[
  {
    "path": ".gitattributes",
    "content": "*.js linguist-language=python\n*.css linguist-language=python\n*.html linguist-language=python\n"
  },
  {
    "path": "CloudCreat",
    "content": "# coding: utf-8\n\nfrom wordcloud import WordCloud\nimport cv2\nimport jieba\nimport matplotlib.pyplot as plt\n\nwith open('test.txt', 'r') as f:\n    text = f.read()\n\ncut_text = \" \".join(jieba.cut(text))\n\ncolor_mask = cv2.imread('back.jpeg')\n\ncloud = WordCloud(\n    # 设置字体，不指定就会出现乱码\n    font_path=\"/Users/caichenyang/Desktop/爬虫尝试/Baoli.ttc\",\n    # font_path=path.join(d,'simsun.ttc'),\n    # 设置背景色\n    background_color='white',\n    # 词云形状\n    mask=color_mask,\n    # 允许最大词汇\n    max_words=120,\n    # 最大号字体\n    max_font_size=2000\n)\n\nwCloud = cloud.generate(cut_text)\nwCloud.to_file('cloud.jpg')\nplt.imshow(wCloud, interpolation='bilinear')\nplt.axis('off')\nplt.show()\n\n"
  },
  {
    "path": "GaoKao_Score/2006-2016浙江高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"a6e1a4ccc0684063a80db155d6ce9db7\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_a6e1a4ccc0684063a80db155d6ce9db7 = echarts.init(\n            document.getElementById('a6e1a4ccc0684063a80db155d6ce9db7'), 'white', {renderer: 'canvas'});\n        var option_a6e1a4ccc0684063a80db155d6ce9db7 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                603,\n                626,\n                621,\n                619,\n                606,\n                571,\n                590,\n                606,\n                550,\n                553,\n                583\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                600,\n                605,\n                597,\n                617,\n                593,\n                550,\n                551,\n                605,\n                550,\n                568,\n                570\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t-\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t-\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t-\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t-\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t-\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t-\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t459\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t478\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t516\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t523\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t550\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t-\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t-\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t-\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t-\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t-\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t-\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t402\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t429\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t504\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t523\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t527\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t2016\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2015\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2014\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2013\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2012\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2011\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2010\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2009\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2008\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2007\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2006\\n\\t\\t\\t\\t\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"2006-2016\\u6d59\\u6c5f\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\"\n        }\n    ]\n};\n        chart_a6e1a4ccc0684063a80db155d6ce9db7.setOption(option_a6e1a4ccc0684063a80db155d6ce9db7);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2016海南高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"d46411e52a1f41e4aa73bf14d5e2d047\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_d46411e52a1f41e4aa73bf14d5e2d047 = echarts.init(\n            document.getElementById('d46411e52a1f41e4aa73bf14d5e2d047'), 'white', {renderer: 'canvas'});\n        var option_d46411e52a1f41e4aa73bf14d5e2d047 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                662,\n                666,\n                667,\n                668,\n                671,\n                670,\n                670\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                608,\n                606,\n                608,\n                614,\n                615,\n                624,\n                632\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t588\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t590\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t590\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t591\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t595\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t600\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t600\\n\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t546\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t542\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t541\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t545\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t548\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t563\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t573\\n\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n\\t\\t\\t\\t2015\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t2014\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t2013\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t2012\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t2011\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t2010\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t2009\\n\\t\\t\\t\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"2006-2016\\u6d77\\u5357\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b)\"\n        }\n    ]\n};\n        chart_d46411e52a1f41e4aa73bf14d5e2d047.setOption(option_d46411e52a1f41e4aa73bf14d5e2d047);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2017上海高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"430d7b707dee457089d1addddc0ff579\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_430d7b707dee457089d1addddc0ff579 = echarts.init(\n            document.getElementById('430d7b707dee457089d1addddc0ff579'), 'white', {renderer: 'canvas'});\n        var option_430d7b707dee457089d1addddc0ff579 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                434,\n                444,\n                448,\n                438,\n                468,\n                464,\n                471,\n                471,\n                465,\n                490\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                414,\n                423,\n                405,\n                423,\n                462,\n                465,\n                455,\n                467,\n                461,\n                466\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t372\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t390\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t403\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t397\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t412\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t404\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t429\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t428\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t424\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t450\\n\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t348\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t351\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t331\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t342\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t393\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t400\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t389\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t399\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t394\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t412\\n\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2017\\u4e0a\\u6d77\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_430d7b707dee457089d1addddc0ff579.setOption(option_430d7b707dee457089d1addddc0ff579);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2017安徽高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"d5d8c2ded9844687a2355989f6478108\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_d5d8c2ded9844687a2355989f6478108 = echarts.init(\n            document.getElementById('d5d8c2ded9844687a2355989f6478108'), 'white', {renderer: 'canvas'});\n        var option_d5d8c2ded9844687a2355989f6478108 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                550,\n                515,\n                521,\n                597,\n                541,\n                540,\n                577,\n                547,\n                573,\n                543,\n                553,\n                551,\n                573\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                505,\n                487,\n                518,\n                555,\n                489,\n                490,\n                534,\n                570,\n                562,\n                579,\n                563,\n                563,\n                566\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t486\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t440\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t482\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t558\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t500\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t498\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t541\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t510\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t534\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t501\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t513\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t515\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t523\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t432\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t413\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t473\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t511\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t438\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t429\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t477\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t520\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t507\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t520\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t507\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t505\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t504\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2017\\u5b89\\u5fbd\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_d5d8c2ded9844687a2355989f6478108.setOption(option_d5d8c2ded9844687a2355989f6478108);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2017山东高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"7913122e8a2d433cab02b0f2689758ec\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_7913122e8a2d433cab02b0f2689758ec = echarts.init(\n            document.getElementById('7913122e8a2d433cab02b0f2689758ec'), 'white', {renderer: 'canvas'});\n        var option_7913122e8a2d433cab02b0f2689758ec = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                483,\n                530,\n                568,\n                579,\n                570,\n                573,\n                570,\n                606,\n                596,\n                584,\n                593,\n                568\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                433,\n                537,\n                562,\n                572,\n                554,\n                582,\n                567,\n                580,\n                586,\n                582,\n                573,\n                583\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t2017\\u5e74\\u8d77\\u672c\\u79d1\\u4e0d\\u5206\\u6279\\u6b21\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t474\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t510\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t554\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t465\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t516\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t512\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t578\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t575\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t566\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t577\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t549\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\u67e5\\u770b\\u8be6\\u60c5\\n\\n\",\n                \"\\n\\t\\t\\t\\t\\t451\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t490\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t547\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t435\\u00a0\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t515\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t503\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t542\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t554\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t556\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t545\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t553\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2017\\u5c71\\u4e1c\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_7913122e8a2d433cab02b0f2689758ec.setOption(option_7913122e8a2d433cab02b0f2689758ec);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2017山西高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"5320919801744e71a61d5784b3299df3\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_5320919801744e71a61d5784b3299df3 = echarts.init(\n            document.getElementById('5320919801744e71a61d5784b3299df3'), 'white', {renderer: 'canvas'});\n        var option_5320919801744e71a61d5784b3299df3 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                518,\n                518,\n                513,\n                526,\n                507,\n                539,\n                543,\n                533,\n                548,\n                545,\n                580,\n                561\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                481,\n                519,\n                515,\n                534,\n                493,\n                530,\n                570,\n                536,\n                547,\n                546,\n                572,\n                552\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t452\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t460\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t462\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t478\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t459\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t492\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t496\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t492\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t507\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t510\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t553\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t528\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t400\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t438\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t442\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t462\\u00a0\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t440\\u00a0\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t476\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t520\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t491\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t505\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t511\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t439\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t515\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2017\\u5c71\\u897f\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_5320919801744e71a61d5784b3299df3.setOption(option_5320919801744e71a61d5784b3299df3);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2017新疆高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"fec56a65ff624daba39a0e2fce63d6ef\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_fec56a65ff624daba39a0e2fce63d6ef = echarts.init(\n            document.getElementById('fec56a65ff624daba39a0e2fce63d6ef'), 'white', {renderer: 'canvas'});\n        var option_fec56a65ff624daba39a0e2fce63d6ef = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                486,\n                487,\n                486,\n                516,\n                460,\n                493,\n                504,\n                485,\n                499,\n                525,\n                520,\n                517\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                437,\n                464,\n                446,\n                475,\n                443,\n                445,\n                473,\n                471,\n                521,\n                558,\n                562,\n                566\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t375\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t415\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t414\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t446\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t394\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t426\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t433\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t433\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t445\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t467\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t457\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t452\\n\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t333\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t394\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t381\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t405\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t378\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t390\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t407\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t415\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t470\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t507\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t516\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t512\\n\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2017\\u65b0\\u7586\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_fec56a65ff624daba39a0e2fce63d6ef.setOption(option_fec56a65ff624daba39a0e2fce63d6ef);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2017河南高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"7f490b7729d2483eb46330e070b68ea9\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_7f490b7729d2483eb46330e070b68ea9 = echarts.init(\n            document.getElementById('7f490b7729d2483eb46330e070b68ea9'), 'white', {renderer: 'canvas'});\n        var option_7f490b7729d2483eb46330e070b68ea9 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                517,\n                513,\n                536,\n                519,\n                557,\n                562,\n                532,\n                552,\n                557,\n                589,\n                591\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                523,\n                529,\n                547,\n                505,\n                540,\n                582,\n                552,\n                567,\n                563,\n                596,\n                590\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t458\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t455\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t483\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t465\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t509\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t515\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t489\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t510\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t513\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t552\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t547\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t447\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t458\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t476\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t443\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t481\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t531\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t500\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t520\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t517\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t553\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t548\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2017\\u6cb3\\u5357\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_7f490b7729d2483eb46330e070b68ea9.setOption(option_7f490b7729d2483eb46330e070b68ea9);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2017福建高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"6a877e236f3346e89681046d01987691\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_6a877e236f3346e89681046d01987691 = echarts.init(\n            document.getElementById('6a877e236f3346e89681046d01987691'), 'white', {renderer: 'canvas'});\n        var option_6a877e236f3346e89681046d01987691 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                489,\n                501,\n                547,\n                561,\n                513,\n                557,\n                564,\n                557,\n                582,\n                547,\n                565,\n                574\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                441,\n                465,\n                525,\n                506,\n                501,\n                546,\n                573,\n                539,\n                569,\n                534,\n                562,\n                561\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t380\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t403\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t462\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t482\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t431\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t466\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t473\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t494\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t518\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t487\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t505\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t514\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t333\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t352\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t410\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t408\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t401\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t435\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t460\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t472\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t500\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t471\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t495\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t490\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2017\\u798f\\u5efa\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_6a877e236f3346e89681046d01987691.setOption(option_6a877e236f3346e89681046d01987691);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2017重庆高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"826d7f0f17b947828e227285a0f99adf\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_826d7f0f17b947828e227285a0f99adf = echarts.init(\n            document.getElementById('826d7f0f17b947828e227285a0f99adf'), 'white', {renderer: 'canvas'});\n        var option_826d7f0f17b947828e227285a0f99adf = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                525,\n                527,\n                572,\n                555,\n                556,\n                554,\n                564,\n                573,\n                546,\n                576,\n                540,\n                556\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                492,\n                525,\n                573,\n                514,\n                520,\n                522,\n                533,\n                533,\n                557,\n                544,\n                505,\n                531\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t436\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t435\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t532\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t507\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t499\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t494\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t504\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t510\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t480\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t510\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t476\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t486\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t395\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t416\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t527\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t455\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t462\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t462\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t479\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t478\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t502\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t488\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t450\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t476\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2017\\u91cd\\u5e86\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_826d7f0f17b947828e227285a0f99adf.setOption(option_826d7f0f17b947828e227285a0f99adf);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2017黑龙江高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"80262ba6cbd24451a7b4948b87c3dd10\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_80262ba6cbd24451a7b4948b87c3dd10 = echarts.init(\n            document.getElementById('80262ba6cbd24451a7b4948b87c3dd10'), 'white', {renderer: 'canvas'});\n        var option_80262ba6cbd24451a7b4948b87c3dd10 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                481,\n                481,\n                495,\n                541,\n                504,\n                526,\n                500,\n                523,\n                531,\n                569,\n                567,\n                557\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                455,\n                486,\n                483,\n                529,\n                527,\n                514,\n                486,\n                532,\n                538,\n                577,\n                588,\n                578\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t400\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t401\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t410\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t454\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t424\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t449\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t463\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t450\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t467\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t504\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t499\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t492\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t335\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t369\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t371\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t414\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t437\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t425\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t444\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t448\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t464\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t508\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t526\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t516\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2017\\u9ed1\\u9f99\\u6c5f\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\n\"\n        }\n    ]\n};\n        chart_80262ba6cbd24451a7b4948b87c3dd10.setOption(option_80262ba6cbd24451a7b4948b87c3dd10);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018云南高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"e86a5cd984c047b7afddb7e7236731ed\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_e86a5cd984c047b7afddb7e7236731ed = echarts.init(\n            document.getElementById('e86a5cd984c047b7afddb7e7236731ed'), 'white', {renderer: 'canvas'});\n        var option_e86a5cd984c047b7afddb7e7236731ed = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                575,\n                555,\n                560,\n                540,\n                565,\n                520,\n                520,\n                495,\n                495,\n                520,\n                550,\n                575,\n                550\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                530,\n                500,\n                525,\n                550,\n                525,\n                495,\n                465,\n                465,\n                500,\n                500,\n                530,\n                560,\n                550\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t490\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t465\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t495\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t470\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t500\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t455\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t460\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t445\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t450\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t478\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t510\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t530\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t505\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t430\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t410\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t445\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t425\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t445\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t425\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t395\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t380\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t430\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t442\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t475\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t500\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t485\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u4e91\\u5357\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_e86a5cd984c047b7afddb7e7236731ed.setOption(option_e86a5cd984c047b7afddb7e7236731ed);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018内蒙古高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"52b6a1dd2bbc463bb3bcaa7f85d4331d\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_52b6a1dd2bbc463bb3bcaa7f85d4331d = echarts.init(\n            document.getElementById('52b6a1dd2bbc463bb3bcaa7f85d4331d'), 'white', {renderer: 'canvas'});\n        var option_52b6a1dd2bbc463bb3bcaa7f85d4331d = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                501,\n                472,\n                474,\n                487,\n                525,\n                474,\n                492,\n                486,\n                475,\n                497,\n                543,\n                559,\n                530\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                478,\n                466,\n                484,\n                464,\n                501,\n                482,\n                469,\n                480,\n                510,\n                501,\n                548,\n                559,\n                557\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t399\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t375\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t375\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t385\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t455\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t409\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t429\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t430\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t423\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t452\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t502\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t515\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t481\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t336\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t328\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t346\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t336\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t388\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t399\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t390\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t409\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t442\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t444\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t497\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t511\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t495\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u5185\\u8499\\u53e4\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_52b6a1dd2bbc463bb3bcaa7f85d4331d.setOption(option_52b6a1dd2bbc463bb3bcaa7f85d4331d);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018北京高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"620764f0f0d241e281db63e3a4d02b75\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_620764f0f0d241e281db63e3a4d02b75 = echarts.init(\n            document.getElementById('620764f0f0d241e281db63e3a4d02b75'), 'white', {renderer: 'canvas'});\n        var option_620764f0f0d241e281db63e3a4d02b75 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                576,\n                555,\n                583,\n                579,\n                565,\n                549,\n                495,\n                524,\n                524,\n                532,\n                515,\n                528,\n                516\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                532,\n                537,\n                548,\n                548,\n                543,\n                550,\n                477,\n                484,\n                494,\n                501,\n                502,\n                531,\n                528\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t488\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t468\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t532\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t527\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t507\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t494\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t446\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t481\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t474\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t489\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t472\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t486\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t476\\n\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t432\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t439\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t494\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t495\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t495\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t505\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t433\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t435\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t441\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t459\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t455\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t478\\n\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t476\\n\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u5317\\u4eac\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_620764f0f0d241e281db63e3a4d02b75.setOption(option_620764f0f0d241e281db63e3a4d02b75);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018吉林高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"264a6b5f85a446f7aa39e9af0dffd2a8\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_264a6b5f85a446f7aa39e9af0dffd2a8 = echarts.init(\n            document.getElementById('264a6b5f85a446f7aa39e9af0dffd2a8'), 'white', {renderer: 'canvas'});\n        var option_264a6b5f85a446f7aa39e9af0dffd2a8 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                542,\n                528,\n                531,\n                543,\n                560,\n                510,\n                529,\n                537,\n                517,\n                530,\n                565,\n                567,\n                550\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                533,\n                507,\n                530,\n                525,\n                555,\n                535,\n                515,\n                548,\n                530,\n                539,\n                569,\n                574,\n                570\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t432\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t412\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t413\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t433\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t459\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t401\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t435\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t437\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t425\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t466\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t497\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t487\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t480\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t405\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t379\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t402\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t405\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t445\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t421\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t412\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t443\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t427\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t466\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t493\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t487\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t480\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u5409\\u6797\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_264a6b5f85a446f7aa39e9af0dffd2a8.setOption(option_264a6b5f85a446f7aa39e9af0dffd2a8);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018四川高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"bbc6a1ebdf2b4c7380d5439d4842d0e7\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_bbc6a1ebdf2b4c7380d5439d4842d0e7 = echarts.init(\n            document.getElementById('bbc6a1ebdf2b4c7380d5439d4842d0e7'), 'white', {renderer: 'canvas'});\n        var option_bbc6a1ebdf2b4c7380d5439d4842d0e7 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                502,\n                537,\n                540,\n                543,\n                551,\n                567,\n                516,\n                533,\n                543,\n                540,\n                598,\n                559,\n                550\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                483,\n                511,\n                532,\n                528,\n                540,\n                562,\n                518,\n                519,\n                512,\n                498,\n                593,\n                533,\n                560\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t456\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t470\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t480\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t473\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t500\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t505\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t454\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t473\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t483\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t480\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t548\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t510\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t502\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t436\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t436\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t453\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t445\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t475\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t492\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t445\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t448\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t441\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t436\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t534\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t474\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t512\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u56db\\u5ddd\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_bbc6a1ebdf2b4c7380d5439d4842d0e7.setOption(option_bbc6a1ebdf2b4c7380d5439d4842d0e7);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018天津高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"6b19855df39c4a01ba59ea0e0334711b\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_6b19855df39c4a01ba59ea0e0334711b = echarts.init(\n            document.getElementById('6b19855df39c4a01ba59ea0e0334711b'), 'white', {renderer: 'canvas'});\n        var option_6b19855df39c4a01ba59ea0e0334711b = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                436,\n                531,\n                512,\n                547,\n                523,\n                533,\n                549,\n                519,\n                519,\n                511,\n                523,\n                513,\n                477\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                407,\n                521,\n                532,\n                538,\n                516,\n                521,\n                530,\n                515,\n                509,\n                502,\n                522,\n                509,\n                505\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\n\",\n                \"\\n\\t\\t\\t\\t\\t401\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t460\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t486\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t462\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t474\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t440\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t460\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t466\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t422\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t483\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t473\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t436\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\n\",\n                \"\\n\\t\\t\\t\\t\\t395\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t424\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t459\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t439\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t436\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t489\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t429\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t445\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t435\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t466\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t453\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t455\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u5929\\u6d25\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_6b19855df39c4a01ba59ea0e0334711b.setOption(option_6b19855df39c4a01ba59ea0e0334711b);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018宁夏高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"9617da4342da4ec9a3174ae820d2e5b7\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_9617da4342da4ec9a3174ae820d2e5b7 = echarts.init(\n            document.getElementById('9617da4342da4ec9a3174ae820d2e5b7'), 'white', {renderer: 'canvas'});\n        var option_9617da4342da4ec9a3174ae820d2e5b7 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                528,\n                519,\n                516,\n                507,\n                517,\n                487,\n                489,\n                500,\n                496,\n                501,\n                532,\n                548,\n                516\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                463,\n                439,\n                465,\n                445,\n                473,\n                455,\n                440,\n                486,\n                474,\n                468,\n                498,\n                531,\n                514\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t498\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t487\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t486\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t478\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t486\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t450\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t453\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t463\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t464\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t467\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t488\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t503\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t471\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t432\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t408\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t434\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t416\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t440\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t417\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t401\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t444\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t436\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t428\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t457\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t493\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t469\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u5b81\\u590f\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_9617da4342da4ec9a3174ae820d2e5b7.setOption(option_9617da4342da4ec9a3174ae820d2e5b7);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018广东高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"29d2b28b06a24d46833aa261ca7d6940\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_29d2b28b06a24d46833aa261ca7d6940 = echarts.init(\n            document.getElementById('29d2b28b06a24d46833aa261ca7d6940'), 'white', {renderer: 'canvas'});\n        var option_29d2b28b06a24d46833aa261ca7d6940 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                443,\n                520,\n                514,\n                573,\n                579,\n                594,\n                589,\n                580,\n                595,\n                587,\n                570,\n                591\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                376,\n                485,\n                508,\n                577,\n                560,\n                574,\n                585,\n                568,\n                621,\n                585,\n                564,\n                557\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t215\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t418\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t417\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA524\\uff1bB474\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA534\\uff1bB483\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA546 \\uff1bB498\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA545 \\uff1bB502\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA536 \\uff1bB489\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA554 \\uff1bB518\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA540 \\uff1bB507\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA524 \\uff1bB494\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA551 \\uff1bB528\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t205\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t360\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t402\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA519 \\uff1bB483\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA504\\uff1bB465\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA516\\uff1bB480\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA523\\uff1bB484\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA504\\uff1bB460\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA567\\uff1bB527\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA530\\uff1bB507\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA510\\uff1bB488\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\tA502\\uff1bB480\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u5e7f\\u4e1c\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_29d2b28b06a24d46833aa261ca7d6940.setOption(option_29d2b28b06a24d46833aa261ca7d6940);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018广西高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"180dc75d34474c4a98eef13771d89400\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_180dc75d34474c4a98eef13771d89400 = echarts.init(\n            document.getElementById('180dc75d34474c4a98eef13771d89400'), 'white', {renderer: 'canvas'});\n        var option_180dc75d34474c4a98eef13771d89400 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                547,\n                535,\n                545,\n                530,\n                550,\n                541,\n                544,\n                519,\n                510,\n                523,\n                528,\n                574,\n                558\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                513,\n                473,\n                502,\n                480,\n                520,\n                510,\n                528,\n                506,\n                500,\n                507,\n                501,\n                545,\n                538\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t403\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t387\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t400\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t380\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t463\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t467\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t473\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t456\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t453\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t467\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t470\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t522\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t500\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t345\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t318\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t333\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t320\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t407\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t413\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t444\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t424\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t433\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t443\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t440\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t481\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t473\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t2018\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2017\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2016\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2015\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2014\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2013\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2012\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2011\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2010\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2009\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2008\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2007\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2006\\n\\t\\t\\t\\t\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u5e7f\\u897f\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_180dc75d34474c4a98eef13771d89400.setOption(option_180dc75d34474c4a98eef13771d89400);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018江西高考分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"6539b2b573194497994801a8b77cb200\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_6539b2b573194497994801a8b77cb200 = echarts.init(\n            document.getElementById('6539b2b573194497994801a8b77cb200'), 'white', {renderer: 'canvas'});\n        var option_6539b2b573194497994801a8b77cb200 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                568,\n                535,\n                523,\n                528,\n                524,\n                532,\n                570,\n                547,\n                521,\n                515,\n                520,\n                573,\n                563\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                527,\n                473,\n                529,\n                540,\n                526,\n                517,\n                547,\n                570,\n                515,\n                518,\n                512,\n                571,\n                550\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t496\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t387\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t450\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t487\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t479\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t484\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t523\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t510\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t479\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t482\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t487\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t538\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t520\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t447\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t318\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t445\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t490\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t471\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t456\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t486\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t520\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t462\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t466\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t461\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t521\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t496\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t2018\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2017\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2016\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2015\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2014\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2013\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2012\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2011\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2010\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2009\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2008\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2007\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2006\\n\\t\\t\\t\\t\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u6c5f\\u897f\\u9ad8\\u8003\\u5206\\u6570\\u7ebf\\n\"\n        }\n    ]\n};\n        chart_6539b2b573194497994801a8b77cb200.setOption(option_6539b2b573194497994801a8b77cb200);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018河北高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"81454775c8884bf6ace858e3bd2304fd\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_81454775c8884bf6ace858e3bd2304fd = echarts.init(\n            document.getElementById('81454775c8884bf6ace858e3bd2304fd'), 'white', {renderer: 'canvas'});\n        var option_81454775c8884bf6ace858e3bd2304fd = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                559,\n                517,\n                535,\n                548,\n                563,\n                561,\n                572,\n                564,\n                539,\n                539,\n                537,\n                566,\n                561\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                511,\n                485,\n                525,\n                544,\n                573,\n                538,\n                564,\n                533,\n                561,\n                569,\n                552,\n                587,\n                577\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t441\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t395\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t416\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t496\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t513\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t511\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t529\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t504\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t504\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t502\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t503\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t538\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t530\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t358\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t326\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t364\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t474\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t503\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t478\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t509\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t479\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t518\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t524\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t514\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t549\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t540\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u6cb3\\u5317\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_81454775c8884bf6ace858e3bd2304fd.setOption(option_81454775c8884bf6ace858e3bd2304fd);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018湖北高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"390ad1f5c9dc4786be341d8e77f1fe51\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_390ad1f5c9dc4786be341d8e77f1fe51 = echarts.init(\n            document.getElementById('390ad1f5c9dc4786be341d8e77f1fe51'), 'white', {renderer: 'canvas'});\n        var option_390ad1f5c9dc4786be341d8e77f1fe51 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                561,\n                528,\n                520,\n                521,\n                535,\n                531,\n                561,\n                547,\n                530,\n                518,\n                532,\n                525,\n                545\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                512,\n                484,\n                512,\n                510,\n                539,\n                527,\n                551,\n                571,\n                557,\n                540,\n                548,\n                548,\n                546\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t441\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t406\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t403\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t477\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t495\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t480\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t515\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t507\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t488\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t491\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t508\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t500\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t519\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t375\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t345\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t350\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t448\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t480\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t462\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t494\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t517\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t506\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t506\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t516\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t517\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t516\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t2018\\n\\t\\t\\t\\t\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u6e56\\u5317\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_390ad1f5c9dc4786be341d8e77f1fe51.setOption(option_390ad1f5c9dc4786be341d8e77f1fe51);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018湖南高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"609e6a2807f84e33bb2a8bac3f6cd303\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_609e6a2807f84e33bb2a8bac3f6cd303 = echarts.init(\n            document.getElementById('609e6a2807f84e33bb2a8bac3f6cd303'), 'white', {renderer: 'canvas'});\n        var option_609e6a2807f84e33bb2a8bac3f6cd303 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                569,\n                548,\n                530,\n                535,\n                562,\n                557,\n                571,\n                583,\n                578,\n                554,\n                581,\n                562,\n                593\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                513,\n                505,\n                517,\n                526,\n                522,\n                495,\n                520,\n                572,\n                567,\n                534,\n                536,\n                535,\n                547\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t526\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t485\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t476\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t481\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t501\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t502\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t523\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t528\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t523\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t507\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t537\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t526\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t556\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t450\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t424\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t439\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t455\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t442\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t423\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t451\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t492\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t494\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t471\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t482\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t487\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t496\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u6e56\\u5357\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_609e6a2807f84e33bb2a8bac3f6cd303.setOption(option_609e6a2807f84e33bb2a8bac3f6cd303);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018甘肃高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"6151782ea6354e9ca035dfc1f58fc84b\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_6151782ea6354e9ca035dfc1f58fc84b = echarts.init(\n            document.getElementById('6151782ea6354e9ca035dfc1f58fc84b'), 'white', {renderer: 'canvas'});\n        var option_6151782ea6354e9ca035dfc1f58fc84b = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                502,\n                505,\n                504,\n                517,\n                543,\n                503,\n                533,\n                504,\n                511,\n                516,\n                560,\n                564,\n                542\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                483,\n                460,\n                490,\n                475,\n                516,\n                489,\n                517,\n                501,\n                531,\n                521,\n                558,\n                562,\n                566\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t456\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t458\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t455\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t465\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t499\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t451\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t485\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t458\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t467\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t466\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t501\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t503\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t483\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t436\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t408\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t435\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t417\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t459\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t430\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t462\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t448\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t481\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t470\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t507\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t516\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t512\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u7518\\u8083\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_6151782ea6354e9ca035dfc1f58fc84b.setOption(option_6151782ea6354e9ca035dfc1f58fc84b);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018西藏高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"325fb8fbfc0441bb8c84e825106fe15d\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_325fb8fbfc0441bb8c84e825106fe15d = echarts.init(\n            document.getElementById('325fb8fbfc0441bb8c84e825106fe15d'), 'white', {renderer: 'canvas'});\n        var option_325fb8fbfc0441bb8c84e825106fe15d = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                460,\n                441,\n                440,\n                440,\n                500,\n                480,\n                490,\n                485,\n                455,\n                450,\n                500,\n                515,\n                495\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                445,\n                426,\n                425,\n                420,\n                460,\n                470,\n                460,\n                450,\n                455,\n                450,\n                500,\n                515,\n                505\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t355\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t356\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t355\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t355\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t355\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t335\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t345\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t350\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t315\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t315\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t360\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t370\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t352\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t335\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t316\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t235\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t315\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t310\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t315\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t325\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t315\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t315\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t315\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t365\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t370\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t370\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u897f\\u85cf\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_325fb8fbfc0441bb8c84e825106fe15d.setOption(option_325fb8fbfc0441bb8c84e825106fe15d);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018贵州高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"a0ab08eb35f04bb3abaa667db441f7e8\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_a0ab08eb35f04bb3abaa667db441f7e8 = echarts.init(\n            document.getElementById('a0ab08eb35f04bb3abaa667db441f7e8'), 'white', {renderer: 'canvas'});\n        var option_a0ab08eb35f04bb3abaa667db441f7e8 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                575,\n                545,\n                551,\n                543,\n                569,\n                522,\n                539,\n                516,\n                514,\n                532,\n                566,\n                567,\n                528\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                484,\n                456,\n                473,\n                453,\n                484,\n                449,\n                470,\n                448,\n                481,\n                477,\n                521,\n                536,\n                523\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t477\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t453\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t457\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t472\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t489\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t446\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t461\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t446\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t448\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t471\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t503\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t496\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t463\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t379\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t361\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t365\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t372\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t382\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t360\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t390\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t376\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t415\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t422\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t468\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t487\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t464\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u8d35\\u5dde\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_a0ab08eb35f04bb3abaa667db441f7e8.setOption(option_a0ab08eb35f04bb3abaa667db441f7e8);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018辽宁高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"f2c33f553b3649a1a26db96feee50f08\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_f2c33f553b3649a1a26db96feee50f08 = echarts.init(\n            document.getElementById('f2c33f553b3649a1a26db96feee50f08'), 'white', {renderer: 'canvas'});\n        var option_f2c33f553b3649a1a26db96feee50f08 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                532,\n                525,\n                530,\n                552,\n                554,\n                563,\n                535,\n                531,\n                559,\n                538,\n                538,\n                538\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                480,\n                498,\n                500,\n                526,\n                538,\n                517,\n                520,\n                518,\n                520,\n                515,\n                519,\n                503\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t428\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t417\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t460\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t490\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t499\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t506\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t475\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t465\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t495\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t470\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t472\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t469\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t350\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t373\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t419\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t450\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t470\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t445\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t452\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t442\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t439\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t433\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t433\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t430\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u8fbd\\u5b81\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_f2c33f553b3649a1a26db96feee50f08.setOption(option_f2c33f553b3649a1a26db96feee50f08);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018陕西高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"428e540814f44897a4ec031802e42583\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_428e540814f44897a4ec031802e42583 = echarts.init(\n            document.getElementById('428e540814f44897a4ec031802e42583'), 'white', {renderer: 'canvas'});\n        var option_428e540814f44897a4ec031802e42583 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                518,\n                509,\n                511,\n                510,\n                548,\n                540,\n                556,\n                543,\n                559,\n                540,\n                557,\n                567,\n                560\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                474,\n                449,\n                470,\n                480,\n                503,\n                485,\n                517,\n                540,\n                556,\n                537,\n                527,\n                527,\n                545\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t469\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t457\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t460\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t467\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t492\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t486\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t497\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t595\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t500\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t495\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t520\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t530\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t520\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t425\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t397\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t423\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t440\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t452\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t435\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t461\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t488\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t500\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t495\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t490\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t490\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t505\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t2018\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2017\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2016\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2015\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2014\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2013\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2012\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2011\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2010\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2009\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2008\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2007\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t2006\\n\\t\\t\\t\\t\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u9655\\u897f\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\n\"\n        }\n    ]\n};\n        chart_428e540814f44897a4ec031802e42583.setOption(option_428e540814f44897a4ec031802e42583);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2006-2018青海高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"2964b1b8b4c84b5b8bef65431c71d688\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_2964b1b8b4c84b5b8bef65431c71d688 = echarts.init(\n            document.getElementById('2964b1b8b4c84b5b8bef65431c71d688'), 'white', {renderer: 'canvas'});\n        var option_2964b1b8b4c84b5b8bef65431c71d688 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                475,\n                463,\n                457,\n                466,\n                473,\n                435,\n                433,\n                430,\n                430,\n                443,\n                490,\n                495,\n                452\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                403,\n                391,\n                416,\n                400,\n                406,\n                383,\n                401,\n                380,\n                405,\n                400,\n                438,\n                467,\n                434\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t424\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t421\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t415\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t420\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t426\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t382\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t372\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t380\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t386\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t405\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t425\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t418\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t386\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t365\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t356\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t380\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t363\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t362\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t340\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t355\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t331\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t363\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t365\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t388\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t405\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t374\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n\\t\\t\\t\\t\\t2018\\n\",\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\",\n                \"\\n2009\\n\",\n                \"\\n2008\\n\",\n                \"\\n2007\\n\",\n                \"\\n2006\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2006-2018\\u9752\\u6d77\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_2964b1b8b4c84b5b8bef65431c71d688.setOption(option_2964b1b8b4c84b5b8bef65431c71d688);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/2010-2017江苏高考录取分数线.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"591a80001c6b41eabd6b22a006e24ada\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_591a80001c6b41eabd6b22a006e24ada = echarts.init(\n            document.getElementById('591a80001c6b41eabd6b22a006e24ada'), 'white', {renderer: 'canvas'});\n        var option_591a80001c6b41eabd6b22a006e24ada = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                333,\n                355,\n                342,\n                333,\n                328,\n                341,\n                343,\n                345\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n            \"data\": [\n                331,\n                353,\n                344,\n                345,\n                338,\n                340,\n                343,\n                355\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n281\\n\",\n                \"\\n\\t\\t\\t\\t\\t325\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t313\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t301\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t299\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t311\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t319\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t321\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"bar\",\n            \"name\": \"\\u7406\\u79d1(\\u4e8c\\u672c)\",\n            \"data\": [\n                \"\\n269\\n\",\n                \"\\n\\t\\t\\t\\t\\t315\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t310\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t312\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t312\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t312\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t320\\n\\t\\t\\t\\t\",\n                \"\\n\\t\\t\\t\\t\\t328\\n\\t\\t\\t\\t\"\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\",\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\",\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\"\n            ],\n            \"selected\": {\n                \"\\u6587\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e00\\u672c)\": true,\n                \"\\u6587\\u79d1(\\u4e8c\\u672c)\": true,\n                \"\\u7406\\u79d1(\\u4e8c\\u672c)\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\n2017\\n\",\n                \"\\n2016\\n\",\n                \"\\n2015\\n\",\n                \"\\n2014\\n\",\n                \"\\n2013\\n\",\n                \"\\n2012\\n\",\n                \"\\n2011\\n\",\n                \"\\n2010\\n\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\n2010-2017\\u6c5f\\u82cf\\u9ad8\\u8003\\u5f55\\u53d6\\u5206\\u6570\\u7ebf\\uff08\\u6c47\\u603b\\uff09\\n\"\n        }\n    ]\n};\n        chart_591a80001c6b41eabd6b22a006e24ada.setOption(option_591a80001c6b41eabd6b22a006e24ada);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/文科(一本)全国高考录取分数平均值比较.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"60273eeaa5b04f638676ac2b512512f8\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_60273eeaa5b04f638676ac2b512512f8 = echarts.init(\n            document.getElementById('60273eeaa5b04f638676ac2b512512f8'), 'white', {renderer: 'canvas'});\n        var option_60273eeaa5b04f638676ac2b512512f8 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"data\": [\n                541.62,\n                568.33,\n                550.85,\n                514.85,\n                340.0,\n                539.15,\n                541.25,\n                523.38,\n                552.38,\n                563.31,\n                534.92,\n                553.67,\n                544.54,\n                546.42,\n                457.08,\n                522.92,\n                539.92,\n                539.85,\n                538.77,\n                667.71,\n                593.45,\n                501.15,\n                473.15,\n                535.92,\n                547.73,\n                459.3,\n                561.25,\n                543.62,\n                540.0,\n                512.0,\n                498.17\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"line\",\n            \"connectNulls\": false,\n            \"symbolSize\": 4,\n            \"showSymbol\": true,\n            \"smooth\": false,\n            \"step\": false,\n            \"data\": [\n                [\n                    \"\\u5317\\u4eac\",\n                    541.62\n                ],\n                [\n                    \"\\u5c71\\u4e1c\",\n                    568.33\n                ],\n                [\n                    \"\\u6cb3\\u5317\",\n                    550.85\n                ],\n                [\n                    \"\\u5929\\u6d25\",\n                    514.85\n                ],\n                [\n                    \"\\u6c5f\\u82cf\",\n                    340.0\n                ],\n                [\n                    \"\\u5409\\u6797\",\n                    539.15\n                ],\n                [\n                    \"\\u8fbd\\u5b81\",\n                    541.25\n                ],\n                [\n                    \"\\u7518\\u8083\",\n                    523.38\n                ],\n                [\n                    \"\\u5b89\\u5fbd\",\n                    552.38\n                ],\n                [\n                    \"\\u6e56\\u5357\",\n                    563.31\n                ],\n                [\n                    \"\\u6e56\\u5317\",\n                    534.92\n                ],\n                [\n                    \"\\u91cd\\u5e86\",\n                    553.67\n                ],\n                [\n                    \"\\u56db\\u5ddd\",\n                    544.54\n                ],\n                [\n                    \"\\u798f\\u5efa\",\n                    546.42\n                ],\n                [\n                    \"\\u9752\\u6d77\",\n                    457.08\n                ],\n                [\n                    \"\\u9ed1\\u9f99\",\n                    522.92\n                ],\n                [\n                    \"\\u6c5f\\u897f\",\n                    539.92\n                ],\n                [\n                    \"\\u9655\\u897f\",\n                    539.85\n                ],\n                [\n                    \"\\u5e7f\\u897f\",\n                    538.77\n                ],\n                [\n                    \"\\u6d77\\u5357\",\n                    667.71\n                ],\n                [\n                    \"\\u6d59\\u6c5f\",\n                    593.45\n                ],\n                [\n                    \"\\u5185\\u8499\",\n                    501.15\n                ],\n                [\n                    \"\\u897f\\u85cf\",\n                    473.15\n                ],\n                [\n                    \"\\u5c71\\u897f\",\n                    535.92\n                ],\n                [\n                    \"\\u6cb3\\u5357\",\n                    547.73\n                ],\n                [\n                    \"\\u4e0a\\u6d77\",\n                    459.3\n                ],\n                [\n                    \"\\u5e7f\\u4e1c\",\n                    561.25\n                ],\n                [\n                    \"\\u8d35\\u5dde\",\n                    543.62\n                ],\n                [\n                    \"\\u4e91\\u5357\",\n                    540.0\n                ],\n                [\n                    \"\\u5b81\\u590f\",\n                    512.0\n                ],\n                [\n                    \"\\u65b0\\u7586\",\n                    498.17\n                ]\n            ],\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            },\n            \"lineStyle\": {\n                \"width\": 1,\n                \"opacity\": 1,\n                \"curveness\": 0,\n                \"type\": \"solid\"\n            },\n            \"areaStyle\": {\n                \"opacity\": 0\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\",\n                \"\"\n            ],\n            \"selected\": {\n                \"\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"axisLabel\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"rotate\": 60,\n                \"margin\": 8\n            },\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\u5317\\u4eac\",\n                \"\\u5c71\\u4e1c\",\n                \"\\u6cb3\\u5317\",\n                \"\\u5929\\u6d25\",\n                \"\\u6c5f\\u82cf\",\n                \"\\u5409\\u6797\",\n                \"\\u8fbd\\u5b81\",\n                \"\\u7518\\u8083\",\n                \"\\u5b89\\u5fbd\",\n                \"\\u6e56\\u5357\",\n                \"\\u6e56\\u5317\",\n                \"\\u91cd\\u5e86\",\n                \"\\u56db\\u5ddd\",\n                \"\\u798f\\u5efa\",\n                \"\\u9752\\u6d77\",\n                \"\\u9ed1\\u9f99\",\n                \"\\u6c5f\\u897f\",\n                \"\\u9655\\u897f\",\n                \"\\u5e7f\\u897f\",\n                \"\\u6d77\\u5357\",\n                \"\\u6d59\\u6c5f\",\n                \"\\u5185\\u8499\",\n                \"\\u897f\\u85cf\",\n                \"\\u5c71\\u897f\",\n                \"\\u6cb3\\u5357\",\n                \"\\u4e0a\\u6d77\",\n                \"\\u5e7f\\u4e1c\",\n                \"\\u8d35\\u5dde\",\n                \"\\u4e91\\u5357\",\n                \"\\u5b81\\u590f\",\n                \"\\u65b0\\u7586\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\u5168\\u56fd\\u9ad8\\u8003\\u6587\\u79d1(\\u4e00\\u672c)\\u5f55\\u53d6\\u5206\\u6570\\u5e73\\u5747\\u503c\\u6bd4\\u8f83\"\n        }\n    ]\n};\n        chart_60273eeaa5b04f638676ac2b512512f8.setOption(option_60273eeaa5b04f638676ac2b512512f8);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "GaoKao_Score/理科(一本)全国高考录取分数平均值比较.html",
    "content": "<!DOCTYPE html>\n<html>\n<head>\n    <meta charset=\"UTF-8\">\n    <title>Awesome-pyecharts</title>\n            <script type=\"text/javascript\" src=\"https://assets.pyecharts.org/assets/echarts.min.js\"></script>\n\n</head>\n<body>\n    <div id=\"57f5ed82063348159874412766694954\" style=\"width:900px; height:500px;\"></div>\n    <script>\n        var chart_57f5ed82063348159874412766694954 = echarts.init(\n            document.getElementById('57f5ed82063348159874412766694954'), 'white', {renderer: 'canvas'});\n        var option_57f5ed82063348159874412766694954 = {\n    \"color\": [\n        \"#c23531\",\n        \"#2f4554\",\n        \"#61a0a8\",\n        \"#d48265\",\n        \"#749f83\",\n        \"#ca8622\",\n        \"#bda29a\",\n        \"#6e7074\",\n        \"#546570\",\n        \"#c4ccd3\",\n        \"#f05b72\",\n        \"#ef5b9c\",\n        \"#f47920\",\n        \"#905a3d\",\n        \"#fab27b\",\n        \"#2a5caa\",\n        \"#444693\",\n        \"#726930\",\n        \"#b2d235\",\n        \"#6d8346\",\n        \"#ac6767\",\n        \"#1d953f\",\n        \"#6950a1\",\n        \"#918597\"\n    ],\n    \"series\": [\n        {\n            \"type\": \"bar\",\n            \"data\": [\n                521.15,\n                559.25,\n                547.62,\n                509.77,\n                343.62,\n                540.77,\n                512.83,\n                513.0,\n                537.0,\n                529.92,\n                534.23,\n                529.08,\n                529.92,\n                526.83,\n                409.54,\n                524.42,\n                530.38,\n                508.46,\n                509.46,\n                615.29,\n                582.36,\n                499.92,\n                460.08,\n                532.92,\n                554.0,\n                444.1,\n                546.67,\n                481.15,\n                515.0,\n                473.15,\n                488.42\n            ],\n            \"barCategoryGap\": \"20%\",\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            }\n        },\n        {\n            \"type\": \"line\",\n            \"connectNulls\": false,\n            \"symbolSize\": 4,\n            \"showSymbol\": true,\n            \"smooth\": false,\n            \"step\": false,\n            \"data\": [\n                [\n                    \"\\u5317\\u4eac\",\n                    521.15\n                ],\n                [\n                    \"\\u5c71\\u4e1c\",\n                    559.25\n                ],\n                [\n                    \"\\u6cb3\\u5317\",\n                    547.62\n                ],\n                [\n                    \"\\u5929\\u6d25\",\n                    509.77\n                ],\n                [\n                    \"\\u6c5f\\u82cf\",\n                    343.62\n                ],\n                [\n                    \"\\u5409\\u6797\",\n                    540.77\n                ],\n                [\n                    \"\\u8fbd\\u5b81\",\n                    512.83\n                ],\n                [\n                    \"\\u7518\\u8083\",\n                    513.0\n                ],\n                [\n                    \"\\u5b89\\u5fbd\",\n                    537.0\n                ],\n                [\n                    \"\\u6e56\\u5357\",\n                    529.92\n                ],\n                [\n                    \"\\u6e56\\u5317\",\n                    534.23\n                ],\n                [\n                    \"\\u91cd\\u5e86\",\n                    529.08\n                ],\n                [\n                    \"\\u56db\\u5ddd\",\n                    529.92\n                ],\n                [\n                    \"\\u798f\\u5efa\",\n                    526.83\n                ],\n                [\n                    \"\\u9752\\u6d77\",\n                    409.54\n                ],\n                [\n                    \"\\u9ed1\\u9f99\",\n                    524.42\n                ],\n                [\n                    \"\\u6c5f\\u897f\",\n                    530.38\n                ],\n                [\n                    \"\\u9655\\u897f\",\n                    508.46\n                ],\n                [\n                    \"\\u5e7f\\u897f\",\n                    509.46\n                ],\n                [\n                    \"\\u6d77\\u5357\",\n                    615.29\n                ],\n                [\n                    \"\\u6d59\\u6c5f\",\n                    582.36\n                ],\n                [\n                    \"\\u5185\\u8499\",\n                    499.92\n                ],\n                [\n                    \"\\u897f\\u85cf\",\n                    460.08\n                ],\n                [\n                    \"\\u5c71\\u897f\",\n                    532.92\n                ],\n                [\n                    \"\\u6cb3\\u5357\",\n                    554.0\n                ],\n                [\n                    \"\\u4e0a\\u6d77\",\n                    444.1\n                ],\n                [\n                    \"\\u5e7f\\u4e1c\",\n                    546.67\n                ],\n                [\n                    \"\\u8d35\\u5dde\",\n                    481.15\n                ],\n                [\n                    \"\\u4e91\\u5357\",\n                    515.0\n                ],\n                [\n                    \"\\u5b81\\u590f\",\n                    473.15\n                ],\n                [\n                    \"\\u65b0\\u7586\",\n                    488.42\n                ]\n            ],\n            \"label\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"margin\": 8\n            },\n            \"lineStyle\": {\n                \"width\": 1,\n                \"opacity\": 1,\n                \"curveness\": 0,\n                \"type\": \"solid\"\n            },\n            \"areaStyle\": {\n                \"opacity\": 0\n            }\n        }\n    ],\n    \"legend\": [\n        {\n            \"data\": [\n                \"\",\n                \"\"\n            ],\n            \"selected\": {\n                \"\": true\n            },\n            \"show\": true\n        }\n    ],\n    \"tooltip\": {\n        \"show\": true,\n        \"trigger\": \"item\",\n        \"triggerOn\": \"mousemove|click\",\n        \"axisPointer\": {\n            \"type\": \"line\"\n        },\n        \"textStyle\": {\n            \"fontSize\": 14\n        },\n        \"borderWidth\": 0\n    },\n    \"xAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"axisLabel\": {\n                \"show\": true,\n                \"position\": \"top\",\n                \"rotate\": 60,\n                \"margin\": 8\n            },\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            },\n            \"data\": [\n                \"\\u5317\\u4eac\",\n                \"\\u5c71\\u4e1c\",\n                \"\\u6cb3\\u5317\",\n                \"\\u5929\\u6d25\",\n                \"\\u6c5f\\u82cf\",\n                \"\\u5409\\u6797\",\n                \"\\u8fbd\\u5b81\",\n                \"\\u7518\\u8083\",\n                \"\\u5b89\\u5fbd\",\n                \"\\u6e56\\u5357\",\n                \"\\u6e56\\u5317\",\n                \"\\u91cd\\u5e86\",\n                \"\\u56db\\u5ddd\",\n                \"\\u798f\\u5efa\",\n                \"\\u9752\\u6d77\",\n                \"\\u9ed1\\u9f99\",\n                \"\\u6c5f\\u897f\",\n                \"\\u9655\\u897f\",\n                \"\\u5e7f\\u897f\",\n                \"\\u6d77\\u5357\",\n                \"\\u6d59\\u6c5f\",\n                \"\\u5185\\u8499\",\n                \"\\u897f\\u85cf\",\n                \"\\u5c71\\u897f\",\n                \"\\u6cb3\\u5357\",\n                \"\\u4e0a\\u6d77\",\n                \"\\u5e7f\\u4e1c\",\n                \"\\u8d35\\u5dde\",\n                \"\\u4e91\\u5357\",\n                \"\\u5b81\\u590f\",\n                \"\\u65b0\\u7586\"\n            ]\n        }\n    ],\n    \"yAxis\": [\n        {\n            \"show\": true,\n            \"scale\": false,\n            \"nameLocation\": \"end\",\n            \"nameGap\": 15,\n            \"gridIndex\": 0,\n            \"inverse\": false,\n            \"offset\": 0,\n            \"splitNumber\": 5,\n            \"minInterval\": 0,\n            \"splitLine\": {\n                \"show\": false,\n                \"lineStyle\": {\n                    \"width\": 1,\n                    \"opacity\": 1,\n                    \"curveness\": 0,\n                    \"type\": \"solid\"\n                }\n            }\n        }\n    ],\n    \"title\": [\n        {\n            \"text\": \"\\u5168\\u56fd\\u9ad8\\u8003\\u7406\\u79d1(\\u4e00\\u672c)\\u5f55\\u53d6\\u5206\\u6570\\u5e73\\u5747\\u503c\\u6bd4\\u8f83\"\n        }\n    ]\n};\n        chart_57f5ed82063348159874412766694954.setOption(option_57f5ed82063348159874412766694954);\n    </script>\n</body>\n</html>\n"
  },
  {
    "path": "LICENSE",
    "content": "MIT License\n\nCopyright (c) 2019 wistbean\n\nPermission is hereby granted, free of charge, to any person obtaining a copy\nof this software and associated documentation files (the \"Software\"), to deal\nin the Software without restriction, including without limitation the rights\nto use, copy, modify, merge, publish, distribute, sublicense, and/or sell\ncopies of the Software, and to permit persons to whom the Software is\nfurnished to do so, subject to the following conditions:\n\nThe above copyright notice and this permission notice shall be included in all\ncopies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\nIMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\nFITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\nAUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\nLIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\nOUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\nSOFTWARE.\n"
  },
  {
    "path": "README.md",
    "content": "\n# learn_python3_spider\n接下来就是，学习python的正确姿势！\n\n[等下，阿里云服务器/2核2G/3M/40g，99元/年？？？](https://t.aliyun.com/U/DYTxRF)\n\npeace.\n\n# 我开发的小程序「要克制」\n\n帮你戒色：\n![要克制小程序](https://github.com/wistbean/learn_python3_spider/blob/master/ykz.png)\n\n# python爬虫教程从0到1\n\n## 爬虫负基础\n\n- [python爬虫系列教程-1 ｜ 不会代码也想爬数据？这就教你！](https://mp.weixin.qq.com/s?__biz=MzkyNTExNzY4NA==&mid=2247484935&idx=1&sn=ad9f68845455ca35c08c0e11f92aa4a6&chksm=c1ca3b9cf6bdb28a8647bc911079221b790780611e019e628613657ebfbc38e1e317f53ab00f&token=1453775207&lang=zh_CN#rd)\n\n\n## python爬虫前，抓包\n\n- [python爬虫系列教程00 | 什么是爬虫，怎么玩爬虫？](http://mp.weixin.qq.com/s?__biz=Mzg2NzYyNjg2Nw==&amp;mid=2247489892&amp;idx=1&amp;sn=40f3f6b70d467ca72b838939aa63d720&amp;chksm=ceb9e378f9ce6a6e089459fad40e2ef8bdce9f46a0a7b9e8332cdbe6d2bc09a47879dc99dd4c&amp;scene=27#wechat_redirect)\n- [python爬虫系列教程01 | 教你在 Chrome 浏览器轻松抓包](http://mp.weixin.qq.com/s?__biz=Mzg2NzYyNjg2Nw==&amp;mid=2247489893&amp;idx=1&amp;sn=32cc4fe30066a148485f40629aff598a&amp;chksm=ceb9e379f9ce6a6f609b95a729d01ff1745c101c14fe005fd2ed73e32dec08e1ed4d102bc9c9&amp;scene=27#wechat_redirect)\n- [python爬虫系列教程02 | 教你通过 Fiddler 进行手机抓包？](https://mp.weixin.qq.com/s?__biz=Mzg2NzYyNjg2Nw==&amp;mid=2247489894&amp;idx=1&amp;sn=d620c16bf3fcb4657c8c44152d936fc7&amp;chksm=ceb9e37af9ce6a6c3017158256b06afd5fb1945a4cd05f9db7e27c31606626ee73d0cc44a074&amp;scene=27#wechat_redirect)\n\n\n## python爬虫库的使用\n- [python爬虫系列教程03 | 那个叫做 Urllib 的库让我们的 python 假装是浏览器](http://mp.weixin.qq.com/s?__biz=Mzg2NzYyNjg2Nw==&amp;mid=2247489895&amp;idx=1&amp;sn=9cddfab13d7d251ab3f7e81a882961ce&amp;chksm=ceb9e37bf9ce6a6d1014e00a7d4730249dc1e9104a8fd70ebc34211714a136bc003a962853b8&amp;scene=27#wechat_redirect)\n- [python爬虫系列教程04 | 长江后浪推前浪，Requests库把urllib库拍在沙滩上](http://mp.weixin.qq.com/s?__biz=Mzg2NzYyNjg2Nw==&amp;mid=2247489896&amp;idx=1&amp;sn=a4686a0cefb12a9bc5d41b062327f545&amp;chksm=ceb9e374f9ce6a622723e99c8e6c04dc25b268d474f259f85ec8da73d755f0de562bb584c63c&amp;scene=27#wechat_redirect)\n- [python爬虫系列教程05 | 年轻人，不会正则表达式你睡得着觉？有点出息没有？](https://vip.fxxkpython.com/?p=1928)\n- [python爬虫系列教程06 | 你的第一个爬虫，爬取当当网 Top 500 本五星好评书籍](https://vip.fxxkpython.com/?p=1903)\n- [python爬虫系列教程07 | 有了 BeautifulSoup ，妈妈再也不用担心我的正则表达式了](https://vip.fxxkpython.com/?p=1891)\n- [python爬虫系列教程08 | 你的第二个爬虫，要过年了，爬取豆瓣最受欢迎的250部电影慢慢看](https://vip.fxxkpython.com/?p=1871)\n- [python爬虫系列教程09 | 上来，自己动 ！这就是 selenium 的牛逼之处](https://vip.fxxkpython.com/?p=1854)\n- [python爬虫系列教程10 | 这次，将带你使用 selenium+ phantomJS 爬取b站上的NBA形象大使蔡徐坤和他的球友们](https://vip.fxxkpython.com/?p=4699)\n- [python爬虫系列教程11 | python爬虫的时候对Json数据的解析](https://vip.fxxkpython.com/?p=4723)\n- [python爬虫系列教程12 | 秒爬，python爬虫中的多线程，多进程，协程](https://vip.fxxkpython.com/?p=4736)\n- [python爬虫系列教程13 | 就这么说吧，如果你不懂python多线程和线程池，那就去河边摸鱼！](https://vip.fxxkpython.com/?p=4756)\n- [python爬虫系列教程14 | 害羞，用多线程秒爬那些万恶的妹纸们，纸巾呢？](https://vip.fxxkpython.com/?p=5293)\n- [python爬虫系列教程15 | 你，快去试试用多进程的方式重新去爬取豆瓣上的电影](https://vip.fxxkpython.com/?p=4793)\n- [python爬虫系列教程16 | 听说你又被封 ip 了，你要学会伪装好自己，这次说说伪装你的头部](https://vip.fxxkpython.com/?p=4803)\n- [python爬虫系列教程17 | 就算你被封了也能继续爬，使用IP代理池伪装你的IP地址，让IP飘一会](https://vip.fxxkpython.com/?p=4818)\n- [海外评比第一的代理 IP 提供商，代理抓取成功率 99%。](https://get.brightdata.com/k47ir0cpnkh2)\n- [python爬虫系列教程18 | 遇到需要的登录的网站怎么办？用这3招轻松搞定！](https://vip.fxxkpython.com/?p=4833)\n- [python爬虫系列教程19 | 小帅b教你如何识别图片验证码](https://vip.fxxkpython.com/?p=4848)\n- [python爬虫系列教程20 | 对于b站这样的滑动验证码，不好意思，照样自动识别](https://vip.fxxkpython.com/?p=4878)\n- [python爬虫系列教程21 | 以后我再讲「模拟登录」我就是狗](https://vip.fxxkpython.com/?p=4919)\n- [python爬虫系列教程22 | 手机，这次要让你上来自己动了。这就是 Appium+Python 的牛x之处](https://vip.fxxkpython.com/?p=4929)\n- [python爬虫系列教程23 | 搞事情了，用 Appium 爬取你的微信朋友圈。](https://vip.fxxkpython.com/?p=4950)\n- [python爬虫系列教程24 |爬取下来的数据怎么保存？ CSV 了解一下](https://vip.fxxkpython.com/?p=4975)\n- [python爬虫系列教程25 | 把数据爬取下来之后就存储到你的MySQL数据库。](https://vip.fxxkpython.com/?p=4990)\n- [python爬虫系列教程26 | 当Python遇到MongoDB的时候，存储av女优的数据变得如此顺滑爽～](https://vip.fxxkpython.com/?p=5005)\n- [python爬虫系列教程27 | 你爬下的数据不分析一波可就亏了啊，使用python进行数据可视化](https://vip.fxxkpython.com/?p=5020)\n- [python爬虫系列教程28 | 使用scrapy爬取糗事百科的例子，告诉你它有多厉害！](https://vip.fxxkpython.com/?p=5038)\n- [python爬虫系列教程30 | scrapy后续，把「糗事百科」的段子爬下来然后存到数据库中](https://vip.fxxkpython.com/?p=5059)\n- [mitmproxy | 那个站在中间的男人，使用Python就能直接操控你的上网请求](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247485104&idx=1&sn=5ee4a04e6ce2854e5507cd320517fd0d&chksm=fc8bbe21cbfc373738d926e0ca3250f44079449a85c1fe88f307805e28a3cc4ada07d9e322bb&token=2085568099&lang=zh_CN#rd)\n- [mitmproxy | 如何使用 mitmproxy 监控你的手机](https://mp.weixin.qq.com/s?__biz=Mzg2NzYyNjg2Nw==&mid=2247490016&idx=1&sn=4749ad1707fd33be167118d5f3aadeab&source=41#wechat_redirect)\n\n\n## python爬虫进阶：python爬虫反爬\n\n- [python爬虫反爬 | 对方是如何丧心病狂的通过 css 加密让你爬不到数据的](http://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&amp;mid=2247484810&amp;idx=1&amp;sn=ed3297773c1eeb741bdabfb31c3ea00e&amp;chksm=fc8bbd1bcbfc340d6ae0166e035dd8c8e106afae8adc5fc32162a17b68916b69383b0ab67265&amp;scene=27#wechat_redirect) \n- [python爬虫反反爬 | 看完这篇，你几乎可以横扫大部分 css 字体加密的网站！](http://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&amp;mid=2247484921&amp;idx=1&amp;sn=72a707c5bc67eede144947829cab4dc6&amp;chksm=fc8bbd68cbfc347eca6727ff90f85ef58a4fdd7c2f75a962aee3ccd5e9c4266dbe5f4e6e2262&amp;scene=27#wechat_redirect) \n- [python爬虫反反爬 | 像有道词典这样的 JS 混淆加密应该怎么破](http://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&amp;mid=2247484997&amp;idx=1&amp;sn=b304304aacb3cba31f5f7a6c6bb1ba69&amp;chksm=fc8bbed4cbfc37c29db631c187295757c164ae75ff3e0381dbbf685a9f3d1410098e5b751e33&amp;scene=27#wechat_redirect) \n- [你想逆向我的 js 代码？呵呵，先过了我的反 debug 再说吧！](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247485338&idx=1&sn=5b4d6ed34a27ed5e81a3e5d8ccf8bee9&scene=19&token=464856977&lang=zh_CN#wechat_redirect)\n- [js 逆向分析，代码扣取](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247488874&idx=1&sn=709dc1b0005bb3e39b59a90d75cccfa7&chksm=fc8badfbcbfc24ede7a35f6b0d6b1becddb5ca57ab9efe2b394d962581e84804c05208c94f79&token=1628227326&lang=zh_CN#rd)\n- [Python 逆向抓取 APP 数据](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247488910&idx=1&sn=2b5cc2571220086b9ac3e2c95fd41cde&chksm=fc8bad1fcbfc24090c06a86da2725e506d17993bddf0dfa57330d3069a003a5f0d66fb602d11&token=1628227326&lang=zh_CN#rd)\n- [这次有点骚了，破解安卓某 APP 低层加密](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247489255&idx=1&sn=4abbd544ff0a63f4d24eb06a0f954df1&chksm=fc8bae76cbfc2760a71267cca2cade5f6847a7291fa4adc0abf37743c878bfbda65a496f2305&scene=178&cur_album_id=1321044729160859650#rd)\n- [当你通过 Python 请求网站得到一堆无厘头的 JS 时...](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247489477&idx=1&sn=891944cbceab3eb77966055604645457&chksm=fc8baf54cbfc2642a171cf8851c20f8a05f3eb2b844e8d0b1a6e7539590ce7c69ffae21f10f5&scene=178&cur_album_id=1321044729160859650#rd)\n\n## Python websocket 爬虫：\n- [哇靠，这些数据疯狂变化，该怎么爬取？](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247485466&idx=1&sn=1e4db96f3ca1d3a263dd7e075cbd7600&scene=19&token=464856977&lang=zh_CN#wechat_redirect)\n\n## Python 分布式爬虫\n- [说说分布式爬虫](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247485718&idx=1&sn=2d42d1c7408b14781ef4c1e97fbac8f6&scene=19&token=464856977&lang=zh_CN#wechat_redirect)\n- [我整来了几台服务器，就是为了给你演示一下分布式爬虫的整个过程](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247485863&idx=1&sn=34f9fb196c77dffdcce4a610b622270d&scene=19&token=464856977&lang=zh_CN#wechat_redirect)\n\n## 爬虫实战教程\n- [python爬取 20w 表情包之后，从此你就成为了微信斗图届的高手](https://fxxkpython.com/python-pa-qu-biao-qing-bao.html)\n- [python爬取你喜欢的公众号的所有原创文章，然后搞成PDF慢慢看](http://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&amp;mid=2247484657&amp;idx=1&amp;sn=998bfcce6cd22b7fedff29e68a46fe3f&amp;chksm=fc8bbc60cbfc3576f117d3566fbea8a042ee573d840bbe6a3d4ec9bffef815c691b7f9a59711&amp;scene=27#wechat_redirect) \n- [当 python 遇到你的微信的时候，你才发现原来你的微信好友是这样的](http://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&amp;mid=2247484710&amp;idx=1&amp;sn=cf17f2e87405ebffb20edd0ca0a7315b&amp;chksm=fc8bbdb7cbfc34a1389e17d4485b677d5ada497a404dc8f14107914e50382c640e7bd3cb93a4&amp;scene=27#wechat_redirect) \n- [高考要来了，扒一扒历年高考录取分数来压压惊](http://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&amp;mid=2247484745&amp;idx=1&amp;sn=24362e73605d30e06ebe05d1fe7225f2&amp;chksm=fc8bbdd8cbfc34ce100b9461f46c8a1c0008172f101b34b38e146f56323bc40bbd373a127ee8&amp;scene=27#wechat_redirect) \n- [随着身子的一阵颤抖，Python爬取抖音上的小姐姐突然变得索然无味](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247485150&idx=1&sn=b813993925a1031d4e85eb8841ccdb37&scene=19#wechat_redirect)\n- [使用 scrapy 爬取 stackoverflow 上的所有 Python 问答](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247485754&idx=1&sn=3e52aa0ac13f3a23c6dee2b75424f0f5&scene=19&token=464856977&lang=zh_CN#wechat_redirect)\n- [爬取周杰伦新歌《说好不哭》的所有评论，然后生成词云图](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247485571&idx=1&sn=094517114b22a4684988008aecab2639&scene=19&token=464856977&lang=zh_CN#wechat_redirect)\n- [我整来了几台服务器，就是为了给你演示一下分布式爬虫的整个过程](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247485863&idx=1&sn=34f9fb196c77dffdcce4a610b622270d&scene=19&token=464856977&lang=zh_CN#wechat_redirect)\n\n\n## 爬虫实例源代码\n\n图文教程 | 相关源码\n---- | ---\n[1、爬取当当网 Top 500 本五星好评书籍](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247484142&idx=1&sn=d4893c734e44a16db871f7904910bdcb&scene=19#wechat_redirect) | [源码](https://github.com/wistbean/learn_python3_spider/blob/master/dangdang_top_500.py)\n[2、爬取豆瓣最受欢迎的250部电影慢慢看](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247484156&idx=1&sn=dc732b380d162f39ff63d55cac5a0dd6&scene=19#wechat_redirect) | [源码](https://github.com/wistbean/learn_python3_spider/blob/master/douban_top_250_books.py)   \n[3、爬取b站上的NBA形象大使蔡徐坤和他的球友们](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247484182&idx=1&sn=1b1c0058e402a9dc559d16ab37a30e98&scene=19#wechat_redirect) | [源码](https://github.com/wistbean/learn_python3_spider/blob/master/ikun_basketball.py)\n[4、用多线程秒爬那些万恶的妹纸们，纸巾呢？](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247484225&idx=1&sn=077fba66aaa1d806193403ce51e75279&scene=19#wechat_redirect) | [源码](https://github.com/wistbean/learn_python3_spider/blob/master/meizitu.py)\n[5、自动识别b站滑动验证码](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247484321&idx=1&sn=4bc73324acfacda7d3bc82120b19d11a&scene=19#wechat_redirect) | [源码](https://github.com/wistbean/learn_python3_spider/blob/master/fuck_bilibili_captcha.py)\n[6、搞事情了，用 Appium 爬取你的微信朋友圈](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247484386&idx=1&sn=7f0545f27f095f20d69deedfa9f606a1&scene=19#wechat_redirect) | [源码](https://github.com/wistbean/learn_python3_spider/blob/master/wechat_moment.py)\n[7、scrapy爬取糗事百科段子到MongoDB（上）](https://fxxkpython.com/python3-web-fxxkpython-spider-tutorial-29.html)、[scrapy爬取糗事百科段子到MongoDB(下)](https://fxxkpython.com/python3-web-fxxkpython-spider-tutorial-30.html) | [源码](https://github.com/wistbean/learn_python3_spider/tree/master/qiushibaike) \n[8、python爬取 20w 表情包之后，从此你就成为了微信斗图届的高手](https://fxxkpython.com/python-pa-qu-biao-qing-bao.html) | [源码](https://github.com/wistbean/learn_python3_spider/tree/master/biaoqingbao)\n[9、python爬取你喜欢的公众号的所有原创文章，然后搞成PDF慢慢看](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247484657&idx=1&sn=998bfcce6cd22b7fedff29e68a46fe3f&scene=19&token=464856977&lang=zh_CN#wechat_redirect) | [源码](https://github.com/wistbean/learn_python3_spider/blob/master/wechat_public_account.py)\n[10、当 python 遇到你的微信的时候，你才发现原来你的微信好友是这样的](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247484710&idx=1&sn=cf17f2e87405ebffb20edd0ca0a7315b&scene=19&token=464856977&lang=zh_CN#wechat_redirect) | [--](https://wistbean.github.io)\n> 未完待续...\n\n## 爬虫技巧\n- [给你们说几点鲜有人知的爬虫技巧](https://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&mid=2247485129&idx=1&sn=56a9aecafa73162c639a873b5bbdf534&chksm=fc8bbe58cbfc374e5c033a37a82b94e8391855d85f1db26975579ddb3cf0882f1157e37f224c&token=2111372640&lang=zh_CN#rd)\n\n\n## python爬虫段子\n\n- [网站维护人员：真的求求你们了，不要再来爬取了！！](https://vip.fxxkpython.com/?p=4679)\n\n## python相关\n- [python如何赚钱？ python爬虫如何进阶？ python就业？ 如何快速入门python？ .....](http://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&amp;mid=2247484770&amp;idx=1&amp;sn=16427865c7b2785594acfbcf4505e26f&amp;chksm=fc8bbdf3cbfc34e5856dd36dd825f9b89b05a4ab3def08dac48b760771e4ee0454fdf9ddee72&amp;scene=27#wechat_redirect) \n- [ 如何自学 Python 高效一些](http://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&amp;mid=2247484608&amp;idx=1&amp;sn=0ebde7cbfea6e42e9e8e316bbec35b2b&amp;chksm=fc8bbc51cbfc35475daa15a026c44727bc7954bd722b24870eab567ef937a8f175369c546962&amp;scene=27#wechat_redirect) \n- [python教程资源](https://wistbean.github.io/categories/python/)\n- [吐血分享这两个爬虫用到的 Chrome 牛逼插件](http://mp.weixin.qq.com/s?__biz=MzU2ODYzNTkwMg==&amp;mid=2247484859&amp;idx=1&amp;sn=b5f91ab1dc027d06e34dea1b37091b34&amp;chksm=fc8bbd2acbfc343ce3123fb3e3aec1fa1e34c96b15e998a34e01a75f4ca90b0089e1692f5a31&amp;scene=27#wechat_redirect) \n\n## 公众号获取 Python 相关帅书\n\n微信搜索id：fxxkpython\n名称：帅彬老仙\n*进去发送「帅书」即可领取。*\n\n\n\n## Python 技巧视频教程\n\n[那些被低估了的 Python 技巧](https://www.bilibili.com/video/BV1P5411S7B6/?vd_source=ed99ef1bdeb96f04c35ccaea6eba97a8)\n\n\n\n\n\n\n\n"
  },
  {
    "path": "biaoqingbao/biaoqingbao.py",
    "content": "#-*- coding:UTF-8 -*-\nimport os\nfrom time import time\n\nimport requests\nfrom bs4 import BeautifulSoup\nfrom queue import Queue\nfrom threading import Thread\n\n\nclass DownloadBiaoqingbao(Thread):\n\n    def __init__(self, queue, path):\n        Thread.__init__(self)\n        self.queue = queue\n        self.path = '/home/wistbean/biaoqingbao/'\n        if not os.path.exists(path):\n            os.makedirs(path)\n\n    def run(self):\n        while True:\n            url = self.queue.get()\n            try:\n                # print(url)\n                download_biaoqingbaos(url, self.path)\n            finally:\n                self.queue.task_done()\n\n\ndef download_biaoqingbaos(url, path):\n\n    response = requests.get(url)\n    soup = BeautifulSoup(response.content, 'lxml')\n    img_list = soup.find_all('img', class_='ui image lazy')\n\n    for img in img_list:\n        image = img.get('data-original')\n        title = img.get('title')\n        print('下载图片： ', title)\n\n        try:\n            with open(path + title + os.path.splitext(image)[-1], 'wb') as f:\n                img = requests.get(image).content\n                f.write(img)\n        except OSError:\n            print('length  failed')\n            break\n\n\nif __name__ == '__main__':\n\n    start = time()\n\n    # 构建所有的链接\n    _url = 'https://fabiaoqing.com/biaoqing/lists/page/{page}.html'\n    urls = [_url.format(page=page) for page in range(1, 4328+1)]\n\n    queue = Queue()\n    path = '/home/wistbean/biaoqingbao/'\n\n    # 创建线程\n    for x in range(10):\n        worker = DownloadBiaoqingbao(queue, path)\n        worker.daemon = True\n        worker.start()\n\n    # 加入队列\n    for url in urls:\n        queue.put(url)\n\n    queue.join()\n\n    print('下载完毕耗时：  ', time()-start)\n\n\n\n"
  },
  {
    "path": "biaoqingbao/search.py",
    "content": "#-*- coding:UTF-8 -*-\nimport glob\nimport time\n\nimport itchat\nfrom itchat.content import TEXT, PICTURE\n\n\nimgs = []\n\ndef searchImage(text):\n    print('收到关键词: ', text)\n    for name in glob.glob('/home/wistbean/biaoqingbao/*'+text+'*.jpg'):\n        imgs.append(name)\n\n\n@itchat.msg_register([PICTURE, TEXT])\ndef text_reply(msg):\n    searchImage(msg.text)\n    for img in imgs[:6]:\n        msg.user.send_image(img)\n        time.sleep(0.3)\n        print('开始发送表情： ', img)\n    imgs.clear()\n\n\nitchat.auto_login(hotReload=True)\nitchat.run()\n"
  },
  {
    "path": "dangdang_top_500.py",
    "content": "import requests\nimport re\nimport json\n\n\ndef request_dandan(url):\n    try:\n        response = requests.get(url)\n        if response.status_code == 200:\n            return response.text\n    except requests.RequestException as e:\n        print(e)\n        return None\n\n\ndef parse_result(html):\n    pattern = re.compile(\n        '<li.*?list_num.*?(\\d+)\\.</div>.*?<img src=\"(.*?)\".*?class=\"name\".*?title=\"(.*?)\">.*?class=\"star\">.*?class=\"tuijian\">(.*?)</span>.*?class=\"publisher_info\">.*?target=\"_blank\">(.*?)</a>.*?class=\"biaosheng\">.*?<span>(.*?)</span></div>.*?<p><span class=\"price_n\">(.*?)</span>.*?</li>', re.S)\n    items = re.findall(pattern, html)\n\n    for item in items:\n        yield {\n            'range': item[0],\n            'image': item[1],\n            'title': item[2],\n            'recommend': item[3],\n            'author': item[4],\n            'times': item[5],\n            'price': item[6]\n        }\n\n\ndef write_item_to_file(item):\n    print('开始写入数据 ====> ' + str(item))\n    with open('book.txt', 'a', encoding='UTF-8') as f:\n        f.write(json.dumps(item, ensure_ascii=False) + '\\n')\n\n\ndef main(page):\n    url = 'http://bang.dangdang.com/books/fivestars/01.00.00.00.00.00-recent30-0-0-1-' + str(page)\n    html = request_dandan(url)\n    items = parse_result(html)  # 解析过滤我们想要的信息\n    for item in items:\n        write_item_to_file(item)\n\n\nif __name__ == \"__main__\":\n    for i in range(1, 26):\n        main(i)\n"
  },
  {
    "path": "douban_top_250_books.py",
    "content": "import requests\nfrom bs4 import BeautifulSoup\nimport xlwt\n\n\ndef request_douban(url):\nheaders = {\n        'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) '\n                      'Chrome/88.0.4324.146 Safari/537.36',\n    }\n\n    try:\n        response = requests.get(url=url, headers=headers)\n        if response.status_code == 200:\n            return response.text\n    except requests.RequestException:\n        return None\n\n\nbook = xlwt.Workbook(encoding='utf-8', style_compression=0)\n\nsheet = book.add_sheet('豆瓣电影Top250', cell_overwrite_ok=True)\nsheet.write(0, 0, '名称')\nsheet.write(0, 1, '图片')\nsheet.write(0, 2, '排名')\nsheet.write(0, 3, '评分')\nsheet.write(0, 4, '作者')\nsheet.write(0, 5, '简介')\n\nn = 1\n\n\ndef save_to_excel(soup):\n    list = soup.find(class_='grid_view').find_all('li')\n\n    for item in list:\n        item_name = item.find(class_='title').string\n        item_img = item.find('a').find('img').get('src')\n        item_index = item.find(class_='').string\n        item_score = item.find(class_='rating_num').string\n        item_author = item.find('p').text\n        if item.find(class_='inq') is not None:\n            item_intr = item.find(class_='inq').string\n        else:\n            item_intr = 'NOT AVAILABLE'        \n\n        # print('爬取电影：' + item_index + ' | ' + item_name +' | ' + item_img +' | ' + item_score +' | ' + item_author +' | ' + item_intr )\n        print('爬取电影：' + item_index + ' | ' + item_name + ' | ' + item_score + ' | ' + item_intr)\n\n        global n\n\n        sheet.write(n, 0, item_name)\n        sheet.write(n, 1, item_img)\n        sheet.write(n, 2, item_index)\n        sheet.write(n, 3, item_score)\n        sheet.write(n, 4, item_author)\n        sheet.write(n, 5, item_intr)\n\n        n = n + 1\n\n\ndef main(page):\n    url = 'https://movie.douban.com/top250?start=' + str(page * 25) + '&filter='\n    html = request_douban(url)\n    soup = BeautifulSoup(html, 'lxml')\n    save_to_excel(soup)\n\n\nif __name__ == '__main__':\n\n    for i in range(0, 10):\n        main(i)\n\nbook.save(u'豆瓣最受欢迎的250部电影.xlsx')\n"
  },
  {
    "path": "douban_top_250_books_mul_process.py",
    "content": "import requests\nfrom bs4 import BeautifulSoup\nimport xlwt\nimport multiprocessing\nimport time\nimport sys\n\ndef request_douban(url):\n    try:\n        response = requests.get(url,headers={'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64)'})\n        if response.status_code == 200:\n            return response.text\n    except requests.RequestException:\n        return None\n\ndef main(url):\n    sys.setrecursionlimit(1000000)\n    data = []\n    html = request_douban(url)\n    # soup = BeautifulSoup(html, 'lxml')\n    soup = BeautifulSoup(html, 'html.parser')\n    list = soup.find(class_='grid_view').find_all('li')\n    for item in list:\n        item_name = item.find(class_='title').string\n        item_img = item.find('a').find('img').get('src')\n        item_index = item.find(class_='').string\n        item_score = item.find(class_='rating_num').string\n        item_author = item.find('p').text\n        item_intr = ''\n        if (item.find(class_='inq') != None):\n            item_intr = item.find(class_='inq').string\n        print('爬取电影：' + item_index + ' | ' + item_name + ' | ' + item_score + ' | ' + item_intr)\n        item = {\n            'item_index': item_index,\n            'item_name': item_name,\n            'item_score': item_score,\n            'item_intr': item_intr,\n            'item_img': item_img,\n            'item_author': item_author\n        }\n        data.append(item)\n    return data\n    \nif __name__ == '__main__':\n    startTime = time.time()\n    data = []\n    urls = []\n    pool = multiprocessing.Pool(multiprocessing.cpu_count()-1)\n    for i in range(0, 10):\n        url = 'https://movie.douban.com/top250?start=' + str(i * 25) + '&filter='\n        urls.append(url)\n    pool.map(main, urls)\n    for pageItem in pool.map(main, urls):\n        data.extend(pageItem)\n    book = xlwt.Workbook(encoding='utf-8', style_compression=0)\n    sheet = book.add_sheet('豆瓣电影Top250-test', cell_overwrite_ok=True)\n    sheet.write(0, 0, '名称')\n    sheet.write(0, 1, '图片')\n    sheet.write(0, 2, '排名')\n    sheet.write(0, 3, '评分')\n    sheet.write(0, 4, '作者')\n    sheet.write(0, 5, '简介')\n    for index,item in enumerate(data):\n        sheet.write(index+1, 0, item['item_name'])\n        sheet.write(index+1, 1, item['item_img'])\n        sheet.write(index+1, 2, item['item_index'])\n        sheet.write(index+1, 3, item['item_score'])\n        sheet.write(index+1, 4, item['item_author'])\n        sheet.write(index+1, 5, item['item_intr'])\n    book.save(u'豆瓣最受欢迎的250部电影-mul.xlsx')\n\n    endTime = time.time()\n    dtime = endTime - startTime\n    print(\"程序运行时间：%s s\" % dtime)  # 4.036666631698608 s"
  },
  {
    "path": "fuck_bilibili_captcha.py",
    "content": "import time\nimport requests\nfrom PIL import Image\nfrom selenium import webdriver\nfrom selenium.webdriver import ActionChains\nfrom selenium.webdriver.common.by import By\nfrom selenium.webdriver.support.ui import WebDriverWait\nfrom selenium.webdriver.support import expected_conditions as EC\nfrom bs4 import BeautifulSoup\nimport re\nfrom io import BytesIO\n\ndriver = webdriver.Chrome('/usr/lib/chromium-browser/chromedriver')\nWAIT = WebDriverWait(driver, 10)\nurl = 'https://passport.bilibili.com/login'\n\n\ndef mergy_Image(image_file, location_list):\n    \"\"\"\n    将原始图片进行合成\n    :param image_file: 图片文件\n    :param location_list: 图片位置\n    :return: 合成新的图片\n    \"\"\"\n\n    # 存放上下部分的各个小块\n    upper_half_list = []\n    down_half_list = []\n\n    image = Image.open(image_file)\n\n    # 通过 y 的位置来判断是上半部分还是下半部分,然后切割\n    for location in location_list:\n        if location['y'] == -58:\n            # 间距为10，y：58-116\n            im = image.crop((abs(location['x']), 58, abs(location['x'])+10, 116))\n            upper_half_list.append(im)\n        if location['y'] == 0:\n            # 间距为10，y：0-58\n            im = image.crop((abs(location['x']), 0, abs(location['x']) + 10, 58))\n            down_half_list.append(im)\n\n    # 创建一张大小一样的图片\n    new_image = Image.new('RGB', (260, 116))\n\n    # 粘贴好上半部分 y坐标是从上到下（0-116）\n    offset = 0\n    for im in upper_half_list:\n        new_image.paste(im, (offset, 0))\n        offset += 10\n\n    # 粘贴好下半部分\n    offset = 0\n    for im in down_half_list:\n        new_image.paste(im, (offset, 58))\n        offset += 10\n\n    return new_image\n\n\ndef get_distance(bg_Image, fullbg_Image):\n\n    # 阈值\n    threshold = 200\n\n    print(bg_Image.size[0])\n    print(bg_Image.size[1])\n\n\n    for i in range(60, bg_Image.size[0]):\n        for j in range(bg_Image.size[1]):\n            bg_pix = bg_Image.getpixel((i, j))\n            fullbg_pix = fullbg_Image.getpixel((i, j))\n            r = abs(bg_pix[0] - fullbg_pix[0])\n            g = abs(bg_pix[1] - fullbg_pix[1])\n            b = abs(bg_pix[2] - fullbg_pix[2])\n\n            if r + g + b > threshold:\n               return i\n\n\n\n\ndef get_path(distance):\n        result = []\n        current = 0\n        mid = distance * 4 / 5\n        t = 0.2\n        v = 0\n        while current < (distance - 10):\n            if current < mid:\n                a = 2\n            else:\n                a = -3\n            v0 = v\n            v = v0 + a * t\n            s = v0 * t + 0.5 * a * t * t\n            current += s\n            result.append(round(s))\n        return result\n\n\ndef start_drag(driver, distance):\n\n    # 被妖怪吃掉了\n    # knob =  WAIT.until(EC.presence_of_element_located((By.CSS_SELECTOR, \"#gc-box > div > div.gt_slider > div.gt_slider_knob.gt_show\")))\n    # ActionChains(driver).click_and_hold(knob).perform()\n    # ActionChains(driver).move_by_offset(xoffset=distance, yoffset=0.1).perform()\n    # time.sleep(0.5)\n    # ActionChains(driver).release(knob).perform()\n\n    # 被妖怪吃掉了\n    # ActionChains(driver).drag_and_drop_by_offset(knob, distance-10, 0).perform()\n\n    knob = WAIT.until(EC.presence_of_element_located((By.CSS_SELECTOR, \"#gc-box > div > div.gt_slider > div.gt_slider_knob.gt_show\")))\n    result = get_path(distance)\n    ActionChains(driver).click_and_hold(knob).perform()\n\n    for x in result:\n        ActionChains(driver).move_by_offset(xoffset=x, yoffset=0).perform()\n\n    time.sleep(0.5)\n    ActionChains(driver).release(knob).perform()\n\n\ndef recognize_code(driver):\n    \"\"\"\n    识别滑动验证码\n    :param driver: selenium驱动\n    :return:\n    \"\"\"\n\n    bs = BeautifulSoup(driver.page_source,'lxml')\n    # 找到背景图片和缺口图片的div\n    bg_div = bs.find_all(class_='gt_cut_bg_slice')\n    fullbg_div = bs.find_all(class_='gt_cut_fullbg_slice')\n\n    # 获取缺口背景图片url\n    bg_url = re.findall('background-image:\\surl\\(\"(.*?)\"\\)',bg_div[0].get('style'))\n    # 获取背景图片url\n    fullbg_url = re.findall('background-image:\\surl\\(\"(.*?)\"\\)',fullbg_div[0].get('style'))\n\n    # 存放每个合成缺口背景图片的位置\n    bg_location_list = []\n    # 存放每个合成背景图片的位置\n    fullbg_location_list = []\n\n    for bg in bg_div:\n        location = {}\n        location['x'] = int(re.findall('background-position:\\s(.*?)px\\s(.*?)px;', bg.get('style'))[0][0])\n        location['y'] = int(re.findall('background-position:\\s(.*?)px\\s(.*?)px;', bg.get('style'))[0][1])\n        bg_location_list.append(location)\n\n    for fullbg in fullbg_div:\n        location = {}\n        location['x'] = int(re.findall('background-position:\\s(.*?)px\\s(.*?)px;', fullbg.get('style'))[0][0])\n        location['y'] = int(re.findall('background-position:\\s(.*?)px\\s(.*?)px;', fullbg.get('style'))[0][1])\n        fullbg_location_list.append(location)\n\n    print(bg_location_list)\n    print(fullbg_location_list)\n\n    # 将图片格式存为 jpg 格式\n    bg_url = bg_url[0].replace('webp', 'jpg')\n    fullbg_url = fullbg_url[0].replace('webp', 'jpg')\n    # print(bg_url)\n    # print(fullbg_url)\n\n    # 下载图片\n    bg_image = requests.get(bg_url).content\n    fullbg_image = requests.get(fullbg_url).content\n    print('完成图片下载')\n\n    # 写入图片\n    bg_image_file = BytesIO(bg_image)\n    fullbg_image_file = BytesIO(fullbg_image)\n\n    # 合成图片\n    bg_Image = mergy_Image(bg_image_file, bg_location_list)\n    fullbg_Image = mergy_Image(fullbg_image_file, fullbg_location_list)\n    # bg_Image.show()\n    # fullbg_Image.show()\n\n    # 计算缺口偏移距离\n    distance = get_distance(bg_Image, fullbg_Image)\n    print('得到距离：%s' % str(distance))\n\n    start_drag(driver, distance)\n\n\n\n\nif __name__ == '__main__':\n\n    # 获取滑块按钮\n    driver.get(url)\n    slider = WAIT.until(EC.element_to_be_clickable(\n        (By.CSS_SELECTOR, \"#gc-box > div > div.gt_slider > div.gt_slider_knob.gt_show\")))\n\n    recognize_code(driver)\n\n\n    # driver.close()\n\n"
  },
  {
    "path": "ikun_basketball.py",
    "content": "# coding=utf-8\n\n# 最新版的selenium(4.x.x)已经不支持PhantomJS。如要用PhantomJS，可用旧版本selenium。如pip install selenium==3.8.0。\nfrom selenium import webdriver\nfrom selenium.common.exceptions import TimeoutException\nfrom selenium.webdriver.common.by import By\nfrom selenium.webdriver.support.ui import WebDriverWait\nfrom selenium.webdriver.support import expected_conditions as EC\nfrom bs4 import BeautifulSoup\nimport xlwt\n\n# browser = webdriver.PhantomJS()\nbrowser = webdriver.Chrome()\nWAIT = WebDriverWait(browser, 10)\nbrowser.set_window_size(1400, 900)\n\nbook = xlwt.Workbook(encoding='utf-8', style_compression=0)\n\nsheet = book.add_sheet('蔡徐坤篮球', cell_overwrite_ok=True)\nsheet.write(0, 0, '名称')\nsheet.write(0, 1, '地址')\nsheet.write(0, 2, '描述')\nsheet.write(0, 3, '观看次数')\nsheet.write(0, 4, '弹幕数')\nsheet.write(0, 5, '发布时间')\n\nn = 1\n\n\ndef search():\n    try:\n        print('开始访问b站....')\n        browser.get(\"https://www.bilibili.com/\")\n\n        # 被那个破登录遮住了\n        # index = WAIT.until(EC.element_to_be_clickable((By.CSS_SELECTOR, \"#primary_menu > ul > li.home > a\")))\n        # index.click()\n\n        input = WAIT.until(EC.presence_of_element_located((By.CSS_SELECTOR, \"#nav_searchform > input\")))\n        submit = WAIT.until(EC.element_to_be_clickable(\n            (By.XPATH, '/html/body/div[2]/div/div[1]/div[1]/div/div[2]/div/form/div/button')))\n\n        input.send_keys('蔡徐坤 篮球')\n        submit.click()\n\n        # 跳转到新的窗口\n        print('跳转到新窗口')\n        all_h = browser.window_handles\n        browser.switch_to.window(all_h[1])\n        get_source()\n\n        total = WAIT.until(EC.presence_of_element_located((By.CSS_SELECTOR,\n                                                           \"#all-list > div.flow-loader > div.page-wrap > div > ul > li.page-item.last > button\")))\n        return int(total.text)\n    except TimeoutException:\n        return search()\n\n\ndef next_page(page_num):\n    try:\n        print('获取下一页数据')\n        next_btn = WAIT.until(EC.element_to_be_clickable((By.CSS_SELECTOR,\n                                                          '#all-list > div.flow-loader > div.page-wrap > div > ul > li.page-item.next > button')))\n        next_btn.click()\n        WAIT.until(EC.text_to_be_present_in_element((By.CSS_SELECTOR,\n                                                     '#all-list > div.flow-loader > div.page-wrap > div > ul > li.page-item.active > button'),\n                                                    str(page_num)))\n        get_source()\n    except TimeoutException:\n        browser.refresh()\n        return next_page(page_num)\n\n\ndef save_to_excel(soup):\n    list = soup.find(class_='video-list clearfix').find_all(class_='video-item matrix')\n\n    for item in list:\n        item_title = item.find('a').get('title')\n        item_link = item.find('a').get('href')\n        item_dec = item.find(class_='des hide').text\n        item_view = item.find(class_='so-icon watch-num').text\n        item_biubiu = item.find(class_='so-icon hide').text\n        item_date = item.find(class_='so-icon time').text\n\n        print('爬取：' + item_title)\n\n        global n\n\n        sheet.write(n, 0, item_title)\n        sheet.write(n, 1, item_link)\n        sheet.write(n, 2, item_dec)\n        sheet.write(n, 3, item_view)\n        sheet.write(n, 4, item_biubiu)\n        sheet.write(n, 5, item_date)\n\n        n = n + 1\n\n\ndef get_source():\n    WAIT.until(EC.presence_of_element_located(\n        (By.CSS_SELECTOR, '#all-list > div.flow-loader > div.filter-wrap')))\n\n    html = browser.page_source\n    soup = BeautifulSoup(html, 'lxml')\n    print('到这')\n\n    save_to_excel(soup)\n\n\ndef main():\n    try:\n        total = search()\n        print(total)\n\n        for i in range(2, int(total + 1)):\n            next_page(i)\n\n    finally:\n        browser.close()\n\n\nif __name__ == '__main__':\n    main()\n    book.save('蔡徐坤篮球.xlsx')\n"
  },
  {
    "path": "meizitu.py",
    "content": "# encoding = utf-8\nimport concurrent\nimport os\nfrom concurrent.futures import ThreadPoolExecutor\nimport requests\nfrom bs4 import BeautifulSoup\n\n\ndef header(referer):\n\n    headers = {\n        'Host': 'i.meizitu.net',\n        'Pragma': 'no-cache',\n        'Accept-Encoding': 'gzip, deflate',\n        'Accept-Language': 'zh-CN,zh;q=0.8,en;q=0.6',\n        'Cache-Control': 'no-cache',\n        'Connection': 'keep-alive',\n        'User-Agent': 'Mozilla/5.0 (Windows NT 6.1; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3626.121 Safari/537.36',\n        'Accept': 'image/webp,image/apng,image/*,*/*;q=0.8',\n        'Referer': '{}'.format(referer),\n    }\n\n    return headers\n\n\ndef request_page(url):\n    try:\n        response = requests.get(url)\n        if response.status_code == 200:\n            return response.text\n    except requests.RequestException:\n        return None\n\n\ndef get_page_urls():\n\n    for i in range(1, 2):\n        baseurl = 'https://www.mzitu.com/page/{}'.format(i)\n        html = request_page(baseurl)\n        soup = BeautifulSoup(html, 'lxml')\n        elements = soup.find(class_='postlist').find_all('li')\n        urls = []\n        for item in elements:\n            url = item.find('span').find('a').get('href')\n            print('页面链接：%s' % url)\n            urls.append(url)\n\n    return urls\n\n\ndef download_Pic(title, image_list):\n    # 新建文件夹\n    os.mkdir(title)\n    j = 1\n    # 下载图片\n    for item in image_list:\n        filename = '%s/%s.jpg' % (title, str(j))\n        print('downloading....%s : NO.%s' % (title, str(j)))\n        with open(filename, 'wb') as f:\n            img = requests.get(item, headers=header(item)).content\n            f.write(img)\n        j += 1\n\ndef download(url):\n    html = request_page(url)\n    soup = BeautifulSoup(html, 'lxml')\n    total = soup.find(class_='pagenavi').find_all('a')[-2].find('span').string\n    title = soup.find('h2').string\n    image_list = []\n\n    for i in range(int(total)):\n        html = request_page(url + '/%s' % (i + 1))\n        soup = BeautifulSoup(html, 'lxml')\n        img_url = soup.find('img').get('src')\n        image_list.append(img_url)\n\n    download_Pic(title, image_list)\n\n\ndef download_all_images(list_page_urls):\n    # 获取每一个详情妹纸\n    # works = len(list_page_urls)\n    with concurrent.futures.ProcessPoolExecutor(max_workers=5) as exector:\n        for url in list_page_urls:\n            exector.submit(download, url)\n\n\nif __name__ == '__main__':\n    # 获取每一页的链接和名称\n    list_page_urls = get_page_urls()\n    download_all_images(list_page_urls)"
  },
  {
    "path": "qiushibaike/qiushibaike/__init__.py",
    "content": ""
  },
  {
    "path": "qiushibaike/qiushibaike/items.py",
    "content": "# -*- coding: utf-8 -*-\n\n# Define here the models for your scraped items\n#\n# See documentation in:\n# https://doc.scrapy.org/en/latest/topics/items.html\n\nimport scrapy\n\n\nclass QiushibaikeItem(scrapy.Item):\n    # define the fields for your item here like:\n    # name = scrapy.Field()\n    author = scrapy.Field()\n    content = scrapy.Field()\n    _id = scrapy.Field()\n\n\n"
  },
  {
    "path": "qiushibaike/qiushibaike/middlewares.py",
    "content": "# -*- coding: utf-8 -*-\n\n# Define here the models for your spider middleware\n#\n# See documentation in:\n# https://doc.scrapy.org/en/latest/topics/spider-middleware.html\n\nfrom scrapy import signals\n\n\nclass QiushibaikeSpiderMiddleware(object):\n    # Not all methods need to be defined. If a method is not defined,\n    # scrapy acts as if the spider middleware does not modify the\n    # passed objects.\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        # This method is used by Scrapy to create your spiders.\n        s = cls()\n        crawler.signals.connect(s.spider_opened, signal=signals.spider_opened)\n        return s\n\n    def process_spider_input(self, response, spider):\n        # Called for each response that goes through the spider\n        # middleware and into the spider.\n\n        # Should return None or raise an exception.\n        return None\n\n    def process_spider_output(self, response, result, spider):\n        # Called with the results returned from the Spider, after\n        # it has processed the response.\n\n        # Must return an iterable of Request, dict or Item objects.\n        for i in result:\n            yield i\n\n    def process_spider_exception(self, response, exception, spider):\n        # Called when a spider or process_spider_input() method\n        # (from other spider middleware) raises an exception.\n\n        # Should return either None or an iterable of Response, dict\n        # or Item objects.\n        pass\n\n    def process_start_requests(self, start_requests, spider):\n        # Called with the start requests of the spider, and works\n        # similarly to the process_spider_output() method, except\n        # that it doesn’t have a response associated.\n\n        # Must return only requests (not items).\n        for r in start_requests:\n            yield r\n\n    def spider_opened(self, spider):\n        spider.logger.info('Spider opened: %s' % spider.name)\n\n\nclass QiushibaikeDownloaderMiddleware(object):\n    # Not all methods need to be defined. If a method is not defined,\n    # scrapy acts as if the downloader middleware does not modify the\n    # passed objects.\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        # This method is used by Scrapy to create your spiders.\n        s = cls()\n        crawler.signals.connect(s.spider_opened, signal=signals.spider_opened)\n        return s\n\n    def process_request(self, request, spider):\n        # Called for each request that goes through the downloader\n        # middleware.\n\n        # Must either:\n        # - return None: continue processing this request\n        # - or return a Response object\n        # - or return a Request object\n        # - or raise IgnoreRequest: process_exception() methods of\n        #   installed downloader middleware will be called\n        return None\n\n    def process_response(self, request, response, spider):\n        # Called with the response returned from the downloader.\n\n        # Must either;\n        # - return a Response object\n        # - return a Request object\n        # - or raise IgnoreRequest\n        return response\n\n    def process_exception(self, request, exception, spider):\n        # Called when a download handler or a process_request()\n        # (from other downloader middleware) raises an exception.\n\n        # Must either:\n        # - return None: continue processing this exception\n        # - return a Response object: stops process_exception() chain\n        # - return a Request object: stops process_exception() chain\n        pass\n\n    def spider_opened(self, spider):\n        spider.logger.info('Spider opened: %s' % spider.name)\n"
  },
  {
    "path": "qiushibaike/qiushibaike/pipelines.py",
    "content": "# -*- coding: utf-8 -*-\n\n# Define your item pipelines here\n#\n# Don't forget to add your pipeline to the ITEM_PIPELINES setting\n# See: https://doc.scrapy.org/en/latest/topics/item-pipeline.html\nimport pymongo\n\n\nclass QiushibaikePipeline(object):\n\n    def __init__(self):\n        self.connection = pymongo.MongoClient('localhost', 27017)\n        self.db = self.connection.scrapy\n        self.collection = self.db.qiushibaike\n\n    def process_item(self, item, spider):\n        if not self.connection or not item:\n            return\n        self.collection.save(item)\n\n    def __del__(self):\n        if self.connection:\n            self.connection.close()\n\n\n"
  },
  {
    "path": "qiushibaike/qiushibaike/settings.py",
    "content": "# -*- coding: utf-8 -*-\n\n# Scrapy settings for qiushibaike project\n#\n# For simplicity, this file contains only settings considered important or\n# commonly used. You can find more settings consulting the documentation:\n#\n#     https://doc.scrapy.org/en/latest/topics/settings.html\n#     https://doc.scrapy.org/en/latest/topics/downloader-middleware.html\n#     https://doc.scrapy.org/en/latest/topics/spider-middleware.html\n\nBOT_NAME = 'qiushibaike'\n\nSPIDER_MODULES = ['qiushibaike.spiders']\nNEWSPIDER_MODULE = 'qiushibaike.spiders'\n\nFEED_EXPORT_ENCODING = 'utf-8'\n\n\n# Crawl responsibly by identifying yourself (and your website) on the user-agent\nUSER_AGENT = 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Ubuntu Chromium/73.0.3683.86 Chrome/73.0.3683.86 Safari/537.36'\n\n# Obey robots.txt rules\nROBOTSTXT_OBEY = True\n\n# Configure maximum concurrent requests performed by Scrapy (default: 16)\n#CONCURRENT_REQUESTS = 32\n\n# Configure a delay for requests for the same website (default: 0)\n# See https://doc.scrapy.org/en/latest/topics/settings.html#download-delay\n# See also autothrottle settings and docs\n#DOWNLOAD_DELAY = 3\n# The download delay setting will honor only one of:\n#CONCURRENT_REQUESTS_PER_DOMAIN = 16\n#CONCURRENT_REQUESTS_PER_IP = 16\n\n# Disable cookies (enabled by default)\n#COOKIES_ENABLED = False\n\n# Disable Telnet Console (enabled by default)\n#TELNETCONSOLE_ENABLED = False\n\n# Override the default request headers:\n#DEFAULT_REQUEST_HEADERS = {\n#   'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',\n#   'Accept-Language': 'en',\n#}\n\n# Enable or disable spider middlewares\n# See https://doc.scrapy.org/en/latest/topics/spider-middleware.html\n#SPIDER_MIDDLEWARES = {\n#    'qiushibaike.middlewares.QiushibaikeSpiderMiddleware': 543,\n#}\n\n# Enable or disable downloader middlewares\n# See https://doc.scrapy.org/en/latest/topics/downloader-middleware.html\n#DOWNLOADER_MIDDLEWARES = {\n#    'qiushibaike.middlewares.QiushibaikeDownloaderMiddleware': 543,\n#}\n\n# Enable or disable extensions\n# See https://doc.scrapy.org/en/latest/topics/extensions.html\n#EXTENSIONS = {\n#    'scrapy.extensions.telnet.TelnetConsole': None,\n#}\n\n# Configure item pipelines\n# See https://doc.scrapy.org/en/latest/topics/item-pipeline.html\nITEM_PIPELINES = {\n   'qiushibaike.pipelines.QiushibaikePipeline': 300,\n}\n\n# Enable and configure the AutoThrottle extension (disabled by default)\n# See https://doc.scrapy.org/en/latest/topics/autothrottle.html\n#AUTOTHROTTLE_ENABLED = True\n# The initial download delay\n#AUTOTHROTTLE_START_DELAY = 5\n# The maximum download delay to be set in case of high latencies\n#AUTOTHROTTLE_MAX_DELAY = 60\n# The average number of requests Scrapy should be sending in parallel to\n# each remote server\n#AUTOTHROTTLE_TARGET_CONCURRENCY = 1.0\n# Enable showing throttling stats for every response received:\n#AUTOTHROTTLE_DEBUG = False\n\n# Enable and configure HTTP caching (disabled by default)\n# See https://doc.scrapy.org/en/latest/topics/downloader-middleware.html#httpcache-middleware-settings\n#HTTPCACHE_ENABLED = True\n#HTTPCACHE_EXPIRATION_SECS = 0\n#HTTPCACHE_DIR = 'httpcache'\n#HTTPCACHE_IGNORE_HTTP_CODES = []\n#HTTPCACHE_STORAGE = 'scrapy.extensions.httpcache.FilesystemCacheStorage'\n"
  },
  {
    "path": "qiushibaike/qiushibaike/spiders/__init__.py",
    "content": "# This package will contain the spiders of your Scrapy project\n#\n# Please refer to the documentation for information on how to create and manage\n# your spiders.\n"
  },
  {
    "path": "qiushibaike/qiushibaike/spiders/qiushibaike_spider.py",
    "content": "# -*- coding: utf-8 -*-\nimport random\n\nimport scrapy\n\nfrom qiushibaike.items import QiushibaikeItem\n\n\nclass QiushiSpider(scrapy.Spider):\n    # 这里定义一个唯一的名称，用来标识糗事的爬虫，在项目中不能和别的爬虫名称一样，等会会用到这个名称\n    name = \"qiushibaike\"\n\n\n    def start_requests(self):\n        urls = [\n            'https://www.qiushibaike.com/text/page/1/',\n        ]\n        for url in urls:\n            yield scrapy.Request(url=url, callback=self.parse)\n\n    def parse(self, response):\n\n        content_left_div = response.xpath('//*[@id=\"content-left\"]')\n        content_list_div = content_left_div.xpath('./div')\n\n        for content_div in content_list_div:\n            item = QiushibaikeItem()\n            item['author'] = content_div.xpath('./div/a[2]/h2/text()').get()\n            item['content'] = content_div.xpath('./a/div/span/text()').getall()\n            item['_id'] = content_div.attrib['id']\n            yield item\n\n        next_page = response.xpath('//*[@id=\"content-left\"]/ul/li[last()]/a').attrib['href']\n\n        if next_page is not None:\n            yield response.follow(next_page, callback=self.parse)"
  },
  {
    "path": "qiushibaike/scrapy.cfg",
    "content": "# Automatically created by: scrapy startproject\n#\n# For more information about the [deploy] section see:\n# https://scrapyd.readthedocs.io/en/latest/deploy.html\n\n[settings]\ndefault = qiushibaike.settings\n\n[deploy]\n#url = http://localhost:6800/\nproject = qiushibaike\n"
  },
  {
    "path": "stackoverflow/.idea/inspectionProfiles/profiles_settings.xml",
    "content": "<component name=\"InspectionProjectProfileManager\">\n  <settings>\n    <option name=\"USE_PROJECT_PROFILE\" value=\"false\" />\n    <version value=\"1.0\" />\n  </settings>\n</component>"
  },
  {
    "path": "stackoverflow/.idea/misc.xml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n  <component name=\"ProjectRootManager\" version=\"2\" project-jdk-name=\"Python 3.6 (stackoverflow)\" project-jdk-type=\"Python SDK\" />\n</project>"
  },
  {
    "path": "stackoverflow/.idea/modules.xml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n  <component name=\"ProjectModuleManager\">\n    <modules>\n      <module fileurl=\"file://$PROJECT_DIR$/.idea/stackoverflow.iml\" filepath=\"$PROJECT_DIR$/.idea/stackoverflow.iml\" />\n    </modules>\n  </component>\n</project>"
  },
  {
    "path": "stackoverflow/.idea/stackoverflow.iml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<module type=\"PYTHON_MODULE\" version=\"4\">\n  <component name=\"NewModuleRootManager\">\n    <content url=\"file://$MODULE_DIR$\">\n      <excludeFolder url=\"file://$MODULE_DIR$/venv\" />\n    </content>\n    <orderEntry type=\"jdk\" jdkName=\"Python 3.6 (stackoverflow)\" jdkType=\"Python SDK\" />\n    <orderEntry type=\"sourceFolder\" forTests=\"false\" />\n  </component>\n  <component name=\"TestRunnerService\">\n    <option name=\"projectConfiguration\" value=\"Twisted Trial\" />\n    <option name=\"PROJECT_TEST_RUNNER\" value=\"Twisted Trial\" />\n  </component>\n</module>"
  },
  {
    "path": "stackoverflow/.idea/vcs.xml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n  <component name=\"VcsDirectoryMappings\">\n    <mapping directory=\"$PROJECT_DIR$/..\" vcs=\"Git\" />\n  </component>\n</project>"
  },
  {
    "path": "stackoverflow/.idea/workspace.xml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n  <component name=\"ChangeListManager\">\n    <list default=\"true\" id=\"d727a472-97fb-4747-a4bb-38b0e47efab5\" name=\"Default Changelist\" comment=\"\">\n      <change afterPath=\"$PROJECT_DIR$/.idea/vcs.xml\" afterDir=\"false\" />\n      <change beforePath=\"$PROJECT_DIR$/.idea/misc.xml\" beforeDir=\"false\" afterPath=\"$PROJECT_DIR$/.idea/misc.xml\" afterDir=\"false\" />\n      <change beforePath=\"$PROJECT_DIR$/.idea/stackoverflow.iml\" beforeDir=\"false\" afterPath=\"$PROJECT_DIR$/.idea/stackoverflow.iml\" afterDir=\"false\" />\n      <change beforePath=\"$PROJECT_DIR$/.idea/workspace.xml\" beforeDir=\"false\" afterPath=\"$PROJECT_DIR$/.idea/workspace.xml\" afterDir=\"false\" />\n      <change beforePath=\"$PROJECT_DIR$/stackoverflow/pipelines.py\" beforeDir=\"false\" afterPath=\"$PROJECT_DIR$/stackoverflow/pipelines.py\" afterDir=\"false\" />\n      <change beforePath=\"$PROJECT_DIR$/stackoverflow/settings.py\" beforeDir=\"false\" afterPath=\"$PROJECT_DIR$/stackoverflow/settings.py\" afterDir=\"false\" />\n    </list>\n    <option name=\"EXCLUDED_CONVERTED_TO_IGNORED\" value=\"true\" />\n    <option name=\"SHOW_DIALOG\" value=\"false\" />\n    <option name=\"HIGHLIGHT_CONFLICTS\" value=\"true\" />\n    <option name=\"HIGHLIGHT_NON_ACTIVE_CHANGELIST\" value=\"false\" />\n    <option name=\"LAST_RESOLUTION\" value=\"IGNORE\" />\n  </component>\n  <component name=\"FileTemplateManagerImpl\">\n    <option name=\"RECENT_TEMPLATES\">\n      <list>\n        <option value=\"Python Script\" />\n      </list>\n    </option>\n  </component>\n  <component name=\"Git.Settings\">\n    <option name=\"RECENT_GIT_ROOT_PATH\" value=\"$PROJECT_DIR$/..\" />\n  </component>\n  <component name=\"HighlightingSettingsPerFile\">\n    <setting file=\"file://$PROJECT_DIR$/stackoverflow/pipelines.py\" root0=\"SKIP_HIGHLIGHTING\" />\n    <setting file=\"file://$PROJECT_DIR$/stackoverflow/requirement.txt\" root0=\"SKIP_INSPECTION\" />\n    <setting file=\"file://$PROJECT_DIR$/stackoverflow/settings.py\" root0=\"SKIP_INSPECTION\" />\n  </component>\n  <component name=\"ProjectId\" id=\"1SHFrr4TuSLZAtNyu5lCpHTWVu6\" />\n  <component name=\"ProjectLevelVcsManager\" settingsEditedManually=\"true\" />\n  <component name=\"PropertiesComponent\">\n    <property name=\"SHARE_PROJECT_CONFIGURATION_FILES\" value=\"true\" />\n    <property name=\"last_opened_file_path\" value=\"$PROJECT_DIR$\" />\n    <property name=\"settings.editor.selected.configurable\" value=\"com.jetbrains.python.configuration.PyActiveSdkModuleConfigurable\" />\n  </component>\n  <component name=\"RecentsManager\">\n    <key name=\"MoveFile.RECENT_KEYS\">\n      <recent name=\"$PROJECT_DIR$/stackoverflow\" />\n    </key>\n  </component>\n  <component name=\"RunDashboard\">\n    <option name=\"ruleStates\">\n      <list>\n        <RuleState>\n          <option name=\"name\" value=\"ConfigurationTypeDashboardGroupingRule\" />\n        </RuleState>\n        <RuleState>\n          <option name=\"name\" value=\"StatusDashboardGroupingRule\" />\n        </RuleState>\n      </list>\n    </option>\n  </component>\n  <component name=\"RunManager\">\n    <configuration name=\"stackoverflow-python-spider\" type=\"PythonConfigurationType\" factoryName=\"Python\" temporary=\"true\">\n      <module name=\"stackoverflow\" />\n      <option name=\"INTERPRETER_OPTIONS\" value=\"\" />\n      <option name=\"PARENT_ENVS\" value=\"true\" />\n      <envs>\n        <env name=\"PYTHONUNBUFFERED\" value=\"1\" />\n      </envs>\n      <option name=\"SDK_HOME\" value=\"$USER_HOME$/PycharmProjects/test/venv/bin/python\" />\n      <option name=\"WORKING_DIRECTORY\" value=\"$PROJECT_DIR$/stackoverflow/spiders\" />\n      <option name=\"IS_MODULE_SDK\" value=\"false\" />\n      <option name=\"ADD_CONTENT_ROOTS\" value=\"true\" />\n      <option name=\"ADD_SOURCE_ROOTS\" value=\"true\" />\n      <option name=\"SCRIPT_NAME\" value=\"$PROJECT_DIR$/stackoverflow/spiders/stackoverflow-python-spider.py\" />\n      <option name=\"PARAMETERS\" value=\"\" />\n      <option name=\"SHOW_COMMAND_LINE\" value=\"false\" />\n      <option name=\"EMULATE_TERMINAL\" value=\"false\" />\n      <option name=\"MODULE_MODE\" value=\"false\" />\n      <option name=\"REDIRECT_INPUT\" value=\"false\" />\n      <option name=\"INPUT_FILE\" value=\"\" />\n      <method v=\"2\" />\n    </configuration>\n    <recent_temporary>\n      <list>\n        <item itemvalue=\"Python.stackoverflow-python-spider\" />\n      </list>\n    </recent_temporary>\n  </component>\n  <component name=\"SvnConfiguration\">\n    <configuration />\n  </component>\n  <component name=\"TaskManager\">\n    <task active=\"true\" id=\"Default\" summary=\"Default task\">\n      <changelist id=\"d727a472-97fb-4747-a4bb-38b0e47efab5\" name=\"Default Changelist\" comment=\"\" />\n      <created>1571212815240</created>\n      <option name=\"number\" value=\"Default\" />\n      <option name=\"presentableId\" value=\"Default\" />\n      <updated>1571212815240</updated>\n    </task>\n    <servers />\n  </component>\n  <component name=\"Vcs.Log.Tabs.Properties\">\n    <option name=\"TAB_STATES\">\n      <map>\n        <entry key=\"MAIN\">\n          <value>\n            <State>\n              <option name=\"COLUMN_ORDER\" />\n            </State>\n          </value>\n        </entry>\n      </map>\n    </option>\n  </component>\n</project>"
  },
  {
    "path": "stackoverflow/scrapy.cfg",
    "content": "# Automatically created by: scrapy startproject\n#\n# For more information about the [deploy] section see:\n# https://scrapyd.readthedocs.io/en/latest/deploy.html\n\n[settings]\ndefault = stackoverflow.settings\n\n[deploy]\n#url = http://localhost:6800/\nproject = stackoverflow\n"
  },
  {
    "path": "stackoverflow/stackoverflow/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/stackoverflow/items.py",
    "content": "# -*- coding: utf-8 -*-\n\n# Define here the models for your scraped items\n#\n# See documentation in:\n# https://doc.scrapy.org/en/latest/topics/items.html\n\nimport scrapy\n\nclass StackoverflowPythonItem(scrapy.Item):\n    _id = scrapy.Field()\n    questions = scrapy.Field()\n    votes = scrapy.Field()\n    answers = scrapy.Field()\n    views = scrapy.Field()\n    links = scrapy.Field()\n\n"
  },
  {
    "path": "stackoverflow/stackoverflow/middlewares/StackoverflowDownloaderMiddleware.py",
    "content": "from scrapy.downloadermiddlewares.httpproxy import HttpProxyMiddleware\n\n\nclass HttpProxy(HttpProxyMiddleware):\n\n    @staticmethod\n    def proxy_shadowsocks():\n        proxy = \"http://127.0.0.1:1080\"\n        return proxy\n"
  },
  {
    "path": "stackoverflow/stackoverflow/middlewares/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/stackoverflow/middlewares.py",
    "content": "# -*- coding: utf-8 -*-\n\n# Define here the models for your spider middleware\n#\n# See documentation in:\n# https://doc.scrapy.org/en/latest/topics/spider-middleware.html\n\nfrom scrapy import signals\n\n\nclass StackoverflowSpiderMiddleware(object):\n    # Not all methods need to be defined. If a method is not defined,\n    # scrapy acts as if the spider middleware does not modify the\n    # passed objects.\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        # This method is used by Scrapy to create your spiders.\n        s = cls()\n        crawler.signals.connect(s.spider_opened, signal=signals.spider_opened)\n        return s\n\n    def process_spider_input(self, response, spider):\n        # Called for each response that goes through the spider\n        # middleware and into the spider.\n\n        # Should return None or raise an exception.\n        return None\n\n    def process_spider_output(self, response, result, spider):\n        # Called with the results returned from the Spider, after\n        # it has processed the response.\n\n        # Must return an iterable of Request, dict or Item objects.\n        for i in result:\n            yield i\n\n    def process_spider_exception(self, response, exception, spider):\n        # Called when a spider or process_spider_input() method\n        # (from other spider middleware) raises an exception.\n\n        # Should return either None or an iterable of Response, dict\n        # or Item objects.\n        pass\n\n    def process_start_requests(self, start_requests, spider):\n        # Called with the start requests of the spider, and works\n        # similarly to the process_spider_output() method, except\n        # that it doesn’t have a response associated.\n\n        # Must return only requests (not items).\n        for r in start_requests:\n            yield r\n\n    def spider_opened(self, spider):\n        spider.logger.info('Spider opened: %s' % spider.name)\n\n\nclass StackoverflowDownloaderMiddleware(object):\n    # Not all methods need to be defined. If a method is not defined,\n    # scrapy acts as if the downloader middleware does not modify the\n    # passed objects.\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        # This method is used by Scrapy to create your spiders.\n        s = cls()\n        crawler.signals.connect(s.spider_opened, signal=signals.spider_opened)\n        return s\n\n    def process_request(self, request, spider):\n        # Called for each request that goes through the downloader\n        # middleware.\n\n        # Must either:\n        # - return None: continue processing this request\n        # - or return a Response object\n        # - or return a Request object\n        # - or raise IgnoreRequest: process_exception() methods of\n        #   installed downloader middleware will be called\n        return None\n\n    def process_response(self, request, response, spider):\n        # Called with the response returned from the downloader.\n\n        # Must either;\n        # - return a Response object\n        # - return a Request object\n        # - or raise IgnoreRequest\n        return response\n\n    def process_exception(self, request, exception, spider):\n        # Called when a download handler or a process_request()\n        # (from other downloader middleware) raises an exception.\n\n        # Must either:\n        # - return None: continue processing this exception\n        # - return a Response object: stops process_exception() chain\n        # - return a Request object: stops process_exception() chain\n        pass\n\n    def spider_opened(self, spider):\n        spider.logger.info('Spider opened: %s' % spider.name)\n"
  },
  {
    "path": "stackoverflow/stackoverflow/pipelines.py",
    "content": "# -*- coding: utf-8 -*-\n\n# Define your item pipelines here\n#\n# Don't forget to add your pipeline to the ITEM_PIPELINES setting\n# See: https://doc.scrapy.org/en/latest/topics/item-pipeline.html\nimport pymongo\n\nclass StackoverflowPipeline(object):\n    def __init__(self):\n        self.connection = pymongo.MongoClient('68.183.180.71', 27017)\n        self.db = self.connection.scrapy\n        self.collection = self.db.stackoverflow\n\n    def process_item(self, item, spider):\n        if not self.connection or not item:\n            return\n        self.collection.save(item)\n\n    def __del__(self):\n        if self.connection:\n            self.connection.close()\n"
  },
  {
    "path": "stackoverflow/stackoverflow/requirement.txt",
    "content": "pymongo==3.9.0\nredis==3.3.11\nScrapy==1.7.4\nscrapy-redis==0.6.8\nlxml==4.4.1\nparsel==1.5.2\n\n\n\n"
  },
  {
    "path": "stackoverflow/stackoverflow/settings.py",
    "content": "# -*- coding: utf-8 -*-\n\n# Scrapy settings for stackoverflow project\n#\n# For simplicity, this file contains only settings considered important or\n# commonly used. You can find more settings consulting the documentation:\n#\n#     https://doc.scrapy.org/en/latest/topics/settings.html\n#     https://doc.scrapy.org/en/latest/topics/downloader-middleware.html\n#     https://doc.scrapy.org/en/latest/topics/spider-middleware.html\n\nBOT_NAME = 'stackoverflow'\n\nSPIDER_MODULES = ['stackoverflow.spiders']\nNEWSPIDER_MODULE = 'stackoverflow.spiders'\n\n\n# Crawl responsibly by identifying yourself (and your website) on the user-agent\nUSER_AGENT = 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Ubuntu Chromium/73.0.3683.86 Chrome/73.0.3683.86 Safari/537.36'\n\n# Obey robots.txt rules\nROBOTSTXT_OBEY = True\n\n# Configure maximum concurrent requests performed by Scrapy (default: 16)\n#CONCURRENT_REQUESTS = 32\n\n# Configure a delay for requests for the same website (default: 0)\n# See https://doc.scrapy.org/en/latest/topics/settings.html#download-delay\n# See also autothrottle settings and docs\nDOWNLOAD_DELAY = 1\n# The download delay setting will honor only one of:\n#CONCURRENT_REQUESTS_PER_DOMAIN = 16\n#CONCURRENT_REQUESTS_PER_IP = 16\n\n# Disable cookies (enabled by default)\n#COOKIES_ENABLED = False\n\n# Disable Telnet Console (enabled by default)\n#TELNETCONSOLE_ENABLED = False\n\n# Override the default request headers:\n#DEFAULT_REQUEST_HEADERS = {\n#   'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',\n#   'Accept-Language': 'en',\n#}\n\n# Enable or disable spider middlewares\n# See https://doc.scrapy.org/en/latest/topics/spider-middleware.html\n#SPIDER_MIDDLEWARES = {\n#    'stackoverflow.middlewares.StackoverflowSpiderMiddleware': 543,\n#}\n\n# Enable or disable downloader middlewares\n# See https://doc.scrapy.org/en/latest/topics/downloader-middleware.html\nDOWNLOADER_MIDDLEWARES = {\n   'stackoverflow.middlewares.StackoverflowDownloaderMiddleware.HttpProxy': 543,\n}\n\n# Enable or disable extensions\n# See https://doc.scrapy.org/en/latest/topics/extensions.html\n#EXTENSIONS = {\n#    'scrapy.extensions.telnet.TelnetConsole': None,\n#}\n\n# Configure item pipelines\n# See https://doc.scrapy.org/en/latest/topics/item-pipeline.html\nITEM_PIPELINES = {\n   'stackoverflow.pipelines.StackoverflowPipeline': 300,\n}\n\n# Enable and configure the AutoThrottle extension (disabled by default)\n# See https://doc.scrapy.org/en/latest/topics/autothrottle.html\n#AUTOTHROTTLE_ENABLED = True\n# The initial download delay\n#AUTOTHROTTLE_START_DELAY = 5\n# The maximum download delay to be set in case of high latencies\n#AUTOTHROTTLE_MAX_DELAY = 60\n# The average number of requests Scrapy should be sending in parallel to\n# each remote server\n#AUTOTHROTTLE_TARGET_CONCURRENCY = 1.0\n# Enable showing throttling stats for every response received:\n#AUTOTHROTTLE_DEBUG = False\n\n# Enable and configure HTTP caching (disabled by default)\n# See https://doc.scrapy.org/en/latest/topics/downloader-middleware.html#httpcache-middleware-settings\n#HTTPCACHE_ENABLED = True\n#HTTPCACHE_EXPIRATION_SECS = 0\n#HTTPCACHE_DIR = 'httpcache'\n#HTTPCACHE_IGNORE_HTTP_CODES = []\n#HTTPCACHE_STORAGE = 'scrapy.extensions.httpcache.FilesystemCacheStorage'\n\n\n# 调度器改为 scrapy_redis\nSCHEDULER = 'scrapy_redis.scheduler.Scheduler'\n# redis 去重\nDUPEFILTER_CLASS = \"scrapy_redis.dupefilter.RFPDupeFilter\"\n# redis服务器地址\nREDIS_HOST = '68.183.180.0'\nREDIS_PORT = 6379\n\n\n\n\n\n\n"
  },
  {
    "path": "stackoverflow/stackoverflow/spiders/__init__.py",
    "content": "# This package will contain the spiders of your Scrapy project\n#\n# Please refer to the documentation for information on how to create and manage\n# your spiders.\n"
  },
  {
    "path": "stackoverflow/stackoverflow/spiders/stackoverflow-python-spider.py",
    "content": "import scrapy\nfrom stackoverflow.items import StackoverflowPythonItem\n\nclass StackoverflowPythonSpider(scrapy.Spider):\n\n    name = \"stackoverflow-python\"\n\n    def start_requests(self):\n        urls = []\n        _url = 'https://stackoverflow.com/questions/tagged/python?tab=votes&page={}&pagesize=15'\n\n        for page in range(1, 84322):\n            urls.append(_url.format(page))\n\n        for url in urls:\n            yield scrapy.Request(url=url, callback=self.parse)\n\n    def parse(self, response):\n        question_list = response.xpath('//*[@id=\"questions\"]')\n\n        for question in question_list.xpath('./div'):\n            item = StackoverflowPythonItem()\n            item['_id'] = question.attrib['id']\n            item['questions'] = question.xpath('div[2]/h3/a/text()').extract()\n            item['votes'] = question.xpath(\n                    'div[1]/div[1]/div[1]/div[1]/span/strong/text()').extract()\n            item['answers'] = question.xpath(\n                    'div[1]/div[1]/div[2]/strong/text()').extract()\n            item['views'] = question.xpath('div[1]/div[2]/@title').extract()\n            item['links'] = question.xpath('div[2]/h3/a/@href').extract()\n            yield item\n\n\n\n\n"
  },
  {
    "path": "stackoverflow/venv/bin/activate",
    "content": "# This file must be used with \"source bin/activate\" *from bash*\n# you cannot run it directly\n\ndeactivate () {\n    # reset old environment variables\n    if [ -n \"${_OLD_VIRTUAL_PATH:-}\" ] ; then\n        PATH=\"${_OLD_VIRTUAL_PATH:-}\"\n        export PATH\n        unset _OLD_VIRTUAL_PATH\n    fi\n    if [ -n \"${_OLD_VIRTUAL_PYTHONHOME:-}\" ] ; then\n        PYTHONHOME=\"${_OLD_VIRTUAL_PYTHONHOME:-}\"\n        export PYTHONHOME\n        unset _OLD_VIRTUAL_PYTHONHOME\n    fi\n\n    # This should detect bash and zsh, which have a hash command that must\n    # be called to get it to forget past commands.  Without forgetting\n    # past commands the $PATH changes we made may not be respected\n    if [ -n \"${BASH:-}\" -o -n \"${ZSH_VERSION:-}\" ] ; then\n        hash -r\n    fi\n\n    if [ -n \"${_OLD_VIRTUAL_PS1:-}\" ] ; then\n        PS1=\"${_OLD_VIRTUAL_PS1:-}\"\n        export PS1\n        unset _OLD_VIRTUAL_PS1\n    fi\n\n    unset VIRTUAL_ENV\n    if [ ! \"$1\" = \"nondestructive\" ] ; then\n    # Self destruct!\n        unset -f deactivate\n    fi\n}\n\n# unset irrelevant variables\ndeactivate nondestructive\n\nVIRTUAL_ENV=\"/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv\"\nexport VIRTUAL_ENV\n\n_OLD_VIRTUAL_PATH=\"$PATH\"\nPATH=\"$VIRTUAL_ENV/bin:$PATH\"\nexport PATH\n\n# unset PYTHONHOME if set\n# this will fail if PYTHONHOME is set to the empty string (which is bad anyway)\n# could use `if (set -u; : $PYTHONHOME) ;` in bash\nif [ -n \"${PYTHONHOME:-}\" ] ; then\n    _OLD_VIRTUAL_PYTHONHOME=\"${PYTHONHOME:-}\"\n    unset PYTHONHOME\nfi\n\nif [ -z \"${VIRTUAL_ENV_DISABLE_PROMPT:-}\" ] ; then\n    _OLD_VIRTUAL_PS1=\"${PS1:-}\"\n    if [ \"x(venv) \" != x ] ; then\n\tPS1=\"(venv) ${PS1:-}\"\n    else\n    if [ \"`basename \\\"$VIRTUAL_ENV\\\"`\" = \"__\" ] ; then\n        # special case for Aspen magic directories\n        # see http://www.zetadev.com/software/aspen/\n        PS1=\"[`basename \\`dirname \\\"$VIRTUAL_ENV\\\"\\``] $PS1\"\n    else\n        PS1=\"(`basename \\\"$VIRTUAL_ENV\\\"`)$PS1\"\n    fi\n    fi\n    export PS1\nfi\n\n# This should detect bash and zsh, which have a hash command that must\n# be called to get it to forget past commands.  Without forgetting\n# past commands the $PATH changes we made may not be respected\nif [ -n \"${BASH:-}\" -o -n \"${ZSH_VERSION:-}\" ] ; then\n    hash -r\nfi\n"
  },
  {
    "path": "stackoverflow/venv/bin/activate.csh",
    "content": "# This file must be used with \"source bin/activate.csh\" *from csh*.\n# You cannot run it directly.\n# Created by Davide Di Blasi <davidedb@gmail.com>.\n# Ported to Python 3.3 venv by Andrew Svetlov <andrew.svetlov@gmail.com>\n\nalias deactivate 'test $?_OLD_VIRTUAL_PATH != 0 && setenv PATH \"$_OLD_VIRTUAL_PATH\" && unset _OLD_VIRTUAL_PATH; rehash; test $?_OLD_VIRTUAL_PROMPT != 0 && set prompt=\"$_OLD_VIRTUAL_PROMPT\" && unset _OLD_VIRTUAL_PROMPT; unsetenv VIRTUAL_ENV; test \"\\!:*\" != \"nondestructive\" && unalias deactivate'\n\n# Unset irrelevant variables.\ndeactivate nondestructive\n\nsetenv VIRTUAL_ENV \"/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv\"\n\nset _OLD_VIRTUAL_PATH=\"$PATH\"\nsetenv PATH \"$VIRTUAL_ENV/bin:$PATH\"\n\n\nset _OLD_VIRTUAL_PROMPT=\"$prompt\"\n\nif (! \"$?VIRTUAL_ENV_DISABLE_PROMPT\") then\n    if (\"venv\" != \"\") then\n        set env_name = \"venv\"\n    else\n        if (`basename \"VIRTUAL_ENV\"` == \"__\") then\n            # special case for Aspen magic directories\n            # see http://www.zetadev.com/software/aspen/\n            set env_name = `basename \\`dirname \"$VIRTUAL_ENV\"\\``\n        else\n            set env_name = `basename \"$VIRTUAL_ENV\"`\n        endif\n    endif\n    set prompt = \"[$env_name] $prompt\"\n    unset env_name\nendif\n\nalias pydoc python -m pydoc\n\nrehash\n"
  },
  {
    "path": "stackoverflow/venv/bin/activate.fish",
    "content": "# This file must be used with \". bin/activate.fish\" *from fish* (http://fishshell.org)\n# you cannot run it directly\n\nfunction deactivate  -d \"Exit virtualenv and return to normal shell environment\"\n    # reset old environment variables\n    if test -n \"$_OLD_VIRTUAL_PATH\"\n        set -gx PATH $_OLD_VIRTUAL_PATH\n        set -e _OLD_VIRTUAL_PATH\n    end\n    if test -n \"$_OLD_VIRTUAL_PYTHONHOME\"\n        set -gx PYTHONHOME $_OLD_VIRTUAL_PYTHONHOME\n        set -e _OLD_VIRTUAL_PYTHONHOME\n    end\n\n    if test -n \"$_OLD_FISH_PROMPT_OVERRIDE\"\n        functions -e fish_prompt\n        set -e _OLD_FISH_PROMPT_OVERRIDE\n        functions -c _old_fish_prompt fish_prompt\n        functions -e _old_fish_prompt\n    end\n\n    set -e VIRTUAL_ENV\n    if test \"$argv[1]\" != \"nondestructive\"\n        # Self destruct!\n        functions -e deactivate\n    end\nend\n\n# unset irrelevant variables\ndeactivate nondestructive\n\nset -gx VIRTUAL_ENV \"/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv\"\n\nset -gx _OLD_VIRTUAL_PATH $PATH\nset -gx PATH \"$VIRTUAL_ENV/bin\" $PATH\n\n# unset PYTHONHOME if set\nif set -q PYTHONHOME\n    set -gx _OLD_VIRTUAL_PYTHONHOME $PYTHONHOME\n    set -e PYTHONHOME\nend\n\nif test -z \"$VIRTUAL_ENV_DISABLE_PROMPT\"\n    # fish uses a function instead of an env var to generate the prompt.\n\n    # save the current fish_prompt function as the function _old_fish_prompt\n    functions -c fish_prompt _old_fish_prompt\n\n    # with the original prompt function renamed, we can override with our own.\n    function fish_prompt\n        # Save the return status of the last command\n        set -l old_status $status\n\n        # Prompt override?\n        if test -n \"(venv) \"            \n            printf \"%s%s\" \"(venv) \" (set_color normal)\n        else\n            # ...Otherwise, prepend env\n            set -l _checkbase (basename \"$VIRTUAL_ENV\")\n            if test $_checkbase = \"__\"\n                # special case for Aspen magic directories\n                # see http://www.zetadev.com/software/aspen/\n                printf \"%s[%s]%s \" (set_color -b blue white) (basename (dirname \"$VIRTUAL_ENV\")) (set_color normal)\n            else\n                printf \"%s(%s)%s\" (set_color -b blue white) (basename \"$VIRTUAL_ENV\") (set_color normal)\n            end\n        end\n\n        # Restore the return status of the previous command.\n        echo \"exit $old_status\" | .\n        _old_fish_prompt\n    end\n\n    set -gx _OLD_FISH_PROMPT_OVERRIDE \"$VIRTUAL_ENV\"\nend\n"
  },
  {
    "path": "stackoverflow/venv/bin/automat-visualize",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# -*- coding: utf-8 -*-\nimport re\nimport sys\n\nfrom automat._visualize import tool\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(tool())\n"
  },
  {
    "path": "stackoverflow/venv/bin/cftp",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# -*- coding: utf-8 -*-\nimport re\nimport sys\n\nfrom twisted.conch.scripts.cftp import run\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(run())\n"
  },
  {
    "path": "stackoverflow/venv/bin/ckeygen",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# -*- coding: utf-8 -*-\nimport re\nimport sys\n\nfrom twisted.conch.scripts.ckeygen import run\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(run())\n"
  },
  {
    "path": "stackoverflow/venv/bin/conch",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# -*- coding: utf-8 -*-\nimport re\nimport sys\n\nfrom twisted.conch.scripts.conch import run\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(run())\n"
  },
  {
    "path": "stackoverflow/venv/bin/easy_install",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# EASY-INSTALL-ENTRY-SCRIPT: 'setuptools==40.8.0','console_scripts','easy_install'\n__requires__ = 'setuptools==40.8.0'\nimport re\nimport sys\nfrom pkg_resources import load_entry_point\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(\n        load_entry_point('setuptools==40.8.0', 'console_scripts', 'easy_install')()\n    )\n"
  },
  {
    "path": "stackoverflow/venv/bin/easy_install-3.6",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# EASY-INSTALL-ENTRY-SCRIPT: 'setuptools==40.8.0','console_scripts','easy_install-3.6'\n__requires__ = 'setuptools==40.8.0'\nimport re\nimport sys\nfrom pkg_resources import load_entry_point\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(\n        load_entry_point('setuptools==40.8.0', 'console_scripts', 'easy_install-3.6')()\n    )\n"
  },
  {
    "path": "stackoverflow/venv/bin/mailmail",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# -*- coding: utf-8 -*-\nimport re\nimport sys\n\nfrom twisted.mail.scripts.mailmail import run\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(run())\n"
  },
  {
    "path": "stackoverflow/venv/bin/pip",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# EASY-INSTALL-ENTRY-SCRIPT: 'pip==19.0.3','console_scripts','pip'\n__requires__ = 'pip==19.0.3'\nimport re\nimport sys\nfrom pkg_resources import load_entry_point\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(\n        load_entry_point('pip==19.0.3', 'console_scripts', 'pip')()\n    )\n"
  },
  {
    "path": "stackoverflow/venv/bin/pip3",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# EASY-INSTALL-ENTRY-SCRIPT: 'pip==19.0.3','console_scripts','pip3'\n__requires__ = 'pip==19.0.3'\nimport re\nimport sys\nfrom pkg_resources import load_entry_point\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(\n        load_entry_point('pip==19.0.3', 'console_scripts', 'pip3')()\n    )\n"
  },
  {
    "path": "stackoverflow/venv/bin/pip3.6",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# EASY-INSTALL-ENTRY-SCRIPT: 'pip==19.0.3','console_scripts','pip3.6'\n__requires__ = 'pip==19.0.3'\nimport re\nimport sys\nfrom pkg_resources import load_entry_point\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(\n        load_entry_point('pip==19.0.3', 'console_scripts', 'pip3.6')()\n    )\n"
  },
  {
    "path": "stackoverflow/venv/bin/pyhtmlizer",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# -*- coding: utf-8 -*-\nimport re\nimport sys\n\nfrom twisted.scripts.htmlizer import run\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(run())\n"
  },
  {
    "path": "stackoverflow/venv/bin/scrapy",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# -*- coding: utf-8 -*-\nimport re\nimport sys\n\nfrom scrapy.cmdline import execute\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(execute())\n"
  },
  {
    "path": "stackoverflow/venv/bin/tkconch",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# -*- coding: utf-8 -*-\nimport re\nimport sys\n\nfrom twisted.conch.scripts.tkconch import run\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(run())\n"
  },
  {
    "path": "stackoverflow/venv/bin/trial",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# -*- coding: utf-8 -*-\nimport re\nimport sys\n\nfrom twisted.scripts.trial import run\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(run())\n"
  },
  {
    "path": "stackoverflow/venv/bin/twist",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# -*- coding: utf-8 -*-\nimport re\nimport sys\n\nfrom twisted.application.twist._twist import Twist\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(Twist.main())\n"
  },
  {
    "path": "stackoverflow/venv/bin/twistd",
    "content": "#!/home/wistbean/githubproject/learn_python3_spider/stackoverflow/venv/bin/python\n# -*- coding: utf-8 -*-\nimport re\nimport sys\n\nfrom twisted.scripts.twistd import run\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(run())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Automat-0.8.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Automat-0.8.0.dist-info/LICENSE",
    "content": "Copyright (c) 2014\nRackspace\n\nPermission is hereby granted, free of charge, to any person obtaining\na copy of this software and associated documentation files (the\n\"Software\"), to deal in the Software without restriction, including\nwithout limitation the rights to use, copy, modify, merge, publish,\ndistribute, sublicense, and/or sell copies of the Software, and to\npermit persons to whom the Software is furnished to do so, subject to\nthe following conditions:\n\nThe above copyright notice and this permission notice shall be\nincluded in all copies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND,\nEXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND\nNONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE\nLIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION\nOF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION\nWITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Automat-0.8.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: Automat\nVersion: 0.8.0\nSummary: Self-service finite-state machines for the programmer on the go.\nHome-page: https://github.com/glyph/Automat\nAuthor: Glyph\nAuthor-email: glyph@twistedmatrix.com\nLicense: MIT\nKeywords: fsm finite state machine automata\nPlatform: UNKNOWN\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: MIT License\nClassifier: Operating System :: OS Independent\nClassifier: Programming Language :: Python\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nClassifier: Programming Language :: Python :: 3.8\nRequires-Dist: attrs (>=16.1.0)\nRequires-Dist: six\nProvides-Extra: visualize\nRequires-Dist: graphviz (>0.5.1) ; extra == 'visualize'\nRequires-Dist: Twisted (>=16.1.1) ; extra == 'visualize'\n\nAutomat\n=======\n\n\n.. image:: https://readthedocs.org/projects/automat/badge/?version=latest\n   :target: http://automat.readthedocs.io/en/latest/\n   :alt: Documentation Status\n\n\n.. image:: https://travis-ci.org/glyph/automat.svg?branch=master\n   :target: https://travis-ci.org/glyph/automat\n   :alt: Build Status\n\n\n.. image:: https://coveralls.io/repos/glyph/automat/badge.png\n   :target: https://coveralls.io/r/glyph/automat\n   :alt: Coverage Status\n\n\nSelf-service finite-state machines for the programmer on the go.\n----------------------------------------------------------------\n\nAutomat is a library for concise, idiomatic Python expression of finite-state\nautomata (particularly deterministic finite-state transducers).\n\nRead more here, or on `Read the Docs <https://automat.readthedocs.io/>`_\\ , or watch the following videos for an overview and presentation\n\nOverview and presentation by **Glyph Lefkowitz** at the first talk of the first Pyninsula meetup, on February 21st, 2017:\n\n.. image:: https://img.youtube.com/vi/0wOZBpD1VVk/0.jpg\n   :target: https://www.youtube.com/watch?v=0wOZBpD1VVk\n   :alt: Glyph Lefkowitz - Automat - Pyninsula #0\n\n\nPresentation by **Clinton Roy** at PyCon Australia, on August 6th 2017:\n\n.. image:: https://img.youtube.com/vi/TedUKXhu9kE/0.jpg\n   :target: https://www.youtube.com/watch?v=TedUKXhu9kE\n   :alt: Clinton Roy - State Machines - Pycon Australia 2017\n\n\nWhy use state machines?\n^^^^^^^^^^^^^^^^^^^^^^^\n\nSometimes you have to create an object whose behavior varies with its state,\nbut still wishes to present a consistent interface to its callers.\n\nFor example, let's say you're writing the software for a coffee machine.  It\nhas a lid that can be opened or closed, a chamber for water, a chamber for\ncoffee beans, and a button for \"brew\".\n\nThere are a number of possible states for the coffee machine.  It might or\nmight not have water.  It might or might not have beans.  The lid might be open\nor closed.  The \"brew\" button should only actually attempt to brew coffee in\none of these configurations, and the \"open lid\" button should only work if the\ncoffee is not, in fact, brewing.\n\nWith diligence and attention to detail, you can implement this correctly using\na collection of attributes on an object; ``has_water``\\ , ``has_beans``\\ ,\n``is_lid_open`` and so on.  However, you have to keep all these attributes\nconsistent.  As the coffee maker becomes more complex - perhaps you add an\nadditional chamber for flavorings so you can make hazelnut coffee, for\nexample - you have to keep adding more and more checks and more and more\nreasoning about which combinations of states are allowed.\n\nRather than adding tedious 'if' checks to every single method to make sure that\neach of these flags are exactly what you expect, you can use a state machine to\nensure that if your code runs at all, it will be run with all the required\nvalues initialized, because they have to be called in the order you declare\nthem.\n\nYou can read about state machines and their advantages for Python programmers\nin considerably more detail\n`in this excellent series of articles from ClusterHQ <https://clusterhq.com/blog/what-is-a-state-machine/>`_.\n\nWhat makes Automat different?\n^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n\nThere are\n`dozens of libraries on PyPI implementing state machines <https://pypi.org/search/?q=finite+state+machine>`_.\nSo it behooves me to say why yet another one would be a good idea.\n\nAutomat is designed around this principle: while organizing your code around\nstate machines is a good idea, your callers don't, and shouldn't have to, care\nthat you've done so.  In Python, the \"input\" to a stateful system is a method\ncall; the \"output\" may be a method call, if you need to invoke a side effect,\nor a return value, if you are just performing a computation in memory.  Most\nother state-machine libraries require you to explicitly create an input object,\nprovide that object to a generic \"input\" method, and then receive results,\nsometimes in terms of that library's interfaces and sometimes in terms of\nclasses you define yourself.\n\nFor example, a snippet of the coffee-machine example above might be implemented\nas follows in naive Python:\n\n.. code-block:: python\n\n   class CoffeeMachine(object):\n       def brew_button(self):\n           if self.has_water and self.has_beans and not self.is_lid_open:\n               self.heat_the_heating_element()\n               # ...\n\nWith Automat, you'd create a class with a ``MethodicalMachine`` attribute:\n\n.. code-block:: python\n\n   from automat import MethodicalMachine\n\n   class CoffeeBrewer(object):\n       _machine = MethodicalMachine()\n\nand then you would break the above logic into two pieces - the ``brew_button``\n*input*\\ , declared like so:\n\n.. code-block:: python\n\n       @_machine.input()\n       def brew_button(self):\n           \"The user pressed the 'brew' button.\"\n\nIt wouldn't do any good to declare a method *body* on this, however, because\ninput methods don't actually execute their bodies when called; doing actual\nwork is the *output*\\ 's job:\n\n.. code-block:: python\n\n       @_machine.output()\n       def _heat_the_heating_element(self):\n           \"Heat up the heating element, which should cause coffee to happen.\"\n           self._heating_element.turn_on()\n\nAs well as a couple of *states* - and for simplicity's sake let's say that the\nonly two states are ``have_beans`` and ``dont_have_beans``\\ :\n\n.. code-block:: python\n\n       @_machine.state()\n       def have_beans(self):\n           \"In this state, you have some beans.\"\n       @_machine.state(initial=True)\n       def dont_have_beans(self):\n           \"In this state, you don't have any beans.\"\n\n``dont_have_beans`` is the ``initial`` state because ``CoffeeBrewer`` starts without beans\nin it.\n\n(And another input to put some beans in:)\n\n.. code-block:: python\n\n       @_machine.input()\n       def put_in_beans(self):\n           \"The user put in some beans.\"\n\nFinally, you hook everything together with the ``upon`` method of the functions\ndecorated with ``_machine.state``\\ :\n\n.. code-block:: python\n\n\n       # When we don't have beans, upon putting in beans, we will then have beans\n       # (and produce no output)\n       dont_have_beans.upon(put_in_beans, enter=have_beans, outputs=[])\n\n       # When we have beans, upon pressing the brew button, we will then not have\n       # beans any more (as they have been entered into the brewing chamber) and\n       # our output will be heating the heating element.\n       have_beans.upon(brew_button, enter=dont_have_beans,\n                       outputs=[_heat_the_heating_element])\n\nTo *users* of this coffee machine class though, it still looks like a POPO\n(Plain Old Python Object):\n\n.. code-block:: python\n\n   >>> coffee_machine = CoffeeMachine()\n   >>> coffee_machine.put_in_beans()\n   >>> coffee_machine.brew_button()\n\nAll of the *inputs* are provided by calling them like methods, all of the\n*outputs* are automatically invoked when they are produced according to the\noutputs specified to ``upon`` and all of the states are simply opaque tokens -\nalthough the fact that they're defined as methods like inputs and outputs\nallows you to put docstrings on them easily to document them.\n\nHow do I get the current state of a state machine?\n--------------------------------------------------\n\nDon't do that.\n\nOne major reason for having a state machine is that you want the callers of the\nstate machine to just provide the appropriate input to the machine at the\nappropriate time, and *not have to check themselves* what state the machine is\nin.  So if you are tempted to write some code like this:\n\n.. code-block:: python\n\n   if connection_state_machine.state == \"CONNECTED\":\n       connection_state_machine.send_message()\n   else:\n       print(\"not connected\")\n\nInstead, just make your calling code do this:\n\n.. code-block:: python\n\n   connection_state_machine.send_message()\n\nand then change your state machine to look like this:\n\n.. code-block:: python\n\n       @_machine.state()\n       def connected(self):\n           \"connected\"\n       @_machine.state()\n       def not_connected(self):\n           \"not connected\"\n       @_machine.input()\n       def send_message(self):\n           \"send a message\"\n       @_machine.output()\n       def _actually_send_message(self):\n           self._transport.send(b\"message\")\n       @_machine.output()\n       def _report_sending_failure(self):\n           print(\"not connected\")\n       connected.upon(send_message, enter=connected, [_actually_send_message])\n       not_connected.upon(send_message, enter=not_connected, [_report_sending_failure])\n\nso that the responsibility for knowing which state the state machine is in\nremains within the state machine itself.\n\nInput for Inputs and Output for Outputs\n---------------------------------------\n\nQuite often you want to be able to pass parameters to your methods, as well as\ninspecting their results.  For example, when you brew the coffee, you might\nexpect a cup of coffee to result, and you would like to see what kind of coffee\nit is.  And if you were to put delicious hand-roasted small-batch artisanal\nbeans into the machine, you would expect a *better* cup of coffee than if you\nwere to use mass-produced beans.  You would do this in plain old Python by\nadding a parameter, so that's how you do it in Automat as well.\n\n.. code-block:: python\n\n       @_machine.input()\n       def put_in_beans(self, beans):\n           \"The user put in some beans.\"\n\nHowever, one important difference here is that *we can't add any\nimplementation code to the input method*.  Inputs are purely a declaration of\nthe interface; the behavior must all come from outputs.  Therefore, the change\nin the state of the coffee machine must be represented as an output.  We can\nadd an output method like this:\n\n.. code-block:: python\n\n       @_machine.output()\n       def _save_beans(self, beans):\n           \"The beans are now in the machine; save them.\"\n           self._beans = beans\n\nand then connect it to the ``put_in_beans`` by changing the transition from\n``dont_have_beans`` to ``have_beans`` like so:\n\n.. code-block:: python\n\n       dont_have_beans.upon(put_in_beans, enter=have_beans,\n                            outputs=[_save_beans])\n\nNow, when you call:\n\n.. code-block:: python\n\n   coffee_machine.put_in_beans(\"real good beans\")\n\nthe machine will remember the beans for later.\n\nSo how do we get the beans back out again?  One of our outputs needs to have a\nreturn value.  It would make sense if our ``brew_button`` method returned the cup\nof coffee that it made, so we should add an output.  So, in addition to heating\nthe heating element, let's add a return value that describes the coffee.  First\na new output:\n\n.. code-block:: python\n\n       @_machine.output()\n       def _describe_coffee(self):\n           return \"A cup of coffee made with {}.\".format(self._beans)\n\nNote that we don't need to check first whether ``self._beans`` exists or not,\nbecause we can only reach this output method if the state machine says we've\ngone through a set of states that sets this attribute.\n\nNow, we need to hook up ``_describe_coffee`` to the process of brewing, so change\nthe brewing transition to:\n\n.. code-block:: python\n\n       have_beans.upon(brew_button, enter=dont_have_beans,\n                       outputs=[_heat_the_heating_element,\n                                _describe_coffee])\n\nNow, we can call it:\n\n.. code-block:: python\n\n   >>> coffee_machine.brew_button()\n   [None, 'A cup of coffee made with real good beans.']\n\nExcept... wait a second, what's that ``None`` doing there?\n\nSince every input can produce multiple outputs, in automat, the default return\nvalue from every input invocation is a ``list``.  In this case, we have both\n``_heat_the_heating_element`` and ``_describe_coffee`` outputs, so we're seeing\nboth of their return values.  However, this can be customized, with the\n``collector`` argument to ``upon``\\ ; the ``collector`` is a callable which takes an\niterable of all the outputs' return values and \"collects\" a single return value\nto return to the caller of the state machine.\n\nIn this case, we only care about the last output, so we can adjust the call to\n``upon`` like this:\n\n.. code-block:: python\n\n       have_beans.upon(brew_button, enter=dont_have_beans,\n                       outputs=[_heat_the_heating_element,\n                                _describe_coffee],\n                       collector=lambda iterable: list(iterable)[-1]\n       )\n\nAnd now, we'll get just the return value we want:\n\n.. code-block:: python\n\n   >>> coffee_machine.brew_button()\n   'A cup of coffee made with real good beans.'\n\nIf I can't get the state of the state machine, how can I save it to (a database, an API response, a file on disk...)\n--------------------------------------------------------------------------------------------------------------------\n\nThere are APIs for serializing the state machine.\n\nFirst, you have to decide on a persistent representation of each state, via the\n``serialized=`` argument to the ``MethodicalMachine.state()`` decorator.\n\nLet's take this very simple \"light switch\" state machine, which can be on or\noff, and flipped to reverse its state:\n\n.. code-block:: python\n\n   class LightSwitch(object):\n       _machine = MethodicalMachine()\n       @_machine.state(serialized=\"on\")\n       def on_state(self):\n           \"the switch is on\"\n       @_machine.state(serialized=\"off\", initial=True)\n       def off_state(self):\n           \"the switch is off\"\n       @_machine.input()\n       def flip(self):\n           \"flip the switch\"\n       on_state.upon(flip, enter=off_state, outputs=[])\n       off_state.upon(flip, enter=on_state, outputs=[])\n\nIn this case, we've chosen a serialized representation for each state via the\n``serialized`` argument.  The on state is represented by the string ``\"on\"``\\ , and\nthe off state is represented by the string ``\"off\"``.\n\nNow, let's just add an input that lets us tell if the switch is on or not.\n\n.. code-block:: python\n\n       @_machine.input()\n       def query_power(self):\n           \"return True if powered, False otherwise\"\n       @_machine.output()\n       def _is_powered(self):\n           return True\n       @_machine.output()\n       def _not_powered(self):\n           return False\n       on_state.upon(query_power, enter=on_state, outputs=[_is_powered],\n                     collector=next)\n       off_state.upon(query_power, enter=off_state, outputs=[_not_powered],\n                      collector=next)\n\nTo save the state, we have the ``MethodicalMachine.serializer()`` method.  A\nmethod decorated with ``@serializer()`` gets an extra argument injected at the\nbeginning of its argument list: the serialized identifier for the state.  In\nthis case, either ``\"on\"`` or ``\"off\"``.  Since state machine output methods can\nalso affect other state on the object, a serializer method is expected to\nreturn *all* relevant state for serialization.\n\nFor our simple light switch, such a method might look like this:\n\n.. code-block:: python\n\n       @_machine.serializer()\n       def save(self, state):\n           return {\"is-it-on\": state}\n\nSerializers can be public methods, and they can return whatever you like.  If\nnecessary, you can have different serializers - just multiple methods decorated\nwith ``@_machine.serializer()`` - for different formats; return one data-structure\nfor JSON, one for XML, one for a database row, and so on.\n\nWhen it comes time to unserialize, though, you generally want a private method,\nbecause an unserializer has to take a not-fully-initialized instance and\npopulate it with state.  It is expected to *return* the serialized machine\nstate token that was passed to the serializer, but it can take whatever\narguments you like.  Of course, in order to return that, it probably has to\ntake it somewhere in its arguments, so it will generally take whatever a paired\nserializer has returned as an argument.\n\nSo our unserializer would look like this:\n\n.. code-block:: python\n\n       @_machine.unserializer()\n       def _restore(self, blob):\n           return blob[\"is-it-on\"]\n\nGenerally you will want a classmethod deserialization constructor which you\nwrite yourself to call this, so that you know how to create an instance of your\nown object, like so:\n\n.. code-block:: python\n\n       @classmethod\n       def from_blob(cls, blob):\n           self = cls()\n           self._restore(blob)\n           return self\n\nSaving and loading our ``LightSwitch`` along with its state-machine state can now\nbe accomplished as follows:\n\n.. code-block:: python\n\n   >>> switch1 = LightSwitch()\n   >>> switch1.query_power()\n   False\n   >>> switch1.flip()\n   []\n   >>> switch1.query_power()\n   True\n   >>> blob = switch1.save()\n   >>> switch2 = LightSwitch.from_blob(blob)\n   >>> switch2.query_power()\n   True\n\nMore comprehensive (tested, working) examples are present in ``docs/examples``.\n\nGo forth and machine all the state!\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Automat-0.8.0.dist-info/RECORD",
    "content": "../../../bin/automat-visualize,sha256=VjaldkbEc5rfj7J6UEu5q63H4NX3pe_kve9ePk9txE0,283\r\nAutomat-0.8.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nAutomat-0.8.0.dist-info/LICENSE,sha256=siATAWeNCpN9k4VDgnyhNgcS6zTiPejuPzv_-9TA43Y,1053\r\nAutomat-0.8.0.dist-info/METADATA,sha256=IMGy5LioGR1j8VhvNYvnWPCGalDNx0WlqYU0ShTjOMc,17919\r\nAutomat-0.8.0.dist-info/RECORD,,\r\nAutomat-0.8.0.dist-info/WHEEL,sha256=8zNYZbwQSXoB9IfXOjPfeNwvAsALAjffgk27FqvCWbo,110\r\nAutomat-0.8.0.dist-info/entry_points.txt,sha256=i4tDM5qwy3v1KIN7ETS2XRVcHkThhkq7ZFTPuyP6BpA,63\r\nAutomat-0.8.0.dist-info/top_level.txt,sha256=vg4zAOyhP_3YCmpKZLNgFw1uMF3lC_b6TKsdz7jBSpI,8\r\nautomat/__init__.py,sha256=ec8PILBwt35xyzsstU9kx8p5ADi6KX9d1rBLZsocN_Y,169\r\nautomat/__pycache__/__init__.cpython-36.pyc,,\r\nautomat/__pycache__/_core.cpython-36.pyc,,\r\nautomat/__pycache__/_discover.cpython-36.pyc,,\r\nautomat/__pycache__/_introspection.cpython-36.pyc,,\r\nautomat/__pycache__/_methodical.cpython-36.pyc,,\r\nautomat/__pycache__/_visualize.cpython-36.pyc,,\r\nautomat/_core.py,sha256=IEtZHq3wsBZPX_VfMHMFy_uNjx1kfE11Qq-nmIXZe28,4819\r\nautomat/_discover.py,sha256=ye7NHLZkrwYsPmBpTIyJuJ-VRCmwkOUpA0is-A81z04,4367\r\nautomat/_introspection.py,sha256=i5UEGdj8lp2BnHnGeAyIwEyoN2gU1nXYg-ZPNX7oBbM,1274\r\nautomat/_methodical.py,sha256=AEWagTYaAF8PCXsYoQRYeRn07Jg5fdKDFuAlPvGYHUM,15932\r\nautomat/_test/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0\r\nautomat/_test/__pycache__/__init__.cpython-36.pyc,,\r\nautomat/_test/__pycache__/test_core.cpython-36.pyc,,\r\nautomat/_test/__pycache__/test_discover.cpython-36.pyc,,\r\nautomat/_test/__pycache__/test_methodical.cpython-36.pyc,,\r\nautomat/_test/__pycache__/test_trace.cpython-36.pyc,,\r\nautomat/_test/__pycache__/test_visualize.cpython-36.pyc,,\r\nautomat/_test/test_core.py,sha256=CDmGBQNi9Pr7ZktfBcOhBvwI7wjLLYRtWZ0P5baXONY,2833\r\nautomat/_test/test_discover.py,sha256=O9ndAdRAC8uO0uDhioz3e45EsJCF19jQZESj0RBC7ZM,21846\r\nautomat/_test/test_methodical.py,sha256=t1CAKtT1fs-FoKMQxXl4ky6_6pgpG7lGDbyQrb_vIeo,18856\r\nautomat/_test/test_trace.py,sha256=Mx1B8QgaE7QFk6blTie2j-Vx95hTV-zySnlxLalt8ek,3279\r\nautomat/_test/test_visualize.py,sha256=8ErNYxovTiDyZkYkoP1BcyEazU_s0YQ3NHdfH9OihAg,13744\r\nautomat/_visualize.py,sha256=jY8HkzaGdMoXB7LavvaneW4GdtBN6PRShl7-4OXDvss,6335\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Automat-0.8.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.33.6)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Automat-0.8.0.dist-info/entry_points.txt",
    "content": "[console_scripts]\nautomat-visualize = automat._visualize:tool\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Automat-0.8.0.dist-info/top_level.txt",
    "content": "automat\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/OpenSSL/SSL.py",
    "content": "import os\nimport socket\nfrom sys import platform\nfrom functools import wraps, partial\nfrom itertools import count, chain\nfrom weakref import WeakValueDictionary\nfrom errno import errorcode\n\nfrom cryptography.utils import deprecated\n\nfrom six import (\n    binary_type as _binary_type, integer_types as integer_types, int2byte,\n    indexbytes)\n\nfrom OpenSSL._util import (\n    UNSPECIFIED as _UNSPECIFIED,\n    exception_from_error_queue as _exception_from_error_queue,\n    ffi as _ffi,\n    lib as _lib,\n    make_assert as _make_assert,\n    native as _native,\n    path_string as _path_string,\n    text_to_bytes_and_warn as _text_to_bytes_and_warn,\n    no_zero_allocator as _no_zero_allocator,\n)\n\nfrom OpenSSL.crypto import (\n    FILETYPE_PEM, _PassphraseHelper, PKey, X509Name, X509, X509Store)\n\n__all__ = [\n    'OPENSSL_VERSION_NUMBER',\n    'SSLEAY_VERSION',\n    'SSLEAY_CFLAGS',\n    'SSLEAY_PLATFORM',\n    'SSLEAY_DIR',\n    'SSLEAY_BUILT_ON',\n    'SENT_SHUTDOWN',\n    'RECEIVED_SHUTDOWN',\n    'SSLv2_METHOD',\n    'SSLv3_METHOD',\n    'SSLv23_METHOD',\n    'TLSv1_METHOD',\n    'TLSv1_1_METHOD',\n    'TLSv1_2_METHOD',\n    'OP_NO_SSLv2',\n    'OP_NO_SSLv3',\n    'OP_NO_TLSv1',\n    'OP_NO_TLSv1_1',\n    'OP_NO_TLSv1_2',\n    'MODE_RELEASE_BUFFERS',\n    'OP_SINGLE_DH_USE',\n    'OP_SINGLE_ECDH_USE',\n    'OP_EPHEMERAL_RSA',\n    'OP_MICROSOFT_SESS_ID_BUG',\n    'OP_NETSCAPE_CHALLENGE_BUG',\n    'OP_NETSCAPE_REUSE_CIPHER_CHANGE_BUG',\n    'OP_SSLREF2_REUSE_CERT_TYPE_BUG',\n    'OP_MICROSOFT_BIG_SSLV3_BUFFER',\n    'OP_MSIE_SSLV2_RSA_PADDING',\n    'OP_SSLEAY_080_CLIENT_DH_BUG',\n    'OP_TLS_D5_BUG',\n    'OP_TLS_BLOCK_PADDING_BUG',\n    'OP_DONT_INSERT_EMPTY_FRAGMENTS',\n    'OP_CIPHER_SERVER_PREFERENCE',\n    'OP_TLS_ROLLBACK_BUG',\n    'OP_PKCS1_CHECK_1',\n    'OP_PKCS1_CHECK_2',\n    'OP_NETSCAPE_CA_DN_BUG',\n    'OP_NETSCAPE_DEMO_CIPHER_CHANGE_BUG',\n    'OP_NO_COMPRESSION',\n    'OP_NO_QUERY_MTU',\n    'OP_COOKIE_EXCHANGE',\n    'OP_NO_TICKET',\n    'OP_ALL',\n    'VERIFY_PEER',\n    'VERIFY_FAIL_IF_NO_PEER_CERT',\n    'VERIFY_CLIENT_ONCE',\n    'VERIFY_NONE',\n    'SESS_CACHE_OFF',\n    'SESS_CACHE_CLIENT',\n    'SESS_CACHE_SERVER',\n    'SESS_CACHE_BOTH',\n    'SESS_CACHE_NO_AUTO_CLEAR',\n    'SESS_CACHE_NO_INTERNAL_LOOKUP',\n    'SESS_CACHE_NO_INTERNAL_STORE',\n    'SESS_CACHE_NO_INTERNAL',\n    'SSL_ST_CONNECT',\n    'SSL_ST_ACCEPT',\n    'SSL_ST_MASK',\n    'SSL_CB_LOOP',\n    'SSL_CB_EXIT',\n    'SSL_CB_READ',\n    'SSL_CB_WRITE',\n    'SSL_CB_ALERT',\n    'SSL_CB_READ_ALERT',\n    'SSL_CB_WRITE_ALERT',\n    'SSL_CB_ACCEPT_LOOP',\n    'SSL_CB_ACCEPT_EXIT',\n    'SSL_CB_CONNECT_LOOP',\n    'SSL_CB_CONNECT_EXIT',\n    'SSL_CB_HANDSHAKE_START',\n    'SSL_CB_HANDSHAKE_DONE',\n    'Error',\n    'WantReadError',\n    'WantWriteError',\n    'WantX509LookupError',\n    'ZeroReturnError',\n    'SysCallError',\n    'SSLeay_version',\n    'Session',\n    'Context',\n    'Connection'\n]\n\ntry:\n    _buffer = buffer\nexcept NameError:\n    class _buffer(object):\n        pass\n\nOPENSSL_VERSION_NUMBER = _lib.OPENSSL_VERSION_NUMBER\nSSLEAY_VERSION = _lib.SSLEAY_VERSION\nSSLEAY_CFLAGS = _lib.SSLEAY_CFLAGS\nSSLEAY_PLATFORM = _lib.SSLEAY_PLATFORM\nSSLEAY_DIR = _lib.SSLEAY_DIR\nSSLEAY_BUILT_ON = _lib.SSLEAY_BUILT_ON\n\nSENT_SHUTDOWN = _lib.SSL_SENT_SHUTDOWN\nRECEIVED_SHUTDOWN = _lib.SSL_RECEIVED_SHUTDOWN\n\nSSLv2_METHOD = 1\nSSLv3_METHOD = 2\nSSLv23_METHOD = 3\nTLSv1_METHOD = 4\nTLSv1_1_METHOD = 5\nTLSv1_2_METHOD = 6\n\nOP_NO_SSLv2 = _lib.SSL_OP_NO_SSLv2\nOP_NO_SSLv3 = _lib.SSL_OP_NO_SSLv3\nOP_NO_TLSv1 = _lib.SSL_OP_NO_TLSv1\nOP_NO_TLSv1_1 = _lib.SSL_OP_NO_TLSv1_1\nOP_NO_TLSv1_2 = _lib.SSL_OP_NO_TLSv1_2\n\nMODE_RELEASE_BUFFERS = _lib.SSL_MODE_RELEASE_BUFFERS\n\nOP_SINGLE_DH_USE = _lib.SSL_OP_SINGLE_DH_USE\nOP_SINGLE_ECDH_USE = _lib.SSL_OP_SINGLE_ECDH_USE\nOP_EPHEMERAL_RSA = _lib.SSL_OP_EPHEMERAL_RSA\nOP_MICROSOFT_SESS_ID_BUG = _lib.SSL_OP_MICROSOFT_SESS_ID_BUG\nOP_NETSCAPE_CHALLENGE_BUG = _lib.SSL_OP_NETSCAPE_CHALLENGE_BUG\nOP_NETSCAPE_REUSE_CIPHER_CHANGE_BUG = (\n    _lib.SSL_OP_NETSCAPE_REUSE_CIPHER_CHANGE_BUG\n)\nOP_SSLREF2_REUSE_CERT_TYPE_BUG = _lib.SSL_OP_SSLREF2_REUSE_CERT_TYPE_BUG\nOP_MICROSOFT_BIG_SSLV3_BUFFER = _lib.SSL_OP_MICROSOFT_BIG_SSLV3_BUFFER\nOP_MSIE_SSLV2_RSA_PADDING = _lib.SSL_OP_MSIE_SSLV2_RSA_PADDING\nOP_SSLEAY_080_CLIENT_DH_BUG = _lib.SSL_OP_SSLEAY_080_CLIENT_DH_BUG\nOP_TLS_D5_BUG = _lib.SSL_OP_TLS_D5_BUG\nOP_TLS_BLOCK_PADDING_BUG = _lib.SSL_OP_TLS_BLOCK_PADDING_BUG\nOP_DONT_INSERT_EMPTY_FRAGMENTS = _lib.SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS\nOP_CIPHER_SERVER_PREFERENCE = _lib.SSL_OP_CIPHER_SERVER_PREFERENCE\nOP_TLS_ROLLBACK_BUG = _lib.SSL_OP_TLS_ROLLBACK_BUG\nOP_PKCS1_CHECK_1 = _lib.SSL_OP_PKCS1_CHECK_1\nOP_PKCS1_CHECK_2 = _lib.SSL_OP_PKCS1_CHECK_2\nOP_NETSCAPE_CA_DN_BUG = _lib.SSL_OP_NETSCAPE_CA_DN_BUG\nOP_NETSCAPE_DEMO_CIPHER_CHANGE_BUG = (\n    _lib.SSL_OP_NETSCAPE_DEMO_CIPHER_CHANGE_BUG\n)\nOP_NO_COMPRESSION = _lib.SSL_OP_NO_COMPRESSION\n\nOP_NO_QUERY_MTU = _lib.SSL_OP_NO_QUERY_MTU\nOP_COOKIE_EXCHANGE = _lib.SSL_OP_COOKIE_EXCHANGE\nOP_NO_TICKET = _lib.SSL_OP_NO_TICKET\n\nOP_ALL = _lib.SSL_OP_ALL\n\nVERIFY_PEER = _lib.SSL_VERIFY_PEER\nVERIFY_FAIL_IF_NO_PEER_CERT = _lib.SSL_VERIFY_FAIL_IF_NO_PEER_CERT\nVERIFY_CLIENT_ONCE = _lib.SSL_VERIFY_CLIENT_ONCE\nVERIFY_NONE = _lib.SSL_VERIFY_NONE\n\nSESS_CACHE_OFF = _lib.SSL_SESS_CACHE_OFF\nSESS_CACHE_CLIENT = _lib.SSL_SESS_CACHE_CLIENT\nSESS_CACHE_SERVER = _lib.SSL_SESS_CACHE_SERVER\nSESS_CACHE_BOTH = _lib.SSL_SESS_CACHE_BOTH\nSESS_CACHE_NO_AUTO_CLEAR = _lib.SSL_SESS_CACHE_NO_AUTO_CLEAR\nSESS_CACHE_NO_INTERNAL_LOOKUP = _lib.SSL_SESS_CACHE_NO_INTERNAL_LOOKUP\nSESS_CACHE_NO_INTERNAL_STORE = _lib.SSL_SESS_CACHE_NO_INTERNAL_STORE\nSESS_CACHE_NO_INTERNAL = _lib.SSL_SESS_CACHE_NO_INTERNAL\n\nSSL_ST_CONNECT = _lib.SSL_ST_CONNECT\nSSL_ST_ACCEPT = _lib.SSL_ST_ACCEPT\nSSL_ST_MASK = _lib.SSL_ST_MASK\nif _lib.Cryptography_HAS_SSL_ST:\n    SSL_ST_INIT = _lib.SSL_ST_INIT\n    SSL_ST_BEFORE = _lib.SSL_ST_BEFORE\n    SSL_ST_OK = _lib.SSL_ST_OK\n    SSL_ST_RENEGOTIATE = _lib.SSL_ST_RENEGOTIATE\n    __all__.extend([\n        'SSL_ST_INIT',\n        'SSL_ST_BEFORE',\n        'SSL_ST_OK',\n        'SSL_ST_RENEGOTIATE',\n    ])\n\nSSL_CB_LOOP = _lib.SSL_CB_LOOP\nSSL_CB_EXIT = _lib.SSL_CB_EXIT\nSSL_CB_READ = _lib.SSL_CB_READ\nSSL_CB_WRITE = _lib.SSL_CB_WRITE\nSSL_CB_ALERT = _lib.SSL_CB_ALERT\nSSL_CB_READ_ALERT = _lib.SSL_CB_READ_ALERT\nSSL_CB_WRITE_ALERT = _lib.SSL_CB_WRITE_ALERT\nSSL_CB_ACCEPT_LOOP = _lib.SSL_CB_ACCEPT_LOOP\nSSL_CB_ACCEPT_EXIT = _lib.SSL_CB_ACCEPT_EXIT\nSSL_CB_CONNECT_LOOP = _lib.SSL_CB_CONNECT_LOOP\nSSL_CB_CONNECT_EXIT = _lib.SSL_CB_CONNECT_EXIT\nSSL_CB_HANDSHAKE_START = _lib.SSL_CB_HANDSHAKE_START\nSSL_CB_HANDSHAKE_DONE = _lib.SSL_CB_HANDSHAKE_DONE\n\n# Taken from https://golang.org/src/crypto/x509/root_linux.go\n_CERTIFICATE_FILE_LOCATIONS = [\n    \"/etc/ssl/certs/ca-certificates.crt\",  # Debian/Ubuntu/Gentoo etc.\n    \"/etc/pki/tls/certs/ca-bundle.crt\",  # Fedora/RHEL 6\n    \"/etc/ssl/ca-bundle.pem\",  # OpenSUSE\n    \"/etc/pki/tls/cacert.pem\",  # OpenELEC\n    \"/etc/pki/ca-trust/extracted/pem/tls-ca-bundle.pem\",  # CentOS/RHEL 7\n]\n\n_CERTIFICATE_PATH_LOCATIONS = [\n    \"/etc/ssl/certs\",  # SLES10/SLES11\n]\n\n# These values are compared to output from cffi's ffi.string so they must be\n# byte strings.\n_CRYPTOGRAPHY_MANYLINUX1_CA_DIR = b\"/opt/pyca/cryptography/openssl/certs\"\n_CRYPTOGRAPHY_MANYLINUX1_CA_FILE = b\"/opt/pyca/cryptography/openssl/cert.pem\"\n\n\nclass Error(Exception):\n    \"\"\"\n    An error occurred in an `OpenSSL.SSL` API.\n    \"\"\"\n\n\n_raise_current_error = partial(_exception_from_error_queue, Error)\n_openssl_assert = _make_assert(Error)\n\n\nclass WantReadError(Error):\n    pass\n\n\nclass WantWriteError(Error):\n    pass\n\n\nclass WantX509LookupError(Error):\n    pass\n\n\nclass ZeroReturnError(Error):\n    pass\n\n\nclass SysCallError(Error):\n    pass\n\n\nclass _CallbackExceptionHelper(object):\n    \"\"\"\n    A base class for wrapper classes that allow for intelligent exception\n    handling in OpenSSL callbacks.\n\n    :ivar list _problems: Any exceptions that occurred while executing in a\n        context where they could not be raised in the normal way.  Typically\n        this is because OpenSSL has called into some Python code and requires a\n        return value.  The exceptions are saved to be raised later when it is\n        possible to do so.\n    \"\"\"\n\n    def __init__(self):\n        self._problems = []\n\n    def raise_if_problem(self):\n        \"\"\"\n        Raise an exception from the OpenSSL error queue or that was previously\n        captured whe running a callback.\n        \"\"\"\n        if self._problems:\n            try:\n                _raise_current_error()\n            except Error:\n                pass\n            raise self._problems.pop(0)\n\n\nclass _VerifyHelper(_CallbackExceptionHelper):\n    \"\"\"\n    Wrap a callback such that it can be used as a certificate verification\n    callback.\n    \"\"\"\n\n    def __init__(self, callback):\n        _CallbackExceptionHelper.__init__(self)\n\n        @wraps(callback)\n        def wrapper(ok, store_ctx):\n            x509 = _lib.X509_STORE_CTX_get_current_cert(store_ctx)\n            _lib.X509_up_ref(x509)\n            cert = X509._from_raw_x509_ptr(x509)\n            error_number = _lib.X509_STORE_CTX_get_error(store_ctx)\n            error_depth = _lib.X509_STORE_CTX_get_error_depth(store_ctx)\n\n            index = _lib.SSL_get_ex_data_X509_STORE_CTX_idx()\n            ssl = _lib.X509_STORE_CTX_get_ex_data(store_ctx, index)\n            connection = Connection._reverse_mapping[ssl]\n\n            try:\n                result = callback(\n                    connection, cert, error_number, error_depth, ok\n                )\n            except Exception as e:\n                self._problems.append(e)\n                return 0\n            else:\n                if result:\n                    _lib.X509_STORE_CTX_set_error(store_ctx, _lib.X509_V_OK)\n                    return 1\n                else:\n                    return 0\n\n        self.callback = _ffi.callback(\n            \"int (*)(int, X509_STORE_CTX *)\", wrapper)\n\n\nclass _NpnAdvertiseHelper(_CallbackExceptionHelper):\n    \"\"\"\n    Wrap a callback such that it can be used as an NPN advertisement callback.\n    \"\"\"\n\n    def __init__(self, callback):\n        _CallbackExceptionHelper.__init__(self)\n\n        @wraps(callback)\n        def wrapper(ssl, out, outlen, arg):\n            try:\n                conn = Connection._reverse_mapping[ssl]\n                protos = callback(conn)\n\n                # Join the protocols into a Python bytestring, length-prefixing\n                # each element.\n                protostr = b''.join(\n                    chain.from_iterable((int2byte(len(p)), p) for p in protos)\n                )\n\n                # Save our callback arguments on the connection object. This is\n                # done to make sure that they don't get freed before OpenSSL\n                # uses them. Then, return them appropriately in the output\n                # parameters.\n                conn._npn_advertise_callback_args = [\n                    _ffi.new(\"unsigned int *\", len(protostr)),\n                    _ffi.new(\"unsigned char[]\", protostr),\n                ]\n                outlen[0] = conn._npn_advertise_callback_args[0][0]\n                out[0] = conn._npn_advertise_callback_args[1]\n                return 0\n            except Exception as e:\n                self._problems.append(e)\n                return 2  # SSL_TLSEXT_ERR_ALERT_FATAL\n\n        self.callback = _ffi.callback(\n            \"int (*)(SSL *, const unsigned char **, unsigned int *, void *)\",\n            wrapper\n        )\n\n\nclass _NpnSelectHelper(_CallbackExceptionHelper):\n    \"\"\"\n    Wrap a callback such that it can be used as an NPN selection callback.\n    \"\"\"\n\n    def __init__(self, callback):\n        _CallbackExceptionHelper.__init__(self)\n\n        @wraps(callback)\n        def wrapper(ssl, out, outlen, in_, inlen, arg):\n            try:\n                conn = Connection._reverse_mapping[ssl]\n\n                # The string passed to us is actually made up of multiple\n                # length-prefixed bytestrings. We need to split that into a\n                # list.\n                instr = _ffi.buffer(in_, inlen)[:]\n                protolist = []\n                while instr:\n                    length = indexbytes(instr, 0)\n                    proto = instr[1:length + 1]\n                    protolist.append(proto)\n                    instr = instr[length + 1:]\n\n                # Call the callback\n                outstr = callback(conn, protolist)\n\n                # Save our callback arguments on the connection object. This is\n                # done to make sure that they don't get freed before OpenSSL\n                # uses them. Then, return them appropriately in the output\n                # parameters.\n                conn._npn_select_callback_args = [\n                    _ffi.new(\"unsigned char *\", len(outstr)),\n                    _ffi.new(\"unsigned char[]\", outstr),\n                ]\n                outlen[0] = conn._npn_select_callback_args[0][0]\n                out[0] = conn._npn_select_callback_args[1]\n                return 0\n            except Exception as e:\n                self._problems.append(e)\n                return 2  # SSL_TLSEXT_ERR_ALERT_FATAL\n\n        self.callback = _ffi.callback(\n            (\"int (*)(SSL *, unsigned char **, unsigned char *, \"\n                \"const unsigned char *, unsigned int, void *)\"),\n            wrapper\n        )\n\n\nclass _ALPNSelectHelper(_CallbackExceptionHelper):\n    \"\"\"\n    Wrap a callback such that it can be used as an ALPN selection callback.\n    \"\"\"\n\n    def __init__(self, callback):\n        _CallbackExceptionHelper.__init__(self)\n\n        @wraps(callback)\n        def wrapper(ssl, out, outlen, in_, inlen, arg):\n            try:\n                conn = Connection._reverse_mapping[ssl]\n\n                # The string passed to us is made up of multiple\n                # length-prefixed bytestrings. We need to split that into a\n                # list.\n                instr = _ffi.buffer(in_, inlen)[:]\n                protolist = []\n                while instr:\n                    encoded_len = indexbytes(instr, 0)\n                    proto = instr[1:encoded_len + 1]\n                    protolist.append(proto)\n                    instr = instr[encoded_len + 1:]\n\n                # Call the callback\n                outstr = callback(conn, protolist)\n\n                if not isinstance(outstr, _binary_type):\n                    raise TypeError(\"ALPN callback must return a bytestring.\")\n\n                # Save our callback arguments on the connection object to make\n                # sure that they don't get freed before OpenSSL can use them.\n                # Then, return them in the appropriate output parameters.\n                conn._alpn_select_callback_args = [\n                    _ffi.new(\"unsigned char *\", len(outstr)),\n                    _ffi.new(\"unsigned char[]\", outstr),\n                ]\n                outlen[0] = conn._alpn_select_callback_args[0][0]\n                out[0] = conn._alpn_select_callback_args[1]\n                return 0\n            except Exception as e:\n                self._problems.append(e)\n                return 2  # SSL_TLSEXT_ERR_ALERT_FATAL\n\n        self.callback = _ffi.callback(\n            (\"int (*)(SSL *, unsigned char **, unsigned char *, \"\n                \"const unsigned char *, unsigned int, void *)\"),\n            wrapper\n        )\n\n\nclass _OCSPServerCallbackHelper(_CallbackExceptionHelper):\n    \"\"\"\n    Wrap a callback such that it can be used as an OCSP callback for the server\n    side.\n\n    Annoyingly, OpenSSL defines one OCSP callback but uses it in two different\n    ways. For servers, that callback is expected to retrieve some OCSP data and\n    hand it to OpenSSL, and may return only SSL_TLSEXT_ERR_OK,\n    SSL_TLSEXT_ERR_FATAL, and SSL_TLSEXT_ERR_NOACK. For clients, that callback\n    is expected to check the OCSP data, and returns a negative value on error,\n    0 if the response is not acceptable, or positive if it is. These are\n    mutually exclusive return code behaviours, and they mean that we need two\n    helpers so that we always return an appropriate error code if the user's\n    code throws an exception.\n\n    Given that we have to have two helpers anyway, these helpers are a bit more\n    helpery than most: specifically, they hide a few more of the OpenSSL\n    functions so that the user has an easier time writing these callbacks.\n\n    This helper implements the server side.\n    \"\"\"\n\n    def __init__(self, callback):\n        _CallbackExceptionHelper.__init__(self)\n\n        @wraps(callback)\n        def wrapper(ssl, cdata):\n            try:\n                conn = Connection._reverse_mapping[ssl]\n\n                # Extract the data if any was provided.\n                if cdata != _ffi.NULL:\n                    data = _ffi.from_handle(cdata)\n                else:\n                    data = None\n\n                # Call the callback.\n                ocsp_data = callback(conn, data)\n\n                if not isinstance(ocsp_data, _binary_type):\n                    raise TypeError(\"OCSP callback must return a bytestring.\")\n\n                # If the OCSP data was provided, we will pass it to OpenSSL.\n                # However, we have an early exit here: if no OCSP data was\n                # provided we will just exit out and tell OpenSSL that there\n                # is nothing to do.\n                if not ocsp_data:\n                    return 3  # SSL_TLSEXT_ERR_NOACK\n\n                # OpenSSL takes ownership of this data and expects it to have\n                # been allocated by OPENSSL_malloc.\n                ocsp_data_length = len(ocsp_data)\n                data_ptr = _lib.OPENSSL_malloc(ocsp_data_length)\n                _ffi.buffer(data_ptr, ocsp_data_length)[:] = ocsp_data\n\n                _lib.SSL_set_tlsext_status_ocsp_resp(\n                    ssl, data_ptr, ocsp_data_length\n                )\n\n                return 0\n            except Exception as e:\n                self._problems.append(e)\n                return 2  # SSL_TLSEXT_ERR_ALERT_FATAL\n\n        self.callback = _ffi.callback(\"int (*)(SSL *, void *)\", wrapper)\n\n\nclass _OCSPClientCallbackHelper(_CallbackExceptionHelper):\n    \"\"\"\n    Wrap a callback such that it can be used as an OCSP callback for the client\n    side.\n\n    Annoyingly, OpenSSL defines one OCSP callback but uses it in two different\n    ways. For servers, that callback is expected to retrieve some OCSP data and\n    hand it to OpenSSL, and may return only SSL_TLSEXT_ERR_OK,\n    SSL_TLSEXT_ERR_FATAL, and SSL_TLSEXT_ERR_NOACK. For clients, that callback\n    is expected to check the OCSP data, and returns a negative value on error,\n    0 if the response is not acceptable, or positive if it is. These are\n    mutually exclusive return code behaviours, and they mean that we need two\n    helpers so that we always return an appropriate error code if the user's\n    code throws an exception.\n\n    Given that we have to have two helpers anyway, these helpers are a bit more\n    helpery than most: specifically, they hide a few more of the OpenSSL\n    functions so that the user has an easier time writing these callbacks.\n\n    This helper implements the client side.\n    \"\"\"\n\n    def __init__(self, callback):\n        _CallbackExceptionHelper.__init__(self)\n\n        @wraps(callback)\n        def wrapper(ssl, cdata):\n            try:\n                conn = Connection._reverse_mapping[ssl]\n\n                # Extract the data if any was provided.\n                if cdata != _ffi.NULL:\n                    data = _ffi.from_handle(cdata)\n                else:\n                    data = None\n\n                # Get the OCSP data.\n                ocsp_ptr = _ffi.new(\"unsigned char **\")\n                ocsp_len = _lib.SSL_get_tlsext_status_ocsp_resp(ssl, ocsp_ptr)\n                if ocsp_len < 0:\n                    # No OCSP data.\n                    ocsp_data = b''\n                else:\n                    # Copy the OCSP data, then pass it to the callback.\n                    ocsp_data = _ffi.buffer(ocsp_ptr[0], ocsp_len)[:]\n\n                valid = callback(conn, ocsp_data, data)\n\n                # Return 1 on success or 0 on error.\n                return int(bool(valid))\n\n            except Exception as e:\n                self._problems.append(e)\n                # Return negative value if an exception is hit.\n                return -1\n\n        self.callback = _ffi.callback(\"int (*)(SSL *, void *)\", wrapper)\n\n\ndef _asFileDescriptor(obj):\n    fd = None\n    if not isinstance(obj, integer_types):\n        meth = getattr(obj, \"fileno\", None)\n        if meth is not None:\n            obj = meth()\n\n    if isinstance(obj, integer_types):\n        fd = obj\n\n    if not isinstance(fd, integer_types):\n        raise TypeError(\"argument must be an int, or have a fileno() method.\")\n    elif fd < 0:\n        raise ValueError(\n            \"file descriptor cannot be a negative integer (%i)\" % (fd,))\n\n    return fd\n\n\ndef SSLeay_version(type):\n    \"\"\"\n    Return a string describing the version of OpenSSL in use.\n\n    :param type: One of the :const:`SSLEAY_` constants defined in this module.\n    \"\"\"\n    return _ffi.string(_lib.SSLeay_version(type))\n\n\ndef _make_requires(flag, error):\n    \"\"\"\n    Builds a decorator that ensures that functions that rely on OpenSSL\n    functions that are not present in this build raise NotImplementedError,\n    rather than AttributeError coming out of cryptography.\n\n    :param flag: A cryptography flag that guards the functions, e.g.\n        ``Cryptography_HAS_NEXTPROTONEG``.\n    :param error: The string to be used in the exception if the flag is false.\n    \"\"\"\n    def _requires_decorator(func):\n        if not flag:\n            @wraps(func)\n            def explode(*args, **kwargs):\n                raise NotImplementedError(error)\n            return explode\n        else:\n            return func\n\n    return _requires_decorator\n\n\n_requires_npn = _make_requires(\n    _lib.Cryptography_HAS_NEXTPROTONEG, \"NPN not available\"\n)\n\n\n_requires_alpn = _make_requires(\n    _lib.Cryptography_HAS_ALPN, \"ALPN not available\"\n)\n\n\n_requires_sni = _make_requires(\n    _lib.Cryptography_HAS_TLSEXT_HOSTNAME, \"SNI not available\"\n)\n\n\nclass Session(object):\n    \"\"\"\n    A class representing an SSL session.  A session defines certain connection\n    parameters which may be re-used to speed up the setup of subsequent\n    connections.\n\n    .. versionadded:: 0.14\n    \"\"\"\n    pass\n\n\nclass Context(object):\n    \"\"\"\n    :class:`OpenSSL.SSL.Context` instances define the parameters for setting\n    up new SSL connections.\n\n    :param method: One of SSLv2_METHOD, SSLv3_METHOD, SSLv23_METHOD, or\n        TLSv1_METHOD.\n    \"\"\"\n    _methods = {\n        SSLv2_METHOD: \"SSLv2_method\",\n        SSLv3_METHOD: \"SSLv3_method\",\n        SSLv23_METHOD: \"SSLv23_method\",\n        TLSv1_METHOD: \"TLSv1_method\",\n        TLSv1_1_METHOD: \"TLSv1_1_method\",\n        TLSv1_2_METHOD: \"TLSv1_2_method\",\n    }\n    _methods = dict(\n        (identifier, getattr(_lib, name))\n        for (identifier, name) in _methods.items()\n        if getattr(_lib, name, None) is not None)\n\n    def __init__(self, method):\n        if not isinstance(method, integer_types):\n            raise TypeError(\"method must be an integer\")\n\n        try:\n            method_func = self._methods[method]\n        except KeyError:\n            raise ValueError(\"No such protocol\")\n\n        method_obj = method_func()\n        _openssl_assert(method_obj != _ffi.NULL)\n\n        context = _lib.SSL_CTX_new(method_obj)\n        _openssl_assert(context != _ffi.NULL)\n        context = _ffi.gc(context, _lib.SSL_CTX_free)\n\n        # If SSL_CTX_set_ecdh_auto is available then set it so the ECDH curve\n        # will be auto-selected. This function was added in 1.0.2 and made a\n        # noop in 1.1.0+ (where it is set automatically).\n        try:\n            res = _lib.SSL_CTX_set_ecdh_auto(context, 1)\n            _openssl_assert(res == 1)\n        except AttributeError:\n            pass\n\n        self._context = context\n        self._passphrase_helper = None\n        self._passphrase_callback = None\n        self._passphrase_userdata = None\n        self._verify_helper = None\n        self._verify_callback = None\n        self._info_callback = None\n        self._tlsext_servername_callback = None\n        self._app_data = None\n        self._npn_advertise_helper = None\n        self._npn_advertise_callback = None\n        self._npn_select_helper = None\n        self._npn_select_callback = None\n        self._alpn_select_helper = None\n        self._alpn_select_callback = None\n        self._ocsp_helper = None\n        self._ocsp_callback = None\n        self._ocsp_data = None\n\n        self.set_mode(_lib.SSL_MODE_ENABLE_PARTIAL_WRITE)\n\n    def load_verify_locations(self, cafile, capath=None):\n        \"\"\"\n        Let SSL know where we can find trusted certificates for the certificate\n        chain.  Note that the certificates have to be in PEM format.\n\n        If capath is passed, it must be a directory prepared using the\n        ``c_rehash`` tool included with OpenSSL.  Either, but not both, of\n        *pemfile* or *capath* may be :data:`None`.\n\n        :param cafile: In which file we can find the certificates (``bytes`` or\n            ``unicode``).\n        :param capath: In which directory we can find the certificates\n            (``bytes`` or ``unicode``).\n\n        :return: None\n        \"\"\"\n        if cafile is None:\n            cafile = _ffi.NULL\n        else:\n            cafile = _path_string(cafile)\n\n        if capath is None:\n            capath = _ffi.NULL\n        else:\n            capath = _path_string(capath)\n\n        load_result = _lib.SSL_CTX_load_verify_locations(\n            self._context, cafile, capath\n        )\n        if not load_result:\n            _raise_current_error()\n\n    def _wrap_callback(self, callback):\n        @wraps(callback)\n        def wrapper(size, verify, userdata):\n            return callback(size, verify, self._passphrase_userdata)\n        return _PassphraseHelper(\n            FILETYPE_PEM, wrapper, more_args=True, truncate=True)\n\n    def set_passwd_cb(self, callback, userdata=None):\n        \"\"\"\n        Set the passphrase callback.  This function will be called\n        when a private key with a passphrase is loaded.\n\n        :param callback: The Python callback to use.  This must accept three\n            positional arguments.  First, an integer giving the maximum length\n            of the passphrase it may return.  If the returned passphrase is\n            longer than this, it will be truncated.  Second, a boolean value\n            which will be true if the user should be prompted for the\n            passphrase twice and the callback should verify that the two values\n            supplied are equal. Third, the value given as the *userdata*\n            parameter to :meth:`set_passwd_cb`.  The *callback* must return\n            a byte string. If an error occurs, *callback* should return a false\n            value (e.g. an empty string).\n        :param userdata: (optional) A Python object which will be given as\n                         argument to the callback\n        :return: None\n        \"\"\"\n        if not callable(callback):\n            raise TypeError(\"callback must be callable\")\n\n        self._passphrase_helper = self._wrap_callback(callback)\n        self._passphrase_callback = self._passphrase_helper.callback\n        _lib.SSL_CTX_set_default_passwd_cb(\n            self._context, self._passphrase_callback)\n        self._passphrase_userdata = userdata\n\n    def set_default_verify_paths(self):\n        \"\"\"\n        Specify that the platform provided CA certificates are to be used for\n        verification purposes. This method has some caveats related to the\n        binary wheels that cryptography (pyOpenSSL's primary dependency) ships:\n\n        *   macOS will only load certificates using this method if the user has\n            the ``openssl@1.1`` `Homebrew <https://brew.sh>`_ formula installed\n            in the default location.\n        *   Windows will not work.\n        *   manylinux1 cryptography wheels will work on most common Linux\n            distributions in pyOpenSSL 17.1.0 and above.  pyOpenSSL detects the\n            manylinux1 wheel and attempts to load roots via a fallback path.\n\n        :return: None\n        \"\"\"\n        # SSL_CTX_set_default_verify_paths will attempt to load certs from\n        # both a cafile and capath that are set at compile time. However,\n        # it will first check environment variables and, if present, load\n        # those paths instead\n        set_result = _lib.SSL_CTX_set_default_verify_paths(self._context)\n        _openssl_assert(set_result == 1)\n        # After attempting to set default_verify_paths we need to know whether\n        # to go down the fallback path.\n        # First we'll check to see if any env vars have been set. If so,\n        # we won't try to do anything else because the user has set the path\n        # themselves.\n        dir_env_var = _ffi.string(\n            _lib.X509_get_default_cert_dir_env()\n        ).decode(\"ascii\")\n        file_env_var = _ffi.string(\n            _lib.X509_get_default_cert_file_env()\n        ).decode(\"ascii\")\n        if not self._check_env_vars_set(dir_env_var, file_env_var):\n            default_dir = _ffi.string(_lib.X509_get_default_cert_dir())\n            default_file = _ffi.string(_lib.X509_get_default_cert_file())\n            # Now we check to see if the default_dir and default_file are set\n            # to the exact values we use in our manylinux1 builds. If they are\n            # then we know to load the fallbacks\n            if (\n                default_dir == _CRYPTOGRAPHY_MANYLINUX1_CA_DIR and\n                default_file == _CRYPTOGRAPHY_MANYLINUX1_CA_FILE\n            ):\n                # This is manylinux1, let's load our fallback paths\n                self._fallback_default_verify_paths(\n                    _CERTIFICATE_FILE_LOCATIONS,\n                    _CERTIFICATE_PATH_LOCATIONS\n                )\n\n    def _check_env_vars_set(self, dir_env_var, file_env_var):\n        \"\"\"\n        Check to see if the default cert dir/file environment vars are present.\n\n        :return: bool\n        \"\"\"\n        return (\n            os.environ.get(file_env_var) is not None or\n            os.environ.get(dir_env_var) is not None\n        )\n\n    def _fallback_default_verify_paths(self, file_path, dir_path):\n        \"\"\"\n        Default verify paths are based on the compiled version of OpenSSL.\n        However, when pyca/cryptography is compiled as a manylinux1 wheel\n        that compiled location can potentially be wrong. So, like Go, we\n        will try a predefined set of paths and attempt to load roots\n        from there.\n\n        :return: None\n        \"\"\"\n        for cafile in file_path:\n            if os.path.isfile(cafile):\n                self.load_verify_locations(cafile)\n                break\n\n        for capath in dir_path:\n            if os.path.isdir(capath):\n                self.load_verify_locations(None, capath)\n                break\n\n    def use_certificate_chain_file(self, certfile):\n        \"\"\"\n        Load a certificate chain from a file.\n\n        :param certfile: The name of the certificate chain file (``bytes`` or\n            ``unicode``).  Must be PEM encoded.\n\n        :return: None\n        \"\"\"\n        certfile = _path_string(certfile)\n\n        result = _lib.SSL_CTX_use_certificate_chain_file(\n            self._context, certfile\n        )\n        if not result:\n            _raise_current_error()\n\n    def use_certificate_file(self, certfile, filetype=FILETYPE_PEM):\n        \"\"\"\n        Load a certificate from a file\n\n        :param certfile: The name of the certificate file (``bytes`` or\n            ``unicode``).\n        :param filetype: (optional) The encoding of the file, which is either\n            :const:`FILETYPE_PEM` or :const:`FILETYPE_ASN1`.  The default is\n            :const:`FILETYPE_PEM`.\n\n        :return: None\n        \"\"\"\n        certfile = _path_string(certfile)\n        if not isinstance(filetype, integer_types):\n            raise TypeError(\"filetype must be an integer\")\n\n        use_result = _lib.SSL_CTX_use_certificate_file(\n            self._context, certfile, filetype\n        )\n        if not use_result:\n            _raise_current_error()\n\n    def use_certificate(self, cert):\n        \"\"\"\n        Load a certificate from a X509 object\n\n        :param cert: The X509 object\n        :return: None\n        \"\"\"\n        if not isinstance(cert, X509):\n            raise TypeError(\"cert must be an X509 instance\")\n\n        use_result = _lib.SSL_CTX_use_certificate(self._context, cert._x509)\n        if not use_result:\n            _raise_current_error()\n\n    def add_extra_chain_cert(self, certobj):\n        \"\"\"\n        Add certificate to chain\n\n        :param certobj: The X509 certificate object to add to the chain\n        :return: None\n        \"\"\"\n        if not isinstance(certobj, X509):\n            raise TypeError(\"certobj must be an X509 instance\")\n\n        copy = _lib.X509_dup(certobj._x509)\n        add_result = _lib.SSL_CTX_add_extra_chain_cert(self._context, copy)\n        if not add_result:\n            # TODO: This is untested.\n            _lib.X509_free(copy)\n            _raise_current_error()\n\n    def _raise_passphrase_exception(self):\n        if self._passphrase_helper is not None:\n            self._passphrase_helper.raise_if_problem(Error)\n\n        _raise_current_error()\n\n    def use_privatekey_file(self, keyfile, filetype=_UNSPECIFIED):\n        \"\"\"\n        Load a private key from a file\n\n        :param keyfile: The name of the key file (``bytes`` or ``unicode``)\n        :param filetype: (optional) The encoding of the file, which is either\n            :const:`FILETYPE_PEM` or :const:`FILETYPE_ASN1`.  The default is\n            :const:`FILETYPE_PEM`.\n\n        :return: None\n        \"\"\"\n        keyfile = _path_string(keyfile)\n\n        if filetype is _UNSPECIFIED:\n            filetype = FILETYPE_PEM\n        elif not isinstance(filetype, integer_types):\n            raise TypeError(\"filetype must be an integer\")\n\n        use_result = _lib.SSL_CTX_use_PrivateKey_file(\n            self._context, keyfile, filetype)\n        if not use_result:\n            self._raise_passphrase_exception()\n\n    def use_privatekey(self, pkey):\n        \"\"\"\n        Load a private key from a PKey object\n\n        :param pkey: The PKey object\n        :return: None\n        \"\"\"\n        if not isinstance(pkey, PKey):\n            raise TypeError(\"pkey must be a PKey instance\")\n\n        use_result = _lib.SSL_CTX_use_PrivateKey(self._context, pkey._pkey)\n        if not use_result:\n            self._raise_passphrase_exception()\n\n    def check_privatekey(self):\n        \"\"\"\n        Check if the private key (loaded with :meth:`use_privatekey`) matches\n        the certificate (loaded with :meth:`use_certificate`)\n\n        :return: :data:`None` (raises :exc:`Error` if something's wrong)\n        \"\"\"\n        if not _lib.SSL_CTX_check_private_key(self._context):\n            _raise_current_error()\n\n    def load_client_ca(self, cafile):\n        \"\"\"\n        Load the trusted certificates that will be sent to the client.  Does\n        not actually imply any of the certificates are trusted; that must be\n        configured separately.\n\n        :param bytes cafile: The path to a certificates file in PEM format.\n        :return: None\n        \"\"\"\n        ca_list = _lib.SSL_load_client_CA_file(\n            _text_to_bytes_and_warn(\"cafile\", cafile)\n        )\n        _openssl_assert(ca_list != _ffi.NULL)\n        _lib.SSL_CTX_set_client_CA_list(self._context, ca_list)\n\n    def set_session_id(self, buf):\n        \"\"\"\n        Set the session id to *buf* within which a session can be reused for\n        this Context object.  This is needed when doing session resumption,\n        because there is no way for a stored session to know which Context\n        object it is associated with.\n\n        :param bytes buf: The session id.\n\n        :returns: None\n        \"\"\"\n        buf = _text_to_bytes_and_warn(\"buf\", buf)\n        _openssl_assert(\n            _lib.SSL_CTX_set_session_id_context(\n                self._context,\n                buf,\n                len(buf),\n            ) == 1\n        )\n\n    def set_session_cache_mode(self, mode):\n        \"\"\"\n        Set the behavior of the session cache used by all connections using\n        this Context.  The previously set mode is returned.  See\n        :const:`SESS_CACHE_*` for details about particular modes.\n\n        :param mode: One or more of the SESS_CACHE_* flags (combine using\n            bitwise or)\n        :returns: The previously set caching mode.\n\n        .. versionadded:: 0.14\n        \"\"\"\n        if not isinstance(mode, integer_types):\n            raise TypeError(\"mode must be an integer\")\n\n        return _lib.SSL_CTX_set_session_cache_mode(self._context, mode)\n\n    def get_session_cache_mode(self):\n        \"\"\"\n        Get the current session cache mode.\n\n        :returns: The currently used cache mode.\n\n        .. versionadded:: 0.14\n        \"\"\"\n        return _lib.SSL_CTX_get_session_cache_mode(self._context)\n\n    def set_verify(self, mode, callback):\n        \"\"\"\n        et the verification flags for this Context object to *mode* and specify\n        that *callback* should be used for verification callbacks.\n\n        :param mode: The verify mode, this should be one of\n            :const:`VERIFY_NONE` and :const:`VERIFY_PEER`. If\n            :const:`VERIFY_PEER` is used, *mode* can be OR:ed with\n            :const:`VERIFY_FAIL_IF_NO_PEER_CERT` and\n            :const:`VERIFY_CLIENT_ONCE` to further control the behaviour.\n        :param callback: The Python callback to use.  This should take five\n            arguments: A Connection object, an X509 object, and three integer\n            variables, which are in turn potential error number, error depth\n            and return code. *callback* should return True if verification\n            passes and False otherwise.\n        :return: None\n\n        See SSL_CTX_set_verify(3SSL) for further details.\n        \"\"\"\n        if not isinstance(mode, integer_types):\n            raise TypeError(\"mode must be an integer\")\n\n        if not callable(callback):\n            raise TypeError(\"callback must be callable\")\n\n        self._verify_helper = _VerifyHelper(callback)\n        self._verify_callback = self._verify_helper.callback\n        _lib.SSL_CTX_set_verify(self._context, mode, self._verify_callback)\n\n    def set_verify_depth(self, depth):\n        \"\"\"\n        Set the maximum depth for the certificate chain verification that shall\n        be allowed for this Context object.\n\n        :param depth: An integer specifying the verify depth\n        :return: None\n        \"\"\"\n        if not isinstance(depth, integer_types):\n            raise TypeError(\"depth must be an integer\")\n\n        _lib.SSL_CTX_set_verify_depth(self._context, depth)\n\n    def get_verify_mode(self):\n        \"\"\"\n        Retrieve the Context object's verify mode, as set by\n        :meth:`set_verify`.\n\n        :return: The verify mode\n        \"\"\"\n        return _lib.SSL_CTX_get_verify_mode(self._context)\n\n    def get_verify_depth(self):\n        \"\"\"\n        Retrieve the Context object's verify depth, as set by\n        :meth:`set_verify_depth`.\n\n        :return: The verify depth\n        \"\"\"\n        return _lib.SSL_CTX_get_verify_depth(self._context)\n\n    def load_tmp_dh(self, dhfile):\n        \"\"\"\n        Load parameters for Ephemeral Diffie-Hellman\n\n        :param dhfile: The file to load EDH parameters from (``bytes`` or\n            ``unicode``).\n\n        :return: None\n        \"\"\"\n        dhfile = _path_string(dhfile)\n\n        bio = _lib.BIO_new_file(dhfile, b\"r\")\n        if bio == _ffi.NULL:\n            _raise_current_error()\n        bio = _ffi.gc(bio, _lib.BIO_free)\n\n        dh = _lib.PEM_read_bio_DHparams(bio, _ffi.NULL, _ffi.NULL, _ffi.NULL)\n        dh = _ffi.gc(dh, _lib.DH_free)\n        _lib.SSL_CTX_set_tmp_dh(self._context, dh)\n\n    def set_tmp_ecdh(self, curve):\n        \"\"\"\n        Select a curve to use for ECDHE key exchange.\n\n        :param curve: A curve object to use as returned by either\n            :meth:`OpenSSL.crypto.get_elliptic_curve` or\n            :meth:`OpenSSL.crypto.get_elliptic_curves`.\n\n        :return: None\n        \"\"\"\n        _lib.SSL_CTX_set_tmp_ecdh(self._context, curve._to_EC_KEY())\n\n    def set_cipher_list(self, cipher_list):\n        \"\"\"\n        Set the list of ciphers to be used in this context.\n\n        See the OpenSSL manual for more information (e.g.\n        :manpage:`ciphers(1)`).\n\n        :param bytes cipher_list: An OpenSSL cipher string.\n        :return: None\n        \"\"\"\n        cipher_list = _text_to_bytes_and_warn(\"cipher_list\", cipher_list)\n\n        if not isinstance(cipher_list, bytes):\n            raise TypeError(\"cipher_list must be a byte string.\")\n\n        _openssl_assert(\n            _lib.SSL_CTX_set_cipher_list(self._context, cipher_list) == 1\n        )\n        # In OpenSSL 1.1.1 setting the cipher list will always return TLS 1.3\n        # ciphers even if you pass an invalid cipher. Applications (like\n        # Twisted) have tests that depend on an error being raised if an\n        # invalid cipher string is passed, but without the following check\n        # for the TLS 1.3 specific cipher suites it would never error.\n        tmpconn = Connection(self, None)\n        _openssl_assert(\n            tmpconn.get_cipher_list() != [\n                'TLS_AES_256_GCM_SHA384',\n                'TLS_CHACHA20_POLY1305_SHA256',\n                'TLS_AES_128_GCM_SHA256'\n            ]\n        )\n\n    def set_client_ca_list(self, certificate_authorities):\n        \"\"\"\n        Set the list of preferred client certificate signers for this server\n        context.\n\n        This list of certificate authorities will be sent to the client when\n        the server requests a client certificate.\n\n        :param certificate_authorities: a sequence of X509Names.\n        :return: None\n\n        .. versionadded:: 0.10\n        \"\"\"\n        name_stack = _lib.sk_X509_NAME_new_null()\n        _openssl_assert(name_stack != _ffi.NULL)\n\n        try:\n            for ca_name in certificate_authorities:\n                if not isinstance(ca_name, X509Name):\n                    raise TypeError(\n                        \"client CAs must be X509Name objects, not %s \"\n                        \"objects\" % (\n                            type(ca_name).__name__,\n                        )\n                    )\n                copy = _lib.X509_NAME_dup(ca_name._name)\n                _openssl_assert(copy != _ffi.NULL)\n                push_result = _lib.sk_X509_NAME_push(name_stack, copy)\n                if not push_result:\n                    _lib.X509_NAME_free(copy)\n                    _raise_current_error()\n        except Exception:\n            _lib.sk_X509_NAME_free(name_stack)\n            raise\n\n        _lib.SSL_CTX_set_client_CA_list(self._context, name_stack)\n\n    def add_client_ca(self, certificate_authority):\n        \"\"\"\n        Add the CA certificate to the list of preferred signers for this\n        context.\n\n        The list of certificate authorities will be sent to the client when the\n        server requests a client certificate.\n\n        :param certificate_authority: certificate authority's X509 certificate.\n        :return: None\n\n        .. versionadded:: 0.10\n        \"\"\"\n        if not isinstance(certificate_authority, X509):\n            raise TypeError(\"certificate_authority must be an X509 instance\")\n\n        add_result = _lib.SSL_CTX_add_client_CA(\n            self._context, certificate_authority._x509)\n        _openssl_assert(add_result == 1)\n\n    def set_timeout(self, timeout):\n        \"\"\"\n        Set the timeout for newly created sessions for this Context object to\n        *timeout*.  The default value is 300 seconds. See the OpenSSL manual\n        for more information (e.g. :manpage:`SSL_CTX_set_timeout(3)`).\n\n        :param timeout: The timeout in (whole) seconds\n        :return: The previous session timeout\n        \"\"\"\n        if not isinstance(timeout, integer_types):\n            raise TypeError(\"timeout must be an integer\")\n\n        return _lib.SSL_CTX_set_timeout(self._context, timeout)\n\n    def get_timeout(self):\n        \"\"\"\n        Retrieve session timeout, as set by :meth:`set_timeout`. The default\n        is 300 seconds.\n\n        :return: The session timeout\n        \"\"\"\n        return _lib.SSL_CTX_get_timeout(self._context)\n\n    def set_info_callback(self, callback):\n        \"\"\"\n        Set the information callback to *callback*. This function will be\n        called from time to time during SSL handshakes.\n\n        :param callback: The Python callback to use.  This should take three\n            arguments: a Connection object and two integers.  The first integer\n            specifies where in the SSL handshake the function was called, and\n            the other the return code from a (possibly failed) internal\n            function call.\n        :return: None\n        \"\"\"\n        @wraps(callback)\n        def wrapper(ssl, where, return_code):\n            callback(Connection._reverse_mapping[ssl], where, return_code)\n        self._info_callback = _ffi.callback(\n            \"void (*)(const SSL *, int, int)\", wrapper)\n        _lib.SSL_CTX_set_info_callback(self._context, self._info_callback)\n\n    def get_app_data(self):\n        \"\"\"\n        Get the application data (supplied via :meth:`set_app_data()`)\n\n        :return: The application data\n        \"\"\"\n        return self._app_data\n\n    def set_app_data(self, data):\n        \"\"\"\n        Set the application data (will be returned from get_app_data())\n\n        :param data: Any Python object\n        :return: None\n        \"\"\"\n        self._app_data = data\n\n    def get_cert_store(self):\n        \"\"\"\n        Get the certificate store for the context.  This can be used to add\n        \"trusted\" certificates without using the\n        :meth:`load_verify_locations` method.\n\n        :return: A X509Store object or None if it does not have one.\n        \"\"\"\n        store = _lib.SSL_CTX_get_cert_store(self._context)\n        if store == _ffi.NULL:\n            # TODO: This is untested.\n            return None\n\n        pystore = X509Store.__new__(X509Store)\n        pystore._store = store\n        return pystore\n\n    def set_options(self, options):\n        \"\"\"\n        Add options. Options set before are not cleared!\n        This method should be used with the :const:`OP_*` constants.\n\n        :param options: The options to add.\n        :return: The new option bitmask.\n        \"\"\"\n        if not isinstance(options, integer_types):\n            raise TypeError(\"options must be an integer\")\n\n        return _lib.SSL_CTX_set_options(self._context, options)\n\n    def set_mode(self, mode):\n        \"\"\"\n        Add modes via bitmask. Modes set before are not cleared!  This method\n        should be used with the :const:`MODE_*` constants.\n\n        :param mode: The mode to add.\n        :return: The new mode bitmask.\n        \"\"\"\n        if not isinstance(mode, integer_types):\n            raise TypeError(\"mode must be an integer\")\n\n        return _lib.SSL_CTX_set_mode(self._context, mode)\n\n    @_requires_sni\n    def set_tlsext_servername_callback(self, callback):\n        \"\"\"\n        Specify a callback function to be called when clients specify a server\n        name.\n\n        :param callback: The callback function.  It will be invoked with one\n            argument, the Connection instance.\n\n        .. versionadded:: 0.13\n        \"\"\"\n        @wraps(callback)\n        def wrapper(ssl, alert, arg):\n            callback(Connection._reverse_mapping[ssl])\n            return 0\n\n        self._tlsext_servername_callback = _ffi.callback(\n            \"int (*)(SSL *, int *, void *)\", wrapper)\n        _lib.SSL_CTX_set_tlsext_servername_callback(\n            self._context, self._tlsext_servername_callback)\n\n    def set_tlsext_use_srtp(self, profiles):\n        \"\"\"\n        Enable support for negotiating SRTP keying material.\n\n        :param bytes profiles: A colon delimited list of protection profile\n            names, like ``b'SRTP_AES128_CM_SHA1_80:SRTP_AES128_CM_SHA1_32'``.\n        :return: None\n        \"\"\"\n        if not isinstance(profiles, bytes):\n            raise TypeError(\"profiles must be a byte string.\")\n\n        _openssl_assert(\n            _lib.SSL_CTX_set_tlsext_use_srtp(self._context, profiles) == 0\n        )\n\n    @_requires_npn\n    def set_npn_advertise_callback(self, callback):\n        \"\"\"\n        Specify a callback function that will be called when offering `Next\n        Protocol Negotiation\n        <https://technotes.googlecode.com/git/nextprotoneg.html>`_ as a server.\n\n        :param callback: The callback function.  It will be invoked with one\n            argument, the :class:`Connection` instance.  It should return a\n            list of bytestrings representing the advertised protocols, like\n            ``[b'http/1.1', b'spdy/2']``.\n\n        .. versionadded:: 0.15\n        \"\"\"\n        self._npn_advertise_helper = _NpnAdvertiseHelper(callback)\n        self._npn_advertise_callback = self._npn_advertise_helper.callback\n        _lib.SSL_CTX_set_next_protos_advertised_cb(\n            self._context, self._npn_advertise_callback, _ffi.NULL)\n\n    @_requires_npn\n    def set_npn_select_callback(self, callback):\n        \"\"\"\n        Specify a callback function that will be called when a server offers\n        Next Protocol Negotiation options.\n\n        :param callback: The callback function.  It will be invoked with two\n            arguments: the Connection, and a list of offered protocols as\n            bytestrings, e.g. ``[b'http/1.1', b'spdy/2']``.  It should return\n            one of those bytestrings, the chosen protocol.\n\n        .. versionadded:: 0.15\n        \"\"\"\n        self._npn_select_helper = _NpnSelectHelper(callback)\n        self._npn_select_callback = self._npn_select_helper.callback\n        _lib.SSL_CTX_set_next_proto_select_cb(\n            self._context, self._npn_select_callback, _ffi.NULL)\n\n    @_requires_alpn\n    def set_alpn_protos(self, protos):\n        \"\"\"\n        Specify the protocols that the client is prepared to speak after the\n        TLS connection has been negotiated using Application Layer Protocol\n        Negotiation.\n\n        :param protos: A list of the protocols to be offered to the server.\n            This list should be a Python list of bytestrings representing the\n            protocols to offer, e.g. ``[b'http/1.1', b'spdy/2']``.\n        \"\"\"\n        # Take the list of protocols and join them together, prefixing them\n        # with their lengths.\n        protostr = b''.join(\n            chain.from_iterable((int2byte(len(p)), p) for p in protos)\n        )\n\n        # Build a C string from the list. We don't need to save this off\n        # because OpenSSL immediately copies the data out.\n        input_str = _ffi.new(\"unsigned char[]\", protostr)\n        _lib.SSL_CTX_set_alpn_protos(self._context, input_str, len(protostr))\n\n    @_requires_alpn\n    def set_alpn_select_callback(self, callback):\n        \"\"\"\n        Specify a callback function that will be called on the server when a\n        client offers protocols using ALPN.\n\n        :param callback: The callback function.  It will be invoked with two\n            arguments: the Connection, and a list of offered protocols as\n            bytestrings, e.g ``[b'http/1.1', b'spdy/2']``.  It should return\n            one of those bytestrings, the chosen protocol.\n        \"\"\"\n        self._alpn_select_helper = _ALPNSelectHelper(callback)\n        self._alpn_select_callback = self._alpn_select_helper.callback\n        _lib.SSL_CTX_set_alpn_select_cb(\n            self._context, self._alpn_select_callback, _ffi.NULL)\n\n    def _set_ocsp_callback(self, helper, data):\n        \"\"\"\n        This internal helper does the common work for\n        ``set_ocsp_server_callback`` and ``set_ocsp_client_callback``, which is\n        almost all of it.\n        \"\"\"\n        self._ocsp_helper = helper\n        self._ocsp_callback = helper.callback\n        if data is None:\n            self._ocsp_data = _ffi.NULL\n        else:\n            self._ocsp_data = _ffi.new_handle(data)\n\n        rc = _lib.SSL_CTX_set_tlsext_status_cb(\n            self._context, self._ocsp_callback\n        )\n        _openssl_assert(rc == 1)\n        rc = _lib.SSL_CTX_set_tlsext_status_arg(self._context, self._ocsp_data)\n        _openssl_assert(rc == 1)\n\n    def set_ocsp_server_callback(self, callback, data=None):\n        \"\"\"\n        Set a callback to provide OCSP data to be stapled to the TLS handshake\n        on the server side.\n\n        :param callback: The callback function. It will be invoked with two\n            arguments: the Connection, and the optional arbitrary data you have\n            provided. The callback must return a bytestring that contains the\n            OCSP data to staple to the handshake. If no OCSP data is available\n            for this connection, return the empty bytestring.\n        :param data: Some opaque data that will be passed into the callback\n            function when called. This can be used to avoid needing to do\n            complex data lookups or to keep track of what context is being\n            used. This parameter is optional.\n        \"\"\"\n        helper = _OCSPServerCallbackHelper(callback)\n        self._set_ocsp_callback(helper, data)\n\n    def set_ocsp_client_callback(self, callback, data=None):\n        \"\"\"\n        Set a callback to validate OCSP data stapled to the TLS handshake on\n        the client side.\n\n        :param callback: The callback function. It will be invoked with three\n            arguments: the Connection, a bytestring containing the stapled OCSP\n            assertion, and the optional arbitrary data you have provided. The\n            callback must return a boolean that indicates the result of\n            validating the OCSP data: ``True`` if the OCSP data is valid and\n            the certificate can be trusted, or ``False`` if either the OCSP\n            data is invalid or the certificate has been revoked.\n        :param data: Some opaque data that will be passed into the callback\n            function when called. This can be used to avoid needing to do\n            complex data lookups or to keep track of what context is being\n            used. This parameter is optional.\n        \"\"\"\n        helper = _OCSPClientCallbackHelper(callback)\n        self._set_ocsp_callback(helper, data)\n\n\nContextType = deprecated(\n    Context, __name__,\n    \"ContextType has been deprecated, use Context instead\", DeprecationWarning\n)\n\n\nclass Connection(object):\n    \"\"\"\n    \"\"\"\n    _reverse_mapping = WeakValueDictionary()\n\n    def __init__(self, context, socket=None):\n        \"\"\"\n        Create a new Connection object, using the given OpenSSL.SSL.Context\n        instance and socket.\n\n        :param context: An SSL Context to use for this connection\n        :param socket: The socket to use for transport layer\n        \"\"\"\n        if not isinstance(context, Context):\n            raise TypeError(\"context must be a Context instance\")\n\n        ssl = _lib.SSL_new(context._context)\n        self._ssl = _ffi.gc(ssl, _lib.SSL_free)\n        # We set SSL_MODE_AUTO_RETRY to handle situations where OpenSSL returns\n        # an SSL_ERROR_WANT_READ when processing a non-application data packet\n        # even though there is still data on the underlying transport.\n        # See https://github.com/openssl/openssl/issues/6234 for more details.\n        _lib.SSL_set_mode(self._ssl, _lib.SSL_MODE_AUTO_RETRY)\n        self._context = context\n        self._app_data = None\n\n        # References to strings used for Next Protocol Negotiation. OpenSSL's\n        # header files suggest that these might get copied at some point, but\n        # doesn't specify when, so we store them here to make sure they don't\n        # get freed before OpenSSL uses them.\n        self._npn_advertise_callback_args = None\n        self._npn_select_callback_args = None\n\n        # References to strings used for Application Layer Protocol\n        # Negotiation. These strings get copied at some point but it's well\n        # after the callback returns, so we have to hang them somewhere to\n        # avoid them getting freed.\n        self._alpn_select_callback_args = None\n\n        self._reverse_mapping[self._ssl] = self\n\n        if socket is None:\n            self._socket = None\n            # Don't set up any gc for these, SSL_free will take care of them.\n            self._into_ssl = _lib.BIO_new(_lib.BIO_s_mem())\n            _openssl_assert(self._into_ssl != _ffi.NULL)\n\n            self._from_ssl = _lib.BIO_new(_lib.BIO_s_mem())\n            _openssl_assert(self._from_ssl != _ffi.NULL)\n\n            _lib.SSL_set_bio(self._ssl, self._into_ssl, self._from_ssl)\n        else:\n            self._into_ssl = None\n            self._from_ssl = None\n            self._socket = socket\n            set_result = _lib.SSL_set_fd(\n                self._ssl, _asFileDescriptor(self._socket))\n            _openssl_assert(set_result == 1)\n\n    def __getattr__(self, name):\n        \"\"\"\n        Look up attributes on the wrapped socket object if they are not found\n        on the Connection object.\n        \"\"\"\n        if self._socket is None:\n            raise AttributeError(\"'%s' object has no attribute '%s'\" % (\n                self.__class__.__name__, name\n            ))\n        else:\n            return getattr(self._socket, name)\n\n    def _raise_ssl_error(self, ssl, result):\n        if self._context._verify_helper is not None:\n            self._context._verify_helper.raise_if_problem()\n        if self._context._npn_advertise_helper is not None:\n            self._context._npn_advertise_helper.raise_if_problem()\n        if self._context._npn_select_helper is not None:\n            self._context._npn_select_helper.raise_if_problem()\n        if self._context._alpn_select_helper is not None:\n            self._context._alpn_select_helper.raise_if_problem()\n        if self._context._ocsp_helper is not None:\n            self._context._ocsp_helper.raise_if_problem()\n\n        error = _lib.SSL_get_error(ssl, result)\n        if error == _lib.SSL_ERROR_WANT_READ:\n            raise WantReadError()\n        elif error == _lib.SSL_ERROR_WANT_WRITE:\n            raise WantWriteError()\n        elif error == _lib.SSL_ERROR_ZERO_RETURN:\n            raise ZeroReturnError()\n        elif error == _lib.SSL_ERROR_WANT_X509_LOOKUP:\n            # TODO: This is untested.\n            raise WantX509LookupError()\n        elif error == _lib.SSL_ERROR_SYSCALL:\n            if _lib.ERR_peek_error() == 0:\n                if result < 0:\n                    if platform == \"win32\":\n                        errno = _ffi.getwinerror()[0]\n                    else:\n                        errno = _ffi.errno\n\n                    if errno != 0:\n                        raise SysCallError(errno, errorcode.get(errno))\n                raise SysCallError(-1, \"Unexpected EOF\")\n            else:\n                # TODO: This is untested.\n                _raise_current_error()\n        elif error == _lib.SSL_ERROR_NONE:\n            pass\n        else:\n            _raise_current_error()\n\n    def get_context(self):\n        \"\"\"\n        Retrieve the :class:`Context` object associated with this\n        :class:`Connection`.\n        \"\"\"\n        return self._context\n\n    def set_context(self, context):\n        \"\"\"\n        Switch this connection to a new session context.\n\n        :param context: A :class:`Context` instance giving the new session\n            context to use.\n        \"\"\"\n        if not isinstance(context, Context):\n            raise TypeError(\"context must be a Context instance\")\n\n        _lib.SSL_set_SSL_CTX(self._ssl, context._context)\n        self._context = context\n\n    @_requires_sni\n    def get_servername(self):\n        \"\"\"\n        Retrieve the servername extension value if provided in the client hello\n        message, or None if there wasn't one.\n\n        :return: A byte string giving the server name or :data:`None`.\n\n        .. versionadded:: 0.13\n        \"\"\"\n        name = _lib.SSL_get_servername(\n            self._ssl, _lib.TLSEXT_NAMETYPE_host_name\n        )\n        if name == _ffi.NULL:\n            return None\n\n        return _ffi.string(name)\n\n    @_requires_sni\n    def set_tlsext_host_name(self, name):\n        \"\"\"\n        Set the value of the servername extension to send in the client hello.\n\n        :param name: A byte string giving the name.\n\n        .. versionadded:: 0.13\n        \"\"\"\n        if not isinstance(name, bytes):\n            raise TypeError(\"name must be a byte string\")\n        elif b\"\\0\" in name:\n            raise TypeError(\"name must not contain NUL byte\")\n\n        # XXX I guess this can fail sometimes?\n        _lib.SSL_set_tlsext_host_name(self._ssl, name)\n\n    def pending(self):\n        \"\"\"\n        Get the number of bytes that can be safely read from the SSL buffer\n        (**not** the underlying transport buffer).\n\n        :return: The number of bytes available in the receive buffer.\n        \"\"\"\n        return _lib.SSL_pending(self._ssl)\n\n    def send(self, buf, flags=0):\n        \"\"\"\n        Send data on the connection. NOTE: If you get one of the WantRead,\n        WantWrite or WantX509Lookup exceptions on this, you have to call the\n        method again with the SAME buffer.\n\n        :param buf: The string, buffer or memoryview to send\n        :param flags: (optional) Included for compatibility with the socket\n                      API, the value is ignored\n        :return: The number of bytes written\n        \"\"\"\n        # Backward compatibility\n        buf = _text_to_bytes_and_warn(\"buf\", buf)\n\n        if isinstance(buf, memoryview):\n            buf = buf.tobytes()\n        if isinstance(buf, _buffer):\n            buf = str(buf)\n        if not isinstance(buf, bytes):\n            raise TypeError(\"data must be a memoryview, buffer or byte string\")\n        if len(buf) > 2147483647:\n            raise ValueError(\"Cannot send more than 2**31-1 bytes at once.\")\n\n        result = _lib.SSL_write(self._ssl, buf, len(buf))\n        self._raise_ssl_error(self._ssl, result)\n        return result\n    write = send\n\n    def sendall(self, buf, flags=0):\n        \"\"\"\n        Send \"all\" data on the connection. This calls send() repeatedly until\n        all data is sent. If an error occurs, it's impossible to tell how much\n        data has been sent.\n\n        :param buf: The string, buffer or memoryview to send\n        :param flags: (optional) Included for compatibility with the socket\n                      API, the value is ignored\n        :return: The number of bytes written\n        \"\"\"\n        buf = _text_to_bytes_and_warn(\"buf\", buf)\n\n        if isinstance(buf, memoryview):\n            buf = buf.tobytes()\n        if isinstance(buf, _buffer):\n            buf = str(buf)\n        if not isinstance(buf, bytes):\n            raise TypeError(\"buf must be a memoryview, buffer or byte string\")\n\n        left_to_send = len(buf)\n        total_sent = 0\n        data = _ffi.new(\"char[]\", buf)\n\n        while left_to_send:\n            # SSL_write's num arg is an int,\n            # so we cannot send more than 2**31-1 bytes at once.\n            result = _lib.SSL_write(\n                self._ssl,\n                data + total_sent,\n                min(left_to_send, 2147483647)\n            )\n            self._raise_ssl_error(self._ssl, result)\n            total_sent += result\n            left_to_send -= result\n\n    def recv(self, bufsiz, flags=None):\n        \"\"\"\n        Receive data on the connection.\n\n        :param bufsiz: The maximum number of bytes to read\n        :param flags: (optional) The only supported flag is ``MSG_PEEK``,\n            all other flags are ignored.\n        :return: The string read from the Connection\n        \"\"\"\n        buf = _no_zero_allocator(\"char[]\", bufsiz)\n        if flags is not None and flags & socket.MSG_PEEK:\n            result = _lib.SSL_peek(self._ssl, buf, bufsiz)\n        else:\n            result = _lib.SSL_read(self._ssl, buf, bufsiz)\n        self._raise_ssl_error(self._ssl, result)\n        return _ffi.buffer(buf, result)[:]\n    read = recv\n\n    def recv_into(self, buffer, nbytes=None, flags=None):\n        \"\"\"\n        Receive data on the connection and copy it directly into the provided\n        buffer, rather than creating a new string.\n\n        :param buffer: The buffer to copy into.\n        :param nbytes: (optional) The maximum number of bytes to read into the\n            buffer. If not present, defaults to the size of the buffer. If\n            larger than the size of the buffer, is reduced to the size of the\n            buffer.\n        :param flags: (optional) The only supported flag is ``MSG_PEEK``,\n            all other flags are ignored.\n        :return: The number of bytes read into the buffer.\n        \"\"\"\n        if nbytes is None:\n            nbytes = len(buffer)\n        else:\n            nbytes = min(nbytes, len(buffer))\n\n        # We need to create a temporary buffer. This is annoying, it would be\n        # better if we could pass memoryviews straight into the SSL_read call,\n        # but right now we can't. Revisit this if CFFI gets that ability.\n        buf = _no_zero_allocator(\"char[]\", nbytes)\n        if flags is not None and flags & socket.MSG_PEEK:\n            result = _lib.SSL_peek(self._ssl, buf, nbytes)\n        else:\n            result = _lib.SSL_read(self._ssl, buf, nbytes)\n        self._raise_ssl_error(self._ssl, result)\n\n        # This strange line is all to avoid a memory copy. The buffer protocol\n        # should allow us to assign a CFFI buffer to the LHS of this line, but\n        # on CPython 3.3+ that segfaults. As a workaround, we can temporarily\n        # wrap it in a memoryview.\n        buffer[:result] = memoryview(_ffi.buffer(buf, result))\n\n        return result\n\n    def _handle_bio_errors(self, bio, result):\n        if _lib.BIO_should_retry(bio):\n            if _lib.BIO_should_read(bio):\n                raise WantReadError()\n            elif _lib.BIO_should_write(bio):\n                # TODO: This is untested.\n                raise WantWriteError()\n            elif _lib.BIO_should_io_special(bio):\n                # TODO: This is untested.  I think io_special means the socket\n                # BIO has a not-yet connected socket.\n                raise ValueError(\"BIO_should_io_special\")\n            else:\n                # TODO: This is untested.\n                raise ValueError(\"unknown bio failure\")\n        else:\n            # TODO: This is untested.\n            _raise_current_error()\n\n    def bio_read(self, bufsiz):\n        \"\"\"\n        If the Connection was created with a memory BIO, this method can be\n        used to read bytes from the write end of that memory BIO.  Many\n        Connection methods will add bytes which must be read in this manner or\n        the buffer will eventually fill up and the Connection will be able to\n        take no further actions.\n\n        :param bufsiz: The maximum number of bytes to read\n        :return: The string read.\n        \"\"\"\n        if self._from_ssl is None:\n            raise TypeError(\"Connection sock was not None\")\n\n        if not isinstance(bufsiz, integer_types):\n            raise TypeError(\"bufsiz must be an integer\")\n\n        buf = _no_zero_allocator(\"char[]\", bufsiz)\n        result = _lib.BIO_read(self._from_ssl, buf, bufsiz)\n        if result <= 0:\n            self._handle_bio_errors(self._from_ssl, result)\n\n        return _ffi.buffer(buf, result)[:]\n\n    def bio_write(self, buf):\n        \"\"\"\n        If the Connection was created with a memory BIO, this method can be\n        used to add bytes to the read end of that memory BIO.  The Connection\n        can then read the bytes (for example, in response to a call to\n        :meth:`recv`).\n\n        :param buf: The string to put into the memory BIO.\n        :return: The number of bytes written\n        \"\"\"\n        buf = _text_to_bytes_and_warn(\"buf\", buf)\n\n        if self._into_ssl is None:\n            raise TypeError(\"Connection sock was not None\")\n\n        result = _lib.BIO_write(self._into_ssl, buf, len(buf))\n        if result <= 0:\n            self._handle_bio_errors(self._into_ssl, result)\n        return result\n\n    def renegotiate(self):\n        \"\"\"\n        Renegotiate the session.\n\n        :return: True if the renegotiation can be started, False otherwise\n        :rtype: bool\n        \"\"\"\n        if not self.renegotiate_pending():\n            _openssl_assert(_lib.SSL_renegotiate(self._ssl) == 1)\n            return True\n        return False\n\n    def do_handshake(self):\n        \"\"\"\n        Perform an SSL handshake (usually called after :meth:`renegotiate` or\n        one of :meth:`set_accept_state` or :meth:`set_accept_state`). This can\n        raise the same exceptions as :meth:`send` and :meth:`recv`.\n\n        :return: None.\n        \"\"\"\n        result = _lib.SSL_do_handshake(self._ssl)\n        self._raise_ssl_error(self._ssl, result)\n\n    def renegotiate_pending(self):\n        \"\"\"\n        Check if there's a renegotiation in progress, it will return False once\n        a renegotiation is finished.\n\n        :return: Whether there's a renegotiation in progress\n        :rtype: bool\n        \"\"\"\n        return _lib.SSL_renegotiate_pending(self._ssl) == 1\n\n    def total_renegotiations(self):\n        \"\"\"\n        Find out the total number of renegotiations.\n\n        :return: The number of renegotiations.\n        :rtype: int\n        \"\"\"\n        return _lib.SSL_total_renegotiations(self._ssl)\n\n    def connect(self, addr):\n        \"\"\"\n        Call the :meth:`connect` method of the underlying socket and set up SSL\n        on the socket, using the :class:`Context` object supplied to this\n        :class:`Connection` object at creation.\n\n        :param addr: A remote address\n        :return: What the socket's connect method returns\n        \"\"\"\n        _lib.SSL_set_connect_state(self._ssl)\n        return self._socket.connect(addr)\n\n    def connect_ex(self, addr):\n        \"\"\"\n        Call the :meth:`connect_ex` method of the underlying socket and set up\n        SSL on the socket, using the Context object supplied to this Connection\n        object at creation. Note that if the :meth:`connect_ex` method of the\n        socket doesn't return 0, SSL won't be initialized.\n\n        :param addr: A remove address\n        :return: What the socket's connect_ex method returns\n        \"\"\"\n        connect_ex = self._socket.connect_ex\n        self.set_connect_state()\n        return connect_ex(addr)\n\n    def accept(self):\n        \"\"\"\n        Call the :meth:`accept` method of the underlying socket and set up SSL\n        on the returned socket, using the Context object supplied to this\n        :class:`Connection` object at creation.\n\n        :return: A *(conn, addr)* pair where *conn* is the new\n            :class:`Connection` object created, and *address* is as returned by\n            the socket's :meth:`accept`.\n        \"\"\"\n        client, addr = self._socket.accept()\n        conn = Connection(self._context, client)\n        conn.set_accept_state()\n        return (conn, addr)\n\n    def bio_shutdown(self):\n        \"\"\"\n        If the Connection was created with a memory BIO, this method can be\n        used to indicate that *end of file* has been reached on the read end of\n        that memory BIO.\n\n        :return: None\n        \"\"\"\n        if self._from_ssl is None:\n            raise TypeError(\"Connection sock was not None\")\n\n        _lib.BIO_set_mem_eof_return(self._into_ssl, 0)\n\n    def shutdown(self):\n        \"\"\"\n        Send the shutdown message to the Connection.\n\n        :return: True if the shutdown completed successfully (i.e. both sides\n                 have sent closure alerts), False otherwise (in which case you\n                 call :meth:`recv` or :meth:`send` when the connection becomes\n                 readable/writeable).\n        \"\"\"\n        result = _lib.SSL_shutdown(self._ssl)\n        if result < 0:\n            self._raise_ssl_error(self._ssl, result)\n        elif result > 0:\n            return True\n        else:\n            return False\n\n    def get_cipher_list(self):\n        \"\"\"\n        Retrieve the list of ciphers used by the Connection object.\n\n        :return: A list of native cipher strings.\n        \"\"\"\n        ciphers = []\n        for i in count():\n            result = _lib.SSL_get_cipher_list(self._ssl, i)\n            if result == _ffi.NULL:\n                break\n            ciphers.append(_native(_ffi.string(result)))\n        return ciphers\n\n    def get_client_ca_list(self):\n        \"\"\"\n        Get CAs whose certificates are suggested for client authentication.\n\n        :return: If this is a server connection, the list of certificate\n            authorities that will be sent or has been sent to the client, as\n            controlled by this :class:`Connection`'s :class:`Context`.\n\n            If this is a client connection, the list will be empty until the\n            connection with the server is established.\n\n        .. versionadded:: 0.10\n        \"\"\"\n        ca_names = _lib.SSL_get_client_CA_list(self._ssl)\n        if ca_names == _ffi.NULL:\n            # TODO: This is untested.\n            return []\n\n        result = []\n        for i in range(_lib.sk_X509_NAME_num(ca_names)):\n            name = _lib.sk_X509_NAME_value(ca_names, i)\n            copy = _lib.X509_NAME_dup(name)\n            _openssl_assert(copy != _ffi.NULL)\n\n            pyname = X509Name.__new__(X509Name)\n            pyname._name = _ffi.gc(copy, _lib.X509_NAME_free)\n            result.append(pyname)\n        return result\n\n    def makefile(self, *args, **kwargs):\n        \"\"\"\n        The makefile() method is not implemented, since there is no dup\n        semantics for SSL connections\n\n        :raise: NotImplementedError\n        \"\"\"\n        raise NotImplementedError(\n            \"Cannot make file object of OpenSSL.SSL.Connection\")\n\n    def get_app_data(self):\n        \"\"\"\n        Retrieve application data as set by :meth:`set_app_data`.\n\n        :return: The application data\n        \"\"\"\n        return self._app_data\n\n    def set_app_data(self, data):\n        \"\"\"\n        Set application data\n\n        :param data: The application data\n        :return: None\n        \"\"\"\n        self._app_data = data\n\n    def get_shutdown(self):\n        \"\"\"\n        Get the shutdown state of the Connection.\n\n        :return: The shutdown state, a bitvector of SENT_SHUTDOWN,\n            RECEIVED_SHUTDOWN.\n        \"\"\"\n        return _lib.SSL_get_shutdown(self._ssl)\n\n    def set_shutdown(self, state):\n        \"\"\"\n        Set the shutdown state of the Connection.\n\n        :param state: bitvector of SENT_SHUTDOWN, RECEIVED_SHUTDOWN.\n        :return: None\n        \"\"\"\n        if not isinstance(state, integer_types):\n            raise TypeError(\"state must be an integer\")\n\n        _lib.SSL_set_shutdown(self._ssl, state)\n\n    def get_state_string(self):\n        \"\"\"\n        Retrieve a verbose string detailing the state of the Connection.\n\n        :return: A string representing the state\n        :rtype: bytes\n        \"\"\"\n        return _ffi.string(_lib.SSL_state_string_long(self._ssl))\n\n    def server_random(self):\n        \"\"\"\n        Retrieve the random value used with the server hello message.\n\n        :return: A string representing the state\n        \"\"\"\n        session = _lib.SSL_get_session(self._ssl)\n        if session == _ffi.NULL:\n            return None\n        length = _lib.SSL_get_server_random(self._ssl, _ffi.NULL, 0)\n        assert length > 0\n        outp = _no_zero_allocator(\"unsigned char[]\", length)\n        _lib.SSL_get_server_random(self._ssl, outp, length)\n        return _ffi.buffer(outp, length)[:]\n\n    def client_random(self):\n        \"\"\"\n        Retrieve the random value used with the client hello message.\n\n        :return: A string representing the state\n        \"\"\"\n        session = _lib.SSL_get_session(self._ssl)\n        if session == _ffi.NULL:\n            return None\n\n        length = _lib.SSL_get_client_random(self._ssl, _ffi.NULL, 0)\n        assert length > 0\n        outp = _no_zero_allocator(\"unsigned char[]\", length)\n        _lib.SSL_get_client_random(self._ssl, outp, length)\n        return _ffi.buffer(outp, length)[:]\n\n    def master_key(self):\n        \"\"\"\n        Retrieve the value of the master key for this session.\n\n        :return: A string representing the state\n        \"\"\"\n        session = _lib.SSL_get_session(self._ssl)\n        if session == _ffi.NULL:\n            return None\n\n        length = _lib.SSL_SESSION_get_master_key(session, _ffi.NULL, 0)\n        assert length > 0\n        outp = _no_zero_allocator(\"unsigned char[]\", length)\n        _lib.SSL_SESSION_get_master_key(session, outp, length)\n        return _ffi.buffer(outp, length)[:]\n\n    def export_keying_material(self, label, olen, context=None):\n        \"\"\"\n        Obtain keying material for application use.\n\n        :param: label - a disambiguating label string as described in RFC 5705\n        :param: olen - the length of the exported key material in bytes\n        :param: context - a per-association context value\n        :return: the exported key material bytes or None\n        \"\"\"\n        outp = _no_zero_allocator(\"unsigned char[]\", olen)\n        context_buf = _ffi.NULL\n        context_len = 0\n        use_context = 0\n        if context is not None:\n            context_buf = context\n            context_len = len(context)\n            use_context = 1\n        success = _lib.SSL_export_keying_material(self._ssl, outp, olen,\n                                                  label, len(label),\n                                                  context_buf, context_len,\n                                                  use_context)\n        _openssl_assert(success == 1)\n        return _ffi.buffer(outp, olen)[:]\n\n    def sock_shutdown(self, *args, **kwargs):\n        \"\"\"\n        Call the :meth:`shutdown` method of the underlying socket.\n        See :manpage:`shutdown(2)`.\n\n        :return: What the socket's shutdown() method returns\n        \"\"\"\n        return self._socket.shutdown(*args, **kwargs)\n\n    def get_certificate(self):\n        \"\"\"\n        Retrieve the local certificate (if any)\n\n        :return: The local certificate\n        \"\"\"\n        cert = _lib.SSL_get_certificate(self._ssl)\n        if cert != _ffi.NULL:\n            _lib.X509_up_ref(cert)\n            return X509._from_raw_x509_ptr(cert)\n        return None\n\n    def get_peer_certificate(self):\n        \"\"\"\n        Retrieve the other side's certificate (if any)\n\n        :return: The peer's certificate\n        \"\"\"\n        cert = _lib.SSL_get_peer_certificate(self._ssl)\n        if cert != _ffi.NULL:\n            return X509._from_raw_x509_ptr(cert)\n        return None\n\n    def get_peer_cert_chain(self):\n        \"\"\"\n        Retrieve the other side's certificate (if any)\n\n        :return: A list of X509 instances giving the peer's certificate chain,\n                 or None if it does not have one.\n        \"\"\"\n        cert_stack = _lib.SSL_get_peer_cert_chain(self._ssl)\n        if cert_stack == _ffi.NULL:\n            return None\n\n        result = []\n        for i in range(_lib.sk_X509_num(cert_stack)):\n            # TODO could incref instead of dup here\n            cert = _lib.X509_dup(_lib.sk_X509_value(cert_stack, i))\n            pycert = X509._from_raw_x509_ptr(cert)\n            result.append(pycert)\n        return result\n\n    def want_read(self):\n        \"\"\"\n        Checks if more data has to be read from the transport layer to complete\n        an operation.\n\n        :return: True iff more data has to be read\n        \"\"\"\n        return _lib.SSL_want_read(self._ssl)\n\n    def want_write(self):\n        \"\"\"\n        Checks if there is data to write to the transport layer to complete an\n        operation.\n\n        :return: True iff there is data to write\n        \"\"\"\n        return _lib.SSL_want_write(self._ssl)\n\n    def set_accept_state(self):\n        \"\"\"\n        Set the connection to work in server mode. The handshake will be\n        handled automatically by read/write.\n\n        :return: None\n        \"\"\"\n        _lib.SSL_set_accept_state(self._ssl)\n\n    def set_connect_state(self):\n        \"\"\"\n        Set the connection to work in client mode. The handshake will be\n        handled automatically by read/write.\n\n        :return: None\n        \"\"\"\n        _lib.SSL_set_connect_state(self._ssl)\n\n    def get_session(self):\n        \"\"\"\n        Returns the Session currently used.\n\n        :return: An instance of :class:`OpenSSL.SSL.Session` or\n            :obj:`None` if no session exists.\n\n        .. versionadded:: 0.14\n        \"\"\"\n        session = _lib.SSL_get1_session(self._ssl)\n        if session == _ffi.NULL:\n            return None\n\n        pysession = Session.__new__(Session)\n        pysession._session = _ffi.gc(session, _lib.SSL_SESSION_free)\n        return pysession\n\n    def set_session(self, session):\n        \"\"\"\n        Set the session to be used when the TLS/SSL connection is established.\n\n        :param session: A Session instance representing the session to use.\n        :returns: None\n\n        .. versionadded:: 0.14\n        \"\"\"\n        if not isinstance(session, Session):\n            raise TypeError(\"session must be a Session instance\")\n\n        result = _lib.SSL_set_session(self._ssl, session._session)\n        if not result:\n            _raise_current_error()\n\n    def _get_finished_message(self, function):\n        \"\"\"\n        Helper to implement :meth:`get_finished` and\n        :meth:`get_peer_finished`.\n\n        :param function: Either :data:`SSL_get_finished`: or\n            :data:`SSL_get_peer_finished`.\n\n        :return: :data:`None` if the desired message has not yet been\n            received, otherwise the contents of the message.\n        :rtype: :class:`bytes` or :class:`NoneType`\n        \"\"\"\n        # The OpenSSL documentation says nothing about what might happen if the\n        # count argument given is zero.  Specifically, it doesn't say whether\n        # the output buffer may be NULL in that case or not.  Inspection of the\n        # implementation reveals that it calls memcpy() unconditionally.\n        # Section 7.1.4, paragraph 1 of the C standard suggests that\n        # memcpy(NULL, source, 0) is not guaranteed to produce defined (let\n        # alone desirable) behavior (though it probably does on just about\n        # every implementation...)\n        #\n        # Allocate a tiny buffer to pass in (instead of just passing NULL as\n        # one might expect) for the initial call so as to be safe against this\n        # potentially undefined behavior.\n        empty = _ffi.new(\"char[]\", 0)\n        size = function(self._ssl, empty, 0)\n        if size == 0:\n            # No Finished message so far.\n            return None\n\n        buf = _no_zero_allocator(\"char[]\", size)\n        function(self._ssl, buf, size)\n        return _ffi.buffer(buf, size)[:]\n\n    def get_finished(self):\n        \"\"\"\n        Obtain the latest TLS Finished message that we sent.\n\n        :return: The contents of the message or :obj:`None` if the TLS\n            handshake has not yet completed.\n        :rtype: :class:`bytes` or :class:`NoneType`\n\n        .. versionadded:: 0.15\n        \"\"\"\n        return self._get_finished_message(_lib.SSL_get_finished)\n\n    def get_peer_finished(self):\n        \"\"\"\n        Obtain the latest TLS Finished message that we received from the peer.\n\n        :return: The contents of the message or :obj:`None` if the TLS\n            handshake has not yet completed.\n        :rtype: :class:`bytes` or :class:`NoneType`\n\n        .. versionadded:: 0.15\n        \"\"\"\n        return self._get_finished_message(_lib.SSL_get_peer_finished)\n\n    def get_cipher_name(self):\n        \"\"\"\n        Obtain the name of the currently used cipher.\n\n        :returns: The name of the currently used cipher or :obj:`None`\n            if no connection has been established.\n        :rtype: :class:`unicode` or :class:`NoneType`\n\n        .. versionadded:: 0.15\n        \"\"\"\n        cipher = _lib.SSL_get_current_cipher(self._ssl)\n        if cipher == _ffi.NULL:\n            return None\n        else:\n            name = _ffi.string(_lib.SSL_CIPHER_get_name(cipher))\n            return name.decode(\"utf-8\")\n\n    def get_cipher_bits(self):\n        \"\"\"\n        Obtain the number of secret bits of the currently used cipher.\n\n        :returns: The number of secret bits of the currently used cipher\n            or :obj:`None` if no connection has been established.\n        :rtype: :class:`int` or :class:`NoneType`\n\n        .. versionadded:: 0.15\n        \"\"\"\n        cipher = _lib.SSL_get_current_cipher(self._ssl)\n        if cipher == _ffi.NULL:\n            return None\n        else:\n            return _lib.SSL_CIPHER_get_bits(cipher, _ffi.NULL)\n\n    def get_cipher_version(self):\n        \"\"\"\n        Obtain the protocol version of the currently used cipher.\n\n        :returns: The protocol name of the currently used cipher\n            or :obj:`None` if no connection has been established.\n        :rtype: :class:`unicode` or :class:`NoneType`\n\n        .. versionadded:: 0.15\n        \"\"\"\n        cipher = _lib.SSL_get_current_cipher(self._ssl)\n        if cipher == _ffi.NULL:\n            return None\n        else:\n            version = _ffi.string(_lib.SSL_CIPHER_get_version(cipher))\n            return version.decode(\"utf-8\")\n\n    def get_protocol_version_name(self):\n        \"\"\"\n        Retrieve the protocol version of the current connection.\n\n        :returns: The TLS version of the current connection, for example\n            the value for TLS 1.2 would be ``TLSv1.2``or ``Unknown``\n            for connections that were not successfully established.\n        :rtype: :class:`unicode`\n        \"\"\"\n        version = _ffi.string(_lib.SSL_get_version(self._ssl))\n        return version.decode(\"utf-8\")\n\n    def get_protocol_version(self):\n        \"\"\"\n        Retrieve the SSL or TLS protocol version of the current connection.\n\n        :returns: The TLS version of the current connection.  For example,\n            it will return ``0x769`` for connections made over TLS version 1.\n        :rtype: :class:`int`\n        \"\"\"\n        version = _lib.SSL_version(self._ssl)\n        return version\n\n    @_requires_npn\n    def get_next_proto_negotiated(self):\n        \"\"\"\n        Get the protocol that was negotiated by NPN.\n\n        :returns: A bytestring of the protocol name.  If no protocol has been\n            negotiated yet, returns an empty string.\n\n        .. versionadded:: 0.15\n        \"\"\"\n        data = _ffi.new(\"unsigned char **\")\n        data_len = _ffi.new(\"unsigned int *\")\n\n        _lib.SSL_get0_next_proto_negotiated(self._ssl, data, data_len)\n\n        return _ffi.buffer(data[0], data_len[0])[:]\n\n    @_requires_alpn\n    def set_alpn_protos(self, protos):\n        \"\"\"\n        Specify the client's ALPN protocol list.\n\n        These protocols are offered to the server during protocol negotiation.\n\n        :param protos: A list of the protocols to be offered to the server.\n            This list should be a Python list of bytestrings representing the\n            protocols to offer, e.g. ``[b'http/1.1', b'spdy/2']``.\n        \"\"\"\n        # Take the list of protocols and join them together, prefixing them\n        # with their lengths.\n        protostr = b''.join(\n            chain.from_iterable((int2byte(len(p)), p) for p in protos)\n        )\n\n        # Build a C string from the list. We don't need to save this off\n        # because OpenSSL immediately copies the data out.\n        input_str = _ffi.new(\"unsigned char[]\", protostr)\n        _lib.SSL_set_alpn_protos(self._ssl, input_str, len(protostr))\n\n    @_requires_alpn\n    def get_alpn_proto_negotiated(self):\n        \"\"\"\n        Get the protocol that was negotiated by ALPN.\n\n        :returns: A bytestring of the protocol name.  If no protocol has been\n            negotiated yet, returns an empty string.\n        \"\"\"\n        data = _ffi.new(\"unsigned char **\")\n        data_len = _ffi.new(\"unsigned int *\")\n\n        _lib.SSL_get0_alpn_selected(self._ssl, data, data_len)\n\n        if not data_len:\n            return b''\n\n        return _ffi.buffer(data[0], data_len[0])[:]\n\n    def request_ocsp(self):\n        \"\"\"\n        Called to request that the server sends stapled OCSP data, if\n        available. If this is not called on the client side then the server\n        will not send OCSP data. Should be used in conjunction with\n        :meth:`Context.set_ocsp_client_callback`.\n        \"\"\"\n        rc = _lib.SSL_set_tlsext_status_type(\n            self._ssl, _lib.TLSEXT_STATUSTYPE_ocsp\n        )\n        _openssl_assert(rc == 1)\n\n\nConnectionType = deprecated(\n    Connection, __name__,\n    \"ConnectionType has been deprecated, use Connection instead\",\n    DeprecationWarning\n)\n\n# This is similar to the initialization calls at the end of OpenSSL/crypto.py\n# but is exercised mostly by the Context initializer.\n_lib.SSL_library_init()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/OpenSSL/__init__.py",
    "content": "# Copyright (C) AB Strakt\n# See LICENSE for details.\n\n\"\"\"\npyOpenSSL - A simple wrapper around the OpenSSL library\n\"\"\"\n\nfrom OpenSSL import crypto, SSL\nfrom OpenSSL.version import (\n    __author__, __copyright__, __email__, __license__, __summary__, __title__,\n    __uri__, __version__,\n)\n\n\n__all__ = [\n    \"SSL\", \"crypto\",\n\n    \"__author__\", \"__copyright__\", \"__email__\", \"__license__\", \"__summary__\",\n    \"__title__\", \"__uri__\", \"__version__\",\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/OpenSSL/_util.py",
    "content": "import sys\nimport warnings\n\nfrom six import PY3, binary_type, text_type\n\nfrom cryptography.hazmat.bindings.openssl.binding import Binding\n\n\nbinding = Binding()\nbinding.init_static_locks()\nffi = binding.ffi\nlib = binding.lib\n\n\n# This is a special CFFI allocator that does not bother to zero its memory\n# after allocation. This has vastly better performance on large allocations and\n# so should be used whenever we don't need the memory zeroed out.\nno_zero_allocator = ffi.new_allocator(should_clear_after_alloc=False)\n\n\ndef text(charp):\n    \"\"\"\n    Get a native string type representing of the given CFFI ``char*`` object.\n\n    :param charp: A C-style string represented using CFFI.\n\n    :return: :class:`str`\n    \"\"\"\n    if not charp:\n        return \"\"\n    return native(ffi.string(charp))\n\n\ndef exception_from_error_queue(exception_type):\n    \"\"\"\n    Convert an OpenSSL library failure into a Python exception.\n\n    When a call to the native OpenSSL library fails, this is usually signalled\n    by the return value, and an error code is stored in an error queue\n    associated with the current thread. The err library provides functions to\n    obtain these error codes and textual error messages.\n    \"\"\"\n    errors = []\n\n    while True:\n        error = lib.ERR_get_error()\n        if error == 0:\n            break\n        errors.append((\n            text(lib.ERR_lib_error_string(error)),\n            text(lib.ERR_func_error_string(error)),\n            text(lib.ERR_reason_error_string(error))))\n\n    raise exception_type(errors)\n\n\ndef make_assert(error):\n    \"\"\"\n    Create an assert function that uses :func:`exception_from_error_queue` to\n    raise an exception wrapped by *error*.\n    \"\"\"\n    def openssl_assert(ok):\n        \"\"\"\n        If *ok* is not True, retrieve the error from OpenSSL and raise it.\n        \"\"\"\n        if ok is not True:\n            exception_from_error_queue(error)\n\n    return openssl_assert\n\n\ndef native(s):\n    \"\"\"\n    Convert :py:class:`bytes` or :py:class:`unicode` to the native\n    :py:class:`str` type, using UTF-8 encoding if conversion is necessary.\n\n    :raise UnicodeError: The input string is not UTF-8 decodeable.\n\n    :raise TypeError: The input is neither :py:class:`bytes` nor\n        :py:class:`unicode`.\n    \"\"\"\n    if not isinstance(s, (binary_type, text_type)):\n        raise TypeError(\"%r is neither bytes nor unicode\" % s)\n    if PY3:\n        if isinstance(s, binary_type):\n            return s.decode(\"utf-8\")\n    else:\n        if isinstance(s, text_type):\n            return s.encode(\"utf-8\")\n    return s\n\n\ndef path_string(s):\n    \"\"\"\n    Convert a Python string to a :py:class:`bytes` string identifying the same\n    path and which can be passed into an OpenSSL API accepting a filename.\n\n    :param s: An instance of :py:class:`bytes` or :py:class:`unicode`.\n\n    :return: An instance of :py:class:`bytes`.\n    \"\"\"\n    if isinstance(s, binary_type):\n        return s\n    elif isinstance(s, text_type):\n        return s.encode(sys.getfilesystemencoding())\n    else:\n        raise TypeError(\"Path must be represented as bytes or unicode string\")\n\n\nif PY3:\n    def byte_string(s):\n        return s.encode(\"charmap\")\nelse:\n    def byte_string(s):\n        return s\n\n\n# A marker object to observe whether some optional arguments are passed any\n# value or not.\nUNSPECIFIED = object()\n\n_TEXT_WARNING = (\n    text_type.__name__ + \" for {0} is no longer accepted, use bytes\"\n)\n\n\ndef text_to_bytes_and_warn(label, obj):\n    \"\"\"\n    If ``obj`` is text, emit a warning that it should be bytes instead and try\n    to convert it to bytes automatically.\n\n    :param str label: The name of the parameter from which ``obj`` was taken\n        (so a developer can easily find the source of the problem and correct\n        it).\n\n    :return: If ``obj`` is the text string type, a ``bytes`` object giving the\n        UTF-8 encoding of that text is returned.  Otherwise, ``obj`` itself is\n        returned.\n    \"\"\"\n    if isinstance(obj, text_type):\n        warnings.warn(\n            _TEXT_WARNING.format(label),\n            category=DeprecationWarning,\n            stacklevel=3\n        )\n        return obj.encode('utf-8')\n    return obj\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/OpenSSL/crypto.py",
    "content": "import datetime\n\nfrom base64 import b16encode\nfrom functools import partial\nfrom operator import __eq__, __ne__, __lt__, __le__, __gt__, __ge__\n\nfrom six import (\n    integer_types as _integer_types,\n    text_type as _text_type,\n    PY3 as _PY3)\n\nfrom cryptography import x509\nfrom cryptography.hazmat.primitives.asymmetric import dsa, rsa\nfrom cryptography.utils import deprecated\n\nfrom OpenSSL._util import (\n    ffi as _ffi,\n    lib as _lib,\n    exception_from_error_queue as _exception_from_error_queue,\n    byte_string as _byte_string,\n    native as _native,\n    UNSPECIFIED as _UNSPECIFIED,\n    text_to_bytes_and_warn as _text_to_bytes_and_warn,\n    make_assert as _make_assert,\n)\n\n__all__ = [\n    'FILETYPE_PEM',\n    'FILETYPE_ASN1',\n    'FILETYPE_TEXT',\n    'TYPE_RSA',\n    'TYPE_DSA',\n    'Error',\n    'PKey',\n    'get_elliptic_curves',\n    'get_elliptic_curve',\n    'X509Name',\n    'X509Extension',\n    'X509Req',\n    'X509',\n    'X509StoreFlags',\n    'X509Store',\n    'X509StoreContextError',\n    'X509StoreContext',\n    'load_certificate',\n    'dump_certificate',\n    'dump_publickey',\n    'dump_privatekey',\n    'Revoked',\n    'CRL',\n    'PKCS7',\n    'PKCS12',\n    'NetscapeSPKI',\n    'load_publickey',\n    'load_privatekey',\n    'dump_certificate_request',\n    'load_certificate_request',\n    'sign',\n    'verify',\n    'dump_crl',\n    'load_crl',\n    'load_pkcs7_data',\n    'load_pkcs12'\n]\n\nFILETYPE_PEM = _lib.SSL_FILETYPE_PEM\nFILETYPE_ASN1 = _lib.SSL_FILETYPE_ASN1\n\n# TODO This was an API mistake.  OpenSSL has no such constant.\nFILETYPE_TEXT = 2 ** 16 - 1\n\nTYPE_RSA = _lib.EVP_PKEY_RSA\nTYPE_DSA = _lib.EVP_PKEY_DSA\nTYPE_DH = _lib.EVP_PKEY_DH\nTYPE_EC = _lib.EVP_PKEY_EC\n\n\nclass Error(Exception):\n    \"\"\"\n    An error occurred in an `OpenSSL.crypto` API.\n    \"\"\"\n\n\n_raise_current_error = partial(_exception_from_error_queue, Error)\n_openssl_assert = _make_assert(Error)\n\n\ndef _get_backend():\n    \"\"\"\n    Importing the backend from cryptography has the side effect of activating\n    the osrandom engine. This mutates the global state of OpenSSL in the\n    process and causes issues for various programs that use subinterpreters or\n    embed Python. By putting the import in this function we can avoid\n    triggering this side effect unless _get_backend is called.\n    \"\"\"\n    from cryptography.hazmat.backends.openssl.backend import backend\n    return backend\n\n\ndef _untested_error(where):\n    \"\"\"\n    An OpenSSL API failed somehow.  Additionally, the failure which was\n    encountered isn't one that's exercised by the test suite so future behavior\n    of pyOpenSSL is now somewhat less predictable.\n    \"\"\"\n    raise RuntimeError(\"Unknown %s failure\" % (where,))\n\n\ndef _new_mem_buf(buffer=None):\n    \"\"\"\n    Allocate a new OpenSSL memory BIO.\n\n    Arrange for the garbage collector to clean it up automatically.\n\n    :param buffer: None or some bytes to use to put into the BIO so that they\n        can be read out.\n    \"\"\"\n    if buffer is None:\n        bio = _lib.BIO_new(_lib.BIO_s_mem())\n        free = _lib.BIO_free\n    else:\n        data = _ffi.new(\"char[]\", buffer)\n        bio = _lib.BIO_new_mem_buf(data, len(buffer))\n\n        # Keep the memory alive as long as the bio is alive!\n        def free(bio, ref=data):\n            return _lib.BIO_free(bio)\n\n    _openssl_assert(bio != _ffi.NULL)\n\n    bio = _ffi.gc(bio, free)\n    return bio\n\n\ndef _bio_to_string(bio):\n    \"\"\"\n    Copy the contents of an OpenSSL BIO object into a Python byte string.\n    \"\"\"\n    result_buffer = _ffi.new('char**')\n    buffer_length = _lib.BIO_get_mem_data(bio, result_buffer)\n    return _ffi.buffer(result_buffer[0], buffer_length)[:]\n\n\ndef _set_asn1_time(boundary, when):\n    \"\"\"\n    The the time value of an ASN1 time object.\n\n    @param boundary: An ASN1_TIME pointer (or an object safely\n        castable to that type) which will have its value set.\n    @param when: A string representation of the desired time value.\n\n    @raise TypeError: If C{when} is not a L{bytes} string.\n    @raise ValueError: If C{when} does not represent a time in the required\n        format.\n    @raise RuntimeError: If the time value cannot be set for some other\n        (unspecified) reason.\n    \"\"\"\n    if not isinstance(when, bytes):\n        raise TypeError(\"when must be a byte string\")\n\n    set_result = _lib.ASN1_TIME_set_string(boundary, when)\n    if set_result == 0:\n        raise ValueError(\"Invalid string\")\n\n\ndef _get_asn1_time(timestamp):\n    \"\"\"\n    Retrieve the time value of an ASN1 time object.\n\n    @param timestamp: An ASN1_GENERALIZEDTIME* (or an object safely castable to\n        that type) from which the time value will be retrieved.\n\n    @return: The time value from C{timestamp} as a L{bytes} string in a certain\n        format.  Or C{None} if the object contains no time value.\n    \"\"\"\n    string_timestamp = _ffi.cast('ASN1_STRING*', timestamp)\n    if _lib.ASN1_STRING_length(string_timestamp) == 0:\n        return None\n    elif (\n        _lib.ASN1_STRING_type(string_timestamp) == _lib.V_ASN1_GENERALIZEDTIME\n    ):\n        return _ffi.string(_lib.ASN1_STRING_data(string_timestamp))\n    else:\n        generalized_timestamp = _ffi.new(\"ASN1_GENERALIZEDTIME**\")\n        _lib.ASN1_TIME_to_generalizedtime(timestamp, generalized_timestamp)\n        if generalized_timestamp[0] == _ffi.NULL:\n            # This may happen:\n            #   - if timestamp was not an ASN1_TIME\n            #   - if allocating memory for the ASN1_GENERALIZEDTIME failed\n            #   - if a copy of the time data from timestamp cannot be made for\n            #     the newly allocated ASN1_GENERALIZEDTIME\n            #\n            # These are difficult to test.  cffi enforces the ASN1_TIME type.\n            # Memory allocation failures are a pain to trigger\n            # deterministically.\n            _untested_error(\"ASN1_TIME_to_generalizedtime\")\n        else:\n            string_timestamp = _ffi.cast(\n                \"ASN1_STRING*\", generalized_timestamp[0])\n            string_data = _lib.ASN1_STRING_data(string_timestamp)\n            string_result = _ffi.string(string_data)\n            _lib.ASN1_GENERALIZEDTIME_free(generalized_timestamp[0])\n            return string_result\n\n\nclass _X509NameInvalidator(object):\n    def __init__(self):\n        self._names = []\n\n    def add(self, name):\n        self._names.append(name)\n\n    def clear(self):\n        for name in self._names:\n            # Breaks the object, but also prevents UAF!\n            del name._name\n\n\nclass PKey(object):\n    \"\"\"\n    A class representing an DSA or RSA public key or key pair.\n    \"\"\"\n    _only_public = False\n    _initialized = True\n\n    def __init__(self):\n        pkey = _lib.EVP_PKEY_new()\n        self._pkey = _ffi.gc(pkey, _lib.EVP_PKEY_free)\n        self._initialized = False\n\n    def to_cryptography_key(self):\n        \"\"\"\n        Export as a ``cryptography`` key.\n\n        :rtype: One of ``cryptography``'s `key interfaces`_.\n\n        .. _key interfaces: https://cryptography.io/en/latest/hazmat/\\\n            primitives/asymmetric/rsa/#key-interfaces\n\n        .. versionadded:: 16.1.0\n        \"\"\"\n        backend = _get_backend()\n        if self._only_public:\n            return backend._evp_pkey_to_public_key(self._pkey)\n        else:\n            return backend._evp_pkey_to_private_key(self._pkey)\n\n    @classmethod\n    def from_cryptography_key(cls, crypto_key):\n        \"\"\"\n        Construct based on a ``cryptography`` *crypto_key*.\n\n        :param crypto_key: A ``cryptography`` key.\n        :type crypto_key: One of ``cryptography``'s `key interfaces`_.\n\n        :rtype: PKey\n\n        .. versionadded:: 16.1.0\n        \"\"\"\n        pkey = cls()\n        if not isinstance(crypto_key, (rsa.RSAPublicKey, rsa.RSAPrivateKey,\n                                       dsa.DSAPublicKey, dsa.DSAPrivateKey)):\n            raise TypeError(\"Unsupported key type\")\n\n        pkey._pkey = crypto_key._evp_pkey\n        if isinstance(crypto_key, (rsa.RSAPublicKey, dsa.DSAPublicKey)):\n            pkey._only_public = True\n        pkey._initialized = True\n        return pkey\n\n    def generate_key(self, type, bits):\n        \"\"\"\n        Generate a key pair of the given type, with the given number of bits.\n\n        This generates a key \"into\" the this object.\n\n        :param type: The key type.\n        :type type: :py:data:`TYPE_RSA` or :py:data:`TYPE_DSA`\n        :param bits: The number of bits.\n        :type bits: :py:data:`int` ``>= 0``\n        :raises TypeError: If :py:data:`type` or :py:data:`bits` isn't\n            of the appropriate type.\n        :raises ValueError: If the number of bits isn't an integer of\n            the appropriate size.\n        :return: ``None``\n        \"\"\"\n        if not isinstance(type, int):\n            raise TypeError(\"type must be an integer\")\n\n        if not isinstance(bits, int):\n            raise TypeError(\"bits must be an integer\")\n\n        if type == TYPE_RSA:\n            if bits <= 0:\n                raise ValueError(\"Invalid number of bits\")\n\n            # TODO Check error return\n            exponent = _lib.BN_new()\n            exponent = _ffi.gc(exponent, _lib.BN_free)\n            _lib.BN_set_word(exponent, _lib.RSA_F4)\n\n            rsa = _lib.RSA_new()\n\n            result = _lib.RSA_generate_key_ex(rsa, bits, exponent, _ffi.NULL)\n            _openssl_assert(result == 1)\n\n            result = _lib.EVP_PKEY_assign_RSA(self._pkey, rsa)\n            _openssl_assert(result == 1)\n\n        elif type == TYPE_DSA:\n            dsa = _lib.DSA_new()\n            _openssl_assert(dsa != _ffi.NULL)\n\n            dsa = _ffi.gc(dsa, _lib.DSA_free)\n            res = _lib.DSA_generate_parameters_ex(\n                dsa, bits, _ffi.NULL, 0, _ffi.NULL, _ffi.NULL, _ffi.NULL\n            )\n            _openssl_assert(res == 1)\n\n            _openssl_assert(_lib.DSA_generate_key(dsa) == 1)\n            _openssl_assert(_lib.EVP_PKEY_set1_DSA(self._pkey, dsa) == 1)\n        else:\n            raise Error(\"No such key type\")\n\n        self._initialized = True\n\n    def check(self):\n        \"\"\"\n        Check the consistency of an RSA private key.\n\n        This is the Python equivalent of OpenSSL's ``RSA_check_key``.\n\n        :return: ``True`` if key is consistent.\n\n        :raise OpenSSL.crypto.Error: if the key is inconsistent.\n\n        :raise TypeError: if the key is of a type which cannot be checked.\n            Only RSA keys can currently be checked.\n        \"\"\"\n        if self._only_public:\n            raise TypeError(\"public key only\")\n\n        if _lib.EVP_PKEY_type(self.type()) != _lib.EVP_PKEY_RSA:\n            raise TypeError(\"key type unsupported\")\n\n        rsa = _lib.EVP_PKEY_get1_RSA(self._pkey)\n        rsa = _ffi.gc(rsa, _lib.RSA_free)\n        result = _lib.RSA_check_key(rsa)\n        if result:\n            return True\n        _raise_current_error()\n\n    def type(self):\n        \"\"\"\n        Returns the type of the key\n\n        :return: The type of the key.\n        \"\"\"\n        return _lib.EVP_PKEY_id(self._pkey)\n\n    def bits(self):\n        \"\"\"\n        Returns the number of bits of the key\n\n        :return: The number of bits of the key.\n        \"\"\"\n        return _lib.EVP_PKEY_bits(self._pkey)\n\n\nPKeyType = deprecated(\n    PKey, __name__,\n    \"PKeyType has been deprecated, use PKey instead\",\n    DeprecationWarning\n)\n\n\nclass _EllipticCurve(object):\n    \"\"\"\n    A representation of a supported elliptic curve.\n\n    @cvar _curves: :py:obj:`None` until an attempt is made to load the curves.\n        Thereafter, a :py:type:`set` containing :py:type:`_EllipticCurve`\n        instances each of which represents one curve supported by the system.\n    @type _curves: :py:type:`NoneType` or :py:type:`set`\n    \"\"\"\n    _curves = None\n\n    if _PY3:\n        # This only necessary on Python 3.  Morever, it is broken on Python 2.\n        def __ne__(self, other):\n            \"\"\"\n            Implement cooperation with the right-hand side argument of ``!=``.\n\n            Python 3 seems to have dropped this cooperation in this very narrow\n            circumstance.\n            \"\"\"\n            if isinstance(other, _EllipticCurve):\n                return super(_EllipticCurve, self).__ne__(other)\n            return NotImplemented\n\n    @classmethod\n    def _load_elliptic_curves(cls, lib):\n        \"\"\"\n        Get the curves supported by OpenSSL.\n\n        :param lib: The OpenSSL library binding object.\n\n        :return: A :py:type:`set` of ``cls`` instances giving the names of the\n            elliptic curves the underlying library supports.\n        \"\"\"\n        num_curves = lib.EC_get_builtin_curves(_ffi.NULL, 0)\n        builtin_curves = _ffi.new('EC_builtin_curve[]', num_curves)\n        # The return value on this call should be num_curves again.  We\n        # could check it to make sure but if it *isn't* then.. what could\n        # we do? Abort the whole process, I suppose...?  -exarkun\n        lib.EC_get_builtin_curves(builtin_curves, num_curves)\n        return set(\n            cls.from_nid(lib, c.nid)\n            for c in builtin_curves)\n\n    @classmethod\n    def _get_elliptic_curves(cls, lib):\n        \"\"\"\n        Get, cache, and return the curves supported by OpenSSL.\n\n        :param lib: The OpenSSL library binding object.\n\n        :return: A :py:type:`set` of ``cls`` instances giving the names of the\n            elliptic curves the underlying library supports.\n        \"\"\"\n        if cls._curves is None:\n            cls._curves = cls._load_elliptic_curves(lib)\n        return cls._curves\n\n    @classmethod\n    def from_nid(cls, lib, nid):\n        \"\"\"\n        Instantiate a new :py:class:`_EllipticCurve` associated with the given\n        OpenSSL NID.\n\n        :param lib: The OpenSSL library binding object.\n\n        :param nid: The OpenSSL NID the resulting curve object will represent.\n            This must be a curve NID (and not, for example, a hash NID) or\n            subsequent operations will fail in unpredictable ways.\n        :type nid: :py:class:`int`\n\n        :return: The curve object.\n        \"\"\"\n        return cls(lib, nid, _ffi.string(lib.OBJ_nid2sn(nid)).decode(\"ascii\"))\n\n    def __init__(self, lib, nid, name):\n        \"\"\"\n        :param _lib: The :py:mod:`cryptography` binding instance used to\n            interface with OpenSSL.\n\n        :param _nid: The OpenSSL NID identifying the curve this object\n            represents.\n        :type _nid: :py:class:`int`\n\n        :param name: The OpenSSL short name identifying the curve this object\n            represents.\n        :type name: :py:class:`unicode`\n        \"\"\"\n        self._lib = lib\n        self._nid = nid\n        self.name = name\n\n    def __repr__(self):\n        return \"<Curve %r>\" % (self.name,)\n\n    def _to_EC_KEY(self):\n        \"\"\"\n        Create a new OpenSSL EC_KEY structure initialized to use this curve.\n\n        The structure is automatically garbage collected when the Python object\n        is garbage collected.\n        \"\"\"\n        key = self._lib.EC_KEY_new_by_curve_name(self._nid)\n        return _ffi.gc(key, _lib.EC_KEY_free)\n\n\ndef get_elliptic_curves():\n    \"\"\"\n    Return a set of objects representing the elliptic curves supported in the\n    OpenSSL build in use.\n\n    The curve objects have a :py:class:`unicode` ``name`` attribute by which\n    they identify themselves.\n\n    The curve objects are useful as values for the argument accepted by\n    :py:meth:`Context.set_tmp_ecdh` to specify which elliptical curve should be\n    used for ECDHE key exchange.\n    \"\"\"\n    return _EllipticCurve._get_elliptic_curves(_lib)\n\n\ndef get_elliptic_curve(name):\n    \"\"\"\n    Return a single curve object selected by name.\n\n    See :py:func:`get_elliptic_curves` for information about curve objects.\n\n    :param name: The OpenSSL short name identifying the curve object to\n        retrieve.\n    :type name: :py:class:`unicode`\n\n    If the named curve is not supported then :py:class:`ValueError` is raised.\n    \"\"\"\n    for curve in get_elliptic_curves():\n        if curve.name == name:\n            return curve\n    raise ValueError(\"unknown curve name\", name)\n\n\nclass X509Name(object):\n    \"\"\"\n    An X.509 Distinguished Name.\n\n    :ivar countryName: The country of the entity.\n    :ivar C: Alias for  :py:attr:`countryName`.\n\n    :ivar stateOrProvinceName: The state or province of the entity.\n    :ivar ST: Alias for :py:attr:`stateOrProvinceName`.\n\n    :ivar localityName: The locality of the entity.\n    :ivar L: Alias for :py:attr:`localityName`.\n\n    :ivar organizationName: The organization name of the entity.\n    :ivar O: Alias for :py:attr:`organizationName`.\n\n    :ivar organizationalUnitName: The organizational unit of the entity.\n    :ivar OU: Alias for :py:attr:`organizationalUnitName`\n\n    :ivar commonName: The common name of the entity.\n    :ivar CN: Alias for :py:attr:`commonName`.\n\n    :ivar emailAddress: The e-mail address of the entity.\n    \"\"\"\n\n    def __init__(self, name):\n        \"\"\"\n        Create a new X509Name, copying the given X509Name instance.\n\n        :param name: The name to copy.\n        :type name: :py:class:`X509Name`\n        \"\"\"\n        name = _lib.X509_NAME_dup(name._name)\n        self._name = _ffi.gc(name, _lib.X509_NAME_free)\n\n    def __setattr__(self, name, value):\n        if name.startswith('_'):\n            return super(X509Name, self).__setattr__(name, value)\n\n        # Note: we really do not want str subclasses here, so we do not use\n        # isinstance.\n        if type(name) is not str:\n            raise TypeError(\"attribute name must be string, not '%.200s'\" % (\n                type(value).__name__,))\n\n        nid = _lib.OBJ_txt2nid(_byte_string(name))\n        if nid == _lib.NID_undef:\n            try:\n                _raise_current_error()\n            except Error:\n                pass\n            raise AttributeError(\"No such attribute\")\n\n        # If there's an old entry for this NID, remove it\n        for i in range(_lib.X509_NAME_entry_count(self._name)):\n            ent = _lib.X509_NAME_get_entry(self._name, i)\n            ent_obj = _lib.X509_NAME_ENTRY_get_object(ent)\n            ent_nid = _lib.OBJ_obj2nid(ent_obj)\n            if nid == ent_nid:\n                ent = _lib.X509_NAME_delete_entry(self._name, i)\n                _lib.X509_NAME_ENTRY_free(ent)\n                break\n\n        if isinstance(value, _text_type):\n            value = value.encode('utf-8')\n\n        add_result = _lib.X509_NAME_add_entry_by_NID(\n            self._name, nid, _lib.MBSTRING_UTF8, value, -1, -1, 0)\n        if not add_result:\n            _raise_current_error()\n\n    def __getattr__(self, name):\n        \"\"\"\n        Find attribute. An X509Name object has the following attributes:\n        countryName (alias C), stateOrProvince (alias ST), locality (alias L),\n        organization (alias O), organizationalUnit (alias OU), commonName\n        (alias CN) and more...\n        \"\"\"\n        nid = _lib.OBJ_txt2nid(_byte_string(name))\n        if nid == _lib.NID_undef:\n            # This is a bit weird.  OBJ_txt2nid indicated failure, but it seems\n            # a lower level function, a2d_ASN1_OBJECT, also feels the need to\n            # push something onto the error queue.  If we don't clean that up\n            # now, someone else will bump into it later and be quite confused.\n            # See lp#314814.\n            try:\n                _raise_current_error()\n            except Error:\n                pass\n            return super(X509Name, self).__getattr__(name)\n\n        entry_index = _lib.X509_NAME_get_index_by_NID(self._name, nid, -1)\n        if entry_index == -1:\n            return None\n\n        entry = _lib.X509_NAME_get_entry(self._name, entry_index)\n        data = _lib.X509_NAME_ENTRY_get_data(entry)\n\n        result_buffer = _ffi.new(\"unsigned char**\")\n        data_length = _lib.ASN1_STRING_to_UTF8(result_buffer, data)\n        _openssl_assert(data_length >= 0)\n\n        try:\n            result = _ffi.buffer(\n                result_buffer[0], data_length\n            )[:].decode('utf-8')\n        finally:\n            # XXX untested\n            _lib.OPENSSL_free(result_buffer[0])\n        return result\n\n    def _cmp(op):\n        def f(self, other):\n            if not isinstance(other, X509Name):\n                return NotImplemented\n            result = _lib.X509_NAME_cmp(self._name, other._name)\n            return op(result, 0)\n        return f\n\n    __eq__ = _cmp(__eq__)\n    __ne__ = _cmp(__ne__)\n\n    __lt__ = _cmp(__lt__)\n    __le__ = _cmp(__le__)\n\n    __gt__ = _cmp(__gt__)\n    __ge__ = _cmp(__ge__)\n\n    def __repr__(self):\n        \"\"\"\n        String representation of an X509Name\n        \"\"\"\n        result_buffer = _ffi.new(\"char[]\", 512)\n        format_result = _lib.X509_NAME_oneline(\n            self._name, result_buffer, len(result_buffer))\n        _openssl_assert(format_result != _ffi.NULL)\n\n        return \"<X509Name object '%s'>\" % (\n            _native(_ffi.string(result_buffer)),)\n\n    def hash(self):\n        \"\"\"\n        Return an integer representation of the first four bytes of the\n        MD5 digest of the DER representation of the name.\n\n        This is the Python equivalent of OpenSSL's ``X509_NAME_hash``.\n\n        :return: The (integer) hash of this name.\n        :rtype: :py:class:`int`\n        \"\"\"\n        return _lib.X509_NAME_hash(self._name)\n\n    def der(self):\n        \"\"\"\n        Return the DER encoding of this name.\n\n        :return: The DER encoded form of this name.\n        :rtype: :py:class:`bytes`\n        \"\"\"\n        result_buffer = _ffi.new('unsigned char**')\n        encode_result = _lib.i2d_X509_NAME(self._name, result_buffer)\n        _openssl_assert(encode_result >= 0)\n\n        string_result = _ffi.buffer(result_buffer[0], encode_result)[:]\n        _lib.OPENSSL_free(result_buffer[0])\n        return string_result\n\n    def get_components(self):\n        \"\"\"\n        Returns the components of this name, as a sequence of 2-tuples.\n\n        :return: The components of this name.\n        :rtype: :py:class:`list` of ``name, value`` tuples.\n        \"\"\"\n        result = []\n        for i in range(_lib.X509_NAME_entry_count(self._name)):\n            ent = _lib.X509_NAME_get_entry(self._name, i)\n\n            fname = _lib.X509_NAME_ENTRY_get_object(ent)\n            fval = _lib.X509_NAME_ENTRY_get_data(ent)\n\n            nid = _lib.OBJ_obj2nid(fname)\n            name = _lib.OBJ_nid2sn(nid)\n\n            # ffi.string does not handle strings containing NULL bytes\n            # (which may have been generated by old, broken software)\n            value = _ffi.buffer(_lib.ASN1_STRING_data(fval),\n                                _lib.ASN1_STRING_length(fval))[:]\n            result.append((_ffi.string(name), value))\n\n        return result\n\n\nX509NameType = deprecated(\n    X509Name, __name__,\n    \"X509NameType has been deprecated, use X509Name instead\",\n    DeprecationWarning\n)\n\n\nclass X509Extension(object):\n    \"\"\"\n    An X.509 v3 certificate extension.\n    \"\"\"\n\n    def __init__(self, type_name, critical, value, subject=None, issuer=None):\n        \"\"\"\n        Initializes an X509 extension.\n\n        :param type_name: The name of the type of extension_ to create.\n        :type type_name: :py:data:`bytes`\n\n        :param bool critical: A flag indicating whether this is a critical\n            extension.\n\n        :param value: The value of the extension.\n        :type value: :py:data:`bytes`\n\n        :param subject: Optional X509 certificate to use as subject.\n        :type subject: :py:class:`X509`\n\n        :param issuer: Optional X509 certificate to use as issuer.\n        :type issuer: :py:class:`X509`\n\n        .. _extension: https://www.openssl.org/docs/manmaster/man5/\n            x509v3_config.html#STANDARD-EXTENSIONS\n        \"\"\"\n        ctx = _ffi.new(\"X509V3_CTX*\")\n\n        # A context is necessary for any extension which uses the r2i\n        # conversion method.  That is, X509V3_EXT_nconf may segfault if passed\n        # a NULL ctx. Start off by initializing most of the fields to NULL.\n        _lib.X509V3_set_ctx(ctx, _ffi.NULL, _ffi.NULL, _ffi.NULL, _ffi.NULL, 0)\n\n        # We have no configuration database - but perhaps we should (some\n        # extensions may require it).\n        _lib.X509V3_set_ctx_nodb(ctx)\n\n        # Initialize the subject and issuer, if appropriate.  ctx is a local,\n        # and as far as I can tell none of the X509V3_* APIs invoked here steal\n        # any references, so no need to mess with reference counts or\n        # duplicates.\n        if issuer is not None:\n            if not isinstance(issuer, X509):\n                raise TypeError(\"issuer must be an X509 instance\")\n            ctx.issuer_cert = issuer._x509\n        if subject is not None:\n            if not isinstance(subject, X509):\n                raise TypeError(\"subject must be an X509 instance\")\n            ctx.subject_cert = subject._x509\n\n        if critical:\n            # There are other OpenSSL APIs which would let us pass in critical\n            # separately, but they're harder to use, and since value is already\n            # a pile of crappy junk smuggling a ton of utterly important\n            # structured data, what's the point of trying to avoid nasty stuff\n            # with strings? (However, X509V3_EXT_i2d in particular seems like\n            # it would be a better API to invoke.  I do not know where to get\n            # the ext_struc it desires for its last parameter, though.)\n            value = b\"critical,\" + value\n\n        extension = _lib.X509V3_EXT_nconf(_ffi.NULL, ctx, type_name, value)\n        if extension == _ffi.NULL:\n            _raise_current_error()\n        self._extension = _ffi.gc(extension, _lib.X509_EXTENSION_free)\n\n    @property\n    def _nid(self):\n        return _lib.OBJ_obj2nid(\n            _lib.X509_EXTENSION_get_object(self._extension)\n        )\n\n    _prefixes = {\n        _lib.GEN_EMAIL: \"email\",\n        _lib.GEN_DNS: \"DNS\",\n        _lib.GEN_URI: \"URI\",\n    }\n\n    def _subjectAltNameString(self):\n        names = _ffi.cast(\n            \"GENERAL_NAMES*\", _lib.X509V3_EXT_d2i(self._extension)\n        )\n\n        names = _ffi.gc(names, _lib.GENERAL_NAMES_free)\n        parts = []\n        for i in range(_lib.sk_GENERAL_NAME_num(names)):\n            name = _lib.sk_GENERAL_NAME_value(names, i)\n            try:\n                label = self._prefixes[name.type]\n            except KeyError:\n                bio = _new_mem_buf()\n                _lib.GENERAL_NAME_print(bio, name)\n                parts.append(_native(_bio_to_string(bio)))\n            else:\n                value = _native(\n                    _ffi.buffer(name.d.ia5.data, name.d.ia5.length)[:])\n                parts.append(label + \":\" + value)\n        return \", \".join(parts)\n\n    def __str__(self):\n        \"\"\"\n        :return: a nice text representation of the extension\n        \"\"\"\n        if _lib.NID_subject_alt_name == self._nid:\n            return self._subjectAltNameString()\n\n        bio = _new_mem_buf()\n        print_result = _lib.X509V3_EXT_print(bio, self._extension, 0, 0)\n        _openssl_assert(print_result != 0)\n\n        return _native(_bio_to_string(bio))\n\n    def get_critical(self):\n        \"\"\"\n        Returns the critical field of this X.509 extension.\n\n        :return: The critical field.\n        \"\"\"\n        return _lib.X509_EXTENSION_get_critical(self._extension)\n\n    def get_short_name(self):\n        \"\"\"\n        Returns the short type name of this X.509 extension.\n\n        The result is a byte string such as :py:const:`b\"basicConstraints\"`.\n\n        :return: The short type name.\n        :rtype: :py:data:`bytes`\n\n        .. versionadded:: 0.12\n        \"\"\"\n        obj = _lib.X509_EXTENSION_get_object(self._extension)\n        nid = _lib.OBJ_obj2nid(obj)\n        return _ffi.string(_lib.OBJ_nid2sn(nid))\n\n    def get_data(self):\n        \"\"\"\n        Returns the data of the X509 extension, encoded as ASN.1.\n\n        :return: The ASN.1 encoded data of this X509 extension.\n        :rtype: :py:data:`bytes`\n\n        .. versionadded:: 0.12\n        \"\"\"\n        octet_result = _lib.X509_EXTENSION_get_data(self._extension)\n        string_result = _ffi.cast('ASN1_STRING*', octet_result)\n        char_result = _lib.ASN1_STRING_data(string_result)\n        result_length = _lib.ASN1_STRING_length(string_result)\n        return _ffi.buffer(char_result, result_length)[:]\n\n\nX509ExtensionType = deprecated(\n    X509Extension, __name__,\n    \"X509ExtensionType has been deprecated, use X509Extension instead\",\n    DeprecationWarning\n)\n\n\nclass X509Req(object):\n    \"\"\"\n    An X.509 certificate signing requests.\n    \"\"\"\n\n    def __init__(self):\n        req = _lib.X509_REQ_new()\n        self._req = _ffi.gc(req, _lib.X509_REQ_free)\n        # Default to version 0.\n        self.set_version(0)\n\n    def to_cryptography(self):\n        \"\"\"\n        Export as a ``cryptography`` certificate signing request.\n\n        :rtype: ``cryptography.x509.CertificateSigningRequest``\n\n        .. versionadded:: 17.1.0\n        \"\"\"\n        from cryptography.hazmat.backends.openssl.x509 import (\n            _CertificateSigningRequest\n        )\n        backend = _get_backend()\n        return _CertificateSigningRequest(backend, self._req)\n\n    @classmethod\n    def from_cryptography(cls, crypto_req):\n        \"\"\"\n        Construct based on a ``cryptography`` *crypto_req*.\n\n        :param crypto_req: A ``cryptography`` X.509 certificate signing request\n        :type crypto_req: ``cryptography.x509.CertificateSigningRequest``\n\n        :rtype: X509Req\n\n        .. versionadded:: 17.1.0\n        \"\"\"\n        if not isinstance(crypto_req, x509.CertificateSigningRequest):\n            raise TypeError(\"Must be a certificate signing request\")\n\n        req = cls()\n        req._req = crypto_req._x509_req\n        return req\n\n    def set_pubkey(self, pkey):\n        \"\"\"\n        Set the public key of the certificate signing request.\n\n        :param pkey: The public key to use.\n        :type pkey: :py:class:`PKey`\n\n        :return: ``None``\n        \"\"\"\n        set_result = _lib.X509_REQ_set_pubkey(self._req, pkey._pkey)\n        _openssl_assert(set_result == 1)\n\n    def get_pubkey(self):\n        \"\"\"\n        Get the public key of the certificate signing request.\n\n        :return: The public key.\n        :rtype: :py:class:`PKey`\n        \"\"\"\n        pkey = PKey.__new__(PKey)\n        pkey._pkey = _lib.X509_REQ_get_pubkey(self._req)\n        _openssl_assert(pkey._pkey != _ffi.NULL)\n        pkey._pkey = _ffi.gc(pkey._pkey, _lib.EVP_PKEY_free)\n        pkey._only_public = True\n        return pkey\n\n    def set_version(self, version):\n        \"\"\"\n        Set the version subfield (RFC 2459, section 4.1.2.1) of the certificate\n        request.\n\n        :param int version: The version number.\n        :return: ``None``\n        \"\"\"\n        set_result = _lib.X509_REQ_set_version(self._req, version)\n        _openssl_assert(set_result == 1)\n\n    def get_version(self):\n        \"\"\"\n        Get the version subfield (RFC 2459, section 4.1.2.1) of the certificate\n        request.\n\n        :return: The value of the version subfield.\n        :rtype: :py:class:`int`\n        \"\"\"\n        return _lib.X509_REQ_get_version(self._req)\n\n    def get_subject(self):\n        \"\"\"\n        Return the subject of this certificate signing request.\n\n        This creates a new :class:`X509Name` that wraps the underlying subject\n        name field on the certificate signing request. Modifying it will modify\n        the underlying signing request, and will have the effect of modifying\n        any other :class:`X509Name` that refers to this subject.\n\n        :return: The subject of this certificate signing request.\n        :rtype: :class:`X509Name`\n        \"\"\"\n        name = X509Name.__new__(X509Name)\n        name._name = _lib.X509_REQ_get_subject_name(self._req)\n        _openssl_assert(name._name != _ffi.NULL)\n\n        # The name is owned by the X509Req structure.  As long as the X509Name\n        # Python object is alive, keep the X509Req Python object alive.\n        name._owner = self\n\n        return name\n\n    def add_extensions(self, extensions):\n        \"\"\"\n        Add extensions to the certificate signing request.\n\n        :param extensions: The X.509 extensions to add.\n        :type extensions: iterable of :py:class:`X509Extension`\n        :return: ``None``\n        \"\"\"\n        stack = _lib.sk_X509_EXTENSION_new_null()\n        _openssl_assert(stack != _ffi.NULL)\n\n        stack = _ffi.gc(stack, _lib.sk_X509_EXTENSION_free)\n\n        for ext in extensions:\n            if not isinstance(ext, X509Extension):\n                raise ValueError(\"One of the elements is not an X509Extension\")\n\n            # TODO push can fail (here and elsewhere)\n            _lib.sk_X509_EXTENSION_push(stack, ext._extension)\n\n        add_result = _lib.X509_REQ_add_extensions(self._req, stack)\n        _openssl_assert(add_result == 1)\n\n    def get_extensions(self):\n        \"\"\"\n        Get X.509 extensions in the certificate signing request.\n\n        :return: The X.509 extensions in this request.\n        :rtype: :py:class:`list` of :py:class:`X509Extension` objects.\n\n        .. versionadded:: 0.15\n        \"\"\"\n        exts = []\n        native_exts_obj = _lib.X509_REQ_get_extensions(self._req)\n        for i in range(_lib.sk_X509_EXTENSION_num(native_exts_obj)):\n            ext = X509Extension.__new__(X509Extension)\n            ext._extension = _lib.sk_X509_EXTENSION_value(native_exts_obj, i)\n            exts.append(ext)\n        return exts\n\n    def sign(self, pkey, digest):\n        \"\"\"\n        Sign the certificate signing request with this key and digest type.\n\n        :param pkey: The key pair to sign with.\n        :type pkey: :py:class:`PKey`\n        :param digest: The name of the message digest to use for the signature,\n            e.g. :py:data:`b\"sha256\"`.\n        :type digest: :py:class:`bytes`\n        :return: ``None``\n        \"\"\"\n        if pkey._only_public:\n            raise ValueError(\"Key has only public part\")\n\n        if not pkey._initialized:\n            raise ValueError(\"Key is uninitialized\")\n\n        digest_obj = _lib.EVP_get_digestbyname(_byte_string(digest))\n        if digest_obj == _ffi.NULL:\n            raise ValueError(\"No such digest method\")\n\n        sign_result = _lib.X509_REQ_sign(self._req, pkey._pkey, digest_obj)\n        _openssl_assert(sign_result > 0)\n\n    def verify(self, pkey):\n        \"\"\"\n        Verifies the signature on this certificate signing request.\n\n        :param PKey key: A public key.\n\n        :return: ``True`` if the signature is correct.\n        :rtype: bool\n\n        :raises OpenSSL.crypto.Error: If the signature is invalid or there is a\n            problem verifying the signature.\n        \"\"\"\n        if not isinstance(pkey, PKey):\n            raise TypeError(\"pkey must be a PKey instance\")\n\n        result = _lib.X509_REQ_verify(self._req, pkey._pkey)\n        if result <= 0:\n            _raise_current_error()\n\n        return result\n\n\nX509ReqType = deprecated(\n    X509Req, __name__,\n    \"X509ReqType has been deprecated, use X509Req instead\",\n    DeprecationWarning\n)\n\n\nclass X509(object):\n    \"\"\"\n    An X.509 certificate.\n    \"\"\"\n    def __init__(self):\n        x509 = _lib.X509_new()\n        _openssl_assert(x509 != _ffi.NULL)\n        self._x509 = _ffi.gc(x509, _lib.X509_free)\n\n        self._issuer_invalidator = _X509NameInvalidator()\n        self._subject_invalidator = _X509NameInvalidator()\n\n    @classmethod\n    def _from_raw_x509_ptr(cls, x509):\n        cert = cls.__new__(cls)\n        cert._x509 = _ffi.gc(x509, _lib.X509_free)\n        cert._issuer_invalidator = _X509NameInvalidator()\n        cert._subject_invalidator = _X509NameInvalidator()\n        return cert\n\n    def to_cryptography(self):\n        \"\"\"\n        Export as a ``cryptography`` certificate.\n\n        :rtype: ``cryptography.x509.Certificate``\n\n        .. versionadded:: 17.1.0\n        \"\"\"\n        from cryptography.hazmat.backends.openssl.x509 import _Certificate\n        backend = _get_backend()\n        return _Certificate(backend, self._x509)\n\n    @classmethod\n    def from_cryptography(cls, crypto_cert):\n        \"\"\"\n        Construct based on a ``cryptography`` *crypto_cert*.\n\n        :param crypto_key: A ``cryptography`` X.509 certificate.\n        :type crypto_key: ``cryptography.x509.Certificate``\n\n        :rtype: X509\n\n        .. versionadded:: 17.1.0\n        \"\"\"\n        if not isinstance(crypto_cert, x509.Certificate):\n            raise TypeError(\"Must be a certificate\")\n\n        cert = cls()\n        cert._x509 = crypto_cert._x509\n        return cert\n\n    def set_version(self, version):\n        \"\"\"\n        Set the version number of the certificate. Note that the\n        version value is zero-based, eg. a value of 0 is V1.\n\n        :param version: The version number of the certificate.\n        :type version: :py:class:`int`\n\n        :return: ``None``\n        \"\"\"\n        if not isinstance(version, int):\n            raise TypeError(\"version must be an integer\")\n\n        _lib.X509_set_version(self._x509, version)\n\n    def get_version(self):\n        \"\"\"\n        Return the version number of the certificate.\n\n        :return: The version number of the certificate.\n        :rtype: :py:class:`int`\n        \"\"\"\n        return _lib.X509_get_version(self._x509)\n\n    def get_pubkey(self):\n        \"\"\"\n        Get the public key of the certificate.\n\n        :return: The public key.\n        :rtype: :py:class:`PKey`\n        \"\"\"\n        pkey = PKey.__new__(PKey)\n        pkey._pkey = _lib.X509_get_pubkey(self._x509)\n        if pkey._pkey == _ffi.NULL:\n            _raise_current_error()\n        pkey._pkey = _ffi.gc(pkey._pkey, _lib.EVP_PKEY_free)\n        pkey._only_public = True\n        return pkey\n\n    def set_pubkey(self, pkey):\n        \"\"\"\n        Set the public key of the certificate.\n\n        :param pkey: The public key.\n        :type pkey: :py:class:`PKey`\n\n        :return: :py:data:`None`\n        \"\"\"\n        if not isinstance(pkey, PKey):\n            raise TypeError(\"pkey must be a PKey instance\")\n\n        set_result = _lib.X509_set_pubkey(self._x509, pkey._pkey)\n        _openssl_assert(set_result == 1)\n\n    def sign(self, pkey, digest):\n        \"\"\"\n        Sign the certificate with this key and digest type.\n\n        :param pkey: The key to sign with.\n        :type pkey: :py:class:`PKey`\n\n        :param digest: The name of the message digest to use.\n        :type digest: :py:class:`bytes`\n\n        :return: :py:data:`None`\n        \"\"\"\n        if not isinstance(pkey, PKey):\n            raise TypeError(\"pkey must be a PKey instance\")\n\n        if pkey._only_public:\n            raise ValueError(\"Key only has public part\")\n\n        if not pkey._initialized:\n            raise ValueError(\"Key is uninitialized\")\n\n        evp_md = _lib.EVP_get_digestbyname(_byte_string(digest))\n        if evp_md == _ffi.NULL:\n            raise ValueError(\"No such digest method\")\n\n        sign_result = _lib.X509_sign(self._x509, pkey._pkey, evp_md)\n        _openssl_assert(sign_result > 0)\n\n    def get_signature_algorithm(self):\n        \"\"\"\n        Return the signature algorithm used in the certificate.\n\n        :return: The name of the algorithm.\n        :rtype: :py:class:`bytes`\n\n        :raises ValueError: If the signature algorithm is undefined.\n\n        .. versionadded:: 0.13\n        \"\"\"\n        algor = _lib.X509_get0_tbs_sigalg(self._x509)\n        nid = _lib.OBJ_obj2nid(algor.algorithm)\n        if nid == _lib.NID_undef:\n            raise ValueError(\"Undefined signature algorithm\")\n        return _ffi.string(_lib.OBJ_nid2ln(nid))\n\n    def digest(self, digest_name):\n        \"\"\"\n        Return the digest of the X509 object.\n\n        :param digest_name: The name of the digest algorithm to use.\n        :type digest_name: :py:class:`bytes`\n\n        :return: The digest of the object, formatted as\n            :py:const:`b\":\"`-delimited hex pairs.\n        :rtype: :py:class:`bytes`\n        \"\"\"\n        digest = _lib.EVP_get_digestbyname(_byte_string(digest_name))\n        if digest == _ffi.NULL:\n            raise ValueError(\"No such digest method\")\n\n        result_buffer = _ffi.new(\"unsigned char[]\", _lib.EVP_MAX_MD_SIZE)\n        result_length = _ffi.new(\"unsigned int[]\", 1)\n        result_length[0] = len(result_buffer)\n\n        digest_result = _lib.X509_digest(\n            self._x509, digest, result_buffer, result_length)\n        _openssl_assert(digest_result == 1)\n\n        return b\":\".join([\n            b16encode(ch).upper() for ch\n            in _ffi.buffer(result_buffer, result_length[0])])\n\n    def subject_name_hash(self):\n        \"\"\"\n        Return the hash of the X509 subject.\n\n        :return: The hash of the subject.\n        :rtype: :py:class:`bytes`\n        \"\"\"\n        return _lib.X509_subject_name_hash(self._x509)\n\n    def set_serial_number(self, serial):\n        \"\"\"\n        Set the serial number of the certificate.\n\n        :param serial: The new serial number.\n        :type serial: :py:class:`int`\n\n        :return: :py:data`None`\n        \"\"\"\n        if not isinstance(serial, _integer_types):\n            raise TypeError(\"serial must be an integer\")\n\n        hex_serial = hex(serial)[2:]\n        if not isinstance(hex_serial, bytes):\n            hex_serial = hex_serial.encode('ascii')\n\n        bignum_serial = _ffi.new(\"BIGNUM**\")\n\n        # BN_hex2bn stores the result in &bignum.  Unless it doesn't feel like\n        # it.  If bignum is still NULL after this call, then the return value\n        # is actually the result.  I hope.  -exarkun\n        small_serial = _lib.BN_hex2bn(bignum_serial, hex_serial)\n\n        if bignum_serial[0] == _ffi.NULL:\n            set_result = _lib.ASN1_INTEGER_set(\n                _lib.X509_get_serialNumber(self._x509), small_serial)\n            if set_result:\n                # TODO Not tested\n                _raise_current_error()\n        else:\n            asn1_serial = _lib.BN_to_ASN1_INTEGER(bignum_serial[0], _ffi.NULL)\n            _lib.BN_free(bignum_serial[0])\n            if asn1_serial == _ffi.NULL:\n                # TODO Not tested\n                _raise_current_error()\n            asn1_serial = _ffi.gc(asn1_serial, _lib.ASN1_INTEGER_free)\n            set_result = _lib.X509_set_serialNumber(self._x509, asn1_serial)\n            _openssl_assert(set_result == 1)\n\n    def get_serial_number(self):\n        \"\"\"\n        Return the serial number of this certificate.\n\n        :return: The serial number.\n        :rtype: int\n        \"\"\"\n        asn1_serial = _lib.X509_get_serialNumber(self._x509)\n        bignum_serial = _lib.ASN1_INTEGER_to_BN(asn1_serial, _ffi.NULL)\n        try:\n            hex_serial = _lib.BN_bn2hex(bignum_serial)\n            try:\n                hexstring_serial = _ffi.string(hex_serial)\n                serial = int(hexstring_serial, 16)\n                return serial\n            finally:\n                _lib.OPENSSL_free(hex_serial)\n        finally:\n            _lib.BN_free(bignum_serial)\n\n    def gmtime_adj_notAfter(self, amount):\n        \"\"\"\n        Adjust the time stamp on which the certificate stops being valid.\n\n        :param int amount: The number of seconds by which to adjust the\n            timestamp.\n        :return: ``None``\n        \"\"\"\n        if not isinstance(amount, int):\n            raise TypeError(\"amount must be an integer\")\n\n        notAfter = _lib.X509_get_notAfter(self._x509)\n        _lib.X509_gmtime_adj(notAfter, amount)\n\n    def gmtime_adj_notBefore(self, amount):\n        \"\"\"\n        Adjust the timestamp on which the certificate starts being valid.\n\n        :param amount: The number of seconds by which to adjust the timestamp.\n        :return: ``None``\n        \"\"\"\n        if not isinstance(amount, int):\n            raise TypeError(\"amount must be an integer\")\n\n        notBefore = _lib.X509_get_notBefore(self._x509)\n        _lib.X509_gmtime_adj(notBefore, amount)\n\n    def has_expired(self):\n        \"\"\"\n        Check whether the certificate has expired.\n\n        :return: ``True`` if the certificate has expired, ``False`` otherwise.\n        :rtype: bool\n        \"\"\"\n        time_string = _native(self.get_notAfter())\n        not_after = datetime.datetime.strptime(time_string, \"%Y%m%d%H%M%SZ\")\n\n        return not_after < datetime.datetime.utcnow()\n\n    def _get_boundary_time(self, which):\n        return _get_asn1_time(which(self._x509))\n\n    def get_notBefore(self):\n        \"\"\"\n        Get the timestamp at which the certificate starts being valid.\n\n        The timestamp is formatted as an ASN.1 TIME::\n\n            YYYYMMDDhhmmssZ\n\n        :return: A timestamp string, or ``None`` if there is none.\n        :rtype: bytes or NoneType\n        \"\"\"\n        return self._get_boundary_time(_lib.X509_get_notBefore)\n\n    def _set_boundary_time(self, which, when):\n        return _set_asn1_time(which(self._x509), when)\n\n    def set_notBefore(self, when):\n        \"\"\"\n        Set the timestamp at which the certificate starts being valid.\n\n        The timestamp is formatted as an ASN.1 TIME::\n\n            YYYYMMDDhhmmssZ\n\n        :param bytes when: A timestamp string.\n        :return: ``None``\n        \"\"\"\n        return self._set_boundary_time(_lib.X509_get_notBefore, when)\n\n    def get_notAfter(self):\n        \"\"\"\n        Get the timestamp at which the certificate stops being valid.\n\n        The timestamp is formatted as an ASN.1 TIME::\n\n            YYYYMMDDhhmmssZ\n\n        :return: A timestamp string, or ``None`` if there is none.\n        :rtype: bytes or NoneType\n        \"\"\"\n        return self._get_boundary_time(_lib.X509_get_notAfter)\n\n    def set_notAfter(self, when):\n        \"\"\"\n        Set the timestamp at which the certificate stops being valid.\n\n        The timestamp is formatted as an ASN.1 TIME::\n\n            YYYYMMDDhhmmssZ\n\n        :param bytes when: A timestamp string.\n        :return: ``None``\n        \"\"\"\n        return self._set_boundary_time(_lib.X509_get_notAfter, when)\n\n    def _get_name(self, which):\n        name = X509Name.__new__(X509Name)\n        name._name = which(self._x509)\n        _openssl_assert(name._name != _ffi.NULL)\n\n        # The name is owned by the X509 structure.  As long as the X509Name\n        # Python object is alive, keep the X509 Python object alive.\n        name._owner = self\n\n        return name\n\n    def _set_name(self, which, name):\n        if not isinstance(name, X509Name):\n            raise TypeError(\"name must be an X509Name\")\n        set_result = which(self._x509, name._name)\n        _openssl_assert(set_result == 1)\n\n    def get_issuer(self):\n        \"\"\"\n        Return the issuer of this certificate.\n\n        This creates a new :class:`X509Name` that wraps the underlying issuer\n        name field on the certificate. Modifying it will modify the underlying\n        certificate, and will have the effect of modifying any other\n        :class:`X509Name` that refers to this issuer.\n\n        :return: The issuer of this certificate.\n        :rtype: :class:`X509Name`\n        \"\"\"\n        name = self._get_name(_lib.X509_get_issuer_name)\n        self._issuer_invalidator.add(name)\n        return name\n\n    def set_issuer(self, issuer):\n        \"\"\"\n        Set the issuer of this certificate.\n\n        :param issuer: The issuer.\n        :type issuer: :py:class:`X509Name`\n\n        :return: ``None``\n        \"\"\"\n        self._set_name(_lib.X509_set_issuer_name, issuer)\n        self._issuer_invalidator.clear()\n\n    def get_subject(self):\n        \"\"\"\n        Return the subject of this certificate.\n\n        This creates a new :class:`X509Name` that wraps the underlying subject\n        name field on the certificate. Modifying it will modify the underlying\n        certificate, and will have the effect of modifying any other\n        :class:`X509Name` that refers to this subject.\n\n        :return: The subject of this certificate.\n        :rtype: :class:`X509Name`\n        \"\"\"\n        name = self._get_name(_lib.X509_get_subject_name)\n        self._subject_invalidator.add(name)\n        return name\n\n    def set_subject(self, subject):\n        \"\"\"\n        Set the subject of this certificate.\n\n        :param subject: The subject.\n        :type subject: :py:class:`X509Name`\n\n        :return: ``None``\n        \"\"\"\n        self._set_name(_lib.X509_set_subject_name, subject)\n        self._subject_invalidator.clear()\n\n    def get_extension_count(self):\n        \"\"\"\n        Get the number of extensions on this certificate.\n\n        :return: The number of extensions.\n        :rtype: :py:class:`int`\n\n        .. versionadded:: 0.12\n        \"\"\"\n        return _lib.X509_get_ext_count(self._x509)\n\n    def add_extensions(self, extensions):\n        \"\"\"\n        Add extensions to the certificate.\n\n        :param extensions: The extensions to add.\n        :type extensions: An iterable of :py:class:`X509Extension` objects.\n        :return: ``None``\n        \"\"\"\n        for ext in extensions:\n            if not isinstance(ext, X509Extension):\n                raise ValueError(\"One of the elements is not an X509Extension\")\n\n            add_result = _lib.X509_add_ext(self._x509, ext._extension, -1)\n            if not add_result:\n                _raise_current_error()\n\n    def get_extension(self, index):\n        \"\"\"\n        Get a specific extension of the certificate by index.\n\n        Extensions on a certificate are kept in order. The index\n        parameter selects which extension will be returned.\n\n        :param int index: The index of the extension to retrieve.\n        :return: The extension at the specified index.\n        :rtype: :py:class:`X509Extension`\n        :raises IndexError: If the extension index was out of bounds.\n\n        .. versionadded:: 0.12\n        \"\"\"\n        ext = X509Extension.__new__(X509Extension)\n        ext._extension = _lib.X509_get_ext(self._x509, index)\n        if ext._extension == _ffi.NULL:\n            raise IndexError(\"extension index out of bounds\")\n\n        extension = _lib.X509_EXTENSION_dup(ext._extension)\n        ext._extension = _ffi.gc(extension, _lib.X509_EXTENSION_free)\n        return ext\n\n\nX509Type = deprecated(\n    X509, __name__,\n    \"X509Type has been deprecated, use X509 instead\",\n    DeprecationWarning\n)\n\n\nclass X509StoreFlags(object):\n    \"\"\"\n    Flags for X509 verification, used to change the behavior of\n    :class:`X509Store`.\n\n    See `OpenSSL Verification Flags`_ for details.\n\n    .. _OpenSSL Verification Flags:\n        https://www.openssl.org/docs/manmaster/man3/X509_VERIFY_PARAM_set_flags.html\n    \"\"\"\n    CRL_CHECK = _lib.X509_V_FLAG_CRL_CHECK\n    CRL_CHECK_ALL = _lib.X509_V_FLAG_CRL_CHECK_ALL\n    IGNORE_CRITICAL = _lib.X509_V_FLAG_IGNORE_CRITICAL\n    X509_STRICT = _lib.X509_V_FLAG_X509_STRICT\n    ALLOW_PROXY_CERTS = _lib.X509_V_FLAG_ALLOW_PROXY_CERTS\n    POLICY_CHECK = _lib.X509_V_FLAG_POLICY_CHECK\n    EXPLICIT_POLICY = _lib.X509_V_FLAG_EXPLICIT_POLICY\n    INHIBIT_MAP = _lib.X509_V_FLAG_INHIBIT_MAP\n    NOTIFY_POLICY = _lib.X509_V_FLAG_NOTIFY_POLICY\n    CHECK_SS_SIGNATURE = _lib.X509_V_FLAG_CHECK_SS_SIGNATURE\n    CB_ISSUER_CHECK = _lib.X509_V_FLAG_CB_ISSUER_CHECK\n\n\nclass X509Store(object):\n    \"\"\"\n    An X.509 store.\n\n    An X.509 store is used to describe a context in which to verify a\n    certificate. A description of a context may include a set of certificates\n    to trust, a set of certificate revocation lists, verification flags and\n    more.\n\n    An X.509 store, being only a description, cannot be used by itself to\n    verify a certificate. To carry out the actual verification process, see\n    :class:`X509StoreContext`.\n    \"\"\"\n\n    def __init__(self):\n        store = _lib.X509_STORE_new()\n        self._store = _ffi.gc(store, _lib.X509_STORE_free)\n\n    def add_cert(self, cert):\n        \"\"\"\n        Adds a trusted certificate to this store.\n\n        Adding a certificate with this method adds this certificate as a\n        *trusted* certificate.\n\n        :param X509 cert: The certificate to add to this store.\n\n        :raises TypeError: If the certificate is not an :class:`X509`.\n\n        :raises OpenSSL.crypto.Error: If OpenSSL was unhappy with your\n            certificate.\n\n        :return: ``None`` if the certificate was added successfully.\n        \"\"\"\n        if not isinstance(cert, X509):\n            raise TypeError()\n\n        # As of OpenSSL 1.1.0i adding the same cert to the store more than\n        # once doesn't cause an error. Accordingly, this code now silences\n        # the error for OpenSSL < 1.1.0i as well.\n        if _lib.X509_STORE_add_cert(self._store, cert._x509) == 0:\n            code = _lib.ERR_peek_error()\n            err_reason = _lib.ERR_GET_REASON(code)\n            _openssl_assert(\n                err_reason == _lib.X509_R_CERT_ALREADY_IN_HASH_TABLE\n            )\n            _lib.ERR_clear_error()\n\n    def add_crl(self, crl):\n        \"\"\"\n        Add a certificate revocation list to this store.\n\n        The certificate revocation lists added to a store will only be used if\n        the associated flags are configured to check certificate revocation\n        lists.\n\n        .. versionadded:: 16.1.0\n\n        :param CRL crl: The certificate revocation list to add to this store.\n        :return: ``None`` if the certificate revocation list was added\n            successfully.\n        \"\"\"\n        _openssl_assert(_lib.X509_STORE_add_crl(self._store, crl._crl) != 0)\n\n    def set_flags(self, flags):\n        \"\"\"\n        Set verification flags to this store.\n\n        Verification flags can be combined by oring them together.\n\n        .. note::\n\n          Setting a verification flag sometimes requires clients to add\n          additional information to the store, otherwise a suitable error will\n          be raised.\n\n          For example, in setting flags to enable CRL checking a\n          suitable CRL must be added to the store otherwise an error will be\n          raised.\n\n        .. versionadded:: 16.1.0\n\n        :param int flags: The verification flags to set on this store.\n            See :class:`X509StoreFlags` for available constants.\n        :return: ``None`` if the verification flags were successfully set.\n        \"\"\"\n        _openssl_assert(_lib.X509_STORE_set_flags(self._store, flags) != 0)\n\n    def set_time(self, vfy_time):\n        \"\"\"\n        Set the time against which the certificates are verified.\n\n        Normally the current time is used.\n\n        .. note::\n\n          For example, you can determine if a certificate was valid at a given\n          time.\n\n        .. versionadded:: 17.0.0\n\n        :param datetime vfy_time: The verification time to set on this store.\n        :return: ``None`` if the verification time was successfully set.\n        \"\"\"\n        param = _lib.X509_VERIFY_PARAM_new()\n        param = _ffi.gc(param, _lib.X509_VERIFY_PARAM_free)\n\n        _lib.X509_VERIFY_PARAM_set_time(param, int(vfy_time.strftime('%s')))\n        _openssl_assert(_lib.X509_STORE_set1_param(self._store, param) != 0)\n\n\nX509StoreType = deprecated(\n    X509Store, __name__,\n    \"X509StoreType has been deprecated, use X509Store instead\",\n    DeprecationWarning\n)\n\n\nclass X509StoreContextError(Exception):\n    \"\"\"\n    An exception raised when an error occurred while verifying a certificate\n    using `OpenSSL.X509StoreContext.verify_certificate`.\n\n    :ivar certificate: The certificate which caused verificate failure.\n    :type certificate: :class:`X509`\n    \"\"\"\n\n    def __init__(self, message, certificate):\n        super(X509StoreContextError, self).__init__(message)\n        self.certificate = certificate\n\n\nclass X509StoreContext(object):\n    \"\"\"\n    An X.509 store context.\n\n    An X.509 store context is used to carry out the actual verification process\n    of a certificate in a described context. For describing such a context, see\n    :class:`X509Store`.\n\n    :ivar _store_ctx: The underlying X509_STORE_CTX structure used by this\n        instance.  It is dynamically allocated and automatically garbage\n        collected.\n    :ivar _store: See the ``store`` ``__init__`` parameter.\n    :ivar _cert: See the ``certificate`` ``__init__`` parameter.\n    :param X509Store store: The certificates which will be trusted for the\n        purposes of any verifications.\n    :param X509 certificate: The certificate to be verified.\n    \"\"\"\n\n    def __init__(self, store, certificate):\n        store_ctx = _lib.X509_STORE_CTX_new()\n        self._store_ctx = _ffi.gc(store_ctx, _lib.X509_STORE_CTX_free)\n        self._store = store\n        self._cert = certificate\n        # Make the store context available for use after instantiating this\n        # class by initializing it now. Per testing, subsequent calls to\n        # :meth:`_init` have no adverse affect.\n        self._init()\n\n    def _init(self):\n        \"\"\"\n        Set up the store context for a subsequent verification operation.\n\n        Calling this method more than once without first calling\n        :meth:`_cleanup` will leak memory.\n        \"\"\"\n        ret = _lib.X509_STORE_CTX_init(\n            self._store_ctx, self._store._store, self._cert._x509, _ffi.NULL\n        )\n        if ret <= 0:\n            _raise_current_error()\n\n    def _cleanup(self):\n        \"\"\"\n        Internally cleans up the store context.\n\n        The store context can then be reused with a new call to :meth:`_init`.\n        \"\"\"\n        _lib.X509_STORE_CTX_cleanup(self._store_ctx)\n\n    def _exception_from_context(self):\n        \"\"\"\n        Convert an OpenSSL native context error failure into a Python\n        exception.\n\n        When a call to native OpenSSL X509_verify_cert fails, additional\n        information about the failure can be obtained from the store context.\n        \"\"\"\n        errors = [\n            _lib.X509_STORE_CTX_get_error(self._store_ctx),\n            _lib.X509_STORE_CTX_get_error_depth(self._store_ctx),\n            _native(_ffi.string(_lib.X509_verify_cert_error_string(\n                _lib.X509_STORE_CTX_get_error(self._store_ctx)))),\n        ]\n        # A context error should always be associated with a certificate, so we\n        # expect this call to never return :class:`None`.\n        _x509 = _lib.X509_STORE_CTX_get_current_cert(self._store_ctx)\n        _cert = _lib.X509_dup(_x509)\n        pycert = X509._from_raw_x509_ptr(_cert)\n        return X509StoreContextError(errors, pycert)\n\n    def set_store(self, store):\n        \"\"\"\n        Set the context's X.509 store.\n\n        .. versionadded:: 0.15\n\n        :param X509Store store: The store description which will be used for\n            the purposes of any *future* verifications.\n        \"\"\"\n        self._store = store\n\n    def verify_certificate(self):\n        \"\"\"\n        Verify a certificate in a context.\n\n        .. versionadded:: 0.15\n\n        :raises X509StoreContextError: If an error occurred when validating a\n          certificate in the context. Sets ``certificate`` attribute to\n          indicate which certificate caused the error.\n        \"\"\"\n        # Always re-initialize the store context in case\n        # :meth:`verify_certificate` is called multiple times.\n        #\n        # :meth:`_init` is called in :meth:`__init__` so _cleanup is called\n        # before _init to ensure memory is not leaked.\n        self._cleanup()\n        self._init()\n        ret = _lib.X509_verify_cert(self._store_ctx)\n        self._cleanup()\n        if ret <= 0:\n            raise self._exception_from_context()\n\n\ndef load_certificate(type, buffer):\n    \"\"\"\n    Load a certificate (X509) from the string *buffer* encoded with the\n    type *type*.\n\n    :param type: The file type (one of FILETYPE_PEM, FILETYPE_ASN1)\n\n    :param bytes buffer: The buffer the certificate is stored in\n\n    :return: The X509 object\n    \"\"\"\n    if isinstance(buffer, _text_type):\n        buffer = buffer.encode(\"ascii\")\n\n    bio = _new_mem_buf(buffer)\n\n    if type == FILETYPE_PEM:\n        x509 = _lib.PEM_read_bio_X509(bio, _ffi.NULL, _ffi.NULL, _ffi.NULL)\n    elif type == FILETYPE_ASN1:\n        x509 = _lib.d2i_X509_bio(bio, _ffi.NULL)\n    else:\n        raise ValueError(\n            \"type argument must be FILETYPE_PEM or FILETYPE_ASN1\")\n\n    if x509 == _ffi.NULL:\n        _raise_current_error()\n\n    return X509._from_raw_x509_ptr(x509)\n\n\ndef dump_certificate(type, cert):\n    \"\"\"\n    Dump the certificate *cert* into a buffer string encoded with the type\n    *type*.\n\n    :param type: The file type (one of FILETYPE_PEM, FILETYPE_ASN1, or\n        FILETYPE_TEXT)\n    :param cert: The certificate to dump\n    :return: The buffer with the dumped certificate in\n    \"\"\"\n    bio = _new_mem_buf()\n\n    if type == FILETYPE_PEM:\n        result_code = _lib.PEM_write_bio_X509(bio, cert._x509)\n    elif type == FILETYPE_ASN1:\n        result_code = _lib.i2d_X509_bio(bio, cert._x509)\n    elif type == FILETYPE_TEXT:\n        result_code = _lib.X509_print_ex(bio, cert._x509, 0, 0)\n    else:\n        raise ValueError(\n            \"type argument must be FILETYPE_PEM, FILETYPE_ASN1, or \"\n            \"FILETYPE_TEXT\")\n\n    assert result_code == 1\n    return _bio_to_string(bio)\n\n\ndef dump_publickey(type, pkey):\n    \"\"\"\n    Dump a public key to a buffer.\n\n    :param type: The file type (one of :data:`FILETYPE_PEM` or\n        :data:`FILETYPE_ASN1`).\n    :param PKey pkey: The public key to dump\n    :return: The buffer with the dumped key in it.\n    :rtype: bytes\n    \"\"\"\n    bio = _new_mem_buf()\n    if type == FILETYPE_PEM:\n        write_bio = _lib.PEM_write_bio_PUBKEY\n    elif type == FILETYPE_ASN1:\n        write_bio = _lib.i2d_PUBKEY_bio\n    else:\n        raise ValueError(\"type argument must be FILETYPE_PEM or FILETYPE_ASN1\")\n\n    result_code = write_bio(bio, pkey._pkey)\n    if result_code != 1:  # pragma: no cover\n        _raise_current_error()\n\n    return _bio_to_string(bio)\n\n\ndef dump_privatekey(type, pkey, cipher=None, passphrase=None):\n    \"\"\"\n    Dump the private key *pkey* into a buffer string encoded with the type\n    *type*.  Optionally (if *type* is :const:`FILETYPE_PEM`) encrypting it\n    using *cipher* and *passphrase*.\n\n    :param type: The file type (one of :const:`FILETYPE_PEM`,\n        :const:`FILETYPE_ASN1`, or :const:`FILETYPE_TEXT`)\n    :param PKey pkey: The PKey to dump\n    :param cipher: (optional) if encrypted PEM format, the cipher to use\n    :param passphrase: (optional) if encrypted PEM format, this can be either\n        the passphrase to use, or a callback for providing the passphrase.\n\n    :return: The buffer with the dumped key in\n    :rtype: bytes\n    \"\"\"\n    bio = _new_mem_buf()\n\n    if not isinstance(pkey, PKey):\n        raise TypeError(\"pkey must be a PKey\")\n\n    if cipher is not None:\n        if passphrase is None:\n            raise TypeError(\n                \"if a value is given for cipher \"\n                \"one must also be given for passphrase\")\n        cipher_obj = _lib.EVP_get_cipherbyname(_byte_string(cipher))\n        if cipher_obj == _ffi.NULL:\n            raise ValueError(\"Invalid cipher name\")\n    else:\n        cipher_obj = _ffi.NULL\n\n    helper = _PassphraseHelper(type, passphrase)\n    if type == FILETYPE_PEM:\n        result_code = _lib.PEM_write_bio_PrivateKey(\n            bio, pkey._pkey, cipher_obj, _ffi.NULL, 0,\n            helper.callback, helper.callback_args)\n        helper.raise_if_problem()\n    elif type == FILETYPE_ASN1:\n        result_code = _lib.i2d_PrivateKey_bio(bio, pkey._pkey)\n    elif type == FILETYPE_TEXT:\n        if _lib.EVP_PKEY_id(pkey._pkey) != _lib.EVP_PKEY_RSA:\n            raise TypeError(\"Only RSA keys are supported for FILETYPE_TEXT\")\n\n        rsa = _ffi.gc(\n            _lib.EVP_PKEY_get1_RSA(pkey._pkey),\n            _lib.RSA_free\n        )\n        result_code = _lib.RSA_print(bio, rsa, 0)\n    else:\n        raise ValueError(\n            \"type argument must be FILETYPE_PEM, FILETYPE_ASN1, or \"\n            \"FILETYPE_TEXT\")\n\n    _openssl_assert(result_code != 0)\n\n    return _bio_to_string(bio)\n\n\nclass Revoked(object):\n    \"\"\"\n    A certificate revocation.\n    \"\"\"\n    # https://www.openssl.org/docs/manmaster/man5/x509v3_config.html#CRL-distribution-points\n    # which differs from crl_reasons of crypto/x509v3/v3_enum.c that matches\n    # OCSP_crl_reason_str.  We use the latter, just like the command line\n    # program.\n    _crl_reasons = [\n        b\"unspecified\",\n        b\"keyCompromise\",\n        b\"CACompromise\",\n        b\"affiliationChanged\",\n        b\"superseded\",\n        b\"cessationOfOperation\",\n        b\"certificateHold\",\n        # b\"removeFromCRL\",\n    ]\n\n    def __init__(self):\n        revoked = _lib.X509_REVOKED_new()\n        self._revoked = _ffi.gc(revoked, _lib.X509_REVOKED_free)\n\n    def set_serial(self, hex_str):\n        \"\"\"\n        Set the serial number.\n\n        The serial number is formatted as a hexadecimal number encoded in\n        ASCII.\n\n        :param bytes hex_str: The new serial number.\n\n        :return: ``None``\n        \"\"\"\n        bignum_serial = _ffi.gc(_lib.BN_new(), _lib.BN_free)\n        bignum_ptr = _ffi.new(\"BIGNUM**\")\n        bignum_ptr[0] = bignum_serial\n        bn_result = _lib.BN_hex2bn(bignum_ptr, hex_str)\n        if not bn_result:\n            raise ValueError(\"bad hex string\")\n\n        asn1_serial = _ffi.gc(\n            _lib.BN_to_ASN1_INTEGER(bignum_serial, _ffi.NULL),\n            _lib.ASN1_INTEGER_free)\n        _lib.X509_REVOKED_set_serialNumber(self._revoked, asn1_serial)\n\n    def get_serial(self):\n        \"\"\"\n        Get the serial number.\n\n        The serial number is formatted as a hexadecimal number encoded in\n        ASCII.\n\n        :return: The serial number.\n        :rtype: bytes\n        \"\"\"\n        bio = _new_mem_buf()\n\n        asn1_int = _lib.X509_REVOKED_get0_serialNumber(self._revoked)\n        _openssl_assert(asn1_int != _ffi.NULL)\n        result = _lib.i2a_ASN1_INTEGER(bio, asn1_int)\n        _openssl_assert(result >= 0)\n        return _bio_to_string(bio)\n\n    def _delete_reason(self):\n        for i in range(_lib.X509_REVOKED_get_ext_count(self._revoked)):\n            ext = _lib.X509_REVOKED_get_ext(self._revoked, i)\n            obj = _lib.X509_EXTENSION_get_object(ext)\n            if _lib.OBJ_obj2nid(obj) == _lib.NID_crl_reason:\n                _lib.X509_EXTENSION_free(ext)\n                _lib.X509_REVOKED_delete_ext(self._revoked, i)\n                break\n\n    def set_reason(self, reason):\n        \"\"\"\n        Set the reason of this revocation.\n\n        If :data:`reason` is ``None``, delete the reason instead.\n\n        :param reason: The reason string.\n        :type reason: :class:`bytes` or :class:`NoneType`\n\n        :return: ``None``\n\n        .. seealso::\n\n            :meth:`all_reasons`, which gives you a list of all supported\n            reasons which you might pass to this method.\n        \"\"\"\n        if reason is None:\n            self._delete_reason()\n        elif not isinstance(reason, bytes):\n            raise TypeError(\"reason must be None or a byte string\")\n        else:\n            reason = reason.lower().replace(b' ', b'')\n            reason_code = [r.lower() for r in self._crl_reasons].index(reason)\n\n            new_reason_ext = _lib.ASN1_ENUMERATED_new()\n            _openssl_assert(new_reason_ext != _ffi.NULL)\n            new_reason_ext = _ffi.gc(new_reason_ext, _lib.ASN1_ENUMERATED_free)\n\n            set_result = _lib.ASN1_ENUMERATED_set(new_reason_ext, reason_code)\n            _openssl_assert(set_result != _ffi.NULL)\n\n            self._delete_reason()\n            add_result = _lib.X509_REVOKED_add1_ext_i2d(\n                self._revoked, _lib.NID_crl_reason, new_reason_ext, 0, 0)\n            _openssl_assert(add_result == 1)\n\n    def get_reason(self):\n        \"\"\"\n        Get the reason of this revocation.\n\n        :return: The reason, or ``None`` if there is none.\n        :rtype: bytes or NoneType\n\n        .. seealso::\n\n            :meth:`all_reasons`, which gives you a list of all supported\n            reasons this method might return.\n        \"\"\"\n        for i in range(_lib.X509_REVOKED_get_ext_count(self._revoked)):\n            ext = _lib.X509_REVOKED_get_ext(self._revoked, i)\n            obj = _lib.X509_EXTENSION_get_object(ext)\n            if _lib.OBJ_obj2nid(obj) == _lib.NID_crl_reason:\n                bio = _new_mem_buf()\n\n                print_result = _lib.X509V3_EXT_print(bio, ext, 0, 0)\n                if not print_result:\n                    print_result = _lib.M_ASN1_OCTET_STRING_print(\n                        bio, _lib.X509_EXTENSION_get_data(ext)\n                    )\n                    _openssl_assert(print_result != 0)\n\n                return _bio_to_string(bio)\n\n    def all_reasons(self):\n        \"\"\"\n        Return a list of all the supported reason strings.\n\n        This list is a copy; modifying it does not change the supported reason\n        strings.\n\n        :return: A list of reason strings.\n        :rtype: :class:`list` of :class:`bytes`\n        \"\"\"\n        return self._crl_reasons[:]\n\n    def set_rev_date(self, when):\n        \"\"\"\n        Set the revocation timestamp.\n\n        :param bytes when: The timestamp of the revocation,\n            as ASN.1 TIME.\n        :return: ``None``\n        \"\"\"\n        dt = _lib.X509_REVOKED_get0_revocationDate(self._revoked)\n        return _set_asn1_time(dt, when)\n\n    def get_rev_date(self):\n        \"\"\"\n        Get the revocation timestamp.\n\n        :return: The timestamp of the revocation, as ASN.1 TIME.\n        :rtype: bytes\n        \"\"\"\n        dt = _lib.X509_REVOKED_get0_revocationDate(self._revoked)\n        return _get_asn1_time(dt)\n\n\nclass CRL(object):\n    \"\"\"\n    A certificate revocation list.\n    \"\"\"\n\n    def __init__(self):\n        crl = _lib.X509_CRL_new()\n        self._crl = _ffi.gc(crl, _lib.X509_CRL_free)\n\n    def to_cryptography(self):\n        \"\"\"\n        Export as a ``cryptography`` CRL.\n\n        :rtype: ``cryptography.x509.CertificateRevocationList``\n\n        .. versionadded:: 17.1.0\n        \"\"\"\n        from cryptography.hazmat.backends.openssl.x509 import (\n            _CertificateRevocationList\n        )\n        backend = _get_backend()\n        return _CertificateRevocationList(backend, self._crl)\n\n    @classmethod\n    def from_cryptography(cls, crypto_crl):\n        \"\"\"\n        Construct based on a ``cryptography`` *crypto_crl*.\n\n        :param crypto_crl: A ``cryptography`` certificate revocation list\n        :type crypto_crl: ``cryptography.x509.CertificateRevocationList``\n\n        :rtype: CRL\n\n        .. versionadded:: 17.1.0\n        \"\"\"\n        if not isinstance(crypto_crl, x509.CertificateRevocationList):\n            raise TypeError(\"Must be a certificate revocation list\")\n\n        crl = cls()\n        crl._crl = crypto_crl._x509_crl\n        return crl\n\n    def get_revoked(self):\n        \"\"\"\n        Return the revocations in this certificate revocation list.\n\n        These revocations will be provided by value, not by reference.\n        That means it's okay to mutate them: it won't affect this CRL.\n\n        :return: The revocations in this CRL.\n        :rtype: :class:`tuple` of :class:`Revocation`\n        \"\"\"\n        results = []\n        revoked_stack = _lib.X509_CRL_get_REVOKED(self._crl)\n        for i in range(_lib.sk_X509_REVOKED_num(revoked_stack)):\n            revoked = _lib.sk_X509_REVOKED_value(revoked_stack, i)\n            revoked_copy = _lib.Cryptography_X509_REVOKED_dup(revoked)\n            pyrev = Revoked.__new__(Revoked)\n            pyrev._revoked = _ffi.gc(revoked_copy, _lib.X509_REVOKED_free)\n            results.append(pyrev)\n        if results:\n            return tuple(results)\n\n    def add_revoked(self, revoked):\n        \"\"\"\n        Add a revoked (by value not reference) to the CRL structure\n\n        This revocation will be added by value, not by reference. That\n        means it's okay to mutate it after adding: it won't affect\n        this CRL.\n\n        :param Revoked revoked: The new revocation.\n        :return: ``None``\n        \"\"\"\n        copy = _lib.Cryptography_X509_REVOKED_dup(revoked._revoked)\n        _openssl_assert(copy != _ffi.NULL)\n\n        add_result = _lib.X509_CRL_add0_revoked(self._crl, copy)\n        _openssl_assert(add_result != 0)\n\n    def get_issuer(self):\n        \"\"\"\n        Get the CRL's issuer.\n\n        .. versionadded:: 16.1.0\n\n        :rtype: X509Name\n        \"\"\"\n        _issuer = _lib.X509_NAME_dup(_lib.X509_CRL_get_issuer(self._crl))\n        _openssl_assert(_issuer != _ffi.NULL)\n        _issuer = _ffi.gc(_issuer, _lib.X509_NAME_free)\n        issuer = X509Name.__new__(X509Name)\n        issuer._name = _issuer\n        return issuer\n\n    def set_version(self, version):\n        \"\"\"\n        Set the CRL version.\n\n        .. versionadded:: 16.1.0\n\n        :param int version: The version of the CRL.\n        :return: ``None``\n        \"\"\"\n        _openssl_assert(_lib.X509_CRL_set_version(self._crl, version) != 0)\n\n    def _set_boundary_time(self, which, when):\n        return _set_asn1_time(which(self._crl), when)\n\n    def set_lastUpdate(self, when):\n        \"\"\"\n        Set when the CRL was last updated.\n\n        The timestamp is formatted as an ASN.1 TIME::\n\n            YYYYMMDDhhmmssZ\n\n        .. versionadded:: 16.1.0\n\n        :param bytes when: A timestamp string.\n        :return: ``None``\n        \"\"\"\n        return self._set_boundary_time(_lib.X509_CRL_get_lastUpdate, when)\n\n    def set_nextUpdate(self, when):\n        \"\"\"\n        Set when the CRL will next be udpated.\n\n        The timestamp is formatted as an ASN.1 TIME::\n\n            YYYYMMDDhhmmssZ\n\n        .. versionadded:: 16.1.0\n\n        :param bytes when: A timestamp string.\n        :return: ``None``\n        \"\"\"\n        return self._set_boundary_time(_lib.X509_CRL_get_nextUpdate, when)\n\n    def sign(self, issuer_cert, issuer_key, digest):\n        \"\"\"\n        Sign the CRL.\n\n        Signing a CRL enables clients to associate the CRL itself with an\n        issuer. Before a CRL is meaningful to other OpenSSL functions, it must\n        be signed by an issuer.\n\n        This method implicitly sets the issuer's name based on the issuer\n        certificate and private key used to sign the CRL.\n\n        .. versionadded:: 16.1.0\n\n        :param X509 issuer_cert: The issuer's certificate.\n        :param PKey issuer_key: The issuer's private key.\n        :param bytes digest: The digest method to sign the CRL with.\n        \"\"\"\n        digest_obj = _lib.EVP_get_digestbyname(digest)\n        _openssl_assert(digest_obj != _ffi.NULL)\n        _lib.X509_CRL_set_issuer_name(\n            self._crl, _lib.X509_get_subject_name(issuer_cert._x509))\n        _lib.X509_CRL_sort(self._crl)\n        result = _lib.X509_CRL_sign(self._crl, issuer_key._pkey, digest_obj)\n        _openssl_assert(result != 0)\n\n    def export(self, cert, key, type=FILETYPE_PEM, days=100,\n               digest=_UNSPECIFIED):\n        \"\"\"\n        Export the CRL as a string.\n\n        :param X509 cert: The certificate used to sign the CRL.\n        :param PKey key: The key used to sign the CRL.\n        :param int type: The export format, either :data:`FILETYPE_PEM`,\n            :data:`FILETYPE_ASN1`, or :data:`FILETYPE_TEXT`.\n        :param int days: The number of days until the next update of this CRL.\n        :param bytes digest: The name of the message digest to use (eg\n            ``b\"sha2566\"``).\n        :rtype: bytes\n        \"\"\"\n\n        if not isinstance(cert, X509):\n            raise TypeError(\"cert must be an X509 instance\")\n        if not isinstance(key, PKey):\n            raise TypeError(\"key must be a PKey instance\")\n        if not isinstance(type, int):\n            raise TypeError(\"type must be an integer\")\n\n        if digest is _UNSPECIFIED:\n            raise TypeError(\"digest must be provided\")\n\n        digest_obj = _lib.EVP_get_digestbyname(digest)\n        if digest_obj == _ffi.NULL:\n            raise ValueError(\"No such digest method\")\n\n        bio = _lib.BIO_new(_lib.BIO_s_mem())\n        _openssl_assert(bio != _ffi.NULL)\n\n        # A scratch time object to give different values to different CRL\n        # fields\n        sometime = _lib.ASN1_TIME_new()\n        _openssl_assert(sometime != _ffi.NULL)\n\n        _lib.X509_gmtime_adj(sometime, 0)\n        _lib.X509_CRL_set_lastUpdate(self._crl, sometime)\n\n        _lib.X509_gmtime_adj(sometime, days * 24 * 60 * 60)\n        _lib.X509_CRL_set_nextUpdate(self._crl, sometime)\n\n        _lib.X509_CRL_set_issuer_name(\n            self._crl, _lib.X509_get_subject_name(cert._x509)\n        )\n\n        sign_result = _lib.X509_CRL_sign(self._crl, key._pkey, digest_obj)\n        if not sign_result:\n            _raise_current_error()\n\n        return dump_crl(type, self)\n\n\nCRLType = deprecated(\n    CRL, __name__,\n    \"CRLType has been deprecated, use CRL instead\",\n    DeprecationWarning\n)\n\n\nclass PKCS7(object):\n    def type_is_signed(self):\n        \"\"\"\n        Check if this NID_pkcs7_signed object\n\n        :return: True if the PKCS7 is of type signed\n        \"\"\"\n        return bool(_lib.PKCS7_type_is_signed(self._pkcs7))\n\n    def type_is_enveloped(self):\n        \"\"\"\n        Check if this NID_pkcs7_enveloped object\n\n        :returns: True if the PKCS7 is of type enveloped\n        \"\"\"\n        return bool(_lib.PKCS7_type_is_enveloped(self._pkcs7))\n\n    def type_is_signedAndEnveloped(self):\n        \"\"\"\n        Check if this NID_pkcs7_signedAndEnveloped object\n\n        :returns: True if the PKCS7 is of type signedAndEnveloped\n        \"\"\"\n        return bool(_lib.PKCS7_type_is_signedAndEnveloped(self._pkcs7))\n\n    def type_is_data(self):\n        \"\"\"\n        Check if this NID_pkcs7_data object\n\n        :return: True if the PKCS7 is of type data\n        \"\"\"\n        return bool(_lib.PKCS7_type_is_data(self._pkcs7))\n\n    def get_type_name(self):\n        \"\"\"\n        Returns the type name of the PKCS7 structure\n\n        :return: A string with the typename\n        \"\"\"\n        nid = _lib.OBJ_obj2nid(self._pkcs7.type)\n        string_type = _lib.OBJ_nid2sn(nid)\n        return _ffi.string(string_type)\n\n\nPKCS7Type = deprecated(\n    PKCS7, __name__,\n    \"PKCS7Type has been deprecated, use PKCS7 instead\",\n    DeprecationWarning\n)\n\n\nclass PKCS12(object):\n    \"\"\"\n    A PKCS #12 archive.\n    \"\"\"\n\n    def __init__(self):\n        self._pkey = None\n        self._cert = None\n        self._cacerts = None\n        self._friendlyname = None\n\n    def get_certificate(self):\n        \"\"\"\n        Get the certificate in the PKCS #12 structure.\n\n        :return: The certificate, or :py:const:`None` if there is none.\n        :rtype: :py:class:`X509` or :py:const:`None`\n        \"\"\"\n        return self._cert\n\n    def set_certificate(self, cert):\n        \"\"\"\n        Set the certificate in the PKCS #12 structure.\n\n        :param cert: The new certificate, or :py:const:`None` to unset it.\n        :type cert: :py:class:`X509` or :py:const:`None`\n\n        :return: ``None``\n        \"\"\"\n        if not isinstance(cert, X509):\n            raise TypeError(\"cert must be an X509 instance\")\n        self._cert = cert\n\n    def get_privatekey(self):\n        \"\"\"\n        Get the private key in the PKCS #12 structure.\n\n        :return: The private key, or :py:const:`None` if there is none.\n        :rtype: :py:class:`PKey`\n        \"\"\"\n        return self._pkey\n\n    def set_privatekey(self, pkey):\n        \"\"\"\n        Set the certificate portion of the PKCS #12 structure.\n\n        :param pkey: The new private key, or :py:const:`None` to unset it.\n        :type pkey: :py:class:`PKey` or :py:const:`None`\n\n        :return: ``None``\n        \"\"\"\n        if not isinstance(pkey, PKey):\n            raise TypeError(\"pkey must be a PKey instance\")\n        self._pkey = pkey\n\n    def get_ca_certificates(self):\n        \"\"\"\n        Get the CA certificates in the PKCS #12 structure.\n\n        :return: A tuple with the CA certificates in the chain, or\n            :py:const:`None` if there are none.\n        :rtype: :py:class:`tuple` of :py:class:`X509` or :py:const:`None`\n        \"\"\"\n        if self._cacerts is not None:\n            return tuple(self._cacerts)\n\n    def set_ca_certificates(self, cacerts):\n        \"\"\"\n        Replace or set the CA certificates within the PKCS12 object.\n\n        :param cacerts: The new CA certificates, or :py:const:`None` to unset\n            them.\n        :type cacerts: An iterable of :py:class:`X509` or :py:const:`None`\n\n        :return: ``None``\n        \"\"\"\n        if cacerts is None:\n            self._cacerts = None\n        else:\n            cacerts = list(cacerts)\n            for cert in cacerts:\n                if not isinstance(cert, X509):\n                    raise TypeError(\n                        \"iterable must only contain X509 instances\"\n                    )\n            self._cacerts = cacerts\n\n    def set_friendlyname(self, name):\n        \"\"\"\n        Set the friendly name in the PKCS #12 structure.\n\n        :param name: The new friendly name, or :py:const:`None` to unset.\n        :type name: :py:class:`bytes` or :py:const:`None`\n\n        :return: ``None``\n        \"\"\"\n        if name is None:\n            self._friendlyname = None\n        elif not isinstance(name, bytes):\n            raise TypeError(\n                \"name must be a byte string or None (not %r)\" % (name,)\n            )\n        self._friendlyname = name\n\n    def get_friendlyname(self):\n        \"\"\"\n        Get the friendly name in the PKCS# 12 structure.\n\n        :returns: The friendly name,  or :py:const:`None` if there is none.\n        :rtype: :py:class:`bytes` or :py:const:`None`\n        \"\"\"\n        return self._friendlyname\n\n    def export(self, passphrase=None, iter=2048, maciter=1):\n        \"\"\"\n        Dump a PKCS12 object as a string.\n\n        For more information, see the :c:func:`PKCS12_create` man page.\n\n        :param passphrase: The passphrase used to encrypt the structure. Unlike\n            some other passphrase arguments, this *must* be a string, not a\n            callback.\n        :type passphrase: :py:data:`bytes`\n\n        :param iter: Number of times to repeat the encryption step.\n        :type iter: :py:data:`int`\n\n        :param maciter: Number of times to repeat the MAC step.\n        :type maciter: :py:data:`int`\n\n        :return: The string representation of the PKCS #12 structure.\n        :rtype:\n        \"\"\"\n        passphrase = _text_to_bytes_and_warn(\"passphrase\", passphrase)\n\n        if self._cacerts is None:\n            cacerts = _ffi.NULL\n        else:\n            cacerts = _lib.sk_X509_new_null()\n            cacerts = _ffi.gc(cacerts, _lib.sk_X509_free)\n            for cert in self._cacerts:\n                _lib.sk_X509_push(cacerts, cert._x509)\n\n        if passphrase is None:\n            passphrase = _ffi.NULL\n\n        friendlyname = self._friendlyname\n        if friendlyname is None:\n            friendlyname = _ffi.NULL\n\n        if self._pkey is None:\n            pkey = _ffi.NULL\n        else:\n            pkey = self._pkey._pkey\n\n        if self._cert is None:\n            cert = _ffi.NULL\n        else:\n            cert = self._cert._x509\n\n        pkcs12 = _lib.PKCS12_create(\n            passphrase, friendlyname, pkey, cert, cacerts,\n            _lib.NID_pbe_WithSHA1And3_Key_TripleDES_CBC,\n            _lib.NID_pbe_WithSHA1And3_Key_TripleDES_CBC,\n            iter, maciter, 0)\n        if pkcs12 == _ffi.NULL:\n            _raise_current_error()\n        pkcs12 = _ffi.gc(pkcs12, _lib.PKCS12_free)\n\n        bio = _new_mem_buf()\n        _lib.i2d_PKCS12_bio(bio, pkcs12)\n        return _bio_to_string(bio)\n\n\nPKCS12Type = deprecated(\n    PKCS12, __name__,\n    \"PKCS12Type has been deprecated, use PKCS12 instead\",\n    DeprecationWarning\n)\n\n\nclass NetscapeSPKI(object):\n    \"\"\"\n    A Netscape SPKI object.\n    \"\"\"\n\n    def __init__(self):\n        spki = _lib.NETSCAPE_SPKI_new()\n        self._spki = _ffi.gc(spki, _lib.NETSCAPE_SPKI_free)\n\n    def sign(self, pkey, digest):\n        \"\"\"\n        Sign the certificate request with this key and digest type.\n\n        :param pkey: The private key to sign with.\n        :type pkey: :py:class:`PKey`\n\n        :param digest: The message digest to use.\n        :type digest: :py:class:`bytes`\n\n        :return: ``None``\n        \"\"\"\n        if pkey._only_public:\n            raise ValueError(\"Key has only public part\")\n\n        if not pkey._initialized:\n            raise ValueError(\"Key is uninitialized\")\n\n        digest_obj = _lib.EVP_get_digestbyname(_byte_string(digest))\n        if digest_obj == _ffi.NULL:\n            raise ValueError(\"No such digest method\")\n\n        sign_result = _lib.NETSCAPE_SPKI_sign(\n            self._spki, pkey._pkey, digest_obj\n        )\n        _openssl_assert(sign_result > 0)\n\n    def verify(self, key):\n        \"\"\"\n        Verifies a signature on a certificate request.\n\n        :param PKey key: The public key that signature is supposedly from.\n\n        :return: ``True`` if the signature is correct.\n        :rtype: bool\n\n        :raises OpenSSL.crypto.Error: If the signature is invalid, or there was\n            a problem verifying the signature.\n        \"\"\"\n        answer = _lib.NETSCAPE_SPKI_verify(self._spki, key._pkey)\n        if answer <= 0:\n            _raise_current_error()\n        return True\n\n    def b64_encode(self):\n        \"\"\"\n        Generate a base64 encoded representation of this SPKI object.\n\n        :return: The base64 encoded string.\n        :rtype: :py:class:`bytes`\n        \"\"\"\n        encoded = _lib.NETSCAPE_SPKI_b64_encode(self._spki)\n        result = _ffi.string(encoded)\n        _lib.OPENSSL_free(encoded)\n        return result\n\n    def get_pubkey(self):\n        \"\"\"\n        Get the public key of this certificate.\n\n        :return: The public key.\n        :rtype: :py:class:`PKey`\n        \"\"\"\n        pkey = PKey.__new__(PKey)\n        pkey._pkey = _lib.NETSCAPE_SPKI_get_pubkey(self._spki)\n        _openssl_assert(pkey._pkey != _ffi.NULL)\n        pkey._pkey = _ffi.gc(pkey._pkey, _lib.EVP_PKEY_free)\n        pkey._only_public = True\n        return pkey\n\n    def set_pubkey(self, pkey):\n        \"\"\"\n        Set the public key of the certificate\n\n        :param pkey: The public key\n        :return: ``None``\n        \"\"\"\n        set_result = _lib.NETSCAPE_SPKI_set_pubkey(self._spki, pkey._pkey)\n        _openssl_assert(set_result == 1)\n\n\nNetscapeSPKIType = deprecated(\n    NetscapeSPKI, __name__,\n    \"NetscapeSPKIType has been deprecated, use NetscapeSPKI instead\",\n    DeprecationWarning\n)\n\n\nclass _PassphraseHelper(object):\n    def __init__(self, type, passphrase, more_args=False, truncate=False):\n        if type != FILETYPE_PEM and passphrase is not None:\n            raise ValueError(\n                \"only FILETYPE_PEM key format supports encryption\"\n            )\n        self._passphrase = passphrase\n        self._more_args = more_args\n        self._truncate = truncate\n        self._problems = []\n\n    @property\n    def callback(self):\n        if self._passphrase is None:\n            return _ffi.NULL\n        elif isinstance(self._passphrase, bytes):\n            return _ffi.NULL\n        elif callable(self._passphrase):\n            return _ffi.callback(\"pem_password_cb\", self._read_passphrase)\n        else:\n            raise TypeError(\n                \"Last argument must be a byte string or a callable.\"\n            )\n\n    @property\n    def callback_args(self):\n        if self._passphrase is None:\n            return _ffi.NULL\n        elif isinstance(self._passphrase, bytes):\n            return self._passphrase\n        elif callable(self._passphrase):\n            return _ffi.NULL\n        else:\n            raise TypeError(\n                \"Last argument must be a byte string or a callable.\"\n            )\n\n    def raise_if_problem(self, exceptionType=Error):\n        if self._problems:\n\n            # Flush the OpenSSL error queue\n            try:\n                _exception_from_error_queue(exceptionType)\n            except exceptionType:\n                pass\n\n            raise self._problems.pop(0)\n\n    def _read_passphrase(self, buf, size, rwflag, userdata):\n        try:\n            if self._more_args:\n                result = self._passphrase(size, rwflag, userdata)\n            else:\n                result = self._passphrase(rwflag)\n            if not isinstance(result, bytes):\n                raise ValueError(\"String expected\")\n            if len(result) > size:\n                if self._truncate:\n                    result = result[:size]\n                else:\n                    raise ValueError(\n                        \"passphrase returned by callback is too long\"\n                    )\n            for i in range(len(result)):\n                buf[i] = result[i:i + 1]\n            return len(result)\n        except Exception as e:\n            self._problems.append(e)\n            return 0\n\n\ndef load_publickey(type, buffer):\n    \"\"\"\n    Load a public key from a buffer.\n\n    :param type: The file type (one of :data:`FILETYPE_PEM`,\n        :data:`FILETYPE_ASN1`).\n    :param buffer: The buffer the key is stored in.\n    :type buffer: A Python string object, either unicode or bytestring.\n    :return: The PKey object.\n    :rtype: :class:`PKey`\n    \"\"\"\n    if isinstance(buffer, _text_type):\n        buffer = buffer.encode(\"ascii\")\n\n    bio = _new_mem_buf(buffer)\n\n    if type == FILETYPE_PEM:\n        evp_pkey = _lib.PEM_read_bio_PUBKEY(\n            bio, _ffi.NULL, _ffi.NULL, _ffi.NULL)\n    elif type == FILETYPE_ASN1:\n        evp_pkey = _lib.d2i_PUBKEY_bio(bio, _ffi.NULL)\n    else:\n        raise ValueError(\"type argument must be FILETYPE_PEM or FILETYPE_ASN1\")\n\n    if evp_pkey == _ffi.NULL:\n        _raise_current_error()\n\n    pkey = PKey.__new__(PKey)\n    pkey._pkey = _ffi.gc(evp_pkey, _lib.EVP_PKEY_free)\n    pkey._only_public = True\n    return pkey\n\n\ndef load_privatekey(type, buffer, passphrase=None):\n    \"\"\"\n    Load a private key (PKey) from the string *buffer* encoded with the type\n    *type*.\n\n    :param type: The file type (one of FILETYPE_PEM, FILETYPE_ASN1)\n    :param buffer: The buffer the key is stored in\n    :param passphrase: (optional) if encrypted PEM format, this can be\n                       either the passphrase to use, or a callback for\n                       providing the passphrase.\n\n    :return: The PKey object\n    \"\"\"\n    if isinstance(buffer, _text_type):\n        buffer = buffer.encode(\"ascii\")\n\n    bio = _new_mem_buf(buffer)\n\n    helper = _PassphraseHelper(type, passphrase)\n    if type == FILETYPE_PEM:\n        evp_pkey = _lib.PEM_read_bio_PrivateKey(\n            bio, _ffi.NULL, helper.callback, helper.callback_args)\n        helper.raise_if_problem()\n    elif type == FILETYPE_ASN1:\n        evp_pkey = _lib.d2i_PrivateKey_bio(bio, _ffi.NULL)\n    else:\n        raise ValueError(\"type argument must be FILETYPE_PEM or FILETYPE_ASN1\")\n\n    if evp_pkey == _ffi.NULL:\n        _raise_current_error()\n\n    pkey = PKey.__new__(PKey)\n    pkey._pkey = _ffi.gc(evp_pkey, _lib.EVP_PKEY_free)\n    return pkey\n\n\ndef dump_certificate_request(type, req):\n    \"\"\"\n    Dump the certificate request *req* into a buffer string encoded with the\n    type *type*.\n\n    :param type: The file type (one of FILETYPE_PEM, FILETYPE_ASN1)\n    :param req: The certificate request to dump\n    :return: The buffer with the dumped certificate request in\n    \"\"\"\n    bio = _new_mem_buf()\n\n    if type == FILETYPE_PEM:\n        result_code = _lib.PEM_write_bio_X509_REQ(bio, req._req)\n    elif type == FILETYPE_ASN1:\n        result_code = _lib.i2d_X509_REQ_bio(bio, req._req)\n    elif type == FILETYPE_TEXT:\n        result_code = _lib.X509_REQ_print_ex(bio, req._req, 0, 0)\n    else:\n        raise ValueError(\n            \"type argument must be FILETYPE_PEM, FILETYPE_ASN1, or \"\n            \"FILETYPE_TEXT\"\n        )\n\n    _openssl_assert(result_code != 0)\n\n    return _bio_to_string(bio)\n\n\ndef load_certificate_request(type, buffer):\n    \"\"\"\n    Load a certificate request (X509Req) from the string *buffer* encoded with\n    the type *type*.\n\n    :param type: The file type (one of FILETYPE_PEM, FILETYPE_ASN1)\n    :param buffer: The buffer the certificate request is stored in\n    :return: The X509Req object\n    \"\"\"\n    if isinstance(buffer, _text_type):\n        buffer = buffer.encode(\"ascii\")\n\n    bio = _new_mem_buf(buffer)\n\n    if type == FILETYPE_PEM:\n        req = _lib.PEM_read_bio_X509_REQ(bio, _ffi.NULL, _ffi.NULL, _ffi.NULL)\n    elif type == FILETYPE_ASN1:\n        req = _lib.d2i_X509_REQ_bio(bio, _ffi.NULL)\n    else:\n        raise ValueError(\"type argument must be FILETYPE_PEM or FILETYPE_ASN1\")\n\n    _openssl_assert(req != _ffi.NULL)\n\n    x509req = X509Req.__new__(X509Req)\n    x509req._req = _ffi.gc(req, _lib.X509_REQ_free)\n    return x509req\n\n\ndef sign(pkey, data, digest):\n    \"\"\"\n    Sign a data string using the given key and message digest.\n\n    :param pkey: PKey to sign with\n    :param data: data to be signed\n    :param digest: message digest to use\n    :return: signature\n\n    .. versionadded:: 0.11\n    \"\"\"\n    data = _text_to_bytes_and_warn(\"data\", data)\n\n    digest_obj = _lib.EVP_get_digestbyname(_byte_string(digest))\n    if digest_obj == _ffi.NULL:\n        raise ValueError(\"No such digest method\")\n\n    md_ctx = _lib.Cryptography_EVP_MD_CTX_new()\n    md_ctx = _ffi.gc(md_ctx, _lib.Cryptography_EVP_MD_CTX_free)\n\n    _lib.EVP_SignInit(md_ctx, digest_obj)\n    _lib.EVP_SignUpdate(md_ctx, data, len(data))\n\n    length = _lib.EVP_PKEY_size(pkey._pkey)\n    _openssl_assert(length > 0)\n    signature_buffer = _ffi.new(\"unsigned char[]\", length)\n    signature_length = _ffi.new(\"unsigned int *\")\n    final_result = _lib.EVP_SignFinal(\n        md_ctx, signature_buffer, signature_length, pkey._pkey)\n    _openssl_assert(final_result == 1)\n\n    return _ffi.buffer(signature_buffer, signature_length[0])[:]\n\n\ndef verify(cert, signature, data, digest):\n    \"\"\"\n    Verify the signature for a data string.\n\n    :param cert: signing certificate (X509 object) corresponding to the\n        private key which generated the signature.\n    :param signature: signature returned by sign function\n    :param data: data to be verified\n    :param digest: message digest to use\n    :return: ``None`` if the signature is correct, raise exception otherwise.\n\n    .. versionadded:: 0.11\n    \"\"\"\n    data = _text_to_bytes_and_warn(\"data\", data)\n\n    digest_obj = _lib.EVP_get_digestbyname(_byte_string(digest))\n    if digest_obj == _ffi.NULL:\n        raise ValueError(\"No such digest method\")\n\n    pkey = _lib.X509_get_pubkey(cert._x509)\n    _openssl_assert(pkey != _ffi.NULL)\n    pkey = _ffi.gc(pkey, _lib.EVP_PKEY_free)\n\n    md_ctx = _lib.Cryptography_EVP_MD_CTX_new()\n    md_ctx = _ffi.gc(md_ctx, _lib.Cryptography_EVP_MD_CTX_free)\n\n    _lib.EVP_VerifyInit(md_ctx, digest_obj)\n    _lib.EVP_VerifyUpdate(md_ctx, data, len(data))\n    verify_result = _lib.EVP_VerifyFinal(\n        md_ctx, signature, len(signature), pkey\n    )\n\n    if verify_result != 1:\n        _raise_current_error()\n\n\ndef dump_crl(type, crl):\n    \"\"\"\n    Dump a certificate revocation list to a buffer.\n\n    :param type: The file type (one of ``FILETYPE_PEM``, ``FILETYPE_ASN1``, or\n        ``FILETYPE_TEXT``).\n    :param CRL crl: The CRL to dump.\n\n    :return: The buffer with the CRL.\n    :rtype: bytes\n    \"\"\"\n    bio = _new_mem_buf()\n\n    if type == FILETYPE_PEM:\n        ret = _lib.PEM_write_bio_X509_CRL(bio, crl._crl)\n    elif type == FILETYPE_ASN1:\n        ret = _lib.i2d_X509_CRL_bio(bio, crl._crl)\n    elif type == FILETYPE_TEXT:\n        ret = _lib.X509_CRL_print(bio, crl._crl)\n    else:\n        raise ValueError(\n            \"type argument must be FILETYPE_PEM, FILETYPE_ASN1, or \"\n            \"FILETYPE_TEXT\")\n\n    assert ret == 1\n    return _bio_to_string(bio)\n\n\ndef load_crl(type, buffer):\n    \"\"\"\n    Load Certificate Revocation List (CRL) data from a string *buffer*.\n    *buffer* encoded with the type *type*.\n\n    :param type: The file type (one of FILETYPE_PEM, FILETYPE_ASN1)\n    :param buffer: The buffer the CRL is stored in\n\n    :return: The PKey object\n    \"\"\"\n    if isinstance(buffer, _text_type):\n        buffer = buffer.encode(\"ascii\")\n\n    bio = _new_mem_buf(buffer)\n\n    if type == FILETYPE_PEM:\n        crl = _lib.PEM_read_bio_X509_CRL(bio, _ffi.NULL, _ffi.NULL, _ffi.NULL)\n    elif type == FILETYPE_ASN1:\n        crl = _lib.d2i_X509_CRL_bio(bio, _ffi.NULL)\n    else:\n        raise ValueError(\"type argument must be FILETYPE_PEM or FILETYPE_ASN1\")\n\n    if crl == _ffi.NULL:\n        _raise_current_error()\n\n    result = CRL.__new__(CRL)\n    result._crl = _ffi.gc(crl, _lib.X509_CRL_free)\n    return result\n\n\ndef load_pkcs7_data(type, buffer):\n    \"\"\"\n    Load pkcs7 data from the string *buffer* encoded with the type\n    *type*.\n\n    :param type: The file type (one of FILETYPE_PEM or FILETYPE_ASN1)\n    :param buffer: The buffer with the pkcs7 data.\n    :return: The PKCS7 object\n    \"\"\"\n    if isinstance(buffer, _text_type):\n        buffer = buffer.encode(\"ascii\")\n\n    bio = _new_mem_buf(buffer)\n\n    if type == FILETYPE_PEM:\n        pkcs7 = _lib.PEM_read_bio_PKCS7(bio, _ffi.NULL, _ffi.NULL, _ffi.NULL)\n    elif type == FILETYPE_ASN1:\n        pkcs7 = _lib.d2i_PKCS7_bio(bio, _ffi.NULL)\n    else:\n        raise ValueError(\"type argument must be FILETYPE_PEM or FILETYPE_ASN1\")\n\n    if pkcs7 == _ffi.NULL:\n        _raise_current_error()\n\n    pypkcs7 = PKCS7.__new__(PKCS7)\n    pypkcs7._pkcs7 = _ffi.gc(pkcs7, _lib.PKCS7_free)\n    return pypkcs7\n\n\ndef load_pkcs12(buffer, passphrase=None):\n    \"\"\"\n    Load pkcs12 data from the string *buffer*. If the pkcs12 structure is\n    encrypted, a *passphrase* must be included.  The MAC is always\n    checked and thus required.\n\n    See also the man page for the C function :py:func:`PKCS12_parse`.\n\n    :param buffer: The buffer the certificate is stored in\n    :param passphrase: (Optional) The password to decrypt the PKCS12 lump\n    :returns: The PKCS12 object\n    \"\"\"\n    passphrase = _text_to_bytes_and_warn(\"passphrase\", passphrase)\n\n    if isinstance(buffer, _text_type):\n        buffer = buffer.encode(\"ascii\")\n\n    bio = _new_mem_buf(buffer)\n\n    # Use null passphrase if passphrase is None or empty string. With PKCS#12\n    # password based encryption no password and a zero length password are two\n    # different things, but OpenSSL implementation will try both to figure out\n    # which one works.\n    if not passphrase:\n        passphrase = _ffi.NULL\n\n    p12 = _lib.d2i_PKCS12_bio(bio, _ffi.NULL)\n    if p12 == _ffi.NULL:\n        _raise_current_error()\n    p12 = _ffi.gc(p12, _lib.PKCS12_free)\n\n    pkey = _ffi.new(\"EVP_PKEY**\")\n    cert = _ffi.new(\"X509**\")\n    cacerts = _ffi.new(\"Cryptography_STACK_OF_X509**\")\n\n    parse_result = _lib.PKCS12_parse(p12, passphrase, pkey, cert, cacerts)\n    if not parse_result:\n        _raise_current_error()\n\n    cacerts = _ffi.gc(cacerts[0], _lib.sk_X509_free)\n\n    # openssl 1.0.0 sometimes leaves an X509_check_private_key error in the\n    # queue for no particular reason.  This error isn't interesting to anyone\n    # outside this function.  It's not even interesting to us.  Get rid of it.\n    try:\n        _raise_current_error()\n    except Error:\n        pass\n\n    if pkey[0] == _ffi.NULL:\n        pykey = None\n    else:\n        pykey = PKey.__new__(PKey)\n        pykey._pkey = _ffi.gc(pkey[0], _lib.EVP_PKEY_free)\n\n    if cert[0] == _ffi.NULL:\n        pycert = None\n        friendlyname = None\n    else:\n        pycert = X509._from_raw_x509_ptr(cert[0])\n\n        friendlyname_length = _ffi.new(\"int*\")\n        friendlyname_buffer = _lib.X509_alias_get0(\n            cert[0], friendlyname_length\n        )\n        friendlyname = _ffi.buffer(\n            friendlyname_buffer, friendlyname_length[0]\n        )[:]\n        if friendlyname_buffer == _ffi.NULL:\n            friendlyname = None\n\n    pycacerts = []\n    for i in range(_lib.sk_X509_num(cacerts)):\n        x509 = _lib.sk_X509_value(cacerts, i)\n        pycacert = X509._from_raw_x509_ptr(x509)\n        pycacerts.append(pycacert)\n    if not pycacerts:\n        pycacerts = None\n\n    pkcs12 = PKCS12.__new__(PKCS12)\n    pkcs12._pkey = pykey\n    pkcs12._cert = pycert\n    pkcs12._cacerts = pycacerts\n    pkcs12._friendlyname = friendlyname\n    return pkcs12\n\n\n# There are no direct unit tests for this initialization.  It is tested\n# indirectly since it is necessary for functions like dump_privatekey when\n# using encryption.\n#\n# Thus OpenSSL.test.test_crypto.FunctionTests.test_dump_privatekey_passphrase\n# and some other similar tests may fail without this (though they may not if\n# the Python runtime has already done some initialization of the underlying\n# OpenSSL library (and is linked against the same one that cryptography is\n# using)).\n_lib.OpenSSL_add_all_algorithms()\n\n# This is similar but exercised mainly by exception_from_error_queue.  It calls\n# both ERR_load_crypto_strings() and ERR_load_SSL_strings().\n_lib.SSL_load_error_strings()\n\n\n# Set the default string mask to match OpenSSL upstream (since 2005) and\n# RFC5280 recommendations.\n_lib.ASN1_STRING_set_default_mask_asc(b'utf8only')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/OpenSSL/debug.py",
    "content": "from __future__ import print_function\n\nimport ssl\nimport sys\n\nimport OpenSSL.SSL\nimport cffi\nimport cryptography\n\nfrom . import version\n\n\n_env_info = u\"\"\"\\\npyOpenSSL: {pyopenssl}\ncryptography: {cryptography}\ncffi: {cffi}\ncryptography's compiled against OpenSSL: {crypto_openssl_compile}\ncryptography's linked OpenSSL: {crypto_openssl_link}\nPythons's OpenSSL: {python_openssl}\nPython executable: {python}\nPython version: {python_version}\nPlatform: {platform}\nsys.path: {sys_path}\"\"\".format(\n    pyopenssl=version.__version__,\n    crypto_openssl_compile=OpenSSL._util.ffi.string(\n        OpenSSL._util.lib.OPENSSL_VERSION_TEXT,\n    ).decode(\"ascii\"),\n    crypto_openssl_link=OpenSSL.SSL.SSLeay_version(\n        OpenSSL.SSL.SSLEAY_VERSION\n    ).decode(\"ascii\"),\n    python_openssl=getattr(ssl, \"OPENSSL_VERSION\", \"n/a\"),\n    cryptography=cryptography.__version__,\n    cffi=cffi.__version__,\n    python=sys.executable,\n    python_version=sys.version,\n    platform=sys.platform,\n    sys_path=sys.path,\n)\n\n\nif __name__ == \"__main__\":\n    print(_env_info)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/OpenSSL/rand.py",
    "content": "\"\"\"\nPRNG management routines, thin wrappers.\n\"\"\"\n\nfrom OpenSSL._util import lib as _lib\n\n\ndef add(buffer, entropy):\n    \"\"\"\n    Mix bytes from *string* into the PRNG state.\n\n    The *entropy* argument is (the lower bound of) an estimate of how much\n    randomness is contained in *string*, measured in bytes.\n\n    For more information, see e.g. :rfc:`1750`.\n\n    This function is only relevant if you are forking Python processes and\n    need to reseed the CSPRNG after fork.\n\n    :param buffer: Buffer with random data.\n    :param entropy: The entropy (in bytes) measurement of the buffer.\n\n    :return: :obj:`None`\n    \"\"\"\n    if not isinstance(buffer, bytes):\n        raise TypeError(\"buffer must be a byte string\")\n\n    if not isinstance(entropy, int):\n        raise TypeError(\"entropy must be an integer\")\n\n    _lib.RAND_add(buffer, len(buffer), entropy)\n\n\ndef status():\n    \"\"\"\n    Check whether the PRNG has been seeded with enough data.\n\n    :return: 1 if the PRNG is seeded enough, 0 otherwise.\n    \"\"\"\n    return _lib.RAND_status()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/OpenSSL/tsafe.py",
    "content": "import warnings\nfrom threading import RLock as _RLock\n\nfrom OpenSSL import SSL as _ssl\n\n\nwarnings.warn(\n    \"OpenSSL.tsafe is deprecated and will be removed\",\n    DeprecationWarning, stacklevel=3\n)\n\n\nclass Connection:\n    def __init__(self, *args):\n        self._ssl_conn = _ssl.Connection(*args)\n        self._lock = _RLock()\n\n    for f in ('get_context', 'pending', 'send', 'write', 'recv', 'read',\n              'renegotiate', 'bind', 'listen', 'connect', 'accept',\n              'setblocking', 'fileno', 'shutdown', 'close', 'get_cipher_list',\n              'getpeername', 'getsockname', 'getsockopt', 'setsockopt',\n              'makefile', 'get_app_data', 'set_app_data', 'state_string',\n              'sock_shutdown', 'get_peer_certificate', 'get_peer_cert_chain',\n              'want_read', 'want_write', 'set_connect_state',\n              'set_accept_state', 'connect_ex', 'sendall'):\n        exec(\"\"\"def %s(self, *args):\n            self._lock.acquire()\n            try:\n                return self._ssl_conn.%s(*args)\n            finally:\n                self._lock.release()\\n\"\"\" % (f, f))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/OpenSSL/version.py",
    "content": "# Copyright (C) AB Strakt\n# Copyright (C) Jean-Paul Calderone\n# See LICENSE for details.\n\n\"\"\"\npyOpenSSL - A simple wrapper around the OpenSSL library\n\"\"\"\n\n__all__ = [\n    \"__author__\", \"__copyright__\", \"__email__\", \"__license__\", \"__summary__\",\n    \"__title__\", \"__uri__\", \"__version__\",\n]\n\n__version__ = \"19.0.0\"\n\n__title__ = \"pyOpenSSL\"\n__uri__ = \"https://pyopenssl.org/\"\n__summary__ = \"Python wrapper module around the OpenSSL library\"\n__author__ = \"The pyOpenSSL developers\"\n__email__ = \"cryptography-dev@python.org\"\n__license__ = \"Apache License, Version 2.0\"\n__copyright__ = \"Copyright 2001-2017 {0}\".format(__author__)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyDispatcher-2.0.5-py3.6.egg-info/PKG-INFO",
    "content": "Metadata-Version: 1.2\nName: PyDispatcher\nVersion: 2.0.5\nSummary: Multi-producer-multi-consumer signal dispatching mechanism\nHome-page: http://pydispatcher.sourceforge.net\nAuthor: Patrick K. O'Brien\nAuthor-email: pydispatcher-devel@lists.sourceforge.net\nMaintainer: Mike C. Fletcher\nMaintainer-email: pydispatcher-devel@lists.sourceforge.net\nLicense: BSD\nDescription: Dispatcher mechanism for creating event models\n        \n        PyDispatcher is an enhanced version of Patrick K. O'Brien's\n        original dispatcher.py module.  It provides the Python\n        programmer with a robust mechanism for event routing within\n        various application contexts.\n        \n        Included in the package are the robustapply and saferef\n        modules, which provide the ability to selectively apply\n        arguments to callable objects and to reference instance\n        methods using weak-references.\n        \nKeywords: dispatcher,dispatch,pydispatch,event,signal,sender,receiver,propagate,multi-consumer,multi-producer,saferef,robustapply,apply\nPlatform: Any\nClassifier: License :: OSI Approved :: BSD License\nClassifier: Programming Language :: Python\nClassifier: Programming Language :: Python :: 3\nClassifier: Topic :: Software Development :: Libraries :: Python Modules\nClassifier: Intended Audience :: Developers\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyDispatcher-2.0.5-py3.6.egg-info/SOURCES.txt",
    "content": "MANIFEST.in\nlicense.txt\nsetup.cfg\nsetup.py\nPyDispatcher.egg-info/PKG-INFO\nPyDispatcher.egg-info/SOURCES.txt\nPyDispatcher.egg-info/dependency_links.txt\nPyDispatcher.egg-info/top_level.txt\ndocs/index.html\ndocs/images/greypinstripe.png\ndocs/pydoc/__init__.py\ndocs/pydoc/builddocs.py\ndocs/pydoc/pydispatch.__init__.html\ndocs/pydoc/pydispatch.dispatcher.html\ndocs/pydoc/pydispatch.errors.html\ndocs/pydoc/pydispatch.html\ndocs/pydoc/pydispatch.robust.html\ndocs/pydoc/pydispatch.robustapply.html\ndocs/pydoc/pydispatch.saferef.html\ndocs/pydoc/pydoc2.py\ndocs/pydoc/weakref.html\ndocs/style/sitestyle.css\nexamples/__init__.py\nexamples/extra_args.py\nexamples/hello_messages.py\nexamples/simple_sample.py\npydispatch/__init__.py\npydispatch/dispatcher.py\npydispatch/errors.py\npydispatch/robust.py\npydispatch/robustapply.py\npydispatch/saferef.py\ntests/__init__.py\ntests/test_dispatcher.py\ntests/test_robustapply.py\ntests/test_saferef.py"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyDispatcher-2.0.5-py3.6.egg-info/dependency_links.txt",
    "content": "\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyDispatcher-2.0.5-py3.6.egg-info/installed-files.txt",
    "content": "../pydispatch/__init__.py\n../pydispatch/__pycache__/__init__.cpython-36.pyc\n../pydispatch/__pycache__/dispatcher.cpython-36.pyc\n../pydispatch/__pycache__/errors.cpython-36.pyc\n../pydispatch/__pycache__/robust.cpython-36.pyc\n../pydispatch/__pycache__/robustapply.cpython-36.pyc\n../pydispatch/__pycache__/saferef.cpython-36.pyc\n../pydispatch/dispatcher.py\n../pydispatch/errors.py\n../pydispatch/robust.py\n../pydispatch/robustapply.py\n../pydispatch/saferef.py\nPKG-INFO\nSOURCES.txt\ndependency_links.txt\ntop_level.txt\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyDispatcher-2.0.5-py3.6.egg-info/top_level.txt",
    "content": "pydispatch\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyHamcrest-1.9.0.dist-info/DESCRIPTION.rst",
    "content": "PyHamcrest\n==========\n\n| |docs| |travis| |coveralls| |landscape| |scrutinizer| |codeclimate|\n| |version| |downloads| |wheel| |supported-versions| |supported-implementations|\n\n.. |docs| image:: https://readthedocs.org/projects/pyhamcrest/badge/?style=flat\n    :target: https://pyhamcrest.readthedocs.org/\n    :alt: Documentation Status\n\n.. |travis| image:: http://img.shields.io/travis/hamcrest/PyHamcrest/master.png?style=flat\n    :alt: Travis-CI Build Status\n    :target: https://travis-ci.org/hamcrest/PyHamcrest\n\n.. |appveyor| image:: https://ci.appveyor.com/api/projects/status/github/hamcrest/PyHamcrest?branch=master\n    :alt: AppVeyor Build Status\n    :target: https://ci.appveyor.com/project/hamcrest/PyHamcrest\n\n.. |coveralls| image:: http://img.shields.io/coveralls/hamcrest/PyHamcrest/master.png?style=flat\n    :alt: Coverage Status\n    :target: https://coveralls.io/r/hamcrest/PyHamcrest\n\n.. |landscape| image:: https://landscape.io/github/hamcrest/PyHamcrest/master/landscape.svg?style=flat\n    :target: https://landscape.io/github/hamcrest/PyHamcrest/master\n    :alt: Code Quality Status\n\n.. |codeclimate| image:: https://codeclimate.com/github/hamcrest/PyHamcrest/badges/gpa.svg\n   :target: https://codeclimate.com/github/hamcrest/PyHamcrest\n   :alt: Code Climate\n\n.. |version| image:: http://img.shields.io/pypi/v/PyHamcrest.png?style=flat\n    :alt: PyPI Package latest release\n    :target: https://pypi.python.org/pypi/PyHamcrest\n\n.. |downloads| image:: http://img.shields.io/pypi/dm/PyHamcrest.png?style=flat\n    :alt: PyPI Package monthly downloads\n    :target: https://pypi.python.org/pypi/PyHamcrest\n\n.. |wheel| image:: https://pypip.in/wheel/PyHamcrest/badge.png?style=flat\n    :alt: PyPI Wheel\n    :target: https://pypi.python.org/pypi/PyHamcrest\n\n.. |supported-versions| image:: https://pypip.in/py_versions/PyHamcrest/badge.png?style=flat\n    :alt: Supported versions\n    :target: https://pypi.python.org/pypi/PyHamcrest\n\n.. |supported-implementations| image:: https://pypip.in/implementation/PyHamcrest/badge.png?style=flat\n    :alt: Supported imlementations\n    :target: https://pypi.python.org/pypi/PyHamcrest\n\n.. |scrutinizer| image:: https://img.shields.io/scrutinizer/g/hamcrest/PyHamcrest/master.png?style=flat\n    :alt: Scrtinizer Status\n    :target: https://scrutinizer-ci.com/g/hamcrest/PyHamcrest/\n\n\nIntroduction\n============\n\nPyHamcrest is a framework for writing matcher objects, allowing you to\ndeclaratively define \"match\" rules. There are a number of situations where\nmatchers are invaluable, such as UI validation, or data filtering, but it is in\nthe area of writing flexible tests that matchers are most commonly used. This\ntutorial shows you how to use PyHamcrest for unit testing.\n\nWhen writing tests it is sometimes difficult to get the balance right between\noverspecifying the test (and making it brittle to changes), and not specifying\nenough (making the test less valuable since it continues to pass even when the\nthing being tested is broken). Having a tool that allows you to pick out\nprecisely the aspect under test and describe the values it should have, to a\ncontrolled level of precision, helps greatly in writing tests that are \"just\nright.\" Such tests fail when the behavior of the aspect under test deviates\nfrom the expected behavior, yet continue to pass when minor, unrelated changes\nto the behaviour are made.\n\nInstallation\n============\n\nHamcrest can be installed using the usual Python packaging tools. It depends on\ndistribute, but as long as you have a network connection when you install, the\ninstallation process will take care of that for you.\n\nMy first PyHamcrest test\n========================\n\nWe'll start by writing a very simple PyUnit test, but instead of using PyUnit's\n``assertEqual`` method, we'll use PyHamcrest's ``assert_that`` construct and\nthe standard set of matchers:\n\n.. code:: python\n\n from hamcrest import *\n import unittest\n\n class BiscuitTest(unittest.TestCase):\n     def testEquals(self):\n         theBiscuit = Biscuit('Ginger')\n         myBiscuit = Biscuit('Ginger')\n         assert_that(theBiscuit, equal_to(myBiscuit))\n\n if __name__ == '__main__':\n     unittest.main()\n\nThe ``assert_that`` function is a stylized sentence for making a test\nassertion. In this example, the subject of the assertion is the object\n``theBiscuit``, which is the first method parameter. The second method\nparameter is a matcher for ``Biscuit`` objects, here a matcher that checks one\nobject is equal to another using the Python ``==`` operator. The test passes\nsince the ``Biscuit`` class defines an ``__eq__`` method.\n\nIf you have more than one assertion in your test you can include an identifier\nfor the tested value in the assertion:\n\n.. code:: python\n\n assert_that(theBiscuit.getChocolateChipCount(), equal_to(10), 'chocolate chips')\n assert_that(theBiscuit.getHazelnutCount(), equal_to(3), 'hazelnuts')\n\nAs a convenience, assert_that can also be used to verify a boolean condition:\n\n.. code:: python\n\n assert_that(theBiscuit.isCooked(), 'cooked')\n\nThis is equivalent to the ``assert_`` method of unittest.TestCase, but because\nit's a standalone function, it offers greater flexibility in test writing.\n\n\nPredefined matchers\n===================\n\nPyHamcrest comes with a library of useful matchers:\n\n* Object\n\n  * ``equal_to`` - match equal object\n  * ``has_length`` - match ``len()``\n  * ``has_property`` - match value of property with given name\n  * ``has_properties`` - match an object that has all of the given properties.\n  * ``has_string`` - match ``str()``\n  * ``instance_of`` - match object type\n  * ``none``, ``not_none`` - match ``None``, or not ``None``\n  * ``same_instance`` - match same object\n  * ``calling, raises`` - wrap a method call and assert that it raises an exception\n\n* Number\n\n  * ``close_to`` - match number close to a given value\n  * ``greater_than``, ``greater_than_or_equal_to``, ``less_than``,\n    ``less_than_or_equal_to`` - match numeric ordering\n\n* Text\n\n  * ``contains_string`` - match part of a string\n  * ``ends_with`` - match the end of a string\n  * ``equal_to_ignoring_case`` - match the complete string but ignore case\n  * ``equal_to_ignoring_whitespace`` - match the complete string but ignore extra whitespace\n  * ``matches_regexp`` - match a regular expression in a string\n  * ``starts_with`` - match the beginning of a string\n  * ``string_contains_in_order`` - match parts of a string, in relative order\n\n* Logical\n\n  * ``all_of`` - ``and`` together all matchers\n  * ``any_of`` - ``or`` together all matchers\n  * ``anything`` - match anything, useful in composite matchers when you don't care about a particular value\n  * ``is_not`` - negate the matcher\n\n* Sequence\n\n  * ``contains`` - exactly match the entire sequence\n  * ``contains_inanyorder`` - match the entire sequence, but in any order\n  * ``has_item`` - match if given item appears in the sequence\n  * ``has_items`` - match if all given items appear in the sequence, in any order\n  * ``is_in`` - match if item appears in the given sequence\n  * ``only_contains`` - match if sequence's items appear in given list\n  * ``empty`` - match if the sequence is empty\n\n* Dictionary\n\n  * ``has_entries`` - match dictionary with list of key-value pairs\n  * ``has_entry`` - match dictionary containing a key-value pair\n  * ``has_key`` - match dictionary with a key\n  * ``has_value`` - match dictionary with a value\n\n* Decorator\n\n  * ``calling`` - wrap a callable in a deffered object, for subsequent matching on calling behaviour\n  * ``raises`` - Ensure that a deferred callable raises as expected\n  * ``described_as`` - give the matcher a custom failure description\n  * ``is_`` - decorator to improve readability - see `Syntactic sugar` below\n\nThe arguments for many of these matchers accept not just a matching value, but\nanother matcher, so matchers can be composed for greater flexibility. For\nexample, ``only_contains(less_than(5))`` will match any sequence where every\nitem is less than 5.\n\n\nSyntactic sugar\n===============\n\nPyHamcrest strives to make your tests as readable as possible. For example, the\n``is_`` matcher is a wrapper that doesn't add any extra behavior to the\nunderlying matcher. The following assertions are all equivalent:\n\n.. code:: python\n\n assert_that(theBiscuit, equal_to(myBiscuit))\n assert_that(theBiscuit, is_(equal_to(myBiscuit)))\n assert_that(theBiscuit, is_(myBiscuit))\n\nThe last form is allowed since ``is_(value)`` wraps most non-matcher arguments\nwith ``equal_to``. But if the argument is a type, it is wrapped with\n``instance_of``, so the following are also equivalent:\n\n.. code:: python\n\n assert_that(theBiscuit, instance_of(Biscuit))\n assert_that(theBiscuit, is_(instance_of(Biscuit)))\n assert_that(theBiscuit, is_(Biscuit))\n\n*Note that PyHamcrest's ``is_`` matcher is unrelated to Python's ``is``\noperator. The matcher for object identity is ``same_instance``.*\n\n\nWriting custom matchers\n=======================\n\nPyHamcrest comes bundled with lots of useful matchers, but you'll probably find\nthat you need to create your own from time to time to fit your testing needs.\nThis commonly occurs when you find a fragment of code that tests the same set\nof properties over and over again (and in different tests), and you want to\nbundle the fragment into a single assertion. By writing your own matcher you'll\neliminate code duplication and make your tests more readable!\n\nLet's write our own matcher for testing if a calendar date falls on a Saturday.\nThis is the test we want to write:\n\n.. code:: python\n\n def testDateIsOnASaturday(self):\n     d = datetime.date(2008, 04, 26)\n     assert_that(d, is_(on_a_saturday()))\n\nAnd here's the implementation:\n\n.. code:: python\n\n from hamcrest.core.base_matcher import BaseMatcher\n from hamcrest.core.helpers.hasmethod import hasmethod\n\n class IsGivenDayOfWeek(BaseMatcher):\n\n     def __init__(self, day):\n         self.day = day  # Monday is 0, Sunday is 6\n\n     def _matches(self, item):\n         if not hasmethod(item, 'weekday'):\n             return False\n         return item.weekday() == self.day\n\n     def describe_to(self, description):\n         day_as_string = ['Monday', 'Tuesday', 'Wednesday', 'Thursday',\n                          'Friday', 'Saturday', 'Sunday']\n         description.append_text('calendar date falling on ')    \\\n                    .append_text(day_as_string[self.day])\n\n def on_a_saturday():\n     return IsGivenDayOfWeek(5)\n\nFor our Matcher implementation we implement the ``_matches`` method - which\ncalls the ``weekday`` method after confirming that the argument (which may not\nbe a date) has such a method - and the ``describe_to`` method - which is used\nto produce a failure message when a test fails. Here's an example of how the\nfailure message looks:\n\n.. code:: python\n\n assert_that(datetime.date(2008, 04, 06), is_(on_a_saturday()))\n\nfails with the message::\n\n    AssertionError:\n    Expected: is calendar date falling on Saturday\n         got: <2008-04-06>\n\nLet's say this matcher is saved in a module named ``isgivendayofweek``. We\ncould use it in our test by importing the factory function ``on_a_saturday``:\n\n.. code:: python\n\n from hamcrest import *\n import unittest\n from isgivendayofweek import on_a_saturday\n\n class DateTest(unittest.TestCase):\n     def testDateIsOnASaturday(self):\n         d = datetime.date(2008, 04, 26)\n         assert_that(d, is_(on_a_saturday()))\n\n if __name__ == '__main__':\n     unittest.main()\n\nEven though the ``on_a_saturday`` function creates a new matcher each time it\nis called, you should not assume this is the only usage pattern for your\nmatcher. Therefore you should make sure your matcher is stateless, so a single\ninstance can be reused between matches.\n\n\nMore resources\n==============\n\n* Documentation_\n* Package_\n* Sources_\n* Hamcrest_\n\n.. _Documentation: http://readthedocs.org/docs/pyhamcrest/en/V1.8.2/\n.. _Package: http://pypi.python.org/pypi/PyHamcrest\n.. _Sources: https://github.com/hamcrest/PyHamcrest\n.. _Hamcrest: http://hamcrest.org\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyHamcrest-1.9.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyHamcrest-1.9.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.0\nName: PyHamcrest\nVersion: 1.9.0\nSummary: Hamcrest framework for matcher objects\nHome-page: https://github.com/hamcrest/PyHamcrest\nAuthor: Chris Rose\nAuthor-email: offline@offby1.net\nLicense: New BSD\nDownload-URL: http://pypi.python.org/packages/source/P/PyHamcrest/PyHamcrest-1.9.0.tar.gz\nKeywords: hamcrest matchers pyunit unit test testing unittest unittesting\nPlatform: All\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Environment :: Console\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: BSD License\nClassifier: Natural Language :: English\nClassifier: Operating System :: OS Independent\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: Implementation :: CPython\nClassifier: Programming Language :: Python :: Implementation :: Jython\nClassifier: Programming Language :: Python :: Implementation :: PyPy\nClassifier: Topic :: Software Development\nClassifier: Topic :: Software Development :: Quality Assurance\nClassifier: Topic :: Software Development :: Testing\nProvides: hamcrest\nRequires-Dist: setuptools\nRequires-Dist: six\n\nPyHamcrest\n==========\n\n| |docs| |travis| |coveralls| |landscape| |scrutinizer| |codeclimate|\n| |version| |downloads| |wheel| |supported-versions| |supported-implementations|\n\n.. |docs| image:: https://readthedocs.org/projects/pyhamcrest/badge/?style=flat\n    :target: https://pyhamcrest.readthedocs.org/\n    :alt: Documentation Status\n\n.. |travis| image:: http://img.shields.io/travis/hamcrest/PyHamcrest/master.png?style=flat\n    :alt: Travis-CI Build Status\n    :target: https://travis-ci.org/hamcrest/PyHamcrest\n\n.. |appveyor| image:: https://ci.appveyor.com/api/projects/status/github/hamcrest/PyHamcrest?branch=master\n    :alt: AppVeyor Build Status\n    :target: https://ci.appveyor.com/project/hamcrest/PyHamcrest\n\n.. |coveralls| image:: http://img.shields.io/coveralls/hamcrest/PyHamcrest/master.png?style=flat\n    :alt: Coverage Status\n    :target: https://coveralls.io/r/hamcrest/PyHamcrest\n\n.. |landscape| image:: https://landscape.io/github/hamcrest/PyHamcrest/master/landscape.svg?style=flat\n    :target: https://landscape.io/github/hamcrest/PyHamcrest/master\n    :alt: Code Quality Status\n\n.. |codeclimate| image:: https://codeclimate.com/github/hamcrest/PyHamcrest/badges/gpa.svg\n   :target: https://codeclimate.com/github/hamcrest/PyHamcrest\n   :alt: Code Climate\n\n.. |version| image:: http://img.shields.io/pypi/v/PyHamcrest.png?style=flat\n    :alt: PyPI Package latest release\n    :target: https://pypi.python.org/pypi/PyHamcrest\n\n.. |downloads| image:: http://img.shields.io/pypi/dm/PyHamcrest.png?style=flat\n    :alt: PyPI Package monthly downloads\n    :target: https://pypi.python.org/pypi/PyHamcrest\n\n.. |wheel| image:: https://pypip.in/wheel/PyHamcrest/badge.png?style=flat\n    :alt: PyPI Wheel\n    :target: https://pypi.python.org/pypi/PyHamcrest\n\n.. |supported-versions| image:: https://pypip.in/py_versions/PyHamcrest/badge.png?style=flat\n    :alt: Supported versions\n    :target: https://pypi.python.org/pypi/PyHamcrest\n\n.. |supported-implementations| image:: https://pypip.in/implementation/PyHamcrest/badge.png?style=flat\n    :alt: Supported imlementations\n    :target: https://pypi.python.org/pypi/PyHamcrest\n\n.. |scrutinizer| image:: https://img.shields.io/scrutinizer/g/hamcrest/PyHamcrest/master.png?style=flat\n    :alt: Scrtinizer Status\n    :target: https://scrutinizer-ci.com/g/hamcrest/PyHamcrest/\n\n\nIntroduction\n============\n\nPyHamcrest is a framework for writing matcher objects, allowing you to\ndeclaratively define \"match\" rules. There are a number of situations where\nmatchers are invaluable, such as UI validation, or data filtering, but it is in\nthe area of writing flexible tests that matchers are most commonly used. This\ntutorial shows you how to use PyHamcrest for unit testing.\n\nWhen writing tests it is sometimes difficult to get the balance right between\noverspecifying the test (and making it brittle to changes), and not specifying\nenough (making the test less valuable since it continues to pass even when the\nthing being tested is broken). Having a tool that allows you to pick out\nprecisely the aspect under test and describe the values it should have, to a\ncontrolled level of precision, helps greatly in writing tests that are \"just\nright.\" Such tests fail when the behavior of the aspect under test deviates\nfrom the expected behavior, yet continue to pass when minor, unrelated changes\nto the behaviour are made.\n\nInstallation\n============\n\nHamcrest can be installed using the usual Python packaging tools. It depends on\ndistribute, but as long as you have a network connection when you install, the\ninstallation process will take care of that for you.\n\nMy first PyHamcrest test\n========================\n\nWe'll start by writing a very simple PyUnit test, but instead of using PyUnit's\n``assertEqual`` method, we'll use PyHamcrest's ``assert_that`` construct and\nthe standard set of matchers:\n\n.. code:: python\n\n from hamcrest import *\n import unittest\n\n class BiscuitTest(unittest.TestCase):\n     def testEquals(self):\n         theBiscuit = Biscuit('Ginger')\n         myBiscuit = Biscuit('Ginger')\n         assert_that(theBiscuit, equal_to(myBiscuit))\n\n if __name__ == '__main__':\n     unittest.main()\n\nThe ``assert_that`` function is a stylized sentence for making a test\nassertion. In this example, the subject of the assertion is the object\n``theBiscuit``, which is the first method parameter. The second method\nparameter is a matcher for ``Biscuit`` objects, here a matcher that checks one\nobject is equal to another using the Python ``==`` operator. The test passes\nsince the ``Biscuit`` class defines an ``__eq__`` method.\n\nIf you have more than one assertion in your test you can include an identifier\nfor the tested value in the assertion:\n\n.. code:: python\n\n assert_that(theBiscuit.getChocolateChipCount(), equal_to(10), 'chocolate chips')\n assert_that(theBiscuit.getHazelnutCount(), equal_to(3), 'hazelnuts')\n\nAs a convenience, assert_that can also be used to verify a boolean condition:\n\n.. code:: python\n\n assert_that(theBiscuit.isCooked(), 'cooked')\n\nThis is equivalent to the ``assert_`` method of unittest.TestCase, but because\nit's a standalone function, it offers greater flexibility in test writing.\n\n\nPredefined matchers\n===================\n\nPyHamcrest comes with a library of useful matchers:\n\n* Object\n\n  * ``equal_to`` - match equal object\n  * ``has_length`` - match ``len()``\n  * ``has_property`` - match value of property with given name\n  * ``has_properties`` - match an object that has all of the given properties.\n  * ``has_string`` - match ``str()``\n  * ``instance_of`` - match object type\n  * ``none``, ``not_none`` - match ``None``, or not ``None``\n  * ``same_instance`` - match same object\n  * ``calling, raises`` - wrap a method call and assert that it raises an exception\n\n* Number\n\n  * ``close_to`` - match number close to a given value\n  * ``greater_than``, ``greater_than_or_equal_to``, ``less_than``,\n    ``less_than_or_equal_to`` - match numeric ordering\n\n* Text\n\n  * ``contains_string`` - match part of a string\n  * ``ends_with`` - match the end of a string\n  * ``equal_to_ignoring_case`` - match the complete string but ignore case\n  * ``equal_to_ignoring_whitespace`` - match the complete string but ignore extra whitespace\n  * ``matches_regexp`` - match a regular expression in a string\n  * ``starts_with`` - match the beginning of a string\n  * ``string_contains_in_order`` - match parts of a string, in relative order\n\n* Logical\n\n  * ``all_of`` - ``and`` together all matchers\n  * ``any_of`` - ``or`` together all matchers\n  * ``anything`` - match anything, useful in composite matchers when you don't care about a particular value\n  * ``is_not`` - negate the matcher\n\n* Sequence\n\n  * ``contains`` - exactly match the entire sequence\n  * ``contains_inanyorder`` - match the entire sequence, but in any order\n  * ``has_item`` - match if given item appears in the sequence\n  * ``has_items`` - match if all given items appear in the sequence, in any order\n  * ``is_in`` - match if item appears in the given sequence\n  * ``only_contains`` - match if sequence's items appear in given list\n  * ``empty`` - match if the sequence is empty\n\n* Dictionary\n\n  * ``has_entries`` - match dictionary with list of key-value pairs\n  * ``has_entry`` - match dictionary containing a key-value pair\n  * ``has_key`` - match dictionary with a key\n  * ``has_value`` - match dictionary with a value\n\n* Decorator\n\n  * ``calling`` - wrap a callable in a deffered object, for subsequent matching on calling behaviour\n  * ``raises`` - Ensure that a deferred callable raises as expected\n  * ``described_as`` - give the matcher a custom failure description\n  * ``is_`` - decorator to improve readability - see `Syntactic sugar` below\n\nThe arguments for many of these matchers accept not just a matching value, but\nanother matcher, so matchers can be composed for greater flexibility. For\nexample, ``only_contains(less_than(5))`` will match any sequence where every\nitem is less than 5.\n\n\nSyntactic sugar\n===============\n\nPyHamcrest strives to make your tests as readable as possible. For example, the\n``is_`` matcher is a wrapper that doesn't add any extra behavior to the\nunderlying matcher. The following assertions are all equivalent:\n\n.. code:: python\n\n assert_that(theBiscuit, equal_to(myBiscuit))\n assert_that(theBiscuit, is_(equal_to(myBiscuit)))\n assert_that(theBiscuit, is_(myBiscuit))\n\nThe last form is allowed since ``is_(value)`` wraps most non-matcher arguments\nwith ``equal_to``. But if the argument is a type, it is wrapped with\n``instance_of``, so the following are also equivalent:\n\n.. code:: python\n\n assert_that(theBiscuit, instance_of(Biscuit))\n assert_that(theBiscuit, is_(instance_of(Biscuit)))\n assert_that(theBiscuit, is_(Biscuit))\n\n*Note that PyHamcrest's ``is_`` matcher is unrelated to Python's ``is``\noperator. The matcher for object identity is ``same_instance``.*\n\n\nWriting custom matchers\n=======================\n\nPyHamcrest comes bundled with lots of useful matchers, but you'll probably find\nthat you need to create your own from time to time to fit your testing needs.\nThis commonly occurs when you find a fragment of code that tests the same set\nof properties over and over again (and in different tests), and you want to\nbundle the fragment into a single assertion. By writing your own matcher you'll\neliminate code duplication and make your tests more readable!\n\nLet's write our own matcher for testing if a calendar date falls on a Saturday.\nThis is the test we want to write:\n\n.. code:: python\n\n def testDateIsOnASaturday(self):\n     d = datetime.date(2008, 04, 26)\n     assert_that(d, is_(on_a_saturday()))\n\nAnd here's the implementation:\n\n.. code:: python\n\n from hamcrest.core.base_matcher import BaseMatcher\n from hamcrest.core.helpers.hasmethod import hasmethod\n\n class IsGivenDayOfWeek(BaseMatcher):\n\n     def __init__(self, day):\n         self.day = day  # Monday is 0, Sunday is 6\n\n     def _matches(self, item):\n         if not hasmethod(item, 'weekday'):\n             return False\n         return item.weekday() == self.day\n\n     def describe_to(self, description):\n         day_as_string = ['Monday', 'Tuesday', 'Wednesday', 'Thursday',\n                          'Friday', 'Saturday', 'Sunday']\n         description.append_text('calendar date falling on ')    \\\n                    .append_text(day_as_string[self.day])\n\n def on_a_saturday():\n     return IsGivenDayOfWeek(5)\n\nFor our Matcher implementation we implement the ``_matches`` method - which\ncalls the ``weekday`` method after confirming that the argument (which may not\nbe a date) has such a method - and the ``describe_to`` method - which is used\nto produce a failure message when a test fails. Here's an example of how the\nfailure message looks:\n\n.. code:: python\n\n assert_that(datetime.date(2008, 04, 06), is_(on_a_saturday()))\n\nfails with the message::\n\n    AssertionError:\n    Expected: is calendar date falling on Saturday\n         got: <2008-04-06>\n\nLet's say this matcher is saved in a module named ``isgivendayofweek``. We\ncould use it in our test by importing the factory function ``on_a_saturday``:\n\n.. code:: python\n\n from hamcrest import *\n import unittest\n from isgivendayofweek import on_a_saturday\n\n class DateTest(unittest.TestCase):\n     def testDateIsOnASaturday(self):\n         d = datetime.date(2008, 04, 26)\n         assert_that(d, is_(on_a_saturday()))\n\n if __name__ == '__main__':\n     unittest.main()\n\nEven though the ``on_a_saturday`` function creates a new matcher each time it\nis called, you should not assume this is the only usage pattern for your\nmatcher. Therefore you should make sure your matcher is stateless, so a single\ninstance can be reused between matches.\n\n\nMore resources\n==============\n\n* Documentation_\n* Package_\n* Sources_\n* Hamcrest_\n\n.. _Documentation: http://readthedocs.org/docs/pyhamcrest/en/V1.8.2/\n.. _Package: http://pypi.python.org/pypi/PyHamcrest\n.. _Sources: https://github.com/hamcrest/PyHamcrest\n.. _Hamcrest: http://hamcrest.org\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyHamcrest-1.9.0.dist-info/RECORD",
    "content": "PyHamcrest-1.9.0.dist-info/DESCRIPTION.rst,sha256=13XTDh2baR2aJ91v_lAOjEXD7Ydush_RHhk0Z3azfs8,11973\r\nPyHamcrest-1.9.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nPyHamcrest-1.9.0.dist-info/METADATA,sha256=s0naXZHUZhft0MWcUeZVaZYlREKPOqHp3mUQrhUoC6s,13276\r\nPyHamcrest-1.9.0.dist-info/RECORD,,\r\nPyHamcrest-1.9.0.dist-info/WHEEL,sha256=AvR0WeTpDaxT645bl5FQxUK6NPsTls2ttpcGJg3j1Xg,110\r\nPyHamcrest-1.9.0.dist-info/metadata.json,sha256=Jqs-ZSW5kWSnfvxDsRMwSQH6TxEqSJjBJWiQk1G-c_A,1545\r\nPyHamcrest-1.9.0.dist-info/pbr.json,sha256=jdAcCmfO0nnMs9-YKXuwDyKnxc4qGwyUxyGulF9Pam4,47\r\nPyHamcrest-1.9.0.dist-info/top_level.txt,sha256=mRc0yPsPQSqFgWBmZBY33u-05Xtm5M4GEve4NjYdloQ,9\r\nhamcrest/__init__.py,sha256=Uo0mxeePyXP9_yIzBBvKqIL6tzEHqBwBO1eSHfAKies,230\r\nhamcrest/__pycache__/__init__.cpython-36.pyc,,\r\nhamcrest/core/__init__.py,sha256=nDkYm1E1P7XpHmR8EHu17eahlmC6uYix4HurTyJjhlE,230\r\nhamcrest/core/__pycache__/__init__.cpython-36.pyc,,\r\nhamcrest/core/__pycache__/assert_that.cpython-36.pyc,,\r\nhamcrest/core/__pycache__/base_description.cpython-36.pyc,,\r\nhamcrest/core/__pycache__/base_matcher.cpython-36.pyc,,\r\nhamcrest/core/__pycache__/compat.cpython-36.pyc,,\r\nhamcrest/core/__pycache__/description.cpython-36.pyc,,\r\nhamcrest/core/__pycache__/matcher.cpython-36.pyc,,\r\nhamcrest/core/__pycache__/selfdescribing.cpython-36.pyc,,\r\nhamcrest/core/__pycache__/selfdescribingvalue.cpython-36.pyc,,\r\nhamcrest/core/__pycache__/string_description.cpython-36.pyc,,\r\nhamcrest/core/assert_that.py,sha256=mPdTQQVsjUliK3xp8l_Vn3YmMzg_h5rYhWJk2mstMc0,2428\r\nhamcrest/core/base_description.py,sha256=auvrelro2vGh_A05TQxwbaBJStvfHiFqm0TL56luxEU,2841\r\nhamcrest/core/base_matcher.py,sha256=eRhLv7zFBJGaz68vEsDlvKbrWwU8GRDfZc7pWBNcxwI,1193\r\nhamcrest/core/compat.py,sha256=wUi1u_nIhgUA3kFGJDZLQ2D_cRw79E1SxPDMaI4mzG0,642\r\nhamcrest/core/core/__init__.py,sha256=7q_pNO9cmtV3BEixiGcueNdbxRxlKEFZ1RSO-5GP58E,770\r\nhamcrest/core/core/__pycache__/__init__.cpython-36.pyc,,\r\nhamcrest/core/core/__pycache__/allof.cpython-36.pyc,,\r\nhamcrest/core/core/__pycache__/anyof.cpython-36.pyc,,\r\nhamcrest/core/core/__pycache__/described_as.cpython-36.pyc,,\r\nhamcrest/core/core/__pycache__/is_.cpython-36.pyc,,\r\nhamcrest/core/core/__pycache__/isanything.cpython-36.pyc,,\r\nhamcrest/core/core/__pycache__/isequal.cpython-36.pyc,,\r\nhamcrest/core/core/__pycache__/isinstanceof.cpython-36.pyc,,\r\nhamcrest/core/core/__pycache__/isnone.cpython-36.pyc,,\r\nhamcrest/core/core/__pycache__/isnot.cpython-36.pyc,,\r\nhamcrest/core/core/__pycache__/issame.cpython-36.pyc,,\r\nhamcrest/core/core/__pycache__/raises.cpython-36.pyc,,\r\nhamcrest/core/core/allof.py,sha256=x2ea18Z5cioRybs1heTd3E8zYtpFbuBJg3vIU3vl9k0,1487\r\nhamcrest/core/core/anyof.py,sha256=8j2KAsaToXbv8CA5hed4bqPR3hscODIiaFhAlAyJ2Vs,1097\r\nhamcrest/core/core/described_as.py,sha256=kyy_qRpoebWB1bS2ReAkNDt-79iXu6HqHxOG0GT7PtQ,1623\r\nhamcrest/core/core/is_.py,sha256=C7UCASfr4AIlaaMZnT5d34OthAZQ3rYv8OhszQjz-Eg,2547\r\nhamcrest/core/core/isanything.py,sha256=D2QO5dbDhwlVRGLFrnxOSijTyeKN2iWLRwjpvnumkvg,798\r\nhamcrest/core/core/isequal.py,sha256=TAwF_lWIjVokPruXN8IGS6ajzPGlThanTLPdhktKwRQ,893\r\nhamcrest/core/core/isinstanceof.py,sha256=dnt8YKLhYwGZvDkJ0OTdLd1PN9cB9ZWCg5k8kdnEuqI,1352\r\nhamcrest/core/core/isnone.py,sha256=51ueQKBgg0RzWVLzjFOyt6K0ejk2EbXUlUX90ORPm80,557\r\nhamcrest/core/core/isnot.py,sha256=_z_ynAVUXEUGWoiRlynFa_yaCVh9cK9LIOznDfKVZeo,1533\r\nhamcrest/core/core/issame.py,sha256=8FvAjud4HTuyz7O-XoJbzLtKhChCr1_5JmzMYMeQt1s,1261\r\nhamcrest/core/core/raises.py,sha256=BZXtMlQiEqEjQMYT76HUiuQNRjTECIUmL82_FKYhAvs,3610\r\nhamcrest/core/description.py,sha256=gbVS-ejZJ783o-WEA66bXnXc9DH5cOlQXg0FlzoVGro,1729\r\nhamcrest/core/helpers/__init__.py,sha256=mPsycYI18LoGawOo9BfETa7yKtnM-fDjFOr43BIevUg,146\r\nhamcrest/core/helpers/__pycache__/__init__.cpython-36.pyc,,\r\nhamcrest/core/helpers/__pycache__/hasmethod.cpython-36.pyc,,\r\nhamcrest/core/helpers/__pycache__/wrap_matcher.cpython-36.pyc,,\r\nhamcrest/core/helpers/hasmethod.py,sha256=LPh_WDRuyKYII3G3fX_x2Ql-ECuPJn4tK5eWMLbetLg,325\r\nhamcrest/core/helpers/wrap_matcher.py,sha256=IQTtw98Pp1NXcVTy9boaNh6jayvawKHhX62R3ZwnVwQ,880\r\nhamcrest/core/matcher.py,sha256=BG6e8bIJvwFI0qkaSkt_SOuuLI0VidvoX8GQLadYssU,1851\r\nhamcrest/core/selfdescribing.py,sha256=RzwqHRGg00AJYweGiP8JzSxoHFdBo0Q7m5axYfutfG8,574\r\nhamcrest/core/selfdescribingvalue.py,sha256=OpGLOjdPA9FSgmLZzmkfYrDvpG261TDDiM56muROFqQ,834\r\nhamcrest/core/string_description.py,sha256=Jp-SbuY8LAwPucL4NMrwWqRhkg6CMwYE-pH0ZDMUq8A,908\r\nhamcrest/library/__init__.py,sha256=2atNiBCC2g3c-7jw53CltNgU4wEao1uRcheUPl1ML50,1014\r\nhamcrest/library/__pycache__/__init__.cpython-36.pyc,,\r\nhamcrest/library/collection/__init__.py,sha256=iJU6WCsf0R22m11fqMA9Ztb161AZAdrsKG-4Cj38lZ0,635\r\nhamcrest/library/collection/__pycache__/__init__.cpython-36.pyc,,\r\nhamcrest/library/collection/__pycache__/is_empty.cpython-36.pyc,,\r\nhamcrest/library/collection/__pycache__/isdict_containing.cpython-36.pyc,,\r\nhamcrest/library/collection/__pycache__/isdict_containingentries.cpython-36.pyc,,\r\nhamcrest/library/collection/__pycache__/isdict_containingkey.cpython-36.pyc,,\r\nhamcrest/library/collection/__pycache__/isdict_containingvalue.cpython-36.pyc,,\r\nhamcrest/library/collection/__pycache__/isin.cpython-36.pyc,,\r\nhamcrest/library/collection/__pycache__/issequence_containing.cpython-36.pyc,,\r\nhamcrest/library/collection/__pycache__/issequence_containinginanyorder.cpython-36.pyc,,\r\nhamcrest/library/collection/__pycache__/issequence_containinginorder.cpython-36.pyc,,\r\nhamcrest/library/collection/__pycache__/issequence_onlycontaining.cpython-36.pyc,,\r\nhamcrest/library/collection/is_empty.py,sha256=p3-B7DCmdbVzqiW3D1h3krdeqmu9B0mfYOaa6HehODg,913\r\nhamcrest/library/collection/isdict_containing.py,sha256=6QxDtDp_Z2TK-6om8cHnJDh45YdmaNHAEy5n97rzf00,2056\r\nhamcrest/library/collection/isdict_containingentries.py,sha256=xKtdFjrwLN32rUdRR4PBUSYa3yACa6jXsmlZv0D9YAU,5168\r\nhamcrest/library/collection/isdict_containingkey.py,sha256=aiBpusjpZmkUEMZ_rUFZBB1GxIfsqluMjhXoWNScqZY,1535\r\nhamcrest/library/collection/isdict_containingvalue.py,sha256=N7mHKgMnd7q6HsQekHH6DShNYbLiSXN9cpQgcdMIjlw,1565\r\nhamcrest/library/collection/isin.py,sha256=bcVslW0fUq0pM_SrT9gdltTlNfeJkrVPZAlg6riV2Ys,774\r\nhamcrest/library/collection/issequence_containing.py,sha256=ZwYMm2-Ul_JtvjcgdMjipYdz82yUbGmRNsdPAjO9RX0,3001\r\nhamcrest/library/collection/issequence_containinginanyorder.py,sha256=Px_W2-_0XDOXiL2NTTMp16ZTZvBl4m5rXjlMoR4Ulmw,3613\r\nhamcrest/library/collection/issequence_containinginorder.py,sha256=x7AT_kOCaPY0LmZw28ln8xLLHBtT-I3NneoCWzMJoYA,3219\r\nhamcrest/library/collection/issequence_onlycontaining.py,sha256=Ia17P1HVgb43lZfdUEhmPyUUUWtGLix__fqXIQJTUiI,1626\r\nhamcrest/library/integration/__init__.py,sha256=3aiupojVacPksKTXVhqRs9OwUDoUlUw-bjWItJnRg8Q,254\r\nhamcrest/library/integration/__pycache__/__init__.cpython-36.pyc,,\r\nhamcrest/library/integration/__pycache__/match_equality.cpython-36.pyc,,\r\nhamcrest/library/integration/match_equality.py,sha256=0BMth20YLTqjqTLT4qMVldAe2dQV3CJ2j3zLXDIGl9c,1192\r\nhamcrest/library/number/__init__.py,sha256=J3UoFdR9UPq9zXSKe1a9qAlpjaVst8-pnaxsvbCPj78,335\r\nhamcrest/library/number/__pycache__/__init__.cpython-36.pyc,,\r\nhamcrest/library/number/__pycache__/iscloseto.cpython-36.pyc,,\r\nhamcrest/library/number/__pycache__/ordering_comparison.cpython-36.pyc,,\r\nhamcrest/library/number/iscloseto.py,sha256=2lQTw3Xvo5MW-aePxpWVUOwyV_ydXtH6cCAIAxeopk8,2259\r\nhamcrest/library/number/ordering_comparison.py,sha256=8XxVSOzPK29D14h4wtBZYVYKZf6IcABaQEKihEuzlhI,1700\r\nhamcrest/library/object/__init__.py,sha256=pxzCpybBHRaIg7RJUAw7R1Po0llw8QBbVv_R1TXNBhc,319\r\nhamcrest/library/object/__pycache__/__init__.cpython-36.pyc,,\r\nhamcrest/library/object/__pycache__/haslength.cpython-36.pyc,,\r\nhamcrest/library/object/__pycache__/hasproperty.cpython-36.pyc,,\r\nhamcrest/library/object/__pycache__/hasstring.cpython-36.pyc,,\r\nhamcrest/library/object/haslength.py,sha256=mpYVvrBZV548FwEeqlHWYofv9LPgChvnypZ4RhZDMp0,1681\r\nhamcrest/library/object/hasproperty.py,sha256=9t8upZxjqSQp6IvGyTm4ftGvcpBeyk0dy36HgvlXZBg,5740\r\nhamcrest/library/object/hasstring.py,sha256=_Ht1x-DwV4hk2fRuGo_KoayoLOIoWObKoA30u7HnABU,1250\r\nhamcrest/library/text/__init__.py,sha256=3Uuy1lY2p0VEUy1SAIO6IZgDDgyx8ZsB98k-J2FA_R0,548\r\nhamcrest/library/text/__pycache__/__init__.cpython-36.pyc,,\r\nhamcrest/library/text/__pycache__/isequal_ignoring_case.cpython-36.pyc,,\r\nhamcrest/library/text/__pycache__/isequal_ignoring_whitespace.cpython-36.pyc,,\r\nhamcrest/library/text/__pycache__/stringcontains.cpython-36.pyc,,\r\nhamcrest/library/text/__pycache__/stringcontainsinorder.cpython-36.pyc,,\r\nhamcrest/library/text/__pycache__/stringendswith.cpython-36.pyc,,\r\nhamcrest/library/text/__pycache__/stringmatches.cpython-36.pyc,,\r\nhamcrest/library/text/__pycache__/stringstartswith.cpython-36.pyc,,\r\nhamcrest/library/text/__pycache__/substringmatcher.cpython-36.pyc,,\r\nhamcrest/library/text/isequal_ignoring_case.py,sha256=VGkR3PNDOVE1MJT9H4a3SjR2SIYNzT80VoV6NEq3aqw,1257\r\nhamcrest/library/text/isequal_ignoring_whitespace.py,sha256=NQzswc7fk5rOhcoHO4zbYSWqn-WQdQ7Hwf0FoDHAwBM,1667\r\nhamcrest/library/text/stringcontains.py,sha256=JbkSxdFkpRrNYJfSUghboxe1jRLfHAJvOn6PYvMx7fQ,953\r\nhamcrest/library/text/stringcontainsinorder.py,sha256=B3qG7TG24_WyVPGJER2iqi7fzOMZN0UsBRJPtWutBkc,1705\r\nhamcrest/library/text/stringendswith.py,sha256=JjukJWSVWgURvTstrbCGCQdQzY0PMWLul__UlDh2NGA,980\r\nhamcrest/library/text/stringmatches.py,sha256=AEBn8NI3q-YzRUdXiAfnw1Kmse-LLxJUluDAuy_D9nU,1151\r\nhamcrest/library/text/stringstartswith.py,sha256=oOro8G3z8nAOUyOjHHkHhUvY-lt7XRTJzDr9dYxxons,1007\r\nhamcrest/library/text/substringmatcher.py,sha256=lSPxE7pTpTJlUkMtd28WgsM1FFm56JVZixSvAldSZXk,695\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyHamcrest-1.9.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.24.0)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyHamcrest-1.9.0.dist-info/metadata.json",
    "content": "{\"license\": \"New BSD\", \"download_url\": \"http://pypi.python.org/packages/source/P/PyHamcrest/PyHamcrest-1.9.0.tar.gz\", \"name\": \"PyHamcrest\", \"provides\": \"hamcrest\", \"test_requires\": [{\"requires\": [\"hypothesis (>=1.11)\", \"pytest (>=2.8)\", \"mock\", \"pytest-cov\"]}], \"extensions\": {\"python.details\": {\"project_urls\": {\"Home\": \"https://github.com/hamcrest/PyHamcrest\"}, \"contacts\": [{\"name\": \"Chris Rose\", \"role\": \"author\", \"email\": \"offline@offby1.net\"}], \"document_names\": {\"description\": \"DESCRIPTION.rst\"}}}, \"run_requires\": [{\"requires\": [\"setuptools\", \"six\"]}], \"generator\": \"bdist_wheel (0.24.0)\", \"summary\": \"Hamcrest framework for matcher objects\", \"extras\": [], \"classifiers\": [\"Development Status :: 5 - Production/Stable\", \"Environment :: Console\", \"Intended Audience :: Developers\", \"License :: OSI Approved :: BSD License\", \"Natural Language :: English\", \"Operating System :: OS Independent\", \"Programming Language :: Python :: 2\", \"Programming Language :: Python :: 2.7\", \"Programming Language :: Python :: 3\", \"Programming Language :: Python :: 3.4\", \"Programming Language :: Python :: Implementation :: CPython\", \"Programming Language :: Python :: Implementation :: Jython\", \"Programming Language :: Python :: Implementation :: PyPy\", \"Topic :: Software Development\", \"Topic :: Software Development :: Quality Assurance\", \"Topic :: Software Development :: Testing\"], \"version\": \"1.9.0\", \"metadata_version\": \"2.0\", \"keywords\": [\"hamcrest\", \"matchers\", \"pyunit\", \"unit\", \"test\", \"testing\", \"unittest\", \"unittesting\"], \"platform\": \"All\"}"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyHamcrest-1.9.0.dist-info/pbr.json",
    "content": "{\"is_release\": false, \"git_version\": \"d572d69\"}"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/PyHamcrest-1.9.0.dist-info/top_level.txt",
    "content": "hamcrest\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Scrapy-1.7.4.dist-info/AUTHORS",
    "content": "Scrapy was brought to life by Shane Evans while hacking a scraping framework\nprototype for Mydeco (mydeco.com). It soon became maintained, extended and\nimproved by Insophia (insophia.com), with the initial sponsorship of Mydeco to\nbootstrap the project. In mid-2011, Scrapinghub became the new official\nmaintainer.\n\nHere is the list of the primary authors & contributors:\n\n * Pablo Hoffman\n * Daniel Graña\n * Martin Olveyra\n * Gabriel García\n * Michael Cetrulo\n * Artem Bogomyagkov\n * Damian Canabal\n * Andres Moreira\n * Ismael Carnales\n * Matías Aguirre\n * German Hoffmann\n * Anibal Pacheco\n * Bruno Deferrari\n * Shane Evans\n * Ezequiel Rivero\n * Patrick Mezard\n * Rolando Espinoza\n * Ping Yin\n * Lucian Ursu\n * Shuaib Khan\n * Didier Deshommes\n * Vikas Dhiman\n * Jochen Maes\n * Darian Moody\n * Jordi Lonch\n * Zuhao Wan\n * Steven Almeroth\n * Tom Mortimer-Jones\n * Chris Tilden\n * Alexandr N Zamaraev\n * Emanuel Schorsch\n * Michal Danilak\n * Natan Lao\n * Hasnain Lakhani\n * Pedro Faustino\n * Alex Cepoi\n * Ilya Baryshev\n * Libor Nenadál\n * Jae-Myoung Yu\n * Vladislav Poluhin\n * Marc Abramowitz\n * Valentin-Costel Hăloiu\n * Jason Yeo\n * Сергей Прохоров\n * Simon Ratne\n * Julien Duponchelle\n * Jochen Maes\n * Vikas Dhiman\n * Juan Picca\n * Nicolás Ramírez\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Scrapy-1.7.4.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Scrapy-1.7.4.dist-info/LICENSE",
    "content": "Copyright (c) Scrapy developers.\nAll rights reserved.\n\nRedistribution and use in source and binary forms, with or without modification,\nare permitted provided that the following conditions are met:\n\n    1. Redistributions of source code must retain the above copyright notice,\n       this list of conditions, and the following disclaimer.\n\n    2. Redistributions in binary form must reproduce the above copyright\n       notice, this list of conditions, and the following disclaimer in the\n       documentation and/or other materials provided with the distribution.\n\n    3. Neither the name of Scrapy nor the names of its contributors may be used\n       to endorse or promote products derived from this software without\n       specific prior written permission.\n\nTHIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\nANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\nWARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\nDISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR\nANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\nLOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON\nANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\nSOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Scrapy-1.7.4.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: Scrapy\nVersion: 1.7.4\nSummary: A high-level Web Crawling and Web Scraping framework\nHome-page: https://scrapy.org\nAuthor: Scrapy developers\nMaintainer: Pablo Hoffman\nMaintainer-email: pablo@pablohoffman.com\nLicense: BSD\nPlatform: UNKNOWN\nClassifier: Framework :: Scrapy\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Environment :: Console\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: BSD License\nClassifier: Operating System :: OS Independent\nClassifier: Programming Language :: Python\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nClassifier: Programming Language :: Python :: Implementation :: CPython\nClassifier: Programming Language :: Python :: Implementation :: PyPy\nClassifier: Topic :: Internet :: WWW/HTTP\nClassifier: Topic :: Software Development :: Libraries :: Application Frameworks\nClassifier: Topic :: Software Development :: Libraries :: Python Modules\nRequires-Python: >=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*\nRequires-Dist: w3lib (>=1.17.0)\nRequires-Dist: queuelib\nRequires-Dist: pyOpenSSL\nRequires-Dist: cssselect (>=0.9)\nRequires-Dist: six (>=1.5.2)\nRequires-Dist: parsel (>=1.5)\nRequires-Dist: PyDispatcher (>=2.0.5)\nRequires-Dist: service-identity\nRequires-Dist: PyPyDispatcher (>=2.1.0) ; platform_python_implementation == \"PyPy\"\nRequires-Dist: Twisted (>=13.1.0) ; python_version != \"3.4\"\nRequires-Dist: lxml ; python_version != \"3.4\"\nRequires-Dist: Twisted (<=19.2.0,>=13.1.0) ; python_version == \"3.4\"\nRequires-Dist: lxml (<=4.3.5) ; python_version == \"3.4\"\n\n======\nScrapy\n======\n\n.. image:: https://img.shields.io/pypi/v/Scrapy.svg\n   :target: https://pypi.python.org/pypi/Scrapy\n   :alt: PyPI Version\n\n.. image:: https://img.shields.io/pypi/pyversions/Scrapy.svg\n   :target: https://pypi.python.org/pypi/Scrapy\n   :alt: Supported Python Versions\n\n.. image:: https://img.shields.io/travis/scrapy/scrapy/master.svg\n   :target: https://travis-ci.org/scrapy/scrapy\n   :alt: Build Status\n\n.. image:: https://img.shields.io/badge/wheel-yes-brightgreen.svg\n   :target: https://pypi.python.org/pypi/Scrapy\n   :alt: Wheel Status\n\n.. image:: https://img.shields.io/codecov/c/github/scrapy/scrapy/master.svg\n   :target: https://codecov.io/github/scrapy/scrapy?branch=master\n   :alt: Coverage report\n\n.. image:: https://anaconda.org/conda-forge/scrapy/badges/version.svg\n   :target: https://anaconda.org/conda-forge/scrapy\n   :alt: Conda Version\n\n\nOverview\n========\n\nScrapy is a fast high-level web crawling and web scraping framework, used to\ncrawl websites and extract structured data from their pages. It can be used for\na wide range of purposes, from data mining to monitoring and automated testing.\n\nFor more information including a list of features check the Scrapy homepage at:\nhttps://scrapy.org\n\nRequirements\n============\n\n* Python 2.7 or Python 3.4+\n* Works on Linux, Windows, Mac OSX, BSD\n\nInstall\n=======\n\nThe quick way::\n\n    pip install scrapy\n\nFor more details see the install section in the documentation:\nhttps://docs.scrapy.org/en/latest/intro/install.html\n\nDocumentation\n=============\n\nDocumentation is available online at https://docs.scrapy.org/ and in the ``docs``\ndirectory.\n\nReleases\n========\n\nYou can find release notes at https://docs.scrapy.org/en/latest/news.html\n\nCommunity (blog, twitter, mail list, IRC)\n=========================================\n\nSee https://scrapy.org/community/\n\nContributing\n============\n\nSee https://docs.scrapy.org/en/master/contributing.html\n\nCode of Conduct\n---------------\n\nPlease note that this project is released with a Contributor Code of Conduct\n(see https://github.com/scrapy/scrapy/blob/master/CODE_OF_CONDUCT.md).\n\nBy participating in this project you agree to abide by its terms.\nPlease report unacceptable behavior to opensource@scrapinghub.com.\n\nCompanies using Scrapy\n======================\n\nSee https://scrapy.org/companies/\n\nCommercial Support\n==================\n\nSee https://scrapy.org/support/\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Scrapy-1.7.4.dist-info/RECORD",
    "content": "../../../bin/scrapy,sha256=nBpGRsKtbys-Xp4iWs4bUk8T8k7OmhWXZrXiaWhKU1Q,285\r\nScrapy-1.7.4.dist-info/AUTHORS,sha256=wBeg3cpJ5eH5Ilhbd22N1Npk17-KVy7CwXL0uRshrYM,1273\r\nScrapy-1.7.4.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nScrapy-1.7.4.dist-info/LICENSE,sha256=_TMa88y4d2u-fzF4IeXguRwqt8c0ZOd0JdUiBPe12YA,1517\r\nScrapy-1.7.4.dist-info/METADATA,sha256=Xj14ruhbCZkQFrJRpOz6IYGkmpQSzZ0UNgPoeWsjGWc,4273\r\nScrapy-1.7.4.dist-info/RECORD,,\r\nScrapy-1.7.4.dist-info/WHEEL,sha256=8zNYZbwQSXoB9IfXOjPfeNwvAsALAjffgk27FqvCWbo,110\r\nScrapy-1.7.4.dist-info/entry_points.txt,sha256=WDkmo-mkyyTA0TS6pVQtxOnkG9VXzFeotzjdI7r5DO4,51\r\nScrapy-1.7.4.dist-info/top_level.txt,sha256=daQJ2I8J6o-AN_sw03XNdbAoaiFVV2v9xkB7FxB6dao,7\r\nscrapy/VERSION,sha256=wKWmSTuO_WdX5f7Mb8zT38UTsZYzMffIryxNaFT5v2Y,6\r\nscrapy/__init__.py,sha256=GtWfEXEqceruqbQHf_nbzQ_t-Gu8menXdEaj7C6qhR8,1146\r\nscrapy/__main__.py,sha256=0pB9bs0MIwKYELCv21imsZMzlfacVRGv6q49Vnbclvw,77\r\nscrapy/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/__pycache__/__main__.cpython-36.pyc,,\r\nscrapy/__pycache__/_monkeypatches.cpython-36.pyc,,\r\nscrapy/__pycache__/cmdline.cpython-36.pyc,,\r\nscrapy/__pycache__/crawler.cpython-36.pyc,,\r\nscrapy/__pycache__/dupefilters.cpython-36.pyc,,\r\nscrapy/__pycache__/exceptions.cpython-36.pyc,,\r\nscrapy/__pycache__/exporters.cpython-36.pyc,,\r\nscrapy/__pycache__/extension.cpython-36.pyc,,\r\nscrapy/__pycache__/interfaces.cpython-36.pyc,,\r\nscrapy/__pycache__/item.cpython-36.pyc,,\r\nscrapy/__pycache__/link.cpython-36.pyc,,\r\nscrapy/__pycache__/logformatter.cpython-36.pyc,,\r\nscrapy/__pycache__/mail.cpython-36.pyc,,\r\nscrapy/__pycache__/middleware.cpython-36.pyc,,\r\nscrapy/__pycache__/pqueues.cpython-36.pyc,,\r\nscrapy/__pycache__/resolver.cpython-36.pyc,,\r\nscrapy/__pycache__/responsetypes.cpython-36.pyc,,\r\nscrapy/__pycache__/shell.cpython-36.pyc,,\r\nscrapy/__pycache__/signalmanager.cpython-36.pyc,,\r\nscrapy/__pycache__/signals.cpython-36.pyc,,\r\nscrapy/__pycache__/spiderloader.cpython-36.pyc,,\r\nscrapy/__pycache__/squeues.cpython-36.pyc,,\r\nscrapy/__pycache__/statscollectors.cpython-36.pyc,,\r\nscrapy/_monkeypatches.py,sha256=IbS8a61u3tlJ-1KA_wdrDWGSjlO0MjYA23WGmGOPU8k,976\r\nscrapy/cmdline.py,sha256=VwGYKBNrih2fpVZ7vqG5A68kdT3egvM_1dK3TjyVk7E,5486\r\nscrapy/commands/__init__.py,sha256=RcI0G7rAPZ_FRycx9TDxV_vdI5ViJqNIbQyLSzgn9WI,3532\r\nscrapy/commands/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/bench.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/check.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/crawl.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/edit.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/fetch.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/genspider.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/list.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/parse.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/runspider.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/settings.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/shell.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/startproject.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/version.cpython-36.pyc,,\r\nscrapy/commands/__pycache__/view.cpython-36.pyc,,\r\nscrapy/commands/bench.py,sha256=vm6kFt45KdJsCTNydR7BK1zki8cQfVbG9VcNVbPpIgQ,1640\r\nscrapy/commands/check.py,sha256=TaUfMEhB2IwgCGgk4i5BHGmqdtWUfm2D4FgfXpLlBPQ,3453\r\nscrapy/commands/crawl.py,sha256=u41-TBL-3Avw9CVGHNpflJKy83Jt-bPmOMpUGlL7jHQ,2625\r\nscrapy/commands/edit.py,sha256=OERVroFVEvfFoDda9xQ2Hm-0Sshq79cRV9g-UQKW1R8,1051\r\nscrapy/commands/fetch.py,sha256=m23twt8conAjm43S8nNReWcEt264O-4RqNf2IgOIDjo,2734\r\nscrapy/commands/genspider.py,sha256=7Yx4AZEGgzP1YfKAcaQkcJhR5svI7KZ92ls61sHybOg,4915\r\nscrapy/commands/list.py,sha256=L2C-B5m7rRNrENSOUNov_BZBdB_GF4ncJmaO7HVLOoQ,374\r\nscrapy/commands/parse.py,sha256=lUV4En8O_rOiQ_e0lfg4WgYq_v6yYcQ_twI4Q89w07c,10296\r\nscrapy/commands/runspider.py,sha256=UslNwaSU5kkCLO5cwprJI57t7rPO4djfak9fZCdNqgY,3668\r\nscrapy/commands/settings.py,sha256=0hbpJmWFcJTSpP7Xl67Szk03d5WJR9hJzCxKOUlctnA,1750\r\nscrapy/commands/shell.py,sha256=-RPATQEypBo6vGRZLY_76asJfH5jgXkLmQJnk1tiD3U,2720\r\nscrapy/commands/startproject.py,sha256=07eNX97Om03GDWdNATbCe6ff5kblTaVC85zPLY6Lq5E,3921\r\nscrapy/commands/version.py,sha256=4p4Aw_J-w2a5EOxwGX0QSUcuE_awKnSqLSGHZnvU2TE,1021\r\nscrapy/commands/view.py,sha256=naXH4HTkXjdSjkaevs5JuJcTbFE8o_EeHdvvfi_MWWM,557\r\nscrapy/contracts/__init__.py,sha256=r8HO_NAh0YjEszksbddFf64JFXhL32mSaC6VGZX8iBs,6017\r\nscrapy/contracts/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/contracts/__pycache__/default.cpython-36.pyc,,\r\nscrapy/contracts/default.py,sha256=NLJkh6yhxbm10R0d_m3FbhehxL7109OhORH9b_Iu3Ag,2334\r\nscrapy/core/__init__.py,sha256=qWrZeCfaO0rc0hg-MW2Famk13S-U5VcBqmJzRxEL8mc,51\r\nscrapy/core/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/core/__pycache__/engine.cpython-36.pyc,,\r\nscrapy/core/__pycache__/scheduler.cpython-36.pyc,,\r\nscrapy/core/__pycache__/scraper.cpython-36.pyc,,\r\nscrapy/core/__pycache__/spidermw.cpython-36.pyc,,\r\nscrapy/core/downloader/__init__.py,sha256=Cxa-FfH6Mz1A1Mp7PGBDpI9qWYtMea4Jt6u_DJWism4,7208\r\nscrapy/core/downloader/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/core/downloader/__pycache__/contextfactory.cpython-36.pyc,,\r\nscrapy/core/downloader/__pycache__/middleware.cpython-36.pyc,,\r\nscrapy/core/downloader/__pycache__/tls.cpython-36.pyc,,\r\nscrapy/core/downloader/__pycache__/webclient.cpython-36.pyc,,\r\nscrapy/core/downloader/contextfactory.py,sha256=Fvr6UnBKjEVfdnR2-LHHuvvURxI7jEoL9wdGbwN7Jy8,4480\r\nscrapy/core/downloader/handlers/__init__.py,sha256=Kf963BJqJgqknLvuDuuPg8rOdcbQWwNdoz8kQThN1WE,2806\r\nscrapy/core/downloader/handlers/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/core/downloader/handlers/__pycache__/datauri.cpython-36.pyc,,\r\nscrapy/core/downloader/handlers/__pycache__/file.cpython-36.pyc,,\r\nscrapy/core/downloader/handlers/__pycache__/ftp.cpython-36.pyc,,\r\nscrapy/core/downloader/handlers/__pycache__/http.cpython-36.pyc,,\r\nscrapy/core/downloader/handlers/__pycache__/http10.cpython-36.pyc,,\r\nscrapy/core/downloader/handlers/__pycache__/http11.cpython-36.pyc,,\r\nscrapy/core/downloader/handlers/__pycache__/s3.cpython-36.pyc,,\r\nscrapy/core/downloader/handlers/datauri.py,sha256=7nKvTXPCot1H8kqHYJnhj37SWgfafMi8wbCkv6k6p7s,791\r\nscrapy/core/downloader/handlers/file.py,sha256=I9YXSEhplT4-RyAjhLGeko_Uej_A5PeZew8ze32XcDY,535\r\nscrapy/core/downloader/handlers/ftp.py,sha256=8263S1q_4Av0T_dJ6YGvTIP5wkJ_hCt0sCjAgMQk_rA,4568\r\nscrapy/core/downloader/handlers/http.py,sha256=HKHUa25ANNGtrxEp3PDVhMno57K0EaWm2ZeroZPMZXQ,146\r\nscrapy/core/downloader/handlers/http10.py,sha256=BVxK2wWcmMUoSdpXf4-_3P4Ys1orVbm4dSHs_BVupIk,994\r\nscrapy/core/downloader/handlers/http11.py,sha256=12P2EfHOFXf4SMc9iO3s7bsR9NiY3oWTFw4nDQ8MznI,21150\r\nscrapy/core/downloader/handlers/s3.py,sha256=QKJqc4HtcKPlSQj6m7Ds936aPs8b_ELeEynCIi0B2tk,3870\r\nscrapy/core/downloader/middleware.py,sha256=Q_hkW8G5Dh6IV6Kcb6sOeWIZpVwYT9lbQCAAcNe8Agc,3500\r\nscrapy/core/downloader/tls.py,sha256=ckhjPgbcCBuwXGyADSK_LGE2jzpX_m11K7RniQST4Q0,3620\r\nscrapy/core/downloader/webclient.py,sha256=0I-V6vxB3dBmVsvpuKja7moGH9imAyGJ475Cu6Err6g,5796\r\nscrapy/core/engine.py,sha256=b_W67uhavv0W_eOOIOWfWXudw2inxT2-p_xwISrT_Ro,13114\r\nscrapy/core/scheduler.py,sha256=AXyJdDFk42wwcQtglrVjfDLM4sJM2Ebeiop04Ka9qR4,7220\r\nscrapy/core/scraper.py,sha256=CAXJZFV6HqHjaiT7hf7luNSZ4NmedEKIFAn1mx0PSGU,10190\r\nscrapy/core/spidermw.py,sha256=UuP_Eip2pMKB52RzoWuOMmFzcVS3ACPF63xJaHma3VA,5409\r\nscrapy/crawler.py,sha256=HQ-RTrk_XZhq-m0lY7NvG1vKJmSVxHETmpuLxuq0GVY,13435\r\nscrapy/downloadermiddlewares/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0\r\nscrapy/downloadermiddlewares/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/ajaxcrawl.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/chunked.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/cookies.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/decompression.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/defaultheaders.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/downloadtimeout.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/httpauth.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/httpcache.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/httpcompression.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/httpproxy.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/redirect.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/retry.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/robotstxt.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/stats.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/__pycache__/useragent.cpython-36.pyc,,\r\nscrapy/downloadermiddlewares/ajaxcrawl.py,sha256=wZp8pcTX4diWPRUuSfi7L80i7xa_nUDAanwDKrL6_Bc,3365\r\nscrapy/downloadermiddlewares/chunked.py,sha256=2BEDL3dYZNSrTSJEODMYRwVp_FcnxTmGYughULNafdk,773\r\nscrapy/downloadermiddlewares/cookies.py,sha256=Nv87VOoKoriX5VM98f_Xw_vir4lt8LQNTbhwTnSrFFM,3330\r\nscrapy/downloadermiddlewares/decompression.py,sha256=yueO97rb4GQxKEoON5qA6r7MfMVK6olMjfT2SSix0_I,2629\r\nscrapy/downloadermiddlewares/defaultheaders.py,sha256=2Q9ExGM7fM57k7nrv6U9NIJcl_BL9Wpaa_gRY-L_3x4,568\r\nscrapy/downloadermiddlewares/downloadtimeout.py,sha256=Pt-9xbi3obt8eEVjMD85VWcPXZc-VI0qB1uFC1pNQaY,709\r\nscrapy/downloadermiddlewares/httpauth.py,sha256=3ALLKVZmnsGIwTzbBad8R2As7Dt2GIRUPzXO-Jrso4s,893\r\nscrapy/downloadermiddlewares/httpcache.py,sha256=USiehBnBQncT_Q_MSzJdioAfFWi4raWXbqiSWuyh4Hc,4706\r\nscrapy/downloadermiddlewares/httpcompression.py,sha256=GE8MgpBzItVM3tcS2a11Avs5QS3dw87MIQMmAhl865c,2605\r\nscrapy/downloadermiddlewares/httpproxy.py,sha256=JJzzrLbmKEsXF-We2Iim4wXn-ulhekr1M69wxe1yzS0,2561\r\nscrapy/downloadermiddlewares/redirect.py,sha256=vjcwFvCewTsOHXW7GtBBPtl4r_tMjuUJCX6UBzYBhI4,4436\r\nscrapy/downloadermiddlewares/retry.py,sha256=eh6MIdgapC1ftJqYoypZDbCtDhFbjHc3Z0ImLXRp6L8,3746\r\nscrapy/downloadermiddlewares/robotstxt.py,sha256=j5fsGDc0ZINZhvaeX3kyj0DwHrKhazx7wysmGmK_L7o,4490\r\nscrapy/downloadermiddlewares/stats.py,sha256=djbnZUa9POgJbInehoJGA3NhzlXwXQeb5OqX1ngUs1I,1495\r\nscrapy/downloadermiddlewares/useragent.py,sha256=q-IAslxHg5ryft03xcyv8xzElGGP3zZTJCYPHTa8DQE,749\r\nscrapy/dupefilters.py,sha256=Hyf0ZSZ05VnmCHwL8JcRLAbY5OquxeaY7bhR-5BSODU,2302\r\nscrapy/exceptions.py,sha256=HUXqpZCoQuKnZxa-5eiK-GerV2EIqoLmYTcfANCj4ek,1620\r\nscrapy/exporters.py,sha256=xCJBbUVlF6DoBjoWN6XErnD30dtKez0hihiq5WckLeg,12541\r\nscrapy/extension.py,sha256=BAMLf4nYbRZkLwZZ6mXkKxozBWcnQFAaslTfCW-BqFw,396\r\nscrapy/extensions/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0\r\nscrapy/extensions/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/extensions/__pycache__/closespider.cpython-36.pyc,,\r\nscrapy/extensions/__pycache__/corestats.cpython-36.pyc,,\r\nscrapy/extensions/__pycache__/debug.cpython-36.pyc,,\r\nscrapy/extensions/__pycache__/feedexport.cpython-36.pyc,,\r\nscrapy/extensions/__pycache__/httpcache.cpython-36.pyc,,\r\nscrapy/extensions/__pycache__/logstats.cpython-36.pyc,,\r\nscrapy/extensions/__pycache__/memdebug.cpython-36.pyc,,\r\nscrapy/extensions/__pycache__/memusage.cpython-36.pyc,,\r\nscrapy/extensions/__pycache__/spiderstate.cpython-36.pyc,,\r\nscrapy/extensions/__pycache__/statsmailer.cpython-36.pyc,,\r\nscrapy/extensions/__pycache__/telnet.cpython-36.pyc,,\r\nscrapy/extensions/__pycache__/throttle.cpython-36.pyc,,\r\nscrapy/extensions/closespider.py,sha256=TaIUui6l9ZJfLWLQ4X6jKyW_WREQenUmZttN04qESJU,2583\r\nscrapy/extensions/corestats.py,sha256=YAdF8DoCx2HeNqjvKijEcBMhMXpNyAQ9RcOrJSheCvM,1772\r\nscrapy/extensions/debug.py,sha256=XzJwGpW8jrRrl1g6b6pr5ABoakqHv9hU_v57RasCCYw,1890\r\nscrapy/extensions/feedexport.py,sha256=vtXB9mB34Y1TcA_YCab4THBjIHNSuAQEeUUmyNq15GE,11047\r\nscrapy/extensions/httpcache.py,sha256=FaM1QYyjRaeHKYgrDnEET61S0qx7tx6_CXhET2oTWF8,16924\r\nscrapy/extensions/logstats.py,sha256=5_Ds4kqQ5kf7RbjnPpUkZAZOHNK5uvWgDOQ7PzDFiEg,1754\r\nscrapy/extensions/memdebug.py,sha256=blguRbnQhDEXDUpsOQFfaRrRwVH6skymG-vH3jYdABs,945\r\nscrapy/extensions/memusage.py,sha256=CkteP9viQ8A5Exb5niRVsz_DnuDsIZUmZ3u7PqqFOd4,4940\r\nscrapy/extensions/spiderstate.py,sha256=oitUjBiG7_2d0UsXgwLF0FUJtBBOWVoQjSxI0NZcZVo,1169\r\nscrapy/extensions/statsmailer.py,sha256=BH22wLlpo2aCOvu-RJ3sfF5HrFf-SQlw8O8_gYKnpa8,1242\r\nscrapy/extensions/telnet.py,sha256=vTJLZvs6E0aaVRbxsSJGSbqCVS-OzhVgEvhegW0lXdM,4136\r\nscrapy/extensions/throttle.py,sha256=pRZLfXJqu_wnFkHNkKdDA2Z5vKuFhgVOpJ8TtzaRtPo,3586\r\nscrapy/http/__init__.py,sha256=5VPoouMGxjXuKrX42XKZQhEISVjbkWXNJqr1ID0cuVc,602\r\nscrapy/http/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/http/__pycache__/common.cpython-36.pyc,,\r\nscrapy/http/__pycache__/cookies.cpython-36.pyc,,\r\nscrapy/http/__pycache__/headers.cpython-36.pyc,,\r\nscrapy/http/common.py,sha256=xSv2z7fQKyyAtSj98H68xIcEoZI-1W7BVDD4lWM5mFM,247\r\nscrapy/http/cookies.py,sha256=uE3Js0R-lQZztadT3MMSRrlIouOaVQ4-uTdecUni8nk,5842\r\nscrapy/http/headers.py,sha256=95O4zWPdUmXJFgy2wMBe2SjvWfXPqzFtn6x2r8N_5-o,2738\r\nscrapy/http/request/__init__.py,sha256=ruK2uoGLPlocbhhccQaFFbfYvy8-pT6s1w8Wi5K4d-w,3483\r\nscrapy/http/request/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/http/request/__pycache__/form.cpython-36.pyc,,\r\nscrapy/http/request/__pycache__/json_request.cpython-36.pyc,,\r\nscrapy/http/request/__pycache__/rpc.cpython-36.pyc,,\r\nscrapy/http/request/form.py,sha256=XJhxnWFTjD6uBloDzIgr1AEnKtFHXuwshkxipTg-cWQ,7852\r\nscrapy/http/request/json_request.py,sha256=kLnvuqkml5L-nUHRjIT9QplTPCen4pBiNKNgSqZ6MKE,1722\r\nscrapy/http/request/rpc.py,sha256=81jlEaaSR3kOw1y7j6HQMEqdjxR__7bdnlG6PlrMEug,1109\r\nscrapy/http/response/__init__.py,sha256=7RgWzEdOVmmB3SEUZl3gAbVBkGOpqa1HzVikMNsyFKI,4624\r\nscrapy/http/response/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/http/response/__pycache__/html.cpython-36.pyc,,\r\nscrapy/http/response/__pycache__/text.cpython-36.pyc,,\r\nscrapy/http/response/__pycache__/xml.cpython-36.pyc,,\r\nscrapy/http/response/html.py,sha256=OMbreqX9_9ME0fUgl1FlGay86er_-bkJQCk-L7pn_DE,299\r\nscrapy/http/response/text.py,sha256=VlBm4EI3Qqu_VF3jhhSBt1DnhOTRgpFKm37S-PoHmvU,6459\r\nscrapy/http/response/xml.py,sha256=W02SvIrRv6OMNwqP3m5fnQVRVlExrMDOYZyyoiuNxAI,296\r\nscrapy/interfaces.py,sha256=DGvtWeh-AqQstCHTzhSTW7GR46OY0Q9Vyql0LVNCR-g,558\r\nscrapy/item.py,sha256=A6K2CvBY_dGmjahs83QaVqjTl5OPSPUZrDRhxDYwWHA,2936\r\nscrapy/link.py,sha256=Z8DIzb3SKfZFoyo9ZSaLVVYjxQYo-LxVbIjLj7-RPZ8,1456\r\nscrapy/linkextractors/__init__.py,sha256=UxqtWN2RYU9M9rFS0s8CeDmj4D1KXE-whvI3S4PRUuY,4272\r\nscrapy/linkextractors/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/linkextractors/__pycache__/htmlparser.cpython-36.pyc,,\r\nscrapy/linkextractors/__pycache__/lxmlhtml.cpython-36.pyc,,\r\nscrapy/linkextractors/__pycache__/regex.cpython-36.pyc,,\r\nscrapy/linkextractors/__pycache__/sgml.cpython-36.pyc,,\r\nscrapy/linkextractors/htmlparser.py,sha256=e02ScMDkPaft4X8aPIDboo0K0L4WmSSFgjRfDiK_tOs,3098\r\nscrapy/linkextractors/lxmlhtml.py,sha256=3aLIZYqNdHYTiFlHbpNjIpcV1byScQnLTwIKnsGHYGc,5167\r\nscrapy/linkextractors/regex.py,sha256=cFNdKeznrceSOjmFG7CneFMsi4Qt3e40-8PqFSsoPxQ,1365\r\nscrapy/linkextractors/sgml.py,sha256=Yud2amivbIrv0RHFxJbKKjVfk1GuNNqdqKQUd5sK6bw,6174\r\nscrapy/loader/__init__.py,sha256=t12Ut1BxLGYYnerT9c32bm5E2HWiq6H2xU912Ehwi-w,7377\r\nscrapy/loader/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/loader/__pycache__/common.cpython-36.pyc,,\r\nscrapy/loader/__pycache__/processors.cpython-36.pyc,,\r\nscrapy/loader/common.py,sha256=w6UWdlw7XwgBY0KhHpHoCBDBSsDg6DAJpXt8jPkYjQw,467\r\nscrapy/loader/processors.py,sha256=7yeJTlOl2HYHnv7siPpQgR5ZofepLJH18ufu-Pjb3is,3514\r\nscrapy/logformatter.py,sha256=S_J90TIMaAWIL1J19dqOYyQVmaCoCf-hhu6TATr-TPQ,2669\r\nscrapy/mail.py,sha256=nhEXQT_mW_KhIHe7SHc9E64jG4Ev2ByZHAJPorTIOoE,5008\r\nscrapy/middleware.py,sha256=O5I6Y14LojjmM6b72s6xCiw2MzfcwiptK2vbmp_YJSo,2729\r\nscrapy/mime.types,sha256=7qvGIyoPSzvg9yaUpGQ8Du29MCGWi4Em_W30NUnX8qQ,20392\r\nscrapy/pipelines/__init__.py,sha256=weq8sXL8EXHmgxrP5jXwijVI7hSfDJPY60_tGRzwNJA,714\r\nscrapy/pipelines/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/pipelines/__pycache__/files.cpython-36.pyc,,\r\nscrapy/pipelines/__pycache__/images.cpython-36.pyc,,\r\nscrapy/pipelines/__pycache__/media.cpython-36.pyc,,\r\nscrapy/pipelines/files.py,sha256=FuuOXlAR1uUbw8vGbGT1eJ1QvWcnT35vX_7PA43iWKE,17220\r\nscrapy/pipelines/images.py,sha256=zYgT6LBmU7fC_9HSKb9kFT-pCxR_Qtmr6lLZk6yx0-E,6282\r\nscrapy/pipelines/media.py,sha256=5uKBskmxqUv3iEhHSXZUth9ZWVDUPeVdGaS4CpjZnxA,7927\r\nscrapy/pqueues.py,sha256=559g--Af_FuI7nqd-swG2pI6BhmL2mTxVnzk6wzzBPk,7020\r\nscrapy/resolver.py,sha256=yvEwscKAwSN_k0rQcqKwZEmOoC89FGSzSD4SLgsFN-c,1114\r\nscrapy/responsetypes.py,sha256=c-0mDpDd4AzRAWL07Njsn4YDnQeJKgaMo6SyhlSFwpo,4856\r\nscrapy/selector/__init__.py,sha256=mqtn-787YUiKAQRNKSTrfcy7msFih5dvSfLk-Pxa0aE,56\r\nscrapy/selector/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/selector/__pycache__/unified.cpython-36.pyc,,\r\nscrapy/selector/unified.py,sha256=GPGc-44XU8boqL6BW4MOKKPJLofAJJ5L46QuFMRmWbw,2751\r\nscrapy/settings/__init__.py,sha256=ph4PLiBWcMLnJa5uk52W5cslp6VfZljM29g-yyUpiNE,15983\r\nscrapy/settings/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/settings/__pycache__/default_settings.cpython-36.pyc,,\r\nscrapy/settings/__pycache__/deprecated.cpython-36.pyc,,\r\nscrapy/settings/default_settings.py,sha256=AB8f1BJ81PvT6c0ip7VvzuvWg-77rGQ1PugrM28Jk8M,8753\r\nscrapy/settings/deprecated.py,sha256=QnHMsOyZ6FDD1h92Tev15HKgOt4MkUM8K8uLgxnAwRQ,1451\r\nscrapy/shell.py,sha256=mQjwfVt_57lkBZONQBBxJBd12p6JSUfUTE05w7-7GjA,7545\r\nscrapy/signalmanager.py,sha256=S1H3hKakZt6SihB9gjucPut9d_HtfMY8QpG4H5EcN84,2475\r\nscrapy/signals.py,sha256=rhvhVrwAeiuB1dXBgnjRVybdOOKnvfyWyLnoEynOQMY,726\r\nscrapy/spiderloader.py,sha256=QDSTZ7hZXI9x5_kyN611NxnZllyDv7MsG9o9S5KDSZc,2993\r\nscrapy/spidermiddlewares/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0\r\nscrapy/spidermiddlewares/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/spidermiddlewares/__pycache__/depth.cpython-36.pyc,,\r\nscrapy/spidermiddlewares/__pycache__/httperror.cpython-36.pyc,,\r\nscrapy/spidermiddlewares/__pycache__/offsite.cpython-36.pyc,,\r\nscrapy/spidermiddlewares/__pycache__/referer.cpython-36.pyc,,\r\nscrapy/spidermiddlewares/__pycache__/urllength.cpython-36.pyc,,\r\nscrapy/spidermiddlewares/depth.py,sha256=9PKNJhjK5ifYSAQkPm7A9a0HPgdcXy1ljNrStmN8kE4,2020\r\nscrapy/spidermiddlewares/httperror.py,sha256=S--1Fj3kDjGRpWxKrKBDI_ZbfKyTnXY1442GXx3WeLc,1921\r\nscrapy/spidermiddlewares/offsite.py,sha256=oj7KXRCb1yVixLCEtQfpJ_88fS4MP_l4oUyKlD3mkyE,2563\r\nscrapy/spidermiddlewares/referer.py,sha256=-qnECc8aGubdd2MNxFH-7KqCgTFiKwuB6cnddmnRe-U,13626\r\nscrapy/spidermiddlewares/urllength.py,sha256=ZLzHSY8GlgYElyY4L2v-XzXQ7e9ukEZ22nPfRfeeZEc,1059\r\nscrapy/spiders/__init__.py,sha256=7prK-GN_kfDtgqme7-40Br-R7DFuR-EUnaxVKjnHbD4,3370\r\nscrapy/spiders/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/spiders/__pycache__/crawl.cpython-36.pyc,,\r\nscrapy/spiders/__pycache__/feed.cpython-36.pyc,,\r\nscrapy/spiders/__pycache__/init.cpython-36.pyc,,\r\nscrapy/spiders/__pycache__/sitemap.cpython-36.pyc,,\r\nscrapy/spiders/crawl.py,sha256=6-5o4H2gcpTCQ51kOMIAMedKuQ0oWlncIt-Zi0fYkZU,4382\r\nscrapy/spiders/feed.py,sha256=uglx45zWWSCkHuMPxn-X_rBKc7qo3QU8Rz1gib4dyDo,5441\r\nscrapy/spiders/init.py,sha256=6moM5Uc_JHkB3ktCiEALBGukUIgBGKcbvGrqaZTVP6U,1354\r\nscrapy/spiders/sitemap.py,sha256=WOFv_p6cldLxaj4RDpdMYYXxqPFpG8aGiNp_3y_7NHs,3579\r\nscrapy/squeues.py,sha256=dTxBInUZUvE-jODzXZsA3ZGogeH43MGdU_IzdqOp1Ok,1301\r\nscrapy/statscollectors.py,sha256=lPGG3O2pifgY0hkPc47_BP1RxLpsC-4jLNG4BaxCC8U,2129\r\nscrapy/templates/project/module/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0\r\nscrapy/templates/project/module/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/templates/project/module/items.py.tmpl,sha256=PhB4ktMFPN6sxgq7NvBBc-jmNUl9IqIufiRigI86LJg,295\r\nscrapy/templates/project/module/middlewares.py.tmpl,sha256=KiJuaxDkJ2Ec7YlEZ1kare3_P7hH6Kk4il0gUDU0bFo,3613\r\nscrapy/templates/project/module/pipelines.py.tmpl,sha256=3d07xChH5DWvqHOhxnqFvwbNwVTIkHQKl5KwO-s8W1M,296\r\nscrapy/templates/project/module/settings.py.tmpl,sha256=Yl1ax5pQbCQb1lBf1VePOL65SFtWNPkzTqKD9bNTZUU,3162\r\nscrapy/templates/project/module/spiders/__init__.py,sha256=ULwecZkx3_NTphkz7y_qiazBeUoHFnCCWnKSjoDCZj0,161\r\nscrapy/templates/project/module/spiders/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/templates/project/scrapy.cfg,sha256=rRXe96NnAjpS8_2AtC_flgy7uleqtduLmPd-K720IG4,273\r\nscrapy/templates/spiders/basic.tmpl,sha256=DbIobzgnP0SSwCUFdpvF79zcViqO7Hp3MKlrSEYlriI,208\r\nscrapy/templates/spiders/crawl.tmpl,sha256=-X_oA4pShxJtcC6BsXXp3HljYeJDknBKG1uAueFmdHk,657\r\nscrapy/templates/spiders/csvfeed.tmpl,sha256=uxN0675_-ntfDkK9OBiu0B7x7dSXmxYWj5G5fV-0vIo,571\r\nscrapy/templates/spiders/xmlfeed.tmpl,sha256=cStRh3fgz_48X5B9tHtlqsyYbqfvBYC4cOTmzZx8nds,565\r\nscrapy/utils/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0\r\nscrapy/utils/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/benchserver.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/boto.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/conf.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/console.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/datatypes.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/decorators.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/defer.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/deprecate.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/display.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/engine.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/ftp.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/gz.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/http.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/httpobj.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/iterators.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/job.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/log.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/markup.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/misc.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/multipart.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/ossignal.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/project.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/python.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/reactor.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/reqser.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/request.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/response.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/serialize.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/signal.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/sitemap.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/spider.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/template.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/test.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/testproc.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/testsite.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/trackref.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/url.cpython-36.pyc,,\r\nscrapy/utils/__pycache__/versions.cpython-36.pyc,,\r\nscrapy/utils/benchserver.py,sha256=WVbn3Qq78Ul7P8LbBPNxBp5-dh7h87STziVFnEVe044,1332\r\nscrapy/utils/boto.py,sha256=XOuDGZFSFu52k-zT8HR7Vmza6RevrrckvXhPPyyt45M,494\r\nscrapy/utils/conf.py,sha256=sDQtbM-G1vUhUy4ye3nY4g6pdHw6cv7r-xC3_TaIzlI,4102\r\nscrapy/utils/console.py,sha256=o_8iJo5CarNN5NgSEMnxkTTRScmsP4-iULNTMsr1ZPA,3403\r\nscrapy/utils/datatypes.py,sha256=M9Hb_GIy2E7Zi79acxIePD8WP_ns0gI4GGzlrj_KXhU,9823\r\nscrapy/utils/decorators.py,sha256=OR-tu3Xh2JW4tQsPFw18K7BdlY4xU64ukpqTFBQ8t0k,1273\r\nscrapy/utils/defer.py,sha256=k8gTXwubNeHa-dJ9kF910d0NVIxOIqNdrIMg7_wjGf4,3576\r\nscrapy/utils/deprecate.py,sha256=e9JdhwgIg4ygfYtxBMXi_Vw7oy69CHn1nHs7Mkcd3ho,6710\r\nscrapy/utils/display.py,sha256=e1fwP0uIEZyEmrJtYRynwKfrAfVPa58sh_NS1q3s7aM,699\r\nscrapy/utils/engine.py,sha256=DdlrtdxTAAT-lnC325WfGRrjJVfYYs_EIy2fXZl0p5w,1376\r\nscrapy/utils/ftp.py,sha256=Nt5QYvnBC1fs2RTm3dGfr5v1JeuXebS9Ass7bqjY6ds,531\r\nscrapy/utils/gz.py,sha256=3Hn1C_ck0nzowXo4NWau67ecp3GAySxnWOQ5IbFQn2U,2200\r\nscrapy/utils/http.py,sha256=lNaFKDZxXqbA-5kkCn_zMYp4s3KkSW-Q1Q8OC6uy8lw,905\r\nscrapy/utils/httpobj.py,sha256=zrs-XKmo12LCXqSzQUbkp17tx8CzjiM_a8K14M0805s,516\r\nscrapy/utils/iterators.py,sha256=KlR9nWVdWZ61YWwtCeY8KkMEp5VrM2IgPb7VUmE0l40,5025\r\nscrapy/utils/job.py,sha256=9aMdjUE8yXj_TUbTVzTVmyXpmT8WSSuytNJNM1L7Tx8,148\r\nscrapy/utils/log.py,sha256=oSB5QV5etHOBwpzF0rRUJwRcmkciWW7Fkh0t18UpyTU,6558\r\nscrapy/utils/markup.py,sha256=PTuqniHxdLO9IgjgdJA9_1P1iUR6itySyN5VHzdh4ss,400\r\nscrapy/utils/misc.py,sha256=loIAdMP21eLM26wbKNDg_8TgTyOaek1iC9E1MvWV4mg,5030\r\nscrapy/utils/multipart.py,sha256=sNbnG1slp7cNnI7ZJBFRMWeQodlPFTR_Hr8ZG2-vhjY,488\r\nscrapy/utils/ossignal.py,sha256=kxrCur_rPYVipHIBlwWHUScEFgULrC3UNi7IHIox_Kg,994\r\nscrapy/utils/project.py,sha256=ufFEQ5QSJ2uG9DEakWSdNOVC1R86NsG-pf8LstH65VI,2590\r\nscrapy/utils/python.py,sha256=m1ZocXLJHnxbhWHUw-ut1Rif8LNqWFSaWZCXwagaXhc,11805\r\nscrapy/utils/reactor.py,sha256=LkmKoT-YLTmIvCrBsvuPR_1Frkmj_0HAeOays4F9ztQ,1360\r\nscrapy/utils/reqser.py,sha256=E1bvBMrP_lKufCXUp_pbRfZtdTmps7lq0QUaPHU9LlM,3213\r\nscrapy/utils/request.py,sha256=Psnh6DX1vPjCIxVrYf19Zlrqh0FmH_xGj45qdeg9dGM,3459\r\nscrapy/utils/response.py,sha256=lI_NJ-oYJOQuWTXHh61Bmu0eY9qh6jVqAepI7e5A9-Y,2665\r\nscrapy/utils/serialize.py,sha256=J3T9E05j8HXqoqHuX_ZWSSqDes07iirCRl_BznHeyxg,1201\r\nscrapy/utils/signal.py,sha256=b4fTZbiqVSxZazdGmLLBirKHHW0U7e-7XqbWHd_5a04,2969\r\nscrapy/utils/sitemap.py,sha256=PSi3joL-4nVbBwhOqasDnOFcCQP8VA-BTtvEqX134as,1518\r\nscrapy/utils/spider.py,sha256=VdMMl1EhmN65nA3tC-Z4uKn-wKfBaGApsbJjGZZnUJw,1911\r\nscrapy/utils/template.py,sha256=JNCXL8NT0gGFgEK4aC0oCeUQlKOWzisdjdGNvnPJ4Q0,816\r\nscrapy/utils/test.py,sha256=fhMskcoxNFyNeSS9EZ1cCt_StVNgyr0UmRhUxdIW-cw,3089\r\nscrapy/utils/testproc.py,sha256=xDcuLRPWChiTL7L7wwYOT9XZjdzQUu0tDsMKyFSXzwc,1508\r\nscrapy/utils/testsite.py,sha256=yDS8GwhSKKBuNLCswrrmD2GfsB827sTlKfuQ8iorxao,1562\r\nscrapy/utils/trackref.py,sha256=rg82Iib9fkjqkfmFdE507VVxcOBfycG_FZZ9Hldyz08,2081\r\nscrapy/utils/url.py,sha256=5sWMcSbQQBe53pa2v5JOPMSq2cQmzsI09OEvQdCg0W8,5119\r\nscrapy/utils/versions.py,sha256=eMWzL4F0jIWnSxlSd-hysa9LoCSJjc9cwirxsdlWZIg,1419\r\nscrapy/xlib/__init__.py,sha256=CbHNJHO8-CRSs6dP3WIWf1u4ruo2KyTrio-GBpxr45Y,92\r\nscrapy/xlib/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy/xlib/__pycache__/pydispatch.cpython-36.pyc,,\r\nscrapy/xlib/__pycache__/tx.cpython-36.pyc,,\r\nscrapy/xlib/pydispatch.py,sha256=Z4y2vxQ5k4SrDfLfjJsR2BUGNY0Pghn9lmVqpJEXyRo,629\r\nscrapy/xlib/tx.py,sha256=v08NnjBxl_kdLlCVSLEJcyEti-DHhw2Sklai2eCZhbY,749\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Scrapy-1.7.4.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.33.6)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Scrapy-1.7.4.dist-info/entry_points.txt",
    "content": "[console_scripts]\nscrapy = scrapy.cmdline:execute\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Scrapy-1.7.4.dist-info/top_level.txt",
    "content": "scrapy\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Twisted-19.7.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Twisted-19.7.0.dist-info/LICENSE",
    "content": "Copyright (c) 2001-2019\nAllen Short\nAmber Hawkie Brown\nAndrew Bennetts\nAndy Gayton\nAntoine Pitrou\nApple Computer, Inc.\nAshwini Oruganti\nBenjamin Bruheim\nBob Ippolito\nCanonical Limited\nChristopher Armstrong\nCiena Corporation\nDavid Reid\nDivmod Inc.\nDonovan Preston\nEric Mangold\nEyal Lotem\nGoogle Inc.\nHybrid Logic Ltd.\nHynek Schlawack\nItamar Turner-Trauring\nJames Knight\nJason A. Mobarak\nJean-Paul Calderone\nJessica McKellar\nJonathan D. Simms\nJonathan Jacobs\nJonathan Lange\nJulian Berman\nJürgen Hermann\nKevin Horn\nKevin Turner\nLaurens Van Houtven\nMary Gardiner\nMassachusetts Institute of Technology\nMatthew Lefkowitz\nMoshe Zadka\nPaul Swartz\nPavel Pergamenshchik\nRackspace, US Inc.\nRalph Meijer\nRichard Wall\nSean Riley\nSoftware Freedom Conservancy\nTavendo GmbH\nThijs Triemstra\nThomas Herve\nTimothy Allen\nTom Most\nTom Prince\nTravis B. Hartwell\n\nand others that have contributed code to the public domain.\n\nPermission is hereby granted, free of charge, to any person obtaining\na copy of this software and associated documentation files (the\n\"Software\"), to deal in the Software without restriction, including\nwithout limitation the rights to use, copy, modify, merge, publish,\ndistribute, sublicense, and/or sell copies of the Software, and to\npermit persons to whom the Software is furnished to do so, subject to\nthe following conditions:\n\nThe above copyright notice and this permission notice shall be\nincluded in all copies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND,\nEXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND\nNONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE\nLIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION\nOF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION\nWITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Twisted-19.7.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: Twisted\nVersion: 19.7.0\nSummary: An asynchronous networking framework written in Python\nHome-page: https://twistedmatrix.com/\nAuthor: Twisted Matrix Laboratories\nAuthor-email: twisted-python@twistedmatrix.com\nMaintainer: Glyph Lefkowitz\nMaintainer-email: glyph@twistedmatrix.com\nLicense: MIT\nProject-URL: Documentation, https://twistedmatrix.com/documents/current/\nProject-URL: Source, https://github.com/twisted/twisted\nProject-URL: Issues, https://twistedmatrix.com/trac/report\nPlatform: UNKNOWN\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nDescription-Content-Type: text/x-rst\nRequires-Dist: zope.interface (>=4.4.2)\nRequires-Dist: constantly (>=15.1)\nRequires-Dist: incremental (>=16.10.1)\nRequires-Dist: Automat (>=0.3.0)\nRequires-Dist: hyperlink (>=17.1.1)\nRequires-Dist: PyHamcrest (>=1.9.0)\nRequires-Dist: attrs (>=17.4.0)\nProvides-Extra: all_non_platform\nRequires-Dist: pyopenssl (>=16.0.0) ; extra == 'all_non_platform'\nRequires-Dist: service-identity (>=18.1.0) ; extra == 'all_non_platform'\nRequires-Dist: idna (!=2.3,>=0.6) ; extra == 'all_non_platform'\nRequires-Dist: pyasn1 ; extra == 'all_non_platform'\nRequires-Dist: cryptography (>=2.5) ; extra == 'all_non_platform'\nRequires-Dist: appdirs (>=1.4.0) ; extra == 'all_non_platform'\nRequires-Dist: bcrypt (>=3.0.0) ; extra == 'all_non_platform'\nRequires-Dist: soappy ; extra == 'all_non_platform'\nRequires-Dist: pyserial (>=3.0) ; extra == 'all_non_platform'\nRequires-Dist: h2 (<4.0,>=3.0) ; extra == 'all_non_platform'\nRequires-Dist: priority (<2.0,>=1.1.0) ; extra == 'all_non_platform'\nProvides-Extra: conch\nRequires-Dist: pyasn1 ; extra == 'conch'\nRequires-Dist: cryptography (>=2.5) ; extra == 'conch'\nRequires-Dist: appdirs (>=1.4.0) ; extra == 'conch'\nRequires-Dist: bcrypt (>=3.0.0) ; extra == 'conch'\nProvides-Extra: dev\nRequires-Dist: pyflakes (>=1.0.0) ; extra == 'dev'\nRequires-Dist: twisted-dev-tools (>=0.0.2) ; extra == 'dev'\nRequires-Dist: python-subunit ; extra == 'dev'\nRequires-Dist: sphinx (>=1.3.1) ; extra == 'dev'\nRequires-Dist: towncrier (>=17.4.0) ; extra == 'dev'\nProvides-Extra: http2\nRequires-Dist: h2 (<4.0,>=3.0) ; extra == 'http2'\nRequires-Dist: priority (<2.0,>=1.1.0) ; extra == 'http2'\nProvides-Extra: macos_platform\nRequires-Dist: pyobjc-core ; extra == 'macos_platform'\nRequires-Dist: pyobjc-framework-CFNetwork ; extra == 'macos_platform'\nRequires-Dist: pyobjc-framework-Cocoa ; extra == 'macos_platform'\nRequires-Dist: pyopenssl (>=16.0.0) ; extra == 'macos_platform'\nRequires-Dist: service-identity (>=18.1.0) ; extra == 'macos_platform'\nRequires-Dist: idna (!=2.3,>=0.6) ; extra == 'macos_platform'\nRequires-Dist: pyasn1 ; extra == 'macos_platform'\nRequires-Dist: cryptography (>=2.5) ; extra == 'macos_platform'\nRequires-Dist: appdirs (>=1.4.0) ; extra == 'macos_platform'\nRequires-Dist: bcrypt (>=3.0.0) ; extra == 'macos_platform'\nRequires-Dist: soappy ; extra == 'macos_platform'\nRequires-Dist: pyserial (>=3.0) ; extra == 'macos_platform'\nRequires-Dist: h2 (<4.0,>=3.0) ; extra == 'macos_platform'\nRequires-Dist: priority (<2.0,>=1.1.0) ; extra == 'macos_platform'\nProvides-Extra: osx_platform\nRequires-Dist: pyobjc-core ; extra == 'osx_platform'\nRequires-Dist: pyobjc-framework-CFNetwork ; extra == 'osx_platform'\nRequires-Dist: pyobjc-framework-Cocoa ; extra == 'osx_platform'\nRequires-Dist: pyopenssl (>=16.0.0) ; extra == 'osx_platform'\nRequires-Dist: service-identity (>=18.1.0) ; extra == 'osx_platform'\nRequires-Dist: idna (!=2.3,>=0.6) ; extra == 'osx_platform'\nRequires-Dist: pyasn1 ; extra == 'osx_platform'\nRequires-Dist: cryptography (>=2.5) ; extra == 'osx_platform'\nRequires-Dist: appdirs (>=1.4.0) ; extra == 'osx_platform'\nRequires-Dist: bcrypt (>=3.0.0) ; extra == 'osx_platform'\nRequires-Dist: soappy ; extra == 'osx_platform'\nRequires-Dist: pyserial (>=3.0) ; extra == 'osx_platform'\nRequires-Dist: h2 (<4.0,>=3.0) ; extra == 'osx_platform'\nRequires-Dist: priority (<2.0,>=1.1.0) ; extra == 'osx_platform'\nProvides-Extra: serial\nRequires-Dist: pyserial (>=3.0) ; extra == 'serial'\nProvides-Extra: soap\nRequires-Dist: soappy ; extra == 'soap'\nProvides-Extra: tls\nRequires-Dist: pyopenssl (>=16.0.0) ; extra == 'tls'\nRequires-Dist: service-identity (>=18.1.0) ; extra == 'tls'\nRequires-Dist: idna (!=2.3,>=0.6) ; extra == 'tls'\nProvides-Extra: windows_platform\nRequires-Dist: pywin32 ; extra == 'windows_platform'\nRequires-Dist: pyopenssl (>=16.0.0) ; extra == 'windows_platform'\nRequires-Dist: service-identity (>=18.1.0) ; extra == 'windows_platform'\nRequires-Dist: idna (!=2.3,>=0.6) ; extra == 'windows_platform'\nRequires-Dist: pyasn1 ; extra == 'windows_platform'\nRequires-Dist: cryptography (>=2.5) ; extra == 'windows_platform'\nRequires-Dist: appdirs (>=1.4.0) ; extra == 'windows_platform'\nRequires-Dist: bcrypt (>=3.0.0) ; extra == 'windows_platform'\nRequires-Dist: soappy ; extra == 'windows_platform'\nRequires-Dist: pyserial (>=3.0) ; extra == 'windows_platform'\nRequires-Dist: h2 (<4.0,>=3.0) ; extra == 'windows_platform'\nRequires-Dist: priority (<2.0,>=1.1.0) ; extra == 'windows_platform'\n\nTwisted\n=======\n\n|pypi|_\n|travis|_\n|circleci|_\n\nFor information on what's new in Twisted 19.2.0, see the `NEWS <https://github.com/twisted/twisted/blob/trunk/NEWS.rst>`_ file that comes with the distribution.\n\n\nWhat is this?\n-------------\n\nTwisted is an event-based framework for internet applications, supporting Python 2.7 and Python 3.5+.\nIt includes modules for many different purposes, including the following:\n\n- ``twisted.web``: HTTP clients and servers, HTML templating, and a WSGI server\n- ``twisted.conch``: SSHv2 and Telnet clients and servers and terminal emulators\n- ``twisted.words``: Clients and servers for IRC, XMPP, and other IM protocols\n- ``twisted.mail``: IMAPv4, POP3, SMTP clients and servers\n- ``twisted.positioning``: Tools for communicating with NMEA-compatible GPS receivers\n- ``twisted.names``: DNS client and tools for making your own DNS servers\n- ``twisted.trial``: A unit testing framework that integrates well with Twisted-based code.\n\nTwisted supports all major system event loops -- ``select`` (all platforms), ``poll`` (most POSIX platforms), ``epoll`` (Linux), ``kqueue`` (FreeBSD, macOS), IOCP (Windows), and various GUI event loops (GTK+2/3, Qt, wxWidgets).\nThird-party reactors can plug into Twisted, and provide support for additional event loops.\n\n\nInstalling\n----------\n\nTo install the latest version of Twisted using pip::\n\n  $ pip install twisted\n\nAdditional instructions for installing this software are in `the installation instructions <https://github.com/twisted/twisted/blob/trunk/INSTALL.rst>`_.\n\n\nDocumentation and Support\n-------------------------\n\nTwisted's documentation is available from the `Twisted Matrix website <https://twistedmatrix.com/documents/current/>`_.\nThis documentation contains how-tos, code examples, and an API reference.\n\nHelp is also available on the `Twisted mailing list <https://twistedmatrix.com/cgi-bin/mailman/listinfo/twisted-python>`_.\n\nThere is also a pair of very lively IRC channels, ``#twisted`` (for general Twisted questions) and ``#twisted.web`` (for Twisted Web), on ``chat.freenode.net``.\n\n\nUnit Tests\n----------\n\nTwisted has a comprehensive test suite, which can be run by ``tox``::\n\n  $ tox -l            # to view all test environments\n  $ tox -e py27-tests # to run the tests for Python 2.7\n  $ tox -e py35-tests # to run the tests for Python 3.5\n\n\nYou can test running the test suite under the different reactors with the ``TWISTED_REACTOR`` environment variable::\n\n  $ env TWISTED_REACTOR=epoll tox -e py27-tests\n\n\nSome of these tests may fail if you:\n\n* don't have the dependencies required for a particular subsystem installed,\n* have a firewall blocking some ports (or things like Multicast, which Linux NAT has shown itself to do), or\n* run them as root.\n\n\nCopyright\n---------\n\nAll of the code in this distribution is Copyright (c) 2001-2019 Twisted Matrix Laboratories.\n\nTwisted is made available under the MIT license.\nThe included `LICENSE <https://github.com/twisted/twisted/blob/trunk/LICENSE>`_ file describes this in detail.\n\n\nWarranty\n--------\n\n  THIS SOFTWARE IS PROVIDED \"AS IS\" WITHOUT WARRANTY OF ANY KIND, EITHER\n  EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES\n  OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.  THE ENTIRE RISK AS\n  TO THE USE OF THIS SOFTWARE IS WITH YOU.\n\n  IN NO EVENT WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY\n  AND/OR REDISTRIBUTE THE LIBRARY, BE LIABLE TO YOU FOR ANY DAMAGES, EVEN IF\n  SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH\n  DAMAGES.\n\nAgain, see the included `LICENSE <https://github.com/twisted/twisted/blob/trunk/LICENSE>`_ file for specific legal details.\n\n\n.. |pypi| image:: http://img.shields.io/pypi/v/twisted.svg\n.. _pypi: https://pypi.python.org/pypi/twisted\n\n.. |travis| image:: https://travis-ci.org/twisted/twisted.svg?branch=trunk\n.. _travis: https://travis-ci.org/twisted/twisted\n\n.. |circleci| image:: https://circleci.com/gh/twisted/twisted.svg?style=svg\n.. _circleci: https://circleci.com/gh/twisted/twisted\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Twisted-19.7.0.dist-info/RECORD",
    "content": "../../../bin/cftp,sha256=uQ-4stYf8E120-asLychp7hW1VjLJxFL_6HNQI0aHdo,289\r\n../../../bin/ckeygen,sha256=4GXdm-6Esn7pGzUxOvnNH_g6nl_jIsNazaBBzD_dkM4,292\r\n../../../bin/conch,sha256=_8hQIr6ODtna6muwkpUnV333R-PyKSOVPjW0PORO3Ho,290\r\n../../../bin/mailmail,sha256=QXut2P7LTlyKMFD6eM8uDlaXlUwnm523mrKmxiYgd4Y,292\r\n../../../bin/pyhtmlizer,sha256=fcX6JmFsYRGMDV9hyV1PULC6x3vJhi3fNW8hwlZVLdg,287\r\n../../../bin/tkconch,sha256=m7e0vrKcr_kYHru2A8qfTV-LynkDFJIc4uMZGh8yEMM,292\r\n../../../bin/trial,sha256=m3QRoAfu-MXf3yMnwDsRzEayV-GGnxNl5J9Si3psuX4,284\r\n../../../bin/twist,sha256=kJTyCYIA1VJw8qmtYnumNRt2eOljm68iOeauiljwibY,304\r\n../../../bin/twistd,sha256=RnXH8pBHK-V3QlTXoxihOlZjhkudgOV1hJr174Z7Sw0,285\r\nTwisted-19.7.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nTwisted-19.7.0.dist-info/LICENSE,sha256=hbeYQTuohbBswbke_oV6OfaUBxwpsE6A0j6ibuJx1hM,1926\r\nTwisted-19.7.0.dist-info/METADATA,sha256=9lvJRkxJOpFZ8fFA81XkDN6jkCljIvfEvxHUTrWRyFo,9321\r\nTwisted-19.7.0.dist-info/RECORD,,\r\nTwisted-19.7.0.dist-info/WHEEL,sha256=q6ZS0x11G9XscKQI--PbS172VpPpBOOoLI4QlxtsUa0,109\r\nTwisted-19.7.0.dist-info/entry_points.txt,sha256=UK8U0KNTSAegCW9a4j4bDwbOO5c1579QKqXzwsPPcnI,394\r\nTwisted-19.7.0.dist-info/top_level.txt,sha256=e9eVTH2N7T_qnhIPUQhDQilKWgnW7rTHCvHGyd7xp0k,8\r\ntwisted/__init__.py,sha256=A7hcrXmwPGeAGHDPU_wyOTjgqRHAPAuLVvMI9E6xblg,256\r\ntwisted/__main__.py,sha256=-IXh5Xk046Kf8k4NqwciSb4K6q4X4RnKEMwsrbrsn9g,448\r\ntwisted/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/__pycache__/__main__.cpython-36.pyc,,\r\ntwisted/__pycache__/_version.cpython-36.pyc,,\r\ntwisted/__pycache__/copyright.cpython-36.pyc,,\r\ntwisted/__pycache__/plugin.cpython-36.pyc,,\r\ntwisted/_threads/__init__.py,sha256=XUQc4vy6dlY3VYcNQZEGPOThfz6cB6x9-ySpiv3eW8w,570\r\ntwisted/_threads/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/_threads/__pycache__/_convenience.cpython-36.pyc,,\r\ntwisted/_threads/__pycache__/_ithreads.cpython-36.pyc,,\r\ntwisted/_threads/__pycache__/_memory.cpython-36.pyc,,\r\ntwisted/_threads/__pycache__/_pool.cpython-36.pyc,,\r\ntwisted/_threads/__pycache__/_team.cpython-36.pyc,,\r\ntwisted/_threads/__pycache__/_threadworker.cpython-36.pyc,,\r\ntwisted/_threads/_convenience.py,sha256=bME26wNYCSEtoVqCOSqqwMyEhgU9_UXzFu4r-lK9fsI,969\r\ntwisted/_threads/_ithreads.py,sha256=phOeuVsKw3K-BPex6ZutkvNyij8nrYZAmhVgi5wERUo,1810\r\ntwisted/_threads/_memory.py,sha256=8V-KVBG6ngic_XNenwGAslQWsNyoeRhn4Hd5vv4ByoY,1666\r\ntwisted/_threads/_pool.py,sha256=_Nw_ltHAfF24Vy72CoxPXiNkUAfRUlLD3PFiavzy00E,2399\r\ntwisted/_threads/_team.py,sha256=60gJbzlRrx6Ga8Qse7Klpsv5Sqc4a1DYGh52Qt1GJVA,7259\r\ntwisted/_threads/_threadworker.py,sha256=GnzPGY_4nz9_aohIK4l_UnEPEg-o-0u4jCmR8emV4AE,3376\r\ntwisted/_threads/test/__init__.py,sha256=-tNWrOXAaGo9x-k49W4kk9ol44DaBbLFeBSZaHxtzKk,226\r\ntwisted/_threads/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/_threads/test/__pycache__/test_convenience.cpython-36.pyc,,\r\ntwisted/_threads/test/__pycache__/test_memory.cpython-36.pyc,,\r\ntwisted/_threads/test/__pycache__/test_team.cpython-36.pyc,,\r\ntwisted/_threads/test/__pycache__/test_threadworker.cpython-36.pyc,,\r\ntwisted/_threads/test/test_convenience.py,sha256=-088jkN0O_GroTglswcmnzz9iS7vUdLvOwN0nwMcJuE,1442\r\ntwisted/_threads/test/test_memory.py,sha256=H3pafUk-1CJL3kE7JM_zQKd0Dte6twFJqFD4j3ntkNY,2148\r\ntwisted/_threads/test/test_team.py,sha256=zY3BDEA5TrQgL5ka1WHOFC4A-6NNA0QU2Th8FBgi5G0,9534\r\ntwisted/_threads/test/test_threadworker.py,sha256=O5QpeGz0vLPApZV1jmnq29jfhG9y8MV8ygnh_4A_YXw,8093\r\ntwisted/_version.py,sha256=2gUxEnRoE1XvGCGzKAozLESbm4b5o6Aaa8H9hqtyLFk,260\r\ntwisted/application/__init__.py,sha256=qAl6aEqUMpJJXs69xa8mxSVpiE4E9MzMkKWX26xo8MM,129\r\ntwisted/application/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/application/__pycache__/app.cpython-36.pyc,,\r\ntwisted/application/__pycache__/internet.cpython-36.pyc,,\r\ntwisted/application/__pycache__/reactors.cpython-36.pyc,,\r\ntwisted/application/__pycache__/service.cpython-36.pyc,,\r\ntwisted/application/__pycache__/strports.cpython-36.pyc,,\r\ntwisted/application/app.py,sha256=bILSMk-3-7MLqoZf7OpbbXwZpxu9KSPAeC52WjR26Hg,23465\r\ntwisted/application/internet.py,sha256=EzTydNA6GYP6bPhkw1Bs4u_hxmGmd-RE_oQwpZszXSg,36974\r\ntwisted/application/reactors.py,sha256=p0LAxCG6gUX4L5k07rIaDhwXZu22pyxaELpoD7USe1M,2169\r\ntwisted/application/runner/__init__.py,sha256=oAOyWGGBaaPSeeHS_vHk2pvip3_-nPVZlPvIf4EkKh4,185\r\ntwisted/application/runner/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/application/runner/__pycache__/_exit.cpython-36.pyc,,\r\ntwisted/application/runner/__pycache__/_pidfile.cpython-36.pyc,,\r\ntwisted/application/runner/__pycache__/_runner.cpython-36.pyc,,\r\ntwisted/application/runner/_exit.py,sha256=injGMM6zHAa488X2m7VE_ImIKxRHR76aXIuGftbTZyQ,3984\r\ntwisted/application/runner/_pidfile.py,sha256=7PJHb2IBI5nz6280u_LpE1yoR0SbbojjJBPvIJHlECQ,6995\r\ntwisted/application/runner/_runner.py,sha256=A2wlGmCgxoWMn48mK-AkN74MeODYbfvhzGU6nxCngK0,5765\r\ntwisted/application/runner/test/__init__.py,sha256=NAk9flgxX4siFhfJm6zpSt9odTHr3mmjQeuq-SOBobo,180\r\ntwisted/application/runner/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/application/runner/test/__pycache__/test_exit.cpython-36.pyc,,\r\ntwisted/application/runner/test/__pycache__/test_pidfile.cpython-36.pyc,,\r\ntwisted/application/runner/test/__pycache__/test_runner.cpython-36.pyc,,\r\ntwisted/application/runner/test/test_exit.py,sha256=M3WZICqMykDZg-02VMo2p8QIuyoONkmjMDFKFfIaKMw,2489\r\ntwisted/application/runner/test/test_pidfile.py,sha256=7VHnxmHJJk-_w-77Egk6zm2u-LoN5Sc-DX_Sif-7yHo,12984\r\ntwisted/application/runner/test/test_runner.py,sha256=RZkx-HqEe0lqyTN3QX6t7y7kUbsChAfRo4R5HWKf0s0,13293\r\ntwisted/application/service.py,sha256=7JGdq40MJ_8lgOmEqu_vR7oQHaiXE2H_51hzpneTSJA,12021\r\ntwisted/application/strports.py,sha256=n8kh_673Beui-gQQu5xj7lYxgNyzXWg4IzNNO39UIjk,2233\r\ntwisted/application/test/__init__.py,sha256=QJh3C_0yH0jDm6ViNbaoefp_no7sv7FyuV32ZYWE75s,124\r\ntwisted/application/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/application/test/__pycache__/test_internet.cpython-36.pyc,,\r\ntwisted/application/test/__pycache__/test_service.cpython-36.pyc,,\r\ntwisted/application/test/test_internet.py,sha256=bBcMqDsAoXDy88xg5X1nkm8tMruEYBtVmkCkylyeyoI,42340\r\ntwisted/application/test/test_service.py,sha256=YPdTXv2BdRFUOyJdhKO8cPtdplxOmwi1fQjcft_Kw4M,5091\r\ntwisted/application/twist/__init__.py,sha256=YPzoFOyJSICe6QB4XZXFxNyJWsRru-RRvYizhrN9jJE,166\r\ntwisted/application/twist/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/application/twist/__pycache__/_options.cpython-36.pyc,,\r\ntwisted/application/twist/__pycache__/_twist.cpython-36.pyc,,\r\ntwisted/application/twist/_options.py,sha256=7SUx3kQpZbmXEUusRl4tJrGqv0s78GHJGjSOcWk5088,5719\r\ntwisted/application/twist/_twist.py,sha256=hmdSn31p0CPsBupdKoaa_RvTShH4gwigOyuYsJns3to,3499\r\ntwisted/application/twist/test/__init__.py,sha256=B0KIIGDdfaLWhGhs1WBlDQoABIMxwJBl5tSEQmIkoBo,178\r\ntwisted/application/twist/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/application/twist/test/__pycache__/test_options.cpython-36.pyc,,\r\ntwisted/application/twist/test/__pycache__/test_twist.cpython-36.pyc,,\r\ntwisted/application/twist/test/test_options.py,sha256=XP8TpbptQST3zFChhBxGJ8SKqUdloxYhEPrUznFHPMc,10906\r\ntwisted/application/twist/test/test_twist.py,sha256=SkVSPN9RcaXZMBVzx3QqnBf2Ljquvjcldb4kZo_DzqI,7618\r\ntwisted/conch/__init__.py,sha256=ePuf1Y1dXhse4EBuyIQUPsHFurM3l28cenQc9R3fL3A,198\r\ntwisted/conch/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/avatar.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/checkers.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/endpoints.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/error.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/interfaces.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/ls.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/manhole.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/manhole_ssh.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/manhole_tap.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/mixin.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/recvline.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/stdio.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/tap.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/telnet.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/ttymodes.cpython-36.pyc,,\r\ntwisted/conch/__pycache__/unix.cpython-36.pyc,,\r\ntwisted/conch/avatar.py,sha256=cJqlSmAbhtnxxsBFLvQ6-kRvbnDSuf4FvnrpvZqEo_Y,1438\r\ntwisted/conch/checkers.py,sha256=UPSJAg4CXSF8Sr1e6CvPYyOcrDJjCr9LLpj3kFisD_M,19742\r\ntwisted/conch/client/__init__.py,sha256=vbi0H87oC9ZMg2pFDUwAa-W7W7XDnFnrglQ3S1TOxKM,139\r\ntwisted/conch/client/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/conch/client/__pycache__/agent.cpython-36.pyc,,\r\ntwisted/conch/client/__pycache__/connect.cpython-36.pyc,,\r\ntwisted/conch/client/__pycache__/default.cpython-36.pyc,,\r\ntwisted/conch/client/__pycache__/direct.cpython-36.pyc,,\r\ntwisted/conch/client/__pycache__/knownhosts.cpython-36.pyc,,\r\ntwisted/conch/client/__pycache__/options.cpython-36.pyc,,\r\ntwisted/conch/client/agent.py,sha256=0barVVIXiD1O_DvfBdGsRobOS2i9pH1tHXuqq_kA1jo,1730\r\ntwisted/conch/client/connect.py,sha256=mEiTeBIhhKdZZkb-qYNwZ_RC75CZ1hf9A_b0Rg7eHuw,672\r\ntwisted/conch/client/default.py,sha256=ekQY-TV_kubRLcp2YGdEi3C1OnAc1_egRVV3qlP5VAQ,11976\r\ntwisted/conch/client/direct.py,sha256=O7Jf4KPh7cyh67VqD8HokSKWQtsyG6dAnexAFY-BbpU,3264\r\ntwisted/conch/client/knownhosts.py,sha256=MiXC4BSXkxq8AsvLhPA_wcgSywBwFOCD7KYvzUocDzA,19875\r\ntwisted/conch/client/options.py,sha256=MJPpxYF36jME_VH-b54klDTdCIlS5YevnDq_ozodjtg,4145\r\ntwisted/conch/endpoints.py,sha256=jOs-YG4F9qaZubNI2xKeKbJ5oXJ0cRym6EeqmO69FM8,29743\r\ntwisted/conch/error.py,sha256=ynbrCK0fo_wdvyUhbV5GsMVvNjbNIFZHzvoT05hOEyg,2716\r\ntwisted/conch/insults/__init__.py,sha256=PALruuxw5vHDKLyzbY6XUcn73FFKhMk44dRQpFdrJvc,76\r\ntwisted/conch/insults/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/conch/insults/__pycache__/helper.cpython-36.pyc,,\r\ntwisted/conch/insults/__pycache__/insults.cpython-36.pyc,,\r\ntwisted/conch/insults/__pycache__/text.cpython-36.pyc,,\r\ntwisted/conch/insults/__pycache__/window.cpython-36.pyc,,\r\ntwisted/conch/insults/helper.py,sha256=SwL14WVDDvHl1uWesi0c0H4BD6JLjgDsY2TUsg3IFPo,14396\r\ntwisted/conch/insults/insults.py,sha256=8q8d5kxf0ah9xgxgzaSfeYDqBhbpCtsO7_k06TOl-BQ,35589\r\ntwisted/conch/insults/text.py,sha256=Cc07uGyoLNcsmtsd_uGMj0aT37zZbUamJB2J4uiXqlk,5424\r\ntwisted/conch/insults/window.py,sha256=eC-Delffu-yT-cKOvkvPpm_Ft9nRYk8QF8_zNuJo8Sg,27812\r\ntwisted/conch/interfaces.py,sha256=6pOyjMrOXPqS1TVwYuoiXSoutO4Wmq-RbiXO1E3p_tI,13636\r\ntwisted/conch/ls.py,sha256=1KtrdFww3j6bIEY2gZ0y_gi4TBy6CLQsoHUzWRcsUR8,2551\r\ntwisted/conch/manhole.py,sha256=wjpTsXUQ2QRbev_1WcJ9Z-2pbi1J5OKmHY2XoeLUpeQ,11832\r\ntwisted/conch/manhole_ssh.py,sha256=NqYFUy305e1DH1WQ3X2SFEG8UPZ6aD8CMKfiQ_4Iduk,3990\r\ntwisted/conch/manhole_tap.py,sha256=Q5Ljl6d73Shi_84GNeAmnIcZKFo_MTkhaPBZIKvW9bs,5370\r\ntwisted/conch/mixin.py,sha256=8haxUUg5oxVCUzJ71-agK4lJ_ObJ828O2U2sds8dGPM,1374\r\ntwisted/conch/openssh_compat/__init__.py,sha256=uIe8Ifysdq6wuLyqjeMXT81DKsZw56QqgxWazKZERu0,152\r\ntwisted/conch/openssh_compat/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/conch/openssh_compat/__pycache__/factory.cpython-36.pyc,,\r\ntwisted/conch/openssh_compat/__pycache__/primes.cpython-36.pyc,,\r\ntwisted/conch/openssh_compat/factory.py,sha256=csprCbaqAQV2V3jcm0jmltxDnl4nY8v3hH7ztTf3lNE,2323\r\ntwisted/conch/openssh_compat/primes.py,sha256=_RyvlWjxwymp18gcA0HaiISr8OPwXM3WmsdowkTybeg,682\r\ntwisted/conch/recvline.py,sha256=jre0-Le7dp-RplyURznthdQuhu1ZQ5JC7V2YT93EK20,11523\r\ntwisted/conch/scripts/__init__.py,sha256=UJRr3MgRq7dcUk9OBG9M0jOmMs2H746XbolCl0dZgwI,16\r\ntwisted/conch/scripts/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/conch/scripts/__pycache__/cftp.cpython-36.pyc,,\r\ntwisted/conch/scripts/__pycache__/ckeygen.cpython-36.pyc,,\r\ntwisted/conch/scripts/__pycache__/conch.cpython-36.pyc,,\r\ntwisted/conch/scripts/__pycache__/tkconch.cpython-36.pyc,,\r\ntwisted/conch/scripts/cftp.py,sha256=TF1LsKgpmK1nCM_Z-2mgdP2ArVwULAYW44zWesmStkM,31775\r\ntwisted/conch/scripts/ckeygen.py,sha256=fceeMBsu3imO-lINBtU72KDMJMsXAT9t74jI9C9Mq6I,10078\r\ntwisted/conch/scripts/conch.py,sha256=gNpQFxlMJsrockj4-14kIqkHgEbB1l-xiXK5pQdeVEA,18462\r\ntwisted/conch/scripts/tkconch.py,sha256=nuBbI7FPh-ufV-RZGqOHFtJoN1-btbzjWE9LBsNd1_s,23189\r\ntwisted/conch/ssh/__init__.py,sha256=IDSvIu8OyDtv2iyBNQlgpZCYPmRDQ1OWBYDm2FUnSXM,183\r\ntwisted/conch/ssh/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/_kex.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/address.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/agent.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/channel.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/common.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/connection.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/factory.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/filetransfer.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/forwarding.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/keys.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/service.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/session.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/sexpy.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/transport.cpython-36.pyc,,\r\ntwisted/conch/ssh/__pycache__/userauth.cpython-36.pyc,,\r\ntwisted/conch/ssh/_kex.py,sha256=keHgecXDjuUHu_hv21Aaq6FBasMUZqFk1BtDAZ8DhUE,7668\r\ntwisted/conch/ssh/address.py,sha256=2ZCPpaUa_Evaj_M_KjbBzllx2gf1l2DQt30rXJwL_-s,1158\r\ntwisted/conch/ssh/agent.py,sha256=YITkSpOpiaNSI6EBt4M2EKogOk0Rlj4_QJX0lznRsAs,9692\r\ntwisted/conch/ssh/channel.py,sha256=nS1uE0DmZWUvp0vESpSQoanfktxYI50WNV6Sdfyrz1U,9852\r\ntwisted/conch/ssh/common.py,sha256=B9LRnUkmWZoQOF1PRFk6b-85_NH1jRzMaE0ROPZk1KY,2059\r\ntwisted/conch/ssh/connection.py,sha256=oTD85RQqrKGjHfRBG_PFNoMAJzLc8v6FvZpPY86Vxy0,26151\r\ntwisted/conch/ssh/factory.py,sha256=X28xtqHwEpsDtVswL6ele4Wo_4-q6mLugeW03LGW1As,3820\r\ntwisted/conch/ssh/filetransfer.py,sha256=pIbW2bXLGagYFKSNKmsn9px7tLto-mS3EhTgoM90778,34723\r\ntwisted/conch/ssh/forwarding.py,sha256=L0hBefu4bo4-L-4GCX-wnoFSGmCO9evRFQsm1YcPOVk,8176\r\ntwisted/conch/ssh/keys.py,sha256=zlpe3nNB5xWmgmepeXLN_2RsdCdNmTCR1fmhDw5tIdg,54988\r\ntwisted/conch/ssh/service.py,sha256=YV99lc0ZxNZMqKFurGXe-i5m8VbeBOZjti7HlO61fvU,1456\r\ntwisted/conch/ssh/session.py,sha256=xTVxNdd2MHBP-PhACVZHBLRJPdYn6auAbHZrYPtJ5TE,11225\r\ntwisted/conch/ssh/sexpy.py,sha256=lb0LVT8frScz5WEbMklatpcH5xqSV23ayw-m3CPlJP8,1053\r\ntwisted/conch/ssh/transport.py,sha256=r1xXHsOow7lOooe0rMgfb2cjyRgFcYrgg-JqiXb3los,73499\r\ntwisted/conch/ssh/userauth.py,sha256=jM51sMI7wmOgDVqH8Mbmc0QGWknJK5T5-y0iigchLR4,27336\r\ntwisted/conch/stdio.py,sha256=daZfnkeiP4dWbrAWVS3IwRVRrXA-VWvkyL1JpXO0uco,2764\r\ntwisted/conch/tap.py,sha256=9edTigyWQ7HmwQM52PPXIQEtjK_ENzLIm2TOqbsLnaE,3183\r\ntwisted/conch/telnet.py,sha256=hqa_MuP0QsaBfjqCA5I4qoJNgT0CIevrFZhlZRRqkhk,38539\r\ntwisted/conch/test/__init__.py,sha256=HAuvSUTlRN7E22xo4FEOw_2INTlSQcW-j3maA64RIWE,14\r\ntwisted/conch/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/keydata.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/loopback.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_address.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_agent.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_cftp.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_channel.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_checkers.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_ckeygen.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_conch.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_connection.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_default.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_endpoints.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_filetransfer.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_forwarding.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_helper.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_insults.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_keys.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_knownhosts.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_manhole.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_manhole_tap.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_mixin.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_openssh_compat.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_recvline.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_scripts.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_session.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_ssh.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_tap.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_telnet.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_text.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_transport.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_unix.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_userauth.cpython-36.pyc,,\r\ntwisted/conch/test/__pycache__/test_window.cpython-36.pyc,,\r\ntwisted/conch/test/keydata.py,sha256=kKR2HtebOfEYUJoitfE2f5WP0tLTfiX8T1Y-LuoSzDU,34462\r\ntwisted/conch/test/loopback.py,sha256=qV37tzWIsclzzTBSMiJfZP7-QDu9uBss82vNd926vZk,757\r\ntwisted/conch/test/test_address.py,sha256=OCDd05QbekjIIAMIeTlD39FfFc74TOUScnJSB1fHtQs,1629\r\ntwisted/conch/test/test_agent.py,sha256=9c_mMNa6OesLxvEblONmufuLKgkbngt9hKYZOA4KzAY,13086\r\ntwisted/conch/test/test_cftp.py,sha256=qfSE0uqVjEUqqNGZ24lm4bE3cl4KlisT_k5gT7NQP9Q,50866\r\ntwisted/conch/test/test_channel.py,sha256=xCt_cPTjQdHtu9kMNRBY5v3ZHOZnsiVRsmQaVBNcrO8,12099\r\ntwisted/conch/test/test_checkers.py,sha256=3bQSxiqv_91SAa55bfPKEVsLYccdJGAkQP2W7R2jm2A,31498\r\ntwisted/conch/test/test_ckeygen.py,sha256=Sk0IG-BX77iJfnnwJ6WVOA-1djeDec202WXtIYkL6Es,20158\r\ntwisted/conch/test/test_conch.py,sha256=OOjekhD7uE_VVi-4ShrO8Phss8nQJTbuoyLl2jzqKb0,25140\r\ntwisted/conch/test/test_connection.py,sha256=Bo-o57TFu_HJyD7YSS7L_WPg045bzl7dpoiHfr5F8pY,28729\r\ntwisted/conch/test/test_default.py,sha256=QPDy8v9neuR_q5y2l2-eRk2m7h70ZRX4vl26giyGTJI,11584\r\ntwisted/conch/test/test_endpoints.py,sha256=zEsFSKwShr_D70T5EGPplmldNq5vhKzpwngK-U8FhZE,54561\r\ntwisted/conch/test/test_filetransfer.py,sha256=DNiffEU0csVUwrLHq0kOqRmaRoGzDAgVvKYMh88MuDg,29239\r\ntwisted/conch/test/test_forwarding.py,sha256=DUUceXTLnXBPdEiEdnsRCFr_1mYnDprxgphXXQ3vW5g,2216\r\ntwisted/conch/test/test_helper.py,sha256=Fyl1gfsQbJMwzJN1OgyId5bEVW3rB1wWJdB5KCHpeZ4,20492\r\ntwisted/conch/test/test_insults.py,sha256=8TlCDalzJMnIsXm1nqMuGbkvdzHq9TkfIiR3Jlmtjf0,32330\r\ntwisted/conch/test/test_keys.py,sha256=Cp8SAlEUXm6ExJIo4yzodsDdVLdlnzDNn6DwZnQDwhk,50732\r\ntwisted/conch/test/test_knownhosts.py,sha256=hLDWLTA5UhVFW4kHGjUdXhlviG9ORD0SS0Y8zQy2x2w,49398\r\ntwisted/conch/test/test_manhole.py,sha256=7vznZ_Cye7YcnXUpxvDEMkxug_klwNSAIfiRbfva30U,13462\r\ntwisted/conch/test/test_manhole_tap.py,sha256=MzFrW10USUMe4tR2E7MpIGU94XPQogeSEg9_p6x9bM8,4235\r\ntwisted/conch/test/test_mixin.py,sha256=4_kOBOFf8gbWXEUuPPoggf5e2XBhdrZEa-dcnDoyWM4,1055\r\ntwisted/conch/test/test_openssh_compat.py,sha256=JoSP23u_ITcTvXju4mT_C7iHG3Aad0-R_C9Y7GQxnQM,4630\r\ntwisted/conch/test/test_recvline.py,sha256=81zKYJBYoxwPdr8Mm_yUXMgR4qykVGVaIitDGtK0pUU,25406\r\ntwisted/conch/test/test_scripts.py,sha256=hpbHxsJy4mC9Zn4qH_NVYUhKWaZ85o-9oKPzPppEwq4,1887\r\ntwisted/conch/test/test_session.py,sha256=O9EcNItOWoHaSIs18gzpzzuriKvZ-aQZF2hDpFj3vE8,39464\r\ntwisted/conch/test/test_ssh.py,sha256=XGM-BvVl_kK4bW9NFerqyZUeSso2cmDkxyyxCZbPrG0,32377\r\ntwisted/conch/test/test_tap.py,sha256=UDKmRhcEtFtV3G2D7WTyObP3z9QL1yBremFGxSBY7oc,4951\r\ntwisted/conch/test/test_telnet.py,sha256=-RCx8XJzNvSeygjJVco-RxyK-VYlTnVt29vbjfRGrK8,26524\r\ntwisted/conch/test/test_text.py,sha256=QvJbWCZTTLyAd87Cti2HmZPbDt9QECENq2nrNUvr-bk,3943\r\ntwisted/conch/test/test_transport.py,sha256=8QGS8Fp7bv5WoWEcXMXuvcBH1o_qBvJDNtSepffFzCg,94204\r\ntwisted/conch/test/test_unix.py,sha256=P5M6yUwDYz9x5mbbpO2KW13D-5I4aL2lpyRZ7PMr-9M,2533\r\ntwisted/conch/test/test_userauth.py,sha256=FHck9BxouYpJB42vth9xTCrfUQ2D0TaLwt1RBPuu8m8,32604\r\ntwisted/conch/test/test_window.py,sha256=2Qzq_paXugLOlUWEel3p79g71OuAOPahtQV_1d87mnU,2115\r\ntwisted/conch/ttymodes.py,sha256=J0Z95i2ljFJi9Wrclw_h7RvudTQp5TWXY_QerE8gY8Q,2239\r\ntwisted/conch/ui/__init__.py,sha256=RizFn8MwYiNGvqshvLD3SPhUGafTcMZ-o8U9EkwSF8k,167\r\ntwisted/conch/ui/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/conch/ui/__pycache__/ansi.cpython-36.pyc,,\r\ntwisted/conch/ui/__pycache__/tkvt100.cpython-36.pyc,,\r\ntwisted/conch/ui/ansi.py,sha256=ZMh5UAKbHP55G8nKJcWzdrrQO9wWj8bBMbTRA1c2zZY,7181\r\ntwisted/conch/ui/tkvt100.py,sha256=q3a8r-97Qya7ompsc2wxVHS55uNY_FPe-5vNzOBzoZY,7052\r\ntwisted/conch/unix.py,sha256=dbOqv_-62mWg-6LwfscElkY5ZWvRZIB0AfEry4k6lEk,16307\r\ntwisted/copyright.py,sha256=_BzTp6ekKVHGxy_igsXo4e4Y7TkQiRkGFglIjK0PHkQ,1531\r\ntwisted/cred/__init__.py,sha256=W4NhTuZj7C95wT9UlvVbCa37jcHD_QJCyo5CImBK8Pg,189\r\ntwisted/cred/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/cred/__pycache__/_digest.cpython-36.pyc,,\r\ntwisted/cred/__pycache__/checkers.cpython-36.pyc,,\r\ntwisted/cred/__pycache__/credentials.cpython-36.pyc,,\r\ntwisted/cred/__pycache__/error.cpython-36.pyc,,\r\ntwisted/cred/__pycache__/portal.cpython-36.pyc,,\r\ntwisted/cred/__pycache__/strcred.cpython-36.pyc,,\r\ntwisted/cred/_digest.py,sha256=sSpPeBMKKWYmYrW_fJ-5OwRUykFMVTsUAWHyonBbQ78,4114\r\ntwisted/cred/checkers.py,sha256=cAUY_9xiu8Fmrl1uMbvrkbxgaf137IOYQE8O5dYzKfQ,9219\r\ntwisted/cred/credentials.py,sha256=Q47WuA1omb0v5NoxIenOJV2sTUu_oFk1Ogfmlc2WMqU,16220\r\ntwisted/cred/error.py,sha256=Cpk_fR1EETu-HUAX7pbZakS-gw5nT8IADPbfdPMCt3Q,1037\r\ntwisted/cred/portal.py,sha256=-oz18ZO9qFnWGmTE4bqXmFIvjqJYKJBjebVhjkTuyh4,5406\r\ntwisted/cred/strcred.py,sha256=7_LkVWPalXkU5aTeU-KhNbnQs4Ov0wkM3fhW8xwRLIY,8385\r\ntwisted/cred/test/__init__.py,sha256=dJnJovocFbB0NlnMradQkTYnlhmluUFWNL3_wFUzJek,157\r\ntwisted/cred/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/cred/test/__pycache__/test_cramauth.cpython-36.pyc,,\r\ntwisted/cred/test/__pycache__/test_cred.cpython-36.pyc,,\r\ntwisted/cred/test/__pycache__/test_digestauth.cpython-36.pyc,,\r\ntwisted/cred/test/__pycache__/test_simpleauth.cpython-36.pyc,,\r\ntwisted/cred/test/__pycache__/test_strcred.cpython-36.pyc,,\r\ntwisted/cred/test/test_cramauth.py,sha256=8t4EMvxjl2iJBwSFEjppRO_VOunyzd_BWT5qGsJhLyM,2878\r\ntwisted/cred/test/test_cred.py,sha256=ikCGIkSBUkzXqNmqrX3PCJ2dsmAs8FN7FfG2Br3RYXM,13589\r\ntwisted/cred/test/test_digestauth.py,sha256=hJq6Zb5ZUY8FsOLf39tFSSpZxNFJ_0wq3W-DNfTsssU,24353\r\ntwisted/cred/test/test_simpleauth.py,sha256=9RuqcmpS17hEE6le1S5i44AO4PLYhKVhDVLsa5s0AyQ,2953\r\ntwisted/cred/test/test_strcred.py,sha256=CYIaHDkPqfD3lt-w2FPQNdDXZO0Q4CdSrYiDTniV9Z8,26359\r\ntwisted/enterprise/__init__.py,sha256=GnETu2_bpAushHQriI67GNeToHIqtrGNqOjXqg-cGsY,162\r\ntwisted/enterprise/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/enterprise/__pycache__/adbapi.cpython-36.pyc,,\r\ntwisted/enterprise/adbapi.py,sha256=-sHE2s0wLHiIEmModgIc8LfxZRjpG_Ljzv0h4D-rXp4,16883\r\ntwisted/internet/__init__.py,sha256=ickB0k1GfdghN-mprceL4YNhZOqOJTSbTssukmcHhyw,521\r\ntwisted/internet/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_baseprocess.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_dumbwin32proc.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_glibbase.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_idna.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_newtls.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_pollingfile.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_posixserialport.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_posixstdio.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_producer_helpers.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_resolver.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_signals.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_sslverify.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_threadedselect.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_win32serialport.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/_win32stdio.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/abstract.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/address.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/asyncioreactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/base.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/cfreactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/default.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/defer.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/endpoints.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/epollreactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/error.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/fdesc.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/gireactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/glib2reactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/gtk2reactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/gtk3reactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/inotify.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/interfaces.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/kqreactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/main.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/pollreactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/posixbase.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/process.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/protocol.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/pyuisupport.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/reactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/selectreactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/serialport.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/ssl.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/stdio.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/task.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/tcp.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/testing.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/threads.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/tksupport.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/udp.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/unix.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/utils.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/win32eventreactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/wxreactor.cpython-36.pyc,,\r\ntwisted/internet/__pycache__/wxsupport.cpython-36.pyc,,\r\ntwisted/internet/_baseprocess.py,sha256=oA5Yr481sEDg4UgsRyPDdwgz7RXJmasV6-jfuiSxlbE,1913\r\ntwisted/internet/_dumbwin32proc.py,sha256=7v0Zi003NzCWLE755g8cxr5ymcV2tN7R2B0Vdqc2WiI,13107\r\ntwisted/internet/_glibbase.py,sha256=UYNKRhHRPS9Qz8xmBIdDzZvYW9_-yQIy94P12O6pqGs,12813\r\ntwisted/internet/_idna.py,sha256=gYjexNDtZN1i0h6qoM161lGgOJrJHuBa1eP53oRr2jw,1397\r\ntwisted/internet/_newtls.py,sha256=NOCNH8CX-3CplooDfnprvg9o6qkUyt8QaMwN2r8_IKY,9332\r\ntwisted/internet/_pollingfile.py,sha256=qJAGGqXSJ6WYX6EyYe9wb-7OogZ_8DckKmTWjruyJDE,8982\r\ntwisted/internet/_posixserialport.py,sha256=gg1KrS3F4k33mULmkxekoM80XE8nhrZ-_oQxq27uTm8,1995\r\ntwisted/internet/_posixstdio.py,sha256=6vMt5L3wPA0c-rsTMyqDA583yVzsiR5o6lQ5FwmHkF8,4687\r\ntwisted/internet/_producer_helpers.py,sha256=eOqBQC5NsjBWT41oxQLwkyBQBh819uACCq-fIYDWRAs,3788\r\ntwisted/internet/_resolver.py,sha256=XjW_CQC8HxeWs7RvZXLLL6F4vN111Z1JC6uTbRK-skc,8530\r\ntwisted/internet/_signals.py,sha256=632Qy-EUB5v5RmhhhyntSkziY4jbb-kr2OhRDIHIrVQ,2718\r\ntwisted/internet/_sslverify.py,sha256=0wkJdmFhwHg4bA6iLSxRUU_hUZalgL0z5eT8WdrSrPk,72643\r\ntwisted/internet/_threadedselect.py,sha256=kYBjTox4Izt0jwTay-zrijjPN1PBZsOcbF1Q2HmsKi0,11764\r\ntwisted/internet/_win32serialport.py,sha256=BG-J2A18t-OWpFgRb0O3kN4KX6YPxVBq7q2knVA9muU,4744\r\ntwisted/internet/_win32stdio.py,sha256=XEF95KvNvyAThHvO3xBBR1ZZSRxyuuAnbWexYFN35Gc,3204\r\ntwisted/internet/abstract.py,sha256=64vN7f-4wT0SjMvZWxGbL0gLCagly7K_jfTJbhhylSU,19274\r\ntwisted/internet/address.py,sha256=etExPe2zLdiMZLMMPdl4sKw-b14-z4qk-es5AjR44P0,5246\r\ntwisted/internet/asyncioreactor.py,sha256=RgqUpwhb9Oj4wuj5S1YSZDcvDD0qfnIGeQ3Dl1T7djA,10553\r\ntwisted/internet/base.py,sha256=YosxpOp73JRDyuUFe6F86Vw5jbxfKkm3UJHgcsw71tE,44807\r\ntwisted/internet/cfreactor.py,sha256=XD3vxoojc4ol__9m-l1UjI7_8x_iy1mS91qK7rrFxDE,17501\r\ntwisted/internet/default.py,sha256=Kaer40mBJZh2FNUjdwkcjLx0H4otwVjSxGJAjah1PeA,1942\r\ntwisted/internet/defer.py,sha256=7tVf05OEL9ZeHi_fbEE5NhsP0e1KCFkt4eOIObyKEi0,71538\r\ntwisted/internet/endpoints.py,sha256=5w7doQW1XUaZeYCXovxOSEZKIun6ZZs8onbe-4p1sAA,77326\r\ntwisted/internet/epollreactor.py,sha256=C88W-ZnEGxH7rLHOyyZEVdjLqA0N4yeprhpMax3gTXc,8493\r\ntwisted/internet/error.py,sha256=sGIWVe03xkrfFv3B3y6oCfxxbvchBZFJg0bU5gPoJ6I,12930\r\ntwisted/internet/fdesc.py,sha256=nVL6TE6JBUJW-Yfyh7uaWBv-NHqE_Uc1qIT2Myz30qk,3223\r\ntwisted/internet/gireactor.py,sha256=CtgJNXQymPyihhiqrWHZqT89g65hSXXZHrITwypVQjI,6123\r\ntwisted/internet/glib2reactor.py,sha256=_fHgbRRmABRTuLZ9hGia_cf5WsKYUoUfn7G3Ue6r8oY,1115\r\ntwisted/internet/gtk2reactor.py,sha256=otOVjJ41g2XqlSkv917z_XjoXtxYku1G6Qu6OrkLCXA,3614\r\ntwisted/internet/gtk3reactor.py,sha256=j_m-9nnTk267VQpfE-SVRplkJTEQGmsRz-dZMQz5kZA,2252\r\ntwisted/internet/inotify.py,sha256=X4mQASe4bdY2_hyh80JdHQYElzqYmsH7I6GMHcJhXxM,14691\r\ntwisted/internet/interfaces.py,sha256=CQTA8orAZHIXl4SLOaPklIHBbplfF7qMT6W0JT_gX2g,96841\r\ntwisted/internet/iocpreactor/__init__.py,sha256=27qHsOLp9irn3pKHUwlAOyJdu9khir4tTTPLj8djNIg,191\r\ntwisted/internet/iocpreactor/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/internet/iocpreactor/__pycache__/abstract.cpython-36.pyc,,\r\ntwisted/internet/iocpreactor/__pycache__/const.cpython-36.pyc,,\r\ntwisted/internet/iocpreactor/__pycache__/interfaces.cpython-36.pyc,,\r\ntwisted/internet/iocpreactor/__pycache__/reactor.cpython-36.pyc,,\r\ntwisted/internet/iocpreactor/__pycache__/setup.cpython-36.pyc,,\r\ntwisted/internet/iocpreactor/__pycache__/tcp.cpython-36.pyc,,\r\ntwisted/internet/iocpreactor/__pycache__/udp.cpython-36.pyc,,\r\ntwisted/internet/iocpreactor/abstract.py,sha256=I9NG1gYeV_qM2GK0OQOsnATXo4mfbGov3KsMZuFKgVU,13140\r\ntwisted/internet/iocpreactor/const.py,sha256=t66XJONPOmxAo65y--PGT3hGuCuzW0hkZSYPn3_rxM0,524\r\ntwisted/internet/iocpreactor/interfaces.py,sha256=QjNOs3GrwNkJDhXno7a6t8cmYPYYZimfzAcolyW5APM,942\r\ntwisted/internet/iocpreactor/notes.txt,sha256=M0nci0EaspffjVOb52oxwbdcCldjBd861kJYbCtOpAg,890\r\ntwisted/internet/iocpreactor/reactor.py,sha256=ljIs-BjzYA4WdWWDuAeWq_FHOis4OhIsZxviOK0tDpE,9190\r\ntwisted/internet/iocpreactor/setup.py,sha256=cDNm15Q783-ma3x24dn_AskmZKzcw_Lm6kSTsb_5kXE,588\r\ntwisted/internet/iocpreactor/tcp.py,sha256=jpM9wcpgvuVvABk8pdWFd52IFOdVEZxG4u_ug_-6wIs,20143\r\ntwisted/internet/iocpreactor/udp.py,sha256=PDN_RpvDmk3P4wr_0NbUjB0c6d3_JWE99_BqIR7QZMA,14016\r\ntwisted/internet/kqreactor.py,sha256=q6rBYkifSJRLgvHM8_DG9yUxfIMrWD8GqXR3IhFOzI0,10292\r\ntwisted/internet/main.py,sha256=Be-vOTGwAjtJp4ClfJS_YcFNi4K6OD5MRZbPAdf1z0c,1054\r\ntwisted/internet/pollreactor.py,sha256=-8iCPvvAmFdrppsUmVi0Y3YB13shYVx5Butm804ECp8,6026\r\ntwisted/internet/posixbase.py,sha256=gqF-AR9g5fuZFuTYgE_bBomw15nf6wayV7T2w2PE0LY,26357\r\ntwisted/internet/process.py,sha256=xjwiddhe5gc77KuNaoJ_wvaoJHuB0PNpD7q32ELzvG4,37757\r\ntwisted/internet/protocol.py,sha256=4H2pC8sMBybJp91_1WEHMELsdndtydqnMIwzgyNnHmA,27134\r\ntwisted/internet/pyuisupport.py,sha256=v265CibEt7gJzS295Gp8krpqWi-6LQc8jOSuKPwILWs,817\r\ntwisted/internet/reactor.py,sha256=MKC3G2suikAAo6jxm2HTVRWizJ6aIoDUp4BBlG_TZ2Q,1863\r\ntwisted/internet/selectreactor.py,sha256=_4uNzRQ1pId94vFgYAILlfMNEC81P5OFjXfY4tXCBkE,6215\r\ntwisted/internet/serialport.py,sha256=6h2KSqB_U1GfduHwNO-XWVQ7deZdIaT9izwyI_OCQf0,2317\r\ntwisted/internet/ssl.py,sha256=p_eXSk4crn1yS9659veU9y-d0npj-61xKwdrLl7Lees,8444\r\ntwisted/internet/stdio.py,sha256=kbU3W7OTnXOvsHGgis2AeX13vzIgmzrgeS3DLRxlUnY,1045\r\ntwisted/internet/task.py,sha256=YwT9EXKh8X9W4UTnwDDVVWMbRQ755HfNc5Vd5sQ-pxs,31157\r\ntwisted/internet/tcp.py,sha256=jBDVMB8PVj2QvvwAgBkRgCLFCkhYT8hmW7X-0qI70EY,54908\r\ntwisted/internet/test/__init__.py,sha256=R0XCXlTn2bvT1mHPrDoQkW4y-WEXFq_jVBO83Nax7jY,112\r\ntwisted/internet/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/_posixifaces.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/_win32ifaces.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/connectionmixins.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/fakeendpoint.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/modulehelpers.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/process_cli.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/process_connectionlost.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/process_gireactornocompat.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/process_helper.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/reactormixins.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_abstract.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_address.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_asyncioreactor.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_base.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_baseprocess.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_core.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_coroutines.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_default.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_endpoints.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_epollreactor.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_error.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_fdset.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_filedescriptor.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_gireactor.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_glibbase.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_inlinecb.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_inotify.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_iocp.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_kqueuereactor.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_main.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_newtls.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_pollingfile.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_posixbase.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_posixprocess.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_process.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_protocol.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_resolver.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_serialport.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_sigchld.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_socket.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_stdio.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_tcp.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_testing.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_threads.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_time.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_tls.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_udp.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_udp_internals.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_unix.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_win32events.cpython-36.pyc,,\r\ntwisted/internet/test/__pycache__/test_win32serialport.cpython-36.pyc,,\r\ntwisted/internet/test/_awaittests.py.3only,sha256=651lYVAeyzETW_iKSUSuSC5e4PhbsA-wWTtTg_j8cKY,6175\r\ntwisted/internet/test/_posixifaces.py,sha256=xL3pSciwjrgsc2vDGnDKHOvE4mdrgcl7bn8k0Ntv_VU,4689\r\ntwisted/internet/test/_win32ifaces.py,sha256=vVJB50tK-ld9Dl4twObaEmKkPVUJ33aXGoR3_D-PJdA,3883\r\ntwisted/internet/test/_yieldfromtests.py.3only,sha256=cF9nuNuy-83kpGw7EaIbqZLWyopXSCI_VWNtLl3fZUM,4333\r\ntwisted/internet/test/connectionmixins.py,sha256=Pue7N7q7eKo3YmhcnAofG6Ywqm6qlg0aM-PEVyUo8zw,20442\r\ntwisted/internet/test/fake_CAs/chain.pem,sha256=3oISrpA2Sb0kD6NysWF0imvVJL3B27li6fhvN0f8NWQ,2090\r\ntwisted/internet/test/fake_CAs/not-a-certificate,sha256=GJS9_LOIDdjtHP_M9HZVBli__V-Drd2i_sWSMUyfzlg,84\r\ntwisted/internet/test/fake_CAs/thing1.pem,sha256=RWz-DQyE72AFJo6awm6JarF4NAtDdryvmlYCL1hgkEA,1339\r\ntwisted/internet/test/fake_CAs/thing2-duplicate.pem,sha256=jl9GaNBh32s56E8BGhxhvX9g-VcLFE9bmrcYh-ONyXU,1339\r\ntwisted/internet/test/fake_CAs/thing2.pem,sha256=jl9GaNBh32s56E8BGhxhvX9g-VcLFE9bmrcYh-ONyXU,1339\r\ntwisted/internet/test/fakeendpoint.py,sha256=WyT9ss1Fc_2yeLLgJYkHuunArjULjxP_vzq1NSJUIHQ,1555\r\ntwisted/internet/test/modulehelpers.py,sha256=mA3sU_zQ42YObsSffwtei1JaiB3vZHOQwJG864Nj3pU,1726\r\ntwisted/internet/test/process_cli.py,sha256=SJl3N3-wknNAZsd7gpLVSLNHAbd8XaoGxCgyczRkbE8,664\r\ntwisted/internet/test/process_connectionlost.py,sha256=aDGj_l1QlH2pSmwWRPQbW-YSqjgy-3pVm7tEjmveRVE,119\r\ntwisted/internet/test/process_gireactornocompat.py,sha256=2p8sOZbMzmzI3XsEF5KmG7f09fkNNIL9WSBl1B_5V6o,721\r\ntwisted/internet/test/process_helper.py,sha256=rTonb5m0GZ7SEHdD--OBxitBvOurLo_KXSewArnznos,1081\r\ntwisted/internet/test/reactormixins.py,sha256=bQDbUUhazlVO9ZAsFGD10WNicNlKxC_7MdgfWznPMQo,14054\r\ntwisted/internet/test/test_abstract.py,sha256=mxQNphfzUEaFw24JSP0EXE9DeSwqqoaxPY8u4xS6jc0,2032\r\ntwisted/internet/test/test_address.py,sha256=s2SRx7zOIfNzHsdyyd-Up54C1--5yPgYK_bifGpsCzg,8598\r\ntwisted/internet/test/test_asyncioreactor.py,sha256=AvqcLlFgGKeoMAH_KT0v09v0Kz1-Q-f2JBR6jsf57tg,1331\r\ntwisted/internet/test/test_base.py,sha256=ppOqFt_1MBBG6Gyod47GTwqIhwTiM_y2cyMPfRz8ISc,13369\r\ntwisted/internet/test/test_baseprocess.py,sha256=Z9RUmCFPJ8P75H0rnY7bpXor2ziJ3SG0dWcwYk3FYAM,2613\r\ntwisted/internet/test/test_core.py,sha256=Qvk9lprgYzWgLmGppftwu8VxG6m4trqIbohsRag8Oq4,11262\r\ntwisted/internet/test/test_coroutines.py,sha256=h7mJtgpmxyufah9lGIuobxR9zWZq021YtMhDbJW9dSg,1787\r\ntwisted/internet/test/test_default.py,sha256=Nzy-gVFdIG-jSuaLy79QryRBKKj7yCJN0cb5P2c0L1s,3540\r\ntwisted/internet/test/test_endpoints.py,sha256=cAEAumCdQvM7Hzsgv0zxVKe4-nyHZvvJUxifWKVCaRs,148715\r\ntwisted/internet/test/test_epollreactor.py,sha256=d4AYzKsTlX3vltXsYeuLs1_izD_SDlLppzZu3r8mkok,7336\r\ntwisted/internet/test/test_error.py,sha256=oDVs6B66RlGVry9EUFcB3veY6F7XKbP8ollJtzl3Vls,1117\r\ntwisted/internet/test/test_fdset.py,sha256=4nb3OZQ4IkvxdctWv9D7aqHt9Q2oG2AEnk96id_je8g,13501\r\ntwisted/internet/test/test_filedescriptor.py,sha256=n5dk7wBEBkdEHkdVoP8giao8TuNozXXhuo4u7Rck_Fc,2808\r\ntwisted/internet/test/test_gireactor.py,sha256=nKg_WP2t7Px0qLG0OWwYctQPNFA6umxPB8apJS4cJec,9042\r\ntwisted/internet/test/test_glibbase.py,sha256=cy_fhIkPU1hWGR7X7HCHdxyttwsCW9znx6TfkUx3Ydw,2284\r\ntwisted/internet/test/test_inlinecb.py,sha256=EVvSMw9_P-S6ZPFsvxTl_T1dDsqoa10mrY1ZmxK6pPI,11599\r\ntwisted/internet/test/test_inotify.py,sha256=iNsOQCxh7STqv6UyFVM3CPCUcMGHHoHj5lH9bR-sV-I,16686\r\ntwisted/internet/test/test_iocp.py,sha256=ToWR8uGVP-xRi95rLrgg3XihthvR5vbiJXd0KlRaM-E,5170\r\ntwisted/internet/test/test_kqueuereactor.py,sha256=gwI-cGpRR9clo65AT2O5hJ_ywk4Aa2s3fC5dQ8N5R-o,1916\r\ntwisted/internet/test/test_main.py,sha256=GTjenqA-4z9NgFjkol_umHmFT9yJPc7_hRZm5qvhOgM,1436\r\ntwisted/internet/test/test_newtls.py,sha256=lRPyRBQB23xjyYl26xsHmk3DNvRAXrGq8MGzu0IEMnk,6693\r\ntwisted/internet/test/test_pollingfile.py,sha256=Q9lXthu2zLgpSx8-0JxxRWso3rYy2KzTMS4oYefBKIU,1278\r\ntwisted/internet/test/test_posixbase.py,sha256=yViBaItENJAHROGogmQfYLcCpr214vxRb3Xs6hn-OhE,9536\r\ntwisted/internet/test/test_posixprocess.py,sha256=MAx23Bu8oDxxLD4wsiH8r8U0dG6mwzOC4Hoaxg3F-jQ,11166\r\ntwisted/internet/test/test_process.py,sha256=N7DsHIzbIHA2fQrPeuUKyFonWLOmC3u-yUkek08xWVU,32045\r\ntwisted/internet/test/test_protocol.py,sha256=FYOzV9o1sfU0f9mX-sqmnGRBTIqMFC0AX2VHxXfTkc8,18727\r\ntwisted/internet/test/test_resolver.py,sha256=XelBnCD7C7407RoIi_pmjejNkP7lKvYopFHoXI-ulzw,20153\r\ntwisted/internet/test/test_serialport.py,sha256=61zuFJtDV9_UTAbWWHqFN1X84q5lweVB9hswsjs_b8Q,1948\r\ntwisted/internet/test/test_sigchld.py,sha256=STT-nfEsm4n1Y2NJVkHzQhbQNc-6RnZlu3sXvbL65DU,3935\r\ntwisted/internet/test/test_socket.py,sha256=mYp89LTUAPIHQ-hk0dwBV07WY-jGHaT_xT47dshgLzs,9329\r\ntwisted/internet/test/test_stdio.py,sha256=rcuJcxmqTy253faCcKn5IOb4H37FA9-zD-WmRwRvSLk,6449\r\ntwisted/internet/test/test_tcp.py,sha256=eu263u3jtvHW8NJSMiWZ1D6cRwSznVIUXzGxclWLCGo,108446\r\ntwisted/internet/test/test_testing.py,sha256=3piwz-YZPbta29JSQ35u-gjJIJIB8LvhealU1nO9vGY,16676\r\ntwisted/internet/test/test_threads.py,sha256=QHJlDT8yrt2p694J73OyYuyaQbfoE5JFGhVY11PBrBA,8582\r\ntwisted/internet/test/test_time.py,sha256=mkm9Dzb7WGfSLrGKrO2H_FWYcj9Hd2N23sutQrZM9uY,3717\r\ntwisted/internet/test/test_tls.py,sha256=6B_p8wgbLtiREd7RC7bq91d6Nq3Ttu9EnMFiMxQXbns,13459\r\ntwisted/internet/test/test_udp.py,sha256=xG2LDYVIUDAt9GKo017kkIk2rZV2uDDSMg2Z6zOuaWc,17140\r\ntwisted/internet/test/test_udp_internals.py,sha256=W3KXCY9AGz_BCwSEP86XPmNfHBRPqLwHA1rS2oeXh0Q,4909\r\ntwisted/internet/test/test_unix.py,sha256=uImznrC0H-zKauZsH8EWD_ByLYc3Qc8bZZMj0k2u_yo,35712\r\ntwisted/internet/test/test_win32events.py,sha256=9mDXR-8OVTXow8hgR9F9ygn42NoWPtQjpcLA_RWRmjE,6500\r\ntwisted/internet/test/test_win32serialport.py,sha256=5--jrNIeK1Q5268i1qFlTyj8rvAHKuos53muqidCaNE,5282\r\ntwisted/internet/testing.py,sha256=3k4bJWjcekOwK1N7mT3A-R_IWYXa89gFpgRcv_MOTLc,29106\r\ntwisted/internet/threads.py,sha256=9iwvudl1ROPFollGPXuD7vHLHzZFajNO4QR-9C_apr8,3953\r\ntwisted/internet/tksupport.py,sha256=th9iaGhbwYdurBXmOHfqjagRvi3vKMF-f30FPMne_fk,2045\r\ntwisted/internet/udp.py,sha256=HUJClZLNANFQpmaWqRRV_zM8jbEhHNY7JT3dx8L4ljI,18569\r\ntwisted/internet/unix.py,sha256=i7213Texp8VocUlaFtSp0P75XMmYFkKjJ0Se3sNoOvU,21965\r\ntwisted/internet/utils.py,sha256=38YGqBFgj4aqWuXq6Zme3sAPIYoNB42kBF0qiejJtmc,8347\r\ntwisted/internet/win32eventreactor.py,sha256=XgPo4hKF0a1hLbOVCxRWspGUoB5DtTBQVzNBtV_Dkkc,15193\r\ntwisted/internet/wxreactor.py,sha256=Bj43Qo8v0tm1SDiehiFEZO81wn2vVBdSifKGH3LZuq4,5290\r\ntwisted/internet/wxsupport.py,sha256=gNrChXmxkAVv_ANnVWYIXM7_MHYztDrZXoP8GVGIDqA,1363\r\ntwisted/logger/__init__.py,sha256=wua2tX8Am7sKMFTGoIMhFzT6b6HJRZ46sV9zEVLOzKU,3318\r\ntwisted/logger/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_buffer.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_capture.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_file.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_filter.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_flatten.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_format.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_global.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_io.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_json.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_legacy.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_levels.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_logger.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_observer.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_stdlib.cpython-36.pyc,,\r\ntwisted/logger/__pycache__/_util.cpython-36.pyc,,\r\ntwisted/logger/_buffer.py,sha256=Ey_2hKMColHaD4hmmSAfeWx54_y6k2NN05ZtAlSSObg,1484\r\ntwisted/logger/_capture.py,sha256=gkkka_YA9mivTlOakGk1svO39-0z-PgaIyDAM1S_bZU,459\r\ntwisted/logger/_file.py,sha256=cTcmdYkAUG6ZXvSoPUEw6DCjWM9SeHR--KzSy0uoDtg,2485\r\ntwisted/logger/_filter.py,sha256=hFxcx_Zj2MXUdNqjCtxLdFQbd8LMJdtPrUfBxB6Jfgk,6986\r\ntwisted/logger/_flatten.py,sha256=4IHEykWLzF7ETajOPemB-SPJYWsnKlcjjDmiM2tbovA,5091\r\ntwisted/logger/_format.py,sha256=oL_JqJcitW7oB_qUkKNcoJdexU0vQahK8k8otQi4kDM,12436\r\ntwisted/logger/_global.py,sha256=vulnbrNmcfWWArNLjApYasXFt0qiH97w1_Ngu3khvqk,8787\r\ntwisted/logger/_io.py,sha256=nBp4WrTrb7QS2UL4rm8tIEXgBjOHq1pay6jcSWPC2PU,4459\r\ntwisted/logger/_json.py,sha256=8mWj_DOABHynHDSvUBEBqUMVHYZ-O4deVwKJGKx0TqE,10069\r\ntwisted/logger/_legacy.py,sha256=IGc2gfq-FFYz5gJwz-XpLuhHdGrpL0CNvyWiYTNJS2U,5237\r\ntwisted/logger/_levels.py,sha256=EHzcJgMG3TyKV0hnUqX1LIExbPlvXwlEbxQmca0qfLI,3772\r\ntwisted/logger/_logger.py,sha256=htbvVZ-uTQPgu_6SdH2G_S7-0QB6Ui6mcUrYYLHrWz8,9548\r\ntwisted/logger/_observer.py,sha256=3R7RC7t1HQzzoPPLsst76vAqAc8821ofXdL9qQrlcJw,4991\r\ntwisted/logger/_stdlib.py,sha256=FjMeA8N4BzrQL4F-ldsap8nIdBvYOXfYwDPr-39L5gI,4611\r\ntwisted/logger/_util.py,sha256=tjt6KwCfV4aCTZrKgTFhunTgMKsAY19JTUIBgSmDDZM,1328\r\ntwisted/logger/test/__init__.py,sha256=cGAk-ROeAJboDWOal_3es3XGNfc2Krzid7s4tD6zC40,161\r\ntwisted/logger/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_buffer.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_capture.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_file.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_filter.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_flatten.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_format.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_global.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_io.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_json.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_legacy.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_levels.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_logger.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_observer.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_stdlib.cpython-36.pyc,,\r\ntwisted/logger/test/__pycache__/test_util.cpython-36.pyc,,\r\ntwisted/logger/test/test_buffer.py,sha256=1aktli9DYcJNP6RoSP9UEGWFOZPRkt7X-JjXIp8Yodg,1642\r\ntwisted/logger/test/test_capture.py,sha256=RY6MlSSxV3t2CQfpSL4Bw22lAntqkv3_S9rdUav2vzs,1083\r\ntwisted/logger/test/test_file.py,sha256=cheG1k5tukraq-D69-YkpyYLVuCRwDZBxSJ6Vq_7AtE,5623\r\ntwisted/logger/test/test_filter.py,sha256=eKTEDG9D3A40xean4VURrDqt1E6ahW9zMH4c4M_SPeI,12010\r\ntwisted/logger/test/test_flatten.py,sha256=ED2GgB3lbdSPquZa05sp1A8C2V-vEfIjqIeSgg_ZiMs,9137\r\ntwisted/logger/test/test_format.py,sha256=Ai0fX0tiug5XeFwKkSC0KS5A1Il0zLSONSU6SAymhiA,22563\r\ntwisted/logger/test/test_global.py,sha256=ASCp2U2HY9pxX5mVxezfDf-AlI4Sz92p_DfE1z3_TqM,12049\r\ntwisted/logger/test/test_io.py,sha256=23iLbLF5LW6NNtl1OUF1cewOhahXANuzJdYnDg8zL5c,7212\r\ntwisted/logger/test/test_json.py,sha256=7b4vPpSA_rDvU4odC18GWgHNkGQd-424eENIv-vc4WA,18584\r\ntwisted/logger/test/test_legacy.py,sha256=1UunwkcS4wNj55U4UbI_ju9Ode_AEIP9rO0hERfFchQ,14395\r\ntwisted/logger/test/test_levels.py,sha256=tOk3LKjszhlzyL1Yf9mWDli7JnP3KokbFEk8hH2KSAM,875\r\ntwisted/logger/test/test_logger.py,sha256=DpDTOl2Uunn9MndN7eqxVEU4xZ0rOV7rs8wOJ2XrjoU,7354\r\ntwisted/logger/test/test_observer.py,sha256=gJxSYGkZDddedE5bRufQP6WZqOaVwpmQIykEPemRHEo,5253\r\ntwisted/logger/test/test_stdlib.py,sha256=0jMzZ7VT2KwXKqxmzycArG9FKzmOg6wwuktMJtodgk4,8639\r\ntwisted/logger/test/test_util.py,sha256=dyGJWIINUYI2MeIPEG-NntOByrg6eQ0IeZZhrcdt2K8,2671\r\ntwisted/mail/__init__.py,sha256=TTwDhFQPpKH_2LKY6Bcc1_eBoua-VUIeuY2S1-P22JI,142\r\ntwisted/mail/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/mail/__pycache__/_cred.cpython-36.pyc,,\r\ntwisted/mail/__pycache__/_except.cpython-36.pyc,,\r\ntwisted/mail/__pycache__/imap4.cpython-36.pyc,,\r\ntwisted/mail/__pycache__/interfaces.cpython-36.pyc,,\r\ntwisted/mail/__pycache__/pop3.cpython-36.pyc,,\r\ntwisted/mail/__pycache__/pop3client.cpython-36.pyc,,\r\ntwisted/mail/__pycache__/protocols.cpython-36.pyc,,\r\ntwisted/mail/__pycache__/relay.cpython-36.pyc,,\r\ntwisted/mail/__pycache__/smtp.cpython-36.pyc,,\r\ntwisted/mail/_cred.py,sha256=V-98-Kn5dWa1_6UboZEr77FgshnyFQSdPVcFypXcnZ4,2786\r\ntwisted/mail/_except.py,sha256=2bhvABOlSg_b2rwyyNIgAI4TpaNIsz0mkSVqHv0qn9o,8763\r\ntwisted/mail/imap4.py,sha256=Oa2_Utr0ojbY-cMuaQmGLowZ8_rm4rmalTqrz2W3aug,211261\r\ntwisted/mail/interfaces.py,sha256=RpN6ZHGZ34n2O7R4__AnVXyavlFdxF0hO20HG9-_Elc,32153\r\ntwisted/mail/pop3.py,sha256=IRFvrotm_YB7E3DXGXIn0rpRz4yVBgF4jxQt6TDfYWE,54946\r\ntwisted/mail/pop3client.py,sha256=dWHzCuiijPz2mm9p0AFGCVHzZccjcf2KN5wy6aF4yBY,46706\r\ntwisted/mail/protocols.py,sha256=OdMKy9HSqLjPfma78rFtu5UaHz_SzCBCV9vFucSjOOc,12644\r\ntwisted/mail/relay.py,sha256=DoGtkPnwEL6N9nutaWn4EmV8pxBTFrz_Mnh2tWwvQsY,5361\r\ntwisted/mail/scripts/__pycache__/mailmail.cpython-36.pyc,,\r\ntwisted/mail/scripts/mailmail.py,sha256=grFSxZpUjZvcegj2OkwUkfDunUGpAYv-c75nGY2JfT0,10581\r\ntwisted/mail/smtp.py,sha256=4t5MEHp3_1oaicOO1OQBHhKb-nDdha1FVhZrAu2USQA,71612\r\ntwisted/mail/test/__init__.py,sha256=p5MeYvSnUTo_P8vZfiYhJ1KXeI-Y090YiJfedQFqvkE,24\r\ntwisted/mail/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/mail/test/__pycache__/pop3testserver.cpython-36.pyc,,\r\ntwisted/mail/test/__pycache__/test_imap.cpython-36.pyc,,\r\ntwisted/mail/test/__pycache__/test_mailmail.cpython-36.pyc,,\r\ntwisted/mail/test/__pycache__/test_pop3.cpython-36.pyc,,\r\ntwisted/mail/test/__pycache__/test_pop3client.cpython-36.pyc,,\r\ntwisted/mail/test/__pycache__/test_smtp.cpython-36.pyc,,\r\ntwisted/mail/test/pop3testserver.py,sha256=GC8MrFuOEWCA55VkGuZ0cl5eQ8iL7lYj12PzegNhE6w,8249\r\ntwisted/mail/test/rfc822.message,sha256=0nsnccDczctGjuZaRUBDgJ29EViOh-lRVFvgy8Mhwwg,3834\r\ntwisted/mail/test/test_imap.py,sha256=903XJQbfxHo2QOvarhxi5k5vm6-dfTVQAZV3KK8AtX4,265738\r\ntwisted/mail/test/test_mailmail.py,sha256=DzcZrQr7HS_Mpkxtt5UQpIDyX5KwgauTQEbe1tvmHus,12930\r\ntwisted/mail/test/test_pop3.py,sha256=EC0-NqaECqKBEVC0-3vartbdySYWyzTf6w4wNhp5y9E,42094\r\ntwisted/mail/test/test_pop3client.py,sha256=sLFvUs8SEvR79eLVEOLos4ebYuw3xUZvc6_rxVs-pyQ,21986\r\ntwisted/mail/test/test_smtp.py,sha256=j8TwKunZaHIhY7sfS5VtnNRKjEYbp0HRKyojAiChDvc,63927\r\ntwisted/names/__init__.py,sha256=pn-zinHevqxkH0Ww1O7gdT7u_xNISy_is4ODYmO071E,135\r\ntwisted/names/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/names/__pycache__/_rfc1982.cpython-36.pyc,,\r\ntwisted/names/__pycache__/authority.cpython-36.pyc,,\r\ntwisted/names/__pycache__/cache.cpython-36.pyc,,\r\ntwisted/names/__pycache__/client.cpython-36.pyc,,\r\ntwisted/names/__pycache__/common.cpython-36.pyc,,\r\ntwisted/names/__pycache__/dns.cpython-36.pyc,,\r\ntwisted/names/__pycache__/error.cpython-36.pyc,,\r\ntwisted/names/__pycache__/hosts.cpython-36.pyc,,\r\ntwisted/names/__pycache__/resolve.cpython-36.pyc,,\r\ntwisted/names/__pycache__/root.cpython-36.pyc,,\r\ntwisted/names/__pycache__/secondary.cpython-36.pyc,,\r\ntwisted/names/__pycache__/server.cpython-36.pyc,,\r\ntwisted/names/__pycache__/srvconnect.cpython-36.pyc,,\r\ntwisted/names/__pycache__/tap.cpython-36.pyc,,\r\ntwisted/names/_rfc1982.py,sha256=m4BrYSy8VRvdlg4io8DeMB5wzF5v6c2hePVueBnN7Ec,9113\r\ntwisted/names/authority.py,sha256=_wFwPeeSsyMvhtvlCXdOm1CZRlYEhN-nHEO5tw0EHis,16530\r\ntwisted/names/cache.py,sha256=vRGMwuE4lFhf4W2BodlwD8u8SSaMpAOYmTtl8zH1AAE,3804\r\ntwisted/names/client.py,sha256=PDqrkmpwagwzKXGLw5vsisfnCt_YQaxbYpBFWbY1nhw,24549\r\ntwisted/names/common.py,sha256=nFbHZKgxS2m9mv4oOYYTTTxa2XR-Wf0UZ3wqlpTJfCA,7860\r\ntwisted/names/dns.py,sha256=7t4GaYbIOmPx7s54BPEjlktRPQ2lPF89fxsQbJ4-RqM,96976\r\ntwisted/names/error.py,sha256=02_cTkNE6K1Gahwpxwors_qd9gr5ts3x0PghidZejMQ,2056\r\ntwisted/names/hosts.py,sha256=RQlExFaZGDTLvFhRoBH85KeeRI8Eq7UtxcpECBpMF98,4521\r\ntwisted/names/resolve.py,sha256=-zMAKlRaex2DuUXGw7-o2RxYRRrxAGNNa5o_x0Dxrdc,3361\r\ntwisted/names/root.py,sha256=-Q17Eu87jHN8V1V2xkyS5Jk-rn-11Nd5jUvxPoMZ_Uw,12448\r\ntwisted/names/secondary.py,sha256=Rzwbf-PCbzePioyR5AArHoS7ua_qXOz5GwkYNOJhmP4,6085\r\ntwisted/names/server.py,sha256=jtcUz8H2GW3a0XeUrpmkhmlF7GVJZHd8u9Rei06BDJY,22305\r\ntwisted/names/srvconnect.py,sha256=uGSBa0VzKQJgi-E4NbyB0MQgDNiX2BUSgPqJGPF5rW8,9144\r\ntwisted/names/tap.py,sha256=Jls1yZyObp10LUj9DdWFDXniWfju5JbXG8qMJYBHrCY,4832\r\ntwisted/names/test/__init__.py,sha256=d3JTIolomvO_PAkMM5Huipo6vc06Zyp3zhfeAuu_rEQ,26\r\ntwisted/names/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_cache.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_client.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_common.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_dns.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_examples.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_hosts.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_names.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_resolve.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_rfc1982.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_rootresolve.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_server.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_srvconnect.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_tap.cpython-36.pyc,,\r\ntwisted/names/test/__pycache__/test_util.cpython-36.pyc,,\r\ntwisted/names/test/test_cache.py,sha256=YNu7OeMpeNNFPJbzvE9a6OxDMybG_hU3xd466ZM_ztM,4916\r\ntwisted/names/test/test_client.py,sha256=nbfVm1Zep5DpKtXhKASpaqXDrH1NbsQwVYC6WcWN1wc,41764\r\ntwisted/names/test/test_common.py,sha256=3iP0IAmfWr-RKQdCmCKNvJw5k8U6DhII6BIN1zvOR7c,4206\r\ntwisted/names/test/test_dns.py,sha256=Y-8t2MAVHOijV_zNx_5aaNr4C8Ac0ALOrg7LGa7ppow,158849\r\ntwisted/names/test/test_examples.py,sha256=-VKU30q-Jkfw2ucz0so0hyyjrH1fJOpcKD1u7NcS6yY,5349\r\ntwisted/names/test/test_hosts.py,sha256=c5cs0ksd5N6s9qa0gxC-rnKd7baJVSiehvSB46EnlDg,8547\r\ntwisted/names/test/test_names.py,sha256=KLblh3uylJ30Fr8Ku83qOwoCKdIg8v9D9JkEN7lMUNE,43096\r\ntwisted/names/test/test_resolve.py,sha256=A3KYPzouCKlR5UOcUz0NATHYhey8QnVLL_398BXQaCo,1075\r\ntwisted/names/test/test_rfc1982.py,sha256=Ib4CocE0s8JAEqp_TvaZH6EjweB_QnrTuuDPmBEmkDo,13992\r\ntwisted/names/test/test_rootresolve.py,sha256=1Cp_QKpBToYSyjW8R3EdJRvbfbHcvvnVMwKeQyNAG8Q,25643\r\ntwisted/names/test/test_server.py,sha256=JQYGRbPoW6Hk5Sq9vsinlehP3KSToh2nRoZdVc3RSFA,41234\r\ntwisted/names/test/test_srvconnect.py,sha256=XSatW9AjCca_uL60AhXrPpOLlosV0AkW733r6kw-iVc,10124\r\ntwisted/names/test/test_tap.py,sha256=kLMsChF8IiCt5l0FQNZeVxoOIG7FlIupb17q6Ld3Q_U,4961\r\ntwisted/names/test/test_util.py,sha256=IGGlPKZ5Wn5L0A_Jj0MdN3_r_xghj_X4J0VLAqR8LTQ,3915\r\ntwisted/pair/__init__.py,sha256=69Cr0TdbaWqxKH2AEB9jxdRNydRnbWwx4kHzYlAFs7c,315\r\ntwisted/pair/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/pair/__pycache__/ethernet.cpython-36.pyc,,\r\ntwisted/pair/__pycache__/ip.cpython-36.pyc,,\r\ntwisted/pair/__pycache__/raw.cpython-36.pyc,,\r\ntwisted/pair/__pycache__/rawudp.cpython-36.pyc,,\r\ntwisted/pair/__pycache__/testing.cpython-36.pyc,,\r\ntwisted/pair/__pycache__/tuntap.cpython-36.pyc,,\r\ntwisted/pair/ethernet.py,sha256=ZKLmhJ9rqPsDVFFgcYqjtnyQf8gkGL-G7jnMNaXc2jo,1698\r\ntwisted/pair/ip.py,sha256=Kb5HfbLZ0wikbfIaKPLgGQHkPHcba5GlbGad3s5932k,2595\r\ntwisted/pair/raw.py,sha256=NJOSZ0D9qp78r3B_T9jivDozAGPaUagg8xtQOogtbAo,811\r\ntwisted/pair/rawudp.py,sha256=F67B2yZ0IqpW9bMNWk3-4gvQ1YtW9DZyBL6ZeWwzG8Q,1813\r\ntwisted/pair/test/__init__.py,sha256=mAc-2NR8lrqRyWN-YI4kn9LUZ7So6ae3xJ2RzldDQ1w,13\r\ntwisted/pair/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/pair/test/__pycache__/test_ethernet.cpython-36.pyc,,\r\ntwisted/pair/test/__pycache__/test_ip.cpython-36.pyc,,\r\ntwisted/pair/test/__pycache__/test_rawudp.cpython-36.pyc,,\r\ntwisted/pair/test/__pycache__/test_tuntap.cpython-36.pyc,,\r\ntwisted/pair/test/test_ethernet.py,sha256=iWxYX0e65w5Nq6r_cthyLSpAwvWjVW7AX-UVhfBpR_c,6653\r\ntwisted/pair/test/test_ip.py,sha256=euftwHEBKqvwaQQpta9jvKS5de49tz3oqtLC10p2xlg,15148\r\ntwisted/pair/test/test_rawudp.py,sha256=yze31pPb0eKWsfRUrHOFBIr6jC9tTgGvekw42Gk-T5M,13074\r\ntwisted/pair/test/test_tuntap.py,sha256=S2OTUrXwu1-ku_dEM6MHjmTlKpuRsajQuUgn9XJKnpo,47567\r\ntwisted/pair/testing.py,sha256=MZRPms9JY-FTQX8k91gND5MNd23Esz_RDLBLqNZodp0,17307\r\ntwisted/pair/tuntap.py,sha256=TxshMXYq2GYTWyxxjaNPpIPggigozJ0PFLkAnG-z8GA,12538\r\ntwisted/persisted/__init__.py,sha256=zyAGR02ZdUO8fNoKHf602wUApt3DvnnfD-B4iJ1QJqI,136\r\ntwisted/persisted/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/persisted/__pycache__/aot.cpython-36.pyc,,\r\ntwisted/persisted/__pycache__/crefutil.cpython-36.pyc,,\r\ntwisted/persisted/__pycache__/dirdbm.cpython-36.pyc,,\r\ntwisted/persisted/__pycache__/sob.cpython-36.pyc,,\r\ntwisted/persisted/__pycache__/styles.cpython-36.pyc,,\r\ntwisted/persisted/aot.py,sha256=9J-HHadGM8z7jDH37peHqP1WdgZ9roqmAnqycOeB-n8,18605\r\ntwisted/persisted/crefutil.py,sha256=Xp3-vK0OeOroNd2NJH1vJhiXUHsmBZ6_9r_uDK9FE8g,4375\r\ntwisted/persisted/dirdbm.py,sha256=JU8ZwO7ZF2lIhc6H-T6lCvAsgXxiydYc31JRkLqbj_8,10141\r\ntwisted/persisted/sob.py,sha256=-yhIm6Ah6UhGRTs3v6l6ZWHJMU8DorDuadg34YztWHs,5197\r\ntwisted/persisted/styles.py,sha256=wD9iJHv7hIH6GUTP9s5HuREfNzCA4yguaRHeWacFzc4,13495\r\ntwisted/persisted/test/__init__.py,sha256=C5rPf38HFfuGrl35BEIrhxgs9HtwoEMpxPvNdNHNELk,113\r\ntwisted/persisted/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/persisted/test/__pycache__/test_styles.cpython-36.pyc,,\r\ntwisted/persisted/test/test_styles.py,sha256=0s26icbUsYU1v4FLhTpxaT49vLuYDhr4Y6etvTru1JQ,3388\r\ntwisted/plugin.py,sha256=1ZW0wvUbQ0GYV0ry7JX2qu2LTH35b6WzfPRTG9HhwDo,8407\r\ntwisted/plugins/__init__.py,sha256=lk9vXST0ZZip_WzApTLgsFmWKA0SDJLHe5HyNBFDers,590\r\ntwisted/plugins/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/cred_anonymous.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/cred_file.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/cred_memory.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/cred_sshkeys.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/cred_unix.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/twisted_conch.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/twisted_core.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/twisted_ftp.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/twisted_inet.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/twisted_names.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/twisted_portforward.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/twisted_reactors.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/twisted_runner.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/twisted_socks.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/twisted_trial.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/twisted_web.cpython-36.pyc,,\r\ntwisted/plugins/__pycache__/twisted_words.cpython-36.pyc,,\r\ntwisted/plugins/cred_anonymous.py,sha256=vpl3-TdqBrPcPYEMnuDPcI0ZfWDmvxS6n0W6rt9dS-Q,1017\r\ntwisted/plugins/cred_file.py,sha256=EbDvh1Sgf5BcoTD5k9-sJey43wiJpJNmypHUVWD4TcA,1875\r\ntwisted/plugins/cred_memory.py,sha256=8rRWaV93xIOIY5sXnUCpFsvD2va0v_iqs3dDO7KAUp0,2387\r\ntwisted/plugins/cred_sshkeys.py,sha256=0bSoTYESFswyRdGxSsmr5q9LZs4JL0sAnAzXMeLeecc,1498\r\ntwisted/plugins/cred_unix.py,sha256=xUlXtGd6RPEpWrO5J1cB6Cw6URJ1cSEtdcq1Xe5vBYc,5905\r\ntwisted/plugins/twisted_conch.py,sha256=5uZ8DxMkL9ZoajHKqTCxOGEMarZIeomKgfY9JfGA2LA,519\r\ntwisted/plugins/twisted_core.py,sha256=UYnNWMLp3tMpbWjzQYDNYGyQeO6CKhrum7-Qo_wUnos,589\r\ntwisted/plugins/twisted_ftp.py,sha256=2YITyfTb3iAUnJoEfMCh0jVjnGjO6O_nHR_SAS4auGs,229\r\ntwisted/plugins/twisted_inet.py,sha256=VBtuyAPilMxsjykF4rVLyGgtr0R_Q3dXB8E-SBFztVk,260\r\ntwisted/plugins/twisted_names.py,sha256=8dMOvdQzlVu6etrsLKGFcj4LJlbg9N2FFqzTZais7bg,247\r\ntwisted/plugins/twisted_portforward.py,sha256=f3tDxoFwoJV0BfW8b1jXrYjr72GQIKcgGykaxkUBcpg,275\r\ntwisted/plugins/twisted_reactors.py,sha256=bZjUWLDKFMRW5kReCWCyPTb6zYiPCSyZ4_dJJ0vgTH0,1880\r\ntwisted/plugins/twisted_runner.py,sha256=4onfqhfRsx2XnBn7c4bWt8dxMmQyrpALUYeB9ZZ20EQ,278\r\ntwisted/plugins/twisted_socks.py,sha256=M8G4xLBbk3S-klsY0HNwWIA2xXhy4VQpjsLRM_bIvLE,247\r\ntwisted/plugins/twisted_trial.py,sha256=hpii1iu8KvcTz6basUtpz0VfZ3b6TLCINYpLjy2l78I,2084\r\ntwisted/plugins/twisted_web.py,sha256=ef7vqQPmVigdoowgJWR3zAwgPs9ANV9ezC5cEQOuaQc,312\r\ntwisted/plugins/twisted_words.py,sha256=Qf1p7QsLjl0uqGAm-MvricGjyZE-Ceq3PqjwwrJokYo,1029\r\ntwisted/positioning/__init__.py,sha256=y_fhSJlC3z4GeB-rC3z2tiprb3JxxGvlYv-GHmuhv1Q,223\r\ntwisted/positioning/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/positioning/__pycache__/_sentence.cpython-36.pyc,,\r\ntwisted/positioning/__pycache__/base.cpython-36.pyc,,\r\ntwisted/positioning/__pycache__/ipositioning.cpython-36.pyc,,\r\ntwisted/positioning/__pycache__/nmea.cpython-36.pyc,,\r\ntwisted/positioning/_sentence.py,sha256=G8vKaSb_8T-khzyGeeDht6PWtQYugU4_kQr4-VdET8A,4004\r\ntwisted/positioning/base.py,sha256=H83JCeCxX0V3GGN0sEyHiEDeuM1GyDOMAgf6ngnl4LQ,28410\r\ntwisted/positioning/ipositioning.py,sha256=hxGOOrFK0Hqj0gvNA5lTU0J6sbQr-zN4ErVh8gRnffA,3013\r\ntwisted/positioning/nmea.py,sha256=1rcMypYwWD6A468USl9lbOb80Qxla6_VVsSTTOqXPyY,35975\r\ntwisted/positioning/test/__init__.py,sha256=Ekrh30kyy4hMgeFG33jFNP-S209JCflSF7hTan4MKEo,125\r\ntwisted/positioning/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/positioning/test/__pycache__/receiver.cpython-36.pyc,,\r\ntwisted/positioning/test/__pycache__/test_base.cpython-36.pyc,,\r\ntwisted/positioning/test/__pycache__/test_nmea.cpython-36.pyc,,\r\ntwisted/positioning/test/__pycache__/test_sentence.cpython-36.pyc,,\r\ntwisted/positioning/test/receiver.py,sha256=eLkfrggQVEPHfpB12vC1E8T3oud5tvAYK4gEejC4wjE,1166\r\ntwisted/positioning/test/test_base.py,sha256=FbsYzs122PkztgjDKxCb44Lb626UAqOyJBwwLXQjn6g,28897\r\ntwisted/positioning/test/test_nmea.py,sha256=mTs_PNwZv-DmMJC_QIibP_kbSazNXl2DY14BaheHKAw,39925\r\ntwisted/positioning/test/test_sentence.py,sha256=REOT5BUY-vUz_FEbmWrapgel9-dmcH41fIpeNo4peJE,4770\r\ntwisted/protocols/__init__.py,sha256=11Pa7Emr3WMc3VvzbjfrTydeVl4rpQJ587BWXZD125w,391\r\ntwisted/protocols/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/amp.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/basic.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/dict.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/finger.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/ftp.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/htb.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/ident.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/loopback.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/memcache.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/pcp.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/policies.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/portforward.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/postfix.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/sip.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/socks.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/stateful.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/tls.cpython-36.pyc,,\r\ntwisted/protocols/__pycache__/wire.cpython-36.pyc,,\r\ntwisted/protocols/amp.py,sha256=y_Nvxa4lOQpx3D3qrWIB_XkY3AiMCG7OQPSm5lBwI1Y,97898\r\ntwisted/protocols/basic.py,sha256=aJGgFcI8hRVuqcXJrp5aPCgUx-U73SKUYhOSprEK4LQ,32061\r\ntwisted/protocols/dict.py,sha256=osi8Fjn7QALiRTtuFyDdZymRtdjxceO5CxwIaQBeqSk,10762\r\ntwisted/protocols/finger.py,sha256=MHoysns-8Wi3QfrZNIvoUQVyASQSzx-t3GzjYp9MPK0,1220\r\ntwisted/protocols/ftp.py,sha256=DzUEKyf9NmVXtOrzOZbV0IPkpR96WSvcRRW1REM8CEk,106132\r\ntwisted/protocols/haproxy/__init__.py,sha256=TyD3qy2qDa2p6zw0Q3DkPeWS5ChiAEzX0JZfAfFdtYg,251\r\ntwisted/protocols/haproxy/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/__pycache__/_exceptions.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/__pycache__/_info.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/__pycache__/_interfaces.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/__pycache__/_parser.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/__pycache__/_v1parser.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/__pycache__/_v2parser.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/__pycache__/_wrapper.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/_exceptions.py,sha256=SW9Zeft6X9W2HtPY9Mfh2AIbQVuoX8UNs7l4eOz0Izo,1085\r\ntwisted/protocols/haproxy/_info.py,sha256=OB180dloGeTnpjxeVBObB6P-e3VU223ZK4ImHsBNvZM,929\r\ntwisted/protocols/haproxy/_interfaces.py,sha256=bDsfV4TKelDi5vW_dig0vmh8grcM7R6KZJrb7kTnlO0,1794\r\ntwisted/protocols/haproxy/_parser.py,sha256=AT7MMzwMx8kaMbVjDjLiJSt8MiuzApbwu7LFn5vxTOI,2051\r\ntwisted/protocols/haproxy/_v1parser.py,sha256=LAM2OeeV-vC5b85ohEPk1mcUnqMOQJgnUvA0NF7kUKk,4326\r\ntwisted/protocols/haproxy/_v2parser.py,sha256=JkSl8VWd7YMw5V6JNJ6LhunnWf_DVl_jde6isu7_VF4,6307\r\ntwisted/protocols/haproxy/_wrapper.py,sha256=4lA_nXL-pdzgXJ_5DXPwrnqvfOSC9gWLuovOdlMJ6jA,3323\r\ntwisted/protocols/haproxy/test/__init__.py,sha256=gxu5b7Qz4fM2tMbIm4VeUfMY4NthR3rzZlnX1VO_JUU,183\r\ntwisted/protocols/haproxy/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/test/__pycache__/test_parser.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/test/__pycache__/test_v1parser.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/test/__pycache__/test_v2parser.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/test/__pycache__/test_wrapper.cpython-36.pyc,,\r\ntwisted/protocols/haproxy/test/test_parser.py,sha256=k7RipRqyta7A4XySeBDQQrNBTqWO3nMr7ZgTgHpYLy4,3467\r\ntwisted/protocols/haproxy/test/test_v1parser.py,sha256=4hUm8u_vbAwPrrdRouAN1bDephjikVn5yFrB3e6b1H8,4694\r\ntwisted/protocols/haproxy/test/test_v2parser.py,sha256=PuyYjAYyLho-M8iOU1znggWjEvowhFTFVemblipH-EE,11777\r\ntwisted/protocols/haproxy/test/test_wrapper.py,sha256=8vRib0ifsoeAeeefQN0y5r0lo0_sTEMpoMzKUx6W4c4,13035\r\ntwisted/protocols/htb.py,sha256=NAiAptbEWvk46eDOlvLi1NjDfgkhSAFzNdS46mPjqsM,9327\r\ntwisted/protocols/ident.py,sha256=KV78Gj7IguHGpsOzEgkgIFPAqaiUNlXoiRSGBUChZcc,7781\r\ntwisted/protocols/loopback.py,sha256=xRPWLdrukRJth5yp8TWXspLofVR_HApqfk65pE7UJ4s,11928\r\ntwisted/protocols/memcache.py,sha256=98KnhDWuVDj_FBiNiM5MAsQrQg6xCrjkIko_rxqigTM,23693\r\ntwisted/protocols/pcp.py,sha256=sZWqAcibTFdsZnep-2Ml9lZwtT86z8FL6QCr-UH7-eU,7088\r\ntwisted/protocols/policies.py,sha256=SIp1MDpyhZTf7296XGiJHP_OC2WmMFS0G3Dwo9wOWl8,21327\r\ntwisted/protocols/portforward.py,sha256=Ob19TUzNKwq5OACeTBe35ZthfaGtu0o96gAbGBMGTNo,2383\r\ntwisted/protocols/postfix.py,sha256=2erA8Ap2nKF9W6t25TXk3ozG9wsW7ynDcjkN5BLwFQE,3953\r\ntwisted/protocols/sip.py,sha256=BSc-8qrcrx7gpz0Ku1vqX_wkdrZssi9huD1nDVEsoWs,37794\r\ntwisted/protocols/socks.py,sha256=kYGCYSO_K4YcSW3eG2iij9qye45-sokhMHz6h5gSejw,7816\r\ntwisted/protocols/stateful.py,sha256=6r-k3nLKMIa4M_9x1NRn5LWJ2BUPrn4jRh1TP8Jqltw,1640\r\ntwisted/protocols/test/__init__.py,sha256=QMkwFc9QOiSDp4ZU06wLjPDi3iw0y3ysUgdjOPceMu0,118\r\ntwisted/protocols/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/protocols/test/__pycache__/test_basic.cpython-36.pyc,,\r\ntwisted/protocols/test/__pycache__/test_tls.cpython-36.pyc,,\r\ntwisted/protocols/test/test_basic.py,sha256=2LqruAhTDMjhjP_afc018EQ2SwxmeBY6KXjS0KMBhZY,43214\r\ntwisted/protocols/test/test_tls.py,sha256=zSTdoAeXZEyNBM8yuMD07rBJSgGsoPJFjdCp7WQ_dyA,75552\r\ntwisted/protocols/tls.py,sha256=GmaSZCckJRo1W-winsYwf_uHfOeg-2wl1CveH5PgEWU,32620\r\ntwisted/protocols/wire.py,sha256=47h5tn358eT-T_c-QULiRm8CavhH74TxdLFKx-B1mUg,2556\r\ntwisted/python/__init__.py,sha256=59IqUE-1fknNPjKnfvC46EWCIdUeqEcUxAofVFiPSSU,674\r\ntwisted/python/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/python/__pycache__/_appdirs.cpython-36.pyc,,\r\ntwisted/python/__pycache__/_inotify.cpython-36.pyc,,\r\ntwisted/python/__pycache__/_oldstyle.cpython-36.pyc,,\r\ntwisted/python/__pycache__/_release.cpython-36.pyc,,\r\ntwisted/python/__pycache__/_setup.cpython-36.pyc,,\r\ntwisted/python/__pycache__/_shellcomp.cpython-36.pyc,,\r\ntwisted/python/__pycache__/_textattributes.cpython-36.pyc,,\r\ntwisted/python/__pycache__/_tzhelper.cpython-36.pyc,,\r\ntwisted/python/__pycache__/_url.cpython-36.pyc,,\r\ntwisted/python/__pycache__/compat.cpython-36.pyc,,\r\ntwisted/python/__pycache__/components.cpython-36.pyc,,\r\ntwisted/python/__pycache__/constants.cpython-36.pyc,,\r\ntwisted/python/__pycache__/context.cpython-36.pyc,,\r\ntwisted/python/__pycache__/deprecate.cpython-36.pyc,,\r\ntwisted/python/__pycache__/failure.cpython-36.pyc,,\r\ntwisted/python/__pycache__/fakepwd.cpython-36.pyc,,\r\ntwisted/python/__pycache__/filepath.cpython-36.pyc,,\r\ntwisted/python/__pycache__/formmethod.cpython-36.pyc,,\r\ntwisted/python/__pycache__/htmlizer.cpython-36.pyc,,\r\ntwisted/python/__pycache__/lockfile.cpython-36.pyc,,\r\ntwisted/python/__pycache__/log.cpython-36.pyc,,\r\ntwisted/python/__pycache__/logfile.cpython-36.pyc,,\r\ntwisted/python/__pycache__/modules.cpython-36.pyc,,\r\ntwisted/python/__pycache__/monkey.cpython-36.pyc,,\r\ntwisted/python/__pycache__/procutils.cpython-36.pyc,,\r\ntwisted/python/__pycache__/randbytes.cpython-36.pyc,,\r\ntwisted/python/__pycache__/rebuild.cpython-36.pyc,,\r\ntwisted/python/__pycache__/reflect.cpython-36.pyc,,\r\ntwisted/python/__pycache__/release.cpython-36.pyc,,\r\ntwisted/python/__pycache__/roots.cpython-36.pyc,,\r\ntwisted/python/__pycache__/runtime.cpython-36.pyc,,\r\ntwisted/python/__pycache__/sendmsg.cpython-36.pyc,,\r\ntwisted/python/__pycache__/shortcut.cpython-36.pyc,,\r\ntwisted/python/__pycache__/syslog.cpython-36.pyc,,\r\ntwisted/python/__pycache__/systemd.cpython-36.pyc,,\r\ntwisted/python/__pycache__/text.cpython-36.pyc,,\r\ntwisted/python/__pycache__/threadable.cpython-36.pyc,,\r\ntwisted/python/__pycache__/threadpool.cpython-36.pyc,,\r\ntwisted/python/__pycache__/url.cpython-36.pyc,,\r\ntwisted/python/__pycache__/urlpath.cpython-36.pyc,,\r\ntwisted/python/__pycache__/usage.cpython-36.pyc,,\r\ntwisted/python/__pycache__/util.cpython-36.pyc,,\r\ntwisted/python/__pycache__/versions.cpython-36.pyc,,\r\ntwisted/python/__pycache__/win32.cpython-36.pyc,,\r\ntwisted/python/__pycache__/zippath.cpython-36.pyc,,\r\ntwisted/python/__pycache__/zipstream.cpython-36.pyc,,\r\ntwisted/python/_appdirs.py,sha256=bw_i8btCVr-TH62QlcP-Gdt5v6R0hoCaiZyYk2ZvVxA,788\r\ntwisted/python/_inotify.py,sha256=aYbn1L_5MM62Gl60GzlkiwOHTc6mB0lUCr1tP-FsgPU,3455\r\ntwisted/python/_oldstyle.py,sha256=ksosHBxHm691H3HwaR1ORGMNC-7q2U-IwTMpcxqugZ0,2593\r\ntwisted/python/_pydoctortemplates/common.html,sha256=KxdAlEXi-ihLekHIh0t1VGHIRNv1QzOHLdU7F3jtuTY,3341\r\ntwisted/python/_pydoctortemplates/index.html,sha256=JecyxRLyBd8Z45KbYD_rQeTeRizrXIjlNslU3uLppjM,3565\r\ntwisted/python/_pydoctortemplates/summary.html,sha256=E_LjXUI4vwx8G7_5ZwAd6LndTeYxUTCrjGUOMiUtu1Y,1980\r\ntwisted/python/_release.py,sha256=xqUE9jUSx0rKKI00hFYfz7NXA8h7b9orFpWZODYRJek,18550\r\ntwisted/python/_setup.py,sha256=0qYzsSph8fvBU-XmVsCi6tTEz41Z2eva_N25E_1c78Q,14352\r\ntwisted/python/_shellcomp.py,sha256=9mb_W8t3VkpejPSNWyrkiT5fGLdTc4V6mi3uvS7Ej7k,24830\r\ntwisted/python/_textattributes.py,sha256=5HDokoRNMdRKmmKh1yrdymoOE7qTWkeNPOm8tOUePx8,9079\r\ntwisted/python/_tzhelper.py,sha256=YFN_nX1P-QvHzMUKKXcA9eQsUf2n9MHYr2lIecLqy70,3192\r\ntwisted/python/_url.py,sha256=7-vSoeXo3oMd6xDG3GvsDb7BXpRx8tnAc6HpPUk9zLQ,253\r\ntwisted/python/compat.py,sha256=NJEtYTaa_LA3j85-TkfyusjkRgk28CqpBy_3aDCvI0k,22907\r\ntwisted/python/components.py,sha256=jf9hOzQqetZfpDgBMELxCPdM6S8ALQYpBV-a2rVK4uc,14242\r\ntwisted/python/constants.py,sha256=GuTBebugkgjf4CkvJaOxy3GLYrV72Ftz_IFexC6dn2Y,544\r\ntwisted/python/context.py,sha256=2mPa-VtpamaSkfz5433svgisrVaT7mKPhQVgQ1i0SZY,4024\r\ntwisted/python/deprecate.py,sha256=EfkGx7d9K0st0vrsiNcvOIaD5_C2fQa8aWZbBCCloXI,26948\r\ntwisted/python/failure.py,sha256=2KBV5GN7gy-umIdziF1Mri_JCLlr6sL9fzx7Exp13i4,27564\r\ntwisted/python/fakepwd.py,sha256=26yDkt13tXXNTGv2Ua3qQ2t_0FJy0sesVge86O8ulAc,6138\r\ntwisted/python/filepath.py,sha256=rtd9HVtB_NZOWq3K2iZpaCw6_R-mjVlouVV6WylGljw,58887\r\ntwisted/python/formmethod.py,sha256=xpgE8EVYQQ_bgWySJp74ZT4ecY1SBL1hY4t5Oz_pDLg,11460\r\ntwisted/python/htmlizer.py,sha256=x91-QwzLlcF8Zfw3vG8NzzCabm7SF4m8EARO1v9llDI,3541\r\ntwisted/python/lockfile.py,sha256=ZgEOdSPnK3RFXTPz9cuvieQrp2uNvGV2bow8qiqSLmE,7718\r\ntwisted/python/log.py,sha256=etGKoolsiXr__IGZN9SG8YMd-JS3hMFIpphvvIRfNak,22472\r\ntwisted/python/logfile.py,sha256=TNbhiOp692oNKnQ9SCBz3oJAlfgbIYk1R6cnYFEYWRY,10083\r\ntwisted/python/modules.py,sha256=Zret5tlILxKbI05x4Rw_b0Qw0pBxcYIMn0ssSGQLaAs,27141\r\ntwisted/python/monkey.py,sha256=dTtT6kIz1vvSmIOUKOGGGlRAmpWS9UCzRGyc09hZHmE,2227\r\ntwisted/python/procutils.py,sha256=lkI5rWeD1iNyKsp9_L0XI8Lm3I4o7W6AzsiwdoFfLDU,1419\r\ntwisted/python/randbytes.py,sha256=dpPatxms22rgQwoLzuPYGWbWJc1ogVOyUrB_eAW1Fjs,3959\r\ntwisted/python/rebuild.py,sha256=9ro6DKmvmfQzMs7RKn3Tho2kL1pjmyyAwI1Rpm8mb2k,9268\r\ntwisted/python/reflect.py,sha256=ul_gpPzj1JhozrflHEW4UdRwysBtUd_N1fjSn8Wsn84,19477\r\ntwisted/python/release.py,sha256=fOCKs0fEKqLZduuDuBijZ0MDIkGEWliJApxEaAYlkEk,1192\r\ntwisted/python/roots.py,sha256=P98gPe16GCettjsnJCNPKAyeBJTyJOkvIKDx1-JMRu4,7404\r\ntwisted/python/runtime.py,sha256=XnzEnaDzX01aFGd-T-hw7sqP_yh30m56ttPALWNB9Fo,6216\r\ntwisted/python/sendmsg.py,sha256=V9Sxc2I2OI6iXS9Fy1GYR__nH8MiWEkLcxlhO6B3m24,3420\r\ntwisted/python/shortcut.py,sha256=HIlHg7G7u9jMhC09DrLPOv8zNnvF4wkz2AjBL-GKrn8,2253\r\ntwisted/python/syslog.py,sha256=Cu67zZN15N21NESUvs9RFQ4yQTdTzzn0ZTikKEhVDjA,3730\r\ntwisted/python/systemd.py,sha256=onsuaC2aPtrUS3DNeHMdoclD3v79vcm4jFmDU_pqBGE,2834\r\ntwisted/python/test/__init__.py,sha256=V0srj7fq1Y17ZVfFgUc0n5ueVkK0InJNIT90pWlEKLI,42\r\ntwisted/python/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/deprecatedattributes.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/modules_helpers.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/pullpipe.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_appdirs.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_components.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_constants.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_deprecate.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_dist3.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_fakepwd.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_htmlizer.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_inotify.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_release.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_runtime.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_sendmsg.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_setup.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_shellcomp.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_syslog.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_systemd.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_textattributes.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_tzhelper.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_url.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_urlpath.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_util.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_versions.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_zippath.cpython-36.pyc,,\r\ntwisted/python/test/__pycache__/test_zipstream.cpython-36.pyc,,\r\ntwisted/python/test/_deprecatetests.py.3only,sha256=qSX82XTcTBq4SpzmvjFlf-fK64geLp0spny-mRM_Kms,1814\r\ntwisted/python/test/deprecatedattributes.py,sha256=oTFSMS8Xi6q4JUgh5nUlBsmH3WrPkANJcKkI8plLJ94,571\r\ntwisted/python/test/modules_helpers.py,sha256=Ugs47h2kBaWydzLUHEYJx5lBf2a4vvpZuPAU3qaH4Sc,1605\r\ntwisted/python/test/pullpipe.py,sha256=hyX-tJuVuAo3QK76Q4Z0-Ots3Jo8ia3-9HWUPexlnuM,1220\r\ntwisted/python/test/test_appdirs.py,sha256=IpWQQKEiFNFnZahLWJZvHmM3dr1RKA_JERpbNLh3wLY,1081\r\ntwisted/python/test/test_components.py,sha256=HNKATjfPnL5lIxVS1wCBGTIb4NYFPkZzo05xNpJLRY8,25974\r\ntwisted/python/test/test_constants.py,sha256=_k490Ijg6HpYx_jHTjSedSD555Ujz0FHbrvLV1xNuYs,38117\r\ntwisted/python/test/test_deprecate.py,sha256=_xNUpOwd8TAbTC39m_wVEmQrSU3DaBfDoyVb40RLoDY,38930\r\ntwisted/python/test/test_dist3.py,sha256=QoIwlgUmeEtwcfbp2BLpqIiqub97v2fAHLw77BEYKbE,1858\r\ntwisted/python/test/test_fakepwd.py,sha256=2ulp3433yk5zIYcmb96ZUd2VXc8X-Q07xGdC54_OLyQ,14107\r\ntwisted/python/test/test_htmlizer.py,sha256=mA0YLFeplomK31oADOCo8-woa8ALbgfEu1FVLGSmLGw,1266\r\ntwisted/python/test/test_inotify.py,sha256=TPSjt9OPRp4hyEk05ZUl4281yuUI_etJ5LETjEMXz6s,3639\r\ntwisted/python/test/test_release.py,sha256=sLrfF-SJYRnjwiwGtbBVICaRniIh8Q_7TB612gPm9wg,41046\r\ntwisted/python/test/test_runtime.py,sha256=W3p_U-4eBEWYb2pQPfFEelUoHP-j9H-whEYbvgZtRKo,7926\r\ntwisted/python/test/test_sendmsg.py,sha256=gmm-zG0rRwfTuy8ozGJ7xeBhDSCJezjyAHyf8djNm1s,25233\r\ntwisted/python/test/test_setup.py,sha256=EXT8DjgyTqS5_ecN150HzZi7eMGJQHLCihwwxbzA6cE,13699\r\ntwisted/python/test/test_shellcomp.py,sha256=6mHTIncdngMe5Nm42x9_oXH-H-O4BO7g3QzwdiwHQ18,21809\r\ntwisted/python/test/test_syslog.py,sha256=2f2Ik8tLD89X905NtsKczHQNw4ssMd9sDmwpI5WTZEA,4948\r\ntwisted/python/test/test_systemd.py,sha256=lC5l4suhb6cQGnXlcxUyx5ZR7MUAAq0Zrci-f9pneCs,6401\r\ntwisted/python/test/test_textattributes.py,sha256=3tIa0LITcWGQraaeuu1S3Ai1v8rnGiNnRYnpRuDvBUE,712\r\ntwisted/python/test/test_tzhelper.py,sha256=qbJVrzd42-2SmiGTXBbDYbLLuSD1i1F4IkbLuT2X124,3984\r\ntwisted/python/test/test_url.py,sha256=mwDdEvACowrPyxYNPqCR_b32s93sN7DzvpR73SqEMZM,29313\r\ntwisted/python/test/test_urlpath.py,sha256=j7qCw-4PNgHeoYmIplna8zzt5EvrnluRFH8wf0d14Gs,10328\r\ntwisted/python/test/test_util.py,sha256=x5clz1UK59zQ1pETP-mKj5L2S8WUYRUjnieY1q-jl6k,36460\r\ntwisted/python/test/test_versions.py,sha256=xCTFjXPc8r6DujRCDzavd9qkzL1hwzcxwyDcT5fOAS8,5400\r\ntwisted/python/test/test_zippath.py,sha256=LRDWmsm8shSxYiw2QOs4NFjXFef1hsCUIzxmOhCn0f0,3474\r\ntwisted/python/test/test_zipstream.py,sha256=ai-XdQAlvQ6uUAmm5ikIjIpj7WU4KhWTj50tgbN_lRg,12308\r\ntwisted/python/text.py,sha256=bI7CKqBudIqueU7lduVKsQqzTZipPdSoZoa0lR9IklI,5482\r\ntwisted/python/threadable.py,sha256=yx-911e3S7loq9svlCLbqrFtLbATJd-IrXtFyC1FzKI,3297\r\ntwisted/python/threadpool.py,sha256=SfnPhHyfbfzB8IBu2p_qyHbA5PKqfEesMhNBKqz0ctQ,9840\r\ntwisted/python/twisted-completion.zsh,sha256=DkNZis_hXXFAxUutigSn6gDRk8i70ylRrJ7ZBy-8NZo,1371\r\ntwisted/python/url.py,sha256=0vJfs6hgMrWkIR2ZgovyPASQlYHh2afVCFaQaGSLA2c,244\r\ntwisted/python/urlpath.py,sha256=GV2oT4B_QwtKVOfKjOZC5J_bIxVzblHGtP7-2aCqxXk,9084\r\ntwisted/python/usage.py,sha256=PmukwnG15RZjJwCwX4Z5moDUShWKwBVHwj1jocLVDZY,35002\r\ntwisted/python/util.py,sha256=4Pz0IZzKDqY9UFwqb-RU4HJoCUgrAO_h2-sLBMNR58o,27931\r\ntwisted/python/versions.py,sha256=VV-6OHSdnxuUPrfZ0tfb1kIxwU_nIIUA8Isedy1wYxc,322\r\ntwisted/python/win32.py,sha256=i2e7daTFnZVYWpmGjlPBH97IsXQKm5kiwX7Zy1vY2S4,4317\r\ntwisted/python/zippath.py,sha256=3iNAMvf_shM4KMaIHttR5HsBawMmHJy_h1z0emsvGPQ,9237\r\ntwisted/python/zipstream.py,sha256=yZb1fdWj1YHXrK9_sG4auyiQbZYrZsf2tsbTE65fT08,9757\r\ntwisted/runner/__init__.py,sha256=ahzGC9cYnSf0DSsEzBgV1oK-AyD_jb3jvVfEZA6mJZ0,124\r\ntwisted/runner/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/runner/__pycache__/inetd.cpython-36.pyc,,\r\ntwisted/runner/__pycache__/inetdconf.cpython-36.pyc,,\r\ntwisted/runner/__pycache__/inetdtap.cpython-36.pyc,,\r\ntwisted/runner/__pycache__/procmon.cpython-36.pyc,,\r\ntwisted/runner/__pycache__/procmontap.cpython-36.pyc,,\r\ntwisted/runner/inetd.py,sha256=EHkgH-8dYHD75CUaby9dkui4zGFToR6HhOpOxd5c7os,1962\r\ntwisted/runner/inetdconf.py,sha256=hHz7QpqQGJtg5YQ2KRj_IdmfmasiYnvw4ZXK4nRy98w,4917\r\ntwisted/runner/inetdtap.py,sha256=3EfntNfqiEBApmNjyXv10v9DZ0u4pk8EUbaf2hPEbX8,3558\r\ntwisted/runner/procmon.py,sha256=e7Rr8ANff3jDDirWYHQxTGm_F5sH24eKQBRZRulrkjg,12675\r\ntwisted/runner/procmontap.py,sha256=3S6LdXV2qIzUrWyNvHlk8ZMpc2Pri79PXjBIB0p6oEw,2298\r\ntwisted/runner/test/__init__.py,sha256=tjveH1kCFEM9rVaT_bsWV8TURsUKAgqn9p3zHZdDK40,114\r\ntwisted/runner/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/runner/test/__pycache__/test_inetdconf.cpython-36.pyc,,\r\ntwisted/runner/test/__pycache__/test_procmon.cpython-36.pyc,,\r\ntwisted/runner/test/__pycache__/test_procmontap.cpython-36.pyc,,\r\ntwisted/runner/test/test_inetdconf.py,sha256=r-HcBqvSvDbqcyc6viHoBdCfLrP0Pqm-ptALYU-kjFU,1785\r\ntwisted/runner/test/test_procmon.py,sha256=juFE0_OW7YLTIr9Ohe35EK84T7NVB0NXGrz4UsuqWNg,23346\r\ntwisted/runner/test/test_procmontap.py,sha256=f237F_JUHlqJQ0IDXoVBB9C_Qu2FZHJGTGOduSXWyNM,2520\r\ntwisted/scripts/__init__.py,sha256=TSubMCp4NhcXtFvbrOT9boiIzXpbSvATakl3yGBQwQY,261\r\ntwisted/scripts/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/scripts/__pycache__/_twistd_unix.cpython-36.pyc,,\r\ntwisted/scripts/__pycache__/_twistw.cpython-36.pyc,,\r\ntwisted/scripts/__pycache__/htmlizer.cpython-36.pyc,,\r\ntwisted/scripts/__pycache__/trial.cpython-36.pyc,,\r\ntwisted/scripts/__pycache__/twistd.cpython-36.pyc,,\r\ntwisted/scripts/_twistd_unix.py,sha256=oxV8dzXcxZe-kwzQLUoBT9TFrOSUmnJnaQvqh0ZL0q4,16380\r\ntwisted/scripts/_twistw.py,sha256=DR_MP8Ij2fqlYNTACS384RPuNHdOdIhrHsO0mDfUJG0,1562\r\ntwisted/scripts/htmlizer.py,sha256=HSlaUZZ5O7Lxnay2tNm-eFq6sqh7pKhvysixJdyGY_s,1868\r\ntwisted/scripts/test/__init__.py,sha256=p8A4Q5FXoU8Mch55_ANwPbv5-vTZikEVox_gvZELTHg,118\r\ntwisted/scripts/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/scripts/test/__pycache__/test_scripts.cpython-36.pyc,,\r\ntwisted/scripts/test/test_scripts.py,sha256=zsK4xm834A3KBsx6qUlbjfNWOiqw4iK1AmY4Ktf7dzg,4880\r\ntwisted/scripts/trial.py,sha256=vlKgrnUIuBmmMB5uAQjv1MYUARKc5EF54bVfQ-XDggY,21132\r\ntwisted/scripts/twistd.py,sha256=1UX9uFucre3pMc5VqLD-QrIfNbLgkF8FQ_Swr0D2wn4,867\r\ntwisted/spread/__init__.py,sha256=gfxmcnrYlpVRF5hdBZ3WUCItFEAc6DNSQw6D8e_f3RE,159\r\ntwisted/spread/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/spread/__pycache__/banana.cpython-36.pyc,,\r\ntwisted/spread/__pycache__/flavors.cpython-36.pyc,,\r\ntwisted/spread/__pycache__/interfaces.cpython-36.pyc,,\r\ntwisted/spread/__pycache__/jelly.cpython-36.pyc,,\r\ntwisted/spread/__pycache__/pb.cpython-36.pyc,,\r\ntwisted/spread/__pycache__/publish.cpython-36.pyc,,\r\ntwisted/spread/__pycache__/util.cpython-36.pyc,,\r\ntwisted/spread/banana.py,sha256=ofAgyONvTiJ5H5AaGhLxK8mnAo-6u7sgo00KqwMrxGY,12334\r\ntwisted/spread/flavors.py,sha256=n2_9c16yhkbpDAk6SkbN6UBVmmQ4_QU2YeUkIW_WgAQ,23455\r\ntwisted/spread/interfaces.py,sha256=A7UjlK03QoQ5KnPMUkvlpSnYqe5pdt7hUKv6MTLWa30,686\r\ntwisted/spread/jelly.py,sha256=aCq16IuReZ7btYNcO2zBGHZwfUDqWJ3YY0AEdmPVMwU,36468\r\ntwisted/spread/pb.py,sha256=BUR4Cf3snqevg95aH3yri__uN1cda5K2WNGeman8ZoU,52385\r\ntwisted/spread/publish.py,sha256=G4n2VvafpTtx7S8eEZtHC8s6naDBdwmLWNG4itifat8,4480\r\ntwisted/spread/test/__init__.py,sha256=67HyXbsJ4DIBtcMcUWJqGMHdQc2Z-NLinUz2MVUEplI,110\r\ntwisted/spread/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/spread/test/__pycache__/test_banana.cpython-36.pyc,,\r\ntwisted/spread/test/__pycache__/test_jelly.cpython-36.pyc,,\r\ntwisted/spread/test/__pycache__/test_pb.cpython-36.pyc,,\r\ntwisted/spread/test/__pycache__/test_pbfailure.cpython-36.pyc,,\r\ntwisted/spread/test/test_banana.py,sha256=wV0I1JtZvg1VJZEZVPvfFEUQYSNS2eL-irtqarZyb_k,15456\r\ntwisted/spread/test/test_jelly.py,sha256=tVs3Ph0cGjO6lU9uqqe6qHTVASoUuPhi5N2Oa1FwFP8,19990\r\ntwisted/spread/test/test_pb.py,sha256=dy7mom3-TD89U_qz2NdnC1RTfwBwA4glz4QwvXxniuw,63874\r\ntwisted/spread/test/test_pbfailure.py,sha256=292uqxxnW0nLSWfubBnW3INJWksGImoECepvAC_h554,15433\r\ntwisted/spread/util.py,sha256=OWm_8dRgzKEvGVWxutxhdWOkupoc1sLj0FSuwX8JW1w,6387\r\ntwisted/tap/__init__.py,sha256=cWvA7ICrsBPoK11cax2E9a3OhvuDMYXRBvj_7tKXMDI,162\r\ntwisted/tap/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/tap/__pycache__/ftp.cpython-36.pyc,,\r\ntwisted/tap/__pycache__/portforward.cpython-36.pyc,,\r\ntwisted/tap/__pycache__/socks.cpython-36.pyc,,\r\ntwisted/tap/ftp.py,sha256=JmF1-GN5eoEYen773DBg0_-hSyHnFE94q1XrsG1Lz9Y,2002\r\ntwisted/tap/portforward.py,sha256=ZMY42wPvX5yfi1A3Ug_XLEOM7F5-UWhgzq2nY2WVNa8,795\r\ntwisted/tap/socks.py,sha256=uF0OnqGl16jcW6vtT7BvRImqsxSZPeJ8GPnUCoKghrc,1292\r\ntwisted/test/__init__.py,sha256=P8kgU78nKls3dRPDEW7-PYoYrm2J_hYMiYB6eJUHNbI,477\r\ntwisted/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/test/__pycache__/crash_test_dummy.cpython-36.pyc,,\r\ntwisted/test/__pycache__/iosim.cpython-36.pyc,,\r\ntwisted/test/__pycache__/mock_win32process.cpython-36.pyc,,\r\ntwisted/test/__pycache__/myrebuilder1.cpython-36.pyc,,\r\ntwisted/test/__pycache__/myrebuilder2.cpython-36.pyc,,\r\ntwisted/test/__pycache__/plugin_basic.cpython-36.pyc,,\r\ntwisted/test/__pycache__/plugin_extra1.cpython-36.pyc,,\r\ntwisted/test/__pycache__/plugin_extra2.cpython-36.pyc,,\r\ntwisted/test/__pycache__/process_cmdline.cpython-36.pyc,,\r\ntwisted/test/__pycache__/process_echoer.cpython-36.pyc,,\r\ntwisted/test/__pycache__/process_fds.cpython-36.pyc,,\r\ntwisted/test/__pycache__/process_getargv.cpython-36.pyc,,\r\ntwisted/test/__pycache__/process_getenv.cpython-36.pyc,,\r\ntwisted/test/__pycache__/process_linger.cpython-36.pyc,,\r\ntwisted/test/__pycache__/process_reader.cpython-36.pyc,,\r\ntwisted/test/__pycache__/process_signal.cpython-36.pyc,,\r\ntwisted/test/__pycache__/process_stdinreader.cpython-36.pyc,,\r\ntwisted/test/__pycache__/process_tester.cpython-36.pyc,,\r\ntwisted/test/__pycache__/process_tty.cpython-36.pyc,,\r\ntwisted/test/__pycache__/process_twisted.cpython-36.pyc,,\r\ntwisted/test/__pycache__/proto_helpers.cpython-36.pyc,,\r\ntwisted/test/__pycache__/reflect_helper_IE.cpython-36.pyc,,\r\ntwisted/test/__pycache__/reflect_helper_VE.cpython-36.pyc,,\r\ntwisted/test/__pycache__/reflect_helper_ZDE.cpython-36.pyc,,\r\ntwisted/test/__pycache__/ssl_helpers.cpython-36.pyc,,\r\ntwisted/test/__pycache__/stdio_test_consumer.cpython-36.pyc,,\r\ntwisted/test/__pycache__/stdio_test_halfclose.cpython-36.pyc,,\r\ntwisted/test/__pycache__/stdio_test_hostpeer.cpython-36.pyc,,\r\ntwisted/test/__pycache__/stdio_test_lastwrite.cpython-36.pyc,,\r\ntwisted/test/__pycache__/stdio_test_loseconn.cpython-36.pyc,,\r\ntwisted/test/__pycache__/stdio_test_producer.cpython-36.pyc,,\r\ntwisted/test/__pycache__/stdio_test_write.cpython-36.pyc,,\r\ntwisted/test/__pycache__/stdio_test_writeseq.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_abstract.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_adbapi.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_amp.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_application.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_compat.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_context.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_cooperator.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_defer.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_defgen.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_dict.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_dirdbm.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_error.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_factories.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_failure.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_fdesc.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_finger.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_formmethod.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_ftp.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_ftp_options.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_htb.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_ident.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_internet.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_iosim.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_iutils.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_lockfile.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_log.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_logfile.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_loopback.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_main.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_memcache.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_modules.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_monkey.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_nooldstyle.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_paths.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_pcp.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_persisted.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_plugin.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_policies.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_postfix.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_process.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_protocols.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_randbytes.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_rebuild.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_reflect.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_roots.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_shortcut.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_sip.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_sob.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_socks.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_ssl.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_sslverify.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_stateful.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_stdio.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_strerror.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_strports.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_task.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_tcp.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_tcp_internals.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_text.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_threadable.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_threadpool.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_threads.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_tpfile.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_twistd.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_twisted.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_udp.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_unix.cpython-36.pyc,,\r\ntwisted/test/__pycache__/test_usage.cpython-36.pyc,,\r\ntwisted/test/__pycache__/testutils.cpython-36.pyc,,\r\ntwisted/test/cert.pem.no_trailing_newline,sha256=zo_jqLPMFx4ihV8QxkdwD-_wT9WIC-zRDZcH23okXgk,1414\r\ntwisted/test/crash_test_dummy.py,sha256=e_KrrGBFmaXSLCLxq59VklPym1tY8UvzcCqZ-6xHzWU,543\r\ntwisted/test/iosim.py,sha256=HTAEcEPxQePmaPoMqBKBs4nS_J062aEyyKvOKax44II,17843\r\ntwisted/test/key.pem.no_trailing_newline,sha256=6ChUJWC8C3KXcoX1BBidlFOglMqHtYS-ul9cr6UMiHk,1707\r\ntwisted/test/mock_win32process.py,sha256=EeeQqdYC2ka1pqW10xDOblWBBuYGuIZc4OSIBRY9Czk,1499\r\ntwisted/test/myrebuilder1.py,sha256=IIZN_g1GPNIFVon6tbvPJmIHId7okkkY6P3QWQxKc1E,158\r\ntwisted/test/myrebuilder2.py,sha256=jCXJikyxA9P65EeQBypSXO5EPvPJ6tFhSfG2tuleLQI,158\r\ntwisted/test/plugin_basic.py,sha256=8xNGvfT0iGqQJoQlXNgV5MZBPh7kckLiCa75WOLPmZY,943\r\ntwisted/test/plugin_extra1.py,sha256=OfoMucKmCvgMRHL3YLhwU_Xi2CL4f862-44Au-SHe7c,407\r\ntwisted/test/plugin_extra2.py,sha256=EznTfuePvwBnCDi6eeth5bbUe41eS-LjLYmy516ynRU,579\r\ntwisted/test/process_cmdline.py,sha256=BimXPJAOrI7p6yeI__pflO_Jalk5y6tlgr-n2zgkaDo,162\r\ntwisted/test/process_echoer.py,sha256=USXd05oAkfmRKITVYXjpQ9lFouVEQbyA_a9mudWELpU,214\r\ntwisted/test/process_fds.py,sha256=id3GJEGB_uv9AmOPIC-yGvLehIRQDKrTEn5UDq_VSx4,945\r\ntwisted/test/process_getargv.py,sha256=WYk6DVL_Zviy160-eNWq263-i4nXAJpezsjpxBbDpUE,283\r\ntwisted/test/process_getenv.py,sha256=3micUPcws3OHsrbz6FvudJmAULuL7QxZQaPQL3yBddA,268\r\ntwisted/test/process_linger.py,sha256=g151drgjRfbI61dKYG0KYi8F8HxXRE3muWxBuzGVp4Q,286\r\ntwisted/test/process_reader.py,sha256=UbbRXJzTl8c6e_lGvFFlGsobtZUxkZovHPTUbfowDjg,188\r\ntwisted/test/process_signal.py,sha256=3HFQ8y72n9abUQHG0m_VuHddGePPgmZbjbCkkIbCpVc,214\r\ntwisted/test/process_stdinreader.py,sha256=2SQ9WN-X_qZPBc65dUBWEHVl1TtK_vOTKGzfbMwaRa4,857\r\ntwisted/test/process_tester.py,sha256=ahvvBnJv2a0z2X4FRXRkiYVrtgaWlotD2OaHHzAgR5I,1035\r\ntwisted/test/process_tty.py,sha256=hLLXgrwy_SF-dq2_moeGQSnpRJwyjgVMW7_z9ejXXvQ,130\r\ntwisted/test/process_twisted.py,sha256=MwDbDERsvFxRFkkuL48g-VJPVkUqI6GKl4skYpy14hg,1206\r\ntwisted/test/proto_helpers.py,sha256=O8Nwlhyg-0o7YmWyGk_0acecBlfbDAYjgXA3IB9CeAs,1009\r\ntwisted/test/raiser.cpython-36m-x86_64-linux-gnu.so,sha256=kLerOiQ3s3gyR_0He4TwA10Et2QImqI--T0CLU4r9OU,99619\r\ntwisted/test/reflect_helper_IE.py,sha256=D7N7dob70tx6BCuf2mTOVON-9iclUwWtKUTfvsU3F3M,61\r\ntwisted/test/reflect_helper_VE.py,sha256=VLu_9ughD3FOfYWMKw6N521vzp6YErR-d5IGnvVINzk,82\r\ntwisted/test/reflect_helper_ZDE.py,sha256=6eJjOrxytcz6G1a-NT3rz5fpIyof7ejuk4ZqxkXTAR0,47\r\ntwisted/test/server.pem,sha256=bAB7jzd2KxoBpd5VYhzgdmuPDKH9_XV_su2nNq6-xlI,4444\r\ntwisted/test/ssl_helpers.py,sha256=ZXyuxzyOz3eoedcTplun835Gru7UI1hj_tsZGGjHH5w,1032\r\ntwisted/test/stdio_test_consumer.py,sha256=UcpBNu9jRBjjplwDMFBvISaKV1G-MoZGpmdEN3y-AB0,1216\r\ntwisted/test/stdio_test_halfclose.py,sha256=1ULDASakPelEWZTmTEiGP_2yoqADEh_uO3NAtvf9f3w,1938\r\ntwisted/test/stdio_test_hostpeer.py,sha256=S4iym1eUrhSTI9q0_NyNFsU2vOt73kM80wQXAZPYiKc,1021\r\ntwisted/test/stdio_test_lastwrite.py,sha256=ja24d-ofVHcBwS-zQfZhepBu2DEMY10ESGNOc7NPiG0,1206\r\ntwisted/test/stdio_test_loseconn.py,sha256=4MuY6FhUQjVUOxJ-Da_oz87uAESTA2eqpOFjz36PbY8,1548\r\ntwisted/test/stdio_test_producer.py,sha256=OChDgtN-lKe4wv5afQiUngvvzJN-5ovdkNwDfsSooEQ,1507\r\ntwisted/test/stdio_test_write.py,sha256=ZzHl8uDvAuN987XKwHeU7huFJeUhkH2m7llj0_lb1TM,923\r\ntwisted/test/stdio_test_writeseq.py,sha256=KjDrpNrGdy6Ao66bUHuRlxk4r1hUxbf9z-q_YQPrrJQ,915\r\ntwisted/test/test_abstract.py,sha256=u1sJ3MqObQNQirOIL9KBdEK5GmHY-hfoX9MaaNbG7JQ,3497\r\ntwisted/test/test_adbapi.py,sha256=YZY7rTrIeImJlW852LbG19mMR_gPHq0gJyOCqBhh618,26148\r\ntwisted/test/test_amp.py,sha256=YsKFvd1aaugyD_lBDG0w6IPnDCKDjtcNPFO7YNmNBck,110553\r\ntwisted/test/test_application.py,sha256=vjgnjo4Q-IQ8NPZT8DH_hgyT2m0nrniw4nLEMpe4DOI,34210\r\ntwisted/test/test_compat.py,sha256=GKXSsM1F11qkVT0pPM6CPfVc1fugOMCUSB9EuBG0PJk,28527\r\ntwisted/test/test_context.py,sha256=zsV4fhj0VCrTLbzhjOdcr2gxG3kAOYCOwRjUvIs1ap4,1515\r\ntwisted/test/test_cooperator.py,sha256=vW_NFZ5arXXHquIBUeBwqUqb8cpLUP6ftFoDi6G-EXQ,21467\r\ntwisted/test/test_defer.py,sha256=3mNCERZAqGEP63g3dlCzJ4RGc-A2bD48zRaIM6_uyi8,104143\r\ntwisted/test/test_defer.py.3only,sha256=VUYRAxF1fFS6HBFPEmgQJF5cbF0T7hXMyuZI6ZOXqLM,2500\r\ntwisted/test/test_defgen.py,sha256=FcjjeYL5N9BbAnSf0rgTD36dN-zKTq2SR3pTKfBlBr0,10701\r\ntwisted/test/test_dict.py,sha256=GCmGM7c6XlVwIsQpkPJxeAW_Nyjy_kR2C6TsqXVruCU,1442\r\ntwisted/test/test_dirdbm.py,sha256=cPN4kXEgtG20KChbnVDwGfrRUCEiuvp8fSxY8UfBTM4,6695\r\ntwisted/test/test_error.py,sha256=3qPMbLZfUo_qvJx3E0m6mbXx-DYE_uP9mhkapMDix8g,8593\r\ntwisted/test/test_factories.py,sha256=i_dbiMVIhvx7f47BQK9I_Y8vdloV-9k33-0h2iX3uQ8,4637\r\ntwisted/test/test_failure.py,sha256=5G91yYuoSJ4-pwQlPTQIF3yMowcr7XFKFmSGA1vN09Q,32814\r\ntwisted/test/test_fdesc.py,sha256=DDqHNCrc5Q_gnDLyqGKI_ReNFjR1Qv79GQLjaWysIO0,7371\r\ntwisted/test/test_finger.py,sha256=lE5o_NacakzRCt5yYkCh-z_SktcXwK4FXhI5GXg9E0s,1997\r\ntwisted/test/test_formmethod.py,sha256=9aSzdUJSAzdrUhYGe-cf7nvDPU1L3JZCDIpYlSlrjjA,3645\r\ntwisted/test/test_ftp.py,sha256=Dmre2zNP4odYzKmK6KPzutLsv3T8zVS40eKmBkXvA80,130321\r\ntwisted/test/test_ftp_options.py,sha256=eGD8-ot2TGhcMTeP79EGhpmo-HfxmH3by_KzopdHNDw,2685\r\ntwisted/test/test_htb.py,sha256=nT0xU1fTt5TawiOd53Q7mQOkbSybNXa5Hdud74KO-bs,3190\r\ntwisted/test/test_ident.py,sha256=27hHDLdWQjZj_3511PpJ9jk-GKK8gRUOtmCzRLNMspw,7015\r\ntwisted/test/test_internet.py,sha256=WBPCf4NPaNWtDB9fIJ6Efwlel8QIn5DDC4BeBc2k3D0,46803\r\ntwisted/test/test_iosim.py,sha256=ZaDyIAoVKKjmmpZCugfrT6sKp0lVcgIrfGxqjvpqHL8,9060\r\ntwisted/test/test_iutils.py,sha256=Kv3t0iIi9u9fgzluaU2SVxVPGCQbcp3gwQfpkai0Spk,14384\r\ntwisted/test/test_lockfile.py,sha256=PsCJl1pA0K-aA-SIwW_i7VyN-43xTfxtmcmkPqDNQ3k,15506\r\ntwisted/test/test_log.py,sha256=0rlzX1ua_ZSqfDNsHc2tih12QZxsodgG4Ht4ELNpLzQ,36330\r\ntwisted/test/test_logfile.py,sha256=MPFH14kANpfxPbokwn9sZU4bK984kR6D1anoFJy_r58,18227\r\ntwisted/test/test_loopback.py,sha256=PTSDXS5TFz6L1GEkdXLWBHRrp3CJ0ds2WDodMrLWtLE,14486\r\ntwisted/test/test_main.py,sha256=F3x8NqO0CxZvfnmm6H2-x5Z4UsLH0htWUe0nwO_v4Qk,2501\r\ntwisted/test/test_memcache.py,sha256=lTdDfwGIOUIYv3nWC4TOpuY2oZ8D3--d6Z78a-5Spb4,25143\r\ntwisted/test/test_modules.py,sha256=VWkroMXc5duBPTOTtJnHgJDFSHUBmK2TfaJwvfa7w88,17888\r\ntwisted/test/test_monkey.py,sha256=D37NHborDX663mPE3vnYQP2OA8Ey37YDpuHCuXu4Gu4,5637\r\ntwisted/test/test_nooldstyle.py,sha256=hwfH8G2l4KJrHqUCmH__iUjhoFW34aGVy_WOE2iXi5g,5955\r\ntwisted/test/test_paths.py,sha256=j_0l5igUqehcYqvFfBG9KU0ZZlQKnho36ysoBNHxv64,74357\r\ntwisted/test/test_pcp.py,sha256=k13lppisnl5WYCS5BD-kAbyUzM1CZBLxbQ0rG_S3a-M,12551\r\ntwisted/test/test_persisted.py,sha256=KHfsZlx2feaihD0Ja5KBq_-h56CQ2ilxWDQ32xq-JnA,14624\r\ntwisted/test/test_plugin.py,sha256=r20OZv-hMr9DjMyk9tJxDykMV_g1seLgyDfp3eVz6Ww,26113\r\ntwisted/test/test_policies.py,sha256=KtUlbJZRqmqOpQT4E20PHb3V_6gvBa45DzkFZEr3Hck,33499\r\ntwisted/test/test_postfix.py,sha256=CrDVuSkr18QQDVhJ5lCCy07Fy6RQjOaMffUKmno0nZM,4243\r\ntwisted/test/test_process.py,sha256=Y5ntI0AwGXEsxuiViOB8bdVIyyFLUO3Efw3O9fs4vJk,86120\r\ntwisted/test/test_protocols.py,sha256=ZIk1-7OhE-04Oytmr9-ScYWBi_PrsBDh-aUFiiUYqgY,7450\r\ntwisted/test/test_randbytes.py,sha256=MkUMH7zYTdJ4Ln8J9VJDLueHFcZ4HR1Qz2aNPVFHKnw,3357\r\ntwisted/test/test_rebuild.py,sha256=iscBE4IMkfOmEGkHlyjCZC8ioXjnwNi5kQwmf19eduk,8495\r\ntwisted/test/test_reflect.py,sha256=riIAjcwwIq4ZeM4rGZIaxuDFLkrKtqr315-xM-j7ANw,26085\r\ntwisted/test/test_roots.py,sha256=4TzR1qugGrfLdjwO34KO0SAweOxOMHqkJtMwkWtbmm4,1812\r\ntwisted/test/test_shortcut.py,sha256=NkA5ho-Rvhhu9Dj_JD5N6VZS4lzNWHInPe2J4Clv-L4,1991\r\ntwisted/test/test_sip.py,sha256=wFVIuH_XqHAGlenbvtswDjBFZpo3E4RnIRAxEel_AEI,25284\r\ntwisted/test/test_sob.py,sha256=ttrn_p7OpR2ikvTm8oNxgxrxnQ4xMdT7YdIc02egl58,5632\r\ntwisted/test/test_socks.py,sha256=ImzFJie1KZesqrTM1LyhhCSD_WLXB-_eRrWWpAzw31c,17738\r\ntwisted/test/test_ssl.py,sha256=kqOXu-IGJKW4HuCSdTs4U2rORO-P4SrGBby5stQfmOE,22923\r\ntwisted/test/test_sslverify.py,sha256=iAjE3Zo6FKDhCaRE_PiyIFwVOGbAJ58ZAQcvsSisAJY,116121\r\ntwisted/test/test_stateful.py,sha256=-X78ROUUyb5c6-jzJ4DIi_NYf0t8xmLegEOSqrQSxnE,2021\r\ntwisted/test/test_stdio.py,sha256=M7agWsEf2cC2tpHrtqXEVn9jQXIqYYzYEW2eQ5RoB5U,13156\r\ntwisted/test/test_strerror.py,sha256=4lT14E-7oGKDHpsAoJ4Es6WDPa9h6fK3FS92B51w3s8,5183\r\ntwisted/test/test_strports.py,sha256=oM-EGX3x5WWQIMTXYWUy7fgscvVuhoaoKdxCqHTgSLE,1797\r\ntwisted/test/test_task.py,sha256=-7MgKjHCcIclp6DmwOegRo-C5Ury2lF4i3W5xBJRbLA,39683\r\ntwisted/test/test_tcp.py,sha256=ywEI3OaF7iJfY4l7eA6ZYBuem-TIegIiF1yEg8Bpuak,66192\r\ntwisted/test/test_tcp_internals.py,sha256=DCBr5-a2W12EvX9gWBlf8vIGc8YEizQ1Uodcdu5tfqk,13255\r\ntwisted/test/test_text.py,sha256=ZDBTmtLnIGkYwL08uX0MJ4Xq-B1oPgt8rAzO1_FT62o,6456\r\ntwisted/test/test_threadable.py,sha256=85oUaY3J3Cg7Y-uvm6Wk4f5cQ-RhYi5SCLIbS8fb7ZQ,3738\r\ntwisted/test/test_threadpool.py,sha256=1qoaUY1zYLmeW4M0ZRRNfvzH0CUwAkdPjQ-5L_Q0lEk,22204\r\ntwisted/test/test_threads.py,sha256=bLzBn98GjVgBCylKpps1oLFwpJKaGV9Q_79_6jDT_uc,13268\r\ntwisted/test/test_tpfile.py,sha256=f3apHS3fbcoNspvqJ4d3Tljtv44lHU3FcWgJIoyy4Gk,1601\r\ntwisted/test/test_twistd.py,sha256=BYTWg5qB6NVwGjIkM6qWUd54U6pj308SVQPfAA1Pw_Y,74201\r\ntwisted/test/test_twisted.py,sha256=JFiWXtkK0Si6NLrh1i3iLLplxie2_zZNb6DHB-tmAjo,9214\r\ntwisted/test/test_udp.py,sha256=K6uHGFmp7pLUpIjmfjNNFtyiFQmNHyO6XVVO783b3zU,24992\r\ntwisted/test/test_unix.py,sha256=sxRkpz0NzS98bXy1ZlfN_p3J2GRk2BbLg8aGGLv5vnM,15157\r\ntwisted/test/test_usage.py,sha256=E3vSRYqzzUbjWg3CZW4bFYAK8eoAtiuUGdb9jJH9JeY,23645\r\ntwisted/test/testutils.py,sha256=VWozf8WzYsiwRA8LCR7jIaLyi9x0dE2HOHJaJQTmtwc,5321\r\ntwisted/trial/__init__.py,sha256=2ib2sy-amXD8irsLolFFjjeNur8BnaXwBWaOCASmsFU,2040\r\ntwisted/trial/__main__.py,sha256=noqg0SgiYqvgjWVTPJCyrxZDdpR-l1p666wuE4a5388,249\r\ntwisted/trial/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/trial/__pycache__/__main__.cpython-36.pyc,,\r\ntwisted/trial/__pycache__/_asyncrunner.cpython-36.pyc,,\r\ntwisted/trial/__pycache__/_asynctest.cpython-36.pyc,,\r\ntwisted/trial/__pycache__/_synctest.cpython-36.pyc,,\r\ntwisted/trial/__pycache__/itrial.cpython-36.pyc,,\r\ntwisted/trial/__pycache__/reporter.cpython-36.pyc,,\r\ntwisted/trial/__pycache__/runner.cpython-36.pyc,,\r\ntwisted/trial/__pycache__/unittest.cpython-36.pyc,,\r\ntwisted/trial/__pycache__/util.cpython-36.pyc,,\r\ntwisted/trial/_asyncrunner.py,sha256=oNL10LsWsYgfPDZhAzO9Hes-yKZa17M6PF-JyAFamuw,4530\r\ntwisted/trial/_asynctest.py,sha256=qUGroPSQz4SPywueE4vxXnk8JtkbwopGFqA6D1J9-UA,14634\r\ntwisted/trial/_dist/__init__.py,sha256=0v2hhp_DnNSlYu4-6rS6SzWwFTqcl_1DCqPrWxKdEXc,1941\r\ntwisted/trial/_dist/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/trial/_dist/__pycache__/distreporter.cpython-36.pyc,,\r\ntwisted/trial/_dist/__pycache__/disttrial.cpython-36.pyc,,\r\ntwisted/trial/_dist/__pycache__/managercommands.cpython-36.pyc,,\r\ntwisted/trial/_dist/__pycache__/options.cpython-36.pyc,,\r\ntwisted/trial/_dist/__pycache__/worker.cpython-36.pyc,,\r\ntwisted/trial/_dist/__pycache__/workercommands.cpython-36.pyc,,\r\ntwisted/trial/_dist/__pycache__/workerreporter.cpython-36.pyc,,\r\ntwisted/trial/_dist/__pycache__/workertrial.cpython-36.pyc,,\r\ntwisted/trial/_dist/distreporter.py,sha256=4oiCkv6AZOIfBfZt8qDKyKSERZtx5S7r9AA170DAeYU,2495\r\ntwisted/trial/_dist/disttrial.py,sha256=T-QHOl0r5MztVjVBbfCyGtERQQs1ixeLqkYjOvtSXEM,8711\r\ntwisted/trial/_dist/managercommands.py,sha256=FDoWQMJXMu1UIzYseCtS4t2A7yKyZFfEM_Zc3U9qs7E,1897\r\ntwisted/trial/_dist/options.py,sha256=7GLbC2y5zGM3IwimCBg7H26AOlwiPb2dkoebWQFezzE,739\r\ntwisted/trial/_dist/test/__init__.py,sha256=IOS3XedcenVmIEF2Dn-7IhLiGyeN1IG33V51Pk_iS7o,118\r\ntwisted/trial/_dist/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/trial/_dist/test/__pycache__/test_distreporter.cpython-36.pyc,,\r\ntwisted/trial/_dist/test/__pycache__/test_disttrial.cpython-36.pyc,,\r\ntwisted/trial/_dist/test/__pycache__/test_options.cpython-36.pyc,,\r\ntwisted/trial/_dist/test/__pycache__/test_worker.cpython-36.pyc,,\r\ntwisted/trial/_dist/test/__pycache__/test_workerreporter.cpython-36.pyc,,\r\ntwisted/trial/_dist/test/__pycache__/test_workertrial.cpython-36.pyc,,\r\ntwisted/trial/_dist/test/test_distreporter.py,sha256=wrXX0UllZZRgCAArA8gdKHipm9JLi0cFMzdgk_pn2DU,2051\r\ntwisted/trial/_dist/test/test_disttrial.py,sha256=aJ7-xg5Ew1uwyoFq5F0T_YMK5u-JfZfbdAdYGJE3a9M,16757\r\ntwisted/trial/_dist/test/test_options.py,sha256=8cMl8nKBeXvnfuRDwL6oTluwnbtJ3GR9HZl45YEiAyA,1312\r\ntwisted/trial/_dist/test/test_worker.py,sha256=Lu4I8xl0i3kgyrpBTinEAgxrpDBX43vRF9otsDrZH4c,14784\r\ntwisted/trial/_dist/test/test_workerreporter.py,sha256=lNGGrJoiWsu58wVMAY9lF6twFISQgMyoRh60HT9ww80,5390\r\ntwisted/trial/_dist/test/test_workertrial.py,sha256=StZMQYWknt0nVg2F4KaJ9ZPUNFX-JVh0-5uF6d1kHB0,5014\r\ntwisted/trial/_dist/worker.py,sha256=uuzghTilXOwfiNHjKkgYUppJNkqzo4_VBEqwKNIXkR8,9153\r\ntwisted/trial/_dist/workercommands.py,sha256=GerNCLGPNP8asXy22Cl8qAKQYJ9sKiXDo729Lc1AbbE,641\r\ntwisted/trial/_dist/workerreporter.py,sha256=ysGwtY-e6c_sSTR3IGhy7f8kqgqOQI46EnJysD2LJxk,4856\r\ntwisted/trial/_dist/workertrial.py,sha256=BQDJ2KHnHQ6MtPwOq_pU428h2zvT7k-JYVnsc1Z62VY,2859\r\ntwisted/trial/_synctest.py,sha256=HgxTQKu4jMXjUjJyC48yNX7LVw4f8nEynMi3VyDdGtk,50017\r\ntwisted/trial/itrial.py,sha256=EmbbuIA4WItHcgQKEOGhfORSTxTuWX-DrRezBrcbj9k,6857\r\ntwisted/trial/reporter.py,sha256=peShSfUXXNGxHTQyxY-1WXuTEAaEhaWrUqRDh0YaPxI,40105\r\ntwisted/trial/runner.py,sha256=mzT5AVFYlBL97jCK8CjJLZjKor9zysNV-yff7bLX7OQ,36720\r\ntwisted/trial/test/__init__.py,sha256=uWFvjebi50_v57TkFDrFhvUS5oUq8Jo5y_vRBvpP9o4,130\r\ntwisted/trial/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/detests.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/erroneous.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/mockcustomsuite.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/mockcustomsuite2.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/mockcustomsuite3.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/mockdoctest.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/moduleself.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/moduletest.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/novars.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/ordertests.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/packages.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/sample.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/scripttest.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/skipping.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/suppression.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_assertions.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_asyncassertions.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_deferred.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_doctest.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_keyboard.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_loader.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_log.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_output.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_plugins.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_pyunitcompat.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_reporter.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_runner.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_script.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_suppression.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_testcase.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_tests.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_util.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/test_warning.cpython-36.pyc,,\r\ntwisted/trial/test/__pycache__/weird.cpython-36.pyc,,\r\ntwisted/trial/test/detests.py,sha256=7uYBWdLD-Slpq6cXrgtdJyalwCvAZzhJGL0KX2jhbUA,5368\r\ntwisted/trial/test/erroneous.py,sha256=fM-kSxh_M7QfB0Oc9bIIQDX-r_29ZdJIrabqUqjxZhc,4829\r\ntwisted/trial/test/mockcustomsuite.py,sha256=pNEnsIgTTx-fp2hYS4GxkAenBER6uPot11VbkDzqQgM,535\r\ntwisted/trial/test/mockcustomsuite2.py,sha256=GPSbV-Ou5XCACyVF_DgD2SXDH3Ekvzab9rQiC0roUuQ,532\r\ntwisted/trial/test/mockcustomsuite3.py,sha256=zc_roFFRqTPwVGto3VL7_Ic15nGm4WvCEG-w5rHiYlw,675\r\ntwisted/trial/test/mockdoctest.py,sha256=f89ND666XnQnUuvIyR4begtzQWM_mBxzRWs5F9AeWvE,2645\r\ntwisted/trial/test/moduleself.py,sha256=UWx4cOBRU6OlGdjfjgEgNQPpfbp-biul5WCAtI30GD4,170\r\ntwisted/trial/test/moduletest.py,sha256=Yx-H7C4qwBgzKFkp1B_JYyq2D8CCiSEpE9qS2jwfD7A,310\r\ntwisted/trial/test/novars.py,sha256=asKIwzyfBjiDqHi8zeTzcHHdLYGBk1JQf1QvbZl25zc,189\r\ntwisted/trial/test/ordertests.py,sha256=ZZm2zhvHrEtN7hVXH49vVTOB7dEsXfuargd_8M1d0wM,867\r\ntwisted/trial/test/packages.py,sha256=lnN006Agb_-kEkNrKGus38S-ePaIl4JT8azwJFhTGRg,4927\r\ntwisted/trial/test/sample.py,sha256=nWBJwh0ZAu3tpLhV8N5RoNUI7HUQQWrkLIbVHrDDGbk,2155\r\ntwisted/trial/test/scripttest.py,sha256=1wey0lWic-hQv_NZ4YR6BS-GHFqcJaxf8CHGitkdosY,466\r\ntwisted/trial/test/skipping.py,sha256=y1Pkj2IMNGfVdrtwBEkPzRWh_zBia3srnkHySEbszPg,5356\r\ntwisted/trial/test/suppression.py,sha256=rHQuaV53Au_YXyYw0zZC4UToHp-o5_uQUB_vbmiS9GI,2497\r\ntwisted/trial/test/test_assertions.py,sha256=rIbGSAeiouJh_20HJZUib8D4u-wHN8rIVnUXIyFZYvI,46630\r\ntwisted/trial/test/test_asyncassertions.py,sha256=f-OE4xvhJ9jZmVUd74azvoUKgYcUW-BLHwRbYjIcCB8,2571\r\ntwisted/trial/test/test_deferred.py,sha256=d-iLD-GqYvAq2IvFUhmr8eVtOwGeP4X9bFg_BoqMAeY,8889\r\ntwisted/trial/test/test_doctest.py,sha256=p5fpDtW76E461ltTr5vrrz0V3Gas5nGz7lUypOvi90U,1766\r\ntwisted/trial/test/test_keyboard.py,sha256=Zc3E7yyNElQ9bI2E8wlsRj_1V5jOXFv_ylTi3FW9db8,4036\r\ntwisted/trial/test/test_loader.py,sha256=b6r0-_40GUTMZ2svo58Q_NBMXkxY3HmE5ffBb2mp4n8,26783\r\ntwisted/trial/test/test_log.py,sha256=4KbBgmQwI7IjFnZ8W8ZNdtb5RcSLoPGov7QL2Znxjmw,7969\r\ntwisted/trial/test/test_output.py,sha256=zQ94RkuSX1FOLTxlt7VqSAueSWmvpsYrGIHeTDINo8M,5299\r\ntwisted/trial/test/test_plugins.py,sha256=9KUuBPPm05bO1a7RxQP6fMRDr23S7_FKf81ssYL3GHo,1451\r\ntwisted/trial/test/test_pyunitcompat.py,sha256=HkGUKXAp9hfYOqjPY_DVWBvxpTVm-QC2qPAZXJHfUII,7670\r\ntwisted/trial/test/test_reporter.py,sha256=3vFYKFQSF5g_Gf21MN99PNiUAUdE9Xwq5-Wxp86Lpzw,57428\r\ntwisted/trial/test/test_runner.py,sha256=pRK1B-bIjTn9pCu2gSte_IVP_3i0OMitwasxQYBuptQ,34074\r\ntwisted/trial/test/test_script.py,sha256=YaO9q-4fH_9T6yhSTeEm0ciGv5ivM1DBdAlIDWa9U3I,29717\r\ntwisted/trial/test/test_suppression.py,sha256=vw8R3i_EaZgtdcGNxrzSbVI7gvLVm2baHh348g_yVvc,6089\r\ntwisted/trial/test/test_testcase.py,sha256=f2xpFykUxZoW8T5HzSiw7dc0pqOAh5ZswK4u1eC9ZOw,2043\r\ntwisted/trial/test/test_tests.py,sha256=koXRAKkmWDMXElmy87uPQCuIspyeYr4VeO4dbf1XPpc,50030\r\ntwisted/trial/test/test_util.py,sha256=faNL8ZBaOR83bcNQV7x7pNtXUofSSvj8h9gbq1m6o0s,24709\r\ntwisted/trial/test/test_warning.py,sha256=aZZSrMvdCvAf_EALAvTSBpQozfSpef_5GyelC7qpCgk,16770\r\ntwisted/trial/test/weird.py,sha256=apD_gjh7qeK_gEi9r3WErMHYvPuf0PIk_BoJZNAbvCA,721\r\ntwisted/trial/unittest.py,sha256=JQAudPGd--a9KNzsaGRCnzbQ2H_JzMSQFC-nMVJ4Xng,978\r\ntwisted/trial/util.py,sha256=FjW69s1ttgn3MHUXkv7HmhK2JXzceiE0BgTiAQnNgHw,13410\r\ntwisted/web/__init__.py,sha256=XDcQGn3KmRxndOIDTJZcSWGhxPALqHLMxbzsRhqsra4,384\r\ntwisted/web/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/web/__pycache__/_element.cpython-36.pyc,,\r\ntwisted/web/__pycache__/_flatten.cpython-36.pyc,,\r\ntwisted/web/__pycache__/_http2.cpython-36.pyc,,\r\ntwisted/web/__pycache__/_newclient.cpython-36.pyc,,\r\ntwisted/web/__pycache__/_responses.cpython-36.pyc,,\r\ntwisted/web/__pycache__/_stan.cpython-36.pyc,,\r\ntwisted/web/__pycache__/client.cpython-36.pyc,,\r\ntwisted/web/__pycache__/demo.cpython-36.pyc,,\r\ntwisted/web/__pycache__/distrib.cpython-36.pyc,,\r\ntwisted/web/__pycache__/domhelpers.cpython-36.pyc,,\r\ntwisted/web/__pycache__/error.cpython-36.pyc,,\r\ntwisted/web/__pycache__/guard.cpython-36.pyc,,\r\ntwisted/web/__pycache__/html.cpython-36.pyc,,\r\ntwisted/web/__pycache__/http.cpython-36.pyc,,\r\ntwisted/web/__pycache__/http_headers.cpython-36.pyc,,\r\ntwisted/web/__pycache__/iweb.cpython-36.pyc,,\r\ntwisted/web/__pycache__/microdom.cpython-36.pyc,,\r\ntwisted/web/__pycache__/proxy.cpython-36.pyc,,\r\ntwisted/web/__pycache__/resource.cpython-36.pyc,,\r\ntwisted/web/__pycache__/rewrite.cpython-36.pyc,,\r\ntwisted/web/__pycache__/script.cpython-36.pyc,,\r\ntwisted/web/__pycache__/server.cpython-36.pyc,,\r\ntwisted/web/__pycache__/static.cpython-36.pyc,,\r\ntwisted/web/__pycache__/sux.cpython-36.pyc,,\r\ntwisted/web/__pycache__/tap.cpython-36.pyc,,\r\ntwisted/web/__pycache__/template.cpython-36.pyc,,\r\ntwisted/web/__pycache__/twcgi.cpython-36.pyc,,\r\ntwisted/web/__pycache__/util.cpython-36.pyc,,\r\ntwisted/web/__pycache__/vhost.cpython-36.pyc,,\r\ntwisted/web/__pycache__/wsgi.cpython-36.pyc,,\r\ntwisted/web/__pycache__/xmlrpc.cpython-36.pyc,,\r\ntwisted/web/_auth/__init__.py,sha256=GD_euhqqSJj1fv_srRt5Yl5RfcExpzifR-PYLNTKIwI,190\r\ntwisted/web/_auth/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/web/_auth/__pycache__/basic.cpython-36.pyc,,\r\ntwisted/web/_auth/__pycache__/digest.cpython-36.pyc,,\r\ntwisted/web/_auth/__pycache__/wrapper.cpython-36.pyc,,\r\ntwisted/web/_auth/basic.py,sha256=S3KTEXHVdz8EFnrR3Un3kulhOO_kOUitt0D1cleHIzg,1689\r\ntwisted/web/_auth/digest.py,sha256=Cr3akmx_l73w-yZxUqB3CcF1DFNc9R41Ibpw63MIfHc,1770\r\ntwisted/web/_auth/wrapper.py,sha256=QjwuVhM9rwMcxiV1oF8u9YmH7YEy3EPC4BfzGsQy4U8,8566\r\ntwisted/web/_element.py,sha256=7vBEF4yTwCUsmeAsBCjSwYbutvNrLS4Bp-9PA0ae7mU,5947\r\ntwisted/web/_flatten.py,sha256=obSfnAN4wJ0n3DK_e1fxlj5qiVc_CwLkyMFKAI0QzdI,15912\r\ntwisted/web/_http2.py,sha256=mlomwH5LyFPIl3wZ1GE60BtIAx1mls-x54wagPni5AA,45545\r\ntwisted/web/_newclient.py,sha256=bsD00poQNKPGLeFY0pXkxZ1yaDV20Xe9sH5oc0x-KAg,63973\r\ntwisted/web/_responses.py,sha256=IuFI3g88Klz01-6AGus3FDu4ifFiSZcGpH_7xQFKv8U,3655\r\ntwisted/web/_stan.py,sha256=hr8FW8_qo-wFShnq3iGUmALNVew2k0is5YbRnuXliJ4,10790\r\ntwisted/web/client.py,sha256=wf2N3Rzn4lZ_lLc-DPc-euuiI0O7l35e1QxO2eeJLOg,76971\r\ntwisted/web/demo.py,sha256=g3JC8qhso0-sYmmRVjT_di_F2_-J09kdsM9Z5kH7u3g,554\r\ntwisted/web/distrib.py,sha256=ky8W3tDRSsVXmarhx3z7Ys9oKmho0UtNIKd0gv72LVE,11881\r\ntwisted/web/domhelpers.py,sha256=JJor6qQbzybg-D9rVX-9Q3vTvJZUDNbzp9HyaACvPc0,8645\r\ntwisted/web/error.py,sha256=z_QFN-l4gy370GEWXuue3MIliddbNa1VXroIRcfsfHA,12537\r\ntwisted/web/guard.py,sha256=2vGjNL9ZxbPxHZWuqXwJ1UFXGHfFgAxdD7kQ90I0OqU,630\r\ntwisted/web/html.py,sha256=7uKIiee9Sg6vKlV5juUTHoTSwLPVa6jXLSKTOkg6SKs,1557\r\ntwisted/web/http.py,sha256=xTllJJrr8PWDEmyvpkBNSVqsdrZo_ovErRz4fG8tEAc,104055\r\ntwisted/web/http_headers.py,sha256=L9yz-tM4HUP_xDU7fqvnNIuiEzj6yYRp6O766HDsYLA,8853\r\ntwisted/web/iweb.py,sha256=KYQqCnUp6ebvwa5BNCogYjKpdrY2p7_flVDbCa8A9rE,26778\r\ntwisted/web/microdom.py,sha256=a-LdI_UIIXFLMfFdHDVKYnAM8vTEfKhSkPAqeK_PC34,36197\r\ntwisted/web/proxy.py,sha256=u_LqSCDNuFKjs_K85LNzimWcsxrvtRuMe5ZHs3QO6lU,9837\r\ntwisted/web/resource.py,sha256=kpKqmCAWKXwNvokIGYM2pCCWM4AevSOgklRX20Oy3-8,13610\r\ntwisted/web/rewrite.py,sha256=ezcoNJcAy-ET1WmS2UF3JzTNhhNR1bGoyDK0dl_q9Fg,1852\r\ntwisted/web/script.py,sha256=pIQ-kiryhNxUjZlJUQyd2knXWjdzO_VZFm8-weXDIh0,5745\r\ntwisted/web/server.py,sha256=eDdTtMBs2fANGFR0oL5UWJLLrdRdClpIdAUJ0kbw0ic,28329\r\ntwisted/web/static.py,sha256=3iCMORPZXIwcujH1D4lwU7R-vISY-2RbBqUiC11vNHc,38007\r\ntwisted/web/sux.py,sha256=ue2_D9mzOOOPpPvJNTL-31jWbnAgsG-EimiuAIJQx2Q,20892\r\ntwisted/web/tap.py,sha256=nMnaXPp8dEHhOLDj_L6ogXyulXR387_-3hMVucoX5Vg,10331\r\ntwisted/web/template.py,sha256=IZMkl-eBtxot8sFb96C2xHBXMcHwwgvjE8egjy30pKo,17631\r\ntwisted/web/test/__init__.py,sha256=fUhYepItGqSYT0CsZLxIbU9lDRjUkJ0pGsdsr8GRp0c,108\r\ntwisted/web/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/_util.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/injectionhelpers.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/requesthelper.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_agent.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_cgi.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_client.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_distrib.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_domhelpers.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_error.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_flatten.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_html.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_http.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_http2.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_http_headers.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_httpauth.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_newclient.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_proxy.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_resource.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_script.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_stan.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_static.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_tap.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_template.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_util.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_vhost.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_web.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_web__responses.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_webclient.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_wsgi.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_xml.cpython-36.pyc,,\r\ntwisted/web/test/__pycache__/test_xmlrpc.cpython-36.pyc,,\r\ntwisted/web/test/_util.py,sha256=6pb3RDrdZoJ1DaELSW8PdaXUywANty8JN8j8AUwOKAM,2568\r\ntwisted/web/test/injectionhelpers.py,sha256=V2QQTamzKkOjypM7qdt2Y2iVHzQi4c83mZTesOt2_JU,5627\r\ntwisted/web/test/requesthelper.py,sha256=oP_zp0MkntT7TKvJPMIg6_7LlyQiuQ0-izoHRiYNIB0,13702\r\ntwisted/web/test/test_agent.py,sha256=ghnRnHIpSsrvi7ilIqdFU4a1MENBBzJ-PItrw6IAVQY,116623\r\ntwisted/web/test/test_cgi.py,sha256=fPZPDFG8JAOUJD2pXr7H_FOenrzy-RLdLW3FOTmM4L8,13761\r\ntwisted/web/test/test_client.py,sha256=rnMgKFRmeVFgtKTjnyAhJL2LvOI8P6WIjXJa--Juv5M,1372\r\ntwisted/web/test/test_distrib.py,sha256=SAHzSQyQa3IoYGi1dc0csEvSl69hSnBzRZGzKbfSIoI,18288\r\ntwisted/web/test/test_domhelpers.py,sha256=ir_GSEC4Y5eJUIP4mKi9GzFUdwLXvuDuBEHiUmSC2go,11103\r\ntwisted/web/test/test_error.py,sha256=a-KtTSqsH05SlDijTSPA50C7m-dgPhZH3Avc9uKs3uE,16210\r\ntwisted/web/test/test_flatten.py,sha256=TJTlohdbkYUC6OLIprKuYQrHoUh2aY86kVgzIQyp9Nk,18259\r\ntwisted/web/test/test_html.py,sha256=BBbAgc2B9f8-PmYvcyGDbhjKDUpBQTiuikNgaNpKaGo,1264\r\ntwisted/web/test/test_http.py,sha256=4IrPhkpFTHNSXbjQu9cjrOi6c-3X4LFGz6DYXIMah6k,131929\r\ntwisted/web/test/test_http2.py,sha256=LLlY0PSmFovpGoGe05bfTFrM8UetVZIhGrwCX4V_RUc,99939\r\ntwisted/web/test/test_http_headers.py,sha256=c3uv_Zbs5hDJQ64eGEErzs4iCVSnDdDCTp8sY3hbs0g,22177\r\ntwisted/web/test/test_httpauth.py,sha256=VyOB2BQqn2SEjXUsSUUc9OLHFgesUwjCvQD0U87XMSg,24128\r\ntwisted/web/test/test_newclient.py,sha256=rq4_W0WxH4NhCozadpy3gudGsD4zZTUDkdib1MMUSCY,110593\r\ntwisted/web/test/test_proxy.py,sha256=DW2jc_1elz_bPp4eU7qLK5peNTc_WM39p1TDnIMBaC8,20346\r\ntwisted/web/test/test_resource.py,sha256=EgBRDWfHTO01PNJgDbbAnUv9Pp_C5NmC2ZUOHiL-buI,9243\r\ntwisted/web/test/test_script.py,sha256=rQilL-H4VzO-NGU6_2Dv9h32VA3j4pZSPtwMW30e86E,3784\r\ntwisted/web/test/test_stan.py,sha256=5IqsRlFv_yp7HVZXFaqlFR1g79H2etwtPriydZkjaFE,5667\r\ntwisted/web/test/test_static.py,sha256=PqkZKWxhQ3GGmlMqwx2oDfrY_RlNc8ZPE5oaWLL74XU,67858\r\ntwisted/web/test/test_tap.py,sha256=w1GFPg5RbSWryvvp1wf7HleTz0EJHSoxHN3oMGpvzuc,12200\r\ntwisted/web/test/test_template.py,sha256=tVpMImaRl2wZQo1m-CPR1EfnApPSxhZedkLT4xTEsww,25977\r\ntwisted/web/test/test_util.py,sha256=pGxkGSoNPuWmunh_xqVJ8k4z97rMcZafvTgz6VOC770,12590\r\ntwisted/web/test/test_vhost.py,sha256=lF3ch-BlKMRqwug79z-y_dmFyJwQjVwLqhziruVeZz4,7398\r\ntwisted/web/test/test_web.py,sha256=CsyyQrdvYh-_r12YjuYXMS2z21hMR_bMZrXvqjfBgx8,64296\r\ntwisted/web/test/test_web__responses.py,sha256=Hsq7CDGZoxE9Iq78xaYuhZxqoN58qNuKsoaR4cgAMK0,877\r\ntwisted/web/test/test_webclient.py,sha256=Ww5dnXrDvtTsTwUAXtchL1vgKbQMrK_3Lbw4X9UtUMM,59615\r\ntwisted/web/test/test_wsgi.py,sha256=WAsGDXhOATeEIdDj-PPimPdrSoMVRKUl8EgCWVRcegw,78210\r\ntwisted/web/test/test_xml.py,sha256=zEnd97a1PSltKUfNyobziKKt7laDLWJV3jdfxJw3caw,42357\r\ntwisted/web/test/test_xmlrpc.py,sha256=6OL77o-ZcYUGS80cu5cyrbZA89DOkIB98xceNIOmQeA,30302\r\ntwisted/web/twcgi.py,sha256=_BIZTsI0soo5v7tf4gx25bqhbJhwNB8ZZCoDIdIgCr0,11343\r\ntwisted/web/util.py,sha256=Nwt-k63WLnLLhfA7vOh-10EkBboLhZehTM2oHpkFfjE,12412\r\ntwisted/web/vhost.py,sha256=9Y-li_wuLQmTJKPJWs4KOiT_WTVqhrnbfdcobtpbQnk,4463\r\ntwisted/web/wsgi.py,sha256=bjbeVJI5DrrhHlB1VFK-DVrOknosC_uRB6B4HGIMPDw,21879\r\ntwisted/web/xmlrpc.py,sha256=H5mFDI1rk1-dmj8QPijFyd34K5T7gKxTv8i-XMNFwak,20203\r\ntwisted/words/__init__.py,sha256=ffiFEwEz9RTE5rrSHV9jzhWhuomlg-tT7RQAXhlpGNI,215\r\ntwisted/words/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/words/__pycache__/ewords.cpython-36.pyc,,\r\ntwisted/words/__pycache__/iwords.cpython-36.pyc,,\r\ntwisted/words/__pycache__/service.cpython-36.pyc,,\r\ntwisted/words/__pycache__/tap.cpython-36.pyc,,\r\ntwisted/words/__pycache__/xmpproutertap.cpython-36.pyc,,\r\ntwisted/words/ewords.py,sha256=XOOQe4IRjQrj-kRj8Hu07VhjT6gCJYXmJ5MeFDhMEpE,623\r\ntwisted/words/im/__init__.py,sha256=ojtUkusjr0Xe56X-Oo4kmcmDCRCsC9C5qwZQZ_7vyPc,129\r\ntwisted/words/im/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/words/im/__pycache__/baseaccount.cpython-36.pyc,,\r\ntwisted/words/im/__pycache__/basechat.cpython-36.pyc,,\r\ntwisted/words/im/__pycache__/basesupport.cpython-36.pyc,,\r\ntwisted/words/im/__pycache__/interfaces.cpython-36.pyc,,\r\ntwisted/words/im/__pycache__/ircsupport.cpython-36.pyc,,\r\ntwisted/words/im/__pycache__/locals.cpython-36.pyc,,\r\ntwisted/words/im/__pycache__/pbsupport.cpython-36.pyc,,\r\ntwisted/words/im/baseaccount.py,sha256=s4wY-BSOVxOpuY85qyWzAV_Jcf53V48gPs7MA4ODitc,1808\r\ntwisted/words/im/basechat.py,sha256=sa3FXpKVESXmoCATOAq781KzPg-02vpk_Om42UcN1es,16454\r\ntwisted/words/im/basesupport.py,sha256=AmZMFNSPJRqriDckFSRrx2Ae2DeZUMblNdzi_yIPTpY,7842\r\ntwisted/words/im/instancemessenger.glade,sha256=Scnco66vE3ByEHRbXpG4jkjW8wBquLjVrPtTRXurkRs,77126\r\ntwisted/words/im/interfaces.py,sha256=C8hxSNUyi-BDhC7uzGQFAoQMGEb2BiqTekob5cOe-8o,8675\r\ntwisted/words/im/ircsupport.py,sha256=ZBhiItd93QgRcXZvEcSygIBi0-QJs5sWfyVAUY2bfQM,9150\r\ntwisted/words/im/locals.py,sha256=JCVxJC5thNvnoTQ9VbrGtdXtGoYDBAm4u9ZhqqL8G0I,499\r\ntwisted/words/im/pbsupport.py,sha256=964WKGL-swV-24Y_JT1-5hvfZwBxixjP-aDq5BebcJ8,9676\r\ntwisted/words/iwords.py,sha256=YtWBU_LM980pJN6_MjMToSVkZteZXYtTgM-wg5S9kPM,8528\r\ntwisted/words/protocols/__init__.py,sha256=zmeNC2QVvHipjDnBJSx2CKRWMONswC98R2IlwuAhWBw,97\r\ntwisted/words/protocols/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/words/protocols/__pycache__/irc.cpython-36.pyc,,\r\ntwisted/words/protocols/irc.py,sha256=spjIqZTWOAecb1e8iP5yTCxt5ArerCjo1gRpkxY_54I,125664\r\ntwisted/words/protocols/jabber/__init__.py,sha256=yofokZPwf09uggpzpyRuUCZf_qAkzijZZCZnDpkEN90,167\r\ntwisted/words/protocols/jabber/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/words/protocols/jabber/__pycache__/client.cpython-36.pyc,,\r\ntwisted/words/protocols/jabber/__pycache__/component.cpython-36.pyc,,\r\ntwisted/words/protocols/jabber/__pycache__/error.cpython-36.pyc,,\r\ntwisted/words/protocols/jabber/__pycache__/ijabber.cpython-36.pyc,,\r\ntwisted/words/protocols/jabber/__pycache__/jid.cpython-36.pyc,,\r\ntwisted/words/protocols/jabber/__pycache__/jstrports.cpython-36.pyc,,\r\ntwisted/words/protocols/jabber/__pycache__/sasl.cpython-36.pyc,,\r\ntwisted/words/protocols/jabber/__pycache__/sasl_mechanisms.cpython-36.pyc,,\r\ntwisted/words/protocols/jabber/__pycache__/xmlstream.cpython-36.pyc,,\r\ntwisted/words/protocols/jabber/__pycache__/xmpp_stringprep.cpython-36.pyc,,\r\ntwisted/words/protocols/jabber/client.py,sha256=L4rpVpZFzNGjaGw7nb4468ZIpPxzPdlRa6mjiJZIZ3U,14382\r\ntwisted/words/protocols/jabber/component.py,sha256=bcXoz0-mtxYrYjZy8m_BlFJhuiZk3TG5jQm_hLHx15o,15595\r\ntwisted/words/protocols/jabber/error.py,sha256=GsmBMFqyQ3dJMfMebbocmF1Dp_MFYWObsKswKoqiwLA,10802\r\ntwisted/words/protocols/jabber/ijabber.py,sha256=R2Y4N6jWJFb7Rqz5O_QelpHtbQpCA6yjGXNUWXe8xpE,5380\r\ntwisted/words/protocols/jabber/jid.py,sha256=xqT9MfeTo2YD2hqSmFJqkxmi6Fsf_3zdy423UWukFTE,7249\r\ntwisted/words/protocols/jabber/jstrports.py,sha256=RoATh0iNGE-qN1MoJKTd9TXN_51Sshoo80a7qlJQ2Nc,978\r\ntwisted/words/protocols/jabber/sasl.py,sha256=uEVeYQ9snoX4ODHQmxOQSC0-zIWEoA8Dnaki-vpxiFA,7461\r\ntwisted/words/protocols/jabber/sasl_mechanisms.py,sha256=rPBzN-_kiyIne3GDVHVyHi8tRoKoEeS2Nv2tD46un2U,8730\r\ntwisted/words/protocols/jabber/xmlstream.py,sha256=bExNRabsilWpyGLxjQeat4TJoHt7nE0OegMb4NBGLUg,36848\r\ntwisted/words/protocols/jabber/xmpp_stringprep.py,sha256=JaC22A1_c9_mR0RoxjHZ1oO_VKbRHE4h4kViPK9YcGQ,7221\r\ntwisted/words/service.py,sha256=gREUR1_Cq5kEUEDA9BnjWAM87nqYq_3JPUoIZf7VjTM,38173\r\ntwisted/words/tap.py,sha256=a0Q_SX7jt6adZYHX_sSkB16qwWqz-uLGTOYV-br54W8,2422\r\ntwisted/words/test/__init__.py,sha256=wDdSRMUVT0_hf5Fe36M3C6GiB4N1TOqgB41q9B-Ia04,14\r\ntwisted/words/test/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_basechat.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_basesupport.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_domish.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_irc.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_irc_service.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_ircsupport.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_jabberclient.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_jabbercomponent.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_jabbererror.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_jabberjid.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_jabberjstrports.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_jabbersasl.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_jabbersaslmechanisms.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_jabberxmlstream.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_jabberxmppstringprep.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_service.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_tap.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_xishutil.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_xmlstream.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_xmpproutertap.cpython-36.pyc,,\r\ntwisted/words/test/__pycache__/test_xpath.cpython-36.pyc,,\r\ntwisted/words/test/test_basechat.py,sha256=y01cIaQ3LrPRUbsdsiTt50w5WeRu-tQrDLHqZe9MQos,2504\r\ntwisted/words/test/test_basesupport.py,sha256=YtA2z8fxt1aP-AYSHpO3PCLNA9t-G5De5ibFH_JEEd8,3064\r\ntwisted/words/test/test_domish.py,sha256=QFHbVSG9SHOy0IJ2_Gx-hTD-KLHHGVeSMJC8IinO3xA,20172\r\ntwisted/words/test/test_irc.py,sha256=LNcjt-o8U2BSbxx6kNpBb-b5z5OTi1kbuM54pwfQIxU,103397\r\ntwisted/words/test/test_irc_service.py,sha256=X_pjwDVCfKBShdEHIiezZH4UFyoyxWaRkAWzP5yGEOM,9639\r\ntwisted/words/test/test_ircsupport.py,sha256=vhzh3PXjUynPnsf3NwZ5Nu67w-4ZBuC4u1Oiz4tBVgs,10702\r\ntwisted/words/test/test_jabberclient.py,sha256=22MQ-lfQCgrRe9r5qTmXuHluFa_pPaxSRHkONpAlj4E,16866\r\ntwisted/words/test/test_jabbercomponent.py,sha256=gw_WkkLLegqMjjWpnCJP59pSNlgBQB0Wbu7mLjpPDe0,14204\r\ntwisted/words/test/test_jabbererror.py,sha256=h97z_XCO11UhFw8Zkb2GH1y31uF6wcILTIdkTdqdsNU,11521\r\ntwisted/words/test/test_jabberjid.py,sha256=5WlXkppYf9H7y_zDOLpBaXAYo2Am2SB0SkvT4x2_LN0,7210\r\ntwisted/words/test/test_jabberjstrports.py,sha256=0SJ1Z8J27DcBHANt-7w6rgn34rlY65LNaTZcp2ysQuY,996\r\ntwisted/words/test/test_jabbersasl.py,sha256=2aTrH1bZXhmejB0ILDjcYHOrAvWN_nM6tMPaGOoBrTU,9432\r\ntwisted/words/test/test_jabbersaslmechanisms.py,sha256=uz_kmwx2T_sFGms27gZ7NGbGBPESRGy46HiWiP2o6mU,5758\r\ntwisted/words/test/test_jabberxmlstream.py,sha256=kasBxkHYAr22DwlscSsO9dNUk8xmFQQ9bphSgk0hnbA,45718\r\ntwisted/words/test/test_jabberxmppstringprep.py,sha256=9E7K3ji2kRRzTYU9NWqqjdSUyvT4iOxYJELgVZhDShk,5549\r\ntwisted/words/test/test_service.py,sha256=cH-DqZL7lV4_kTHlyF6_XzA3w9g4Zs8lbt0J2XdRqWw,28462\r\ntwisted/words/test/test_tap.py,sha256=rNN4d-kYxOe-6dUmRwHmJe1wjN74Px0v2MltP02_TB4,2180\r\ntwisted/words/test/test_xishutil.py,sha256=onFjooPZ3cM3r42-iw2H9ihBcXZ5q865C8p5JgpftgA,9396\r\ntwisted/words/test/test_xmlstream.py,sha256=YuCLqVj1s1Ccll11b7OG_bm8IaoNOlFjNZeNKeLIfJQ,6274\r\ntwisted/words/test/test_xmpproutertap.py,sha256=qROkHmUyHZ1kRwThHV9-28LOhR74lQJXM-g5NUIRMww,2398\r\ntwisted/words/test/test_xpath.py,sha256=m2Fvr_21iIKlBiWNWp-7Pf8YTJm6f9_e1t9Ga4XjMO4,11002\r\ntwisted/words/xish/__init__.py,sha256=XJs3sqZxj1QVTrrgkbVAUcpxMekKLPEKzuEXFJVwp0k,177\r\ntwisted/words/xish/__pycache__/__init__.cpython-36.pyc,,\r\ntwisted/words/xish/__pycache__/domish.cpython-36.pyc,,\r\ntwisted/words/xish/__pycache__/utility.cpython-36.pyc,,\r\ntwisted/words/xish/__pycache__/xmlstream.cpython-36.pyc,,\r\ntwisted/words/xish/__pycache__/xpath.cpython-36.pyc,,\r\ntwisted/words/xish/__pycache__/xpathparser.cpython-36.pyc,,\r\ntwisted/words/xish/domish.py,sha256=O41aNQaLjs5aAhleDGctdPOG5EU1r9QQJ_K6JHLEIlY,30564\r\ntwisted/words/xish/utility.py,sha256=bCnYogLhRc1BWprU8ewiPqiU9kCUUoDZQqcdZoXFuZI,13482\r\ntwisted/words/xish/xmlstream.py,sha256=p9zjmPIaBSDFIb8a4Cgi6ReOIeDO4GllurTclNLljJc,9189\r\ntwisted/words/xish/xpath.py,sha256=KLvSEWoNXnD7ruqsATQYIy70cMFD7uXE8B7mp6xV3bY,9556\r\ntwisted/words/xish/xpathparser.g,sha256=eJQMsCzdX76niIJm8hHiLNLLqq4G6uJl6TDx9iPx6qk,18122\r\ntwisted/words/xish/xpathparser.py,sha256=iPE2dtF79_SU2i0GDQR9jW2Gc2UP6yWeJ_EEgPLCHwk,22851\r\ntwisted/words/xmpproutertap.py,sha256=n9oc9f4xelocf6NGS0_BreuRGbe9YBMpsdKuMjPrd8E,820\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Twisted-19.7.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.33.4)\nRoot-Is-Purelib: false\nTag: cp36-cp36m-manylinux1_x86_64\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Twisted-19.7.0.dist-info/entry_points.txt",
    "content": "[console_scripts]\ncftp = twisted.conch.scripts.cftp:run\nckeygen = twisted.conch.scripts.ckeygen:run\nconch = twisted.conch.scripts.conch:run\nmailmail = twisted.mail.scripts.mailmail:run\npyhtmlizer = twisted.scripts.htmlizer:run\ntkconch = twisted.conch.scripts.tkconch:run\ntrial = twisted.scripts.trial:run\ntwist = twisted.application.twist._twist:Twist.main\ntwistd = twisted.scripts.twistd:run\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/Twisted-19.7.0.dist-info/top_level.txt",
    "content": "twisted\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/__init__.py",
    "content": "from __future__ import absolute_import, division, print_function\n\nfrom functools import partial\n\nfrom . import converters, exceptions, filters, validators\nfrom ._config import get_run_validators, set_run_validators\nfrom ._funcs import asdict, assoc, astuple, evolve, has\nfrom ._make import (\n    NOTHING,\n    Attribute,\n    Factory,\n    attrib,\n    attrs,\n    fields,\n    fields_dict,\n    make_class,\n    validate,\n)\nfrom ._version_info import VersionInfo\n\n\n__version__ = \"19.3.0\"\n__version_info__ = VersionInfo._from_version_string(__version__)\n\n__title__ = \"attrs\"\n__description__ = \"Classes Without Boilerplate\"\n__url__ = \"https://www.attrs.org/\"\n__uri__ = __url__\n__doc__ = __description__ + \" <\" + __uri__ + \">\"\n\n__author__ = \"Hynek Schlawack\"\n__email__ = \"hs@ox.cx\"\n\n__license__ = \"MIT\"\n__copyright__ = \"Copyright (c) 2015 Hynek Schlawack\"\n\n\ns = attributes = attrs\nib = attr = attrib\ndataclass = partial(attrs, auto_attribs=True)  # happy Easter ;)\n\n\n__all__ = [\n    \"Attribute\",\n    \"Factory\",\n    \"NOTHING\",\n    \"asdict\",\n    \"assoc\",\n    \"astuple\",\n    \"attr\",\n    \"attrib\",\n    \"attributes\",\n    \"attrs\",\n    \"converters\",\n    \"evolve\",\n    \"exceptions\",\n    \"fields\",\n    \"fields_dict\",\n    \"filters\",\n    \"get_run_validators\",\n    \"has\",\n    \"ib\",\n    \"make_class\",\n    \"s\",\n    \"set_run_validators\",\n    \"validate\",\n    \"validators\",\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/__init__.pyi",
    "content": "from typing import (\n    Any,\n    Callable,\n    Dict,\n    Generic,\n    List,\n    Optional,\n    Sequence,\n    Mapping,\n    Tuple,\n    Type,\n    TypeVar,\n    Union,\n    overload,\n)\n\n# `import X as X` is required to make these public\nfrom . import exceptions as exceptions\nfrom . import filters as filters\nfrom . import converters as converters\nfrom . import validators as validators\n\nfrom ._version_info import VersionInfo\n\n__version__: str\n__version_info__: VersionInfo\n__title__: str\n__description__: str\n__url__: str\n__uri__: str\n__author__: str\n__email__: str\n__license__: str\n__copyright__: str\n\n_T = TypeVar(\"_T\")\n_C = TypeVar(\"_C\", bound=type)\n\n_ValidatorType = Callable[[Any, Attribute[_T], _T], Any]\n_ConverterType = Callable[[Any], _T]\n_FilterType = Callable[[Attribute[_T], _T], bool]\n_ReprType = Callable[[Any], str]\n_ReprArgType = Union[bool, _ReprType]\n# FIXME: in reality, if multiple validators are passed they must be in a list or tuple,\n# but those are invariant and so would prevent subtypes of _ValidatorType from working\n# when passed in a list or tuple.\n_ValidatorArgType = Union[_ValidatorType[_T], Sequence[_ValidatorType[_T]]]\n\n# _make --\n\nNOTHING: object\n\n# NOTE: Factory lies about its return type to make this possible: `x: List[int] = Factory(list)`\n# Work around mypy issue #4554 in the common case by using an overload.\n@overload\ndef Factory(factory: Callable[[], _T]) -> _T: ...\n@overload\ndef Factory(\n    factory: Union[Callable[[Any], _T], Callable[[], _T]],\n    takes_self: bool = ...,\n) -> _T: ...\n\nclass Attribute(Generic[_T]):\n    name: str\n    default: Optional[_T]\n    validator: Optional[_ValidatorType[_T]]\n    repr: _ReprArgType\n    cmp: bool\n    eq: bool\n    order: bool\n    hash: Optional[bool]\n    init: bool\n    converter: Optional[_ConverterType[_T]]\n    metadata: Dict[Any, Any]\n    type: Optional[Type[_T]]\n    kw_only: bool\n\n# NOTE: We had several choices for the annotation to use for type arg:\n# 1) Type[_T]\n#   - Pros: Handles simple cases correctly\n#   - Cons: Might produce less informative errors in the case of conflicting TypeVars\n#   e.g. `attr.ib(default='bad', type=int)`\n# 2) Callable[..., _T]\n#   - Pros: Better error messages than #1 for conflicting TypeVars\n#   - Cons: Terrible error messages for validator checks.\n#   e.g. attr.ib(type=int, validator=validate_str)\n#        -> error: Cannot infer function type argument\n# 3) type (and do all of the work in the mypy plugin)\n#   - Pros: Simple here, and we could customize the plugin with our own errors.\n#   - Cons: Would need to write mypy plugin code to handle all the cases.\n# We chose option #1.\n\n# `attr` lies about its return type to make the following possible:\n#     attr()    -> Any\n#     attr(8)   -> int\n#     attr(validator=<some callable>)  -> Whatever the callable expects.\n# This makes this type of assignments possible:\n#     x: int = attr(8)\n#\n# This form catches explicit None or no default but with no other arguments returns Any.\n@overload\ndef attrib(\n    default: None = ...,\n    validator: None = ...,\n    repr: _ReprArgType = ...,\n    cmp: Optional[bool] = ...,\n    hash: Optional[bool] = ...,\n    init: bool = ...,\n    metadata: Optional[Mapping[Any, Any]] = ...,\n    type: None = ...,\n    converter: None = ...,\n    factory: None = ...,\n    kw_only: bool = ...,\n    eq: Optional[bool] = ...,\n    order: Optional[bool] = ...,\n) -> Any: ...\n\n# This form catches an explicit None or no default and infers the type from the other arguments.\n@overload\ndef attrib(\n    default: None = ...,\n    validator: Optional[_ValidatorArgType[_T]] = ...,\n    repr: _ReprArgType = ...,\n    cmp: Optional[bool] = ...,\n    hash: Optional[bool] = ...,\n    init: bool = ...,\n    metadata: Optional[Mapping[Any, Any]] = ...,\n    type: Optional[Type[_T]] = ...,\n    converter: Optional[_ConverterType[_T]] = ...,\n    factory: Optional[Callable[[], _T]] = ...,\n    kw_only: bool = ...,\n    eq: Optional[bool] = ...,\n    order: Optional[bool] = ...,\n) -> _T: ...\n\n# This form catches an explicit default argument.\n@overload\ndef attrib(\n    default: _T,\n    validator: Optional[_ValidatorArgType[_T]] = ...,\n    repr: _ReprArgType = ...,\n    cmp: Optional[bool] = ...,\n    hash: Optional[bool] = ...,\n    init: bool = ...,\n    metadata: Optional[Mapping[Any, Any]] = ...,\n    type: Optional[Type[_T]] = ...,\n    converter: Optional[_ConverterType[_T]] = ...,\n    factory: Optional[Callable[[], _T]] = ...,\n    kw_only: bool = ...,\n    eq: Optional[bool] = ...,\n    order: Optional[bool] = ...,\n) -> _T: ...\n\n# This form covers type=non-Type: e.g. forward references (str), Any\n@overload\ndef attrib(\n    default: Optional[_T] = ...,\n    validator: Optional[_ValidatorArgType[_T]] = ...,\n    repr: _ReprArgType = ...,\n    cmp: Optional[bool] = ...,\n    hash: Optional[bool] = ...,\n    init: bool = ...,\n    metadata: Optional[Mapping[Any, Any]] = ...,\n    type: object = ...,\n    converter: Optional[_ConverterType[_T]] = ...,\n    factory: Optional[Callable[[], _T]] = ...,\n    kw_only: bool = ...,\n    eq: Optional[bool] = ...,\n    order: Optional[bool] = ...,\n) -> Any: ...\n@overload\ndef attrs(\n    maybe_cls: _C,\n    these: Optional[Dict[str, Any]] = ...,\n    repr_ns: Optional[str] = ...,\n    repr: bool = ...,\n    cmp: Optional[bool] = ...,\n    hash: Optional[bool] = ...,\n    init: bool = ...,\n    slots: bool = ...,\n    frozen: bool = ...,\n    weakref_slot: bool = ...,\n    str: bool = ...,\n    auto_attribs: bool = ...,\n    kw_only: bool = ...,\n    cache_hash: bool = ...,\n    auto_exc: bool = ...,\n    eq: Optional[bool] = ...,\n    order: Optional[bool] = ...,\n) -> _C: ...\n@overload\ndef attrs(\n    maybe_cls: None = ...,\n    these: Optional[Dict[str, Any]] = ...,\n    repr_ns: Optional[str] = ...,\n    repr: bool = ...,\n    cmp: Optional[bool] = ...,\n    hash: Optional[bool] = ...,\n    init: bool = ...,\n    slots: bool = ...,\n    frozen: bool = ...,\n    weakref_slot: bool = ...,\n    str: bool = ...,\n    auto_attribs: bool = ...,\n    kw_only: bool = ...,\n    cache_hash: bool = ...,\n    auto_exc: bool = ...,\n    eq: Optional[bool] = ...,\n    order: Optional[bool] = ...,\n) -> Callable[[_C], _C]: ...\n\n# TODO: add support for returning NamedTuple from the mypy plugin\nclass _Fields(Tuple[Attribute[Any], ...]):\n    def __getattr__(self, name: str) -> Attribute[Any]: ...\n\ndef fields(cls: type) -> _Fields: ...\ndef fields_dict(cls: type) -> Dict[str, Attribute[Any]]: ...\ndef validate(inst: Any) -> None: ...\n\n# TODO: add support for returning a proper attrs class from the mypy plugin\n# we use Any instead of _CountingAttr so that e.g. `make_class('Foo', [attr.ib()])` is valid\ndef make_class(\n    name: str,\n    attrs: Union[List[str], Tuple[str, ...], Dict[str, Any]],\n    bases: Tuple[type, ...] = ...,\n    repr_ns: Optional[str] = ...,\n    repr: bool = ...,\n    cmp: Optional[bool] = ...,\n    hash: Optional[bool] = ...,\n    init: bool = ...,\n    slots: bool = ...,\n    frozen: bool = ...,\n    weakref_slot: bool = ...,\n    str: bool = ...,\n    auto_attribs: bool = ...,\n    kw_only: bool = ...,\n    cache_hash: bool = ...,\n    auto_exc: bool = ...,\n    eq: Optional[bool] = ...,\n    order: Optional[bool] = ...,\n) -> type: ...\n\n# _funcs --\n\n# TODO: add support for returning TypedDict from the mypy plugin\n# FIXME: asdict/astuple do not honor their factory args.  waiting on one of these:\n# https://github.com/python/mypy/issues/4236\n# https://github.com/python/typing/issues/253\ndef asdict(\n    inst: Any,\n    recurse: bool = ...,\n    filter: Optional[_FilterType[Any]] = ...,\n    dict_factory: Type[Mapping[Any, Any]] = ...,\n    retain_collection_types: bool = ...,\n) -> Dict[str, Any]: ...\n\n# TODO: add support for returning NamedTuple from the mypy plugin\ndef astuple(\n    inst: Any,\n    recurse: bool = ...,\n    filter: Optional[_FilterType[Any]] = ...,\n    tuple_factory: Type[Sequence[Any]] = ...,\n    retain_collection_types: bool = ...,\n) -> Tuple[Any, ...]: ...\ndef has(cls: type) -> bool: ...\ndef assoc(inst: _T, **changes: Any) -> _T: ...\ndef evolve(inst: _T, **changes: Any) -> _T: ...\n\n# _config --\n\ndef set_run_validators(run: bool) -> None: ...\ndef get_run_validators() -> bool: ...\n\n# aliases --\n\ns = attributes = attrs\nib = attr = attrib\ndataclass = attrs  # Technically, partial(attrs, auto_attribs=True) ;)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/_compat.py",
    "content": "from __future__ import absolute_import, division, print_function\n\nimport platform\nimport sys\nimport types\nimport warnings\n\n\nPY2 = sys.version_info[0] == 2\nPYPY = platform.python_implementation() == \"PyPy\"\n\n\nif PYPY or sys.version_info[:2] >= (3, 6):\n    ordered_dict = dict\nelse:\n    from collections import OrderedDict\n\n    ordered_dict = OrderedDict\n\n\nif PY2:\n    from UserDict import IterableUserDict\n    from collections import Mapping, Sequence\n\n    # We 'bundle' isclass instead of using inspect as importing inspect is\n    # fairly expensive (order of 10-15 ms for a modern machine in 2016)\n    def isclass(klass):\n        return isinstance(klass, (type, types.ClassType))\n\n    # TYPE is used in exceptions, repr(int) is different on Python 2 and 3.\n    TYPE = \"type\"\n\n    def iteritems(d):\n        return d.iteritems()\n\n    # Python 2 is bereft of a read-only dict proxy, so we make one!\n    class ReadOnlyDict(IterableUserDict):\n        \"\"\"\n        Best-effort read-only dict wrapper.\n        \"\"\"\n\n        def __setitem__(self, key, val):\n            # We gently pretend we're a Python 3 mappingproxy.\n            raise TypeError(\n                \"'mappingproxy' object does not support item assignment\"\n            )\n\n        def update(self, _):\n            # We gently pretend we're a Python 3 mappingproxy.\n            raise AttributeError(\n                \"'mappingproxy' object has no attribute 'update'\"\n            )\n\n        def __delitem__(self, _):\n            # We gently pretend we're a Python 3 mappingproxy.\n            raise TypeError(\n                \"'mappingproxy' object does not support item deletion\"\n            )\n\n        def clear(self):\n            # We gently pretend we're a Python 3 mappingproxy.\n            raise AttributeError(\n                \"'mappingproxy' object has no attribute 'clear'\"\n            )\n\n        def pop(self, key, default=None):\n            # We gently pretend we're a Python 3 mappingproxy.\n            raise AttributeError(\n                \"'mappingproxy' object has no attribute 'pop'\"\n            )\n\n        def popitem(self):\n            # We gently pretend we're a Python 3 mappingproxy.\n            raise AttributeError(\n                \"'mappingproxy' object has no attribute 'popitem'\"\n            )\n\n        def setdefault(self, key, default=None):\n            # We gently pretend we're a Python 3 mappingproxy.\n            raise AttributeError(\n                \"'mappingproxy' object has no attribute 'setdefault'\"\n            )\n\n        def __repr__(self):\n            # Override to be identical to the Python 3 version.\n            return \"mappingproxy(\" + repr(self.data) + \")\"\n\n    def metadata_proxy(d):\n        res = ReadOnlyDict()\n        res.data.update(d)  # We blocked update, so we have to do it like this.\n        return res\n\n    def just_warn(*args, **kw):  # pragma: nocover\n        \"\"\"\n        We only warn on Python 3 because we are not aware of any concrete\n        consequences of not setting the cell on Python 2.\n        \"\"\"\n\n\nelse:  # Python 3 and later.\n    from collections.abc import Mapping, Sequence  # noqa\n\n    def just_warn(*args, **kw):\n        \"\"\"\n        We only warn on Python 3 because we are not aware of any concrete\n        consequences of not setting the cell on Python 2.\n        \"\"\"\n        warnings.warn(\n            \"Running interpreter doesn't sufficiently support code object \"\n            \"introspection.  Some features like bare super() or accessing \"\n            \"__class__ will not work with slotted classes.\",\n            RuntimeWarning,\n            stacklevel=2,\n        )\n\n    def isclass(klass):\n        return isinstance(klass, type)\n\n    TYPE = \"class\"\n\n    def iteritems(d):\n        return d.items()\n\n    def metadata_proxy(d):\n        return types.MappingProxyType(dict(d))\n\n\ndef make_set_closure_cell():\n    \"\"\"Return a function of two arguments (cell, value) which sets\n    the value stored in the closure cell `cell` to `value`.\n    \"\"\"\n    # pypy makes this easy. (It also supports the logic below, but\n    # why not do the easy/fast thing?)\n    if PYPY:  # pragma: no cover\n\n        def set_closure_cell(cell, value):\n            cell.__setstate__((value,))\n\n        return set_closure_cell\n\n    # Otherwise gotta do it the hard way.\n\n    # Create a function that will set its first cellvar to `value`.\n    def set_first_cellvar_to(value):\n        x = value\n        return\n\n        # This function will be eliminated as dead code, but\n        # not before its reference to `x` forces `x` to be\n        # represented as a closure cell rather than a local.\n        def force_x_to_be_a_cell():  # pragma: no cover\n            return x\n\n    try:\n        # Extract the code object and make sure our assumptions about\n        # the closure behavior are correct.\n        if PY2:\n            co = set_first_cellvar_to.func_code\n        else:\n            co = set_first_cellvar_to.__code__\n        if co.co_cellvars != (\"x\",) or co.co_freevars != ():\n            raise AssertionError  # pragma: no cover\n\n        # Convert this code object to a code object that sets the\n        # function's first _freevar_ (not cellvar) to the argument.\n        if sys.version_info >= (3, 8):\n            # CPython 3.8+ has an incompatible CodeType signature\n            # (added a posonlyargcount argument) but also added\n            # CodeType.replace() to do this without counting parameters.\n            set_first_freevar_code = co.replace(\n                co_cellvars=co.co_freevars, co_freevars=co.co_cellvars\n            )\n        else:\n            args = [co.co_argcount]\n            if not PY2:\n                args.append(co.co_kwonlyargcount)\n            args.extend(\n                [\n                    co.co_nlocals,\n                    co.co_stacksize,\n                    co.co_flags,\n                    co.co_code,\n                    co.co_consts,\n                    co.co_names,\n                    co.co_varnames,\n                    co.co_filename,\n                    co.co_name,\n                    co.co_firstlineno,\n                    co.co_lnotab,\n                    # These two arguments are reversed:\n                    co.co_cellvars,\n                    co.co_freevars,\n                ]\n            )\n            set_first_freevar_code = types.CodeType(*args)\n\n        def set_closure_cell(cell, value):\n            # Create a function using the set_first_freevar_code,\n            # whose first closure cell is `cell`. Calling it will\n            # change the value of that cell.\n            setter = types.FunctionType(\n                set_first_freevar_code, {}, \"setter\", (), (cell,)\n            )\n            # And call it to set the cell.\n            setter(value)\n\n        # Make sure it works on this interpreter:\n        def make_func_with_cell():\n            x = None\n\n            def func():\n                return x  # pragma: no cover\n\n            return func\n\n        if PY2:\n            cell = make_func_with_cell().func_closure[0]\n        else:\n            cell = make_func_with_cell().__closure__[0]\n        set_closure_cell(cell, 100)\n        if cell.cell_contents != 100:\n            raise AssertionError  # pragma: no cover\n\n    except Exception:\n        return just_warn\n    else:\n        return set_closure_cell\n\n\nset_closure_cell = make_set_closure_cell()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/_config.py",
    "content": "from __future__ import absolute_import, division, print_function\n\n\n__all__ = [\"set_run_validators\", \"get_run_validators\"]\n\n_run_validators = True\n\n\ndef set_run_validators(run):\n    \"\"\"\n    Set whether or not validators are run.  By default, they are run.\n    \"\"\"\n    if not isinstance(run, bool):\n        raise TypeError(\"'run' must be bool.\")\n    global _run_validators\n    _run_validators = run\n\n\ndef get_run_validators():\n    \"\"\"\n    Return whether or not validators are run.\n    \"\"\"\n    return _run_validators\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/_funcs.py",
    "content": "from __future__ import absolute_import, division, print_function\n\nimport copy\n\nfrom ._compat import iteritems\nfrom ._make import NOTHING, _obj_setattr, fields\nfrom .exceptions import AttrsAttributeNotFoundError\n\n\ndef asdict(\n    inst,\n    recurse=True,\n    filter=None,\n    dict_factory=dict,\n    retain_collection_types=False,\n):\n    \"\"\"\n    Return the ``attrs`` attribute values of *inst* as a dict.\n\n    Optionally recurse into other ``attrs``-decorated classes.\n\n    :param inst: Instance of an ``attrs``-decorated class.\n    :param bool recurse: Recurse into classes that are also\n        ``attrs``-decorated.\n    :param callable filter: A callable whose return code determines whether an\n        attribute or element is included (``True``) or dropped (``False``).  Is\n        called with the `attr.Attribute` as the first argument and the\n        value as the second argument.\n    :param callable dict_factory: A callable to produce dictionaries from.  For\n        example, to produce ordered dictionaries instead of normal Python\n        dictionaries, pass in ``collections.OrderedDict``.\n    :param bool retain_collection_types: Do not convert to ``list`` when\n        encountering an attribute whose type is ``tuple`` or ``set``.  Only\n        meaningful if ``recurse`` is ``True``.\n\n    :rtype: return type of *dict_factory*\n\n    :raise attr.exceptions.NotAnAttrsClassError: If *cls* is not an ``attrs``\n        class.\n\n    ..  versionadded:: 16.0.0 *dict_factory*\n    ..  versionadded:: 16.1.0 *retain_collection_types*\n    \"\"\"\n    attrs = fields(inst.__class__)\n    rv = dict_factory()\n    for a in attrs:\n        v = getattr(inst, a.name)\n        if filter is not None and not filter(a, v):\n            continue\n        if recurse is True:\n            if has(v.__class__):\n                rv[a.name] = asdict(\n                    v, True, filter, dict_factory, retain_collection_types\n                )\n            elif isinstance(v, (tuple, list, set)):\n                cf = v.__class__ if retain_collection_types is True else list\n                rv[a.name] = cf(\n                    [\n                        _asdict_anything(\n                            i, filter, dict_factory, retain_collection_types\n                        )\n                        for i in v\n                    ]\n                )\n            elif isinstance(v, dict):\n                df = dict_factory\n                rv[a.name] = df(\n                    (\n                        _asdict_anything(\n                            kk, filter, df, retain_collection_types\n                        ),\n                        _asdict_anything(\n                            vv, filter, df, retain_collection_types\n                        ),\n                    )\n                    for kk, vv in iteritems(v)\n                )\n            else:\n                rv[a.name] = v\n        else:\n            rv[a.name] = v\n    return rv\n\n\ndef _asdict_anything(val, filter, dict_factory, retain_collection_types):\n    \"\"\"\n    ``asdict`` only works on attrs instances, this works on anything.\n    \"\"\"\n    if getattr(val.__class__, \"__attrs_attrs__\", None) is not None:\n        # Attrs class.\n        rv = asdict(val, True, filter, dict_factory, retain_collection_types)\n    elif isinstance(val, (tuple, list, set)):\n        cf = val.__class__ if retain_collection_types is True else list\n        rv = cf(\n            [\n                _asdict_anything(\n                    i, filter, dict_factory, retain_collection_types\n                )\n                for i in val\n            ]\n        )\n    elif isinstance(val, dict):\n        df = dict_factory\n        rv = df(\n            (\n                _asdict_anything(kk, filter, df, retain_collection_types),\n                _asdict_anything(vv, filter, df, retain_collection_types),\n            )\n            for kk, vv in iteritems(val)\n        )\n    else:\n        rv = val\n    return rv\n\n\ndef astuple(\n    inst,\n    recurse=True,\n    filter=None,\n    tuple_factory=tuple,\n    retain_collection_types=False,\n):\n    \"\"\"\n    Return the ``attrs`` attribute values of *inst* as a tuple.\n\n    Optionally recurse into other ``attrs``-decorated classes.\n\n    :param inst: Instance of an ``attrs``-decorated class.\n    :param bool recurse: Recurse into classes that are also\n        ``attrs``-decorated.\n    :param callable filter: A callable whose return code determines whether an\n        attribute or element is included (``True``) or dropped (``False``).  Is\n        called with the `attr.Attribute` as the first argument and the\n        value as the second argument.\n    :param callable tuple_factory: A callable to produce tuples from.  For\n        example, to produce lists instead of tuples.\n    :param bool retain_collection_types: Do not convert to ``list``\n        or ``dict`` when encountering an attribute which type is\n        ``tuple``, ``dict`` or ``set``.  Only meaningful if ``recurse`` is\n        ``True``.\n\n    :rtype: return type of *tuple_factory*\n\n    :raise attr.exceptions.NotAnAttrsClassError: If *cls* is not an ``attrs``\n        class.\n\n    ..  versionadded:: 16.2.0\n    \"\"\"\n    attrs = fields(inst.__class__)\n    rv = []\n    retain = retain_collection_types  # Very long. :/\n    for a in attrs:\n        v = getattr(inst, a.name)\n        if filter is not None and not filter(a, v):\n            continue\n        if recurse is True:\n            if has(v.__class__):\n                rv.append(\n                    astuple(\n                        v,\n                        recurse=True,\n                        filter=filter,\n                        tuple_factory=tuple_factory,\n                        retain_collection_types=retain,\n                    )\n                )\n            elif isinstance(v, (tuple, list, set)):\n                cf = v.__class__ if retain is True else list\n                rv.append(\n                    cf(\n                        [\n                            astuple(\n                                j,\n                                recurse=True,\n                                filter=filter,\n                                tuple_factory=tuple_factory,\n                                retain_collection_types=retain,\n                            )\n                            if has(j.__class__)\n                            else j\n                            for j in v\n                        ]\n                    )\n                )\n            elif isinstance(v, dict):\n                df = v.__class__ if retain is True else dict\n                rv.append(\n                    df(\n                        (\n                            astuple(\n                                kk,\n                                tuple_factory=tuple_factory,\n                                retain_collection_types=retain,\n                            )\n                            if has(kk.__class__)\n                            else kk,\n                            astuple(\n                                vv,\n                                tuple_factory=tuple_factory,\n                                retain_collection_types=retain,\n                            )\n                            if has(vv.__class__)\n                            else vv,\n                        )\n                        for kk, vv in iteritems(v)\n                    )\n                )\n            else:\n                rv.append(v)\n        else:\n            rv.append(v)\n    return rv if tuple_factory is list else tuple_factory(rv)\n\n\ndef has(cls):\n    \"\"\"\n    Check whether *cls* is a class with ``attrs`` attributes.\n\n    :param type cls: Class to introspect.\n    :raise TypeError: If *cls* is not a class.\n\n    :rtype: bool\n    \"\"\"\n    return getattr(cls, \"__attrs_attrs__\", None) is not None\n\n\ndef assoc(inst, **changes):\n    \"\"\"\n    Copy *inst* and apply *changes*.\n\n    :param inst: Instance of a class with ``attrs`` attributes.\n    :param changes: Keyword changes in the new copy.\n\n    :return: A copy of inst with *changes* incorporated.\n\n    :raise attr.exceptions.AttrsAttributeNotFoundError: If *attr_name* couldn't\n        be found on *cls*.\n    :raise attr.exceptions.NotAnAttrsClassError: If *cls* is not an ``attrs``\n        class.\n\n    ..  deprecated:: 17.1.0\n        Use `evolve` instead.\n    \"\"\"\n    import warnings\n\n    warnings.warn(\n        \"assoc is deprecated and will be removed after 2018/01.\",\n        DeprecationWarning,\n        stacklevel=2,\n    )\n    new = copy.copy(inst)\n    attrs = fields(inst.__class__)\n    for k, v in iteritems(changes):\n        a = getattr(attrs, k, NOTHING)\n        if a is NOTHING:\n            raise AttrsAttributeNotFoundError(\n                \"{k} is not an attrs attribute on {cl}.\".format(\n                    k=k, cl=new.__class__\n                )\n            )\n        _obj_setattr(new, k, v)\n    return new\n\n\ndef evolve(inst, **changes):\n    \"\"\"\n    Create a new instance, based on *inst* with *changes* applied.\n\n    :param inst: Instance of a class with ``attrs`` attributes.\n    :param changes: Keyword changes in the new copy.\n\n    :return: A copy of inst with *changes* incorporated.\n\n    :raise TypeError: If *attr_name* couldn't be found in the class\n        ``__init__``.\n    :raise attr.exceptions.NotAnAttrsClassError: If *cls* is not an ``attrs``\n        class.\n\n    ..  versionadded:: 17.1.0\n    \"\"\"\n    cls = inst.__class__\n    attrs = fields(cls)\n    for a in attrs:\n        if not a.init:\n            continue\n        attr_name = a.name  # To deal with private attributes.\n        init_name = attr_name if attr_name[0] != \"_\" else attr_name[1:]\n        if init_name not in changes:\n            changes[init_name] = getattr(inst, attr_name)\n    return cls(**changes)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/_make.py",
    "content": "from __future__ import absolute_import, division, print_function\n\nimport copy\nimport linecache\nimport sys\nimport threading\nimport uuid\nimport warnings\n\nfrom operator import itemgetter\n\nfrom . import _config\nfrom ._compat import (\n    PY2,\n    isclass,\n    iteritems,\n    metadata_proxy,\n    ordered_dict,\n    set_closure_cell,\n)\nfrom .exceptions import (\n    DefaultAlreadySetError,\n    FrozenInstanceError,\n    NotAnAttrsClassError,\n    PythonTooOldError,\n    UnannotatedAttributeError,\n)\n\n\n# This is used at least twice, so cache it here.\n_obj_setattr = object.__setattr__\n_init_converter_pat = \"__attr_converter_{}\"\n_init_factory_pat = \"__attr_factory_{}\"\n_tuple_property_pat = (\n    \"    {attr_name} = _attrs_property(_attrs_itemgetter({index}))\"\n)\n_classvar_prefixes = (\"typing.ClassVar\", \"t.ClassVar\", \"ClassVar\")\n# we don't use a double-underscore prefix because that triggers\n# name mangling when trying to create a slot for the field\n# (when slots=True)\n_hash_cache_field = \"_attrs_cached_hash\"\n\n_empty_metadata_singleton = metadata_proxy({})\n\n# Unique object for unequivocal getattr() defaults.\n_sentinel = object()\n\n\nclass _Nothing(object):\n    \"\"\"\n    Sentinel class to indicate the lack of a value when ``None`` is ambiguous.\n\n    ``_Nothing`` is a singleton. There is only ever one of it.\n    \"\"\"\n\n    _singleton = None\n\n    def __new__(cls):\n        if _Nothing._singleton is None:\n            _Nothing._singleton = super(_Nothing, cls).__new__(cls)\n        return _Nothing._singleton\n\n    def __repr__(self):\n        return \"NOTHING\"\n\n\nNOTHING = _Nothing()\n\"\"\"\nSentinel to indicate the lack of a value when ``None`` is ambiguous.\n\"\"\"\n\n\ndef attrib(\n    default=NOTHING,\n    validator=None,\n    repr=True,\n    cmp=None,\n    hash=None,\n    init=True,\n    metadata=None,\n    type=None,\n    converter=None,\n    factory=None,\n    kw_only=False,\n    eq=None,\n    order=None,\n):\n    \"\"\"\n    Create a new attribute on a class.\n\n    ..  warning::\n\n        Does *not* do anything unless the class is also decorated with\n        `attr.s`!\n\n    :param default: A value that is used if an ``attrs``-generated ``__init__``\n        is used and no value is passed while instantiating or the attribute is\n        excluded using ``init=False``.\n\n        If the value is an instance of `Factory`, its callable will be\n        used to construct a new value (useful for mutable data types like lists\n        or dicts).\n\n        If a default is not set (or set manually to ``attr.NOTHING``), a value\n        *must* be supplied when instantiating; otherwise a `TypeError`\n        will be raised.\n\n        The default can also be set using decorator notation as shown below.\n\n    :type default: Any value\n\n    :param callable factory: Syntactic sugar for\n        ``default=attr.Factory(callable)``.\n\n    :param validator: `callable` that is called by ``attrs``-generated\n        ``__init__`` methods after the instance has been initialized.  They\n        receive the initialized instance, the `Attribute`, and the\n        passed value.\n\n        The return value is *not* inspected so the validator has to throw an\n        exception itself.\n\n        If a ``list`` is passed, its items are treated as validators and must\n        all pass.\n\n        Validators can be globally disabled and re-enabled using\n        `get_run_validators`.\n\n        The validator can also be set using decorator notation as shown below.\n\n    :type validator: ``callable`` or a ``list`` of ``callable``\\\\ s.\n\n    :param repr: Include this attribute in the generated ``__repr__``\n        method. If ``True``, include the attribute; if ``False``, omit it. By\n        default, the built-in ``repr()`` function is used. To override how the\n        attribute value is formatted, pass a ``callable`` that takes a single\n        value and returns a string. Note that the resulting string is used\n        as-is, i.e. it will be used directly *instead* of calling ``repr()``\n        (the default).\n    :type repr: a ``bool`` or a ``callable`` to use a custom function.\n    :param bool eq: If ``True`` (default), include this attribute in the\n        generated ``__eq__`` and ``__ne__`` methods that check two instances\n        for equality.\n    :param bool order: If ``True`` (default), include this attributes in the\n        generated ``__lt__``, ``__le__``, ``__gt__`` and ``__ge__`` methods.\n    :param bool cmp: Setting to ``True`` is equivalent to setting ``eq=True,\n        order=True``. Deprecated in favor of *eq* and *order*.\n    :param hash: Include this attribute in the generated ``__hash__``\n        method.  If ``None`` (default), mirror *eq*'s value.  This is the\n        correct behavior according the Python spec.  Setting this value to\n        anything else than ``None`` is *discouraged*.\n    :type hash: ``bool`` or ``None``\n    :param bool init: Include this attribute in the generated ``__init__``\n        method.  It is possible to set this to ``False`` and set a default\n        value.  In that case this attributed is unconditionally initialized\n        with the specified default value or factory.\n    :param callable converter: `callable` that is called by\n        ``attrs``-generated ``__init__`` methods to converter attribute's value\n        to the desired format.  It is given the passed-in value, and the\n        returned value will be used as the new value of the attribute.  The\n        value is converted before being passed to the validator, if any.\n    :param metadata: An arbitrary mapping, to be used by third-party\n        components.  See `extending_metadata`.\n    :param type: The type of the attribute.  In Python 3.6 or greater, the\n        preferred method to specify the type is using a variable annotation\n        (see `PEP 526 <https://www.python.org/dev/peps/pep-0526/>`_).\n        This argument is provided for backward compatibility.\n        Regardless of the approach used, the type will be stored on\n        ``Attribute.type``.\n\n        Please note that ``attrs`` doesn't do anything with this metadata by\n        itself. You can use it as part of your own code or for\n        `static type checking <types>`.\n    :param kw_only: Make this attribute keyword-only (Python 3+)\n        in the generated ``__init__`` (if ``init`` is ``False``, this\n        parameter is ignored).\n\n    .. versionadded:: 15.2.0 *convert*\n    .. versionadded:: 16.3.0 *metadata*\n    .. versionchanged:: 17.1.0 *validator* can be a ``list`` now.\n    .. versionchanged:: 17.1.0\n       *hash* is ``None`` and therefore mirrors *eq* by default.\n    .. versionadded:: 17.3.0 *type*\n    .. deprecated:: 17.4.0 *convert*\n    .. versionadded:: 17.4.0 *converter* as a replacement for the deprecated\n       *convert* to achieve consistency with other noun-based arguments.\n    .. versionadded:: 18.1.0\n       ``factory=f`` is syntactic sugar for ``default=attr.Factory(f)``.\n    .. versionadded:: 18.2.0 *kw_only*\n    .. versionchanged:: 19.2.0 *convert* keyword argument removed\n    .. versionchanged:: 19.2.0 *repr* also accepts a custom callable.\n    .. deprecated:: 19.2.0 *cmp* Removal on or after 2021-06-01.\n    .. versionadded:: 19.2.0 *eq* and *order*\n    \"\"\"\n    eq, order = _determine_eq_order(cmp, eq, order)\n\n    if hash is not None and hash is not True and hash is not False:\n        raise TypeError(\n            \"Invalid value for hash.  Must be True, False, or None.\"\n        )\n\n    if factory is not None:\n        if default is not NOTHING:\n            raise ValueError(\n                \"The `default` and `factory` arguments are mutually \"\n                \"exclusive.\"\n            )\n        if not callable(factory):\n            raise ValueError(\"The `factory` argument must be a callable.\")\n        default = Factory(factory)\n\n    if metadata is None:\n        metadata = {}\n\n    return _CountingAttr(\n        default=default,\n        validator=validator,\n        repr=repr,\n        cmp=None,\n        hash=hash,\n        init=init,\n        converter=converter,\n        metadata=metadata,\n        type=type,\n        kw_only=kw_only,\n        eq=eq,\n        order=order,\n    )\n\n\ndef _make_attr_tuple_class(cls_name, attr_names):\n    \"\"\"\n    Create a tuple subclass to hold `Attribute`s for an `attrs` class.\n\n    The subclass is a bare tuple with properties for names.\n\n    class MyClassAttributes(tuple):\n        __slots__ = ()\n        x = property(itemgetter(0))\n    \"\"\"\n    attr_class_name = \"{}Attributes\".format(cls_name)\n    attr_class_template = [\n        \"class {}(tuple):\".format(attr_class_name),\n        \"    __slots__ = ()\",\n    ]\n    if attr_names:\n        for i, attr_name in enumerate(attr_names):\n            attr_class_template.append(\n                _tuple_property_pat.format(index=i, attr_name=attr_name)\n            )\n    else:\n        attr_class_template.append(\"    pass\")\n    globs = {\"_attrs_itemgetter\": itemgetter, \"_attrs_property\": property}\n    eval(compile(\"\\n\".join(attr_class_template), \"\", \"exec\"), globs)\n\n    return globs[attr_class_name]\n\n\n# Tuple class for extracted attributes from a class definition.\n# `base_attrs` is a subset of `attrs`.\n_Attributes = _make_attr_tuple_class(\n    \"_Attributes\",\n    [\n        # all attributes to build dunder methods for\n        \"attrs\",\n        # attributes that have been inherited\n        \"base_attrs\",\n        # map inherited attributes to their originating classes\n        \"base_attrs_map\",\n    ],\n)\n\n\ndef _is_class_var(annot):\n    \"\"\"\n    Check whether *annot* is a typing.ClassVar.\n\n    The string comparison hack is used to avoid evaluating all string\n    annotations which would put attrs-based classes at a performance\n    disadvantage compared to plain old classes.\n    \"\"\"\n    return str(annot).startswith(_classvar_prefixes)\n\n\ndef _get_annotations(cls):\n    \"\"\"\n    Get annotations for *cls*.\n    \"\"\"\n    anns = getattr(cls, \"__annotations__\", None)\n    if anns is None:\n        return {}\n\n    # Verify that the annotations aren't merely inherited.\n    for base_cls in cls.__mro__[1:]:\n        if anns is getattr(base_cls, \"__annotations__\", None):\n            return {}\n\n    return anns\n\n\ndef _counter_getter(e):\n    \"\"\"\n    Key function for sorting to avoid re-creating a lambda for every class.\n    \"\"\"\n    return e[1].counter\n\n\ndef _transform_attrs(cls, these, auto_attribs, kw_only):\n    \"\"\"\n    Transform all `_CountingAttr`s on a class into `Attribute`s.\n\n    If *these* is passed, use that and don't look for them on the class.\n\n    Return an `_Attributes`.\n    \"\"\"\n    cd = cls.__dict__\n    anns = _get_annotations(cls)\n\n    if these is not None:\n        ca_list = [(name, ca) for name, ca in iteritems(these)]\n\n        if not isinstance(these, ordered_dict):\n            ca_list.sort(key=_counter_getter)\n    elif auto_attribs is True:\n        ca_names = {\n            name\n            for name, attr in cd.items()\n            if isinstance(attr, _CountingAttr)\n        }\n        ca_list = []\n        annot_names = set()\n        for attr_name, type in anns.items():\n            if _is_class_var(type):\n                continue\n            annot_names.add(attr_name)\n            a = cd.get(attr_name, NOTHING)\n            if not isinstance(a, _CountingAttr):\n                if a is NOTHING:\n                    a = attrib()\n                else:\n                    a = attrib(default=a)\n            ca_list.append((attr_name, a))\n\n        unannotated = ca_names - annot_names\n        if len(unannotated) > 0:\n            raise UnannotatedAttributeError(\n                \"The following `attr.ib`s lack a type annotation: \"\n                + \", \".join(\n                    sorted(unannotated, key=lambda n: cd.get(n).counter)\n                )\n                + \".\"\n            )\n    else:\n        ca_list = sorted(\n            (\n                (name, attr)\n                for name, attr in cd.items()\n                if isinstance(attr, _CountingAttr)\n            ),\n            key=lambda e: e[1].counter,\n        )\n\n    own_attrs = [\n        Attribute.from_counting_attr(\n            name=attr_name, ca=ca, type=anns.get(attr_name)\n        )\n        for attr_name, ca in ca_list\n    ]\n\n    base_attrs = []\n    base_attr_map = {}  # A dictionary of base attrs to their classes.\n    taken_attr_names = {a.name: a for a in own_attrs}\n\n    # Traverse the MRO and collect attributes.\n    for base_cls in cls.__mro__[1:-1]:\n        sub_attrs = getattr(base_cls, \"__attrs_attrs__\", None)\n        if sub_attrs is not None:\n            for a in sub_attrs:\n                prev_a = taken_attr_names.get(a.name)\n                # Only add an attribute if it hasn't been defined before.  This\n                # allows for overwriting attribute definitions by subclassing.\n                if prev_a is None:\n                    base_attrs.append(a)\n                    taken_attr_names[a.name] = a\n                    base_attr_map[a.name] = base_cls\n\n    attr_names = [a.name for a in base_attrs + own_attrs]\n\n    AttrsClass = _make_attr_tuple_class(cls.__name__, attr_names)\n\n    if kw_only:\n        own_attrs = [a._assoc(kw_only=True) for a in own_attrs]\n        base_attrs = [a._assoc(kw_only=True) for a in base_attrs]\n\n    attrs = AttrsClass(base_attrs + own_attrs)\n\n    # Mandatory vs non-mandatory attr order only matters when they are part of\n    # the __init__ signature and when they aren't kw_only (which are moved to\n    # the end and can be mandatory or non-mandatory in any order, as they will\n    # be specified as keyword args anyway). Check the order of those attrs:\n    had_default = False\n    for a in (a for a in attrs if a.init is not False and a.kw_only is False):\n        if had_default is True and a.default is NOTHING:\n            raise ValueError(\n                \"No mandatory attributes allowed after an attribute with a \"\n                \"default value or factory.  Attribute in question: %r\" % (a,)\n            )\n\n        if had_default is False and a.default is not NOTHING:\n            had_default = True\n\n    return _Attributes((attrs, base_attrs, base_attr_map))\n\n\ndef _frozen_setattrs(self, name, value):\n    \"\"\"\n    Attached to frozen classes as __setattr__.\n    \"\"\"\n    raise FrozenInstanceError()\n\n\ndef _frozen_delattrs(self, name):\n    \"\"\"\n    Attached to frozen classes as __delattr__.\n    \"\"\"\n    raise FrozenInstanceError()\n\n\nclass _ClassBuilder(object):\n    \"\"\"\n    Iteratively build *one* class.\n    \"\"\"\n\n    __slots__ = (\n        \"_cls\",\n        \"_cls_dict\",\n        \"_attrs\",\n        \"_base_names\",\n        \"_attr_names\",\n        \"_slots\",\n        \"_frozen\",\n        \"_weakref_slot\",\n        \"_cache_hash\",\n        \"_has_post_init\",\n        \"_delete_attribs\",\n        \"_base_attr_map\",\n        \"_is_exc\",\n    )\n\n    def __init__(\n        self,\n        cls,\n        these,\n        slots,\n        frozen,\n        weakref_slot,\n        auto_attribs,\n        kw_only,\n        cache_hash,\n        is_exc,\n    ):\n        attrs, base_attrs, base_map = _transform_attrs(\n            cls, these, auto_attribs, kw_only\n        )\n\n        self._cls = cls\n        self._cls_dict = dict(cls.__dict__) if slots else {}\n        self._attrs = attrs\n        self._base_names = set(a.name for a in base_attrs)\n        self._base_attr_map = base_map\n        self._attr_names = tuple(a.name for a in attrs)\n        self._slots = slots\n        self._frozen = frozen or _has_frozen_base_class(cls)\n        self._weakref_slot = weakref_slot\n        self._cache_hash = cache_hash\n        self._has_post_init = bool(getattr(cls, \"__attrs_post_init__\", False))\n        self._delete_attribs = not bool(these)\n        self._is_exc = is_exc\n\n        self._cls_dict[\"__attrs_attrs__\"] = self._attrs\n\n        if frozen:\n            self._cls_dict[\"__setattr__\"] = _frozen_setattrs\n            self._cls_dict[\"__delattr__\"] = _frozen_delattrs\n\n    def __repr__(self):\n        return \"<_ClassBuilder(cls={cls})>\".format(cls=self._cls.__name__)\n\n    def build_class(self):\n        \"\"\"\n        Finalize class based on the accumulated configuration.\n\n        Builder cannot be used after calling this method.\n        \"\"\"\n        if self._slots is True:\n            return self._create_slots_class()\n        else:\n            return self._patch_original_class()\n\n    def _patch_original_class(self):\n        \"\"\"\n        Apply accumulated methods and return the class.\n        \"\"\"\n        cls = self._cls\n        base_names = self._base_names\n\n        # Clean class of attribute definitions (`attr.ib()`s).\n        if self._delete_attribs:\n            for name in self._attr_names:\n                if (\n                    name not in base_names\n                    and getattr(cls, name, _sentinel) is not _sentinel\n                ):\n                    try:\n                        delattr(cls, name)\n                    except AttributeError:\n                        # This can happen if a base class defines a class\n                        # variable and we want to set an attribute with the\n                        # same name by using only a type annotation.\n                        pass\n\n        # Attach our dunder methods.\n        for name, value in self._cls_dict.items():\n            setattr(cls, name, value)\n\n        # Attach __setstate__. This is necessary to clear the hash code\n        # cache on deserialization. See issue\n        # https://github.com/python-attrs/attrs/issues/482 .\n        # Note that this code only handles setstate for dict classes.\n        # For slotted classes, see similar code in _create_slots_class .\n        if self._cache_hash:\n            existing_set_state_method = getattr(cls, \"__setstate__\", None)\n            if existing_set_state_method:\n                raise NotImplementedError(\n                    \"Currently you cannot use hash caching if \"\n                    \"you specify your own __setstate__ method.\"\n                    \"See https://github.com/python-attrs/attrs/issues/494 .\"\n                )\n\n            def cache_hash_set_state(chss_self, _):\n                # clear hash code cache\n                setattr(chss_self, _hash_cache_field, None)\n\n            setattr(cls, \"__setstate__\", cache_hash_set_state)\n\n        return cls\n\n    def _create_slots_class(self):\n        \"\"\"\n        Build and return a new class with a `__slots__` attribute.\n        \"\"\"\n        base_names = self._base_names\n        cd = {\n            k: v\n            for k, v in iteritems(self._cls_dict)\n            if k not in tuple(self._attr_names) + (\"__dict__\", \"__weakref__\")\n        }\n\n        weakref_inherited = False\n\n        # Traverse the MRO to check for an existing __weakref__.\n        for base_cls in self._cls.__mro__[1:-1]:\n            if \"__weakref__\" in getattr(base_cls, \"__dict__\", ()):\n                weakref_inherited = True\n                break\n\n        names = self._attr_names\n        if (\n            self._weakref_slot\n            and \"__weakref__\" not in getattr(self._cls, \"__slots__\", ())\n            and \"__weakref__\" not in names\n            and not weakref_inherited\n        ):\n            names += (\"__weakref__\",)\n\n        # We only add the names of attributes that aren't inherited.\n        # Settings __slots__ to inherited attributes wastes memory.\n        slot_names = [name for name in names if name not in base_names]\n        if self._cache_hash:\n            slot_names.append(_hash_cache_field)\n        cd[\"__slots__\"] = tuple(slot_names)\n\n        qualname = getattr(self._cls, \"__qualname__\", None)\n        if qualname is not None:\n            cd[\"__qualname__\"] = qualname\n\n        # __weakref__ is not writable.\n        state_attr_names = tuple(\n            an for an in self._attr_names if an != \"__weakref__\"\n        )\n\n        def slots_getstate(self):\n            \"\"\"\n            Automatically created by attrs.\n            \"\"\"\n            return tuple(getattr(self, name) for name in state_attr_names)\n\n        hash_caching_enabled = self._cache_hash\n\n        def slots_setstate(self, state):\n            \"\"\"\n            Automatically created by attrs.\n            \"\"\"\n            __bound_setattr = _obj_setattr.__get__(self, Attribute)\n            for name, value in zip(state_attr_names, state):\n                __bound_setattr(name, value)\n            # Clearing the hash code cache on deserialization is needed\n            # because hash codes can change from run to run. See issue\n            # https://github.com/python-attrs/attrs/issues/482 .\n            # Note that this code only handles setstate for slotted classes.\n            # For dict classes, see similar code in _patch_original_class .\n            if hash_caching_enabled:\n                __bound_setattr(_hash_cache_field, None)\n\n        # slots and frozen require __getstate__/__setstate__ to work\n        cd[\"__getstate__\"] = slots_getstate\n        cd[\"__setstate__\"] = slots_setstate\n\n        # Create new class based on old class and our methods.\n        cls = type(self._cls)(self._cls.__name__, self._cls.__bases__, cd)\n\n        # The following is a fix for\n        # https://github.com/python-attrs/attrs/issues/102.  On Python 3,\n        # if a method mentions `__class__` or uses the no-arg super(), the\n        # compiler will bake a reference to the class in the method itself\n        # as `method.__closure__`.  Since we replace the class with a\n        # clone, we rewrite these references so it keeps working.\n        for item in cls.__dict__.values():\n            if isinstance(item, (classmethod, staticmethod)):\n                # Class- and staticmethods hide their functions inside.\n                # These might need to be rewritten as well.\n                closure_cells = getattr(item.__func__, \"__closure__\", None)\n            else:\n                closure_cells = getattr(item, \"__closure__\", None)\n\n            if not closure_cells:  # Catch None or the empty list.\n                continue\n            for cell in closure_cells:\n                if cell.cell_contents is self._cls:\n                    set_closure_cell(cell, cls)\n\n        return cls\n\n    def add_repr(self, ns):\n        self._cls_dict[\"__repr__\"] = self._add_method_dunders(\n            _make_repr(self._attrs, ns=ns)\n        )\n        return self\n\n    def add_str(self):\n        repr = self._cls_dict.get(\"__repr__\")\n        if repr is None:\n            raise ValueError(\n                \"__str__ can only be generated if a __repr__ exists.\"\n            )\n\n        def __str__(self):\n            return self.__repr__()\n\n        self._cls_dict[\"__str__\"] = self._add_method_dunders(__str__)\n        return self\n\n    def make_unhashable(self):\n        self._cls_dict[\"__hash__\"] = None\n        return self\n\n    def add_hash(self):\n        self._cls_dict[\"__hash__\"] = self._add_method_dunders(\n            _make_hash(\n                self._cls,\n                self._attrs,\n                frozen=self._frozen,\n                cache_hash=self._cache_hash,\n            )\n        )\n\n        return self\n\n    def add_init(self):\n        self._cls_dict[\"__init__\"] = self._add_method_dunders(\n            _make_init(\n                self._cls,\n                self._attrs,\n                self._has_post_init,\n                self._frozen,\n                self._slots,\n                self._cache_hash,\n                self._base_attr_map,\n                self._is_exc,\n            )\n        )\n\n        return self\n\n    def add_eq(self):\n        cd = self._cls_dict\n\n        cd[\"__eq__\"], cd[\"__ne__\"] = (\n            self._add_method_dunders(meth)\n            for meth in _make_eq(self._cls, self._attrs)\n        )\n\n        return self\n\n    def add_order(self):\n        cd = self._cls_dict\n\n        cd[\"__lt__\"], cd[\"__le__\"], cd[\"__gt__\"], cd[\"__ge__\"] = (\n            self._add_method_dunders(meth)\n            for meth in _make_order(self._cls, self._attrs)\n        )\n\n        return self\n\n    def _add_method_dunders(self, method):\n        \"\"\"\n        Add __module__ and __qualname__ to a *method* if possible.\n        \"\"\"\n        try:\n            method.__module__ = self._cls.__module__\n        except AttributeError:\n            pass\n\n        try:\n            method.__qualname__ = \".\".join(\n                (self._cls.__qualname__, method.__name__)\n            )\n        except AttributeError:\n            pass\n\n        return method\n\n\n_CMP_DEPRECATION = (\n    \"The usage of `cmp` is deprecated and will be removed on or after \"\n    \"2021-06-01.  Please use `eq` and `order` instead.\"\n)\n\n\ndef _determine_eq_order(cmp, eq, order):\n    \"\"\"\n    Validate the combination of *cmp*, *eq*, and *order*. Derive the effective\n    values of eq and order.\n    \"\"\"\n    if cmp is not None and any((eq is not None, order is not None)):\n        raise ValueError(\"Don't mix `cmp` with `eq' and `order`.\")\n\n    # cmp takes precedence due to bw-compatibility.\n    if cmp is not None:\n        warnings.warn(_CMP_DEPRECATION, DeprecationWarning, stacklevel=3)\n\n        return cmp, cmp\n\n    # If left None, equality is on and ordering mirrors equality.\n    if eq is None:\n        eq = True\n\n    if order is None:\n        order = eq\n\n    if eq is False and order is True:\n        raise ValueError(\"`order` can only be True if `eq` is True too.\")\n\n    return eq, order\n\n\ndef attrs(\n    maybe_cls=None,\n    these=None,\n    repr_ns=None,\n    repr=True,\n    cmp=None,\n    hash=None,\n    init=True,\n    slots=False,\n    frozen=False,\n    weakref_slot=True,\n    str=False,\n    auto_attribs=False,\n    kw_only=False,\n    cache_hash=False,\n    auto_exc=False,\n    eq=None,\n    order=None,\n):\n    r\"\"\"\n    A class decorator that adds `dunder\n    <https://wiki.python.org/moin/DunderAlias>`_\\ -methods according to the\n    specified attributes using `attr.ib` or the *these* argument.\n\n    :param these: A dictionary of name to `attr.ib` mappings.  This is\n        useful to avoid the definition of your attributes within the class body\n        because you can't (e.g. if you want to add ``__repr__`` methods to\n        Django models) or don't want to.\n\n        If *these* is not ``None``, ``attrs`` will *not* search the class body\n        for attributes and will *not* remove any attributes from it.\n\n        If *these* is an ordered dict (`dict` on Python 3.6+,\n        `collections.OrderedDict` otherwise), the order is deduced from\n        the order of the attributes inside *these*.  Otherwise the order\n        of the definition of the attributes is used.\n\n    :type these: `dict` of `str` to `attr.ib`\n\n    :param str repr_ns: When using nested classes, there's no way in Python 2\n        to automatically detect that.  Therefore it's possible to set the\n        namespace explicitly for a more meaningful ``repr`` output.\n    :param bool repr: Create a ``__repr__`` method with a human readable\n        representation of ``attrs`` attributes..\n    :param bool str: Create a ``__str__`` method that is identical to\n        ``__repr__``.  This is usually not necessary except for\n        `Exception`\\ s.\n    :param bool eq: If ``True`` or ``None`` (default), add ``__eq__`` and\n        ``__ne__`` methods that check two instances for equality.\n\n        They compare the instances as if they were tuples of their ``attrs``\n        attributes, but only iff the types of both classes are *identical*!\n    :type eq: `bool` or `None`\n    :param bool order: If ``True``, add ``__lt__``, ``__le__``, ``__gt__``,\n        and ``__ge__`` methods that behave like *eq* above and allow instances\n        to be ordered. If ``None`` (default) mirror value of *eq*.\n    :type order: `bool` or `None`\n    :param cmp: Setting to ``True`` is equivalent to setting ``eq=True,\n        order=True``. Deprecated in favor of *eq* and *order*, has precedence\n        over them for backward-compatibility though. Must not be mixed with\n        *eq* or *order*.\n    :type cmp: `bool` or `None`\n    :param hash: If ``None`` (default), the ``__hash__`` method is generated\n        according how *eq* and *frozen* are set.\n\n        1. If *both* are True, ``attrs`` will generate a ``__hash__`` for you.\n        2. If *eq* is True and *frozen* is False, ``__hash__`` will be set to\n           None, marking it unhashable (which it is).\n        3. If *eq* is False, ``__hash__`` will be left untouched meaning the\n           ``__hash__`` method of the base class will be used (if base class is\n           ``object``, this means it will fall back to id-based hashing.).\n\n        Although not recommended, you can decide for yourself and force\n        ``attrs`` to create one (e.g. if the class is immutable even though you\n        didn't freeze it programmatically) by passing ``True`` or not.  Both of\n        these cases are rather special and should be used carefully.\n\n        See our documentation on `hashing`, Python's documentation on\n        `object.__hash__`, and the `GitHub issue that led to the default \\\n        behavior <https://github.com/python-attrs/attrs/issues/136>`_ for more\n        details.\n    :type hash: ``bool`` or ``None``\n    :param bool init: Create a ``__init__`` method that initializes the\n        ``attrs`` attributes.  Leading underscores are stripped for the\n        argument name.  If a ``__attrs_post_init__`` method exists on the\n        class, it will be called after the class is fully initialized.\n    :param bool slots: Create a `slotted class <slotted classes>` that's more\n        memory-efficient.\n    :param bool frozen: Make instances immutable after initialization.  If\n        someone attempts to modify a frozen instance,\n        `attr.exceptions.FrozenInstanceError` is raised.\n\n        Please note:\n\n            1. This is achieved by installing a custom ``__setattr__`` method\n               on your class, so you can't implement your own.\n\n            2. True immutability is impossible in Python.\n\n            3. This *does* have a minor a runtime performance `impact\n               <how-frozen>` when initializing new instances.  In other words:\n               ``__init__`` is slightly slower with ``frozen=True``.\n\n            4. If a class is frozen, you cannot modify ``self`` in\n               ``__attrs_post_init__`` or a self-written ``__init__``. You can\n               circumvent that limitation by using\n               ``object.__setattr__(self, \"attribute_name\", value)``.\n\n    :param bool weakref_slot: Make instances weak-referenceable.  This has no\n        effect unless ``slots`` is also enabled.\n    :param bool auto_attribs: If True, collect `PEP 526`_-annotated attributes\n        (Python 3.6 and later only) from the class body.\n\n        In this case, you **must** annotate every field.  If ``attrs``\n        encounters a field that is set to an `attr.ib` but lacks a type\n        annotation, an `attr.exceptions.UnannotatedAttributeError` is\n        raised.  Use ``field_name: typing.Any = attr.ib(...)`` if you don't\n        want to set a type.\n\n        If you assign a value to those attributes (e.g. ``x: int = 42``), that\n        value becomes the default value like if it were passed using\n        ``attr.ib(default=42)``.  Passing an instance of `Factory` also\n        works as expected.\n\n        Attributes annotated as `typing.ClassVar`, and attributes that are\n        neither annotated nor set to an `attr.ib` are **ignored**.\n\n        .. _`PEP 526`: https://www.python.org/dev/peps/pep-0526/\n    :param bool kw_only: Make all attributes keyword-only (Python 3+)\n        in the generated ``__init__`` (if ``init`` is ``False``, this\n        parameter is ignored).\n    :param bool cache_hash: Ensure that the object's hash code is computed\n        only once and stored on the object.  If this is set to ``True``,\n        hashing must be either explicitly or implicitly enabled for this\n        class.  If the hash code is cached, avoid any reassignments of\n        fields involved in hash code computation or mutations of the objects\n        those fields point to after object creation.  If such changes occur,\n        the behavior of the object's hash code is undefined.\n    :param bool auto_exc: If the class subclasses `BaseException`\n        (which implicitly includes any subclass of any exception), the\n        following happens to behave like a well-behaved Python exceptions\n        class:\n\n        - the values for *eq*, *order*, and *hash* are ignored and the\n          instances compare and hash by the instance's ids (N.B. ``attrs`` will\n          *not* remove existing implementations of ``__hash__`` or the equality\n          methods. It just won't add own ones.),\n        - all attributes that are either passed into ``__init__`` or have a\n          default value are additionally available as a tuple in the ``args``\n          attribute,\n        - the value of *str* is ignored leaving ``__str__`` to base classes.\n\n    .. versionadded:: 16.0.0 *slots*\n    .. versionadded:: 16.1.0 *frozen*\n    .. versionadded:: 16.3.0 *str*\n    .. versionadded:: 16.3.0 Support for ``__attrs_post_init__``.\n    .. versionchanged:: 17.1.0\n       *hash* supports ``None`` as value which is also the default now.\n    .. versionadded:: 17.3.0 *auto_attribs*\n    .. versionchanged:: 18.1.0\n       If *these* is passed, no attributes are deleted from the class body.\n    .. versionchanged:: 18.1.0 If *these* is ordered, the order is retained.\n    .. versionadded:: 18.2.0 *weakref_slot*\n    .. deprecated:: 18.2.0\n       ``__lt__``, ``__le__``, ``__gt__``, and ``__ge__`` now raise a\n       `DeprecationWarning` if the classes compared are subclasses of\n       each other. ``__eq`` and ``__ne__`` never tried to compared subclasses\n       to each other.\n    .. versionchanged:: 19.2.0\n       ``__lt__``, ``__le__``, ``__gt__``, and ``__ge__`` now do not consider\n       subclasses comparable anymore.\n    .. versionadded:: 18.2.0 *kw_only*\n    .. versionadded:: 18.2.0 *cache_hash*\n    .. versionadded:: 19.1.0 *auto_exc*\n    .. deprecated:: 19.2.0 *cmp* Removal on or after 2021-06-01.\n    .. versionadded:: 19.2.0 *eq* and *order*\n    \"\"\"\n    eq, order = _determine_eq_order(cmp, eq, order)\n\n    def wrap(cls):\n\n        if getattr(cls, \"__class__\", None) is None:\n            raise TypeError(\"attrs only works with new-style classes.\")\n\n        is_exc = auto_exc is True and issubclass(cls, BaseException)\n\n        builder = _ClassBuilder(\n            cls,\n            these,\n            slots,\n            frozen,\n            weakref_slot,\n            auto_attribs,\n            kw_only,\n            cache_hash,\n            is_exc,\n        )\n\n        if repr is True:\n            builder.add_repr(repr_ns)\n        if str is True:\n            builder.add_str()\n        if eq is True and not is_exc:\n            builder.add_eq()\n        if order is True and not is_exc:\n            builder.add_order()\n\n        if hash is not True and hash is not False and hash is not None:\n            # Can't use `hash in` because 1 == True for example.\n            raise TypeError(\n                \"Invalid value for hash.  Must be True, False, or None.\"\n            )\n        elif hash is False or (hash is None and eq is False) or is_exc:\n            # Don't do anything. Should fall back to __object__'s __hash__\n            # which is by id.\n            if cache_hash:\n                raise TypeError(\n                    \"Invalid value for cache_hash.  To use hash caching,\"\n                    \" hashing must be either explicitly or implicitly \"\n                    \"enabled.\"\n                )\n        elif hash is True or (hash is None and eq is True and frozen is True):\n            # Build a __hash__ if told so, or if it's safe.\n            builder.add_hash()\n        else:\n            # Raise TypeError on attempts to hash.\n            if cache_hash:\n                raise TypeError(\n                    \"Invalid value for cache_hash.  To use hash caching,\"\n                    \" hashing must be either explicitly or implicitly \"\n                    \"enabled.\"\n                )\n            builder.make_unhashable()\n\n        if init is True:\n            builder.add_init()\n        else:\n            if cache_hash:\n                raise TypeError(\n                    \"Invalid value for cache_hash.  To use hash caching,\"\n                    \" init must be True.\"\n                )\n\n        return builder.build_class()\n\n    # maybe_cls's type depends on the usage of the decorator.  It's a class\n    # if it's used as `@attrs` but ``None`` if used as `@attrs()`.\n    if maybe_cls is None:\n        return wrap\n    else:\n        return wrap(maybe_cls)\n\n\n_attrs = attrs\n\"\"\"\nInternal alias so we can use it in functions that take an argument called\n*attrs*.\n\"\"\"\n\n\nif PY2:\n\n    def _has_frozen_base_class(cls):\n        \"\"\"\n        Check whether *cls* has a frozen ancestor by looking at its\n        __setattr__.\n        \"\"\"\n        return (\n            getattr(cls.__setattr__, \"__module__\", None)\n            == _frozen_setattrs.__module__\n            and cls.__setattr__.__name__ == _frozen_setattrs.__name__\n        )\n\n\nelse:\n\n    def _has_frozen_base_class(cls):\n        \"\"\"\n        Check whether *cls* has a frozen ancestor by looking at its\n        __setattr__.\n        \"\"\"\n        return cls.__setattr__ == _frozen_setattrs\n\n\ndef _attrs_to_tuple(obj, attrs):\n    \"\"\"\n    Create a tuple of all values of *obj*'s *attrs*.\n    \"\"\"\n    return tuple(getattr(obj, a.name) for a in attrs)\n\n\ndef _generate_unique_filename(cls, func_name):\n    \"\"\"\n    Create a \"filename\" suitable for a function being generated.\n    \"\"\"\n    unique_id = uuid.uuid4()\n    extra = \"\"\n    count = 1\n\n    while True:\n        unique_filename = \"<attrs generated {0} {1}.{2}{3}>\".format(\n            func_name,\n            cls.__module__,\n            getattr(cls, \"__qualname__\", cls.__name__),\n            extra,\n        )\n        # To handle concurrency we essentially \"reserve\" our spot in\n        # the linecache with a dummy line.  The caller can then\n        # set this value correctly.\n        cache_line = (1, None, (str(unique_id),), unique_filename)\n        if (\n            linecache.cache.setdefault(unique_filename, cache_line)\n            == cache_line\n        ):\n            return unique_filename\n\n        # Looks like this spot is taken. Try again.\n        count += 1\n        extra = \"-{0}\".format(count)\n\n\ndef _make_hash(cls, attrs, frozen, cache_hash):\n    attrs = tuple(\n        a for a in attrs if a.hash is True or (a.hash is None and a.eq is True)\n    )\n\n    tab = \"        \"\n\n    unique_filename = _generate_unique_filename(cls, \"hash\")\n    type_hash = hash(unique_filename)\n\n    method_lines = [\"def __hash__(self):\"]\n\n    def append_hash_computation_lines(prefix, indent):\n        \"\"\"\n        Generate the code for actually computing the hash code.\n        Below this will either be returned directly or used to compute\n        a value which is then cached, depending on the value of cache_hash\n        \"\"\"\n        method_lines.extend(\n            [indent + prefix + \"hash((\", indent + \"        %d,\" % (type_hash,)]\n        )\n\n        for a in attrs:\n            method_lines.append(indent + \"        self.%s,\" % a.name)\n\n        method_lines.append(indent + \"    ))\")\n\n    if cache_hash:\n        method_lines.append(tab + \"if self.%s is None:\" % _hash_cache_field)\n        if frozen:\n            append_hash_computation_lines(\n                \"object.__setattr__(self, '%s', \" % _hash_cache_field, tab * 2\n            )\n            method_lines.append(tab * 2 + \")\")  # close __setattr__\n        else:\n            append_hash_computation_lines(\n                \"self.%s = \" % _hash_cache_field, tab * 2\n            )\n        method_lines.append(tab + \"return self.%s\" % _hash_cache_field)\n    else:\n        append_hash_computation_lines(\"return \", tab)\n\n    script = \"\\n\".join(method_lines)\n    globs = {}\n    locs = {}\n    bytecode = compile(script, unique_filename, \"exec\")\n    eval(bytecode, globs, locs)\n\n    # In order of debuggers like PDB being able to step through the code,\n    # we add a fake linecache entry.\n    linecache.cache[unique_filename] = (\n        len(script),\n        None,\n        script.splitlines(True),\n        unique_filename,\n    )\n\n    return locs[\"__hash__\"]\n\n\ndef _add_hash(cls, attrs):\n    \"\"\"\n    Add a hash method to *cls*.\n    \"\"\"\n    cls.__hash__ = _make_hash(cls, attrs, frozen=False, cache_hash=False)\n    return cls\n\n\ndef __ne__(self, other):\n    \"\"\"\n    Check equality and either forward a NotImplemented or return the result\n    negated.\n    \"\"\"\n    result = self.__eq__(other)\n    if result is NotImplemented:\n        return NotImplemented\n\n    return not result\n\n\ndef _make_eq(cls, attrs):\n    attrs = [a for a in attrs if a.eq]\n\n    unique_filename = _generate_unique_filename(cls, \"eq\")\n    lines = [\n        \"def __eq__(self, other):\",\n        \"    if other.__class__ is not self.__class__:\",\n        \"        return NotImplemented\",\n    ]\n    # We can't just do a big self.x = other.x and... clause due to\n    # irregularities like nan == nan is false but (nan,) == (nan,) is true.\n    if attrs:\n        lines.append(\"    return  (\")\n        others = [\"    ) == (\"]\n        for a in attrs:\n            lines.append(\"        self.%s,\" % (a.name,))\n            others.append(\"        other.%s,\" % (a.name,))\n\n        lines += others + [\"    )\"]\n    else:\n        lines.append(\"    return True\")\n\n    script = \"\\n\".join(lines)\n    globs = {}\n    locs = {}\n    bytecode = compile(script, unique_filename, \"exec\")\n    eval(bytecode, globs, locs)\n\n    # In order of debuggers like PDB being able to step through the code,\n    # we add a fake linecache entry.\n    linecache.cache[unique_filename] = (\n        len(script),\n        None,\n        script.splitlines(True),\n        unique_filename,\n    )\n    return locs[\"__eq__\"], __ne__\n\n\ndef _make_order(cls, attrs):\n    attrs = [a for a in attrs if a.order]\n\n    def attrs_to_tuple(obj):\n        \"\"\"\n        Save us some typing.\n        \"\"\"\n        return _attrs_to_tuple(obj, attrs)\n\n    def __lt__(self, other):\n        \"\"\"\n        Automatically created by attrs.\n        \"\"\"\n        if other.__class__ is self.__class__:\n            return attrs_to_tuple(self) < attrs_to_tuple(other)\n\n        return NotImplemented\n\n    def __le__(self, other):\n        \"\"\"\n        Automatically created by attrs.\n        \"\"\"\n        if other.__class__ is self.__class__:\n            return attrs_to_tuple(self) <= attrs_to_tuple(other)\n\n        return NotImplemented\n\n    def __gt__(self, other):\n        \"\"\"\n        Automatically created by attrs.\n        \"\"\"\n        if other.__class__ is self.__class__:\n            return attrs_to_tuple(self) > attrs_to_tuple(other)\n\n        return NotImplemented\n\n    def __ge__(self, other):\n        \"\"\"\n        Automatically created by attrs.\n        \"\"\"\n        if other.__class__ is self.__class__:\n            return attrs_to_tuple(self) >= attrs_to_tuple(other)\n\n        return NotImplemented\n\n    return __lt__, __le__, __gt__, __ge__\n\n\ndef _add_eq(cls, attrs=None):\n    \"\"\"\n    Add equality methods to *cls* with *attrs*.\n    \"\"\"\n    if attrs is None:\n        attrs = cls.__attrs_attrs__\n\n    cls.__eq__, cls.__ne__ = _make_eq(cls, attrs)\n\n    return cls\n\n\n_already_repring = threading.local()\n\n\ndef _make_repr(attrs, ns):\n    \"\"\"\n    Make a repr method that includes relevant *attrs*, adding *ns* to the full\n    name.\n    \"\"\"\n\n    # Figure out which attributes to include, and which function to use to\n    # format them. The a.repr value can be either bool or a custom callable.\n    attr_names_with_reprs = tuple(\n        (a.name, repr if a.repr is True else a.repr)\n        for a in attrs\n        if a.repr is not False\n    )\n\n    def __repr__(self):\n        \"\"\"\n        Automatically created by attrs.\n        \"\"\"\n        try:\n            working_set = _already_repring.working_set\n        except AttributeError:\n            working_set = set()\n            _already_repring.working_set = working_set\n\n        if id(self) in working_set:\n            return \"...\"\n        real_cls = self.__class__\n        if ns is None:\n            qualname = getattr(real_cls, \"__qualname__\", None)\n            if qualname is not None:\n                class_name = qualname.rsplit(\">.\", 1)[-1]\n            else:\n                class_name = real_cls.__name__\n        else:\n            class_name = ns + \".\" + real_cls.__name__\n\n        # Since 'self' remains on the stack (i.e.: strongly referenced) for the\n        # duration of this call, it's safe to depend on id(...) stability, and\n        # not need to track the instance and therefore worry about properties\n        # like weakref- or hash-ability.\n        working_set.add(id(self))\n        try:\n            result = [class_name, \"(\"]\n            first = True\n            for name, attr_repr in attr_names_with_reprs:\n                if first:\n                    first = False\n                else:\n                    result.append(\", \")\n                result.extend(\n                    (name, \"=\", attr_repr(getattr(self, name, NOTHING)))\n                )\n            return \"\".join(result) + \")\"\n        finally:\n            working_set.remove(id(self))\n\n    return __repr__\n\n\ndef _add_repr(cls, ns=None, attrs=None):\n    \"\"\"\n    Add a repr method to *cls*.\n    \"\"\"\n    if attrs is None:\n        attrs = cls.__attrs_attrs__\n\n    cls.__repr__ = _make_repr(attrs, ns)\n    return cls\n\n\ndef _make_init(\n    cls, attrs, post_init, frozen, slots, cache_hash, base_attr_map, is_exc\n):\n    attrs = [a for a in attrs if a.init or a.default is not NOTHING]\n\n    unique_filename = _generate_unique_filename(cls, \"init\")\n\n    script, globs, annotations = _attrs_to_init_script(\n        attrs, frozen, slots, post_init, cache_hash, base_attr_map, is_exc\n    )\n    locs = {}\n    bytecode = compile(script, unique_filename, \"exec\")\n    attr_dict = dict((a.name, a) for a in attrs)\n    globs.update({\"NOTHING\": NOTHING, \"attr_dict\": attr_dict})\n\n    if frozen is True:\n        # Save the lookup overhead in __init__ if we need to circumvent\n        # immutability.\n        globs[\"_cached_setattr\"] = _obj_setattr\n\n    eval(bytecode, globs, locs)\n\n    # In order of debuggers like PDB being able to step through the code,\n    # we add a fake linecache entry.\n    linecache.cache[unique_filename] = (\n        len(script),\n        None,\n        script.splitlines(True),\n        unique_filename,\n    )\n\n    __init__ = locs[\"__init__\"]\n    __init__.__annotations__ = annotations\n\n    return __init__\n\n\ndef fields(cls):\n    \"\"\"\n    Return the tuple of ``attrs`` attributes for a class.\n\n    The tuple also allows accessing the fields by their names (see below for\n    examples).\n\n    :param type cls: Class to introspect.\n\n    :raise TypeError: If *cls* is not a class.\n    :raise attr.exceptions.NotAnAttrsClassError: If *cls* is not an ``attrs``\n        class.\n\n    :rtype: tuple (with name accessors) of `attr.Attribute`\n\n    ..  versionchanged:: 16.2.0 Returned tuple allows accessing the fields\n        by name.\n    \"\"\"\n    if not isclass(cls):\n        raise TypeError(\"Passed object must be a class.\")\n    attrs = getattr(cls, \"__attrs_attrs__\", None)\n    if attrs is None:\n        raise NotAnAttrsClassError(\n            \"{cls!r} is not an attrs-decorated class.\".format(cls=cls)\n        )\n    return attrs\n\n\ndef fields_dict(cls):\n    \"\"\"\n    Return an ordered dictionary of ``attrs`` attributes for a class, whose\n    keys are the attribute names.\n\n    :param type cls: Class to introspect.\n\n    :raise TypeError: If *cls* is not a class.\n    :raise attr.exceptions.NotAnAttrsClassError: If *cls* is not an ``attrs``\n        class.\n\n    :rtype: an ordered dict where keys are attribute names and values are\n        `attr.Attribute`\\\\ s. This will be a `dict` if it's\n        naturally ordered like on Python 3.6+ or an\n        :class:`~collections.OrderedDict` otherwise.\n\n    .. versionadded:: 18.1.0\n    \"\"\"\n    if not isclass(cls):\n        raise TypeError(\"Passed object must be a class.\")\n    attrs = getattr(cls, \"__attrs_attrs__\", None)\n    if attrs is None:\n        raise NotAnAttrsClassError(\n            \"{cls!r} is not an attrs-decorated class.\".format(cls=cls)\n        )\n    return ordered_dict(((a.name, a) for a in attrs))\n\n\ndef validate(inst):\n    \"\"\"\n    Validate all attributes on *inst* that have a validator.\n\n    Leaves all exceptions through.\n\n    :param inst: Instance of a class with ``attrs`` attributes.\n    \"\"\"\n    if _config._run_validators is False:\n        return\n\n    for a in fields(inst.__class__):\n        v = a.validator\n        if v is not None:\n            v(inst, a, getattr(inst, a.name))\n\n\ndef _is_slot_cls(cls):\n    return \"__slots__\" in cls.__dict__\n\n\ndef _is_slot_attr(a_name, base_attr_map):\n    \"\"\"\n    Check if the attribute name comes from a slot class.\n    \"\"\"\n    return a_name in base_attr_map and _is_slot_cls(base_attr_map[a_name])\n\n\ndef _attrs_to_init_script(\n    attrs, frozen, slots, post_init, cache_hash, base_attr_map, is_exc\n):\n    \"\"\"\n    Return a script of an initializer for *attrs* and a dict of globals.\n\n    The globals are expected by the generated script.\n\n    If *frozen* is True, we cannot set the attributes directly so we use\n    a cached ``object.__setattr__``.\n    \"\"\"\n    lines = []\n    any_slot_ancestors = any(\n        _is_slot_attr(a.name, base_attr_map) for a in attrs\n    )\n    if frozen is True:\n        if slots is True:\n            lines.append(\n                # Circumvent the __setattr__ descriptor to save one lookup per\n                # assignment.\n                # Note _setattr will be used again below if cache_hash is True\n                \"_setattr = _cached_setattr.__get__(self, self.__class__)\"\n            )\n\n            def fmt_setter(attr_name, value_var):\n                return \"_setattr('%(attr_name)s', %(value_var)s)\" % {\n                    \"attr_name\": attr_name,\n                    \"value_var\": value_var,\n                }\n\n            def fmt_setter_with_converter(attr_name, value_var):\n                conv_name = _init_converter_pat.format(attr_name)\n                return \"_setattr('%(attr_name)s', %(conv)s(%(value_var)s))\" % {\n                    \"attr_name\": attr_name,\n                    \"value_var\": value_var,\n                    \"conv\": conv_name,\n                }\n\n        else:\n            # Dict frozen classes assign directly to __dict__.\n            # But only if the attribute doesn't come from an ancestor slot\n            # class.\n            # Note _inst_dict will be used again below if cache_hash is True\n            lines.append(\"_inst_dict = self.__dict__\")\n            if any_slot_ancestors:\n                lines.append(\n                    # Circumvent the __setattr__ descriptor to save one lookup\n                    # per assignment.\n                    \"_setattr = _cached_setattr.__get__(self, self.__class__)\"\n                )\n\n            def fmt_setter(attr_name, value_var):\n                if _is_slot_attr(attr_name, base_attr_map):\n                    res = \"_setattr('%(attr_name)s', %(value_var)s)\" % {\n                        \"attr_name\": attr_name,\n                        \"value_var\": value_var,\n                    }\n                else:\n                    res = \"_inst_dict['%(attr_name)s'] = %(value_var)s\" % {\n                        \"attr_name\": attr_name,\n                        \"value_var\": value_var,\n                    }\n                return res\n\n            def fmt_setter_with_converter(attr_name, value_var):\n                conv_name = _init_converter_pat.format(attr_name)\n                if _is_slot_attr(attr_name, base_attr_map):\n                    tmpl = \"_setattr('%(attr_name)s', %(c)s(%(value_var)s))\"\n                else:\n                    tmpl = \"_inst_dict['%(attr_name)s'] = %(c)s(%(value_var)s)\"\n                return tmpl % {\n                    \"attr_name\": attr_name,\n                    \"value_var\": value_var,\n                    \"c\": conv_name,\n                }\n\n    else:\n        # Not frozen.\n        def fmt_setter(attr_name, value):\n            return \"self.%(attr_name)s = %(value)s\" % {\n                \"attr_name\": attr_name,\n                \"value\": value,\n            }\n\n        def fmt_setter_with_converter(attr_name, value_var):\n            conv_name = _init_converter_pat.format(attr_name)\n            return \"self.%(attr_name)s = %(conv)s(%(value_var)s)\" % {\n                \"attr_name\": attr_name,\n                \"value_var\": value_var,\n                \"conv\": conv_name,\n            }\n\n    args = []\n    kw_only_args = []\n    attrs_to_validate = []\n\n    # This is a dictionary of names to validator and converter callables.\n    # Injecting this into __init__ globals lets us avoid lookups.\n    names_for_globals = {}\n    annotations = {\"return\": None}\n\n    for a in attrs:\n        if a.validator:\n            attrs_to_validate.append(a)\n        attr_name = a.name\n        arg_name = a.name.lstrip(\"_\")\n        has_factory = isinstance(a.default, Factory)\n        if has_factory and a.default.takes_self:\n            maybe_self = \"self\"\n        else:\n            maybe_self = \"\"\n        if a.init is False:\n            if has_factory:\n                init_factory_name = _init_factory_pat.format(a.name)\n                if a.converter is not None:\n                    lines.append(\n                        fmt_setter_with_converter(\n                            attr_name,\n                            init_factory_name + \"({0})\".format(maybe_self),\n                        )\n                    )\n                    conv_name = _init_converter_pat.format(a.name)\n                    names_for_globals[conv_name] = a.converter\n                else:\n                    lines.append(\n                        fmt_setter(\n                            attr_name,\n                            init_factory_name + \"({0})\".format(maybe_self),\n                        )\n                    )\n                names_for_globals[init_factory_name] = a.default.factory\n            else:\n                if a.converter is not None:\n                    lines.append(\n                        fmt_setter_with_converter(\n                            attr_name,\n                            \"attr_dict['{attr_name}'].default\".format(\n                                attr_name=attr_name\n                            ),\n                        )\n                    )\n                    conv_name = _init_converter_pat.format(a.name)\n                    names_for_globals[conv_name] = a.converter\n                else:\n                    lines.append(\n                        fmt_setter(\n                            attr_name,\n                            \"attr_dict['{attr_name}'].default\".format(\n                                attr_name=attr_name\n                            ),\n                        )\n                    )\n        elif a.default is not NOTHING and not has_factory:\n            arg = \"{arg_name}=attr_dict['{attr_name}'].default\".format(\n                arg_name=arg_name, attr_name=attr_name\n            )\n            if a.kw_only:\n                kw_only_args.append(arg)\n            else:\n                args.append(arg)\n            if a.converter is not None:\n                lines.append(fmt_setter_with_converter(attr_name, arg_name))\n                names_for_globals[\n                    _init_converter_pat.format(a.name)\n                ] = a.converter\n            else:\n                lines.append(fmt_setter(attr_name, arg_name))\n        elif has_factory:\n            arg = \"{arg_name}=NOTHING\".format(arg_name=arg_name)\n            if a.kw_only:\n                kw_only_args.append(arg)\n            else:\n                args.append(arg)\n            lines.append(\n                \"if {arg_name} is not NOTHING:\".format(arg_name=arg_name)\n            )\n            init_factory_name = _init_factory_pat.format(a.name)\n            if a.converter is not None:\n                lines.append(\n                    \"    \" + fmt_setter_with_converter(attr_name, arg_name)\n                )\n                lines.append(\"else:\")\n                lines.append(\n                    \"    \"\n                    + fmt_setter_with_converter(\n                        attr_name,\n                        init_factory_name + \"({0})\".format(maybe_self),\n                    )\n                )\n                names_for_globals[\n                    _init_converter_pat.format(a.name)\n                ] = a.converter\n            else:\n                lines.append(\"    \" + fmt_setter(attr_name, arg_name))\n                lines.append(\"else:\")\n                lines.append(\n                    \"    \"\n                    + fmt_setter(\n                        attr_name,\n                        init_factory_name + \"({0})\".format(maybe_self),\n                    )\n                )\n            names_for_globals[init_factory_name] = a.default.factory\n        else:\n            if a.kw_only:\n                kw_only_args.append(arg_name)\n            else:\n                args.append(arg_name)\n            if a.converter is not None:\n                lines.append(fmt_setter_with_converter(attr_name, arg_name))\n                names_for_globals[\n                    _init_converter_pat.format(a.name)\n                ] = a.converter\n            else:\n                lines.append(fmt_setter(attr_name, arg_name))\n\n        if a.init is True and a.converter is None and a.type is not None:\n            annotations[arg_name] = a.type\n\n    if attrs_to_validate:  # we can skip this if there are no validators.\n        names_for_globals[\"_config\"] = _config\n        lines.append(\"if _config._run_validators is True:\")\n        for a in attrs_to_validate:\n            val_name = \"__attr_validator_{}\".format(a.name)\n            attr_name = \"__attr_{}\".format(a.name)\n            lines.append(\n                \"    {}(self, {}, self.{})\".format(val_name, attr_name, a.name)\n            )\n            names_for_globals[val_name] = a.validator\n            names_for_globals[attr_name] = a\n    if post_init:\n        lines.append(\"self.__attrs_post_init__()\")\n\n    # because this is set only after __attrs_post_init is called, a crash\n    # will result if post-init tries to access the hash code.  This seemed\n    # preferable to setting this beforehand, in which case alteration to\n    # field values during post-init combined with post-init accessing the\n    # hash code would result in silent bugs.\n    if cache_hash:\n        if frozen:\n            if slots:\n                # if frozen and slots, then _setattr defined above\n                init_hash_cache = \"_setattr('%s', %s)\"\n            else:\n                # if frozen and not slots, then _inst_dict defined above\n                init_hash_cache = \"_inst_dict['%s'] = %s\"\n        else:\n            init_hash_cache = \"self.%s = %s\"\n        lines.append(init_hash_cache % (_hash_cache_field, \"None\"))\n\n    # For exceptions we rely on BaseException.__init__ for proper\n    # initialization.\n    if is_exc:\n        vals = \",\".join(\"self.\" + a.name for a in attrs if a.init)\n\n        lines.append(\"BaseException.__init__(self, %s)\" % (vals,))\n\n    args = \", \".join(args)\n    if kw_only_args:\n        if PY2:\n            raise PythonTooOldError(\n                \"Keyword-only arguments only work on Python 3 and later.\"\n            )\n\n        args += \"{leading_comma}*, {kw_only_args}\".format(\n            leading_comma=\", \" if args else \"\",\n            kw_only_args=\", \".join(kw_only_args),\n        )\n    return (\n        \"\"\"\\\ndef __init__(self, {args}):\n    {lines}\n\"\"\".format(\n            args=args, lines=\"\\n    \".join(lines) if lines else \"pass\"\n        ),\n        names_for_globals,\n        annotations,\n    )\n\n\nclass Attribute(object):\n    \"\"\"\n    *Read-only* representation of an attribute.\n\n    :attribute name: The name of the attribute.\n\n    Plus *all* arguments of `attr.ib` (except for ``factory``\n    which is only syntactic sugar for ``default=Factory(...)``.\n\n    For the version history of the fields, see `attr.ib`.\n    \"\"\"\n\n    __slots__ = (\n        \"name\",\n        \"default\",\n        \"validator\",\n        \"repr\",\n        \"eq\",\n        \"order\",\n        \"hash\",\n        \"init\",\n        \"metadata\",\n        \"type\",\n        \"converter\",\n        \"kw_only\",\n    )\n\n    def __init__(\n        self,\n        name,\n        default,\n        validator,\n        repr,\n        cmp,  # XXX: unused, remove along with other cmp code.\n        hash,\n        init,\n        metadata=None,\n        type=None,\n        converter=None,\n        kw_only=False,\n        eq=None,\n        order=None,\n    ):\n        eq, order = _determine_eq_order(cmp, eq, order)\n\n        # Cache this descriptor here to speed things up later.\n        bound_setattr = _obj_setattr.__get__(self, Attribute)\n\n        # Despite the big red warning, people *do* instantiate `Attribute`\n        # themselves.\n        bound_setattr(\"name\", name)\n        bound_setattr(\"default\", default)\n        bound_setattr(\"validator\", validator)\n        bound_setattr(\"repr\", repr)\n        bound_setattr(\"eq\", eq)\n        bound_setattr(\"order\", order)\n        bound_setattr(\"hash\", hash)\n        bound_setattr(\"init\", init)\n        bound_setattr(\"converter\", converter)\n        bound_setattr(\n            \"metadata\",\n            (\n                metadata_proxy(metadata)\n                if metadata\n                else _empty_metadata_singleton\n            ),\n        )\n        bound_setattr(\"type\", type)\n        bound_setattr(\"kw_only\", kw_only)\n\n    def __setattr__(self, name, value):\n        raise FrozenInstanceError()\n\n    @classmethod\n    def from_counting_attr(cls, name, ca, type=None):\n        # type holds the annotated value. deal with conflicts:\n        if type is None:\n            type = ca.type\n        elif ca.type is not None:\n            raise ValueError(\n                \"Type annotation and type argument cannot both be present\"\n            )\n        inst_dict = {\n            k: getattr(ca, k)\n            for k in Attribute.__slots__\n            if k\n            not in (\n                \"name\",\n                \"validator\",\n                \"default\",\n                \"type\",\n            )  # exclude methods and deprecated alias\n        }\n        return cls(\n            name=name,\n            validator=ca._validator,\n            default=ca._default,\n            type=type,\n            cmp=None,\n            **inst_dict\n        )\n\n    @property\n    def cmp(self):\n        \"\"\"\n        Simulate the presence of a cmp attribute and warn.\n        \"\"\"\n        warnings.warn(_CMP_DEPRECATION, DeprecationWarning, stacklevel=2)\n\n        return self.eq and self.order\n\n    # Don't use attr.assoc since fields(Attribute) doesn't work\n    def _assoc(self, **changes):\n        \"\"\"\n        Copy *self* and apply *changes*.\n        \"\"\"\n        new = copy.copy(self)\n\n        new._setattrs(changes.items())\n\n        return new\n\n    # Don't use _add_pickle since fields(Attribute) doesn't work\n    def __getstate__(self):\n        \"\"\"\n        Play nice with pickle.\n        \"\"\"\n        return tuple(\n            getattr(self, name) if name != \"metadata\" else dict(self.metadata)\n            for name in self.__slots__\n        )\n\n    def __setstate__(self, state):\n        \"\"\"\n        Play nice with pickle.\n        \"\"\"\n        self._setattrs(zip(self.__slots__, state))\n\n    def _setattrs(self, name_values_pairs):\n        bound_setattr = _obj_setattr.__get__(self, Attribute)\n        for name, value in name_values_pairs:\n            if name != \"metadata\":\n                bound_setattr(name, value)\n            else:\n                bound_setattr(\n                    name,\n                    metadata_proxy(value)\n                    if value\n                    else _empty_metadata_singleton,\n                )\n\n\n_a = [\n    Attribute(\n        name=name,\n        default=NOTHING,\n        validator=None,\n        repr=True,\n        cmp=None,\n        eq=True,\n        order=False,\n        hash=(name != \"metadata\"),\n        init=True,\n    )\n    for name in Attribute.__slots__\n]\n\nAttribute = _add_hash(\n    _add_eq(_add_repr(Attribute, attrs=_a), attrs=_a),\n    attrs=[a for a in _a if a.hash],\n)\n\n\nclass _CountingAttr(object):\n    \"\"\"\n    Intermediate representation of attributes that uses a counter to preserve\n    the order in which the attributes have been defined.\n\n    *Internal* data structure of the attrs library.  Running into is most\n    likely the result of a bug like a forgotten `@attr.s` decorator.\n    \"\"\"\n\n    __slots__ = (\n        \"counter\",\n        \"_default\",\n        \"repr\",\n        \"eq\",\n        \"order\",\n        \"hash\",\n        \"init\",\n        \"metadata\",\n        \"_validator\",\n        \"converter\",\n        \"type\",\n        \"kw_only\",\n    )\n    __attrs_attrs__ = tuple(\n        Attribute(\n            name=name,\n            default=NOTHING,\n            validator=None,\n            repr=True,\n            cmp=None,\n            hash=True,\n            init=True,\n            kw_only=False,\n            eq=True,\n            order=False,\n        )\n        for name in (\n            \"counter\",\n            \"_default\",\n            \"repr\",\n            \"eq\",\n            \"order\",\n            \"hash\",\n            \"init\",\n        )\n    ) + (\n        Attribute(\n            name=\"metadata\",\n            default=None,\n            validator=None,\n            repr=True,\n            cmp=None,\n            hash=False,\n            init=True,\n            kw_only=False,\n            eq=True,\n            order=False,\n        ),\n    )\n    cls_counter = 0\n\n    def __init__(\n        self,\n        default,\n        validator,\n        repr,\n        cmp,  # XXX: unused, remove along with cmp\n        hash,\n        init,\n        converter,\n        metadata,\n        type,\n        kw_only,\n        eq,\n        order,\n    ):\n        _CountingAttr.cls_counter += 1\n        self.counter = _CountingAttr.cls_counter\n        self._default = default\n        # If validator is a list/tuple, wrap it using helper validator.\n        if validator and isinstance(validator, (list, tuple)):\n            self._validator = and_(*validator)\n        else:\n            self._validator = validator\n        self.repr = repr\n        self.eq = eq\n        self.order = order\n        self.hash = hash\n        self.init = init\n        self.converter = converter\n        self.metadata = metadata\n        self.type = type\n        self.kw_only = kw_only\n\n    def validator(self, meth):\n        \"\"\"\n        Decorator that adds *meth* to the list of validators.\n\n        Returns *meth* unchanged.\n\n        .. versionadded:: 17.1.0\n        \"\"\"\n        if self._validator is None:\n            self._validator = meth\n        else:\n            self._validator = and_(self._validator, meth)\n        return meth\n\n    def default(self, meth):\n        \"\"\"\n        Decorator that allows to set the default for an attribute.\n\n        Returns *meth* unchanged.\n\n        :raises DefaultAlreadySetError: If default has been set before.\n\n        .. versionadded:: 17.1.0\n        \"\"\"\n        if self._default is not NOTHING:\n            raise DefaultAlreadySetError()\n\n        self._default = Factory(meth, takes_self=True)\n\n        return meth\n\n\n_CountingAttr = _add_eq(_add_repr(_CountingAttr))\n\n\n@attrs(slots=True, init=False, hash=True)\nclass Factory(object):\n    \"\"\"\n    Stores a factory callable.\n\n    If passed as the default value to `attr.ib`, the factory is used to\n    generate a new value.\n\n    :param callable factory: A callable that takes either none or exactly one\n        mandatory positional argument depending on *takes_self*.\n    :param bool takes_self: Pass the partially initialized instance that is\n        being initialized as a positional argument.\n\n    .. versionadded:: 17.1.0  *takes_self*\n    \"\"\"\n\n    factory = attrib()\n    takes_self = attrib()\n\n    def __init__(self, factory, takes_self=False):\n        \"\"\"\n        `Factory` is part of the default machinery so if we want a default\n        value here, we have to implement it ourselves.\n        \"\"\"\n        self.factory = factory\n        self.takes_self = takes_self\n\n\ndef make_class(name, attrs, bases=(object,), **attributes_arguments):\n    \"\"\"\n    A quick way to create a new class called *name* with *attrs*.\n\n    :param name: The name for the new class.\n    :type name: str\n\n    :param attrs: A list of names or a dictionary of mappings of names to\n        attributes.\n\n        If *attrs* is a list or an ordered dict (`dict` on Python 3.6+,\n        `collections.OrderedDict` otherwise), the order is deduced from\n        the order of the names or attributes inside *attrs*.  Otherwise the\n        order of the definition of the attributes is used.\n    :type attrs: `list` or `dict`\n\n    :param tuple bases: Classes that the new class will subclass.\n\n    :param attributes_arguments: Passed unmodified to `attr.s`.\n\n    :return: A new class with *attrs*.\n    :rtype: type\n\n    .. versionadded:: 17.1.0 *bases*\n    .. versionchanged:: 18.1.0 If *attrs* is ordered, the order is retained.\n    \"\"\"\n    if isinstance(attrs, dict):\n        cls_dict = attrs\n    elif isinstance(attrs, (list, tuple)):\n        cls_dict = dict((a, attrib()) for a in attrs)\n    else:\n        raise TypeError(\"attrs argument must be a dict or a list.\")\n\n    post_init = cls_dict.pop(\"__attrs_post_init__\", None)\n    type_ = type(\n        name,\n        bases,\n        {} if post_init is None else {\"__attrs_post_init__\": post_init},\n    )\n    # For pickling to work, the __module__ variable needs to be set to the\n    # frame where the class is created.  Bypass this step in environments where\n    # sys._getframe is not defined (Jython for example) or sys._getframe is not\n    # defined for arguments greater than 0 (IronPython).\n    try:\n        type_.__module__ = sys._getframe(1).f_globals.get(\n            \"__name__\", \"__main__\"\n        )\n    except (AttributeError, ValueError):\n        pass\n\n    # We do it here for proper warnings with meaningful stacklevel.\n    cmp = attributes_arguments.pop(\"cmp\", None)\n    attributes_arguments[\"eq\"], attributes_arguments[\n        \"order\"\n    ] = _determine_eq_order(\n        cmp, attributes_arguments.get(\"eq\"), attributes_arguments.get(\"order\")\n    )\n\n    return _attrs(these=cls_dict, **attributes_arguments)(type_)\n\n\n# These are required by within this module so we define them here and merely\n# import into .validators.\n\n\n@attrs(slots=True, hash=True)\nclass _AndValidator(object):\n    \"\"\"\n    Compose many validators to a single one.\n    \"\"\"\n\n    _validators = attrib()\n\n    def __call__(self, inst, attr, value):\n        for v in self._validators:\n            v(inst, attr, value)\n\n\ndef and_(*validators):\n    \"\"\"\n    A validator that composes multiple validators into one.\n\n    When called on a value, it runs all wrapped validators.\n\n    :param validators: Arbitrary number of validators.\n    :type validators: callables\n\n    .. versionadded:: 17.1.0\n    \"\"\"\n    vals = []\n    for validator in validators:\n        vals.extend(\n            validator._validators\n            if isinstance(validator, _AndValidator)\n            else [validator]\n        )\n\n    return _AndValidator(tuple(vals))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/_version_info.py",
    "content": "from __future__ import absolute_import, division, print_function\n\nfrom functools import total_ordering\n\nfrom ._funcs import astuple\nfrom ._make import attrib, attrs\n\n\n@total_ordering\n@attrs(eq=False, order=False, slots=True, frozen=True)\nclass VersionInfo(object):\n    \"\"\"\n    A version object that can be compared to tuple of length 1--4:\n\n    >>> attr.VersionInfo(19, 1, 0, \"final\")  <= (19, 2)\n    True\n    >>> attr.VersionInfo(19, 1, 0, \"final\") < (19, 1, 1)\n    True\n    >>> vi = attr.VersionInfo(19, 2, 0, \"final\")\n    >>> vi < (19, 1, 1)\n    False\n    >>> vi < (19,)\n    False\n    >>> vi == (19, 2,)\n    True\n    >>> vi == (19, 2, 1)\n    False\n\n    .. versionadded:: 19.2\n    \"\"\"\n\n    year = attrib(type=int)\n    minor = attrib(type=int)\n    micro = attrib(type=int)\n    releaselevel = attrib(type=str)\n\n    @classmethod\n    def _from_version_string(cls, s):\n        \"\"\"\n        Parse *s* and return a _VersionInfo.\n        \"\"\"\n        v = s.split(\".\")\n        if len(v) == 3:\n            v.append(\"final\")\n\n        return cls(\n            year=int(v[0]), minor=int(v[1]), micro=int(v[2]), releaselevel=v[3]\n        )\n\n    def _ensure_tuple(self, other):\n        \"\"\"\n        Ensure *other* is a tuple of a valid length.\n\n        Returns a possibly transformed *other* and ourselves as a tuple of\n        the same length as *other*.\n        \"\"\"\n\n        if self.__class__ is other.__class__:\n            other = astuple(other)\n\n        if not isinstance(other, tuple):\n            raise NotImplementedError\n\n        if not (1 <= len(other) <= 4):\n            raise NotImplementedError\n\n        return astuple(self)[: len(other)], other\n\n    def __eq__(self, other):\n        try:\n            us, them = self._ensure_tuple(other)\n        except NotImplementedError:\n            return NotImplemented\n\n        return us == them\n\n    def __lt__(self, other):\n        try:\n            us, them = self._ensure_tuple(other)\n        except NotImplementedError:\n            return NotImplemented\n\n        # Since alphabetically \"dev0\" < \"final\" < \"post1\" < \"post2\", we don't\n        # have to do anything special with releaselevel for now.\n        return us < them\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/_version_info.pyi",
    "content": "class VersionInfo:\n    @property\n    def year(self) -> int: ...\n    @property\n    def minor(self) -> int: ...\n    @property\n    def micro(self) -> int: ...\n    @property\n    def releaselevel(self) -> str: ...\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/converters.py",
    "content": "\"\"\"\nCommonly useful converters.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom ._make import NOTHING, Factory\n\n\ndef optional(converter):\n    \"\"\"\n    A converter that allows an attribute to be optional. An optional attribute\n    is one which can be set to ``None``.\n\n    :param callable converter: the converter that is used for non-``None``\n        values.\n\n    .. versionadded:: 17.1.0\n    \"\"\"\n\n    def optional_converter(val):\n        if val is None:\n            return None\n        return converter(val)\n\n    return optional_converter\n\n\ndef default_if_none(default=NOTHING, factory=None):\n    \"\"\"\n    A converter that allows to replace ``None`` values by *default* or the\n    result of *factory*.\n\n    :param default: Value to be used if ``None`` is passed. Passing an instance\n       of `attr.Factory` is supported, however the ``takes_self`` option\n       is *not*.\n    :param callable factory: A callable that takes not parameters whose result\n       is used if ``None`` is passed.\n\n    :raises TypeError: If **neither** *default* or *factory* is passed.\n    :raises TypeError: If **both** *default* and *factory* are passed.\n    :raises ValueError: If an instance of `attr.Factory` is passed with\n       ``takes_self=True``.\n\n    .. versionadded:: 18.2.0\n    \"\"\"\n    if default is NOTHING and factory is None:\n        raise TypeError(\"Must pass either `default` or `factory`.\")\n\n    if default is not NOTHING and factory is not None:\n        raise TypeError(\n            \"Must pass either `default` or `factory` but not both.\"\n        )\n\n    if factory is not None:\n        default = Factory(factory)\n\n    if isinstance(default, Factory):\n        if default.takes_self:\n            raise ValueError(\n                \"`takes_self` is not supported by default_if_none.\"\n            )\n\n        def default_if_none_converter(val):\n            if val is not None:\n                return val\n\n            return default.factory()\n\n    else:\n\n        def default_if_none_converter(val):\n            if val is not None:\n                return val\n\n            return default\n\n    return default_if_none_converter\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/converters.pyi",
    "content": "from typing import TypeVar, Optional, Callable, overload\nfrom . import _ConverterType\n\n_T = TypeVar(\"_T\")\n\ndef optional(\n    converter: _ConverterType[_T]\n) -> _ConverterType[Optional[_T]]: ...\n@overload\ndef default_if_none(default: _T) -> _ConverterType[_T]: ...\n@overload\ndef default_if_none(*, factory: Callable[[], _T]) -> _ConverterType[_T]: ...\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/exceptions.py",
    "content": "from __future__ import absolute_import, division, print_function\n\n\nclass FrozenInstanceError(AttributeError):\n    \"\"\"\n    A frozen/immutable instance has been attempted to be modified.\n\n    It mirrors the behavior of ``namedtuples`` by using the same error message\n    and subclassing `AttributeError`.\n\n    .. versionadded:: 16.1.0\n    \"\"\"\n\n    msg = \"can't set attribute\"\n    args = [msg]\n\n\nclass AttrsAttributeNotFoundError(ValueError):\n    \"\"\"\n    An ``attrs`` function couldn't find an attribute that the user asked for.\n\n    .. versionadded:: 16.2.0\n    \"\"\"\n\n\nclass NotAnAttrsClassError(ValueError):\n    \"\"\"\n    A non-``attrs`` class has been passed into an ``attrs`` function.\n\n    .. versionadded:: 16.2.0\n    \"\"\"\n\n\nclass DefaultAlreadySetError(RuntimeError):\n    \"\"\"\n    A default has been set using ``attr.ib()`` and is attempted to be reset\n    using the decorator.\n\n    .. versionadded:: 17.1.0\n    \"\"\"\n\n\nclass UnannotatedAttributeError(RuntimeError):\n    \"\"\"\n    A class with ``auto_attribs=True`` has an ``attr.ib()`` without a type\n    annotation.\n\n    .. versionadded:: 17.3.0\n    \"\"\"\n\n\nclass PythonTooOldError(RuntimeError):\n    \"\"\"\n    An ``attrs`` feature requiring a more recent python version has been used.\n\n    .. versionadded:: 18.2.0\n    \"\"\"\n\n\nclass NotCallableError(TypeError):\n    \"\"\"\n    A ``attr.ib()`` requiring a callable has been set with a value\n    that is not callable.\n\n    .. versionadded:: 19.2.0\n    \"\"\"\n\n    def __init__(self, msg, value):\n        super(TypeError, self).__init__(msg, value)\n        self.msg = msg\n        self.value = value\n\n    def __str__(self):\n        return str(self.msg)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/exceptions.pyi",
    "content": "from typing import Any\n\nclass FrozenInstanceError(AttributeError):\n    msg: str = ...\n\nclass AttrsAttributeNotFoundError(ValueError): ...\nclass NotAnAttrsClassError(ValueError): ...\nclass DefaultAlreadySetError(RuntimeError): ...\nclass UnannotatedAttributeError(RuntimeError): ...\nclass PythonTooOldError(RuntimeError): ...\n\nclass NotCallableError(TypeError):\n    msg: str = ...\n    value: Any = ...\n    def __init__(self, msg: str, value: Any) -> None: ...\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/filters.py",
    "content": "\"\"\"\nCommonly useful filters for `attr.asdict`.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom ._compat import isclass\nfrom ._make import Attribute\n\n\ndef _split_what(what):\n    \"\"\"\n    Returns a tuple of `frozenset`s of classes and attributes.\n    \"\"\"\n    return (\n        frozenset(cls for cls in what if isclass(cls)),\n        frozenset(cls for cls in what if isinstance(cls, Attribute)),\n    )\n\n\ndef include(*what):\n    \"\"\"\n    Whitelist *what*.\n\n    :param what: What to whitelist.\n    :type what: `list` of `type` or `attr.Attribute`\\\\ s\n\n    :rtype: `callable`\n    \"\"\"\n    cls, attrs = _split_what(what)\n\n    def include_(attribute, value):\n        return value.__class__ in cls or attribute in attrs\n\n    return include_\n\n\ndef exclude(*what):\n    \"\"\"\n    Blacklist *what*.\n\n    :param what: What to blacklist.\n    :type what: `list` of classes or `attr.Attribute`\\\\ s.\n\n    :rtype: `callable`\n    \"\"\"\n    cls, attrs = _split_what(what)\n\n    def exclude_(attribute, value):\n        return value.__class__ not in cls and attribute not in attrs\n\n    return exclude_\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/filters.pyi",
    "content": "from typing import Union, Any\nfrom . import Attribute, _FilterType\n\ndef include(*what: Union[type, Attribute[Any]]) -> _FilterType[Any]: ...\ndef exclude(*what: Union[type, Attribute[Any]]) -> _FilterType[Any]: ...\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/py.typed",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/validators.py",
    "content": "\"\"\"\nCommonly useful validators.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nimport re\n\nfrom ._make import _AndValidator, and_, attrib, attrs\nfrom .exceptions import NotCallableError\n\n\n__all__ = [\n    \"and_\",\n    \"deep_iterable\",\n    \"deep_mapping\",\n    \"in_\",\n    \"instance_of\",\n    \"is_callable\",\n    \"matches_re\",\n    \"optional\",\n    \"provides\",\n]\n\n\n@attrs(repr=False, slots=True, hash=True)\nclass _InstanceOfValidator(object):\n    type = attrib()\n\n    def __call__(self, inst, attr, value):\n        \"\"\"\n        We use a callable class to be able to change the ``__repr__``.\n        \"\"\"\n        if not isinstance(value, self.type):\n            raise TypeError(\n                \"'{name}' must be {type!r} (got {value!r} that is a \"\n                \"{actual!r}).\".format(\n                    name=attr.name,\n                    type=self.type,\n                    actual=value.__class__,\n                    value=value,\n                ),\n                attr,\n                self.type,\n                value,\n            )\n\n    def __repr__(self):\n        return \"<instance_of validator for type {type!r}>\".format(\n            type=self.type\n        )\n\n\ndef instance_of(type):\n    \"\"\"\n    A validator that raises a `TypeError` if the initializer is called\n    with a wrong type for this particular attribute (checks are performed using\n    `isinstance` therefore it's also valid to pass a tuple of types).\n\n    :param type: The type to check for.\n    :type type: type or tuple of types\n\n    :raises TypeError: With a human readable error message, the attribute\n        (of type `attr.Attribute`), the expected type, and the value it\n        got.\n    \"\"\"\n    return _InstanceOfValidator(type)\n\n\n@attrs(repr=False, frozen=True)\nclass _MatchesReValidator(object):\n    regex = attrib()\n    flags = attrib()\n    match_func = attrib()\n\n    def __call__(self, inst, attr, value):\n        \"\"\"\n        We use a callable class to be able to change the ``__repr__``.\n        \"\"\"\n        if not self.match_func(value):\n            raise ValueError(\n                \"'{name}' must match regex {regex!r}\"\n                \" ({value!r} doesn't)\".format(\n                    name=attr.name, regex=self.regex.pattern, value=value\n                ),\n                attr,\n                self.regex,\n                value,\n            )\n\n    def __repr__(self):\n        return \"<matches_re validator for pattern {regex!r}>\".format(\n            regex=self.regex\n        )\n\n\ndef matches_re(regex, flags=0, func=None):\n    r\"\"\"\n    A validator that raises `ValueError` if the initializer is called\n    with a string that doesn't match *regex*.\n\n    :param str regex: a regex string to match against\n    :param int flags: flags that will be passed to the underlying re function\n        (default 0)\n    :param callable func: which underlying `re` function to call (options\n        are `re.fullmatch`, `re.search`, `re.match`, default\n        is ``None`` which means either `re.fullmatch` or an emulation of\n        it on Python 2). For performance reasons, they won't be used directly\n        but on a pre-`re.compile`\\ ed pattern.\n\n    .. versionadded:: 19.2.0\n    \"\"\"\n    fullmatch = getattr(re, \"fullmatch\", None)\n    valid_funcs = (fullmatch, None, re.search, re.match)\n    if func not in valid_funcs:\n        raise ValueError(\n            \"'func' must be one of %s.\"\n            % (\n                \", \".join(\n                    sorted(\n                        e and e.__name__ or \"None\" for e in set(valid_funcs)\n                    )\n                ),\n            )\n        )\n\n    pattern = re.compile(regex, flags)\n    if func is re.match:\n        match_func = pattern.match\n    elif func is re.search:\n        match_func = pattern.search\n    else:\n        if fullmatch:\n            match_func = pattern.fullmatch\n        else:\n            pattern = re.compile(r\"(?:{})\\Z\".format(regex), flags)\n            match_func = pattern.match\n\n    return _MatchesReValidator(pattern, flags, match_func)\n\n\n@attrs(repr=False, slots=True, hash=True)\nclass _ProvidesValidator(object):\n    interface = attrib()\n\n    def __call__(self, inst, attr, value):\n        \"\"\"\n        We use a callable class to be able to change the ``__repr__``.\n        \"\"\"\n        if not self.interface.providedBy(value):\n            raise TypeError(\n                \"'{name}' must provide {interface!r} which {value!r} \"\n                \"doesn't.\".format(\n                    name=attr.name, interface=self.interface, value=value\n                ),\n                attr,\n                self.interface,\n                value,\n            )\n\n    def __repr__(self):\n        return \"<provides validator for interface {interface!r}>\".format(\n            interface=self.interface\n        )\n\n\ndef provides(interface):\n    \"\"\"\n    A validator that raises a `TypeError` if the initializer is called\n    with an object that does not provide the requested *interface* (checks are\n    performed using ``interface.providedBy(value)`` (see `zope.interface\n    <https://zopeinterface.readthedocs.io/en/latest/>`_).\n\n    :param zope.interface.Interface interface: The interface to check for.\n\n    :raises TypeError: With a human readable error message, the attribute\n        (of type `attr.Attribute`), the expected interface, and the\n        value it got.\n    \"\"\"\n    return _ProvidesValidator(interface)\n\n\n@attrs(repr=False, slots=True, hash=True)\nclass _OptionalValidator(object):\n    validator = attrib()\n\n    def __call__(self, inst, attr, value):\n        if value is None:\n            return\n\n        self.validator(inst, attr, value)\n\n    def __repr__(self):\n        return \"<optional validator for {what} or None>\".format(\n            what=repr(self.validator)\n        )\n\n\ndef optional(validator):\n    \"\"\"\n    A validator that makes an attribute optional.  An optional attribute is one\n    which can be set to ``None`` in addition to satisfying the requirements of\n    the sub-validator.\n\n    :param validator: A validator (or a list of validators) that is used for\n        non-``None`` values.\n    :type validator: callable or `list` of callables.\n\n    .. versionadded:: 15.1.0\n    .. versionchanged:: 17.1.0 *validator* can be a list of validators.\n    \"\"\"\n    if isinstance(validator, list):\n        return _OptionalValidator(_AndValidator(validator))\n    return _OptionalValidator(validator)\n\n\n@attrs(repr=False, slots=True, hash=True)\nclass _InValidator(object):\n    options = attrib()\n\n    def __call__(self, inst, attr, value):\n        try:\n            in_options = value in self.options\n        except TypeError:  # e.g. `1 in \"abc\"`\n            in_options = False\n\n        if not in_options:\n            raise ValueError(\n                \"'{name}' must be in {options!r} (got {value!r})\".format(\n                    name=attr.name, options=self.options, value=value\n                )\n            )\n\n    def __repr__(self):\n        return \"<in_ validator with options {options!r}>\".format(\n            options=self.options\n        )\n\n\ndef in_(options):\n    \"\"\"\n    A validator that raises a `ValueError` if the initializer is called\n    with a value that does not belong in the options provided.  The check is\n    performed using ``value in options``.\n\n    :param options: Allowed options.\n    :type options: list, tuple, `enum.Enum`, ...\n\n    :raises ValueError: With a human readable error message, the attribute (of\n       type `attr.Attribute`), the expected options, and the value it\n       got.\n\n    .. versionadded:: 17.1.0\n    \"\"\"\n    return _InValidator(options)\n\n\n@attrs(repr=False, slots=False, hash=True)\nclass _IsCallableValidator(object):\n    def __call__(self, inst, attr, value):\n        \"\"\"\n        We use a callable class to be able to change the ``__repr__``.\n        \"\"\"\n        if not callable(value):\n            message = (\n                \"'{name}' must be callable \"\n                \"(got {value!r} that is a {actual!r}).\"\n            )\n            raise NotCallableError(\n                msg=message.format(\n                    name=attr.name, value=value, actual=value.__class__\n                ),\n                value=value,\n            )\n\n    def __repr__(self):\n        return \"<is_callable validator>\"\n\n\ndef is_callable():\n    \"\"\"\n    A validator that raises a `attr.exceptions.NotCallableError` if the\n    initializer is called with a value for this particular attribute\n    that is not callable.\n\n    .. versionadded:: 19.1.0\n\n    :raises `attr.exceptions.NotCallableError`: With a human readable error\n        message containing the attribute (`attr.Attribute`) name,\n        and the value it got.\n    \"\"\"\n    return _IsCallableValidator()\n\n\n@attrs(repr=False, slots=True, hash=True)\nclass _DeepIterable(object):\n    member_validator = attrib(validator=is_callable())\n    iterable_validator = attrib(\n        default=None, validator=optional(is_callable())\n    )\n\n    def __call__(self, inst, attr, value):\n        \"\"\"\n        We use a callable class to be able to change the ``__repr__``.\n        \"\"\"\n        if self.iterable_validator is not None:\n            self.iterable_validator(inst, attr, value)\n\n        for member in value:\n            self.member_validator(inst, attr, member)\n\n    def __repr__(self):\n        iterable_identifier = (\n            \"\"\n            if self.iterable_validator is None\n            else \" {iterable!r}\".format(iterable=self.iterable_validator)\n        )\n        return (\n            \"<deep_iterable validator for{iterable_identifier}\"\n            \" iterables of {member!r}>\"\n        ).format(\n            iterable_identifier=iterable_identifier,\n            member=self.member_validator,\n        )\n\n\ndef deep_iterable(member_validator, iterable_validator=None):\n    \"\"\"\n    A validator that performs deep validation of an iterable.\n\n    :param member_validator: Validator to apply to iterable members\n    :param iterable_validator: Validator to apply to iterable itself\n        (optional)\n\n    .. versionadded:: 19.1.0\n\n    :raises TypeError: if any sub-validators fail\n    \"\"\"\n    return _DeepIterable(member_validator, iterable_validator)\n\n\n@attrs(repr=False, slots=True, hash=True)\nclass _DeepMapping(object):\n    key_validator = attrib(validator=is_callable())\n    value_validator = attrib(validator=is_callable())\n    mapping_validator = attrib(default=None, validator=optional(is_callable()))\n\n    def __call__(self, inst, attr, value):\n        \"\"\"\n        We use a callable class to be able to change the ``__repr__``.\n        \"\"\"\n        if self.mapping_validator is not None:\n            self.mapping_validator(inst, attr, value)\n\n        for key in value:\n            self.key_validator(inst, attr, key)\n            self.value_validator(inst, attr, value[key])\n\n    def __repr__(self):\n        return (\n            \"<deep_mapping validator for objects mapping {key!r} to {value!r}>\"\n        ).format(key=self.key_validator, value=self.value_validator)\n\n\ndef deep_mapping(key_validator, value_validator, mapping_validator=None):\n    \"\"\"\n    A validator that performs deep validation of a dictionary.\n\n    :param key_validator: Validator to apply to dictionary keys\n    :param value_validator: Validator to apply to dictionary values\n    :param mapping_validator: Validator to apply to top-level mapping\n        attribute (optional)\n\n    .. versionadded:: 19.1.0\n\n    :raises TypeError: if any sub-validators fail\n    \"\"\"\n    return _DeepMapping(key_validator, value_validator, mapping_validator)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attr/validators.pyi",
    "content": "from typing import (\n    Container,\n    List,\n    Union,\n    TypeVar,\n    Type,\n    Any,\n    Optional,\n    Tuple,\n    Iterable,\n    Mapping,\n    Callable,\n    Match,\n    AnyStr,\n    overload,\n)\nfrom . import _ValidatorType\n\n_T = TypeVar(\"_T\")\n_T1 = TypeVar(\"_T1\")\n_T2 = TypeVar(\"_T2\")\n_T3 = TypeVar(\"_T3\")\n_I = TypeVar(\"_I\", bound=Iterable)\n_K = TypeVar(\"_K\")\n_V = TypeVar(\"_V\")\n_M = TypeVar(\"_M\", bound=Mapping)\n\n# To be more precise on instance_of use some overloads.\n# If there are more than 3 items in the tuple then we fall back to Any\n@overload\ndef instance_of(type: Type[_T]) -> _ValidatorType[_T]: ...\n@overload\ndef instance_of(type: Tuple[Type[_T]]) -> _ValidatorType[_T]: ...\n@overload\ndef instance_of(\n    type: Tuple[Type[_T1], Type[_T2]]\n) -> _ValidatorType[Union[_T1, _T2]]: ...\n@overload\ndef instance_of(\n    type: Tuple[Type[_T1], Type[_T2], Type[_T3]]\n) -> _ValidatorType[Union[_T1, _T2, _T3]]: ...\n@overload\ndef instance_of(type: Tuple[type, ...]) -> _ValidatorType[Any]: ...\ndef provides(interface: Any) -> _ValidatorType[Any]: ...\ndef optional(\n    validator: Union[_ValidatorType[_T], List[_ValidatorType[_T]]]\n) -> _ValidatorType[Optional[_T]]: ...\ndef in_(options: Container[_T]) -> _ValidatorType[_T]: ...\ndef and_(*validators: _ValidatorType[_T]) -> _ValidatorType[_T]: ...\ndef matches_re(\n    regex: AnyStr,\n    flags: int = ...,\n    func: Optional[\n        Callable[[AnyStr, AnyStr, int], Optional[Match[AnyStr]]]\n    ] = ...,\n) -> _ValidatorType[AnyStr]: ...\ndef deep_iterable(\n    member_validator: _ValidatorType[_T],\n    iterable_validator: Optional[_ValidatorType[_I]] = ...,\n) -> _ValidatorType[_I]: ...\ndef deep_mapping(\n    key_validator: _ValidatorType[_K],\n    value_validator: _ValidatorType[_V],\n    mapping_validator: Optional[_ValidatorType[_M]] = ...,\n) -> _ValidatorType[_M]: ...\ndef is_callable() -> _ValidatorType[_T]: ...\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attrs-19.3.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attrs-19.3.0.dist-info/LICENSE",
    "content": "The MIT License (MIT)\n\nCopyright (c) 2015 Hynek Schlawack\n\nPermission is hereby granted, free of charge, to any person obtaining a copy\nof this software and associated documentation files (the \"Software\"), to deal\nin the Software without restriction, including without limitation the rights\nto use, copy, modify, merge, publish, distribute, sublicense, and/or sell\ncopies of the Software, and to permit persons to whom the Software is\nfurnished to do so, subject to the following conditions:\n\nThe above copyright notice and this permission notice shall be included in all\ncopies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\nIMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\nFITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\nAUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\nLIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\nOUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\nSOFTWARE.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attrs-19.3.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: attrs\nVersion: 19.3.0\nSummary: Classes Without Boilerplate\nHome-page: https://www.attrs.org/\nAuthor: Hynek Schlawack\nAuthor-email: hs@ox.cx\nMaintainer: Hynek Schlawack\nMaintainer-email: hs@ox.cx\nLicense: MIT\nProject-URL: Documentation, https://www.attrs.org/\nProject-URL: Bug Tracker, https://github.com/python-attrs/attrs/issues\nProject-URL: Source Code, https://github.com/python-attrs/attrs\nKeywords: class,attribute,boilerplate\nPlatform: UNKNOWN\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Intended Audience :: Developers\nClassifier: Natural Language :: English\nClassifier: License :: OSI Approved :: MIT License\nClassifier: Operating System :: OS Independent\nClassifier: Programming Language :: Python\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nClassifier: Programming Language :: Python :: 3.8\nClassifier: Programming Language :: Python :: Implementation :: CPython\nClassifier: Programming Language :: Python :: Implementation :: PyPy\nClassifier: Topic :: Software Development :: Libraries :: Python Modules\nRequires-Python: >=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*\nDescription-Content-Type: text/x-rst\nProvides-Extra: azure-pipelines\nRequires-Dist: coverage ; extra == 'azure-pipelines'\nRequires-Dist: hypothesis ; extra == 'azure-pipelines'\nRequires-Dist: pympler ; extra == 'azure-pipelines'\nRequires-Dist: pytest (>=4.3.0) ; extra == 'azure-pipelines'\nRequires-Dist: six ; extra == 'azure-pipelines'\nRequires-Dist: zope.interface ; extra == 'azure-pipelines'\nRequires-Dist: pytest-azurepipelines ; extra == 'azure-pipelines'\nProvides-Extra: dev\nRequires-Dist: coverage ; extra == 'dev'\nRequires-Dist: hypothesis ; extra == 'dev'\nRequires-Dist: pympler ; extra == 'dev'\nRequires-Dist: pytest (>=4.3.0) ; extra == 'dev'\nRequires-Dist: six ; extra == 'dev'\nRequires-Dist: zope.interface ; extra == 'dev'\nRequires-Dist: sphinx ; extra == 'dev'\nRequires-Dist: pre-commit ; extra == 'dev'\nProvides-Extra: docs\nRequires-Dist: sphinx ; extra == 'docs'\nRequires-Dist: zope.interface ; extra == 'docs'\nProvides-Extra: tests\nRequires-Dist: coverage ; extra == 'tests'\nRequires-Dist: hypothesis ; extra == 'tests'\nRequires-Dist: pympler ; extra == 'tests'\nRequires-Dist: pytest (>=4.3.0) ; extra == 'tests'\nRequires-Dist: six ; extra == 'tests'\nRequires-Dist: zope.interface ; extra == 'tests'\n\n.. image:: https://www.attrs.org/en/latest/_static/attrs_logo.png\n   :alt: attrs Logo\n\n======================================\n``attrs``: Classes Without Boilerplate\n======================================\n\n.. image:: https://readthedocs.org/projects/attrs/badge/?version=stable\n   :target: https://www.attrs.org/en/stable/?badge=stable\n   :alt: Documentation Status\n\n.. image:: https://attrs.visualstudio.com/attrs/_apis/build/status/python-attrs.attrs?branchName=master\n   :target: https://attrs.visualstudio.com/attrs/_build/latest?definitionId=1&branchName=master\n   :alt: CI Status\n\n.. image:: https://codecov.io/github/python-attrs/attrs/branch/master/graph/badge.svg\n   :target: https://codecov.io/github/python-attrs/attrs\n   :alt: Test Coverage\n\n.. image:: https://img.shields.io/badge/code%20style-black-000000.svg\n   :target: https://github.com/psf/black\n   :alt: Code style: black\n\n.. teaser-begin\n\n``attrs`` is the Python package that will bring back the **joy** of **writing classes** by relieving you from the drudgery of implementing object protocols (aka `dunder <https://nedbatchelder.com/blog/200605/dunder.html>`_ methods).\n\nIts main goal is to help you to write **concise** and **correct** software without slowing down your code.\n\n.. -spiel-end-\n\nFor that, it gives you a class decorator and a way to declaratively define the attributes on that class:\n\n.. -code-begin-\n\n.. code-block:: pycon\n\n   >>> import attr\n\n   >>> @attr.s\n   ... class SomeClass(object):\n   ...     a_number = attr.ib(default=42)\n   ...     list_of_numbers = attr.ib(factory=list)\n   ...\n   ...     def hard_math(self, another_number):\n   ...         return self.a_number + sum(self.list_of_numbers) * another_number\n\n\n   >>> sc = SomeClass(1, [1, 2, 3])\n   >>> sc\n   SomeClass(a_number=1, list_of_numbers=[1, 2, 3])\n\n   >>> sc.hard_math(3)\n   19\n   >>> sc == SomeClass(1, [1, 2, 3])\n   True\n   >>> sc != SomeClass(2, [3, 2, 1])\n   True\n\n   >>> attr.asdict(sc)\n   {'a_number': 1, 'list_of_numbers': [1, 2, 3]}\n\n   >>> SomeClass()\n   SomeClass(a_number=42, list_of_numbers=[])\n\n   >>> C = attr.make_class(\"C\", [\"a\", \"b\"])\n   >>> C(\"foo\", \"bar\")\n   C(a='foo', b='bar')\n\n\nAfter *declaring* your attributes ``attrs`` gives you:\n\n- a concise and explicit overview of the class's attributes,\n- a nice human-readable ``__repr__``,\n- a complete set of comparison methods (equality and ordering),\n- an initializer,\n- and much more,\n\n*without* writing dull boilerplate code again and again and *without* runtime performance penalties.\n\nOn Python 3.6 and later, you can often even drop the calls to ``attr.ib()`` by using `type annotations <https://www.attrs.org/en/latest/types.html>`_.\n\nThis gives you the power to use actual classes with actual types in your code instead of confusing ``tuple``\\ s or `confusingly behaving <https://www.attrs.org/en/stable/why.html#namedtuples>`_ ``namedtuple``\\ s.\nWhich in turn encourages you to write *small classes* that do `one thing well <https://www.destroyallsoftware.com/talks/boundaries>`_.\nNever again violate the `single responsibility principle <https://en.wikipedia.org/wiki/Single_responsibility_principle>`_ just because implementing ``__init__`` et al is a painful drag.\n\n\n.. -testimonials-\n\nTestimonials\n============\n\n**Amber Hawkie Brown**, Twisted Release Manager and Computer Owl:\n\n  Writing a fully-functional class using attrs takes me less time than writing this testimonial.\n\n\n**Glyph Lefkowitz**, creator of `Twisted <https://twistedmatrix.com/>`_, `Automat <https://pypi.org/project/Automat/>`_, and other open source software, in `The One Python Library Everyone Needs <https://glyph.twistedmatrix.com/2016/08/attrs.html>`_:\n\n  I’m looking forward to is being able to program in Python-with-attrs everywhere.\n  It exerts a subtle, but positive, design influence in all the codebases I’ve see it used in.\n\n\n**Kenneth Reitz**, creator of `Requests <https://github.com/psf/requests>`_ (`on paper no less <https://twitter.com/hynek/status/866817877650751488>`_!):\n\n  attrs—classes for humans.  I like it.\n\n\n**Łukasz Langa**, creator of `Black <https://github.com/psf/black>`_, prolific Python core developer, and release manager for Python 3.8 and 3.9:\n\n  I'm increasingly digging your attr.ocity. Good job!\n\n\n.. -end-\n\n.. -project-information-\n\nGetting Help\n============\n\nPlease use the ``python-attrs`` tag on `StackOverflow <https://stackoverflow.com/questions/tagged/python-attrs>`_ to get help.\n\nAnswering questions of your fellow developers is also great way to help the project!\n\n\nProject Information\n===================\n\n``attrs`` is released under the `MIT <https://choosealicense.com/licenses/mit/>`_ license,\nits documentation lives at `Read the Docs <https://www.attrs.org/>`_,\nthe code on `GitHub <https://github.com/python-attrs/attrs>`_,\nand the latest release on `PyPI <https://pypi.org/project/attrs/>`_.\nIt’s rigorously tested on Python 2.7, 3.4+, and PyPy.\n\nWe collect information on **third-party extensions** in our `wiki <https://github.com/python-attrs/attrs/wiki/Extensions-to-attrs>`_.\nFeel free to browse and add your own!\n\nIf you'd like to contribute to ``attrs`` you're most welcome and we've written `a little guide <https://www.attrs.org/en/latest/contributing.html>`_ to get you started!\n\n\nRelease Information\n===================\n\n19.3.0 (2019-10-15)\n-------------------\n\nChanges\n^^^^^^^\n\n- Fixed ``auto_attribs`` usage when default values cannot be compared directly with ``==``, such as ``numpy`` arrays.\n  `#585 <https://github.com/python-attrs/attrs/issues/585>`_\n\n`Full changelog <https://www.attrs.org/en/stable/changelog.html>`_.\n\nCredits\n=======\n\n``attrs`` is written and maintained by `Hynek Schlawack <https://hynek.me/>`_.\n\nThe development is kindly supported by `Variomedia AG <https://www.variomedia.de/>`_.\n\nA full list of contributors can be found in `GitHub's overview <https://github.com/python-attrs/attrs/graphs/contributors>`_.\n\nIt’s the spiritual successor of `characteristic <https://characteristic.readthedocs.io/>`_ and aspires to fix some of it clunkiness and unfortunate decisions.\nBoth were inspired by Twisted’s `FancyEqMixin <https://twistedmatrix.com/documents/current/api/twisted.python.util.FancyEqMixin.html>`_ but both are implemented using class decorators because `subclassing is bad for you <https://www.youtube.com/watch?v=3MNVP9-hglc>`_, m’kay?\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attrs-19.3.0.dist-info/RECORD",
    "content": "attr/__init__.py,sha256=ONaI-ZEGOIC7IDqH2HANgesnOxPE1m0GIRRYPPsXEHk,1349\r\nattr/__init__.pyi,sha256=fOnMRTF00b5J23PYPF74u66UVhVzzm0KYVxzmVXHPw0,8257\r\nattr/__pycache__/__init__.cpython-36.pyc,,\r\nattr/__pycache__/_compat.cpython-36.pyc,,\r\nattr/__pycache__/_config.cpython-36.pyc,,\r\nattr/__pycache__/_funcs.cpython-36.pyc,,\r\nattr/__pycache__/_make.cpython-36.pyc,,\r\nattr/__pycache__/_version_info.cpython-36.pyc,,\r\nattr/__pycache__/converters.cpython-36.pyc,,\r\nattr/__pycache__/exceptions.cpython-36.pyc,,\r\nattr/__pycache__/filters.cpython-36.pyc,,\r\nattr/__pycache__/validators.cpython-36.pyc,,\r\nattr/_compat.py,sha256=-pJtdtqgCg0K6rH_BWf3wKuTum58GD-WWPclQQ2SUaU,7326\r\nattr/_config.py,sha256=_KvW0mQdH2PYjHc0YfIUaV_o2pVfM7ziMEYTxwmEhOA,514\r\nattr/_funcs.py,sha256=unAJfNGSTOzxyFzkj7Rs3O1bfsQodmXyir9uZKen-vY,9696\r\nattr/_make.py,sha256=HhjGhFEbnxPKuUb9hFmAjXoQGpekniw1IEF3_Z-vwCc,70807\r\nattr/_version_info.py,sha256=azMi1lNelb3cJvvYUMXsXVbUANkRzbD5IEiaXVpeVr4,2162\r\nattr/_version_info.pyi,sha256=x_M3L3WuB7r_ULXAWjx959udKQ4HLB8l-hsc1FDGNvk,209\r\nattr/converters.py,sha256=5QJRYSXE8G7PW0289y_SPwvvZIcw-nJIuBlfYVdB4BQ,2141\r\nattr/converters.pyi,sha256=wAhCoOT1MFV8t323rpD87O7bxQ8CYLTPiBQd-29BieI,351\r\nattr/exceptions.py,sha256=hbhOa3b4W8_mRrbj3FsMTR4Bt5xzbJs5xaFTWn8s6h4,1635\r\nattr/exceptions.pyi,sha256=4zuaJyl2axxWbqnZgxo_2oTpPNbyowEw3A4hqV5PmAc,458\r\nattr/filters.py,sha256=weDxwATsa69T_0bPVjiM1fGsciAMQmwhY5G8Jm5BxuI,1098\r\nattr/filters.pyi,sha256=xDpmKQlFdssgxGa5tsl1ADh_3zwAwAT4vUhd8h-8-Tk,214\r\nattr/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0\r\nattr/validators.py,sha256=8AsxgdDgh3sGPseiUIMPGcTr6PvaDYfH3AK46tsvs8U,11460\r\nattr/validators.pyi,sha256=vZgsJqUwrJevh4v_Hd7_RSXqDrBctE6-3AEZ7uYKodo,1868\r\nattrs-19.3.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nattrs-19.3.0.dist-info/LICENSE,sha256=v2WaKLSSQGAvVrvfSQy-LsUJsVuY-Z17GaUsdA4yeGM,1082\r\nattrs-19.3.0.dist-info/METADATA,sha256=WmnjYy_TftebL3pewXyGEaD4TZRrLUEHk3frEkAtqL0,9022\r\nattrs-19.3.0.dist-info/RECORD,,\r\nattrs-19.3.0.dist-info/WHEEL,sha256=8zNYZbwQSXoB9IfXOjPfeNwvAsALAjffgk27FqvCWbo,110\r\nattrs-19.3.0.dist-info/top_level.txt,sha256=tlRYMddkRlKPqJ96wP2_j9uEsmcNHgD2SbuWd4CzGVU,5\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attrs-19.3.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.33.6)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/attrs-19.3.0.dist-info/top_level.txt",
    "content": "attr\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/automat/__init__.py",
    "content": "# -*- test-case-name: automat -*-\nfrom ._methodical import MethodicalMachine\nfrom ._core import NoTransition\n\n__all__ = [\n    'MethodicalMachine',\n    'NoTransition',\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/automat/_core.py",
    "content": "# -*- test-case-name: automat._test.test_core -*-\n\n\"\"\"\nA core state-machine abstraction.\n\nPerhaps something that could be replaced with or integrated into machinist.\n\"\"\"\n\nfrom itertools import chain\n\n_NO_STATE = \"<no state>\"\n\n\nclass NoTransition(Exception):\n    \"\"\"\n    A finite state machine in C{state} has no transition for C{symbol}.\n\n    @param state: the finite state machine's state at the time of the\n        illegal transition.\n\n    @param symbol: the input symbol for which no transition exists.\n    \"\"\"\n\n    def __init__(self, state, symbol):\n        self.state = state\n        self.symbol = symbol\n        super(Exception, self).__init__(\n            \"no transition for {} in {}\".format(symbol, state)\n        )\n\n\nclass Automaton(object):\n    \"\"\"\n    A declaration of a finite state machine.\n\n    Note that this is not the machine itself; it is immutable.\n    \"\"\"\n\n    def __init__(self):\n        \"\"\"\n        Initialize the set of transitions and the initial state.\n        \"\"\"\n        self._initialState = _NO_STATE\n        self._transitions = set()\n\n\n    @property\n    def initialState(self):\n        \"\"\"\n        Return this automaton's initial state.\n        \"\"\"\n        return self._initialState\n\n\n    @initialState.setter\n    def initialState(self, state):\n        \"\"\"\n        Set this automaton's initial state.  Raises a ValueError if\n        this automaton already has an initial state.\n        \"\"\"\n\n        if self._initialState is not _NO_STATE:\n            raise ValueError(\n                \"initial state already set to {}\".format(self._initialState))\n\n        self._initialState = state\n\n\n    def addTransition(self, inState, inputSymbol, outState, outputSymbols):\n        \"\"\"\n        Add the given transition to the outputSymbol. Raise ValueError if\n        there is already a transition with the same inState and inputSymbol.\n        \"\"\"\n        # keeping self._transitions in a flat list makes addTransition\n        # O(n^2), but state machines don't tend to have hundreds of\n        # transitions.\n        for (anInState, anInputSymbol, anOutState, _) in self._transitions:\n            if (anInState == inState and anInputSymbol == inputSymbol):\n                raise ValueError(\n                    \"already have transition from {} via {}\".format(inState, inputSymbol))\n        self._transitions.add(\n            (inState, inputSymbol, outState, tuple(outputSymbols))\n        )\n\n\n    def allTransitions(self):\n        \"\"\"\n        All transitions.\n        \"\"\"\n        return frozenset(self._transitions)\n\n\n    def inputAlphabet(self):\n        \"\"\"\n        The full set of symbols acceptable to this automaton.\n        \"\"\"\n        return {inputSymbol for (inState, inputSymbol, outState,\n                                 outputSymbol) in self._transitions}\n\n\n    def outputAlphabet(self):\n        \"\"\"\n        The full set of symbols which can be produced by this automaton.\n        \"\"\"\n        return set(\n            chain.from_iterable(\n                outputSymbols for\n                (inState, inputSymbol, outState, outputSymbols)\n                in self._transitions\n            )\n        )\n\n\n    def states(self):\n        \"\"\"\n        All valid states; \"Q\" in the mathematical description of a state\n        machine.\n        \"\"\"\n        return frozenset(\n            chain.from_iterable(\n                (inState, outState)\n                for\n                (inState, inputSymbol, outState, outputSymbol)\n                in self._transitions\n            )\n        )\n\n\n    def outputForInput(self, inState, inputSymbol):\n        \"\"\"\n        A 2-tuple of (outState, outputSymbols) for inputSymbol.\n        \"\"\"\n        for (anInState, anInputSymbol,\n             outState, outputSymbols) in self._transitions:\n            if (inState, inputSymbol) == (anInState, anInputSymbol):\n                return (outState, list(outputSymbols))\n        raise NoTransition(state=inState, symbol=inputSymbol)\n\n\nclass Transitioner(object):\n    \"\"\"\n    The combination of a current state and an L{Automaton}.\n    \"\"\"\n\n    def __init__(self, automaton, initialState):\n        self._automaton = automaton\n        self._state = initialState\n        self._tracer = None\n\n    def setTrace(self, tracer):\n        self._tracer = tracer\n\n    def transition(self, inputSymbol):\n        \"\"\"\n        Transition between states, returning any outputs.\n        \"\"\"\n        outState, outputSymbols = self._automaton.outputForInput(self._state,\n                                                                 inputSymbol)\n        outTracer = None\n        if self._tracer:\n            outTracer = self._tracer(self._state._name(),\n                                     inputSymbol._name(),\n                                     outState._name())\n        self._state = outState\n        return (outputSymbols, outTracer)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/automat/_discover.py",
    "content": "import collections\nimport inspect\nfrom automat import MethodicalMachine\nfrom twisted.python.modules import PythonModule, getModule\n\n\ndef isOriginalLocation(attr):\n    \"\"\"\n    Attempt to discover if this appearance of a PythonAttribute\n    representing a class refers to the module where that class was\n    defined.\n    \"\"\"\n    sourceModule = inspect.getmodule(attr.load())\n    if sourceModule is None:\n        return False\n\n    currentModule = attr\n    while not isinstance(currentModule, PythonModule):\n        currentModule = currentModule.onObject\n\n    return currentModule.name == sourceModule.__name__\n\n\ndef findMachinesViaWrapper(within):\n    \"\"\"\n    Recursively yield L{MethodicalMachine}s and their FQPNs within a\n    L{PythonModule} or a L{twisted.python.modules.PythonAttribute}\n    wrapper object.\n\n    Note that L{PythonModule}s may refer to packages, as well.\n\n    The discovery heuristic considers L{MethodicalMachine} instances\n    that are module-level attributes or class-level attributes\n    accessible from module scope.  Machines inside nested classes will\n    be discovered, but those returned from functions or methods will not be.\n\n    @type within: L{PythonModule} or L{twisted.python.modules.PythonAttribute}\n    @param within: Where to start the search.\n\n    @return: a generator which yields FQPN, L{MethodicalMachine} pairs.\n    \"\"\"\n    queue = collections.deque([within])\n    visited = set()\n\n    while queue:\n        attr = queue.pop()\n        value = attr.load()\n\n        if isinstance(value, MethodicalMachine) and value not in visited:\n            visited.add(value)\n            yield attr.name, value\n        elif (inspect.isclass(value) and isOriginalLocation(attr) and\n              value not in visited):\n            visited.add(value)\n            queue.extendleft(attr.iterAttributes())\n        elif isinstance(attr, PythonModule) and value not in visited:\n            visited.add(value)\n            queue.extendleft(attr.iterAttributes())\n            queue.extendleft(attr.iterModules())\n\n\nclass InvalidFQPN(Exception):\n    \"\"\"\n    The given FQPN was not a dot-separated list of Python objects.\n    \"\"\"\n\n\nclass NoModule(InvalidFQPN):\n    \"\"\"\n    A prefix of the FQPN was not an importable module or package.\n    \"\"\"\n\n\nclass NoObject(InvalidFQPN):\n    \"\"\"\n    A suffix of the FQPN was not an accessible object\n    \"\"\"\n\n\ndef wrapFQPN(fqpn):\n    \"\"\"\n    Given an FQPN, retrieve the object via the global Python module\n    namespace and wrap it with a L{PythonModule} or a\n    L{twisted.python.modules.PythonAttribute}.\n    \"\"\"\n    # largely cribbed from t.p.reflect.namedAny\n\n    if not fqpn:\n        raise InvalidFQPN(\"FQPN was empty\")\n\n    components = collections.deque(fqpn.split('.'))\n\n    if '' in components:\n        raise InvalidFQPN(\n            \"name must be a string giving a '.'-separated list of Python \"\n            \"identifiers, not %r\" % (fqpn,))\n\n    component = components.popleft()\n    try:\n        module = getModule(component)\n    except KeyError:\n        raise NoModule(component)\n\n    # find the bottom-most module\n    while components:\n        component = components.popleft()\n        try:\n            module = module[component]\n        except KeyError:\n            components.appendleft(component)\n            break\n        else:\n            module.load()\n    else:\n        return module\n\n    # find the bottom-most attribute\n    attribute = module\n    for component in components:\n        try:\n            attribute = next(child for child in attribute.iterAttributes()\n                             if child.name.rsplit('.', 1)[-1] == component)\n        except StopIteration:\n            raise NoObject('{}.{}'.format(attribute.name, component))\n\n    return attribute\n\n\ndef findMachines(fqpn):\n    \"\"\"\n    Recursively yield L{MethodicalMachine}s and their FQPNs in and\n    under the a Python object specified by an FQPN.\n\n    The discovery heuristic considers L{MethodicalMachine} instances\n    that are module-level attributes or class-level attributes\n    accessible from module scope.  Machines inside nested classes will\n    be discovered, but those returned from functions or methods will not be.\n\n    @type within: an FQPN\n    @param within: Where to start the search.\n\n    @return: a generator which yields FQPN, L{MethodicalMachine} pairs.\n    \"\"\"\n    return findMachinesViaWrapper(wrapFQPN(fqpn))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/automat/_introspection.py",
    "content": "\"\"\"\nPython introspection helpers.\n\"\"\"\n\nfrom types import CodeType as code, FunctionType as function\n\n\ndef copycode(template, changes):\n    names = [\n        \"argcount\", \"nlocals\", \"stacksize\", \"flags\", \"code\", \"consts\",\n        \"names\", \"varnames\", \"filename\", \"name\", \"firstlineno\", \"lnotab\",\n        \"freevars\", \"cellvars\"\n    ]\n    if hasattr(code, \"co_kwonlyargcount\"):\n        names.insert(1, \"kwonlyargcount\")\n    if hasattr(code, \"co_posonlyargcount\"):\n        # PEP 570 added \"positional only arguments\"\n        names.insert(1, \"posonlyargcount\")\n    values = [\n        changes.get(name, getattr(template, \"co_\" + name))\n        for name in names\n    ]\n    return code(*values)\n\n\n\ndef copyfunction(template, funcchanges, codechanges):\n    names = [\n        \"globals\", \"name\", \"defaults\", \"closure\",\n    ]\n    values = [\n        funcchanges.get(name, getattr(template, \"__\" + name + \"__\"))\n        for name in names\n    ]\n    return function(copycode(template.__code__, codechanges), *values)\n\n\ndef preserveName(f):\n    \"\"\"\n    Preserve the name of the given function on the decorated function.\n    \"\"\"\n    def decorator(decorated):\n        return copyfunction(decorated,\n                            dict(name=f.__name__), dict(name=f.__name__))\n    return decorator\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/automat/_methodical.py",
    "content": "# -*- test-case-name: automat._test.test_methodical -*-\n\nimport collections\nfrom functools import wraps\nfrom itertools import count\n\ntry:\n    # Python 3\n    from inspect import getfullargspec as getArgsSpec\nexcept ImportError:\n    # Python 2\n    from inspect import getargspec as getArgsSpec\n\nimport attr\nimport six\n\nfrom ._core import Transitioner, Automaton\nfrom ._introspection import preserveName\n\n\nArgSpec = collections.namedtuple('ArgSpec', ['args', 'varargs', 'varkw',\n                                             'defaults', 'kwonlyargs',\n                                             'kwonlydefaults', 'annotations'])\n\n\ndef _getArgSpec(func):\n    \"\"\"\n    Normalize inspect.ArgSpec across python versions\n    and convert mutable attributes to immutable types.\n\n    :param Callable func: A function.\n    :return: The function's ArgSpec.\n    :rtype: ArgSpec\n    \"\"\"\n    spec = getArgsSpec(func)\n    return ArgSpec(\n        args=tuple(spec.args),\n        varargs=spec.varargs,\n        varkw=spec.varkw if six.PY3 else spec.keywords,\n        defaults=spec.defaults if spec.defaults else (),\n        kwonlyargs=tuple(spec.kwonlyargs) if six.PY3 else (),\n        kwonlydefaults=(\n            tuple(spec.kwonlydefaults.items())\n            if spec.kwonlydefaults else ()\n        ) if six.PY3 else (),\n        annotations=tuple(spec.annotations.items()) if six.PY3 else (),\n    )\n\n\ndef _getArgNames(spec):\n    \"\"\"\n    Get the name of all arguments defined in a function signature.\n\n    The name of * and ** arguments is normalized to \"*args\" and \"**kwargs\".\n\n    :param ArgSpec spec: A function to interrogate for a signature.\n    :return: The set of all argument names in `func`s signature.\n    :rtype: Set[str]\n    \"\"\"\n    return set(\n        spec.args\n        + spec.kwonlyargs\n        + (('*args',) if spec.varargs else ())\n        + (('**kwargs',) if spec.varkw else ())\n        + spec.annotations\n    )\n\n\ndef _keywords_only(f):\n    \"\"\"\n    Decorate a function so all its arguments must be passed by keyword.\n\n    A useful utility for decorators that take arguments so that they don't\n    accidentally get passed the thing they're decorating as their first\n    argument.\n\n    Only works for methods right now.\n    \"\"\"\n    @wraps(f)\n    def g(self, **kw):\n        return f(self, **kw)\n    return g\n\n\n@attr.s(frozen=True)\nclass MethodicalState(object):\n    \"\"\"\n    A state for a L{MethodicalMachine}.\n    \"\"\"\n    machine = attr.ib(repr=False)\n    method = attr.ib()\n    serialized = attr.ib(repr=False)\n\n    def upon(self, input, enter, outputs, collector=list):\n        \"\"\"\n        Declare a state transition within the :class:`automat.MethodicalMachine`\n        associated with this :class:`automat.MethodicalState`:\n        upon the receipt of the `input`, enter the `state`,\n        emitting each output in `outputs`.\n\n        :param MethodicalInput input: The input triggering a state transition.\n        :param MethodicalState enter: The resulting state.\n        :param Iterable[MethodicalOutput] outputs: The outputs to be triggered\n            as a result of the declared state transition.\n        :param Callable collector: The function to be used when collecting\n            output return values.\n\n        :raises TypeError: if any of the `outputs` signatures do not match\n            the `inputs` signature.\n        :raises ValueError: if the state transition from `self` via `input`\n            has already been defined.\n        \"\"\"\n        inputArgs = _getArgNames(input.argSpec)\n        for output in outputs:\n            outputArgs = _getArgNames(output.argSpec)\n            if not outputArgs.issubset(inputArgs):\n                raise TypeError(\n                    \"method {input} signature {inputSignature} \"\n                    \"does not match output {output} \"\n                    \"signature {outputSignature}\".format(\n                        input=input.method.__name__,\n                        output=output.method.__name__,\n                        inputSignature=getArgsSpec(input.method),\n                        outputSignature=getArgsSpec(output.method),\n                ))\n        self.machine._oneTransition(self, input, enter, outputs, collector)\n\n    def _name(self):\n        return self.method.__name__\n\n\ndef _transitionerFromInstance(oself, symbol, automaton):\n    \"\"\"\n    Get a L{Transitioner}\n    \"\"\"\n    transitioner = getattr(oself, symbol, None)\n    if transitioner is None:\n        transitioner = Transitioner(\n            automaton,\n            automaton.initialState,\n        )\n        setattr(oself, symbol, transitioner)\n    return transitioner\n\n\ndef _empty():\n    pass\n\ndef _docstring():\n    \"\"\"docstring\"\"\"\n\ndef assertNoCode(inst, attribute, f):\n    # The function body must be empty, i.e. \"pass\" or \"return None\", which\n    # both yield the same bytecode: LOAD_CONST (None), RETURN_VALUE. We also\n    # accept functions with only a docstring, which yields slightly different\n    # bytecode, because the \"None\" is put in a different constant slot.\n\n    # Unfortunately, this does not catch function bodies that return a\n    # constant value, e.g. \"return 1\", because their code is identical to a\n    # \"return None\". They differ in the contents of their constant table, but\n    # checking that would require us to parse the bytecode, find the index\n    # being returned, then making sure the table has a None at that index.\n\n    if f.__code__.co_code not in (_empty.__code__.co_code,\n                                  _docstring.__code__.co_code):\n        raise ValueError(\"function body must be empty\")\n\n\ndef _filterArgs(args, kwargs, inputSpec, outputSpec):\n    \"\"\"\n    Filter out arguments that were passed to input that output won't accept.\n\n    :param tuple args: The *args that input received.\n    :param dict kwargs: The **kwargs that input received.\n    :param ArgSpec inputSpec: The input's arg spec.\n    :param ArgSpec outputSpec: The output's arg spec.\n    :return: The args and kwargs that output will accept.\n    :rtype: Tuple[tuple, dict]\n    \"\"\"\n    named_args = tuple(zip(inputSpec.args[1:], args))\n    if outputSpec.varargs:\n        # Only return all args if the output accepts *args.\n        return_args = args\n    else:\n        # Filter out arguments that don't appear\n        # in the output's method signature.\n        return_args = [v for n, v in named_args if n in outputSpec.args]\n\n    # Get any of input's default arguments that were not passed.\n    passed_arg_names = tuple(kwargs)\n    for name, value in named_args:\n        passed_arg_names += (name, value)\n    defaults = zip(inputSpec.args[::-1], inputSpec.defaults[::-1])\n    full_kwargs = {n: v for n, v in defaults if n not in passed_arg_names}\n    full_kwargs.update(kwargs)\n\n    if outputSpec.varkw:\n        # Only pass all kwargs if the output method accepts **kwargs.\n        return_kwargs = full_kwargs\n    else:\n        # Filter out names that the output method does not accept.\n        all_accepted_names = outputSpec.args[1:] + outputSpec.kwonlyargs\n        return_kwargs = {n: v for n, v in full_kwargs.items()\n                         if n in all_accepted_names}\n\n    return return_args, return_kwargs\n\n\n@attr.s(cmp=False, hash=False)\nclass MethodicalInput(object):\n    \"\"\"\n    An input for a L{MethodicalMachine}.\n    \"\"\"\n    automaton = attr.ib(repr=False)\n    method = attr.ib(validator=assertNoCode)\n    symbol = attr.ib(repr=False)\n    collectors = attr.ib(default=attr.Factory(dict), repr=False)\n    argSpec = attr.ib(init=False, repr=False)\n\n    @argSpec.default\n    def _buildArgSpec(self):\n        return _getArgSpec(self.method)\n\n    def __get__(self, oself, type=None):\n        \"\"\"\n        Return a function that takes no arguments and returns values returned\n        by output functions produced by the given L{MethodicalInput} in\n        C{oself}'s current state.\n        \"\"\"\n        transitioner = _transitionerFromInstance(oself, self.symbol,\n                                                 self.automaton)\n        @preserveName(self.method)\n        @wraps(self.method)\n        def doInput(*args, **kwargs):\n            self.method(oself, *args, **kwargs)\n            previousState = transitioner._state\n            (outputs, outTracer) = transitioner.transition(self)\n            collector = self.collectors[previousState]\n            values = []\n            for output in outputs:\n                if outTracer:\n                    outTracer(output._name())\n                a, k = _filterArgs(args, kwargs, self.argSpec, output.argSpec)\n                value = output(oself, *a, **k)\n                values.append(value)\n            return collector(values)\n        return doInput\n\n    def _name(self):\n        return self.method.__name__\n\n\n@attr.s(frozen=True)\nclass MethodicalOutput(object):\n    \"\"\"\n    An output for a L{MethodicalMachine}.\n    \"\"\"\n    machine = attr.ib(repr=False)\n    method = attr.ib()\n    argSpec = attr.ib(init=False, repr=False)\n\n    @argSpec.default\n    def _buildArgSpec(self):\n        return _getArgSpec(self.method)\n\n    def __get__(self, oself, type=None):\n        \"\"\"\n        Outputs are private, so raise an exception when we attempt to get one.\n        \"\"\"\n        raise AttributeError(\n            \"{cls}.{method} is a state-machine output method; \"\n            \"to produce this output, call an input method instead.\".format(\n                cls=type.__name__,\n                method=self.method.__name__\n            )\n        )\n\n\n    def __call__(self, oself, *args, **kwargs):\n        \"\"\"\n        Call the underlying method.\n        \"\"\"\n        return self.method(oself, *args, **kwargs)\n\n    def _name(self):\n        return self.method.__name__\n\n@attr.s(cmp=False, hash=False)\nclass MethodicalTracer(object):\n    automaton = attr.ib(repr=False)\n    symbol = attr.ib(repr=False)\n\n\n    def __get__(self, oself, type=None):\n        transitioner = _transitionerFromInstance(oself, self.symbol,\n                                                 self.automaton)\n        def setTrace(tracer):\n            transitioner.setTrace(tracer)\n        return setTrace\n\n\n\ncounter = count()\ndef gensym():\n    \"\"\"\n    Create a unique Python identifier.\n    \"\"\"\n    return \"_symbol_\" + str(next(counter))\n\n\n\nclass MethodicalMachine(object):\n    \"\"\"\n    A :class:`MethodicalMachine` is an interface to an `Automaton`\n    that uses methods on a class.\n    \"\"\"\n\n    def __init__(self):\n        self._automaton = Automaton()\n        self._reducers = {}\n        self._symbol = gensym()\n\n\n    def __get__(self, oself, type=None):\n        \"\"\"\n        L{MethodicalMachine} is an implementation detail for setting up\n        class-level state; applications should never need to access it on an\n        instance.\n        \"\"\"\n        if oself is not None:\n            raise AttributeError(\n                \"MethodicalMachine is an implementation detail.\")\n        return self\n\n\n    @_keywords_only\n    def state(self, initial=False, terminal=False,\n              serialized=None):\n        \"\"\"\n        Declare a state, possibly an initial state or a terminal state.\n\n        This is a decorator for methods, but it will modify the method so as\n        not to be callable any more.\n\n        :param bool initial: is this state the initial state?\n            Only one state on this :class:`automat.MethodicalMachine`\n            may be an initial state; more than one is an error.\n\n        :param bool terminal: Is this state a terminal state?\n            i.e. a state that the machine can end up in?\n            (This is purely informational at this point.)\n\n        :param Hashable serialized: a serializable value\n            to be used to represent this state to external systems.\n            This value should be hashable;\n            :py:func:`unicode` is a good type to use.\n        \"\"\"\n        def decorator(stateMethod):\n            state = MethodicalState(machine=self,\n                                    method=stateMethod,\n                                    serialized=serialized)\n            if initial:\n                self._automaton.initialState = state\n            return state\n        return decorator\n\n\n    @_keywords_only\n    def input(self):\n        \"\"\"\n        Declare an input.\n\n        This is a decorator for methods.\n        \"\"\"\n        def decorator(inputMethod):\n            return MethodicalInput(automaton=self._automaton,\n                                   method=inputMethod,\n                                   symbol=self._symbol)\n        return decorator\n\n\n    @_keywords_only\n    def output(self):\n        \"\"\"\n        Declare an output.\n\n        This is a decorator for methods.\n\n        This method will be called when the state machine transitions to this\n        state as specified in the decorated `output` method.\n        \"\"\"\n        def decorator(outputMethod):\n            return MethodicalOutput(machine=self, method=outputMethod)\n        return decorator\n\n\n    def _oneTransition(self, startState, inputToken, endState, outputTokens,\n                       collector):\n        \"\"\"\n        See L{MethodicalState.upon}.\n        \"\"\"\n        # FIXME: tests for all of this (some of it is wrong)\n        # if not isinstance(startState, MethodicalState):\n        #     raise NotImplementedError(\"start state {} isn't a state\"\n        #                               .format(startState))\n        # if not isinstance(inputToken, MethodicalInput):\n        #     raise NotImplementedError(\"start state {} isn't an input\"\n        #                               .format(inputToken))\n        # if not isinstance(endState, MethodicalState):\n        #     raise NotImplementedError(\"end state {} isn't a state\"\n        #                               .format(startState))\n        # for output in outputTokens:\n        #     if not isinstance(endState, MethodicalState):\n        #         raise NotImplementedError(\"output state {} isn't a state\"\n        #                                   .format(endState))\n        self._automaton.addTransition(startState, inputToken, endState,\n                                      tuple(outputTokens))\n        inputToken.collectors[startState] = collector\n\n\n    @_keywords_only\n    def serializer(self):\n        \"\"\"\n\n        \"\"\"\n        def decorator(decoratee):\n            @wraps(decoratee)\n            def serialize(oself):\n                transitioner = _transitionerFromInstance(oself, self._symbol,\n                                                         self._automaton)\n                return decoratee(oself, transitioner._state.serialized)\n            return serialize\n        return decorator\n\n    @_keywords_only\n    def unserializer(self):\n        \"\"\"\n\n        \"\"\"\n        def decorator(decoratee):\n            @wraps(decoratee)\n            def unserialize(oself, *args, **kwargs):\n                state = decoratee(oself, *args, **kwargs)\n                mapping = {}\n                for eachState in self._automaton.states():\n                    mapping[eachState.serialized] = eachState\n                transitioner = _transitionerFromInstance(\n                    oself, self._symbol, self._automaton)\n                transitioner._state = mapping[state]\n                return None # it's on purpose\n            return unserialize\n        return decorator\n\n    @property\n    def _setTrace(self):\n        return MethodicalTracer(self._automaton, self._symbol)\n\n    def asDigraph(self):\n        \"\"\"\n        Generate a L{graphviz.Digraph} that represents this machine's\n        states and transitions.\n\n        @return: L{graphviz.Digraph} object; for more information, please\n            see the documentation for\n            U{graphviz<https://graphviz.readthedocs.io/>}\n\n        \"\"\"\n        from ._visualize import makeDigraph\n        return makeDigraph(\n            self._automaton,\n            stateAsString=lambda state: state.method.__name__,\n            inputAsString=lambda input: input.method.__name__,\n            outputAsString=lambda output: output.method.__name__,\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/automat/_test/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/automat/_test/test_core.py",
    "content": "\nfrom .._core import Automaton, NoTransition\n\nfrom unittest import TestCase\n\nclass CoreTests(TestCase):\n    \"\"\"\n    Tests for Automat's (currently private, implementation detail) core.\n    \"\"\"\n\n    def test_NoTransition(self):\n        \"\"\"\n        A L{NoTransition} exception describes the state and input symbol\n        that caused it.\n        \"\"\"\n        # NoTransition requires two arguments\n        with self.assertRaises(TypeError):\n            NoTransition()\n\n        state = \"current-state\"\n        symbol = \"transitionless-symbol\"\n        noTransitionException = NoTransition(state=state, symbol=symbol)\n\n        self.assertIs(noTransitionException.symbol, symbol)\n\n        self.assertIn(state, str(noTransitionException))\n        self.assertIn(symbol, str(noTransitionException))\n\n\n    def test_noOutputForInput(self):\n        \"\"\"\n        L{Automaton.outputForInput} raises L{NoTransition} if no\n        transition for that input is defined.\n        \"\"\"\n        a = Automaton()\n        self.assertRaises(NoTransition, a.outputForInput,\n                          \"no-state\", \"no-symbol\")\n\n\n    def test_oneTransition(self):\n        \"\"\"\n        L{Automaton.addTransition} adds its input symbol to\n        L{Automaton.inputAlphabet}, all its outputs to\n        L{Automaton.outputAlphabet}, and causes L{Automaton.outputForInput} to\n        start returning the new state and output symbols.\n        \"\"\"\n        a = Automaton()\n        a.addTransition(\"beginning\", \"begin\", \"ending\", [\"end\"])\n        self.assertEqual(a.inputAlphabet(), {\"begin\"})\n        self.assertEqual(a.outputAlphabet(), {\"end\"})\n        self.assertEqual(a.outputForInput(\"beginning\", \"begin\"),\n                         (\"ending\", [\"end\"]))\n        self.assertEqual(a.states(), {\"beginning\", \"ending\"})\n\n\n    def test_oneTransition_nonIterableOutputs(self):\n        \"\"\"\n        L{Automaton.addTransition} raises a TypeError when given outputs\n        that aren't iterable and doesn't add any transitions.\n        \"\"\"\n        a = Automaton()\n        nonIterableOutputs = 1\n        self.assertRaises(\n            TypeError,\n            a.addTransition,\n            \"fromState\", \"viaSymbol\", \"toState\", nonIterableOutputs)\n        self.assertFalse(a.inputAlphabet())\n        self.assertFalse(a.outputAlphabet())\n        self.assertFalse(a.states())\n        self.assertFalse(a.allTransitions())\n\n\n    def test_initialState(self):\n        \"\"\"\n        L{Automaton.initialState} is a descriptor that sets the initial\n        state if it's not yet set, and raises L{ValueError} if it is.\n\n        \"\"\"\n        a = Automaton()\n        a.initialState = \"a state\"\n        self.assertEqual(a.initialState, \"a state\")\n        with self.assertRaises(ValueError):\n            a.initialState = \"another state\"\n\n\n# FIXME: addTransition for transition that's been added before\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/automat/_test/test_discover.py",
    "content": "import operator\nimport os\nimport shutil\nimport sys\nimport textwrap\nimport tempfile\nfrom unittest import skipIf, TestCase\n\nimport six\n\n\ndef isTwistedInstalled():\n    try:\n        __import__('twisted')\n    except ImportError:\n        return False\n    else:\n        return True\n\n\nclass _WritesPythonModules(TestCase):\n    \"\"\"\n    A helper that enables generating Python module test fixtures.\n    \"\"\"\n\n    def setUp(self):\n        super(_WritesPythonModules, self).setUp()\n\n        from twisted.python.modules import getModule, PythonPath\n        from twisted.python.filepath import FilePath\n\n        self.getModule = getModule\n        self.PythonPath = PythonPath\n        self.FilePath = FilePath\n\n        self.originalSysModules = set(sys.modules.keys())\n        self.savedSysPath = sys.path[:]\n\n        self.pathDir = tempfile.mkdtemp()\n        self.makeImportable(self.pathDir)\n\n    def tearDown(self):\n        super(_WritesPythonModules, self).tearDown()\n\n        sys.path[:] = self.savedSysPath\n        modulesToDelete = six.viewkeys(sys.modules) - self.originalSysModules\n        for module in modulesToDelete:\n            del sys.modules[module]\n\n        shutil.rmtree(self.pathDir)\n\n    def makeImportable(self, path):\n        sys.path.append(path)\n\n    def writeSourceInto(self, source, path, moduleName):\n        directory = self.FilePath(path)\n\n        module = directory.child(moduleName)\n        # FilePath always opens a file in binary mode - but that will\n        # break on Python 3\n        with open(module.path, 'w') as f:\n            f.write(textwrap.dedent(source))\n\n        return self.PythonPath([directory.path])\n\n    def makeModule(self, source, path, moduleName):\n        pythonModuleName, _ = os.path.splitext(moduleName)\n        return self.writeSourceInto(source, path, moduleName)[pythonModuleName]\n\n    def attributesAsDict(self, hasIterAttributes):\n        return {attr.name: attr for attr in hasIterAttributes.iterAttributes()}\n\n    def loadModuleAsDict(self, module):\n        module.load()\n        return self.attributesAsDict(module)\n\n    def makeModuleAsDict(self, source, path, name):\n        return self.loadModuleAsDict(self.makeModule(source, path, name))\n\n\n@skipIf(not isTwistedInstalled(), \"Twisted is not installed.\")\nclass OriginalLocationTests(_WritesPythonModules):\n    \"\"\"\n    Tests that L{isOriginalLocation} detects when a\n    L{PythonAttribute}'s FQPN refers to an object inside the module\n    where it was defined.\n\n    For example: A L{twisted.python.modules.PythonAttribute} with a\n    name of 'foo.bar' that refers to a 'bar' object defined in module\n    'baz' does *not* refer to bar's original location, while a\n    L{PythonAttribute} with a name of 'baz.bar' does.\n\n    \"\"\"\n    def setUp(self):\n        super(OriginalLocationTests, self).setUp()\n        from .._discover import isOriginalLocation\n        self.isOriginalLocation = isOriginalLocation\n\n    def test_failsWithNoModule(self):\n        \"\"\"\n        L{isOriginalLocation} returns False when the attribute refers to an\n        object whose source module cannot be determined.\n        \"\"\"\n        source = \"\"\"\\\n        class Fake(object):\n            pass\n        hasEmptyModule = Fake()\n        hasEmptyModule.__module__ = None\n        \"\"\"\n\n        moduleDict = self.makeModuleAsDict(source,\n                                           self.pathDir,\n                                           'empty_module_attr.py')\n\n        self.assertFalse(self.isOriginalLocation(\n            moduleDict['empty_module_attr.hasEmptyModule']))\n\n    def test_failsWithDifferentModule(self):\n        \"\"\"\n        L{isOriginalLocation} returns False when the attribute refers to\n        an object outside of the module where that object was defined.\n        \"\"\"\n        originalSource = \"\"\"\\\n        class ImportThisClass(object):\n            pass\n        importThisObject = ImportThisClass()\n        importThisNestingObject = ImportThisClass()\n        importThisNestingObject.nestedObject = ImportThisClass()\n        \"\"\"\n\n        importingSource = \"\"\"\\\n        from original import (ImportThisClass,\n                              importThisObject,\n                              importThisNestingObject)\n        \"\"\"\n\n        self.makeModule(originalSource, self.pathDir, 'original.py')\n        importingDict = self.makeModuleAsDict(importingSource,\n                                              self.pathDir,\n                                              'importing.py')\n        self.assertFalse(\n            self.isOriginalLocation(\n                importingDict['importing.ImportThisClass']))\n        self.assertFalse(\n            self.isOriginalLocation(\n                importingDict['importing.importThisObject']))\n\n        nestingObject = importingDict['importing.importThisNestingObject']\n        nestingObjectDict = self.attributesAsDict(nestingObject)\n        nestedObject = nestingObjectDict[\n            'importing.importThisNestingObject.nestedObject']\n\n        self.assertFalse(self.isOriginalLocation(nestedObject))\n\n    def test_succeedsWithSameModule(self):\n        \"\"\"\n        L{isOriginalLocation} returns True when the attribute refers to an\n        object inside the module where that object was defined.\n        \"\"\"\n        mSource = textwrap.dedent(\"\"\"\n        class ThisClassWasDefinedHere(object):\n            pass\n        anObject = ThisClassWasDefinedHere()\n        aNestingObject = ThisClassWasDefinedHere()\n        aNestingObject.nestedObject = ThisClassWasDefinedHere()\n        \"\"\")\n        mDict = self.makeModuleAsDict(mSource, self.pathDir, 'm.py')\n        self.assertTrue(self.isOriginalLocation(\n            mDict['m.ThisClassWasDefinedHere']))\n        self.assertTrue(self.isOriginalLocation(mDict['m.aNestingObject']))\n\n        nestingObject = mDict['m.aNestingObject']\n        nestingObjectDict = self.attributesAsDict(nestingObject)\n        nestedObject = nestingObjectDict['m.aNestingObject.nestedObject']\n\n        self.assertTrue(self.isOriginalLocation(nestedObject))\n\n\n@skipIf(not isTwistedInstalled(), \"Twisted is not installed.\")\nclass FindMachinesViaWrapperTests(_WritesPythonModules):\n    \"\"\"\n    L{findMachinesViaWrapper} recursively yields FQPN,\n    L{MethodicalMachine} pairs in and under a given\n    L{twisted.python.modules.PythonModule} or\n    L{twisted.python.modules.PythonAttribute}.\n    \"\"\"\n    TEST_MODULE_SOURCE = \"\"\"\n    from automat import MethodicalMachine\n\n\n    class PythonClass(object):\n        _classMachine = MethodicalMachine()\n\n        class NestedClass(object):\n            _nestedClassMachine = MethodicalMachine()\n\n        ignoredAttribute = \"I am ignored.\"\n\n        def ignoredMethod(self):\n            \"I am also ignored.\"\n\n    rootLevelMachine = MethodicalMachine()\n    ignoredPythonObject = PythonClass()\n    anotherIgnoredPythonObject = \"I am ignored.\"\n    \"\"\"\n\n    def setUp(self):\n        super(FindMachinesViaWrapperTests, self).setUp()\n        from .._discover import findMachinesViaWrapper\n        self.findMachinesViaWrapper = findMachinesViaWrapper\n\n    def test_yieldsMachine(self):\n        \"\"\"\n        When given a L{twisted.python.modules.PythonAttribute} that refers\n        directly to a L{MethodicalMachine}, L{findMachinesViaWrapper}\n        yields that machine and its FQPN.\n        \"\"\"\n        source = \"\"\"\\\n        from automat import MethodicalMachine\n\n        rootMachine = MethodicalMachine()\n        \"\"\"\n\n        moduleDict = self.makeModuleAsDict(source, self.pathDir, 'root.py')\n        rootMachine = moduleDict['root.rootMachine']\n        self.assertIn(('root.rootMachine', rootMachine.load()),\n                      list(self.findMachinesViaWrapper(rootMachine)))\n\n    def test_yieldsMachineInClass(self):\n        \"\"\"\n        When given a L{twisted.python.modules.PythonAttribute} that refers\n        to a class that contains a L{MethodicalMachine} as a class\n        variable, L{findMachinesViaWrapper} yields that machine and\n        its FQPN.\n        \"\"\"\n        source = \"\"\"\\\n        from automat import MethodicalMachine\n\n        class PythonClass(object):\n            _classMachine = MethodicalMachine()\n        \"\"\"\n        moduleDict = self.makeModuleAsDict(source, self.pathDir, 'clsmod.py')\n        PythonClass = moduleDict['clsmod.PythonClass']\n        self.assertIn(('clsmod.PythonClass._classMachine',\n                       PythonClass.load()._classMachine),\n                      list(self.findMachinesViaWrapper(PythonClass)))\n\n    def test_yieldsMachineInNestedClass(self):\n        \"\"\"\n        When given a L{twisted.python.modules.PythonAttribute} that refers\n        to a nested class that contains a L{MethodicalMachine} as a\n        class variable, L{findMachinesViaWrapper} yields that machine\n        and its FQPN.\n        \"\"\"\n        source = \"\"\"\\\n        from automat import MethodicalMachine\n\n        class PythonClass(object):\n            class NestedClass(object):\n                _classMachine = MethodicalMachine()\n        \"\"\"\n        moduleDict = self.makeModuleAsDict(source,\n                                           self.pathDir,\n                                           'nestedcls.py')\n\n        PythonClass = moduleDict['nestedcls.PythonClass']\n        self.assertIn(('nestedcls.PythonClass.NestedClass._classMachine',\n                       PythonClass.load().NestedClass._classMachine),\n                      list(self.findMachinesViaWrapper(PythonClass)))\n\n    def test_yieldsMachineInModule(self):\n        \"\"\"\n        When given a L{twisted.python.modules.PythonModule} that refers to\n        a module that contains a L{MethodicalMachine},\n        L{findMachinesViaWrapper} yields that machine and its FQPN.\n        \"\"\"\n        source = \"\"\"\\\n        from automat import MethodicalMachine\n\n        rootMachine = MethodicalMachine()\n        \"\"\"\n        module = self.makeModule(source, self.pathDir, 'root.py')\n        rootMachine = self.loadModuleAsDict(module)['root.rootMachine'].load()\n        self.assertIn(('root.rootMachine', rootMachine),\n                      list(self.findMachinesViaWrapper(module)))\n\n    def test_yieldsMachineInClassInModule(self):\n        \"\"\"\n        When given a L{twisted.python.modules.PythonModule} that refers to\n        the original module of a class containing a\n        L{MethodicalMachine}, L{findMachinesViaWrapper} yields that\n        machine and its FQPN.\n        \"\"\"\n        source = \"\"\"\\\n        from automat import MethodicalMachine\n\n        class PythonClass(object):\n            _classMachine = MethodicalMachine()\n        \"\"\"\n        module = self.makeModule(source, self.pathDir, 'clsmod.py')\n        PythonClass = self.loadModuleAsDict(\n            module)['clsmod.PythonClass'].load()\n        self.assertIn(('clsmod.PythonClass._classMachine',\n                       PythonClass._classMachine),\n                      list(self.findMachinesViaWrapper(module)))\n\n    def test_yieldsMachineInNestedClassInModule(self):\n        \"\"\"\n        When given a L{twisted.python.modules.PythonModule} that refers to\n        the original module of a nested class containing a\n        L{MethodicalMachine}, L{findMachinesViaWrapper} yields that\n        machine and its FQPN.\n        \"\"\"\n        source = \"\"\"\\\n        from automat import MethodicalMachine\n\n        class PythonClass(object):\n            class NestedClass(object):\n                _classMachine = MethodicalMachine()\n        \"\"\"\n        module = self.makeModule(source, self.pathDir, 'nestedcls.py')\n        PythonClass = self.loadModuleAsDict(\n            module)['nestedcls.PythonClass'].load()\n\n        self.assertIn(('nestedcls.PythonClass.NestedClass._classMachine',\n                       PythonClass.NestedClass._classMachine),\n                      list(self.findMachinesViaWrapper(module)))\n\n    def test_ignoresImportedClass(self):\n        \"\"\"\n        When given a L{twisted.python.modules.PythonAttribute} that refers\n        to a class imported from another module, any\n        L{MethodicalMachine}s on that class are ignored.\n\n        This behavior ensures that a machine is only discovered on a\n        class when visiting the module where that class was defined.\n        \"\"\"\n        originalSource = \"\"\"\n        from automat import MethodicalMachine\n\n        class PythonClass(object):\n            _classMachine = MethodicalMachine()\n        \"\"\"\n\n        importingSource = \"\"\"\n        from original import PythonClass\n        \"\"\"\n\n        self.makeModule(originalSource, self.pathDir, 'original.py')\n        importingModule = self.makeModule(importingSource,\n                                          self.pathDir,\n                                          'importing.py')\n\n        self.assertFalse(list(self.findMachinesViaWrapper(importingModule)))\n\n    def test_descendsIntoPackages(self):\n        \"\"\"\n        L{findMachinesViaWrapper} descends into packages to discover\n        machines.\n        \"\"\"\n        pythonPath = self.PythonPath([self.pathDir])\n        package = self.FilePath(self.pathDir).child(\"test_package\")\n        package.makedirs()\n        package.child('__init__.py').touch()\n\n        source = \"\"\"\n        from automat import MethodicalMachine\n\n\n        class PythonClass(object):\n            _classMachine = MethodicalMachine()\n\n\n        rootMachine = MethodicalMachine()\n        \"\"\"\n        self.makeModule(source, package.path, 'module.py')\n\n        test_package = pythonPath['test_package']\n        machines = sorted(self.findMachinesViaWrapper(test_package),\n                          key=operator.itemgetter(0))\n\n        moduleDict = self.loadModuleAsDict(test_package['module'])\n        rootMachine = moduleDict['test_package.module.rootMachine'].load()\n        PythonClass = moduleDict['test_package.module.PythonClass'].load()\n\n        expectedMachines = sorted(\n            [('test_package.module.rootMachine',\n              rootMachine),\n             ('test_package.module.PythonClass._classMachine',\n              PythonClass._classMachine)], key=operator.itemgetter(0))\n\n        self.assertEqual(expectedMachines, machines)\n\n    def test_infiniteLoop(self):\n        \"\"\"\n        L{findMachinesViaWrapper} ignores infinite loops.\n\n        Note this test can't fail - it can only run forever!\n        \"\"\"\n        source = \"\"\"\n        class InfiniteLoop(object):\n            pass\n\n        InfiniteLoop.loop = InfiniteLoop\n        \"\"\"\n        module = self.makeModule(source, self.pathDir, 'loop.py')\n        self.assertFalse(list(self.findMachinesViaWrapper(module)))\n\n\n@skipIf(not isTwistedInstalled(), \"Twisted is not installed.\")\nclass WrapFQPNTests(TestCase):\n    \"\"\"\n    Tests that ensure L{wrapFQPN} loads the\n    L{twisted.python.modules.PythonModule} or\n    L{twisted.python.modules.PythonAttribute} for a given FQPN.\n    \"\"\"\n\n    def setUp(self):\n        from twisted.python.modules import PythonModule, PythonAttribute\n        from .._discover import wrapFQPN, InvalidFQPN, NoModule, NoObject\n\n        self.PythonModule = PythonModule\n        self.PythonAttribute = PythonAttribute\n        self.wrapFQPN = wrapFQPN\n        self.InvalidFQPN = InvalidFQPN\n        self.NoModule = NoModule\n        self.NoObject = NoObject\n\n    def assertModuleWrapperRefersTo(self, moduleWrapper, module):\n        \"\"\"\n        Assert that a L{twisted.python.modules.PythonModule} refers to a\n        particular Python module.\n        \"\"\"\n        self.assertIsInstance(moduleWrapper, self.PythonModule)\n        self.assertEqual(moduleWrapper.name, module.__name__)\n        self.assertIs(moduleWrapper.load(), module)\n\n    def assertAttributeWrapperRefersTo(self, attributeWrapper, fqpn, obj):\n        \"\"\"\n        Assert that a L{twisted.python.modules.PythonAttribute} refers to a\n        particular Python object.\n        \"\"\"\n        self.assertIsInstance(attributeWrapper, self.PythonAttribute)\n        self.assertEqual(attributeWrapper.name, fqpn)\n        self.assertIs(attributeWrapper.load(), obj)\n\n    def test_failsWithEmptyFQPN(self):\n        \"\"\"\n        L{wrapFQPN} raises L{InvalidFQPN} when given an empty string.\n        \"\"\"\n        with self.assertRaises(self.InvalidFQPN):\n            self.wrapFQPN('')\n\n    def test_failsWithBadDotting(self):\n        \"\"\"\"\n        L{wrapFQPN} raises L{InvalidFQPN} when given a badly-dotted\n        FQPN.  (e.g., x..y).\n        \"\"\"\n        for bad in ('.fails', 'fails.', 'this..fails'):\n            with self.assertRaises(self.InvalidFQPN):\n                self.wrapFQPN(bad)\n\n    def test_singleModule(self):\n        \"\"\"\n        L{wrapFQPN} returns a L{twisted.python.modules.PythonModule}\n        referring to the single module a dotless FQPN describes.\n        \"\"\"\n        import os\n\n        moduleWrapper = self.wrapFQPN('os')\n\n        self.assertIsInstance(moduleWrapper, self.PythonModule)\n        self.assertIs(moduleWrapper.load(), os)\n\n    def test_failsWithMissingSingleModuleOrPackage(self):\n        \"\"\"\n        L{wrapFQPN} raises L{NoModule} when given a dotless FQPN that does\n        not refer to a module or package.\n        \"\"\"\n        with self.assertRaises(self.NoModule):\n            self.wrapFQPN(\"this is not an acceptable name!\")\n\n    def test_singlePackage(self):\n        \"\"\"\n        L{wrapFQPN} returns a L{twisted.python.modules.PythonModule}\n        referring to the single package a dotless FQPN describes.\n        \"\"\"\n        import xml\n        self.assertModuleWrapperRefersTo(self.wrapFQPN('xml'), xml)\n\n    def test_multiplePackages(self):\n        \"\"\"\n        L{wrapFQPN} returns a L{twisted.python.modules.PythonModule}\n        referring to the deepest package described by dotted FQPN.\n        \"\"\"\n        import xml.etree\n        self.assertModuleWrapperRefersTo(self.wrapFQPN('xml.etree'), xml.etree)\n\n    def test_multiplePackagesFinalModule(self):\n        \"\"\"\n        L{wrapFQPN} returns a L{twisted.python.modules.PythonModule}\n        referring to the deepest module described by dotted FQPN.\n        \"\"\"\n        import xml.etree.ElementTree\n        self.assertModuleWrapperRefersTo(\n            self.wrapFQPN('xml.etree.ElementTree'), xml.etree.ElementTree)\n\n    def test_singleModuleObject(self):\n        \"\"\"\n        L{wrapFQPN} returns a L{twisted.python.modules.PythonAttribute}\n        referring to the deepest object an FQPN names, traversing one module.\n        \"\"\"\n        import os\n        self.assertAttributeWrapperRefersTo(\n            self.wrapFQPN('os.path'), 'os.path', os.path)\n\n    def test_multiplePackagesObject(self):\n        \"\"\"\n        L{wrapFQPN} returns a L{twisted.python.modules.PythonAttribute}\n        referring to the deepest object described by an FQPN,\n        descending through several packages.\n        \"\"\"\n        import xml.etree.ElementTree\n        import automat\n\n        for fqpn, obj in [('xml.etree.ElementTree.fromstring',\n                           xml.etree.ElementTree.fromstring),\n                          ('automat.MethodicalMachine.__doc__',\n                           automat.MethodicalMachine.__doc__)]:\n            self.assertAttributeWrapperRefersTo(\n                self.wrapFQPN(fqpn), fqpn, obj)\n\n    def test_failsWithMultiplePackagesMissingModuleOrPackage(self):\n        \"\"\"\n        L{wrapFQPN} raises L{NoObject} when given an FQPN that contains a\n        missing attribute, module, or package.\n        \"\"\"\n        for bad in ('xml.etree.nope!',\n                    'xml.etree.nope!.but.the.rest.is.believable'):\n            with self.assertRaises(self.NoObject):\n                self.wrapFQPN(bad)\n\n\n@skipIf(not isTwistedInstalled(), \"Twisted is not installed.\")\nclass FindMachinesIntegrationTests(_WritesPythonModules):\n    \"\"\"\n    Integration tests to check that L{findMachines} yields all\n    machines discoverable at or below an FQPN.\n    \"\"\"\n\n    SOURCE = \"\"\"\n    from automat import MethodicalMachine\n\n    class PythonClass(object):\n        _machine = MethodicalMachine()\n        ignored = \"i am ignored\"\n\n    rootLevel = MethodicalMachine()\n\n    ignored = \"i am ignored\"\n    \"\"\"\n\n    def setUp(self):\n        super(FindMachinesIntegrationTests, self).setUp()\n        from .._discover import findMachines\n\n        self.findMachines = findMachines\n\n        packageDir = self.FilePath(self.pathDir).child(\"test_package\")\n        packageDir.makedirs()\n        self.pythonPath = self.PythonPath([self.pathDir])\n        self.writeSourceInto(self.SOURCE, packageDir.path, '__init__.py')\n\n        subPackageDir = packageDir.child('subpackage')\n        subPackageDir.makedirs()\n        subPackageDir.child('__init__.py').touch()\n\n        self.makeModule(self.SOURCE, subPackageDir.path, 'module.py')\n\n        self.packageDict = self.loadModuleAsDict(\n            self.pythonPath['test_package'])\n        self.moduleDict = self.loadModuleAsDict(\n            self.pythonPath['test_package']['subpackage']['module'])\n\n    def test_discoverAll(self):\n        \"\"\"\n        Given a top-level package FQPN, L{findMachines} discovers all\n        L{MethodicalMachine} instances in and below it.\n        \"\"\"\n        machines = sorted(self.findMachines('test_package'),\n                          key=operator.itemgetter(0))\n\n        tpRootLevel = self.packageDict['test_package.rootLevel'].load()\n        tpPythonClass = self.packageDict['test_package.PythonClass'].load()\n\n        mRLAttr = self.moduleDict['test_package.subpackage.module.rootLevel']\n        mRootLevel = mRLAttr.load()\n        mPCAttr = self.moduleDict['test_package.subpackage.module.PythonClass']\n        mPythonClass = mPCAttr.load()\n\n        expectedMachines = sorted(\n            [('test_package.rootLevel', tpRootLevel),\n             ('test_package.PythonClass._machine', tpPythonClass._machine),\n             ('test_package.subpackage.module.rootLevel', mRootLevel),\n             ('test_package.subpackage.module.PythonClass._machine',\n              mPythonClass._machine)],\n            key=operator.itemgetter(0))\n\n        self.assertEqual(expectedMachines, machines)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/automat/_test/test_methodical.py",
    "content": "\n\"\"\"\nTests for the public interface of Automat.\n\"\"\"\n\nfrom functools import reduce\nfrom unittest import TestCase\n\nfrom automat._methodical import ArgSpec, _getArgNames, _getArgSpec, _filterArgs\nfrom .. import MethodicalMachine, NoTransition\nfrom .. import _methodical\n\n\nclass MethodicalTests(TestCase):\n    \"\"\"\n    Tests for L{MethodicalMachine}.\n    \"\"\"\n\n    def test_oneTransition(self):\n        \"\"\"\n        L{MethodicalMachine} provides a way for you to declare a state machine\n        with inputs, outputs, and states as methods.  When you have declared an\n        input, an output, and a state, calling the input method in that state\n        will produce the specified output.\n        \"\"\"\n\n        class Machination(object):\n            machine = MethodicalMachine()\n            @machine.input()\n            def anInput(self):\n                \"an input\"\n\n            @machine.output()\n            def anOutput(self):\n                \"an output\"\n                return \"an-output-value\"\n\n            @machine.output()\n            def anotherOutput(self):\n                \"another output\"\n                return \"another-output-value\"\n\n            @machine.state(initial=True)\n            def anState(self):\n                \"a state\"\n\n            @machine.state()\n            def anotherState(self):\n                \"another state\"\n\n            anState.upon(anInput, enter=anotherState, outputs=[anOutput])\n            anotherState.upon(anInput, enter=anotherState,\n                              outputs=[anotherOutput])\n\n        m = Machination()\n        self.assertEqual(m.anInput(), [\"an-output-value\"])\n        self.assertEqual(m.anInput(), [\"another-output-value\"])\n\n\n    def test_machineItselfIsPrivate(self):\n        \"\"\"\n        L{MethodicalMachine} is an implementation detail.  If you attempt to\n        access it on an instance of your class, you will get an exception.\n        However, since tools may need to access it for the purposes of, for\n        example, visualization, you may access it on the class itself.\n        \"\"\"\n        expectedMachine = MethodicalMachine()\n        class Machination(object):\n            machine = expectedMachine\n        machination = Machination()\n        with self.assertRaises(AttributeError) as cm:\n            machination.machine\n        self.assertIn(\"MethodicalMachine is an implementation detail\",\n                      str(cm.exception))\n        self.assertIs(Machination.machine, expectedMachine)\n\n\n    def test_outputsArePrivate(self):\n        \"\"\"\n        One of the benefits of using a state machine is that your output method\n        implementations don't need to take invalid state transitions into\n        account - the methods simply won't be called.  This property would be\n        broken if client code called output methods directly, so output methods\n        are not directly visible under their names.\n        \"\"\"\n        class Machination(object):\n            machine = MethodicalMachine()\n            counter = 0\n            @machine.input()\n            def anInput(self):\n                \"an input\"\n            @machine.output()\n            def anOutput(self):\n                self.counter += 1\n            @machine.state(initial=True)\n            def state(self):\n                \"a machine state\"\n            state.upon(anInput, enter=state, outputs=[anOutput])\n        mach1 = Machination()\n        mach1.anInput()\n        self.assertEqual(mach1.counter, 1)\n        mach2 = Machination()\n        with self.assertRaises(AttributeError) as cm:\n            mach2.anOutput\n        self.assertEqual(mach2.counter, 0)\n\n        self.assertIn(\n            \"Machination.anOutput is a state-machine output method; to \"\n            \"produce this output, call an input method instead.\",\n            str(cm.exception)\n        )\n\n\n    def test_multipleMachines(self):\n        \"\"\"\n        Two machines may co-exist happily on the same instance; they don't\n        interfere with each other.\n        \"\"\"\n        class MultiMach(object):\n            a = MethodicalMachine()\n            b = MethodicalMachine()\n\n            @a.input()\n            def inputA(self):\n                \"input A\"\n            @b.input()\n            def inputB(self):\n                \"input B\"\n            @a.state(initial=True)\n            def initialA(self):\n                \"initial A\"\n            @b.state(initial=True)\n            def initialB(self):\n                \"initial B\"\n            @a.output()\n            def outputA(self):\n                return \"A\"\n            @b.output()\n            def outputB(self):\n                return \"B\"\n            initialA.upon(inputA, initialA, [outputA])\n            initialB.upon(inputB, initialB, [outputB])\n\n        mm = MultiMach()\n        self.assertEqual(mm.inputA(), [\"A\"])\n        self.assertEqual(mm.inputB(), [\"B\"])\n\n\n    def test_collectOutputs(self):\n        \"\"\"\n        Outputs can be combined with the \"collector\" argument to \"upon\".\n        \"\"\"\n        import operator\n        class Machine(object):\n            m = MethodicalMachine()\n            @m.input()\n            def input(self):\n                \"an input\"\n            @m.output()\n            def outputA(self):\n                return \"A\"\n            @m.output()\n            def outputB(self):\n                return \"B\"\n            @m.state(initial=True)\n            def state(self):\n                \"a state\"\n            state.upon(input, state, [outputA, outputB],\n                       collector=lambda x: reduce(operator.add, x))\n        m = Machine()\n        self.assertEqual(m.input(), \"AB\")\n\n\n    def test_methodName(self):\n        \"\"\"\n        Input methods preserve their declared names.\n        \"\"\"\n        class Mech(object):\n            m = MethodicalMachine()\n            @m.input()\n            def declaredInputName(self):\n                \"an input\"\n            @m.state(initial=True)\n            def aState(self):\n                \"state\"\n        m = Mech()\n        with self.assertRaises(TypeError) as cm:\n            m.declaredInputName(\"too\", \"many\", \"arguments\")\n        self.assertIn(\"declaredInputName\", str(cm.exception))\n\n\n    def test_inputWithArguments(self):\n        \"\"\"\n        If an input takes an argument, it will pass that along to its output.\n        \"\"\"\n        class Mechanism(object):\n            m = MethodicalMachine()\n            @m.input()\n            def input(self, x, y=1):\n                \"an input\"\n            @m.state(initial=True)\n            def state(self):\n                \"a state\"\n            @m.output()\n            def output(self, x, y=1):\n                self._x = x\n                return x + y\n            state.upon(input, state, [output])\n\n        m = Mechanism()\n        self.assertEqual(m.input(3), [4])\n        self.assertEqual(m._x, 3)\n\n\n    def test_outputWithSubsetOfArguments(self):\n        \"\"\"\n        Inputs pass arguments that output will accept.\n        \"\"\"\n        class Mechanism(object):\n            m = MethodicalMachine()\n            @m.input()\n            def input(self, x, y=1):\n                \"an input\"\n            @m.state(initial=True)\n            def state(self):\n                \"a state\"\n            @m.output()\n            def outputX(self, x):\n                self._x = x\n                return x\n            @m.output()\n            def outputY(self, y):\n                self._y = y\n                return y\n            @m.output()\n            def outputNoArgs(self):\n                return None\n            state.upon(input, state, [outputX, outputY, outputNoArgs])\n\n        m = Mechanism()\n\n        # Pass x as positional argument.\n        self.assertEqual(m.input(3), [3, 1, None])\n        self.assertEqual(m._x, 3)\n        self.assertEqual(m._y, 1)\n\n        # Pass x as key word argument.\n        self.assertEqual(m.input(x=4), [4, 1, None])\n        self.assertEqual(m._x, 4)\n        self.assertEqual(m._y, 1)\n\n        # Pass y as positional argument.\n        self.assertEqual(m.input(6, 3), [6, 3, None])\n        self.assertEqual(m._x, 6)\n        self.assertEqual(m._y, 3)\n\n        # Pass y as key word argument.\n        self.assertEqual(m.input(5, y=2), [5, 2, None])\n        self.assertEqual(m._x, 5)\n        self.assertEqual(m._y, 2)\n\n\n    def test_inputFunctionsMustBeEmpty(self):\n        \"\"\"\n        The wrapped input function must have an empty body.\n        \"\"\"\n        # input functions are executed to assert that the signature matches,\n        # but their body must be empty\n\n        _methodical._empty() # chase coverage\n        _methodical._docstring()\n\n        class Mechanism(object):\n            m = MethodicalMachine()\n            with self.assertRaises(ValueError) as cm:\n                @m.input()\n                def input(self):\n                    \"an input\"\n                    list() # pragma: no cover\n            self.assertEqual(str(cm.exception), \"function body must be empty\")\n\n        # all three of these cases should be valid. Functions/methods with\n        # docstrings produce slightly different bytecode than ones without.\n\n        class MechanismWithDocstring(object):\n            m = MethodicalMachine()\n            @m.input()\n            def input(self):\n                \"an input\"\n            @m.state(initial=True)\n            def start(self):\n                \"starting state\"\n            start.upon(input, enter=start, outputs=[])\n        MechanismWithDocstring().input()\n\n        class MechanismWithPass(object):\n            m = MethodicalMachine()\n            @m.input()\n            def input(self):\n                pass\n            @m.state(initial=True)\n            def start(self):\n                \"starting state\"\n            start.upon(input, enter=start, outputs=[])\n        MechanismWithPass().input()\n\n        class MechanismWithDocstringAndPass(object):\n            m = MethodicalMachine()\n            @m.input()\n            def input(self):\n                \"an input\"\n                pass\n            @m.state(initial=True)\n            def start(self):\n                \"starting state\"\n            start.upon(input, enter=start, outputs=[])\n        MechanismWithDocstringAndPass().input()\n\n        class MechanismReturnsNone(object):\n            m = MethodicalMachine()\n            @m.input()\n            def input(self):\n                return None\n            @m.state(initial=True)\n            def start(self):\n                \"starting state\"\n            start.upon(input, enter=start, outputs=[])\n        MechanismReturnsNone().input()\n\n        class MechanismWithDocstringAndReturnsNone(object):\n            m = MethodicalMachine()\n            @m.input()\n            def input(self):\n                \"an input\"\n                return None\n            @m.state(initial=True)\n            def start(self):\n                \"starting state\"\n            start.upon(input, enter=start, outputs=[])\n        MechanismWithDocstringAndReturnsNone().input()\n\n\n    def test_inputOutputMismatch(self):\n        \"\"\"\n        All the argument lists of the outputs for a given input must match; if\n        one does not the call to C{upon} will raise a C{TypeError}.\n        \"\"\"\n        class Mechanism(object):\n            m = MethodicalMachine()\n            @m.input()\n            def nameOfInput(self, a):\n                \"an input\"\n            @m.output()\n            def outputThatMatches(self, a):\n                \"an output that matches\"\n            @m.output()\n            def outputThatDoesntMatch(self, b):\n                \"an output that doesn't match\"\n            @m.state()\n            def state(self):\n                \"a state\"\n            with self.assertRaises(TypeError) as cm:\n                state.upon(nameOfInput, state, [outputThatMatches,\n                                                outputThatDoesntMatch])\n            self.assertIn(\"nameOfInput\", str(cm.exception))\n            self.assertIn(\"outputThatDoesntMatch\", str(cm.exception))\n\n\n    def test_getArgNames(self):\n        \"\"\"\n        Type annotations should be included in the set of\n        \"\"\"\n        spec = ArgSpec(\n            args=('a', 'b'),\n            varargs=None,\n            varkw=None,\n            defaults=None,\n            kwonlyargs=(),\n            kwonlydefaults=None,\n            annotations=(('a', int), ('b', str)),\n        )\n        self.assertEqual(\n            _getArgNames(spec),\n            {'a', 'b', ('a', int), ('b', str)},\n        )\n\n\n    def test_filterArgs(self):\n        \"\"\"\n        filterArgs() should not filter the `args` parameter\n        if outputSpec accepts `*args`.\n        \"\"\"\n        inputSpec = _getArgSpec(lambda *args, **kwargs: None)\n        outputSpec = _getArgSpec(lambda *args, **kwargs: None)\n        argsIn = ()\n        argsOut, _ = _filterArgs(argsIn, {}, inputSpec, outputSpec)\n        self.assertIs(argsIn, argsOut)\n\n\n    def test_multipleInitialStatesFailure(self):\n        \"\"\"\n        A L{MethodicalMachine} can only have one initial state.\n        \"\"\"\n\n        class WillFail(object):\n            m = MethodicalMachine()\n\n            @m.state(initial=True)\n            def firstInitialState(self):\n                \"The first initial state -- this is OK.\"\n\n            with self.assertRaises(ValueError):\n                @m.state(initial=True)\n                def secondInitialState(self):\n                    \"The second initial state -- results in a ValueError.\"\n\n\n    def test_multipleTransitionsFailure(self):\n        \"\"\"\n        A L{MethodicalMachine} can only have one transition per start/event\n        pair.\n        \"\"\"\n\n        class WillFail(object):\n            m = MethodicalMachine()\n\n            @m.state(initial=True)\n            def start(self):\n                \"We start here.\"\n            @m.state()\n            def end(self):\n                \"Rainbows end.\"\n\n            @m.input()\n            def event(self):\n                \"An event.\"\n            start.upon(event, enter=end, outputs=[])\n            with self.assertRaises(ValueError):\n                start.upon(event, enter=end, outputs=[])\n\n\n    def test_badTransitionForCurrentState(self):\n        \"\"\"\n        Calling any input method that lacks a transition for the machine's\n        current state raises an informative L{NoTransition}.\n        \"\"\"\n\n        class OnlyOnePath(object):\n            m = MethodicalMachine()\n            @m.state(initial=True)\n            def start(self):\n                \"Start state.\"\n            @m.state()\n            def end(self):\n                \"End state.\"\n            @m.input()\n            def advance(self):\n                \"Move from start to end.\"\n            @m.input()\n            def deadEnd(self):\n                \"A transition from nowhere to nowhere.\"\n            start.upon(advance, end, [])\n\n        machine = OnlyOnePath()\n        with self.assertRaises(NoTransition) as cm:\n            machine.deadEnd()\n        self.assertIn(\"deadEnd\", str(cm.exception))\n        self.assertIn(\"start\", str(cm.exception))\n        machine.advance()\n        with self.assertRaises(NoTransition) as cm:\n            machine.deadEnd()\n        self.assertIn(\"deadEnd\", str(cm.exception))\n        self.assertIn(\"end\", str(cm.exception))\n\n\n    def test_saveState(self):\n        \"\"\"\n        L{MethodicalMachine.serializer} is a decorator that modifies its\n        decoratee's signature to take a \"state\" object as its first argument,\n        which is the \"serialized\" argument to the L{MethodicalMachine.state}\n        decorator.\n        \"\"\"\n\n        class Mechanism(object):\n            m = MethodicalMachine()\n            def __init__(self):\n                self.value = 1\n            @m.state(serialized=\"first-state\", initial=True)\n            def first(self):\n                \"First state.\"\n            @m.state(serialized=\"second-state\")\n            def second(self):\n                \"Second state.\"\n            @m.serializer()\n            def save(self, state):\n                return {\n                    'machine-state': state,\n                    'some-value': self.value,\n                }\n\n        self.assertEqual(\n            Mechanism().save(),\n            {\n                \"machine-state\": \"first-state\",\n                \"some-value\": 1,\n            }\n        )\n\n\n    def test_restoreState(self):\n        \"\"\"\n        L{MethodicalMachine.unserializer} decorates a function that becomes a\n        machine-state unserializer; its return value is mapped to the\n        C{serialized} parameter to C{state}, and the L{MethodicalMachine}\n        associated with that instance's state is updated to that state.\n        \"\"\"\n\n        class Mechanism(object):\n            m = MethodicalMachine()\n            def __init__(self):\n                self.value = 1\n                self.ranOutput = False\n            @m.state(serialized=\"first-state\", initial=True)\n            def first(self):\n                \"First state.\"\n            @m.state(serialized=\"second-state\")\n            def second(self):\n                \"Second state.\"\n            @m.input()\n            def input(self):\n                \"an input\"\n            @m.output()\n            def output(self):\n                self.value = 2\n                self.ranOutput = True\n                return 1\n            @m.output()\n            def output2(self):\n                return 2\n            first.upon(input, second, [output],\n                       collector=lambda x: list(x)[0])\n            second.upon(input, second, [output2],\n                        collector=lambda x: list(x)[0])\n            @m.serializer()\n            def save(self, state):\n                return {\n                    'machine-state': state,\n                    'some-value': self.value,\n                }\n\n            @m.unserializer()\n            def _restore(self, blob):\n                self.value = blob['some-value']\n                return blob['machine-state']\n\n            @classmethod\n            def fromBlob(cls, blob):\n                self = cls()\n                self._restore(blob)\n                return self\n\n        m1 = Mechanism()\n        m1.input()\n        blob = m1.save()\n        m2 = Mechanism.fromBlob(blob)\n        self.assertEqual(m2.ranOutput, False)\n        self.assertEqual(m2.input(), 2)\n        self.assertEqual(\n            m2.save(),\n            {\n                'machine-state': 'second-state',\n                'some-value': 2,\n            }\n        )\n\n\n\n# FIXME: error for wrong types on any call to _oneTransition\n# FIXME: better public API for .upon; maybe a context manager?\n# FIXME: when transitions are defined, validate that we can always get to\n# terminal? do we care about this?\n# FIXME: implementation (and use-case/example) for passing args from in to out\n\n# FIXME: possibly these need some kind of support from core\n# FIXME: wildcard state (in all states, when input X, emit Y and go to Z)\n# FIXME: wildcard input (in state X, when any input, emit Y and go to Z)\n# FIXME: combined wildcards (in any state for any input, emit Y go to Z)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/automat/_test/test_trace.py",
    "content": "from unittest import TestCase\nfrom .._methodical import MethodicalMachine\n\nclass SampleObject(object):\n    mm = MethodicalMachine()\n\n    @mm.state(initial=True)\n    def begin(self):\n        \"initial state\"\n    @mm.state()\n    def middle(self):\n        \"middle state\"\n    @mm.state()\n    def end(self):\n        \"end state\"\n\n    @mm.input()\n    def go1(self):\n        \"sample input\"\n    @mm.input()\n    def go2(self):\n        \"sample input\"\n    @mm.input()\n    def back(self):\n        \"sample input\"\n\n    @mm.output()\n    def out(self):\n        \"sample output\"\n\n    setTrace = mm._setTrace\n\n    begin.upon(go1, middle, [out])\n    middle.upon(go2, end, [out])\n    end.upon(back, middle, [])\n    middle.upon(back, begin, [])\n\nclass TraceTests(TestCase):\n    def test_only_inputs(self):\n        traces = []\n        def tracer(old_state, input, new_state):\n            traces.append((old_state, input, new_state))\n            return None # \"I only care about inputs, not outputs\"\n        s = SampleObject()\n        s.setTrace(tracer)\n\n        s.go1()\n        self.assertEqual(traces, [(\"begin\", \"go1\", \"middle\"),\n                                  ])\n\n        s.go2()\n        self.assertEqual(traces, [(\"begin\", \"go1\", \"middle\"),\n                                  (\"middle\", \"go2\", \"end\"),\n                                  ])\n        s.setTrace(None)\n        s.back()\n        self.assertEqual(traces, [(\"begin\", \"go1\", \"middle\"),\n                                  (\"middle\", \"go2\", \"end\"),\n                                  ])\n        s.go2()\n        self.assertEqual(traces, [(\"begin\", \"go1\", \"middle\"),\n                                  (\"middle\", \"go2\", \"end\"),\n                                  ])\n\n    def test_inputs_and_outputs(self):\n        traces = []\n        def tracer(old_state, input, new_state):\n            traces.append((old_state, input, new_state, None))\n            def trace_outputs(output):\n                traces.append((old_state, input, new_state, output))\n            return trace_outputs # \"I care about outputs too\"\n        s = SampleObject()\n        s.setTrace(tracer)\n\n        s.go1()\n        self.assertEqual(traces, [(\"begin\", \"go1\", \"middle\", None),\n                                  (\"begin\", \"go1\", \"middle\", \"out\"),\n                                  ])\n\n        s.go2()\n        self.assertEqual(traces, [(\"begin\", \"go1\", \"middle\", None),\n                                  (\"begin\", \"go1\", \"middle\", \"out\"),\n                                  (\"middle\", \"go2\", \"end\", None),\n                                  (\"middle\", \"go2\", \"end\", \"out\"),\n                                  ])\n        s.setTrace(None)\n        s.back()\n        self.assertEqual(traces, [(\"begin\", \"go1\", \"middle\", None),\n                                  (\"begin\", \"go1\", \"middle\", \"out\"),\n                                  (\"middle\", \"go2\", \"end\", None),\n                                  (\"middle\", \"go2\", \"end\", \"out\"),\n                                  ])\n        s.go2()\n        self.assertEqual(traces, [(\"begin\", \"go1\", \"middle\", None),\n                                  (\"begin\", \"go1\", \"middle\", \"out\"),\n                                  (\"middle\", \"go2\", \"end\", None),\n                                  (\"middle\", \"go2\", \"end\", \"out\"),\n                                  ])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/automat/_test/test_visualize.py",
    "content": "from __future__ import print_function\nimport functools\n\nimport os\nimport subprocess\nfrom unittest import TestCase, skipIf\n\nimport attr\n\nfrom .._methodical import MethodicalMachine\n\nfrom .test_discover import isTwistedInstalled\n\n\ndef isGraphvizModuleInstalled():\n    \"\"\"\n    Is the graphviz Python module installed?\n    \"\"\"\n    try:\n        __import__(\"graphviz\")\n    except ImportError:\n        return False\n    else:\n        return True\n\n\ndef isGraphvizInstalled():\n    \"\"\"\n    Are the graphviz tools installed?\n    \"\"\"\n    r, w = os.pipe()\n    os.close(w)\n    try:\n        return not subprocess.call(\"dot\", stdin=r, shell=True)\n    finally:\n        os.close(r)\n\n\n\ndef sampleMachine():\n    \"\"\"\n    Create a sample L{MethodicalMachine} with some sample states.\n    \"\"\"\n    mm = MethodicalMachine()\n    class SampleObject(object):\n        @mm.state(initial=True)\n        def begin(self):\n            \"initial state\"\n        @mm.state()\n        def end(self):\n            \"end state\"\n        @mm.input()\n        def go(self):\n            \"sample input\"\n        @mm.output()\n        def out(self):\n            \"sample output\"\n        begin.upon(go, end, [out])\n    so = SampleObject()\n    so.go()\n    return mm\n\n\n@skipIf(not isGraphvizModuleInstalled(), \"Graphviz module is not installed.\")\nclass ElementMakerTests(TestCase):\n    \"\"\"\n    L{elementMaker} generates HTML representing the specified element.\n    \"\"\"\n\n    def setUp(self):\n        from .._visualize import elementMaker\n        self.elementMaker = elementMaker\n\n    def test_sortsAttrs(self):\n        \"\"\"\n        L{elementMaker} orders HTML attributes lexicographically.\n        \"\"\"\n        expected = r'<div a=\"1\" b=\"2\" c=\"3\"></div>'\n        self.assertEqual(expected,\n                         self.elementMaker(\"div\",\n                                           b='2',\n                                           a='1',\n                                           c='3'))\n\n    def test_quotesAttrs(self):\n        \"\"\"\n        L{elementMaker} quotes HTML attributes according to DOT's quoting rule.\n\n        See U{http://www.graphviz.org/doc/info/lang.html}, footnote 1.\n        \"\"\"\n        expected = r'<div a=\"1\" b=\"a \\\" quote\" c=\"a string\"></div>'\n        self.assertEqual(expected,\n                         self.elementMaker(\"div\",\n                                           b='a \" quote',\n                                           a=1,\n                                           c=\"a string\"))\n\n    def test_noAttrs(self):\n        \"\"\"\n        L{elementMaker} should render an element with no attributes.\n        \"\"\"\n        expected = r'<div ></div>'\n        self.assertEqual(expected, self.elementMaker(\"div\"))\n\n\n@attr.s\nclass HTMLElement(object):\n    \"\"\"Holds an HTML element, as created by elementMaker.\"\"\"\n    name = attr.ib()\n    children = attr.ib()\n    attributes = attr.ib()\n\n\ndef findElements(element, predicate):\n    \"\"\"\n    Recursively collect all elements in an L{HTMLElement} tree that\n    match the optional predicate.\n    \"\"\"\n    if predicate(element):\n        return [element]\n    elif isLeaf(element):\n        return []\n\n    return [result\n            for child in element.children\n            for result in findElements(child, predicate)]\n\n\ndef isLeaf(element):\n    \"\"\"\n    This HTML element is actually leaf node.\n    \"\"\"\n    return not isinstance(element, HTMLElement)\n\n\n@skipIf(not isGraphvizModuleInstalled(), \"Graphviz module is not installed.\")\nclass TableMakerTests(TestCase):\n    \"\"\"\n    Tests that ensure L{tableMaker} generates HTML tables usable as\n    labels in DOT graphs.\n\n    For more information, read the \"HTML-Like Labels\" section of\n    U{http://www.graphviz.org/doc/info/shapes.html}.\n    \"\"\"\n\n    def fakeElementMaker(self, name, *children, **attributes):\n        return HTMLElement(name=name, children=children, attributes=attributes)\n\n    def setUp(self):\n        from .._visualize import tableMaker\n\n        self.inputLabel = \"input label\"\n        self.port = \"the port\"\n        self.tableMaker = functools.partial(tableMaker,\n                                            _E=self.fakeElementMaker)\n\n    def test_inputLabelRow(self):\n        \"\"\"\n        The table returned by L{tableMaker} always contains the input\n        symbol label in its first row, and that row contains one cell\n        with a port attribute set to the provided port.\n        \"\"\"\n\n        def hasPort(element):\n            return (not isLeaf(element)\n                    and element.attributes.get(\"port\") == self.port)\n\n        for outputLabels in ([], [\"an output label\"]):\n            table = self.tableMaker(self.inputLabel, outputLabels,\n                                    port=self.port)\n            self.assertGreater(len(table.children), 0)\n            inputLabelRow = table.children[0]\n\n            portCandidates = findElements(table, hasPort)\n\n            self.assertEqual(len(portCandidates), 1)\n            self.assertEqual(portCandidates[0].name, \"td\")\n            self.assertEqual(findElements(inputLabelRow, isLeaf),\n                             [self.inputLabel])\n\n    def test_noOutputLabels(self):\n        \"\"\"\n        L{tableMaker} does not add a colspan attribute to the input\n        label's cell or a second row if there no output labels.\n        \"\"\"\n        table = self.tableMaker(\"input label\", (), port=self.port)\n        self.assertEqual(len(table.children), 1)\n        (inputLabelRow,) = table.children\n        self.assertNotIn(\"colspan\", inputLabelRow.attributes)\n\n    def test_withOutputLabels(self):\n        \"\"\"\n        L{tableMaker} adds a colspan attribute to the input label's cell\n        equal to the number of output labels and a second row that\n        contains the output labels.\n        \"\"\"\n        table = self.tableMaker(self.inputLabel, (\"output label 1\",\n                                                  \"output label 2\"),\n                                port=self.port)\n\n        self.assertEqual(len(table.children), 2)\n        inputRow, outputRow = table.children\n\n        def hasCorrectColspan(element):\n            return (not isLeaf(element)\n                    and element.name == \"td\"\n                    and element.attributes.get('colspan') == \"2\")\n\n        self.assertEqual(len(findElements(inputRow, hasCorrectColspan)),\n                         1)\n        self.assertEqual(findElements(outputRow, isLeaf), [\"output label 1\",\n                                                           \"output label 2\"])\n\n\n@skipIf(not isGraphvizModuleInstalled(), \"Graphviz module is not installed.\")\n@skipIf(not isGraphvizInstalled(), \"Graphviz tools are not installed.\")\nclass IntegrationTests(TestCase):\n    \"\"\"\n    Tests which make sure Graphviz can understand the output produced by\n    Automat.\n    \"\"\"\n\n    def test_validGraphviz(self):\n        \"\"\"\n        L{graphviz} emits valid graphviz data.\n        \"\"\"\n        p = subprocess.Popen(\"dot\", stdin=subprocess.PIPE,\n                             stdout=subprocess.PIPE)\n        out, err = p.communicate(\"\".join(sampleMachine().asDigraph())\n                                 .encode(\"utf-8\"))\n        self.assertEqual(p.returncode, 0)\n\n\n@skipIf(not isGraphvizModuleInstalled(), \"Graphviz module is not installed.\")\nclass SpotChecks(TestCase):\n    \"\"\"\n    Tests to make sure that the output contains salient features of the machine\n    being generated.\n    \"\"\"\n\n    def test_containsMachineFeatures(self):\n        \"\"\"\n        The output of L{graphviz} should contain the names of the states,\n        inputs, outputs in the state machine.\n        \"\"\"\n        gvout = \"\".join(sampleMachine().asDigraph())\n        self.assertIn(\"begin\", gvout)\n        self.assertIn(\"end\", gvout)\n        self.assertIn(\"go\", gvout)\n        self.assertIn(\"out\", gvout)\n\n\nclass RecordsDigraphActions(object):\n    \"\"\"\n    Records calls made to L{FakeDigraph}.\n    \"\"\"\n\n    def __init__(self):\n        self.reset()\n\n    def reset(self):\n        self.renderCalls = []\n        self.saveCalls = []\n\n\nclass FakeDigraph(object):\n    \"\"\"\n    A fake L{graphviz.Digraph}.  Instantiate it with a\n    L{RecordsDigraphActions}.\n    \"\"\"\n\n    def __init__(self, recorder):\n        self._recorder = recorder\n\n    def render(self, **kwargs):\n        self._recorder.renderCalls.append(kwargs)\n\n    def save(self, **kwargs):\n        self._recorder.saveCalls.append(kwargs)\n\n\nclass FakeMethodicalMachine(object):\n    \"\"\"\n    A fake L{MethodicalMachine}.  Instantiate it with a L{FakeDigraph}\n    \"\"\"\n\n    def __init__(self, digraph):\n        self._digraph = digraph\n\n    def asDigraph(self):\n        return self._digraph\n\n\n@skipIf(not isGraphvizModuleInstalled(), \"Graphviz module is not installed.\")\n@skipIf(not isGraphvizInstalled(), \"Graphviz tools are not installed.\")\n@skipIf(not isTwistedInstalled(), \"Twisted is not installed.\")\nclass VisualizeToolTests(TestCase):\n\n    def setUp(self):\n        self.digraphRecorder = RecordsDigraphActions()\n        self.fakeDigraph = FakeDigraph(self.digraphRecorder)\n\n        self.fakeProgname = 'tool-test'\n        self.fakeSysPath = ['ignored']\n        self.collectedOutput = []\n        self.fakeFQPN = 'fake.fqpn'\n\n    def collectPrints(self, *args):\n        self.collectedOutput.append(' '.join(args))\n\n    def fakeFindMachines(self, fqpn):\n        yield fqpn, FakeMethodicalMachine(self.fakeDigraph)\n\n    def tool(self,\n             progname=None,\n             argv=None,\n             syspath=None,\n             findMachines=None,\n             print=None):\n        from .._visualize import tool\n        return tool(\n            _progname=progname or self.fakeProgname,\n            _argv=argv or [self.fakeFQPN],\n            _syspath=syspath or self.fakeSysPath,\n            _findMachines=findMachines or self.fakeFindMachines,\n            _print=print or self.collectPrints)\n\n    def test_checksCurrentDirectory(self):\n        \"\"\"\n        L{tool} adds '' to sys.path to ensure\n        L{automat._discover.findMachines} searches the current\n        directory.\n        \"\"\"\n        self.tool(argv=[self.fakeFQPN])\n        self.assertEqual(self.fakeSysPath[0], '')\n\n    def test_quietHidesOutput(self):\n        \"\"\"\n        Passing -q/--quiet hides all output.\n        \"\"\"\n        self.tool(argv=[self.fakeFQPN, '--quiet'])\n        self.assertFalse(self.collectedOutput)\n        self.tool(argv=[self.fakeFQPN, '-q'])\n        self.assertFalse(self.collectedOutput)\n\n    def test_onlySaveDot(self):\n        \"\"\"\n        Passing an empty string for --image-directory/-i disables\n        rendering images.\n        \"\"\"\n        for arg in ('--image-directory', '-i'):\n            self.digraphRecorder.reset()\n            self.collectedOutput = []\n\n            self.tool(argv=[self.fakeFQPN, arg, ''])\n            self.assertFalse(any(\"image\" in line\n                                 for line in self.collectedOutput))\n\n            self.assertEqual(len(self.digraphRecorder.saveCalls), 1)\n            (call,) = self.digraphRecorder.saveCalls\n            self.assertEqual(\"{}.dot\".format(self.fakeFQPN),\n                             call['filename'])\n\n            self.assertFalse(self.digraphRecorder.renderCalls)\n\n    def test_saveOnlyImage(self):\n        \"\"\"\n        Passing an empty string for --dot-directory/-d disables saving dot\n        files.\n        \"\"\"\n        for arg in ('--dot-directory', '-d'):\n            self.digraphRecorder.reset()\n            self.collectedOutput = []\n            self.tool(argv=[self.fakeFQPN, arg, ''])\n\n            self.assertFalse(any(\"dot\" in line\n                                 for line in self.collectedOutput))\n\n            self.assertEqual(len(self.digraphRecorder.renderCalls), 1)\n            (call,) = self.digraphRecorder.renderCalls\n            self.assertEqual(\"{}.dot\".format(self.fakeFQPN),\n                             call['filename'])\n            self.assertTrue(call['cleanup'])\n\n            self.assertFalse(self.digraphRecorder.saveCalls)\n\n    def test_saveDotAndImagesInDifferentDirectories(self):\n        \"\"\"\n        Passing different directories to --image-directory and --dot-directory\n        writes images and dot files to those directories.\n        \"\"\"\n        imageDirectory = 'image'\n        dotDirectory = 'dot'\n        self.tool(argv=[self.fakeFQPN,\n                        '--image-directory', imageDirectory,\n                        '--dot-directory', dotDirectory])\n\n        self.assertTrue(any(\"image\" in line\n                            for line in self.collectedOutput))\n        self.assertTrue(any(\"dot\" in line\n                            for line in self.collectedOutput))\n\n        self.assertEqual(len(self.digraphRecorder.renderCalls), 1)\n        (renderCall,) = self.digraphRecorder.renderCalls\n        self.assertEqual(renderCall[\"directory\"], imageDirectory)\n        self.assertTrue(renderCall['cleanup'])\n\n        self.assertEqual(len(self.digraphRecorder.saveCalls), 1)\n        (saveCall,) = self.digraphRecorder.saveCalls\n        self.assertEqual(saveCall[\"directory\"], dotDirectory)\n\n    def test_saveDotAndImagesInSameDirectory(self):\n        \"\"\"\n        Passing the same directory to --image-directory and --dot-directory\n        writes images and dot files to that one directory.\n        \"\"\"\n        directory = 'imagesAndDot'\n        self.tool(argv=[self.fakeFQPN,\n                        '--image-directory', directory,\n                        '--dot-directory', directory])\n\n        self.assertTrue(any(\"image and dot\" in line\n                            for line in self.collectedOutput))\n\n        self.assertEqual(len(self.digraphRecorder.renderCalls), 1)\n        (renderCall,) = self.digraphRecorder.renderCalls\n        self.assertEqual(renderCall[\"directory\"], directory)\n        self.assertFalse(renderCall['cleanup'])\n\n        self.assertFalse(len(self.digraphRecorder.saveCalls))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/automat/_visualize.py",
    "content": "from __future__ import print_function\nimport argparse\nimport sys\n\nimport graphviz\n\nfrom ._discover import findMachines\n\n\ndef _gvquote(s):\n    return '\"{}\"'.format(s.replace('\"', r'\\\"'))\n\n\ndef _gvhtml(s):\n    return '<{}>'.format(s)\n\n\ndef elementMaker(name, *children, **attrs):\n    \"\"\"\n    Construct a string from the HTML element description.\n    \"\"\"\n    formattedAttrs = ' '.join('{}={}'.format(key, _gvquote(str(value)))\n                              for key, value in sorted(attrs.items()))\n    formattedChildren = ''.join(children)\n    return u'<{name} {attrs}>{children}</{name}>'.format(\n        name=name,\n        attrs=formattedAttrs,\n        children=formattedChildren)\n\n\ndef tableMaker(inputLabel, outputLabels, port, _E=elementMaker):\n    \"\"\"\n    Construct an HTML table to label a state transition.\n    \"\"\"\n    colspan = {}\n    if outputLabels:\n        colspan['colspan'] = str(len(outputLabels))\n\n    inputLabelCell = _E(\"td\",\n                        _E(\"font\",\n                           inputLabel,\n                           face=\"menlo-italic\"),\n                        color=\"purple\",\n                        port=port,\n                        **colspan)\n\n    pointSize = {\"point-size\": \"9\"}\n    outputLabelCells = [_E(\"td\",\n                           _E(\"font\",\n                              outputLabel,\n                              **pointSize),\n                           color=\"pink\")\n                        for outputLabel in outputLabels]\n\n    rows = [_E(\"tr\", inputLabelCell)]\n\n    if outputLabels:\n        rows.append(_E(\"tr\", *outputLabelCells))\n\n    return _E(\"table\", *rows)\n\n\ndef makeDigraph(automaton, inputAsString=repr,\n                outputAsString=repr,\n                stateAsString=repr):\n    \"\"\"\n    Produce a L{graphviz.Digraph} object from an automaton.\n    \"\"\"\n    digraph = graphviz.Digraph(graph_attr={'pack': 'true',\n                                           'dpi': '100'},\n                               node_attr={'fontname': 'Menlo'},\n                               edge_attr={'fontname': 'Menlo'})\n\n    for state in automaton.states():\n        if state is automaton.initialState:\n            stateShape = \"bold\"\n            fontName = \"Menlo-Bold\"\n        else:\n            stateShape = \"\"\n            fontName = \"Menlo\"\n        digraph.node(stateAsString(state),\n                     fontame=fontName,\n                     shape=\"ellipse\",\n                     style=stateShape,\n                     color=\"blue\")\n    for n, eachTransition in enumerate(automaton.allTransitions()):\n        inState, inputSymbol, outState, outputSymbols = eachTransition\n        thisTransition = \"t{}\".format(n)\n        inputLabel = inputAsString(inputSymbol)\n\n        port = \"tableport\"\n        table = tableMaker(inputLabel, [outputAsString(outputSymbol)\n                                        for outputSymbol in outputSymbols],\n                           port=port)\n\n        digraph.node(thisTransition,\n                     label=_gvhtml(table), margin=\"0.2\", shape=\"none\")\n\n        digraph.edge(stateAsString(inState),\n                     '{}:{}:w'.format(thisTransition, port),\n                     arrowhead=\"none\")\n        digraph.edge('{}:{}:e'.format(thisTransition, port),\n                     stateAsString(outState))\n\n    return digraph\n\n\ndef tool(_progname=sys.argv[0],\n         _argv=sys.argv[1:],\n         _syspath=sys.path,\n         _findMachines=findMachines,\n         _print=print):\n    \"\"\"\n    Entry point for command line utility.\n    \"\"\"\n\n    DESCRIPTION = \"\"\"\n    Visualize automat.MethodicalMachines as graphviz graphs.\n    \"\"\"\n    EPILOG = \"\"\"\n    You must have the graphviz tool suite installed.  Please visit\n    http://www.graphviz.org for more information.\n    \"\"\"\n    if _syspath[0]:\n        _syspath.insert(0, '')\n    argumentParser = argparse.ArgumentParser(\n        prog=_progname,\n        description=DESCRIPTION,\n        epilog=EPILOG)\n    argumentParser.add_argument('fqpn',\n                                help=\"A Fully Qualified Path name\"\n                                \" representing where to find machines.\")\n    argumentParser.add_argument('--quiet', '-q',\n                                help=\"suppress output\",\n                                default=False,\n                                action=\"store_true\")\n    argumentParser.add_argument('--dot-directory', '-d',\n                                help=\"Where to write out .dot files.\",\n                                default=\".automat_visualize\")\n    argumentParser.add_argument('--image-directory', '-i',\n                                help=\"Where to write out image files.\",\n                                default=\".automat_visualize\")\n    argumentParser.add_argument('--image-type', '-t',\n                                help=\"The image format.\",\n                                choices=graphviz.FORMATS,\n                                default='png')\n    argumentParser.add_argument('--view', '-v',\n                                help=\"View rendered graphs with\"\n                                \" default image viewer\",\n                                default=False,\n                                action=\"store_true\")\n    args = argumentParser.parse_args(_argv)\n\n    explicitlySaveDot = (args.dot_directory\n                         and (not args.image_directory\n                              or args.image_directory != args.dot_directory))\n    if args.quiet:\n        def _print(*args):\n            pass\n\n    for fqpn, machine in _findMachines(args.fqpn):\n        _print(fqpn, '...discovered')\n\n        digraph = machine.asDigraph()\n\n        if explicitlySaveDot:\n            digraph.save(filename=\"{}.dot\".format(fqpn),\n                         directory=args.dot_directory)\n            _print(fqpn, \"...wrote dot into\", args.dot_directory)\n\n        if args.image_directory:\n            deleteDot = not args.dot_directory or explicitlySaveDot\n            digraph.format = args.image_type\n            digraph.render(filename=\"{}.dot\".format(fqpn),\n                           directory=args.image_directory,\n                           view=args.view,\n                           cleanup=deleteDot)\n            if deleteDot:\n                msg = \"...wrote image into\"\n            else:\n                msg = \"...wrote image and dot into\"\n            _print(fqpn, msg, args.image_directory)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/__init__.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"BSON (Binary JSON) encoding and decoding.\n\nThe mapping from Python types to BSON types is as follows:\n\n=======================================  =============  ===================\nPython Type                              BSON Type      Supported Direction\n=======================================  =============  ===================\nNone                                     null           both\nbool                                     boolean        both\nint [#int]_                              int32 / int64  py -> bson\nlong                                     int64          py -> bson\n`bson.int64.Int64`                       int64          both\nfloat                                    number (real)  both\nstring                                   string         py -> bson\nunicode                                  string         both\nlist                                     array          both\ndict / `SON`                             object         both\ndatetime.datetime [#dt]_ [#dt2]_         date           both\n`bson.regex.Regex`                       regex          both\ncompiled re [#re]_                       regex          py -> bson\n`bson.binary.Binary`                     binary         both\n`bson.objectid.ObjectId`                 oid            both\n`bson.dbref.DBRef`                       dbref          both\nNone                                     undefined      bson -> py\nunicode                                  code           bson -> py\n`bson.code.Code`                         code           py -> bson\nunicode                                  symbol         bson -> py\nbytes (Python 3) [#bytes]_               binary         both\n=======================================  =============  ===================\n\nNote that, when using Python 2.x, to save binary data it must be wrapped as\nan instance of `bson.binary.Binary`. Otherwise it will be saved as a BSON\nstring and retrieved as unicode. Users of Python 3.x can use the Python bytes\ntype.\n\n.. [#int] A Python int will be saved as a BSON int32 or BSON int64 depending\n   on its size. A BSON int32 will always decode to a Python int. A BSON\n   int64 will always decode to a :class:`~bson.int64.Int64`.\n.. [#dt] datetime.datetime instances will be rounded to the nearest\n   millisecond when saved\n.. [#dt2] all datetime.datetime instances are treated as *naive*. clients\n   should always use UTC.\n.. [#re] :class:`~bson.regex.Regex` instances and regular expression\n   objects from ``re.compile()`` are both saved as BSON regular expressions.\n   BSON regular expressions are decoded as :class:`~bson.regex.Regex`\n   instances.\n.. [#bytes] The bytes type from Python 3.x is encoded as BSON binary with\n   subtype 0. In Python 3.x it will be decoded back to bytes. In Python 2.x\n   it will be decoded to an instance of :class:`~bson.binary.Binary` with\n   subtype 0.\n\"\"\"\n\nimport calendar\nimport datetime\nimport itertools\nimport platform\nimport re\nimport struct\nimport sys\nimport uuid\n\nfrom codecs import (utf_8_decode as _utf_8_decode,\n                    utf_8_encode as _utf_8_encode)\n\nfrom bson.binary import (Binary, OLD_UUID_SUBTYPE,\n                         JAVA_LEGACY, CSHARP_LEGACY,\n                         UUIDLegacy)\nfrom bson.code import Code\nfrom bson.codec_options import (\n    CodecOptions, DEFAULT_CODEC_OPTIONS, _raw_document_class)\nfrom bson.dbref import DBRef\nfrom bson.decimal128 import Decimal128\nfrom bson.errors import (InvalidBSON,\n                         InvalidDocument,\n                         InvalidStringData)\nfrom bson.int64 import Int64\nfrom bson.max_key import MaxKey\nfrom bson.min_key import MinKey\nfrom bson.objectid import ObjectId\nfrom bson.py3compat import (abc,\n                            b,\n                            PY3,\n                            iteritems,\n                            text_type,\n                            string_type,\n                            reraise)\nfrom bson.regex import Regex\nfrom bson.son import SON, RE_TYPE\nfrom bson.timestamp import Timestamp\nfrom bson.tz_util import utc\n\n\ntry:\n    from bson import _cbson\n    _USE_C = True\nexcept ImportError:\n    _USE_C = False\n\n\nEPOCH_AWARE = datetime.datetime.fromtimestamp(0, utc)\nEPOCH_NAIVE = datetime.datetime.utcfromtimestamp(0)\n\n\nBSONNUM = b\"\\x01\" # Floating point\nBSONSTR = b\"\\x02\" # UTF-8 string\nBSONOBJ = b\"\\x03\" # Embedded document\nBSONARR = b\"\\x04\" # Array\nBSONBIN = b\"\\x05\" # Binary\nBSONUND = b\"\\x06\" # Undefined\nBSONOID = b\"\\x07\" # ObjectId\nBSONBOO = b\"\\x08\" # Boolean\nBSONDAT = b\"\\x09\" # UTC Datetime\nBSONNUL = b\"\\x0A\" # Null\nBSONRGX = b\"\\x0B\" # Regex\nBSONREF = b\"\\x0C\" # DBRef\nBSONCOD = b\"\\x0D\" # Javascript code\nBSONSYM = b\"\\x0E\" # Symbol\nBSONCWS = b\"\\x0F\" # Javascript code with scope\nBSONINT = b\"\\x10\" # 32bit int\nBSONTIM = b\"\\x11\" # Timestamp\nBSONLON = b\"\\x12\" # 64bit int\nBSONDEC = b\"\\x13\" # Decimal128\nBSONMIN = b\"\\xFF\" # Min key\nBSONMAX = b\"\\x7F\" # Max key\n\n\n_UNPACK_FLOAT_FROM = struct.Struct(\"<d\").unpack_from\n_UNPACK_INT = struct.Struct(\"<i\").unpack\n_UNPACK_INT_FROM = struct.Struct(\"<i\").unpack_from\n_UNPACK_LENGTH_SUBTYPE_FROM = struct.Struct(\"<iB\").unpack_from\n_UNPACK_LONG_FROM = struct.Struct(\"<q\").unpack_from\n_UNPACK_TIMESTAMP_FROM = struct.Struct(\"<II\").unpack_from\n\n\nif PY3:\n    _OBJEND = 0\n    # Only used to generate the _ELEMENT_GETTER dict\n    def _maybe_ord(element_type):\n        return ord(element_type)\n    # Only used in _raise_unkown_type below\n    def _elt_to_hex(element_type):\n        return chr(element_type).encode()\n    _supported_buffer_types = (bytes, bytearray)\nelse:\n    _OBJEND = b\"\\x00\"\n    def _maybe_ord(element_type):\n        return element_type\n    def _elt_to_hex(element_type):\n        return element_type\n    _supported_buffer_types = (bytes,)\n\n\n\nif platform.python_implementation() == 'Jython':\n    # This is why we can't have nice things.\n    # https://bugs.jython.org/issue2788\n    def get_data_and_view(data):\n        if isinstance(data, _supported_buffer_types):\n            return data, data\n        data = memoryview(data).tobytes()\n        return data, data\nelse:\n    def get_data_and_view(data):\n        if isinstance(data, _supported_buffer_types):\n            return data, memoryview(data)\n        view = memoryview(data)\n        return view.tobytes(), view\n\n\ndef _raise_unknown_type(element_type, element_name):\n    \"\"\"Unknown type helper.\"\"\"\n    raise InvalidBSON(\"Detected unknown BSON type %r for fieldname '%s'. Are \"\n                      \"you using the latest driver version?\" % (\n                          _elt_to_hex(element_type), element_name))\n\n\ndef _get_int(data, view, position, dummy0, dummy1, dummy2):\n    \"\"\"Decode a BSON int32 to python int.\"\"\"\n    return _UNPACK_INT_FROM(data, position)[0], position + 4\n\n\ndef _get_c_string(data, view, position, opts):\n    \"\"\"Decode a BSON 'C' string to python unicode string.\"\"\"\n    end = data.index(b\"\\x00\", position)\n    return _utf_8_decode(view[position:end],\n                         opts.unicode_decode_error_handler, True)[0], end + 1\n\n\ndef _get_float(data, view, position, dummy0, dummy1, dummy2):\n    \"\"\"Decode a BSON double to python float.\"\"\"\n    return _UNPACK_FLOAT_FROM(data, position)[0], position + 8\n\n\ndef _get_string(data, view, position, obj_end, opts, dummy):\n    \"\"\"Decode a BSON string to python unicode string.\"\"\"\n    length = _UNPACK_INT_FROM(data, position)[0]\n    position += 4\n    if length < 1 or obj_end - position < length:\n        raise InvalidBSON(\"invalid string length\")\n    end = position + length - 1\n    if data[end] != _OBJEND:\n        raise InvalidBSON(\"invalid end of string\")\n    return _utf_8_decode(view[position:end],\n                         opts.unicode_decode_error_handler, True)[0], end + 1\n\n\ndef _get_object_size(data, position, obj_end):\n    \"\"\"Validate and return a BSON document's size.\"\"\"\n    try:\n        obj_size = _UNPACK_INT_FROM(data, position)[0]\n    except struct.error as exc:\n        raise InvalidBSON(str(exc))\n    end = position + obj_size - 1\n    if data[end] != _OBJEND:\n        raise InvalidBSON(\"bad eoo\")\n    if end >= obj_end:\n        raise InvalidBSON(\"invalid object length\")\n    # If this is the top-level document, validate the total size too.\n    if position == 0 and obj_size != obj_end:\n        raise InvalidBSON(\"invalid object length\")\n    return obj_size, end\n\n\ndef _get_object(data, view, position, obj_end, opts, dummy):\n    \"\"\"Decode a BSON subdocument to opts.document_class or bson.dbref.DBRef.\"\"\"\n    obj_size, end = _get_object_size(data, position, obj_end)\n    if _raw_document_class(opts.document_class):\n        return (opts.document_class(data[position:end + 1], opts),\n                position + obj_size)\n\n    obj = _elements_to_dict(data, view, position + 4, end, opts)\n\n    position += obj_size\n    if \"$ref\" in obj:\n        return (DBRef(obj.pop(\"$ref\"), obj.pop(\"$id\", None),\n                      obj.pop(\"$db\", None), obj), position)\n    return obj, position\n\n\ndef _get_array(data, view, position, obj_end, opts, element_name):\n    \"\"\"Decode a BSON array to python list.\"\"\"\n    size = _UNPACK_INT_FROM(data, position)[0]\n    end = position + size - 1\n    if data[end] != _OBJEND:\n        raise InvalidBSON(\"bad eoo\")\n\n    position += 4\n    end -= 1\n    result = []\n\n    # Avoid doing global and attribute lookups in the loop.\n    append = result.append\n    index = data.index\n    getter = _ELEMENT_GETTER\n    decoder_map = opts.type_registry._decoder_map\n\n    while position < end:\n        element_type = data[position]\n        # Just skip the keys.\n        position = index(b'\\x00', position) + 1\n        try:\n            value, position = getter[element_type](\n                data, view, position, obj_end, opts, element_name)\n        except KeyError:\n            _raise_unknown_type(element_type, element_name)\n\n        if decoder_map:\n            custom_decoder = decoder_map.get(type(value))\n            if custom_decoder is not None:\n                value = custom_decoder(value)\n\n        append(value)\n\n    if position != end + 1:\n        raise InvalidBSON('bad array length')\n    return result, position + 1\n\n\ndef _get_binary(data, view, position, obj_end, opts, dummy1):\n    \"\"\"Decode a BSON binary to bson.binary.Binary or python UUID.\"\"\"\n    length, subtype = _UNPACK_LENGTH_SUBTYPE_FROM(data, position)\n    position += 5\n    if subtype == 2:\n        length2 = _UNPACK_INT_FROM(data, position)[0]\n        position += 4\n        if length2 != length - 4:\n            raise InvalidBSON(\"invalid binary (st 2) - lengths don't match!\")\n        length = length2\n    end = position + length\n    if length < 0 or end > obj_end:\n        raise InvalidBSON('bad binary object length')\n    if subtype == 3:\n        # Java Legacy\n        uuid_representation = opts.uuid_representation\n        if uuid_representation == JAVA_LEGACY:\n            java = data[position:end]\n            value = uuid.UUID(bytes=java[0:8][::-1] + java[8:16][::-1])\n        # C# legacy\n        elif uuid_representation == CSHARP_LEGACY:\n            value = uuid.UUID(bytes_le=data[position:end])\n        # Python\n        else:\n            value = uuid.UUID(bytes=data[position:end])\n        return value, end\n    if subtype == 4:\n        return uuid.UUID(bytes=data[position:end]), end\n    # Python3 special case. Decode subtype 0 to 'bytes'.\n    if PY3 and subtype == 0:\n        value = data[position:end]\n    else:\n        value = Binary(data[position:end], subtype)\n    return value, end\n\n\ndef _get_oid(data, view, position, dummy0, dummy1, dummy2):\n    \"\"\"Decode a BSON ObjectId to bson.objectid.ObjectId.\"\"\"\n    end = position + 12\n    return ObjectId(data[position:end]), end\n\n\ndef _get_boolean(data, view, position, dummy0, dummy1, dummy2):\n    \"\"\"Decode a BSON true/false to python True/False.\"\"\"\n    end = position + 1\n    boolean_byte = data[position:end]\n    if boolean_byte == b'\\x00':\n        return False, end\n    elif boolean_byte == b'\\x01':\n        return True, end\n    raise InvalidBSON('invalid boolean value: %r' % boolean_byte)\n\n\ndef _get_date(data, view, position, dummy0, opts, dummy1):\n    \"\"\"Decode a BSON datetime to python datetime.datetime.\"\"\"\n    return _millis_to_datetime(\n        _UNPACK_LONG_FROM(data, position)[0], opts), position + 8\n\n\ndef _get_code(data, view, position, obj_end, opts, element_name):\n    \"\"\"Decode a BSON code to bson.code.Code.\"\"\"\n    code, position = _get_string(data, view, position, obj_end, opts, element_name)\n    return Code(code), position\n\n\ndef _get_code_w_scope(data, view, position, obj_end, opts, element_name):\n    \"\"\"Decode a BSON code_w_scope to bson.code.Code.\"\"\"\n    code_end = position + _UNPACK_INT_FROM(data, position)[0]\n    code, position = _get_string(\n        data, view, position + 4, code_end, opts, element_name)\n    scope, position = _get_object(data, view, position, code_end, opts, element_name)\n    if position != code_end:\n        raise InvalidBSON('scope outside of javascript code boundaries')\n    return Code(code, scope), position\n\n\ndef _get_regex(data, view, position, dummy0, opts, dummy1):\n    \"\"\"Decode a BSON regex to bson.regex.Regex or a python pattern object.\"\"\"\n    pattern, position = _get_c_string(data, view, position, opts)\n    bson_flags, position = _get_c_string(data, view, position, opts)\n    bson_re = Regex(pattern, bson_flags)\n    return bson_re, position\n\n\ndef _get_ref(data, view, position, obj_end, opts, element_name):\n    \"\"\"Decode (deprecated) BSON DBPointer to bson.dbref.DBRef.\"\"\"\n    collection, position = _get_string(\n        data, view, position, obj_end, opts, element_name)\n    oid, position = _get_oid(data, view, position, obj_end, opts, element_name)\n    return DBRef(collection, oid), position\n\n\ndef _get_timestamp(data, view, position, dummy0, dummy1, dummy2):\n    \"\"\"Decode a BSON timestamp to bson.timestamp.Timestamp.\"\"\"\n    inc, timestamp = _UNPACK_TIMESTAMP_FROM(data, position)\n    return Timestamp(timestamp, inc), position + 8\n\n\ndef _get_int64(data, view, position, dummy0, dummy1, dummy2):\n    \"\"\"Decode a BSON int64 to bson.int64.Int64.\"\"\"\n    return Int64(_UNPACK_LONG_FROM(data, position)[0]), position + 8\n\n\ndef _get_decimal128(data, view, position, dummy0, dummy1, dummy2):\n    \"\"\"Decode a BSON decimal128 to bson.decimal128.Decimal128.\"\"\"\n    end = position + 16\n    return Decimal128.from_bid(data[position:end]), end\n\n\n# Each decoder function's signature is:\n#   - data: bytes\n#   - view: memoryview that references `data`\n#   - position: int, beginning of object in 'data' to decode\n#   - obj_end: int, end of object to decode in 'data' if variable-length type\n#   - opts: a CodecOptions\n_ELEMENT_GETTER = {\n    _maybe_ord(BSONNUM): _get_float,\n    _maybe_ord(BSONSTR): _get_string,\n    _maybe_ord(BSONOBJ): _get_object,\n    _maybe_ord(BSONARR): _get_array,\n    _maybe_ord(BSONBIN): _get_binary,\n    _maybe_ord(BSONUND): lambda u, v, w, x, y, z: (None, w),  # Deprecated undefined\n    _maybe_ord(BSONOID): _get_oid,\n    _maybe_ord(BSONBOO): _get_boolean,\n    _maybe_ord(BSONDAT): _get_date,\n    _maybe_ord(BSONNUL): lambda u, v, w, x, y, z: (None, w),\n    _maybe_ord(BSONRGX): _get_regex,\n    _maybe_ord(BSONREF): _get_ref,  # Deprecated DBPointer\n    _maybe_ord(BSONCOD): _get_code,\n    _maybe_ord(BSONSYM): _get_string,  # Deprecated symbol\n    _maybe_ord(BSONCWS): _get_code_w_scope,\n    _maybe_ord(BSONINT): _get_int,\n    _maybe_ord(BSONTIM): _get_timestamp,\n    _maybe_ord(BSONLON): _get_int64,\n    _maybe_ord(BSONDEC): _get_decimal128,\n    _maybe_ord(BSONMIN): lambda u, v, w, x, y, z: (MinKey(), w),\n    _maybe_ord(BSONMAX): lambda u, v, w, x, y, z: (MaxKey(), w)}\n\n\nif _USE_C:\n    def _element_to_dict(data, view, position, obj_end, opts):\n        return _cbson._element_to_dict(data, position, obj_end, opts)\nelse:\n    def _element_to_dict(data, view, position, obj_end, opts):\n        \"\"\"Decode a single key, value pair.\"\"\"\n        element_type = data[position]\n        position += 1\n        element_name, position = _get_c_string(data, view, position, opts)\n        try:\n            value, position = _ELEMENT_GETTER[element_type](data, view, position,\n                                                            obj_end, opts,\n                                                            element_name)\n        except KeyError:\n            _raise_unknown_type(element_type, element_name)\n\n        if opts.type_registry._decoder_map:\n            custom_decoder = opts.type_registry._decoder_map.get(type(value))\n            if custom_decoder is not None:\n                value = custom_decoder(value)\n\n        return element_name, value, position\n\n\ndef _raw_to_dict(data, position, obj_end, opts, result):\n    data, view = get_data_and_view(data)\n    return _elements_to_dict(data, view, position, obj_end, opts, result)\n\n\ndef _elements_to_dict(data, view, position, obj_end, opts, result=None):\n    \"\"\"Decode a BSON document into result.\"\"\"\n    if result is None:\n        result = opts.document_class()\n    end = obj_end - 1\n    while position < end:\n        key, value, position = _element_to_dict(data, view, position, obj_end, opts)\n        result[key] = value\n    if position != obj_end:\n        raise InvalidBSON('bad object or element length')\n    return result\n\n\ndef _bson_to_dict(data, opts):\n    \"\"\"Decode a BSON string to document_class.\"\"\"\n    data, view = get_data_and_view(data)\n    try:\n        if _raw_document_class(opts.document_class):\n            return opts.document_class(data, opts)\n        _, end = _get_object_size(data, 0, len(data))\n        return _elements_to_dict(data, view, 4, end, opts)\n    except InvalidBSON:\n        raise\n    except Exception:\n        # Change exception type to InvalidBSON but preserve traceback.\n        _, exc_value, exc_tb = sys.exc_info()\n        reraise(InvalidBSON, exc_value, exc_tb)\nif _USE_C:\n    _bson_to_dict = _cbson._bson_to_dict\n\n\n_PACK_FLOAT = struct.Struct(\"<d\").pack\n_PACK_INT = struct.Struct(\"<i\").pack\n_PACK_LENGTH_SUBTYPE = struct.Struct(\"<iB\").pack\n_PACK_LONG = struct.Struct(\"<q\").pack\n_PACK_TIMESTAMP = struct.Struct(\"<II\").pack\n_LIST_NAMES = tuple(b(str(i)) + b\"\\x00\" for i in range(1000))\n\n\ndef gen_list_name():\n    \"\"\"Generate \"keys\" for encoded lists in the sequence\n    b\"0\\x00\", b\"1\\x00\", b\"2\\x00\", ...\n\n    The first 1000 keys are returned from a pre-built cache. All\n    subsequent keys are generated on the fly.\n    \"\"\"\n    for name in _LIST_NAMES:\n        yield name\n\n    counter = itertools.count(1000)\n    while True:\n        yield b(str(next(counter))) + b\"\\x00\"\n\n\ndef _make_c_string_check(string):\n    \"\"\"Make a 'C' string, checking for embedded NUL characters.\"\"\"\n    if isinstance(string, bytes):\n        if b\"\\x00\" in string:\n            raise InvalidDocument(\"BSON keys / regex patterns must not \"\n                                  \"contain a NUL character\")\n        try:\n            _utf_8_decode(string, None, True)\n            return string + b\"\\x00\"\n        except UnicodeError:\n            raise InvalidStringData(\"strings in documents must be valid \"\n                                    \"UTF-8: %r\" % string)\n    else:\n        if \"\\x00\" in string:\n            raise InvalidDocument(\"BSON keys / regex patterns must not \"\n                                  \"contain a NUL character\")\n        return _utf_8_encode(string)[0] + b\"\\x00\"\n\n\ndef _make_c_string(string):\n    \"\"\"Make a 'C' string.\"\"\"\n    if isinstance(string, bytes):\n        try:\n            _utf_8_decode(string, None, True)\n            return string + b\"\\x00\"\n        except UnicodeError:\n            raise InvalidStringData(\"strings in documents must be valid \"\n                                    \"UTF-8: %r\" % string)\n    else:\n        return _utf_8_encode(string)[0] + b\"\\x00\"\n\n\nif PY3:\n    def _make_name(string):\n        \"\"\"Make a 'C' string suitable for a BSON key.\"\"\"\n        # Keys can only be text in python 3.\n        if \"\\x00\" in string:\n            raise InvalidDocument(\"BSON keys / regex patterns must not \"\n                                  \"contain a NUL character\")\n        return _utf_8_encode(string)[0] + b\"\\x00\"\nelse:\n    # Keys can be unicode or bytes in python 2.\n    _make_name = _make_c_string_check\n\n\ndef _encode_float(name, value, dummy0, dummy1):\n    \"\"\"Encode a float.\"\"\"\n    return b\"\\x01\" + name + _PACK_FLOAT(value)\n\n\nif PY3:\n    def _encode_bytes(name, value, dummy0, dummy1):\n        \"\"\"Encode a python bytes.\"\"\"\n        # Python3 special case. Store 'bytes' as BSON binary subtype 0.\n        return b\"\\x05\" + name + _PACK_INT(len(value)) + b\"\\x00\" + value\nelse:\n    def _encode_bytes(name, value, dummy0, dummy1):\n        \"\"\"Encode a python str (python 2.x).\"\"\"\n        try:\n            _utf_8_decode(value, None, True)\n        except UnicodeError:\n            raise InvalidStringData(\"strings in documents must be valid \"\n                                    \"UTF-8: %r\" % (value,))\n        return b\"\\x02\" + name + _PACK_INT(len(value) + 1) + value + b\"\\x00\"\n\n\ndef _encode_mapping(name, value, check_keys, opts):\n    \"\"\"Encode a mapping type.\"\"\"\n    if _raw_document_class(value):\n        return b'\\x03' + name + value.raw\n    data = b\"\".join([_element_to_bson(key, val, check_keys, opts)\n                     for key, val in iteritems(value)])\n    return b\"\\x03\" + name + _PACK_INT(len(data) + 5) + data + b\"\\x00\"\n\n\ndef _encode_dbref(name, value, check_keys, opts):\n    \"\"\"Encode bson.dbref.DBRef.\"\"\"\n    buf = bytearray(b\"\\x03\" + name + b\"\\x00\\x00\\x00\\x00\")\n    begin = len(buf) - 4\n\n    buf += _name_value_to_bson(b\"$ref\\x00\",\n                               value.collection, check_keys, opts)\n    buf += _name_value_to_bson(b\"$id\\x00\",\n                               value.id, check_keys, opts)\n    if value.database is not None:\n        buf += _name_value_to_bson(\n            b\"$db\\x00\", value.database, check_keys, opts)\n    for key, val in iteritems(value._DBRef__kwargs):\n        buf += _element_to_bson(key, val, check_keys, opts)\n\n    buf += b\"\\x00\"\n    buf[begin:begin + 4] = _PACK_INT(len(buf) - begin)\n    return bytes(buf)\n\n\ndef _encode_list(name, value, check_keys, opts):\n    \"\"\"Encode a list/tuple.\"\"\"\n    lname = gen_list_name()\n    data = b\"\".join([_name_value_to_bson(next(lname), item,\n                                         check_keys, opts)\n                     for item in value])\n    return b\"\\x04\" + name + _PACK_INT(len(data) + 5) + data + b\"\\x00\"\n\n\ndef _encode_text(name, value, dummy0, dummy1):\n    \"\"\"Encode a python unicode (python 2.x) / str (python 3.x).\"\"\"\n    value = _utf_8_encode(value)[0]\n    return b\"\\x02\" + name + _PACK_INT(len(value) + 1) + value + b\"\\x00\"\n\n\ndef _encode_binary(name, value, dummy0, dummy1):\n    \"\"\"Encode bson.binary.Binary.\"\"\"\n    subtype = value.subtype\n    if subtype == 2:\n        value = _PACK_INT(len(value)) + value\n    return b\"\\x05\" + name + _PACK_LENGTH_SUBTYPE(len(value), subtype) + value\n\n\ndef _encode_uuid(name, value, dummy, opts):\n    \"\"\"Encode uuid.UUID.\"\"\"\n    uuid_representation = opts.uuid_representation\n    # Python Legacy Common Case\n    if uuid_representation == OLD_UUID_SUBTYPE:\n        return b\"\\x05\" + name + b'\\x10\\x00\\x00\\x00\\x03' + value.bytes\n    # Java Legacy\n    elif uuid_representation == JAVA_LEGACY:\n        from_uuid = value.bytes\n        data = from_uuid[0:8][::-1] + from_uuid[8:16][::-1]\n        return b\"\\x05\" + name + b'\\x10\\x00\\x00\\x00\\x03' + data\n    # C# legacy\n    elif uuid_representation == CSHARP_LEGACY:\n        # Microsoft GUID representation.\n        return b\"\\x05\" + name + b'\\x10\\x00\\x00\\x00\\x03' + value.bytes_le\n    # New\n    return b\"\\x05\" + name + b'\\x10\\x00\\x00\\x00\\x04' + value.bytes\n\n\ndef _encode_objectid(name, value, dummy0, dummy1):\n    \"\"\"Encode bson.objectid.ObjectId.\"\"\"\n    return b\"\\x07\" + name + value.binary\n\n\ndef _encode_bool(name, value, dummy0, dummy1):\n    \"\"\"Encode a python boolean (True/False).\"\"\"\n    return b\"\\x08\" + name + (value and b\"\\x01\" or b\"\\x00\")\n\n\ndef _encode_datetime(name, value, dummy0, dummy1):\n    \"\"\"Encode datetime.datetime.\"\"\"\n    millis = _datetime_to_millis(value)\n    return b\"\\x09\" + name + _PACK_LONG(millis)\n\n\ndef _encode_none(name, dummy0, dummy1, dummy2):\n    \"\"\"Encode python None.\"\"\"\n    return b\"\\x0A\" + name\n\n\ndef _encode_regex(name, value, dummy0, dummy1):\n    \"\"\"Encode a python regex or bson.regex.Regex.\"\"\"\n    flags = value.flags\n    # Python 2 common case\n    if flags == 0:\n        return b\"\\x0B\" + name + _make_c_string_check(value.pattern) + b\"\\x00\"\n    # Python 3 common case\n    elif flags == re.UNICODE:\n        return b\"\\x0B\" + name + _make_c_string_check(value.pattern) + b\"u\\x00\"\n    else:\n        sflags = b\"\"\n        if flags & re.IGNORECASE:\n            sflags += b\"i\"\n        if flags & re.LOCALE:\n            sflags += b\"l\"\n        if flags & re.MULTILINE:\n            sflags += b\"m\"\n        if flags & re.DOTALL:\n            sflags += b\"s\"\n        if flags & re.UNICODE:\n            sflags += b\"u\"\n        if flags & re.VERBOSE:\n            sflags += b\"x\"\n        sflags += b\"\\x00\"\n        return b\"\\x0B\" + name + _make_c_string_check(value.pattern) + sflags\n\n\ndef _encode_code(name, value, dummy, opts):\n    \"\"\"Encode bson.code.Code.\"\"\"\n    cstring = _make_c_string(value)\n    cstrlen = len(cstring)\n    if value.scope is None:\n        return b\"\\x0D\" + name + _PACK_INT(cstrlen) + cstring\n    scope = _dict_to_bson(value.scope, False, opts, False)\n    full_length = _PACK_INT(8 + cstrlen + len(scope))\n    return b\"\\x0F\" + name + full_length + _PACK_INT(cstrlen) + cstring + scope\n\n\ndef _encode_int(name, value, dummy0, dummy1):\n    \"\"\"Encode a python int.\"\"\"\n    if -2147483648 <= value <= 2147483647:\n        return b\"\\x10\" + name + _PACK_INT(value)\n    else:\n        try:\n            return b\"\\x12\" + name + _PACK_LONG(value)\n        except struct.error:\n            raise OverflowError(\"BSON can only handle up to 8-byte ints\")\n\n\ndef _encode_timestamp(name, value, dummy0, dummy1):\n    \"\"\"Encode bson.timestamp.Timestamp.\"\"\"\n    return b\"\\x11\" + name + _PACK_TIMESTAMP(value.inc, value.time)\n\n\ndef _encode_long(name, value, dummy0, dummy1):\n    \"\"\"Encode a python long (python 2.x)\"\"\"\n    try:\n        return b\"\\x12\" + name + _PACK_LONG(value)\n    except struct.error:\n        raise OverflowError(\"BSON can only handle up to 8-byte ints\")\n\n\ndef _encode_decimal128(name, value, dummy0, dummy1):\n    \"\"\"Encode bson.decimal128.Decimal128.\"\"\"\n    return b\"\\x13\" + name + value.bid\n\n\ndef _encode_minkey(name, dummy0, dummy1, dummy2):\n    \"\"\"Encode bson.min_key.MinKey.\"\"\"\n    return b\"\\xFF\" + name\n\n\ndef _encode_maxkey(name, dummy0, dummy1, dummy2):\n    \"\"\"Encode bson.max_key.MaxKey.\"\"\"\n    return b\"\\x7F\" + name\n\n\n# Each encoder function's signature is:\n#   - name: utf-8 bytes\n#   - value: a Python data type, e.g. a Python int for _encode_int\n#   - check_keys: bool, whether to check for invalid names\n#   - opts: a CodecOptions\n_ENCODERS = {\n    bool: _encode_bool,\n    bytes: _encode_bytes,\n    datetime.datetime: _encode_datetime,\n    dict: _encode_mapping,\n    float: _encode_float,\n    int: _encode_int,\n    list: _encode_list,\n    # unicode in py2, str in py3\n    text_type: _encode_text,\n    tuple: _encode_list,\n    type(None): _encode_none,\n    uuid.UUID: _encode_uuid,\n    Binary: _encode_binary,\n    Int64: _encode_long,\n    Code: _encode_code,\n    DBRef: _encode_dbref,\n    MaxKey: _encode_maxkey,\n    MinKey: _encode_minkey,\n    ObjectId: _encode_objectid,\n    Regex: _encode_regex,\n    RE_TYPE: _encode_regex,\n    SON: _encode_mapping,\n    Timestamp: _encode_timestamp,\n    UUIDLegacy: _encode_binary,\n    Decimal128: _encode_decimal128,\n    # Special case. This will never be looked up directly.\n    abc.Mapping: _encode_mapping,\n}\n\n\n_MARKERS = {\n    5: _encode_binary,\n    7: _encode_objectid,\n    11: _encode_regex,\n    13: _encode_code,\n    17: _encode_timestamp,\n    18: _encode_long,\n    100: _encode_dbref,\n    127: _encode_maxkey,\n    255: _encode_minkey,\n}\n\nif not PY3:\n    _ENCODERS[long] = _encode_long\n\n\n_BUILT_IN_TYPES = tuple(t for t in _ENCODERS)\n\n\ndef _name_value_to_bson(name, value, check_keys, opts,\n                        in_custom_call=False,\n                        in_fallback_call=False):\n    \"\"\"Encode a single name, value pair.\"\"\"\n    # First see if the type is already cached. KeyError will only ever\n    # happen once per subtype.\n    try:\n        return _ENCODERS[type(value)](name, value, check_keys, opts)\n    except KeyError:\n        pass\n\n    # Second, fall back to trying _type_marker. This has to be done\n    # before the loop below since users could subclass one of our\n    # custom types that subclasses a python built-in (e.g. Binary)\n    marker = getattr(value, \"_type_marker\", None)\n    if isinstance(marker, int) and marker in _MARKERS:\n        func = _MARKERS[marker]\n        # Cache this type for faster subsequent lookup.\n        _ENCODERS[type(value)] = func\n        return func(name, value, check_keys, opts)\n\n    # Third, check if a type encoder is registered for this type.\n    # Note that subtypes of registered custom types are not auto-encoded.\n    if not in_custom_call and opts.type_registry._encoder_map:\n        custom_encoder = opts.type_registry._encoder_map.get(type(value))\n        if custom_encoder is not None:\n            return _name_value_to_bson(\n                name, custom_encoder(value), check_keys, opts,\n                in_custom_call=True)\n\n    # Fourth, test each base type. This will only happen once for\n    # a subtype of a supported base type. Unlike in the C-extensions, this\n    # is done after trying the custom type encoder because checking for each\n    # subtype is expensive.\n    for base in _BUILT_IN_TYPES:\n        if isinstance(value, base):\n            func = _ENCODERS[base]\n            # Cache this type for faster subsequent lookup.\n            _ENCODERS[type(value)] = func\n            return func(name, value, check_keys, opts)\n\n    # As a last resort, try using the fallback encoder, if the user has\n    # provided one.\n    fallback_encoder = opts.type_registry._fallback_encoder\n    if not in_fallback_call and fallback_encoder is not None:\n        return _name_value_to_bson(\n            name, fallback_encoder(value), check_keys, opts,\n            in_fallback_call=True)\n\n    raise InvalidDocument(\n        \"cannot encode object: %r, of type: %r\" % (value, type(value)))\n\n\ndef _element_to_bson(key, value, check_keys, opts):\n    \"\"\"Encode a single key, value pair.\"\"\"\n    if not isinstance(key, string_type):\n        raise InvalidDocument(\"documents must have only string keys, \"\n                              \"key was %r\" % (key,))\n    if check_keys:\n        if key.startswith(\"$\"):\n            raise InvalidDocument(\"key %r must not start with '$'\" % (key,))\n        if \".\" in key:\n            raise InvalidDocument(\"key %r must not contain '.'\" % (key,))\n\n    name = _make_name(key)\n    return _name_value_to_bson(name, value, check_keys, opts)\n\n\ndef _dict_to_bson(doc, check_keys, opts, top_level=True):\n    \"\"\"Encode a document to BSON.\"\"\"\n    if _raw_document_class(doc):\n        return doc.raw\n    try:\n        elements = []\n        if top_level and \"_id\" in doc:\n            elements.append(_name_value_to_bson(b\"_id\\x00\", doc[\"_id\"],\n                                                check_keys, opts))\n        for (key, value) in iteritems(doc):\n            if not top_level or key != \"_id\":\n                elements.append(_element_to_bson(key, value,\n                                                 check_keys, opts))\n    except AttributeError:\n        raise TypeError(\"encoder expected a mapping type but got: %r\" % (doc,))\n\n    encoded = b\"\".join(elements)\n    return _PACK_INT(len(encoded) + 5) + encoded + b\"\\x00\"\nif _USE_C:\n    _dict_to_bson = _cbson._dict_to_bson\n\n\ndef _millis_to_datetime(millis, opts):\n    \"\"\"Convert milliseconds since epoch UTC to datetime.\"\"\"\n    diff = ((millis % 1000) + 1000) % 1000\n    seconds = (millis - diff) // 1000\n    micros = diff * 1000\n    if opts.tz_aware:\n        dt = EPOCH_AWARE + datetime.timedelta(seconds=seconds,\n                                              microseconds=micros)\n        if opts.tzinfo:\n            dt = dt.astimezone(opts.tzinfo)\n        return dt\n    else:\n        return EPOCH_NAIVE + datetime.timedelta(seconds=seconds,\n                                                microseconds=micros)\n\n\ndef _datetime_to_millis(dtm):\n    \"\"\"Convert datetime to milliseconds since epoch UTC.\"\"\"\n    if dtm.utcoffset() is not None:\n        dtm = dtm - dtm.utcoffset()\n    return int(calendar.timegm(dtm.timetuple()) * 1000 +\n               dtm.microsecond // 1000)\n\n\n_CODEC_OPTIONS_TYPE_ERROR = TypeError(\n    \"codec_options must be an instance of CodecOptions\")\n\n\ndef encode(document, check_keys=False, codec_options=DEFAULT_CODEC_OPTIONS):\n    \"\"\"Encode a document to BSON.\n\n    A document can be any mapping type (like :class:`dict`).\n\n    Raises :class:`TypeError` if `document` is not a mapping type,\n    or contains keys that are not instances of\n    :class:`basestring` (:class:`str` in python 3). Raises\n    :class:`~bson.errors.InvalidDocument` if `document` cannot be\n    converted to :class:`BSON`.\n\n    :Parameters:\n      - `document`: mapping type representing a document\n      - `check_keys` (optional): check if keys start with '$' or\n        contain '.', raising :class:`~bson.errors.InvalidDocument` in\n        either case\n      - `codec_options` (optional): An instance of\n        :class:`~bson.codec_options.CodecOptions`.\n\n    .. versionadded:: 3.9\n    \"\"\"\n    if not isinstance(codec_options, CodecOptions):\n        raise _CODEC_OPTIONS_TYPE_ERROR\n\n    return _dict_to_bson(document, check_keys, codec_options)\n\n\ndef decode(data, codec_options=DEFAULT_CODEC_OPTIONS):\n    \"\"\"Decode BSON to a document.\n\n    By default, returns a BSON document represented as a Python\n    :class:`dict`. To use a different :class:`MutableMapping` class,\n    configure a :class:`~bson.codec_options.CodecOptions`::\n\n        >>> import collections  # From Python standard library.\n        >>> import bson\n        >>> from bson.codec_options import CodecOptions\n        >>> data = bson.encode({'a': 1})\n        >>> decoded_doc = bson.decode(data)\n        <type 'dict'>\n        >>> options = CodecOptions(document_class=collections.OrderedDict)\n        >>> decoded_doc = bson.decode(data, codec_options=options)\n        >>> type(decoded_doc)\n        <class 'collections.OrderedDict'>\n\n    :Parameters:\n      - `data`: the BSON to decode. Any bytes-like object that implements\n        the buffer protocol.\n      - `codec_options` (optional): An instance of\n        :class:`~bson.codec_options.CodecOptions`.\n\n    .. versionadded:: 3.9\n    \"\"\"\n    if not isinstance(codec_options, CodecOptions):\n        raise _CODEC_OPTIONS_TYPE_ERROR\n\n    return _bson_to_dict(data, codec_options)\n\n\ndef decode_all(data, codec_options=DEFAULT_CODEC_OPTIONS):\n    \"\"\"Decode BSON data to multiple documents.\n\n    `data` must be a bytes-like object implementing the buffer protocol that\n    provides concatenated, valid, BSON-encoded documents.\n\n    :Parameters:\n      - `data`: BSON data\n      - `codec_options` (optional): An instance of\n        :class:`~bson.codec_options.CodecOptions`.\n\n    .. versionchanged:: 3.9\n       Supports bytes-like objects that implement the buffer protocol.\n\n    .. versionchanged:: 3.0\n       Removed `compile_re` option: PyMongo now always represents BSON regular\n       expressions as :class:`~bson.regex.Regex` objects. Use\n       :meth:`~bson.regex.Regex.try_compile` to attempt to convert from a\n       BSON regular expression to a Python regular expression object.\n\n       Replaced `as_class`, `tz_aware`, and `uuid_subtype` options with\n       `codec_options`.\n\n    .. versionchanged:: 2.7\n       Added `compile_re` option. If set to False, PyMongo represented BSON\n       regular expressions as :class:`~bson.regex.Regex` objects instead of\n       attempting to compile BSON regular expressions as Python native\n       regular expressions, thus preventing errors for some incompatible\n       patterns, see `PYTHON-500`_.\n\n    .. _PYTHON-500: https://jira.mongodb.org/browse/PYTHON-500\n    \"\"\"\n    data, view = get_data_and_view(data)\n    if not isinstance(codec_options, CodecOptions):\n        raise _CODEC_OPTIONS_TYPE_ERROR\n\n    data_len = len(data)\n    docs = []\n    position = 0\n    end = data_len - 1\n    use_raw = _raw_document_class(codec_options.document_class)\n    try:\n        while position < end:\n            obj_size = _UNPACK_INT_FROM(data, position)[0]\n            if data_len - position < obj_size:\n                raise InvalidBSON(\"invalid object size\")\n            obj_end = position + obj_size - 1\n            if data[obj_end] != _OBJEND:\n                raise InvalidBSON(\"bad eoo\")\n            if use_raw:\n                docs.append(\n                    codec_options.document_class(\n                        data[position:obj_end + 1], codec_options))\n            else:\n                docs.append(_elements_to_dict(data,\n                                              view,\n                                              position + 4,\n                                              obj_end,\n                                              codec_options))\n            position += obj_size\n        return docs\n    except InvalidBSON:\n        raise\n    except Exception:\n        # Change exception type to InvalidBSON but preserve traceback.\n        _, exc_value, exc_tb = sys.exc_info()\n        reraise(InvalidBSON, exc_value, exc_tb)\n\n\nif _USE_C:\n    decode_all = _cbson.decode_all\n\n\ndef _decode_selective(rawdoc, fields, codec_options):\n    if _raw_document_class(codec_options.document_class):\n        # If document_class is RawBSONDocument, use vanilla dictionary for\n        # decoding command response.\n        doc = {}\n    else:\n        # Else, use the specified document_class.\n        doc = codec_options.document_class()\n    for key, value in iteritems(rawdoc):\n        if key in fields:\n            if fields[key] == 1:\n                doc[key] = _bson_to_dict(rawdoc.raw, codec_options)[key]\n            else:\n                doc[key] = _decode_selective(value, fields[key], codec_options)\n        else:\n            doc[key] = value\n    return doc\n\n\ndef _decode_all_selective(data, codec_options, fields):\n    \"\"\"Decode BSON data to a single document while using user-provided\n    custom decoding logic.\n\n    `data` must be a string representing a valid, BSON-encoded document.\n\n    :Parameters:\n      - `data`: BSON data\n      - `codec_options`: An instance of\n        :class:`~bson.codec_options.CodecOptions` with user-specified type\n        decoders. If no decoders are found, this method is the same as\n        ``decode_all``.\n      - `fields`: Map of document namespaces where data that needs\n        to be custom decoded lives or None. For example, to custom decode a\n        list of objects in 'field1.subfield1', the specified value should be\n        ``{'field1': {'subfield1': 1}}``. If ``fields``  is an empty map or\n        None, this method is the same as ``decode_all``.\n\n    :Returns:\n      - `document_list`: Single-member list containing the decoded document.\n\n    .. versionadded:: 3.8\n    \"\"\"\n    if not codec_options.type_registry._decoder_map:\n        return decode_all(data, codec_options)\n\n    if not fields:\n        return decode_all(data, codec_options.with_options(type_registry=None))\n\n    # Decode documents for internal use.\n    from bson.raw_bson import RawBSONDocument\n    internal_codec_options = codec_options.with_options(\n        document_class=RawBSONDocument, type_registry=None)\n    _doc = _bson_to_dict(data, internal_codec_options)\n    return [_decode_selective(_doc, fields, codec_options,)]\n\n\ndef decode_iter(data, codec_options=DEFAULT_CODEC_OPTIONS):\n    \"\"\"Decode BSON data to multiple documents as a generator.\n\n    Works similarly to the decode_all function, but yields one document at a\n    time.\n\n    `data` must be a string of concatenated, valid, BSON-encoded\n    documents.\n\n    :Parameters:\n      - `data`: BSON data\n      - `codec_options` (optional): An instance of\n        :class:`~bson.codec_options.CodecOptions`.\n\n    .. versionchanged:: 3.0\n       Replaced `as_class`, `tz_aware`, and `uuid_subtype` options with\n       `codec_options`.\n\n    .. versionadded:: 2.8\n    \"\"\"\n    if not isinstance(codec_options, CodecOptions):\n        raise _CODEC_OPTIONS_TYPE_ERROR\n\n    position = 0\n    end = len(data) - 1\n    while position < end:\n        obj_size = _UNPACK_INT_FROM(data, position)[0]\n        elements = data[position:position + obj_size]\n        position += obj_size\n\n        yield _bson_to_dict(elements, codec_options)\n\n\ndef decode_file_iter(file_obj, codec_options=DEFAULT_CODEC_OPTIONS):\n    \"\"\"Decode bson data from a file to multiple documents as a generator.\n\n    Works similarly to the decode_all function, but reads from the file object\n    in chunks and parses bson in chunks, yielding one document at a time.\n\n    :Parameters:\n      - `file_obj`: A file object containing BSON data.\n      - `codec_options` (optional): An instance of\n        :class:`~bson.codec_options.CodecOptions`.\n\n    .. versionchanged:: 3.0\n       Replaced `as_class`, `tz_aware`, and `uuid_subtype` options with\n       `codec_options`.\n\n    .. versionadded:: 2.8\n    \"\"\"\n    while True:\n        # Read size of next object.\n        size_data = file_obj.read(4)\n        if not size_data:\n            break  # Finished with file normaly.\n        elif len(size_data) != 4:\n            raise InvalidBSON(\"cut off in middle of objsize\")\n        obj_size = _UNPACK_INT_FROM(size_data, 0)[0] - 4\n        elements = size_data + file_obj.read(obj_size)\n        yield _bson_to_dict(elements, codec_options)\n\n\ndef is_valid(bson):\n    \"\"\"Check that the given string represents valid :class:`BSON` data.\n\n    Raises :class:`TypeError` if `bson` is not an instance of\n    :class:`str` (:class:`bytes` in python 3). Returns ``True``\n    if `bson` is valid :class:`BSON`, ``False`` otherwise.\n\n    :Parameters:\n      - `bson`: the data to be validated\n    \"\"\"\n    if not isinstance(bson, bytes):\n        raise TypeError(\"BSON data must be an instance of a subclass of bytes\")\n\n    try:\n        _bson_to_dict(bson, DEFAULT_CODEC_OPTIONS)\n        return True\n    except Exception:\n        return False\n\n\nclass BSON(bytes):\n    \"\"\"BSON (Binary JSON) data.\n\n    .. warning:: Using this class to encode and decode BSON adds a performance\n       cost. For better performance use the module level functions\n       :func:`encode` and :func:`decode` instead.\n    \"\"\"\n\n    @classmethod\n    def encode(cls, document, check_keys=False,\n               codec_options=DEFAULT_CODEC_OPTIONS):\n        \"\"\"Encode a document to a new :class:`BSON` instance.\n\n        A document can be any mapping type (like :class:`dict`).\n\n        Raises :class:`TypeError` if `document` is not a mapping type,\n        or contains keys that are not instances of\n        :class:`basestring` (:class:`str` in python 3). Raises\n        :class:`~bson.errors.InvalidDocument` if `document` cannot be\n        converted to :class:`BSON`.\n\n        :Parameters:\n          - `document`: mapping type representing a document\n          - `check_keys` (optional): check if keys start with '$' or\n            contain '.', raising :class:`~bson.errors.InvalidDocument` in\n            either case\n          - `codec_options` (optional): An instance of\n            :class:`~bson.codec_options.CodecOptions`.\n\n        .. versionchanged:: 3.0\n           Replaced `uuid_subtype` option with `codec_options`.\n        \"\"\"\n        return cls(encode(document, check_keys, codec_options))\n\n    def decode(self, codec_options=DEFAULT_CODEC_OPTIONS):\n        \"\"\"Decode this BSON data.\n\n        By default, returns a BSON document represented as a Python\n        :class:`dict`. To use a different :class:`MutableMapping` class,\n        configure a :class:`~bson.codec_options.CodecOptions`::\n\n            >>> import collections  # From Python standard library.\n            >>> import bson\n            >>> from bson.codec_options import CodecOptions\n            >>> data = bson.BSON.encode({'a': 1})\n            >>> decoded_doc = bson.BSON(data).decode()\n            <type 'dict'>\n            >>> options = CodecOptions(document_class=collections.OrderedDict)\n            >>> decoded_doc = bson.BSON(data).decode(codec_options=options)\n            >>> type(decoded_doc)\n            <class 'collections.OrderedDict'>\n\n        :Parameters:\n          - `codec_options` (optional): An instance of\n            :class:`~bson.codec_options.CodecOptions`.\n\n        .. versionchanged:: 3.0\n           Removed `compile_re` option: PyMongo now always represents BSON\n           regular expressions as :class:`~bson.regex.Regex` objects. Use\n           :meth:`~bson.regex.Regex.try_compile` to attempt to convert from a\n           BSON regular expression to a Python regular expression object.\n\n           Replaced `as_class`, `tz_aware`, and `uuid_subtype` options with\n           `codec_options`.\n\n        .. versionchanged:: 2.7\n           Added `compile_re` option. If set to False, PyMongo represented BSON\n           regular expressions as :class:`~bson.regex.Regex` objects instead of\n           attempting to compile BSON regular expressions as Python native\n           regular expressions, thus preventing errors for some incompatible\n           patterns, see `PYTHON-500`_.\n\n        .. _PYTHON-500: https://jira.mongodb.org/browse/PYTHON-500\n        \"\"\"\n        return decode(self, codec_options)\n\n\ndef has_c():\n    \"\"\"Is the C extension installed?\n    \"\"\"\n    return _USE_C\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/binary.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\nfrom uuid import UUID\n\nfrom bson.py3compat import PY3\n\n\"\"\"Tools for representing BSON binary data.\n\"\"\"\n\nBINARY_SUBTYPE = 0\n\"\"\"BSON binary subtype for binary data.\n\nThis is the default subtype for binary data.\n\"\"\"\n\nFUNCTION_SUBTYPE = 1\n\"\"\"BSON binary subtype for functions.\n\"\"\"\n\nOLD_BINARY_SUBTYPE = 2\n\"\"\"Old BSON binary subtype for binary data.\n\nThis is the old default subtype, the current\ndefault is :data:`BINARY_SUBTYPE`.\n\"\"\"\n\nOLD_UUID_SUBTYPE = 3\n\"\"\"Old BSON binary subtype for a UUID.\n\n:class:`uuid.UUID` instances will automatically be encoded\nby :mod:`bson` using this subtype.\n\n.. versionadded:: 2.1\n\"\"\"\n\nUUID_SUBTYPE = 4\n\"\"\"BSON binary subtype for a UUID.\n\nThis is the new BSON binary subtype for UUIDs. The\ncurrent default is :data:`OLD_UUID_SUBTYPE`.\n\n.. versionchanged:: 2.1\n   Changed to subtype 4.\n\"\"\"\n\nSTANDARD = UUID_SUBTYPE\n\"\"\"The standard UUID representation.\n\n:class:`uuid.UUID` instances will automatically be encoded to\nand decoded from BSON binary, using RFC-4122 byte order with\nbinary subtype :data:`UUID_SUBTYPE`.\n\n.. versionadded:: 3.0\n\"\"\"\n\nPYTHON_LEGACY = OLD_UUID_SUBTYPE\n\"\"\"The Python legacy UUID representation.\n\n:class:`uuid.UUID` instances will automatically be encoded to\nand decoded from BSON binary, using RFC-4122 byte order with\nbinary subtype :data:`OLD_UUID_SUBTYPE`.\n\n.. versionadded:: 3.0\n\"\"\"\n\nJAVA_LEGACY = 5\n\"\"\"The Java legacy UUID representation.\n\n:class:`uuid.UUID` instances will automatically be encoded to\nand decoded from BSON binary subtype :data:`OLD_UUID_SUBTYPE`,\nusing the Java driver's legacy byte order.\n\n.. versionchanged:: 3.6\n  BSON binary subtype 4 is decoded using RFC-4122 byte order.\n.. versionadded:: 2.3\n\"\"\"\n\nCSHARP_LEGACY = 6\n\"\"\"The C#/.net legacy UUID representation.\n\n:class:`uuid.UUID` instances will automatically be encoded to\nand decoded from BSON binary subtype :data:`OLD_UUID_SUBTYPE`,\nusing the C# driver's legacy byte order.\n\n.. versionchanged:: 3.6\n  BSON binary subtype 4 is decoded using RFC-4122 byte order.\n.. versionadded:: 2.3\n\"\"\"\n\nALL_UUID_SUBTYPES = (OLD_UUID_SUBTYPE, UUID_SUBTYPE)\nALL_UUID_REPRESENTATIONS = (STANDARD, PYTHON_LEGACY, JAVA_LEGACY, CSHARP_LEGACY)\nUUID_REPRESENTATION_NAMES = {\n    PYTHON_LEGACY: 'PYTHON_LEGACY',\n    STANDARD: 'STANDARD',\n    JAVA_LEGACY: 'JAVA_LEGACY',\n    CSHARP_LEGACY: 'CSHARP_LEGACY'}\n\nMD5_SUBTYPE = 5\n\"\"\"BSON binary subtype for an MD5 hash.\n\"\"\"\n\nUSER_DEFINED_SUBTYPE = 128\n\"\"\"BSON binary subtype for any user defined structure.\n\"\"\"\n\n\nclass Binary(bytes):\n    \"\"\"Representation of BSON binary data.\n\n    This is necessary because we want to represent Python strings as\n    the BSON string type. We need to wrap binary data so we can tell\n    the difference between what should be considered binary data and\n    what should be considered a string when we encode to BSON.\n\n    Raises TypeError if `data` is not an instance of :class:`bytes`\n    (:class:`str` in python 2) or `subtype` is not an instance of\n    :class:`int`. Raises ValueError if `subtype` is not in [0, 256).\n\n    .. note::\n      In python 3 instances of Binary with subtype 0 will be decoded\n      directly to :class:`bytes`.\n\n    :Parameters:\n      - `data`: the binary data to represent. Can be any bytes-like type\n        that implements the buffer protocol.\n      - `subtype` (optional): the `binary subtype\n        <http://bsonspec.org/#/specification>`_\n        to use\n\n    .. versionchanged:: 3.9\n      Support any bytes-like type that implements the buffer protocol.\n    \"\"\"\n\n    _type_marker = 5\n\n    def __new__(cls, data, subtype=BINARY_SUBTYPE):\n        if not isinstance(subtype, int):\n            raise TypeError(\"subtype must be an instance of int\")\n        if subtype >= 256 or subtype < 0:\n            raise ValueError(\"subtype must be contained in [0, 256)\")\n        # Support any type that implements the buffer protocol.\n        self = bytes.__new__(cls, memoryview(data).tobytes())\n        self.__subtype = subtype\n        return self\n\n    @property\n    def subtype(self):\n        \"\"\"Subtype of this binary data.\n        \"\"\"\n        return self.__subtype\n\n    def __getnewargs__(self):\n        # Work around http://bugs.python.org/issue7382\n        data = super(Binary, self).__getnewargs__()[0]\n        if PY3 and not isinstance(data, bytes):\n            data = data.encode('latin-1')\n        return data, self.__subtype\n\n    def __eq__(self, other):\n        if isinstance(other, Binary):\n            return ((self.__subtype, bytes(self)) ==\n                    (other.subtype, bytes(other)))\n        # We don't return NotImplemented here because if we did then\n        # Binary(\"foo\") == \"foo\" would return True, since Binary is a\n        # subclass of str...\n        return False\n\n    def __hash__(self):\n        return super(Binary, self).__hash__() ^ hash(self.__subtype)\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __repr__(self):\n        return \"Binary(%s, %s)\" % (bytes.__repr__(self), self.__subtype)\n\n\nclass UUIDLegacy(Binary):\n    \"\"\"UUID wrapper to support working with UUIDs stored as PYTHON_LEGACY.\n\n    .. doctest::\n\n      >>> import uuid\n      >>> from bson.binary import Binary, UUIDLegacy, STANDARD\n      >>> from bson.codec_options import CodecOptions\n      >>> my_uuid = uuid.uuid4()\n      >>> coll = db.get_collection('test',\n      ...                          CodecOptions(uuid_representation=STANDARD))\n      >>> coll.insert_one({'uuid': Binary(my_uuid.bytes, 3)}).inserted_id\n      ObjectId('...')\n      >>> coll.count_documents({'uuid': my_uuid})\n      0\n      >>> coll.count_documents({'uuid': UUIDLegacy(my_uuid)})\n      1\n      >>> coll.find({'uuid': UUIDLegacy(my_uuid)})[0]['uuid']\n      UUID('...')\n      >>>\n      >>> # Convert from subtype 3 to subtype 4\n      >>> doc = coll.find_one({'uuid': UUIDLegacy(my_uuid)})\n      >>> coll.replace_one({\"_id\": doc[\"_id\"]}, doc).matched_count\n      1\n      >>> coll.count_documents({'uuid': UUIDLegacy(my_uuid)})\n      0\n      >>> coll.count_documents({'uuid': {'$in': [UUIDLegacy(my_uuid), my_uuid]}})\n      1\n      >>> coll.find_one({'uuid': my_uuid})['uuid']\n      UUID('...')\n\n    Raises TypeError if `obj` is not an instance of :class:`~uuid.UUID`.\n\n    :Parameters:\n      - `obj`: An instance of :class:`~uuid.UUID`.\n    \"\"\"\n\n    def __new__(cls, obj):\n        if not isinstance(obj, UUID):\n            raise TypeError(\"obj must be an instance of uuid.UUID\")\n        self = Binary.__new__(cls, obj.bytes, OLD_UUID_SUBTYPE)\n        self.__uuid = obj\n        return self\n\n    def __getnewargs__(self):\n        # Support copy and deepcopy\n        return (self.__uuid,)\n\n    @property\n    def uuid(self):\n        \"\"\"UUID instance wrapped by this UUIDLegacy instance.\n        \"\"\"\n        return self.__uuid\n\n    def __repr__(self):\n        return \"UUIDLegacy('%s')\" % self.__uuid\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/code.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for representing JavaScript code in BSON.\n\"\"\"\n\nfrom bson.py3compat import abc, string_type, PY3, text_type\n\n\nclass Code(str):\n    \"\"\"BSON's JavaScript code type.\n\n    Raises :class:`TypeError` if `code` is not an instance of\n    :class:`basestring` (:class:`str` in python 3) or `scope`\n    is not ``None`` or an instance of :class:`dict`.\n\n    Scope variables can be set by passing a dictionary as the `scope`\n    argument or by using keyword arguments. If a variable is set as a\n    keyword argument it will override any setting for that variable in\n    the `scope` dictionary.\n\n    :Parameters:\n      - `code`: A string containing JavaScript code to be evaluated or another\n        instance of Code. In the latter case, the scope of `code` becomes this\n        Code's :attr:`scope`.\n      - `scope` (optional): dictionary representing the scope in which\n        `code` should be evaluated - a mapping from identifiers (as\n        strings) to values. Defaults to ``None``. This is applied after any\n        scope associated with a given `code` above.\n      - `**kwargs` (optional): scope variables can also be passed as\n        keyword arguments. These are applied after `scope` and `code`.\n\n    .. versionchanged:: 3.4\n      The default value for :attr:`scope` is ``None`` instead of ``{}``.\n\n    \"\"\"\n\n    _type_marker = 13\n\n    def __new__(cls, code, scope=None, **kwargs):\n        if not isinstance(code, string_type):\n            raise TypeError(\"code must be an \"\n                            \"instance of %s\" % (string_type.__name__))\n\n        if not PY3 and isinstance(code, text_type):\n            self = str.__new__(cls, code.encode('utf8'))\n        else:\n            self = str.__new__(cls, code)\n\n        try:\n            self.__scope = code.scope\n        except AttributeError:\n            self.__scope = None\n\n        if scope is not None:\n            if not isinstance(scope, abc.Mapping):\n                raise TypeError(\"scope must be an instance of dict\")\n            if self.__scope is not None:\n                self.__scope.update(scope)\n            else:\n                self.__scope = scope\n\n        if kwargs:\n            if self.__scope is not None:\n                self.__scope.update(kwargs)\n            else:\n                self.__scope = kwargs\n\n        return self\n\n    @property\n    def scope(self):\n        \"\"\"Scope dictionary for this instance or ``None``.\n        \"\"\"\n        return self.__scope\n\n    def __repr__(self):\n        return \"Code(%s, %r)\" % (str.__repr__(self), self.__scope)\n\n    def __eq__(self, other):\n        if isinstance(other, Code):\n            return (self.__scope, str(self)) == (other.__scope, str(other))\n        return False\n\n    __hash__ = None\n\n    def __ne__(self, other):\n        return not self == other\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/codec_options.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for specifying BSON codec options.\"\"\"\n\nimport datetime\n\nfrom abc import abstractmethod\nfrom collections import namedtuple\n\nfrom bson.py3compat import ABC, abc, abstractproperty, string_type\n\nfrom bson.binary import (ALL_UUID_REPRESENTATIONS,\n                         PYTHON_LEGACY,\n                         UUID_REPRESENTATION_NAMES)\n\n\n_RAW_BSON_DOCUMENT_MARKER = 101\n\n\ndef _raw_document_class(document_class):\n    \"\"\"Determine if a document_class is a RawBSONDocument class.\"\"\"\n    marker = getattr(document_class, '_type_marker', None)\n    return marker == _RAW_BSON_DOCUMENT_MARKER\n\n\nclass TypeEncoder(ABC):\n    \"\"\"Base class for defining type codec classes which describe how a\n    custom type can be transformed to one of the types BSON understands.\n\n    Codec classes must implement the ``python_type`` attribute, and the\n    ``transform_python`` method to support encoding.\n\n    See :ref:`custom-type-type-codec` documentation for an example.\n    \"\"\"\n    @abstractproperty\n    def python_type(self):\n        \"\"\"The Python type to be converted into something serializable.\"\"\"\n        pass\n\n    @abstractmethod\n    def transform_python(self, value):\n        \"\"\"Convert the given Python object into something serializable.\"\"\"\n        pass\n\n\nclass TypeDecoder(ABC):\n    \"\"\"Base class for defining type codec classes which describe how a\n    BSON type can be transformed to a custom type.\n\n    Codec classes must implement the ``bson_type`` attribute, and the\n    ``transform_bson`` method to support decoding.\n\n    See :ref:`custom-type-type-codec` documentation for an example.\n    \"\"\"\n    @abstractproperty\n    def bson_type(self):\n        \"\"\"The BSON type to be converted into our own type.\"\"\"\n        pass\n\n    @abstractmethod\n    def transform_bson(self, value):\n        \"\"\"Convert the given BSON value into our own type.\"\"\"\n        pass\n\n\nclass TypeCodec(TypeEncoder, TypeDecoder):\n    \"\"\"Base class for defining type codec classes which describe how a\n    custom type can be transformed to/from one of the types :mod:`bson`\n    can already encode/decode.\n\n    Codec classes must implement the ``python_type`` attribute, and the\n    ``transform_python`` method to support encoding, as well as the\n    ``bson_type`` attribute, and the ``transform_bson`` method to support\n    decoding.\n\n    See :ref:`custom-type-type-codec` documentation for an example.\n    \"\"\"\n    pass\n\n\nclass TypeRegistry(object):\n    \"\"\"Encapsulates type codecs used in encoding and / or decoding BSON, as\n    well as the fallback encoder. Type registries cannot be modified after\n    instantiation.\n\n    ``TypeRegistry`` can be initialized with an iterable of type codecs, and\n    a callable for the fallback encoder::\n\n      >>> from bson.codec_options import TypeRegistry\n      >>> type_registry = TypeRegistry([Codec1, Codec2, Codec3, ...],\n      ...                              fallback_encoder)\n\n    See :ref:`custom-type-type-registry` documentation for an example.\n\n    :Parameters:\n      - `type_codecs` (optional): iterable of type codec instances. If\n        ``type_codecs`` contains multiple codecs that transform a single\n        python or BSON type, the transformation specified by the type codec\n        occurring last prevails. A TypeError will be raised if one or more\n        type codecs modify the encoding behavior of a built-in :mod:`bson`\n        type.\n      - `fallback_encoder` (optional): callable that accepts a single,\n        unencodable python value and transforms it into a type that\n        :mod:`bson` can encode. See :ref:`fallback-encoder-callable`\n        documentation for an example.\n    \"\"\"\n    def __init__(self, type_codecs=None, fallback_encoder=None):\n        self.__type_codecs = list(type_codecs or [])\n        self._fallback_encoder = fallback_encoder\n        self._encoder_map = {}\n        self._decoder_map = {}\n\n        if self._fallback_encoder is not None:\n            if not callable(fallback_encoder):\n                raise TypeError(\"fallback_encoder %r is not a callable\" % (\n                    fallback_encoder))\n\n        for codec in self.__type_codecs:\n            is_valid_codec = False\n            if isinstance(codec, TypeEncoder):\n                self._validate_type_encoder(codec)\n                is_valid_codec = True\n                self._encoder_map[codec.python_type] = codec.transform_python\n            if isinstance(codec, TypeDecoder):\n                is_valid_codec = True\n                self._decoder_map[codec.bson_type] = codec.transform_bson\n            if not is_valid_codec:\n                raise TypeError(\n                    \"Expected an instance of %s, %s, or %s, got %r instead\" % (\n                        TypeEncoder.__name__, TypeDecoder.__name__,\n                        TypeCodec.__name__, codec))\n\n    def _validate_type_encoder(self, codec):\n        from bson import _BUILT_IN_TYPES\n        for pytype in _BUILT_IN_TYPES:\n            if issubclass(codec.python_type, pytype):\n                err_msg = (\"TypeEncoders cannot change how built-in types are \"\n                           \"encoded (encoder %s transforms type %s)\" %\n                           (codec, pytype))\n                raise TypeError(err_msg)\n\n    def __repr__(self):\n        return ('%s(type_codecs=%r, fallback_encoder=%r)' % (\n            self.__class__.__name__, self.__type_codecs,\n            self._fallback_encoder))\n\n    def __eq__(self, other):\n        if not isinstance(other, type(self)):\n            return NotImplemented\n        return ((self._decoder_map == other._decoder_map) and\n                (self._encoder_map == other._encoder_map) and\n                (self._fallback_encoder == other._fallback_encoder))\n\n\n_options_base = namedtuple(\n    'CodecOptions',\n    ('document_class', 'tz_aware', 'uuid_representation',\n     'unicode_decode_error_handler', 'tzinfo', 'type_registry'))\n\n\nclass CodecOptions(_options_base):\n    \"\"\"Encapsulates options used encoding and / or decoding BSON.\n\n    The `document_class` option is used to define a custom type for use\n    decoding BSON documents. Access to the underlying raw BSON bytes for\n    a document is available using the :class:`~bson.raw_bson.RawBSONDocument`\n    type::\n\n      >>> from bson.raw_bson import RawBSONDocument\n      >>> from bson.codec_options import CodecOptions\n      >>> codec_options = CodecOptions(document_class=RawBSONDocument)\n      >>> coll = db.get_collection('test', codec_options=codec_options)\n      >>> doc = coll.find_one()\n      >>> doc.raw\n      '\\\\x16\\\\x00\\\\x00\\\\x00\\\\x07_id\\\\x00[0\\\\x165\\\\x91\\\\x10\\\\xea\\\\x14\\\\xe8\\\\xc5\\\\x8b\\\\x93\\\\x00'\n\n    The document class can be any type that inherits from\n    :class:`~collections.MutableMapping`::\n\n      >>> class AttributeDict(dict):\n      ...     # A dict that supports attribute access.\n      ...     def __getattr__(self, key):\n      ...         return self[key]\n      ...     def __setattr__(self, key, value):\n      ...         self[key] = value\n      ...\n      >>> codec_options = CodecOptions(document_class=AttributeDict)\n      >>> coll = db.get_collection('test', codec_options=codec_options)\n      >>> doc = coll.find_one()\n      >>> doc._id\n      ObjectId('5b3016359110ea14e8c58b93')\n\n    See :doc:`/examples/datetimes` for examples using the `tz_aware` and\n    `tzinfo` options.\n\n    See :class:`~bson.binary.UUIDLegacy` for examples using the\n    `uuid_representation` option.\n\n    :Parameters:\n      - `document_class`: BSON documents returned in queries will be decoded\n        to an instance of this class. Must be a subclass of\n        :class:`~collections.MutableMapping`. Defaults to :class:`dict`.\n      - `tz_aware`: If ``True``, BSON datetimes will be decoded to timezone\n        aware instances of :class:`~datetime.datetime`. Otherwise they will be\n        naive. Defaults to ``False``.\n      - `uuid_representation`: The BSON representation to use when encoding\n        and decoding instances of :class:`~uuid.UUID`. Defaults to\n        :data:`~bson.binary.PYTHON_LEGACY`.\n      - `unicode_decode_error_handler`: The error handler to apply when\n        a Unicode-related error occurs during BSON decoding that would\n        otherwise raise :exc:`UnicodeDecodeError`. Valid options include\n        'strict', 'replace', and 'ignore'. Defaults to 'strict'.\n      - `tzinfo`: A :class:`~datetime.tzinfo` subclass that specifies the\n        timezone to/from which :class:`~datetime.datetime` objects should be\n        encoded/decoded.\n      - `type_registry`: Instance of :class:`TypeRegistry` used to customize\n        encoding and decoding behavior.\n\n    .. versionadded:: 3.8\n       `type_registry` attribute.\n\n    .. warning:: Care must be taken when changing\n       `unicode_decode_error_handler` from its default value ('strict').\n       The 'replace' and 'ignore' modes should not be used when documents\n       retrieved from the server will be modified in the client application\n       and stored back to the server.\n    \"\"\"\n\n    def __new__(cls, document_class=dict,\n                tz_aware=False, uuid_representation=PYTHON_LEGACY,\n                unicode_decode_error_handler=\"strict\",\n                tzinfo=None, type_registry=None):\n        if not (issubclass(document_class, abc.MutableMapping) or\n                _raw_document_class(document_class)):\n            raise TypeError(\"document_class must be dict, bson.son.SON, \"\n                            \"bson.raw_bson.RawBSONDocument, or a \"\n                            \"sublass of collections.MutableMapping\")\n        if not isinstance(tz_aware, bool):\n            raise TypeError(\"tz_aware must be True or False\")\n        if uuid_representation not in ALL_UUID_REPRESENTATIONS:\n            raise ValueError(\"uuid_representation must be a value \"\n                             \"from bson.binary.ALL_UUID_REPRESENTATIONS\")\n        if not isinstance(unicode_decode_error_handler, (string_type, None)):\n            raise ValueError(\"unicode_decode_error_handler must be a string \"\n                             \"or None\")\n        if tzinfo is not None:\n            if not isinstance(tzinfo, datetime.tzinfo):\n                raise TypeError(\n                    \"tzinfo must be an instance of datetime.tzinfo\")\n            if not tz_aware:\n                raise ValueError(\n                    \"cannot specify tzinfo without also setting tz_aware=True\")\n\n        type_registry = type_registry or TypeRegistry()\n\n        if not isinstance(type_registry, TypeRegistry):\n            raise TypeError(\"type_registry must be an instance of TypeRegistry\")\n\n        return tuple.__new__(\n            cls, (document_class, tz_aware, uuid_representation,\n                  unicode_decode_error_handler, tzinfo, type_registry))\n\n    def _arguments_repr(self):\n        \"\"\"Representation of the arguments used to create this object.\"\"\"\n        document_class_repr = (\n            'dict' if self.document_class is dict\n            else repr(self.document_class))\n\n        uuid_rep_repr = UUID_REPRESENTATION_NAMES.get(self.uuid_representation,\n                                                      self.uuid_representation)\n\n        return ('document_class=%s, tz_aware=%r, uuid_representation=%s, '\n                'unicode_decode_error_handler=%r, tzinfo=%r, '\n                'type_registry=%r' %\n                (document_class_repr, self.tz_aware, uuid_rep_repr,\n                 self.unicode_decode_error_handler, self.tzinfo,\n                 self.type_registry))\n\n    def __repr__(self):\n        return '%s(%s)' % (self.__class__.__name__, self._arguments_repr())\n\n    def with_options(self, **kwargs):\n        \"\"\"Make a copy of this CodecOptions, overriding some options::\n\n            >>> from bson.codec_options import DEFAULT_CODEC_OPTIONS\n            >>> DEFAULT_CODEC_OPTIONS.tz_aware\n            False\n            >>> options = DEFAULT_CODEC_OPTIONS.with_options(tz_aware=True)\n            >>> options.tz_aware\n            True\n\n        .. versionadded:: 3.5\n        \"\"\"\n        return CodecOptions(\n            kwargs.get('document_class', self.document_class),\n            kwargs.get('tz_aware', self.tz_aware),\n            kwargs.get('uuid_representation', self.uuid_representation),\n            kwargs.get('unicode_decode_error_handler',\n                       self.unicode_decode_error_handler),\n            kwargs.get('tzinfo', self.tzinfo),\n            kwargs.get('type_registry', self.type_registry)\n        )\n\n\nDEFAULT_CODEC_OPTIONS = CodecOptions()\n\n\ndef _parse_codec_options(options):\n    \"\"\"Parse BSON codec options.\"\"\"\n    return CodecOptions(\n        document_class=options.get(\n            'document_class', DEFAULT_CODEC_OPTIONS.document_class),\n        tz_aware=options.get(\n            'tz_aware', DEFAULT_CODEC_OPTIONS.tz_aware),\n        uuid_representation=options.get(\n            'uuidrepresentation', DEFAULT_CODEC_OPTIONS.uuid_representation),\n        unicode_decode_error_handler=options.get(\n            'unicode_decode_error_handler',\n            DEFAULT_CODEC_OPTIONS.unicode_decode_error_handler),\n        tzinfo=options.get('tzinfo', DEFAULT_CODEC_OPTIONS.tzinfo),\n        type_registry=options.get(\n            'type_registry', DEFAULT_CODEC_OPTIONS.type_registry))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/dbref.py",
    "content": "# Copyright 2009-2015 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for manipulating DBRefs (references to MongoDB documents).\"\"\"\n\nfrom copy import deepcopy\n\nfrom bson.py3compat import iteritems, string_type\nfrom bson.son import SON\n\n\nclass DBRef(object):\n    \"\"\"A reference to a document stored in MongoDB.\n    \"\"\"\n\n    # DBRef isn't actually a BSON \"type\" so this number was arbitrarily chosen.\n    _type_marker = 100\n\n    def __init__(self, collection, id, database=None, _extra={}, **kwargs):\n        \"\"\"Initialize a new :class:`DBRef`.\n\n        Raises :class:`TypeError` if `collection` or `database` is not\n        an instance of :class:`basestring` (:class:`str` in python 3).\n        `database` is optional and allows references to documents to work\n        across databases. Any additional keyword arguments will create\n        additional fields in the resultant embedded document.\n\n        :Parameters:\n          - `collection`: name of the collection the document is stored in\n          - `id`: the value of the document's ``\"_id\"`` field\n          - `database` (optional): name of the database to reference\n          - `**kwargs` (optional): additional keyword arguments will\n            create additional, custom fields\n\n        .. mongodoc:: dbrefs\n        \"\"\"\n        if not isinstance(collection, string_type):\n            raise TypeError(\"collection must be an \"\n                            \"instance of %s\" % string_type.__name__)\n        if database is not None and not isinstance(database, string_type):\n            raise TypeError(\"database must be an \"\n                            \"instance of %s\" % string_type.__name__)\n\n        self.__collection = collection\n        self.__id = id\n        self.__database = database\n        kwargs.update(_extra)\n        self.__kwargs = kwargs\n\n    @property\n    def collection(self):\n        \"\"\"Get the name of this DBRef's collection as unicode.\n        \"\"\"\n        return self.__collection\n\n    @property\n    def id(self):\n        \"\"\"Get this DBRef's _id.\n        \"\"\"\n        return self.__id\n\n    @property\n    def database(self):\n        \"\"\"Get the name of this DBRef's database.\n\n        Returns None if this DBRef doesn't specify a database.\n        \"\"\"\n        return self.__database\n\n    def __getattr__(self, key):\n        try:\n            return self.__kwargs[key]\n        except KeyError:\n            raise AttributeError(key)\n\n    # Have to provide __setstate__ to avoid\n    # infinite recursion since we override\n    # __getattr__.\n    def __setstate__(self, state):\n        self.__dict__.update(state)\n\n    def as_doc(self):\n        \"\"\"Get the SON document representation of this DBRef.\n\n        Generally not needed by application developers\n        \"\"\"\n        doc = SON([(\"$ref\", self.collection),\n                   (\"$id\", self.id)])\n        if self.database is not None:\n            doc[\"$db\"] = self.database\n        doc.update(self.__kwargs)\n        return doc\n\n    def __repr__(self):\n        extra = \"\".join([\", %s=%r\" % (k, v)\n                         for k, v in iteritems(self.__kwargs)])\n        if self.database is None:\n            return \"DBRef(%r, %r%s)\" % (self.collection, self.id, extra)\n        return \"DBRef(%r, %r, %r%s)\" % (self.collection, self.id,\n                                        self.database, extra)\n\n    def __eq__(self, other):\n        if isinstance(other, DBRef):\n            us = (self.__database, self.__collection,\n                  self.__id, self.__kwargs)\n            them = (other.__database, other.__collection,\n                    other.__id, other.__kwargs)\n            return us == them\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        \"\"\"Get a hash value for this :class:`DBRef`.\"\"\"\n        return hash((self.__collection, self.__id, self.__database,\n                     tuple(sorted(self.__kwargs.items()))))\n\n    def __deepcopy__(self, memo):\n        \"\"\"Support function for `copy.deepcopy()`.\"\"\"\n        return DBRef(deepcopy(self.__collection, memo),\n                     deepcopy(self.__id, memo),\n                     deepcopy(self.__database, memo),\n                     deepcopy(self.__kwargs, memo))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/decimal128.py",
    "content": "# Copyright 2016-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for working with the BSON decimal128 type.\n\n.. versionadded:: 3.4\n\n.. note:: The Decimal128 BSON type requires MongoDB 3.4+.\n\"\"\"\n\nimport decimal\nimport struct\nimport sys\n\nfrom bson.py3compat import (PY3 as _PY3,\n                            string_type as _string_type)\n\n\nif _PY3:\n    _from_bytes = int.from_bytes  # pylint: disable=no-member, invalid-name\nelse:\n    import binascii\n    def _from_bytes(value, dummy, _int=int, _hexlify=binascii.hexlify):\n        \"An implementation of int.from_bytes for python 2.x.\"\n        return _int(_hexlify(value), 16)\n\n\n_PACK_64 = struct.Struct(\"<Q\").pack\n_UNPACK_64 = struct.Struct(\"<Q\").unpack\n\n_EXPONENT_MASK = 3 << 61\n_EXPONENT_BIAS = 6176\n_EXPONENT_MAX = 6144\n_EXPONENT_MIN = -6143\n_MAX_DIGITS = 34\n\n_INF = 0x7800000000000000\n_NAN = 0x7c00000000000000\n_SNAN = 0x7e00000000000000\n_SIGN = 0x8000000000000000\n\n_NINF = (_INF + _SIGN, 0)\n_PINF = (_INF, 0)\n_NNAN = (_NAN + _SIGN, 0)\n_PNAN = (_NAN, 0)\n_NSNAN = (_SNAN + _SIGN, 0)\n_PSNAN = (_SNAN, 0)\n\n_CTX_OPTIONS = {\n    'prec': _MAX_DIGITS,\n    'rounding': decimal.ROUND_HALF_EVEN,\n    'Emin': _EXPONENT_MIN,\n    'Emax': _EXPONENT_MAX,\n    'capitals': 1,\n    'flags': [],\n    'traps': [decimal.InvalidOperation,\n              decimal.Overflow,\n              decimal.Inexact]\n}\n\ntry:\n    # Python >= 3.3, cdecimal\n    decimal.Context(clamp=1)  # pylint: disable=unexpected-keyword-arg\n    _CTX_OPTIONS['clamp'] = 1\nexcept TypeError:\n    # Python < 3.3\n    _CTX_OPTIONS['_clamp'] = 1\n\n_DEC128_CTX = decimal.Context(**_CTX_OPTIONS.copy())\n\n\ndef create_decimal128_context():\n    \"\"\"Returns an instance of :class:`decimal.Context` appropriate\n    for working with IEEE-754 128-bit decimal floating point values.\n    \"\"\"\n    opts = _CTX_OPTIONS.copy()\n    opts['traps'] = []\n    return decimal.Context(**opts)\n\n\ndef _decimal_to_128(value):\n    \"\"\"Converts a decimal.Decimal to BID (high bits, low bits).\n\n    :Parameters:\n      - `value`: An instance of decimal.Decimal\n    \"\"\"\n    with decimal.localcontext(_DEC128_CTX) as ctx:\n        value = ctx.create_decimal(value)\n\n    if value.is_infinite():\n        return _NINF if value.is_signed() else _PINF\n\n    sign, digits, exponent = value.as_tuple()\n\n    if value.is_nan():\n        if digits:\n            raise ValueError(\"NaN with debug payload is not supported\")\n        if value.is_snan():\n            return _NSNAN if value.is_signed() else _PSNAN\n        return _NNAN if value.is_signed() else _PNAN\n\n    significand = int(\"\".join([str(digit) for digit in digits]))\n    bit_length = significand.bit_length()\n\n    high = 0\n    low = 0\n    for i in range(min(64, bit_length)):\n        if significand & (1 << i):\n            low |= 1 << i\n\n    for i in range(64, bit_length):\n        if significand & (1 << i):\n            high |= 1 << (i - 64)\n\n    biased_exponent = exponent + _EXPONENT_BIAS\n\n    if high >> 49 == 1:\n        high = high & 0x7fffffffffff\n        high |= _EXPONENT_MASK\n        high |= (biased_exponent & 0x3fff) << 47\n    else:\n        high |= biased_exponent << 49\n\n    if sign:\n        high |= _SIGN\n\n    return high, low\n\n\nclass Decimal128(object):\n    \"\"\"BSON Decimal128 type::\n\n      >>> Decimal128(Decimal(\"0.0005\"))\n      Decimal128('0.0005')\n      >>> Decimal128(\"0.0005\")\n      Decimal128('0.0005')\n      >>> Decimal128((3474527112516337664, 5))\n      Decimal128('0.0005')\n\n    :Parameters:\n      - `value`: An instance of :class:`decimal.Decimal`, string, or tuple of\n        (high bits, low bits) from Binary Integer Decimal (BID) format.\n\n    .. note:: :class:`~Decimal128` uses an instance of :class:`decimal.Context`\n      configured for IEEE-754 Decimal128 when validating parameters.\n      Signals like :class:`decimal.InvalidOperation`, :class:`decimal.Inexact`,\n      and :class:`decimal.Overflow` are trapped and raised as exceptions::\n\n        >>> Decimal128(\".13.1\")\n        Traceback (most recent call last):\n          File \"<stdin>\", line 1, in <module>\n          ...\n        decimal.InvalidOperation: [<class 'decimal.ConversionSyntax'>]\n        >>>\n        >>> Decimal128(\"1E-6177\")\n        Traceback (most recent call last):\n          File \"<stdin>\", line 1, in <module>\n          ...\n        decimal.Inexact: [<class 'decimal.Inexact'>]\n        >>>\n        >>> Decimal128(\"1E6145\")\n        Traceback (most recent call last):\n          File \"<stdin>\", line 1, in <module>\n          ...\n        decimal.Overflow: [<class 'decimal.Overflow'>, <class 'decimal.Rounded'>]\n\n      To ensure the result of a calculation can always be stored as BSON\n      Decimal128 use the context returned by\n      :func:`create_decimal128_context`::\n\n        >>> import decimal\n        >>> decimal128_ctx = create_decimal128_context()\n        >>> with decimal.localcontext(decimal128_ctx) as ctx:\n        ...     Decimal128(ctx.create_decimal(\".13.3\"))\n        ...\n        Decimal128('NaN')\n        >>>\n        >>> with decimal.localcontext(decimal128_ctx) as ctx:\n        ...     Decimal128(ctx.create_decimal(\"1E-6177\"))\n        ...\n        Decimal128('0E-6176')\n        >>>\n        >>> with decimal.localcontext(DECIMAL128_CTX) as ctx:\n        ...     Decimal128(ctx.create_decimal(\"1E6145\"))\n        ...\n        Decimal128('Infinity')\n\n      To match the behavior of MongoDB's Decimal128 implementation\n      str(Decimal(value)) may not match str(Decimal128(value)) for NaN values::\n\n        >>> Decimal128(Decimal('NaN'))\n        Decimal128('NaN')\n        >>> Decimal128(Decimal('-NaN'))\n        Decimal128('NaN')\n        >>> Decimal128(Decimal('sNaN'))\n        Decimal128('NaN')\n        >>> Decimal128(Decimal('-sNaN'))\n        Decimal128('NaN')\n\n      However, :meth:`~Decimal128.to_decimal` will return the exact value::\n\n        >>> Decimal128(Decimal('NaN')).to_decimal()\n        Decimal('NaN')\n        >>> Decimal128(Decimal('-NaN')).to_decimal()\n        Decimal('-NaN')\n        >>> Decimal128(Decimal('sNaN')).to_decimal()\n        Decimal('sNaN')\n        >>> Decimal128(Decimal('-sNaN')).to_decimal()\n        Decimal('-sNaN')\n\n      Two instances of :class:`Decimal128` compare equal if their Binary\n      Integer Decimal encodings are equal::\n\n        >>> Decimal128('NaN') == Decimal128('NaN')\n        True\n        >>> Decimal128('NaN').bid == Decimal128('NaN').bid\n        True\n\n      This differs from :class:`decimal.Decimal` comparisons for NaN::\n\n        >>> Decimal('NaN') == Decimal('NaN')\n        False\n    \"\"\"\n    __slots__ = ('__high', '__low')\n\n    _type_marker = 19\n\n    def __init__(self, value):\n        if isinstance(value, (_string_type, decimal.Decimal)):\n            self.__high, self.__low = _decimal_to_128(value)\n        elif isinstance(value, (list, tuple)):\n            if len(value) != 2:\n                raise ValueError('Invalid size for creation of Decimal128 '\n                                 'from list or tuple. Must have exactly 2 '\n                                 'elements.')\n            self.__high, self.__low = value\n        else:\n            raise TypeError(\"Cannot convert %r to Decimal128\" % (value,))\n\n    def to_decimal(self):\n        \"\"\"Returns an instance of :class:`decimal.Decimal` for this\n        :class:`Decimal128`.\n        \"\"\"\n        high = self.__high\n        low = self.__low\n        sign = 1 if (high & _SIGN) else 0\n\n        if (high & _SNAN) == _SNAN:\n            return decimal.Decimal((sign, (), 'N'))\n        elif (high & _NAN) == _NAN:\n            return decimal.Decimal((sign, (), 'n'))\n        elif (high & _INF) == _INF:\n            return decimal.Decimal((sign, (), 'F'))\n\n        if (high & _EXPONENT_MASK) == _EXPONENT_MASK:\n            exponent = ((high & 0x1fffe00000000000) >> 47) - _EXPONENT_BIAS\n            return decimal.Decimal((sign, (0,), exponent))\n        else:\n            exponent = ((high & 0x7fff800000000000) >> 49) - _EXPONENT_BIAS\n\n        arr = bytearray(15)\n        mask = 0x00000000000000ff\n        for i in range(14, 6, -1):\n            arr[i] = (low & mask) >> ((14 - i) << 3)\n            mask = mask << 8\n\n        mask = 0x00000000000000ff\n        for i in range(6, 0, -1):\n            arr[i] = (high & mask) >> ((6 - i) << 3)\n            mask = mask << 8\n\n        mask = 0x0001000000000000\n        arr[0] = (high & mask) >> 48\n\n        # cdecimal only accepts a tuple for digits.\n        digits = tuple(\n            int(digit) for digit in str(_from_bytes(arr, 'big')))\n\n        with decimal.localcontext(_DEC128_CTX) as ctx:\n            return ctx.create_decimal((sign, digits, exponent))\n\n    @classmethod\n    def from_bid(cls, value):\n        \"\"\"Create an instance of :class:`Decimal128` from Binary Integer\n        Decimal string.\n\n        :Parameters:\n          - `value`: 16 byte string (128-bit IEEE 754-2008 decimal floating\n            point in Binary Integer Decimal (BID) format).\n        \"\"\"\n        if not isinstance(value, bytes):\n            raise TypeError(\"value must be an instance of bytes\")\n        if len(value) != 16:\n            raise ValueError(\"value must be exactly 16 bytes\")\n        return cls((_UNPACK_64(value[8:])[0], _UNPACK_64(value[:8])[0]))\n\n    @property\n    def bid(self):\n        \"\"\"The Binary Integer Decimal (BID) encoding of this instance.\"\"\"\n        return _PACK_64(self.__low) + _PACK_64(self.__high)\n\n    def __str__(self):\n        dec = self.to_decimal()\n        if dec.is_nan():\n            # Required by the drivers spec to match MongoDB behavior.\n            return \"NaN\"\n        return str(dec)\n\n    def __repr__(self):\n        return \"Decimal128('%s')\" % (str(self),)\n\n    def __setstate__(self, value):\n        self.__high, self.__low = value\n\n    def __getstate__(self):\n        return self.__high, self.__low\n\n    def __eq__(self, other):\n        if isinstance(other, Decimal128):\n            return self.bid == other.bid\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/errors.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Exceptions raised by the BSON package.\"\"\"\n\n\nclass BSONError(Exception):\n    \"\"\"Base class for all BSON exceptions.\n    \"\"\"\n\n\nclass InvalidBSON(BSONError):\n    \"\"\"Raised when trying to create a BSON object from invalid data.\n    \"\"\"\n\n\nclass InvalidStringData(BSONError):\n    \"\"\"Raised when trying to encode a string containing non-UTF8 data.\n    \"\"\"\n\n\nclass InvalidDocument(BSONError):\n    \"\"\"Raised when trying to create a BSON object from an invalid document.\n    \"\"\"\n\n\nclass InvalidId(BSONError):\n    \"\"\"Raised when trying to create an ObjectId from invalid data.\n    \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/int64.py",
    "content": "# Copyright 2014-2015 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"A BSON wrapper for long (int in python3)\"\"\"\n\nfrom bson.py3compat import PY3\n\nif PY3:\n    long = int\n\n\nclass Int64(long):\n    \"\"\"Representation of the BSON int64 type.\n\n    This is necessary because every integral number is an :class:`int` in\n    Python 3. Small integral numbers are encoded to BSON int32 by default,\n    but Int64 numbers will always be encoded to BSON int64.\n\n    :Parameters:\n      - `value`: the numeric value to represent\n    \"\"\"\n\n    _type_marker = 18\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/json_util.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for using Python's :mod:`json` module with BSON documents.\n\nThis module provides two helper methods `dumps` and `loads` that wrap the\nnative :mod:`json` methods and provide explicit BSON conversion to and from\nJSON. :class:`~bson.json_util.JSONOptions` provides a way to control how JSON\nis emitted and parsed, with the default being the legacy PyMongo format.\n:mod:`~bson.json_util` can also generate Canonical or Relaxed `Extended JSON`_\nwhen :const:`CANONICAL_JSON_OPTIONS` or :const:`RELAXED_JSON_OPTIONS` is\nprovided, respectively.\n\n.. _Extended JSON: https://github.com/mongodb/specifications/blob/master/source/extended-json.rst\n\nExample usage (deserialization):\n\n.. doctest::\n\n   >>> from bson.json_util import loads\n   >>> loads('[{\"foo\": [1, 2]}, {\"bar\": {\"hello\": \"world\"}}, {\"code\": {\"$scope\": {}, \"$code\": \"function x() { return 1; }\"}}, {\"bin\": {\"$type\": \"80\", \"$binary\": \"AQIDBA==\"}}]')\n   [{u'foo': [1, 2]}, {u'bar': {u'hello': u'world'}}, {u'code': Code('function x() { return 1; }', {})}, {u'bin': Binary('...', 128)}]\n\nExample usage (serialization):\n\n.. doctest::\n\n   >>> from bson import Binary, Code\n   >>> from bson.json_util import dumps\n   >>> dumps([{'foo': [1, 2]},\n   ...        {'bar': {'hello': 'world'}},\n   ...        {'code': Code(\"function x() { return 1; }\", {})},\n   ...        {'bin': Binary(b\"\\x01\\x02\\x03\\x04\")}])\n   '[{\"foo\": [1, 2]}, {\"bar\": {\"hello\": \"world\"}}, {\"code\": {\"$code\": \"function x() { return 1; }\", \"$scope\": {}}}, {\"bin\": {\"$binary\": \"AQIDBA==\", \"$type\": \"00\"}}]'\n\nExample usage (with :const:`CANONICAL_JSON_OPTIONS`):\n\n.. doctest::\n\n   >>> from bson import Binary, Code\n   >>> from bson.json_util import dumps, CANONICAL_JSON_OPTIONS\n   >>> dumps([{'foo': [1, 2]},\n   ...        {'bar': {'hello': 'world'}},\n   ...        {'code': Code(\"function x() { return 1; }\")},\n   ...        {'bin': Binary(b\"\\x01\\x02\\x03\\x04\")}],\n   ...       json_options=CANONICAL_JSON_OPTIONS)\n   '[{\"foo\": [{\"$numberInt\": \"1\"}, {\"$numberInt\": \"2\"}]}, {\"bar\": {\"hello\": \"world\"}}, {\"code\": {\"$code\": \"function x() { return 1; }\"}}, {\"bin\": {\"$binary\": {\"base64\": \"AQIDBA==\", \"subType\": \"00\"}}}]'\n\nExample usage (with :const:`RELAXED_JSON_OPTIONS`):\n\n.. doctest::\n\n   >>> from bson import Binary, Code\n   >>> from bson.json_util import dumps, RELAXED_JSON_OPTIONS\n   >>> dumps([{'foo': [1, 2]},\n   ...        {'bar': {'hello': 'world'}},\n   ...        {'code': Code(\"function x() { return 1; }\")},\n   ...        {'bin': Binary(b\"\\x01\\x02\\x03\\x04\")}],\n   ...       json_options=RELAXED_JSON_OPTIONS)\n   '[{\"foo\": [1, 2]}, {\"bar\": {\"hello\": \"world\"}}, {\"code\": {\"$code\": \"function x() { return 1; }\"}}, {\"bin\": {\"$binary\": {\"base64\": \"AQIDBA==\", \"subType\": \"00\"}}}]'\n\nAlternatively, you can manually pass the `default` to :func:`json.dumps`.\nIt won't handle :class:`~bson.binary.Binary` and :class:`~bson.code.Code`\ninstances (as they are extended strings you can't provide custom defaults),\nbut it will be faster as there is less recursion.\n\n.. note::\n   If your application does not need the flexibility offered by\n   :class:`JSONOptions` and spends a large amount of time in the `json_util`\n   module, look to\n   `python-bsonjs <https://pypi.python.org/pypi/python-bsonjs>`_ for a nice\n   performance improvement. `python-bsonjs` is a fast BSON to MongoDB\n   Extended JSON converter for Python built on top of\n   `libbson <https://github.com/mongodb/libbson>`_. `python-bsonjs` works best\n   with PyMongo when using :class:`~bson.raw_bson.RawBSONDocument`.\n\n.. versionchanged:: 2.8\n   The output format for :class:`~bson.timestamp.Timestamp` has changed from\n   '{\"t\": <int>, \"i\": <int>}' to '{\"$timestamp\": {\"t\": <int>, \"i\": <int>}}'.\n   This new format will be decoded to an instance of\n   :class:`~bson.timestamp.Timestamp`. The old format will continue to be\n   decoded to a python dict as before. Encoding to the old format is no longer\n   supported as it was never correct and loses type information.\n   Added support for $numberLong and $undefined - new in MongoDB 2.6 - and\n   parsing $date in ISO-8601 format.\n\n.. versionchanged:: 2.7\n   Preserves order when rendering SON, Timestamp, Code, Binary, and DBRef\n   instances.\n\n.. versionchanged:: 2.3\n   Added dumps and loads helpers to automatically handle conversion to and\n   from json and supports :class:`~bson.binary.Binary` and\n   :class:`~bson.code.Code`\n\"\"\"\n\nimport base64\nimport datetime\nimport json\nimport math\nimport re\nimport sys\nimport uuid\n\nfrom pymongo.errors import ConfigurationError\n\nimport bson\nfrom bson import EPOCH_AWARE, EPOCH_NAIVE, RE_TYPE, SON\nfrom bson.binary import (Binary, JAVA_LEGACY, CSHARP_LEGACY, OLD_UUID_SUBTYPE,\n                         UUID_SUBTYPE)\nfrom bson.code import Code\nfrom bson.codec_options import CodecOptions\nfrom bson.dbref import DBRef\nfrom bson.decimal128 import Decimal128\nfrom bson.int64 import Int64\nfrom bson.max_key import MaxKey\nfrom bson.min_key import MinKey\nfrom bson.objectid import ObjectId\nfrom bson.py3compat import (PY3, iteritems, integer_types, string_type,\n                            text_type)\nfrom bson.regex import Regex\nfrom bson.timestamp import Timestamp\nfrom bson.tz_util import utc\n\n\n_RE_OPT_TABLE = {\n    \"i\": re.I,\n    \"l\": re.L,\n    \"m\": re.M,\n    \"s\": re.S,\n    \"u\": re.U,\n    \"x\": re.X,\n}\n\n# Dollar-prefixed keys which may appear in DBRefs.\n_DBREF_KEYS = frozenset(['$id', '$ref', '$db'])\n\n\nclass DatetimeRepresentation:\n    LEGACY = 0\n    \"\"\"Legacy MongoDB Extended JSON datetime representation.\n\n    :class:`datetime.datetime` instances will be encoded to JSON in the\n    format `{\"$date\": <dateAsMilliseconds>}`, where `dateAsMilliseconds` is\n    a 64-bit signed integer giving the number of milliseconds since the Unix\n    epoch UTC. This was the default encoding before PyMongo version 3.4.\n\n    .. versionadded:: 3.4\n    \"\"\"\n\n    NUMBERLONG = 1\n    \"\"\"NumberLong datetime representation.\n\n    :class:`datetime.datetime` instances will be encoded to JSON in the\n    format `{\"$date\": {\"$numberLong\": \"<dateAsMilliseconds>\"}}`,\n    where `dateAsMilliseconds` is the string representation of a 64-bit signed\n    integer giving the number of milliseconds since the Unix epoch UTC.\n\n    .. versionadded:: 3.4\n    \"\"\"\n\n    ISO8601 = 2\n    \"\"\"ISO-8601 datetime representation.\n\n    :class:`datetime.datetime` instances greater than or equal to the Unix\n    epoch UTC will be encoded to JSON in the format `{\"$date\": \"<ISO-8601>\"}`.\n    :class:`datetime.datetime` instances before the Unix epoch UTC will be\n    encoded as if the datetime representation is\n    :const:`~DatetimeRepresentation.NUMBERLONG`.\n\n    .. versionadded:: 3.4\n    \"\"\"\n\n\nclass JSONMode:\n    LEGACY = 0\n    \"\"\"Legacy Extended JSON representation.\n\n    In this mode, :func:`~bson.json_util.dumps` produces PyMongo's legacy\n    non-standard JSON output. Consider using\n    :const:`~bson.json_util.JSONMode.RELAXED` or\n    :const:`~bson.json_util.JSONMode.CANONICAL` instead.\n\n    .. versionadded:: 3.5\n    \"\"\"\n\n    RELAXED = 1\n    \"\"\"Relaxed Extended JSON representation.\n\n    In this mode, :func:`~bson.json_util.dumps` produces Relaxed Extended JSON,\n    a mostly JSON-like format. Consider using this for things like a web API,\n    where one is sending a document (or a projection of a document) that only\n    uses ordinary JSON type primitives. In particular, the ``int``,\n    :class:`~bson.int64.Int64`, and ``float`` numeric types are represented in\n    the native JSON number format. This output is also the most human readable\n    and is useful for debugging and documentation.\n\n    .. seealso:: The specification for Relaxed `Extended JSON`_.\n\n    .. versionadded:: 3.5\n    \"\"\"\n\n    CANONICAL = 2\n    \"\"\"Canonical Extended JSON representation.\n\n    In this mode, :func:`~bson.json_util.dumps` produces Canonical Extended\n    JSON, a type preserving format. Consider using this for things like\n    testing, where one has to precisely specify expected types in JSON. In\n    particular, the ``int``, :class:`~bson.int64.Int64`, and ``float`` numeric\n    types are encoded with type wrappers.\n\n    .. seealso:: The specification for Canonical `Extended JSON`_.\n\n    .. versionadded:: 3.5\n    \"\"\"\n\n\nclass JSONOptions(CodecOptions):\n    \"\"\"Encapsulates JSON options for :func:`dumps` and :func:`loads`.\n\n    :Parameters:\n      - `strict_number_long`: If ``True``, :class:`~bson.int64.Int64` objects\n        are encoded to MongoDB Extended JSON's *Strict mode* type\n        `NumberLong`, ie ``'{\"$numberLong\": \"<number>\" }'``. Otherwise they\n        will be encoded as an `int`. Defaults to ``False``.\n      - `datetime_representation`: The representation to use when encoding\n        instances of :class:`datetime.datetime`. Defaults to\n        :const:`~DatetimeRepresentation.LEGACY`.\n      - `strict_uuid`: If ``True``, :class:`uuid.UUID` object are encoded to\n        MongoDB Extended JSON's *Strict mode* type `Binary`. Otherwise it\n        will be encoded as ``'{\"$uuid\": \"<hex>\" }'``. Defaults to ``False``.\n      - `json_mode`: The :class:`JSONMode` to use when encoding BSON types to\n        Extended JSON. Defaults to :const:`~JSONMode.LEGACY`.\n      - `document_class`: BSON documents returned by :func:`loads` will be\n        decoded to an instance of this class. Must be a subclass of\n        :class:`collections.MutableMapping`. Defaults to :class:`dict`.\n      - `uuid_representation`: The BSON representation to use when encoding\n        and decoding instances of :class:`uuid.UUID`. Defaults to\n        :const:`~bson.binary.PYTHON_LEGACY`.\n      - `tz_aware`: If ``True``, MongoDB Extended JSON's *Strict mode* type\n        `Date` will be decoded to timezone aware instances of\n        :class:`datetime.datetime`. Otherwise they will be naive. Defaults\n        to ``True``.\n      - `tzinfo`: A :class:`datetime.tzinfo` subclass that specifies the\n        timezone from which :class:`~datetime.datetime` objects should be\n        decoded. Defaults to :const:`~bson.tz_util.utc`.\n      - `args`: arguments to :class:`~bson.codec_options.CodecOptions`\n      - `kwargs`: arguments to :class:`~bson.codec_options.CodecOptions`\n\n    .. seealso:: The specification for Relaxed and Canonical `Extended JSON`_.\n\n    .. versionadded:: 3.4\n\n    .. versionchanged:: 3.5\n       Accepts the optional parameter `json_mode`.\n\n    \"\"\"\n\n    def __new__(cls, strict_number_long=False,\n                datetime_representation=DatetimeRepresentation.LEGACY,\n                strict_uuid=False, json_mode=JSONMode.LEGACY,\n                *args, **kwargs):\n        kwargs[\"tz_aware\"] = kwargs.get(\"tz_aware\", True)\n        if kwargs[\"tz_aware\"]:\n            kwargs[\"tzinfo\"] = kwargs.get(\"tzinfo\", utc)\n        if datetime_representation not in (DatetimeRepresentation.LEGACY,\n                                           DatetimeRepresentation.NUMBERLONG,\n                                           DatetimeRepresentation.ISO8601):\n            raise ConfigurationError(\n                \"JSONOptions.datetime_representation must be one of LEGACY, \"\n                \"NUMBERLONG, or ISO8601 from DatetimeRepresentation.\")\n        self = super(JSONOptions, cls).__new__(cls, *args, **kwargs)\n        if json_mode not in (JSONMode.LEGACY,\n                             JSONMode.RELAXED,\n                             JSONMode.CANONICAL):\n            raise ConfigurationError(\n                \"JSONOptions.json_mode must be one of LEGACY, RELAXED, \"\n                \"or CANONICAL from JSONMode.\")\n        self.json_mode = json_mode\n        if self.json_mode == JSONMode.RELAXED:\n            self.strict_number_long = False\n            self.datetime_representation = DatetimeRepresentation.ISO8601\n            self.strict_uuid = True\n        elif self.json_mode == JSONMode.CANONICAL:\n            self.strict_number_long = True\n            self.datetime_representation = DatetimeRepresentation.NUMBERLONG\n            self.strict_uuid = True\n        else:\n            self.strict_number_long = strict_number_long\n            self.datetime_representation = datetime_representation\n            self.strict_uuid = strict_uuid\n        return self\n\n    def _arguments_repr(self):\n        return ('strict_number_long=%r, '\n                'datetime_representation=%r, '\n                'strict_uuid=%r, json_mode=%r, %s' % (\n                    self.strict_number_long,\n                    self.datetime_representation,\n                    self.strict_uuid,\n                    self.json_mode,\n                    super(JSONOptions, self)._arguments_repr()))\n\n\nLEGACY_JSON_OPTIONS = JSONOptions(json_mode=JSONMode.LEGACY)\n\"\"\":class:`JSONOptions` for encoding to PyMongo's legacy JSON format.\n\n.. seealso:: The documentation for :const:`bson.json_util.JSONMode.LEGACY`.\n\n.. versionadded:: 3.5\n\"\"\"\n\nDEFAULT_JSON_OPTIONS = LEGACY_JSON_OPTIONS\n\"\"\"The default :class:`JSONOptions` for JSON encoding/decoding.\n\nThe same as :const:`LEGACY_JSON_OPTIONS`. This will change to\n:const:`RELAXED_JSON_OPTIONS` in a future release.\n\n.. versionadded:: 3.4\n\"\"\"\n\nCANONICAL_JSON_OPTIONS = JSONOptions(json_mode=JSONMode.CANONICAL)\n\"\"\":class:`JSONOptions` for Canonical Extended JSON.\n\n.. seealso:: The documentation for :const:`bson.json_util.JSONMode.CANONICAL`.\n\n.. versionadded:: 3.5\n\"\"\"\n\nRELAXED_JSON_OPTIONS = JSONOptions(json_mode=JSONMode.RELAXED)\n\"\"\":class:`JSONOptions` for Relaxed Extended JSON.\n\n.. seealso:: The documentation for :const:`bson.json_util.JSONMode.RELAXED`.\n\n.. versionadded:: 3.5\n\"\"\"\n\nSTRICT_JSON_OPTIONS = JSONOptions(\n    strict_number_long=True,\n    datetime_representation=DatetimeRepresentation.ISO8601,\n    strict_uuid=True)\n\"\"\"**DEPRECATED** - :class:`JSONOptions` for MongoDB Extended JSON's *Strict\nmode* encoding.\n\n.. versionadded:: 3.4\n\n.. versionchanged:: 3.5\n   Deprecated. Use :const:`RELAXED_JSON_OPTIONS` or\n   :const:`CANONICAL_JSON_OPTIONS` instead.\n\"\"\"\n\n\ndef dumps(obj, *args, **kwargs):\n    \"\"\"Helper function that wraps :func:`json.dumps`.\n\n    Recursive function that handles all BSON types including\n    :class:`~bson.binary.Binary` and :class:`~bson.code.Code`.\n\n    :Parameters:\n      - `json_options`: A :class:`JSONOptions` instance used to modify the\n        encoding of MongoDB Extended JSON types. Defaults to\n        :const:`DEFAULT_JSON_OPTIONS`.\n\n    .. versionchanged:: 3.4\n       Accepts optional parameter `json_options`. See :class:`JSONOptions`.\n\n    .. versionchanged:: 2.7\n       Preserves order when rendering SON, Timestamp, Code, Binary, and DBRef\n       instances.\n    \"\"\"\n    json_options = kwargs.pop(\"json_options\", DEFAULT_JSON_OPTIONS)\n    return json.dumps(_json_convert(obj, json_options), *args, **kwargs)\n\n\ndef loads(s, *args, **kwargs):\n    \"\"\"Helper function that wraps :func:`json.loads`.\n\n    Automatically passes the object_hook for BSON type conversion.\n\n    Raises ``TypeError``, ``ValueError``, ``KeyError``, or\n    :exc:`~bson.errors.InvalidId` on invalid MongoDB Extended JSON.\n\n    :Parameters:\n      - `json_options`: A :class:`JSONOptions` instance used to modify the\n        decoding of MongoDB Extended JSON types. Defaults to\n        :const:`DEFAULT_JSON_OPTIONS`.\n\n    .. versionchanged:: 3.5\n       Parses Relaxed and Canonical Extended JSON as well as PyMongo's legacy\n       format. Now raises ``TypeError`` or ``ValueError`` when parsing JSON\n       type wrappers with values of the wrong type or any extra keys.\n\n    .. versionchanged:: 3.4\n       Accepts optional parameter `json_options`. See :class:`JSONOptions`.\n    \"\"\"\n    json_options = kwargs.pop(\"json_options\", DEFAULT_JSON_OPTIONS)\n    kwargs[\"object_pairs_hook\"] = lambda pairs: object_pairs_hook(\n        pairs, json_options)\n    return json.loads(s, *args, **kwargs)\n\n\ndef _json_convert(obj, json_options=DEFAULT_JSON_OPTIONS):\n    \"\"\"Recursive helper method that converts BSON types so they can be\n    converted into json.\n    \"\"\"\n    if hasattr(obj, 'iteritems') or hasattr(obj, 'items'):  # PY3 support\n        return SON(((k, _json_convert(v, json_options))\n                    for k, v in iteritems(obj)))\n    elif hasattr(obj, '__iter__') and not isinstance(obj, (text_type, bytes)):\n        return list((_json_convert(v, json_options) for v in obj))\n    try:\n        return default(obj, json_options)\n    except TypeError:\n        return obj\n\n\ndef object_pairs_hook(pairs, json_options=DEFAULT_JSON_OPTIONS):\n    return object_hook(json_options.document_class(pairs), json_options)\n\n\ndef object_hook(dct, json_options=DEFAULT_JSON_OPTIONS):\n    if \"$oid\" in dct:\n        return _parse_canonical_oid(dct)\n    if \"$ref\" in dct:\n        return _parse_canonical_dbref(dct)\n    if \"$date\" in dct:\n        return _parse_canonical_datetime(dct, json_options)\n    if \"$regex\" in dct:\n        return _parse_legacy_regex(dct)\n    if \"$minKey\" in dct:\n        return _parse_canonical_minkey(dct)\n    if \"$maxKey\" in dct:\n        return _parse_canonical_maxkey(dct)\n    if \"$binary\" in dct:\n        if \"$type\" in dct:\n            return _parse_legacy_binary(dct, json_options)\n        else:\n            return _parse_canonical_binary(dct, json_options)\n    if \"$code\" in dct:\n        return _parse_canonical_code(dct)\n    if \"$uuid\" in dct:\n        return _parse_legacy_uuid(dct)\n    if \"$undefined\" in dct:\n        return None\n    if \"$numberLong\" in dct:\n        return _parse_canonical_int64(dct)\n    if \"$timestamp\" in dct:\n        tsp = dct[\"$timestamp\"]\n        return Timestamp(tsp[\"t\"], tsp[\"i\"])\n    if \"$numberDecimal\" in dct:\n        return _parse_canonical_decimal128(dct)\n    if \"$dbPointer\" in dct:\n        return _parse_canonical_dbpointer(dct)\n    if \"$regularExpression\" in dct:\n        return _parse_canonical_regex(dct)\n    if \"$symbol\" in dct:\n        return _parse_canonical_symbol(dct)\n    if \"$numberInt\" in dct:\n        return _parse_canonical_int32(dct)\n    if \"$numberDouble\" in dct:\n        return _parse_canonical_double(dct)\n    return dct\n\n\ndef _parse_legacy_regex(doc):\n    pattern = doc[\"$regex\"]\n    # Check if this is the $regex query operator.\n    if isinstance(pattern, Regex):\n        return doc\n    flags = 0\n    # PyMongo always adds $options but some other tools may not.\n    for opt in doc.get(\"$options\", \"\"):\n        flags |= _RE_OPT_TABLE.get(opt, 0)\n    return Regex(pattern, flags)\n\n\ndef _parse_legacy_uuid(doc):\n    \"\"\"Decode a JSON legacy $uuid to Python UUID.\"\"\"\n    if len(doc) != 1:\n        raise TypeError('Bad $uuid, extra field(s): %s' % (doc,))\n    return uuid.UUID(doc[\"$uuid\"])\n\n\ndef _binary_or_uuid(data, subtype, json_options):\n    # special handling for UUID\n    if subtype == OLD_UUID_SUBTYPE:\n        if json_options.uuid_representation == CSHARP_LEGACY:\n            return uuid.UUID(bytes_le=data)\n        if json_options.uuid_representation == JAVA_LEGACY:\n            data = data[7::-1] + data[:7:-1]\n        return uuid.UUID(bytes=data)\n    if subtype == UUID_SUBTYPE:\n        return uuid.UUID(bytes=data)\n    if PY3 and subtype == 0:\n        return data\n    return Binary(data, subtype)\n\n\ndef _parse_legacy_binary(doc, json_options):\n    if isinstance(doc[\"$type\"], int):\n        doc[\"$type\"] = \"%02x\" % doc[\"$type\"]\n    subtype = int(doc[\"$type\"], 16)\n    if subtype >= 0xffffff80:  # Handle mongoexport values\n        subtype = int(doc[\"$type\"][6:], 16)\n    data = base64.b64decode(doc[\"$binary\"].encode())\n    return _binary_or_uuid(data, subtype, json_options)\n\n\ndef _parse_canonical_binary(doc, json_options):\n    binary = doc[\"$binary\"]\n    b64 = binary[\"base64\"]\n    subtype = binary[\"subType\"]\n    if not isinstance(b64, string_type):\n        raise TypeError('$binary base64 must be a string: %s' % (doc,))\n    if not isinstance(subtype, string_type) or len(subtype) > 2:\n        raise TypeError('$binary subType must be a string at most 2 '\n                        'characters: %s' % (doc,))\n    if len(binary) != 2:\n        raise TypeError('$binary must include only \"base64\" and \"subType\" '\n                        'components: %s' % (doc,))\n\n    data = base64.b64decode(b64.encode())\n    return _binary_or_uuid(data, int(subtype, 16), json_options)\n\n\ndef _parse_canonical_datetime(doc, json_options):\n    \"\"\"Decode a JSON datetime to python datetime.datetime.\"\"\"\n    dtm = doc[\"$date\"]\n    if len(doc) != 1:\n        raise TypeError('Bad $date, extra field(s): %s' % (doc,))\n    # mongoexport 2.6 and newer\n    if isinstance(dtm, string_type):\n        # Parse offset\n        if dtm[-1] == 'Z':\n            dt = dtm[:-1]\n            offset = 'Z'\n        elif dtm[-6] in ('+', '-') and dtm[-3] == ':':\n            # (+|-)HH:MM\n            dt = dtm[:-6]\n            offset = dtm[-6:]\n        elif dtm[-5] in ('+', '-'):\n            # (+|-)HHMM\n            dt = dtm[:-5]\n            offset = dtm[-5:]\n        elif dtm[-3] in ('+', '-'):\n            # (+|-)HH\n            dt = dtm[:-3]\n            offset = dtm[-3:]\n        else:\n            dt = dtm\n            offset = ''\n\n        # Parse the optional factional seconds portion.\n        dot_index = dt.rfind('.')\n        microsecond = 0\n        if dot_index != -1:\n            microsecond = int(float(dt[dot_index:]) * 1000000)\n            dt = dt[:dot_index]\n\n        aware = datetime.datetime.strptime(\n            dt, \"%Y-%m-%dT%H:%M:%S\").replace(microsecond=microsecond,\n                                             tzinfo=utc)\n\n        if offset and offset != 'Z':\n            if len(offset) == 6:\n                hours, minutes = offset[1:].split(':')\n                secs = (int(hours) * 3600 + int(minutes) * 60)\n            elif len(offset) == 5:\n                secs = (int(offset[1:3]) * 3600 + int(offset[3:]) * 60)\n            elif len(offset) == 3:\n                secs = int(offset[1:3]) * 3600\n            if offset[0] == \"-\":\n                secs *= -1\n            aware = aware - datetime.timedelta(seconds=secs)\n\n        if json_options.tz_aware:\n            if json_options.tzinfo:\n                aware = aware.astimezone(json_options.tzinfo)\n            return aware\n        else:\n            return aware.replace(tzinfo=None)\n    return bson._millis_to_datetime(int(dtm), json_options)\n\n\ndef _parse_canonical_oid(doc):\n    \"\"\"Decode a JSON ObjectId to bson.objectid.ObjectId.\"\"\"\n    if len(doc) != 1:\n        raise TypeError('Bad $oid, extra field(s): %s' % (doc,))\n    return ObjectId(doc['$oid'])\n\n\ndef _parse_canonical_symbol(doc):\n    \"\"\"Decode a JSON symbol to Python string.\"\"\"\n    symbol = doc['$symbol']\n    if len(doc) != 1:\n        raise TypeError('Bad $symbol, extra field(s): %s' % (doc,))\n    return text_type(symbol)\n\n\ndef _parse_canonical_code(doc):\n    \"\"\"Decode a JSON code to bson.code.Code.\"\"\"\n    for key in doc:\n        if key not in ('$code', '$scope'):\n            raise TypeError('Bad $code, extra field(s): %s' % (doc,))\n    return Code(doc['$code'], scope=doc.get('$scope'))\n\n\ndef _parse_canonical_regex(doc):\n    \"\"\"Decode a JSON regex to bson.regex.Regex.\"\"\"\n    regex = doc['$regularExpression']\n    if len(doc) != 1:\n        raise TypeError('Bad $regularExpression, extra field(s): %s' % (doc,))\n    if len(regex) != 2:\n        raise TypeError('Bad $regularExpression must include only \"pattern\"'\n                        'and \"options\" components: %s' % (doc,))\n    return Regex(regex['pattern'], regex['options'])\n\n\ndef _parse_canonical_dbref(doc):\n    \"\"\"Decode a JSON DBRef to bson.dbref.DBRef.\"\"\"\n    for key in doc:\n        if key.startswith('$') and key not in _DBREF_KEYS:\n            # Other keys start with $, so dct cannot be parsed as a DBRef.\n            return doc\n    return DBRef(doc.pop('$ref'), doc.pop('$id'),\n                 database=doc.pop('$db', None), **doc)\n\n\ndef _parse_canonical_dbpointer(doc):\n    \"\"\"Decode a JSON (deprecated) DBPointer to bson.dbref.DBRef.\"\"\"\n    dbref = doc['$dbPointer']\n    if len(doc) != 1:\n        raise TypeError('Bad $dbPointer, extra field(s): %s' % (doc,))\n    if isinstance(dbref, DBRef):\n        dbref_doc = dbref.as_doc()\n        # DBPointer must not contain $db in its value.\n        if dbref.database is not None:\n            raise TypeError(\n                'Bad $dbPointer, extra field $db: %s' % (dbref_doc,))\n        if not isinstance(dbref.id, ObjectId):\n            raise TypeError(\n                'Bad $dbPointer, $id must be an ObjectId: %s' % (dbref_doc,))\n        if len(dbref_doc) != 2:\n            raise TypeError(\n                'Bad $dbPointer, extra field(s) in DBRef: %s' % (dbref_doc,))\n        return dbref\n    else:\n        raise TypeError('Bad $dbPointer, expected a DBRef: %s' % (doc,))\n\n\ndef _parse_canonical_int32(doc):\n    \"\"\"Decode a JSON int32 to python int.\"\"\"\n    i_str = doc['$numberInt']\n    if len(doc) != 1:\n        raise TypeError('Bad $numberInt, extra field(s): %s' % (doc,))\n    if not isinstance(i_str, string_type):\n        raise TypeError('$numberInt must be string: %s' % (doc,))\n    return int(i_str)\n\n\ndef _parse_canonical_int64(doc):\n    \"\"\"Decode a JSON int64 to bson.int64.Int64.\"\"\"\n    l_str = doc['$numberLong']\n    if len(doc) != 1:\n        raise TypeError('Bad $numberLong, extra field(s): %s' % (doc,))\n    return Int64(l_str)\n\n\ndef _parse_canonical_double(doc):\n    \"\"\"Decode a JSON double to python float.\"\"\"\n    d_str = doc['$numberDouble']\n    if len(doc) != 1:\n        raise TypeError('Bad $numberDouble, extra field(s): %s' % (doc,))\n    if not isinstance(d_str, string_type):\n        raise TypeError('$numberDouble must be string: %s' % (doc,))\n    return float(d_str)\n\n\ndef _parse_canonical_decimal128(doc):\n    \"\"\"Decode a JSON decimal128 to bson.decimal128.Decimal128.\"\"\"\n    d_str = doc['$numberDecimal']\n    if len(doc) != 1:\n        raise TypeError('Bad $numberDecimal, extra field(s): %s' % (doc,))\n    if not isinstance(d_str, string_type):\n        raise TypeError('$numberDecimal must be string: %s' % (doc,))\n    return Decimal128(d_str)\n\n\ndef _parse_canonical_minkey(doc):\n    \"\"\"Decode a JSON MinKey to bson.min_key.MinKey.\"\"\"\n    if doc['$minKey'] is not 1:\n        raise TypeError('$minKey value must be 1: %s' % (doc,))\n    if len(doc) != 1:\n        raise TypeError('Bad $minKey, extra field(s): %s' % (doc,))\n    return MinKey()\n\n\ndef _parse_canonical_maxkey(doc):\n    \"\"\"Decode a JSON MaxKey to bson.max_key.MaxKey.\"\"\"\n    if doc['$maxKey'] is not 1:\n        raise TypeError('$maxKey value must be 1: %s', (doc,))\n    if len(doc) != 1:\n        raise TypeError('Bad $minKey, extra field(s): %s' % (doc,))\n    return MaxKey()\n\n\ndef _encode_binary(data, subtype, json_options):\n    if json_options.json_mode == JSONMode.LEGACY:\n        return SON([\n            ('$binary', base64.b64encode(data).decode()),\n            ('$type', \"%02x\" % subtype)])\n    return {'$binary': SON([\n        ('base64', base64.b64encode(data).decode()),\n        ('subType', \"%02x\" % subtype)])}\n\n\ndef default(obj, json_options=DEFAULT_JSON_OPTIONS):\n    # We preserve key order when rendering SON, DBRef, etc. as JSON by\n    # returning a SON for those types instead of a dict.\n    if isinstance(obj, ObjectId):\n        return {\"$oid\": str(obj)}\n    if isinstance(obj, DBRef):\n        return _json_convert(obj.as_doc(), json_options=json_options)\n    if isinstance(obj, datetime.datetime):\n        if (json_options.datetime_representation ==\n                DatetimeRepresentation.ISO8601):\n            if not obj.tzinfo:\n                obj = obj.replace(tzinfo=utc)\n            if obj >= EPOCH_AWARE:\n                off = obj.tzinfo.utcoffset(obj)\n                if (off.days, off.seconds, off.microseconds) == (0, 0, 0):\n                    tz_string = 'Z'\n                else:\n                    tz_string = obj.strftime('%z')\n                millis = int(obj.microsecond / 1000)\n                fracsecs = \".%03d\" % (millis,) if millis else \"\"\n                return {\"$date\": \"%s%s%s\" % (\n                    obj.strftime(\"%Y-%m-%dT%H:%M:%S\"), fracsecs, tz_string)}\n\n        millis = bson._datetime_to_millis(obj)\n        if (json_options.datetime_representation ==\n                DatetimeRepresentation.LEGACY):\n            return {\"$date\": millis}\n        return {\"$date\": {\"$numberLong\": str(millis)}}\n    if json_options.strict_number_long and isinstance(obj, Int64):\n        return {\"$numberLong\": str(obj)}\n    if isinstance(obj, (RE_TYPE, Regex)):\n        flags = \"\"\n        if obj.flags & re.IGNORECASE:\n            flags += \"i\"\n        if obj.flags & re.LOCALE:\n            flags += \"l\"\n        if obj.flags & re.MULTILINE:\n            flags += \"m\"\n        if obj.flags & re.DOTALL:\n            flags += \"s\"\n        if obj.flags & re.UNICODE:\n            flags += \"u\"\n        if obj.flags & re.VERBOSE:\n            flags += \"x\"\n        if isinstance(obj.pattern, text_type):\n            pattern = obj.pattern\n        else:\n            pattern = obj.pattern.decode('utf-8')\n        if json_options.json_mode == JSONMode.LEGACY:\n            return SON([(\"$regex\", pattern), (\"$options\", flags)])\n        return {'$regularExpression': SON([(\"pattern\", pattern),\n                                           (\"options\", flags)])}\n    if isinstance(obj, MinKey):\n        return {\"$minKey\": 1}\n    if isinstance(obj, MaxKey):\n        return {\"$maxKey\": 1}\n    if isinstance(obj, Timestamp):\n        return {\"$timestamp\": SON([(\"t\", obj.time), (\"i\", obj.inc)])}\n    if isinstance(obj, Code):\n        if obj.scope is None:\n            return {'$code': str(obj)}\n        return SON([\n            ('$code', str(obj)),\n            ('$scope', _json_convert(obj.scope, json_options))])\n    if isinstance(obj, Binary):\n        return _encode_binary(obj, obj.subtype, json_options)\n    if PY3 and isinstance(obj, bytes):\n        return _encode_binary(obj, 0, json_options)\n    if isinstance(obj, uuid.UUID):\n        if json_options.strict_uuid:\n            data = obj.bytes\n            subtype = OLD_UUID_SUBTYPE\n            if json_options.uuid_representation == CSHARP_LEGACY:\n                data = obj.bytes_le\n            elif json_options.uuid_representation == JAVA_LEGACY:\n                data = data[7::-1] + data[:7:-1]\n            elif json_options.uuid_representation == UUID_SUBTYPE:\n                subtype = UUID_SUBTYPE\n            return _encode_binary(data, subtype, json_options)\n        else:\n            return {\"$uuid\": obj.hex}\n    if isinstance(obj, Decimal128):\n        return {\"$numberDecimal\": str(obj)}\n    if isinstance(obj, bool):\n        return obj\n    if (json_options.json_mode == JSONMode.CANONICAL and\n            isinstance(obj, integer_types)):\n        if -2 ** 31 <= obj < 2 ** 31:\n            return {'$numberInt': text_type(obj)}\n        return {'$numberLong': text_type(obj)}\n    if json_options.json_mode != JSONMode.LEGACY and isinstance(obj, float):\n        if math.isnan(obj):\n            return {'$numberDouble': 'NaN'}\n        elif math.isinf(obj):\n            representation = 'Infinity' if obj > 0 else '-Infinity'\n            return {'$numberDouble': representation}\n        elif json_options.json_mode == JSONMode.CANONICAL:\n            # repr() will return the shortest string guaranteed to produce the\n            # original value, when float() is called on it. str produces a\n            # shorter string in Python 2.\n            return {'$numberDouble': text_type(repr(obj))}\n    raise TypeError(\"%r is not JSON serializable\" % obj)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/max_key.py",
    "content": "# Copyright 2010-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Representation for the MongoDB internal MaxKey type.\n\"\"\"\n\n\nclass MaxKey(object):\n    \"\"\"MongoDB internal MaxKey type.\n\n    .. versionchanged:: 2.7\n       ``MaxKey`` now implements comparison operators.\n    \"\"\"\n\n    _type_marker = 127\n\n    def __eq__(self, other):\n        return isinstance(other, MaxKey)\n\n    def __hash__(self):\n        return hash(self._type_marker)\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __le__(self, other):\n        return isinstance(other, MaxKey)\n\n    def __lt__(self, dummy):\n        return False\n\n    def __ge__(self, dummy):\n        return True\n\n    def __gt__(self, other):\n        return not isinstance(other, MaxKey)\n\n    def __repr__(self):\n        return \"MaxKey()\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/min_key.py",
    "content": "# Copyright 2010-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Representation for the MongoDB internal MinKey type.\n\"\"\"\n\n\nclass MinKey(object):\n    \"\"\"MongoDB internal MinKey type.\n\n    .. versionchanged:: 2.7\n       ``MinKey`` now implements comparison operators.\n    \"\"\"\n\n    _type_marker = 255\n\n    def __eq__(self, other):\n        return isinstance(other, MinKey)\n\n    def __hash__(self):\n        return hash(self._type_marker)\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __le__(self, dummy):\n        return True\n\n    def __lt__(self, other):\n        return not isinstance(other, MinKey)\n\n    def __ge__(self, other):\n        return isinstance(other, MinKey)\n\n    def __gt__(self, dummy):\n        return False\n\n    def __repr__(self):\n        return \"MinKey()\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/objectid.py",
    "content": "# Copyright 2009-2015 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for working with MongoDB `ObjectIds\n<http://dochub.mongodb.org/core/objectids>`_.\n\"\"\"\n\nimport binascii\nimport calendar\nimport datetime\nimport os\nimport struct\nimport threading\nimport time\n\nfrom random import SystemRandom\n\nfrom bson.errors import InvalidId\nfrom bson.py3compat import PY3, bytes_from_hex, string_type, text_type\nfrom bson.tz_util import utc\n\n\n_MAX_COUNTER_VALUE = 0xFFFFFF\n\n\ndef _raise_invalid_id(oid):\n    raise InvalidId(\n        \"%r is not a valid ObjectId, it must be a 12-byte input\"\n        \" or a 24-character hex string\" % oid)\n\n\ndef _random_bytes():\n    \"\"\"Get the 5-byte random field of an ObjectId.\"\"\"\n    return os.urandom(5)\n\n\nclass ObjectId(object):\n    \"\"\"A MongoDB ObjectId.\n    \"\"\"\n\n    _pid = os.getpid()\n\n    _inc = SystemRandom().randint(0, _MAX_COUNTER_VALUE)\n    _inc_lock = threading.Lock()\n\n    __random = _random_bytes()\n\n    __slots__ = ('__id',)\n\n    _type_marker = 7\n\n    def __init__(self, oid=None):\n        \"\"\"Initialize a new ObjectId.\n\n        An ObjectId is a 12-byte unique identifier consisting of:\n\n          - a 4-byte value representing the seconds since the Unix epoch,\n          - a 5-byte random value,\n          - a 3-byte counter, starting with a random value.\n\n        By default, ``ObjectId()`` creates a new unique identifier. The\n        optional parameter `oid` can be an :class:`ObjectId`, or any 12\n        :class:`bytes` or, in Python 2, any 12-character :class:`str`.\n\n        For example, the 12 bytes b'foo-bar-quux' do not follow the ObjectId\n        specification but they are acceptable input::\n\n          >>> ObjectId(b'foo-bar-quux')\n          ObjectId('666f6f2d6261722d71757578')\n\n        `oid` can also be a :class:`unicode` or :class:`str` of 24 hex digits::\n\n          >>> ObjectId('0123456789ab0123456789ab')\n          ObjectId('0123456789ab0123456789ab')\n          >>>\n          >>> # A u-prefixed unicode literal:\n          >>> ObjectId(u'0123456789ab0123456789ab')\n          ObjectId('0123456789ab0123456789ab')\n\n        Raises :class:`~bson.errors.InvalidId` if `oid` is not 12 bytes nor\n        24 hex digits, or :class:`TypeError` if `oid` is not an accepted type.\n\n        :Parameters:\n          - `oid` (optional): a valid ObjectId.\n\n        .. mongodoc:: objectids\n\n        .. versionchanged:: 3.8\n           :class:`~bson.objectid.ObjectId` now implements the `ObjectID\n           specification version 0.2\n           <https://github.com/mongodb/specifications/blob/master/source/\n           objectid.rst>`_.\n        \"\"\"\n        if oid is None:\n            self.__generate()\n        elif isinstance(oid, bytes) and len(oid) == 12:\n            self.__id = oid\n        else:\n            self.__validate(oid)\n\n    @classmethod\n    def from_datetime(cls, generation_time):\n        \"\"\"Create a dummy ObjectId instance with a specific generation time.\n\n        This method is useful for doing range queries on a field\n        containing :class:`ObjectId` instances.\n\n        .. warning::\n           It is not safe to insert a document containing an ObjectId\n           generated using this method. This method deliberately\n           eliminates the uniqueness guarantee that ObjectIds\n           generally provide. ObjectIds generated with this method\n           should be used exclusively in queries.\n\n        `generation_time` will be converted to UTC. Naive datetime\n        instances will be treated as though they already contain UTC.\n\n        An example using this helper to get documents where ``\"_id\"``\n        was generated before January 1, 2010 would be:\n\n        >>> gen_time = datetime.datetime(2010, 1, 1)\n        >>> dummy_id = ObjectId.from_datetime(gen_time)\n        >>> result = collection.find({\"_id\": {\"$lt\": dummy_id}})\n\n        :Parameters:\n          - `generation_time`: :class:`~datetime.datetime` to be used\n            as the generation time for the resulting ObjectId.\n        \"\"\"\n        if generation_time.utcoffset() is not None:\n            generation_time = generation_time - generation_time.utcoffset()\n        timestamp = calendar.timegm(generation_time.timetuple())\n        oid = struct.pack(\n            \">I\", int(timestamp)) + b\"\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\"\n        return cls(oid)\n\n    @classmethod\n    def is_valid(cls, oid):\n        \"\"\"Checks if a `oid` string is valid or not.\n\n        :Parameters:\n          - `oid`: the object id to validate\n\n        .. versionadded:: 2.3\n        \"\"\"\n        if not oid:\n            return False\n\n        try:\n            ObjectId(oid)\n            return True\n        except (InvalidId, TypeError):\n            return False\n\n    @classmethod\n    def _random(cls):\n        \"\"\"Generate a 5-byte random number once per process.\n        \"\"\"\n        pid = os.getpid()\n        if pid != cls._pid:\n            cls._pid = pid\n            cls.__random = _random_bytes()\n        return cls.__random\n\n    def __generate(self):\n        \"\"\"Generate a new value for this ObjectId.\n        \"\"\"\n\n        # 4 bytes current time\n        oid = struct.pack(\">I\", int(time.time()))\n\n        # 5 bytes random\n        oid += ObjectId._random()\n\n        # 3 bytes inc\n        with ObjectId._inc_lock:\n            oid += struct.pack(\">I\", ObjectId._inc)[1:4]\n            ObjectId._inc = (ObjectId._inc + 1) % (_MAX_COUNTER_VALUE + 1)\n\n        self.__id = oid\n\n    def __validate(self, oid):\n        \"\"\"Validate and use the given id for this ObjectId.\n\n        Raises TypeError if id is not an instance of\n        (:class:`basestring` (:class:`str` or :class:`bytes`\n        in python 3), ObjectId) and InvalidId if it is not a\n        valid ObjectId.\n\n        :Parameters:\n          - `oid`: a valid ObjectId\n        \"\"\"\n        if isinstance(oid, ObjectId):\n            self.__id = oid.binary\n        # bytes or unicode in python 2, str in python 3\n        elif isinstance(oid, string_type):\n            if len(oid) == 24:\n                try:\n                    self.__id = bytes_from_hex(oid)\n                except (TypeError, ValueError):\n                    _raise_invalid_id(oid)\n            else:\n                _raise_invalid_id(oid)\n        else:\n            raise TypeError(\"id must be an instance of (bytes, %s, ObjectId), \"\n                            \"not %s\" % (text_type.__name__, type(oid)))\n\n    @property\n    def binary(self):\n        \"\"\"12-byte binary representation of this ObjectId.\n        \"\"\"\n        return self.__id\n\n    @property\n    def generation_time(self):\n        \"\"\"A :class:`datetime.datetime` instance representing the time of\n        generation for this :class:`ObjectId`.\n\n        The :class:`datetime.datetime` is timezone aware, and\n        represents the generation time in UTC. It is precise to the\n        second.\n        \"\"\"\n        timestamp = struct.unpack(\">I\", self.__id[0:4])[0]\n        return datetime.datetime.fromtimestamp(timestamp, utc)\n\n    def __getstate__(self):\n        \"\"\"return value of object for pickling.\n        needed explicitly because __slots__() defined.\n        \"\"\"\n        return self.__id\n\n    def __setstate__(self, value):\n        \"\"\"explicit state set from pickling\n        \"\"\"\n        # Provide backwards compatability with OIDs\n        # pickled with pymongo-1.9 or older.\n        if isinstance(value, dict):\n            oid = value[\"_ObjectId__id\"]\n        else:\n            oid = value\n        # ObjectIds pickled in python 2.x used `str` for __id.\n        # In python 3.x this has to be converted to `bytes`\n        # by encoding latin-1.\n        if PY3 and isinstance(oid, text_type):\n            self.__id = oid.encode('latin-1')\n        else:\n            self.__id = oid\n\n    def __str__(self):\n        if PY3:\n            return binascii.hexlify(self.__id).decode()\n        return binascii.hexlify(self.__id)\n\n    def __repr__(self):\n        return \"ObjectId('%s')\" % (str(self),)\n\n    def __eq__(self, other):\n        if isinstance(other, ObjectId):\n            return self.__id == other.binary\n        return NotImplemented\n\n    def __ne__(self, other):\n        if isinstance(other, ObjectId):\n            return self.__id != other.binary\n        return NotImplemented\n\n    def __lt__(self, other):\n        if isinstance(other, ObjectId):\n            return self.__id < other.binary\n        return NotImplemented\n\n    def __le__(self, other):\n        if isinstance(other, ObjectId):\n            return self.__id <= other.binary\n        return NotImplemented\n\n    def __gt__(self, other):\n        if isinstance(other, ObjectId):\n            return self.__id > other.binary\n        return NotImplemented\n\n    def __ge__(self, other):\n        if isinstance(other, ObjectId):\n            return self.__id >= other.binary\n        return NotImplemented\n\n    def __hash__(self):\n        \"\"\"Get a hash value for this :class:`ObjectId`.\"\"\"\n        return hash(self.__id)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/py3compat.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Utility functions and definitions for python3 compatibility.\"\"\"\n\nimport sys\n\nPY3 = sys.version_info[0] == 3\n\nif PY3:\n    import codecs\n    import collections.abc as abc\n    import _thread as thread\n    from abc import ABC, abstractmethod\n    from io import BytesIO as StringIO\n\n    def abstractproperty(func):\n        return property(abstractmethod(func))\n\n    MAXSIZE = sys.maxsize\n\n    imap = map\n\n    def b(s):\n        # BSON and socket operations deal in binary data. In\n        # python 3 that means instances of `bytes`. In python\n        # 2.7 you can create an alias for `bytes` using\n        # the b prefix (e.g. b'foo').\n        # See http://python3porting.com/problems.html#nicer-solutions\n        return codecs.latin_1_encode(s)[0]\n\n    def bytes_from_hex(h):\n        return bytes.fromhex(h)\n\n    def iteritems(d):\n        return iter(d.items())\n\n    def itervalues(d):\n        return iter(d.values())\n\n    def reraise(exctype, value, trace=None):\n        raise exctype(str(value)).with_traceback(trace)\n\n    def reraise_instance(exc_instance, trace=None):\n        raise exc_instance.with_traceback(trace)\n\n    def _unicode(s):\n        return s\n\n    text_type = str\n    string_type = str\n    integer_types = int\nelse:\n    import collections as abc\n    import thread\n    from abc import ABCMeta, abstractproperty\n\n    from itertools import imap\n    try:\n        from cStringIO import StringIO\n    except ImportError:\n        from StringIO import StringIO\n\n    ABC = ABCMeta('ABC', (object,), {})\n\n    MAXSIZE = sys.maxint\n\n    def b(s):\n        # See comments above. In python 2.x b('foo') is just 'foo'.\n        return s\n\n    def bytes_from_hex(h):\n        return h.decode('hex')\n\n    def iteritems(d):\n        return d.iteritems()\n\n    def itervalues(d):\n        return d.itervalues()\n\n    def reraise(exctype, value, trace=None):\n        _reraise(exctype, str(value), trace)\n\n    def reraise_instance(exc_instance, trace=None):\n        _reraise(exc_instance, None, trace)\n\n    # \"raise x, y, z\" raises SyntaxError in Python 3\n    exec(\"\"\"def _reraise(exc, value, trace):\n    raise exc, value, trace\n\"\"\")\n\n    _unicode = unicode\n\n    string_type = basestring\n    text_type = unicode\n    integer_types = (int, long)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/raw_bson.py",
    "content": "# Copyright 2015-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for representing raw BSON documents.\n\"\"\"\n\nfrom bson import _raw_to_dict, _get_object_size\nfrom bson.py3compat import abc, iteritems\nfrom bson.codec_options import (\n    DEFAULT_CODEC_OPTIONS as DEFAULT, _RAW_BSON_DOCUMENT_MARKER)\nfrom bson.son import SON\n\n\nclass RawBSONDocument(abc.Mapping):\n    \"\"\"Representation for a MongoDB document that provides access to the raw\n    BSON bytes that compose it.\n\n    Only when a field is accessed or modified within the document does\n    RawBSONDocument decode its bytes.\n    \"\"\"\n\n    __slots__ = ('__raw', '__inflated_doc', '__codec_options')\n    _type_marker = _RAW_BSON_DOCUMENT_MARKER\n\n    def __init__(self, bson_bytes, codec_options=None):\n        \"\"\"Create a new :class:`RawBSONDocument`\n\n        :class:`RawBSONDocument` is a representation of a BSON document that\n        provides access to the underlying raw BSON bytes. Only when a field is\n        accessed or modified within the document does RawBSONDocument decode\n        its bytes.\n\n        :class:`RawBSONDocument` implements the ``Mapping`` abstract base\n        class from the standard library so it can be used like a read-only\n        ``dict``::\n\n            >>> raw_doc = RawBSONDocument(BSON.encode({'_id': 'my_doc'}))\n            >>> raw_doc.raw\n            b'...'\n            >>> raw_doc['_id']\n            'my_doc'\n\n        :Parameters:\n          - `bson_bytes`: the BSON bytes that compose this document\n          - `codec_options` (optional): An instance of\n            :class:`~bson.codec_options.CodecOptions` whose ``document_class``\n            must be :class:`RawBSONDocument`. The default is\n            :attr:`DEFAULT_RAW_BSON_OPTIONS`.\n\n        .. versionchanged:: 3.8\n          :class:`RawBSONDocument` now validates that the ``bson_bytes``\n          passed in represent a single bson document.\n\n        .. versionchanged:: 3.5\n          If a :class:`~bson.codec_options.CodecOptions` is passed in, its\n          `document_class` must be :class:`RawBSONDocument`.\n        \"\"\"\n        self.__raw = bson_bytes\n        self.__inflated_doc = None\n        # Can't default codec_options to DEFAULT_RAW_BSON_OPTIONS in signature,\n        # it refers to this class RawBSONDocument.\n        if codec_options is None:\n            codec_options = DEFAULT_RAW_BSON_OPTIONS\n        elif codec_options.document_class is not RawBSONDocument:\n            raise TypeError(\n                \"RawBSONDocument cannot use CodecOptions with document \"\n                \"class %s\" % (codec_options.document_class, ))\n        self.__codec_options = codec_options\n        # Validate the bson object size.\n        _get_object_size(bson_bytes, 0, len(bson_bytes))\n\n    @property\n    def raw(self):\n        \"\"\"The raw BSON bytes composing this document.\"\"\"\n        return self.__raw\n\n    def items(self):\n        \"\"\"Lazily decode and iterate elements in this document.\"\"\"\n        return iteritems(self.__inflated)\n\n    @property\n    def __inflated(self):\n        if self.__inflated_doc is None:\n            # We already validated the object's size when this document was\n            # created, so no need to do that again.\n            # Use SON to preserve ordering of elements.\n            self.__inflated_doc = _inflate_bson(\n                self.__raw, self.__codec_options)\n        return self.__inflated_doc\n\n    def __getitem__(self, item):\n        return self.__inflated[item]\n\n    def __iter__(self):\n        return iter(self.__inflated)\n\n    def __len__(self):\n        return len(self.__inflated)\n\n    def __eq__(self, other):\n        if isinstance(other, RawBSONDocument):\n            return self.__raw == other.raw\n        return NotImplemented\n\n    def __repr__(self):\n        return (\"RawBSONDocument(%r, codec_options=%r)\"\n                % (self.raw, self.__codec_options))\n\n\ndef _inflate_bson(bson_bytes, codec_options):\n    \"\"\"Inflates the top level fields of a BSON document.\n\n    :Parameters:\n      - `bson_bytes`: the BSON bytes that compose this document\n      - `codec_options`: An instance of\n        :class:`~bson.codec_options.CodecOptions` whose ``document_class``\n        must be :class:`RawBSONDocument`.\n    \"\"\"\n    # Use SON to preserve ordering of elements.\n    return _raw_to_dict(\n        bson_bytes, 4, len(bson_bytes)-1, codec_options, SON())\n\n\nDEFAULT_RAW_BSON_OPTIONS = DEFAULT.with_options(document_class=RawBSONDocument)\n\"\"\"The default :class:`~bson.codec_options.CodecOptions` for\n:class:`RawBSONDocument`.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/regex.py",
    "content": "# Copyright 2013-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for representing MongoDB regular expressions.\n\"\"\"\n\nimport re\n\nfrom bson.son import RE_TYPE\nfrom bson.py3compat import string_type, text_type\n\n\ndef str_flags_to_int(str_flags):\n    flags = 0\n    if \"i\" in str_flags:\n        flags |= re.IGNORECASE\n    if \"l\" in str_flags:\n        flags |= re.LOCALE\n    if \"m\" in str_flags:\n        flags |= re.MULTILINE\n    if \"s\" in str_flags:\n        flags |= re.DOTALL\n    if \"u\" in str_flags:\n        flags |= re.UNICODE\n    if \"x\" in str_flags:\n        flags |= re.VERBOSE\n\n    return flags\n\n\nclass Regex(object):\n    \"\"\"BSON regular expression data.\"\"\"\n    _type_marker = 11\n\n    @classmethod\n    def from_native(cls, regex):\n        \"\"\"Convert a Python regular expression into a ``Regex`` instance.\n\n        Note that in Python 3, a regular expression compiled from a\n        :class:`str` has the ``re.UNICODE`` flag set. If it is undesirable\n        to store this flag in a BSON regular expression, unset it first::\n\n          >>> pattern = re.compile('.*')\n          >>> regex = Regex.from_native(pattern)\n          >>> regex.flags ^= re.UNICODE\n          >>> db.collection.insert({'pattern': regex})\n\n        :Parameters:\n          - `regex`: A regular expression object from ``re.compile()``.\n\n        .. warning::\n           Python regular expressions use a different syntax and different\n           set of flags than MongoDB, which uses `PCRE`_. A regular\n           expression retrieved from the server may not compile in\n           Python, or may match a different set of strings in Python than\n           when used in a MongoDB query.\n\n        .. _PCRE: http://www.pcre.org/\n        \"\"\"\n        if not isinstance(regex, RE_TYPE):\n            raise TypeError(\n                \"regex must be a compiled regular expression, not %s\"\n                % type(regex))\n\n        return Regex(regex.pattern, regex.flags)\n\n    def __init__(self, pattern, flags=0):\n        \"\"\"BSON regular expression data.\n\n        This class is useful to store and retrieve regular expressions that are\n        incompatible with Python's regular expression dialect.\n\n        :Parameters:\n          - `pattern`: string\n          - `flags`: (optional) an integer bitmask, or a string of flag\n            characters like \"im\" for IGNORECASE and MULTILINE\n        \"\"\"\n        if not isinstance(pattern, (text_type, bytes)):\n            raise TypeError(\"pattern must be a string, not %s\" % type(pattern))\n        self.pattern = pattern\n\n        if isinstance(flags, string_type):\n            self.flags = str_flags_to_int(flags)\n        elif isinstance(flags, int):\n            self.flags = flags\n        else:\n            raise TypeError(\n                \"flags must be a string or int, not %s\" % type(flags))\n\n    def __eq__(self, other):\n        if isinstance(other, Regex):\n            return self.pattern == other.pattern and self.flags == other.flags\n        else:\n            return NotImplemented\n\n    __hash__ = None\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __repr__(self):\n        return \"Regex(%r, %r)\" % (self.pattern, self.flags)\n\n    def try_compile(self):\n        \"\"\"Compile this :class:`Regex` as a Python regular expression.\n\n        .. warning::\n           Python regular expressions use a different syntax and different\n           set of flags than MongoDB, which uses `PCRE`_. A regular\n           expression retrieved from the server may not compile in\n           Python, or may match a different set of strings in Python than\n           when used in a MongoDB query. :meth:`try_compile()` may raise\n           :exc:`re.error`.\n\n        .. _PCRE: http://www.pcre.org/\n        \"\"\"\n        return re.compile(self.pattern, self.flags)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/son.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for creating and manipulating SON, the Serialized Ocument Notation.\n\nRegular dictionaries can be used instead of SON objects, but not when the order\nof keys is important. A SON object can be used just like a normal Python\ndictionary.\"\"\"\n\nimport copy\nimport re\n\nfrom bson.py3compat import abc, iteritems\n\n\n# This sort of sucks, but seems to be as good as it gets...\n# This is essentially the same as re._pattern_type\nRE_TYPE = type(re.compile(\"\"))\n\n\nclass SON(dict):\n    \"\"\"SON data.\n\n    A subclass of dict that maintains ordering of keys and provides a\n    few extra niceties for dealing with SON. SON provides an API\n    similar to collections.OrderedDict from Python 2.7+.\n    \"\"\"\n\n    def __init__(self, data=None, **kwargs):\n        self.__keys = []\n        dict.__init__(self)\n        self.update(data)\n        self.update(kwargs)\n\n    def __new__(cls, *args, **kwargs):\n        instance = super(SON, cls).__new__(cls, *args, **kwargs)\n        instance.__keys = []\n        return instance\n\n    def __repr__(self):\n        result = []\n        for key in self.__keys:\n            result.append(\"(%r, %r)\" % (key, self[key]))\n        return \"SON([%s])\" % \", \".join(result)\n\n    def __setitem__(self, key, value):\n        if key not in self.__keys:\n            self.__keys.append(key)\n        dict.__setitem__(self, key, value)\n\n    def __delitem__(self, key):\n        self.__keys.remove(key)\n        dict.__delitem__(self, key)\n\n    def keys(self):\n        return list(self.__keys)\n\n    def copy(self):\n        other = SON()\n        other.update(self)\n        return other\n\n    # TODO this is all from UserDict.DictMixin. it could probably be made more\n    # efficient.\n    # second level definitions support higher levels\n    def __iter__(self):\n        for k in self.__keys:\n            yield k\n\n    def has_key(self, key):\n        return key in self.__keys\n\n    # third level takes advantage of second level definitions\n    def iteritems(self):\n        for k in self:\n            yield (k, self[k])\n\n    def iterkeys(self):\n        return self.__iter__()\n\n    # fourth level uses definitions from lower levels\n    def itervalues(self):\n        for _, v in self.iteritems():\n            yield v\n\n    def values(self):\n        return [v for _, v in self.iteritems()]\n\n    def items(self):\n        return [(key, self[key]) for key in self]\n\n    def clear(self):\n        self.__keys = []\n        super(SON, self).clear()\n\n    def setdefault(self, key, default=None):\n        try:\n            return self[key]\n        except KeyError:\n            self[key] = default\n        return default\n\n    def pop(self, key, *args):\n        if len(args) > 1:\n            raise TypeError(\"pop expected at most 2 arguments, got \"\\\n                                + repr(1 + len(args)))\n        try:\n            value = self[key]\n        except KeyError:\n            if args:\n                return args[0]\n            raise\n        del self[key]\n        return value\n\n    def popitem(self):\n        try:\n            k, v = next(self.iteritems())\n        except StopIteration:\n            raise KeyError('container is empty')\n        del self[k]\n        return (k, v)\n\n    def update(self, other=None, **kwargs):\n        # Make progressively weaker assumptions about \"other\"\n        if other is None:\n            pass\n        elif hasattr(other, 'iteritems'):  # iteritems saves memory and lookups\n            for k, v in other.iteritems():\n                self[k] = v\n        elif hasattr(other, 'keys'):\n            for k in other.keys():\n                self[k] = other[k]\n        else:\n            for k, v in other:\n                self[k] = v\n        if kwargs:\n            self.update(kwargs)\n\n    def get(self, key, default=None):\n        try:\n            return self[key]\n        except KeyError:\n            return default\n\n    def __eq__(self, other):\n        \"\"\"Comparison to another SON is order-sensitive while comparison to a\n        regular dictionary is order-insensitive.\n        \"\"\"\n        if isinstance(other, SON):\n            return len(self) == len(other) and self.items() == other.items()\n        return self.to_dict() == other\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __len__(self):\n        return len(self.__keys)\n\n    def to_dict(self):\n        \"\"\"Convert a SON document to a normal Python dictionary instance.\n\n        This is trickier than just *dict(...)* because it needs to be\n        recursive.\n        \"\"\"\n\n        def transform_value(value):\n            if isinstance(value, list):\n                return [transform_value(v) for v in value]\n            elif isinstance(value, abc.Mapping):\n                return dict([\n                    (k, transform_value(v))\n                    for k, v in iteritems(value)])\n            else:\n                return value\n\n        return transform_value(dict(self))\n\n    def __deepcopy__(self, memo):\n        out = SON()\n        val_id = id(self)\n        if val_id in memo:\n            return memo.get(val_id)\n        memo[val_id] = out\n        for k, v in self.iteritems():\n            if not isinstance(v, RE_TYPE):\n                v = copy.deepcopy(v, memo)\n            out[k] = v\n        return out\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/timestamp.py",
    "content": "# Copyright 2010-2015 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for representing MongoDB internal Timestamps.\n\"\"\"\n\nimport calendar\nimport datetime\n\nfrom bson.py3compat import integer_types\nfrom bson.tz_util import utc\n\nUPPERBOUND = 4294967296\n\n\nclass Timestamp(object):\n    \"\"\"MongoDB internal timestamps used in the opLog.\n    \"\"\"\n\n    _type_marker = 17\n\n    def __init__(self, time, inc):\n        \"\"\"Create a new :class:`Timestamp`.\n\n        This class is only for use with the MongoDB opLog. If you need\n        to store a regular timestamp, please use a\n        :class:`~datetime.datetime`.\n\n        Raises :class:`TypeError` if `time` is not an instance of\n        :class: `int` or :class:`~datetime.datetime`, or `inc` is not\n        an instance of :class:`int`. Raises :class:`ValueError` if\n        `time` or `inc` is not in [0, 2**32).\n\n        :Parameters:\n          - `time`: time in seconds since epoch UTC, or a naive UTC\n            :class:`~datetime.datetime`, or an aware\n            :class:`~datetime.datetime`\n          - `inc`: the incrementing counter\n        \"\"\"\n        if isinstance(time, datetime.datetime):\n            if time.utcoffset() is not None:\n                time = time - time.utcoffset()\n            time = int(calendar.timegm(time.timetuple()))\n        if not isinstance(time, integer_types):\n            raise TypeError(\"time must be an instance of int\")\n        if not isinstance(inc, integer_types):\n            raise TypeError(\"inc must be an instance of int\")\n        if not 0 <= time < UPPERBOUND:\n            raise ValueError(\"time must be contained in [0, 2**32)\")\n        if not 0 <= inc < UPPERBOUND:\n            raise ValueError(\"inc must be contained in [0, 2**32)\")\n\n        self.__time = time\n        self.__inc = inc\n\n    @property\n    def time(self):\n        \"\"\"Get the time portion of this :class:`Timestamp`.\n        \"\"\"\n        return self.__time\n\n    @property\n    def inc(self):\n        \"\"\"Get the inc portion of this :class:`Timestamp`.\n        \"\"\"\n        return self.__inc\n\n    def __eq__(self, other):\n        if isinstance(other, Timestamp):\n            return (self.__time == other.time and self.__inc == other.inc)\n        else:\n            return NotImplemented\n\n    def __hash__(self):\n        return hash(self.time) ^ hash(self.inc)\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __lt__(self, other):\n        if isinstance(other, Timestamp):\n            return (self.time, self.inc) < (other.time, other.inc)\n        return NotImplemented\n\n    def __le__(self, other):\n        if isinstance(other, Timestamp):\n            return (self.time, self.inc) <= (other.time, other.inc)\n        return NotImplemented\n\n    def __gt__(self, other):\n        if isinstance(other, Timestamp):\n            return (self.time, self.inc) > (other.time, other.inc)\n        return NotImplemented\n\n    def __ge__(self, other):\n        if isinstance(other, Timestamp):\n            return (self.time, self.inc) >= (other.time, other.inc)\n        return NotImplemented\n\n    def __repr__(self):\n        return \"Timestamp(%s, %s)\" % (self.__time, self.__inc)\n\n    def as_datetime(self):\n        \"\"\"Return a :class:`~datetime.datetime` instance corresponding\n        to the time portion of this :class:`Timestamp`.\n\n        The returned datetime's timezone is UTC.\n        \"\"\"\n        return datetime.datetime.fromtimestamp(self.__time, utc)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/bson/tz_util.py",
    "content": "# Copyright 2010-2015 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Timezone related utilities for BSON.\"\"\"\n\nfrom datetime import (timedelta,\n                      tzinfo)\n\nZERO = timedelta(0)\n\n\nclass FixedOffset(tzinfo):\n    \"\"\"Fixed offset timezone, in minutes east from UTC.\n\n    Implementation based from the Python `standard library documentation\n    <http://docs.python.org/library/datetime.html#tzinfo-objects>`_.\n    Defining __getinitargs__ enables pickling / copying.\n    \"\"\"\n\n    def __init__(self, offset, name):\n        if isinstance(offset, timedelta):\n            self.__offset = offset\n        else:\n            self.__offset = timedelta(minutes=offset)\n        self.__name = name\n\n    def __getinitargs__(self):\n        return self.__offset, self.__name\n\n    def utcoffset(self, dt):\n        return self.__offset\n\n    def tzname(self, dt):\n        return self.__name\n\n    def dst(self, dt):\n        return ZERO\n\n\nutc = FixedOffset(0, \"UTC\")\n\"\"\"Fixed offset timezone representing UTC.\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/__init__.py",
    "content": "__all__ = ['FFI', 'VerificationError', 'VerificationMissing', 'CDefError',\n           'FFIError']\n\nfrom .api import FFI\nfrom .error import CDefError, FFIError, VerificationError, VerificationMissing\nfrom .error import PkgConfigError\n\n__version__ = \"1.13.1\"\n__version_info__ = (1, 13, 1)\n\n# The verifier module file names are based on the CRC32 of a string that\n# contains the following version number.  It may be older than __version__\n# if nothing is clearly incompatible.\n__version_verifier_modules__ = \"0.8.6\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/_cffi_errors.h",
    "content": "#ifndef CFFI_MESSAGEBOX\n# ifdef _MSC_VER\n#  define CFFI_MESSAGEBOX  1\n# else\n#  define CFFI_MESSAGEBOX  0\n# endif\n#endif\n\n\n#if CFFI_MESSAGEBOX\n/* Windows only: logic to take the Python-CFFI embedding logic\n   initialization errors and display them in a background thread\n   with MessageBox.  The idea is that if the whole program closes\n   as a result of this problem, then likely it is already a console\n   program and you can read the stderr output in the console too.\n   If it is not a console program, then it will likely show its own\n   dialog to complain, or generally not abruptly close, and for this\n   case the background thread should stay alive.\n*/\nstatic void *volatile _cffi_bootstrap_text;\n\nstatic PyObject *_cffi_start_error_capture(void)\n{\n    PyObject *result = NULL;\n    PyObject *x, *m, *bi;\n\n    if (InterlockedCompareExchangePointer(&_cffi_bootstrap_text,\n            (void *)1, NULL) != NULL)\n        return (PyObject *)1;\n\n    m = PyImport_AddModule(\"_cffi_error_capture\");\n    if (m == NULL)\n        goto error;\n\n    result = PyModule_GetDict(m);\n    if (result == NULL)\n        goto error;\n\n#if PY_MAJOR_VERSION >= 3\n    bi = PyImport_ImportModule(\"builtins\");\n#else\n    bi = PyImport_ImportModule(\"__builtin__\");\n#endif\n    if (bi == NULL)\n        goto error;\n    PyDict_SetItemString(result, \"__builtins__\", bi);\n    Py_DECREF(bi);\n\n    x = PyRun_String(\n        \"import sys\\n\"\n        \"class FileLike:\\n\"\n        \"  def write(self, x):\\n\"\n        \"    try:\\n\"\n        \"      of.write(x)\\n\"\n        \"    except: pass\\n\"\n        \"    self.buf += x\\n\"\n        \"fl = FileLike()\\n\"\n        \"fl.buf = ''\\n\"\n        \"of = sys.stderr\\n\"\n        \"sys.stderr = fl\\n\"\n        \"def done():\\n\"\n        \"  sys.stderr = of\\n\"\n        \"  return fl.buf\\n\",   /* make sure the returned value stays alive */\n        Py_file_input,\n        result, result);\n    Py_XDECREF(x);\n\n error:\n    if (PyErr_Occurred())\n    {\n        PyErr_WriteUnraisable(Py_None);\n        PyErr_Clear();\n    }\n    return result;\n}\n\n#pragma comment(lib, \"user32.lib\")\n\nstatic DWORD WINAPI _cffi_bootstrap_dialog(LPVOID ignored)\n{\n    Sleep(666);    /* may be interrupted if the whole process is closing */\n#if PY_MAJOR_VERSION >= 3\n    MessageBoxW(NULL, (wchar_t *)_cffi_bootstrap_text,\n                L\"Python-CFFI error\",\n                MB_OK | MB_ICONERROR);\n#else\n    MessageBoxA(NULL, (char *)_cffi_bootstrap_text,\n                \"Python-CFFI error\",\n                MB_OK | MB_ICONERROR);\n#endif\n    _cffi_bootstrap_text = NULL;\n    return 0;\n}\n\nstatic void _cffi_stop_error_capture(PyObject *ecap)\n{\n    PyObject *s;\n    void *text;\n\n    if (ecap == (PyObject *)1)\n        return;\n\n    if (ecap == NULL)\n        goto error;\n\n    s = PyRun_String(\"done()\", Py_eval_input, ecap, ecap);\n    if (s == NULL)\n        goto error;\n\n    /* Show a dialog box, but in a background thread, and\n       never show multiple dialog boxes at once. */\n#if PY_MAJOR_VERSION >= 3\n    text = PyUnicode_AsWideCharString(s, NULL);\n#else\n    text = PyString_AsString(s);\n#endif\n\n    _cffi_bootstrap_text = text;\n\n    if (text != NULL)\n    {\n        HANDLE h;\n        h = CreateThread(NULL, 0, _cffi_bootstrap_dialog,\n                         NULL, 0, NULL);\n        if (h != NULL)\n            CloseHandle(h);\n    }\n    /* decref the string, but it should stay alive as 'fl.buf'\n       in the small module above.  It will really be freed only if\n       we later get another similar error.  So it's a leak of at\n       most one copy of the small module.  That's fine for this\n       situation which is usually a \"fatal error\" anyway. */\n    Py_DECREF(s);\n    PyErr_Clear();\n    return;\n\n  error:\n    _cffi_bootstrap_text = NULL;\n    PyErr_Clear();\n}\n\n#else\n\nstatic PyObject *_cffi_start_error_capture(void) { return NULL; }\nstatic void _cffi_stop_error_capture(PyObject *ecap) { }\n\n#endif\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/_cffi_include.h",
    "content": "#define _CFFI_\n\n/* We try to define Py_LIMITED_API before including Python.h.\n\n   Mess: we can only define it if Py_DEBUG, Py_TRACE_REFS and\n   Py_REF_DEBUG are not defined.  This is a best-effort approximation:\n   we can learn about Py_DEBUG from pyconfig.h, but it is unclear if\n   the same works for the other two macros.  Py_DEBUG implies them,\n   but not the other way around.\n\n   Issue #350 is still open: on Windows, the code here causes it to link\n   with PYTHON36.DLL (for example) instead of PYTHON3.DLL.  A fix was\n   attempted in 164e526a5515 and 14ce6985e1c3, but reverted: virtualenv\n   does not make PYTHON3.DLL available, and so the \"correctly\" compiled\n   version would not run inside a virtualenv.  We will re-apply the fix\n   after virtualenv has been fixed for some time.  For explanation, see\n   issue #355.  For a workaround if you want PYTHON3.DLL and don't worry\n   about virtualenv, see issue #350.  See also 'py_limited_api' in\n   setuptools_ext.py.\n*/\n#if !defined(_CFFI_USE_EMBEDDING) && !defined(Py_LIMITED_API)\n#  include <pyconfig.h>\n#  if !defined(Py_DEBUG) && !defined(Py_TRACE_REFS) && !defined(Py_REF_DEBUG)\n#    define Py_LIMITED_API\n#  endif\n#endif\n\n#include <Python.h>\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n#include <stddef.h>\n#include \"parse_c_type.h\"\n\n/* this block of #ifs should be kept exactly identical between\n   c/_cffi_backend.c, cffi/vengine_cpy.py, cffi/vengine_gen.py\n   and cffi/_cffi_include.h */\n#if defined(_MSC_VER)\n# include <malloc.h>   /* for alloca() */\n# if _MSC_VER < 1600   /* MSVC < 2010 */\n   typedef __int8 int8_t;\n   typedef __int16 int16_t;\n   typedef __int32 int32_t;\n   typedef __int64 int64_t;\n   typedef unsigned __int8 uint8_t;\n   typedef unsigned __int16 uint16_t;\n   typedef unsigned __int32 uint32_t;\n   typedef unsigned __int64 uint64_t;\n   typedef __int8 int_least8_t;\n   typedef __int16 int_least16_t;\n   typedef __int32 int_least32_t;\n   typedef __int64 int_least64_t;\n   typedef unsigned __int8 uint_least8_t;\n   typedef unsigned __int16 uint_least16_t;\n   typedef unsigned __int32 uint_least32_t;\n   typedef unsigned __int64 uint_least64_t;\n   typedef __int8 int_fast8_t;\n   typedef __int16 int_fast16_t;\n   typedef __int32 int_fast32_t;\n   typedef __int64 int_fast64_t;\n   typedef unsigned __int8 uint_fast8_t;\n   typedef unsigned __int16 uint_fast16_t;\n   typedef unsigned __int32 uint_fast32_t;\n   typedef unsigned __int64 uint_fast64_t;\n   typedef __int64 intmax_t;\n   typedef unsigned __int64 uintmax_t;\n# else\n#  include <stdint.h>\n# endif\n# if _MSC_VER < 1800   /* MSVC < 2013 */\n#  ifndef __cplusplus\n    typedef unsigned char _Bool;\n#  endif\n# endif\n#else\n# include <stdint.h>\n# if (defined (__SVR4) && defined (__sun)) || defined(_AIX) || defined(__hpux)\n#  include <alloca.h>\n# endif\n#endif\n\n#ifdef __GNUC__\n# define _CFFI_UNUSED_FN  __attribute__((unused))\n#else\n# define _CFFI_UNUSED_FN  /* nothing */\n#endif\n\n#ifdef __cplusplus\n# ifndef _Bool\n   typedef bool _Bool;   /* semi-hackish: C++ has no _Bool; bool is builtin */\n# endif\n#endif\n\n/**********  CPython-specific section  **********/\n#ifndef PYPY_VERSION\n\n\n#if PY_MAJOR_VERSION >= 3\n# define PyInt_FromLong PyLong_FromLong\n#endif\n\n#define _cffi_from_c_double PyFloat_FromDouble\n#define _cffi_from_c_float PyFloat_FromDouble\n#define _cffi_from_c_long PyInt_FromLong\n#define _cffi_from_c_ulong PyLong_FromUnsignedLong\n#define _cffi_from_c_longlong PyLong_FromLongLong\n#define _cffi_from_c_ulonglong PyLong_FromUnsignedLongLong\n#define _cffi_from_c__Bool PyBool_FromLong\n\n#define _cffi_to_c_double PyFloat_AsDouble\n#define _cffi_to_c_float PyFloat_AsDouble\n\n#define _cffi_from_c_int(x, type)                                        \\\n    (((type)-1) > 0 ? /* unsigned */                                     \\\n        (sizeof(type) < sizeof(long) ?                                   \\\n            PyInt_FromLong((long)x) :                                    \\\n         sizeof(type) == sizeof(long) ?                                  \\\n            PyLong_FromUnsignedLong((unsigned long)x) :                  \\\n            PyLong_FromUnsignedLongLong((unsigned long long)x)) :        \\\n        (sizeof(type) <= sizeof(long) ?                                  \\\n            PyInt_FromLong((long)x) :                                    \\\n            PyLong_FromLongLong((long long)x)))\n\n#define _cffi_to_c_int(o, type)                                          \\\n    ((type)(                                                             \\\n     sizeof(type) == 1 ? (((type)-1) > 0 ? (type)_cffi_to_c_u8(o)        \\\n                                         : (type)_cffi_to_c_i8(o)) :     \\\n     sizeof(type) == 2 ? (((type)-1) > 0 ? (type)_cffi_to_c_u16(o)       \\\n                                         : (type)_cffi_to_c_i16(o)) :    \\\n     sizeof(type) == 4 ? (((type)-1) > 0 ? (type)_cffi_to_c_u32(o)       \\\n                                         : (type)_cffi_to_c_i32(o)) :    \\\n     sizeof(type) == 8 ? (((type)-1) > 0 ? (type)_cffi_to_c_u64(o)       \\\n                                         : (type)_cffi_to_c_i64(o)) :    \\\n     (Py_FatalError(\"unsupported size for type \" #type), (type)0)))\n\n#define _cffi_to_c_i8                                                    \\\n                 ((int(*)(PyObject *))_cffi_exports[1])\n#define _cffi_to_c_u8                                                    \\\n                 ((int(*)(PyObject *))_cffi_exports[2])\n#define _cffi_to_c_i16                                                   \\\n                 ((int(*)(PyObject *))_cffi_exports[3])\n#define _cffi_to_c_u16                                                   \\\n                 ((int(*)(PyObject *))_cffi_exports[4])\n#define _cffi_to_c_i32                                                   \\\n                 ((int(*)(PyObject *))_cffi_exports[5])\n#define _cffi_to_c_u32                                                   \\\n                 ((unsigned int(*)(PyObject *))_cffi_exports[6])\n#define _cffi_to_c_i64                                                   \\\n                 ((long long(*)(PyObject *))_cffi_exports[7])\n#define _cffi_to_c_u64                                                   \\\n                 ((unsigned long long(*)(PyObject *))_cffi_exports[8])\n#define _cffi_to_c_char                                                  \\\n                 ((int(*)(PyObject *))_cffi_exports[9])\n#define _cffi_from_c_pointer                                             \\\n    ((PyObject *(*)(char *, struct _cffi_ctypedescr *))_cffi_exports[10])\n#define _cffi_to_c_pointer                                               \\\n    ((char *(*)(PyObject *, struct _cffi_ctypedescr *))_cffi_exports[11])\n#define _cffi_get_struct_layout                                          \\\n    not used any more\n#define _cffi_restore_errno                                              \\\n    ((void(*)(void))_cffi_exports[13])\n#define _cffi_save_errno                                                 \\\n    ((void(*)(void))_cffi_exports[14])\n#define _cffi_from_c_char                                                \\\n    ((PyObject *(*)(char))_cffi_exports[15])\n#define _cffi_from_c_deref                                               \\\n    ((PyObject *(*)(char *, struct _cffi_ctypedescr *))_cffi_exports[16])\n#define _cffi_to_c                                                       \\\n    ((int(*)(char *, struct _cffi_ctypedescr *, PyObject *))_cffi_exports[17])\n#define _cffi_from_c_struct                                              \\\n    ((PyObject *(*)(char *, struct _cffi_ctypedescr *))_cffi_exports[18])\n#define _cffi_to_c_wchar_t                                               \\\n    ((_cffi_wchar_t(*)(PyObject *))_cffi_exports[19])\n#define _cffi_from_c_wchar_t                                             \\\n    ((PyObject *(*)(_cffi_wchar_t))_cffi_exports[20])\n#define _cffi_to_c_long_double                                           \\\n    ((long double(*)(PyObject *))_cffi_exports[21])\n#define _cffi_to_c__Bool                                                 \\\n    ((_Bool(*)(PyObject *))_cffi_exports[22])\n#define _cffi_prepare_pointer_call_argument                              \\\n    ((Py_ssize_t(*)(struct _cffi_ctypedescr *,                           \\\n                    PyObject *, char **))_cffi_exports[23])\n#define _cffi_convert_array_from_object                                  \\\n    ((int(*)(char *, struct _cffi_ctypedescr *, PyObject *))_cffi_exports[24])\n#define _CFFI_CPIDX  25\n#define _cffi_call_python                                                \\\n    ((void(*)(struct _cffi_externpy_s *, char *))_cffi_exports[_CFFI_CPIDX])\n#define _cffi_to_c_wchar3216_t                                           \\\n    ((int(*)(PyObject *))_cffi_exports[26])\n#define _cffi_from_c_wchar3216_t                                         \\\n    ((PyObject *(*)(int))_cffi_exports[27])\n#define _CFFI_NUM_EXPORTS 28\n\nstruct _cffi_ctypedescr;\n\nstatic void *_cffi_exports[_CFFI_NUM_EXPORTS];\n\n#define _cffi_type(index)   (                           \\\n    assert((((uintptr_t)_cffi_types[index]) & 1) == 0), \\\n    (struct _cffi_ctypedescr *)_cffi_types[index])\n\nstatic PyObject *_cffi_init(const char *module_name, Py_ssize_t version,\n                            const struct _cffi_type_context_s *ctx)\n{\n    PyObject *module, *o_arg, *new_module;\n    void *raw[] = {\n        (void *)module_name,\n        (void *)version,\n        (void *)_cffi_exports,\n        (void *)ctx,\n    };\n\n    module = PyImport_ImportModule(\"_cffi_backend\");\n    if (module == NULL)\n        goto failure;\n\n    o_arg = PyLong_FromVoidPtr((void *)raw);\n    if (o_arg == NULL)\n        goto failure;\n\n    new_module = PyObject_CallMethod(\n        module, (char *)\"_init_cffi_1_0_external_module\", (char *)\"O\", o_arg);\n\n    Py_DECREF(o_arg);\n    Py_DECREF(module);\n    return new_module;\n\n  failure:\n    Py_XDECREF(module);\n    return NULL;\n}\n\n\n#ifdef HAVE_WCHAR_H\ntypedef wchar_t _cffi_wchar_t;\n#else\ntypedef uint16_t _cffi_wchar_t;   /* same random pick as _cffi_backend.c */\n#endif\n\n_CFFI_UNUSED_FN static uint16_t _cffi_to_c_char16_t(PyObject *o)\n{\n    if (sizeof(_cffi_wchar_t) == 2)\n        return (uint16_t)_cffi_to_c_wchar_t(o);\n    else\n        return (uint16_t)_cffi_to_c_wchar3216_t(o);\n}\n\n_CFFI_UNUSED_FN static PyObject *_cffi_from_c_char16_t(uint16_t x)\n{\n    if (sizeof(_cffi_wchar_t) == 2)\n        return _cffi_from_c_wchar_t((_cffi_wchar_t)x);\n    else\n        return _cffi_from_c_wchar3216_t((int)x);\n}\n\n_CFFI_UNUSED_FN static int _cffi_to_c_char32_t(PyObject *o)\n{\n    if (sizeof(_cffi_wchar_t) == 4)\n        return (int)_cffi_to_c_wchar_t(o);\n    else\n        return (int)_cffi_to_c_wchar3216_t(o);\n}\n\n_CFFI_UNUSED_FN static PyObject *_cffi_from_c_char32_t(int x)\n{\n    if (sizeof(_cffi_wchar_t) == 4)\n        return _cffi_from_c_wchar_t((_cffi_wchar_t)x);\n    else\n        return _cffi_from_c_wchar3216_t(x);\n}\n\n\n/**********  end CPython-specific section  **********/\n#else\n_CFFI_UNUSED_FN\nstatic void (*_cffi_call_python_org)(struct _cffi_externpy_s *, char *);\n# define _cffi_call_python  _cffi_call_python_org\n#endif\n\n\n#define _cffi_array_len(array)   (sizeof(array) / sizeof((array)[0]))\n\n#define _cffi_prim_int(size, sign)                                      \\\n    ((size) == 1 ? ((sign) ? _CFFI_PRIM_INT8  : _CFFI_PRIM_UINT8)  :    \\\n     (size) == 2 ? ((sign) ? _CFFI_PRIM_INT16 : _CFFI_PRIM_UINT16) :    \\\n     (size) == 4 ? ((sign) ? _CFFI_PRIM_INT32 : _CFFI_PRIM_UINT32) :    \\\n     (size) == 8 ? ((sign) ? _CFFI_PRIM_INT64 : _CFFI_PRIM_UINT64) :    \\\n     _CFFI__UNKNOWN_PRIM)\n\n#define _cffi_prim_float(size)                                          \\\n    ((size) == sizeof(float) ? _CFFI_PRIM_FLOAT :                       \\\n     (size) == sizeof(double) ? _CFFI_PRIM_DOUBLE :                     \\\n     (size) == sizeof(long double) ? _CFFI__UNKNOWN_LONG_DOUBLE :       \\\n     _CFFI__UNKNOWN_FLOAT_PRIM)\n\n#define _cffi_check_int(got, got_nonpos, expected)      \\\n    ((got_nonpos) == (expected <= 0) &&                 \\\n     (got) == (unsigned long long)expected)\n\n#ifdef MS_WIN32\n# define _cffi_stdcall  __stdcall\n#else\n# define _cffi_stdcall  /* nothing */\n#endif\n\n#ifdef __cplusplus\n}\n#endif\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/_embedding.h",
    "content": "\n/***** Support code for embedding *****/\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n\n#if defined(_WIN32)\n#  define CFFI_DLLEXPORT  __declspec(dllexport)\n#elif defined(__GNUC__)\n#  define CFFI_DLLEXPORT  __attribute__((visibility(\"default\")))\n#else\n#  define CFFI_DLLEXPORT  /* nothing */\n#endif\n\n\n/* There are two global variables of type _cffi_call_python_fnptr:\n\n   * _cffi_call_python, which we declare just below, is the one called\n     by ``extern \"Python\"`` implementations.\n\n   * _cffi_call_python_org, which on CPython is actually part of the\n     _cffi_exports[] array, is the function pointer copied from\n     _cffi_backend.\n\n   After initialization is complete, both are equal.  However, the\n   first one remains equal to &_cffi_start_and_call_python until the\n   very end of initialization, when we are (or should be) sure that\n   concurrent threads also see a completely initialized world, and\n   only then is it changed.\n*/\n#undef _cffi_call_python\ntypedef void (*_cffi_call_python_fnptr)(struct _cffi_externpy_s *, char *);\nstatic void _cffi_start_and_call_python(struct _cffi_externpy_s *, char *);\nstatic _cffi_call_python_fnptr _cffi_call_python = &_cffi_start_and_call_python;\n\n\n#ifndef _MSC_VER\n   /* --- Assuming a GCC not infinitely old --- */\n# define cffi_compare_and_swap(l,o,n)  __sync_bool_compare_and_swap(l,o,n)\n# define cffi_write_barrier()          __sync_synchronize()\n# if !defined(__amd64__) && !defined(__x86_64__) &&   \\\n     !defined(__i386__) && !defined(__i386)\n#   define cffi_read_barrier()         __sync_synchronize()\n# else\n#   define cffi_read_barrier()         (void)0\n# endif\n#else\n   /* --- Windows threads version --- */\n# include <Windows.h>\n# define cffi_compare_and_swap(l,o,n) \\\n                               (InterlockedCompareExchangePointer(l,n,o) == (o))\n# define cffi_write_barrier()       InterlockedCompareExchange(&_cffi_dummy,0,0)\n# define cffi_read_barrier()           (void)0\nstatic volatile LONG _cffi_dummy;\n#endif\n\n#ifdef WITH_THREAD\n# ifndef _MSC_VER\n#  include <pthread.h>\n   static pthread_mutex_t _cffi_embed_startup_lock;\n# else\n   static CRITICAL_SECTION _cffi_embed_startup_lock;\n# endif\n  static char _cffi_embed_startup_lock_ready = 0;\n#endif\n\nstatic void _cffi_acquire_reentrant_mutex(void)\n{\n    static void *volatile lock = NULL;\n\n    while (!cffi_compare_and_swap(&lock, NULL, (void *)1)) {\n        /* should ideally do a spin loop instruction here, but\n           hard to do it portably and doesn't really matter I\n           think: pthread_mutex_init() should be very fast, and\n           this is only run at start-up anyway. */\n    }\n\n#ifdef WITH_THREAD\n    if (!_cffi_embed_startup_lock_ready) {\n# ifndef _MSC_VER\n        pthread_mutexattr_t attr;\n        pthread_mutexattr_init(&attr);\n        pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_RECURSIVE);\n        pthread_mutex_init(&_cffi_embed_startup_lock, &attr);\n# else\n        InitializeCriticalSection(&_cffi_embed_startup_lock);\n# endif\n        _cffi_embed_startup_lock_ready = 1;\n    }\n#endif\n\n    while (!cffi_compare_and_swap(&lock, (void *)1, NULL))\n        ;\n\n#ifndef _MSC_VER\n    pthread_mutex_lock(&_cffi_embed_startup_lock);\n#else\n    EnterCriticalSection(&_cffi_embed_startup_lock);\n#endif\n}\n\nstatic void _cffi_release_reentrant_mutex(void)\n{\n#ifndef _MSC_VER\n    pthread_mutex_unlock(&_cffi_embed_startup_lock);\n#else\n    LeaveCriticalSection(&_cffi_embed_startup_lock);\n#endif\n}\n\n\n/**********  CPython-specific section  **********/\n#ifndef PYPY_VERSION\n\n#include \"_cffi_errors.h\"\n\n\n#define _cffi_call_python_org  _cffi_exports[_CFFI_CPIDX]\n\nPyMODINIT_FUNC _CFFI_PYTHON_STARTUP_FUNC(void);   /* forward */\n\nstatic void _cffi_py_initialize(void)\n{\n    /* XXX use initsigs=0, which \"skips initialization registration of\n       signal handlers, which might be useful when Python is\n       embedded\" according to the Python docs.  But review and think\n       if it should be a user-controllable setting.\n\n       XXX we should also give a way to write errors to a buffer\n       instead of to stderr.\n\n       XXX if importing 'site' fails, CPython (any version) calls\n       exit().  Should we try to work around this behavior here?\n    */\n    Py_InitializeEx(0);\n}\n\nstatic int _cffi_initialize_python(void)\n{\n    /* This initializes Python, imports _cffi_backend, and then the\n       present .dll/.so is set up as a CPython C extension module.\n    */\n    int result;\n    PyGILState_STATE state;\n    PyObject *pycode=NULL, *global_dict=NULL, *x;\n    PyObject *builtins;\n\n    state = PyGILState_Ensure();\n\n    /* Call the initxxx() function from the present module.  It will\n       create and initialize us as a CPython extension module, instead\n       of letting the startup Python code do it---it might reimport\n       the same .dll/.so and get maybe confused on some platforms.\n       It might also have troubles locating the .dll/.so again for all\n       I know.\n    */\n    (void)_CFFI_PYTHON_STARTUP_FUNC();\n    if (PyErr_Occurred())\n        goto error;\n\n    /* Now run the Python code provided to ffi.embedding_init_code().\n     */\n    pycode = Py_CompileString(_CFFI_PYTHON_STARTUP_CODE,\n                              \"<init code for '\" _CFFI_MODULE_NAME \"'>\",\n                              Py_file_input);\n    if (pycode == NULL)\n        goto error;\n    global_dict = PyDict_New();\n    if (global_dict == NULL)\n        goto error;\n    builtins = PyEval_GetBuiltins();\n    if (builtins == NULL)\n        goto error;\n    if (PyDict_SetItemString(global_dict, \"__builtins__\", builtins) < 0)\n        goto error;\n    x = PyEval_EvalCode(\n#if PY_MAJOR_VERSION < 3\n                        (PyCodeObject *)\n#endif\n                        pycode, global_dict, global_dict);\n    if (x == NULL)\n        goto error;\n    Py_DECREF(x);\n\n    /* Done!  Now if we've been called from\n       _cffi_start_and_call_python() in an ``extern \"Python\"``, we can\n       only hope that the Python code did correctly set up the\n       corresponding @ffi.def_extern() function.  Otherwise, the\n       general logic of ``extern \"Python\"`` functions (inside the\n       _cffi_backend module) will find that the reference is still\n       missing and print an error.\n     */\n    result = 0;\n done:\n    Py_XDECREF(pycode);\n    Py_XDECREF(global_dict);\n    PyGILState_Release(state);\n    return result;\n\n error:;\n    {\n        /* Print as much information as potentially useful.\n           Debugging load-time failures with embedding is not fun\n        */\n        PyObject *ecap;\n        PyObject *exception, *v, *tb, *f, *modules, *mod;\n        PyErr_Fetch(&exception, &v, &tb);\n        ecap = _cffi_start_error_capture();\n        f = PySys_GetObject((char *)\"stderr\");\n        if (f != NULL && f != Py_None) {\n            PyFile_WriteString(\n                \"Failed to initialize the Python-CFFI embedding logic:\\n\\n\", f);\n        }\n\n        if (exception != NULL) {\n            PyErr_NormalizeException(&exception, &v, &tb);\n            PyErr_Display(exception, v, tb);\n        }\n        Py_XDECREF(exception);\n        Py_XDECREF(v);\n        Py_XDECREF(tb);\n\n        if (f != NULL && f != Py_None) {\n            PyFile_WriteString(\"\\nFrom: \" _CFFI_MODULE_NAME\n                               \"\\ncompiled with cffi version: 1.13.1\"\n                               \"\\n_cffi_backend module: \", f);\n            modules = PyImport_GetModuleDict();\n            mod = PyDict_GetItemString(modules, \"_cffi_backend\");\n            if (mod == NULL) {\n                PyFile_WriteString(\"not loaded\", f);\n            }\n            else {\n                v = PyObject_GetAttrString(mod, \"__file__\");\n                PyFile_WriteObject(v, f, 0);\n                Py_XDECREF(v);\n            }\n            PyFile_WriteString(\"\\nsys.path: \", f);\n            PyFile_WriteObject(PySys_GetObject((char *)\"path\"), f, 0);\n            PyFile_WriteString(\"\\n\\n\", f);\n        }\n        _cffi_stop_error_capture(ecap);\n    }\n    result = -1;\n    goto done;\n}\n\nPyAPI_DATA(char *) _PyParser_TokenNames[];  /* from CPython */\n\nstatic int _cffi_carefully_make_gil(void)\n{\n    /* This does the basic initialization of Python.  It can be called\n       completely concurrently from unrelated threads.  It assumes\n       that we don't hold the GIL before (if it exists), and we don't\n       hold it afterwards.\n\n       (What it really does used to be completely different in Python 2\n       and Python 3, with the Python 2 solution avoiding the spin-lock\n       around the Py_InitializeEx() call.  However, after recent changes\n       to CPython 2.7 (issue #358) it no longer works.  So we use the\n       Python 3 solution everywhere.)\n\n       This initializes Python by calling Py_InitializeEx().\n       Important: this must not be called concurrently at all.\n       So we use a global variable as a simple spin lock.  This global\n       variable must be from 'libpythonX.Y.so', not from this\n       cffi-based extension module, because it must be shared from\n       different cffi-based extension modules.\n\n       In Python < 3.8, we choose\n       _PyParser_TokenNames[0] as a completely arbitrary pointer value\n       that is never written to.  The default is to point to the\n       string \"ENDMARKER\".  We change it temporarily to point to the\n       next character in that string.  (Yes, I know it's REALLY\n       obscure.)\n\n       In Python >= 3.8, this string array is no longer writable, so\n       instead we pick PyCapsuleType.tp_version_tag.  We can't change\n       Python < 3.8 because someone might use a mixture of cffi\n       embedded modules, some of which were compiled before this file\n       changed.\n    */\n\n#ifdef WITH_THREAD\n# if PY_VERSION_HEX < 0x03080000\n    char *volatile *lock = (char *volatile *)_PyParser_TokenNames;\n    char *old_value, *locked_value;\n\n    while (1) {    /* spin loop */\n        old_value = *lock;\n        locked_value = old_value + 1;\n        if (old_value[0] == 'E') {\n            assert(old_value[1] == 'N');\n            if (cffi_compare_and_swap(lock, old_value, locked_value))\n                break;\n        }\n        else {\n            assert(old_value[0] == 'N');\n            /* should ideally do a spin loop instruction here, but\n               hard to do it portably and doesn't really matter I\n               think: PyEval_InitThreads() should be very fast, and\n               this is only run at start-up anyway. */\n        }\n    }\n# else\n    int volatile *lock = (int volatile *)&PyCapsule_Type.tp_version_tag;\n    int old_value, locked_value;\n    assert(!(PyCapsule_Type.tp_flags & Py_TPFLAGS_HAVE_VERSION_TAG));\n\n    while (1) {    /* spin loop */\n        old_value = *lock;\n        locked_value = -42;\n        if (old_value == 0) {\n            if (cffi_compare_and_swap(lock, old_value, locked_value))\n                break;\n        }\n        else {\n            assert(old_value == locked_value);\n            /* should ideally do a spin loop instruction here, but\n               hard to do it portably and doesn't really matter I\n               think: PyEval_InitThreads() should be very fast, and\n               this is only run at start-up anyway. */\n        }\n    }\n# endif\n#endif\n\n    /* call Py_InitializeEx() */\n    if (!Py_IsInitialized()) {\n        _cffi_py_initialize();\n        PyEval_InitThreads();\n        PyEval_SaveThread();  /* release the GIL */\n        /* the returned tstate must be the one that has been stored into the\n           autoTLSkey by _PyGILState_Init() called from Py_Initialize(). */\n    }\n    else {\n        PyGILState_STATE state = PyGILState_Ensure();\n        PyEval_InitThreads();\n        PyGILState_Release(state);\n    }\n\n#ifdef WITH_THREAD\n    /* release the lock */\n    while (!cffi_compare_and_swap(lock, locked_value, old_value))\n        ;\n#endif\n\n    return 0;\n}\n\n/**********  end CPython-specific section  **********/\n\n\n#else\n\n\n/**********  PyPy-specific section  **********/\n\nPyMODINIT_FUNC _CFFI_PYTHON_STARTUP_FUNC(const void *[]);   /* forward */\n\nstatic struct _cffi_pypy_init_s {\n    const char *name;\n    void (*func)(const void *[]);\n    const char *code;\n} _cffi_pypy_init = {\n    _CFFI_MODULE_NAME,\n    (void(*)(const void *[]))_CFFI_PYTHON_STARTUP_FUNC,\n    _CFFI_PYTHON_STARTUP_CODE,\n};\n\nextern int pypy_carefully_make_gil(const char *);\nextern int pypy_init_embedded_cffi_module(int, struct _cffi_pypy_init_s *);\n\nstatic int _cffi_carefully_make_gil(void)\n{\n    return pypy_carefully_make_gil(_CFFI_MODULE_NAME);\n}\n\nstatic int _cffi_initialize_python(void)\n{\n    return pypy_init_embedded_cffi_module(0xB011, &_cffi_pypy_init);\n}\n\n/**********  end PyPy-specific section  **********/\n\n\n#endif\n\n\n#ifdef __GNUC__\n__attribute__((noinline))\n#endif\nstatic _cffi_call_python_fnptr _cffi_start_python(void)\n{\n    /* Delicate logic to initialize Python.  This function can be\n       called multiple times concurrently, e.g. when the process calls\n       its first ``extern \"Python\"`` functions in multiple threads at\n       once.  It can also be called recursively, in which case we must\n       ignore it.  We also have to consider what occurs if several\n       different cffi-based extensions reach this code in parallel\n       threads---it is a different copy of the code, then, and we\n       can't have any shared global variable unless it comes from\n       'libpythonX.Y.so'.\n\n       Idea:\n\n       * _cffi_carefully_make_gil(): \"carefully\" call\n         PyEval_InitThreads() (possibly with Py_InitializeEx() first).\n\n       * then we use a (local) custom lock to make sure that a call to this\n         cffi-based extension will wait if another call to the *same*\n         extension is running the initialization in another thread.\n         It is reentrant, so that a recursive call will not block, but\n         only one from a different thread.\n\n       * then we grab the GIL and (Python 2) we call Py_InitializeEx().\n         At this point, concurrent calls to Py_InitializeEx() are not\n         possible: we have the GIL.\n\n       * do the rest of the specific initialization, which may\n         temporarily release the GIL but not the custom lock.\n         Only release the custom lock when we are done.\n    */\n    static char called = 0;\n\n    if (_cffi_carefully_make_gil() != 0)\n        return NULL;\n\n    _cffi_acquire_reentrant_mutex();\n\n    /* Here the GIL exists, but we don't have it.  We're only protected\n       from concurrency by the reentrant mutex. */\n\n    /* This file only initializes the embedded module once, the first\n       time this is called, even if there are subinterpreters. */\n    if (!called) {\n        called = 1;  /* invoke _cffi_initialize_python() only once,\n                        but don't set '_cffi_call_python' right now,\n                        otherwise concurrent threads won't call\n                        this function at all (we need them to wait) */\n        if (_cffi_initialize_python() == 0) {\n            /* now initialization is finished.  Switch to the fast-path. */\n\n            /* We would like nobody to see the new value of\n               '_cffi_call_python' without also seeing the rest of the\n               data initialized.  However, this is not possible.  But\n               the new value of '_cffi_call_python' is the function\n               'cffi_call_python()' from _cffi_backend.  So:  */\n            cffi_write_barrier();\n            /* ^^^ we put a write barrier here, and a corresponding\n               read barrier at the start of cffi_call_python().  This\n               ensures that after that read barrier, we see everything\n               done here before the write barrier.\n            */\n\n            assert(_cffi_call_python_org != NULL);\n            _cffi_call_python = (_cffi_call_python_fnptr)_cffi_call_python_org;\n        }\n        else {\n            /* initialization failed.  Reset this to NULL, even if it was\n               already set to some other value.  Future calls to\n               _cffi_start_python() are still forced to occur, and will\n               always return NULL from now on. */\n            _cffi_call_python_org = NULL;\n        }\n    }\n\n    _cffi_release_reentrant_mutex();\n\n    return (_cffi_call_python_fnptr)_cffi_call_python_org;\n}\n\nstatic\nvoid _cffi_start_and_call_python(struct _cffi_externpy_s *externpy, char *args)\n{\n    _cffi_call_python_fnptr fnptr;\n    int current_err = errno;\n#ifdef _MSC_VER\n    int current_lasterr = GetLastError();\n#endif\n    fnptr = _cffi_start_python();\n    if (fnptr == NULL) {\n        fprintf(stderr, \"function %s() called, but initialization code \"\n                        \"failed.  Returning 0.\\n\", externpy->name);\n        memset(args, 0, externpy->size_of_result);\n    }\n#ifdef _MSC_VER\n    SetLastError(current_lasterr);\n#endif\n    errno = current_err;\n\n    if (fnptr != NULL)\n        fnptr(externpy, args);\n}\n\n\n/* The cffi_start_python() function makes sure Python is initialized\n   and our cffi module is set up.  It can be called manually from the\n   user C code.  The same effect is obtained automatically from any\n   dll-exported ``extern \"Python\"`` function.  This function returns\n   -1 if initialization failed, 0 if all is OK.  */\n_CFFI_UNUSED_FN\nstatic int cffi_start_python(void)\n{\n    if (_cffi_call_python == &_cffi_start_and_call_python) {\n        if (_cffi_start_python() == NULL)\n            return -1;\n    }\n    cffi_read_barrier();\n    return 0;\n}\n\n#undef cffi_compare_and_swap\n#undef cffi_write_barrier\n#undef cffi_read_barrier\n\n#ifdef __cplusplus\n}\n#endif\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/api.py",
    "content": "import sys, types\nfrom .lock import allocate_lock\nfrom .error import CDefError\nfrom . import model\n\ntry:\n    callable\nexcept NameError:\n    # Python 3.1\n    from collections import Callable\n    callable = lambda x: isinstance(x, Callable)\n\ntry:\n    basestring\nexcept NameError:\n    # Python 3.x\n    basestring = str\n\n_unspecified = object()\n\n\n\nclass FFI(object):\n    r'''\n    The main top-level class that you instantiate once, or once per module.\n\n    Example usage:\n\n        ffi = FFI()\n        ffi.cdef(\"\"\"\n            int printf(const char *, ...);\n        \"\"\")\n\n        C = ffi.dlopen(None)   # standard library\n        -or-\n        C = ffi.verify()  # use a C compiler: verify the decl above is right\n\n        C.printf(\"hello, %s!\\n\", ffi.new(\"char[]\", \"world\"))\n    '''\n\n    def __init__(self, backend=None):\n        \"\"\"Create an FFI instance.  The 'backend' argument is used to\n        select a non-default backend, mostly for tests.\n        \"\"\"\n        if backend is None:\n            # You need PyPy (>= 2.0 beta), or a CPython (>= 2.6) with\n            # _cffi_backend.so compiled.\n            import _cffi_backend as backend\n            from . import __version__\n            if backend.__version__ != __version__:\n                # bad version!  Try to be as explicit as possible.\n                if hasattr(backend, '__file__'):\n                    # CPython\n                    raise Exception(\"Version mismatch: this is the 'cffi' package version %s, located in %r.  When we import the top-level '_cffi_backend' extension module, we get version %s, located in %r.  The two versions should be equal; check your installation.\" % (\n                        __version__, __file__,\n                        backend.__version__, backend.__file__))\n                else:\n                    # PyPy\n                    raise Exception(\"Version mismatch: this is the 'cffi' package version %s, located in %r.  This interpreter comes with a built-in '_cffi_backend' module, which is version %s.  The two versions should be equal; check your installation.\" % (\n                        __version__, __file__, backend.__version__))\n            # (If you insist you can also try to pass the option\n            # 'backend=backend_ctypes.CTypesBackend()', but don't\n            # rely on it!  It's probably not going to work well.)\n\n        from . import cparser\n        self._backend = backend\n        self._lock = allocate_lock()\n        self._parser = cparser.Parser()\n        self._cached_btypes = {}\n        self._parsed_types = types.ModuleType('parsed_types').__dict__\n        self._new_types = types.ModuleType('new_types').__dict__\n        self._function_caches = []\n        self._libraries = []\n        self._cdefsources = []\n        self._included_ffis = []\n        self._windows_unicode = None\n        self._init_once_cache = {}\n        self._cdef_version = None\n        self._embedding = None\n        self._typecache = model.get_typecache(backend)\n        if hasattr(backend, 'set_ffi'):\n            backend.set_ffi(self)\n        for name in list(backend.__dict__):\n            if name.startswith('RTLD_'):\n                setattr(self, name, getattr(backend, name))\n        #\n        with self._lock:\n            self.BVoidP = self._get_cached_btype(model.voidp_type)\n            self.BCharA = self._get_cached_btype(model.char_array_type)\n        if isinstance(backend, types.ModuleType):\n            # _cffi_backend: attach these constants to the class\n            if not hasattr(FFI, 'NULL'):\n                FFI.NULL = self.cast(self.BVoidP, 0)\n                FFI.CData, FFI.CType = backend._get_types()\n        else:\n            # ctypes backend: attach these constants to the instance\n            self.NULL = self.cast(self.BVoidP, 0)\n            self.CData, self.CType = backend._get_types()\n        self.buffer = backend.buffer\n\n    def cdef(self, csource, override=False, packed=False, pack=None):\n        \"\"\"Parse the given C source.  This registers all declared functions,\n        types, and global variables.  The functions and global variables can\n        then be accessed via either 'ffi.dlopen()' or 'ffi.verify()'.\n        The types can be used in 'ffi.new()' and other functions.\n        If 'packed' is specified as True, all structs declared inside this\n        cdef are packed, i.e. laid out without any field alignment at all.\n        Alternatively, 'pack' can be a small integer, and requests for\n        alignment greater than that are ignored (pack=1 is equivalent to\n        packed=True).\n        \"\"\"\n        self._cdef(csource, override=override, packed=packed, pack=pack)\n\n    def embedding_api(self, csource, packed=False, pack=None):\n        self._cdef(csource, packed=packed, pack=pack, dllexport=True)\n        if self._embedding is None:\n            self._embedding = ''\n\n    def _cdef(self, csource, override=False, **options):\n        if not isinstance(csource, str):    # unicode, on Python 2\n            if not isinstance(csource, basestring):\n                raise TypeError(\"cdef() argument must be a string\")\n            csource = csource.encode('ascii')\n        with self._lock:\n            self._cdef_version = object()\n            self._parser.parse(csource, override=override, **options)\n            self._cdefsources.append(csource)\n            if override:\n                for cache in self._function_caches:\n                    cache.clear()\n            finishlist = self._parser._recomplete\n            if finishlist:\n                self._parser._recomplete = []\n                for tp in finishlist:\n                    tp.finish_backend_type(self, finishlist)\n\n    def dlopen(self, name, flags=0):\n        \"\"\"Load and return a dynamic library identified by 'name'.\n        The standard C library can be loaded by passing None.\n        Note that functions and types declared by 'ffi.cdef()' are not\n        linked to a particular library, just like C headers; in the\n        library we only look for the actual (untyped) symbols.\n        \"\"\"\n        assert isinstance(name, basestring) or name is None\n        with self._lock:\n            lib, function_cache = _make_ffi_library(self, name, flags)\n            self._function_caches.append(function_cache)\n            self._libraries.append(lib)\n        return lib\n\n    def dlclose(self, lib):\n        \"\"\"Close a library obtained with ffi.dlopen().  After this call,\n        access to functions or variables from the library will fail\n        (possibly with a segmentation fault).\n        \"\"\"\n        type(lib).__cffi_close__(lib)\n\n    def _typeof_locked(self, cdecl):\n        # call me with the lock!\n        key = cdecl\n        if key in self._parsed_types:\n            return self._parsed_types[key]\n        #\n        if not isinstance(cdecl, str):    # unicode, on Python 2\n            cdecl = cdecl.encode('ascii')\n        #\n        type = self._parser.parse_type(cdecl)\n        really_a_function_type = type.is_raw_function\n        if really_a_function_type:\n            type = type.as_function_pointer()\n        btype = self._get_cached_btype(type)\n        result = btype, really_a_function_type\n        self._parsed_types[key] = result\n        return result\n\n    def _typeof(self, cdecl, consider_function_as_funcptr=False):\n        # string -> ctype object\n        try:\n            result = self._parsed_types[cdecl]\n        except KeyError:\n            with self._lock:\n                result = self._typeof_locked(cdecl)\n        #\n        btype, really_a_function_type = result\n        if really_a_function_type and not consider_function_as_funcptr:\n            raise CDefError(\"the type %r is a function type, not a \"\n                            \"pointer-to-function type\" % (cdecl,))\n        return btype\n\n    def typeof(self, cdecl):\n        \"\"\"Parse the C type given as a string and return the\n        corresponding <ctype> object.\n        It can also be used on 'cdata' instance to get its C type.\n        \"\"\"\n        if isinstance(cdecl, basestring):\n            return self._typeof(cdecl)\n        if isinstance(cdecl, self.CData):\n            return self._backend.typeof(cdecl)\n        if isinstance(cdecl, types.BuiltinFunctionType):\n            res = _builtin_function_type(cdecl)\n            if res is not None:\n                return res\n        if (isinstance(cdecl, types.FunctionType)\n                and hasattr(cdecl, '_cffi_base_type')):\n            with self._lock:\n                return self._get_cached_btype(cdecl._cffi_base_type)\n        raise TypeError(type(cdecl))\n\n    def sizeof(self, cdecl):\n        \"\"\"Return the size in bytes of the argument.  It can be a\n        string naming a C type, or a 'cdata' instance.\n        \"\"\"\n        if isinstance(cdecl, basestring):\n            BType = self._typeof(cdecl)\n            return self._backend.sizeof(BType)\n        else:\n            return self._backend.sizeof(cdecl)\n\n    def alignof(self, cdecl):\n        \"\"\"Return the natural alignment size in bytes of the C type\n        given as a string.\n        \"\"\"\n        if isinstance(cdecl, basestring):\n            cdecl = self._typeof(cdecl)\n        return self._backend.alignof(cdecl)\n\n    def offsetof(self, cdecl, *fields_or_indexes):\n        \"\"\"Return the offset of the named field inside the given\n        structure or array, which must be given as a C type name.\n        You can give several field names in case of nested structures.\n        You can also give numeric values which correspond to array\n        items, in case of an array type.\n        \"\"\"\n        if isinstance(cdecl, basestring):\n            cdecl = self._typeof(cdecl)\n        return self._typeoffsetof(cdecl, *fields_or_indexes)[1]\n\n    def new(self, cdecl, init=None):\n        \"\"\"Allocate an instance according to the specified C type and\n        return a pointer to it.  The specified C type must be either a\n        pointer or an array: ``new('X *')`` allocates an X and returns\n        a pointer to it, whereas ``new('X[n]')`` allocates an array of\n        n X'es and returns an array referencing it (which works\n        mostly like a pointer, like in C).  You can also use\n        ``new('X[]', n)`` to allocate an array of a non-constant\n        length n.\n\n        The memory is initialized following the rules of declaring a\n        global variable in C: by default it is zero-initialized, but\n        an explicit initializer can be given which can be used to\n        fill all or part of the memory.\n\n        When the returned <cdata> object goes out of scope, the memory\n        is freed.  In other words the returned <cdata> object has\n        ownership of the value of type 'cdecl' that it points to.  This\n        means that the raw data can be used as long as this object is\n        kept alive, but must not be used for a longer time.  Be careful\n        about that when copying the pointer to the memory somewhere\n        else, e.g. into another structure.\n        \"\"\"\n        if isinstance(cdecl, basestring):\n            cdecl = self._typeof(cdecl)\n        return self._backend.newp(cdecl, init)\n\n    def new_allocator(self, alloc=None, free=None,\n                      should_clear_after_alloc=True):\n        \"\"\"Return a new allocator, i.e. a function that behaves like ffi.new()\n        but uses the provided low-level 'alloc' and 'free' functions.\n\n        'alloc' is called with the size as argument.  If it returns NULL, a\n        MemoryError is raised.  'free' is called with the result of 'alloc'\n        as argument.  Both can be either Python function or directly C\n        functions.  If 'free' is None, then no free function is called.\n        If both 'alloc' and 'free' are None, the default is used.\n\n        If 'should_clear_after_alloc' is set to False, then the memory\n        returned by 'alloc' is assumed to be already cleared (or you are\n        fine with garbage); otherwise CFFI will clear it.\n        \"\"\"\n        compiled_ffi = self._backend.FFI()\n        allocator = compiled_ffi.new_allocator(alloc, free,\n                                               should_clear_after_alloc)\n        def allocate(cdecl, init=None):\n            if isinstance(cdecl, basestring):\n                cdecl = self._typeof(cdecl)\n            return allocator(cdecl, init)\n        return allocate\n\n    def cast(self, cdecl, source):\n        \"\"\"Similar to a C cast: returns an instance of the named C\n        type initialized with the given 'source'.  The source is\n        casted between integers or pointers of any type.\n        \"\"\"\n        if isinstance(cdecl, basestring):\n            cdecl = self._typeof(cdecl)\n        return self._backend.cast(cdecl, source)\n\n    def string(self, cdata, maxlen=-1):\n        \"\"\"Return a Python string (or unicode string) from the 'cdata'.\n        If 'cdata' is a pointer or array of characters or bytes, returns\n        the null-terminated string.  The returned string extends until\n        the first null character, or at most 'maxlen' characters.  If\n        'cdata' is an array then 'maxlen' defaults to its length.\n\n        If 'cdata' is a pointer or array of wchar_t, returns a unicode\n        string following the same rules.\n\n        If 'cdata' is a single character or byte or a wchar_t, returns\n        it as a string or unicode string.\n\n        If 'cdata' is an enum, returns the value of the enumerator as a\n        string, or 'NUMBER' if the value is out of range.\n        \"\"\"\n        return self._backend.string(cdata, maxlen)\n\n    def unpack(self, cdata, length):\n        \"\"\"Unpack an array of C data of the given length,\n        returning a Python string/unicode/list.\n\n        If 'cdata' is a pointer to 'char', returns a byte string.\n        It does not stop at the first null.  This is equivalent to:\n        ffi.buffer(cdata, length)[:]\n\n        If 'cdata' is a pointer to 'wchar_t', returns a unicode string.\n        'length' is measured in wchar_t's; it is not the size in bytes.\n\n        If 'cdata' is a pointer to anything else, returns a list of\n        'length' items.  This is a faster equivalent to:\n        [cdata[i] for i in range(length)]\n        \"\"\"\n        return self._backend.unpack(cdata, length)\n\n   #def buffer(self, cdata, size=-1):\n   #    \"\"\"Return a read-write buffer object that references the raw C data\n   #    pointed to by the given 'cdata'.  The 'cdata' must be a pointer or\n   #    an array.  Can be passed to functions expecting a buffer, or directly\n   #    manipulated with:\n   #\n   #        buf[:]          get a copy of it in a regular string, or\n   #        buf[idx]        as a single character\n   #        buf[:] = ...\n   #        buf[idx] = ...  change the content\n   #    \"\"\"\n   #    note that 'buffer' is a type, set on this instance by __init__\n\n    def from_buffer(self, cdecl, python_buffer=_unspecified,\n                    require_writable=False):\n        \"\"\"Return a cdata of the given type pointing to the data of the\n        given Python object, which must support the buffer interface.\n        Note that this is not meant to be used on the built-in types\n        str or unicode (you can build 'char[]' arrays explicitly)\n        but only on objects containing large quantities of raw data\n        in some other format, like 'array.array' or numpy arrays.\n\n        The first argument is optional and default to 'char[]'.\n        \"\"\"\n        if python_buffer is _unspecified:\n            cdecl, python_buffer = self.BCharA, cdecl\n        elif isinstance(cdecl, basestring):\n            cdecl = self._typeof(cdecl)\n        return self._backend.from_buffer(cdecl, python_buffer,\n                                         require_writable)\n\n    def memmove(self, dest, src, n):\n        \"\"\"ffi.memmove(dest, src, n) copies n bytes of memory from src to dest.\n\n        Like the C function memmove(), the memory areas may overlap;\n        apart from that it behaves like the C function memcpy().\n\n        'src' can be any cdata ptr or array, or any Python buffer object.\n        'dest' can be any cdata ptr or array, or a writable Python buffer\n        object.  The size to copy, 'n', is always measured in bytes.\n\n        Unlike other methods, this one supports all Python buffer including\n        byte strings and bytearrays---but it still does not support\n        non-contiguous buffers.\n        \"\"\"\n        return self._backend.memmove(dest, src, n)\n\n    def callback(self, cdecl, python_callable=None, error=None, onerror=None):\n        \"\"\"Return a callback object or a decorator making such a\n        callback object.  'cdecl' must name a C function pointer type.\n        The callback invokes the specified 'python_callable' (which may\n        be provided either directly or via a decorator).  Important: the\n        callback object must be manually kept alive for as long as the\n        callback may be invoked from the C level.\n        \"\"\"\n        def callback_decorator_wrap(python_callable):\n            if not callable(python_callable):\n                raise TypeError(\"the 'python_callable' argument \"\n                                \"is not callable\")\n            return self._backend.callback(cdecl, python_callable,\n                                          error, onerror)\n        if isinstance(cdecl, basestring):\n            cdecl = self._typeof(cdecl, consider_function_as_funcptr=True)\n        if python_callable is None:\n            return callback_decorator_wrap                # decorator mode\n        else:\n            return callback_decorator_wrap(python_callable)  # direct mode\n\n    def getctype(self, cdecl, replace_with=''):\n        \"\"\"Return a string giving the C type 'cdecl', which may be itself\n        a string or a <ctype> object.  If 'replace_with' is given, it gives\n        extra text to append (or insert for more complicated C types), like\n        a variable name, or '*' to get actually the C type 'pointer-to-cdecl'.\n        \"\"\"\n        if isinstance(cdecl, basestring):\n            cdecl = self._typeof(cdecl)\n        replace_with = replace_with.strip()\n        if (replace_with.startswith('*')\n                and '&[' in self._backend.getcname(cdecl, '&')):\n            replace_with = '(%s)' % replace_with\n        elif replace_with and not replace_with[0] in '[(':\n            replace_with = ' ' + replace_with\n        return self._backend.getcname(cdecl, replace_with)\n\n    def gc(self, cdata, destructor, size=0):\n        \"\"\"Return a new cdata object that points to the same\n        data.  Later, when this new cdata object is garbage-collected,\n        'destructor(old_cdata_object)' will be called.\n\n        The optional 'size' gives an estimate of the size, used to\n        trigger the garbage collection more eagerly.  So far only used\n        on PyPy.  It tells the GC that the returned object keeps alive\n        roughly 'size' bytes of external memory.\n        \"\"\"\n        return self._backend.gcp(cdata, destructor, size)\n\n    def _get_cached_btype(self, type):\n        assert self._lock.acquire(False) is False\n        # call me with the lock!\n        try:\n            BType = self._cached_btypes[type]\n        except KeyError:\n            finishlist = []\n            BType = type.get_cached_btype(self, finishlist)\n            for type in finishlist:\n                type.finish_backend_type(self, finishlist)\n        return BType\n\n    def verify(self, source='', tmpdir=None, **kwargs):\n        \"\"\"Verify that the current ffi signatures compile on this\n        machine, and return a dynamic library object.  The dynamic\n        library can be used to call functions and access global\n        variables declared in this 'ffi'.  The library is compiled\n        by the C compiler: it gives you C-level API compatibility\n        (including calling macros).  This is unlike 'ffi.dlopen()',\n        which requires binary compatibility in the signatures.\n        \"\"\"\n        from .verifier import Verifier, _caller_dir_pycache\n        #\n        # If set_unicode(True) was called, insert the UNICODE and\n        # _UNICODE macro declarations\n        if self._windows_unicode:\n            self._apply_windows_unicode(kwargs)\n        #\n        # Set the tmpdir here, and not in Verifier.__init__: it picks\n        # up the caller's directory, which we want to be the caller of\n        # ffi.verify(), as opposed to the caller of Veritier().\n        tmpdir = tmpdir or _caller_dir_pycache()\n        #\n        # Make a Verifier() and use it to load the library.\n        self.verifier = Verifier(self, source, tmpdir, **kwargs)\n        lib = self.verifier.load_library()\n        #\n        # Save the loaded library for keep-alive purposes, even\n        # if the caller doesn't keep it alive itself (it should).\n        self._libraries.append(lib)\n        return lib\n\n    def _get_errno(self):\n        return self._backend.get_errno()\n    def _set_errno(self, errno):\n        self._backend.set_errno(errno)\n    errno = property(_get_errno, _set_errno, None,\n                     \"the value of 'errno' from/to the C calls\")\n\n    def getwinerror(self, code=-1):\n        return self._backend.getwinerror(code)\n\n    def _pointer_to(self, ctype):\n        with self._lock:\n            return model.pointer_cache(self, ctype)\n\n    def addressof(self, cdata, *fields_or_indexes):\n        \"\"\"Return the address of a <cdata 'struct-or-union'>.\n        If 'fields_or_indexes' are given, returns the address of that\n        field or array item in the structure or array, recursively in\n        case of nested structures.\n        \"\"\"\n        try:\n            ctype = self._backend.typeof(cdata)\n        except TypeError:\n            if '__addressof__' in type(cdata).__dict__:\n                return type(cdata).__addressof__(cdata, *fields_or_indexes)\n            raise\n        if fields_or_indexes:\n            ctype, offset = self._typeoffsetof(ctype, *fields_or_indexes)\n        else:\n            if ctype.kind == \"pointer\":\n                raise TypeError(\"addressof(pointer)\")\n            offset = 0\n        ctypeptr = self._pointer_to(ctype)\n        return self._backend.rawaddressof(ctypeptr, cdata, offset)\n\n    def _typeoffsetof(self, ctype, field_or_index, *fields_or_indexes):\n        ctype, offset = self._backend.typeoffsetof(ctype, field_or_index)\n        for field1 in fields_or_indexes:\n            ctype, offset1 = self._backend.typeoffsetof(ctype, field1, 1)\n            offset += offset1\n        return ctype, offset\n\n    def include(self, ffi_to_include):\n        \"\"\"Includes the typedefs, structs, unions and enums defined\n        in another FFI instance.  Usage is similar to a #include in C,\n        where a part of the program might include types defined in\n        another part for its own usage.  Note that the include()\n        method has no effect on functions, constants and global\n        variables, which must anyway be accessed directly from the\n        lib object returned by the original FFI instance.\n        \"\"\"\n        if not isinstance(ffi_to_include, FFI):\n            raise TypeError(\"ffi.include() expects an argument that is also of\"\n                            \" type cffi.FFI, not %r\" % (\n                                type(ffi_to_include).__name__,))\n        if ffi_to_include is self:\n            raise ValueError(\"self.include(self)\")\n        with ffi_to_include._lock:\n            with self._lock:\n                self._parser.include(ffi_to_include._parser)\n                self._cdefsources.append('[')\n                self._cdefsources.extend(ffi_to_include._cdefsources)\n                self._cdefsources.append(']')\n                self._included_ffis.append(ffi_to_include)\n\n    def new_handle(self, x):\n        return self._backend.newp_handle(self.BVoidP, x)\n\n    def from_handle(self, x):\n        return self._backend.from_handle(x)\n\n    def release(self, x):\n        self._backend.release(x)\n\n    def set_unicode(self, enabled_flag):\n        \"\"\"Windows: if 'enabled_flag' is True, enable the UNICODE and\n        _UNICODE defines in C, and declare the types like TCHAR and LPTCSTR\n        to be (pointers to) wchar_t.  If 'enabled_flag' is False,\n        declare these types to be (pointers to) plain 8-bit characters.\n        This is mostly for backward compatibility; you usually want True.\n        \"\"\"\n        if self._windows_unicode is not None:\n            raise ValueError(\"set_unicode() can only be called once\")\n        enabled_flag = bool(enabled_flag)\n        if enabled_flag:\n            self.cdef(\"typedef wchar_t TBYTE;\"\n                      \"typedef wchar_t TCHAR;\"\n                      \"typedef const wchar_t *LPCTSTR;\"\n                      \"typedef const wchar_t *PCTSTR;\"\n                      \"typedef wchar_t *LPTSTR;\"\n                      \"typedef wchar_t *PTSTR;\"\n                      \"typedef TBYTE *PTBYTE;\"\n                      \"typedef TCHAR *PTCHAR;\")\n        else:\n            self.cdef(\"typedef char TBYTE;\"\n                      \"typedef char TCHAR;\"\n                      \"typedef const char *LPCTSTR;\"\n                      \"typedef const char *PCTSTR;\"\n                      \"typedef char *LPTSTR;\"\n                      \"typedef char *PTSTR;\"\n                      \"typedef TBYTE *PTBYTE;\"\n                      \"typedef TCHAR *PTCHAR;\")\n        self._windows_unicode = enabled_flag\n\n    def _apply_windows_unicode(self, kwds):\n        defmacros = kwds.get('define_macros', ())\n        if not isinstance(defmacros, (list, tuple)):\n            raise TypeError(\"'define_macros' must be a list or tuple\")\n        defmacros = list(defmacros) + [('UNICODE', '1'),\n                                       ('_UNICODE', '1')]\n        kwds['define_macros'] = defmacros\n\n    def _apply_embedding_fix(self, kwds):\n        # must include an argument like \"-lpython2.7\" for the compiler\n        def ensure(key, value):\n            lst = kwds.setdefault(key, [])\n            if value not in lst:\n                lst.append(value)\n        #\n        if '__pypy__' in sys.builtin_module_names:\n            import os\n            if sys.platform == \"win32\":\n                # we need 'libpypy-c.lib'.  Current distributions of\n                # pypy (>= 4.1) contain it as 'libs/python27.lib'.\n                pythonlib = \"python{0[0]}{0[1]}\".format(sys.version_info)\n                if hasattr(sys, 'prefix'):\n                    ensure('library_dirs', os.path.join(sys.prefix, 'libs'))\n            else:\n                # we need 'libpypy-c.{so,dylib}', which should be by\n                # default located in 'sys.prefix/bin' for installed\n                # systems.\n                if sys.version_info < (3,):\n                    pythonlib = \"pypy-c\"\n                else:\n                    pythonlib = \"pypy3-c\"\n                if hasattr(sys, 'prefix'):\n                    ensure('library_dirs', os.path.join(sys.prefix, 'bin'))\n            # On uninstalled pypy's, the libpypy-c is typically found in\n            # .../pypy/goal/.\n            if hasattr(sys, 'prefix'):\n                ensure('library_dirs', os.path.join(sys.prefix, 'pypy', 'goal'))\n        else:\n            if sys.platform == \"win32\":\n                template = \"python%d%d\"\n                if hasattr(sys, 'gettotalrefcount'):\n                    template += '_d'\n            else:\n                try:\n                    import sysconfig\n                except ImportError:    # 2.6\n                    from distutils import sysconfig\n                template = \"python%d.%d\"\n                if sysconfig.get_config_var('DEBUG_EXT'):\n                    template += sysconfig.get_config_var('DEBUG_EXT')\n            pythonlib = (template %\n                    (sys.hexversion >> 24, (sys.hexversion >> 16) & 0xff))\n            if hasattr(sys, 'abiflags'):\n                pythonlib += sys.abiflags\n        ensure('libraries', pythonlib)\n        if sys.platform == \"win32\":\n            ensure('extra_link_args', '/MANIFEST')\n\n    def set_source(self, module_name, source, source_extension='.c', **kwds):\n        import os\n        if hasattr(self, '_assigned_source'):\n            raise ValueError(\"set_source() cannot be called several times \"\n                             \"per ffi object\")\n        if not isinstance(module_name, basestring):\n            raise TypeError(\"'module_name' must be a string\")\n        if os.sep in module_name or (os.altsep and os.altsep in module_name):\n            raise ValueError(\"'module_name' must not contain '/': use a dotted \"\n                             \"name to make a 'package.module' location\")\n        self._assigned_source = (str(module_name), source,\n                                 source_extension, kwds)\n\n    def set_source_pkgconfig(self, module_name, pkgconfig_libs, source,\n                             source_extension='.c', **kwds):\n        from . import pkgconfig\n        if not isinstance(pkgconfig_libs, list):\n            raise TypeError(\"the pkgconfig_libs argument must be a list \"\n                            \"of package names\")\n        kwds2 = pkgconfig.flags_from_pkgconfig(pkgconfig_libs)\n        pkgconfig.merge_flags(kwds, kwds2)\n        self.set_source(module_name, source, source_extension, **kwds)\n\n    def distutils_extension(self, tmpdir='build', verbose=True):\n        from distutils.dir_util import mkpath\n        from .recompiler import recompile\n        #\n        if not hasattr(self, '_assigned_source'):\n            if hasattr(self, 'verifier'):     # fallback, 'tmpdir' ignored\n                return self.verifier.get_extension()\n            raise ValueError(\"set_source() must be called before\"\n                             \" distutils_extension()\")\n        module_name, source, source_extension, kwds = self._assigned_source\n        if source is None:\n            raise TypeError(\"distutils_extension() is only for C extension \"\n                            \"modules, not for dlopen()-style pure Python \"\n                            \"modules\")\n        mkpath(tmpdir)\n        ext, updated = recompile(self, module_name,\n                                 source, tmpdir=tmpdir, extradir=tmpdir,\n                                 source_extension=source_extension,\n                                 call_c_compiler=False, **kwds)\n        if verbose:\n            if updated:\n                sys.stderr.write(\"regenerated: %r\\n\" % (ext.sources[0],))\n            else:\n                sys.stderr.write(\"not modified: %r\\n\" % (ext.sources[0],))\n        return ext\n\n    def emit_c_code(self, filename):\n        from .recompiler import recompile\n        #\n        if not hasattr(self, '_assigned_source'):\n            raise ValueError(\"set_source() must be called before emit_c_code()\")\n        module_name, source, source_extension, kwds = self._assigned_source\n        if source is None:\n            raise TypeError(\"emit_c_code() is only for C extension modules, \"\n                            \"not for dlopen()-style pure Python modules\")\n        recompile(self, module_name, source,\n                  c_file=filename, call_c_compiler=False, **kwds)\n\n    def emit_python_code(self, filename):\n        from .recompiler import recompile\n        #\n        if not hasattr(self, '_assigned_source'):\n            raise ValueError(\"set_source() must be called before emit_c_code()\")\n        module_name, source, source_extension, kwds = self._assigned_source\n        if source is not None:\n            raise TypeError(\"emit_python_code() is only for dlopen()-style \"\n                            \"pure Python modules, not for C extension modules\")\n        recompile(self, module_name, source,\n                  c_file=filename, call_c_compiler=False, **kwds)\n\n    def compile(self, tmpdir='.', verbose=0, target=None, debug=None):\n        \"\"\"The 'target' argument gives the final file name of the\n        compiled DLL.  Use '*' to force distutils' choice, suitable for\n        regular CPython C API modules.  Use a file name ending in '.*'\n        to ask for the system's default extension for dynamic libraries\n        (.so/.dll/.dylib).\n\n        The default is '*' when building a non-embedded C API extension,\n        and (module_name + '.*') when building an embedded library.\n        \"\"\"\n        from .recompiler import recompile\n        #\n        if not hasattr(self, '_assigned_source'):\n            raise ValueError(\"set_source() must be called before compile()\")\n        module_name, source, source_extension, kwds = self._assigned_source\n        return recompile(self, module_name, source, tmpdir=tmpdir,\n                         target=target, source_extension=source_extension,\n                         compiler_verbose=verbose, debug=debug, **kwds)\n\n    def init_once(self, func, tag):\n        # Read _init_once_cache[tag], which is either (False, lock) if\n        # we're calling the function now in some thread, or (True, result).\n        # Don't call setdefault() in most cases, to avoid allocating and\n        # immediately freeing a lock; but still use setdefaut() to avoid\n        # races.\n        try:\n            x = self._init_once_cache[tag]\n        except KeyError:\n            x = self._init_once_cache.setdefault(tag, (False, allocate_lock()))\n        # Common case: we got (True, result), so we return the result.\n        if x[0]:\n            return x[1]\n        # Else, it's a lock.  Acquire it to serialize the following tests.\n        with x[1]:\n            # Read again from _init_once_cache the current status.\n            x = self._init_once_cache[tag]\n            if x[0]:\n                return x[1]\n            # Call the function and store the result back.\n            result = func()\n            self._init_once_cache[tag] = (True, result)\n        return result\n\n    def embedding_init_code(self, pysource):\n        if self._embedding:\n            raise ValueError(\"embedding_init_code() can only be called once\")\n        # fix 'pysource' before it gets dumped into the C file:\n        # - remove empty lines at the beginning, so it starts at \"line 1\"\n        # - dedent, if all non-empty lines are indented\n        # - check for SyntaxErrors\n        import re\n        match = re.match(r'\\s*\\n', pysource)\n        if match:\n            pysource = pysource[match.end():]\n        lines = pysource.splitlines() or ['']\n        prefix = re.match(r'\\s*', lines[0]).group()\n        for i in range(1, len(lines)):\n            line = lines[i]\n            if line.rstrip():\n                while not line.startswith(prefix):\n                    prefix = prefix[:-1]\n        i = len(prefix)\n        lines = [line[i:]+'\\n' for line in lines]\n        pysource = ''.join(lines)\n        #\n        compile(pysource, \"cffi_init\", \"exec\")\n        #\n        self._embedding = pysource\n\n    def def_extern(self, *args, **kwds):\n        raise ValueError(\"ffi.def_extern() is only available on API-mode FFI \"\n                         \"objects\")\n\n    def list_types(self):\n        \"\"\"Returns the user type names known to this FFI instance.\n        This returns a tuple containing three lists of names:\n        (typedef_names, names_of_structs, names_of_unions)\n        \"\"\"\n        typedefs = []\n        structs = []\n        unions = []\n        for key in self._parser._declarations:\n            if key.startswith('typedef '):\n                typedefs.append(key[8:])\n            elif key.startswith('struct '):\n                structs.append(key[7:])\n            elif key.startswith('union '):\n                unions.append(key[6:])\n        typedefs.sort()\n        structs.sort()\n        unions.sort()\n        return (typedefs, structs, unions)\n\n\ndef _load_backend_lib(backend, name, flags):\n    import os\n    if name is None:\n        if sys.platform != \"win32\":\n            return backend.load_library(None, flags)\n        name = \"c\"    # Windows: load_library(None) fails, but this works\n                      # on Python 2 (backward compatibility hack only)\n    first_error = None\n    if '.' in name or '/' in name or os.sep in name:\n        try:\n            return backend.load_library(name, flags)\n        except OSError as e:\n            first_error = e\n    import ctypes.util\n    path = ctypes.util.find_library(name)\n    if path is None:\n        if name == \"c\" and sys.platform == \"win32\" and sys.version_info >= (3,):\n            raise OSError(\"dlopen(None) cannot work on Windows for Python 3 \"\n                          \"(see http://bugs.python.org/issue23606)\")\n        msg = (\"ctypes.util.find_library() did not manage \"\n               \"to locate a library called %r\" % (name,))\n        if first_error is not None:\n            msg = \"%s.  Additionally, %s\" % (first_error, msg)\n        raise OSError(msg)\n    return backend.load_library(path, flags)\n\ndef _make_ffi_library(ffi, libname, flags):\n    backend = ffi._backend\n    backendlib = _load_backend_lib(backend, libname, flags)\n    #\n    def accessor_function(name):\n        key = 'function ' + name\n        tp, _ = ffi._parser._declarations[key]\n        BType = ffi._get_cached_btype(tp)\n        value = backendlib.load_function(BType, name)\n        library.__dict__[name] = value\n    #\n    def accessor_variable(name):\n        key = 'variable ' + name\n        tp, _ = ffi._parser._declarations[key]\n        BType = ffi._get_cached_btype(tp)\n        read_variable = backendlib.read_variable\n        write_variable = backendlib.write_variable\n        setattr(FFILibrary, name, property(\n            lambda self: read_variable(BType, name),\n            lambda self, value: write_variable(BType, name, value)))\n    #\n    def addressof_var(name):\n        try:\n            return addr_variables[name]\n        except KeyError:\n            with ffi._lock:\n                if name not in addr_variables:\n                    key = 'variable ' + name\n                    tp, _ = ffi._parser._declarations[key]\n                    BType = ffi._get_cached_btype(tp)\n                    if BType.kind != 'array':\n                        BType = model.pointer_cache(ffi, BType)\n                    p = backendlib.load_function(BType, name)\n                    addr_variables[name] = p\n            return addr_variables[name]\n    #\n    def accessor_constant(name):\n        raise NotImplementedError(\"non-integer constant '%s' cannot be \"\n                                  \"accessed from a dlopen() library\" % (name,))\n    #\n    def accessor_int_constant(name):\n        library.__dict__[name] = ffi._parser._int_constants[name]\n    #\n    accessors = {}\n    accessors_version = [False]\n    addr_variables = {}\n    #\n    def update_accessors():\n        if accessors_version[0] is ffi._cdef_version:\n            return\n        #\n        for key, (tp, _) in ffi._parser._declarations.items():\n            if not isinstance(tp, model.EnumType):\n                tag, name = key.split(' ', 1)\n                if tag == 'function':\n                    accessors[name] = accessor_function\n                elif tag == 'variable':\n                    accessors[name] = accessor_variable\n                elif tag == 'constant':\n                    accessors[name] = accessor_constant\n            else:\n                for i, enumname in enumerate(tp.enumerators):\n                    def accessor_enum(name, tp=tp, i=i):\n                        tp.check_not_partial()\n                        library.__dict__[name] = tp.enumvalues[i]\n                    accessors[enumname] = accessor_enum\n        for name in ffi._parser._int_constants:\n            accessors.setdefault(name, accessor_int_constant)\n        accessors_version[0] = ffi._cdef_version\n    #\n    def make_accessor(name):\n        with ffi._lock:\n            if name in library.__dict__ or name in FFILibrary.__dict__:\n                return    # added by another thread while waiting for the lock\n            if name not in accessors:\n                update_accessors()\n                if name not in accessors:\n                    raise AttributeError(name)\n            accessors[name](name)\n    #\n    class FFILibrary(object):\n        def __getattr__(self, name):\n            make_accessor(name)\n            return getattr(self, name)\n        def __setattr__(self, name, value):\n            try:\n                property = getattr(self.__class__, name)\n            except AttributeError:\n                make_accessor(name)\n                setattr(self, name, value)\n            else:\n                property.__set__(self, value)\n        def __dir__(self):\n            with ffi._lock:\n                update_accessors()\n                return accessors.keys()\n        def __addressof__(self, name):\n            if name in library.__dict__:\n                return library.__dict__[name]\n            if name in FFILibrary.__dict__:\n                return addressof_var(name)\n            make_accessor(name)\n            if name in library.__dict__:\n                return library.__dict__[name]\n            if name in FFILibrary.__dict__:\n                return addressof_var(name)\n            raise AttributeError(\"cffi library has no function or \"\n                                 \"global variable named '%s'\" % (name,))\n        def __cffi_close__(self):\n            backendlib.close_lib()\n            self.__dict__.clear()\n    #\n    if libname is not None:\n        try:\n            if not isinstance(libname, str):    # unicode, on Python 2\n                libname = libname.encode('utf-8')\n            FFILibrary.__name__ = 'FFILibrary_%s' % libname\n        except UnicodeError:\n            pass\n    library = FFILibrary()\n    return library, library.__dict__\n\ndef _builtin_function_type(func):\n    # a hack to make at least ffi.typeof(builtin_function) work,\n    # if the builtin function was obtained by 'vengine_cpy'.\n    import sys\n    try:\n        module = sys.modules[func.__module__]\n        ffi = module._cffi_original_ffi\n        types_of_builtin_funcs = module._cffi_types_of_builtin_funcs\n        tp = types_of_builtin_funcs[func]\n    except (KeyError, AttributeError, TypeError):\n        return None\n    else:\n        with ffi._lock:\n            return ffi._get_cached_btype(tp)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/backend_ctypes.py",
    "content": "import ctypes, ctypes.util, operator, sys\nfrom . import model\n\nif sys.version_info < (3,):\n    bytechr = chr\nelse:\n    unicode = str\n    long = int\n    xrange = range\n    bytechr = lambda num: bytes([num])\n\nclass CTypesType(type):\n    pass\n\nclass CTypesData(object):\n    __metaclass__ = CTypesType\n    __slots__ = ['__weakref__']\n    __name__ = '<cdata>'\n\n    def __init__(self, *args):\n        raise TypeError(\"cannot instantiate %r\" % (self.__class__,))\n\n    @classmethod\n    def _newp(cls, init):\n        raise TypeError(\"expected a pointer or array ctype, got '%s'\"\n                        % (cls._get_c_name(),))\n\n    @staticmethod\n    def _to_ctypes(value):\n        raise TypeError\n\n    @classmethod\n    def _arg_to_ctypes(cls, *value):\n        try:\n            ctype = cls._ctype\n        except AttributeError:\n            raise TypeError(\"cannot create an instance of %r\" % (cls,))\n        if value:\n            res = cls._to_ctypes(*value)\n            if not isinstance(res, ctype):\n                res = cls._ctype(res)\n        else:\n            res = cls._ctype()\n        return res\n\n    @classmethod\n    def _create_ctype_obj(cls, init):\n        if init is None:\n            return cls._arg_to_ctypes()\n        else:\n            return cls._arg_to_ctypes(init)\n\n    @staticmethod\n    def _from_ctypes(ctypes_value):\n        raise TypeError\n\n    @classmethod\n    def _get_c_name(cls, replace_with=''):\n        return cls._reftypename.replace(' &', replace_with)\n\n    @classmethod\n    def _fix_class(cls):\n        cls.__name__ = 'CData<%s>' % (cls._get_c_name(),)\n        cls.__qualname__ = 'CData<%s>' % (cls._get_c_name(),)\n        cls.__module__ = 'ffi'\n\n    def _get_own_repr(self):\n        raise NotImplementedError\n\n    def _addr_repr(self, address):\n        if address == 0:\n            return 'NULL'\n        else:\n            if address < 0:\n                address += 1 << (8*ctypes.sizeof(ctypes.c_void_p))\n            return '0x%x' % address\n\n    def __repr__(self, c_name=None):\n        own = self._get_own_repr()\n        return '<cdata %r %s>' % (c_name or self._get_c_name(), own)\n\n    def _convert_to_address(self, BClass):\n        if BClass is None:\n            raise TypeError(\"cannot convert %r to an address\" % (\n                self._get_c_name(),))\n        else:\n            raise TypeError(\"cannot convert %r to %r\" % (\n                self._get_c_name(), BClass._get_c_name()))\n\n    @classmethod\n    def _get_size(cls):\n        return ctypes.sizeof(cls._ctype)\n\n    def _get_size_of_instance(self):\n        return ctypes.sizeof(self._ctype)\n\n    @classmethod\n    def _cast_from(cls, source):\n        raise TypeError(\"cannot cast to %r\" % (cls._get_c_name(),))\n\n    def _cast_to_integer(self):\n        return self._convert_to_address(None)\n\n    @classmethod\n    def _alignment(cls):\n        return ctypes.alignment(cls._ctype)\n\n    def __iter__(self):\n        raise TypeError(\"cdata %r does not support iteration\" % (\n            self._get_c_name()),)\n\n    def _make_cmp(name):\n        cmpfunc = getattr(operator, name)\n        def cmp(self, other):\n            v_is_ptr = not isinstance(self, CTypesGenericPrimitive)\n            w_is_ptr = (isinstance(other, CTypesData) and\n                           not isinstance(other, CTypesGenericPrimitive))\n            if v_is_ptr and w_is_ptr:\n                return cmpfunc(self._convert_to_address(None),\n                               other._convert_to_address(None))\n            elif v_is_ptr or w_is_ptr:\n                return NotImplemented\n            else:\n                if isinstance(self, CTypesGenericPrimitive):\n                    self = self._value\n                if isinstance(other, CTypesGenericPrimitive):\n                    other = other._value\n                return cmpfunc(self, other)\n        cmp.func_name = name\n        return cmp\n\n    __eq__ = _make_cmp('__eq__')\n    __ne__ = _make_cmp('__ne__')\n    __lt__ = _make_cmp('__lt__')\n    __le__ = _make_cmp('__le__')\n    __gt__ = _make_cmp('__gt__')\n    __ge__ = _make_cmp('__ge__')\n\n    def __hash__(self):\n        return hash(self._convert_to_address(None))\n\n    def _to_string(self, maxlen):\n        raise TypeError(\"string(): %r\" % (self,))\n\n\nclass CTypesGenericPrimitive(CTypesData):\n    __slots__ = []\n\n    def __hash__(self):\n        return hash(self._value)\n\n    def _get_own_repr(self):\n        return repr(self._from_ctypes(self._value))\n\n\nclass CTypesGenericArray(CTypesData):\n    __slots__ = []\n\n    @classmethod\n    def _newp(cls, init):\n        return cls(init)\n\n    def __iter__(self):\n        for i in xrange(len(self)):\n            yield self[i]\n\n    def _get_own_repr(self):\n        return self._addr_repr(ctypes.addressof(self._blob))\n\n\nclass CTypesGenericPtr(CTypesData):\n    __slots__ = ['_address', '_as_ctype_ptr']\n    _automatic_casts = False\n    kind = \"pointer\"\n\n    @classmethod\n    def _newp(cls, init):\n        return cls(init)\n\n    @classmethod\n    def _cast_from(cls, source):\n        if source is None:\n            address = 0\n        elif isinstance(source, CTypesData):\n            address = source._cast_to_integer()\n        elif isinstance(source, (int, long)):\n            address = source\n        else:\n            raise TypeError(\"bad type for cast to %r: %r\" %\n                            (cls, type(source).__name__))\n        return cls._new_pointer_at(address)\n\n    @classmethod\n    def _new_pointer_at(cls, address):\n        self = cls.__new__(cls)\n        self._address = address\n        self._as_ctype_ptr = ctypes.cast(address, cls._ctype)\n        return self\n\n    def _get_own_repr(self):\n        try:\n            return self._addr_repr(self._address)\n        except AttributeError:\n            return '???'\n\n    def _cast_to_integer(self):\n        return self._address\n\n    def __nonzero__(self):\n        return bool(self._address)\n    __bool__ = __nonzero__\n\n    @classmethod\n    def _to_ctypes(cls, value):\n        if not isinstance(value, CTypesData):\n            raise TypeError(\"unexpected %s object\" % type(value).__name__)\n        address = value._convert_to_address(cls)\n        return ctypes.cast(address, cls._ctype)\n\n    @classmethod\n    def _from_ctypes(cls, ctypes_ptr):\n        address = ctypes.cast(ctypes_ptr, ctypes.c_void_p).value or 0\n        return cls._new_pointer_at(address)\n\n    @classmethod\n    def _initialize(cls, ctypes_ptr, value):\n        if value:\n            ctypes_ptr.contents = cls._to_ctypes(value).contents\n\n    def _convert_to_address(self, BClass):\n        if (BClass in (self.__class__, None) or BClass._automatic_casts\n            or self._automatic_casts):\n            return self._address\n        else:\n            return CTypesData._convert_to_address(self, BClass)\n\n\nclass CTypesBaseStructOrUnion(CTypesData):\n    __slots__ = ['_blob']\n\n    @classmethod\n    def _create_ctype_obj(cls, init):\n        # may be overridden\n        raise TypeError(\"cannot instantiate opaque type %s\" % (cls,))\n\n    def _get_own_repr(self):\n        return self._addr_repr(ctypes.addressof(self._blob))\n\n    @classmethod\n    def _offsetof(cls, fieldname):\n        return getattr(cls._ctype, fieldname).offset\n\n    def _convert_to_address(self, BClass):\n        if getattr(BClass, '_BItem', None) is self.__class__:\n            return ctypes.addressof(self._blob)\n        else:\n            return CTypesData._convert_to_address(self, BClass)\n\n    @classmethod\n    def _from_ctypes(cls, ctypes_struct_or_union):\n        self = cls.__new__(cls)\n        self._blob = ctypes_struct_or_union\n        return self\n\n    @classmethod\n    def _to_ctypes(cls, value):\n        return value._blob\n\n    def __repr__(self, c_name=None):\n        return CTypesData.__repr__(self, c_name or self._get_c_name(' &'))\n\n\nclass CTypesBackend(object):\n\n    PRIMITIVE_TYPES = {\n        'char': ctypes.c_char,\n        'short': ctypes.c_short,\n        'int': ctypes.c_int,\n        'long': ctypes.c_long,\n        'long long': ctypes.c_longlong,\n        'signed char': ctypes.c_byte,\n        'unsigned char': ctypes.c_ubyte,\n        'unsigned short': ctypes.c_ushort,\n        'unsigned int': ctypes.c_uint,\n        'unsigned long': ctypes.c_ulong,\n        'unsigned long long': ctypes.c_ulonglong,\n        'float': ctypes.c_float,\n        'double': ctypes.c_double,\n        '_Bool': ctypes.c_bool,\n        }\n\n    for _name in ['unsigned long long', 'unsigned long',\n                  'unsigned int', 'unsigned short', 'unsigned char']:\n        _size = ctypes.sizeof(PRIMITIVE_TYPES[_name])\n        PRIMITIVE_TYPES['uint%d_t' % (8*_size)] = PRIMITIVE_TYPES[_name]\n        if _size == ctypes.sizeof(ctypes.c_void_p):\n            PRIMITIVE_TYPES['uintptr_t'] = PRIMITIVE_TYPES[_name]\n        if _size == ctypes.sizeof(ctypes.c_size_t):\n            PRIMITIVE_TYPES['size_t'] = PRIMITIVE_TYPES[_name]\n\n    for _name in ['long long', 'long', 'int', 'short', 'signed char']:\n        _size = ctypes.sizeof(PRIMITIVE_TYPES[_name])\n        PRIMITIVE_TYPES['int%d_t' % (8*_size)] = PRIMITIVE_TYPES[_name]\n        if _size == ctypes.sizeof(ctypes.c_void_p):\n            PRIMITIVE_TYPES['intptr_t'] = PRIMITIVE_TYPES[_name]\n            PRIMITIVE_TYPES['ptrdiff_t'] = PRIMITIVE_TYPES[_name]\n        if _size == ctypes.sizeof(ctypes.c_size_t):\n            PRIMITIVE_TYPES['ssize_t'] = PRIMITIVE_TYPES[_name]\n\n\n    def __init__(self):\n        self.RTLD_LAZY = 0   # not supported anyway by ctypes\n        self.RTLD_NOW  = 0\n        self.RTLD_GLOBAL = ctypes.RTLD_GLOBAL\n        self.RTLD_LOCAL = ctypes.RTLD_LOCAL\n\n    def set_ffi(self, ffi):\n        self.ffi = ffi\n\n    def _get_types(self):\n        return CTypesData, CTypesType\n\n    def load_library(self, path, flags=0):\n        cdll = ctypes.CDLL(path, flags)\n        return CTypesLibrary(self, cdll)\n\n    def new_void_type(self):\n        class CTypesVoid(CTypesData):\n            __slots__ = []\n            _reftypename = 'void &'\n            @staticmethod\n            def _from_ctypes(novalue):\n                return None\n            @staticmethod\n            def _to_ctypes(novalue):\n                if novalue is not None:\n                    raise TypeError(\"None expected, got %s object\" %\n                                    (type(novalue).__name__,))\n                return None\n        CTypesVoid._fix_class()\n        return CTypesVoid\n\n    def new_primitive_type(self, name):\n        if name == 'wchar_t':\n            raise NotImplementedError(name)\n        ctype = self.PRIMITIVE_TYPES[name]\n        if name == 'char':\n            kind = 'char'\n        elif name in ('float', 'double'):\n            kind = 'float'\n        else:\n            if name in ('signed char', 'unsigned char'):\n                kind = 'byte'\n            elif name == '_Bool':\n                kind = 'bool'\n            else:\n                kind = 'int'\n            is_signed = (ctype(-1).value == -1)\n        #\n        def _cast_source_to_int(source):\n            if isinstance(source, (int, long, float)):\n                source = int(source)\n            elif isinstance(source, CTypesData):\n                source = source._cast_to_integer()\n            elif isinstance(source, bytes):\n                source = ord(source)\n            elif source is None:\n                source = 0\n            else:\n                raise TypeError(\"bad type for cast to %r: %r\" %\n                                (CTypesPrimitive, type(source).__name__))\n            return source\n        #\n        kind1 = kind\n        class CTypesPrimitive(CTypesGenericPrimitive):\n            __slots__ = ['_value']\n            _ctype = ctype\n            _reftypename = '%s &' % name\n            kind = kind1\n\n            def __init__(self, value):\n                self._value = value\n\n            @staticmethod\n            def _create_ctype_obj(init):\n                if init is None:\n                    return ctype()\n                return ctype(CTypesPrimitive._to_ctypes(init))\n\n            if kind == 'int' or kind == 'byte':\n                @classmethod\n                def _cast_from(cls, source):\n                    source = _cast_source_to_int(source)\n                    source = ctype(source).value     # cast within range\n                    return cls(source)\n                def __int__(self):\n                    return self._value\n\n            if kind == 'bool':\n                @classmethod\n                def _cast_from(cls, source):\n                    if not isinstance(source, (int, long, float)):\n                        source = _cast_source_to_int(source)\n                    return cls(bool(source))\n                def __int__(self):\n                    return int(self._value)\n\n            if kind == 'char':\n                @classmethod\n                def _cast_from(cls, source):\n                    source = _cast_source_to_int(source)\n                    source = bytechr(source & 0xFF)\n                    return cls(source)\n                def __int__(self):\n                    return ord(self._value)\n\n            if kind == 'float':\n                @classmethod\n                def _cast_from(cls, source):\n                    if isinstance(source, float):\n                        pass\n                    elif isinstance(source, CTypesGenericPrimitive):\n                        if hasattr(source, '__float__'):\n                            source = float(source)\n                        else:\n                            source = int(source)\n                    else:\n                        source = _cast_source_to_int(source)\n                    source = ctype(source).value     # fix precision\n                    return cls(source)\n                def __int__(self):\n                    return int(self._value)\n                def __float__(self):\n                    return self._value\n\n            _cast_to_integer = __int__\n\n            if kind == 'int' or kind == 'byte' or kind == 'bool':\n                @staticmethod\n                def _to_ctypes(x):\n                    if not isinstance(x, (int, long)):\n                        if isinstance(x, CTypesData):\n                            x = int(x)\n                        else:\n                            raise TypeError(\"integer expected, got %s\" %\n                                            type(x).__name__)\n                    if ctype(x).value != x:\n                        if not is_signed and x < 0:\n                            raise OverflowError(\"%s: negative integer\" % name)\n                        else:\n                            raise OverflowError(\"%s: integer out of bounds\"\n                                                % name)\n                    return x\n\n            if kind == 'char':\n                @staticmethod\n                def _to_ctypes(x):\n                    if isinstance(x, bytes) and len(x) == 1:\n                        return x\n                    if isinstance(x, CTypesPrimitive):    # <CData <char>>\n                        return x._value\n                    raise TypeError(\"character expected, got %s\" %\n                                    type(x).__name__)\n                def __nonzero__(self):\n                    return ord(self._value) != 0\n            else:\n                def __nonzero__(self):\n                    return self._value != 0\n            __bool__ = __nonzero__\n\n            if kind == 'float':\n                @staticmethod\n                def _to_ctypes(x):\n                    if not isinstance(x, (int, long, float, CTypesData)):\n                        raise TypeError(\"float expected, got %s\" %\n                                        type(x).__name__)\n                    return ctype(x).value\n\n            @staticmethod\n            def _from_ctypes(value):\n                return getattr(value, 'value', value)\n\n            @staticmethod\n            def _initialize(blob, init):\n                blob.value = CTypesPrimitive._to_ctypes(init)\n\n            if kind == 'char':\n                def _to_string(self, maxlen):\n                    return self._value\n            if kind == 'byte':\n                def _to_string(self, maxlen):\n                    return chr(self._value & 0xff)\n        #\n        CTypesPrimitive._fix_class()\n        return CTypesPrimitive\n\n    def new_pointer_type(self, BItem):\n        getbtype = self.ffi._get_cached_btype\n        if BItem is getbtype(model.PrimitiveType('char')):\n            kind = 'charp'\n        elif BItem in (getbtype(model.PrimitiveType('signed char')),\n                       getbtype(model.PrimitiveType('unsigned char'))):\n            kind = 'bytep'\n        elif BItem is getbtype(model.void_type):\n            kind = 'voidp'\n        else:\n            kind = 'generic'\n        #\n        class CTypesPtr(CTypesGenericPtr):\n            __slots__ = ['_own']\n            if kind == 'charp':\n                __slots__ += ['__as_strbuf']\n            _BItem = BItem\n            if hasattr(BItem, '_ctype'):\n                _ctype = ctypes.POINTER(BItem._ctype)\n                _bitem_size = ctypes.sizeof(BItem._ctype)\n            else:\n                _ctype = ctypes.c_void_p\n            if issubclass(BItem, CTypesGenericArray):\n                _reftypename = BItem._get_c_name('(* &)')\n            else:\n                _reftypename = BItem._get_c_name(' * &')\n\n            def __init__(self, init):\n                ctypeobj = BItem._create_ctype_obj(init)\n                if kind == 'charp':\n                    self.__as_strbuf = ctypes.create_string_buffer(\n                        ctypeobj.value + b'\\x00')\n                    self._as_ctype_ptr = ctypes.cast(\n                        self.__as_strbuf, self._ctype)\n                else:\n                    self._as_ctype_ptr = ctypes.pointer(ctypeobj)\n                self._address = ctypes.cast(self._as_ctype_ptr,\n                                            ctypes.c_void_p).value\n                self._own = True\n\n            def __add__(self, other):\n                if isinstance(other, (int, long)):\n                    return self._new_pointer_at(self._address +\n                                                other * self._bitem_size)\n                else:\n                    return NotImplemented\n\n            def __sub__(self, other):\n                if isinstance(other, (int, long)):\n                    return self._new_pointer_at(self._address -\n                                                other * self._bitem_size)\n                elif type(self) is type(other):\n                    return (self._address - other._address) // self._bitem_size\n                else:\n                    return NotImplemented\n\n            def __getitem__(self, index):\n                if getattr(self, '_own', False) and index != 0:\n                    raise IndexError\n                return BItem._from_ctypes(self._as_ctype_ptr[index])\n\n            def __setitem__(self, index, value):\n                self._as_ctype_ptr[index] = BItem._to_ctypes(value)\n\n            if kind == 'charp' or kind == 'voidp':\n                @classmethod\n                def _arg_to_ctypes(cls, *value):\n                    if value and isinstance(value[0], bytes):\n                        return ctypes.c_char_p(value[0])\n                    else:\n                        return super(CTypesPtr, cls)._arg_to_ctypes(*value)\n\n            if kind == 'charp' or kind == 'bytep':\n                def _to_string(self, maxlen):\n                    if maxlen < 0:\n                        maxlen = sys.maxsize\n                    p = ctypes.cast(self._as_ctype_ptr,\n                                    ctypes.POINTER(ctypes.c_char))\n                    n = 0\n                    while n < maxlen and p[n] != b'\\x00':\n                        n += 1\n                    return b''.join([p[i] for i in range(n)])\n\n            def _get_own_repr(self):\n                if getattr(self, '_own', False):\n                    return 'owning %d bytes' % (\n                        ctypes.sizeof(self._as_ctype_ptr.contents),)\n                return super(CTypesPtr, self)._get_own_repr()\n        #\n        if (BItem is self.ffi._get_cached_btype(model.void_type) or\n            BItem is self.ffi._get_cached_btype(model.PrimitiveType('char'))):\n            CTypesPtr._automatic_casts = True\n        #\n        CTypesPtr._fix_class()\n        return CTypesPtr\n\n    def new_array_type(self, CTypesPtr, length):\n        if length is None:\n            brackets = ' &[]'\n        else:\n            brackets = ' &[%d]' % length\n        BItem = CTypesPtr._BItem\n        getbtype = self.ffi._get_cached_btype\n        if BItem is getbtype(model.PrimitiveType('char')):\n            kind = 'char'\n        elif BItem in (getbtype(model.PrimitiveType('signed char')),\n                       getbtype(model.PrimitiveType('unsigned char'))):\n            kind = 'byte'\n        else:\n            kind = 'generic'\n        #\n        class CTypesArray(CTypesGenericArray):\n            __slots__ = ['_blob', '_own']\n            if length is not None:\n                _ctype = BItem._ctype * length\n            else:\n                __slots__.append('_ctype')\n            _reftypename = BItem._get_c_name(brackets)\n            _declared_length = length\n            _CTPtr = CTypesPtr\n\n            def __init__(self, init):\n                if length is None:\n                    if isinstance(init, (int, long)):\n                        len1 = init\n                        init = None\n                    elif kind == 'char' and isinstance(init, bytes):\n                        len1 = len(init) + 1    # extra null\n                    else:\n                        init = tuple(init)\n                        len1 = len(init)\n                    self._ctype = BItem._ctype * len1\n                self._blob = self._ctype()\n                self._own = True\n                if init is not None:\n                    self._initialize(self._blob, init)\n\n            @staticmethod\n            def _initialize(blob, init):\n                if isinstance(init, bytes):\n                    init = [init[i:i+1] for i in range(len(init))]\n                else:\n                    if isinstance(init, CTypesGenericArray):\n                        if (len(init) != len(blob) or\n                            not isinstance(init, CTypesArray)):\n                            raise TypeError(\"length/type mismatch: %s\" % (init,))\n                    init = tuple(init)\n                if len(init) > len(blob):\n                    raise IndexError(\"too many initializers\")\n                addr = ctypes.cast(blob, ctypes.c_void_p).value\n                PTR = ctypes.POINTER(BItem._ctype)\n                itemsize = ctypes.sizeof(BItem._ctype)\n                for i, value in enumerate(init):\n                    p = ctypes.cast(addr + i * itemsize, PTR)\n                    BItem._initialize(p.contents, value)\n\n            def __len__(self):\n                return len(self._blob)\n\n            def __getitem__(self, index):\n                if not (0 <= index < len(self._blob)):\n                    raise IndexError\n                return BItem._from_ctypes(self._blob[index])\n\n            def __setitem__(self, index, value):\n                if not (0 <= index < len(self._blob)):\n                    raise IndexError\n                self._blob[index] = BItem._to_ctypes(value)\n\n            if kind == 'char' or kind == 'byte':\n                def _to_string(self, maxlen):\n                    if maxlen < 0:\n                        maxlen = len(self._blob)\n                    p = ctypes.cast(self._blob,\n                                    ctypes.POINTER(ctypes.c_char))\n                    n = 0\n                    while n < maxlen and p[n] != b'\\x00':\n                        n += 1\n                    return b''.join([p[i] for i in range(n)])\n\n            def _get_own_repr(self):\n                if getattr(self, '_own', False):\n                    return 'owning %d bytes' % (ctypes.sizeof(self._blob),)\n                return super(CTypesArray, self)._get_own_repr()\n\n            def _convert_to_address(self, BClass):\n                if BClass in (CTypesPtr, None) or BClass._automatic_casts:\n                    return ctypes.addressof(self._blob)\n                else:\n                    return CTypesData._convert_to_address(self, BClass)\n\n            @staticmethod\n            def _from_ctypes(ctypes_array):\n                self = CTypesArray.__new__(CTypesArray)\n                self._blob = ctypes_array\n                return self\n\n            @staticmethod\n            def _arg_to_ctypes(value):\n                return CTypesPtr._arg_to_ctypes(value)\n\n            def __add__(self, other):\n                if isinstance(other, (int, long)):\n                    return CTypesPtr._new_pointer_at(\n                        ctypes.addressof(self._blob) +\n                        other * ctypes.sizeof(BItem._ctype))\n                else:\n                    return NotImplemented\n\n            @classmethod\n            def _cast_from(cls, source):\n                raise NotImplementedError(\"casting to %r\" % (\n                    cls._get_c_name(),))\n        #\n        CTypesArray._fix_class()\n        return CTypesArray\n\n    def _new_struct_or_union(self, kind, name, base_ctypes_class):\n        #\n        class struct_or_union(base_ctypes_class):\n            pass\n        struct_or_union.__name__ = '%s_%s' % (kind, name)\n        kind1 = kind\n        #\n        class CTypesStructOrUnion(CTypesBaseStructOrUnion):\n            __slots__ = ['_blob']\n            _ctype = struct_or_union\n            _reftypename = '%s &' % (name,)\n            _kind = kind = kind1\n        #\n        CTypesStructOrUnion._fix_class()\n        return CTypesStructOrUnion\n\n    def new_struct_type(self, name):\n        return self._new_struct_or_union('struct', name, ctypes.Structure)\n\n    def new_union_type(self, name):\n        return self._new_struct_or_union('union', name, ctypes.Union)\n\n    def complete_struct_or_union(self, CTypesStructOrUnion, fields, tp,\n                                 totalsize=-1, totalalignment=-1, sflags=0,\n                                 pack=0):\n        if totalsize >= 0 or totalalignment >= 0:\n            raise NotImplementedError(\"the ctypes backend of CFFI does not support \"\n                                      \"structures completed by verify(); please \"\n                                      \"compile and install the _cffi_backend module.\")\n        struct_or_union = CTypesStructOrUnion._ctype\n        fnames = [fname for (fname, BField, bitsize) in fields]\n        btypes = [BField for (fname, BField, bitsize) in fields]\n        bitfields = [bitsize for (fname, BField, bitsize) in fields]\n        #\n        bfield_types = {}\n        cfields = []\n        for (fname, BField, bitsize) in fields:\n            if bitsize < 0:\n                cfields.append((fname, BField._ctype))\n                bfield_types[fname] = BField\n            else:\n                cfields.append((fname, BField._ctype, bitsize))\n                bfield_types[fname] = Ellipsis\n        if sflags & 8:\n            struct_or_union._pack_ = 1\n        elif pack:\n            struct_or_union._pack_ = pack\n        struct_or_union._fields_ = cfields\n        CTypesStructOrUnion._bfield_types = bfield_types\n        #\n        @staticmethod\n        def _create_ctype_obj(init):\n            result = struct_or_union()\n            if init is not None:\n                initialize(result, init)\n            return result\n        CTypesStructOrUnion._create_ctype_obj = _create_ctype_obj\n        #\n        def initialize(blob, init):\n            if is_union:\n                if len(init) > 1:\n                    raise ValueError(\"union initializer: %d items given, but \"\n                                    \"only one supported (use a dict if needed)\"\n                                     % (len(init),))\n            if not isinstance(init, dict):\n                if isinstance(init, (bytes, unicode)):\n                    raise TypeError(\"union initializer: got a str\")\n                init = tuple(init)\n                if len(init) > len(fnames):\n                    raise ValueError(\"too many values for %s initializer\" %\n                                     CTypesStructOrUnion._get_c_name())\n                init = dict(zip(fnames, init))\n            addr = ctypes.addressof(blob)\n            for fname, value in init.items():\n                BField, bitsize = name2fieldtype[fname]\n                assert bitsize < 0, \\\n                       \"not implemented: initializer with bit fields\"\n                offset = CTypesStructOrUnion._offsetof(fname)\n                PTR = ctypes.POINTER(BField._ctype)\n                p = ctypes.cast(addr + offset, PTR)\n                BField._initialize(p.contents, value)\n        is_union = CTypesStructOrUnion._kind == 'union'\n        name2fieldtype = dict(zip(fnames, zip(btypes, bitfields)))\n        #\n        for fname, BField, bitsize in fields:\n            if fname == '':\n                raise NotImplementedError(\"nested anonymous structs/unions\")\n            if hasattr(CTypesStructOrUnion, fname):\n                raise ValueError(\"the field name %r conflicts in \"\n                                 \"the ctypes backend\" % fname)\n            if bitsize < 0:\n                def getter(self, fname=fname, BField=BField,\n                           offset=CTypesStructOrUnion._offsetof(fname),\n                           PTR=ctypes.POINTER(BField._ctype)):\n                    addr = ctypes.addressof(self._blob)\n                    p = ctypes.cast(addr + offset, PTR)\n                    return BField._from_ctypes(p.contents)\n                def setter(self, value, fname=fname, BField=BField):\n                    setattr(self._blob, fname, BField._to_ctypes(value))\n                #\n                if issubclass(BField, CTypesGenericArray):\n                    setter = None\n                    if BField._declared_length == 0:\n                        def getter(self, fname=fname, BFieldPtr=BField._CTPtr,\n                                   offset=CTypesStructOrUnion._offsetof(fname),\n                                   PTR=ctypes.POINTER(BField._ctype)):\n                            addr = ctypes.addressof(self._blob)\n                            p = ctypes.cast(addr + offset, PTR)\n                            return BFieldPtr._from_ctypes(p)\n                #\n            else:\n                def getter(self, fname=fname, BField=BField):\n                    return BField._from_ctypes(getattr(self._blob, fname))\n                def setter(self, value, fname=fname, BField=BField):\n                    # xxx obscure workaround\n                    value = BField._to_ctypes(value)\n                    oldvalue = getattr(self._blob, fname)\n                    setattr(self._blob, fname, value)\n                    if value != getattr(self._blob, fname):\n                        setattr(self._blob, fname, oldvalue)\n                        raise OverflowError(\"value too large for bitfield\")\n            setattr(CTypesStructOrUnion, fname, property(getter, setter))\n        #\n        CTypesPtr = self.ffi._get_cached_btype(model.PointerType(tp))\n        for fname in fnames:\n            if hasattr(CTypesPtr, fname):\n                raise ValueError(\"the field name %r conflicts in \"\n                                 \"the ctypes backend\" % fname)\n            def getter(self, fname=fname):\n                return getattr(self[0], fname)\n            def setter(self, value, fname=fname):\n                setattr(self[0], fname, value)\n            setattr(CTypesPtr, fname, property(getter, setter))\n\n    def new_function_type(self, BArgs, BResult, has_varargs):\n        nameargs = [BArg._get_c_name() for BArg in BArgs]\n        if has_varargs:\n            nameargs.append('...')\n        nameargs = ', '.join(nameargs)\n        #\n        class CTypesFunctionPtr(CTypesGenericPtr):\n            __slots__ = ['_own_callback', '_name']\n            _ctype = ctypes.CFUNCTYPE(getattr(BResult, '_ctype', None),\n                                      *[BArg._ctype for BArg in BArgs],\n                                      use_errno=True)\n            _reftypename = BResult._get_c_name('(* &)(%s)' % (nameargs,))\n\n            def __init__(self, init, error=None):\n                # create a callback to the Python callable init()\n                import traceback\n                assert not has_varargs, \"varargs not supported for callbacks\"\n                if getattr(BResult, '_ctype', None) is not None:\n                    error = BResult._from_ctypes(\n                        BResult._create_ctype_obj(error))\n                else:\n                    error = None\n                def callback(*args):\n                    args2 = []\n                    for arg, BArg in zip(args, BArgs):\n                        args2.append(BArg._from_ctypes(arg))\n                    try:\n                        res2 = init(*args2)\n                        res2 = BResult._to_ctypes(res2)\n                    except:\n                        traceback.print_exc()\n                        res2 = error\n                    if issubclass(BResult, CTypesGenericPtr):\n                        if res2:\n                            res2 = ctypes.cast(res2, ctypes.c_void_p).value\n                                # .value: http://bugs.python.org/issue1574593\n                        else:\n                            res2 = None\n                    #print repr(res2)\n                    return res2\n                if issubclass(BResult, CTypesGenericPtr):\n                    # The only pointers callbacks can return are void*s:\n                    # http://bugs.python.org/issue5710\n                    callback_ctype = ctypes.CFUNCTYPE(\n                        ctypes.c_void_p,\n                        *[BArg._ctype for BArg in BArgs],\n                        use_errno=True)\n                else:\n                    callback_ctype = CTypesFunctionPtr._ctype\n                self._as_ctype_ptr = callback_ctype(callback)\n                self._address = ctypes.cast(self._as_ctype_ptr,\n                                            ctypes.c_void_p).value\n                self._own_callback = init\n\n            @staticmethod\n            def _initialize(ctypes_ptr, value):\n                if value:\n                    raise NotImplementedError(\"ctypes backend: not supported: \"\n                                          \"initializers for function pointers\")\n\n            def __repr__(self):\n                c_name = getattr(self, '_name', None)\n                if c_name:\n                    i = self._reftypename.index('(* &)')\n                    if self._reftypename[i-1] not in ' )*':\n                        c_name = ' ' + c_name\n                    c_name = self._reftypename.replace('(* &)', c_name)\n                return CTypesData.__repr__(self, c_name)\n\n            def _get_own_repr(self):\n                if getattr(self, '_own_callback', None) is not None:\n                    return 'calling %r' % (self._own_callback,)\n                return super(CTypesFunctionPtr, self)._get_own_repr()\n\n            def __call__(self, *args):\n                if has_varargs:\n                    assert len(args) >= len(BArgs)\n                    extraargs = args[len(BArgs):]\n                    args = args[:len(BArgs)]\n                else:\n                    assert len(args) == len(BArgs)\n                ctypes_args = []\n                for arg, BArg in zip(args, BArgs):\n                    ctypes_args.append(BArg._arg_to_ctypes(arg))\n                if has_varargs:\n                    for i, arg in enumerate(extraargs):\n                        if arg is None:\n                            ctypes_args.append(ctypes.c_void_p(0))  # NULL\n                            continue\n                        if not isinstance(arg, CTypesData):\n                            raise TypeError(\n                                \"argument %d passed in the variadic part \"\n                                \"needs to be a cdata object (got %s)\" %\n                                (1 + len(BArgs) + i, type(arg).__name__))\n                        ctypes_args.append(arg._arg_to_ctypes(arg))\n                result = self._as_ctype_ptr(*ctypes_args)\n                return BResult._from_ctypes(result)\n        #\n        CTypesFunctionPtr._fix_class()\n        return CTypesFunctionPtr\n\n    def new_enum_type(self, name, enumerators, enumvalues, CTypesInt):\n        assert isinstance(name, str)\n        reverse_mapping = dict(zip(reversed(enumvalues),\n                                   reversed(enumerators)))\n        #\n        class CTypesEnum(CTypesInt):\n            __slots__ = []\n            _reftypename = '%s &' % name\n\n            def _get_own_repr(self):\n                value = self._value\n                try:\n                    return '%d: %s' % (value, reverse_mapping[value])\n                except KeyError:\n                    return str(value)\n\n            def _to_string(self, maxlen):\n                value = self._value\n                try:\n                    return reverse_mapping[value]\n                except KeyError:\n                    return str(value)\n        #\n        CTypesEnum._fix_class()\n        return CTypesEnum\n\n    def get_errno(self):\n        return ctypes.get_errno()\n\n    def set_errno(self, value):\n        ctypes.set_errno(value)\n\n    def string(self, b, maxlen=-1):\n        return b._to_string(maxlen)\n\n    def buffer(self, bptr, size=-1):\n        raise NotImplementedError(\"buffer() with ctypes backend\")\n\n    def sizeof(self, cdata_or_BType):\n        if isinstance(cdata_or_BType, CTypesData):\n            return cdata_or_BType._get_size_of_instance()\n        else:\n            assert issubclass(cdata_or_BType, CTypesData)\n            return cdata_or_BType._get_size()\n\n    def alignof(self, BType):\n        assert issubclass(BType, CTypesData)\n        return BType._alignment()\n\n    def newp(self, BType, source):\n        if not issubclass(BType, CTypesData):\n            raise TypeError\n        return BType._newp(source)\n\n    def cast(self, BType, source):\n        return BType._cast_from(source)\n\n    def callback(self, BType, source, error, onerror):\n        assert onerror is None   # XXX not implemented\n        return BType(source, error)\n\n    _weakref_cache_ref = None\n\n    def gcp(self, cdata, destructor, size=0):\n        if self._weakref_cache_ref is None:\n            import weakref\n            class MyRef(weakref.ref):\n                def __eq__(self, other):\n                    myref = self()\n                    return self is other or (\n                        myref is not None and myref is other())\n                def __ne__(self, other):\n                    return not (self == other)\n                def __hash__(self):\n                    try:\n                        return self._hash\n                    except AttributeError:\n                        self._hash = hash(self())\n                        return self._hash\n            self._weakref_cache_ref = {}, MyRef\n        weak_cache, MyRef = self._weakref_cache_ref\n\n        if destructor is None:\n            try:\n                del weak_cache[MyRef(cdata)]\n            except KeyError:\n                raise TypeError(\"Can remove destructor only on a object \"\n                                \"previously returned by ffi.gc()\")\n            return None\n\n        def remove(k):\n            cdata, destructor = weak_cache.pop(k, (None, None))\n            if destructor is not None:\n                destructor(cdata)\n\n        new_cdata = self.cast(self.typeof(cdata), cdata)\n        assert new_cdata is not cdata\n        weak_cache[MyRef(new_cdata, remove)] = (cdata, destructor)\n        return new_cdata\n\n    typeof = type\n\n    def getcname(self, BType, replace_with):\n        return BType._get_c_name(replace_with)\n\n    def typeoffsetof(self, BType, fieldname, num=0):\n        if isinstance(fieldname, str):\n            if num == 0 and issubclass(BType, CTypesGenericPtr):\n                BType = BType._BItem\n            if not issubclass(BType, CTypesBaseStructOrUnion):\n                raise TypeError(\"expected a struct or union ctype\")\n            BField = BType._bfield_types[fieldname]\n            if BField is Ellipsis:\n                raise TypeError(\"not supported for bitfields\")\n            return (BField, BType._offsetof(fieldname))\n        elif isinstance(fieldname, (int, long)):\n            if issubclass(BType, CTypesGenericArray):\n                BType = BType._CTPtr\n            if not issubclass(BType, CTypesGenericPtr):\n                raise TypeError(\"expected an array or ptr ctype\")\n            BItem = BType._BItem\n            offset = BItem._get_size() * fieldname\n            if offset > sys.maxsize:\n                raise OverflowError\n            return (BItem, offset)\n        else:\n            raise TypeError(type(fieldname))\n\n    def rawaddressof(self, BTypePtr, cdata, offset=None):\n        if isinstance(cdata, CTypesBaseStructOrUnion):\n            ptr = ctypes.pointer(type(cdata)._to_ctypes(cdata))\n        elif isinstance(cdata, CTypesGenericPtr):\n            if offset is None or not issubclass(type(cdata)._BItem,\n                                                CTypesBaseStructOrUnion):\n                raise TypeError(\"unexpected cdata type\")\n            ptr = type(cdata)._to_ctypes(cdata)\n        elif isinstance(cdata, CTypesGenericArray):\n            ptr = type(cdata)._to_ctypes(cdata)\n        else:\n            raise TypeError(\"expected a <cdata 'struct-or-union'>\")\n        if offset:\n            ptr = ctypes.cast(\n                ctypes.c_void_p(\n                    ctypes.cast(ptr, ctypes.c_void_p).value + offset),\n                type(ptr))\n        return BTypePtr._from_ctypes(ptr)\n\n\nclass CTypesLibrary(object):\n\n    def __init__(self, backend, cdll):\n        self.backend = backend\n        self.cdll = cdll\n\n    def load_function(self, BType, name):\n        c_func = getattr(self.cdll, name)\n        funcobj = BType._from_ctypes(c_func)\n        funcobj._name = name\n        return funcobj\n\n    def read_variable(self, BType, name):\n        try:\n            ctypes_obj = BType._ctype.in_dll(self.cdll, name)\n        except AttributeError as e:\n            raise NotImplementedError(e)\n        return BType._from_ctypes(ctypes_obj)\n\n    def write_variable(self, BType, name, value):\n        new_ctypes_obj = BType._to_ctypes(value)\n        ctypes_obj = BType._ctype.in_dll(self.cdll, name)\n        ctypes.memmove(ctypes.addressof(ctypes_obj),\n                       ctypes.addressof(new_ctypes_obj),\n                       ctypes.sizeof(BType._ctype))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/cffi_opcode.py",
    "content": "from .error import VerificationError\n\nclass CffiOp(object):\n    def __init__(self, op, arg):\n        self.op = op\n        self.arg = arg\n\n    def as_c_expr(self):\n        if self.op is None:\n            assert isinstance(self.arg, str)\n            return '(_cffi_opcode_t)(%s)' % (self.arg,)\n        classname = CLASS_NAME[self.op]\n        return '_CFFI_OP(_CFFI_OP_%s, %s)' % (classname, self.arg)\n\n    def as_python_bytes(self):\n        if self.op is None and self.arg.isdigit():\n            value = int(self.arg)     # non-negative: '-' not in self.arg\n            if value >= 2**31:\n                raise OverflowError(\"cannot emit %r: limited to 2**31-1\"\n                                    % (self.arg,))\n            return format_four_bytes(value)\n        if isinstance(self.arg, str):\n            raise VerificationError(\"cannot emit to Python: %r\" % (self.arg,))\n        return format_four_bytes((self.arg << 8) | self.op)\n\n    def __str__(self):\n        classname = CLASS_NAME.get(self.op, self.op)\n        return '(%s %s)' % (classname, self.arg)\n\ndef format_four_bytes(num):\n    return '\\\\x%02X\\\\x%02X\\\\x%02X\\\\x%02X' % (\n        (num >> 24) & 0xFF,\n        (num >> 16) & 0xFF,\n        (num >>  8) & 0xFF,\n        (num      ) & 0xFF)\n\nOP_PRIMITIVE       = 1\nOP_POINTER         = 3\nOP_ARRAY           = 5\nOP_OPEN_ARRAY      = 7\nOP_STRUCT_UNION    = 9\nOP_ENUM            = 11\nOP_FUNCTION        = 13\nOP_FUNCTION_END    = 15\nOP_NOOP            = 17\nOP_BITFIELD        = 19\nOP_TYPENAME        = 21\nOP_CPYTHON_BLTN_V  = 23   # varargs\nOP_CPYTHON_BLTN_N  = 25   # noargs\nOP_CPYTHON_BLTN_O  = 27   # O  (i.e. a single arg)\nOP_CONSTANT        = 29\nOP_CONSTANT_INT    = 31\nOP_GLOBAL_VAR      = 33\nOP_DLOPEN_FUNC     = 35\nOP_DLOPEN_CONST    = 37\nOP_GLOBAL_VAR_F    = 39\nOP_EXTERN_PYTHON   = 41\n\nPRIM_VOID          = 0\nPRIM_BOOL          = 1\nPRIM_CHAR          = 2\nPRIM_SCHAR         = 3\nPRIM_UCHAR         = 4\nPRIM_SHORT         = 5\nPRIM_USHORT        = 6\nPRIM_INT           = 7\nPRIM_UINT          = 8\nPRIM_LONG          = 9\nPRIM_ULONG         = 10\nPRIM_LONGLONG      = 11\nPRIM_ULONGLONG     = 12\nPRIM_FLOAT         = 13\nPRIM_DOUBLE        = 14\nPRIM_LONGDOUBLE    = 15\n\nPRIM_WCHAR         = 16\nPRIM_INT8          = 17\nPRIM_UINT8         = 18\nPRIM_INT16         = 19\nPRIM_UINT16        = 20\nPRIM_INT32         = 21\nPRIM_UINT32        = 22\nPRIM_INT64         = 23\nPRIM_UINT64        = 24\nPRIM_INTPTR        = 25\nPRIM_UINTPTR       = 26\nPRIM_PTRDIFF       = 27\nPRIM_SIZE          = 28\nPRIM_SSIZE         = 29\nPRIM_INT_LEAST8    = 30\nPRIM_UINT_LEAST8   = 31\nPRIM_INT_LEAST16   = 32\nPRIM_UINT_LEAST16  = 33\nPRIM_INT_LEAST32   = 34\nPRIM_UINT_LEAST32  = 35\nPRIM_INT_LEAST64   = 36\nPRIM_UINT_LEAST64  = 37\nPRIM_INT_FAST8     = 38\nPRIM_UINT_FAST8    = 39\nPRIM_INT_FAST16    = 40\nPRIM_UINT_FAST16   = 41\nPRIM_INT_FAST32    = 42\nPRIM_UINT_FAST32   = 43\nPRIM_INT_FAST64    = 44\nPRIM_UINT_FAST64   = 45\nPRIM_INTMAX        = 46\nPRIM_UINTMAX       = 47\nPRIM_FLOATCOMPLEX  = 48\nPRIM_DOUBLECOMPLEX = 49\nPRIM_CHAR16        = 50\nPRIM_CHAR32        = 51\n\n_NUM_PRIM          = 52\n_UNKNOWN_PRIM          = -1\n_UNKNOWN_FLOAT_PRIM    = -2\n_UNKNOWN_LONG_DOUBLE   = -3\n\n_IO_FILE_STRUCT        = -1\n\nPRIMITIVE_TO_INDEX = {\n    'char':               PRIM_CHAR,\n    'short':              PRIM_SHORT,\n    'int':                PRIM_INT,\n    'long':               PRIM_LONG,\n    'long long':          PRIM_LONGLONG,\n    'signed char':        PRIM_SCHAR,\n    'unsigned char':      PRIM_UCHAR,\n    'unsigned short':     PRIM_USHORT,\n    'unsigned int':       PRIM_UINT,\n    'unsigned long':      PRIM_ULONG,\n    'unsigned long long': PRIM_ULONGLONG,\n    'float':              PRIM_FLOAT,\n    'double':             PRIM_DOUBLE,\n    'long double':        PRIM_LONGDOUBLE,\n    'float _Complex':     PRIM_FLOATCOMPLEX,\n    'double _Complex':    PRIM_DOUBLECOMPLEX,\n    '_Bool':              PRIM_BOOL,\n    'wchar_t':            PRIM_WCHAR,\n    'char16_t':           PRIM_CHAR16,\n    'char32_t':           PRIM_CHAR32,\n    'int8_t':             PRIM_INT8,\n    'uint8_t':            PRIM_UINT8,\n    'int16_t':            PRIM_INT16,\n    'uint16_t':           PRIM_UINT16,\n    'int32_t':            PRIM_INT32,\n    'uint32_t':           PRIM_UINT32,\n    'int64_t':            PRIM_INT64,\n    'uint64_t':           PRIM_UINT64,\n    'intptr_t':           PRIM_INTPTR,\n    'uintptr_t':          PRIM_UINTPTR,\n    'ptrdiff_t':          PRIM_PTRDIFF,\n    'size_t':             PRIM_SIZE,\n    'ssize_t':            PRIM_SSIZE,\n    'int_least8_t':       PRIM_INT_LEAST8,\n    'uint_least8_t':      PRIM_UINT_LEAST8,\n    'int_least16_t':      PRIM_INT_LEAST16,\n    'uint_least16_t':     PRIM_UINT_LEAST16,\n    'int_least32_t':      PRIM_INT_LEAST32,\n    'uint_least32_t':     PRIM_UINT_LEAST32,\n    'int_least64_t':      PRIM_INT_LEAST64,\n    'uint_least64_t':     PRIM_UINT_LEAST64,\n    'int_fast8_t':        PRIM_INT_FAST8,\n    'uint_fast8_t':       PRIM_UINT_FAST8,\n    'int_fast16_t':       PRIM_INT_FAST16,\n    'uint_fast16_t':      PRIM_UINT_FAST16,\n    'int_fast32_t':       PRIM_INT_FAST32,\n    'uint_fast32_t':      PRIM_UINT_FAST32,\n    'int_fast64_t':       PRIM_INT_FAST64,\n    'uint_fast64_t':      PRIM_UINT_FAST64,\n    'intmax_t':           PRIM_INTMAX,\n    'uintmax_t':          PRIM_UINTMAX,\n    }\n\nF_UNION         = 0x01\nF_CHECK_FIELDS  = 0x02\nF_PACKED        = 0x04\nF_EXTERNAL      = 0x08\nF_OPAQUE        = 0x10\n\nG_FLAGS = dict([('_CFFI_' + _key, globals()[_key])\n                for _key in ['F_UNION', 'F_CHECK_FIELDS', 'F_PACKED',\n                             'F_EXTERNAL', 'F_OPAQUE']])\n\nCLASS_NAME = {}\nfor _name, _value in list(globals().items()):\n    if _name.startswith('OP_') and isinstance(_value, int):\n        CLASS_NAME[_value] = _name[3:]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/commontypes.py",
    "content": "import sys\nfrom . import model\nfrom .error import FFIError\n\n\nCOMMON_TYPES = {}\n\ntry:\n    # fetch \"bool\" and all simple Windows types\n    from _cffi_backend import _get_common_types\n    _get_common_types(COMMON_TYPES)\nexcept ImportError:\n    pass\n\nCOMMON_TYPES['FILE'] = model.unknown_type('FILE', '_IO_FILE')\nCOMMON_TYPES['bool'] = '_Bool'    # in case we got ImportError above\n\nfor _type in model.PrimitiveType.ALL_PRIMITIVE_TYPES:\n    if _type.endswith('_t'):\n        COMMON_TYPES[_type] = _type\ndel _type\n\n_CACHE = {}\n\ndef resolve_common_type(parser, commontype):\n    try:\n        return _CACHE[commontype]\n    except KeyError:\n        cdecl = COMMON_TYPES.get(commontype, commontype)\n        if not isinstance(cdecl, str):\n            result, quals = cdecl, 0    # cdecl is already a BaseType\n        elif cdecl in model.PrimitiveType.ALL_PRIMITIVE_TYPES:\n            result, quals = model.PrimitiveType(cdecl), 0\n        elif cdecl == 'set-unicode-needed':\n            raise FFIError(\"The Windows type %r is only available after \"\n                           \"you call ffi.set_unicode()\" % (commontype,))\n        else:\n            if commontype == cdecl:\n                raise FFIError(\n                    \"Unsupported type: %r.  Please look at \"\n        \"http://cffi.readthedocs.io/en/latest/cdef.html#ffi-cdef-limitations \"\n                    \"and file an issue if you think this type should really \"\n                    \"be supported.\" % (commontype,))\n            result, quals = parser.parse_type_and_quals(cdecl)   # recursive\n\n        assert isinstance(result, model.BaseTypeByIdentity)\n        _CACHE[commontype] = result, quals\n        return result, quals\n\n\n# ____________________________________________________________\n# extra types for Windows (most of them are in commontypes.c)\n\n\ndef win_common_types():\n    return {\n        \"UNICODE_STRING\": model.StructType(\n            \"_UNICODE_STRING\",\n            [\"Length\",\n             \"MaximumLength\",\n             \"Buffer\"],\n            [model.PrimitiveType(\"unsigned short\"),\n             model.PrimitiveType(\"unsigned short\"),\n             model.PointerType(model.PrimitiveType(\"wchar_t\"))],\n            [-1, -1, -1]),\n        \"PUNICODE_STRING\": \"UNICODE_STRING *\",\n        \"PCUNICODE_STRING\": \"const UNICODE_STRING *\",\n\n        \"TBYTE\": \"set-unicode-needed\",\n        \"TCHAR\": \"set-unicode-needed\",\n        \"LPCTSTR\": \"set-unicode-needed\",\n        \"PCTSTR\": \"set-unicode-needed\",\n        \"LPTSTR\": \"set-unicode-needed\",\n        \"PTSTR\": \"set-unicode-needed\",\n        \"PTBYTE\": \"set-unicode-needed\",\n        \"PTCHAR\": \"set-unicode-needed\",\n        }\n\nif sys.platform == 'win32':\n    COMMON_TYPES.update(win_common_types())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/cparser.py",
    "content": "from . import model\nfrom .commontypes import COMMON_TYPES, resolve_common_type\nfrom .error import FFIError, CDefError\ntry:\n    from . import _pycparser as pycparser\nexcept ImportError:\n    import pycparser\nimport weakref, re, sys\n\ntry:\n    if sys.version_info < (3,):\n        import thread as _thread\n    else:\n        import _thread\n    lock = _thread.allocate_lock()\nexcept ImportError:\n    lock = None\n\ndef _workaround_for_static_import_finders():\n    # Issue #392: packaging tools like cx_Freeze can not find these\n    # because pycparser uses exec dynamic import.  This is an obscure\n    # workaround.  This function is never called.\n    import pycparser.yacctab\n    import pycparser.lextab\n\nCDEF_SOURCE_STRING = \"<cdef source string>\"\n_r_comment = re.compile(r\"/\\*.*?\\*/|//([^\\n\\\\]|\\\\.)*?$\",\n                        re.DOTALL | re.MULTILINE)\n_r_define  = re.compile(r\"^\\s*#\\s*define\\s+([A-Za-z_][A-Za-z_0-9]*)\"\n                        r\"\\b((?:[^\\n\\\\]|\\\\.)*?)$\",\n                        re.DOTALL | re.MULTILINE)\n_r_partial_enum = re.compile(r\"=\\s*\\.\\.\\.\\s*[,}]|\\.\\.\\.\\s*\\}\")\n_r_enum_dotdotdot = re.compile(r\"__dotdotdot\\d+__$\")\n_r_partial_array = re.compile(r\"\\[\\s*\\.\\.\\.\\s*\\]\")\n_r_words = re.compile(r\"\\w+|\\S\")\n_parser_cache = None\n_r_int_literal = re.compile(r\"-?0?x?[0-9a-f]+[lu]*$\", re.IGNORECASE)\n_r_stdcall1 = re.compile(r\"\\b(__stdcall|WINAPI)\\b\")\n_r_stdcall2 = re.compile(r\"[(]\\s*(__stdcall|WINAPI)\\b\")\n_r_cdecl = re.compile(r\"\\b__cdecl\\b\")\n_r_extern_python = re.compile(r'\\bextern\\s*\"'\n                              r'(Python|Python\\s*\\+\\s*C|C\\s*\\+\\s*Python)\"\\s*.')\n_r_star_const_space = re.compile(       # matches \"* const \"\n    r\"[*]\\s*((const|volatile|restrict)\\b\\s*)+\")\n_r_int_dotdotdot = re.compile(r\"(\\b(int|long|short|signed|unsigned|char)\\s*)+\"\n                              r\"\\.\\.\\.\")\n_r_float_dotdotdot = re.compile(r\"\\b(double|float)\\s*\\.\\.\\.\")\n\ndef _get_parser():\n    global _parser_cache\n    if _parser_cache is None:\n        _parser_cache = pycparser.CParser()\n    return _parser_cache\n\ndef _workaround_for_old_pycparser(csource):\n    # Workaround for a pycparser issue (fixed between pycparser 2.10 and\n    # 2.14): \"char*const***\" gives us a wrong syntax tree, the same as\n    # for \"char***(*const)\".  This means we can't tell the difference\n    # afterwards.  But \"char(*const(***))\" gives us the right syntax\n    # tree.  The issue only occurs if there are several stars in\n    # sequence with no parenthesis inbetween, just possibly qualifiers.\n    # Attempt to fix it by adding some parentheses in the source: each\n    # time we see \"* const\" or \"* const *\", we add an opening\n    # parenthesis before each star---the hard part is figuring out where\n    # to close them.\n    parts = []\n    while True:\n        match = _r_star_const_space.search(csource)\n        if not match:\n            break\n        #print repr(''.join(parts)+csource), '=>',\n        parts.append(csource[:match.start()])\n        parts.append('('); closing = ')'\n        parts.append(match.group())   # e.g. \"* const \"\n        endpos = match.end()\n        if csource.startswith('*', endpos):\n            parts.append('('); closing += ')'\n        level = 0\n        i = endpos\n        while i < len(csource):\n            c = csource[i]\n            if c == '(':\n                level += 1\n            elif c == ')':\n                if level == 0:\n                    break\n                level -= 1\n            elif c in ',;=':\n                if level == 0:\n                    break\n            i += 1\n        csource = csource[endpos:i] + closing + csource[i:]\n        #print repr(''.join(parts)+csource)\n    parts.append(csource)\n    return ''.join(parts)\n\ndef _preprocess_extern_python(csource):\n    # input: `extern \"Python\" int foo(int);` or\n    #        `extern \"Python\" { int foo(int); }`\n    # output:\n    #     void __cffi_extern_python_start;\n    #     int foo(int);\n    #     void __cffi_extern_python_stop;\n    #\n    # input: `extern \"Python+C\" int foo(int);`\n    # output:\n    #     void __cffi_extern_python_plus_c_start;\n    #     int foo(int);\n    #     void __cffi_extern_python_stop;\n    parts = []\n    while True:\n        match = _r_extern_python.search(csource)\n        if not match:\n            break\n        endpos = match.end() - 1\n        #print\n        #print ''.join(parts)+csource\n        #print '=>'\n        parts.append(csource[:match.start()])\n        if 'C' in match.group(1):\n            parts.append('void __cffi_extern_python_plus_c_start; ')\n        else:\n            parts.append('void __cffi_extern_python_start; ')\n        if csource[endpos] == '{':\n            # grouping variant\n            closing = csource.find('}', endpos)\n            if closing < 0:\n                raise CDefError(\"'extern \\\"Python\\\" {': no '}' found\")\n            if csource.find('{', endpos + 1, closing) >= 0:\n                raise NotImplementedError(\"cannot use { } inside a block \"\n                                          \"'extern \\\"Python\\\" { ... }'\")\n            parts.append(csource[endpos+1:closing])\n            csource = csource[closing+1:]\n        else:\n            # non-grouping variant\n            semicolon = csource.find(';', endpos)\n            if semicolon < 0:\n                raise CDefError(\"'extern \\\"Python\\\": no ';' found\")\n            parts.append(csource[endpos:semicolon+1])\n            csource = csource[semicolon+1:]\n        parts.append(' void __cffi_extern_python_stop;')\n        #print ''.join(parts)+csource\n        #print\n    parts.append(csource)\n    return ''.join(parts)\n\ndef _warn_for_string_literal(csource):\n    if '\"' not in csource:\n        return\n    for line in csource.splitlines():\n        if '\"' in line and not line.lstrip().startswith('#'):\n            import warnings\n            warnings.warn(\"String literal found in cdef() or type source. \"\n                          \"String literals are ignored here, but you should \"\n                          \"remove them anyway because some character sequences \"\n                          \"confuse pre-parsing.\")\n            break\n\ndef _warn_for_non_extern_non_static_global_variable(decl):\n    if not decl.storage:\n        import warnings\n        warnings.warn(\"Declaration of global variable '%s' in cdef() should \"\n                      \"be marked 'extern' for consistency (or possibly \"\n                      \"'static' in API mode)\" % (decl.name,))\n\ndef _preprocess(csource):\n    # Remove comments.  NOTE: this only work because the cdef() section\n    # should not contain any string literal!\n    csource = _r_comment.sub(' ', csource)\n    # Remove the \"#define FOO x\" lines\n    macros = {}\n    for match in _r_define.finditer(csource):\n        macroname, macrovalue = match.groups()\n        macrovalue = macrovalue.replace('\\\\\\n', '').strip()\n        macros[macroname] = macrovalue\n    csource = _r_define.sub('', csource)\n    #\n    if pycparser.__version__ < '2.14':\n        csource = _workaround_for_old_pycparser(csource)\n    #\n    # BIG HACK: replace WINAPI or __stdcall with \"volatile const\".\n    # It doesn't make sense for the return type of a function to be\n    # \"volatile volatile const\", so we abuse it to detect __stdcall...\n    # Hack number 2 is that \"int(volatile *fptr)();\" is not valid C\n    # syntax, so we place the \"volatile\" before the opening parenthesis.\n    csource = _r_stdcall2.sub(' volatile volatile const(', csource)\n    csource = _r_stdcall1.sub(' volatile volatile const ', csource)\n    csource = _r_cdecl.sub(' ', csource)\n    #\n    # Replace `extern \"Python\"` with start/end markers\n    csource = _preprocess_extern_python(csource)\n    #\n    # Now there should not be any string literal left; warn if we get one\n    _warn_for_string_literal(csource)\n    #\n    # Replace \"[...]\" with \"[__dotdotdotarray__]\"\n    csource = _r_partial_array.sub('[__dotdotdotarray__]', csource)\n    #\n    # Replace \"...}\" with \"__dotdotdotNUM__}\".  This construction should\n    # occur only at the end of enums; at the end of structs we have \"...;}\"\n    # and at the end of vararg functions \"...);\".  Also replace \"=...[,}]\"\n    # with \",__dotdotdotNUM__[,}]\": this occurs in the enums too, when\n    # giving an unknown value.\n    matches = list(_r_partial_enum.finditer(csource))\n    for number, match in enumerate(reversed(matches)):\n        p = match.start()\n        if csource[p] == '=':\n            p2 = csource.find('...', p, match.end())\n            assert p2 > p\n            csource = '%s,__dotdotdot%d__ %s' % (csource[:p], number,\n                                                 csource[p2+3:])\n        else:\n            assert csource[p:p+3] == '...'\n            csource = '%s __dotdotdot%d__ %s' % (csource[:p], number,\n                                                 csource[p+3:])\n    # Replace \"int ...\" or \"unsigned long int...\" with \"__dotdotdotint__\"\n    csource = _r_int_dotdotdot.sub(' __dotdotdotint__ ', csource)\n    # Replace \"float ...\" or \"double...\" with \"__dotdotdotfloat__\"\n    csource = _r_float_dotdotdot.sub(' __dotdotdotfloat__ ', csource)\n    # Replace all remaining \"...\" with the same name, \"__dotdotdot__\",\n    # which is declared with a typedef for the purpose of C parsing.\n    return csource.replace('...', ' __dotdotdot__ '), macros\n\ndef _common_type_names(csource):\n    # Look in the source for what looks like usages of types from the\n    # list of common types.  A \"usage\" is approximated here as the\n    # appearance of the word, minus a \"definition\" of the type, which\n    # is the last word in a \"typedef\" statement.  Approximative only\n    # but should be fine for all the common types.\n    look_for_words = set(COMMON_TYPES)\n    look_for_words.add(';')\n    look_for_words.add(',')\n    look_for_words.add('(')\n    look_for_words.add(')')\n    look_for_words.add('typedef')\n    words_used = set()\n    is_typedef = False\n    paren = 0\n    previous_word = ''\n    for word in _r_words.findall(csource):\n        if word in look_for_words:\n            if word == ';':\n                if is_typedef:\n                    words_used.discard(previous_word)\n                    look_for_words.discard(previous_word)\n                    is_typedef = False\n            elif word == 'typedef':\n                is_typedef = True\n                paren = 0\n            elif word == '(':\n                paren += 1\n            elif word == ')':\n                paren -= 1\n            elif word == ',':\n                if is_typedef and paren == 0:\n                    words_used.discard(previous_word)\n                    look_for_words.discard(previous_word)\n            else:   # word in COMMON_TYPES\n                words_used.add(word)\n        previous_word = word\n    return words_used\n\n\nclass Parser(object):\n\n    def __init__(self):\n        self._declarations = {}\n        self._included_declarations = set()\n        self._anonymous_counter = 0\n        self._structnode2type = weakref.WeakKeyDictionary()\n        self._options = {}\n        self._int_constants = {}\n        self._recomplete = []\n        self._uses_new_feature = None\n\n    def _parse(self, csource):\n        csource, macros = _preprocess(csource)\n        # XXX: for more efficiency we would need to poke into the\n        # internals of CParser...  the following registers the\n        # typedefs, because their presence or absence influences the\n        # parsing itself (but what they are typedef'ed to plays no role)\n        ctn = _common_type_names(csource)\n        typenames = []\n        for name in sorted(self._declarations):\n            if name.startswith('typedef '):\n                name = name[8:]\n                typenames.append(name)\n                ctn.discard(name)\n        typenames += sorted(ctn)\n        #\n        csourcelines = []\n        csourcelines.append('# 1 \"<cdef automatic initialization code>\"')\n        for typename in typenames:\n            csourcelines.append('typedef int %s;' % typename)\n        csourcelines.append('typedef int __dotdotdotint__, __dotdotdotfloat__,'\n                            ' __dotdotdot__;')\n        # this forces pycparser to consider the following in the file\n        # called <cdef source string> from line 1\n        csourcelines.append('# 1 \"%s\"' % (CDEF_SOURCE_STRING,))\n        csourcelines.append(csource)\n        fullcsource = '\\n'.join(csourcelines)\n        if lock is not None:\n            lock.acquire()     # pycparser is not thread-safe...\n        try:\n            ast = _get_parser().parse(fullcsource)\n        except pycparser.c_parser.ParseError as e:\n            self.convert_pycparser_error(e, csource)\n        finally:\n            if lock is not None:\n                lock.release()\n        # csource will be used to find buggy source text\n        return ast, macros, csource\n\n    def _convert_pycparser_error(self, e, csource):\n        # xxx look for \"<cdef source string>:NUM:\" at the start of str(e)\n        # and interpret that as a line number.  This will not work if\n        # the user gives explicit ``# NUM \"FILE\"`` directives.\n        line = None\n        msg = str(e)\n        match = re.match(r\"%s:(\\d+):\" % (CDEF_SOURCE_STRING,), msg)\n        if match:\n            linenum = int(match.group(1), 10)\n            csourcelines = csource.splitlines()\n            if 1 <= linenum <= len(csourcelines):\n                line = csourcelines[linenum-1]\n        return line\n\n    def convert_pycparser_error(self, e, csource):\n        line = self._convert_pycparser_error(e, csource)\n\n        msg = str(e)\n        if line:\n            msg = 'cannot parse \"%s\"\\n%s' % (line.strip(), msg)\n        else:\n            msg = 'parse error\\n%s' % (msg,)\n        raise CDefError(msg)\n\n    def parse(self, csource, override=False, packed=False, pack=None,\n                    dllexport=False):\n        if packed:\n            if packed != True:\n                raise ValueError(\"'packed' should be False or True; use \"\n                                 \"'pack' to give another value\")\n            if pack:\n                raise ValueError(\"cannot give both 'pack' and 'packed'\")\n            pack = 1\n        elif pack:\n            if pack & (pack - 1):\n                raise ValueError(\"'pack' must be a power of two, not %r\" %\n                    (pack,))\n        else:\n            pack = 0\n        prev_options = self._options\n        try:\n            self._options = {'override': override,\n                             'packed': pack,\n                             'dllexport': dllexport}\n            self._internal_parse(csource)\n        finally:\n            self._options = prev_options\n\n    def _internal_parse(self, csource):\n        ast, macros, csource = self._parse(csource)\n        # add the macros\n        self._process_macros(macros)\n        # find the first \"__dotdotdot__\" and use that as a separator\n        # between the repeated typedefs and the real csource\n        iterator = iter(ast.ext)\n        for decl in iterator:\n            if decl.name == '__dotdotdot__':\n                break\n        else:\n            assert 0\n        current_decl = None\n        #\n        try:\n            self._inside_extern_python = '__cffi_extern_python_stop'\n            for decl in iterator:\n                current_decl = decl\n                if isinstance(decl, pycparser.c_ast.Decl):\n                    self._parse_decl(decl)\n                elif isinstance(decl, pycparser.c_ast.Typedef):\n                    if not decl.name:\n                        raise CDefError(\"typedef does not declare any name\",\n                                        decl)\n                    quals = 0\n                    if (isinstance(decl.type.type, pycparser.c_ast.IdentifierType) and\n                            decl.type.type.names[-1].startswith('__dotdotdot')):\n                        realtype = self._get_unknown_type(decl)\n                    elif (isinstance(decl.type, pycparser.c_ast.PtrDecl) and\n                          isinstance(decl.type.type, pycparser.c_ast.TypeDecl) and\n                          isinstance(decl.type.type.type,\n                                     pycparser.c_ast.IdentifierType) and\n                          decl.type.type.type.names[-1].startswith('__dotdotdot')):\n                        realtype = self._get_unknown_ptr_type(decl)\n                    else:\n                        realtype, quals = self._get_type_and_quals(\n                            decl.type, name=decl.name, partial_length_ok=True)\n                    self._declare('typedef ' + decl.name, realtype, quals=quals)\n                elif decl.__class__.__name__ == 'Pragma':\n                    pass    # skip pragma, only in pycparser 2.15\n                else:\n                    raise CDefError(\"unexpected <%s>: this construct is valid \"\n                                    \"C but not valid in cdef()\" %\n                                    decl.__class__.__name__, decl)\n        except CDefError as e:\n            if len(e.args) == 1:\n                e.args = e.args + (current_decl,)\n            raise\n        except FFIError as e:\n            msg = self._convert_pycparser_error(e, csource)\n            if msg:\n                e.args = (e.args[0] + \"\\n    *** Err: %s\" % msg,)\n            raise\n\n    def _add_constants(self, key, val):\n        if key in self._int_constants:\n            if self._int_constants[key] == val:\n                return     # ignore identical double declarations\n            raise FFIError(\n                \"multiple declarations of constant: %s\" % (key,))\n        self._int_constants[key] = val\n\n    def _add_integer_constant(self, name, int_str):\n        int_str = int_str.lower().rstrip(\"ul\")\n        neg = int_str.startswith('-')\n        if neg:\n            int_str = int_str[1:]\n        # \"010\" is not valid oct in py3\n        if (int_str.startswith(\"0\") and int_str != '0'\n                and not int_str.startswith(\"0x\")):\n            int_str = \"0o\" + int_str[1:]\n        pyvalue = int(int_str, 0)\n        if neg:\n            pyvalue = -pyvalue\n        self._add_constants(name, pyvalue)\n        self._declare('macro ' + name, pyvalue)\n\n    def _process_macros(self, macros):\n        for key, value in macros.items():\n            value = value.strip()\n            if _r_int_literal.match(value):\n                self._add_integer_constant(key, value)\n            elif value == '...':\n                self._declare('macro ' + key, value)\n            else:\n                raise CDefError(\n                    'only supports one of the following syntax:\\n'\n                    '  #define %s ...     (literally dot-dot-dot)\\n'\n                    '  #define %s NUMBER  (with NUMBER an integer'\n                                    ' constant, decimal/hex/octal)\\n'\n                    'got:\\n'\n                    '  #define %s %s'\n                    % (key, key, key, value))\n\n    def _declare_function(self, tp, quals, decl):\n        tp = self._get_type_pointer(tp, quals)\n        if self._options.get('dllexport'):\n            tag = 'dllexport_python '\n        elif self._inside_extern_python == '__cffi_extern_python_start':\n            tag = 'extern_python '\n        elif self._inside_extern_python == '__cffi_extern_python_plus_c_start':\n            tag = 'extern_python_plus_c '\n        else:\n            tag = 'function '\n        self._declare(tag + decl.name, tp)\n\n    def _parse_decl(self, decl):\n        node = decl.type\n        if isinstance(node, pycparser.c_ast.FuncDecl):\n            tp, quals = self._get_type_and_quals(node, name=decl.name)\n            assert isinstance(tp, model.RawFunctionType)\n            self._declare_function(tp, quals, decl)\n        else:\n            if isinstance(node, pycparser.c_ast.Struct):\n                self._get_struct_union_enum_type('struct', node)\n            elif isinstance(node, pycparser.c_ast.Union):\n                self._get_struct_union_enum_type('union', node)\n            elif isinstance(node, pycparser.c_ast.Enum):\n                self._get_struct_union_enum_type('enum', node)\n            elif not decl.name:\n                raise CDefError(\"construct does not declare any variable\",\n                                decl)\n            #\n            if decl.name:\n                tp, quals = self._get_type_and_quals(node,\n                                                     partial_length_ok=True)\n                if tp.is_raw_function:\n                    self._declare_function(tp, quals, decl)\n                elif (tp.is_integer_type() and\n                        hasattr(decl, 'init') and\n                        hasattr(decl.init, 'value') and\n                        _r_int_literal.match(decl.init.value)):\n                    self._add_integer_constant(decl.name, decl.init.value)\n                elif (tp.is_integer_type() and\n                        isinstance(decl.init, pycparser.c_ast.UnaryOp) and\n                        decl.init.op == '-' and\n                        hasattr(decl.init.expr, 'value') and\n                        _r_int_literal.match(decl.init.expr.value)):\n                    self._add_integer_constant(decl.name,\n                                               '-' + decl.init.expr.value)\n                elif (tp is model.void_type and\n                      decl.name.startswith('__cffi_extern_python_')):\n                    # hack: `extern \"Python\"` in the C source is replaced\n                    # with \"void __cffi_extern_python_start;\" and\n                    # \"void __cffi_extern_python_stop;\"\n                    self._inside_extern_python = decl.name\n                else:\n                    if self._inside_extern_python !='__cffi_extern_python_stop':\n                        raise CDefError(\n                            \"cannot declare constants or \"\n                            \"variables with 'extern \\\"Python\\\"'\")\n                    if (quals & model.Q_CONST) and not tp.is_array_type:\n                        self._declare('constant ' + decl.name, tp, quals=quals)\n                    else:\n                        _warn_for_non_extern_non_static_global_variable(decl)\n                        self._declare('variable ' + decl.name, tp, quals=quals)\n\n    def parse_type(self, cdecl):\n        return self.parse_type_and_quals(cdecl)[0]\n\n    def parse_type_and_quals(self, cdecl):\n        ast, macros = self._parse('void __dummy(\\n%s\\n);' % cdecl)[:2]\n        assert not macros\n        exprnode = ast.ext[-1].type.args.params[0]\n        if isinstance(exprnode, pycparser.c_ast.ID):\n            raise CDefError(\"unknown identifier '%s'\" % (exprnode.name,))\n        return self._get_type_and_quals(exprnode.type)\n\n    def _declare(self, name, obj, included=False, quals=0):\n        if name in self._declarations:\n            prevobj, prevquals = self._declarations[name]\n            if prevobj is obj and prevquals == quals:\n                return\n            if not self._options.get('override'):\n                raise FFIError(\n                    \"multiple declarations of %s (for interactive usage, \"\n                    \"try cdef(xx, override=True))\" % (name,))\n        assert '__dotdotdot__' not in name.split()\n        self._declarations[name] = (obj, quals)\n        if included:\n            self._included_declarations.add(obj)\n\n    def _extract_quals(self, type):\n        quals = 0\n        if isinstance(type, (pycparser.c_ast.TypeDecl,\n                             pycparser.c_ast.PtrDecl)):\n            if 'const' in type.quals:\n                quals |= model.Q_CONST\n            if 'volatile' in type.quals:\n                quals |= model.Q_VOLATILE\n            if 'restrict' in type.quals:\n                quals |= model.Q_RESTRICT\n        return quals\n\n    def _get_type_pointer(self, type, quals, declname=None):\n        if isinstance(type, model.RawFunctionType):\n            return type.as_function_pointer()\n        if (isinstance(type, model.StructOrUnionOrEnum) and\n                type.name.startswith('$') and type.name[1:].isdigit() and\n                type.forcename is None and declname is not None):\n            return model.NamedPointerType(type, declname, quals)\n        return model.PointerType(type, quals)\n\n    def _get_type_and_quals(self, typenode, name=None, partial_length_ok=False):\n        # first, dereference typedefs, if we have it already parsed, we're good\n        if (isinstance(typenode, pycparser.c_ast.TypeDecl) and\n            isinstance(typenode.type, pycparser.c_ast.IdentifierType) and\n            len(typenode.type.names) == 1 and\n            ('typedef ' + typenode.type.names[0]) in self._declarations):\n            tp, quals = self._declarations['typedef ' + typenode.type.names[0]]\n            quals |= self._extract_quals(typenode)\n            return tp, quals\n        #\n        if isinstance(typenode, pycparser.c_ast.ArrayDecl):\n            # array type\n            if typenode.dim is None:\n                length = None\n            else:\n                length = self._parse_constant(\n                    typenode.dim, partial_length_ok=partial_length_ok)\n            tp, quals = self._get_type_and_quals(typenode.type,\n                                partial_length_ok=partial_length_ok)\n            return model.ArrayType(tp, length), quals\n        #\n        if isinstance(typenode, pycparser.c_ast.PtrDecl):\n            # pointer type\n            itemtype, itemquals = self._get_type_and_quals(typenode.type)\n            tp = self._get_type_pointer(itemtype, itemquals, declname=name)\n            quals = self._extract_quals(typenode)\n            return tp, quals\n        #\n        if isinstance(typenode, pycparser.c_ast.TypeDecl):\n            quals = self._extract_quals(typenode)\n            type = typenode.type\n            if isinstance(type, pycparser.c_ast.IdentifierType):\n                # assume a primitive type.  get it from .names, but reduce\n                # synonyms to a single chosen combination\n                names = list(type.names)\n                if names != ['signed', 'char']:    # keep this unmodified\n                    prefixes = {}\n                    while names:\n                        name = names[0]\n                        if name in ('short', 'long', 'signed', 'unsigned'):\n                            prefixes[name] = prefixes.get(name, 0) + 1\n                            del names[0]\n                        else:\n                            break\n                    # ignore the 'signed' prefix below, and reorder the others\n                    newnames = []\n                    for prefix in ('unsigned', 'short', 'long'):\n                        for i in range(prefixes.get(prefix, 0)):\n                            newnames.append(prefix)\n                    if not names:\n                        names = ['int']    # implicitly\n                    if names == ['int']:   # but kill it if 'short' or 'long'\n                        if 'short' in prefixes or 'long' in prefixes:\n                            names = []\n                    names = newnames + names\n                ident = ' '.join(names)\n                if ident == 'void':\n                    return model.void_type, quals\n                if ident == '__dotdotdot__':\n                    raise FFIError(':%d: bad usage of \"...\"' %\n                            typenode.coord.line)\n                tp0, quals0 = resolve_common_type(self, ident)\n                return tp0, (quals | quals0)\n            #\n            if isinstance(type, pycparser.c_ast.Struct):\n                # 'struct foobar'\n                tp = self._get_struct_union_enum_type('struct', type, name)\n                return tp, quals\n            #\n            if isinstance(type, pycparser.c_ast.Union):\n                # 'union foobar'\n                tp = self._get_struct_union_enum_type('union', type, name)\n                return tp, quals\n            #\n            if isinstance(type, pycparser.c_ast.Enum):\n                # 'enum foobar'\n                tp = self._get_struct_union_enum_type('enum', type, name)\n                return tp, quals\n        #\n        if isinstance(typenode, pycparser.c_ast.FuncDecl):\n            # a function type\n            return self._parse_function_type(typenode, name), 0\n        #\n        # nested anonymous structs or unions end up here\n        if isinstance(typenode, pycparser.c_ast.Struct):\n            return self._get_struct_union_enum_type('struct', typenode, name,\n                                                    nested=True), 0\n        if isinstance(typenode, pycparser.c_ast.Union):\n            return self._get_struct_union_enum_type('union', typenode, name,\n                                                    nested=True), 0\n        #\n        raise FFIError(\":%d: bad or unsupported type declaration\" %\n                typenode.coord.line)\n\n    def _parse_function_type(self, typenode, funcname=None):\n        params = list(getattr(typenode.args, 'params', []))\n        for i, arg in enumerate(params):\n            if not hasattr(arg, 'type'):\n                raise CDefError(\"%s arg %d: unknown type '%s'\"\n                    \" (if you meant to use the old C syntax of giving\"\n                    \" untyped arguments, it is not supported)\"\n                    % (funcname or 'in expression', i + 1,\n                       getattr(arg, 'name', '?')))\n        ellipsis = (\n            len(params) > 0 and\n            isinstance(params[-1].type, pycparser.c_ast.TypeDecl) and\n            isinstance(params[-1].type.type,\n                       pycparser.c_ast.IdentifierType) and\n            params[-1].type.type.names == ['__dotdotdot__'])\n        if ellipsis:\n            params.pop()\n            if not params:\n                raise CDefError(\n                    \"%s: a function with only '(...)' as argument\"\n                    \" is not correct C\" % (funcname or 'in expression'))\n        args = [self._as_func_arg(*self._get_type_and_quals(argdeclnode.type))\n                for argdeclnode in params]\n        if not ellipsis and args == [model.void_type]:\n            args = []\n        result, quals = self._get_type_and_quals(typenode.type)\n        # the 'quals' on the result type are ignored.  HACK: we absure them\n        # to detect __stdcall functions: we textually replace \"__stdcall\"\n        # with \"volatile volatile const\" above.\n        abi = None\n        if hasattr(typenode.type, 'quals'): # else, probable syntax error anyway\n            if typenode.type.quals[-3:] == ['volatile', 'volatile', 'const']:\n                abi = '__stdcall'\n        return model.RawFunctionType(tuple(args), result, ellipsis, abi)\n\n    def _as_func_arg(self, type, quals):\n        if isinstance(type, model.ArrayType):\n            return model.PointerType(type.item, quals)\n        elif isinstance(type, model.RawFunctionType):\n            return type.as_function_pointer()\n        else:\n            return type\n\n    def _get_struct_union_enum_type(self, kind, type, name=None, nested=False):\n        # First, a level of caching on the exact 'type' node of the AST.\n        # This is obscure, but needed because pycparser \"unrolls\" declarations\n        # such as \"typedef struct { } foo_t, *foo_p\" and we end up with\n        # an AST that is not a tree, but a DAG, with the \"type\" node of the\n        # two branches foo_t and foo_p of the trees being the same node.\n        # It's a bit silly but detecting \"DAG-ness\" in the AST tree seems\n        # to be the only way to distinguish this case from two independent\n        # structs.  See test_struct_with_two_usages.\n        try:\n            return self._structnode2type[type]\n        except KeyError:\n            pass\n        #\n        # Note that this must handle parsing \"struct foo\" any number of\n        # times and always return the same StructType object.  Additionally,\n        # one of these times (not necessarily the first), the fields of\n        # the struct can be specified with \"struct foo { ...fields... }\".\n        # If no name is given, then we have to create a new anonymous struct\n        # with no caching; in this case, the fields are either specified\n        # right now or never.\n        #\n        force_name = name\n        name = type.name\n        #\n        # get the type or create it if needed\n        if name is None:\n            # 'force_name' is used to guess a more readable name for\n            # anonymous structs, for the common case \"typedef struct { } foo\".\n            if force_name is not None:\n                explicit_name = '$%s' % force_name\n            else:\n                self._anonymous_counter += 1\n                explicit_name = '$%d' % self._anonymous_counter\n            tp = None\n        else:\n            explicit_name = name\n            key = '%s %s' % (kind, name)\n            tp, _ = self._declarations.get(key, (None, None))\n        #\n        if tp is None:\n            if kind == 'struct':\n                tp = model.StructType(explicit_name, None, None, None)\n            elif kind == 'union':\n                tp = model.UnionType(explicit_name, None, None, None)\n            elif kind == 'enum':\n                if explicit_name == '__dotdotdot__':\n                    raise CDefError(\"Enums cannot be declared with ...\")\n                tp = self._build_enum_type(explicit_name, type.values)\n            else:\n                raise AssertionError(\"kind = %r\" % (kind,))\n            if name is not None:\n                self._declare(key, tp)\n        else:\n            if kind == 'enum' and type.values is not None:\n                raise NotImplementedError(\n                    \"enum %s: the '{}' declaration should appear on the first \"\n                    \"time the enum is mentioned, not later\" % explicit_name)\n        if not tp.forcename:\n            tp.force_the_name(force_name)\n        if tp.forcename and '$' in tp.name:\n            self._declare('anonymous %s' % tp.forcename, tp)\n        #\n        self._structnode2type[type] = tp\n        #\n        # enums: done here\n        if kind == 'enum':\n            return tp\n        #\n        # is there a 'type.decls'?  If yes, then this is the place in the\n        # C sources that declare the fields.  If no, then just return the\n        # existing type, possibly still incomplete.\n        if type.decls is None:\n            return tp\n        #\n        if tp.fldnames is not None:\n            raise CDefError(\"duplicate declaration of struct %s\" % name)\n        fldnames = []\n        fldtypes = []\n        fldbitsize = []\n        fldquals = []\n        for decl in type.decls:\n            if (isinstance(decl.type, pycparser.c_ast.IdentifierType) and\n                    ''.join(decl.type.names) == '__dotdotdot__'):\n                # XXX pycparser is inconsistent: 'names' should be a list\n                # of strings, but is sometimes just one string.  Use\n                # str.join() as a way to cope with both.\n                self._make_partial(tp, nested)\n                continue\n            if decl.bitsize is None:\n                bitsize = -1\n            else:\n                bitsize = self._parse_constant(decl.bitsize)\n            self._partial_length = False\n            type, fqual = self._get_type_and_quals(decl.type,\n                                                   partial_length_ok=True)\n            if self._partial_length:\n                self._make_partial(tp, nested)\n            if isinstance(type, model.StructType) and type.partial:\n                self._make_partial(tp, nested)\n            fldnames.append(decl.name or '')\n            fldtypes.append(type)\n            fldbitsize.append(bitsize)\n            fldquals.append(fqual)\n        tp.fldnames = tuple(fldnames)\n        tp.fldtypes = tuple(fldtypes)\n        tp.fldbitsize = tuple(fldbitsize)\n        tp.fldquals = tuple(fldquals)\n        if fldbitsize != [-1] * len(fldbitsize):\n            if isinstance(tp, model.StructType) and tp.partial:\n                raise NotImplementedError(\"%s: using both bitfields and '...;'\"\n                                          % (tp,))\n        tp.packed = self._options.get('packed')\n        if tp.completed:    # must be re-completed: it is not opaque any more\n            tp.completed = 0\n            self._recomplete.append(tp)\n        return tp\n\n    def _make_partial(self, tp, nested):\n        if not isinstance(tp, model.StructOrUnion):\n            raise CDefError(\"%s cannot be partial\" % (tp,))\n        if not tp.has_c_name() and not nested:\n            raise NotImplementedError(\"%s is partial but has no C name\" %(tp,))\n        tp.partial = True\n\n    def _parse_constant(self, exprnode, partial_length_ok=False):\n        # for now, limited to expressions that are an immediate number\n        # or positive/negative number\n        if isinstance(exprnode, pycparser.c_ast.Constant):\n            s = exprnode.value\n            if '0' <= s[0] <= '9':\n                s = s.rstrip('uUlL')\n                try:\n                    if s.startswith('0'):\n                        return int(s, 8)\n                    else:\n                        return int(s, 10)\n                except ValueError:\n                    if len(s) > 1:\n                        if s.lower()[0:2] == '0x':\n                            return int(s, 16)\n                        elif s.lower()[0:2] == '0b':\n                            return int(s, 2)\n                raise CDefError(\"invalid constant %r\" % (s,))\n            elif s[0] == \"'\" and s[-1] == \"'\" and (\n                    len(s) == 3 or (len(s) == 4 and s[1] == \"\\\\\")):\n                return ord(s[-2])\n            else:\n                raise CDefError(\"invalid constant %r\" % (s,))\n        #\n        if (isinstance(exprnode, pycparser.c_ast.UnaryOp) and\n                exprnode.op == '+'):\n            return self._parse_constant(exprnode.expr)\n        #\n        if (isinstance(exprnode, pycparser.c_ast.UnaryOp) and\n                exprnode.op == '-'):\n            return -self._parse_constant(exprnode.expr)\n        # load previously defined int constant\n        if (isinstance(exprnode, pycparser.c_ast.ID) and\n                exprnode.name in self._int_constants):\n            return self._int_constants[exprnode.name]\n        #\n        if (isinstance(exprnode, pycparser.c_ast.ID) and\n                    exprnode.name == '__dotdotdotarray__'):\n            if partial_length_ok:\n                self._partial_length = True\n                return '...'\n            raise FFIError(\":%d: unsupported '[...]' here, cannot derive \"\n                           \"the actual array length in this context\"\n                           % exprnode.coord.line)\n        #\n        if isinstance(exprnode, pycparser.c_ast.BinaryOp):\n            left = self._parse_constant(exprnode.left)\n            right = self._parse_constant(exprnode.right)\n            if exprnode.op == '+':\n                return left + right\n            elif exprnode.op == '-':\n                return left - right\n            elif exprnode.op == '*':\n                return left * right\n            elif exprnode.op == '/':\n                return self._c_div(left, right)\n            elif exprnode.op == '%':\n                return left - self._c_div(left, right) * right\n            elif exprnode.op == '<<':\n                return left << right\n            elif exprnode.op == '>>':\n                return left >> right\n            elif exprnode.op == '&':\n                return left & right\n            elif exprnode.op == '|':\n                return left | right\n            elif exprnode.op == '^':\n                return left ^ right\n        #\n        raise FFIError(\":%d: unsupported expression: expected a \"\n                       \"simple numeric constant\" % exprnode.coord.line)\n\n    def _c_div(self, a, b):\n        result = a // b\n        if ((a < 0) ^ (b < 0)) and (a % b) != 0:\n            result += 1\n        return result\n\n    def _build_enum_type(self, explicit_name, decls):\n        if decls is not None:\n            partial = False\n            enumerators = []\n            enumvalues = []\n            nextenumvalue = 0\n            for enum in decls.enumerators:\n                if _r_enum_dotdotdot.match(enum.name):\n                    partial = True\n                    continue\n                if enum.value is not None:\n                    nextenumvalue = self._parse_constant(enum.value)\n                enumerators.append(enum.name)\n                enumvalues.append(nextenumvalue)\n                self._add_constants(enum.name, nextenumvalue)\n                nextenumvalue += 1\n            enumerators = tuple(enumerators)\n            enumvalues = tuple(enumvalues)\n            tp = model.EnumType(explicit_name, enumerators, enumvalues)\n            tp.partial = partial\n        else:   # opaque enum\n            tp = model.EnumType(explicit_name, (), ())\n        return tp\n\n    def include(self, other):\n        for name, (tp, quals) in other._declarations.items():\n            if name.startswith('anonymous $enum_$'):\n                continue   # fix for test_anonymous_enum_include\n            kind = name.split(' ', 1)[0]\n            if kind in ('struct', 'union', 'enum', 'anonymous', 'typedef'):\n                self._declare(name, tp, included=True, quals=quals)\n        for k, v in other._int_constants.items():\n            self._add_constants(k, v)\n\n    def _get_unknown_type(self, decl):\n        typenames = decl.type.type.names\n        if typenames == ['__dotdotdot__']:\n            return model.unknown_type(decl.name)\n\n        if typenames == ['__dotdotdotint__']:\n            if self._uses_new_feature is None:\n                self._uses_new_feature = \"'typedef int... %s'\" % decl.name\n            return model.UnknownIntegerType(decl.name)\n\n        if typenames == ['__dotdotdotfloat__']:\n            # note: not for 'long double' so far\n            if self._uses_new_feature is None:\n                self._uses_new_feature = \"'typedef float... %s'\" % decl.name\n            return model.UnknownFloatType(decl.name)\n\n        raise FFIError(':%d: unsupported usage of \"...\" in typedef'\n                       % decl.coord.line)\n\n    def _get_unknown_ptr_type(self, decl):\n        if decl.type.type.type.names == ['__dotdotdot__']:\n            return model.unknown_ptr_type(decl.name)\n        raise FFIError(':%d: unsupported usage of \"...\" in typedef'\n                       % decl.coord.line)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/error.py",
    "content": "\nclass FFIError(Exception):\n    __module__ = 'cffi'\n\nclass CDefError(Exception):\n    __module__ = 'cffi'\n    def __str__(self):\n        try:\n            current_decl = self.args[1]\n            filename = current_decl.coord.file\n            linenum = current_decl.coord.line\n            prefix = '%s:%d: ' % (filename, linenum)\n        except (AttributeError, TypeError, IndexError):\n            prefix = ''\n        return '%s%s' % (prefix, self.args[0])\n\nclass VerificationError(Exception):\n    \"\"\" An error raised when verification fails\n    \"\"\"\n    __module__ = 'cffi'\n\nclass VerificationMissing(Exception):\n    \"\"\" An error raised when incomplete structures are passed into\n    cdef, but no verification has been done\n    \"\"\"\n    __module__ = 'cffi'\n\nclass PkgConfigError(Exception):\n    \"\"\" An error raised for missing modules in pkg-config\n    \"\"\"\n    __module__ = 'cffi'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/ffiplatform.py",
    "content": "import sys, os\nfrom .error import VerificationError\n\n\nLIST_OF_FILE_NAMES = ['sources', 'include_dirs', 'library_dirs',\n                      'extra_objects', 'depends']\n\ndef get_extension(srcfilename, modname, sources=(), **kwds):\n    _hack_at_distutils()\n    from distutils.core import Extension\n    allsources = [srcfilename]\n    for src in sources:\n        allsources.append(os.path.normpath(src))\n    return Extension(name=modname, sources=allsources, **kwds)\n\ndef compile(tmpdir, ext, compiler_verbose=0, debug=None):\n    \"\"\"Compile a C extension module using distutils.\"\"\"\n\n    _hack_at_distutils()\n    saved_environ = os.environ.copy()\n    try:\n        outputfilename = _build(tmpdir, ext, compiler_verbose, debug)\n        outputfilename = os.path.abspath(outputfilename)\n    finally:\n        # workaround for a distutils bugs where some env vars can\n        # become longer and longer every time it is used\n        for key, value in saved_environ.items():\n            if os.environ.get(key) != value:\n                os.environ[key] = value\n    return outputfilename\n\ndef _build(tmpdir, ext, compiler_verbose=0, debug=None):\n    # XXX compact but horrible :-(\n    from distutils.core import Distribution\n    import distutils.errors, distutils.log\n    #\n    dist = Distribution({'ext_modules': [ext]})\n    dist.parse_config_files()\n    options = dist.get_option_dict('build_ext')\n    if debug is None:\n        debug = sys.flags.debug\n    options['debug'] = ('ffiplatform', debug)\n    options['force'] = ('ffiplatform', True)\n    options['build_lib'] = ('ffiplatform', tmpdir)\n    options['build_temp'] = ('ffiplatform', tmpdir)\n    #\n    try:\n        old_level = distutils.log.set_threshold(0) or 0\n        try:\n            distutils.log.set_verbosity(compiler_verbose)\n            dist.run_command('build_ext')\n            cmd_obj = dist.get_command_obj('build_ext')\n            [soname] = cmd_obj.get_outputs()\n        finally:\n            distutils.log.set_threshold(old_level)\n    except (distutils.errors.CompileError,\n            distutils.errors.LinkError) as e:\n        raise VerificationError('%s: %s' % (e.__class__.__name__, e))\n    #\n    return soname\n\ntry:\n    from os.path import samefile\nexcept ImportError:\n    def samefile(f1, f2):\n        return os.path.abspath(f1) == os.path.abspath(f2)\n\ndef maybe_relative_path(path):\n    if not os.path.isabs(path):\n        return path      # already relative\n    dir = path\n    names = []\n    while True:\n        prevdir = dir\n        dir, name = os.path.split(prevdir)\n        if dir == prevdir or not dir:\n            return path     # failed to make it relative\n        names.append(name)\n        try:\n            if samefile(dir, os.curdir):\n                names.reverse()\n                return os.path.join(*names)\n        except OSError:\n            pass\n\n# ____________________________________________________________\n\ntry:\n    int_or_long = (int, long)\n    import cStringIO\nexcept NameError:\n    int_or_long = int      # Python 3\n    import io as cStringIO\n\ndef _flatten(x, f):\n    if isinstance(x, str):\n        f.write('%ds%s' % (len(x), x))\n    elif isinstance(x, dict):\n        keys = sorted(x.keys())\n        f.write('%dd' % len(keys))\n        for key in keys:\n            _flatten(key, f)\n            _flatten(x[key], f)\n    elif isinstance(x, (list, tuple)):\n        f.write('%dl' % len(x))\n        for value in x:\n            _flatten(value, f)\n    elif isinstance(x, int_or_long):\n        f.write('%di' % (x,))\n    else:\n        raise TypeError(\n            \"the keywords to verify() contains unsupported object %r\" % (x,))\n\ndef flatten(x):\n    f = cStringIO.StringIO()\n    _flatten(x, f)\n    return f.getvalue()\n\ndef _hack_at_distutils():\n    # Windows-only workaround for some configurations: see\n    # https://bugs.python.org/issue23246 (Python 2.7 with \n    # a specific MS compiler suite download)\n    if sys.platform == \"win32\":\n        try:\n            import setuptools    # for side-effects, patches distutils\n        except ImportError:\n            pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/lock.py",
    "content": "import sys\n\nif sys.version_info < (3,):\n    try:\n        from thread import allocate_lock\n    except ImportError:\n        from dummy_thread import allocate_lock\nelse:\n    try:\n        from _thread import allocate_lock\n    except ImportError:\n        from _dummy_thread import allocate_lock\n\n\n##import sys\n##l1 = allocate_lock\n\n##class allocate_lock(object):\n##    def __init__(self):\n##        self._real = l1()\n##    def __enter__(self):\n##        for i in range(4, 0, -1):\n##            print sys._getframe(i).f_code\n##        print\n##        return self._real.__enter__()\n##    def __exit__(self, *args):\n##        return self._real.__exit__(*args)\n##    def acquire(self, f):\n##        assert f is False\n##        return self._real.acquire(f)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/model.py",
    "content": "import types\nimport weakref\n\nfrom .lock import allocate_lock\nfrom .error import CDefError, VerificationError, VerificationMissing\n\n# type qualifiers\nQ_CONST    = 0x01\nQ_RESTRICT = 0x02\nQ_VOLATILE = 0x04\n\ndef qualify(quals, replace_with):\n    if quals & Q_CONST:\n        replace_with = ' const ' + replace_with.lstrip()\n    if quals & Q_VOLATILE:\n        replace_with = ' volatile ' + replace_with.lstrip()\n    if quals & Q_RESTRICT:\n        # It seems that __restrict is supported by gcc and msvc.\n        # If you hit some different compiler, add a #define in\n        # _cffi_include.h for it (and in its copies, documented there)\n        replace_with = ' __restrict ' + replace_with.lstrip()\n    return replace_with\n\n\nclass BaseTypeByIdentity(object):\n    is_array_type = False\n    is_raw_function = False\n\n    def get_c_name(self, replace_with='', context='a C file', quals=0):\n        result = self.c_name_with_marker\n        assert result.count('&') == 1\n        # some logic duplication with ffi.getctype()... :-(\n        replace_with = replace_with.strip()\n        if replace_with:\n            if replace_with.startswith('*') and '&[' in result:\n                replace_with = '(%s)' % replace_with\n            elif not replace_with[0] in '[(':\n                replace_with = ' ' + replace_with\n        replace_with = qualify(quals, replace_with)\n        result = result.replace('&', replace_with)\n        if '$' in result:\n            raise VerificationError(\n                \"cannot generate '%s' in %s: unknown type name\"\n                % (self._get_c_name(), context))\n        return result\n\n    def _get_c_name(self):\n        return self.c_name_with_marker.replace('&', '')\n\n    def has_c_name(self):\n        return '$' not in self._get_c_name()\n\n    def is_integer_type(self):\n        return False\n\n    def get_cached_btype(self, ffi, finishlist, can_delay=False):\n        try:\n            BType = ffi._cached_btypes[self]\n        except KeyError:\n            BType = self.build_backend_type(ffi, finishlist)\n            BType2 = ffi._cached_btypes.setdefault(self, BType)\n            assert BType2 is BType\n        return BType\n\n    def __repr__(self):\n        return '<%s>' % (self._get_c_name(),)\n\n    def _get_items(self):\n        return [(name, getattr(self, name)) for name in self._attrs_]\n\n\nclass BaseType(BaseTypeByIdentity):\n\n    def __eq__(self, other):\n        return (self.__class__ == other.__class__ and\n                self._get_items() == other._get_items())\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((self.__class__, tuple(self._get_items())))\n\n\nclass VoidType(BaseType):\n    _attrs_ = ()\n\n    def __init__(self):\n        self.c_name_with_marker = 'void&'\n\n    def build_backend_type(self, ffi, finishlist):\n        return global_cache(self, ffi, 'new_void_type')\n\nvoid_type = VoidType()\n\n\nclass BasePrimitiveType(BaseType):\n    def is_complex_type(self):\n        return False\n\n\nclass PrimitiveType(BasePrimitiveType):\n    _attrs_ = ('name',)\n\n    ALL_PRIMITIVE_TYPES = {\n        'char':               'c',\n        'short':              'i',\n        'int':                'i',\n        'long':               'i',\n        'long long':          'i',\n        'signed char':        'i',\n        'unsigned char':      'i',\n        'unsigned short':     'i',\n        'unsigned int':       'i',\n        'unsigned long':      'i',\n        'unsigned long long': 'i',\n        'float':              'f',\n        'double':             'f',\n        'long double':        'f',\n        'float _Complex':     'j',\n        'double _Complex':    'j',\n        '_Bool':              'i',\n        # the following types are not primitive in the C sense\n        'wchar_t':            'c',\n        'char16_t':           'c',\n        'char32_t':           'c',\n        'int8_t':             'i',\n        'uint8_t':            'i',\n        'int16_t':            'i',\n        'uint16_t':           'i',\n        'int32_t':            'i',\n        'uint32_t':           'i',\n        'int64_t':            'i',\n        'uint64_t':           'i',\n        'int_least8_t':       'i',\n        'uint_least8_t':      'i',\n        'int_least16_t':      'i',\n        'uint_least16_t':     'i',\n        'int_least32_t':      'i',\n        'uint_least32_t':     'i',\n        'int_least64_t':      'i',\n        'uint_least64_t':     'i',\n        'int_fast8_t':        'i',\n        'uint_fast8_t':       'i',\n        'int_fast16_t':       'i',\n        'uint_fast16_t':      'i',\n        'int_fast32_t':       'i',\n        'uint_fast32_t':      'i',\n        'int_fast64_t':       'i',\n        'uint_fast64_t':      'i',\n        'intptr_t':           'i',\n        'uintptr_t':          'i',\n        'intmax_t':           'i',\n        'uintmax_t':          'i',\n        'ptrdiff_t':          'i',\n        'size_t':             'i',\n        'ssize_t':            'i',\n        }\n\n    def __init__(self, name):\n        assert name in self.ALL_PRIMITIVE_TYPES\n        self.name = name\n        self.c_name_with_marker = name + '&'\n\n    def is_char_type(self):\n        return self.ALL_PRIMITIVE_TYPES[self.name] == 'c'\n    def is_integer_type(self):\n        return self.ALL_PRIMITIVE_TYPES[self.name] == 'i'\n    def is_float_type(self):\n        return self.ALL_PRIMITIVE_TYPES[self.name] == 'f'\n    def is_complex_type(self):\n        return self.ALL_PRIMITIVE_TYPES[self.name] == 'j'\n\n    def build_backend_type(self, ffi, finishlist):\n        return global_cache(self, ffi, 'new_primitive_type', self.name)\n\n\nclass UnknownIntegerType(BasePrimitiveType):\n    _attrs_ = ('name',)\n\n    def __init__(self, name):\n        self.name = name\n        self.c_name_with_marker = name + '&'\n\n    def is_integer_type(self):\n        return True\n\n    def build_backend_type(self, ffi, finishlist):\n        raise NotImplementedError(\"integer type '%s' can only be used after \"\n                                  \"compilation\" % self.name)\n\nclass UnknownFloatType(BasePrimitiveType):\n    _attrs_ = ('name', )\n\n    def __init__(self, name):\n        self.name = name\n        self.c_name_with_marker = name + '&'\n\n    def build_backend_type(self, ffi, finishlist):\n        raise NotImplementedError(\"float type '%s' can only be used after \"\n                                  \"compilation\" % self.name)\n\n\nclass BaseFunctionType(BaseType):\n    _attrs_ = ('args', 'result', 'ellipsis', 'abi')\n\n    def __init__(self, args, result, ellipsis, abi=None):\n        self.args = args\n        self.result = result\n        self.ellipsis = ellipsis\n        self.abi = abi\n        #\n        reprargs = [arg._get_c_name() for arg in self.args]\n        if self.ellipsis:\n            reprargs.append('...')\n        reprargs = reprargs or ['void']\n        replace_with = self._base_pattern % (', '.join(reprargs),)\n        if abi is not None:\n            replace_with = replace_with[:1] + abi + ' ' + replace_with[1:]\n        self.c_name_with_marker = (\n            self.result.c_name_with_marker.replace('&', replace_with))\n\n\nclass RawFunctionType(BaseFunctionType):\n    # Corresponds to a C type like 'int(int)', which is the C type of\n    # a function, but not a pointer-to-function.  The backend has no\n    # notion of such a type; it's used temporarily by parsing.\n    _base_pattern = '(&)(%s)'\n    is_raw_function = True\n\n    def build_backend_type(self, ffi, finishlist):\n        raise CDefError(\"cannot render the type %r: it is a function \"\n                        \"type, not a pointer-to-function type\" % (self,))\n\n    def as_function_pointer(self):\n        return FunctionPtrType(self.args, self.result, self.ellipsis, self.abi)\n\n\nclass FunctionPtrType(BaseFunctionType):\n    _base_pattern = '(*&)(%s)'\n\n    def build_backend_type(self, ffi, finishlist):\n        result = self.result.get_cached_btype(ffi, finishlist)\n        args = []\n        for tp in self.args:\n            args.append(tp.get_cached_btype(ffi, finishlist))\n        abi_args = ()\n        if self.abi == \"__stdcall\":\n            if not self.ellipsis:    # __stdcall ignored for variadic funcs\n                try:\n                    abi_args = (ffi._backend.FFI_STDCALL,)\n                except AttributeError:\n                    pass\n        return global_cache(self, ffi, 'new_function_type',\n                            tuple(args), result, self.ellipsis, *abi_args)\n\n    def as_raw_function(self):\n        return RawFunctionType(self.args, self.result, self.ellipsis, self.abi)\n\n\nclass PointerType(BaseType):\n    _attrs_ = ('totype', 'quals')\n\n    def __init__(self, totype, quals=0):\n        self.totype = totype\n        self.quals = quals\n        extra = qualify(quals, \" *&\")\n        if totype.is_array_type:\n            extra = \"(%s)\" % (extra.lstrip(),)\n        self.c_name_with_marker = totype.c_name_with_marker.replace('&', extra)\n\n    def build_backend_type(self, ffi, finishlist):\n        BItem = self.totype.get_cached_btype(ffi, finishlist, can_delay=True)\n        return global_cache(self, ffi, 'new_pointer_type', BItem)\n\nvoidp_type = PointerType(void_type)\n\ndef ConstPointerType(totype):\n    return PointerType(totype, Q_CONST)\n\nconst_voidp_type = ConstPointerType(void_type)\n\n\nclass NamedPointerType(PointerType):\n    _attrs_ = ('totype', 'name')\n\n    def __init__(self, totype, name, quals=0):\n        PointerType.__init__(self, totype, quals)\n        self.name = name\n        self.c_name_with_marker = name + '&'\n\n\nclass ArrayType(BaseType):\n    _attrs_ = ('item', 'length')\n    is_array_type = True\n\n    def __init__(self, item, length):\n        self.item = item\n        self.length = length\n        #\n        if length is None:\n            brackets = '&[]'\n        elif length == '...':\n            brackets = '&[/*...*/]'\n        else:\n            brackets = '&[%s]' % length\n        self.c_name_with_marker = (\n            self.item.c_name_with_marker.replace('&', brackets))\n\n    def resolve_length(self, newlength):\n        return ArrayType(self.item, newlength)\n\n    def build_backend_type(self, ffi, finishlist):\n        if self.length == '...':\n            raise CDefError(\"cannot render the type %r: unknown length\" %\n                            (self,))\n        self.item.get_cached_btype(ffi, finishlist)   # force the item BType\n        BPtrItem = PointerType(self.item).get_cached_btype(ffi, finishlist)\n        return global_cache(self, ffi, 'new_array_type', BPtrItem, self.length)\n\nchar_array_type = ArrayType(PrimitiveType('char'), None)\n\n\nclass StructOrUnionOrEnum(BaseTypeByIdentity):\n    _attrs_ = ('name',)\n    forcename = None\n\n    def build_c_name_with_marker(self):\n        name = self.forcename or '%s %s' % (self.kind, self.name)\n        self.c_name_with_marker = name + '&'\n\n    def force_the_name(self, forcename):\n        self.forcename = forcename\n        self.build_c_name_with_marker()\n\n    def get_official_name(self):\n        assert self.c_name_with_marker.endswith('&')\n        return self.c_name_with_marker[:-1]\n\n\nclass StructOrUnion(StructOrUnionOrEnum):\n    fixedlayout = None\n    completed = 0\n    partial = False\n    packed = 0\n\n    def __init__(self, name, fldnames, fldtypes, fldbitsize, fldquals=None):\n        self.name = name\n        self.fldnames = fldnames\n        self.fldtypes = fldtypes\n        self.fldbitsize = fldbitsize\n        self.fldquals = fldquals\n        self.build_c_name_with_marker()\n\n    def anonymous_struct_fields(self):\n        if self.fldtypes is not None:\n            for name, type in zip(self.fldnames, self.fldtypes):\n                if name == '' and isinstance(type, StructOrUnion):\n                    yield type\n\n    def enumfields(self, expand_anonymous_struct_union=True):\n        fldquals = self.fldquals\n        if fldquals is None:\n            fldquals = (0,) * len(self.fldnames)\n        for name, type, bitsize, quals in zip(self.fldnames, self.fldtypes,\n                                              self.fldbitsize, fldquals):\n            if (name == '' and isinstance(type, StructOrUnion)\n                    and expand_anonymous_struct_union):\n                # nested anonymous struct/union\n                for result in type.enumfields():\n                    yield result\n            else:\n                yield (name, type, bitsize, quals)\n\n    def force_flatten(self):\n        # force the struct or union to have a declaration that lists\n        # directly all fields returned by enumfields(), flattening\n        # nested anonymous structs/unions.\n        names = []\n        types = []\n        bitsizes = []\n        fldquals = []\n        for name, type, bitsize, quals in self.enumfields():\n            names.append(name)\n            types.append(type)\n            bitsizes.append(bitsize)\n            fldquals.append(quals)\n        self.fldnames = tuple(names)\n        self.fldtypes = tuple(types)\n        self.fldbitsize = tuple(bitsizes)\n        self.fldquals = tuple(fldquals)\n\n    def get_cached_btype(self, ffi, finishlist, can_delay=False):\n        BType = StructOrUnionOrEnum.get_cached_btype(self, ffi, finishlist,\n                                                     can_delay)\n        if not can_delay:\n            self.finish_backend_type(ffi, finishlist)\n        return BType\n\n    def finish_backend_type(self, ffi, finishlist):\n        if self.completed:\n            if self.completed != 2:\n                raise NotImplementedError(\"recursive structure declaration \"\n                                          \"for '%s'\" % (self.name,))\n            return\n        BType = ffi._cached_btypes[self]\n        #\n        self.completed = 1\n        #\n        if self.fldtypes is None:\n            pass    # not completing it: it's an opaque struct\n            #\n        elif self.fixedlayout is None:\n            fldtypes = [tp.get_cached_btype(ffi, finishlist)\n                        for tp in self.fldtypes]\n            lst = list(zip(self.fldnames, fldtypes, self.fldbitsize))\n            extra_flags = ()\n            if self.packed:\n                if self.packed == 1:\n                    extra_flags = (8,)    # SF_PACKED\n                else:\n                    extra_flags = (0, self.packed)\n            ffi._backend.complete_struct_or_union(BType, lst, self,\n                                                  -1, -1, *extra_flags)\n            #\n        else:\n            fldtypes = []\n            fieldofs, fieldsize, totalsize, totalalignment = self.fixedlayout\n            for i in range(len(self.fldnames)):\n                fsize = fieldsize[i]\n                ftype = self.fldtypes[i]\n                #\n                if isinstance(ftype, ArrayType) and ftype.length == '...':\n                    # fix the length to match the total size\n                    BItemType = ftype.item.get_cached_btype(ffi, finishlist)\n                    nlen, nrest = divmod(fsize, ffi.sizeof(BItemType))\n                    if nrest != 0:\n                        self._verification_error(\n                            \"field '%s.%s' has a bogus size?\" % (\n                            self.name, self.fldnames[i] or '{}'))\n                    ftype = ftype.resolve_length(nlen)\n                    self.fldtypes = (self.fldtypes[:i] + (ftype,) +\n                                     self.fldtypes[i+1:])\n                #\n                BFieldType = ftype.get_cached_btype(ffi, finishlist)\n                if isinstance(ftype, ArrayType) and ftype.length is None:\n                    assert fsize == 0\n                else:\n                    bitemsize = ffi.sizeof(BFieldType)\n                    if bitemsize != fsize:\n                        self._verification_error(\n                            \"field '%s.%s' is declared as %d bytes, but is \"\n                            \"really %d bytes\" % (self.name,\n                                                 self.fldnames[i] or '{}',\n                                                 bitemsize, fsize))\n                fldtypes.append(BFieldType)\n            #\n            lst = list(zip(self.fldnames, fldtypes, self.fldbitsize, fieldofs))\n            ffi._backend.complete_struct_or_union(BType, lst, self,\n                                                  totalsize, totalalignment)\n        self.completed = 2\n\n    def _verification_error(self, msg):\n        raise VerificationError(msg)\n\n    def check_not_partial(self):\n        if self.partial and self.fixedlayout is None:\n            raise VerificationMissing(self._get_c_name())\n\n    def build_backend_type(self, ffi, finishlist):\n        self.check_not_partial()\n        finishlist.append(self)\n        #\n        return global_cache(self, ffi, 'new_%s_type' % self.kind,\n                            self.get_official_name(), key=self)\n\n\nclass StructType(StructOrUnion):\n    kind = 'struct'\n\n\nclass UnionType(StructOrUnion):\n    kind = 'union'\n\n\nclass EnumType(StructOrUnionOrEnum):\n    kind = 'enum'\n    partial = False\n    partial_resolved = False\n\n    def __init__(self, name, enumerators, enumvalues, baseinttype=None):\n        self.name = name\n        self.enumerators = enumerators\n        self.enumvalues = enumvalues\n        self.baseinttype = baseinttype\n        self.build_c_name_with_marker()\n\n    def force_the_name(self, forcename):\n        StructOrUnionOrEnum.force_the_name(self, forcename)\n        if self.forcename is None:\n            name = self.get_official_name()\n            self.forcename = '$' + name.replace(' ', '_')\n\n    def check_not_partial(self):\n        if self.partial and not self.partial_resolved:\n            raise VerificationMissing(self._get_c_name())\n\n    def build_backend_type(self, ffi, finishlist):\n        self.check_not_partial()\n        base_btype = self.build_baseinttype(ffi, finishlist)\n        return global_cache(self, ffi, 'new_enum_type',\n                            self.get_official_name(),\n                            self.enumerators, self.enumvalues,\n                            base_btype, key=self)\n\n    def build_baseinttype(self, ffi, finishlist):\n        if self.baseinttype is not None:\n            return self.baseinttype.get_cached_btype(ffi, finishlist)\n        #\n        if self.enumvalues:\n            smallest_value = min(self.enumvalues)\n            largest_value = max(self.enumvalues)\n        else:\n            import warnings\n            try:\n                # XXX!  The goal is to ensure that the warnings.warn()\n                # will not suppress the warning.  We want to get it\n                # several times if we reach this point several times.\n                __warningregistry__.clear()\n            except NameError:\n                pass\n            warnings.warn(\"%r has no values explicitly defined; \"\n                          \"guessing that it is equivalent to 'unsigned int'\"\n                          % self._get_c_name())\n            smallest_value = largest_value = 0\n        if smallest_value < 0:   # needs a signed type\n            sign = 1\n            candidate1 = PrimitiveType(\"int\")\n            candidate2 = PrimitiveType(\"long\")\n        else:\n            sign = 0\n            candidate1 = PrimitiveType(\"unsigned int\")\n            candidate2 = PrimitiveType(\"unsigned long\")\n        btype1 = candidate1.get_cached_btype(ffi, finishlist)\n        btype2 = candidate2.get_cached_btype(ffi, finishlist)\n        size1 = ffi.sizeof(btype1)\n        size2 = ffi.sizeof(btype2)\n        if (smallest_value >= ((-1) << (8*size1-1)) and\n            largest_value < (1 << (8*size1-sign))):\n            return btype1\n        if (smallest_value >= ((-1) << (8*size2-1)) and\n            largest_value < (1 << (8*size2-sign))):\n            return btype2\n        raise CDefError(\"%s values don't all fit into either 'long' \"\n                        \"or 'unsigned long'\" % self._get_c_name())\n\ndef unknown_type(name, structname=None):\n    if structname is None:\n        structname = '$%s' % name\n    tp = StructType(structname, None, None, None)\n    tp.force_the_name(name)\n    tp.origin = \"unknown_type\"\n    return tp\n\ndef unknown_ptr_type(name, structname=None):\n    if structname is None:\n        structname = '$$%s' % name\n    tp = StructType(structname, None, None, None)\n    return NamedPointerType(tp, name)\n\n\nglobal_lock = allocate_lock()\n_typecache_cffi_backend = weakref.WeakValueDictionary()\n\ndef get_typecache(backend):\n    # returns _typecache_cffi_backend if backend is the _cffi_backend\n    # module, or type(backend).__typecache if backend is an instance of\n    # CTypesBackend (or some FakeBackend class during tests)\n    if isinstance(backend, types.ModuleType):\n        return _typecache_cffi_backend\n    with global_lock:\n        if not hasattr(type(backend), '__typecache'):\n            type(backend).__typecache = weakref.WeakValueDictionary()\n        return type(backend).__typecache\n\ndef global_cache(srctype, ffi, funcname, *args, **kwds):\n    key = kwds.pop('key', (funcname, args))\n    assert not kwds\n    try:\n        return ffi._typecache[key]\n    except KeyError:\n        pass\n    try:\n        res = getattr(ffi._backend, funcname)(*args)\n    except NotImplementedError as e:\n        raise NotImplementedError(\"%s: %r: %s\" % (funcname, srctype, e))\n    # note that setdefault() on WeakValueDictionary is not atomic\n    # and contains a rare bug (http://bugs.python.org/issue19542);\n    # we have to use a lock and do it ourselves\n    cache = ffi._typecache\n    with global_lock:\n        res1 = cache.get(key)\n        if res1 is None:\n            cache[key] = res\n            return res\n        else:\n            return res1\n\ndef pointer_cache(ffi, BType):\n    return global_cache('?', ffi, 'new_pointer_type', BType)\n\ndef attach_exception_info(e, name):\n    if e.args and type(e.args[0]) is str:\n        e.args = ('%s: %s' % (name, e.args[0]),) + e.args[1:]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/parse_c_type.h",
    "content": "\n/* This part is from file 'cffi/parse_c_type.h'.  It is copied at the\n   beginning of C sources generated by CFFI's ffi.set_source(). */\n\ntypedef void *_cffi_opcode_t;\n\n#define _CFFI_OP(opcode, arg)   (_cffi_opcode_t)(opcode | (((uintptr_t)(arg)) << 8))\n#define _CFFI_GETOP(cffi_opcode)    ((unsigned char)(uintptr_t)cffi_opcode)\n#define _CFFI_GETARG(cffi_opcode)   (((intptr_t)cffi_opcode) >> 8)\n\n#define _CFFI_OP_PRIMITIVE       1\n#define _CFFI_OP_POINTER         3\n#define _CFFI_OP_ARRAY           5\n#define _CFFI_OP_OPEN_ARRAY      7\n#define _CFFI_OP_STRUCT_UNION    9\n#define _CFFI_OP_ENUM           11\n#define _CFFI_OP_FUNCTION       13\n#define _CFFI_OP_FUNCTION_END   15\n#define _CFFI_OP_NOOP           17\n#define _CFFI_OP_BITFIELD       19\n#define _CFFI_OP_TYPENAME       21\n#define _CFFI_OP_CPYTHON_BLTN_V 23   // varargs\n#define _CFFI_OP_CPYTHON_BLTN_N 25   // noargs\n#define _CFFI_OP_CPYTHON_BLTN_O 27   // O  (i.e. a single arg)\n#define _CFFI_OP_CONSTANT       29\n#define _CFFI_OP_CONSTANT_INT   31\n#define _CFFI_OP_GLOBAL_VAR     33\n#define _CFFI_OP_DLOPEN_FUNC    35\n#define _CFFI_OP_DLOPEN_CONST   37\n#define _CFFI_OP_GLOBAL_VAR_F   39\n#define _CFFI_OP_EXTERN_PYTHON  41\n\n#define _CFFI_PRIM_VOID          0\n#define _CFFI_PRIM_BOOL          1\n#define _CFFI_PRIM_CHAR          2\n#define _CFFI_PRIM_SCHAR         3\n#define _CFFI_PRIM_UCHAR         4\n#define _CFFI_PRIM_SHORT         5\n#define _CFFI_PRIM_USHORT        6\n#define _CFFI_PRIM_INT           7\n#define _CFFI_PRIM_UINT          8\n#define _CFFI_PRIM_LONG          9\n#define _CFFI_PRIM_ULONG        10\n#define _CFFI_PRIM_LONGLONG     11\n#define _CFFI_PRIM_ULONGLONG    12\n#define _CFFI_PRIM_FLOAT        13\n#define _CFFI_PRIM_DOUBLE       14\n#define _CFFI_PRIM_LONGDOUBLE   15\n\n#define _CFFI_PRIM_WCHAR        16\n#define _CFFI_PRIM_INT8         17\n#define _CFFI_PRIM_UINT8        18\n#define _CFFI_PRIM_INT16        19\n#define _CFFI_PRIM_UINT16       20\n#define _CFFI_PRIM_INT32        21\n#define _CFFI_PRIM_UINT32       22\n#define _CFFI_PRIM_INT64        23\n#define _CFFI_PRIM_UINT64       24\n#define _CFFI_PRIM_INTPTR       25\n#define _CFFI_PRIM_UINTPTR      26\n#define _CFFI_PRIM_PTRDIFF      27\n#define _CFFI_PRIM_SIZE         28\n#define _CFFI_PRIM_SSIZE        29\n#define _CFFI_PRIM_INT_LEAST8   30\n#define _CFFI_PRIM_UINT_LEAST8  31\n#define _CFFI_PRIM_INT_LEAST16  32\n#define _CFFI_PRIM_UINT_LEAST16 33\n#define _CFFI_PRIM_INT_LEAST32  34\n#define _CFFI_PRIM_UINT_LEAST32 35\n#define _CFFI_PRIM_INT_LEAST64  36\n#define _CFFI_PRIM_UINT_LEAST64 37\n#define _CFFI_PRIM_INT_FAST8    38\n#define _CFFI_PRIM_UINT_FAST8   39\n#define _CFFI_PRIM_INT_FAST16   40\n#define _CFFI_PRIM_UINT_FAST16  41\n#define _CFFI_PRIM_INT_FAST32   42\n#define _CFFI_PRIM_UINT_FAST32  43\n#define _CFFI_PRIM_INT_FAST64   44\n#define _CFFI_PRIM_UINT_FAST64  45\n#define _CFFI_PRIM_INTMAX       46\n#define _CFFI_PRIM_UINTMAX      47\n#define _CFFI_PRIM_FLOATCOMPLEX 48\n#define _CFFI_PRIM_DOUBLECOMPLEX 49\n#define _CFFI_PRIM_CHAR16       50\n#define _CFFI_PRIM_CHAR32       51\n\n#define _CFFI__NUM_PRIM         52\n#define _CFFI__UNKNOWN_PRIM           (-1)\n#define _CFFI__UNKNOWN_FLOAT_PRIM     (-2)\n#define _CFFI__UNKNOWN_LONG_DOUBLE    (-3)\n\n#define _CFFI__IO_FILE_STRUCT         (-1)\n\n\nstruct _cffi_global_s {\n    const char *name;\n    void *address;\n    _cffi_opcode_t type_op;\n    void *size_or_direct_fn;  // OP_GLOBAL_VAR: size, or 0 if unknown\n                              // OP_CPYTHON_BLTN_*: addr of direct function\n};\n\nstruct _cffi_getconst_s {\n    unsigned long long value;\n    const struct _cffi_type_context_s *ctx;\n    int gindex;\n};\n\nstruct _cffi_struct_union_s {\n    const char *name;\n    int type_index;          // -> _cffi_types, on a OP_STRUCT_UNION\n    int flags;               // _CFFI_F_* flags below\n    size_t size;\n    int alignment;\n    int first_field_index;   // -> _cffi_fields array\n    int num_fields;\n};\n#define _CFFI_F_UNION         0x01   // is a union, not a struct\n#define _CFFI_F_CHECK_FIELDS  0x02   // complain if fields are not in the\n                                     // \"standard layout\" or if some are missing\n#define _CFFI_F_PACKED        0x04   // for CHECK_FIELDS, assume a packed struct\n#define _CFFI_F_EXTERNAL      0x08   // in some other ffi.include()\n#define _CFFI_F_OPAQUE        0x10   // opaque\n\nstruct _cffi_field_s {\n    const char *name;\n    size_t field_offset;\n    size_t field_size;\n    _cffi_opcode_t field_type_op;\n};\n\nstruct _cffi_enum_s {\n    const char *name;\n    int type_index;          // -> _cffi_types, on a OP_ENUM\n    int type_prim;           // _CFFI_PRIM_xxx\n    const char *enumerators; // comma-delimited string\n};\n\nstruct _cffi_typename_s {\n    const char *name;\n    int type_index;   /* if opaque, points to a possibly artificial\n                         OP_STRUCT which is itself opaque */\n};\n\nstruct _cffi_type_context_s {\n    _cffi_opcode_t *types;\n    const struct _cffi_global_s *globals;\n    const struct _cffi_field_s *fields;\n    const struct _cffi_struct_union_s *struct_unions;\n    const struct _cffi_enum_s *enums;\n    const struct _cffi_typename_s *typenames;\n    int num_globals;\n    int num_struct_unions;\n    int num_enums;\n    int num_typenames;\n    const char *const *includes;\n    int num_types;\n    int flags;      /* future extension */\n};\n\nstruct _cffi_parse_info_s {\n    const struct _cffi_type_context_s *ctx;\n    _cffi_opcode_t *output;\n    unsigned int output_size;\n    size_t error_location;\n    const char *error_message;\n};\n\nstruct _cffi_externpy_s {\n    const char *name;\n    size_t size_of_result;\n    void *reserved1, *reserved2;\n};\n\n#ifdef _CFFI_INTERNAL\nstatic int parse_c_type(struct _cffi_parse_info_s *info, const char *input);\nstatic int search_in_globals(const struct _cffi_type_context_s *ctx,\n                             const char *search, size_t search_len);\nstatic int search_in_struct_unions(const struct _cffi_type_context_s *ctx,\n                                   const char *search, size_t search_len);\n#endif\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/pkgconfig.py",
    "content": "# pkg-config, https://www.freedesktop.org/wiki/Software/pkg-config/ integration for cffi\nimport sys, os, subprocess\n\nfrom .error import PkgConfigError\n\n\ndef merge_flags(cfg1, cfg2):\n    \"\"\"Merge values from cffi config flags cfg2 to cf1\n\n    Example:\n        merge_flags({\"libraries\": [\"one\"]}, {\"libraries\": [\"two\"]})\n        {\"libraries\": [\"one\", \"two\"]}\n    \"\"\"\n    for key, value in cfg2.items():\n        if key not in cfg1:\n            cfg1[key] = value\n        else:\n            if not isinstance(cfg1[key], list):\n                raise TypeError(\"cfg1[%r] should be a list of strings\" % (key,))\n            if not isinstance(value, list):\n                raise TypeError(\"cfg2[%r] should be a list of strings\" % (key,))\n            cfg1[key].extend(value)\n    return cfg1\n\n\ndef call(libname, flag, encoding=sys.getfilesystemencoding()):\n    \"\"\"Calls pkg-config and returns the output if found\n    \"\"\"\n    a = [\"pkg-config\", \"--print-errors\"]\n    a.append(flag)\n    a.append(libname)\n    try:\n        pc = subprocess.Popen(a, stdout=subprocess.PIPE, stderr=subprocess.PIPE)\n    except EnvironmentError as e:\n        raise PkgConfigError(\"cannot run pkg-config: %s\" % (str(e).strip(),))\n\n    bout, berr = pc.communicate()\n    if pc.returncode != 0:\n        try:\n            berr = berr.decode(encoding)\n        except Exception:\n            pass\n        raise PkgConfigError(berr.strip())\n\n    if sys.version_info >= (3,) and not isinstance(bout, str):   # Python 3.x\n        try:\n            bout = bout.decode(encoding)\n        except UnicodeDecodeError:\n            raise PkgConfigError(\"pkg-config %s %s returned bytes that cannot \"\n                                 \"be decoded with encoding %r:\\n%r\" %\n                                 (flag, libname, encoding, bout))\n\n    if os.altsep != '\\\\' and '\\\\' in bout:\n        raise PkgConfigError(\"pkg-config %s %s returned an unsupported \"\n                             \"backslash-escaped output:\\n%r\" %\n                             (flag, libname, bout))\n    return bout\n\n\ndef flags_from_pkgconfig(libs):\n    r\"\"\"Return compiler line flags for FFI.set_source based on pkg-config output\n\n    Usage\n        ...\n        ffibuilder.set_source(\"_foo\", pkgconfig = [\"libfoo\", \"libbar >= 1.8.3\"])\n\n    If pkg-config is installed on build machine, then arguments include_dirs,\n    library_dirs, libraries, define_macros, extra_compile_args and\n    extra_link_args are extended with an output of pkg-config for libfoo and\n    libbar.\n\n    Raises PkgConfigError in case the pkg-config call fails.\n    \"\"\"\n\n    def get_include_dirs(string):\n        return [x[2:] for x in string.split() if x.startswith(\"-I\")]\n\n    def get_library_dirs(string):\n        return [x[2:] for x in string.split() if x.startswith(\"-L\")]\n\n    def get_libraries(string):\n        return [x[2:] for x in string.split() if x.startswith(\"-l\")]\n\n    # convert -Dfoo=bar to list of tuples [(\"foo\", \"bar\")] expected by distutils\n    def get_macros(string):\n        def _macro(x):\n            x = x[2:]    # drop \"-D\"\n            if '=' in x:\n                return tuple(x.split(\"=\", 1))  # \"-Dfoo=bar\" => (\"foo\", \"bar\")\n            else:\n                return (x, None)               # \"-Dfoo\" => (\"foo\", None)\n        return [_macro(x) for x in string.split() if x.startswith(\"-D\")]\n\n    def get_other_cflags(string):\n        return [x for x in string.split() if not x.startswith(\"-I\") and\n                                             not x.startswith(\"-D\")]\n\n    def get_other_libs(string):\n        return [x for x in string.split() if not x.startswith(\"-L\") and\n                                             not x.startswith(\"-l\")]\n\n    # return kwargs for given libname\n    def kwargs(libname):\n        fse = sys.getfilesystemencoding()\n        all_cflags = call(libname, \"--cflags\")\n        all_libs = call(libname, \"--libs\")\n        return {\n            \"include_dirs\": get_include_dirs(all_cflags),\n            \"library_dirs\": get_library_dirs(all_libs),\n            \"libraries\": get_libraries(all_libs),\n            \"define_macros\": get_macros(all_cflags),\n            \"extra_compile_args\": get_other_cflags(all_cflags),\n            \"extra_link_args\": get_other_libs(all_libs),\n            }\n\n    # merge all arguments together\n    ret = {}\n    for libname in libs:\n        lib_flags = kwargs(libname)\n        merge_flags(ret, lib_flags)\n    return ret\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/recompiler.py",
    "content": "import os, sys, io\nfrom . import ffiplatform, model\nfrom .error import VerificationError\nfrom .cffi_opcode import *\n\nVERSION_BASE = 0x2601\nVERSION_EMBEDDED = 0x2701\nVERSION_CHAR16CHAR32 = 0x2801\n\n\nclass GlobalExpr:\n    def __init__(self, name, address, type_op, size=0, check_value=0):\n        self.name = name\n        self.address = address\n        self.type_op = type_op\n        self.size = size\n        self.check_value = check_value\n\n    def as_c_expr(self):\n        return '  { \"%s\", (void *)%s, %s, (void *)%s },' % (\n            self.name, self.address, self.type_op.as_c_expr(), self.size)\n\n    def as_python_expr(self):\n        return \"b'%s%s',%d\" % (self.type_op.as_python_bytes(), self.name,\n                               self.check_value)\n\nclass FieldExpr:\n    def __init__(self, name, field_offset, field_size, fbitsize, field_type_op):\n        self.name = name\n        self.field_offset = field_offset\n        self.field_size = field_size\n        self.fbitsize = fbitsize\n        self.field_type_op = field_type_op\n\n    def as_c_expr(self):\n        spaces = \" \" * len(self.name)\n        return ('  { \"%s\", %s,\\n' % (self.name, self.field_offset) +\n                '     %s   %s,\\n' % (spaces, self.field_size) +\n                '     %s   %s },' % (spaces, self.field_type_op.as_c_expr()))\n\n    def as_python_expr(self):\n        raise NotImplementedError\n\n    def as_field_python_expr(self):\n        if self.field_type_op.op == OP_NOOP:\n            size_expr = ''\n        elif self.field_type_op.op == OP_BITFIELD:\n            size_expr = format_four_bytes(self.fbitsize)\n        else:\n            raise NotImplementedError\n        return \"b'%s%s%s'\" % (self.field_type_op.as_python_bytes(),\n                              size_expr,\n                              self.name)\n\nclass StructUnionExpr:\n    def __init__(self, name, type_index, flags, size, alignment, comment,\n                 first_field_index, c_fields):\n        self.name = name\n        self.type_index = type_index\n        self.flags = flags\n        self.size = size\n        self.alignment = alignment\n        self.comment = comment\n        self.first_field_index = first_field_index\n        self.c_fields = c_fields\n\n    def as_c_expr(self):\n        return ('  { \"%s\", %d, %s,' % (self.name, self.type_index, self.flags)\n                + '\\n    %s, %s, ' % (self.size, self.alignment)\n                + '%d, %d ' % (self.first_field_index, len(self.c_fields))\n                + ('/* %s */ ' % self.comment if self.comment else '')\n                + '},')\n\n    def as_python_expr(self):\n        flags = eval(self.flags, G_FLAGS)\n        fields_expr = [c_field.as_field_python_expr()\n                       for c_field in self.c_fields]\n        return \"(b'%s%s%s',%s)\" % (\n            format_four_bytes(self.type_index),\n            format_four_bytes(flags),\n            self.name,\n            ','.join(fields_expr))\n\nclass EnumExpr:\n    def __init__(self, name, type_index, size, signed, allenums):\n        self.name = name\n        self.type_index = type_index\n        self.size = size\n        self.signed = signed\n        self.allenums = allenums\n\n    def as_c_expr(self):\n        return ('  { \"%s\", %d, _cffi_prim_int(%s, %s),\\n'\n                '    \"%s\" },' % (self.name, self.type_index,\n                                 self.size, self.signed, self.allenums))\n\n    def as_python_expr(self):\n        prim_index = {\n            (1, 0): PRIM_UINT8,  (1, 1):  PRIM_INT8,\n            (2, 0): PRIM_UINT16, (2, 1):  PRIM_INT16,\n            (4, 0): PRIM_UINT32, (4, 1):  PRIM_INT32,\n            (8, 0): PRIM_UINT64, (8, 1):  PRIM_INT64,\n            }[self.size, self.signed]\n        return \"b'%s%s%s\\\\x00%s'\" % (format_four_bytes(self.type_index),\n                                     format_four_bytes(prim_index),\n                                     self.name, self.allenums)\n\nclass TypenameExpr:\n    def __init__(self, name, type_index):\n        self.name = name\n        self.type_index = type_index\n\n    def as_c_expr(self):\n        return '  { \"%s\", %d },' % (self.name, self.type_index)\n\n    def as_python_expr(self):\n        return \"b'%s%s'\" % (format_four_bytes(self.type_index), self.name)\n\n\n# ____________________________________________________________\n\n\nclass Recompiler:\n    _num_externpy = 0\n\n    def __init__(self, ffi, module_name, target_is_python=False):\n        self.ffi = ffi\n        self.module_name = module_name\n        self.target_is_python = target_is_python\n        self._version = VERSION_BASE\n\n    def needs_version(self, ver):\n        self._version = max(self._version, ver)\n\n    def collect_type_table(self):\n        self._typesdict = {}\n        self._generate(\"collecttype\")\n        #\n        all_decls = sorted(self._typesdict, key=str)\n        #\n        # prepare all FUNCTION bytecode sequences first\n        self.cffi_types = []\n        for tp in all_decls:\n            if tp.is_raw_function:\n                assert self._typesdict[tp] is None\n                self._typesdict[tp] = len(self.cffi_types)\n                self.cffi_types.append(tp)     # placeholder\n                for tp1 in tp.args:\n                    assert isinstance(tp1, (model.VoidType,\n                                            model.BasePrimitiveType,\n                                            model.PointerType,\n                                            model.StructOrUnionOrEnum,\n                                            model.FunctionPtrType))\n                    if self._typesdict[tp1] is None:\n                        self._typesdict[tp1] = len(self.cffi_types)\n                    self.cffi_types.append(tp1)   # placeholder\n                self.cffi_types.append('END')     # placeholder\n        #\n        # prepare all OTHER bytecode sequences\n        for tp in all_decls:\n            if not tp.is_raw_function and self._typesdict[tp] is None:\n                self._typesdict[tp] = len(self.cffi_types)\n                self.cffi_types.append(tp)        # placeholder\n                if tp.is_array_type and tp.length is not None:\n                    self.cffi_types.append('LEN') # placeholder\n        assert None not in self._typesdict.values()\n        #\n        # collect all structs and unions and enums\n        self._struct_unions = {}\n        self._enums = {}\n        for tp in all_decls:\n            if isinstance(tp, model.StructOrUnion):\n                self._struct_unions[tp] = None\n            elif isinstance(tp, model.EnumType):\n                self._enums[tp] = None\n        for i, tp in enumerate(sorted(self._struct_unions,\n                                      key=lambda tp: tp.name)):\n            self._struct_unions[tp] = i\n        for i, tp in enumerate(sorted(self._enums,\n                                      key=lambda tp: tp.name)):\n            self._enums[tp] = i\n        #\n        # emit all bytecode sequences now\n        for tp in all_decls:\n            method = getattr(self, '_emit_bytecode_' + tp.__class__.__name__)\n            method(tp, self._typesdict[tp])\n        #\n        # consistency check\n        for op in self.cffi_types:\n            assert isinstance(op, CffiOp)\n        self.cffi_types = tuple(self.cffi_types)    # don't change any more\n\n    def _do_collect_type(self, tp):\n        if not isinstance(tp, model.BaseTypeByIdentity):\n            if isinstance(tp, tuple):\n                for x in tp:\n                    self._do_collect_type(x)\n            return\n        if tp not in self._typesdict:\n            self._typesdict[tp] = None\n            if isinstance(tp, model.FunctionPtrType):\n                self._do_collect_type(tp.as_raw_function())\n            elif isinstance(tp, model.StructOrUnion):\n                if tp.fldtypes is not None and (\n                        tp not in self.ffi._parser._included_declarations):\n                    for name1, tp1, _, _ in tp.enumfields():\n                        self._do_collect_type(self._field_type(tp, name1, tp1))\n            else:\n                for _, x in tp._get_items():\n                    self._do_collect_type(x)\n\n    def _generate(self, step_name):\n        lst = self.ffi._parser._declarations.items()\n        for name, (tp, quals) in sorted(lst):\n            kind, realname = name.split(' ', 1)\n            try:\n                method = getattr(self, '_generate_cpy_%s_%s' % (kind,\n                                                                step_name))\n            except AttributeError:\n                raise VerificationError(\n                    \"not implemented in recompile(): %r\" % name)\n            try:\n                self._current_quals = quals\n                method(tp, realname)\n            except Exception as e:\n                model.attach_exception_info(e, name)\n                raise\n\n    # ----------\n\n    ALL_STEPS = [\"global\", \"field\", \"struct_union\", \"enum\", \"typename\"]\n\n    def collect_step_tables(self):\n        # collect the declarations for '_cffi_globals', '_cffi_typenames', etc.\n        self._lsts = {}\n        for step_name in self.ALL_STEPS:\n            self._lsts[step_name] = []\n        self._seen_struct_unions = set()\n        self._generate(\"ctx\")\n        self._add_missing_struct_unions()\n        #\n        for step_name in self.ALL_STEPS:\n            lst = self._lsts[step_name]\n            if step_name != \"field\":\n                lst.sort(key=lambda entry: entry.name)\n            self._lsts[step_name] = tuple(lst)    # don't change any more\n        #\n        # check for a possible internal inconsistency: _cffi_struct_unions\n        # should have been generated with exactly self._struct_unions\n        lst = self._lsts[\"struct_union\"]\n        for tp, i in self._struct_unions.items():\n            assert i < len(lst)\n            assert lst[i].name == tp.name\n        assert len(lst) == len(self._struct_unions)\n        # same with enums\n        lst = self._lsts[\"enum\"]\n        for tp, i in self._enums.items():\n            assert i < len(lst)\n            assert lst[i].name == tp.name\n        assert len(lst) == len(self._enums)\n\n    # ----------\n\n    def _prnt(self, what=''):\n        self._f.write(what + '\\n')\n\n    def write_source_to_f(self, f, preamble):\n        if self.target_is_python:\n            assert preamble is None\n            self.write_py_source_to_f(f)\n        else:\n            assert preamble is not None\n            self.write_c_source_to_f(f, preamble)\n\n    def _rel_readlines(self, filename):\n        g = open(os.path.join(os.path.dirname(__file__), filename), 'r')\n        lines = g.readlines()\n        g.close()\n        return lines\n\n    def write_c_source_to_f(self, f, preamble):\n        self._f = f\n        prnt = self._prnt\n        if self.ffi._embedding is not None:\n            prnt('#define _CFFI_USE_EMBEDDING')\n        #\n        # first the '#include' (actually done by inlining the file's content)\n        lines = self._rel_readlines('_cffi_include.h')\n        i = lines.index('#include \"parse_c_type.h\"\\n')\n        lines[i:i+1] = self._rel_readlines('parse_c_type.h')\n        prnt(''.join(lines))\n        #\n        # if we have ffi._embedding != None, we give it here as a macro\n        # and include an extra file\n        base_module_name = self.module_name.split('.')[-1]\n        if self.ffi._embedding is not None:\n            prnt('#define _CFFI_MODULE_NAME  \"%s\"' % (self.module_name,))\n            prnt('static const char _CFFI_PYTHON_STARTUP_CODE[] = {')\n            self._print_string_literal_in_array(self.ffi._embedding)\n            prnt('0 };')\n            prnt('#ifdef PYPY_VERSION')\n            prnt('# define _CFFI_PYTHON_STARTUP_FUNC  _cffi_pypyinit_%s' % (\n                base_module_name,))\n            prnt('#elif PY_MAJOR_VERSION >= 3')\n            prnt('# define _CFFI_PYTHON_STARTUP_FUNC  PyInit_%s' % (\n                base_module_name,))\n            prnt('#else')\n            prnt('# define _CFFI_PYTHON_STARTUP_FUNC  init%s' % (\n                base_module_name,))\n            prnt('#endif')\n            lines = self._rel_readlines('_embedding.h')\n            i = lines.index('#include \"_cffi_errors.h\"\\n')\n            lines[i:i+1] = self._rel_readlines('_cffi_errors.h')\n            prnt(''.join(lines))\n            self.needs_version(VERSION_EMBEDDED)\n        #\n        # then paste the C source given by the user, verbatim.\n        prnt('/************************************************************/')\n        prnt()\n        prnt(preamble)\n        prnt()\n        prnt('/************************************************************/')\n        prnt()\n        #\n        # the declaration of '_cffi_types'\n        prnt('static void *_cffi_types[] = {')\n        typeindex2type = dict([(i, tp) for (tp, i) in self._typesdict.items()])\n        for i, op in enumerate(self.cffi_types):\n            comment = ''\n            if i in typeindex2type:\n                comment = ' // ' + typeindex2type[i]._get_c_name()\n            prnt('/* %2d */ %s,%s' % (i, op.as_c_expr(), comment))\n        if not self.cffi_types:\n            prnt('  0')\n        prnt('};')\n        prnt()\n        #\n        # call generate_cpy_xxx_decl(), for every xxx found from\n        # ffi._parser._declarations.  This generates all the functions.\n        self._seen_constants = set()\n        self._generate(\"decl\")\n        #\n        # the declaration of '_cffi_globals' and '_cffi_typenames'\n        nums = {}\n        for step_name in self.ALL_STEPS:\n            lst = self._lsts[step_name]\n            nums[step_name] = len(lst)\n            if nums[step_name] > 0:\n                prnt('static const struct _cffi_%s_s _cffi_%ss[] = {' % (\n                    step_name, step_name))\n                for entry in lst:\n                    prnt(entry.as_c_expr())\n                prnt('};')\n                prnt()\n        #\n        # the declaration of '_cffi_includes'\n        if self.ffi._included_ffis:\n            prnt('static const char * const _cffi_includes[] = {')\n            for ffi_to_include in self.ffi._included_ffis:\n                try:\n                    included_module_name, included_source = (\n                        ffi_to_include._assigned_source[:2])\n                except AttributeError:\n                    raise VerificationError(\n                        \"ffi object %r includes %r, but the latter has not \"\n                        \"been prepared with set_source()\" % (\n                            self.ffi, ffi_to_include,))\n                if included_source is None:\n                    raise VerificationError(\n                        \"not implemented yet: ffi.include() of a Python-based \"\n                        \"ffi inside a C-based ffi\")\n                prnt('  \"%s\",' % (included_module_name,))\n            prnt('  NULL')\n            prnt('};')\n            prnt()\n        #\n        # the declaration of '_cffi_type_context'\n        prnt('static const struct _cffi_type_context_s _cffi_type_context = {')\n        prnt('  _cffi_types,')\n        for step_name in self.ALL_STEPS:\n            if nums[step_name] > 0:\n                prnt('  _cffi_%ss,' % step_name)\n            else:\n                prnt('  NULL,  /* no %ss */' % step_name)\n        for step_name in self.ALL_STEPS:\n            if step_name != \"field\":\n                prnt('  %d,  /* num_%ss */' % (nums[step_name], step_name))\n        if self.ffi._included_ffis:\n            prnt('  _cffi_includes,')\n        else:\n            prnt('  NULL,  /* no includes */')\n        prnt('  %d,  /* num_types */' % (len(self.cffi_types),))\n        flags = 0\n        if self._num_externpy:\n            flags |= 1     # set to mean that we use extern \"Python\"\n        prnt('  %d,  /* flags */' % flags)\n        prnt('};')\n        prnt()\n        #\n        # the init function\n        prnt('#ifdef __GNUC__')\n        prnt('#  pragma GCC visibility push(default)  /* for -fvisibility= */')\n        prnt('#endif')\n        prnt()\n        prnt('#ifdef PYPY_VERSION')\n        prnt('PyMODINIT_FUNC')\n        prnt('_cffi_pypyinit_%s(const void *p[])' % (base_module_name,))\n        prnt('{')\n        if self._num_externpy:\n            prnt('    if (((intptr_t)p[0]) >= 0x0A03) {')\n            prnt('        _cffi_call_python_org = '\n                 '(void(*)(struct _cffi_externpy_s *, char *))p[1];')\n            prnt('    }')\n        prnt('    p[0] = (const void *)0x%x;' % self._version)\n        prnt('    p[1] = &_cffi_type_context;')\n        prnt('#if PY_MAJOR_VERSION >= 3')\n        prnt('    return NULL;')\n        prnt('#endif')\n        prnt('}')\n        # on Windows, distutils insists on putting init_cffi_xyz in\n        # 'export_symbols', so instead of fighting it, just give up and\n        # give it one\n        prnt('#  ifdef _MSC_VER')\n        prnt('     PyMODINIT_FUNC')\n        prnt('#  if PY_MAJOR_VERSION >= 3')\n        prnt('     PyInit_%s(void) { return NULL; }' % (base_module_name,))\n        prnt('#  else')\n        prnt('     init%s(void) { }' % (base_module_name,))\n        prnt('#  endif')\n        prnt('#  endif')\n        prnt('#elif PY_MAJOR_VERSION >= 3')\n        prnt('PyMODINIT_FUNC')\n        prnt('PyInit_%s(void)' % (base_module_name,))\n        prnt('{')\n        prnt('  return _cffi_init(\"%s\", 0x%x, &_cffi_type_context);' % (\n            self.module_name, self._version))\n        prnt('}')\n        prnt('#else')\n        prnt('PyMODINIT_FUNC')\n        prnt('init%s(void)' % (base_module_name,))\n        prnt('{')\n        prnt('  _cffi_init(\"%s\", 0x%x, &_cffi_type_context);' % (\n            self.module_name, self._version))\n        prnt('}')\n        prnt('#endif')\n        prnt()\n        prnt('#ifdef __GNUC__')\n        prnt('#  pragma GCC visibility pop')\n        prnt('#endif')\n        self._version = None\n\n    def _to_py(self, x):\n        if isinstance(x, str):\n            return \"b'%s'\" % (x,)\n        if isinstance(x, (list, tuple)):\n            rep = [self._to_py(item) for item in x]\n            if len(rep) == 1:\n                rep.append('')\n            return \"(%s)\" % (','.join(rep),)\n        return x.as_python_expr()  # Py2: unicode unexpected; Py3: bytes unexp.\n\n    def write_py_source_to_f(self, f):\n        self._f = f\n        prnt = self._prnt\n        #\n        # header\n        prnt(\"# auto-generated file\")\n        prnt(\"import _cffi_backend\")\n        #\n        # the 'import' of the included ffis\n        num_includes = len(self.ffi._included_ffis or ())\n        for i in range(num_includes):\n            ffi_to_include = self.ffi._included_ffis[i]\n            try:\n                included_module_name, included_source = (\n                    ffi_to_include._assigned_source[:2])\n            except AttributeError:\n                raise VerificationError(\n                    \"ffi object %r includes %r, but the latter has not \"\n                    \"been prepared with set_source()\" % (\n                        self.ffi, ffi_to_include,))\n            if included_source is not None:\n                raise VerificationError(\n                    \"not implemented yet: ffi.include() of a C-based \"\n                    \"ffi inside a Python-based ffi\")\n            prnt('from %s import ffi as _ffi%d' % (included_module_name, i))\n        prnt()\n        prnt(\"ffi = _cffi_backend.FFI('%s',\" % (self.module_name,))\n        prnt(\"    _version = 0x%x,\" % (self._version,))\n        self._version = None\n        #\n        # the '_types' keyword argument\n        self.cffi_types = tuple(self.cffi_types)    # don't change any more\n        types_lst = [op.as_python_bytes() for op in self.cffi_types]\n        prnt('    _types = %s,' % (self._to_py(''.join(types_lst)),))\n        typeindex2type = dict([(i, tp) for (tp, i) in self._typesdict.items()])\n        #\n        # the keyword arguments from ALL_STEPS\n        for step_name in self.ALL_STEPS:\n            lst = self._lsts[step_name]\n            if len(lst) > 0 and step_name != \"field\":\n                prnt('    _%ss = %s,' % (step_name, self._to_py(lst)))\n        #\n        # the '_includes' keyword argument\n        if num_includes > 0:\n            prnt('    _includes = (%s,),' % (\n                ', '.join(['_ffi%d' % i for i in range(num_includes)]),))\n        #\n        # the footer\n        prnt(')')\n\n    # ----------\n\n    def _gettypenum(self, type):\n        # a KeyError here is a bug.  please report it! :-)\n        return self._typesdict[type]\n\n    def _convert_funcarg_to_c(self, tp, fromvar, tovar, errcode):\n        extraarg = ''\n        if isinstance(tp, model.BasePrimitiveType) and not tp.is_complex_type():\n            if tp.is_integer_type() and tp.name != '_Bool':\n                converter = '_cffi_to_c_int'\n                extraarg = ', %s' % tp.name\n            elif isinstance(tp, model.UnknownFloatType):\n                # don't check with is_float_type(): it may be a 'long\n                # double' here, and _cffi_to_c_double would loose precision\n                converter = '(%s)_cffi_to_c_double' % (tp.get_c_name(''),)\n            else:\n                cname = tp.get_c_name('')\n                converter = '(%s)_cffi_to_c_%s' % (cname,\n                                                   tp.name.replace(' ', '_'))\n                if cname in ('char16_t', 'char32_t'):\n                    self.needs_version(VERSION_CHAR16CHAR32)\n            errvalue = '-1'\n        #\n        elif isinstance(tp, model.PointerType):\n            self._convert_funcarg_to_c_ptr_or_array(tp, fromvar,\n                                                    tovar, errcode)\n            return\n        #\n        elif (isinstance(tp, model.StructOrUnionOrEnum) or\n              isinstance(tp, model.BasePrimitiveType)):\n            # a struct (not a struct pointer) as a function argument;\n            # or, a complex (the same code works)\n            self._prnt('  if (_cffi_to_c((char *)&%s, _cffi_type(%d), %s) < 0)'\n                      % (tovar, self._gettypenum(tp), fromvar))\n            self._prnt('    %s;' % errcode)\n            return\n        #\n        elif isinstance(tp, model.FunctionPtrType):\n            converter = '(%s)_cffi_to_c_pointer' % tp.get_c_name('')\n            extraarg = ', _cffi_type(%d)' % self._gettypenum(tp)\n            errvalue = 'NULL'\n        #\n        else:\n            raise NotImplementedError(tp)\n        #\n        self._prnt('  %s = %s(%s%s);' % (tovar, converter, fromvar, extraarg))\n        self._prnt('  if (%s == (%s)%s && PyErr_Occurred())' % (\n            tovar, tp.get_c_name(''), errvalue))\n        self._prnt('    %s;' % errcode)\n\n    def _extra_local_variables(self, tp, localvars):\n        if isinstance(tp, model.PointerType):\n            localvars.add('Py_ssize_t datasize')\n\n    def _convert_funcarg_to_c_ptr_or_array(self, tp, fromvar, tovar, errcode):\n        self._prnt('  datasize = _cffi_prepare_pointer_call_argument(')\n        self._prnt('      _cffi_type(%d), %s, (char **)&%s);' % (\n            self._gettypenum(tp), fromvar, tovar))\n        self._prnt('  if (datasize != 0) {')\n        self._prnt('    if (datasize < 0)')\n        self._prnt('      %s;' % errcode)\n        self._prnt('    %s = (%s)alloca((size_t)datasize);' % (\n            tovar, tp.get_c_name('')))\n        self._prnt('    memset((void *)%s, 0, (size_t)datasize);' % (tovar,))\n        self._prnt('    if (_cffi_convert_array_from_object('\n                   '(char *)%s, _cffi_type(%d), %s) < 0)' % (\n            tovar, self._gettypenum(tp), fromvar))\n        self._prnt('      %s;' % errcode)\n        self._prnt('  }')\n\n    def _convert_expr_from_c(self, tp, var, context):\n        if isinstance(tp, model.BasePrimitiveType):\n            if tp.is_integer_type() and tp.name != '_Bool':\n                return '_cffi_from_c_int(%s, %s)' % (var, tp.name)\n            elif isinstance(tp, model.UnknownFloatType):\n                return '_cffi_from_c_double(%s)' % (var,)\n            elif tp.name != 'long double' and not tp.is_complex_type():\n                cname = tp.name.replace(' ', '_')\n                if cname in ('char16_t', 'char32_t'):\n                    self.needs_version(VERSION_CHAR16CHAR32)\n                return '_cffi_from_c_%s(%s)' % (cname, var)\n            else:\n                return '_cffi_from_c_deref((char *)&%s, _cffi_type(%d))' % (\n                    var, self._gettypenum(tp))\n        elif isinstance(tp, (model.PointerType, model.FunctionPtrType)):\n            return '_cffi_from_c_pointer((char *)%s, _cffi_type(%d))' % (\n                var, self._gettypenum(tp))\n        elif isinstance(tp, model.ArrayType):\n            return '_cffi_from_c_pointer((char *)%s, _cffi_type(%d))' % (\n                var, self._gettypenum(model.PointerType(tp.item)))\n        elif isinstance(tp, model.StructOrUnion):\n            if tp.fldnames is None:\n                raise TypeError(\"'%s' is used as %s, but is opaque\" % (\n                    tp._get_c_name(), context))\n            return '_cffi_from_c_struct((char *)&%s, _cffi_type(%d))' % (\n                var, self._gettypenum(tp))\n        elif isinstance(tp, model.EnumType):\n            return '_cffi_from_c_deref((char *)&%s, _cffi_type(%d))' % (\n                var, self._gettypenum(tp))\n        else:\n            raise NotImplementedError(tp)\n\n    # ----------\n    # typedefs\n\n    def _typedef_type(self, tp, name):\n        return self._global_type(tp, \"(*(%s *)0)\" % (name,))\n\n    def _generate_cpy_typedef_collecttype(self, tp, name):\n        self._do_collect_type(self._typedef_type(tp, name))\n\n    def _generate_cpy_typedef_decl(self, tp, name):\n        pass\n\n    def _typedef_ctx(self, tp, name):\n        type_index = self._typesdict[tp]\n        self._lsts[\"typename\"].append(TypenameExpr(name, type_index))\n\n    def _generate_cpy_typedef_ctx(self, tp, name):\n        tp = self._typedef_type(tp, name)\n        self._typedef_ctx(tp, name)\n        if getattr(tp, \"origin\", None) == \"unknown_type\":\n            self._struct_ctx(tp, tp.name, approxname=None)\n        elif isinstance(tp, model.NamedPointerType):\n            self._struct_ctx(tp.totype, tp.totype.name, approxname=tp.name,\n                             named_ptr=tp)\n\n    # ----------\n    # function declarations\n\n    def _generate_cpy_function_collecttype(self, tp, name):\n        self._do_collect_type(tp.as_raw_function())\n        if tp.ellipsis and not self.target_is_python:\n            self._do_collect_type(tp)\n\n    def _generate_cpy_function_decl(self, tp, name):\n        assert not self.target_is_python\n        assert isinstance(tp, model.FunctionPtrType)\n        if tp.ellipsis:\n            # cannot support vararg functions better than this: check for its\n            # exact type (including the fixed arguments), and build it as a\n            # constant function pointer (no CPython wrapper)\n            self._generate_cpy_constant_decl(tp, name)\n            return\n        prnt = self._prnt\n        numargs = len(tp.args)\n        if numargs == 0:\n            argname = 'noarg'\n        elif numargs == 1:\n            argname = 'arg0'\n        else:\n            argname = 'args'\n        #\n        # ------------------------------\n        # the 'd' version of the function, only for addressof(lib, 'func')\n        arguments = []\n        call_arguments = []\n        context = 'argument of %s' % name\n        for i, type in enumerate(tp.args):\n            arguments.append(type.get_c_name(' x%d' % i, context))\n            call_arguments.append('x%d' % i)\n        repr_arguments = ', '.join(arguments)\n        repr_arguments = repr_arguments or 'void'\n        if tp.abi:\n            abi = tp.abi + ' '\n        else:\n            abi = ''\n        name_and_arguments = '%s_cffi_d_%s(%s)' % (abi, name, repr_arguments)\n        prnt('static %s' % (tp.result.get_c_name(name_and_arguments),))\n        prnt('{')\n        call_arguments = ', '.join(call_arguments)\n        result_code = 'return '\n        if isinstance(tp.result, model.VoidType):\n            result_code = ''\n        prnt('  %s%s(%s);' % (result_code, name, call_arguments))\n        prnt('}')\n        #\n        prnt('#ifndef PYPY_VERSION')        # ------------------------------\n        #\n        prnt('static PyObject *')\n        prnt('_cffi_f_%s(PyObject *self, PyObject *%s)' % (name, argname))\n        prnt('{')\n        #\n        context = 'argument of %s' % name\n        for i, type in enumerate(tp.args):\n            arg = type.get_c_name(' x%d' % i, context)\n            prnt('  %s;' % arg)\n        #\n        localvars = set()\n        for type in tp.args:\n            self._extra_local_variables(type, localvars)\n        for decl in localvars:\n            prnt('  %s;' % (decl,))\n        #\n        if not isinstance(tp.result, model.VoidType):\n            result_code = 'result = '\n            context = 'result of %s' % name\n            result_decl = '  %s;' % tp.result.get_c_name(' result', context)\n            prnt(result_decl)\n        else:\n            result_decl = None\n            result_code = ''\n        #\n        if len(tp.args) > 1:\n            rng = range(len(tp.args))\n            for i in rng:\n                prnt('  PyObject *arg%d;' % i)\n            prnt()\n            prnt('  if (!PyArg_UnpackTuple(args, \"%s\", %d, %d, %s))' % (\n                name, len(rng), len(rng),\n                ', '.join(['&arg%d' % i for i in rng])))\n            prnt('    return NULL;')\n        prnt()\n        #\n        for i, type in enumerate(tp.args):\n            self._convert_funcarg_to_c(type, 'arg%d' % i, 'x%d' % i,\n                                       'return NULL')\n            prnt()\n        #\n        prnt('  Py_BEGIN_ALLOW_THREADS')\n        prnt('  _cffi_restore_errno();')\n        call_arguments = ['x%d' % i for i in range(len(tp.args))]\n        call_arguments = ', '.join(call_arguments)\n        prnt('  { %s%s(%s); }' % (result_code, name, call_arguments))\n        prnt('  _cffi_save_errno();')\n        prnt('  Py_END_ALLOW_THREADS')\n        prnt()\n        #\n        prnt('  (void)self; /* unused */')\n        if numargs == 0:\n            prnt('  (void)noarg; /* unused */')\n        if result_code:\n            prnt('  return %s;' %\n                 self._convert_expr_from_c(tp.result, 'result', 'result type'))\n        else:\n            prnt('  Py_INCREF(Py_None);')\n            prnt('  return Py_None;')\n        prnt('}')\n        #\n        prnt('#else')        # ------------------------------\n        #\n        # the PyPy version: need to replace struct/union arguments with\n        # pointers, and if the result is a struct/union, insert a first\n        # arg that is a pointer to the result.  We also do that for\n        # complex args and return type.\n        def need_indirection(type):\n            return (isinstance(type, model.StructOrUnion) or\n                    (isinstance(type, model.PrimitiveType) and\n                     type.is_complex_type()))\n        difference = False\n        arguments = []\n        call_arguments = []\n        context = 'argument of %s' % name\n        for i, type in enumerate(tp.args):\n            indirection = ''\n            if need_indirection(type):\n                indirection = '*'\n                difference = True\n            arg = type.get_c_name(' %sx%d' % (indirection, i), context)\n            arguments.append(arg)\n            call_arguments.append('%sx%d' % (indirection, i))\n        tp_result = tp.result\n        if need_indirection(tp_result):\n            context = 'result of %s' % name\n            arg = tp_result.get_c_name(' *result', context)\n            arguments.insert(0, arg)\n            tp_result = model.void_type\n            result_decl = None\n            result_code = '*result = '\n            difference = True\n        if difference:\n            repr_arguments = ', '.join(arguments)\n            repr_arguments = repr_arguments or 'void'\n            name_and_arguments = '%s_cffi_f_%s(%s)' % (abi, name,\n                                                       repr_arguments)\n            prnt('static %s' % (tp_result.get_c_name(name_and_arguments),))\n            prnt('{')\n            if result_decl:\n                prnt(result_decl)\n            call_arguments = ', '.join(call_arguments)\n            prnt('  { %s%s(%s); }' % (result_code, name, call_arguments))\n            if result_decl:\n                prnt('  return result;')\n            prnt('}')\n        else:\n            prnt('#  define _cffi_f_%s _cffi_d_%s' % (name, name))\n        #\n        prnt('#endif')        # ------------------------------\n        prnt()\n\n    def _generate_cpy_function_ctx(self, tp, name):\n        if tp.ellipsis and not self.target_is_python:\n            self._generate_cpy_constant_ctx(tp, name)\n            return\n        type_index = self._typesdict[tp.as_raw_function()]\n        numargs = len(tp.args)\n        if self.target_is_python:\n            meth_kind = OP_DLOPEN_FUNC\n        elif numargs == 0:\n            meth_kind = OP_CPYTHON_BLTN_N   # 'METH_NOARGS'\n        elif numargs == 1:\n            meth_kind = OP_CPYTHON_BLTN_O   # 'METH_O'\n        else:\n            meth_kind = OP_CPYTHON_BLTN_V   # 'METH_VARARGS'\n        self._lsts[\"global\"].append(\n            GlobalExpr(name, '_cffi_f_%s' % name,\n                       CffiOp(meth_kind, type_index),\n                       size='_cffi_d_%s' % name))\n\n    # ----------\n    # named structs or unions\n\n    def _field_type(self, tp_struct, field_name, tp_field):\n        if isinstance(tp_field, model.ArrayType):\n            actual_length = tp_field.length\n            if actual_length == '...':\n                ptr_struct_name = tp_struct.get_c_name('*')\n                actual_length = '_cffi_array_len(((%s)0)->%s)' % (\n                    ptr_struct_name, field_name)\n            tp_item = self._field_type(tp_struct, '%s[0]' % field_name,\n                                       tp_field.item)\n            tp_field = model.ArrayType(tp_item, actual_length)\n        return tp_field\n\n    def _struct_collecttype(self, tp):\n        self._do_collect_type(tp)\n        if self.target_is_python:\n            # also requires nested anon struct/unions in ABI mode, recursively\n            for fldtype in tp.anonymous_struct_fields():\n                self._struct_collecttype(fldtype)\n\n    def _struct_decl(self, tp, cname, approxname):\n        if tp.fldtypes is None:\n            return\n        prnt = self._prnt\n        checkfuncname = '_cffi_checkfld_%s' % (approxname,)\n        prnt('_CFFI_UNUSED_FN')\n        prnt('static void %s(%s *p)' % (checkfuncname, cname))\n        prnt('{')\n        prnt('  /* only to generate compile-time warnings or errors */')\n        prnt('  (void)p;')\n        for fname, ftype, fbitsize, fqual in tp.enumfields():\n            try:\n                if ftype.is_integer_type() or fbitsize >= 0:\n                    # accept all integers, but complain on float or double\n                    if fname != '':\n                        prnt(\"  (void)((p->%s) | 0);  /* check that '%s.%s' is \"\n                             \"an integer */\" % (fname, cname, fname))\n                    continue\n                # only accept exactly the type declared, except that '[]'\n                # is interpreted as a '*' and so will match any array length.\n                # (It would also match '*', but that's harder to detect...)\n                while (isinstance(ftype, model.ArrayType)\n                       and (ftype.length is None or ftype.length == '...')):\n                    ftype = ftype.item\n                    fname = fname + '[0]'\n                prnt('  { %s = &p->%s; (void)tmp; }' % (\n                    ftype.get_c_name('*tmp', 'field %r'%fname, quals=fqual),\n                    fname))\n            except VerificationError as e:\n                prnt('  /* %s */' % str(e))   # cannot verify it, ignore\n        prnt('}')\n        prnt('struct _cffi_align_%s { char x; %s y; };' % (approxname, cname))\n        prnt()\n\n    def _struct_ctx(self, tp, cname, approxname, named_ptr=None):\n        type_index = self._typesdict[tp]\n        reason_for_not_expanding = None\n        flags = []\n        if isinstance(tp, model.UnionType):\n            flags.append(\"_CFFI_F_UNION\")\n        if tp.fldtypes is None:\n            flags.append(\"_CFFI_F_OPAQUE\")\n            reason_for_not_expanding = \"opaque\"\n        if (tp not in self.ffi._parser._included_declarations and\n                (named_ptr is None or\n                 named_ptr not in self.ffi._parser._included_declarations)):\n            if tp.fldtypes is None:\n                pass    # opaque\n            elif tp.partial or any(tp.anonymous_struct_fields()):\n                pass    # field layout obtained silently from the C compiler\n            else:\n                flags.append(\"_CFFI_F_CHECK_FIELDS\")\n            if tp.packed:\n                if tp.packed > 1:\n                    raise NotImplementedError(\n                        \"%r is declared with 'pack=%r'; only 0 or 1 are \"\n                        \"supported in API mode (try to use \\\"...;\\\", which \"\n                        \"does not require a 'pack' declaration)\" %\n                        (tp, tp.packed))\n                flags.append(\"_CFFI_F_PACKED\")\n        else:\n            flags.append(\"_CFFI_F_EXTERNAL\")\n            reason_for_not_expanding = \"external\"\n        flags = '|'.join(flags) or '0'\n        c_fields = []\n        if reason_for_not_expanding is None:\n            expand_anonymous_struct_union = not self.target_is_python\n            enumfields = list(tp.enumfields(expand_anonymous_struct_union))\n            for fldname, fldtype, fbitsize, fqual in enumfields:\n                fldtype = self._field_type(tp, fldname, fldtype)\n                self._check_not_opaque(fldtype,\n                                       \"field '%s.%s'\" % (tp.name, fldname))\n                # cname is None for _add_missing_struct_unions() only\n                op = OP_NOOP\n                if fbitsize >= 0:\n                    op = OP_BITFIELD\n                    size = '%d /* bits */' % fbitsize\n                elif cname is None or (\n                        isinstance(fldtype, model.ArrayType) and\n                        fldtype.length is None):\n                    size = '(size_t)-1'\n                else:\n                    size = 'sizeof(((%s)0)->%s)' % (\n                        tp.get_c_name('*') if named_ptr is None\n                                           else named_ptr.name,\n                        fldname)\n                if cname is None or fbitsize >= 0:\n                    offset = '(size_t)-1'\n                elif named_ptr is not None:\n                    offset = '((char *)&((%s)0)->%s) - (char *)0' % (\n                        named_ptr.name, fldname)\n                else:\n                    offset = 'offsetof(%s, %s)' % (tp.get_c_name(''), fldname)\n                c_fields.append(\n                    FieldExpr(fldname, offset, size, fbitsize,\n                              CffiOp(op, self._typesdict[fldtype])))\n            first_field_index = len(self._lsts[\"field\"])\n            self._lsts[\"field\"].extend(c_fields)\n            #\n            if cname is None:  # unknown name, for _add_missing_struct_unions\n                size = '(size_t)-2'\n                align = -2\n                comment = \"unnamed\"\n            else:\n                if named_ptr is not None:\n                    size = 'sizeof(*(%s)0)' % (named_ptr.name,)\n                    align = '-1 /* unknown alignment */'\n                else:\n                    size = 'sizeof(%s)' % (cname,)\n                    align = 'offsetof(struct _cffi_align_%s, y)' % (approxname,)\n                comment = None\n        else:\n            size = '(size_t)-1'\n            align = -1\n            first_field_index = -1\n            comment = reason_for_not_expanding\n        self._lsts[\"struct_union\"].append(\n            StructUnionExpr(tp.name, type_index, flags, size, align, comment,\n                            first_field_index, c_fields))\n        self._seen_struct_unions.add(tp)\n\n    def _check_not_opaque(self, tp, location):\n        while isinstance(tp, model.ArrayType):\n            tp = tp.item\n        if isinstance(tp, model.StructOrUnion) and tp.fldtypes is None:\n            raise TypeError(\n                \"%s is of an opaque type (not declared in cdef())\" % location)\n\n    def _add_missing_struct_unions(self):\n        # not very nice, but some struct declarations might be missing\n        # because they don't have any known C name.  Check that they are\n        # not partial (we can't complete or verify them!) and emit them\n        # anonymously.\n        lst = list(self._struct_unions.items())\n        lst.sort(key=lambda tp_order: tp_order[1])\n        for tp, order in lst:\n            if tp not in self._seen_struct_unions:\n                if tp.partial:\n                    raise NotImplementedError(\"internal inconsistency: %r is \"\n                                              \"partial but was not seen at \"\n                                              \"this point\" % (tp,))\n                if tp.name.startswith('$') and tp.name[1:].isdigit():\n                    approxname = tp.name[1:]\n                elif tp.name == '_IO_FILE' and tp.forcename == 'FILE':\n                    approxname = 'FILE'\n                    self._typedef_ctx(tp, 'FILE')\n                else:\n                    raise NotImplementedError(\"internal inconsistency: %r\" %\n                                              (tp,))\n                self._struct_ctx(tp, None, approxname)\n\n    def _generate_cpy_struct_collecttype(self, tp, name):\n        self._struct_collecttype(tp)\n    _generate_cpy_union_collecttype = _generate_cpy_struct_collecttype\n\n    def _struct_names(self, tp):\n        cname = tp.get_c_name('')\n        if ' ' in cname:\n            return cname, cname.replace(' ', '_')\n        else:\n            return cname, '_' + cname\n\n    def _generate_cpy_struct_decl(self, tp, name):\n        self._struct_decl(tp, *self._struct_names(tp))\n    _generate_cpy_union_decl = _generate_cpy_struct_decl\n\n    def _generate_cpy_struct_ctx(self, tp, name):\n        self._struct_ctx(tp, *self._struct_names(tp))\n    _generate_cpy_union_ctx = _generate_cpy_struct_ctx\n\n    # ----------\n    # 'anonymous' declarations.  These are produced for anonymous structs\n    # or unions; the 'name' is obtained by a typedef.\n\n    def _generate_cpy_anonymous_collecttype(self, tp, name):\n        if isinstance(tp, model.EnumType):\n            self._generate_cpy_enum_collecttype(tp, name)\n        else:\n            self._struct_collecttype(tp)\n\n    def _generate_cpy_anonymous_decl(self, tp, name):\n        if isinstance(tp, model.EnumType):\n            self._generate_cpy_enum_decl(tp)\n        else:\n            self._struct_decl(tp, name, 'typedef_' + name)\n\n    def _generate_cpy_anonymous_ctx(self, tp, name):\n        if isinstance(tp, model.EnumType):\n            self._enum_ctx(tp, name)\n        else:\n            self._struct_ctx(tp, name, 'typedef_' + name)\n\n    # ----------\n    # constants, declared with \"static const ...\"\n\n    def _generate_cpy_const(self, is_int, name, tp=None, category='const',\n                            check_value=None):\n        if (category, name) in self._seen_constants:\n            raise VerificationError(\n                \"duplicate declaration of %s '%s'\" % (category, name))\n        self._seen_constants.add((category, name))\n        #\n        prnt = self._prnt\n        funcname = '_cffi_%s_%s' % (category, name)\n        if is_int:\n            prnt('static int %s(unsigned long long *o)' % funcname)\n            prnt('{')\n            prnt('  int n = (%s) <= 0;' % (name,))\n            prnt('  *o = (unsigned long long)((%s) | 0);'\n                 '  /* check that %s is an integer */' % (name, name))\n            if check_value is not None:\n                if check_value > 0:\n                    check_value = '%dU' % (check_value,)\n                prnt('  if (!_cffi_check_int(*o, n, %s))' % (check_value,))\n                prnt('    n |= 2;')\n            prnt('  return n;')\n            prnt('}')\n        else:\n            assert check_value is None\n            prnt('static void %s(char *o)' % funcname)\n            prnt('{')\n            prnt('  *(%s)o = %s;' % (tp.get_c_name('*'), name))\n            prnt('}')\n        prnt()\n\n    def _generate_cpy_constant_collecttype(self, tp, name):\n        is_int = tp.is_integer_type()\n        if not is_int or self.target_is_python:\n            self._do_collect_type(tp)\n\n    def _generate_cpy_constant_decl(self, tp, name):\n        is_int = tp.is_integer_type()\n        self._generate_cpy_const(is_int, name, tp)\n\n    def _generate_cpy_constant_ctx(self, tp, name):\n        if not self.target_is_python and tp.is_integer_type():\n            type_op = CffiOp(OP_CONSTANT_INT, -1)\n        else:\n            if self.target_is_python:\n                const_kind = OP_DLOPEN_CONST\n            else:\n                const_kind = OP_CONSTANT\n            type_index = self._typesdict[tp]\n            type_op = CffiOp(const_kind, type_index)\n        self._lsts[\"global\"].append(\n            GlobalExpr(name, '_cffi_const_%s' % name, type_op))\n\n    # ----------\n    # enums\n\n    def _generate_cpy_enum_collecttype(self, tp, name):\n        self._do_collect_type(tp)\n\n    def _generate_cpy_enum_decl(self, tp, name=None):\n        for enumerator in tp.enumerators:\n            self._generate_cpy_const(True, enumerator)\n\n    def _enum_ctx(self, tp, cname):\n        type_index = self._typesdict[tp]\n        type_op = CffiOp(OP_ENUM, -1)\n        if self.target_is_python:\n            tp.check_not_partial()\n        for enumerator, enumvalue in zip(tp.enumerators, tp.enumvalues):\n            self._lsts[\"global\"].append(\n                GlobalExpr(enumerator, '_cffi_const_%s' % enumerator, type_op,\n                           check_value=enumvalue))\n        #\n        if cname is not None and '$' not in cname and not self.target_is_python:\n            size = \"sizeof(%s)\" % cname\n            signed = \"((%s)-1) <= 0\" % cname\n        else:\n            basetp = tp.build_baseinttype(self.ffi, [])\n            size = self.ffi.sizeof(basetp)\n            signed = int(int(self.ffi.cast(basetp, -1)) < 0)\n        allenums = \",\".join(tp.enumerators)\n        self._lsts[\"enum\"].append(\n            EnumExpr(tp.name, type_index, size, signed, allenums))\n\n    def _generate_cpy_enum_ctx(self, tp, name):\n        self._enum_ctx(tp, tp._get_c_name())\n\n    # ----------\n    # macros: for now only for integers\n\n    def _generate_cpy_macro_collecttype(self, tp, name):\n        pass\n\n    def _generate_cpy_macro_decl(self, tp, name):\n        if tp == '...':\n            check_value = None\n        else:\n            check_value = tp     # an integer\n        self._generate_cpy_const(True, name, check_value=check_value)\n\n    def _generate_cpy_macro_ctx(self, tp, name):\n        if tp == '...':\n            if self.target_is_python:\n                raise VerificationError(\n                    \"cannot use the syntax '...' in '#define %s ...' when \"\n                    \"using the ABI mode\" % (name,))\n            check_value = None\n        else:\n            check_value = tp     # an integer\n        type_op = CffiOp(OP_CONSTANT_INT, -1)\n        self._lsts[\"global\"].append(\n            GlobalExpr(name, '_cffi_const_%s' % name, type_op,\n                       check_value=check_value))\n\n    # ----------\n    # global variables\n\n    def _global_type(self, tp, global_name):\n        if isinstance(tp, model.ArrayType):\n            actual_length = tp.length\n            if actual_length == '...':\n                actual_length = '_cffi_array_len(%s)' % (global_name,)\n            tp_item = self._global_type(tp.item, '%s[0]' % global_name)\n            tp = model.ArrayType(tp_item, actual_length)\n        return tp\n\n    def _generate_cpy_variable_collecttype(self, tp, name):\n        self._do_collect_type(self._global_type(tp, name))\n\n    def _generate_cpy_variable_decl(self, tp, name):\n        prnt = self._prnt\n        tp = self._global_type(tp, name)\n        if isinstance(tp, model.ArrayType) and tp.length is None:\n            tp = tp.item\n            ampersand = ''\n        else:\n            ampersand = '&'\n        # This code assumes that casts from \"tp *\" to \"void *\" is a\n        # no-op, i.e. a function that returns a \"tp *\" can be called\n        # as if it returned a \"void *\".  This should be generally true\n        # on any modern machine.  The only exception to that rule (on\n        # uncommon architectures, and as far as I can tell) might be\n        # if 'tp' were a function type, but that is not possible here.\n        # (If 'tp' is a function _pointer_ type, then casts from \"fn_t\n        # **\" to \"void *\" are again no-ops, as far as I can tell.)\n        decl = '*_cffi_var_%s(void)' % (name,)\n        prnt('static ' + tp.get_c_name(decl, quals=self._current_quals))\n        prnt('{')\n        prnt('  return %s(%s);' % (ampersand, name))\n        prnt('}')\n        prnt()\n\n    def _generate_cpy_variable_ctx(self, tp, name):\n        tp = self._global_type(tp, name)\n        type_index = self._typesdict[tp]\n        if self.target_is_python:\n            op = OP_GLOBAL_VAR\n        else:\n            op = OP_GLOBAL_VAR_F\n        self._lsts[\"global\"].append(\n            GlobalExpr(name, '_cffi_var_%s' % name, CffiOp(op, type_index)))\n\n    # ----------\n    # extern \"Python\"\n\n    def _generate_cpy_extern_python_collecttype(self, tp, name):\n        assert isinstance(tp, model.FunctionPtrType)\n        self._do_collect_type(tp)\n    _generate_cpy_dllexport_python_collecttype = \\\n      _generate_cpy_extern_python_plus_c_collecttype = \\\n      _generate_cpy_extern_python_collecttype\n\n    def _extern_python_decl(self, tp, name, tag_and_space):\n        prnt = self._prnt\n        if isinstance(tp.result, model.VoidType):\n            size_of_result = '0'\n        else:\n            context = 'result of %s' % name\n            size_of_result = '(int)sizeof(%s)' % (\n                tp.result.get_c_name('', context),)\n        prnt('static struct _cffi_externpy_s _cffi_externpy__%s =' % name)\n        prnt('  { \"%s.%s\", %s };' % (self.module_name, name, size_of_result))\n        prnt()\n        #\n        arguments = []\n        context = 'argument of %s' % name\n        for i, type in enumerate(tp.args):\n            arg = type.get_c_name(' a%d' % i, context)\n            arguments.append(arg)\n        #\n        repr_arguments = ', '.join(arguments)\n        repr_arguments = repr_arguments or 'void'\n        name_and_arguments = '%s(%s)' % (name, repr_arguments)\n        if tp.abi == \"__stdcall\":\n            name_and_arguments = '_cffi_stdcall ' + name_and_arguments\n        #\n        def may_need_128_bits(tp):\n            return (isinstance(tp, model.PrimitiveType) and\n                    tp.name == 'long double')\n        #\n        size_of_a = max(len(tp.args)*8, 8)\n        if may_need_128_bits(tp.result):\n            size_of_a = max(size_of_a, 16)\n        if isinstance(tp.result, model.StructOrUnion):\n            size_of_a = 'sizeof(%s) > %d ? sizeof(%s) : %d' % (\n                tp.result.get_c_name(''), size_of_a,\n                tp.result.get_c_name(''), size_of_a)\n        prnt('%s%s' % (tag_and_space, tp.result.get_c_name(name_and_arguments)))\n        prnt('{')\n        prnt('  char a[%s];' % size_of_a)\n        prnt('  char *p = a;')\n        for i, type in enumerate(tp.args):\n            arg = 'a%d' % i\n            if (isinstance(type, model.StructOrUnion) or\n                    may_need_128_bits(type)):\n                arg = '&' + arg\n                type = model.PointerType(type)\n            prnt('  *(%s)(p + %d) = %s;' % (type.get_c_name('*'), i*8, arg))\n        prnt('  _cffi_call_python(&_cffi_externpy__%s, p);' % name)\n        if not isinstance(tp.result, model.VoidType):\n            prnt('  return *(%s)p;' % (tp.result.get_c_name('*'),))\n        prnt('}')\n        prnt()\n        self._num_externpy += 1\n\n    def _generate_cpy_extern_python_decl(self, tp, name):\n        self._extern_python_decl(tp, name, 'static ')\n\n    def _generate_cpy_dllexport_python_decl(self, tp, name):\n        self._extern_python_decl(tp, name, 'CFFI_DLLEXPORT ')\n\n    def _generate_cpy_extern_python_plus_c_decl(self, tp, name):\n        self._extern_python_decl(tp, name, '')\n\n    def _generate_cpy_extern_python_ctx(self, tp, name):\n        if self.target_is_python:\n            raise VerificationError(\n                \"cannot use 'extern \\\"Python\\\"' in the ABI mode\")\n        if tp.ellipsis:\n            raise NotImplementedError(\"a vararg function is extern \\\"Python\\\"\")\n        type_index = self._typesdict[tp]\n        type_op = CffiOp(OP_EXTERN_PYTHON, type_index)\n        self._lsts[\"global\"].append(\n            GlobalExpr(name, '&_cffi_externpy__%s' % name, type_op, name))\n\n    _generate_cpy_dllexport_python_ctx = \\\n      _generate_cpy_extern_python_plus_c_ctx = \\\n      _generate_cpy_extern_python_ctx\n\n    def _print_string_literal_in_array(self, s):\n        prnt = self._prnt\n        prnt('// # NB. this is not a string because of a size limit in MSVC')\n        for line in s.splitlines(True):\n            prnt(('// ' + line).rstrip())\n            printed_line = ''\n            for c in line:\n                if len(printed_line) >= 76:\n                    prnt(printed_line)\n                    printed_line = ''\n                printed_line += '%d,' % (ord(c),)\n            prnt(printed_line)\n\n    # ----------\n    # emitting the opcodes for individual types\n\n    def _emit_bytecode_VoidType(self, tp, index):\n        self.cffi_types[index] = CffiOp(OP_PRIMITIVE, PRIM_VOID)\n\n    def _emit_bytecode_PrimitiveType(self, tp, index):\n        prim_index = PRIMITIVE_TO_INDEX[tp.name]\n        self.cffi_types[index] = CffiOp(OP_PRIMITIVE, prim_index)\n\n    def _emit_bytecode_UnknownIntegerType(self, tp, index):\n        s = ('_cffi_prim_int(sizeof(%s), (\\n'\n             '           ((%s)-1) | 0 /* check that %s is an integer type */\\n'\n             '         ) <= 0)' % (tp.name, tp.name, tp.name))\n        self.cffi_types[index] = CffiOp(OP_PRIMITIVE, s)\n\n    def _emit_bytecode_UnknownFloatType(self, tp, index):\n        s = ('_cffi_prim_float(sizeof(%s) *\\n'\n             '           (((%s)1) / 2) * 2 /* integer => 0, float => 1 */\\n'\n             '         )' % (tp.name, tp.name))\n        self.cffi_types[index] = CffiOp(OP_PRIMITIVE, s)\n\n    def _emit_bytecode_RawFunctionType(self, tp, index):\n        self.cffi_types[index] = CffiOp(OP_FUNCTION, self._typesdict[tp.result])\n        index += 1\n        for tp1 in tp.args:\n            realindex = self._typesdict[tp1]\n            if index != realindex:\n                if isinstance(tp1, model.PrimitiveType):\n                    self._emit_bytecode_PrimitiveType(tp1, index)\n                else:\n                    self.cffi_types[index] = CffiOp(OP_NOOP, realindex)\n            index += 1\n        flags = int(tp.ellipsis)\n        if tp.abi is not None:\n            if tp.abi == '__stdcall':\n                flags |= 2\n            else:\n                raise NotImplementedError(\"abi=%r\" % (tp.abi,))\n        self.cffi_types[index] = CffiOp(OP_FUNCTION_END, flags)\n\n    def _emit_bytecode_PointerType(self, tp, index):\n        self.cffi_types[index] = CffiOp(OP_POINTER, self._typesdict[tp.totype])\n\n    _emit_bytecode_ConstPointerType = _emit_bytecode_PointerType\n    _emit_bytecode_NamedPointerType = _emit_bytecode_PointerType\n\n    def _emit_bytecode_FunctionPtrType(self, tp, index):\n        raw = tp.as_raw_function()\n        self.cffi_types[index] = CffiOp(OP_POINTER, self._typesdict[raw])\n\n    def _emit_bytecode_ArrayType(self, tp, index):\n        item_index = self._typesdict[tp.item]\n        if tp.length is None:\n            self.cffi_types[index] = CffiOp(OP_OPEN_ARRAY, item_index)\n        elif tp.length == '...':\n            raise VerificationError(\n                \"type %s badly placed: the '...' array length can only be \"\n                \"used on global arrays or on fields of structures\" % (\n                    str(tp).replace('/*...*/', '...'),))\n        else:\n            assert self.cffi_types[index + 1] == 'LEN'\n            self.cffi_types[index] = CffiOp(OP_ARRAY, item_index)\n            self.cffi_types[index + 1] = CffiOp(None, str(tp.length))\n\n    def _emit_bytecode_StructType(self, tp, index):\n        struct_index = self._struct_unions[tp]\n        self.cffi_types[index] = CffiOp(OP_STRUCT_UNION, struct_index)\n    _emit_bytecode_UnionType = _emit_bytecode_StructType\n\n    def _emit_bytecode_EnumType(self, tp, index):\n        enum_index = self._enums[tp]\n        self.cffi_types[index] = CffiOp(OP_ENUM, enum_index)\n\n\nif sys.version_info >= (3,):\n    NativeIO = io.StringIO\nelse:\n    class NativeIO(io.BytesIO):\n        def write(self, s):\n            if isinstance(s, unicode):\n                s = s.encode('ascii')\n            super(NativeIO, self).write(s)\n\ndef _make_c_or_py_source(ffi, module_name, preamble, target_file, verbose):\n    if verbose:\n        print(\"generating %s\" % (target_file,))\n    recompiler = Recompiler(ffi, module_name,\n                            target_is_python=(preamble is None))\n    recompiler.collect_type_table()\n    recompiler.collect_step_tables()\n    f = NativeIO()\n    recompiler.write_source_to_f(f, preamble)\n    output = f.getvalue()\n    try:\n        with open(target_file, 'r') as f1:\n            if f1.read(len(output) + 1) != output:\n                raise IOError\n        if verbose:\n            print(\"(already up-to-date)\")\n        return False     # already up-to-date\n    except IOError:\n        tmp_file = '%s.~%d' % (target_file, os.getpid())\n        with open(tmp_file, 'w') as f1:\n            f1.write(output)\n        try:\n            os.rename(tmp_file, target_file)\n        except OSError:\n            os.unlink(target_file)\n            os.rename(tmp_file, target_file)\n        return True\n\ndef make_c_source(ffi, module_name, preamble, target_c_file, verbose=False):\n    assert preamble is not None\n    return _make_c_or_py_source(ffi, module_name, preamble, target_c_file,\n                                verbose)\n\ndef make_py_source(ffi, module_name, target_py_file, verbose=False):\n    return _make_c_or_py_source(ffi, module_name, None, target_py_file,\n                                verbose)\n\ndef _modname_to_file(outputdir, modname, extension):\n    parts = modname.split('.')\n    try:\n        os.makedirs(os.path.join(outputdir, *parts[:-1]))\n    except OSError:\n        pass\n    parts[-1] += extension\n    return os.path.join(outputdir, *parts), parts\n\n\n# Aaargh.  Distutils is not tested at all for the purpose of compiling\n# DLLs that are not extension modules.  Here are some hacks to work\n# around that, in the _patch_for_*() functions...\n\ndef _patch_meth(patchlist, cls, name, new_meth):\n    old = getattr(cls, name)\n    patchlist.append((cls, name, old))\n    setattr(cls, name, new_meth)\n    return old\n\ndef _unpatch_meths(patchlist):\n    for cls, name, old_meth in reversed(patchlist):\n        setattr(cls, name, old_meth)\n\ndef _patch_for_embedding(patchlist):\n    if sys.platform == 'win32':\n        # we must not remove the manifest when building for embedding!\n        from distutils.msvc9compiler import MSVCCompiler\n        _patch_meth(patchlist, MSVCCompiler, '_remove_visual_c_ref',\n                    lambda self, manifest_file: manifest_file)\n\n    if sys.platform == 'darwin':\n        # we must not make a '-bundle', but a '-dynamiclib' instead\n        from distutils.ccompiler import CCompiler\n        def my_link_shared_object(self, *args, **kwds):\n            if '-bundle' in self.linker_so:\n                self.linker_so = list(self.linker_so)\n                i = self.linker_so.index('-bundle')\n                self.linker_so[i] = '-dynamiclib'\n            return old_link_shared_object(self, *args, **kwds)\n        old_link_shared_object = _patch_meth(patchlist, CCompiler,\n                                             'link_shared_object',\n                                             my_link_shared_object)\n\ndef _patch_for_target(patchlist, target):\n    from distutils.command.build_ext import build_ext\n    # if 'target' is different from '*', we need to patch some internal\n    # method to just return this 'target' value, instead of having it\n    # built from module_name\n    if target.endswith('.*'):\n        target = target[:-2]\n        if sys.platform == 'win32':\n            target += '.dll'\n        elif sys.platform == 'darwin':\n            target += '.dylib'\n        else:\n            target += '.so'\n    _patch_meth(patchlist, build_ext, 'get_ext_filename',\n                lambda self, ext_name: target)\n\n\ndef recompile(ffi, module_name, preamble, tmpdir='.', call_c_compiler=True,\n              c_file=None, source_extension='.c', extradir=None,\n              compiler_verbose=1, target=None, debug=None, **kwds):\n    if not isinstance(module_name, str):\n        module_name = module_name.encode('ascii')\n    if ffi._windows_unicode:\n        ffi._apply_windows_unicode(kwds)\n    if preamble is not None:\n        embedding = (ffi._embedding is not None)\n        if embedding:\n            ffi._apply_embedding_fix(kwds)\n        if c_file is None:\n            c_file, parts = _modname_to_file(tmpdir, module_name,\n                                             source_extension)\n            if extradir:\n                parts = [extradir] + parts\n            ext_c_file = os.path.join(*parts)\n        else:\n            ext_c_file = c_file\n        #\n        if target is None:\n            if embedding:\n                target = '%s.*' % module_name\n            else:\n                target = '*'\n        #\n        ext = ffiplatform.get_extension(ext_c_file, module_name, **kwds)\n        updated = make_c_source(ffi, module_name, preamble, c_file,\n                                verbose=compiler_verbose)\n        if call_c_compiler:\n            patchlist = []\n            cwd = os.getcwd()\n            try:\n                if embedding:\n                    _patch_for_embedding(patchlist)\n                if target != '*':\n                    _patch_for_target(patchlist, target)\n                if compiler_verbose:\n                    if tmpdir == '.':\n                        msg = 'the current directory is'\n                    else:\n                        msg = 'setting the current directory to'\n                    print('%s %r' % (msg, os.path.abspath(tmpdir)))\n                os.chdir(tmpdir)\n                outputfilename = ffiplatform.compile('.', ext,\n                                                     compiler_verbose, debug)\n            finally:\n                os.chdir(cwd)\n                _unpatch_meths(patchlist)\n            return outputfilename\n        else:\n            return ext, updated\n    else:\n        if c_file is None:\n            c_file, _ = _modname_to_file(tmpdir, module_name, '.py')\n        updated = make_py_source(ffi, module_name, c_file,\n                                 verbose=compiler_verbose)\n        if call_c_compiler:\n            return c_file\n        else:\n            return None, updated\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/setuptools_ext.py",
    "content": "import os\nimport sys\n\ntry:\n    basestring\nexcept NameError:\n    # Python 3.x\n    basestring = str\n\ndef error(msg):\n    from distutils.errors import DistutilsSetupError\n    raise DistutilsSetupError(msg)\n\n\ndef execfile(filename, glob):\n    # We use execfile() (here rewritten for Python 3) instead of\n    # __import__() to load the build script.  The problem with\n    # a normal import is that in some packages, the intermediate\n    # __init__.py files may already try to import the file that\n    # we are generating.\n    with open(filename) as f:\n        src = f.read()\n    src += '\\n'      # Python 2.6 compatibility\n    code = compile(src, filename, 'exec')\n    exec(code, glob, glob)\n\n\ndef add_cffi_module(dist, mod_spec):\n    from cffi.api import FFI\n\n    if not isinstance(mod_spec, basestring):\n        error(\"argument to 'cffi_modules=...' must be a str or a list of str,\"\n              \" not %r\" % (type(mod_spec).__name__,))\n    mod_spec = str(mod_spec)\n    try:\n        build_file_name, ffi_var_name = mod_spec.split(':')\n    except ValueError:\n        error(\"%r must be of the form 'path/build.py:ffi_variable'\" %\n              (mod_spec,))\n    if not os.path.exists(build_file_name):\n        ext = ''\n        rewritten = build_file_name.replace('.', '/') + '.py'\n        if os.path.exists(rewritten):\n            ext = ' (rewrite cffi_modules to [%r])' % (\n                rewritten + ':' + ffi_var_name,)\n        error(\"%r does not name an existing file%s\" % (build_file_name, ext))\n\n    mod_vars = {'__name__': '__cffi__', '__file__': build_file_name}\n    execfile(build_file_name, mod_vars)\n\n    try:\n        ffi = mod_vars[ffi_var_name]\n    except KeyError:\n        error(\"%r: object %r not found in module\" % (mod_spec,\n                                                     ffi_var_name))\n    if not isinstance(ffi, FFI):\n        ffi = ffi()      # maybe it's a function instead of directly an ffi\n    if not isinstance(ffi, FFI):\n        error(\"%r is not an FFI instance (got %r)\" % (mod_spec,\n                                                      type(ffi).__name__))\n    if not hasattr(ffi, '_assigned_source'):\n        error(\"%r: the set_source() method was not called\" % (mod_spec,))\n    module_name, source, source_extension, kwds = ffi._assigned_source\n    if ffi._windows_unicode:\n        kwds = kwds.copy()\n        ffi._apply_windows_unicode(kwds)\n\n    if source is None:\n        _add_py_module(dist, ffi, module_name)\n    else:\n        _add_c_module(dist, ffi, module_name, source, source_extension, kwds)\n\ndef _set_py_limited_api(Extension, kwds):\n    \"\"\"\n    Add py_limited_api to kwds if setuptools >= 26 is in use.\n    Do not alter the setting if it already exists.\n    Setuptools takes care of ignoring the flag on Python 2 and PyPy.\n\n    CPython itself should ignore the flag in a debugging version\n    (by not listing .abi3.so in the extensions it supports), but\n    it doesn't so far, creating troubles.  That's why we check\n    for \"not hasattr(sys, 'gettotalrefcount')\" (the 2.7 compatible equivalent\n    of 'd' not in sys.abiflags). (http://bugs.python.org/issue28401)\n\n    On Windows, with CPython <= 3.4, it's better not to use py_limited_api\n    because virtualenv *still* doesn't copy PYTHON3.DLL on these versions.\n    For now we'll skip py_limited_api on all Windows versions to avoid an\n    inconsistent mess.\n    \"\"\"\n    if ('py_limited_api' not in kwds and not hasattr(sys, 'gettotalrefcount')\n            and sys.platform != 'win32'):\n        import setuptools\n        try:\n            setuptools_major_version = int(setuptools.__version__.partition('.')[0])\n            if setuptools_major_version >= 26:\n                kwds['py_limited_api'] = True\n        except ValueError:  # certain development versions of setuptools\n            # If we don't know the version number of setuptools, we\n            # try to set 'py_limited_api' anyway.  At worst, we get a\n            # warning.\n            kwds['py_limited_api'] = True\n    return kwds\n\ndef _add_c_module(dist, ffi, module_name, source, source_extension, kwds):\n    from distutils.core import Extension\n    # We are a setuptools extension. Need this build_ext for py_limited_api.\n    from setuptools.command.build_ext import build_ext\n    from distutils.dir_util import mkpath\n    from distutils import log\n    from cffi import recompiler\n\n    allsources = ['$PLACEHOLDER']\n    allsources.extend(kwds.pop('sources', []))\n    kwds = _set_py_limited_api(Extension, kwds)\n    ext = Extension(name=module_name, sources=allsources, **kwds)\n\n    def make_mod(tmpdir, pre_run=None):\n        c_file = os.path.join(tmpdir, module_name + source_extension)\n        log.info(\"generating cffi module %r\" % c_file)\n        mkpath(tmpdir)\n        # a setuptools-only, API-only hook: called with the \"ext\" and \"ffi\"\n        # arguments just before we turn the ffi into C code.  To use it,\n        # subclass the 'distutils.command.build_ext.build_ext' class and\n        # add a method 'def pre_run(self, ext, ffi)'.\n        if pre_run is not None:\n            pre_run(ext, ffi)\n        updated = recompiler.make_c_source(ffi, module_name, source, c_file)\n        if not updated:\n            log.info(\"already up-to-date\")\n        return c_file\n\n    if dist.ext_modules is None:\n        dist.ext_modules = []\n    dist.ext_modules.append(ext)\n\n    base_class = dist.cmdclass.get('build_ext', build_ext)\n    class build_ext_make_mod(base_class):\n        def run(self):\n            if ext.sources[0] == '$PLACEHOLDER':\n                pre_run = getattr(self, 'pre_run', None)\n                ext.sources[0] = make_mod(self.build_temp, pre_run)\n            base_class.run(self)\n    dist.cmdclass['build_ext'] = build_ext_make_mod\n    # NB. multiple runs here will create multiple 'build_ext_make_mod'\n    # classes.  Even in this case the 'build_ext' command should be\n    # run once; but just in case, the logic above does nothing if\n    # called again.\n\n\ndef _add_py_module(dist, ffi, module_name):\n    from distutils.dir_util import mkpath\n    from setuptools.command.build_py import build_py\n    from setuptools.command.build_ext import build_ext\n    from distutils import log\n    from cffi import recompiler\n\n    def generate_mod(py_file):\n        log.info(\"generating cffi module %r\" % py_file)\n        mkpath(os.path.dirname(py_file))\n        updated = recompiler.make_py_source(ffi, module_name, py_file)\n        if not updated:\n            log.info(\"already up-to-date\")\n\n    base_class = dist.cmdclass.get('build_py', build_py)\n    class build_py_make_mod(base_class):\n        def run(self):\n            base_class.run(self)\n            module_path = module_name.split('.')\n            module_path[-1] += '.py'\n            generate_mod(os.path.join(self.build_lib, *module_path))\n        def get_source_files(self):\n            # This is called from 'setup.py sdist' only.  Exclude\n            # the generate .py module in this case.\n            saved_py_modules = self.py_modules\n            try:\n                if saved_py_modules:\n                    self.py_modules = [m for m in saved_py_modules\n                                         if m != module_name]\n                return base_class.get_source_files(self)\n            finally:\n                self.py_modules = saved_py_modules\n    dist.cmdclass['build_py'] = build_py_make_mod\n\n    # distutils and setuptools have no notion I could find of a\n    # generated python module.  If we don't add module_name to\n    # dist.py_modules, then things mostly work but there are some\n    # combination of options (--root and --record) that will miss\n    # the module.  So we add it here, which gives a few apparently\n    # harmless warnings about not finding the file outside the\n    # build directory.\n    # Then we need to hack more in get_source_files(); see above.\n    if dist.py_modules is None:\n        dist.py_modules = []\n    dist.py_modules.append(module_name)\n\n    # the following is only for \"build_ext -i\"\n    base_class_2 = dist.cmdclass.get('build_ext', build_ext)\n    class build_ext_make_mod(base_class_2):\n        def run(self):\n            base_class_2.run(self)\n            if self.inplace:\n                # from get_ext_fullpath() in distutils/command/build_ext.py\n                module_path = module_name.split('.')\n                package = '.'.join(module_path[:-1])\n                build_py = self.get_finalized_command('build_py')\n                package_dir = build_py.get_package_dir(package)\n                file_name = module_path[-1] + '.py'\n                generate_mod(os.path.join(package_dir, file_name))\n    dist.cmdclass['build_ext'] = build_ext_make_mod\n\ndef cffi_modules(dist, attr, value):\n    assert attr == 'cffi_modules'\n    if isinstance(value, basestring):\n        value = [value]\n\n    for cffi_module in value:\n        add_cffi_module(dist, cffi_module)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/vengine_cpy.py",
    "content": "#\n# DEPRECATED: implementation for ffi.verify()\n#\nimport sys, imp\nfrom . import model\nfrom .error import VerificationError\n\n\nclass VCPythonEngine(object):\n    _class_key = 'x'\n    _gen_python_module = True\n\n    def __init__(self, verifier):\n        self.verifier = verifier\n        self.ffi = verifier.ffi\n        self._struct_pending_verification = {}\n        self._types_of_builtin_functions = {}\n\n    def patch_extension_kwds(self, kwds):\n        pass\n\n    def find_module(self, module_name, path, so_suffixes):\n        try:\n            f, filename, descr = imp.find_module(module_name, path)\n        except ImportError:\n            return None\n        if f is not None:\n            f.close()\n        # Note that after a setuptools installation, there are both .py\n        # and .so files with the same basename.  The code here relies on\n        # imp.find_module() locating the .so in priority.\n        if descr[0] not in so_suffixes:\n            return None\n        return filename\n\n    def collect_types(self):\n        self._typesdict = {}\n        self._generate(\"collecttype\")\n\n    def _prnt(self, what=''):\n        self._f.write(what + '\\n')\n\n    def _gettypenum(self, type):\n        # a KeyError here is a bug.  please report it! :-)\n        return self._typesdict[type]\n\n    def _do_collect_type(self, tp):\n        if ((not isinstance(tp, model.PrimitiveType)\n             or tp.name == 'long double')\n                and tp not in self._typesdict):\n            num = len(self._typesdict)\n            self._typesdict[tp] = num\n\n    def write_source_to_f(self):\n        self.collect_types()\n        #\n        # The new module will have a _cffi_setup() function that receives\n        # objects from the ffi world, and that calls some setup code in\n        # the module.  This setup code is split in several independent\n        # functions, e.g. one per constant.  The functions are \"chained\"\n        # by ending in a tail call to each other.\n        #\n        # This is further split in two chained lists, depending on if we\n        # can do it at import-time or if we must wait for _cffi_setup() to\n        # provide us with the <ctype> objects.  This is needed because we\n        # need the values of the enum constants in order to build the\n        # <ctype 'enum'> that we may have to pass to _cffi_setup().\n        #\n        # The following two 'chained_list_constants' items contains\n        # the head of these two chained lists, as a string that gives the\n        # call to do, if any.\n        self._chained_list_constants = ['((void)lib,0)', '((void)lib,0)']\n        #\n        prnt = self._prnt\n        # first paste some standard set of lines that are mostly '#define'\n        prnt(cffimod_header)\n        prnt()\n        # then paste the C source given by the user, verbatim.\n        prnt(self.verifier.preamble)\n        prnt()\n        #\n        # call generate_cpy_xxx_decl(), for every xxx found from\n        # ffi._parser._declarations.  This generates all the functions.\n        self._generate(\"decl\")\n        #\n        # implement the function _cffi_setup_custom() as calling the\n        # head of the chained list.\n        self._generate_setup_custom()\n        prnt()\n        #\n        # produce the method table, including the entries for the\n        # generated Python->C function wrappers, which are done\n        # by generate_cpy_function_method().\n        prnt('static PyMethodDef _cffi_methods[] = {')\n        self._generate(\"method\")\n        prnt('  {\"_cffi_setup\", _cffi_setup, METH_VARARGS, NULL},')\n        prnt('  {NULL, NULL, 0, NULL}    /* Sentinel */')\n        prnt('};')\n        prnt()\n        #\n        # standard init.\n        modname = self.verifier.get_module_name()\n        constants = self._chained_list_constants[False]\n        prnt('#if PY_MAJOR_VERSION >= 3')\n        prnt()\n        prnt('static struct PyModuleDef _cffi_module_def = {')\n        prnt('  PyModuleDef_HEAD_INIT,')\n        prnt('  \"%s\",' % modname)\n        prnt('  NULL,')\n        prnt('  -1,')\n        prnt('  _cffi_methods,')\n        prnt('  NULL, NULL, NULL, NULL')\n        prnt('};')\n        prnt()\n        prnt('PyMODINIT_FUNC')\n        prnt('PyInit_%s(void)' % modname)\n        prnt('{')\n        prnt('  PyObject *lib;')\n        prnt('  lib = PyModule_Create(&_cffi_module_def);')\n        prnt('  if (lib == NULL)')\n        prnt('    return NULL;')\n        prnt('  if (%s < 0 || _cffi_init() < 0) {' % (constants,))\n        prnt('    Py_DECREF(lib);')\n        prnt('    return NULL;')\n        prnt('  }')\n        prnt('  return lib;')\n        prnt('}')\n        prnt()\n        prnt('#else')\n        prnt()\n        prnt('PyMODINIT_FUNC')\n        prnt('init%s(void)' % modname)\n        prnt('{')\n        prnt('  PyObject *lib;')\n        prnt('  lib = Py_InitModule(\"%s\", _cffi_methods);' % modname)\n        prnt('  if (lib == NULL)')\n        prnt('    return;')\n        prnt('  if (%s < 0 || _cffi_init() < 0)' % (constants,))\n        prnt('    return;')\n        prnt('  return;')\n        prnt('}')\n        prnt()\n        prnt('#endif')\n\n    def load_library(self, flags=None):\n        # XXX review all usages of 'self' here!\n        # import it as a new extension module\n        imp.acquire_lock()\n        try:\n            if hasattr(sys, \"getdlopenflags\"):\n                previous_flags = sys.getdlopenflags()\n            try:\n                if hasattr(sys, \"setdlopenflags\") and flags is not None:\n                    sys.setdlopenflags(flags)\n                module = imp.load_dynamic(self.verifier.get_module_name(),\n                                          self.verifier.modulefilename)\n            except ImportError as e:\n                error = \"importing %r: %s\" % (self.verifier.modulefilename, e)\n                raise VerificationError(error)\n            finally:\n                if hasattr(sys, \"setdlopenflags\"):\n                    sys.setdlopenflags(previous_flags)\n        finally:\n            imp.release_lock()\n        #\n        # call loading_cpy_struct() to get the struct layout inferred by\n        # the C compiler\n        self._load(module, 'loading')\n        #\n        # the C code will need the <ctype> objects.  Collect them in\n        # order in a list.\n        revmapping = dict([(value, key)\n                           for (key, value) in self._typesdict.items()])\n        lst = [revmapping[i] for i in range(len(revmapping))]\n        lst = list(map(self.ffi._get_cached_btype, lst))\n        #\n        # build the FFILibrary class and instance and call _cffi_setup().\n        # this will set up some fields like '_cffi_types', and only then\n        # it will invoke the chained list of functions that will really\n        # build (notably) the constant objects, as <cdata> if they are\n        # pointers, and store them as attributes on the 'library' object.\n        class FFILibrary(object):\n            _cffi_python_module = module\n            _cffi_ffi = self.ffi\n            _cffi_dir = []\n            def __dir__(self):\n                return FFILibrary._cffi_dir + list(self.__dict__)\n        library = FFILibrary()\n        if module._cffi_setup(lst, VerificationError, library):\n            import warnings\n            warnings.warn(\"reimporting %r might overwrite older definitions\"\n                          % (self.verifier.get_module_name()))\n        #\n        # finally, call the loaded_cpy_xxx() functions.  This will perform\n        # the final adjustments, like copying the Python->C wrapper\n        # functions from the module to the 'library' object, and setting\n        # up the FFILibrary class with properties for the global C variables.\n        self._load(module, 'loaded', library=library)\n        module._cffi_original_ffi = self.ffi\n        module._cffi_types_of_builtin_funcs = self._types_of_builtin_functions\n        return library\n\n    def _get_declarations(self):\n        lst = [(key, tp) for (key, (tp, qual)) in\n                                self.ffi._parser._declarations.items()]\n        lst.sort()\n        return lst\n\n    def _generate(self, step_name):\n        for name, tp in self._get_declarations():\n            kind, realname = name.split(' ', 1)\n            try:\n                method = getattr(self, '_generate_cpy_%s_%s' % (kind,\n                                                                step_name))\n            except AttributeError:\n                raise VerificationError(\n                    \"not implemented in verify(): %r\" % name)\n            try:\n                method(tp, realname)\n            except Exception as e:\n                model.attach_exception_info(e, name)\n                raise\n\n    def _load(self, module, step_name, **kwds):\n        for name, tp in self._get_declarations():\n            kind, realname = name.split(' ', 1)\n            method = getattr(self, '_%s_cpy_%s' % (step_name, kind))\n            try:\n                method(tp, realname, module, **kwds)\n            except Exception as e:\n                model.attach_exception_info(e, name)\n                raise\n\n    def _generate_nothing(self, tp, name):\n        pass\n\n    def _loaded_noop(self, tp, name, module, **kwds):\n        pass\n\n    # ----------\n\n    def _convert_funcarg_to_c(self, tp, fromvar, tovar, errcode):\n        extraarg = ''\n        if isinstance(tp, model.PrimitiveType):\n            if tp.is_integer_type() and tp.name != '_Bool':\n                converter = '_cffi_to_c_int'\n                extraarg = ', %s' % tp.name\n            else:\n                converter = '(%s)_cffi_to_c_%s' % (tp.get_c_name(''),\n                                                   tp.name.replace(' ', '_'))\n            errvalue = '-1'\n        #\n        elif isinstance(tp, model.PointerType):\n            self._convert_funcarg_to_c_ptr_or_array(tp, fromvar,\n                                                    tovar, errcode)\n            return\n        #\n        elif isinstance(tp, (model.StructOrUnion, model.EnumType)):\n            # a struct (not a struct pointer) as a function argument\n            self._prnt('  if (_cffi_to_c((char *)&%s, _cffi_type(%d), %s) < 0)'\n                      % (tovar, self._gettypenum(tp), fromvar))\n            self._prnt('    %s;' % errcode)\n            return\n        #\n        elif isinstance(tp, model.FunctionPtrType):\n            converter = '(%s)_cffi_to_c_pointer' % tp.get_c_name('')\n            extraarg = ', _cffi_type(%d)' % self._gettypenum(tp)\n            errvalue = 'NULL'\n        #\n        else:\n            raise NotImplementedError(tp)\n        #\n        self._prnt('  %s = %s(%s%s);' % (tovar, converter, fromvar, extraarg))\n        self._prnt('  if (%s == (%s)%s && PyErr_Occurred())' % (\n            tovar, tp.get_c_name(''), errvalue))\n        self._prnt('    %s;' % errcode)\n\n    def _extra_local_variables(self, tp, localvars):\n        if isinstance(tp, model.PointerType):\n            localvars.add('Py_ssize_t datasize')\n\n    def _convert_funcarg_to_c_ptr_or_array(self, tp, fromvar, tovar, errcode):\n        self._prnt('  datasize = _cffi_prepare_pointer_call_argument(')\n        self._prnt('      _cffi_type(%d), %s, (char **)&%s);' % (\n            self._gettypenum(tp), fromvar, tovar))\n        self._prnt('  if (datasize != 0) {')\n        self._prnt('    if (datasize < 0)')\n        self._prnt('      %s;' % errcode)\n        self._prnt('    %s = alloca((size_t)datasize);' % (tovar,))\n        self._prnt('    memset((void *)%s, 0, (size_t)datasize);' % (tovar,))\n        self._prnt('    if (_cffi_convert_array_from_object('\n                   '(char *)%s, _cffi_type(%d), %s) < 0)' % (\n            tovar, self._gettypenum(tp), fromvar))\n        self._prnt('      %s;' % errcode)\n        self._prnt('  }')\n\n    def _convert_expr_from_c(self, tp, var, context):\n        if isinstance(tp, model.PrimitiveType):\n            if tp.is_integer_type() and tp.name != '_Bool':\n                return '_cffi_from_c_int(%s, %s)' % (var, tp.name)\n            elif tp.name != 'long double':\n                return '_cffi_from_c_%s(%s)' % (tp.name.replace(' ', '_'), var)\n            else:\n                return '_cffi_from_c_deref((char *)&%s, _cffi_type(%d))' % (\n                    var, self._gettypenum(tp))\n        elif isinstance(tp, (model.PointerType, model.FunctionPtrType)):\n            return '_cffi_from_c_pointer((char *)%s, _cffi_type(%d))' % (\n                var, self._gettypenum(tp))\n        elif isinstance(tp, model.ArrayType):\n            return '_cffi_from_c_pointer((char *)%s, _cffi_type(%d))' % (\n                var, self._gettypenum(model.PointerType(tp.item)))\n        elif isinstance(tp, model.StructOrUnion):\n            if tp.fldnames is None:\n                raise TypeError(\"'%s' is used as %s, but is opaque\" % (\n                    tp._get_c_name(), context))\n            return '_cffi_from_c_struct((char *)&%s, _cffi_type(%d))' % (\n                var, self._gettypenum(tp))\n        elif isinstance(tp, model.EnumType):\n            return '_cffi_from_c_deref((char *)&%s, _cffi_type(%d))' % (\n                var, self._gettypenum(tp))\n        else:\n            raise NotImplementedError(tp)\n\n    # ----------\n    # typedefs: generates no code so far\n\n    _generate_cpy_typedef_collecttype = _generate_nothing\n    _generate_cpy_typedef_decl   = _generate_nothing\n    _generate_cpy_typedef_method = _generate_nothing\n    _loading_cpy_typedef         = _loaded_noop\n    _loaded_cpy_typedef          = _loaded_noop\n\n    # ----------\n    # function declarations\n\n    def _generate_cpy_function_collecttype(self, tp, name):\n        assert isinstance(tp, model.FunctionPtrType)\n        if tp.ellipsis:\n            self._do_collect_type(tp)\n        else:\n            # don't call _do_collect_type(tp) in this common case,\n            # otherwise test_autofilled_struct_as_argument fails\n            for type in tp.args:\n                self._do_collect_type(type)\n            self._do_collect_type(tp.result)\n\n    def _generate_cpy_function_decl(self, tp, name):\n        assert isinstance(tp, model.FunctionPtrType)\n        if tp.ellipsis:\n            # cannot support vararg functions better than this: check for its\n            # exact type (including the fixed arguments), and build it as a\n            # constant function pointer (no CPython wrapper)\n            self._generate_cpy_const(False, name, tp)\n            return\n        prnt = self._prnt\n        numargs = len(tp.args)\n        if numargs == 0:\n            argname = 'noarg'\n        elif numargs == 1:\n            argname = 'arg0'\n        else:\n            argname = 'args'\n        prnt('static PyObject *')\n        prnt('_cffi_f_%s(PyObject *self, PyObject *%s)' % (name, argname))\n        prnt('{')\n        #\n        context = 'argument of %s' % name\n        for i, type in enumerate(tp.args):\n            prnt('  %s;' % type.get_c_name(' x%d' % i, context))\n        #\n        localvars = set()\n        for type in tp.args:\n            self._extra_local_variables(type, localvars)\n        for decl in localvars:\n            prnt('  %s;' % (decl,))\n        #\n        if not isinstance(tp.result, model.VoidType):\n            result_code = 'result = '\n            context = 'result of %s' % name\n            prnt('  %s;' % tp.result.get_c_name(' result', context))\n        else:\n            result_code = ''\n        #\n        if len(tp.args) > 1:\n            rng = range(len(tp.args))\n            for i in rng:\n                prnt('  PyObject *arg%d;' % i)\n            prnt()\n            prnt('  if (!PyArg_ParseTuple(args, \"%s:%s\", %s))' % (\n                'O' * numargs, name, ', '.join(['&arg%d' % i for i in rng])))\n            prnt('    return NULL;')\n        prnt()\n        #\n        for i, type in enumerate(tp.args):\n            self._convert_funcarg_to_c(type, 'arg%d' % i, 'x%d' % i,\n                                       'return NULL')\n            prnt()\n        #\n        prnt('  Py_BEGIN_ALLOW_THREADS')\n        prnt('  _cffi_restore_errno();')\n        prnt('  { %s%s(%s); }' % (\n            result_code, name,\n            ', '.join(['x%d' % i for i in range(len(tp.args))])))\n        prnt('  _cffi_save_errno();')\n        prnt('  Py_END_ALLOW_THREADS')\n        prnt()\n        #\n        prnt('  (void)self; /* unused */')\n        if numargs == 0:\n            prnt('  (void)noarg; /* unused */')\n        if result_code:\n            prnt('  return %s;' %\n                 self._convert_expr_from_c(tp.result, 'result', 'result type'))\n        else:\n            prnt('  Py_INCREF(Py_None);')\n            prnt('  return Py_None;')\n        prnt('}')\n        prnt()\n\n    def _generate_cpy_function_method(self, tp, name):\n        if tp.ellipsis:\n            return\n        numargs = len(tp.args)\n        if numargs == 0:\n            meth = 'METH_NOARGS'\n        elif numargs == 1:\n            meth = 'METH_O'\n        else:\n            meth = 'METH_VARARGS'\n        self._prnt('  {\"%s\", _cffi_f_%s, %s, NULL},' % (name, name, meth))\n\n    _loading_cpy_function = _loaded_noop\n\n    def _loaded_cpy_function(self, tp, name, module, library):\n        if tp.ellipsis:\n            return\n        func = getattr(module, name)\n        setattr(library, name, func)\n        self._types_of_builtin_functions[func] = tp\n\n    # ----------\n    # named structs\n\n    _generate_cpy_struct_collecttype = _generate_nothing\n    def _generate_cpy_struct_decl(self, tp, name):\n        assert name == tp.name\n        self._generate_struct_or_union_decl(tp, 'struct', name)\n    def _generate_cpy_struct_method(self, tp, name):\n        self._generate_struct_or_union_method(tp, 'struct', name)\n    def _loading_cpy_struct(self, tp, name, module):\n        self._loading_struct_or_union(tp, 'struct', name, module)\n    def _loaded_cpy_struct(self, tp, name, module, **kwds):\n        self._loaded_struct_or_union(tp)\n\n    _generate_cpy_union_collecttype = _generate_nothing\n    def _generate_cpy_union_decl(self, tp, name):\n        assert name == tp.name\n        self._generate_struct_or_union_decl(tp, 'union', name)\n    def _generate_cpy_union_method(self, tp, name):\n        self._generate_struct_or_union_method(tp, 'union', name)\n    def _loading_cpy_union(self, tp, name, module):\n        self._loading_struct_or_union(tp, 'union', name, module)\n    def _loaded_cpy_union(self, tp, name, module, **kwds):\n        self._loaded_struct_or_union(tp)\n\n    def _generate_struct_or_union_decl(self, tp, prefix, name):\n        if tp.fldnames is None:\n            return     # nothing to do with opaque structs\n        checkfuncname = '_cffi_check_%s_%s' % (prefix, name)\n        layoutfuncname = '_cffi_layout_%s_%s' % (prefix, name)\n        cname = ('%s %s' % (prefix, name)).strip()\n        #\n        prnt = self._prnt\n        prnt('static void %s(%s *p)' % (checkfuncname, cname))\n        prnt('{')\n        prnt('  /* only to generate compile-time warnings or errors */')\n        prnt('  (void)p;')\n        for fname, ftype, fbitsize, fqual in tp.enumfields():\n            if (isinstance(ftype, model.PrimitiveType)\n                and ftype.is_integer_type()) or fbitsize >= 0:\n                # accept all integers, but complain on float or double\n                prnt('  (void)((p->%s) << 1);' % fname)\n            else:\n                # only accept exactly the type declared.\n                try:\n                    prnt('  { %s = &p->%s; (void)tmp; }' % (\n                        ftype.get_c_name('*tmp', 'field %r'%fname, quals=fqual),\n                        fname))\n                except VerificationError as e:\n                    prnt('  /* %s */' % str(e))   # cannot verify it, ignore\n        prnt('}')\n        prnt('static PyObject *')\n        prnt('%s(PyObject *self, PyObject *noarg)' % (layoutfuncname,))\n        prnt('{')\n        prnt('  struct _cffi_aligncheck { char x; %s y; };' % cname)\n        prnt('  static Py_ssize_t nums[] = {')\n        prnt('    sizeof(%s),' % cname)\n        prnt('    offsetof(struct _cffi_aligncheck, y),')\n        for fname, ftype, fbitsize, fqual in tp.enumfields():\n            if fbitsize >= 0:\n                continue      # xxx ignore fbitsize for now\n            prnt('    offsetof(%s, %s),' % (cname, fname))\n            if isinstance(ftype, model.ArrayType) and ftype.length is None:\n                prnt('    0,  /* %s */' % ftype._get_c_name())\n            else:\n                prnt('    sizeof(((%s *)0)->%s),' % (cname, fname))\n        prnt('    -1')\n        prnt('  };')\n        prnt('  (void)self; /* unused */')\n        prnt('  (void)noarg; /* unused */')\n        prnt('  return _cffi_get_struct_layout(nums);')\n        prnt('  /* the next line is not executed, but compiled */')\n        prnt('  %s(0);' % (checkfuncname,))\n        prnt('}')\n        prnt()\n\n    def _generate_struct_or_union_method(self, tp, prefix, name):\n        if tp.fldnames is None:\n            return     # nothing to do with opaque structs\n        layoutfuncname = '_cffi_layout_%s_%s' % (prefix, name)\n        self._prnt('  {\"%s\", %s, METH_NOARGS, NULL},' % (layoutfuncname,\n                                                         layoutfuncname))\n\n    def _loading_struct_or_union(self, tp, prefix, name, module):\n        if tp.fldnames is None:\n            return     # nothing to do with opaque structs\n        layoutfuncname = '_cffi_layout_%s_%s' % (prefix, name)\n        #\n        function = getattr(module, layoutfuncname)\n        layout = function()\n        if isinstance(tp, model.StructOrUnion) and tp.partial:\n            # use the function()'s sizes and offsets to guide the\n            # layout of the struct\n            totalsize = layout[0]\n            totalalignment = layout[1]\n            fieldofs = layout[2::2]\n            fieldsize = layout[3::2]\n            tp.force_flatten()\n            assert len(fieldofs) == len(fieldsize) == len(tp.fldnames)\n            tp.fixedlayout = fieldofs, fieldsize, totalsize, totalalignment\n        else:\n            cname = ('%s %s' % (prefix, name)).strip()\n            self._struct_pending_verification[tp] = layout, cname\n\n    def _loaded_struct_or_union(self, tp):\n        if tp.fldnames is None:\n            return     # nothing to do with opaque structs\n        self.ffi._get_cached_btype(tp)   # force 'fixedlayout' to be considered\n\n        if tp in self._struct_pending_verification:\n            # check that the layout sizes and offsets match the real ones\n            def check(realvalue, expectedvalue, msg):\n                if realvalue != expectedvalue:\n                    raise VerificationError(\n                        \"%s (we have %d, but C compiler says %d)\"\n                        % (msg, expectedvalue, realvalue))\n            ffi = self.ffi\n            BStruct = ffi._get_cached_btype(tp)\n            layout, cname = self._struct_pending_verification.pop(tp)\n            check(layout[0], ffi.sizeof(BStruct), \"wrong total size\")\n            check(layout[1], ffi.alignof(BStruct), \"wrong total alignment\")\n            i = 2\n            for fname, ftype, fbitsize, fqual in tp.enumfields():\n                if fbitsize >= 0:\n                    continue        # xxx ignore fbitsize for now\n                check(layout[i], ffi.offsetof(BStruct, fname),\n                      \"wrong offset for field %r\" % (fname,))\n                if layout[i+1] != 0:\n                    BField = ffi._get_cached_btype(ftype)\n                    check(layout[i+1], ffi.sizeof(BField),\n                          \"wrong size for field %r\" % (fname,))\n                i += 2\n            assert i == len(layout)\n\n    # ----------\n    # 'anonymous' declarations.  These are produced for anonymous structs\n    # or unions; the 'name' is obtained by a typedef.\n\n    _generate_cpy_anonymous_collecttype = _generate_nothing\n\n    def _generate_cpy_anonymous_decl(self, tp, name):\n        if isinstance(tp, model.EnumType):\n            self._generate_cpy_enum_decl(tp, name, '')\n        else:\n            self._generate_struct_or_union_decl(tp, '', name)\n\n    def _generate_cpy_anonymous_method(self, tp, name):\n        if not isinstance(tp, model.EnumType):\n            self._generate_struct_or_union_method(tp, '', name)\n\n    def _loading_cpy_anonymous(self, tp, name, module):\n        if isinstance(tp, model.EnumType):\n            self._loading_cpy_enum(tp, name, module)\n        else:\n            self._loading_struct_or_union(tp, '', name, module)\n\n    def _loaded_cpy_anonymous(self, tp, name, module, **kwds):\n        if isinstance(tp, model.EnumType):\n            self._loaded_cpy_enum(tp, name, module, **kwds)\n        else:\n            self._loaded_struct_or_union(tp)\n\n    # ----------\n    # constants, likely declared with '#define'\n\n    def _generate_cpy_const(self, is_int, name, tp=None, category='const',\n                            vartp=None, delayed=True, size_too=False,\n                            check_value=None):\n        prnt = self._prnt\n        funcname = '_cffi_%s_%s' % (category, name)\n        prnt('static int %s(PyObject *lib)' % funcname)\n        prnt('{')\n        prnt('  PyObject *o;')\n        prnt('  int res;')\n        if not is_int:\n            prnt('  %s;' % (vartp or tp).get_c_name(' i', name))\n        else:\n            assert category == 'const'\n        #\n        if check_value is not None:\n            self._check_int_constant_value(name, check_value)\n        #\n        if not is_int:\n            if category == 'var':\n                realexpr = '&' + name\n            else:\n                realexpr = name\n            prnt('  i = (%s);' % (realexpr,))\n            prnt('  o = %s;' % (self._convert_expr_from_c(tp, 'i',\n                                                          'variable type'),))\n            assert delayed\n        else:\n            prnt('  o = _cffi_from_c_int_const(%s);' % name)\n        prnt('  if (o == NULL)')\n        prnt('    return -1;')\n        if size_too:\n            prnt('  {')\n            prnt('    PyObject *o1 = o;')\n            prnt('    o = Py_BuildValue(\"On\", o1, (Py_ssize_t)sizeof(%s));'\n                 % (name,))\n            prnt('    Py_DECREF(o1);')\n            prnt('    if (o == NULL)')\n            prnt('      return -1;')\n            prnt('  }')\n        prnt('  res = PyObject_SetAttrString(lib, \"%s\", o);' % name)\n        prnt('  Py_DECREF(o);')\n        prnt('  if (res < 0)')\n        prnt('    return -1;')\n        prnt('  return %s;' % self._chained_list_constants[delayed])\n        self._chained_list_constants[delayed] = funcname + '(lib)'\n        prnt('}')\n        prnt()\n\n    def _generate_cpy_constant_collecttype(self, tp, name):\n        is_int = isinstance(tp, model.PrimitiveType) and tp.is_integer_type()\n        if not is_int:\n            self._do_collect_type(tp)\n\n    def _generate_cpy_constant_decl(self, tp, name):\n        is_int = isinstance(tp, model.PrimitiveType) and tp.is_integer_type()\n        self._generate_cpy_const(is_int, name, tp)\n\n    _generate_cpy_constant_method = _generate_nothing\n    _loading_cpy_constant = _loaded_noop\n    _loaded_cpy_constant  = _loaded_noop\n\n    # ----------\n    # enums\n\n    def _check_int_constant_value(self, name, value, err_prefix=''):\n        prnt = self._prnt\n        if value <= 0:\n            prnt('  if ((%s) > 0 || (long)(%s) != %dL) {' % (\n                name, name, value))\n        else:\n            prnt('  if ((%s) <= 0 || (unsigned long)(%s) != %dUL) {' % (\n                name, name, value))\n        prnt('    char buf[64];')\n        prnt('    if ((%s) <= 0)' % name)\n        prnt('        snprintf(buf, 63, \"%%ld\", (long)(%s));' % name)\n        prnt('    else')\n        prnt('        snprintf(buf, 63, \"%%lu\", (unsigned long)(%s));' %\n             name)\n        prnt('    PyErr_Format(_cffi_VerificationError,')\n        prnt('                 \"%s%s has the real value %s, not %s\",')\n        prnt('                 \"%s\", \"%s\", buf, \"%d\");' % (\n            err_prefix, name, value))\n        prnt('    return -1;')\n        prnt('  }')\n\n    def _enum_funcname(self, prefix, name):\n        # \"$enum_$1\" => \"___D_enum____D_1\"\n        name = name.replace('$', '___D_')\n        return '_cffi_e_%s_%s' % (prefix, name)\n\n    def _generate_cpy_enum_decl(self, tp, name, prefix='enum'):\n        if tp.partial:\n            for enumerator in tp.enumerators:\n                self._generate_cpy_const(True, enumerator, delayed=False)\n            return\n        #\n        funcname = self._enum_funcname(prefix, name)\n        prnt = self._prnt\n        prnt('static int %s(PyObject *lib)' % funcname)\n        prnt('{')\n        for enumerator, enumvalue in zip(tp.enumerators, tp.enumvalues):\n            self._check_int_constant_value(enumerator, enumvalue,\n                                           \"enum %s: \" % name)\n        prnt('  return %s;' % self._chained_list_constants[True])\n        self._chained_list_constants[True] = funcname + '(lib)'\n        prnt('}')\n        prnt()\n\n    _generate_cpy_enum_collecttype = _generate_nothing\n    _generate_cpy_enum_method = _generate_nothing\n\n    def _loading_cpy_enum(self, tp, name, module):\n        if tp.partial:\n            enumvalues = [getattr(module, enumerator)\n                          for enumerator in tp.enumerators]\n            tp.enumvalues = tuple(enumvalues)\n            tp.partial_resolved = True\n\n    def _loaded_cpy_enum(self, tp, name, module, library):\n        for enumerator, enumvalue in zip(tp.enumerators, tp.enumvalues):\n            setattr(library, enumerator, enumvalue)\n\n    # ----------\n    # macros: for now only for integers\n\n    def _generate_cpy_macro_decl(self, tp, name):\n        if tp == '...':\n            check_value = None\n        else:\n            check_value = tp     # an integer\n        self._generate_cpy_const(True, name, check_value=check_value)\n\n    _generate_cpy_macro_collecttype = _generate_nothing\n    _generate_cpy_macro_method = _generate_nothing\n    _loading_cpy_macro = _loaded_noop\n    _loaded_cpy_macro  = _loaded_noop\n\n    # ----------\n    # global variables\n\n    def _generate_cpy_variable_collecttype(self, tp, name):\n        if isinstance(tp, model.ArrayType):\n            tp_ptr = model.PointerType(tp.item)\n        else:\n            tp_ptr = model.PointerType(tp)\n        self._do_collect_type(tp_ptr)\n\n    def _generate_cpy_variable_decl(self, tp, name):\n        if isinstance(tp, model.ArrayType):\n            tp_ptr = model.PointerType(tp.item)\n            self._generate_cpy_const(False, name, tp, vartp=tp_ptr,\n                                     size_too = (tp.length == '...'))\n        else:\n            tp_ptr = model.PointerType(tp)\n            self._generate_cpy_const(False, name, tp_ptr, category='var')\n\n    _generate_cpy_variable_method = _generate_nothing\n    _loading_cpy_variable = _loaded_noop\n\n    def _loaded_cpy_variable(self, tp, name, module, library):\n        value = getattr(library, name)\n        if isinstance(tp, model.ArrayType):   # int a[5] is \"constant\" in the\n                                              # sense that \"a=...\" is forbidden\n            if tp.length == '...':\n                assert isinstance(value, tuple)\n                (value, size) = value\n                BItemType = self.ffi._get_cached_btype(tp.item)\n                length, rest = divmod(size, self.ffi.sizeof(BItemType))\n                if rest != 0:\n                    raise VerificationError(\n                        \"bad size: %r does not seem to be an array of %s\" %\n                        (name, tp.item))\n                tp = tp.resolve_length(length)\n            # 'value' is a <cdata 'type *'> which we have to replace with\n            # a <cdata 'type[N]'> if the N is actually known\n            if tp.length is not None:\n                BArray = self.ffi._get_cached_btype(tp)\n                value = self.ffi.cast(BArray, value)\n                setattr(library, name, value)\n            return\n        # remove ptr=<cdata 'int *'> from the library instance, and replace\n        # it by a property on the class, which reads/writes into ptr[0].\n        ptr = value\n        delattr(library, name)\n        def getter(library):\n            return ptr[0]\n        def setter(library, value):\n            ptr[0] = value\n        setattr(type(library), name, property(getter, setter))\n        type(library)._cffi_dir.append(name)\n\n    # ----------\n\n    def _generate_setup_custom(self):\n        prnt = self._prnt\n        prnt('static int _cffi_setup_custom(PyObject *lib)')\n        prnt('{')\n        prnt('  return %s;' % self._chained_list_constants[True])\n        prnt('}')\n\ncffimod_header = r'''\n#include <Python.h>\n#include <stddef.h>\n\n/* this block of #ifs should be kept exactly identical between\n   c/_cffi_backend.c, cffi/vengine_cpy.py, cffi/vengine_gen.py\n   and cffi/_cffi_include.h */\n#if defined(_MSC_VER)\n# include <malloc.h>   /* for alloca() */\n# if _MSC_VER < 1600   /* MSVC < 2010 */\n   typedef __int8 int8_t;\n   typedef __int16 int16_t;\n   typedef __int32 int32_t;\n   typedef __int64 int64_t;\n   typedef unsigned __int8 uint8_t;\n   typedef unsigned __int16 uint16_t;\n   typedef unsigned __int32 uint32_t;\n   typedef unsigned __int64 uint64_t;\n   typedef __int8 int_least8_t;\n   typedef __int16 int_least16_t;\n   typedef __int32 int_least32_t;\n   typedef __int64 int_least64_t;\n   typedef unsigned __int8 uint_least8_t;\n   typedef unsigned __int16 uint_least16_t;\n   typedef unsigned __int32 uint_least32_t;\n   typedef unsigned __int64 uint_least64_t;\n   typedef __int8 int_fast8_t;\n   typedef __int16 int_fast16_t;\n   typedef __int32 int_fast32_t;\n   typedef __int64 int_fast64_t;\n   typedef unsigned __int8 uint_fast8_t;\n   typedef unsigned __int16 uint_fast16_t;\n   typedef unsigned __int32 uint_fast32_t;\n   typedef unsigned __int64 uint_fast64_t;\n   typedef __int64 intmax_t;\n   typedef unsigned __int64 uintmax_t;\n# else\n#  include <stdint.h>\n# endif\n# if _MSC_VER < 1800   /* MSVC < 2013 */\n#  ifndef __cplusplus\n    typedef unsigned char _Bool;\n#  endif\n# endif\n#else\n# include <stdint.h>\n# if (defined (__SVR4) && defined (__sun)) || defined(_AIX) || defined(__hpux)\n#  include <alloca.h>\n# endif\n#endif\n\n#if PY_MAJOR_VERSION < 3\n# undef PyCapsule_CheckExact\n# undef PyCapsule_GetPointer\n# define PyCapsule_CheckExact(capsule) (PyCObject_Check(capsule))\n# define PyCapsule_GetPointer(capsule, name) \\\n    (PyCObject_AsVoidPtr(capsule))\n#endif\n\n#if PY_MAJOR_VERSION >= 3\n# define PyInt_FromLong PyLong_FromLong\n#endif\n\n#define _cffi_from_c_double PyFloat_FromDouble\n#define _cffi_from_c_float PyFloat_FromDouble\n#define _cffi_from_c_long PyInt_FromLong\n#define _cffi_from_c_ulong PyLong_FromUnsignedLong\n#define _cffi_from_c_longlong PyLong_FromLongLong\n#define _cffi_from_c_ulonglong PyLong_FromUnsignedLongLong\n#define _cffi_from_c__Bool PyBool_FromLong\n\n#define _cffi_to_c_double PyFloat_AsDouble\n#define _cffi_to_c_float PyFloat_AsDouble\n\n#define _cffi_from_c_int_const(x)                                        \\\n    (((x) > 0) ?                                                         \\\n        ((unsigned long long)(x) <= (unsigned long long)LONG_MAX) ?      \\\n            PyInt_FromLong((long)(x)) :                                  \\\n            PyLong_FromUnsignedLongLong((unsigned long long)(x)) :       \\\n        ((long long)(x) >= (long long)LONG_MIN) ?                        \\\n            PyInt_FromLong((long)(x)) :                                  \\\n            PyLong_FromLongLong((long long)(x)))\n\n#define _cffi_from_c_int(x, type)                                        \\\n    (((type)-1) > 0 ? /* unsigned */                                     \\\n        (sizeof(type) < sizeof(long) ?                                   \\\n            PyInt_FromLong((long)x) :                                    \\\n         sizeof(type) == sizeof(long) ?                                  \\\n            PyLong_FromUnsignedLong((unsigned long)x) :                  \\\n            PyLong_FromUnsignedLongLong((unsigned long long)x)) :        \\\n        (sizeof(type) <= sizeof(long) ?                                  \\\n            PyInt_FromLong((long)x) :                                    \\\n            PyLong_FromLongLong((long long)x)))\n\n#define _cffi_to_c_int(o, type)                                          \\\n    ((type)(                                                             \\\n     sizeof(type) == 1 ? (((type)-1) > 0 ? (type)_cffi_to_c_u8(o)        \\\n                                         : (type)_cffi_to_c_i8(o)) :     \\\n     sizeof(type) == 2 ? (((type)-1) > 0 ? (type)_cffi_to_c_u16(o)       \\\n                                         : (type)_cffi_to_c_i16(o)) :    \\\n     sizeof(type) == 4 ? (((type)-1) > 0 ? (type)_cffi_to_c_u32(o)       \\\n                                         : (type)_cffi_to_c_i32(o)) :    \\\n     sizeof(type) == 8 ? (((type)-1) > 0 ? (type)_cffi_to_c_u64(o)       \\\n                                         : (type)_cffi_to_c_i64(o)) :    \\\n     (Py_FatalError(\"unsupported size for type \" #type), (type)0)))\n\n#define _cffi_to_c_i8                                                    \\\n                 ((int(*)(PyObject *))_cffi_exports[1])\n#define _cffi_to_c_u8                                                    \\\n                 ((int(*)(PyObject *))_cffi_exports[2])\n#define _cffi_to_c_i16                                                   \\\n                 ((int(*)(PyObject *))_cffi_exports[3])\n#define _cffi_to_c_u16                                                   \\\n                 ((int(*)(PyObject *))_cffi_exports[4])\n#define _cffi_to_c_i32                                                   \\\n                 ((int(*)(PyObject *))_cffi_exports[5])\n#define _cffi_to_c_u32                                                   \\\n                 ((unsigned int(*)(PyObject *))_cffi_exports[6])\n#define _cffi_to_c_i64                                                   \\\n                 ((long long(*)(PyObject *))_cffi_exports[7])\n#define _cffi_to_c_u64                                                   \\\n                 ((unsigned long long(*)(PyObject *))_cffi_exports[8])\n#define _cffi_to_c_char                                                  \\\n                 ((int(*)(PyObject *))_cffi_exports[9])\n#define _cffi_from_c_pointer                                             \\\n    ((PyObject *(*)(char *, CTypeDescrObject *))_cffi_exports[10])\n#define _cffi_to_c_pointer                                               \\\n    ((char *(*)(PyObject *, CTypeDescrObject *))_cffi_exports[11])\n#define _cffi_get_struct_layout                                          \\\n    ((PyObject *(*)(Py_ssize_t[]))_cffi_exports[12])\n#define _cffi_restore_errno                                              \\\n    ((void(*)(void))_cffi_exports[13])\n#define _cffi_save_errno                                                 \\\n    ((void(*)(void))_cffi_exports[14])\n#define _cffi_from_c_char                                                \\\n    ((PyObject *(*)(char))_cffi_exports[15])\n#define _cffi_from_c_deref                                               \\\n    ((PyObject *(*)(char *, CTypeDescrObject *))_cffi_exports[16])\n#define _cffi_to_c                                                       \\\n    ((int(*)(char *, CTypeDescrObject *, PyObject *))_cffi_exports[17])\n#define _cffi_from_c_struct                                              \\\n    ((PyObject *(*)(char *, CTypeDescrObject *))_cffi_exports[18])\n#define _cffi_to_c_wchar_t                                               \\\n    ((wchar_t(*)(PyObject *))_cffi_exports[19])\n#define _cffi_from_c_wchar_t                                             \\\n    ((PyObject *(*)(wchar_t))_cffi_exports[20])\n#define _cffi_to_c_long_double                                           \\\n    ((long double(*)(PyObject *))_cffi_exports[21])\n#define _cffi_to_c__Bool                                                 \\\n    ((_Bool(*)(PyObject *))_cffi_exports[22])\n#define _cffi_prepare_pointer_call_argument                              \\\n    ((Py_ssize_t(*)(CTypeDescrObject *, PyObject *, char **))_cffi_exports[23])\n#define _cffi_convert_array_from_object                                  \\\n    ((int(*)(char *, CTypeDescrObject *, PyObject *))_cffi_exports[24])\n#define _CFFI_NUM_EXPORTS 25\n\ntypedef struct _ctypedescr CTypeDescrObject;\n\nstatic void *_cffi_exports[_CFFI_NUM_EXPORTS];\nstatic PyObject *_cffi_types, *_cffi_VerificationError;\n\nstatic int _cffi_setup_custom(PyObject *lib);   /* forward */\n\nstatic PyObject *_cffi_setup(PyObject *self, PyObject *args)\n{\n    PyObject *library;\n    int was_alive = (_cffi_types != NULL);\n    (void)self; /* unused */\n    if (!PyArg_ParseTuple(args, \"OOO\", &_cffi_types, &_cffi_VerificationError,\n                                       &library))\n        return NULL;\n    Py_INCREF(_cffi_types);\n    Py_INCREF(_cffi_VerificationError);\n    if (_cffi_setup_custom(library) < 0)\n        return NULL;\n    return PyBool_FromLong(was_alive);\n}\n\nstatic int _cffi_init(void)\n{\n    PyObject *module, *c_api_object = NULL;\n\n    module = PyImport_ImportModule(\"_cffi_backend\");\n    if (module == NULL)\n        goto failure;\n\n    c_api_object = PyObject_GetAttrString(module, \"_C_API\");\n    if (c_api_object == NULL)\n        goto failure;\n    if (!PyCapsule_CheckExact(c_api_object)) {\n        PyErr_SetNone(PyExc_ImportError);\n        goto failure;\n    }\n    memcpy(_cffi_exports, PyCapsule_GetPointer(c_api_object, \"cffi\"),\n           _CFFI_NUM_EXPORTS * sizeof(void *));\n\n    Py_DECREF(module);\n    Py_DECREF(c_api_object);\n    return 0;\n\n  failure:\n    Py_XDECREF(module);\n    Py_XDECREF(c_api_object);\n    return -1;\n}\n\n#define _cffi_type(num) ((CTypeDescrObject *)PyList_GET_ITEM(_cffi_types, num))\n\n/**********/\n'''\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/vengine_gen.py",
    "content": "#\n# DEPRECATED: implementation for ffi.verify()\n#\nimport sys, os\nimport types\n\nfrom . import model\nfrom .error import VerificationError\n\n\nclass VGenericEngine(object):\n    _class_key = 'g'\n    _gen_python_module = False\n\n    def __init__(self, verifier):\n        self.verifier = verifier\n        self.ffi = verifier.ffi\n        self.export_symbols = []\n        self._struct_pending_verification = {}\n\n    def patch_extension_kwds(self, kwds):\n        # add 'export_symbols' to the dictionary.  Note that we add the\n        # list before filling it.  When we fill it, it will thus also show\n        # up in kwds['export_symbols'].\n        kwds.setdefault('export_symbols', self.export_symbols)\n\n    def find_module(self, module_name, path, so_suffixes):\n        for so_suffix in so_suffixes:\n            basename = module_name + so_suffix\n            if path is None:\n                path = sys.path\n            for dirname in path:\n                filename = os.path.join(dirname, basename)\n                if os.path.isfile(filename):\n                    return filename\n\n    def collect_types(self):\n        pass      # not needed in the generic engine\n\n    def _prnt(self, what=''):\n        self._f.write(what + '\\n')\n\n    def write_source_to_f(self):\n        prnt = self._prnt\n        # first paste some standard set of lines that are mostly '#include'\n        prnt(cffimod_header)\n        # then paste the C source given by the user, verbatim.\n        prnt(self.verifier.preamble)\n        #\n        # call generate_gen_xxx_decl(), for every xxx found from\n        # ffi._parser._declarations.  This generates all the functions.\n        self._generate('decl')\n        #\n        # on Windows, distutils insists on putting init_cffi_xyz in\n        # 'export_symbols', so instead of fighting it, just give up and\n        # give it one\n        if sys.platform == 'win32':\n            if sys.version_info >= (3,):\n                prefix = 'PyInit_'\n            else:\n                prefix = 'init'\n            modname = self.verifier.get_module_name()\n            prnt(\"void %s%s(void) { }\\n\" % (prefix, modname))\n\n    def load_library(self, flags=0):\n        # import it with the CFFI backend\n        backend = self.ffi._backend\n        # needs to make a path that contains '/', on Posix\n        filename = os.path.join(os.curdir, self.verifier.modulefilename)\n        module = backend.load_library(filename, flags)\n        #\n        # call loading_gen_struct() to get the struct layout inferred by\n        # the C compiler\n        self._load(module, 'loading')\n\n        # build the FFILibrary class and instance, this is a module subclass\n        # because modules are expected to have usually-constant-attributes and\n        # in PyPy this means the JIT is able to treat attributes as constant,\n        # which we want.\n        class FFILibrary(types.ModuleType):\n            _cffi_generic_module = module\n            _cffi_ffi = self.ffi\n            _cffi_dir = []\n            def __dir__(self):\n                return FFILibrary._cffi_dir\n        library = FFILibrary(\"\")\n        #\n        # finally, call the loaded_gen_xxx() functions.  This will set\n        # up the 'library' object.\n        self._load(module, 'loaded', library=library)\n        return library\n\n    def _get_declarations(self):\n        lst = [(key, tp) for (key, (tp, qual)) in\n                                self.ffi._parser._declarations.items()]\n        lst.sort()\n        return lst\n\n    def _generate(self, step_name):\n        for name, tp in self._get_declarations():\n            kind, realname = name.split(' ', 1)\n            try:\n                method = getattr(self, '_generate_gen_%s_%s' % (kind,\n                                                                step_name))\n            except AttributeError:\n                raise VerificationError(\n                    \"not implemented in verify(): %r\" % name)\n            try:\n                method(tp, realname)\n            except Exception as e:\n                model.attach_exception_info(e, name)\n                raise\n\n    def _load(self, module, step_name, **kwds):\n        for name, tp in self._get_declarations():\n            kind, realname = name.split(' ', 1)\n            method = getattr(self, '_%s_gen_%s' % (step_name, kind))\n            try:\n                method(tp, realname, module, **kwds)\n            except Exception as e:\n                model.attach_exception_info(e, name)\n                raise\n\n    def _generate_nothing(self, tp, name):\n        pass\n\n    def _loaded_noop(self, tp, name, module, **kwds):\n        pass\n\n    # ----------\n    # typedefs: generates no code so far\n\n    _generate_gen_typedef_decl   = _generate_nothing\n    _loading_gen_typedef         = _loaded_noop\n    _loaded_gen_typedef          = _loaded_noop\n\n    # ----------\n    # function declarations\n\n    def _generate_gen_function_decl(self, tp, name):\n        assert isinstance(tp, model.FunctionPtrType)\n        if tp.ellipsis:\n            # cannot support vararg functions better than this: check for its\n            # exact type (including the fixed arguments), and build it as a\n            # constant function pointer (no _cffi_f_%s wrapper)\n            self._generate_gen_const(False, name, tp)\n            return\n        prnt = self._prnt\n        numargs = len(tp.args)\n        argnames = []\n        for i, type in enumerate(tp.args):\n            indirection = ''\n            if isinstance(type, model.StructOrUnion):\n                indirection = '*'\n            argnames.append('%sx%d' % (indirection, i))\n        context = 'argument of %s' % name\n        arglist = [type.get_c_name(' %s' % arg, context)\n                   for type, arg in zip(tp.args, argnames)]\n        tpresult = tp.result\n        if isinstance(tpresult, model.StructOrUnion):\n            arglist.insert(0, tpresult.get_c_name(' *r', context))\n            tpresult = model.void_type\n        arglist = ', '.join(arglist) or 'void'\n        wrappername = '_cffi_f_%s' % name\n        self.export_symbols.append(wrappername)\n        if tp.abi:\n            abi = tp.abi + ' '\n        else:\n            abi = ''\n        funcdecl = ' %s%s(%s)' % (abi, wrappername, arglist)\n        context = 'result of %s' % name\n        prnt(tpresult.get_c_name(funcdecl, context))\n        prnt('{')\n        #\n        if isinstance(tp.result, model.StructOrUnion):\n            result_code = '*r = '\n        elif not isinstance(tp.result, model.VoidType):\n            result_code = 'return '\n        else:\n            result_code = ''\n        prnt('  %s%s(%s);' % (result_code, name, ', '.join(argnames)))\n        prnt('}')\n        prnt()\n\n    _loading_gen_function = _loaded_noop\n\n    def _loaded_gen_function(self, tp, name, module, library):\n        assert isinstance(tp, model.FunctionPtrType)\n        if tp.ellipsis:\n            newfunction = self._load_constant(False, tp, name, module)\n        else:\n            indirections = []\n            base_tp = tp\n            if (any(isinstance(typ, model.StructOrUnion) for typ in tp.args)\n                    or isinstance(tp.result, model.StructOrUnion)):\n                indirect_args = []\n                for i, typ in enumerate(tp.args):\n                    if isinstance(typ, model.StructOrUnion):\n                        typ = model.PointerType(typ)\n                        indirections.append((i, typ))\n                    indirect_args.append(typ)\n                indirect_result = tp.result\n                if isinstance(indirect_result, model.StructOrUnion):\n                    if indirect_result.fldtypes is None:\n                        raise TypeError(\"'%s' is used as result type, \"\n                                        \"but is opaque\" % (\n                                            indirect_result._get_c_name(),))\n                    indirect_result = model.PointerType(indirect_result)\n                    indirect_args.insert(0, indirect_result)\n                    indirections.insert(0, (\"result\", indirect_result))\n                    indirect_result = model.void_type\n                tp = model.FunctionPtrType(tuple(indirect_args),\n                                           indirect_result, tp.ellipsis)\n            BFunc = self.ffi._get_cached_btype(tp)\n            wrappername = '_cffi_f_%s' % name\n            newfunction = module.load_function(BFunc, wrappername)\n            for i, typ in indirections:\n                newfunction = self._make_struct_wrapper(newfunction, i, typ,\n                                                        base_tp)\n        setattr(library, name, newfunction)\n        type(library)._cffi_dir.append(name)\n\n    def _make_struct_wrapper(self, oldfunc, i, tp, base_tp):\n        backend = self.ffi._backend\n        BType = self.ffi._get_cached_btype(tp)\n        if i == \"result\":\n            ffi = self.ffi\n            def newfunc(*args):\n                res = ffi.new(BType)\n                oldfunc(res, *args)\n                return res[0]\n        else:\n            def newfunc(*args):\n                args = args[:i] + (backend.newp(BType, args[i]),) + args[i+1:]\n                return oldfunc(*args)\n        newfunc._cffi_base_type = base_tp\n        return newfunc\n\n    # ----------\n    # named structs\n\n    def _generate_gen_struct_decl(self, tp, name):\n        assert name == tp.name\n        self._generate_struct_or_union_decl(tp, 'struct', name)\n\n    def _loading_gen_struct(self, tp, name, module):\n        self._loading_struct_or_union(tp, 'struct', name, module)\n\n    def _loaded_gen_struct(self, tp, name, module, **kwds):\n        self._loaded_struct_or_union(tp)\n\n    def _generate_gen_union_decl(self, tp, name):\n        assert name == tp.name\n        self._generate_struct_or_union_decl(tp, 'union', name)\n\n    def _loading_gen_union(self, tp, name, module):\n        self._loading_struct_or_union(tp, 'union', name, module)\n\n    def _loaded_gen_union(self, tp, name, module, **kwds):\n        self._loaded_struct_or_union(tp)\n\n    def _generate_struct_or_union_decl(self, tp, prefix, name):\n        if tp.fldnames is None:\n            return     # nothing to do with opaque structs\n        checkfuncname = '_cffi_check_%s_%s' % (prefix, name)\n        layoutfuncname = '_cffi_layout_%s_%s' % (prefix, name)\n        cname = ('%s %s' % (prefix, name)).strip()\n        #\n        prnt = self._prnt\n        prnt('static void %s(%s *p)' % (checkfuncname, cname))\n        prnt('{')\n        prnt('  /* only to generate compile-time warnings or errors */')\n        prnt('  (void)p;')\n        for fname, ftype, fbitsize, fqual in tp.enumfields():\n            if (isinstance(ftype, model.PrimitiveType)\n                and ftype.is_integer_type()) or fbitsize >= 0:\n                # accept all integers, but complain on float or double\n                prnt('  (void)((p->%s) << 1);' % fname)\n            else:\n                # only accept exactly the type declared.\n                try:\n                    prnt('  { %s = &p->%s; (void)tmp; }' % (\n                        ftype.get_c_name('*tmp', 'field %r'%fname, quals=fqual),\n                        fname))\n                except VerificationError as e:\n                    prnt('  /* %s */' % str(e))   # cannot verify it, ignore\n        prnt('}')\n        self.export_symbols.append(layoutfuncname)\n        prnt('intptr_t %s(intptr_t i)' % (layoutfuncname,))\n        prnt('{')\n        prnt('  struct _cffi_aligncheck { char x; %s y; };' % cname)\n        prnt('  static intptr_t nums[] = {')\n        prnt('    sizeof(%s),' % cname)\n        prnt('    offsetof(struct _cffi_aligncheck, y),')\n        for fname, ftype, fbitsize, fqual in tp.enumfields():\n            if fbitsize >= 0:\n                continue      # xxx ignore fbitsize for now\n            prnt('    offsetof(%s, %s),' % (cname, fname))\n            if isinstance(ftype, model.ArrayType) and ftype.length is None:\n                prnt('    0,  /* %s */' % ftype._get_c_name())\n            else:\n                prnt('    sizeof(((%s *)0)->%s),' % (cname, fname))\n        prnt('    -1')\n        prnt('  };')\n        prnt('  return nums[i];')\n        prnt('  /* the next line is not executed, but compiled */')\n        prnt('  %s(0);' % (checkfuncname,))\n        prnt('}')\n        prnt()\n\n    def _loading_struct_or_union(self, tp, prefix, name, module):\n        if tp.fldnames is None:\n            return     # nothing to do with opaque structs\n        layoutfuncname = '_cffi_layout_%s_%s' % (prefix, name)\n        #\n        BFunc = self.ffi._typeof_locked(\"intptr_t(*)(intptr_t)\")[0]\n        function = module.load_function(BFunc, layoutfuncname)\n        layout = []\n        num = 0\n        while True:\n            x = function(num)\n            if x < 0: break\n            layout.append(x)\n            num += 1\n        if isinstance(tp, model.StructOrUnion) and tp.partial:\n            # use the function()'s sizes and offsets to guide the\n            # layout of the struct\n            totalsize = layout[0]\n            totalalignment = layout[1]\n            fieldofs = layout[2::2]\n            fieldsize = layout[3::2]\n            tp.force_flatten()\n            assert len(fieldofs) == len(fieldsize) == len(tp.fldnames)\n            tp.fixedlayout = fieldofs, fieldsize, totalsize, totalalignment\n        else:\n            cname = ('%s %s' % (prefix, name)).strip()\n            self._struct_pending_verification[tp] = layout, cname\n\n    def _loaded_struct_or_union(self, tp):\n        if tp.fldnames is None:\n            return     # nothing to do with opaque structs\n        self.ffi._get_cached_btype(tp)   # force 'fixedlayout' to be considered\n\n        if tp in self._struct_pending_verification:\n            # check that the layout sizes and offsets match the real ones\n            def check(realvalue, expectedvalue, msg):\n                if realvalue != expectedvalue:\n                    raise VerificationError(\n                        \"%s (we have %d, but C compiler says %d)\"\n                        % (msg, expectedvalue, realvalue))\n            ffi = self.ffi\n            BStruct = ffi._get_cached_btype(tp)\n            layout, cname = self._struct_pending_verification.pop(tp)\n            check(layout[0], ffi.sizeof(BStruct), \"wrong total size\")\n            check(layout[1], ffi.alignof(BStruct), \"wrong total alignment\")\n            i = 2\n            for fname, ftype, fbitsize, fqual in tp.enumfields():\n                if fbitsize >= 0:\n                    continue        # xxx ignore fbitsize for now\n                check(layout[i], ffi.offsetof(BStruct, fname),\n                      \"wrong offset for field %r\" % (fname,))\n                if layout[i+1] != 0:\n                    BField = ffi._get_cached_btype(ftype)\n                    check(layout[i+1], ffi.sizeof(BField),\n                          \"wrong size for field %r\" % (fname,))\n                i += 2\n            assert i == len(layout)\n\n    # ----------\n    # 'anonymous' declarations.  These are produced for anonymous structs\n    # or unions; the 'name' is obtained by a typedef.\n\n    def _generate_gen_anonymous_decl(self, tp, name):\n        if isinstance(tp, model.EnumType):\n            self._generate_gen_enum_decl(tp, name, '')\n        else:\n            self._generate_struct_or_union_decl(tp, '', name)\n\n    def _loading_gen_anonymous(self, tp, name, module):\n        if isinstance(tp, model.EnumType):\n            self._loading_gen_enum(tp, name, module, '')\n        else:\n            self._loading_struct_or_union(tp, '', name, module)\n\n    def _loaded_gen_anonymous(self, tp, name, module, **kwds):\n        if isinstance(tp, model.EnumType):\n            self._loaded_gen_enum(tp, name, module, **kwds)\n        else:\n            self._loaded_struct_or_union(tp)\n\n    # ----------\n    # constants, likely declared with '#define'\n\n    def _generate_gen_const(self, is_int, name, tp=None, category='const',\n                            check_value=None):\n        prnt = self._prnt\n        funcname = '_cffi_%s_%s' % (category, name)\n        self.export_symbols.append(funcname)\n        if check_value is not None:\n            assert is_int\n            assert category == 'const'\n            prnt('int %s(char *out_error)' % funcname)\n            prnt('{')\n            self._check_int_constant_value(name, check_value)\n            prnt('  return 0;')\n            prnt('}')\n        elif is_int:\n            assert category == 'const'\n            prnt('int %s(long long *out_value)' % funcname)\n            prnt('{')\n            prnt('  *out_value = (long long)(%s);' % (name,))\n            prnt('  return (%s) <= 0;' % (name,))\n            prnt('}')\n        else:\n            assert tp is not None\n            assert check_value is None\n            if category == 'var':\n                ampersand = '&'\n            else:\n                ampersand = ''\n            extra = ''\n            if category == 'const' and isinstance(tp, model.StructOrUnion):\n                extra = 'const *'\n                ampersand = '&'\n            prnt(tp.get_c_name(' %s%s(void)' % (extra, funcname), name))\n            prnt('{')\n            prnt('  return (%s%s);' % (ampersand, name))\n            prnt('}')\n        prnt()\n\n    def _generate_gen_constant_decl(self, tp, name):\n        is_int = isinstance(tp, model.PrimitiveType) and tp.is_integer_type()\n        self._generate_gen_const(is_int, name, tp)\n\n    _loading_gen_constant = _loaded_noop\n\n    def _load_constant(self, is_int, tp, name, module, check_value=None):\n        funcname = '_cffi_const_%s' % name\n        if check_value is not None:\n            assert is_int\n            self._load_known_int_constant(module, funcname)\n            value = check_value\n        elif is_int:\n            BType = self.ffi._typeof_locked(\"long long*\")[0]\n            BFunc = self.ffi._typeof_locked(\"int(*)(long long*)\")[0]\n            function = module.load_function(BFunc, funcname)\n            p = self.ffi.new(BType)\n            negative = function(p)\n            value = int(p[0])\n            if value < 0 and not negative:\n                BLongLong = self.ffi._typeof_locked(\"long long\")[0]\n                value += (1 << (8*self.ffi.sizeof(BLongLong)))\n        else:\n            assert check_value is None\n            fntypeextra = '(*)(void)'\n            if isinstance(tp, model.StructOrUnion):\n                fntypeextra = '*' + fntypeextra\n            BFunc = self.ffi._typeof_locked(tp.get_c_name(fntypeextra, name))[0]\n            function = module.load_function(BFunc, funcname)\n            value = function()\n            if isinstance(tp, model.StructOrUnion):\n                value = value[0]\n        return value\n\n    def _loaded_gen_constant(self, tp, name, module, library):\n        is_int = isinstance(tp, model.PrimitiveType) and tp.is_integer_type()\n        value = self._load_constant(is_int, tp, name, module)\n        setattr(library, name, value)\n        type(library)._cffi_dir.append(name)\n\n    # ----------\n    # enums\n\n    def _check_int_constant_value(self, name, value):\n        prnt = self._prnt\n        if value <= 0:\n            prnt('  if ((%s) > 0 || (long)(%s) != %dL) {' % (\n                name, name, value))\n        else:\n            prnt('  if ((%s) <= 0 || (unsigned long)(%s) != %dUL) {' % (\n                name, name, value))\n        prnt('    char buf[64];')\n        prnt('    if ((%s) <= 0)' % name)\n        prnt('        sprintf(buf, \"%%ld\", (long)(%s));' % name)\n        prnt('    else')\n        prnt('        sprintf(buf, \"%%lu\", (unsigned long)(%s));' %\n             name)\n        prnt('    sprintf(out_error, \"%s has the real value %s, not %s\",')\n        prnt('            \"%s\", buf, \"%d\");' % (name[:100], value))\n        prnt('    return -1;')\n        prnt('  }')\n\n    def _load_known_int_constant(self, module, funcname):\n        BType = self.ffi._typeof_locked(\"char[]\")[0]\n        BFunc = self.ffi._typeof_locked(\"int(*)(char*)\")[0]\n        function = module.load_function(BFunc, funcname)\n        p = self.ffi.new(BType, 256)\n        if function(p) < 0:\n            error = self.ffi.string(p)\n            if sys.version_info >= (3,):\n                error = str(error, 'utf-8')\n            raise VerificationError(error)\n\n    def _enum_funcname(self, prefix, name):\n        # \"$enum_$1\" => \"___D_enum____D_1\"\n        name = name.replace('$', '___D_')\n        return '_cffi_e_%s_%s' % (prefix, name)\n\n    def _generate_gen_enum_decl(self, tp, name, prefix='enum'):\n        if tp.partial:\n            for enumerator in tp.enumerators:\n                self._generate_gen_const(True, enumerator)\n            return\n        #\n        funcname = self._enum_funcname(prefix, name)\n        self.export_symbols.append(funcname)\n        prnt = self._prnt\n        prnt('int %s(char *out_error)' % funcname)\n        prnt('{')\n        for enumerator, enumvalue in zip(tp.enumerators, tp.enumvalues):\n            self._check_int_constant_value(enumerator, enumvalue)\n        prnt('  return 0;')\n        prnt('}')\n        prnt()\n\n    def _loading_gen_enum(self, tp, name, module, prefix='enum'):\n        if tp.partial:\n            enumvalues = [self._load_constant(True, tp, enumerator, module)\n                          for enumerator in tp.enumerators]\n            tp.enumvalues = tuple(enumvalues)\n            tp.partial_resolved = True\n        else:\n            funcname = self._enum_funcname(prefix, name)\n            self._load_known_int_constant(module, funcname)\n\n    def _loaded_gen_enum(self, tp, name, module, library):\n        for enumerator, enumvalue in zip(tp.enumerators, tp.enumvalues):\n            setattr(library, enumerator, enumvalue)\n            type(library)._cffi_dir.append(enumerator)\n\n    # ----------\n    # macros: for now only for integers\n\n    def _generate_gen_macro_decl(self, tp, name):\n        if tp == '...':\n            check_value = None\n        else:\n            check_value = tp     # an integer\n        self._generate_gen_const(True, name, check_value=check_value)\n\n    _loading_gen_macro = _loaded_noop\n\n    def _loaded_gen_macro(self, tp, name, module, library):\n        if tp == '...':\n            check_value = None\n        else:\n            check_value = tp     # an integer\n        value = self._load_constant(True, tp, name, module,\n                                    check_value=check_value)\n        setattr(library, name, value)\n        type(library)._cffi_dir.append(name)\n\n    # ----------\n    # global variables\n\n    def _generate_gen_variable_decl(self, tp, name):\n        if isinstance(tp, model.ArrayType):\n            if tp.length == '...':\n                prnt = self._prnt\n                funcname = '_cffi_sizeof_%s' % (name,)\n                self.export_symbols.append(funcname)\n                prnt(\"size_t %s(void)\" % funcname)\n                prnt(\"{\")\n                prnt(\"  return sizeof(%s);\" % (name,))\n                prnt(\"}\")\n            tp_ptr = model.PointerType(tp.item)\n            self._generate_gen_const(False, name, tp_ptr)\n        else:\n            tp_ptr = model.PointerType(tp)\n            self._generate_gen_const(False, name, tp_ptr, category='var')\n\n    _loading_gen_variable = _loaded_noop\n\n    def _loaded_gen_variable(self, tp, name, module, library):\n        if isinstance(tp, model.ArrayType):   # int a[5] is \"constant\" in the\n                                              # sense that \"a=...\" is forbidden\n            if tp.length == '...':\n                funcname = '_cffi_sizeof_%s' % (name,)\n                BFunc = self.ffi._typeof_locked('size_t(*)(void)')[0]\n                function = module.load_function(BFunc, funcname)\n                size = function()\n                BItemType = self.ffi._get_cached_btype(tp.item)\n                length, rest = divmod(size, self.ffi.sizeof(BItemType))\n                if rest != 0:\n                    raise VerificationError(\n                        \"bad size: %r does not seem to be an array of %s\" %\n                        (name, tp.item))\n                tp = tp.resolve_length(length)\n            tp_ptr = model.PointerType(tp.item)\n            value = self._load_constant(False, tp_ptr, name, module)\n            # 'value' is a <cdata 'type *'> which we have to replace with\n            # a <cdata 'type[N]'> if the N is actually known\n            if tp.length is not None:\n                BArray = self.ffi._get_cached_btype(tp)\n                value = self.ffi.cast(BArray, value)\n            setattr(library, name, value)\n            type(library)._cffi_dir.append(name)\n            return\n        # remove ptr=<cdata 'int *'> from the library instance, and replace\n        # it by a property on the class, which reads/writes into ptr[0].\n        funcname = '_cffi_var_%s' % name\n        BFunc = self.ffi._typeof_locked(tp.get_c_name('*(*)(void)', name))[0]\n        function = module.load_function(BFunc, funcname)\n        ptr = function()\n        def getter(library):\n            return ptr[0]\n        def setter(library, value):\n            ptr[0] = value\n        setattr(type(library), name, property(getter, setter))\n        type(library)._cffi_dir.append(name)\n\ncffimod_header = r'''\n#include <stdio.h>\n#include <stddef.h>\n#include <stdarg.h>\n#include <errno.h>\n#include <sys/types.h>   /* XXX for ssize_t on some platforms */\n\n/* this block of #ifs should be kept exactly identical between\n   c/_cffi_backend.c, cffi/vengine_cpy.py, cffi/vengine_gen.py\n   and cffi/_cffi_include.h */\n#if defined(_MSC_VER)\n# include <malloc.h>   /* for alloca() */\n# if _MSC_VER < 1600   /* MSVC < 2010 */\n   typedef __int8 int8_t;\n   typedef __int16 int16_t;\n   typedef __int32 int32_t;\n   typedef __int64 int64_t;\n   typedef unsigned __int8 uint8_t;\n   typedef unsigned __int16 uint16_t;\n   typedef unsigned __int32 uint32_t;\n   typedef unsigned __int64 uint64_t;\n   typedef __int8 int_least8_t;\n   typedef __int16 int_least16_t;\n   typedef __int32 int_least32_t;\n   typedef __int64 int_least64_t;\n   typedef unsigned __int8 uint_least8_t;\n   typedef unsigned __int16 uint_least16_t;\n   typedef unsigned __int32 uint_least32_t;\n   typedef unsigned __int64 uint_least64_t;\n   typedef __int8 int_fast8_t;\n   typedef __int16 int_fast16_t;\n   typedef __int32 int_fast32_t;\n   typedef __int64 int_fast64_t;\n   typedef unsigned __int8 uint_fast8_t;\n   typedef unsigned __int16 uint_fast16_t;\n   typedef unsigned __int32 uint_fast32_t;\n   typedef unsigned __int64 uint_fast64_t;\n   typedef __int64 intmax_t;\n   typedef unsigned __int64 uintmax_t;\n# else\n#  include <stdint.h>\n# endif\n# if _MSC_VER < 1800   /* MSVC < 2013 */\n#  ifndef __cplusplus\n    typedef unsigned char _Bool;\n#  endif\n# endif\n#else\n# include <stdint.h>\n# if (defined (__SVR4) && defined (__sun)) || defined(_AIX) || defined(__hpux)\n#  include <alloca.h>\n# endif\n#endif\n'''\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi/verifier.py",
    "content": "#\n# DEPRECATED: implementation for ffi.verify()\n#\nimport sys, os, binascii, shutil, io\nfrom . import __version_verifier_modules__\nfrom . import ffiplatform\nfrom .error import VerificationError\n\nif sys.version_info >= (3, 3):\n    import importlib.machinery\n    def _extension_suffixes():\n        return importlib.machinery.EXTENSION_SUFFIXES[:]\nelse:\n    import imp\n    def _extension_suffixes():\n        return [suffix for suffix, _, type in imp.get_suffixes()\n                if type == imp.C_EXTENSION]\n\n\nif sys.version_info >= (3,):\n    NativeIO = io.StringIO\nelse:\n    class NativeIO(io.BytesIO):\n        def write(self, s):\n            if isinstance(s, unicode):\n                s = s.encode('ascii')\n            super(NativeIO, self).write(s)\n\n\nclass Verifier(object):\n\n    def __init__(self, ffi, preamble, tmpdir=None, modulename=None,\n                 ext_package=None, tag='', force_generic_engine=False,\n                 source_extension='.c', flags=None, relative_to=None, **kwds):\n        if ffi._parser._uses_new_feature:\n            raise VerificationError(\n                \"feature not supported with ffi.verify(), but only \"\n                \"with ffi.set_source(): %s\" % (ffi._parser._uses_new_feature,))\n        self.ffi = ffi\n        self.preamble = preamble\n        if not modulename:\n            flattened_kwds = ffiplatform.flatten(kwds)\n        vengine_class = _locate_engine_class(ffi, force_generic_engine)\n        self._vengine = vengine_class(self)\n        self._vengine.patch_extension_kwds(kwds)\n        self.flags = flags\n        self.kwds = self.make_relative_to(kwds, relative_to)\n        #\n        if modulename:\n            if tag:\n                raise TypeError(\"can't specify both 'modulename' and 'tag'\")\n        else:\n            key = '\\x00'.join([sys.version[:3], __version_verifier_modules__,\n                               preamble, flattened_kwds] +\n                              ffi._cdefsources)\n            if sys.version_info >= (3,):\n                key = key.encode('utf-8')\n            k1 = hex(binascii.crc32(key[0::2]) & 0xffffffff)\n            k1 = k1.lstrip('0x').rstrip('L')\n            k2 = hex(binascii.crc32(key[1::2]) & 0xffffffff)\n            k2 = k2.lstrip('0').rstrip('L')\n            modulename = '_cffi_%s_%s%s%s' % (tag, self._vengine._class_key,\n                                              k1, k2)\n        suffix = _get_so_suffixes()[0]\n        self.tmpdir = tmpdir or _caller_dir_pycache()\n        self.sourcefilename = os.path.join(self.tmpdir, modulename + source_extension)\n        self.modulefilename = os.path.join(self.tmpdir, modulename + suffix)\n        self.ext_package = ext_package\n        self._has_source = False\n        self._has_module = False\n\n    def write_source(self, file=None):\n        \"\"\"Write the C source code.  It is produced in 'self.sourcefilename',\n        which can be tweaked beforehand.\"\"\"\n        with self.ffi._lock:\n            if self._has_source and file is None:\n                raise VerificationError(\n                    \"source code already written\")\n            self._write_source(file)\n\n    def compile_module(self):\n        \"\"\"Write the C source code (if not done already) and compile it.\n        This produces a dynamic link library in 'self.modulefilename'.\"\"\"\n        with self.ffi._lock:\n            if self._has_module:\n                raise VerificationError(\"module already compiled\")\n            if not self._has_source:\n                self._write_source()\n            self._compile_module()\n\n    def load_library(self):\n        \"\"\"Get a C module from this Verifier instance.\n        Returns an instance of a FFILibrary class that behaves like the\n        objects returned by ffi.dlopen(), but that delegates all\n        operations to the C module.  If necessary, the C code is written\n        and compiled first.\n        \"\"\"\n        with self.ffi._lock:\n            if not self._has_module:\n                self._locate_module()\n                if not self._has_module:\n                    if not self._has_source:\n                        self._write_source()\n                    self._compile_module()\n            return self._load_library()\n\n    def get_module_name(self):\n        basename = os.path.basename(self.modulefilename)\n        # kill both the .so extension and the other .'s, as introduced\n        # by Python 3: 'basename.cpython-33m.so'\n        basename = basename.split('.', 1)[0]\n        # and the _d added in Python 2 debug builds --- but try to be\n        # conservative and not kill a legitimate _d\n        if basename.endswith('_d') and hasattr(sys, 'gettotalrefcount'):\n            basename = basename[:-2]\n        return basename\n\n    def get_extension(self):\n        ffiplatform._hack_at_distutils() # backward compatibility hack\n        if not self._has_source:\n            with self.ffi._lock:\n                if not self._has_source:\n                    self._write_source()\n        sourcename = ffiplatform.maybe_relative_path(self.sourcefilename)\n        modname = self.get_module_name()\n        return ffiplatform.get_extension(sourcename, modname, **self.kwds)\n\n    def generates_python_module(self):\n        return self._vengine._gen_python_module\n\n    def make_relative_to(self, kwds, relative_to):\n        if relative_to and os.path.dirname(relative_to):\n            dirname = os.path.dirname(relative_to)\n            kwds = kwds.copy()\n            for key in ffiplatform.LIST_OF_FILE_NAMES:\n                if key in kwds:\n                    lst = kwds[key]\n                    if not isinstance(lst, (list, tuple)):\n                        raise TypeError(\"keyword '%s' should be a list or tuple\"\n                                        % (key,))\n                    lst = [os.path.join(dirname, fn) for fn in lst]\n                    kwds[key] = lst\n        return kwds\n\n    # ----------\n\n    def _locate_module(self):\n        if not os.path.isfile(self.modulefilename):\n            if self.ext_package:\n                try:\n                    pkg = __import__(self.ext_package, None, None, ['__doc__'])\n                except ImportError:\n                    return      # cannot import the package itself, give up\n                    # (e.g. it might be called differently before installation)\n                path = pkg.__path__\n            else:\n                path = None\n            filename = self._vengine.find_module(self.get_module_name(), path,\n                                                 _get_so_suffixes())\n            if filename is None:\n                return\n            self.modulefilename = filename\n        self._vengine.collect_types()\n        self._has_module = True\n\n    def _write_source_to(self, file):\n        self._vengine._f = file\n        try:\n            self._vengine.write_source_to_f()\n        finally:\n            del self._vengine._f\n\n    def _write_source(self, file=None):\n        if file is not None:\n            self._write_source_to(file)\n        else:\n            # Write our source file to an in memory file.\n            f = NativeIO()\n            self._write_source_to(f)\n            source_data = f.getvalue()\n\n            # Determine if this matches the current file\n            if os.path.exists(self.sourcefilename):\n                with open(self.sourcefilename, \"r\") as fp:\n                    needs_written = not (fp.read() == source_data)\n            else:\n                needs_written = True\n\n            # Actually write the file out if it doesn't match\n            if needs_written:\n                _ensure_dir(self.sourcefilename)\n                with open(self.sourcefilename, \"w\") as fp:\n                    fp.write(source_data)\n\n            # Set this flag\n            self._has_source = True\n\n    def _compile_module(self):\n        # compile this C source\n        tmpdir = os.path.dirname(self.sourcefilename)\n        outputfilename = ffiplatform.compile(tmpdir, self.get_extension())\n        try:\n            same = ffiplatform.samefile(outputfilename, self.modulefilename)\n        except OSError:\n            same = False\n        if not same:\n            _ensure_dir(self.modulefilename)\n            shutil.move(outputfilename, self.modulefilename)\n        self._has_module = True\n\n    def _load_library(self):\n        assert self._has_module\n        if self.flags is not None:\n            return self._vengine.load_library(self.flags)\n        else:\n            return self._vengine.load_library()\n\n# ____________________________________________________________\n\n_FORCE_GENERIC_ENGINE = False      # for tests\n\ndef _locate_engine_class(ffi, force_generic_engine):\n    if _FORCE_GENERIC_ENGINE:\n        force_generic_engine = True\n    if not force_generic_engine:\n        if '__pypy__' in sys.builtin_module_names:\n            force_generic_engine = True\n        else:\n            try:\n                import _cffi_backend\n            except ImportError:\n                _cffi_backend = '?'\n            if ffi._backend is not _cffi_backend:\n                force_generic_engine = True\n    if force_generic_engine:\n        from . import vengine_gen\n        return vengine_gen.VGenericEngine\n    else:\n        from . import vengine_cpy\n        return vengine_cpy.VCPythonEngine\n\n# ____________________________________________________________\n\n_TMPDIR = None\n\ndef _caller_dir_pycache():\n    if _TMPDIR:\n        return _TMPDIR\n    result = os.environ.get('CFFI_TMPDIR')\n    if result:\n        return result\n    filename = sys._getframe(2).f_code.co_filename\n    return os.path.abspath(os.path.join(os.path.dirname(filename),\n                           '__pycache__'))\n\ndef set_tmpdir(dirname):\n    \"\"\"Set the temporary directory to use instead of __pycache__.\"\"\"\n    global _TMPDIR\n    _TMPDIR = dirname\n\ndef cleanup_tmpdir(tmpdir=None, keep_so=False):\n    \"\"\"Clean up the temporary directory by removing all files in it\n    called `_cffi_*.{c,so}` as well as the `build` subdirectory.\"\"\"\n    tmpdir = tmpdir or _caller_dir_pycache()\n    try:\n        filelist = os.listdir(tmpdir)\n    except OSError:\n        return\n    if keep_so:\n        suffix = '.c'   # only remove .c files\n    else:\n        suffix = _get_so_suffixes()[0].lower()\n    for fn in filelist:\n        if fn.lower().startswith('_cffi_') and (\n                fn.lower().endswith(suffix) or fn.lower().endswith('.c')):\n            try:\n                os.unlink(os.path.join(tmpdir, fn))\n            except OSError:\n                pass\n    clean_dir = [os.path.join(tmpdir, 'build')]\n    for dir in clean_dir:\n        try:\n            for fn in os.listdir(dir):\n                fn = os.path.join(dir, fn)\n                if os.path.isdir(fn):\n                    clean_dir.append(fn)\n                else:\n                    os.unlink(fn)\n        except OSError:\n            pass\n\ndef _get_so_suffixes():\n    suffixes = _extension_suffixes()\n    if not suffixes:\n        # bah, no C_EXTENSION available.  Occurs on pypy without cpyext\n        if sys.platform == 'win32':\n            suffixes = [\".pyd\"]\n        else:\n            suffixes = [\".so\"]\n\n    return suffixes\n\ndef _ensure_dir(filename):\n    dirname = os.path.dirname(filename)\n    if dirname and not os.path.isdir(dirname):\n        os.makedirs(dirname)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi-1.13.1.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi-1.13.1.dist-info/LICENSE.txt",
    "content": "\nExcept when otherwise stated (look for LICENSE files in directories or\ninformation at the beginning of each file) all software and\ndocumentation is licensed as follows: \n\n    The MIT License\n\n    Permission is hereby granted, free of charge, to any person \n    obtaining a copy of this software and associated documentation \n    files (the \"Software\"), to deal in the Software without \n    restriction, including without limitation the rights to use, \n    copy, modify, merge, publish, distribute, sublicense, and/or \n    sell copies of the Software, and to permit persons to whom the \n    Software is furnished to do so, subject to the following conditions:\n\n    The above copyright notice and this permission notice shall be included \n    in all copies or substantial portions of the Software.\n\n    THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS \n    OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, \n    FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL \n    THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER \n    LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING \n    FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER \n    DEALINGS IN THE SOFTWARE.\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi-1.13.1.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: cffi\nVersion: 1.13.1\nSummary: Foreign Function Interface for Python calling C code.\nHome-page: http://cffi.readthedocs.org\nAuthor: Armin Rigo, Maciej Fijalkowski\nAuthor-email: python-cffi@googlegroups.com\nLicense: MIT\nPlatform: UNKNOWN\nClassifier: Programming Language :: Python\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.6\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.2\nClassifier: Programming Language :: Python :: 3.3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: Implementation :: CPython\nClassifier: Programming Language :: Python :: Implementation :: PyPy\nRequires-Dist: pycparser\n\n\nCFFI\n====\n\nForeign Function Interface for Python calling C code.\nPlease see the `Documentation <http://cffi.readthedocs.org/>`_.\n\nContact\n-------\n\n`Mailing list <https://groups.google.com/forum/#!forum/python-cffi>`_\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi-1.13.1.dist-info/RECORD",
    "content": ".libs_cffi_backend/libffi-10449faf.so.5.0.6,sha256=PG7U56gJ8uCf3HUyfp4gVBQTu7rwI2GdyE7quplTB2o,34248\r\n_cffi_backend.cpython-36m-x86_64-linux-gnu.so,sha256=lyO5RSJGQG5eqiZKAfaFBevoOb4awoyRoAXv8qaxO0s,849704\r\ncffi-1.13.1.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\ncffi-1.13.1.dist-info/LICENSE.txt,sha256=BLgPWwd7vtaICM_rreteNSPyqMmpZJXFh72W3x6sKjM,1294\r\ncffi-1.13.1.dist-info/METADATA,sha256=M7h8dR2tpB6Q5V46_Imv7Gxe7pKzA1hufeVHtu2sNAo,1140\r\ncffi-1.13.1.dist-info/RECORD,,\r\ncffi-1.13.1.dist-info/WHEEL,sha256=d2ILPScH-y2UwGxsW1PeA2TT-KW0Git4AJ6LeOK8sQo,109\r\ncffi-1.13.1.dist-info/entry_points.txt,sha256=Q9f5C9IpjYxo0d2PK9eUcnkgxHc9pHWwjEMaANPKNCI,76\r\ncffi-1.13.1.dist-info/top_level.txt,sha256=rE7WR3rZfNKxWI9-jn6hsHCAl7MDkB-FmuQbxWjFehQ,19\r\ncffi/__init__.py,sha256=vMoBBQacAlqzOsFf931EfnNqZnslrwcuaSeLUO6JTvY,513\r\ncffi/__pycache__/__init__.cpython-36.pyc,,\r\ncffi/__pycache__/api.cpython-36.pyc,,\r\ncffi/__pycache__/backend_ctypes.cpython-36.pyc,,\r\ncffi/__pycache__/cffi_opcode.cpython-36.pyc,,\r\ncffi/__pycache__/commontypes.cpython-36.pyc,,\r\ncffi/__pycache__/cparser.cpython-36.pyc,,\r\ncffi/__pycache__/error.cpython-36.pyc,,\r\ncffi/__pycache__/ffiplatform.cpython-36.pyc,,\r\ncffi/__pycache__/lock.cpython-36.pyc,,\r\ncffi/__pycache__/model.cpython-36.pyc,,\r\ncffi/__pycache__/pkgconfig.cpython-36.pyc,,\r\ncffi/__pycache__/recompiler.cpython-36.pyc,,\r\ncffi/__pycache__/setuptools_ext.cpython-36.pyc,,\r\ncffi/__pycache__/vengine_cpy.cpython-36.pyc,,\r\ncffi/__pycache__/vengine_gen.cpython-36.pyc,,\r\ncffi/__pycache__/verifier.cpython-36.pyc,,\r\ncffi/_cffi_errors.h,sha256=6nFQ-4dRQI1bXRoSeqdvyKU33TmutQJB_2fAhWSzdl8,3856\r\ncffi/_cffi_include.h,sha256=JuFfmwpRE65vym3Nxr9vDMOIEuv21tXdarkL1l2WNms,12149\r\ncffi/_embedding.h,sha256=bhLhKOkF46V3C5gHLb4OkxH9pdcwMJqpjPHNDYojwbc,17411\r\ncffi/api.py,sha256=Q07iwDD0FRwWa2fx2ZzQft69iJs9aNR52fvrtUy3EY4,41800\r\ncffi/backend_ctypes.py,sha256=h5ZIzLc6BFVXnGyc9xPqZWUS7qGy7yFSDqXe68Sa8z4,42454\r\ncffi/cffi_opcode.py,sha256=v9RdD_ovA8rCtqsC95Ivki5V667rAOhGgs3fb2q9xpM,5724\r\ncffi/commontypes.py,sha256=QS4uxCDI7JhtTyjh1hlnCA-gynmaszWxJaRRLGkJa1A,2689\r\ncffi/cparser.py,sha256=DIChXOqV-T3bZ3APc42V9zgeU0PdF4e57GU4WvIK4JQ,42079\r\ncffi/error.py,sha256=v6xTiS4U0kvDcy4h_BDRo5v39ZQuj-IMRYLv5ETddZs,877\r\ncffi/ffiplatform.py,sha256=HMXqR8ks2wtdsNxGaWpQ_PyqIvtiuos_vf1qKCy-cwg,4046\r\ncffi/lock.py,sha256=l9TTdwMIMpi6jDkJGnQgE9cvTIR7CAntIJr8EGHt3pY,747\r\ncffi/model.py,sha256=AYyjS26uiFKXtkm43qmStpy9zfGh5HVJF4UETYFBt6w,21682\r\ncffi/parse_c_type.h,sha256=OdwQfwM9ktq6vlCB43exFQmxDBtj2MBNdK8LYl15tjw,5976\r\ncffi/pkgconfig.py,sha256=LP1w7vmWvmKwyqLaU1Z243FOWGNQMrgMUZrvgFuOlco,4374\r\ncffi/recompiler.py,sha256=9BR4oOQ9wFTMrp6CGa4Pa4U1pAU64Mv5-KwW5Hdn3ZM,62755\r\ncffi/setuptools_ext.py,sha256=qc6arfrSzm4RNT5oJz6d5td7KJ-pHfI7bqYD0X4Q-08,8848\r\ncffi/vengine_cpy.py,sha256=hdyjjZNijLrg_uGMnnFyC-7GG_LxWtwB8BlS2vvVDQ0,41470\r\ncffi/vengine_gen.py,sha256=Zkq0-EdeZwn6qUvf_CI8iUEs2UxVIvDmKCH1j0-y0GI,26676\r\ncffi/verifier.py,sha256=J9Enz2rbJb9CHPqWlWQ5uQESoyr0uc7MNWugchjXBv4,11207\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi-1.13.1.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.31.1)\nRoot-Is-Purelib: false\nTag: cp36-cp36m-manylinux1_x86_64\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi-1.13.1.dist-info/entry_points.txt",
    "content": "[distutils.setup_keywords]\ncffi_modules = cffi.setuptools_ext:cffi_modules\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cffi-1.13.1.dist-info/top_level.txt",
    "content": "_cffi_backend\ncffi\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/constantly/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom constantly._constants import (\n    NamedConstant, Names, ValueConstant, Values, FlagConstant, Flags\n)\n\nfrom ._version import get_versions\n__version__ = get_versions()['version']\ndel get_versions\n\n__author__  = \"Twisted Matrix Laboratories\"\n__license__ = \"MIT\"\n__copyright__ = \"Copyright 2011-2015 {0}\".format(__author__)\n\n\n__all__ = [\n    'NamedConstant',\n    'ValueConstant',\n    'FlagConstant',\n    'Names',\n    'Values',\n    'Flags',\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/constantly/_constants.py",
    "content": "# -*- test-case-name: constantly.test.test_constants -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nSymbolic constant support, including collections and constants with text,\nnumeric, and bit flag values.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__all__ = [\n    'NamedConstant', 'ValueConstant', 'FlagConstant',\n    'Names', 'Values', 'Flags']\n\nfrom functools import partial\nfrom itertools import count\nfrom operator import and_, or_, xor\n\n_unspecified = object()\n_constantOrder = partial(next, count())\n\n\nclass _Constant(object):\n    \"\"\"\n    @ivar _index: A C{int} allocated from a shared counter in order to keep\n        track of the order in which L{_Constant}s are instantiated.\n\n    @ivar name: A C{str} giving the name of this constant; only set once the\n        constant is initialized by L{_ConstantsContainer}.\n\n    @ivar _container: The L{_ConstantsContainer} subclass this constant belongs\n        to; C{None} until the constant is initialized by that subclass.\n    \"\"\"\n    def __init__(self):\n        self._container = None\n        self._index = _constantOrder()\n\n\n    def __repr__(self):\n        \"\"\"\n        Return text identifying both which constant this is and which\n        collection it belongs to.\n        \"\"\"\n        return \"<%s=%s>\" % (self._container.__name__, self.name)\n\n\n    def __lt__(self, other):\n        \"\"\"\n        Implements C{<}.  Order is defined by instantiation order.\n\n        @param other: An object.\n\n        @return: C{NotImplemented} if C{other} is not a constant belonging to\n            the same container as this constant, C{True} if this constant is\n            defined before C{other}, otherwise C{False}.\n        \"\"\"\n        if (\n            not isinstance(other, self.__class__) or\n            not self._container == other._container\n        ):\n            return NotImplemented\n        return self._index < other._index\n\n\n    def __le__(self, other):\n        \"\"\"\n        Implements C{<=}.  Order is defined by instantiation order.\n\n        @param other: An object.\n\n        @return: C{NotImplemented} if C{other} is not a constant belonging to\n            the same container as this constant, C{True} if this constant is\n            defined before or equal to C{other}, otherwise C{False}.\n        \"\"\"\n        if (\n            not isinstance(other, self.__class__) or\n            not self._container == other._container\n        ):\n            return NotImplemented\n        return self is other or self._index < other._index\n\n\n    def __gt__(self, other):\n        \"\"\"\n        Implements C{>}.  Order is defined by instantiation order.\n\n        @param other: An object.\n\n        @return: C{NotImplemented} if C{other} is not a constant belonging to\n            the same container as this constant, C{True} if this constant is\n            defined after C{other}, otherwise C{False}.\n        \"\"\"\n        if (\n            not isinstance(other, self.__class__) or\n            not self._container == other._container\n        ):\n            return NotImplemented\n        return self._index > other._index\n\n\n    def __ge__(self, other):\n        \"\"\"\n        Implements C{>=}.  Order is defined by instantiation order.\n\n        @param other: An object.\n\n        @return: C{NotImplemented} if C{other} is not a constant belonging to\n            the same container as this constant, C{True} if this constant is\n            defined after or equal to C{other}, otherwise C{False}.\n        \"\"\"\n        if (\n            not isinstance(other, self.__class__) or\n            not self._container == other._container\n        ):\n            return NotImplemented\n        return self is other or self._index > other._index\n\n\n    def _realize(self, container, name, value):\n        \"\"\"\n        Complete the initialization of this L{_Constant}.\n\n        @param container: The L{_ConstantsContainer} subclass this constant is\n            part of.\n\n        @param name: The name of this constant in its container.\n\n        @param value: The value of this constant; not used, as named constants\n            have no value apart from their identity.\n        \"\"\"\n        self._container = container\n        self.name = name\n\n\n\nclass _ConstantsContainerType(type):\n    \"\"\"\n    L{_ConstantsContainerType} is a metaclass for creating constants container\n    classes.\n    \"\"\"\n    def __new__(self, name, bases, attributes):\n        \"\"\"\n        Create a new constants container class.\n\n        If C{attributes} includes a value of C{None} for the C{\"_constantType\"}\n        key, the new class will not be initialized as a constants container and\n        it will behave as a normal class.\n\n        @param name: The name of the container class.\n        @type name: L{str}\n\n        @param bases: A tuple of the base classes for the new container class.\n        @type bases: L{tuple} of L{_ConstantsContainerType} instances\n\n        @param attributes: The attributes of the new container class, including\n            any constants it is to contain.\n        @type attributes: L{dict}\n        \"\"\"\n        cls = super(_ConstantsContainerType, self).__new__(\n            self, name, bases, attributes)\n\n        # Only realize constants in concrete _ConstantsContainer subclasses.\n        # Ignore intermediate base classes.\n        constantType = getattr(cls, '_constantType', None)\n        if constantType is None:\n            return cls\n\n        constants = []\n        for (name, descriptor) in attributes.items():\n            if isinstance(descriptor, cls._constantType):\n                if descriptor._container is not None:\n                    raise ValueError(\n                        \"Cannot use %s as the value of an attribute on %s\" % (\n                            descriptor, cls.__name__))\n                constants.append((descriptor._index, name, descriptor))\n\n        enumerants = {}\n        for (index, enumerant, descriptor) in sorted(constants):\n            value = cls._constantFactory(enumerant, descriptor)\n            descriptor._realize(cls, enumerant, value)\n            enumerants[enumerant] = descriptor\n\n        # Save the dictionary which contains *only* constants (distinct from\n        # any other attributes the application may have given the container)\n        # where the class can use it later (eg for lookupByName).\n        cls._enumerants = enumerants\n\n        return cls\n\n\n\n# In Python3 metaclasses are defined using a C{metaclass} keyword argument in\n# the class definition. This would cause a syntax error in Python2.\n# So we use L{type} to introduce an intermediate base class with the desired\n# metaclass.\n# See:\n# * http://docs.python.org/2/library/functions.html#type\n# * http://docs.python.org/3/reference/datamodel.html#customizing-class-creation\nclass _ConstantsContainer(_ConstantsContainerType('', (object,), {})):\n    \"\"\"\n    L{_ConstantsContainer} is a class with attributes used as symbolic\n    constants.  It is up to subclasses to specify what kind of constants are\n    allowed.\n\n    @cvar _constantType: Specified by a L{_ConstantsContainer} subclass to\n        specify the type of constants allowed by that subclass.\n\n    @cvar _enumerants: A C{dict} mapping the names of constants (eg\n        L{NamedConstant} instances) found in the class definition to those\n        instances.\n    \"\"\"\n\n    _constantType = None\n\n    def __new__(cls):\n        \"\"\"\n        Classes representing constants containers are not intended to be\n        instantiated.\n\n        The class object itself is used directly.\n        \"\"\"\n        raise TypeError(\"%s may not be instantiated.\" % (cls.__name__,))\n\n\n    @classmethod\n    def _constantFactory(cls, name, descriptor):\n        \"\"\"\n        Construct the value for a new constant to add to this container.\n\n        @param name: The name of the constant to create.\n\n        @param descriptor: An instance of a L{_Constant} subclass (eg\n            L{NamedConstant}) which is assigned to C{name}.\n\n        @return: L{NamedConstant} instances have no value apart from identity,\n            so return a meaningless dummy value.\n        \"\"\"\n        return _unspecified\n\n\n    @classmethod\n    def lookupByName(cls, name):\n        \"\"\"\n        Retrieve a constant by its name or raise a C{ValueError} if there is no\n        constant associated with that name.\n\n        @param name: A C{str} giving the name of one of the constants defined\n            by C{cls}.\n\n        @raise ValueError: If C{name} is not the name of one of the constants\n            defined by C{cls}.\n\n        @return: The L{NamedConstant} associated with C{name}.\n        \"\"\"\n        if name in cls._enumerants:\n            return getattr(cls, name)\n        raise ValueError(name)\n\n\n    @classmethod\n    def iterconstants(cls):\n        \"\"\"\n        Iteration over a L{Names} subclass results in all of the constants it\n        contains.\n\n        @return: an iterator the elements of which are the L{NamedConstant}\n            instances defined in the body of this L{Names} subclass.\n        \"\"\"\n        constants = cls._enumerants.values()\n\n        return iter(\n            sorted(constants, key=lambda descriptor: descriptor._index))\n\n\n\nclass NamedConstant(_Constant):\n    \"\"\"\n    L{NamedConstant} defines an attribute to be a named constant within a\n    collection defined by a L{Names} subclass.\n\n    L{NamedConstant} is only for use in the definition of L{Names}\n    subclasses.  Do not instantiate L{NamedConstant} elsewhere and do not\n    subclass it.\n    \"\"\"\n\n\n\nclass Names(_ConstantsContainer):\n    \"\"\"\n    A L{Names} subclass contains constants which differ only in their names and\n    identities.\n    \"\"\"\n    _constantType = NamedConstant\n\n\n\nclass ValueConstant(_Constant):\n    \"\"\"\n    L{ValueConstant} defines an attribute to be a named constant within a\n    collection defined by a L{Values} subclass.\n\n    L{ValueConstant} is only for use in the definition of L{Values} subclasses.\n    Do not instantiate L{ValueConstant} elsewhere and do not subclass it.\n    \"\"\"\n    def __init__(self, value):\n        _Constant.__init__(self)\n        self.value = value\n\n\n\nclass Values(_ConstantsContainer):\n    \"\"\"\n    A L{Values} subclass contains constants which are associated with arbitrary\n    values.\n    \"\"\"\n    _constantType = ValueConstant\n\n    @classmethod\n    def lookupByValue(cls, value):\n        \"\"\"\n        Retrieve a constant by its value or raise a C{ValueError} if there is\n        no constant associated with that value.\n\n        @param value: The value of one of the constants defined by C{cls}.\n\n        @raise ValueError: If C{value} is not the value of one of the constants\n            defined by C{cls}.\n\n        @return: The L{ValueConstant} associated with C{value}.\n        \"\"\"\n        for constant in cls.iterconstants():\n            if constant.value == value:\n                return constant\n        raise ValueError(value)\n\n\n\ndef _flagOp(op, left, right):\n    \"\"\"\n    Implement a binary operator for a L{FlagConstant} instance.\n\n    @param op: A two-argument callable implementing the binary operation.  For\n        example, C{operator.or_}.\n\n    @param left: The left-hand L{FlagConstant} instance.\n    @param right: The right-hand L{FlagConstant} instance.\n\n    @return: A new L{FlagConstant} instance representing the result of the\n        operation.\n    \"\"\"\n    value = op(left.value, right.value)\n    names = op(left.names, right.names)\n    result = FlagConstant()\n    result._realize(left._container, names, value)\n    return result\n\n\n\nclass FlagConstant(_Constant):\n    \"\"\"\n    L{FlagConstant} defines an attribute to be a flag constant within a\n    collection defined by a L{Flags} subclass.\n\n    L{FlagConstant} is only for use in the definition of L{Flags} subclasses.\n    Do not instantiate L{FlagConstant} elsewhere and do not subclass it.\n    \"\"\"\n    def __init__(self, value=_unspecified):\n        _Constant.__init__(self)\n        self.value = value\n\n\n    def _realize(self, container, names, value):\n        \"\"\"\n        Complete the initialization of this L{FlagConstant}.\n\n        This implementation differs from other C{_realize} implementations in\n        that a L{FlagConstant} may have several names which apply to it, due to\n        flags being combined with various operators.\n\n        @param container: The L{Flags} subclass this constant is part of.\n\n        @param names: When a single-flag value is being initialized, a C{str}\n            giving the name of that flag.  This is the case which happens when\n            a L{Flags} subclass is being initialized and L{FlagConstant}\n            instances from its body are being realized.  Otherwise, a C{set} of\n            C{str} giving names of all the flags set on this L{FlagConstant}\n            instance.  This is the case when two flags are combined using C{|},\n            for example.\n        \"\"\"\n        if isinstance(names, str):\n            name = names\n            names = set([names])\n        elif len(names) == 1:\n            (name,) = names\n        else:\n            name = \"{\" + \",\".join(sorted(names)) + \"}\"\n        _Constant._realize(self, container, name, value)\n        self.value = value\n        self.names = names\n\n\n    def __or__(self, other):\n        \"\"\"\n        Define C{|} on two L{FlagConstant} instances to create a new\n        L{FlagConstant} instance with all flags set in either instance set.\n        \"\"\"\n        return _flagOp(or_, self, other)\n\n\n    def __and__(self, other):\n        \"\"\"\n        Define C{&} on two L{FlagConstant} instances to create a new\n        L{FlagConstant} instance with only flags set in both instances set.\n        \"\"\"\n        return _flagOp(and_, self, other)\n\n\n    def __xor__(self, other):\n        \"\"\"\n        Define C{^} on two L{FlagConstant} instances to create a new\n        L{FlagConstant} instance with only flags set on exactly one instance\n        set.\n        \"\"\"\n        return _flagOp(xor, self, other)\n\n\n    def __invert__(self):\n        \"\"\"\n        Define C{~} on a L{FlagConstant} instance to create a new\n        L{FlagConstant} instance with all flags not set on this instance set.\n        \"\"\"\n        result = FlagConstant()\n        result._realize(self._container, set(), 0)\n        for flag in self._container.iterconstants():\n            if flag.value & self.value == 0:\n                result |= flag\n        return result\n\n\n    def __iter__(self):\n        \"\"\"\n        @return: An iterator of flags set on this instance set.\n        \"\"\"\n        return (self._container.lookupByName(name) for name in self.names)\n\n\n    def __contains__(self, flag):\n        \"\"\"\n        @param flag: The flag to test for membership in this instance\n            set.\n\n        @return: C{True} if C{flag} is in this instance set, else\n            C{False}.\n        \"\"\"\n        # Optimization for testing membership without iteration.\n        return bool(flag & self)\n\n\n    def __nonzero__(self):\n        \"\"\"\n        @return: C{False} if this flag's value is 0, else C{True}.\n        \"\"\"\n        return bool(self.value)\n    __bool__ = __nonzero__\n\n\n\nclass Flags(Values):\n    \"\"\"\n    A L{Flags} subclass contains constants which can be combined using the\n    common bitwise operators (C{|}, C{&}, etc) similar to a I{bitvector} from a\n    language like C.\n    \"\"\"\n    _constantType = FlagConstant\n\n    _value = 1\n\n    @classmethod\n    def _constantFactory(cls, name, descriptor):\n        \"\"\"\n        For L{FlagConstant} instances with no explicitly defined value, assign\n        the next power of two as its value.\n\n        @param name: The name of the constant to create.\n\n        @param descriptor: An instance of a L{FlagConstant} which is assigned\n            to C{name}.\n\n        @return: Either the value passed to the C{descriptor} constructor, or\n            the next power of 2 value which will be assigned to C{descriptor},\n            relative to the value of the last defined L{FlagConstant}.\n        \"\"\"\n        if descriptor.value is _unspecified:\n            value = cls._value\n            cls._value <<= 1\n        else:\n            value = descriptor.value\n            cls._value = value << 1\n        return value\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/constantly/_version.py",
    "content": "\n# This file was generated by 'versioneer.py' (0.15) from\n# revision-control system data, or from the parent directory name of an\n# unpacked source archive. Distribution tarballs contain a pre-generated copy\n# of this file.\n\nimport json\nimport sys\n\nversion_json = '''\n{\n \"dirty\": false,\n \"error\": null,\n \"full-revisionid\": \"c8375a7e3431792ea1b1b44678f3f6878d5e8c9a\",\n \"version\": \"15.1.0\"\n}\n'''  # END VERSION_JSON\n\n\ndef get_versions():\n    return json.loads(version_json)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/constantly-15.1.0.dist-info/DESCRIPTION.rst",
    "content": "Constantly\n==========\n\nA library that provides symbolic constant support.\nIt includes collections and constants with text, numeric, and bit flag values.\nOriginally ``twisted.python.constants`` from the `Twisted <https://twistedmatrix.com/>`_ project.\n\n\nTests\n-----\n\nTo run tests::\n\n    $ tox\n\nThis will run tests on Python 2.7, 3.3, 3.4, and PyPy, as well as doing coverage and pyflakes checks.\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/constantly-15.1.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/constantly-15.1.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.0\nName: constantly\nVersion: 15.1.0\nSummary: Symbolic constants in Python\nHome-page: https://github.com/twisted/constantly\nAuthor: Twisted Matrix Labs Developers\nAuthor-email: UNKNOWN\nLicense: MIT\nKeywords: constants,enum,twisted\nPlatform: UNKNOWN\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: MIT License\nClassifier: Operating System :: OS Independent\nClassifier: Programming Language :: Python\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3.3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: Implementation :: CPython\nClassifier: Programming Language :: Python :: Implementation :: PyPy\nClassifier: Topic :: Software Development :: Libraries :: Python Modules\n\nConstantly\n==========\n\nA library that provides symbolic constant support.\nIt includes collections and constants with text, numeric, and bit flag values.\nOriginally ``twisted.python.constants`` from the `Twisted <https://twistedmatrix.com/>`_ project.\n\n\nTests\n-----\n\nTo run tests::\n\n    $ tox\n\nThis will run tests on Python 2.7, 3.3, 3.4, and PyPy, as well as doing coverage and pyflakes checks.\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/constantly-15.1.0.dist-info/RECORD",
    "content": "constantly-15.1.0.dist-info/DESCRIPTION.rst,sha256=sx7cfQa9trLrI06ORsPDOgA4UkW9KdPxYfygiqt50R4,397\r\nconstantly-15.1.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nconstantly-15.1.0.dist-info/METADATA,sha256=4Rt-WjQ0S-JhhzVk__zpXfYLaC7KaVjQzW9SVaBhwoY,1214\r\nconstantly-15.1.0.dist-info/RECORD,,\r\nconstantly-15.1.0.dist-info/WHEEL,sha256=AvR0WeTpDaxT645bl5FQxUK6NPsTls2ttpcGJg3j1Xg,110\r\nconstantly-15.1.0.dist-info/metadata.json,sha256=y1-W-VJW79doSoMail8qNDduY5oHC2JGG1-tBZ_dA0k,923\r\nconstantly-15.1.0.dist-info/pbr.json,sha256=of4UIk4TOAoS3Gxf7oE2PwaRBcQW2ij9ZLRX1LMhy1A,47\r\nconstantly-15.1.0.dist-info/top_level.txt,sha256=Z3LZxRT3sV7OIcLddygWy8rRaguc4a1hlGotDs-vFIM,11\r\nconstantly/__init__.py,sha256=K2EFx89mIF8TkuE4F2ZhqeiE9UuB9S0DpFy0SNhu6uc,517\r\nconstantly/__pycache__/__init__.cpython-36.pyc,,\r\nconstantly/__pycache__/_constants.cpython-36.pyc,,\r\nconstantly/__pycache__/_version.cpython-36.pyc,,\r\nconstantly/_constants.py,sha256=n-QpkK73fCIyebkqp6hvUMuEe3uYeIptBtl4KahxpcI,16090\r\nconstantly/_version.py,sha256=kp8Hoj2tpH_Xpb4CONVFfYjTpEOr3EGzNRaT_IFZ3Ao,472\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/constantly-15.1.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.24.0)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/constantly-15.1.0.dist-info/metadata.json",
    "content": "{\"license\": \"MIT\", \"name\": \"constantly\", \"metadata_version\": \"2.0\", \"generator\": \"bdist_wheel (0.24.0)\", \"summary\": \"Symbolic constants in Python\", \"version\": \"15.1.0\", \"extensions\": {\"python.details\": {\"project_urls\": {\"Home\": \"https://github.com/twisted/constantly\"}, \"document_names\": {\"description\": \"DESCRIPTION.rst\"}, \"contacts\": [{\"role\": \"author\", \"name\": \"Twisted Matrix Labs Developers\"}]}}, \"keywords\": [\"constants\", \"enum\", \"twisted\"], \"classifiers\": [\"Intended Audience :: Developers\", \"License :: OSI Approved :: MIT License\", \"Operating System :: OS Independent\", \"Programming Language :: Python\", \"Programming Language :: Python :: 2.7\", \"Programming Language :: Python :: 3.3\", \"Programming Language :: Python :: 3.4\", \"Programming Language :: Python :: Implementation :: CPython\", \"Programming Language :: Python :: Implementation :: PyPy\", \"Topic :: Software Development :: Libraries :: Python Modules\"]}"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/constantly-15.1.0.dist-info/pbr.json",
    "content": "{\"is_release\": false, \"git_version\": \"c8375a7\"}"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/constantly-15.1.0.dist-info/top_level.txt",
    "content": "constantly\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/__about__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\n__all__ = [\n    \"__title__\", \"__summary__\", \"__uri__\", \"__version__\", \"__author__\",\n    \"__email__\", \"__license__\", \"__copyright__\",\n]\n\n__title__ = \"cryptography\"\n__summary__ = (\"cryptography is a package which provides cryptographic recipes\"\n               \" and primitives to Python developers.\")\n__uri__ = \"https://github.com/pyca/cryptography\"\n\n__version__ = \"2.8\"\n\n__author__ = \"The cryptography developers\"\n__email__ = \"cryptography-dev@python.org\"\n\n__license__ = \"BSD or Apache License, Version 2.0\"\n__copyright__ = \"Copyright 2013-2019 {}\".format(__author__)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography.__about__ import (\n    __author__, __copyright__, __email__, __license__, __summary__, __title__,\n    __uri__, __version__\n)\n\n\n__all__ = [\n    \"__title__\", \"__summary__\", \"__uri__\", \"__version__\", \"__author__\",\n    \"__email__\", \"__license__\", \"__copyright__\",\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/exceptions.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom enum import Enum\n\n\nclass _Reasons(Enum):\n    BACKEND_MISSING_INTERFACE = 0\n    UNSUPPORTED_HASH = 1\n    UNSUPPORTED_CIPHER = 2\n    UNSUPPORTED_PADDING = 3\n    UNSUPPORTED_MGF = 4\n    UNSUPPORTED_PUBLIC_KEY_ALGORITHM = 5\n    UNSUPPORTED_ELLIPTIC_CURVE = 6\n    UNSUPPORTED_SERIALIZATION = 7\n    UNSUPPORTED_X509 = 8\n    UNSUPPORTED_EXCHANGE_ALGORITHM = 9\n    UNSUPPORTED_DIFFIE_HELLMAN = 10\n    UNSUPPORTED_MAC = 11\n\n\nclass UnsupportedAlgorithm(Exception):\n    def __init__(self, message, reason=None):\n        super(UnsupportedAlgorithm, self).__init__(message)\n        self._reason = reason\n\n\nclass AlreadyFinalized(Exception):\n    pass\n\n\nclass AlreadyUpdated(Exception):\n    pass\n\n\nclass NotYetFinalized(Exception):\n    pass\n\n\nclass InvalidTag(Exception):\n    pass\n\n\nclass InvalidSignature(Exception):\n    pass\n\n\nclass InternalError(Exception):\n    def __init__(self, msg, err_code):\n        super(InternalError, self).__init__(msg)\n        self.err_code = err_code\n\n\nclass InvalidKey(Exception):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/fernet.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport base64\nimport binascii\nimport os\nimport struct\nimport time\n\nimport six\n\nfrom cryptography import utils\nfrom cryptography.exceptions import InvalidSignature\nfrom cryptography.hazmat.backends import default_backend\nfrom cryptography.hazmat.primitives import hashes, padding\nfrom cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes\nfrom cryptography.hazmat.primitives.hmac import HMAC\n\n\nclass InvalidToken(Exception):\n    pass\n\n\n_MAX_CLOCK_SKEW = 60\n\n\nclass Fernet(object):\n    def __init__(self, key, backend=None):\n        if backend is None:\n            backend = default_backend()\n\n        key = base64.urlsafe_b64decode(key)\n        if len(key) != 32:\n            raise ValueError(\n                \"Fernet key must be 32 url-safe base64-encoded bytes.\"\n            )\n\n        self._signing_key = key[:16]\n        self._encryption_key = key[16:]\n        self._backend = backend\n\n    @classmethod\n    def generate_key(cls):\n        return base64.urlsafe_b64encode(os.urandom(32))\n\n    def encrypt(self, data):\n        current_time = int(time.time())\n        iv = os.urandom(16)\n        return self._encrypt_from_parts(data, current_time, iv)\n\n    def _encrypt_from_parts(self, data, current_time, iv):\n        utils._check_bytes(\"data\", data)\n\n        padder = padding.PKCS7(algorithms.AES.block_size).padder()\n        padded_data = padder.update(data) + padder.finalize()\n        encryptor = Cipher(\n            algorithms.AES(self._encryption_key), modes.CBC(iv), self._backend\n        ).encryptor()\n        ciphertext = encryptor.update(padded_data) + encryptor.finalize()\n\n        basic_parts = (\n            b\"\\x80\" + struct.pack(\">Q\", current_time) + iv + ciphertext\n        )\n\n        h = HMAC(self._signing_key, hashes.SHA256(), backend=self._backend)\n        h.update(basic_parts)\n        hmac = h.finalize()\n        return base64.urlsafe_b64encode(basic_parts + hmac)\n\n    def decrypt(self, token, ttl=None):\n        timestamp, data = Fernet._get_unverified_token_data(token)\n        return self._decrypt_data(data, timestamp, ttl)\n\n    def extract_timestamp(self, token):\n        timestamp, data = Fernet._get_unverified_token_data(token)\n        # Verify the token was not tampered with.\n        self._verify_signature(data)\n        return timestamp\n\n    @staticmethod\n    def _get_unverified_token_data(token):\n        utils._check_bytes(\"token\", token)\n        try:\n            data = base64.urlsafe_b64decode(token)\n        except (TypeError, binascii.Error):\n            raise InvalidToken\n\n        if not data or six.indexbytes(data, 0) != 0x80:\n            raise InvalidToken\n\n        try:\n            timestamp, = struct.unpack(\">Q\", data[1:9])\n        except struct.error:\n            raise InvalidToken\n        return timestamp, data\n\n    def _verify_signature(self, data):\n        h = HMAC(self._signing_key, hashes.SHA256(), backend=self._backend)\n        h.update(data[:-32])\n        try:\n            h.verify(data[-32:])\n        except InvalidSignature:\n            raise InvalidToken\n\n    def _decrypt_data(self, data, timestamp, ttl):\n        current_time = int(time.time())\n        if ttl is not None:\n            if timestamp + ttl < current_time:\n                raise InvalidToken\n\n            if current_time + _MAX_CLOCK_SKEW < timestamp:\n                raise InvalidToken\n\n        self._verify_signature(data)\n\n        iv = data[9:25]\n        ciphertext = data[25:-32]\n        decryptor = Cipher(\n            algorithms.AES(self._encryption_key), modes.CBC(iv), self._backend\n        ).decryptor()\n        plaintext_padded = decryptor.update(ciphertext)\n        try:\n            plaintext_padded += decryptor.finalize()\n        except ValueError:\n            raise InvalidToken\n        unpadder = padding.PKCS7(algorithms.AES.block_size).unpadder()\n\n        unpadded = unpadder.update(plaintext_padded)\n        try:\n            unpadded += unpadder.finalize()\n        except ValueError:\n            raise InvalidToken\n        return unpadded\n\n\nclass MultiFernet(object):\n    def __init__(self, fernets):\n        fernets = list(fernets)\n        if not fernets:\n            raise ValueError(\n                \"MultiFernet requires at least one Fernet instance\"\n            )\n        self._fernets = fernets\n\n    def encrypt(self, msg):\n        return self._fernets[0].encrypt(msg)\n\n    def rotate(self, msg):\n        timestamp, data = Fernet._get_unverified_token_data(msg)\n        for f in self._fernets:\n            try:\n                p = f._decrypt_data(data, timestamp, None)\n                break\n            except InvalidToken:\n                pass\n        else:\n            raise InvalidToken\n\n        iv = os.urandom(16)\n        return self._fernets[0]._encrypt_from_parts(p, timestamp, iv)\n\n    def decrypt(self, msg, ttl=None):\n        for f in self._fernets:\n            try:\n                return f.decrypt(msg, ttl)\n            except InvalidToken:\n                pass\n        raise InvalidToken\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\"\"\"\nHazardous Materials\n\nThis is a \"Hazardous Materials\" module. You should ONLY use it if you're\n100% absolutely sure that you know what you're doing because this module\nis full of land mines, dragons, and dinosaurs with laser guns.\n\"\"\"\nfrom __future__ import absolute_import, division, print_function\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/_der.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport six\n\nfrom cryptography.utils import int_from_bytes, int_to_bytes\n\n\n# This module contains a lightweight DER encoder and decoder. See X.690 for the\n# specification. This module intentionally does not implement the more complex\n# BER encoding, only DER.\n#\n# Note this implementation treats an element's constructed bit as part of the\n# tag. This is fine for DER, where the bit is always computable from the type.\n\n\nCONSTRUCTED = 0x20\nCONTEXT_SPECIFIC = 0x80\n\nINTEGER = 0x02\nBIT_STRING = 0x03\nOCTET_STRING = 0x04\nNULL = 0x05\nOBJECT_IDENTIFIER = 0x06\nSEQUENCE = 0x10 | CONSTRUCTED\nSET = 0x11 | CONSTRUCTED\nPRINTABLE_STRING = 0x13\nUTC_TIME = 0x17\nGENERALIZED_TIME = 0x18\n\n\nclass DERReader(object):\n    def __init__(self, data):\n        self.data = memoryview(data)\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_value, tb):\n        if exc_value is None:\n            self.check_empty()\n\n    def is_empty(self):\n        return len(self.data) == 0\n\n    def check_empty(self):\n        if not self.is_empty():\n            raise ValueError(\"Invalid DER input: trailing data\")\n\n    def read_byte(self):\n        if len(self.data) < 1:\n            raise ValueError(\"Invalid DER input: insufficient data\")\n        ret = six.indexbytes(self.data, 0)\n        self.data = self.data[1:]\n        return ret\n\n    def read_bytes(self, n):\n        if len(self.data) < n:\n            raise ValueError(\"Invalid DER input: insufficient data\")\n        ret = self.data[:n]\n        self.data = self.data[n:]\n        return ret\n\n    def read_any_element(self):\n        tag = self.read_byte()\n        # Tag numbers 31 or higher are stored in multiple bytes. No supported\n        # ASN.1 types use such tags, so reject these.\n        if tag & 0x1f == 0x1f:\n            raise ValueError(\"Invalid DER input: unexpected high tag number\")\n        length_byte = self.read_byte()\n        if length_byte & 0x80 == 0:\n            # If the high bit is clear, the first length byte is the length.\n            length = length_byte\n        else:\n            # If the high bit is set, the first length byte encodes the length\n            # of the length.\n            length_byte &= 0x7f\n            if length_byte == 0:\n                raise ValueError(\n                    \"Invalid DER input: indefinite length form is not allowed \"\n                    \"in DER\"\n                )\n            length = 0\n            for i in range(length_byte):\n                length <<= 8\n                length |= self.read_byte()\n                if length == 0:\n                    raise ValueError(\n                        \"Invalid DER input: length was not minimally-encoded\"\n                    )\n            if length < 0x80:\n                # If the length could have been encoded in short form, it must\n                # not use long form.\n                raise ValueError(\n                    \"Invalid DER input: length was not minimally-encoded\"\n                )\n        body = self.read_bytes(length)\n        return tag, DERReader(body)\n\n    def read_element(self, expected_tag):\n        tag, body = self.read_any_element()\n        if tag != expected_tag:\n            raise ValueError(\"Invalid DER input: unexpected tag\")\n        return body\n\n    def read_single_element(self, expected_tag):\n        with self:\n            return self.read_element(expected_tag)\n\n    def read_optional_element(self, expected_tag):\n        if len(self.data) > 0 and six.indexbytes(self.data, 0) == expected_tag:\n            return self.read_element(expected_tag)\n        return None\n\n    def as_integer(self):\n        if len(self.data) == 0:\n            raise ValueError(\"Invalid DER input: empty integer contents\")\n        first = six.indexbytes(self.data, 0)\n        if first & 0x80 == 0x80:\n            raise ValueError(\"Negative DER integers are not supported\")\n        # The first 9 bits must not all be zero or all be ones. Otherwise, the\n        # encoding should have been one byte shorter.\n        if len(self.data) > 1:\n            second = six.indexbytes(self.data, 1)\n            if first == 0 and second & 0x80 == 0:\n                raise ValueError(\n                    \"Invalid DER input: integer not minimally-encoded\"\n                )\n        return int_from_bytes(self.data, \"big\")\n\n\ndef encode_der_integer(x):\n    if not isinstance(x, six.integer_types):\n        raise ValueError(\"Value must be an integer\")\n    if x < 0:\n        raise ValueError(\"Negative integers are not supported\")\n    n = x.bit_length() // 8 + 1\n    return int_to_bytes(x, n)\n\n\ndef encode_der(tag, *children):\n    length = 0\n    for child in children:\n        length += len(child)\n    chunks = [six.int2byte(tag)]\n    if length < 0x80:\n        chunks.append(six.int2byte(length))\n    else:\n        length_bytes = int_to_bytes(length)\n        chunks.append(six.int2byte(0x80 | len(length_bytes)))\n        chunks.append(length_bytes)\n    chunks.extend(children)\n    return b\"\".join(chunks)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/_oid.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import utils\n\n\nclass ObjectIdentifier(object):\n    def __init__(self, dotted_string):\n        self._dotted_string = dotted_string\n\n        nodes = self._dotted_string.split(\".\")\n        intnodes = []\n\n        # There must be at least 2 nodes, the first node must be 0..2, and\n        # if less than 2, the second node cannot have a value outside the\n        # range 0..39.  All nodes must be integers.\n        for node in nodes:\n            try:\n                intnodes.append(int(node, 0))\n            except ValueError:\n                raise ValueError(\n                    \"Malformed OID: %s (non-integer nodes)\" % (\n                        self._dotted_string))\n\n        if len(nodes) < 2:\n            raise ValueError(\n                \"Malformed OID: %s (insufficient number of nodes)\" % (\n                    self._dotted_string))\n\n        if intnodes[0] > 2:\n            raise ValueError(\n                \"Malformed OID: %s (first node outside valid range)\" % (\n                    self._dotted_string))\n\n        if intnodes[0] < 2 and intnodes[1] >= 40:\n            raise ValueError(\n                \"Malformed OID: %s (second node outside valid range)\" % (\n                    self._dotted_string))\n\n    def __eq__(self, other):\n        if not isinstance(other, ObjectIdentifier):\n            return NotImplemented\n\n        return self.dotted_string == other.dotted_string\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __repr__(self):\n        return \"<ObjectIdentifier(oid={}, name={})>\".format(\n            self.dotted_string,\n            self._name\n        )\n\n    def __hash__(self):\n        return hash(self.dotted_string)\n\n    @property\n    def _name(self):\n        # Lazy import to avoid an import cycle\n        from cryptography.x509.oid import _OID_NAMES\n        return _OID_NAMES.get(self, \"Unknown OID\")\n\n    dotted_string = utils.read_only_property(\"_dotted_string\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\n\n_default_backend = None\n\n\ndef default_backend():\n    global _default_backend\n\n    if _default_backend is None:\n        from cryptography.hazmat.backends.openssl.backend import backend\n        _default_backend = backend\n\n    return _default_backend\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/interfaces.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass CipherBackend(object):\n    @abc.abstractmethod\n    def cipher_supported(self, cipher, mode):\n        \"\"\"\n        Return True if the given cipher and mode are supported.\n        \"\"\"\n\n    @abc.abstractmethod\n    def create_symmetric_encryption_ctx(self, cipher, mode):\n        \"\"\"\n        Get a CipherContext that can be used for encryption.\n        \"\"\"\n\n    @abc.abstractmethod\n    def create_symmetric_decryption_ctx(self, cipher, mode):\n        \"\"\"\n        Get a CipherContext that can be used for decryption.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass HashBackend(object):\n    @abc.abstractmethod\n    def hash_supported(self, algorithm):\n        \"\"\"\n        Return True if the hash algorithm is supported by this backend.\n        \"\"\"\n\n    @abc.abstractmethod\n    def create_hash_ctx(self, algorithm):\n        \"\"\"\n        Create a HashContext for calculating a message digest.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass HMACBackend(object):\n    @abc.abstractmethod\n    def hmac_supported(self, algorithm):\n        \"\"\"\n        Return True if the hash algorithm is supported for HMAC by this\n        backend.\n        \"\"\"\n\n    @abc.abstractmethod\n    def create_hmac_ctx(self, key, algorithm):\n        \"\"\"\n        Create a context for calculating a message authentication code.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass CMACBackend(object):\n    @abc.abstractmethod\n    def cmac_algorithm_supported(self, algorithm):\n        \"\"\"\n        Returns True if the block cipher is supported for CMAC by this backend\n        \"\"\"\n\n    @abc.abstractmethod\n    def create_cmac_ctx(self, algorithm):\n        \"\"\"\n        Create a context for calculating a message authentication code.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass PBKDF2HMACBackend(object):\n    @abc.abstractmethod\n    def pbkdf2_hmac_supported(self, algorithm):\n        \"\"\"\n        Return True if the hash algorithm is supported for PBKDF2 by this\n        backend.\n        \"\"\"\n\n    @abc.abstractmethod\n    def derive_pbkdf2_hmac(self, algorithm, length, salt, iterations,\n                           key_material):\n        \"\"\"\n        Return length bytes derived from provided PBKDF2 parameters.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass RSABackend(object):\n    @abc.abstractmethod\n    def generate_rsa_private_key(self, public_exponent, key_size):\n        \"\"\"\n        Generate an RSAPrivateKey instance with public_exponent and a modulus\n        of key_size bits.\n        \"\"\"\n\n    @abc.abstractmethod\n    def rsa_padding_supported(self, padding):\n        \"\"\"\n        Returns True if the backend supports the given padding options.\n        \"\"\"\n\n    @abc.abstractmethod\n    def generate_rsa_parameters_supported(self, public_exponent, key_size):\n        \"\"\"\n        Returns True if the backend supports the given parameters for key\n        generation.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_rsa_private_numbers(self, numbers):\n        \"\"\"\n        Returns an RSAPrivateKey provider.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_rsa_public_numbers(self, numbers):\n        \"\"\"\n        Returns an RSAPublicKey provider.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass DSABackend(object):\n    @abc.abstractmethod\n    def generate_dsa_parameters(self, key_size):\n        \"\"\"\n        Generate a DSAParameters instance with a modulus of key_size bits.\n        \"\"\"\n\n    @abc.abstractmethod\n    def generate_dsa_private_key(self, parameters):\n        \"\"\"\n        Generate a DSAPrivateKey instance with parameters as a DSAParameters\n        object.\n        \"\"\"\n\n    @abc.abstractmethod\n    def generate_dsa_private_key_and_parameters(self, key_size):\n        \"\"\"\n        Generate a DSAPrivateKey instance using key size only.\n        \"\"\"\n\n    @abc.abstractmethod\n    def dsa_hash_supported(self, algorithm):\n        \"\"\"\n        Return True if the hash algorithm is supported by the backend for DSA.\n        \"\"\"\n\n    @abc.abstractmethod\n    def dsa_parameters_supported(self, p, q, g):\n        \"\"\"\n        Return True if the parameters are supported by the backend for DSA.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_dsa_private_numbers(self, numbers):\n        \"\"\"\n        Returns a DSAPrivateKey provider.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_dsa_public_numbers(self, numbers):\n        \"\"\"\n        Returns a DSAPublicKey provider.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_dsa_parameter_numbers(self, numbers):\n        \"\"\"\n        Returns a DSAParameters provider.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass EllipticCurveBackend(object):\n    @abc.abstractmethod\n    def elliptic_curve_signature_algorithm_supported(\n        self, signature_algorithm, curve\n    ):\n        \"\"\"\n        Returns True if the backend supports the named elliptic curve with the\n        specified signature algorithm.\n        \"\"\"\n\n    @abc.abstractmethod\n    def elliptic_curve_supported(self, curve):\n        \"\"\"\n        Returns True if the backend supports the named elliptic curve.\n        \"\"\"\n\n    @abc.abstractmethod\n    def generate_elliptic_curve_private_key(self, curve):\n        \"\"\"\n        Return an object conforming to the EllipticCurvePrivateKey interface.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_elliptic_curve_public_numbers(self, numbers):\n        \"\"\"\n        Return an EllipticCurvePublicKey provider using the given numbers.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_elliptic_curve_private_numbers(self, numbers):\n        \"\"\"\n        Return an EllipticCurvePrivateKey provider using the given numbers.\n        \"\"\"\n\n    @abc.abstractmethod\n    def elliptic_curve_exchange_algorithm_supported(self, algorithm, curve):\n        \"\"\"\n        Returns whether the exchange algorithm is supported by this backend.\n        \"\"\"\n\n    @abc.abstractmethod\n    def derive_elliptic_curve_private_key(self, private_value, curve):\n        \"\"\"\n        Compute the private key given the private value and curve.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass PEMSerializationBackend(object):\n    @abc.abstractmethod\n    def load_pem_private_key(self, data, password):\n        \"\"\"\n        Loads a private key from PEM encoded data, using the provided password\n        if the data is encrypted.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_pem_public_key(self, data):\n        \"\"\"\n        Loads a public key from PEM encoded data.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_pem_parameters(self, data):\n        \"\"\"\n        Load encryption parameters from PEM encoded data.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass DERSerializationBackend(object):\n    @abc.abstractmethod\n    def load_der_private_key(self, data, password):\n        \"\"\"\n        Loads a private key from DER encoded data. Uses the provided password\n        if the data is encrypted.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_der_public_key(self, data):\n        \"\"\"\n        Loads a public key from DER encoded data.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_der_parameters(self, data):\n        \"\"\"\n        Load encryption parameters from DER encoded data.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass X509Backend(object):\n    @abc.abstractmethod\n    def load_pem_x509_certificate(self, data):\n        \"\"\"\n        Load an X.509 certificate from PEM encoded data.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_der_x509_certificate(self, data):\n        \"\"\"\n        Load an X.509 certificate from DER encoded data.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_der_x509_csr(self, data):\n        \"\"\"\n        Load an X.509 CSR from DER encoded data.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_pem_x509_csr(self, data):\n        \"\"\"\n        Load an X.509 CSR from PEM encoded data.\n        \"\"\"\n\n    @abc.abstractmethod\n    def create_x509_csr(self, builder, private_key, algorithm):\n        \"\"\"\n        Create and sign an X.509 CSR from a CSR builder object.\n        \"\"\"\n\n    @abc.abstractmethod\n    def create_x509_certificate(self, builder, private_key, algorithm):\n        \"\"\"\n        Create and sign an X.509 certificate from a CertificateBuilder object.\n        \"\"\"\n\n    @abc.abstractmethod\n    def create_x509_crl(self, builder, private_key, algorithm):\n        \"\"\"\n        Create and sign an X.509 CertificateRevocationList from a\n        CertificateRevocationListBuilder object.\n        \"\"\"\n\n    @abc.abstractmethod\n    def create_x509_revoked_certificate(self, builder):\n        \"\"\"\n        Create a RevokedCertificate object from a RevokedCertificateBuilder\n        object.\n        \"\"\"\n\n    @abc.abstractmethod\n    def x509_name_bytes(self, name):\n        \"\"\"\n        Compute the DER encoded bytes of an X509 Name object.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass DHBackend(object):\n    @abc.abstractmethod\n    def generate_dh_parameters(self, generator, key_size):\n        \"\"\"\n        Generate a DHParameters instance with a modulus of key_size bits.\n        Using the given generator. Often 2 or 5.\n        \"\"\"\n\n    @abc.abstractmethod\n    def generate_dh_private_key(self, parameters):\n        \"\"\"\n        Generate a DHPrivateKey instance with parameters as a DHParameters\n        object.\n        \"\"\"\n\n    @abc.abstractmethod\n    def generate_dh_private_key_and_parameters(self, generator, key_size):\n        \"\"\"\n        Generate a DHPrivateKey instance using key size only.\n        Using the given generator. Often 2 or 5.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_dh_private_numbers(self, numbers):\n        \"\"\"\n        Load a DHPrivateKey from DHPrivateNumbers\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_dh_public_numbers(self, numbers):\n        \"\"\"\n        Load a DHPublicKey from DHPublicNumbers.\n        \"\"\"\n\n    @abc.abstractmethod\n    def load_dh_parameter_numbers(self, numbers):\n        \"\"\"\n        Load DHParameters from DHParameterNumbers.\n        \"\"\"\n\n    @abc.abstractmethod\n    def dh_parameters_supported(self, p, g, q=None):\n        \"\"\"\n        Returns whether the backend supports DH with these parameter values.\n        \"\"\"\n\n    @abc.abstractmethod\n    def dh_x942_serialization_supported(self):\n        \"\"\"\n        Returns True if the backend supports the serialization of DH objects\n        with subgroup order (q).\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass ScryptBackend(object):\n    @abc.abstractmethod\n    def derive_scrypt(self, key_material, salt, length, n, r, p):\n        \"\"\"\n        Return bytes derived from provided Scrypt parameters.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography.hazmat.backends.openssl.backend import backend\n\n\n__all__ = [\"backend\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/aead.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography.exceptions import InvalidTag\n\n\n_ENCRYPT = 1\n_DECRYPT = 0\n\n\ndef _aead_cipher_name(cipher):\n    from cryptography.hazmat.primitives.ciphers.aead import (\n        AESCCM, AESGCM, ChaCha20Poly1305\n    )\n    if isinstance(cipher, ChaCha20Poly1305):\n        return b\"chacha20-poly1305\"\n    elif isinstance(cipher, AESCCM):\n        return \"aes-{}-ccm\".format(len(cipher._key) * 8).encode(\"ascii\")\n    else:\n        assert isinstance(cipher, AESGCM)\n        return \"aes-{}-gcm\".format(len(cipher._key) * 8).encode(\"ascii\")\n\n\ndef _aead_setup(backend, cipher_name, key, nonce, tag, tag_len, operation):\n    evp_cipher = backend._lib.EVP_get_cipherbyname(cipher_name)\n    backend.openssl_assert(evp_cipher != backend._ffi.NULL)\n    ctx = backend._lib.EVP_CIPHER_CTX_new()\n    ctx = backend._ffi.gc(ctx, backend._lib.EVP_CIPHER_CTX_free)\n    res = backend._lib.EVP_CipherInit_ex(\n        ctx, evp_cipher,\n        backend._ffi.NULL,\n        backend._ffi.NULL,\n        backend._ffi.NULL,\n        int(operation == _ENCRYPT)\n    )\n    backend.openssl_assert(res != 0)\n    res = backend._lib.EVP_CIPHER_CTX_set_key_length(ctx, len(key))\n    backend.openssl_assert(res != 0)\n    res = backend._lib.EVP_CIPHER_CTX_ctrl(\n        ctx, backend._lib.EVP_CTRL_AEAD_SET_IVLEN, len(nonce),\n        backend._ffi.NULL\n    )\n    backend.openssl_assert(res != 0)\n    if operation == _DECRYPT:\n        res = backend._lib.EVP_CIPHER_CTX_ctrl(\n            ctx, backend._lib.EVP_CTRL_AEAD_SET_TAG, len(tag), tag\n        )\n        backend.openssl_assert(res != 0)\n    elif cipher_name.endswith(b\"-ccm\"):\n        res = backend._lib.EVP_CIPHER_CTX_ctrl(\n            ctx, backend._lib.EVP_CTRL_AEAD_SET_TAG, tag_len, backend._ffi.NULL\n        )\n        backend.openssl_assert(res != 0)\n\n    nonce_ptr = backend._ffi.from_buffer(nonce)\n    key_ptr = backend._ffi.from_buffer(key)\n    res = backend._lib.EVP_CipherInit_ex(\n        ctx,\n        backend._ffi.NULL,\n        backend._ffi.NULL,\n        key_ptr,\n        nonce_ptr,\n        int(operation == _ENCRYPT)\n    )\n    backend.openssl_assert(res != 0)\n    return ctx\n\n\ndef _set_length(backend, ctx, data_len):\n    intptr = backend._ffi.new(\"int *\")\n    res = backend._lib.EVP_CipherUpdate(\n        ctx,\n        backend._ffi.NULL,\n        intptr,\n        backend._ffi.NULL,\n        data_len\n    )\n    backend.openssl_assert(res != 0)\n\n\ndef _process_aad(backend, ctx, associated_data):\n    outlen = backend._ffi.new(\"int *\")\n    res = backend._lib.EVP_CipherUpdate(\n        ctx, backend._ffi.NULL, outlen, associated_data, len(associated_data)\n    )\n    backend.openssl_assert(res != 0)\n\n\ndef _process_data(backend, ctx, data):\n    outlen = backend._ffi.new(\"int *\")\n    buf = backend._ffi.new(\"unsigned char[]\", len(data))\n    res = backend._lib.EVP_CipherUpdate(ctx, buf, outlen, data, len(data))\n    backend.openssl_assert(res != 0)\n    return backend._ffi.buffer(buf, outlen[0])[:]\n\n\ndef _encrypt(backend, cipher, nonce, data, associated_data, tag_length):\n    from cryptography.hazmat.primitives.ciphers.aead import AESCCM\n    cipher_name = _aead_cipher_name(cipher)\n    ctx = _aead_setup(\n        backend, cipher_name, cipher._key, nonce, None, tag_length, _ENCRYPT\n    )\n    # CCM requires us to pass the length of the data before processing anything\n    # However calling this with any other AEAD results in an error\n    if isinstance(cipher, AESCCM):\n        _set_length(backend, ctx, len(data))\n\n    _process_aad(backend, ctx, associated_data)\n    processed_data = _process_data(backend, ctx, data)\n    outlen = backend._ffi.new(\"int *\")\n    res = backend._lib.EVP_CipherFinal_ex(ctx, backend._ffi.NULL, outlen)\n    backend.openssl_assert(res != 0)\n    backend.openssl_assert(outlen[0] == 0)\n    tag_buf = backend._ffi.new(\"unsigned char[]\", tag_length)\n    res = backend._lib.EVP_CIPHER_CTX_ctrl(\n        ctx, backend._lib.EVP_CTRL_AEAD_GET_TAG, tag_length, tag_buf\n    )\n    backend.openssl_assert(res != 0)\n    tag = backend._ffi.buffer(tag_buf)[:]\n\n    return processed_data + tag\n\n\ndef _decrypt(backend, cipher, nonce, data, associated_data, tag_length):\n    from cryptography.hazmat.primitives.ciphers.aead import AESCCM\n    if len(data) < tag_length:\n        raise InvalidTag\n    tag = data[-tag_length:]\n    data = data[:-tag_length]\n    cipher_name = _aead_cipher_name(cipher)\n    ctx = _aead_setup(\n        backend, cipher_name, cipher._key, nonce, tag, tag_length, _DECRYPT\n    )\n    # CCM requires us to pass the length of the data before processing anything\n    # However calling this with any other AEAD results in an error\n    if isinstance(cipher, AESCCM):\n        _set_length(backend, ctx, len(data))\n\n    _process_aad(backend, ctx, associated_data)\n    # CCM has a different error path if the tag doesn't match. Errors are\n    # raised in Update and Final is irrelevant.\n    if isinstance(cipher, AESCCM):\n        outlen = backend._ffi.new(\"int *\")\n        buf = backend._ffi.new(\"unsigned char[]\", len(data))\n        res = backend._lib.EVP_CipherUpdate(ctx, buf, outlen, data, len(data))\n        if res != 1:\n            backend._consume_errors()\n            raise InvalidTag\n\n        processed_data = backend._ffi.buffer(buf, outlen[0])[:]\n    else:\n        processed_data = _process_data(backend, ctx, data)\n        outlen = backend._ffi.new(\"int *\")\n        res = backend._lib.EVP_CipherFinal_ex(ctx, backend._ffi.NULL, outlen)\n        if res == 0:\n            backend._consume_errors()\n            raise InvalidTag\n\n    return processed_data\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/backend.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport base64\nimport collections\nimport contextlib\nimport itertools\nfrom contextlib import contextmanager\n\nimport six\nfrom six.moves import range\n\nfrom cryptography import utils, x509\nfrom cryptography.exceptions import UnsupportedAlgorithm, _Reasons\nfrom cryptography.hazmat._der import (\n    INTEGER, NULL, SEQUENCE, encode_der, encode_der_integer\n)\nfrom cryptography.hazmat.backends.interfaces import (\n    CMACBackend, CipherBackend, DERSerializationBackend, DHBackend, DSABackend,\n    EllipticCurveBackend, HMACBackend, HashBackend, PBKDF2HMACBackend,\n    PEMSerializationBackend, RSABackend, ScryptBackend, X509Backend\n)\nfrom cryptography.hazmat.backends.openssl import aead\nfrom cryptography.hazmat.backends.openssl.ciphers import _CipherContext\nfrom cryptography.hazmat.backends.openssl.cmac import _CMACContext\nfrom cryptography.hazmat.backends.openssl.decode_asn1 import (\n    _CRL_ENTRY_REASON_ENUM_TO_CODE\n)\nfrom cryptography.hazmat.backends.openssl.dh import (\n    _DHParameters, _DHPrivateKey, _DHPublicKey, _dh_params_dup\n)\nfrom cryptography.hazmat.backends.openssl.dsa import (\n    _DSAParameters, _DSAPrivateKey, _DSAPublicKey\n)\nfrom cryptography.hazmat.backends.openssl.ec import (\n    _EllipticCurvePrivateKey, _EllipticCurvePublicKey\n)\nfrom cryptography.hazmat.backends.openssl.ed25519 import (\n    _Ed25519PrivateKey, _Ed25519PublicKey\n)\nfrom cryptography.hazmat.backends.openssl.ed448 import (\n    _ED448_KEY_SIZE, _Ed448PrivateKey, _Ed448PublicKey\n)\nfrom cryptography.hazmat.backends.openssl.encode_asn1 import (\n    _CRL_ENTRY_EXTENSION_ENCODE_HANDLERS,\n    _CRL_EXTENSION_ENCODE_HANDLERS, _EXTENSION_ENCODE_HANDLERS,\n    _OCSP_BASICRESP_EXTENSION_ENCODE_HANDLERS,\n    _OCSP_REQUEST_EXTENSION_ENCODE_HANDLERS,\n    _encode_asn1_int_gc, _encode_asn1_str_gc, _encode_name_gc, _txt2obj_gc,\n)\nfrom cryptography.hazmat.backends.openssl.hashes import _HashContext\nfrom cryptography.hazmat.backends.openssl.hmac import _HMACContext\nfrom cryptography.hazmat.backends.openssl.ocsp import (\n    _OCSPRequest, _OCSPResponse\n)\nfrom cryptography.hazmat.backends.openssl.poly1305 import (\n    _POLY1305_KEY_SIZE, _Poly1305Context\n)\nfrom cryptography.hazmat.backends.openssl.rsa import (\n    _RSAPrivateKey, _RSAPublicKey\n)\nfrom cryptography.hazmat.backends.openssl.x25519 import (\n    _X25519PrivateKey, _X25519PublicKey\n)\nfrom cryptography.hazmat.backends.openssl.x448 import (\n    _X448PrivateKey, _X448PublicKey\n)\nfrom cryptography.hazmat.backends.openssl.x509 import (\n    _Certificate, _CertificateRevocationList,\n    _CertificateSigningRequest, _RevokedCertificate\n)\nfrom cryptography.hazmat.bindings.openssl import binding\nfrom cryptography.hazmat.primitives import hashes, serialization\nfrom cryptography.hazmat.primitives.asymmetric import (\n    dsa, ec, ed25519, ed448, rsa\n)\nfrom cryptography.hazmat.primitives.asymmetric.padding import (\n    MGF1, OAEP, PKCS1v15, PSS\n)\nfrom cryptography.hazmat.primitives.ciphers.algorithms import (\n    AES, ARC4, Blowfish, CAST5, Camellia, ChaCha20, IDEA, SEED, TripleDES\n)\nfrom cryptography.hazmat.primitives.ciphers.modes import (\n    CBC, CFB, CFB8, CTR, ECB, GCM, OFB, XTS\n)\nfrom cryptography.hazmat.primitives.kdf import scrypt\nfrom cryptography.hazmat.primitives.serialization import ssh\nfrom cryptography.x509 import ocsp\n\n\n_MemoryBIO = collections.namedtuple(\"_MemoryBIO\", [\"bio\", \"char_ptr\"])\n\n\n@utils.register_interface(CipherBackend)\n@utils.register_interface(CMACBackend)\n@utils.register_interface(DERSerializationBackend)\n@utils.register_interface(DHBackend)\n@utils.register_interface(DSABackend)\n@utils.register_interface(EllipticCurveBackend)\n@utils.register_interface(HashBackend)\n@utils.register_interface(HMACBackend)\n@utils.register_interface(PBKDF2HMACBackend)\n@utils.register_interface(RSABackend)\n@utils.register_interface(PEMSerializationBackend)\n@utils.register_interface(X509Backend)\n@utils.register_interface_if(\n    binding.Binding().lib.Cryptography_HAS_SCRYPT, ScryptBackend\n)\nclass Backend(object):\n    \"\"\"\n    OpenSSL API binding interfaces.\n    \"\"\"\n    name = \"openssl\"\n\n    def __init__(self):\n        self._binding = binding.Binding()\n        self._ffi = self._binding.ffi\n        self._lib = self._binding.lib\n\n        self._cipher_registry = {}\n        self._register_default_ciphers()\n        self.activate_osrandom_engine()\n        self._dh_types = [self._lib.EVP_PKEY_DH]\n        if self._lib.Cryptography_HAS_EVP_PKEY_DHX:\n            self._dh_types.append(self._lib.EVP_PKEY_DHX)\n\n    def openssl_assert(self, ok):\n        return binding._openssl_assert(self._lib, ok)\n\n    def activate_builtin_random(self):\n        if self._lib.Cryptography_HAS_ENGINE:\n            # Obtain a new structural reference.\n            e = self._lib.ENGINE_get_default_RAND()\n            if e != self._ffi.NULL:\n                self._lib.ENGINE_unregister_RAND(e)\n                # Reset the RNG to use the built-in.\n                res = self._lib.RAND_set_rand_method(self._ffi.NULL)\n                self.openssl_assert(res == 1)\n                # decrement the structural reference from get_default_RAND\n                res = self._lib.ENGINE_finish(e)\n                self.openssl_assert(res == 1)\n\n    @contextlib.contextmanager\n    def _get_osurandom_engine(self):\n        # Fetches an engine by id and returns it. This creates a structural\n        # reference.\n        e = self._lib.ENGINE_by_id(self._lib.Cryptography_osrandom_engine_id)\n        self.openssl_assert(e != self._ffi.NULL)\n        # Initialize the engine for use. This adds a functional reference.\n        res = self._lib.ENGINE_init(e)\n        self.openssl_assert(res == 1)\n\n        try:\n            yield e\n        finally:\n            # Decrement the structural ref incremented by ENGINE_by_id.\n            res = self._lib.ENGINE_free(e)\n            self.openssl_assert(res == 1)\n            # Decrement the functional ref incremented by ENGINE_init.\n            res = self._lib.ENGINE_finish(e)\n            self.openssl_assert(res == 1)\n\n    def activate_osrandom_engine(self):\n        if self._lib.Cryptography_HAS_ENGINE:\n            # Unregister and free the current engine.\n            self.activate_builtin_random()\n            with self._get_osurandom_engine() as e:\n                # Set the engine as the default RAND provider.\n                res = self._lib.ENGINE_set_default_RAND(e)\n                self.openssl_assert(res == 1)\n            # Reset the RNG to use the engine\n            res = self._lib.RAND_set_rand_method(self._ffi.NULL)\n            self.openssl_assert(res == 1)\n\n    def osrandom_engine_implementation(self):\n        buf = self._ffi.new(\"char[]\", 64)\n        with self._get_osurandom_engine() as e:\n            res = self._lib.ENGINE_ctrl_cmd(e, b\"get_implementation\",\n                                            len(buf), buf,\n                                            self._ffi.NULL, 0)\n            self.openssl_assert(res > 0)\n        return self._ffi.string(buf).decode('ascii')\n\n    def openssl_version_text(self):\n        \"\"\"\n        Friendly string name of the loaded OpenSSL library. This is not\n        necessarily the same version as it was compiled against.\n\n        Example: OpenSSL 1.0.1e 11 Feb 2013\n        \"\"\"\n        return self._ffi.string(\n            self._lib.OpenSSL_version(self._lib.OPENSSL_VERSION)\n        ).decode(\"ascii\")\n\n    def openssl_version_number(self):\n        return self._lib.OpenSSL_version_num()\n\n    def create_hmac_ctx(self, key, algorithm):\n        return _HMACContext(self, key, algorithm)\n\n    def _evp_md_from_algorithm(self, algorithm):\n        if algorithm.name == \"blake2b\" or algorithm.name == \"blake2s\":\n            alg = \"{}{}\".format(\n                algorithm.name, algorithm.digest_size * 8\n            ).encode(\"ascii\")\n        else:\n            alg = algorithm.name.encode(\"ascii\")\n\n        evp_md = self._lib.EVP_get_digestbyname(alg)\n        return evp_md\n\n    def _evp_md_non_null_from_algorithm(self, algorithm):\n        evp_md = self._evp_md_from_algorithm(algorithm)\n        self.openssl_assert(evp_md != self._ffi.NULL)\n        return evp_md\n\n    def hash_supported(self, algorithm):\n        evp_md = self._evp_md_from_algorithm(algorithm)\n        return evp_md != self._ffi.NULL\n\n    def hmac_supported(self, algorithm):\n        return self.hash_supported(algorithm)\n\n    def create_hash_ctx(self, algorithm):\n        return _HashContext(self, algorithm)\n\n    def cipher_supported(self, cipher, mode):\n        try:\n            adapter = self._cipher_registry[type(cipher), type(mode)]\n        except KeyError:\n            return False\n        evp_cipher = adapter(self, cipher, mode)\n        return self._ffi.NULL != evp_cipher\n\n    def register_cipher_adapter(self, cipher_cls, mode_cls, adapter):\n        if (cipher_cls, mode_cls) in self._cipher_registry:\n            raise ValueError(\"Duplicate registration for: {} {}.\".format(\n                cipher_cls, mode_cls)\n            )\n        self._cipher_registry[cipher_cls, mode_cls] = adapter\n\n    def _register_default_ciphers(self):\n        for mode_cls in [CBC, CTR, ECB, OFB, CFB, CFB8, GCM]:\n            self.register_cipher_adapter(\n                AES,\n                mode_cls,\n                GetCipherByName(\"{cipher.name}-{cipher.key_size}-{mode.name}\")\n            )\n        for mode_cls in [CBC, CTR, ECB, OFB, CFB]:\n            self.register_cipher_adapter(\n                Camellia,\n                mode_cls,\n                GetCipherByName(\"{cipher.name}-{cipher.key_size}-{mode.name}\")\n            )\n        for mode_cls in [CBC, CFB, CFB8, OFB]:\n            self.register_cipher_adapter(\n                TripleDES,\n                mode_cls,\n                GetCipherByName(\"des-ede3-{mode.name}\")\n            )\n        self.register_cipher_adapter(\n            TripleDES,\n            ECB,\n            GetCipherByName(\"des-ede3\")\n        )\n        for mode_cls in [CBC, CFB, OFB, ECB]:\n            self.register_cipher_adapter(\n                Blowfish,\n                mode_cls,\n                GetCipherByName(\"bf-{mode.name}\")\n            )\n        for mode_cls in [CBC, CFB, OFB, ECB]:\n            self.register_cipher_adapter(\n                SEED,\n                mode_cls,\n                GetCipherByName(\"seed-{mode.name}\")\n            )\n        for cipher_cls, mode_cls in itertools.product(\n            [CAST5, IDEA],\n            [CBC, OFB, CFB, ECB],\n        ):\n            self.register_cipher_adapter(\n                cipher_cls,\n                mode_cls,\n                GetCipherByName(\"{cipher.name}-{mode.name}\")\n            )\n        self.register_cipher_adapter(\n            ARC4,\n            type(None),\n            GetCipherByName(\"rc4\")\n        )\n        self.register_cipher_adapter(\n            ChaCha20,\n            type(None),\n            GetCipherByName(\"chacha20\")\n        )\n        self.register_cipher_adapter(AES, XTS, _get_xts_cipher)\n\n    def create_symmetric_encryption_ctx(self, cipher, mode):\n        return _CipherContext(self, cipher, mode, _CipherContext._ENCRYPT)\n\n    def create_symmetric_decryption_ctx(self, cipher, mode):\n        return _CipherContext(self, cipher, mode, _CipherContext._DECRYPT)\n\n    def pbkdf2_hmac_supported(self, algorithm):\n        return self.hmac_supported(algorithm)\n\n    def derive_pbkdf2_hmac(self, algorithm, length, salt, iterations,\n                           key_material):\n        buf = self._ffi.new(\"unsigned char[]\", length)\n        evp_md = self._evp_md_non_null_from_algorithm(algorithm)\n        key_material_ptr = self._ffi.from_buffer(key_material)\n        res = self._lib.PKCS5_PBKDF2_HMAC(\n            key_material_ptr,\n            len(key_material),\n            salt,\n            len(salt),\n            iterations,\n            evp_md,\n            length,\n            buf\n        )\n        self.openssl_assert(res == 1)\n        return self._ffi.buffer(buf)[:]\n\n    def _consume_errors(self):\n        return binding._consume_errors(self._lib)\n\n    def _bn_to_int(self, bn):\n        assert bn != self._ffi.NULL\n\n        if not six.PY2:\n            # Python 3 has constant time from_bytes, so use that.\n            bn_num_bytes = self._lib.BN_num_bytes(bn)\n            bin_ptr = self._ffi.new(\"unsigned char[]\", bn_num_bytes)\n            bin_len = self._lib.BN_bn2bin(bn, bin_ptr)\n            # A zero length means the BN has value 0\n            self.openssl_assert(bin_len >= 0)\n            val = int.from_bytes(self._ffi.buffer(bin_ptr)[:bin_len], \"big\")\n            if self._lib.BN_is_negative(bn):\n                val = -val\n            return val\n        else:\n            # Under Python 2 the best we can do is hex()\n            hex_cdata = self._lib.BN_bn2hex(bn)\n            self.openssl_assert(hex_cdata != self._ffi.NULL)\n            hex_str = self._ffi.string(hex_cdata)\n            self._lib.OPENSSL_free(hex_cdata)\n            return int(hex_str, 16)\n\n    def _int_to_bn(self, num, bn=None):\n        \"\"\"\n        Converts a python integer to a BIGNUM. The returned BIGNUM will not\n        be garbage collected (to support adding them to structs that take\n        ownership of the object). Be sure to register it for GC if it will\n        be discarded after use.\n        \"\"\"\n        assert bn is None or bn != self._ffi.NULL\n\n        if bn is None:\n            bn = self._ffi.NULL\n\n        if not six.PY2:\n            # Python 3 has constant time to_bytes, so use that.\n\n            binary = num.to_bytes(int(num.bit_length() / 8.0 + 1), \"big\")\n            bn_ptr = self._lib.BN_bin2bn(binary, len(binary), bn)\n            self.openssl_assert(bn_ptr != self._ffi.NULL)\n            return bn_ptr\n\n        else:\n            # Under Python 2 the best we can do is hex(), [2:] removes the 0x\n            # prefix.\n            hex_num = hex(num).rstrip(\"L\")[2:].encode(\"ascii\")\n            bn_ptr = self._ffi.new(\"BIGNUM **\")\n            bn_ptr[0] = bn\n            res = self._lib.BN_hex2bn(bn_ptr, hex_num)\n            self.openssl_assert(res != 0)\n            self.openssl_assert(bn_ptr[0] != self._ffi.NULL)\n            return bn_ptr[0]\n\n    def generate_rsa_private_key(self, public_exponent, key_size):\n        rsa._verify_rsa_parameters(public_exponent, key_size)\n\n        rsa_cdata = self._lib.RSA_new()\n        self.openssl_assert(rsa_cdata != self._ffi.NULL)\n        rsa_cdata = self._ffi.gc(rsa_cdata, self._lib.RSA_free)\n\n        bn = self._int_to_bn(public_exponent)\n        bn = self._ffi.gc(bn, self._lib.BN_free)\n\n        res = self._lib.RSA_generate_key_ex(\n            rsa_cdata, key_size, bn, self._ffi.NULL\n        )\n        self.openssl_assert(res == 1)\n        evp_pkey = self._rsa_cdata_to_evp_pkey(rsa_cdata)\n\n        return _RSAPrivateKey(self, rsa_cdata, evp_pkey)\n\n    def generate_rsa_parameters_supported(self, public_exponent, key_size):\n        return (public_exponent >= 3 and public_exponent & 1 != 0 and\n                key_size >= 512)\n\n    def load_rsa_private_numbers(self, numbers):\n        rsa._check_private_key_components(\n            numbers.p,\n            numbers.q,\n            numbers.d,\n            numbers.dmp1,\n            numbers.dmq1,\n            numbers.iqmp,\n            numbers.public_numbers.e,\n            numbers.public_numbers.n\n        )\n        rsa_cdata = self._lib.RSA_new()\n        self.openssl_assert(rsa_cdata != self._ffi.NULL)\n        rsa_cdata = self._ffi.gc(rsa_cdata, self._lib.RSA_free)\n        p = self._int_to_bn(numbers.p)\n        q = self._int_to_bn(numbers.q)\n        d = self._int_to_bn(numbers.d)\n        dmp1 = self._int_to_bn(numbers.dmp1)\n        dmq1 = self._int_to_bn(numbers.dmq1)\n        iqmp = self._int_to_bn(numbers.iqmp)\n        e = self._int_to_bn(numbers.public_numbers.e)\n        n = self._int_to_bn(numbers.public_numbers.n)\n        res = self._lib.RSA_set0_factors(rsa_cdata, p, q)\n        self.openssl_assert(res == 1)\n        res = self._lib.RSA_set0_key(rsa_cdata, n, e, d)\n        self.openssl_assert(res == 1)\n        res = self._lib.RSA_set0_crt_params(rsa_cdata, dmp1, dmq1, iqmp)\n        self.openssl_assert(res == 1)\n        res = self._lib.RSA_blinding_on(rsa_cdata, self._ffi.NULL)\n        self.openssl_assert(res == 1)\n        evp_pkey = self._rsa_cdata_to_evp_pkey(rsa_cdata)\n\n        return _RSAPrivateKey(self, rsa_cdata, evp_pkey)\n\n    def load_rsa_public_numbers(self, numbers):\n        rsa._check_public_key_components(numbers.e, numbers.n)\n        rsa_cdata = self._lib.RSA_new()\n        self.openssl_assert(rsa_cdata != self._ffi.NULL)\n        rsa_cdata = self._ffi.gc(rsa_cdata, self._lib.RSA_free)\n        e = self._int_to_bn(numbers.e)\n        n = self._int_to_bn(numbers.n)\n        res = self._lib.RSA_set0_key(rsa_cdata, n, e, self._ffi.NULL)\n        self.openssl_assert(res == 1)\n        evp_pkey = self._rsa_cdata_to_evp_pkey(rsa_cdata)\n\n        return _RSAPublicKey(self, rsa_cdata, evp_pkey)\n\n    def _create_evp_pkey_gc(self):\n        evp_pkey = self._lib.EVP_PKEY_new()\n        self.openssl_assert(evp_pkey != self._ffi.NULL)\n        evp_pkey = self._ffi.gc(evp_pkey, self._lib.EVP_PKEY_free)\n        return evp_pkey\n\n    def _rsa_cdata_to_evp_pkey(self, rsa_cdata):\n        evp_pkey = self._create_evp_pkey_gc()\n        res = self._lib.EVP_PKEY_set1_RSA(evp_pkey, rsa_cdata)\n        self.openssl_assert(res == 1)\n        return evp_pkey\n\n    def _bytes_to_bio(self, data):\n        \"\"\"\n        Return a _MemoryBIO namedtuple of (BIO, char*).\n\n        The char* is the storage for the BIO and it must stay alive until the\n        BIO is finished with.\n        \"\"\"\n        data_ptr = self._ffi.from_buffer(data)\n        bio = self._lib.BIO_new_mem_buf(\n            data_ptr, len(data)\n        )\n        self.openssl_assert(bio != self._ffi.NULL)\n\n        return _MemoryBIO(self._ffi.gc(bio, self._lib.BIO_free), data_ptr)\n\n    def _create_mem_bio_gc(self):\n        \"\"\"\n        Creates an empty memory BIO.\n        \"\"\"\n        bio_method = self._lib.BIO_s_mem()\n        self.openssl_assert(bio_method != self._ffi.NULL)\n        bio = self._lib.BIO_new(bio_method)\n        self.openssl_assert(bio != self._ffi.NULL)\n        bio = self._ffi.gc(bio, self._lib.BIO_free)\n        return bio\n\n    def _read_mem_bio(self, bio):\n        \"\"\"\n        Reads a memory BIO. This only works on memory BIOs.\n        \"\"\"\n        buf = self._ffi.new(\"char **\")\n        buf_len = self._lib.BIO_get_mem_data(bio, buf)\n        self.openssl_assert(buf_len > 0)\n        self.openssl_assert(buf[0] != self._ffi.NULL)\n        bio_data = self._ffi.buffer(buf[0], buf_len)[:]\n        return bio_data\n\n    def _evp_pkey_to_private_key(self, evp_pkey):\n        \"\"\"\n        Return the appropriate type of PrivateKey given an evp_pkey cdata\n        pointer.\n        \"\"\"\n\n        key_type = self._lib.EVP_PKEY_id(evp_pkey)\n\n        if key_type == self._lib.EVP_PKEY_RSA:\n            rsa_cdata = self._lib.EVP_PKEY_get1_RSA(evp_pkey)\n            self.openssl_assert(rsa_cdata != self._ffi.NULL)\n            rsa_cdata = self._ffi.gc(rsa_cdata, self._lib.RSA_free)\n            return _RSAPrivateKey(self, rsa_cdata, evp_pkey)\n        elif key_type == self._lib.EVP_PKEY_DSA:\n            dsa_cdata = self._lib.EVP_PKEY_get1_DSA(evp_pkey)\n            self.openssl_assert(dsa_cdata != self._ffi.NULL)\n            dsa_cdata = self._ffi.gc(dsa_cdata, self._lib.DSA_free)\n            return _DSAPrivateKey(self, dsa_cdata, evp_pkey)\n        elif key_type == self._lib.EVP_PKEY_EC:\n            ec_cdata = self._lib.EVP_PKEY_get1_EC_KEY(evp_pkey)\n            self.openssl_assert(ec_cdata != self._ffi.NULL)\n            ec_cdata = self._ffi.gc(ec_cdata, self._lib.EC_KEY_free)\n            return _EllipticCurvePrivateKey(self, ec_cdata, evp_pkey)\n        elif key_type in self._dh_types:\n            dh_cdata = self._lib.EVP_PKEY_get1_DH(evp_pkey)\n            self.openssl_assert(dh_cdata != self._ffi.NULL)\n            dh_cdata = self._ffi.gc(dh_cdata, self._lib.DH_free)\n            return _DHPrivateKey(self, dh_cdata, evp_pkey)\n        elif key_type == getattr(self._lib, \"EVP_PKEY_ED25519\", None):\n            # EVP_PKEY_ED25519 is not present in OpenSSL < 1.1.1\n            return _Ed25519PrivateKey(self, evp_pkey)\n        elif key_type == getattr(self._lib, \"EVP_PKEY_X448\", None):\n            # EVP_PKEY_X448 is not present in OpenSSL < 1.1.1\n            return _X448PrivateKey(self, evp_pkey)\n        elif key_type == getattr(self._lib, \"EVP_PKEY_X25519\", None):\n            # EVP_PKEY_X25519 is not present in OpenSSL < 1.1.0\n            return _X25519PrivateKey(self, evp_pkey)\n        elif key_type == getattr(self._lib, \"EVP_PKEY_ED448\", None):\n            # EVP_PKEY_ED448 is not present in OpenSSL < 1.1.1\n            return _Ed448PrivateKey(self, evp_pkey)\n        else:\n            raise UnsupportedAlgorithm(\"Unsupported key type.\")\n\n    def _evp_pkey_to_public_key(self, evp_pkey):\n        \"\"\"\n        Return the appropriate type of PublicKey given an evp_pkey cdata\n        pointer.\n        \"\"\"\n\n        key_type = self._lib.EVP_PKEY_id(evp_pkey)\n\n        if key_type == self._lib.EVP_PKEY_RSA:\n            rsa_cdata = self._lib.EVP_PKEY_get1_RSA(evp_pkey)\n            self.openssl_assert(rsa_cdata != self._ffi.NULL)\n            rsa_cdata = self._ffi.gc(rsa_cdata, self._lib.RSA_free)\n            return _RSAPublicKey(self, rsa_cdata, evp_pkey)\n        elif key_type == self._lib.EVP_PKEY_DSA:\n            dsa_cdata = self._lib.EVP_PKEY_get1_DSA(evp_pkey)\n            self.openssl_assert(dsa_cdata != self._ffi.NULL)\n            dsa_cdata = self._ffi.gc(dsa_cdata, self._lib.DSA_free)\n            return _DSAPublicKey(self, dsa_cdata, evp_pkey)\n        elif key_type == self._lib.EVP_PKEY_EC:\n            ec_cdata = self._lib.EVP_PKEY_get1_EC_KEY(evp_pkey)\n            self.openssl_assert(ec_cdata != self._ffi.NULL)\n            ec_cdata = self._ffi.gc(ec_cdata, self._lib.EC_KEY_free)\n            return _EllipticCurvePublicKey(self, ec_cdata, evp_pkey)\n        elif key_type in self._dh_types:\n            dh_cdata = self._lib.EVP_PKEY_get1_DH(evp_pkey)\n            self.openssl_assert(dh_cdata != self._ffi.NULL)\n            dh_cdata = self._ffi.gc(dh_cdata, self._lib.DH_free)\n            return _DHPublicKey(self, dh_cdata, evp_pkey)\n        elif key_type == getattr(self._lib, \"EVP_PKEY_ED25519\", None):\n            # EVP_PKEY_ED25519 is not present in OpenSSL < 1.1.1\n            return _Ed25519PublicKey(self, evp_pkey)\n        elif key_type == getattr(self._lib, \"EVP_PKEY_X448\", None):\n            # EVP_PKEY_X448 is not present in OpenSSL < 1.1.1\n            return _X448PublicKey(self, evp_pkey)\n        elif key_type == getattr(self._lib, \"EVP_PKEY_X25519\", None):\n            # EVP_PKEY_X25519 is not present in OpenSSL < 1.1.0\n            return _X25519PublicKey(self, evp_pkey)\n        elif key_type == getattr(self._lib, \"EVP_PKEY_ED448\", None):\n            # EVP_PKEY_X25519 is not present in OpenSSL < 1.1.1\n            return _Ed448PublicKey(self, evp_pkey)\n        else:\n            raise UnsupportedAlgorithm(\"Unsupported key type.\")\n\n    def _oaep_hash_supported(self, algorithm):\n        if self._lib.Cryptography_HAS_RSA_OAEP_MD:\n            return isinstance(\n                algorithm, (\n                    hashes.SHA1,\n                    hashes.SHA224,\n                    hashes.SHA256,\n                    hashes.SHA384,\n                    hashes.SHA512,\n                )\n            )\n        else:\n            return isinstance(algorithm, hashes.SHA1)\n\n    def rsa_padding_supported(self, padding):\n        if isinstance(padding, PKCS1v15):\n            return True\n        elif isinstance(padding, PSS) and isinstance(padding._mgf, MGF1):\n            return self.hash_supported(padding._mgf._algorithm)\n        elif isinstance(padding, OAEP) and isinstance(padding._mgf, MGF1):\n            return (\n                self._oaep_hash_supported(padding._mgf._algorithm) and\n                self._oaep_hash_supported(padding._algorithm) and\n                (\n                    (padding._label is None or len(padding._label) == 0) or\n                    self._lib.Cryptography_HAS_RSA_OAEP_LABEL == 1\n                )\n            )\n        else:\n            return False\n\n    def generate_dsa_parameters(self, key_size):\n        if key_size not in (1024, 2048, 3072):\n            raise ValueError(\"Key size must be 1024 or 2048 or 3072 bits.\")\n\n        ctx = self._lib.DSA_new()\n        self.openssl_assert(ctx != self._ffi.NULL)\n        ctx = self._ffi.gc(ctx, self._lib.DSA_free)\n\n        res = self._lib.DSA_generate_parameters_ex(\n            ctx, key_size, self._ffi.NULL, 0,\n            self._ffi.NULL, self._ffi.NULL, self._ffi.NULL\n        )\n\n        self.openssl_assert(res == 1)\n\n        return _DSAParameters(self, ctx)\n\n    def generate_dsa_private_key(self, parameters):\n        ctx = self._lib.DSAparams_dup(parameters._dsa_cdata)\n        self.openssl_assert(ctx != self._ffi.NULL)\n        ctx = self._ffi.gc(ctx, self._lib.DSA_free)\n        self._lib.DSA_generate_key(ctx)\n        evp_pkey = self._dsa_cdata_to_evp_pkey(ctx)\n\n        return _DSAPrivateKey(self, ctx, evp_pkey)\n\n    def generate_dsa_private_key_and_parameters(self, key_size):\n        parameters = self.generate_dsa_parameters(key_size)\n        return self.generate_dsa_private_key(parameters)\n\n    def _dsa_cdata_set_values(self, dsa_cdata, p, q, g, pub_key, priv_key):\n        res = self._lib.DSA_set0_pqg(dsa_cdata, p, q, g)\n        self.openssl_assert(res == 1)\n        res = self._lib.DSA_set0_key(dsa_cdata, pub_key, priv_key)\n        self.openssl_assert(res == 1)\n\n    def load_dsa_private_numbers(self, numbers):\n        dsa._check_dsa_private_numbers(numbers)\n        parameter_numbers = numbers.public_numbers.parameter_numbers\n\n        dsa_cdata = self._lib.DSA_new()\n        self.openssl_assert(dsa_cdata != self._ffi.NULL)\n        dsa_cdata = self._ffi.gc(dsa_cdata, self._lib.DSA_free)\n\n        p = self._int_to_bn(parameter_numbers.p)\n        q = self._int_to_bn(parameter_numbers.q)\n        g = self._int_to_bn(parameter_numbers.g)\n        pub_key = self._int_to_bn(numbers.public_numbers.y)\n        priv_key = self._int_to_bn(numbers.x)\n        self._dsa_cdata_set_values(dsa_cdata, p, q, g, pub_key, priv_key)\n\n        evp_pkey = self._dsa_cdata_to_evp_pkey(dsa_cdata)\n\n        return _DSAPrivateKey(self, dsa_cdata, evp_pkey)\n\n    def load_dsa_public_numbers(self, numbers):\n        dsa._check_dsa_parameters(numbers.parameter_numbers)\n        dsa_cdata = self._lib.DSA_new()\n        self.openssl_assert(dsa_cdata != self._ffi.NULL)\n        dsa_cdata = self._ffi.gc(dsa_cdata, self._lib.DSA_free)\n\n        p = self._int_to_bn(numbers.parameter_numbers.p)\n        q = self._int_to_bn(numbers.parameter_numbers.q)\n        g = self._int_to_bn(numbers.parameter_numbers.g)\n        pub_key = self._int_to_bn(numbers.y)\n        priv_key = self._ffi.NULL\n        self._dsa_cdata_set_values(dsa_cdata, p, q, g, pub_key, priv_key)\n\n        evp_pkey = self._dsa_cdata_to_evp_pkey(dsa_cdata)\n\n        return _DSAPublicKey(self, dsa_cdata, evp_pkey)\n\n    def load_dsa_parameter_numbers(self, numbers):\n        dsa._check_dsa_parameters(numbers)\n        dsa_cdata = self._lib.DSA_new()\n        self.openssl_assert(dsa_cdata != self._ffi.NULL)\n        dsa_cdata = self._ffi.gc(dsa_cdata, self._lib.DSA_free)\n\n        p = self._int_to_bn(numbers.p)\n        q = self._int_to_bn(numbers.q)\n        g = self._int_to_bn(numbers.g)\n        res = self._lib.DSA_set0_pqg(dsa_cdata, p, q, g)\n        self.openssl_assert(res == 1)\n\n        return _DSAParameters(self, dsa_cdata)\n\n    def _dsa_cdata_to_evp_pkey(self, dsa_cdata):\n        evp_pkey = self._create_evp_pkey_gc()\n        res = self._lib.EVP_PKEY_set1_DSA(evp_pkey, dsa_cdata)\n        self.openssl_assert(res == 1)\n        return evp_pkey\n\n    def dsa_hash_supported(self, algorithm):\n        return self.hash_supported(algorithm)\n\n    def dsa_parameters_supported(self, p, q, g):\n        return True\n\n    def cmac_algorithm_supported(self, algorithm):\n        return self.cipher_supported(\n            algorithm, CBC(b\"\\x00\" * algorithm.block_size)\n        )\n\n    def create_cmac_ctx(self, algorithm):\n        return _CMACContext(self, algorithm)\n\n    def create_x509_csr(self, builder, private_key, algorithm):\n        if not isinstance(builder, x509.CertificateSigningRequestBuilder):\n            raise TypeError('Builder type mismatch.')\n\n        if isinstance(private_key,\n                      (ed25519.Ed25519PrivateKey, ed448.Ed448PrivateKey)):\n            if algorithm is not None:\n                raise ValueError(\n                    \"algorithm must be None when signing via ed25519 or ed448\"\n                )\n        elif not isinstance(algorithm, hashes.HashAlgorithm):\n            raise TypeError('Algorithm must be a registered hash algorithm.')\n        elif (\n            isinstance(algorithm, hashes.MD5) and not\n            isinstance(private_key, rsa.RSAPrivateKey)\n        ):\n            raise ValueError(\n                \"MD5 is not a supported hash algorithm for EC/DSA CSRs\"\n            )\n\n        # Resolve the signature algorithm.\n        evp_md = self._evp_md_x509_null_if_eddsa(private_key, algorithm)\n\n        # Create an empty request.\n        x509_req = self._lib.X509_REQ_new()\n        self.openssl_assert(x509_req != self._ffi.NULL)\n        x509_req = self._ffi.gc(x509_req, self._lib.X509_REQ_free)\n\n        # Set x509 version.\n        res = self._lib.X509_REQ_set_version(x509_req, x509.Version.v1.value)\n        self.openssl_assert(res == 1)\n\n        # Set subject name.\n        res = self._lib.X509_REQ_set_subject_name(\n            x509_req, _encode_name_gc(self, builder._subject_name)\n        )\n        self.openssl_assert(res == 1)\n\n        # Set subject public key.\n        public_key = private_key.public_key()\n        res = self._lib.X509_REQ_set_pubkey(\n            x509_req, public_key._evp_pkey\n        )\n        self.openssl_assert(res == 1)\n\n        # Add extensions.\n        sk_extension = self._lib.sk_X509_EXTENSION_new_null()\n        self.openssl_assert(sk_extension != self._ffi.NULL)\n        sk_extension = self._ffi.gc(\n            sk_extension,\n            lambda x: self._lib.sk_X509_EXTENSION_pop_free(\n                x, self._ffi.addressof(\n                    self._lib._original_lib, \"X509_EXTENSION_free\"\n                )\n            )\n        )\n        # Don't GC individual extensions because the memory is owned by\n        # sk_extensions and will be freed along with it.\n        self._create_x509_extensions(\n            extensions=builder._extensions,\n            handlers=_EXTENSION_ENCODE_HANDLERS,\n            x509_obj=sk_extension,\n            add_func=self._lib.sk_X509_EXTENSION_insert,\n            gc=False\n        )\n        res = self._lib.X509_REQ_add_extensions(x509_req, sk_extension)\n        self.openssl_assert(res == 1)\n\n        # Sign the request using the requester's private key.\n        res = self._lib.X509_REQ_sign(\n            x509_req, private_key._evp_pkey, evp_md\n        )\n        if res == 0:\n            errors = self._consume_errors()\n            self.openssl_assert(\n                errors[0]._lib_reason_match(\n                    self._lib.ERR_LIB_RSA,\n                    self._lib.RSA_R_DIGEST_TOO_BIG_FOR_RSA_KEY\n                )\n            )\n\n            raise ValueError(\"Digest too big for RSA key\")\n\n        return _CertificateSigningRequest(self, x509_req)\n\n    def create_x509_certificate(self, builder, private_key, algorithm):\n        if not isinstance(builder, x509.CertificateBuilder):\n            raise TypeError('Builder type mismatch.')\n        if isinstance(private_key,\n                      (ed25519.Ed25519PrivateKey, ed448.Ed448PrivateKey)):\n            if algorithm is not None:\n                raise ValueError(\n                    \"algorithm must be None when signing via ed25519 or ed448\"\n                )\n        elif not isinstance(algorithm, hashes.HashAlgorithm):\n            raise TypeError('Algorithm must be a registered hash algorithm.')\n\n        if (\n            isinstance(algorithm, hashes.MD5) and not\n            isinstance(private_key, rsa.RSAPrivateKey)\n        ):\n            raise ValueError(\n                \"MD5 is only (reluctantly) supported for RSA certificates\"\n            )\n\n        # Resolve the signature algorithm.\n        evp_md = self._evp_md_x509_null_if_eddsa(private_key, algorithm)\n\n        # Create an empty certificate.\n        x509_cert = self._lib.X509_new()\n        x509_cert = self._ffi.gc(x509_cert, backend._lib.X509_free)\n\n        # Set the x509 version.\n        res = self._lib.X509_set_version(x509_cert, builder._version.value)\n        self.openssl_assert(res == 1)\n\n        # Set the subject's name.\n        res = self._lib.X509_set_subject_name(\n            x509_cert, _encode_name_gc(self, builder._subject_name)\n        )\n        self.openssl_assert(res == 1)\n\n        # Set the subject's public key.\n        res = self._lib.X509_set_pubkey(\n            x509_cert, builder._public_key._evp_pkey\n        )\n        self.openssl_assert(res == 1)\n\n        # Set the certificate serial number.\n        serial_number = _encode_asn1_int_gc(self, builder._serial_number)\n        res = self._lib.X509_set_serialNumber(x509_cert, serial_number)\n        self.openssl_assert(res == 1)\n\n        # Set the \"not before\" time.\n        self._set_asn1_time(\n            self._lib.X509_getm_notBefore(x509_cert), builder._not_valid_before\n        )\n\n        # Set the \"not after\" time.\n        self._set_asn1_time(\n            self._lib.X509_getm_notAfter(x509_cert), builder._not_valid_after\n        )\n\n        # Add extensions.\n        self._create_x509_extensions(\n            extensions=builder._extensions,\n            handlers=_EXTENSION_ENCODE_HANDLERS,\n            x509_obj=x509_cert,\n            add_func=self._lib.X509_add_ext,\n            gc=True\n        )\n\n        # Set the issuer name.\n        res = self._lib.X509_set_issuer_name(\n            x509_cert, _encode_name_gc(self, builder._issuer_name)\n        )\n        self.openssl_assert(res == 1)\n\n        # Sign the certificate with the issuer's private key.\n        res = self._lib.X509_sign(\n            x509_cert, private_key._evp_pkey, evp_md\n        )\n        if res == 0:\n            errors = self._consume_errors()\n            self.openssl_assert(\n                errors[0]._lib_reason_match(\n                    self._lib.ERR_LIB_RSA,\n                    self._lib.RSA_R_DIGEST_TOO_BIG_FOR_RSA_KEY\n                )\n            )\n            raise ValueError(\"Digest too big for RSA key\")\n\n        return _Certificate(self, x509_cert)\n\n    def _evp_md_x509_null_if_eddsa(self, private_key, algorithm):\n        if isinstance(private_key,\n                      (ed25519.Ed25519PrivateKey, ed448.Ed448PrivateKey)):\n            # OpenSSL requires us to pass NULL for EVP_MD for ed25519/ed448\n            return self._ffi.NULL\n        else:\n            return self._evp_md_non_null_from_algorithm(algorithm)\n\n    def _set_asn1_time(self, asn1_time, time):\n        if time.year >= 2050:\n            asn1_str = time.strftime('%Y%m%d%H%M%SZ').encode('ascii')\n        else:\n            asn1_str = time.strftime('%y%m%d%H%M%SZ').encode('ascii')\n        res = self._lib.ASN1_TIME_set_string(asn1_time, asn1_str)\n        self.openssl_assert(res == 1)\n\n    def _create_asn1_time(self, time):\n        asn1_time = self._lib.ASN1_TIME_new()\n        self.openssl_assert(asn1_time != self._ffi.NULL)\n        asn1_time = self._ffi.gc(asn1_time, self._lib.ASN1_TIME_free)\n        self._set_asn1_time(asn1_time, time)\n        return asn1_time\n\n    def create_x509_crl(self, builder, private_key, algorithm):\n        if not isinstance(builder, x509.CertificateRevocationListBuilder):\n            raise TypeError('Builder type mismatch.')\n        if isinstance(private_key,\n                      (ed25519.Ed25519PrivateKey, ed448.Ed448PrivateKey)):\n            if algorithm is not None:\n                raise ValueError(\n                    \"algorithm must be None when signing via ed25519 or ed448\"\n                )\n        elif not isinstance(algorithm, hashes.HashAlgorithm):\n            raise TypeError('Algorithm must be a registered hash algorithm.')\n\n        if (\n            isinstance(algorithm, hashes.MD5) and not\n            isinstance(private_key, rsa.RSAPrivateKey)\n        ):\n            raise ValueError(\n                \"MD5 is not a supported hash algorithm for EC/DSA CRLs\"\n            )\n\n        evp_md = self._evp_md_x509_null_if_eddsa(private_key, algorithm)\n\n        # Create an empty CRL.\n        x509_crl = self._lib.X509_CRL_new()\n        x509_crl = self._ffi.gc(x509_crl, backend._lib.X509_CRL_free)\n\n        # Set the x509 CRL version. We only support v2 (integer value 1).\n        res = self._lib.X509_CRL_set_version(x509_crl, 1)\n        self.openssl_assert(res == 1)\n\n        # Set the issuer name.\n        res = self._lib.X509_CRL_set_issuer_name(\n            x509_crl, _encode_name_gc(self, builder._issuer_name)\n        )\n        self.openssl_assert(res == 1)\n\n        # Set the last update time.\n        last_update = self._create_asn1_time(builder._last_update)\n        res = self._lib.X509_CRL_set_lastUpdate(x509_crl, last_update)\n        self.openssl_assert(res == 1)\n\n        # Set the next update time.\n        next_update = self._create_asn1_time(builder._next_update)\n        res = self._lib.X509_CRL_set_nextUpdate(x509_crl, next_update)\n        self.openssl_assert(res == 1)\n\n        # Add extensions.\n        self._create_x509_extensions(\n            extensions=builder._extensions,\n            handlers=_CRL_EXTENSION_ENCODE_HANDLERS,\n            x509_obj=x509_crl,\n            add_func=self._lib.X509_CRL_add_ext,\n            gc=True\n        )\n\n        # add revoked certificates\n        for revoked_cert in builder._revoked_certificates:\n            # Duplicating because the X509_CRL takes ownership and will free\n            # this memory when X509_CRL_free is called.\n            revoked = self._lib.Cryptography_X509_REVOKED_dup(\n                revoked_cert._x509_revoked\n            )\n            self.openssl_assert(revoked != self._ffi.NULL)\n            res = self._lib.X509_CRL_add0_revoked(x509_crl, revoked)\n            self.openssl_assert(res == 1)\n\n        res = self._lib.X509_CRL_sign(\n            x509_crl, private_key._evp_pkey, evp_md\n        )\n        if res == 0:\n            errors = self._consume_errors()\n            self.openssl_assert(\n                errors[0]._lib_reason_match(\n                    self._lib.ERR_LIB_RSA,\n                    self._lib.RSA_R_DIGEST_TOO_BIG_FOR_RSA_KEY\n                )\n            )\n            raise ValueError(\"Digest too big for RSA key\")\n\n        return _CertificateRevocationList(self, x509_crl)\n\n    def _create_x509_extensions(self, extensions, handlers, x509_obj,\n                                add_func, gc):\n        for i, extension in enumerate(extensions):\n            x509_extension = self._create_x509_extension(\n                handlers, extension\n            )\n            self.openssl_assert(x509_extension != self._ffi.NULL)\n\n            if gc:\n                x509_extension = self._ffi.gc(\n                    x509_extension, self._lib.X509_EXTENSION_free\n                )\n            res = add_func(x509_obj, x509_extension, i)\n            self.openssl_assert(res >= 1)\n\n    def _create_raw_x509_extension(self, extension, value):\n        obj = _txt2obj_gc(self, extension.oid.dotted_string)\n        return self._lib.X509_EXTENSION_create_by_OBJ(\n            self._ffi.NULL, obj, 1 if extension.critical else 0, value\n        )\n\n    def _create_x509_extension(self, handlers, extension):\n        if isinstance(extension.value, x509.UnrecognizedExtension):\n            value = _encode_asn1_str_gc(self, extension.value.value)\n            return self._create_raw_x509_extension(extension, value)\n        elif isinstance(extension.value, x509.TLSFeature):\n            asn1 = encode_der(\n                SEQUENCE,\n                *[\n                    encode_der(INTEGER, encode_der_integer(x.value))\n                    for x in extension.value\n                ]\n            )\n            value = _encode_asn1_str_gc(self, asn1)\n            return self._create_raw_x509_extension(extension, value)\n        elif isinstance(extension.value, x509.PrecertPoison):\n            value = _encode_asn1_str_gc(self, encode_der(NULL))\n            return self._create_raw_x509_extension(extension, value)\n        else:\n            try:\n                encode = handlers[extension.oid]\n            except KeyError:\n                raise NotImplementedError(\n                    'Extension not supported: {}'.format(extension.oid)\n                )\n\n            ext_struct = encode(self, extension.value)\n            nid = self._lib.OBJ_txt2nid(\n                extension.oid.dotted_string.encode(\"ascii\")\n            )\n            backend.openssl_assert(nid != self._lib.NID_undef)\n            return self._lib.X509V3_EXT_i2d(\n                nid, 1 if extension.critical else 0, ext_struct\n            )\n\n    def create_x509_revoked_certificate(self, builder):\n        if not isinstance(builder, x509.RevokedCertificateBuilder):\n            raise TypeError('Builder type mismatch.')\n\n        x509_revoked = self._lib.X509_REVOKED_new()\n        self.openssl_assert(x509_revoked != self._ffi.NULL)\n        x509_revoked = self._ffi.gc(x509_revoked, self._lib.X509_REVOKED_free)\n        serial_number = _encode_asn1_int_gc(self, builder._serial_number)\n        res = self._lib.X509_REVOKED_set_serialNumber(\n            x509_revoked, serial_number\n        )\n        self.openssl_assert(res == 1)\n        rev_date = self._create_asn1_time(builder._revocation_date)\n        res = self._lib.X509_REVOKED_set_revocationDate(x509_revoked, rev_date)\n        self.openssl_assert(res == 1)\n        # add CRL entry extensions\n        self._create_x509_extensions(\n            extensions=builder._extensions,\n            handlers=_CRL_ENTRY_EXTENSION_ENCODE_HANDLERS,\n            x509_obj=x509_revoked,\n            add_func=self._lib.X509_REVOKED_add_ext,\n            gc=True\n        )\n        return _RevokedCertificate(self, None, x509_revoked)\n\n    def load_pem_private_key(self, data, password):\n        return self._load_key(\n            self._lib.PEM_read_bio_PrivateKey,\n            self._evp_pkey_to_private_key,\n            data,\n            password,\n        )\n\n    def load_pem_public_key(self, data):\n        mem_bio = self._bytes_to_bio(data)\n        evp_pkey = self._lib.PEM_read_bio_PUBKEY(\n            mem_bio.bio, self._ffi.NULL, self._ffi.NULL, self._ffi.NULL\n        )\n        if evp_pkey != self._ffi.NULL:\n            evp_pkey = self._ffi.gc(evp_pkey, self._lib.EVP_PKEY_free)\n            return self._evp_pkey_to_public_key(evp_pkey)\n        else:\n            # It's not a (RSA/DSA/ECDSA) subjectPublicKeyInfo, but we still\n            # need to check to see if it is a pure PKCS1 RSA public key (not\n            # embedded in a subjectPublicKeyInfo)\n            self._consume_errors()\n            res = self._lib.BIO_reset(mem_bio.bio)\n            self.openssl_assert(res == 1)\n            rsa_cdata = self._lib.PEM_read_bio_RSAPublicKey(\n                mem_bio.bio, self._ffi.NULL, self._ffi.NULL, self._ffi.NULL\n            )\n            if rsa_cdata != self._ffi.NULL:\n                rsa_cdata = self._ffi.gc(rsa_cdata, self._lib.RSA_free)\n                evp_pkey = self._rsa_cdata_to_evp_pkey(rsa_cdata)\n                return _RSAPublicKey(self, rsa_cdata, evp_pkey)\n            else:\n                self._handle_key_loading_error()\n\n    def load_pem_parameters(self, data):\n        mem_bio = self._bytes_to_bio(data)\n        # only DH is supported currently\n        dh_cdata = self._lib.PEM_read_bio_DHparams(\n            mem_bio.bio, self._ffi.NULL, self._ffi.NULL, self._ffi.NULL)\n        if dh_cdata != self._ffi.NULL:\n            dh_cdata = self._ffi.gc(dh_cdata, self._lib.DH_free)\n            return _DHParameters(self, dh_cdata)\n        else:\n            self._handle_key_loading_error()\n\n    def load_der_private_key(self, data, password):\n        # OpenSSL has a function called d2i_AutoPrivateKey that in theory\n        # handles this automatically, however it doesn't handle encrypted\n        # private keys. Instead we try to load the key two different ways.\n        # First we'll try to load it as a traditional key.\n        bio_data = self._bytes_to_bio(data)\n        key = self._evp_pkey_from_der_traditional_key(bio_data, password)\n        if key:\n            return self._evp_pkey_to_private_key(key)\n        else:\n            # Finally we try to load it with the method that handles encrypted\n            # PKCS8 properly.\n            return self._load_key(\n                self._lib.d2i_PKCS8PrivateKey_bio,\n                self._evp_pkey_to_private_key,\n                data,\n                password,\n            )\n\n    def _evp_pkey_from_der_traditional_key(self, bio_data, password):\n        key = self._lib.d2i_PrivateKey_bio(bio_data.bio, self._ffi.NULL)\n        if key != self._ffi.NULL:\n            key = self._ffi.gc(key, self._lib.EVP_PKEY_free)\n            if password is not None:\n                raise TypeError(\n                    \"Password was given but private key is not encrypted.\"\n                )\n\n            return key\n        else:\n            self._consume_errors()\n            return None\n\n    def load_der_public_key(self, data):\n        mem_bio = self._bytes_to_bio(data)\n        evp_pkey = self._lib.d2i_PUBKEY_bio(mem_bio.bio, self._ffi.NULL)\n        if evp_pkey != self._ffi.NULL:\n            evp_pkey = self._ffi.gc(evp_pkey, self._lib.EVP_PKEY_free)\n            return self._evp_pkey_to_public_key(evp_pkey)\n        else:\n            # It's not a (RSA/DSA/ECDSA) subjectPublicKeyInfo, but we still\n            # need to check to see if it is a pure PKCS1 RSA public key (not\n            # embedded in a subjectPublicKeyInfo)\n            self._consume_errors()\n            res = self._lib.BIO_reset(mem_bio.bio)\n            self.openssl_assert(res == 1)\n            rsa_cdata = self._lib.d2i_RSAPublicKey_bio(\n                mem_bio.bio, self._ffi.NULL\n            )\n            if rsa_cdata != self._ffi.NULL:\n                rsa_cdata = self._ffi.gc(rsa_cdata, self._lib.RSA_free)\n                evp_pkey = self._rsa_cdata_to_evp_pkey(rsa_cdata)\n                return _RSAPublicKey(self, rsa_cdata, evp_pkey)\n            else:\n                self._handle_key_loading_error()\n\n    def load_der_parameters(self, data):\n        mem_bio = self._bytes_to_bio(data)\n        dh_cdata = self._lib.d2i_DHparams_bio(\n            mem_bio.bio, self._ffi.NULL\n        )\n        if dh_cdata != self._ffi.NULL:\n            dh_cdata = self._ffi.gc(dh_cdata, self._lib.DH_free)\n            return _DHParameters(self, dh_cdata)\n        elif self._lib.Cryptography_HAS_EVP_PKEY_DHX:\n            # We check to see if the is dhx.\n            self._consume_errors()\n            res = self._lib.BIO_reset(mem_bio.bio)\n            self.openssl_assert(res == 1)\n            dh_cdata = self._lib.Cryptography_d2i_DHxparams_bio(\n                mem_bio.bio, self._ffi.NULL\n            )\n            if dh_cdata != self._ffi.NULL:\n                dh_cdata = self._ffi.gc(dh_cdata, self._lib.DH_free)\n                return _DHParameters(self, dh_cdata)\n\n        self._handle_key_loading_error()\n\n    def load_pem_x509_certificate(self, data):\n        mem_bio = self._bytes_to_bio(data)\n        x509 = self._lib.PEM_read_bio_X509(\n            mem_bio.bio, self._ffi.NULL, self._ffi.NULL, self._ffi.NULL\n        )\n        if x509 == self._ffi.NULL:\n            self._consume_errors()\n            raise ValueError(\n                \"Unable to load certificate. See https://cryptography.io/en/la\"\n                \"test/faq/#why-can-t-i-import-my-pem-file for more details.\"\n            )\n\n        x509 = self._ffi.gc(x509, self._lib.X509_free)\n        return _Certificate(self, x509)\n\n    def load_der_x509_certificate(self, data):\n        mem_bio = self._bytes_to_bio(data)\n        x509 = self._lib.d2i_X509_bio(mem_bio.bio, self._ffi.NULL)\n        if x509 == self._ffi.NULL:\n            self._consume_errors()\n            raise ValueError(\"Unable to load certificate\")\n\n        x509 = self._ffi.gc(x509, self._lib.X509_free)\n        return _Certificate(self, x509)\n\n    def load_pem_x509_crl(self, data):\n        mem_bio = self._bytes_to_bio(data)\n        x509_crl = self._lib.PEM_read_bio_X509_CRL(\n            mem_bio.bio, self._ffi.NULL, self._ffi.NULL, self._ffi.NULL\n        )\n        if x509_crl == self._ffi.NULL:\n            self._consume_errors()\n            raise ValueError(\n                \"Unable to load CRL. See https://cryptography.io/en/la\"\n                \"test/faq/#why-can-t-i-import-my-pem-file for more details.\"\n            )\n\n        x509_crl = self._ffi.gc(x509_crl, self._lib.X509_CRL_free)\n        return _CertificateRevocationList(self, x509_crl)\n\n    def load_der_x509_crl(self, data):\n        mem_bio = self._bytes_to_bio(data)\n        x509_crl = self._lib.d2i_X509_CRL_bio(mem_bio.bio, self._ffi.NULL)\n        if x509_crl == self._ffi.NULL:\n            self._consume_errors()\n            raise ValueError(\"Unable to load CRL\")\n\n        x509_crl = self._ffi.gc(x509_crl, self._lib.X509_CRL_free)\n        return _CertificateRevocationList(self, x509_crl)\n\n    def load_pem_x509_csr(self, data):\n        mem_bio = self._bytes_to_bio(data)\n        x509_req = self._lib.PEM_read_bio_X509_REQ(\n            mem_bio.bio, self._ffi.NULL, self._ffi.NULL, self._ffi.NULL\n        )\n        if x509_req == self._ffi.NULL:\n            self._consume_errors()\n            raise ValueError(\n                \"Unable to load request. See https://cryptography.io/en/la\"\n                \"test/faq/#why-can-t-i-import-my-pem-file for more details.\"\n            )\n\n        x509_req = self._ffi.gc(x509_req, self._lib.X509_REQ_free)\n        return _CertificateSigningRequest(self, x509_req)\n\n    def load_der_x509_csr(self, data):\n        mem_bio = self._bytes_to_bio(data)\n        x509_req = self._lib.d2i_X509_REQ_bio(mem_bio.bio, self._ffi.NULL)\n        if x509_req == self._ffi.NULL:\n            self._consume_errors()\n            raise ValueError(\"Unable to load request\")\n\n        x509_req = self._ffi.gc(x509_req, self._lib.X509_REQ_free)\n        return _CertificateSigningRequest(self, x509_req)\n\n    def _load_key(self, openssl_read_func, convert_func, data, password):\n        mem_bio = self._bytes_to_bio(data)\n\n        userdata = self._ffi.new(\"CRYPTOGRAPHY_PASSWORD_DATA *\")\n        if password is not None:\n            utils._check_byteslike(\"password\", password)\n            password_ptr = self._ffi.from_buffer(password)\n            userdata.password = password_ptr\n            userdata.length = len(password)\n\n        evp_pkey = openssl_read_func(\n            mem_bio.bio,\n            self._ffi.NULL,\n            self._ffi.addressof(\n                self._lib._original_lib, \"Cryptography_pem_password_cb\"\n            ),\n            userdata,\n        )\n\n        if evp_pkey == self._ffi.NULL:\n            if userdata.error != 0:\n                errors = self._consume_errors()\n                self.openssl_assert(errors)\n                if userdata.error == -1:\n                    raise TypeError(\n                        \"Password was not given but private key is encrypted\"\n                    )\n                else:\n                    assert userdata.error == -2\n                    raise ValueError(\n                        \"Passwords longer than {} bytes are not supported \"\n                        \"by this backend.\".format(userdata.maxsize - 1)\n                    )\n            else:\n                self._handle_key_loading_error()\n\n        evp_pkey = self._ffi.gc(evp_pkey, self._lib.EVP_PKEY_free)\n\n        if password is not None and userdata.called == 0:\n            raise TypeError(\n                \"Password was given but private key is not encrypted.\")\n\n        assert (\n            (password is not None and userdata.called == 1) or\n            password is None\n        )\n\n        return convert_func(evp_pkey)\n\n    def _handle_key_loading_error(self):\n        errors = self._consume_errors()\n\n        if not errors:\n            raise ValueError(\"Could not deserialize key data.\")\n\n        elif (\n            errors[0]._lib_reason_match(\n                self._lib.ERR_LIB_EVP, self._lib.EVP_R_BAD_DECRYPT\n            ) or errors[0]._lib_reason_match(\n                self._lib.ERR_LIB_PKCS12,\n                self._lib.PKCS12_R_PKCS12_CIPHERFINAL_ERROR\n            )\n        ):\n            raise ValueError(\"Bad decrypt. Incorrect password?\")\n\n        elif (\n            errors[0]._lib_reason_match(\n                self._lib.ERR_LIB_EVP, self._lib.EVP_R_UNKNOWN_PBE_ALGORITHM\n            ) or errors[0]._lib_reason_match(\n                self._lib.ERR_LIB_PEM, self._lib.PEM_R_UNSUPPORTED_ENCRYPTION\n            )\n        ):\n            raise UnsupportedAlgorithm(\n                \"PEM data is encrypted with an unsupported cipher\",\n                _Reasons.UNSUPPORTED_CIPHER\n            )\n\n        elif any(\n            error._lib_reason_match(\n                self._lib.ERR_LIB_EVP,\n                self._lib.EVP_R_UNSUPPORTED_PRIVATE_KEY_ALGORITHM\n            )\n            for error in errors\n        ):\n            raise ValueError(\"Unsupported public key algorithm.\")\n\n        else:\n            assert errors[0].lib in (\n                self._lib.ERR_LIB_EVP,\n                self._lib.ERR_LIB_PEM,\n                self._lib.ERR_LIB_ASN1,\n            )\n            raise ValueError(\"Could not deserialize key data.\")\n\n    def elliptic_curve_supported(self, curve):\n        try:\n            curve_nid = self._elliptic_curve_to_nid(curve)\n        except UnsupportedAlgorithm:\n            curve_nid = self._lib.NID_undef\n\n        group = self._lib.EC_GROUP_new_by_curve_name(curve_nid)\n\n        if group == self._ffi.NULL:\n            errors = self._consume_errors()\n            self.openssl_assert(\n                curve_nid == self._lib.NID_undef or\n                errors[0]._lib_reason_match(\n                    self._lib.ERR_LIB_EC,\n                    self._lib.EC_R_UNKNOWN_GROUP\n                )\n            )\n            return False\n        else:\n            self.openssl_assert(curve_nid != self._lib.NID_undef)\n            self._lib.EC_GROUP_free(group)\n            return True\n\n    def elliptic_curve_signature_algorithm_supported(\n        self, signature_algorithm, curve\n    ):\n        # We only support ECDSA right now.\n        if not isinstance(signature_algorithm, ec.ECDSA):\n            return False\n\n        return self.elliptic_curve_supported(curve)\n\n    def generate_elliptic_curve_private_key(self, curve):\n        \"\"\"\n        Generate a new private key on the named curve.\n        \"\"\"\n\n        if self.elliptic_curve_supported(curve):\n            ec_cdata = self._ec_key_new_by_curve(curve)\n\n            res = self._lib.EC_KEY_generate_key(ec_cdata)\n            self.openssl_assert(res == 1)\n\n            evp_pkey = self._ec_cdata_to_evp_pkey(ec_cdata)\n\n            return _EllipticCurvePrivateKey(self, ec_cdata, evp_pkey)\n        else:\n            raise UnsupportedAlgorithm(\n                \"Backend object does not support {}.\".format(curve.name),\n                _Reasons.UNSUPPORTED_ELLIPTIC_CURVE\n            )\n\n    def load_elliptic_curve_private_numbers(self, numbers):\n        public = numbers.public_numbers\n\n        ec_cdata = self._ec_key_new_by_curve(public.curve)\n\n        private_value = self._ffi.gc(\n            self._int_to_bn(numbers.private_value), self._lib.BN_clear_free\n        )\n        res = self._lib.EC_KEY_set_private_key(ec_cdata, private_value)\n        self.openssl_assert(res == 1)\n\n        ec_cdata = self._ec_key_set_public_key_affine_coordinates(\n            ec_cdata, public.x, public.y)\n\n        evp_pkey = self._ec_cdata_to_evp_pkey(ec_cdata)\n\n        return _EllipticCurvePrivateKey(self, ec_cdata, evp_pkey)\n\n    def load_elliptic_curve_public_numbers(self, numbers):\n        ec_cdata = self._ec_key_new_by_curve(numbers.curve)\n        ec_cdata = self._ec_key_set_public_key_affine_coordinates(\n            ec_cdata, numbers.x, numbers.y)\n        evp_pkey = self._ec_cdata_to_evp_pkey(ec_cdata)\n\n        return _EllipticCurvePublicKey(self, ec_cdata, evp_pkey)\n\n    def load_elliptic_curve_public_bytes(self, curve, point_bytes):\n        ec_cdata = self._ec_key_new_by_curve(curve)\n        group = self._lib.EC_KEY_get0_group(ec_cdata)\n        self.openssl_assert(group != self._ffi.NULL)\n        point = self._lib.EC_POINT_new(group)\n        self.openssl_assert(point != self._ffi.NULL)\n        point = self._ffi.gc(point, self._lib.EC_POINT_free)\n        with self._tmp_bn_ctx() as bn_ctx:\n            res = self._lib.EC_POINT_oct2point(\n                group, point, point_bytes, len(point_bytes), bn_ctx\n            )\n            if res != 1:\n                self._consume_errors()\n                raise ValueError(\"Invalid public bytes for the given curve\")\n\n        res = self._lib.EC_KEY_set_public_key(ec_cdata, point)\n        self.openssl_assert(res == 1)\n        evp_pkey = self._ec_cdata_to_evp_pkey(ec_cdata)\n        return _EllipticCurvePublicKey(self, ec_cdata, evp_pkey)\n\n    def derive_elliptic_curve_private_key(self, private_value, curve):\n        ec_cdata = self._ec_key_new_by_curve(curve)\n\n        get_func, group = self._ec_key_determine_group_get_func(ec_cdata)\n\n        point = self._lib.EC_POINT_new(group)\n        self.openssl_assert(point != self._ffi.NULL)\n        point = self._ffi.gc(point, self._lib.EC_POINT_free)\n\n        value = self._int_to_bn(private_value)\n        value = self._ffi.gc(value, self._lib.BN_clear_free)\n\n        with self._tmp_bn_ctx() as bn_ctx:\n            res = self._lib.EC_POINT_mul(group, point, value, self._ffi.NULL,\n                                         self._ffi.NULL, bn_ctx)\n            self.openssl_assert(res == 1)\n\n            bn_x = self._lib.BN_CTX_get(bn_ctx)\n            bn_y = self._lib.BN_CTX_get(bn_ctx)\n\n            res = get_func(group, point, bn_x, bn_y, bn_ctx)\n            self.openssl_assert(res == 1)\n\n        res = self._lib.EC_KEY_set_public_key(ec_cdata, point)\n        self.openssl_assert(res == 1)\n        private = self._int_to_bn(private_value)\n        private = self._ffi.gc(private, self._lib.BN_clear_free)\n        res = self._lib.EC_KEY_set_private_key(ec_cdata, private)\n        self.openssl_assert(res == 1)\n\n        evp_pkey = self._ec_cdata_to_evp_pkey(ec_cdata)\n\n        return _EllipticCurvePrivateKey(self, ec_cdata, evp_pkey)\n\n    def _ec_key_new_by_curve(self, curve):\n        curve_nid = self._elliptic_curve_to_nid(curve)\n        ec_cdata = self._lib.EC_KEY_new_by_curve_name(curve_nid)\n        self.openssl_assert(ec_cdata != self._ffi.NULL)\n        return self._ffi.gc(ec_cdata, self._lib.EC_KEY_free)\n\n    def load_der_ocsp_request(self, data):\n        mem_bio = self._bytes_to_bio(data)\n        request = self._lib.d2i_OCSP_REQUEST_bio(mem_bio.bio, self._ffi.NULL)\n        if request == self._ffi.NULL:\n            self._consume_errors()\n            raise ValueError(\"Unable to load OCSP request\")\n\n        request = self._ffi.gc(request, self._lib.OCSP_REQUEST_free)\n        return _OCSPRequest(self, request)\n\n    def load_der_ocsp_response(self, data):\n        mem_bio = self._bytes_to_bio(data)\n        response = self._lib.d2i_OCSP_RESPONSE_bio(mem_bio.bio, self._ffi.NULL)\n        if response == self._ffi.NULL:\n            self._consume_errors()\n            raise ValueError(\"Unable to load OCSP response\")\n\n        response = self._ffi.gc(response, self._lib.OCSP_RESPONSE_free)\n        return _OCSPResponse(self, response)\n\n    def create_ocsp_request(self, builder):\n        ocsp_req = self._lib.OCSP_REQUEST_new()\n        self.openssl_assert(ocsp_req != self._ffi.NULL)\n        ocsp_req = self._ffi.gc(ocsp_req, self._lib.OCSP_REQUEST_free)\n        cert, issuer, algorithm = builder._request\n        evp_md = self._evp_md_non_null_from_algorithm(algorithm)\n        certid = self._lib.OCSP_cert_to_id(\n            evp_md, cert._x509, issuer._x509\n        )\n        self.openssl_assert(certid != self._ffi.NULL)\n        onereq = self._lib.OCSP_request_add0_id(ocsp_req, certid)\n        self.openssl_assert(onereq != self._ffi.NULL)\n        self._create_x509_extensions(\n            extensions=builder._extensions,\n            handlers=_OCSP_REQUEST_EXTENSION_ENCODE_HANDLERS,\n            x509_obj=ocsp_req,\n            add_func=self._lib.OCSP_REQUEST_add_ext,\n            gc=True,\n        )\n        return _OCSPRequest(self, ocsp_req)\n\n    def _create_ocsp_basic_response(self, builder, private_key, algorithm):\n        basic = self._lib.OCSP_BASICRESP_new()\n        self.openssl_assert(basic != self._ffi.NULL)\n        basic = self._ffi.gc(basic, self._lib.OCSP_BASICRESP_free)\n        evp_md = self._evp_md_non_null_from_algorithm(\n            builder._response._algorithm\n        )\n        certid = self._lib.OCSP_cert_to_id(\n            evp_md, builder._response._cert._x509,\n            builder._response._issuer._x509\n        )\n        self.openssl_assert(certid != self._ffi.NULL)\n        certid = self._ffi.gc(certid, self._lib.OCSP_CERTID_free)\n        if builder._response._revocation_reason is None:\n            reason = -1\n        else:\n            reason = _CRL_ENTRY_REASON_ENUM_TO_CODE[\n                builder._response._revocation_reason\n            ]\n        if builder._response._revocation_time is None:\n            rev_time = self._ffi.NULL\n        else:\n            rev_time = self._create_asn1_time(\n                builder._response._revocation_time\n            )\n\n        next_update = self._ffi.NULL\n        if builder._response._next_update is not None:\n            next_update = self._create_asn1_time(\n                builder._response._next_update\n            )\n\n        this_update = self._create_asn1_time(builder._response._this_update)\n\n        res = self._lib.OCSP_basic_add1_status(\n            basic,\n            certid,\n            builder._response._cert_status.value,\n            reason,\n            rev_time,\n            this_update,\n            next_update\n        )\n        self.openssl_assert(res != self._ffi.NULL)\n        # okay, now sign the basic structure\n        evp_md = self._evp_md_x509_null_if_eddsa(private_key, algorithm)\n        responder_cert, responder_encoding = builder._responder_id\n        flags = self._lib.OCSP_NOCERTS\n        if responder_encoding is ocsp.OCSPResponderEncoding.HASH:\n            flags |= self._lib.OCSP_RESPID_KEY\n\n        if builder._certs is not None:\n            for cert in builder._certs:\n                res = self._lib.OCSP_basic_add1_cert(basic, cert._x509)\n                self.openssl_assert(res == 1)\n\n        self._create_x509_extensions(\n            extensions=builder._extensions,\n            handlers=_OCSP_BASICRESP_EXTENSION_ENCODE_HANDLERS,\n            x509_obj=basic,\n            add_func=self._lib.OCSP_BASICRESP_add_ext,\n            gc=True,\n        )\n\n        res = self._lib.OCSP_basic_sign(\n            basic, responder_cert._x509, private_key._evp_pkey,\n            evp_md, self._ffi.NULL, flags\n        )\n        if res != 1:\n            errors = self._consume_errors()\n            self.openssl_assert(\n                errors[0]._lib_reason_match(\n                    self._lib.ERR_LIB_X509,\n                    self._lib.X509_R_KEY_VALUES_MISMATCH\n                )\n            )\n            raise ValueError(\"responder_cert must be signed by private_key\")\n\n        return basic\n\n    def create_ocsp_response(self, response_status, builder, private_key,\n                             algorithm):\n        if response_status is ocsp.OCSPResponseStatus.SUCCESSFUL:\n            basic = self._create_ocsp_basic_response(\n                builder, private_key, algorithm\n            )\n        else:\n            basic = self._ffi.NULL\n\n        ocsp_resp = self._lib.OCSP_response_create(\n            response_status.value, basic\n        )\n        self.openssl_assert(ocsp_resp != self._ffi.NULL)\n        ocsp_resp = self._ffi.gc(ocsp_resp, self._lib.OCSP_RESPONSE_free)\n        return _OCSPResponse(self, ocsp_resp)\n\n    def elliptic_curve_exchange_algorithm_supported(self, algorithm, curve):\n        return (\n            self.elliptic_curve_supported(curve) and\n            isinstance(algorithm, ec.ECDH)\n        )\n\n    def _ec_cdata_to_evp_pkey(self, ec_cdata):\n        evp_pkey = self._create_evp_pkey_gc()\n        res = self._lib.EVP_PKEY_set1_EC_KEY(evp_pkey, ec_cdata)\n        self.openssl_assert(res == 1)\n        return evp_pkey\n\n    def _elliptic_curve_to_nid(self, curve):\n        \"\"\"\n        Get the NID for a curve name.\n        \"\"\"\n\n        curve_aliases = {\n            \"secp192r1\": \"prime192v1\",\n            \"secp256r1\": \"prime256v1\"\n        }\n\n        curve_name = curve_aliases.get(curve.name, curve.name)\n\n        curve_nid = self._lib.OBJ_sn2nid(curve_name.encode())\n        if curve_nid == self._lib.NID_undef:\n            raise UnsupportedAlgorithm(\n                \"{} is not a supported elliptic curve\".format(curve.name),\n                _Reasons.UNSUPPORTED_ELLIPTIC_CURVE\n            )\n        return curve_nid\n\n    @contextmanager\n    def _tmp_bn_ctx(self):\n        bn_ctx = self._lib.BN_CTX_new()\n        self.openssl_assert(bn_ctx != self._ffi.NULL)\n        bn_ctx = self._ffi.gc(bn_ctx, self._lib.BN_CTX_free)\n        self._lib.BN_CTX_start(bn_ctx)\n        try:\n            yield bn_ctx\n        finally:\n            self._lib.BN_CTX_end(bn_ctx)\n\n    def _ec_key_determine_group_get_func(self, ctx):\n        \"\"\"\n        Given an EC_KEY determine the group and what function is required to\n        get point coordinates.\n        \"\"\"\n        self.openssl_assert(ctx != self._ffi.NULL)\n\n        nid_two_field = self._lib.OBJ_sn2nid(b\"characteristic-two-field\")\n        self.openssl_assert(nid_two_field != self._lib.NID_undef)\n\n        group = self._lib.EC_KEY_get0_group(ctx)\n        self.openssl_assert(group != self._ffi.NULL)\n\n        method = self._lib.EC_GROUP_method_of(group)\n        self.openssl_assert(method != self._ffi.NULL)\n\n        nid = self._lib.EC_METHOD_get_field_type(method)\n        self.openssl_assert(nid != self._lib.NID_undef)\n\n        if nid == nid_two_field and self._lib.Cryptography_HAS_EC2M:\n            get_func = self._lib.EC_POINT_get_affine_coordinates_GF2m\n        else:\n            get_func = self._lib.EC_POINT_get_affine_coordinates_GFp\n\n        assert get_func\n\n        return get_func, group\n\n    def _ec_key_set_public_key_affine_coordinates(self, ctx, x, y):\n        \"\"\"\n        Sets the public key point in the EC_KEY context to the affine x and y\n        values.\n        \"\"\"\n\n        if x < 0 or y < 0:\n            raise ValueError(\n                \"Invalid EC key. Both x and y must be non-negative.\"\n            )\n\n        x = self._ffi.gc(self._int_to_bn(x), self._lib.BN_free)\n        y = self._ffi.gc(self._int_to_bn(y), self._lib.BN_free)\n        res = self._lib.EC_KEY_set_public_key_affine_coordinates(ctx, x, y)\n        if res != 1:\n            self._consume_errors()\n            raise ValueError(\"Invalid EC key.\")\n\n        return ctx\n\n    def _private_key_bytes(self, encoding, format, encryption_algorithm,\n                           evp_pkey, cdata):\n        if not isinstance(format, serialization.PrivateFormat):\n            raise TypeError(\n                \"format must be an item from the PrivateFormat enum\"\n            )\n\n        # X9.62 encoding is only valid for EC public keys\n        if encoding is serialization.Encoding.X962:\n            raise ValueError(\"X9.62 format is only valid for EC public keys\")\n\n        # Raw format and encoding are only valid for X25519, Ed25519, X448, and\n        # Ed448 keys. We capture those cases before this method is called so if\n        # we see those enum values here it means the caller has passed them to\n        # a key that doesn't support raw type\n        if format is serialization.PrivateFormat.Raw:\n            raise ValueError(\"raw format is invalid with this key or encoding\")\n\n        if encoding is serialization.Encoding.Raw:\n            raise ValueError(\"raw encoding is invalid with this key or format\")\n\n        if not isinstance(encryption_algorithm,\n                          serialization.KeySerializationEncryption):\n            raise TypeError(\n                \"Encryption algorithm must be a KeySerializationEncryption \"\n                \"instance\"\n            )\n\n        if isinstance(encryption_algorithm, serialization.NoEncryption):\n            password = b\"\"\n            passlen = 0\n            evp_cipher = self._ffi.NULL\n        elif isinstance(encryption_algorithm,\n                        serialization.BestAvailableEncryption):\n            # This is a curated value that we will update over time.\n            evp_cipher = self._lib.EVP_get_cipherbyname(\n                b\"aes-256-cbc\"\n            )\n            password = encryption_algorithm.password\n            passlen = len(password)\n            if passlen > 1023:\n                raise ValueError(\n                    \"Passwords longer than 1023 bytes are not supported by \"\n                    \"this backend\"\n                )\n        else:\n            raise ValueError(\"Unsupported encryption type\")\n\n        key_type = self._lib.EVP_PKEY_id(evp_pkey)\n        if encoding is serialization.Encoding.PEM:\n            if format is serialization.PrivateFormat.PKCS8:\n                write_bio = self._lib.PEM_write_bio_PKCS8PrivateKey\n                key = evp_pkey\n            else:\n                assert format is serialization.PrivateFormat.TraditionalOpenSSL\n                if key_type == self._lib.EVP_PKEY_RSA:\n                    write_bio = self._lib.PEM_write_bio_RSAPrivateKey\n                elif key_type == self._lib.EVP_PKEY_DSA:\n                    write_bio = self._lib.PEM_write_bio_DSAPrivateKey\n                else:\n                    assert key_type == self._lib.EVP_PKEY_EC\n                    write_bio = self._lib.PEM_write_bio_ECPrivateKey\n\n                key = cdata\n        elif encoding is serialization.Encoding.DER:\n            if format is serialization.PrivateFormat.TraditionalOpenSSL:\n                if not isinstance(\n                    encryption_algorithm, serialization.NoEncryption\n                ):\n                    raise ValueError(\n                        \"Encryption is not supported for DER encoded \"\n                        \"traditional OpenSSL keys\"\n                    )\n\n                return self._private_key_bytes_traditional_der(key_type, cdata)\n            else:\n                assert format is serialization.PrivateFormat.PKCS8\n                write_bio = self._lib.i2d_PKCS8PrivateKey_bio\n                key = evp_pkey\n        else:\n            raise TypeError(\"encoding must be Encoding.PEM or Encoding.DER\")\n\n        bio = self._create_mem_bio_gc()\n        res = write_bio(\n            bio,\n            key,\n            evp_cipher,\n            password,\n            passlen,\n            self._ffi.NULL,\n            self._ffi.NULL\n        )\n        self.openssl_assert(res == 1)\n        return self._read_mem_bio(bio)\n\n    def _private_key_bytes_traditional_der(self, key_type, cdata):\n        if key_type == self._lib.EVP_PKEY_RSA:\n            write_bio = self._lib.i2d_RSAPrivateKey_bio\n        elif key_type == self._lib.EVP_PKEY_EC:\n            write_bio = self._lib.i2d_ECPrivateKey_bio\n        else:\n            self.openssl_assert(key_type == self._lib.EVP_PKEY_DSA)\n            write_bio = self._lib.i2d_DSAPrivateKey_bio\n\n        bio = self._create_mem_bio_gc()\n        res = write_bio(bio, cdata)\n        self.openssl_assert(res == 1)\n        return self._read_mem_bio(bio)\n\n    def _public_key_bytes(self, encoding, format, key, evp_pkey, cdata):\n        if not isinstance(encoding, serialization.Encoding):\n            raise TypeError(\"encoding must be an item from the Encoding enum\")\n\n        # Compressed/UncompressedPoint are only valid for EC keys and those\n        # cases are handled by the ECPublicKey public_bytes method before this\n        # method is called\n        if format in (serialization.PublicFormat.UncompressedPoint,\n                      serialization.PublicFormat.CompressedPoint):\n            raise ValueError(\"Point formats are not valid for this key type\")\n\n        # Raw format and encoding are only valid for X25519, Ed25519, X448, and\n        # Ed448 keys. We capture those cases before this method is called so if\n        # we see those enum values here it means the caller has passed them to\n        # a key that doesn't support raw type\n        if format is serialization.PublicFormat.Raw:\n            raise ValueError(\"raw format is invalid with this key or encoding\")\n\n        if encoding is serialization.Encoding.Raw:\n            raise ValueError(\"raw encoding is invalid with this key or format\")\n\n        if (\n            format is serialization.PublicFormat.OpenSSH or\n            encoding is serialization.Encoding.OpenSSH\n        ):\n            if (\n                format is not serialization.PublicFormat.OpenSSH or\n                encoding is not serialization.Encoding.OpenSSH\n            ):\n                raise ValueError(\n                    \"OpenSSH format must be used with OpenSSH encoding\"\n                )\n            return self._openssh_public_key_bytes(key)\n        elif format is serialization.PublicFormat.SubjectPublicKeyInfo:\n            if encoding is serialization.Encoding.PEM:\n                write_bio = self._lib.PEM_write_bio_PUBKEY\n            else:\n                assert encoding is serialization.Encoding.DER\n                write_bio = self._lib.i2d_PUBKEY_bio\n\n            key = evp_pkey\n        elif format is serialization.PublicFormat.PKCS1:\n            # Only RSA is supported here.\n            assert self._lib.EVP_PKEY_id(evp_pkey) == self._lib.EVP_PKEY_RSA\n            if encoding is serialization.Encoding.PEM:\n                write_bio = self._lib.PEM_write_bio_RSAPublicKey\n            else:\n                assert encoding is serialization.Encoding.DER\n                write_bio = self._lib.i2d_RSAPublicKey_bio\n\n            key = cdata\n        else:\n            raise TypeError(\n                \"format must be an item from the PublicFormat enum\"\n            )\n\n        bio = self._create_mem_bio_gc()\n        res = write_bio(bio, key)\n        self.openssl_assert(res == 1)\n        return self._read_mem_bio(bio)\n\n    def _openssh_public_key_bytes(self, key):\n        if isinstance(key, rsa.RSAPublicKey):\n            public_numbers = key.public_numbers()\n            return b\"ssh-rsa \" + base64.b64encode(\n                ssh._ssh_write_string(b\"ssh-rsa\") +\n                ssh._ssh_write_mpint(public_numbers.e) +\n                ssh._ssh_write_mpint(public_numbers.n)\n            )\n        elif isinstance(key, dsa.DSAPublicKey):\n            public_numbers = key.public_numbers()\n            parameter_numbers = public_numbers.parameter_numbers\n            return b\"ssh-dss \" + base64.b64encode(\n                ssh._ssh_write_string(b\"ssh-dss\") +\n                ssh._ssh_write_mpint(parameter_numbers.p) +\n                ssh._ssh_write_mpint(parameter_numbers.q) +\n                ssh._ssh_write_mpint(parameter_numbers.g) +\n                ssh._ssh_write_mpint(public_numbers.y)\n            )\n        elif isinstance(key, ed25519.Ed25519PublicKey):\n            raw_bytes = key.public_bytes(serialization.Encoding.Raw,\n                                         serialization.PublicFormat.Raw)\n            return b\"ssh-ed25519 \" + base64.b64encode(\n                ssh._ssh_write_string(b\"ssh-ed25519\") +\n                ssh._ssh_write_string(raw_bytes)\n            )\n        elif isinstance(key, ec.EllipticCurvePublicKey):\n            public_numbers = key.public_numbers()\n            try:\n                curve_name = {\n                    ec.SECP256R1: b\"nistp256\",\n                    ec.SECP384R1: b\"nistp384\",\n                    ec.SECP521R1: b\"nistp521\",\n                }[type(public_numbers.curve)]\n            except KeyError:\n                raise ValueError(\n                    \"Only SECP256R1, SECP384R1, and SECP521R1 curves are \"\n                    \"supported by the SSH public key format\"\n                )\n\n            point = key.public_bytes(\n                serialization.Encoding.X962,\n                serialization.PublicFormat.UncompressedPoint\n            )\n            return b\"ecdsa-sha2-\" + curve_name + b\" \" + base64.b64encode(\n                ssh._ssh_write_string(b\"ecdsa-sha2-\" + curve_name) +\n                ssh._ssh_write_string(curve_name) +\n                ssh._ssh_write_string(point)\n            )\n        else:\n            raise ValueError(\n                \"OpenSSH encoding is not supported for this key type\"\n            )\n\n    def _parameter_bytes(self, encoding, format, cdata):\n        if encoding is serialization.Encoding.OpenSSH:\n            raise TypeError(\n                \"OpenSSH encoding is not supported\"\n            )\n\n        # Only DH is supported here currently.\n        q = self._ffi.new(\"BIGNUM **\")\n        self._lib.DH_get0_pqg(cdata,\n                              self._ffi.NULL,\n                              q,\n                              self._ffi.NULL)\n        if encoding is serialization.Encoding.PEM:\n            if q[0] != self._ffi.NULL:\n                write_bio = self._lib.PEM_write_bio_DHxparams\n            else:\n                write_bio = self._lib.PEM_write_bio_DHparams\n        elif encoding is serialization.Encoding.DER:\n            if q[0] != self._ffi.NULL:\n                write_bio = self._lib.Cryptography_i2d_DHxparams_bio\n            else:\n                write_bio = self._lib.i2d_DHparams_bio\n        else:\n            raise TypeError(\"encoding must be an item from the Encoding enum\")\n\n        bio = self._create_mem_bio_gc()\n        res = write_bio(bio, cdata)\n        self.openssl_assert(res == 1)\n        return self._read_mem_bio(bio)\n\n    def generate_dh_parameters(self, generator, key_size):\n        if key_size < 512:\n            raise ValueError(\"DH key_size must be at least 512 bits\")\n\n        if generator not in (2, 5):\n            raise ValueError(\"DH generator must be 2 or 5\")\n\n        dh_param_cdata = self._lib.DH_new()\n        self.openssl_assert(dh_param_cdata != self._ffi.NULL)\n        dh_param_cdata = self._ffi.gc(dh_param_cdata, self._lib.DH_free)\n\n        res = self._lib.DH_generate_parameters_ex(\n            dh_param_cdata,\n            key_size,\n            generator,\n            self._ffi.NULL\n        )\n        self.openssl_assert(res == 1)\n\n        return _DHParameters(self, dh_param_cdata)\n\n    def _dh_cdata_to_evp_pkey(self, dh_cdata):\n        evp_pkey = self._create_evp_pkey_gc()\n        res = self._lib.EVP_PKEY_set1_DH(evp_pkey, dh_cdata)\n        self.openssl_assert(res == 1)\n        return evp_pkey\n\n    def generate_dh_private_key(self, parameters):\n        dh_key_cdata = _dh_params_dup(parameters._dh_cdata, self)\n\n        res = self._lib.DH_generate_key(dh_key_cdata)\n        self.openssl_assert(res == 1)\n\n        evp_pkey = self._dh_cdata_to_evp_pkey(dh_key_cdata)\n\n        return _DHPrivateKey(self, dh_key_cdata, evp_pkey)\n\n    def generate_dh_private_key_and_parameters(self, generator, key_size):\n        return self.generate_dh_private_key(\n            self.generate_dh_parameters(generator, key_size))\n\n    def load_dh_private_numbers(self, numbers):\n        parameter_numbers = numbers.public_numbers.parameter_numbers\n\n        dh_cdata = self._lib.DH_new()\n        self.openssl_assert(dh_cdata != self._ffi.NULL)\n        dh_cdata = self._ffi.gc(dh_cdata, self._lib.DH_free)\n\n        p = self._int_to_bn(parameter_numbers.p)\n        g = self._int_to_bn(parameter_numbers.g)\n\n        if parameter_numbers.q is not None:\n            q = self._int_to_bn(parameter_numbers.q)\n        else:\n            q = self._ffi.NULL\n\n        pub_key = self._int_to_bn(numbers.public_numbers.y)\n        priv_key = self._int_to_bn(numbers.x)\n\n        res = self._lib.DH_set0_pqg(dh_cdata, p, q, g)\n        self.openssl_assert(res == 1)\n\n        res = self._lib.DH_set0_key(dh_cdata, pub_key, priv_key)\n        self.openssl_assert(res == 1)\n\n        codes = self._ffi.new(\"int[]\", 1)\n        res = self._lib.Cryptography_DH_check(dh_cdata, codes)\n        self.openssl_assert(res == 1)\n\n        # DH_check will return DH_NOT_SUITABLE_GENERATOR if p % 24 does not\n        # equal 11 when the generator is 2 (a quadratic nonresidue).\n        # We want to ignore that error because p % 24 == 23 is also fine.\n        # Specifically, g is then a quadratic residue. Within the context of\n        # Diffie-Hellman this means it can only generate half the possible\n        # values. That sounds bad, but quadratic nonresidues leak a bit of\n        # the key to the attacker in exchange for having the full key space\n        # available. See: https://crypto.stackexchange.com/questions/12961\n        if codes[0] != 0 and not (\n            parameter_numbers.g == 2 and\n            codes[0] ^ self._lib.DH_NOT_SUITABLE_GENERATOR == 0\n        ):\n            raise ValueError(\n                \"DH private numbers did not pass safety checks.\"\n            )\n\n        evp_pkey = self._dh_cdata_to_evp_pkey(dh_cdata)\n\n        return _DHPrivateKey(self, dh_cdata, evp_pkey)\n\n    def load_dh_public_numbers(self, numbers):\n        dh_cdata = self._lib.DH_new()\n        self.openssl_assert(dh_cdata != self._ffi.NULL)\n        dh_cdata = self._ffi.gc(dh_cdata, self._lib.DH_free)\n\n        parameter_numbers = numbers.parameter_numbers\n\n        p = self._int_to_bn(parameter_numbers.p)\n        g = self._int_to_bn(parameter_numbers.g)\n\n        if parameter_numbers.q is not None:\n            q = self._int_to_bn(parameter_numbers.q)\n        else:\n            q = self._ffi.NULL\n\n        pub_key = self._int_to_bn(numbers.y)\n\n        res = self._lib.DH_set0_pqg(dh_cdata, p, q, g)\n        self.openssl_assert(res == 1)\n\n        res = self._lib.DH_set0_key(dh_cdata, pub_key, self._ffi.NULL)\n        self.openssl_assert(res == 1)\n\n        evp_pkey = self._dh_cdata_to_evp_pkey(dh_cdata)\n\n        return _DHPublicKey(self, dh_cdata, evp_pkey)\n\n    def load_dh_parameter_numbers(self, numbers):\n        dh_cdata = self._lib.DH_new()\n        self.openssl_assert(dh_cdata != self._ffi.NULL)\n        dh_cdata = self._ffi.gc(dh_cdata, self._lib.DH_free)\n\n        p = self._int_to_bn(numbers.p)\n        g = self._int_to_bn(numbers.g)\n\n        if numbers.q is not None:\n            q = self._int_to_bn(numbers.q)\n        else:\n            q = self._ffi.NULL\n\n        res = self._lib.DH_set0_pqg(dh_cdata, p, q, g)\n        self.openssl_assert(res == 1)\n\n        return _DHParameters(self, dh_cdata)\n\n    def dh_parameters_supported(self, p, g, q=None):\n        dh_cdata = self._lib.DH_new()\n        self.openssl_assert(dh_cdata != self._ffi.NULL)\n        dh_cdata = self._ffi.gc(dh_cdata, self._lib.DH_free)\n\n        p = self._int_to_bn(p)\n        g = self._int_to_bn(g)\n\n        if q is not None:\n            q = self._int_to_bn(q)\n        else:\n            q = self._ffi.NULL\n\n        res = self._lib.DH_set0_pqg(dh_cdata, p, q, g)\n        self.openssl_assert(res == 1)\n\n        codes = self._ffi.new(\"int[]\", 1)\n        res = self._lib.Cryptography_DH_check(dh_cdata, codes)\n        self.openssl_assert(res == 1)\n\n        return codes[0] == 0\n\n    def dh_x942_serialization_supported(self):\n        return self._lib.Cryptography_HAS_EVP_PKEY_DHX == 1\n\n    def x509_name_bytes(self, name):\n        x509_name = _encode_name_gc(self, name)\n        pp = self._ffi.new(\"unsigned char **\")\n        res = self._lib.i2d_X509_NAME(x509_name, pp)\n        self.openssl_assert(pp[0] != self._ffi.NULL)\n        pp = self._ffi.gc(\n            pp, lambda pointer: self._lib.OPENSSL_free(pointer[0])\n        )\n        self.openssl_assert(res > 0)\n        return self._ffi.buffer(pp[0], res)[:]\n\n    def x25519_load_public_bytes(self, data):\n        # When we drop support for CRYPTOGRAPHY_OPENSSL_LESS_THAN_111 we can\n        # switch this to EVP_PKEY_new_raw_public_key\n        if len(data) != 32:\n            raise ValueError(\"An X25519 public key is 32 bytes long\")\n\n        evp_pkey = self._create_evp_pkey_gc()\n        res = self._lib.EVP_PKEY_set_type(evp_pkey, self._lib.NID_X25519)\n        backend.openssl_assert(res == 1)\n        res = self._lib.EVP_PKEY_set1_tls_encodedpoint(\n            evp_pkey, data, len(data)\n        )\n        backend.openssl_assert(res == 1)\n        return _X25519PublicKey(self, evp_pkey)\n\n    def x25519_load_private_bytes(self, data):\n        # When we drop support for CRYPTOGRAPHY_OPENSSL_LESS_THAN_111 we can\n        # switch this to EVP_PKEY_new_raw_private_key and drop the\n        # zeroed_bytearray garbage.\n        # OpenSSL only has facilities for loading PKCS8 formatted private\n        # keys using the algorithm identifiers specified in\n        # https://tools.ietf.org/html/draft-ietf-curdle-pkix-09.\n        # This is the standard PKCS8 prefix for a 32 byte X25519 key.\n        # The form is:\n        #    0:d=0  hl=2 l=  46 cons: SEQUENCE\n        #    2:d=1  hl=2 l=   1 prim: INTEGER           :00\n        #    5:d=1  hl=2 l=   5 cons: SEQUENCE\n        #    7:d=2  hl=2 l=   3 prim: OBJECT            :1.3.101.110\n        #    12:d=1  hl=2 l=  34 prim: OCTET STRING      (the key)\n        # Of course there's a bit more complexity. In reality OCTET STRING\n        # contains an OCTET STRING of length 32! So the last two bytes here\n        # are \\x04\\x20, which is an OCTET STRING of length 32.\n        if len(data) != 32:\n            raise ValueError(\"An X25519 private key is 32 bytes long\")\n\n        pkcs8_prefix = b'0.\\x02\\x01\\x000\\x05\\x06\\x03+en\\x04\"\\x04 '\n        with self._zeroed_bytearray(48) as ba:\n            ba[0:16] = pkcs8_prefix\n            ba[16:] = data\n            bio = self._bytes_to_bio(ba)\n            evp_pkey = backend._lib.d2i_PrivateKey_bio(bio.bio, self._ffi.NULL)\n\n        self.openssl_assert(evp_pkey != self._ffi.NULL)\n        evp_pkey = self._ffi.gc(evp_pkey, self._lib.EVP_PKEY_free)\n        self.openssl_assert(\n            self._lib.EVP_PKEY_id(evp_pkey) == self._lib.EVP_PKEY_X25519\n        )\n        return _X25519PrivateKey(self, evp_pkey)\n\n    def _evp_pkey_keygen_gc(self, nid):\n        evp_pkey_ctx = self._lib.EVP_PKEY_CTX_new_id(nid, self._ffi.NULL)\n        self.openssl_assert(evp_pkey_ctx != self._ffi.NULL)\n        evp_pkey_ctx = self._ffi.gc(evp_pkey_ctx, self._lib.EVP_PKEY_CTX_free)\n        res = self._lib.EVP_PKEY_keygen_init(evp_pkey_ctx)\n        self.openssl_assert(res == 1)\n        evp_ppkey = self._ffi.new(\"EVP_PKEY **\")\n        res = self._lib.EVP_PKEY_keygen(evp_pkey_ctx, evp_ppkey)\n        self.openssl_assert(res == 1)\n        self.openssl_assert(evp_ppkey[0] != self._ffi.NULL)\n        evp_pkey = self._ffi.gc(evp_ppkey[0], self._lib.EVP_PKEY_free)\n        return evp_pkey\n\n    def x25519_generate_key(self):\n        evp_pkey = self._evp_pkey_keygen_gc(self._lib.NID_X25519)\n        return _X25519PrivateKey(self, evp_pkey)\n\n    def x25519_supported(self):\n        return self._lib.CRYPTOGRAPHY_OPENSSL_110_OR_GREATER\n\n    def x448_load_public_bytes(self, data):\n        if len(data) != 56:\n            raise ValueError(\"An X448 public key is 56 bytes long\")\n\n        evp_pkey = self._lib.EVP_PKEY_new_raw_public_key(\n            self._lib.NID_X448, self._ffi.NULL, data, len(data)\n        )\n        self.openssl_assert(evp_pkey != self._ffi.NULL)\n        evp_pkey = self._ffi.gc(evp_pkey, self._lib.EVP_PKEY_free)\n        return _X448PublicKey(self, evp_pkey)\n\n    def x448_load_private_bytes(self, data):\n        if len(data) != 56:\n            raise ValueError(\"An X448 private key is 56 bytes long\")\n\n        data_ptr = self._ffi.from_buffer(data)\n        evp_pkey = self._lib.EVP_PKEY_new_raw_private_key(\n            self._lib.NID_X448, self._ffi.NULL, data_ptr, len(data)\n        )\n        self.openssl_assert(evp_pkey != self._ffi.NULL)\n        evp_pkey = self._ffi.gc(evp_pkey, self._lib.EVP_PKEY_free)\n        return _X448PrivateKey(self, evp_pkey)\n\n    def x448_generate_key(self):\n        evp_pkey = self._evp_pkey_keygen_gc(self._lib.NID_X448)\n        return _X448PrivateKey(self, evp_pkey)\n\n    def x448_supported(self):\n        return not self._lib.CRYPTOGRAPHY_OPENSSL_LESS_THAN_111\n\n    def ed25519_supported(self):\n        return not self._lib.CRYPTOGRAPHY_OPENSSL_LESS_THAN_111B\n\n    def ed25519_load_public_bytes(self, data):\n        utils._check_bytes(\"data\", data)\n\n        if len(data) != ed25519._ED25519_KEY_SIZE:\n            raise ValueError(\"An Ed25519 public key is 32 bytes long\")\n\n        evp_pkey = self._lib.EVP_PKEY_new_raw_public_key(\n            self._lib.NID_ED25519, self._ffi.NULL, data, len(data)\n        )\n        self.openssl_assert(evp_pkey != self._ffi.NULL)\n        evp_pkey = self._ffi.gc(evp_pkey, self._lib.EVP_PKEY_free)\n\n        return _Ed25519PublicKey(self, evp_pkey)\n\n    def ed25519_load_private_bytes(self, data):\n        if len(data) != ed25519._ED25519_KEY_SIZE:\n            raise ValueError(\"An Ed25519 private key is 32 bytes long\")\n\n        utils._check_byteslike(\"data\", data)\n        data_ptr = self._ffi.from_buffer(data)\n        evp_pkey = self._lib.EVP_PKEY_new_raw_private_key(\n            self._lib.NID_ED25519, self._ffi.NULL, data_ptr, len(data)\n        )\n        self.openssl_assert(evp_pkey != self._ffi.NULL)\n        evp_pkey = self._ffi.gc(evp_pkey, self._lib.EVP_PKEY_free)\n\n        return _Ed25519PrivateKey(self, evp_pkey)\n\n    def ed25519_generate_key(self):\n        evp_pkey = self._evp_pkey_keygen_gc(self._lib.NID_ED25519)\n        return _Ed25519PrivateKey(self, evp_pkey)\n\n    def ed448_supported(self):\n        return not self._lib.CRYPTOGRAPHY_OPENSSL_LESS_THAN_111B\n\n    def ed448_load_public_bytes(self, data):\n        utils._check_bytes(\"data\", data)\n        if len(data) != _ED448_KEY_SIZE:\n            raise ValueError(\"An Ed448 public key is 57 bytes long\")\n\n        evp_pkey = self._lib.EVP_PKEY_new_raw_public_key(\n            self._lib.NID_ED448, self._ffi.NULL, data, len(data)\n        )\n        self.openssl_assert(evp_pkey != self._ffi.NULL)\n        evp_pkey = self._ffi.gc(evp_pkey, self._lib.EVP_PKEY_free)\n\n        return _Ed448PublicKey(self, evp_pkey)\n\n    def ed448_load_private_bytes(self, data):\n        utils._check_byteslike(\"data\", data)\n        if len(data) != _ED448_KEY_SIZE:\n            raise ValueError(\"An Ed448 private key is 57 bytes long\")\n\n        data_ptr = self._ffi.from_buffer(data)\n        evp_pkey = self._lib.EVP_PKEY_new_raw_private_key(\n            self._lib.NID_ED448, self._ffi.NULL, data_ptr, len(data)\n        )\n        self.openssl_assert(evp_pkey != self._ffi.NULL)\n        evp_pkey = self._ffi.gc(evp_pkey, self._lib.EVP_PKEY_free)\n\n        return _Ed448PrivateKey(self, evp_pkey)\n\n    def ed448_generate_key(self):\n        evp_pkey = self._evp_pkey_keygen_gc(self._lib.NID_ED448)\n        return _Ed448PrivateKey(self, evp_pkey)\n\n    def derive_scrypt(self, key_material, salt, length, n, r, p):\n        buf = self._ffi.new(\"unsigned char[]\", length)\n        key_material_ptr = self._ffi.from_buffer(key_material)\n        res = self._lib.EVP_PBE_scrypt(\n            key_material_ptr, len(key_material), salt, len(salt), n, r, p,\n            scrypt._MEM_LIMIT, buf, length\n        )\n        if res != 1:\n            errors = self._consume_errors()\n            if not self._lib.CRYPTOGRAPHY_OPENSSL_LESS_THAN_111:\n                # This error is only added to the stack in 1.1.1+\n                self.openssl_assert(\n                    errors[0]._lib_reason_match(\n                        self._lib.ERR_LIB_EVP,\n                        self._lib.ERR_R_MALLOC_FAILURE\n                    ) or\n                    errors[0]._lib_reason_match(\n                        self._lib.ERR_LIB_EVP,\n                        self._lib.EVP_R_MEMORY_LIMIT_EXCEEDED\n                    )\n                )\n\n            # memory required formula explained here:\n            # https://blog.filippo.io/the-scrypt-parameters/\n            min_memory = 128 * n * r // (1024**2)\n            raise MemoryError(\n                \"Not enough memory to derive key. These parameters require\"\n                \" {} MB of memory.\".format(min_memory)\n            )\n        return self._ffi.buffer(buf)[:]\n\n    def aead_cipher_supported(self, cipher):\n        cipher_name = aead._aead_cipher_name(cipher)\n        return (\n            self._lib.EVP_get_cipherbyname(cipher_name) != self._ffi.NULL\n        )\n\n    @contextlib.contextmanager\n    def _zeroed_bytearray(self, length):\n        \"\"\"\n        This method creates a bytearray, which we copy data into (hopefully\n        also from a mutable buffer that can be dynamically erased!), and then\n        zero when we're done.\n        \"\"\"\n        ba = bytearray(length)\n        try:\n            yield ba\n        finally:\n            self._zero_data(ba, length)\n\n    def _zero_data(self, data, length):\n        # We clear things this way because at the moment we're not\n        # sure of a better way that can guarantee it overwrites the\n        # memory of a bytearray and doesn't just replace the underlying char *.\n        for i in range(length):\n            data[i] = 0\n\n    @contextlib.contextmanager\n    def _zeroed_null_terminated_buf(self, data):\n        \"\"\"\n        This method takes bytes, which can be a bytestring or a mutable\n        buffer like a bytearray, and yields a null-terminated version of that\n        data. This is required because PKCS12_parse doesn't take a length with\n        its password char * and ffi.from_buffer doesn't provide null\n        termination. So, to support zeroing the data via bytearray we\n        need to build this ridiculous construct that copies the memory, but\n        zeroes it after use.\n        \"\"\"\n        if data is None:\n            yield self._ffi.NULL\n        else:\n            data_len = len(data)\n            buf = self._ffi.new(\"char[]\", data_len + 1)\n            self._ffi.memmove(buf, data, data_len)\n            try:\n                yield buf\n            finally:\n                # Cast to a uint8_t * so we can assign by integer\n                self._zero_data(self._ffi.cast(\"uint8_t *\", buf), data_len)\n\n    def load_key_and_certificates_from_pkcs12(self, data, password):\n        if password is not None:\n            utils._check_byteslike(\"password\", password)\n\n        bio = self._bytes_to_bio(data)\n        p12 = self._lib.d2i_PKCS12_bio(bio.bio, self._ffi.NULL)\n        if p12 == self._ffi.NULL:\n            self._consume_errors()\n            raise ValueError(\"Could not deserialize PKCS12 data\")\n\n        p12 = self._ffi.gc(p12, self._lib.PKCS12_free)\n        evp_pkey_ptr = self._ffi.new(\"EVP_PKEY **\")\n        x509_ptr = self._ffi.new(\"X509 **\")\n        sk_x509_ptr = self._ffi.new(\"Cryptography_STACK_OF_X509 **\")\n        with self._zeroed_null_terminated_buf(password) as password_buf:\n            res = self._lib.PKCS12_parse(\n                p12, password_buf, evp_pkey_ptr, x509_ptr, sk_x509_ptr\n            )\n\n        if res == 0:\n            self._consume_errors()\n            raise ValueError(\"Invalid password or PKCS12 data\")\n\n        cert = None\n        key = None\n        additional_certificates = []\n\n        if evp_pkey_ptr[0] != self._ffi.NULL:\n            evp_pkey = self._ffi.gc(evp_pkey_ptr[0], self._lib.EVP_PKEY_free)\n            key = self._evp_pkey_to_private_key(evp_pkey)\n\n        if x509_ptr[0] != self._ffi.NULL:\n            x509 = self._ffi.gc(x509_ptr[0], self._lib.X509_free)\n            cert = _Certificate(self, x509)\n\n        if sk_x509_ptr[0] != self._ffi.NULL:\n            sk_x509 = self._ffi.gc(sk_x509_ptr[0], self._lib.sk_X509_free)\n            num = self._lib.sk_X509_num(sk_x509_ptr[0])\n            for i in range(num):\n                x509 = self._lib.sk_X509_value(sk_x509, i)\n                x509 = self._ffi.gc(x509, self._lib.X509_free)\n                self.openssl_assert(x509 != self._ffi.NULL)\n                additional_certificates.append(_Certificate(self, x509))\n\n        return (key, cert, additional_certificates)\n\n    def poly1305_supported(self):\n        return self._lib.Cryptography_HAS_POLY1305 == 1\n\n    def create_poly1305_ctx(self, key):\n        utils._check_byteslike(\"key\", key)\n        if len(key) != _POLY1305_KEY_SIZE:\n            raise ValueError(\"A poly1305 key is 32 bytes long\")\n\n        return _Poly1305Context(self, key)\n\n\nclass GetCipherByName(object):\n    def __init__(self, fmt):\n        self._fmt = fmt\n\n    def __call__(self, backend, cipher, mode):\n        cipher_name = self._fmt.format(cipher=cipher, mode=mode).lower()\n        return backend._lib.EVP_get_cipherbyname(cipher_name.encode(\"ascii\"))\n\n\ndef _get_xts_cipher(backend, cipher, mode):\n    cipher_name = \"aes-{}-xts\".format(cipher.key_size // 2)\n    return backend._lib.EVP_get_cipherbyname(cipher_name.encode(\"ascii\"))\n\n\nbackend = Backend()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/ciphers.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import utils\nfrom cryptography.exceptions import InvalidTag, UnsupportedAlgorithm, _Reasons\nfrom cryptography.hazmat.primitives import ciphers\nfrom cryptography.hazmat.primitives.ciphers import modes\n\n\n@utils.register_interface(ciphers.CipherContext)\n@utils.register_interface(ciphers.AEADCipherContext)\n@utils.register_interface(ciphers.AEADEncryptionContext)\n@utils.register_interface(ciphers.AEADDecryptionContext)\nclass _CipherContext(object):\n    _ENCRYPT = 1\n    _DECRYPT = 0\n\n    def __init__(self, backend, cipher, mode, operation):\n        self._backend = backend\n        self._cipher = cipher\n        self._mode = mode\n        self._operation = operation\n        self._tag = None\n\n        if isinstance(self._cipher, ciphers.BlockCipherAlgorithm):\n            self._block_size_bytes = self._cipher.block_size // 8\n        else:\n            self._block_size_bytes = 1\n\n        ctx = self._backend._lib.EVP_CIPHER_CTX_new()\n        ctx = self._backend._ffi.gc(\n            ctx, self._backend._lib.EVP_CIPHER_CTX_free\n        )\n\n        registry = self._backend._cipher_registry\n        try:\n            adapter = registry[type(cipher), type(mode)]\n        except KeyError:\n            raise UnsupportedAlgorithm(\n                \"cipher {} in {} mode is not supported \"\n                \"by this backend.\".format(\n                    cipher.name, mode.name if mode else mode),\n                _Reasons.UNSUPPORTED_CIPHER\n            )\n\n        evp_cipher = adapter(self._backend, cipher, mode)\n        if evp_cipher == self._backend._ffi.NULL:\n            msg = \"cipher {0.name} \".format(cipher)\n            if mode is not None:\n                msg += \"in {0.name} mode \".format(mode)\n            msg += (\n                \"is not supported by this backend (Your version of OpenSSL \"\n                \"may be too old. Current version: {}.)\"\n            ).format(self._backend.openssl_version_text())\n            raise UnsupportedAlgorithm(msg, _Reasons.UNSUPPORTED_CIPHER)\n\n        if isinstance(mode, modes.ModeWithInitializationVector):\n            iv_nonce = self._backend._ffi.from_buffer(\n                mode.initialization_vector\n            )\n        elif isinstance(mode, modes.ModeWithTweak):\n            iv_nonce = self._backend._ffi.from_buffer(mode.tweak)\n        elif isinstance(mode, modes.ModeWithNonce):\n            iv_nonce = self._backend._ffi.from_buffer(mode.nonce)\n        elif isinstance(cipher, modes.ModeWithNonce):\n            iv_nonce = self._backend._ffi.from_buffer(cipher.nonce)\n        else:\n            iv_nonce = self._backend._ffi.NULL\n        # begin init with cipher and operation type\n        res = self._backend._lib.EVP_CipherInit_ex(ctx, evp_cipher,\n                                                   self._backend._ffi.NULL,\n                                                   self._backend._ffi.NULL,\n                                                   self._backend._ffi.NULL,\n                                                   operation)\n        self._backend.openssl_assert(res != 0)\n        # set the key length to handle variable key ciphers\n        res = self._backend._lib.EVP_CIPHER_CTX_set_key_length(\n            ctx, len(cipher.key)\n        )\n        self._backend.openssl_assert(res != 0)\n        if isinstance(mode, modes.GCM):\n            res = self._backend._lib.EVP_CIPHER_CTX_ctrl(\n                ctx, self._backend._lib.EVP_CTRL_AEAD_SET_IVLEN,\n                len(iv_nonce), self._backend._ffi.NULL\n            )\n            self._backend.openssl_assert(res != 0)\n            if mode.tag is not None:\n                res = self._backend._lib.EVP_CIPHER_CTX_ctrl(\n                    ctx, self._backend._lib.EVP_CTRL_AEAD_SET_TAG,\n                    len(mode.tag), mode.tag\n                )\n                self._backend.openssl_assert(res != 0)\n                self._tag = mode.tag\n            elif (\n                self._operation == self._DECRYPT and\n                self._backend._lib.CRYPTOGRAPHY_OPENSSL_LESS_THAN_102 and\n                not self._backend._lib.CRYPTOGRAPHY_IS_LIBRESSL\n            ):\n                raise NotImplementedError(\n                    \"delayed passing of GCM tag requires OpenSSL >= 1.0.2.\"\n                    \" To use this feature please update OpenSSL\"\n                )\n\n        # pass key/iv\n        res = self._backend._lib.EVP_CipherInit_ex(\n            ctx,\n            self._backend._ffi.NULL,\n            self._backend._ffi.NULL,\n            self._backend._ffi.from_buffer(cipher.key),\n            iv_nonce,\n            operation\n        )\n        self._backend.openssl_assert(res != 0)\n        # We purposely disable padding here as it's handled higher up in the\n        # API.\n        self._backend._lib.EVP_CIPHER_CTX_set_padding(ctx, 0)\n        self._ctx = ctx\n\n    def update(self, data):\n        buf = bytearray(len(data) + self._block_size_bytes - 1)\n        n = self.update_into(data, buf)\n        return bytes(buf[:n])\n\n    def update_into(self, data, buf):\n        if len(buf) < (len(data) + self._block_size_bytes - 1):\n            raise ValueError(\n                \"buffer must be at least {} bytes for this \"\n                \"payload\".format(len(data) + self._block_size_bytes - 1)\n            )\n\n        buf = self._backend._ffi.cast(\n            \"unsigned char *\", self._backend._ffi.from_buffer(buf)\n        )\n        outlen = self._backend._ffi.new(\"int *\")\n        res = self._backend._lib.EVP_CipherUpdate(\n            self._ctx, buf, outlen,\n            self._backend._ffi.from_buffer(data), len(data)\n        )\n        self._backend.openssl_assert(res != 0)\n        return outlen[0]\n\n    def finalize(self):\n        # OpenSSL 1.0.1 on Ubuntu 12.04 (and possibly other distributions)\n        # appears to have a bug where you must make at least one call to update\n        # even if you are only using authenticate_additional_data or the\n        # GCM tag will be wrong. An (empty) call to update resolves this\n        # and is harmless for all other versions of OpenSSL.\n        if isinstance(self._mode, modes.GCM):\n            self.update(b\"\")\n\n        if (\n            self._operation == self._DECRYPT and\n            isinstance(self._mode, modes.ModeWithAuthenticationTag) and\n            self.tag is None\n        ):\n            raise ValueError(\n                \"Authentication tag must be provided when decrypting.\"\n            )\n\n        buf = self._backend._ffi.new(\"unsigned char[]\", self._block_size_bytes)\n        outlen = self._backend._ffi.new(\"int *\")\n        res = self._backend._lib.EVP_CipherFinal_ex(self._ctx, buf, outlen)\n        if res == 0:\n            errors = self._backend._consume_errors()\n\n            if not errors and isinstance(self._mode, modes.GCM):\n                raise InvalidTag\n\n            self._backend.openssl_assert(\n                errors[0]._lib_reason_match(\n                    self._backend._lib.ERR_LIB_EVP,\n                    self._backend._lib.EVP_R_DATA_NOT_MULTIPLE_OF_BLOCK_LENGTH\n                )\n            )\n            raise ValueError(\n                \"The length of the provided data is not a multiple of \"\n                \"the block length.\"\n            )\n\n        if (isinstance(self._mode, modes.GCM) and\n           self._operation == self._ENCRYPT):\n            tag_buf = self._backend._ffi.new(\n                \"unsigned char[]\", self._block_size_bytes\n            )\n            res = self._backend._lib.EVP_CIPHER_CTX_ctrl(\n                self._ctx, self._backend._lib.EVP_CTRL_AEAD_GET_TAG,\n                self._block_size_bytes, tag_buf\n            )\n            self._backend.openssl_assert(res != 0)\n            self._tag = self._backend._ffi.buffer(tag_buf)[:]\n\n        res = self._backend._lib.EVP_CIPHER_CTX_cleanup(self._ctx)\n        self._backend.openssl_assert(res == 1)\n        return self._backend._ffi.buffer(buf)[:outlen[0]]\n\n    def finalize_with_tag(self, tag):\n        if (\n            self._backend._lib.CRYPTOGRAPHY_OPENSSL_LESS_THAN_102 and\n            not self._backend._lib.CRYPTOGRAPHY_IS_LIBRESSL\n        ):\n            raise NotImplementedError(\n                \"finalize_with_tag requires OpenSSL >= 1.0.2. To use this \"\n                \"method please update OpenSSL\"\n            )\n        if len(tag) < self._mode._min_tag_length:\n            raise ValueError(\n                \"Authentication tag must be {} bytes or longer.\".format(\n                    self._mode._min_tag_length)\n            )\n        res = self._backend._lib.EVP_CIPHER_CTX_ctrl(\n            self._ctx, self._backend._lib.EVP_CTRL_AEAD_SET_TAG,\n            len(tag), tag\n        )\n        self._backend.openssl_assert(res != 0)\n        self._tag = tag\n        return self.finalize()\n\n    def authenticate_additional_data(self, data):\n        outlen = self._backend._ffi.new(\"int *\")\n        res = self._backend._lib.EVP_CipherUpdate(\n            self._ctx, self._backend._ffi.NULL, outlen,\n            self._backend._ffi.from_buffer(data), len(data)\n        )\n        self._backend.openssl_assert(res != 0)\n\n    tag = utils.read_only_property(\"_tag\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/cmac.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    InvalidSignature, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.primitives import constant_time\nfrom cryptography.hazmat.primitives.ciphers.modes import CBC\n\n\nclass _CMACContext(object):\n    def __init__(self, backend, algorithm, ctx=None):\n        if not backend.cmac_algorithm_supported(algorithm):\n            raise UnsupportedAlgorithm(\"This backend does not support CMAC.\",\n                                       _Reasons.UNSUPPORTED_CIPHER)\n\n        self._backend = backend\n        self._key = algorithm.key\n        self._algorithm = algorithm\n        self._output_length = algorithm.block_size // 8\n\n        if ctx is None:\n            registry = self._backend._cipher_registry\n            adapter = registry[type(algorithm), CBC]\n\n            evp_cipher = adapter(self._backend, algorithm, CBC)\n\n            ctx = self._backend._lib.CMAC_CTX_new()\n\n            self._backend.openssl_assert(ctx != self._backend._ffi.NULL)\n            ctx = self._backend._ffi.gc(ctx, self._backend._lib.CMAC_CTX_free)\n\n            key_ptr = self._backend._ffi.from_buffer(self._key)\n            res = self._backend._lib.CMAC_Init(\n                ctx, key_ptr, len(self._key),\n                evp_cipher, self._backend._ffi.NULL\n            )\n            self._backend.openssl_assert(res == 1)\n\n        self._ctx = ctx\n\n    algorithm = utils.read_only_property(\"_algorithm\")\n\n    def update(self, data):\n        res = self._backend._lib.CMAC_Update(self._ctx, data, len(data))\n        self._backend.openssl_assert(res == 1)\n\n    def finalize(self):\n        buf = self._backend._ffi.new(\"unsigned char[]\", self._output_length)\n        length = self._backend._ffi.new(\"size_t *\", self._output_length)\n        res = self._backend._lib.CMAC_Final(\n            self._ctx, buf, length\n        )\n        self._backend.openssl_assert(res == 1)\n\n        self._ctx = None\n\n        return self._backend._ffi.buffer(buf)[:]\n\n    def copy(self):\n        copied_ctx = self._backend._lib.CMAC_CTX_new()\n        copied_ctx = self._backend._ffi.gc(\n            copied_ctx, self._backend._lib.CMAC_CTX_free\n        )\n        res = self._backend._lib.CMAC_CTX_copy(\n            copied_ctx, self._ctx\n        )\n        self._backend.openssl_assert(res == 1)\n        return _CMACContext(\n            self._backend, self._algorithm, ctx=copied_ctx\n        )\n\n    def verify(self, signature):\n        digest = self.finalize()\n        if not constant_time.bytes_eq(digest, signature):\n            raise InvalidSignature(\"Signature did not match digest.\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/decode_asn1.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport datetime\nimport ipaddress\n\nimport six\n\nfrom cryptography import x509\nfrom cryptography.hazmat._der import DERReader, INTEGER, NULL, SEQUENCE\nfrom cryptography.x509.extensions import _TLS_FEATURE_TYPE_TO_ENUM\nfrom cryptography.x509.name import _ASN1_TYPE_TO_ENUM\nfrom cryptography.x509.oid import (\n    CRLEntryExtensionOID, CertificatePoliciesOID, ExtensionOID,\n    OCSPExtensionOID,\n)\n\n\ndef _obj2txt(backend, obj):\n    # Set to 80 on the recommendation of\n    # https://www.openssl.org/docs/crypto/OBJ_nid2ln.html#return_values\n    #\n    # But OIDs longer than this occur in real life (e.g. Active\n    # Directory makes some very long OIDs).  So we need to detect\n    # and properly handle the case where the default buffer is not\n    # big enough.\n    #\n    buf_len = 80\n    buf = backend._ffi.new(\"char[]\", buf_len)\n\n    # 'res' is the number of bytes that *would* be written if the\n    # buffer is large enough.  If 'res' > buf_len - 1, we need to\n    # alloc a big-enough buffer and go again.\n    res = backend._lib.OBJ_obj2txt(buf, buf_len, obj, 1)\n    if res > buf_len - 1:  # account for terminating null byte\n        buf_len = res + 1\n        buf = backend._ffi.new(\"char[]\", buf_len)\n        res = backend._lib.OBJ_obj2txt(buf, buf_len, obj, 1)\n    backend.openssl_assert(res > 0)\n    return backend._ffi.buffer(buf, res)[:].decode()\n\n\ndef _decode_x509_name_entry(backend, x509_name_entry):\n    obj = backend._lib.X509_NAME_ENTRY_get_object(x509_name_entry)\n    backend.openssl_assert(obj != backend._ffi.NULL)\n    data = backend._lib.X509_NAME_ENTRY_get_data(x509_name_entry)\n    backend.openssl_assert(data != backend._ffi.NULL)\n    value = _asn1_string_to_utf8(backend, data)\n    oid = _obj2txt(backend, obj)\n    type = _ASN1_TYPE_TO_ENUM[data.type]\n\n    return x509.NameAttribute(x509.ObjectIdentifier(oid), value, type)\n\n\ndef _decode_x509_name(backend, x509_name):\n    count = backend._lib.X509_NAME_entry_count(x509_name)\n    attributes = []\n    prev_set_id = -1\n    for x in range(count):\n        entry = backend._lib.X509_NAME_get_entry(x509_name, x)\n        attribute = _decode_x509_name_entry(backend, entry)\n        set_id = backend._lib.Cryptography_X509_NAME_ENTRY_set(entry)\n        if set_id != prev_set_id:\n            attributes.append(set([attribute]))\n        else:\n            # is in the same RDN a previous entry\n            attributes[-1].add(attribute)\n        prev_set_id = set_id\n\n    return x509.Name(x509.RelativeDistinguishedName(rdn) for rdn in attributes)\n\n\ndef _decode_general_names(backend, gns):\n    num = backend._lib.sk_GENERAL_NAME_num(gns)\n    names = []\n    for i in range(num):\n        gn = backend._lib.sk_GENERAL_NAME_value(gns, i)\n        backend.openssl_assert(gn != backend._ffi.NULL)\n        names.append(_decode_general_name(backend, gn))\n\n    return names\n\n\ndef _decode_general_name(backend, gn):\n    if gn.type == backend._lib.GEN_DNS:\n        # Convert to bytes and then decode to utf8. We don't use\n        # asn1_string_to_utf8 here because it doesn't properly convert\n        # utf8 from ia5strings.\n        data = _asn1_string_to_bytes(backend, gn.d.dNSName).decode(\"utf8\")\n        # We don't use the constructor for DNSName so we can bypass validation\n        # This allows us to create DNSName objects that have unicode chars\n        # when a certificate (against the RFC) contains them.\n        return x509.DNSName._init_without_validation(data)\n    elif gn.type == backend._lib.GEN_URI:\n        # Convert to bytes and then decode to utf8. We don't use\n        # asn1_string_to_utf8 here because it doesn't properly convert\n        # utf8 from ia5strings.\n        data = _asn1_string_to_bytes(\n            backend, gn.d.uniformResourceIdentifier\n        ).decode(\"utf8\")\n        # We don't use the constructor for URI so we can bypass validation\n        # This allows us to create URI objects that have unicode chars\n        # when a certificate (against the RFC) contains them.\n        return x509.UniformResourceIdentifier._init_without_validation(data)\n    elif gn.type == backend._lib.GEN_RID:\n        oid = _obj2txt(backend, gn.d.registeredID)\n        return x509.RegisteredID(x509.ObjectIdentifier(oid))\n    elif gn.type == backend._lib.GEN_IPADD:\n        data = _asn1_string_to_bytes(backend, gn.d.iPAddress)\n        data_len = len(data)\n        if data_len == 8 or data_len == 32:\n            # This is an IPv4 or IPv6 Network and not a single IP. This\n            # type of data appears in Name Constraints. Unfortunately,\n            # ipaddress doesn't support packed bytes + netmask. Additionally,\n            # IPv6Network can only handle CIDR rather than the full 16 byte\n            # netmask. To handle this we convert the netmask to integer, then\n            # find the first 0 bit, which will be the prefix. If another 1\n            # bit is present after that the netmask is invalid.\n            base = ipaddress.ip_address(data[:data_len // 2])\n            netmask = ipaddress.ip_address(data[data_len // 2:])\n            bits = bin(int(netmask))[2:]\n            prefix = bits.find('0')\n            # If no 0 bits are found it is a /32 or /128\n            if prefix == -1:\n                prefix = len(bits)\n\n            if \"1\" in bits[prefix:]:\n                raise ValueError(\"Invalid netmask\")\n\n            ip = ipaddress.ip_network(base.exploded + u\"/{}\".format(prefix))\n        else:\n            ip = ipaddress.ip_address(data)\n\n        return x509.IPAddress(ip)\n    elif gn.type == backend._lib.GEN_DIRNAME:\n        return x509.DirectoryName(\n            _decode_x509_name(backend, gn.d.directoryName)\n        )\n    elif gn.type == backend._lib.GEN_EMAIL:\n        # Convert to bytes and then decode to utf8. We don't use\n        # asn1_string_to_utf8 here because it doesn't properly convert\n        # utf8 from ia5strings.\n        data = _asn1_string_to_bytes(backend, gn.d.rfc822Name).decode(\"utf8\")\n        # We don't use the constructor for RFC822Name so we can bypass\n        # validation. This allows us to create RFC822Name objects that have\n        # unicode chars when a certificate (against the RFC) contains them.\n        return x509.RFC822Name._init_without_validation(data)\n    elif gn.type == backend._lib.GEN_OTHERNAME:\n        type_id = _obj2txt(backend, gn.d.otherName.type_id)\n        value = _asn1_to_der(backend, gn.d.otherName.value)\n        return x509.OtherName(x509.ObjectIdentifier(type_id), value)\n    else:\n        # x400Address or ediPartyName\n        raise x509.UnsupportedGeneralNameType(\n            \"{} is not a supported type\".format(\n                x509._GENERAL_NAMES.get(gn.type, gn.type)\n            ),\n            gn.type\n        )\n\n\ndef _decode_ocsp_no_check(backend, ext):\n    return x509.OCSPNoCheck()\n\n\ndef _decode_crl_number(backend, ext):\n    asn1_int = backend._ffi.cast(\"ASN1_INTEGER *\", ext)\n    asn1_int = backend._ffi.gc(asn1_int, backend._lib.ASN1_INTEGER_free)\n    return x509.CRLNumber(_asn1_integer_to_int(backend, asn1_int))\n\n\ndef _decode_delta_crl_indicator(backend, ext):\n    asn1_int = backend._ffi.cast(\"ASN1_INTEGER *\", ext)\n    asn1_int = backend._ffi.gc(asn1_int, backend._lib.ASN1_INTEGER_free)\n    return x509.DeltaCRLIndicator(_asn1_integer_to_int(backend, asn1_int))\n\n\nclass _X509ExtensionParser(object):\n    def __init__(self, ext_count, get_ext, handlers):\n        self.ext_count = ext_count\n        self.get_ext = get_ext\n        self.handlers = handlers\n\n    def parse(self, backend, x509_obj):\n        extensions = []\n        seen_oids = set()\n        for i in range(self.ext_count(backend, x509_obj)):\n            ext = self.get_ext(backend, x509_obj, i)\n            backend.openssl_assert(ext != backend._ffi.NULL)\n            crit = backend._lib.X509_EXTENSION_get_critical(ext)\n            critical = crit == 1\n            oid = x509.ObjectIdentifier(\n                _obj2txt(backend, backend._lib.X509_EXTENSION_get_object(ext))\n            )\n            if oid in seen_oids:\n                raise x509.DuplicateExtension(\n                    \"Duplicate {} extension found\".format(oid), oid\n                )\n\n            # These OIDs are only supported in OpenSSL 1.1.0+ but we want\n            # to support them in all versions of OpenSSL so we decode them\n            # ourselves.\n            if oid == ExtensionOID.TLS_FEATURE:\n                # The extension contents are a SEQUENCE OF INTEGERs.\n                data = backend._lib.X509_EXTENSION_get_data(ext)\n                data_bytes = _asn1_string_to_bytes(backend, data)\n                features = DERReader(data_bytes).read_single_element(SEQUENCE)\n                parsed = []\n                while not features.is_empty():\n                    parsed.append(features.read_element(INTEGER).as_integer())\n                # Map the features to their enum value.\n                value = x509.TLSFeature(\n                    [_TLS_FEATURE_TYPE_TO_ENUM[x] for x in parsed]\n                )\n                extensions.append(x509.Extension(oid, critical, value))\n                seen_oids.add(oid)\n                continue\n            elif oid == ExtensionOID.PRECERT_POISON:\n                data = backend._lib.X509_EXTENSION_get_data(ext)\n                # The contents of the extension must be an ASN.1 NULL.\n                reader = DERReader(_asn1_string_to_bytes(backend, data))\n                reader.read_single_element(NULL).check_empty()\n                extensions.append(x509.Extension(\n                    oid, critical, x509.PrecertPoison()\n                ))\n                seen_oids.add(oid)\n                continue\n\n            try:\n                handler = self.handlers[oid]\n            except KeyError:\n                # Dump the DER payload into an UnrecognizedExtension object\n                data = backend._lib.X509_EXTENSION_get_data(ext)\n                backend.openssl_assert(data != backend._ffi.NULL)\n                der = backend._ffi.buffer(data.data, data.length)[:]\n                unrecognized = x509.UnrecognizedExtension(oid, der)\n                extensions.append(\n                    x509.Extension(oid, critical, unrecognized)\n                )\n            else:\n                ext_data = backend._lib.X509V3_EXT_d2i(ext)\n                if ext_data == backend._ffi.NULL:\n                    backend._consume_errors()\n                    raise ValueError(\n                        \"The {} extension is invalid and can't be \"\n                        \"parsed\".format(oid)\n                    )\n\n                value = handler(backend, ext_data)\n                extensions.append(x509.Extension(oid, critical, value))\n\n            seen_oids.add(oid)\n\n        return x509.Extensions(extensions)\n\n\ndef _decode_certificate_policies(backend, cp):\n    cp = backend._ffi.cast(\"Cryptography_STACK_OF_POLICYINFO *\", cp)\n    cp = backend._ffi.gc(cp, backend._lib.CERTIFICATEPOLICIES_free)\n\n    num = backend._lib.sk_POLICYINFO_num(cp)\n    certificate_policies = []\n    for i in range(num):\n        qualifiers = None\n        pi = backend._lib.sk_POLICYINFO_value(cp, i)\n        oid = x509.ObjectIdentifier(_obj2txt(backend, pi.policyid))\n        if pi.qualifiers != backend._ffi.NULL:\n            qnum = backend._lib.sk_POLICYQUALINFO_num(pi.qualifiers)\n            qualifiers = []\n            for j in range(qnum):\n                pqi = backend._lib.sk_POLICYQUALINFO_value(\n                    pi.qualifiers, j\n                )\n                pqualid = x509.ObjectIdentifier(\n                    _obj2txt(backend, pqi.pqualid)\n                )\n                if pqualid == CertificatePoliciesOID.CPS_QUALIFIER:\n                    cpsuri = backend._ffi.buffer(\n                        pqi.d.cpsuri.data, pqi.d.cpsuri.length\n                    )[:].decode('ascii')\n                    qualifiers.append(cpsuri)\n                else:\n                    assert pqualid == CertificatePoliciesOID.CPS_USER_NOTICE\n                    user_notice = _decode_user_notice(\n                        backend, pqi.d.usernotice\n                    )\n                    qualifiers.append(user_notice)\n\n        certificate_policies.append(\n            x509.PolicyInformation(oid, qualifiers)\n        )\n\n    return x509.CertificatePolicies(certificate_policies)\n\n\ndef _decode_user_notice(backend, un):\n    explicit_text = None\n    notice_reference = None\n\n    if un.exptext != backend._ffi.NULL:\n        explicit_text = _asn1_string_to_utf8(backend, un.exptext)\n\n    if un.noticeref != backend._ffi.NULL:\n        organization = _asn1_string_to_utf8(\n            backend, un.noticeref.organization\n        )\n\n        num = backend._lib.sk_ASN1_INTEGER_num(\n            un.noticeref.noticenos\n        )\n        notice_numbers = []\n        for i in range(num):\n            asn1_int = backend._lib.sk_ASN1_INTEGER_value(\n                un.noticeref.noticenos, i\n            )\n            notice_num = _asn1_integer_to_int(backend, asn1_int)\n            notice_numbers.append(notice_num)\n\n        notice_reference = x509.NoticeReference(\n            organization, notice_numbers\n        )\n\n    return x509.UserNotice(notice_reference, explicit_text)\n\n\ndef _decode_basic_constraints(backend, bc_st):\n    basic_constraints = backend._ffi.cast(\"BASIC_CONSTRAINTS *\", bc_st)\n    basic_constraints = backend._ffi.gc(\n        basic_constraints, backend._lib.BASIC_CONSTRAINTS_free\n    )\n    # The byte representation of an ASN.1 boolean true is \\xff. OpenSSL\n    # chooses to just map this to its ordinal value, so true is 255 and\n    # false is 0.\n    ca = basic_constraints.ca == 255\n    path_length = _asn1_integer_to_int_or_none(\n        backend, basic_constraints.pathlen\n    )\n\n    return x509.BasicConstraints(ca, path_length)\n\n\ndef _decode_subject_key_identifier(backend, asn1_string):\n    asn1_string = backend._ffi.cast(\"ASN1_OCTET_STRING *\", asn1_string)\n    asn1_string = backend._ffi.gc(\n        asn1_string, backend._lib.ASN1_OCTET_STRING_free\n    )\n    return x509.SubjectKeyIdentifier(\n        backend._ffi.buffer(asn1_string.data, asn1_string.length)[:]\n    )\n\n\ndef _decode_authority_key_identifier(backend, akid):\n    akid = backend._ffi.cast(\"AUTHORITY_KEYID *\", akid)\n    akid = backend._ffi.gc(akid, backend._lib.AUTHORITY_KEYID_free)\n    key_identifier = None\n    authority_cert_issuer = None\n\n    if akid.keyid != backend._ffi.NULL:\n        key_identifier = backend._ffi.buffer(\n            akid.keyid.data, akid.keyid.length\n        )[:]\n\n    if akid.issuer != backend._ffi.NULL:\n        authority_cert_issuer = _decode_general_names(\n            backend, akid.issuer\n        )\n\n    authority_cert_serial_number = _asn1_integer_to_int_or_none(\n        backend, akid.serial\n    )\n\n    return x509.AuthorityKeyIdentifier(\n        key_identifier, authority_cert_issuer, authority_cert_serial_number\n    )\n\n\ndef _decode_authority_information_access(backend, aia):\n    aia = backend._ffi.cast(\"Cryptography_STACK_OF_ACCESS_DESCRIPTION *\", aia)\n    aia = backend._ffi.gc(\n        aia,\n        lambda x: backend._lib.sk_ACCESS_DESCRIPTION_pop_free(\n            x, backend._ffi.addressof(\n                backend._lib._original_lib, \"ACCESS_DESCRIPTION_free\"\n            )\n        )\n    )\n    num = backend._lib.sk_ACCESS_DESCRIPTION_num(aia)\n    access_descriptions = []\n    for i in range(num):\n        ad = backend._lib.sk_ACCESS_DESCRIPTION_value(aia, i)\n        backend.openssl_assert(ad.method != backend._ffi.NULL)\n        oid = x509.ObjectIdentifier(_obj2txt(backend, ad.method))\n        backend.openssl_assert(ad.location != backend._ffi.NULL)\n        gn = _decode_general_name(backend, ad.location)\n        access_descriptions.append(x509.AccessDescription(oid, gn))\n\n    return x509.AuthorityInformationAccess(access_descriptions)\n\n\ndef _decode_key_usage(backend, bit_string):\n    bit_string = backend._ffi.cast(\"ASN1_BIT_STRING *\", bit_string)\n    bit_string = backend._ffi.gc(bit_string, backend._lib.ASN1_BIT_STRING_free)\n    get_bit = backend._lib.ASN1_BIT_STRING_get_bit\n    digital_signature = get_bit(bit_string, 0) == 1\n    content_commitment = get_bit(bit_string, 1) == 1\n    key_encipherment = get_bit(bit_string, 2) == 1\n    data_encipherment = get_bit(bit_string, 3) == 1\n    key_agreement = get_bit(bit_string, 4) == 1\n    key_cert_sign = get_bit(bit_string, 5) == 1\n    crl_sign = get_bit(bit_string, 6) == 1\n    encipher_only = get_bit(bit_string, 7) == 1\n    decipher_only = get_bit(bit_string, 8) == 1\n    return x509.KeyUsage(\n        digital_signature,\n        content_commitment,\n        key_encipherment,\n        data_encipherment,\n        key_agreement,\n        key_cert_sign,\n        crl_sign,\n        encipher_only,\n        decipher_only\n    )\n\n\ndef _decode_general_names_extension(backend, gns):\n    gns = backend._ffi.cast(\"GENERAL_NAMES *\", gns)\n    gns = backend._ffi.gc(gns, backend._lib.GENERAL_NAMES_free)\n    general_names = _decode_general_names(backend, gns)\n    return general_names\n\n\ndef _decode_subject_alt_name(backend, ext):\n    return x509.SubjectAlternativeName(\n        _decode_general_names_extension(backend, ext)\n    )\n\n\ndef _decode_issuer_alt_name(backend, ext):\n    return x509.IssuerAlternativeName(\n        _decode_general_names_extension(backend, ext)\n    )\n\n\ndef _decode_name_constraints(backend, nc):\n    nc = backend._ffi.cast(\"NAME_CONSTRAINTS *\", nc)\n    nc = backend._ffi.gc(nc, backend._lib.NAME_CONSTRAINTS_free)\n    permitted = _decode_general_subtrees(backend, nc.permittedSubtrees)\n    excluded = _decode_general_subtrees(backend, nc.excludedSubtrees)\n    return x509.NameConstraints(\n        permitted_subtrees=permitted, excluded_subtrees=excluded\n    )\n\n\ndef _decode_general_subtrees(backend, stack_subtrees):\n    if stack_subtrees == backend._ffi.NULL:\n        return None\n\n    num = backend._lib.sk_GENERAL_SUBTREE_num(stack_subtrees)\n    subtrees = []\n\n    for i in range(num):\n        obj = backend._lib.sk_GENERAL_SUBTREE_value(stack_subtrees, i)\n        backend.openssl_assert(obj != backend._ffi.NULL)\n        name = _decode_general_name(backend, obj.base)\n        subtrees.append(name)\n\n    return subtrees\n\n\ndef _decode_issuing_dist_point(backend, idp):\n    idp = backend._ffi.cast(\"ISSUING_DIST_POINT *\", idp)\n    idp = backend._ffi.gc(idp, backend._lib.ISSUING_DIST_POINT_free)\n    if idp.distpoint != backend._ffi.NULL:\n        full_name, relative_name = _decode_distpoint(backend, idp.distpoint)\n    else:\n        full_name = None\n        relative_name = None\n\n    only_user = idp.onlyuser == 255\n    only_ca = idp.onlyCA == 255\n    indirect_crl = idp.indirectCRL == 255\n    only_attr = idp.onlyattr == 255\n    if idp.onlysomereasons != backend._ffi.NULL:\n        only_some_reasons = _decode_reasons(backend, idp.onlysomereasons)\n    else:\n        only_some_reasons = None\n\n    return x509.IssuingDistributionPoint(\n        full_name, relative_name, only_user, only_ca, only_some_reasons,\n        indirect_crl, only_attr\n    )\n\n\ndef _decode_policy_constraints(backend, pc):\n    pc = backend._ffi.cast(\"POLICY_CONSTRAINTS *\", pc)\n    pc = backend._ffi.gc(pc, backend._lib.POLICY_CONSTRAINTS_free)\n\n    require_explicit_policy = _asn1_integer_to_int_or_none(\n        backend, pc.requireExplicitPolicy\n    )\n    inhibit_policy_mapping = _asn1_integer_to_int_or_none(\n        backend, pc.inhibitPolicyMapping\n    )\n\n    return x509.PolicyConstraints(\n        require_explicit_policy, inhibit_policy_mapping\n    )\n\n\ndef _decode_extended_key_usage(backend, sk):\n    sk = backend._ffi.cast(\"Cryptography_STACK_OF_ASN1_OBJECT *\", sk)\n    sk = backend._ffi.gc(sk, backend._lib.sk_ASN1_OBJECT_free)\n    num = backend._lib.sk_ASN1_OBJECT_num(sk)\n    ekus = []\n\n    for i in range(num):\n        obj = backend._lib.sk_ASN1_OBJECT_value(sk, i)\n        backend.openssl_assert(obj != backend._ffi.NULL)\n        oid = x509.ObjectIdentifier(_obj2txt(backend, obj))\n        ekus.append(oid)\n\n    return x509.ExtendedKeyUsage(ekus)\n\n\n_DISTPOINT_TYPE_FULLNAME = 0\n_DISTPOINT_TYPE_RELATIVENAME = 1\n\n\ndef _decode_dist_points(backend, cdps):\n    cdps = backend._ffi.cast(\"Cryptography_STACK_OF_DIST_POINT *\", cdps)\n    cdps = backend._ffi.gc(cdps, backend._lib.CRL_DIST_POINTS_free)\n\n    num = backend._lib.sk_DIST_POINT_num(cdps)\n    dist_points = []\n    for i in range(num):\n        full_name = None\n        relative_name = None\n        crl_issuer = None\n        reasons = None\n        cdp = backend._lib.sk_DIST_POINT_value(cdps, i)\n        if cdp.reasons != backend._ffi.NULL:\n            reasons = _decode_reasons(backend, cdp.reasons)\n\n        if cdp.CRLissuer != backend._ffi.NULL:\n            crl_issuer = _decode_general_names(backend, cdp.CRLissuer)\n\n        # Certificates may have a crl_issuer/reasons and no distribution\n        # point so make sure it's not null.\n        if cdp.distpoint != backend._ffi.NULL:\n            full_name, relative_name = _decode_distpoint(\n                backend, cdp.distpoint\n            )\n\n        dist_points.append(\n            x509.DistributionPoint(\n                full_name, relative_name, reasons, crl_issuer\n            )\n        )\n\n    return dist_points\n\n\n# ReasonFlags ::= BIT STRING {\n#      unused                  (0),\n#      keyCompromise           (1),\n#      cACompromise            (2),\n#      affiliationChanged      (3),\n#      superseded              (4),\n#      cessationOfOperation    (5),\n#      certificateHold         (6),\n#      privilegeWithdrawn      (7),\n#      aACompromise            (8) }\n_REASON_BIT_MAPPING = {\n    1: x509.ReasonFlags.key_compromise,\n    2: x509.ReasonFlags.ca_compromise,\n    3: x509.ReasonFlags.affiliation_changed,\n    4: x509.ReasonFlags.superseded,\n    5: x509.ReasonFlags.cessation_of_operation,\n    6: x509.ReasonFlags.certificate_hold,\n    7: x509.ReasonFlags.privilege_withdrawn,\n    8: x509.ReasonFlags.aa_compromise,\n}\n\n\ndef _decode_reasons(backend, reasons):\n    # We will check each bit from RFC 5280\n    enum_reasons = []\n    for bit_position, reason in six.iteritems(_REASON_BIT_MAPPING):\n        if backend._lib.ASN1_BIT_STRING_get_bit(reasons, bit_position):\n            enum_reasons.append(reason)\n\n    return frozenset(enum_reasons)\n\n\ndef _decode_distpoint(backend, distpoint):\n    if distpoint.type == _DISTPOINT_TYPE_FULLNAME:\n        full_name = _decode_general_names(backend, distpoint.name.fullname)\n        return full_name, None\n\n    # OpenSSL code doesn't test for a specific type for\n    # relativename, everything that isn't fullname is considered\n    # relativename.  Per RFC 5280:\n    #\n    # DistributionPointName ::= CHOICE {\n    #      fullName                [0]      GeneralNames,\n    #      nameRelativeToCRLIssuer [1]      RelativeDistinguishedName }\n    rns = distpoint.name.relativename\n    rnum = backend._lib.sk_X509_NAME_ENTRY_num(rns)\n    attributes = set()\n    for i in range(rnum):\n        rn = backend._lib.sk_X509_NAME_ENTRY_value(\n            rns, i\n        )\n        backend.openssl_assert(rn != backend._ffi.NULL)\n        attributes.add(\n            _decode_x509_name_entry(backend, rn)\n        )\n\n    relative_name = x509.RelativeDistinguishedName(attributes)\n\n    return None, relative_name\n\n\ndef _decode_crl_distribution_points(backend, cdps):\n    dist_points = _decode_dist_points(backend, cdps)\n    return x509.CRLDistributionPoints(dist_points)\n\n\ndef _decode_freshest_crl(backend, cdps):\n    dist_points = _decode_dist_points(backend, cdps)\n    return x509.FreshestCRL(dist_points)\n\n\ndef _decode_inhibit_any_policy(backend, asn1_int):\n    asn1_int = backend._ffi.cast(\"ASN1_INTEGER *\", asn1_int)\n    asn1_int = backend._ffi.gc(asn1_int, backend._lib.ASN1_INTEGER_free)\n    skip_certs = _asn1_integer_to_int(backend, asn1_int)\n    return x509.InhibitAnyPolicy(skip_certs)\n\n\ndef _decode_precert_signed_certificate_timestamps(backend, asn1_scts):\n    from cryptography.hazmat.backends.openssl.x509 import (\n        _SignedCertificateTimestamp\n    )\n    asn1_scts = backend._ffi.cast(\"Cryptography_STACK_OF_SCT *\", asn1_scts)\n    asn1_scts = backend._ffi.gc(asn1_scts, backend._lib.SCT_LIST_free)\n\n    scts = []\n    for i in range(backend._lib.sk_SCT_num(asn1_scts)):\n        sct = backend._lib.sk_SCT_value(asn1_scts, i)\n\n        scts.append(_SignedCertificateTimestamp(backend, asn1_scts, sct))\n    return x509.PrecertificateSignedCertificateTimestamps(scts)\n\n\n#    CRLReason ::= ENUMERATED {\n#        unspecified             (0),\n#        keyCompromise           (1),\n#        cACompromise            (2),\n#        affiliationChanged      (3),\n#        superseded              (4),\n#        cessationOfOperation    (5),\n#        certificateHold         (6),\n#             -- value 7 is not used\n#        removeFromCRL           (8),\n#        privilegeWithdrawn      (9),\n#        aACompromise           (10) }\n_CRL_ENTRY_REASON_CODE_TO_ENUM = {\n    0: x509.ReasonFlags.unspecified,\n    1: x509.ReasonFlags.key_compromise,\n    2: x509.ReasonFlags.ca_compromise,\n    3: x509.ReasonFlags.affiliation_changed,\n    4: x509.ReasonFlags.superseded,\n    5: x509.ReasonFlags.cessation_of_operation,\n    6: x509.ReasonFlags.certificate_hold,\n    8: x509.ReasonFlags.remove_from_crl,\n    9: x509.ReasonFlags.privilege_withdrawn,\n    10: x509.ReasonFlags.aa_compromise,\n}\n\n\n_CRL_ENTRY_REASON_ENUM_TO_CODE = {\n    x509.ReasonFlags.unspecified: 0,\n    x509.ReasonFlags.key_compromise: 1,\n    x509.ReasonFlags.ca_compromise: 2,\n    x509.ReasonFlags.affiliation_changed: 3,\n    x509.ReasonFlags.superseded: 4,\n    x509.ReasonFlags.cessation_of_operation: 5,\n    x509.ReasonFlags.certificate_hold: 6,\n    x509.ReasonFlags.remove_from_crl: 8,\n    x509.ReasonFlags.privilege_withdrawn: 9,\n    x509.ReasonFlags.aa_compromise: 10\n}\n\n\ndef _decode_crl_reason(backend, enum):\n    enum = backend._ffi.cast(\"ASN1_ENUMERATED *\", enum)\n    enum = backend._ffi.gc(enum, backend._lib.ASN1_ENUMERATED_free)\n    code = backend._lib.ASN1_ENUMERATED_get(enum)\n\n    try:\n        return x509.CRLReason(_CRL_ENTRY_REASON_CODE_TO_ENUM[code])\n    except KeyError:\n        raise ValueError(\"Unsupported reason code: {}\".format(code))\n\n\ndef _decode_invalidity_date(backend, inv_date):\n    generalized_time = backend._ffi.cast(\n        \"ASN1_GENERALIZEDTIME *\", inv_date\n    )\n    generalized_time = backend._ffi.gc(\n        generalized_time, backend._lib.ASN1_GENERALIZEDTIME_free\n    )\n    return x509.InvalidityDate(\n        _parse_asn1_generalized_time(backend, generalized_time)\n    )\n\n\ndef _decode_cert_issuer(backend, gns):\n    gns = backend._ffi.cast(\"GENERAL_NAMES *\", gns)\n    gns = backend._ffi.gc(gns, backend._lib.GENERAL_NAMES_free)\n    general_names = _decode_general_names(backend, gns)\n    return x509.CertificateIssuer(general_names)\n\n\ndef _asn1_to_der(backend, asn1_type):\n    buf = backend._ffi.new(\"unsigned char **\")\n    res = backend._lib.i2d_ASN1_TYPE(asn1_type, buf)\n    backend.openssl_assert(res >= 0)\n    backend.openssl_assert(buf[0] != backend._ffi.NULL)\n    buf = backend._ffi.gc(\n        buf, lambda buffer: backend._lib.OPENSSL_free(buffer[0])\n    )\n    return backend._ffi.buffer(buf[0], res)[:]\n\n\ndef _asn1_integer_to_int(backend, asn1_int):\n    bn = backend._lib.ASN1_INTEGER_to_BN(asn1_int, backend._ffi.NULL)\n    backend.openssl_assert(bn != backend._ffi.NULL)\n    bn = backend._ffi.gc(bn, backend._lib.BN_free)\n    return backend._bn_to_int(bn)\n\n\ndef _asn1_integer_to_int_or_none(backend, asn1_int):\n    if asn1_int == backend._ffi.NULL:\n        return None\n    else:\n        return _asn1_integer_to_int(backend, asn1_int)\n\n\ndef _asn1_string_to_bytes(backend, asn1_string):\n    return backend._ffi.buffer(asn1_string.data, asn1_string.length)[:]\n\n\ndef _asn1_string_to_ascii(backend, asn1_string):\n    return _asn1_string_to_bytes(backend, asn1_string).decode(\"ascii\")\n\n\ndef _asn1_string_to_utf8(backend, asn1_string):\n    buf = backend._ffi.new(\"unsigned char **\")\n    res = backend._lib.ASN1_STRING_to_UTF8(buf, asn1_string)\n    if res == -1:\n        raise ValueError(\n            \"Unsupported ASN1 string type. Type: {}\".format(asn1_string.type)\n        )\n\n    backend.openssl_assert(buf[0] != backend._ffi.NULL)\n    buf = backend._ffi.gc(\n        buf, lambda buffer: backend._lib.OPENSSL_free(buffer[0])\n    )\n    return backend._ffi.buffer(buf[0], res)[:].decode('utf8')\n\n\ndef _parse_asn1_time(backend, asn1_time):\n    backend.openssl_assert(asn1_time != backend._ffi.NULL)\n    generalized_time = backend._lib.ASN1_TIME_to_generalizedtime(\n        asn1_time, backend._ffi.NULL\n    )\n    if generalized_time == backend._ffi.NULL:\n        raise ValueError(\n            \"Couldn't parse ASN.1 time as generalizedtime {!r}\".format(\n                _asn1_string_to_bytes(backend, asn1_time)\n            )\n        )\n\n    generalized_time = backend._ffi.gc(\n        generalized_time, backend._lib.ASN1_GENERALIZEDTIME_free\n    )\n    return _parse_asn1_generalized_time(backend, generalized_time)\n\n\ndef _parse_asn1_generalized_time(backend, generalized_time):\n    time = _asn1_string_to_ascii(\n        backend, backend._ffi.cast(\"ASN1_STRING *\", generalized_time)\n    )\n    return datetime.datetime.strptime(time, \"%Y%m%d%H%M%SZ\")\n\n\ndef _decode_nonce(backend, nonce):\n    nonce = backend._ffi.cast(\"ASN1_OCTET_STRING *\", nonce)\n    nonce = backend._ffi.gc(nonce, backend._lib.ASN1_OCTET_STRING_free)\n    return x509.OCSPNonce(_asn1_string_to_bytes(backend, nonce))\n\n\n_EXTENSION_HANDLERS_NO_SCT = {\n    ExtensionOID.BASIC_CONSTRAINTS: _decode_basic_constraints,\n    ExtensionOID.SUBJECT_KEY_IDENTIFIER: _decode_subject_key_identifier,\n    ExtensionOID.KEY_USAGE: _decode_key_usage,\n    ExtensionOID.SUBJECT_ALTERNATIVE_NAME: _decode_subject_alt_name,\n    ExtensionOID.EXTENDED_KEY_USAGE: _decode_extended_key_usage,\n    ExtensionOID.AUTHORITY_KEY_IDENTIFIER: _decode_authority_key_identifier,\n    ExtensionOID.AUTHORITY_INFORMATION_ACCESS: (\n        _decode_authority_information_access\n    ),\n    ExtensionOID.CERTIFICATE_POLICIES: _decode_certificate_policies,\n    ExtensionOID.CRL_DISTRIBUTION_POINTS: _decode_crl_distribution_points,\n    ExtensionOID.FRESHEST_CRL: _decode_freshest_crl,\n    ExtensionOID.OCSP_NO_CHECK: _decode_ocsp_no_check,\n    ExtensionOID.INHIBIT_ANY_POLICY: _decode_inhibit_any_policy,\n    ExtensionOID.ISSUER_ALTERNATIVE_NAME: _decode_issuer_alt_name,\n    ExtensionOID.NAME_CONSTRAINTS: _decode_name_constraints,\n    ExtensionOID.POLICY_CONSTRAINTS: _decode_policy_constraints,\n}\n_EXTENSION_HANDLERS = _EXTENSION_HANDLERS_NO_SCT.copy()\n_EXTENSION_HANDLERS[\n    ExtensionOID.PRECERT_SIGNED_CERTIFICATE_TIMESTAMPS\n] = _decode_precert_signed_certificate_timestamps\n\n\n_REVOKED_EXTENSION_HANDLERS = {\n    CRLEntryExtensionOID.CRL_REASON: _decode_crl_reason,\n    CRLEntryExtensionOID.INVALIDITY_DATE: _decode_invalidity_date,\n    CRLEntryExtensionOID.CERTIFICATE_ISSUER: _decode_cert_issuer,\n}\n\n_CRL_EXTENSION_HANDLERS = {\n    ExtensionOID.CRL_NUMBER: _decode_crl_number,\n    ExtensionOID.DELTA_CRL_INDICATOR: _decode_delta_crl_indicator,\n    ExtensionOID.AUTHORITY_KEY_IDENTIFIER: _decode_authority_key_identifier,\n    ExtensionOID.ISSUER_ALTERNATIVE_NAME: _decode_issuer_alt_name,\n    ExtensionOID.AUTHORITY_INFORMATION_ACCESS: (\n        _decode_authority_information_access\n    ),\n    ExtensionOID.ISSUING_DISTRIBUTION_POINT: _decode_issuing_dist_point,\n    ExtensionOID.FRESHEST_CRL: _decode_freshest_crl,\n}\n\n_OCSP_REQ_EXTENSION_HANDLERS = {\n    OCSPExtensionOID.NONCE: _decode_nonce,\n}\n\n_OCSP_BASICRESP_EXTENSION_HANDLERS = {\n    OCSPExtensionOID.NONCE: _decode_nonce,\n}\n\n_CERTIFICATE_EXTENSION_PARSER_NO_SCT = _X509ExtensionParser(\n    ext_count=lambda backend, x: backend._lib.X509_get_ext_count(x),\n    get_ext=lambda backend, x, i: backend._lib.X509_get_ext(x, i),\n    handlers=_EXTENSION_HANDLERS_NO_SCT\n)\n\n_CERTIFICATE_EXTENSION_PARSER = _X509ExtensionParser(\n    ext_count=lambda backend, x: backend._lib.X509_get_ext_count(x),\n    get_ext=lambda backend, x, i: backend._lib.X509_get_ext(x, i),\n    handlers=_EXTENSION_HANDLERS\n)\n\n_CSR_EXTENSION_PARSER = _X509ExtensionParser(\n    ext_count=lambda backend, x: backend._lib.sk_X509_EXTENSION_num(x),\n    get_ext=lambda backend, x, i: backend._lib.sk_X509_EXTENSION_value(x, i),\n    handlers=_EXTENSION_HANDLERS\n)\n\n_REVOKED_CERTIFICATE_EXTENSION_PARSER = _X509ExtensionParser(\n    ext_count=lambda backend, x: backend._lib.X509_REVOKED_get_ext_count(x),\n    get_ext=lambda backend, x, i: backend._lib.X509_REVOKED_get_ext(x, i),\n    handlers=_REVOKED_EXTENSION_HANDLERS,\n)\n\n_CRL_EXTENSION_PARSER = _X509ExtensionParser(\n    ext_count=lambda backend, x: backend._lib.X509_CRL_get_ext_count(x),\n    get_ext=lambda backend, x, i: backend._lib.X509_CRL_get_ext(x, i),\n    handlers=_CRL_EXTENSION_HANDLERS,\n)\n\n_OCSP_REQ_EXT_PARSER = _X509ExtensionParser(\n    ext_count=lambda backend, x: backend._lib.OCSP_REQUEST_get_ext_count(x),\n    get_ext=lambda backend, x, i: backend._lib.OCSP_REQUEST_get_ext(x, i),\n    handlers=_OCSP_REQ_EXTENSION_HANDLERS,\n)\n\n_OCSP_BASICRESP_EXT_PARSER = _X509ExtensionParser(\n    ext_count=lambda backend, x: backend._lib.OCSP_BASICRESP_get_ext_count(x),\n    get_ext=lambda backend, x, i: backend._lib.OCSP_BASICRESP_get_ext(x, i),\n    handlers=_OCSP_BASICRESP_EXTENSION_HANDLERS,\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/dh.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import utils\nfrom cryptography.exceptions import UnsupportedAlgorithm, _Reasons\nfrom cryptography.hazmat.primitives import serialization\nfrom cryptography.hazmat.primitives.asymmetric import dh\n\n\ndef _dh_params_dup(dh_cdata, backend):\n    lib = backend._lib\n    ffi = backend._ffi\n\n    param_cdata = lib.DHparams_dup(dh_cdata)\n    backend.openssl_assert(param_cdata != ffi.NULL)\n    param_cdata = ffi.gc(param_cdata, lib.DH_free)\n    if lib.CRYPTOGRAPHY_OPENSSL_LESS_THAN_102:\n        # In OpenSSL versions < 1.0.2 or libressl DHparams_dup don't copy q\n        q = ffi.new(\"BIGNUM **\")\n        lib.DH_get0_pqg(dh_cdata, ffi.NULL, q, ffi.NULL)\n        q_dup = lib.BN_dup(q[0])\n        res = lib.DH_set0_pqg(param_cdata, ffi.NULL, q_dup, ffi.NULL)\n        backend.openssl_assert(res == 1)\n\n    return param_cdata\n\n\ndef _dh_cdata_to_parameters(dh_cdata, backend):\n    param_cdata = _dh_params_dup(dh_cdata, backend)\n    return _DHParameters(backend, param_cdata)\n\n\n@utils.register_interface(dh.DHParametersWithSerialization)\nclass _DHParameters(object):\n    def __init__(self, backend, dh_cdata):\n        self._backend = backend\n        self._dh_cdata = dh_cdata\n\n    def parameter_numbers(self):\n        p = self._backend._ffi.new(\"BIGNUM **\")\n        g = self._backend._ffi.new(\"BIGNUM **\")\n        q = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DH_get0_pqg(self._dh_cdata, p, q, g)\n        self._backend.openssl_assert(p[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(g[0] != self._backend._ffi.NULL)\n        if q[0] == self._backend._ffi.NULL:\n            q_val = None\n        else:\n            q_val = self._backend._bn_to_int(q[0])\n        return dh.DHParameterNumbers(\n            p=self._backend._bn_to_int(p[0]),\n            g=self._backend._bn_to_int(g[0]),\n            q=q_val\n        )\n\n    def generate_private_key(self):\n        return self._backend.generate_dh_private_key(self)\n\n    def parameter_bytes(self, encoding, format):\n        if format is not serialization.ParameterFormat.PKCS3:\n            raise ValueError(\n                \"Only PKCS3 serialization is supported\"\n            )\n        if not self._backend._lib.Cryptography_HAS_EVP_PKEY_DHX:\n            q = self._backend._ffi.new(\"BIGNUM **\")\n            self._backend._lib.DH_get0_pqg(self._dh_cdata,\n                                           self._backend._ffi.NULL,\n                                           q,\n                                           self._backend._ffi.NULL)\n            if q[0] != self._backend._ffi.NULL:\n                raise UnsupportedAlgorithm(\n                    \"DH X9.42 serialization is not supported\",\n                    _Reasons.UNSUPPORTED_SERIALIZATION)\n\n        return self._backend._parameter_bytes(\n            encoding,\n            format,\n            self._dh_cdata\n        )\n\n\ndef _handle_dh_compute_key_error(errors, backend):\n    lib = backend._lib\n\n    backend.openssl_assert(\n        errors[0]._lib_reason_match(\n            lib.ERR_LIB_DH, lib.DH_R_INVALID_PUBKEY\n        )\n    )\n\n    raise ValueError(\"Public key value is invalid for this exchange.\")\n\n\ndef _get_dh_num_bits(backend, dh_cdata):\n    p = backend._ffi.new(\"BIGNUM **\")\n    backend._lib.DH_get0_pqg(dh_cdata, p,\n                             backend._ffi.NULL,\n                             backend._ffi.NULL)\n    backend.openssl_assert(p[0] != backend._ffi.NULL)\n    return backend._lib.BN_num_bits(p[0])\n\n\n@utils.register_interface(dh.DHPrivateKeyWithSerialization)\nclass _DHPrivateKey(object):\n    def __init__(self, backend, dh_cdata, evp_pkey):\n        self._backend = backend\n        self._dh_cdata = dh_cdata\n        self._evp_pkey = evp_pkey\n        self._key_size_bytes = self._backend._lib.DH_size(dh_cdata)\n\n    @property\n    def key_size(self):\n        return _get_dh_num_bits(self._backend, self._dh_cdata)\n\n    def private_numbers(self):\n        p = self._backend._ffi.new(\"BIGNUM **\")\n        g = self._backend._ffi.new(\"BIGNUM **\")\n        q = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DH_get0_pqg(self._dh_cdata, p, q, g)\n        self._backend.openssl_assert(p[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(g[0] != self._backend._ffi.NULL)\n        if q[0] == self._backend._ffi.NULL:\n            q_val = None\n        else:\n            q_val = self._backend._bn_to_int(q[0])\n        pub_key = self._backend._ffi.new(\"BIGNUM **\")\n        priv_key = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DH_get0_key(self._dh_cdata, pub_key, priv_key)\n        self._backend.openssl_assert(pub_key[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(priv_key[0] != self._backend._ffi.NULL)\n        return dh.DHPrivateNumbers(\n            public_numbers=dh.DHPublicNumbers(\n                parameter_numbers=dh.DHParameterNumbers(\n                    p=self._backend._bn_to_int(p[0]),\n                    g=self._backend._bn_to_int(g[0]),\n                    q=q_val\n                ),\n                y=self._backend._bn_to_int(pub_key[0])\n            ),\n            x=self._backend._bn_to_int(priv_key[0])\n        )\n\n    def exchange(self, peer_public_key):\n\n        buf = self._backend._ffi.new(\"unsigned char[]\", self._key_size_bytes)\n        pub_key = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DH_get0_key(peer_public_key._dh_cdata, pub_key,\n                                       self._backend._ffi.NULL)\n        self._backend.openssl_assert(pub_key[0] != self._backend._ffi.NULL)\n        res = self._backend._lib.DH_compute_key(\n            buf,\n            pub_key[0],\n            self._dh_cdata\n        )\n\n        if res == -1:\n            errors = self._backend._consume_errors()\n            return _handle_dh_compute_key_error(errors, self._backend)\n        else:\n            self._backend.openssl_assert(res >= 1)\n\n            key = self._backend._ffi.buffer(buf)[:res]\n            pad = self._key_size_bytes - len(key)\n\n            if pad > 0:\n                key = (b\"\\x00\" * pad) + key\n\n            return key\n\n    def public_key(self):\n        dh_cdata = _dh_params_dup(self._dh_cdata, self._backend)\n        pub_key = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DH_get0_key(self._dh_cdata,\n                                       pub_key, self._backend._ffi.NULL)\n        self._backend.openssl_assert(pub_key[0] != self._backend._ffi.NULL)\n        pub_key_dup = self._backend._lib.BN_dup(pub_key[0])\n        self._backend.openssl_assert(pub_key_dup != self._backend._ffi.NULL)\n\n        res = self._backend._lib.DH_set0_key(dh_cdata,\n                                             pub_key_dup,\n                                             self._backend._ffi.NULL)\n        self._backend.openssl_assert(res == 1)\n        evp_pkey = self._backend._dh_cdata_to_evp_pkey(dh_cdata)\n        return _DHPublicKey(self._backend, dh_cdata, evp_pkey)\n\n    def parameters(self):\n        return _dh_cdata_to_parameters(self._dh_cdata, self._backend)\n\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        if format is not serialization.PrivateFormat.PKCS8:\n            raise ValueError(\n                \"DH private keys support only PKCS8 serialization\"\n            )\n        if not self._backend._lib.Cryptography_HAS_EVP_PKEY_DHX:\n            q = self._backend._ffi.new(\"BIGNUM **\")\n            self._backend._lib.DH_get0_pqg(self._dh_cdata,\n                                           self._backend._ffi.NULL,\n                                           q,\n                                           self._backend._ffi.NULL)\n            if q[0] != self._backend._ffi.NULL:\n                raise UnsupportedAlgorithm(\n                    \"DH X9.42 serialization is not supported\",\n                    _Reasons.UNSUPPORTED_SERIALIZATION)\n\n        return self._backend._private_key_bytes(\n            encoding,\n            format,\n            encryption_algorithm,\n            self._evp_pkey,\n            self._dh_cdata\n        )\n\n\n@utils.register_interface(dh.DHPublicKeyWithSerialization)\nclass _DHPublicKey(object):\n    def __init__(self, backend, dh_cdata, evp_pkey):\n        self._backend = backend\n        self._dh_cdata = dh_cdata\n        self._evp_pkey = evp_pkey\n        self._key_size_bits = _get_dh_num_bits(self._backend, self._dh_cdata)\n\n    @property\n    def key_size(self):\n        return self._key_size_bits\n\n    def public_numbers(self):\n        p = self._backend._ffi.new(\"BIGNUM **\")\n        g = self._backend._ffi.new(\"BIGNUM **\")\n        q = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DH_get0_pqg(self._dh_cdata, p, q, g)\n        self._backend.openssl_assert(p[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(g[0] != self._backend._ffi.NULL)\n        if q[0] == self._backend._ffi.NULL:\n            q_val = None\n        else:\n            q_val = self._backend._bn_to_int(q[0])\n        pub_key = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DH_get0_key(self._dh_cdata,\n                                       pub_key, self._backend._ffi.NULL)\n        self._backend.openssl_assert(pub_key[0] != self._backend._ffi.NULL)\n        return dh.DHPublicNumbers(\n            parameter_numbers=dh.DHParameterNumbers(\n                p=self._backend._bn_to_int(p[0]),\n                g=self._backend._bn_to_int(g[0]),\n                q=q_val\n            ),\n            y=self._backend._bn_to_int(pub_key[0])\n        )\n\n    def parameters(self):\n        return _dh_cdata_to_parameters(self._dh_cdata, self._backend)\n\n    def public_bytes(self, encoding, format):\n        if format is not serialization.PublicFormat.SubjectPublicKeyInfo:\n            raise ValueError(\n                \"DH public keys support only \"\n                \"SubjectPublicKeyInfo serialization\"\n            )\n\n        if not self._backend._lib.Cryptography_HAS_EVP_PKEY_DHX:\n            q = self._backend._ffi.new(\"BIGNUM **\")\n            self._backend._lib.DH_get0_pqg(self._dh_cdata,\n                                           self._backend._ffi.NULL,\n                                           q,\n                                           self._backend._ffi.NULL)\n            if q[0] != self._backend._ffi.NULL:\n                raise UnsupportedAlgorithm(\n                    \"DH X9.42 serialization is not supported\",\n                    _Reasons.UNSUPPORTED_SERIALIZATION)\n\n        return self._backend._public_key_bytes(\n            encoding,\n            format,\n            self,\n            self._evp_pkey,\n            None\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/dsa.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import utils\nfrom cryptography.exceptions import InvalidSignature\nfrom cryptography.hazmat.backends.openssl.utils import (\n    _calculate_digest_and_algorithm, _check_not_prehashed,\n    _warn_sign_verify_deprecated\n)\nfrom cryptography.hazmat.primitives import hashes, serialization\nfrom cryptography.hazmat.primitives.asymmetric import (\n    AsymmetricSignatureContext, AsymmetricVerificationContext, dsa\n)\n\n\ndef _dsa_sig_sign(backend, private_key, data):\n    sig_buf_len = backend._lib.DSA_size(private_key._dsa_cdata)\n    sig_buf = backend._ffi.new(\"unsigned char[]\", sig_buf_len)\n    buflen = backend._ffi.new(\"unsigned int *\")\n\n    # The first parameter passed to DSA_sign is unused by OpenSSL but\n    # must be an integer.\n    res = backend._lib.DSA_sign(\n        0, data, len(data), sig_buf, buflen, private_key._dsa_cdata\n    )\n    backend.openssl_assert(res == 1)\n    backend.openssl_assert(buflen[0])\n\n    return backend._ffi.buffer(sig_buf)[:buflen[0]]\n\n\ndef _dsa_sig_verify(backend, public_key, signature, data):\n    # The first parameter passed to DSA_verify is unused by OpenSSL but\n    # must be an integer.\n    res = backend._lib.DSA_verify(\n        0, data, len(data), signature, len(signature), public_key._dsa_cdata\n    )\n\n    if res != 1:\n        backend._consume_errors()\n        raise InvalidSignature\n\n\n@utils.register_interface(AsymmetricVerificationContext)\nclass _DSAVerificationContext(object):\n    def __init__(self, backend, public_key, signature, algorithm):\n        self._backend = backend\n        self._public_key = public_key\n        self._signature = signature\n        self._algorithm = algorithm\n\n        self._hash_ctx = hashes.Hash(self._algorithm, self._backend)\n\n    def update(self, data):\n        self._hash_ctx.update(data)\n\n    def verify(self):\n        data_to_verify = self._hash_ctx.finalize()\n\n        _dsa_sig_verify(\n            self._backend, self._public_key, self._signature, data_to_verify\n        )\n\n\n@utils.register_interface(AsymmetricSignatureContext)\nclass _DSASignatureContext(object):\n    def __init__(self, backend, private_key, algorithm):\n        self._backend = backend\n        self._private_key = private_key\n        self._algorithm = algorithm\n        self._hash_ctx = hashes.Hash(self._algorithm, self._backend)\n\n    def update(self, data):\n        self._hash_ctx.update(data)\n\n    def finalize(self):\n        data_to_sign = self._hash_ctx.finalize()\n        return _dsa_sig_sign(self._backend, self._private_key, data_to_sign)\n\n\n@utils.register_interface(dsa.DSAParametersWithNumbers)\nclass _DSAParameters(object):\n    def __init__(self, backend, dsa_cdata):\n        self._backend = backend\n        self._dsa_cdata = dsa_cdata\n\n    def parameter_numbers(self):\n        p = self._backend._ffi.new(\"BIGNUM **\")\n        q = self._backend._ffi.new(\"BIGNUM **\")\n        g = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DSA_get0_pqg(self._dsa_cdata, p, q, g)\n        self._backend.openssl_assert(p[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(q[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(g[0] != self._backend._ffi.NULL)\n        return dsa.DSAParameterNumbers(\n            p=self._backend._bn_to_int(p[0]),\n            q=self._backend._bn_to_int(q[0]),\n            g=self._backend._bn_to_int(g[0])\n        )\n\n    def generate_private_key(self):\n        return self._backend.generate_dsa_private_key(self)\n\n\n@utils.register_interface(dsa.DSAPrivateKeyWithSerialization)\nclass _DSAPrivateKey(object):\n    def __init__(self, backend, dsa_cdata, evp_pkey):\n        self._backend = backend\n        self._dsa_cdata = dsa_cdata\n        self._evp_pkey = evp_pkey\n\n        p = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DSA_get0_pqg(\n            dsa_cdata, p, self._backend._ffi.NULL, self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(p[0] != backend._ffi.NULL)\n        self._key_size = self._backend._lib.BN_num_bits(p[0])\n\n    key_size = utils.read_only_property(\"_key_size\")\n\n    def signer(self, signature_algorithm):\n        _warn_sign_verify_deprecated()\n        _check_not_prehashed(signature_algorithm)\n        return _DSASignatureContext(self._backend, self, signature_algorithm)\n\n    def private_numbers(self):\n        p = self._backend._ffi.new(\"BIGNUM **\")\n        q = self._backend._ffi.new(\"BIGNUM **\")\n        g = self._backend._ffi.new(\"BIGNUM **\")\n        pub_key = self._backend._ffi.new(\"BIGNUM **\")\n        priv_key = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DSA_get0_pqg(self._dsa_cdata, p, q, g)\n        self._backend.openssl_assert(p[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(q[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(g[0] != self._backend._ffi.NULL)\n        self._backend._lib.DSA_get0_key(self._dsa_cdata, pub_key, priv_key)\n        self._backend.openssl_assert(pub_key[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(priv_key[0] != self._backend._ffi.NULL)\n        return dsa.DSAPrivateNumbers(\n            public_numbers=dsa.DSAPublicNumbers(\n                parameter_numbers=dsa.DSAParameterNumbers(\n                    p=self._backend._bn_to_int(p[0]),\n                    q=self._backend._bn_to_int(q[0]),\n                    g=self._backend._bn_to_int(g[0])\n                ),\n                y=self._backend._bn_to_int(pub_key[0])\n            ),\n            x=self._backend._bn_to_int(priv_key[0])\n        )\n\n    def public_key(self):\n        dsa_cdata = self._backend._lib.DSAparams_dup(self._dsa_cdata)\n        self._backend.openssl_assert(dsa_cdata != self._backend._ffi.NULL)\n        dsa_cdata = self._backend._ffi.gc(\n            dsa_cdata, self._backend._lib.DSA_free\n        )\n        pub_key = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DSA_get0_key(\n            self._dsa_cdata, pub_key, self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(pub_key[0] != self._backend._ffi.NULL)\n        pub_key_dup = self._backend._lib.BN_dup(pub_key[0])\n        res = self._backend._lib.DSA_set0_key(\n            dsa_cdata, pub_key_dup, self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(res == 1)\n        evp_pkey = self._backend._dsa_cdata_to_evp_pkey(dsa_cdata)\n        return _DSAPublicKey(self._backend, dsa_cdata, evp_pkey)\n\n    def parameters(self):\n        dsa_cdata = self._backend._lib.DSAparams_dup(self._dsa_cdata)\n        self._backend.openssl_assert(dsa_cdata != self._backend._ffi.NULL)\n        dsa_cdata = self._backend._ffi.gc(\n            dsa_cdata, self._backend._lib.DSA_free\n        )\n        return _DSAParameters(self._backend, dsa_cdata)\n\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        return self._backend._private_key_bytes(\n            encoding,\n            format,\n            encryption_algorithm,\n            self._evp_pkey,\n            self._dsa_cdata\n        )\n\n    def sign(self, data, algorithm):\n        data, algorithm = _calculate_digest_and_algorithm(\n            self._backend, data, algorithm\n        )\n        return _dsa_sig_sign(self._backend, self, data)\n\n\n@utils.register_interface(dsa.DSAPublicKeyWithSerialization)\nclass _DSAPublicKey(object):\n    def __init__(self, backend, dsa_cdata, evp_pkey):\n        self._backend = backend\n        self._dsa_cdata = dsa_cdata\n        self._evp_pkey = evp_pkey\n        p = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DSA_get0_pqg(\n            dsa_cdata, p, self._backend._ffi.NULL, self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(p[0] != backend._ffi.NULL)\n        self._key_size = self._backend._lib.BN_num_bits(p[0])\n\n    key_size = utils.read_only_property(\"_key_size\")\n\n    def verifier(self, signature, signature_algorithm):\n        _warn_sign_verify_deprecated()\n        utils._check_bytes(\"signature\", signature)\n\n        _check_not_prehashed(signature_algorithm)\n        return _DSAVerificationContext(\n            self._backend, self, signature, signature_algorithm\n        )\n\n    def public_numbers(self):\n        p = self._backend._ffi.new(\"BIGNUM **\")\n        q = self._backend._ffi.new(\"BIGNUM **\")\n        g = self._backend._ffi.new(\"BIGNUM **\")\n        pub_key = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.DSA_get0_pqg(self._dsa_cdata, p, q, g)\n        self._backend.openssl_assert(p[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(q[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(g[0] != self._backend._ffi.NULL)\n        self._backend._lib.DSA_get0_key(\n            self._dsa_cdata, pub_key, self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(pub_key[0] != self._backend._ffi.NULL)\n        return dsa.DSAPublicNumbers(\n            parameter_numbers=dsa.DSAParameterNumbers(\n                p=self._backend._bn_to_int(p[0]),\n                q=self._backend._bn_to_int(q[0]),\n                g=self._backend._bn_to_int(g[0])\n            ),\n            y=self._backend._bn_to_int(pub_key[0])\n        )\n\n    def parameters(self):\n        dsa_cdata = self._backend._lib.DSAparams_dup(self._dsa_cdata)\n        dsa_cdata = self._backend._ffi.gc(\n            dsa_cdata, self._backend._lib.DSA_free\n        )\n        return _DSAParameters(self._backend, dsa_cdata)\n\n    def public_bytes(self, encoding, format):\n        if format is serialization.PublicFormat.PKCS1:\n            raise ValueError(\n                \"DSA public keys do not support PKCS1 serialization\"\n            )\n\n        return self._backend._public_key_bytes(\n            encoding,\n            format,\n            self,\n            self._evp_pkey,\n            None\n        )\n\n    def verify(self, signature, data, algorithm):\n        data, algorithm = _calculate_digest_and_algorithm(\n            self._backend, data, algorithm\n        )\n        return _dsa_sig_verify(self._backend, self, signature, data)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/ec.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    InvalidSignature, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.openssl.utils import (\n    _calculate_digest_and_algorithm, _check_not_prehashed,\n    _warn_sign_verify_deprecated\n)\nfrom cryptography.hazmat.primitives import hashes, serialization\nfrom cryptography.hazmat.primitives.asymmetric import (\n    AsymmetricSignatureContext, AsymmetricVerificationContext, ec\n)\n\n\ndef _check_signature_algorithm(signature_algorithm):\n    if not isinstance(signature_algorithm, ec.ECDSA):\n        raise UnsupportedAlgorithm(\n            \"Unsupported elliptic curve signature algorithm.\",\n            _Reasons.UNSUPPORTED_PUBLIC_KEY_ALGORITHM)\n\n\ndef _ec_key_curve_sn(backend, ec_key):\n    group = backend._lib.EC_KEY_get0_group(ec_key)\n    backend.openssl_assert(group != backend._ffi.NULL)\n\n    nid = backend._lib.EC_GROUP_get_curve_name(group)\n    # The following check is to find EC keys with unnamed curves and raise\n    # an error for now.\n    if nid == backend._lib.NID_undef:\n        raise NotImplementedError(\n            \"ECDSA keys with unnamed curves are unsupported \"\n            \"at this time\"\n        )\n\n    # This is like the above check, but it also catches the case where you\n    # explicitly encoded a curve with the same parameters as a named curve.\n    # Don't do that.\n    if (\n        backend._lib.CRYPTOGRAPHY_OPENSSL_110_OR_GREATER and\n        backend._lib.EC_GROUP_get_asn1_flag(group) == 0\n    ):\n        raise NotImplementedError(\n            \"ECDSA keys with unnamed curves are unsupported \"\n            \"at this time\"\n        )\n\n    curve_name = backend._lib.OBJ_nid2sn(nid)\n    backend.openssl_assert(curve_name != backend._ffi.NULL)\n\n    sn = backend._ffi.string(curve_name).decode('ascii')\n    return sn\n\n\ndef _mark_asn1_named_ec_curve(backend, ec_cdata):\n    \"\"\"\n    Set the named curve flag on the EC_KEY. This causes OpenSSL to\n    serialize EC keys along with their curve OID which makes\n    deserialization easier.\n    \"\"\"\n\n    backend._lib.EC_KEY_set_asn1_flag(\n        ec_cdata, backend._lib.OPENSSL_EC_NAMED_CURVE\n    )\n\n\ndef _sn_to_elliptic_curve(backend, sn):\n    try:\n        return ec._CURVE_TYPES[sn]()\n    except KeyError:\n        raise UnsupportedAlgorithm(\n            \"{} is not a supported elliptic curve\".format(sn),\n            _Reasons.UNSUPPORTED_ELLIPTIC_CURVE\n        )\n\n\ndef _ecdsa_sig_sign(backend, private_key, data):\n    max_size = backend._lib.ECDSA_size(private_key._ec_key)\n    backend.openssl_assert(max_size > 0)\n\n    sigbuf = backend._ffi.new(\"unsigned char[]\", max_size)\n    siglen_ptr = backend._ffi.new(\"unsigned int[]\", 1)\n    res = backend._lib.ECDSA_sign(\n        0, data, len(data), sigbuf, siglen_ptr, private_key._ec_key\n    )\n    backend.openssl_assert(res == 1)\n    return backend._ffi.buffer(sigbuf)[:siglen_ptr[0]]\n\n\ndef _ecdsa_sig_verify(backend, public_key, signature, data):\n    res = backend._lib.ECDSA_verify(\n        0, data, len(data), signature, len(signature), public_key._ec_key\n    )\n    if res != 1:\n        backend._consume_errors()\n        raise InvalidSignature\n\n\n@utils.register_interface(AsymmetricSignatureContext)\nclass _ECDSASignatureContext(object):\n    def __init__(self, backend, private_key, algorithm):\n        self._backend = backend\n        self._private_key = private_key\n        self._digest = hashes.Hash(algorithm, backend)\n\n    def update(self, data):\n        self._digest.update(data)\n\n    def finalize(self):\n        digest = self._digest.finalize()\n\n        return _ecdsa_sig_sign(self._backend, self._private_key, digest)\n\n\n@utils.register_interface(AsymmetricVerificationContext)\nclass _ECDSAVerificationContext(object):\n    def __init__(self, backend, public_key, signature, algorithm):\n        self._backend = backend\n        self._public_key = public_key\n        self._signature = signature\n        self._digest = hashes.Hash(algorithm, backend)\n\n    def update(self, data):\n        self._digest.update(data)\n\n    def verify(self):\n        digest = self._digest.finalize()\n        _ecdsa_sig_verify(\n            self._backend, self._public_key, self._signature, digest\n        )\n\n\n@utils.register_interface(ec.EllipticCurvePrivateKeyWithSerialization)\nclass _EllipticCurvePrivateKey(object):\n    def __init__(self, backend, ec_key_cdata, evp_pkey):\n        self._backend = backend\n        self._ec_key = ec_key_cdata\n        self._evp_pkey = evp_pkey\n\n        sn = _ec_key_curve_sn(backend, ec_key_cdata)\n        self._curve = _sn_to_elliptic_curve(backend, sn)\n        _mark_asn1_named_ec_curve(backend, ec_key_cdata)\n\n    curve = utils.read_only_property(\"_curve\")\n\n    @property\n    def key_size(self):\n        return self.curve.key_size\n\n    def signer(self, signature_algorithm):\n        _warn_sign_verify_deprecated()\n        _check_signature_algorithm(signature_algorithm)\n        _check_not_prehashed(signature_algorithm.algorithm)\n        return _ECDSASignatureContext(\n            self._backend, self, signature_algorithm.algorithm\n        )\n\n    def exchange(self, algorithm, peer_public_key):\n        if not (\n            self._backend.elliptic_curve_exchange_algorithm_supported(\n                algorithm, self.curve\n            )\n        ):\n            raise UnsupportedAlgorithm(\n                \"This backend does not support the ECDH algorithm.\",\n                _Reasons.UNSUPPORTED_EXCHANGE_ALGORITHM\n            )\n\n        if peer_public_key.curve.name != self.curve.name:\n            raise ValueError(\n                \"peer_public_key and self are not on the same curve\"\n            )\n\n        group = self._backend._lib.EC_KEY_get0_group(self._ec_key)\n        z_len = (self._backend._lib.EC_GROUP_get_degree(group) + 7) // 8\n        self._backend.openssl_assert(z_len > 0)\n        z_buf = self._backend._ffi.new(\"uint8_t[]\", z_len)\n        peer_key = self._backend._lib.EC_KEY_get0_public_key(\n            peer_public_key._ec_key\n        )\n\n        r = self._backend._lib.ECDH_compute_key(\n            z_buf, z_len, peer_key, self._ec_key, self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(r > 0)\n        return self._backend._ffi.buffer(z_buf)[:z_len]\n\n    def public_key(self):\n        group = self._backend._lib.EC_KEY_get0_group(self._ec_key)\n        self._backend.openssl_assert(group != self._backend._ffi.NULL)\n\n        curve_nid = self._backend._lib.EC_GROUP_get_curve_name(group)\n\n        public_ec_key = self._backend._lib.EC_KEY_new_by_curve_name(curve_nid)\n        self._backend.openssl_assert(public_ec_key != self._backend._ffi.NULL)\n        public_ec_key = self._backend._ffi.gc(\n            public_ec_key, self._backend._lib.EC_KEY_free\n        )\n\n        point = self._backend._lib.EC_KEY_get0_public_key(self._ec_key)\n        self._backend.openssl_assert(point != self._backend._ffi.NULL)\n\n        res = self._backend._lib.EC_KEY_set_public_key(public_ec_key, point)\n        self._backend.openssl_assert(res == 1)\n\n        evp_pkey = self._backend._ec_cdata_to_evp_pkey(public_ec_key)\n\n        return _EllipticCurvePublicKey(self._backend, public_ec_key, evp_pkey)\n\n    def private_numbers(self):\n        bn = self._backend._lib.EC_KEY_get0_private_key(self._ec_key)\n        private_value = self._backend._bn_to_int(bn)\n        return ec.EllipticCurvePrivateNumbers(\n            private_value=private_value,\n            public_numbers=self.public_key().public_numbers()\n        )\n\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        return self._backend._private_key_bytes(\n            encoding,\n            format,\n            encryption_algorithm,\n            self._evp_pkey,\n            self._ec_key\n        )\n\n    def sign(self, data, signature_algorithm):\n        _check_signature_algorithm(signature_algorithm)\n        data, algorithm = _calculate_digest_and_algorithm(\n            self._backend, data, signature_algorithm._algorithm\n        )\n        return _ecdsa_sig_sign(self._backend, self, data)\n\n\n@utils.register_interface(ec.EllipticCurvePublicKeyWithSerialization)\nclass _EllipticCurvePublicKey(object):\n    def __init__(self, backend, ec_key_cdata, evp_pkey):\n        self._backend = backend\n        self._ec_key = ec_key_cdata\n        self._evp_pkey = evp_pkey\n\n        sn = _ec_key_curve_sn(backend, ec_key_cdata)\n        self._curve = _sn_to_elliptic_curve(backend, sn)\n        _mark_asn1_named_ec_curve(backend, ec_key_cdata)\n\n    curve = utils.read_only_property(\"_curve\")\n\n    @property\n    def key_size(self):\n        return self.curve.key_size\n\n    def verifier(self, signature, signature_algorithm):\n        _warn_sign_verify_deprecated()\n        utils._check_bytes(\"signature\", signature)\n\n        _check_signature_algorithm(signature_algorithm)\n        _check_not_prehashed(signature_algorithm.algorithm)\n        return _ECDSAVerificationContext(\n            self._backend, self, signature, signature_algorithm.algorithm\n        )\n\n    def public_numbers(self):\n        get_func, group = (\n            self._backend._ec_key_determine_group_get_func(self._ec_key)\n        )\n        point = self._backend._lib.EC_KEY_get0_public_key(self._ec_key)\n        self._backend.openssl_assert(point != self._backend._ffi.NULL)\n\n        with self._backend._tmp_bn_ctx() as bn_ctx:\n            bn_x = self._backend._lib.BN_CTX_get(bn_ctx)\n            bn_y = self._backend._lib.BN_CTX_get(bn_ctx)\n\n            res = get_func(group, point, bn_x, bn_y, bn_ctx)\n            self._backend.openssl_assert(res == 1)\n\n            x = self._backend._bn_to_int(bn_x)\n            y = self._backend._bn_to_int(bn_y)\n\n        return ec.EllipticCurvePublicNumbers(\n            x=x,\n            y=y,\n            curve=self._curve\n        )\n\n    def _encode_point(self, format):\n        if format is serialization.PublicFormat.CompressedPoint:\n            conversion = self._backend._lib.POINT_CONVERSION_COMPRESSED\n        else:\n            assert format is serialization.PublicFormat.UncompressedPoint\n            conversion = self._backend._lib.POINT_CONVERSION_UNCOMPRESSED\n\n        group = self._backend._lib.EC_KEY_get0_group(self._ec_key)\n        self._backend.openssl_assert(group != self._backend._ffi.NULL)\n        point = self._backend._lib.EC_KEY_get0_public_key(self._ec_key)\n        self._backend.openssl_assert(point != self._backend._ffi.NULL)\n        with self._backend._tmp_bn_ctx() as bn_ctx:\n            buflen = self._backend._lib.EC_POINT_point2oct(\n                group, point, conversion, self._backend._ffi.NULL, 0, bn_ctx\n            )\n            self._backend.openssl_assert(buflen > 0)\n            buf = self._backend._ffi.new(\"char[]\", buflen)\n            res = self._backend._lib.EC_POINT_point2oct(\n                group, point, conversion, buf, buflen, bn_ctx\n            )\n            self._backend.openssl_assert(buflen == res)\n\n        return self._backend._ffi.buffer(buf)[:]\n\n    def public_bytes(self, encoding, format):\n        if format is serialization.PublicFormat.PKCS1:\n            raise ValueError(\n                \"EC public keys do not support PKCS1 serialization\"\n            )\n\n        if (\n            encoding is serialization.Encoding.X962 or\n            format is serialization.PublicFormat.CompressedPoint or\n            format is serialization.PublicFormat.UncompressedPoint\n        ):\n            if (\n                encoding is not serialization.Encoding.X962 or\n                format not in (\n                    serialization.PublicFormat.CompressedPoint,\n                    serialization.PublicFormat.UncompressedPoint\n                )\n            ):\n                raise ValueError(\n                    \"X962 encoding must be used with CompressedPoint or \"\n                    \"UncompressedPoint format\"\n                )\n\n            return self._encode_point(format)\n        else:\n            return self._backend._public_key_bytes(\n                encoding,\n                format,\n                self,\n                self._evp_pkey,\n                None\n            )\n\n    def verify(self, signature, data, signature_algorithm):\n        _check_signature_algorithm(signature_algorithm)\n        data, algorithm = _calculate_digest_and_algorithm(\n            self._backend, data, signature_algorithm._algorithm\n        )\n        _ecdsa_sig_verify(self._backend, self, signature, data)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/ed25519.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import exceptions, utils\nfrom cryptography.hazmat.primitives import serialization\nfrom cryptography.hazmat.primitives.asymmetric.ed25519 import (\n    Ed25519PrivateKey, Ed25519PublicKey, _ED25519_KEY_SIZE, _ED25519_SIG_SIZE\n)\n\n\n@utils.register_interface(Ed25519PublicKey)\nclass _Ed25519PublicKey(object):\n    def __init__(self, backend, evp_pkey):\n        self._backend = backend\n        self._evp_pkey = evp_pkey\n\n    def public_bytes(self, encoding, format):\n        if (\n            encoding is serialization.Encoding.Raw or\n            format is serialization.PublicFormat.Raw\n        ):\n            if (\n                encoding is not serialization.Encoding.Raw or\n                format is not serialization.PublicFormat.Raw\n            ):\n                raise ValueError(\n                    \"When using Raw both encoding and format must be Raw\"\n                )\n\n            return self._raw_public_bytes()\n\n        if (\n            encoding in serialization._PEM_DER and\n            format is not serialization.PublicFormat.SubjectPublicKeyInfo\n        ):\n            raise ValueError(\n                \"format must be SubjectPublicKeyInfo when encoding is PEM or \"\n                \"DER\"\n            )\n\n        return self._backend._public_key_bytes(\n            encoding, format, self, self._evp_pkey, None\n        )\n\n    def _raw_public_bytes(self):\n        buf = self._backend._ffi.new(\"unsigned char []\", _ED25519_KEY_SIZE)\n        buflen = self._backend._ffi.new(\"size_t *\", _ED25519_KEY_SIZE)\n        res = self._backend._lib.EVP_PKEY_get_raw_public_key(\n            self._evp_pkey, buf, buflen\n        )\n        self._backend.openssl_assert(res == 1)\n        self._backend.openssl_assert(buflen[0] == _ED25519_KEY_SIZE)\n        return self._backend._ffi.buffer(buf, _ED25519_KEY_SIZE)[:]\n\n    def verify(self, signature, data):\n        evp_md_ctx = self._backend._lib.Cryptography_EVP_MD_CTX_new()\n        self._backend.openssl_assert(evp_md_ctx != self._backend._ffi.NULL)\n        evp_md_ctx = self._backend._ffi.gc(\n            evp_md_ctx, self._backend._lib.Cryptography_EVP_MD_CTX_free\n        )\n        res = self._backend._lib.EVP_DigestVerifyInit(\n            evp_md_ctx, self._backend._ffi.NULL, self._backend._ffi.NULL,\n            self._backend._ffi.NULL, self._evp_pkey\n        )\n        self._backend.openssl_assert(res == 1)\n        res = self._backend._lib.EVP_DigestVerify(\n            evp_md_ctx, signature, len(signature), data, len(data)\n        )\n        if res != 1:\n            self._backend._consume_errors()\n            raise exceptions.InvalidSignature\n\n\n@utils.register_interface(Ed25519PrivateKey)\nclass _Ed25519PrivateKey(object):\n    def __init__(self, backend, evp_pkey):\n        self._backend = backend\n        self._evp_pkey = evp_pkey\n\n    def public_key(self):\n        buf = self._backend._ffi.new(\"unsigned char []\", _ED25519_KEY_SIZE)\n        buflen = self._backend._ffi.new(\"size_t *\", _ED25519_KEY_SIZE)\n        res = self._backend._lib.EVP_PKEY_get_raw_public_key(\n            self._evp_pkey, buf, buflen\n        )\n        self._backend.openssl_assert(res == 1)\n        self._backend.openssl_assert(buflen[0] == _ED25519_KEY_SIZE)\n        public_bytes = self._backend._ffi.buffer(buf)[:]\n        return self._backend.ed25519_load_public_bytes(public_bytes)\n\n    def sign(self, data):\n        evp_md_ctx = self._backend._lib.Cryptography_EVP_MD_CTX_new()\n        self._backend.openssl_assert(evp_md_ctx != self._backend._ffi.NULL)\n        evp_md_ctx = self._backend._ffi.gc(\n            evp_md_ctx, self._backend._lib.Cryptography_EVP_MD_CTX_free\n        )\n        res = self._backend._lib.EVP_DigestSignInit(\n            evp_md_ctx, self._backend._ffi.NULL, self._backend._ffi.NULL,\n            self._backend._ffi.NULL, self._evp_pkey\n        )\n        self._backend.openssl_assert(res == 1)\n        buf = self._backend._ffi.new(\"unsigned char[]\", _ED25519_SIG_SIZE)\n        buflen = self._backend._ffi.new(\"size_t *\", len(buf))\n        res = self._backend._lib.EVP_DigestSign(\n            evp_md_ctx, buf, buflen, data, len(data)\n        )\n        self._backend.openssl_assert(res == 1)\n        self._backend.openssl_assert(buflen[0] == _ED25519_SIG_SIZE)\n        return self._backend._ffi.buffer(buf, buflen[0])[:]\n\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        if (\n            encoding is serialization.Encoding.Raw or\n            format is serialization.PublicFormat.Raw\n        ):\n            if (\n                format is not serialization.PrivateFormat.Raw or\n                encoding is not serialization.Encoding.Raw or not\n                isinstance(encryption_algorithm, serialization.NoEncryption)\n            ):\n                raise ValueError(\n                    \"When using Raw both encoding and format must be Raw \"\n                    \"and encryption_algorithm must be NoEncryption()\"\n                )\n\n            return self._raw_private_bytes()\n\n        if (\n            encoding in serialization._PEM_DER and\n            format is not serialization.PrivateFormat.PKCS8\n        ):\n            raise ValueError(\n                \"format must be PKCS8 when encoding is PEM or DER\"\n            )\n\n        return self._backend._private_key_bytes(\n            encoding, format, encryption_algorithm, self._evp_pkey, None\n        )\n\n    def _raw_private_bytes(self):\n        buf = self._backend._ffi.new(\"unsigned char []\", _ED25519_KEY_SIZE)\n        buflen = self._backend._ffi.new(\"size_t *\", _ED25519_KEY_SIZE)\n        res = self._backend._lib.EVP_PKEY_get_raw_private_key(\n            self._evp_pkey, buf, buflen\n        )\n        self._backend.openssl_assert(res == 1)\n        self._backend.openssl_assert(buflen[0] == _ED25519_KEY_SIZE)\n        return self._backend._ffi.buffer(buf, _ED25519_KEY_SIZE)[:]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/ed448.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import exceptions, utils\nfrom cryptography.hazmat.primitives import serialization\nfrom cryptography.hazmat.primitives.asymmetric.ed448 import (\n    Ed448PrivateKey, Ed448PublicKey\n)\n\n_ED448_KEY_SIZE = 57\n_ED448_SIG_SIZE = 114\n\n\n@utils.register_interface(Ed448PublicKey)\nclass _Ed448PublicKey(object):\n    def __init__(self, backend, evp_pkey):\n        self._backend = backend\n        self._evp_pkey = evp_pkey\n\n    def public_bytes(self, encoding, format):\n        if (\n            encoding is serialization.Encoding.Raw or\n            format is serialization.PublicFormat.Raw\n        ):\n            if (\n                encoding is not serialization.Encoding.Raw or\n                format is not serialization.PublicFormat.Raw\n            ):\n                raise ValueError(\n                    \"When using Raw both encoding and format must be Raw\"\n                )\n\n            return self._raw_public_bytes()\n\n        if (\n            encoding in serialization._PEM_DER and\n            format is not serialization.PublicFormat.SubjectPublicKeyInfo\n        ):\n            raise ValueError(\n                \"format must be SubjectPublicKeyInfo when encoding is PEM or \"\n                \"DER\"\n            )\n\n        return self._backend._public_key_bytes(\n            encoding, format, self, self._evp_pkey, None\n        )\n\n    def _raw_public_bytes(self):\n        buf = self._backend._ffi.new(\"unsigned char []\", _ED448_KEY_SIZE)\n        buflen = self._backend._ffi.new(\"size_t *\", _ED448_KEY_SIZE)\n        res = self._backend._lib.EVP_PKEY_get_raw_public_key(\n            self._evp_pkey, buf, buflen\n        )\n        self._backend.openssl_assert(res == 1)\n        self._backend.openssl_assert(buflen[0] == _ED448_KEY_SIZE)\n        return self._backend._ffi.buffer(buf, _ED448_KEY_SIZE)[:]\n\n    def verify(self, signature, data):\n        evp_md_ctx = self._backend._lib.Cryptography_EVP_MD_CTX_new()\n        self._backend.openssl_assert(evp_md_ctx != self._backend._ffi.NULL)\n        evp_md_ctx = self._backend._ffi.gc(\n            evp_md_ctx, self._backend._lib.Cryptography_EVP_MD_CTX_free\n        )\n        res = self._backend._lib.EVP_DigestVerifyInit(\n            evp_md_ctx, self._backend._ffi.NULL, self._backend._ffi.NULL,\n            self._backend._ffi.NULL, self._evp_pkey\n        )\n        self._backend.openssl_assert(res == 1)\n        res = self._backend._lib.EVP_DigestVerify(\n            evp_md_ctx, signature, len(signature), data, len(data)\n        )\n        if res != 1:\n            self._backend._consume_errors()\n            raise exceptions.InvalidSignature\n\n\n@utils.register_interface(Ed448PrivateKey)\nclass _Ed448PrivateKey(object):\n    def __init__(self, backend, evp_pkey):\n        self._backend = backend\n        self._evp_pkey = evp_pkey\n\n    def public_key(self):\n        buf = self._backend._ffi.new(\"unsigned char []\", _ED448_KEY_SIZE)\n        buflen = self._backend._ffi.new(\"size_t *\", _ED448_KEY_SIZE)\n        res = self._backend._lib.EVP_PKEY_get_raw_public_key(\n            self._evp_pkey, buf, buflen\n        )\n        self._backend.openssl_assert(res == 1)\n        self._backend.openssl_assert(buflen[0] == _ED448_KEY_SIZE)\n        public_bytes = self._backend._ffi.buffer(buf)[:]\n        return self._backend.ed448_load_public_bytes(public_bytes)\n\n    def sign(self, data):\n        evp_md_ctx = self._backend._lib.Cryptography_EVP_MD_CTX_new()\n        self._backend.openssl_assert(evp_md_ctx != self._backend._ffi.NULL)\n        evp_md_ctx = self._backend._ffi.gc(\n            evp_md_ctx, self._backend._lib.Cryptography_EVP_MD_CTX_free\n        )\n        res = self._backend._lib.EVP_DigestSignInit(\n            evp_md_ctx, self._backend._ffi.NULL, self._backend._ffi.NULL,\n            self._backend._ffi.NULL, self._evp_pkey\n        )\n        self._backend.openssl_assert(res == 1)\n        buf = self._backend._ffi.new(\"unsigned char[]\", _ED448_SIG_SIZE)\n        buflen = self._backend._ffi.new(\"size_t *\", len(buf))\n        res = self._backend._lib.EVP_DigestSign(\n            evp_md_ctx, buf, buflen, data, len(data)\n        )\n        self._backend.openssl_assert(res == 1)\n        self._backend.openssl_assert(buflen[0] == _ED448_SIG_SIZE)\n        return self._backend._ffi.buffer(buf, buflen[0])[:]\n\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        if (\n            encoding is serialization.Encoding.Raw or\n            format is serialization.PublicFormat.Raw\n        ):\n            if (\n                format is not serialization.PrivateFormat.Raw or\n                encoding is not serialization.Encoding.Raw or not\n                isinstance(encryption_algorithm, serialization.NoEncryption)\n            ):\n                raise ValueError(\n                    \"When using Raw both encoding and format must be Raw \"\n                    \"and encryption_algorithm must be NoEncryption()\"\n                )\n\n            return self._raw_private_bytes()\n\n        if (\n            encoding in serialization._PEM_DER and\n            format is not serialization.PrivateFormat.PKCS8\n        ):\n            raise ValueError(\n                \"format must be PKCS8 when encoding is PEM or DER\"\n            )\n\n        return self._backend._private_key_bytes(\n            encoding, format, encryption_algorithm, self._evp_pkey, None\n        )\n\n    def _raw_private_bytes(self):\n        buf = self._backend._ffi.new(\"unsigned char []\", _ED448_KEY_SIZE)\n        buflen = self._backend._ffi.new(\"size_t *\", _ED448_KEY_SIZE)\n        res = self._backend._lib.EVP_PKEY_get_raw_private_key(\n            self._evp_pkey, buf, buflen\n        )\n        self._backend.openssl_assert(res == 1)\n        self._backend.openssl_assert(buflen[0] == _ED448_KEY_SIZE)\n        return self._backend._ffi.buffer(buf, _ED448_KEY_SIZE)[:]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/encode_asn1.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport calendar\nimport ipaddress\n\nimport six\n\nfrom cryptography import utils, x509\nfrom cryptography.hazmat.backends.openssl.decode_asn1 import (\n    _CRL_ENTRY_REASON_ENUM_TO_CODE, _DISTPOINT_TYPE_FULLNAME,\n    _DISTPOINT_TYPE_RELATIVENAME\n)\nfrom cryptography.x509.name import _ASN1Type\nfrom cryptography.x509.oid import (\n    CRLEntryExtensionOID, ExtensionOID, OCSPExtensionOID,\n)\n\n\ndef _encode_asn1_int(backend, x):\n    \"\"\"\n    Converts a python integer to an ASN1_INTEGER. The returned ASN1_INTEGER\n    will not be garbage collected (to support adding them to structs that take\n    ownership of the object). Be sure to register it for GC if it will be\n    discarded after use.\n\n    \"\"\"\n    # Convert Python integer to OpenSSL \"bignum\" in case value exceeds\n    # machine's native integer limits (note: `int_to_bn` doesn't automatically\n    # GC).\n    i = backend._int_to_bn(x)\n    i = backend._ffi.gc(i, backend._lib.BN_free)\n\n    # Wrap in an ASN.1 integer.  Don't GC -- as documented.\n    i = backend._lib.BN_to_ASN1_INTEGER(i, backend._ffi.NULL)\n    backend.openssl_assert(i != backend._ffi.NULL)\n    return i\n\n\ndef _encode_asn1_int_gc(backend, x):\n    i = _encode_asn1_int(backend, x)\n    i = backend._ffi.gc(i, backend._lib.ASN1_INTEGER_free)\n    return i\n\n\ndef _encode_asn1_str(backend, data):\n    \"\"\"\n    Create an ASN1_OCTET_STRING from a Python byte string.\n    \"\"\"\n    s = backend._lib.ASN1_OCTET_STRING_new()\n    res = backend._lib.ASN1_OCTET_STRING_set(s, data, len(data))\n    backend.openssl_assert(res == 1)\n    return s\n\n\ndef _encode_asn1_utf8_str(backend, string):\n    \"\"\"\n    Create an ASN1_UTF8STRING from a Python unicode string.\n    This object will be an ASN1_STRING with UTF8 type in OpenSSL and\n    can be decoded with ASN1_STRING_to_UTF8.\n    \"\"\"\n    s = backend._lib.ASN1_UTF8STRING_new()\n    res = backend._lib.ASN1_STRING_set(\n        s, string.encode(\"utf8\"), len(string.encode(\"utf8\"))\n    )\n    backend.openssl_assert(res == 1)\n    return s\n\n\ndef _encode_asn1_str_gc(backend, data):\n    s = _encode_asn1_str(backend, data)\n    s = backend._ffi.gc(s, backend._lib.ASN1_OCTET_STRING_free)\n    return s\n\n\ndef _encode_inhibit_any_policy(backend, inhibit_any_policy):\n    return _encode_asn1_int_gc(backend, inhibit_any_policy.skip_certs)\n\n\ndef _encode_name(backend, name):\n    \"\"\"\n    The X509_NAME created will not be gc'd. Use _encode_name_gc if needed.\n    \"\"\"\n    subject = backend._lib.X509_NAME_new()\n    for rdn in name.rdns:\n        set_flag = 0  # indicate whether to add to last RDN or create new RDN\n        for attribute in rdn:\n            name_entry = _encode_name_entry(backend, attribute)\n            # X509_NAME_add_entry dups the object so we need to gc this copy\n            name_entry = backend._ffi.gc(\n                name_entry, backend._lib.X509_NAME_ENTRY_free\n            )\n            res = backend._lib.X509_NAME_add_entry(\n                subject, name_entry, -1, set_flag)\n            backend.openssl_assert(res == 1)\n            set_flag = -1\n    return subject\n\n\ndef _encode_name_gc(backend, attributes):\n    subject = _encode_name(backend, attributes)\n    subject = backend._ffi.gc(subject, backend._lib.X509_NAME_free)\n    return subject\n\n\ndef _encode_sk_name_entry(backend, attributes):\n    \"\"\"\n    The sk_X509_NAME_ENTRY created will not be gc'd.\n    \"\"\"\n    stack = backend._lib.sk_X509_NAME_ENTRY_new_null()\n    for attribute in attributes:\n        name_entry = _encode_name_entry(backend, attribute)\n        res = backend._lib.sk_X509_NAME_ENTRY_push(stack, name_entry)\n        backend.openssl_assert(res >= 1)\n    return stack\n\n\ndef _encode_name_entry(backend, attribute):\n    if attribute._type is _ASN1Type.BMPString:\n        value = attribute.value.encode('utf_16_be')\n    elif attribute._type is _ASN1Type.UniversalString:\n        value = attribute.value.encode('utf_32_be')\n    else:\n        value = attribute.value.encode('utf8')\n\n    obj = _txt2obj_gc(backend, attribute.oid.dotted_string)\n\n    name_entry = backend._lib.X509_NAME_ENTRY_create_by_OBJ(\n        backend._ffi.NULL, obj, attribute._type.value, value, len(value)\n    )\n    return name_entry\n\n\ndef _encode_crl_number_delta_crl_indicator(backend, ext):\n    return _encode_asn1_int_gc(backend, ext.crl_number)\n\n\ndef _encode_issuing_dist_point(backend, ext):\n    idp = backend._lib.ISSUING_DIST_POINT_new()\n    backend.openssl_assert(idp != backend._ffi.NULL)\n    idp = backend._ffi.gc(idp, backend._lib.ISSUING_DIST_POINT_free)\n    idp.onlyuser = 255 if ext.only_contains_user_certs else 0\n    idp.onlyCA = 255 if ext.only_contains_ca_certs else 0\n    idp.indirectCRL = 255 if ext.indirect_crl else 0\n    idp.onlyattr = 255 if ext.only_contains_attribute_certs else 0\n    if ext.only_some_reasons:\n        idp.onlysomereasons = _encode_reasonflags(\n            backend, ext.only_some_reasons\n        )\n\n    if ext.full_name:\n        idp.distpoint = _encode_full_name(backend, ext.full_name)\n\n    if ext.relative_name:\n        idp.distpoint = _encode_relative_name(backend, ext.relative_name)\n\n    return idp\n\n\ndef _encode_crl_reason(backend, crl_reason):\n    asn1enum = backend._lib.ASN1_ENUMERATED_new()\n    backend.openssl_assert(asn1enum != backend._ffi.NULL)\n    asn1enum = backend._ffi.gc(asn1enum, backend._lib.ASN1_ENUMERATED_free)\n    res = backend._lib.ASN1_ENUMERATED_set(\n        asn1enum, _CRL_ENTRY_REASON_ENUM_TO_CODE[crl_reason.reason]\n    )\n    backend.openssl_assert(res == 1)\n\n    return asn1enum\n\n\ndef _encode_invalidity_date(backend, invalidity_date):\n    time = backend._lib.ASN1_GENERALIZEDTIME_set(\n        backend._ffi.NULL, calendar.timegm(\n            invalidity_date.invalidity_date.timetuple()\n        )\n    )\n    backend.openssl_assert(time != backend._ffi.NULL)\n    time = backend._ffi.gc(time, backend._lib.ASN1_GENERALIZEDTIME_free)\n\n    return time\n\n\ndef _encode_certificate_policies(backend, certificate_policies):\n    cp = backend._lib.sk_POLICYINFO_new_null()\n    backend.openssl_assert(cp != backend._ffi.NULL)\n    cp = backend._ffi.gc(cp, backend._lib.sk_POLICYINFO_free)\n    for policy_info in certificate_policies:\n        pi = backend._lib.POLICYINFO_new()\n        backend.openssl_assert(pi != backend._ffi.NULL)\n        res = backend._lib.sk_POLICYINFO_push(cp, pi)\n        backend.openssl_assert(res >= 1)\n        oid = _txt2obj(backend, policy_info.policy_identifier.dotted_string)\n        pi.policyid = oid\n        if policy_info.policy_qualifiers:\n            pqis = backend._lib.sk_POLICYQUALINFO_new_null()\n            backend.openssl_assert(pqis != backend._ffi.NULL)\n            for qualifier in policy_info.policy_qualifiers:\n                pqi = backend._lib.POLICYQUALINFO_new()\n                backend.openssl_assert(pqi != backend._ffi.NULL)\n                res = backend._lib.sk_POLICYQUALINFO_push(pqis, pqi)\n                backend.openssl_assert(res >= 1)\n                if isinstance(qualifier, six.text_type):\n                    pqi.pqualid = _txt2obj(\n                        backend, x509.OID_CPS_QUALIFIER.dotted_string\n                    )\n                    pqi.d.cpsuri = _encode_asn1_str(\n                        backend,\n                        qualifier.encode(\"ascii\"),\n                    )\n                else:\n                    assert isinstance(qualifier, x509.UserNotice)\n                    pqi.pqualid = _txt2obj(\n                        backend, x509.OID_CPS_USER_NOTICE.dotted_string\n                    )\n                    un = backend._lib.USERNOTICE_new()\n                    backend.openssl_assert(un != backend._ffi.NULL)\n                    pqi.d.usernotice = un\n                    if qualifier.explicit_text:\n                        un.exptext = _encode_asn1_utf8_str(\n                            backend, qualifier.explicit_text\n                        )\n\n                    un.noticeref = _encode_notice_reference(\n                        backend, qualifier.notice_reference\n                    )\n\n            pi.qualifiers = pqis\n\n    return cp\n\n\ndef _encode_notice_reference(backend, notice):\n    if notice is None:\n        return backend._ffi.NULL\n    else:\n        nr = backend._lib.NOTICEREF_new()\n        backend.openssl_assert(nr != backend._ffi.NULL)\n        # organization is a required field\n        nr.organization = _encode_asn1_utf8_str(backend, notice.organization)\n\n        notice_stack = backend._lib.sk_ASN1_INTEGER_new_null()\n        nr.noticenos = notice_stack\n        for number in notice.notice_numbers:\n            num = _encode_asn1_int(backend, number)\n            res = backend._lib.sk_ASN1_INTEGER_push(notice_stack, num)\n            backend.openssl_assert(res >= 1)\n\n        return nr\n\n\ndef _txt2obj(backend, name):\n    \"\"\"\n    Converts a Python string with an ASN.1 object ID in dotted form to a\n    ASN1_OBJECT.\n    \"\"\"\n    name = name.encode('ascii')\n    obj = backend._lib.OBJ_txt2obj(name, 1)\n    backend.openssl_assert(obj != backend._ffi.NULL)\n    return obj\n\n\ndef _txt2obj_gc(backend, name):\n    obj = _txt2obj(backend, name)\n    obj = backend._ffi.gc(obj, backend._lib.ASN1_OBJECT_free)\n    return obj\n\n\ndef _encode_ocsp_nocheck(backend, ext):\n    # Doesn't need to be GC'd\n    return backend._lib.ASN1_NULL_new()\n\n\ndef _encode_key_usage(backend, key_usage):\n    set_bit = backend._lib.ASN1_BIT_STRING_set_bit\n    ku = backend._lib.ASN1_BIT_STRING_new()\n    ku = backend._ffi.gc(ku, backend._lib.ASN1_BIT_STRING_free)\n    res = set_bit(ku, 0, key_usage.digital_signature)\n    backend.openssl_assert(res == 1)\n    res = set_bit(ku, 1, key_usage.content_commitment)\n    backend.openssl_assert(res == 1)\n    res = set_bit(ku, 2, key_usage.key_encipherment)\n    backend.openssl_assert(res == 1)\n    res = set_bit(ku, 3, key_usage.data_encipherment)\n    backend.openssl_assert(res == 1)\n    res = set_bit(ku, 4, key_usage.key_agreement)\n    backend.openssl_assert(res == 1)\n    res = set_bit(ku, 5, key_usage.key_cert_sign)\n    backend.openssl_assert(res == 1)\n    res = set_bit(ku, 6, key_usage.crl_sign)\n    backend.openssl_assert(res == 1)\n    if key_usage.key_agreement:\n        res = set_bit(ku, 7, key_usage.encipher_only)\n        backend.openssl_assert(res == 1)\n        res = set_bit(ku, 8, key_usage.decipher_only)\n        backend.openssl_assert(res == 1)\n    else:\n        res = set_bit(ku, 7, 0)\n        backend.openssl_assert(res == 1)\n        res = set_bit(ku, 8, 0)\n        backend.openssl_assert(res == 1)\n\n    return ku\n\n\ndef _encode_authority_key_identifier(backend, authority_keyid):\n    akid = backend._lib.AUTHORITY_KEYID_new()\n    backend.openssl_assert(akid != backend._ffi.NULL)\n    akid = backend._ffi.gc(akid, backend._lib.AUTHORITY_KEYID_free)\n    if authority_keyid.key_identifier is not None:\n        akid.keyid = _encode_asn1_str(\n            backend,\n            authority_keyid.key_identifier,\n        )\n\n    if authority_keyid.authority_cert_issuer is not None:\n        akid.issuer = _encode_general_names(\n            backend, authority_keyid.authority_cert_issuer\n        )\n\n    if authority_keyid.authority_cert_serial_number is not None:\n        akid.serial = _encode_asn1_int(\n            backend, authority_keyid.authority_cert_serial_number\n        )\n\n    return akid\n\n\ndef _encode_basic_constraints(backend, basic_constraints):\n    constraints = backend._lib.BASIC_CONSTRAINTS_new()\n    constraints = backend._ffi.gc(\n        constraints, backend._lib.BASIC_CONSTRAINTS_free\n    )\n    constraints.ca = 255 if basic_constraints.ca else 0\n    if basic_constraints.ca and basic_constraints.path_length is not None:\n        constraints.pathlen = _encode_asn1_int(\n            backend, basic_constraints.path_length\n        )\n\n    return constraints\n\n\ndef _encode_authority_information_access(backend, authority_info_access):\n    aia = backend._lib.sk_ACCESS_DESCRIPTION_new_null()\n    backend.openssl_assert(aia != backend._ffi.NULL)\n    aia = backend._ffi.gc(\n        aia,\n        lambda x: backend._lib.sk_ACCESS_DESCRIPTION_pop_free(\n            x, backend._ffi.addressof(\n                backend._lib._original_lib, \"ACCESS_DESCRIPTION_free\"\n            )\n        )\n    )\n    for access_description in authority_info_access:\n        ad = backend._lib.ACCESS_DESCRIPTION_new()\n        method = _txt2obj(\n            backend, access_description.access_method.dotted_string\n        )\n        _encode_general_name_preallocated(\n            backend, access_description.access_location, ad.location\n        )\n        ad.method = method\n        res = backend._lib.sk_ACCESS_DESCRIPTION_push(aia, ad)\n        backend.openssl_assert(res >= 1)\n\n    return aia\n\n\ndef _encode_general_names(backend, names):\n    general_names = backend._lib.GENERAL_NAMES_new()\n    backend.openssl_assert(general_names != backend._ffi.NULL)\n    for name in names:\n        gn = _encode_general_name(backend, name)\n        res = backend._lib.sk_GENERAL_NAME_push(general_names, gn)\n        backend.openssl_assert(res != 0)\n\n    return general_names\n\n\ndef _encode_alt_name(backend, san):\n    general_names = _encode_general_names(backend, san)\n    general_names = backend._ffi.gc(\n        general_names, backend._lib.GENERAL_NAMES_free\n    )\n    return general_names\n\n\ndef _encode_subject_key_identifier(backend, ski):\n    return _encode_asn1_str_gc(backend, ski.digest)\n\n\ndef _encode_general_name(backend, name):\n    gn = backend._lib.GENERAL_NAME_new()\n    _encode_general_name_preallocated(backend, name, gn)\n    return gn\n\n\ndef _encode_general_name_preallocated(backend, name, gn):\n    if isinstance(name, x509.DNSName):\n        backend.openssl_assert(gn != backend._ffi.NULL)\n        gn.type = backend._lib.GEN_DNS\n\n        ia5 = backend._lib.ASN1_IA5STRING_new()\n        backend.openssl_assert(ia5 != backend._ffi.NULL)\n        # ia5strings are supposed to be ITU T.50 but to allow round-tripping\n        # of broken certs that encode utf8 we'll encode utf8 here too.\n        value = name.value.encode(\"utf8\")\n\n        res = backend._lib.ASN1_STRING_set(ia5, value, len(value))\n        backend.openssl_assert(res == 1)\n        gn.d.dNSName = ia5\n    elif isinstance(name, x509.RegisteredID):\n        backend.openssl_assert(gn != backend._ffi.NULL)\n        gn.type = backend._lib.GEN_RID\n        obj = backend._lib.OBJ_txt2obj(\n            name.value.dotted_string.encode('ascii'), 1\n        )\n        backend.openssl_assert(obj != backend._ffi.NULL)\n        gn.d.registeredID = obj\n    elif isinstance(name, x509.DirectoryName):\n        backend.openssl_assert(gn != backend._ffi.NULL)\n        dir_name = _encode_name(backend, name.value)\n        gn.type = backend._lib.GEN_DIRNAME\n        gn.d.directoryName = dir_name\n    elif isinstance(name, x509.IPAddress):\n        backend.openssl_assert(gn != backend._ffi.NULL)\n        if isinstance(name.value, ipaddress.IPv4Network):\n            packed = (\n                name.value.network_address.packed +\n                utils.int_to_bytes(((1 << 32) - name.value.num_addresses), 4)\n            )\n        elif isinstance(name.value, ipaddress.IPv6Network):\n            packed = (\n                name.value.network_address.packed +\n                utils.int_to_bytes((1 << 128) - name.value.num_addresses, 16)\n            )\n        else:\n            packed = name.value.packed\n        ipaddr = _encode_asn1_str(backend, packed)\n        gn.type = backend._lib.GEN_IPADD\n        gn.d.iPAddress = ipaddr\n    elif isinstance(name, x509.OtherName):\n        backend.openssl_assert(gn != backend._ffi.NULL)\n        other_name = backend._lib.OTHERNAME_new()\n        backend.openssl_assert(other_name != backend._ffi.NULL)\n\n        type_id = backend._lib.OBJ_txt2obj(\n            name.type_id.dotted_string.encode('ascii'), 1\n        )\n        backend.openssl_assert(type_id != backend._ffi.NULL)\n        data = backend._ffi.new(\"unsigned char[]\", name.value)\n        data_ptr_ptr = backend._ffi.new(\"unsigned char **\")\n        data_ptr_ptr[0] = data\n        value = backend._lib.d2i_ASN1_TYPE(\n            backend._ffi.NULL, data_ptr_ptr, len(name.value)\n        )\n        if value == backend._ffi.NULL:\n            backend._consume_errors()\n            raise ValueError(\"Invalid ASN.1 data\")\n        other_name.type_id = type_id\n        other_name.value = value\n        gn.type = backend._lib.GEN_OTHERNAME\n        gn.d.otherName = other_name\n    elif isinstance(name, x509.RFC822Name):\n        backend.openssl_assert(gn != backend._ffi.NULL)\n        # ia5strings are supposed to be ITU T.50 but to allow round-tripping\n        # of broken certs that encode utf8 we'll encode utf8 here too.\n        data = name.value.encode(\"utf8\")\n        asn1_str = _encode_asn1_str(backend, data)\n        gn.type = backend._lib.GEN_EMAIL\n        gn.d.rfc822Name = asn1_str\n    elif isinstance(name, x509.UniformResourceIdentifier):\n        backend.openssl_assert(gn != backend._ffi.NULL)\n        # ia5strings are supposed to be ITU T.50 but to allow round-tripping\n        # of broken certs that encode utf8 we'll encode utf8 here too.\n        data = name.value.encode(\"utf8\")\n        asn1_str = _encode_asn1_str(backend, data)\n        gn.type = backend._lib.GEN_URI\n        gn.d.uniformResourceIdentifier = asn1_str\n    else:\n        raise ValueError(\n            \"{} is an unknown GeneralName type\".format(name)\n        )\n\n\ndef _encode_extended_key_usage(backend, extended_key_usage):\n    eku = backend._lib.sk_ASN1_OBJECT_new_null()\n    eku = backend._ffi.gc(eku, backend._lib.sk_ASN1_OBJECT_free)\n    for oid in extended_key_usage:\n        obj = _txt2obj(backend, oid.dotted_string)\n        res = backend._lib.sk_ASN1_OBJECT_push(eku, obj)\n        backend.openssl_assert(res >= 1)\n\n    return eku\n\n\n_CRLREASONFLAGS = {\n    x509.ReasonFlags.key_compromise: 1,\n    x509.ReasonFlags.ca_compromise: 2,\n    x509.ReasonFlags.affiliation_changed: 3,\n    x509.ReasonFlags.superseded: 4,\n    x509.ReasonFlags.cessation_of_operation: 5,\n    x509.ReasonFlags.certificate_hold: 6,\n    x509.ReasonFlags.privilege_withdrawn: 7,\n    x509.ReasonFlags.aa_compromise: 8,\n}\n\n\ndef _encode_reasonflags(backend, reasons):\n    bitmask = backend._lib.ASN1_BIT_STRING_new()\n    backend.openssl_assert(bitmask != backend._ffi.NULL)\n    for reason in reasons:\n        res = backend._lib.ASN1_BIT_STRING_set_bit(\n            bitmask, _CRLREASONFLAGS[reason], 1\n        )\n        backend.openssl_assert(res == 1)\n\n    return bitmask\n\n\ndef _encode_full_name(backend, full_name):\n    dpn = backend._lib.DIST_POINT_NAME_new()\n    backend.openssl_assert(dpn != backend._ffi.NULL)\n    dpn.type = _DISTPOINT_TYPE_FULLNAME\n    dpn.name.fullname = _encode_general_names(backend, full_name)\n    return dpn\n\n\ndef _encode_relative_name(backend, relative_name):\n    dpn = backend._lib.DIST_POINT_NAME_new()\n    backend.openssl_assert(dpn != backend._ffi.NULL)\n    dpn.type = _DISTPOINT_TYPE_RELATIVENAME\n    dpn.name.relativename = _encode_sk_name_entry(backend, relative_name)\n    return dpn\n\n\ndef _encode_cdps_freshest_crl(backend, cdps):\n    cdp = backend._lib.sk_DIST_POINT_new_null()\n    cdp = backend._ffi.gc(cdp, backend._lib.sk_DIST_POINT_free)\n    for point in cdps:\n        dp = backend._lib.DIST_POINT_new()\n        backend.openssl_assert(dp != backend._ffi.NULL)\n\n        if point.reasons:\n            dp.reasons = _encode_reasonflags(backend, point.reasons)\n\n        if point.full_name:\n            dp.distpoint = _encode_full_name(backend, point.full_name)\n\n        if point.relative_name:\n            dp.distpoint = _encode_relative_name(backend, point.relative_name)\n\n        if point.crl_issuer:\n            dp.CRLissuer = _encode_general_names(backend, point.crl_issuer)\n\n        res = backend._lib.sk_DIST_POINT_push(cdp, dp)\n        backend.openssl_assert(res >= 1)\n\n    return cdp\n\n\ndef _encode_name_constraints(backend, name_constraints):\n    nc = backend._lib.NAME_CONSTRAINTS_new()\n    backend.openssl_assert(nc != backend._ffi.NULL)\n    nc = backend._ffi.gc(nc, backend._lib.NAME_CONSTRAINTS_free)\n    permitted = _encode_general_subtree(\n        backend, name_constraints.permitted_subtrees\n    )\n    nc.permittedSubtrees = permitted\n    excluded = _encode_general_subtree(\n        backend, name_constraints.excluded_subtrees\n    )\n    nc.excludedSubtrees = excluded\n\n    return nc\n\n\ndef _encode_policy_constraints(backend, policy_constraints):\n    pc = backend._lib.POLICY_CONSTRAINTS_new()\n    backend.openssl_assert(pc != backend._ffi.NULL)\n    pc = backend._ffi.gc(pc, backend._lib.POLICY_CONSTRAINTS_free)\n    if policy_constraints.require_explicit_policy is not None:\n        pc.requireExplicitPolicy = _encode_asn1_int(\n            backend, policy_constraints.require_explicit_policy\n        )\n\n    if policy_constraints.inhibit_policy_mapping is not None:\n        pc.inhibitPolicyMapping = _encode_asn1_int(\n            backend, policy_constraints.inhibit_policy_mapping\n        )\n\n    return pc\n\n\ndef _encode_general_subtree(backend, subtrees):\n    if subtrees is None:\n        return backend._ffi.NULL\n    else:\n        general_subtrees = backend._lib.sk_GENERAL_SUBTREE_new_null()\n        for name in subtrees:\n            gs = backend._lib.GENERAL_SUBTREE_new()\n            gs.base = _encode_general_name(backend, name)\n            res = backend._lib.sk_GENERAL_SUBTREE_push(general_subtrees, gs)\n            assert res >= 1\n\n        return general_subtrees\n\n\ndef _encode_nonce(backend, nonce):\n    return _encode_asn1_str_gc(backend, nonce.nonce)\n\n\n_EXTENSION_ENCODE_HANDLERS = {\n    ExtensionOID.BASIC_CONSTRAINTS: _encode_basic_constraints,\n    ExtensionOID.SUBJECT_KEY_IDENTIFIER: _encode_subject_key_identifier,\n    ExtensionOID.KEY_USAGE: _encode_key_usage,\n    ExtensionOID.SUBJECT_ALTERNATIVE_NAME: _encode_alt_name,\n    ExtensionOID.ISSUER_ALTERNATIVE_NAME: _encode_alt_name,\n    ExtensionOID.EXTENDED_KEY_USAGE: _encode_extended_key_usage,\n    ExtensionOID.AUTHORITY_KEY_IDENTIFIER: _encode_authority_key_identifier,\n    ExtensionOID.CERTIFICATE_POLICIES: _encode_certificate_policies,\n    ExtensionOID.AUTHORITY_INFORMATION_ACCESS: (\n        _encode_authority_information_access\n    ),\n    ExtensionOID.CRL_DISTRIBUTION_POINTS: _encode_cdps_freshest_crl,\n    ExtensionOID.FRESHEST_CRL: _encode_cdps_freshest_crl,\n    ExtensionOID.INHIBIT_ANY_POLICY: _encode_inhibit_any_policy,\n    ExtensionOID.OCSP_NO_CHECK: _encode_ocsp_nocheck,\n    ExtensionOID.NAME_CONSTRAINTS: _encode_name_constraints,\n    ExtensionOID.POLICY_CONSTRAINTS: _encode_policy_constraints,\n}\n\n_CRL_EXTENSION_ENCODE_HANDLERS = {\n    ExtensionOID.ISSUER_ALTERNATIVE_NAME: _encode_alt_name,\n    ExtensionOID.AUTHORITY_KEY_IDENTIFIER: _encode_authority_key_identifier,\n    ExtensionOID.AUTHORITY_INFORMATION_ACCESS: (\n        _encode_authority_information_access\n    ),\n    ExtensionOID.CRL_NUMBER: _encode_crl_number_delta_crl_indicator,\n    ExtensionOID.DELTA_CRL_INDICATOR: _encode_crl_number_delta_crl_indicator,\n    ExtensionOID.ISSUING_DISTRIBUTION_POINT: _encode_issuing_dist_point,\n    ExtensionOID.FRESHEST_CRL: _encode_cdps_freshest_crl,\n}\n\n_CRL_ENTRY_EXTENSION_ENCODE_HANDLERS = {\n    CRLEntryExtensionOID.CERTIFICATE_ISSUER: _encode_alt_name,\n    CRLEntryExtensionOID.CRL_REASON: _encode_crl_reason,\n    CRLEntryExtensionOID.INVALIDITY_DATE: _encode_invalidity_date,\n}\n\n_OCSP_REQUEST_EXTENSION_ENCODE_HANDLERS = {\n    OCSPExtensionOID.NONCE: _encode_nonce,\n}\n\n_OCSP_BASICRESP_EXTENSION_ENCODE_HANDLERS = {\n    OCSPExtensionOID.NONCE: _encode_nonce,\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/hashes.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\n\nfrom cryptography import utils\nfrom cryptography.exceptions import UnsupportedAlgorithm, _Reasons\nfrom cryptography.hazmat.primitives import hashes\n\n\n@utils.register_interface(hashes.HashContext)\nclass _HashContext(object):\n    def __init__(self, backend, algorithm, ctx=None):\n        self._algorithm = algorithm\n\n        self._backend = backend\n\n        if ctx is None:\n            ctx = self._backend._lib.Cryptography_EVP_MD_CTX_new()\n            ctx = self._backend._ffi.gc(\n                ctx, self._backend._lib.Cryptography_EVP_MD_CTX_free\n            )\n            evp_md = self._backend._evp_md_from_algorithm(algorithm)\n            if evp_md == self._backend._ffi.NULL:\n                raise UnsupportedAlgorithm(\n                    \"{} is not a supported hash on this backend.\".format(\n                        algorithm.name),\n                    _Reasons.UNSUPPORTED_HASH\n                )\n            res = self._backend._lib.EVP_DigestInit_ex(ctx, evp_md,\n                                                       self._backend._ffi.NULL)\n            self._backend.openssl_assert(res != 0)\n\n        self._ctx = ctx\n\n    algorithm = utils.read_only_property(\"_algorithm\")\n\n    def copy(self):\n        copied_ctx = self._backend._lib.Cryptography_EVP_MD_CTX_new()\n        copied_ctx = self._backend._ffi.gc(\n            copied_ctx, self._backend._lib.Cryptography_EVP_MD_CTX_free\n        )\n        res = self._backend._lib.EVP_MD_CTX_copy_ex(copied_ctx, self._ctx)\n        self._backend.openssl_assert(res != 0)\n        return _HashContext(self._backend, self.algorithm, ctx=copied_ctx)\n\n    def update(self, data):\n        data_ptr = self._backend._ffi.from_buffer(data)\n        res = self._backend._lib.EVP_DigestUpdate(\n            self._ctx, data_ptr, len(data)\n        )\n        self._backend.openssl_assert(res != 0)\n\n    def finalize(self):\n        if isinstance(self.algorithm, hashes.ExtendableOutputFunction):\n            # extendable output functions use a different finalize\n            return self._finalize_xof()\n        else:\n            buf = self._backend._ffi.new(\"unsigned char[]\",\n                                         self._backend._lib.EVP_MAX_MD_SIZE)\n            outlen = self._backend._ffi.new(\"unsigned int *\")\n            res = self._backend._lib.EVP_DigestFinal_ex(self._ctx, buf, outlen)\n            self._backend.openssl_assert(res != 0)\n            self._backend.openssl_assert(\n                outlen[0] == self.algorithm.digest_size\n            )\n            return self._backend._ffi.buffer(buf)[:outlen[0]]\n\n    def _finalize_xof(self):\n        buf = self._backend._ffi.new(\"unsigned char[]\",\n                                     self.algorithm.digest_size)\n        res = self._backend._lib.EVP_DigestFinalXOF(\n            self._ctx, buf, self.algorithm.digest_size\n        )\n        self._backend.openssl_assert(res != 0)\n        return self._backend._ffi.buffer(buf)[:self.algorithm.digest_size]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/hmac.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    InvalidSignature, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.primitives import constant_time, hashes\n\n\n@utils.register_interface(hashes.HashContext)\nclass _HMACContext(object):\n    def __init__(self, backend, key, algorithm, ctx=None):\n        self._algorithm = algorithm\n        self._backend = backend\n\n        if ctx is None:\n            ctx = self._backend._lib.Cryptography_HMAC_CTX_new()\n            self._backend.openssl_assert(ctx != self._backend._ffi.NULL)\n            ctx = self._backend._ffi.gc(\n                ctx, self._backend._lib.Cryptography_HMAC_CTX_free\n            )\n            evp_md = self._backend._evp_md_from_algorithm(algorithm)\n            if evp_md == self._backend._ffi.NULL:\n                raise UnsupportedAlgorithm(\n                    \"{} is not a supported hash on this backend\".format(\n                        algorithm.name),\n                    _Reasons.UNSUPPORTED_HASH\n                )\n            key_ptr = self._backend._ffi.from_buffer(key)\n            res = self._backend._lib.HMAC_Init_ex(\n                ctx, key_ptr, len(key), evp_md, self._backend._ffi.NULL\n            )\n            self._backend.openssl_assert(res != 0)\n\n        self._ctx = ctx\n        self._key = key\n\n    algorithm = utils.read_only_property(\"_algorithm\")\n\n    def copy(self):\n        copied_ctx = self._backend._lib.Cryptography_HMAC_CTX_new()\n        self._backend.openssl_assert(copied_ctx != self._backend._ffi.NULL)\n        copied_ctx = self._backend._ffi.gc(\n            copied_ctx, self._backend._lib.Cryptography_HMAC_CTX_free\n        )\n        res = self._backend._lib.HMAC_CTX_copy(copied_ctx, self._ctx)\n        self._backend.openssl_assert(res != 0)\n        return _HMACContext(\n            self._backend, self._key, self.algorithm, ctx=copied_ctx\n        )\n\n    def update(self, data):\n        data_ptr = self._backend._ffi.from_buffer(data)\n        res = self._backend._lib.HMAC_Update(self._ctx, data_ptr, len(data))\n        self._backend.openssl_assert(res != 0)\n\n    def finalize(self):\n        buf = self._backend._ffi.new(\"unsigned char[]\",\n                                     self._backend._lib.EVP_MAX_MD_SIZE)\n        outlen = self._backend._ffi.new(\"unsigned int *\")\n        res = self._backend._lib.HMAC_Final(self._ctx, buf, outlen)\n        self._backend.openssl_assert(res != 0)\n        self._backend.openssl_assert(outlen[0] == self.algorithm.digest_size)\n        return self._backend._ffi.buffer(buf)[:outlen[0]]\n\n    def verify(self, signature):\n        digest = self.finalize()\n        if not constant_time.bytes_eq(digest, signature):\n            raise InvalidSignature(\"Signature did not match digest.\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/ocsp.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport functools\n\nfrom cryptography import utils, x509\nfrom cryptography.exceptions import UnsupportedAlgorithm\nfrom cryptography.hazmat.backends.openssl.decode_asn1 import (\n    _CRL_ENTRY_REASON_CODE_TO_ENUM, _OCSP_BASICRESP_EXT_PARSER,\n    _OCSP_REQ_EXT_PARSER, _asn1_integer_to_int,\n    _asn1_string_to_bytes, _decode_x509_name, _obj2txt,\n    _parse_asn1_generalized_time,\n)\nfrom cryptography.hazmat.backends.openssl.x509 import _Certificate\nfrom cryptography.hazmat.primitives import serialization\nfrom cryptography.x509.ocsp import (\n    OCSPCertStatus, OCSPRequest, OCSPResponse, OCSPResponseStatus,\n    _CERT_STATUS_TO_ENUM, _OIDS_TO_HASH, _RESPONSE_STATUS_TO_ENUM,\n)\n\n\ndef _requires_successful_response(func):\n    @functools.wraps(func)\n    def wrapper(self, *args):\n        if self.response_status != OCSPResponseStatus.SUCCESSFUL:\n            raise ValueError(\n                \"OCSP response status is not successful so the property \"\n                \"has no value\"\n            )\n        else:\n            return func(self, *args)\n\n    return wrapper\n\n\ndef _issuer_key_hash(backend, cert_id):\n    key_hash = backend._ffi.new(\"ASN1_OCTET_STRING **\")\n    res = backend._lib.OCSP_id_get0_info(\n        backend._ffi.NULL, backend._ffi.NULL,\n        key_hash, backend._ffi.NULL, cert_id\n    )\n    backend.openssl_assert(res == 1)\n    backend.openssl_assert(key_hash[0] != backend._ffi.NULL)\n    return _asn1_string_to_bytes(backend, key_hash[0])\n\n\ndef _issuer_name_hash(backend, cert_id):\n    name_hash = backend._ffi.new(\"ASN1_OCTET_STRING **\")\n    res = backend._lib.OCSP_id_get0_info(\n        name_hash, backend._ffi.NULL,\n        backend._ffi.NULL, backend._ffi.NULL, cert_id\n    )\n    backend.openssl_assert(res == 1)\n    backend.openssl_assert(name_hash[0] != backend._ffi.NULL)\n    return _asn1_string_to_bytes(backend, name_hash[0])\n\n\ndef _serial_number(backend, cert_id):\n    num = backend._ffi.new(\"ASN1_INTEGER **\")\n    res = backend._lib.OCSP_id_get0_info(\n        backend._ffi.NULL, backend._ffi.NULL,\n        backend._ffi.NULL, num, cert_id\n    )\n    backend.openssl_assert(res == 1)\n    backend.openssl_assert(num[0] != backend._ffi.NULL)\n    return _asn1_integer_to_int(backend, num[0])\n\n\ndef _hash_algorithm(backend, cert_id):\n    asn1obj = backend._ffi.new(\"ASN1_OBJECT **\")\n    res = backend._lib.OCSP_id_get0_info(\n        backend._ffi.NULL, asn1obj,\n        backend._ffi.NULL, backend._ffi.NULL, cert_id\n    )\n    backend.openssl_assert(res == 1)\n    backend.openssl_assert(asn1obj[0] != backend._ffi.NULL)\n    oid = _obj2txt(backend, asn1obj[0])\n    try:\n        return _OIDS_TO_HASH[oid]\n    except KeyError:\n        raise UnsupportedAlgorithm(\n            \"Signature algorithm OID: {} not recognized\".format(oid)\n        )\n\n\n@utils.register_interface(OCSPResponse)\nclass _OCSPResponse(object):\n    def __init__(self, backend, ocsp_response):\n        self._backend = backend\n        self._ocsp_response = ocsp_response\n        status = self._backend._lib.OCSP_response_status(self._ocsp_response)\n        self._backend.openssl_assert(status in _RESPONSE_STATUS_TO_ENUM)\n        self._status = _RESPONSE_STATUS_TO_ENUM[status]\n        if self._status is OCSPResponseStatus.SUCCESSFUL:\n            basic = self._backend._lib.OCSP_response_get1_basic(\n                self._ocsp_response\n            )\n            self._backend.openssl_assert(basic != self._backend._ffi.NULL)\n            self._basic = self._backend._ffi.gc(\n                basic, self._backend._lib.OCSP_BASICRESP_free\n            )\n            self._backend.openssl_assert(\n                self._backend._lib.OCSP_resp_count(self._basic) == 1\n            )\n            self._single = self._backend._lib.OCSP_resp_get0(self._basic, 0)\n            self._backend.openssl_assert(\n                self._single != self._backend._ffi.NULL\n            )\n            self._cert_id = self._backend._lib.OCSP_SINGLERESP_get0_id(\n                self._single\n            )\n            self._backend.openssl_assert(\n                self._cert_id != self._backend._ffi.NULL\n            )\n\n    response_status = utils.read_only_property(\"_status\")\n\n    @property\n    @_requires_successful_response\n    def signature_algorithm_oid(self):\n        alg = self._backend._lib.OCSP_resp_get0_tbs_sigalg(self._basic)\n        self._backend.openssl_assert(alg != self._backend._ffi.NULL)\n        oid = _obj2txt(self._backend, alg.algorithm)\n        return x509.ObjectIdentifier(oid)\n\n    @property\n    @_requires_successful_response\n    def signature_hash_algorithm(self):\n        oid = self.signature_algorithm_oid\n        try:\n            return x509._SIG_OIDS_TO_HASH[oid]\n        except KeyError:\n            raise UnsupportedAlgorithm(\n                \"Signature algorithm OID:{} not recognized\".format(oid)\n            )\n\n    @property\n    @_requires_successful_response\n    def signature(self):\n        sig = self._backend._lib.OCSP_resp_get0_signature(self._basic)\n        self._backend.openssl_assert(sig != self._backend._ffi.NULL)\n        return _asn1_string_to_bytes(self._backend, sig)\n\n    @property\n    @_requires_successful_response\n    def tbs_response_bytes(self):\n        respdata = self._backend._lib.OCSP_resp_get0_respdata(self._basic)\n        self._backend.openssl_assert(respdata != self._backend._ffi.NULL)\n        pp = self._backend._ffi.new(\"unsigned char **\")\n        res = self._backend._lib.i2d_OCSP_RESPDATA(respdata, pp)\n        self._backend.openssl_assert(pp[0] != self._backend._ffi.NULL)\n        pp = self._backend._ffi.gc(\n            pp, lambda pointer: self._backend._lib.OPENSSL_free(pointer[0])\n        )\n        self._backend.openssl_assert(res > 0)\n        return self._backend._ffi.buffer(pp[0], res)[:]\n\n    @property\n    @_requires_successful_response\n    def certificates(self):\n        sk_x509 = self._backend._lib.OCSP_resp_get0_certs(self._basic)\n        num = self._backend._lib.sk_X509_num(sk_x509)\n        certs = []\n        for i in range(num):\n            x509 = self._backend._lib.sk_X509_value(sk_x509, i)\n            self._backend.openssl_assert(x509 != self._backend._ffi.NULL)\n            cert = _Certificate(self._backend, x509)\n            # We need to keep the OCSP response that the certificate came from\n            # alive until the Certificate object itself goes out of scope, so\n            # we give it a private reference.\n            cert._ocsp_resp = self\n            certs.append(cert)\n\n        return certs\n\n    @property\n    @_requires_successful_response\n    def responder_key_hash(self):\n        _, asn1_string = self._responder_key_name()\n        if asn1_string == self._backend._ffi.NULL:\n            return None\n        else:\n            return _asn1_string_to_bytes(self._backend, asn1_string)\n\n    @property\n    @_requires_successful_response\n    def responder_name(self):\n        x509_name, _ = self._responder_key_name()\n        if x509_name == self._backend._ffi.NULL:\n            return None\n        else:\n            return _decode_x509_name(self._backend, x509_name)\n\n    def _responder_key_name(self):\n        asn1_string = self._backend._ffi.new(\"ASN1_OCTET_STRING **\")\n        x509_name = self._backend._ffi.new(\"X509_NAME **\")\n        res = self._backend._lib.OCSP_resp_get0_id(\n            self._basic, asn1_string, x509_name\n        )\n        self._backend.openssl_assert(res == 1)\n        return x509_name[0], asn1_string[0]\n\n    @property\n    @_requires_successful_response\n    def produced_at(self):\n        produced_at = self._backend._lib.OCSP_resp_get0_produced_at(\n            self._basic\n        )\n        return _parse_asn1_generalized_time(self._backend, produced_at)\n\n    @property\n    @_requires_successful_response\n    def certificate_status(self):\n        status = self._backend._lib.OCSP_single_get0_status(\n            self._single,\n            self._backend._ffi.NULL,\n            self._backend._ffi.NULL,\n            self._backend._ffi.NULL,\n            self._backend._ffi.NULL,\n        )\n        self._backend.openssl_assert(status in _CERT_STATUS_TO_ENUM)\n        return _CERT_STATUS_TO_ENUM[status]\n\n    @property\n    @_requires_successful_response\n    def revocation_time(self):\n        if self.certificate_status is not OCSPCertStatus.REVOKED:\n            return None\n\n        asn1_time = self._backend._ffi.new(\"ASN1_GENERALIZEDTIME **\")\n        self._backend._lib.OCSP_single_get0_status(\n            self._single,\n            self._backend._ffi.NULL,\n            asn1_time,\n            self._backend._ffi.NULL,\n            self._backend._ffi.NULL,\n        )\n        self._backend.openssl_assert(asn1_time[0] != self._backend._ffi.NULL)\n        return _parse_asn1_generalized_time(self._backend, asn1_time[0])\n\n    @property\n    @_requires_successful_response\n    def revocation_reason(self):\n        if self.certificate_status is not OCSPCertStatus.REVOKED:\n            return None\n\n        reason_ptr = self._backend._ffi.new(\"int *\")\n        self._backend._lib.OCSP_single_get0_status(\n            self._single,\n            reason_ptr,\n            self._backend._ffi.NULL,\n            self._backend._ffi.NULL,\n            self._backend._ffi.NULL,\n        )\n        # If no reason is encoded OpenSSL returns -1\n        if reason_ptr[0] == -1:\n            return None\n        else:\n            self._backend.openssl_assert(\n                reason_ptr[0] in _CRL_ENTRY_REASON_CODE_TO_ENUM\n            )\n            return _CRL_ENTRY_REASON_CODE_TO_ENUM[reason_ptr[0]]\n\n    @property\n    @_requires_successful_response\n    def this_update(self):\n        asn1_time = self._backend._ffi.new(\"ASN1_GENERALIZEDTIME **\")\n        self._backend._lib.OCSP_single_get0_status(\n            self._single,\n            self._backend._ffi.NULL,\n            self._backend._ffi.NULL,\n            asn1_time,\n            self._backend._ffi.NULL,\n        )\n        self._backend.openssl_assert(asn1_time[0] != self._backend._ffi.NULL)\n        return _parse_asn1_generalized_time(self._backend, asn1_time[0])\n\n    @property\n    @_requires_successful_response\n    def next_update(self):\n        asn1_time = self._backend._ffi.new(\"ASN1_GENERALIZEDTIME **\")\n        self._backend._lib.OCSP_single_get0_status(\n            self._single,\n            self._backend._ffi.NULL,\n            self._backend._ffi.NULL,\n            self._backend._ffi.NULL,\n            asn1_time,\n        )\n        if asn1_time[0] != self._backend._ffi.NULL:\n            return _parse_asn1_generalized_time(self._backend, asn1_time[0])\n        else:\n            return None\n\n    @property\n    @_requires_successful_response\n    def issuer_key_hash(self):\n        return _issuer_key_hash(self._backend, self._cert_id)\n\n    @property\n    @_requires_successful_response\n    def issuer_name_hash(self):\n        return _issuer_name_hash(self._backend, self._cert_id)\n\n    @property\n    @_requires_successful_response\n    def hash_algorithm(self):\n        return _hash_algorithm(self._backend, self._cert_id)\n\n    @property\n    @_requires_successful_response\n    def serial_number(self):\n        return _serial_number(self._backend, self._cert_id)\n\n    @utils.cached_property\n    @_requires_successful_response\n    def extensions(self):\n        return _OCSP_BASICRESP_EXT_PARSER.parse(self._backend, self._basic)\n\n    def public_bytes(self, encoding):\n        if encoding is not serialization.Encoding.DER:\n            raise ValueError(\n                \"The only allowed encoding value is Encoding.DER\"\n            )\n\n        bio = self._backend._create_mem_bio_gc()\n        res = self._backend._lib.i2d_OCSP_RESPONSE_bio(\n            bio, self._ocsp_response\n        )\n        self._backend.openssl_assert(res > 0)\n        return self._backend._read_mem_bio(bio)\n\n\n@utils.register_interface(OCSPRequest)\nclass _OCSPRequest(object):\n    def __init__(self, backend, ocsp_request):\n        if backend._lib.OCSP_request_onereq_count(ocsp_request) > 1:\n            raise NotImplementedError(\n                'OCSP request contains more than one request'\n            )\n        self._backend = backend\n        self._ocsp_request = ocsp_request\n        self._request = self._backend._lib.OCSP_request_onereq_get0(\n            self._ocsp_request, 0\n        )\n        self._backend.openssl_assert(self._request != self._backend._ffi.NULL)\n        self._cert_id = self._backend._lib.OCSP_onereq_get0_id(self._request)\n        self._backend.openssl_assert(self._cert_id != self._backend._ffi.NULL)\n\n    @property\n    def issuer_key_hash(self):\n        return _issuer_key_hash(self._backend, self._cert_id)\n\n    @property\n    def issuer_name_hash(self):\n        return _issuer_name_hash(self._backend, self._cert_id)\n\n    @property\n    def serial_number(self):\n        return _serial_number(self._backend, self._cert_id)\n\n    @property\n    def hash_algorithm(self):\n        return _hash_algorithm(self._backend, self._cert_id)\n\n    @utils.cached_property\n    def extensions(self):\n        return _OCSP_REQ_EXT_PARSER.parse(self._backend, self._ocsp_request)\n\n    def public_bytes(self, encoding):\n        if encoding is not serialization.Encoding.DER:\n            raise ValueError(\n                \"The only allowed encoding value is Encoding.DER\"\n            )\n\n        bio = self._backend._create_mem_bio_gc()\n        res = self._backend._lib.i2d_OCSP_REQUEST_bio(bio, self._ocsp_request)\n        self._backend.openssl_assert(res > 0)\n        return self._backend._read_mem_bio(bio)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/poly1305.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\n\nfrom cryptography.exceptions import InvalidSignature\nfrom cryptography.hazmat.primitives import constant_time\n\n\n_POLY1305_TAG_SIZE = 16\n_POLY1305_KEY_SIZE = 32\n\n\nclass _Poly1305Context(object):\n    def __init__(self, backend, key):\n        self._backend = backend\n\n        key_ptr = self._backend._ffi.from_buffer(key)\n        # This function copies the key into OpenSSL-owned memory so we don't\n        # need to retain it ourselves\n        evp_pkey = self._backend._lib.EVP_PKEY_new_raw_private_key(\n            self._backend._lib.NID_poly1305,\n            self._backend._ffi.NULL, key_ptr, len(key)\n        )\n        self._backend.openssl_assert(evp_pkey != self._backend._ffi.NULL)\n        self._evp_pkey = self._backend._ffi.gc(\n            evp_pkey, self._backend._lib.EVP_PKEY_free\n        )\n        ctx = self._backend._lib.Cryptography_EVP_MD_CTX_new()\n        self._backend.openssl_assert(ctx != self._backend._ffi.NULL)\n        self._ctx = self._backend._ffi.gc(\n            ctx, self._backend._lib.Cryptography_EVP_MD_CTX_free\n        )\n        res = self._backend._lib.EVP_DigestSignInit(\n            self._ctx, self._backend._ffi.NULL, self._backend._ffi.NULL,\n            self._backend._ffi.NULL, self._evp_pkey\n        )\n        self._backend.openssl_assert(res == 1)\n\n    def update(self, data):\n        data_ptr = self._backend._ffi.from_buffer(data)\n        res = self._backend._lib.EVP_DigestSignUpdate(\n            self._ctx, data_ptr, len(data)\n        )\n        self._backend.openssl_assert(res != 0)\n\n    def finalize(self):\n        buf = self._backend._ffi.new(\"unsigned char[]\", _POLY1305_TAG_SIZE)\n        outlen = self._backend._ffi.new(\"size_t *\")\n        res = self._backend._lib.EVP_DigestSignFinal(self._ctx, buf, outlen)\n        self._backend.openssl_assert(res != 0)\n        self._backend.openssl_assert(outlen[0] == _POLY1305_TAG_SIZE)\n        return self._backend._ffi.buffer(buf)[:outlen[0]]\n\n    def verify(self, tag):\n        mac = self.finalize()\n        if not constant_time.bytes_eq(mac, tag):\n            raise InvalidSignature(\"Value did not match computed tag.\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/rsa.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport math\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    InvalidSignature, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.openssl.utils import (\n    _calculate_digest_and_algorithm, _check_not_prehashed,\n    _warn_sign_verify_deprecated\n)\nfrom cryptography.hazmat.primitives import hashes\nfrom cryptography.hazmat.primitives.asymmetric import (\n    AsymmetricSignatureContext, AsymmetricVerificationContext, rsa\n)\nfrom cryptography.hazmat.primitives.asymmetric.padding import (\n    AsymmetricPadding, MGF1, OAEP, PKCS1v15, PSS, calculate_max_pss_salt_length\n)\nfrom cryptography.hazmat.primitives.asymmetric.rsa import (\n    RSAPrivateKeyWithSerialization, RSAPublicKeyWithSerialization\n)\n\n\ndef _get_rsa_pss_salt_length(pss, key, hash_algorithm):\n    salt = pss._salt_length\n\n    if salt is MGF1.MAX_LENGTH or salt is PSS.MAX_LENGTH:\n        return calculate_max_pss_salt_length(key, hash_algorithm)\n    else:\n        return salt\n\n\ndef _enc_dec_rsa(backend, key, data, padding):\n    if not isinstance(padding, AsymmetricPadding):\n        raise TypeError(\"Padding must be an instance of AsymmetricPadding.\")\n\n    if isinstance(padding, PKCS1v15):\n        padding_enum = backend._lib.RSA_PKCS1_PADDING\n    elif isinstance(padding, OAEP):\n        padding_enum = backend._lib.RSA_PKCS1_OAEP_PADDING\n\n        if not isinstance(padding._mgf, MGF1):\n            raise UnsupportedAlgorithm(\n                \"Only MGF1 is supported by this backend.\",\n                _Reasons.UNSUPPORTED_MGF\n            )\n\n        if not backend.rsa_padding_supported(padding):\n            raise UnsupportedAlgorithm(\n                \"This combination of padding and hash algorithm is not \"\n                \"supported by this backend.\",\n                _Reasons.UNSUPPORTED_PADDING\n            )\n\n    else:\n        raise UnsupportedAlgorithm(\n            \"{} is not supported by this backend.\".format(\n                padding.name\n            ),\n            _Reasons.UNSUPPORTED_PADDING\n        )\n\n    return _enc_dec_rsa_pkey_ctx(backend, key, data, padding_enum, padding)\n\n\ndef _enc_dec_rsa_pkey_ctx(backend, key, data, padding_enum, padding):\n    if isinstance(key, _RSAPublicKey):\n        init = backend._lib.EVP_PKEY_encrypt_init\n        crypt = backend._lib.EVP_PKEY_encrypt\n    else:\n        init = backend._lib.EVP_PKEY_decrypt_init\n        crypt = backend._lib.EVP_PKEY_decrypt\n\n    pkey_ctx = backend._lib.EVP_PKEY_CTX_new(\n        key._evp_pkey, backend._ffi.NULL\n    )\n    backend.openssl_assert(pkey_ctx != backend._ffi.NULL)\n    pkey_ctx = backend._ffi.gc(pkey_ctx, backend._lib.EVP_PKEY_CTX_free)\n    res = init(pkey_ctx)\n    backend.openssl_assert(res == 1)\n    res = backend._lib.EVP_PKEY_CTX_set_rsa_padding(\n        pkey_ctx, padding_enum)\n    backend.openssl_assert(res > 0)\n    buf_size = backend._lib.EVP_PKEY_size(key._evp_pkey)\n    backend.openssl_assert(buf_size > 0)\n    if (\n        isinstance(padding, OAEP) and\n        backend._lib.Cryptography_HAS_RSA_OAEP_MD\n    ):\n        mgf1_md = backend._evp_md_non_null_from_algorithm(\n            padding._mgf._algorithm)\n        res = backend._lib.EVP_PKEY_CTX_set_rsa_mgf1_md(pkey_ctx, mgf1_md)\n        backend.openssl_assert(res > 0)\n        oaep_md = backend._evp_md_non_null_from_algorithm(padding._algorithm)\n        res = backend._lib.EVP_PKEY_CTX_set_rsa_oaep_md(pkey_ctx, oaep_md)\n        backend.openssl_assert(res > 0)\n\n    if (\n        isinstance(padding, OAEP) and\n        padding._label is not None and\n        len(padding._label) > 0\n    ):\n        # set0_rsa_oaep_label takes ownership of the char * so we need to\n        # copy it into some new memory\n        labelptr = backend._lib.OPENSSL_malloc(len(padding._label))\n        backend.openssl_assert(labelptr != backend._ffi.NULL)\n        backend._ffi.memmove(labelptr, padding._label, len(padding._label))\n        res = backend._lib.EVP_PKEY_CTX_set0_rsa_oaep_label(\n            pkey_ctx, labelptr, len(padding._label)\n        )\n        backend.openssl_assert(res == 1)\n\n    outlen = backend._ffi.new(\"size_t *\", buf_size)\n    buf = backend._ffi.new(\"unsigned char[]\", buf_size)\n    res = crypt(pkey_ctx, buf, outlen, data, len(data))\n    if res <= 0:\n        _handle_rsa_enc_dec_error(backend, key)\n\n    return backend._ffi.buffer(buf)[:outlen[0]]\n\n\ndef _handle_rsa_enc_dec_error(backend, key):\n    errors = backend._consume_errors()\n    backend.openssl_assert(errors)\n    backend.openssl_assert(errors[0].lib == backend._lib.ERR_LIB_RSA)\n    if isinstance(key, _RSAPublicKey):\n        backend.openssl_assert(\n            errors[0].reason == backend._lib.RSA_R_DATA_TOO_LARGE_FOR_KEY_SIZE\n        )\n        raise ValueError(\n            \"Data too long for key size. Encrypt less data or use a \"\n            \"larger key size.\"\n        )\n    else:\n        decoding_errors = [\n            backend._lib.RSA_R_BLOCK_TYPE_IS_NOT_01,\n            backend._lib.RSA_R_BLOCK_TYPE_IS_NOT_02,\n            backend._lib.RSA_R_OAEP_DECODING_ERROR,\n            # Though this error looks similar to the\n            # RSA_R_DATA_TOO_LARGE_FOR_KEY_SIZE, this occurs on decrypts,\n            # rather than on encrypts\n            backend._lib.RSA_R_DATA_TOO_LARGE_FOR_MODULUS,\n        ]\n        if backend._lib.Cryptography_HAS_RSA_R_PKCS_DECODING_ERROR:\n            decoding_errors.append(backend._lib.RSA_R_PKCS_DECODING_ERROR)\n\n        backend.openssl_assert(errors[0].reason in decoding_errors)\n        raise ValueError(\"Decryption failed.\")\n\n\ndef _rsa_sig_determine_padding(backend, key, padding, algorithm):\n    if not isinstance(padding, AsymmetricPadding):\n        raise TypeError(\"Expected provider of AsymmetricPadding.\")\n\n    pkey_size = backend._lib.EVP_PKEY_size(key._evp_pkey)\n    backend.openssl_assert(pkey_size > 0)\n\n    if isinstance(padding, PKCS1v15):\n        padding_enum = backend._lib.RSA_PKCS1_PADDING\n    elif isinstance(padding, PSS):\n        if not isinstance(padding._mgf, MGF1):\n            raise UnsupportedAlgorithm(\n                \"Only MGF1 is supported by this backend.\",\n                _Reasons.UNSUPPORTED_MGF\n            )\n\n        # Size of key in bytes - 2 is the maximum\n        # PSS signature length (salt length is checked later)\n        if pkey_size - algorithm.digest_size - 2 < 0:\n            raise ValueError(\"Digest too large for key size. Use a larger \"\n                             \"key or different digest.\")\n\n        padding_enum = backend._lib.RSA_PKCS1_PSS_PADDING\n    else:\n        raise UnsupportedAlgorithm(\n            \"{} is not supported by this backend.\".format(padding.name),\n            _Reasons.UNSUPPORTED_PADDING\n        )\n\n    return padding_enum\n\n\ndef _rsa_sig_setup(backend, padding, algorithm, key, data, init_func):\n    padding_enum = _rsa_sig_determine_padding(backend, key, padding, algorithm)\n    evp_md = backend._evp_md_non_null_from_algorithm(algorithm)\n    pkey_ctx = backend._lib.EVP_PKEY_CTX_new(key._evp_pkey, backend._ffi.NULL)\n    backend.openssl_assert(pkey_ctx != backend._ffi.NULL)\n    pkey_ctx = backend._ffi.gc(pkey_ctx, backend._lib.EVP_PKEY_CTX_free)\n    res = init_func(pkey_ctx)\n    backend.openssl_assert(res == 1)\n    res = backend._lib.EVP_PKEY_CTX_set_signature_md(pkey_ctx, evp_md)\n    if res == 0:\n        backend._consume_errors()\n        raise UnsupportedAlgorithm(\n            \"{} is not supported by this backend for RSA signing.\".format(\n                algorithm.name\n            ),\n            _Reasons.UNSUPPORTED_HASH\n        )\n    res = backend._lib.EVP_PKEY_CTX_set_rsa_padding(pkey_ctx, padding_enum)\n    backend.openssl_assert(res > 0)\n    if isinstance(padding, PSS):\n        res = backend._lib.EVP_PKEY_CTX_set_rsa_pss_saltlen(\n            pkey_ctx, _get_rsa_pss_salt_length(padding, key, algorithm)\n        )\n        backend.openssl_assert(res > 0)\n\n        mgf1_md = backend._evp_md_non_null_from_algorithm(\n            padding._mgf._algorithm)\n        res = backend._lib.EVP_PKEY_CTX_set_rsa_mgf1_md(pkey_ctx, mgf1_md)\n        backend.openssl_assert(res > 0)\n\n    return pkey_ctx\n\n\ndef _rsa_sig_sign(backend, padding, algorithm, private_key, data):\n    pkey_ctx = _rsa_sig_setup(\n        backend, padding, algorithm, private_key, data,\n        backend._lib.EVP_PKEY_sign_init\n    )\n    buflen = backend._ffi.new(\"size_t *\")\n    res = backend._lib.EVP_PKEY_sign(\n        pkey_ctx,\n        backend._ffi.NULL,\n        buflen,\n        data,\n        len(data)\n    )\n    backend.openssl_assert(res == 1)\n    buf = backend._ffi.new(\"unsigned char[]\", buflen[0])\n    res = backend._lib.EVP_PKEY_sign(\n        pkey_ctx, buf, buflen, data, len(data))\n    if res != 1:\n        errors = backend._consume_errors()\n        backend.openssl_assert(errors[0].lib == backend._lib.ERR_LIB_RSA)\n        if (\n            errors[0].reason ==\n            backend._lib.RSA_R_DATA_TOO_LARGE_FOR_KEY_SIZE\n        ):\n            reason = (\"Salt length too long for key size. Try using \"\n                      \"MAX_LENGTH instead.\")\n        else:\n            backend.openssl_assert(\n                errors[0].reason ==\n                backend._lib.RSA_R_DIGEST_TOO_BIG_FOR_RSA_KEY\n            )\n            reason = \"Digest too large for key size. Use a larger key.\"\n        raise ValueError(reason)\n\n    return backend._ffi.buffer(buf)[:]\n\n\ndef _rsa_sig_verify(backend, padding, algorithm, public_key, signature, data):\n    pkey_ctx = _rsa_sig_setup(\n        backend, padding, algorithm, public_key, data,\n        backend._lib.EVP_PKEY_verify_init\n    )\n    res = backend._lib.EVP_PKEY_verify(\n        pkey_ctx, signature, len(signature), data, len(data)\n    )\n    # The previous call can return negative numbers in the event of an\n    # error. This is not a signature failure but we need to fail if it\n    # occurs.\n    backend.openssl_assert(res >= 0)\n    if res == 0:\n        backend._consume_errors()\n        raise InvalidSignature\n\n\n@utils.register_interface(AsymmetricSignatureContext)\nclass _RSASignatureContext(object):\n    def __init__(self, backend, private_key, padding, algorithm):\n        self._backend = backend\n        self._private_key = private_key\n\n        # We now call _rsa_sig_determine_padding in _rsa_sig_setup. However\n        # we need to make a pointless call to it here so we maintain the\n        # API of erroring on init with this context if the values are invalid.\n        _rsa_sig_determine_padding(backend, private_key, padding, algorithm)\n        self._padding = padding\n        self._algorithm = algorithm\n        self._hash_ctx = hashes.Hash(self._algorithm, self._backend)\n\n    def update(self, data):\n        self._hash_ctx.update(data)\n\n    def finalize(self):\n        return _rsa_sig_sign(\n            self._backend,\n            self._padding,\n            self._algorithm,\n            self._private_key,\n            self._hash_ctx.finalize()\n        )\n\n\n@utils.register_interface(AsymmetricVerificationContext)\nclass _RSAVerificationContext(object):\n    def __init__(self, backend, public_key, signature, padding, algorithm):\n        self._backend = backend\n        self._public_key = public_key\n        self._signature = signature\n        self._padding = padding\n        # We now call _rsa_sig_determine_padding in _rsa_sig_setup. However\n        # we need to make a pointless call to it here so we maintain the\n        # API of erroring on init with this context if the values are invalid.\n        _rsa_sig_determine_padding(backend, public_key, padding, algorithm)\n\n        padding = padding\n        self._algorithm = algorithm\n        self._hash_ctx = hashes.Hash(self._algorithm, self._backend)\n\n    def update(self, data):\n        self._hash_ctx.update(data)\n\n    def verify(self):\n        return _rsa_sig_verify(\n            self._backend,\n            self._padding,\n            self._algorithm,\n            self._public_key,\n            self._signature,\n            self._hash_ctx.finalize()\n        )\n\n\n@utils.register_interface(RSAPrivateKeyWithSerialization)\nclass _RSAPrivateKey(object):\n    def __init__(self, backend, rsa_cdata, evp_pkey):\n        self._backend = backend\n        self._rsa_cdata = rsa_cdata\n        self._evp_pkey = evp_pkey\n\n        n = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.RSA_get0_key(\n            self._rsa_cdata, n, self._backend._ffi.NULL,\n            self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(n[0] != self._backend._ffi.NULL)\n        self._key_size = self._backend._lib.BN_num_bits(n[0])\n\n    key_size = utils.read_only_property(\"_key_size\")\n\n    def signer(self, padding, algorithm):\n        _warn_sign_verify_deprecated()\n        _check_not_prehashed(algorithm)\n        return _RSASignatureContext(self._backend, self, padding, algorithm)\n\n    def decrypt(self, ciphertext, padding):\n        key_size_bytes = int(math.ceil(self.key_size / 8.0))\n        if key_size_bytes != len(ciphertext):\n            raise ValueError(\"Ciphertext length must be equal to key size.\")\n\n        return _enc_dec_rsa(self._backend, self, ciphertext, padding)\n\n    def public_key(self):\n        ctx = self._backend._lib.RSAPublicKey_dup(self._rsa_cdata)\n        self._backend.openssl_assert(ctx != self._backend._ffi.NULL)\n        ctx = self._backend._ffi.gc(ctx, self._backend._lib.RSA_free)\n        res = self._backend._lib.RSA_blinding_on(ctx, self._backend._ffi.NULL)\n        self._backend.openssl_assert(res == 1)\n        evp_pkey = self._backend._rsa_cdata_to_evp_pkey(ctx)\n        return _RSAPublicKey(self._backend, ctx, evp_pkey)\n\n    def private_numbers(self):\n        n = self._backend._ffi.new(\"BIGNUM **\")\n        e = self._backend._ffi.new(\"BIGNUM **\")\n        d = self._backend._ffi.new(\"BIGNUM **\")\n        p = self._backend._ffi.new(\"BIGNUM **\")\n        q = self._backend._ffi.new(\"BIGNUM **\")\n        dmp1 = self._backend._ffi.new(\"BIGNUM **\")\n        dmq1 = self._backend._ffi.new(\"BIGNUM **\")\n        iqmp = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.RSA_get0_key(self._rsa_cdata, n, e, d)\n        self._backend.openssl_assert(n[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(e[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(d[0] != self._backend._ffi.NULL)\n        self._backend._lib.RSA_get0_factors(self._rsa_cdata, p, q)\n        self._backend.openssl_assert(p[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(q[0] != self._backend._ffi.NULL)\n        self._backend._lib.RSA_get0_crt_params(\n            self._rsa_cdata, dmp1, dmq1, iqmp\n        )\n        self._backend.openssl_assert(dmp1[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(dmq1[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(iqmp[0] != self._backend._ffi.NULL)\n        return rsa.RSAPrivateNumbers(\n            p=self._backend._bn_to_int(p[0]),\n            q=self._backend._bn_to_int(q[0]),\n            d=self._backend._bn_to_int(d[0]),\n            dmp1=self._backend._bn_to_int(dmp1[0]),\n            dmq1=self._backend._bn_to_int(dmq1[0]),\n            iqmp=self._backend._bn_to_int(iqmp[0]),\n            public_numbers=rsa.RSAPublicNumbers(\n                e=self._backend._bn_to_int(e[0]),\n                n=self._backend._bn_to_int(n[0]),\n            )\n        )\n\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        return self._backend._private_key_bytes(\n            encoding,\n            format,\n            encryption_algorithm,\n            self._evp_pkey,\n            self._rsa_cdata\n        )\n\n    def sign(self, data, padding, algorithm):\n        data, algorithm = _calculate_digest_and_algorithm(\n            self._backend, data, algorithm\n        )\n        return _rsa_sig_sign(self._backend, padding, algorithm, self, data)\n\n\n@utils.register_interface(RSAPublicKeyWithSerialization)\nclass _RSAPublicKey(object):\n    def __init__(self, backend, rsa_cdata, evp_pkey):\n        self._backend = backend\n        self._rsa_cdata = rsa_cdata\n        self._evp_pkey = evp_pkey\n\n        n = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.RSA_get0_key(\n            self._rsa_cdata, n, self._backend._ffi.NULL,\n            self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(n[0] != self._backend._ffi.NULL)\n        self._key_size = self._backend._lib.BN_num_bits(n[0])\n\n    key_size = utils.read_only_property(\"_key_size\")\n\n    def verifier(self, signature, padding, algorithm):\n        _warn_sign_verify_deprecated()\n        utils._check_bytes(\"signature\", signature)\n\n        _check_not_prehashed(algorithm)\n        return _RSAVerificationContext(\n            self._backend, self, signature, padding, algorithm\n        )\n\n    def encrypt(self, plaintext, padding):\n        return _enc_dec_rsa(self._backend, self, plaintext, padding)\n\n    def public_numbers(self):\n        n = self._backend._ffi.new(\"BIGNUM **\")\n        e = self._backend._ffi.new(\"BIGNUM **\")\n        self._backend._lib.RSA_get0_key(\n            self._rsa_cdata, n, e, self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(n[0] != self._backend._ffi.NULL)\n        self._backend.openssl_assert(e[0] != self._backend._ffi.NULL)\n        return rsa.RSAPublicNumbers(\n            e=self._backend._bn_to_int(e[0]),\n            n=self._backend._bn_to_int(n[0]),\n        )\n\n    def public_bytes(self, encoding, format):\n        return self._backend._public_key_bytes(\n            encoding,\n            format,\n            self,\n            self._evp_pkey,\n            self._rsa_cdata\n        )\n\n    def verify(self, signature, data, padding, algorithm):\n        data, algorithm = _calculate_digest_and_algorithm(\n            self._backend, data, algorithm\n        )\n        return _rsa_sig_verify(\n            self._backend, padding, algorithm, self, signature, data\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/utils.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport warnings\n\nfrom cryptography import utils\nfrom cryptography.hazmat.primitives import hashes\nfrom cryptography.hazmat.primitives.asymmetric.utils import Prehashed\n\n\ndef _evp_pkey_derive(backend, evp_pkey, peer_public_key):\n    ctx = backend._lib.EVP_PKEY_CTX_new(evp_pkey, backend._ffi.NULL)\n    backend.openssl_assert(ctx != backend._ffi.NULL)\n    ctx = backend._ffi.gc(ctx, backend._lib.EVP_PKEY_CTX_free)\n    res = backend._lib.EVP_PKEY_derive_init(ctx)\n    backend.openssl_assert(res == 1)\n    res = backend._lib.EVP_PKEY_derive_set_peer(\n        ctx, peer_public_key._evp_pkey\n    )\n    backend.openssl_assert(res == 1)\n    keylen = backend._ffi.new(\"size_t *\")\n    res = backend._lib.EVP_PKEY_derive(ctx, backend._ffi.NULL, keylen)\n    backend.openssl_assert(res == 1)\n    backend.openssl_assert(keylen[0] > 0)\n    buf = backend._ffi.new(\"unsigned char[]\", keylen[0])\n    res = backend._lib.EVP_PKEY_derive(ctx, buf, keylen)\n    if res != 1:\n        raise ValueError(\n            \"Null shared key derived from public/private pair.\"\n        )\n\n    return backend._ffi.buffer(buf, keylen[0])[:]\n\n\ndef _calculate_digest_and_algorithm(backend, data, algorithm):\n    if not isinstance(algorithm, Prehashed):\n        hash_ctx = hashes.Hash(algorithm, backend)\n        hash_ctx.update(data)\n        data = hash_ctx.finalize()\n    else:\n        algorithm = algorithm._algorithm\n\n    if len(data) != algorithm.digest_size:\n        raise ValueError(\n            \"The provided data must be the same length as the hash \"\n            \"algorithm's digest size.\"\n        )\n\n    return (data, algorithm)\n\n\ndef _check_not_prehashed(signature_algorithm):\n    if isinstance(signature_algorithm, Prehashed):\n        raise TypeError(\n            \"Prehashed is only supported in the sign and verify methods. \"\n            \"It cannot be used with signer or verifier.\"\n        )\n\n\ndef _warn_sign_verify_deprecated():\n    warnings.warn(\n        \"signer and verifier have been deprecated. Please use sign \"\n        \"and verify instead.\",\n        utils.PersistentlyDeprecated2017,\n        stacklevel=3\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/x25519.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport warnings\n\nfrom cryptography import utils\nfrom cryptography.hazmat.backends.openssl.utils import _evp_pkey_derive\nfrom cryptography.hazmat.primitives import serialization\nfrom cryptography.hazmat.primitives.asymmetric.x25519 import (\n    X25519PrivateKey, X25519PublicKey\n)\n\n\n_X25519_KEY_SIZE = 32\n\n\n@utils.register_interface(X25519PublicKey)\nclass _X25519PublicKey(object):\n    def __init__(self, backend, evp_pkey):\n        self._backend = backend\n        self._evp_pkey = evp_pkey\n\n    def public_bytes(self, encoding=None, format=None):\n        if encoding is None or format is None:\n            if encoding is not None or format is not None:\n                raise ValueError(\"Both encoding and format are required\")\n            else:\n                warnings.warn(\n                    \"public_bytes now requires encoding and format arguments. \"\n                    \"Support for calling without arguments will be removed in \"\n                    \"cryptography 2.7\",\n                    utils.DeprecatedIn25,\n                )\n                encoding = serialization.Encoding.Raw\n                format = serialization.PublicFormat.Raw\n        if (\n            encoding is serialization.Encoding.Raw or\n            format is serialization.PublicFormat.Raw\n        ):\n            if (\n                encoding is not serialization.Encoding.Raw or\n                format is not serialization.PublicFormat.Raw\n            ):\n                raise ValueError(\n                    \"When using Raw both encoding and format must be Raw\"\n                )\n\n            return self._raw_public_bytes()\n\n        if (\n            encoding in serialization._PEM_DER and\n            format is not serialization.PublicFormat.SubjectPublicKeyInfo\n        ):\n            raise ValueError(\n                \"format must be SubjectPublicKeyInfo when encoding is PEM or \"\n                \"DER\"\n            )\n\n        return self._backend._public_key_bytes(\n            encoding, format, self, self._evp_pkey, None\n        )\n\n    def _raw_public_bytes(self):\n        ucharpp = self._backend._ffi.new(\"unsigned char **\")\n        res = self._backend._lib.EVP_PKEY_get1_tls_encodedpoint(\n            self._evp_pkey, ucharpp\n        )\n        self._backend.openssl_assert(res == 32)\n        self._backend.openssl_assert(ucharpp[0] != self._backend._ffi.NULL)\n        data = self._backend._ffi.gc(\n            ucharpp[0], self._backend._lib.OPENSSL_free\n        )\n        return self._backend._ffi.buffer(data, res)[:]\n\n\n@utils.register_interface(X25519PrivateKey)\nclass _X25519PrivateKey(object):\n    def __init__(self, backend, evp_pkey):\n        self._backend = backend\n        self._evp_pkey = evp_pkey\n\n    def public_key(self):\n        bio = self._backend._create_mem_bio_gc()\n        res = self._backend._lib.i2d_PUBKEY_bio(bio, self._evp_pkey)\n        self._backend.openssl_assert(res == 1)\n        evp_pkey = self._backend._lib.d2i_PUBKEY_bio(\n            bio, self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(evp_pkey != self._backend._ffi.NULL)\n        evp_pkey = self._backend._ffi.gc(\n            evp_pkey, self._backend._lib.EVP_PKEY_free\n        )\n        return _X25519PublicKey(self._backend, evp_pkey)\n\n    def exchange(self, peer_public_key):\n        if not isinstance(peer_public_key, X25519PublicKey):\n            raise TypeError(\"peer_public_key must be X25519PublicKey.\")\n\n        return _evp_pkey_derive(\n            self._backend, self._evp_pkey, peer_public_key\n        )\n\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        if (\n            encoding is serialization.Encoding.Raw or\n            format is serialization.PublicFormat.Raw\n        ):\n            if (\n                format is not serialization.PrivateFormat.Raw or\n                encoding is not serialization.Encoding.Raw or not\n                isinstance(encryption_algorithm, serialization.NoEncryption)\n            ):\n                raise ValueError(\n                    \"When using Raw both encoding and format must be Raw \"\n                    \"and encryption_algorithm must be NoEncryption()\"\n                )\n\n            return self._raw_private_bytes()\n\n        if (\n            encoding in serialization._PEM_DER and\n            format is not serialization.PrivateFormat.PKCS8\n        ):\n            raise ValueError(\n                \"format must be PKCS8 when encoding is PEM or DER\"\n            )\n\n        return self._backend._private_key_bytes(\n            encoding, format, encryption_algorithm, self._evp_pkey, None\n        )\n\n    def _raw_private_bytes(self):\n        # When we drop support for CRYPTOGRAPHY_OPENSSL_LESS_THAN_111 we can\n        # switch this to EVP_PKEY_new_raw_private_key\n        # The trick we use here is serializing to a PKCS8 key and just\n        # using the last 32 bytes, which is the key itself.\n        bio = self._backend._create_mem_bio_gc()\n        res = self._backend._lib.i2d_PKCS8PrivateKey_bio(\n            bio, self._evp_pkey,\n            self._backend._ffi.NULL, self._backend._ffi.NULL,\n            0, self._backend._ffi.NULL, self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(res == 1)\n        pkcs8 = self._backend._read_mem_bio(bio)\n        self._backend.openssl_assert(len(pkcs8) == 48)\n        return pkcs8[-_X25519_KEY_SIZE:]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/x448.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import utils\nfrom cryptography.hazmat.backends.openssl.utils import _evp_pkey_derive\nfrom cryptography.hazmat.primitives import serialization\nfrom cryptography.hazmat.primitives.asymmetric.x448 import (\n    X448PrivateKey, X448PublicKey\n)\n\n_X448_KEY_SIZE = 56\n\n\n@utils.register_interface(X448PublicKey)\nclass _X448PublicKey(object):\n    def __init__(self, backend, evp_pkey):\n        self._backend = backend\n        self._evp_pkey = evp_pkey\n\n    def public_bytes(self, encoding, format):\n        if (\n            encoding is serialization.Encoding.Raw or\n            format is serialization.PublicFormat.Raw\n        ):\n            if (\n                encoding is not serialization.Encoding.Raw or\n                format is not serialization.PublicFormat.Raw\n            ):\n                raise ValueError(\n                    \"When using Raw both encoding and format must be Raw\"\n                )\n\n            return self._raw_public_bytes()\n\n        if (\n            encoding in serialization._PEM_DER and\n            format is not serialization.PublicFormat.SubjectPublicKeyInfo\n        ):\n            raise ValueError(\n                \"format must be SubjectPublicKeyInfo when encoding is PEM or \"\n                \"DER\"\n            )\n\n        return self._backend._public_key_bytes(\n            encoding, format, self, self._evp_pkey, None\n        )\n\n    def _raw_public_bytes(self):\n        buf = self._backend._ffi.new(\"unsigned char []\", _X448_KEY_SIZE)\n        buflen = self._backend._ffi.new(\"size_t *\", _X448_KEY_SIZE)\n        res = self._backend._lib.EVP_PKEY_get_raw_public_key(\n            self._evp_pkey, buf, buflen\n        )\n        self._backend.openssl_assert(res == 1)\n        self._backend.openssl_assert(buflen[0] == _X448_KEY_SIZE)\n        return self._backend._ffi.buffer(buf, _X448_KEY_SIZE)[:]\n\n\n@utils.register_interface(X448PrivateKey)\nclass _X448PrivateKey(object):\n    def __init__(self, backend, evp_pkey):\n        self._backend = backend\n        self._evp_pkey = evp_pkey\n\n    def public_key(self):\n        buf = self._backend._ffi.new(\"unsigned char []\", _X448_KEY_SIZE)\n        buflen = self._backend._ffi.new(\"size_t *\", _X448_KEY_SIZE)\n        res = self._backend._lib.EVP_PKEY_get_raw_public_key(\n            self._evp_pkey, buf, buflen\n        )\n        self._backend.openssl_assert(res == 1)\n        self._backend.openssl_assert(buflen[0] == _X448_KEY_SIZE)\n        return self._backend.x448_load_public_bytes(buf)\n\n    def exchange(self, peer_public_key):\n        if not isinstance(peer_public_key, X448PublicKey):\n            raise TypeError(\"peer_public_key must be X448PublicKey.\")\n\n        return _evp_pkey_derive(\n            self._backend, self._evp_pkey, peer_public_key\n        )\n\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        if (\n            encoding is serialization.Encoding.Raw or\n            format is serialization.PublicFormat.Raw\n        ):\n            if (\n                format is not serialization.PrivateFormat.Raw or\n                encoding is not serialization.Encoding.Raw or not\n                isinstance(encryption_algorithm, serialization.NoEncryption)\n            ):\n                raise ValueError(\n                    \"When using Raw both encoding and format must be Raw \"\n                    \"and encryption_algorithm must be NoEncryption()\"\n                )\n\n            return self._raw_private_bytes()\n\n        if (\n            encoding in serialization._PEM_DER and\n            format is not serialization.PrivateFormat.PKCS8\n        ):\n            raise ValueError(\n                \"format must be PKCS8 when encoding is PEM or DER\"\n            )\n\n        return self._backend._private_key_bytes(\n            encoding, format, encryption_algorithm, self._evp_pkey, None\n        )\n\n    def _raw_private_bytes(self):\n        buf = self._backend._ffi.new(\"unsigned char []\", _X448_KEY_SIZE)\n        buflen = self._backend._ffi.new(\"size_t *\", _X448_KEY_SIZE)\n        res = self._backend._lib.EVP_PKEY_get_raw_private_key(\n            self._evp_pkey, buf, buflen\n        )\n        self._backend.openssl_assert(res == 1)\n        self._backend.openssl_assert(buflen[0] == _X448_KEY_SIZE)\n        return self._backend._ffi.buffer(buf, _X448_KEY_SIZE)[:]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/backends/openssl/x509.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport datetime\nimport operator\n\nfrom cryptography import utils, x509\nfrom cryptography.exceptions import UnsupportedAlgorithm\nfrom cryptography.hazmat.backends.openssl.decode_asn1 import (\n    _CERTIFICATE_EXTENSION_PARSER, _CERTIFICATE_EXTENSION_PARSER_NO_SCT,\n    _CRL_EXTENSION_PARSER, _CSR_EXTENSION_PARSER,\n    _REVOKED_CERTIFICATE_EXTENSION_PARSER, _asn1_integer_to_int,\n    _asn1_string_to_bytes, _decode_x509_name, _obj2txt, _parse_asn1_time\n)\nfrom cryptography.hazmat.backends.openssl.encode_asn1 import (\n    _encode_asn1_int_gc\n)\nfrom cryptography.hazmat.primitives import hashes, serialization\nfrom cryptography.hazmat.primitives.asymmetric import dsa, ec, rsa\n\n\n@utils.register_interface(x509.Certificate)\nclass _Certificate(object):\n    def __init__(self, backend, x509):\n        self._backend = backend\n        self._x509 = x509\n\n    def __repr__(self):\n        return \"<Certificate(subject={}, ...)>\".format(self.subject)\n\n    def __eq__(self, other):\n        if not isinstance(other, x509.Certificate):\n            return NotImplemented\n\n        res = self._backend._lib.X509_cmp(self._x509, other._x509)\n        return res == 0\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.public_bytes(serialization.Encoding.DER))\n\n    def fingerprint(self, algorithm):\n        h = hashes.Hash(algorithm, self._backend)\n        h.update(self.public_bytes(serialization.Encoding.DER))\n        return h.finalize()\n\n    @property\n    def version(self):\n        version = self._backend._lib.X509_get_version(self._x509)\n        if version == 0:\n            return x509.Version.v1\n        elif version == 2:\n            return x509.Version.v3\n        else:\n            raise x509.InvalidVersion(\n                \"{} is not a valid X509 version\".format(version), version\n            )\n\n    @property\n    def serial_number(self):\n        asn1_int = self._backend._lib.X509_get_serialNumber(self._x509)\n        self._backend.openssl_assert(asn1_int != self._backend._ffi.NULL)\n        return _asn1_integer_to_int(self._backend, asn1_int)\n\n    def public_key(self):\n        pkey = self._backend._lib.X509_get_pubkey(self._x509)\n        if pkey == self._backend._ffi.NULL:\n            # Remove errors from the stack.\n            self._backend._consume_errors()\n            raise ValueError(\"Certificate public key is of an unknown type\")\n\n        pkey = self._backend._ffi.gc(pkey, self._backend._lib.EVP_PKEY_free)\n\n        return self._backend._evp_pkey_to_public_key(pkey)\n\n    @property\n    def not_valid_before(self):\n        asn1_time = self._backend._lib.X509_getm_notBefore(self._x509)\n        return _parse_asn1_time(self._backend, asn1_time)\n\n    @property\n    def not_valid_after(self):\n        asn1_time = self._backend._lib.X509_getm_notAfter(self._x509)\n        return _parse_asn1_time(self._backend, asn1_time)\n\n    @property\n    def issuer(self):\n        issuer = self._backend._lib.X509_get_issuer_name(self._x509)\n        self._backend.openssl_assert(issuer != self._backend._ffi.NULL)\n        return _decode_x509_name(self._backend, issuer)\n\n    @property\n    def subject(self):\n        subject = self._backend._lib.X509_get_subject_name(self._x509)\n        self._backend.openssl_assert(subject != self._backend._ffi.NULL)\n        return _decode_x509_name(self._backend, subject)\n\n    @property\n    def signature_hash_algorithm(self):\n        oid = self.signature_algorithm_oid\n        try:\n            return x509._SIG_OIDS_TO_HASH[oid]\n        except KeyError:\n            raise UnsupportedAlgorithm(\n                \"Signature algorithm OID:{} not recognized\".format(oid)\n            )\n\n    @property\n    def signature_algorithm_oid(self):\n        alg = self._backend._ffi.new(\"X509_ALGOR **\")\n        self._backend._lib.X509_get0_signature(\n            self._backend._ffi.NULL, alg, self._x509\n        )\n        self._backend.openssl_assert(alg[0] != self._backend._ffi.NULL)\n        oid = _obj2txt(self._backend, alg[0].algorithm)\n        return x509.ObjectIdentifier(oid)\n\n    @utils.cached_property\n    def extensions(self):\n        if self._backend._lib.CRYPTOGRAPHY_OPENSSL_110_OR_GREATER:\n            return _CERTIFICATE_EXTENSION_PARSER.parse(\n                self._backend, self._x509\n            )\n        else:\n            return _CERTIFICATE_EXTENSION_PARSER_NO_SCT.parse(\n                self._backend, self._x509\n            )\n\n    @property\n    def signature(self):\n        sig = self._backend._ffi.new(\"ASN1_BIT_STRING **\")\n        self._backend._lib.X509_get0_signature(\n            sig, self._backend._ffi.NULL, self._x509\n        )\n        self._backend.openssl_assert(sig[0] != self._backend._ffi.NULL)\n        return _asn1_string_to_bytes(self._backend, sig[0])\n\n    @property\n    def tbs_certificate_bytes(self):\n        pp = self._backend._ffi.new(\"unsigned char **\")\n        res = self._backend._lib.i2d_re_X509_tbs(self._x509, pp)\n        self._backend.openssl_assert(res > 0)\n        pp = self._backend._ffi.gc(\n            pp, lambda pointer: self._backend._lib.OPENSSL_free(pointer[0])\n        )\n        return self._backend._ffi.buffer(pp[0], res)[:]\n\n    def public_bytes(self, encoding):\n        bio = self._backend._create_mem_bio_gc()\n        if encoding is serialization.Encoding.PEM:\n            res = self._backend._lib.PEM_write_bio_X509(bio, self._x509)\n        elif encoding is serialization.Encoding.DER:\n            res = self._backend._lib.i2d_X509_bio(bio, self._x509)\n        else:\n            raise TypeError(\"encoding must be an item from the Encoding enum\")\n\n        self._backend.openssl_assert(res == 1)\n        return self._backend._read_mem_bio(bio)\n\n\n@utils.register_interface(x509.RevokedCertificate)\nclass _RevokedCertificate(object):\n    def __init__(self, backend, crl, x509_revoked):\n        self._backend = backend\n        # The X509_REVOKED_value is a X509_REVOKED * that has\n        # no reference counting. This means when X509_CRL_free is\n        # called then the CRL and all X509_REVOKED * are freed. Since\n        # you can retain a reference to a single revoked certificate\n        # and let the CRL fall out of scope we need to retain a\n        # private reference to the CRL inside the RevokedCertificate\n        # object to prevent the gc from being called inappropriately.\n        self._crl = crl\n        self._x509_revoked = x509_revoked\n\n    @property\n    def serial_number(self):\n        asn1_int = self._backend._lib.X509_REVOKED_get0_serialNumber(\n            self._x509_revoked\n        )\n        self._backend.openssl_assert(asn1_int != self._backend._ffi.NULL)\n        return _asn1_integer_to_int(self._backend, asn1_int)\n\n    @property\n    def revocation_date(self):\n        return _parse_asn1_time(\n            self._backend,\n            self._backend._lib.X509_REVOKED_get0_revocationDate(\n                self._x509_revoked\n            )\n        )\n\n    @utils.cached_property\n    def extensions(self):\n        return _REVOKED_CERTIFICATE_EXTENSION_PARSER.parse(\n            self._backend, self._x509_revoked\n        )\n\n\n@utils.register_interface(x509.CertificateRevocationList)\nclass _CertificateRevocationList(object):\n    def __init__(self, backend, x509_crl):\n        self._backend = backend\n        self._x509_crl = x509_crl\n\n    def __eq__(self, other):\n        if not isinstance(other, x509.CertificateRevocationList):\n            return NotImplemented\n\n        res = self._backend._lib.X509_CRL_cmp(self._x509_crl, other._x509_crl)\n        return res == 0\n\n    def __ne__(self, other):\n        return not self == other\n\n    def fingerprint(self, algorithm):\n        h = hashes.Hash(algorithm, self._backend)\n        bio = self._backend._create_mem_bio_gc()\n        res = self._backend._lib.i2d_X509_CRL_bio(\n            bio, self._x509_crl\n        )\n        self._backend.openssl_assert(res == 1)\n        der = self._backend._read_mem_bio(bio)\n        h.update(der)\n        return h.finalize()\n\n    @utils.cached_property\n    def _sorted_crl(self):\n        # X509_CRL_get0_by_serial sorts in place, which breaks a variety of\n        # things we don't want to break (like iteration and the signature).\n        # Let's dupe it and sort that instead.\n        dup = self._backend._lib.X509_CRL_dup(self._x509_crl)\n        self._backend.openssl_assert(dup != self._backend._ffi.NULL)\n        dup = self._backend._ffi.gc(dup, self._backend._lib.X509_CRL_free)\n        return dup\n\n    def get_revoked_certificate_by_serial_number(self, serial_number):\n        revoked = self._backend._ffi.new(\"X509_REVOKED **\")\n        asn1_int = _encode_asn1_int_gc(self._backend, serial_number)\n        res = self._backend._lib.X509_CRL_get0_by_serial(\n            self._sorted_crl, revoked, asn1_int\n        )\n        if res == 0:\n            return None\n        else:\n            self._backend.openssl_assert(\n                revoked[0] != self._backend._ffi.NULL\n            )\n            return _RevokedCertificate(\n                self._backend, self._sorted_crl, revoked[0]\n            )\n\n    @property\n    def signature_hash_algorithm(self):\n        oid = self.signature_algorithm_oid\n        try:\n            return x509._SIG_OIDS_TO_HASH[oid]\n        except KeyError:\n            raise UnsupportedAlgorithm(\n                \"Signature algorithm OID:{} not recognized\".format(oid)\n            )\n\n    @property\n    def signature_algorithm_oid(self):\n        alg = self._backend._ffi.new(\"X509_ALGOR **\")\n        self._backend._lib.X509_CRL_get0_signature(\n            self._x509_crl, self._backend._ffi.NULL, alg\n        )\n        self._backend.openssl_assert(alg[0] != self._backend._ffi.NULL)\n        oid = _obj2txt(self._backend, alg[0].algorithm)\n        return x509.ObjectIdentifier(oid)\n\n    @property\n    def issuer(self):\n        issuer = self._backend._lib.X509_CRL_get_issuer(self._x509_crl)\n        self._backend.openssl_assert(issuer != self._backend._ffi.NULL)\n        return _decode_x509_name(self._backend, issuer)\n\n    @property\n    def next_update(self):\n        nu = self._backend._lib.X509_CRL_get_nextUpdate(self._x509_crl)\n        self._backend.openssl_assert(nu != self._backend._ffi.NULL)\n        return _parse_asn1_time(self._backend, nu)\n\n    @property\n    def last_update(self):\n        lu = self._backend._lib.X509_CRL_get_lastUpdate(self._x509_crl)\n        self._backend.openssl_assert(lu != self._backend._ffi.NULL)\n        return _parse_asn1_time(self._backend, lu)\n\n    @property\n    def signature(self):\n        sig = self._backend._ffi.new(\"ASN1_BIT_STRING **\")\n        self._backend._lib.X509_CRL_get0_signature(\n            self._x509_crl, sig, self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(sig[0] != self._backend._ffi.NULL)\n        return _asn1_string_to_bytes(self._backend, sig[0])\n\n    @property\n    def tbs_certlist_bytes(self):\n        pp = self._backend._ffi.new(\"unsigned char **\")\n        res = self._backend._lib.i2d_re_X509_CRL_tbs(self._x509_crl, pp)\n        self._backend.openssl_assert(res > 0)\n        pp = self._backend._ffi.gc(\n            pp, lambda pointer: self._backend._lib.OPENSSL_free(pointer[0])\n        )\n        return self._backend._ffi.buffer(pp[0], res)[:]\n\n    def public_bytes(self, encoding):\n        bio = self._backend._create_mem_bio_gc()\n        if encoding is serialization.Encoding.PEM:\n            res = self._backend._lib.PEM_write_bio_X509_CRL(\n                bio, self._x509_crl\n            )\n        elif encoding is serialization.Encoding.DER:\n            res = self._backend._lib.i2d_X509_CRL_bio(bio, self._x509_crl)\n        else:\n            raise TypeError(\"encoding must be an item from the Encoding enum\")\n\n        self._backend.openssl_assert(res == 1)\n        return self._backend._read_mem_bio(bio)\n\n    def _revoked_cert(self, idx):\n        revoked = self._backend._lib.X509_CRL_get_REVOKED(self._x509_crl)\n        r = self._backend._lib.sk_X509_REVOKED_value(revoked, idx)\n        self._backend.openssl_assert(r != self._backend._ffi.NULL)\n        return _RevokedCertificate(self._backend, self, r)\n\n    def __iter__(self):\n        for i in range(len(self)):\n            yield self._revoked_cert(i)\n\n    def __getitem__(self, idx):\n        if isinstance(idx, slice):\n            start, stop, step = idx.indices(len(self))\n            return [self._revoked_cert(i) for i in range(start, stop, step)]\n        else:\n            idx = operator.index(idx)\n            if idx < 0:\n                idx += len(self)\n            if not 0 <= idx < len(self):\n                raise IndexError\n            return self._revoked_cert(idx)\n\n    def __len__(self):\n        revoked = self._backend._lib.X509_CRL_get_REVOKED(self._x509_crl)\n        if revoked == self._backend._ffi.NULL:\n            return 0\n        else:\n            return self._backend._lib.sk_X509_REVOKED_num(revoked)\n\n    @utils.cached_property\n    def extensions(self):\n        return _CRL_EXTENSION_PARSER.parse(self._backend, self._x509_crl)\n\n    def is_signature_valid(self, public_key):\n        if not isinstance(public_key, (dsa.DSAPublicKey, rsa.RSAPublicKey,\n                                       ec.EllipticCurvePublicKey)):\n            raise TypeError('Expecting one of DSAPublicKey, RSAPublicKey,'\n                            ' or EllipticCurvePublicKey.')\n        res = self._backend._lib.X509_CRL_verify(\n            self._x509_crl, public_key._evp_pkey\n        )\n\n        if res != 1:\n            self._backend._consume_errors()\n            return False\n\n        return True\n\n\n@utils.register_interface(x509.CertificateSigningRequest)\nclass _CertificateSigningRequest(object):\n    def __init__(self, backend, x509_req):\n        self._backend = backend\n        self._x509_req = x509_req\n\n    def __eq__(self, other):\n        if not isinstance(other, _CertificateSigningRequest):\n            return NotImplemented\n\n        self_bytes = self.public_bytes(serialization.Encoding.DER)\n        other_bytes = other.public_bytes(serialization.Encoding.DER)\n        return self_bytes == other_bytes\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.public_bytes(serialization.Encoding.DER))\n\n    def public_key(self):\n        pkey = self._backend._lib.X509_REQ_get_pubkey(self._x509_req)\n        self._backend.openssl_assert(pkey != self._backend._ffi.NULL)\n        pkey = self._backend._ffi.gc(pkey, self._backend._lib.EVP_PKEY_free)\n        return self._backend._evp_pkey_to_public_key(pkey)\n\n    @property\n    def subject(self):\n        subject = self._backend._lib.X509_REQ_get_subject_name(self._x509_req)\n        self._backend.openssl_assert(subject != self._backend._ffi.NULL)\n        return _decode_x509_name(self._backend, subject)\n\n    @property\n    def signature_hash_algorithm(self):\n        oid = self.signature_algorithm_oid\n        try:\n            return x509._SIG_OIDS_TO_HASH[oid]\n        except KeyError:\n            raise UnsupportedAlgorithm(\n                \"Signature algorithm OID:{} not recognized\".format(oid)\n            )\n\n    @property\n    def signature_algorithm_oid(self):\n        alg = self._backend._ffi.new(\"X509_ALGOR **\")\n        self._backend._lib.X509_REQ_get0_signature(\n            self._x509_req, self._backend._ffi.NULL, alg\n        )\n        self._backend.openssl_assert(alg[0] != self._backend._ffi.NULL)\n        oid = _obj2txt(self._backend, alg[0].algorithm)\n        return x509.ObjectIdentifier(oid)\n\n    @utils.cached_property\n    def extensions(self):\n        x509_exts = self._backend._lib.X509_REQ_get_extensions(self._x509_req)\n        x509_exts = self._backend._ffi.gc(\n            x509_exts,\n            lambda x: self._backend._lib.sk_X509_EXTENSION_pop_free(\n                x, self._backend._ffi.addressof(\n                    self._backend._lib._original_lib, \"X509_EXTENSION_free\"\n                )\n            )\n        )\n        return _CSR_EXTENSION_PARSER.parse(self._backend, x509_exts)\n\n    def public_bytes(self, encoding):\n        bio = self._backend._create_mem_bio_gc()\n        if encoding is serialization.Encoding.PEM:\n            res = self._backend._lib.PEM_write_bio_X509_REQ(\n                bio, self._x509_req\n            )\n        elif encoding is serialization.Encoding.DER:\n            res = self._backend._lib.i2d_X509_REQ_bio(bio, self._x509_req)\n        else:\n            raise TypeError(\"encoding must be an item from the Encoding enum\")\n\n        self._backend.openssl_assert(res == 1)\n        return self._backend._read_mem_bio(bio)\n\n    @property\n    def tbs_certrequest_bytes(self):\n        pp = self._backend._ffi.new(\"unsigned char **\")\n        res = self._backend._lib.i2d_re_X509_REQ_tbs(self._x509_req, pp)\n        self._backend.openssl_assert(res > 0)\n        pp = self._backend._ffi.gc(\n            pp, lambda pointer: self._backend._lib.OPENSSL_free(pointer[0])\n        )\n        return self._backend._ffi.buffer(pp[0], res)[:]\n\n    @property\n    def signature(self):\n        sig = self._backend._ffi.new(\"ASN1_BIT_STRING **\")\n        self._backend._lib.X509_REQ_get0_signature(\n            self._x509_req, sig, self._backend._ffi.NULL\n        )\n        self._backend.openssl_assert(sig[0] != self._backend._ffi.NULL)\n        return _asn1_string_to_bytes(self._backend, sig[0])\n\n    @property\n    def is_signature_valid(self):\n        pkey = self._backend._lib.X509_REQ_get_pubkey(self._x509_req)\n        self._backend.openssl_assert(pkey != self._backend._ffi.NULL)\n        pkey = self._backend._ffi.gc(pkey, self._backend._lib.EVP_PKEY_free)\n        res = self._backend._lib.X509_REQ_verify(self._x509_req, pkey)\n\n        if res != 1:\n            self._backend._consume_errors()\n            return False\n\n        return True\n\n\n@utils.register_interface(\n    x509.certificate_transparency.SignedCertificateTimestamp\n)\nclass _SignedCertificateTimestamp(object):\n    def __init__(self, backend, sct_list, sct):\n        self._backend = backend\n        # Keep the SCT_LIST that this SCT came from alive.\n        self._sct_list = sct_list\n        self._sct = sct\n\n    @property\n    def version(self):\n        version = self._backend._lib.SCT_get_version(self._sct)\n        assert version == self._backend._lib.SCT_VERSION_V1\n        return x509.certificate_transparency.Version.v1\n\n    @property\n    def log_id(self):\n        out = self._backend._ffi.new(\"unsigned char **\")\n        log_id_length = self._backend._lib.SCT_get0_log_id(self._sct, out)\n        assert log_id_length >= 0\n        return self._backend._ffi.buffer(out[0], log_id_length)[:]\n\n    @property\n    def timestamp(self):\n        timestamp = self._backend._lib.SCT_get_timestamp(self._sct)\n        milliseconds = timestamp % 1000\n        return datetime.datetime.utcfromtimestamp(\n            timestamp // 1000\n        ).replace(microsecond=milliseconds * 1000)\n\n    @property\n    def entry_type(self):\n        entry_type = self._backend._lib.SCT_get_log_entry_type(self._sct)\n        # We currently only support loading SCTs from the X.509 extension, so\n        # we only have precerts.\n        assert entry_type == self._backend._lib.CT_LOG_ENTRY_TYPE_PRECERT\n        return x509.certificate_transparency.LogEntryType.PRE_CERTIFICATE\n\n    @property\n    def _signature(self):\n        ptrptr = self._backend._ffi.new(\"unsigned char **\")\n        res = self._backend._lib.SCT_get0_signature(self._sct, ptrptr)\n        self._backend.openssl_assert(res > 0)\n        self._backend.openssl_assert(ptrptr[0] != self._backend._ffi.NULL)\n        return self._backend._ffi.buffer(ptrptr[0], res)[:]\n\n    def __hash__(self):\n        return hash(self._signature)\n\n    def __eq__(self, other):\n        if not isinstance(other, _SignedCertificateTimestamp):\n            return NotImplemented\n\n        return self._signature == other._signature\n\n    def __ne__(self, other):\n        return not self == other\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/bindings/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/bindings/openssl/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/bindings/openssl/_conditional.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\n\ndef cryptography_has_ec2m():\n    return [\n        \"EC_POINT_set_affine_coordinates_GF2m\",\n        \"EC_POINT_get_affine_coordinates_GF2m\",\n        \"EC_POINT_set_compressed_coordinates_GF2m\",\n    ]\n\n\ndef cryptography_has_ec_1_0_2():\n    return [\n        \"EC_curve_nid2nist\",\n    ]\n\n\ndef cryptography_has_set_ecdh_auto():\n    return [\n        \"SSL_CTX_set_ecdh_auto\",\n    ]\n\n\ndef cryptography_has_rsa_r_pkcs_decoding_error():\n    return [\n        \"RSA_R_PKCS_DECODING_ERROR\"\n    ]\n\n\ndef cryptography_has_rsa_oaep_md():\n    return [\n        \"EVP_PKEY_CTX_set_rsa_oaep_md\",\n    ]\n\n\ndef cryptography_has_rsa_oaep_label():\n    return [\n        \"EVP_PKEY_CTX_set0_rsa_oaep_label\",\n    ]\n\n\ndef cryptography_has_ssl3_method():\n    return [\n        \"SSLv3_method\",\n        \"SSLv3_client_method\",\n        \"SSLv3_server_method\",\n    ]\n\n\ndef cryptography_has_alpn():\n    return [\n        \"SSL_CTX_set_alpn_protos\",\n        \"SSL_set_alpn_protos\",\n        \"SSL_CTX_set_alpn_select_cb\",\n        \"SSL_get0_alpn_selected\",\n    ]\n\n\ndef cryptography_has_compression():\n    return [\n        \"SSL_get_current_compression\",\n        \"SSL_get_current_expansion\",\n        \"SSL_COMP_get_name\",\n    ]\n\n\ndef cryptography_has_get_server_tmp_key():\n    return [\n        \"SSL_get_server_tmp_key\",\n    ]\n\n\ndef cryptography_has_102_verification_error_codes():\n    return [\n        'X509_V_ERR_SUITE_B_INVALID_VERSION',\n        'X509_V_ERR_SUITE_B_INVALID_ALGORITHM',\n        'X509_V_ERR_SUITE_B_INVALID_CURVE',\n        'X509_V_ERR_SUITE_B_INVALID_SIGNATURE_ALGORITHM',\n        'X509_V_ERR_SUITE_B_LOS_NOT_ALLOWED',\n        'X509_V_ERR_SUITE_B_CANNOT_SIGN_P_384_WITH_P_256',\n        'X509_V_ERR_HOSTNAME_MISMATCH',\n        'X509_V_ERR_EMAIL_MISMATCH',\n        'X509_V_ERR_IP_ADDRESS_MISMATCH'\n    ]\n\n\ndef cryptography_has_102_verification_params():\n    return [\n        \"X509_V_FLAG_SUITEB_128_LOS_ONLY\",\n        \"X509_V_FLAG_SUITEB_192_LOS\",\n        \"X509_V_FLAG_SUITEB_128_LOS\",\n        \"X509_VERIFY_PARAM_set1_host\",\n        \"X509_VERIFY_PARAM_set1_email\",\n        \"X509_VERIFY_PARAM_set1_ip\",\n        \"X509_VERIFY_PARAM_set1_ip_asc\",\n        \"X509_VERIFY_PARAM_set_hostflags\",\n        \"SSL_get0_param\",\n        \"X509_CHECK_FLAG_ALWAYS_CHECK_SUBJECT\",\n        \"X509_CHECK_FLAG_NO_WILDCARDS\",\n        \"X509_CHECK_FLAG_NO_PARTIAL_WILDCARDS\",\n        \"X509_CHECK_FLAG_MULTI_LABEL_WILDCARDS\",\n        \"X509_CHECK_FLAG_SINGLE_LABEL_SUBDOMAINS\"\n    ]\n\n\ndef cryptography_has_110_verification_params():\n    return [\n        \"X509_CHECK_FLAG_NEVER_CHECK_SUBJECT\"\n    ]\n\n\ndef cryptography_has_x509_v_flag_trusted_first():\n    return [\n        \"X509_V_FLAG_TRUSTED_FIRST\",\n    ]\n\n\ndef cryptography_has_x509_v_flag_partial_chain():\n    return [\n        \"X509_V_FLAG_PARTIAL_CHAIN\",\n    ]\n\n\ndef cryptography_has_set_cert_cb():\n    return [\n        \"SSL_CTX_set_cert_cb\",\n        \"SSL_set_cert_cb\",\n    ]\n\n\ndef cryptography_has_ssl_st():\n    return [\n        \"SSL_ST_BEFORE\",\n        \"SSL_ST_OK\",\n        \"SSL_ST_INIT\",\n        \"SSL_ST_RENEGOTIATE\",\n    ]\n\n\ndef cryptography_has_tls_st():\n    return [\n        \"TLS_ST_BEFORE\",\n        \"TLS_ST_OK\",\n    ]\n\n\ndef cryptography_has_locking_callbacks():\n    return [\n        \"Cryptography_setup_ssl_threads\",\n    ]\n\n\ndef cryptography_has_scrypt():\n    return [\n        \"EVP_PBE_scrypt\",\n    ]\n\n\ndef cryptography_has_generic_dtls_method():\n    return [\n        \"DTLS_method\",\n        \"DTLS_server_method\",\n        \"DTLS_client_method\",\n        \"SSL_OP_NO_DTLSv1\",\n        \"SSL_OP_NO_DTLSv1_2\",\n        \"DTLS_set_link_mtu\",\n        \"DTLS_get_link_min_mtu\",\n    ]\n\n\ndef cryptography_has_evp_pkey_dhx():\n    return [\n        \"EVP_PKEY_DHX\",\n    ]\n\n\ndef cryptography_has_mem_functions():\n    return [\n        \"Cryptography_CRYPTO_set_mem_functions\",\n    ]\n\n\ndef cryptography_has_sct():\n    return [\n        \"SCT_get_version\",\n        \"SCT_get_log_entry_type\",\n        \"SCT_get0_log_id\",\n        \"SCT_get0_signature\",\n        \"SCT_get_timestamp\",\n        \"SCT_set_source\",\n        \"sk_SCT_num\",\n        \"sk_SCT_value\",\n        \"SCT_LIST_free\",\n        \"sk_SCT_push\",\n        \"sk_SCT_new_null\",\n        \"SCT_new\",\n        \"SCT_set1_log_id\",\n        \"SCT_set_timestamp\",\n        \"SCT_set_version\",\n        \"SCT_set_log_entry_type\",\n    ]\n\n\ndef cryptography_has_x509_store_ctx_get_issuer():\n    return [\n        \"X509_STORE_get_get_issuer\",\n        \"X509_STORE_set_get_issuer\",\n    ]\n\n\ndef cryptography_has_x25519():\n    return [\n        \"EVP_PKEY_X25519\",\n        \"NID_X25519\",\n    ]\n\n\ndef cryptography_has_x448():\n    return [\n        \"EVP_PKEY_X448\",\n        \"NID_X448\",\n    ]\n\n\ndef cryptography_has_ed448():\n    return [\n        \"EVP_PKEY_ED448\",\n        \"NID_ED448\",\n    ]\n\n\ndef cryptography_has_ed25519():\n    return [\n        \"NID_ED25519\",\n        \"EVP_PKEY_ED25519\",\n    ]\n\n\ndef cryptography_has_poly1305():\n    return [\n        \"NID_poly1305\",\n        \"EVP_PKEY_POLY1305\",\n    ]\n\n\ndef cryptography_has_oneshot_evp_digest_sign_verify():\n    return [\n        \"EVP_DigestSign\",\n        \"EVP_DigestVerify\",\n    ]\n\n\ndef cryptography_has_evp_digestfinal_xof():\n    return [\n        \"EVP_DigestFinalXOF\",\n    ]\n\n\ndef cryptography_has_evp_pkey_get_set_tls_encodedpoint():\n    return [\n        \"EVP_PKEY_get1_tls_encodedpoint\",\n        \"EVP_PKEY_set1_tls_encodedpoint\",\n    ]\n\n\ndef cryptography_has_fips():\n    return [\n        \"FIPS_mode_set\",\n        \"FIPS_mode\",\n    ]\n\n\ndef cryptography_has_ssl_sigalgs():\n    return [\n        \"SSL_CTX_set1_sigalgs_list\",\n        \"SSL_get_sigalgs\",\n    ]\n\n\ndef cryptography_has_psk():\n    return [\n        \"SSL_CTX_use_psk_identity_hint\",\n        \"SSL_CTX_set_psk_server_callback\",\n        \"SSL_CTX_set_psk_client_callback\",\n    ]\n\n\ndef cryptography_has_custom_ext():\n    return [\n        \"SSL_CTX_add_client_custom_ext\",\n        \"SSL_CTX_add_server_custom_ext\",\n        \"SSL_extension_supported\",\n    ]\n\n\ndef cryptography_has_openssl_cleanup():\n    return [\n        \"OPENSSL_cleanup\",\n    ]\n\n\ndef cryptography_has_cipher_details():\n    return [\n        \"SSL_CIPHER_is_aead\",\n        \"SSL_CIPHER_get_cipher_nid\",\n        \"SSL_CIPHER_get_digest_nid\",\n        \"SSL_CIPHER_get_kx_nid\",\n        \"SSL_CIPHER_get_auth_nid\",\n    ]\n\n\ndef cryptography_has_tlsv13():\n    return [\n        \"SSL_OP_NO_TLSv1_3\",\n        \"SSL_VERIFY_POST_HANDSHAKE\",\n        \"SSL_CTX_set_ciphersuites\",\n        \"SSL_verify_client_post_handshake\",\n        \"SSL_CTX_set_post_handshake_auth\",\n        \"SSL_set_post_handshake_auth\",\n        \"SSL_SESSION_get_max_early_data\",\n        \"SSL_write_early_data\",\n        \"SSL_read_early_data\",\n        \"SSL_CTX_set_max_early_data\",\n    ]\n\n\ndef cryptography_has_raw_key():\n    return [\n        \"EVP_PKEY_new_raw_private_key\",\n        \"EVP_PKEY_new_raw_public_key\",\n        \"EVP_PKEY_get_raw_private_key\",\n        \"EVP_PKEY_get_raw_public_key\",\n    ]\n\n\ndef cryptography_has_evp_r_memory_limit_exceeded():\n    return [\n        \"EVP_R_MEMORY_LIMIT_EXCEEDED\",\n    ]\n\n\ndef cryptography_has_engine():\n    return [\n        \"ENGINE_by_id\",\n        \"ENGINE_init\",\n        \"ENGINE_finish\",\n        \"ENGINE_get_default_RAND\",\n        \"ENGINE_set_default_RAND\",\n        \"ENGINE_unregister_RAND\",\n        \"ENGINE_ctrl_cmd\",\n        \"ENGINE_free\",\n        \"ENGINE_get_name\",\n        \"Cryptography_add_osrandom_engine\",\n    ]\n\n\ndef cryptography_has_verified_chain():\n    return [\n        \"SSL_get0_verified_chain\",\n    ]\n\n\n# This is a mapping of\n# {condition: function-returning-names-dependent-on-that-condition} so we can\n# loop over them and delete unsupported names at runtime. It will be removed\n# when cffi supports #if in cdef. We use functions instead of just a dict of\n# lists so we can use coverage to measure which are used.\nCONDITIONAL_NAMES = {\n    \"Cryptography_HAS_EC2M\": cryptography_has_ec2m,\n    \"Cryptography_HAS_EC_1_0_2\": cryptography_has_ec_1_0_2,\n    \"Cryptography_HAS_SET_ECDH_AUTO\": cryptography_has_set_ecdh_auto,\n    \"Cryptography_HAS_RSA_R_PKCS_DECODING_ERROR\": (\n        cryptography_has_rsa_r_pkcs_decoding_error\n    ),\n    \"Cryptography_HAS_RSA_OAEP_MD\": cryptography_has_rsa_oaep_md,\n    \"Cryptography_HAS_RSA_OAEP_LABEL\": cryptography_has_rsa_oaep_label,\n    \"Cryptography_HAS_SSL3_METHOD\": cryptography_has_ssl3_method,\n    \"Cryptography_HAS_ALPN\": cryptography_has_alpn,\n    \"Cryptography_HAS_COMPRESSION\": cryptography_has_compression,\n    \"Cryptography_HAS_GET_SERVER_TMP_KEY\": cryptography_has_get_server_tmp_key,\n    \"Cryptography_HAS_102_VERIFICATION_ERROR_CODES\": (\n        cryptography_has_102_verification_error_codes\n    ),\n    \"Cryptography_HAS_102_VERIFICATION_PARAMS\": (\n        cryptography_has_102_verification_params\n    ),\n    \"Cryptography_HAS_110_VERIFICATION_PARAMS\": (\n        cryptography_has_110_verification_params\n    ),\n    \"Cryptography_HAS_X509_V_FLAG_TRUSTED_FIRST\": (\n        cryptography_has_x509_v_flag_trusted_first\n    ),\n    \"Cryptography_HAS_X509_V_FLAG_PARTIAL_CHAIN\": (\n        cryptography_has_x509_v_flag_partial_chain\n    ),\n    \"Cryptography_HAS_SET_CERT_CB\": cryptography_has_set_cert_cb,\n    \"Cryptography_HAS_SSL_ST\": cryptography_has_ssl_st,\n    \"Cryptography_HAS_TLS_ST\": cryptography_has_tls_st,\n    \"Cryptography_HAS_LOCKING_CALLBACKS\": cryptography_has_locking_callbacks,\n    \"Cryptography_HAS_SCRYPT\": cryptography_has_scrypt,\n    \"Cryptography_HAS_GENERIC_DTLS_METHOD\": (\n        cryptography_has_generic_dtls_method\n    ),\n    \"Cryptography_HAS_EVP_PKEY_DHX\": cryptography_has_evp_pkey_dhx,\n    \"Cryptography_HAS_MEM_FUNCTIONS\": cryptography_has_mem_functions,\n    \"Cryptography_HAS_SCT\": cryptography_has_sct,\n    \"Cryptography_HAS_X509_STORE_CTX_GET_ISSUER\": (\n        cryptography_has_x509_store_ctx_get_issuer\n    ),\n    \"Cryptography_HAS_X25519\": cryptography_has_x25519,\n    \"Cryptography_HAS_X448\": cryptography_has_x448,\n    \"Cryptography_HAS_ED448\": cryptography_has_ed448,\n    \"Cryptography_HAS_ED25519\": cryptography_has_ed25519,\n    \"Cryptography_HAS_POLY1305\": cryptography_has_poly1305,\n    \"Cryptography_HAS_ONESHOT_EVP_DIGEST_SIGN_VERIFY\": (\n        cryptography_has_oneshot_evp_digest_sign_verify\n    ),\n    \"Cryptography_HAS_EVP_PKEY_get_set_tls_encodedpoint\": (\n        cryptography_has_evp_pkey_get_set_tls_encodedpoint\n    ),\n    \"Cryptography_HAS_FIPS\": cryptography_has_fips,\n    \"Cryptography_HAS_SIGALGS\": cryptography_has_ssl_sigalgs,\n    \"Cryptography_HAS_PSK\": cryptography_has_psk,\n    \"Cryptography_HAS_CUSTOM_EXT\": cryptography_has_custom_ext,\n    \"Cryptography_HAS_OPENSSL_CLEANUP\": cryptography_has_openssl_cleanup,\n    \"Cryptography_HAS_CIPHER_DETAILS\": cryptography_has_cipher_details,\n    \"Cryptography_HAS_TLSv1_3\": cryptography_has_tlsv13,\n    \"Cryptography_HAS_RAW_KEY\": cryptography_has_raw_key,\n    \"Cryptography_HAS_EVP_DIGESTFINAL_XOF\": (\n        cryptography_has_evp_digestfinal_xof\n    ),\n    \"Cryptography_HAS_EVP_R_MEMORY_LIMIT_EXCEEDED\": (\n        cryptography_has_evp_r_memory_limit_exceeded\n    ),\n    \"Cryptography_HAS_ENGINE\": cryptography_has_engine,\n    \"Cryptography_HAS_VERIFIED_CHAIN\": cryptography_has_verified_chain,\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/bindings/openssl/binding.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport collections\nimport threading\nimport types\nimport warnings\n\nimport cryptography\nfrom cryptography import utils\nfrom cryptography.exceptions import InternalError\nfrom cryptography.hazmat.bindings._openssl import ffi, lib\nfrom cryptography.hazmat.bindings.openssl._conditional import CONDITIONAL_NAMES\n\n_OpenSSLErrorWithText = collections.namedtuple(\n    \"_OpenSSLErrorWithText\", [\"code\", \"lib\", \"func\", \"reason\", \"reason_text\"]\n)\n\n\nclass _OpenSSLError(object):\n    def __init__(self, code, lib, func, reason):\n        self._code = code\n        self._lib = lib\n        self._func = func\n        self._reason = reason\n\n    def _lib_reason_match(self, lib, reason):\n        return lib == self.lib and reason == self.reason\n\n    code = utils.read_only_property(\"_code\")\n    lib = utils.read_only_property(\"_lib\")\n    func = utils.read_only_property(\"_func\")\n    reason = utils.read_only_property(\"_reason\")\n\n\ndef _consume_errors(lib):\n    errors = []\n    while True:\n        code = lib.ERR_get_error()\n        if code == 0:\n            break\n\n        err_lib = lib.ERR_GET_LIB(code)\n        err_func = lib.ERR_GET_FUNC(code)\n        err_reason = lib.ERR_GET_REASON(code)\n\n        errors.append(_OpenSSLError(code, err_lib, err_func, err_reason))\n\n    return errors\n\n\ndef _openssl_assert(lib, ok):\n    if not ok:\n        errors = _consume_errors(lib)\n        errors_with_text = []\n        for err in errors:\n            buf = ffi.new(\"char[]\", 256)\n            lib.ERR_error_string_n(err.code, buf, len(buf))\n            err_text_reason = ffi.string(buf)\n\n            errors_with_text.append(\n                _OpenSSLErrorWithText(\n                    err.code, err.lib, err.func, err.reason, err_text_reason\n                )\n            )\n\n        raise InternalError(\n            \"Unknown OpenSSL error. This error is commonly encountered when \"\n            \"another library is not cleaning up the OpenSSL error stack. If \"\n            \"you are using cryptography with another library that uses \"\n            \"OpenSSL try disabling it before reporting a bug. Otherwise \"\n            \"please file an issue at https://github.com/pyca/cryptography/\"\n            \"issues with information on how to reproduce \"\n            \"this. ({0!r})\".format(errors_with_text),\n            errors_with_text\n        )\n\n\ndef build_conditional_library(lib, conditional_names):\n    conditional_lib = types.ModuleType(\"lib\")\n    conditional_lib._original_lib = lib\n    excluded_names = set()\n    for condition, names_cb in conditional_names.items():\n        if not getattr(lib, condition):\n            excluded_names.update(names_cb())\n\n    for attr in dir(lib):\n        if attr not in excluded_names:\n            setattr(conditional_lib, attr, getattr(lib, attr))\n\n    return conditional_lib\n\n\nclass Binding(object):\n    \"\"\"\n    OpenSSL API wrapper.\n    \"\"\"\n    lib = None\n    ffi = ffi\n    _lib_loaded = False\n    _init_lock = threading.Lock()\n    _lock_init_lock = threading.Lock()\n\n    def __init__(self):\n        self._ensure_ffi_initialized()\n\n    @classmethod\n    def _register_osrandom_engine(cls):\n        # Clear any errors extant in the queue before we start. In many\n        # scenarios other things may be interacting with OpenSSL in the same\n        # process space and it has proven untenable to assume that they will\n        # reliably clear the error queue. Once we clear it here we will\n        # error on any subsequent unexpected item in the stack.\n        cls.lib.ERR_clear_error()\n        if cls.lib.Cryptography_HAS_ENGINE:\n            result = cls.lib.Cryptography_add_osrandom_engine()\n            _openssl_assert(cls.lib, result in (1, 2))\n\n    @classmethod\n    def _ensure_ffi_initialized(cls):\n        with cls._init_lock:\n            if not cls._lib_loaded:\n                cls.lib = build_conditional_library(lib, CONDITIONAL_NAMES)\n                cls._lib_loaded = True\n                # initialize the SSL library\n                cls.lib.SSL_library_init()\n                # adds all ciphers/digests for EVP\n                cls.lib.OpenSSL_add_all_algorithms()\n                # loads error strings for libcrypto and libssl functions\n                cls.lib.SSL_load_error_strings()\n                cls._register_osrandom_engine()\n\n    @classmethod\n    def init_static_locks(cls):\n        with cls._lock_init_lock:\n            cls._ensure_ffi_initialized()\n            # Use Python's implementation if available, importing _ssl triggers\n            # the setup for this.\n            __import__(\"_ssl\")\n\n            if (not cls.lib.Cryptography_HAS_LOCKING_CALLBACKS or\n                    cls.lib.CRYPTO_get_locking_callback() != cls.ffi.NULL):\n                return\n\n            # If nothing else has setup a locking callback already, we set up\n            # our own\n            res = lib.Cryptography_setup_ssl_threads()\n            _openssl_assert(cls.lib, res == 1)\n\n\ndef _verify_openssl_version(lib):\n    if (\n        lib.CRYPTOGRAPHY_OPENSSL_LESS_THAN_102 and\n        not lib.CRYPTOGRAPHY_IS_LIBRESSL\n    ):\n        warnings.warn(\n            \"OpenSSL version 1.0.1 is no longer supported by the OpenSSL \"\n            \"project, please upgrade. The next version of cryptography will \"\n            \"drop support for it.\",\n            utils.CryptographyDeprecationWarning\n        )\n\n\ndef _verify_package_version(version):\n    # Occasionally we run into situations where the version of the Python\n    # package does not match the version of the shared object that is loaded.\n    # This may occur in environments where multiple versions of cryptography\n    # are installed and available in the python path. To avoid errors cropping\n    # up later this code checks that the currently imported package and the\n    # shared object that were loaded have the same version and raise an\n    # ImportError if they do not\n    so_package_version = ffi.string(lib.CRYPTOGRAPHY_PACKAGE_VERSION)\n    if version.encode(\"ascii\") != so_package_version:\n        raise ImportError(\n            \"The version of cryptography does not match the loaded \"\n            \"shared object. This can happen if you have multiple copies of \"\n            \"cryptography installed in your Python path. Please try creating \"\n            \"a new virtual environment to resolve this issue. \"\n            \"Loaded python version: {}, shared object version: {}\".format(\n                version, so_package_version\n            )\n        )\n\n\n_verify_package_version(cryptography.__version__)\n\n# OpenSSL is not thread safe until the locks are initialized. We call this\n# method in module scope so that it executes with the import lock. On\n# Pythons < 3.4 this import lock is a global lock, which can prevent a race\n# condition registering the OpenSSL locks. On Python 3.4+ the import lock\n# is per module so this approach will not work.\nBinding.init_static_locks()\n\n_verify_openssl_version(Binding.lib)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/asymmetric/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass AsymmetricSignatureContext(object):\n    @abc.abstractmethod\n    def update(self, data):\n        \"\"\"\n        Processes the provided bytes and returns nothing.\n        \"\"\"\n\n    @abc.abstractmethod\n    def finalize(self):\n        \"\"\"\n        Returns the signature as bytes.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass AsymmetricVerificationContext(object):\n    @abc.abstractmethod\n    def update(self, data):\n        \"\"\"\n        Processes the provided bytes and returns nothing.\n        \"\"\"\n\n    @abc.abstractmethod\n    def verify(self):\n        \"\"\"\n        Raises an exception if the bytes provided to update do not match the\n        signature or the signature does not match the public key.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/asymmetric/dh.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\nfrom cryptography import utils\n\n\ndef generate_parameters(generator, key_size, backend):\n    return backend.generate_dh_parameters(generator, key_size)\n\n\nclass DHPrivateNumbers(object):\n    def __init__(self, x, public_numbers):\n        if not isinstance(x, six.integer_types):\n            raise TypeError(\"x must be an integer.\")\n\n        if not isinstance(public_numbers, DHPublicNumbers):\n            raise TypeError(\"public_numbers must be an instance of \"\n                            \"DHPublicNumbers.\")\n\n        self._x = x\n        self._public_numbers = public_numbers\n\n    def __eq__(self, other):\n        if not isinstance(other, DHPrivateNumbers):\n            return NotImplemented\n\n        return (\n            self._x == other._x and\n            self._public_numbers == other._public_numbers\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def private_key(self, backend):\n        return backend.load_dh_private_numbers(self)\n\n    public_numbers = utils.read_only_property(\"_public_numbers\")\n    x = utils.read_only_property(\"_x\")\n\n\nclass DHPublicNumbers(object):\n    def __init__(self, y, parameter_numbers):\n        if not isinstance(y, six.integer_types):\n            raise TypeError(\"y must be an integer.\")\n\n        if not isinstance(parameter_numbers, DHParameterNumbers):\n            raise TypeError(\n                \"parameters must be an instance of DHParameterNumbers.\")\n\n        self._y = y\n        self._parameter_numbers = parameter_numbers\n\n    def __eq__(self, other):\n        if not isinstance(other, DHPublicNumbers):\n            return NotImplemented\n\n        return (\n            self._y == other._y and\n            self._parameter_numbers == other._parameter_numbers\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def public_key(self, backend):\n        return backend.load_dh_public_numbers(self)\n\n    y = utils.read_only_property(\"_y\")\n    parameter_numbers = utils.read_only_property(\"_parameter_numbers\")\n\n\nclass DHParameterNumbers(object):\n    def __init__(self, p, g, q=None):\n        if (\n            not isinstance(p, six.integer_types) or\n            not isinstance(g, six.integer_types)\n        ):\n            raise TypeError(\"p and g must be integers\")\n        if q is not None and not isinstance(q, six.integer_types):\n            raise TypeError(\"q must be integer or None\")\n\n        if g < 2:\n            raise ValueError(\"DH generator must be 2 or greater\")\n\n        self._p = p\n        self._g = g\n        self._q = q\n\n    def __eq__(self, other):\n        if not isinstance(other, DHParameterNumbers):\n            return NotImplemented\n\n        return (\n            self._p == other._p and\n            self._g == other._g and\n            self._q == other._q\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def parameters(self, backend):\n        return backend.load_dh_parameter_numbers(self)\n\n    p = utils.read_only_property(\"_p\")\n    g = utils.read_only_property(\"_g\")\n    q = utils.read_only_property(\"_q\")\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass DHParameters(object):\n    @abc.abstractmethod\n    def generate_private_key(self):\n        \"\"\"\n        Generates and returns a DHPrivateKey.\n        \"\"\"\n\n    @abc.abstractmethod\n    def parameter_bytes(self, encoding, format):\n        \"\"\"\n        Returns the parameters serialized as bytes.\n        \"\"\"\n\n    @abc.abstractmethod\n    def parameter_numbers(self):\n        \"\"\"\n        Returns a DHParameterNumbers.\n        \"\"\"\n\n\nDHParametersWithSerialization = DHParameters\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass DHPrivateKey(object):\n    @abc.abstractproperty\n    def key_size(self):\n        \"\"\"\n        The bit length of the prime modulus.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_key(self):\n        \"\"\"\n        The DHPublicKey associated with this private key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def parameters(self):\n        \"\"\"\n        The DHParameters object associated with this private key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def exchange(self, peer_public_key):\n        \"\"\"\n        Given peer's DHPublicKey, carry out the key exchange and\n        return shared key as bytes.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass DHPrivateKeyWithSerialization(DHPrivateKey):\n    @abc.abstractmethod\n    def private_numbers(self):\n        \"\"\"\n        Returns a DHPrivateNumbers.\n        \"\"\"\n\n    @abc.abstractmethod\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        \"\"\"\n        Returns the key serialized as bytes.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass DHPublicKey(object):\n    @abc.abstractproperty\n    def key_size(self):\n        \"\"\"\n        The bit length of the prime modulus.\n        \"\"\"\n\n    @abc.abstractmethod\n    def parameters(self):\n        \"\"\"\n        The DHParameters object associated with this public key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_numbers(self):\n        \"\"\"\n        Returns a DHPublicNumbers.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_bytes(self, encoding, format):\n        \"\"\"\n        Returns the key serialized as bytes.\n        \"\"\"\n\n\nDHPublicKeyWithSerialization = DHPublicKey\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/asymmetric/dsa.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\nfrom cryptography import utils\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass DSAParameters(object):\n    @abc.abstractmethod\n    def generate_private_key(self):\n        \"\"\"\n        Generates and returns a DSAPrivateKey.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass DSAParametersWithNumbers(DSAParameters):\n    @abc.abstractmethod\n    def parameter_numbers(self):\n        \"\"\"\n        Returns a DSAParameterNumbers.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass DSAPrivateKey(object):\n    @abc.abstractproperty\n    def key_size(self):\n        \"\"\"\n        The bit length of the prime modulus.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_key(self):\n        \"\"\"\n        The DSAPublicKey associated with this private key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def parameters(self):\n        \"\"\"\n        The DSAParameters object associated with this private key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def signer(self, signature_algorithm):\n        \"\"\"\n        Returns an AsymmetricSignatureContext used for signing data.\n        \"\"\"\n\n    @abc.abstractmethod\n    def sign(self, data, algorithm):\n        \"\"\"\n        Signs the data\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass DSAPrivateKeyWithSerialization(DSAPrivateKey):\n    @abc.abstractmethod\n    def private_numbers(self):\n        \"\"\"\n        Returns a DSAPrivateNumbers.\n        \"\"\"\n\n    @abc.abstractmethod\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        \"\"\"\n        Returns the key serialized as bytes.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass DSAPublicKey(object):\n    @abc.abstractproperty\n    def key_size(self):\n        \"\"\"\n        The bit length of the prime modulus.\n        \"\"\"\n\n    @abc.abstractmethod\n    def parameters(self):\n        \"\"\"\n        The DSAParameters object associated with this public key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def verifier(self, signature, signature_algorithm):\n        \"\"\"\n        Returns an AsymmetricVerificationContext used for signing data.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_numbers(self):\n        \"\"\"\n        Returns a DSAPublicNumbers.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_bytes(self, encoding, format):\n        \"\"\"\n        Returns the key serialized as bytes.\n        \"\"\"\n\n    @abc.abstractmethod\n    def verify(self, signature, data, algorithm):\n        \"\"\"\n        Verifies the signature of the data.\n        \"\"\"\n\n\nDSAPublicKeyWithSerialization = DSAPublicKey\n\n\ndef generate_parameters(key_size, backend):\n    return backend.generate_dsa_parameters(key_size)\n\n\ndef generate_private_key(key_size, backend):\n    return backend.generate_dsa_private_key_and_parameters(key_size)\n\n\ndef _check_dsa_parameters(parameters):\n    if parameters.p.bit_length() not in [1024, 2048, 3072]:\n        raise ValueError(\"p must be exactly 1024, 2048, or 3072 bits long\")\n    if parameters.q.bit_length() not in [160, 224, 256]:\n        raise ValueError(\"q must be exactly 160, 224, or 256 bits long\")\n\n    if not (1 < parameters.g < parameters.p):\n        raise ValueError(\"g, p don't satisfy 1 < g < p.\")\n\n\ndef _check_dsa_private_numbers(numbers):\n    parameters = numbers.public_numbers.parameter_numbers\n    _check_dsa_parameters(parameters)\n    if numbers.x <= 0 or numbers.x >= parameters.q:\n        raise ValueError(\"x must be > 0 and < q.\")\n\n    if numbers.public_numbers.y != pow(parameters.g, numbers.x, parameters.p):\n        raise ValueError(\"y must be equal to (g ** x % p).\")\n\n\nclass DSAParameterNumbers(object):\n    def __init__(self, p, q, g):\n        if (\n            not isinstance(p, six.integer_types) or\n            not isinstance(q, six.integer_types) or\n            not isinstance(g, six.integer_types)\n        ):\n            raise TypeError(\n                \"DSAParameterNumbers p, q, and g arguments must be integers.\"\n            )\n\n        self._p = p\n        self._q = q\n        self._g = g\n\n    p = utils.read_only_property(\"_p\")\n    q = utils.read_only_property(\"_q\")\n    g = utils.read_only_property(\"_g\")\n\n    def parameters(self, backend):\n        return backend.load_dsa_parameter_numbers(self)\n\n    def __eq__(self, other):\n        if not isinstance(other, DSAParameterNumbers):\n            return NotImplemented\n\n        return self.p == other.p and self.q == other.q and self.g == other.g\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __repr__(self):\n        return (\n            \"<DSAParameterNumbers(p={self.p}, q={self.q}, g={self.g})>\".format(\n                self=self\n            )\n        )\n\n\nclass DSAPublicNumbers(object):\n    def __init__(self, y, parameter_numbers):\n        if not isinstance(y, six.integer_types):\n            raise TypeError(\"DSAPublicNumbers y argument must be an integer.\")\n\n        if not isinstance(parameter_numbers, DSAParameterNumbers):\n            raise TypeError(\n                \"parameter_numbers must be a DSAParameterNumbers instance.\"\n            )\n\n        self._y = y\n        self._parameter_numbers = parameter_numbers\n\n    y = utils.read_only_property(\"_y\")\n    parameter_numbers = utils.read_only_property(\"_parameter_numbers\")\n\n    def public_key(self, backend):\n        return backend.load_dsa_public_numbers(self)\n\n    def __eq__(self, other):\n        if not isinstance(other, DSAPublicNumbers):\n            return NotImplemented\n\n        return (\n            self.y == other.y and\n            self.parameter_numbers == other.parameter_numbers\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __repr__(self):\n        return (\n            \"<DSAPublicNumbers(y={self.y}, \"\n            \"parameter_numbers={self.parameter_numbers})>\".format(self=self)\n        )\n\n\nclass DSAPrivateNumbers(object):\n    def __init__(self, x, public_numbers):\n        if not isinstance(x, six.integer_types):\n            raise TypeError(\"DSAPrivateNumbers x argument must be an integer.\")\n\n        if not isinstance(public_numbers, DSAPublicNumbers):\n            raise TypeError(\n                \"public_numbers must be a DSAPublicNumbers instance.\"\n            )\n        self._public_numbers = public_numbers\n        self._x = x\n\n    x = utils.read_only_property(\"_x\")\n    public_numbers = utils.read_only_property(\"_public_numbers\")\n\n    def private_key(self, backend):\n        return backend.load_dsa_private_numbers(self)\n\n    def __eq__(self, other):\n        if not isinstance(other, DSAPrivateNumbers):\n            return NotImplemented\n\n        return (\n            self.x == other.x and self.public_numbers == other.public_numbers\n        )\n\n    def __ne__(self, other):\n        return not self == other\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/asymmetric/ec.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\nimport warnings\n\nimport six\n\nfrom cryptography import utils\nfrom cryptography.hazmat._oid import ObjectIdentifier\n\n\nclass EllipticCurveOID(object):\n    SECP192R1 = ObjectIdentifier(\"1.2.840.10045.3.1.1\")\n    SECP224R1 = ObjectIdentifier(\"1.3.132.0.33\")\n    SECP256K1 = ObjectIdentifier(\"1.3.132.0.10\")\n    SECP256R1 = ObjectIdentifier(\"1.2.840.10045.3.1.7\")\n    SECP384R1 = ObjectIdentifier(\"1.3.132.0.34\")\n    SECP521R1 = ObjectIdentifier(\"1.3.132.0.35\")\n    BRAINPOOLP256R1 = ObjectIdentifier(\"1.3.36.3.3.2.8.1.1.7\")\n    BRAINPOOLP384R1 = ObjectIdentifier(\"1.3.36.3.3.2.8.1.1.11\")\n    BRAINPOOLP512R1 = ObjectIdentifier(\"1.3.36.3.3.2.8.1.1.13\")\n    SECT163K1 = ObjectIdentifier(\"1.3.132.0.1\")\n    SECT163R2 = ObjectIdentifier(\"1.3.132.0.15\")\n    SECT233K1 = ObjectIdentifier(\"1.3.132.0.26\")\n    SECT233R1 = ObjectIdentifier(\"1.3.132.0.27\")\n    SECT283K1 = ObjectIdentifier(\"1.3.132.0.16\")\n    SECT283R1 = ObjectIdentifier(\"1.3.132.0.17\")\n    SECT409K1 = ObjectIdentifier(\"1.3.132.0.36\")\n    SECT409R1 = ObjectIdentifier(\"1.3.132.0.37\")\n    SECT571K1 = ObjectIdentifier(\"1.3.132.0.38\")\n    SECT571R1 = ObjectIdentifier(\"1.3.132.0.39\")\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass EllipticCurve(object):\n    @abc.abstractproperty\n    def name(self):\n        \"\"\"\n        The name of the curve. e.g. secp256r1.\n        \"\"\"\n\n    @abc.abstractproperty\n    def key_size(self):\n        \"\"\"\n        Bit size of a secret scalar for the curve.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass EllipticCurveSignatureAlgorithm(object):\n    @abc.abstractproperty\n    def algorithm(self):\n        \"\"\"\n        The digest algorithm used with this signature.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass EllipticCurvePrivateKey(object):\n    @abc.abstractmethod\n    def signer(self, signature_algorithm):\n        \"\"\"\n        Returns an AsymmetricSignatureContext used for signing data.\n        \"\"\"\n\n    @abc.abstractmethod\n    def exchange(self, algorithm, peer_public_key):\n        \"\"\"\n        Performs a key exchange operation using the provided algorithm with the\n        provided peer's public key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_key(self):\n        \"\"\"\n        The EllipticCurvePublicKey for this private key.\n        \"\"\"\n\n    @abc.abstractproperty\n    def curve(self):\n        \"\"\"\n        The EllipticCurve that this key is on.\n        \"\"\"\n\n    @abc.abstractproperty\n    def key_size(self):\n        \"\"\"\n        Bit size of a secret scalar for the curve.\n        \"\"\"\n\n    @abc.abstractmethod\n    def sign(self, data, signature_algorithm):\n        \"\"\"\n        Signs the data\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass EllipticCurvePrivateKeyWithSerialization(EllipticCurvePrivateKey):\n    @abc.abstractmethod\n    def private_numbers(self):\n        \"\"\"\n        Returns an EllipticCurvePrivateNumbers.\n        \"\"\"\n\n    @abc.abstractmethod\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        \"\"\"\n        Returns the key serialized as bytes.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass EllipticCurvePublicKey(object):\n    @abc.abstractmethod\n    def verifier(self, signature, signature_algorithm):\n        \"\"\"\n        Returns an AsymmetricVerificationContext used for signing data.\n        \"\"\"\n\n    @abc.abstractproperty\n    def curve(self):\n        \"\"\"\n        The EllipticCurve that this key is on.\n        \"\"\"\n\n    @abc.abstractproperty\n    def key_size(self):\n        \"\"\"\n        Bit size of a secret scalar for the curve.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_numbers(self):\n        \"\"\"\n        Returns an EllipticCurvePublicNumbers.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_bytes(self, encoding, format):\n        \"\"\"\n        Returns the key serialized as bytes.\n        \"\"\"\n\n    @abc.abstractmethod\n    def verify(self, signature, data, signature_algorithm):\n        \"\"\"\n        Verifies the signature of the data.\n        \"\"\"\n\n    @classmethod\n    def from_encoded_point(cls, curve, data):\n        utils._check_bytes(\"data\", data)\n\n        if not isinstance(curve, EllipticCurve):\n            raise TypeError(\"curve must be an EllipticCurve instance\")\n\n        if len(data) == 0:\n            raise ValueError(\"data must not be an empty byte string\")\n\n        if six.indexbytes(data, 0) not in [0x02, 0x03, 0x04]:\n            raise ValueError(\"Unsupported elliptic curve point type\")\n\n        from cryptography.hazmat.backends.openssl.backend import backend\n        return backend.load_elliptic_curve_public_bytes(curve, data)\n\n\nEllipticCurvePublicKeyWithSerialization = EllipticCurvePublicKey\n\n\n@utils.register_interface(EllipticCurve)\nclass SECT571R1(object):\n    name = \"sect571r1\"\n    key_size = 570\n\n\n@utils.register_interface(EllipticCurve)\nclass SECT409R1(object):\n    name = \"sect409r1\"\n    key_size = 409\n\n\n@utils.register_interface(EllipticCurve)\nclass SECT283R1(object):\n    name = \"sect283r1\"\n    key_size = 283\n\n\n@utils.register_interface(EllipticCurve)\nclass SECT233R1(object):\n    name = \"sect233r1\"\n    key_size = 233\n\n\n@utils.register_interface(EllipticCurve)\nclass SECT163R2(object):\n    name = \"sect163r2\"\n    key_size = 163\n\n\n@utils.register_interface(EllipticCurve)\nclass SECT571K1(object):\n    name = \"sect571k1\"\n    key_size = 571\n\n\n@utils.register_interface(EllipticCurve)\nclass SECT409K1(object):\n    name = \"sect409k1\"\n    key_size = 409\n\n\n@utils.register_interface(EllipticCurve)\nclass SECT283K1(object):\n    name = \"sect283k1\"\n    key_size = 283\n\n\n@utils.register_interface(EllipticCurve)\nclass SECT233K1(object):\n    name = \"sect233k1\"\n    key_size = 233\n\n\n@utils.register_interface(EllipticCurve)\nclass SECT163K1(object):\n    name = \"sect163k1\"\n    key_size = 163\n\n\n@utils.register_interface(EllipticCurve)\nclass SECP521R1(object):\n    name = \"secp521r1\"\n    key_size = 521\n\n\n@utils.register_interface(EllipticCurve)\nclass SECP384R1(object):\n    name = \"secp384r1\"\n    key_size = 384\n\n\n@utils.register_interface(EllipticCurve)\nclass SECP256R1(object):\n    name = \"secp256r1\"\n    key_size = 256\n\n\n@utils.register_interface(EllipticCurve)\nclass SECP256K1(object):\n    name = \"secp256k1\"\n    key_size = 256\n\n\n@utils.register_interface(EllipticCurve)\nclass SECP224R1(object):\n    name = \"secp224r1\"\n    key_size = 224\n\n\n@utils.register_interface(EllipticCurve)\nclass SECP192R1(object):\n    name = \"secp192r1\"\n    key_size = 192\n\n\n@utils.register_interface(EllipticCurve)\nclass BrainpoolP256R1(object):\n    name = \"brainpoolP256r1\"\n    key_size = 256\n\n\n@utils.register_interface(EllipticCurve)\nclass BrainpoolP384R1(object):\n    name = \"brainpoolP384r1\"\n    key_size = 384\n\n\n@utils.register_interface(EllipticCurve)\nclass BrainpoolP512R1(object):\n    name = \"brainpoolP512r1\"\n    key_size = 512\n\n\n_CURVE_TYPES = {\n    \"prime192v1\": SECP192R1,\n    \"prime256v1\": SECP256R1,\n\n    \"secp192r1\": SECP192R1,\n    \"secp224r1\": SECP224R1,\n    \"secp256r1\": SECP256R1,\n    \"secp384r1\": SECP384R1,\n    \"secp521r1\": SECP521R1,\n    \"secp256k1\": SECP256K1,\n\n    \"sect163k1\": SECT163K1,\n    \"sect233k1\": SECT233K1,\n    \"sect283k1\": SECT283K1,\n    \"sect409k1\": SECT409K1,\n    \"sect571k1\": SECT571K1,\n\n    \"sect163r2\": SECT163R2,\n    \"sect233r1\": SECT233R1,\n    \"sect283r1\": SECT283R1,\n    \"sect409r1\": SECT409R1,\n    \"sect571r1\": SECT571R1,\n\n    \"brainpoolP256r1\": BrainpoolP256R1,\n    \"brainpoolP384r1\": BrainpoolP384R1,\n    \"brainpoolP512r1\": BrainpoolP512R1,\n}\n\n\n@utils.register_interface(EllipticCurveSignatureAlgorithm)\nclass ECDSA(object):\n    def __init__(self, algorithm):\n        self._algorithm = algorithm\n\n    algorithm = utils.read_only_property(\"_algorithm\")\n\n\ndef generate_private_key(curve, backend):\n    return backend.generate_elliptic_curve_private_key(curve)\n\n\ndef derive_private_key(private_value, curve, backend):\n    if not isinstance(private_value, six.integer_types):\n        raise TypeError(\"private_value must be an integer type.\")\n\n    if private_value <= 0:\n        raise ValueError(\"private_value must be a positive integer.\")\n\n    if not isinstance(curve, EllipticCurve):\n        raise TypeError(\"curve must provide the EllipticCurve interface.\")\n\n    return backend.derive_elliptic_curve_private_key(private_value, curve)\n\n\nclass EllipticCurvePublicNumbers(object):\n    def __init__(self, x, y, curve):\n        if (\n            not isinstance(x, six.integer_types) or\n            not isinstance(y, six.integer_types)\n        ):\n            raise TypeError(\"x and y must be integers.\")\n\n        if not isinstance(curve, EllipticCurve):\n            raise TypeError(\"curve must provide the EllipticCurve interface.\")\n\n        self._y = y\n        self._x = x\n        self._curve = curve\n\n    def public_key(self, backend):\n        return backend.load_elliptic_curve_public_numbers(self)\n\n    def encode_point(self):\n        warnings.warn(\n            \"encode_point has been deprecated on EllipticCurvePublicNumbers\"\n            \" and will be removed in a future version. Please use \"\n            \"EllipticCurvePublicKey.public_bytes to obtain both \"\n            \"compressed and uncompressed point encoding.\",\n            utils.DeprecatedIn25,\n            stacklevel=2,\n        )\n        # key_size is in bits. Convert to bytes and round up\n        byte_length = (self.curve.key_size + 7) // 8\n        return (\n            b'\\x04' + utils.int_to_bytes(self.x, byte_length) +\n            utils.int_to_bytes(self.y, byte_length)\n        )\n\n    @classmethod\n    def from_encoded_point(cls, curve, data):\n        if not isinstance(curve, EllipticCurve):\n            raise TypeError(\"curve must be an EllipticCurve instance\")\n\n        warnings.warn(\n            \"Support for unsafe construction of public numbers from \"\n            \"encoded data will be removed in a future version. \"\n            \"Please use EllipticCurvePublicKey.from_encoded_point\",\n            utils.DeprecatedIn25,\n            stacklevel=2,\n        )\n\n        if data.startswith(b'\\x04'):\n            # key_size is in bits. Convert to bytes and round up\n            byte_length = (curve.key_size + 7) // 8\n            if len(data) == 2 * byte_length + 1:\n                x = utils.int_from_bytes(data[1:byte_length + 1], 'big')\n                y = utils.int_from_bytes(data[byte_length + 1:], 'big')\n                return cls(x, y, curve)\n            else:\n                raise ValueError('Invalid elliptic curve point data length')\n        else:\n            raise ValueError('Unsupported elliptic curve point type')\n\n    curve = utils.read_only_property(\"_curve\")\n    x = utils.read_only_property(\"_x\")\n    y = utils.read_only_property(\"_y\")\n\n    def __eq__(self, other):\n        if not isinstance(other, EllipticCurvePublicNumbers):\n            return NotImplemented\n\n        return (\n            self.x == other.x and\n            self.y == other.y and\n            self.curve.name == other.curve.name and\n            self.curve.key_size == other.curve.key_size\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((self.x, self.y, self.curve.name, self.curve.key_size))\n\n    def __repr__(self):\n        return (\n            \"<EllipticCurvePublicNumbers(curve={0.curve.name}, x={0.x}, \"\n            \"y={0.y}>\".format(self)\n        )\n\n\nclass EllipticCurvePrivateNumbers(object):\n    def __init__(self, private_value, public_numbers):\n        if not isinstance(private_value, six.integer_types):\n            raise TypeError(\"private_value must be an integer.\")\n\n        if not isinstance(public_numbers, EllipticCurvePublicNumbers):\n            raise TypeError(\n                \"public_numbers must be an EllipticCurvePublicNumbers \"\n                \"instance.\"\n            )\n\n        self._private_value = private_value\n        self._public_numbers = public_numbers\n\n    def private_key(self, backend):\n        return backend.load_elliptic_curve_private_numbers(self)\n\n    private_value = utils.read_only_property(\"_private_value\")\n    public_numbers = utils.read_only_property(\"_public_numbers\")\n\n    def __eq__(self, other):\n        if not isinstance(other, EllipticCurvePrivateNumbers):\n            return NotImplemented\n\n        return (\n            self.private_value == other.private_value and\n            self.public_numbers == other.public_numbers\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((self.private_value, self.public_numbers))\n\n\nclass ECDH(object):\n    pass\n\n\n_OID_TO_CURVE = {\n    EllipticCurveOID.SECP192R1: SECP192R1,\n    EllipticCurveOID.SECP224R1: SECP224R1,\n    EllipticCurveOID.SECP256K1: SECP256K1,\n    EllipticCurveOID.SECP256R1: SECP256R1,\n    EllipticCurveOID.SECP384R1: SECP384R1,\n    EllipticCurveOID.SECP521R1: SECP521R1,\n    EllipticCurveOID.BRAINPOOLP256R1: BrainpoolP256R1,\n    EllipticCurveOID.BRAINPOOLP384R1: BrainpoolP384R1,\n    EllipticCurveOID.BRAINPOOLP512R1: BrainpoolP512R1,\n    EllipticCurveOID.SECT163K1: SECT163K1,\n    EllipticCurveOID.SECT163R2: SECT163R2,\n    EllipticCurveOID.SECT233K1: SECT233K1,\n    EllipticCurveOID.SECT233R1: SECT233R1,\n    EllipticCurveOID.SECT283K1: SECT283K1,\n    EllipticCurveOID.SECT283R1: SECT283R1,\n    EllipticCurveOID.SECT409K1: SECT409K1,\n    EllipticCurveOID.SECT409R1: SECT409R1,\n    EllipticCurveOID.SECT571K1: SECT571K1,\n    EllipticCurveOID.SECT571R1: SECT571R1,\n}\n\n\ndef get_curve_for_oid(oid):\n    try:\n        return _OID_TO_CURVE[oid]\n    except KeyError:\n        raise LookupError(\n            \"The provided object identifier has no matching elliptic \"\n            \"curve class\"\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/asymmetric/ed25519.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\nfrom cryptography.exceptions import UnsupportedAlgorithm, _Reasons\n\n\n_ED25519_KEY_SIZE = 32\n_ED25519_SIG_SIZE = 64\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass Ed25519PublicKey(object):\n    @classmethod\n    def from_public_bytes(cls, data):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.ed25519_supported():\n            raise UnsupportedAlgorithm(\n                \"ed25519 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_PUBLIC_KEY_ALGORITHM\n            )\n\n        return backend.ed25519_load_public_bytes(data)\n\n    @abc.abstractmethod\n    def public_bytes(self, encoding, format):\n        \"\"\"\n        The serialized bytes of the public key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def verify(self, signature, data):\n        \"\"\"\n        Verify the signature.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass Ed25519PrivateKey(object):\n    @classmethod\n    def generate(cls):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.ed25519_supported():\n            raise UnsupportedAlgorithm(\n                \"ed25519 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_PUBLIC_KEY_ALGORITHM\n            )\n\n        return backend.ed25519_generate_key()\n\n    @classmethod\n    def from_private_bytes(cls, data):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.ed25519_supported():\n            raise UnsupportedAlgorithm(\n                \"ed25519 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_PUBLIC_KEY_ALGORITHM\n            )\n\n        return backend.ed25519_load_private_bytes(data)\n\n    @abc.abstractmethod\n    def public_key(self):\n        \"\"\"\n        The Ed25519PublicKey derived from the private key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        \"\"\"\n        The serialized bytes of the private key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def sign(self, data):\n        \"\"\"\n        Signs the data.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/asymmetric/ed448.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\nfrom cryptography.exceptions import UnsupportedAlgorithm, _Reasons\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass Ed448PublicKey(object):\n    @classmethod\n    def from_public_bytes(cls, data):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.ed448_supported():\n            raise UnsupportedAlgorithm(\n                \"ed448 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_PUBLIC_KEY_ALGORITHM\n            )\n\n        return backend.ed448_load_public_bytes(data)\n\n    @abc.abstractmethod\n    def public_bytes(self, encoding, format):\n        \"\"\"\n        The serialized bytes of the public key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def verify(self, signature, data):\n        \"\"\"\n        Verify the signature.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass Ed448PrivateKey(object):\n    @classmethod\n    def generate(cls):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.ed448_supported():\n            raise UnsupportedAlgorithm(\n                \"ed448 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_PUBLIC_KEY_ALGORITHM\n            )\n        return backend.ed448_generate_key()\n\n    @classmethod\n    def from_private_bytes(cls, data):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.ed448_supported():\n            raise UnsupportedAlgorithm(\n                \"ed448 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_PUBLIC_KEY_ALGORITHM\n            )\n\n        return backend.ed448_load_private_bytes(data)\n\n    @abc.abstractmethod\n    def public_key(self):\n        \"\"\"\n        The Ed448PublicKey derived from the private key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def sign(self, data):\n        \"\"\"\n        Signs the data.\n        \"\"\"\n\n    @abc.abstractmethod\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        \"\"\"\n        The serialized bytes of the private key.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/asymmetric/padding.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\nimport math\n\nimport six\n\nfrom cryptography import utils\nfrom cryptography.hazmat.primitives import hashes\nfrom cryptography.hazmat.primitives.asymmetric import rsa\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass AsymmetricPadding(object):\n    @abc.abstractproperty\n    def name(self):\n        \"\"\"\n        A string naming this padding (e.g. \"PSS\", \"PKCS1\").\n        \"\"\"\n\n\n@utils.register_interface(AsymmetricPadding)\nclass PKCS1v15(object):\n    name = \"EMSA-PKCS1-v1_5\"\n\n\n@utils.register_interface(AsymmetricPadding)\nclass PSS(object):\n    MAX_LENGTH = object()\n    name = \"EMSA-PSS\"\n\n    def __init__(self, mgf, salt_length):\n        self._mgf = mgf\n\n        if (not isinstance(salt_length, six.integer_types) and\n                salt_length is not self.MAX_LENGTH):\n            raise TypeError(\"salt_length must be an integer.\")\n\n        if salt_length is not self.MAX_LENGTH and salt_length < 0:\n            raise ValueError(\"salt_length must be zero or greater.\")\n\n        self._salt_length = salt_length\n\n\n@utils.register_interface(AsymmetricPadding)\nclass OAEP(object):\n    name = \"EME-OAEP\"\n\n    def __init__(self, mgf, algorithm, label):\n        if not isinstance(algorithm, hashes.HashAlgorithm):\n            raise TypeError(\"Expected instance of hashes.HashAlgorithm.\")\n\n        self._mgf = mgf\n        self._algorithm = algorithm\n        self._label = label\n\n\nclass MGF1(object):\n    MAX_LENGTH = object()\n\n    def __init__(self, algorithm):\n        if not isinstance(algorithm, hashes.HashAlgorithm):\n            raise TypeError(\"Expected instance of hashes.HashAlgorithm.\")\n\n        self._algorithm = algorithm\n\n\ndef calculate_max_pss_salt_length(key, hash_algorithm):\n    if not isinstance(key, (rsa.RSAPrivateKey, rsa.RSAPublicKey)):\n        raise TypeError(\"key must be an RSA public or private key\")\n    # bit length - 1 per RFC 3447\n    emlen = int(math.ceil((key.key_size - 1) / 8.0))\n    salt_length = emlen - hash_algorithm.digest_size - 2\n    assert salt_length >= 0\n    return salt_length\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/asymmetric/rsa.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\ntry:\n    # Only available in math in 3.5+\n    from math import gcd\nexcept ImportError:\n    from fractions import gcd\n\nimport six\n\nfrom cryptography import utils\nfrom cryptography.exceptions import UnsupportedAlgorithm, _Reasons\nfrom cryptography.hazmat.backends.interfaces import RSABackend\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass RSAPrivateKey(object):\n    @abc.abstractmethod\n    def signer(self, padding, algorithm):\n        \"\"\"\n        Returns an AsymmetricSignatureContext used for signing data.\n        \"\"\"\n\n    @abc.abstractmethod\n    def decrypt(self, ciphertext, padding):\n        \"\"\"\n        Decrypts the provided ciphertext.\n        \"\"\"\n\n    @abc.abstractproperty\n    def key_size(self):\n        \"\"\"\n        The bit length of the public modulus.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_key(self):\n        \"\"\"\n        The RSAPublicKey associated with this private key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def sign(self, data, padding, algorithm):\n        \"\"\"\n        Signs the data.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass RSAPrivateKeyWithSerialization(RSAPrivateKey):\n    @abc.abstractmethod\n    def private_numbers(self):\n        \"\"\"\n        Returns an RSAPrivateNumbers.\n        \"\"\"\n\n    @abc.abstractmethod\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        \"\"\"\n        Returns the key serialized as bytes.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass RSAPublicKey(object):\n    @abc.abstractmethod\n    def verifier(self, signature, padding, algorithm):\n        \"\"\"\n        Returns an AsymmetricVerificationContext used for verifying signatures.\n        \"\"\"\n\n    @abc.abstractmethod\n    def encrypt(self, plaintext, padding):\n        \"\"\"\n        Encrypts the given plaintext.\n        \"\"\"\n\n    @abc.abstractproperty\n    def key_size(self):\n        \"\"\"\n        The bit length of the public modulus.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_numbers(self):\n        \"\"\"\n        Returns an RSAPublicNumbers\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_bytes(self, encoding, format):\n        \"\"\"\n        Returns the key serialized as bytes.\n        \"\"\"\n\n    @abc.abstractmethod\n    def verify(self, signature, data, padding, algorithm):\n        \"\"\"\n        Verifies the signature of the data.\n        \"\"\"\n\n\nRSAPublicKeyWithSerialization = RSAPublicKey\n\n\ndef generate_private_key(public_exponent, key_size, backend):\n    if not isinstance(backend, RSABackend):\n        raise UnsupportedAlgorithm(\n            \"Backend object does not implement RSABackend.\",\n            _Reasons.BACKEND_MISSING_INTERFACE\n        )\n\n    _verify_rsa_parameters(public_exponent, key_size)\n    return backend.generate_rsa_private_key(public_exponent, key_size)\n\n\ndef _verify_rsa_parameters(public_exponent, key_size):\n    if public_exponent < 3:\n        raise ValueError(\"public_exponent must be >= 3.\")\n\n    if public_exponent & 1 == 0:\n        raise ValueError(\"public_exponent must be odd.\")\n\n    if key_size < 512:\n        raise ValueError(\"key_size must be at least 512-bits.\")\n\n\ndef _check_private_key_components(p, q, private_exponent, dmp1, dmq1, iqmp,\n                                  public_exponent, modulus):\n    if modulus < 3:\n        raise ValueError(\"modulus must be >= 3.\")\n\n    if p >= modulus:\n        raise ValueError(\"p must be < modulus.\")\n\n    if q >= modulus:\n        raise ValueError(\"q must be < modulus.\")\n\n    if dmp1 >= modulus:\n        raise ValueError(\"dmp1 must be < modulus.\")\n\n    if dmq1 >= modulus:\n        raise ValueError(\"dmq1 must be < modulus.\")\n\n    if iqmp >= modulus:\n        raise ValueError(\"iqmp must be < modulus.\")\n\n    if private_exponent >= modulus:\n        raise ValueError(\"private_exponent must be < modulus.\")\n\n    if public_exponent < 3 or public_exponent >= modulus:\n        raise ValueError(\"public_exponent must be >= 3 and < modulus.\")\n\n    if public_exponent & 1 == 0:\n        raise ValueError(\"public_exponent must be odd.\")\n\n    if dmp1 & 1 == 0:\n        raise ValueError(\"dmp1 must be odd.\")\n\n    if dmq1 & 1 == 0:\n        raise ValueError(\"dmq1 must be odd.\")\n\n    if p * q != modulus:\n        raise ValueError(\"p*q must equal modulus.\")\n\n\ndef _check_public_key_components(e, n):\n    if n < 3:\n        raise ValueError(\"n must be >= 3.\")\n\n    if e < 3 or e >= n:\n        raise ValueError(\"e must be >= 3 and < n.\")\n\n    if e & 1 == 0:\n        raise ValueError(\"e must be odd.\")\n\n\ndef _modinv(e, m):\n    \"\"\"\n    Modular Multiplicative Inverse. Returns x such that: (x*e) mod m == 1\n    \"\"\"\n    x1, y1, x2, y2 = 1, 0, 0, 1\n    a, b = e, m\n    while b > 0:\n        q, r = divmod(a, b)\n        xn, yn = x1 - q * x2, y1 - q * y2\n        a, b, x1, y1, x2, y2 = b, r, x2, y2, xn, yn\n    return x1 % m\n\n\ndef rsa_crt_iqmp(p, q):\n    \"\"\"\n    Compute the CRT (q ** -1) % p value from RSA primes p and q.\n    \"\"\"\n    return _modinv(q, p)\n\n\ndef rsa_crt_dmp1(private_exponent, p):\n    \"\"\"\n    Compute the CRT private_exponent % (p - 1) value from the RSA\n    private_exponent (d) and p.\n    \"\"\"\n    return private_exponent % (p - 1)\n\n\ndef rsa_crt_dmq1(private_exponent, q):\n    \"\"\"\n    Compute the CRT private_exponent % (q - 1) value from the RSA\n    private_exponent (d) and q.\n    \"\"\"\n    return private_exponent % (q - 1)\n\n\n# Controls the number of iterations rsa_recover_prime_factors will perform\n# to obtain the prime factors. Each iteration increments by 2 so the actual\n# maximum attempts is half this number.\n_MAX_RECOVERY_ATTEMPTS = 1000\n\n\ndef rsa_recover_prime_factors(n, e, d):\n    \"\"\"\n    Compute factors p and q from the private exponent d. We assume that n has\n    no more than two factors. This function is adapted from code in PyCrypto.\n    \"\"\"\n    # See 8.2.2(i) in Handbook of Applied Cryptography.\n    ktot = d * e - 1\n    # The quantity d*e-1 is a multiple of phi(n), even,\n    # and can be represented as t*2^s.\n    t = ktot\n    while t % 2 == 0:\n        t = t // 2\n    # Cycle through all multiplicative inverses in Zn.\n    # The algorithm is non-deterministic, but there is a 50% chance\n    # any candidate a leads to successful factoring.\n    # See \"Digitalized Signatures and Public Key Functions as Intractable\n    # as Factorization\", M. Rabin, 1979\n    spotted = False\n    a = 2\n    while not spotted and a < _MAX_RECOVERY_ATTEMPTS:\n        k = t\n        # Cycle through all values a^{t*2^i}=a^k\n        while k < ktot:\n            cand = pow(a, k, n)\n            # Check if a^k is a non-trivial root of unity (mod n)\n            if cand != 1 and cand != (n - 1) and pow(cand, 2, n) == 1:\n                # We have found a number such that (cand-1)(cand+1)=0 (mod n).\n                # Either of the terms divides n.\n                p = gcd(cand + 1, n)\n                spotted = True\n                break\n            k *= 2\n        # This value was not any good... let's try another!\n        a += 2\n    if not spotted:\n        raise ValueError(\"Unable to compute factors p and q from exponent d.\")\n    # Found !\n    q, r = divmod(n, p)\n    assert r == 0\n    p, q = sorted((p, q), reverse=True)\n    return (p, q)\n\n\nclass RSAPrivateNumbers(object):\n    def __init__(self, p, q, d, dmp1, dmq1, iqmp,\n                 public_numbers):\n        if (\n            not isinstance(p, six.integer_types) or\n            not isinstance(q, six.integer_types) or\n            not isinstance(d, six.integer_types) or\n            not isinstance(dmp1, six.integer_types) or\n            not isinstance(dmq1, six.integer_types) or\n            not isinstance(iqmp, six.integer_types)\n        ):\n            raise TypeError(\n                \"RSAPrivateNumbers p, q, d, dmp1, dmq1, iqmp arguments must\"\n                \" all be an integers.\"\n            )\n\n        if not isinstance(public_numbers, RSAPublicNumbers):\n            raise TypeError(\n                \"RSAPrivateNumbers public_numbers must be an RSAPublicNumbers\"\n                \" instance.\"\n            )\n\n        self._p = p\n        self._q = q\n        self._d = d\n        self._dmp1 = dmp1\n        self._dmq1 = dmq1\n        self._iqmp = iqmp\n        self._public_numbers = public_numbers\n\n    p = utils.read_only_property(\"_p\")\n    q = utils.read_only_property(\"_q\")\n    d = utils.read_only_property(\"_d\")\n    dmp1 = utils.read_only_property(\"_dmp1\")\n    dmq1 = utils.read_only_property(\"_dmq1\")\n    iqmp = utils.read_only_property(\"_iqmp\")\n    public_numbers = utils.read_only_property(\"_public_numbers\")\n\n    def private_key(self, backend):\n        return backend.load_rsa_private_numbers(self)\n\n    def __eq__(self, other):\n        if not isinstance(other, RSAPrivateNumbers):\n            return NotImplemented\n\n        return (\n            self.p == other.p and\n            self.q == other.q and\n            self.d == other.d and\n            self.dmp1 == other.dmp1 and\n            self.dmq1 == other.dmq1 and\n            self.iqmp == other.iqmp and\n            self.public_numbers == other.public_numbers\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((\n            self.p,\n            self.q,\n            self.d,\n            self.dmp1,\n            self.dmq1,\n            self.iqmp,\n            self.public_numbers,\n        ))\n\n\nclass RSAPublicNumbers(object):\n    def __init__(self, e, n):\n        if (\n            not isinstance(e, six.integer_types) or\n            not isinstance(n, six.integer_types)\n        ):\n            raise TypeError(\"RSAPublicNumbers arguments must be integers.\")\n\n        self._e = e\n        self._n = n\n\n    e = utils.read_only_property(\"_e\")\n    n = utils.read_only_property(\"_n\")\n\n    def public_key(self, backend):\n        return backend.load_rsa_public_numbers(self)\n\n    def __repr__(self):\n        return \"<RSAPublicNumbers(e={0.e}, n={0.n})>\".format(self)\n\n    def __eq__(self, other):\n        if not isinstance(other, RSAPublicNumbers):\n            return NotImplemented\n\n        return self.e == other.e and self.n == other.n\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((self.e, self.n))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/asymmetric/utils.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import utils\nfrom cryptography.hazmat._der import (\n    DERReader, INTEGER, SEQUENCE, encode_der, encode_der_integer\n)\nfrom cryptography.hazmat.primitives import hashes\n\n\ndef decode_dss_signature(signature):\n    with DERReader(signature).read_single_element(SEQUENCE) as seq:\n        r = seq.read_element(INTEGER).as_integer()\n        s = seq.read_element(INTEGER).as_integer()\n        return r, s\n\n\ndef encode_dss_signature(r, s):\n    return encode_der(\n        SEQUENCE,\n        encode_der(INTEGER, encode_der_integer(r)),\n        encode_der(INTEGER, encode_der_integer(s)),\n    )\n\n\nclass Prehashed(object):\n    def __init__(self, algorithm):\n        if not isinstance(algorithm, hashes.HashAlgorithm):\n            raise TypeError(\"Expected instance of HashAlgorithm.\")\n\n        self._algorithm = algorithm\n        self._digest_size = algorithm.digest_size\n\n    digest_size = utils.read_only_property(\"_digest_size\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/asymmetric/x25519.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\nfrom cryptography.exceptions import UnsupportedAlgorithm, _Reasons\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass X25519PublicKey(object):\n    @classmethod\n    def from_public_bytes(cls, data):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.x25519_supported():\n            raise UnsupportedAlgorithm(\n                \"X25519 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_EXCHANGE_ALGORITHM\n            )\n\n        return backend.x25519_load_public_bytes(data)\n\n    @abc.abstractmethod\n    def public_bytes(self, encoding=None, format=None):\n        \"\"\"\n        The serialized bytes of the public key.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass X25519PrivateKey(object):\n    @classmethod\n    def generate(cls):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.x25519_supported():\n            raise UnsupportedAlgorithm(\n                \"X25519 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_EXCHANGE_ALGORITHM\n            )\n        return backend.x25519_generate_key()\n\n    @classmethod\n    def from_private_bytes(cls, data):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.x25519_supported():\n            raise UnsupportedAlgorithm(\n                \"X25519 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_EXCHANGE_ALGORITHM\n            )\n\n        return backend.x25519_load_private_bytes(data)\n\n    @abc.abstractmethod\n    def public_key(self):\n        \"\"\"\n        The serialized bytes of the public key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        \"\"\"\n        The serialized bytes of the private key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def exchange(self, peer_public_key):\n        \"\"\"\n        Performs a key exchange operation using the provided peer's public key.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/asymmetric/x448.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\nfrom cryptography.exceptions import UnsupportedAlgorithm, _Reasons\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass X448PublicKey(object):\n    @classmethod\n    def from_public_bytes(cls, data):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.x448_supported():\n            raise UnsupportedAlgorithm(\n                \"X448 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_EXCHANGE_ALGORITHM\n            )\n\n        return backend.x448_load_public_bytes(data)\n\n    @abc.abstractmethod\n    def public_bytes(self, encoding, format):\n        \"\"\"\n        The serialized bytes of the public key.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass X448PrivateKey(object):\n    @classmethod\n    def generate(cls):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.x448_supported():\n            raise UnsupportedAlgorithm(\n                \"X448 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_EXCHANGE_ALGORITHM\n            )\n        return backend.x448_generate_key()\n\n    @classmethod\n    def from_private_bytes(cls, data):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.x448_supported():\n            raise UnsupportedAlgorithm(\n                \"X448 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_EXCHANGE_ALGORITHM\n            )\n\n        return backend.x448_load_private_bytes(data)\n\n    @abc.abstractmethod\n    def public_key(self):\n        \"\"\"\n        The serialized bytes of the public key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def private_bytes(self, encoding, format, encryption_algorithm):\n        \"\"\"\n        The serialized bytes of the private key.\n        \"\"\"\n\n    @abc.abstractmethod\n    def exchange(self, peer_public_key):\n        \"\"\"\n        Performs a key exchange operation using the provided peer's public key.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/ciphers/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography.hazmat.primitives.ciphers.base import (\n    AEADCipherContext, AEADDecryptionContext, AEADEncryptionContext,\n    BlockCipherAlgorithm, Cipher, CipherAlgorithm, CipherContext\n)\n\n\n__all__ = [\n    \"Cipher\",\n    \"CipherAlgorithm\",\n    \"BlockCipherAlgorithm\",\n    \"CipherContext\",\n    \"AEADCipherContext\",\n    \"AEADDecryptionContext\",\n    \"AEADEncryptionContext\",\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/ciphers/aead.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport os\n\nfrom cryptography import exceptions, utils\nfrom cryptography.hazmat.backends.openssl import aead\nfrom cryptography.hazmat.backends.openssl.backend import backend\n\n\nclass ChaCha20Poly1305(object):\n    _MAX_SIZE = 2 ** 32\n\n    def __init__(self, key):\n        if not backend.aead_cipher_supported(self):\n            raise exceptions.UnsupportedAlgorithm(\n                \"ChaCha20Poly1305 is not supported by this version of OpenSSL\",\n                exceptions._Reasons.UNSUPPORTED_CIPHER\n            )\n        utils._check_byteslike(\"key\", key)\n\n        if len(key) != 32:\n            raise ValueError(\"ChaCha20Poly1305 key must be 32 bytes.\")\n\n        self._key = key\n\n    @classmethod\n    def generate_key(cls):\n        return os.urandom(32)\n\n    def encrypt(self, nonce, data, associated_data):\n        if associated_data is None:\n            associated_data = b\"\"\n\n        if len(data) > self._MAX_SIZE or len(associated_data) > self._MAX_SIZE:\n            # This is OverflowError to match what cffi would raise\n            raise OverflowError(\n                \"Data or associated data too long. Max 2**32 bytes\"\n            )\n\n        self._check_params(nonce, data, associated_data)\n        return aead._encrypt(\n            backend, self, nonce, data, associated_data, 16\n        )\n\n    def decrypt(self, nonce, data, associated_data):\n        if associated_data is None:\n            associated_data = b\"\"\n\n        self._check_params(nonce, data, associated_data)\n        return aead._decrypt(\n            backend, self, nonce, data, associated_data, 16\n        )\n\n    def _check_params(self, nonce, data, associated_data):\n        utils._check_byteslike(\"nonce\", nonce)\n        utils._check_bytes(\"data\", data)\n        utils._check_bytes(\"associated_data\", associated_data)\n        if len(nonce) != 12:\n            raise ValueError(\"Nonce must be 12 bytes\")\n\n\nclass AESCCM(object):\n    _MAX_SIZE = 2 ** 32\n\n    def __init__(self, key, tag_length=16):\n        utils._check_byteslike(\"key\", key)\n        if len(key) not in (16, 24, 32):\n            raise ValueError(\"AESCCM key must be 128, 192, or 256 bits.\")\n\n        self._key = key\n        if not isinstance(tag_length, int):\n            raise TypeError(\"tag_length must be an integer\")\n\n        if tag_length not in (4, 6, 8, 10, 12, 14, 16):\n            raise ValueError(\"Invalid tag_length\")\n\n        self._tag_length = tag_length\n\n        if not backend.aead_cipher_supported(self):\n            raise exceptions.UnsupportedAlgorithm(\n                \"AESCCM is not supported by this version of OpenSSL\",\n                exceptions._Reasons.UNSUPPORTED_CIPHER\n            )\n\n    @classmethod\n    def generate_key(cls, bit_length):\n        if not isinstance(bit_length, int):\n            raise TypeError(\"bit_length must be an integer\")\n\n        if bit_length not in (128, 192, 256):\n            raise ValueError(\"bit_length must be 128, 192, or 256\")\n\n        return os.urandom(bit_length // 8)\n\n    def encrypt(self, nonce, data, associated_data):\n        if associated_data is None:\n            associated_data = b\"\"\n\n        if len(data) > self._MAX_SIZE or len(associated_data) > self._MAX_SIZE:\n            # This is OverflowError to match what cffi would raise\n            raise OverflowError(\n                \"Data or associated data too long. Max 2**32 bytes\"\n            )\n\n        self._check_params(nonce, data, associated_data)\n        self._validate_lengths(nonce, len(data))\n        return aead._encrypt(\n            backend, self, nonce, data, associated_data, self._tag_length\n        )\n\n    def decrypt(self, nonce, data, associated_data):\n        if associated_data is None:\n            associated_data = b\"\"\n\n        self._check_params(nonce, data, associated_data)\n        return aead._decrypt(\n            backend, self, nonce, data, associated_data, self._tag_length\n        )\n\n    def _validate_lengths(self, nonce, data_len):\n        # For information about computing this, see\n        # https://tools.ietf.org/html/rfc3610#section-2.1\n        l_val = 15 - len(nonce)\n        if 2 ** (8 * l_val) < data_len:\n            raise ValueError(\"Nonce too long for data\")\n\n    def _check_params(self, nonce, data, associated_data):\n        utils._check_byteslike(\"nonce\", nonce)\n        utils._check_bytes(\"data\", data)\n        utils._check_bytes(\"associated_data\", associated_data)\n        if not 7 <= len(nonce) <= 13:\n            raise ValueError(\"Nonce must be between 7 and 13 bytes\")\n\n\nclass AESGCM(object):\n    _MAX_SIZE = 2 ** 32\n\n    def __init__(self, key):\n        utils._check_byteslike(\"key\", key)\n        if len(key) not in (16, 24, 32):\n            raise ValueError(\"AESGCM key must be 128, 192, or 256 bits.\")\n\n        self._key = key\n\n    @classmethod\n    def generate_key(cls, bit_length):\n        if not isinstance(bit_length, int):\n            raise TypeError(\"bit_length must be an integer\")\n\n        if bit_length not in (128, 192, 256):\n            raise ValueError(\"bit_length must be 128, 192, or 256\")\n\n        return os.urandom(bit_length // 8)\n\n    def encrypt(self, nonce, data, associated_data):\n        if associated_data is None:\n            associated_data = b\"\"\n\n        if len(data) > self._MAX_SIZE or len(associated_data) > self._MAX_SIZE:\n            # This is OverflowError to match what cffi would raise\n            raise OverflowError(\n                \"Data or associated data too long. Max 2**32 bytes\"\n            )\n\n        self._check_params(nonce, data, associated_data)\n        return aead._encrypt(\n            backend, self, nonce, data, associated_data, 16\n        )\n\n    def decrypt(self, nonce, data, associated_data):\n        if associated_data is None:\n            associated_data = b\"\"\n\n        self._check_params(nonce, data, associated_data)\n        return aead._decrypt(\n            backend, self, nonce, data, associated_data, 16\n        )\n\n    def _check_params(self, nonce, data, associated_data):\n        utils._check_byteslike(\"nonce\", nonce)\n        utils._check_bytes(\"data\", data)\n        utils._check_bytes(\"associated_data\", associated_data)\n        if len(nonce) == 0:\n            raise ValueError(\"Nonce must be at least 1 byte\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/ciphers/algorithms.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import utils\nfrom cryptography.hazmat.primitives.ciphers import (\n    BlockCipherAlgorithm, CipherAlgorithm\n)\nfrom cryptography.hazmat.primitives.ciphers.modes import ModeWithNonce\n\n\ndef _verify_key_size(algorithm, key):\n    # Verify that the key is instance of bytes\n    utils._check_byteslike(\"key\", key)\n\n    # Verify that the key size matches the expected key size\n    if len(key) * 8 not in algorithm.key_sizes:\n        raise ValueError(\"Invalid key size ({}) for {}.\".format(\n            len(key) * 8, algorithm.name\n        ))\n    return key\n\n\n@utils.register_interface(BlockCipherAlgorithm)\n@utils.register_interface(CipherAlgorithm)\nclass AES(object):\n    name = \"AES\"\n    block_size = 128\n    # 512 added to support AES-256-XTS, which uses 512-bit keys\n    key_sizes = frozenset([128, 192, 256, 512])\n\n    def __init__(self, key):\n        self.key = _verify_key_size(self, key)\n\n    @property\n    def key_size(self):\n        return len(self.key) * 8\n\n\n@utils.register_interface(BlockCipherAlgorithm)\n@utils.register_interface(CipherAlgorithm)\nclass Camellia(object):\n    name = \"camellia\"\n    block_size = 128\n    key_sizes = frozenset([128, 192, 256])\n\n    def __init__(self, key):\n        self.key = _verify_key_size(self, key)\n\n    @property\n    def key_size(self):\n        return len(self.key) * 8\n\n\n@utils.register_interface(BlockCipherAlgorithm)\n@utils.register_interface(CipherAlgorithm)\nclass TripleDES(object):\n    name = \"3DES\"\n    block_size = 64\n    key_sizes = frozenset([64, 128, 192])\n\n    def __init__(self, key):\n        if len(key) == 8:\n            key += key + key\n        elif len(key) == 16:\n            key += key[:8]\n        self.key = _verify_key_size(self, key)\n\n    @property\n    def key_size(self):\n        return len(self.key) * 8\n\n\n@utils.register_interface(BlockCipherAlgorithm)\n@utils.register_interface(CipherAlgorithm)\nclass Blowfish(object):\n    name = \"Blowfish\"\n    block_size = 64\n    key_sizes = frozenset(range(32, 449, 8))\n\n    def __init__(self, key):\n        self.key = _verify_key_size(self, key)\n\n    @property\n    def key_size(self):\n        return len(self.key) * 8\n\n\n@utils.register_interface(BlockCipherAlgorithm)\n@utils.register_interface(CipherAlgorithm)\nclass CAST5(object):\n    name = \"CAST5\"\n    block_size = 64\n    key_sizes = frozenset(range(40, 129, 8))\n\n    def __init__(self, key):\n        self.key = _verify_key_size(self, key)\n\n    @property\n    def key_size(self):\n        return len(self.key) * 8\n\n\n@utils.register_interface(CipherAlgorithm)\nclass ARC4(object):\n    name = \"RC4\"\n    key_sizes = frozenset([40, 56, 64, 80, 128, 160, 192, 256])\n\n    def __init__(self, key):\n        self.key = _verify_key_size(self, key)\n\n    @property\n    def key_size(self):\n        return len(self.key) * 8\n\n\n@utils.register_interface(CipherAlgorithm)\nclass IDEA(object):\n    name = \"IDEA\"\n    block_size = 64\n    key_sizes = frozenset([128])\n\n    def __init__(self, key):\n        self.key = _verify_key_size(self, key)\n\n    @property\n    def key_size(self):\n        return len(self.key) * 8\n\n\n@utils.register_interface(BlockCipherAlgorithm)\n@utils.register_interface(CipherAlgorithm)\nclass SEED(object):\n    name = \"SEED\"\n    block_size = 128\n    key_sizes = frozenset([128])\n\n    def __init__(self, key):\n        self.key = _verify_key_size(self, key)\n\n    @property\n    def key_size(self):\n        return len(self.key) * 8\n\n\n@utils.register_interface(CipherAlgorithm)\n@utils.register_interface(ModeWithNonce)\nclass ChaCha20(object):\n    name = \"ChaCha20\"\n    key_sizes = frozenset([256])\n\n    def __init__(self, key, nonce):\n        self.key = _verify_key_size(self, key)\n        utils._check_byteslike(\"nonce\", nonce)\n\n        if len(nonce) != 16:\n            raise ValueError(\"nonce must be 128-bits (16 bytes)\")\n\n        self._nonce = nonce\n\n    nonce = utils.read_only_property(\"_nonce\")\n\n    @property\n    def key_size(self):\n        return len(self.key) * 8\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/ciphers/base.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    AlreadyFinalized, AlreadyUpdated, NotYetFinalized, UnsupportedAlgorithm,\n    _Reasons\n)\nfrom cryptography.hazmat.backends.interfaces import CipherBackend\nfrom cryptography.hazmat.primitives.ciphers import modes\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass CipherAlgorithm(object):\n    @abc.abstractproperty\n    def name(self):\n        \"\"\"\n        A string naming this mode (e.g. \"AES\", \"Camellia\").\n        \"\"\"\n\n    @abc.abstractproperty\n    def key_size(self):\n        \"\"\"\n        The size of the key being used as an integer in bits (e.g. 128, 256).\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass BlockCipherAlgorithm(object):\n    @abc.abstractproperty\n    def block_size(self):\n        \"\"\"\n        The size of a block as an integer in bits (e.g. 64, 128).\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass CipherContext(object):\n    @abc.abstractmethod\n    def update(self, data):\n        \"\"\"\n        Processes the provided bytes through the cipher and returns the results\n        as bytes.\n        \"\"\"\n\n    @abc.abstractmethod\n    def update_into(self, data, buf):\n        \"\"\"\n        Processes the provided bytes and writes the resulting data into the\n        provided buffer. Returns the number of bytes written.\n        \"\"\"\n\n    @abc.abstractmethod\n    def finalize(self):\n        \"\"\"\n        Returns the results of processing the final block as bytes.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass AEADCipherContext(object):\n    @abc.abstractmethod\n    def authenticate_additional_data(self, data):\n        \"\"\"\n        Authenticates the provided bytes.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass AEADDecryptionContext(object):\n    @abc.abstractmethod\n    def finalize_with_tag(self, tag):\n        \"\"\"\n        Returns the results of processing the final block as bytes and allows\n        delayed passing of the authentication tag.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass AEADEncryptionContext(object):\n    @abc.abstractproperty\n    def tag(self):\n        \"\"\"\n        Returns tag bytes. This is only available after encryption is\n        finalized.\n        \"\"\"\n\n\nclass Cipher(object):\n    def __init__(self, algorithm, mode, backend):\n        if not isinstance(backend, CipherBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement CipherBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n\n        if not isinstance(algorithm, CipherAlgorithm):\n            raise TypeError(\"Expected interface of CipherAlgorithm.\")\n\n        if mode is not None:\n            mode.validate_for_algorithm(algorithm)\n\n        self.algorithm = algorithm\n        self.mode = mode\n        self._backend = backend\n\n    def encryptor(self):\n        if isinstance(self.mode, modes.ModeWithAuthenticationTag):\n            if self.mode.tag is not None:\n                raise ValueError(\n                    \"Authentication tag must be None when encrypting.\"\n                )\n        ctx = self._backend.create_symmetric_encryption_ctx(\n            self.algorithm, self.mode\n        )\n        return self._wrap_ctx(ctx, encrypt=True)\n\n    def decryptor(self):\n        ctx = self._backend.create_symmetric_decryption_ctx(\n            self.algorithm, self.mode\n        )\n        return self._wrap_ctx(ctx, encrypt=False)\n\n    def _wrap_ctx(self, ctx, encrypt):\n        if isinstance(self.mode, modes.ModeWithAuthenticationTag):\n            if encrypt:\n                return _AEADEncryptionContext(ctx)\n            else:\n                return _AEADCipherContext(ctx)\n        else:\n            return _CipherContext(ctx)\n\n\n@utils.register_interface(CipherContext)\nclass _CipherContext(object):\n    def __init__(self, ctx):\n        self._ctx = ctx\n\n    def update(self, data):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        return self._ctx.update(data)\n\n    def update_into(self, data, buf):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        return self._ctx.update_into(data, buf)\n\n    def finalize(self):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        data = self._ctx.finalize()\n        self._ctx = None\n        return data\n\n\n@utils.register_interface(AEADCipherContext)\n@utils.register_interface(CipherContext)\n@utils.register_interface(AEADDecryptionContext)\nclass _AEADCipherContext(object):\n    def __init__(self, ctx):\n        self._ctx = ctx\n        self._bytes_processed = 0\n        self._aad_bytes_processed = 0\n        self._tag = None\n        self._updated = False\n\n    def _check_limit(self, data_size):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        self._updated = True\n        self._bytes_processed += data_size\n        if self._bytes_processed > self._ctx._mode._MAX_ENCRYPTED_BYTES:\n            raise ValueError(\n                \"{} has a maximum encrypted byte limit of {}\".format(\n                    self._ctx._mode.name, self._ctx._mode._MAX_ENCRYPTED_BYTES\n                )\n            )\n\n    def update(self, data):\n        self._check_limit(len(data))\n        return self._ctx.update(data)\n\n    def update_into(self, data, buf):\n        self._check_limit(len(data))\n        return self._ctx.update_into(data, buf)\n\n    def finalize(self):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        data = self._ctx.finalize()\n        self._tag = self._ctx.tag\n        self._ctx = None\n        return data\n\n    def finalize_with_tag(self, tag):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        data = self._ctx.finalize_with_tag(tag)\n        self._tag = self._ctx.tag\n        self._ctx = None\n        return data\n\n    def authenticate_additional_data(self, data):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        if self._updated:\n            raise AlreadyUpdated(\"Update has been called on this context.\")\n\n        self._aad_bytes_processed += len(data)\n        if self._aad_bytes_processed > self._ctx._mode._MAX_AAD_BYTES:\n            raise ValueError(\n                \"{} has a maximum AAD byte limit of {}\".format(\n                    self._ctx._mode.name, self._ctx._mode._MAX_AAD_BYTES\n                )\n            )\n\n        self._ctx.authenticate_additional_data(data)\n\n\n@utils.register_interface(AEADEncryptionContext)\nclass _AEADEncryptionContext(_AEADCipherContext):\n    @property\n    def tag(self):\n        if self._ctx is not None:\n            raise NotYetFinalized(\"You must finalize encryption before \"\n                                  \"getting the tag.\")\n        return self._tag\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/ciphers/modes.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\nfrom cryptography import utils\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass Mode(object):\n    @abc.abstractproperty\n    def name(self):\n        \"\"\"\n        A string naming this mode (e.g. \"ECB\", \"CBC\").\n        \"\"\"\n\n    @abc.abstractmethod\n    def validate_for_algorithm(self, algorithm):\n        \"\"\"\n        Checks that all the necessary invariants of this (mode, algorithm)\n        combination are met.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass ModeWithInitializationVector(object):\n    @abc.abstractproperty\n    def initialization_vector(self):\n        \"\"\"\n        The value of the initialization vector for this mode as bytes.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass ModeWithTweak(object):\n    @abc.abstractproperty\n    def tweak(self):\n        \"\"\"\n        The value of the tweak for this mode as bytes.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass ModeWithNonce(object):\n    @abc.abstractproperty\n    def nonce(self):\n        \"\"\"\n        The value of the nonce for this mode as bytes.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass ModeWithAuthenticationTag(object):\n    @abc.abstractproperty\n    def tag(self):\n        \"\"\"\n        The value of the tag supplied to the constructor of this mode.\n        \"\"\"\n\n\ndef _check_aes_key_length(self, algorithm):\n    if algorithm.key_size > 256 and algorithm.name == \"AES\":\n        raise ValueError(\n            \"Only 128, 192, and 256 bit keys are allowed for this AES mode\"\n        )\n\n\ndef _check_iv_length(self, algorithm):\n    if len(self.initialization_vector) * 8 != algorithm.block_size:\n        raise ValueError(\"Invalid IV size ({}) for {}.\".format(\n            len(self.initialization_vector), self.name\n        ))\n\n\ndef _check_iv_and_key_length(self, algorithm):\n    _check_aes_key_length(self, algorithm)\n    _check_iv_length(self, algorithm)\n\n\n@utils.register_interface(Mode)\n@utils.register_interface(ModeWithInitializationVector)\nclass CBC(object):\n    name = \"CBC\"\n\n    def __init__(self, initialization_vector):\n        utils._check_byteslike(\"initialization_vector\", initialization_vector)\n        self._initialization_vector = initialization_vector\n\n    initialization_vector = utils.read_only_property(\"_initialization_vector\")\n    validate_for_algorithm = _check_iv_and_key_length\n\n\n@utils.register_interface(Mode)\n@utils.register_interface(ModeWithTweak)\nclass XTS(object):\n    name = \"XTS\"\n\n    def __init__(self, tweak):\n        utils._check_byteslike(\"tweak\", tweak)\n\n        if len(tweak) != 16:\n            raise ValueError(\"tweak must be 128-bits (16 bytes)\")\n\n        self._tweak = tweak\n\n    tweak = utils.read_only_property(\"_tweak\")\n\n    def validate_for_algorithm(self, algorithm):\n        if algorithm.key_size not in (256, 512):\n            raise ValueError(\n                \"The XTS specification requires a 256-bit key for AES-128-XTS\"\n                \" and 512-bit key for AES-256-XTS\"\n            )\n\n\n@utils.register_interface(Mode)\nclass ECB(object):\n    name = \"ECB\"\n\n    validate_for_algorithm = _check_aes_key_length\n\n\n@utils.register_interface(Mode)\n@utils.register_interface(ModeWithInitializationVector)\nclass OFB(object):\n    name = \"OFB\"\n\n    def __init__(self, initialization_vector):\n        utils._check_byteslike(\"initialization_vector\", initialization_vector)\n        self._initialization_vector = initialization_vector\n\n    initialization_vector = utils.read_only_property(\"_initialization_vector\")\n    validate_for_algorithm = _check_iv_and_key_length\n\n\n@utils.register_interface(Mode)\n@utils.register_interface(ModeWithInitializationVector)\nclass CFB(object):\n    name = \"CFB\"\n\n    def __init__(self, initialization_vector):\n        utils._check_byteslike(\"initialization_vector\", initialization_vector)\n        self._initialization_vector = initialization_vector\n\n    initialization_vector = utils.read_only_property(\"_initialization_vector\")\n    validate_for_algorithm = _check_iv_and_key_length\n\n\n@utils.register_interface(Mode)\n@utils.register_interface(ModeWithInitializationVector)\nclass CFB8(object):\n    name = \"CFB8\"\n\n    def __init__(self, initialization_vector):\n        utils._check_byteslike(\"initialization_vector\", initialization_vector)\n        self._initialization_vector = initialization_vector\n\n    initialization_vector = utils.read_only_property(\"_initialization_vector\")\n    validate_for_algorithm = _check_iv_and_key_length\n\n\n@utils.register_interface(Mode)\n@utils.register_interface(ModeWithNonce)\nclass CTR(object):\n    name = \"CTR\"\n\n    def __init__(self, nonce):\n        utils._check_byteslike(\"nonce\", nonce)\n        self._nonce = nonce\n\n    nonce = utils.read_only_property(\"_nonce\")\n\n    def validate_for_algorithm(self, algorithm):\n        _check_aes_key_length(self, algorithm)\n        if len(self.nonce) * 8 != algorithm.block_size:\n            raise ValueError(\"Invalid nonce size ({}) for {}.\".format(\n                len(self.nonce), self.name\n            ))\n\n\n@utils.register_interface(Mode)\n@utils.register_interface(ModeWithInitializationVector)\n@utils.register_interface(ModeWithAuthenticationTag)\nclass GCM(object):\n    name = \"GCM\"\n    _MAX_ENCRYPTED_BYTES = (2 ** 39 - 256) // 8\n    _MAX_AAD_BYTES = (2 ** 64) // 8\n\n    def __init__(self, initialization_vector, tag=None, min_tag_length=16):\n        # len(initialization_vector) must in [1, 2 ** 64), but it's impossible\n        # to actually construct a bytes object that large, so we don't check\n        # for it\n        utils._check_byteslike(\"initialization_vector\", initialization_vector)\n        if len(initialization_vector) == 0:\n            raise ValueError(\"initialization_vector must be at least 1 byte\")\n        self._initialization_vector = initialization_vector\n        if tag is not None:\n            utils._check_bytes(\"tag\", tag)\n            if min_tag_length < 4:\n                raise ValueError(\"min_tag_length must be >= 4\")\n            if len(tag) < min_tag_length:\n                raise ValueError(\n                    \"Authentication tag must be {} bytes or longer.\".format(\n                        min_tag_length)\n                )\n        self._tag = tag\n        self._min_tag_length = min_tag_length\n\n    tag = utils.read_only_property(\"_tag\")\n    initialization_vector = utils.read_only_property(\"_initialization_vector\")\n\n    def validate_for_algorithm(self, algorithm):\n        _check_aes_key_length(self, algorithm)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/cmac.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    AlreadyFinalized, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.interfaces import CMACBackend\nfrom cryptography.hazmat.primitives import ciphers\n\n\nclass CMAC(object):\n    def __init__(self, algorithm, backend, ctx=None):\n        if not isinstance(backend, CMACBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement CMACBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n\n        if not isinstance(algorithm, ciphers.BlockCipherAlgorithm):\n            raise TypeError(\n                \"Expected instance of BlockCipherAlgorithm.\"\n            )\n        self._algorithm = algorithm\n\n        self._backend = backend\n        if ctx is None:\n            self._ctx = self._backend.create_cmac_ctx(self._algorithm)\n        else:\n            self._ctx = ctx\n\n    def update(self, data):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n\n        utils._check_bytes(\"data\", data)\n        self._ctx.update(data)\n\n    def finalize(self):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        digest = self._ctx.finalize()\n        self._ctx = None\n        return digest\n\n    def verify(self, signature):\n        utils._check_bytes(\"signature\", signature)\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n\n        ctx, self._ctx = self._ctx, None\n        ctx.verify(signature)\n\n    def copy(self):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        return CMAC(\n            self._algorithm,\n            backend=self._backend,\n            ctx=self._ctx.copy()\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/constant_time.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport hmac\nimport warnings\n\nfrom cryptography import utils\nfrom cryptography.hazmat.bindings._constant_time import lib\n\n\nif hasattr(hmac, \"compare_digest\"):\n    def bytes_eq(a, b):\n        if not isinstance(a, bytes) or not isinstance(b, bytes):\n            raise TypeError(\"a and b must be bytes.\")\n\n        return hmac.compare_digest(a, b)\n\nelse:\n    warnings.warn(\n        \"Support for your Python version is deprecated. The next version of \"\n        \"cryptography will remove support. Please upgrade to a release \"\n        \"(2.7.7+) that supports hmac.compare_digest as soon as possible.\",\n        utils.PersistentlyDeprecated2018,\n    )\n\n    def bytes_eq(a, b):\n        if not isinstance(a, bytes) or not isinstance(b, bytes):\n            raise TypeError(\"a and b must be bytes.\")\n\n        return lib.Cryptography_constant_time_bytes_eq(\n            a, len(a), b, len(b)\n        ) == 1\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/hashes.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    AlreadyFinalized, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.interfaces import HashBackend\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass HashAlgorithm(object):\n    @abc.abstractproperty\n    def name(self):\n        \"\"\"\n        A string naming this algorithm (e.g. \"sha256\", \"md5\").\n        \"\"\"\n\n    @abc.abstractproperty\n    def digest_size(self):\n        \"\"\"\n        The size of the resulting digest in bytes.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass HashContext(object):\n    @abc.abstractproperty\n    def algorithm(self):\n        \"\"\"\n        A HashAlgorithm that will be used by this context.\n        \"\"\"\n\n    @abc.abstractmethod\n    def update(self, data):\n        \"\"\"\n        Processes the provided bytes through the hash.\n        \"\"\"\n\n    @abc.abstractmethod\n    def finalize(self):\n        \"\"\"\n        Finalizes the hash context and returns the hash digest as bytes.\n        \"\"\"\n\n    @abc.abstractmethod\n    def copy(self):\n        \"\"\"\n        Return a HashContext that is a copy of the current context.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass ExtendableOutputFunction(object):\n    \"\"\"\n    An interface for extendable output functions.\n    \"\"\"\n\n\n@utils.register_interface(HashContext)\nclass Hash(object):\n    def __init__(self, algorithm, backend, ctx=None):\n        if not isinstance(backend, HashBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement HashBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n\n        if not isinstance(algorithm, HashAlgorithm):\n            raise TypeError(\"Expected instance of hashes.HashAlgorithm.\")\n        self._algorithm = algorithm\n\n        self._backend = backend\n\n        if ctx is None:\n            self._ctx = self._backend.create_hash_ctx(self.algorithm)\n        else:\n            self._ctx = ctx\n\n    algorithm = utils.read_only_property(\"_algorithm\")\n\n    def update(self, data):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        utils._check_byteslike(\"data\", data)\n        self._ctx.update(data)\n\n    def copy(self):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        return Hash(\n            self.algorithm, backend=self._backend, ctx=self._ctx.copy()\n        )\n\n    def finalize(self):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        digest = self._ctx.finalize()\n        self._ctx = None\n        return digest\n\n\n@utils.register_interface(HashAlgorithm)\nclass SHA1(object):\n    name = \"sha1\"\n    digest_size = 20\n    block_size = 64\n\n\n@utils.register_interface(HashAlgorithm)\nclass SHA512_224(object):  # noqa: N801\n    name = \"sha512-224\"\n    digest_size = 28\n    block_size = 128\n\n\n@utils.register_interface(HashAlgorithm)\nclass SHA512_256(object):  # noqa: N801\n    name = \"sha512-256\"\n    digest_size = 32\n    block_size = 128\n\n\n@utils.register_interface(HashAlgorithm)\nclass SHA224(object):\n    name = \"sha224\"\n    digest_size = 28\n    block_size = 64\n\n\n@utils.register_interface(HashAlgorithm)\nclass SHA256(object):\n    name = \"sha256\"\n    digest_size = 32\n    block_size = 64\n\n\n@utils.register_interface(HashAlgorithm)\nclass SHA384(object):\n    name = \"sha384\"\n    digest_size = 48\n    block_size = 128\n\n\n@utils.register_interface(HashAlgorithm)\nclass SHA512(object):\n    name = \"sha512\"\n    digest_size = 64\n    block_size = 128\n\n\n@utils.register_interface(HashAlgorithm)\nclass SHA3_224(object):  # noqa: N801\n    name = \"sha3-224\"\n    digest_size = 28\n\n\n@utils.register_interface(HashAlgorithm)\nclass SHA3_256(object):  # noqa: N801\n    name = \"sha3-256\"\n    digest_size = 32\n\n\n@utils.register_interface(HashAlgorithm)\nclass SHA3_384(object):  # noqa: N801\n    name = \"sha3-384\"\n    digest_size = 48\n\n\n@utils.register_interface(HashAlgorithm)\nclass SHA3_512(object):  # noqa: N801\n    name = \"sha3-512\"\n    digest_size = 64\n\n\n@utils.register_interface(HashAlgorithm)\n@utils.register_interface(ExtendableOutputFunction)\nclass SHAKE128(object):\n    name = \"shake128\"\n\n    def __init__(self, digest_size):\n        if not isinstance(digest_size, six.integer_types):\n            raise TypeError(\"digest_size must be an integer\")\n\n        if digest_size < 1:\n            raise ValueError(\"digest_size must be a positive integer\")\n\n        self._digest_size = digest_size\n\n    digest_size = utils.read_only_property(\"_digest_size\")\n\n\n@utils.register_interface(HashAlgorithm)\n@utils.register_interface(ExtendableOutputFunction)\nclass SHAKE256(object):\n    name = \"shake256\"\n\n    def __init__(self, digest_size):\n        if not isinstance(digest_size, six.integer_types):\n            raise TypeError(\"digest_size must be an integer\")\n\n        if digest_size < 1:\n            raise ValueError(\"digest_size must be a positive integer\")\n\n        self._digest_size = digest_size\n\n    digest_size = utils.read_only_property(\"_digest_size\")\n\n\n@utils.register_interface(HashAlgorithm)\nclass MD5(object):\n    name = \"md5\"\n    digest_size = 16\n    block_size = 64\n\n\n@utils.register_interface(HashAlgorithm)\nclass BLAKE2b(object):\n    name = \"blake2b\"\n    _max_digest_size = 64\n    _min_digest_size = 1\n    block_size = 128\n\n    def __init__(self, digest_size):\n\n        if digest_size != 64:\n            raise ValueError(\"Digest size must be 64\")\n\n        self._digest_size = digest_size\n\n    digest_size = utils.read_only_property(\"_digest_size\")\n\n\n@utils.register_interface(HashAlgorithm)\nclass BLAKE2s(object):\n    name = \"blake2s\"\n    block_size = 64\n    _max_digest_size = 32\n    _min_digest_size = 1\n\n    def __init__(self, digest_size):\n\n        if digest_size != 32:\n            raise ValueError(\"Digest size must be 32\")\n\n        self._digest_size = digest_size\n\n    digest_size = utils.read_only_property(\"_digest_size\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/hmac.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    AlreadyFinalized, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.interfaces import HMACBackend\nfrom cryptography.hazmat.primitives import hashes\n\n\n@utils.register_interface(hashes.HashContext)\nclass HMAC(object):\n    def __init__(self, key, algorithm, backend, ctx=None):\n        if not isinstance(backend, HMACBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement HMACBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n\n        if not isinstance(algorithm, hashes.HashAlgorithm):\n            raise TypeError(\"Expected instance of hashes.HashAlgorithm.\")\n        self._algorithm = algorithm\n\n        self._backend = backend\n        self._key = key\n        if ctx is None:\n            self._ctx = self._backend.create_hmac_ctx(key, self.algorithm)\n        else:\n            self._ctx = ctx\n\n    algorithm = utils.read_only_property(\"_algorithm\")\n\n    def update(self, data):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        utils._check_byteslike(\"data\", data)\n        self._ctx.update(data)\n\n    def copy(self):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        return HMAC(\n            self._key,\n            self.algorithm,\n            backend=self._backend,\n            ctx=self._ctx.copy()\n        )\n\n    def finalize(self):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        digest = self._ctx.finalize()\n        self._ctx = None\n        return digest\n\n    def verify(self, signature):\n        utils._check_bytes(\"signature\", signature)\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n\n        ctx, self._ctx = self._ctx, None\n        ctx.verify(signature)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/kdf/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass KeyDerivationFunction(object):\n    @abc.abstractmethod\n    def derive(self, key_material):\n        \"\"\"\n        Deterministically generates and returns a new key based on the existing\n        key material.\n        \"\"\"\n\n    @abc.abstractmethod\n    def verify(self, key_material, expected_key):\n        \"\"\"\n        Checks whether the key generated by the key material matches the\n        expected derived key. Raises an exception if they do not match.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/kdf/concatkdf.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport struct\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    AlreadyFinalized, InvalidKey, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.interfaces import HMACBackend\nfrom cryptography.hazmat.backends.interfaces import HashBackend\nfrom cryptography.hazmat.primitives import constant_time, hashes, hmac\nfrom cryptography.hazmat.primitives.kdf import KeyDerivationFunction\n\n\ndef _int_to_u32be(n):\n    return struct.pack('>I', n)\n\n\ndef _common_args_checks(algorithm, length, otherinfo):\n    max_length = algorithm.digest_size * (2 ** 32 - 1)\n    if length > max_length:\n        raise ValueError(\n            \"Can not derive keys larger than {} bits.\".format(\n                max_length\n            ))\n    if otherinfo is not None:\n        utils._check_bytes(\"otherinfo\", otherinfo)\n\n\ndef _concatkdf_derive(key_material, length, auxfn, otherinfo):\n    utils._check_byteslike(\"key_material\", key_material)\n    output = [b\"\"]\n    outlen = 0\n    counter = 1\n\n    while (length > outlen):\n        h = auxfn()\n        h.update(_int_to_u32be(counter))\n        h.update(key_material)\n        h.update(otherinfo)\n        output.append(h.finalize())\n        outlen += len(output[-1])\n        counter += 1\n\n    return b\"\".join(output)[:length]\n\n\n@utils.register_interface(KeyDerivationFunction)\nclass ConcatKDFHash(object):\n    def __init__(self, algorithm, length, otherinfo, backend):\n\n        _common_args_checks(algorithm, length, otherinfo)\n        self._algorithm = algorithm\n        self._length = length\n        self._otherinfo = otherinfo\n        if self._otherinfo is None:\n            self._otherinfo = b\"\"\n\n        if not isinstance(backend, HashBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement HashBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n        self._backend = backend\n        self._used = False\n\n    def _hash(self):\n        return hashes.Hash(self._algorithm, self._backend)\n\n    def derive(self, key_material):\n        if self._used:\n            raise AlreadyFinalized\n        self._used = True\n        return _concatkdf_derive(key_material, self._length,\n                                 self._hash, self._otherinfo)\n\n    def verify(self, key_material, expected_key):\n        if not constant_time.bytes_eq(self.derive(key_material), expected_key):\n            raise InvalidKey\n\n\n@utils.register_interface(KeyDerivationFunction)\nclass ConcatKDFHMAC(object):\n    def __init__(self, algorithm, length, salt, otherinfo, backend):\n\n        _common_args_checks(algorithm, length, otherinfo)\n        self._algorithm = algorithm\n        self._length = length\n        self._otherinfo = otherinfo\n        if self._otherinfo is None:\n            self._otherinfo = b\"\"\n\n        if salt is None:\n            salt = b\"\\x00\" * algorithm.block_size\n        else:\n            utils._check_bytes(\"salt\", salt)\n\n        self._salt = salt\n\n        if not isinstance(backend, HMACBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement HMACBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n        self._backend = backend\n        self._used = False\n\n    def _hmac(self):\n        return hmac.HMAC(self._salt, self._algorithm, self._backend)\n\n    def derive(self, key_material):\n        if self._used:\n            raise AlreadyFinalized\n        self._used = True\n        return _concatkdf_derive(key_material, self._length,\n                                 self._hmac, self._otherinfo)\n\n    def verify(self, key_material, expected_key):\n        if not constant_time.bytes_eq(self.derive(key_material), expected_key):\n            raise InvalidKey\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/kdf/hkdf.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport six\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    AlreadyFinalized, InvalidKey, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.interfaces import HMACBackend\nfrom cryptography.hazmat.primitives import constant_time, hmac\nfrom cryptography.hazmat.primitives.kdf import KeyDerivationFunction\n\n\n@utils.register_interface(KeyDerivationFunction)\nclass HKDF(object):\n    def __init__(self, algorithm, length, salt, info, backend):\n        if not isinstance(backend, HMACBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement HMACBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n\n        self._algorithm = algorithm\n\n        if salt is None:\n            salt = b\"\\x00\" * self._algorithm.digest_size\n        else:\n            utils._check_bytes(\"salt\", salt)\n\n        self._salt = salt\n\n        self._backend = backend\n\n        self._hkdf_expand = HKDFExpand(self._algorithm, length, info, backend)\n\n    def _extract(self, key_material):\n        h = hmac.HMAC(self._salt, self._algorithm, backend=self._backend)\n        h.update(key_material)\n        return h.finalize()\n\n    def derive(self, key_material):\n        utils._check_byteslike(\"key_material\", key_material)\n        return self._hkdf_expand.derive(self._extract(key_material))\n\n    def verify(self, key_material, expected_key):\n        if not constant_time.bytes_eq(self.derive(key_material), expected_key):\n            raise InvalidKey\n\n\n@utils.register_interface(KeyDerivationFunction)\nclass HKDFExpand(object):\n    def __init__(self, algorithm, length, info, backend):\n        if not isinstance(backend, HMACBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement HMACBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n\n        self._algorithm = algorithm\n\n        self._backend = backend\n\n        max_length = 255 * algorithm.digest_size\n\n        if length > max_length:\n            raise ValueError(\n                \"Can not derive keys larger than {} octets.\".format(\n                    max_length\n                ))\n\n        self._length = length\n\n        if info is None:\n            info = b\"\"\n        else:\n            utils._check_bytes(\"info\", info)\n\n        self._info = info\n\n        self._used = False\n\n    def _expand(self, key_material):\n        output = [b\"\"]\n        counter = 1\n\n        while self._algorithm.digest_size * (len(output) - 1) < self._length:\n            h = hmac.HMAC(key_material, self._algorithm, backend=self._backend)\n            h.update(output[-1])\n            h.update(self._info)\n            h.update(six.int2byte(counter))\n            output.append(h.finalize())\n            counter += 1\n\n        return b\"\".join(output)[:self._length]\n\n    def derive(self, key_material):\n        utils._check_byteslike(\"key_material\", key_material)\n        if self._used:\n            raise AlreadyFinalized\n\n        self._used = True\n        return self._expand(key_material)\n\n    def verify(self, key_material, expected_key):\n        if not constant_time.bytes_eq(self.derive(key_material), expected_key):\n            raise InvalidKey\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/kdf/kbkdf.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom enum import Enum\n\nfrom six.moves import range\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    AlreadyFinalized, InvalidKey, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.interfaces import HMACBackend\nfrom cryptography.hazmat.primitives import constant_time, hashes, hmac\nfrom cryptography.hazmat.primitives.kdf import KeyDerivationFunction\n\n\nclass Mode(Enum):\n    CounterMode = \"ctr\"\n\n\nclass CounterLocation(Enum):\n    BeforeFixed = \"before_fixed\"\n    AfterFixed = \"after_fixed\"\n\n\n@utils.register_interface(KeyDerivationFunction)\nclass KBKDFHMAC(object):\n    def __init__(self, algorithm, mode, length, rlen, llen,\n                 location, label, context, fixed, backend):\n        if not isinstance(backend, HMACBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement HMACBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n\n        if not isinstance(algorithm, hashes.HashAlgorithm):\n            raise UnsupportedAlgorithm(\n                \"Algorithm supplied is not a supported hash algorithm.\",\n                _Reasons.UNSUPPORTED_HASH\n            )\n\n        if not backend.hmac_supported(algorithm):\n            raise UnsupportedAlgorithm(\n                \"Algorithm supplied is not a supported hmac algorithm.\",\n                _Reasons.UNSUPPORTED_HASH\n            )\n\n        if not isinstance(mode, Mode):\n            raise TypeError(\"mode must be of type Mode\")\n\n        if not isinstance(location, CounterLocation):\n            raise TypeError(\"location must be of type CounterLocation\")\n\n        if (label or context) and fixed:\n            raise ValueError(\"When supplying fixed data, \"\n                             \"label and context are ignored.\")\n\n        if rlen is None or not self._valid_byte_length(rlen):\n            raise ValueError(\"rlen must be between 1 and 4\")\n\n        if llen is None and fixed is None:\n            raise ValueError(\"Please specify an llen\")\n\n        if llen is not None and not isinstance(llen, int):\n            raise TypeError(\"llen must be an integer\")\n\n        if label is None:\n            label = b''\n\n        if context is None:\n            context = b''\n\n        utils._check_bytes(\"label\", label)\n        utils._check_bytes(\"context\", context)\n        self._algorithm = algorithm\n        self._mode = mode\n        self._length = length\n        self._rlen = rlen\n        self._llen = llen\n        self._location = location\n        self._label = label\n        self._context = context\n        self._backend = backend\n        self._used = False\n        self._fixed_data = fixed\n\n    def _valid_byte_length(self, value):\n        if not isinstance(value, int):\n            raise TypeError('value must be of type int')\n\n        value_bin = utils.int_to_bytes(1, value)\n        if not 1 <= len(value_bin) <= 4:\n            return False\n        return True\n\n    def derive(self, key_material):\n        if self._used:\n            raise AlreadyFinalized\n\n        utils._check_byteslike(\"key_material\", key_material)\n        self._used = True\n\n        # inverse floor division (equivalent to ceiling)\n        rounds = -(-self._length // self._algorithm.digest_size)\n\n        output = [b'']\n\n        # For counter mode, the number of iterations shall not be\n        # larger than 2^r-1, where r <= 32 is the binary length of the counter\n        # This ensures that the counter values used as an input to the\n        # PRF will not repeat during a particular call to the KDF function.\n        r_bin = utils.int_to_bytes(1, self._rlen)\n        if rounds > pow(2, len(r_bin) * 8) - 1:\n            raise ValueError('There are too many iterations.')\n\n        for i in range(1, rounds + 1):\n            h = hmac.HMAC(key_material, self._algorithm, backend=self._backend)\n\n            counter = utils.int_to_bytes(i, self._rlen)\n            if self._location == CounterLocation.BeforeFixed:\n                h.update(counter)\n\n            h.update(self._generate_fixed_input())\n\n            if self._location == CounterLocation.AfterFixed:\n                h.update(counter)\n\n            output.append(h.finalize())\n\n        return b''.join(output)[:self._length]\n\n    def _generate_fixed_input(self):\n        if self._fixed_data and isinstance(self._fixed_data, bytes):\n            return self._fixed_data\n\n        l_val = utils.int_to_bytes(self._length * 8, self._llen)\n\n        return b\"\".join([self._label, b\"\\x00\", self._context, l_val])\n\n    def verify(self, key_material, expected_key):\n        if not constant_time.bytes_eq(self.derive(key_material), expected_key):\n            raise InvalidKey\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/kdf/pbkdf2.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    AlreadyFinalized, InvalidKey, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.interfaces import PBKDF2HMACBackend\nfrom cryptography.hazmat.primitives import constant_time\nfrom cryptography.hazmat.primitives.kdf import KeyDerivationFunction\n\n\n@utils.register_interface(KeyDerivationFunction)\nclass PBKDF2HMAC(object):\n    def __init__(self, algorithm, length, salt, iterations, backend):\n        if not isinstance(backend, PBKDF2HMACBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement PBKDF2HMACBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n\n        if not backend.pbkdf2_hmac_supported(algorithm):\n            raise UnsupportedAlgorithm(\n                \"{} is not supported for PBKDF2 by this backend.\".format(\n                    algorithm.name),\n                _Reasons.UNSUPPORTED_HASH\n            )\n        self._used = False\n        self._algorithm = algorithm\n        self._length = length\n        utils._check_bytes(\"salt\", salt)\n        self._salt = salt\n        self._iterations = iterations\n        self._backend = backend\n\n    def derive(self, key_material):\n        if self._used:\n            raise AlreadyFinalized(\"PBKDF2 instances can only be used once.\")\n        self._used = True\n\n        utils._check_byteslike(\"key_material\", key_material)\n        return self._backend.derive_pbkdf2_hmac(\n            self._algorithm,\n            self._length,\n            self._salt,\n            self._iterations,\n            key_material\n        )\n\n    def verify(self, key_material, expected_key):\n        derived_key = self.derive(key_material)\n        if not constant_time.bytes_eq(derived_key, expected_key):\n            raise InvalidKey(\"Keys do not match.\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/kdf/scrypt.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport sys\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    AlreadyFinalized, InvalidKey, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.interfaces import ScryptBackend\nfrom cryptography.hazmat.primitives import constant_time\nfrom cryptography.hazmat.primitives.kdf import KeyDerivationFunction\n\n\n# This is used by the scrypt tests to skip tests that require more memory\n# than the MEM_LIMIT\n_MEM_LIMIT = sys.maxsize // 2\n\n\n@utils.register_interface(KeyDerivationFunction)\nclass Scrypt(object):\n    def __init__(self, salt, length, n, r, p, backend):\n        if not isinstance(backend, ScryptBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement ScryptBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n\n        self._length = length\n        utils._check_bytes(\"salt\", salt)\n        if n < 2 or (n & (n - 1)) != 0:\n            raise ValueError(\"n must be greater than 1 and be a power of 2.\")\n\n        if r < 1:\n            raise ValueError(\"r must be greater than or equal to 1.\")\n\n        if p < 1:\n            raise ValueError(\"p must be greater than or equal to 1.\")\n\n        self._used = False\n        self._salt = salt\n        self._n = n\n        self._r = r\n        self._p = p\n        self._backend = backend\n\n    def derive(self, key_material):\n        if self._used:\n            raise AlreadyFinalized(\"Scrypt instances can only be used once.\")\n        self._used = True\n\n        utils._check_byteslike(\"key_material\", key_material)\n        return self._backend.derive_scrypt(\n            key_material, self._salt, self._length, self._n, self._r, self._p\n        )\n\n    def verify(self, key_material, expected_key):\n        derived_key = self.derive(key_material)\n        if not constant_time.bytes_eq(derived_key, expected_key):\n            raise InvalidKey(\"Keys do not match.\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/kdf/x963kdf.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport struct\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    AlreadyFinalized, InvalidKey, UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.interfaces import HashBackend\nfrom cryptography.hazmat.primitives import constant_time, hashes\nfrom cryptography.hazmat.primitives.kdf import KeyDerivationFunction\n\n\ndef _int_to_u32be(n):\n    return struct.pack('>I', n)\n\n\n@utils.register_interface(KeyDerivationFunction)\nclass X963KDF(object):\n    def __init__(self, algorithm, length, sharedinfo, backend):\n\n        max_len = algorithm.digest_size * (2 ** 32 - 1)\n        if length > max_len:\n            raise ValueError(\n                \"Can not derive keys larger than {} bits.\".format(max_len))\n        if sharedinfo is not None:\n            utils._check_bytes(\"sharedinfo\", sharedinfo)\n\n        self._algorithm = algorithm\n        self._length = length\n        self._sharedinfo = sharedinfo\n\n        if not isinstance(backend, HashBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement HashBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n        self._backend = backend\n        self._used = False\n\n    def derive(self, key_material):\n        if self._used:\n            raise AlreadyFinalized\n        self._used = True\n        utils._check_byteslike(\"key_material\", key_material)\n        output = [b\"\"]\n        outlen = 0\n        counter = 1\n\n        while self._length > outlen:\n            h = hashes.Hash(self._algorithm, self._backend)\n            h.update(key_material)\n            h.update(_int_to_u32be(counter))\n            if self._sharedinfo is not None:\n                h.update(self._sharedinfo)\n            output.append(h.finalize())\n            outlen += len(output[-1])\n            counter += 1\n\n        return b\"\".join(output)[:self._length]\n\n    def verify(self, key_material, expected_key):\n        if not constant_time.bytes_eq(self.derive(key_material), expected_key):\n            raise InvalidKey\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/keywrap.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport struct\n\nfrom cryptography.hazmat.primitives.ciphers import Cipher\nfrom cryptography.hazmat.primitives.ciphers.algorithms import AES\nfrom cryptography.hazmat.primitives.ciphers.modes import ECB\nfrom cryptography.hazmat.primitives.constant_time import bytes_eq\n\n\ndef _wrap_core(wrapping_key, a, r, backend):\n    # RFC 3394 Key Wrap - 2.2.1 (index method)\n    encryptor = Cipher(AES(wrapping_key), ECB(), backend).encryptor()\n    n = len(r)\n    for j in range(6):\n        for i in range(n):\n            # every encryption operation is a discrete 16 byte chunk (because\n            # AES has a 128-bit block size) and since we're using ECB it is\n            # safe to reuse the encryptor for the entire operation\n            b = encryptor.update(a + r[i])\n            # pack/unpack are safe as these are always 64-bit chunks\n            a = struct.pack(\n                \">Q\", struct.unpack(\">Q\", b[:8])[0] ^ ((n * j) + i + 1)\n            )\n            r[i] = b[-8:]\n\n    assert encryptor.finalize() == b\"\"\n\n    return a + b\"\".join(r)\n\n\ndef aes_key_wrap(wrapping_key, key_to_wrap, backend):\n    if len(wrapping_key) not in [16, 24, 32]:\n        raise ValueError(\"The wrapping key must be a valid AES key length\")\n\n    if len(key_to_wrap) < 16:\n        raise ValueError(\"The key to wrap must be at least 16 bytes\")\n\n    if len(key_to_wrap) % 8 != 0:\n        raise ValueError(\"The key to wrap must be a multiple of 8 bytes\")\n\n    a = b\"\\xa6\\xa6\\xa6\\xa6\\xa6\\xa6\\xa6\\xa6\"\n    r = [key_to_wrap[i:i + 8] for i in range(0, len(key_to_wrap), 8)]\n    return _wrap_core(wrapping_key, a, r, backend)\n\n\ndef _unwrap_core(wrapping_key, a, r, backend):\n    # Implement RFC 3394 Key Unwrap - 2.2.2 (index method)\n    decryptor = Cipher(AES(wrapping_key), ECB(), backend).decryptor()\n    n = len(r)\n    for j in reversed(range(6)):\n        for i in reversed(range(n)):\n            # pack/unpack are safe as these are always 64-bit chunks\n            atr = struct.pack(\n                \">Q\", struct.unpack(\">Q\", a)[0] ^ ((n * j) + i + 1)\n            ) + r[i]\n            # every decryption operation is a discrete 16 byte chunk so\n            # it is safe to reuse the decryptor for the entire operation\n            b = decryptor.update(atr)\n            a = b[:8]\n            r[i] = b[-8:]\n\n    assert decryptor.finalize() == b\"\"\n    return a, r\n\n\ndef aes_key_wrap_with_padding(wrapping_key, key_to_wrap, backend):\n    if len(wrapping_key) not in [16, 24, 32]:\n        raise ValueError(\"The wrapping key must be a valid AES key length\")\n\n    aiv = b\"\\xA6\\x59\\x59\\xA6\" + struct.pack(\">i\", len(key_to_wrap))\n    # pad the key to wrap if necessary\n    pad = (8 - (len(key_to_wrap) % 8)) % 8\n    key_to_wrap = key_to_wrap + b\"\\x00\" * pad\n    if len(key_to_wrap) == 8:\n        # RFC 5649 - 4.1 - exactly 8 octets after padding\n        encryptor = Cipher(AES(wrapping_key), ECB(), backend).encryptor()\n        b = encryptor.update(aiv + key_to_wrap)\n        assert encryptor.finalize() == b\"\"\n        return b\n    else:\n        r = [key_to_wrap[i:i + 8] for i in range(0, len(key_to_wrap), 8)]\n        return _wrap_core(wrapping_key, aiv, r, backend)\n\n\ndef aes_key_unwrap_with_padding(wrapping_key, wrapped_key, backend):\n    if len(wrapped_key) < 16:\n        raise InvalidUnwrap(\"Must be at least 16 bytes\")\n\n    if len(wrapping_key) not in [16, 24, 32]:\n        raise ValueError(\"The wrapping key must be a valid AES key length\")\n\n    if len(wrapped_key) == 16:\n        # RFC 5649 - 4.2 - exactly two 64-bit blocks\n        decryptor = Cipher(AES(wrapping_key), ECB(), backend).decryptor()\n        b = decryptor.update(wrapped_key)\n        assert decryptor.finalize() == b\"\"\n        a = b[:8]\n        data = b[8:]\n        n = 1\n    else:\n        r = [wrapped_key[i:i + 8] for i in range(0, len(wrapped_key), 8)]\n        encrypted_aiv = r.pop(0)\n        n = len(r)\n        a, r = _unwrap_core(wrapping_key, encrypted_aiv, r, backend)\n        data = b\"\".join(r)\n\n    # 1) Check that MSB(32,A) = A65959A6.\n    # 2) Check that 8*(n-1) < LSB(32,A) <= 8*n.  If so, let\n    #    MLI = LSB(32,A).\n    # 3) Let b = (8*n)-MLI, and then check that the rightmost b octets of\n    #    the output data are zero.\n    (mli,) = struct.unpack(\">I\", a[4:])\n    b = (8 * n) - mli\n    if (\n        not bytes_eq(a[:4], b\"\\xa6\\x59\\x59\\xa6\") or not\n        8 * (n - 1) < mli <= 8 * n or (\n            b != 0 and not bytes_eq(data[-b:], b\"\\x00\" * b)\n        )\n    ):\n        raise InvalidUnwrap()\n\n    if b == 0:\n        return data\n    else:\n        return data[:-b]\n\n\ndef aes_key_unwrap(wrapping_key, wrapped_key, backend):\n    if len(wrapped_key) < 24:\n        raise InvalidUnwrap(\"Must be at least 24 bytes\")\n\n    if len(wrapped_key) % 8 != 0:\n        raise InvalidUnwrap(\"The wrapped key must be a multiple of 8 bytes\")\n\n    if len(wrapping_key) not in [16, 24, 32]:\n        raise ValueError(\"The wrapping key must be a valid AES key length\")\n\n    aiv = b\"\\xa6\\xa6\\xa6\\xa6\\xa6\\xa6\\xa6\\xa6\"\n    r = [wrapped_key[i:i + 8] for i in range(0, len(wrapped_key), 8)]\n    a = r.pop(0)\n    a, r = _unwrap_core(wrapping_key, a, r, backend)\n    if not bytes_eq(a, aiv):\n        raise InvalidUnwrap()\n\n    return b\"\".join(r)\n\n\nclass InvalidUnwrap(Exception):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/padding.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\n\nimport six\n\nfrom cryptography import utils\nfrom cryptography.exceptions import AlreadyFinalized\nfrom cryptography.hazmat.bindings._padding import lib\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass PaddingContext(object):\n    @abc.abstractmethod\n    def update(self, data):\n        \"\"\"\n        Pads the provided bytes and returns any available data as bytes.\n        \"\"\"\n\n    @abc.abstractmethod\n    def finalize(self):\n        \"\"\"\n        Finalize the padding, returns bytes.\n        \"\"\"\n\n\ndef _byte_padding_check(block_size):\n    if not (0 <= block_size <= 2040):\n        raise ValueError(\"block_size must be in range(0, 2041).\")\n\n    if block_size % 8 != 0:\n        raise ValueError(\"block_size must be a multiple of 8.\")\n\n\ndef _byte_padding_update(buffer_, data, block_size):\n    if buffer_ is None:\n        raise AlreadyFinalized(\"Context was already finalized.\")\n\n    utils._check_bytes(\"data\", data)\n\n    buffer_ += data\n\n    finished_blocks = len(buffer_) // (block_size // 8)\n\n    result = buffer_[:finished_blocks * (block_size // 8)]\n    buffer_ = buffer_[finished_blocks * (block_size // 8):]\n\n    return buffer_, result\n\n\ndef _byte_padding_pad(buffer_, block_size, paddingfn):\n    if buffer_ is None:\n        raise AlreadyFinalized(\"Context was already finalized.\")\n\n    pad_size = block_size // 8 - len(buffer_)\n    return buffer_ + paddingfn(pad_size)\n\n\ndef _byte_unpadding_update(buffer_, data, block_size):\n    if buffer_ is None:\n        raise AlreadyFinalized(\"Context was already finalized.\")\n\n    utils._check_bytes(\"data\", data)\n\n    buffer_ += data\n\n    finished_blocks = max(len(buffer_) // (block_size // 8) - 1, 0)\n\n    result = buffer_[:finished_blocks * (block_size // 8)]\n    buffer_ = buffer_[finished_blocks * (block_size // 8):]\n\n    return buffer_, result\n\n\ndef _byte_unpadding_check(buffer_, block_size, checkfn):\n    if buffer_ is None:\n        raise AlreadyFinalized(\"Context was already finalized.\")\n\n    if len(buffer_) != block_size // 8:\n        raise ValueError(\"Invalid padding bytes.\")\n\n    valid = checkfn(buffer_, block_size // 8)\n\n    if not valid:\n        raise ValueError(\"Invalid padding bytes.\")\n\n    pad_size = six.indexbytes(buffer_, -1)\n    return buffer_[:-pad_size]\n\n\nclass PKCS7(object):\n    def __init__(self, block_size):\n        _byte_padding_check(block_size)\n        self.block_size = block_size\n\n    def padder(self):\n        return _PKCS7PaddingContext(self.block_size)\n\n    def unpadder(self):\n        return _PKCS7UnpaddingContext(self.block_size)\n\n\n@utils.register_interface(PaddingContext)\nclass _PKCS7PaddingContext(object):\n    def __init__(self, block_size):\n        self.block_size = block_size\n        # TODO: more copies than necessary, we should use zero-buffer (#193)\n        self._buffer = b\"\"\n\n    def update(self, data):\n        self._buffer, result = _byte_padding_update(\n            self._buffer, data, self.block_size)\n        return result\n\n    def _padding(self, size):\n        return six.int2byte(size) * size\n\n    def finalize(self):\n        result = _byte_padding_pad(\n            self._buffer, self.block_size, self._padding)\n        self._buffer = None\n        return result\n\n\n@utils.register_interface(PaddingContext)\nclass _PKCS7UnpaddingContext(object):\n    def __init__(self, block_size):\n        self.block_size = block_size\n        # TODO: more copies than necessary, we should use zero-buffer (#193)\n        self._buffer = b\"\"\n\n    def update(self, data):\n        self._buffer, result = _byte_unpadding_update(\n            self._buffer, data, self.block_size)\n        return result\n\n    def finalize(self):\n        result = _byte_unpadding_check(\n            self._buffer, self.block_size,\n            lib.Cryptography_check_pkcs7_padding)\n        self._buffer = None\n        return result\n\n\nclass ANSIX923(object):\n    def __init__(self, block_size):\n        _byte_padding_check(block_size)\n        self.block_size = block_size\n\n    def padder(self):\n        return _ANSIX923PaddingContext(self.block_size)\n\n    def unpadder(self):\n        return _ANSIX923UnpaddingContext(self.block_size)\n\n\n@utils.register_interface(PaddingContext)\nclass _ANSIX923PaddingContext(object):\n    def __init__(self, block_size):\n        self.block_size = block_size\n        # TODO: more copies than necessary, we should use zero-buffer (#193)\n        self._buffer = b\"\"\n\n    def update(self, data):\n        self._buffer, result = _byte_padding_update(\n            self._buffer, data, self.block_size)\n        return result\n\n    def _padding(self, size):\n        return six.int2byte(0) * (size - 1) + six.int2byte(size)\n\n    def finalize(self):\n        result = _byte_padding_pad(\n            self._buffer, self.block_size, self._padding)\n        self._buffer = None\n        return result\n\n\n@utils.register_interface(PaddingContext)\nclass _ANSIX923UnpaddingContext(object):\n    def __init__(self, block_size):\n        self.block_size = block_size\n        # TODO: more copies than necessary, we should use zero-buffer (#193)\n        self._buffer = b\"\"\n\n    def update(self, data):\n        self._buffer, result = _byte_unpadding_update(\n            self._buffer, data, self.block_size)\n        return result\n\n    def finalize(self):\n        result = _byte_unpadding_check(\n            self._buffer, self.block_size,\n            lib.Cryptography_check_ansix923_padding)\n        self._buffer = None\n        return result\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/poly1305.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\n\nfrom cryptography import utils\nfrom cryptography.exceptions import (\n    AlreadyFinalized, UnsupportedAlgorithm, _Reasons\n)\n\n\nclass Poly1305(object):\n    def __init__(self, key):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not backend.poly1305_supported():\n            raise UnsupportedAlgorithm(\n                \"poly1305 is not supported by this version of OpenSSL.\",\n                _Reasons.UNSUPPORTED_MAC\n            )\n        self._ctx = backend.create_poly1305_ctx(key)\n\n    def update(self, data):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        utils._check_byteslike(\"data\", data)\n        self._ctx.update(data)\n\n    def finalize(self):\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n        mac = self._ctx.finalize()\n        self._ctx = None\n        return mac\n\n    def verify(self, tag):\n        utils._check_bytes(\"tag\", tag)\n        if self._ctx is None:\n            raise AlreadyFinalized(\"Context was already finalized.\")\n\n        ctx, self._ctx = self._ctx, None\n        ctx.verify(tag)\n\n    @classmethod\n    def generate_tag(cls, key, data):\n        p = Poly1305(key)\n        p.update(data)\n        return p.finalize()\n\n    @classmethod\n    def verify_tag(cls, key, data, tag):\n        p = Poly1305(key)\n        p.update(data)\n        p.verify(tag)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/serialization/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography.hazmat.primitives.serialization.base import (\n    BestAvailableEncryption, Encoding, KeySerializationEncryption,\n    NoEncryption, ParameterFormat, PrivateFormat, PublicFormat,\n    load_der_parameters, load_der_private_key, load_der_public_key,\n    load_pem_parameters, load_pem_private_key, load_pem_public_key,\n)\nfrom cryptography.hazmat.primitives.serialization.ssh import (\n    load_ssh_public_key\n)\n\n\n_PEM_DER = (Encoding.PEM, Encoding.DER)\n\n__all__ = [\n    \"load_der_parameters\", \"load_der_private_key\", \"load_der_public_key\",\n    \"load_pem_parameters\", \"load_pem_private_key\", \"load_pem_public_key\",\n    \"load_ssh_public_key\", \"Encoding\", \"PrivateFormat\", \"PublicFormat\",\n    \"ParameterFormat\", \"KeySerializationEncryption\", \"BestAvailableEncryption\",\n    \"NoEncryption\",\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/serialization/base.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\nfrom enum import Enum\n\nimport six\n\nfrom cryptography import utils\n\n\ndef load_pem_private_key(data, password, backend):\n    return backend.load_pem_private_key(data, password)\n\n\ndef load_pem_public_key(data, backend):\n    return backend.load_pem_public_key(data)\n\n\ndef load_pem_parameters(data, backend):\n    return backend.load_pem_parameters(data)\n\n\ndef load_der_private_key(data, password, backend):\n    return backend.load_der_private_key(data, password)\n\n\ndef load_der_public_key(data, backend):\n    return backend.load_der_public_key(data)\n\n\ndef load_der_parameters(data, backend):\n    return backend.load_der_parameters(data)\n\n\nclass Encoding(Enum):\n    PEM = \"PEM\"\n    DER = \"DER\"\n    OpenSSH = \"OpenSSH\"\n    Raw = \"Raw\"\n    X962 = \"ANSI X9.62\"\n\n\nclass PrivateFormat(Enum):\n    PKCS8 = \"PKCS8\"\n    TraditionalOpenSSL = \"TraditionalOpenSSL\"\n    Raw = \"Raw\"\n\n\nclass PublicFormat(Enum):\n    SubjectPublicKeyInfo = \"X.509 subjectPublicKeyInfo with PKCS#1\"\n    PKCS1 = \"Raw PKCS#1\"\n    OpenSSH = \"OpenSSH\"\n    Raw = \"Raw\"\n    CompressedPoint = \"X9.62 Compressed Point\"\n    UncompressedPoint = \"X9.62 Uncompressed Point\"\n\n\nclass ParameterFormat(Enum):\n    PKCS3 = \"PKCS3\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass KeySerializationEncryption(object):\n    pass\n\n\n@utils.register_interface(KeySerializationEncryption)\nclass BestAvailableEncryption(object):\n    def __init__(self, password):\n        if not isinstance(password, bytes) or len(password) == 0:\n            raise ValueError(\"Password must be 1 or more bytes.\")\n\n        self.password = password\n\n\n@utils.register_interface(KeySerializationEncryption)\nclass NoEncryption(object):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/serialization/pkcs12.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\n\ndef load_key_and_certificates(data, password, backend):\n    return backend.load_key_and_certificates_from_pkcs12(data, password)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/serialization/ssh.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport base64\nimport struct\n\nimport six\n\nfrom cryptography import utils\nfrom cryptography.exceptions import UnsupportedAlgorithm\nfrom cryptography.hazmat.primitives.asymmetric import dsa, ec, ed25519, rsa\n\n\ndef load_ssh_public_key(data, backend):\n    key_parts = data.split(b' ', 2)\n\n    if len(key_parts) < 2:\n        raise ValueError(\n            'Key is not in the proper format or contains extra data.')\n\n    key_type = key_parts[0]\n\n    if key_type == b'ssh-rsa':\n        loader = _load_ssh_rsa_public_key\n    elif key_type == b'ssh-dss':\n        loader = _load_ssh_dss_public_key\n    elif key_type in [\n        b'ecdsa-sha2-nistp256', b'ecdsa-sha2-nistp384', b'ecdsa-sha2-nistp521',\n    ]:\n        loader = _load_ssh_ecdsa_public_key\n    elif key_type == b'ssh-ed25519':\n        loader = _load_ssh_ed25519_public_key\n    else:\n        raise UnsupportedAlgorithm('Key type is not supported.')\n\n    key_body = key_parts[1]\n\n    try:\n        decoded_data = base64.b64decode(key_body)\n    except TypeError:\n        raise ValueError('Key is not in the proper format.')\n\n    inner_key_type, rest = _ssh_read_next_string(decoded_data)\n\n    if inner_key_type != key_type:\n        raise ValueError(\n            'Key header and key body contain different key type values.'\n        )\n\n    return loader(key_type, rest, backend)\n\n\ndef _load_ssh_rsa_public_key(key_type, decoded_data, backend):\n    e, rest = _ssh_read_next_mpint(decoded_data)\n    n, rest = _ssh_read_next_mpint(rest)\n\n    if rest:\n        raise ValueError('Key body contains extra bytes.')\n\n    return rsa.RSAPublicNumbers(e, n).public_key(backend)\n\n\ndef _load_ssh_dss_public_key(key_type, decoded_data, backend):\n    p, rest = _ssh_read_next_mpint(decoded_data)\n    q, rest = _ssh_read_next_mpint(rest)\n    g, rest = _ssh_read_next_mpint(rest)\n    y, rest = _ssh_read_next_mpint(rest)\n\n    if rest:\n        raise ValueError('Key body contains extra bytes.')\n\n    parameter_numbers = dsa.DSAParameterNumbers(p, q, g)\n    public_numbers = dsa.DSAPublicNumbers(y, parameter_numbers)\n\n    return public_numbers.public_key(backend)\n\n\ndef _load_ssh_ecdsa_public_key(expected_key_type, decoded_data, backend):\n    curve_name, rest = _ssh_read_next_string(decoded_data)\n    data, rest = _ssh_read_next_string(rest)\n\n    if expected_key_type != b\"ecdsa-sha2-\" + curve_name:\n        raise ValueError(\n            'Key header and key body contain different key type values.'\n        )\n\n    if rest:\n        raise ValueError('Key body contains extra bytes.')\n\n    curve = {\n        b\"nistp256\": ec.SECP256R1,\n        b\"nistp384\": ec.SECP384R1,\n        b\"nistp521\": ec.SECP521R1,\n    }[curve_name]()\n\n    if six.indexbytes(data, 0) != 4:\n        raise NotImplementedError(\n            \"Compressed elliptic curve points are not supported\"\n        )\n\n    return ec.EllipticCurvePublicKey.from_encoded_point(curve, data)\n\n\ndef _load_ssh_ed25519_public_key(expected_key_type, decoded_data, backend):\n    data, rest = _ssh_read_next_string(decoded_data)\n\n    if rest:\n        raise ValueError('Key body contains extra bytes.')\n\n    return ed25519.Ed25519PublicKey.from_public_bytes(data)\n\n\ndef _ssh_read_next_string(data):\n    \"\"\"\n    Retrieves the next RFC 4251 string value from the data.\n\n    While the RFC calls these strings, in Python they are bytes objects.\n    \"\"\"\n    if len(data) < 4:\n        raise ValueError(\"Key is not in the proper format\")\n\n    str_len, = struct.unpack('>I', data[:4])\n    if len(data) < str_len + 4:\n        raise ValueError(\"Key is not in the proper format\")\n\n    return data[4:4 + str_len], data[4 + str_len:]\n\n\ndef _ssh_read_next_mpint(data):\n    \"\"\"\n    Reads the next mpint from the data.\n\n    Currently, all mpints are interpreted as unsigned.\n    \"\"\"\n    mpint_data, rest = _ssh_read_next_string(data)\n\n    return (\n        utils.int_from_bytes(mpint_data, byteorder='big', signed=False), rest\n    )\n\n\ndef _ssh_write_string(data):\n    return struct.pack(\">I\", len(data)) + data\n\n\ndef _ssh_write_mpint(value):\n    data = utils.int_to_bytes(value)\n    if six.indexbytes(data, 0) & 0x80:\n        data = b\"\\x00\" + data\n    return _ssh_write_string(data)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/twofactor/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\n\nclass InvalidToken(Exception):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/twofactor/hotp.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport struct\n\nimport six\n\nfrom cryptography.exceptions import (\n    UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.interfaces import HMACBackend\nfrom cryptography.hazmat.primitives import constant_time, hmac\nfrom cryptography.hazmat.primitives.hashes import SHA1, SHA256, SHA512\nfrom cryptography.hazmat.primitives.twofactor import InvalidToken\nfrom cryptography.hazmat.primitives.twofactor.utils import _generate_uri\n\n\nclass HOTP(object):\n    def __init__(self, key, length, algorithm, backend,\n                 enforce_key_length=True):\n        if not isinstance(backend, HMACBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement HMACBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n\n        if len(key) < 16 and enforce_key_length is True:\n            raise ValueError(\"Key length has to be at least 128 bits.\")\n\n        if not isinstance(length, six.integer_types):\n            raise TypeError(\"Length parameter must be an integer type.\")\n\n        if length < 6 or length > 8:\n            raise ValueError(\"Length of HOTP has to be between 6 to 8.\")\n\n        if not isinstance(algorithm, (SHA1, SHA256, SHA512)):\n            raise TypeError(\"Algorithm must be SHA1, SHA256 or SHA512.\")\n\n        self._key = key\n        self._length = length\n        self._algorithm = algorithm\n        self._backend = backend\n\n    def generate(self, counter):\n        truncated_value = self._dynamic_truncate(counter)\n        hotp = truncated_value % (10 ** self._length)\n        return \"{0:0{1}}\".format(hotp, self._length).encode()\n\n    def verify(self, hotp, counter):\n        if not constant_time.bytes_eq(self.generate(counter), hotp):\n            raise InvalidToken(\"Supplied HOTP value does not match.\")\n\n    def _dynamic_truncate(self, counter):\n        ctx = hmac.HMAC(self._key, self._algorithm, self._backend)\n        ctx.update(struct.pack(\">Q\", counter))\n        hmac_value = ctx.finalize()\n\n        offset = six.indexbytes(hmac_value, len(hmac_value) - 1) & 0b1111\n        p = hmac_value[offset:offset + 4]\n        return struct.unpack(\">I\", p)[0] & 0x7fffffff\n\n    def get_provisioning_uri(self, account_name, counter, issuer):\n        return _generate_uri(self, \"hotp\", account_name, issuer, [\n            (\"counter\", int(counter)),\n        ])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/twofactor/totp.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography.exceptions import (\n    UnsupportedAlgorithm, _Reasons\n)\nfrom cryptography.hazmat.backends.interfaces import HMACBackend\nfrom cryptography.hazmat.primitives import constant_time\nfrom cryptography.hazmat.primitives.twofactor import InvalidToken\nfrom cryptography.hazmat.primitives.twofactor.hotp import HOTP\nfrom cryptography.hazmat.primitives.twofactor.utils import _generate_uri\n\n\nclass TOTP(object):\n    def __init__(self, key, length, algorithm, time_step, backend,\n                 enforce_key_length=True):\n        if not isinstance(backend, HMACBackend):\n            raise UnsupportedAlgorithm(\n                \"Backend object does not implement HMACBackend.\",\n                _Reasons.BACKEND_MISSING_INTERFACE\n            )\n\n        self._time_step = time_step\n        self._hotp = HOTP(key, length, algorithm, backend, enforce_key_length)\n\n    def generate(self, time):\n        counter = int(time / self._time_step)\n        return self._hotp.generate(counter)\n\n    def verify(self, totp, time):\n        if not constant_time.bytes_eq(self.generate(time), totp):\n            raise InvalidToken(\"Supplied TOTP value does not match.\")\n\n    def get_provisioning_uri(self, account_name, issuer):\n        return _generate_uri(self._hotp, \"totp\", account_name, issuer, [\n            (\"period\", int(self._time_step)),\n        ])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/hazmat/primitives/twofactor/utils.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport base64\n\nfrom six.moves.urllib.parse import quote, urlencode\n\n\ndef _generate_uri(hotp, type_name, account_name, issuer, extra_parameters):\n    parameters = [\n        (\"digits\", hotp._length),\n        (\"secret\", base64.b32encode(hotp._key)),\n        (\"algorithm\", hotp._algorithm.name.upper()),\n    ]\n\n    if issuer is not None:\n        parameters.append((\"issuer\", issuer))\n\n    parameters.extend(extra_parameters)\n\n    uriparts = {\n        \"type\": type_name,\n        \"label\": (\"%s:%s\" % (quote(issuer), quote(account_name)) if issuer\n                  else quote(account_name)),\n        \"parameters\": urlencode(parameters),\n    }\n    return \"otpauth://{type}/{label}?{parameters}\".format(**uriparts)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/utils.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\nimport binascii\nimport inspect\nimport sys\nimport warnings\n\n\n# We use a UserWarning subclass, instead of DeprecationWarning, because CPython\n# decided deprecation warnings should be invisble by default.\nclass CryptographyDeprecationWarning(UserWarning):\n    pass\n\n\n# Several APIs were deprecated with no specific end-of-life date because of the\n# ubiquity of their use. They should not be removed until we agree on when that\n# cycle ends.\nPersistentlyDeprecated2017 = CryptographyDeprecationWarning\nPersistentlyDeprecated2018 = CryptographyDeprecationWarning\nDeprecatedIn25 = CryptographyDeprecationWarning\nDeprecatedIn27 = CryptographyDeprecationWarning\n\n\ndef _check_bytes(name, value):\n    if not isinstance(value, bytes):\n        raise TypeError(\"{} must be bytes\".format(name))\n\n\ndef _check_byteslike(name, value):\n    try:\n        memoryview(value)\n    except TypeError:\n        raise TypeError(\"{} must be bytes-like\".format(name))\n\n\ndef read_only_property(name):\n    return property(lambda self: getattr(self, name))\n\n\ndef register_interface(iface):\n    def register_decorator(klass):\n        verify_interface(iface, klass)\n        iface.register(klass)\n        return klass\n    return register_decorator\n\n\ndef register_interface_if(predicate, iface):\n    def register_decorator(klass):\n        if predicate:\n            verify_interface(iface, klass)\n            iface.register(klass)\n        return klass\n    return register_decorator\n\n\nif hasattr(int, \"from_bytes\"):\n    int_from_bytes = int.from_bytes\nelse:\n    def int_from_bytes(data, byteorder, signed=False):\n        assert byteorder == 'big'\n        assert not signed\n\n        return int(binascii.hexlify(data), 16)\n\n\nif hasattr(int, \"to_bytes\"):\n    def int_to_bytes(integer, length=None):\n        return integer.to_bytes(\n            length or (integer.bit_length() + 7) // 8 or 1, 'big'\n        )\nelse:\n    def int_to_bytes(integer, length=None):\n        hex_string = '%x' % integer\n        if length is None:\n            n = len(hex_string)\n        else:\n            n = length * 2\n        return binascii.unhexlify(hex_string.zfill(n + (n & 1)))\n\n\nclass InterfaceNotImplemented(Exception):\n    pass\n\n\nif hasattr(inspect, \"signature\"):\n    signature = inspect.signature\nelse:\n    signature = inspect.getargspec\n\n\ndef verify_interface(iface, klass):\n    for method in iface.__abstractmethods__:\n        if not hasattr(klass, method):\n            raise InterfaceNotImplemented(\n                \"{} is missing a {!r} method\".format(klass, method)\n            )\n        if isinstance(getattr(iface, method), abc.abstractproperty):\n            # Can't properly verify these yet.\n            continue\n        sig = signature(getattr(iface, method))\n        actual = signature(getattr(klass, method))\n        if sig != actual:\n            raise InterfaceNotImplemented(\n                \"{}.{}'s signature differs from the expected. Expected: \"\n                \"{!r}. Received: {!r}\".format(\n                    klass, method, sig, actual\n                )\n            )\n\n\n# No longer needed as of 2.2, but retained because we have external consumers\n# who use it.\ndef bit_length(x):\n    return x.bit_length()\n\n\nclass _DeprecatedValue(object):\n    def __init__(self, value, message, warning_class):\n        self.value = value\n        self.message = message\n        self.warning_class = warning_class\n\n\nclass _ModuleWithDeprecations(object):\n    def __init__(self, module):\n        self.__dict__[\"_module\"] = module\n\n    def __getattr__(self, attr):\n        obj = getattr(self._module, attr)\n        if isinstance(obj, _DeprecatedValue):\n            warnings.warn(obj.message, obj.warning_class, stacklevel=2)\n            obj = obj.value\n        return obj\n\n    def __setattr__(self, attr, value):\n        setattr(self._module, attr, value)\n\n    def __delattr__(self, attr):\n        obj = getattr(self._module, attr)\n        if isinstance(obj, _DeprecatedValue):\n            warnings.warn(obj.message, obj.warning_class, stacklevel=2)\n\n        delattr(self._module, attr)\n\n    def __dir__(self):\n        return [\"_module\"] + dir(self._module)\n\n\ndef deprecated(value, module_name, message, warning_class):\n    module = sys.modules[module_name]\n    if not isinstance(module, _ModuleWithDeprecations):\n        sys.modules[module_name] = _ModuleWithDeprecations(module)\n    return _DeprecatedValue(value, message, warning_class)\n\n\ndef cached_property(func):\n    cached_name = \"_cached_{}\".format(func)\n    sentinel = object()\n\n    def inner(instance):\n        cache = getattr(instance, cached_name, sentinel)\n        if cache is not sentinel:\n            return cache\n        result = func(instance)\n        setattr(instance, cached_name, result)\n        return result\n    return property(inner)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/x509/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography.x509 import certificate_transparency\nfrom cryptography.x509.base import (\n    Certificate, CertificateBuilder, CertificateRevocationList,\n    CertificateRevocationListBuilder,\n    CertificateSigningRequest, CertificateSigningRequestBuilder,\n    InvalidVersion, RevokedCertificate, RevokedCertificateBuilder,\n    Version, load_der_x509_certificate, load_der_x509_crl, load_der_x509_csr,\n    load_pem_x509_certificate, load_pem_x509_crl, load_pem_x509_csr,\n    random_serial_number,\n)\nfrom cryptography.x509.extensions import (\n    AccessDescription, AuthorityInformationAccess,\n    AuthorityKeyIdentifier, BasicConstraints, CRLDistributionPoints,\n    CRLNumber, CRLReason, CertificateIssuer, CertificatePolicies,\n    DeltaCRLIndicator, DistributionPoint, DuplicateExtension, ExtendedKeyUsage,\n    Extension, ExtensionNotFound, ExtensionType, Extensions, FreshestCRL,\n    GeneralNames, InhibitAnyPolicy, InvalidityDate, IssuerAlternativeName,\n    IssuingDistributionPoint, KeyUsage, NameConstraints, NoticeReference,\n    OCSPNoCheck, OCSPNonce, PolicyConstraints, PolicyInformation,\n    PrecertPoison, PrecertificateSignedCertificateTimestamps, ReasonFlags,\n    SubjectAlternativeName, SubjectKeyIdentifier, TLSFeature, TLSFeatureType,\n    UnrecognizedExtension, UserNotice\n)\nfrom cryptography.x509.general_name import (\n    DNSName, DirectoryName, GeneralName, IPAddress, OtherName, RFC822Name,\n    RegisteredID, UniformResourceIdentifier, UnsupportedGeneralNameType,\n    _GENERAL_NAMES\n)\nfrom cryptography.x509.name import (\n    Name, NameAttribute, RelativeDistinguishedName\n)\nfrom cryptography.x509.oid import (\n    AuthorityInformationAccessOID, CRLEntryExtensionOID,\n    CertificatePoliciesOID, ExtendedKeyUsageOID, ExtensionOID, NameOID,\n    ObjectIdentifier, SignatureAlgorithmOID, _SIG_OIDS_TO_HASH\n)\n\n\nOID_AUTHORITY_INFORMATION_ACCESS = ExtensionOID.AUTHORITY_INFORMATION_ACCESS\nOID_AUTHORITY_KEY_IDENTIFIER = ExtensionOID.AUTHORITY_KEY_IDENTIFIER\nOID_BASIC_CONSTRAINTS = ExtensionOID.BASIC_CONSTRAINTS\nOID_CERTIFICATE_POLICIES = ExtensionOID.CERTIFICATE_POLICIES\nOID_CRL_DISTRIBUTION_POINTS = ExtensionOID.CRL_DISTRIBUTION_POINTS\nOID_EXTENDED_KEY_USAGE = ExtensionOID.EXTENDED_KEY_USAGE\nOID_FRESHEST_CRL = ExtensionOID.FRESHEST_CRL\nOID_INHIBIT_ANY_POLICY = ExtensionOID.INHIBIT_ANY_POLICY\nOID_ISSUER_ALTERNATIVE_NAME = ExtensionOID.ISSUER_ALTERNATIVE_NAME\nOID_KEY_USAGE = ExtensionOID.KEY_USAGE\nOID_NAME_CONSTRAINTS = ExtensionOID.NAME_CONSTRAINTS\nOID_OCSP_NO_CHECK = ExtensionOID.OCSP_NO_CHECK\nOID_POLICY_CONSTRAINTS = ExtensionOID.POLICY_CONSTRAINTS\nOID_POLICY_MAPPINGS = ExtensionOID.POLICY_MAPPINGS\nOID_SUBJECT_ALTERNATIVE_NAME = ExtensionOID.SUBJECT_ALTERNATIVE_NAME\nOID_SUBJECT_DIRECTORY_ATTRIBUTES = ExtensionOID.SUBJECT_DIRECTORY_ATTRIBUTES\nOID_SUBJECT_INFORMATION_ACCESS = ExtensionOID.SUBJECT_INFORMATION_ACCESS\nOID_SUBJECT_KEY_IDENTIFIER = ExtensionOID.SUBJECT_KEY_IDENTIFIER\n\nOID_DSA_WITH_SHA1 = SignatureAlgorithmOID.DSA_WITH_SHA1\nOID_DSA_WITH_SHA224 = SignatureAlgorithmOID.DSA_WITH_SHA224\nOID_DSA_WITH_SHA256 = SignatureAlgorithmOID.DSA_WITH_SHA256\nOID_ECDSA_WITH_SHA1 = SignatureAlgorithmOID.ECDSA_WITH_SHA1\nOID_ECDSA_WITH_SHA224 = SignatureAlgorithmOID.ECDSA_WITH_SHA224\nOID_ECDSA_WITH_SHA256 = SignatureAlgorithmOID.ECDSA_WITH_SHA256\nOID_ECDSA_WITH_SHA384 = SignatureAlgorithmOID.ECDSA_WITH_SHA384\nOID_ECDSA_WITH_SHA512 = SignatureAlgorithmOID.ECDSA_WITH_SHA512\nOID_RSA_WITH_MD5 = SignatureAlgorithmOID.RSA_WITH_MD5\nOID_RSA_WITH_SHA1 = SignatureAlgorithmOID.RSA_WITH_SHA1\nOID_RSA_WITH_SHA224 = SignatureAlgorithmOID.RSA_WITH_SHA224\nOID_RSA_WITH_SHA256 = SignatureAlgorithmOID.RSA_WITH_SHA256\nOID_RSA_WITH_SHA384 = SignatureAlgorithmOID.RSA_WITH_SHA384\nOID_RSA_WITH_SHA512 = SignatureAlgorithmOID.RSA_WITH_SHA512\nOID_RSASSA_PSS = SignatureAlgorithmOID.RSASSA_PSS\n\nOID_COMMON_NAME = NameOID.COMMON_NAME\nOID_COUNTRY_NAME = NameOID.COUNTRY_NAME\nOID_DOMAIN_COMPONENT = NameOID.DOMAIN_COMPONENT\nOID_DN_QUALIFIER = NameOID.DN_QUALIFIER\nOID_EMAIL_ADDRESS = NameOID.EMAIL_ADDRESS\nOID_GENERATION_QUALIFIER = NameOID.GENERATION_QUALIFIER\nOID_GIVEN_NAME = NameOID.GIVEN_NAME\nOID_LOCALITY_NAME = NameOID.LOCALITY_NAME\nOID_ORGANIZATIONAL_UNIT_NAME = NameOID.ORGANIZATIONAL_UNIT_NAME\nOID_ORGANIZATION_NAME = NameOID.ORGANIZATION_NAME\nOID_PSEUDONYM = NameOID.PSEUDONYM\nOID_SERIAL_NUMBER = NameOID.SERIAL_NUMBER\nOID_STATE_OR_PROVINCE_NAME = NameOID.STATE_OR_PROVINCE_NAME\nOID_SURNAME = NameOID.SURNAME\nOID_TITLE = NameOID.TITLE\n\nOID_CLIENT_AUTH = ExtendedKeyUsageOID.CLIENT_AUTH\nOID_CODE_SIGNING = ExtendedKeyUsageOID.CODE_SIGNING\nOID_EMAIL_PROTECTION = ExtendedKeyUsageOID.EMAIL_PROTECTION\nOID_OCSP_SIGNING = ExtendedKeyUsageOID.OCSP_SIGNING\nOID_SERVER_AUTH = ExtendedKeyUsageOID.SERVER_AUTH\nOID_TIME_STAMPING = ExtendedKeyUsageOID.TIME_STAMPING\n\nOID_ANY_POLICY = CertificatePoliciesOID.ANY_POLICY\nOID_CPS_QUALIFIER = CertificatePoliciesOID.CPS_QUALIFIER\nOID_CPS_USER_NOTICE = CertificatePoliciesOID.CPS_USER_NOTICE\n\nOID_CERTIFICATE_ISSUER = CRLEntryExtensionOID.CERTIFICATE_ISSUER\nOID_CRL_REASON = CRLEntryExtensionOID.CRL_REASON\nOID_INVALIDITY_DATE = CRLEntryExtensionOID.INVALIDITY_DATE\n\nOID_CA_ISSUERS = AuthorityInformationAccessOID.CA_ISSUERS\nOID_OCSP = AuthorityInformationAccessOID.OCSP\n\n__all__ = [\n    \"certificate_transparency\",\n    \"load_pem_x509_certificate\",\n    \"load_der_x509_certificate\",\n    \"load_pem_x509_csr\",\n    \"load_der_x509_csr\",\n    \"load_pem_x509_crl\",\n    \"load_der_x509_crl\",\n    \"random_serial_number\",\n    \"InvalidVersion\",\n    \"DeltaCRLIndicator\",\n    \"DuplicateExtension\",\n    \"ExtensionNotFound\",\n    \"UnsupportedGeneralNameType\",\n    \"NameAttribute\",\n    \"Name\",\n    \"RelativeDistinguishedName\",\n    \"ObjectIdentifier\",\n    \"ExtensionType\",\n    \"Extensions\",\n    \"Extension\",\n    \"ExtendedKeyUsage\",\n    \"FreshestCRL\",\n    \"IssuingDistributionPoint\",\n    \"TLSFeature\",\n    \"TLSFeatureType\",\n    \"OCSPNoCheck\",\n    \"BasicConstraints\",\n    \"CRLNumber\",\n    \"KeyUsage\",\n    \"AuthorityInformationAccess\",\n    \"AccessDescription\",\n    \"CertificatePolicies\",\n    \"PolicyInformation\",\n    \"UserNotice\",\n    \"NoticeReference\",\n    \"SubjectKeyIdentifier\",\n    \"NameConstraints\",\n    \"CRLDistributionPoints\",\n    \"DistributionPoint\",\n    \"ReasonFlags\",\n    \"InhibitAnyPolicy\",\n    \"SubjectAlternativeName\",\n    \"IssuerAlternativeName\",\n    \"AuthorityKeyIdentifier\",\n    \"GeneralNames\",\n    \"GeneralName\",\n    \"RFC822Name\",\n    \"DNSName\",\n    \"UniformResourceIdentifier\",\n    \"RegisteredID\",\n    \"DirectoryName\",\n    \"IPAddress\",\n    \"OtherName\",\n    \"Certificate\",\n    \"CertificateRevocationList\",\n    \"CertificateRevocationListBuilder\",\n    \"CertificateSigningRequest\",\n    \"RevokedCertificate\",\n    \"RevokedCertificateBuilder\",\n    \"CertificateSigningRequestBuilder\",\n    \"CertificateBuilder\",\n    \"Version\",\n    \"_SIG_OIDS_TO_HASH\",\n    \"OID_CA_ISSUERS\",\n    \"OID_OCSP\",\n    \"_GENERAL_NAMES\",\n    \"CertificateIssuer\",\n    \"CRLReason\",\n    \"InvalidityDate\",\n    \"UnrecognizedExtension\",\n    \"PolicyConstraints\",\n    \"PrecertificateSignedCertificateTimestamps\",\n    \"PrecertPoison\",\n    \"OCSPNonce\",\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/x509/base.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\nimport datetime\nimport os\nfrom enum import Enum\n\nimport six\n\nfrom cryptography import utils\nfrom cryptography.hazmat.primitives.asymmetric import (\n    dsa, ec, ed25519, ed448, rsa\n)\nfrom cryptography.x509.extensions import Extension, ExtensionType\nfrom cryptography.x509.name import Name\n\n\n_EARLIEST_UTC_TIME = datetime.datetime(1950, 1, 1)\n\n\ndef _reject_duplicate_extension(extension, extensions):\n    # This is quadratic in the number of extensions\n    for e in extensions:\n        if e.oid == extension.oid:\n            raise ValueError('This extension has already been set.')\n\n\ndef _convert_to_naive_utc_time(time):\n    \"\"\"Normalizes a datetime to a naive datetime in UTC.\n\n    time -- datetime to normalize. Assumed to be in UTC if not timezone\n            aware.\n    \"\"\"\n    if time.tzinfo is not None:\n        offset = time.utcoffset()\n        offset = offset if offset else datetime.timedelta()\n        return time.replace(tzinfo=None) - offset\n    else:\n        return time\n\n\nclass Version(Enum):\n    v1 = 0\n    v3 = 2\n\n\ndef load_pem_x509_certificate(data, backend):\n    return backend.load_pem_x509_certificate(data)\n\n\ndef load_der_x509_certificate(data, backend):\n    return backend.load_der_x509_certificate(data)\n\n\ndef load_pem_x509_csr(data, backend):\n    return backend.load_pem_x509_csr(data)\n\n\ndef load_der_x509_csr(data, backend):\n    return backend.load_der_x509_csr(data)\n\n\ndef load_pem_x509_crl(data, backend):\n    return backend.load_pem_x509_crl(data)\n\n\ndef load_der_x509_crl(data, backend):\n    return backend.load_der_x509_crl(data)\n\n\nclass InvalidVersion(Exception):\n    def __init__(self, msg, parsed_version):\n        super(InvalidVersion, self).__init__(msg)\n        self.parsed_version = parsed_version\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass Certificate(object):\n    @abc.abstractmethod\n    def fingerprint(self, algorithm):\n        \"\"\"\n        Returns bytes using digest passed.\n        \"\"\"\n\n    @abc.abstractproperty\n    def serial_number(self):\n        \"\"\"\n        Returns certificate serial number\n        \"\"\"\n\n    @abc.abstractproperty\n    def version(self):\n        \"\"\"\n        Returns the certificate version\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_key(self):\n        \"\"\"\n        Returns the public key\n        \"\"\"\n\n    @abc.abstractproperty\n    def not_valid_before(self):\n        \"\"\"\n        Not before time (represented as UTC datetime)\n        \"\"\"\n\n    @abc.abstractproperty\n    def not_valid_after(self):\n        \"\"\"\n        Not after time (represented as UTC datetime)\n        \"\"\"\n\n    @abc.abstractproperty\n    def issuer(self):\n        \"\"\"\n        Returns the issuer name object.\n        \"\"\"\n\n    @abc.abstractproperty\n    def subject(self):\n        \"\"\"\n        Returns the subject name object.\n        \"\"\"\n\n    @abc.abstractproperty\n    def signature_hash_algorithm(self):\n        \"\"\"\n        Returns a HashAlgorithm corresponding to the type of the digest signed\n        in the certificate.\n        \"\"\"\n\n    @abc.abstractproperty\n    def signature_algorithm_oid(self):\n        \"\"\"\n        Returns the ObjectIdentifier of the signature algorithm.\n        \"\"\"\n\n    @abc.abstractproperty\n    def extensions(self):\n        \"\"\"\n        Returns an Extensions object.\n        \"\"\"\n\n    @abc.abstractproperty\n    def signature(self):\n        \"\"\"\n        Returns the signature bytes.\n        \"\"\"\n\n    @abc.abstractproperty\n    def tbs_certificate_bytes(self):\n        \"\"\"\n        Returns the tbsCertificate payload bytes as defined in RFC 5280.\n        \"\"\"\n\n    @abc.abstractmethod\n    def __eq__(self, other):\n        \"\"\"\n        Checks equality.\n        \"\"\"\n\n    @abc.abstractmethod\n    def __ne__(self, other):\n        \"\"\"\n        Checks not equal.\n        \"\"\"\n\n    @abc.abstractmethod\n    def __hash__(self):\n        \"\"\"\n        Computes a hash.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_bytes(self, encoding):\n        \"\"\"\n        Serializes the certificate to PEM or DER format.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass CertificateRevocationList(object):\n    @abc.abstractmethod\n    def public_bytes(self, encoding):\n        \"\"\"\n        Serializes the CRL to PEM or DER format.\n        \"\"\"\n\n    @abc.abstractmethod\n    def fingerprint(self, algorithm):\n        \"\"\"\n        Returns bytes using digest passed.\n        \"\"\"\n\n    @abc.abstractmethod\n    def get_revoked_certificate_by_serial_number(self, serial_number):\n        \"\"\"\n        Returns an instance of RevokedCertificate or None if the serial_number\n        is not in the CRL.\n        \"\"\"\n\n    @abc.abstractproperty\n    def signature_hash_algorithm(self):\n        \"\"\"\n        Returns a HashAlgorithm corresponding to the type of the digest signed\n        in the certificate.\n        \"\"\"\n\n    @abc.abstractproperty\n    def signature_algorithm_oid(self):\n        \"\"\"\n        Returns the ObjectIdentifier of the signature algorithm.\n        \"\"\"\n\n    @abc.abstractproperty\n    def issuer(self):\n        \"\"\"\n        Returns the X509Name with the issuer of this CRL.\n        \"\"\"\n\n    @abc.abstractproperty\n    def next_update(self):\n        \"\"\"\n        Returns the date of next update for this CRL.\n        \"\"\"\n\n    @abc.abstractproperty\n    def last_update(self):\n        \"\"\"\n        Returns the date of last update for this CRL.\n        \"\"\"\n\n    @abc.abstractproperty\n    def extensions(self):\n        \"\"\"\n        Returns an Extensions object containing a list of CRL extensions.\n        \"\"\"\n\n    @abc.abstractproperty\n    def signature(self):\n        \"\"\"\n        Returns the signature bytes.\n        \"\"\"\n\n    @abc.abstractproperty\n    def tbs_certlist_bytes(self):\n        \"\"\"\n        Returns the tbsCertList payload bytes as defined in RFC 5280.\n        \"\"\"\n\n    @abc.abstractmethod\n    def __eq__(self, other):\n        \"\"\"\n        Checks equality.\n        \"\"\"\n\n    @abc.abstractmethod\n    def __ne__(self, other):\n        \"\"\"\n        Checks not equal.\n        \"\"\"\n\n    @abc.abstractmethod\n    def __len__(self):\n        \"\"\"\n        Number of revoked certificates in the CRL.\n        \"\"\"\n\n    @abc.abstractmethod\n    def __getitem__(self, idx):\n        \"\"\"\n        Returns a revoked certificate (or slice of revoked certificates).\n        \"\"\"\n\n    @abc.abstractmethod\n    def __iter__(self):\n        \"\"\"\n        Iterator over the revoked certificates\n        \"\"\"\n\n    @abc.abstractmethod\n    def is_signature_valid(self, public_key):\n        \"\"\"\n        Verifies signature of revocation list against given public key.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass CertificateSigningRequest(object):\n    @abc.abstractmethod\n    def __eq__(self, other):\n        \"\"\"\n        Checks equality.\n        \"\"\"\n\n    @abc.abstractmethod\n    def __ne__(self, other):\n        \"\"\"\n        Checks not equal.\n        \"\"\"\n\n    @abc.abstractmethod\n    def __hash__(self):\n        \"\"\"\n        Computes a hash.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_key(self):\n        \"\"\"\n        Returns the public key\n        \"\"\"\n\n    @abc.abstractproperty\n    def subject(self):\n        \"\"\"\n        Returns the subject name object.\n        \"\"\"\n\n    @abc.abstractproperty\n    def signature_hash_algorithm(self):\n        \"\"\"\n        Returns a HashAlgorithm corresponding to the type of the digest signed\n        in the certificate.\n        \"\"\"\n\n    @abc.abstractproperty\n    def signature_algorithm_oid(self):\n        \"\"\"\n        Returns the ObjectIdentifier of the signature algorithm.\n        \"\"\"\n\n    @abc.abstractproperty\n    def extensions(self):\n        \"\"\"\n        Returns the extensions in the signing request.\n        \"\"\"\n\n    @abc.abstractmethod\n    def public_bytes(self, encoding):\n        \"\"\"\n        Encodes the request to PEM or DER format.\n        \"\"\"\n\n    @abc.abstractproperty\n    def signature(self):\n        \"\"\"\n        Returns the signature bytes.\n        \"\"\"\n\n    @abc.abstractproperty\n    def tbs_certrequest_bytes(self):\n        \"\"\"\n        Returns the PKCS#10 CertificationRequestInfo bytes as defined in RFC\n        2986.\n        \"\"\"\n\n    @abc.abstractproperty\n    def is_signature_valid(self):\n        \"\"\"\n        Verifies signature of signing request.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass RevokedCertificate(object):\n    @abc.abstractproperty\n    def serial_number(self):\n        \"\"\"\n        Returns the serial number of the revoked certificate.\n        \"\"\"\n\n    @abc.abstractproperty\n    def revocation_date(self):\n        \"\"\"\n        Returns the date of when this certificate was revoked.\n        \"\"\"\n\n    @abc.abstractproperty\n    def extensions(self):\n        \"\"\"\n        Returns an Extensions object containing a list of Revoked extensions.\n        \"\"\"\n\n\nclass CertificateSigningRequestBuilder(object):\n    def __init__(self, subject_name=None, extensions=[]):\n        \"\"\"\n        Creates an empty X.509 certificate request (v1).\n        \"\"\"\n        self._subject_name = subject_name\n        self._extensions = extensions\n\n    def subject_name(self, name):\n        \"\"\"\n        Sets the certificate requestor's distinguished name.\n        \"\"\"\n        if not isinstance(name, Name):\n            raise TypeError('Expecting x509.Name object.')\n        if self._subject_name is not None:\n            raise ValueError('The subject name may only be set once.')\n        return CertificateSigningRequestBuilder(name, self._extensions)\n\n    def add_extension(self, extension, critical):\n        \"\"\"\n        Adds an X.509 extension to the certificate request.\n        \"\"\"\n        if not isinstance(extension, ExtensionType):\n            raise TypeError(\"extension must be an ExtensionType\")\n\n        extension = Extension(extension.oid, critical, extension)\n        _reject_duplicate_extension(extension, self._extensions)\n\n        return CertificateSigningRequestBuilder(\n            self._subject_name, self._extensions + [extension]\n        )\n\n    def sign(self, private_key, algorithm, backend):\n        \"\"\"\n        Signs the request using the requestor's private key.\n        \"\"\"\n        if self._subject_name is None:\n            raise ValueError(\"A CertificateSigningRequest must have a subject\")\n        return backend.create_x509_csr(self, private_key, algorithm)\n\n\nclass CertificateBuilder(object):\n    def __init__(self, issuer_name=None, subject_name=None,\n                 public_key=None, serial_number=None, not_valid_before=None,\n                 not_valid_after=None, extensions=[]):\n        self._version = Version.v3\n        self._issuer_name = issuer_name\n        self._subject_name = subject_name\n        self._public_key = public_key\n        self._serial_number = serial_number\n        self._not_valid_before = not_valid_before\n        self._not_valid_after = not_valid_after\n        self._extensions = extensions\n\n    def issuer_name(self, name):\n        \"\"\"\n        Sets the CA's distinguished name.\n        \"\"\"\n        if not isinstance(name, Name):\n            raise TypeError('Expecting x509.Name object.')\n        if self._issuer_name is not None:\n            raise ValueError('The issuer name may only be set once.')\n        return CertificateBuilder(\n            name, self._subject_name, self._public_key,\n            self._serial_number, self._not_valid_before,\n            self._not_valid_after, self._extensions\n        )\n\n    def subject_name(self, name):\n        \"\"\"\n        Sets the requestor's distinguished name.\n        \"\"\"\n        if not isinstance(name, Name):\n            raise TypeError('Expecting x509.Name object.')\n        if self._subject_name is not None:\n            raise ValueError('The subject name may only be set once.')\n        return CertificateBuilder(\n            self._issuer_name, name, self._public_key,\n            self._serial_number, self._not_valid_before,\n            self._not_valid_after, self._extensions\n        )\n\n    def public_key(self, key):\n        \"\"\"\n        Sets the requestor's public key (as found in the signing request).\n        \"\"\"\n        if not isinstance(key, (dsa.DSAPublicKey, rsa.RSAPublicKey,\n                                ec.EllipticCurvePublicKey,\n                                ed25519.Ed25519PublicKey,\n                                ed448.Ed448PublicKey)):\n            raise TypeError('Expecting one of DSAPublicKey, RSAPublicKey,'\n                            ' EllipticCurvePublicKey, Ed25519PublicKey or'\n                            ' Ed448PublicKey.')\n        if self._public_key is not None:\n            raise ValueError('The public key may only be set once.')\n        return CertificateBuilder(\n            self._issuer_name, self._subject_name, key,\n            self._serial_number, self._not_valid_before,\n            self._not_valid_after, self._extensions\n        )\n\n    def serial_number(self, number):\n        \"\"\"\n        Sets the certificate serial number.\n        \"\"\"\n        if not isinstance(number, six.integer_types):\n            raise TypeError('Serial number must be of integral type.')\n        if self._serial_number is not None:\n            raise ValueError('The serial number may only be set once.')\n        if number <= 0:\n            raise ValueError('The serial number should be positive.')\n\n        # ASN.1 integers are always signed, so most significant bit must be\n        # zero.\n        if number.bit_length() >= 160:  # As defined in RFC 5280\n            raise ValueError('The serial number should not be more than 159 '\n                             'bits.')\n        return CertificateBuilder(\n            self._issuer_name, self._subject_name,\n            self._public_key, number, self._not_valid_before,\n            self._not_valid_after, self._extensions\n        )\n\n    def not_valid_before(self, time):\n        \"\"\"\n        Sets the certificate activation time.\n        \"\"\"\n        if not isinstance(time, datetime.datetime):\n            raise TypeError('Expecting datetime object.')\n        if self._not_valid_before is not None:\n            raise ValueError('The not valid before may only be set once.')\n        time = _convert_to_naive_utc_time(time)\n        if time < _EARLIEST_UTC_TIME:\n            raise ValueError('The not valid before date must be on or after'\n                             ' 1950 January 1).')\n        if self._not_valid_after is not None and time > self._not_valid_after:\n            raise ValueError(\n                'The not valid before date must be before the not valid after '\n                'date.'\n            )\n        return CertificateBuilder(\n            self._issuer_name, self._subject_name,\n            self._public_key, self._serial_number, time,\n            self._not_valid_after, self._extensions\n        )\n\n    def not_valid_after(self, time):\n        \"\"\"\n        Sets the certificate expiration time.\n        \"\"\"\n        if not isinstance(time, datetime.datetime):\n            raise TypeError('Expecting datetime object.')\n        if self._not_valid_after is not None:\n            raise ValueError('The not valid after may only be set once.')\n        time = _convert_to_naive_utc_time(time)\n        if time < _EARLIEST_UTC_TIME:\n            raise ValueError('The not valid after date must be on or after'\n                             ' 1950 January 1.')\n        if (self._not_valid_before is not None and\n                time < self._not_valid_before):\n            raise ValueError(\n                'The not valid after date must be after the not valid before '\n                'date.'\n            )\n        return CertificateBuilder(\n            self._issuer_name, self._subject_name,\n            self._public_key, self._serial_number, self._not_valid_before,\n            time, self._extensions\n        )\n\n    def add_extension(self, extension, critical):\n        \"\"\"\n        Adds an X.509 extension to the certificate.\n        \"\"\"\n        if not isinstance(extension, ExtensionType):\n            raise TypeError(\"extension must be an ExtensionType\")\n\n        extension = Extension(extension.oid, critical, extension)\n        _reject_duplicate_extension(extension, self._extensions)\n\n        return CertificateBuilder(\n            self._issuer_name, self._subject_name,\n            self._public_key, self._serial_number, self._not_valid_before,\n            self._not_valid_after, self._extensions + [extension]\n        )\n\n    def sign(self, private_key, algorithm, backend):\n        \"\"\"\n        Signs the certificate using the CA's private key.\n        \"\"\"\n        if self._subject_name is None:\n            raise ValueError(\"A certificate must have a subject name\")\n\n        if self._issuer_name is None:\n            raise ValueError(\"A certificate must have an issuer name\")\n\n        if self._serial_number is None:\n            raise ValueError(\"A certificate must have a serial number\")\n\n        if self._not_valid_before is None:\n            raise ValueError(\"A certificate must have a not valid before time\")\n\n        if self._not_valid_after is None:\n            raise ValueError(\"A certificate must have a not valid after time\")\n\n        if self._public_key is None:\n            raise ValueError(\"A certificate must have a public key\")\n\n        return backend.create_x509_certificate(self, private_key, algorithm)\n\n\nclass CertificateRevocationListBuilder(object):\n    def __init__(self, issuer_name=None, last_update=None, next_update=None,\n                 extensions=[], revoked_certificates=[]):\n        self._issuer_name = issuer_name\n        self._last_update = last_update\n        self._next_update = next_update\n        self._extensions = extensions\n        self._revoked_certificates = revoked_certificates\n\n    def issuer_name(self, issuer_name):\n        if not isinstance(issuer_name, Name):\n            raise TypeError('Expecting x509.Name object.')\n        if self._issuer_name is not None:\n            raise ValueError('The issuer name may only be set once.')\n        return CertificateRevocationListBuilder(\n            issuer_name, self._last_update, self._next_update,\n            self._extensions, self._revoked_certificates\n        )\n\n    def last_update(self, last_update):\n        if not isinstance(last_update, datetime.datetime):\n            raise TypeError('Expecting datetime object.')\n        if self._last_update is not None:\n            raise ValueError('Last update may only be set once.')\n        last_update = _convert_to_naive_utc_time(last_update)\n        if last_update < _EARLIEST_UTC_TIME:\n            raise ValueError('The last update date must be on or after'\n                             ' 1950 January 1.')\n        if self._next_update is not None and last_update > self._next_update:\n            raise ValueError(\n                'The last update date must be before the next update date.'\n            )\n        return CertificateRevocationListBuilder(\n            self._issuer_name, last_update, self._next_update,\n            self._extensions, self._revoked_certificates\n        )\n\n    def next_update(self, next_update):\n        if not isinstance(next_update, datetime.datetime):\n            raise TypeError('Expecting datetime object.')\n        if self._next_update is not None:\n            raise ValueError('Last update may only be set once.')\n        next_update = _convert_to_naive_utc_time(next_update)\n        if next_update < _EARLIEST_UTC_TIME:\n            raise ValueError('The last update date must be on or after'\n                             ' 1950 January 1.')\n        if self._last_update is not None and next_update < self._last_update:\n            raise ValueError(\n                'The next update date must be after the last update date.'\n            )\n        return CertificateRevocationListBuilder(\n            self._issuer_name, self._last_update, next_update,\n            self._extensions, self._revoked_certificates\n        )\n\n    def add_extension(self, extension, critical):\n        \"\"\"\n        Adds an X.509 extension to the certificate revocation list.\n        \"\"\"\n        if not isinstance(extension, ExtensionType):\n            raise TypeError(\"extension must be an ExtensionType\")\n\n        extension = Extension(extension.oid, critical, extension)\n        _reject_duplicate_extension(extension, self._extensions)\n        return CertificateRevocationListBuilder(\n            self._issuer_name, self._last_update, self._next_update,\n            self._extensions + [extension], self._revoked_certificates\n        )\n\n    def add_revoked_certificate(self, revoked_certificate):\n        \"\"\"\n        Adds a revoked certificate to the CRL.\n        \"\"\"\n        if not isinstance(revoked_certificate, RevokedCertificate):\n            raise TypeError(\"Must be an instance of RevokedCertificate\")\n\n        return CertificateRevocationListBuilder(\n            self._issuer_name, self._last_update,\n            self._next_update, self._extensions,\n            self._revoked_certificates + [revoked_certificate]\n        )\n\n    def sign(self, private_key, algorithm, backend):\n        if self._issuer_name is None:\n            raise ValueError(\"A CRL must have an issuer name\")\n\n        if self._last_update is None:\n            raise ValueError(\"A CRL must have a last update time\")\n\n        if self._next_update is None:\n            raise ValueError(\"A CRL must have a next update time\")\n\n        return backend.create_x509_crl(self, private_key, algorithm)\n\n\nclass RevokedCertificateBuilder(object):\n    def __init__(self, serial_number=None, revocation_date=None,\n                 extensions=[]):\n        self._serial_number = serial_number\n        self._revocation_date = revocation_date\n        self._extensions = extensions\n\n    def serial_number(self, number):\n        if not isinstance(number, six.integer_types):\n            raise TypeError('Serial number must be of integral type.')\n        if self._serial_number is not None:\n            raise ValueError('The serial number may only be set once.')\n        if number <= 0:\n            raise ValueError('The serial number should be positive')\n\n        # ASN.1 integers are always signed, so most significant bit must be\n        # zero.\n        if number.bit_length() >= 160:  # As defined in RFC 5280\n            raise ValueError('The serial number should not be more than 159 '\n                             'bits.')\n        return RevokedCertificateBuilder(\n            number, self._revocation_date, self._extensions\n        )\n\n    def revocation_date(self, time):\n        if not isinstance(time, datetime.datetime):\n            raise TypeError('Expecting datetime object.')\n        if self._revocation_date is not None:\n            raise ValueError('The revocation date may only be set once.')\n        time = _convert_to_naive_utc_time(time)\n        if time < _EARLIEST_UTC_TIME:\n            raise ValueError('The revocation date must be on or after'\n                             ' 1950 January 1.')\n        return RevokedCertificateBuilder(\n            self._serial_number, time, self._extensions\n        )\n\n    def add_extension(self, extension, critical):\n        if not isinstance(extension, ExtensionType):\n            raise TypeError(\"extension must be an ExtensionType\")\n\n        extension = Extension(extension.oid, critical, extension)\n        _reject_duplicate_extension(extension, self._extensions)\n        return RevokedCertificateBuilder(\n            self._serial_number, self._revocation_date,\n            self._extensions + [extension]\n        )\n\n    def build(self, backend):\n        if self._serial_number is None:\n            raise ValueError(\"A revoked certificate must have a serial number\")\n        if self._revocation_date is None:\n            raise ValueError(\n                \"A revoked certificate must have a revocation date\"\n            )\n\n        return backend.create_x509_revoked_certificate(self)\n\n\ndef random_serial_number():\n    return utils.int_from_bytes(os.urandom(20), \"big\") >> 1\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/x509/certificate_transparency.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\nfrom enum import Enum\n\nimport six\n\n\nclass LogEntryType(Enum):\n    X509_CERTIFICATE = 0\n    PRE_CERTIFICATE = 1\n\n\nclass Version(Enum):\n    v1 = 0\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass SignedCertificateTimestamp(object):\n    @abc.abstractproperty\n    def version(self):\n        \"\"\"\n        Returns the SCT version.\n        \"\"\"\n\n    @abc.abstractproperty\n    def log_id(self):\n        \"\"\"\n        Returns an identifier indicating which log this SCT is for.\n        \"\"\"\n\n    @abc.abstractproperty\n    def timestamp(self):\n        \"\"\"\n        Returns the timestamp for this SCT.\n        \"\"\"\n\n    @abc.abstractproperty\n    def entry_type(self):\n        \"\"\"\n        Returns whether this is an SCT for a certificate or pre-certificate.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/x509/extensions.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\nimport datetime\nimport hashlib\nimport ipaddress\nimport warnings\nfrom enum import Enum\n\nimport six\n\nfrom cryptography import utils\nfrom cryptography.hazmat._der import (\n    BIT_STRING, DERReader, OBJECT_IDENTIFIER, SEQUENCE\n)\nfrom cryptography.hazmat.primitives import constant_time, serialization\nfrom cryptography.hazmat.primitives.asymmetric.ec import EllipticCurvePublicKey\nfrom cryptography.hazmat.primitives.asymmetric.rsa import RSAPublicKey\nfrom cryptography.x509.certificate_transparency import (\n    SignedCertificateTimestamp\n)\nfrom cryptography.x509.general_name import GeneralName, IPAddress, OtherName\nfrom cryptography.x509.name import RelativeDistinguishedName\nfrom cryptography.x509.oid import (\n    CRLEntryExtensionOID, ExtensionOID, OCSPExtensionOID, ObjectIdentifier,\n)\n\n\ndef _key_identifier_from_public_key(public_key):\n    if isinstance(public_key, RSAPublicKey):\n        data = public_key.public_bytes(\n            serialization.Encoding.DER,\n            serialization.PublicFormat.PKCS1,\n        )\n    elif isinstance(public_key, EllipticCurvePublicKey):\n        data = public_key.public_bytes(\n            serialization.Encoding.X962,\n            serialization.PublicFormat.UncompressedPoint\n        )\n    else:\n        # This is a very slow way to do this.\n        serialized = public_key.public_bytes(\n            serialization.Encoding.DER,\n            serialization.PublicFormat.SubjectPublicKeyInfo\n        )\n\n        reader = DERReader(serialized)\n        with reader.read_single_element(SEQUENCE) as public_key_info:\n            algorithm = public_key_info.read_element(SEQUENCE)\n            public_key = public_key_info.read_element(BIT_STRING)\n\n        # Double-check the algorithm structure.\n        with algorithm:\n            algorithm.read_element(OBJECT_IDENTIFIER)\n            if not algorithm.is_empty():\n                # Skip the optional parameters field.\n                algorithm.read_any_element()\n\n        # BIT STRING contents begin with the number of padding bytes added. It\n        # must be zero for SubjectPublicKeyInfo structures.\n        if public_key.read_byte() != 0:\n            raise ValueError('Invalid public key encoding')\n\n        data = public_key.data\n\n    return hashlib.sha1(data).digest()\n\n\ndef _make_sequence_methods(field_name):\n    def len_method(self):\n        return len(getattr(self, field_name))\n\n    def iter_method(self):\n        return iter(getattr(self, field_name))\n\n    def getitem_method(self, idx):\n        return getattr(self, field_name)[idx]\n\n    return len_method, iter_method, getitem_method\n\n\nclass DuplicateExtension(Exception):\n    def __init__(self, msg, oid):\n        super(DuplicateExtension, self).__init__(msg)\n        self.oid = oid\n\n\nclass ExtensionNotFound(Exception):\n    def __init__(self, msg, oid):\n        super(ExtensionNotFound, self).__init__(msg)\n        self.oid = oid\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass ExtensionType(object):\n    @abc.abstractproperty\n    def oid(self):\n        \"\"\"\n        Returns the oid associated with the given extension type.\n        \"\"\"\n\n\nclass Extensions(object):\n    def __init__(self, extensions):\n        self._extensions = extensions\n\n    def get_extension_for_oid(self, oid):\n        for ext in self:\n            if ext.oid == oid:\n                return ext\n\n        raise ExtensionNotFound(\"No {} extension was found\".format(oid), oid)\n\n    def get_extension_for_class(self, extclass):\n        if extclass is UnrecognizedExtension:\n            raise TypeError(\n                \"UnrecognizedExtension can't be used with \"\n                \"get_extension_for_class because more than one instance of the\"\n                \" class may be present.\"\n            )\n\n        for ext in self:\n            if isinstance(ext.value, extclass):\n                return ext\n\n        raise ExtensionNotFound(\n            \"No {} extension was found\".format(extclass), extclass.oid\n        )\n\n    __len__, __iter__, __getitem__ = _make_sequence_methods(\"_extensions\")\n\n    def __repr__(self):\n        return (\n            \"<Extensions({})>\".format(self._extensions)\n        )\n\n\n@utils.register_interface(ExtensionType)\nclass CRLNumber(object):\n    oid = ExtensionOID.CRL_NUMBER\n\n    def __init__(self, crl_number):\n        if not isinstance(crl_number, six.integer_types):\n            raise TypeError(\"crl_number must be an integer\")\n\n        self._crl_number = crl_number\n\n    def __eq__(self, other):\n        if not isinstance(other, CRLNumber):\n            return NotImplemented\n\n        return self.crl_number == other.crl_number\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.crl_number)\n\n    def __repr__(self):\n        return \"<CRLNumber({})>\".format(self.crl_number)\n\n    crl_number = utils.read_only_property(\"_crl_number\")\n\n\n@utils.register_interface(ExtensionType)\nclass AuthorityKeyIdentifier(object):\n    oid = ExtensionOID.AUTHORITY_KEY_IDENTIFIER\n\n    def __init__(self, key_identifier, authority_cert_issuer,\n                 authority_cert_serial_number):\n        if (authority_cert_issuer is None) != (\n            authority_cert_serial_number is None\n        ):\n            raise ValueError(\n                \"authority_cert_issuer and authority_cert_serial_number \"\n                \"must both be present or both None\"\n            )\n\n        if authority_cert_issuer is not None:\n            authority_cert_issuer = list(authority_cert_issuer)\n            if not all(\n                isinstance(x, GeneralName) for x in authority_cert_issuer\n            ):\n                raise TypeError(\n                    \"authority_cert_issuer must be a list of GeneralName \"\n                    \"objects\"\n                )\n\n        if authority_cert_serial_number is not None and not isinstance(\n            authority_cert_serial_number, six.integer_types\n        ):\n            raise TypeError(\n                \"authority_cert_serial_number must be an integer\"\n            )\n\n        self._key_identifier = key_identifier\n        self._authority_cert_issuer = authority_cert_issuer\n        self._authority_cert_serial_number = authority_cert_serial_number\n\n    @classmethod\n    def from_issuer_public_key(cls, public_key):\n        digest = _key_identifier_from_public_key(public_key)\n        return cls(\n            key_identifier=digest,\n            authority_cert_issuer=None,\n            authority_cert_serial_number=None\n        )\n\n    @classmethod\n    def from_issuer_subject_key_identifier(cls, ski):\n        if isinstance(ski, SubjectKeyIdentifier):\n            digest = ski.digest\n        else:\n            digest = ski.value.digest\n            warnings.warn(\n                \"Extension objects are deprecated as arguments to \"\n                \"from_issuer_subject_key_identifier and support will be \"\n                \"removed soon. Please migrate to passing a \"\n                \"SubjectKeyIdentifier directly.\",\n                utils.DeprecatedIn27,\n                stacklevel=2,\n            )\n\n        return cls(\n            key_identifier=digest,\n            authority_cert_issuer=None,\n            authority_cert_serial_number=None\n        )\n\n    def __repr__(self):\n        return (\n            \"<AuthorityKeyIdentifier(key_identifier={0.key_identifier!r}, \"\n            \"authority_cert_issuer={0.authority_cert_issuer}, \"\n            \"authority_cert_serial_number={0.authority_cert_serial_number}\"\n            \")>\".format(self)\n        )\n\n    def __eq__(self, other):\n        if not isinstance(other, AuthorityKeyIdentifier):\n            return NotImplemented\n\n        return (\n            self.key_identifier == other.key_identifier and\n            self.authority_cert_issuer == other.authority_cert_issuer and\n            self.authority_cert_serial_number ==\n            other.authority_cert_serial_number\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        if self.authority_cert_issuer is None:\n            aci = None\n        else:\n            aci = tuple(self.authority_cert_issuer)\n        return hash((\n            self.key_identifier, aci, self.authority_cert_serial_number\n        ))\n\n    key_identifier = utils.read_only_property(\"_key_identifier\")\n    authority_cert_issuer = utils.read_only_property(\"_authority_cert_issuer\")\n    authority_cert_serial_number = utils.read_only_property(\n        \"_authority_cert_serial_number\"\n    )\n\n\n@utils.register_interface(ExtensionType)\nclass SubjectKeyIdentifier(object):\n    oid = ExtensionOID.SUBJECT_KEY_IDENTIFIER\n\n    def __init__(self, digest):\n        self._digest = digest\n\n    @classmethod\n    def from_public_key(cls, public_key):\n        return cls(_key_identifier_from_public_key(public_key))\n\n    digest = utils.read_only_property(\"_digest\")\n\n    def __repr__(self):\n        return \"<SubjectKeyIdentifier(digest={0!r})>\".format(self.digest)\n\n    def __eq__(self, other):\n        if not isinstance(other, SubjectKeyIdentifier):\n            return NotImplemented\n\n        return constant_time.bytes_eq(self.digest, other.digest)\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.digest)\n\n\n@utils.register_interface(ExtensionType)\nclass AuthorityInformationAccess(object):\n    oid = ExtensionOID.AUTHORITY_INFORMATION_ACCESS\n\n    def __init__(self, descriptions):\n        descriptions = list(descriptions)\n        if not all(isinstance(x, AccessDescription) for x in descriptions):\n            raise TypeError(\n                \"Every item in the descriptions list must be an \"\n                \"AccessDescription\"\n            )\n\n        self._descriptions = descriptions\n\n    __len__, __iter__, __getitem__ = _make_sequence_methods(\"_descriptions\")\n\n    def __repr__(self):\n        return \"<AuthorityInformationAccess({})>\".format(self._descriptions)\n\n    def __eq__(self, other):\n        if not isinstance(other, AuthorityInformationAccess):\n            return NotImplemented\n\n        return self._descriptions == other._descriptions\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(tuple(self._descriptions))\n\n\nclass AccessDescription(object):\n    def __init__(self, access_method, access_location):\n        if not isinstance(access_method, ObjectIdentifier):\n            raise TypeError(\"access_method must be an ObjectIdentifier\")\n\n        if not isinstance(access_location, GeneralName):\n            raise TypeError(\"access_location must be a GeneralName\")\n\n        self._access_method = access_method\n        self._access_location = access_location\n\n    def __repr__(self):\n        return (\n            \"<AccessDescription(access_method={0.access_method}, access_locati\"\n            \"on={0.access_location})>\".format(self)\n        )\n\n    def __eq__(self, other):\n        if not isinstance(other, AccessDescription):\n            return NotImplemented\n\n        return (\n            self.access_method == other.access_method and\n            self.access_location == other.access_location\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((self.access_method, self.access_location))\n\n    access_method = utils.read_only_property(\"_access_method\")\n    access_location = utils.read_only_property(\"_access_location\")\n\n\n@utils.register_interface(ExtensionType)\nclass BasicConstraints(object):\n    oid = ExtensionOID.BASIC_CONSTRAINTS\n\n    def __init__(self, ca, path_length):\n        if not isinstance(ca, bool):\n            raise TypeError(\"ca must be a boolean value\")\n\n        if path_length is not None and not ca:\n            raise ValueError(\"path_length must be None when ca is False\")\n\n        if (\n            path_length is not None and\n            (not isinstance(path_length, six.integer_types) or path_length < 0)\n        ):\n            raise TypeError(\n                \"path_length must be a non-negative integer or None\"\n            )\n\n        self._ca = ca\n        self._path_length = path_length\n\n    ca = utils.read_only_property(\"_ca\")\n    path_length = utils.read_only_property(\"_path_length\")\n\n    def __repr__(self):\n        return (\"<BasicConstraints(ca={0.ca}, \"\n                \"path_length={0.path_length})>\").format(self)\n\n    def __eq__(self, other):\n        if not isinstance(other, BasicConstraints):\n            return NotImplemented\n\n        return self.ca == other.ca and self.path_length == other.path_length\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((self.ca, self.path_length))\n\n\n@utils.register_interface(ExtensionType)\nclass DeltaCRLIndicator(object):\n    oid = ExtensionOID.DELTA_CRL_INDICATOR\n\n    def __init__(self, crl_number):\n        if not isinstance(crl_number, six.integer_types):\n            raise TypeError(\"crl_number must be an integer\")\n\n        self._crl_number = crl_number\n\n    crl_number = utils.read_only_property(\"_crl_number\")\n\n    def __eq__(self, other):\n        if not isinstance(other, DeltaCRLIndicator):\n            return NotImplemented\n\n        return self.crl_number == other.crl_number\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.crl_number)\n\n    def __repr__(self):\n        return \"<DeltaCRLIndicator(crl_number={0.crl_number})>\".format(self)\n\n\n@utils.register_interface(ExtensionType)\nclass CRLDistributionPoints(object):\n    oid = ExtensionOID.CRL_DISTRIBUTION_POINTS\n\n    def __init__(self, distribution_points):\n        distribution_points = list(distribution_points)\n        if not all(\n            isinstance(x, DistributionPoint) for x in distribution_points\n        ):\n            raise TypeError(\n                \"distribution_points must be a list of DistributionPoint \"\n                \"objects\"\n            )\n\n        self._distribution_points = distribution_points\n\n    __len__, __iter__, __getitem__ = _make_sequence_methods(\n        \"_distribution_points\"\n    )\n\n    def __repr__(self):\n        return \"<CRLDistributionPoints({})>\".format(self._distribution_points)\n\n    def __eq__(self, other):\n        if not isinstance(other, CRLDistributionPoints):\n            return NotImplemented\n\n        return self._distribution_points == other._distribution_points\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(tuple(self._distribution_points))\n\n\n@utils.register_interface(ExtensionType)\nclass FreshestCRL(object):\n    oid = ExtensionOID.FRESHEST_CRL\n\n    def __init__(self, distribution_points):\n        distribution_points = list(distribution_points)\n        if not all(\n            isinstance(x, DistributionPoint) for x in distribution_points\n        ):\n            raise TypeError(\n                \"distribution_points must be a list of DistributionPoint \"\n                \"objects\"\n            )\n\n        self._distribution_points = distribution_points\n\n    __len__, __iter__, __getitem__ = _make_sequence_methods(\n        \"_distribution_points\"\n    )\n\n    def __repr__(self):\n        return \"<FreshestCRL({})>\".format(self._distribution_points)\n\n    def __eq__(self, other):\n        if not isinstance(other, FreshestCRL):\n            return NotImplemented\n\n        return self._distribution_points == other._distribution_points\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(tuple(self._distribution_points))\n\n\nclass DistributionPoint(object):\n    def __init__(self, full_name, relative_name, reasons, crl_issuer):\n        if full_name and relative_name:\n            raise ValueError(\n                \"You cannot provide both full_name and relative_name, at \"\n                \"least one must be None.\"\n            )\n\n        if full_name:\n            full_name = list(full_name)\n            if not all(isinstance(x, GeneralName) for x in full_name):\n                raise TypeError(\n                    \"full_name must be a list of GeneralName objects\"\n                )\n\n        if relative_name:\n            if not isinstance(relative_name, RelativeDistinguishedName):\n                raise TypeError(\n                    \"relative_name must be a RelativeDistinguishedName\"\n                )\n\n        if crl_issuer:\n            crl_issuer = list(crl_issuer)\n            if not all(isinstance(x, GeneralName) for x in crl_issuer):\n                raise TypeError(\n                    \"crl_issuer must be None or a list of general names\"\n                )\n\n        if reasons and (not isinstance(reasons, frozenset) or not all(\n            isinstance(x, ReasonFlags) for x in reasons\n        )):\n            raise TypeError(\"reasons must be None or frozenset of ReasonFlags\")\n\n        if reasons and (\n            ReasonFlags.unspecified in reasons or\n            ReasonFlags.remove_from_crl in reasons\n        ):\n            raise ValueError(\n                \"unspecified and remove_from_crl are not valid reasons in a \"\n                \"DistributionPoint\"\n            )\n\n        if reasons and not crl_issuer and not (full_name or relative_name):\n            raise ValueError(\n                \"You must supply crl_issuer, full_name, or relative_name when \"\n                \"reasons is not None\"\n            )\n\n        self._full_name = full_name\n        self._relative_name = relative_name\n        self._reasons = reasons\n        self._crl_issuer = crl_issuer\n\n    def __repr__(self):\n        return (\n            \"<DistributionPoint(full_name={0.full_name}, relative_name={0.rela\"\n            \"tive_name}, reasons={0.reasons}, crl_issuer={0.crl_issuer})>\"\n            .format(self)\n        )\n\n    def __eq__(self, other):\n        if not isinstance(other, DistributionPoint):\n            return NotImplemented\n\n        return (\n            self.full_name == other.full_name and\n            self.relative_name == other.relative_name and\n            self.reasons == other.reasons and\n            self.crl_issuer == other.crl_issuer\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        if self.full_name is not None:\n            fn = tuple(self.full_name)\n        else:\n            fn = None\n\n        if self.crl_issuer is not None:\n            crl_issuer = tuple(self.crl_issuer)\n        else:\n            crl_issuer = None\n\n        return hash((fn, self.relative_name, self.reasons, crl_issuer))\n\n    full_name = utils.read_only_property(\"_full_name\")\n    relative_name = utils.read_only_property(\"_relative_name\")\n    reasons = utils.read_only_property(\"_reasons\")\n    crl_issuer = utils.read_only_property(\"_crl_issuer\")\n\n\nclass ReasonFlags(Enum):\n    unspecified = \"unspecified\"\n    key_compromise = \"keyCompromise\"\n    ca_compromise = \"cACompromise\"\n    affiliation_changed = \"affiliationChanged\"\n    superseded = \"superseded\"\n    cessation_of_operation = \"cessationOfOperation\"\n    certificate_hold = \"certificateHold\"\n    privilege_withdrawn = \"privilegeWithdrawn\"\n    aa_compromise = \"aACompromise\"\n    remove_from_crl = \"removeFromCRL\"\n\n\n@utils.register_interface(ExtensionType)\nclass PolicyConstraints(object):\n    oid = ExtensionOID.POLICY_CONSTRAINTS\n\n    def __init__(self, require_explicit_policy, inhibit_policy_mapping):\n        if require_explicit_policy is not None and not isinstance(\n            require_explicit_policy, six.integer_types\n        ):\n            raise TypeError(\n                \"require_explicit_policy must be a non-negative integer or \"\n                \"None\"\n            )\n\n        if inhibit_policy_mapping is not None and not isinstance(\n            inhibit_policy_mapping, six.integer_types\n        ):\n            raise TypeError(\n                \"inhibit_policy_mapping must be a non-negative integer or None\"\n            )\n\n        if inhibit_policy_mapping is None and require_explicit_policy is None:\n            raise ValueError(\n                \"At least one of require_explicit_policy and \"\n                \"inhibit_policy_mapping must not be None\"\n            )\n\n        self._require_explicit_policy = require_explicit_policy\n        self._inhibit_policy_mapping = inhibit_policy_mapping\n\n    def __repr__(self):\n        return (\n            u\"<PolicyConstraints(require_explicit_policy={0.require_explicit\"\n            u\"_policy}, inhibit_policy_mapping={0.inhibit_policy_\"\n            u\"mapping})>\".format(self)\n        )\n\n    def __eq__(self, other):\n        if not isinstance(other, PolicyConstraints):\n            return NotImplemented\n\n        return (\n            self.require_explicit_policy == other.require_explicit_policy and\n            self.inhibit_policy_mapping == other.inhibit_policy_mapping\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(\n            (self.require_explicit_policy, self.inhibit_policy_mapping)\n        )\n\n    require_explicit_policy = utils.read_only_property(\n        \"_require_explicit_policy\"\n    )\n    inhibit_policy_mapping = utils.read_only_property(\n        \"_inhibit_policy_mapping\"\n    )\n\n\n@utils.register_interface(ExtensionType)\nclass CertificatePolicies(object):\n    oid = ExtensionOID.CERTIFICATE_POLICIES\n\n    def __init__(self, policies):\n        policies = list(policies)\n        if not all(isinstance(x, PolicyInformation) for x in policies):\n            raise TypeError(\n                \"Every item in the policies list must be a \"\n                \"PolicyInformation\"\n            )\n\n        self._policies = policies\n\n    __len__, __iter__, __getitem__ = _make_sequence_methods(\"_policies\")\n\n    def __repr__(self):\n        return \"<CertificatePolicies({})>\".format(self._policies)\n\n    def __eq__(self, other):\n        if not isinstance(other, CertificatePolicies):\n            return NotImplemented\n\n        return self._policies == other._policies\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(tuple(self._policies))\n\n\nclass PolicyInformation(object):\n    def __init__(self, policy_identifier, policy_qualifiers):\n        if not isinstance(policy_identifier, ObjectIdentifier):\n            raise TypeError(\"policy_identifier must be an ObjectIdentifier\")\n\n        self._policy_identifier = policy_identifier\n\n        if policy_qualifiers:\n            policy_qualifiers = list(policy_qualifiers)\n            if not all(\n                    isinstance(x, (six.text_type, UserNotice))\n                    for x in policy_qualifiers\n            ):\n                raise TypeError(\n                    \"policy_qualifiers must be a list of strings and/or \"\n                    \"UserNotice objects or None\"\n                )\n\n        self._policy_qualifiers = policy_qualifiers\n\n    def __repr__(self):\n        return (\n            \"<PolicyInformation(policy_identifier={0.policy_identifier}, polic\"\n            \"y_qualifiers={0.policy_qualifiers})>\".format(self)\n        )\n\n    def __eq__(self, other):\n        if not isinstance(other, PolicyInformation):\n            return NotImplemented\n\n        return (\n            self.policy_identifier == other.policy_identifier and\n            self.policy_qualifiers == other.policy_qualifiers\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        if self.policy_qualifiers is not None:\n            pq = tuple(self.policy_qualifiers)\n        else:\n            pq = None\n\n        return hash((self.policy_identifier, pq))\n\n    policy_identifier = utils.read_only_property(\"_policy_identifier\")\n    policy_qualifiers = utils.read_only_property(\"_policy_qualifiers\")\n\n\nclass UserNotice(object):\n    def __init__(self, notice_reference, explicit_text):\n        if notice_reference and not isinstance(\n            notice_reference, NoticeReference\n        ):\n            raise TypeError(\n                \"notice_reference must be None or a NoticeReference\"\n            )\n\n        self._notice_reference = notice_reference\n        self._explicit_text = explicit_text\n\n    def __repr__(self):\n        return (\n            \"<UserNotice(notice_reference={0.notice_reference}, explicit_text=\"\n            \"{0.explicit_text!r})>\".format(self)\n        )\n\n    def __eq__(self, other):\n        if not isinstance(other, UserNotice):\n            return NotImplemented\n\n        return (\n            self.notice_reference == other.notice_reference and\n            self.explicit_text == other.explicit_text\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((self.notice_reference, self.explicit_text))\n\n    notice_reference = utils.read_only_property(\"_notice_reference\")\n    explicit_text = utils.read_only_property(\"_explicit_text\")\n\n\nclass NoticeReference(object):\n    def __init__(self, organization, notice_numbers):\n        self._organization = organization\n        notice_numbers = list(notice_numbers)\n        if not all(isinstance(x, int) for x in notice_numbers):\n            raise TypeError(\n                \"notice_numbers must be a list of integers\"\n            )\n\n        self._notice_numbers = notice_numbers\n\n    def __repr__(self):\n        return (\n            \"<NoticeReference(organization={0.organization!r}, notice_numbers=\"\n            \"{0.notice_numbers})>\".format(self)\n        )\n\n    def __eq__(self, other):\n        if not isinstance(other, NoticeReference):\n            return NotImplemented\n\n        return (\n            self.organization == other.organization and\n            self.notice_numbers == other.notice_numbers\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((self.organization, tuple(self.notice_numbers)))\n\n    organization = utils.read_only_property(\"_organization\")\n    notice_numbers = utils.read_only_property(\"_notice_numbers\")\n\n\n@utils.register_interface(ExtensionType)\nclass ExtendedKeyUsage(object):\n    oid = ExtensionOID.EXTENDED_KEY_USAGE\n\n    def __init__(self, usages):\n        usages = list(usages)\n        if not all(isinstance(x, ObjectIdentifier) for x in usages):\n            raise TypeError(\n                \"Every item in the usages list must be an ObjectIdentifier\"\n            )\n\n        self._usages = usages\n\n    __len__, __iter__, __getitem__ = _make_sequence_methods(\"_usages\")\n\n    def __repr__(self):\n        return \"<ExtendedKeyUsage({})>\".format(self._usages)\n\n    def __eq__(self, other):\n        if not isinstance(other, ExtendedKeyUsage):\n            return NotImplemented\n\n        return self._usages == other._usages\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(tuple(self._usages))\n\n\n@utils.register_interface(ExtensionType)\nclass OCSPNoCheck(object):\n    oid = ExtensionOID.OCSP_NO_CHECK\n\n    def __eq__(self, other):\n        if not isinstance(other, OCSPNoCheck):\n            return NotImplemented\n\n        return True\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(OCSPNoCheck)\n\n    def __repr__(self):\n        return \"<OCSPNoCheck()>\"\n\n\n@utils.register_interface(ExtensionType)\nclass PrecertPoison(object):\n    oid = ExtensionOID.PRECERT_POISON\n\n    def __eq__(self, other):\n        if not isinstance(other, PrecertPoison):\n            return NotImplemented\n\n        return True\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(PrecertPoison)\n\n    def __repr__(self):\n        return \"<PrecertPoison()>\"\n\n\n@utils.register_interface(ExtensionType)\nclass TLSFeature(object):\n    oid = ExtensionOID.TLS_FEATURE\n\n    def __init__(self, features):\n        features = list(features)\n        if (\n            not all(isinstance(x, TLSFeatureType) for x in features) or\n            len(features) == 0\n        ):\n            raise TypeError(\n                \"features must be a list of elements from the TLSFeatureType \"\n                \"enum\"\n            )\n\n        self._features = features\n\n    __len__, __iter__, __getitem__ = _make_sequence_methods(\"_features\")\n\n    def __repr__(self):\n        return \"<TLSFeature(features={0._features})>\".format(self)\n\n    def __eq__(self, other):\n        if not isinstance(other, TLSFeature):\n            return NotImplemented\n\n        return self._features == other._features\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(tuple(self._features))\n\n\nclass TLSFeatureType(Enum):\n    # status_request is defined in RFC 6066 and is used for what is commonly\n    # called OCSP Must-Staple when present in the TLS Feature extension in an\n    # X.509 certificate.\n    status_request = 5\n    # status_request_v2 is defined in RFC 6961 and allows multiple OCSP\n    # responses to be provided. It is not currently in use by clients or\n    # servers.\n    status_request_v2 = 17\n\n\n_TLS_FEATURE_TYPE_TO_ENUM = dict((x.value, x) for x in TLSFeatureType)\n\n\n@utils.register_interface(ExtensionType)\nclass InhibitAnyPolicy(object):\n    oid = ExtensionOID.INHIBIT_ANY_POLICY\n\n    def __init__(self, skip_certs):\n        if not isinstance(skip_certs, six.integer_types):\n            raise TypeError(\"skip_certs must be an integer\")\n\n        if skip_certs < 0:\n            raise ValueError(\"skip_certs must be a non-negative integer\")\n\n        self._skip_certs = skip_certs\n\n    def __repr__(self):\n        return \"<InhibitAnyPolicy(skip_certs={0.skip_certs})>\".format(self)\n\n    def __eq__(self, other):\n        if not isinstance(other, InhibitAnyPolicy):\n            return NotImplemented\n\n        return self.skip_certs == other.skip_certs\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.skip_certs)\n\n    skip_certs = utils.read_only_property(\"_skip_certs\")\n\n\n@utils.register_interface(ExtensionType)\nclass KeyUsage(object):\n    oid = ExtensionOID.KEY_USAGE\n\n    def __init__(self, digital_signature, content_commitment, key_encipherment,\n                 data_encipherment, key_agreement, key_cert_sign, crl_sign,\n                 encipher_only, decipher_only):\n        if not key_agreement and (encipher_only or decipher_only):\n            raise ValueError(\n                \"encipher_only and decipher_only can only be true when \"\n                \"key_agreement is true\"\n            )\n\n        self._digital_signature = digital_signature\n        self._content_commitment = content_commitment\n        self._key_encipherment = key_encipherment\n        self._data_encipherment = data_encipherment\n        self._key_agreement = key_agreement\n        self._key_cert_sign = key_cert_sign\n        self._crl_sign = crl_sign\n        self._encipher_only = encipher_only\n        self._decipher_only = decipher_only\n\n    digital_signature = utils.read_only_property(\"_digital_signature\")\n    content_commitment = utils.read_only_property(\"_content_commitment\")\n    key_encipherment = utils.read_only_property(\"_key_encipherment\")\n    data_encipherment = utils.read_only_property(\"_data_encipherment\")\n    key_agreement = utils.read_only_property(\"_key_agreement\")\n    key_cert_sign = utils.read_only_property(\"_key_cert_sign\")\n    crl_sign = utils.read_only_property(\"_crl_sign\")\n\n    @property\n    def encipher_only(self):\n        if not self.key_agreement:\n            raise ValueError(\n                \"encipher_only is undefined unless key_agreement is true\"\n            )\n        else:\n            return self._encipher_only\n\n    @property\n    def decipher_only(self):\n        if not self.key_agreement:\n            raise ValueError(\n                \"decipher_only is undefined unless key_agreement is true\"\n            )\n        else:\n            return self._decipher_only\n\n    def __repr__(self):\n        try:\n            encipher_only = self.encipher_only\n            decipher_only = self.decipher_only\n        except ValueError:\n            encipher_only = None\n            decipher_only = None\n\n        return (\"<KeyUsage(digital_signature={0.digital_signature}, \"\n                \"content_commitment={0.content_commitment}, \"\n                \"key_encipherment={0.key_encipherment}, \"\n                \"data_encipherment={0.data_encipherment}, \"\n                \"key_agreement={0.key_agreement}, \"\n                \"key_cert_sign={0.key_cert_sign}, crl_sign={0.crl_sign}, \"\n                \"encipher_only={1}, decipher_only={2})>\").format(\n                    self, encipher_only, decipher_only)\n\n    def __eq__(self, other):\n        if not isinstance(other, KeyUsage):\n            return NotImplemented\n\n        return (\n            self.digital_signature == other.digital_signature and\n            self.content_commitment == other.content_commitment and\n            self.key_encipherment == other.key_encipherment and\n            self.data_encipherment == other.data_encipherment and\n            self.key_agreement == other.key_agreement and\n            self.key_cert_sign == other.key_cert_sign and\n            self.crl_sign == other.crl_sign and\n            self._encipher_only == other._encipher_only and\n            self._decipher_only == other._decipher_only\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((\n            self.digital_signature, self.content_commitment,\n            self.key_encipherment, self.data_encipherment,\n            self.key_agreement, self.key_cert_sign,\n            self.crl_sign, self._encipher_only,\n            self._decipher_only\n        ))\n\n\n@utils.register_interface(ExtensionType)\nclass NameConstraints(object):\n    oid = ExtensionOID.NAME_CONSTRAINTS\n\n    def __init__(self, permitted_subtrees, excluded_subtrees):\n        if permitted_subtrees is not None:\n            permitted_subtrees = list(permitted_subtrees)\n            if not all(\n                isinstance(x, GeneralName) for x in permitted_subtrees\n            ):\n                raise TypeError(\n                    \"permitted_subtrees must be a list of GeneralName objects \"\n                    \"or None\"\n                )\n\n            self._validate_ip_name(permitted_subtrees)\n\n        if excluded_subtrees is not None:\n            excluded_subtrees = list(excluded_subtrees)\n            if not all(\n                isinstance(x, GeneralName) for x in excluded_subtrees\n            ):\n                raise TypeError(\n                    \"excluded_subtrees must be a list of GeneralName objects \"\n                    \"or None\"\n                )\n\n            self._validate_ip_name(excluded_subtrees)\n\n        if permitted_subtrees is None and excluded_subtrees is None:\n            raise ValueError(\n                \"At least one of permitted_subtrees and excluded_subtrees \"\n                \"must not be None\"\n            )\n\n        self._permitted_subtrees = permitted_subtrees\n        self._excluded_subtrees = excluded_subtrees\n\n    def __eq__(self, other):\n        if not isinstance(other, NameConstraints):\n            return NotImplemented\n\n        return (\n            self.excluded_subtrees == other.excluded_subtrees and\n            self.permitted_subtrees == other.permitted_subtrees\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def _validate_ip_name(self, tree):\n        if any(isinstance(name, IPAddress) and not isinstance(\n            name.value, (ipaddress.IPv4Network, ipaddress.IPv6Network)\n        ) for name in tree):\n            raise TypeError(\n                \"IPAddress name constraints must be an IPv4Network or\"\n                \" IPv6Network object\"\n            )\n\n    def __repr__(self):\n        return (\n            u\"<NameConstraints(permitted_subtrees={0.permitted_subtrees}, \"\n            u\"excluded_subtrees={0.excluded_subtrees})>\".format(self)\n        )\n\n    def __hash__(self):\n        if self.permitted_subtrees is not None:\n            ps = tuple(self.permitted_subtrees)\n        else:\n            ps = None\n\n        if self.excluded_subtrees is not None:\n            es = tuple(self.excluded_subtrees)\n        else:\n            es = None\n\n        return hash((ps, es))\n\n    permitted_subtrees = utils.read_only_property(\"_permitted_subtrees\")\n    excluded_subtrees = utils.read_only_property(\"_excluded_subtrees\")\n\n\nclass Extension(object):\n    def __init__(self, oid, critical, value):\n        if not isinstance(oid, ObjectIdentifier):\n            raise TypeError(\n                \"oid argument must be an ObjectIdentifier instance.\"\n            )\n\n        if not isinstance(critical, bool):\n            raise TypeError(\"critical must be a boolean value\")\n\n        self._oid = oid\n        self._critical = critical\n        self._value = value\n\n    oid = utils.read_only_property(\"_oid\")\n    critical = utils.read_only_property(\"_critical\")\n    value = utils.read_only_property(\"_value\")\n\n    def __repr__(self):\n        return (\"<Extension(oid={0.oid}, critical={0.critical}, \"\n                \"value={0.value})>\").format(self)\n\n    def __eq__(self, other):\n        if not isinstance(other, Extension):\n            return NotImplemented\n\n        return (\n            self.oid == other.oid and\n            self.critical == other.critical and\n            self.value == other.value\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((self.oid, self.critical, self.value))\n\n\nclass GeneralNames(object):\n    def __init__(self, general_names):\n        general_names = list(general_names)\n        if not all(isinstance(x, GeneralName) for x in general_names):\n            raise TypeError(\n                \"Every item in the general_names list must be an \"\n                \"object conforming to the GeneralName interface\"\n            )\n\n        self._general_names = general_names\n    __len__, __iter__, __getitem__ = _make_sequence_methods(\"_general_names\")\n\n    def get_values_for_type(self, type):\n        # Return the value of each GeneralName, except for OtherName instances\n        # which we return directly because it has two important properties not\n        # just one value.\n        objs = (i for i in self if isinstance(i, type))\n        if type != OtherName:\n            objs = (i.value for i in objs)\n        return list(objs)\n\n    def __repr__(self):\n        return \"<GeneralNames({})>\".format(self._general_names)\n\n    def __eq__(self, other):\n        if not isinstance(other, GeneralNames):\n            return NotImplemented\n\n        return self._general_names == other._general_names\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(tuple(self._general_names))\n\n\n@utils.register_interface(ExtensionType)\nclass SubjectAlternativeName(object):\n    oid = ExtensionOID.SUBJECT_ALTERNATIVE_NAME\n\n    def __init__(self, general_names):\n        self._general_names = GeneralNames(general_names)\n\n    __len__, __iter__, __getitem__ = _make_sequence_methods(\"_general_names\")\n\n    def get_values_for_type(self, type):\n        return self._general_names.get_values_for_type(type)\n\n    def __repr__(self):\n        return \"<SubjectAlternativeName({})>\".format(self._general_names)\n\n    def __eq__(self, other):\n        if not isinstance(other, SubjectAlternativeName):\n            return NotImplemented\n\n        return self._general_names == other._general_names\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self._general_names)\n\n\n@utils.register_interface(ExtensionType)\nclass IssuerAlternativeName(object):\n    oid = ExtensionOID.ISSUER_ALTERNATIVE_NAME\n\n    def __init__(self, general_names):\n        self._general_names = GeneralNames(general_names)\n\n    __len__, __iter__, __getitem__ = _make_sequence_methods(\"_general_names\")\n\n    def get_values_for_type(self, type):\n        return self._general_names.get_values_for_type(type)\n\n    def __repr__(self):\n        return \"<IssuerAlternativeName({})>\".format(self._general_names)\n\n    def __eq__(self, other):\n        if not isinstance(other, IssuerAlternativeName):\n            return NotImplemented\n\n        return self._general_names == other._general_names\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self._general_names)\n\n\n@utils.register_interface(ExtensionType)\nclass CertificateIssuer(object):\n    oid = CRLEntryExtensionOID.CERTIFICATE_ISSUER\n\n    def __init__(self, general_names):\n        self._general_names = GeneralNames(general_names)\n\n    __len__, __iter__, __getitem__ = _make_sequence_methods(\"_general_names\")\n\n    def get_values_for_type(self, type):\n        return self._general_names.get_values_for_type(type)\n\n    def __repr__(self):\n        return \"<CertificateIssuer({})>\".format(self._general_names)\n\n    def __eq__(self, other):\n        if not isinstance(other, CertificateIssuer):\n            return NotImplemented\n\n        return self._general_names == other._general_names\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self._general_names)\n\n\n@utils.register_interface(ExtensionType)\nclass CRLReason(object):\n    oid = CRLEntryExtensionOID.CRL_REASON\n\n    def __init__(self, reason):\n        if not isinstance(reason, ReasonFlags):\n            raise TypeError(\"reason must be an element from ReasonFlags\")\n\n        self._reason = reason\n\n    def __repr__(self):\n        return \"<CRLReason(reason={})>\".format(self._reason)\n\n    def __eq__(self, other):\n        if not isinstance(other, CRLReason):\n            return NotImplemented\n\n        return self.reason == other.reason\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.reason)\n\n    reason = utils.read_only_property(\"_reason\")\n\n\n@utils.register_interface(ExtensionType)\nclass InvalidityDate(object):\n    oid = CRLEntryExtensionOID.INVALIDITY_DATE\n\n    def __init__(self, invalidity_date):\n        if not isinstance(invalidity_date, datetime.datetime):\n            raise TypeError(\"invalidity_date must be a datetime.datetime\")\n\n        self._invalidity_date = invalidity_date\n\n    def __repr__(self):\n        return \"<InvalidityDate(invalidity_date={})>\".format(\n            self._invalidity_date\n        )\n\n    def __eq__(self, other):\n        if not isinstance(other, InvalidityDate):\n            return NotImplemented\n\n        return self.invalidity_date == other.invalidity_date\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.invalidity_date)\n\n    invalidity_date = utils.read_only_property(\"_invalidity_date\")\n\n\n@utils.register_interface(ExtensionType)\nclass PrecertificateSignedCertificateTimestamps(object):\n    oid = ExtensionOID.PRECERT_SIGNED_CERTIFICATE_TIMESTAMPS\n\n    def __init__(self, signed_certificate_timestamps):\n        signed_certificate_timestamps = list(signed_certificate_timestamps)\n        if not all(\n            isinstance(sct, SignedCertificateTimestamp)\n            for sct in signed_certificate_timestamps\n        ):\n            raise TypeError(\n                \"Every item in the signed_certificate_timestamps list must be \"\n                \"a SignedCertificateTimestamp\"\n            )\n        self._signed_certificate_timestamps = signed_certificate_timestamps\n\n    __len__, __iter__, __getitem__ = _make_sequence_methods(\n        \"_signed_certificate_timestamps\"\n    )\n\n    def __repr__(self):\n        return (\n            \"<PrecertificateSignedCertificateTimestamps({})>\".format(\n                list(self)\n            )\n        )\n\n    def __hash__(self):\n        return hash(tuple(self._signed_certificate_timestamps))\n\n    def __eq__(self, other):\n        if not isinstance(other, PrecertificateSignedCertificateTimestamps):\n            return NotImplemented\n\n        return (\n            self._signed_certificate_timestamps ==\n            other._signed_certificate_timestamps\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n\n@utils.register_interface(ExtensionType)\nclass OCSPNonce(object):\n    oid = OCSPExtensionOID.NONCE\n\n    def __init__(self, nonce):\n        if not isinstance(nonce, bytes):\n            raise TypeError(\"nonce must be bytes\")\n\n        self._nonce = nonce\n\n    def __eq__(self, other):\n        if not isinstance(other, OCSPNonce):\n            return NotImplemented\n\n        return self.nonce == other.nonce\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.nonce)\n\n    def __repr__(self):\n        return \"<OCSPNonce(nonce={0.nonce!r})>\".format(self)\n\n    nonce = utils.read_only_property(\"_nonce\")\n\n\n@utils.register_interface(ExtensionType)\nclass IssuingDistributionPoint(object):\n    oid = ExtensionOID.ISSUING_DISTRIBUTION_POINT\n\n    def __init__(self, full_name, relative_name, only_contains_user_certs,\n                 only_contains_ca_certs, only_some_reasons, indirect_crl,\n                 only_contains_attribute_certs):\n        if (\n            only_some_reasons and (\n                not isinstance(only_some_reasons, frozenset) or not all(\n                    isinstance(x, ReasonFlags) for x in only_some_reasons\n                )\n            )\n        ):\n            raise TypeError(\n                \"only_some_reasons must be None or frozenset of ReasonFlags\"\n            )\n\n        if only_some_reasons and (\n            ReasonFlags.unspecified in only_some_reasons or\n            ReasonFlags.remove_from_crl in only_some_reasons\n        ):\n            raise ValueError(\n                \"unspecified and remove_from_crl are not valid reasons in an \"\n                \"IssuingDistributionPoint\"\n            )\n\n        if not (\n            isinstance(only_contains_user_certs, bool) and\n            isinstance(only_contains_ca_certs, bool) and\n            isinstance(indirect_crl, bool) and\n            isinstance(only_contains_attribute_certs, bool)\n        ):\n            raise TypeError(\n                \"only_contains_user_certs, only_contains_ca_certs, \"\n                \"indirect_crl and only_contains_attribute_certs \"\n                \"must all be boolean.\"\n            )\n\n        crl_constraints = [\n            only_contains_user_certs, only_contains_ca_certs,\n            indirect_crl, only_contains_attribute_certs\n        ]\n\n        if len([x for x in crl_constraints if x]) > 1:\n            raise ValueError(\n                \"Only one of the following can be set to True: \"\n                \"only_contains_user_certs, only_contains_ca_certs, \"\n                \"indirect_crl, only_contains_attribute_certs\"\n            )\n\n        if (\n            not any([\n                only_contains_user_certs, only_contains_ca_certs,\n                indirect_crl, only_contains_attribute_certs, full_name,\n                relative_name, only_some_reasons\n            ])\n        ):\n            raise ValueError(\n                \"Cannot create empty extension: \"\n                \"if only_contains_user_certs, only_contains_ca_certs, \"\n                \"indirect_crl, and only_contains_attribute_certs are all False\"\n                \", then either full_name, relative_name, or only_some_reasons \"\n                \"must have a value.\"\n            )\n\n        self._only_contains_user_certs = only_contains_user_certs\n        self._only_contains_ca_certs = only_contains_ca_certs\n        self._indirect_crl = indirect_crl\n        self._only_contains_attribute_certs = only_contains_attribute_certs\n        self._only_some_reasons = only_some_reasons\n        self._full_name = full_name\n        self._relative_name = relative_name\n\n    def __repr__(self):\n        return (\n            \"<IssuingDistributionPoint(full_name={0.full_name}, \"\n            \"relative_name={0.relative_name}, \"\n            \"only_contains_user_certs={0.only_contains_user_certs}, \"\n            \"only_contains_ca_certs={0.only_contains_ca_certs}, \"\n            \"only_some_reasons={0.only_some_reasons}, \"\n            \"indirect_crl={0.indirect_crl}, \"\n            \"only_contains_attribute_certs=\"\n            \"{0.only_contains_attribute_certs})>\".format(self)\n        )\n\n    def __eq__(self, other):\n        if not isinstance(other, IssuingDistributionPoint):\n            return NotImplemented\n\n        return (\n            self.full_name == other.full_name and\n            self.relative_name == other.relative_name and\n            self.only_contains_user_certs == other.only_contains_user_certs and\n            self.only_contains_ca_certs == other.only_contains_ca_certs and\n            self.only_some_reasons == other.only_some_reasons and\n            self.indirect_crl == other.indirect_crl and\n            self.only_contains_attribute_certs ==\n            other.only_contains_attribute_certs\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((\n            self.full_name,\n            self.relative_name,\n            self.only_contains_user_certs,\n            self.only_contains_ca_certs,\n            self.only_some_reasons,\n            self.indirect_crl,\n            self.only_contains_attribute_certs,\n        ))\n\n    full_name = utils.read_only_property(\"_full_name\")\n    relative_name = utils.read_only_property(\"_relative_name\")\n    only_contains_user_certs = utils.read_only_property(\n        \"_only_contains_user_certs\"\n    )\n    only_contains_ca_certs = utils.read_only_property(\n        \"_only_contains_ca_certs\"\n    )\n    only_some_reasons = utils.read_only_property(\"_only_some_reasons\")\n    indirect_crl = utils.read_only_property(\"_indirect_crl\")\n    only_contains_attribute_certs = utils.read_only_property(\n        \"_only_contains_attribute_certs\"\n    )\n\n\n@utils.register_interface(ExtensionType)\nclass UnrecognizedExtension(object):\n    def __init__(self, oid, value):\n        if not isinstance(oid, ObjectIdentifier):\n            raise TypeError(\"oid must be an ObjectIdentifier\")\n        self._oid = oid\n        self._value = value\n\n    oid = utils.read_only_property(\"_oid\")\n    value = utils.read_only_property(\"_value\")\n\n    def __repr__(self):\n        return (\n            \"<UnrecognizedExtension(oid={0.oid}, value={0.value!r})>\".format(\n                self\n            )\n        )\n\n    def __eq__(self, other):\n        if not isinstance(other, UnrecognizedExtension):\n            return NotImplemented\n\n        return self.oid == other.oid and self.value == other.value\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((self.oid, self.value))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/x509/general_name.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\nimport ipaddress\nimport warnings\nfrom email.utils import parseaddr\n\nimport six\nfrom six.moves import urllib_parse\n\nfrom cryptography import utils\nfrom cryptography.x509.name import Name\nfrom cryptography.x509.oid import ObjectIdentifier\n\n\n_GENERAL_NAMES = {\n    0: \"otherName\",\n    1: \"rfc822Name\",\n    2: \"dNSName\",\n    3: \"x400Address\",\n    4: \"directoryName\",\n    5: \"ediPartyName\",\n    6: \"uniformResourceIdentifier\",\n    7: \"iPAddress\",\n    8: \"registeredID\",\n}\n\n\ndef _lazy_import_idna():\n    # Import idna lazily becase it allocates a decent amount of memory, and\n    # we're only using it in deprecated paths.\n    try:\n        import idna\n        return idna\n    except ImportError:\n        raise ImportError(\n            \"idna is not installed, but a deprecated feature that requires it\"\n            \" was used. See: https://cryptography.io/en/latest/faq/#importe\"\n            \"rror-idna-is-not-installed\"\n        )\n\n\nclass UnsupportedGeneralNameType(Exception):\n    def __init__(self, msg, type):\n        super(UnsupportedGeneralNameType, self).__init__(msg)\n        self.type = type\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass GeneralName(object):\n    @abc.abstractproperty\n    def value(self):\n        \"\"\"\n        Return the value of the object\n        \"\"\"\n\n\n@utils.register_interface(GeneralName)\nclass RFC822Name(object):\n    def __init__(self, value):\n        if isinstance(value, six.text_type):\n            try:\n                value.encode(\"ascii\")\n            except UnicodeEncodeError:\n                value = self._idna_encode(value)\n                warnings.warn(\n                    \"RFC822Name values should be passed as an A-label string. \"\n                    \"This means unicode characters should be encoded via \"\n                    \"idna. Support for passing unicode strings (aka U-label) \"\n                    \"will be removed in a future version.\",\n                    utils.PersistentlyDeprecated2017,\n                    stacklevel=2,\n                )\n        else:\n            raise TypeError(\"value must be string\")\n\n        name, address = parseaddr(value)\n        if name or not address:\n            # parseaddr has found a name (e.g. Name <email>) or the entire\n            # value is an empty string.\n            raise ValueError(\"Invalid rfc822name value\")\n\n        self._value = value\n\n    value = utils.read_only_property(\"_value\")\n\n    @classmethod\n    def _init_without_validation(cls, value):\n        instance = cls.__new__(cls)\n        instance._value = value\n        return instance\n\n    def _idna_encode(self, value):\n        idna = _lazy_import_idna()\n        _, address = parseaddr(value)\n        parts = address.split(u\"@\")\n        return parts[0] + \"@\" + idna.encode(parts[1]).decode(\"ascii\")\n\n    def __repr__(self):\n        return \"<RFC822Name(value={0!r})>\".format(self.value)\n\n    def __eq__(self, other):\n        if not isinstance(other, RFC822Name):\n            return NotImplemented\n\n        return self.value == other.value\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.value)\n\n\ndef _idna_encode(value):\n    idna = _lazy_import_idna()\n    # Retain prefixes '*.' for common/alt names and '.' for name constraints\n    for prefix in ['*.', '.']:\n        if value.startswith(prefix):\n            value = value[len(prefix):]\n            return prefix + idna.encode(value).decode(\"ascii\")\n    return idna.encode(value).decode(\"ascii\")\n\n\n@utils.register_interface(GeneralName)\nclass DNSName(object):\n    def __init__(self, value):\n        if isinstance(value, six.text_type):\n            try:\n                value.encode(\"ascii\")\n            except UnicodeEncodeError:\n                value = _idna_encode(value)\n                warnings.warn(\n                    \"DNSName values should be passed as an A-label string. \"\n                    \"This means unicode characters should be encoded via \"\n                    \"idna. Support for passing unicode strings (aka U-label) \"\n                    \"will be removed in a future version.\",\n                    utils.PersistentlyDeprecated2017,\n                    stacklevel=2,\n                )\n        else:\n            raise TypeError(\"value must be string\")\n\n        self._value = value\n\n    value = utils.read_only_property(\"_value\")\n\n    @classmethod\n    def _init_without_validation(cls, value):\n        instance = cls.__new__(cls)\n        instance._value = value\n        return instance\n\n    def __repr__(self):\n        return \"<DNSName(value={0!r})>\".format(self.value)\n\n    def __eq__(self, other):\n        if not isinstance(other, DNSName):\n            return NotImplemented\n\n        return self.value == other.value\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.value)\n\n\n@utils.register_interface(GeneralName)\nclass UniformResourceIdentifier(object):\n    def __init__(self, value):\n        if isinstance(value, six.text_type):\n            try:\n                value.encode(\"ascii\")\n            except UnicodeEncodeError:\n                value = self._idna_encode(value)\n                warnings.warn(\n                    \"URI values should be passed as an A-label string. \"\n                    \"This means unicode characters should be encoded via \"\n                    \"idna. Support for passing unicode strings (aka U-label) \"\n                    \" will be removed in a future version.\",\n                    utils.PersistentlyDeprecated2017,\n                    stacklevel=2,\n                )\n        else:\n            raise TypeError(\"value must be string\")\n\n        self._value = value\n\n    value = utils.read_only_property(\"_value\")\n\n    @classmethod\n    def _init_without_validation(cls, value):\n        instance = cls.__new__(cls)\n        instance._value = value\n        return instance\n\n    def _idna_encode(self, value):\n        idna = _lazy_import_idna()\n        parsed = urllib_parse.urlparse(value)\n        if parsed.port:\n            netloc = (\n                idna.encode(parsed.hostname) +\n                \":{}\".format(parsed.port).encode(\"ascii\")\n            ).decode(\"ascii\")\n        else:\n            netloc = idna.encode(parsed.hostname).decode(\"ascii\")\n\n        # Note that building a URL in this fashion means it should be\n        # semantically indistinguishable from the original but is not\n        # guaranteed to be exactly the same.\n        return urllib_parse.urlunparse((\n            parsed.scheme,\n            netloc,\n            parsed.path,\n            parsed.params,\n            parsed.query,\n            parsed.fragment\n        ))\n\n    def __repr__(self):\n        return \"<UniformResourceIdentifier(value={0!r})>\".format(self.value)\n\n    def __eq__(self, other):\n        if not isinstance(other, UniformResourceIdentifier):\n            return NotImplemented\n\n        return self.value == other.value\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.value)\n\n\n@utils.register_interface(GeneralName)\nclass DirectoryName(object):\n    def __init__(self, value):\n        if not isinstance(value, Name):\n            raise TypeError(\"value must be a Name\")\n\n        self._value = value\n\n    value = utils.read_only_property(\"_value\")\n\n    def __repr__(self):\n        return \"<DirectoryName(value={})>\".format(self.value)\n\n    def __eq__(self, other):\n        if not isinstance(other, DirectoryName):\n            return NotImplemented\n\n        return self.value == other.value\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.value)\n\n\n@utils.register_interface(GeneralName)\nclass RegisteredID(object):\n    def __init__(self, value):\n        if not isinstance(value, ObjectIdentifier):\n            raise TypeError(\"value must be an ObjectIdentifier\")\n\n        self._value = value\n\n    value = utils.read_only_property(\"_value\")\n\n    def __repr__(self):\n        return \"<RegisteredID(value={})>\".format(self.value)\n\n    def __eq__(self, other):\n        if not isinstance(other, RegisteredID):\n            return NotImplemented\n\n        return self.value == other.value\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.value)\n\n\n@utils.register_interface(GeneralName)\nclass IPAddress(object):\n    def __init__(self, value):\n        if not isinstance(\n            value,\n            (\n                ipaddress.IPv4Address,\n                ipaddress.IPv6Address,\n                ipaddress.IPv4Network,\n                ipaddress.IPv6Network\n            )\n        ):\n            raise TypeError(\n                \"value must be an instance of ipaddress.IPv4Address, \"\n                \"ipaddress.IPv6Address, ipaddress.IPv4Network, or \"\n                \"ipaddress.IPv6Network\"\n            )\n\n        self._value = value\n\n    value = utils.read_only_property(\"_value\")\n\n    def __repr__(self):\n        return \"<IPAddress(value={})>\".format(self.value)\n\n    def __eq__(self, other):\n        if not isinstance(other, IPAddress):\n            return NotImplemented\n\n        return self.value == other.value\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.value)\n\n\n@utils.register_interface(GeneralName)\nclass OtherName(object):\n    def __init__(self, type_id, value):\n        if not isinstance(type_id, ObjectIdentifier):\n            raise TypeError(\"type_id must be an ObjectIdentifier\")\n        if not isinstance(value, bytes):\n            raise TypeError(\"value must be a binary string\")\n\n        self._type_id = type_id\n        self._value = value\n\n    type_id = utils.read_only_property(\"_type_id\")\n    value = utils.read_only_property(\"_value\")\n\n    def __repr__(self):\n        return \"<OtherName(type_id={}, value={!r})>\".format(\n            self.type_id, self.value)\n\n    def __eq__(self, other):\n        if not isinstance(other, OtherName):\n            return NotImplemented\n\n        return self.type_id == other.type_id and self.value == other.value\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((self.type_id, self.value))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/x509/name.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom enum import Enum\n\nimport six\n\nfrom cryptography import utils\nfrom cryptography.x509.oid import NameOID, ObjectIdentifier\n\n\nclass _ASN1Type(Enum):\n    UTF8String = 12\n    NumericString = 18\n    PrintableString = 19\n    T61String = 20\n    IA5String = 22\n    UTCTime = 23\n    GeneralizedTime = 24\n    VisibleString = 26\n    UniversalString = 28\n    BMPString = 30\n\n\n_ASN1_TYPE_TO_ENUM = dict((i.value, i) for i in _ASN1Type)\n_SENTINEL = object()\n_NAMEOID_DEFAULT_TYPE = {\n    NameOID.COUNTRY_NAME: _ASN1Type.PrintableString,\n    NameOID.JURISDICTION_COUNTRY_NAME: _ASN1Type.PrintableString,\n    NameOID.SERIAL_NUMBER: _ASN1Type.PrintableString,\n    NameOID.DN_QUALIFIER: _ASN1Type.PrintableString,\n    NameOID.EMAIL_ADDRESS: _ASN1Type.IA5String,\n    NameOID.DOMAIN_COMPONENT: _ASN1Type.IA5String,\n}\n\n#: Short attribute names from RFC 4514:\n#: https://tools.ietf.org/html/rfc4514#page-7\n_NAMEOID_TO_NAME = {\n    NameOID.COMMON_NAME: 'CN',\n    NameOID.LOCALITY_NAME: 'L',\n    NameOID.STATE_OR_PROVINCE_NAME: 'ST',\n    NameOID.ORGANIZATION_NAME: 'O',\n    NameOID.ORGANIZATIONAL_UNIT_NAME: 'OU',\n    NameOID.COUNTRY_NAME: 'C',\n    NameOID.STREET_ADDRESS: 'STREET',\n    NameOID.DOMAIN_COMPONENT: 'DC',\n    NameOID.USER_ID: 'UID',\n}\n\n\ndef _escape_dn_value(val):\n    \"\"\"Escape special characters in RFC4514 Distinguished Name value.\"\"\"\n\n    # See https://tools.ietf.org/html/rfc4514#section-2.4\n    val = val.replace('\\\\', '\\\\\\\\')\n    val = val.replace('\"', '\\\\\"')\n    val = val.replace('+', '\\\\+')\n    val = val.replace(',', '\\\\,')\n    val = val.replace(';', '\\\\;')\n    val = val.replace('<', '\\\\<')\n    val = val.replace('>', '\\\\>')\n    val = val.replace('\\0', '\\\\00')\n\n    if val[0] in ('#', ' '):\n        val = '\\\\' + val\n    if val[-1] == ' ':\n        val = val[:-1] + '\\\\ '\n\n    return val\n\n\nclass NameAttribute(object):\n    def __init__(self, oid, value, _type=_SENTINEL):\n        if not isinstance(oid, ObjectIdentifier):\n            raise TypeError(\n                \"oid argument must be an ObjectIdentifier instance.\"\n            )\n\n        if not isinstance(value, six.text_type):\n            raise TypeError(\n                \"value argument must be a text type.\"\n            )\n\n        if (\n            oid == NameOID.COUNTRY_NAME or\n            oid == NameOID.JURISDICTION_COUNTRY_NAME\n        ):\n            if len(value.encode(\"utf8\")) != 2:\n                raise ValueError(\n                    \"Country name must be a 2 character country code\"\n                )\n\n        if len(value) == 0:\n            raise ValueError(\"Value cannot be an empty string\")\n\n        # The appropriate ASN1 string type varies by OID and is defined across\n        # multiple RFCs including 2459, 3280, and 5280. In general UTF8String\n        # is preferred (2459), but 3280 and 5280 specify several OIDs with\n        # alternate types. This means when we see the sentinel value we need\n        # to look up whether the OID has a non-UTF8 type. If it does, set it\n        # to that. Otherwise, UTF8!\n        if _type == _SENTINEL:\n            _type = _NAMEOID_DEFAULT_TYPE.get(oid, _ASN1Type.UTF8String)\n\n        if not isinstance(_type, _ASN1Type):\n            raise TypeError(\"_type must be from the _ASN1Type enum\")\n\n        self._oid = oid\n        self._value = value\n        self._type = _type\n\n    oid = utils.read_only_property(\"_oid\")\n    value = utils.read_only_property(\"_value\")\n\n    def rfc4514_string(self):\n        \"\"\"\n        Format as RFC4514 Distinguished Name string.\n\n        Use short attribute name if available, otherwise fall back to OID\n        dotted string.\n        \"\"\"\n        key = _NAMEOID_TO_NAME.get(self.oid, self.oid.dotted_string)\n        return '%s=%s' % (key, _escape_dn_value(self.value))\n\n    def __eq__(self, other):\n        if not isinstance(other, NameAttribute):\n            return NotImplemented\n\n        return (\n            self.oid == other.oid and\n            self.value == other.value\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash((self.oid, self.value))\n\n    def __repr__(self):\n        return \"<NameAttribute(oid={0.oid}, value={0.value!r})>\".format(self)\n\n\nclass RelativeDistinguishedName(object):\n    def __init__(self, attributes):\n        attributes = list(attributes)\n        if not attributes:\n            raise ValueError(\"a relative distinguished name cannot be empty\")\n        if not all(isinstance(x, NameAttribute) for x in attributes):\n            raise TypeError(\"attributes must be an iterable of NameAttribute\")\n\n        # Keep list and frozenset to preserve attribute order where it matters\n        self._attributes = attributes\n        self._attribute_set = frozenset(attributes)\n\n        if len(self._attribute_set) != len(attributes):\n            raise ValueError(\"duplicate attributes are not allowed\")\n\n    def get_attributes_for_oid(self, oid):\n        return [i for i in self if i.oid == oid]\n\n    def rfc4514_string(self):\n        \"\"\"\n        Format as RFC4514 Distinguished Name string.\n\n        Within each RDN, attributes are joined by '+', although that is rarely\n        used in certificates.\n        \"\"\"\n        return '+'.join(attr.rfc4514_string() for attr in self._attributes)\n\n    def __eq__(self, other):\n        if not isinstance(other, RelativeDistinguishedName):\n            return NotImplemented\n\n        return self._attribute_set == other._attribute_set\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self._attribute_set)\n\n    def __iter__(self):\n        return iter(self._attributes)\n\n    def __len__(self):\n        return len(self._attributes)\n\n    def __repr__(self):\n        return \"<RelativeDistinguishedName({})>\".format(self.rfc4514_string())\n\n\nclass Name(object):\n    def __init__(self, attributes):\n        attributes = list(attributes)\n        if all(isinstance(x, NameAttribute) for x in attributes):\n            self._attributes = [\n                RelativeDistinguishedName([x]) for x in attributes\n            ]\n        elif all(isinstance(x, RelativeDistinguishedName) for x in attributes):\n            self._attributes = attributes\n        else:\n            raise TypeError(\n                \"attributes must be a list of NameAttribute\"\n                \" or a list RelativeDistinguishedName\"\n            )\n\n    def rfc4514_string(self):\n        \"\"\"\n        Format as RFC4514 Distinguished Name string.\n        For example 'CN=foobar.com,O=Foo Corp,C=US'\n\n        An X.509 name is a two-level structure: a list of sets of attributes.\n        Each list element is separated by ',' and within each list element, set\n        elements are separated by '+'. The latter is almost never used in\n        real world certificates.\n        \"\"\"\n        return ','.join(attr.rfc4514_string() for attr in self._attributes)\n\n    def get_attributes_for_oid(self, oid):\n        return [i for i in self if i.oid == oid]\n\n    @property\n    def rdns(self):\n        return self._attributes\n\n    def public_bytes(self, backend):\n        return backend.x509_name_bytes(self)\n\n    def __eq__(self, other):\n        if not isinstance(other, Name):\n            return NotImplemented\n\n        return self._attributes == other._attributes\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        # TODO: this is relatively expensive, if this looks like a bottleneck\n        # for you, consider optimizing!\n        return hash(tuple(self._attributes))\n\n    def __iter__(self):\n        for rdn in self._attributes:\n            for ava in rdn:\n                yield ava\n\n    def __len__(self):\n        return sum(len(rdn) for rdn in self._attributes)\n\n    def __repr__(self):\n        if six.PY2:\n            return \"<Name({})>\".format(self.rfc4514_string().encode('utf8'))\n        else:\n            return \"<Name({})>\".format(self.rfc4514_string())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/x509/ocsp.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\nimport datetime\nfrom enum import Enum\n\nimport six\n\nfrom cryptography import x509\nfrom cryptography.hazmat.primitives import hashes\nfrom cryptography.hazmat.primitives.asymmetric import ed25519, ed448\nfrom cryptography.x509.base import (\n    _EARLIEST_UTC_TIME, _convert_to_naive_utc_time, _reject_duplicate_extension\n)\n\n\n_OIDS_TO_HASH = {\n    \"1.3.14.3.2.26\": hashes.SHA1(),\n    \"2.16.840.1.101.3.4.2.4\": hashes.SHA224(),\n    \"2.16.840.1.101.3.4.2.1\": hashes.SHA256(),\n    \"2.16.840.1.101.3.4.2.2\": hashes.SHA384(),\n    \"2.16.840.1.101.3.4.2.3\": hashes.SHA512(),\n}\n\n\nclass OCSPResponderEncoding(Enum):\n    HASH = \"By Hash\"\n    NAME = \"By Name\"\n\n\nclass OCSPResponseStatus(Enum):\n    SUCCESSFUL = 0\n    MALFORMED_REQUEST = 1\n    INTERNAL_ERROR = 2\n    TRY_LATER = 3\n    SIG_REQUIRED = 5\n    UNAUTHORIZED = 6\n\n\n_RESPONSE_STATUS_TO_ENUM = dict((x.value, x) for x in OCSPResponseStatus)\n_ALLOWED_HASHES = (\n    hashes.SHA1, hashes.SHA224, hashes.SHA256,\n    hashes.SHA384, hashes.SHA512\n)\n\n\ndef _verify_algorithm(algorithm):\n    if not isinstance(algorithm, _ALLOWED_HASHES):\n        raise ValueError(\n            \"Algorithm must be SHA1, SHA224, SHA256, SHA384, or SHA512\"\n        )\n\n\nclass OCSPCertStatus(Enum):\n    GOOD = 0\n    REVOKED = 1\n    UNKNOWN = 2\n\n\n_CERT_STATUS_TO_ENUM = dict((x.value, x) for x in OCSPCertStatus)\n\n\ndef load_der_ocsp_request(data):\n    from cryptography.hazmat.backends.openssl.backend import backend\n    return backend.load_der_ocsp_request(data)\n\n\ndef load_der_ocsp_response(data):\n    from cryptography.hazmat.backends.openssl.backend import backend\n    return backend.load_der_ocsp_response(data)\n\n\nclass OCSPRequestBuilder(object):\n    def __init__(self, request=None, extensions=[]):\n        self._request = request\n        self._extensions = extensions\n\n    def add_certificate(self, cert, issuer, algorithm):\n        if self._request is not None:\n            raise ValueError(\"Only one certificate can be added to a request\")\n\n        _verify_algorithm(algorithm)\n        if (\n            not isinstance(cert, x509.Certificate) or\n            not isinstance(issuer, x509.Certificate)\n        ):\n            raise TypeError(\"cert and issuer must be a Certificate\")\n\n        return OCSPRequestBuilder((cert, issuer, algorithm), self._extensions)\n\n    def add_extension(self, extension, critical):\n        if not isinstance(extension, x509.ExtensionType):\n            raise TypeError(\"extension must be an ExtensionType\")\n\n        extension = x509.Extension(extension.oid, critical, extension)\n        _reject_duplicate_extension(extension, self._extensions)\n\n        return OCSPRequestBuilder(\n            self._request, self._extensions + [extension]\n        )\n\n    def build(self):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if self._request is None:\n            raise ValueError(\"You must add a certificate before building\")\n\n        return backend.create_ocsp_request(self)\n\n\nclass _SingleResponse(object):\n    def __init__(self, cert, issuer, algorithm, cert_status, this_update,\n                 next_update, revocation_time, revocation_reason):\n        if (\n            not isinstance(cert, x509.Certificate) or\n            not isinstance(issuer, x509.Certificate)\n        ):\n            raise TypeError(\"cert and issuer must be a Certificate\")\n\n        _verify_algorithm(algorithm)\n        if not isinstance(this_update, datetime.datetime):\n            raise TypeError(\"this_update must be a datetime object\")\n        if (\n            next_update is not None and\n            not isinstance(next_update, datetime.datetime)\n        ):\n            raise TypeError(\"next_update must be a datetime object or None\")\n\n        self._cert = cert\n        self._issuer = issuer\n        self._algorithm = algorithm\n        self._this_update = this_update\n        self._next_update = next_update\n\n        if not isinstance(cert_status, OCSPCertStatus):\n            raise TypeError(\n                \"cert_status must be an item from the OCSPCertStatus enum\"\n            )\n        if cert_status is not OCSPCertStatus.REVOKED:\n            if revocation_time is not None:\n                raise ValueError(\n                    \"revocation_time can only be provided if the certificate \"\n                    \"is revoked\"\n                )\n            if revocation_reason is not None:\n                raise ValueError(\n                    \"revocation_reason can only be provided if the certificate\"\n                    \" is revoked\"\n                )\n        else:\n            if not isinstance(revocation_time, datetime.datetime):\n                raise TypeError(\"revocation_time must be a datetime object\")\n\n            revocation_time = _convert_to_naive_utc_time(revocation_time)\n            if revocation_time < _EARLIEST_UTC_TIME:\n                raise ValueError('The revocation_time must be on or after'\n                                 ' 1950 January 1.')\n\n            if (\n                revocation_reason is not None and\n                not isinstance(revocation_reason, x509.ReasonFlags)\n            ):\n                raise TypeError(\n                    \"revocation_reason must be an item from the ReasonFlags \"\n                    \"enum or None\"\n                )\n\n        self._cert_status = cert_status\n        self._revocation_time = revocation_time\n        self._revocation_reason = revocation_reason\n\n\nclass OCSPResponseBuilder(object):\n    def __init__(self, response=None, responder_id=None, certs=None,\n                 extensions=[]):\n        self._response = response\n        self._responder_id = responder_id\n        self._certs = certs\n        self._extensions = extensions\n\n    def add_response(self, cert, issuer, algorithm, cert_status, this_update,\n                     next_update, revocation_time, revocation_reason):\n        if self._response is not None:\n            raise ValueError(\"Only one response per OCSPResponse.\")\n\n        singleresp = _SingleResponse(\n            cert, issuer, algorithm, cert_status, this_update, next_update,\n            revocation_time, revocation_reason\n        )\n        return OCSPResponseBuilder(\n            singleresp, self._responder_id,\n            self._certs, self._extensions,\n        )\n\n    def responder_id(self, encoding, responder_cert):\n        if self._responder_id is not None:\n            raise ValueError(\"responder_id can only be set once\")\n        if not isinstance(responder_cert, x509.Certificate):\n            raise TypeError(\"responder_cert must be a Certificate\")\n        if not isinstance(encoding, OCSPResponderEncoding):\n            raise TypeError(\n                \"encoding must be an element from OCSPResponderEncoding\"\n            )\n\n        return OCSPResponseBuilder(\n            self._response, (responder_cert, encoding),\n            self._certs, self._extensions,\n        )\n\n    def certificates(self, certs):\n        if self._certs is not None:\n            raise ValueError(\"certificates may only be set once\")\n        certs = list(certs)\n        if len(certs) == 0:\n            raise ValueError(\"certs must not be an empty list\")\n        if not all(isinstance(x, x509.Certificate) for x in certs):\n            raise TypeError(\"certs must be a list of Certificates\")\n        return OCSPResponseBuilder(\n            self._response, self._responder_id,\n            certs, self._extensions,\n        )\n\n    def add_extension(self, extension, critical):\n        if not isinstance(extension, x509.ExtensionType):\n            raise TypeError(\"extension must be an ExtensionType\")\n\n        extension = x509.Extension(extension.oid, critical, extension)\n        _reject_duplicate_extension(extension, self._extensions)\n\n        return OCSPResponseBuilder(\n            self._response, self._responder_id,\n            self._certs, self._extensions + [extension],\n        )\n\n    def sign(self, private_key, algorithm):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if self._response is None:\n            raise ValueError(\"You must add a response before signing\")\n        if self._responder_id is None:\n            raise ValueError(\"You must add a responder_id before signing\")\n\n        if isinstance(private_key,\n                      (ed25519.Ed25519PrivateKey, ed448.Ed448PrivateKey)):\n            if algorithm is not None:\n                raise ValueError(\n                    \"algorithm must be None when signing via ed25519 or ed448\"\n                )\n        elif not isinstance(algorithm, hashes.HashAlgorithm):\n            raise TypeError(\"Algorithm must be a registered hash algorithm.\")\n\n        return backend.create_ocsp_response(\n            OCSPResponseStatus.SUCCESSFUL, self, private_key, algorithm\n        )\n\n    @classmethod\n    def build_unsuccessful(cls, response_status):\n        from cryptography.hazmat.backends.openssl.backend import backend\n        if not isinstance(response_status, OCSPResponseStatus):\n            raise TypeError(\n                \"response_status must be an item from OCSPResponseStatus\"\n            )\n        if response_status is OCSPResponseStatus.SUCCESSFUL:\n            raise ValueError(\"response_status cannot be SUCCESSFUL\")\n\n        return backend.create_ocsp_response(response_status, None, None, None)\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass OCSPRequest(object):\n    @abc.abstractproperty\n    def issuer_key_hash(self):\n        \"\"\"\n        The hash of the issuer public key\n        \"\"\"\n\n    @abc.abstractproperty\n    def issuer_name_hash(self):\n        \"\"\"\n        The hash of the issuer name\n        \"\"\"\n\n    @abc.abstractproperty\n    def hash_algorithm(self):\n        \"\"\"\n        The hash algorithm used in the issuer name and key hashes\n        \"\"\"\n\n    @abc.abstractproperty\n    def serial_number(self):\n        \"\"\"\n        The serial number of the cert whose status is being checked\n        \"\"\"\n    @abc.abstractmethod\n    def public_bytes(self, encoding):\n        \"\"\"\n        Serializes the request to DER\n        \"\"\"\n\n    @abc.abstractproperty\n    def extensions(self):\n        \"\"\"\n        The list of request extensions. Not single request extensions.\n        \"\"\"\n\n\n@six.add_metaclass(abc.ABCMeta)\nclass OCSPResponse(object):\n    @abc.abstractproperty\n    def response_status(self):\n        \"\"\"\n        The status of the response. This is a value from the OCSPResponseStatus\n        enumeration\n        \"\"\"\n\n    @abc.abstractproperty\n    def signature_algorithm_oid(self):\n        \"\"\"\n        The ObjectIdentifier of the signature algorithm\n        \"\"\"\n\n    @abc.abstractproperty\n    def signature_hash_algorithm(self):\n        \"\"\"\n        Returns a HashAlgorithm corresponding to the type of the digest signed\n        \"\"\"\n\n    @abc.abstractproperty\n    def signature(self):\n        \"\"\"\n        The signature bytes\n        \"\"\"\n\n    @abc.abstractproperty\n    def tbs_response_bytes(self):\n        \"\"\"\n        The tbsResponseData bytes\n        \"\"\"\n\n    @abc.abstractproperty\n    def certificates(self):\n        \"\"\"\n        A list of certificates used to help build a chain to verify the OCSP\n        response. This situation occurs when the OCSP responder uses a delegate\n        certificate.\n        \"\"\"\n\n    @abc.abstractproperty\n    def responder_key_hash(self):\n        \"\"\"\n        The responder's key hash or None\n        \"\"\"\n\n    @abc.abstractproperty\n    def responder_name(self):\n        \"\"\"\n        The responder's Name or None\n        \"\"\"\n\n    @abc.abstractproperty\n    def produced_at(self):\n        \"\"\"\n        The time the response was produced\n        \"\"\"\n\n    @abc.abstractproperty\n    def certificate_status(self):\n        \"\"\"\n        The status of the certificate (an element from the OCSPCertStatus enum)\n        \"\"\"\n\n    @abc.abstractproperty\n    def revocation_time(self):\n        \"\"\"\n        The date of when the certificate was revoked or None if not\n        revoked.\n        \"\"\"\n\n    @abc.abstractproperty\n    def revocation_reason(self):\n        \"\"\"\n        The reason the certificate was revoked or None if not specified or\n        not revoked.\n        \"\"\"\n\n    @abc.abstractproperty\n    def this_update(self):\n        \"\"\"\n        The most recent time at which the status being indicated is known by\n        the responder to have been correct\n        \"\"\"\n\n    @abc.abstractproperty\n    def next_update(self):\n        \"\"\"\n        The time when newer information will be available\n        \"\"\"\n\n    @abc.abstractproperty\n    def issuer_key_hash(self):\n        \"\"\"\n        The hash of the issuer public key\n        \"\"\"\n\n    @abc.abstractproperty\n    def issuer_name_hash(self):\n        \"\"\"\n        The hash of the issuer name\n        \"\"\"\n\n    @abc.abstractproperty\n    def hash_algorithm(self):\n        \"\"\"\n        The hash algorithm used in the issuer name and key hashes\n        \"\"\"\n\n    @abc.abstractproperty\n    def serial_number(self):\n        \"\"\"\n        The serial number of the cert whose status is being checked\n        \"\"\"\n\n    @abc.abstractproperty\n    def extensions(self):\n        \"\"\"\n        The list of response extensions. Not single response extensions.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography/x509/oid.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom cryptography.hazmat._oid import ObjectIdentifier\nfrom cryptography.hazmat.primitives import hashes\n\n\nclass ExtensionOID(object):\n    SUBJECT_DIRECTORY_ATTRIBUTES = ObjectIdentifier(\"2.5.29.9\")\n    SUBJECT_KEY_IDENTIFIER = ObjectIdentifier(\"2.5.29.14\")\n    KEY_USAGE = ObjectIdentifier(\"2.5.29.15\")\n    SUBJECT_ALTERNATIVE_NAME = ObjectIdentifier(\"2.5.29.17\")\n    ISSUER_ALTERNATIVE_NAME = ObjectIdentifier(\"2.5.29.18\")\n    BASIC_CONSTRAINTS = ObjectIdentifier(\"2.5.29.19\")\n    NAME_CONSTRAINTS = ObjectIdentifier(\"2.5.29.30\")\n    CRL_DISTRIBUTION_POINTS = ObjectIdentifier(\"2.5.29.31\")\n    CERTIFICATE_POLICIES = ObjectIdentifier(\"2.5.29.32\")\n    POLICY_MAPPINGS = ObjectIdentifier(\"2.5.29.33\")\n    AUTHORITY_KEY_IDENTIFIER = ObjectIdentifier(\"2.5.29.35\")\n    POLICY_CONSTRAINTS = ObjectIdentifier(\"2.5.29.36\")\n    EXTENDED_KEY_USAGE = ObjectIdentifier(\"2.5.29.37\")\n    FRESHEST_CRL = ObjectIdentifier(\"2.5.29.46\")\n    INHIBIT_ANY_POLICY = ObjectIdentifier(\"2.5.29.54\")\n    ISSUING_DISTRIBUTION_POINT = ObjectIdentifier(\"2.5.29.28\")\n    AUTHORITY_INFORMATION_ACCESS = ObjectIdentifier(\"1.3.6.1.5.5.7.1.1\")\n    SUBJECT_INFORMATION_ACCESS = ObjectIdentifier(\"1.3.6.1.5.5.7.1.11\")\n    OCSP_NO_CHECK = ObjectIdentifier(\"1.3.6.1.5.5.7.48.1.5\")\n    TLS_FEATURE = ObjectIdentifier(\"1.3.6.1.5.5.7.1.24\")\n    CRL_NUMBER = ObjectIdentifier(\"2.5.29.20\")\n    DELTA_CRL_INDICATOR = ObjectIdentifier(\"2.5.29.27\")\n    PRECERT_SIGNED_CERTIFICATE_TIMESTAMPS = (\n        ObjectIdentifier(\"1.3.6.1.4.1.11129.2.4.2\")\n    )\n    PRECERT_POISON = (\n        ObjectIdentifier(\"1.3.6.1.4.1.11129.2.4.3\")\n    )\n\n\nclass OCSPExtensionOID(object):\n    NONCE = ObjectIdentifier(\"1.3.6.1.5.5.7.48.1.2\")\n\n\nclass CRLEntryExtensionOID(object):\n    CERTIFICATE_ISSUER = ObjectIdentifier(\"2.5.29.29\")\n    CRL_REASON = ObjectIdentifier(\"2.5.29.21\")\n    INVALIDITY_DATE = ObjectIdentifier(\"2.5.29.24\")\n\n\nclass NameOID(object):\n    COMMON_NAME = ObjectIdentifier(\"2.5.4.3\")\n    COUNTRY_NAME = ObjectIdentifier(\"2.5.4.6\")\n    LOCALITY_NAME = ObjectIdentifier(\"2.5.4.7\")\n    STATE_OR_PROVINCE_NAME = ObjectIdentifier(\"2.5.4.8\")\n    STREET_ADDRESS = ObjectIdentifier(\"2.5.4.9\")\n    ORGANIZATION_NAME = ObjectIdentifier(\"2.5.4.10\")\n    ORGANIZATIONAL_UNIT_NAME = ObjectIdentifier(\"2.5.4.11\")\n    SERIAL_NUMBER = ObjectIdentifier(\"2.5.4.5\")\n    SURNAME = ObjectIdentifier(\"2.5.4.4\")\n    GIVEN_NAME = ObjectIdentifier(\"2.5.4.42\")\n    TITLE = ObjectIdentifier(\"2.5.4.12\")\n    GENERATION_QUALIFIER = ObjectIdentifier(\"2.5.4.44\")\n    X500_UNIQUE_IDENTIFIER = ObjectIdentifier(\"2.5.4.45\")\n    DN_QUALIFIER = ObjectIdentifier(\"2.5.4.46\")\n    PSEUDONYM = ObjectIdentifier(\"2.5.4.65\")\n    USER_ID = ObjectIdentifier(\"0.9.2342.19200300.100.1.1\")\n    DOMAIN_COMPONENT = ObjectIdentifier(\"0.9.2342.19200300.100.1.25\")\n    EMAIL_ADDRESS = ObjectIdentifier(\"1.2.840.113549.1.9.1\")\n    JURISDICTION_COUNTRY_NAME = ObjectIdentifier(\"1.3.6.1.4.1.311.60.2.1.3\")\n    JURISDICTION_LOCALITY_NAME = ObjectIdentifier(\"1.3.6.1.4.1.311.60.2.1.1\")\n    JURISDICTION_STATE_OR_PROVINCE_NAME = ObjectIdentifier(\n        \"1.3.6.1.4.1.311.60.2.1.2\"\n    )\n    BUSINESS_CATEGORY = ObjectIdentifier(\"2.5.4.15\")\n    POSTAL_ADDRESS = ObjectIdentifier(\"2.5.4.16\")\n    POSTAL_CODE = ObjectIdentifier(\"2.5.4.17\")\n\n\nclass SignatureAlgorithmOID(object):\n    RSA_WITH_MD5 = ObjectIdentifier(\"1.2.840.113549.1.1.4\")\n    RSA_WITH_SHA1 = ObjectIdentifier(\"1.2.840.113549.1.1.5\")\n    # This is an alternate OID for RSA with SHA1 that is occasionally seen\n    _RSA_WITH_SHA1 = ObjectIdentifier(\"1.3.14.3.2.29\")\n    RSA_WITH_SHA224 = ObjectIdentifier(\"1.2.840.113549.1.1.14\")\n    RSA_WITH_SHA256 = ObjectIdentifier(\"1.2.840.113549.1.1.11\")\n    RSA_WITH_SHA384 = ObjectIdentifier(\"1.2.840.113549.1.1.12\")\n    RSA_WITH_SHA512 = ObjectIdentifier(\"1.2.840.113549.1.1.13\")\n    RSASSA_PSS = ObjectIdentifier(\"1.2.840.113549.1.1.10\")\n    ECDSA_WITH_SHA1 = ObjectIdentifier(\"1.2.840.10045.4.1\")\n    ECDSA_WITH_SHA224 = ObjectIdentifier(\"1.2.840.10045.4.3.1\")\n    ECDSA_WITH_SHA256 = ObjectIdentifier(\"1.2.840.10045.4.3.2\")\n    ECDSA_WITH_SHA384 = ObjectIdentifier(\"1.2.840.10045.4.3.3\")\n    ECDSA_WITH_SHA512 = ObjectIdentifier(\"1.2.840.10045.4.3.4\")\n    DSA_WITH_SHA1 = ObjectIdentifier(\"1.2.840.10040.4.3\")\n    DSA_WITH_SHA224 = ObjectIdentifier(\"2.16.840.1.101.3.4.3.1\")\n    DSA_WITH_SHA256 = ObjectIdentifier(\"2.16.840.1.101.3.4.3.2\")\n    ED25519 = ObjectIdentifier(\"1.3.101.112\")\n    ED448 = ObjectIdentifier(\"1.3.101.113\")\n\n\n_SIG_OIDS_TO_HASH = {\n    SignatureAlgorithmOID.RSA_WITH_MD5: hashes.MD5(),\n    SignatureAlgorithmOID.RSA_WITH_SHA1: hashes.SHA1(),\n    SignatureAlgorithmOID._RSA_WITH_SHA1: hashes.SHA1(),\n    SignatureAlgorithmOID.RSA_WITH_SHA224: hashes.SHA224(),\n    SignatureAlgorithmOID.RSA_WITH_SHA256: hashes.SHA256(),\n    SignatureAlgorithmOID.RSA_WITH_SHA384: hashes.SHA384(),\n    SignatureAlgorithmOID.RSA_WITH_SHA512: hashes.SHA512(),\n    SignatureAlgorithmOID.ECDSA_WITH_SHA1: hashes.SHA1(),\n    SignatureAlgorithmOID.ECDSA_WITH_SHA224: hashes.SHA224(),\n    SignatureAlgorithmOID.ECDSA_WITH_SHA256: hashes.SHA256(),\n    SignatureAlgorithmOID.ECDSA_WITH_SHA384: hashes.SHA384(),\n    SignatureAlgorithmOID.ECDSA_WITH_SHA512: hashes.SHA512(),\n    SignatureAlgorithmOID.DSA_WITH_SHA1: hashes.SHA1(),\n    SignatureAlgorithmOID.DSA_WITH_SHA224: hashes.SHA224(),\n    SignatureAlgorithmOID.DSA_WITH_SHA256: hashes.SHA256(),\n    SignatureAlgorithmOID.ED25519: None,\n    SignatureAlgorithmOID.ED448: None,\n}\n\n\nclass ExtendedKeyUsageOID(object):\n    SERVER_AUTH = ObjectIdentifier(\"1.3.6.1.5.5.7.3.1\")\n    CLIENT_AUTH = ObjectIdentifier(\"1.3.6.1.5.5.7.3.2\")\n    CODE_SIGNING = ObjectIdentifier(\"1.3.6.1.5.5.7.3.3\")\n    EMAIL_PROTECTION = ObjectIdentifier(\"1.3.6.1.5.5.7.3.4\")\n    TIME_STAMPING = ObjectIdentifier(\"1.3.6.1.5.5.7.3.8\")\n    OCSP_SIGNING = ObjectIdentifier(\"1.3.6.1.5.5.7.3.9\")\n    ANY_EXTENDED_KEY_USAGE = ObjectIdentifier(\"2.5.29.37.0\")\n\n\nclass AuthorityInformationAccessOID(object):\n    CA_ISSUERS = ObjectIdentifier(\"1.3.6.1.5.5.7.48.2\")\n    OCSP = ObjectIdentifier(\"1.3.6.1.5.5.7.48.1\")\n\n\nclass CertificatePoliciesOID(object):\n    CPS_QUALIFIER = ObjectIdentifier(\"1.3.6.1.5.5.7.2.1\")\n    CPS_USER_NOTICE = ObjectIdentifier(\"1.3.6.1.5.5.7.2.2\")\n    ANY_POLICY = ObjectIdentifier(\"2.5.29.32.0\")\n\n\n_OID_NAMES = {\n    NameOID.COMMON_NAME: \"commonName\",\n    NameOID.COUNTRY_NAME: \"countryName\",\n    NameOID.LOCALITY_NAME: \"localityName\",\n    NameOID.STATE_OR_PROVINCE_NAME: \"stateOrProvinceName\",\n    NameOID.STREET_ADDRESS: \"streetAddress\",\n    NameOID.ORGANIZATION_NAME: \"organizationName\",\n    NameOID.ORGANIZATIONAL_UNIT_NAME: \"organizationalUnitName\",\n    NameOID.SERIAL_NUMBER: \"serialNumber\",\n    NameOID.SURNAME: \"surname\",\n    NameOID.GIVEN_NAME: \"givenName\",\n    NameOID.TITLE: \"title\",\n    NameOID.GENERATION_QUALIFIER: \"generationQualifier\",\n    NameOID.X500_UNIQUE_IDENTIFIER: \"x500UniqueIdentifier\",\n    NameOID.DN_QUALIFIER: \"dnQualifier\",\n    NameOID.PSEUDONYM: \"pseudonym\",\n    NameOID.USER_ID: \"userID\",\n    NameOID.DOMAIN_COMPONENT: \"domainComponent\",\n    NameOID.EMAIL_ADDRESS: \"emailAddress\",\n    NameOID.JURISDICTION_COUNTRY_NAME: \"jurisdictionCountryName\",\n    NameOID.JURISDICTION_LOCALITY_NAME: \"jurisdictionLocalityName\",\n    NameOID.JURISDICTION_STATE_OR_PROVINCE_NAME: (\n        \"jurisdictionStateOrProvinceName\"\n    ),\n    NameOID.BUSINESS_CATEGORY: \"businessCategory\",\n    NameOID.POSTAL_ADDRESS: \"postalAddress\",\n    NameOID.POSTAL_CODE: \"postalCode\",\n\n    SignatureAlgorithmOID.RSA_WITH_MD5: \"md5WithRSAEncryption\",\n    SignatureAlgorithmOID.RSA_WITH_SHA1: \"sha1WithRSAEncryption\",\n    SignatureAlgorithmOID.RSA_WITH_SHA224: \"sha224WithRSAEncryption\",\n    SignatureAlgorithmOID.RSA_WITH_SHA256: \"sha256WithRSAEncryption\",\n    SignatureAlgorithmOID.RSA_WITH_SHA384: \"sha384WithRSAEncryption\",\n    SignatureAlgorithmOID.RSA_WITH_SHA512: \"sha512WithRSAEncryption\",\n    SignatureAlgorithmOID.RSASSA_PSS: \"RSASSA-PSS\",\n    SignatureAlgorithmOID.ECDSA_WITH_SHA1: \"ecdsa-with-SHA1\",\n    SignatureAlgorithmOID.ECDSA_WITH_SHA224: \"ecdsa-with-SHA224\",\n    SignatureAlgorithmOID.ECDSA_WITH_SHA256: \"ecdsa-with-SHA256\",\n    SignatureAlgorithmOID.ECDSA_WITH_SHA384: \"ecdsa-with-SHA384\",\n    SignatureAlgorithmOID.ECDSA_WITH_SHA512: \"ecdsa-with-SHA512\",\n    SignatureAlgorithmOID.DSA_WITH_SHA1: \"dsa-with-sha1\",\n    SignatureAlgorithmOID.DSA_WITH_SHA224: \"dsa-with-sha224\",\n    SignatureAlgorithmOID.DSA_WITH_SHA256: \"dsa-with-sha256\",\n    SignatureAlgorithmOID.ED25519: \"ed25519\",\n    SignatureAlgorithmOID.ED448: \"ed448\",\n    ExtendedKeyUsageOID.SERVER_AUTH: \"serverAuth\",\n    ExtendedKeyUsageOID.CLIENT_AUTH: \"clientAuth\",\n    ExtendedKeyUsageOID.CODE_SIGNING: \"codeSigning\",\n    ExtendedKeyUsageOID.EMAIL_PROTECTION: \"emailProtection\",\n    ExtendedKeyUsageOID.TIME_STAMPING: \"timeStamping\",\n    ExtendedKeyUsageOID.OCSP_SIGNING: \"OCSPSigning\",\n    ExtensionOID.SUBJECT_DIRECTORY_ATTRIBUTES: \"subjectDirectoryAttributes\",\n    ExtensionOID.SUBJECT_KEY_IDENTIFIER: \"subjectKeyIdentifier\",\n    ExtensionOID.KEY_USAGE: \"keyUsage\",\n    ExtensionOID.SUBJECT_ALTERNATIVE_NAME: \"subjectAltName\",\n    ExtensionOID.ISSUER_ALTERNATIVE_NAME: \"issuerAltName\",\n    ExtensionOID.BASIC_CONSTRAINTS: \"basicConstraints\",\n    ExtensionOID.PRECERT_SIGNED_CERTIFICATE_TIMESTAMPS: (\n        \"signedCertificateTimestampList\"\n    ),\n    ExtensionOID.PRECERT_POISON: \"ctPoison\",\n    CRLEntryExtensionOID.CRL_REASON: \"cRLReason\",\n    CRLEntryExtensionOID.INVALIDITY_DATE: \"invalidityDate\",\n    CRLEntryExtensionOID.CERTIFICATE_ISSUER: \"certificateIssuer\",\n    ExtensionOID.NAME_CONSTRAINTS: \"nameConstraints\",\n    ExtensionOID.CRL_DISTRIBUTION_POINTS: \"cRLDistributionPoints\",\n    ExtensionOID.CERTIFICATE_POLICIES: \"certificatePolicies\",\n    ExtensionOID.POLICY_MAPPINGS: \"policyMappings\",\n    ExtensionOID.AUTHORITY_KEY_IDENTIFIER: \"authorityKeyIdentifier\",\n    ExtensionOID.POLICY_CONSTRAINTS: \"policyConstraints\",\n    ExtensionOID.EXTENDED_KEY_USAGE: \"extendedKeyUsage\",\n    ExtensionOID.FRESHEST_CRL: \"freshestCRL\",\n    ExtensionOID.INHIBIT_ANY_POLICY: \"inhibitAnyPolicy\",\n    ExtensionOID.ISSUING_DISTRIBUTION_POINT: (\n        \"issuingDistributionPoint\"\n    ),\n    ExtensionOID.AUTHORITY_INFORMATION_ACCESS: \"authorityInfoAccess\",\n    ExtensionOID.SUBJECT_INFORMATION_ACCESS: \"subjectInfoAccess\",\n    ExtensionOID.OCSP_NO_CHECK: \"OCSPNoCheck\",\n    ExtensionOID.CRL_NUMBER: \"cRLNumber\",\n    ExtensionOID.DELTA_CRL_INDICATOR: \"deltaCRLIndicator\",\n    ExtensionOID.TLS_FEATURE: \"TLSFeature\",\n    AuthorityInformationAccessOID.OCSP: \"OCSP\",\n    AuthorityInformationAccessOID.CA_ISSUERS: \"caIssuers\",\n    CertificatePoliciesOID.CPS_QUALIFIER: \"id-qt-cps\",\n    CertificatePoliciesOID.CPS_USER_NOTICE: \"id-qt-unotice\",\n    OCSPExtensionOID.NONCE: \"OCSPNonce\",\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography-2.8.dist-info/AUTHORS.rst",
    "content": "AUTHORS\n=======\n\nPGP key fingerprints are enclosed in parentheses.\n\n* Alex Gaynor <alex.gaynor@gmail.com> (E27D 4AA0 1651 72CB C5D2  AF2B 125F 5C67 DFE9 4084)\n* Hynek Schlawack <hs@ox.cx> (C2A0 4F86 ACE2 8ADC F817 DBB7 AE25 3622 7F69 F181)\n* Donald Stufft <donald@stufft.io>\n* Laurens Van Houtven <_@lvh.io> (D9DC 4315 772F 8E91 DD22 B153 DFD1 3DF7 A8DD 569B)\n* Christian Heimes <christian@python.org>\n* Paul Kehrer <paul.l.kehrer@gmail.com> (05FD 9FA1 6CF7 5735 0D91 A560 235A E5F1 29F9 ED98)\n* Jarret Raim <jarito@gmail.com>\n* Alex Stapleton <alexs@prol.etari.at> (A1C7 E50B 66DE 39ED C847 9665 8E3C 20D1 9BD9 5C4C)\n* David Reid <dreid@dreid.org> (0F83 CC87 B32F 482B C726  B58A 9FBF D8F4 DA89 6D74)\n* Matthew Lefkowitz <glyph@twistedmatrix.com> (06AB F638 E878 CD29 1264  18AB 7EC2 8125 0FBC 4A07)\n* Konstantinos Koukopoulos <koukopoulos@gmail.com> (D6BD 52B6 8C99 A91C E2C8  934D 3300 566B 3A46 726E)\n* Stephen Holsapple <sholsapp@gmail.com>\n* Terry Chia <terrycwk1994@gmail.com>\n* Matthew Iversen <matt@notevencode.com> (2F04 3DCC D6E6 D5AC D262  2E0B C046 E8A8 7452 2973)\n* Mohammed Attia <skeuomorf@gmail.com>\n* Michael Hart <michael.hart1994@gmail.com>\n* Mark Adams <mark@markadams.me> (A18A 7DD3 283C CF2A B0CE FE0E C7A0 5E3F C972 098C)\n* Gregory Haynes <greg@greghaynes.net> (6FB6 44BF 9FD0 EBA2 1CE9  471F B08F 42F9 0DC6 599F)\n* Chelsea Winfree <chelsea.winfree@gmail.com>\n* Steven Buss <steven.buss@gmail.com> (1FB9 2EC1 CF93 DFD6 B47F F583 B1A5 6C22 290D A4C3)\n* Andre Caron <andre.l.caron@gmail.com>\n* Jiangge Zhang <tonyseek@gmail.com> (BBEC 782B 015F 71B1 5FF7  EACA 1A8C AA98 255F 5000)\n* Major Hayden <major@mhtx.net> (1BF9 9264 9596 0033 698C  252B 7370 51E0 C101 1FB1)\n* Phoebe Queen <foibey@gmail.com> (10D4 7741 AB65 50F4 B264 3888 DA40 201A 072B C1FA)\n* Google Inc.\n* Amaury Forgeot d'Arc <amauryfa@google.com>\n* Dirkjan Ochtman <dirkjan@ochtman.nl> (25BB BAC1 13C1 BFD5 AA59  4A4C 9F96 B929 3038 0381)\n* Maximilian Hils <max@maximilianhils.com>\n* Simo Sorce <simo@redhat.com>\n* Thomas Sileo <t@a4.io>\n* Fraser Tweedale <ftweedal@redhat.com>\n* Ofek Lev <ofekmeister@gmail.com> (FFB6 B92B 30B1 7848 546E 9912 972F E913 DAD5 A46E)\n* Erik Daguerre <fallenwolf@wolfthefallen.com>\n* Aviv Palivoda <palaviv@gmail.com>\n* Chris Wolfe <chriswwolfe@gmail.com>\n* Jeremy Lainé <jeremy.laine@m4x.org>\n* Denis Gladkikh <denis@gladkikh.email>\n* John Pacific <me@johnpacific.com> (2CF6 0381 B5EF 29B7 D48C 2020 7BB9 71A0 E891 44D9)\n* Marti Raudsepp <marti@juffo.org>\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography-2.8.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography-2.8.dist-info/LICENSE",
    "content": "This software is made available under the terms of *either* of the licenses\nfound in LICENSE.APACHE or LICENSE.BSD. Contributions to cryptography are made\nunder the terms of *both* these licenses.\n\nThe code used in the OpenSSL locking callback and OS random engine is derived\nfrom CPython, and is licensed under the terms of the PSF License Agreement.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography-2.8.dist-info/LICENSE.APACHE",
    "content": "\n                                 Apache License\n                           Version 2.0, January 2004\n                        https://www.apache.org/licenses/\n\n   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION\n\n   1. Definitions.\n\n      \"License\" shall mean the terms and conditions for use, reproduction,\n      and distribution as defined by Sections 1 through 9 of this document.\n\n      \"Licensor\" shall mean the copyright owner or entity authorized by\n      the copyright owner that is granting the License.\n\n      \"Legal Entity\" shall mean the union of the acting entity and all\n      other entities that control, are controlled by, or are under common\n      control with that entity. For the purposes of this definition,\n      \"control\" means (i) the power, direct or indirect, to cause the\n      direction or management of such entity, whether by contract or\n      otherwise, or (ii) ownership of fifty percent (50%) or more of the\n      outstanding shares, or (iii) beneficial ownership of such entity.\n\n      \"You\" (or \"Your\") shall mean an individual or Legal Entity\n      exercising permissions granted by this License.\n\n      \"Source\" form shall mean the preferred form for making modifications,\n      including but not limited to software source code, documentation\n      source, and configuration files.\n\n      \"Object\" form shall mean any form resulting from mechanical\n      transformation or translation of a Source form, including but\n      not limited to compiled object code, generated documentation,\n      and conversions to other media types.\n\n      \"Work\" shall mean the work of authorship, whether in Source or\n      Object form, made available under the License, as indicated by a\n      copyright notice that is included in or attached to the work\n      (an example is provided in the Appendix below).\n\n      \"Derivative Works\" shall mean any work, whether in Source or Object\n      form, that is based on (or derived from) the Work and for which the\n      editorial revisions, annotations, elaborations, or other modifications\n      represent, as a whole, an original work of authorship. For the purposes\n      of this License, Derivative Works shall not include works that remain\n      separable from, or merely link (or bind by name) to the interfaces of,\n      the Work and Derivative Works thereof.\n\n      \"Contribution\" shall mean any work of authorship, including\n      the original version of the Work and any modifications or additions\n      to that Work or Derivative Works thereof, that is intentionally\n      submitted to Licensor for inclusion in the Work by the copyright owner\n      or by an individual or Legal Entity authorized to submit on behalf of\n      the copyright owner. For the purposes of this definition, \"submitted\"\n      means any form of electronic, verbal, or written communication sent\n      to the Licensor or its representatives, including but not limited to\n      communication on electronic mailing lists, source code control systems,\n      and issue tracking systems that are managed by, or on behalf of, the\n      Licensor for the purpose of discussing and improving the Work, but\n      excluding communication that is conspicuously marked or otherwise\n      designated in writing by the copyright owner as \"Not a Contribution.\"\n\n      \"Contributor\" shall mean Licensor and any individual or Legal Entity\n      on behalf of whom a Contribution has been received by Licensor and\n      subsequently incorporated within the Work.\n\n   2. Grant of Copyright License. Subject to the terms and conditions of\n      this License, each Contributor hereby grants to You a perpetual,\n      worldwide, non-exclusive, no-charge, royalty-free, irrevocable\n      copyright license to reproduce, prepare Derivative Works of,\n      publicly display, publicly perform, sublicense, and distribute the\n      Work and such Derivative Works in Source or Object form.\n\n   3. Grant of Patent License. Subject to the terms and conditions of\n      this License, each Contributor hereby grants to You a perpetual,\n      worldwide, non-exclusive, no-charge, royalty-free, irrevocable\n      (except as stated in this section) patent license to make, have made,\n      use, offer to sell, sell, import, and otherwise transfer the Work,\n      where such license applies only to those patent claims licensable\n      by such Contributor that are necessarily infringed by their\n      Contribution(s) alone or by combination of their Contribution(s)\n      with the Work to which such Contribution(s) was submitted. If You\n      institute patent litigation against any entity (including a\n      cross-claim or counterclaim in a lawsuit) alleging that the Work\n      or a Contribution incorporated within the Work constitutes direct\n      or contributory patent infringement, then any patent licenses\n      granted to You under this License for that Work shall terminate\n      as of the date such litigation is filed.\n\n   4. Redistribution. You may reproduce and distribute copies of the\n      Work or Derivative Works thereof in any medium, with or without\n      modifications, and in Source or Object form, provided that You\n      meet the following conditions:\n\n      (a) You must give any other recipients of the Work or\n          Derivative Works a copy of this License; and\n\n      (b) You must cause any modified files to carry prominent notices\n          stating that You changed the files; and\n\n      (c) You must retain, in the Source form of any Derivative Works\n          that You distribute, all copyright, patent, trademark, and\n          attribution notices from the Source form of the Work,\n          excluding those notices that do not pertain to any part of\n          the Derivative Works; and\n\n      (d) If the Work includes a \"NOTICE\" text file as part of its\n          distribution, then any Derivative Works that You distribute must\n          include a readable copy of the attribution notices contained\n          within such NOTICE file, excluding those notices that do not\n          pertain to any part of the Derivative Works, in at least one\n          of the following places: within a NOTICE text file distributed\n          as part of the Derivative Works; within the Source form or\n          documentation, if provided along with the Derivative Works; or,\n          within a display generated by the Derivative Works, if and\n          wherever such third-party notices normally appear. The contents\n          of the NOTICE file are for informational purposes only and\n          do not modify the License. You may add Your own attribution\n          notices within Derivative Works that You distribute, alongside\n          or as an addendum to the NOTICE text from the Work, provided\n          that such additional attribution notices cannot be construed\n          as modifying the License.\n\n      You may add Your own copyright statement to Your modifications and\n      may provide additional or different license terms and conditions\n      for use, reproduction, or distribution of Your modifications, or\n      for any such Derivative Works as a whole, provided Your use,\n      reproduction, and distribution of the Work otherwise complies with\n      the conditions stated in this License.\n\n   5. Submission of Contributions. Unless You explicitly state otherwise,\n      any Contribution intentionally submitted for inclusion in the Work\n      by You to the Licensor shall be under the terms and conditions of\n      this License, without any additional terms or conditions.\n      Notwithstanding the above, nothing herein shall supersede or modify\n      the terms of any separate license agreement you may have executed\n      with Licensor regarding such Contributions.\n\n   6. Trademarks. This License does not grant permission to use the trade\n      names, trademarks, service marks, or product names of the Licensor,\n      except as required for reasonable and customary use in describing the\n      origin of the Work and reproducing the content of the NOTICE file.\n\n   7. Disclaimer of Warranty. Unless required by applicable law or\n      agreed to in writing, Licensor provides the Work (and each\n      Contributor provides its Contributions) on an \"AS IS\" BASIS,\n      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n      implied, including, without limitation, any warranties or conditions\n      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A\n      PARTICULAR PURPOSE. You are solely responsible for determining the\n      appropriateness of using or redistributing the Work and assume any\n      risks associated with Your exercise of permissions under this License.\n\n   8. Limitation of Liability. In no event and under no legal theory,\n      whether in tort (including negligence), contract, or otherwise,\n      unless required by applicable law (such as deliberate and grossly\n      negligent acts) or agreed to in writing, shall any Contributor be\n      liable to You for damages, including any direct, indirect, special,\n      incidental, or consequential damages of any character arising as a\n      result of this License or out of the use or inability to use the\n      Work (including but not limited to damages for loss of goodwill,\n      work stoppage, computer failure or malfunction, or any and all\n      other commercial damages or losses), even if such Contributor\n      has been advised of the possibility of such damages.\n\n   9. Accepting Warranty or Additional Liability. While redistributing\n      the Work or Derivative Works thereof, You may choose to offer,\n      and charge a fee for, acceptance of support, warranty, indemnity,\n      or other liability obligations and/or rights consistent with this\n      License. However, in accepting such obligations, You may act only\n      on Your own behalf and on Your sole responsibility, not on behalf\n      of any other Contributor, and only if You agree to indemnify,\n      defend, and hold each Contributor harmless for any liability\n      incurred by, or claims asserted against, such Contributor by reason\n      of your accepting any such warranty or additional liability.\n\n   END OF TERMS AND CONDITIONS\n\n   APPENDIX: How to apply the Apache License to your work.\n\n      To apply the Apache License to your work, attach the following\n      boilerplate notice, with the fields enclosed by brackets \"[]\"\n      replaced with your own identifying information. (Don't include\n      the brackets!)  The text should be enclosed in the appropriate\n      comment syntax for the file format. We also recommend that a\n      file or class name and description of purpose be included on the\n      same \"printed page\" as the copyright notice for easier\n      identification within third-party archives.\n\n   Copyright [yyyy] [name of copyright owner]\n\n   Licensed under the Apache License, Version 2.0 (the \"License\");\n   you may not use this file except in compliance with the License.\n   You may obtain a copy of the License at\n\n       https://www.apache.org/licenses/LICENSE-2.0\n\n   Unless required by applicable law or agreed to in writing, software\n   distributed under the License is distributed on an \"AS IS\" BASIS,\n   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n   See the License for the specific language governing permissions and\n   limitations under the License.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography-2.8.dist-info/LICENSE.BSD",
    "content": "Copyright (c) Individual contributors.\nAll rights reserved.\n\nRedistribution and use in source and binary forms, with or without\nmodification, are permitted provided that the following conditions are met:\n\n    1. Redistributions of source code must retain the above copyright notice,\n       this list of conditions and the following disclaimer.\n\n    2. Redistributions in binary form must reproduce the above copyright\n       notice, this list of conditions and the following disclaimer in the\n       documentation and/or other materials provided with the distribution.\n\n    3. Neither the name of PyCA Cryptography nor the names of its contributors\n       may be used to endorse or promote products derived from this software\n       without specific prior written permission.\n\nTHIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\nANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\nWARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\nDISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR\nANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\nLOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON\nANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\nSOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography-2.8.dist-info/LICENSE.PSF",
    "content": "1. This LICENSE AGREEMENT is between the Python Software Foundation (\"PSF\"), and\n   the Individual or Organization (\"Licensee\") accessing and otherwise using Python\n   2.7.12 software in source or binary form and its associated documentation.\n\n2. Subject to the terms and conditions of this License Agreement, PSF hereby\n   grants Licensee a nonexclusive, royalty-free, world-wide license to reproduce,\n   analyze, test, perform and/or display publicly, prepare derivative works,\n   distribute, and otherwise use Python 2.7.12 alone or in any derivative\n   version, provided, however, that PSF's License Agreement and PSF's notice of\n   copyright, i.e., \"Copyright © 2001-2016 Python Software Foundation; All Rights\n   Reserved\" are retained in Python 2.7.12 alone or in any derivative version\n   prepared by Licensee.\n\n3. In the event Licensee prepares a derivative work that is based on or\n   incorporates Python 2.7.12 or any part thereof, and wants to make the\n   derivative work available to others as provided herein, then Licensee hereby\n   agrees to include in any such work a brief summary of the changes made to Python\n   2.7.12.\n\n4. PSF is making Python 2.7.12 available to Licensee on an \"AS IS\" basis.\n   PSF MAKES NO REPRESENTATIONS OR WARRANTIES, EXPRESS OR IMPLIED.  BY WAY OF\n   EXAMPLE, BUT NOT LIMITATION, PSF MAKES NO AND DISCLAIMS ANY REPRESENTATION OR\n   WARRANTY OF MERCHANTABILITY OR FITNESS FOR ANY PARTICULAR PURPOSE OR THAT THE\n   USE OF PYTHON 2.7.12 WILL NOT INFRINGE ANY THIRD PARTY RIGHTS.\n\n5. PSF SHALL NOT BE LIABLE TO LICENSEE OR ANY OTHER USERS OF PYTHON 2.7.12\n   FOR ANY INCIDENTAL, SPECIAL, OR CONSEQUENTIAL DAMAGES OR LOSS AS A RESULT OF\n   MODIFYING, DISTRIBUTING, OR OTHERWISE USING PYTHON 2.7.12, OR ANY DERIVATIVE\n   THEREOF, EVEN IF ADVISED OF THE POSSIBILITY THEREOF.\n\n6. This License Agreement will automatically terminate upon a material breach of\n   its terms and conditions.\n\n7. Nothing in this License Agreement shall be deemed to create any relationship\n   of agency, partnership, or joint venture between PSF and Licensee.  This License\n   Agreement does not grant permission to use PSF trademarks or trade name in a\n   trademark sense to endorse or promote products or services of Licensee, or any\n   third party.\n\n8. By copying, installing or otherwise using Python 2.7.12, Licensee agrees\n   to be bound by the terms and conditions of this License Agreement.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography-2.8.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: cryptography\nVersion: 2.8\nSummary: cryptography is a package which provides cryptographic recipes and primitives to Python developers.\nHome-page: https://github.com/pyca/cryptography\nAuthor: The cryptography developers\nAuthor-email: cryptography-dev@python.org\nLicense: BSD or Apache License, Version 2.0\nPlatform: UNKNOWN\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: Apache Software License\nClassifier: License :: OSI Approved :: BSD License\nClassifier: Natural Language :: English\nClassifier: Operating System :: MacOS :: MacOS X\nClassifier: Operating System :: POSIX\nClassifier: Operating System :: POSIX :: BSD\nClassifier: Operating System :: POSIX :: Linux\nClassifier: Operating System :: Microsoft :: Windows\nClassifier: Programming Language :: Python\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nClassifier: Programming Language :: Python :: 3.8\nClassifier: Programming Language :: Python :: Implementation :: CPython\nClassifier: Programming Language :: Python :: Implementation :: PyPy\nClassifier: Topic :: Security :: Cryptography\nRequires-Python: >=2.7,!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*\nDescription-Content-Type: text/x-rst\nRequires-Dist: six (>=1.4.1)\nRequires-Dist: cffi (!=1.11.3,>=1.8)\nRequires-Dist: enum34 ; python_version < '3'\nRequires-Dist: ipaddress ; python_version < '3'\nProvides-Extra: docs\nRequires-Dist: sphinx (!=1.8.0,>=1.6.5) ; extra == 'docs'\nRequires-Dist: sphinx-rtd-theme ; extra == 'docs'\nProvides-Extra: docstest\nRequires-Dist: doc8 ; extra == 'docstest'\nRequires-Dist: pyenchant (>=1.6.11) ; extra == 'docstest'\nRequires-Dist: twine (>=1.12.0) ; extra == 'docstest'\nRequires-Dist: sphinxcontrib-spelling (>=4.0.1) ; extra == 'docstest'\nProvides-Extra: idna\nRequires-Dist: idna (>=2.1) ; extra == 'idna'\nProvides-Extra: pep8test\nRequires-Dist: flake8 ; extra == 'pep8test'\nRequires-Dist: flake8-import-order ; extra == 'pep8test'\nRequires-Dist: pep8-naming ; extra == 'pep8test'\nProvides-Extra: test\nRequires-Dist: pytest (!=3.9.0,!=3.9.1,!=3.9.2,>=3.6.0) ; extra == 'test'\nRequires-Dist: pretend ; extra == 'test'\nRequires-Dist: iso8601 ; extra == 'test'\nRequires-Dist: pytz ; extra == 'test'\nRequires-Dist: hypothesis (!=3.79.2,>=1.11.4) ; extra == 'test'\n\npyca/cryptography\n=================\n\n.. image:: https://img.shields.io/pypi/v/cryptography.svg\n    :target: https://pypi.org/project/cryptography/\n    :alt: Latest Version\n\n.. image:: https://readthedocs.org/projects/cryptography/badge/?version=latest\n    :target: https://cryptography.io\n    :alt: Latest Docs\n\n.. image:: https://travis-ci.org/pyca/cryptography.svg?branch=master\n    :target: https://travis-ci.org/pyca/cryptography\n\n.. image:: https://dev.azure.com/pyca/cryptography/_apis/build/status/Azure%20CI?branchName=master\n    :target: https://dev.azure.com/pyca/cryptography/_build/latest?definitionId=3&branchName=master\n\n.. image:: https://codecov.io/github/pyca/cryptography/coverage.svg?branch=master\n    :target: https://codecov.io/github/pyca/cryptography?branch=master\n\n\n``cryptography`` is a package which provides cryptographic recipes and\nprimitives to Python developers.  Our goal is for it to be your \"cryptographic\nstandard library\". It supports Python 2.7, Python 3.4+, and PyPy 5.4+.\n\n``cryptography`` includes both high level recipes and low level interfaces to\ncommon cryptographic algorithms such as symmetric ciphers, message digests, and\nkey derivation functions. For example, to encrypt something with\n``cryptography``'s high level symmetric encryption recipe:\n\n.. code-block:: pycon\n\n    >>> from cryptography.fernet import Fernet\n    >>> # Put this somewhere safe!\n    >>> key = Fernet.generate_key()\n    >>> f = Fernet(key)\n    >>> token = f.encrypt(b\"A really secret message. Not for prying eyes.\")\n    >>> token\n    '...'\n    >>> f.decrypt(token)\n    'A really secret message. Not for prying eyes.'\n\nYou can find more information in the `documentation`_.\n\nYou can install ``cryptography`` with:\n\n.. code-block:: console\n\n    $ pip install cryptography\n\nFor full details see `the installation documentation`_.\n\nDiscussion\n~~~~~~~~~~\n\nIf you run into bugs, you can file them in our `issue tracker`_.\n\nWe maintain a `cryptography-dev`_ mailing list for development discussion.\n\nYou can also join ``#cryptography-dev`` on Freenode to ask questions or get\ninvolved.\n\nSecurity\n~~~~~~~~\n\nNeed to report a security issue? Please consult our `security reporting`_\ndocumentation.\n\n\n.. _`documentation`: https://cryptography.io/\n.. _`the installation documentation`: https://cryptography.io/en/latest/installation/\n.. _`issue tracker`: https://github.com/pyca/cryptography/issues\n.. _`cryptography-dev`: https://mail.python.org/mailman/listinfo/cryptography-dev\n.. _`security reporting`: https://cryptography.io/en/latest/security/\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography-2.8.dist-info/RECORD",
    "content": "cryptography-2.8.dist-info/AUTHORS.rst,sha256=MoKTlP6yOmnLC_KXarHVQP0sItBk11dtZ7LzV0VhNB0,2475\r\ncryptography-2.8.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\ncryptography-2.8.dist-info/LICENSE,sha256=NUUrVX-rDvsegNftucTlEYuThAgq2qBR3eNCECy53o0,352\r\ncryptography-2.8.dist-info/LICENSE.APACHE,sha256=qsc7MUj20dcRHbyjIJn2jSbGRMaBOuHk8F9leaomY_4,11360\r\ncryptography-2.8.dist-info/LICENSE.BSD,sha256=YCxMdILeZHndLpeTzaJ15eY9dz2s0eymiSMqtwCPtPs,1532\r\ncryptography-2.8.dist-info/LICENSE.PSF,sha256=aT7ApmKzn5laTyUrA6YiKUVHDBtvEsoCkY5O_g32S58,2415\r\ncryptography-2.8.dist-info/METADATA,sha256=DTs0WZ8nip9kDpwx2m_l-9t0E6gBmIPs-BuE_EJOtbg,5175\r\ncryptography-2.8.dist-info/RECORD,,\r\ncryptography-2.8.dist-info/WHEEL,sha256=QMVol4obO-h_ZZLSvUyPjs3tbFnVOtWLzOTlaMWgEN8,111\r\ncryptography-2.8.dist-info/top_level.txt,sha256=QCkYQE4HJBpqIr-aBqbOZ70NlfbejKnDE6ODbNgUwwg,46\r\ncryptography/__about__.py,sha256=DfioEQ1oTJa9q9bA7yTTxFvxt_oik9bZQDZbgeU5XcE,814\r\ncryptography/__init__.py,sha256=M7mQrfCHYuk7TpEPpfYxkhc95comqxOt41xYjLa5wiA,527\r\ncryptography/__pycache__/__about__.cpython-36.pyc,,\r\ncryptography/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/__pycache__/exceptions.cpython-36.pyc,,\r\ncryptography/__pycache__/fernet.cpython-36.pyc,,\r\ncryptography/__pycache__/utils.cpython-36.pyc,,\r\ncryptography/exceptions.py,sha256=NPtDqIq1lsQ1Gb1BXkjsGIvbMrWMaKCaT8epiSgi010,1259\r\ncryptography/fernet.py,sha256=CA4iWQvPDeF9EN0IWq8xyuBBqMvcpEE17Ii8VGbi19Y,5220\r\ncryptography/hazmat/__init__.py,sha256=hEPNQw8dgjIPIn42qaLwXNRLCyTGNZeSvkQb57DPhbs,483\r\ncryptography/hazmat/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/hazmat/__pycache__/_der.cpython-36.pyc,,\r\ncryptography/hazmat/__pycache__/_oid.cpython-36.pyc,,\r\ncryptography/hazmat/_der.py,sha256=9wV7usssA-_Ikxo0h5uVEJJcY6uRbw4UhlgjLhXYsk0,5205\r\ncryptography/hazmat/_oid.py,sha256=F1RU1q8LPLrCoCxyBk_TZ5yJeFt1kYcPMqaIHu4sBRY,2178\r\ncryptography/hazmat/backends/__init__.py,sha256=92UZdmqTyQPOYA2ui17tksyjxBnTmj1XDsxDCChLvxE,496\r\ncryptography/hazmat/backends/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/hazmat/backends/__pycache__/interfaces.cpython-36.pyc,,\r\ncryptography/hazmat/backends/interfaces.py,sha256=MoNrfcaP5cpD0_wJH5v6vyGSXC8OsbAAHm4-9TZSIU0,10783\r\ncryptography/hazmat/backends/openssl/__init__.py,sha256=k4DMe228_hTuB2kY3Lwk62JdI3EmCd7VkV01zJm57ps,336\r\ncryptography/hazmat/backends/openssl/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/aead.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/backend.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/ciphers.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/cmac.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/decode_asn1.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/dh.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/dsa.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/ec.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/ed25519.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/ed448.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/encode_asn1.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/hashes.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/hmac.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/ocsp.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/poly1305.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/rsa.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/utils.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/x25519.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/x448.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/__pycache__/x509.cpython-36.pyc,,\r\ncryptography/hazmat/backends/openssl/aead.py,sha256=U0Ncw0z4-pqEWRxJu9GzZDPTvp8YBW5GHFebckaFLTs,5750\r\ncryptography/hazmat/backends/openssl/backend.py,sha256=9ZcByUpQS8kwqLKeZoKUDZGj1dwCnrnAyEJ1ng__TUc,97231\r\ncryptography/hazmat/backends/openssl/ciphers.py,sha256=glsURUBxfMqj0XYTcEosZx6oBL-FCadhIIuQA1cxmfU,9314\r\ncryptography/hazmat/backends/openssl/cmac.py,sha256=wxCHffVAEFxcn6ATMPy7HATIjWZWMoKdTXHJCgeUf48,2855\r\ncryptography/hazmat/backends/openssl/decode_asn1.py,sha256=kPsCTGczXnxkGP471kot8rw9CBFvcuyAtJX13caubDo,33303\r\ncryptography/hazmat/backends/openssl/dh.py,sha256=kXH0LXLsgo7FLNan6V5BiidS30zVkWNwaWuVZ-n6Uog,10814\r\ncryptography/hazmat/backends/openssl/dsa.py,sha256=YOFM_ml2J4q6TI5-oh8M9RPS3u2dcUWxT51Yxfpbs7o,10228\r\ncryptography/hazmat/backends/openssl/ec.py,sha256=okZ87EcaOJRGmjEUvIPqDV7Jp6xcky4oFPSN6fXbGrs,12590\r\ncryptography/hazmat/backends/openssl/ed25519.py,sha256=66dkJPZ6gvUCJSA0RPydi1-0Q2WjhiAcKwvD2R59Zzc,6081\r\ncryptography/hazmat/backends/openssl/ed448.py,sha256=2W6KwzPQXPvvkaNZWFxI_L8rIP80vhBcdZVbIzS5MmY,6045\r\ncryptography/hazmat/backends/openssl/encode_asn1.py,sha256=8XUOTdGreOYvWhiVeQtL7XVqlBpP-rnLuDrmM7bG4LQ,23593\r\ncryptography/hazmat/backends/openssl/hashes.py,sha256=_uYcKjrWzCifz9uONPFBGba7QC3o66-KzxkSNf2uI_A,3196\r\ncryptography/hazmat/backends/openssl/hmac.py,sha256=-5MsNq9-A7Is_nUjMdz0FnOpdy3MnowCWqDGGL67hyM,2998\r\ncryptography/hazmat/backends/openssl/ocsp.py,sha256=lnCm5e37lLoqI_dTgf2dv5qS-vGo8CL3MQh6ojLFBA0,13654\r\ncryptography/hazmat/backends/openssl/poly1305.py,sha256=WaQ3LyxPD2m9auySy4mzDMMoWxTT4pw_zhg55n1D6Gg,2356\r\ncryptography/hazmat/backends/openssl/rsa.py,sha256=swgjJBJfxskdLzAiUJ_jJ9lAzkn83un5Tqvi4fV8p98,18021\r\ncryptography/hazmat/backends/openssl/utils.py,sha256=LqzoMfLbO3385h-JgV8RiWQj0bvtRy76LzimRqjIT2Q,2339\r\ncryptography/hazmat/backends/openssl/x25519.py,sha256=Soo-zS0WsXp6jwJgzVWjhhosMNWbZ6QR6kC-Splwd8I,5580\r\ncryptography/hazmat/backends/openssl/x448.py,sha256=-vMoIJJ4X3HdB4LrWxxq0_xp0sDM69S6VM_P-dqie24,4526\r\ncryptography/hazmat/backends/openssl/x509.py,sha256=Jjl-sJiQvtmM9CbnRCqGs3bxeyfW-TrDsUAX0GvHqrM,20099\r\ncryptography/hazmat/bindings/__init__.py,sha256=0wGw2OF9R7fHX7NWENCmrsYigbXHU2ojgn-N4Rkjs9U,246\r\ncryptography/hazmat/bindings/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/hazmat/bindings/_constant_time.abi3.so,sha256=F5VZJgeBmqhXqtR39Uf3-T3tZUwRx0Qcwm5XZL_MoXI,30048\r\ncryptography/hazmat/bindings/_openssl.abi3.so,sha256=k2K7IN4Ao0OhMNPZY-GV3CgX0ie3f2WS3XzDZKltrSw,5627248\r\ncryptography/hazmat/bindings/_padding.abi3.so,sha256=pT7wrkBNuG7Y-gm6XSqV7pq_Ni1nadb1rJAh7QUKQNM,33520\r\ncryptography/hazmat/bindings/openssl/__init__.py,sha256=0wGw2OF9R7fHX7NWENCmrsYigbXHU2ojgn-N4Rkjs9U,246\r\ncryptography/hazmat/bindings/openssl/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/hazmat/bindings/openssl/__pycache__/_conditional.cpython-36.pyc,,\r\ncryptography/hazmat/bindings/openssl/__pycache__/binding.cpython-36.pyc,,\r\ncryptography/hazmat/bindings/openssl/_conditional.py,sha256=HXtnoHgt5jIsEjWcKQFHJ47yBAVsBfLO2XMSbffd-JE,11233\r\ncryptography/hazmat/bindings/openssl/binding.py,sha256=QCYFKaDiuYFhxK3l6Lkvr4V-PXuu26saC09AUNzUJvQ,7120\r\ncryptography/hazmat/primitives/__init__.py,sha256=0wGw2OF9R7fHX7NWENCmrsYigbXHU2ojgn-N4Rkjs9U,246\r\ncryptography/hazmat/primitives/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/__pycache__/cmac.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/__pycache__/constant_time.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/__pycache__/hashes.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/__pycache__/hmac.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/__pycache__/keywrap.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/__pycache__/padding.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/__pycache__/poly1305.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/asymmetric/__init__.py,sha256=WhUn3tGxoLAxGAsZHElJ2aOILXSh55AZi04MBudYmQA,1020\r\ncryptography/hazmat/primitives/asymmetric/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/asymmetric/__pycache__/dh.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/asymmetric/__pycache__/dsa.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/asymmetric/__pycache__/ec.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/asymmetric/__pycache__/ed25519.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/asymmetric/__pycache__/ed448.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/asymmetric/__pycache__/padding.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/asymmetric/__pycache__/rsa.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/asymmetric/__pycache__/utils.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/asymmetric/__pycache__/x25519.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/asymmetric/__pycache__/x448.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/asymmetric/dh.py,sha256=6Xl01bjTVHFCcdJr3Ph2cQ7hxkYYedqm-SekZpxnntY,5454\r\ncryptography/hazmat/primitives/asymmetric/dsa.py,sha256=uzK7qpe0BtqHkgVLSrNGtska1w3JSUN_uZp6XAA5LMY,6891\r\ncryptography/hazmat/primitives/asymmetric/ec.py,sha256=omk32C3oyISuzjH37lmzO2e95DU3qnkTPwzZAHXj4dw,13758\r\ncryptography/hazmat/primitives/asymmetric/ed25519.py,sha256=K7dGHENDEmO0kS0fqeT6dcmMRo9IbKLus26WAfDDhjM,2395\r\ncryptography/hazmat/primitives/asymmetric/ed448.py,sha256=eoRniA5yN3fgT0Vutuo-j6i1yeiKEKA_-4aErJPdl6w,2322\r\ncryptography/hazmat/primitives/asymmetric/padding.py,sha256=aCZatU5-q_WW5vazBWeKPF8ZZa0AI8hWzbJaVRN3RWI,2261\r\ncryptography/hazmat/primitives/asymmetric/rsa.py,sha256=V7MKK29BpNGF2f3uWEs3HPYbGuL3YtDFujvjFQrle0Q,10317\r\ncryptography/hazmat/primitives/asymmetric/utils.py,sha256=Og5jZxYoCE9BMb3dmquMTantjsjzl0z2mqoc9s-0588,1184\r\ncryptography/hazmat/primitives/asymmetric/x25519.py,sha256=LZ9dKxAjFdR-VE5OO0CijGUyJxiqFFynCeucTOYQUCk,2281\r\ncryptography/hazmat/primitives/asymmetric/x448.py,sha256=gbZ_UdVIozeZV7FfdpI5qp4t31nWGUXiKwfgMYrF2iY,2249\r\ncryptography/hazmat/primitives/ciphers/__init__.py,sha256=QxaxejeFfz6CPhI1c4iNq_7DsiB41Y_Q-uLfzOx7fv8,626\r\ncryptography/hazmat/primitives/ciphers/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/ciphers/__pycache__/aead.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/ciphers/__pycache__/algorithms.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/ciphers/__pycache__/base.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/ciphers/__pycache__/modes.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/ciphers/aead.py,sha256=XpXxKVAOznjEpFcPxa-sU_kJSowGjGljpp779Ob8W9g,6437\r\ncryptography/hazmat/primitives/ciphers/algorithms.py,sha256=IXGUj-SRVKyHfDdyqUkRkVdySJ5s9qjIesjFd-EIbwI,4190\r\ncryptography/hazmat/primitives/ciphers/base.py,sha256=hUe5MPVeWB-21ako6_yVGI7GBNCnROkkS53zy8oSO-o,7144\r\ncryptography/hazmat/primitives/ciphers/modes.py,sha256=nUHeQ9I0AIs30Ni2w9TcU9w-AQIpeOA6wLdfA-zkTmI,6641\r\ncryptography/hazmat/primitives/cmac.py,sha256=QgOXACkva7RUbVYvSq3ryw2RdZLOOJgt_zgyCKBmJF4,2075\r\ncryptography/hazmat/primitives/constant_time.py,sha256=TYFSRknWvKlz68rCwfdMw93w0Jy1-3B5F9PQzxH0MbI,1139\r\ncryptography/hazmat/primitives/hashes.py,sha256=hqAOjSu4l7ZOG0U7kJQn0kSHgFuI57o5nb4oTQ7vGnE,6206\r\ncryptography/hazmat/primitives/hmac.py,sha256=MGsVrE_ghlZW0HUH70seV4vCWlIZNSUgB0v9n05vcGg,2196\r\ncryptography/hazmat/primitives/kdf/__init__.py,sha256=nod5HjPswjZr8wFp6Tsu6en9blHYF3khgXI5R0zIcnM,771\r\ncryptography/hazmat/primitives/kdf/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/kdf/__pycache__/concatkdf.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/kdf/__pycache__/hkdf.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/kdf/__pycache__/kbkdf.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/kdf/__pycache__/pbkdf2.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/kdf/__pycache__/scrypt.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/kdf/__pycache__/x963kdf.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/kdf/concatkdf.py,sha256=MSb4abF8jrICg1v9NSr0QQMfQ1r23RDoUkU0X8rQrhE,3981\r\ncryptography/hazmat/primitives/kdf/hkdf.py,sha256=lcqU0pI3HFKUC9L5LpO4gxPSRsES-x1lePDfryu5U4w,3463\r\ncryptography/hazmat/primitives/kdf/kbkdf.py,sha256=EWeLFPINGl50hkSJj3z62WwePpzRiqGMo1nKm7at1_g,4905\r\ncryptography/hazmat/primitives/kdf/pbkdf2.py,sha256=EK3xDD-Y29DLJulQjHraWrwX7psqCWs7NwSTto4YRxs,2088\r\ncryptography/hazmat/primitives/kdf/scrypt.py,sha256=2BrGwbyk3VvY4szQY2EBvZMaf8AYPWlX84aSj-TXLXk,2155\r\ncryptography/hazmat/primitives/kdf/x963kdf.py,sha256=YL88ILo4eBYP_LhlJcEgKnMqputkOmB-FBCsy6KZ2RA,2280\r\ncryptography/hazmat/primitives/keywrap.py,sha256=LqjkVIs7ub5I5gwmYSb9Ia0VdXMqWWHmnKSdQ7HOGEA,5462\r\ncryptography/hazmat/primitives/padding.py,sha256=CtKBj2nR50m4ZXFAonOxDcymW8Jkj0A9xxt7EMLbpJY,5644\r\ncryptography/hazmat/primitives/poly1305.py,sha256=n7CbIXH3F3HwDsXIaaHJGC-RsSPUuLZG1MJeb1FqBv8,1668\r\ncryptography/hazmat/primitives/serialization/__init__.py,sha256=R-4wUb_UMp3Wh_tWn8nIBJXWVR7Oo0ZRhgm1wEPCMjE,1046\r\ncryptography/hazmat/primitives/serialization/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/serialization/__pycache__/base.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/serialization/__pycache__/pkcs12.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/serialization/__pycache__/ssh.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/serialization/base.py,sha256=CY8d3TjQ2wPotHpQpkZ-kyVkAwW95y6TFw0JN9KpbFM,1904\r\ncryptography/hazmat/primitives/serialization/pkcs12.py,sha256=LWIA6SVMxc4nnAtSivs8rTpwG6Fy3ppSfHRDiJGdJUw,377\r\ncryptography/hazmat/primitives/serialization/ssh.py,sha256=U94cOHI42BlgiqRXDlsPoqUa5C_Ww_uuu2Njr93d1fA,4381\r\ncryptography/hazmat/primitives/twofactor/__init__.py,sha256=BWrm3DKDoAa281E7U_nzz8v44OmAiXmlIycFcsehwfE,288\r\ncryptography/hazmat/primitives/twofactor/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/twofactor/__pycache__/hotp.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/twofactor/__pycache__/totp.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/twofactor/__pycache__/utils.cpython-36.pyc,,\r\ncryptography/hazmat/primitives/twofactor/hotp.py,sha256=6_EnKl-zRs0yCXuHxQhs2TEkHaprWxZnfJGrQjs5RIg,2589\r\ncryptography/hazmat/primitives/twofactor/totp.py,sha256=KL3A4bjpqaqynQYd9hfPVkvs5vYVqf1JVpucEX7_ddM,1594\r\ncryptography/hazmat/primitives/twofactor/utils.py,sha256=71gX1bJeP9TQa-HbSPzeUUJwVY78ALYQNvuusknUO4U,954\r\ncryptography/utils.py,sha256=2ml4dp8EPZ-1SNwmqy5vVVFhMWTeHVvHoDJo9QswlPc,5010\r\ncryptography/x509/__init__.py,sha256=F01ZMHaefgsvMeSthFQEa1gz_q7553LMa_IqOq8tD7w,7305\r\ncryptography/x509/__pycache__/__init__.cpython-36.pyc,,\r\ncryptography/x509/__pycache__/base.cpython-36.pyc,,\r\ncryptography/x509/__pycache__/certificate_transparency.cpython-36.pyc,,\r\ncryptography/x509/__pycache__/extensions.cpython-36.pyc,,\r\ncryptography/x509/__pycache__/general_name.cpython-36.pyc,,\r\ncryptography/x509/__pycache__/name.cpython-36.pyc,,\r\ncryptography/x509/__pycache__/ocsp.cpython-36.pyc,,\r\ncryptography/x509/__pycache__/oid.cpython-36.pyc,,\r\ncryptography/x509/base.py,sha256=HlnDQMCpOqZu_ARcysk6zjUNulMPP7nuQz57L8bW-HM,23939\r\ncryptography/x509/certificate_transparency.py,sha256=eJ9lrITdyMn4XsrcVdrTaFVI_RR7mX_VzMZyiaEpbps,1000\r\ncryptography/x509/extensions.py,sha256=T_Xo0Rugk4xZUwDVTtEaci7y2MDHeBXf5jXT3fB_8PU,50781\r\ncryptography/x509/general_name.py,sha256=cwcI1Yez1K9OEdG0wukDWGfS_b6xN21eHOyPaCqjrGY,10462\r\ncryptography/x509/name.py,sha256=f4lg9Ej5izBMHm2sv5OeviQpzmvjSA3951PMGWUF7ac,8131\r\ncryptography/x509/ocsp.py,sha256=_Tbb3M2qe65r2MYlsjXH_vjLwDvaAZZ7-Y5GAXwuqxY,13310\r\ncryptography/x509/oid.py,sha256=iN1TLtCuI1j-WebvLeQM_yni-Uu90nYOglGJAXCCYao,10936\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography-2.8.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.33.6)\nRoot-Is-Purelib: false\nTag: cp34-abi3-manylinux2010_x86_64\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cryptography-2.8.dist-info/top_level.txt",
    "content": "_constant_time\n_openssl\n_padding\ncryptography\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cssselect/__init__.py",
    "content": "# -*- coding: utf-8 -*-\n\"\"\"\n    CSS Selectors based on XPath\n    ============================\n\n    This module supports selecting XML/HTML elements based on CSS selectors.\n    See the `CSSSelector` class for details.\n\n\n    :copyright: (c) 2007-2012 Ian Bicking and contributors.\n                See AUTHORS for more details.\n    :license: BSD, see LICENSE for more details.\n\n\"\"\"\n\nfrom cssselect.parser import (parse, Selector, FunctionalPseudoElement,\n                              SelectorError, SelectorSyntaxError)\nfrom cssselect.xpath import GenericTranslator, HTMLTranslator, ExpressionError\n\n\nVERSION = '1.1.0'\n__version__ = VERSION\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cssselect/parser.py",
    "content": "# -*- coding: utf-8 -*-\n\"\"\"\n    cssselect.parser\n    ================\n\n    Tokenizer, parser and parsed objects for CSS selectors.\n\n\n    :copyright: (c) 2007-2012 Ian Bicking and contributors.\n                See AUTHORS for more details.\n    :license: BSD, see LICENSE for more details.\n\n\"\"\"\n\nimport sys\nimport re\nimport operator\n\n\nif sys.version_info[0] < 3:\n    _unicode = unicode\n    _unichr = unichr\nelse:\n    _unicode = str\n    _unichr = chr\n\n\ndef ascii_lower(string):\n    \"\"\"Lower-case, but only in the ASCII range.\"\"\"\n    return string.encode('utf8').lower().decode('utf8')\n\n\nclass SelectorError(Exception):\n    \"\"\"Common parent for :class:`SelectorSyntaxError` and\n    :class:`ExpressionError`.\n\n    You can just use ``except SelectorError:`` when calling\n    :meth:`~GenericTranslator.css_to_xpath` and handle both exceptions types.\n\n    \"\"\"\n\nclass SelectorSyntaxError(SelectorError, SyntaxError):\n    \"\"\"Parsing a selector that does not match the grammar.\"\"\"\n\n\n#### Parsed objects\n\nclass Selector(object):\n    \"\"\"\n    Represents a parsed selector.\n\n    :meth:`~GenericTranslator.selector_to_xpath` accepts this object,\n    but ignores :attr:`pseudo_element`. It is the user’s responsibility\n    to account for pseudo-elements and reject selectors with unknown\n    or unsupported pseudo-elements.\n\n    \"\"\"\n    def __init__(self, tree, pseudo_element=None):\n        self.parsed_tree = tree\n        if pseudo_element is not None and not isinstance(\n                pseudo_element, FunctionalPseudoElement):\n            pseudo_element = ascii_lower(pseudo_element)\n        #: A :class:`FunctionalPseudoElement`,\n        #: or the identifier for the pseudo-element as a string,\n        #  or ``None``.\n        #:\n        #: +-------------------------+----------------+--------------------------------+\n        #: |                         | Selector       | Pseudo-element                 |\n        #: +=========================+================+================================+\n        #: | CSS3 syntax             | ``a::before``  | ``'before'``                   |\n        #: +-------------------------+----------------+--------------------------------+\n        #: | Older syntax            | ``a:before``   | ``'before'``                   |\n        #: +-------------------------+----------------+--------------------------------+\n        #: | From the Lists3_ draft, | ``li::marker`` | ``'marker'``                   |\n        #: | not in Selectors3       |                |                                |\n        #: +-------------------------+----------------+--------------------------------+\n        #: | Invalid pseudo-class    | ``li:marker``  | ``None``                       |\n        #: +-------------------------+----------------+--------------------------------+\n        #: | Functional              | ``a::foo(2)``  | ``FunctionalPseudoElement(…)`` |\n        #: +-------------------------+----------------+--------------------------------+\n        #:\n        #: .. _Lists3: http://www.w3.org/TR/2011/WD-css3-lists-20110524/#marker-pseudoelement\n        self.pseudo_element = pseudo_element\n\n    def __repr__(self):\n        if isinstance(self.pseudo_element, FunctionalPseudoElement):\n            pseudo_element = repr(self.pseudo_element)\n        elif self.pseudo_element:\n            pseudo_element = '::%s' % self.pseudo_element\n        else:\n            pseudo_element = ''\n        return '%s[%r%s]' % (\n            self.__class__.__name__, self.parsed_tree, pseudo_element)\n\n    def canonical(self):\n        \"\"\"Return a CSS representation for this selector (a string)\n        \"\"\"\n        if isinstance(self.pseudo_element, FunctionalPseudoElement):\n            pseudo_element = '::%s' % self.pseudo_element.canonical()\n        elif self.pseudo_element:\n            pseudo_element = '::%s' % self.pseudo_element\n        else:\n            pseudo_element = ''\n        res = '%s%s' % (self.parsed_tree.canonical(), pseudo_element)\n        if len(res) > 1:\n            res = res.lstrip('*')\n        return res\n\n    def specificity(self):\n        \"\"\"Return the specificity_ of this selector as a tuple of 3 integers.\n\n        .. _specificity: http://www.w3.org/TR/selectors/#specificity\n\n        \"\"\"\n        a, b, c = self.parsed_tree.specificity()\n        if self.pseudo_element:\n            c += 1\n        return a, b, c\n\n\nclass Class(object):\n    \"\"\"\n    Represents selector.class_name\n    \"\"\"\n    def __init__(self, selector, class_name):\n        self.selector = selector\n        self.class_name = class_name\n\n    def __repr__(self):\n        return '%s[%r.%s]' % (\n            self.__class__.__name__, self.selector, self.class_name)\n\n    def canonical(self):\n        return '%s.%s' % (self.selector.canonical(), self.class_name)\n\n    def specificity(self):\n        a, b, c = self.selector.specificity()\n        b += 1\n        return a, b, c\n\n\nclass FunctionalPseudoElement(object):\n    \"\"\"\n    Represents selector::name(arguments)\n\n    .. attribute:: name\n\n        The name (identifier) of the pseudo-element, as a string.\n\n    .. attribute:: arguments\n\n        The arguments of the pseudo-element, as a list of tokens.\n\n        **Note:** tokens are not part of the public API,\n        and may change between cssselect versions.\n        Use at your own risks.\n\n    \"\"\"\n    def __init__(self, name, arguments):\n        self.name = ascii_lower(name)\n        self.arguments = arguments\n\n    def __repr__(self):\n        return '%s[::%s(%r)]' % (\n            self.__class__.__name__, self.name,\n            [token.value for token in self.arguments])\n\n    def argument_types(self):\n        return [token.type for token in self.arguments]\n\n    def canonical(self):\n        args = ''.join(token.css() for token in self.arguments)\n        return '%s(%s)' % (self.name, args)\n\n    def specificity(self):\n        a, b, c = self.selector.specificity()\n        b += 1\n        return a, b, c\n\n\nclass Function(object):\n    \"\"\"\n    Represents selector:name(expr)\n    \"\"\"\n    def __init__(self, selector, name, arguments):\n        self.selector = selector\n        self.name = ascii_lower(name)\n        self.arguments = arguments\n\n    def __repr__(self):\n        return '%s[%r:%s(%r)]' % (\n            self.__class__.__name__, self.selector, self.name,\n            [token.value for token in self.arguments])\n\n    def argument_types(self):\n        return [token.type for token in self.arguments]\n\n    def canonical(self):\n        args = ''.join(token.css() for token in self.arguments)\n        return '%s:%s(%s)' % (self.selector.canonical(), self.name, args)\n\n    def specificity(self):\n        a, b, c = self.selector.specificity()\n        b += 1\n        return a, b, c\n\n\nclass Pseudo(object):\n    \"\"\"\n    Represents selector:ident\n    \"\"\"\n    def __init__(self, selector, ident):\n        self.selector = selector\n        self.ident = ascii_lower(ident)\n\n    def __repr__(self):\n        return '%s[%r:%s]' % (\n            self.__class__.__name__, self.selector, self.ident)\n\n    def canonical(self):\n        return '%s:%s' % (self.selector.canonical(), self.ident)\n\n    def specificity(self):\n        a, b, c = self.selector.specificity()\n        b += 1\n        return a, b, c\n\n\nclass Negation(object):\n    \"\"\"\n    Represents selector:not(subselector)\n    \"\"\"\n    def __init__(self, selector, subselector):\n        self.selector = selector\n        self.subselector = subselector\n\n    def __repr__(self):\n        return '%s[%r:not(%r)]' % (\n            self.__class__.__name__, self.selector, self.subselector)\n\n    def canonical(self):\n        subsel = self.subselector.canonical()\n        if len(subsel) > 1:\n            subsel = subsel.lstrip('*')\n        return '%s:not(%s)' % (self.selector.canonical(), subsel)\n\n    def specificity(self):\n        a1, b1, c1 = self.selector.specificity()\n        a2, b2, c2 = self.subselector.specificity()\n        return a1 + a2, b1 + b2, c1 + c2\n\n\nclass Attrib(object):\n    \"\"\"\n    Represents selector[namespace|attrib operator value]\n    \"\"\"\n    def __init__(self, selector, namespace, attrib, operator, value):\n        self.selector = selector\n        self.namespace = namespace\n        self.attrib = attrib\n        self.operator = operator\n        self.value = value\n\n    def __repr__(self):\n        if self.namespace:\n            attrib = '%s|%s' % (self.namespace, self.attrib)\n        else:\n            attrib = self.attrib\n        if self.operator == 'exists':\n            return '%s[%r[%s]]' % (\n                self.__class__.__name__, self.selector, attrib)\n        else:\n            return '%s[%r[%s %s %r]]' % (\n                self.__class__.__name__, self.selector, attrib,\n                self.operator, self.value.value)\n\n    def canonical(self):\n        if self.namespace:\n            attrib = '%s|%s' % (self.namespace, self.attrib)\n        else:\n            attrib = self.attrib\n\n        if self.operator == 'exists':\n            op = attrib\n        else:\n            op = '%s%s%s' % (attrib, self.operator, self.value.css())\n\n        return '%s[%s]' % (self.selector.canonical(), op)\n\n    def specificity(self):\n        a, b, c = self.selector.specificity()\n        b += 1\n        return a, b, c\n\n\nclass Element(object):\n    \"\"\"\n    Represents namespace|element\n\n    `None` is for the universal selector '*'\n\n    \"\"\"\n    def __init__(self, namespace=None, element=None):\n        self.namespace = namespace\n        self.element = element\n\n    def __repr__(self):\n        return '%s[%s]' % (self.__class__.__name__, self.canonical())\n\n    def canonical(self):\n        element = self.element or '*'\n        if self.namespace:\n            element = '%s|%s' % (self.namespace, element)\n        return element\n\n    def specificity(self):\n        if self.element:\n            return 0, 0, 1\n        else:\n            return 0, 0, 0\n\n\nclass Hash(object):\n    \"\"\"\n    Represents selector#id\n    \"\"\"\n    def __init__(self, selector, id):\n        self.selector = selector\n        self.id = id\n\n    def __repr__(self):\n        return '%s[%r#%s]' % (\n            self.__class__.__name__, self.selector, self.id)\n\n    def canonical(self):\n        return '%s#%s' % (self.selector.canonical(), self.id)\n\n    def specificity(self):\n        a, b, c = self.selector.specificity()\n        a += 1\n        return a, b, c\n\n\nclass CombinedSelector(object):\n    def __init__(self, selector, combinator, subselector):\n        assert selector is not None\n        self.selector = selector\n        self.combinator = combinator\n        self.subselector = subselector\n\n    def __repr__(self):\n        if self.combinator == ' ':\n            comb = '<followed>'\n        else:\n            comb = self.combinator\n        return '%s[%r %s %r]' % (\n            self.__class__.__name__, self.selector, comb, self.subselector)\n\n    def canonical(self):\n        subsel = self.subselector.canonical()\n        if len(subsel) > 1:\n            subsel = subsel.lstrip('*')\n        return '%s %s %s' % (\n            self.selector.canonical(), self.combinator, subsel)\n\n    def specificity(self):\n        a1, b1, c1 = self.selector.specificity()\n        a2, b2, c2 = self.subselector.specificity()\n        return a1 + a2, b1 + b2, c1 + c2\n\n\n#### Parser\n\n# foo\n_el_re = re.compile(r'^[ \\t\\r\\n\\f]*([a-zA-Z]+)[ \\t\\r\\n\\f]*$')\n\n# foo#bar or #bar\n_id_re = re.compile(r'^[ \\t\\r\\n\\f]*([a-zA-Z]*)#([a-zA-Z0-9_-]+)[ \\t\\r\\n\\f]*$')\n\n# foo.bar or .bar\n_class_re = re.compile(\n    r'^[ \\t\\r\\n\\f]*([a-zA-Z]*)\\.([a-zA-Z][a-zA-Z0-9_-]*)[ \\t\\r\\n\\f]*$')\n\n\ndef parse(css):\n    \"\"\"Parse a CSS *group of selectors*.\n\n    If you don't care about pseudo-elements or selector specificity,\n    you can skip this and use :meth:`~GenericTranslator.css_to_xpath`.\n\n    :param css:\n        A *group of selectors* as an Unicode string.\n    :raises:\n        :class:`SelectorSyntaxError` on invalid selectors.\n    :returns:\n        A list of parsed :class:`Selector` objects, one for each\n        selector in the comma-separated group.\n\n    \"\"\"\n    # Fast path for simple cases\n    match = _el_re.match(css)\n    if match:\n        return [Selector(Element(element=match.group(1)))]\n    match = _id_re.match(css)\n    if match is not None:\n        return [Selector(Hash(Element(element=match.group(1) or None),\n                              match.group(2)))]\n    match = _class_re.match(css)\n    if match is not None:\n        return [Selector(Class(Element(element=match.group(1) or None),\n                               match.group(2)))]\n\n    stream = TokenStream(tokenize(css))\n    stream.source = css\n    return list(parse_selector_group(stream))\n#    except SelectorSyntaxError:\n#        e = sys.exc_info()[1]\n#        message = \"%s at %s -> %r\" % (\n#            e, stream.used, stream.peek())\n#        e.msg = message\n#        e.args = tuple([message])\n#        raise\n\n\ndef parse_selector_group(stream):\n    stream.skip_whitespace()\n    while 1:\n        yield Selector(*parse_selector(stream))\n        if stream.peek() == ('DELIM', ','):\n            stream.next()\n            stream.skip_whitespace()\n        else:\n            break\n\ndef parse_selector(stream):\n    result, pseudo_element = parse_simple_selector(stream)\n    while 1:\n        stream.skip_whitespace()\n        peek = stream.peek()\n        if peek in (('EOF', None), ('DELIM', ',')):\n            break\n        if pseudo_element:\n            raise SelectorSyntaxError(\n                'Got pseudo-element ::%s not at the end of a selector'\n                % pseudo_element)\n        if peek.is_delim('+', '>', '~'):\n            # A combinator\n            combinator = stream.next().value\n            stream.skip_whitespace()\n        else:\n            # By exclusion, the last parse_simple_selector() ended\n            # at peek == ' '\n            combinator = ' '\n        next_selector, pseudo_element = parse_simple_selector(stream)\n        result = CombinedSelector(result, combinator, next_selector)\n    return result, pseudo_element\n\n\ndef parse_simple_selector(stream, inside_negation=False):\n    stream.skip_whitespace()\n    selector_start = len(stream.used)\n    peek = stream.peek()\n    if peek.type == 'IDENT' or peek == ('DELIM', '*'):\n        if peek.type == 'IDENT':\n            namespace = stream.next().value\n        else:\n            stream.next()\n            namespace = None\n        if stream.peek() == ('DELIM', '|'):\n            stream.next()\n            element = stream.next_ident_or_star()\n        else:\n            element = namespace\n            namespace = None\n    else:\n        element = namespace = None\n    result = Element(namespace, element)\n    pseudo_element = None\n    while 1:\n        peek = stream.peek()\n        if peek.type in ('S', 'EOF') or peek.is_delim(',', '+', '>', '~') or (\n                inside_negation and peek == ('DELIM', ')')):\n            break\n        if pseudo_element:\n            raise SelectorSyntaxError(\n                'Got pseudo-element ::%s not at the end of a selector'\n                % pseudo_element)\n        if peek.type == 'HASH':\n            result = Hash(result, stream.next().value)\n        elif peek == ('DELIM', '.'):\n            stream.next()\n            result = Class(result, stream.next_ident())\n        elif peek == ('DELIM', '|'):\n            stream.next()\n            result = Element(None, stream.next_ident())\n        elif peek == ('DELIM', '['):\n            stream.next()\n            result = parse_attrib(result, stream)\n        elif peek == ('DELIM', ':'):\n            stream.next()\n            if stream.peek() == ('DELIM', ':'):\n                stream.next()\n                pseudo_element = stream.next_ident()\n                if stream.peek() == ('DELIM', '('):\n                    stream.next()\n                    pseudo_element = FunctionalPseudoElement(\n                        pseudo_element, parse_arguments(stream))\n                continue\n            ident = stream.next_ident()\n            if ident.lower() in ('first-line', 'first-letter',\n                                 'before', 'after'):\n                # Special case: CSS 2.1 pseudo-elements can have a single ':'\n                # Any new pseudo-element must have two.\n                pseudo_element = _unicode(ident)\n                continue\n            if stream.peek() != ('DELIM', '('):\n                result = Pseudo(result, ident)\n                if result.__repr__() == 'Pseudo[Element[*]:scope]':\n                    if not (len(stream.used) == 2 or\n                            (len(stream.used) == 3\n                             and stream.used[0].type == 'S')):\n                        raise SelectorSyntaxError(\n                            'Got immediate child pseudo-element \":scope\" '\n                            'not at the start of a selector')\n                continue\n            stream.next()\n            stream.skip_whitespace()\n            if ident.lower() == 'not':\n                if inside_negation:\n                    raise SelectorSyntaxError('Got nested :not()')\n                argument, argument_pseudo_element = parse_simple_selector(\n                    stream, inside_negation=True)\n                next = stream.next()\n                if argument_pseudo_element:\n                    raise SelectorSyntaxError(\n                        'Got pseudo-element ::%s inside :not() at %s'\n                        % (argument_pseudo_element, next.pos))\n                if next != ('DELIM', ')'):\n                    raise SelectorSyntaxError(\"Expected ')', got %s\" % (next,))\n                result = Negation(result, argument)\n            else:\n                result = Function(result, ident, parse_arguments(stream))\n        else:\n            raise SelectorSyntaxError(\n                \"Expected selector, got %s\" % (peek,))\n    if len(stream.used) == selector_start:\n        raise SelectorSyntaxError(\n            \"Expected selector, got %s\" % (stream.peek(),))\n    return result, pseudo_element\n\n\ndef parse_arguments(stream):\n    arguments = []\n    while 1:\n        stream.skip_whitespace()\n        next = stream.next()\n        if next.type in ('IDENT', 'STRING', 'NUMBER') or next in [\n                ('DELIM', '+'), ('DELIM', '-')]:\n            arguments.append(next)\n        elif next == ('DELIM', ')'):\n            return arguments\n        else:\n            raise SelectorSyntaxError(\n                \"Expected an argument, got %s\" % (next,))\n\n\ndef parse_attrib(selector, stream):\n    stream.skip_whitespace()\n    attrib = stream.next_ident_or_star()\n    if attrib is None and stream.peek() != ('DELIM', '|'):\n        raise SelectorSyntaxError(\n            \"Expected '|', got %s\" % (stream.peek(),))\n    if stream.peek() == ('DELIM', '|'):\n        stream.next()\n        if stream.peek() == ('DELIM', '='):\n            namespace = None\n            stream.next()\n            op = '|='\n        else:\n            namespace = attrib\n            attrib = stream.next_ident()\n            op = None\n    else:\n        namespace = op = None\n    if op is None:\n        stream.skip_whitespace()\n        next = stream.next()\n        if next == ('DELIM', ']'):\n            return Attrib(selector, namespace, attrib, 'exists', None)\n        elif next == ('DELIM', '='):\n            op = '='\n        elif next.is_delim('^', '$', '*', '~', '|', '!') and (\n                stream.peek() == ('DELIM', '=')):\n            op = next.value + '='\n            stream.next()\n        else:\n            raise SelectorSyntaxError(\n                \"Operator expected, got %s\" % (next,))\n    stream.skip_whitespace()\n    value = stream.next()\n    if value.type not in ('IDENT', 'STRING'):\n        raise SelectorSyntaxError(\n            \"Expected string or ident, got %s\" % (value,))\n    stream.skip_whitespace()\n    next = stream.next()\n    if next != ('DELIM', ']'):\n        raise SelectorSyntaxError(\n            \"Expected ']', got %s\" % (next,))\n    return Attrib(selector, namespace, attrib, op, value)\n\n\ndef parse_series(tokens):\n    \"\"\"\n    Parses the arguments for :nth-child() and friends.\n\n    :raises: A list of tokens\n    :returns: :``(a, b)``\n\n    \"\"\"\n    for token in tokens:\n        if token.type == 'STRING':\n            raise ValueError('String tokens not allowed in series.')\n    s = ''.join(token.value for token in tokens).strip()\n    if s == 'odd':\n        return 2, 1\n    elif s == 'even':\n        return 2, 0\n    elif s == 'n':\n        return 1, 0\n    if 'n' not in s:\n        # Just b\n        return 0, int(s)\n    a, b = s.split('n', 1)\n    if not a:\n        a = 1\n    elif a == '-' or a == '+':\n        a = int(a+'1')\n    else:\n        a = int(a)\n    if not b:\n        b = 0\n    else:\n        b = int(b)\n    return a, b\n\n\n#### Token objects\n\nclass Token(tuple):\n    def __new__(cls, type_, value, pos):\n        obj = tuple.__new__(cls, (type_, value))\n        obj.pos = pos\n        return obj\n\n    def __repr__(self):\n        return \"<%s '%s' at %i>\" % (self.type, self.value, self.pos)\n\n    def is_delim(self, *values):\n        return self.type == 'DELIM' and self.value in values\n\n    type = property(operator.itemgetter(0))\n    value = property(operator.itemgetter(1))\n\n    def css(self):\n        if self.type == 'STRING':\n            return repr(self.value)\n        else:\n            return self.value\n\n\nclass EOFToken(Token):\n    def __new__(cls, pos):\n        return Token.__new__(cls, 'EOF', None, pos)\n\n    def __repr__(self):\n        return '<%s at %i>' % (self.type, self.pos)\n\n\n#### Tokenizer\n\n\nclass TokenMacros:\n    unicode_escape = r'\\\\([0-9a-f]{1,6})(?:\\r\\n|[ \\n\\r\\t\\f])?'\n    escape = unicode_escape + r'|\\\\[^\\n\\r\\f0-9a-f]'\n    string_escape = r'\\\\(?:\\n|\\r\\n|\\r|\\f)|' + escape\n    nonascii = r'[^\\0-\\177]'\n    nmchar = '[_a-z0-9-]|%s|%s' % (escape, nonascii)\n    nmstart = '[_a-z]|%s|%s' % (escape, nonascii)\n\ndef _compile(pattern):\n    return re.compile(pattern % vars(TokenMacros), re.IGNORECASE).match\n\n_match_whitespace = _compile(r'[ \\t\\r\\n\\f]+')\n_match_number = _compile(r'[+-]?(?:[0-9]*\\.[0-9]+|[0-9]+)')\n_match_hash = _compile('#(?:%(nmchar)s)+')\n_match_ident = _compile('-?(?:%(nmstart)s)(?:%(nmchar)s)*')\n_match_string_by_quote = {\n    \"'\": _compile(r\"([^\\n\\r\\f\\\\']|%(string_escape)s)*\"),\n    '\"': _compile(r'([^\\n\\r\\f\\\\\"]|%(string_escape)s)*'),\n}\n\n_sub_simple_escape = re.compile(r'\\\\(.)').sub\n_sub_unicode_escape = re.compile(TokenMacros.unicode_escape, re.I).sub\n_sub_newline_escape =re.compile(r'\\\\(?:\\n|\\r\\n|\\r|\\f)').sub\n\n# Same as r'\\1', but faster on CPython\n_replace_simple = operator.methodcaller('group', 1)\n\ndef _replace_unicode(match):\n    codepoint = int(match.group(1), 16)\n    if codepoint > sys.maxunicode:\n        codepoint = 0xFFFD\n    return _unichr(codepoint)\n\n\ndef unescape_ident(value):\n    value = _sub_unicode_escape(_replace_unicode, value)\n    value = _sub_simple_escape(_replace_simple, value)\n    return value\n\n\ndef tokenize(s):\n    pos = 0\n    len_s = len(s)\n    while pos < len_s:\n        match = _match_whitespace(s, pos=pos)\n        if match:\n            yield Token('S', ' ', pos)\n            pos = match.end()\n            continue\n\n        match = _match_ident(s, pos=pos)\n        if match:\n            value = _sub_simple_escape(_replace_simple,\n                    _sub_unicode_escape(_replace_unicode, match.group()))\n            yield Token('IDENT', value, pos)\n            pos = match.end()\n            continue\n\n        match = _match_hash(s, pos=pos)\n        if match:\n            value = _sub_simple_escape(_replace_simple,\n                    _sub_unicode_escape(_replace_unicode, match.group()[1:]))\n            yield Token('HASH', value, pos)\n            pos = match.end()\n            continue\n\n        quote = s[pos]\n        if quote in _match_string_by_quote:\n            match = _match_string_by_quote[quote](s, pos=pos + 1)\n            assert match, 'Should have found at least an empty match'\n            end_pos = match.end()\n            if end_pos == len_s:\n                raise SelectorSyntaxError('Unclosed string at %s' % pos)\n            if s[end_pos] != quote:\n                raise SelectorSyntaxError('Invalid string at %s' % pos)\n            value = _sub_simple_escape(_replace_simple,\n                    _sub_unicode_escape(_replace_unicode,\n                    _sub_newline_escape('', match.group())))\n            yield Token('STRING', value, pos)\n            pos = end_pos + 1\n            continue\n\n        match = _match_number(s, pos=pos)\n        if match:\n            value = match.group()\n            yield Token('NUMBER', value, pos)\n            pos = match.end()\n            continue\n\n        pos2 = pos + 2\n        if s[pos:pos2] == '/*':\n            pos = s.find('*/', pos2)\n            if pos == -1:\n                pos = len_s\n            else:\n                pos += 2\n            continue\n\n        yield Token('DELIM', s[pos], pos)\n        pos += 1\n\n    assert pos == len_s\n    yield EOFToken(pos)\n\n\nclass TokenStream(object):\n    def __init__(self, tokens, source=None):\n        self.used = []\n        self.tokens = iter(tokens)\n        self.source = source\n        self.peeked = None\n        self._peeking = False\n        try:\n            self.next_token = self.tokens.next\n        except AttributeError:\n            # Python 3\n            self.next_token = self.tokens.__next__\n\n    def next(self):\n        if self._peeking:\n            self._peeking = False\n            self.used.append(self.peeked)\n            return self.peeked\n        else:\n            next = self.next_token()\n            self.used.append(next)\n            return next\n\n    def peek(self):\n        if not self._peeking:\n            self.peeked = self.next_token()\n            self._peeking = True\n        return self.peeked\n\n    def next_ident(self):\n        next = self.next()\n        if next.type != 'IDENT':\n            raise SelectorSyntaxError('Expected ident, got %s' % (next,))\n        return next.value\n\n    def next_ident_or_star(self):\n        next = self.next()\n        if next.type == 'IDENT':\n            return next.value\n        elif next == ('DELIM', '*'):\n            return None\n        else:\n            raise SelectorSyntaxError(\n                \"Expected ident or '*', got %s\" % (next,))\n\n    def skip_whitespace(self):\n        peek = self.peek()\n        if peek.type == 'S':\n            self.next()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cssselect/xpath.py",
    "content": "# -*- coding: utf-8 -*-\n\"\"\"\n    cssselect.xpath\n    ===============\n\n    Translation of parsed CSS selectors to XPath expressions.\n\n\n    :copyright: (c) 2007-2012 Ian Bicking and contributors.\n                See AUTHORS for more details.\n    :license: BSD, see LICENSE for more details.\n\n\"\"\"\n\nimport sys\nimport re\n\nfrom cssselect.parser import parse, parse_series, SelectorError\n\n\nif sys.version_info[0] < 3:\n    _basestring = basestring\n    _unicode = unicode\nelse:\n    _basestring = str\n    _unicode = str\n\n\ndef _unicode_safe_getattr(obj, name, default=None):\n    # getattr() with a non-ASCII name fails on Python 2.x\n    name = name.encode('ascii', 'replace').decode('ascii')\n    return getattr(obj, name, default)\n\n\nclass ExpressionError(SelectorError, RuntimeError):\n    \"\"\"Unknown or unsupported selector (eg. pseudo-class).\"\"\"\n\n\n#### XPath Helpers\n\nclass XPathExpr(object):\n\n    def __init__(self, path='', element='*', condition='', star_prefix=False):\n        self.path = path\n        self.element = element\n        self.condition = condition\n\n    def __str__(self):\n        path =  _unicode(self.path) + _unicode(self.element)\n        if self.condition:\n            path += '[%s]' % self.condition\n        return path\n\n    def __repr__(self):\n        return '%s[%s]' % (self.__class__.__name__, self)\n\n    def add_condition(self, condition):\n        if self.condition:\n            self.condition = '%s and (%s)' % (self.condition, condition)\n        else:\n            self.condition = condition\n        return self\n\n    def add_name_test(self):\n        if self.element == '*':\n            # We weren't doing a test anyway\n            return\n        self.add_condition(\n            \"name() = %s\" % GenericTranslator.xpath_literal(self.element))\n        self.element = '*'\n\n    def add_star_prefix(self):\n        \"\"\"\n        Append '*/' to the path to keep the context constrained\n        to a single parent.\n        \"\"\"\n        self.path += '*/'\n\n    def join(self, combiner, other):\n        path = _unicode(self) + combiner\n        # Any \"star prefix\" is redundant when joining.\n        if other.path != '*/':\n            path += other.path\n        self.path = path\n        self.element = other.element\n        self.condition = other.condition\n        return self\n\n\nsplit_at_single_quotes = re.compile(\"('+)\").split\n\n# The spec is actually more permissive than that, but don’t bother.\n# This is just for the fast path.\n# http://www.w3.org/TR/REC-xml/#NT-NameStartChar\nis_safe_name = re.compile('^[a-zA-Z_][a-zA-Z0-9_.-]*$').match\n\n# Test that the string is not empty and does not contain whitespace\nis_non_whitespace = re.compile(r'^[^ \\t\\r\\n\\f]+$').match\n\n\n#### Translation\n\nclass GenericTranslator(object):\n    \"\"\"\n    Translator for \"generic\" XML documents.\n\n    Everything is case-sensitive, no assumption is made on the meaning\n    of element names and attribute names.\n\n    \"\"\"\n\n    ####\n    ####  HERE BE DRAGONS\n    ####\n    ####  You are welcome to hook into this to change some behavior,\n    ####  but do so at your own risks.\n    ####  Until it has received a lot more work and review,\n    ####  I reserve the right to change this API in backward-incompatible ways\n    ####  with any minor version of cssselect.\n    ####  See https://github.com/scrapy/cssselect/pull/22\n    ####  -- Simon Sapin.\n    ####\n\n    combinator_mapping = {\n        ' ': 'descendant',\n        '>': 'child',\n        '+': 'direct_adjacent',\n        '~': 'indirect_adjacent',\n    }\n\n    attribute_operator_mapping = {\n       'exists': 'exists',\n        '=': 'equals',\n        '~=': 'includes',\n        '|=': 'dashmatch',\n        '^=': 'prefixmatch',\n        '$=': 'suffixmatch',\n        '*=': 'substringmatch',\n        '!=': 'different',  # XXX Not in Level 3 but meh\n    }\n\n    #: The attribute used for ID selectors depends on the document language:\n    #: http://www.w3.org/TR/selectors/#id-selectors\n    id_attribute = 'id'\n\n    #: The attribute used for ``:lang()`` depends on the document language:\n    #: http://www.w3.org/TR/selectors/#lang-pseudo\n    lang_attribute = 'xml:lang'\n\n    #: The case sensitivity of document language element names,\n    #: attribute names, and attribute values in selectors depends\n    #: on the document language.\n    #: http://www.w3.org/TR/selectors/#casesens\n    #:\n    #: When a document language defines one of these as case-insensitive,\n    #: cssselect assumes that the document parser makes the parsed values\n    #: lower-case. Making the selector lower-case too makes the comparaison\n    #: case-insensitive.\n    #:\n    #: In HTML, element names and attributes names (but not attribute values)\n    #: are case-insensitive. All of lxml.html, html5lib, BeautifulSoup4\n    #: and HTMLParser make them lower-case in their parse result, so\n    #: the assumption holds.\n    lower_case_element_names = False\n    lower_case_attribute_names = False\n    lower_case_attribute_values = False\n\n    # class used to represent and xpath expression\n    xpathexpr_cls = XPathExpr\n\n    def css_to_xpath(self, css, prefix='descendant-or-self::'):\n        \"\"\"Translate a *group of selectors* to XPath.\n\n        Pseudo-elements are not supported here since XPath only knows\n        about \"real\" elements.\n\n        :param css:\n            A *group of selectors* as an Unicode string.\n        :param prefix:\n            This string is prepended to the XPath expression for each selector.\n            The default makes selectors scoped to the context node’s subtree.\n        :raises:\n            :class:`SelectorSyntaxError` on invalid selectors,\n            :class:`ExpressionError` on unknown/unsupported selectors,\n            including pseudo-elements.\n        :returns:\n            The equivalent XPath 1.0 expression as an Unicode string.\n\n        \"\"\"\n        return ' | '.join(self.selector_to_xpath(selector, prefix,\n                                                 translate_pseudo_elements=True)\n                          for selector in parse(css))\n\n    def selector_to_xpath(self, selector, prefix='descendant-or-self::',\n                          translate_pseudo_elements=False):\n        \"\"\"Translate a parsed selector to XPath.\n\n\n        :param selector:\n            A parsed :class:`Selector` object.\n        :param prefix:\n            This string is prepended to the resulting XPath expression.\n            The default makes selectors scoped to the context node’s subtree.\n        :param translate_pseudo_elements:\n            Unless this is set to ``True`` (as :meth:`css_to_xpath` does),\n            the :attr:`~Selector.pseudo_element` attribute of the selector\n            is ignored.\n            It is the caller's responsibility to reject selectors\n            with pseudo-elements, or to account for them somehow.\n        :raises:\n            :class:`ExpressionError` on unknown/unsupported selectors.\n        :returns:\n            The equivalent XPath 1.0 expression as an Unicode string.\n\n        \"\"\"\n        tree = getattr(selector, 'parsed_tree', None)\n        if not tree:\n            raise TypeError('Expected a parsed selector, got %r' % (selector,))\n        xpath = self.xpath(tree)\n        assert isinstance(xpath, self.xpathexpr_cls)  # help debug a missing 'return'\n        if translate_pseudo_elements and selector.pseudo_element:\n            xpath = self.xpath_pseudo_element(xpath, selector.pseudo_element)\n        return (prefix or '') + _unicode(xpath)\n\n    def xpath_pseudo_element(self, xpath, pseudo_element):\n        \"\"\"Translate a pseudo-element.\n\n        Defaults to not supporting pseudo-elements at all,\n        but can be overridden by sub-classes.\n\n        \"\"\"\n        raise ExpressionError('Pseudo-elements are not supported.')\n\n    @staticmethod\n    def xpath_literal(s):\n        s = _unicode(s)\n        if \"'\" not in s:\n            s = \"'%s'\" % s\n        elif '\"' not in s:\n            s = '\"%s\"' % s\n        else:\n            s = \"concat(%s)\" % ','.join([\n                ((\"'\" in part) and '\"%s\"' or \"'%s'\") % part\n                for part in split_at_single_quotes(s) if part\n                ])\n        return s\n\n    def xpath(self, parsed_selector):\n        \"\"\"Translate any parsed selector object.\"\"\"\n        type_name = type(parsed_selector).__name__\n        method = getattr(self, 'xpath_%s' % type_name.lower(), None)\n        if method is None:\n            raise ExpressionError('%s is not supported.' %  type_name)\n        return method(parsed_selector)\n\n\n    # Dispatched by parsed object type\n\n    def xpath_combinedselector(self, combined):\n        \"\"\"Translate a combined selector.\"\"\"\n        combinator = self.combinator_mapping[combined.combinator]\n        method = getattr(self, 'xpath_%s_combinator' % combinator)\n        return method(self.xpath(combined.selector),\n                      self.xpath(combined.subselector))\n\n    def xpath_negation(self, negation):\n        xpath = self.xpath(negation.selector)\n        sub_xpath = self.xpath(negation.subselector)\n        sub_xpath.add_name_test()\n        if sub_xpath.condition:\n            return xpath.add_condition('not(%s)' % sub_xpath.condition)\n        else:\n            return xpath.add_condition('0')\n\n    def xpath_function(self, function):\n        \"\"\"Translate a functional pseudo-class.\"\"\"\n        method = 'xpath_%s_function' % function.name.replace('-', '_')\n        method = _unicode_safe_getattr(self, method, None)\n        if not method:\n            raise ExpressionError(\n                \"The pseudo-class :%s() is unknown\" % function.name)\n        return method(self.xpath(function.selector), function)\n\n    def xpath_pseudo(self, pseudo):\n        \"\"\"Translate a pseudo-class.\"\"\"\n        method = 'xpath_%s_pseudo' % pseudo.ident.replace('-', '_')\n        method = _unicode_safe_getattr(self, method, None)\n        if not method:\n            # TODO: better error message for pseudo-elements?\n            raise ExpressionError(\n                \"The pseudo-class :%s is unknown\" % pseudo.ident)\n        return method(self.xpath(pseudo.selector))\n\n\n    def xpath_attrib(self, selector):\n        \"\"\"Translate an attribute selector.\"\"\"\n        operator = self.attribute_operator_mapping[selector.operator]\n        method = getattr(self, 'xpath_attrib_%s' % operator)\n        if self.lower_case_attribute_names:\n            name = selector.attrib.lower()\n        else:\n            name = selector.attrib\n        safe = is_safe_name(name)\n        if selector.namespace:\n            name = '%s:%s' % (selector.namespace, name)\n            safe = safe and is_safe_name(selector.namespace)\n        if safe:\n            attrib = '@' + name\n        else:\n            attrib = 'attribute::*[name() = %s]' % self.xpath_literal(name)\n        if selector.value is None:\n            value = None\n        elif self.lower_case_attribute_values:\n            value = selector.value.value.lower()\n        else:\n            value = selector.value.value\n        return method(self.xpath(selector.selector), attrib, value)\n\n    def xpath_class(self, class_selector):\n        \"\"\"Translate a class selector.\"\"\"\n        # .foo is defined as [class~=foo] in the spec.\n        xpath = self.xpath(class_selector.selector)\n        return self.xpath_attrib_includes(\n            xpath, '@class', class_selector.class_name)\n\n    def xpath_hash(self, id_selector):\n        \"\"\"Translate an ID selector.\"\"\"\n        xpath = self.xpath(id_selector.selector)\n        return self.xpath_attrib_equals(xpath, '@id', id_selector.id)\n\n    def xpath_element(self, selector):\n        \"\"\"Translate a type or universal selector.\"\"\"\n        element = selector.element\n        if not element:\n            element = '*'\n            safe = True\n        else:\n            safe = is_safe_name(element)\n            if self.lower_case_element_names:\n                element = element.lower()\n        if selector.namespace:\n            # Namespace prefixes are case-sensitive.\n            # http://www.w3.org/TR/css3-namespace/#prefixes\n            element = '%s:%s' % (selector.namespace, element)\n            safe = safe and is_safe_name(selector.namespace)\n        xpath = self.xpathexpr_cls(element=element)\n        if not safe:\n            xpath.add_name_test()\n        return xpath\n\n\n    # CombinedSelector: dispatch by combinator\n\n    def xpath_descendant_combinator(self, left, right):\n        \"\"\"right is a child, grand-child or further descendant of left\"\"\"\n        return left.join('/descendant-or-self::*/', right)\n\n    def xpath_child_combinator(self, left, right):\n        \"\"\"right is an immediate child of left\"\"\"\n        return left.join('/', right)\n\n    def xpath_direct_adjacent_combinator(self, left, right):\n        \"\"\"right is a sibling immediately after left\"\"\"\n        xpath = left.join('/following-sibling::', right)\n        xpath.add_name_test()\n        return xpath.add_condition('position() = 1')\n\n    def xpath_indirect_adjacent_combinator(self, left, right):\n        \"\"\"right is a sibling after left, immediately or not\"\"\"\n        return left.join('/following-sibling::', right)\n\n\n    # Function: dispatch by function/pseudo-class name\n\n    def xpath_nth_child_function(self, xpath, function, last=False,\n                                 add_name_test=True):\n        try:\n            a, b = parse_series(function.arguments)\n        except ValueError:\n            raise ExpressionError(\"Invalid series: '%r'\" % function.arguments)\n\n        # From https://www.w3.org/TR/css3-selectors/#structural-pseudos:\n        #\n        # :nth-child(an+b)\n        #       an+b-1 siblings before\n        #\n        # :nth-last-child(an+b)\n        #       an+b-1 siblings after\n        #\n        # :nth-of-type(an+b)\n        #       an+b-1 siblings with the same expanded element name before\n        #\n        # :nth-last-of-type(an+b)\n        #       an+b-1 siblings with the same expanded element name after\n        #\n        # So,\n        # for :nth-child and :nth-of-type\n        #\n        #    count(preceding-sibling::<nodetest>) = an+b-1\n        #\n        # for :nth-last-child and :nth-last-of-type\n        #\n        #    count(following-sibling::<nodetest>) = an+b-1\n        #\n        # therefore,\n        #    count(...) - (b-1) ≡ 0 (mod a)\n        #\n        # if a == 0:\n        # ~~~~~~~~~~\n        #    count(...) = b-1\n        #\n        # if a < 0:\n        # ~~~~~~~~~\n        #    count(...) - b +1 <= 0\n        # -> count(...) <= b-1\n        #\n        # if a > 0:\n        # ~~~~~~~~~\n        #    count(...) - b +1 >= 0\n        # -> count(...) >= b-1\n\n        # work with b-1 instead\n        b_min_1 = b - 1\n\n        # early-exit condition 1:\n        # ~~~~~~~~~~~~~~~~~~~~~~~\n        # for a == 1, nth-*(an+b) means n+b-1 siblings before/after,\n        # and since n ∈ {0, 1, 2, ...}, if b-1<=0,\n        # there is always an \"n\" matching any number of siblings (maybe none)\n        if a == 1 and b_min_1 <=0:\n            return xpath\n\n        # early-exit condition 2:\n        # ~~~~~~~~~~~~~~~~~~~~~~~\n        # an+b-1 siblings with a<0 and (b-1)<0 is not possible\n        if a < 0 and b_min_1 < 0:\n            return xpath.add_condition('0')\n\n        # `add_name_test` boolean is inverted and somewhat counter-intuitive:\n        #\n        # nth_of_type() calls nth_child(add_name_test=False)\n        if add_name_test:\n            nodetest = '*'\n        else:\n            nodetest  = '%s' % xpath.element\n\n        # count siblings before or after the element\n        if not last:\n            siblings_count = 'count(preceding-sibling::%s)' % nodetest\n        else:\n            siblings_count = 'count(following-sibling::%s)' % nodetest\n\n        # special case of fixed position: nth-*(0n+b)\n        # if a == 0:\n        # ~~~~~~~~~~\n        #    count(***-sibling::***) = b-1\n        if a == 0:\n            return xpath.add_condition('%s = %s' % (siblings_count, b_min_1))\n\n        expr = []\n\n        if a > 0:\n            # siblings count, an+b-1, is always >= 0,\n            # so if a>0, and (b-1)<=0, an \"n\" exists to satisfy this,\n            # therefore, the predicate is only interesting if (b-1)>0\n            if b_min_1 > 0:\n                expr.append('%s >= %s' % (siblings_count, b_min_1))\n        else:\n            # if a<0, and (b-1)<0, no \"n\" satisfies this,\n            # this is tested above as an early exist condition\n            # otherwise,\n            expr.append('%s <= %s' % (siblings_count, b_min_1))\n\n        # operations modulo 1 or -1 are simpler, one only needs to verify:\n        #\n        # - either:\n        # count(***-sibling::***) - (b-1) = n = 0, 1, 2, 3, etc.,\n        #   i.e. count(***-sibling::***) >= (b-1)\n        #\n        # - or:\n        # count(***-sibling::***) - (b-1) = -n = 0, -1, -2, -3, etc.,\n        #   i.e. count(***-sibling::***) <= (b-1)\n        # we we just did above.\n        #\n        if abs(a) != 1:\n            # count(***-sibling::***) - (b-1) ≡ 0 (mod a)\n            left = siblings_count\n\n            # apply \"modulo a\" on 2nd term, -(b-1),\n            # to simplify things like \"(... +6) % -3\",\n            # and also make it positive with |a|\n            b_neg = (-b_min_1) % abs(a)\n\n            if b_neg != 0:\n                b_neg = '+%s' % b_neg\n                left = '(%s %s)' % (left, b_neg)\n\n            expr.append('%s mod %s = 0' % (left, a))\n\n        xpath.add_condition(' and '.join(expr))\n        return xpath\n\n    def xpath_nth_last_child_function(self, xpath, function):\n        return self.xpath_nth_child_function(xpath, function, last=True)\n\n    def xpath_nth_of_type_function(self, xpath, function):\n        if xpath.element == '*':\n            raise ExpressionError(\n                \"*:nth-of-type() is not implemented\")\n        return self.xpath_nth_child_function(xpath, function,\n                                             add_name_test=False)\n\n    def xpath_nth_last_of_type_function(self, xpath, function):\n        if xpath.element == '*':\n            raise ExpressionError(\n                \"*:nth-of-type() is not implemented\")\n        return self.xpath_nth_child_function(xpath, function, last=True,\n                                             add_name_test=False)\n\n    def xpath_contains_function(self, xpath, function):\n        # Defined there, removed in later drafts:\n        # http://www.w3.org/TR/2001/CR-css3-selectors-20011113/#content-selectors\n        if function.argument_types() not in (['STRING'], ['IDENT']):\n            raise ExpressionError(\n                \"Expected a single string or ident for :contains(), got %r\"\n                % function.arguments)\n        value = function.arguments[0].value\n        return xpath.add_condition(\n            'contains(., %s)' % self.xpath_literal(value))\n\n    def xpath_lang_function(self, xpath, function):\n        if function.argument_types() not in (['STRING'], ['IDENT']):\n            raise ExpressionError(\n                \"Expected a single string or ident for :lang(), got %r\"\n                % function.arguments)\n        value = function.arguments[0].value\n        return xpath.add_condition(\n            \"lang(%s)\" % (self.xpath_literal(value)))\n\n\n    # Pseudo: dispatch by pseudo-class name\n\n    def xpath_root_pseudo(self, xpath):\n        return xpath.add_condition(\"not(parent::*)\")\n\n    # CSS immediate children (CSS \":scope > div\" to XPath \"child::div\" or \"./div\")\n    # Works only at the start of a selector\n    # Needed to get immediate children of a processed selector in Scrapy\n    # for product in response.css('.product'):\n    #     description = product.css(':scope > div::text').get()\n    def xpath_scope_pseudo(self, xpath):\n        return xpath.add_condition(\"1\")\n\n    def xpath_first_child_pseudo(self, xpath):\n        return xpath.add_condition('count(preceding-sibling::*) = 0')\n\n    def xpath_last_child_pseudo(self, xpath):\n        return xpath.add_condition('count(following-sibling::*) = 0')\n\n    def xpath_first_of_type_pseudo(self, xpath):\n        if xpath.element == '*':\n            raise ExpressionError(\n                \"*:first-of-type is not implemented\")\n        return xpath.add_condition('count(preceding-sibling::%s) = 0' % xpath.element)\n\n    def xpath_last_of_type_pseudo(self, xpath):\n        if xpath.element == '*':\n            raise ExpressionError(\n                \"*:last-of-type is not implemented\")\n        return xpath.add_condition('count(following-sibling::%s) = 0' % xpath.element)\n\n    def xpath_only_child_pseudo(self, xpath):\n        return xpath.add_condition('count(parent::*/child::*) = 1')\n\n    def xpath_only_of_type_pseudo(self, xpath):\n        if xpath.element == '*':\n            raise ExpressionError(\n                \"*:only-of-type is not implemented\")\n        return xpath.add_condition('count(parent::*/child::%s) = 1' % xpath.element)\n\n    def xpath_empty_pseudo(self, xpath):\n        return xpath.add_condition(\"not(*) and not(string-length())\")\n\n    def pseudo_never_matches(self, xpath):\n        \"\"\"Common implementation for pseudo-classes that never match.\"\"\"\n        return xpath.add_condition(\"0\")\n\n    xpath_link_pseudo = pseudo_never_matches\n    xpath_visited_pseudo = pseudo_never_matches\n    xpath_hover_pseudo = pseudo_never_matches\n    xpath_active_pseudo = pseudo_never_matches\n    xpath_focus_pseudo = pseudo_never_matches\n    xpath_target_pseudo = pseudo_never_matches\n    xpath_enabled_pseudo = pseudo_never_matches\n    xpath_disabled_pseudo = pseudo_never_matches\n    xpath_checked_pseudo = pseudo_never_matches\n\n    # Attrib: dispatch by attribute operator\n\n    def xpath_attrib_exists(self, xpath, name, value):\n        assert not value\n        xpath.add_condition(name)\n        return xpath\n\n    def xpath_attrib_equals(self, xpath, name, value):\n        xpath.add_condition('%s = %s' % (name, self.xpath_literal(value)))\n        return xpath\n\n    def xpath_attrib_different(self, xpath, name, value):\n        # FIXME: this seems like a weird hack...\n        if value:\n            xpath.add_condition('not(%s) or %s != %s'\n                                % (name, name, self.xpath_literal(value)))\n        else:\n            xpath.add_condition('%s != %s'\n                                % (name, self.xpath_literal(value)))\n        return xpath\n\n    def xpath_attrib_includes(self, xpath, name, value):\n        if is_non_whitespace(value):\n            xpath.add_condition(\n                \"%s and contains(concat(' ', normalize-space(%s), ' '), %s)\"\n                % (name, name, self.xpath_literal(' '+value+' ')))\n        else:\n            xpath.add_condition('0')\n        return xpath\n\n    def xpath_attrib_dashmatch(self, xpath, name, value):\n        # Weird, but true...\n        xpath.add_condition('%s and (%s = %s or starts-with(%s, %s))' % (\n            name,\n            name, self.xpath_literal(value),\n            name, self.xpath_literal(value + '-')))\n        return xpath\n\n    def xpath_attrib_prefixmatch(self, xpath, name, value):\n        if value:\n            xpath.add_condition('%s and starts-with(%s, %s)' % (\n                name, name, self.xpath_literal(value)))\n        else:\n            xpath.add_condition('0')\n        return xpath\n\n    def xpath_attrib_suffixmatch(self, xpath, name, value):\n        if value:\n            # Oddly there is a starts-with in XPath 1.0, but not ends-with\n            xpath.add_condition(\n                '%s and substring(%s, string-length(%s)-%s) = %s'\n                % (name, name, name, len(value)-1, self.xpath_literal(value)))\n        else:\n            xpath.add_condition('0')\n        return xpath\n\n    def xpath_attrib_substringmatch(self, xpath, name, value):\n        if value:\n            # Attribute selectors are case sensitive\n            xpath.add_condition('%s and contains(%s, %s)' % (\n                name, name, self.xpath_literal(value)))\n        else:\n            xpath.add_condition('0')\n        return xpath\n\n\nclass HTMLTranslator(GenericTranslator):\n    \"\"\"\n    Translator for (X)HTML documents.\n\n    Has a more useful implementation of some pseudo-classes based on\n    HTML-specific element names and attribute names, as described in\n    the `HTML5 specification`_. It assumes no-quirks mode.\n    The API is the same as :class:`GenericTranslator`.\n\n    .. _HTML5 specification: http://www.w3.org/TR/html5/links.html#selectors\n\n    :param xhtml:\n        If false (the default), element names and attribute names\n        are case-insensitive.\n\n    \"\"\"\n\n    lang_attribute = 'lang'\n\n    def __init__(self, xhtml=False):\n        self.xhtml = xhtml  # Might be useful for sub-classes?\n        if not xhtml:\n            # See their definition in GenericTranslator.\n            self.lower_case_element_names = True\n            self.lower_case_attribute_names = True\n\n    def xpath_checked_pseudo(self, xpath):\n        # FIXME: is this really all the elements?\n        return xpath.add_condition(\n            \"(@selected and name(.) = 'option') or \"\n            \"(@checked \"\n                \"and (name(.) = 'input' or name(.) = 'command')\"\n                \"and (@type = 'checkbox' or @type = 'radio'))\")\n\n    def xpath_lang_function(self, xpath, function):\n        if function.argument_types() not in (['STRING'], ['IDENT']):\n            raise ExpressionError(\n                \"Expected a single string or ident for :lang(), got %r\"\n                % function.arguments)\n        value = function.arguments[0].value\n        return xpath.add_condition(\n            \"ancestor-or-self::*[@lang][1][starts-with(concat(\"\n                # XPath 1.0 has no lower-case function...\n                \"translate(@%s, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ', \"\n                               \"'abcdefghijklmnopqrstuvwxyz'), \"\n                \"'-'), %s)]\"\n            % (self.lang_attribute, self.xpath_literal(value.lower() + '-')))\n\n    def xpath_link_pseudo(self, xpath):\n        return xpath.add_condition(\"@href and \"\n            \"(name(.) = 'a' or name(.) = 'link' or name(.) = 'area')\")\n\n    # Links are never visited, the implementation for :visited is the same\n    # as in GenericTranslator\n\n    def xpath_disabled_pseudo(self, xpath):\n        # http://www.w3.org/TR/html5/section-index.html#attributes-1\n        return xpath.add_condition('''\n        (\n            @disabled and\n            (\n                (name(.) = 'input' and @type != 'hidden') or\n                name(.) = 'button' or\n                name(.) = 'select' or\n                name(.) = 'textarea' or\n                name(.) = 'command' or\n                name(.) = 'fieldset' or\n                name(.) = 'optgroup' or\n                name(.) = 'option'\n            )\n        ) or (\n            (\n                (name(.) = 'input' and @type != 'hidden') or\n                name(.) = 'button' or\n                name(.) = 'select' or\n                name(.) = 'textarea'\n            )\n            and ancestor::fieldset[@disabled]\n        )\n        ''')\n        # FIXME: in the second half, add \"and is not a descendant of that\n        # fieldset element's first legend element child, if any.\"\n\n    def xpath_enabled_pseudo(self, xpath):\n        # http://www.w3.org/TR/html5/section-index.html#attributes-1\n        return xpath.add_condition('''\n        (\n            @href and (\n                name(.) = 'a' or\n                name(.) = 'link' or\n                name(.) = 'area'\n            )\n        ) or (\n            (\n                name(.) = 'command' or\n                name(.) = 'fieldset' or\n                name(.) = 'optgroup'\n            )\n            and not(@disabled)\n        ) or (\n            (\n                (name(.) = 'input' and @type != 'hidden') or\n                name(.) = 'button' or\n                name(.) = 'select' or\n                name(.) = 'textarea' or\n                name(.) = 'keygen'\n            )\n            and not (@disabled or ancestor::fieldset[@disabled])\n        ) or (\n            name(.) = 'option' and not(\n                @disabled or ancestor::optgroup[@disabled]\n            )\n        )\n        ''')\n        # FIXME: ... or \"li elements that are children of menu elements,\n        # and that have a child element that defines a command, if the first\n        # such element's Disabled State facet is false (not disabled)\".\n        # FIXME: after ancestor::fieldset[@disabled], add \"and is not a\n        # descendant of that fieldset element's first legend element child,\n        # if any.\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cssselect-1.1.0.dist-info/AUTHORS",
    "content": "Daniel Graña\nIan Bicking\nJames Salter\nLaurence Rowe\nMikhail Korobov\nNik Nyby\nPaul Tremberth\nSimon Potter\nSimon Sapin\nStefan Behnel\nThomas Grainger\nVarialus\nArthur Darcet\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cssselect-1.1.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cssselect-1.1.0.dist-info/LICENSE",
    "content": "Copyright (c) 2007-2012 Ian Bicking and contributors. See AUTHORS\nfor more details.\n\nAll rights reserved.\n\nRedistribution and use in source and binary forms, with or without\nmodification, are permitted provided that the following conditions are\nmet:\n\n1. Redistributions of source code must retain the above copyright\nnotice, this list of conditions and the following disclaimer.\n\n2. Redistributions in binary form must reproduce the above copyright\nnotice, this list of conditions and the following disclaimer in\nthe documentation and/or other materials provided with the\ndistribution.\n\n3. Neither the name of Ian Bicking nor the names of its contributors may\nbe used to endorse or promote products derived from this software\nwithout specific prior written permission.\n\nTHIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n\"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\nLIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR\nA PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL IAN BICKING OR\nCONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,\nEXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,\nPROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR\nPROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF\nLIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING\nNEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\nSOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cssselect-1.1.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: cssselect\nVersion: 1.1.0\nSummary: cssselect parses CSS3 Selectors and translates them to XPath 1.0\nHome-page: https://github.com/scrapy/cssselect\nAuthor: Ian Bicking\nAuthor-email: ianb@colorstudy.com\nMaintainer: Paul Tremberth\nMaintainer-email: paul.tremberth@gmail.com\nLicense: BSD\nPlatform: UNKNOWN\nClassifier: Development Status :: 4 - Beta\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: BSD License\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nRequires-Python: >=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*\n\n===================================\ncssselect: CSS Selectors for Python\n===================================\n\n.. image:: https://img.shields.io/pypi/v/cssselect.svg\n   :target: https://pypi.python.org/pypi/cssselect\n   :alt: PyPI Version\n\n.. image:: https://img.shields.io/pypi/pyversions/cssselect.svg\n   :target: https://pypi.python.org/pypi/cssselect\n   :alt: Supported Python Versions\n\n.. image:: https://img.shields.io/travis/scrapy/cssselect/master.svg\n   :target: https://travis-ci.org/scrapy/cssselect\n   :alt: Build Status\n\n.. image:: https://img.shields.io/codecov/c/github/scrapy/cssselect/master.svg\n   :target: https://codecov.io/github/scrapy/cssselect?branch=master\n   :alt: Coverage report\n\n*cssselect* parses `CSS3 Selectors`_ and translate them to `XPath 1.0`_\nexpressions. Such expressions can be used in lxml_ or another XPath engine\nto find the matching elements in an XML or HTML document.\n\nThis module used to live inside of lxml as ``lxml.cssselect`` before it was\nextracted as a stand-alone project.\n\n.. _CSS3 Selectors: https://www.w3.org/TR/css3-selectors/\n.. _XPath 1.0: https://www.w3.org/TR/xpath/\n.. _lxml: http://lxml.de/\n\n\nQuick facts:\n\n* Free software: BSD licensed\n* Compatible with Python 2.7 and 3.4+\n* Latest documentation `on Read the Docs <https://cssselect.readthedocs.io/>`_\n* Source, issues and pull requests `on GitHub\n  <https://github.com/scrapy/cssselect>`_\n* Releases `on PyPI <http://pypi.python.org/pypi/cssselect>`_\n* Install with ``pip install cssselect``\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cssselect-1.1.0.dist-info/RECORD",
    "content": "cssselect-1.1.0.dist-info/AUTHORS,sha256=0xOj3H8iII6M_KWmoDYQRuzTrYrLPbJ8K2kVSAoQ5zQ,171\r\ncssselect-1.1.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\ncssselect-1.1.0.dist-info/LICENSE,sha256=XI2p90Tgr7qBpIybXb5zBI95izKH1vGvigXuCOuxCJI,1517\r\ncssselect-1.1.0.dist-info/METADATA,sha256=L1k9gxlz3quPBMPepkTOo0tPXV2l8cQl-yZGnO-gNUc,2332\r\ncssselect-1.1.0.dist-info/RECORD,,\r\ncssselect-1.1.0.dist-info/WHEEL,sha256=h_aVn5OB2IERUjMbi2pucmR_zzWJtk303YXvhh60NJ8,110\r\ncssselect-1.1.0.dist-info/top_level.txt,sha256=GKK3Utu_ceog6CK27VXNdbyiqGnoyJo3970FLo5JdUU,10\r\ncssselect/__init__.py,sha256=fmdpKrz5-uYAzXUh3LMOrEPiJMENB1gf962v5Nq5yis,639\r\ncssselect/__pycache__/__init__.cpython-36.pyc,,\r\ncssselect/__pycache__/parser.cpython-36.pyc,,\r\ncssselect/__pycache__/xpath.cpython-36.pyc,,\r\ncssselect/parser.py,sha256=jrlRxEpSFfiqYHKfUHjgERdMQwFbvsh3sONi_HiTDys,26145\r\ncssselect/xpath.py,sha256=Izy4CXmK6zMHg13PP63bBp065eFZNBfPJeNyhjSsS7Q,28257\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cssselect-1.1.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.33.4)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/cssselect-1.1.0.dist-info/top_level.txt",
    "content": "cssselect\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/easy-install.pth",
    "content": "./setuptools-40.8.0-py3.6.egg\n./pip-19.0.3-py3.6.egg\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/exampleproj/__init__.py",
    "content": "\"\"\"\nAn example project.\n\n@added: exampleproj NEXT\n\"\"\"\n\nfrom incremental import Version\nfrom ._version import __version__\n\n__all__ = [\"__version__\"]\n\nif Version(\"exampleproj\", \"NEXT\", 0, 0) > __version__:\n    print(\"Unreleased!\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/exampleproj/_version.py",
    "content": "# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update exampleproj` to change this file.\n\nfrom incremental import Version\n__version__ = Version('exampleproj', 1, 2, 3)\n\n__all__ = [\"__version__\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/gridfs/__init__.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"GridFS is a specification for storing large objects in Mongo.\n\nThe :mod:`gridfs` package is an implementation of GridFS on top of\n:mod:`pymongo`, exposing a file-like interface.\n\n.. mongodoc:: gridfs\n\"\"\"\n\nfrom bson.py3compat import abc\nfrom gridfs.errors import NoFile\nfrom gridfs.grid_file import (GridIn,\n                              GridOut,\n                              GridOutCursor,\n                              DEFAULT_CHUNK_SIZE,\n                              _clear_entity_type_registry)\nfrom pymongo import (ASCENDING,\n                     DESCENDING)\nfrom pymongo.common import UNAUTHORIZED_CODES, validate_string\nfrom pymongo.database import Database\nfrom pymongo.errors import ConfigurationError, OperationFailure\n\n\nclass GridFS(object):\n    \"\"\"An instance of GridFS on top of a single Database.\n    \"\"\"\n    def __init__(self, database, collection=\"fs\", disable_md5=False):\n        \"\"\"Create a new instance of :class:`GridFS`.\n\n        Raises :class:`TypeError` if `database` is not an instance of\n        :class:`~pymongo.database.Database`.\n\n        :Parameters:\n          - `database`: database to use\n          - `collection` (optional): root collection to use\n          - `disable_md5` (optional): When True, MD5 checksums will not be\n            computed for uploaded files. Useful in environments where MD5\n            cannot be used for regulatory or other reasons. Defaults to False.\n\n        .. versionchanged:: 3.1\n           Indexes are only ensured on the first write to the DB.\n\n        .. versionchanged:: 3.0\n           `database` must use an acknowledged\n           :attr:`~pymongo.database.Database.write_concern`\n\n        .. mongodoc:: gridfs\n        \"\"\"\n        if not isinstance(database, Database):\n            raise TypeError(\"database must be an instance of Database\")\n\n        database = _clear_entity_type_registry(database)\n\n        if not database.write_concern.acknowledged:\n            raise ConfigurationError('database must use '\n                                     'acknowledged write_concern')\n\n        self.__database = database\n        self.__collection = database[collection]\n        self.__files = self.__collection.files\n        self.__chunks = self.__collection.chunks\n        self.__disable_md5 = disable_md5\n\n    def new_file(self, **kwargs):\n        \"\"\"Create a new file in GridFS.\n\n        Returns a new :class:`~gridfs.grid_file.GridIn` instance to\n        which data can be written. Any keyword arguments will be\n        passed through to :meth:`~gridfs.grid_file.GridIn`.\n\n        If the ``\"_id\"`` of the file is manually specified, it must\n        not already exist in GridFS. Otherwise\n        :class:`~gridfs.errors.FileExists` is raised.\n\n        :Parameters:\n          - `**kwargs` (optional): keyword arguments for file creation\n        \"\"\"\n        # No need for __ensure_index_files_id() here; GridIn ensures\n        # the (files_id, n) index when needed.\n        return GridIn(\n            self.__collection, disable_md5=self.__disable_md5, **kwargs)\n\n    def put(self, data, **kwargs):\n        \"\"\"Put data in GridFS as a new file.\n\n        Equivalent to doing::\n\n          try:\n              f = new_file(**kwargs)\n              f.write(data)\n          finally:\n              f.close()\n\n        `data` can be either an instance of :class:`str` (:class:`bytes`\n        in python 3) or a file-like object providing a :meth:`read` method.\n        If an `encoding` keyword argument is passed, `data` can also be a\n        :class:`unicode` (:class:`str` in python 3) instance, which will\n        be encoded as `encoding` before being written. Any keyword arguments\n        will be passed through to the created file - see\n        :meth:`~gridfs.grid_file.GridIn` for possible arguments. Returns the\n        ``\"_id\"`` of the created file.\n\n        If the ``\"_id\"`` of the file is manually specified, it must\n        not already exist in GridFS. Otherwise\n        :class:`~gridfs.errors.FileExists` is raised.\n\n        :Parameters:\n          - `data`: data to be written as a file.\n          - `**kwargs` (optional): keyword arguments for file creation\n\n        .. versionchanged:: 3.0\n           w=0 writes to GridFS are now prohibited.\n        \"\"\"\n        grid_file = GridIn(\n            self.__collection, disable_md5=self.__disable_md5, **kwargs)\n        try:\n            grid_file.write(data)\n        finally:\n            grid_file.close()\n\n        return grid_file._id\n\n    def get(self, file_id, session=None):\n        \"\"\"Get a file from GridFS by ``\"_id\"``.\n\n        Returns an instance of :class:`~gridfs.grid_file.GridOut`,\n        which provides a file-like interface for reading.\n\n        :Parameters:\n          - `file_id`: ``\"_id\"`` of the file to get\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        gout = GridOut(self.__collection, file_id, session=session)\n\n        # Raise NoFile now, instead of on first attribute access.\n        gout._ensure_file()\n        return gout\n\n    def get_version(self, filename=None, version=-1, session=None, **kwargs):\n        \"\"\"Get a file from GridFS by ``\"filename\"`` or metadata fields.\n\n        Returns a version of the file in GridFS whose filename matches\n        `filename` and whose metadata fields match the supplied keyword\n        arguments, as an instance of :class:`~gridfs.grid_file.GridOut`.\n\n        Version numbering is a convenience atop the GridFS API provided\n        by MongoDB. If more than one file matches the query (either by\n        `filename` alone, by metadata fields, or by a combination of\n        both), then version ``-1`` will be the most recently uploaded\n        matching file, ``-2`` the second most recently\n        uploaded, etc. Version ``0`` will be the first version\n        uploaded, ``1`` the second version, etc. So if three versions\n        have been uploaded, then version ``0`` is the same as version\n        ``-3``, version ``1`` is the same as version ``-2``, and\n        version ``2`` is the same as version ``-1``.\n\n        Raises :class:`~gridfs.errors.NoFile` if no such version of\n        that file exists.\n\n        :Parameters:\n          - `filename`: ``\"filename\"`` of the file to get, or `None`\n          - `version` (optional): version of the file to get (defaults\n            to -1, the most recent version uploaded)\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n          - `**kwargs` (optional): find files by custom metadata.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.1\n           ``get_version`` no longer ensures indexes.\n        \"\"\"\n        query = kwargs\n        if filename is not None:\n            query[\"filename\"] = filename\n\n        cursor = self.__files.find(query, session=session)\n        if version < 0:\n            skip = abs(version) - 1\n            cursor.limit(-1).skip(skip).sort(\"uploadDate\", DESCENDING)\n        else:\n            cursor.limit(-1).skip(version).sort(\"uploadDate\", ASCENDING)\n        try:\n            doc = next(cursor)\n            return GridOut(\n                self.__collection, file_document=doc, session=session)\n        except StopIteration:\n            raise NoFile(\"no version %d for filename %r\" % (version, filename))\n\n    def get_last_version(self, filename=None, session=None, **kwargs):\n        \"\"\"Get the most recent version of a file in GridFS by ``\"filename\"``\n        or metadata fields.\n\n        Equivalent to calling :meth:`get_version` with the default\n        `version` (``-1``).\n\n        :Parameters:\n          - `filename`: ``\"filename\"`` of the file to get, or `None`\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n          - `**kwargs` (optional): find files by custom metadata.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        return self.get_version(filename=filename, session=session, **kwargs)\n\n    # TODO add optional safe mode for chunk removal?\n    def delete(self, file_id, session=None):\n        \"\"\"Delete a file from GridFS by ``\"_id\"``.\n\n        Deletes all data belonging to the file with ``\"_id\"``:\n        `file_id`.\n\n        .. warning:: Any processes/threads reading from the file while\n           this method is executing will likely see an invalid/corrupt\n           file. Care should be taken to avoid concurrent reads to a file\n           while it is being deleted.\n\n        .. note:: Deletes of non-existent files are considered successful\n           since the end result is the same: no file with that _id remains.\n\n        :Parameters:\n          - `file_id`: ``\"_id\"`` of the file to delete\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.1\n           ``delete`` no longer ensures indexes.\n        \"\"\"\n        self.__files.delete_one({\"_id\": file_id}, session=session)\n        self.__chunks.delete_many({\"files_id\": file_id}, session=session)\n\n    def list(self, session=None):\n        \"\"\"List the names of all files stored in this instance of\n        :class:`GridFS`.\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.1\n           ``list`` no longer ensures indexes.\n        \"\"\"\n        # With an index, distinct includes documents with no filename\n        # as None.\n        return [\n            name for name in self.__files.distinct(\"filename\", session=session)\n            if name is not None]\n\n    def find_one(self, filter=None, session=None, *args, **kwargs):\n        \"\"\"Get a single file from gridfs.\n\n        All arguments to :meth:`find` are also valid arguments for\n        :meth:`find_one`, although any `limit` argument will be\n        ignored. Returns a single :class:`~gridfs.grid_file.GridOut`,\n        or ``None`` if no matching file is found. For example::\n\n            file = fs.find_one({\"filename\": \"lisa.txt\"})\n\n        :Parameters:\n          - `filter` (optional): a dictionary specifying\n            the query to be performing OR any other type to be used as\n            the value for a query for ``\"_id\"`` in the file collection.\n          - `*args` (optional): any additional positional arguments are\n            the same as the arguments to :meth:`find`.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n          - `**kwargs` (optional): any additional keyword arguments\n            are the same as the arguments to :meth:`find`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        if filter is not None and not isinstance(filter, abc.Mapping):\n            filter = {\"_id\": filter}\n\n        for f in self.find(filter, *args, session=session, **kwargs):\n            return f\n\n        return None\n\n    def find(self, *args, **kwargs):\n        \"\"\"Query GridFS for files.\n\n        Returns a cursor that iterates across files matching\n        arbitrary queries on the files collection. Can be combined\n        with other modifiers for additional control. For example::\n\n          for grid_out in fs.find({\"filename\": \"lisa.txt\"},\n                                  no_cursor_timeout=True):\n              data = grid_out.read()\n\n        would iterate through all versions of \"lisa.txt\" stored in GridFS.\n        Note that setting no_cursor_timeout to True may be important to\n        prevent the cursor from timing out during long multi-file processing\n        work.\n\n        As another example, the call::\n\n          most_recent_three = fs.find().sort(\"uploadDate\", -1).limit(3)\n\n        would return a cursor to the three most recently uploaded files\n        in GridFS.\n\n        Follows a similar interface to\n        :meth:`~pymongo.collection.Collection.find`\n        in :class:`~pymongo.collection.Collection`.\n\n        If a :class:`~pymongo.client_session.ClientSession` is passed to\n        :meth:`find`, all returned :class:`~gridfs.grid_file.GridOut` instances\n        are associated with that session.\n\n        :Parameters:\n          - `filter` (optional): a SON object specifying elements which\n            must be present for a document to be included in the\n            result set\n          - `skip` (optional): the number of files to omit (from\n            the start of the result set) when returning the results\n          - `limit` (optional): the maximum number of results to\n            return\n          - `no_cursor_timeout` (optional): if False (the default), any\n            returned cursor is closed by the server after 10 minutes of\n            inactivity. If set to True, the returned cursor will never\n            time out on the server. Care should be taken to ensure that\n            cursors with no_cursor_timeout turned on are properly closed.\n          - `sort` (optional): a list of (key, direction) pairs\n            specifying the sort order for this query. See\n            :meth:`~pymongo.cursor.Cursor.sort` for details.\n\n        Raises :class:`TypeError` if any of the arguments are of\n        improper type. Returns an instance of\n        :class:`~gridfs.grid_file.GridOutCursor`\n        corresponding to this query.\n\n        .. versionchanged:: 3.0\n           Removed the read_preference, tag_sets, and\n           secondary_acceptable_latency_ms options.\n        .. versionadded:: 2.7\n        .. mongodoc:: find\n        \"\"\"\n        return GridOutCursor(self.__collection, *args, **kwargs)\n\n    def exists(self, document_or_id=None, session=None, **kwargs):\n        \"\"\"Check if a file exists in this instance of :class:`GridFS`.\n\n        The file to check for can be specified by the value of its\n        ``_id`` key, or by passing in a query document. A query\n        document can be passed in as dictionary, or by using keyword\n        arguments. Thus, the following three calls are equivalent:\n\n        >>> fs.exists(file_id)\n        >>> fs.exists({\"_id\": file_id})\n        >>> fs.exists(_id=file_id)\n\n        As are the following two calls:\n\n        >>> fs.exists({\"filename\": \"mike.txt\"})\n        >>> fs.exists(filename=\"mike.txt\")\n\n        And the following two:\n\n        >>> fs.exists({\"foo\": {\"$gt\": 12}})\n        >>> fs.exists(foo={\"$gt\": 12})\n\n        Returns ``True`` if a matching file exists, ``False``\n        otherwise. Calls to :meth:`exists` will not automatically\n        create appropriate indexes; application developers should be\n        sure to create indexes if needed and as appropriate.\n\n        :Parameters:\n          - `document_or_id` (optional): query document, or _id of the\n            document to check for\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n          - `**kwargs` (optional): keyword arguments are used as a\n            query document, if they're present.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        if kwargs:\n            f = self.__files.find_one(kwargs, [\"_id\"], session=session)\n        else:\n            f = self.__files.find_one(document_or_id, [\"_id\"], session=session)\n\n        return f is not None\n\n\nclass GridFSBucket(object):\n    \"\"\"An instance of GridFS on top of a single Database.\"\"\"\n\n    def __init__(self, db, bucket_name=\"fs\",\n                 chunk_size_bytes=DEFAULT_CHUNK_SIZE, write_concern=None,\n                 read_preference=None, disable_md5=False):\n        \"\"\"Create a new instance of :class:`GridFSBucket`.\n\n        Raises :exc:`TypeError` if `database` is not an instance of\n        :class:`~pymongo.database.Database`.\n\n        Raises :exc:`~pymongo.errors.ConfigurationError` if `write_concern`\n        is not acknowledged.\n\n        :Parameters:\n          - `database`: database to use.\n          - `bucket_name` (optional): The name of the bucket. Defaults to 'fs'.\n          - `chunk_size_bytes` (optional): The chunk size in bytes. Defaults\n            to 255KB.\n          - `write_concern` (optional): The\n            :class:`~pymongo.write_concern.WriteConcern` to use. If ``None``\n            (the default) db.write_concern is used.\n          - `read_preference` (optional): The read preference to use. If\n            ``None`` (the default) db.read_preference is used.\n          - `disable_md5` (optional): When True, MD5 checksums will not be\n            computed for uploaded files. Useful in environments where MD5\n            cannot be used for regulatory or other reasons. Defaults to False.\n\n        .. versionadded:: 3.1\n\n        .. mongodoc:: gridfs\n        \"\"\"\n        if not isinstance(db, Database):\n            raise TypeError(\"database must be an instance of Database\")\n\n        db = _clear_entity_type_registry(db)\n\n        wtc = write_concern if write_concern is not None else db.write_concern\n        if not wtc.acknowledged:\n            raise ConfigurationError('write concern must be acknowledged')\n\n        self._db = db\n        self._bucket_name = bucket_name\n        self._collection = db[bucket_name]\n        self._disable_md5 = disable_md5\n\n        self._chunks = self._collection.chunks.with_options(\n            write_concern=write_concern,\n            read_preference=read_preference)\n\n        self._files = self._collection.files.with_options(\n            write_concern=write_concern,\n            read_preference=read_preference)\n\n        self._chunk_size_bytes = chunk_size_bytes\n\n    def open_upload_stream(self, filename, chunk_size_bytes=None,\n                           metadata=None, session=None):\n        \"\"\"Opens a Stream that the application can write the contents of the\n        file to.\n\n        The user must specify the filename, and can choose to add any\n        additional information in the metadata field of the file document or\n        modify the chunk size.\n        For example::\n\n          my_db = MongoClient().test\n          fs = GridFSBucket(my_db)\n          grid_in = fs.open_upload_stream(\n                \"test_file\", chunk_size_bytes=4,\n                metadata={\"contentType\": \"text/plain\"})\n          grid_in.write(\"data I want to store!\")\n          grid_in.close()  # uploaded on close\n\n        Returns an instance of :class:`~gridfs.grid_file.GridIn`.\n\n        Raises :exc:`~gridfs.errors.NoFile` if no such version of\n        that file exists.\n        Raises :exc:`~ValueError` if `filename` is not a string.\n\n        :Parameters:\n          - `filename`: The name of the file to upload.\n          - `chunk_size_bytes` (options): The number of bytes per chunk of this\n            file. Defaults to the chunk_size_bytes in :class:`GridFSBucket`.\n          - `metadata` (optional): User data for the 'metadata' field of the\n            files collection document. If not provided the metadata field will\n            be omitted from the files collection document.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        validate_string(\"filename\", filename)\n\n        opts = {\"filename\": filename,\n                \"chunk_size\": (chunk_size_bytes if chunk_size_bytes\n                               is not None else self._chunk_size_bytes)}\n        if metadata is not None:\n            opts[\"metadata\"] = metadata\n\n        return GridIn(\n            self._collection,\n            session=session,\n            disable_md5=self._disable_md5,\n            **opts)\n\n    def open_upload_stream_with_id(\n            self, file_id, filename, chunk_size_bytes=None, metadata=None,\n            session=None):\n        \"\"\"Opens a Stream that the application can write the contents of the\n        file to.\n\n        The user must specify the file id and filename, and can choose to add\n        any additional information in the metadata field of the file document\n        or modify the chunk size.\n        For example::\n\n          my_db = MongoClient().test\n          fs = GridFSBucket(my_db)\n          grid_in = fs.open_upload_stream_with_id(\n                ObjectId(),\n                \"test_file\",\n                chunk_size_bytes=4,\n                metadata={\"contentType\": \"text/plain\"})\n          grid_in.write(\"data I want to store!\")\n          grid_in.close()  # uploaded on close\n\n        Returns an instance of :class:`~gridfs.grid_file.GridIn`.\n\n        Raises :exc:`~gridfs.errors.NoFile` if no such version of\n        that file exists.\n        Raises :exc:`~ValueError` if `filename` is not a string.\n\n        :Parameters:\n          - `file_id`: The id to use for this file. The id must not have\n            already been used for another file.\n          - `filename`: The name of the file to upload.\n          - `chunk_size_bytes` (options): The number of bytes per chunk of this\n            file. Defaults to the chunk_size_bytes in :class:`GridFSBucket`.\n          - `metadata` (optional): User data for the 'metadata' field of the\n            files collection document. If not provided the metadata field will\n            be omitted from the files collection document.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        validate_string(\"filename\", filename)\n\n        opts = {\"_id\": file_id,\n                \"filename\": filename,\n                \"chunk_size\": (chunk_size_bytes if chunk_size_bytes\n                               is not None else self._chunk_size_bytes)}\n        if metadata is not None:\n            opts[\"metadata\"] = metadata\n\n        return GridIn(\n            self._collection,\n            session=session,\n            disable_md5=self._disable_md5,\n            **opts)\n\n    def upload_from_stream(self, filename, source, chunk_size_bytes=None,\n                           metadata=None, session=None):\n        \"\"\"Uploads a user file to a GridFS bucket.\n\n        Reads the contents of the user file from `source` and uploads\n        it to the file `filename`. Source can be a string or file-like object.\n        For example::\n\n          my_db = MongoClient().test\n          fs = GridFSBucket(my_db)\n          file_id = fs.upload_from_stream(\n              \"test_file\",\n              \"data I want to store!\",\n              chunk_size_bytes=4,\n              metadata={\"contentType\": \"text/plain\"})\n\n        Returns the _id of the uploaded file.\n\n        Raises :exc:`~gridfs.errors.NoFile` if no such version of\n        that file exists.\n        Raises :exc:`~ValueError` if `filename` is not a string.\n\n        :Parameters:\n          - `filename`: The name of the file to upload.\n          - `source`: The source stream of the content to be uploaded. Must be\n            a file-like object that implements :meth:`read` or a string.\n          - `chunk_size_bytes` (options): The number of bytes per chunk of this\n            file. Defaults to the chunk_size_bytes of :class:`GridFSBucket`.\n          - `metadata` (optional): User data for the 'metadata' field of the\n            files collection document. If not provided the metadata field will\n            be omitted from the files collection document.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        with self.open_upload_stream(\n                filename, chunk_size_bytes, metadata, session=session) as gin:\n            gin.write(source)\n\n        return gin._id\n\n    def upload_from_stream_with_id(self, file_id, filename, source,\n                                   chunk_size_bytes=None, metadata=None,\n                                   session=None):\n        \"\"\"Uploads a user file to a GridFS bucket with a custom file id.\n\n        Reads the contents of the user file from `source` and uploads\n        it to the file `filename`. Source can be a string or file-like object.\n        For example::\n\n          my_db = MongoClient().test\n          fs = GridFSBucket(my_db)\n          file_id = fs.upload_from_stream(\n              ObjectId(),\n              \"test_file\",\n              \"data I want to store!\",\n              chunk_size_bytes=4,\n              metadata={\"contentType\": \"text/plain\"})\n\n        Raises :exc:`~gridfs.errors.NoFile` if no such version of\n        that file exists.\n        Raises :exc:`~ValueError` if `filename` is not a string.\n\n        :Parameters:\n          - `file_id`: The id to use for this file. The id must not have\n            already been used for another file.\n          - `filename`: The name of the file to upload.\n          - `source`: The source stream of the content to be uploaded. Must be\n            a file-like object that implements :meth:`read` or a string.\n          - `chunk_size_bytes` (options): The number of bytes per chunk of this\n            file. Defaults to the chunk_size_bytes of :class:`GridFSBucket`.\n          - `metadata` (optional): User data for the 'metadata' field of the\n            files collection document. If not provided the metadata field will\n            be omitted from the files collection document.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        with self.open_upload_stream_with_id(\n                file_id, filename, chunk_size_bytes, metadata,\n                session=session) as gin:\n            gin.write(source)\n\n    def open_download_stream(self, file_id, session=None):\n        \"\"\"Opens a Stream from which the application can read the contents of\n        the stored file specified by file_id.\n\n        For example::\n\n          my_db = MongoClient().test\n          fs = GridFSBucket(my_db)\n          # get _id of file to read.\n          file_id = fs.upload_from_stream(\"test_file\", \"data I want to store!\")\n          grid_out = fs.open_download_stream(file_id)\n          contents = grid_out.read()\n\n        Returns an instance of :class:`~gridfs.grid_file.GridOut`.\n\n        Raises :exc:`~gridfs.errors.NoFile` if no file with file_id exists.\n\n        :Parameters:\n          - `file_id`: The _id of the file to be downloaded.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        gout = GridOut(self._collection, file_id, session=session)\n\n        # Raise NoFile now, instead of on first attribute access.\n        gout._ensure_file()\n        return gout\n\n    def download_to_stream(self, file_id, destination, session=None):\n        \"\"\"Downloads the contents of the stored file specified by file_id and\n        writes the contents to `destination`.\n\n        For example::\n\n          my_db = MongoClient().test\n          fs = GridFSBucket(my_db)\n          # Get _id of file to read\n          file_id = fs.upload_from_stream(\"test_file\", \"data I want to store!\")\n          # Get file to write to\n          file = open('myfile','wb+')\n          fs.download_to_stream(file_id, file)\n          file.seek(0)\n          contents = file.read()\n\n        Raises :exc:`~gridfs.errors.NoFile` if no file with file_id exists.\n\n        :Parameters:\n          - `file_id`: The _id of the file to be downloaded.\n          - `destination`: a file-like object implementing :meth:`write`.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        with self.open_download_stream(file_id, session=session) as gout:\n            for chunk in gout:\n                destination.write(chunk)\n\n    def delete(self, file_id, session=None):\n        \"\"\"Given an file_id, delete this stored file's files collection document\n        and associated chunks from a GridFS bucket.\n\n        For example::\n\n          my_db = MongoClient().test\n          fs = GridFSBucket(my_db)\n          # Get _id of file to delete\n          file_id = fs.upload_from_stream(\"test_file\", \"data I want to store!\")\n          fs.delete(file_id)\n\n        Raises :exc:`~gridfs.errors.NoFile` if no file with file_id exists.\n\n        :Parameters:\n          - `file_id`: The _id of the file to be deleted.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        res = self._files.delete_one({\"_id\": file_id}, session=session)\n        self._chunks.delete_many({\"files_id\": file_id}, session=session)\n        if not res.deleted_count:\n            raise NoFile(\n                \"no file could be deleted because none matched %s\" % file_id)\n\n    def find(self, *args, **kwargs):\n        \"\"\"Find and return the files collection documents that match ``filter``\n\n        Returns a cursor that iterates across files matching\n        arbitrary queries on the files collection. Can be combined\n        with other modifiers for additional control.\n\n        For example::\n\n          for grid_data in fs.find({\"filename\": \"lisa.txt\"},\n                                  no_cursor_timeout=True):\n              data = grid_data.read()\n\n        would iterate through all versions of \"lisa.txt\" stored in GridFS.\n        Note that setting no_cursor_timeout to True may be important to\n        prevent the cursor from timing out during long multi-file processing\n        work.\n\n        As another example, the call::\n\n          most_recent_three = fs.find().sort(\"uploadDate\", -1).limit(3)\n\n        would return a cursor to the three most recently uploaded files\n        in GridFS.\n\n        Follows a similar interface to\n        :meth:`~pymongo.collection.Collection.find`\n        in :class:`~pymongo.collection.Collection`.\n\n        If a :class:`~pymongo.client_session.ClientSession` is passed to\n        :meth:`find`, all returned :class:`~gridfs.grid_file.GridOut` instances\n        are associated with that session.\n\n        :Parameters:\n          - `filter`: Search query.\n          - `batch_size` (optional): The number of documents to return per\n            batch.\n          - `limit` (optional): The maximum number of documents to return.\n          - `no_cursor_timeout` (optional): The server normally times out idle\n            cursors after an inactivity period (10 minutes) to prevent excess\n            memory use. Set this option to True prevent that.\n          - `skip` (optional): The number of documents to skip before\n            returning.\n          - `sort` (optional): The order by which to sort results. Defaults to\n            None.\n        \"\"\"\n        return GridOutCursor(self._collection, *args, **kwargs)\n\n    def open_download_stream_by_name(self, filename, revision=-1, session=None):\n        \"\"\"Opens a Stream from which the application can read the contents of\n        `filename` and optional `revision`.\n\n        For example::\n\n          my_db = MongoClient().test\n          fs = GridFSBucket(my_db)\n          grid_out = fs.open_download_stream_by_name(\"test_file\")\n          contents = grid_out.read()\n\n        Returns an instance of :class:`~gridfs.grid_file.GridOut`.\n\n        Raises :exc:`~gridfs.errors.NoFile` if no such version of\n        that file exists.\n\n        Raises :exc:`~ValueError` filename is not a string.\n\n        :Parameters:\n          - `filename`: The name of the file to read from.\n          - `revision` (optional): Which revision (documents with the same\n            filename and different uploadDate) of the file to retrieve.\n            Defaults to -1 (the most recent revision).\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        :Note: Revision numbers are defined as follows:\n\n          - 0 = the original stored file\n          - 1 = the first revision\n          - 2 = the second revision\n          - etc...\n          - -2 = the second most recent revision\n          - -1 = the most recent revision\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        validate_string(\"filename\", filename)\n\n        query = {\"filename\": filename}\n\n        cursor = self._files.find(query, session=session)\n        if revision < 0:\n            skip = abs(revision) - 1\n            cursor.limit(-1).skip(skip).sort(\"uploadDate\", DESCENDING)\n        else:\n            cursor.limit(-1).skip(revision).sort(\"uploadDate\", ASCENDING)\n        try:\n            grid_file = next(cursor)\n            return GridOut(\n                self._collection, file_document=grid_file, session=session)\n        except StopIteration:\n            raise NoFile(\n                \"no version %d for filename %r\" % (revision, filename))\n\n    def download_to_stream_by_name(self, filename, destination, revision=-1,\n                                   session=None):\n        \"\"\"Write the contents of `filename` (with optional `revision`) to\n        `destination`.\n\n        For example::\n\n          my_db = MongoClient().test\n          fs = GridFSBucket(my_db)\n          # Get file to write to\n          file = open('myfile','wb')\n          fs.download_to_stream_by_name(\"test_file\", file)\n\n        Raises :exc:`~gridfs.errors.NoFile` if no such version of\n        that file exists.\n\n        Raises :exc:`~ValueError` if `filename` is not a string.\n\n        :Parameters:\n          - `filename`: The name of the file to read from.\n          - `destination`: A file-like object that implements :meth:`write`.\n          - `revision` (optional): Which revision (documents with the same\n            filename and different uploadDate) of the file to retrieve.\n            Defaults to -1 (the most recent revision).\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        :Note: Revision numbers are defined as follows:\n\n          - 0 = the original stored file\n          - 1 = the first revision\n          - 2 = the second revision\n          - etc...\n          - -2 = the second most recent revision\n          - -1 = the most recent revision\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        with self.open_download_stream_by_name(\n                filename, revision, session=session) as gout:\n            for chunk in gout:\n                destination.write(chunk)\n\n    def rename(self, file_id, new_filename, session=None):\n        \"\"\"Renames the stored file with the specified file_id.\n\n        For example::\n\n          my_db = MongoClient().test\n          fs = GridFSBucket(my_db)\n          # Get _id of file to rename\n          file_id = fs.upload_from_stream(\"test_file\", \"data I want to store!\")\n          fs.rename(file_id, \"new_test_name\")\n\n        Raises :exc:`~gridfs.errors.NoFile` if no file with file_id exists.\n\n        :Parameters:\n          - `file_id`: The _id of the file to be renamed.\n          - `new_filename`: The new name of the file.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        result = self._files.update_one({\"_id\": file_id},\n                                        {\"$set\": {\"filename\": new_filename}},\n                                        session=session)\n        if not result.matched_count:\n            raise NoFile(\"no files could be renamed %r because none \"\n                         \"matched file_id %i\" % (new_filename, file_id))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/gridfs/errors.py",
    "content": "# Copyright 2009-2015 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Exceptions raised by the :mod:`gridfs` package\"\"\"\n\nfrom pymongo.errors import PyMongoError\n\n\nclass GridFSError(PyMongoError):\n    \"\"\"Base class for all GridFS exceptions.\"\"\"\n\n\nclass CorruptGridFile(GridFSError):\n    \"\"\"Raised when a file in :class:`~gridfs.GridFS` is malformed.\"\"\"\n\n\nclass NoFile(GridFSError):\n    \"\"\"Raised when trying to read from a non-existent file.\"\"\"\n\n\nclass FileExists(GridFSError):\n    \"\"\"Raised when trying to create a file that already exists.\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/gridfs/grid_file.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for representing files stored in GridFS.\"\"\"\nimport datetime\nimport hashlib\nimport io\nimport math\nimport os\n\nfrom bson.int64 import Int64\nfrom bson.son import SON\nfrom bson.binary import Binary\nfrom bson.objectid import ObjectId\nfrom bson.py3compat import text_type, StringIO\nfrom gridfs.errors import CorruptGridFile, FileExists, NoFile\nfrom pymongo import ASCENDING\nfrom pymongo.collection import Collection\nfrom pymongo.cursor import Cursor\nfrom pymongo.errors import (ConfigurationError,\n                            CursorNotFound,\n                            DuplicateKeyError,\n                            OperationFailure)\nfrom pymongo.read_preferences import ReadPreference\n\ntry:\n    _SEEK_SET = os.SEEK_SET\n    _SEEK_CUR = os.SEEK_CUR\n    _SEEK_END = os.SEEK_END\n# before 2.5\nexcept AttributeError:\n    _SEEK_SET = 0\n    _SEEK_CUR = 1\n    _SEEK_END = 2\n\nEMPTY = b\"\"\nNEWLN = b\"\\n\"\n\n\"\"\"Default chunk size, in bytes.\"\"\"\n# Slightly under a power of 2, to work well with server's record allocations.\nDEFAULT_CHUNK_SIZE = 255 * 1024\n\n_C_INDEX = SON([(\"files_id\", ASCENDING), (\"n\", ASCENDING)])\n_F_INDEX = SON([(\"filename\", ASCENDING), (\"uploadDate\", ASCENDING)])\n\n\ndef _grid_in_property(field_name, docstring, read_only=False,\n                      closed_only=False):\n    \"\"\"Create a GridIn property.\"\"\"\n    def getter(self):\n        if closed_only and not self._closed:\n            raise AttributeError(\"can only get %r on a closed file\" %\n                                 field_name)\n        # Protect against PHP-237\n        if field_name == 'length':\n            return self._file.get(field_name, 0)\n        return self._file.get(field_name, None)\n\n    def setter(self, value):\n        if self._closed:\n            self._coll.files.update_one({\"_id\": self._file[\"_id\"]},\n                                        {\"$set\": {field_name: value}})\n        self._file[field_name] = value\n\n    if read_only:\n        docstring += \"\\n\\nThis attribute is read-only.\"\n    elif closed_only:\n        docstring = \"%s\\n\\n%s\" % (docstring, \"This attribute is read-only and \"\n                                  \"can only be read after :meth:`close` \"\n                                  \"has been called.\")\n\n    if not read_only and not closed_only:\n        return property(getter, setter, doc=docstring)\n    return property(getter, doc=docstring)\n\n\ndef _grid_out_property(field_name, docstring):\n    \"\"\"Create a GridOut property.\"\"\"\n    def getter(self):\n        self._ensure_file()\n\n        # Protect against PHP-237\n        if field_name == 'length':\n            return self._file.get(field_name, 0)\n        return self._file.get(field_name, None)\n\n    docstring += \"\\n\\nThis attribute is read-only.\"\n    return property(getter, doc=docstring)\n\n\ndef _clear_entity_type_registry(entity, **kwargs):\n    \"\"\"Clear the given database/collection object's type registry.\"\"\"\n    codecopts = entity.codec_options.with_options(type_registry=None)\n    return entity.with_options(codec_options=codecopts, **kwargs)\n\n\nclass GridIn(object):\n    \"\"\"Class to write data to GridFS.\n    \"\"\"\n    def __init__(\n            self, root_collection, session=None, disable_md5=False, **kwargs):\n        \"\"\"Write a file to GridFS\n\n        Application developers should generally not need to\n        instantiate this class directly - instead see the methods\n        provided by :class:`~gridfs.GridFS`.\n\n        Raises :class:`TypeError` if `root_collection` is not an\n        instance of :class:`~pymongo.collection.Collection`.\n\n        Any of the file level options specified in the `GridFS Spec\n        <http://dochub.mongodb.org/core/gridfsspec>`_ may be passed as\n        keyword arguments. Any additional keyword arguments will be\n        set as additional fields on the file document. Valid keyword\n        arguments include:\n\n          - ``\"_id\"``: unique ID for this file (default:\n            :class:`~bson.objectid.ObjectId`) - this ``\"_id\"`` must\n            not have already been used for another file\n\n          - ``\"filename\"``: human name for the file\n\n          - ``\"contentType\"`` or ``\"content_type\"``: valid mime-type\n            for the file\n\n          - ``\"chunkSize\"`` or ``\"chunk_size\"``: size of each of the\n            chunks, in bytes (default: 255 kb)\n\n          - ``\"encoding\"``: encoding used for this file. In Python 2,\n            any :class:`unicode` that is written to the file will be\n            converted to a :class:`str`. In Python 3, any :class:`str`\n            that is written to the file will be converted to\n            :class:`bytes`.\n\n        :Parameters:\n          - `root_collection`: root collection to write to\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession` to use for all\n            commands\n          - `disable_md5` (optional): When True, an MD5 checksum will not be\n            computed for the uploaded file. Useful in environments where\n            MD5 cannot be used for regulatory or other reasons. Defaults to\n            False.\n          - `**kwargs` (optional): file level options (see above)\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.0\n           `root_collection` must use an acknowledged\n           :attr:`~pymongo.collection.Collection.write_concern`\n        \"\"\"\n        if not isinstance(root_collection, Collection):\n            raise TypeError(\"root_collection must be an \"\n                            \"instance of Collection\")\n\n        if not root_collection.write_concern.acknowledged:\n            raise ConfigurationError('root_collection must use '\n                                     'acknowledged write_concern')\n\n        # Handle alternative naming\n        if \"content_type\" in kwargs:\n            kwargs[\"contentType\"] = kwargs.pop(\"content_type\")\n        if \"chunk_size\" in kwargs:\n            kwargs[\"chunkSize\"] = kwargs.pop(\"chunk_size\")\n\n        coll = _clear_entity_type_registry(\n            root_collection, read_preference=ReadPreference.PRIMARY)\n\n        if not disable_md5:\n            kwargs[\"md5\"] = hashlib.md5()\n        # Defaults\n        kwargs[\"_id\"] = kwargs.get(\"_id\", ObjectId())\n        kwargs[\"chunkSize\"] = kwargs.get(\"chunkSize\", DEFAULT_CHUNK_SIZE)\n        object.__setattr__(self, \"_session\", session)\n        object.__setattr__(self, \"_coll\", coll)\n        object.__setattr__(self, \"_chunks\", coll.chunks)\n        object.__setattr__(self, \"_file\", kwargs)\n        object.__setattr__(self, \"_buffer\", StringIO())\n        object.__setattr__(self, \"_position\", 0)\n        object.__setattr__(self, \"_chunk_number\", 0)\n        object.__setattr__(self, \"_closed\", False)\n        object.__setattr__(self, \"_ensured_index\", False)\n\n    def __create_index(self, collection, index_key, unique):\n        doc = collection.find_one(projection={\"_id\": 1}, session=self._session)\n        if doc is None:\n            try:\n                index_keys = [index_spec['key'] for index_spec in\n                              collection.list_indexes(session=self._session)]\n            except OperationFailure:\n                index_keys = []\n            if index_key not in index_keys:\n                collection.create_index(\n                    index_key.items(), unique=unique, session=self._session)\n\n    def __ensure_indexes(self):\n        if not object.__getattribute__(self, \"_ensured_index\"):\n            self.__create_index(self._coll.files, _F_INDEX, False)\n            self.__create_index(self._coll.chunks, _C_INDEX, True)\n            object.__setattr__(self, \"_ensured_index\", True)\n\n    def abort(self):\n        \"\"\"Remove all chunks/files that may have been uploaded and close.\n        \"\"\"\n        self._coll.chunks.delete_many(\n            {\"files_id\": self._file['_id']}, session=self._session)\n        self._coll.files.delete_one(\n            {\"_id\": self._file['_id']}, session=self._session)\n        object.__setattr__(self, \"_closed\", True)\n\n    @property\n    def closed(self):\n        \"\"\"Is this file closed?\n        \"\"\"\n        return self._closed\n\n    _id = _grid_in_property(\"_id\", \"The ``'_id'`` value for this file.\",\n                            read_only=True)\n    filename = _grid_in_property(\"filename\", \"Name of this file.\")\n    name = _grid_in_property(\"filename\", \"Alias for `filename`.\")\n    content_type = _grid_in_property(\"contentType\", \"Mime-type for this file.\")\n    length = _grid_in_property(\"length\", \"Length (in bytes) of this file.\",\n                               closed_only=True)\n    chunk_size = _grid_in_property(\"chunkSize\", \"Chunk size for this file.\",\n                                   read_only=True)\n    upload_date = _grid_in_property(\"uploadDate\",\n                                    \"Date that this file was uploaded.\",\n                                    closed_only=True)\n    md5 = _grid_in_property(\"md5\", \"MD5 of the contents of this file \"\n                            \"if an md5 sum was created.\",\n                            closed_only=True)\n\n    def __getattr__(self, name):\n        if name in self._file:\n            return self._file[name]\n        raise AttributeError(\"GridIn object has no attribute '%s'\" % name)\n\n    def __setattr__(self, name, value):\n        # For properties of this instance like _buffer, or descriptors set on\n        # the class like filename, use regular __setattr__\n        if name in self.__dict__ or name in self.__class__.__dict__:\n            object.__setattr__(self, name, value)\n        else:\n            # All other attributes are part of the document in db.fs.files.\n            # Store them to be sent to server on close() or if closed, send\n            # them now.\n            self._file[name] = value\n            if self._closed:\n                self._coll.files.update_one({\"_id\": self._file[\"_id\"]},\n                                            {\"$set\": {name: value}})\n\n    def __flush_data(self, data):\n        \"\"\"Flush `data` to a chunk.\n        \"\"\"\n        self.__ensure_indexes()\n        if 'md5' in self._file:\n            self._file['md5'].update(data)\n\n        if not data:\n            return\n        assert(len(data) <= self.chunk_size)\n\n        chunk = {\"files_id\": self._file[\"_id\"],\n                 \"n\": self._chunk_number,\n                 \"data\": Binary(data)}\n\n        try:\n            self._chunks.insert_one(chunk, session=self._session)\n        except DuplicateKeyError:\n            self._raise_file_exists(self._file['_id'])\n        self._chunk_number += 1\n        self._position += len(data)\n\n    def __flush_buffer(self):\n        \"\"\"Flush the buffer contents out to a chunk.\n        \"\"\"\n        self.__flush_data(self._buffer.getvalue())\n        self._buffer.close()\n        self._buffer = StringIO()\n\n    def __flush(self):\n        \"\"\"Flush the file to the database.\n        \"\"\"\n        try:\n            self.__flush_buffer()\n\n            if \"md5\" in self._file:\n                self._file[\"md5\"] = self._file[\"md5\"].hexdigest()\n            # The GridFS spec says length SHOULD be an Int64.\n            self._file[\"length\"] = Int64(self._position)\n            self._file[\"uploadDate\"] = datetime.datetime.utcnow()\n\n            return self._coll.files.insert_one(\n                self._file, session=self._session)\n        except DuplicateKeyError:\n            self._raise_file_exists(self._id)\n\n    def _raise_file_exists(self, file_id):\n        \"\"\"Raise a FileExists exception for the given file_id.\"\"\"\n        raise FileExists(\"file with _id %r already exists\" % file_id)\n\n    def close(self):\n        \"\"\"Flush the file and close it.\n\n        A closed file cannot be written any more. Calling\n        :meth:`close` more than once is allowed.\n        \"\"\"\n        if not self._closed:\n            self.__flush()\n            object.__setattr__(self, \"_closed\", True)\n\n    def read(self, size=-1):\n        raise io.UnsupportedOperation('read')\n\n    def readable(self):\n        return False\n\n    def seekable(self):\n        return False\n\n    def write(self, data):\n        \"\"\"Write data to the file. There is no return value.\n\n        `data` can be either a string of bytes or a file-like object\n        (implementing :meth:`read`). If the file has an\n        :attr:`encoding` attribute, `data` can also be a\n        :class:`unicode` (:class:`str` in python 3) instance, which\n        will be encoded as :attr:`encoding` before being written.\n\n        Due to buffering, the data may not actually be written to the\n        database until the :meth:`close` method is called. Raises\n        :class:`ValueError` if this file is already closed. Raises\n        :class:`TypeError` if `data` is not an instance of\n        :class:`str` (:class:`bytes` in python 3), a file-like object,\n        or an instance of :class:`unicode` (:class:`str` in python 3).\n        Unicode data is only allowed if the file has an :attr:`encoding`\n        attribute.\n\n        :Parameters:\n          - `data`: string of bytes or file-like object to be written\n            to the file\n        \"\"\"\n        if self._closed:\n            raise ValueError(\"cannot write to a closed file\")\n\n        try:\n            # file-like\n            read = data.read\n        except AttributeError:\n            # string\n            if not isinstance(data, (text_type, bytes)):\n                raise TypeError(\"can only write strings or file-like objects\")\n            if isinstance(data, text_type):\n                try:\n                    data = data.encode(self.encoding)\n                except AttributeError:\n                    raise TypeError(\"must specify an encoding for file in \"\n                                    \"order to write %s\" % (text_type.__name__,))\n            read = StringIO(data).read\n\n        if self._buffer.tell() > 0:\n            # Make sure to flush only when _buffer is complete\n            space = self.chunk_size - self._buffer.tell()\n            if space:\n                try:\n                    to_write = read(space)\n                except:\n                    self.abort()\n                    raise\n                self._buffer.write(to_write)\n                if len(to_write) < space:\n                    return  # EOF or incomplete\n            self.__flush_buffer()\n        to_write = read(self.chunk_size)\n        while to_write and len(to_write) == self.chunk_size:\n            self.__flush_data(to_write)\n            to_write = read(self.chunk_size)\n        self._buffer.write(to_write)\n\n    def writelines(self, sequence):\n        \"\"\"Write a sequence of strings to the file.\n\n        Does not add seperators.\n        \"\"\"\n        for line in sequence:\n            self.write(line)\n\n    def writeable(self):\n        return True\n\n    def __enter__(self):\n        \"\"\"Support for the context manager protocol.\n        \"\"\"\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        \"\"\"Support for the context manager protocol.\n\n        Close the file and allow exceptions to propagate.\n        \"\"\"\n        self.close()\n\n        # propagate exceptions\n        return False\n\n\nclass GridOut(object):\n    \"\"\"Class to read data out of GridFS.\n    \"\"\"\n    def __init__(self, root_collection, file_id=None, file_document=None,\n                 session=None):\n        \"\"\"Read a file from GridFS\n\n        Application developers should generally not need to\n        instantiate this class directly - instead see the methods\n        provided by :class:`~gridfs.GridFS`.\n\n        Either `file_id` or `file_document` must be specified,\n        `file_document` will be given priority if present. Raises\n        :class:`TypeError` if `root_collection` is not an instance of\n        :class:`~pymongo.collection.Collection`.\n\n        :Parameters:\n          - `root_collection`: root collection to read from\n          - `file_id` (optional): value of ``\"_id\"`` for the file to read\n          - `file_document` (optional): file document from\n            `root_collection.files`\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession` to use for all\n            commands\n\n        .. versionchanged:: 3.8\n           For better performance and to better follow the GridFS spec,\n           :class:`GridOut` now uses a single cursor to read all the chunks in\n           the file.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.0\n           Creating a GridOut does not immediately retrieve the file metadata\n           from the server. Metadata is fetched when first needed.\n        \"\"\"\n        if not isinstance(root_collection, Collection):\n            raise TypeError(\"root_collection must be an \"\n                            \"instance of Collection\")\n\n        root_collection = _clear_entity_type_registry(root_collection)\n\n        self.__chunks = root_collection.chunks\n        self.__files = root_collection.files\n        self.__file_id = file_id\n        self.__buffer = EMPTY\n        self.__chunk_iter = None\n        self.__position = 0\n        self._file = file_document\n        self._session = session\n\n    _id = _grid_out_property(\"_id\", \"The ``'_id'`` value for this file.\")\n    filename = _grid_out_property(\"filename\", \"Name of this file.\")\n    name = _grid_out_property(\"filename\", \"Alias for `filename`.\")\n    content_type = _grid_out_property(\"contentType\", \"Mime-type for this file.\")\n    length = _grid_out_property(\"length\", \"Length (in bytes) of this file.\")\n    chunk_size = _grid_out_property(\"chunkSize\", \"Chunk size for this file.\")\n    upload_date = _grid_out_property(\"uploadDate\",\n                                     \"Date that this file was first uploaded.\")\n    aliases = _grid_out_property(\"aliases\", \"List of aliases for this file.\")\n    metadata = _grid_out_property(\"metadata\", \"Metadata attached to this file.\")\n    md5 = _grid_out_property(\"md5\", \"MD5 of the contents of this file \"\n                             \"if an md5 sum was created.\")\n\n    def _ensure_file(self):\n        if not self._file:\n            self._file = self.__files.find_one({\"_id\": self.__file_id},\n                                               session=self._session)\n            if not self._file:\n                raise NoFile(\"no file in gridfs collection %r with _id %r\" %\n                             (self.__files, self.__file_id))\n\n    def __getattr__(self, name):\n        self._ensure_file()\n        if name in self._file:\n            return self._file[name]\n        raise AttributeError(\"GridOut object has no attribute '%s'\" % name)\n\n    def readable(self):\n        return True\n\n    def readchunk(self):\n        \"\"\"Reads a chunk at a time. If the current position is within a\n        chunk the remainder of the chunk is returned.\n        \"\"\"\n        received = len(self.__buffer)\n        chunk_data = EMPTY\n        chunk_size = int(self.chunk_size)\n\n        if received > 0:\n            chunk_data = self.__buffer\n        elif self.__position < int(self.length):\n            chunk_number = int((received + self.__position) / chunk_size)\n            if self.__chunk_iter is None:\n                self.__chunk_iter = _GridOutChunkIterator(\n                    self, self.__chunks, self._session, chunk_number)\n\n            chunk = self.__chunk_iter.next()\n            chunk_data = chunk[\"data\"][self.__position % chunk_size:]\n\n            if not chunk_data:\n                raise CorruptGridFile(\"truncated chunk\")\n\n        self.__position += len(chunk_data)\n        self.__buffer = EMPTY\n        return chunk_data\n\n    def read(self, size=-1):\n        \"\"\"Read at most `size` bytes from the file (less if there\n        isn't enough data).\n\n        The bytes are returned as an instance of :class:`str` (:class:`bytes`\n        in python 3). If `size` is negative or omitted all data is read.\n\n        :Parameters:\n          - `size` (optional): the number of bytes to read\n\n        .. versionchanged:: 3.8\n           This method now only checks for extra chunks after reading the\n           entire file. Previously, this method would check for extra chunks\n           on every call.\n        \"\"\"\n        self._ensure_file()\n\n        remainder = int(self.length) - self.__position\n        if size < 0 or size > remainder:\n            size = remainder\n\n        if size == 0:\n            return EMPTY\n\n        received = 0\n        data = StringIO()\n        while received < size:\n            chunk_data = self.readchunk()\n            received += len(chunk_data)\n            data.write(chunk_data)\n\n        # Detect extra chunks after reading the entire file.\n        if size == remainder and self.__chunk_iter:\n            try:\n                self.__chunk_iter.next()\n            except StopIteration:\n                pass\n\n        self.__position -= received - size\n\n        # Return 'size' bytes and store the rest.\n        data.seek(size)\n        self.__buffer = data.read()\n        data.seek(0)\n        return data.read(size)\n\n    def readline(self, size=-1):\n        \"\"\"Read one line or up to `size` bytes from the file.\n\n        :Parameters:\n         - `size` (optional): the maximum number of bytes to read\n        \"\"\"\n        remainder = int(self.length) - self.__position\n        if size < 0 or size > remainder:\n            size = remainder\n\n        if size == 0:\n            return EMPTY\n\n        received = 0\n        data = StringIO()\n        while received < size:\n            chunk_data = self.readchunk()\n            pos = chunk_data.find(NEWLN, 0, size)\n            if pos != -1:\n                size = received + pos + 1\n\n            received += len(chunk_data)\n            data.write(chunk_data)\n            if pos != -1:\n                break\n\n        self.__position -= received - size\n\n        # Return 'size' bytes and store the rest.\n        data.seek(size)\n        self.__buffer = data.read()\n        data.seek(0)\n        return data.read(size)\n\n    def tell(self):\n        \"\"\"Return the current position of this file.\n        \"\"\"\n        return self.__position\n\n    def seek(self, pos, whence=_SEEK_SET):\n        \"\"\"Set the current position of this file.\n\n        :Parameters:\n         - `pos`: the position (or offset if using relative\n           positioning) to seek to\n         - `whence` (optional): where to seek\n           from. :attr:`os.SEEK_SET` (``0``) for absolute file\n           positioning, :attr:`os.SEEK_CUR` (``1``) to seek relative\n           to the current position, :attr:`os.SEEK_END` (``2``) to\n           seek relative to the file's end.\n        \"\"\"\n        if whence == _SEEK_SET:\n            new_pos = pos\n        elif whence == _SEEK_CUR:\n            new_pos = self.__position + pos\n        elif whence == _SEEK_END:\n            new_pos = int(self.length) + pos\n        else:\n            raise IOError(22, \"Invalid value for `whence`\")\n\n        if new_pos < 0:\n            raise IOError(22, \"Invalid value for `pos` - must be positive\")\n\n        # Optimization, continue using the same buffer and chunk iterator.\n        if new_pos == self.__position:\n            return\n\n        self.__position = new_pos\n        self.__buffer = EMPTY\n        if self.__chunk_iter:\n            self.__chunk_iter.close()\n            self.__chunk_iter = None\n\n    def seekable(self):\n        return True\n\n    def __iter__(self):\n        \"\"\"Return an iterator over all of this file's data.\n\n        The iterator will return chunk-sized instances of\n        :class:`str` (:class:`bytes` in python 3). This can be\n        useful when serving files using a webserver that handles\n        such an iterator efficiently.\n\n        .. note::\n           This is different from :py:class:`io.IOBase` which iterates over\n           *lines* in the file. Use :meth:`GridOut.readline` to read line by\n           line instead of chunk by chunk.\n\n        .. versionchanged:: 3.8\n           The iterator now raises :class:`CorruptGridFile` when encountering\n           any truncated, missing, or extra chunk in a file. The previous\n           behavior was to only raise :class:`CorruptGridFile` on a missing\n           chunk.\n        \"\"\"\n        return GridOutIterator(self, self.__chunks, self._session)\n\n    def close(self):\n        \"\"\"Make GridOut more generically file-like.\"\"\"\n        if self.__chunk_iter:\n            self.__chunk_iter.close()\n            self.__chunk_iter = None\n\n    def write(self, value):\n        raise io.UnsupportedOperation('write')\n\n    def __enter__(self):\n        \"\"\"Makes it possible to use :class:`GridOut` files\n        with the context manager protocol.\n        \"\"\"\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        \"\"\"Makes it possible to use :class:`GridOut` files\n        with the context manager protocol.\n        \"\"\"\n        self.close()\n        return False\n\n\nclass _GridOutChunkIterator(object):\n    \"\"\"Iterates over a file's chunks using a single cursor.\n\n    Raises CorruptGridFile when encountering any truncated, missing, or extra\n    chunk in a file.\n    \"\"\"\n    def __init__(self, grid_out, chunks, session, next_chunk):\n        self._id = grid_out._id\n        self._chunk_size = int(grid_out.chunk_size)\n        self._length = int(grid_out.length)\n        self._chunks = chunks\n        self._session = session\n        self._next_chunk = next_chunk\n        self._num_chunks = math.ceil(float(self._length) / self._chunk_size)\n        self._cursor = None\n\n    def expected_chunk_length(self, chunk_n):\n        if chunk_n < self._num_chunks - 1:\n            return self._chunk_size\n        return self._length - (self._chunk_size * (self._num_chunks - 1))\n\n    def __iter__(self):\n        return self\n\n    def _create_cursor(self):\n        filter = {\"files_id\": self._id}\n        if self._next_chunk > 0:\n            filter[\"n\"] = {\"$gte\": self._next_chunk}\n        self._cursor = self._chunks.find(filter, sort=[(\"n\", 1)],\n                                         session=self._session)\n\n    def _next_with_retry(self):\n        \"\"\"Return the next chunk and retry once on CursorNotFound.\n\n        We retry on CursorNotFound to maintain backwards compatibility in\n        cases where two calls to read occur more than 10 minutes apart (the\n        server's default cursor timeout).\n        \"\"\"\n        if self._cursor is None:\n            self._create_cursor()\n\n        try:\n            return self._cursor.next()\n        except CursorNotFound:\n            self._cursor.close()\n            self._create_cursor()\n            return self._cursor.next()\n\n    def next(self):\n        try:\n            chunk = self._next_with_retry()\n        except StopIteration:\n            if self._next_chunk >= self._num_chunks:\n                raise\n            raise CorruptGridFile(\"no chunk #%d\" % self._next_chunk)\n\n        if chunk[\"n\"] != self._next_chunk:\n            self.close()\n            raise CorruptGridFile(\n                \"Missing chunk: expected chunk #%d but found \"\n                \"chunk with n=%d\" % (self._next_chunk, chunk[\"n\"]))\n\n        if chunk[\"n\"] >= self._num_chunks:\n            # According to spec, ignore extra chunks if they are empty.\n            if len(chunk[\"data\"]):\n                self.close()\n                raise CorruptGridFile(\n                    \"Extra chunk found: expected %d chunks but found \"\n                    \"chunk with n=%d\" % (self._num_chunks, chunk[\"n\"]))\n\n        expected_length = self.expected_chunk_length(chunk[\"n\"])\n        if len(chunk[\"data\"]) != expected_length:\n            self.close()\n            raise CorruptGridFile(\n                \"truncated chunk #%d: expected chunk length to be %d but \"\n                \"found chunk with length %d\" % (\n                    chunk[\"n\"], expected_length, len(chunk[\"data\"])))\n\n        self._next_chunk += 1\n        return chunk\n\n    __next__ = next\n\n    def close(self):\n        if self._cursor:\n            self._cursor.close()\n            self._cursor = None\n\n\nclass GridOutIterator(object):\n    def __init__(self, grid_out, chunks, session):\n        self.__chunk_iter = _GridOutChunkIterator(grid_out, chunks, session, 0)\n\n    def __iter__(self):\n        return self\n\n    def next(self):\n        chunk = self.__chunk_iter.next()\n        return bytes(chunk[\"data\"])\n\n    __next__ = next\n\n\nclass GridOutCursor(Cursor):\n    \"\"\"A cursor / iterator for returning GridOut objects as the result\n    of an arbitrary query against the GridFS files collection.\n    \"\"\"\n    def __init__(self, collection, filter=None, skip=0, limit=0,\n                 no_cursor_timeout=False, sort=None, batch_size=0,\n                 session=None):\n        \"\"\"Create a new cursor, similar to the normal\n        :class:`~pymongo.cursor.Cursor`.\n\n        Should not be called directly by application developers - see\n        the :class:`~gridfs.GridFS` method :meth:`~gridfs.GridFS.find` instead.\n\n        .. versionadded 2.7\n\n        .. mongodoc:: cursors\n        \"\"\"\n        collection = _clear_entity_type_registry(collection)\n\n        # Hold on to the base \"fs\" collection to create GridOut objects later.\n        self.__root_collection = collection\n\n        super(GridOutCursor, self).__init__(\n            collection.files, filter, skip=skip, limit=limit,\n            no_cursor_timeout=no_cursor_timeout, sort=sort,\n            batch_size=batch_size, session=session)\n\n    def next(self):\n        \"\"\"Get next GridOut object from cursor.\n        \"\"\"\n        # Work around \"super is not iterable\" issue in Python 3.x\n        next_file = super(GridOutCursor, self).next()\n        return GridOut(self.__root_collection, file_document=next_file,\n                       session=self.session)\n\n    __next__ = next\n\n    def add_option(self, *args, **kwargs):\n        raise NotImplementedError(\"Method does not exist for GridOutCursor\")\n\n    def remove_option(self, *args, **kwargs):\n        raise NotImplementedError(\"Method does not exist for GridOutCursor\")\n\n    def _clone_base(self, session):\n        \"\"\"Creates an empty GridOutCursor for information to be copied into.\n        \"\"\"\n        return GridOutCursor(self.__root_collection, session=session)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/__init__.py",
    "content": "from __future__ import absolute_import\nfrom hamcrest.core import *\nfrom hamcrest.library import *\n\n__version__ = \"1.9.0\"\n__author__ = \"Chris Rose\"\n__copyright__ = \"Copyright 2015 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/__init__.py",
    "content": "from __future__ import absolute_import\nfrom hamcrest.core.assert_that import assert_that\nfrom hamcrest.core.core import *\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/assert_that.py",
    "content": "from __future__ import absolute_import\nfrom hamcrest.core.matcher import Matcher\nfrom hamcrest.core.string_description import StringDescription\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n# unittest integration; hide these frames from tracebacks\n__unittest = True\n# py.test integration; hide these frames from tracebacks\n__tracebackhide__ = True\n\ndef assert_that(arg1, arg2=None, arg3=''):\n    \"\"\"Asserts that actual value satisfies matcher. (Can also assert plain\n    boolean condition.)\n\n    :param actual: The object to evaluate as the actual value.\n    :param matcher: The matcher to satisfy as the expected condition.\n    :param reason: Optional explanation to include in failure description.\n\n    ``assert_that`` passes the actual value to the matcher for evaluation. If\n    the matcher is not satisfied, an exception is thrown describing the\n    mismatch.\n\n    ``assert_that`` is designed to integrate well with PyUnit and other unit\n    testing frameworks. The exception raised for an unmet assertion is an\n    :py:exc:`AssertionError`, which PyUnit reports as a test failure.\n\n    With a different set of parameters, ``assert_that`` can also verify a\n    boolean condition:\n\n    .. function:: assert_that(assertion[, reason])\n\n    :param assertion:  Boolean condition to verify.\n    :param reason:  Optional explanation to include in failure description.\n\n    This is equivalent to the :py:meth:`~unittest.TestCase.assertTrue` method\n    of :py:class:`unittest.TestCase`, but offers greater flexibility in test\n    writing by being a standalone function.\n\n    \"\"\"\n    if isinstance(arg2, Matcher):\n        _assert_match(actual=arg1, matcher=arg2, reason=arg3)\n    else:\n        _assert_bool(assertion=arg1, reason=arg2)\n\n\ndef _assert_match(actual, matcher, reason):\n    if not matcher.matches(actual):\n        description = StringDescription()\n        description.append_text(reason)             \\\n                   .append_text('\\nExpected: ')     \\\n                   .append_description_of(matcher)  \\\n                   .append_text('\\n     but: ')\n        matcher.describe_mismatch(actual, description)\n        description.append_text('\\n')\n        raise AssertionError(description)\n\n\ndef _assert_bool(assertion, reason=None):\n    if not assertion:\n        if not reason:\n            reason = 'Assertion failed'\n        raise AssertionError(reason)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/base_description.py",
    "content": "from __future__ import absolute_import\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nimport warnings\nimport six\n\nfrom hamcrest.core.description import Description\nfrom hamcrest.core.selfdescribingvalue import SelfDescribingValue\nfrom hamcrest.core.helpers.hasmethod import hasmethod\n\nclass BaseDescription(Description):\n    \"\"\"Base class for all :py:class:`~hamcrest.core.description.Description`\n    implementations.\n\n    \"\"\"\n\n    def append_text(self, text):\n        self.append(text)\n        return self\n\n    def append_description_of(self, value):\n        if hasmethod(value, 'describe_to'):\n            value.describe_to(self)\n        elif six.PY3 and isinstance(value, six.text_type):\n            self.append(repr(value))\n        elif six.PY2 and isinstance(value, six.binary_type):\n            self.append_string_in_python_syntax(value)\n        elif isinstance(value, six.text_type):\n            self.append_string_in_python_syntax(value)\n        else:\n            description = str(value)\n            if description[:1] == '<' and description[-1:] == '>':\n                self.append(description)\n            else:\n                self.append('<')\n                self.append(description)\n                self.append('>')\n        return self\n\n    def append_value(self, value):\n        warnings.warn('Call append_description_of instead of append_value',\n                      DeprecationWarning)\n        if isinstance(value, str):\n            self.append_string_in_python_syntax(value)\n        else:\n            self.append('<')\n            self.append(str(value))\n            self.append('>')\n        return self\n\n    def append_value_list(self, start, separator, end, list):\n        warnings.warn('Call append_list instead of append_value_list',\n                      DeprecationWarning)\n        return self.append_list(start, separator, end,\n                                map(SelfDescribingValue, list))\n\n    def append_list(self, start, separator, end, list):\n        separate = False\n\n        self.append(start)\n        for item in list:\n            if separate:\n                self.append(separator)\n            self.append_description_of(item)\n            separate = True\n        self.append(end)\n        return self\n\n    def append(self, string):\n        \"\"\"Append the string to the description.\"\"\"\n        raise NotImplementedError('append')\n\n    def append_string_in_python_syntax(self, string):\n        self.append(\"'\")\n        for ch in string:\n            self.append(character_in_python_syntax(ch))\n        self.append(\"'\")\n\n\ndef character_in_python_syntax(ch):\n    if ch == \"'\":\n        return \"\\'\"\n    elif ch == '\\n':\n        return '\\\\n'\n    elif ch == '\\r':\n        return '\\\\r'\n    elif ch == '\\t':\n        return '\\\\t'\n    else:\n        return ch\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/base_matcher.py",
    "content": "from __future__ import absolute_import\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nfrom hamcrest.core.matcher import Matcher\nfrom hamcrest.core.string_description import tostring\n\n\nclass BaseMatcher(Matcher):\n    \"\"\"Base class for all :py:class:`~hamcrest.core.matcher.Matcher`\n    implementations.\n\n    Most implementations can just implement :py:obj:`_matches`, leaving the\n    handling of any mismatch description to the ``matches`` method. But if it\n    makes more sense to generate the mismatch description during the matching,\n    override :py:meth:`~hamcrest.core.matcher.Matcher.matches` instead.\n\n    \"\"\"\n\n    def __str__(self):\n        return tostring(self)\n\n    def _matches(self, item):\n        raise NotImplementedError('_matches')\n\n    def matches(self, item, mismatch_description=None):\n        match_result = self._matches(item)\n        if not match_result and mismatch_description:\n            self.describe_mismatch(item, mismatch_description)\n        return match_result\n\n    def describe_mismatch(self, item, mismatch_description):\n        mismatch_description.append_text('was ').append_description_of(item)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/compat.py",
    "content": "__author__ = \"Per Fagrell\"\n__copyright__ = \"Copyright 2013 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n__all__ = ['is_callable']\n\nimport sys\n\n# callable was not part of py3k until 3.2, so we create this\n# generic is_callable to use callable if possible, otherwise\n# we use generic homebrew.\nif sys.version_info[0] == 3 and sys.version_info[1] < 2:\n    def is_callable(function):\n        \"\"\"Return whether the object is callable (i.e., some kind of function).\"\"\"\n        if function is None:\n            return False\n        return any(\"__call__\" in klass.__dict__ for klass in type(function).__mro__)\nelse:\n    is_callable = callable\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/core/__init__.py",
    "content": "from __future__ import absolute_import\n\"\"\"Fundamental matchers of objects and values, and composite matchers.\"\"\"\n\nfrom hamcrest.core.core.allof import all_of\nfrom hamcrest.core.core.anyof import any_of\nfrom hamcrest.core.core.described_as import described_as\nfrom hamcrest.core.core.is_ import is_\nfrom hamcrest.core.core.isanything import anything\nfrom hamcrest.core.core.isequal import equal_to\nfrom hamcrest.core.core.isinstanceof import instance_of\nfrom hamcrest.core.core.isnone import none, not_none\nfrom hamcrest.core.core.isnot import is_not, not_\nfrom hamcrest.core.core.issame import same_instance\nfrom hamcrest.core.core.raises import calling, raises\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/core/allof.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass AllOf(BaseMatcher):\n\n    def __init__(self, *matchers):\n        self.matchers = matchers\n\n    def matches(self, item, mismatch_description=None):\n        for matcher in self.matchers:\n            if not matcher.matches(item):\n                if mismatch_description:\n                    mismatch_description.append_description_of(matcher) \\\n                                        .append_text(' ')\n                    matcher.describe_mismatch(item, mismatch_description)\n                return False\n        return True\n\n    def describe_mismatch(self, item, mismatch_description):\n        self.matches(item, mismatch_description)\n\n    def describe_to(self, description):\n        description.append_list('(', ' and ', ')', self.matchers)\n\n\ndef all_of(*items):\n    \"\"\"Matches if all of the given matchers evaluate to ``True``.\n\n    :param matcher1,...:  A comma-separated list of matchers.\n\n    The matchers are evaluated from left to right using short-circuit\n    evaluation, so evaluation stops as soon as a matcher returns ``False``.\n\n    Any argument that is not a matcher is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    \"\"\"\n    return AllOf(*[wrap_matcher(item) for item in items])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/core/anyof.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass AnyOf(BaseMatcher):\n\n    def __init__(self, *matchers):\n        self.matchers = matchers\n\n    def _matches(self, item):\n        for matcher in self.matchers:\n            if matcher.matches(item):\n                return True\n        return False\n\n    def describe_to(self, description):\n        description.append_list('(', ' or ', ')', self.matchers)\n\n\ndef any_of(*items):\n    \"\"\"Matches if any of the given matchers evaluate to ``True``.\n\n    :param matcher1,...:  A comma-separated list of matchers.\n\n    The matchers are evaluated from left to right using short-circuit\n    evaluation, so evaluation stops as soon as a matcher returns ``True``.\n\n    Any argument that is not a matcher is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    \"\"\"\n    return AnyOf(*[wrap_matcher(item) for item in items])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/core/described_as.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nimport re\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nARG_PATTERN = re.compile('%([0-9]+)')\n\n\nclass DescribedAs(BaseMatcher):\n\n    def __init__(self, description_template, matcher, *values):\n        self.template = description_template\n        self.matcher = matcher\n        self.values = values\n\n    def matches(self, item, mismatch_description=None):\n        return self.matcher.matches(item, mismatch_description)\n\n    def describe_mismatch(self, item, mismatch_description):\n        self.matcher.describe_mismatch(item, mismatch_description)\n\n    def describe_to(self, description):\n        text_start = 0\n        for match in re.finditer(ARG_PATTERN, self.template):\n            description.append_text(self.template[text_start:match.start()])\n            arg_index = int(match.group()[1:])\n            description.append_description_of(self.values[arg_index])\n            text_start = match.end()\n\n        if text_start < len(self.template):\n            description.append_text(self.template[text_start:])\n\n\ndef described_as(description, matcher, *values):\n    \"\"\"Adds custom failure description to a given matcher.\n\n    :param description: Overrides the matcher's description.\n    :param matcher: The matcher to satisfy.\n    :param value1,...: Optional comma-separated list of substitution values.\n\n    The description may contain substitution placeholders %0, %1, etc. These\n    will be replaced by any values that follow the matcher.\n\n    \"\"\"\n    return DescribedAs(description, matcher, *values)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/core/is_.py",
    "content": "from __future__ import absolute_import\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nfrom hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher, is_matchable_type\nfrom .isinstanceof import instance_of\n\n\nclass Is(BaseMatcher):\n\n    def __init__(self, matcher):\n        self.matcher = matcher\n\n    def matches(self, item, mismatch_description=None):\n        return self.matcher.matches(item, mismatch_description)\n\n    def describe_mismatch(self, item, mismatch_description):\n        return self.matcher.describe_mismatch(item, mismatch_description)\n\n    def describe_to(self, description):\n        description.append_description_of(self.matcher)\n\n\ndef wrap_value_or_type(x):\n    if is_matchable_type(x):\n        return instance_of(x)\n    else:\n        return wrap_matcher(x)\n\n\ndef is_(x):\n    \"\"\"Decorates another matcher, or provides shortcuts to the frequently used\n    ``is(equal_to(x))`` and ``is(instance_of(x))``.\n\n    :param x: The matcher to satisfy,  or a type for\n        :py:func:`~hamcrest.core.core.isinstanceof.instance_of` matching, or an\n        expected value for :py:func:`~hamcrest.core.core.isequal.equal_to`\n        matching.\n\n    This matcher compares the evaluated object to the given matcher.\n\n    .. note::\n\n        PyHamcrest's ``is_`` matcher is unrelated to Python's ``is`` operator.\n        The matcher for object identity is\n        :py:func:`~hamcrest.core.core.issame.same_instance`.\n\n    If the ``x`` argument is a matcher, its behavior is retained, but the test\n    may be more expressive. For example::\n\n        assert_that(value, less_than(5))\n        assert_that(value, is_(less_than(5)))\n\n    If the ``x`` argument is a type, it is wrapped in an\n    :py:func:`~hamcrest.core.core.isinstanceof.instance_of` matcher. This makes\n    the following statements equivalent::\n\n        assert_that(cheese, instance_of(Cheddar))\n        assert_that(cheese, is_(instance_of(Cheddar)))\n        assert_that(cheese, is_(Cheddar))\n\n    Otherwise, if the ``x`` argument is not a matcher, it is wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher. This makes the\n    following statements equivalent::\n\n        assert_that(cheese, equal_to(smelly))\n        assert_that(cheese, is_(equal_to(smelly)))\n        assert_that(cheese, is_(smelly))\n\n    Choose the style that makes your expression most readable. This will vary\n    depending on context.\n\n    \"\"\"\n    return Is(wrap_value_or_type(x))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/core/isanything.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass IsAnything(BaseMatcher):\n\n    def __init__(self, description):\n        self.description = description\n        if not description:\n            self.description = 'ANYTHING'\n\n    def _matches(self, item):\n        return True\n\n    def describe_to(self, description):\n        description.append_text(self.description)\n\n\ndef anything(description=None):\n    \"\"\"Matches anything.\n\n    :param description: Optional string used to describe this matcher.\n\n    This matcher always evaluates to ``True``. Specify this in composite\n    matchers when the value of a particular element is unimportant.\n\n    \"\"\"\n    return IsAnything(description)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/core/isequal.py",
    "content": "__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nfrom hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.matcher import Matcher\n\n\nclass IsEqual(BaseMatcher):\n\n    def __init__(self, equals):\n        self.object = equals\n\n    def _matches(self, item):\n        return item == self.object\n\n    def describe_to(self, description):\n        nested_matcher = isinstance(self.object, Matcher)\n        if nested_matcher:\n            description.append_text('<')\n        description.append_description_of(self.object)\n        if nested_matcher:\n            description.append_text('>')\n\n\ndef equal_to(obj):\n    \"\"\"Matches if object is equal to a given object.\n\n    :param obj: The object to compare against as the expected value.\n\n    This matcher compares the evaluated object to ``obj`` for equality.\"\"\"\n    return IsEqual(obj)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/core/isinstanceof.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.wrap_matcher import is_matchable_type\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nimport types\n\nclass IsInstanceOf(BaseMatcher):\n\n    def __init__(self, expected_type):\n        if not is_matchable_type(expected_type):\n            raise TypeError('IsInstanceOf requires type or a tuple of classes and types')\n        self.expected_type = expected_type\n\n    def _matches(self, item):\n        return isinstance(item, self.expected_type)\n\n    def describe_to(self, description):\n        try:\n            type_description = self.expected_type.__name__\n        except AttributeError:\n            type_description = \"one of %s\" % \",\".join(str(e) for e in self.expected_type)\n        description.append_text('an instance of ')              \\\n                    .append_text(type_description)\n\n\ndef instance_of(atype):\n    \"\"\"Matches if object is an instance of, or inherits from, a given type.\n\n    :param atype: The type to compare against as the expected type or a tuple\n        of types.\n\n    This matcher checks whether the evaluated object is an instance of\n    ``atype`` or an instance of any class that inherits from ``atype``.\n\n    Example::\n\n        instance_of(str)\n\n    \"\"\"\n    return IsInstanceOf(atype)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/core/isnone.py",
    "content": "from __future__ import absolute_import\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nfrom hamcrest.core.base_matcher import BaseMatcher\nfrom .isnot import is_not\n\n\nclass IsNone(BaseMatcher):\n\n    def _matches(self, item):\n        return item is None\n\n    def describe_to(self, description):\n        description.append_text('None')\n\n\ndef none():\n    \"\"\"Matches if object is ``None``.\"\"\"\n    return IsNone()\n\n\ndef not_none():\n    \"\"\"Matches if object is not ``None``.\"\"\"\n    return is_not(none())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/core/isnot.py",
    "content": "from __future__ import absolute_import\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nfrom hamcrest.core.base_matcher import BaseMatcher, Matcher\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher, is_matchable_type\nfrom .isequal import equal_to\nfrom .isinstanceof import instance_of\n\n\nclass IsNot(BaseMatcher):\n\n    def __init__(self, matcher):\n        self.matcher = matcher\n\n    def _matches(self, item):\n        return not self.matcher.matches(item)\n\n    def describe_to(self, description):\n        description.append_text('not ').append_description_of(self.matcher)\n\n\ndef wrap_value_or_type(x):\n    if is_matchable_type(x):\n        return instance_of(x)\n    else:\n        return wrap_matcher(x)\n\n\ndef is_not(match):\n    \"\"\"Inverts the given matcher to its logical negation.\n\n    :param match: The matcher to negate.\n\n    This matcher compares the evaluated object to the negation of the given\n    matcher. If the ``match`` argument is not a matcher, it is implicitly\n    wrapped in an :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to\n    check for equality, and thus matches for inequality.\n\n    Examples::\n\n        assert_that(cheese, is_not(equal_to(smelly)))\n        assert_that(cheese, is_not(smelly))\n\n    \"\"\"\n    return IsNot(wrap_value_or_type(match))\n\ndef not_(match):\n    \"\"\"Alias of :py:func:`is_not` for better readability of negations.\n\n    Examples::\n\n        assert_that(alist, not_(has_item(item)))\n\n    \"\"\"\n    return is_not(match)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/core/issame.py",
    "content": "__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nfrom hamcrest.core.base_matcher import BaseMatcher\n\n\nclass IsSame(BaseMatcher):\n\n    def __init__(self, object):\n        self.object = object\n\n    def _matches(self, item):\n        return item is self.object\n\n    def describe_to(self, description):\n        description.append_text('same instance as ')            \\\n                   .append_text(hex(id(self.object)))           \\\n                   .append_text(' ')                            \\\n                   .append_description_of(self.object)\n\n    def describe_mismatch(self, item, mismatch_description):\n        mismatch_description.append_text('was ')\n        if item is not None:\n            mismatch_description.append_text(hex(id(item)))         \\\n                                .append_text(' ')\n        mismatch_description.append_description_of(item)\n\n\ndef same_instance(obj):\n    \"\"\"Matches if evaluated object is the same instance as a given object.\n\n    :param obj: The object to compare against as the expected value.\n\n    This matcher invokes the ``is`` identity operator to determine if the\n    evaluated object is the the same object as ``obj``.\n\n    \"\"\"\n    return IsSame(obj)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/core/raises.py",
    "content": "from weakref import ref\nimport re\nimport sys\nfrom hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.compat import is_callable\n\n__author__ = \"Per Fagrell\"\n__copyright__ = \"Copyright 2013 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass Raises(BaseMatcher):\n    def __init__(self, expected, pattern=None):\n        self.pattern = pattern\n        self.expected = expected\n        self.actual = None\n        self.function = None\n\n    def _matches(self, function):\n        if not is_callable(function):\n            return False\n\n        self.function = ref(function)\n        return self._call_function(function)\n\n    def _call_function(self, function):\n        self.actual = None\n        try:\n            function()\n        except Exception:\n            self.actual = sys.exc_info()[1]\n\n            if isinstance(self.actual, self.expected):\n                if self.pattern is not None:\n                    return re.search(self.pattern, str(self.actual)) is not None\n                return True\n        return False\n\n    def describe_to(self, description):\n        description.append_text('Expected a callable raising %s' % self.expected)\n\n    def describe_mismatch(self, item, description):\n        if not is_callable(item):\n            description.append_text('%s is not callable' % item)\n            return\n\n        function = None if self.function is None else self.function()\n        if function is None or function is not item:\n            self.function = ref(item)\n            if not self._call_function(item):\n                return\n\n        if self.actual is None:\n            description.append_text('No exception raised.')\n        elif isinstance(self.actual, self.expected) and self.pattern is not None:\n            description.append_text('Correct assertion type raised, but the expected pattern (\"%s\") not found.' % self.pattern)\n            description.append_text('\\n          message was: \"%s\"' % str(self.actual))\n        else:\n            description.append_text('%s was raised instead' % type(self.actual))\n\n\ndef raises(exception, pattern=None):\n    \"\"\"Matches if the called function raised the expected exception.\n\n    :param exception:  The class of the expected exception\n    :param pattern:    Optional regular expression to match exception message.\n\n    Expects the actual to be wrapped by using :py:func:`~hamcrest.core.core.raises.calling`,\n    or a callable taking no arguments.\n    Optional argument pattern should be a string containing a regular expression.  If provided,\n    the string representation of the actual exception - e.g. `str(actual)` - must match pattern.\n\n    Examples::\n\n        assert_that(calling(int).with_args('q'), raises(TypeError))\n        assert_that(calling(parse, broken_input), raises(ValueError))\n    \"\"\"\n    return Raises(exception, pattern)\n\n\nclass DeferredCallable(object):\n    def __init__(self, func):\n        self.func = func\n        self.args = tuple()\n        self.kwargs = {}\n\n    def __call__(self):\n        return self.func(*self.args, **self.kwargs)\n\n    def with_args(self, *args, **kwargs):\n        self.args = args\n        self.kwargs = kwargs\n        return self\n\n\ndef calling(func):\n    \"\"\"Wrapper for function call that delays the actual execution so that\n    :py:func:`~hamcrest.core.core.raises.raises` matcher can catch any thrown exception.\n\n    :param func: The function or method to be called\n\n    The arguments can be provided with a call to the `with_args` function on the returned\n    object::\n\n           calling(my_method).with_args(arguments, and_='keywords')\n    \"\"\"\n    return DeferredCallable(func)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/description.py",
    "content": "__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass Description(object):\n    \"\"\"A description of a :py:class:`~hamcrest.core.matcher.Matcher`.\n\n    A :py:class:`~hamcrest.core.matcher.Matcher` will describe itself to a\n    description which can later be used for reporting.\n\n    \"\"\"\n\n    def append_text(self, text):\n        \"\"\"Appends some plain text to the description.\n\n        :returns: ``self``, for chaining\n\n        \"\"\"\n        raise NotImplementedError('append_text')\n\n    def append_description_of(self, value):\n        \"\"\"Appends description of given value to this description.\n\n        If the value implements\n        :py:meth:`~hamcrest.core.selfdescribing.SelfDescribing.describe_to`,\n        then it will be used.\n\n        :returns: ``self``, for chaining\n\n        \"\"\"\n        raise NotImplementedError('append_description_of')\n\n    def append_value(self, value):\n        \"\"\"Appends an arbitary value to the description.\n\n        **Deprecated:** Call\n        :py:meth:`~hamcrest.core.description.Description.append_description_of`\n        instead.\n\n        :returns: ``self``, for chaining\n\n        \"\"\"\n        raise NotImplementedError('append_value')\n\n    def append_list(self, start, separator, end, list):\n        \"\"\"Appends a list of objects to the description.\n\n        :param start: String that will begin the list description.\n        :param separator: String that will separate each object in the\n            description.\n        :param end: String that will end the list description.\n        :param list: List of objects to be described.\n\n        :returns: ``self``, for chaining\n\n        \"\"\"\n        raise NotImplementedError('append_list')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/helpers/__init__.py",
    "content": "\"\"\"Utilities for writing Matchers.\"\"\"\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/helpers/hasmethod.py",
    "content": "__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\ndef hasmethod(obj, methodname):\n    \"\"\"Does ``obj`` have a method named ``methodname``?\"\"\"\n\n    if not hasattr(obj, methodname):\n        return False\n    method = getattr(obj, methodname)\n    return callable(method)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/helpers/wrap_matcher.py",
    "content": "import six\n\nfrom hamcrest.core.base_matcher import Matcher\nfrom hamcrest.core.core.isequal import equal_to\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nimport types\n\ndef wrap_matcher(x):\n    \"\"\"Wraps argument in a matcher, if necessary.\n\n    :returns: the argument as-is if it is already a matcher, otherwise wrapped\n        in an :py:func:`~hamcrest.core.core.isequal.equal_to` matcher.\n\n    \"\"\"\n    if isinstance(x, Matcher):\n        return x\n    else:\n        return equal_to(x)\n\ndef is_matchable_type(expected_type):\n    if isinstance(expected_type, type):\n        return True\n\n    if isinstance(expected_type, six.class_types):\n        return True\n\n    if isinstance(expected_type, tuple) and \\\n       expected_type and \\\n       all(map(is_matchable_type, expected_type)):\n        return True\n\n    return False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/matcher.py",
    "content": "from __future__ import absolute_import\nfrom .selfdescribing import SelfDescribing\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass Matcher(SelfDescribing):\n    \"\"\"A matcher over acceptable values.\n\n    A matcher is able to describe itself to give feedback when it fails.\n\n    Matcher implementations should *not* directly implement this protocol.\n    Instead, *extend* the :py:class:`~hamcrest.core.base_matcher.BaseMatcher`\n    class, which will ensure that the\n    :py:class:`~hamcrest.core.matcher.Matcher` API can grow to support new\n    features and remain compatible with all\n    :py:class:`~hamcrest.core.matcher.Matcher` implementations.\n\n    \"\"\"\n\n    def matches(self, item, mismatch_description=None):\n        \"\"\"Evaluates the matcher for argument item.\n\n        If a mismatch is detected and argument ``mismatch_description`` is\n        provided, it will generate a description of why the matcher has not\n        accepted the item.\n\n        :param item: The object against which the matcher is evaluated.\n        :returns: ``True`` if ``item`` matches, otherwise ``False``.\n\n        \"\"\"\n        raise NotImplementedError('matches')\n\n    def describe_mismatch(self, item, mismatch_description):\n        \"\"\"Generates a description of why the matcher has not accepted the\n        item.\n\n        The description will be part of a larger description of why a matching\n        failed, so it should be concise.\n\n        This method assumes that ``matches(item)`` is ``False``, but will not\n        check this.\n\n        :param item: The item that the\n            :py:class:`~hamcrest.core.matcher.Matcher` has rejected.\n        :param mismatch_description: The description to be built or appended\n            to.\n\n        \"\"\"\n        raise NotImplementedError('describe_mismatch')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/selfdescribing.py",
    "content": "__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass SelfDescribing(object):\n    \"\"\"The ability of an object to describe itself.\"\"\"\n\n    def describe_to(self, description):\n        \"\"\"Generates a description of the object.\n\n        The description may be part of a description of a larger object of\n        which this is just a component, so it should be worded appropriately.\n\n        :param description: The description to be built or appended to.\n\n        \"\"\"\n        raise NotImplementedError('describe_to')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/selfdescribingvalue.py",
    "content": "from hamcrest.core.selfdescribing import SelfDescribing\n\nimport warnings\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass SelfDescribingValue(SelfDescribing):\n    \"\"\"Wrap any value in a ``SelfDescribingValue`` to satisfy the\n    :py:class:`~hamcrest.core.selfdescribing.SelfDescribing` interface.\n\n    **Deprecated:** No need for this class now that\n    :py:meth:`~hamcrest.core.description.Description.append_description_of`\n    handles any type of value.\n\n    \"\"\"\n\n    def __init__(self, value):\n        warnings.warn('SelfDescribingValue no longer needed',\n                      DeprecationWarning)\n        self.value = value\n\n    def describe_to(self, description):\n        \"\"\"Generates a description of the value.\"\"\"\n        description.append_value(self.value)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/core/string_description.py",
    "content": "from __future__ import absolute_import\n\nimport codecs\nimport six\n\nfrom .base_description import BaseDescription\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\ndef tostring(selfdescribing):\n    \"\"\"Returns the description of a\n    :py:class:`~hamcrest.core.selfdescribing.SelfDescribing` object as a\n    string.\n\n    :param selfdescribing: The object to be described.\n    :returns: The description of the object.\n    \"\"\"\n    return str(StringDescription().append_description_of(selfdescribing))\n\n\nclass StringDescription(BaseDescription):\n    \"\"\"A :py:class:`~hamcrest.core.description.Description` that is stored as a\n    string.\n\n    \"\"\"\n\n    def __init__(self):\n        self.out = ''\n\n    def __str__(self):\n        \"\"\"Returns the description.\"\"\"\n        return self.out\n\n    def append(self, string):\n        self.out += six.text_type(string)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/__init__.py",
    "content": "from __future__ import absolute_import\n\"\"\"Library of Matcher implementations.\"\"\"\n\nfrom hamcrest.core import *\nfrom hamcrest.library.collection import *\nfrom hamcrest.library.integration import *\nfrom hamcrest.library.number import *\nfrom hamcrest.library.object import *\nfrom hamcrest.library.text import *\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n__all__ = [\n    'has_entry',\n    'has_entries',\n    'has_key',\n    'has_value',\n    'is_in',\n    'empty',\n    'has_item',\n    'has_items',\n    'contains_inanyorder',\n    'contains',\n    'only_contains',\n    'match_equality',\n    'matches_regexp',\n    'close_to',\n    'greater_than',\n    'greater_than_or_equal_to',\n    'less_than',\n    'less_than_or_equal_to',\n    'has_length',\n    'has_property',\n    'has_properties',\n    'has_string',\n    'equal_to_ignoring_case',\n    'equal_to_ignoring_whitespace',\n    'contains_string',\n    'ends_with',\n    'starts_with',\n    'string_contains_in_order',\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/collection/__init__.py",
    "content": "\"\"\"Matchers of collections.\"\"\"\nfrom __future__ import absolute_import\nfrom .isdict_containing import has_entry\nfrom .isdict_containingentries import has_entries\nfrom .isdict_containingkey import has_key\nfrom .isdict_containingvalue import has_value\nfrom .isin import is_in\nfrom .issequence_containing import has_item, has_items\nfrom .issequence_containinginanyorder import contains_inanyorder\nfrom .issequence_containinginorder import contains\nfrom .issequence_onlycontaining import only_contains\nfrom .is_empty import empty\n\n__author__ = \"Chris Rose\"\n__copyright__ = \"Copyright 2013 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/collection/is_empty.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\n\n__author__ = \"Chris Rose\"\n__copyright__ = \"Copyright 2012 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass IsEmpty(BaseMatcher):\n\n    def matches(self, item, mismatch_description=None):\n        try:\n            if len(item) == 0:\n                return True\n\n            if mismatch_description:\n                mismatch_description \\\n                    .append_text('has %d item(s)' % len(item))\n\n        except TypeError:\n            if mismatch_description:\n                mismatch_description \\\n                    .append_text('does not support length')\n\n            return False\n\n    def describe_to(self, description):\n        description.append_text('an empty collection')\n\n\ndef empty():\n    \"\"\"\n    This matcher matches any collection-like object that responds to the\n    __len__ method, and has a length of 0.\n    \"\"\"\n    return IsEmpty()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/collection/isdict_containing.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.hasmethod import hasmethod\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass IsDictContaining(BaseMatcher):\n\n    def __init__(self, key_matcher, value_matcher):\n        self.key_matcher = key_matcher\n        self.value_matcher = value_matcher\n\n    def _matches(self, dictionary):\n        if hasmethod(dictionary, 'items'):\n            for key, value in dictionary.items():\n                if self.key_matcher.matches(key) and self.value_matcher.matches(value):\n                    return True\n        return False\n\n    def describe_to(self, description):\n        description.append_text('a dictionary containing [')        \\\n                    .append_description_of(self.key_matcher)        \\\n                    .append_text(': ')                              \\\n                    .append_description_of(self.value_matcher)      \\\n                    .append_text(']')\n\n\ndef has_entry(key_match, value_match):\n    \"\"\"Matches if dictionary contains key-value entry satisfying a given pair\n    of matchers.\n\n    :param key_match: The matcher to satisfy for the key, or an expected value\n        for :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n    :param value_match: The matcher to satisfy for the value, or an expected\n        value for :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n\n    This matcher iterates the evaluated dictionary, searching for any key-value\n    entry that satisfies ``key_match`` and ``value_match``. If a matching entry\n    is found, ``has_entry`` is satisfied.\n\n    Any argument that is not a matcher is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    Examples::\n\n        has_entry(equal_to('foo'), equal_to(1))\n        has_entry('foo', 1)\n\n    \"\"\"\n    return IsDictContaining(wrap_matcher(key_match), wrap_matcher(value_match))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/collection/isdict_containingentries.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.hasmethod import hasmethod\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass IsDictContainingEntries(BaseMatcher):\n\n    def __init__(self, value_matchers):\n        self.value_matchers = sorted(value_matchers.items())\n\n    def _not_a_dictionary(self, dictionary, mismatch_description):\n        if mismatch_description:\n            mismatch_description.append_description_of(dictionary) \\\n                                .append_text(' is not a mapping object')\n        return False\n\n    def matches(self, dictionary, mismatch_description=None):\n        for key, value_matcher in self.value_matchers:\n\n            try:\n                if not key in dictionary:\n                    if mismatch_description:\n                        mismatch_description.append_text('no ')             \\\n                                            .append_description_of(key)     \\\n                                            .append_text(' key in ')        \\\n                                            .append_description_of(dictionary)\n                    return False\n            except TypeError:\n                return self._not_a_dictionary(dictionary, mismatch_description)\n\n            try:\n                actual_value = dictionary[key]\n            except TypeError:\n                return self._not_a_dictionary(dictionary, mismatch_description)\n\n            if not value_matcher.matches(actual_value):\n                if mismatch_description:\n                    mismatch_description.append_text('value for ')  \\\n                                        .append_description_of(key) \\\n                                        .append_text(' ')\n                    value_matcher.describe_mismatch(actual_value, mismatch_description)\n                return False\n\n        return True\n\n    def describe_mismatch(self, item, mismatch_description):\n        self.matches(item, mismatch_description)\n\n    def describe_keyvalue(self, index, value, description):\n        \"\"\"Describes key-value pair at given index.\"\"\"\n        description.append_description_of(index)                        \\\n                   .append_text(': ')                                   \\\n                   .append_description_of(value)\n\n    def describe_to(self, description):\n        description.append_text('a dictionary containing {')\n        first = True\n        for key, value in self.value_matchers:\n            if not first:\n                description.append_text(', ')\n            self.describe_keyvalue(key, value, description)\n            first = False\n        description.append_text('}')\n\n\ndef has_entries(*keys_valuematchers, **kv_args):\n    \"\"\"Matches if dictionary contains entries satisfying a dictionary of keys\n    and corresponding value matchers.\n\n    :param matcher_dict: A dictionary mapping keys to associated value matchers,\n        or to expected values for\n        :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n\n    Note that the keys must be actual keys, not matchers. Any value argument\n    that is not a matcher is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    Examples::\n\n        has_entries({'foo':equal_to(1), 'bar':equal_to(2)})\n        has_entries({'foo':1, 'bar':2})\n\n    ``has_entries`` also accepts a list of keyword arguments:\n\n    .. function:: has_entries(keyword1=value_matcher1[, keyword2=value_matcher2[, ...]])\n\n    :param keyword1: A keyword to look up.\n    :param valueMatcher1: The matcher to satisfy for the value, or an expected\n        value for :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n\n    Examples::\n\n        has_entries(foo=equal_to(1), bar=equal_to(2))\n        has_entries(foo=1, bar=2)\n\n    Finally, ``has_entries`` also accepts a list of alternating keys and their\n    value matchers:\n\n    .. function:: has_entries(key1, value_matcher1[, ...])\n\n    :param key1: A key (not a matcher) to look up.\n    :param valueMatcher1: The matcher to satisfy for the value, or an expected\n        value for :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n\n    Examples::\n\n        has_entries('foo', equal_to(1), 'bar', equal_to(2))\n        has_entries('foo', 1, 'bar', 2)\n\n    \"\"\"\n    if len(keys_valuematchers) == 1:\n        try:\n            base_dict = keys_valuematchers[0].copy()\n            for key in base_dict:\n                base_dict[key] = wrap_matcher(base_dict[key])\n        except AttributeError:\n            raise ValueError('single-argument calls to has_entries must pass a dict as the argument')\n    else:\n        if len(keys_valuematchers) % 2:\n            raise ValueError('has_entries requires key-value pairs')\n        base_dict = {}\n        for index in range(int(len(keys_valuematchers) / 2)):\n            base_dict[keys_valuematchers[2 * index]] = wrap_matcher(keys_valuematchers[2 * index + 1])\n\n    for key, value in kv_args.items():\n        base_dict[key] = wrap_matcher(value)\n\n    return IsDictContainingEntries(base_dict)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/collection/isdict_containingkey.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.hasmethod import hasmethod\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass IsDictContainingKey(BaseMatcher):\n\n    def __init__(self, key_matcher):\n        self.key_matcher = key_matcher\n\n    def _matches(self, dictionary):\n        if hasmethod(dictionary, 'keys'):\n            for key in dictionary.keys():\n                if self.key_matcher.matches(key):\n                    return True\n        return False\n\n    def describe_to(self, description):\n        description.append_text('a dictionary containing key ')     \\\n                    .append_description_of(self.key_matcher)\n\n\ndef has_key(key_match):\n    \"\"\"Matches if dictionary contains an entry whose key satisfies a given\n    matcher.\n\n    :param key_match: The matcher to satisfy for the key, or an expected value\n        for :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n\n    This matcher iterates the evaluated dictionary, searching for any key-value\n    entry whose key satisfies the given matcher. If a matching entry is found,\n    ``has_key`` is satisfied.\n\n    Any argument that is not a matcher is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    Examples::\n\n        has_key(equal_to('foo'))\n        has_key('foo')\n\n    \"\"\"\n    return IsDictContainingKey(wrap_matcher(key_match))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/collection/isdict_containingvalue.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.hasmethod import hasmethod\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass IsDictContainingValue(BaseMatcher):\n\n    def __init__(self, value_matcher):\n        self.value_matcher = value_matcher\n\n    def _matches(self, dictionary):\n        if hasmethod(dictionary, 'values'):\n            for value in dictionary.values():\n                if self.value_matcher.matches(value):\n                    return True\n        return False\n\n    def describe_to(self, description):\n        description.append_text('a dictionary containing value ')   \\\n                    .append_description_of(self.value_matcher)\n\n\ndef has_value(value):\n    \"\"\"Matches if dictionary contains an entry whose value satisfies a given\n    matcher.\n\n    :param value_match: The matcher to satisfy for the value, or an expected\n        value for :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n\n    This matcher iterates the evaluated dictionary, searching for any key-value\n    entry whose value satisfies the given matcher. If a matching entry is\n    found, ``has_value`` is satisfied.\n\n    Any argument that is not a matcher is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    Examples::\n\n        has_value(equal_to('bar'))\n        has_value('bar')\n\n    \"\"\"\n    return IsDictContainingValue(wrap_matcher(value))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/collection/isin.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass IsIn(BaseMatcher):\n\n    def __init__(self, sequence):\n        self.sequence = sequence\n\n    def _matches(self, item):\n        return item in self.sequence\n\n    def describe_to(self, description):\n        description.append_text('one of ')      \\\n                   .append_list('(', ', ', ')', self.sequence)\n\n\ndef is_in(sequence):\n    \"\"\"Matches if evaluated object is present in a given sequence.\n\n    :param sequence: The sequence to search.\n\n    This matcher invokes the ``in`` membership operator to determine if the\n    evaluated object is a member of the sequence.\n\n    \"\"\"\n    return IsIn(sequence)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/collection/issequence_containing.py",
    "content": "__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nfrom hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.core.allof import all_of\nfrom hamcrest.core.helpers.hasmethod import hasmethod\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n\nclass IsSequenceContaining(BaseMatcher):\n\n    def __init__(self, element_matcher):\n        self.element_matcher = element_matcher\n\n    def _matches(self, sequence):\n        try:\n            for item in sequence:\n                if self.element_matcher.matches(item):\n                    return True\n        except TypeError: # not a sequence\n            return False\n\n    def describe_to(self, description):\n        description.append_text('a sequence containing ')           \\\n                    .append_description_of(self.element_matcher)\n\n\n# It'd be great to make use of all_of, but we can't be sure we won't\n# be seeing a one-time sequence here (like a generator); see issue #20\n# Instead, we wrap it inside a class that will convert the sequence into\n# a concrete list and then hand it off to the all_of matcher.\nclass IsSequenceContainingEvery(BaseMatcher):\n\n    def __init__(self, *element_matchers):\n        delegates = [has_item(e) for e in element_matchers]\n        self.matcher = all_of(*delegates)\n\n    def _matches(self, sequence):\n        try:\n            return self.matcher.matches(list(sequence))\n        except TypeError:\n            return False\n\n    def describe_mismatch(self, item, mismatch_description):\n        self.matcher.describe_mismatch(item, mismatch_description)\n\n    def describe_to(self, description):\n        self.matcher.describe_to(description)\n\n\n\ndef has_item(match):\n    \"\"\"Matches if any element of sequence satisfies a given matcher.\n\n    :param match: The matcher to satisfy, or an expected value for\n        :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n\n    This matcher iterates the evaluated sequence, searching for any element\n    that satisfies a given matcher. If a matching element is found,\n    ``has_item`` is satisfied.\n\n    If the ``match`` argument is not a matcher, it is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    \"\"\"\n    return IsSequenceContaining(wrap_matcher(match))\n\n\ndef has_items(*items):\n    \"\"\"Matches if all of the given matchers are satisfied by any elements of\n    the sequence.\n\n    :param match1,...: A comma-separated list of matchers.\n\n    This matcher iterates the given matchers, searching for any elements in the\n    evaluated sequence that satisfy them. If each matcher is satisfied, then\n    ``has_items`` is satisfied.\n\n    Any argument that is not a matcher is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    \"\"\"\n    matchers = []\n    for item in items:\n        matchers.append(wrap_matcher(item))\n    return IsSequenceContainingEvery(*matchers)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/collection/issequence_containinginanyorder.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.hasmethod import hasmethod\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass MatchInAnyOrder(object):\n    def __init__(self, matchers, mismatch_description):\n        self.matchers = matchers[:]\n        self.mismatch_description = mismatch_description\n\n    def matches(self, item):\n        return self.isnotsurplus(item) and self.ismatched(item)\n\n    def isfinished(self, sequence):\n        if not self.matchers:\n            return True\n        if self.mismatch_description:\n            self.mismatch_description.append_text('no item matches: ')      \\\n                                .append_list('', ', ', '', self.matchers)   \\\n                                .append_text(' in ')                        \\\n                                .append_list('[', ', ', ']', sequence)\n        return False\n\n    def isnotsurplus(self, item):\n        if not self.matchers:\n            if self.mismatch_description:\n                self.mismatch_description.append_text('not matched: ')  \\\n                                         .append_description_of(item)\n            return False\n        return True\n\n    def ismatched(self, item):\n        for index, matcher in enumerate(self.matchers):\n            if matcher.matches(item):\n                del self.matchers[index]\n                return True\n\n        if self.mismatch_description:\n            self.mismatch_description.append_text('not matched: ')  \\\n                                     .append_description_of(item)\n        return False\n\n\nclass IsSequenceContainingInAnyOrder(BaseMatcher):\n\n    def __init__(self, matchers):\n        self.matchers = matchers\n\n    def matches(self, sequence, mismatch_description=None):\n        try:\n            sequence = list(sequence)\n            matchsequence = MatchInAnyOrder(self.matchers, mismatch_description)\n            for item in sequence:\n                if not matchsequence.matches(item):\n                    return False\n            return matchsequence.isfinished(sequence)\n        except TypeError:\n            if mismatch_description:\n                super(IsSequenceContainingInAnyOrder, self)             \\\n                    .describe_mismatch(sequence, mismatch_description)\n            return False\n\n    def describe_mismatch(self, item, mismatch_description):\n        self.matches(item, mismatch_description)\n\n    def describe_to(self, description):\n        description.append_text('a sequence over ')             \\\n                   .append_list('[', ', ', ']', self.matchers)  \\\n                   .append_text(' in any order')\n\n\ndef contains_inanyorder(*items):\n    \"\"\"Matches if sequences's elements, in any order, satisfy a given list of\n    matchers.\n\n    :param match1,...: A comma-separated list of matchers.\n\n    This matcher iterates the evaluated sequence, seeing if each element\n    satisfies any of the given matchers. The matchers are tried from left to\n    right, and when a satisfied matcher is found, it is no longer a candidate\n    for the remaining elements. If a one-to-one correspondence is established\n    between elements and matchers, ``contains_inanyorder`` is satisfied.\n\n    Any argument that is not a matcher is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    \"\"\"\n\n    matchers = []\n    for item in items:\n        matchers.append(wrap_matcher(item))\n    return IsSequenceContainingInAnyOrder(matchers)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/collection/issequence_containinginorder.py",
    "content": "__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nfrom hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.hasmethod import hasmethod\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n\nclass MatchingInOrder(object):\n    def __init__(self, matchers, mismatch_description):\n        self.matchers = matchers\n        self.mismatch_description = mismatch_description\n        self.next_match_index = 0\n\n    def matches(self, item):\n        return self.isnotsurplus(item) and self.ismatched(item)\n\n    def isfinished(self):\n        if self.next_match_index < len(self.matchers):\n            if self.mismatch_description:\n                self.mismatch_description.append_text('No item matched: ') \\\n                                 .append_description_of(self.matchers[self.next_match_index])\n            return False\n        return True\n\n    def ismatched(self, item):\n        matcher = self.matchers[self.next_match_index]\n        if not matcher.matches(item):\n            if self.mismatch_description:\n                self.mismatch_description.append_text('item ' + str(self.next_match_index) + ': ')\n                matcher.describe_mismatch(item, self.mismatch_description)\n            return False\n        self.next_match_index += 1\n        return True\n\n    def isnotsurplus(self, item):\n        if len(self.matchers) <= self.next_match_index:\n            if self.mismatch_description:\n                self.mismatch_description.append_text('Not matched: ')  \\\n                                         .append_description_of(item)\n            return False\n        return True\n\n\nclass IsSequenceContainingInOrder(BaseMatcher):\n\n    def __init__(self, matchers):\n        self.matchers = matchers\n\n    def matches(self, sequence, mismatch_description=None):\n        try:\n            matchsequence = MatchingInOrder(self.matchers, mismatch_description)\n            for item in sequence:\n                if not matchsequence.matches(item):\n                    return False\n            return matchsequence.isfinished()\n        except TypeError:\n            if mismatch_description:\n                super(IsSequenceContainingInOrder, self)                \\\n                    .describe_mismatch(sequence, mismatch_description)\n            return False\n\n    def describe_mismatch(self, item, mismatch_description):\n        self.matches(item, mismatch_description)\n\n    def describe_to(self, description):\n        description.append_text('a sequence containing ')   \\\n                   .append_list('[', ', ', ']', self.matchers)\n\n\ndef contains(*items):\n    \"\"\"Matches if sequence's elements satisfy a given list of matchers, in order.\n\n    :param match1,...: A comma-separated list of matchers.\n\n    This matcher iterates the evaluated sequence and a given list of matchers,\n    seeing if each element satisfies its corresponding matcher.\n\n    Any argument that is not a matcher is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    \"\"\"\n    matchers = []\n    for item in items:\n        matchers.append(wrap_matcher(item))\n    return IsSequenceContainingInOrder(matchers)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/collection/issequence_onlycontaining.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.core.anyof import any_of\nfrom hamcrest.core.helpers.hasmethod import hasmethod\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass IsSequenceOnlyContaining(BaseMatcher):\n\n    def __init__(self, matcher):\n        self.matcher = matcher\n\n    def _matches(self, sequence):\n        try:\n            sequence = list(sequence)\n            if len(sequence) == 0:\n                return False\n            for item in sequence:\n                if not self.matcher.matches(item):\n                    return False\n            return True\n        except TypeError:\n            return False\n\n    def describe_to(self, description):\n        description.append_text('a sequence containing items matching ')    \\\n                    .append_description_of(self.matcher)\n\n\ndef only_contains(*items):\n    \"\"\"Matches if each element of sequence satisfies any of the given matchers.\n\n    :param match1,...: A comma-separated list of matchers.\n\n    This matcher iterates the evaluated sequence, confirming whether each\n    element satisfies any of the given matchers.\n\n    Example::\n\n        only_contains(less_than(4))\n\n    will match ``[3,1,2]``.\n\n    Any argument that is not a matcher is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    \"\"\"\n    matchers = []\n    for item in items:\n        matchers.append(wrap_matcher(item))\n    return IsSequenceOnlyContaining(any_of(*matchers))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/integration/__init__.py",
    "content": "from __future__ import absolute_import\n\"\"\"Utilities for integrating Hamcrest with other libraries.\"\"\"\n\nfrom .match_equality import match_equality\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/integration/match_equality.py",
    "content": "from hamcrest.core.string_description import tostring\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n__author__ = \"Chris Rose\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n__unittest = True\n\n\nclass EqualityWrapper(object):\n\n    def __init__(self, matcher):\n        self.matcher = matcher\n\n    def __eq__(self, object):\n        return self.matcher.matches(object)\n\n    def __str__(self):\n        return repr(self)\n\n    def __repr__(self):\n        return tostring(self.matcher)\n\n\ndef match_equality(matcher):\n    \"\"\"Wraps a matcher to define equality in terms of satisfying the matcher.\n\n    ``match_equality`` allows Hamcrest matchers to be used in libraries that\n    are not Hamcrest-aware. They might use the equality operator::\n\n        assert match_equality(matcher) == object\n\n    Or they might provide a method that uses equality for its test::\n\n        library.method_that_tests_eq(match_equality(matcher))\n\n    One concrete example is integrating with the ``assert_called_with`` methods\n    in Michael Foord's `mock <http://www.voidspace.org.uk/python/mock/>`_\n    library.\n\n    \"\"\"\n    return EqualityWrapper(wrap_matcher(matcher))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/number/__init__.py",
    "content": "from __future__ import absolute_import\n\"\"\"Matchers that perform numeric comparisons.\"\"\"\n\nfrom .iscloseto import close_to\nfrom .ordering_comparison import greater_than, greater_than_or_equal_to, less_than, less_than_or_equal_to\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/number/iscloseto.py",
    "content": "import six\nfrom hamcrest.core.base_matcher import BaseMatcher\nfrom math import fabs\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\ndef isnumeric(value):\n    \"\"\"Confirm that 'value' can be treated numerically; duck-test accordingly\n    \"\"\"\n    if isinstance(value, (float, complex) + six.integer_types):\n        return True\n\n    try:\n        _ = (fabs(value) + 0 - 0) * 1\n        return True\n    except ArithmeticError:\n        return True\n    except:\n        return False\n    return False\n\n\nclass IsCloseTo(BaseMatcher):\n\n    def __init__(self, value, delta):\n        if not isnumeric(value):\n            raise TypeError('IsCloseTo value must be numeric')\n        if not isnumeric(delta):\n            raise TypeError('IsCloseTo delta must be numeric')\n\n        self.value = value\n        self.delta = delta\n\n    def _matches(self, item):\n        if not isnumeric(item):\n            return False\n        return fabs(item - self.value) <= self.delta\n\n    def describe_mismatch(self, item, mismatch_description):\n        if not isnumeric(item):\n            super(IsCloseTo, self).describe_mismatch(item, mismatch_description)\n        else:\n            actual_delta = fabs(item - self.value)\n            mismatch_description.append_description_of(item)            \\\n                                .append_text(' differed by ')           \\\n                                .append_description_of(actual_delta)\n\n    def describe_to(self, description):\n        description.append_text('a numeric value within ')  \\\n                   .append_description_of(self.delta)       \\\n                   .append_text(' of ')                     \\\n                   .append_description_of(self.value)\n\n\ndef close_to(value, delta):\n    \"\"\"Matches if object is a number close to a given value, within a given\n    delta.\n\n    :param value: The value to compare against as the expected value.\n    :param delta: The maximum delta between the values for which the numbers\n        are considered close.\n\n    This matcher compares the evaluated object against ``value`` to see if the\n    difference is within a positive ``delta``.\n\n    Example::\n\n        close_to(3.0, 0.25)\n\n    \"\"\"\n    return IsCloseTo(value, delta)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/number/ordering_comparison.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nimport operator\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass OrderingComparison(BaseMatcher):\n\n    def __init__(self, value, comparison_function, comparison_description):\n        self.value = value\n        self.comparison_function = comparison_function\n        self.comparison_description = comparison_description\n\n    def _matches(self, item):\n        return self.comparison_function(item, self.value)\n\n    def describe_to(self, description):\n        description.append_text('a value ')                     \\\n                   .append_text(self.comparison_description)    \\\n                   .append_text(' ')                            \\\n                   .append_description_of(self.value)\n\n\ndef greater_than(value):\n    \"\"\"Matches if object is greater than a given value.\n\n    :param value: The value to compare against.\n\n    \"\"\"\n    return OrderingComparison(value, operator.gt, 'greater than')\n\n\ndef greater_than_or_equal_to(value):\n    \"\"\"Matches if object is greater than or equal to a given value.\n\n    :param value: The value to compare against.\n\n    \"\"\"\n    return OrderingComparison(value, operator.ge, 'greater than or equal to')\n\n\ndef less_than(value):\n    \"\"\"Matches if object is less than a given value.\n\n    :param value: The value to compare against.\n\n    \"\"\"\n    return OrderingComparison(value, operator.lt, 'less than')\n\n\ndef less_than_or_equal_to(value):\n    \"\"\"Matches if object is less than or equal to a given value.\n\n    :param value: The value to compare against.\n\n    \"\"\"\n    return OrderingComparison(value, operator.le, 'less than or equal to')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/object/__init__.py",
    "content": "from __future__ import absolute_import\n\"\"\"Matchers that inspect objects and classes.\"\"\"\n\nfrom .haslength import has_length\nfrom .hasproperty import has_property, has_properties\nfrom .hasstring import has_string\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/object/haslength.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.hasmethod import hasmethod\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass HasLength(BaseMatcher):\n\n    def __init__(self, len_matcher):\n        self.len_matcher = len_matcher\n\n    def _matches(self, item):\n        if not hasmethod(item, '__len__'):\n            return False\n        return self.len_matcher.matches(len(item))\n\n    def describe_mismatch(self, item, mismatch_description):\n        super(HasLength, self).describe_mismatch(item, mismatch_description)\n        if hasmethod(item, '__len__'):\n            mismatch_description.append_text(' with length of ')    \\\n                                .append_description_of(len(item))\n\n    def describe_to(self, description):\n        description.append_text('an object with length of ')    \\\n                    .append_description_of(self.len_matcher)\n\n\ndef has_length(match):\n    \"\"\"Matches if ``len(item)`` satisfies a given matcher.\n\n    :param match: The matcher to satisfy, or an expected value for\n        :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n\n    This matcher invokes the :py:func:`len` function on the evaluated object to\n    get its length, passing the result to a given matcher for evaluation.\n\n    If the ``match`` argument is not a matcher, it is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    :equality.\n\n    Examples::\n\n        has_length(greater_than(6))\n        has_length(5)\n\n    \"\"\"\n    return HasLength(wrap_matcher(match))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/object/hasproperty.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core import anything\nfrom hamcrest.core.core.allof import all_of\nfrom hamcrest.core.string_description import StringDescription\nfrom hamcrest.core.helpers.hasmethod import hasmethod\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher as wrap_shortcut\n\n__author__ = \"Chris Rose\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass IsObjectWithProperty(BaseMatcher):\n\n    def __init__(self, property_name, value_matcher):\n        self.property_name = property_name\n        self.value_matcher = value_matcher\n\n    def _matches(self, o):\n        if o is None:\n            return False\n\n        if not hasattr(o, self.property_name):\n            return False\n\n        value = getattr(o, self.property_name)\n        return self.value_matcher.matches(value)\n\n    def describe_to(self, description):\n        description.append_text(\"an object with a property '\") \\\n                                        .append_text(self.property_name) \\\n                                        .append_text(\"' matching \") \\\n                                        .append_description_of(self.value_matcher)\n\n    def describe_mismatch(self, item, mismatch_description):\n        if item is None:\n            mismatch_description.append_text('was None')\n            return\n\n        if not hasattr(item, self.property_name):\n            mismatch_description.append_value(item) \\\n                                                    .append_text(' did not have the ') \\\n                                                    .append_value(self.property_name) \\\n                                                    .append_text(' property')\n            return\n\n        mismatch_description.append_text('property ').append_value(self.property_name).append_text(' ')\n        value = getattr(item, self.property_name)\n        self.value_matcher.describe_mismatch(value, mismatch_description)\n\n    def __str__(self):\n        d = StringDescription()\n        self.describe_to(d)\n        return str(d)\n\n\ndef has_property(name, match=None):\n    \"\"\"Matches if object has a property with a given name whose value satisfies\n    a given matcher.\n\n    :param name: The name of the property.\n    :param match: Optional matcher to satisfy.\n\n    This matcher determines if the evaluated object has a property with a given\n    name. If no such property is found, ``has_property`` is not satisfied.\n\n    If the property is found, its value is passed to a given matcher for\n    evaluation. If the ``match`` argument is not a matcher, it is implicitly\n    wrapped in an :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to\n    check for equality.\n\n    If the ``match`` argument is not provided, the\n    :py:func:`~hamcrest.core.core.isanything.anything` matcher is used so that\n    ``has_property`` is satisfied if a matching property is found.\n\n    Examples::\n\n        has_property('name', starts_with('J'))\n        has_property('name', 'Jon')\n        has_property('name')\n\n    \"\"\"\n\n    if match is None:\n        match = anything()\n\n    return IsObjectWithProperty(name, wrap_shortcut(match))\n\n\ndef has_properties(*keys_valuematchers, **kv_args):\n    \"\"\"Matches if an object has properties satisfying all of a dictionary\n    of string property names and corresponding value matchers.\n\n    :param matcher_dict: A dictionary mapping keys to associated value matchers,\n        or to expected values for\n        :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n\n    Note that the keys must be actual keys, not matchers. Any value argument\n    that is not a matcher is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    Examples::\n\n        has_properties({'foo':equal_to(1), 'bar':equal_to(2)})\n        has_properties({'foo':1, 'bar':2})\n\n    ``has_properties`` also accepts a list of keyword arguments:\n\n    .. function:: has_properties(keyword1=value_matcher1[, keyword2=value_matcher2[, ...]])\n\n    :param keyword1: A keyword to look up.\n    :param valueMatcher1: The matcher to satisfy for the value, or an expected\n        value for :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n\n    Examples::\n\n        has_properties(foo=equal_to(1), bar=equal_to(2))\n        has_properties(foo=1, bar=2)\n\n    Finally, ``has_properties`` also accepts a list of alternating keys and their\n    value matchers:\n\n    .. function:: has_properties(key1, value_matcher1[, ...])\n\n    :param key1: A key (not a matcher) to look up.\n    :param valueMatcher1: The matcher to satisfy for the value, or an expected\n        value for :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n\n    Examples::\n\n        has_properties('foo', equal_to(1), 'bar', equal_to(2))\n        has_properties('foo', 1, 'bar', 2)\n\n    \"\"\"\n    if len(keys_valuematchers) == 1:\n        try:\n            base_dict = keys_valuematchers[0].copy()\n            for key in base_dict:\n                base_dict[key] = wrap_shortcut(base_dict[key])\n        except AttributeError:\n            raise ValueError('single-argument calls to has_properties must pass a dict as the argument')\n    else:\n        if len(keys_valuematchers) % 2:\n            raise ValueError('has_properties requires key-value pairs')\n        base_dict = {}\n        for index in range(int(len(keys_valuematchers) / 2)):\n            base_dict[keys_valuematchers[2 * index]] = wrap_shortcut(keys_valuematchers[2 * index + 1])\n\n    for key, value in kv_args.items():\n        base_dict[key] = wrap_shortcut(value)\n\n    return all_of(*[has_property(property_name, property_value_matcher) for \\\n                   property_name, property_value_matcher in base_dict.items()])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/object/hasstring.py",
    "content": "from hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.wrap_matcher import wrap_matcher\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass HasString(BaseMatcher):\n\n    def __init__(self, str_matcher):\n        self.str_matcher = str_matcher\n\n    def _matches(self, item):\n        return self.str_matcher.matches(str(item))\n\n    def describe_to(self, description):\n        description.append_text('an object with str ')          \\\n                    .append_description_of(self.str_matcher)\n\n\ndef has_string(match):\n    \"\"\"Matches if ``str(item)`` satisfies a given matcher.\n\n    :param match: The matcher to satisfy, or an expected value for\n        :py:func:`~hamcrest.core.core.isequal.equal_to` matching.\n\n    This matcher invokes the :py:func:`str` function on the evaluated object to\n    get its length, passing the result to a given matcher for evaluation. If\n    the ``match`` argument is not a matcher, it is implicitly wrapped in an\n    :py:func:`~hamcrest.core.core.isequal.equal_to` matcher to check for\n    equality.\n\n    Examples::\n\n        has_string(starts_with('foo'))\n        has_string('bar')\n\n    \"\"\"\n    return HasString(wrap_matcher(match))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/text/__init__.py",
    "content": "from __future__ import absolute_import\n\"\"\"Matchers that perform text comparisons.\"\"\"\n\nfrom .isequal_ignoring_case import equal_to_ignoring_case\nfrom .isequal_ignoring_whitespace import equal_to_ignoring_whitespace\nfrom .stringcontains import contains_string\nfrom .stringendswith import ends_with\nfrom .stringstartswith import starts_with\nfrom .stringmatches import matches_regexp\nfrom .stringcontainsinorder import string_contains_in_order\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/text/isequal_ignoring_case.py",
    "content": "__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nfrom hamcrest.core.base_matcher import BaseMatcher\n\nimport six\n\nclass IsEqualIgnoringCase(BaseMatcher):\n\n    def __init__(self, string):\n        if not isinstance(string, six.string_types):\n            raise TypeError('IsEqualIgnoringCase requires string')\n        self.original_string = string\n        self.lowered_string = string.lower()\n\n    def _matches(self, item):\n        if not isinstance(item, six.string_types):\n            return False\n        return self.lowered_string == item.lower()\n\n    def describe_to(self, description):\n        description.append_description_of(self.original_string)    \\\n                   .append_text(' ignoring case')\n\n\ndef equal_to_ignoring_case(string):\n    \"\"\"Matches if object is a string equal to a given string, ignoring case\n    differences.\n\n    :param string: The string to compare against as the expected value.\n\n    This matcher first checks whether the evaluated object is a string. If so,\n    it compares it with ``string``, ignoring differences of case.\n\n    Example::\n\n        equal_to_ignoring_case(\"hello world\")\n\n    will match \"heLLo WorlD\".\n\n    \"\"\"\n    return IsEqualIgnoringCase(string)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/text/isequal_ignoring_whitespace.py",
    "content": "__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nfrom hamcrest.core.base_matcher import BaseMatcher\n\nimport six\n\ndef stripspace(string):\n    result = ''\n    last_was_space = True\n    for character in string:\n        if character.isspace():\n            if not last_was_space:\n                result += ' '\n            last_was_space = True\n        else:\n            result += character\n            last_was_space = False\n    return result.strip()\n\n\nclass IsEqualIgnoringWhiteSpace(BaseMatcher):\n\n    def __init__(self, string):\n        if not isinstance(string, six.string_types):\n            raise TypeError('IsEqualIgnoringWhiteSpace requires string')\n        self.original_string = string\n        self.stripped_string = stripspace(string)\n\n    def _matches(self, item):\n        if not isinstance(item, six.string_types):\n            return False\n        return self.stripped_string == stripspace(item)\n\n    def describe_to(self, description):\n        description.append_description_of(self.original_string)    \\\n                   .append_text(' ignoring whitespace')\n\n\ndef equal_to_ignoring_whitespace(string):\n    \"\"\"Matches if object is a string equal to a given string, ignoring\n    differences in whitespace.\n\n    :param string: The string to compare against as the expected value.\n\n    This matcher first checks whether the evaluated object is a string. If so,\n    it compares it with ``string``, ignoring differences in runs of whitespace.\n\n    Example::\n\n        equal_to_ignoring_whitespace(\"hello world\")\n\n    will match ``\"hello   world\"``.\n\n    \"\"\"\n    return IsEqualIgnoringWhiteSpace(string)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/text/stringcontains.py",
    "content": "from hamcrest.library.text.substringmatcher import SubstringMatcher\nfrom hamcrest.core.helpers.hasmethod import hasmethod\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass StringContains(SubstringMatcher):\n\n    def __init__(self, substring):\n        super(StringContains, self).__init__(substring)\n\n    def _matches(self, item):\n        if not hasmethod(item, 'find'):\n            return False\n        return item.find(self.substring) >= 0\n\n    def relationship(self):\n        return 'containing'\n\n\ndef contains_string(substring):\n    \"\"\"Matches if object is a string containing a given string.\n\n    :param string: The string to search for.\n\n    This matcher first checks whether the evaluated object is a string. If so,\n    it checks whether it contains ``string``.\n\n    Example::\n\n        contains_string(\"def\")\n\n    will match \"abcdefg\".\n\n    \"\"\"\n    return StringContains(substring)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/text/stringcontainsinorder.py",
    "content": "__author__ = \"Romilly Cocking\"\r\n__copyright__ = \"Copyright 2011 hamcrest.org\"\r\n__license__ = \"BSD, see License.txt\"\r\n\r\nfrom hamcrest.core.base_matcher import BaseMatcher\r\nfrom hamcrest.core.helpers.hasmethod import hasmethod\r\n\r\nimport six\r\n\r\nclass StringContainsInOrder(BaseMatcher):\r\n\r\n    def __init__(self, *substrings):\r\n        for substring in substrings:\r\n            if not isinstance(substring, six.string_types):\r\n                raise TypeError(self.__class__.__name__\r\n                                + ' requires string arguments')\r\n        self.substrings = substrings\r\n\r\n    def _matches(self, item):\r\n        if not hasmethod(item, 'find'):\r\n            return False\r\n        from_index = 0\r\n        for substring in self.substrings:\r\n            from_index = item.find(substring, from_index)\r\n            if from_index == -1:\r\n                return False\r\n        return True\r\n\r\n    def describe_to(self, description):\r\n        description.append_list('a string containing ', ', ', ' in order',\r\n                                self.substrings)\r\n\r\n\r\ndef string_contains_in_order(*substrings):\r\n    \"\"\"Matches if object is a string containing a given list of substrings in\r\n    relative order.\r\n\r\n    :param string1,...:  A comma-separated list of strings.\r\n\r\n    This matcher first checks whether the evaluated object is a string. If so,\r\n    it checks whether it contains a given list of strings, in relative order to\r\n    each other. The searches are performed starting from the beginning of the\r\n    evaluated string.\r\n\r\n    Example::\r\n\r\n        string_contains_in_order(\"bc\", \"fg\", \"jkl\")\r\n\r\n    will match \"abcdefghijklm\".\r\n\r\n    \"\"\"\r\n    return StringContainsInOrder(*substrings)\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/text/stringendswith.py",
    "content": "from hamcrest.library.text.substringmatcher import SubstringMatcher\nfrom hamcrest.core.helpers.hasmethod import hasmethod\n\n__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\n\nclass StringEndsWith(SubstringMatcher):\n\n    def __init__(self, substring):\n        super(StringEndsWith, self).__init__(substring)\n\n    def _matches(self, item):\n        if not hasmethod(item, 'endswith'):\n            return False\n        return item.endswith(self.substring)\n\n    def relationship(self):\n        return 'ending with'\n\n\ndef ends_with(string):\n    \"\"\"Matches if object is a string ending with a given string.\n\n    :param string: The string to search for.\n\n    This matcher first checks whether the evaluated object is a string. If so,\n    it checks if ``string`` matches the ending characters of the evaluated\n    object.\n\n    Example::\n\n        ends_with(\"bar\")\n\n    will match \"foobar\".\n\n    \"\"\"\n    return StringEndsWith(string)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/text/stringmatches.py",
    "content": "__author__ = \"Chris Rose\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nimport re\n\nimport six\n\nfrom hamcrest.core.base_matcher import BaseMatcher\nfrom hamcrest.core.helpers.hasmethod import hasmethod\n\nclass StringMatchesPattern(BaseMatcher):\n\n    def __init__(self, pattern):\n        self.pattern = pattern\n\n    def describe_to(self, description):\n        description.append_text(\"a string matching '\") \\\n                                   .append_text(self.pattern.pattern) \\\n                                   .append_text(\"'\")\n\n    def _matches(self, item):\n        return self.pattern.search(item) is not None\n\n\ndef matches_regexp(pattern):\n    \"\"\"Matches if object is a string containing a match for a given regular\n    expression.\n\n    :param pattern: The regular expression to search for.\n\n    This matcher first checks whether the evaluated object is a string. If so,\n    it checks if the regular expression ``pattern`` matches anywhere within the\n    evaluated object.\n\n    \"\"\"\n    if isinstance(pattern, six.string_types):\n        pattern = re.compile(pattern)\n\n    return StringMatchesPattern(pattern)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/text/stringstartswith.py",
    "content": "__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nfrom hamcrest.library.text.substringmatcher import SubstringMatcher\nfrom hamcrest.core.helpers.hasmethod import hasmethod\n\n\nclass StringStartsWith(SubstringMatcher):\n\n    def __init__(self, substring):\n        super(StringStartsWith, self).__init__(substring)\n\n    def _matches(self, item):\n        if not hasmethod(item, 'startswith'):\n            return False\n        return item.startswith(self.substring)\n\n    def relationship(self):\n        return 'starting with'\n\n\ndef starts_with(substring):\n    \"\"\"Matches if object is a string starting with a given string.\n\n    :param string: The string to search for.\n\n    This matcher first checks whether the evaluated object is a string. If so,\n    it checks if ``string`` matches the beginning characters of the evaluated\n    object.\n\n    Example::\n\n        starts_with(\"foo\")\n\n    will match \"foobar\".\n\n    \"\"\"\n    return StringStartsWith(substring)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hamcrest/library/text/substringmatcher.py",
    "content": "__author__ = \"Jon Reid\"\n__copyright__ = \"Copyright 2011 hamcrest.org\"\n__license__ = \"BSD, see License.txt\"\n\nfrom hamcrest.core.base_matcher import BaseMatcher\n\nimport six\n\nclass SubstringMatcher(BaseMatcher):\n\n    def __init__(self, substring):\n        if not isinstance(substring, six.string_types):\n            raise TypeError(self.__class__.__name__ + ' requires string')\n        self.substring = substring\n\n    def describe_to(self, description):\n        description.append_text('a string ')                \\\n                   .append_text(self.relationship())        \\\n                   .append_text(' ')                        \\\n                   .append_description_of(self.substring)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink/__init__.py",
    "content": "\nfrom ._url import (URL,\n                   parse,\n                   EncodedURL,\n                   DecodedURL,\n                   URLParseError,\n                   register_scheme)\n\n__all__ = [\n    \"URL\",\n    \"parse\",\n    \"EncodedURL\",\n    \"DecodedURL\",\n    \"URLParseError\",\n    \"register_scheme\",\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink/_url.py",
    "content": "# -*- coding: utf-8 -*-\nu\"\"\"Hyperlink provides Pythonic URL parsing, construction, and rendering.\n\nUsage is straightforward::\n\n   >>> from hyperlink import URL\n   >>> url = URL.from_text(u'http://github.com/mahmoud/hyperlink?utm_source=docs')\n   >>> url.host\n   u'github.com'\n   >>> secure_url = url.replace(scheme=u'https')\n   >>> secure_url.get('utm_source')[0]\n   u'docs'\n\nAs seen here, the API revolves around the lightweight and immutable\n:class:`URL` type, documented below.\n\"\"\"\n\nimport re\nimport sys\nimport string\nimport socket\nfrom unicodedata import normalize\ntry:\n    from socket import inet_pton\nexcept ImportError:\n    inet_pton = None  # defined below\ntry:\n    from collections.abc import Mapping\nexcept ImportError:  # Python 2\n    from collections import Mapping\n\n# Note: IDNAError is a subclass of UnicodeError\nfrom idna import encode as idna_encode, decode as idna_decode, IDNAError\n\n\nif inet_pton is None:\n    # based on https://gist.github.com/nnemkin/4966028\n    # this code only applies on Windows Python 2.7\n    import ctypes\n\n    class _sockaddr(ctypes.Structure):\n        _fields_ = [(\"sa_family\", ctypes.c_short),\n                    (\"__pad1\", ctypes.c_ushort),\n                    (\"ipv4_addr\", ctypes.c_byte * 4),\n                    (\"ipv6_addr\", ctypes.c_byte * 16),\n                    (\"__pad2\", ctypes.c_ulong)]\n\n    WSAStringToAddressA = ctypes.windll.ws2_32.WSAStringToAddressA\n    WSAAddressToStringA = ctypes.windll.ws2_32.WSAAddressToStringA\n\n    def inet_pton(address_family, ip_string):\n        addr = _sockaddr()\n        ip_string = ip_string.encode('ascii')\n        addr.sa_family = address_family\n        addr_size = ctypes.c_int(ctypes.sizeof(addr))\n\n        if WSAStringToAddressA(ip_string, address_family, None, ctypes.byref(addr), ctypes.byref(addr_size)) != 0:\n            raise socket.error(ctypes.FormatError())\n\n        if address_family == socket.AF_INET:\n            return ctypes.string_at(addr.ipv4_addr, 4)\n        if address_family == socket.AF_INET6:\n            return ctypes.string_at(addr.ipv6_addr, 16)\n        raise socket.error('unknown address family')\n\n\nPY2 = (sys.version_info[0] == 2)\nunicode = type(u'')\ntry:\n    unichr\nexcept NameError:\n    unichr = chr  # py3\nNoneType = type(None)\n\n\n# from boltons.typeutils\ndef make_sentinel(name='_MISSING', var_name=None):\n    \"\"\"Creates and returns a new **instance** of a new class, suitable for\n    usage as a \"sentinel\", a kind of singleton often used to indicate\n    a value is missing when ``None`` is a valid input.\n\n    Args:\n        name (str): Name of the Sentinel\n        var_name (str): Set this name to the name of the variable in\n            its respective module enable pickleability.\n\n    >>> make_sentinel(var_name='_MISSING')\n    _MISSING\n\n    The most common use cases here in boltons are as default values\n    for optional function arguments, partly because of its\n    less-confusing appearance in automatically generated\n    documentation. Sentinels also function well as placeholders in queues\n    and linked lists.\n\n    .. note::\n\n      By design, additional calls to ``make_sentinel`` with the same\n      values will not produce equivalent objects.\n\n      >>> make_sentinel('TEST') == make_sentinel('TEST')\n      False\n      >>> type(make_sentinel('TEST')) == type(make_sentinel('TEST'))\n      False\n\n    \"\"\"\n    class Sentinel(object):\n        def __init__(self):\n            self.name = name\n            self.var_name = var_name\n\n        def __repr__(self):\n            if self.var_name:\n                return self.var_name\n            return '%s(%r)' % (self.__class__.__name__, self.name)\n        if var_name:\n            def __reduce__(self):\n                return self.var_name\n\n        def __nonzero__(self):\n            return False\n\n        __bool__ = __nonzero__\n\n    return Sentinel()\n\n\n_unspecified = _UNSET = make_sentinel('_UNSET')\n\n\n# RFC 3986 Section 2.3, Unreserved URI Characters\n#   https://tools.ietf.org/html/rfc3986#section-2.3\n_UNRESERVED_CHARS = frozenset('~-._0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ'\n                              'abcdefghijklmnopqrstuvwxyz')\n\n\n# URL parsing regex (based on RFC 3986 Appendix B, with modifications)\n_URL_RE = re.compile(r'^((?P<scheme>[^:/?#]+):)?'\n                     r'((?P<_netloc_sep>//)'\n                     r'(?P<authority>[^/?#]*))?'\n                     r'(?P<path>[^?#]*)'\n                     r'(\\?(?P<query>[^#]*))?'\n                     r'(#(?P<fragment>.*))?$')\n_SCHEME_RE = re.compile(r'^[a-zA-Z0-9+-.]*$')\n_AUTHORITY_RE = re.compile(r'^(?:(?P<userinfo>[^@/?#]*)@)?'\n                           r'(?P<host>'\n                           r'(?:\\[(?P<ipv6_host>[^[\\]/?#]*)\\])'\n                           r'|(?P<plain_host>[^:/?#[\\]]*)'\n                           r'|(?P<bad_host>.*?))?'\n                           r'(?::(?P<port>.*))?$')\n\n\n_HEX_CHAR_MAP = dict([((a + b).encode('ascii'),\n                       unichr(int(a + b, 16)).encode('charmap'))\n                      for a in string.hexdigits for b in string.hexdigits])\n_ASCII_RE = re.compile('([\\x00-\\x7f]+)')\n\n# RFC 3986 section 2.2, Reserved Characters\n#   https://tools.ietf.org/html/rfc3986#section-2.2\n_GEN_DELIMS = frozenset(u':/?#[]@')\n_SUB_DELIMS = frozenset(u\"!$&'()*+,;=\")\n_ALL_DELIMS = _GEN_DELIMS | _SUB_DELIMS\n\n_USERINFO_SAFE = _UNRESERVED_CHARS | _SUB_DELIMS | set(u'%')\n_USERINFO_DELIMS = _ALL_DELIMS - _USERINFO_SAFE\n_PATH_SAFE = _USERINFO_SAFE | set(u':@')\n_PATH_DELIMS = _ALL_DELIMS - _PATH_SAFE\n_SCHEMELESS_PATH_SAFE = _PATH_SAFE - set(':')\n_SCHEMELESS_PATH_DELIMS = _ALL_DELIMS - _SCHEMELESS_PATH_SAFE\n_FRAGMENT_SAFE = _UNRESERVED_CHARS | _PATH_SAFE | set(u'/?')\n_FRAGMENT_DELIMS = _ALL_DELIMS - _FRAGMENT_SAFE\n_QUERY_VALUE_SAFE = _UNRESERVED_CHARS | _FRAGMENT_SAFE - set(u'&+')\n_QUERY_VALUE_DELIMS = _ALL_DELIMS - _QUERY_VALUE_SAFE\n_QUERY_KEY_SAFE = _UNRESERVED_CHARS | _QUERY_VALUE_SAFE - set(u'=')\n_QUERY_KEY_DELIMS = _ALL_DELIMS - _QUERY_KEY_SAFE\n\n\ndef _make_decode_map(delims, allow_percent=False):\n    ret = dict(_HEX_CHAR_MAP)\n    if not allow_percent:\n        delims = set(delims) | set([u'%'])\n    for delim in delims:\n        _hexord = '{0:02X}'.format(ord(delim)).encode('ascii')\n        _hexord_lower = _hexord.lower()\n        ret.pop(_hexord)\n        if _hexord != _hexord_lower:\n            ret.pop(_hexord_lower)\n    return ret\n\n\ndef _make_quote_map(safe_chars):\n    ret = {}\n    # v is included in the dict for py3 mostly, because bytestrings\n    # are iterables of ints, of course!\n    for i, v in zip(range(256), range(256)):\n        c = chr(v)\n        if c in safe_chars:\n            ret[c] = ret[v] = c\n        else:\n            ret[c] = ret[v] = '%{0:02X}'.format(i)\n    return ret\n\n\n_USERINFO_PART_QUOTE_MAP = _make_quote_map(_USERINFO_SAFE)\n_USERINFO_DECODE_MAP = _make_decode_map(_USERINFO_DELIMS)\n_PATH_PART_QUOTE_MAP = _make_quote_map(_PATH_SAFE)\n_SCHEMELESS_PATH_PART_QUOTE_MAP = _make_quote_map(_SCHEMELESS_PATH_SAFE)\n_PATH_DECODE_MAP = _make_decode_map(_PATH_DELIMS)\n_QUERY_KEY_QUOTE_MAP = _make_quote_map(_QUERY_KEY_SAFE)\n_QUERY_KEY_DECODE_MAP = _make_decode_map(_QUERY_KEY_DELIMS)\n_QUERY_VALUE_QUOTE_MAP = _make_quote_map(_QUERY_VALUE_SAFE)\n_QUERY_VALUE_DECODE_MAP = _make_decode_map(_QUERY_VALUE_DELIMS)\n_FRAGMENT_QUOTE_MAP = _make_quote_map(_FRAGMENT_SAFE)\n_FRAGMENT_DECODE_MAP = _make_decode_map(_FRAGMENT_DELIMS)\n_UNRESERVED_QUOTE_MAP = _make_quote_map(_UNRESERVED_CHARS)\n_UNRESERVED_DECODE_MAP = dict([(k, v) for k, v in _HEX_CHAR_MAP.items()\n                               if v.decode('ascii', 'replace')\n                               in _UNRESERVED_CHARS])\n\n_ROOT_PATHS = frozenset(((), (u'',)))\n\n\ndef _encode_reserved(text, maximal=True):\n    \"\"\"A very comprehensive percent encoding for encoding all\n    delimiters. Used for arguments to DecodedURL, where a % means a\n    percent sign, and not the character used by URLs for escaping\n    bytes.\n    \"\"\"\n    if maximal:\n        bytestr = normalize('NFC', text).encode('utf8')\n        return u''.join([_UNRESERVED_QUOTE_MAP[b] for b in bytestr])\n    return u''.join([_UNRESERVED_QUOTE_MAP[t] if t in _UNRESERVED_CHARS\n                     else t for t in text])\n\n\ndef _encode_path_part(text, maximal=True):\n    \"Percent-encode a single segment of a URL path.\"\n    if maximal:\n        bytestr = normalize('NFC', text).encode('utf8')\n        return u''.join([_PATH_PART_QUOTE_MAP[b] for b in bytestr])\n    return u''.join([_PATH_PART_QUOTE_MAP[t] if t in _PATH_DELIMS else t\n                     for t in text])\n\n\ndef _encode_schemeless_path_part(text, maximal=True):\n    \"\"\"Percent-encode the first segment of a URL path for a URL without a\n    scheme specified.\n    \"\"\"\n    if maximal:\n        bytestr = normalize('NFC', text).encode('utf8')\n        return u''.join([_SCHEMELESS_PATH_PART_QUOTE_MAP[b] for b in bytestr])\n    return u''.join([_SCHEMELESS_PATH_PART_QUOTE_MAP[t]\n                     if t in _SCHEMELESS_PATH_DELIMS else t for t in text])\n\n\ndef _encode_path_parts(text_parts, rooted=False, has_scheme=True,\n                       has_authority=True, joined=True, maximal=True):\n    \"\"\"\n    Percent-encode a tuple of path parts into a complete path.\n\n    Setting *maximal* to False percent-encodes only the reserved\n    characters that are syntactically necessary for serialization,\n    preserving any IRI-style textual data.\n\n    Leaving *maximal* set to its default True percent-encodes\n    everything required to convert a portion of an IRI to a portion of\n    a URI.\n\n    RFC 3986 3.3:\n\n       If a URI contains an authority component, then the path component\n       must either be empty or begin with a slash (\"/\") character.  If a URI\n       does not contain an authority component, then the path cannot begin\n       with two slash characters (\"//\").  In addition, a URI reference\n       (Section 4.1) may be a relative-path reference, in which case the\n       first path segment cannot contain a colon (\":\") character.\n    \"\"\"\n    if not text_parts:\n        return u'' if joined else text_parts\n    if rooted:\n        text_parts = (u'',) + text_parts\n    # elif has_authority and text_parts:\n    #     raise Exception('see rfc above')  # TODO: too late to fail like this?\n    encoded_parts = []\n    if has_scheme:\n        encoded_parts = [_encode_path_part(part, maximal=maximal)\n                         if part else part for part in text_parts]\n    else:\n        encoded_parts = [_encode_schemeless_path_part(text_parts[0])]\n        encoded_parts.extend([_encode_path_part(part, maximal=maximal)\n                              if part else part for part in text_parts[1:]])\n    if joined:\n        return u'/'.join(encoded_parts)\n    return tuple(encoded_parts)\n\n\ndef _encode_query_key(text, maximal=True):\n    \"\"\"\n    Percent-encode a single query string key or value.\n    \"\"\"\n    if maximal:\n        bytestr = normalize('NFC', text).encode('utf8')\n        return u''.join([_QUERY_KEY_QUOTE_MAP[b] for b in bytestr])\n    return u''.join([_QUERY_KEY_QUOTE_MAP[t] if t in _QUERY_KEY_DELIMS else t\n                     for t in text])\n\n\ndef _encode_query_value(text, maximal=True):\n    \"\"\"\n    Percent-encode a single query string key or value.\n    \"\"\"\n    if maximal:\n        bytestr = normalize('NFC', text).encode('utf8')\n        return u''.join([_QUERY_VALUE_QUOTE_MAP[b] for b in bytestr])\n    return u''.join([_QUERY_VALUE_QUOTE_MAP[t]\n                     if t in _QUERY_VALUE_DELIMS else t for t in text])\n\n\ndef _encode_fragment_part(text, maximal=True):\n    \"\"\"Quote the fragment part of the URL. Fragments don't have\n    subdelimiters, so the whole URL fragment can be passed.\n    \"\"\"\n    if maximal:\n        bytestr = normalize('NFC', text).encode('utf8')\n        return u''.join([_FRAGMENT_QUOTE_MAP[b] for b in bytestr])\n    return u''.join([_FRAGMENT_QUOTE_MAP[t] if t in _FRAGMENT_DELIMS else t\n                     for t in text])\n\n\ndef _encode_userinfo_part(text, maximal=True):\n    \"\"\"Quote special characters in either the username or password\n    section of the URL.\n    \"\"\"\n    if maximal:\n        bytestr = normalize('NFC', text).encode('utf8')\n        return u''.join([_USERINFO_PART_QUOTE_MAP[b] for b in bytestr])\n    return u''.join([_USERINFO_PART_QUOTE_MAP[t] if t in _USERINFO_DELIMS\n                     else t for t in text])\n\n\n\n# This port list painstakingly curated by hand searching through\n# https://www.iana.org/assignments/uri-schemes/uri-schemes.xhtml\n# and\n# https://www.iana.org/assignments/service-names-port-numbers/service-names-port-numbers.xhtml\nSCHEME_PORT_MAP = {'acap': 674, 'afp': 548, 'dict': 2628, 'dns': 53,\n                   'file': None, 'ftp': 21, 'git': 9418, 'gopher': 70,\n                   'http': 80, 'https': 443, 'imap': 143, 'ipp': 631,\n                   'ipps': 631, 'irc': 194, 'ircs': 6697, 'ldap': 389,\n                   'ldaps': 636, 'mms': 1755, 'msrp': 2855, 'msrps': None,\n                   'mtqp': 1038, 'nfs': 111, 'nntp': 119, 'nntps': 563,\n                   'pop': 110, 'prospero': 1525, 'redis': 6379, 'rsync': 873,\n                   'rtsp': 554, 'rtsps': 322, 'rtspu': 5005, 'sftp': 22,\n                   'smb': 445, 'snmp': 161, 'ssh': 22, 'steam': None,\n                   'svn': 3690, 'telnet': 23, 'ventrilo': 3784, 'vnc': 5900,\n                   'wais': 210, 'ws': 80, 'wss': 443, 'xmpp': None}\n\n# This list of schemes that don't use authorities is also from the link above.\nNO_NETLOC_SCHEMES = set(['urn', 'about', 'bitcoin', 'blob', 'data', 'geo',\n                         'magnet', 'mailto', 'news', 'pkcs11',\n                         'sip', 'sips', 'tel'])\n# As of Mar 11, 2017, there were 44 netloc schemes, and 13 non-netloc\n\n\ndef register_scheme(text, uses_netloc=True, default_port=None):\n    \"\"\"Registers new scheme information, resulting in correct port and\n    slash behavior from the URL object. There are dozens of standard\n    schemes preregistered, so this function is mostly meant for\n    proprietary internal customizations or stopgaps on missing\n    standards information. If a scheme seems to be missing, please\n    `file an issue`_!\n\n    Args:\n        text (unicode): Text representing the scheme.\n           (the 'http' in 'http://hatnote.com')\n        uses_netloc (bool): Does the scheme support specifying a\n           network host? For instance, \"http\" does, \"mailto\" does\n           not. Defaults to True.\n        default_port (int): The default port, if any, for netloc-using\n           schemes.\n\n    .. _file an issue: https://github.com/mahmoud/hyperlink/issues\n\n    \"\"\"\n    text = text.lower()\n    if default_port is not None:\n        try:\n            default_port = int(default_port)\n        except (ValueError, TypeError):\n            raise ValueError('default_port expected integer or None, not %r'\n                             % (default_port,))\n\n    if uses_netloc is True:\n        SCHEME_PORT_MAP[text] = default_port\n    elif uses_netloc is False:\n        if default_port is not None:\n            raise ValueError('unexpected default port while specifying'\n                             ' non-netloc scheme: %r' % default_port)\n        NO_NETLOC_SCHEMES.add(text)\n    else:\n        raise ValueError('uses_netloc expected bool, not: %r' % uses_netloc)\n\n    return\n\n\ndef scheme_uses_netloc(scheme, default=None):\n    \"\"\"Whether or not a URL uses :code:`:` or :code:`://` to separate the\n    scheme from the rest of the URL depends on the scheme's own\n    standard definition. There is no way to infer this behavior\n    from other parts of the URL. A scheme either supports network\n    locations or it does not.\n\n    The URL type's approach to this is to check for explicitly\n    registered schemes, with common schemes like HTTP\n    preregistered. This is the same approach taken by\n    :mod:`urlparse`.\n\n    URL adds two additional heuristics if the scheme as a whole is\n    not registered. First, it attempts to check the subpart of the\n    scheme after the last ``+`` character. This adds intuitive\n    behavior for schemes like ``git+ssh``. Second, if a URL with\n    an unrecognized scheme is loaded, it will maintain the\n    separator it sees.\n    \"\"\"\n    if not scheme:\n        return False\n    scheme = scheme.lower()\n    if scheme in SCHEME_PORT_MAP:\n        return True\n    if scheme in NO_NETLOC_SCHEMES:\n        return False\n    if scheme.split('+')[-1] in SCHEME_PORT_MAP:\n        return True\n    return default\n\n\nclass URLParseError(ValueError):\n    \"\"\"Exception inheriting from :exc:`ValueError`, raised when failing to\n    parse a URL. Mostly raised on invalid ports and IPv6 addresses.\n    \"\"\"\n    pass\n\n\ndef _optional(argument, default):\n    if argument is _UNSET:\n        return default\n    else:\n        return argument\n\n\ndef _typecheck(name, value, *types):\n    \"\"\"\n    Check that the given *value* is one of the given *types*, or raise an\n    exception describing the problem using *name*.\n    \"\"\"\n    if not types:\n        raise ValueError('expected one or more types, maybe use _textcheck?')\n    if not isinstance(value, types):\n        raise TypeError(\"expected %s for %s, got %r\"\n                        % (\" or \".join([t.__name__ for t in types]),\n                           name, value))\n    return value\n\n\ndef _textcheck(name, value, delims=frozenset(), nullable=False):\n    if not isinstance(value, unicode):\n        if nullable and value is None:\n            return value  # used by query string values\n        else:\n            str_name = \"unicode\" if PY2 else \"str\"\n            exp = str_name + ' or NoneType' if nullable else str_name\n            raise TypeError('expected %s for %s, got %r' % (exp, name, value))\n    if delims and set(value) & set(delims):  # TODO: test caching into regexes\n        raise ValueError('one or more reserved delimiters %s present in %s: %r'\n                         % (''.join(delims), name, value))\n    return value\n\n\ndef iter_pairs(iterable):\n    \"\"\"\n    Iterate over the (key, value) pairs in ``iterable``.\n\n    This handles dictionaries sensibly, and falls back to assuming the\n    iterable yields (key, value) pairs. This behaviour is similar to\n    what Python's ``dict()`` constructor does.\n    \"\"\"\n    if isinstance(iterable, Mapping):\n        iterable = iterable.items()\n    return iter(iterable)\n\n\ndef _decode_unreserved(text, normalize_case=False, encode_stray_percents=False):\n    return _percent_decode(text, normalize_case=normalize_case,\n                           encode_stray_percents=encode_stray_percents,\n                           _decode_map=_UNRESERVED_DECODE_MAP)\n\n\ndef _decode_userinfo_part(text, normalize_case=False, encode_stray_percents=False):\n    return _percent_decode(text, normalize_case=normalize_case,\n                           encode_stray_percents=encode_stray_percents,\n                           _decode_map=_USERINFO_DECODE_MAP)\n\n\ndef _decode_path_part(text, normalize_case=False, encode_stray_percents=False):\n    \"\"\"\n    >>> _decode_path_part(u'%61%77%2f%7a')\n    u'aw%2fz'\n    >>> _decode_path_part(u'%61%77%2f%7a', normalize_case=True)\n    u'aw%2Fz'\n    \"\"\"\n    return _percent_decode(text, normalize_case=normalize_case,\n                           encode_stray_percents=encode_stray_percents,\n                           _decode_map=_PATH_DECODE_MAP)\n\n\ndef _decode_query_key(text, normalize_case=False, encode_stray_percents=False):\n    return _percent_decode(text, normalize_case=normalize_case,\n                           encode_stray_percents=encode_stray_percents,\n                           _decode_map=_QUERY_KEY_DECODE_MAP)\n\n\ndef _decode_query_value(text, normalize_case=False, encode_stray_percents=False):\n    return _percent_decode(text, normalize_case=normalize_case,\n                           encode_stray_percents=encode_stray_percents,\n                           _decode_map=_QUERY_VALUE_DECODE_MAP)\n\n\ndef _decode_fragment_part(text, normalize_case=False, encode_stray_percents=False):\n    return _percent_decode(text, normalize_case=normalize_case,\n                           encode_stray_percents=encode_stray_percents,\n                           _decode_map=_FRAGMENT_DECODE_MAP)\n\n\ndef _percent_decode(text, normalize_case=False, subencoding='utf-8',\n                    raise_subencoding_exc=False, encode_stray_percents=False,\n                    _decode_map=_HEX_CHAR_MAP):\n    \"\"\"Convert percent-encoded text characters to their normal,\n    human-readable equivalents.\n\n    All characters in the input text must be encodable by\n    *subencoding*. All special characters underlying the values in the\n    percent-encoding must be decodable as *subencoding*. If a\n    non-*subencoding*-valid string is passed, the original text is\n    returned with no changes applied.\n\n    Only called by field-tailored variants, e.g.,\n    :func:`_decode_path_part`, as every percent-encodable part of the\n    URL has characters which should not be percent decoded.\n\n    >>> _percent_decode(u'abc%20def')\n    u'abc def'\n\n    Args:\n       text (unicode): Text with percent-encoding present.\n       normalize_case (bool): Whether undecoded percent segments, such\n          as encoded delimiters, should be uppercased, per RFC 3986\n          Section 2.1. See :func:`_decode_path_part` for an example.\n       subencoding (unicode): The name of the encoding underlying the\n          percent-encoding. Pass `False` to get back raw bytes.\n       raise_subencoding_exc (bool): Whether an error in decoding the bytes\n          underlying the percent-decoding should be raised.\n\n    Returns:\n       unicode: The percent-decoded version of *text*, decoded by\n         *subencoding*, unless `subencoding=False` which returns bytes.\n\n    \"\"\"\n    try:\n        quoted_bytes = text.encode('utf-8' if subencoding is False else subencoding)\n    except UnicodeEncodeError:\n        return text\n\n    bits = quoted_bytes.split(b'%')\n    if len(bits) == 1:\n        return text\n\n    res = [bits[0]]\n    append = res.append\n\n    for item in bits[1:]:\n        hexpair, rest = item[:2], item[2:]\n        try:\n            append(_decode_map[hexpair])\n            append(rest)\n        except KeyError:\n            pair_is_hex = hexpair in _HEX_CHAR_MAP\n            if pair_is_hex or not encode_stray_percents:\n                append(b'%')\n            else:\n                # if it's undecodable, treat as a real percent sign,\n                # which is reserved (because it wasn't in the\n                # context-aware _decode_map passed in), and should\n                # stay in an encoded state.\n                append(b'%25')\n            if normalize_case and pair_is_hex:\n                append(hexpair.upper())\n                append(rest)\n            else:\n                append(item)\n\n    unquoted_bytes = b''.join(res)\n\n    if subencoding is False:\n        return unquoted_bytes\n    try:\n        return unquoted_bytes.decode(subencoding)\n    except UnicodeDecodeError:\n        if raise_subencoding_exc:\n            raise\n        return text\n\n\ndef _decode_host(host):\n    \"\"\"Decode a host from ASCII-encodable text to IDNA-decoded text. If\n    the host text is not ASCII, it is returned unchanged, as it is\n    presumed that it is already IDNA-decoded.\n\n    Some technical details: _decode_host is built on top of the \"idna\"\n    package, which has some quirks:\n\n    Capital letters are not valid IDNA2008. The idna package will\n    raise an exception like this on capital letters:\n\n    > idna.core.InvalidCodepoint: Codepoint U+004B at position 1 ... not allowed\n\n    However, if a segment of a host (i.e., something in\n    url.host.split('.')) is already ASCII, idna doesn't perform its\n    usual checks. In fact, for capital letters it automatically\n    lowercases them.\n\n    This check and some other functionality can be bypassed by passing\n    uts46=True to idna.encode/decode. This allows a more permissive and\n    convenient interface. So far it seems like the balanced approach.\n\n    Example output (from idna==2.6):\n\n    >> idna.encode(u'mahmöud.io')\n    'xn--mahmud-zxa.io'\n    >> idna.encode(u'Mahmöud.io')\n    Traceback (most recent call last):\n      File \"<stdin>\", line 1, in <module>\n      File \"/home/mahmoud/virtualenvs/hyperlink/local/lib/python2.7/site-packages/idna/core.py\", line 355, in encode\n        result.append(alabel(label))\n      File \"/home/mahmoud/virtualenvs/hyperlink/local/lib/python2.7/site-packages/idna/core.py\", line 276, in alabel\n        check_label(label)\n      File \"/home/mahmoud/virtualenvs/hyperlink/local/lib/python2.7/site-packages/idna/core.py\", line 253, in check_label\n        raise InvalidCodepoint('Codepoint {0} at position {1} of {2} not allowed'.format(_unot(cp_value), pos+1, repr(label)))\n    idna.core.InvalidCodepoint: Codepoint U+004D at position 1 of u'Mahm\\xf6ud' not allowed\n    >> idna.encode(u'Mahmoud.io')\n    'Mahmoud.io'\n\n    # Similar behavior for decodes below\n    >> idna.decode(u'Mahmoud.io')\n    u'mahmoud.io\n    >> idna.decode(u'Méhmoud.io', uts46=True)\n    u'm\\xe9hmoud.io'\n    \"\"\"\n    if not host:\n        return u''\n    try:\n        host_bytes = host.encode(\"ascii\")\n    except UnicodeEncodeError:\n        host_text = host\n    else:\n        try:\n            host_text = idna_decode(host_bytes, uts46=True)\n        except ValueError:\n            # only reached on \"narrow\" (UCS-2) Python builds <3.4, see #7\n            # NOTE: not going to raise here, because there's no\n            # ambiguity in the IDNA, and the host is still\n            # technically usable\n            host_text = host\n    return host_text\n\n\ndef _resolve_dot_segments(path):\n    \"\"\"Normalize the URL path by resolving segments of '.' and '..'. For\n    more details, see `RFC 3986 section 5.2.4, Remove Dot Segments`_.\n\n    Args:\n       path (list): path segments in string form\n\n    Returns:\n       list: a new list of path segments with the '.' and '..' elements\n          removed and resolved.\n\n    .. _RFC 3986 section 5.2.4, Remove Dot Segments: https://tools.ietf.org/html/rfc3986#section-5.2.4\n    \"\"\"\n    segs = []\n\n    for seg in path:\n        if seg == u'.':\n            pass\n        elif seg == u'..':\n            if segs:\n                segs.pop()\n        else:\n            segs.append(seg)\n\n    if list(path[-1:]) in ([u'.'], [u'..']):\n        segs.append(u'')\n\n    return segs\n\n\ndef parse_host(host):\n    \"\"\"Parse the host into a tuple of ``(family, host)``, where family\n    is the appropriate :mod:`socket` module constant when the host is\n    an IP address. Family is ``None`` when the host is not an IP.\n\n    Will raise :class:`URLParseError` on invalid IPv6 constants.\n\n    Returns:\n      tuple: family (socket constant or None), host (string)\n\n    >>> parse_host('googlewebsite.com') == (None, 'googlewebsite.com')\n    True\n    >>> parse_host('::1') == (socket.AF_INET6, '::1')\n    True\n    >>> parse_host('192.168.1.1') == (socket.AF_INET, '192.168.1.1')\n    True\n    \"\"\"\n    if not host:\n        return None, u''\n    if u':' in host:\n        try:\n            inet_pton(socket.AF_INET6, host)\n        except socket.error as se:\n            raise URLParseError('invalid IPv6 host: %r (%r)' % (host, se))\n        except UnicodeEncodeError:\n            pass  # TODO: this can't be a real host right?\n        else:\n            family = socket.AF_INET6\n            return family, host\n    try:\n        inet_pton(socket.AF_INET, host)\n    except (socket.error, UnicodeEncodeError):\n        family = None  # not an IP\n    else:\n        family = socket.AF_INET\n    return family, host\n\n\nclass URL(object):\n    \"\"\"From blogs to billboards, URLs are so common, that it's easy to\n    overlook their complexity and power. With hyperlink's\n    :class:`URL` type, working with URLs doesn't have to be hard.\n\n    URLs are made of many parts. Most of these parts are officially\n    named in `RFC 3986`_ and this diagram may prove handy in identifying\n    them::\n\n       foo://user:pass@example.com:8042/over/there?name=ferret#nose\n       \\_/   \\_______/ \\_________/ \\__/\\_________/ \\_________/ \\__/\n        |        |          |        |      |           |        |\n      scheme  userinfo     host     port   path       query   fragment\n\n    While :meth:`~URL.from_text` is used for parsing whole URLs, the\n    :class:`URL` constructor builds a URL from the individual\n    components, like so::\n\n        >>> from hyperlink import URL\n        >>> url = URL(scheme=u'https', host=u'example.com', path=[u'hello', u'world'])\n        >>> print(url.to_text())\n        https://example.com/hello/world\n\n    The constructor runs basic type checks. All strings are expected\n    to be decoded (:class:`unicode` in Python 2). All arguments are\n    optional, defaulting to appropriately empty values. A full list of\n    constructor arguments is below.\n\n    Args:\n       scheme (unicode): The text name of the scheme.\n       host (unicode): The host portion of the network location\n       port (int): The port part of the network location. If\n          ``None`` or no port is passed, the port will default to\n          the default port of the scheme, if it is known. See the\n          ``SCHEME_PORT_MAP`` and :func:`register_default_port`\n          for more info.\n       path (tuple): A tuple of strings representing the\n          slash-separated parts of the path.\n       query (tuple): The query parameters, as a dictionary or\n          as an iterable of key-value pairs.\n       fragment (unicode): The fragment part of the URL.\n       rooted (bool): Whether or not the path begins with a slash.\n       userinfo (unicode): The username or colon-separated\n          username:password pair.\n       uses_netloc (bool): Indicates whether two slashes appear\n          between the scheme and the host (``http://eg.com`` vs\n          ``mailto:e@g.com``). Set automatically based on scheme.\n\n    All of these parts are also exposed as read-only attributes of\n    URL instances, along with several useful methods.\n\n    .. _RFC 3986: https://tools.ietf.org/html/rfc3986\n    .. _RFC 3987: https://tools.ietf.org/html/rfc3987\n    \"\"\"\n\n    def __init__(self, scheme=None, host=None, path=(), query=(), fragment=u'',\n                 port=None, rooted=None, userinfo=u'', uses_netloc=None):\n        if host is not None and scheme is None:\n            scheme = u'http'  # TODO: why\n        if port is None:\n            port = SCHEME_PORT_MAP.get(scheme)\n        if host and query and not path:\n            # per RFC 3986 6.2.3, \"a URI that uses the generic syntax\n            # for authority with an empty path should be normalized to\n            # a path of '/'.\"\n            path = (u'',)\n\n        # Now that we're done detecting whether they were passed, we can set\n        # them to their defaults:\n        if scheme is None:\n            scheme = u''\n        if host is None:\n            host = u''\n        if rooted is None:\n            rooted = bool(host)\n\n        # Set attributes.\n        self._scheme = _textcheck(\"scheme\", scheme)\n        if self._scheme:\n            if not _SCHEME_RE.match(self._scheme):\n                raise ValueError('invalid scheme: %r. Only alphanumeric, \"+\",'\n                                 ' \"-\", and \".\" allowed. Did you meant to call'\n                                 ' %s.from_text()?'\n                                 % (self._scheme, self.__class__.__name__))\n\n        _, self._host = parse_host(_textcheck('host', host, '/?#@'))\n        if isinstance(path, unicode):\n            raise TypeError(\"expected iterable of text for path, not: %r\"\n                            % (path,))\n        self._path = tuple((_textcheck(\"path segment\", segment, '/?#')\n                            for segment in path))\n        self._query = tuple(\n            (_textcheck(\"query parameter name\", k, '&=#'),\n             _textcheck(\"query parameter value\", v, '&#', nullable=True))\n            for k, v in iter_pairs(query))\n        self._fragment = _textcheck(\"fragment\", fragment)\n        self._port = _typecheck(\"port\", port, int, NoneType)\n        self._rooted = _typecheck(\"rooted\", rooted, bool)\n        self._userinfo = _textcheck(\"userinfo\", userinfo, '/?#@')\n\n        uses_netloc = scheme_uses_netloc(self._scheme, uses_netloc)\n        self._uses_netloc = _typecheck(\"uses_netloc\",\n                                       uses_netloc, bool, NoneType)\n\n        return\n\n    def get_decoded_url(self, lazy=False):\n        try:\n            return self._decoded_url\n        except AttributeError:\n            self._decoded_url = DecodedURL(self, lazy=lazy)\n        return self._decoded_url\n\n    @property\n    def scheme(self):\n        \"\"\"The scheme is a string, and the first part of an absolute URL, the\n        part before the first colon, and the part which defines the\n        semantics of the rest of the URL. Examples include \"http\",\n        \"https\", \"ssh\", \"file\", \"mailto\", and many others. See\n        :func:`~hyperlink.register_scheme()` for more info.\n        \"\"\"\n        return self._scheme\n\n    @property\n    def host(self):\n        \"\"\"The host is a string, and the second standard part of an absolute\n        URL. When present, a valid host must be a domain name, or an\n        IP (v4 or v6). It occurs before the first slash, or the second\n        colon, if a :attr:`~hyperlink.URL.port` is provided.\n        \"\"\"\n        return self._host\n\n    @property\n    def port(self):\n        \"\"\"The port is an integer that is commonly used in connecting to the\n        :attr:`host`, and almost never appears without it.\n\n        When not present in the original URL, this attribute defaults\n        to the scheme's default port. If the scheme's default port is\n        not known, and the port is not provided, this attribute will\n        be set to None.\n\n        >>> URL.from_text(u'http://example.com/pa/th').port\n        80\n        >>> URL.from_text(u'foo://example.com/pa/th').port\n        >>> URL.from_text(u'foo://example.com:8042/pa/th').port\n        8042\n\n        .. note::\n\n           Per the standard, when the port is the same as the schemes\n           default port, it will be omitted in the text URL.\n\n        \"\"\"\n        return self._port\n\n    @property\n    def path(self):\n        \"\"\"A tuple of strings, created by splitting the slash-separated\n        hierarchical path. Started by the first slash after the host,\n        terminated by a \"?\", which indicates the start of the\n        :attr:`~hyperlink.URL.query` string.\n        \"\"\"\n        return self._path\n\n    @property\n    def query(self):\n        \"\"\"Tuple of pairs, created by splitting the ampersand-separated\n        mapping of keys and optional values representing\n        non-hierarchical data used to identify the resource. Keys are\n        always strings. Values are strings when present, or None when\n        missing.\n\n        For more operations on the mapping, see\n        :meth:`~hyperlink.URL.get()`, :meth:`~hyperlink.URL.add()`,\n        :meth:`~hyperlink.URL.set()`, and\n        :meth:`~hyperlink.URL.delete()`.\n        \"\"\"\n        return self._query\n\n    @property\n    def fragment(self):\n        \"\"\"A string, the last part of the URL, indicated by the first \"#\"\n        after the :attr:`~hyperlink.URL.path` or\n        :attr:`~hyperlink.URL.query`. Enables indirect identification\n        of a secondary resource, like an anchor within an HTML page.\n\n        \"\"\"\n        return self._fragment\n\n    @property\n    def rooted(self):\n        \"\"\"Whether or not the path starts with a forward slash (``/``).\n\n        This is taken from the terminology in the BNF grammar,\n        specifically the \"path-rootless\", rule, since \"absolute path\"\n        and \"absolute URI\" are somewhat ambiguous. :attr:`path` does\n        not contain the implicit prefixed ``\"/\"`` since that is\n        somewhat awkward to work with.\n\n        \"\"\"\n        return self._rooted\n\n    @property\n    def userinfo(self):\n        \"\"\"The colon-separated string forming the username-password\n        combination.\n        \"\"\"\n        return self._userinfo\n\n    @property\n    def uses_netloc(self):\n        \"\"\"\n        \"\"\"\n        return self._uses_netloc\n\n    @property\n    def user(self):\n        \"\"\"\n        The user portion of :attr:`~hyperlink.URL.userinfo`.\n        \"\"\"\n        return self.userinfo.split(u':')[0]\n\n    def authority(self, with_password=False, **kw):\n        \"\"\"Compute and return the appropriate host/port/userinfo combination.\n\n        >>> url = URL.from_text(u'http://user:pass@localhost:8080/a/b?x=y')\n        >>> url.authority()\n        u'user:@localhost:8080'\n        >>> url.authority(with_password=True)\n        u'user:pass@localhost:8080'\n\n        Args:\n           with_password (bool): Whether the return value of this\n              method include the password in the URL, if it is\n              set. Defaults to False.\n\n        Returns:\n           str: The authority (network location and user information) portion\n              of the URL.\n        \"\"\"\n        # first, a bit of twisted compat\n        with_password = kw.pop('includeSecrets', with_password)\n        if kw:\n            raise TypeError('got unexpected keyword arguments: %r' % kw.keys())\n        host = self.host\n        if ':' in host:\n            hostport = ['[' + host + ']']\n        else:\n            hostport = [self.host]\n        if self.port != SCHEME_PORT_MAP.get(self.scheme):\n            hostport.append(unicode(self.port))\n        authority = []\n        if self.userinfo:\n            userinfo = self.userinfo\n            if not with_password and u\":\" in userinfo:\n                userinfo = userinfo[:userinfo.index(u\":\") + 1]\n            authority.append(userinfo)\n        authority.append(u\":\".join(hostport))\n        return u\"@\".join(authority)\n\n    def __eq__(self, other):\n        if not isinstance(other, self.__class__):\n            return NotImplemented\n        for attr in ['scheme', 'userinfo', 'host', 'query',\n                     'fragment', 'port', 'uses_netloc']:\n            if getattr(self, attr) != getattr(other, attr):\n                return False\n        if self.path == other.path or (self.path in _ROOT_PATHS\n                                       and other.path in _ROOT_PATHS):\n            return True\n        return False\n\n    def __ne__(self, other):\n        if not isinstance(other, self.__class__):\n            return NotImplemented\n        return not self.__eq__(other)\n\n    def __hash__(self):\n        return hash((self.__class__, self.scheme, self.userinfo, self.host,\n                     self.path, self.query, self.fragment, self.port,\n                     self.rooted, self.uses_netloc))\n\n    @property\n    def absolute(self):\n        \"\"\"Whether or not the URL is \"absolute\". Absolute URLs are complete\n        enough to resolve to a network resource without being relative\n        to a base URI.\n\n        >>> URL.from_text(u'http://wikipedia.org/').absolute\n        True\n        >>> URL.from_text(u'?a=b&c=d').absolute\n        False\n\n        Absolute URLs must have both a scheme and a host set.\n        \"\"\"\n        return bool(self.scheme and self.host)\n\n    def replace(self, scheme=_UNSET, host=_UNSET, path=_UNSET, query=_UNSET,\n                fragment=_UNSET, port=_UNSET, rooted=_UNSET, userinfo=_UNSET,\n                uses_netloc=_UNSET):\n        \"\"\":class:`URL` objects are immutable, which means that attributes\n        are designed to be set only once, at construction. Instead of\n        modifying an existing URL, one simply creates a copy with the\n        desired changes.\n\n        If any of the following arguments is omitted, it defaults to\n        the value on the current URL.\n\n        Args:\n           scheme (unicode): The text name of the scheme.\n           host (unicode): The host portion of the network location\n           port (int): The port part of the network location.\n           path (tuple): A tuple of strings representing the\n              slash-separated parts of the path.\n           query (tuple): The query parameters, as a tuple of\n              key-value pairs.\n           query (tuple): The query parameters, as a dictionary or\n              as an iterable of key-value pairs.\n           fragment (unicode): The fragment part of the URL.\n           rooted (bool): Whether or not the path begins with a slash.\n           userinfo (unicode): The username or colon-separated\n              username:password pair.\n           uses_netloc (bool): Indicates whether two slashes appear\n              between the scheme and the host (``http://eg.com`` vs\n              ``mailto:e@g.com``)\n\n        Returns:\n           URL: a copy of the current :class:`URL`, with new values for\n              parameters passed.\n\n        \"\"\"\n        return self.__class__(\n            scheme=_optional(scheme, self.scheme),\n            host=_optional(host, self.host),\n            path=_optional(path, self.path),\n            query=_optional(query, self.query),\n            fragment=_optional(fragment, self.fragment),\n            port=_optional(port, self.port),\n            rooted=_optional(rooted, self.rooted),\n            userinfo=_optional(userinfo, self.userinfo),\n            uses_netloc=_optional(uses_netloc, self.uses_netloc)\n        )\n\n    @classmethod\n    def from_text(cls, text):\n        \"\"\"Whereas the :class:`URL` constructor is useful for constructing\n        URLs from parts, :meth:`~URL.from_text` supports parsing whole\n        URLs from their string form::\n\n           >>> URL.from_text(u'http://example.com')\n           URL.from_text(u'http://example.com')\n           >>> URL.from_text(u'?a=b&x=y')\n           URL.from_text(u'?a=b&x=y')\n\n        As you can see above, it's also used as the :func:`repr` of\n        :class:`URL` objects. The natural counterpart to\n        :func:`~URL.to_text()`. This method only accepts *text*, so be\n        sure to decode those bytestrings.\n\n        Args:\n           text (unicode): A valid URL string.\n\n        Returns:\n           URL: The structured object version of the parsed string.\n\n        .. note::\n\n            Somewhat unexpectedly, URLs are a far more permissive\n            format than most would assume. Many strings which don't\n            look like URLs are still valid URLs. As a result, this\n            method only raises :class:`URLParseError` on invalid port\n            and IPv6 values in the host portion of the URL.\n\n        \"\"\"\n        um = _URL_RE.match(_textcheck('text', text))\n        try:\n            gs = um.groupdict()\n        except AttributeError:\n            raise URLParseError('could not parse url: %r' % text)\n\n        au_text = gs['authority'] or u''\n        au_m = _AUTHORITY_RE.match(au_text)\n        try:\n            au_gs = au_m.groupdict()\n        except AttributeError:\n            raise URLParseError('invalid authority %r in url: %r'\n                                % (au_text, text))\n        if au_gs['bad_host']:\n            raise URLParseError('invalid host %r in url: %r'\n                               % (au_gs['bad_host'], text))\n\n        userinfo = au_gs['userinfo'] or u''\n\n        host = au_gs['ipv6_host'] or au_gs['plain_host']\n        port = au_gs['port']\n        if port is not None:\n            try:\n                port = int(port)\n            except ValueError:\n                if not port:  # TODO: excessive?\n                    raise URLParseError('port must not be empty: %r' % au_text)\n                raise URLParseError('expected integer for port, not %r' % port)\n\n        scheme = gs['scheme'] or u''\n        fragment = gs['fragment'] or u''\n        uses_netloc = bool(gs['_netloc_sep'])\n\n        if gs['path']:\n            path = gs['path'].split(u\"/\")\n            if not path[0]:\n                path.pop(0)\n                rooted = True\n            else:\n                rooted = False\n        else:\n            path = ()\n            rooted = bool(au_text)\n        if gs['query']:\n            query = ((qe.split(u\"=\", 1) if u'=' in qe else (qe, None))\n                     for qe in gs['query'].split(u\"&\"))\n        else:\n            query = ()\n        return cls(scheme, host, path, query, fragment, port,\n                   rooted, userinfo, uses_netloc)\n\n    def normalize(self, scheme=True, host=True, path=True, query=True,\n                  fragment=True, userinfo=True, percents=True):\n        \"\"\"Return a new URL object with several standard normalizations\n        applied:\n\n        * Decode unreserved characters (`RFC 3986 2.3`_)\n        * Uppercase remaining percent-encoded octets (`RFC 3986 2.1`_)\n        * Convert scheme and host casing to lowercase (`RFC 3986 3.2.2`_)\n        * Resolve any \".\" and \"..\" references in the path (`RFC 3986 6.2.2.3`_)\n        * Ensure an ending slash on URLs with an empty path (`RFC 3986 6.2.3`_)\n        * Encode any stray percent signs (`%`) in percent-encoded\n          fields (path, query, fragment, userinfo) (`RFC 3986 2.4`_)\n\n        All are applied by default, but normalizations can be disabled\n        per-part by passing `False` for that part's corresponding\n        name.\n\n        Args:\n           scheme (bool): Convert the scheme to lowercase\n           host (bool): Convert the host to lowercase\n           path (bool): Normalize the path (see above for details)\n           query (bool): Normalize the query string\n           fragment (bool): Normalize the fragment\n           userinfo (bool): Normalize the userinfo\n           percents (bool): Encode isolated percent signs\n              for any percent-encoded fields which are being\n              normalized (defaults to True).\n\n        >>> url = URL.from_text(u'Http://example.COM/a/../b/./c%2f?%61%')\n        >>> print(url.normalize().to_text())\n        http://example.com/b/c%2F?a%25\n\n        .. _RFC 3986 3.2.2: https://tools.ietf.org/html/rfc3986#section-3.2.2\n        .. _RFC 3986 2.3: https://tools.ietf.org/html/rfc3986#section-2.3\n        .. _RFC 3986 2.1: https://tools.ietf.org/html/rfc3986#section-2.1\n        .. _RFC 3986 6.2.2.3: https://tools.ietf.org/html/rfc3986#section-6.2.2.3\n        .. _RFC 3986 6.2.3: https://tools.ietf.org/html/rfc3986#section-6.2.3\n        .. _RFC 3986 2.4: https://tools.ietf.org/html/rfc3986#section-2.4\n\n        \"\"\"\n        kw = {}\n        if scheme:\n            kw['scheme'] = self.scheme.lower()\n        if host:\n            kw['host'] = self.host.lower()\n        def _dec_unres(target):\n            return _decode_unreserved(target, normalize_case=True,\n                                      encode_stray_percents=percents)\n        if path:\n            if self.path:\n                kw['path'] = [_dec_unres(p) for p in _resolve_dot_segments(self.path)]\n            else:\n                kw['path'] = (u'',)\n        if query:\n            kw['query'] = [(_dec_unres(k), _dec_unres(v) if v else v)\n                           for k, v in self.query]\n        if fragment:\n            kw['fragment'] = _dec_unres(self.fragment)\n        if userinfo:\n            kw['userinfo'] = u':'.join([_dec_unres(p)\n                                        for p in self.userinfo.split(':', 1)])\n\n        return self.replace(**kw)\n\n    def child(self, *segments):\n        \"\"\"Make a new :class:`URL` where the given path segments are a child\n        of this URL, preserving other parts of the URL, including the\n        query string and fragment.\n\n        For example::\n\n            >>> url = URL.from_text(u'http://localhost/a/b?x=y')\n            >>> child_url = url.child(u\"c\", u\"d\")\n            >>> child_url.to_text()\n            u'http://localhost/a/b/c/d?x=y'\n\n        Args:\n           segments (unicode): Additional parts to be joined and added to\n              the path, like :func:`os.path.join`. Special characters\n              in segments will be percent encoded.\n\n        Returns:\n           URL: A copy of the current URL with the extra path segments.\n\n        \"\"\"\n        if not segments:\n            return self\n\n        segments = [_textcheck('path segment', s) for s in segments]\n        new_segs = _encode_path_parts(segments, joined=False, maximal=False)\n        new_path = self.path[:-1 if (self.path and self.path[-1] == u'')\n                             else None] + new_segs\n        return self.replace(path=new_path)\n\n    def sibling(self, segment):\n        \"\"\"Make a new :class:`URL` with a single path segment that is a\n        sibling of this URL path.\n\n        Args:\n           segment (unicode): A single path segment.\n\n        Returns:\n           URL: A copy of the current URL with the last path segment\n              replaced by *segment*. Special characters such as\n              ``/?#`` will be percent encoded.\n\n        \"\"\"\n        _textcheck('path segment', segment)\n        new_path = self.path[:-1] + (_encode_path_part(segment),)\n        return self.replace(path=new_path)\n\n    def click(self, href=u''):\n        \"\"\"Resolve the given URL relative to this URL.\n\n        The resulting URI should match what a web browser would\n        generate if you visited the current URL and clicked on *href*.\n\n           >>> url = URL.from_text(u'http://blog.hatnote.com/')\n           >>> url.click(u'/post/155074058790').to_text()\n           u'http://blog.hatnote.com/post/155074058790'\n           >>> url = URL.from_text(u'http://localhost/a/b/c/')\n           >>> url.click(u'../d/./e').to_text()\n           u'http://localhost/a/b/d/e'\n\n        Args:\n            href (unicode): A string representing a clicked URL.\n\n        Return:\n            URL: A copy of the current URL with navigation logic applied.\n\n        For more information, see `RFC 3986 section 5`_.\n\n        .. _RFC 3986 section 5: https://tools.ietf.org/html/rfc3986#section-5\n        \"\"\"\n        if href:\n            if isinstance(href, URL):\n                clicked = href\n            else:\n                # TODO: This error message is not completely accurate,\n                # as URL objects are now also valid, but Twisted's\n                # test suite (wrongly) relies on this exact message.\n                _textcheck('relative URL', href)\n                clicked = URL.from_text(href)\n            if clicked.absolute:\n                return clicked\n        else:\n            clicked = self\n\n        query = clicked.query\n        if clicked.scheme and not clicked.rooted:\n            # Schemes with relative paths are not well-defined.  RFC 3986 calls\n            # them a \"loophole in prior specifications\" that should be avoided,\n            # or supported only for backwards compatibility.\n            raise NotImplementedError('absolute URI with rootless path: %r'\n                                      % (href,))\n        else:\n            if clicked.rooted:\n                path = clicked.path\n            elif clicked.path:\n                path = self.path[:-1] + clicked.path\n            else:\n                path = self.path\n                if not query:\n                    query = self.query\n        return self.replace(scheme=clicked.scheme or self.scheme,\n                            host=clicked.host or self.host,\n                            port=clicked.port or self.port,\n                            path=_resolve_dot_segments(path),\n                            query=query,\n                            fragment=clicked.fragment)\n\n    def to_uri(self):\n        u\"\"\"Make a new :class:`URL` instance with all non-ASCII characters\n        appropriately percent-encoded. This is useful to do in preparation\n        for sending a :class:`URL` over a network protocol.\n\n        For example::\n\n            >>> URL.from_text(u'https://ايران.com/foo⇧bar/').to_uri()\n            URL.from_text(u'https://xn--mgba3a4fra.com/foo%E2%87%A7bar/')\n\n        Returns:\n            URL: A new instance with its path segments, query parameters, and\n            hostname encoded, so that they are all in the standard\n            US-ASCII range.\n        \"\"\"\n        new_userinfo = u':'.join([_encode_userinfo_part(p) for p in\n                                  self.userinfo.split(':', 1)])\n        new_path = _encode_path_parts(self.path, has_scheme=bool(self.scheme),\n                                      rooted=False, joined=False, maximal=True)\n        new_host = self.host if not self.host else idna_encode(self.host, uts46=True).decode(\"ascii\")\n        return self.replace(\n            userinfo=new_userinfo,\n            host=new_host,\n            path=new_path,\n            query=tuple([(_encode_query_key(k, maximal=True),\n                          _encode_query_value(v, maximal=True)\n                          if v is not None else None)\n                         for k, v in self.query]),\n            fragment=_encode_fragment_part(self.fragment, maximal=True)\n        )\n\n    def to_iri(self):\n        u\"\"\"Make a new :class:`URL` instance with all but a few reserved\n        characters decoded into human-readable format.\n\n        Percent-encoded Unicode and IDNA-encoded hostnames are\n        decoded, like so::\n\n            >>> url = URL.from_text(u'https://xn--mgba3a4fra.example.com/foo%E2%87%A7bar/')\n            >>> print(url.to_iri().to_text())\n            https://ايران.example.com/foo⇧bar/\n\n        .. note::\n\n            As a general Python issue, \"narrow\" (UCS-2) builds of\n            Python may not be able to fully decode certain URLs, and\n            the in those cases, this method will return a best-effort,\n            partially-decoded, URL which is still valid. This issue\n            does not affect any Python builds 3.4+.\n\n        Returns:\n            URL: A new instance with its path segments, query parameters, and\n            hostname decoded for display purposes.\n        \"\"\"\n        new_userinfo = u':'.join([_decode_userinfo_part(p) for p in\n                                  self.userinfo.split(':', 1)])\n        host_text = _decode_host(self.host)\n\n        return self.replace(userinfo=new_userinfo,\n                            host=host_text,\n                            path=[_decode_path_part(segment)\n                                  for segment in self.path],\n                            query=[(_decode_query_key(k),\n                                    _decode_query_value(v)\n                                    if v is not None else None)\n                                   for k, v in self.query],\n                            fragment=_decode_fragment_part(self.fragment))\n\n    def to_text(self, with_password=False):\n        \"\"\"Render this URL to its textual representation.\n\n        By default, the URL text will *not* include a password, if one\n        is set. RFC 3986 considers using URLs to represent such\n        sensitive information as deprecated. Quoting from RFC 3986,\n        `section 3.2.1`:\n\n            \"Applications should not render as clear text any data after the\n            first colon (\":\") character found within a userinfo subcomponent\n            unless the data after the colon is the empty string (indicating no\n            password).\"\n\n        Args:\n            with_password (bool): Whether or not to include the\n               password in the URL text. Defaults to False.\n\n        Returns:\n            str: The serialized textual representation of this URL,\n            such as ``u\"http://example.com/some/path?some=query\"``.\n\n        The natural counterpart to :class:`URL.from_text()`.\n\n        .. _section 3.2.1: https://tools.ietf.org/html/rfc3986#section-3.2.1\n        \"\"\"\n        scheme = self.scheme\n        authority = self.authority(with_password)\n        path = _encode_path_parts(self.path,\n                                  rooted=self.rooted,\n                                  has_scheme=bool(scheme),\n                                  has_authority=bool(authority),\n                                  maximal=False)\n        query_parts = []\n        for k, v in self.query:\n            if v is None:\n                query_parts.append(_encode_query_key(k, maximal=False))\n            else:\n                query_parts.append(u'='.join((_encode_query_key(k, maximal=False),\n                                              _encode_query_value(v, maximal=False))))\n        query_string = u'&'.join(query_parts)\n\n        fragment = self.fragment\n\n        parts = []\n        _add = parts.append\n        if scheme:\n            _add(scheme)\n            _add(':')\n        if authority:\n            _add('//')\n            _add(authority)\n        elif (scheme and path[:2] != '//' and self.uses_netloc):\n            _add('//')\n        if path:\n            if scheme and authority and path[:1] != '/':\n                _add('/')  # relpaths with abs authorities auto get '/'\n            _add(path)\n        if query_string:\n            _add('?')\n            _add(query_string)\n        if fragment:\n            _add('#')\n            _add(fragment)\n        return u''.join(parts)\n\n    def __repr__(self):\n        \"\"\"Convert this URL to an representation that shows all of its\n        constituent parts, as well as being a valid argument to\n        :func:`eval`.\n        \"\"\"\n        return '%s.from_text(%r)' % (self.__class__.__name__, self.to_text())\n\n    def _to_bytes(self):\n        \"\"\"\n        Allows for direct usage of URL objects with libraries like\n        requests, which automatically stringify URL parameters. See\n        issue #49.\n        \"\"\"\n        return self.to_uri().to_text().encode('ascii')\n\n    if PY2:\n        __str__ = _to_bytes\n        __unicode__ = to_text\n    else:\n        __bytes__ = _to_bytes\n        __str__ = to_text\n\n    # # Begin Twisted Compat Code\n    asURI = to_uri\n    asIRI = to_iri\n\n    @classmethod\n    def fromText(cls, s):\n        return cls.from_text(s)\n\n    def asText(self, includeSecrets=False):\n        return self.to_text(with_password=includeSecrets)\n\n    def __dir__(self):\n        try:\n            ret = object.__dir__(self)\n        except AttributeError:\n            # object.__dir__ == AttributeError  # pdw for py2\n            ret = dir(self.__class__) + list(self.__dict__.keys())\n        ret = sorted(set(ret) - set(['fromText', 'asURI', 'asIRI', 'asText']))\n        return ret\n\n    # # End Twisted Compat Code\n\n    def add(self, name, value=None):\n        \"\"\"Make a new :class:`URL` instance with a given query argument,\n        *name*, added to it with the value *value*, like so::\n\n            >>> URL.from_text(u'https://example.com/?x=y').add(u'x')\n            URL.from_text(u'https://example.com/?x=y&x')\n            >>> URL.from_text(u'https://example.com/?x=y').add(u'x', u'z')\n            URL.from_text(u'https://example.com/?x=y&x=z')\n\n        Args:\n            name (unicode): The name of the query parameter to add. The\n                part before the ``=``.\n            value (unicode): The value of the query parameter to add. The\n                part after the ``=``. Defaults to ``None``, meaning no\n                value.\n\n        Returns:\n            URL: A new :class:`URL` instance with the parameter added.\n        \"\"\"\n        return self.replace(query=self.query + ((name, value),))\n\n    def set(self, name, value=None):\n        \"\"\"Make a new :class:`URL` instance with the query parameter *name*\n        set to *value*. All existing occurences, if any are replaced\n        by the single name-value pair.\n\n            >>> URL.from_text(u'https://example.com/?x=y').set(u'x')\n            URL.from_text(u'https://example.com/?x')\n            >>> URL.from_text(u'https://example.com/?x=y').set(u'x', u'z')\n            URL.from_text(u'https://example.com/?x=z')\n\n        Args:\n            name (unicode): The name of the query parameter to set. The\n                part before the ``=``.\n            value (unicode): The value of the query parameter to set. The\n                part after the ``=``. Defaults to ``None``, meaning no\n                value.\n\n        Returns:\n            URL: A new :class:`URL` instance with the parameter set.\n        \"\"\"\n        # Preserve the original position of the query key in the list\n        q = [(k, v) for (k, v) in self.query if k != name]\n        idx = next((i for (i, (k, v)) in enumerate(self.query)\n                    if k == name), -1)\n        q[idx:idx] = [(name, value)]\n        return self.replace(query=q)\n\n    def get(self, name):\n        \"\"\"Get a list of values for the given query parameter, *name*::\n\n            >>> url = URL.from_text(u'?x=1&x=2')\n            >>> url.get('x')\n            [u'1', u'2']\n            >>> url.get('y')\n            []\n\n        If the given *name* is not set, an empty list is returned. A\n        list is always returned, and this method raises no exceptions.\n\n        Args:\n            name (unicode): The name of the query parameter to get.\n\n        Returns:\n            list: A list of all the values associated with the key, in\n                string form.\n\n        \"\"\"\n        return [value for (key, value) in self.query if name == key]\n\n    def remove(self, name, value=_UNSET, limit=None):\n        \"\"\"Make a new :class:`URL` instance with occurrences of the query\n        parameter *name* removed, or, if *value* is set, parameters\n        matching *name* and *value*. No exception is raised if the\n        parameter is not already set.\n\n        Args:\n            name (unicode): The name of the query parameter to remove.\n            value (unicode): Optional value to additionally filter\n               on. Setting this removes query parameters which match\n               both name and value.\n            limit (int): Optional maximum number of parameters to remove.\n\n        Returns:\n            URL: A new :class:`URL` instance with the parameter removed.\n        \"\"\"\n        if limit is None:\n            if value is _UNSET:\n                nq = [(k, v) for (k, v) in self.query if k != name]\n            else:\n                nq = [(k, v) for (k, v) in self.query if not (k == name and v == value)]\n        else:\n            nq, removed_count = [], 0\n\n            for k, v in self.query:\n                if k == name and (value is _UNSET or v == value) and removed_count < limit:\n                    removed_count += 1  # drop it\n                else:\n                    nq.append((k, v))  # keep it\n\n        return self.replace(query=nq)\n\n\nEncodedURL = URL  # An alias better describing what the URL really is\n\n\nclass DecodedURL(object):\n    \"\"\"DecodedURL is a type meant to act as a higher-level interface to\n    the URL. It is the `unicode` to URL's `bytes`. `DecodedURL` has\n    almost exactly the same API as `URL`, but everything going in and\n    out is in its maximally decoded state. All percent decoding is\n    handled automatically.\n\n    Where applicable, a UTF-8 encoding is presumed. Be advised that\n    some interactions can raise :exc:`UnicodeEncodeErrors` and\n    :exc:`UnicodeDecodeErrors`, just like when working with\n    bytestrings. Examples of such interactions include handling query\n    strings encoding binary data, and paths containing segments with\n    special characters encoded with codecs other than UTF-8.\n\n    Args:\n       url (URL): A :class:`URL` object to wrap.\n       lazy (bool): Set to True to avoid pre-decode all parts of the\n           URL to check for validity. Defaults to False.\n\n    \"\"\"\n    def __init__(self, url, lazy=False):\n        self._url = url\n        if not lazy:\n            # cache the following, while triggering any decoding\n            # issues with decodable fields\n            self.host, self.userinfo, self.path, self.query, self.fragment\n        return\n\n    @classmethod\n    def from_text(cls, text, lazy=False):\n        \"\"\"\\\n        Make a `DecodedURL` instance from any text string containing a URL.\n\n        Args:\n          text (unicode): Text containing the URL\n          lazy (bool): Whether to pre-decode all parts of the URL to\n              check for validity. Defaults to True.\n        \"\"\"\n        _url = URL.from_text(text)\n        return cls(_url, lazy=lazy)\n\n    @property\n    def encoded_url(self):\n        \"\"\"Access the underlying :class:`URL` object, which has any special\n        characters encoded.\n        \"\"\"\n        return self._url\n\n    def to_text(self, *a, **kw):\n        \"Passthrough to :meth:`~hyperlink.URL.to_text()`\"\n        return self._url.to_text(*a, **kw)\n\n    def to_uri(self, *a, **kw):\n        \"Passthrough to :meth:`~hyperlink.URL.to_uri()`\"\n        return self._url.to_uri(*a, **kw)\n\n    def to_iri(self, *a, **kw):\n        \"Passthrough to :meth:`~hyperlink.URL.to_iri()`\"\n        return self._url.to_iri(*a, **kw)\n\n    def click(self, href=u''):\n        \"Return a new DecodedURL wrapping the result of :meth:`~hyperlink.URL.click()`\"\n        if isinstance(href, DecodedURL):\n            href = href._url\n        return self.__class__(self._url.click(href=href))\n\n    def sibling(self, segment):\n        \"\"\"Automatically encode any reserved characters in *segment* and\n        return a new `DecodedURL` wrapping the result of\n        :meth:`~hyperlink.URL.sibling()`\n        \"\"\"\n        return self.__class__(self._url.sibling(_encode_reserved(segment)))\n\n    def child(self, *segments):\n        \"\"\"Automatically encode any reserved characters in *segments* and\n        return a new `DecodedURL` wrapping the result of\n        :meth:`~hyperlink.URL.child()`.\n        \"\"\"\n        if not segments:\n            return self\n        new_segs = [_encode_reserved(s) for s in segments]\n        return self.__class__(self._url.child(*new_segs))\n\n    def normalize(self, *a, **kw):\n        \"Return a new `DecodedURL` wrapping the result of :meth:`~hyperlink.URL.normalize()`\"\n        return self.__class__(self._url.normalize(*a, **kw))\n\n    @property\n    def absolute(self):\n        return self._url.absolute\n\n    @property\n    def scheme(self):\n        return self._url.scheme\n\n    @property\n    def host(self):\n        return _decode_host(self._url.host)\n\n    @property\n    def port(self):\n        return self._url.port\n\n    @property\n    def rooted(self):\n        return self._url.rooted\n\n    @property\n    def path(self):\n        try:\n            return self._path\n        except AttributeError:\n            pass\n        self._path = tuple([_percent_decode(p, raise_subencoding_exc=True)\n                            for p in self._url.path])\n        return self._path\n\n    @property\n    def query(self):\n        try:\n            return self._query\n        except AttributeError:\n            pass\n        _q = [tuple(_percent_decode(x, raise_subencoding_exc=True)\n                    if x is not None else None\n                    for x in (k, v))\n              for k, v in self._url.query]\n        self._query = tuple(_q)\n        return self._query\n\n    @property\n    def fragment(self):\n        try:\n            return self._fragment\n        except AttributeError:\n            pass\n        frag = self._url.fragment\n        self._fragment = _percent_decode(frag, raise_subencoding_exc=True)\n        return self._fragment\n\n    @property\n    def userinfo(self):\n        try:\n            return self._userinfo\n        except AttributeError:\n            pass\n        self._userinfo = tuple([_percent_decode(p, raise_subencoding_exc=True)\n                                for p in self._url.userinfo.split(':', 1)])\n        return self._userinfo\n\n    @property\n    def user(self):\n        return self.userinfo[0]\n\n    @property\n    def uses_netloc(self):\n        return self._url.uses_netloc\n\n    def replace(self, scheme=_UNSET, host=_UNSET, path=_UNSET, query=_UNSET,\n                fragment=_UNSET, port=_UNSET, rooted=_UNSET, userinfo=_UNSET,\n                uses_netloc=_UNSET):\n        \"\"\"While the signature is the same, this `replace()` differs a little\n        from URL.replace. For instance, it accepts userinfo as a\n        tuple, not as a string, handling the case of having a username\n        containing a `:`. As with the rest of the methods on\n        DecodedURL, if you pass a reserved character, it will be\n        automatically encoded instead of an error being raised.\n\n        \"\"\"\n        if path is not _UNSET:\n            path = [_encode_reserved(p) for p in path]\n        if query is not _UNSET:\n            query = [[_encode_reserved(x)\n                      if x is not None else None\n                      for x in (k, v)]\n                     for k, v in iter_pairs(query)]\n        if userinfo is not _UNSET:\n            if len(userinfo) > 2:\n                raise ValueError('userinfo expected sequence of [\"user\"] or'\n                                 ' [\"user\", \"password\"], got %r' % userinfo)\n            userinfo = u':'.join([_encode_reserved(p) for p in userinfo])\n        new_url = self._url.replace(scheme=scheme,\n                                    host=host,\n                                    path=path,\n                                    query=query,\n                                    fragment=fragment,\n                                    port=port,\n                                    rooted=rooted,\n                                    userinfo=userinfo,\n                                    uses_netloc=uses_netloc)\n        return self.__class__(url=new_url)\n\n    def get(self, name):\n        \"Get the value of all query parameters whose name matches *name*\"\n        return [v for (k, v) in self.query if name == k]\n\n    def add(self, name, value=None):\n        \"Return a new DecodedURL with the query parameter *name* and *value* added.\"\n        return self.replace(query=self.query + ((name, value),))\n\n    def set(self, name, value=None):\n        \"Return a new DecodedURL with query parameter *name* set to *value*\"\n        query = self.query\n        q = [(k, v) for (k, v) in query if k != name]\n        idx = next((i for (i, (k, v)) in enumerate(query) if k == name), -1)\n        q[idx:idx] = [(name, value)]\n        return self.replace(query=q)\n\n    def remove(self, name, value=_UNSET, limit=None):\n        \"\"\"Return a new DecodedURL with query parameter *name* removed.\n\n        Optionally also filter for *value*, as well as cap the number\n        of parameters removed with *limit*.\n        \"\"\"\n        if limit is None:\n            if value is _UNSET:\n                nq = [(k, v) for (k, v) in self.query if k != name]\n            else:\n                nq = [(k, v) for (k, v) in self.query if not (k == name and v == value)]\n        else:\n            nq, removed_count = [], 0\n            for k, v in self.query:\n                if k == name and (value is _UNSET or v == value) and removed_count < limit:\n                    removed_count += 1  # drop it\n                else:\n                    nq.append((k, v))  # keep it\n\n        return self.replace(query=nq)\n\n    def __repr__(self):\n        cn = self.__class__.__name__\n        return '%s(url=%r)' % (cn, self._url)\n\n    def __str__(self):\n        # TODO: the underlying URL's __str__ needs to change to make\n        # this work as the URL, see #55\n        return str(self._url)\n\n    def __eq__(self, other):\n        if not isinstance(other, self.__class__):\n            return NotImplemented\n        return self.normalize().to_uri() == other.normalize().to_uri()\n\n    def __ne__(self, other):\n        if not isinstance(other, self.__class__):\n            return NotImplemented\n        return not self.__eq__(other)\n\n    def __hash__(self):\n        return hash((self.__class__, self.scheme, self.userinfo, self.host,\n                     self.path, self.query, self.fragment, self.port,\n                     self.rooted, self.uses_netloc))\n\n    # # Begin Twisted Compat Code\n    asURI = to_uri\n    asIRI = to_iri\n\n    @classmethod\n    def fromText(cls, s, lazy=False):\n        return cls.from_text(s, lazy=lazy)\n\n    def asText(self, includeSecrets=False):\n        return self.to_text(with_password=includeSecrets)\n\n    def __dir__(self):\n        try:\n            ret = object.__dir__(self)\n        except AttributeError:\n            # object.__dir__ == AttributeError  # pdw for py2\n            ret = dir(self.__class__) + list(self.__dict__.keys())\n        ret = sorted(set(ret) - set(['fromText', 'asURI', 'asIRI', 'asText']))\n        return ret\n\n    # # End Twisted Compat Code\n\n\ndef parse(url, decoded=True, lazy=False):\n    \"\"\"Automatically turn text into a structured URL object.\n\n    Args:\n\n       decoded (bool): Whether or not to return a :class:`DecodedURL`,\n          which automatically handles all\n          encoding/decoding/quoting/unquoting for all the various\n          accessors of parts of the URL, or an :class:`EncodedURL`,\n          which has the same API, but requires handling of special\n          characters for different parts of the URL.\n\n       lazy (bool): In the case of `decoded=True`, this controls\n          whether the URL is decoded immediately or as accessed. The\n          default, `lazy=False`, checks all encoded parts of the URL\n          for decodability.\n    \"\"\"\n    enc_url = EncodedURL.from_text(url)\n    if not decoded:\n        return enc_url\n    dec_url = DecodedURL(enc_url, lazy=lazy)\n    return dec_url\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink/test/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink/test/common.py",
    "content": "\n\nfrom unittest import TestCase\n\n\nclass HyperlinkTestCase(TestCase):\n    \"\"\"This type mostly exists to provide a backwards-compatible\n    assertRaises method for Python 2.6 testing.\n    \"\"\"\n    def assertRaises(self, excClass, callableObj=None, *args, **kwargs):\n        \"\"\"Fail unless an exception of class excClass is raised\n           by callableObj when invoked with arguments args and keyword\n           arguments kwargs. If a different type of exception is\n           raised, it will not be caught, and the test case will be\n           deemed to have suffered an error, exactly as for an\n           unexpected exception.\n\n           If called with callableObj omitted or None, will return a\n           context object used like this::\n\n                with self.assertRaises(SomeException):\n                    do_something()\n\n           The context manager keeps a reference to the exception as\n           the 'exception' attribute. This allows you to inspect the\n           exception after the assertion::\n\n               with self.assertRaises(SomeException) as cm:\n                   do_something()\n               the_exception = cm.exception\n               self.assertEqual(the_exception.error_code, 3)\n        \"\"\"\n        context = _AssertRaisesContext(excClass, self)\n        if callableObj is None:\n            return context\n        with context:\n            callableObj(*args, **kwargs)\n\n\nclass _AssertRaisesContext(object):\n    \"A context manager used to implement HyperlinkTestCase.assertRaises.\"\n\n    def __init__(self, expected, test_case):\n        self.expected = expected\n        self.failureException = test_case.failureException\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_value, tb):\n        if exc_type is None:\n            exc_name = self.expected.__name__\n            raise self.failureException(\"%s not raised\" % (exc_name,))\n        if not issubclass(exc_type, self.expected):\n            # let unexpected exceptions pass through\n            return False\n        self.exception = exc_value  # store for later retrieval\n        return True\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink/test/test_common.py",
    "content": "\"\"\"\nTests for hyperlink.test.common\n\"\"\"\nfrom unittest import TestCase\nfrom .common import HyperlinkTestCase\n\n\nclass _ExpectedException(Exception):\n    \"\"\"An exception used to test HyperlinkTestCase.assertRaises.\n\n    \"\"\"\n\n\nclass _UnexpectedException(Exception):\n    \"\"\"An exception used to test HyperlinkTestCase.assertRaises.\n\n    \"\"\"\n\n\nclass TestHyperlink(TestCase):\n    \"\"\"Tests for HyperlinkTestCase\"\"\"\n\n    def setUp(self):\n        self.hyperlink_test = HyperlinkTestCase(\"run\")\n\n    def test_assertRaisesWithCallable(self):\n        \"\"\"HyperlinkTestCase.assertRaises does not raise an AssertionError\n        when given a callable that, when called with the provided\n        arguments, raises the expected exception.\n\n        \"\"\"\n        called_with = []\n\n        def raisesExpected(*args, **kwargs):\n            called_with.append((args, kwargs))\n            raise _ExpectedException\n\n        self.hyperlink_test.assertRaises(_ExpectedException,\n                                         raisesExpected, 1, keyword=True)\n        self.assertEqual(called_with, [((1,), {\"keyword\": True})])\n\n    def test_assertRaisesWithCallableUnexpectedException(self):\n        \"\"\"When given a callable that raises an unexpected exception,\n        HyperlinkTestCase.assertRaises raises that exception.\n\n        \"\"\"\n\n        def doesNotRaiseExpected(*args, **kwargs):\n            raise _UnexpectedException\n\n        try:\n            self.hyperlink_test.assertRaises(_ExpectedException,\n                                             doesNotRaiseExpected)\n        except _UnexpectedException:\n            pass\n\n    def test_assertRaisesWithCallableDoesNotRaise(self):\n        \"\"\"HyperlinkTestCase.assertRaises raises an AssertionError when given\n        a callable that, when called, does not raise any exception.\n\n        \"\"\"\n\n        def doesNotRaise(*args, **kwargs):\n            return True\n\n        try:\n            self.hyperlink_test.assertRaises(_ExpectedException,\n                                             doesNotRaise)\n        except AssertionError:\n            pass\n\n    def test_assertRaisesContextManager(self):\n        \"\"\"HyperlinkTestCase.assertRaises does not raise an AssertionError\n        when used as a context manager with a suite that raises the\n        expected exception.  The context manager stores the exception\n        instance under its `exception` instance variable.\n\n        \"\"\"\n        with self.hyperlink_test.assertRaises(_ExpectedException) as cm:\n            raise _ExpectedException\n\n        self.assertTrue(isinstance(cm.exception, _ExpectedException))\n\n    def test_assertRaisesContextManagerUnexpectedException(self):\n        \"\"\"When used as a context manager with a block that raises an\n        unexpected exception, HyperlinkTestCase.assertRaises raises\n        that unexpected exception.\n\n        \"\"\"\n        try:\n            with self.hyperlink_test.assertRaises(_ExpectedException):\n                raise _UnexpectedException\n        except _UnexpectedException:\n            pass\n\n    def test_assertRaisesContextManagerDoesNotRaise(self):\n        \"\"\"HyperlinkTestcase.assertRaises raises an AssertionError when used\n        as a context manager with a block that does not raise any\n        exception.\n\n        \"\"\"\n        try:\n            with self.hyperlink_test.assertRaises(_ExpectedException):\n                pass\n        except AssertionError:\n            pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink/test/test_decoded_url.py",
    "content": "# -*- coding: utf-8 -*-\n\nfrom __future__ import unicode_literals\n\nfrom .. import DecodedURL\nfrom .._url import _percent_decode\nfrom .common import HyperlinkTestCase\n\nBASIC_URL = 'http://example.com/#'\nTOTAL_URL = \"https://%75%73%65%72:%00%00%00%00@xn--bcher-kva.ch:8080/a/nice%20nice/./path/?zot=23%25&zut#frég\"\n\n\nclass TestURL(HyperlinkTestCase):\n\n    def test_durl_basic(self):\n        bdurl = DecodedURL.from_text(BASIC_URL)\n        assert bdurl.scheme == 'http'\n        assert bdurl.host == 'example.com'\n        assert bdurl.port == 80\n        assert bdurl.path == ('',)\n        assert bdurl.fragment == ''\n\n        durl = DecodedURL.from_text(TOTAL_URL)\n\n        assert durl.scheme == 'https'\n        assert durl.host == 'bücher.ch'\n        assert durl.port == 8080\n        assert durl.path == ('a', 'nice nice', '.', 'path', '')\n        assert durl.fragment == 'frég'\n        assert durl.get('zot') == ['23%']\n\n        assert durl.user == 'user'\n        assert durl.userinfo == ('user', '\\0\\0\\0\\0')\n\n    def test_passthroughs(self):\n        # just basic tests for the methods that more or less pass straight\n        # through to the underlying URL\n\n        durl = DecodedURL.from_text(TOTAL_URL)\n        assert durl.sibling('te%t').path[-1] == 'te%t'\n        assert durl.child('../test2%').path[-1] == '../test2%'\n        assert durl.child() == durl\n        assert durl.child() is durl\n        assert durl.click('/').path[-1] == ''\n        assert durl.user == 'user'\n\n        assert '.' in durl.path\n        assert '.' not in durl.normalize().path\n\n        assert durl.to_uri().fragment == 'fr%C3%A9g'\n        assert ' ' in durl.to_iri().path[1]\n\n        assert durl.to_text(with_password=True) == TOTAL_URL\n\n        assert durl.absolute\n        assert durl.rooted\n\n        assert durl == durl.encoded_url.get_decoded_url()\n\n        durl2 = DecodedURL.from_text(TOTAL_URL, lazy=True)\n        assert durl2 == durl2.encoded_url.get_decoded_url(lazy=True)\n\n        assert str(DecodedURL.from_text(BASIC_URL).child(' ')) == 'http://example.com/%20'\n\n        assert not (durl == 1)\n        assert durl != 1\n\n    def test_repr(self):\n        durl = DecodedURL.from_text(TOTAL_URL)\n        assert repr(durl) == 'DecodedURL(url=' + repr(durl._url) + ')'\n\n    def test_query_manipulation(self):\n        durl = DecodedURL.from_text(TOTAL_URL)\n\n        assert durl.get('zot') == ['23%']\n        durl = durl.add(' ', 'space')\n        assert durl.get(' ') == ['space']\n        durl = durl.set(' ', 'spa%ed')\n        assert durl.get(' ') == ['spa%ed']\n\n        durl = DecodedURL(url=durl.to_uri())\n        assert durl.get(' ') == ['spa%ed']\n        durl = durl.remove(' ')\n        assert durl.get(' ') == []\n\n        durl = DecodedURL.from_text('/?%61rg=b&arg=c')\n        assert durl.get('arg') == ['b', 'c']\n\n        assert durl.set('arg', 'd').get('arg') == ['d']\n\n        durl = DecodedURL.from_text(u\"https://example.com/a/b/?fóó=1&bar=2&fóó=3\")\n        assert durl.remove(\"fóó\") == DecodedURL.from_text(\"https://example.com/a/b/?bar=2\")\n        assert durl.remove(\"fóó\", value=\"1\") == DecodedURL.from_text(\"https://example.com/a/b/?bar=2&fóó=3\")\n        assert durl.remove(\"fóó\", limit=1) == DecodedURL.from_text(\"https://example.com/a/b/?bar=2&fóó=3\")\n        assert durl.remove(\"fóó\", value=\"1\", limit=0) == DecodedURL.from_text(\"https://example.com/a/b/?fóó=1&bar=2&fóó=3\")\n\n    def test_equality_and_hashability(self):\n        durl = DecodedURL.from_text(TOTAL_URL)\n        durl2 = DecodedURL.from_text(TOTAL_URL)\n        burl = DecodedURL.from_text(BASIC_URL)\n        durl_uri = durl.to_uri()\n\n        assert durl == durl\n        assert durl == durl2\n        assert durl != burl\n        assert durl != None\n        assert durl != durl._url\n\n        durl_map = {}\n        durl_map[durl] = durl\n        durl_map[durl2] = durl2\n\n        assert len(durl_map) == 1\n\n        durl_map[burl] = burl\n\n        assert len(durl_map) == 2\n\n        durl_map[durl_uri] = durl_uri\n\n        assert len(durl_map) == 3\n\n    def test_replace_roundtrip(self):\n        durl = DecodedURL.from_text(TOTAL_URL)\n\n        durl2 = durl.replace(scheme=durl.scheme,\n                             host=durl.host,\n                             path=durl.path,\n                             query=durl.query,\n                             fragment=durl.fragment,\n                             port=durl.port,\n                             rooted=durl.rooted,\n                             userinfo=durl.userinfo,\n                             uses_netloc=durl.uses_netloc)\n\n        assert durl == durl2\n\n    def test_replace_userinfo(self):\n        durl = DecodedURL.from_text(TOTAL_URL)\n        with self.assertRaises(ValueError):\n            durl.replace(userinfo=['user', 'pw', 'thiswillcauseafailure'])\n        return\n\n    def test_twisted_compat(self):\n        durl = DecodedURL.from_text(TOTAL_URL)\n\n        assert durl == DecodedURL.fromText(TOTAL_URL)\n        assert 'to_text' in dir(durl)\n        assert 'asText' not in dir(durl)\n        assert durl.to_text() == durl.asText()\n\n    def test_percent_decode_bytes(self):\n        assert _percent_decode('%00', subencoding=False) == b'\\0'\n\n    def test_percent_decode_mixed(self):\n        # See https://github.com/python-hyper/hyperlink/pull/59 for a\n        # nice discussion of the possibilities\n        assert _percent_decode('abcdé%C3%A9éfg') == 'abcdéééfg'\n\n        # still allow percent encoding in the case of an error\n        assert _percent_decode('abcdé%C3éfg') == 'abcdé%C3éfg'\n\n        # ...unless explicitly told otherwise\n        with self.assertRaises(UnicodeDecodeError):\n            _percent_decode('abcdé%C3éfg', raise_subencoding_exc=True)\n\n        # check that getting raw bytes works ok\n        assert _percent_decode('a%00b', subencoding=False) == b'a\\x00b'\n\n        # when not encodable as subencoding\n        assert _percent_decode('é%25é', subencoding='ascii') == 'é%25é'\n\n    def test_click_decoded_url(self):\n        durl = DecodedURL.from_text(TOTAL_URL)\n        durl_dest = DecodedURL.from_text('/tëst')\n\n        clicked = durl.click(durl_dest)\n        assert clicked.host == durl.host\n        assert clicked.path == durl_dest.path\n        assert clicked.path == ('tëst',)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink/test/test_parse.py",
    "content": "# -*- coding: utf-8 -*-\n\nfrom __future__ import unicode_literals\n\nfrom .common import HyperlinkTestCase\nfrom hyperlink import parse, EncodedURL, DecodedURL\n\nBASIC_URL = 'http://example.com/#'\nTOTAL_URL = \"https://%75%73%65%72:%00%00%00%00@xn--bcher-kva.ch:8080/a/nice%20nice/./path/?zot=23%25&zut#frég\"\nUNDECODABLE_FRAG_URL = TOTAL_URL + '%C3'\n# the %C3 above percent-decodes to an unpaired \\xc3 byte which makes this\n# invalid utf8\n\n\nclass TestURL(HyperlinkTestCase):\n    def test_parse(self):\n        purl = parse(TOTAL_URL)\n        assert isinstance(purl, DecodedURL)\n        assert purl.user == 'user'\n        assert purl.get('zot') == ['23%']\n        assert purl.fragment == 'frég'\n\n        purl2 = parse(TOTAL_URL, decoded=False)\n        assert isinstance(purl2, EncodedURL)\n        assert purl2.get('zot') == ['23%25']\n\n        with self.assertRaises(UnicodeDecodeError):\n            purl3 = parse(UNDECODABLE_FRAG_URL)\n\n        purl3 = parse(UNDECODABLE_FRAG_URL, lazy=True)\n\n        with self.assertRaises(UnicodeDecodeError):\n            purl3.fragment\n\n        return\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink/test/test_scheme_registration.py",
    "content": "# -*- coding: utf-8 -*-\nfrom __future__ import unicode_literals\n\n\nfrom .. import _url\nfrom .common import HyperlinkTestCase\nfrom .._url import register_scheme, URL\n\n\nclass TestSchemeRegistration(HyperlinkTestCase):\n\n    def setUp(self):\n        self._orig_scheme_port_map = dict(_url.SCHEME_PORT_MAP)\n        self._orig_no_netloc_schemes = set(_url.NO_NETLOC_SCHEMES)\n\n    def tearDown(self):\n        _url.SCHEME_PORT_MAP = self._orig_scheme_port_map\n        _url.NO_NETLOC_SCHEMES = self._orig_no_netloc_schemes\n\n    def test_register_scheme_basic(self):\n        register_scheme('deltron', uses_netloc=True, default_port=3030)\n\n        u1 = URL.from_text('deltron://example.com')\n        assert u1.scheme == 'deltron'\n        assert u1.port == 3030\n        assert u1.uses_netloc is True\n\n        # test netloc works even when the original gives no indication\n        u2 = URL.from_text('deltron:')\n        u2 = u2.replace(host='example.com')\n        assert u2.to_text() == 'deltron://example.com'\n\n        # test default port means no emission\n        u3 = URL.from_text('deltron://example.com:3030')\n        assert u3.to_text() == 'deltron://example.com'\n\n        register_scheme('nonetron', default_port=3031)\n        u4 = URL(scheme='nonetron')\n        u4 = u4.replace(host='example.com')\n        assert u4.to_text() == 'nonetron://example.com'\n\n    def test_register_no_netloc_scheme(self):\n        register_scheme('noloctron', uses_netloc=False)\n        u4 = URL(scheme='noloctron')\n        u4 = u4.replace(path=(\"example\", \"path\"))\n        assert u4.to_text() == 'noloctron:example/path'\n\n    def test_register_no_netloc_with_port(self):\n        with self.assertRaises(ValueError):\n            register_scheme('badnetlocless', uses_netloc=False, default_port=7)\n\n    def test_invalid_uses_netloc(self):\n        with self.assertRaises(ValueError):\n            register_scheme('badnetloc', uses_netloc=None)\n        with self.assertRaises(ValueError):\n            register_scheme('badnetloc', uses_netloc=object())\n\n    def test_register_invalid_uses_netloc(self):\n        with self.assertRaises(ValueError):\n            register_scheme('lol', uses_netloc=lambda: 'nope')\n\n    def test_register_invalid_port(self):\n        with self.assertRaises(ValueError):\n            register_scheme('nope', default_port=lambda: 'lol')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink/test/test_url.py",
    "content": "# -*- coding: utf-8 -*-\n\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom __future__ import unicode_literals\n\nimport sys\nimport socket\n\nfrom .common import HyperlinkTestCase\nfrom .. import URL, URLParseError\n# automatically import the py27 windows implementation when appropriate\nfrom .. import _url\nfrom .._url import inet_pton, SCHEME_PORT_MAP, parse_host\n\n\nPY2 = (sys.version_info[0] == 2)\nunicode = type(u'')\n\n\nBASIC_URL = \"http://www.foo.com/a/nice/path/?zot=23&zut\"\n\n# Examples from RFC 3986 section 5.4, Reference Resolution Examples\nrelativeLinkBaseForRFC3986 = 'http://a/b/c/d;p?q'\nrelativeLinkTestsForRFC3986 = [\n    # \"Normal\"\n    # ('g:h', 'g:h'),  # can't click on a scheme-having url without an abs path\n    ('g', 'http://a/b/c/g'),\n    ('./g', 'http://a/b/c/g'),\n    ('g/', 'http://a/b/c/g/'),\n    ('/g', 'http://a/g'),\n    ('//g', 'http://g'),\n    ('?y', 'http://a/b/c/d;p?y'),\n    ('g?y', 'http://a/b/c/g?y'),\n    ('#s', 'http://a/b/c/d;p?q#s'),\n    ('g#s', 'http://a/b/c/g#s'),\n    ('g?y#s', 'http://a/b/c/g?y#s'),\n    (';x', 'http://a/b/c/;x'),\n    ('g;x', 'http://a/b/c/g;x'),\n    ('g;x?y#s', 'http://a/b/c/g;x?y#s'),\n    ('', 'http://a/b/c/d;p?q'),\n    ('.', 'http://a/b/c/'),\n    ('./', 'http://a/b/c/'),\n    ('..', 'http://a/b/'),\n    ('../', 'http://a/b/'),\n    ('../g', 'http://a/b/g'),\n    ('../..', 'http://a/'),\n    ('../../', 'http://a/'),\n    ('../../g', 'http://a/g'),\n\n    # Abnormal examples\n    # \"..\" cannot be used to change the authority component of a URI.\n    ('../../../g', 'http://a/g'),\n    ('../../../../g', 'http://a/g'),\n\n    # Only include \".\" and \"..\" when they are only part of a larger segment,\n    # not by themselves.\n    ('/./g', 'http://a/g'),\n    ('/../g', 'http://a/g'),\n    ('g.', 'http://a/b/c/g.'),\n    ('.g', 'http://a/b/c/.g'),\n    ('g..', 'http://a/b/c/g..'),\n    ('..g', 'http://a/b/c/..g'),\n    # Unnecessary or nonsensical forms of \".\" and \"..\".\n    ('./../g', 'http://a/b/g'),\n    ('./g/.', 'http://a/b/c/g/'),\n    ('g/./h', 'http://a/b/c/g/h'),\n    ('g/../h', 'http://a/b/c/h'),\n    ('g;x=1/./y', 'http://a/b/c/g;x=1/y'),\n    ('g;x=1/../y', 'http://a/b/c/y'),\n    # Separating the reference's query and fragment components from the path.\n    ('g?y/./x', 'http://a/b/c/g?y/./x'),\n    ('g?y/../x', 'http://a/b/c/g?y/../x'),\n    ('g#s/./x', 'http://a/b/c/g#s/./x'),\n    ('g#s/../x', 'http://a/b/c/g#s/../x')\n]\n\n\nROUNDTRIP_TESTS = (\n    \"http://localhost\",\n    \"http://localhost/\",\n    \"http://127.0.0.1/\",\n    \"http://[::127.0.0.1]/\",\n    \"http://[::1]/\",\n    \"http://localhost/foo\",\n    \"http://localhost/foo/\",\n    \"http://localhost/foo!!bar/\",\n    \"http://localhost/foo%20bar/\",\n    \"http://localhost/foo%2Fbar/\",\n    \"http://localhost/foo?n\",\n    \"http://localhost/foo?n=v\",\n    \"http://localhost/foo?n=/a/b\",\n    \"http://example.com/foo!@$bar?b!@z=123\",\n    \"http://localhost/asd?a=asd%20sdf/345\",\n    \"http://(%2525)/(%2525)?(%2525)&(%2525)=(%2525)#(%2525)\",\n    \"http://(%C3%A9)/(%C3%A9)?(%C3%A9)&(%C3%A9)=(%C3%A9)#(%C3%A9)\",\n    \"?sslrootcert=/Users/glyph/Downloads/rds-ca-2015-root.pem&sslmode=verify\",\n\n    # from boltons.urlutils' tests\n\n    'http://googlewebsite.com/e-shops.aspx',\n    'http://example.com:8080/search?q=123&business=Nothing%20Special',\n    'http://hatnote.com:9000/?arg=1&arg=2&arg=3',\n    'https://xn--bcher-kva.ch',\n    'http://xn--ggbla1c4e.xn--ngbc5azd/',\n    'http://tools.ietf.org/html/rfc3986#section-3.4',\n    # 'http://wiki:pedia@hatnote.com',\n    'ftp://ftp.rfc-editor.org/in-notes/tar/RFCs0001-0500.tar.gz',\n    'http://[1080:0:0:0:8:800:200C:417A]/index.html',\n    'ssh://192.0.2.16:2222/',\n    'https://[::101.45.75.219]:80/?hi=bye',\n    'ldap://[::192.9.5.5]/dc=example,dc=com??sub?(sn=Jensen)',\n    'mailto:me@example.com?to=me@example.com&body=hi%20http://wikipedia.org',\n    'news:alt.rec.motorcycle',\n    'tel:+1-800-867-5309',\n    'urn:oasis:member:A00024:x',\n    ('magnet:?xt=urn:btih:1a42b9e04e122b97a5254e3df77ab3c4b7da725f&dn=Puppy%'\n     '20Linux%20precise-5.7.1.iso&tr=udp://tracker.openbittorrent.com:80&'\n     'tr=udp://tracker.publicbt.com:80&tr=udp://tracker.istole.it:6969&'\n     'tr=udp://tracker.ccc.de:80&tr=udp://open.demonii.com:1337'),\n\n    # percent-encoded delimiters in percent-encodable fields\n\n    'https://%3A@example.com/',  # colon in username\n    'https://%40@example.com/',  # at sign in username\n    'https://%2f@example.com/',  # slash in username\n    'https://a:%3a@example.com/',  # colon in password\n    'https://a:%40@example.com/',  # at sign in password\n    'https://a:%2f@example.com/',  # slash in password\n    'https://a:%3f@example.com/',  # question mark in password\n    'https://example.com/%2F/',  # slash in path\n    'https://example.com/%3F/',  # question mark in path\n    'https://example.com/%23/',  # hash in path\n    'https://example.com/?%23=b',  # hash in query param name\n    'https://example.com/?%3D=b',  # equals in query param name\n    'https://example.com/?%26=b',  # ampersand in query param name\n    'https://example.com/?a=%23',  # hash in query param value\n    'https://example.com/?a=%26',  # ampersand in query param value\n    'https://example.com/?a=%3D',  # equals in query param value\n    # double-encoded percent sign in all percent-encodable positions:\n    \"http://(%2525):(%2525)@example.com/(%2525)/?(%2525)=(%2525)#(%2525)\",\n    # colon in first part of schemeless relative url\n    'first_seg_rel_path__colon%3Anotok/second_seg__colon%3Aok',\n)\n\n\nclass TestURL(HyperlinkTestCase):\n    \"\"\"\n    Tests for L{URL}.\n    \"\"\"\n\n    def assertUnicoded(self, u):\n        \"\"\"\n        The given L{URL}'s components should be L{unicode}.\n\n        @param u: The L{URL} to test.\n        \"\"\"\n        self.assertTrue(isinstance(u.scheme, unicode) or u.scheme is None,\n                        repr(u))\n        self.assertTrue(isinstance(u.host, unicode) or u.host is None,\n                        repr(u))\n        for seg in u.path:\n            self.assertEqual(type(seg), unicode, repr(u))\n        for (k, v) in u.query:\n            self.assertEqual(type(seg), unicode, repr(u))\n            self.assertTrue(v is None or isinstance(v, unicode), repr(u))\n        self.assertEqual(type(u.fragment), unicode, repr(u))\n\n    def assertURL(self, u, scheme, host, path, query,\n                  fragment, port, userinfo=''):\n        \"\"\"\n        The given L{URL} should have the given components.\n\n        @param u: The actual L{URL} to examine.\n\n        @param scheme: The expected scheme.\n\n        @param host: The expected host.\n\n        @param path: The expected path.\n\n        @param query: The expected query.\n\n        @param fragment: The expected fragment.\n\n        @param port: The expected port.\n\n        @param userinfo: The expected userinfo.\n        \"\"\"\n        actual = (u.scheme, u.host, u.path, u.query,\n                  u.fragment, u.port, u.userinfo)\n        expected = (scheme, host, tuple(path), tuple(query),\n                    fragment, port, u.userinfo)\n        self.assertEqual(actual, expected)\n\n    def test_initDefaults(self):\n        \"\"\"\n        L{URL} should have appropriate default values.\n        \"\"\"\n        def check(u):\n            self.assertUnicoded(u)\n            self.assertURL(u, 'http', '', [], [], '', 80, '')\n\n        check(URL('http', ''))\n        check(URL('http', '', [], []))\n        check(URL('http', '', [], [], ''))\n\n    def test_init(self):\n        \"\"\"\n        L{URL} should accept L{unicode} parameters.\n        \"\"\"\n        u = URL('s', 'h', ['p'], [('k', 'v'), ('k', None)], 'f')\n        self.assertUnicoded(u)\n        self.assertURL(u, 's', 'h', ['p'], [('k', 'v'), ('k', None)],\n                       'f', None)\n\n        self.assertURL(URL('http', '\\xe0', ['\\xe9'],\n                           [('\\u03bb', '\\u03c0')], '\\u22a5'),\n                       'http', '\\xe0', ['\\xe9'],\n                       [('\\u03bb', '\\u03c0')], '\\u22a5', 80)\n\n    def test_initPercent(self):\n        \"\"\"\n        L{URL} should accept (and not interpret) percent characters.\n        \"\"\"\n        u = URL('s', '%68', ['%70'], [('%6B', '%76'), ('%6B', None)],\n                '%66')\n        self.assertUnicoded(u)\n        self.assertURL(u,\n                       's', '%68', ['%70'],\n                       [('%6B', '%76'), ('%6B', None)],\n                       '%66', None)\n\n    def test_repr(self):\n        \"\"\"\n        L{URL.__repr__} will display the canonical form of the URL, wrapped in\n        a L{URL.from_text} invocation, so that it is C{eval}-able but still easy\n        to read.\n        \"\"\"\n        self.assertEqual(\n            repr(URL(scheme='http', host='foo', path=['bar'],\n                     query=[('baz', None), ('k', 'v')],\n                     fragment='frob')),\n            \"URL.from_text(%s)\" % (repr(u\"http://foo/bar?baz&k=v#frob\"),)\n        )\n\n    def test_from_text(self):\n        \"\"\"\n        Round-tripping L{URL.from_text} with C{str} results in an equivalent\n        URL.\n        \"\"\"\n        urlpath = URL.from_text(BASIC_URL)\n        self.assertEqual(BASIC_URL, urlpath.to_text())\n\n    def test_roundtrip(self):\n        \"\"\"\n        L{URL.to_text} should invert L{URL.from_text}.\n        \"\"\"\n        for test in ROUNDTRIP_TESTS:\n            result = URL.from_text(test).to_text(with_password=True)\n            self.assertEqual(test, result)\n\n    def test_roundtrip_double_iri(self):\n        for test in ROUNDTRIP_TESTS:\n            url = URL.from_text(test)\n            iri = url.to_iri()\n            double_iri = iri.to_iri()\n            assert iri == double_iri\n\n            iri_text = iri.to_text(with_password=True)\n            double_iri_text = double_iri.to_text(with_password=True)\n            assert iri_text == double_iri_text\n        return\n\n    def test_equality(self):\n        \"\"\"\n        Two URLs decoded using L{URL.from_text} will be equal (C{==}) if they\n        decoded same URL string, and unequal (C{!=}) if they decoded different\n        strings.\n        \"\"\"\n        urlpath = URL.from_text(BASIC_URL)\n        self.assertEqual(urlpath, URL.from_text(BASIC_URL))\n        self.assertNotEqual(\n            urlpath,\n            URL.from_text('ftp://www.anotherinvaliddomain.com/'\n                          'foo/bar/baz/?zot=21&zut')\n        )\n\n    def test_fragmentEquality(self):\n        \"\"\"\n        An URL created with the empty string for a fragment compares equal\n        to an URL created with an unspecified fragment.\n        \"\"\"\n        self.assertEqual(URL(fragment=''), URL())\n        self.assertEqual(URL.from_text(u\"http://localhost/#\"),\n                         URL.from_text(u\"http://localhost/\"))\n\n    def test_child(self):\n        \"\"\"\n        L{URL.child} appends a new path segment, but does not affect the query\n        or fragment.\n        \"\"\"\n        urlpath = URL.from_text(BASIC_URL)\n        self.assertEqual(\"http://www.foo.com/a/nice/path/gong?zot=23&zut\",\n                         urlpath.child('gong').to_text())\n        self.assertEqual(\"http://www.foo.com/a/nice/path/gong%2F?zot=23&zut\",\n                         urlpath.child('gong/').to_text())\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/path/gong%2Fdouble?zot=23&zut\",\n            urlpath.child('gong/double').to_text()\n        )\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/path/gong%2Fdouble%2F?zot=23&zut\",\n            urlpath.child('gong/double/').to_text()\n        )\n\n    def test_multiChild(self):\n        \"\"\"\n        L{URL.child} receives multiple segments as C{*args} and appends each in\n        turn.\n        \"\"\"\n        url = URL.from_text('http://example.com/a/b')\n        self.assertEqual(url.child('c', 'd', 'e').to_text(),\n                         'http://example.com/a/b/c/d/e')\n\n    def test_childInitRoot(self):\n        \"\"\"\n        L{URL.child} of a L{URL} without a path produces a L{URL} with a single\n        path segment.\n        \"\"\"\n        childURL = URL(host=u\"www.foo.com\").child(u\"c\")\n        self.assertTrue(childURL.rooted)\n        self.assertEqual(\"http://www.foo.com/c\", childURL.to_text())\n\n    def test_emptyChild(self):\n        \"\"\"\n        L{URL.child} without any new segments returns the original L{URL}.\n        \"\"\"\n        url = URL(host=u\"www.foo.com\")\n        self.assertEqual(url.child(), url)\n\n    def test_sibling(self):\n        \"\"\"\n        L{URL.sibling} of a L{URL} replaces the last path segment, but does not\n        affect the query or fragment.\n        \"\"\"\n        urlpath = URL.from_text(BASIC_URL)\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/path/sister?zot=23&zut\",\n            urlpath.sibling('sister').to_text()\n        )\n        # Use an url without trailing '/' to check child removal.\n        url_text = \"http://www.foo.com/a/nice/path?zot=23&zut\"\n        urlpath = URL.from_text(url_text)\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/sister?zot=23&zut\",\n            urlpath.sibling('sister').to_text()\n        )\n\n    def test_click(self):\n        \"\"\"\n        L{URL.click} interprets the given string as a relative URI-reference\n        and returns a new L{URL} interpreting C{self} as the base absolute URI.\n        \"\"\"\n        urlpath = URL.from_text(BASIC_URL)\n        # A null uri should be valid (return here).\n        self.assertEqual(\"http://www.foo.com/a/nice/path/?zot=23&zut\",\n                          urlpath.click(\"\").to_text())\n        # A simple relative path remove the query.\n        self.assertEqual(\"http://www.foo.com/a/nice/path/click\",\n                          urlpath.click(\"click\").to_text())\n        # An absolute path replace path and query.\n        self.assertEqual(\"http://www.foo.com/click\",\n                          urlpath.click(\"/click\").to_text())\n        # Replace just the query.\n        self.assertEqual(\"http://www.foo.com/a/nice/path/?burp\",\n                          urlpath.click(\"?burp\").to_text())\n        # One full url to another should not generate '//' between authority.\n        # and path\n        self.assertTrue(\"//foobar\" not in\n                        urlpath.click('http://www.foo.com/foobar').to_text())\n\n        # From a url with no query clicking a url with a query, the query\n        # should be handled properly.\n        u = URL.from_text('http://www.foo.com/me/noquery')\n        self.assertEqual('http://www.foo.com/me/17?spam=158',\n                         u.click('/me/17?spam=158').to_text())\n\n        # Check that everything from the path onward is removed when the click\n        # link has no path.\n        u = URL.from_text('http://localhost/foo?abc=def')\n        self.assertEqual(u.click('http://www.python.org').to_text(),\n                         'http://www.python.org')\n\n        # https://twistedmatrix.com/trac/ticket/8184\n        u = URL.from_text('http://hatnote.com/a/b/../c/./d/e/..')\n        res = 'http://hatnote.com/a/c/d/'\n        self.assertEqual(u.click('').to_text(), res)\n\n        # test click default arg is same as empty string above\n        self.assertEqual(u.click().to_text(), res)\n\n        # test click on a URL instance\n        u = URL.fromText('http://localhost/foo/?abc=def')\n        u2 = URL.from_text('bar')\n        u3 = u.click(u2)\n        self.assertEqual(u3.to_text(), 'http://localhost/foo/bar')\n\n    def test_clickRFC3986(self):\n        \"\"\"\n        L{URL.click} should correctly resolve the examples in RFC 3986.\n        \"\"\"\n        base = URL.from_text(relativeLinkBaseForRFC3986)\n        for (ref, expected) in relativeLinkTestsForRFC3986:\n            self.assertEqual(base.click(ref).to_text(), expected)\n\n    def test_clickSchemeRelPath(self):\n        \"\"\"\n        L{URL.click} should not accept schemes with relative paths.\n        \"\"\"\n        base = URL.from_text(relativeLinkBaseForRFC3986)\n        self.assertRaises(NotImplementedError, base.click, 'g:h')\n        self.assertRaises(NotImplementedError, base.click, 'http:h')\n\n    def test_cloneUnchanged(self):\n        \"\"\"\n        Verify that L{URL.replace} doesn't change any of the arguments it\n        is passed.\n        \"\"\"\n        urlpath = URL.from_text('https://x:1/y?z=1#A')\n        self.assertEqual(urlpath.replace(urlpath.scheme,\n                                         urlpath.host,\n                                         urlpath.path,\n                                         urlpath.query,\n                                         urlpath.fragment,\n                                         urlpath.port),\n                         urlpath)\n        self.assertEqual(urlpath.replace(), urlpath)\n\n    def test_clickCollapse(self):\n        \"\"\"\n        L{URL.click} collapses C{.} and C{..} according to RFC 3986 section\n        5.2.4.\n        \"\"\"\n        tests = [\n            ['http://localhost/', '.', 'http://localhost/'],\n            ['http://localhost/', '..', 'http://localhost/'],\n            ['http://localhost/a/b/c', '.', 'http://localhost/a/b/'],\n            ['http://localhost/a/b/c', '..', 'http://localhost/a/'],\n            ['http://localhost/a/b/c', './d/e', 'http://localhost/a/b/d/e'],\n            ['http://localhost/a/b/c', '../d/e', 'http://localhost/a/d/e'],\n            ['http://localhost/a/b/c', '/./d/e', 'http://localhost/d/e'],\n            ['http://localhost/a/b/c', '/../d/e', 'http://localhost/d/e'],\n            ['http://localhost/a/b/c/', '../../d/e/',\n             'http://localhost/a/d/e/'],\n            ['http://localhost/a/./c', '../d/e', 'http://localhost/d/e'],\n            ['http://localhost/a/./c/', '../d/e', 'http://localhost/a/d/e'],\n            ['http://localhost/a/b/c/d', './e/../f/../g',\n             'http://localhost/a/b/c/g'],\n            ['http://localhost/a/b/c', 'd//e', 'http://localhost/a/b/d//e'],\n        ]\n        for start, click, expected in tests:\n            actual = URL.from_text(start).click(click).to_text()\n            self.assertEqual(\n                actual,\n                expected,\n                \"{start}.click({click}) => {actual} not {expected}\".format(\n                    start=start,\n                    click=repr(click),\n                    actual=actual,\n                    expected=expected,\n                )\n            )\n\n    def test_queryAdd(self):\n        \"\"\"\n        L{URL.add} adds query parameters.\n        \"\"\"\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/path/?foo=bar\",\n            URL.from_text(\"http://www.foo.com/a/nice/path/\")\n            .add(u\"foo\", u\"bar\").to_text())\n        self.assertEqual(\n            \"http://www.foo.com/?foo=bar\",\n            URL(host=u\"www.foo.com\").add(u\"foo\", u\"bar\")\n            .to_text())\n        urlpath = URL.from_text(BASIC_URL)\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/path/?zot=23&zut&burp\",\n            urlpath.add(u\"burp\").to_text())\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/path/?zot=23&zut&burp=xxx\",\n            urlpath.add(u\"burp\", u\"xxx\").to_text())\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/path/?zot=23&zut&burp=xxx&zing\",\n            urlpath.add(u\"burp\", u\"xxx\").add(u\"zing\").to_text())\n        # Note the inversion!\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/path/?zot=23&zut&zing&burp=xxx\",\n            urlpath.add(u\"zing\").add(u\"burp\", u\"xxx\").to_text())\n        # Note the two values for the same name.\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/path/?zot=23&zut&burp=xxx&zot=32\",\n            urlpath.add(u\"burp\", u\"xxx\").add(u\"zot\", '32')\n            .to_text())\n\n    def test_querySet(self):\n        \"\"\"\n        L{URL.set} replaces query parameters by name.\n        \"\"\"\n        urlpath = URL.from_text(BASIC_URL)\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/path/?zot=32&zut\",\n            urlpath.set(u\"zot\", '32').to_text())\n        # Replace name without value with name/value and vice-versa.\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/path/?zot&zut=itworked\",\n            urlpath.set(u\"zot\").set(u\"zut\", u\"itworked\").to_text()\n        )\n        # Q: what happens when the query has two values and we replace?\n        # A: we replace both values with a single one\n        self.assertEqual(\n            \"http://www.foo.com/a/nice/path/?zot=32&zut\",\n            urlpath.add(u\"zot\", u\"xxx\").set(u\"zot\", '32').to_text()\n        )\n\n    def test_queryRemove(self):\n        \"\"\"\n        L{URL.remove} removes instances of a query parameter.\n        \"\"\"\n        url = URL.from_text(u\"https://example.com/a/b/?foo=1&bar=2&foo=3\")\n        self.assertEqual(\n            url.remove(u\"foo\"),\n            URL.from_text(u\"https://example.com/a/b/?bar=2\")\n        )\n\n        self.assertEqual(\n            url.remove(name=u\"foo\", value=u\"1\"),\n            URL.from_text(u\"https://example.com/a/b/?bar=2&foo=3\")\n        )\n\n        self.assertEqual(\n            url.remove(name=u\"foo\", limit=1),\n            URL.from_text(u\"https://example.com/a/b/?bar=2&foo=3\")\n        )\n\n        self.assertEqual(\n            url.remove(name=u\"foo\", value=u\"1\", limit=0),\n            URL.from_text(u\"https://example.com/a/b/?foo=1&bar=2&foo=3\")\n        )\n\n    def test_parseEqualSignInParamValue(self):\n        \"\"\"\n        Every C{=}-sign after the first in a query parameter is simply included\n        in the value of the parameter.\n        \"\"\"\n        u = URL.from_text('http://localhost/?=x=x=x')\n        self.assertEqual(u.get(''), ['x=x=x'])\n        self.assertEqual(u.to_text(), 'http://localhost/?=x=x=x')\n        u = URL.from_text('http://localhost/?foo=x=x=x&bar=y')\n        self.assertEqual(u.query, (('foo', 'x=x=x'), ('bar', 'y')))\n        self.assertEqual(u.to_text(), 'http://localhost/?foo=x=x=x&bar=y')\n\n        u = URL.from_text('https://example.com/?argument=3&argument=4&operator=%3D')\n        iri = u.to_iri()\n        self.assertEqual(iri.get('operator'), ['='])\n        # assert that the equals is not unnecessarily escaped\n        self.assertEqual(iri.to_uri().get('operator'), ['='])\n\n    def test_empty(self):\n        \"\"\"\n        An empty L{URL} should serialize as the empty string.\n        \"\"\"\n        self.assertEqual(URL().to_text(), '')\n\n    def test_justQueryText(self):\n        \"\"\"\n        An L{URL} with query text should serialize as just query text.\n        \"\"\"\n        u = URL(query=[(u\"hello\", u\"world\")])\n        self.assertEqual(u.to_text(), '?hello=world')\n\n    def test_identicalEqual(self):\n        \"\"\"\n        L{URL} compares equal to itself.\n        \"\"\"\n        u = URL.from_text('http://localhost/')\n        self.assertEqual(u, u)\n\n    def test_similarEqual(self):\n        \"\"\"\n        URLs with equivalent components should compare equal.\n        \"\"\"\n        u1 = URL.from_text('http://u@localhost:8080/p/a/t/h?q=p#f')\n        u2 = URL.from_text('http://u@localhost:8080/p/a/t/h?q=p#f')\n        self.assertEqual(u1, u2)\n\n    def test_differentNotEqual(self):\n        \"\"\"\n        L{URL}s that refer to different resources are both unequal (C{!=}) and\n        also not equal (not C{==}).\n        \"\"\"\n        u1 = URL.from_text('http://localhost/a')\n        u2 = URL.from_text('http://localhost/b')\n        self.assertFalse(u1 == u2, \"%r != %r\" % (u1, u2))\n        self.assertNotEqual(u1, u2)\n\n    def test_otherTypesNotEqual(self):\n        \"\"\"\n        L{URL} is not equal (C{==}) to other types.\n        \"\"\"\n        u = URL.from_text('http://localhost/')\n        self.assertFalse(u == 42, \"URL must not equal a number.\")\n        self.assertFalse(u == object(), \"URL must not equal an object.\")\n        self.assertNotEqual(u, 42)\n        self.assertNotEqual(u, object())\n\n    def test_identicalNotUnequal(self):\n        \"\"\"\n        Identical L{URL}s are not unequal (C{!=}) to each other.\n        \"\"\"\n        u = URL.from_text('http://u@localhost:8080/p/a/t/h?q=p#f')\n        self.assertFalse(u != u, \"%r == itself\" % u)\n\n    def test_similarNotUnequal(self):\n        \"\"\"\n        Structurally similar L{URL}s are not unequal (C{!=}) to each other.\n        \"\"\"\n        u1 = URL.from_text('http://u@localhost:8080/p/a/t/h?q=p#f')\n        u2 = URL.from_text('http://u@localhost:8080/p/a/t/h?q=p#f')\n        self.assertFalse(u1 != u2, \"%r == %r\" % (u1, u2))\n\n    def test_differentUnequal(self):\n        \"\"\"\n        Structurally different L{URL}s are unequal (C{!=}) to each other.\n        \"\"\"\n        u1 = URL.from_text('http://localhost/a')\n        u2 = URL.from_text('http://localhost/b')\n        self.assertTrue(u1 != u2, \"%r == %r\" % (u1, u2))\n\n    def test_otherTypesUnequal(self):\n        \"\"\"\n        L{URL} is unequal (C{!=}) to other types.\n        \"\"\"\n        u = URL.from_text('http://localhost/')\n        self.assertTrue(u != 42, \"URL must differ from a number.\")\n        self.assertTrue(u != object(), \"URL must be differ from an object.\")\n\n    def test_asURI(self):\n        \"\"\"\n        L{URL.asURI} produces an URI which converts any URI unicode encoding\n        into pure US-ASCII and returns a new L{URL}.\n        \"\"\"\n        unicodey = ('http://\\N{LATIN SMALL LETTER E WITH ACUTE}.com/'\n                    '\\N{LATIN SMALL LETTER E}\\N{COMBINING ACUTE ACCENT}'\n                    '?\\N{LATIN SMALL LETTER A}\\N{COMBINING ACUTE ACCENT}='\n                    '\\N{LATIN SMALL LETTER I}\\N{COMBINING ACUTE ACCENT}'\n                    '#\\N{LATIN SMALL LETTER U}\\N{COMBINING ACUTE ACCENT}')\n        iri = URL.from_text(unicodey)\n        uri = iri.asURI()\n        self.assertEqual(iri.host, '\\N{LATIN SMALL LETTER E WITH ACUTE}.com')\n        self.assertEqual(iri.path[0],\n                         '\\N{LATIN SMALL LETTER E}\\N{COMBINING ACUTE ACCENT}')\n        self.assertEqual(iri.to_text(), unicodey)\n        expectedURI = 'http://xn--9ca.com/%C3%A9?%C3%A1=%C3%AD#%C3%BA'\n        actualURI = uri.to_text()\n        self.assertEqual(actualURI, expectedURI,\n                         '%r != %r' % (actualURI, expectedURI))\n\n    def test_asIRI(self):\n        \"\"\"\n        L{URL.asIRI} decodes any percent-encoded text in the URI, making it\n        more suitable for reading by humans, and returns a new L{URL}.\n        \"\"\"\n        asciiish = 'http://xn--9ca.com/%C3%A9?%C3%A1=%C3%AD#%C3%BA'\n        uri = URL.from_text(asciiish)\n        iri = uri.asIRI()\n        self.assertEqual(uri.host, 'xn--9ca.com')\n        self.assertEqual(uri.path[0], '%C3%A9')\n        self.assertEqual(uri.to_text(), asciiish)\n        expectedIRI = ('http://\\N{LATIN SMALL LETTER E WITH ACUTE}.com/'\n                       '\\N{LATIN SMALL LETTER E WITH ACUTE}'\n                       '?\\N{LATIN SMALL LETTER A WITH ACUTE}='\n                       '\\N{LATIN SMALL LETTER I WITH ACUTE}'\n                       '#\\N{LATIN SMALL LETTER U WITH ACUTE}')\n        actualIRI = iri.to_text()\n        self.assertEqual(actualIRI, expectedIRI,\n                         '%r != %r' % (actualIRI, expectedIRI))\n\n    def test_badUTF8AsIRI(self):\n        \"\"\"\n        Bad UTF-8 in a path segment, query parameter, or fragment results in\n        that portion of the URI remaining percent-encoded in the IRI.\n        \"\"\"\n        urlWithBinary = 'http://xn--9ca.com/%00%FF/%C3%A9'\n        uri = URL.from_text(urlWithBinary)\n        iri = uri.asIRI()\n        expectedIRI = ('http://\\N{LATIN SMALL LETTER E WITH ACUTE}.com/'\n                       '%00%FF/'\n                       '\\N{LATIN SMALL LETTER E WITH ACUTE}')\n        actualIRI = iri.to_text()\n        self.assertEqual(actualIRI, expectedIRI,\n                         '%r != %r' % (actualIRI, expectedIRI))\n\n    def test_alreadyIRIAsIRI(self):\n        \"\"\"\n        A L{URL} composed of non-ASCII text will result in non-ASCII text.\n        \"\"\"\n        unicodey = ('http://\\N{LATIN SMALL LETTER E WITH ACUTE}.com/'\n                    '\\N{LATIN SMALL LETTER E}\\N{COMBINING ACUTE ACCENT}'\n                    '?\\N{LATIN SMALL LETTER A}\\N{COMBINING ACUTE ACCENT}='\n                    '\\N{LATIN SMALL LETTER I}\\N{COMBINING ACUTE ACCENT}'\n                    '#\\N{LATIN SMALL LETTER U}\\N{COMBINING ACUTE ACCENT}')\n        iri = URL.from_text(unicodey)\n        alsoIRI = iri.asIRI()\n        self.assertEqual(alsoIRI.to_text(), unicodey)\n\n    def test_alreadyURIAsURI(self):\n        \"\"\"\n        A L{URL} composed of encoded text will remain encoded.\n        \"\"\"\n        expectedURI = 'http://xn--9ca.com/%C3%A9?%C3%A1=%C3%AD#%C3%BA'\n        uri = URL.from_text(expectedURI)\n        actualURI = uri.asURI().to_text()\n        self.assertEqual(actualURI, expectedURI)\n\n    def test_userinfo(self):\n        \"\"\"\n        L{URL.from_text} will parse the C{userinfo} portion of the URI\n        separately from the host and port.\n        \"\"\"\n        url = URL.from_text(\n            'http://someuser:somepassword@example.com/some-segment@ignore'\n        )\n        self.assertEqual(url.authority(True),\n                         'someuser:somepassword@example.com')\n        self.assertEqual(url.authority(False), 'someuser:@example.com')\n        self.assertEqual(url.userinfo, 'someuser:somepassword')\n        self.assertEqual(url.user, 'someuser')\n        self.assertEqual(url.to_text(),\n                         'http://someuser:@example.com/some-segment@ignore')\n        self.assertEqual(\n            url.replace(userinfo=u\"someuser\").to_text(),\n            'http://someuser@example.com/some-segment@ignore'\n        )\n\n    def test_portText(self):\n        \"\"\"\n        L{URL.from_text} parses custom port numbers as integers.\n        \"\"\"\n        portURL = URL.from_text(u\"http://www.example.com:8080/\")\n        self.assertEqual(portURL.port, 8080)\n        self.assertEqual(portURL.to_text(), u\"http://www.example.com:8080/\")\n\n    def test_mailto(self):\n        \"\"\"\n        Although L{URL} instances are mainly for dealing with HTTP, other\n        schemes (such as C{mailto:}) should work as well.  For example,\n        L{URL.from_text}/L{URL.to_text} round-trips cleanly for a C{mailto:} URL\n        representing an email address.\n        \"\"\"\n        self.assertEqual(URL.from_text(u\"mailto:user@example.com\").to_text(),\n                         u\"mailto:user@example.com\")\n\n    def test_queryIterable(self):\n        \"\"\"\n        When a L{URL} is created with a C{query} argument, the C{query}\n        argument is converted into an N-tuple of 2-tuples, sensibly\n        handling dictionaries.\n        \"\"\"\n        expected = (('alpha', 'beta'),)\n        url = URL(query=[['alpha', 'beta']])\n        self.assertEqual(url.query, expected)\n        url = URL(query={'alpha': 'beta'})\n        self.assertEqual(url.query, expected)\n\n    def test_pathIterable(self):\n        \"\"\"\n        When a L{URL} is created with a C{path} argument, the C{path} is\n        converted into a tuple.\n        \"\"\"\n        url = URL(path=['hello', 'world'])\n        self.assertEqual(url.path, ('hello', 'world'))\n\n    def test_invalidArguments(self):\n        \"\"\"\n        Passing an argument of the wrong type to any of the constructor\n        arguments of L{URL} will raise a descriptive L{TypeError}.\n\n        L{URL} typechecks very aggressively to ensure that its constitutent\n        parts are all properly immutable and to prevent confusing errors when\n        bad data crops up in a method call long after the code that called the\n        constructor is off the stack.\n        \"\"\"\n        class Unexpected(object):\n            def __str__(self):\n                return \"wrong\"\n\n            def __repr__(self):\n                return \"<unexpected>\"\n\n        defaultExpectation = \"unicode\" if bytes is str else \"str\"\n\n        def assertRaised(raised, expectation, name):\n            self.assertEqual(str(raised.exception),\n                             \"expected {0} for {1}, got {2}\".format(\n                                 expectation,\n                                 name, \"<unexpected>\"))\n\n        def check(param, expectation=defaultExpectation):\n            with self.assertRaises(TypeError) as raised:\n                URL(**{param: Unexpected()})\n\n            assertRaised(raised, expectation, param)\n\n        check(\"scheme\")\n        check(\"host\")\n        check(\"fragment\")\n        check(\"rooted\", \"bool\")\n        check(\"userinfo\")\n        check(\"port\", \"int or NoneType\")\n\n        with self.assertRaises(TypeError) as raised:\n            URL(path=[Unexpected()])\n\n        assertRaised(raised, defaultExpectation, \"path segment\")\n\n        with self.assertRaises(TypeError) as raised:\n            URL(query=[(u\"name\", Unexpected())])\n\n        assertRaised(raised, defaultExpectation + \" or NoneType\",\n                     \"query parameter value\")\n\n        with self.assertRaises(TypeError) as raised:\n            URL(query=[(Unexpected(), u\"value\")])\n\n        assertRaised(raised, defaultExpectation, \"query parameter name\")\n        # No custom error message for this one, just want to make sure\n        # non-2-tuples don't get through.\n\n        with self.assertRaises(TypeError):\n            URL(query=[Unexpected()])\n\n        with self.assertRaises(ValueError):\n            URL(query=[('k', 'v', 'vv')])\n\n        with self.assertRaises(ValueError):\n            URL(query=[('k',)])\n\n        url = URL.from_text(\"https://valid.example.com/\")\n        with self.assertRaises(TypeError) as raised:\n            url.child(Unexpected())\n        assertRaised(raised, defaultExpectation, \"path segment\")\n        with self.assertRaises(TypeError) as raised:\n            url.sibling(Unexpected())\n        assertRaised(raised, defaultExpectation, \"path segment\")\n        with self.assertRaises(TypeError) as raised:\n            url.click(Unexpected())\n        assertRaised(raised, defaultExpectation, \"relative URL\")\n\n    def test_technicallyTextIsIterableBut(self):\n        \"\"\"\n        Technically, L{str} (or L{unicode}, as appropriate) is iterable, but\n        C{URL(path=\"foo\")} resulting in C{URL.from_text(\"f/o/o\")} is never what\n        you want.\n        \"\"\"\n        with self.assertRaises(TypeError) as raised:\n            URL(path='foo')\n        self.assertEqual(\n            str(raised.exception),\n            \"expected iterable of text for path, not: {0}\"\n            .format(repr('foo'))\n        )\n\n    def test_netloc(self):\n        url = URL(scheme='https')\n        self.assertEqual(url.uses_netloc, True)\n\n        url = URL(scheme='git+https')\n        self.assertEqual(url.uses_netloc, True)\n\n        url = URL(scheme='mailto')\n        self.assertEqual(url.uses_netloc, False)\n\n        url = URL(scheme='ztp')\n        self.assertEqual(url.uses_netloc, None)\n\n        url = URL.from_text('ztp://test.com')\n        self.assertEqual(url.uses_netloc, True)\n\n        url = URL.from_text('ztp:test:com')\n        self.assertEqual(url.uses_netloc, False)\n\n    def test_ipv6_with_port(self):\n        t = 'https://[2001:0db8:85a3:0000:0000:8a2e:0370:7334]:80/'\n        url = URL.from_text(t)\n        assert url.host == '2001:0db8:85a3:0000:0000:8a2e:0370:7334'\n        assert url.port == 80\n        assert SCHEME_PORT_MAP[url.scheme] != url.port\n\n    def test_basic(self):\n        text = 'https://user:pass@example.com/path/to/here?k=v#nice'\n        url = URL.from_text(text)\n        assert url.scheme == 'https'\n        assert url.userinfo == 'user:pass'\n        assert url.host == 'example.com'\n        assert url.path == ('path', 'to', 'here')\n        assert url.fragment == 'nice'\n\n        text = 'https://user:pass@127.0.0.1/path/to/here?k=v#nice'\n        url = URL.from_text(text)\n        assert url.scheme == 'https'\n        assert url.userinfo == 'user:pass'\n        assert url.host == '127.0.0.1'\n        assert url.path == ('path', 'to', 'here')\n\n        text = 'https://user:pass@[::1]/path/to/here?k=v#nice'\n        url = URL.from_text(text)\n        assert url.scheme == 'https'\n        assert url.userinfo == 'user:pass'\n        assert url.host == '::1'\n        assert url.path == ('path', 'to', 'here')\n\n    def test_invalid_url(self):\n        self.assertRaises(URLParseError, URL.from_text, '#\\n\\n')\n\n    def test_invalid_authority_url(self):\n        self.assertRaises(URLParseError, URL.from_text, 'http://abc:\\n\\n/#')\n\n    def test_invalid_ipv6(self):\n        invalid_ipv6_ips = ['2001::0234:C1ab::A0:aabc:003F',\n                            '2001::1::3F',\n                            ':',\n                            '::::',\n                            '::256.0.0.1']\n        for ip in invalid_ipv6_ips:\n            url_text = 'http://[' + ip + ']'\n            self.assertRaises(socket.error, inet_pton,\n                              socket.AF_INET6, ip)\n            self.assertRaises(URLParseError, URL.from_text, url_text)\n\n    def test_invalid_port(self):\n        self.assertRaises(URLParseError, URL.from_text, 'ftp://portmouth:smash')\n        self.assertRaises(ValueError, URL.from_text,\n                          'http://reader.googlewebsite.com:neverforget')\n\n    def test_idna(self):\n        u1 = URL.from_text('http://bücher.ch')\n        self.assertEquals(u1.host, 'bücher.ch')\n        self.assertEquals(u1.to_text(), 'http://bücher.ch')\n        self.assertEquals(u1.to_uri().to_text(), 'http://xn--bcher-kva.ch')\n\n        u2 = URL.from_text('https://xn--bcher-kva.ch')\n        self.assertEquals(u2.host, 'xn--bcher-kva.ch')\n        self.assertEquals(u2.to_text(), 'https://xn--bcher-kva.ch')\n        self.assertEquals(u2.to_iri().to_text(), u'https://bücher.ch')\n\n    def test_netloc_slashes(self):\n        # basic sanity checks\n        url = URL.from_text('mailto:mahmoud@hatnote.com')\n        self.assertEquals(url.scheme, 'mailto')\n        self.assertEquals(url.to_text(), 'mailto:mahmoud@hatnote.com')\n\n        url = URL.from_text('http://hatnote.com')\n        self.assertEquals(url.scheme, 'http')\n        self.assertEquals(url.to_text(), 'http://hatnote.com')\n\n        # test that unrecognized schemes stay consistent with '//'\n        url = URL.from_text('newscheme:a:b:c')\n        self.assertEquals(url.scheme, 'newscheme')\n        self.assertEquals(url.to_text(), 'newscheme:a:b:c')\n\n        url = URL.from_text('newerscheme://a/b/c')\n        self.assertEquals(url.scheme, 'newerscheme')\n        self.assertEquals(url.to_text(), 'newerscheme://a/b/c')\n\n        # test that reasonable guesses are made\n        url = URL.from_text('git+ftp://gitstub.biz/glyph/lefkowitz')\n        self.assertEquals(url.scheme, 'git+ftp')\n        self.assertEquals(url.to_text(),\n                          'git+ftp://gitstub.biz/glyph/lefkowitz')\n\n        url = URL.from_text('what+mailto:freerealestate@enotuniq.org')\n        self.assertEquals(url.scheme, 'what+mailto')\n        self.assertEquals(url.to_text(),\n                          'what+mailto:freerealestate@enotuniq.org')\n\n        url = URL(scheme='ztp', path=('x', 'y', 'z'), rooted=True)\n        self.assertEquals(url.to_text(), 'ztp:/x/y/z')\n\n        # also works when the input doesn't include '//'\n        url = URL(scheme='git+ftp', path=('x', 'y', 'z' ,''),\n                  rooted=True, uses_netloc=True)\n        # broken bc urlunsplit\n        self.assertEquals(url.to_text(), 'git+ftp:///x/y/z/')\n\n        # really why would this ever come up but ok\n        url = URL.from_text('file:///path/to/heck')\n        url2 = url.replace(scheme='mailto')\n        self.assertEquals(url2.to_text(), 'mailto:/path/to/heck')\n\n        url_text = 'unregisteredscheme:///a/b/c'\n        url = URL.from_text(url_text)\n        no_netloc_url = url.replace(uses_netloc=False)\n        self.assertEquals(no_netloc_url.to_text(), 'unregisteredscheme:/a/b/c')\n        netloc_url = url.replace(uses_netloc=True)\n        self.assertEquals(netloc_url.to_text(), url_text)\n\n        return\n\n    def test_wrong_constructor(self):\n        with self.assertRaises(ValueError):\n            # whole URL not allowed\n            URL(BASIC_URL)\n        with self.assertRaises(ValueError):\n            # explicitly bad scheme not allowed\n            URL('HTTP_____more_like_imHoTTeP')\n\n    def test_encoded_userinfo(self):\n        url = URL.from_text('http://user:pass@example.com')\n        assert url.userinfo == 'user:pass'\n        url = url.replace(userinfo='us%20her:pass')\n        iri = url.to_iri()\n        assert iri.to_text(with_password=True) == 'http://us her:pass@example.com'\n        assert iri.to_text(with_password=False) == 'http://us her:@example.com'\n        assert iri.to_uri().to_text(with_password=True) == 'http://us%20her:pass@example.com'\n\n    def test_hash(self):\n        url_map = {}\n        url1 = URL.from_text('http://blog.hatnote.com/ask?utm_source=geocity')\n        assert hash(url1) == hash(url1)  # sanity\n\n        url_map[url1] = 1\n\n        url2 = URL.from_text('http://blog.hatnote.com/ask')\n        url2 = url2.set('utm_source', 'geocity')\n\n        url_map[url2] = 2\n\n        assert len(url_map) == 1\n        assert list(url_map.values()) == [2]\n\n        assert hash(URL()) == hash(URL())  # slightly more sanity\n\n    def test_dir(self):\n        url = URL()\n        res = dir(url)\n\n        assert len(res) > 15\n        # twisted compat\n        assert 'fromText' not in res\n        assert 'asText' not in res\n        assert 'asURI' not in res\n        assert 'asIRI' not in res\n\n    def test_twisted_compat(self):\n        url = URL.fromText(u'http://example.com/a%20té%C3%A9st')\n        assert url.asText() == 'http://example.com/a%20té%C3%A9st'\n        assert url.asURI().asText() == 'http://example.com/a%20t%C3%A9%C3%A9st'\n        # TODO: assert url.asIRI().asText() == u'http://example.com/a%20téést'\n\n    def test_set_ordering(self):\n        # TODO\n        url = URL.from_text('http://example.com/?a=b&c')\n        url = url.set(u'x', u'x')\n        url = url.add(u'x', u'y')\n        assert url.to_text() == u'http://example.com/?a=b&x=x&c&x=y'\n        # Would expect:\n        # assert url.to_text() == u'http://example.com/?a=b&c&x=x&x=y'\n\n    def test_schemeless_path(self):\n        \"See issue #4\"\n        u1 = URL.from_text(\"urn%3Aietf%3Awg%3Aoauth%3A2.0%3Aoob\")\n        u2 = URL.from_text(u1.to_text())\n        assert u1 == u2  # sanity testing roundtripping\n\n        u3 = URL.from_text(u1.to_iri().to_text())\n        assert u1 == u3\n        assert u2 == u3\n\n        # test that colons are ok past the first segment\n        u4 = URL.from_text(\"first-segment/urn%3Aietf%3Awg%3Aoauth%3A2.0%3Aoob\")\n        u5 = u4.to_iri()\n        assert u5.to_text() == u'first-segment/urn:ietf:wg:oauth:2.0:oob'\n\n        u6 = URL.from_text(u5.to_text()).to_uri()\n        assert u5 == u6  # colons stay decoded bc they're not in the first seg\n\n    def test_emoji_domain(self):\n        \"See issue #7, affecting only narrow builds (2.6-3.3)\"\n        url = URL.from_text('https://xn--vi8hiv.ws')\n        iri = url.to_iri()\n        iri.to_text()\n        # as long as we don't get ValueErrors, we're good\n\n    def test_delim_in_param(self):\n        \"Per issue #6 and #8\"\n        self.assertRaises(ValueError, URL, scheme=u'http', host=u'a/c')\n        self.assertRaises(ValueError, URL, path=(u\"?\",))\n        self.assertRaises(ValueError, URL, path=(u\"#\",))\n        self.assertRaises(ValueError, URL, query=((u\"&\", \"test\")))\n\n    def test_empty_paths_eq(self):\n        u1 = URL.from_text('http://example.com/')\n        u2 = URL.from_text('http://example.com')\n\n        assert u1 == u2\n\n        u1 = URL.from_text('http://example.com')\n        u2 = URL.from_text('http://example.com')\n\n        assert u1 == u2\n\n        u1 = URL.from_text('http://example.com')\n        u2 = URL.from_text('http://example.com/')\n\n        assert u1 == u2\n\n        u1 = URL.from_text('http://example.com/')\n        u2 = URL.from_text('http://example.com/')\n\n        assert u1 == u2\n\n    def test_from_text_type(self):\n        assert URL.from_text(u'#ok').fragment == u'ok'  # sanity\n        self.assertRaises(TypeError, URL.from_text, b'bytes://x.y.z')\n        self.assertRaises(TypeError, URL.from_text, object())\n\n    def test_from_text_bad_authority(self):\n        # bad ipv6 brackets\n        self.assertRaises(URLParseError, URL.from_text, 'http://[::1/')\n        self.assertRaises(URLParseError, URL.from_text, 'http://::1]/')\n        self.assertRaises(URLParseError, URL.from_text, 'http://[[::1]/')\n        self.assertRaises(URLParseError, URL.from_text, 'http://[::1]]/')\n\n        # empty port\n        self.assertRaises(URLParseError, URL.from_text, 'http://127.0.0.1:')\n        # non-integer port\n        self.assertRaises(URLParseError, URL.from_text, 'http://127.0.0.1:hi')\n        # extra port colon (makes for an invalid host)\n        self.assertRaises(URLParseError, URL.from_text, 'http://127.0.0.1::80')\n\n    def test_normalize(self):\n        url = URL.from_text('HTTP://Example.com/A%61/./../A%61?B%62=C%63#D%64')\n        assert url.get('Bb') == []\n        assert url.get('B%62') == ['C%63']\n        assert len(url.path) == 4\n\n        # test that most expected normalizations happen\n        norm_url = url.normalize()\n\n        assert norm_url.scheme == 'http'\n        assert norm_url.host == 'example.com'\n        assert norm_url.path == ('Aa',)\n        assert norm_url.get('Bb') == ['Cc']\n        assert norm_url.fragment == 'Dd'\n        assert norm_url.to_text() == 'http://example.com/Aa?Bb=Cc#Dd'\n\n        # test that flags work\n        noop_norm_url = url.normalize(scheme=False, host=False,\n                                      path=False, query=False, fragment=False)\n        assert noop_norm_url == url\n\n        # test that empty paths get at least one slash\n        slashless_url = URL.from_text('http://example.io')\n        slashful_url = slashless_url.normalize()\n        assert slashful_url.to_text() == 'http://example.io/'\n\n        # test case normalization for percent encoding\n        delimited_url = URL.from_text('/a%2fb/cd%3f?k%3d=v%23#test')\n        norm_delimited_url = delimited_url.normalize()\n        assert norm_delimited_url.to_text() == '/a%2Fb/cd%3F?k%3D=v%23#test'\n\n        # test invalid percent encoding during normalize\n        assert URL(path=('', '%te%sts')).normalize(percents=False).to_text() == '/%te%sts'\n        assert URL(path=('', '%te%sts')).normalize().to_text() == '/%25te%25sts'\n\n        percenty_url = URL(scheme='ftp', path=['%%%', '%a%b'], query=[('%', '%%')], fragment='%', userinfo='%:%')\n\n        assert percenty_url.to_text(with_password=True) == 'ftp://%:%@/%%%/%a%b?%=%%#%'\n        assert percenty_url.normalize().to_text(with_password=True) == 'ftp://%25:%25@/%25%25%25/%25a%25b?%25=%25%25#%25'\n\n    def test_str(self):\n        # see also issue #49\n        text = u'http://example.com/á/y%20a%20y/?b=%25'\n        url = URL.from_text(text)\n        assert unicode(url) == text\n        assert bytes(url) == b'http://example.com/%C3%A1/y%20a%20y/?b=%25'\n\n        if PY2:\n            assert isinstance(str(url), bytes)\n            assert isinstance(unicode(url), unicode)\n        else:\n            assert isinstance(str(url), unicode)\n            assert isinstance(bytes(url), bytes)\n\n    def test_idna_corners(self):\n        text = u'http://abé.com/'\n        url = URL.from_text(text)\n        assert url.to_iri().host == u'abé.com'\n        assert url.to_uri().host == u'xn--ab-cja.com'\n\n        url = URL.from_text(\"http://ドメイン.テスト.co.jp#test\")\n        assert url.to_iri().host == u'ドメイン.テスト.co.jp'\n        assert url.to_uri().host == u'xn--eckwd4c7c.xn--zckzah.co.jp'\n\n        assert url.to_uri().get_decoded_url().host == u'ドメイン.テスト.co.jp'\n\n        assert URL.from_text('http://Example.com').to_uri().get_decoded_url().host == 'example.com'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink-19.0.0.dist-info/DESCRIPTION.rst",
    "content": "The humble, but powerful, URL runs everything around us. Chances\nare you've used several just to read this text.\n\nHyperlink is a featureful, pure-Python implementation of the URL, with\nan emphasis on correctness. BSD licensed.\n\nSee the docs at http://hyperlink.readthedocs.io.\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink-19.0.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink-19.0.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.0\nName: hyperlink\nVersion: 19.0.0\nSummary: A featureful, immutable, and correct URL for Python.\nHome-page: https://github.com/python-hyper/hyperlink\nAuthor: Mahmoud Hashemi and Glyph Lefkowitz\nAuthor-email: mahmoud@hatnote.com\nLicense: MIT\nPlatform: any\nClassifier: Topic :: Utilities\nClassifier: Intended Audience :: Developers\nClassifier: Topic :: Software Development :: Libraries\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Programming Language :: Python :: 2.6\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: Implementation :: PyPy\nRequires-Dist: idna (>=2.5)\n\nThe humble, but powerful, URL runs everything around us. Chances\nare you've used several just to read this text.\n\nHyperlink is a featureful, pure-Python implementation of the URL, with\nan emphasis on correctness. BSD licensed.\n\nSee the docs at http://hyperlink.readthedocs.io.\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink-19.0.0.dist-info/RECORD",
    "content": "hyperlink-19.0.0.dist-info/DESCRIPTION.rst,sha256=a-0GCP8glYZ0Ysq4Y0mPEe6VJHqJNsGdheikkI7rwCo,279\r\nhyperlink-19.0.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nhyperlink-19.0.0.dist-info/METADATA,sha256=y172hVTAqkayU3cFJRIJNy5At7oX9iecXN70uD1tY68,1087\r\nhyperlink-19.0.0.dist-info/RECORD,,\r\nhyperlink-19.0.0.dist-info/WHEEL,sha256=5wvfB7GvgZAbKBSE9uX9Zbi6LCL-_KgezgHblXhCRnM,113\r\nhyperlink-19.0.0.dist-info/metadata.json,sha256=JAh7SySskyDcNAPuBXetb6bTuS_-euZRkk75-LVtNBI,983\r\nhyperlink-19.0.0.dist-info/top_level.txt,sha256=qKx9FGU_zxD9mGqiFgleNejfO4AwPY7duhQPaZ30U_M,10\r\nhyperlink/__init__.py,sha256=OFqG_8hDTyyc8MmhVR-LyXL-aShz_Y9Qg98__-vcfTE,302\r\nhyperlink/__pycache__/__init__.cpython-36.pyc,,\r\nhyperlink/__pycache__/_url.cpython-36.pyc,,\r\nhyperlink/_url.py,sha256=JW1raJr9hSmMyqDi_1GTgo0oes2RGL_zsEXhkaQLHKE,72479\r\nhyperlink/test/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0\r\nhyperlink/test/__pycache__/__init__.cpython-36.pyc,,\r\nhyperlink/test/__pycache__/common.cpython-36.pyc,,\r\nhyperlink/test/__pycache__/test_common.cpython-36.pyc,,\r\nhyperlink/test/__pycache__/test_decoded_url.cpython-36.pyc,,\r\nhyperlink/test/__pycache__/test_parse.cpython-36.pyc,,\r\nhyperlink/test/__pycache__/test_scheme_registration.cpython-36.pyc,,\r\nhyperlink/test/__pycache__/test_url.cpython-36.pyc,,\r\nhyperlink/test/common.py,sha256=fZ0gLTlEC1YFnlyn8Hc7_aJJCEGadL1Glw3BVtIvOkQ,2108\r\nhyperlink/test/test_common.py,sha256=6wiI5TjCYO0cyJwPXSL3TFTlkaSyGYGem5_uGIN-6p8,3399\r\nhyperlink/test/test_decoded_url.py,sha256=2aF0fxCJXVjSdownHyD7y-HMnlsnRnsHl4RPOPdKYpM,6259\r\nhyperlink/test/test_parse.py,sha256=HOF7Ns2tGnXUDrX5i8apyVEfnqsiuCtHu2_9uueY5xg,1081\r\nhyperlink/test/test_scheme_registration.py,sha256=cRlrJVt3aFCAYOpz6rqSf9YHFBgjsimbfNdW8PYqbfM,2328\r\nhyperlink/test/test_url.py,sha256=a8mHV7_VfsW4_Uim13q3PSvmBCMLHut_lu9b4zFv8W4,47162\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink-19.0.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.30.0.a0)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink-19.0.0.dist-info/metadata.json",
    "content": "{\"classifiers\": [\"Topic :: Utilities\", \"Intended Audience :: Developers\", \"Topic :: Software Development :: Libraries\", \"Development Status :: 5 - Production/Stable\", \"Programming Language :: Python :: 2.6\", \"Programming Language :: Python :: 2.7\", \"Programming Language :: Python :: 3.4\", \"Programming Language :: Python :: 3.5\", \"Programming Language :: Python :: 3.6\", \"Programming Language :: Python :: Implementation :: PyPy\"], \"extensions\": {\"python.details\": {\"contacts\": [{\"email\": \"mahmoud@hatnote.com\", \"name\": \"Mahmoud Hashemi and Glyph Lefkowitz\", \"role\": \"author\"}], \"document_names\": {\"description\": \"DESCRIPTION.rst\"}, \"project_urls\": {\"Home\": \"https://github.com/python-hyper/hyperlink\"}}}, \"extras\": [], \"generator\": \"bdist_wheel (0.30.0.a0)\", \"license\": \"MIT\", \"metadata_version\": \"2.0\", \"name\": \"hyperlink\", \"platform\": \"any\", \"run_requires\": [{\"requires\": [\"idna (>=2.5)\"]}], \"summary\": \"A featureful, immutable, and correct URL for Python.\", \"version\": \"19.0.0\"}"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/hyperlink-19.0.0.dist-info/top_level.txt",
    "content": "hyperlink\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna/__init__.py",
    "content": "from .package_data import __version__\nfrom .core import *\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna/codec.py",
    "content": "from .core import encode, decode, alabel, ulabel, IDNAError\nimport codecs\nimport re\n\n_unicode_dots_re = re.compile(u'[\\u002e\\u3002\\uff0e\\uff61]')\n\nclass Codec(codecs.Codec):\n\n    def encode(self, data, errors='strict'):\n\n        if errors != 'strict':\n            raise IDNAError(\"Unsupported error handling \\\"{0}\\\"\".format(errors))\n\n        if not data:\n            return \"\", 0\n\n        return encode(data), len(data)\n\n    def decode(self, data, errors='strict'):\n\n        if errors != 'strict':\n            raise IDNAError(\"Unsupported error handling \\\"{0}\\\"\".format(errors))\n\n        if not data:\n            return u\"\", 0\n\n        return decode(data), len(data)\n\nclass IncrementalEncoder(codecs.BufferedIncrementalEncoder):\n    def _buffer_encode(self, data, errors, final):\n        if errors != 'strict':\n            raise IDNAError(\"Unsupported error handling \\\"{0}\\\"\".format(errors))\n\n        if not data:\n            return (\"\", 0)\n\n        labels = _unicode_dots_re.split(data)\n        trailing_dot = u''\n        if labels:\n            if not labels[-1]:\n                trailing_dot = '.'\n                del labels[-1]\n            elif not final:\n                # Keep potentially unfinished label until the next call\n                del labels[-1]\n                if labels:\n                    trailing_dot = '.'\n\n        result = []\n        size = 0\n        for label in labels:\n            result.append(alabel(label))\n            if size:\n                size += 1\n            size += len(label)\n\n        # Join with U+002E\n        result = \".\".join(result) + trailing_dot\n        size += len(trailing_dot)\n        return (result, size)\n\nclass IncrementalDecoder(codecs.BufferedIncrementalDecoder):\n    def _buffer_decode(self, data, errors, final):\n        if errors != 'strict':\n            raise IDNAError(\"Unsupported error handling \\\"{0}\\\"\".format(errors))\n\n        if not data:\n            return (u\"\", 0)\n\n        # IDNA allows decoding to operate on Unicode strings, too.\n        if isinstance(data, unicode):\n            labels = _unicode_dots_re.split(data)\n        else:\n            # Must be ASCII string\n            data = str(data)\n            unicode(data, \"ascii\")\n            labels = data.split(\".\")\n\n        trailing_dot = u''\n        if labels:\n            if not labels[-1]:\n                trailing_dot = u'.'\n                del labels[-1]\n            elif not final:\n                # Keep potentially unfinished label until the next call\n                del labels[-1]\n                if labels:\n                    trailing_dot = u'.'\n\n        result = []\n        size = 0\n        for label in labels:\n            result.append(ulabel(label))\n            if size:\n                size += 1\n            size += len(label)\n\n        result = u\".\".join(result) + trailing_dot\n        size += len(trailing_dot)\n        return (result, size)\n\n\nclass StreamWriter(Codec, codecs.StreamWriter):\n    pass\n\nclass StreamReader(Codec, codecs.StreamReader):\n    pass\n\ndef getregentry():\n    return codecs.CodecInfo(\n        name='idna',\n        encode=Codec().encode,\n        decode=Codec().decode,\n        incrementalencoder=IncrementalEncoder,\n        incrementaldecoder=IncrementalDecoder,\n        streamwriter=StreamWriter,\n        streamreader=StreamReader,\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna/compat.py",
    "content": "from .core import *\nfrom .codec import *\n\ndef ToASCII(label):\n    return encode(label)\n\ndef ToUnicode(label):\n    return decode(label)\n\ndef nameprep(s):\n    raise NotImplementedError(\"IDNA 2008 does not utilise nameprep protocol\")\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna/core.py",
    "content": "from . import idnadata\nimport bisect\nimport unicodedata\nimport re\nimport sys\nfrom .intranges import intranges_contain\n\n_virama_combining_class = 9\n_alabel_prefix = b'xn--'\n_unicode_dots_re = re.compile(u'[\\u002e\\u3002\\uff0e\\uff61]')\n\nif sys.version_info[0] == 3:\n    unicode = str\n    unichr = chr\n\nclass IDNAError(UnicodeError):\n    \"\"\" Base exception for all IDNA-encoding related problems \"\"\"\n    pass\n\n\nclass IDNABidiError(IDNAError):\n    \"\"\" Exception when bidirectional requirements are not satisfied \"\"\"\n    pass\n\n\nclass InvalidCodepoint(IDNAError):\n    \"\"\" Exception when a disallowed or unallocated codepoint is used \"\"\"\n    pass\n\n\nclass InvalidCodepointContext(IDNAError):\n    \"\"\" Exception when the codepoint is not valid in the context it is used \"\"\"\n    pass\n\n\ndef _combining_class(cp):\n    v = unicodedata.combining(unichr(cp))\n    if v == 0:\n        if not unicodedata.name(unichr(cp)):\n            raise ValueError(\"Unknown character in unicodedata\")\n    return v\n\ndef _is_script(cp, script):\n    return intranges_contain(ord(cp), idnadata.scripts[script])\n\ndef _punycode(s):\n    return s.encode('punycode')\n\ndef _unot(s):\n    return 'U+{0:04X}'.format(s)\n\n\ndef valid_label_length(label):\n\n    if len(label) > 63:\n        return False\n    return True\n\n\ndef valid_string_length(label, trailing_dot):\n\n    if len(label) > (254 if trailing_dot else 253):\n        return False\n    return True\n\n\ndef check_bidi(label, check_ltr=False):\n\n    # Bidi rules should only be applied if string contains RTL characters\n    bidi_label = False\n    for (idx, cp) in enumerate(label, 1):\n        direction = unicodedata.bidirectional(cp)\n        if direction == '':\n            # String likely comes from a newer version of Unicode\n            raise IDNABidiError('Unknown directionality in label {0} at position {1}'.format(repr(label), idx))\n        if direction in ['R', 'AL', 'AN']:\n            bidi_label = True\n    if not bidi_label and not check_ltr:\n        return True\n\n    # Bidi rule 1\n    direction = unicodedata.bidirectional(label[0])\n    if direction in ['R', 'AL']:\n        rtl = True\n    elif direction == 'L':\n        rtl = False\n    else:\n        raise IDNABidiError('First codepoint in label {0} must be directionality L, R or AL'.format(repr(label)))\n\n    valid_ending = False\n    number_type = False\n    for (idx, cp) in enumerate(label, 1):\n        direction = unicodedata.bidirectional(cp)\n\n        if rtl:\n            # Bidi rule 2\n            if not direction in ['R', 'AL', 'AN', 'EN', 'ES', 'CS', 'ET', 'ON', 'BN', 'NSM']:\n                raise IDNABidiError('Invalid direction for codepoint at position {0} in a right-to-left label'.format(idx))\n            # Bidi rule 3\n            if direction in ['R', 'AL', 'EN', 'AN']:\n                valid_ending = True\n            elif direction != 'NSM':\n                valid_ending = False\n            # Bidi rule 4\n            if direction in ['AN', 'EN']:\n                if not number_type:\n                    number_type = direction\n                else:\n                    if number_type != direction:\n                        raise IDNABidiError('Can not mix numeral types in a right-to-left label')\n        else:\n            # Bidi rule 5\n            if not direction in ['L', 'EN', 'ES', 'CS', 'ET', 'ON', 'BN', 'NSM']:\n                raise IDNABidiError('Invalid direction for codepoint at position {0} in a left-to-right label'.format(idx))\n            # Bidi rule 6\n            if direction in ['L', 'EN']:\n                valid_ending = True\n            elif direction != 'NSM':\n                valid_ending = False\n\n    if not valid_ending:\n        raise IDNABidiError('Label ends with illegal codepoint directionality')\n\n    return True\n\n\ndef check_initial_combiner(label):\n\n    if unicodedata.category(label[0])[0] == 'M':\n        raise IDNAError('Label begins with an illegal combining character')\n    return True\n\n\ndef check_hyphen_ok(label):\n\n    if label[2:4] == '--':\n        raise IDNAError('Label has disallowed hyphens in 3rd and 4th position')\n    if label[0] == '-' or label[-1] == '-':\n        raise IDNAError('Label must not start or end with a hyphen')\n    return True\n\n\ndef check_nfc(label):\n\n    if unicodedata.normalize('NFC', label) != label:\n        raise IDNAError('Label must be in Normalization Form C')\n\n\ndef valid_contextj(label, pos):\n\n    cp_value = ord(label[pos])\n\n    if cp_value == 0x200c:\n\n        if pos > 0:\n            if _combining_class(ord(label[pos - 1])) == _virama_combining_class:\n                return True\n\n        ok = False\n        for i in range(pos-1, -1, -1):\n            joining_type = idnadata.joining_types.get(ord(label[i]))\n            if joining_type == ord('T'):\n                continue\n            if joining_type in [ord('L'), ord('D')]:\n                ok = True\n                break\n\n        if not ok:\n            return False\n\n        ok = False\n        for i in range(pos+1, len(label)):\n            joining_type = idnadata.joining_types.get(ord(label[i]))\n            if joining_type == ord('T'):\n                continue\n            if joining_type in [ord('R'), ord('D')]:\n                ok = True\n                break\n        return ok\n\n    if cp_value == 0x200d:\n\n        if pos > 0:\n            if _combining_class(ord(label[pos - 1])) == _virama_combining_class:\n                return True\n        return False\n\n    else:\n\n        return False\n\n\ndef valid_contexto(label, pos, exception=False):\n\n    cp_value = ord(label[pos])\n\n    if cp_value == 0x00b7:\n        if 0 < pos < len(label)-1:\n            if ord(label[pos - 1]) == 0x006c and ord(label[pos + 1]) == 0x006c:\n                return True\n        return False\n\n    elif cp_value == 0x0375:\n        if pos < len(label)-1 and len(label) > 1:\n            return _is_script(label[pos + 1], 'Greek')\n        return False\n\n    elif cp_value == 0x05f3 or cp_value == 0x05f4:\n        if pos > 0:\n            return _is_script(label[pos - 1], 'Hebrew')\n        return False\n\n    elif cp_value == 0x30fb:\n        for cp in label:\n            if cp == u'\\u30fb':\n                continue\n            if _is_script(cp, 'Hiragana') or _is_script(cp, 'Katakana') or _is_script(cp, 'Han'):\n                return True\n        return False\n\n    elif 0x660 <= cp_value <= 0x669:\n        for cp in label:\n            if 0x6f0 <= ord(cp) <= 0x06f9:\n                return False\n        return True\n\n    elif 0x6f0 <= cp_value <= 0x6f9:\n        for cp in label:\n            if 0x660 <= ord(cp) <= 0x0669:\n                return False\n        return True\n\n\ndef check_label(label):\n\n    if isinstance(label, (bytes, bytearray)):\n        label = label.decode('utf-8')\n    if len(label) == 0:\n        raise IDNAError('Empty Label')\n\n    check_nfc(label)\n    check_hyphen_ok(label)\n    check_initial_combiner(label)\n\n    for (pos, cp) in enumerate(label):\n        cp_value = ord(cp)\n        if intranges_contain(cp_value, idnadata.codepoint_classes['PVALID']):\n            continue\n        elif intranges_contain(cp_value, idnadata.codepoint_classes['CONTEXTJ']):\n            try:\n                if not valid_contextj(label, pos):\n                    raise InvalidCodepointContext('Joiner {0} not allowed at position {1} in {2}'.format(\n                        _unot(cp_value), pos+1, repr(label)))\n            except ValueError:\n                raise IDNAError('Unknown codepoint adjacent to joiner {0} at position {1} in {2}'.format(\n                    _unot(cp_value), pos+1, repr(label)))\n        elif intranges_contain(cp_value, idnadata.codepoint_classes['CONTEXTO']):\n            if not valid_contexto(label, pos):\n                raise InvalidCodepointContext('Codepoint {0} not allowed at position {1} in {2}'.format(_unot(cp_value), pos+1, repr(label)))\n        else:\n            raise InvalidCodepoint('Codepoint {0} at position {1} of {2} not allowed'.format(_unot(cp_value), pos+1, repr(label)))\n\n    check_bidi(label)\n\n\ndef alabel(label):\n\n    try:\n        label = label.encode('ascii')\n        ulabel(label)\n        if not valid_label_length(label):\n            raise IDNAError('Label too long')\n        return label\n    except UnicodeEncodeError:\n        pass\n\n    if not label:\n        raise IDNAError('No Input')\n\n    label = unicode(label)\n    check_label(label)\n    label = _punycode(label)\n    label = _alabel_prefix + label\n\n    if not valid_label_length(label):\n        raise IDNAError('Label too long')\n\n    return label\n\n\ndef ulabel(label):\n\n    if not isinstance(label, (bytes, bytearray)):\n        try:\n            label = label.encode('ascii')\n        except UnicodeEncodeError:\n            check_label(label)\n            return label\n\n    label = label.lower()\n    if label.startswith(_alabel_prefix):\n        label = label[len(_alabel_prefix):]\n    else:\n        check_label(label)\n        return label.decode('ascii')\n\n    label = label.decode('punycode')\n    check_label(label)\n    return label\n\n\ndef uts46_remap(domain, std3_rules=True, transitional=False):\n    \"\"\"Re-map the characters in the string according to UTS46 processing.\"\"\"\n    from .uts46data import uts46data\n    output = u\"\"\n    try:\n        for pos, char in enumerate(domain):\n            code_point = ord(char)\n            uts46row = uts46data[code_point if code_point < 256 else\n                bisect.bisect_left(uts46data, (code_point, \"Z\")) - 1]\n            status = uts46row[1]\n            replacement = uts46row[2] if len(uts46row) == 3 else None\n            if (status == \"V\" or\n                    (status == \"D\" and not transitional) or\n                    (status == \"3\" and not std3_rules and replacement is None)):\n                output += char\n            elif replacement is not None and (status == \"M\" or\n                    (status == \"3\" and not std3_rules) or\n                    (status == \"D\" and transitional)):\n                output += replacement\n            elif status != \"I\":\n                raise IndexError()\n        return unicodedata.normalize(\"NFC\", output)\n    except IndexError:\n        raise InvalidCodepoint(\n            \"Codepoint {0} not allowed at position {1} in {2}\".format(\n            _unot(code_point), pos + 1, repr(domain)))\n\n\ndef encode(s, strict=False, uts46=False, std3_rules=False, transitional=False):\n\n    if isinstance(s, (bytes, bytearray)):\n        s = s.decode(\"ascii\")\n    if uts46:\n        s = uts46_remap(s, std3_rules, transitional)\n    trailing_dot = False\n    result = []\n    if strict:\n        labels = s.split('.')\n    else:\n        labels = _unicode_dots_re.split(s)\n    if not labels or labels == ['']:\n        raise IDNAError('Empty domain')\n    if labels[-1] == '':\n        del labels[-1]\n        trailing_dot = True\n    for label in labels:\n        s = alabel(label)\n        if s:\n            result.append(s)\n        else:\n            raise IDNAError('Empty label')\n    if trailing_dot:\n        result.append(b'')\n    s = b'.'.join(result)\n    if not valid_string_length(s, trailing_dot):\n        raise IDNAError('Domain too long')\n    return s\n\n\ndef decode(s, strict=False, uts46=False, std3_rules=False):\n\n    if isinstance(s, (bytes, bytearray)):\n        s = s.decode(\"ascii\")\n    if uts46:\n        s = uts46_remap(s, std3_rules, False)\n    trailing_dot = False\n    result = []\n    if not strict:\n        labels = _unicode_dots_re.split(s)\n    else:\n        labels = s.split(u'.')\n    if not labels or labels == ['']:\n        raise IDNAError('Empty domain')\n    if not labels[-1]:\n        del labels[-1]\n        trailing_dot = True\n    for label in labels:\n        s = ulabel(label)\n        if s:\n            result.append(s)\n        else:\n            raise IDNAError('Empty label')\n    if trailing_dot:\n        result.append(u'')\n    return u'.'.join(result)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna/idnadata.py",
    "content": "# This file is automatically generated by tools/idna-data\n\n__version__ = \"11.0.0\"\nscripts = {\n    'Greek': (\n        0x37000000374,\n        0x37500000378,\n        0x37a0000037e,\n        0x37f00000380,\n        0x38400000385,\n        0x38600000387,\n        0x3880000038b,\n        0x38c0000038d,\n        0x38e000003a2,\n        0x3a3000003e2,\n        0x3f000000400,\n        0x1d2600001d2b,\n        0x1d5d00001d62,\n        0x1d6600001d6b,\n        0x1dbf00001dc0,\n        0x1f0000001f16,\n        0x1f1800001f1e,\n        0x1f2000001f46,\n        0x1f4800001f4e,\n        0x1f5000001f58,\n        0x1f5900001f5a,\n        0x1f5b00001f5c,\n        0x1f5d00001f5e,\n        0x1f5f00001f7e,\n        0x1f8000001fb5,\n        0x1fb600001fc5,\n        0x1fc600001fd4,\n        0x1fd600001fdc,\n        0x1fdd00001ff0,\n        0x1ff200001ff5,\n        0x1ff600001fff,\n        0x212600002127,\n        0xab650000ab66,\n        0x101400001018f,\n        0x101a0000101a1,\n        0x1d2000001d246,\n    ),\n    'Han': (\n        0x2e8000002e9a,\n        0x2e9b00002ef4,\n        0x2f0000002fd6,\n        0x300500003006,\n        0x300700003008,\n        0x30210000302a,\n        0x30380000303c,\n        0x340000004db6,\n        0x4e0000009ff0,\n        0xf9000000fa6e,\n        0xfa700000fada,\n        0x200000002a6d7,\n        0x2a7000002b735,\n        0x2b7400002b81e,\n        0x2b8200002cea2,\n        0x2ceb00002ebe1,\n        0x2f8000002fa1e,\n    ),\n    'Hebrew': (\n        0x591000005c8,\n        0x5d0000005eb,\n        0x5ef000005f5,\n        0xfb1d0000fb37,\n        0xfb380000fb3d,\n        0xfb3e0000fb3f,\n        0xfb400000fb42,\n        0xfb430000fb45,\n        0xfb460000fb50,\n    ),\n    'Hiragana': (\n        0x304100003097,\n        0x309d000030a0,\n        0x1b0010001b11f,\n        0x1f2000001f201,\n    ),\n    'Katakana': (\n        0x30a1000030fb,\n        0x30fd00003100,\n        0x31f000003200,\n        0x32d0000032ff,\n        0x330000003358,\n        0xff660000ff70,\n        0xff710000ff9e,\n        0x1b0000001b001,\n    ),\n}\njoining_types = {\n    0x600: 85,\n    0x601: 85,\n    0x602: 85,\n    0x603: 85,\n    0x604: 85,\n    0x605: 85,\n    0x608: 85,\n    0x60b: 85,\n    0x620: 68,\n    0x621: 85,\n    0x622: 82,\n    0x623: 82,\n    0x624: 82,\n    0x625: 82,\n    0x626: 68,\n    0x627: 82,\n    0x628: 68,\n    0x629: 82,\n    0x62a: 68,\n    0x62b: 68,\n    0x62c: 68,\n    0x62d: 68,\n    0x62e: 68,\n    0x62f: 82,\n    0x630: 82,\n    0x631: 82,\n    0x632: 82,\n    0x633: 68,\n    0x634: 68,\n    0x635: 68,\n    0x636: 68,\n    0x637: 68,\n    0x638: 68,\n    0x639: 68,\n    0x63a: 68,\n    0x63b: 68,\n    0x63c: 68,\n    0x63d: 68,\n    0x63e: 68,\n    0x63f: 68,\n    0x640: 67,\n    0x641: 68,\n    0x642: 68,\n    0x643: 68,\n    0x644: 68,\n    0x645: 68,\n    0x646: 68,\n    0x647: 68,\n    0x648: 82,\n    0x649: 68,\n    0x64a: 68,\n    0x66e: 68,\n    0x66f: 68,\n    0x671: 82,\n    0x672: 82,\n    0x673: 82,\n    0x674: 85,\n    0x675: 82,\n    0x676: 82,\n    0x677: 82,\n    0x678: 68,\n    0x679: 68,\n    0x67a: 68,\n    0x67b: 68,\n    0x67c: 68,\n    0x67d: 68,\n    0x67e: 68,\n    0x67f: 68,\n    0x680: 68,\n    0x681: 68,\n    0x682: 68,\n    0x683: 68,\n    0x684: 68,\n    0x685: 68,\n    0x686: 68,\n    0x687: 68,\n    0x688: 82,\n    0x689: 82,\n    0x68a: 82,\n    0x68b: 82,\n    0x68c: 82,\n    0x68d: 82,\n    0x68e: 82,\n    0x68f: 82,\n    0x690: 82,\n    0x691: 82,\n    0x692: 82,\n    0x693: 82,\n    0x694: 82,\n    0x695: 82,\n    0x696: 82,\n    0x697: 82,\n    0x698: 82,\n    0x699: 82,\n    0x69a: 68,\n    0x69b: 68,\n    0x69c: 68,\n    0x69d: 68,\n    0x69e: 68,\n    0x69f: 68,\n    0x6a0: 68,\n    0x6a1: 68,\n    0x6a2: 68,\n    0x6a3: 68,\n    0x6a4: 68,\n    0x6a5: 68,\n    0x6a6: 68,\n    0x6a7: 68,\n    0x6a8: 68,\n    0x6a9: 68,\n    0x6aa: 68,\n    0x6ab: 68,\n    0x6ac: 68,\n    0x6ad: 68,\n    0x6ae: 68,\n    0x6af: 68,\n    0x6b0: 68,\n    0x6b1: 68,\n    0x6b2: 68,\n    0x6b3: 68,\n    0x6b4: 68,\n    0x6b5: 68,\n    0x6b6: 68,\n    0x6b7: 68,\n    0x6b8: 68,\n    0x6b9: 68,\n    0x6ba: 68,\n    0x6bb: 68,\n    0x6bc: 68,\n    0x6bd: 68,\n    0x6be: 68,\n    0x6bf: 68,\n    0x6c0: 82,\n    0x6c1: 68,\n    0x6c2: 68,\n    0x6c3: 82,\n    0x6c4: 82,\n    0x6c5: 82,\n    0x6c6: 82,\n    0x6c7: 82,\n    0x6c8: 82,\n    0x6c9: 82,\n    0x6ca: 82,\n    0x6cb: 82,\n    0x6cc: 68,\n    0x6cd: 82,\n    0x6ce: 68,\n    0x6cf: 82,\n    0x6d0: 68,\n    0x6d1: 68,\n    0x6d2: 82,\n    0x6d3: 82,\n    0x6d5: 82,\n    0x6dd: 85,\n    0x6ee: 82,\n    0x6ef: 82,\n    0x6fa: 68,\n    0x6fb: 68,\n    0x6fc: 68,\n    0x6ff: 68,\n    0x70f: 84,\n    0x710: 82,\n    0x712: 68,\n    0x713: 68,\n    0x714: 68,\n    0x715: 82,\n    0x716: 82,\n    0x717: 82,\n    0x718: 82,\n    0x719: 82,\n    0x71a: 68,\n    0x71b: 68,\n    0x71c: 68,\n    0x71d: 68,\n    0x71e: 82,\n    0x71f: 68,\n    0x720: 68,\n    0x721: 68,\n    0x722: 68,\n    0x723: 68,\n    0x724: 68,\n    0x725: 68,\n    0x726: 68,\n    0x727: 68,\n    0x728: 82,\n    0x729: 68,\n    0x72a: 82,\n    0x72b: 68,\n    0x72c: 82,\n    0x72d: 68,\n    0x72e: 68,\n    0x72f: 82,\n    0x74d: 82,\n    0x74e: 68,\n    0x74f: 68,\n    0x750: 68,\n    0x751: 68,\n    0x752: 68,\n    0x753: 68,\n    0x754: 68,\n    0x755: 68,\n    0x756: 68,\n    0x757: 68,\n    0x758: 68,\n    0x759: 82,\n    0x75a: 82,\n    0x75b: 82,\n    0x75c: 68,\n    0x75d: 68,\n    0x75e: 68,\n    0x75f: 68,\n    0x760: 68,\n    0x761: 68,\n    0x762: 68,\n    0x763: 68,\n    0x764: 68,\n    0x765: 68,\n    0x766: 68,\n    0x767: 68,\n    0x768: 68,\n    0x769: 68,\n    0x76a: 68,\n    0x76b: 82,\n    0x76c: 82,\n    0x76d: 68,\n    0x76e: 68,\n    0x76f: 68,\n    0x770: 68,\n    0x771: 82,\n    0x772: 68,\n    0x773: 82,\n    0x774: 82,\n    0x775: 68,\n    0x776: 68,\n    0x777: 68,\n    0x778: 82,\n    0x779: 82,\n    0x77a: 68,\n    0x77b: 68,\n    0x77c: 68,\n    0x77d: 68,\n    0x77e: 68,\n    0x77f: 68,\n    0x7ca: 68,\n    0x7cb: 68,\n    0x7cc: 68,\n    0x7cd: 68,\n    0x7ce: 68,\n    0x7cf: 68,\n    0x7d0: 68,\n    0x7d1: 68,\n    0x7d2: 68,\n    0x7d3: 68,\n    0x7d4: 68,\n    0x7d5: 68,\n    0x7d6: 68,\n    0x7d7: 68,\n    0x7d8: 68,\n    0x7d9: 68,\n    0x7da: 68,\n    0x7db: 68,\n    0x7dc: 68,\n    0x7dd: 68,\n    0x7de: 68,\n    0x7df: 68,\n    0x7e0: 68,\n    0x7e1: 68,\n    0x7e2: 68,\n    0x7e3: 68,\n    0x7e4: 68,\n    0x7e5: 68,\n    0x7e6: 68,\n    0x7e7: 68,\n    0x7e8: 68,\n    0x7e9: 68,\n    0x7ea: 68,\n    0x7fa: 67,\n    0x840: 82,\n    0x841: 68,\n    0x842: 68,\n    0x843: 68,\n    0x844: 68,\n    0x845: 68,\n    0x846: 82,\n    0x847: 82,\n    0x848: 68,\n    0x849: 82,\n    0x84a: 68,\n    0x84b: 68,\n    0x84c: 68,\n    0x84d: 68,\n    0x84e: 68,\n    0x84f: 68,\n    0x850: 68,\n    0x851: 68,\n    0x852: 68,\n    0x853: 68,\n    0x854: 82,\n    0x855: 68,\n    0x856: 85,\n    0x857: 85,\n    0x858: 85,\n    0x860: 68,\n    0x861: 85,\n    0x862: 68,\n    0x863: 68,\n    0x864: 68,\n    0x865: 68,\n    0x866: 85,\n    0x867: 82,\n    0x868: 68,\n    0x869: 82,\n    0x86a: 82,\n    0x8a0: 68,\n    0x8a1: 68,\n    0x8a2: 68,\n    0x8a3: 68,\n    0x8a4: 68,\n    0x8a5: 68,\n    0x8a6: 68,\n    0x8a7: 68,\n    0x8a8: 68,\n    0x8a9: 68,\n    0x8aa: 82,\n    0x8ab: 82,\n    0x8ac: 82,\n    0x8ad: 85,\n    0x8ae: 82,\n    0x8af: 68,\n    0x8b0: 68,\n    0x8b1: 82,\n    0x8b2: 82,\n    0x8b3: 68,\n    0x8b4: 68,\n    0x8b6: 68,\n    0x8b7: 68,\n    0x8b8: 68,\n    0x8b9: 82,\n    0x8ba: 68,\n    0x8bb: 68,\n    0x8bc: 68,\n    0x8bd: 68,\n    0x8e2: 85,\n    0x1806: 85,\n    0x1807: 68,\n    0x180a: 67,\n    0x180e: 85,\n    0x1820: 68,\n    0x1821: 68,\n    0x1822: 68,\n    0x1823: 68,\n    0x1824: 68,\n    0x1825: 68,\n    0x1826: 68,\n    0x1827: 68,\n    0x1828: 68,\n    0x1829: 68,\n    0x182a: 68,\n    0x182b: 68,\n    0x182c: 68,\n    0x182d: 68,\n    0x182e: 68,\n    0x182f: 68,\n    0x1830: 68,\n    0x1831: 68,\n    0x1832: 68,\n    0x1833: 68,\n    0x1834: 68,\n    0x1835: 68,\n    0x1836: 68,\n    0x1837: 68,\n    0x1838: 68,\n    0x1839: 68,\n    0x183a: 68,\n    0x183b: 68,\n    0x183c: 68,\n    0x183d: 68,\n    0x183e: 68,\n    0x183f: 68,\n    0x1840: 68,\n    0x1841: 68,\n    0x1842: 68,\n    0x1843: 68,\n    0x1844: 68,\n    0x1845: 68,\n    0x1846: 68,\n    0x1847: 68,\n    0x1848: 68,\n    0x1849: 68,\n    0x184a: 68,\n    0x184b: 68,\n    0x184c: 68,\n    0x184d: 68,\n    0x184e: 68,\n    0x184f: 68,\n    0x1850: 68,\n    0x1851: 68,\n    0x1852: 68,\n    0x1853: 68,\n    0x1854: 68,\n    0x1855: 68,\n    0x1856: 68,\n    0x1857: 68,\n    0x1858: 68,\n    0x1859: 68,\n    0x185a: 68,\n    0x185b: 68,\n    0x185c: 68,\n    0x185d: 68,\n    0x185e: 68,\n    0x185f: 68,\n    0x1860: 68,\n    0x1861: 68,\n    0x1862: 68,\n    0x1863: 68,\n    0x1864: 68,\n    0x1865: 68,\n    0x1866: 68,\n    0x1867: 68,\n    0x1868: 68,\n    0x1869: 68,\n    0x186a: 68,\n    0x186b: 68,\n    0x186c: 68,\n    0x186d: 68,\n    0x186e: 68,\n    0x186f: 68,\n    0x1870: 68,\n    0x1871: 68,\n    0x1872: 68,\n    0x1873: 68,\n    0x1874: 68,\n    0x1875: 68,\n    0x1876: 68,\n    0x1877: 68,\n    0x1878: 68,\n    0x1880: 85,\n    0x1881: 85,\n    0x1882: 85,\n    0x1883: 85,\n    0x1884: 85,\n    0x1885: 84,\n    0x1886: 84,\n    0x1887: 68,\n    0x1888: 68,\n    0x1889: 68,\n    0x188a: 68,\n    0x188b: 68,\n    0x188c: 68,\n    0x188d: 68,\n    0x188e: 68,\n    0x188f: 68,\n    0x1890: 68,\n    0x1891: 68,\n    0x1892: 68,\n    0x1893: 68,\n    0x1894: 68,\n    0x1895: 68,\n    0x1896: 68,\n    0x1897: 68,\n    0x1898: 68,\n    0x1899: 68,\n    0x189a: 68,\n    0x189b: 68,\n    0x189c: 68,\n    0x189d: 68,\n    0x189e: 68,\n    0x189f: 68,\n    0x18a0: 68,\n    0x18a1: 68,\n    0x18a2: 68,\n    0x18a3: 68,\n    0x18a4: 68,\n    0x18a5: 68,\n    0x18a6: 68,\n    0x18a7: 68,\n    0x18a8: 68,\n    0x18aa: 68,\n    0x200c: 85,\n    0x200d: 67,\n    0x202f: 85,\n    0x2066: 85,\n    0x2067: 85,\n    0x2068: 85,\n    0x2069: 85,\n    0xa840: 68,\n    0xa841: 68,\n    0xa842: 68,\n    0xa843: 68,\n    0xa844: 68,\n    0xa845: 68,\n    0xa846: 68,\n    0xa847: 68,\n    0xa848: 68,\n    0xa849: 68,\n    0xa84a: 68,\n    0xa84b: 68,\n    0xa84c: 68,\n    0xa84d: 68,\n    0xa84e: 68,\n    0xa84f: 68,\n    0xa850: 68,\n    0xa851: 68,\n    0xa852: 68,\n    0xa853: 68,\n    0xa854: 68,\n    0xa855: 68,\n    0xa856: 68,\n    0xa857: 68,\n    0xa858: 68,\n    0xa859: 68,\n    0xa85a: 68,\n    0xa85b: 68,\n    0xa85c: 68,\n    0xa85d: 68,\n    0xa85e: 68,\n    0xa85f: 68,\n    0xa860: 68,\n    0xa861: 68,\n    0xa862: 68,\n    0xa863: 68,\n    0xa864: 68,\n    0xa865: 68,\n    0xa866: 68,\n    0xa867: 68,\n    0xa868: 68,\n    0xa869: 68,\n    0xa86a: 68,\n    0xa86b: 68,\n    0xa86c: 68,\n    0xa86d: 68,\n    0xa86e: 68,\n    0xa86f: 68,\n    0xa870: 68,\n    0xa871: 68,\n    0xa872: 76,\n    0xa873: 85,\n    0x10ac0: 68,\n    0x10ac1: 68,\n    0x10ac2: 68,\n    0x10ac3: 68,\n    0x10ac4: 68,\n    0x10ac5: 82,\n    0x10ac6: 85,\n    0x10ac7: 82,\n    0x10ac8: 85,\n    0x10ac9: 82,\n    0x10aca: 82,\n    0x10acb: 85,\n    0x10acc: 85,\n    0x10acd: 76,\n    0x10ace: 82,\n    0x10acf: 82,\n    0x10ad0: 82,\n    0x10ad1: 82,\n    0x10ad2: 82,\n    0x10ad3: 68,\n    0x10ad4: 68,\n    0x10ad5: 68,\n    0x10ad6: 68,\n    0x10ad7: 76,\n    0x10ad8: 68,\n    0x10ad9: 68,\n    0x10ada: 68,\n    0x10adb: 68,\n    0x10adc: 68,\n    0x10add: 82,\n    0x10ade: 68,\n    0x10adf: 68,\n    0x10ae0: 68,\n    0x10ae1: 82,\n    0x10ae2: 85,\n    0x10ae3: 85,\n    0x10ae4: 82,\n    0x10aeb: 68,\n    0x10aec: 68,\n    0x10aed: 68,\n    0x10aee: 68,\n    0x10aef: 82,\n    0x10b80: 68,\n    0x10b81: 82,\n    0x10b82: 68,\n    0x10b83: 82,\n    0x10b84: 82,\n    0x10b85: 82,\n    0x10b86: 68,\n    0x10b87: 68,\n    0x10b88: 68,\n    0x10b89: 82,\n    0x10b8a: 68,\n    0x10b8b: 68,\n    0x10b8c: 82,\n    0x10b8d: 68,\n    0x10b8e: 82,\n    0x10b8f: 82,\n    0x10b90: 68,\n    0x10b91: 82,\n    0x10ba9: 82,\n    0x10baa: 82,\n    0x10bab: 82,\n    0x10bac: 82,\n    0x10bad: 68,\n    0x10bae: 68,\n    0x10baf: 85,\n    0x10d00: 76,\n    0x10d01: 68,\n    0x10d02: 68,\n    0x10d03: 68,\n    0x10d04: 68,\n    0x10d05: 68,\n    0x10d06: 68,\n    0x10d07: 68,\n    0x10d08: 68,\n    0x10d09: 68,\n    0x10d0a: 68,\n    0x10d0b: 68,\n    0x10d0c: 68,\n    0x10d0d: 68,\n    0x10d0e: 68,\n    0x10d0f: 68,\n    0x10d10: 68,\n    0x10d11: 68,\n    0x10d12: 68,\n    0x10d13: 68,\n    0x10d14: 68,\n    0x10d15: 68,\n    0x10d16: 68,\n    0x10d17: 68,\n    0x10d18: 68,\n    0x10d19: 68,\n    0x10d1a: 68,\n    0x10d1b: 68,\n    0x10d1c: 68,\n    0x10d1d: 68,\n    0x10d1e: 68,\n    0x10d1f: 68,\n    0x10d20: 68,\n    0x10d21: 68,\n    0x10d22: 82,\n    0x10d23: 68,\n    0x10f30: 68,\n    0x10f31: 68,\n    0x10f32: 68,\n    0x10f33: 82,\n    0x10f34: 68,\n    0x10f35: 68,\n    0x10f36: 68,\n    0x10f37: 68,\n    0x10f38: 68,\n    0x10f39: 68,\n    0x10f3a: 68,\n    0x10f3b: 68,\n    0x10f3c: 68,\n    0x10f3d: 68,\n    0x10f3e: 68,\n    0x10f3f: 68,\n    0x10f40: 68,\n    0x10f41: 68,\n    0x10f42: 68,\n    0x10f43: 68,\n    0x10f44: 68,\n    0x10f45: 85,\n    0x10f51: 68,\n    0x10f52: 68,\n    0x10f53: 68,\n    0x10f54: 82,\n    0x110bd: 85,\n    0x110cd: 85,\n    0x1e900: 68,\n    0x1e901: 68,\n    0x1e902: 68,\n    0x1e903: 68,\n    0x1e904: 68,\n    0x1e905: 68,\n    0x1e906: 68,\n    0x1e907: 68,\n    0x1e908: 68,\n    0x1e909: 68,\n    0x1e90a: 68,\n    0x1e90b: 68,\n    0x1e90c: 68,\n    0x1e90d: 68,\n    0x1e90e: 68,\n    0x1e90f: 68,\n    0x1e910: 68,\n    0x1e911: 68,\n    0x1e912: 68,\n    0x1e913: 68,\n    0x1e914: 68,\n    0x1e915: 68,\n    0x1e916: 68,\n    0x1e917: 68,\n    0x1e918: 68,\n    0x1e919: 68,\n    0x1e91a: 68,\n    0x1e91b: 68,\n    0x1e91c: 68,\n    0x1e91d: 68,\n    0x1e91e: 68,\n    0x1e91f: 68,\n    0x1e920: 68,\n    0x1e921: 68,\n    0x1e922: 68,\n    0x1e923: 68,\n    0x1e924: 68,\n    0x1e925: 68,\n    0x1e926: 68,\n    0x1e927: 68,\n    0x1e928: 68,\n    0x1e929: 68,\n    0x1e92a: 68,\n    0x1e92b: 68,\n    0x1e92c: 68,\n    0x1e92d: 68,\n    0x1e92e: 68,\n    0x1e92f: 68,\n    0x1e930: 68,\n    0x1e931: 68,\n    0x1e932: 68,\n    0x1e933: 68,\n    0x1e934: 68,\n    0x1e935: 68,\n    0x1e936: 68,\n    0x1e937: 68,\n    0x1e938: 68,\n    0x1e939: 68,\n    0x1e93a: 68,\n    0x1e93b: 68,\n    0x1e93c: 68,\n    0x1e93d: 68,\n    0x1e93e: 68,\n    0x1e93f: 68,\n    0x1e940: 68,\n    0x1e941: 68,\n    0x1e942: 68,\n    0x1e943: 68,\n}\ncodepoint_classes = {\n    'PVALID': (\n        0x2d0000002e,\n        0x300000003a,\n        0x610000007b,\n        0xdf000000f7,\n        0xf800000100,\n        0x10100000102,\n        0x10300000104,\n        0x10500000106,\n        0x10700000108,\n        0x1090000010a,\n        0x10b0000010c,\n        0x10d0000010e,\n        0x10f00000110,\n        0x11100000112,\n        0x11300000114,\n        0x11500000116,\n        0x11700000118,\n        0x1190000011a,\n        0x11b0000011c,\n        0x11d0000011e,\n        0x11f00000120,\n        0x12100000122,\n        0x12300000124,\n        0x12500000126,\n        0x12700000128,\n        0x1290000012a,\n        0x12b0000012c,\n        0x12d0000012e,\n        0x12f00000130,\n        0x13100000132,\n        0x13500000136,\n        0x13700000139,\n        0x13a0000013b,\n        0x13c0000013d,\n        0x13e0000013f,\n        0x14200000143,\n        0x14400000145,\n        0x14600000147,\n        0x14800000149,\n        0x14b0000014c,\n        0x14d0000014e,\n        0x14f00000150,\n        0x15100000152,\n        0x15300000154,\n        0x15500000156,\n        0x15700000158,\n        0x1590000015a,\n        0x15b0000015c,\n        0x15d0000015e,\n        0x15f00000160,\n        0x16100000162,\n        0x16300000164,\n        0x16500000166,\n        0x16700000168,\n        0x1690000016a,\n        0x16b0000016c,\n        0x16d0000016e,\n        0x16f00000170,\n        0x17100000172,\n        0x17300000174,\n        0x17500000176,\n        0x17700000178,\n        0x17a0000017b,\n        0x17c0000017d,\n        0x17e0000017f,\n        0x18000000181,\n        0x18300000184,\n        0x18500000186,\n        0x18800000189,\n        0x18c0000018e,\n        0x19200000193,\n        0x19500000196,\n        0x1990000019c,\n        0x19e0000019f,\n        0x1a1000001a2,\n        0x1a3000001a4,\n        0x1a5000001a6,\n        0x1a8000001a9,\n        0x1aa000001ac,\n        0x1ad000001ae,\n        0x1b0000001b1,\n        0x1b4000001b5,\n        0x1b6000001b7,\n        0x1b9000001bc,\n        0x1bd000001c4,\n        0x1ce000001cf,\n        0x1d0000001d1,\n        0x1d2000001d3,\n        0x1d4000001d5,\n        0x1d6000001d7,\n        0x1d8000001d9,\n        0x1da000001db,\n        0x1dc000001de,\n        0x1df000001e0,\n        0x1e1000001e2,\n        0x1e3000001e4,\n        0x1e5000001e6,\n        0x1e7000001e8,\n        0x1e9000001ea,\n        0x1eb000001ec,\n        0x1ed000001ee,\n        0x1ef000001f1,\n        0x1f5000001f6,\n        0x1f9000001fa,\n        0x1fb000001fc,\n        0x1fd000001fe,\n        0x1ff00000200,\n        0x20100000202,\n        0x20300000204,\n        0x20500000206,\n        0x20700000208,\n        0x2090000020a,\n        0x20b0000020c,\n        0x20d0000020e,\n        0x20f00000210,\n        0x21100000212,\n        0x21300000214,\n        0x21500000216,\n        0x21700000218,\n        0x2190000021a,\n        0x21b0000021c,\n        0x21d0000021e,\n        0x21f00000220,\n        0x22100000222,\n        0x22300000224,\n        0x22500000226,\n        0x22700000228,\n        0x2290000022a,\n        0x22b0000022c,\n        0x22d0000022e,\n        0x22f00000230,\n        0x23100000232,\n        0x2330000023a,\n        0x23c0000023d,\n        0x23f00000241,\n        0x24200000243,\n        0x24700000248,\n        0x2490000024a,\n        0x24b0000024c,\n        0x24d0000024e,\n        0x24f000002b0,\n        0x2b9000002c2,\n        0x2c6000002d2,\n        0x2ec000002ed,\n        0x2ee000002ef,\n        0x30000000340,\n        0x34200000343,\n        0x3460000034f,\n        0x35000000370,\n        0x37100000372,\n        0x37300000374,\n        0x37700000378,\n        0x37b0000037e,\n        0x39000000391,\n        0x3ac000003cf,\n        0x3d7000003d8,\n        0x3d9000003da,\n        0x3db000003dc,\n        0x3dd000003de,\n        0x3df000003e0,\n        0x3e1000003e2,\n        0x3e3000003e4,\n        0x3e5000003e6,\n        0x3e7000003e8,\n        0x3e9000003ea,\n        0x3eb000003ec,\n        0x3ed000003ee,\n        0x3ef000003f0,\n        0x3f3000003f4,\n        0x3f8000003f9,\n        0x3fb000003fd,\n        0x43000000460,\n        0x46100000462,\n        0x46300000464,\n        0x46500000466,\n        0x46700000468,\n        0x4690000046a,\n        0x46b0000046c,\n        0x46d0000046e,\n        0x46f00000470,\n        0x47100000472,\n        0x47300000474,\n        0x47500000476,\n        0x47700000478,\n        0x4790000047a,\n        0x47b0000047c,\n        0x47d0000047e,\n        0x47f00000480,\n        0x48100000482,\n        0x48300000488,\n        0x48b0000048c,\n        0x48d0000048e,\n        0x48f00000490,\n        0x49100000492,\n        0x49300000494,\n        0x49500000496,\n        0x49700000498,\n        0x4990000049a,\n        0x49b0000049c,\n        0x49d0000049e,\n        0x49f000004a0,\n        0x4a1000004a2,\n        0x4a3000004a4,\n        0x4a5000004a6,\n        0x4a7000004a8,\n        0x4a9000004aa,\n        0x4ab000004ac,\n        0x4ad000004ae,\n        0x4af000004b0,\n        0x4b1000004b2,\n        0x4b3000004b4,\n        0x4b5000004b6,\n        0x4b7000004b8,\n        0x4b9000004ba,\n        0x4bb000004bc,\n        0x4bd000004be,\n        0x4bf000004c0,\n        0x4c2000004c3,\n        0x4c4000004c5,\n        0x4c6000004c7,\n        0x4c8000004c9,\n        0x4ca000004cb,\n        0x4cc000004cd,\n        0x4ce000004d0,\n        0x4d1000004d2,\n        0x4d3000004d4,\n        0x4d5000004d6,\n        0x4d7000004d8,\n        0x4d9000004da,\n        0x4db000004dc,\n        0x4dd000004de,\n        0x4df000004e0,\n        0x4e1000004e2,\n        0x4e3000004e4,\n        0x4e5000004e6,\n        0x4e7000004e8,\n        0x4e9000004ea,\n        0x4eb000004ec,\n        0x4ed000004ee,\n        0x4ef000004f0,\n        0x4f1000004f2,\n        0x4f3000004f4,\n        0x4f5000004f6,\n        0x4f7000004f8,\n        0x4f9000004fa,\n        0x4fb000004fc,\n        0x4fd000004fe,\n        0x4ff00000500,\n        0x50100000502,\n        0x50300000504,\n        0x50500000506,\n        0x50700000508,\n        0x5090000050a,\n        0x50b0000050c,\n        0x50d0000050e,\n        0x50f00000510,\n        0x51100000512,\n        0x51300000514,\n        0x51500000516,\n        0x51700000518,\n        0x5190000051a,\n        0x51b0000051c,\n        0x51d0000051e,\n        0x51f00000520,\n        0x52100000522,\n        0x52300000524,\n        0x52500000526,\n        0x52700000528,\n        0x5290000052a,\n        0x52b0000052c,\n        0x52d0000052e,\n        0x52f00000530,\n        0x5590000055a,\n        0x56000000587,\n        0x58800000589,\n        0x591000005be,\n        0x5bf000005c0,\n        0x5c1000005c3,\n        0x5c4000005c6,\n        0x5c7000005c8,\n        0x5d0000005eb,\n        0x5ef000005f3,\n        0x6100000061b,\n        0x62000000640,\n        0x64100000660,\n        0x66e00000675,\n        0x679000006d4,\n        0x6d5000006dd,\n        0x6df000006e9,\n        0x6ea000006f0,\n        0x6fa00000700,\n        0x7100000074b,\n        0x74d000007b2,\n        0x7c0000007f6,\n        0x7fd000007fe,\n        0x8000000082e,\n        0x8400000085c,\n        0x8600000086b,\n        0x8a0000008b5,\n        0x8b6000008be,\n        0x8d3000008e2,\n        0x8e300000958,\n        0x96000000964,\n        0x96600000970,\n        0x97100000984,\n        0x9850000098d,\n        0x98f00000991,\n        0x993000009a9,\n        0x9aa000009b1,\n        0x9b2000009b3,\n        0x9b6000009ba,\n        0x9bc000009c5,\n        0x9c7000009c9,\n        0x9cb000009cf,\n        0x9d7000009d8,\n        0x9e0000009e4,\n        0x9e6000009f2,\n        0x9fc000009fd,\n        0x9fe000009ff,\n        0xa0100000a04,\n        0xa0500000a0b,\n        0xa0f00000a11,\n        0xa1300000a29,\n        0xa2a00000a31,\n        0xa3200000a33,\n        0xa3500000a36,\n        0xa3800000a3a,\n        0xa3c00000a3d,\n        0xa3e00000a43,\n        0xa4700000a49,\n        0xa4b00000a4e,\n        0xa5100000a52,\n        0xa5c00000a5d,\n        0xa6600000a76,\n        0xa8100000a84,\n        0xa8500000a8e,\n        0xa8f00000a92,\n        0xa9300000aa9,\n        0xaaa00000ab1,\n        0xab200000ab4,\n        0xab500000aba,\n        0xabc00000ac6,\n        0xac700000aca,\n        0xacb00000ace,\n        0xad000000ad1,\n        0xae000000ae4,\n        0xae600000af0,\n        0xaf900000b00,\n        0xb0100000b04,\n        0xb0500000b0d,\n        0xb0f00000b11,\n        0xb1300000b29,\n        0xb2a00000b31,\n        0xb3200000b34,\n        0xb3500000b3a,\n        0xb3c00000b45,\n        0xb4700000b49,\n        0xb4b00000b4e,\n        0xb5600000b58,\n        0xb5f00000b64,\n        0xb6600000b70,\n        0xb7100000b72,\n        0xb8200000b84,\n        0xb8500000b8b,\n        0xb8e00000b91,\n        0xb9200000b96,\n        0xb9900000b9b,\n        0xb9c00000b9d,\n        0xb9e00000ba0,\n        0xba300000ba5,\n        0xba800000bab,\n        0xbae00000bba,\n        0xbbe00000bc3,\n        0xbc600000bc9,\n        0xbca00000bce,\n        0xbd000000bd1,\n        0xbd700000bd8,\n        0xbe600000bf0,\n        0xc0000000c0d,\n        0xc0e00000c11,\n        0xc1200000c29,\n        0xc2a00000c3a,\n        0xc3d00000c45,\n        0xc4600000c49,\n        0xc4a00000c4e,\n        0xc5500000c57,\n        0xc5800000c5b,\n        0xc6000000c64,\n        0xc6600000c70,\n        0xc8000000c84,\n        0xc8500000c8d,\n        0xc8e00000c91,\n        0xc9200000ca9,\n        0xcaa00000cb4,\n        0xcb500000cba,\n        0xcbc00000cc5,\n        0xcc600000cc9,\n        0xcca00000cce,\n        0xcd500000cd7,\n        0xcde00000cdf,\n        0xce000000ce4,\n        0xce600000cf0,\n        0xcf100000cf3,\n        0xd0000000d04,\n        0xd0500000d0d,\n        0xd0e00000d11,\n        0xd1200000d45,\n        0xd4600000d49,\n        0xd4a00000d4f,\n        0xd5400000d58,\n        0xd5f00000d64,\n        0xd6600000d70,\n        0xd7a00000d80,\n        0xd8200000d84,\n        0xd8500000d97,\n        0xd9a00000db2,\n        0xdb300000dbc,\n        0xdbd00000dbe,\n        0xdc000000dc7,\n        0xdca00000dcb,\n        0xdcf00000dd5,\n        0xdd600000dd7,\n        0xdd800000de0,\n        0xde600000df0,\n        0xdf200000df4,\n        0xe0100000e33,\n        0xe3400000e3b,\n        0xe4000000e4f,\n        0xe5000000e5a,\n        0xe8100000e83,\n        0xe8400000e85,\n        0xe8700000e89,\n        0xe8a00000e8b,\n        0xe8d00000e8e,\n        0xe9400000e98,\n        0xe9900000ea0,\n        0xea100000ea4,\n        0xea500000ea6,\n        0xea700000ea8,\n        0xeaa00000eac,\n        0xead00000eb3,\n        0xeb400000eba,\n        0xebb00000ebe,\n        0xec000000ec5,\n        0xec600000ec7,\n        0xec800000ece,\n        0xed000000eda,\n        0xede00000ee0,\n        0xf0000000f01,\n        0xf0b00000f0c,\n        0xf1800000f1a,\n        0xf2000000f2a,\n        0xf3500000f36,\n        0xf3700000f38,\n        0xf3900000f3a,\n        0xf3e00000f43,\n        0xf4400000f48,\n        0xf4900000f4d,\n        0xf4e00000f52,\n        0xf5300000f57,\n        0xf5800000f5c,\n        0xf5d00000f69,\n        0xf6a00000f6d,\n        0xf7100000f73,\n        0xf7400000f75,\n        0xf7a00000f81,\n        0xf8200000f85,\n        0xf8600000f93,\n        0xf9400000f98,\n        0xf9900000f9d,\n        0xf9e00000fa2,\n        0xfa300000fa7,\n        0xfa800000fac,\n        0xfad00000fb9,\n        0xfba00000fbd,\n        0xfc600000fc7,\n        0x10000000104a,\n        0x10500000109e,\n        0x10d0000010fb,\n        0x10fd00001100,\n        0x120000001249,\n        0x124a0000124e,\n        0x125000001257,\n        0x125800001259,\n        0x125a0000125e,\n        0x126000001289,\n        0x128a0000128e,\n        0x1290000012b1,\n        0x12b2000012b6,\n        0x12b8000012bf,\n        0x12c0000012c1,\n        0x12c2000012c6,\n        0x12c8000012d7,\n        0x12d800001311,\n        0x131200001316,\n        0x13180000135b,\n        0x135d00001360,\n        0x138000001390,\n        0x13a0000013f6,\n        0x14010000166d,\n        0x166f00001680,\n        0x16810000169b,\n        0x16a0000016eb,\n        0x16f1000016f9,\n        0x17000000170d,\n        0x170e00001715,\n        0x172000001735,\n        0x174000001754,\n        0x17600000176d,\n        0x176e00001771,\n        0x177200001774,\n        0x1780000017b4,\n        0x17b6000017d4,\n        0x17d7000017d8,\n        0x17dc000017de,\n        0x17e0000017ea,\n        0x18100000181a,\n        0x182000001879,\n        0x1880000018ab,\n        0x18b0000018f6,\n        0x19000000191f,\n        0x19200000192c,\n        0x19300000193c,\n        0x19460000196e,\n        0x197000001975,\n        0x1980000019ac,\n        0x19b0000019ca,\n        0x19d0000019da,\n        0x1a0000001a1c,\n        0x1a2000001a5f,\n        0x1a6000001a7d,\n        0x1a7f00001a8a,\n        0x1a9000001a9a,\n        0x1aa700001aa8,\n        0x1ab000001abe,\n        0x1b0000001b4c,\n        0x1b5000001b5a,\n        0x1b6b00001b74,\n        0x1b8000001bf4,\n        0x1c0000001c38,\n        0x1c4000001c4a,\n        0x1c4d00001c7e,\n        0x1cd000001cd3,\n        0x1cd400001cfa,\n        0x1d0000001d2c,\n        0x1d2f00001d30,\n        0x1d3b00001d3c,\n        0x1d4e00001d4f,\n        0x1d6b00001d78,\n        0x1d7900001d9b,\n        0x1dc000001dfa,\n        0x1dfb00001e00,\n        0x1e0100001e02,\n        0x1e0300001e04,\n        0x1e0500001e06,\n        0x1e0700001e08,\n        0x1e0900001e0a,\n        0x1e0b00001e0c,\n        0x1e0d00001e0e,\n        0x1e0f00001e10,\n        0x1e1100001e12,\n        0x1e1300001e14,\n        0x1e1500001e16,\n        0x1e1700001e18,\n        0x1e1900001e1a,\n        0x1e1b00001e1c,\n        0x1e1d00001e1e,\n        0x1e1f00001e20,\n        0x1e2100001e22,\n        0x1e2300001e24,\n        0x1e2500001e26,\n        0x1e2700001e28,\n        0x1e2900001e2a,\n        0x1e2b00001e2c,\n        0x1e2d00001e2e,\n        0x1e2f00001e30,\n        0x1e3100001e32,\n        0x1e3300001e34,\n        0x1e3500001e36,\n        0x1e3700001e38,\n        0x1e3900001e3a,\n        0x1e3b00001e3c,\n        0x1e3d00001e3e,\n        0x1e3f00001e40,\n        0x1e4100001e42,\n        0x1e4300001e44,\n        0x1e4500001e46,\n        0x1e4700001e48,\n        0x1e4900001e4a,\n        0x1e4b00001e4c,\n        0x1e4d00001e4e,\n        0x1e4f00001e50,\n        0x1e5100001e52,\n        0x1e5300001e54,\n        0x1e5500001e56,\n        0x1e5700001e58,\n        0x1e5900001e5a,\n        0x1e5b00001e5c,\n        0x1e5d00001e5e,\n        0x1e5f00001e60,\n        0x1e6100001e62,\n        0x1e6300001e64,\n        0x1e6500001e66,\n        0x1e6700001e68,\n        0x1e6900001e6a,\n        0x1e6b00001e6c,\n        0x1e6d00001e6e,\n        0x1e6f00001e70,\n        0x1e7100001e72,\n        0x1e7300001e74,\n        0x1e7500001e76,\n        0x1e7700001e78,\n        0x1e7900001e7a,\n        0x1e7b00001e7c,\n        0x1e7d00001e7e,\n        0x1e7f00001e80,\n        0x1e8100001e82,\n        0x1e8300001e84,\n        0x1e8500001e86,\n        0x1e8700001e88,\n        0x1e8900001e8a,\n        0x1e8b00001e8c,\n        0x1e8d00001e8e,\n        0x1e8f00001e90,\n        0x1e9100001e92,\n        0x1e9300001e94,\n        0x1e9500001e9a,\n        0x1e9c00001e9e,\n        0x1e9f00001ea0,\n        0x1ea100001ea2,\n        0x1ea300001ea4,\n        0x1ea500001ea6,\n        0x1ea700001ea8,\n        0x1ea900001eaa,\n        0x1eab00001eac,\n        0x1ead00001eae,\n        0x1eaf00001eb0,\n        0x1eb100001eb2,\n        0x1eb300001eb4,\n        0x1eb500001eb6,\n        0x1eb700001eb8,\n        0x1eb900001eba,\n        0x1ebb00001ebc,\n        0x1ebd00001ebe,\n        0x1ebf00001ec0,\n        0x1ec100001ec2,\n        0x1ec300001ec4,\n        0x1ec500001ec6,\n        0x1ec700001ec8,\n        0x1ec900001eca,\n        0x1ecb00001ecc,\n        0x1ecd00001ece,\n        0x1ecf00001ed0,\n        0x1ed100001ed2,\n        0x1ed300001ed4,\n        0x1ed500001ed6,\n        0x1ed700001ed8,\n        0x1ed900001eda,\n        0x1edb00001edc,\n        0x1edd00001ede,\n        0x1edf00001ee0,\n        0x1ee100001ee2,\n        0x1ee300001ee4,\n        0x1ee500001ee6,\n        0x1ee700001ee8,\n        0x1ee900001eea,\n        0x1eeb00001eec,\n        0x1eed00001eee,\n        0x1eef00001ef0,\n        0x1ef100001ef2,\n        0x1ef300001ef4,\n        0x1ef500001ef6,\n        0x1ef700001ef8,\n        0x1ef900001efa,\n        0x1efb00001efc,\n        0x1efd00001efe,\n        0x1eff00001f08,\n        0x1f1000001f16,\n        0x1f2000001f28,\n        0x1f3000001f38,\n        0x1f4000001f46,\n        0x1f5000001f58,\n        0x1f6000001f68,\n        0x1f7000001f71,\n        0x1f7200001f73,\n        0x1f7400001f75,\n        0x1f7600001f77,\n        0x1f7800001f79,\n        0x1f7a00001f7b,\n        0x1f7c00001f7d,\n        0x1fb000001fb2,\n        0x1fb600001fb7,\n        0x1fc600001fc7,\n        0x1fd000001fd3,\n        0x1fd600001fd8,\n        0x1fe000001fe3,\n        0x1fe400001fe8,\n        0x1ff600001ff7,\n        0x214e0000214f,\n        0x218400002185,\n        0x2c3000002c5f,\n        0x2c6100002c62,\n        0x2c6500002c67,\n        0x2c6800002c69,\n        0x2c6a00002c6b,\n        0x2c6c00002c6d,\n        0x2c7100002c72,\n        0x2c7300002c75,\n        0x2c7600002c7c,\n        0x2c8100002c82,\n        0x2c8300002c84,\n        0x2c8500002c86,\n        0x2c8700002c88,\n        0x2c8900002c8a,\n        0x2c8b00002c8c,\n        0x2c8d00002c8e,\n        0x2c8f00002c90,\n        0x2c9100002c92,\n        0x2c9300002c94,\n        0x2c9500002c96,\n        0x2c9700002c98,\n        0x2c9900002c9a,\n        0x2c9b00002c9c,\n        0x2c9d00002c9e,\n        0x2c9f00002ca0,\n        0x2ca100002ca2,\n        0x2ca300002ca4,\n        0x2ca500002ca6,\n        0x2ca700002ca8,\n        0x2ca900002caa,\n        0x2cab00002cac,\n        0x2cad00002cae,\n        0x2caf00002cb0,\n        0x2cb100002cb2,\n        0x2cb300002cb4,\n        0x2cb500002cb6,\n        0x2cb700002cb8,\n        0x2cb900002cba,\n        0x2cbb00002cbc,\n        0x2cbd00002cbe,\n        0x2cbf00002cc0,\n        0x2cc100002cc2,\n        0x2cc300002cc4,\n        0x2cc500002cc6,\n        0x2cc700002cc8,\n        0x2cc900002cca,\n        0x2ccb00002ccc,\n        0x2ccd00002cce,\n        0x2ccf00002cd0,\n        0x2cd100002cd2,\n        0x2cd300002cd4,\n        0x2cd500002cd6,\n        0x2cd700002cd8,\n        0x2cd900002cda,\n        0x2cdb00002cdc,\n        0x2cdd00002cde,\n        0x2cdf00002ce0,\n        0x2ce100002ce2,\n        0x2ce300002ce5,\n        0x2cec00002ced,\n        0x2cee00002cf2,\n        0x2cf300002cf4,\n        0x2d0000002d26,\n        0x2d2700002d28,\n        0x2d2d00002d2e,\n        0x2d3000002d68,\n        0x2d7f00002d97,\n        0x2da000002da7,\n        0x2da800002daf,\n        0x2db000002db7,\n        0x2db800002dbf,\n        0x2dc000002dc7,\n        0x2dc800002dcf,\n        0x2dd000002dd7,\n        0x2dd800002ddf,\n        0x2de000002e00,\n        0x2e2f00002e30,\n        0x300500003008,\n        0x302a0000302e,\n        0x303c0000303d,\n        0x304100003097,\n        0x30990000309b,\n        0x309d0000309f,\n        0x30a1000030fb,\n        0x30fc000030ff,\n        0x310500003130,\n        0x31a0000031bb,\n        0x31f000003200,\n        0x340000004db6,\n        0x4e0000009ff0,\n        0xa0000000a48d,\n        0xa4d00000a4fe,\n        0xa5000000a60d,\n        0xa6100000a62c,\n        0xa6410000a642,\n        0xa6430000a644,\n        0xa6450000a646,\n        0xa6470000a648,\n        0xa6490000a64a,\n        0xa64b0000a64c,\n        0xa64d0000a64e,\n        0xa64f0000a650,\n        0xa6510000a652,\n        0xa6530000a654,\n        0xa6550000a656,\n        0xa6570000a658,\n        0xa6590000a65a,\n        0xa65b0000a65c,\n        0xa65d0000a65e,\n        0xa65f0000a660,\n        0xa6610000a662,\n        0xa6630000a664,\n        0xa6650000a666,\n        0xa6670000a668,\n        0xa6690000a66a,\n        0xa66b0000a66c,\n        0xa66d0000a670,\n        0xa6740000a67e,\n        0xa67f0000a680,\n        0xa6810000a682,\n        0xa6830000a684,\n        0xa6850000a686,\n        0xa6870000a688,\n        0xa6890000a68a,\n        0xa68b0000a68c,\n        0xa68d0000a68e,\n        0xa68f0000a690,\n        0xa6910000a692,\n        0xa6930000a694,\n        0xa6950000a696,\n        0xa6970000a698,\n        0xa6990000a69a,\n        0xa69b0000a69c,\n        0xa69e0000a6e6,\n        0xa6f00000a6f2,\n        0xa7170000a720,\n        0xa7230000a724,\n        0xa7250000a726,\n        0xa7270000a728,\n        0xa7290000a72a,\n        0xa72b0000a72c,\n        0xa72d0000a72e,\n        0xa72f0000a732,\n        0xa7330000a734,\n        0xa7350000a736,\n        0xa7370000a738,\n        0xa7390000a73a,\n        0xa73b0000a73c,\n        0xa73d0000a73e,\n        0xa73f0000a740,\n        0xa7410000a742,\n        0xa7430000a744,\n        0xa7450000a746,\n        0xa7470000a748,\n        0xa7490000a74a,\n        0xa74b0000a74c,\n        0xa74d0000a74e,\n        0xa74f0000a750,\n        0xa7510000a752,\n        0xa7530000a754,\n        0xa7550000a756,\n        0xa7570000a758,\n        0xa7590000a75a,\n        0xa75b0000a75c,\n        0xa75d0000a75e,\n        0xa75f0000a760,\n        0xa7610000a762,\n        0xa7630000a764,\n        0xa7650000a766,\n        0xa7670000a768,\n        0xa7690000a76a,\n        0xa76b0000a76c,\n        0xa76d0000a76e,\n        0xa76f0000a770,\n        0xa7710000a779,\n        0xa77a0000a77b,\n        0xa77c0000a77d,\n        0xa77f0000a780,\n        0xa7810000a782,\n        0xa7830000a784,\n        0xa7850000a786,\n        0xa7870000a789,\n        0xa78c0000a78d,\n        0xa78e0000a790,\n        0xa7910000a792,\n        0xa7930000a796,\n        0xa7970000a798,\n        0xa7990000a79a,\n        0xa79b0000a79c,\n        0xa79d0000a79e,\n        0xa79f0000a7a0,\n        0xa7a10000a7a2,\n        0xa7a30000a7a4,\n        0xa7a50000a7a6,\n        0xa7a70000a7a8,\n        0xa7a90000a7aa,\n        0xa7af0000a7b0,\n        0xa7b50000a7b6,\n        0xa7b70000a7b8,\n        0xa7b90000a7ba,\n        0xa7f70000a7f8,\n        0xa7fa0000a828,\n        0xa8400000a874,\n        0xa8800000a8c6,\n        0xa8d00000a8da,\n        0xa8e00000a8f8,\n        0xa8fb0000a8fc,\n        0xa8fd0000a92e,\n        0xa9300000a954,\n        0xa9800000a9c1,\n        0xa9cf0000a9da,\n        0xa9e00000a9ff,\n        0xaa000000aa37,\n        0xaa400000aa4e,\n        0xaa500000aa5a,\n        0xaa600000aa77,\n        0xaa7a0000aac3,\n        0xaadb0000aade,\n        0xaae00000aaf0,\n        0xaaf20000aaf7,\n        0xab010000ab07,\n        0xab090000ab0f,\n        0xab110000ab17,\n        0xab200000ab27,\n        0xab280000ab2f,\n        0xab300000ab5b,\n        0xab600000ab66,\n        0xabc00000abeb,\n        0xabec0000abee,\n        0xabf00000abfa,\n        0xac000000d7a4,\n        0xfa0e0000fa10,\n        0xfa110000fa12,\n        0xfa130000fa15,\n        0xfa1f0000fa20,\n        0xfa210000fa22,\n        0xfa230000fa25,\n        0xfa270000fa2a,\n        0xfb1e0000fb1f,\n        0xfe200000fe30,\n        0xfe730000fe74,\n        0x100000001000c,\n        0x1000d00010027,\n        0x100280001003b,\n        0x1003c0001003e,\n        0x1003f0001004e,\n        0x100500001005e,\n        0x10080000100fb,\n        0x101fd000101fe,\n        0x102800001029d,\n        0x102a0000102d1,\n        0x102e0000102e1,\n        0x1030000010320,\n        0x1032d00010341,\n        0x103420001034a,\n        0x103500001037b,\n        0x103800001039e,\n        0x103a0000103c4,\n        0x103c8000103d0,\n        0x104280001049e,\n        0x104a0000104aa,\n        0x104d8000104fc,\n        0x1050000010528,\n        0x1053000010564,\n        0x1060000010737,\n        0x1074000010756,\n        0x1076000010768,\n        0x1080000010806,\n        0x1080800010809,\n        0x1080a00010836,\n        0x1083700010839,\n        0x1083c0001083d,\n        0x1083f00010856,\n        0x1086000010877,\n        0x108800001089f,\n        0x108e0000108f3,\n        0x108f4000108f6,\n        0x1090000010916,\n        0x109200001093a,\n        0x10980000109b8,\n        0x109be000109c0,\n        0x10a0000010a04,\n        0x10a0500010a07,\n        0x10a0c00010a14,\n        0x10a1500010a18,\n        0x10a1900010a36,\n        0x10a3800010a3b,\n        0x10a3f00010a40,\n        0x10a6000010a7d,\n        0x10a8000010a9d,\n        0x10ac000010ac8,\n        0x10ac900010ae7,\n        0x10b0000010b36,\n        0x10b4000010b56,\n        0x10b6000010b73,\n        0x10b8000010b92,\n        0x10c0000010c49,\n        0x10cc000010cf3,\n        0x10d0000010d28,\n        0x10d3000010d3a,\n        0x10f0000010f1d,\n        0x10f2700010f28,\n        0x10f3000010f51,\n        0x1100000011047,\n        0x1106600011070,\n        0x1107f000110bb,\n        0x110d0000110e9,\n        0x110f0000110fa,\n        0x1110000011135,\n        0x1113600011140,\n        0x1114400011147,\n        0x1115000011174,\n        0x1117600011177,\n        0x11180000111c5,\n        0x111c9000111cd,\n        0x111d0000111db,\n        0x111dc000111dd,\n        0x1120000011212,\n        0x1121300011238,\n        0x1123e0001123f,\n        0x1128000011287,\n        0x1128800011289,\n        0x1128a0001128e,\n        0x1128f0001129e,\n        0x1129f000112a9,\n        0x112b0000112eb,\n        0x112f0000112fa,\n        0x1130000011304,\n        0x113050001130d,\n        0x1130f00011311,\n        0x1131300011329,\n        0x1132a00011331,\n        0x1133200011334,\n        0x113350001133a,\n        0x1133b00011345,\n        0x1134700011349,\n        0x1134b0001134e,\n        0x1135000011351,\n        0x1135700011358,\n        0x1135d00011364,\n        0x113660001136d,\n        0x1137000011375,\n        0x114000001144b,\n        0x114500001145a,\n        0x1145e0001145f,\n        0x11480000114c6,\n        0x114c7000114c8,\n        0x114d0000114da,\n        0x11580000115b6,\n        0x115b8000115c1,\n        0x115d8000115de,\n        0x1160000011641,\n        0x1164400011645,\n        0x116500001165a,\n        0x11680000116b8,\n        0x116c0000116ca,\n        0x117000001171b,\n        0x1171d0001172c,\n        0x117300001173a,\n        0x118000001183b,\n        0x118c0000118ea,\n        0x118ff00011900,\n        0x11a0000011a3f,\n        0x11a4700011a48,\n        0x11a5000011a84,\n        0x11a8600011a9a,\n        0x11a9d00011a9e,\n        0x11ac000011af9,\n        0x11c0000011c09,\n        0x11c0a00011c37,\n        0x11c3800011c41,\n        0x11c5000011c5a,\n        0x11c7200011c90,\n        0x11c9200011ca8,\n        0x11ca900011cb7,\n        0x11d0000011d07,\n        0x11d0800011d0a,\n        0x11d0b00011d37,\n        0x11d3a00011d3b,\n        0x11d3c00011d3e,\n        0x11d3f00011d48,\n        0x11d5000011d5a,\n        0x11d6000011d66,\n        0x11d6700011d69,\n        0x11d6a00011d8f,\n        0x11d9000011d92,\n        0x11d9300011d99,\n        0x11da000011daa,\n        0x11ee000011ef7,\n        0x120000001239a,\n        0x1248000012544,\n        0x130000001342f,\n        0x1440000014647,\n        0x1680000016a39,\n        0x16a4000016a5f,\n        0x16a6000016a6a,\n        0x16ad000016aee,\n        0x16af000016af5,\n        0x16b0000016b37,\n        0x16b4000016b44,\n        0x16b5000016b5a,\n        0x16b6300016b78,\n        0x16b7d00016b90,\n        0x16e6000016e80,\n        0x16f0000016f45,\n        0x16f5000016f7f,\n        0x16f8f00016fa0,\n        0x16fe000016fe2,\n        0x17000000187f2,\n        0x1880000018af3,\n        0x1b0000001b11f,\n        0x1b1700001b2fc,\n        0x1bc000001bc6b,\n        0x1bc700001bc7d,\n        0x1bc800001bc89,\n        0x1bc900001bc9a,\n        0x1bc9d0001bc9f,\n        0x1da000001da37,\n        0x1da3b0001da6d,\n        0x1da750001da76,\n        0x1da840001da85,\n        0x1da9b0001daa0,\n        0x1daa10001dab0,\n        0x1e0000001e007,\n        0x1e0080001e019,\n        0x1e01b0001e022,\n        0x1e0230001e025,\n        0x1e0260001e02b,\n        0x1e8000001e8c5,\n        0x1e8d00001e8d7,\n        0x1e9220001e94b,\n        0x1e9500001e95a,\n        0x200000002a6d7,\n        0x2a7000002b735,\n        0x2b7400002b81e,\n        0x2b8200002cea2,\n        0x2ceb00002ebe1,\n    ),\n    'CONTEXTJ': (\n        0x200c0000200e,\n    ),\n    'CONTEXTO': (\n        0xb7000000b8,\n        0x37500000376,\n        0x5f3000005f5,\n        0x6600000066a,\n        0x6f0000006fa,\n        0x30fb000030fc,\n    ),\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna/intranges.py",
    "content": "\"\"\"\nGiven a list of integers, made up of (hopefully) a small number of long runs\nof consecutive integers, compute a representation of the form\n((start1, end1), (start2, end2) ...). Then answer the question \"was x present\nin the original list?\" in time O(log(# runs)).\n\"\"\"\n\nimport bisect\n\ndef intranges_from_list(list_):\n    \"\"\"Represent a list of integers as a sequence of ranges:\n    ((start_0, end_0), (start_1, end_1), ...), such that the original\n    integers are exactly those x such that start_i <= x < end_i for some i.\n\n    Ranges are encoded as single integers (start << 32 | end), not as tuples.\n    \"\"\"\n\n    sorted_list = sorted(list_)\n    ranges = []\n    last_write = -1\n    for i in range(len(sorted_list)):\n        if i+1 < len(sorted_list):\n            if sorted_list[i] == sorted_list[i+1]-1:\n                continue\n        current_range = sorted_list[last_write+1:i+1]\n        ranges.append(_encode_range(current_range[0], current_range[-1] + 1))\n        last_write = i\n\n    return tuple(ranges)\n\ndef _encode_range(start, end):\n    return (start << 32) | end\n\ndef _decode_range(r):\n    return (r >> 32), (r & ((1 << 32) - 1))\n\n\ndef intranges_contain(int_, ranges):\n    \"\"\"Determine if `int_` falls into one of the ranges in `ranges`.\"\"\"\n    tuple_ = _encode_range(int_, 0)\n    pos = bisect.bisect_left(ranges, tuple_)\n    # we could be immediately ahead of a tuple (start, end)\n    # with start < int_ <= end\n    if pos > 0:\n        left, right = _decode_range(ranges[pos-1])\n        if left <= int_ < right:\n            return True\n    # or we could be immediately behind a tuple (int_, end)\n    if pos < len(ranges):\n        left, _ = _decode_range(ranges[pos])\n        if left == int_:\n            return True\n    return False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna/package_data.py",
    "content": "__version__ = '2.8'\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna/uts46data.py",
    "content": "# This file is automatically generated by tools/idna-data\n# vim: set fileencoding=utf-8 :\n\n\"\"\"IDNA Mapping Table from UTS46.\"\"\"\n\n\n__version__ = \"11.0.0\"\ndef _seg_0():\n    return [\n    (0x0, '3'),\n    (0x1, '3'),\n    (0x2, '3'),\n    (0x3, '3'),\n    (0x4, '3'),\n    (0x5, '3'),\n    (0x6, '3'),\n    (0x7, '3'),\n    (0x8, '3'),\n    (0x9, '3'),\n    (0xA, '3'),\n    (0xB, '3'),\n    (0xC, '3'),\n    (0xD, '3'),\n    (0xE, '3'),\n    (0xF, '3'),\n    (0x10, '3'),\n    (0x11, '3'),\n    (0x12, '3'),\n    (0x13, '3'),\n    (0x14, '3'),\n    (0x15, '3'),\n    (0x16, '3'),\n    (0x17, '3'),\n    (0x18, '3'),\n    (0x19, '3'),\n    (0x1A, '3'),\n    (0x1B, '3'),\n    (0x1C, '3'),\n    (0x1D, '3'),\n    (0x1E, '3'),\n    (0x1F, '3'),\n    (0x20, '3'),\n    (0x21, '3'),\n    (0x22, '3'),\n    (0x23, '3'),\n    (0x24, '3'),\n    (0x25, '3'),\n    (0x26, '3'),\n    (0x27, '3'),\n    (0x28, '3'),\n    (0x29, '3'),\n    (0x2A, '3'),\n    (0x2B, '3'),\n    (0x2C, '3'),\n    (0x2D, 'V'),\n    (0x2E, 'V'),\n    (0x2F, '3'),\n    (0x30, 'V'),\n    (0x31, 'V'),\n    (0x32, 'V'),\n    (0x33, 'V'),\n    (0x34, 'V'),\n    (0x35, 'V'),\n    (0x36, 'V'),\n    (0x37, 'V'),\n    (0x38, 'V'),\n    (0x39, 'V'),\n    (0x3A, '3'),\n    (0x3B, '3'),\n    (0x3C, '3'),\n    (0x3D, '3'),\n    (0x3E, '3'),\n    (0x3F, '3'),\n    (0x40, '3'),\n    (0x41, 'M', u'a'),\n    (0x42, 'M', u'b'),\n    (0x43, 'M', u'c'),\n    (0x44, 'M', u'd'),\n    (0x45, 'M', u'e'),\n    (0x46, 'M', u'f'),\n    (0x47, 'M', u'g'),\n    (0x48, 'M', u'h'),\n    (0x49, 'M', u'i'),\n    (0x4A, 'M', u'j'),\n    (0x4B, 'M', u'k'),\n    (0x4C, 'M', u'l'),\n    (0x4D, 'M', u'm'),\n    (0x4E, 'M', u'n'),\n    (0x4F, 'M', u'o'),\n    (0x50, 'M', u'p'),\n    (0x51, 'M', u'q'),\n    (0x52, 'M', u'r'),\n    (0x53, 'M', u's'),\n    (0x54, 'M', u't'),\n    (0x55, 'M', u'u'),\n    (0x56, 'M', u'v'),\n    (0x57, 'M', u'w'),\n    (0x58, 'M', u'x'),\n    (0x59, 'M', u'y'),\n    (0x5A, 'M', u'z'),\n    (0x5B, '3'),\n    (0x5C, '3'),\n    (0x5D, '3'),\n    (0x5E, '3'),\n    (0x5F, '3'),\n    (0x60, '3'),\n    (0x61, 'V'),\n    (0x62, 'V'),\n    (0x63, 'V'),\n    ]\n\ndef _seg_1():\n    return [\n    (0x64, 'V'),\n    (0x65, 'V'),\n    (0x66, 'V'),\n    (0x67, 'V'),\n    (0x68, 'V'),\n    (0x69, 'V'),\n    (0x6A, 'V'),\n    (0x6B, 'V'),\n    (0x6C, 'V'),\n    (0x6D, 'V'),\n    (0x6E, 'V'),\n    (0x6F, 'V'),\n    (0x70, 'V'),\n    (0x71, 'V'),\n    (0x72, 'V'),\n    (0x73, 'V'),\n    (0x74, 'V'),\n    (0x75, 'V'),\n    (0x76, 'V'),\n    (0x77, 'V'),\n    (0x78, 'V'),\n    (0x79, 'V'),\n    (0x7A, 'V'),\n    (0x7B, '3'),\n    (0x7C, '3'),\n    (0x7D, '3'),\n    (0x7E, '3'),\n    (0x7F, '3'),\n    (0x80, 'X'),\n    (0x81, 'X'),\n    (0x82, 'X'),\n    (0x83, 'X'),\n    (0x84, 'X'),\n    (0x85, 'X'),\n    (0x86, 'X'),\n    (0x87, 'X'),\n    (0x88, 'X'),\n    (0x89, 'X'),\n    (0x8A, 'X'),\n    (0x8B, 'X'),\n    (0x8C, 'X'),\n    (0x8D, 'X'),\n    (0x8E, 'X'),\n    (0x8F, 'X'),\n    (0x90, 'X'),\n    (0x91, 'X'),\n    (0x92, 'X'),\n    (0x93, 'X'),\n    (0x94, 'X'),\n    (0x95, 'X'),\n    (0x96, 'X'),\n    (0x97, 'X'),\n    (0x98, 'X'),\n    (0x99, 'X'),\n    (0x9A, 'X'),\n    (0x9B, 'X'),\n    (0x9C, 'X'),\n    (0x9D, 'X'),\n    (0x9E, 'X'),\n    (0x9F, 'X'),\n    (0xA0, '3', u' '),\n    (0xA1, 'V'),\n    (0xA2, 'V'),\n    (0xA3, 'V'),\n    (0xA4, 'V'),\n    (0xA5, 'V'),\n    (0xA6, 'V'),\n    (0xA7, 'V'),\n    (0xA8, '3', u' ̈'),\n    (0xA9, 'V'),\n    (0xAA, 'M', u'a'),\n    (0xAB, 'V'),\n    (0xAC, 'V'),\n    (0xAD, 'I'),\n    (0xAE, 'V'),\n    (0xAF, '3', u' ̄'),\n    (0xB0, 'V'),\n    (0xB1, 'V'),\n    (0xB2, 'M', u'2'),\n    (0xB3, 'M', u'3'),\n    (0xB4, '3', u' ́'),\n    (0xB5, 'M', u'μ'),\n    (0xB6, 'V'),\n    (0xB7, 'V'),\n    (0xB8, '3', u' ̧'),\n    (0xB9, 'M', u'1'),\n    (0xBA, 'M', u'o'),\n    (0xBB, 'V'),\n    (0xBC, 'M', u'1⁄4'),\n    (0xBD, 'M', u'1⁄2'),\n    (0xBE, 'M', u'3⁄4'),\n    (0xBF, 'V'),\n    (0xC0, 'M', u'à'),\n    (0xC1, 'M', u'á'),\n    (0xC2, 'M', u'â'),\n    (0xC3, 'M', u'ã'),\n    (0xC4, 'M', u'ä'),\n    (0xC5, 'M', u'å'),\n    (0xC6, 'M', u'æ'),\n    (0xC7, 'M', u'ç'),\n    ]\n\ndef _seg_2():\n    return [\n    (0xC8, 'M', u'è'),\n    (0xC9, 'M', u'é'),\n    (0xCA, 'M', u'ê'),\n    (0xCB, 'M', u'ë'),\n    (0xCC, 'M', u'ì'),\n    (0xCD, 'M', u'í'),\n    (0xCE, 'M', u'î'),\n    (0xCF, 'M', u'ï'),\n    (0xD0, 'M', u'ð'),\n    (0xD1, 'M', u'ñ'),\n    (0xD2, 'M', u'ò'),\n    (0xD3, 'M', u'ó'),\n    (0xD4, 'M', u'ô'),\n    (0xD5, 'M', u'õ'),\n    (0xD6, 'M', u'ö'),\n    (0xD7, 'V'),\n    (0xD8, 'M', u'ø'),\n    (0xD9, 'M', u'ù'),\n    (0xDA, 'M', u'ú'),\n    (0xDB, 'M', u'û'),\n    (0xDC, 'M', u'ü'),\n    (0xDD, 'M', u'ý'),\n    (0xDE, 'M', u'þ'),\n    (0xDF, 'D', u'ss'),\n    (0xE0, 'V'),\n    (0xE1, 'V'),\n    (0xE2, 'V'),\n    (0xE3, 'V'),\n    (0xE4, 'V'),\n    (0xE5, 'V'),\n    (0xE6, 'V'),\n    (0xE7, 'V'),\n    (0xE8, 'V'),\n    (0xE9, 'V'),\n    (0xEA, 'V'),\n    (0xEB, 'V'),\n    (0xEC, 'V'),\n    (0xED, 'V'),\n    (0xEE, 'V'),\n    (0xEF, 'V'),\n    (0xF0, 'V'),\n    (0xF1, 'V'),\n    (0xF2, 'V'),\n    (0xF3, 'V'),\n    (0xF4, 'V'),\n    (0xF5, 'V'),\n    (0xF6, 'V'),\n    (0xF7, 'V'),\n    (0xF8, 'V'),\n    (0xF9, 'V'),\n    (0xFA, 'V'),\n    (0xFB, 'V'),\n    (0xFC, 'V'),\n    (0xFD, 'V'),\n    (0xFE, 'V'),\n    (0xFF, 'V'),\n    (0x100, 'M', u'ā'),\n    (0x101, 'V'),\n    (0x102, 'M', u'ă'),\n    (0x103, 'V'),\n    (0x104, 'M', u'ą'),\n    (0x105, 'V'),\n    (0x106, 'M', u'ć'),\n    (0x107, 'V'),\n    (0x108, 'M', u'ĉ'),\n    (0x109, 'V'),\n    (0x10A, 'M', u'ċ'),\n    (0x10B, 'V'),\n    (0x10C, 'M', u'č'),\n    (0x10D, 'V'),\n    (0x10E, 'M', u'ď'),\n    (0x10F, 'V'),\n    (0x110, 'M', u'đ'),\n    (0x111, 'V'),\n    (0x112, 'M', u'ē'),\n    (0x113, 'V'),\n    (0x114, 'M', u'ĕ'),\n    (0x115, 'V'),\n    (0x116, 'M', u'ė'),\n    (0x117, 'V'),\n    (0x118, 'M', u'ę'),\n    (0x119, 'V'),\n    (0x11A, 'M', u'ě'),\n    (0x11B, 'V'),\n    (0x11C, 'M', u'ĝ'),\n    (0x11D, 'V'),\n    (0x11E, 'M', u'ğ'),\n    (0x11F, 'V'),\n    (0x120, 'M', u'ġ'),\n    (0x121, 'V'),\n    (0x122, 'M', u'ģ'),\n    (0x123, 'V'),\n    (0x124, 'M', u'ĥ'),\n    (0x125, 'V'),\n    (0x126, 'M', u'ħ'),\n    (0x127, 'V'),\n    (0x128, 'M', u'ĩ'),\n    (0x129, 'V'),\n    (0x12A, 'M', u'ī'),\n    (0x12B, 'V'),\n    ]\n\ndef _seg_3():\n    return [\n    (0x12C, 'M', u'ĭ'),\n    (0x12D, 'V'),\n    (0x12E, 'M', u'į'),\n    (0x12F, 'V'),\n    (0x130, 'M', u'i̇'),\n    (0x131, 'V'),\n    (0x132, 'M', u'ij'),\n    (0x134, 'M', u'ĵ'),\n    (0x135, 'V'),\n    (0x136, 'M', u'ķ'),\n    (0x137, 'V'),\n    (0x139, 'M', u'ĺ'),\n    (0x13A, 'V'),\n    (0x13B, 'M', u'ļ'),\n    (0x13C, 'V'),\n    (0x13D, 'M', u'ľ'),\n    (0x13E, 'V'),\n    (0x13F, 'M', u'l·'),\n    (0x141, 'M', u'ł'),\n    (0x142, 'V'),\n    (0x143, 'M', u'ń'),\n    (0x144, 'V'),\n    (0x145, 'M', u'ņ'),\n    (0x146, 'V'),\n    (0x147, 'M', u'ň'),\n    (0x148, 'V'),\n    (0x149, 'M', u'ʼn'),\n    (0x14A, 'M', u'ŋ'),\n    (0x14B, 'V'),\n    (0x14C, 'M', u'ō'),\n    (0x14D, 'V'),\n    (0x14E, 'M', u'ŏ'),\n    (0x14F, 'V'),\n    (0x150, 'M', u'ő'),\n    (0x151, 'V'),\n    (0x152, 'M', u'œ'),\n    (0x153, 'V'),\n    (0x154, 'M', u'ŕ'),\n    (0x155, 'V'),\n    (0x156, 'M', u'ŗ'),\n    (0x157, 'V'),\n    (0x158, 'M', u'ř'),\n    (0x159, 'V'),\n    (0x15A, 'M', u'ś'),\n    (0x15B, 'V'),\n    (0x15C, 'M', u'ŝ'),\n    (0x15D, 'V'),\n    (0x15E, 'M', u'ş'),\n    (0x15F, 'V'),\n    (0x160, 'M', u'š'),\n    (0x161, 'V'),\n    (0x162, 'M', u'ţ'),\n    (0x163, 'V'),\n    (0x164, 'M', u'ť'),\n    (0x165, 'V'),\n    (0x166, 'M', u'ŧ'),\n    (0x167, 'V'),\n    (0x168, 'M', u'ũ'),\n    (0x169, 'V'),\n    (0x16A, 'M', u'ū'),\n    (0x16B, 'V'),\n    (0x16C, 'M', u'ŭ'),\n    (0x16D, 'V'),\n    (0x16E, 'M', u'ů'),\n    (0x16F, 'V'),\n    (0x170, 'M', u'ű'),\n    (0x171, 'V'),\n    (0x172, 'M', u'ų'),\n    (0x173, 'V'),\n    (0x174, 'M', u'ŵ'),\n    (0x175, 'V'),\n    (0x176, 'M', u'ŷ'),\n    (0x177, 'V'),\n    (0x178, 'M', u'ÿ'),\n    (0x179, 'M', u'ź'),\n    (0x17A, 'V'),\n    (0x17B, 'M', u'ż'),\n    (0x17C, 'V'),\n    (0x17D, 'M', u'ž'),\n    (0x17E, 'V'),\n    (0x17F, 'M', u's'),\n    (0x180, 'V'),\n    (0x181, 'M', u'ɓ'),\n    (0x182, 'M', u'ƃ'),\n    (0x183, 'V'),\n    (0x184, 'M', u'ƅ'),\n    (0x185, 'V'),\n    (0x186, 'M', u'ɔ'),\n    (0x187, 'M', u'ƈ'),\n    (0x188, 'V'),\n    (0x189, 'M', u'ɖ'),\n    (0x18A, 'M', u'ɗ'),\n    (0x18B, 'M', u'ƌ'),\n    (0x18C, 'V'),\n    (0x18E, 'M', u'ǝ'),\n    (0x18F, 'M', u'ə'),\n    (0x190, 'M', u'ɛ'),\n    (0x191, 'M', u'ƒ'),\n    (0x192, 'V'),\n    (0x193, 'M', u'ɠ'),\n    ]\n\ndef _seg_4():\n    return [\n    (0x194, 'M', u'ɣ'),\n    (0x195, 'V'),\n    (0x196, 'M', u'ɩ'),\n    (0x197, 'M', u'ɨ'),\n    (0x198, 'M', u'ƙ'),\n    (0x199, 'V'),\n    (0x19C, 'M', u'ɯ'),\n    (0x19D, 'M', u'ɲ'),\n    (0x19E, 'V'),\n    (0x19F, 'M', u'ɵ'),\n    (0x1A0, 'M', u'ơ'),\n    (0x1A1, 'V'),\n    (0x1A2, 'M', u'ƣ'),\n    (0x1A3, 'V'),\n    (0x1A4, 'M', u'ƥ'),\n    (0x1A5, 'V'),\n    (0x1A6, 'M', u'ʀ'),\n    (0x1A7, 'M', u'ƨ'),\n    (0x1A8, 'V'),\n    (0x1A9, 'M', u'ʃ'),\n    (0x1AA, 'V'),\n    (0x1AC, 'M', u'ƭ'),\n    (0x1AD, 'V'),\n    (0x1AE, 'M', u'ʈ'),\n    (0x1AF, 'M', u'ư'),\n    (0x1B0, 'V'),\n    (0x1B1, 'M', u'ʊ'),\n    (0x1B2, 'M', u'ʋ'),\n    (0x1B3, 'M', u'ƴ'),\n    (0x1B4, 'V'),\n    (0x1B5, 'M', u'ƶ'),\n    (0x1B6, 'V'),\n    (0x1B7, 'M', u'ʒ'),\n    (0x1B8, 'M', u'ƹ'),\n    (0x1B9, 'V'),\n    (0x1BC, 'M', u'ƽ'),\n    (0x1BD, 'V'),\n    (0x1C4, 'M', u'dž'),\n    (0x1C7, 'M', u'lj'),\n    (0x1CA, 'M', u'nj'),\n    (0x1CD, 'M', u'ǎ'),\n    (0x1CE, 'V'),\n    (0x1CF, 'M', u'ǐ'),\n    (0x1D0, 'V'),\n    (0x1D1, 'M', u'ǒ'),\n    (0x1D2, 'V'),\n    (0x1D3, 'M', u'ǔ'),\n    (0x1D4, 'V'),\n    (0x1D5, 'M', u'ǖ'),\n    (0x1D6, 'V'),\n    (0x1D7, 'M', u'ǘ'),\n    (0x1D8, 'V'),\n    (0x1D9, 'M', u'ǚ'),\n    (0x1DA, 'V'),\n    (0x1DB, 'M', u'ǜ'),\n    (0x1DC, 'V'),\n    (0x1DE, 'M', u'ǟ'),\n    (0x1DF, 'V'),\n    (0x1E0, 'M', u'ǡ'),\n    (0x1E1, 'V'),\n    (0x1E2, 'M', u'ǣ'),\n    (0x1E3, 'V'),\n    (0x1E4, 'M', u'ǥ'),\n    (0x1E5, 'V'),\n    (0x1E6, 'M', u'ǧ'),\n    (0x1E7, 'V'),\n    (0x1E8, 'M', u'ǩ'),\n    (0x1E9, 'V'),\n    (0x1EA, 'M', u'ǫ'),\n    (0x1EB, 'V'),\n    (0x1EC, 'M', u'ǭ'),\n    (0x1ED, 'V'),\n    (0x1EE, 'M', u'ǯ'),\n    (0x1EF, 'V'),\n    (0x1F1, 'M', u'dz'),\n    (0x1F4, 'M', u'ǵ'),\n    (0x1F5, 'V'),\n    (0x1F6, 'M', u'ƕ'),\n    (0x1F7, 'M', u'ƿ'),\n    (0x1F8, 'M', u'ǹ'),\n    (0x1F9, 'V'),\n    (0x1FA, 'M', u'ǻ'),\n    (0x1FB, 'V'),\n    (0x1FC, 'M', u'ǽ'),\n    (0x1FD, 'V'),\n    (0x1FE, 'M', u'ǿ'),\n    (0x1FF, 'V'),\n    (0x200, 'M', u'ȁ'),\n    (0x201, 'V'),\n    (0x202, 'M', u'ȃ'),\n    (0x203, 'V'),\n    (0x204, 'M', u'ȅ'),\n    (0x205, 'V'),\n    (0x206, 'M', u'ȇ'),\n    (0x207, 'V'),\n    (0x208, 'M', u'ȉ'),\n    (0x209, 'V'),\n    (0x20A, 'M', u'ȋ'),\n    (0x20B, 'V'),\n    (0x20C, 'M', u'ȍ'),\n    ]\n\ndef _seg_5():\n    return [\n    (0x20D, 'V'),\n    (0x20E, 'M', u'ȏ'),\n    (0x20F, 'V'),\n    (0x210, 'M', u'ȑ'),\n    (0x211, 'V'),\n    (0x212, 'M', u'ȓ'),\n    (0x213, 'V'),\n    (0x214, 'M', u'ȕ'),\n    (0x215, 'V'),\n    (0x216, 'M', u'ȗ'),\n    (0x217, 'V'),\n    (0x218, 'M', u'ș'),\n    (0x219, 'V'),\n    (0x21A, 'M', u'ț'),\n    (0x21B, 'V'),\n    (0x21C, 'M', u'ȝ'),\n    (0x21D, 'V'),\n    (0x21E, 'M', u'ȟ'),\n    (0x21F, 'V'),\n    (0x220, 'M', u'ƞ'),\n    (0x221, 'V'),\n    (0x222, 'M', u'ȣ'),\n    (0x223, 'V'),\n    (0x224, 'M', u'ȥ'),\n    (0x225, 'V'),\n    (0x226, 'M', u'ȧ'),\n    (0x227, 'V'),\n    (0x228, 'M', u'ȩ'),\n    (0x229, 'V'),\n    (0x22A, 'M', u'ȫ'),\n    (0x22B, 'V'),\n    (0x22C, 'M', u'ȭ'),\n    (0x22D, 'V'),\n    (0x22E, 'M', u'ȯ'),\n    (0x22F, 'V'),\n    (0x230, 'M', u'ȱ'),\n    (0x231, 'V'),\n    (0x232, 'M', u'ȳ'),\n    (0x233, 'V'),\n    (0x23A, 'M', u'ⱥ'),\n    (0x23B, 'M', u'ȼ'),\n    (0x23C, 'V'),\n    (0x23D, 'M', u'ƚ'),\n    (0x23E, 'M', u'ⱦ'),\n    (0x23F, 'V'),\n    (0x241, 'M', u'ɂ'),\n    (0x242, 'V'),\n    (0x243, 'M', u'ƀ'),\n    (0x244, 'M', u'ʉ'),\n    (0x245, 'M', u'ʌ'),\n    (0x246, 'M', u'ɇ'),\n    (0x247, 'V'),\n    (0x248, 'M', u'ɉ'),\n    (0x249, 'V'),\n    (0x24A, 'M', u'ɋ'),\n    (0x24B, 'V'),\n    (0x24C, 'M', u'ɍ'),\n    (0x24D, 'V'),\n    (0x24E, 'M', u'ɏ'),\n    (0x24F, 'V'),\n    (0x2B0, 'M', u'h'),\n    (0x2B1, 'M', u'ɦ'),\n    (0x2B2, 'M', u'j'),\n    (0x2B3, 'M', u'r'),\n    (0x2B4, 'M', u'ɹ'),\n    (0x2B5, 'M', u'ɻ'),\n    (0x2B6, 'M', u'ʁ'),\n    (0x2B7, 'M', u'w'),\n    (0x2B8, 'M', u'y'),\n    (0x2B9, 'V'),\n    (0x2D8, '3', u' ̆'),\n    (0x2D9, '3', u' ̇'),\n    (0x2DA, '3', u' ̊'),\n    (0x2DB, '3', u' ̨'),\n    (0x2DC, '3', u' ̃'),\n    (0x2DD, '3', u' ̋'),\n    (0x2DE, 'V'),\n    (0x2E0, 'M', u'ɣ'),\n    (0x2E1, 'M', u'l'),\n    (0x2E2, 'M', u's'),\n    (0x2E3, 'M', u'x'),\n    (0x2E4, 'M', u'ʕ'),\n    (0x2E5, 'V'),\n    (0x340, 'M', u'̀'),\n    (0x341, 'M', u'́'),\n    (0x342, 'V'),\n    (0x343, 'M', u'̓'),\n    (0x344, 'M', u'̈́'),\n    (0x345, 'M', u'ι'),\n    (0x346, 'V'),\n    (0x34F, 'I'),\n    (0x350, 'V'),\n    (0x370, 'M', u'ͱ'),\n    (0x371, 'V'),\n    (0x372, 'M', u'ͳ'),\n    (0x373, 'V'),\n    (0x374, 'M', u'ʹ'),\n    (0x375, 'V'),\n    (0x376, 'M', u'ͷ'),\n    (0x377, 'V'),\n    ]\n\ndef _seg_6():\n    return [\n    (0x378, 'X'),\n    (0x37A, '3', u' ι'),\n    (0x37B, 'V'),\n    (0x37E, '3', u';'),\n    (0x37F, 'M', u'ϳ'),\n    (0x380, 'X'),\n    (0x384, '3', u' ́'),\n    (0x385, '3', u' ̈́'),\n    (0x386, 'M', u'ά'),\n    (0x387, 'M', u'·'),\n    (0x388, 'M', u'έ'),\n    (0x389, 'M', u'ή'),\n    (0x38A, 'M', u'ί'),\n    (0x38B, 'X'),\n    (0x38C, 'M', u'ό'),\n    (0x38D, 'X'),\n    (0x38E, 'M', u'ύ'),\n    (0x38F, 'M', u'ώ'),\n    (0x390, 'V'),\n    (0x391, 'M', u'α'),\n    (0x392, 'M', u'β'),\n    (0x393, 'M', u'γ'),\n    (0x394, 'M', u'δ'),\n    (0x395, 'M', u'ε'),\n    (0x396, 'M', u'ζ'),\n    (0x397, 'M', u'η'),\n    (0x398, 'M', u'θ'),\n    (0x399, 'M', u'ι'),\n    (0x39A, 'M', u'κ'),\n    (0x39B, 'M', u'λ'),\n    (0x39C, 'M', u'μ'),\n    (0x39D, 'M', u'ν'),\n    (0x39E, 'M', u'ξ'),\n    (0x39F, 'M', u'ο'),\n    (0x3A0, 'M', u'π'),\n    (0x3A1, 'M', u'ρ'),\n    (0x3A2, 'X'),\n    (0x3A3, 'M', u'σ'),\n    (0x3A4, 'M', u'τ'),\n    (0x3A5, 'M', u'υ'),\n    (0x3A6, 'M', u'φ'),\n    (0x3A7, 'M', u'χ'),\n    (0x3A8, 'M', u'ψ'),\n    (0x3A9, 'M', u'ω'),\n    (0x3AA, 'M', u'ϊ'),\n    (0x3AB, 'M', u'ϋ'),\n    (0x3AC, 'V'),\n    (0x3C2, 'D', u'σ'),\n    (0x3C3, 'V'),\n    (0x3CF, 'M', u'ϗ'),\n    (0x3D0, 'M', u'β'),\n    (0x3D1, 'M', u'θ'),\n    (0x3D2, 'M', u'υ'),\n    (0x3D3, 'M', u'ύ'),\n    (0x3D4, 'M', u'ϋ'),\n    (0x3D5, 'M', u'φ'),\n    (0x3D6, 'M', u'π'),\n    (0x3D7, 'V'),\n    (0x3D8, 'M', u'ϙ'),\n    (0x3D9, 'V'),\n    (0x3DA, 'M', u'ϛ'),\n    (0x3DB, 'V'),\n    (0x3DC, 'M', u'ϝ'),\n    (0x3DD, 'V'),\n    (0x3DE, 'M', u'ϟ'),\n    (0x3DF, 'V'),\n    (0x3E0, 'M', u'ϡ'),\n    (0x3E1, 'V'),\n    (0x3E2, 'M', u'ϣ'),\n    (0x3E3, 'V'),\n    (0x3E4, 'M', u'ϥ'),\n    (0x3E5, 'V'),\n    (0x3E6, 'M', u'ϧ'),\n    (0x3E7, 'V'),\n    (0x3E8, 'M', u'ϩ'),\n    (0x3E9, 'V'),\n    (0x3EA, 'M', u'ϫ'),\n    (0x3EB, 'V'),\n    (0x3EC, 'M', u'ϭ'),\n    (0x3ED, 'V'),\n    (0x3EE, 'M', u'ϯ'),\n    (0x3EF, 'V'),\n    (0x3F0, 'M', u'κ'),\n    (0x3F1, 'M', u'ρ'),\n    (0x3F2, 'M', u'σ'),\n    (0x3F3, 'V'),\n    (0x3F4, 'M', u'θ'),\n    (0x3F5, 'M', u'ε'),\n    (0x3F6, 'V'),\n    (0x3F7, 'M', u'ϸ'),\n    (0x3F8, 'V'),\n    (0x3F9, 'M', u'σ'),\n    (0x3FA, 'M', u'ϻ'),\n    (0x3FB, 'V'),\n    (0x3FD, 'M', u'ͻ'),\n    (0x3FE, 'M', u'ͼ'),\n    (0x3FF, 'M', u'ͽ'),\n    (0x400, 'M', u'ѐ'),\n    (0x401, 'M', u'ё'),\n    (0x402, 'M', u'ђ'),\n    ]\n\ndef _seg_7():\n    return [\n    (0x403, 'M', u'ѓ'),\n    (0x404, 'M', u'є'),\n    (0x405, 'M', u'ѕ'),\n    (0x406, 'M', u'і'),\n    (0x407, 'M', u'ї'),\n    (0x408, 'M', u'ј'),\n    (0x409, 'M', u'љ'),\n    (0x40A, 'M', u'њ'),\n    (0x40B, 'M', u'ћ'),\n    (0x40C, 'M', u'ќ'),\n    (0x40D, 'M', u'ѝ'),\n    (0x40E, 'M', u'ў'),\n    (0x40F, 'M', u'џ'),\n    (0x410, 'M', u'а'),\n    (0x411, 'M', u'б'),\n    (0x412, 'M', u'в'),\n    (0x413, 'M', u'г'),\n    (0x414, 'M', u'д'),\n    (0x415, 'M', u'е'),\n    (0x416, 'M', u'ж'),\n    (0x417, 'M', u'з'),\n    (0x418, 'M', u'и'),\n    (0x419, 'M', u'й'),\n    (0x41A, 'M', u'к'),\n    (0x41B, 'M', u'л'),\n    (0x41C, 'M', u'м'),\n    (0x41D, 'M', u'н'),\n    (0x41E, 'M', u'о'),\n    (0x41F, 'M', u'п'),\n    (0x420, 'M', u'р'),\n    (0x421, 'M', u'с'),\n    (0x422, 'M', u'т'),\n    (0x423, 'M', u'у'),\n    (0x424, 'M', u'ф'),\n    (0x425, 'M', u'х'),\n    (0x426, 'M', u'ц'),\n    (0x427, 'M', u'ч'),\n    (0x428, 'M', u'ш'),\n    (0x429, 'M', u'щ'),\n    (0x42A, 'M', u'ъ'),\n    (0x42B, 'M', u'ы'),\n    (0x42C, 'M', u'ь'),\n    (0x42D, 'M', u'э'),\n    (0x42E, 'M', u'ю'),\n    (0x42F, 'M', u'я'),\n    (0x430, 'V'),\n    (0x460, 'M', u'ѡ'),\n    (0x461, 'V'),\n    (0x462, 'M', u'ѣ'),\n    (0x463, 'V'),\n    (0x464, 'M', u'ѥ'),\n    (0x465, 'V'),\n    (0x466, 'M', u'ѧ'),\n    (0x467, 'V'),\n    (0x468, 'M', u'ѩ'),\n    (0x469, 'V'),\n    (0x46A, 'M', u'ѫ'),\n    (0x46B, 'V'),\n    (0x46C, 'M', u'ѭ'),\n    (0x46D, 'V'),\n    (0x46E, 'M', u'ѯ'),\n    (0x46F, 'V'),\n    (0x470, 'M', u'ѱ'),\n    (0x471, 'V'),\n    (0x472, 'M', u'ѳ'),\n    (0x473, 'V'),\n    (0x474, 'M', u'ѵ'),\n    (0x475, 'V'),\n    (0x476, 'M', u'ѷ'),\n    (0x477, 'V'),\n    (0x478, 'M', u'ѹ'),\n    (0x479, 'V'),\n    (0x47A, 'M', u'ѻ'),\n    (0x47B, 'V'),\n    (0x47C, 'M', u'ѽ'),\n    (0x47D, 'V'),\n    (0x47E, 'M', u'ѿ'),\n    (0x47F, 'V'),\n    (0x480, 'M', u'ҁ'),\n    (0x481, 'V'),\n    (0x48A, 'M', u'ҋ'),\n    (0x48B, 'V'),\n    (0x48C, 'M', u'ҍ'),\n    (0x48D, 'V'),\n    (0x48E, 'M', u'ҏ'),\n    (0x48F, 'V'),\n    (0x490, 'M', u'ґ'),\n    (0x491, 'V'),\n    (0x492, 'M', u'ғ'),\n    (0x493, 'V'),\n    (0x494, 'M', u'ҕ'),\n    (0x495, 'V'),\n    (0x496, 'M', u'җ'),\n    (0x497, 'V'),\n    (0x498, 'M', u'ҙ'),\n    (0x499, 'V'),\n    (0x49A, 'M', u'қ'),\n    (0x49B, 'V'),\n    (0x49C, 'M', u'ҝ'),\n    (0x49D, 'V'),\n    ]\n\ndef _seg_8():\n    return [\n    (0x49E, 'M', u'ҟ'),\n    (0x49F, 'V'),\n    (0x4A0, 'M', u'ҡ'),\n    (0x4A1, 'V'),\n    (0x4A2, 'M', u'ң'),\n    (0x4A3, 'V'),\n    (0x4A4, 'M', u'ҥ'),\n    (0x4A5, 'V'),\n    (0x4A6, 'M', u'ҧ'),\n    (0x4A7, 'V'),\n    (0x4A8, 'M', u'ҩ'),\n    (0x4A9, 'V'),\n    (0x4AA, 'M', u'ҫ'),\n    (0x4AB, 'V'),\n    (0x4AC, 'M', u'ҭ'),\n    (0x4AD, 'V'),\n    (0x4AE, 'M', u'ү'),\n    (0x4AF, 'V'),\n    (0x4B0, 'M', u'ұ'),\n    (0x4B1, 'V'),\n    (0x4B2, 'M', u'ҳ'),\n    (0x4B3, 'V'),\n    (0x4B4, 'M', u'ҵ'),\n    (0x4B5, 'V'),\n    (0x4B6, 'M', u'ҷ'),\n    (0x4B7, 'V'),\n    (0x4B8, 'M', u'ҹ'),\n    (0x4B9, 'V'),\n    (0x4BA, 'M', u'һ'),\n    (0x4BB, 'V'),\n    (0x4BC, 'M', u'ҽ'),\n    (0x4BD, 'V'),\n    (0x4BE, 'M', u'ҿ'),\n    (0x4BF, 'V'),\n    (0x4C0, 'X'),\n    (0x4C1, 'M', u'ӂ'),\n    (0x4C2, 'V'),\n    (0x4C3, 'M', u'ӄ'),\n    (0x4C4, 'V'),\n    (0x4C5, 'M', u'ӆ'),\n    (0x4C6, 'V'),\n    (0x4C7, 'M', u'ӈ'),\n    (0x4C8, 'V'),\n    (0x4C9, 'M', u'ӊ'),\n    (0x4CA, 'V'),\n    (0x4CB, 'M', u'ӌ'),\n    (0x4CC, 'V'),\n    (0x4CD, 'M', u'ӎ'),\n    (0x4CE, 'V'),\n    (0x4D0, 'M', u'ӑ'),\n    (0x4D1, 'V'),\n    (0x4D2, 'M', u'ӓ'),\n    (0x4D3, 'V'),\n    (0x4D4, 'M', u'ӕ'),\n    (0x4D5, 'V'),\n    (0x4D6, 'M', u'ӗ'),\n    (0x4D7, 'V'),\n    (0x4D8, 'M', u'ә'),\n    (0x4D9, 'V'),\n    (0x4DA, 'M', u'ӛ'),\n    (0x4DB, 'V'),\n    (0x4DC, 'M', u'ӝ'),\n    (0x4DD, 'V'),\n    (0x4DE, 'M', u'ӟ'),\n    (0x4DF, 'V'),\n    (0x4E0, 'M', u'ӡ'),\n    (0x4E1, 'V'),\n    (0x4E2, 'M', u'ӣ'),\n    (0x4E3, 'V'),\n    (0x4E4, 'M', u'ӥ'),\n    (0x4E5, 'V'),\n    (0x4E6, 'M', u'ӧ'),\n    (0x4E7, 'V'),\n    (0x4E8, 'M', u'ө'),\n    (0x4E9, 'V'),\n    (0x4EA, 'M', u'ӫ'),\n    (0x4EB, 'V'),\n    (0x4EC, 'M', u'ӭ'),\n    (0x4ED, 'V'),\n    (0x4EE, 'M', u'ӯ'),\n    (0x4EF, 'V'),\n    (0x4F0, 'M', u'ӱ'),\n    (0x4F1, 'V'),\n    (0x4F2, 'M', u'ӳ'),\n    (0x4F3, 'V'),\n    (0x4F4, 'M', u'ӵ'),\n    (0x4F5, 'V'),\n    (0x4F6, 'M', u'ӷ'),\n    (0x4F7, 'V'),\n    (0x4F8, 'M', u'ӹ'),\n    (0x4F9, 'V'),\n    (0x4FA, 'M', u'ӻ'),\n    (0x4FB, 'V'),\n    (0x4FC, 'M', u'ӽ'),\n    (0x4FD, 'V'),\n    (0x4FE, 'M', u'ӿ'),\n    (0x4FF, 'V'),\n    (0x500, 'M', u'ԁ'),\n    (0x501, 'V'),\n    (0x502, 'M', u'ԃ'),\n    ]\n\ndef _seg_9():\n    return [\n    (0x503, 'V'),\n    (0x504, 'M', u'ԅ'),\n    (0x505, 'V'),\n    (0x506, 'M', u'ԇ'),\n    (0x507, 'V'),\n    (0x508, 'M', u'ԉ'),\n    (0x509, 'V'),\n    (0x50A, 'M', u'ԋ'),\n    (0x50B, 'V'),\n    (0x50C, 'M', u'ԍ'),\n    (0x50D, 'V'),\n    (0x50E, 'M', u'ԏ'),\n    (0x50F, 'V'),\n    (0x510, 'M', u'ԑ'),\n    (0x511, 'V'),\n    (0x512, 'M', u'ԓ'),\n    (0x513, 'V'),\n    (0x514, 'M', u'ԕ'),\n    (0x515, 'V'),\n    (0x516, 'M', u'ԗ'),\n    (0x517, 'V'),\n    (0x518, 'M', u'ԙ'),\n    (0x519, 'V'),\n    (0x51A, 'M', u'ԛ'),\n    (0x51B, 'V'),\n    (0x51C, 'M', u'ԝ'),\n    (0x51D, 'V'),\n    (0x51E, 'M', u'ԟ'),\n    (0x51F, 'V'),\n    (0x520, 'M', u'ԡ'),\n    (0x521, 'V'),\n    (0x522, 'M', u'ԣ'),\n    (0x523, 'V'),\n    (0x524, 'M', u'ԥ'),\n    (0x525, 'V'),\n    (0x526, 'M', u'ԧ'),\n    (0x527, 'V'),\n    (0x528, 'M', u'ԩ'),\n    (0x529, 'V'),\n    (0x52A, 'M', u'ԫ'),\n    (0x52B, 'V'),\n    (0x52C, 'M', u'ԭ'),\n    (0x52D, 'V'),\n    (0x52E, 'M', u'ԯ'),\n    (0x52F, 'V'),\n    (0x530, 'X'),\n    (0x531, 'M', u'ա'),\n    (0x532, 'M', u'բ'),\n    (0x533, 'M', u'գ'),\n    (0x534, 'M', u'դ'),\n    (0x535, 'M', u'ե'),\n    (0x536, 'M', u'զ'),\n    (0x537, 'M', u'է'),\n    (0x538, 'M', u'ը'),\n    (0x539, 'M', u'թ'),\n    (0x53A, 'M', u'ժ'),\n    (0x53B, 'M', u'ի'),\n    (0x53C, 'M', u'լ'),\n    (0x53D, 'M', u'խ'),\n    (0x53E, 'M', u'ծ'),\n    (0x53F, 'M', u'կ'),\n    (0x540, 'M', u'հ'),\n    (0x541, 'M', u'ձ'),\n    (0x542, 'M', u'ղ'),\n    (0x543, 'M', u'ճ'),\n    (0x544, 'M', u'մ'),\n    (0x545, 'M', u'յ'),\n    (0x546, 'M', u'ն'),\n    (0x547, 'M', u'շ'),\n    (0x548, 'M', u'ո'),\n    (0x549, 'M', u'չ'),\n    (0x54A, 'M', u'պ'),\n    (0x54B, 'M', u'ջ'),\n    (0x54C, 'M', u'ռ'),\n    (0x54D, 'M', u'ս'),\n    (0x54E, 'M', u'վ'),\n    (0x54F, 'M', u'տ'),\n    (0x550, 'M', u'ր'),\n    (0x551, 'M', u'ց'),\n    (0x552, 'M', u'ւ'),\n    (0x553, 'M', u'փ'),\n    (0x554, 'M', u'ք'),\n    (0x555, 'M', u'օ'),\n    (0x556, 'M', u'ֆ'),\n    (0x557, 'X'),\n    (0x559, 'V'),\n    (0x587, 'M', u'եւ'),\n    (0x588, 'V'),\n    (0x58B, 'X'),\n    (0x58D, 'V'),\n    (0x590, 'X'),\n    (0x591, 'V'),\n    (0x5C8, 'X'),\n    (0x5D0, 'V'),\n    (0x5EB, 'X'),\n    (0x5EF, 'V'),\n    (0x5F5, 'X'),\n    (0x606, 'V'),\n    (0x61C, 'X'),\n    (0x61E, 'V'),\n    ]\n\ndef _seg_10():\n    return [\n    (0x675, 'M', u'اٴ'),\n    (0x676, 'M', u'وٴ'),\n    (0x677, 'M', u'ۇٴ'),\n    (0x678, 'M', u'يٴ'),\n    (0x679, 'V'),\n    (0x6DD, 'X'),\n    (0x6DE, 'V'),\n    (0x70E, 'X'),\n    (0x710, 'V'),\n    (0x74B, 'X'),\n    (0x74D, 'V'),\n    (0x7B2, 'X'),\n    (0x7C0, 'V'),\n    (0x7FB, 'X'),\n    (0x7FD, 'V'),\n    (0x82E, 'X'),\n    (0x830, 'V'),\n    (0x83F, 'X'),\n    (0x840, 'V'),\n    (0x85C, 'X'),\n    (0x85E, 'V'),\n    (0x85F, 'X'),\n    (0x860, 'V'),\n    (0x86B, 'X'),\n    (0x8A0, 'V'),\n    (0x8B5, 'X'),\n    (0x8B6, 'V'),\n    (0x8BE, 'X'),\n    (0x8D3, 'V'),\n    (0x8E2, 'X'),\n    (0x8E3, 'V'),\n    (0x958, 'M', u'क़'),\n    (0x959, 'M', u'ख़'),\n    (0x95A, 'M', u'ग़'),\n    (0x95B, 'M', u'ज़'),\n    (0x95C, 'M', u'ड़'),\n    (0x95D, 'M', u'ढ़'),\n    (0x95E, 'M', u'फ़'),\n    (0x95F, 'M', u'य़'),\n    (0x960, 'V'),\n    (0x984, 'X'),\n    (0x985, 'V'),\n    (0x98D, 'X'),\n    (0x98F, 'V'),\n    (0x991, 'X'),\n    (0x993, 'V'),\n    (0x9A9, 'X'),\n    (0x9AA, 'V'),\n    (0x9B1, 'X'),\n    (0x9B2, 'V'),\n    (0x9B3, 'X'),\n    (0x9B6, 'V'),\n    (0x9BA, 'X'),\n    (0x9BC, 'V'),\n    (0x9C5, 'X'),\n    (0x9C7, 'V'),\n    (0x9C9, 'X'),\n    (0x9CB, 'V'),\n    (0x9CF, 'X'),\n    (0x9D7, 'V'),\n    (0x9D8, 'X'),\n    (0x9DC, 'M', u'ড়'),\n    (0x9DD, 'M', u'ঢ়'),\n    (0x9DE, 'X'),\n    (0x9DF, 'M', u'য়'),\n    (0x9E0, 'V'),\n    (0x9E4, 'X'),\n    (0x9E6, 'V'),\n    (0x9FF, 'X'),\n    (0xA01, 'V'),\n    (0xA04, 'X'),\n    (0xA05, 'V'),\n    (0xA0B, 'X'),\n    (0xA0F, 'V'),\n    (0xA11, 'X'),\n    (0xA13, 'V'),\n    (0xA29, 'X'),\n    (0xA2A, 'V'),\n    (0xA31, 'X'),\n    (0xA32, 'V'),\n    (0xA33, 'M', u'ਲ਼'),\n    (0xA34, 'X'),\n    (0xA35, 'V'),\n    (0xA36, 'M', u'ਸ਼'),\n    (0xA37, 'X'),\n    (0xA38, 'V'),\n    (0xA3A, 'X'),\n    (0xA3C, 'V'),\n    (0xA3D, 'X'),\n    (0xA3E, 'V'),\n    (0xA43, 'X'),\n    (0xA47, 'V'),\n    (0xA49, 'X'),\n    (0xA4B, 'V'),\n    (0xA4E, 'X'),\n    (0xA51, 'V'),\n    (0xA52, 'X'),\n    (0xA59, 'M', u'ਖ਼'),\n    (0xA5A, 'M', u'ਗ਼'),\n    (0xA5B, 'M', u'ਜ਼'),\n    ]\n\ndef _seg_11():\n    return [\n    (0xA5C, 'V'),\n    (0xA5D, 'X'),\n    (0xA5E, 'M', u'ਫ਼'),\n    (0xA5F, 'X'),\n    (0xA66, 'V'),\n    (0xA77, 'X'),\n    (0xA81, 'V'),\n    (0xA84, 'X'),\n    (0xA85, 'V'),\n    (0xA8E, 'X'),\n    (0xA8F, 'V'),\n    (0xA92, 'X'),\n    (0xA93, 'V'),\n    (0xAA9, 'X'),\n    (0xAAA, 'V'),\n    (0xAB1, 'X'),\n    (0xAB2, 'V'),\n    (0xAB4, 'X'),\n    (0xAB5, 'V'),\n    (0xABA, 'X'),\n    (0xABC, 'V'),\n    (0xAC6, 'X'),\n    (0xAC7, 'V'),\n    (0xACA, 'X'),\n    (0xACB, 'V'),\n    (0xACE, 'X'),\n    (0xAD0, 'V'),\n    (0xAD1, 'X'),\n    (0xAE0, 'V'),\n    (0xAE4, 'X'),\n    (0xAE6, 'V'),\n    (0xAF2, 'X'),\n    (0xAF9, 'V'),\n    (0xB00, 'X'),\n    (0xB01, 'V'),\n    (0xB04, 'X'),\n    (0xB05, 'V'),\n    (0xB0D, 'X'),\n    (0xB0F, 'V'),\n    (0xB11, 'X'),\n    (0xB13, 'V'),\n    (0xB29, 'X'),\n    (0xB2A, 'V'),\n    (0xB31, 'X'),\n    (0xB32, 'V'),\n    (0xB34, 'X'),\n    (0xB35, 'V'),\n    (0xB3A, 'X'),\n    (0xB3C, 'V'),\n    (0xB45, 'X'),\n    (0xB47, 'V'),\n    (0xB49, 'X'),\n    (0xB4B, 'V'),\n    (0xB4E, 'X'),\n    (0xB56, 'V'),\n    (0xB58, 'X'),\n    (0xB5C, 'M', u'ଡ଼'),\n    (0xB5D, 'M', u'ଢ଼'),\n    (0xB5E, 'X'),\n    (0xB5F, 'V'),\n    (0xB64, 'X'),\n    (0xB66, 'V'),\n    (0xB78, 'X'),\n    (0xB82, 'V'),\n    (0xB84, 'X'),\n    (0xB85, 'V'),\n    (0xB8B, 'X'),\n    (0xB8E, 'V'),\n    (0xB91, 'X'),\n    (0xB92, 'V'),\n    (0xB96, 'X'),\n    (0xB99, 'V'),\n    (0xB9B, 'X'),\n    (0xB9C, 'V'),\n    (0xB9D, 'X'),\n    (0xB9E, 'V'),\n    (0xBA0, 'X'),\n    (0xBA3, 'V'),\n    (0xBA5, 'X'),\n    (0xBA8, 'V'),\n    (0xBAB, 'X'),\n    (0xBAE, 'V'),\n    (0xBBA, 'X'),\n    (0xBBE, 'V'),\n    (0xBC3, 'X'),\n    (0xBC6, 'V'),\n    (0xBC9, 'X'),\n    (0xBCA, 'V'),\n    (0xBCE, 'X'),\n    (0xBD0, 'V'),\n    (0xBD1, 'X'),\n    (0xBD7, 'V'),\n    (0xBD8, 'X'),\n    (0xBE6, 'V'),\n    (0xBFB, 'X'),\n    (0xC00, 'V'),\n    (0xC0D, 'X'),\n    (0xC0E, 'V'),\n    (0xC11, 'X'),\n    (0xC12, 'V'),\n    ]\n\ndef _seg_12():\n    return [\n    (0xC29, 'X'),\n    (0xC2A, 'V'),\n    (0xC3A, 'X'),\n    (0xC3D, 'V'),\n    (0xC45, 'X'),\n    (0xC46, 'V'),\n    (0xC49, 'X'),\n    (0xC4A, 'V'),\n    (0xC4E, 'X'),\n    (0xC55, 'V'),\n    (0xC57, 'X'),\n    (0xC58, 'V'),\n    (0xC5B, 'X'),\n    (0xC60, 'V'),\n    (0xC64, 'X'),\n    (0xC66, 'V'),\n    (0xC70, 'X'),\n    (0xC78, 'V'),\n    (0xC8D, 'X'),\n    (0xC8E, 'V'),\n    (0xC91, 'X'),\n    (0xC92, 'V'),\n    (0xCA9, 'X'),\n    (0xCAA, 'V'),\n    (0xCB4, 'X'),\n    (0xCB5, 'V'),\n    (0xCBA, 'X'),\n    (0xCBC, 'V'),\n    (0xCC5, 'X'),\n    (0xCC6, 'V'),\n    (0xCC9, 'X'),\n    (0xCCA, 'V'),\n    (0xCCE, 'X'),\n    (0xCD5, 'V'),\n    (0xCD7, 'X'),\n    (0xCDE, 'V'),\n    (0xCDF, 'X'),\n    (0xCE0, 'V'),\n    (0xCE4, 'X'),\n    (0xCE6, 'V'),\n    (0xCF0, 'X'),\n    (0xCF1, 'V'),\n    (0xCF3, 'X'),\n    (0xD00, 'V'),\n    (0xD04, 'X'),\n    (0xD05, 'V'),\n    (0xD0D, 'X'),\n    (0xD0E, 'V'),\n    (0xD11, 'X'),\n    (0xD12, 'V'),\n    (0xD45, 'X'),\n    (0xD46, 'V'),\n    (0xD49, 'X'),\n    (0xD4A, 'V'),\n    (0xD50, 'X'),\n    (0xD54, 'V'),\n    (0xD64, 'X'),\n    (0xD66, 'V'),\n    (0xD80, 'X'),\n    (0xD82, 'V'),\n    (0xD84, 'X'),\n    (0xD85, 'V'),\n    (0xD97, 'X'),\n    (0xD9A, 'V'),\n    (0xDB2, 'X'),\n    (0xDB3, 'V'),\n    (0xDBC, 'X'),\n    (0xDBD, 'V'),\n    (0xDBE, 'X'),\n    (0xDC0, 'V'),\n    (0xDC7, 'X'),\n    (0xDCA, 'V'),\n    (0xDCB, 'X'),\n    (0xDCF, 'V'),\n    (0xDD5, 'X'),\n    (0xDD6, 'V'),\n    (0xDD7, 'X'),\n    (0xDD8, 'V'),\n    (0xDE0, 'X'),\n    (0xDE6, 'V'),\n    (0xDF0, 'X'),\n    (0xDF2, 'V'),\n    (0xDF5, 'X'),\n    (0xE01, 'V'),\n    (0xE33, 'M', u'ํา'),\n    (0xE34, 'V'),\n    (0xE3B, 'X'),\n    (0xE3F, 'V'),\n    (0xE5C, 'X'),\n    (0xE81, 'V'),\n    (0xE83, 'X'),\n    (0xE84, 'V'),\n    (0xE85, 'X'),\n    (0xE87, 'V'),\n    (0xE89, 'X'),\n    (0xE8A, 'V'),\n    (0xE8B, 'X'),\n    (0xE8D, 'V'),\n    (0xE8E, 'X'),\n    (0xE94, 'V'),\n    ]\n\ndef _seg_13():\n    return [\n    (0xE98, 'X'),\n    (0xE99, 'V'),\n    (0xEA0, 'X'),\n    (0xEA1, 'V'),\n    (0xEA4, 'X'),\n    (0xEA5, 'V'),\n    (0xEA6, 'X'),\n    (0xEA7, 'V'),\n    (0xEA8, 'X'),\n    (0xEAA, 'V'),\n    (0xEAC, 'X'),\n    (0xEAD, 'V'),\n    (0xEB3, 'M', u'ໍາ'),\n    (0xEB4, 'V'),\n    (0xEBA, 'X'),\n    (0xEBB, 'V'),\n    (0xEBE, 'X'),\n    (0xEC0, 'V'),\n    (0xEC5, 'X'),\n    (0xEC6, 'V'),\n    (0xEC7, 'X'),\n    (0xEC8, 'V'),\n    (0xECE, 'X'),\n    (0xED0, 'V'),\n    (0xEDA, 'X'),\n    (0xEDC, 'M', u'ຫນ'),\n    (0xEDD, 'M', u'ຫມ'),\n    (0xEDE, 'V'),\n    (0xEE0, 'X'),\n    (0xF00, 'V'),\n    (0xF0C, 'M', u'་'),\n    (0xF0D, 'V'),\n    (0xF43, 'M', u'གྷ'),\n    (0xF44, 'V'),\n    (0xF48, 'X'),\n    (0xF49, 'V'),\n    (0xF4D, 'M', u'ཌྷ'),\n    (0xF4E, 'V'),\n    (0xF52, 'M', u'དྷ'),\n    (0xF53, 'V'),\n    (0xF57, 'M', u'བྷ'),\n    (0xF58, 'V'),\n    (0xF5C, 'M', u'ཛྷ'),\n    (0xF5D, 'V'),\n    (0xF69, 'M', u'ཀྵ'),\n    (0xF6A, 'V'),\n    (0xF6D, 'X'),\n    (0xF71, 'V'),\n    (0xF73, 'M', u'ཱི'),\n    (0xF74, 'V'),\n    (0xF75, 'M', u'ཱུ'),\n    (0xF76, 'M', u'ྲྀ'),\n    (0xF77, 'M', u'ྲཱྀ'),\n    (0xF78, 'M', u'ླྀ'),\n    (0xF79, 'M', u'ླཱྀ'),\n    (0xF7A, 'V'),\n    (0xF81, 'M', u'ཱྀ'),\n    (0xF82, 'V'),\n    (0xF93, 'M', u'ྒྷ'),\n    (0xF94, 'V'),\n    (0xF98, 'X'),\n    (0xF99, 'V'),\n    (0xF9D, 'M', u'ྜྷ'),\n    (0xF9E, 'V'),\n    (0xFA2, 'M', u'ྡྷ'),\n    (0xFA3, 'V'),\n    (0xFA7, 'M', u'ྦྷ'),\n    (0xFA8, 'V'),\n    (0xFAC, 'M', u'ྫྷ'),\n    (0xFAD, 'V'),\n    (0xFB9, 'M', u'ྐྵ'),\n    (0xFBA, 'V'),\n    (0xFBD, 'X'),\n    (0xFBE, 'V'),\n    (0xFCD, 'X'),\n    (0xFCE, 'V'),\n    (0xFDB, 'X'),\n    (0x1000, 'V'),\n    (0x10A0, 'X'),\n    (0x10C7, 'M', u'ⴧ'),\n    (0x10C8, 'X'),\n    (0x10CD, 'M', u'ⴭ'),\n    (0x10CE, 'X'),\n    (0x10D0, 'V'),\n    (0x10FC, 'M', u'ნ'),\n    (0x10FD, 'V'),\n    (0x115F, 'X'),\n    (0x1161, 'V'),\n    (0x1249, 'X'),\n    (0x124A, 'V'),\n    (0x124E, 'X'),\n    (0x1250, 'V'),\n    (0x1257, 'X'),\n    (0x1258, 'V'),\n    (0x1259, 'X'),\n    (0x125A, 'V'),\n    (0x125E, 'X'),\n    (0x1260, 'V'),\n    (0x1289, 'X'),\n    (0x128A, 'V'),\n    ]\n\ndef _seg_14():\n    return [\n    (0x128E, 'X'),\n    (0x1290, 'V'),\n    (0x12B1, 'X'),\n    (0x12B2, 'V'),\n    (0x12B6, 'X'),\n    (0x12B8, 'V'),\n    (0x12BF, 'X'),\n    (0x12C0, 'V'),\n    (0x12C1, 'X'),\n    (0x12C2, 'V'),\n    (0x12C6, 'X'),\n    (0x12C8, 'V'),\n    (0x12D7, 'X'),\n    (0x12D8, 'V'),\n    (0x1311, 'X'),\n    (0x1312, 'V'),\n    (0x1316, 'X'),\n    (0x1318, 'V'),\n    (0x135B, 'X'),\n    (0x135D, 'V'),\n    (0x137D, 'X'),\n    (0x1380, 'V'),\n    (0x139A, 'X'),\n    (0x13A0, 'V'),\n    (0x13F6, 'X'),\n    (0x13F8, 'M', u'Ᏸ'),\n    (0x13F9, 'M', u'Ᏹ'),\n    (0x13FA, 'M', u'Ᏺ'),\n    (0x13FB, 'M', u'Ᏻ'),\n    (0x13FC, 'M', u'Ᏼ'),\n    (0x13FD, 'M', u'Ᏽ'),\n    (0x13FE, 'X'),\n    (0x1400, 'V'),\n    (0x1680, 'X'),\n    (0x1681, 'V'),\n    (0x169D, 'X'),\n    (0x16A0, 'V'),\n    (0x16F9, 'X'),\n    (0x1700, 'V'),\n    (0x170D, 'X'),\n    (0x170E, 'V'),\n    (0x1715, 'X'),\n    (0x1720, 'V'),\n    (0x1737, 'X'),\n    (0x1740, 'V'),\n    (0x1754, 'X'),\n    (0x1760, 'V'),\n    (0x176D, 'X'),\n    (0x176E, 'V'),\n    (0x1771, 'X'),\n    (0x1772, 'V'),\n    (0x1774, 'X'),\n    (0x1780, 'V'),\n    (0x17B4, 'X'),\n    (0x17B6, 'V'),\n    (0x17DE, 'X'),\n    (0x17E0, 'V'),\n    (0x17EA, 'X'),\n    (0x17F0, 'V'),\n    (0x17FA, 'X'),\n    (0x1800, 'V'),\n    (0x1806, 'X'),\n    (0x1807, 'V'),\n    (0x180B, 'I'),\n    (0x180E, 'X'),\n    (0x1810, 'V'),\n    (0x181A, 'X'),\n    (0x1820, 'V'),\n    (0x1879, 'X'),\n    (0x1880, 'V'),\n    (0x18AB, 'X'),\n    (0x18B0, 'V'),\n    (0x18F6, 'X'),\n    (0x1900, 'V'),\n    (0x191F, 'X'),\n    (0x1920, 'V'),\n    (0x192C, 'X'),\n    (0x1930, 'V'),\n    (0x193C, 'X'),\n    (0x1940, 'V'),\n    (0x1941, 'X'),\n    (0x1944, 'V'),\n    (0x196E, 'X'),\n    (0x1970, 'V'),\n    (0x1975, 'X'),\n    (0x1980, 'V'),\n    (0x19AC, 'X'),\n    (0x19B0, 'V'),\n    (0x19CA, 'X'),\n    (0x19D0, 'V'),\n    (0x19DB, 'X'),\n    (0x19DE, 'V'),\n    (0x1A1C, 'X'),\n    (0x1A1E, 'V'),\n    (0x1A5F, 'X'),\n    (0x1A60, 'V'),\n    (0x1A7D, 'X'),\n    (0x1A7F, 'V'),\n    (0x1A8A, 'X'),\n    (0x1A90, 'V'),\n    ]\n\ndef _seg_15():\n    return [\n    (0x1A9A, 'X'),\n    (0x1AA0, 'V'),\n    (0x1AAE, 'X'),\n    (0x1AB0, 'V'),\n    (0x1ABF, 'X'),\n    (0x1B00, 'V'),\n    (0x1B4C, 'X'),\n    (0x1B50, 'V'),\n    (0x1B7D, 'X'),\n    (0x1B80, 'V'),\n    (0x1BF4, 'X'),\n    (0x1BFC, 'V'),\n    (0x1C38, 'X'),\n    (0x1C3B, 'V'),\n    (0x1C4A, 'X'),\n    (0x1C4D, 'V'),\n    (0x1C80, 'M', u'в'),\n    (0x1C81, 'M', u'д'),\n    (0x1C82, 'M', u'о'),\n    (0x1C83, 'M', u'с'),\n    (0x1C84, 'M', u'т'),\n    (0x1C86, 'M', u'ъ'),\n    (0x1C87, 'M', u'ѣ'),\n    (0x1C88, 'M', u'ꙋ'),\n    (0x1C89, 'X'),\n    (0x1CC0, 'V'),\n    (0x1CC8, 'X'),\n    (0x1CD0, 'V'),\n    (0x1CFA, 'X'),\n    (0x1D00, 'V'),\n    (0x1D2C, 'M', u'a'),\n    (0x1D2D, 'M', u'æ'),\n    (0x1D2E, 'M', u'b'),\n    (0x1D2F, 'V'),\n    (0x1D30, 'M', u'd'),\n    (0x1D31, 'M', u'e'),\n    (0x1D32, 'M', u'ǝ'),\n    (0x1D33, 'M', u'g'),\n    (0x1D34, 'M', u'h'),\n    (0x1D35, 'M', u'i'),\n    (0x1D36, 'M', u'j'),\n    (0x1D37, 'M', u'k'),\n    (0x1D38, 'M', u'l'),\n    (0x1D39, 'M', u'm'),\n    (0x1D3A, 'M', u'n'),\n    (0x1D3B, 'V'),\n    (0x1D3C, 'M', u'o'),\n    (0x1D3D, 'M', u'ȣ'),\n    (0x1D3E, 'M', u'p'),\n    (0x1D3F, 'M', u'r'),\n    (0x1D40, 'M', u't'),\n    (0x1D41, 'M', u'u'),\n    (0x1D42, 'M', u'w'),\n    (0x1D43, 'M', u'a'),\n    (0x1D44, 'M', u'ɐ'),\n    (0x1D45, 'M', u'ɑ'),\n    (0x1D46, 'M', u'ᴂ'),\n    (0x1D47, 'M', u'b'),\n    (0x1D48, 'M', u'd'),\n    (0x1D49, 'M', u'e'),\n    (0x1D4A, 'M', u'ə'),\n    (0x1D4B, 'M', u'ɛ'),\n    (0x1D4C, 'M', u'ɜ'),\n    (0x1D4D, 'M', u'g'),\n    (0x1D4E, 'V'),\n    (0x1D4F, 'M', u'k'),\n    (0x1D50, 'M', u'm'),\n    (0x1D51, 'M', u'ŋ'),\n    (0x1D52, 'M', u'o'),\n    (0x1D53, 'M', u'ɔ'),\n    (0x1D54, 'M', u'ᴖ'),\n    (0x1D55, 'M', u'ᴗ'),\n    (0x1D56, 'M', u'p'),\n    (0x1D57, 'M', u't'),\n    (0x1D58, 'M', u'u'),\n    (0x1D59, 'M', u'ᴝ'),\n    (0x1D5A, 'M', u'ɯ'),\n    (0x1D5B, 'M', u'v'),\n    (0x1D5C, 'M', u'ᴥ'),\n    (0x1D5D, 'M', u'β'),\n    (0x1D5E, 'M', u'γ'),\n    (0x1D5F, 'M', u'δ'),\n    (0x1D60, 'M', u'φ'),\n    (0x1D61, 'M', u'χ'),\n    (0x1D62, 'M', u'i'),\n    (0x1D63, 'M', u'r'),\n    (0x1D64, 'M', u'u'),\n    (0x1D65, 'M', u'v'),\n    (0x1D66, 'M', u'β'),\n    (0x1D67, 'M', u'γ'),\n    (0x1D68, 'M', u'ρ'),\n    (0x1D69, 'M', u'φ'),\n    (0x1D6A, 'M', u'χ'),\n    (0x1D6B, 'V'),\n    (0x1D78, 'M', u'н'),\n    (0x1D79, 'V'),\n    (0x1D9B, 'M', u'ɒ'),\n    (0x1D9C, 'M', u'c'),\n    (0x1D9D, 'M', u'ɕ'),\n    (0x1D9E, 'M', u'ð'),\n    ]\n\ndef _seg_16():\n    return [\n    (0x1D9F, 'M', u'ɜ'),\n    (0x1DA0, 'M', u'f'),\n    (0x1DA1, 'M', u'ɟ'),\n    (0x1DA2, 'M', u'ɡ'),\n    (0x1DA3, 'M', u'ɥ'),\n    (0x1DA4, 'M', u'ɨ'),\n    (0x1DA5, 'M', u'ɩ'),\n    (0x1DA6, 'M', u'ɪ'),\n    (0x1DA7, 'M', u'ᵻ'),\n    (0x1DA8, 'M', u'ʝ'),\n    (0x1DA9, 'M', u'ɭ'),\n    (0x1DAA, 'M', u'ᶅ'),\n    (0x1DAB, 'M', u'ʟ'),\n    (0x1DAC, 'M', u'ɱ'),\n    (0x1DAD, 'M', u'ɰ'),\n    (0x1DAE, 'M', u'ɲ'),\n    (0x1DAF, 'M', u'ɳ'),\n    (0x1DB0, 'M', u'ɴ'),\n    (0x1DB1, 'M', u'ɵ'),\n    (0x1DB2, 'M', u'ɸ'),\n    (0x1DB3, 'M', u'ʂ'),\n    (0x1DB4, 'M', u'ʃ'),\n    (0x1DB5, 'M', u'ƫ'),\n    (0x1DB6, 'M', u'ʉ'),\n    (0x1DB7, 'M', u'ʊ'),\n    (0x1DB8, 'M', u'ᴜ'),\n    (0x1DB9, 'M', u'ʋ'),\n    (0x1DBA, 'M', u'ʌ'),\n    (0x1DBB, 'M', u'z'),\n    (0x1DBC, 'M', u'ʐ'),\n    (0x1DBD, 'M', u'ʑ'),\n    (0x1DBE, 'M', u'ʒ'),\n    (0x1DBF, 'M', u'θ'),\n    (0x1DC0, 'V'),\n    (0x1DFA, 'X'),\n    (0x1DFB, 'V'),\n    (0x1E00, 'M', u'ḁ'),\n    (0x1E01, 'V'),\n    (0x1E02, 'M', u'ḃ'),\n    (0x1E03, 'V'),\n    (0x1E04, 'M', u'ḅ'),\n    (0x1E05, 'V'),\n    (0x1E06, 'M', u'ḇ'),\n    (0x1E07, 'V'),\n    (0x1E08, 'M', u'ḉ'),\n    (0x1E09, 'V'),\n    (0x1E0A, 'M', u'ḋ'),\n    (0x1E0B, 'V'),\n    (0x1E0C, 'M', u'ḍ'),\n    (0x1E0D, 'V'),\n    (0x1E0E, 'M', u'ḏ'),\n    (0x1E0F, 'V'),\n    (0x1E10, 'M', u'ḑ'),\n    (0x1E11, 'V'),\n    (0x1E12, 'M', u'ḓ'),\n    (0x1E13, 'V'),\n    (0x1E14, 'M', u'ḕ'),\n    (0x1E15, 'V'),\n    (0x1E16, 'M', u'ḗ'),\n    (0x1E17, 'V'),\n    (0x1E18, 'M', u'ḙ'),\n    (0x1E19, 'V'),\n    (0x1E1A, 'M', u'ḛ'),\n    (0x1E1B, 'V'),\n    (0x1E1C, 'M', u'ḝ'),\n    (0x1E1D, 'V'),\n    (0x1E1E, 'M', u'ḟ'),\n    (0x1E1F, 'V'),\n    (0x1E20, 'M', u'ḡ'),\n    (0x1E21, 'V'),\n    (0x1E22, 'M', u'ḣ'),\n    (0x1E23, 'V'),\n    (0x1E24, 'M', u'ḥ'),\n    (0x1E25, 'V'),\n    (0x1E26, 'M', u'ḧ'),\n    (0x1E27, 'V'),\n    (0x1E28, 'M', u'ḩ'),\n    (0x1E29, 'V'),\n    (0x1E2A, 'M', u'ḫ'),\n    (0x1E2B, 'V'),\n    (0x1E2C, 'M', u'ḭ'),\n    (0x1E2D, 'V'),\n    (0x1E2E, 'M', u'ḯ'),\n    (0x1E2F, 'V'),\n    (0x1E30, 'M', u'ḱ'),\n    (0x1E31, 'V'),\n    (0x1E32, 'M', u'ḳ'),\n    (0x1E33, 'V'),\n    (0x1E34, 'M', u'ḵ'),\n    (0x1E35, 'V'),\n    (0x1E36, 'M', u'ḷ'),\n    (0x1E37, 'V'),\n    (0x1E38, 'M', u'ḹ'),\n    (0x1E39, 'V'),\n    (0x1E3A, 'M', u'ḻ'),\n    (0x1E3B, 'V'),\n    (0x1E3C, 'M', u'ḽ'),\n    (0x1E3D, 'V'),\n    (0x1E3E, 'M', u'ḿ'),\n    (0x1E3F, 'V'),\n    ]\n\ndef _seg_17():\n    return [\n    (0x1E40, 'M', u'ṁ'),\n    (0x1E41, 'V'),\n    (0x1E42, 'M', u'ṃ'),\n    (0x1E43, 'V'),\n    (0x1E44, 'M', u'ṅ'),\n    (0x1E45, 'V'),\n    (0x1E46, 'M', u'ṇ'),\n    (0x1E47, 'V'),\n    (0x1E48, 'M', u'ṉ'),\n    (0x1E49, 'V'),\n    (0x1E4A, 'M', u'ṋ'),\n    (0x1E4B, 'V'),\n    (0x1E4C, 'M', u'ṍ'),\n    (0x1E4D, 'V'),\n    (0x1E4E, 'M', u'ṏ'),\n    (0x1E4F, 'V'),\n    (0x1E50, 'M', u'ṑ'),\n    (0x1E51, 'V'),\n    (0x1E52, 'M', u'ṓ'),\n    (0x1E53, 'V'),\n    (0x1E54, 'M', u'ṕ'),\n    (0x1E55, 'V'),\n    (0x1E56, 'M', u'ṗ'),\n    (0x1E57, 'V'),\n    (0x1E58, 'M', u'ṙ'),\n    (0x1E59, 'V'),\n    (0x1E5A, 'M', u'ṛ'),\n    (0x1E5B, 'V'),\n    (0x1E5C, 'M', u'ṝ'),\n    (0x1E5D, 'V'),\n    (0x1E5E, 'M', u'ṟ'),\n    (0x1E5F, 'V'),\n    (0x1E60, 'M', u'ṡ'),\n    (0x1E61, 'V'),\n    (0x1E62, 'M', u'ṣ'),\n    (0x1E63, 'V'),\n    (0x1E64, 'M', u'ṥ'),\n    (0x1E65, 'V'),\n    (0x1E66, 'M', u'ṧ'),\n    (0x1E67, 'V'),\n    (0x1E68, 'M', u'ṩ'),\n    (0x1E69, 'V'),\n    (0x1E6A, 'M', u'ṫ'),\n    (0x1E6B, 'V'),\n    (0x1E6C, 'M', u'ṭ'),\n    (0x1E6D, 'V'),\n    (0x1E6E, 'M', u'ṯ'),\n    (0x1E6F, 'V'),\n    (0x1E70, 'M', u'ṱ'),\n    (0x1E71, 'V'),\n    (0x1E72, 'M', u'ṳ'),\n    (0x1E73, 'V'),\n    (0x1E74, 'M', u'ṵ'),\n    (0x1E75, 'V'),\n    (0x1E76, 'M', u'ṷ'),\n    (0x1E77, 'V'),\n    (0x1E78, 'M', u'ṹ'),\n    (0x1E79, 'V'),\n    (0x1E7A, 'M', u'ṻ'),\n    (0x1E7B, 'V'),\n    (0x1E7C, 'M', u'ṽ'),\n    (0x1E7D, 'V'),\n    (0x1E7E, 'M', u'ṿ'),\n    (0x1E7F, 'V'),\n    (0x1E80, 'M', u'ẁ'),\n    (0x1E81, 'V'),\n    (0x1E82, 'M', u'ẃ'),\n    (0x1E83, 'V'),\n    (0x1E84, 'M', u'ẅ'),\n    (0x1E85, 'V'),\n    (0x1E86, 'M', u'ẇ'),\n    (0x1E87, 'V'),\n    (0x1E88, 'M', u'ẉ'),\n    (0x1E89, 'V'),\n    (0x1E8A, 'M', u'ẋ'),\n    (0x1E8B, 'V'),\n    (0x1E8C, 'M', u'ẍ'),\n    (0x1E8D, 'V'),\n    (0x1E8E, 'M', u'ẏ'),\n    (0x1E8F, 'V'),\n    (0x1E90, 'M', u'ẑ'),\n    (0x1E91, 'V'),\n    (0x1E92, 'M', u'ẓ'),\n    (0x1E93, 'V'),\n    (0x1E94, 'M', u'ẕ'),\n    (0x1E95, 'V'),\n    (0x1E9A, 'M', u'aʾ'),\n    (0x1E9B, 'M', u'ṡ'),\n    (0x1E9C, 'V'),\n    (0x1E9E, 'M', u'ss'),\n    (0x1E9F, 'V'),\n    (0x1EA0, 'M', u'ạ'),\n    (0x1EA1, 'V'),\n    (0x1EA2, 'M', u'ả'),\n    (0x1EA3, 'V'),\n    (0x1EA4, 'M', u'ấ'),\n    (0x1EA5, 'V'),\n    (0x1EA6, 'M', u'ầ'),\n    (0x1EA7, 'V'),\n    (0x1EA8, 'M', u'ẩ'),\n    ]\n\ndef _seg_18():\n    return [\n    (0x1EA9, 'V'),\n    (0x1EAA, 'M', u'ẫ'),\n    (0x1EAB, 'V'),\n    (0x1EAC, 'M', u'ậ'),\n    (0x1EAD, 'V'),\n    (0x1EAE, 'M', u'ắ'),\n    (0x1EAF, 'V'),\n    (0x1EB0, 'M', u'ằ'),\n    (0x1EB1, 'V'),\n    (0x1EB2, 'M', u'ẳ'),\n    (0x1EB3, 'V'),\n    (0x1EB4, 'M', u'ẵ'),\n    (0x1EB5, 'V'),\n    (0x1EB6, 'M', u'ặ'),\n    (0x1EB7, 'V'),\n    (0x1EB8, 'M', u'ẹ'),\n    (0x1EB9, 'V'),\n    (0x1EBA, 'M', u'ẻ'),\n    (0x1EBB, 'V'),\n    (0x1EBC, 'M', u'ẽ'),\n    (0x1EBD, 'V'),\n    (0x1EBE, 'M', u'ế'),\n    (0x1EBF, 'V'),\n    (0x1EC0, 'M', u'ề'),\n    (0x1EC1, 'V'),\n    (0x1EC2, 'M', u'ể'),\n    (0x1EC3, 'V'),\n    (0x1EC4, 'M', u'ễ'),\n    (0x1EC5, 'V'),\n    (0x1EC6, 'M', u'ệ'),\n    (0x1EC7, 'V'),\n    (0x1EC8, 'M', u'ỉ'),\n    (0x1EC9, 'V'),\n    (0x1ECA, 'M', u'ị'),\n    (0x1ECB, 'V'),\n    (0x1ECC, 'M', u'ọ'),\n    (0x1ECD, 'V'),\n    (0x1ECE, 'M', u'ỏ'),\n    (0x1ECF, 'V'),\n    (0x1ED0, 'M', u'ố'),\n    (0x1ED1, 'V'),\n    (0x1ED2, 'M', u'ồ'),\n    (0x1ED3, 'V'),\n    (0x1ED4, 'M', u'ổ'),\n    (0x1ED5, 'V'),\n    (0x1ED6, 'M', u'ỗ'),\n    (0x1ED7, 'V'),\n    (0x1ED8, 'M', u'ộ'),\n    (0x1ED9, 'V'),\n    (0x1EDA, 'M', u'ớ'),\n    (0x1EDB, 'V'),\n    (0x1EDC, 'M', u'ờ'),\n    (0x1EDD, 'V'),\n    (0x1EDE, 'M', u'ở'),\n    (0x1EDF, 'V'),\n    (0x1EE0, 'M', u'ỡ'),\n    (0x1EE1, 'V'),\n    (0x1EE2, 'M', u'ợ'),\n    (0x1EE3, 'V'),\n    (0x1EE4, 'M', u'ụ'),\n    (0x1EE5, 'V'),\n    (0x1EE6, 'M', u'ủ'),\n    (0x1EE7, 'V'),\n    (0x1EE8, 'M', u'ứ'),\n    (0x1EE9, 'V'),\n    (0x1EEA, 'M', u'ừ'),\n    (0x1EEB, 'V'),\n    (0x1EEC, 'M', u'ử'),\n    (0x1EED, 'V'),\n    (0x1EEE, 'M', u'ữ'),\n    (0x1EEF, 'V'),\n    (0x1EF0, 'M', u'ự'),\n    (0x1EF1, 'V'),\n    (0x1EF2, 'M', u'ỳ'),\n    (0x1EF3, 'V'),\n    (0x1EF4, 'M', u'ỵ'),\n    (0x1EF5, 'V'),\n    (0x1EF6, 'M', u'ỷ'),\n    (0x1EF7, 'V'),\n    (0x1EF8, 'M', u'ỹ'),\n    (0x1EF9, 'V'),\n    (0x1EFA, 'M', u'ỻ'),\n    (0x1EFB, 'V'),\n    (0x1EFC, 'M', u'ỽ'),\n    (0x1EFD, 'V'),\n    (0x1EFE, 'M', u'ỿ'),\n    (0x1EFF, 'V'),\n    (0x1F08, 'M', u'ἀ'),\n    (0x1F09, 'M', u'ἁ'),\n    (0x1F0A, 'M', u'ἂ'),\n    (0x1F0B, 'M', u'ἃ'),\n    (0x1F0C, 'M', u'ἄ'),\n    (0x1F0D, 'M', u'ἅ'),\n    (0x1F0E, 'M', u'ἆ'),\n    (0x1F0F, 'M', u'ἇ'),\n    (0x1F10, 'V'),\n    (0x1F16, 'X'),\n    (0x1F18, 'M', u'ἐ'),\n    (0x1F19, 'M', u'ἑ'),\n    (0x1F1A, 'M', u'ἒ'),\n    ]\n\ndef _seg_19():\n    return [\n    (0x1F1B, 'M', u'ἓ'),\n    (0x1F1C, 'M', u'ἔ'),\n    (0x1F1D, 'M', u'ἕ'),\n    (0x1F1E, 'X'),\n    (0x1F20, 'V'),\n    (0x1F28, 'M', u'ἠ'),\n    (0x1F29, 'M', u'ἡ'),\n    (0x1F2A, 'M', u'ἢ'),\n    (0x1F2B, 'M', u'ἣ'),\n    (0x1F2C, 'M', u'ἤ'),\n    (0x1F2D, 'M', u'ἥ'),\n    (0x1F2E, 'M', u'ἦ'),\n    (0x1F2F, 'M', u'ἧ'),\n    (0x1F30, 'V'),\n    (0x1F38, 'M', u'ἰ'),\n    (0x1F39, 'M', u'ἱ'),\n    (0x1F3A, 'M', u'ἲ'),\n    (0x1F3B, 'M', u'ἳ'),\n    (0x1F3C, 'M', u'ἴ'),\n    (0x1F3D, 'M', u'ἵ'),\n    (0x1F3E, 'M', u'ἶ'),\n    (0x1F3F, 'M', u'ἷ'),\n    (0x1F40, 'V'),\n    (0x1F46, 'X'),\n    (0x1F48, 'M', u'ὀ'),\n    (0x1F49, 'M', u'ὁ'),\n    (0x1F4A, 'M', u'ὂ'),\n    (0x1F4B, 'M', u'ὃ'),\n    (0x1F4C, 'M', u'ὄ'),\n    (0x1F4D, 'M', u'ὅ'),\n    (0x1F4E, 'X'),\n    (0x1F50, 'V'),\n    (0x1F58, 'X'),\n    (0x1F59, 'M', u'ὑ'),\n    (0x1F5A, 'X'),\n    (0x1F5B, 'M', u'ὓ'),\n    (0x1F5C, 'X'),\n    (0x1F5D, 'M', u'ὕ'),\n    (0x1F5E, 'X'),\n    (0x1F5F, 'M', u'ὗ'),\n    (0x1F60, 'V'),\n    (0x1F68, 'M', u'ὠ'),\n    (0x1F69, 'M', u'ὡ'),\n    (0x1F6A, 'M', u'ὢ'),\n    (0x1F6B, 'M', u'ὣ'),\n    (0x1F6C, 'M', u'ὤ'),\n    (0x1F6D, 'M', u'ὥ'),\n    (0x1F6E, 'M', u'ὦ'),\n    (0x1F6F, 'M', u'ὧ'),\n    (0x1F70, 'V'),\n    (0x1F71, 'M', u'ά'),\n    (0x1F72, 'V'),\n    (0x1F73, 'M', u'έ'),\n    (0x1F74, 'V'),\n    (0x1F75, 'M', u'ή'),\n    (0x1F76, 'V'),\n    (0x1F77, 'M', u'ί'),\n    (0x1F78, 'V'),\n    (0x1F79, 'M', u'ό'),\n    (0x1F7A, 'V'),\n    (0x1F7B, 'M', u'ύ'),\n    (0x1F7C, 'V'),\n    (0x1F7D, 'M', u'ώ'),\n    (0x1F7E, 'X'),\n    (0x1F80, 'M', u'ἀι'),\n    (0x1F81, 'M', u'ἁι'),\n    (0x1F82, 'M', u'ἂι'),\n    (0x1F83, 'M', u'ἃι'),\n    (0x1F84, 'M', u'ἄι'),\n    (0x1F85, 'M', u'ἅι'),\n    (0x1F86, 'M', u'ἆι'),\n    (0x1F87, 'M', u'ἇι'),\n    (0x1F88, 'M', u'ἀι'),\n    (0x1F89, 'M', u'ἁι'),\n    (0x1F8A, 'M', u'ἂι'),\n    (0x1F8B, 'M', u'ἃι'),\n    (0x1F8C, 'M', u'ἄι'),\n    (0x1F8D, 'M', u'ἅι'),\n    (0x1F8E, 'M', u'ἆι'),\n    (0x1F8F, 'M', u'ἇι'),\n    (0x1F90, 'M', u'ἠι'),\n    (0x1F91, 'M', u'ἡι'),\n    (0x1F92, 'M', u'ἢι'),\n    (0x1F93, 'M', u'ἣι'),\n    (0x1F94, 'M', u'ἤι'),\n    (0x1F95, 'M', u'ἥι'),\n    (0x1F96, 'M', u'ἦι'),\n    (0x1F97, 'M', u'ἧι'),\n    (0x1F98, 'M', u'ἠι'),\n    (0x1F99, 'M', u'ἡι'),\n    (0x1F9A, 'M', u'ἢι'),\n    (0x1F9B, 'M', u'ἣι'),\n    (0x1F9C, 'M', u'ἤι'),\n    (0x1F9D, 'M', u'ἥι'),\n    (0x1F9E, 'M', u'ἦι'),\n    (0x1F9F, 'M', u'ἧι'),\n    (0x1FA0, 'M', u'ὠι'),\n    (0x1FA1, 'M', u'ὡι'),\n    (0x1FA2, 'M', u'ὢι'),\n    (0x1FA3, 'M', u'ὣι'),\n    ]\n\ndef _seg_20():\n    return [\n    (0x1FA4, 'M', u'ὤι'),\n    (0x1FA5, 'M', u'ὥι'),\n    (0x1FA6, 'M', u'ὦι'),\n    (0x1FA7, 'M', u'ὧι'),\n    (0x1FA8, 'M', u'ὠι'),\n    (0x1FA9, 'M', u'ὡι'),\n    (0x1FAA, 'M', u'ὢι'),\n    (0x1FAB, 'M', u'ὣι'),\n    (0x1FAC, 'M', u'ὤι'),\n    (0x1FAD, 'M', u'ὥι'),\n    (0x1FAE, 'M', u'ὦι'),\n    (0x1FAF, 'M', u'ὧι'),\n    (0x1FB0, 'V'),\n    (0x1FB2, 'M', u'ὰι'),\n    (0x1FB3, 'M', u'αι'),\n    (0x1FB4, 'M', u'άι'),\n    (0x1FB5, 'X'),\n    (0x1FB6, 'V'),\n    (0x1FB7, 'M', u'ᾶι'),\n    (0x1FB8, 'M', u'ᾰ'),\n    (0x1FB9, 'M', u'ᾱ'),\n    (0x1FBA, 'M', u'ὰ'),\n    (0x1FBB, 'M', u'ά'),\n    (0x1FBC, 'M', u'αι'),\n    (0x1FBD, '3', u' ̓'),\n    (0x1FBE, 'M', u'ι'),\n    (0x1FBF, '3', u' ̓'),\n    (0x1FC0, '3', u' ͂'),\n    (0x1FC1, '3', u' ̈͂'),\n    (0x1FC2, 'M', u'ὴι'),\n    (0x1FC3, 'M', u'ηι'),\n    (0x1FC4, 'M', u'ήι'),\n    (0x1FC5, 'X'),\n    (0x1FC6, 'V'),\n    (0x1FC7, 'M', u'ῆι'),\n    (0x1FC8, 'M', u'ὲ'),\n    (0x1FC9, 'M', u'έ'),\n    (0x1FCA, 'M', u'ὴ'),\n    (0x1FCB, 'M', u'ή'),\n    (0x1FCC, 'M', u'ηι'),\n    (0x1FCD, '3', u' ̓̀'),\n    (0x1FCE, '3', u' ̓́'),\n    (0x1FCF, '3', u' ̓͂'),\n    (0x1FD0, 'V'),\n    (0x1FD3, 'M', u'ΐ'),\n    (0x1FD4, 'X'),\n    (0x1FD6, 'V'),\n    (0x1FD8, 'M', u'ῐ'),\n    (0x1FD9, 'M', u'ῑ'),\n    (0x1FDA, 'M', u'ὶ'),\n    (0x1FDB, 'M', u'ί'),\n    (0x1FDC, 'X'),\n    (0x1FDD, '3', u' ̔̀'),\n    (0x1FDE, '3', u' ̔́'),\n    (0x1FDF, '3', u' ̔͂'),\n    (0x1FE0, 'V'),\n    (0x1FE3, 'M', u'ΰ'),\n    (0x1FE4, 'V'),\n    (0x1FE8, 'M', u'ῠ'),\n    (0x1FE9, 'M', u'ῡ'),\n    (0x1FEA, 'M', u'ὺ'),\n    (0x1FEB, 'M', u'ύ'),\n    (0x1FEC, 'M', u'ῥ'),\n    (0x1FED, '3', u' ̈̀'),\n    (0x1FEE, '3', u' ̈́'),\n    (0x1FEF, '3', u'`'),\n    (0x1FF0, 'X'),\n    (0x1FF2, 'M', u'ὼι'),\n    (0x1FF3, 'M', u'ωι'),\n    (0x1FF4, 'M', u'ώι'),\n    (0x1FF5, 'X'),\n    (0x1FF6, 'V'),\n    (0x1FF7, 'M', u'ῶι'),\n    (0x1FF8, 'M', u'ὸ'),\n    (0x1FF9, 'M', u'ό'),\n    (0x1FFA, 'M', u'ὼ'),\n    (0x1FFB, 'M', u'ώ'),\n    (0x1FFC, 'M', u'ωι'),\n    (0x1FFD, '3', u' ́'),\n    (0x1FFE, '3', u' ̔'),\n    (0x1FFF, 'X'),\n    (0x2000, '3', u' '),\n    (0x200B, 'I'),\n    (0x200C, 'D', u''),\n    (0x200E, 'X'),\n    (0x2010, 'V'),\n    (0x2011, 'M', u'‐'),\n    (0x2012, 'V'),\n    (0x2017, '3', u' ̳'),\n    (0x2018, 'V'),\n    (0x2024, 'X'),\n    (0x2027, 'V'),\n    (0x2028, 'X'),\n    (0x202F, '3', u' '),\n    (0x2030, 'V'),\n    (0x2033, 'M', u'′′'),\n    (0x2034, 'M', u'′′′'),\n    (0x2035, 'V'),\n    (0x2036, 'M', u'‵‵'),\n    (0x2037, 'M', u'‵‵‵'),\n    ]\n\ndef _seg_21():\n    return [\n    (0x2038, 'V'),\n    (0x203C, '3', u'!!'),\n    (0x203D, 'V'),\n    (0x203E, '3', u' ̅'),\n    (0x203F, 'V'),\n    (0x2047, '3', u'??'),\n    (0x2048, '3', u'?!'),\n    (0x2049, '3', u'!?'),\n    (0x204A, 'V'),\n    (0x2057, 'M', u'′′′′'),\n    (0x2058, 'V'),\n    (0x205F, '3', u' '),\n    (0x2060, 'I'),\n    (0x2061, 'X'),\n    (0x2064, 'I'),\n    (0x2065, 'X'),\n    (0x2070, 'M', u'0'),\n    (0x2071, 'M', u'i'),\n    (0x2072, 'X'),\n    (0x2074, 'M', u'4'),\n    (0x2075, 'M', u'5'),\n    (0x2076, 'M', u'6'),\n    (0x2077, 'M', u'7'),\n    (0x2078, 'M', u'8'),\n    (0x2079, 'M', u'9'),\n    (0x207A, '3', u'+'),\n    (0x207B, 'M', u'−'),\n    (0x207C, '3', u'='),\n    (0x207D, '3', u'('),\n    (0x207E, '3', u')'),\n    (0x207F, 'M', u'n'),\n    (0x2080, 'M', u'0'),\n    (0x2081, 'M', u'1'),\n    (0x2082, 'M', u'2'),\n    (0x2083, 'M', u'3'),\n    (0x2084, 'M', u'4'),\n    (0x2085, 'M', u'5'),\n    (0x2086, 'M', u'6'),\n    (0x2087, 'M', u'7'),\n    (0x2088, 'M', u'8'),\n    (0x2089, 'M', u'9'),\n    (0x208A, '3', u'+'),\n    (0x208B, 'M', u'−'),\n    (0x208C, '3', u'='),\n    (0x208D, '3', u'('),\n    (0x208E, '3', u')'),\n    (0x208F, 'X'),\n    (0x2090, 'M', u'a'),\n    (0x2091, 'M', u'e'),\n    (0x2092, 'M', u'o'),\n    (0x2093, 'M', u'x'),\n    (0x2094, 'M', u'ə'),\n    (0x2095, 'M', u'h'),\n    (0x2096, 'M', u'k'),\n    (0x2097, 'M', u'l'),\n    (0x2098, 'M', u'm'),\n    (0x2099, 'M', u'n'),\n    (0x209A, 'M', u'p'),\n    (0x209B, 'M', u's'),\n    (0x209C, 'M', u't'),\n    (0x209D, 'X'),\n    (0x20A0, 'V'),\n    (0x20A8, 'M', u'rs'),\n    (0x20A9, 'V'),\n    (0x20C0, 'X'),\n    (0x20D0, 'V'),\n    (0x20F1, 'X'),\n    (0x2100, '3', u'a/c'),\n    (0x2101, '3', u'a/s'),\n    (0x2102, 'M', u'c'),\n    (0x2103, 'M', u'°c'),\n    (0x2104, 'V'),\n    (0x2105, '3', u'c/o'),\n    (0x2106, '3', u'c/u'),\n    (0x2107, 'M', u'ɛ'),\n    (0x2108, 'V'),\n    (0x2109, 'M', u'°f'),\n    (0x210A, 'M', u'g'),\n    (0x210B, 'M', u'h'),\n    (0x210F, 'M', u'ħ'),\n    (0x2110, 'M', u'i'),\n    (0x2112, 'M', u'l'),\n    (0x2114, 'V'),\n    (0x2115, 'M', u'n'),\n    (0x2116, 'M', u'no'),\n    (0x2117, 'V'),\n    (0x2119, 'M', u'p'),\n    (0x211A, 'M', u'q'),\n    (0x211B, 'M', u'r'),\n    (0x211E, 'V'),\n    (0x2120, 'M', u'sm'),\n    (0x2121, 'M', u'tel'),\n    (0x2122, 'M', u'tm'),\n    (0x2123, 'V'),\n    (0x2124, 'M', u'z'),\n    (0x2125, 'V'),\n    (0x2126, 'M', u'ω'),\n    (0x2127, 'V'),\n    (0x2128, 'M', u'z'),\n    (0x2129, 'V'),\n    ]\n\ndef _seg_22():\n    return [\n    (0x212A, 'M', u'k'),\n    (0x212B, 'M', u'å'),\n    (0x212C, 'M', u'b'),\n    (0x212D, 'M', u'c'),\n    (0x212E, 'V'),\n    (0x212F, 'M', u'e'),\n    (0x2131, 'M', u'f'),\n    (0x2132, 'X'),\n    (0x2133, 'M', u'm'),\n    (0x2134, 'M', u'o'),\n    (0x2135, 'M', u'א'),\n    (0x2136, 'M', u'ב'),\n    (0x2137, 'M', u'ג'),\n    (0x2138, 'M', u'ד'),\n    (0x2139, 'M', u'i'),\n    (0x213A, 'V'),\n    (0x213B, 'M', u'fax'),\n    (0x213C, 'M', u'π'),\n    (0x213D, 'M', u'γ'),\n    (0x213F, 'M', u'π'),\n    (0x2140, 'M', u'∑'),\n    (0x2141, 'V'),\n    (0x2145, 'M', u'd'),\n    (0x2147, 'M', u'e'),\n    (0x2148, 'M', u'i'),\n    (0x2149, 'M', u'j'),\n    (0x214A, 'V'),\n    (0x2150, 'M', u'1⁄7'),\n    (0x2151, 'M', u'1⁄9'),\n    (0x2152, 'M', u'1⁄10'),\n    (0x2153, 'M', u'1⁄3'),\n    (0x2154, 'M', u'2⁄3'),\n    (0x2155, 'M', u'1⁄5'),\n    (0x2156, 'M', u'2⁄5'),\n    (0x2157, 'M', u'3⁄5'),\n    (0x2158, 'M', u'4⁄5'),\n    (0x2159, 'M', u'1⁄6'),\n    (0x215A, 'M', u'5⁄6'),\n    (0x215B, 'M', u'1⁄8'),\n    (0x215C, 'M', u'3⁄8'),\n    (0x215D, 'M', u'5⁄8'),\n    (0x215E, 'M', u'7⁄8'),\n    (0x215F, 'M', u'1⁄'),\n    (0x2160, 'M', u'i'),\n    (0x2161, 'M', u'ii'),\n    (0x2162, 'M', u'iii'),\n    (0x2163, 'M', u'iv'),\n    (0x2164, 'M', u'v'),\n    (0x2165, 'M', u'vi'),\n    (0x2166, 'M', u'vii'),\n    (0x2167, 'M', u'viii'),\n    (0x2168, 'M', u'ix'),\n    (0x2169, 'M', u'x'),\n    (0x216A, 'M', u'xi'),\n    (0x216B, 'M', u'xii'),\n    (0x216C, 'M', u'l'),\n    (0x216D, 'M', u'c'),\n    (0x216E, 'M', u'd'),\n    (0x216F, 'M', u'm'),\n    (0x2170, 'M', u'i'),\n    (0x2171, 'M', u'ii'),\n    (0x2172, 'M', u'iii'),\n    (0x2173, 'M', u'iv'),\n    (0x2174, 'M', u'v'),\n    (0x2175, 'M', u'vi'),\n    (0x2176, 'M', u'vii'),\n    (0x2177, 'M', u'viii'),\n    (0x2178, 'M', u'ix'),\n    (0x2179, 'M', u'x'),\n    (0x217A, 'M', u'xi'),\n    (0x217B, 'M', u'xii'),\n    (0x217C, 'M', u'l'),\n    (0x217D, 'M', u'c'),\n    (0x217E, 'M', u'd'),\n    (0x217F, 'M', u'm'),\n    (0x2180, 'V'),\n    (0x2183, 'X'),\n    (0x2184, 'V'),\n    (0x2189, 'M', u'0⁄3'),\n    (0x218A, 'V'),\n    (0x218C, 'X'),\n    (0x2190, 'V'),\n    (0x222C, 'M', u'∫∫'),\n    (0x222D, 'M', u'∫∫∫'),\n    (0x222E, 'V'),\n    (0x222F, 'M', u'∮∮'),\n    (0x2230, 'M', u'∮∮∮'),\n    (0x2231, 'V'),\n    (0x2260, '3'),\n    (0x2261, 'V'),\n    (0x226E, '3'),\n    (0x2270, 'V'),\n    (0x2329, 'M', u'〈'),\n    (0x232A, 'M', u'〉'),\n    (0x232B, 'V'),\n    (0x2427, 'X'),\n    (0x2440, 'V'),\n    (0x244B, 'X'),\n    (0x2460, 'M', u'1'),\n    (0x2461, 'M', u'2'),\n    ]\n\ndef _seg_23():\n    return [\n    (0x2462, 'M', u'3'),\n    (0x2463, 'M', u'4'),\n    (0x2464, 'M', u'5'),\n    (0x2465, 'M', u'6'),\n    (0x2466, 'M', u'7'),\n    (0x2467, 'M', u'8'),\n    (0x2468, 'M', u'9'),\n    (0x2469, 'M', u'10'),\n    (0x246A, 'M', u'11'),\n    (0x246B, 'M', u'12'),\n    (0x246C, 'M', u'13'),\n    (0x246D, 'M', u'14'),\n    (0x246E, 'M', u'15'),\n    (0x246F, 'M', u'16'),\n    (0x2470, 'M', u'17'),\n    (0x2471, 'M', u'18'),\n    (0x2472, 'M', u'19'),\n    (0x2473, 'M', u'20'),\n    (0x2474, '3', u'(1)'),\n    (0x2475, '3', u'(2)'),\n    (0x2476, '3', u'(3)'),\n    (0x2477, '3', u'(4)'),\n    (0x2478, '3', u'(5)'),\n    (0x2479, '3', u'(6)'),\n    (0x247A, '3', u'(7)'),\n    (0x247B, '3', u'(8)'),\n    (0x247C, '3', u'(9)'),\n    (0x247D, '3', u'(10)'),\n    (0x247E, '3', u'(11)'),\n    (0x247F, '3', u'(12)'),\n    (0x2480, '3', u'(13)'),\n    (0x2481, '3', u'(14)'),\n    (0x2482, '3', u'(15)'),\n    (0x2483, '3', u'(16)'),\n    (0x2484, '3', u'(17)'),\n    (0x2485, '3', u'(18)'),\n    (0x2486, '3', u'(19)'),\n    (0x2487, '3', u'(20)'),\n    (0x2488, 'X'),\n    (0x249C, '3', u'(a)'),\n    (0x249D, '3', u'(b)'),\n    (0x249E, '3', u'(c)'),\n    (0x249F, '3', u'(d)'),\n    (0x24A0, '3', u'(e)'),\n    (0x24A1, '3', u'(f)'),\n    (0x24A2, '3', u'(g)'),\n    (0x24A3, '3', u'(h)'),\n    (0x24A4, '3', u'(i)'),\n    (0x24A5, '3', u'(j)'),\n    (0x24A6, '3', u'(k)'),\n    (0x24A7, '3', u'(l)'),\n    (0x24A8, '3', u'(m)'),\n    (0x24A9, '3', u'(n)'),\n    (0x24AA, '3', u'(o)'),\n    (0x24AB, '3', u'(p)'),\n    (0x24AC, '3', u'(q)'),\n    (0x24AD, '3', u'(r)'),\n    (0x24AE, '3', u'(s)'),\n    (0x24AF, '3', u'(t)'),\n    (0x24B0, '3', u'(u)'),\n    (0x24B1, '3', u'(v)'),\n    (0x24B2, '3', u'(w)'),\n    (0x24B3, '3', u'(x)'),\n    (0x24B4, '3', u'(y)'),\n    (0x24B5, '3', u'(z)'),\n    (0x24B6, 'M', u'a'),\n    (0x24B7, 'M', u'b'),\n    (0x24B8, 'M', u'c'),\n    (0x24B9, 'M', u'd'),\n    (0x24BA, 'M', u'e'),\n    (0x24BB, 'M', u'f'),\n    (0x24BC, 'M', u'g'),\n    (0x24BD, 'M', u'h'),\n    (0x24BE, 'M', u'i'),\n    (0x24BF, 'M', u'j'),\n    (0x24C0, 'M', u'k'),\n    (0x24C1, 'M', u'l'),\n    (0x24C2, 'M', u'm'),\n    (0x24C3, 'M', u'n'),\n    (0x24C4, 'M', u'o'),\n    (0x24C5, 'M', u'p'),\n    (0x24C6, 'M', u'q'),\n    (0x24C7, 'M', u'r'),\n    (0x24C8, 'M', u's'),\n    (0x24C9, 'M', u't'),\n    (0x24CA, 'M', u'u'),\n    (0x24CB, 'M', u'v'),\n    (0x24CC, 'M', u'w'),\n    (0x24CD, 'M', u'x'),\n    (0x24CE, 'M', u'y'),\n    (0x24CF, 'M', u'z'),\n    (0x24D0, 'M', u'a'),\n    (0x24D1, 'M', u'b'),\n    (0x24D2, 'M', u'c'),\n    (0x24D3, 'M', u'd'),\n    (0x24D4, 'M', u'e'),\n    (0x24D5, 'M', u'f'),\n    (0x24D6, 'M', u'g'),\n    (0x24D7, 'M', u'h'),\n    (0x24D8, 'M', u'i'),\n    ]\n\ndef _seg_24():\n    return [\n    (0x24D9, 'M', u'j'),\n    (0x24DA, 'M', u'k'),\n    (0x24DB, 'M', u'l'),\n    (0x24DC, 'M', u'm'),\n    (0x24DD, 'M', u'n'),\n    (0x24DE, 'M', u'o'),\n    (0x24DF, 'M', u'p'),\n    (0x24E0, 'M', u'q'),\n    (0x24E1, 'M', u'r'),\n    (0x24E2, 'M', u's'),\n    (0x24E3, 'M', u't'),\n    (0x24E4, 'M', u'u'),\n    (0x24E5, 'M', u'v'),\n    (0x24E6, 'M', u'w'),\n    (0x24E7, 'M', u'x'),\n    (0x24E8, 'M', u'y'),\n    (0x24E9, 'M', u'z'),\n    (0x24EA, 'M', u'0'),\n    (0x24EB, 'V'),\n    (0x2A0C, 'M', u'∫∫∫∫'),\n    (0x2A0D, 'V'),\n    (0x2A74, '3', u'::='),\n    (0x2A75, '3', u'=='),\n    (0x2A76, '3', u'==='),\n    (0x2A77, 'V'),\n    (0x2ADC, 'M', u'⫝̸'),\n    (0x2ADD, 'V'),\n    (0x2B74, 'X'),\n    (0x2B76, 'V'),\n    (0x2B96, 'X'),\n    (0x2B98, 'V'),\n    (0x2BC9, 'X'),\n    (0x2BCA, 'V'),\n    (0x2BFF, 'X'),\n    (0x2C00, 'M', u'ⰰ'),\n    (0x2C01, 'M', u'ⰱ'),\n    (0x2C02, 'M', u'ⰲ'),\n    (0x2C03, 'M', u'ⰳ'),\n    (0x2C04, 'M', u'ⰴ'),\n    (0x2C05, 'M', u'ⰵ'),\n    (0x2C06, 'M', u'ⰶ'),\n    (0x2C07, 'M', u'ⰷ'),\n    (0x2C08, 'M', u'ⰸ'),\n    (0x2C09, 'M', u'ⰹ'),\n    (0x2C0A, 'M', u'ⰺ'),\n    (0x2C0B, 'M', u'ⰻ'),\n    (0x2C0C, 'M', u'ⰼ'),\n    (0x2C0D, 'M', u'ⰽ'),\n    (0x2C0E, 'M', u'ⰾ'),\n    (0x2C0F, 'M', u'ⰿ'),\n    (0x2C10, 'M', u'ⱀ'),\n    (0x2C11, 'M', u'ⱁ'),\n    (0x2C12, 'M', u'ⱂ'),\n    (0x2C13, 'M', u'ⱃ'),\n    (0x2C14, 'M', u'ⱄ'),\n    (0x2C15, 'M', u'ⱅ'),\n    (0x2C16, 'M', u'ⱆ'),\n    (0x2C17, 'M', u'ⱇ'),\n    (0x2C18, 'M', u'ⱈ'),\n    (0x2C19, 'M', u'ⱉ'),\n    (0x2C1A, 'M', u'ⱊ'),\n    (0x2C1B, 'M', u'ⱋ'),\n    (0x2C1C, 'M', u'ⱌ'),\n    (0x2C1D, 'M', u'ⱍ'),\n    (0x2C1E, 'M', u'ⱎ'),\n    (0x2C1F, 'M', u'ⱏ'),\n    (0x2C20, 'M', u'ⱐ'),\n    (0x2C21, 'M', u'ⱑ'),\n    (0x2C22, 'M', u'ⱒ'),\n    (0x2C23, 'M', u'ⱓ'),\n    (0x2C24, 'M', u'ⱔ'),\n    (0x2C25, 'M', u'ⱕ'),\n    (0x2C26, 'M', u'ⱖ'),\n    (0x2C27, 'M', u'ⱗ'),\n    (0x2C28, 'M', u'ⱘ'),\n    (0x2C29, 'M', u'ⱙ'),\n    (0x2C2A, 'M', u'ⱚ'),\n    (0x2C2B, 'M', u'ⱛ'),\n    (0x2C2C, 'M', u'ⱜ'),\n    (0x2C2D, 'M', u'ⱝ'),\n    (0x2C2E, 'M', u'ⱞ'),\n    (0x2C2F, 'X'),\n    (0x2C30, 'V'),\n    (0x2C5F, 'X'),\n    (0x2C60, 'M', u'ⱡ'),\n    (0x2C61, 'V'),\n    (0x2C62, 'M', u'ɫ'),\n    (0x2C63, 'M', u'ᵽ'),\n    (0x2C64, 'M', u'ɽ'),\n    (0x2C65, 'V'),\n    (0x2C67, 'M', u'ⱨ'),\n    (0x2C68, 'V'),\n    (0x2C69, 'M', u'ⱪ'),\n    (0x2C6A, 'V'),\n    (0x2C6B, 'M', u'ⱬ'),\n    (0x2C6C, 'V'),\n    (0x2C6D, 'M', u'ɑ'),\n    (0x2C6E, 'M', u'ɱ'),\n    (0x2C6F, 'M', u'ɐ'),\n    (0x2C70, 'M', u'ɒ'),\n    ]\n\ndef _seg_25():\n    return [\n    (0x2C71, 'V'),\n    (0x2C72, 'M', u'ⱳ'),\n    (0x2C73, 'V'),\n    (0x2C75, 'M', u'ⱶ'),\n    (0x2C76, 'V'),\n    (0x2C7C, 'M', u'j'),\n    (0x2C7D, 'M', u'v'),\n    (0x2C7E, 'M', u'ȿ'),\n    (0x2C7F, 'M', u'ɀ'),\n    (0x2C80, 'M', u'ⲁ'),\n    (0x2C81, 'V'),\n    (0x2C82, 'M', u'ⲃ'),\n    (0x2C83, 'V'),\n    (0x2C84, 'M', u'ⲅ'),\n    (0x2C85, 'V'),\n    (0x2C86, 'M', u'ⲇ'),\n    (0x2C87, 'V'),\n    (0x2C88, 'M', u'ⲉ'),\n    (0x2C89, 'V'),\n    (0x2C8A, 'M', u'ⲋ'),\n    (0x2C8B, 'V'),\n    (0x2C8C, 'M', u'ⲍ'),\n    (0x2C8D, 'V'),\n    (0x2C8E, 'M', u'ⲏ'),\n    (0x2C8F, 'V'),\n    (0x2C90, 'M', u'ⲑ'),\n    (0x2C91, 'V'),\n    (0x2C92, 'M', u'ⲓ'),\n    (0x2C93, 'V'),\n    (0x2C94, 'M', u'ⲕ'),\n    (0x2C95, 'V'),\n    (0x2C96, 'M', u'ⲗ'),\n    (0x2C97, 'V'),\n    (0x2C98, 'M', u'ⲙ'),\n    (0x2C99, 'V'),\n    (0x2C9A, 'M', u'ⲛ'),\n    (0x2C9B, 'V'),\n    (0x2C9C, 'M', u'ⲝ'),\n    (0x2C9D, 'V'),\n    (0x2C9E, 'M', u'ⲟ'),\n    (0x2C9F, 'V'),\n    (0x2CA0, 'M', u'ⲡ'),\n    (0x2CA1, 'V'),\n    (0x2CA2, 'M', u'ⲣ'),\n    (0x2CA3, 'V'),\n    (0x2CA4, 'M', u'ⲥ'),\n    (0x2CA5, 'V'),\n    (0x2CA6, 'M', u'ⲧ'),\n    (0x2CA7, 'V'),\n    (0x2CA8, 'M', u'ⲩ'),\n    (0x2CA9, 'V'),\n    (0x2CAA, 'M', u'ⲫ'),\n    (0x2CAB, 'V'),\n    (0x2CAC, 'M', u'ⲭ'),\n    (0x2CAD, 'V'),\n    (0x2CAE, 'M', u'ⲯ'),\n    (0x2CAF, 'V'),\n    (0x2CB0, 'M', u'ⲱ'),\n    (0x2CB1, 'V'),\n    (0x2CB2, 'M', u'ⲳ'),\n    (0x2CB3, 'V'),\n    (0x2CB4, 'M', u'ⲵ'),\n    (0x2CB5, 'V'),\n    (0x2CB6, 'M', u'ⲷ'),\n    (0x2CB7, 'V'),\n    (0x2CB8, 'M', u'ⲹ'),\n    (0x2CB9, 'V'),\n    (0x2CBA, 'M', u'ⲻ'),\n    (0x2CBB, 'V'),\n    (0x2CBC, 'M', u'ⲽ'),\n    (0x2CBD, 'V'),\n    (0x2CBE, 'M', u'ⲿ'),\n    (0x2CBF, 'V'),\n    (0x2CC0, 'M', u'ⳁ'),\n    (0x2CC1, 'V'),\n    (0x2CC2, 'M', u'ⳃ'),\n    (0x2CC3, 'V'),\n    (0x2CC4, 'M', u'ⳅ'),\n    (0x2CC5, 'V'),\n    (0x2CC6, 'M', u'ⳇ'),\n    (0x2CC7, 'V'),\n    (0x2CC8, 'M', u'ⳉ'),\n    (0x2CC9, 'V'),\n    (0x2CCA, 'M', u'ⳋ'),\n    (0x2CCB, 'V'),\n    (0x2CCC, 'M', u'ⳍ'),\n    (0x2CCD, 'V'),\n    (0x2CCE, 'M', u'ⳏ'),\n    (0x2CCF, 'V'),\n    (0x2CD0, 'M', u'ⳑ'),\n    (0x2CD1, 'V'),\n    (0x2CD2, 'M', u'ⳓ'),\n    (0x2CD3, 'V'),\n    (0x2CD4, 'M', u'ⳕ'),\n    (0x2CD5, 'V'),\n    (0x2CD6, 'M', u'ⳗ'),\n    (0x2CD7, 'V'),\n    (0x2CD8, 'M', u'ⳙ'),\n    (0x2CD9, 'V'),\n    (0x2CDA, 'M', u'ⳛ'),\n    ]\n\ndef _seg_26():\n    return [\n    (0x2CDB, 'V'),\n    (0x2CDC, 'M', u'ⳝ'),\n    (0x2CDD, 'V'),\n    (0x2CDE, 'M', u'ⳟ'),\n    (0x2CDF, 'V'),\n    (0x2CE0, 'M', u'ⳡ'),\n    (0x2CE1, 'V'),\n    (0x2CE2, 'M', u'ⳣ'),\n    (0x2CE3, 'V'),\n    (0x2CEB, 'M', u'ⳬ'),\n    (0x2CEC, 'V'),\n    (0x2CED, 'M', u'ⳮ'),\n    (0x2CEE, 'V'),\n    (0x2CF2, 'M', u'ⳳ'),\n    (0x2CF3, 'V'),\n    (0x2CF4, 'X'),\n    (0x2CF9, 'V'),\n    (0x2D26, 'X'),\n    (0x2D27, 'V'),\n    (0x2D28, 'X'),\n    (0x2D2D, 'V'),\n    (0x2D2E, 'X'),\n    (0x2D30, 'V'),\n    (0x2D68, 'X'),\n    (0x2D6F, 'M', u'ⵡ'),\n    (0x2D70, 'V'),\n    (0x2D71, 'X'),\n    (0x2D7F, 'V'),\n    (0x2D97, 'X'),\n    (0x2DA0, 'V'),\n    (0x2DA7, 'X'),\n    (0x2DA8, 'V'),\n    (0x2DAF, 'X'),\n    (0x2DB0, 'V'),\n    (0x2DB7, 'X'),\n    (0x2DB8, 'V'),\n    (0x2DBF, 'X'),\n    (0x2DC0, 'V'),\n    (0x2DC7, 'X'),\n    (0x2DC8, 'V'),\n    (0x2DCF, 'X'),\n    (0x2DD0, 'V'),\n    (0x2DD7, 'X'),\n    (0x2DD8, 'V'),\n    (0x2DDF, 'X'),\n    (0x2DE0, 'V'),\n    (0x2E4F, 'X'),\n    (0x2E80, 'V'),\n    (0x2E9A, 'X'),\n    (0x2E9B, 'V'),\n    (0x2E9F, 'M', u'母'),\n    (0x2EA0, 'V'),\n    (0x2EF3, 'M', u'龟'),\n    (0x2EF4, 'X'),\n    (0x2F00, 'M', u'一'),\n    (0x2F01, 'M', u'丨'),\n    (0x2F02, 'M', u'丶'),\n    (0x2F03, 'M', u'丿'),\n    (0x2F04, 'M', u'乙'),\n    (0x2F05, 'M', u'亅'),\n    (0x2F06, 'M', u'二'),\n    (0x2F07, 'M', u'亠'),\n    (0x2F08, 'M', u'人'),\n    (0x2F09, 'M', u'儿'),\n    (0x2F0A, 'M', u'入'),\n    (0x2F0B, 'M', u'八'),\n    (0x2F0C, 'M', u'冂'),\n    (0x2F0D, 'M', u'冖'),\n    (0x2F0E, 'M', u'冫'),\n    (0x2F0F, 'M', u'几'),\n    (0x2F10, 'M', u'凵'),\n    (0x2F11, 'M', u'刀'),\n    (0x2F12, 'M', u'力'),\n    (0x2F13, 'M', u'勹'),\n    (0x2F14, 'M', u'匕'),\n    (0x2F15, 'M', u'匚'),\n    (0x2F16, 'M', u'匸'),\n    (0x2F17, 'M', u'十'),\n    (0x2F18, 'M', u'卜'),\n    (0x2F19, 'M', u'卩'),\n    (0x2F1A, 'M', u'厂'),\n    (0x2F1B, 'M', u'厶'),\n    (0x2F1C, 'M', u'又'),\n    (0x2F1D, 'M', u'口'),\n    (0x2F1E, 'M', u'囗'),\n    (0x2F1F, 'M', u'土'),\n    (0x2F20, 'M', u'士'),\n    (0x2F21, 'M', u'夂'),\n    (0x2F22, 'M', u'夊'),\n    (0x2F23, 'M', u'夕'),\n    (0x2F24, 'M', u'大'),\n    (0x2F25, 'M', u'女'),\n    (0x2F26, 'M', u'子'),\n    (0x2F27, 'M', u'宀'),\n    (0x2F28, 'M', u'寸'),\n    (0x2F29, 'M', u'小'),\n    (0x2F2A, 'M', u'尢'),\n    (0x2F2B, 'M', u'尸'),\n    (0x2F2C, 'M', u'屮'),\n    (0x2F2D, 'M', u'山'),\n    ]\n\ndef _seg_27():\n    return [\n    (0x2F2E, 'M', u'巛'),\n    (0x2F2F, 'M', u'工'),\n    (0x2F30, 'M', u'己'),\n    (0x2F31, 'M', u'巾'),\n    (0x2F32, 'M', u'干'),\n    (0x2F33, 'M', u'幺'),\n    (0x2F34, 'M', u'广'),\n    (0x2F35, 'M', u'廴'),\n    (0x2F36, 'M', u'廾'),\n    (0x2F37, 'M', u'弋'),\n    (0x2F38, 'M', u'弓'),\n    (0x2F39, 'M', u'彐'),\n    (0x2F3A, 'M', u'彡'),\n    (0x2F3B, 'M', u'彳'),\n    (0x2F3C, 'M', u'心'),\n    (0x2F3D, 'M', u'戈'),\n    (0x2F3E, 'M', u'戶'),\n    (0x2F3F, 'M', u'手'),\n    (0x2F40, 'M', u'支'),\n    (0x2F41, 'M', u'攴'),\n    (0x2F42, 'M', u'文'),\n    (0x2F43, 'M', u'斗'),\n    (0x2F44, 'M', u'斤'),\n    (0x2F45, 'M', u'方'),\n    (0x2F46, 'M', u'无'),\n    (0x2F47, 'M', u'日'),\n    (0x2F48, 'M', u'曰'),\n    (0x2F49, 'M', u'月'),\n    (0x2F4A, 'M', u'木'),\n    (0x2F4B, 'M', u'欠'),\n    (0x2F4C, 'M', u'止'),\n    (0x2F4D, 'M', u'歹'),\n    (0x2F4E, 'M', u'殳'),\n    (0x2F4F, 'M', u'毋'),\n    (0x2F50, 'M', u'比'),\n    (0x2F51, 'M', u'毛'),\n    (0x2F52, 'M', u'氏'),\n    (0x2F53, 'M', u'气'),\n    (0x2F54, 'M', u'水'),\n    (0x2F55, 'M', u'火'),\n    (0x2F56, 'M', u'爪'),\n    (0x2F57, 'M', u'父'),\n    (0x2F58, 'M', u'爻'),\n    (0x2F59, 'M', u'爿'),\n    (0x2F5A, 'M', u'片'),\n    (0x2F5B, 'M', u'牙'),\n    (0x2F5C, 'M', u'牛'),\n    (0x2F5D, 'M', u'犬'),\n    (0x2F5E, 'M', u'玄'),\n    (0x2F5F, 'M', u'玉'),\n    (0x2F60, 'M', u'瓜'),\n    (0x2F61, 'M', u'瓦'),\n    (0x2F62, 'M', u'甘'),\n    (0x2F63, 'M', u'生'),\n    (0x2F64, 'M', u'用'),\n    (0x2F65, 'M', u'田'),\n    (0x2F66, 'M', u'疋'),\n    (0x2F67, 'M', u'疒'),\n    (0x2F68, 'M', u'癶'),\n    (0x2F69, 'M', u'白'),\n    (0x2F6A, 'M', u'皮'),\n    (0x2F6B, 'M', u'皿'),\n    (0x2F6C, 'M', u'目'),\n    (0x2F6D, 'M', u'矛'),\n    (0x2F6E, 'M', u'矢'),\n    (0x2F6F, 'M', u'石'),\n    (0x2F70, 'M', u'示'),\n    (0x2F71, 'M', u'禸'),\n    (0x2F72, 'M', u'禾'),\n    (0x2F73, 'M', u'穴'),\n    (0x2F74, 'M', u'立'),\n    (0x2F75, 'M', u'竹'),\n    (0x2F76, 'M', u'米'),\n    (0x2F77, 'M', u'糸'),\n    (0x2F78, 'M', u'缶'),\n    (0x2F79, 'M', u'网'),\n    (0x2F7A, 'M', u'羊'),\n    (0x2F7B, 'M', u'羽'),\n    (0x2F7C, 'M', u'老'),\n    (0x2F7D, 'M', u'而'),\n    (0x2F7E, 'M', u'耒'),\n    (0x2F7F, 'M', u'耳'),\n    (0x2F80, 'M', u'聿'),\n    (0x2F81, 'M', u'肉'),\n    (0x2F82, 'M', u'臣'),\n    (0x2F83, 'M', u'自'),\n    (0x2F84, 'M', u'至'),\n    (0x2F85, 'M', u'臼'),\n    (0x2F86, 'M', u'舌'),\n    (0x2F87, 'M', u'舛'),\n    (0x2F88, 'M', u'舟'),\n    (0x2F89, 'M', u'艮'),\n    (0x2F8A, 'M', u'色'),\n    (0x2F8B, 'M', u'艸'),\n    (0x2F8C, 'M', u'虍'),\n    (0x2F8D, 'M', u'虫'),\n    (0x2F8E, 'M', u'血'),\n    (0x2F8F, 'M', u'行'),\n    (0x2F90, 'M', u'衣'),\n    (0x2F91, 'M', u'襾'),\n    ]\n\ndef _seg_28():\n    return [\n    (0x2F92, 'M', u'見'),\n    (0x2F93, 'M', u'角'),\n    (0x2F94, 'M', u'言'),\n    (0x2F95, 'M', u'谷'),\n    (0x2F96, 'M', u'豆'),\n    (0x2F97, 'M', u'豕'),\n    (0x2F98, 'M', u'豸'),\n    (0x2F99, 'M', u'貝'),\n    (0x2F9A, 'M', u'赤'),\n    (0x2F9B, 'M', u'走'),\n    (0x2F9C, 'M', u'足'),\n    (0x2F9D, 'M', u'身'),\n    (0x2F9E, 'M', u'車'),\n    (0x2F9F, 'M', u'辛'),\n    (0x2FA0, 'M', u'辰'),\n    (0x2FA1, 'M', u'辵'),\n    (0x2FA2, 'M', u'邑'),\n    (0x2FA3, 'M', u'酉'),\n    (0x2FA4, 'M', u'釆'),\n    (0x2FA5, 'M', u'里'),\n    (0x2FA6, 'M', u'金'),\n    (0x2FA7, 'M', u'長'),\n    (0x2FA8, 'M', u'門'),\n    (0x2FA9, 'M', u'阜'),\n    (0x2FAA, 'M', u'隶'),\n    (0x2FAB, 'M', u'隹'),\n    (0x2FAC, 'M', u'雨'),\n    (0x2FAD, 'M', u'靑'),\n    (0x2FAE, 'M', u'非'),\n    (0x2FAF, 'M', u'面'),\n    (0x2FB0, 'M', u'革'),\n    (0x2FB1, 'M', u'韋'),\n    (0x2FB2, 'M', u'韭'),\n    (0x2FB3, 'M', u'音'),\n    (0x2FB4, 'M', u'頁'),\n    (0x2FB5, 'M', u'風'),\n    (0x2FB6, 'M', u'飛'),\n    (0x2FB7, 'M', u'食'),\n    (0x2FB8, 'M', u'首'),\n    (0x2FB9, 'M', u'香'),\n    (0x2FBA, 'M', u'馬'),\n    (0x2FBB, 'M', u'骨'),\n    (0x2FBC, 'M', u'高'),\n    (0x2FBD, 'M', u'髟'),\n    (0x2FBE, 'M', u'鬥'),\n    (0x2FBF, 'M', u'鬯'),\n    (0x2FC0, 'M', u'鬲'),\n    (0x2FC1, 'M', u'鬼'),\n    (0x2FC2, 'M', u'魚'),\n    (0x2FC3, 'M', u'鳥'),\n    (0x2FC4, 'M', u'鹵'),\n    (0x2FC5, 'M', u'鹿'),\n    (0x2FC6, 'M', u'麥'),\n    (0x2FC7, 'M', u'麻'),\n    (0x2FC8, 'M', u'黃'),\n    (0x2FC9, 'M', u'黍'),\n    (0x2FCA, 'M', u'黑'),\n    (0x2FCB, 'M', u'黹'),\n    (0x2FCC, 'M', u'黽'),\n    (0x2FCD, 'M', u'鼎'),\n    (0x2FCE, 'M', u'鼓'),\n    (0x2FCF, 'M', u'鼠'),\n    (0x2FD0, 'M', u'鼻'),\n    (0x2FD1, 'M', u'齊'),\n    (0x2FD2, 'M', u'齒'),\n    (0x2FD3, 'M', u'龍'),\n    (0x2FD4, 'M', u'龜'),\n    (0x2FD5, 'M', u'龠'),\n    (0x2FD6, 'X'),\n    (0x3000, '3', u' '),\n    (0x3001, 'V'),\n    (0x3002, 'M', u'.'),\n    (0x3003, 'V'),\n    (0x3036, 'M', u'〒'),\n    (0x3037, 'V'),\n    (0x3038, 'M', u'十'),\n    (0x3039, 'M', u'卄'),\n    (0x303A, 'M', u'卅'),\n    (0x303B, 'V'),\n    (0x3040, 'X'),\n    (0x3041, 'V'),\n    (0x3097, 'X'),\n    (0x3099, 'V'),\n    (0x309B, '3', u' ゙'),\n    (0x309C, '3', u' ゚'),\n    (0x309D, 'V'),\n    (0x309F, 'M', u'より'),\n    (0x30A0, 'V'),\n    (0x30FF, 'M', u'コト'),\n    (0x3100, 'X'),\n    (0x3105, 'V'),\n    (0x3130, 'X'),\n    (0x3131, 'M', u'ᄀ'),\n    (0x3132, 'M', u'ᄁ'),\n    (0x3133, 'M', u'ᆪ'),\n    (0x3134, 'M', u'ᄂ'),\n    (0x3135, 'M', u'ᆬ'),\n    (0x3136, 'M', u'ᆭ'),\n    (0x3137, 'M', u'ᄃ'),\n    (0x3138, 'M', u'ᄄ'),\n    ]\n\ndef _seg_29():\n    return [\n    (0x3139, 'M', u'ᄅ'),\n    (0x313A, 'M', u'ᆰ'),\n    (0x313B, 'M', u'ᆱ'),\n    (0x313C, 'M', u'ᆲ'),\n    (0x313D, 'M', u'ᆳ'),\n    (0x313E, 'M', u'ᆴ'),\n    (0x313F, 'M', u'ᆵ'),\n    (0x3140, 'M', u'ᄚ'),\n    (0x3141, 'M', u'ᄆ'),\n    (0x3142, 'M', u'ᄇ'),\n    (0x3143, 'M', u'ᄈ'),\n    (0x3144, 'M', u'ᄡ'),\n    (0x3145, 'M', u'ᄉ'),\n    (0x3146, 'M', u'ᄊ'),\n    (0x3147, 'M', u'ᄋ'),\n    (0x3148, 'M', u'ᄌ'),\n    (0x3149, 'M', u'ᄍ'),\n    (0x314A, 'M', u'ᄎ'),\n    (0x314B, 'M', u'ᄏ'),\n    (0x314C, 'M', u'ᄐ'),\n    (0x314D, 'M', u'ᄑ'),\n    (0x314E, 'M', u'ᄒ'),\n    (0x314F, 'M', u'ᅡ'),\n    (0x3150, 'M', u'ᅢ'),\n    (0x3151, 'M', u'ᅣ'),\n    (0x3152, 'M', u'ᅤ'),\n    (0x3153, 'M', u'ᅥ'),\n    (0x3154, 'M', u'ᅦ'),\n    (0x3155, 'M', u'ᅧ'),\n    (0x3156, 'M', u'ᅨ'),\n    (0x3157, 'M', u'ᅩ'),\n    (0x3158, 'M', u'ᅪ'),\n    (0x3159, 'M', u'ᅫ'),\n    (0x315A, 'M', u'ᅬ'),\n    (0x315B, 'M', u'ᅭ'),\n    (0x315C, 'M', u'ᅮ'),\n    (0x315D, 'M', u'ᅯ'),\n    (0x315E, 'M', u'ᅰ'),\n    (0x315F, 'M', u'ᅱ'),\n    (0x3160, 'M', u'ᅲ'),\n    (0x3161, 'M', u'ᅳ'),\n    (0x3162, 'M', u'ᅴ'),\n    (0x3163, 'M', u'ᅵ'),\n    (0x3164, 'X'),\n    (0x3165, 'M', u'ᄔ'),\n    (0x3166, 'M', u'ᄕ'),\n    (0x3167, 'M', u'ᇇ'),\n    (0x3168, 'M', u'ᇈ'),\n    (0x3169, 'M', u'ᇌ'),\n    (0x316A, 'M', u'ᇎ'),\n    (0x316B, 'M', u'ᇓ'),\n    (0x316C, 'M', u'ᇗ'),\n    (0x316D, 'M', u'ᇙ'),\n    (0x316E, 'M', u'ᄜ'),\n    (0x316F, 'M', u'ᇝ'),\n    (0x3170, 'M', u'ᇟ'),\n    (0x3171, 'M', u'ᄝ'),\n    (0x3172, 'M', u'ᄞ'),\n    (0x3173, 'M', u'ᄠ'),\n    (0x3174, 'M', u'ᄢ'),\n    (0x3175, 'M', u'ᄣ'),\n    (0x3176, 'M', u'ᄧ'),\n    (0x3177, 'M', u'ᄩ'),\n    (0x3178, 'M', u'ᄫ'),\n    (0x3179, 'M', u'ᄬ'),\n    (0x317A, 'M', u'ᄭ'),\n    (0x317B, 'M', u'ᄮ'),\n    (0x317C, 'M', u'ᄯ'),\n    (0x317D, 'M', u'ᄲ'),\n    (0x317E, 'M', u'ᄶ'),\n    (0x317F, 'M', u'ᅀ'),\n    (0x3180, 'M', u'ᅇ'),\n    (0x3181, 'M', u'ᅌ'),\n    (0x3182, 'M', u'ᇱ'),\n    (0x3183, 'M', u'ᇲ'),\n    (0x3184, 'M', u'ᅗ'),\n    (0x3185, 'M', u'ᅘ'),\n    (0x3186, 'M', u'ᅙ'),\n    (0x3187, 'M', u'ᆄ'),\n    (0x3188, 'M', u'ᆅ'),\n    (0x3189, 'M', u'ᆈ'),\n    (0x318A, 'M', u'ᆑ'),\n    (0x318B, 'M', u'ᆒ'),\n    (0x318C, 'M', u'ᆔ'),\n    (0x318D, 'M', u'ᆞ'),\n    (0x318E, 'M', u'ᆡ'),\n    (0x318F, 'X'),\n    (0x3190, 'V'),\n    (0x3192, 'M', u'一'),\n    (0x3193, 'M', u'二'),\n    (0x3194, 'M', u'三'),\n    (0x3195, 'M', u'四'),\n    (0x3196, 'M', u'上'),\n    (0x3197, 'M', u'中'),\n    (0x3198, 'M', u'下'),\n    (0x3199, 'M', u'甲'),\n    (0x319A, 'M', u'乙'),\n    (0x319B, 'M', u'丙'),\n    (0x319C, 'M', u'丁'),\n    (0x319D, 'M', u'天'),\n    ]\n\ndef _seg_30():\n    return [\n    (0x319E, 'M', u'地'),\n    (0x319F, 'M', u'人'),\n    (0x31A0, 'V'),\n    (0x31BB, 'X'),\n    (0x31C0, 'V'),\n    (0x31E4, 'X'),\n    (0x31F0, 'V'),\n    (0x3200, '3', u'(ᄀ)'),\n    (0x3201, '3', u'(ᄂ)'),\n    (0x3202, '3', u'(ᄃ)'),\n    (0x3203, '3', u'(ᄅ)'),\n    (0x3204, '3', u'(ᄆ)'),\n    (0x3205, '3', u'(ᄇ)'),\n    (0x3206, '3', u'(ᄉ)'),\n    (0x3207, '3', u'(ᄋ)'),\n    (0x3208, '3', u'(ᄌ)'),\n    (0x3209, '3', u'(ᄎ)'),\n    (0x320A, '3', u'(ᄏ)'),\n    (0x320B, '3', u'(ᄐ)'),\n    (0x320C, '3', u'(ᄑ)'),\n    (0x320D, '3', u'(ᄒ)'),\n    (0x320E, '3', u'(가)'),\n    (0x320F, '3', u'(나)'),\n    (0x3210, '3', u'(다)'),\n    (0x3211, '3', u'(라)'),\n    (0x3212, '3', u'(마)'),\n    (0x3213, '3', u'(바)'),\n    (0x3214, '3', u'(사)'),\n    (0x3215, '3', u'(아)'),\n    (0x3216, '3', u'(자)'),\n    (0x3217, '3', u'(차)'),\n    (0x3218, '3', u'(카)'),\n    (0x3219, '3', u'(타)'),\n    (0x321A, '3', u'(파)'),\n    (0x321B, '3', u'(하)'),\n    (0x321C, '3', u'(주)'),\n    (0x321D, '3', u'(오전)'),\n    (0x321E, '3', u'(오후)'),\n    (0x321F, 'X'),\n    (0x3220, '3', u'(一)'),\n    (0x3221, '3', u'(二)'),\n    (0x3222, '3', u'(三)'),\n    (0x3223, '3', u'(四)'),\n    (0x3224, '3', u'(五)'),\n    (0x3225, '3', u'(六)'),\n    (0x3226, '3', u'(七)'),\n    (0x3227, '3', u'(八)'),\n    (0x3228, '3', u'(九)'),\n    (0x3229, '3', u'(十)'),\n    (0x322A, '3', u'(月)'),\n    (0x322B, '3', u'(火)'),\n    (0x322C, '3', u'(水)'),\n    (0x322D, '3', u'(木)'),\n    (0x322E, '3', u'(金)'),\n    (0x322F, '3', u'(土)'),\n    (0x3230, '3', u'(日)'),\n    (0x3231, '3', u'(株)'),\n    (0x3232, '3', u'(有)'),\n    (0x3233, '3', u'(社)'),\n    (0x3234, '3', u'(名)'),\n    (0x3235, '3', u'(特)'),\n    (0x3236, '3', u'(財)'),\n    (0x3237, '3', u'(祝)'),\n    (0x3238, '3', u'(労)'),\n    (0x3239, '3', u'(代)'),\n    (0x323A, '3', u'(呼)'),\n    (0x323B, '3', u'(学)'),\n    (0x323C, '3', u'(監)'),\n    (0x323D, '3', u'(企)'),\n    (0x323E, '3', u'(資)'),\n    (0x323F, '3', u'(協)'),\n    (0x3240, '3', u'(祭)'),\n    (0x3241, '3', u'(休)'),\n    (0x3242, '3', u'(自)'),\n    (0x3243, '3', u'(至)'),\n    (0x3244, 'M', u'問'),\n    (0x3245, 'M', u'幼'),\n    (0x3246, 'M', u'文'),\n    (0x3247, 'M', u'箏'),\n    (0x3248, 'V'),\n    (0x3250, 'M', u'pte'),\n    (0x3251, 'M', u'21'),\n    (0x3252, 'M', u'22'),\n    (0x3253, 'M', u'23'),\n    (0x3254, 'M', u'24'),\n    (0x3255, 'M', u'25'),\n    (0x3256, 'M', u'26'),\n    (0x3257, 'M', u'27'),\n    (0x3258, 'M', u'28'),\n    (0x3259, 'M', u'29'),\n    (0x325A, 'M', u'30'),\n    (0x325B, 'M', u'31'),\n    (0x325C, 'M', u'32'),\n    (0x325D, 'M', u'33'),\n    (0x325E, 'M', u'34'),\n    (0x325F, 'M', u'35'),\n    (0x3260, 'M', u'ᄀ'),\n    (0x3261, 'M', u'ᄂ'),\n    (0x3262, 'M', u'ᄃ'),\n    (0x3263, 'M', u'ᄅ'),\n    ]\n\ndef _seg_31():\n    return [\n    (0x3264, 'M', u'ᄆ'),\n    (0x3265, 'M', u'ᄇ'),\n    (0x3266, 'M', u'ᄉ'),\n    (0x3267, 'M', u'ᄋ'),\n    (0x3268, 'M', u'ᄌ'),\n    (0x3269, 'M', u'ᄎ'),\n    (0x326A, 'M', u'ᄏ'),\n    (0x326B, 'M', u'ᄐ'),\n    (0x326C, 'M', u'ᄑ'),\n    (0x326D, 'M', u'ᄒ'),\n    (0x326E, 'M', u'가'),\n    (0x326F, 'M', u'나'),\n    (0x3270, 'M', u'다'),\n    (0x3271, 'M', u'라'),\n    (0x3272, 'M', u'마'),\n    (0x3273, 'M', u'바'),\n    (0x3274, 'M', u'사'),\n    (0x3275, 'M', u'아'),\n    (0x3276, 'M', u'자'),\n    (0x3277, 'M', u'차'),\n    (0x3278, 'M', u'카'),\n    (0x3279, 'M', u'타'),\n    (0x327A, 'M', u'파'),\n    (0x327B, 'M', u'하'),\n    (0x327C, 'M', u'참고'),\n    (0x327D, 'M', u'주의'),\n    (0x327E, 'M', u'우'),\n    (0x327F, 'V'),\n    (0x3280, 'M', u'一'),\n    (0x3281, 'M', u'二'),\n    (0x3282, 'M', u'三'),\n    (0x3283, 'M', u'四'),\n    (0x3284, 'M', u'五'),\n    (0x3285, 'M', u'六'),\n    (0x3286, 'M', u'七'),\n    (0x3287, 'M', u'八'),\n    (0x3288, 'M', u'九'),\n    (0x3289, 'M', u'十'),\n    (0x328A, 'M', u'月'),\n    (0x328B, 'M', u'火'),\n    (0x328C, 'M', u'水'),\n    (0x328D, 'M', u'木'),\n    (0x328E, 'M', u'金'),\n    (0x328F, 'M', u'土'),\n    (0x3290, 'M', u'日'),\n    (0x3291, 'M', u'株'),\n    (0x3292, 'M', u'有'),\n    (0x3293, 'M', u'社'),\n    (0x3294, 'M', u'名'),\n    (0x3295, 'M', u'特'),\n    (0x3296, 'M', u'財'),\n    (0x3297, 'M', u'祝'),\n    (0x3298, 'M', u'労'),\n    (0x3299, 'M', u'秘'),\n    (0x329A, 'M', u'男'),\n    (0x329B, 'M', u'女'),\n    (0x329C, 'M', u'適'),\n    (0x329D, 'M', u'優'),\n    (0x329E, 'M', u'印'),\n    (0x329F, 'M', u'注'),\n    (0x32A0, 'M', u'項'),\n    (0x32A1, 'M', u'休'),\n    (0x32A2, 'M', u'写'),\n    (0x32A3, 'M', u'正'),\n    (0x32A4, 'M', u'上'),\n    (0x32A5, 'M', u'中'),\n    (0x32A6, 'M', u'下'),\n    (0x32A7, 'M', u'左'),\n    (0x32A8, 'M', u'右'),\n    (0x32A9, 'M', u'医'),\n    (0x32AA, 'M', u'宗'),\n    (0x32AB, 'M', u'学'),\n    (0x32AC, 'M', u'監'),\n    (0x32AD, 'M', u'企'),\n    (0x32AE, 'M', u'資'),\n    (0x32AF, 'M', u'協'),\n    (0x32B0, 'M', u'夜'),\n    (0x32B1, 'M', u'36'),\n    (0x32B2, 'M', u'37'),\n    (0x32B3, 'M', u'38'),\n    (0x32B4, 'M', u'39'),\n    (0x32B5, 'M', u'40'),\n    (0x32B6, 'M', u'41'),\n    (0x32B7, 'M', u'42'),\n    (0x32B8, 'M', u'43'),\n    (0x32B9, 'M', u'44'),\n    (0x32BA, 'M', u'45'),\n    (0x32BB, 'M', u'46'),\n    (0x32BC, 'M', u'47'),\n    (0x32BD, 'M', u'48'),\n    (0x32BE, 'M', u'49'),\n    (0x32BF, 'M', u'50'),\n    (0x32C0, 'M', u'1月'),\n    (0x32C1, 'M', u'2月'),\n    (0x32C2, 'M', u'3月'),\n    (0x32C3, 'M', u'4月'),\n    (0x32C4, 'M', u'5月'),\n    (0x32C5, 'M', u'6月'),\n    (0x32C6, 'M', u'7月'),\n    (0x32C7, 'M', u'8月'),\n    ]\n\ndef _seg_32():\n    return [\n    (0x32C8, 'M', u'9月'),\n    (0x32C9, 'M', u'10月'),\n    (0x32CA, 'M', u'11月'),\n    (0x32CB, 'M', u'12月'),\n    (0x32CC, 'M', u'hg'),\n    (0x32CD, 'M', u'erg'),\n    (0x32CE, 'M', u'ev'),\n    (0x32CF, 'M', u'ltd'),\n    (0x32D0, 'M', u'ア'),\n    (0x32D1, 'M', u'イ'),\n    (0x32D2, 'M', u'ウ'),\n    (0x32D3, 'M', u'エ'),\n    (0x32D4, 'M', u'オ'),\n    (0x32D5, 'M', u'カ'),\n    (0x32D6, 'M', u'キ'),\n    (0x32D7, 'M', u'ク'),\n    (0x32D8, 'M', u'ケ'),\n    (0x32D9, 'M', u'コ'),\n    (0x32DA, 'M', u'サ'),\n    (0x32DB, 'M', u'シ'),\n    (0x32DC, 'M', u'ス'),\n    (0x32DD, 'M', u'セ'),\n    (0x32DE, 'M', u'ソ'),\n    (0x32DF, 'M', u'タ'),\n    (0x32E0, 'M', u'チ'),\n    (0x32E1, 'M', u'ツ'),\n    (0x32E2, 'M', u'テ'),\n    (0x32E3, 'M', u'ト'),\n    (0x32E4, 'M', u'ナ'),\n    (0x32E5, 'M', u'ニ'),\n    (0x32E6, 'M', u'ヌ'),\n    (0x32E7, 'M', u'ネ'),\n    (0x32E8, 'M', u'ノ'),\n    (0x32E9, 'M', u'ハ'),\n    (0x32EA, 'M', u'ヒ'),\n    (0x32EB, 'M', u'フ'),\n    (0x32EC, 'M', u'ヘ'),\n    (0x32ED, 'M', u'ホ'),\n    (0x32EE, 'M', u'マ'),\n    (0x32EF, 'M', u'ミ'),\n    (0x32F0, 'M', u'ム'),\n    (0x32F1, 'M', u'メ'),\n    (0x32F2, 'M', u'モ'),\n    (0x32F3, 'M', u'ヤ'),\n    (0x32F4, 'M', u'ユ'),\n    (0x32F5, 'M', u'ヨ'),\n    (0x32F6, 'M', u'ラ'),\n    (0x32F7, 'M', u'リ'),\n    (0x32F8, 'M', u'ル'),\n    (0x32F9, 'M', u'レ'),\n    (0x32FA, 'M', u'ロ'),\n    (0x32FB, 'M', u'ワ'),\n    (0x32FC, 'M', u'ヰ'),\n    (0x32FD, 'M', u'ヱ'),\n    (0x32FE, 'M', u'ヲ'),\n    (0x32FF, 'X'),\n    (0x3300, 'M', u'アパート'),\n    (0x3301, 'M', u'アルファ'),\n    (0x3302, 'M', u'アンペア'),\n    (0x3303, 'M', u'アール'),\n    (0x3304, 'M', u'イニング'),\n    (0x3305, 'M', u'インチ'),\n    (0x3306, 'M', u'ウォン'),\n    (0x3307, 'M', u'エスクード'),\n    (0x3308, 'M', u'エーカー'),\n    (0x3309, 'M', u'オンス'),\n    (0x330A, 'M', u'オーム'),\n    (0x330B, 'M', u'カイリ'),\n    (0x330C, 'M', u'カラット'),\n    (0x330D, 'M', u'カロリー'),\n    (0x330E, 'M', u'ガロン'),\n    (0x330F, 'M', u'ガンマ'),\n    (0x3310, 'M', u'ギガ'),\n    (0x3311, 'M', u'ギニー'),\n    (0x3312, 'M', u'キュリー'),\n    (0x3313, 'M', u'ギルダー'),\n    (0x3314, 'M', u'キロ'),\n    (0x3315, 'M', u'キログラム'),\n    (0x3316, 'M', u'キロメートル'),\n    (0x3317, 'M', u'キロワット'),\n    (0x3318, 'M', u'グラム'),\n    (0x3319, 'M', u'グラムトン'),\n    (0x331A, 'M', u'クルゼイロ'),\n    (0x331B, 'M', u'クローネ'),\n    (0x331C, 'M', u'ケース'),\n    (0x331D, 'M', u'コルナ'),\n    (0x331E, 'M', u'コーポ'),\n    (0x331F, 'M', u'サイクル'),\n    (0x3320, 'M', u'サンチーム'),\n    (0x3321, 'M', u'シリング'),\n    (0x3322, 'M', u'センチ'),\n    (0x3323, 'M', u'セント'),\n    (0x3324, 'M', u'ダース'),\n    (0x3325, 'M', u'デシ'),\n    (0x3326, 'M', u'ドル'),\n    (0x3327, 'M', u'トン'),\n    (0x3328, 'M', u'ナノ'),\n    (0x3329, 'M', u'ノット'),\n    (0x332A, 'M', u'ハイツ'),\n    (0x332B, 'M', u'パーセント'),\n    ]\n\ndef _seg_33():\n    return [\n    (0x332C, 'M', u'パーツ'),\n    (0x332D, 'M', u'バーレル'),\n    (0x332E, 'M', u'ピアストル'),\n    (0x332F, 'M', u'ピクル'),\n    (0x3330, 'M', u'ピコ'),\n    (0x3331, 'M', u'ビル'),\n    (0x3332, 'M', u'ファラッド'),\n    (0x3333, 'M', u'フィート'),\n    (0x3334, 'M', u'ブッシェル'),\n    (0x3335, 'M', u'フラン'),\n    (0x3336, 'M', u'ヘクタール'),\n    (0x3337, 'M', u'ペソ'),\n    (0x3338, 'M', u'ペニヒ'),\n    (0x3339, 'M', u'ヘルツ'),\n    (0x333A, 'M', u'ペンス'),\n    (0x333B, 'M', u'ページ'),\n    (0x333C, 'M', u'ベータ'),\n    (0x333D, 'M', u'ポイント'),\n    (0x333E, 'M', u'ボルト'),\n    (0x333F, 'M', u'ホン'),\n    (0x3340, 'M', u'ポンド'),\n    (0x3341, 'M', u'ホール'),\n    (0x3342, 'M', u'ホーン'),\n    (0x3343, 'M', u'マイクロ'),\n    (0x3344, 'M', u'マイル'),\n    (0x3345, 'M', u'マッハ'),\n    (0x3346, 'M', u'マルク'),\n    (0x3347, 'M', u'マンション'),\n    (0x3348, 'M', u'ミクロン'),\n    (0x3349, 'M', u'ミリ'),\n    (0x334A, 'M', u'ミリバール'),\n    (0x334B, 'M', u'メガ'),\n    (0x334C, 'M', u'メガトン'),\n    (0x334D, 'M', u'メートル'),\n    (0x334E, 'M', u'ヤード'),\n    (0x334F, 'M', u'ヤール'),\n    (0x3350, 'M', u'ユアン'),\n    (0x3351, 'M', u'リットル'),\n    (0x3352, 'M', u'リラ'),\n    (0x3353, 'M', u'ルピー'),\n    (0x3354, 'M', u'ルーブル'),\n    (0x3355, 'M', u'レム'),\n    (0x3356, 'M', u'レントゲン'),\n    (0x3357, 'M', u'ワット'),\n    (0x3358, 'M', u'0点'),\n    (0x3359, 'M', u'1点'),\n    (0x335A, 'M', u'2点'),\n    (0x335B, 'M', u'3点'),\n    (0x335C, 'M', u'4点'),\n    (0x335D, 'M', u'5点'),\n    (0x335E, 'M', u'6点'),\n    (0x335F, 'M', u'7点'),\n    (0x3360, 'M', u'8点'),\n    (0x3361, 'M', u'9点'),\n    (0x3362, 'M', u'10点'),\n    (0x3363, 'M', u'11点'),\n    (0x3364, 'M', u'12点'),\n    (0x3365, 'M', u'13点'),\n    (0x3366, 'M', u'14点'),\n    (0x3367, 'M', u'15点'),\n    (0x3368, 'M', u'16点'),\n    (0x3369, 'M', u'17点'),\n    (0x336A, 'M', u'18点'),\n    (0x336B, 'M', u'19点'),\n    (0x336C, 'M', u'20点'),\n    (0x336D, 'M', u'21点'),\n    (0x336E, 'M', u'22点'),\n    (0x336F, 'M', u'23点'),\n    (0x3370, 'M', u'24点'),\n    (0x3371, 'M', u'hpa'),\n    (0x3372, 'M', u'da'),\n    (0x3373, 'M', u'au'),\n    (0x3374, 'M', u'bar'),\n    (0x3375, 'M', u'ov'),\n    (0x3376, 'M', u'pc'),\n    (0x3377, 'M', u'dm'),\n    (0x3378, 'M', u'dm2'),\n    (0x3379, 'M', u'dm3'),\n    (0x337A, 'M', u'iu'),\n    (0x337B, 'M', u'平成'),\n    (0x337C, 'M', u'昭和'),\n    (0x337D, 'M', u'大正'),\n    (0x337E, 'M', u'明治'),\n    (0x337F, 'M', u'株式会社'),\n    (0x3380, 'M', u'pa'),\n    (0x3381, 'M', u'na'),\n    (0x3382, 'M', u'μa'),\n    (0x3383, 'M', u'ma'),\n    (0x3384, 'M', u'ka'),\n    (0x3385, 'M', u'kb'),\n    (0x3386, 'M', u'mb'),\n    (0x3387, 'M', u'gb'),\n    (0x3388, 'M', u'cal'),\n    (0x3389, 'M', u'kcal'),\n    (0x338A, 'M', u'pf'),\n    (0x338B, 'M', u'nf'),\n    (0x338C, 'M', u'μf'),\n    (0x338D, 'M', u'μg'),\n    (0x338E, 'M', u'mg'),\n    (0x338F, 'M', u'kg'),\n    ]\n\ndef _seg_34():\n    return [\n    (0x3390, 'M', u'hz'),\n    (0x3391, 'M', u'khz'),\n    (0x3392, 'M', u'mhz'),\n    (0x3393, 'M', u'ghz'),\n    (0x3394, 'M', u'thz'),\n    (0x3395, 'M', u'μl'),\n    (0x3396, 'M', u'ml'),\n    (0x3397, 'M', u'dl'),\n    (0x3398, 'M', u'kl'),\n    (0x3399, 'M', u'fm'),\n    (0x339A, 'M', u'nm'),\n    (0x339B, 'M', u'μm'),\n    (0x339C, 'M', u'mm'),\n    (0x339D, 'M', u'cm'),\n    (0x339E, 'M', u'km'),\n    (0x339F, 'M', u'mm2'),\n    (0x33A0, 'M', u'cm2'),\n    (0x33A1, 'M', u'm2'),\n    (0x33A2, 'M', u'km2'),\n    (0x33A3, 'M', u'mm3'),\n    (0x33A4, 'M', u'cm3'),\n    (0x33A5, 'M', u'm3'),\n    (0x33A6, 'M', u'km3'),\n    (0x33A7, 'M', u'm∕s'),\n    (0x33A8, 'M', u'm∕s2'),\n    (0x33A9, 'M', u'pa'),\n    (0x33AA, 'M', u'kpa'),\n    (0x33AB, 'M', u'mpa'),\n    (0x33AC, 'M', u'gpa'),\n    (0x33AD, 'M', u'rad'),\n    (0x33AE, 'M', u'rad∕s'),\n    (0x33AF, 'M', u'rad∕s2'),\n    (0x33B0, 'M', u'ps'),\n    (0x33B1, 'M', u'ns'),\n    (0x33B2, 'M', u'μs'),\n    (0x33B3, 'M', u'ms'),\n    (0x33B4, 'M', u'pv'),\n    (0x33B5, 'M', u'nv'),\n    (0x33B6, 'M', u'μv'),\n    (0x33B7, 'M', u'mv'),\n    (0x33B8, 'M', u'kv'),\n    (0x33B9, 'M', u'mv'),\n    (0x33BA, 'M', u'pw'),\n    (0x33BB, 'M', u'nw'),\n    (0x33BC, 'M', u'μw'),\n    (0x33BD, 'M', u'mw'),\n    (0x33BE, 'M', u'kw'),\n    (0x33BF, 'M', u'mw'),\n    (0x33C0, 'M', u'kω'),\n    (0x33C1, 'M', u'mω'),\n    (0x33C2, 'X'),\n    (0x33C3, 'M', u'bq'),\n    (0x33C4, 'M', u'cc'),\n    (0x33C5, 'M', u'cd'),\n    (0x33C6, 'M', u'c∕kg'),\n    (0x33C7, 'X'),\n    (0x33C8, 'M', u'db'),\n    (0x33C9, 'M', u'gy'),\n    (0x33CA, 'M', u'ha'),\n    (0x33CB, 'M', u'hp'),\n    (0x33CC, 'M', u'in'),\n    (0x33CD, 'M', u'kk'),\n    (0x33CE, 'M', u'km'),\n    (0x33CF, 'M', u'kt'),\n    (0x33D0, 'M', u'lm'),\n    (0x33D1, 'M', u'ln'),\n    (0x33D2, 'M', u'log'),\n    (0x33D3, 'M', u'lx'),\n    (0x33D4, 'M', u'mb'),\n    (0x33D5, 'M', u'mil'),\n    (0x33D6, 'M', u'mol'),\n    (0x33D7, 'M', u'ph'),\n    (0x33D8, 'X'),\n    (0x33D9, 'M', u'ppm'),\n    (0x33DA, 'M', u'pr'),\n    (0x33DB, 'M', u'sr'),\n    (0x33DC, 'M', u'sv'),\n    (0x33DD, 'M', u'wb'),\n    (0x33DE, 'M', u'v∕m'),\n    (0x33DF, 'M', u'a∕m'),\n    (0x33E0, 'M', u'1日'),\n    (0x33E1, 'M', u'2日'),\n    (0x33E2, 'M', u'3日'),\n    (0x33E3, 'M', u'4日'),\n    (0x33E4, 'M', u'5日'),\n    (0x33E5, 'M', u'6日'),\n    (0x33E6, 'M', u'7日'),\n    (0x33E7, 'M', u'8日'),\n    (0x33E8, 'M', u'9日'),\n    (0x33E9, 'M', u'10日'),\n    (0x33EA, 'M', u'11日'),\n    (0x33EB, 'M', u'12日'),\n    (0x33EC, 'M', u'13日'),\n    (0x33ED, 'M', u'14日'),\n    (0x33EE, 'M', u'15日'),\n    (0x33EF, 'M', u'16日'),\n    (0x33F0, 'M', u'17日'),\n    (0x33F1, 'M', u'18日'),\n    (0x33F2, 'M', u'19日'),\n    (0x33F3, 'M', u'20日'),\n    ]\n\ndef _seg_35():\n    return [\n    (0x33F4, 'M', u'21日'),\n    (0x33F5, 'M', u'22日'),\n    (0x33F6, 'M', u'23日'),\n    (0x33F7, 'M', u'24日'),\n    (0x33F8, 'M', u'25日'),\n    (0x33F9, 'M', u'26日'),\n    (0x33FA, 'M', u'27日'),\n    (0x33FB, 'M', u'28日'),\n    (0x33FC, 'M', u'29日'),\n    (0x33FD, 'M', u'30日'),\n    (0x33FE, 'M', u'31日'),\n    (0x33FF, 'M', u'gal'),\n    (0x3400, 'V'),\n    (0x4DB6, 'X'),\n    (0x4DC0, 'V'),\n    (0x9FF0, 'X'),\n    (0xA000, 'V'),\n    (0xA48D, 'X'),\n    (0xA490, 'V'),\n    (0xA4C7, 'X'),\n    (0xA4D0, 'V'),\n    (0xA62C, 'X'),\n    (0xA640, 'M', u'ꙁ'),\n    (0xA641, 'V'),\n    (0xA642, 'M', u'ꙃ'),\n    (0xA643, 'V'),\n    (0xA644, 'M', u'ꙅ'),\n    (0xA645, 'V'),\n    (0xA646, 'M', u'ꙇ'),\n    (0xA647, 'V'),\n    (0xA648, 'M', u'ꙉ'),\n    (0xA649, 'V'),\n    (0xA64A, 'M', u'ꙋ'),\n    (0xA64B, 'V'),\n    (0xA64C, 'M', u'ꙍ'),\n    (0xA64D, 'V'),\n    (0xA64E, 'M', u'ꙏ'),\n    (0xA64F, 'V'),\n    (0xA650, 'M', u'ꙑ'),\n    (0xA651, 'V'),\n    (0xA652, 'M', u'ꙓ'),\n    (0xA653, 'V'),\n    (0xA654, 'M', u'ꙕ'),\n    (0xA655, 'V'),\n    (0xA656, 'M', u'ꙗ'),\n    (0xA657, 'V'),\n    (0xA658, 'M', u'ꙙ'),\n    (0xA659, 'V'),\n    (0xA65A, 'M', u'ꙛ'),\n    (0xA65B, 'V'),\n    (0xA65C, 'M', u'ꙝ'),\n    (0xA65D, 'V'),\n    (0xA65E, 'M', u'ꙟ'),\n    (0xA65F, 'V'),\n    (0xA660, 'M', u'ꙡ'),\n    (0xA661, 'V'),\n    (0xA662, 'M', u'ꙣ'),\n    (0xA663, 'V'),\n    (0xA664, 'M', u'ꙥ'),\n    (0xA665, 'V'),\n    (0xA666, 'M', u'ꙧ'),\n    (0xA667, 'V'),\n    (0xA668, 'M', u'ꙩ'),\n    (0xA669, 'V'),\n    (0xA66A, 'M', u'ꙫ'),\n    (0xA66B, 'V'),\n    (0xA66C, 'M', u'ꙭ'),\n    (0xA66D, 'V'),\n    (0xA680, 'M', u'ꚁ'),\n    (0xA681, 'V'),\n    (0xA682, 'M', u'ꚃ'),\n    (0xA683, 'V'),\n    (0xA684, 'M', u'ꚅ'),\n    (0xA685, 'V'),\n    (0xA686, 'M', u'ꚇ'),\n    (0xA687, 'V'),\n    (0xA688, 'M', u'ꚉ'),\n    (0xA689, 'V'),\n    (0xA68A, 'M', u'ꚋ'),\n    (0xA68B, 'V'),\n    (0xA68C, 'M', u'ꚍ'),\n    (0xA68D, 'V'),\n    (0xA68E, 'M', u'ꚏ'),\n    (0xA68F, 'V'),\n    (0xA690, 'M', u'ꚑ'),\n    (0xA691, 'V'),\n    (0xA692, 'M', u'ꚓ'),\n    (0xA693, 'V'),\n    (0xA694, 'M', u'ꚕ'),\n    (0xA695, 'V'),\n    (0xA696, 'M', u'ꚗ'),\n    (0xA697, 'V'),\n    (0xA698, 'M', u'ꚙ'),\n    (0xA699, 'V'),\n    (0xA69A, 'M', u'ꚛ'),\n    (0xA69B, 'V'),\n    (0xA69C, 'M', u'ъ'),\n    (0xA69D, 'M', u'ь'),\n    (0xA69E, 'V'),\n    (0xA6F8, 'X'),\n    ]\n\ndef _seg_36():\n    return [\n    (0xA700, 'V'),\n    (0xA722, 'M', u'ꜣ'),\n    (0xA723, 'V'),\n    (0xA724, 'M', u'ꜥ'),\n    (0xA725, 'V'),\n    (0xA726, 'M', u'ꜧ'),\n    (0xA727, 'V'),\n    (0xA728, 'M', u'ꜩ'),\n    (0xA729, 'V'),\n    (0xA72A, 'M', u'ꜫ'),\n    (0xA72B, 'V'),\n    (0xA72C, 'M', u'ꜭ'),\n    (0xA72D, 'V'),\n    (0xA72E, 'M', u'ꜯ'),\n    (0xA72F, 'V'),\n    (0xA732, 'M', u'ꜳ'),\n    (0xA733, 'V'),\n    (0xA734, 'M', u'ꜵ'),\n    (0xA735, 'V'),\n    (0xA736, 'M', u'ꜷ'),\n    (0xA737, 'V'),\n    (0xA738, 'M', u'ꜹ'),\n    (0xA739, 'V'),\n    (0xA73A, 'M', u'ꜻ'),\n    (0xA73B, 'V'),\n    (0xA73C, 'M', u'ꜽ'),\n    (0xA73D, 'V'),\n    (0xA73E, 'M', u'ꜿ'),\n    (0xA73F, 'V'),\n    (0xA740, 'M', u'ꝁ'),\n    (0xA741, 'V'),\n    (0xA742, 'M', u'ꝃ'),\n    (0xA743, 'V'),\n    (0xA744, 'M', u'ꝅ'),\n    (0xA745, 'V'),\n    (0xA746, 'M', u'ꝇ'),\n    (0xA747, 'V'),\n    (0xA748, 'M', u'ꝉ'),\n    (0xA749, 'V'),\n    (0xA74A, 'M', u'ꝋ'),\n    (0xA74B, 'V'),\n    (0xA74C, 'M', u'ꝍ'),\n    (0xA74D, 'V'),\n    (0xA74E, 'M', u'ꝏ'),\n    (0xA74F, 'V'),\n    (0xA750, 'M', u'ꝑ'),\n    (0xA751, 'V'),\n    (0xA752, 'M', u'ꝓ'),\n    (0xA753, 'V'),\n    (0xA754, 'M', u'ꝕ'),\n    (0xA755, 'V'),\n    (0xA756, 'M', u'ꝗ'),\n    (0xA757, 'V'),\n    (0xA758, 'M', u'ꝙ'),\n    (0xA759, 'V'),\n    (0xA75A, 'M', u'ꝛ'),\n    (0xA75B, 'V'),\n    (0xA75C, 'M', u'ꝝ'),\n    (0xA75D, 'V'),\n    (0xA75E, 'M', u'ꝟ'),\n    (0xA75F, 'V'),\n    (0xA760, 'M', u'ꝡ'),\n    (0xA761, 'V'),\n    (0xA762, 'M', u'ꝣ'),\n    (0xA763, 'V'),\n    (0xA764, 'M', u'ꝥ'),\n    (0xA765, 'V'),\n    (0xA766, 'M', u'ꝧ'),\n    (0xA767, 'V'),\n    (0xA768, 'M', u'ꝩ'),\n    (0xA769, 'V'),\n    (0xA76A, 'M', u'ꝫ'),\n    (0xA76B, 'V'),\n    (0xA76C, 'M', u'ꝭ'),\n    (0xA76D, 'V'),\n    (0xA76E, 'M', u'ꝯ'),\n    (0xA76F, 'V'),\n    (0xA770, 'M', u'ꝯ'),\n    (0xA771, 'V'),\n    (0xA779, 'M', u'ꝺ'),\n    (0xA77A, 'V'),\n    (0xA77B, 'M', u'ꝼ'),\n    (0xA77C, 'V'),\n    (0xA77D, 'M', u'ᵹ'),\n    (0xA77E, 'M', u'ꝿ'),\n    (0xA77F, 'V'),\n    (0xA780, 'M', u'ꞁ'),\n    (0xA781, 'V'),\n    (0xA782, 'M', u'ꞃ'),\n    (0xA783, 'V'),\n    (0xA784, 'M', u'ꞅ'),\n    (0xA785, 'V'),\n    (0xA786, 'M', u'ꞇ'),\n    (0xA787, 'V'),\n    (0xA78B, 'M', u'ꞌ'),\n    (0xA78C, 'V'),\n    (0xA78D, 'M', u'ɥ'),\n    (0xA78E, 'V'),\n    (0xA790, 'M', u'ꞑ'),\n    (0xA791, 'V'),\n    ]\n\ndef _seg_37():\n    return [\n    (0xA792, 'M', u'ꞓ'),\n    (0xA793, 'V'),\n    (0xA796, 'M', u'ꞗ'),\n    (0xA797, 'V'),\n    (0xA798, 'M', u'ꞙ'),\n    (0xA799, 'V'),\n    (0xA79A, 'M', u'ꞛ'),\n    (0xA79B, 'V'),\n    (0xA79C, 'M', u'ꞝ'),\n    (0xA79D, 'V'),\n    (0xA79E, 'M', u'ꞟ'),\n    (0xA79F, 'V'),\n    (0xA7A0, 'M', u'ꞡ'),\n    (0xA7A1, 'V'),\n    (0xA7A2, 'M', u'ꞣ'),\n    (0xA7A3, 'V'),\n    (0xA7A4, 'M', u'ꞥ'),\n    (0xA7A5, 'V'),\n    (0xA7A6, 'M', u'ꞧ'),\n    (0xA7A7, 'V'),\n    (0xA7A8, 'M', u'ꞩ'),\n    (0xA7A9, 'V'),\n    (0xA7AA, 'M', u'ɦ'),\n    (0xA7AB, 'M', u'ɜ'),\n    (0xA7AC, 'M', u'ɡ'),\n    (0xA7AD, 'M', u'ɬ'),\n    (0xA7AE, 'M', u'ɪ'),\n    (0xA7AF, 'V'),\n    (0xA7B0, 'M', u'ʞ'),\n    (0xA7B1, 'M', u'ʇ'),\n    (0xA7B2, 'M', u'ʝ'),\n    (0xA7B3, 'M', u'ꭓ'),\n    (0xA7B4, 'M', u'ꞵ'),\n    (0xA7B5, 'V'),\n    (0xA7B6, 'M', u'ꞷ'),\n    (0xA7B7, 'V'),\n    (0xA7B8, 'X'),\n    (0xA7B9, 'V'),\n    (0xA7BA, 'X'),\n    (0xA7F7, 'V'),\n    (0xA7F8, 'M', u'ħ'),\n    (0xA7F9, 'M', u'œ'),\n    (0xA7FA, 'V'),\n    (0xA82C, 'X'),\n    (0xA830, 'V'),\n    (0xA83A, 'X'),\n    (0xA840, 'V'),\n    (0xA878, 'X'),\n    (0xA880, 'V'),\n    (0xA8C6, 'X'),\n    (0xA8CE, 'V'),\n    (0xA8DA, 'X'),\n    (0xA8E0, 'V'),\n    (0xA954, 'X'),\n    (0xA95F, 'V'),\n    (0xA97D, 'X'),\n    (0xA980, 'V'),\n    (0xA9CE, 'X'),\n    (0xA9CF, 'V'),\n    (0xA9DA, 'X'),\n    (0xA9DE, 'V'),\n    (0xA9FF, 'X'),\n    (0xAA00, 'V'),\n    (0xAA37, 'X'),\n    (0xAA40, 'V'),\n    (0xAA4E, 'X'),\n    (0xAA50, 'V'),\n    (0xAA5A, 'X'),\n    (0xAA5C, 'V'),\n    (0xAAC3, 'X'),\n    (0xAADB, 'V'),\n    (0xAAF7, 'X'),\n    (0xAB01, 'V'),\n    (0xAB07, 'X'),\n    (0xAB09, 'V'),\n    (0xAB0F, 'X'),\n    (0xAB11, 'V'),\n    (0xAB17, 'X'),\n    (0xAB20, 'V'),\n    (0xAB27, 'X'),\n    (0xAB28, 'V'),\n    (0xAB2F, 'X'),\n    (0xAB30, 'V'),\n    (0xAB5C, 'M', u'ꜧ'),\n    (0xAB5D, 'M', u'ꬷ'),\n    (0xAB5E, 'M', u'ɫ'),\n    (0xAB5F, 'M', u'ꭒ'),\n    (0xAB60, 'V'),\n    (0xAB66, 'X'),\n    (0xAB70, 'M', u'Ꭰ'),\n    (0xAB71, 'M', u'Ꭱ'),\n    (0xAB72, 'M', u'Ꭲ'),\n    (0xAB73, 'M', u'Ꭳ'),\n    (0xAB74, 'M', u'Ꭴ'),\n    (0xAB75, 'M', u'Ꭵ'),\n    (0xAB76, 'M', u'Ꭶ'),\n    (0xAB77, 'M', u'Ꭷ'),\n    (0xAB78, 'M', u'Ꭸ'),\n    (0xAB79, 'M', u'Ꭹ'),\n    (0xAB7A, 'M', u'Ꭺ'),\n    ]\n\ndef _seg_38():\n    return [\n    (0xAB7B, 'M', u'Ꭻ'),\n    (0xAB7C, 'M', u'Ꭼ'),\n    (0xAB7D, 'M', u'Ꭽ'),\n    (0xAB7E, 'M', u'Ꭾ'),\n    (0xAB7F, 'M', u'Ꭿ'),\n    (0xAB80, 'M', u'Ꮀ'),\n    (0xAB81, 'M', u'Ꮁ'),\n    (0xAB82, 'M', u'Ꮂ'),\n    (0xAB83, 'M', u'Ꮃ'),\n    (0xAB84, 'M', u'Ꮄ'),\n    (0xAB85, 'M', u'Ꮅ'),\n    (0xAB86, 'M', u'Ꮆ'),\n    (0xAB87, 'M', u'Ꮇ'),\n    (0xAB88, 'M', u'Ꮈ'),\n    (0xAB89, 'M', u'Ꮉ'),\n    (0xAB8A, 'M', u'Ꮊ'),\n    (0xAB8B, 'M', u'Ꮋ'),\n    (0xAB8C, 'M', u'Ꮌ'),\n    (0xAB8D, 'M', u'Ꮍ'),\n    (0xAB8E, 'M', u'Ꮎ'),\n    (0xAB8F, 'M', u'Ꮏ'),\n    (0xAB90, 'M', u'Ꮐ'),\n    (0xAB91, 'M', u'Ꮑ'),\n    (0xAB92, 'M', u'Ꮒ'),\n    (0xAB93, 'M', u'Ꮓ'),\n    (0xAB94, 'M', u'Ꮔ'),\n    (0xAB95, 'M', u'Ꮕ'),\n    (0xAB96, 'M', u'Ꮖ'),\n    (0xAB97, 'M', u'Ꮗ'),\n    (0xAB98, 'M', u'Ꮘ'),\n    (0xAB99, 'M', u'Ꮙ'),\n    (0xAB9A, 'M', u'Ꮚ'),\n    (0xAB9B, 'M', u'Ꮛ'),\n    (0xAB9C, 'M', u'Ꮜ'),\n    (0xAB9D, 'M', u'Ꮝ'),\n    (0xAB9E, 'M', u'Ꮞ'),\n    (0xAB9F, 'M', u'Ꮟ'),\n    (0xABA0, 'M', u'Ꮠ'),\n    (0xABA1, 'M', u'Ꮡ'),\n    (0xABA2, 'M', u'Ꮢ'),\n    (0xABA3, 'M', u'Ꮣ'),\n    (0xABA4, 'M', u'Ꮤ'),\n    (0xABA5, 'M', u'Ꮥ'),\n    (0xABA6, 'M', u'Ꮦ'),\n    (0xABA7, 'M', u'Ꮧ'),\n    (0xABA8, 'M', u'Ꮨ'),\n    (0xABA9, 'M', u'Ꮩ'),\n    (0xABAA, 'M', u'Ꮪ'),\n    (0xABAB, 'M', u'Ꮫ'),\n    (0xABAC, 'M', u'Ꮬ'),\n    (0xABAD, 'M', u'Ꮭ'),\n    (0xABAE, 'M', u'Ꮮ'),\n    (0xABAF, 'M', u'Ꮯ'),\n    (0xABB0, 'M', u'Ꮰ'),\n    (0xABB1, 'M', u'Ꮱ'),\n    (0xABB2, 'M', u'Ꮲ'),\n    (0xABB3, 'M', u'Ꮳ'),\n    (0xABB4, 'M', u'Ꮴ'),\n    (0xABB5, 'M', u'Ꮵ'),\n    (0xABB6, 'M', u'Ꮶ'),\n    (0xABB7, 'M', u'Ꮷ'),\n    (0xABB8, 'M', u'Ꮸ'),\n    (0xABB9, 'M', u'Ꮹ'),\n    (0xABBA, 'M', u'Ꮺ'),\n    (0xABBB, 'M', u'Ꮻ'),\n    (0xABBC, 'M', u'Ꮼ'),\n    (0xABBD, 'M', u'Ꮽ'),\n    (0xABBE, 'M', u'Ꮾ'),\n    (0xABBF, 'M', u'Ꮿ'),\n    (0xABC0, 'V'),\n    (0xABEE, 'X'),\n    (0xABF0, 'V'),\n    (0xABFA, 'X'),\n    (0xAC00, 'V'),\n    (0xD7A4, 'X'),\n    (0xD7B0, 'V'),\n    (0xD7C7, 'X'),\n    (0xD7CB, 'V'),\n    (0xD7FC, 'X'),\n    (0xF900, 'M', u'豈'),\n    (0xF901, 'M', u'更'),\n    (0xF902, 'M', u'車'),\n    (0xF903, 'M', u'賈'),\n    (0xF904, 'M', u'滑'),\n    (0xF905, 'M', u'串'),\n    (0xF906, 'M', u'句'),\n    (0xF907, 'M', u'龜'),\n    (0xF909, 'M', u'契'),\n    (0xF90A, 'M', u'金'),\n    (0xF90B, 'M', u'喇'),\n    (0xF90C, 'M', u'奈'),\n    (0xF90D, 'M', u'懶'),\n    (0xF90E, 'M', u'癩'),\n    (0xF90F, 'M', u'羅'),\n    (0xF910, 'M', u'蘿'),\n    (0xF911, 'M', u'螺'),\n    (0xF912, 'M', u'裸'),\n    (0xF913, 'M', u'邏'),\n    (0xF914, 'M', u'樂'),\n    (0xF915, 'M', u'洛'),\n    ]\n\ndef _seg_39():\n    return [\n    (0xF916, 'M', u'烙'),\n    (0xF917, 'M', u'珞'),\n    (0xF918, 'M', u'落'),\n    (0xF919, 'M', u'酪'),\n    (0xF91A, 'M', u'駱'),\n    (0xF91B, 'M', u'亂'),\n    (0xF91C, 'M', u'卵'),\n    (0xF91D, 'M', u'欄'),\n    (0xF91E, 'M', u'爛'),\n    (0xF91F, 'M', u'蘭'),\n    (0xF920, 'M', u'鸞'),\n    (0xF921, 'M', u'嵐'),\n    (0xF922, 'M', u'濫'),\n    (0xF923, 'M', u'藍'),\n    (0xF924, 'M', u'襤'),\n    (0xF925, 'M', u'拉'),\n    (0xF926, 'M', u'臘'),\n    (0xF927, 'M', u'蠟'),\n    (0xF928, 'M', u'廊'),\n    (0xF929, 'M', u'朗'),\n    (0xF92A, 'M', u'浪'),\n    (0xF92B, 'M', u'狼'),\n    (0xF92C, 'M', u'郎'),\n    (0xF92D, 'M', u'來'),\n    (0xF92E, 'M', u'冷'),\n    (0xF92F, 'M', u'勞'),\n    (0xF930, 'M', u'擄'),\n    (0xF931, 'M', u'櫓'),\n    (0xF932, 'M', u'爐'),\n    (0xF933, 'M', u'盧'),\n    (0xF934, 'M', u'老'),\n    (0xF935, 'M', u'蘆'),\n    (0xF936, 'M', u'虜'),\n    (0xF937, 'M', u'路'),\n    (0xF938, 'M', u'露'),\n    (0xF939, 'M', u'魯'),\n    (0xF93A, 'M', u'鷺'),\n    (0xF93B, 'M', u'碌'),\n    (0xF93C, 'M', u'祿'),\n    (0xF93D, 'M', u'綠'),\n    (0xF93E, 'M', u'菉'),\n    (0xF93F, 'M', u'錄'),\n    (0xF940, 'M', u'鹿'),\n    (0xF941, 'M', u'論'),\n    (0xF942, 'M', u'壟'),\n    (0xF943, 'M', u'弄'),\n    (0xF944, 'M', u'籠'),\n    (0xF945, 'M', u'聾'),\n    (0xF946, 'M', u'牢'),\n    (0xF947, 'M', u'磊'),\n    (0xF948, 'M', u'賂'),\n    (0xF949, 'M', u'雷'),\n    (0xF94A, 'M', u'壘'),\n    (0xF94B, 'M', u'屢'),\n    (0xF94C, 'M', u'樓'),\n    (0xF94D, 'M', u'淚'),\n    (0xF94E, 'M', u'漏'),\n    (0xF94F, 'M', u'累'),\n    (0xF950, 'M', u'縷'),\n    (0xF951, 'M', u'陋'),\n    (0xF952, 'M', u'勒'),\n    (0xF953, 'M', u'肋'),\n    (0xF954, 'M', u'凜'),\n    (0xF955, 'M', u'凌'),\n    (0xF956, 'M', u'稜'),\n    (0xF957, 'M', u'綾'),\n    (0xF958, 'M', u'菱'),\n    (0xF959, 'M', u'陵'),\n    (0xF95A, 'M', u'讀'),\n    (0xF95B, 'M', u'拏'),\n    (0xF95C, 'M', u'樂'),\n    (0xF95D, 'M', u'諾'),\n    (0xF95E, 'M', u'丹'),\n    (0xF95F, 'M', u'寧'),\n    (0xF960, 'M', u'怒'),\n    (0xF961, 'M', u'率'),\n    (0xF962, 'M', u'異'),\n    (0xF963, 'M', u'北'),\n    (0xF964, 'M', u'磻'),\n    (0xF965, 'M', u'便'),\n    (0xF966, 'M', u'復'),\n    (0xF967, 'M', u'不'),\n    (0xF968, 'M', u'泌'),\n    (0xF969, 'M', u'數'),\n    (0xF96A, 'M', u'索'),\n    (0xF96B, 'M', u'參'),\n    (0xF96C, 'M', u'塞'),\n    (0xF96D, 'M', u'省'),\n    (0xF96E, 'M', u'葉'),\n    (0xF96F, 'M', u'說'),\n    (0xF970, 'M', u'殺'),\n    (0xF971, 'M', u'辰'),\n    (0xF972, 'M', u'沈'),\n    (0xF973, 'M', u'拾'),\n    (0xF974, 'M', u'若'),\n    (0xF975, 'M', u'掠'),\n    (0xF976, 'M', u'略'),\n    (0xF977, 'M', u'亮'),\n    (0xF978, 'M', u'兩'),\n    (0xF979, 'M', u'凉'),\n    ]\n\ndef _seg_40():\n    return [\n    (0xF97A, 'M', u'梁'),\n    (0xF97B, 'M', u'糧'),\n    (0xF97C, 'M', u'良'),\n    (0xF97D, 'M', u'諒'),\n    (0xF97E, 'M', u'量'),\n    (0xF97F, 'M', u'勵'),\n    (0xF980, 'M', u'呂'),\n    (0xF981, 'M', u'女'),\n    (0xF982, 'M', u'廬'),\n    (0xF983, 'M', u'旅'),\n    (0xF984, 'M', u'濾'),\n    (0xF985, 'M', u'礪'),\n    (0xF986, 'M', u'閭'),\n    (0xF987, 'M', u'驪'),\n    (0xF988, 'M', u'麗'),\n    (0xF989, 'M', u'黎'),\n    (0xF98A, 'M', u'力'),\n    (0xF98B, 'M', u'曆'),\n    (0xF98C, 'M', u'歷'),\n    (0xF98D, 'M', u'轢'),\n    (0xF98E, 'M', u'年'),\n    (0xF98F, 'M', u'憐'),\n    (0xF990, 'M', u'戀'),\n    (0xF991, 'M', u'撚'),\n    (0xF992, 'M', u'漣'),\n    (0xF993, 'M', u'煉'),\n    (0xF994, 'M', u'璉'),\n    (0xF995, 'M', u'秊'),\n    (0xF996, 'M', u'練'),\n    (0xF997, 'M', u'聯'),\n    (0xF998, 'M', u'輦'),\n    (0xF999, 'M', u'蓮'),\n    (0xF99A, 'M', u'連'),\n    (0xF99B, 'M', u'鍊'),\n    (0xF99C, 'M', u'列'),\n    (0xF99D, 'M', u'劣'),\n    (0xF99E, 'M', u'咽'),\n    (0xF99F, 'M', u'烈'),\n    (0xF9A0, 'M', u'裂'),\n    (0xF9A1, 'M', u'說'),\n    (0xF9A2, 'M', u'廉'),\n    (0xF9A3, 'M', u'念'),\n    (0xF9A4, 'M', u'捻'),\n    (0xF9A5, 'M', u'殮'),\n    (0xF9A6, 'M', u'簾'),\n    (0xF9A7, 'M', u'獵'),\n    (0xF9A8, 'M', u'令'),\n    (0xF9A9, 'M', u'囹'),\n    (0xF9AA, 'M', u'寧'),\n    (0xF9AB, 'M', u'嶺'),\n    (0xF9AC, 'M', u'怜'),\n    (0xF9AD, 'M', u'玲'),\n    (0xF9AE, 'M', u'瑩'),\n    (0xF9AF, 'M', u'羚'),\n    (0xF9B0, 'M', u'聆'),\n    (0xF9B1, 'M', u'鈴'),\n    (0xF9B2, 'M', u'零'),\n    (0xF9B3, 'M', u'靈'),\n    (0xF9B4, 'M', u'領'),\n    (0xF9B5, 'M', u'例'),\n    (0xF9B6, 'M', u'禮'),\n    (0xF9B7, 'M', u'醴'),\n    (0xF9B8, 'M', u'隸'),\n    (0xF9B9, 'M', u'惡'),\n    (0xF9BA, 'M', u'了'),\n    (0xF9BB, 'M', u'僚'),\n    (0xF9BC, 'M', u'寮'),\n    (0xF9BD, 'M', u'尿'),\n    (0xF9BE, 'M', u'料'),\n    (0xF9BF, 'M', u'樂'),\n    (0xF9C0, 'M', u'燎'),\n    (0xF9C1, 'M', u'療'),\n    (0xF9C2, 'M', u'蓼'),\n    (0xF9C3, 'M', u'遼'),\n    (0xF9C4, 'M', u'龍'),\n    (0xF9C5, 'M', u'暈'),\n    (0xF9C6, 'M', u'阮'),\n    (0xF9C7, 'M', u'劉'),\n    (0xF9C8, 'M', u'杻'),\n    (0xF9C9, 'M', u'柳'),\n    (0xF9CA, 'M', u'流'),\n    (0xF9CB, 'M', u'溜'),\n    (0xF9CC, 'M', u'琉'),\n    (0xF9CD, 'M', u'留'),\n    (0xF9CE, 'M', u'硫'),\n    (0xF9CF, 'M', u'紐'),\n    (0xF9D0, 'M', u'類'),\n    (0xF9D1, 'M', u'六'),\n    (0xF9D2, 'M', u'戮'),\n    (0xF9D3, 'M', u'陸'),\n    (0xF9D4, 'M', u'倫'),\n    (0xF9D5, 'M', u'崙'),\n    (0xF9D6, 'M', u'淪'),\n    (0xF9D7, 'M', u'輪'),\n    (0xF9D8, 'M', u'律'),\n    (0xF9D9, 'M', u'慄'),\n    (0xF9DA, 'M', u'栗'),\n    (0xF9DB, 'M', u'率'),\n    (0xF9DC, 'M', u'隆'),\n    (0xF9DD, 'M', u'利'),\n    ]\n\ndef _seg_41():\n    return [\n    (0xF9DE, 'M', u'吏'),\n    (0xF9DF, 'M', u'履'),\n    (0xF9E0, 'M', u'易'),\n    (0xF9E1, 'M', u'李'),\n    (0xF9E2, 'M', u'梨'),\n    (0xF9E3, 'M', u'泥'),\n    (0xF9E4, 'M', u'理'),\n    (0xF9E5, 'M', u'痢'),\n    (0xF9E6, 'M', u'罹'),\n    (0xF9E7, 'M', u'裏'),\n    (0xF9E8, 'M', u'裡'),\n    (0xF9E9, 'M', u'里'),\n    (0xF9EA, 'M', u'離'),\n    (0xF9EB, 'M', u'匿'),\n    (0xF9EC, 'M', u'溺'),\n    (0xF9ED, 'M', u'吝'),\n    (0xF9EE, 'M', u'燐'),\n    (0xF9EF, 'M', u'璘'),\n    (0xF9F0, 'M', u'藺'),\n    (0xF9F1, 'M', u'隣'),\n    (0xF9F2, 'M', u'鱗'),\n    (0xF9F3, 'M', u'麟'),\n    (0xF9F4, 'M', u'林'),\n    (0xF9F5, 'M', u'淋'),\n    (0xF9F6, 'M', u'臨'),\n    (0xF9F7, 'M', u'立'),\n    (0xF9F8, 'M', u'笠'),\n    (0xF9F9, 'M', u'粒'),\n    (0xF9FA, 'M', u'狀'),\n    (0xF9FB, 'M', u'炙'),\n    (0xF9FC, 'M', u'識'),\n    (0xF9FD, 'M', u'什'),\n    (0xF9FE, 'M', u'茶'),\n    (0xF9FF, 'M', u'刺'),\n    (0xFA00, 'M', u'切'),\n    (0xFA01, 'M', u'度'),\n    (0xFA02, 'M', u'拓'),\n    (0xFA03, 'M', u'糖'),\n    (0xFA04, 'M', u'宅'),\n    (0xFA05, 'M', u'洞'),\n    (0xFA06, 'M', u'暴'),\n    (0xFA07, 'M', u'輻'),\n    (0xFA08, 'M', u'行'),\n    (0xFA09, 'M', u'降'),\n    (0xFA0A, 'M', u'見'),\n    (0xFA0B, 'M', u'廓'),\n    (0xFA0C, 'M', u'兀'),\n    (0xFA0D, 'M', u'嗀'),\n    (0xFA0E, 'V'),\n    (0xFA10, 'M', u'塚'),\n    (0xFA11, 'V'),\n    (0xFA12, 'M', u'晴'),\n    (0xFA13, 'V'),\n    (0xFA15, 'M', u'凞'),\n    (0xFA16, 'M', u'猪'),\n    (0xFA17, 'M', u'益'),\n    (0xFA18, 'M', u'礼'),\n    (0xFA19, 'M', u'神'),\n    (0xFA1A, 'M', u'祥'),\n    (0xFA1B, 'M', u'福'),\n    (0xFA1C, 'M', u'靖'),\n    (0xFA1D, 'M', u'精'),\n    (0xFA1E, 'M', u'羽'),\n    (0xFA1F, 'V'),\n    (0xFA20, 'M', u'蘒'),\n    (0xFA21, 'V'),\n    (0xFA22, 'M', u'諸'),\n    (0xFA23, 'V'),\n    (0xFA25, 'M', u'逸'),\n    (0xFA26, 'M', u'都'),\n    (0xFA27, 'V'),\n    (0xFA2A, 'M', u'飯'),\n    (0xFA2B, 'M', u'飼'),\n    (0xFA2C, 'M', u'館'),\n    (0xFA2D, 'M', u'鶴'),\n    (0xFA2E, 'M', u'郞'),\n    (0xFA2F, 'M', u'隷'),\n    (0xFA30, 'M', u'侮'),\n    (0xFA31, 'M', u'僧'),\n    (0xFA32, 'M', u'免'),\n    (0xFA33, 'M', u'勉'),\n    (0xFA34, 'M', u'勤'),\n    (0xFA35, 'M', u'卑'),\n    (0xFA36, 'M', u'喝'),\n    (0xFA37, 'M', u'嘆'),\n    (0xFA38, 'M', u'器'),\n    (0xFA39, 'M', u'塀'),\n    (0xFA3A, 'M', u'墨'),\n    (0xFA3B, 'M', u'層'),\n    (0xFA3C, 'M', u'屮'),\n    (0xFA3D, 'M', u'悔'),\n    (0xFA3E, 'M', u'慨'),\n    (0xFA3F, 'M', u'憎'),\n    (0xFA40, 'M', u'懲'),\n    (0xFA41, 'M', u'敏'),\n    (0xFA42, 'M', u'既'),\n    (0xFA43, 'M', u'暑'),\n    (0xFA44, 'M', u'梅'),\n    (0xFA45, 'M', u'海'),\n    (0xFA46, 'M', u'渚'),\n    ]\n\ndef _seg_42():\n    return [\n    (0xFA47, 'M', u'漢'),\n    (0xFA48, 'M', u'煮'),\n    (0xFA49, 'M', u'爫'),\n    (0xFA4A, 'M', u'琢'),\n    (0xFA4B, 'M', u'碑'),\n    (0xFA4C, 'M', u'社'),\n    (0xFA4D, 'M', u'祉'),\n    (0xFA4E, 'M', u'祈'),\n    (0xFA4F, 'M', u'祐'),\n    (0xFA50, 'M', u'祖'),\n    (0xFA51, 'M', u'祝'),\n    (0xFA52, 'M', u'禍'),\n    (0xFA53, 'M', u'禎'),\n    (0xFA54, 'M', u'穀'),\n    (0xFA55, 'M', u'突'),\n    (0xFA56, 'M', u'節'),\n    (0xFA57, 'M', u'練'),\n    (0xFA58, 'M', u'縉'),\n    (0xFA59, 'M', u'繁'),\n    (0xFA5A, 'M', u'署'),\n    (0xFA5B, 'M', u'者'),\n    (0xFA5C, 'M', u'臭'),\n    (0xFA5D, 'M', u'艹'),\n    (0xFA5F, 'M', u'著'),\n    (0xFA60, 'M', u'褐'),\n    (0xFA61, 'M', u'視'),\n    (0xFA62, 'M', u'謁'),\n    (0xFA63, 'M', u'謹'),\n    (0xFA64, 'M', u'賓'),\n    (0xFA65, 'M', u'贈'),\n    (0xFA66, 'M', u'辶'),\n    (0xFA67, 'M', u'逸'),\n    (0xFA68, 'M', u'難'),\n    (0xFA69, 'M', u'響'),\n    (0xFA6A, 'M', u'頻'),\n    (0xFA6B, 'M', u'恵'),\n    (0xFA6C, 'M', u'𤋮'),\n    (0xFA6D, 'M', u'舘'),\n    (0xFA6E, 'X'),\n    (0xFA70, 'M', u'並'),\n    (0xFA71, 'M', u'况'),\n    (0xFA72, 'M', u'全'),\n    (0xFA73, 'M', u'侀'),\n    (0xFA74, 'M', u'充'),\n    (0xFA75, 'M', u'冀'),\n    (0xFA76, 'M', u'勇'),\n    (0xFA77, 'M', u'勺'),\n    (0xFA78, 'M', u'喝'),\n    (0xFA79, 'M', u'啕'),\n    (0xFA7A, 'M', u'喙'),\n    (0xFA7B, 'M', u'嗢'),\n    (0xFA7C, 'M', u'塚'),\n    (0xFA7D, 'M', u'墳'),\n    (0xFA7E, 'M', u'奄'),\n    (0xFA7F, 'M', u'奔'),\n    (0xFA80, 'M', u'婢'),\n    (0xFA81, 'M', u'嬨'),\n    (0xFA82, 'M', u'廒'),\n    (0xFA83, 'M', u'廙'),\n    (0xFA84, 'M', u'彩'),\n    (0xFA85, 'M', u'徭'),\n    (0xFA86, 'M', u'惘'),\n    (0xFA87, 'M', u'慎'),\n    (0xFA88, 'M', u'愈'),\n    (0xFA89, 'M', u'憎'),\n    (0xFA8A, 'M', u'慠'),\n    (0xFA8B, 'M', u'懲'),\n    (0xFA8C, 'M', u'戴'),\n    (0xFA8D, 'M', u'揄'),\n    (0xFA8E, 'M', u'搜'),\n    (0xFA8F, 'M', u'摒'),\n    (0xFA90, 'M', u'敖'),\n    (0xFA91, 'M', u'晴'),\n    (0xFA92, 'M', u'朗'),\n    (0xFA93, 'M', u'望'),\n    (0xFA94, 'M', u'杖'),\n    (0xFA95, 'M', u'歹'),\n    (0xFA96, 'M', u'殺'),\n    (0xFA97, 'M', u'流'),\n    (0xFA98, 'M', u'滛'),\n    (0xFA99, 'M', u'滋'),\n    (0xFA9A, 'M', u'漢'),\n    (0xFA9B, 'M', u'瀞'),\n    (0xFA9C, 'M', u'煮'),\n    (0xFA9D, 'M', u'瞧'),\n    (0xFA9E, 'M', u'爵'),\n    (0xFA9F, 'M', u'犯'),\n    (0xFAA0, 'M', u'猪'),\n    (0xFAA1, 'M', u'瑱'),\n    (0xFAA2, 'M', u'甆'),\n    (0xFAA3, 'M', u'画'),\n    (0xFAA4, 'M', u'瘝'),\n    (0xFAA5, 'M', u'瘟'),\n    (0xFAA6, 'M', u'益'),\n    (0xFAA7, 'M', u'盛'),\n    (0xFAA8, 'M', u'直'),\n    (0xFAA9, 'M', u'睊'),\n    (0xFAAA, 'M', u'着'),\n    (0xFAAB, 'M', u'磌'),\n    (0xFAAC, 'M', u'窱'),\n    ]\n\ndef _seg_43():\n    return [\n    (0xFAAD, 'M', u'節'),\n    (0xFAAE, 'M', u'类'),\n    (0xFAAF, 'M', u'絛'),\n    (0xFAB0, 'M', u'練'),\n    (0xFAB1, 'M', u'缾'),\n    (0xFAB2, 'M', u'者'),\n    (0xFAB3, 'M', u'荒'),\n    (0xFAB4, 'M', u'華'),\n    (0xFAB5, 'M', u'蝹'),\n    (0xFAB6, 'M', u'襁'),\n    (0xFAB7, 'M', u'覆'),\n    (0xFAB8, 'M', u'視'),\n    (0xFAB9, 'M', u'調'),\n    (0xFABA, 'M', u'諸'),\n    (0xFABB, 'M', u'請'),\n    (0xFABC, 'M', u'謁'),\n    (0xFABD, 'M', u'諾'),\n    (0xFABE, 'M', u'諭'),\n    (0xFABF, 'M', u'謹'),\n    (0xFAC0, 'M', u'變'),\n    (0xFAC1, 'M', u'贈'),\n    (0xFAC2, 'M', u'輸'),\n    (0xFAC3, 'M', u'遲'),\n    (0xFAC4, 'M', u'醙'),\n    (0xFAC5, 'M', u'鉶'),\n    (0xFAC6, 'M', u'陼'),\n    (0xFAC7, 'M', u'難'),\n    (0xFAC8, 'M', u'靖'),\n    (0xFAC9, 'M', u'韛'),\n    (0xFACA, 'M', u'響'),\n    (0xFACB, 'M', u'頋'),\n    (0xFACC, 'M', u'頻'),\n    (0xFACD, 'M', u'鬒'),\n    (0xFACE, 'M', u'龜'),\n    (0xFACF, 'M', u'𢡊'),\n    (0xFAD0, 'M', u'𢡄'),\n    (0xFAD1, 'M', u'𣏕'),\n    (0xFAD2, 'M', u'㮝'),\n    (0xFAD3, 'M', u'䀘'),\n    (0xFAD4, 'M', u'䀹'),\n    (0xFAD5, 'M', u'𥉉'),\n    (0xFAD6, 'M', u'𥳐'),\n    (0xFAD7, 'M', u'𧻓'),\n    (0xFAD8, 'M', u'齃'),\n    (0xFAD9, 'M', u'龎'),\n    (0xFADA, 'X'),\n    (0xFB00, 'M', u'ff'),\n    (0xFB01, 'M', u'fi'),\n    (0xFB02, 'M', u'fl'),\n    (0xFB03, 'M', u'ffi'),\n    (0xFB04, 'M', u'ffl'),\n    (0xFB05, 'M', u'st'),\n    (0xFB07, 'X'),\n    (0xFB13, 'M', u'մն'),\n    (0xFB14, 'M', u'մե'),\n    (0xFB15, 'M', u'մի'),\n    (0xFB16, 'M', u'վն'),\n    (0xFB17, 'M', u'մխ'),\n    (0xFB18, 'X'),\n    (0xFB1D, 'M', u'יִ'),\n    (0xFB1E, 'V'),\n    (0xFB1F, 'M', u'ײַ'),\n    (0xFB20, 'M', u'ע'),\n    (0xFB21, 'M', u'א'),\n    (0xFB22, 'M', u'ד'),\n    (0xFB23, 'M', u'ה'),\n    (0xFB24, 'M', u'כ'),\n    (0xFB25, 'M', u'ל'),\n    (0xFB26, 'M', u'ם'),\n    (0xFB27, 'M', u'ר'),\n    (0xFB28, 'M', u'ת'),\n    (0xFB29, '3', u'+'),\n    (0xFB2A, 'M', u'שׁ'),\n    (0xFB2B, 'M', u'שׂ'),\n    (0xFB2C, 'M', u'שּׁ'),\n    (0xFB2D, 'M', u'שּׂ'),\n    (0xFB2E, 'M', u'אַ'),\n    (0xFB2F, 'M', u'אָ'),\n    (0xFB30, 'M', u'אּ'),\n    (0xFB31, 'M', u'בּ'),\n    (0xFB32, 'M', u'גּ'),\n    (0xFB33, 'M', u'דּ'),\n    (0xFB34, 'M', u'הּ'),\n    (0xFB35, 'M', u'וּ'),\n    (0xFB36, 'M', u'זּ'),\n    (0xFB37, 'X'),\n    (0xFB38, 'M', u'טּ'),\n    (0xFB39, 'M', u'יּ'),\n    (0xFB3A, 'M', u'ךּ'),\n    (0xFB3B, 'M', u'כּ'),\n    (0xFB3C, 'M', u'לּ'),\n    (0xFB3D, 'X'),\n    (0xFB3E, 'M', u'מּ'),\n    (0xFB3F, 'X'),\n    (0xFB40, 'M', u'נּ'),\n    (0xFB41, 'M', u'סּ'),\n    (0xFB42, 'X'),\n    (0xFB43, 'M', u'ףּ'),\n    (0xFB44, 'M', u'פּ'),\n    (0xFB45, 'X'),\n    ]\n\ndef _seg_44():\n    return [\n    (0xFB46, 'M', u'צּ'),\n    (0xFB47, 'M', u'קּ'),\n    (0xFB48, 'M', u'רּ'),\n    (0xFB49, 'M', u'שּ'),\n    (0xFB4A, 'M', u'תּ'),\n    (0xFB4B, 'M', u'וֹ'),\n    (0xFB4C, 'M', u'בֿ'),\n    (0xFB4D, 'M', u'כֿ'),\n    (0xFB4E, 'M', u'פֿ'),\n    (0xFB4F, 'M', u'אל'),\n    (0xFB50, 'M', u'ٱ'),\n    (0xFB52, 'M', u'ٻ'),\n    (0xFB56, 'M', u'پ'),\n    (0xFB5A, 'M', u'ڀ'),\n    (0xFB5E, 'M', u'ٺ'),\n    (0xFB62, 'M', u'ٿ'),\n    (0xFB66, 'M', u'ٹ'),\n    (0xFB6A, 'M', u'ڤ'),\n    (0xFB6E, 'M', u'ڦ'),\n    (0xFB72, 'M', u'ڄ'),\n    (0xFB76, 'M', u'ڃ'),\n    (0xFB7A, 'M', u'چ'),\n    (0xFB7E, 'M', u'ڇ'),\n    (0xFB82, 'M', u'ڍ'),\n    (0xFB84, 'M', u'ڌ'),\n    (0xFB86, 'M', u'ڎ'),\n    (0xFB88, 'M', u'ڈ'),\n    (0xFB8A, 'M', u'ژ'),\n    (0xFB8C, 'M', u'ڑ'),\n    (0xFB8E, 'M', u'ک'),\n    (0xFB92, 'M', u'گ'),\n    (0xFB96, 'M', u'ڳ'),\n    (0xFB9A, 'M', u'ڱ'),\n    (0xFB9E, 'M', u'ں'),\n    (0xFBA0, 'M', u'ڻ'),\n    (0xFBA4, 'M', u'ۀ'),\n    (0xFBA6, 'M', u'ہ'),\n    (0xFBAA, 'M', u'ھ'),\n    (0xFBAE, 'M', u'ے'),\n    (0xFBB0, 'M', u'ۓ'),\n    (0xFBB2, 'V'),\n    (0xFBC2, 'X'),\n    (0xFBD3, 'M', u'ڭ'),\n    (0xFBD7, 'M', u'ۇ'),\n    (0xFBD9, 'M', u'ۆ'),\n    (0xFBDB, 'M', u'ۈ'),\n    (0xFBDD, 'M', u'ۇٴ'),\n    (0xFBDE, 'M', u'ۋ'),\n    (0xFBE0, 'M', u'ۅ'),\n    (0xFBE2, 'M', u'ۉ'),\n    (0xFBE4, 'M', u'ې'),\n    (0xFBE8, 'M', u'ى'),\n    (0xFBEA, 'M', u'ئا'),\n    (0xFBEC, 'M', u'ئە'),\n    (0xFBEE, 'M', u'ئو'),\n    (0xFBF0, 'M', u'ئۇ'),\n    (0xFBF2, 'M', u'ئۆ'),\n    (0xFBF4, 'M', u'ئۈ'),\n    (0xFBF6, 'M', u'ئې'),\n    (0xFBF9, 'M', u'ئى'),\n    (0xFBFC, 'M', u'ی'),\n    (0xFC00, 'M', u'ئج'),\n    (0xFC01, 'M', u'ئح'),\n    (0xFC02, 'M', u'ئم'),\n    (0xFC03, 'M', u'ئى'),\n    (0xFC04, 'M', u'ئي'),\n    (0xFC05, 'M', u'بج'),\n    (0xFC06, 'M', u'بح'),\n    (0xFC07, 'M', u'بخ'),\n    (0xFC08, 'M', u'بم'),\n    (0xFC09, 'M', u'بى'),\n    (0xFC0A, 'M', u'بي'),\n    (0xFC0B, 'M', u'تج'),\n    (0xFC0C, 'M', u'تح'),\n    (0xFC0D, 'M', u'تخ'),\n    (0xFC0E, 'M', u'تم'),\n    (0xFC0F, 'M', u'تى'),\n    (0xFC10, 'M', u'تي'),\n    (0xFC11, 'M', u'ثج'),\n    (0xFC12, 'M', u'ثم'),\n    (0xFC13, 'M', u'ثى'),\n    (0xFC14, 'M', u'ثي'),\n    (0xFC15, 'M', u'جح'),\n    (0xFC16, 'M', u'جم'),\n    (0xFC17, 'M', u'حج'),\n    (0xFC18, 'M', u'حم'),\n    (0xFC19, 'M', u'خج'),\n    (0xFC1A, 'M', u'خح'),\n    (0xFC1B, 'M', u'خم'),\n    (0xFC1C, 'M', u'سج'),\n    (0xFC1D, 'M', u'سح'),\n    (0xFC1E, 'M', u'سخ'),\n    (0xFC1F, 'M', u'سم'),\n    (0xFC20, 'M', u'صح'),\n    (0xFC21, 'M', u'صم'),\n    (0xFC22, 'M', u'ضج'),\n    (0xFC23, 'M', u'ضح'),\n    (0xFC24, 'M', u'ضخ'),\n    (0xFC25, 'M', u'ضم'),\n    (0xFC26, 'M', u'طح'),\n    ]\n\ndef _seg_45():\n    return [\n    (0xFC27, 'M', u'طم'),\n    (0xFC28, 'M', u'ظم'),\n    (0xFC29, 'M', u'عج'),\n    (0xFC2A, 'M', u'عم'),\n    (0xFC2B, 'M', u'غج'),\n    (0xFC2C, 'M', u'غم'),\n    (0xFC2D, 'M', u'فج'),\n    (0xFC2E, 'M', u'فح'),\n    (0xFC2F, 'M', u'فخ'),\n    (0xFC30, 'M', u'فم'),\n    (0xFC31, 'M', u'فى'),\n    (0xFC32, 'M', u'في'),\n    (0xFC33, 'M', u'قح'),\n    (0xFC34, 'M', u'قم'),\n    (0xFC35, 'M', u'قى'),\n    (0xFC36, 'M', u'قي'),\n    (0xFC37, 'M', u'كا'),\n    (0xFC38, 'M', u'كج'),\n    (0xFC39, 'M', u'كح'),\n    (0xFC3A, 'M', u'كخ'),\n    (0xFC3B, 'M', u'كل'),\n    (0xFC3C, 'M', u'كم'),\n    (0xFC3D, 'M', u'كى'),\n    (0xFC3E, 'M', u'كي'),\n    (0xFC3F, 'M', u'لج'),\n    (0xFC40, 'M', u'لح'),\n    (0xFC41, 'M', u'لخ'),\n    (0xFC42, 'M', u'لم'),\n    (0xFC43, 'M', u'لى'),\n    (0xFC44, 'M', u'لي'),\n    (0xFC45, 'M', u'مج'),\n    (0xFC46, 'M', u'مح'),\n    (0xFC47, 'M', u'مخ'),\n    (0xFC48, 'M', u'مم'),\n    (0xFC49, 'M', u'مى'),\n    (0xFC4A, 'M', u'مي'),\n    (0xFC4B, 'M', u'نج'),\n    (0xFC4C, 'M', u'نح'),\n    (0xFC4D, 'M', u'نخ'),\n    (0xFC4E, 'M', u'نم'),\n    (0xFC4F, 'M', u'نى'),\n    (0xFC50, 'M', u'ني'),\n    (0xFC51, 'M', u'هج'),\n    (0xFC52, 'M', u'هم'),\n    (0xFC53, 'M', u'هى'),\n    (0xFC54, 'M', u'هي'),\n    (0xFC55, 'M', u'يج'),\n    (0xFC56, 'M', u'يح'),\n    (0xFC57, 'M', u'يخ'),\n    (0xFC58, 'M', u'يم'),\n    (0xFC59, 'M', u'يى'),\n    (0xFC5A, 'M', u'يي'),\n    (0xFC5B, 'M', u'ذٰ'),\n    (0xFC5C, 'M', u'رٰ'),\n    (0xFC5D, 'M', u'ىٰ'),\n    (0xFC5E, '3', u' ٌّ'),\n    (0xFC5F, '3', u' ٍّ'),\n    (0xFC60, '3', u' َّ'),\n    (0xFC61, '3', u' ُّ'),\n    (0xFC62, '3', u' ِّ'),\n    (0xFC63, '3', u' ّٰ'),\n    (0xFC64, 'M', u'ئر'),\n    (0xFC65, 'M', u'ئز'),\n    (0xFC66, 'M', u'ئم'),\n    (0xFC67, 'M', u'ئن'),\n    (0xFC68, 'M', u'ئى'),\n    (0xFC69, 'M', u'ئي'),\n    (0xFC6A, 'M', u'بر'),\n    (0xFC6B, 'M', u'بز'),\n    (0xFC6C, 'M', u'بم'),\n    (0xFC6D, 'M', u'بن'),\n    (0xFC6E, 'M', u'بى'),\n    (0xFC6F, 'M', u'بي'),\n    (0xFC70, 'M', u'تر'),\n    (0xFC71, 'M', u'تز'),\n    (0xFC72, 'M', u'تم'),\n    (0xFC73, 'M', u'تن'),\n    (0xFC74, 'M', u'تى'),\n    (0xFC75, 'M', u'تي'),\n    (0xFC76, 'M', u'ثر'),\n    (0xFC77, 'M', u'ثز'),\n    (0xFC78, 'M', u'ثم'),\n    (0xFC79, 'M', u'ثن'),\n    (0xFC7A, 'M', u'ثى'),\n    (0xFC7B, 'M', u'ثي'),\n    (0xFC7C, 'M', u'فى'),\n    (0xFC7D, 'M', u'في'),\n    (0xFC7E, 'M', u'قى'),\n    (0xFC7F, 'M', u'قي'),\n    (0xFC80, 'M', u'كا'),\n    (0xFC81, 'M', u'كل'),\n    (0xFC82, 'M', u'كم'),\n    (0xFC83, 'M', u'كى'),\n    (0xFC84, 'M', u'كي'),\n    (0xFC85, 'M', u'لم'),\n    (0xFC86, 'M', u'لى'),\n    (0xFC87, 'M', u'لي'),\n    (0xFC88, 'M', u'ما'),\n    (0xFC89, 'M', u'مم'),\n    (0xFC8A, 'M', u'نر'),\n    ]\n\ndef _seg_46():\n    return [\n    (0xFC8B, 'M', u'نز'),\n    (0xFC8C, 'M', u'نم'),\n    (0xFC8D, 'M', u'نن'),\n    (0xFC8E, 'M', u'نى'),\n    (0xFC8F, 'M', u'ني'),\n    (0xFC90, 'M', u'ىٰ'),\n    (0xFC91, 'M', u'ير'),\n    (0xFC92, 'M', u'يز'),\n    (0xFC93, 'M', u'يم'),\n    (0xFC94, 'M', u'ين'),\n    (0xFC95, 'M', u'يى'),\n    (0xFC96, 'M', u'يي'),\n    (0xFC97, 'M', u'ئج'),\n    (0xFC98, 'M', u'ئح'),\n    (0xFC99, 'M', u'ئخ'),\n    (0xFC9A, 'M', u'ئم'),\n    (0xFC9B, 'M', u'ئه'),\n    (0xFC9C, 'M', u'بج'),\n    (0xFC9D, 'M', u'بح'),\n    (0xFC9E, 'M', u'بخ'),\n    (0xFC9F, 'M', u'بم'),\n    (0xFCA0, 'M', u'به'),\n    (0xFCA1, 'M', u'تج'),\n    (0xFCA2, 'M', u'تح'),\n    (0xFCA3, 'M', u'تخ'),\n    (0xFCA4, 'M', u'تم'),\n    (0xFCA5, 'M', u'ته'),\n    (0xFCA6, 'M', u'ثم'),\n    (0xFCA7, 'M', u'جح'),\n    (0xFCA8, 'M', u'جم'),\n    (0xFCA9, 'M', u'حج'),\n    (0xFCAA, 'M', u'حم'),\n    (0xFCAB, 'M', u'خج'),\n    (0xFCAC, 'M', u'خم'),\n    (0xFCAD, 'M', u'سج'),\n    (0xFCAE, 'M', u'سح'),\n    (0xFCAF, 'M', u'سخ'),\n    (0xFCB0, 'M', u'سم'),\n    (0xFCB1, 'M', u'صح'),\n    (0xFCB2, 'M', u'صخ'),\n    (0xFCB3, 'M', u'صم'),\n    (0xFCB4, 'M', u'ضج'),\n    (0xFCB5, 'M', u'ضح'),\n    (0xFCB6, 'M', u'ضخ'),\n    (0xFCB7, 'M', u'ضم'),\n    (0xFCB8, 'M', u'طح'),\n    (0xFCB9, 'M', u'ظم'),\n    (0xFCBA, 'M', u'عج'),\n    (0xFCBB, 'M', u'عم'),\n    (0xFCBC, 'M', u'غج'),\n    (0xFCBD, 'M', u'غم'),\n    (0xFCBE, 'M', u'فج'),\n    (0xFCBF, 'M', u'فح'),\n    (0xFCC0, 'M', u'فخ'),\n    (0xFCC1, 'M', u'فم'),\n    (0xFCC2, 'M', u'قح'),\n    (0xFCC3, 'M', u'قم'),\n    (0xFCC4, 'M', u'كج'),\n    (0xFCC5, 'M', u'كح'),\n    (0xFCC6, 'M', u'كخ'),\n    (0xFCC7, 'M', u'كل'),\n    (0xFCC8, 'M', u'كم'),\n    (0xFCC9, 'M', u'لج'),\n    (0xFCCA, 'M', u'لح'),\n    (0xFCCB, 'M', u'لخ'),\n    (0xFCCC, 'M', u'لم'),\n    (0xFCCD, 'M', u'له'),\n    (0xFCCE, 'M', u'مج'),\n    (0xFCCF, 'M', u'مح'),\n    (0xFCD0, 'M', u'مخ'),\n    (0xFCD1, 'M', u'مم'),\n    (0xFCD2, 'M', u'نج'),\n    (0xFCD3, 'M', u'نح'),\n    (0xFCD4, 'M', u'نخ'),\n    (0xFCD5, 'M', u'نم'),\n    (0xFCD6, 'M', u'نه'),\n    (0xFCD7, 'M', u'هج'),\n    (0xFCD8, 'M', u'هم'),\n    (0xFCD9, 'M', u'هٰ'),\n    (0xFCDA, 'M', u'يج'),\n    (0xFCDB, 'M', u'يح'),\n    (0xFCDC, 'M', u'يخ'),\n    (0xFCDD, 'M', u'يم'),\n    (0xFCDE, 'M', u'يه'),\n    (0xFCDF, 'M', u'ئم'),\n    (0xFCE0, 'M', u'ئه'),\n    (0xFCE1, 'M', u'بم'),\n    (0xFCE2, 'M', u'به'),\n    (0xFCE3, 'M', u'تم'),\n    (0xFCE4, 'M', u'ته'),\n    (0xFCE5, 'M', u'ثم'),\n    (0xFCE6, 'M', u'ثه'),\n    (0xFCE7, 'M', u'سم'),\n    (0xFCE8, 'M', u'سه'),\n    (0xFCE9, 'M', u'شم'),\n    (0xFCEA, 'M', u'شه'),\n    (0xFCEB, 'M', u'كل'),\n    (0xFCEC, 'M', u'كم'),\n    (0xFCED, 'M', u'لم'),\n    (0xFCEE, 'M', u'نم'),\n    ]\n\ndef _seg_47():\n    return [\n    (0xFCEF, 'M', u'نه'),\n    (0xFCF0, 'M', u'يم'),\n    (0xFCF1, 'M', u'يه'),\n    (0xFCF2, 'M', u'ـَّ'),\n    (0xFCF3, 'M', u'ـُّ'),\n    (0xFCF4, 'M', u'ـِّ'),\n    (0xFCF5, 'M', u'طى'),\n    (0xFCF6, 'M', u'طي'),\n    (0xFCF7, 'M', u'عى'),\n    (0xFCF8, 'M', u'عي'),\n    (0xFCF9, 'M', u'غى'),\n    (0xFCFA, 'M', u'غي'),\n    (0xFCFB, 'M', u'سى'),\n    (0xFCFC, 'M', u'سي'),\n    (0xFCFD, 'M', u'شى'),\n    (0xFCFE, 'M', u'شي'),\n    (0xFCFF, 'M', u'حى'),\n    (0xFD00, 'M', u'حي'),\n    (0xFD01, 'M', u'جى'),\n    (0xFD02, 'M', u'جي'),\n    (0xFD03, 'M', u'خى'),\n    (0xFD04, 'M', u'خي'),\n    (0xFD05, 'M', u'صى'),\n    (0xFD06, 'M', u'صي'),\n    (0xFD07, 'M', u'ضى'),\n    (0xFD08, 'M', u'ضي'),\n    (0xFD09, 'M', u'شج'),\n    (0xFD0A, 'M', u'شح'),\n    (0xFD0B, 'M', u'شخ'),\n    (0xFD0C, 'M', u'شم'),\n    (0xFD0D, 'M', u'شر'),\n    (0xFD0E, 'M', u'سر'),\n    (0xFD0F, 'M', u'صر'),\n    (0xFD10, 'M', u'ضر'),\n    (0xFD11, 'M', u'طى'),\n    (0xFD12, 'M', u'طي'),\n    (0xFD13, 'M', u'عى'),\n    (0xFD14, 'M', u'عي'),\n    (0xFD15, 'M', u'غى'),\n    (0xFD16, 'M', u'غي'),\n    (0xFD17, 'M', u'سى'),\n    (0xFD18, 'M', u'سي'),\n    (0xFD19, 'M', u'شى'),\n    (0xFD1A, 'M', u'شي'),\n    (0xFD1B, 'M', u'حى'),\n    (0xFD1C, 'M', u'حي'),\n    (0xFD1D, 'M', u'جى'),\n    (0xFD1E, 'M', u'جي'),\n    (0xFD1F, 'M', u'خى'),\n    (0xFD20, 'M', u'خي'),\n    (0xFD21, 'M', u'صى'),\n    (0xFD22, 'M', u'صي'),\n    (0xFD23, 'M', u'ضى'),\n    (0xFD24, 'M', u'ضي'),\n    (0xFD25, 'M', u'شج'),\n    (0xFD26, 'M', u'شح'),\n    (0xFD27, 'M', u'شخ'),\n    (0xFD28, 'M', u'شم'),\n    (0xFD29, 'M', u'شر'),\n    (0xFD2A, 'M', u'سر'),\n    (0xFD2B, 'M', u'صر'),\n    (0xFD2C, 'M', u'ضر'),\n    (0xFD2D, 'M', u'شج'),\n    (0xFD2E, 'M', u'شح'),\n    (0xFD2F, 'M', u'شخ'),\n    (0xFD30, 'M', u'شم'),\n    (0xFD31, 'M', u'سه'),\n    (0xFD32, 'M', u'شه'),\n    (0xFD33, 'M', u'طم'),\n    (0xFD34, 'M', u'سج'),\n    (0xFD35, 'M', u'سح'),\n    (0xFD36, 'M', u'سخ'),\n    (0xFD37, 'M', u'شج'),\n    (0xFD38, 'M', u'شح'),\n    (0xFD39, 'M', u'شخ'),\n    (0xFD3A, 'M', u'طم'),\n    (0xFD3B, 'M', u'ظم'),\n    (0xFD3C, 'M', u'اً'),\n    (0xFD3E, 'V'),\n    (0xFD40, 'X'),\n    (0xFD50, 'M', u'تجم'),\n    (0xFD51, 'M', u'تحج'),\n    (0xFD53, 'M', u'تحم'),\n    (0xFD54, 'M', u'تخم'),\n    (0xFD55, 'M', u'تمج'),\n    (0xFD56, 'M', u'تمح'),\n    (0xFD57, 'M', u'تمخ'),\n    (0xFD58, 'M', u'جمح'),\n    (0xFD5A, 'M', u'حمي'),\n    (0xFD5B, 'M', u'حمى'),\n    (0xFD5C, 'M', u'سحج'),\n    (0xFD5D, 'M', u'سجح'),\n    (0xFD5E, 'M', u'سجى'),\n    (0xFD5F, 'M', u'سمح'),\n    (0xFD61, 'M', u'سمج'),\n    (0xFD62, 'M', u'سمم'),\n    (0xFD64, 'M', u'صحح'),\n    (0xFD66, 'M', u'صمم'),\n    (0xFD67, 'M', u'شحم'),\n    (0xFD69, 'M', u'شجي'),\n    ]\n\ndef _seg_48():\n    return [\n    (0xFD6A, 'M', u'شمخ'),\n    (0xFD6C, 'M', u'شمم'),\n    (0xFD6E, 'M', u'ضحى'),\n    (0xFD6F, 'M', u'ضخم'),\n    (0xFD71, 'M', u'طمح'),\n    (0xFD73, 'M', u'طمم'),\n    (0xFD74, 'M', u'طمي'),\n    (0xFD75, 'M', u'عجم'),\n    (0xFD76, 'M', u'عمم'),\n    (0xFD78, 'M', u'عمى'),\n    (0xFD79, 'M', u'غمم'),\n    (0xFD7A, 'M', u'غمي'),\n    (0xFD7B, 'M', u'غمى'),\n    (0xFD7C, 'M', u'فخم'),\n    (0xFD7E, 'M', u'قمح'),\n    (0xFD7F, 'M', u'قمم'),\n    (0xFD80, 'M', u'لحم'),\n    (0xFD81, 'M', u'لحي'),\n    (0xFD82, 'M', u'لحى'),\n    (0xFD83, 'M', u'لجج'),\n    (0xFD85, 'M', u'لخم'),\n    (0xFD87, 'M', u'لمح'),\n    (0xFD89, 'M', u'محج'),\n    (0xFD8A, 'M', u'محم'),\n    (0xFD8B, 'M', u'محي'),\n    (0xFD8C, 'M', u'مجح'),\n    (0xFD8D, 'M', u'مجم'),\n    (0xFD8E, 'M', u'مخج'),\n    (0xFD8F, 'M', u'مخم'),\n    (0xFD90, 'X'),\n    (0xFD92, 'M', u'مجخ'),\n    (0xFD93, 'M', u'همج'),\n    (0xFD94, 'M', u'همم'),\n    (0xFD95, 'M', u'نحم'),\n    (0xFD96, 'M', u'نحى'),\n    (0xFD97, 'M', u'نجم'),\n    (0xFD99, 'M', u'نجى'),\n    (0xFD9A, 'M', u'نمي'),\n    (0xFD9B, 'M', u'نمى'),\n    (0xFD9C, 'M', u'يمم'),\n    (0xFD9E, 'M', u'بخي'),\n    (0xFD9F, 'M', u'تجي'),\n    (0xFDA0, 'M', u'تجى'),\n    (0xFDA1, 'M', u'تخي'),\n    (0xFDA2, 'M', u'تخى'),\n    (0xFDA3, 'M', u'تمي'),\n    (0xFDA4, 'M', u'تمى'),\n    (0xFDA5, 'M', u'جمي'),\n    (0xFDA6, 'M', u'جحى'),\n    (0xFDA7, 'M', u'جمى'),\n    (0xFDA8, 'M', u'سخى'),\n    (0xFDA9, 'M', u'صحي'),\n    (0xFDAA, 'M', u'شحي'),\n    (0xFDAB, 'M', u'ضحي'),\n    (0xFDAC, 'M', u'لجي'),\n    (0xFDAD, 'M', u'لمي'),\n    (0xFDAE, 'M', u'يحي'),\n    (0xFDAF, 'M', u'يجي'),\n    (0xFDB0, 'M', u'يمي'),\n    (0xFDB1, 'M', u'ممي'),\n    (0xFDB2, 'M', u'قمي'),\n    (0xFDB3, 'M', u'نحي'),\n    (0xFDB4, 'M', u'قمح'),\n    (0xFDB5, 'M', u'لحم'),\n    (0xFDB6, 'M', u'عمي'),\n    (0xFDB7, 'M', u'كمي'),\n    (0xFDB8, 'M', u'نجح'),\n    (0xFDB9, 'M', u'مخي'),\n    (0xFDBA, 'M', u'لجم'),\n    (0xFDBB, 'M', u'كمم'),\n    (0xFDBC, 'M', u'لجم'),\n    (0xFDBD, 'M', u'نجح'),\n    (0xFDBE, 'M', u'جحي'),\n    (0xFDBF, 'M', u'حجي'),\n    (0xFDC0, 'M', u'مجي'),\n    (0xFDC1, 'M', u'فمي'),\n    (0xFDC2, 'M', u'بحي'),\n    (0xFDC3, 'M', u'كمم'),\n    (0xFDC4, 'M', u'عجم'),\n    (0xFDC5, 'M', u'صمم'),\n    (0xFDC6, 'M', u'سخي'),\n    (0xFDC7, 'M', u'نجي'),\n    (0xFDC8, 'X'),\n    (0xFDF0, 'M', u'صلے'),\n    (0xFDF1, 'M', u'قلے'),\n    (0xFDF2, 'M', u'الله'),\n    (0xFDF3, 'M', u'اكبر'),\n    (0xFDF4, 'M', u'محمد'),\n    (0xFDF5, 'M', u'صلعم'),\n    (0xFDF6, 'M', u'رسول'),\n    (0xFDF7, 'M', u'عليه'),\n    (0xFDF8, 'M', u'وسلم'),\n    (0xFDF9, 'M', u'صلى'),\n    (0xFDFA, '3', u'صلى الله عليه وسلم'),\n    (0xFDFB, '3', u'جل جلاله'),\n    (0xFDFC, 'M', u'ریال'),\n    (0xFDFD, 'V'),\n    (0xFDFE, 'X'),\n    (0xFE00, 'I'),\n    (0xFE10, '3', u','),\n    ]\n\ndef _seg_49():\n    return [\n    (0xFE11, 'M', u'、'),\n    (0xFE12, 'X'),\n    (0xFE13, '3', u':'),\n    (0xFE14, '3', u';'),\n    (0xFE15, '3', u'!'),\n    (0xFE16, '3', u'?'),\n    (0xFE17, 'M', u'〖'),\n    (0xFE18, 'M', u'〗'),\n    (0xFE19, 'X'),\n    (0xFE20, 'V'),\n    (0xFE30, 'X'),\n    (0xFE31, 'M', u'—'),\n    (0xFE32, 'M', u'–'),\n    (0xFE33, '3', u'_'),\n    (0xFE35, '3', u'('),\n    (0xFE36, '3', u')'),\n    (0xFE37, '3', u'{'),\n    (0xFE38, '3', u'}'),\n    (0xFE39, 'M', u'〔'),\n    (0xFE3A, 'M', u'〕'),\n    (0xFE3B, 'M', u'【'),\n    (0xFE3C, 'M', u'】'),\n    (0xFE3D, 'M', u'《'),\n    (0xFE3E, 'M', u'》'),\n    (0xFE3F, 'M', u'〈'),\n    (0xFE40, 'M', u'〉'),\n    (0xFE41, 'M', u'「'),\n    (0xFE42, 'M', u'」'),\n    (0xFE43, 'M', u'『'),\n    (0xFE44, 'M', u'』'),\n    (0xFE45, 'V'),\n    (0xFE47, '3', u'['),\n    (0xFE48, '3', u']'),\n    (0xFE49, '3', u' ̅'),\n    (0xFE4D, '3', u'_'),\n    (0xFE50, '3', u','),\n    (0xFE51, 'M', u'、'),\n    (0xFE52, 'X'),\n    (0xFE54, '3', u';'),\n    (0xFE55, '3', u':'),\n    (0xFE56, '3', u'?'),\n    (0xFE57, '3', u'!'),\n    (0xFE58, 'M', u'—'),\n    (0xFE59, '3', u'('),\n    (0xFE5A, '3', u')'),\n    (0xFE5B, '3', u'{'),\n    (0xFE5C, '3', u'}'),\n    (0xFE5D, 'M', u'〔'),\n    (0xFE5E, 'M', u'〕'),\n    (0xFE5F, '3', u'#'),\n    (0xFE60, '3', u'&'),\n    (0xFE61, '3', u'*'),\n    (0xFE62, '3', u'+'),\n    (0xFE63, 'M', u'-'),\n    (0xFE64, '3', u'<'),\n    (0xFE65, '3', u'>'),\n    (0xFE66, '3', u'='),\n    (0xFE67, 'X'),\n    (0xFE68, '3', u'\\\\'),\n    (0xFE69, '3', u'$'),\n    (0xFE6A, '3', u'%'),\n    (0xFE6B, '3', u'@'),\n    (0xFE6C, 'X'),\n    (0xFE70, '3', u' ً'),\n    (0xFE71, 'M', u'ـً'),\n    (0xFE72, '3', u' ٌ'),\n    (0xFE73, 'V'),\n    (0xFE74, '3', u' ٍ'),\n    (0xFE75, 'X'),\n    (0xFE76, '3', u' َ'),\n    (0xFE77, 'M', u'ـَ'),\n    (0xFE78, '3', u' ُ'),\n    (0xFE79, 'M', u'ـُ'),\n    (0xFE7A, '3', u' ِ'),\n    (0xFE7B, 'M', u'ـِ'),\n    (0xFE7C, '3', u' ّ'),\n    (0xFE7D, 'M', u'ـّ'),\n    (0xFE7E, '3', u' ْ'),\n    (0xFE7F, 'M', u'ـْ'),\n    (0xFE80, 'M', u'ء'),\n    (0xFE81, 'M', u'آ'),\n    (0xFE83, 'M', u'أ'),\n    (0xFE85, 'M', u'ؤ'),\n    (0xFE87, 'M', u'إ'),\n    (0xFE89, 'M', u'ئ'),\n    (0xFE8D, 'M', u'ا'),\n    (0xFE8F, 'M', u'ب'),\n    (0xFE93, 'M', u'ة'),\n    (0xFE95, 'M', u'ت'),\n    (0xFE99, 'M', u'ث'),\n    (0xFE9D, 'M', u'ج'),\n    (0xFEA1, 'M', u'ح'),\n    (0xFEA5, 'M', u'خ'),\n    (0xFEA9, 'M', u'د'),\n    (0xFEAB, 'M', u'ذ'),\n    (0xFEAD, 'M', u'ر'),\n    (0xFEAF, 'M', u'ز'),\n    (0xFEB1, 'M', u'س'),\n    (0xFEB5, 'M', u'ش'),\n    (0xFEB9, 'M', u'ص'),\n    ]\n\ndef _seg_50():\n    return [\n    (0xFEBD, 'M', u'ض'),\n    (0xFEC1, 'M', u'ط'),\n    (0xFEC5, 'M', u'ظ'),\n    (0xFEC9, 'M', u'ع'),\n    (0xFECD, 'M', u'غ'),\n    (0xFED1, 'M', u'ف'),\n    (0xFED5, 'M', u'ق'),\n    (0xFED9, 'M', u'ك'),\n    (0xFEDD, 'M', u'ل'),\n    (0xFEE1, 'M', u'م'),\n    (0xFEE5, 'M', u'ن'),\n    (0xFEE9, 'M', u'ه'),\n    (0xFEED, 'M', u'و'),\n    (0xFEEF, 'M', u'ى'),\n    (0xFEF1, 'M', u'ي'),\n    (0xFEF5, 'M', u'لآ'),\n    (0xFEF7, 'M', u'لأ'),\n    (0xFEF9, 'M', u'لإ'),\n    (0xFEFB, 'M', u'لا'),\n    (0xFEFD, 'X'),\n    (0xFEFF, 'I'),\n    (0xFF00, 'X'),\n    (0xFF01, '3', u'!'),\n    (0xFF02, '3', u'\"'),\n    (0xFF03, '3', u'#'),\n    (0xFF04, '3', u'$'),\n    (0xFF05, '3', u'%'),\n    (0xFF06, '3', u'&'),\n    (0xFF07, '3', u'\\''),\n    (0xFF08, '3', u'('),\n    (0xFF09, '3', u')'),\n    (0xFF0A, '3', u'*'),\n    (0xFF0B, '3', u'+'),\n    (0xFF0C, '3', u','),\n    (0xFF0D, 'M', u'-'),\n    (0xFF0E, 'M', u'.'),\n    (0xFF0F, '3', u'/'),\n    (0xFF10, 'M', u'0'),\n    (0xFF11, 'M', u'1'),\n    (0xFF12, 'M', u'2'),\n    (0xFF13, 'M', u'3'),\n    (0xFF14, 'M', u'4'),\n    (0xFF15, 'M', u'5'),\n    (0xFF16, 'M', u'6'),\n    (0xFF17, 'M', u'7'),\n    (0xFF18, 'M', u'8'),\n    (0xFF19, 'M', u'9'),\n    (0xFF1A, '3', u':'),\n    (0xFF1B, '3', u';'),\n    (0xFF1C, '3', u'<'),\n    (0xFF1D, '3', u'='),\n    (0xFF1E, '3', u'>'),\n    (0xFF1F, '3', u'?'),\n    (0xFF20, '3', u'@'),\n    (0xFF21, 'M', u'a'),\n    (0xFF22, 'M', u'b'),\n    (0xFF23, 'M', u'c'),\n    (0xFF24, 'M', u'd'),\n    (0xFF25, 'M', u'e'),\n    (0xFF26, 'M', u'f'),\n    (0xFF27, 'M', u'g'),\n    (0xFF28, 'M', u'h'),\n    (0xFF29, 'M', u'i'),\n    (0xFF2A, 'M', u'j'),\n    (0xFF2B, 'M', u'k'),\n    (0xFF2C, 'M', u'l'),\n    (0xFF2D, 'M', u'm'),\n    (0xFF2E, 'M', u'n'),\n    (0xFF2F, 'M', u'o'),\n    (0xFF30, 'M', u'p'),\n    (0xFF31, 'M', u'q'),\n    (0xFF32, 'M', u'r'),\n    (0xFF33, 'M', u's'),\n    (0xFF34, 'M', u't'),\n    (0xFF35, 'M', u'u'),\n    (0xFF36, 'M', u'v'),\n    (0xFF37, 'M', u'w'),\n    (0xFF38, 'M', u'x'),\n    (0xFF39, 'M', u'y'),\n    (0xFF3A, 'M', u'z'),\n    (0xFF3B, '3', u'['),\n    (0xFF3C, '3', u'\\\\'),\n    (0xFF3D, '3', u']'),\n    (0xFF3E, '3', u'^'),\n    (0xFF3F, '3', u'_'),\n    (0xFF40, '3', u'`'),\n    (0xFF41, 'M', u'a'),\n    (0xFF42, 'M', u'b'),\n    (0xFF43, 'M', u'c'),\n    (0xFF44, 'M', u'd'),\n    (0xFF45, 'M', u'e'),\n    (0xFF46, 'M', u'f'),\n    (0xFF47, 'M', u'g'),\n    (0xFF48, 'M', u'h'),\n    (0xFF49, 'M', u'i'),\n    (0xFF4A, 'M', u'j'),\n    (0xFF4B, 'M', u'k'),\n    (0xFF4C, 'M', u'l'),\n    (0xFF4D, 'M', u'm'),\n    (0xFF4E, 'M', u'n'),\n    ]\n\ndef _seg_51():\n    return [\n    (0xFF4F, 'M', u'o'),\n    (0xFF50, 'M', u'p'),\n    (0xFF51, 'M', u'q'),\n    (0xFF52, 'M', u'r'),\n    (0xFF53, 'M', u's'),\n    (0xFF54, 'M', u't'),\n    (0xFF55, 'M', u'u'),\n    (0xFF56, 'M', u'v'),\n    (0xFF57, 'M', u'w'),\n    (0xFF58, 'M', u'x'),\n    (0xFF59, 'M', u'y'),\n    (0xFF5A, 'M', u'z'),\n    (0xFF5B, '3', u'{'),\n    (0xFF5C, '3', u'|'),\n    (0xFF5D, '3', u'}'),\n    (0xFF5E, '3', u'~'),\n    (0xFF5F, 'M', u'⦅'),\n    (0xFF60, 'M', u'⦆'),\n    (0xFF61, 'M', u'.'),\n    (0xFF62, 'M', u'「'),\n    (0xFF63, 'M', u'」'),\n    (0xFF64, 'M', u'、'),\n    (0xFF65, 'M', u'・'),\n    (0xFF66, 'M', u'ヲ'),\n    (0xFF67, 'M', u'ァ'),\n    (0xFF68, 'M', u'ィ'),\n    (0xFF69, 'M', u'ゥ'),\n    (0xFF6A, 'M', u'ェ'),\n    (0xFF6B, 'M', u'ォ'),\n    (0xFF6C, 'M', u'ャ'),\n    (0xFF6D, 'M', u'ュ'),\n    (0xFF6E, 'M', u'ョ'),\n    (0xFF6F, 'M', u'ッ'),\n    (0xFF70, 'M', u'ー'),\n    (0xFF71, 'M', u'ア'),\n    (0xFF72, 'M', u'イ'),\n    (0xFF73, 'M', u'ウ'),\n    (0xFF74, 'M', u'エ'),\n    (0xFF75, 'M', u'オ'),\n    (0xFF76, 'M', u'カ'),\n    (0xFF77, 'M', u'キ'),\n    (0xFF78, 'M', u'ク'),\n    (0xFF79, 'M', u'ケ'),\n    (0xFF7A, 'M', u'コ'),\n    (0xFF7B, 'M', u'サ'),\n    (0xFF7C, 'M', u'シ'),\n    (0xFF7D, 'M', u'ス'),\n    (0xFF7E, 'M', u'セ'),\n    (0xFF7F, 'M', u'ソ'),\n    (0xFF80, 'M', u'タ'),\n    (0xFF81, 'M', u'チ'),\n    (0xFF82, 'M', u'ツ'),\n    (0xFF83, 'M', u'テ'),\n    (0xFF84, 'M', u'ト'),\n    (0xFF85, 'M', u'ナ'),\n    (0xFF86, 'M', u'ニ'),\n    (0xFF87, 'M', u'ヌ'),\n    (0xFF88, 'M', u'ネ'),\n    (0xFF89, 'M', u'ノ'),\n    (0xFF8A, 'M', u'ハ'),\n    (0xFF8B, 'M', u'ヒ'),\n    (0xFF8C, 'M', u'フ'),\n    (0xFF8D, 'M', u'ヘ'),\n    (0xFF8E, 'M', u'ホ'),\n    (0xFF8F, 'M', u'マ'),\n    (0xFF90, 'M', u'ミ'),\n    (0xFF91, 'M', u'ム'),\n    (0xFF92, 'M', u'メ'),\n    (0xFF93, 'M', u'モ'),\n    (0xFF94, 'M', u'ヤ'),\n    (0xFF95, 'M', u'ユ'),\n    (0xFF96, 'M', u'ヨ'),\n    (0xFF97, 'M', u'ラ'),\n    (0xFF98, 'M', u'リ'),\n    (0xFF99, 'M', u'ル'),\n    (0xFF9A, 'M', u'レ'),\n    (0xFF9B, 'M', u'ロ'),\n    (0xFF9C, 'M', u'ワ'),\n    (0xFF9D, 'M', u'ン'),\n    (0xFF9E, 'M', u'゙'),\n    (0xFF9F, 'M', u'゚'),\n    (0xFFA0, 'X'),\n    (0xFFA1, 'M', u'ᄀ'),\n    (0xFFA2, 'M', u'ᄁ'),\n    (0xFFA3, 'M', u'ᆪ'),\n    (0xFFA4, 'M', u'ᄂ'),\n    (0xFFA5, 'M', u'ᆬ'),\n    (0xFFA6, 'M', u'ᆭ'),\n    (0xFFA7, 'M', u'ᄃ'),\n    (0xFFA8, 'M', u'ᄄ'),\n    (0xFFA9, 'M', u'ᄅ'),\n    (0xFFAA, 'M', u'ᆰ'),\n    (0xFFAB, 'M', u'ᆱ'),\n    (0xFFAC, 'M', u'ᆲ'),\n    (0xFFAD, 'M', u'ᆳ'),\n    (0xFFAE, 'M', u'ᆴ'),\n    (0xFFAF, 'M', u'ᆵ'),\n    (0xFFB0, 'M', u'ᄚ'),\n    (0xFFB1, 'M', u'ᄆ'),\n    (0xFFB2, 'M', u'ᄇ'),\n    ]\n\ndef _seg_52():\n    return [\n    (0xFFB3, 'M', u'ᄈ'),\n    (0xFFB4, 'M', u'ᄡ'),\n    (0xFFB5, 'M', u'ᄉ'),\n    (0xFFB6, 'M', u'ᄊ'),\n    (0xFFB7, 'M', u'ᄋ'),\n    (0xFFB8, 'M', u'ᄌ'),\n    (0xFFB9, 'M', u'ᄍ'),\n    (0xFFBA, 'M', u'ᄎ'),\n    (0xFFBB, 'M', u'ᄏ'),\n    (0xFFBC, 'M', u'ᄐ'),\n    (0xFFBD, 'M', u'ᄑ'),\n    (0xFFBE, 'M', u'ᄒ'),\n    (0xFFBF, 'X'),\n    (0xFFC2, 'M', u'ᅡ'),\n    (0xFFC3, 'M', u'ᅢ'),\n    (0xFFC4, 'M', u'ᅣ'),\n    (0xFFC5, 'M', u'ᅤ'),\n    (0xFFC6, 'M', u'ᅥ'),\n    (0xFFC7, 'M', u'ᅦ'),\n    (0xFFC8, 'X'),\n    (0xFFCA, 'M', u'ᅧ'),\n    (0xFFCB, 'M', u'ᅨ'),\n    (0xFFCC, 'M', u'ᅩ'),\n    (0xFFCD, 'M', u'ᅪ'),\n    (0xFFCE, 'M', u'ᅫ'),\n    (0xFFCF, 'M', u'ᅬ'),\n    (0xFFD0, 'X'),\n    (0xFFD2, 'M', u'ᅭ'),\n    (0xFFD3, 'M', u'ᅮ'),\n    (0xFFD4, 'M', u'ᅯ'),\n    (0xFFD5, 'M', u'ᅰ'),\n    (0xFFD6, 'M', u'ᅱ'),\n    (0xFFD7, 'M', u'ᅲ'),\n    (0xFFD8, 'X'),\n    (0xFFDA, 'M', u'ᅳ'),\n    (0xFFDB, 'M', u'ᅴ'),\n    (0xFFDC, 'M', u'ᅵ'),\n    (0xFFDD, 'X'),\n    (0xFFE0, 'M', u'¢'),\n    (0xFFE1, 'M', u'£'),\n    (0xFFE2, 'M', u'¬'),\n    (0xFFE3, '3', u' ̄'),\n    (0xFFE4, 'M', u'¦'),\n    (0xFFE5, 'M', u'¥'),\n    (0xFFE6, 'M', u'₩'),\n    (0xFFE7, 'X'),\n    (0xFFE8, 'M', u'│'),\n    (0xFFE9, 'M', u'←'),\n    (0xFFEA, 'M', u'↑'),\n    (0xFFEB, 'M', u'→'),\n    (0xFFEC, 'M', u'↓'),\n    (0xFFED, 'M', u'■'),\n    (0xFFEE, 'M', u'○'),\n    (0xFFEF, 'X'),\n    (0x10000, 'V'),\n    (0x1000C, 'X'),\n    (0x1000D, 'V'),\n    (0x10027, 'X'),\n    (0x10028, 'V'),\n    (0x1003B, 'X'),\n    (0x1003C, 'V'),\n    (0x1003E, 'X'),\n    (0x1003F, 'V'),\n    (0x1004E, 'X'),\n    (0x10050, 'V'),\n    (0x1005E, 'X'),\n    (0x10080, 'V'),\n    (0x100FB, 'X'),\n    (0x10100, 'V'),\n    (0x10103, 'X'),\n    (0x10107, 'V'),\n    (0x10134, 'X'),\n    (0x10137, 'V'),\n    (0x1018F, 'X'),\n    (0x10190, 'V'),\n    (0x1019C, 'X'),\n    (0x101A0, 'V'),\n    (0x101A1, 'X'),\n    (0x101D0, 'V'),\n    (0x101FE, 'X'),\n    (0x10280, 'V'),\n    (0x1029D, 'X'),\n    (0x102A0, 'V'),\n    (0x102D1, 'X'),\n    (0x102E0, 'V'),\n    (0x102FC, 'X'),\n    (0x10300, 'V'),\n    (0x10324, 'X'),\n    (0x1032D, 'V'),\n    (0x1034B, 'X'),\n    (0x10350, 'V'),\n    (0x1037B, 'X'),\n    (0x10380, 'V'),\n    (0x1039E, 'X'),\n    (0x1039F, 'V'),\n    (0x103C4, 'X'),\n    (0x103C8, 'V'),\n    (0x103D6, 'X'),\n    (0x10400, 'M', u'𐐨'),\n    (0x10401, 'M', u'𐐩'),\n    ]\n\ndef _seg_53():\n    return [\n    (0x10402, 'M', u'𐐪'),\n    (0x10403, 'M', u'𐐫'),\n    (0x10404, 'M', u'𐐬'),\n    (0x10405, 'M', u'𐐭'),\n    (0x10406, 'M', u'𐐮'),\n    (0x10407, 'M', u'𐐯'),\n    (0x10408, 'M', u'𐐰'),\n    (0x10409, 'M', u'𐐱'),\n    (0x1040A, 'M', u'𐐲'),\n    (0x1040B, 'M', u'𐐳'),\n    (0x1040C, 'M', u'𐐴'),\n    (0x1040D, 'M', u'𐐵'),\n    (0x1040E, 'M', u'𐐶'),\n    (0x1040F, 'M', u'𐐷'),\n    (0x10410, 'M', u'𐐸'),\n    (0x10411, 'M', u'𐐹'),\n    (0x10412, 'M', u'𐐺'),\n    (0x10413, 'M', u'𐐻'),\n    (0x10414, 'M', u'𐐼'),\n    (0x10415, 'M', u'𐐽'),\n    (0x10416, 'M', u'𐐾'),\n    (0x10417, 'M', u'𐐿'),\n    (0x10418, 'M', u'𐑀'),\n    (0x10419, 'M', u'𐑁'),\n    (0x1041A, 'M', u'𐑂'),\n    (0x1041B, 'M', u'𐑃'),\n    (0x1041C, 'M', u'𐑄'),\n    (0x1041D, 'M', u'𐑅'),\n    (0x1041E, 'M', u'𐑆'),\n    (0x1041F, 'M', u'𐑇'),\n    (0x10420, 'M', u'𐑈'),\n    (0x10421, 'M', u'𐑉'),\n    (0x10422, 'M', u'𐑊'),\n    (0x10423, 'M', u'𐑋'),\n    (0x10424, 'M', u'𐑌'),\n    (0x10425, 'M', u'𐑍'),\n    (0x10426, 'M', u'𐑎'),\n    (0x10427, 'M', u'𐑏'),\n    (0x10428, 'V'),\n    (0x1049E, 'X'),\n    (0x104A0, 'V'),\n    (0x104AA, 'X'),\n    (0x104B0, 'M', u'𐓘'),\n    (0x104B1, 'M', u'𐓙'),\n    (0x104B2, 'M', u'𐓚'),\n    (0x104B3, 'M', u'𐓛'),\n    (0x104B4, 'M', u'𐓜'),\n    (0x104B5, 'M', u'𐓝'),\n    (0x104B6, 'M', u'𐓞'),\n    (0x104B7, 'M', u'𐓟'),\n    (0x104B8, 'M', u'𐓠'),\n    (0x104B9, 'M', u'𐓡'),\n    (0x104BA, 'M', u'𐓢'),\n    (0x104BB, 'M', u'𐓣'),\n    (0x104BC, 'M', u'𐓤'),\n    (0x104BD, 'M', u'𐓥'),\n    (0x104BE, 'M', u'𐓦'),\n    (0x104BF, 'M', u'𐓧'),\n    (0x104C0, 'M', u'𐓨'),\n    (0x104C1, 'M', u'𐓩'),\n    (0x104C2, 'M', u'𐓪'),\n    (0x104C3, 'M', u'𐓫'),\n    (0x104C4, 'M', u'𐓬'),\n    (0x104C5, 'M', u'𐓭'),\n    (0x104C6, 'M', u'𐓮'),\n    (0x104C7, 'M', u'𐓯'),\n    (0x104C8, 'M', u'𐓰'),\n    (0x104C9, 'M', u'𐓱'),\n    (0x104CA, 'M', u'𐓲'),\n    (0x104CB, 'M', u'𐓳'),\n    (0x104CC, 'M', u'𐓴'),\n    (0x104CD, 'M', u'𐓵'),\n    (0x104CE, 'M', u'𐓶'),\n    (0x104CF, 'M', u'𐓷'),\n    (0x104D0, 'M', u'𐓸'),\n    (0x104D1, 'M', u'𐓹'),\n    (0x104D2, 'M', u'𐓺'),\n    (0x104D3, 'M', u'𐓻'),\n    (0x104D4, 'X'),\n    (0x104D8, 'V'),\n    (0x104FC, 'X'),\n    (0x10500, 'V'),\n    (0x10528, 'X'),\n    (0x10530, 'V'),\n    (0x10564, 'X'),\n    (0x1056F, 'V'),\n    (0x10570, 'X'),\n    (0x10600, 'V'),\n    (0x10737, 'X'),\n    (0x10740, 'V'),\n    (0x10756, 'X'),\n    (0x10760, 'V'),\n    (0x10768, 'X'),\n    (0x10800, 'V'),\n    (0x10806, 'X'),\n    (0x10808, 'V'),\n    (0x10809, 'X'),\n    (0x1080A, 'V'),\n    (0x10836, 'X'),\n    (0x10837, 'V'),\n    ]\n\ndef _seg_54():\n    return [\n    (0x10839, 'X'),\n    (0x1083C, 'V'),\n    (0x1083D, 'X'),\n    (0x1083F, 'V'),\n    (0x10856, 'X'),\n    (0x10857, 'V'),\n    (0x1089F, 'X'),\n    (0x108A7, 'V'),\n    (0x108B0, 'X'),\n    (0x108E0, 'V'),\n    (0x108F3, 'X'),\n    (0x108F4, 'V'),\n    (0x108F6, 'X'),\n    (0x108FB, 'V'),\n    (0x1091C, 'X'),\n    (0x1091F, 'V'),\n    (0x1093A, 'X'),\n    (0x1093F, 'V'),\n    (0x10940, 'X'),\n    (0x10980, 'V'),\n    (0x109B8, 'X'),\n    (0x109BC, 'V'),\n    (0x109D0, 'X'),\n    (0x109D2, 'V'),\n    (0x10A04, 'X'),\n    (0x10A05, 'V'),\n    (0x10A07, 'X'),\n    (0x10A0C, 'V'),\n    (0x10A14, 'X'),\n    (0x10A15, 'V'),\n    (0x10A18, 'X'),\n    (0x10A19, 'V'),\n    (0x10A36, 'X'),\n    (0x10A38, 'V'),\n    (0x10A3B, 'X'),\n    (0x10A3F, 'V'),\n    (0x10A49, 'X'),\n    (0x10A50, 'V'),\n    (0x10A59, 'X'),\n    (0x10A60, 'V'),\n    (0x10AA0, 'X'),\n    (0x10AC0, 'V'),\n    (0x10AE7, 'X'),\n    (0x10AEB, 'V'),\n    (0x10AF7, 'X'),\n    (0x10B00, 'V'),\n    (0x10B36, 'X'),\n    (0x10B39, 'V'),\n    (0x10B56, 'X'),\n    (0x10B58, 'V'),\n    (0x10B73, 'X'),\n    (0x10B78, 'V'),\n    (0x10B92, 'X'),\n    (0x10B99, 'V'),\n    (0x10B9D, 'X'),\n    (0x10BA9, 'V'),\n    (0x10BB0, 'X'),\n    (0x10C00, 'V'),\n    (0x10C49, 'X'),\n    (0x10C80, 'M', u'𐳀'),\n    (0x10C81, 'M', u'𐳁'),\n    (0x10C82, 'M', u'𐳂'),\n    (0x10C83, 'M', u'𐳃'),\n    (0x10C84, 'M', u'𐳄'),\n    (0x10C85, 'M', u'𐳅'),\n    (0x10C86, 'M', u'𐳆'),\n    (0x10C87, 'M', u'𐳇'),\n    (0x10C88, 'M', u'𐳈'),\n    (0x10C89, 'M', u'𐳉'),\n    (0x10C8A, 'M', u'𐳊'),\n    (0x10C8B, 'M', u'𐳋'),\n    (0x10C8C, 'M', u'𐳌'),\n    (0x10C8D, 'M', u'𐳍'),\n    (0x10C8E, 'M', u'𐳎'),\n    (0x10C8F, 'M', u'𐳏'),\n    (0x10C90, 'M', u'𐳐'),\n    (0x10C91, 'M', u'𐳑'),\n    (0x10C92, 'M', u'𐳒'),\n    (0x10C93, 'M', u'𐳓'),\n    (0x10C94, 'M', u'𐳔'),\n    (0x10C95, 'M', u'𐳕'),\n    (0x10C96, 'M', u'𐳖'),\n    (0x10C97, 'M', u'𐳗'),\n    (0x10C98, 'M', u'𐳘'),\n    (0x10C99, 'M', u'𐳙'),\n    (0x10C9A, 'M', u'𐳚'),\n    (0x10C9B, 'M', u'𐳛'),\n    (0x10C9C, 'M', u'𐳜'),\n    (0x10C9D, 'M', u'𐳝'),\n    (0x10C9E, 'M', u'𐳞'),\n    (0x10C9F, 'M', u'𐳟'),\n    (0x10CA0, 'M', u'𐳠'),\n    (0x10CA1, 'M', u'𐳡'),\n    (0x10CA2, 'M', u'𐳢'),\n    (0x10CA3, 'M', u'𐳣'),\n    (0x10CA4, 'M', u'𐳤'),\n    (0x10CA5, 'M', u'𐳥'),\n    (0x10CA6, 'M', u'𐳦'),\n    (0x10CA7, 'M', u'𐳧'),\n    (0x10CA8, 'M', u'𐳨'),\n    ]\n\ndef _seg_55():\n    return [\n    (0x10CA9, 'M', u'𐳩'),\n    (0x10CAA, 'M', u'𐳪'),\n    (0x10CAB, 'M', u'𐳫'),\n    (0x10CAC, 'M', u'𐳬'),\n    (0x10CAD, 'M', u'𐳭'),\n    (0x10CAE, 'M', u'𐳮'),\n    (0x10CAF, 'M', u'𐳯'),\n    (0x10CB0, 'M', u'𐳰'),\n    (0x10CB1, 'M', u'𐳱'),\n    (0x10CB2, 'M', u'𐳲'),\n    (0x10CB3, 'X'),\n    (0x10CC0, 'V'),\n    (0x10CF3, 'X'),\n    (0x10CFA, 'V'),\n    (0x10D28, 'X'),\n    (0x10D30, 'V'),\n    (0x10D3A, 'X'),\n    (0x10E60, 'V'),\n    (0x10E7F, 'X'),\n    (0x10F00, 'V'),\n    (0x10F28, 'X'),\n    (0x10F30, 'V'),\n    (0x10F5A, 'X'),\n    (0x11000, 'V'),\n    (0x1104E, 'X'),\n    (0x11052, 'V'),\n    (0x11070, 'X'),\n    (0x1107F, 'V'),\n    (0x110BD, 'X'),\n    (0x110BE, 'V'),\n    (0x110C2, 'X'),\n    (0x110D0, 'V'),\n    (0x110E9, 'X'),\n    (0x110F0, 'V'),\n    (0x110FA, 'X'),\n    (0x11100, 'V'),\n    (0x11135, 'X'),\n    (0x11136, 'V'),\n    (0x11147, 'X'),\n    (0x11150, 'V'),\n    (0x11177, 'X'),\n    (0x11180, 'V'),\n    (0x111CE, 'X'),\n    (0x111D0, 'V'),\n    (0x111E0, 'X'),\n    (0x111E1, 'V'),\n    (0x111F5, 'X'),\n    (0x11200, 'V'),\n    (0x11212, 'X'),\n    (0x11213, 'V'),\n    (0x1123F, 'X'),\n    (0x11280, 'V'),\n    (0x11287, 'X'),\n    (0x11288, 'V'),\n    (0x11289, 'X'),\n    (0x1128A, 'V'),\n    (0x1128E, 'X'),\n    (0x1128F, 'V'),\n    (0x1129E, 'X'),\n    (0x1129F, 'V'),\n    (0x112AA, 'X'),\n    (0x112B0, 'V'),\n    (0x112EB, 'X'),\n    (0x112F0, 'V'),\n    (0x112FA, 'X'),\n    (0x11300, 'V'),\n    (0x11304, 'X'),\n    (0x11305, 'V'),\n    (0x1130D, 'X'),\n    (0x1130F, 'V'),\n    (0x11311, 'X'),\n    (0x11313, 'V'),\n    (0x11329, 'X'),\n    (0x1132A, 'V'),\n    (0x11331, 'X'),\n    (0x11332, 'V'),\n    (0x11334, 'X'),\n    (0x11335, 'V'),\n    (0x1133A, 'X'),\n    (0x1133B, 'V'),\n    (0x11345, 'X'),\n    (0x11347, 'V'),\n    (0x11349, 'X'),\n    (0x1134B, 'V'),\n    (0x1134E, 'X'),\n    (0x11350, 'V'),\n    (0x11351, 'X'),\n    (0x11357, 'V'),\n    (0x11358, 'X'),\n    (0x1135D, 'V'),\n    (0x11364, 'X'),\n    (0x11366, 'V'),\n    (0x1136D, 'X'),\n    (0x11370, 'V'),\n    (0x11375, 'X'),\n    (0x11400, 'V'),\n    (0x1145A, 'X'),\n    (0x1145B, 'V'),\n    (0x1145C, 'X'),\n    (0x1145D, 'V'),\n    ]\n\ndef _seg_56():\n    return [\n    (0x1145F, 'X'),\n    (0x11480, 'V'),\n    (0x114C8, 'X'),\n    (0x114D0, 'V'),\n    (0x114DA, 'X'),\n    (0x11580, 'V'),\n    (0x115B6, 'X'),\n    (0x115B8, 'V'),\n    (0x115DE, 'X'),\n    (0x11600, 'V'),\n    (0x11645, 'X'),\n    (0x11650, 'V'),\n    (0x1165A, 'X'),\n    (0x11660, 'V'),\n    (0x1166D, 'X'),\n    (0x11680, 'V'),\n    (0x116B8, 'X'),\n    (0x116C0, 'V'),\n    (0x116CA, 'X'),\n    (0x11700, 'V'),\n    (0x1171B, 'X'),\n    (0x1171D, 'V'),\n    (0x1172C, 'X'),\n    (0x11730, 'V'),\n    (0x11740, 'X'),\n    (0x11800, 'V'),\n    (0x1183C, 'X'),\n    (0x118A0, 'M', u'𑣀'),\n    (0x118A1, 'M', u'𑣁'),\n    (0x118A2, 'M', u'𑣂'),\n    (0x118A3, 'M', u'𑣃'),\n    (0x118A4, 'M', u'𑣄'),\n    (0x118A5, 'M', u'𑣅'),\n    (0x118A6, 'M', u'𑣆'),\n    (0x118A7, 'M', u'𑣇'),\n    (0x118A8, 'M', u'𑣈'),\n    (0x118A9, 'M', u'𑣉'),\n    (0x118AA, 'M', u'𑣊'),\n    (0x118AB, 'M', u'𑣋'),\n    (0x118AC, 'M', u'𑣌'),\n    (0x118AD, 'M', u'𑣍'),\n    (0x118AE, 'M', u'𑣎'),\n    (0x118AF, 'M', u'𑣏'),\n    (0x118B0, 'M', u'𑣐'),\n    (0x118B1, 'M', u'𑣑'),\n    (0x118B2, 'M', u'𑣒'),\n    (0x118B3, 'M', u'𑣓'),\n    (0x118B4, 'M', u'𑣔'),\n    (0x118B5, 'M', u'𑣕'),\n    (0x118B6, 'M', u'𑣖'),\n    (0x118B7, 'M', u'𑣗'),\n    (0x118B8, 'M', u'𑣘'),\n    (0x118B9, 'M', u'𑣙'),\n    (0x118BA, 'M', u'𑣚'),\n    (0x118BB, 'M', u'𑣛'),\n    (0x118BC, 'M', u'𑣜'),\n    (0x118BD, 'M', u'𑣝'),\n    (0x118BE, 'M', u'𑣞'),\n    (0x118BF, 'M', u'𑣟'),\n    (0x118C0, 'V'),\n    (0x118F3, 'X'),\n    (0x118FF, 'V'),\n    (0x11900, 'X'),\n    (0x11A00, 'V'),\n    (0x11A48, 'X'),\n    (0x11A50, 'V'),\n    (0x11A84, 'X'),\n    (0x11A86, 'V'),\n    (0x11AA3, 'X'),\n    (0x11AC0, 'V'),\n    (0x11AF9, 'X'),\n    (0x11C00, 'V'),\n    (0x11C09, 'X'),\n    (0x11C0A, 'V'),\n    (0x11C37, 'X'),\n    (0x11C38, 'V'),\n    (0x11C46, 'X'),\n    (0x11C50, 'V'),\n    (0x11C6D, 'X'),\n    (0x11C70, 'V'),\n    (0x11C90, 'X'),\n    (0x11C92, 'V'),\n    (0x11CA8, 'X'),\n    (0x11CA9, 'V'),\n    (0x11CB7, 'X'),\n    (0x11D00, 'V'),\n    (0x11D07, 'X'),\n    (0x11D08, 'V'),\n    (0x11D0A, 'X'),\n    (0x11D0B, 'V'),\n    (0x11D37, 'X'),\n    (0x11D3A, 'V'),\n    (0x11D3B, 'X'),\n    (0x11D3C, 'V'),\n    (0x11D3E, 'X'),\n    (0x11D3F, 'V'),\n    (0x11D48, 'X'),\n    (0x11D50, 'V'),\n    (0x11D5A, 'X'),\n    (0x11D60, 'V'),\n    ]\n\ndef _seg_57():\n    return [\n    (0x11D66, 'X'),\n    (0x11D67, 'V'),\n    (0x11D69, 'X'),\n    (0x11D6A, 'V'),\n    (0x11D8F, 'X'),\n    (0x11D90, 'V'),\n    (0x11D92, 'X'),\n    (0x11D93, 'V'),\n    (0x11D99, 'X'),\n    (0x11DA0, 'V'),\n    (0x11DAA, 'X'),\n    (0x11EE0, 'V'),\n    (0x11EF9, 'X'),\n    (0x12000, 'V'),\n    (0x1239A, 'X'),\n    (0x12400, 'V'),\n    (0x1246F, 'X'),\n    (0x12470, 'V'),\n    (0x12475, 'X'),\n    (0x12480, 'V'),\n    (0x12544, 'X'),\n    (0x13000, 'V'),\n    (0x1342F, 'X'),\n    (0x14400, 'V'),\n    (0x14647, 'X'),\n    (0x16800, 'V'),\n    (0x16A39, 'X'),\n    (0x16A40, 'V'),\n    (0x16A5F, 'X'),\n    (0x16A60, 'V'),\n    (0x16A6A, 'X'),\n    (0x16A6E, 'V'),\n    (0x16A70, 'X'),\n    (0x16AD0, 'V'),\n    (0x16AEE, 'X'),\n    (0x16AF0, 'V'),\n    (0x16AF6, 'X'),\n    (0x16B00, 'V'),\n    (0x16B46, 'X'),\n    (0x16B50, 'V'),\n    (0x16B5A, 'X'),\n    (0x16B5B, 'V'),\n    (0x16B62, 'X'),\n    (0x16B63, 'V'),\n    (0x16B78, 'X'),\n    (0x16B7D, 'V'),\n    (0x16B90, 'X'),\n    (0x16E60, 'V'),\n    (0x16E9B, 'X'),\n    (0x16F00, 'V'),\n    (0x16F45, 'X'),\n    (0x16F50, 'V'),\n    (0x16F7F, 'X'),\n    (0x16F8F, 'V'),\n    (0x16FA0, 'X'),\n    (0x16FE0, 'V'),\n    (0x16FE2, 'X'),\n    (0x17000, 'V'),\n    (0x187F2, 'X'),\n    (0x18800, 'V'),\n    (0x18AF3, 'X'),\n    (0x1B000, 'V'),\n    (0x1B11F, 'X'),\n    (0x1B170, 'V'),\n    (0x1B2FC, 'X'),\n    (0x1BC00, 'V'),\n    (0x1BC6B, 'X'),\n    (0x1BC70, 'V'),\n    (0x1BC7D, 'X'),\n    (0x1BC80, 'V'),\n    (0x1BC89, 'X'),\n    (0x1BC90, 'V'),\n    (0x1BC9A, 'X'),\n    (0x1BC9C, 'V'),\n    (0x1BCA0, 'I'),\n    (0x1BCA4, 'X'),\n    (0x1D000, 'V'),\n    (0x1D0F6, 'X'),\n    (0x1D100, 'V'),\n    (0x1D127, 'X'),\n    (0x1D129, 'V'),\n    (0x1D15E, 'M', u'𝅗𝅥'),\n    (0x1D15F, 'M', u'𝅘𝅥'),\n    (0x1D160, 'M', u'𝅘𝅥𝅮'),\n    (0x1D161, 'M', u'𝅘𝅥𝅯'),\n    (0x1D162, 'M', u'𝅘𝅥𝅰'),\n    (0x1D163, 'M', u'𝅘𝅥𝅱'),\n    (0x1D164, 'M', u'𝅘𝅥𝅲'),\n    (0x1D165, 'V'),\n    (0x1D173, 'X'),\n    (0x1D17B, 'V'),\n    (0x1D1BB, 'M', u'𝆹𝅥'),\n    (0x1D1BC, 'M', u'𝆺𝅥'),\n    (0x1D1BD, 'M', u'𝆹𝅥𝅮'),\n    (0x1D1BE, 'M', u'𝆺𝅥𝅮'),\n    (0x1D1BF, 'M', u'𝆹𝅥𝅯'),\n    (0x1D1C0, 'M', u'𝆺𝅥𝅯'),\n    (0x1D1C1, 'V'),\n    (0x1D1E9, 'X'),\n    (0x1D200, 'V'),\n    ]\n\ndef _seg_58():\n    return [\n    (0x1D246, 'X'),\n    (0x1D2E0, 'V'),\n    (0x1D2F4, 'X'),\n    (0x1D300, 'V'),\n    (0x1D357, 'X'),\n    (0x1D360, 'V'),\n    (0x1D379, 'X'),\n    (0x1D400, 'M', u'a'),\n    (0x1D401, 'M', u'b'),\n    (0x1D402, 'M', u'c'),\n    (0x1D403, 'M', u'd'),\n    (0x1D404, 'M', u'e'),\n    (0x1D405, 'M', u'f'),\n    (0x1D406, 'M', u'g'),\n    (0x1D407, 'M', u'h'),\n    (0x1D408, 'M', u'i'),\n    (0x1D409, 'M', u'j'),\n    (0x1D40A, 'M', u'k'),\n    (0x1D40B, 'M', u'l'),\n    (0x1D40C, 'M', u'm'),\n    (0x1D40D, 'M', u'n'),\n    (0x1D40E, 'M', u'o'),\n    (0x1D40F, 'M', u'p'),\n    (0x1D410, 'M', u'q'),\n    (0x1D411, 'M', u'r'),\n    (0x1D412, 'M', u's'),\n    (0x1D413, 'M', u't'),\n    (0x1D414, 'M', u'u'),\n    (0x1D415, 'M', u'v'),\n    (0x1D416, 'M', u'w'),\n    (0x1D417, 'M', u'x'),\n    (0x1D418, 'M', u'y'),\n    (0x1D419, 'M', u'z'),\n    (0x1D41A, 'M', u'a'),\n    (0x1D41B, 'M', u'b'),\n    (0x1D41C, 'M', u'c'),\n    (0x1D41D, 'M', u'd'),\n    (0x1D41E, 'M', u'e'),\n    (0x1D41F, 'M', u'f'),\n    (0x1D420, 'M', u'g'),\n    (0x1D421, 'M', u'h'),\n    (0x1D422, 'M', u'i'),\n    (0x1D423, 'M', u'j'),\n    (0x1D424, 'M', u'k'),\n    (0x1D425, 'M', u'l'),\n    (0x1D426, 'M', u'm'),\n    (0x1D427, 'M', u'n'),\n    (0x1D428, 'M', u'o'),\n    (0x1D429, 'M', u'p'),\n    (0x1D42A, 'M', u'q'),\n    (0x1D42B, 'M', u'r'),\n    (0x1D42C, 'M', u's'),\n    (0x1D42D, 'M', u't'),\n    (0x1D42E, 'M', u'u'),\n    (0x1D42F, 'M', u'v'),\n    (0x1D430, 'M', u'w'),\n    (0x1D431, 'M', u'x'),\n    (0x1D432, 'M', u'y'),\n    (0x1D433, 'M', u'z'),\n    (0x1D434, 'M', u'a'),\n    (0x1D435, 'M', u'b'),\n    (0x1D436, 'M', u'c'),\n    (0x1D437, 'M', u'd'),\n    (0x1D438, 'M', u'e'),\n    (0x1D439, 'M', u'f'),\n    (0x1D43A, 'M', u'g'),\n    (0x1D43B, 'M', u'h'),\n    (0x1D43C, 'M', u'i'),\n    (0x1D43D, 'M', u'j'),\n    (0x1D43E, 'M', u'k'),\n    (0x1D43F, 'M', u'l'),\n    (0x1D440, 'M', u'm'),\n    (0x1D441, 'M', u'n'),\n    (0x1D442, 'M', u'o'),\n    (0x1D443, 'M', u'p'),\n    (0x1D444, 'M', u'q'),\n    (0x1D445, 'M', u'r'),\n    (0x1D446, 'M', u's'),\n    (0x1D447, 'M', u't'),\n    (0x1D448, 'M', u'u'),\n    (0x1D449, 'M', u'v'),\n    (0x1D44A, 'M', u'w'),\n    (0x1D44B, 'M', u'x'),\n    (0x1D44C, 'M', u'y'),\n    (0x1D44D, 'M', u'z'),\n    (0x1D44E, 'M', u'a'),\n    (0x1D44F, 'M', u'b'),\n    (0x1D450, 'M', u'c'),\n    (0x1D451, 'M', u'd'),\n    (0x1D452, 'M', u'e'),\n    (0x1D453, 'M', u'f'),\n    (0x1D454, 'M', u'g'),\n    (0x1D455, 'X'),\n    (0x1D456, 'M', u'i'),\n    (0x1D457, 'M', u'j'),\n    (0x1D458, 'M', u'k'),\n    (0x1D459, 'M', u'l'),\n    (0x1D45A, 'M', u'm'),\n    (0x1D45B, 'M', u'n'),\n    (0x1D45C, 'M', u'o'),\n    ]\n\ndef _seg_59():\n    return [\n    (0x1D45D, 'M', u'p'),\n    (0x1D45E, 'M', u'q'),\n    (0x1D45F, 'M', u'r'),\n    (0x1D460, 'M', u's'),\n    (0x1D461, 'M', u't'),\n    (0x1D462, 'M', u'u'),\n    (0x1D463, 'M', u'v'),\n    (0x1D464, 'M', u'w'),\n    (0x1D465, 'M', u'x'),\n    (0x1D466, 'M', u'y'),\n    (0x1D467, 'M', u'z'),\n    (0x1D468, 'M', u'a'),\n    (0x1D469, 'M', u'b'),\n    (0x1D46A, 'M', u'c'),\n    (0x1D46B, 'M', u'd'),\n    (0x1D46C, 'M', u'e'),\n    (0x1D46D, 'M', u'f'),\n    (0x1D46E, 'M', u'g'),\n    (0x1D46F, 'M', u'h'),\n    (0x1D470, 'M', u'i'),\n    (0x1D471, 'M', u'j'),\n    (0x1D472, 'M', u'k'),\n    (0x1D473, 'M', u'l'),\n    (0x1D474, 'M', u'm'),\n    (0x1D475, 'M', u'n'),\n    (0x1D476, 'M', u'o'),\n    (0x1D477, 'M', u'p'),\n    (0x1D478, 'M', u'q'),\n    (0x1D479, 'M', u'r'),\n    (0x1D47A, 'M', u's'),\n    (0x1D47B, 'M', u't'),\n    (0x1D47C, 'M', u'u'),\n    (0x1D47D, 'M', u'v'),\n    (0x1D47E, 'M', u'w'),\n    (0x1D47F, 'M', u'x'),\n    (0x1D480, 'M', u'y'),\n    (0x1D481, 'M', u'z'),\n    (0x1D482, 'M', u'a'),\n    (0x1D483, 'M', u'b'),\n    (0x1D484, 'M', u'c'),\n    (0x1D485, 'M', u'd'),\n    (0x1D486, 'M', u'e'),\n    (0x1D487, 'M', u'f'),\n    (0x1D488, 'M', u'g'),\n    (0x1D489, 'M', u'h'),\n    (0x1D48A, 'M', u'i'),\n    (0x1D48B, 'M', u'j'),\n    (0x1D48C, 'M', u'k'),\n    (0x1D48D, 'M', u'l'),\n    (0x1D48E, 'M', u'm'),\n    (0x1D48F, 'M', u'n'),\n    (0x1D490, 'M', u'o'),\n    (0x1D491, 'M', u'p'),\n    (0x1D492, 'M', u'q'),\n    (0x1D493, 'M', u'r'),\n    (0x1D494, 'M', u's'),\n    (0x1D495, 'M', u't'),\n    (0x1D496, 'M', u'u'),\n    (0x1D497, 'M', u'v'),\n    (0x1D498, 'M', u'w'),\n    (0x1D499, 'M', u'x'),\n    (0x1D49A, 'M', u'y'),\n    (0x1D49B, 'M', u'z'),\n    (0x1D49C, 'M', u'a'),\n    (0x1D49D, 'X'),\n    (0x1D49E, 'M', u'c'),\n    (0x1D49F, 'M', u'd'),\n    (0x1D4A0, 'X'),\n    (0x1D4A2, 'M', u'g'),\n    (0x1D4A3, 'X'),\n    (0x1D4A5, 'M', u'j'),\n    (0x1D4A6, 'M', u'k'),\n    (0x1D4A7, 'X'),\n    (0x1D4A9, 'M', u'n'),\n    (0x1D4AA, 'M', u'o'),\n    (0x1D4AB, 'M', u'p'),\n    (0x1D4AC, 'M', u'q'),\n    (0x1D4AD, 'X'),\n    (0x1D4AE, 'M', u's'),\n    (0x1D4AF, 'M', u't'),\n    (0x1D4B0, 'M', u'u'),\n    (0x1D4B1, 'M', u'v'),\n    (0x1D4B2, 'M', u'w'),\n    (0x1D4B3, 'M', u'x'),\n    (0x1D4B4, 'M', u'y'),\n    (0x1D4B5, 'M', u'z'),\n    (0x1D4B6, 'M', u'a'),\n    (0x1D4B7, 'M', u'b'),\n    (0x1D4B8, 'M', u'c'),\n    (0x1D4B9, 'M', u'd'),\n    (0x1D4BA, 'X'),\n    (0x1D4BB, 'M', u'f'),\n    (0x1D4BC, 'X'),\n    (0x1D4BD, 'M', u'h'),\n    (0x1D4BE, 'M', u'i'),\n    (0x1D4BF, 'M', u'j'),\n    (0x1D4C0, 'M', u'k'),\n    (0x1D4C1, 'M', u'l'),\n    (0x1D4C2, 'M', u'm'),\n    (0x1D4C3, 'M', u'n'),\n    ]\n\ndef _seg_60():\n    return [\n    (0x1D4C4, 'X'),\n    (0x1D4C5, 'M', u'p'),\n    (0x1D4C6, 'M', u'q'),\n    (0x1D4C7, 'M', u'r'),\n    (0x1D4C8, 'M', u's'),\n    (0x1D4C9, 'M', u't'),\n    (0x1D4CA, 'M', u'u'),\n    (0x1D4CB, 'M', u'v'),\n    (0x1D4CC, 'M', u'w'),\n    (0x1D4CD, 'M', u'x'),\n    (0x1D4CE, 'M', u'y'),\n    (0x1D4CF, 'M', u'z'),\n    (0x1D4D0, 'M', u'a'),\n    (0x1D4D1, 'M', u'b'),\n    (0x1D4D2, 'M', u'c'),\n    (0x1D4D3, 'M', u'd'),\n    (0x1D4D4, 'M', u'e'),\n    (0x1D4D5, 'M', u'f'),\n    (0x1D4D6, 'M', u'g'),\n    (0x1D4D7, 'M', u'h'),\n    (0x1D4D8, 'M', u'i'),\n    (0x1D4D9, 'M', u'j'),\n    (0x1D4DA, 'M', u'k'),\n    (0x1D4DB, 'M', u'l'),\n    (0x1D4DC, 'M', u'm'),\n    (0x1D4DD, 'M', u'n'),\n    (0x1D4DE, 'M', u'o'),\n    (0x1D4DF, 'M', u'p'),\n    (0x1D4E0, 'M', u'q'),\n    (0x1D4E1, 'M', u'r'),\n    (0x1D4E2, 'M', u's'),\n    (0x1D4E3, 'M', u't'),\n    (0x1D4E4, 'M', u'u'),\n    (0x1D4E5, 'M', u'v'),\n    (0x1D4E6, 'M', u'w'),\n    (0x1D4E7, 'M', u'x'),\n    (0x1D4E8, 'M', u'y'),\n    (0x1D4E9, 'M', u'z'),\n    (0x1D4EA, 'M', u'a'),\n    (0x1D4EB, 'M', u'b'),\n    (0x1D4EC, 'M', u'c'),\n    (0x1D4ED, 'M', u'd'),\n    (0x1D4EE, 'M', u'e'),\n    (0x1D4EF, 'M', u'f'),\n    (0x1D4F0, 'M', u'g'),\n    (0x1D4F1, 'M', u'h'),\n    (0x1D4F2, 'M', u'i'),\n    (0x1D4F3, 'M', u'j'),\n    (0x1D4F4, 'M', u'k'),\n    (0x1D4F5, 'M', u'l'),\n    (0x1D4F6, 'M', u'm'),\n    (0x1D4F7, 'M', u'n'),\n    (0x1D4F8, 'M', u'o'),\n    (0x1D4F9, 'M', u'p'),\n    (0x1D4FA, 'M', u'q'),\n    (0x1D4FB, 'M', u'r'),\n    (0x1D4FC, 'M', u's'),\n    (0x1D4FD, 'M', u't'),\n    (0x1D4FE, 'M', u'u'),\n    (0x1D4FF, 'M', u'v'),\n    (0x1D500, 'M', u'w'),\n    (0x1D501, 'M', u'x'),\n    (0x1D502, 'M', u'y'),\n    (0x1D503, 'M', u'z'),\n    (0x1D504, 'M', u'a'),\n    (0x1D505, 'M', u'b'),\n    (0x1D506, 'X'),\n    (0x1D507, 'M', u'd'),\n    (0x1D508, 'M', u'e'),\n    (0x1D509, 'M', u'f'),\n    (0x1D50A, 'M', u'g'),\n    (0x1D50B, 'X'),\n    (0x1D50D, 'M', u'j'),\n    (0x1D50E, 'M', u'k'),\n    (0x1D50F, 'M', u'l'),\n    (0x1D510, 'M', u'm'),\n    (0x1D511, 'M', u'n'),\n    (0x1D512, 'M', u'o'),\n    (0x1D513, 'M', u'p'),\n    (0x1D514, 'M', u'q'),\n    (0x1D515, 'X'),\n    (0x1D516, 'M', u's'),\n    (0x1D517, 'M', u't'),\n    (0x1D518, 'M', u'u'),\n    (0x1D519, 'M', u'v'),\n    (0x1D51A, 'M', u'w'),\n    (0x1D51B, 'M', u'x'),\n    (0x1D51C, 'M', u'y'),\n    (0x1D51D, 'X'),\n    (0x1D51E, 'M', u'a'),\n    (0x1D51F, 'M', u'b'),\n    (0x1D520, 'M', u'c'),\n    (0x1D521, 'M', u'd'),\n    (0x1D522, 'M', u'e'),\n    (0x1D523, 'M', u'f'),\n    (0x1D524, 'M', u'g'),\n    (0x1D525, 'M', u'h'),\n    (0x1D526, 'M', u'i'),\n    (0x1D527, 'M', u'j'),\n    (0x1D528, 'M', u'k'),\n    ]\n\ndef _seg_61():\n    return [\n    (0x1D529, 'M', u'l'),\n    (0x1D52A, 'M', u'm'),\n    (0x1D52B, 'M', u'n'),\n    (0x1D52C, 'M', u'o'),\n    (0x1D52D, 'M', u'p'),\n    (0x1D52E, 'M', u'q'),\n    (0x1D52F, 'M', u'r'),\n    (0x1D530, 'M', u's'),\n    (0x1D531, 'M', u't'),\n    (0x1D532, 'M', u'u'),\n    (0x1D533, 'M', u'v'),\n    (0x1D534, 'M', u'w'),\n    (0x1D535, 'M', u'x'),\n    (0x1D536, 'M', u'y'),\n    (0x1D537, 'M', u'z'),\n    (0x1D538, 'M', u'a'),\n    (0x1D539, 'M', u'b'),\n    (0x1D53A, 'X'),\n    (0x1D53B, 'M', u'd'),\n    (0x1D53C, 'M', u'e'),\n    (0x1D53D, 'M', u'f'),\n    (0x1D53E, 'M', u'g'),\n    (0x1D53F, 'X'),\n    (0x1D540, 'M', u'i'),\n    (0x1D541, 'M', u'j'),\n    (0x1D542, 'M', u'k'),\n    (0x1D543, 'M', u'l'),\n    (0x1D544, 'M', u'm'),\n    (0x1D545, 'X'),\n    (0x1D546, 'M', u'o'),\n    (0x1D547, 'X'),\n    (0x1D54A, 'M', u's'),\n    (0x1D54B, 'M', u't'),\n    (0x1D54C, 'M', u'u'),\n    (0x1D54D, 'M', u'v'),\n    (0x1D54E, 'M', u'w'),\n    (0x1D54F, 'M', u'x'),\n    (0x1D550, 'M', u'y'),\n    (0x1D551, 'X'),\n    (0x1D552, 'M', u'a'),\n    (0x1D553, 'M', u'b'),\n    (0x1D554, 'M', u'c'),\n    (0x1D555, 'M', u'd'),\n    (0x1D556, 'M', u'e'),\n    (0x1D557, 'M', u'f'),\n    (0x1D558, 'M', u'g'),\n    (0x1D559, 'M', u'h'),\n    (0x1D55A, 'M', u'i'),\n    (0x1D55B, 'M', u'j'),\n    (0x1D55C, 'M', u'k'),\n    (0x1D55D, 'M', u'l'),\n    (0x1D55E, 'M', u'm'),\n    (0x1D55F, 'M', u'n'),\n    (0x1D560, 'M', u'o'),\n    (0x1D561, 'M', u'p'),\n    (0x1D562, 'M', u'q'),\n    (0x1D563, 'M', u'r'),\n    (0x1D564, 'M', u's'),\n    (0x1D565, 'M', u't'),\n    (0x1D566, 'M', u'u'),\n    (0x1D567, 'M', u'v'),\n    (0x1D568, 'M', u'w'),\n    (0x1D569, 'M', u'x'),\n    (0x1D56A, 'M', u'y'),\n    (0x1D56B, 'M', u'z'),\n    (0x1D56C, 'M', u'a'),\n    (0x1D56D, 'M', u'b'),\n    (0x1D56E, 'M', u'c'),\n    (0x1D56F, 'M', u'd'),\n    (0x1D570, 'M', u'e'),\n    (0x1D571, 'M', u'f'),\n    (0x1D572, 'M', u'g'),\n    (0x1D573, 'M', u'h'),\n    (0x1D574, 'M', u'i'),\n    (0x1D575, 'M', u'j'),\n    (0x1D576, 'M', u'k'),\n    (0x1D577, 'M', u'l'),\n    (0x1D578, 'M', u'm'),\n    (0x1D579, 'M', u'n'),\n    (0x1D57A, 'M', u'o'),\n    (0x1D57B, 'M', u'p'),\n    (0x1D57C, 'M', u'q'),\n    (0x1D57D, 'M', u'r'),\n    (0x1D57E, 'M', u's'),\n    (0x1D57F, 'M', u't'),\n    (0x1D580, 'M', u'u'),\n    (0x1D581, 'M', u'v'),\n    (0x1D582, 'M', u'w'),\n    (0x1D583, 'M', u'x'),\n    (0x1D584, 'M', u'y'),\n    (0x1D585, 'M', u'z'),\n    (0x1D586, 'M', u'a'),\n    (0x1D587, 'M', u'b'),\n    (0x1D588, 'M', u'c'),\n    (0x1D589, 'M', u'd'),\n    (0x1D58A, 'M', u'e'),\n    (0x1D58B, 'M', u'f'),\n    (0x1D58C, 'M', u'g'),\n    (0x1D58D, 'M', u'h'),\n    (0x1D58E, 'M', u'i'),\n    ]\n\ndef _seg_62():\n    return [\n    (0x1D58F, 'M', u'j'),\n    (0x1D590, 'M', u'k'),\n    (0x1D591, 'M', u'l'),\n    (0x1D592, 'M', u'm'),\n    (0x1D593, 'M', u'n'),\n    (0x1D594, 'M', u'o'),\n    (0x1D595, 'M', u'p'),\n    (0x1D596, 'M', u'q'),\n    (0x1D597, 'M', u'r'),\n    (0x1D598, 'M', u's'),\n    (0x1D599, 'M', u't'),\n    (0x1D59A, 'M', u'u'),\n    (0x1D59B, 'M', u'v'),\n    (0x1D59C, 'M', u'w'),\n    (0x1D59D, 'M', u'x'),\n    (0x1D59E, 'M', u'y'),\n    (0x1D59F, 'M', u'z'),\n    (0x1D5A0, 'M', u'a'),\n    (0x1D5A1, 'M', u'b'),\n    (0x1D5A2, 'M', u'c'),\n    (0x1D5A3, 'M', u'd'),\n    (0x1D5A4, 'M', u'e'),\n    (0x1D5A5, 'M', u'f'),\n    (0x1D5A6, 'M', u'g'),\n    (0x1D5A7, 'M', u'h'),\n    (0x1D5A8, 'M', u'i'),\n    (0x1D5A9, 'M', u'j'),\n    (0x1D5AA, 'M', u'k'),\n    (0x1D5AB, 'M', u'l'),\n    (0x1D5AC, 'M', u'm'),\n    (0x1D5AD, 'M', u'n'),\n    (0x1D5AE, 'M', u'o'),\n    (0x1D5AF, 'M', u'p'),\n    (0x1D5B0, 'M', u'q'),\n    (0x1D5B1, 'M', u'r'),\n    (0x1D5B2, 'M', u's'),\n    (0x1D5B3, 'M', u't'),\n    (0x1D5B4, 'M', u'u'),\n    (0x1D5B5, 'M', u'v'),\n    (0x1D5B6, 'M', u'w'),\n    (0x1D5B7, 'M', u'x'),\n    (0x1D5B8, 'M', u'y'),\n    (0x1D5B9, 'M', u'z'),\n    (0x1D5BA, 'M', u'a'),\n    (0x1D5BB, 'M', u'b'),\n    (0x1D5BC, 'M', u'c'),\n    (0x1D5BD, 'M', u'd'),\n    (0x1D5BE, 'M', u'e'),\n    (0x1D5BF, 'M', u'f'),\n    (0x1D5C0, 'M', u'g'),\n    (0x1D5C1, 'M', u'h'),\n    (0x1D5C2, 'M', u'i'),\n    (0x1D5C3, 'M', u'j'),\n    (0x1D5C4, 'M', u'k'),\n    (0x1D5C5, 'M', u'l'),\n    (0x1D5C6, 'M', u'm'),\n    (0x1D5C7, 'M', u'n'),\n    (0x1D5C8, 'M', u'o'),\n    (0x1D5C9, 'M', u'p'),\n    (0x1D5CA, 'M', u'q'),\n    (0x1D5CB, 'M', u'r'),\n    (0x1D5CC, 'M', u's'),\n    (0x1D5CD, 'M', u't'),\n    (0x1D5CE, 'M', u'u'),\n    (0x1D5CF, 'M', u'v'),\n    (0x1D5D0, 'M', u'w'),\n    (0x1D5D1, 'M', u'x'),\n    (0x1D5D2, 'M', u'y'),\n    (0x1D5D3, 'M', u'z'),\n    (0x1D5D4, 'M', u'a'),\n    (0x1D5D5, 'M', u'b'),\n    (0x1D5D6, 'M', u'c'),\n    (0x1D5D7, 'M', u'd'),\n    (0x1D5D8, 'M', u'e'),\n    (0x1D5D9, 'M', u'f'),\n    (0x1D5DA, 'M', u'g'),\n    (0x1D5DB, 'M', u'h'),\n    (0x1D5DC, 'M', u'i'),\n    (0x1D5DD, 'M', u'j'),\n    (0x1D5DE, 'M', u'k'),\n    (0x1D5DF, 'M', u'l'),\n    (0x1D5E0, 'M', u'm'),\n    (0x1D5E1, 'M', u'n'),\n    (0x1D5E2, 'M', u'o'),\n    (0x1D5E3, 'M', u'p'),\n    (0x1D5E4, 'M', u'q'),\n    (0x1D5E5, 'M', u'r'),\n    (0x1D5E6, 'M', u's'),\n    (0x1D5E7, 'M', u't'),\n    (0x1D5E8, 'M', u'u'),\n    (0x1D5E9, 'M', u'v'),\n    (0x1D5EA, 'M', u'w'),\n    (0x1D5EB, 'M', u'x'),\n    (0x1D5EC, 'M', u'y'),\n    (0x1D5ED, 'M', u'z'),\n    (0x1D5EE, 'M', u'a'),\n    (0x1D5EF, 'M', u'b'),\n    (0x1D5F0, 'M', u'c'),\n    (0x1D5F1, 'M', u'd'),\n    (0x1D5F2, 'M', u'e'),\n    ]\n\ndef _seg_63():\n    return [\n    (0x1D5F3, 'M', u'f'),\n    (0x1D5F4, 'M', u'g'),\n    (0x1D5F5, 'M', u'h'),\n    (0x1D5F6, 'M', u'i'),\n    (0x1D5F7, 'M', u'j'),\n    (0x1D5F8, 'M', u'k'),\n    (0x1D5F9, 'M', u'l'),\n    (0x1D5FA, 'M', u'm'),\n    (0x1D5FB, 'M', u'n'),\n    (0x1D5FC, 'M', u'o'),\n    (0x1D5FD, 'M', u'p'),\n    (0x1D5FE, 'M', u'q'),\n    (0x1D5FF, 'M', u'r'),\n    (0x1D600, 'M', u's'),\n    (0x1D601, 'M', u't'),\n    (0x1D602, 'M', u'u'),\n    (0x1D603, 'M', u'v'),\n    (0x1D604, 'M', u'w'),\n    (0x1D605, 'M', u'x'),\n    (0x1D606, 'M', u'y'),\n    (0x1D607, 'M', u'z'),\n    (0x1D608, 'M', u'a'),\n    (0x1D609, 'M', u'b'),\n    (0x1D60A, 'M', u'c'),\n    (0x1D60B, 'M', u'd'),\n    (0x1D60C, 'M', u'e'),\n    (0x1D60D, 'M', u'f'),\n    (0x1D60E, 'M', u'g'),\n    (0x1D60F, 'M', u'h'),\n    (0x1D610, 'M', u'i'),\n    (0x1D611, 'M', u'j'),\n    (0x1D612, 'M', u'k'),\n    (0x1D613, 'M', u'l'),\n    (0x1D614, 'M', u'm'),\n    (0x1D615, 'M', u'n'),\n    (0x1D616, 'M', u'o'),\n    (0x1D617, 'M', u'p'),\n    (0x1D618, 'M', u'q'),\n    (0x1D619, 'M', u'r'),\n    (0x1D61A, 'M', u's'),\n    (0x1D61B, 'M', u't'),\n    (0x1D61C, 'M', u'u'),\n    (0x1D61D, 'M', u'v'),\n    (0x1D61E, 'M', u'w'),\n    (0x1D61F, 'M', u'x'),\n    (0x1D620, 'M', u'y'),\n    (0x1D621, 'M', u'z'),\n    (0x1D622, 'M', u'a'),\n    (0x1D623, 'M', u'b'),\n    (0x1D624, 'M', u'c'),\n    (0x1D625, 'M', u'd'),\n    (0x1D626, 'M', u'e'),\n    (0x1D627, 'M', u'f'),\n    (0x1D628, 'M', u'g'),\n    (0x1D629, 'M', u'h'),\n    (0x1D62A, 'M', u'i'),\n    (0x1D62B, 'M', u'j'),\n    (0x1D62C, 'M', u'k'),\n    (0x1D62D, 'M', u'l'),\n    (0x1D62E, 'M', u'm'),\n    (0x1D62F, 'M', u'n'),\n    (0x1D630, 'M', u'o'),\n    (0x1D631, 'M', u'p'),\n    (0x1D632, 'M', u'q'),\n    (0x1D633, 'M', u'r'),\n    (0x1D634, 'M', u's'),\n    (0x1D635, 'M', u't'),\n    (0x1D636, 'M', u'u'),\n    (0x1D637, 'M', u'v'),\n    (0x1D638, 'M', u'w'),\n    (0x1D639, 'M', u'x'),\n    (0x1D63A, 'M', u'y'),\n    (0x1D63B, 'M', u'z'),\n    (0x1D63C, 'M', u'a'),\n    (0x1D63D, 'M', u'b'),\n    (0x1D63E, 'M', u'c'),\n    (0x1D63F, 'M', u'd'),\n    (0x1D640, 'M', u'e'),\n    (0x1D641, 'M', u'f'),\n    (0x1D642, 'M', u'g'),\n    (0x1D643, 'M', u'h'),\n    (0x1D644, 'M', u'i'),\n    (0x1D645, 'M', u'j'),\n    (0x1D646, 'M', u'k'),\n    (0x1D647, 'M', u'l'),\n    (0x1D648, 'M', u'm'),\n    (0x1D649, 'M', u'n'),\n    (0x1D64A, 'M', u'o'),\n    (0x1D64B, 'M', u'p'),\n    (0x1D64C, 'M', u'q'),\n    (0x1D64D, 'M', u'r'),\n    (0x1D64E, 'M', u's'),\n    (0x1D64F, 'M', u't'),\n    (0x1D650, 'M', u'u'),\n    (0x1D651, 'M', u'v'),\n    (0x1D652, 'M', u'w'),\n    (0x1D653, 'M', u'x'),\n    (0x1D654, 'M', u'y'),\n    (0x1D655, 'M', u'z'),\n    (0x1D656, 'M', u'a'),\n    ]\n\ndef _seg_64():\n    return [\n    (0x1D657, 'M', u'b'),\n    (0x1D658, 'M', u'c'),\n    (0x1D659, 'M', u'd'),\n    (0x1D65A, 'M', u'e'),\n    (0x1D65B, 'M', u'f'),\n    (0x1D65C, 'M', u'g'),\n    (0x1D65D, 'M', u'h'),\n    (0x1D65E, 'M', u'i'),\n    (0x1D65F, 'M', u'j'),\n    (0x1D660, 'M', u'k'),\n    (0x1D661, 'M', u'l'),\n    (0x1D662, 'M', u'm'),\n    (0x1D663, 'M', u'n'),\n    (0x1D664, 'M', u'o'),\n    (0x1D665, 'M', u'p'),\n    (0x1D666, 'M', u'q'),\n    (0x1D667, 'M', u'r'),\n    (0x1D668, 'M', u's'),\n    (0x1D669, 'M', u't'),\n    (0x1D66A, 'M', u'u'),\n    (0x1D66B, 'M', u'v'),\n    (0x1D66C, 'M', u'w'),\n    (0x1D66D, 'M', u'x'),\n    (0x1D66E, 'M', u'y'),\n    (0x1D66F, 'M', u'z'),\n    (0x1D670, 'M', u'a'),\n    (0x1D671, 'M', u'b'),\n    (0x1D672, 'M', u'c'),\n    (0x1D673, 'M', u'd'),\n    (0x1D674, 'M', u'e'),\n    (0x1D675, 'M', u'f'),\n    (0x1D676, 'M', u'g'),\n    (0x1D677, 'M', u'h'),\n    (0x1D678, 'M', u'i'),\n    (0x1D679, 'M', u'j'),\n    (0x1D67A, 'M', u'k'),\n    (0x1D67B, 'M', u'l'),\n    (0x1D67C, 'M', u'm'),\n    (0x1D67D, 'M', u'n'),\n    (0x1D67E, 'M', u'o'),\n    (0x1D67F, 'M', u'p'),\n    (0x1D680, 'M', u'q'),\n    (0x1D681, 'M', u'r'),\n    (0x1D682, 'M', u's'),\n    (0x1D683, 'M', u't'),\n    (0x1D684, 'M', u'u'),\n    (0x1D685, 'M', u'v'),\n    (0x1D686, 'M', u'w'),\n    (0x1D687, 'M', u'x'),\n    (0x1D688, 'M', u'y'),\n    (0x1D689, 'M', u'z'),\n    (0x1D68A, 'M', u'a'),\n    (0x1D68B, 'M', u'b'),\n    (0x1D68C, 'M', u'c'),\n    (0x1D68D, 'M', u'd'),\n    (0x1D68E, 'M', u'e'),\n    (0x1D68F, 'M', u'f'),\n    (0x1D690, 'M', u'g'),\n    (0x1D691, 'M', u'h'),\n    (0x1D692, 'M', u'i'),\n    (0x1D693, 'M', u'j'),\n    (0x1D694, 'M', u'k'),\n    (0x1D695, 'M', u'l'),\n    (0x1D696, 'M', u'm'),\n    (0x1D697, 'M', u'n'),\n    (0x1D698, 'M', u'o'),\n    (0x1D699, 'M', u'p'),\n    (0x1D69A, 'M', u'q'),\n    (0x1D69B, 'M', u'r'),\n    (0x1D69C, 'M', u's'),\n    (0x1D69D, 'M', u't'),\n    (0x1D69E, 'M', u'u'),\n    (0x1D69F, 'M', u'v'),\n    (0x1D6A0, 'M', u'w'),\n    (0x1D6A1, 'M', u'x'),\n    (0x1D6A2, 'M', u'y'),\n    (0x1D6A3, 'M', u'z'),\n    (0x1D6A4, 'M', u'ı'),\n    (0x1D6A5, 'M', u'ȷ'),\n    (0x1D6A6, 'X'),\n    (0x1D6A8, 'M', u'α'),\n    (0x1D6A9, 'M', u'β'),\n    (0x1D6AA, 'M', u'γ'),\n    (0x1D6AB, 'M', u'δ'),\n    (0x1D6AC, 'M', u'ε'),\n    (0x1D6AD, 'M', u'ζ'),\n    (0x1D6AE, 'M', u'η'),\n    (0x1D6AF, 'M', u'θ'),\n    (0x1D6B0, 'M', u'ι'),\n    (0x1D6B1, 'M', u'κ'),\n    (0x1D6B2, 'M', u'λ'),\n    (0x1D6B3, 'M', u'μ'),\n    (0x1D6B4, 'M', u'ν'),\n    (0x1D6B5, 'M', u'ξ'),\n    (0x1D6B6, 'M', u'ο'),\n    (0x1D6B7, 'M', u'π'),\n    (0x1D6B8, 'M', u'ρ'),\n    (0x1D6B9, 'M', u'θ'),\n    (0x1D6BA, 'M', u'σ'),\n    (0x1D6BB, 'M', u'τ'),\n    ]\n\ndef _seg_65():\n    return [\n    (0x1D6BC, 'M', u'υ'),\n    (0x1D6BD, 'M', u'φ'),\n    (0x1D6BE, 'M', u'χ'),\n    (0x1D6BF, 'M', u'ψ'),\n    (0x1D6C0, 'M', u'ω'),\n    (0x1D6C1, 'M', u'∇'),\n    (0x1D6C2, 'M', u'α'),\n    (0x1D6C3, 'M', u'β'),\n    (0x1D6C4, 'M', u'γ'),\n    (0x1D6C5, 'M', u'δ'),\n    (0x1D6C6, 'M', u'ε'),\n    (0x1D6C7, 'M', u'ζ'),\n    (0x1D6C8, 'M', u'η'),\n    (0x1D6C9, 'M', u'θ'),\n    (0x1D6CA, 'M', u'ι'),\n    (0x1D6CB, 'M', u'κ'),\n    (0x1D6CC, 'M', u'λ'),\n    (0x1D6CD, 'M', u'μ'),\n    (0x1D6CE, 'M', u'ν'),\n    (0x1D6CF, 'M', u'ξ'),\n    (0x1D6D0, 'M', u'ο'),\n    (0x1D6D1, 'M', u'π'),\n    (0x1D6D2, 'M', u'ρ'),\n    (0x1D6D3, 'M', u'σ'),\n    (0x1D6D5, 'M', u'τ'),\n    (0x1D6D6, 'M', u'υ'),\n    (0x1D6D7, 'M', u'φ'),\n    (0x1D6D8, 'M', u'χ'),\n    (0x1D6D9, 'M', u'ψ'),\n    (0x1D6DA, 'M', u'ω'),\n    (0x1D6DB, 'M', u'∂'),\n    (0x1D6DC, 'M', u'ε'),\n    (0x1D6DD, 'M', u'θ'),\n    (0x1D6DE, 'M', u'κ'),\n    (0x1D6DF, 'M', u'φ'),\n    (0x1D6E0, 'M', u'ρ'),\n    (0x1D6E1, 'M', u'π'),\n    (0x1D6E2, 'M', u'α'),\n    (0x1D6E3, 'M', u'β'),\n    (0x1D6E4, 'M', u'γ'),\n    (0x1D6E5, 'M', u'δ'),\n    (0x1D6E6, 'M', u'ε'),\n    (0x1D6E7, 'M', u'ζ'),\n    (0x1D6E8, 'M', u'η'),\n    (0x1D6E9, 'M', u'θ'),\n    (0x1D6EA, 'M', u'ι'),\n    (0x1D6EB, 'M', u'κ'),\n    (0x1D6EC, 'M', u'λ'),\n    (0x1D6ED, 'M', u'μ'),\n    (0x1D6EE, 'M', u'ν'),\n    (0x1D6EF, 'M', u'ξ'),\n    (0x1D6F0, 'M', u'ο'),\n    (0x1D6F1, 'M', u'π'),\n    (0x1D6F2, 'M', u'ρ'),\n    (0x1D6F3, 'M', u'θ'),\n    (0x1D6F4, 'M', u'σ'),\n    (0x1D6F5, 'M', u'τ'),\n    (0x1D6F6, 'M', u'υ'),\n    (0x1D6F7, 'M', u'φ'),\n    (0x1D6F8, 'M', u'χ'),\n    (0x1D6F9, 'M', u'ψ'),\n    (0x1D6FA, 'M', u'ω'),\n    (0x1D6FB, 'M', u'∇'),\n    (0x1D6FC, 'M', u'α'),\n    (0x1D6FD, 'M', u'β'),\n    (0x1D6FE, 'M', u'γ'),\n    (0x1D6FF, 'M', u'δ'),\n    (0x1D700, 'M', u'ε'),\n    (0x1D701, 'M', u'ζ'),\n    (0x1D702, 'M', u'η'),\n    (0x1D703, 'M', u'θ'),\n    (0x1D704, 'M', u'ι'),\n    (0x1D705, 'M', u'κ'),\n    (0x1D706, 'M', u'λ'),\n    (0x1D707, 'M', u'μ'),\n    (0x1D708, 'M', u'ν'),\n    (0x1D709, 'M', u'ξ'),\n    (0x1D70A, 'M', u'ο'),\n    (0x1D70B, 'M', u'π'),\n    (0x1D70C, 'M', u'ρ'),\n    (0x1D70D, 'M', u'σ'),\n    (0x1D70F, 'M', u'τ'),\n    (0x1D710, 'M', u'υ'),\n    (0x1D711, 'M', u'φ'),\n    (0x1D712, 'M', u'χ'),\n    (0x1D713, 'M', u'ψ'),\n    (0x1D714, 'M', u'ω'),\n    (0x1D715, 'M', u'∂'),\n    (0x1D716, 'M', u'ε'),\n    (0x1D717, 'M', u'θ'),\n    (0x1D718, 'M', u'κ'),\n    (0x1D719, 'M', u'φ'),\n    (0x1D71A, 'M', u'ρ'),\n    (0x1D71B, 'M', u'π'),\n    (0x1D71C, 'M', u'α'),\n    (0x1D71D, 'M', u'β'),\n    (0x1D71E, 'M', u'γ'),\n    (0x1D71F, 'M', u'δ'),\n    (0x1D720, 'M', u'ε'),\n    (0x1D721, 'M', u'ζ'),\n    ]\n\ndef _seg_66():\n    return [\n    (0x1D722, 'M', u'η'),\n    (0x1D723, 'M', u'θ'),\n    (0x1D724, 'M', u'ι'),\n    (0x1D725, 'M', u'κ'),\n    (0x1D726, 'M', u'λ'),\n    (0x1D727, 'M', u'μ'),\n    (0x1D728, 'M', u'ν'),\n    (0x1D729, 'M', u'ξ'),\n    (0x1D72A, 'M', u'ο'),\n    (0x1D72B, 'M', u'π'),\n    (0x1D72C, 'M', u'ρ'),\n    (0x1D72D, 'M', u'θ'),\n    (0x1D72E, 'M', u'σ'),\n    (0x1D72F, 'M', u'τ'),\n    (0x1D730, 'M', u'υ'),\n    (0x1D731, 'M', u'φ'),\n    (0x1D732, 'M', u'χ'),\n    (0x1D733, 'M', u'ψ'),\n    (0x1D734, 'M', u'ω'),\n    (0x1D735, 'M', u'∇'),\n    (0x1D736, 'M', u'α'),\n    (0x1D737, 'M', u'β'),\n    (0x1D738, 'M', u'γ'),\n    (0x1D739, 'M', u'δ'),\n    (0x1D73A, 'M', u'ε'),\n    (0x1D73B, 'M', u'ζ'),\n    (0x1D73C, 'M', u'η'),\n    (0x1D73D, 'M', u'θ'),\n    (0x1D73E, 'M', u'ι'),\n    (0x1D73F, 'M', u'κ'),\n    (0x1D740, 'M', u'λ'),\n    (0x1D741, 'M', u'μ'),\n    (0x1D742, 'M', u'ν'),\n    (0x1D743, 'M', u'ξ'),\n    (0x1D744, 'M', u'ο'),\n    (0x1D745, 'M', u'π'),\n    (0x1D746, 'M', u'ρ'),\n    (0x1D747, 'M', u'σ'),\n    (0x1D749, 'M', u'τ'),\n    (0x1D74A, 'M', u'υ'),\n    (0x1D74B, 'M', u'φ'),\n    (0x1D74C, 'M', u'χ'),\n    (0x1D74D, 'M', u'ψ'),\n    (0x1D74E, 'M', u'ω'),\n    (0x1D74F, 'M', u'∂'),\n    (0x1D750, 'M', u'ε'),\n    (0x1D751, 'M', u'θ'),\n    (0x1D752, 'M', u'κ'),\n    (0x1D753, 'M', u'φ'),\n    (0x1D754, 'M', u'ρ'),\n    (0x1D755, 'M', u'π'),\n    (0x1D756, 'M', u'α'),\n    (0x1D757, 'M', u'β'),\n    (0x1D758, 'M', u'γ'),\n    (0x1D759, 'M', u'δ'),\n    (0x1D75A, 'M', u'ε'),\n    (0x1D75B, 'M', u'ζ'),\n    (0x1D75C, 'M', u'η'),\n    (0x1D75D, 'M', u'θ'),\n    (0x1D75E, 'M', u'ι'),\n    (0x1D75F, 'M', u'κ'),\n    (0x1D760, 'M', u'λ'),\n    (0x1D761, 'M', u'μ'),\n    (0x1D762, 'M', u'ν'),\n    (0x1D763, 'M', u'ξ'),\n    (0x1D764, 'M', u'ο'),\n    (0x1D765, 'M', u'π'),\n    (0x1D766, 'M', u'ρ'),\n    (0x1D767, 'M', u'θ'),\n    (0x1D768, 'M', u'σ'),\n    (0x1D769, 'M', u'τ'),\n    (0x1D76A, 'M', u'υ'),\n    (0x1D76B, 'M', u'φ'),\n    (0x1D76C, 'M', u'χ'),\n    (0x1D76D, 'M', u'ψ'),\n    (0x1D76E, 'M', u'ω'),\n    (0x1D76F, 'M', u'∇'),\n    (0x1D770, 'M', u'α'),\n    (0x1D771, 'M', u'β'),\n    (0x1D772, 'M', u'γ'),\n    (0x1D773, 'M', u'δ'),\n    (0x1D774, 'M', u'ε'),\n    (0x1D775, 'M', u'ζ'),\n    (0x1D776, 'M', u'η'),\n    (0x1D777, 'M', u'θ'),\n    (0x1D778, 'M', u'ι'),\n    (0x1D779, 'M', u'κ'),\n    (0x1D77A, 'M', u'λ'),\n    (0x1D77B, 'M', u'μ'),\n    (0x1D77C, 'M', u'ν'),\n    (0x1D77D, 'M', u'ξ'),\n    (0x1D77E, 'M', u'ο'),\n    (0x1D77F, 'M', u'π'),\n    (0x1D780, 'M', u'ρ'),\n    (0x1D781, 'M', u'σ'),\n    (0x1D783, 'M', u'τ'),\n    (0x1D784, 'M', u'υ'),\n    (0x1D785, 'M', u'φ'),\n    (0x1D786, 'M', u'χ'),\n    (0x1D787, 'M', u'ψ'),\n    ]\n\ndef _seg_67():\n    return [\n    (0x1D788, 'M', u'ω'),\n    (0x1D789, 'M', u'∂'),\n    (0x1D78A, 'M', u'ε'),\n    (0x1D78B, 'M', u'θ'),\n    (0x1D78C, 'M', u'κ'),\n    (0x1D78D, 'M', u'φ'),\n    (0x1D78E, 'M', u'ρ'),\n    (0x1D78F, 'M', u'π'),\n    (0x1D790, 'M', u'α'),\n    (0x1D791, 'M', u'β'),\n    (0x1D792, 'M', u'γ'),\n    (0x1D793, 'M', u'δ'),\n    (0x1D794, 'M', u'ε'),\n    (0x1D795, 'M', u'ζ'),\n    (0x1D796, 'M', u'η'),\n    (0x1D797, 'M', u'θ'),\n    (0x1D798, 'M', u'ι'),\n    (0x1D799, 'M', u'κ'),\n    (0x1D79A, 'M', u'λ'),\n    (0x1D79B, 'M', u'μ'),\n    (0x1D79C, 'M', u'ν'),\n    (0x1D79D, 'M', u'ξ'),\n    (0x1D79E, 'M', u'ο'),\n    (0x1D79F, 'M', u'π'),\n    (0x1D7A0, 'M', u'ρ'),\n    (0x1D7A1, 'M', u'θ'),\n    (0x1D7A2, 'M', u'σ'),\n    (0x1D7A3, 'M', u'τ'),\n    (0x1D7A4, 'M', u'υ'),\n    (0x1D7A5, 'M', u'φ'),\n    (0x1D7A6, 'M', u'χ'),\n    (0x1D7A7, 'M', u'ψ'),\n    (0x1D7A8, 'M', u'ω'),\n    (0x1D7A9, 'M', u'∇'),\n    (0x1D7AA, 'M', u'α'),\n    (0x1D7AB, 'M', u'β'),\n    (0x1D7AC, 'M', u'γ'),\n    (0x1D7AD, 'M', u'δ'),\n    (0x1D7AE, 'M', u'ε'),\n    (0x1D7AF, 'M', u'ζ'),\n    (0x1D7B0, 'M', u'η'),\n    (0x1D7B1, 'M', u'θ'),\n    (0x1D7B2, 'M', u'ι'),\n    (0x1D7B3, 'M', u'κ'),\n    (0x1D7B4, 'M', u'λ'),\n    (0x1D7B5, 'M', u'μ'),\n    (0x1D7B6, 'M', u'ν'),\n    (0x1D7B7, 'M', u'ξ'),\n    (0x1D7B8, 'M', u'ο'),\n    (0x1D7B9, 'M', u'π'),\n    (0x1D7BA, 'M', u'ρ'),\n    (0x1D7BB, 'M', u'σ'),\n    (0x1D7BD, 'M', u'τ'),\n    (0x1D7BE, 'M', u'υ'),\n    (0x1D7BF, 'M', u'φ'),\n    (0x1D7C0, 'M', u'χ'),\n    (0x1D7C1, 'M', u'ψ'),\n    (0x1D7C2, 'M', u'ω'),\n    (0x1D7C3, 'M', u'∂'),\n    (0x1D7C4, 'M', u'ε'),\n    (0x1D7C5, 'M', u'θ'),\n    (0x1D7C6, 'M', u'κ'),\n    (0x1D7C7, 'M', u'φ'),\n    (0x1D7C8, 'M', u'ρ'),\n    (0x1D7C9, 'M', u'π'),\n    (0x1D7CA, 'M', u'ϝ'),\n    (0x1D7CC, 'X'),\n    (0x1D7CE, 'M', u'0'),\n    (0x1D7CF, 'M', u'1'),\n    (0x1D7D0, 'M', u'2'),\n    (0x1D7D1, 'M', u'3'),\n    (0x1D7D2, 'M', u'4'),\n    (0x1D7D3, 'M', u'5'),\n    (0x1D7D4, 'M', u'6'),\n    (0x1D7D5, 'M', u'7'),\n    (0x1D7D6, 'M', u'8'),\n    (0x1D7D7, 'M', u'9'),\n    (0x1D7D8, 'M', u'0'),\n    (0x1D7D9, 'M', u'1'),\n    (0x1D7DA, 'M', u'2'),\n    (0x1D7DB, 'M', u'3'),\n    (0x1D7DC, 'M', u'4'),\n    (0x1D7DD, 'M', u'5'),\n    (0x1D7DE, 'M', u'6'),\n    (0x1D7DF, 'M', u'7'),\n    (0x1D7E0, 'M', u'8'),\n    (0x1D7E1, 'M', u'9'),\n    (0x1D7E2, 'M', u'0'),\n    (0x1D7E3, 'M', u'1'),\n    (0x1D7E4, 'M', u'2'),\n    (0x1D7E5, 'M', u'3'),\n    (0x1D7E6, 'M', u'4'),\n    (0x1D7E7, 'M', u'5'),\n    (0x1D7E8, 'M', u'6'),\n    (0x1D7E9, 'M', u'7'),\n    (0x1D7EA, 'M', u'8'),\n    (0x1D7EB, 'M', u'9'),\n    (0x1D7EC, 'M', u'0'),\n    (0x1D7ED, 'M', u'1'),\n    (0x1D7EE, 'M', u'2'),\n    ]\n\ndef _seg_68():\n    return [\n    (0x1D7EF, 'M', u'3'),\n    (0x1D7F0, 'M', u'4'),\n    (0x1D7F1, 'M', u'5'),\n    (0x1D7F2, 'M', u'6'),\n    (0x1D7F3, 'M', u'7'),\n    (0x1D7F4, 'M', u'8'),\n    (0x1D7F5, 'M', u'9'),\n    (0x1D7F6, 'M', u'0'),\n    (0x1D7F7, 'M', u'1'),\n    (0x1D7F8, 'M', u'2'),\n    (0x1D7F9, 'M', u'3'),\n    (0x1D7FA, 'M', u'4'),\n    (0x1D7FB, 'M', u'5'),\n    (0x1D7FC, 'M', u'6'),\n    (0x1D7FD, 'M', u'7'),\n    (0x1D7FE, 'M', u'8'),\n    (0x1D7FF, 'M', u'9'),\n    (0x1D800, 'V'),\n    (0x1DA8C, 'X'),\n    (0x1DA9B, 'V'),\n    (0x1DAA0, 'X'),\n    (0x1DAA1, 'V'),\n    (0x1DAB0, 'X'),\n    (0x1E000, 'V'),\n    (0x1E007, 'X'),\n    (0x1E008, 'V'),\n    (0x1E019, 'X'),\n    (0x1E01B, 'V'),\n    (0x1E022, 'X'),\n    (0x1E023, 'V'),\n    (0x1E025, 'X'),\n    (0x1E026, 'V'),\n    (0x1E02B, 'X'),\n    (0x1E800, 'V'),\n    (0x1E8C5, 'X'),\n    (0x1E8C7, 'V'),\n    (0x1E8D7, 'X'),\n    (0x1E900, 'M', u'𞤢'),\n    (0x1E901, 'M', u'𞤣'),\n    (0x1E902, 'M', u'𞤤'),\n    (0x1E903, 'M', u'𞤥'),\n    (0x1E904, 'M', u'𞤦'),\n    (0x1E905, 'M', u'𞤧'),\n    (0x1E906, 'M', u'𞤨'),\n    (0x1E907, 'M', u'𞤩'),\n    (0x1E908, 'M', u'𞤪'),\n    (0x1E909, 'M', u'𞤫'),\n    (0x1E90A, 'M', u'𞤬'),\n    (0x1E90B, 'M', u'𞤭'),\n    (0x1E90C, 'M', u'𞤮'),\n    (0x1E90D, 'M', u'𞤯'),\n    (0x1E90E, 'M', u'𞤰'),\n    (0x1E90F, 'M', u'𞤱'),\n    (0x1E910, 'M', u'𞤲'),\n    (0x1E911, 'M', u'𞤳'),\n    (0x1E912, 'M', u'𞤴'),\n    (0x1E913, 'M', u'𞤵'),\n    (0x1E914, 'M', u'𞤶'),\n    (0x1E915, 'M', u'𞤷'),\n    (0x1E916, 'M', u'𞤸'),\n    (0x1E917, 'M', u'𞤹'),\n    (0x1E918, 'M', u'𞤺'),\n    (0x1E919, 'M', u'𞤻'),\n    (0x1E91A, 'M', u'𞤼'),\n    (0x1E91B, 'M', u'𞤽'),\n    (0x1E91C, 'M', u'𞤾'),\n    (0x1E91D, 'M', u'𞤿'),\n    (0x1E91E, 'M', u'𞥀'),\n    (0x1E91F, 'M', u'𞥁'),\n    (0x1E920, 'M', u'𞥂'),\n    (0x1E921, 'M', u'𞥃'),\n    (0x1E922, 'V'),\n    (0x1E94B, 'X'),\n    (0x1E950, 'V'),\n    (0x1E95A, 'X'),\n    (0x1E95E, 'V'),\n    (0x1E960, 'X'),\n    (0x1EC71, 'V'),\n    (0x1ECB5, 'X'),\n    (0x1EE00, 'M', u'ا'),\n    (0x1EE01, 'M', u'ب'),\n    (0x1EE02, 'M', u'ج'),\n    (0x1EE03, 'M', u'د'),\n    (0x1EE04, 'X'),\n    (0x1EE05, 'M', u'و'),\n    (0x1EE06, 'M', u'ز'),\n    (0x1EE07, 'M', u'ح'),\n    (0x1EE08, 'M', u'ط'),\n    (0x1EE09, 'M', u'ي'),\n    (0x1EE0A, 'M', u'ك'),\n    (0x1EE0B, 'M', u'ل'),\n    (0x1EE0C, 'M', u'م'),\n    (0x1EE0D, 'M', u'ن'),\n    (0x1EE0E, 'M', u'س'),\n    (0x1EE0F, 'M', u'ع'),\n    (0x1EE10, 'M', u'ف'),\n    (0x1EE11, 'M', u'ص'),\n    (0x1EE12, 'M', u'ق'),\n    (0x1EE13, 'M', u'ر'),\n    (0x1EE14, 'M', u'ش'),\n    ]\n\ndef _seg_69():\n    return [\n    (0x1EE15, 'M', u'ت'),\n    (0x1EE16, 'M', u'ث'),\n    (0x1EE17, 'M', u'خ'),\n    (0x1EE18, 'M', u'ذ'),\n    (0x1EE19, 'M', u'ض'),\n    (0x1EE1A, 'M', u'ظ'),\n    (0x1EE1B, 'M', u'غ'),\n    (0x1EE1C, 'M', u'ٮ'),\n    (0x1EE1D, 'M', u'ں'),\n    (0x1EE1E, 'M', u'ڡ'),\n    (0x1EE1F, 'M', u'ٯ'),\n    (0x1EE20, 'X'),\n    (0x1EE21, 'M', u'ب'),\n    (0x1EE22, 'M', u'ج'),\n    (0x1EE23, 'X'),\n    (0x1EE24, 'M', u'ه'),\n    (0x1EE25, 'X'),\n    (0x1EE27, 'M', u'ح'),\n    (0x1EE28, 'X'),\n    (0x1EE29, 'M', u'ي'),\n    (0x1EE2A, 'M', u'ك'),\n    (0x1EE2B, 'M', u'ل'),\n    (0x1EE2C, 'M', u'م'),\n    (0x1EE2D, 'M', u'ن'),\n    (0x1EE2E, 'M', u'س'),\n    (0x1EE2F, 'M', u'ع'),\n    (0x1EE30, 'M', u'ف'),\n    (0x1EE31, 'M', u'ص'),\n    (0x1EE32, 'M', u'ق'),\n    (0x1EE33, 'X'),\n    (0x1EE34, 'M', u'ش'),\n    (0x1EE35, 'M', u'ت'),\n    (0x1EE36, 'M', u'ث'),\n    (0x1EE37, 'M', u'خ'),\n    (0x1EE38, 'X'),\n    (0x1EE39, 'M', u'ض'),\n    (0x1EE3A, 'X'),\n    (0x1EE3B, 'M', u'غ'),\n    (0x1EE3C, 'X'),\n    (0x1EE42, 'M', u'ج'),\n    (0x1EE43, 'X'),\n    (0x1EE47, 'M', u'ح'),\n    (0x1EE48, 'X'),\n    (0x1EE49, 'M', u'ي'),\n    (0x1EE4A, 'X'),\n    (0x1EE4B, 'M', u'ل'),\n    (0x1EE4C, 'X'),\n    (0x1EE4D, 'M', u'ن'),\n    (0x1EE4E, 'M', u'س'),\n    (0x1EE4F, 'M', u'ع'),\n    (0x1EE50, 'X'),\n    (0x1EE51, 'M', u'ص'),\n    (0x1EE52, 'M', u'ق'),\n    (0x1EE53, 'X'),\n    (0x1EE54, 'M', u'ش'),\n    (0x1EE55, 'X'),\n    (0x1EE57, 'M', u'خ'),\n    (0x1EE58, 'X'),\n    (0x1EE59, 'M', u'ض'),\n    (0x1EE5A, 'X'),\n    (0x1EE5B, 'M', u'غ'),\n    (0x1EE5C, 'X'),\n    (0x1EE5D, 'M', u'ں'),\n    (0x1EE5E, 'X'),\n    (0x1EE5F, 'M', u'ٯ'),\n    (0x1EE60, 'X'),\n    (0x1EE61, 'M', u'ب'),\n    (0x1EE62, 'M', u'ج'),\n    (0x1EE63, 'X'),\n    (0x1EE64, 'M', u'ه'),\n    (0x1EE65, 'X'),\n    (0x1EE67, 'M', u'ح'),\n    (0x1EE68, 'M', u'ط'),\n    (0x1EE69, 'M', u'ي'),\n    (0x1EE6A, 'M', u'ك'),\n    (0x1EE6B, 'X'),\n    (0x1EE6C, 'M', u'م'),\n    (0x1EE6D, 'M', u'ن'),\n    (0x1EE6E, 'M', u'س'),\n    (0x1EE6F, 'M', u'ع'),\n    (0x1EE70, 'M', u'ف'),\n    (0x1EE71, 'M', u'ص'),\n    (0x1EE72, 'M', u'ق'),\n    (0x1EE73, 'X'),\n    (0x1EE74, 'M', u'ش'),\n    (0x1EE75, 'M', u'ت'),\n    (0x1EE76, 'M', u'ث'),\n    (0x1EE77, 'M', u'خ'),\n    (0x1EE78, 'X'),\n    (0x1EE79, 'M', u'ض'),\n    (0x1EE7A, 'M', u'ظ'),\n    (0x1EE7B, 'M', u'غ'),\n    (0x1EE7C, 'M', u'ٮ'),\n    (0x1EE7D, 'X'),\n    (0x1EE7E, 'M', u'ڡ'),\n    (0x1EE7F, 'X'),\n    (0x1EE80, 'M', u'ا'),\n    (0x1EE81, 'M', u'ب'),\n    (0x1EE82, 'M', u'ج'),\n    (0x1EE83, 'M', u'د'),\n    ]\n\ndef _seg_70():\n    return [\n    (0x1EE84, 'M', u'ه'),\n    (0x1EE85, 'M', u'و'),\n    (0x1EE86, 'M', u'ز'),\n    (0x1EE87, 'M', u'ح'),\n    (0x1EE88, 'M', u'ط'),\n    (0x1EE89, 'M', u'ي'),\n    (0x1EE8A, 'X'),\n    (0x1EE8B, 'M', u'ل'),\n    (0x1EE8C, 'M', u'م'),\n    (0x1EE8D, 'M', u'ن'),\n    (0x1EE8E, 'M', u'س'),\n    (0x1EE8F, 'M', u'ع'),\n    (0x1EE90, 'M', u'ف'),\n    (0x1EE91, 'M', u'ص'),\n    (0x1EE92, 'M', u'ق'),\n    (0x1EE93, 'M', u'ر'),\n    (0x1EE94, 'M', u'ش'),\n    (0x1EE95, 'M', u'ت'),\n    (0x1EE96, 'M', u'ث'),\n    (0x1EE97, 'M', u'خ'),\n    (0x1EE98, 'M', u'ذ'),\n    (0x1EE99, 'M', u'ض'),\n    (0x1EE9A, 'M', u'ظ'),\n    (0x1EE9B, 'M', u'غ'),\n    (0x1EE9C, 'X'),\n    (0x1EEA1, 'M', u'ب'),\n    (0x1EEA2, 'M', u'ج'),\n    (0x1EEA3, 'M', u'د'),\n    (0x1EEA4, 'X'),\n    (0x1EEA5, 'M', u'و'),\n    (0x1EEA6, 'M', u'ز'),\n    (0x1EEA7, 'M', u'ح'),\n    (0x1EEA8, 'M', u'ط'),\n    (0x1EEA9, 'M', u'ي'),\n    (0x1EEAA, 'X'),\n    (0x1EEAB, 'M', u'ل'),\n    (0x1EEAC, 'M', u'م'),\n    (0x1EEAD, 'M', u'ن'),\n    (0x1EEAE, 'M', u'س'),\n    (0x1EEAF, 'M', u'ع'),\n    (0x1EEB0, 'M', u'ف'),\n    (0x1EEB1, 'M', u'ص'),\n    (0x1EEB2, 'M', u'ق'),\n    (0x1EEB3, 'M', u'ر'),\n    (0x1EEB4, 'M', u'ش'),\n    (0x1EEB5, 'M', u'ت'),\n    (0x1EEB6, 'M', u'ث'),\n    (0x1EEB7, 'M', u'خ'),\n    (0x1EEB8, 'M', u'ذ'),\n    (0x1EEB9, 'M', u'ض'),\n    (0x1EEBA, 'M', u'ظ'),\n    (0x1EEBB, 'M', u'غ'),\n    (0x1EEBC, 'X'),\n    (0x1EEF0, 'V'),\n    (0x1EEF2, 'X'),\n    (0x1F000, 'V'),\n    (0x1F02C, 'X'),\n    (0x1F030, 'V'),\n    (0x1F094, 'X'),\n    (0x1F0A0, 'V'),\n    (0x1F0AF, 'X'),\n    (0x1F0B1, 'V'),\n    (0x1F0C0, 'X'),\n    (0x1F0C1, 'V'),\n    (0x1F0D0, 'X'),\n    (0x1F0D1, 'V'),\n    (0x1F0F6, 'X'),\n    (0x1F101, '3', u'0,'),\n    (0x1F102, '3', u'1,'),\n    (0x1F103, '3', u'2,'),\n    (0x1F104, '3', u'3,'),\n    (0x1F105, '3', u'4,'),\n    (0x1F106, '3', u'5,'),\n    (0x1F107, '3', u'6,'),\n    (0x1F108, '3', u'7,'),\n    (0x1F109, '3', u'8,'),\n    (0x1F10A, '3', u'9,'),\n    (0x1F10B, 'V'),\n    (0x1F10D, 'X'),\n    (0x1F110, '3', u'(a)'),\n    (0x1F111, '3', u'(b)'),\n    (0x1F112, '3', u'(c)'),\n    (0x1F113, '3', u'(d)'),\n    (0x1F114, '3', u'(e)'),\n    (0x1F115, '3', u'(f)'),\n    (0x1F116, '3', u'(g)'),\n    (0x1F117, '3', u'(h)'),\n    (0x1F118, '3', u'(i)'),\n    (0x1F119, '3', u'(j)'),\n    (0x1F11A, '3', u'(k)'),\n    (0x1F11B, '3', u'(l)'),\n    (0x1F11C, '3', u'(m)'),\n    (0x1F11D, '3', u'(n)'),\n    (0x1F11E, '3', u'(o)'),\n    (0x1F11F, '3', u'(p)'),\n    (0x1F120, '3', u'(q)'),\n    (0x1F121, '3', u'(r)'),\n    (0x1F122, '3', u'(s)'),\n    (0x1F123, '3', u'(t)'),\n    (0x1F124, '3', u'(u)'),\n    ]\n\ndef _seg_71():\n    return [\n    (0x1F125, '3', u'(v)'),\n    (0x1F126, '3', u'(w)'),\n    (0x1F127, '3', u'(x)'),\n    (0x1F128, '3', u'(y)'),\n    (0x1F129, '3', u'(z)'),\n    (0x1F12A, 'M', u'〔s〕'),\n    (0x1F12B, 'M', u'c'),\n    (0x1F12C, 'M', u'r'),\n    (0x1F12D, 'M', u'cd'),\n    (0x1F12E, 'M', u'wz'),\n    (0x1F12F, 'V'),\n    (0x1F130, 'M', u'a'),\n    (0x1F131, 'M', u'b'),\n    (0x1F132, 'M', u'c'),\n    (0x1F133, 'M', u'd'),\n    (0x1F134, 'M', u'e'),\n    (0x1F135, 'M', u'f'),\n    (0x1F136, 'M', u'g'),\n    (0x1F137, 'M', u'h'),\n    (0x1F138, 'M', u'i'),\n    (0x1F139, 'M', u'j'),\n    (0x1F13A, 'M', u'k'),\n    (0x1F13B, 'M', u'l'),\n    (0x1F13C, 'M', u'm'),\n    (0x1F13D, 'M', u'n'),\n    (0x1F13E, 'M', u'o'),\n    (0x1F13F, 'M', u'p'),\n    (0x1F140, 'M', u'q'),\n    (0x1F141, 'M', u'r'),\n    (0x1F142, 'M', u's'),\n    (0x1F143, 'M', u't'),\n    (0x1F144, 'M', u'u'),\n    (0x1F145, 'M', u'v'),\n    (0x1F146, 'M', u'w'),\n    (0x1F147, 'M', u'x'),\n    (0x1F148, 'M', u'y'),\n    (0x1F149, 'M', u'z'),\n    (0x1F14A, 'M', u'hv'),\n    (0x1F14B, 'M', u'mv'),\n    (0x1F14C, 'M', u'sd'),\n    (0x1F14D, 'M', u'ss'),\n    (0x1F14E, 'M', u'ppv'),\n    (0x1F14F, 'M', u'wc'),\n    (0x1F150, 'V'),\n    (0x1F16A, 'M', u'mc'),\n    (0x1F16B, 'M', u'md'),\n    (0x1F16C, 'X'),\n    (0x1F170, 'V'),\n    (0x1F190, 'M', u'dj'),\n    (0x1F191, 'V'),\n    (0x1F1AD, 'X'),\n    (0x1F1E6, 'V'),\n    (0x1F200, 'M', u'ほか'),\n    (0x1F201, 'M', u'ココ'),\n    (0x1F202, 'M', u'サ'),\n    (0x1F203, 'X'),\n    (0x1F210, 'M', u'手'),\n    (0x1F211, 'M', u'字'),\n    (0x1F212, 'M', u'双'),\n    (0x1F213, 'M', u'デ'),\n    (0x1F214, 'M', u'二'),\n    (0x1F215, 'M', u'多'),\n    (0x1F216, 'M', u'解'),\n    (0x1F217, 'M', u'天'),\n    (0x1F218, 'M', u'交'),\n    (0x1F219, 'M', u'映'),\n    (0x1F21A, 'M', u'無'),\n    (0x1F21B, 'M', u'料'),\n    (0x1F21C, 'M', u'前'),\n    (0x1F21D, 'M', u'後'),\n    (0x1F21E, 'M', u'再'),\n    (0x1F21F, 'M', u'新'),\n    (0x1F220, 'M', u'初'),\n    (0x1F221, 'M', u'終'),\n    (0x1F222, 'M', u'生'),\n    (0x1F223, 'M', u'販'),\n    (0x1F224, 'M', u'声'),\n    (0x1F225, 'M', u'吹'),\n    (0x1F226, 'M', u'演'),\n    (0x1F227, 'M', u'投'),\n    (0x1F228, 'M', u'捕'),\n    (0x1F229, 'M', u'一'),\n    (0x1F22A, 'M', u'三'),\n    (0x1F22B, 'M', u'遊'),\n    (0x1F22C, 'M', u'左'),\n    (0x1F22D, 'M', u'中'),\n    (0x1F22E, 'M', u'右'),\n    (0x1F22F, 'M', u'指'),\n    (0x1F230, 'M', u'走'),\n    (0x1F231, 'M', u'打'),\n    (0x1F232, 'M', u'禁'),\n    (0x1F233, 'M', u'空'),\n    (0x1F234, 'M', u'合'),\n    (0x1F235, 'M', u'満'),\n    (0x1F236, 'M', u'有'),\n    (0x1F237, 'M', u'月'),\n    (0x1F238, 'M', u'申'),\n    (0x1F239, 'M', u'割'),\n    (0x1F23A, 'M', u'営'),\n    (0x1F23B, 'M', u'配'),\n    ]\n\ndef _seg_72():\n    return [\n    (0x1F23C, 'X'),\n    (0x1F240, 'M', u'〔本〕'),\n    (0x1F241, 'M', u'〔三〕'),\n    (0x1F242, 'M', u'〔二〕'),\n    (0x1F243, 'M', u'〔安〕'),\n    (0x1F244, 'M', u'〔点〕'),\n    (0x1F245, 'M', u'〔打〕'),\n    (0x1F246, 'M', u'〔盗〕'),\n    (0x1F247, 'M', u'〔勝〕'),\n    (0x1F248, 'M', u'〔敗〕'),\n    (0x1F249, 'X'),\n    (0x1F250, 'M', u'得'),\n    (0x1F251, 'M', u'可'),\n    (0x1F252, 'X'),\n    (0x1F260, 'V'),\n    (0x1F266, 'X'),\n    (0x1F300, 'V'),\n    (0x1F6D5, 'X'),\n    (0x1F6E0, 'V'),\n    (0x1F6ED, 'X'),\n    (0x1F6F0, 'V'),\n    (0x1F6FA, 'X'),\n    (0x1F700, 'V'),\n    (0x1F774, 'X'),\n    (0x1F780, 'V'),\n    (0x1F7D9, 'X'),\n    (0x1F800, 'V'),\n    (0x1F80C, 'X'),\n    (0x1F810, 'V'),\n    (0x1F848, 'X'),\n    (0x1F850, 'V'),\n    (0x1F85A, 'X'),\n    (0x1F860, 'V'),\n    (0x1F888, 'X'),\n    (0x1F890, 'V'),\n    (0x1F8AE, 'X'),\n    (0x1F900, 'V'),\n    (0x1F90C, 'X'),\n    (0x1F910, 'V'),\n    (0x1F93F, 'X'),\n    (0x1F940, 'V'),\n    (0x1F971, 'X'),\n    (0x1F973, 'V'),\n    (0x1F977, 'X'),\n    (0x1F97A, 'V'),\n    (0x1F97B, 'X'),\n    (0x1F97C, 'V'),\n    (0x1F9A3, 'X'),\n    (0x1F9B0, 'V'),\n    (0x1F9BA, 'X'),\n    (0x1F9C0, 'V'),\n    (0x1F9C3, 'X'),\n    (0x1F9D0, 'V'),\n    (0x1FA00, 'X'),\n    (0x1FA60, 'V'),\n    (0x1FA6E, 'X'),\n    (0x20000, 'V'),\n    (0x2A6D7, 'X'),\n    (0x2A700, 'V'),\n    (0x2B735, 'X'),\n    (0x2B740, 'V'),\n    (0x2B81E, 'X'),\n    (0x2B820, 'V'),\n    (0x2CEA2, 'X'),\n    (0x2CEB0, 'V'),\n    (0x2EBE1, 'X'),\n    (0x2F800, 'M', u'丽'),\n    (0x2F801, 'M', u'丸'),\n    (0x2F802, 'M', u'乁'),\n    (0x2F803, 'M', u'𠄢'),\n    (0x2F804, 'M', u'你'),\n    (0x2F805, 'M', u'侮'),\n    (0x2F806, 'M', u'侻'),\n    (0x2F807, 'M', u'倂'),\n    (0x2F808, 'M', u'偺'),\n    (0x2F809, 'M', u'備'),\n    (0x2F80A, 'M', u'僧'),\n    (0x2F80B, 'M', u'像'),\n    (0x2F80C, 'M', u'㒞'),\n    (0x2F80D, 'M', u'𠘺'),\n    (0x2F80E, 'M', u'免'),\n    (0x2F80F, 'M', u'兔'),\n    (0x2F810, 'M', u'兤'),\n    (0x2F811, 'M', u'具'),\n    (0x2F812, 'M', u'𠔜'),\n    (0x2F813, 'M', u'㒹'),\n    (0x2F814, 'M', u'內'),\n    (0x2F815, 'M', u'再'),\n    (0x2F816, 'M', u'𠕋'),\n    (0x2F817, 'M', u'冗'),\n    (0x2F818, 'M', u'冤'),\n    (0x2F819, 'M', u'仌'),\n    (0x2F81A, 'M', u'冬'),\n    (0x2F81B, 'M', u'况'),\n    (0x2F81C, 'M', u'𩇟'),\n    (0x2F81D, 'M', u'凵'),\n    (0x2F81E, 'M', u'刃'),\n    (0x2F81F, 'M', u'㓟'),\n    (0x2F820, 'M', u'刻'),\n    (0x2F821, 'M', u'剆'),\n    ]\n\ndef _seg_73():\n    return [\n    (0x2F822, 'M', u'割'),\n    (0x2F823, 'M', u'剷'),\n    (0x2F824, 'M', u'㔕'),\n    (0x2F825, 'M', u'勇'),\n    (0x2F826, 'M', u'勉'),\n    (0x2F827, 'M', u'勤'),\n    (0x2F828, 'M', u'勺'),\n    (0x2F829, 'M', u'包'),\n    (0x2F82A, 'M', u'匆'),\n    (0x2F82B, 'M', u'北'),\n    (0x2F82C, 'M', u'卉'),\n    (0x2F82D, 'M', u'卑'),\n    (0x2F82E, 'M', u'博'),\n    (0x2F82F, 'M', u'即'),\n    (0x2F830, 'M', u'卽'),\n    (0x2F831, 'M', u'卿'),\n    (0x2F834, 'M', u'𠨬'),\n    (0x2F835, 'M', u'灰'),\n    (0x2F836, 'M', u'及'),\n    (0x2F837, 'M', u'叟'),\n    (0x2F838, 'M', u'𠭣'),\n    (0x2F839, 'M', u'叫'),\n    (0x2F83A, 'M', u'叱'),\n    (0x2F83B, 'M', u'吆'),\n    (0x2F83C, 'M', u'咞'),\n    (0x2F83D, 'M', u'吸'),\n    (0x2F83E, 'M', u'呈'),\n    (0x2F83F, 'M', u'周'),\n    (0x2F840, 'M', u'咢'),\n    (0x2F841, 'M', u'哶'),\n    (0x2F842, 'M', u'唐'),\n    (0x2F843, 'M', u'啓'),\n    (0x2F844, 'M', u'啣'),\n    (0x2F845, 'M', u'善'),\n    (0x2F847, 'M', u'喙'),\n    (0x2F848, 'M', u'喫'),\n    (0x2F849, 'M', u'喳'),\n    (0x2F84A, 'M', u'嗂'),\n    (0x2F84B, 'M', u'圖'),\n    (0x2F84C, 'M', u'嘆'),\n    (0x2F84D, 'M', u'圗'),\n    (0x2F84E, 'M', u'噑'),\n    (0x2F84F, 'M', u'噴'),\n    (0x2F850, 'M', u'切'),\n    (0x2F851, 'M', u'壮'),\n    (0x2F852, 'M', u'城'),\n    (0x2F853, 'M', u'埴'),\n    (0x2F854, 'M', u'堍'),\n    (0x2F855, 'M', u'型'),\n    (0x2F856, 'M', u'堲'),\n    (0x2F857, 'M', u'報'),\n    (0x2F858, 'M', u'墬'),\n    (0x2F859, 'M', u'𡓤'),\n    (0x2F85A, 'M', u'売'),\n    (0x2F85B, 'M', u'壷'),\n    (0x2F85C, 'M', u'夆'),\n    (0x2F85D, 'M', u'多'),\n    (0x2F85E, 'M', u'夢'),\n    (0x2F85F, 'M', u'奢'),\n    (0x2F860, 'M', u'𡚨'),\n    (0x2F861, 'M', u'𡛪'),\n    (0x2F862, 'M', u'姬'),\n    (0x2F863, 'M', u'娛'),\n    (0x2F864, 'M', u'娧'),\n    (0x2F865, 'M', u'姘'),\n    (0x2F866, 'M', u'婦'),\n    (0x2F867, 'M', u'㛮'),\n    (0x2F868, 'X'),\n    (0x2F869, 'M', u'嬈'),\n    (0x2F86A, 'M', u'嬾'),\n    (0x2F86C, 'M', u'𡧈'),\n    (0x2F86D, 'M', u'寃'),\n    (0x2F86E, 'M', u'寘'),\n    (0x2F86F, 'M', u'寧'),\n    (0x2F870, 'M', u'寳'),\n    (0x2F871, 'M', u'𡬘'),\n    (0x2F872, 'M', u'寿'),\n    (0x2F873, 'M', u'将'),\n    (0x2F874, 'X'),\n    (0x2F875, 'M', u'尢'),\n    (0x2F876, 'M', u'㞁'),\n    (0x2F877, 'M', u'屠'),\n    (0x2F878, 'M', u'屮'),\n    (0x2F879, 'M', u'峀'),\n    (0x2F87A, 'M', u'岍'),\n    (0x2F87B, 'M', u'𡷤'),\n    (0x2F87C, 'M', u'嵃'),\n    (0x2F87D, 'M', u'𡷦'),\n    (0x2F87E, 'M', u'嵮'),\n    (0x2F87F, 'M', u'嵫'),\n    (0x2F880, 'M', u'嵼'),\n    (0x2F881, 'M', u'巡'),\n    (0x2F882, 'M', u'巢'),\n    (0x2F883, 'M', u'㠯'),\n    (0x2F884, 'M', u'巽'),\n    (0x2F885, 'M', u'帨'),\n    (0x2F886, 'M', u'帽'),\n    (0x2F887, 'M', u'幩'),\n    (0x2F888, 'M', u'㡢'),\n    (0x2F889, 'M', u'𢆃'),\n    ]\n\ndef _seg_74():\n    return [\n    (0x2F88A, 'M', u'㡼'),\n    (0x2F88B, 'M', u'庰'),\n    (0x2F88C, 'M', u'庳'),\n    (0x2F88D, 'M', u'庶'),\n    (0x2F88E, 'M', u'廊'),\n    (0x2F88F, 'M', u'𪎒'),\n    (0x2F890, 'M', u'廾'),\n    (0x2F891, 'M', u'𢌱'),\n    (0x2F893, 'M', u'舁'),\n    (0x2F894, 'M', u'弢'),\n    (0x2F896, 'M', u'㣇'),\n    (0x2F897, 'M', u'𣊸'),\n    (0x2F898, 'M', u'𦇚'),\n    (0x2F899, 'M', u'形'),\n    (0x2F89A, 'M', u'彫'),\n    (0x2F89B, 'M', u'㣣'),\n    (0x2F89C, 'M', u'徚'),\n    (0x2F89D, 'M', u'忍'),\n    (0x2F89E, 'M', u'志'),\n    (0x2F89F, 'M', u'忹'),\n    (0x2F8A0, 'M', u'悁'),\n    (0x2F8A1, 'M', u'㤺'),\n    (0x2F8A2, 'M', u'㤜'),\n    (0x2F8A3, 'M', u'悔'),\n    (0x2F8A4, 'M', u'𢛔'),\n    (0x2F8A5, 'M', u'惇'),\n    (0x2F8A6, 'M', u'慈'),\n    (0x2F8A7, 'M', u'慌'),\n    (0x2F8A8, 'M', u'慎'),\n    (0x2F8A9, 'M', u'慌'),\n    (0x2F8AA, 'M', u'慺'),\n    (0x2F8AB, 'M', u'憎'),\n    (0x2F8AC, 'M', u'憲'),\n    (0x2F8AD, 'M', u'憤'),\n    (0x2F8AE, 'M', u'憯'),\n    (0x2F8AF, 'M', u'懞'),\n    (0x2F8B0, 'M', u'懲'),\n    (0x2F8B1, 'M', u'懶'),\n    (0x2F8B2, 'M', u'成'),\n    (0x2F8B3, 'M', u'戛'),\n    (0x2F8B4, 'M', u'扝'),\n    (0x2F8B5, 'M', u'抱'),\n    (0x2F8B6, 'M', u'拔'),\n    (0x2F8B7, 'M', u'捐'),\n    (0x2F8B8, 'M', u'𢬌'),\n    (0x2F8B9, 'M', u'挽'),\n    (0x2F8BA, 'M', u'拼'),\n    (0x2F8BB, 'M', u'捨'),\n    (0x2F8BC, 'M', u'掃'),\n    (0x2F8BD, 'M', u'揤'),\n    (0x2F8BE, 'M', u'𢯱'),\n    (0x2F8BF, 'M', u'搢'),\n    (0x2F8C0, 'M', u'揅'),\n    (0x2F8C1, 'M', u'掩'),\n    (0x2F8C2, 'M', u'㨮'),\n    (0x2F8C3, 'M', u'摩'),\n    (0x2F8C4, 'M', u'摾'),\n    (0x2F8C5, 'M', u'撝'),\n    (0x2F8C6, 'M', u'摷'),\n    (0x2F8C7, 'M', u'㩬'),\n    (0x2F8C8, 'M', u'敏'),\n    (0x2F8C9, 'M', u'敬'),\n    (0x2F8CA, 'M', u'𣀊'),\n    (0x2F8CB, 'M', u'旣'),\n    (0x2F8CC, 'M', u'書'),\n    (0x2F8CD, 'M', u'晉'),\n    (0x2F8CE, 'M', u'㬙'),\n    (0x2F8CF, 'M', u'暑'),\n    (0x2F8D0, 'M', u'㬈'),\n    (0x2F8D1, 'M', u'㫤'),\n    (0x2F8D2, 'M', u'冒'),\n    (0x2F8D3, 'M', u'冕'),\n    (0x2F8D4, 'M', u'最'),\n    (0x2F8D5, 'M', u'暜'),\n    (0x2F8D6, 'M', u'肭'),\n    (0x2F8D7, 'M', u'䏙'),\n    (0x2F8D8, 'M', u'朗'),\n    (0x2F8D9, 'M', u'望'),\n    (0x2F8DA, 'M', u'朡'),\n    (0x2F8DB, 'M', u'杞'),\n    (0x2F8DC, 'M', u'杓'),\n    (0x2F8DD, 'M', u'𣏃'),\n    (0x2F8DE, 'M', u'㭉'),\n    (0x2F8DF, 'M', u'柺'),\n    (0x2F8E0, 'M', u'枅'),\n    (0x2F8E1, 'M', u'桒'),\n    (0x2F8E2, 'M', u'梅'),\n    (0x2F8E3, 'M', u'𣑭'),\n    (0x2F8E4, 'M', u'梎'),\n    (0x2F8E5, 'M', u'栟'),\n    (0x2F8E6, 'M', u'椔'),\n    (0x2F8E7, 'M', u'㮝'),\n    (0x2F8E8, 'M', u'楂'),\n    (0x2F8E9, 'M', u'榣'),\n    (0x2F8EA, 'M', u'槪'),\n    (0x2F8EB, 'M', u'檨'),\n    (0x2F8EC, 'M', u'𣚣'),\n    (0x2F8ED, 'M', u'櫛'),\n    (0x2F8EE, 'M', u'㰘'),\n    (0x2F8EF, 'M', u'次'),\n    ]\n\ndef _seg_75():\n    return [\n    (0x2F8F0, 'M', u'𣢧'),\n    (0x2F8F1, 'M', u'歔'),\n    (0x2F8F2, 'M', u'㱎'),\n    (0x2F8F3, 'M', u'歲'),\n    (0x2F8F4, 'M', u'殟'),\n    (0x2F8F5, 'M', u'殺'),\n    (0x2F8F6, 'M', u'殻'),\n    (0x2F8F7, 'M', u'𣪍'),\n    (0x2F8F8, 'M', u'𡴋'),\n    (0x2F8F9, 'M', u'𣫺'),\n    (0x2F8FA, 'M', u'汎'),\n    (0x2F8FB, 'M', u'𣲼'),\n    (0x2F8FC, 'M', u'沿'),\n    (0x2F8FD, 'M', u'泍'),\n    (0x2F8FE, 'M', u'汧'),\n    (0x2F8FF, 'M', u'洖'),\n    (0x2F900, 'M', u'派'),\n    (0x2F901, 'M', u'海'),\n    (0x2F902, 'M', u'流'),\n    (0x2F903, 'M', u'浩'),\n    (0x2F904, 'M', u'浸'),\n    (0x2F905, 'M', u'涅'),\n    (0x2F906, 'M', u'𣴞'),\n    (0x2F907, 'M', u'洴'),\n    (0x2F908, 'M', u'港'),\n    (0x2F909, 'M', u'湮'),\n    (0x2F90A, 'M', u'㴳'),\n    (0x2F90B, 'M', u'滋'),\n    (0x2F90C, 'M', u'滇'),\n    (0x2F90D, 'M', u'𣻑'),\n    (0x2F90E, 'M', u'淹'),\n    (0x2F90F, 'M', u'潮'),\n    (0x2F910, 'M', u'𣽞'),\n    (0x2F911, 'M', u'𣾎'),\n    (0x2F912, 'M', u'濆'),\n    (0x2F913, 'M', u'瀹'),\n    (0x2F914, 'M', u'瀞'),\n    (0x2F915, 'M', u'瀛'),\n    (0x2F916, 'M', u'㶖'),\n    (0x2F917, 'M', u'灊'),\n    (0x2F918, 'M', u'災'),\n    (0x2F919, 'M', u'灷'),\n    (0x2F91A, 'M', u'炭'),\n    (0x2F91B, 'M', u'𠔥'),\n    (0x2F91C, 'M', u'煅'),\n    (0x2F91D, 'M', u'𤉣'),\n    (0x2F91E, 'M', u'熜'),\n    (0x2F91F, 'X'),\n    (0x2F920, 'M', u'爨'),\n    (0x2F921, 'M', u'爵'),\n    (0x2F922, 'M', u'牐'),\n    (0x2F923, 'M', u'𤘈'),\n    (0x2F924, 'M', u'犀'),\n    (0x2F925, 'M', u'犕'),\n    (0x2F926, 'M', u'𤜵'),\n    (0x2F927, 'M', u'𤠔'),\n    (0x2F928, 'M', u'獺'),\n    (0x2F929, 'M', u'王'),\n    (0x2F92A, 'M', u'㺬'),\n    (0x2F92B, 'M', u'玥'),\n    (0x2F92C, 'M', u'㺸'),\n    (0x2F92E, 'M', u'瑇'),\n    (0x2F92F, 'M', u'瑜'),\n    (0x2F930, 'M', u'瑱'),\n    (0x2F931, 'M', u'璅'),\n    (0x2F932, 'M', u'瓊'),\n    (0x2F933, 'M', u'㼛'),\n    (0x2F934, 'M', u'甤'),\n    (0x2F935, 'M', u'𤰶'),\n    (0x2F936, 'M', u'甾'),\n    (0x2F937, 'M', u'𤲒'),\n    (0x2F938, 'M', u'異'),\n    (0x2F939, 'M', u'𢆟'),\n    (0x2F93A, 'M', u'瘐'),\n    (0x2F93B, 'M', u'𤾡'),\n    (0x2F93C, 'M', u'𤾸'),\n    (0x2F93D, 'M', u'𥁄'),\n    (0x2F93E, 'M', u'㿼'),\n    (0x2F93F, 'M', u'䀈'),\n    (0x2F940, 'M', u'直'),\n    (0x2F941, 'M', u'𥃳'),\n    (0x2F942, 'M', u'𥃲'),\n    (0x2F943, 'M', u'𥄙'),\n    (0x2F944, 'M', u'𥄳'),\n    (0x2F945, 'M', u'眞'),\n    (0x2F946, 'M', u'真'),\n    (0x2F948, 'M', u'睊'),\n    (0x2F949, 'M', u'䀹'),\n    (0x2F94A, 'M', u'瞋'),\n    (0x2F94B, 'M', u'䁆'),\n    (0x2F94C, 'M', u'䂖'),\n    (0x2F94D, 'M', u'𥐝'),\n    (0x2F94E, 'M', u'硎'),\n    (0x2F94F, 'M', u'碌'),\n    (0x2F950, 'M', u'磌'),\n    (0x2F951, 'M', u'䃣'),\n    (0x2F952, 'M', u'𥘦'),\n    (0x2F953, 'M', u'祖'),\n    (0x2F954, 'M', u'𥚚'),\n    (0x2F955, 'M', u'𥛅'),\n    ]\n\ndef _seg_76():\n    return [\n    (0x2F956, 'M', u'福'),\n    (0x2F957, 'M', u'秫'),\n    (0x2F958, 'M', u'䄯'),\n    (0x2F959, 'M', u'穀'),\n    (0x2F95A, 'M', u'穊'),\n    (0x2F95B, 'M', u'穏'),\n    (0x2F95C, 'M', u'𥥼'),\n    (0x2F95D, 'M', u'𥪧'),\n    (0x2F95F, 'X'),\n    (0x2F960, 'M', u'䈂'),\n    (0x2F961, 'M', u'𥮫'),\n    (0x2F962, 'M', u'篆'),\n    (0x2F963, 'M', u'築'),\n    (0x2F964, 'M', u'䈧'),\n    (0x2F965, 'M', u'𥲀'),\n    (0x2F966, 'M', u'糒'),\n    (0x2F967, 'M', u'䊠'),\n    (0x2F968, 'M', u'糨'),\n    (0x2F969, 'M', u'糣'),\n    (0x2F96A, 'M', u'紀'),\n    (0x2F96B, 'M', u'𥾆'),\n    (0x2F96C, 'M', u'絣'),\n    (0x2F96D, 'M', u'䌁'),\n    (0x2F96E, 'M', u'緇'),\n    (0x2F96F, 'M', u'縂'),\n    (0x2F970, 'M', u'繅'),\n    (0x2F971, 'M', u'䌴'),\n    (0x2F972, 'M', u'𦈨'),\n    (0x2F973, 'M', u'𦉇'),\n    (0x2F974, 'M', u'䍙'),\n    (0x2F975, 'M', u'𦋙'),\n    (0x2F976, 'M', u'罺'),\n    (0x2F977, 'M', u'𦌾'),\n    (0x2F978, 'M', u'羕'),\n    (0x2F979, 'M', u'翺'),\n    (0x2F97A, 'M', u'者'),\n    (0x2F97B, 'M', u'𦓚'),\n    (0x2F97C, 'M', u'𦔣'),\n    (0x2F97D, 'M', u'聠'),\n    (0x2F97E, 'M', u'𦖨'),\n    (0x2F97F, 'M', u'聰'),\n    (0x2F980, 'M', u'𣍟'),\n    (0x2F981, 'M', u'䏕'),\n    (0x2F982, 'M', u'育'),\n    (0x2F983, 'M', u'脃'),\n    (0x2F984, 'M', u'䐋'),\n    (0x2F985, 'M', u'脾'),\n    (0x2F986, 'M', u'媵'),\n    (0x2F987, 'M', u'𦞧'),\n    (0x2F988, 'M', u'𦞵'),\n    (0x2F989, 'M', u'𣎓'),\n    (0x2F98A, 'M', u'𣎜'),\n    (0x2F98B, 'M', u'舁'),\n    (0x2F98C, 'M', u'舄'),\n    (0x2F98D, 'M', u'辞'),\n    (0x2F98E, 'M', u'䑫'),\n    (0x2F98F, 'M', u'芑'),\n    (0x2F990, 'M', u'芋'),\n    (0x2F991, 'M', u'芝'),\n    (0x2F992, 'M', u'劳'),\n    (0x2F993, 'M', u'花'),\n    (0x2F994, 'M', u'芳'),\n    (0x2F995, 'M', u'芽'),\n    (0x2F996, 'M', u'苦'),\n    (0x2F997, 'M', u'𦬼'),\n    (0x2F998, 'M', u'若'),\n    (0x2F999, 'M', u'茝'),\n    (0x2F99A, 'M', u'荣'),\n    (0x2F99B, 'M', u'莭'),\n    (0x2F99C, 'M', u'茣'),\n    (0x2F99D, 'M', u'莽'),\n    (0x2F99E, 'M', u'菧'),\n    (0x2F99F, 'M', u'著'),\n    (0x2F9A0, 'M', u'荓'),\n    (0x2F9A1, 'M', u'菊'),\n    (0x2F9A2, 'M', u'菌'),\n    (0x2F9A3, 'M', u'菜'),\n    (0x2F9A4, 'M', u'𦰶'),\n    (0x2F9A5, 'M', u'𦵫'),\n    (0x2F9A6, 'M', u'𦳕'),\n    (0x2F9A7, 'M', u'䔫'),\n    (0x2F9A8, 'M', u'蓱'),\n    (0x2F9A9, 'M', u'蓳'),\n    (0x2F9AA, 'M', u'蔖'),\n    (0x2F9AB, 'M', u'𧏊'),\n    (0x2F9AC, 'M', u'蕤'),\n    (0x2F9AD, 'M', u'𦼬'),\n    (0x2F9AE, 'M', u'䕝'),\n    (0x2F9AF, 'M', u'䕡'),\n    (0x2F9B0, 'M', u'𦾱'),\n    (0x2F9B1, 'M', u'𧃒'),\n    (0x2F9B2, 'M', u'䕫'),\n    (0x2F9B3, 'M', u'虐'),\n    (0x2F9B4, 'M', u'虜'),\n    (0x2F9B5, 'M', u'虧'),\n    (0x2F9B6, 'M', u'虩'),\n    (0x2F9B7, 'M', u'蚩'),\n    (0x2F9B8, 'M', u'蚈'),\n    (0x2F9B9, 'M', u'蜎'),\n    (0x2F9BA, 'M', u'蛢'),\n    ]\n\ndef _seg_77():\n    return [\n    (0x2F9BB, 'M', u'蝹'),\n    (0x2F9BC, 'M', u'蜨'),\n    (0x2F9BD, 'M', u'蝫'),\n    (0x2F9BE, 'M', u'螆'),\n    (0x2F9BF, 'X'),\n    (0x2F9C0, 'M', u'蟡'),\n    (0x2F9C1, 'M', u'蠁'),\n    (0x2F9C2, 'M', u'䗹'),\n    (0x2F9C3, 'M', u'衠'),\n    (0x2F9C4, 'M', u'衣'),\n    (0x2F9C5, 'M', u'𧙧'),\n    (0x2F9C6, 'M', u'裗'),\n    (0x2F9C7, 'M', u'裞'),\n    (0x2F9C8, 'M', u'䘵'),\n    (0x2F9C9, 'M', u'裺'),\n    (0x2F9CA, 'M', u'㒻'),\n    (0x2F9CB, 'M', u'𧢮'),\n    (0x2F9CC, 'M', u'𧥦'),\n    (0x2F9CD, 'M', u'䚾'),\n    (0x2F9CE, 'M', u'䛇'),\n    (0x2F9CF, 'M', u'誠'),\n    (0x2F9D0, 'M', u'諭'),\n    (0x2F9D1, 'M', u'變'),\n    (0x2F9D2, 'M', u'豕'),\n    (0x2F9D3, 'M', u'𧲨'),\n    (0x2F9D4, 'M', u'貫'),\n    (0x2F9D5, 'M', u'賁'),\n    (0x2F9D6, 'M', u'贛'),\n    (0x2F9D7, 'M', u'起'),\n    (0x2F9D8, 'M', u'𧼯'),\n    (0x2F9D9, 'M', u'𠠄'),\n    (0x2F9DA, 'M', u'跋'),\n    (0x2F9DB, 'M', u'趼'),\n    (0x2F9DC, 'M', u'跰'),\n    (0x2F9DD, 'M', u'𠣞'),\n    (0x2F9DE, 'M', u'軔'),\n    (0x2F9DF, 'M', u'輸'),\n    (0x2F9E0, 'M', u'𨗒'),\n    (0x2F9E1, 'M', u'𨗭'),\n    (0x2F9E2, 'M', u'邔'),\n    (0x2F9E3, 'M', u'郱'),\n    (0x2F9E4, 'M', u'鄑'),\n    (0x2F9E5, 'M', u'𨜮'),\n    (0x2F9E6, 'M', u'鄛'),\n    (0x2F9E7, 'M', u'鈸'),\n    (0x2F9E8, 'M', u'鋗'),\n    (0x2F9E9, 'M', u'鋘'),\n    (0x2F9EA, 'M', u'鉼'),\n    (0x2F9EB, 'M', u'鏹'),\n    (0x2F9EC, 'M', u'鐕'),\n    (0x2F9ED, 'M', u'𨯺'),\n    (0x2F9EE, 'M', u'開'),\n    (0x2F9EF, 'M', u'䦕'),\n    (0x2F9F0, 'M', u'閷'),\n    (0x2F9F1, 'M', u'𨵷'),\n    (0x2F9F2, 'M', u'䧦'),\n    (0x2F9F3, 'M', u'雃'),\n    (0x2F9F4, 'M', u'嶲'),\n    (0x2F9F5, 'M', u'霣'),\n    (0x2F9F6, 'M', u'𩅅'),\n    (0x2F9F7, 'M', u'𩈚'),\n    (0x2F9F8, 'M', u'䩮'),\n    (0x2F9F9, 'M', u'䩶'),\n    (0x2F9FA, 'M', u'韠'),\n    (0x2F9FB, 'M', u'𩐊'),\n    (0x2F9FC, 'M', u'䪲'),\n    (0x2F9FD, 'M', u'𩒖'),\n    (0x2F9FE, 'M', u'頋'),\n    (0x2FA00, 'M', u'頩'),\n    (0x2FA01, 'M', u'𩖶'),\n    (0x2FA02, 'M', u'飢'),\n    (0x2FA03, 'M', u'䬳'),\n    (0x2FA04, 'M', u'餩'),\n    (0x2FA05, 'M', u'馧'),\n    (0x2FA06, 'M', u'駂'),\n    (0x2FA07, 'M', u'駾'),\n    (0x2FA08, 'M', u'䯎'),\n    (0x2FA09, 'M', u'𩬰'),\n    (0x2FA0A, 'M', u'鬒'),\n    (0x2FA0B, 'M', u'鱀'),\n    (0x2FA0C, 'M', u'鳽'),\n    (0x2FA0D, 'M', u'䳎'),\n    (0x2FA0E, 'M', u'䳭'),\n    (0x2FA0F, 'M', u'鵧'),\n    (0x2FA10, 'M', u'𪃎'),\n    (0x2FA11, 'M', u'䳸'),\n    (0x2FA12, 'M', u'𪄅'),\n    (0x2FA13, 'M', u'𪈎'),\n    (0x2FA14, 'M', u'𪊑'),\n    (0x2FA15, 'M', u'麻'),\n    (0x2FA16, 'M', u'䵖'),\n    (0x2FA17, 'M', u'黹'),\n    (0x2FA18, 'M', u'黾'),\n    (0x2FA19, 'M', u'鼅'),\n    (0x2FA1A, 'M', u'鼏'),\n    (0x2FA1B, 'M', u'鼖'),\n    (0x2FA1C, 'M', u'鼻'),\n    (0x2FA1D, 'M', u'𪘀'),\n    (0x2FA1E, 'X'),\n    (0xE0100, 'I'),\n    ]\n\ndef _seg_78():\n    return [\n    (0xE01F0, 'X'),\n    ]\n\nuts46data = tuple(\n    _seg_0()\n    + _seg_1()\n    + _seg_2()\n    + _seg_3()\n    + _seg_4()\n    + _seg_5()\n    + _seg_6()\n    + _seg_7()\n    + _seg_8()\n    + _seg_9()\n    + _seg_10()\n    + _seg_11()\n    + _seg_12()\n    + _seg_13()\n    + _seg_14()\n    + _seg_15()\n    + _seg_16()\n    + _seg_17()\n    + _seg_18()\n    + _seg_19()\n    + _seg_20()\n    + _seg_21()\n    + _seg_22()\n    + _seg_23()\n    + _seg_24()\n    + _seg_25()\n    + _seg_26()\n    + _seg_27()\n    + _seg_28()\n    + _seg_29()\n    + _seg_30()\n    + _seg_31()\n    + _seg_32()\n    + _seg_33()\n    + _seg_34()\n    + _seg_35()\n    + _seg_36()\n    + _seg_37()\n    + _seg_38()\n    + _seg_39()\n    + _seg_40()\n    + _seg_41()\n    + _seg_42()\n    + _seg_43()\n    + _seg_44()\n    + _seg_45()\n    + _seg_46()\n    + _seg_47()\n    + _seg_48()\n    + _seg_49()\n    + _seg_50()\n    + _seg_51()\n    + _seg_52()\n    + _seg_53()\n    + _seg_54()\n    + _seg_55()\n    + _seg_56()\n    + _seg_57()\n    + _seg_58()\n    + _seg_59()\n    + _seg_60()\n    + _seg_61()\n    + _seg_62()\n    + _seg_63()\n    + _seg_64()\n    + _seg_65()\n    + _seg_66()\n    + _seg_67()\n    + _seg_68()\n    + _seg_69()\n    + _seg_70()\n    + _seg_71()\n    + _seg_72()\n    + _seg_73()\n    + _seg_74()\n    + _seg_75()\n    + _seg_76()\n    + _seg_77()\n    + _seg_78()\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna-2.8.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna-2.8.dist-info/LICENSE.rst",
    "content": "License\n-------\n\nCopyright (c) 2013-2018, Kim Davies. All rights reserved.\n\nRedistribution and use in source and binary forms, with or without\nmodification, are permitted provided that the following conditions are met:\n\n#. Redistributions of source code must retain the above copyright\n   notice, this list of conditions and the following disclaimer.\n\n#. Redistributions in binary form must reproduce the above\n   copyright notice, this list of conditions and the following\n   disclaimer in the documentation and/or other materials provided with\n   the distribution.\n\n#. Neither the name of the copyright holder nor the names of the \n   contributors may be used to endorse or promote products derived \n   from this software without specific prior written permission.\n\n#. THIS SOFTWARE IS PROVIDED BY THE CONTRIBUTORS \"AS IS\" AND ANY\n   EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE\n   IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR\n   PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR \n   CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, \n   SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT \n   LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,\n   DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY\n   THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n   (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE\n   USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH\n   DAMAGE.\n\nPortions of the codec implementation and unit tests are derived from the\nPython standard library, which carries the `Python Software Foundation\nLicense <https://docs.python.org/2/license.html>`_:\n\n   Copyright (c) 2001-2014 Python Software Foundation; All Rights Reserved\n\nPortions of the unit tests are derived from the Unicode standard, which \nis subject to the Unicode, Inc. License Agreement:\n\n   Copyright (c) 1991-2014 Unicode, Inc. All rights reserved.\n   Distributed under the Terms of Use in \n   <http://www.unicode.org/copyright.html>.\n\n   Permission is hereby granted, free of charge, to any person obtaining\n   a copy of the Unicode data files and any associated documentation\n   (the \"Data Files\") or Unicode software and any associated documentation\n   (the \"Software\") to deal in the Data Files or Software\n   without restriction, including without limitation the rights to use,\n   copy, modify, merge, publish, distribute, and/or sell copies of\n   the Data Files or Software, and to permit persons to whom the Data Files\n   or Software are furnished to do so, provided that\n   \n   (a) this copyright and permission notice appear with all copies \n   of the Data Files or Software,\n\n   (b) this copyright and permission notice appear in associated \n   documentation, and\n\n   (c) there is clear notice in each modified Data File or in the Software\n   as well as in the documentation associated with the Data File(s) or\n   Software that the data or software has been modified.\n\n   THE DATA FILES AND SOFTWARE ARE PROVIDED \"AS IS\", WITHOUT WARRANTY OF\n   ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE\n   WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND\n   NONINFRINGEMENT OF THIRD PARTY RIGHTS.\n   IN NO EVENT SHALL THE COPYRIGHT HOLDER OR HOLDERS INCLUDED IN THIS\n   NOTICE BE LIABLE FOR ANY CLAIM, OR ANY SPECIAL INDIRECT OR CONSEQUENTIAL\n   DAMAGES, OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,\n   DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER\n   TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR\n   PERFORMANCE OF THE DATA FILES OR SOFTWARE.\n\n   Except as contained in this notice, the name of a copyright holder\n   shall not be used in advertising or otherwise to promote the sale,\n   use or other dealings in these Data Files or Software without prior\n   written authorization of the copyright holder.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna-2.8.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: idna\nVersion: 2.8\nSummary: Internationalized Domain Names in Applications (IDNA)\nHome-page: https://github.com/kjd/idna\nAuthor: Kim Davies\nAuthor-email: kim@cynosure.com.au\nLicense: BSD-like\nPlatform: UNKNOWN\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Intended Audience :: Developers\nClassifier: Intended Audience :: System Administrators\nClassifier: License :: OSI Approved :: BSD License\nClassifier: Operating System :: OS Independent\nClassifier: Programming Language :: Python\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Topic :: Internet :: Name Service (DNS)\nClassifier: Topic :: Software Development :: Libraries :: Python Modules\nClassifier: Topic :: Utilities\nRequires-Python: >=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*\n\nInternationalized Domain Names in Applications (IDNA)\n=====================================================\n\nSupport for the Internationalised Domain Names in Applications\n(IDNA) protocol as specified in `RFC 5891 <http://tools.ietf.org/html/rfc5891>`_.\nThis is the latest version of the protocol and is sometimes referred to as\n“IDNA 2008”.\n\nThis library also provides support for Unicode Technical Standard 46,\n`Unicode IDNA Compatibility Processing <http://unicode.org/reports/tr46/>`_.\n\nThis acts as a suitable replacement for the “encodings.idna” module that\ncomes with the Python standard library, but only supports the\nold, deprecated IDNA specification (`RFC 3490 <http://tools.ietf.org/html/rfc3490>`_).\n\nBasic functions are simply executed:\n\n.. code-block:: pycon\n\n    # Python 3\n    >>> import idna\n    >>> idna.encode('ドメイン.テスト')\n    b'xn--eckwd4c7c.xn--zckzah'\n    >>> print(idna.decode('xn--eckwd4c7c.xn--zckzah'))\n    ドメイン.テスト\n\n    # Python 2\n    >>> import idna\n    >>> idna.encode(u'ドメイン.テスト')\n    'xn--eckwd4c7c.xn--zckzah'\n    >>> print idna.decode('xn--eckwd4c7c.xn--zckzah')\n    ドメイン.テスト\n\nPackages\n--------\n\nThe latest tagged release version is published in the PyPI repository:\n\n.. image:: https://badge.fury.io/py/idna.svg\n   :target: http://badge.fury.io/py/idna\n\n\nInstallation\n------------\n\nTo install this library, you can use pip:\n\n.. code-block:: bash\n\n    $ pip install idna\n\nAlternatively, you can install the package using the bundled setup script:\n\n.. code-block:: bash\n\n    $ python setup.py install\n\nThis library works with Python 2.7 and Python 3.4 or later.\n\n\nUsage\n-----\n\nFor typical usage, the ``encode`` and ``decode`` functions will take a domain\nname argument and perform a conversion to A-labels or U-labels respectively.\n\n.. code-block:: pycon\n\n    # Python 3\n    >>> import idna\n    >>> idna.encode('ドメイン.テスト')\n    b'xn--eckwd4c7c.xn--zckzah'\n    >>> print(idna.decode('xn--eckwd4c7c.xn--zckzah'))\n    ドメイン.テスト\n\nYou may use the codec encoding and decoding methods using the\n``idna.codec`` module:\n\n.. code-block:: pycon\n\n    # Python 2\n    >>> import idna.codec\n    >>> print u'домена.испытание'.encode('idna')\n    xn--80ahd1agd.xn--80akhbyknj4f\n    >>> print 'xn--80ahd1agd.xn--80akhbyknj4f'.decode('idna')\n    домена.испытание\n\nConversions can be applied at a per-label basis using the ``ulabel`` or ``alabel``\nfunctions if necessary:\n\n.. code-block:: pycon\n\n    # Python 2\n    >>> idna.alabel(u'测试')\n    'xn--0zwm56d'\n\nCompatibility Mapping (UTS #46)\n+++++++++++++++++++++++++++++++\n\nAs described in `RFC 5895 <http://tools.ietf.org/html/rfc5895>`_, the IDNA\nspecification no longer normalizes input from different potential ways a user\nmay input a domain name. This functionality, known as a “mapping”, is now\nconsidered by the specification to be a local user-interface issue distinct\nfrom IDNA conversion functionality.\n\nThis library provides one such mapping, that was developed by the Unicode\nConsortium. Known as `Unicode IDNA Compatibility Processing <http://unicode.org/reports/tr46/>`_,\nit provides for both a regular mapping for typical applications, as well as\na transitional mapping to help migrate from older IDNA 2003 applications.\n\nFor example, “Königsgäßchen” is not a permissible label as *LATIN CAPITAL\nLETTER K* is not allowed (nor are capital letters in general). UTS 46 will\nconvert this into lower case prior to applying the IDNA conversion.\n\n.. code-block:: pycon\n\n    # Python 3\n    >>> import idna\n    >>> idna.encode(u'Königsgäßchen')\n    ...\n    idna.core.InvalidCodepoint: Codepoint U+004B at position 1 of 'Königsgäßchen' not allowed\n    >>> idna.encode('Königsgäßchen', uts46=True)\n    b'xn--knigsgchen-b4a3dun'\n    >>> print(idna.decode('xn--knigsgchen-b4a3dun'))\n    königsgäßchen\n\nTransitional processing provides conversions to help transition from the older\n2003 standard to the current standard. For example, in the original IDNA\nspecification, the *LATIN SMALL LETTER SHARP S* (ß) was converted into two\n*LATIN SMALL LETTER S* (ss), whereas in the current IDNA specification this\nconversion is not performed.\n\n.. code-block:: pycon\n\n    # Python 2\n    >>> idna.encode(u'Königsgäßchen', uts46=True, transitional=True)\n    'xn--knigsgsschen-lcb0w'\n\nImplementors should use transitional processing with caution, only in rare\ncases where conversion from legacy labels to current labels must be performed\n(i.e. IDNA implementations that pre-date 2008). For typical applications\nthat just need to convert labels, transitional processing is unlikely to be\nbeneficial and could produce unexpected incompatible results.\n\n``encodings.idna`` Compatibility\n++++++++++++++++++++++++++++++++\n\nFunction calls from the Python built-in ``encodings.idna`` module are\nmapped to their IDNA 2008 equivalents using the ``idna.compat`` module.\nSimply substitute the ``import`` clause in your code to refer to the\nnew module name.\n\nExceptions\n----------\n\nAll errors raised during the conversion following the specification should\nraise an exception derived from the ``idna.IDNAError`` base class.\n\nMore specific exceptions that may be generated as ``idna.IDNABidiError``\nwhen the error reflects an illegal combination of left-to-right and right-to-left\ncharacters in a label; ``idna.InvalidCodepoint`` when a specific codepoint is\nan illegal character in an IDN label (i.e. INVALID); and ``idna.InvalidCodepointContext``\nwhen the codepoint is illegal based on its positional context (i.e. it is CONTEXTO\nor CONTEXTJ but the contextual requirements are not satisfied.)\n\nBuilding and Diagnostics\n------------------------\n\nThe IDNA and UTS 46 functionality relies upon pre-calculated lookup tables for\nperformance. These tables are derived from computing against eligibility criteria\nin the respective standards. These tables are computed using the command-line\nscript ``tools/idna-data``.\n\nThis tool will fetch relevant tables from the Unicode Consortium and perform the\nrequired calculations to identify eligibility. It has three main modes:\n\n* ``idna-data make-libdata``. Generates ``idnadata.py`` and ``uts46data.py``,\n  the pre-calculated lookup tables using for IDNA and UTS 46 conversions. Implementors\n  who wish to track this library against a different Unicode version may use this tool\n  to manually generate a different version of the ``idnadata.py`` and ``uts46data.py``\n  files.\n\n* ``idna-data make-table``. Generate a table of the IDNA disposition\n  (e.g. PVALID, CONTEXTJ, CONTEXTO) in the format found in Appendix B.1 of RFC\n  5892 and the pre-computed tables published by `IANA <http://iana.org/>`_.\n\n* ``idna-data U+0061``. Prints debugging output on the various properties\n  associated with an individual Unicode codepoint (in this case, U+0061), that are\n  used to assess the IDNA and UTS 46 status of a codepoint. This is helpful in debugging\n  or analysis.\n\nThe tool accepts a number of arguments, described using ``idna-data -h``. Most notably,\nthe ``--version`` argument allows the specification of the version of Unicode to use\nin computing the table data. For example, ``idna-data --version 9.0.0 make-libdata``\nwill generate library data against Unicode 9.0.0.\n\nNote that this script requires Python 3, but all generated library data will work\nin Python 2.7.\n\n\nTesting\n-------\n\nThe library has a test suite based on each rule of the IDNA specification, as\nwell as tests that are provided as part of the Unicode Technical Standard 46,\n`Unicode IDNA Compatibility Processing <http://unicode.org/reports/tr46/>`_.\n\nThe tests are run automatically on each commit at Travis CI:\n\n.. image:: https://travis-ci.org/kjd/idna.svg?branch=master\n   :target: https://travis-ci.org/kjd/idna\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna-2.8.dist-info/RECORD",
    "content": "idna-2.8.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nidna-2.8.dist-info/LICENSE.rst,sha256=DUvHq9SNz7FOJCVO5AQGZzf_AWcUTiIpFKIRO4eUaD4,3947\r\nidna-2.8.dist-info/METADATA,sha256=X4QsM_BLMPhl4gC8SEnXjvl5-gj7hvwAl7UCyR418so,8862\r\nidna-2.8.dist-info/RECORD,,\r\nidna-2.8.dist-info/WHEEL,sha256=CihQvCnsGZQBGAHLEUMf0IdA4fRduS_NBUTMgCTtvPM,110\r\nidna-2.8.dist-info/top_level.txt,sha256=jSag9sEDqvSPftxOQy-ABfGV_RSy7oFh4zZJpODV8k0,5\r\nidna/__init__.py,sha256=9Nt7xpyet3DmOrPUGooDdAwmHZZu1qUAy2EaJ93kGiQ,58\r\nidna/__pycache__/__init__.cpython-36.pyc,,\r\nidna/__pycache__/codec.cpython-36.pyc,,\r\nidna/__pycache__/compat.cpython-36.pyc,,\r\nidna/__pycache__/core.cpython-36.pyc,,\r\nidna/__pycache__/idnadata.cpython-36.pyc,,\r\nidna/__pycache__/intranges.cpython-36.pyc,,\r\nidna/__pycache__/package_data.cpython-36.pyc,,\r\nidna/__pycache__/uts46data.cpython-36.pyc,,\r\nidna/codec.py,sha256=lvYb7yu7PhAqFaAIAdWcwgaWI2UmgseUua-1c0AsG0A,3299\r\nidna/compat.py,sha256=R-h29D-6mrnJzbXxymrWUW7iZUvy-26TQwZ0ij57i4U,232\r\nidna/core.py,sha256=JDCZZ_PLESqIgEbU8mPyoEufWwoOiIqygA17-QZIe3s,11733\r\nidna/idnadata.py,sha256=HXaPFw6_YAJ0qppACPu0YLAULtRs3QovRM_CCZHGdY0,40899\r\nidna/intranges.py,sha256=TY1lpxZIQWEP6tNqjZkFA5hgoMWOj1OBmnUG8ihT87E,1749\r\nidna/package_data.py,sha256=kIzeKKXEouXLR4srqwf9Q3zv-NffKSOz5aSDOJARPB0,21\r\nidna/uts46data.py,sha256=oLyNZ1pBaiBlj9zFzLFRd_P7J8MkRcgDisjExZR_4MY,198292\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna-2.8.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.32.2)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/idna-2.8.dist-info/top_level.txt",
    "content": "idna\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nVersions for Python packages.\n\nSee L{Version}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport sys\nimport warnings\n\n#\n# Compat functions\n#\n\nif sys.version_info < (3, 0):\n    _PY3 = False\nelse:\n    _PY3 = True\n\ntry:\n    _cmp = cmp\nexcept NameError:\n    def _cmp(a, b):\n        \"\"\"\n        Compare two objects.\n\n        Returns a negative number if C{a < b}, zero if they are equal, and a\n        positive number if C{a > b}.\n        \"\"\"\n        if a < b:\n            return -1\n        elif a == b:\n            return 0\n        else:\n            return 1\n\n\ndef _comparable(klass):\n    \"\"\"\n    Class decorator that ensures support for the special C{__cmp__} method.\n\n    On Python 2 this does nothing.\n\n    On Python 3, C{__eq__}, C{__lt__}, etc. methods are added to the class,\n    relying on C{__cmp__} to implement their comparisons.\n    \"\"\"\n    # On Python 2, __cmp__ will just work, so no need to add extra methods:\n    if not _PY3:\n        return klass\n\n    def __eq__(self, other):\n        c = self.__cmp__(other)\n        if c is NotImplemented:\n            return c\n        return c == 0\n\n    def __ne__(self, other):\n        c = self.__cmp__(other)\n        if c is NotImplemented:\n            return c\n        return c != 0\n\n    def __lt__(self, other):\n        c = self.__cmp__(other)\n        if c is NotImplemented:\n            return c\n        return c < 0\n\n    def __le__(self, other):\n        c = self.__cmp__(other)\n        if c is NotImplemented:\n            return c\n        return c <= 0\n\n    def __gt__(self, other):\n        c = self.__cmp__(other)\n        if c is NotImplemented:\n            return c\n        return c > 0\n\n    def __ge__(self, other):\n        c = self.__cmp__(other)\n        if c is NotImplemented:\n            return c\n        return c >= 0\n\n    klass.__lt__ = __lt__\n    klass.__gt__ = __gt__\n    klass.__le__ = __le__\n    klass.__ge__ = __ge__\n    klass.__eq__ = __eq__\n    klass.__ne__ = __ne__\n    return klass\n\n#\n# Versioning\n#\n\n\n@_comparable\nclass _inf(object):\n    \"\"\"\n    An object that is bigger than all other objects.\n    \"\"\"\n    def __cmp__(self, other):\n        \"\"\"\n        @param other: Another object.\n        @type other: any\n\n        @return: 0 if other is inf, 1 otherwise.\n        @rtype: C{int}\n        \"\"\"\n        if other is _inf:\n            return 0\n        return 1\n\n\n_inf = _inf()\n\n\nclass IncomparableVersions(TypeError):\n    \"\"\"\n    Two versions could not be compared.\n    \"\"\"\n\n\n@_comparable\nclass Version(object):\n    \"\"\"\n    An encapsulation of a version for a project, with support for outputting\n    PEP-440 compatible version strings.\n\n    This class supports the standard major.minor.micro[rcN] scheme of\n    versioning.\n    \"\"\"\n    def __init__(self, package, major, minor, micro, release_candidate=None,\n                 prerelease=None, dev=None):\n        \"\"\"\n        @param package: Name of the package that this is a version of.\n        @type package: C{str}\n        @param major: The major version number.\n        @type major: C{int} or C{str} (for the \"NEXT\" symbol)\n        @param minor: The minor version number.\n        @type minor: C{int}\n        @param micro: The micro version number.\n        @type micro: C{int}\n        @param release_candidate: The release candidate number.\n        @type release_candidate: C{int}\n        @param prerelease: The prerelease number. (Deprecated)\n        @type prerelease: C{int}\n        @param dev: The development release number.\n        @type dev: C{int}\n        \"\"\"\n        if release_candidate and prerelease:\n            raise ValueError(\"Please only return one of these.\")\n        elif prerelease and not release_candidate:\n            release_candidate = prerelease\n            warnings.warn((\"Passing prerelease to incremental.Version was \"\n                           \"deprecated in Incremental 16.9.0. Please pass \"\n                           \"release_candidate instead.\"),\n                          DeprecationWarning, stacklevel=2)\n\n        if major == \"NEXT\":\n            if minor or micro or release_candidate or dev:\n                raise ValueError((\"When using NEXT, all other values except \"\n                                  \"Package must be 0.\"))\n\n        self.package = package\n        self.major = major\n        self.minor = minor\n        self.micro = micro\n        self.release_candidate = release_candidate\n        self.dev = dev\n\n    @property\n    def prerelease(self):\n        warnings.warn((\"Accessing incremental.Version.prerelease was \"\n                       \"deprecated in Incremental 16.9.0. Use \"\n                       \"Version.release_candidate instead.\"),\n                      DeprecationWarning, stacklevel=2),\n        return self.release_candidate\n\n    def public(self):\n        \"\"\"\n        Return a PEP440-compatible \"public\" representation of this L{Version}.\n\n        Examples:\n\n          - 14.4.0\n          - 1.2.3rc1\n          - 14.2.1rc1dev9\n          - 16.04.0dev0\n        \"\"\"\n        if self.major == \"NEXT\":\n            return self.major\n\n        if self.release_candidate is None:\n            rc = \"\"\n        else:\n            rc = \"rc%s\" % (self.release_candidate,)\n\n        if self.dev is None:\n            dev = \"\"\n        else:\n            dev = \"dev%s\" % (self.dev,)\n\n        return '%r.%d.%d%s%s' % (self.major,\n                                 self.minor,\n                                 self.micro,\n                                 rc, dev)\n\n    base = public\n    short = public\n    local = public\n\n    def __repr__(self):\n\n        if self.release_candidate is None:\n            release_candidate = \"\"\n        else:\n            release_candidate = \", release_candidate=%r\" % (\n                self.release_candidate,)\n\n        if self.dev is None:\n            dev = \"\"\n        else:\n            dev = \", dev=%r\" % (self.dev,)\n\n        return '%s(%r, %r, %d, %d%s%s)' % (\n            self.__class__.__name__,\n            self.package,\n            self.major,\n            self.minor,\n            self.micro,\n            release_candidate,\n            dev)\n\n    def __str__(self):\n        return '[%s, version %s]' % (\n            self.package,\n            self.short())\n\n    def __cmp__(self, other):\n        \"\"\"\n        Compare two versions, considering major versions, minor versions, micro\n        versions, then release candidates. Package names are case insensitive.\n\n        A version with a release candidate is always less than a version\n        without a release candidate. If both versions have release candidates,\n        they will be included in the comparison.\n\n        @param other: Another version.\n        @type other: L{Version}\n\n        @return: NotImplemented when the other object is not a Version, or one\n            of -1, 0, or 1.\n\n        @raise IncomparableVersions: when the package names of the versions\n            differ.\n        \"\"\"\n        if not isinstance(other, self.__class__):\n            return NotImplemented\n        if self.package.lower() != other.package.lower():\n            raise IncomparableVersions(\"%r != %r\"\n                                       % (self.package, other.package))\n\n        if self.major == \"NEXT\":\n            major = _inf\n        else:\n            major = self.major\n\n        if self.release_candidate is None:\n            release_candidate = _inf\n        else:\n            release_candidate = self.release_candidate\n\n        if self.dev is None:\n            dev = _inf\n        else:\n            dev = self.dev\n\n        if other.major == \"NEXT\":\n            othermajor = _inf\n        else:\n            othermajor = other.major\n\n        if other.release_candidate is None:\n            otherrc = _inf\n        else:\n            otherrc = other.release_candidate\n\n        if other.dev is None:\n            otherdev = _inf\n        else:\n            otherdev = other.dev\n\n        x = _cmp((major,\n                  self.minor,\n                  self.micro,\n                  release_candidate,\n                  dev),\n                 (othermajor,\n                  other.minor,\n                  other.micro,\n                  otherrc,\n                  otherdev))\n        return x\n\n\ndef getVersionString(version):\n    \"\"\"\n    Get a friendly string for the given version object.\n\n    @param version: A L{Version} object.\n    @return: A string containing the package and short version number.\n    \"\"\"\n    result = '%s %s' % (version.package, version.short())\n    return result\n\n\ndef _get_version(dist, keyword, value):\n    \"\"\"\n    Get the version from the package listed in the Distribution.\n    \"\"\"\n    if not value:\n        return\n\n    from distutils.command import build_py\n\n    sp_command = build_py.build_py(dist)\n    sp_command.finalize_options()\n\n    for item in sp_command.find_all_modules():\n        if item[1] == \"_version\":\n            version_file = {}\n\n            with open(item[2]) as f:\n                exec(f.read(), version_file)\n\n            dist.metadata.version = version_file[\"__version__\"].public()\n            return None\n\n    raise Exception(\"No _version.py found.\")\n\n\nfrom ._version import __version__ # noqa\n\n\n__all__ = [\"__version__\", \"Version\", \"getVersionString\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental/_version.py",
    "content": "\"\"\"\nProvides Incremental version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update Incremental` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('Incremental', 17, 5, 0)\n__all__ = [\"__version__\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental/tests/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental/tests/test_update.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{incremental.update}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport sys\nimport os\nimport datetime\n\nfrom twisted.python.filepath import FilePath\nfrom twisted.python.compat import NativeStringIO\nfrom twisted.trial.unittest import TestCase\n\nfrom incremental.update import _run, run\n\n\nclass NonCreatedUpdateTests(TestCase):\n\n    def setUp(self):\n\n        self.srcdir = FilePath(self.mktemp())\n        self.srcdir.makedirs()\n\n        packagedir = self.srcdir.child('inctestpkg')\n        packagedir.makedirs()\n\n        packagedir.child('__init__.py').setContent(b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 'NEXT', 0, 0).short()\nnext_released_version = \"inctestpkg NEXT\"\n\"\"\")\n        self.getcwd = lambda: self.srcdir.path\n        self.packagedir = packagedir\n\n        class Date(object):\n            year = 2016\n            month = 8\n\n        self.date = Date()\n\n    def test_create(self):\n        \"\"\"\n        `incremental.update package --create` initialises the version.\n        \"\"\"\n        self.assertFalse(self.packagedir.child(\"_version.py\").exists())\n\n        out = []\n        _run('inctestpkg', path=None, newversion=None, patch=False, rc=False,\n             dev=False, create=True, _date=self.date, _getcwd=self.getcwd,\n             _print=out.append)\n\n        self.assertTrue(self.packagedir.child(\"_version.py\").exists())\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 16, 8, 0)\n__all__ = [\"__version__\"]\n''')\n\n\nclass MissingTests(TestCase):\n\n    def setUp(self):\n\n        self.srcdir = FilePath(self.mktemp())\n        self.srcdir.makedirs()\n\n        self.srcdir.child('srca').makedirs()\n\n        packagedir = self.srcdir.child('srca').child('inctestpkg')\n        packagedir.makedirs()\n\n        packagedir.child('__init__.py').setContent(b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 'NEXT', 0, 0).short()\nnext_released_version = \"inctestpkg NEXT\"\n\"\"\")\n        packagedir.child('_version.py').setContent(b\"\"\"\nfrom incremental import Version\n__version__ = Version('inctestpkg', 1, 2, 3)\n__all__ = [\"__version__\"]\n\"\"\")\n        self.getcwd = lambda: self.srcdir.path\n        self.packagedir = packagedir\n\n        class Date(object):\n            year = 2016\n            month = 8\n\n        self.date = Date()\n\n    def test_path(self):\n        \"\"\"\n        `incremental.update package --dev` raises and quits if it can't find\n        the package.\n        \"\"\"\n        out = []\n        with self.assertRaises(ValueError):\n            _run(u'inctestpkg', path=None, newversion=None,\n                 patch=False, rc=False, dev=True, create=False,\n                 _date=self.date, _getcwd=self.getcwd, _print=out.append)\n\n\nclass CreatedUpdateInSrcTests(TestCase):\n\n    def setUp(self):\n\n        self.srcdir = FilePath(self.mktemp())\n        self.srcdir.makedirs()\n\n        self.srcdir.child('src').makedirs()\n\n        packagedir = self.srcdir.child('src').child('inctestpkg')\n        packagedir.makedirs()\n\n        packagedir.child('__init__.py').setContent(b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 'NEXT', 0, 0).short()\nnext_released_version = \"inctestpkg NEXT\"\n\"\"\")\n        packagedir.child('_version.py').setContent(b\"\"\"\nfrom incremental import Version\n__version__ = Version('inctestpkg', 1, 2, 3)\n__all__ = [\"__version__\"]\n\"\"\")\n        self.getcwd = lambda: self.srcdir.path\n        self.packagedir = packagedir\n\n        class Date(object):\n            year = 2016\n            month = 8\n\n        self.date = Date()\n\n    def test_path(self):\n        \"\"\"\n        `incremental.update package --path=<path> --dev` increments the dev\n        version of the package on the given path\n        \"\"\"\n        out = []\n        _run(u'inctestpkg', path=None, newversion=None,\n             patch=False, rc=False, dev=True, create=False, _date=self.date,\n             _getcwd=self.getcwd, _print=out.append)\n\n        self.assertTrue(self.packagedir.child(\"_version.py\").exists())\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 1, 2, 3, dev=0)\n__all__ = [\"__version__\"]\n''')\n\n        _run(u'inctestpkg', path=None, newversion=None,\n             patch=False, rc=False, dev=True, create=False, _date=self.date,\n             _getcwd=self.getcwd, _print=out.append)\n\n        self.assertTrue(self.packagedir.child(\"_version.py\").exists())\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 1, 2, 3, dev=1)\n__all__ = [\"__version__\"]\n''')\n\n\nclass CreatedUpdateTests(TestCase):\n\n    maxDiff = None\n\n    def setUp(self):\n\n        self.srcdir = FilePath(self.mktemp())\n        self.srcdir.makedirs()\n\n        packagedir = self.srcdir.child('inctestpkg')\n        packagedir.makedirs()\n\n        packagedir.child('__init__.py').setContent(b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 'NEXT', 0, 0).short()\nnext_released_version = \"inctestpkg NEXT\"\n\"\"\")\n        packagedir.child('_version.py').setContent(b\"\"\"\nfrom incremental import Version\n__version__ = Version('inctestpkg', 1, 2, 3)\n__all__ = [\"__version__\"]\n\"\"\")\n        self.getcwd = lambda: self.srcdir.path\n        self.packagedir = packagedir\n\n        class Date(object):\n            year = 2016\n            month = 8\n\n        self.date = Date()\n\n    def test_path(self):\n        \"\"\"\n        `incremental.update package --path=<path> --dev` increments the dev\n        version of the package on the given path\n        \"\"\"\n        out = []\n        _run(u'inctestpkg', path=self.packagedir.path, newversion=None,\n             patch=False, rc=False, dev=True, create=False, _date=self.date,\n             _print=out.append)\n\n        self.assertTrue(self.packagedir.child(\"_version.py\").exists())\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 1, 2, 3, dev=0)\n__all__ = [\"__version__\"]\n''')\n\n    def test_dev(self):\n        \"\"\"\n        `incremental.update package --dev` increments the dev version.\n        \"\"\"\n        out = []\n        _run(u'inctestpkg', path=None, newversion=None, patch=False, rc=False,\n             dev=True, create=False, _date=self.date, _getcwd=self.getcwd,\n             _print=out.append)\n\n        self.assertTrue(self.packagedir.child(\"_version.py\").exists())\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 1, 2, 3, dev=0)\n__all__ = [\"__version__\"]\n''')\n\n    def test_patch(self):\n        \"\"\"\n        `incremental.update package --patch` increments the patch version.\n        \"\"\"\n        out = []\n        _run(u'inctestpkg', path=None, newversion=None, patch=True, rc=False,\n             dev=False, create=False, _date=self.date, _getcwd=self.getcwd,\n             _print=out.append)\n\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 1, 2, 4)\n__all__ = [\"__version__\"]\n''')\n        self.assertEqual(self.packagedir.child(\"__init__.py\").getContent(),\n                         b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 1, 2, 4).short()\nnext_released_version = \"inctestpkg 1.2.4\"\n\"\"\")\n\n    def test_patch_with_prerelease_and_dev(self):\n        \"\"\"\n        `incremental.update package --patch` increments the patch version, and\n        disregards any old prerelease/dev versions.\n        \"\"\"\n        self.packagedir.child('_version.py').setContent(b\"\"\"\nfrom incremental import Version\n__version__ = Version('inctestpkg', 1, 2, 3, release_candidate=1, dev=2)\n__all__ = [\"__version__\"]\n\"\"\")\n\n        out = []\n        _run(u'inctestpkg', path=None, newversion=None, patch=True, rc=False,\n             dev=False, create=False, _date=self.date, _getcwd=self.getcwd,\n             _print=out.append)\n\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 1, 2, 4)\n__all__ = [\"__version__\"]\n''')\n\n    def test_rc_patch(self):\n        \"\"\"\n        `incremental.update package --patch --rc` increments the patch\n        version and makes it a release candidate.\n        \"\"\"\n        out = []\n        _run(u'inctestpkg', path=None, newversion=None, patch=True, rc=True,\n             dev=False, create=False, _date=self.date, _getcwd=self.getcwd,\n             _print=out.append)\n\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 1, 2, 4, release_candidate=1)\n__all__ = [\"__version__\"]\n''')\n        self.assertEqual(self.packagedir.child(\"__init__.py\").getContent(),\n                         b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 1, 2, 4, release_candidate=1).short()\nnext_released_version = \"inctestpkg 1.2.4rc1\"\n\"\"\")\n\n    def test_rc_with_existing_rc(self):\n        \"\"\"\n        `incremental.update package --rc` increments the rc version if the\n        existing version is an rc, and discards any dev version.\n        \"\"\"\n        self.packagedir.child('_version.py').setContent(b\"\"\"\nfrom incremental import Version\n__version__ = Version('inctestpkg', 1, 2, 3, release_candidate=1, dev=2)\n__all__ = [\"__version__\"]\n\"\"\")\n\n        out = []\n        _run(u'inctestpkg', path=None, newversion=None, patch=False, rc=True,\n             dev=False, create=False, _date=self.date, _getcwd=self.getcwd,\n             _print=out.append)\n\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 1, 2, 3, release_candidate=2)\n__all__ = [\"__version__\"]\n''')\n        self.assertEqual(self.packagedir.child(\"__init__.py\").getContent(),\n                         b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 1, 2, 3, release_candidate=2).short()\nnext_released_version = \"inctestpkg 1.2.3rc2\"\n\"\"\")\n\n    def test_rc_with_no_rc(self):\n        \"\"\"\n        `incremental.update package --rc`, when the package is not a release\n        candidate, will issue a new major/minor rc, and disregards the micro\n        and dev.\n        \"\"\"\n        self.packagedir.child('_version.py').setContent(b\"\"\"\nfrom incremental import Version\n__version__ = Version('inctestpkg', 1, 2, 3, dev=2)\n__all__ = [\"__version__\"]\n\"\"\")\n\n        out = []\n        _run(u'inctestpkg', path=None, newversion=None, patch=False, rc=True,\n             dev=False, create=False, _date=self.date, _getcwd=self.getcwd,\n             _print=out.append)\n\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 16, 8, 0, release_candidate=1)\n__all__ = [\"__version__\"]\n''')\n        self.assertEqual(self.packagedir.child(\"__init__.py\").getContent(),\n                         b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 16, 8, 0, release_candidate=1).short()\nnext_released_version = \"inctestpkg 16.8.0rc1\"\n\"\"\")\n\n    def test_full_with_rc(self):\n        \"\"\"\n        `incremental.update package`, when the package is a release\n        candidate, will issue the major/minor, sans release candidate or dev.\n        \"\"\"\n        out = []\n        _run(u'inctestpkg', path=None, newversion=None, patch=False, rc=True,\n             dev=False, create=False, _date=self.date, _getcwd=self.getcwd,\n             _print=out.append)\n\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 16, 8, 0, release_candidate=1)\n__all__ = [\"__version__\"]\n''')\n        self.assertEqual(self.packagedir.child(\"__init__.py\").getContent(),\n                         b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 16, 8, 0, release_candidate=1).short()\nnext_released_version = \"inctestpkg 16.8.0rc1\"\n\"\"\")\n\n        _run(u'inctestpkg', path=None, newversion=None, patch=False, rc=False,\n             dev=False, create=False, _date=self.date, _getcwd=self.getcwd,\n             _print=out.append)\n\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 16, 8, 0)\n__all__ = [\"__version__\"]\n''')\n        self.assertEqual(self.packagedir.child(\"__init__.py\").getContent(),\n                         b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 16, 8, 0).short()\nnext_released_version = \"inctestpkg 16.8.0\"\n\"\"\")\n\n    def test_full_without_rc(self):\n        \"\"\"\n        `incremental.update package`, when the package is NOT a release\n        candidate, will raise an error.\n        \"\"\"\n        out = []\n        with self.assertRaises(ValueError) as e:\n            _run(u'inctestpkg', path=None, newversion=None, patch=False,\n                 rc=False, dev=False, create=False, _date=self.date,\n                 _getcwd=self.getcwd, _print=out.append)\n\n        self.assertEqual(\n            e.exception.args[0],\n            \"You need to issue a rc before updating the major/minor\")\n\n    def test_no_mix_newversion(self):\n        \"\"\"\n        The `--newversion` flag can't be mixed with --patch, --rc, or --dev.\n        \"\"\"\n        out = []\n        with self.assertRaises(ValueError) as e:\n            _run(u'inctestpkg', path=None, newversion=\"1\", patch=True,\n                 rc=False, dev=False, create=False, _date=self.date,\n                 _getcwd=self.getcwd, _print=out.append)\n        self.assertEqual(e.exception.args[0], \"Only give --newversion\")\n\n        with self.assertRaises(ValueError) as e:\n            _run(u'inctestpkg', path=None, newversion=\"1\", patch=False,\n                 rc=True, dev=False, create=False, _date=self.date,\n                 _getcwd=self.getcwd, _print=out.append)\n        self.assertEqual(e.exception.args[0], \"Only give --newversion\")\n\n        with self.assertRaises(ValueError) as e:\n            _run(u'inctestpkg', path=None, newversion=\"1\", patch=False,\n                 rc=False, dev=True, create=False, _date=self.date,\n                 _getcwd=self.getcwd, _print=out.append)\n        self.assertEqual(e.exception.args[0], \"Only give --newversion\")\n\n    def test_no_mix_dev(self):\n        \"\"\"\n        The `--dev` flag can't be mixed with --patch, or --rc.\n        \"\"\"\n        out = []\n        with self.assertRaises(ValueError) as e:\n            _run(u'inctestpkg', path=None, newversion=None, patch=True,\n                 rc=False, dev=True, create=False, _date=self.date,\n                 _getcwd=self.getcwd, _print=out.append)\n        self.assertEqual(e.exception.args[0], \"Only give --dev\")\n\n        with self.assertRaises(ValueError) as e:\n            _run(u'inctestpkg', path=None, newversion=None, patch=False,\n                 rc=True, dev=True, create=False, _date=self.date,\n                 _getcwd=self.getcwd, _print=out.append)\n        self.assertEqual(e.exception.args[0], \"Only give --dev\")\n\n    def test_no_mix_create(self):\n        \"\"\"\n        The `--create` flag can't be mixed with --patch, --rc, --dev, or\n        --newversion.\n        \"\"\"\n        out = []\n        with self.assertRaises(ValueError) as e:\n            _run(u'inctestpkg', path=None, newversion=None, patch=True,\n                 rc=False, dev=False, create=True, _date=self.date,\n                 _getcwd=self.getcwd, _print=out.append)\n        self.assertEqual(e.exception.args[0], \"Only give --create\")\n\n        with self.assertRaises(ValueError) as e:\n            _run(u'inctestpkg', path=None, newversion=\"1\", patch=False,\n                 rc=False, dev=False, create=True, _date=self.date,\n                 _getcwd=self.getcwd, _print=out.append)\n        self.assertEqual(e.exception.args[0], \"Only give --create\")\n\n        with self.assertRaises(ValueError) as e:\n            _run(u'inctestpkg', path=None, newversion=None, patch=False,\n                 rc=True, dev=False, create=True, _date=self.date,\n                 _getcwd=self.getcwd, _print=out.append)\n        self.assertEqual(e.exception.args[0], \"Only give --create\")\n\n        with self.assertRaises(ValueError) as e:\n            _run(u'inctestpkg', path=None, newversion=None, patch=False,\n                 rc=False, dev=True, create=True, _date=self.date,\n                 _getcwd=self.getcwd, _print=out.append)\n        self.assertEqual(e.exception.args[0], \"Only give --create\")\n\n    def test_newversion(self):\n        \"\"\"\n        `incremental.update package --newversion=1.2.3rc1dev3`, will set that\n        version in the package.\n        \"\"\"\n        out = []\n        _run(u'inctestpkg', path=None, newversion=\"1.2.3rc1dev3\", patch=False,\n             rc=False, dev=False, create=False, _date=self.date,\n             _getcwd=self.getcwd, _print=out.append)\n\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 1, 2, 3, release_candidate=1, dev=3)\n__all__ = [\"__version__\"]\n''')\n        self.assertEqual(self.packagedir.child(\"__init__.py\").getContent(),\n                         (b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 1, 2, 3, \"\"\"\n                         b\"\"\"release_candidate=1, dev=3).short()\nnext_released_version = \"inctestpkg 1.2.3rc1dev3\"\n\"\"\"))\n\n    def test_newversion_bare(self):\n        \"\"\"\n        `incremental.update package --newversion=1`, will set that\n        version in the package.\n        \"\"\"\n        out = []\n        _run(u'inctestpkg', path=None, newversion=\"1\", patch=False,\n             rc=False, dev=False, create=False, _date=self.date,\n             _getcwd=self.getcwd, _print=out.append)\n\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 1, 0, 0)\n__all__ = [\"__version__\"]\n''')\n        self.assertEqual(self.packagedir.child(\"__init__.py\").getContent(),\n                         b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 1, 0, 0).short()\nnext_released_version = \"inctestpkg 1.0.0\"\n\"\"\")\n\n\nclass ScriptTests(TestCase):\n\n    def setUp(self):\n\n        self.srcdir = FilePath(self.mktemp())\n        self.srcdir.makedirs()\n\n        self.srcdir.child('src').makedirs()\n\n        packagedir = self.srcdir.child('src').child('inctestpkg')\n        packagedir.makedirs()\n\n        packagedir.child('__init__.py').setContent(b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 'NEXT', 0, 0).short()\nnext_released_version = \"inctestpkg NEXT\"\n\"\"\")\n        packagedir.child('_version.py').setContent(b\"\"\"\nfrom incremental import Version\n__version__ = Version('inctestpkg', 1, 2, 3)\n__all__ = [\"__version__\"]\n\"\"\")\n        self.getcwd = lambda: self.srcdir.path\n        self.packagedir = packagedir\n\n        class Date(object):\n            year = 2016\n            month = 8\n\n        class DateModule(object):\n            def today(self):\n                return Date()\n\n        self.date = DateModule()\n\n    def test_run(self):\n        \"\"\"\n        Calling run() with no args will cause it to print help.\n        \"\"\"\n        stringio = NativeStringIO()\n        self.patch(sys, 'stdout', stringio)\n\n        with self.assertRaises(SystemExit) as e:\n            run([\"--help\"])\n\n        self.assertEqual(e.exception.args[0], 0)\n        self.assertIn(\"Show this message and exit\", stringio.getvalue())\n\n    def test_insufficient_args(self):\n        \"\"\"\n        Calling run() with no args will cause it to print help.\n        \"\"\"\n        stringio = NativeStringIO()\n        self.patch(sys, 'stdout', stringio)\n        self.patch(os, 'getcwd', self.getcwd)\n        self.patch(datetime, 'date', self.date)\n\n        with self.assertRaises(SystemExit) as e:\n            run([\"inctestpkg\", \"--rc\"])\n\n        self.assertEqual(e.exception.args[0], 0)\n        self.assertIn(\"Updating codebase\", stringio.getvalue())\n\n        self.assertEqual(self.packagedir.child(\"_version.py\").getContent(),\n                         b'''\"\"\"\nProvides inctestpkg version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update inctestpkg` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('inctestpkg', 16, 8, 0, release_candidate=1)\n__all__ = [\"__version__\"]\n''')\n        self.assertEqual(self.packagedir.child(\"__init__.py\").getContent(),\n                         b\"\"\"\nfrom incremental import Version\nintroduced_in = Version('inctestpkg', 16, 8, 0, release_candidate=1).short()\nnext_released_version = \"inctestpkg 16.8.0rc1\"\n\"\"\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental/tests/test_version.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{incremental}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport operator\n\nfrom incremental import getVersionString, IncomparableVersions\nfrom incremental import Version, _inf\n\nfrom twisted.trial.unittest import TestCase\n\n\nclass VersionsTests(TestCase):\n\n    def test_localIsShort(self):\n        \"\"\"\n        The local version is the same as the short version.\n        \"\"\"\n        va = Version(\"dummy\", 1, 0, 0, release_candidate=1, dev=3)\n        self.assertEqual(va.local(), va.short())\n\n    def test_versionComparison(self):\n        \"\"\"\n        Versions can be compared for equality and order.\n        \"\"\"\n        va = Version(\"dummy\", 1, 0, 0)\n        vb = Version(\"dummy\", 0, 1, 0)\n        self.assertTrue(va > vb)\n        self.assertTrue(vb < va)\n        self.assertTrue(va >= vb)\n        self.assertTrue(vb <= va)\n        self.assertTrue(va != vb)\n        self.assertTrue(vb == Version(\"dummy\", 0, 1, 0))\n        self.assertTrue(vb == vb)\n\n    def test_versionComparisonCaseInsensitive(self):\n        \"\"\"\n        Version package names are case insensitive.\n        \"\"\"\n        va = Version(\"dummy\", 1, 0, 0)\n        vb = Version(\"DuMmY\", 0, 1, 0)\n        self.assertTrue(va > vb)\n        self.assertTrue(vb < va)\n        self.assertTrue(va >= vb)\n        self.assertTrue(vb <= va)\n        self.assertTrue(va != vb)\n        self.assertTrue(vb == Version(\"dummy\", 0, 1, 0))\n        self.assertTrue(vb == vb)\n\n    def test_comparingNEXTReleases(self):\n        \"\"\"\n        NEXT releases are always larger than numbered releases.\n        \"\"\"\n        va = Version(\"whatever\", \"NEXT\", 0, 0)\n        vb = Version(\"whatever\", 1, 0, 0)\n        self.assertTrue(va > vb)\n        self.assertFalse(va < vb)\n        self.assertNotEquals(vb, va)\n\n    def test_NEXTMustBeAlone(self):\n        \"\"\"\n        NEXT releases must always have the rest of the numbers set to 0.\n        \"\"\"\n        with self.assertRaises(ValueError):\n            Version(\"whatever\", \"NEXT\", 1, 0, release_candidate=0, dev=0)\n\n        with self.assertRaises(ValueError):\n            Version(\"whatever\", \"NEXT\", 0, 1, release_candidate=0, dev=0)\n\n        with self.assertRaises(ValueError):\n            Version(\"whatever\", \"NEXT\", 0, 0, release_candidate=1, dev=0)\n\n        with self.assertRaises(ValueError):\n            Version(\"whatever\", \"NEXT\", 0, 0, release_candidate=0, dev=1)\n\n    def test_comparingNEXTReleasesEqual(self):\n        \"\"\"\n        NEXT releases are equal to each other.\n        \"\"\"\n        va = Version(\"whatever\", \"NEXT\", 0, 0)\n        vb = Version(\"whatever\", \"NEXT\", 0, 0)\n        self.assertEquals(vb, va)\n\n    def test_comparingPrereleasesWithReleases(self):\n        \"\"\"\n        Prereleases are always less than versions without prereleases.\n        \"\"\"\n        va = Version(\"whatever\", 1, 0, 0, prerelease=1)\n        vb = Version(\"whatever\", 1, 0, 0)\n        self.assertTrue(va < vb)\n        self.assertFalse(va > vb)\n        self.assertNotEquals(vb, va)\n\n    def test_prereleaseDeprecated(self):\n        \"\"\"\n        Passing 'prerelease' to Version is deprecated.\n        \"\"\"\n        Version(\"whatever\", 1, 0, 0, prerelease=1)\n        warnings = self.flushWarnings([self.test_prereleaseDeprecated])\n        self.assertEqual(len(warnings), 1)\n        self.assertEqual(\n            warnings[0]['message'],\n            (\"Passing prerelease to incremental.Version was deprecated in \"\n             \"Incremental 16.9.0. Please pass release_candidate instead.\"))\n\n    def test_prereleaseAttributeDeprecated(self):\n        \"\"\"\n        Accessing 'prerelease' on a Version is deprecated.\n        \"\"\"\n        va = Version(\"whatever\", 1, 0, 0, release_candidate=1)\n        va.prerelease\n        warnings = self.flushWarnings(\n            [self.test_prereleaseAttributeDeprecated])\n        self.assertEqual(len(warnings), 1)\n        self.assertEqual(\n            warnings[0]['message'],\n            (\"Accessing incremental.Version.prerelease was deprecated in \"\n             \"Incremental 16.9.0. Use Version.release_candidate instead.\"))\n\n    def test_comparingReleaseCandidatesWithReleases(self):\n        \"\"\"\n        Release Candidates are always less than versions without release\n        candidates.\n        \"\"\"\n        va = Version(\"whatever\", 1, 0, 0, release_candidate=1)\n        vb = Version(\"whatever\", 1, 0, 0)\n        self.assertTrue(va < vb)\n        self.assertFalse(va > vb)\n        self.assertNotEquals(vb, va)\n\n    def test_comparingDevReleasesWithReleases(self):\n        \"\"\"\n        Dev releases are always less than versions without dev releases.\n        \"\"\"\n        va = Version(\"whatever\", 1, 0, 0, dev=1)\n        vb = Version(\"whatever\", 1, 0, 0)\n        self.assertTrue(va < vb)\n        self.assertFalse(va > vb)\n        self.assertNotEquals(vb, va)\n\n    def test_rcEqualspre(self):\n        \"\"\"\n        Release Candidates are equal to prereleases.\n        \"\"\"\n        va = Version(\"whatever\", 1, 0, 0, release_candidate=1)\n        vb = Version(\"whatever\", 1, 0, 0, prerelease=1)\n        self.assertTrue(va == vb)\n        self.assertFalse(va != vb)\n\n    def test_rcOrpreButNotBoth(self):\n        \"\"\"\n        Release Candidate and prerelease can't both be given.\n        \"\"\"\n        with self.assertRaises(ValueError):\n            Version(\"whatever\", 1, 0, 0,\n                    prerelease=1, release_candidate=1)\n\n    def test_comparingReleaseCandidates(self):\n        \"\"\"\n        The value specified as the release candidate is used in version\n        comparisons.\n        \"\"\"\n        va = Version(\"whatever\", 1, 0, 0, release_candidate=1)\n        vb = Version(\"whatever\", 1, 0, 0, release_candidate=2)\n        self.assertTrue(va < vb)\n        self.assertTrue(vb > va)\n        self.assertTrue(va <= vb)\n        self.assertTrue(vb >= va)\n        self.assertTrue(va != vb)\n        self.assertTrue(vb == Version(\"whatever\", 1, 0, 0,\n                                      release_candidate=2))\n        self.assertTrue(va == va)\n\n    def test_comparingDev(self):\n        \"\"\"\n        The value specified as the dev release is used in version comparisons.\n        \"\"\"\n        va = Version(\"whatever\", 1, 0, 0, dev=1)\n        vb = Version(\"whatever\", 1, 0, 0, dev=2)\n        self.assertTrue(va < vb)\n        self.assertTrue(vb > va)\n        self.assertTrue(va <= vb)\n        self.assertTrue(vb >= va)\n        self.assertTrue(va != vb)\n        self.assertTrue(vb == Version(\"whatever\", 1, 0, 0,\n                                      dev=2))\n        self.assertTrue(va == va)\n\n    def test_comparingDevAndRC(self):\n        \"\"\"\n        The value specified as the dev release and release candidate is used in\n        version comparisons.\n        \"\"\"\n        va = Version(\"whatever\", 1, 0, 0, release_candidate=1, dev=1)\n        vb = Version(\"whatever\", 1, 0, 0, release_candidate=1, dev=2)\n        self.assertTrue(va < vb)\n        self.assertTrue(vb > va)\n        self.assertTrue(va <= vb)\n        self.assertTrue(vb >= va)\n        self.assertTrue(va != vb)\n        self.assertTrue(vb == Version(\"whatever\", 1, 0, 0,\n                                      release_candidate=1, dev=2))\n        self.assertTrue(va == va)\n\n    def test_comparingDevAndRCDifferent(self):\n        \"\"\"\n        The value specified as the dev release and release candidate is used in\n        version comparisons.\n        \"\"\"\n        va = Version(\"whatever\", 1, 0, 0, release_candidate=1, dev=1)\n        vb = Version(\"whatever\", 1, 0, 0, release_candidate=2, dev=1)\n        self.assertTrue(va < vb)\n        self.assertTrue(vb > va)\n        self.assertTrue(va <= vb)\n        self.assertTrue(vb >= va)\n        self.assertTrue(va != vb)\n        self.assertTrue(vb == Version(\"whatever\", 1, 0, 0,\n                                      release_candidate=2, dev=1))\n        self.assertTrue(va == va)\n\n    def test_infComparison(self):\n        \"\"\"\n        L{_inf} is equal to L{_inf}.\n\n        This is a regression test.\n        \"\"\"\n        self.assertEqual(_inf, _inf)\n\n    def test_disallowBuggyComparisons(self):\n        \"\"\"\n        The package names of the Version objects need to be the same.\n        \"\"\"\n        self.assertRaises(IncomparableVersions,\n                          operator.eq,\n                          Version(\"dummy\", 1, 0, 0),\n                          Version(\"dumym\", 1, 0, 0))\n\n    def test_notImplementedComparisons(self):\n        \"\"\"\n        Comparing a L{Version} to some other object type results in\n        C{NotImplemented}.\n        \"\"\"\n        va = Version(\"dummy\", 1, 0, 0)\n        vb = (\"dummy\", 1, 0, 0)  # a tuple is not a Version object\n        self.assertEqual(va.__cmp__(vb), NotImplemented)\n\n    def test_repr(self):\n        \"\"\"\n        Calling C{repr} on a version returns a human-readable string\n        representation of the version.\n        \"\"\"\n        self.assertEqual(repr(Version(\"dummy\", 1, 2, 3)),\n                         \"Version('dummy', 1, 2, 3)\")\n\n    def test_reprWithPrerelease(self):\n        \"\"\"\n        Calling C{repr} on a version with a prerelease returns a human-readable\n        string representation of the version including the prerelease as a\n        release candidate..\n        \"\"\"\n        self.assertEqual(repr(Version(\"dummy\", 1, 2, 3, prerelease=4)),\n                         \"Version('dummy', 1, 2, 3, release_candidate=4)\")\n\n    def test_reprWithReleaseCandidate(self):\n        \"\"\"\n        Calling C{repr} on a version with a release candidate returns a\n        human-readable string representation of the version including the rc.\n        \"\"\"\n        self.assertEqual(repr(Version(\"dummy\", 1, 2, 3, release_candidate=4)),\n                         \"Version('dummy', 1, 2, 3, release_candidate=4)\")\n\n    def test_devWithReleaseCandidate(self):\n        \"\"\"\n        Calling C{repr} on a version with a dev release returns a\n        human-readable string representation of the version including the dev\n        release.\n        \"\"\"\n        self.assertEqual(repr(Version(\"dummy\", 1, 2, 3, dev=4)),\n                         \"Version('dummy', 1, 2, 3, dev=4)\")\n\n    def test_str(self):\n        \"\"\"\n        Calling C{str} on a version returns a human-readable string\n        representation of the version.\n        \"\"\"\n        self.assertEqual(str(Version(\"dummy\", 1, 2, 3)),\n                         \"[dummy, version 1.2.3]\")\n\n    def test_strWithPrerelease(self):\n        \"\"\"\n        Calling C{str} on a version with a prerelease includes the prerelease\n        as a release candidate.\n        \"\"\"\n        self.assertEqual(str(Version(\"dummy\", 1, 0, 0, prerelease=1)),\n                         \"[dummy, version 1.0.0rc1]\")\n\n    def test_strWithReleaseCandidate(self):\n        \"\"\"\n        Calling C{str} on a version with a release candidate includes the\n        release candidate.\n        \"\"\"\n        self.assertEqual(str(Version(\"dummy\", 1, 0, 0, release_candidate=1)),\n                         \"[dummy, version 1.0.0rc1]\")\n\n    def test_strWithDevAndReleaseCandidate(self):\n        \"\"\"\n        Calling C{str} on a version with a release candidate and dev release\n        includes the release candidate and the dev release.\n        \"\"\"\n        self.assertEqual(str(Version(\"dummy\", 1, 0, 0,\n                                     release_candidate=1, dev=2)),\n                         \"[dummy, version 1.0.0rc1dev2]\")\n\n    def test_strWithDev(self):\n        \"\"\"\n        Calling C{str} on a version with a dev release includes the dev\n        release.\n        \"\"\"\n        self.assertEqual(str(Version(\"dummy\", 1, 0, 0, dev=1)),\n                         \"[dummy, version 1.0.0dev1]\")\n\n    def testShort(self):\n        self.assertEqual(Version('dummy', 1, 2, 3).short(), '1.2.3')\n\n    def test_getVersionString(self):\n        \"\"\"\n        L{getVersionString} returns a string with the package name and the\n        short version number.\n        \"\"\"\n        self.assertEqual(\n            'Twisted 8.0.0', getVersionString(Version('Twisted', 8, 0, 0)))\n\n    def test_getVersionStringWithPrerelease(self):\n        \"\"\"\n        L{getVersionString} includes the prerelease as a release candidate, if\n        any.\n        \"\"\"\n        self.assertEqual(\n            getVersionString(Version(\"whatever\", 8, 0, 0, prerelease=1)),\n            \"whatever 8.0.0rc1\")\n\n    def test_getVersionStringWithReleaseCandidate(self):\n        \"\"\"\n        L{getVersionString} includes the release candidate, if any.\n        \"\"\"\n        self.assertEqual(\n            getVersionString(Version(\"whatever\", 8, 0, 0,\n                                     release_candidate=1)),\n            \"whatever 8.0.0rc1\")\n\n    def test_getVersionStringWithDev(self):\n        \"\"\"\n        L{getVersionString} includes the dev release, if any.\n        \"\"\"\n        self.assertEqual(\n            getVersionString(Version(\"whatever\", 8, 0, 0,\n                                     dev=1)),\n            \"whatever 8.0.0dev1\")\n\n    def test_getVersionStringWithDevAndRC(self):\n        \"\"\"\n        L{getVersionString} includes the dev release and release candidate, if\n        any.\n        \"\"\"\n        self.assertEqual(\n            getVersionString(Version(\"whatever\", 8, 0, 0,\n                                     release_candidate=2, dev=1)),\n            \"whatever 8.0.0rc2dev1\")\n\n    def test_baseWithNEXT(self):\n        \"\"\"\n        The C{base} method returns just \"NEXT\" when NEXT is the major version.\n        \"\"\"\n        self.assertEqual(Version(\"foo\", \"NEXT\", 0, 0).base(), \"NEXT\")\n\n    def test_base(self):\n        \"\"\"\n        The C{base} method returns a very simple representation of the version.\n        \"\"\"\n        self.assertEqual(Version(\"foo\", 1, 0, 0).base(), \"1.0.0\")\n\n    def test_baseWithPrerelease(self):\n        \"\"\"\n        The base version includes 'rcX' for versions with prereleases.\n        \"\"\"\n        self.assertEqual(Version(\"foo\", 1, 0, 0, prerelease=8).base(),\n                         \"1.0.0rc8\")\n\n    def test_baseWithDev(self):\n        \"\"\"\n        The base version includes 'devX' for versions with dev releases.\n        \"\"\"\n        self.assertEqual(Version(\"foo\", 1, 0, 0, dev=8).base(),\n                         \"1.0.0dev8\")\n\n    def test_baseWithReleaseCandidate(self):\n        \"\"\"\n        The base version includes 'rcX' for versions with prereleases.\n        \"\"\"\n        self.assertEqual(Version(\"foo\", 1, 0, 0, release_candidate=8).base(),\n                         \"1.0.0rc8\")\n\n    def test_baseWithDevAndRC(self):\n        \"\"\"\n        The base version includes 'rcXdevX' for versions with dev releases and\n        a release candidate.\n        \"\"\"\n        self.assertEqual(Version(\"foo\", 1, 0, 0,\n                                 release_candidate=2, dev=8).base(),\n                         \"1.0.0rc2dev8\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental/update.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport click\nimport os\nimport datetime\n\nfrom incremental import Version\nfrom twisted.python.filepath import FilePath\n\n_VERSIONPY_TEMPLATE = '''\"\"\"\nProvides %s version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update %s` to change this file.\n\nfrom incremental import Version\n\n__version__ = %s\n__all__ = [\"__version__\"]\n'''\n\n_YEAR_START = 2000\n\n\ndef _findPath(path, package):\n\n    cwd = FilePath(path)\n\n    src_dir = cwd.child(\"src\").child(package.lower())\n    current_dir = cwd.child(package.lower())\n\n    if src_dir.isdir():\n        return src_dir\n    elif current_dir.isdir():\n        return current_dir\n    else:\n        raise ValueError((\"Can't find under `./src` or `./`. Check the \"\n                          \"package name is right (note that we expect your \"\n                          \"package name to be lower cased), or pass it using \"\n                          \"'--path'.\"))\n\n\ndef _existing_version(path):\n    version_info = {}\n\n    with path.child(\"_version.py\").open('r') as f:\n        exec(f.read(), version_info)\n\n    return version_info[\"__version__\"]\n\n\ndef _run(package, path, newversion, patch, rc, dev, create,\n         _date=None, _getcwd=None, _print=print):\n\n    if not _getcwd:\n        _getcwd = os.getcwd\n\n    if not _date:\n        _date = datetime.date.today()\n\n    if type(package) != str:\n        package = package.encode('utf8')\n\n    if not path:\n        path = _findPath(_getcwd(), package)\n    else:\n        path = FilePath(path)\n\n    if newversion and patch or newversion and dev or newversion and rc:\n        raise ValueError(\"Only give --newversion\")\n\n    if dev and patch or dev and rc:\n        raise ValueError(\"Only give --dev\")\n\n    if create and dev or create and patch or create and rc or \\\n       create and newversion:\n        raise ValueError(\"Only give --create\")\n\n    if newversion:\n        from pkg_resources import parse_version\n        existing = _existing_version(path)\n        st_version = parse_version(newversion)._version\n\n        release = list(st_version.release)\n\n        if len(release) == 1:\n            release.append(0)\n        if len(release) == 2:\n            release.append(0)\n\n        v = Version(\n            package, *release,\n            release_candidate=st_version.pre[1] if st_version.pre else None,\n            dev=st_version.dev[1] if st_version.dev else None)\n\n    elif create:\n        v = Version(package, _date.year - _YEAR_START, _date.month, 0)\n        existing = v\n\n    elif rc and not patch:\n        existing = _existing_version(path)\n\n        if existing.release_candidate:\n            v = Version(package, existing.major, existing.minor,\n                        existing.micro, existing.release_candidate + 1)\n        else:\n            v = Version(package, _date.year - _YEAR_START, _date.month, 0, 1)\n\n    elif patch:\n        if rc:\n            rc = 1\n        else:\n            rc = None\n\n        existing = _existing_version(path)\n        v = Version(package, existing.major, existing.minor,\n                    existing.micro + 1, rc)\n\n    elif dev:\n        existing = _existing_version(path)\n\n        if existing.dev is None:\n            _dev = 0\n        else:\n            _dev = existing.dev + 1\n\n        v = Version(package, existing.major, existing.minor,\n                    existing.micro, existing.release_candidate, dev=_dev)\n\n    else:\n        existing = _existing_version(path)\n\n        if existing.release_candidate:\n            v = Version(package,\n                        existing.major, existing.minor, existing.micro)\n        else:\n            raise ValueError(\n                \"You need to issue a rc before updating the major/minor\")\n\n    NEXT_repr = repr(Version(package, \"NEXT\", 0, 0)).split(\"#\")[0]\n    NEXT_repr_bytes = NEXT_repr.encode('utf8')\n\n    version_repr = repr(v).split(\"#\")[0]\n    version_repr_bytes = version_repr.encode('utf8')\n\n    existing_version_repr = repr(existing).split(\"#\")[0]\n    existing_version_repr_bytes = existing_version_repr.encode('utf8')\n\n    _print(\"Updating codebase to %s\" % (v.public()))\n\n    for x in path.walk():\n\n        if not x.isfile():\n            continue\n\n        original_content = x.getContent()\n        content = original_content\n\n        # Replace previous release_candidate calls to the new one\n        if existing.release_candidate:\n            content = content.replace(existing_version_repr_bytes,\n                                      version_repr_bytes)\n            content = content.replace(\n                (package.encode('utf8') + b\" \" +\n                 existing.public().encode('utf8')),\n                (package.encode('utf8') + b\" \" +\n                 v.public().encode('utf8')))\n\n        # Replace NEXT Version calls with the new one\n        content = content.replace(NEXT_repr_bytes,\n                                  version_repr_bytes)\n        content = content.replace(NEXT_repr_bytes.replace(b\"'\", b'\"'),\n                                  version_repr_bytes)\n\n        # Replace <package> NEXT with <package> <public>\n        content = content.replace(package.encode('utf8') + b\" NEXT\",\n                                  (package.encode('utf8') + b\" \" +\n                                   v.public().encode('utf8')))\n\n        if content != original_content:\n            _print(\"Updating %s\" % (x.path,))\n            with x.open('w') as f:\n                f.write(content)\n\n    _print(\"Updating %s/_version.py\" % (path.path))\n    with path.child(\"_version.py\").open('w') as f:\n        f.write(\n            (_VERSIONPY_TEMPLATE % (\n                package, package, version_repr)).encode('utf8'))\n\n\n@click.command()\n@click.argument('package')\n@click.option('--path', default=None)\n@click.option('--newversion', default=None)\n@click.option('--patch', is_flag=True)\n@click.option('--rc', is_flag=True)\n@click.option('--dev', is_flag=True)\n@click.option('--create', is_flag=True)\ndef run(*args, **kwargs):\n    return _run(*args, **kwargs)\n\n\nif __name__ == '__main__':  # pragma: no cover\n    run()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental-17.5.0.dist-info/DESCRIPTION.rst",
    "content": "Incremental\n===========\n\n|travis|\n|pypi|\n|coverage|\n\nIncremental is a small library that versions your Python projects.\n\nAPI documentation can be found `here <https://hawkowl.github.io/incremental/docs/>`_.\n\n\nQuick Start\n-----------\n\nAdd this to your ``setup.py``\\ 's ``setup()`` call, removing any other versioning arguments:\n\n.. code::\n\n   setup(\n       use_incremental=True,\n       setup_requires=['incremental'],\n       install_requires=['incremental'], # along with any other install dependencies\n       ...\n   }\n\n\nThen run ``python -m incremental.update <projectname> --create`` (you will need ``click`` installed from PyPI).\nIt will create a file in your package named ``_version.py`` and look like this:\n\n.. code::\n\n   from incremental import Version\n\n   __version__ = Version(\"widgetbox\", 17, 1, 0)\n   __all__ = [\"__version__\"]\n\n\nThen, so users of your project can find your version, in your root package's ``__init__.py`` add:\n\n.. code::\n\n   from ._version import __version__\n\n\nSubsequent installations of your project will then use Incremental for versioning.\n\n\nIncremental Versions\n--------------------\n\n``incremental.Version`` is a class that represents a version of a given project.\nIt is made up of the following elements (which are given during instantiation):\n\n- ``package`` (required), the name of the package this ``Version`` represents.\n- ``major``, ``minor``, ``micro`` (all required), the X.Y.Z of your project's ``Version``.\n- ``release_candidate`` (optional), set to 0 or higher to mark this ``Version`` being of a release candidate (also sometimes called a \"prerelease\").\n- ``dev`` (optional), set to 0 or higher to mark this ``Version`` as a development release.\n\nYou can extract a PEP-440 compatible version string by using the following methods:\n\n- ``.local()``, which returns a ``str`` containing the full version plus any Git or SVN information, if available. An example output would be ``\"17.1.1rc1+r123\"`` or ``\"3.7.0+rb2e812003b5d5fcf08efd1dffed6afa98d44ac8c\"``.\n- ``.public()``, which returns a ``str`` containing the full version, without any Git or SVN information. This is the version you should provide to users, or publicly use. An example output would be ``\"13.2.0\"``, ``\"17.1.2dev1\"``, or ``\"18.8.0rc2\"``.\n\nCalling ``repr()`` with a ``Version`` will give a Python-source-code representation of it, and calling ``str()`` with a ``Version`` will provide a string similar to ``'[Incremental, version 16.10.1]'``.\n\n\nUpdating\n--------\n\nIncremental includes a tool to automate updating your Incremental-using project's version called ``incremental.update``.\nIt updates the ``_version.py`` file and automatically updates some uses of Incremental versions from an indeterminate version to the current one.\nIt requires ``click`` from PyPI.\n\n``python -m incremental.update <projectname>`` will perform updates on that package.\nThe commands that can be given after that will determine what the next version is.\n\n- ``--newversion=<version>``, to set the project version to a fully-specified version (like 1.2.3, or 17.1.0dev1).\n- ``--rc``, to set the project version to ``<year-2000>.<month>.0rc1`` if the current version is not a release candidate, or bump the release candidate number by 1 if it is.\n- ``--dev``, to set the project development release number to 0 if it is not a development release, or bump the development release number by 1 if it is.\n- ``--patch``, to increment the patch number of the release. This will also reset the release candidate number, pass ``--rc`` at the same time to increment the patch number and make it a release candidate.\n\nIf you give no arguments, it will strip the release candidate number, making it a \"full release\".\n\nIncremental supports \"indeterminate\" versions, as a stand-in for the next \"full\" version. This can be used when the version which will be displayed to the end-user is unknown (for example \"introduced in\" or \"deprecated in\"). Incremental supports the following indeterminate versions:\n\n- ``Version(\"<projectname>\", \"NEXT\", 0, 0)``\n- ``<projectname> NEXT``\n\nWhen you run ``python -m incremental.update <projectname> --rc``, these will be updated to real versions (assuming the target final version is 17.1.0):\n\n- ``Version(\"<projectname>\", 17, 1, 0, release_candidate=1)``\n- ``<projectname> 17.1.0rc1``\n\nOnce the final version is made, it will become:\n\n- ``Version(\"<projectname>\", 17, 1, 0)``\n- ``<projectname> 17.1.0``\n\n\n.. |coverage| image:: https://codecov.io/github/hawkowl/incremental/coverage.svg?branch=master\n.. _coverage: https://codecov.io/github/hawkowl/incremental\n\n.. |travis| image:: https://travis-ci.org/hawkowl/incremental.svg?branch=master\n.. _travis: http://travis-ci.org/hawkowl/incremental\n\n.. |pypi| image:: http://img.shields.io/pypi/v/incremental.svg\n.. _pypi: https://pypi.python.org/pypi/incremental\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental-17.5.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental-17.5.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.0\nName: incremental\nVersion: 17.5.0\nSummary: UNKNOWN\nHome-page: https://github.com/twisted/incremental\nAuthor: Amber Brown\nAuthor-email: hawkowl@twistedmatrix.com\nLicense: MIT\nPlatform: UNKNOWN\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: MIT License\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.6\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nProvides-Extra: scripts\nRequires-Dist: click (>=6.0); extra == 'scripts'\nRequires-Dist: twisted (>=16.4.0); extra == 'scripts'\n\nIncremental\n===========\n\n|travis|\n|pypi|\n|coverage|\n\nIncremental is a small library that versions your Python projects.\n\nAPI documentation can be found `here <https://hawkowl.github.io/incremental/docs/>`_.\n\n\nQuick Start\n-----------\n\nAdd this to your ``setup.py``\\ 's ``setup()`` call, removing any other versioning arguments:\n\n.. code::\n\n   setup(\n       use_incremental=True,\n       setup_requires=['incremental'],\n       install_requires=['incremental'], # along with any other install dependencies\n       ...\n   }\n\n\nThen run ``python -m incremental.update <projectname> --create`` (you will need ``click`` installed from PyPI).\nIt will create a file in your package named ``_version.py`` and look like this:\n\n.. code::\n\n   from incremental import Version\n\n   __version__ = Version(\"widgetbox\", 17, 1, 0)\n   __all__ = [\"__version__\"]\n\n\nThen, so users of your project can find your version, in your root package's ``__init__.py`` add:\n\n.. code::\n\n   from ._version import __version__\n\n\nSubsequent installations of your project will then use Incremental for versioning.\n\n\nIncremental Versions\n--------------------\n\n``incremental.Version`` is a class that represents a version of a given project.\nIt is made up of the following elements (which are given during instantiation):\n\n- ``package`` (required), the name of the package this ``Version`` represents.\n- ``major``, ``minor``, ``micro`` (all required), the X.Y.Z of your project's ``Version``.\n- ``release_candidate`` (optional), set to 0 or higher to mark this ``Version`` being of a release candidate (also sometimes called a \"prerelease\").\n- ``dev`` (optional), set to 0 or higher to mark this ``Version`` as a development release.\n\nYou can extract a PEP-440 compatible version string by using the following methods:\n\n- ``.local()``, which returns a ``str`` containing the full version plus any Git or SVN information, if available. An example output would be ``\"17.1.1rc1+r123\"`` or ``\"3.7.0+rb2e812003b5d5fcf08efd1dffed6afa98d44ac8c\"``.\n- ``.public()``, which returns a ``str`` containing the full version, without any Git or SVN information. This is the version you should provide to users, or publicly use. An example output would be ``\"13.2.0\"``, ``\"17.1.2dev1\"``, or ``\"18.8.0rc2\"``.\n\nCalling ``repr()`` with a ``Version`` will give a Python-source-code representation of it, and calling ``str()`` with a ``Version`` will provide a string similar to ``'[Incremental, version 16.10.1]'``.\n\n\nUpdating\n--------\n\nIncremental includes a tool to automate updating your Incremental-using project's version called ``incremental.update``.\nIt updates the ``_version.py`` file and automatically updates some uses of Incremental versions from an indeterminate version to the current one.\nIt requires ``click`` from PyPI.\n\n``python -m incremental.update <projectname>`` will perform updates on that package.\nThe commands that can be given after that will determine what the next version is.\n\n- ``--newversion=<version>``, to set the project version to a fully-specified version (like 1.2.3, or 17.1.0dev1).\n- ``--rc``, to set the project version to ``<year-2000>.<month>.0rc1`` if the current version is not a release candidate, or bump the release candidate number by 1 if it is.\n- ``--dev``, to set the project development release number to 0 if it is not a development release, or bump the development release number by 1 if it is.\n- ``--patch``, to increment the patch number of the release. This will also reset the release candidate number, pass ``--rc`` at the same time to increment the patch number and make it a release candidate.\n\nIf you give no arguments, it will strip the release candidate number, making it a \"full release\".\n\nIncremental supports \"indeterminate\" versions, as a stand-in for the next \"full\" version. This can be used when the version which will be displayed to the end-user is unknown (for example \"introduced in\" or \"deprecated in\"). Incremental supports the following indeterminate versions:\n\n- ``Version(\"<projectname>\", \"NEXT\", 0, 0)``\n- ``<projectname> NEXT``\n\nWhen you run ``python -m incremental.update <projectname> --rc``, these will be updated to real versions (assuming the target final version is 17.1.0):\n\n- ``Version(\"<projectname>\", 17, 1, 0, release_candidate=1)``\n- ``<projectname> 17.1.0rc1``\n\nOnce the final version is made, it will become:\n\n- ``Version(\"<projectname>\", 17, 1, 0)``\n- ``<projectname> 17.1.0``\n\n\n.. |coverage| image:: https://codecov.io/github/hawkowl/incremental/coverage.svg?branch=master\n.. _coverage: https://codecov.io/github/hawkowl/incremental\n\n.. |travis| image:: https://travis-ci.org/hawkowl/incremental.svg?branch=master\n.. _travis: http://travis-ci.org/hawkowl/incremental\n\n.. |pypi| image:: http://img.shields.io/pypi/v/incremental.svg\n.. _pypi: https://pypi.python.org/pypi/incremental\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental-17.5.0.dist-info/RECORD",
    "content": "exampleproj/__init__.py,sha256=wVUVOn7507BCBqkRvFS9HK53UcUjXzC5msC6bJRhS6s,229\r\nexampleproj/__pycache__/__init__.cpython-36.pyc,,\r\nexampleproj/__pycache__/_version.cpython-36.pyc,,\r\nexampleproj/_version.py,sha256=rg3bI25RROVfWYekpRHyamIjC57sP9ccNh-WT810ldo,220\r\nincremental-17.5.0.dist-info/DESCRIPTION.rst,sha256=CEhuO8j_yz24FpoelRI9wsJ--6kUA9hIksHUdhrgqLY,4818\r\nincremental-17.5.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nincremental-17.5.0.dist-info/METADATA,sha256=jxH6e70AY99WYfgmo1BM9ovHcuIv3411Gyw8bqsZKyk,5651\r\nincremental-17.5.0.dist-info/RECORD,,\r\nincremental-17.5.0.dist-info/WHEEL,sha256=o2k-Qa-RMNIJmUdIc7KU6VWR_ErNRbWNlxDIpl7lm34,110\r\nincremental-17.5.0.dist-info/entry_points.txt,sha256=8Ap0rJ8G9THgI-ZYxAsGJVIffcEgM5y0GlhwZlLD0zM,83\r\nincremental-17.5.0.dist-info/metadata.json,sha256=kyDlobxp9BacDNwHCDiuuJzgskzntxABnKvt_53VXkQ,1032\r\nincremental-17.5.0.dist-info/top_level.txt,sha256=dVpYwi6ag8TlocBDEAfD7HydlIWoVmh6ESMv04izUdc,12\r\nincremental/__init__.py,sha256=F9sMkt4wNU0o9LilRL_bjh2x2UL3j0o8TQ0Azvt6A2E,9213\r\nincremental/__pycache__/__init__.cpython-36.pyc,,\r\nincremental/__pycache__/_version.cpython-36.pyc,,\r\nincremental/__pycache__/update.cpython-36.pyc,,\r\nincremental/_version.py,sha256=VNbdIBHWnhj2KgEJU1jfCaXE0_TkOofTZlR9Jnnkc7Y,272\r\nincremental/tests/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0\r\nincremental/tests/__pycache__/__init__.cpython-36.pyc,,\r\nincremental/tests/__pycache__/test_update.cpython-36.pyc,,\r\nincremental/tests/__pycache__/test_version.cpython-36.pyc,,\r\nincremental/tests/test_update.py,sha256=Blsbg_4Yddbz12GJ7P1aZepXI0lLYC5mpibjkgeIQ0U,23630\r\nincremental/tests/test_version.py,sha256=zf6SO2T4fLOvmjEKIQWwismMDQoCygqoTnb1Iscn18o,14700\r\nincremental/update.py,sha256=XdWEC3ObYusl1XnrQhwsDzxCeQDjHTlnrqYWYpfGn18,6150\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental-17.5.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.29.0)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental-17.5.0.dist-info/entry_points.txt",
    "content": "\n    [distutils.setup_keywords]\n    use_incremental = incremental:_get_version\n    "
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental-17.5.0.dist-info/metadata.json",
    "content": "{\"classifiers\": [\"Intended Audience :: Developers\", \"License :: OSI Approved :: MIT License\", \"Programming Language :: Python :: 2\", \"Programming Language :: Python :: 2.6\", \"Programming Language :: Python :: 2.7\", \"Programming Language :: Python :: 3\", \"Programming Language :: Python :: 3.3\", \"Programming Language :: Python :: 3.4\", \"Programming Language :: Python :: 3.5\", \"Programming Language :: Python :: 3.6\"], \"extensions\": {\"python.details\": {\"contacts\": [{\"email\": \"hawkowl@twistedmatrix.com\", \"name\": \"Amber Brown\", \"role\": \"author\"}], \"document_names\": {\"description\": \"DESCRIPTION.rst\"}, \"project_urls\": {\"Home\": \"https://github.com/twisted/incremental\"}}, \"python.exports\": {\"distutils.setup_keywords\": {\"use_incremental\": \"incremental:_get_version\"}}}, \"extras\": [\"scripts\"], \"generator\": \"bdist_wheel (0.29.0)\", \"license\": \"MIT\", \"metadata_version\": \"2.0\", \"name\": \"incremental\", \"run_requires\": [{\"extra\": \"scripts\", \"requires\": [\"click (>=6.0)\", \"twisted (>=16.4.0)\"]}], \"summary\": \"UNKNOWN\", \"version\": \"17.5.0\"}"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/incremental-17.5.0.dist-info/top_level.txt",
    "content": "incremental\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/ElementInclude.py",
    "content": "#\n# ElementTree\n# $Id: ElementInclude.py 1862 2004-06-18 07:31:02Z Fredrik $\n#\n# limited xinclude support for element trees\n#\n# history:\n# 2003-08-15 fl   created\n# 2003-11-14 fl   fixed default loader\n#\n# Copyright (c) 2003-2004 by Fredrik Lundh.  All rights reserved.\n#\n# fredrik@pythonware.com\n# http://www.pythonware.com\n#\n# --------------------------------------------------------------------\n# The ElementTree toolkit is\n#\n# Copyright (c) 1999-2004 by Fredrik Lundh\n#\n# By obtaining, using, and/or copying this software and/or its\n# associated documentation, you agree that you have read, understood,\n# and will comply with the following terms and conditions:\n#\n# Permission to use, copy, modify, and distribute this software and\n# its associated documentation for any purpose and without fee is\n# hereby granted, provided that the above copyright notice appears in\n# all copies, and that both that copyright notice and this permission\n# notice appear in supporting documentation, and that the name of\n# Secret Labs AB or the author not be used in advertising or publicity\n# pertaining to distribution of the software without specific, written\n# prior permission.\n#\n# SECRET LABS AB AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD\n# TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANT-\n# ABILITY AND FITNESS.  IN NO EVENT SHALL SECRET LABS AB OR THE AUTHOR\n# BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY\n# DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,\n# WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS\n# ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE\n# OF THIS SOFTWARE.\n# --------------------------------------------------------------------\n\n\"\"\"\nLimited XInclude support for the ElementTree package.\n\nWhile lxml.etree has full support for XInclude (see\n`etree.ElementTree.xinclude()`), this module provides a simpler, pure\nPython, ElementTree compatible implementation that supports a simple\nform of custom URL resolvers.\n\"\"\"\n\nfrom lxml import etree\ntry:\n    from urlparse import urljoin\n    from urllib2 import urlopen\nexcept ImportError:\n    # Python 3\n    from urllib.parse import urljoin\n    from urllib.request import urlopen\n\nXINCLUDE = \"{http://www.w3.org/2001/XInclude}\"\n\nXINCLUDE_INCLUDE = XINCLUDE + \"include\"\nXINCLUDE_FALLBACK = XINCLUDE + \"fallback\"\nXINCLUDE_ITER_TAG = XINCLUDE + \"*\"\n\n# For security reasons, the inclusion depth is limited to this read-only value by default.\nDEFAULT_MAX_INCLUSION_DEPTH = 6\n\n\n##\n# Fatal include error.\n\nclass FatalIncludeError(etree.LxmlSyntaxError):\n    pass\n\n\nclass LimitedRecursiveIncludeError(FatalIncludeError):\n    pass\n\n\n##\n# ET compatible default loader.\n# This loader reads an included resource from disk.\n#\n# @param href Resource reference.\n# @param parse Parse mode.  Either \"xml\" or \"text\".\n# @param encoding Optional text encoding.\n# @return The expanded resource.  If the parse mode is \"xml\", this\n#    is an ElementTree instance.  If the parse mode is \"text\", this\n#    is a Unicode string.  If the loader fails, it can return None\n#    or raise an IOError exception.\n# @throws IOError If the loader fails to load the resource.\n\ndef default_loader(href, parse, encoding=None):\n    file = open(href, 'rb')\n    if parse == \"xml\":\n        data = etree.parse(file).getroot()\n    else:\n        data = file.read()\n        if not encoding:\n            encoding = 'utf-8'\n        data = data.decode(encoding)\n    file.close()\n    return data\n\n\n##\n# Default loader used by lxml.etree - handles custom resolvers properly\n# \n\ndef _lxml_default_loader(href, parse, encoding=None, parser=None):\n    if parse == \"xml\":\n        data = etree.parse(href, parser).getroot()\n    else:\n        if \"://\" in href:\n            f = urlopen(href)\n        else:\n            f = open(href, 'rb')\n        data = f.read()\n        f.close()\n        if not encoding:\n            encoding = 'utf-8'\n        data = data.decode(encoding)\n    return data\n\n\n##\n# Wrapper for ET compatibility - drops the parser\n\ndef _wrap_et_loader(loader):\n    def load(href, parse, encoding=None, parser=None):\n        return loader(href, parse, encoding)\n    return load\n\n\n##\n# Expand XInclude directives.\n#\n# @param elem Root element.\n# @param loader Optional resource loader.  If omitted, it defaults\n#     to {@link default_loader}.  If given, it should be a callable\n#     that implements the same interface as <b>default_loader</b>.\n# @param base_url The base URL of the original file, to resolve\n#     relative include file references.\n# @param max_depth The maximum number of recursive inclusions.\n#     Limited to reduce the risk of malicious content explosion.\n#     Pass None to disable the limitation.\n# @throws LimitedRecursiveIncludeError If the {@link max_depth} was exceeded.\n# @throws FatalIncludeError If the function fails to include a given\n#     resource, or if the tree contains malformed XInclude elements.\n# @throws IOError If the function fails to load a given resource.\n# @returns the node or its replacement if it was an XInclude node\n\ndef include(elem, loader=None, base_url=None,\n            max_depth=DEFAULT_MAX_INCLUSION_DEPTH):\n    if max_depth is None:\n        max_depth = -1\n    elif max_depth < 0:\n        raise ValueError(\"expected non-negative depth or None for 'max_depth', got %r\" % max_depth)\n\n    if base_url is None:\n        if hasattr(elem, 'getroot'):\n            tree = elem\n            elem = elem.getroot()\n        else:\n            tree = elem.getroottree()\n        if hasattr(tree, 'docinfo'):\n            base_url = tree.docinfo.URL\n    elif hasattr(elem, 'getroot'):\n        elem = elem.getroot()\n    _include(elem, loader, base_url, max_depth)\n\n\ndef _include(elem, loader=None, base_url=None,\n             max_depth=DEFAULT_MAX_INCLUSION_DEPTH, _parent_hrefs=None):\n    if loader is not None:\n        load_include = _wrap_et_loader(loader)\n    else:\n        load_include = _lxml_default_loader\n\n    if _parent_hrefs is None:\n        _parent_hrefs = set()\n\n    parser = elem.getroottree().parser\n\n    include_elements = list(\n        elem.iter(XINCLUDE_ITER_TAG))\n\n    for e in include_elements:\n        if e.tag == XINCLUDE_INCLUDE:\n            # process xinclude directive\n            href = urljoin(base_url, e.get(\"href\"))\n            parse = e.get(\"parse\", \"xml\")\n            parent = e.getparent()\n            if parse == \"xml\":\n                if href in _parent_hrefs:\n                    raise FatalIncludeError(\n                        \"recursive include of %r detected\" % href\n                        )\n                if max_depth == 0:\n                    raise LimitedRecursiveIncludeError(\n                        \"maximum xinclude depth reached when including file %s\" % href)\n                _parent_hrefs.add(href)\n                node = load_include(href, parse, parser=parser)\n                if node is None:\n                    raise FatalIncludeError(\n                        \"cannot load %r as %r\" % (href, parse)\n                        )\n                node = _include(node, loader, href, max_depth - 1, _parent_hrefs)\n                if e.tail:\n                    node.tail = (node.tail or \"\") + e.tail\n                if parent is None:\n                    return node # replaced the root node!\n                parent.replace(e, node)\n            elif parse == \"text\":\n                text = load_include(href, parse, encoding=e.get(\"encoding\"))\n                if text is None:\n                    raise FatalIncludeError(\n                        \"cannot load %r as %r\" % (href, parse)\n                        )\n                predecessor = e.getprevious()\n                if predecessor is not None:\n                    predecessor.tail = (predecessor.tail or \"\") + text\n                elif parent is None:\n                    return text # replaced the root node!\n                else:\n                    parent.text = (parent.text or \"\") + text + (e.tail or \"\")\n                parent.remove(e)\n            else:\n                raise FatalIncludeError(\n                    \"unknown parse type in xi:include tag (%r)\" % parse\n                )\n        elif e.tag == XINCLUDE_FALLBACK:\n            parent = e.getparent()\n            if parent is not None and parent.tag != XINCLUDE_INCLUDE:\n                raise FatalIncludeError(\n                    \"xi:fallback tag must be child of xi:include (%r)\" % e.tag\n                    )\n        else:\n            raise FatalIncludeError(\n                \"Invalid element found in XInclude namespace (%r)\" % e.tag\n                )\n    return elem\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/__init__.py",
    "content": "# this is a package\n\ndef get_include():\n    \"\"\"\n    Returns a list of header include paths (for lxml itself, libxml2\n    and libxslt) needed to compile C code against lxml if it was built\n    with statically linked libraries.\n    \"\"\"\n    import os\n    lxml_path = __path__[0]\n    include_path = os.path.join(lxml_path, 'includes')\n    includes = [include_path, lxml_path]\n\n    for name in os.listdir(include_path):\n        path = os.path.join(include_path, name)\n        if os.path.isdir(path):\n            includes.append(path)\n\n    return includes\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/_elementpath.py",
    "content": "# cython: language_level=2\n\n#\n# ElementTree\n# $Id: ElementPath.py 3375 2008-02-13 08:05:08Z fredrik $\n#\n# limited xpath support for element trees\n#\n# history:\n# 2003-05-23 fl   created\n# 2003-05-28 fl   added support for // etc\n# 2003-08-27 fl   fixed parsing of periods in element names\n# 2007-09-10 fl   new selection engine\n# 2007-09-12 fl   fixed parent selector\n# 2007-09-13 fl   added iterfind; changed findall to return a list\n# 2007-11-30 fl   added namespaces support\n# 2009-10-30 fl   added child element value filter\n#\n# Copyright (c) 2003-2009 by Fredrik Lundh.  All rights reserved.\n#\n# fredrik@pythonware.com\n# http://www.pythonware.com\n#\n# --------------------------------------------------------------------\n# The ElementTree toolkit is\n#\n# Copyright (c) 1999-2009 by Fredrik Lundh\n#\n# By obtaining, using, and/or copying this software and/or its\n# associated documentation, you agree that you have read, understood,\n# and will comply with the following terms and conditions:\n#\n# Permission to use, copy, modify, and distribute this software and\n# its associated documentation for any purpose and without fee is\n# hereby granted, provided that the above copyright notice appears in\n# all copies, and that both that copyright notice and this permission\n# notice appear in supporting documentation, and that the name of\n# Secret Labs AB or the author not be used in advertising or publicity\n# pertaining to distribution of the software without specific, written\n# prior permission.\n#\n# SECRET LABS AB AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD\n# TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANT-\n# ABILITY AND FITNESS.  IN NO EVENT SHALL SECRET LABS AB OR THE AUTHOR\n# BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY\n# DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,\n# WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS\n# ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE\n# OF THIS SOFTWARE.\n# --------------------------------------------------------------------\n\n##\n# Implementation module for XPath support.  There's usually no reason\n# to import this module directly; the <b>ElementTree</b> does this for\n# you, if needed.\n##\n\nfrom __future__ import absolute_import\n\nimport re\n\nxpath_tokenizer_re = re.compile(\n    \"(\"\n    \"'[^']*'|\\\"[^\\\"]*\\\"|\"\n    \"::|\"\n    \"//?|\"\n    r\"\\.\\.|\"\n    r\"\\(\\)|\"\n    r\"[/.*:\\[\\]\\(\\)@=])|\"\n    r\"((?:\\{[^}]+\\})?[^/\\[\\]\\(\\)@=\\s]+)|\"\n    r\"\\s+\"\n    )\n\ndef xpath_tokenizer(pattern, namespaces=None):\n    # ElementTree uses '', lxml used None originally.\n    default_namespace = (namespaces.get(None) or namespaces.get('')) if namespaces else None\n    parsing_attribute = False\n    for token in xpath_tokenizer_re.findall(pattern):\n        ttype, tag = token\n        if tag and tag[0] != \"{\":\n            if \":\" in tag:\n                prefix, uri = tag.split(\":\", 1)\n                try:\n                    if not namespaces:\n                        raise KeyError\n                    yield ttype, \"{%s}%s\" % (namespaces[prefix], uri)\n                except KeyError:\n                    raise SyntaxError(\"prefix %r not found in prefix map\" % prefix)\n            elif default_namespace and not parsing_attribute:\n                yield ttype, \"{%s}%s\" % (default_namespace, tag)\n            else:\n                yield token\n            parsing_attribute = False\n        else:\n            yield token\n            parsing_attribute = ttype == '@'\n\n\ndef prepare_child(next, token):\n    tag = token[1]\n    def select(result):\n        for elem in result:\n            for e in elem.iterchildren(tag):\n                yield e\n    return select\n\ndef prepare_star(next, token):\n    def select(result):\n        for elem in result:\n            for e in elem.iterchildren('*'):\n                yield e\n    return select\n\ndef prepare_self(next, token):\n    def select(result):\n        return result\n    return select\n\ndef prepare_descendant(next, token):\n    token = next()\n    if token[0] == \"*\":\n        tag = \"*\"\n    elif not token[0]:\n        tag = token[1]\n    else:\n        raise SyntaxError(\"invalid descendant\")\n    def select(result):\n        for elem in result:\n            for e in elem.iterdescendants(tag):\n                yield e\n    return select\n\ndef prepare_parent(next, token):\n    def select(result):\n        for elem in result:\n            parent = elem.getparent()\n            if parent is not None:\n                yield parent\n    return select\n\ndef prepare_predicate(next, token):\n    # FIXME: replace with real parser!!! refs:\n    # http://effbot.org/zone/simple-iterator-parser.htm\n    # http://javascript.crockford.com/tdop/tdop.html\n    signature = ''\n    predicate = []\n    while 1:\n        token = next()\n        if token[0] == \"]\":\n            break\n        if token == ('', ''):\n            # ignore whitespace\n            continue\n        if token[0] and token[0][:1] in \"'\\\"\":\n            token = \"'\", token[0][1:-1]\n        signature += token[0] or \"-\"\n        predicate.append(token[1])\n\n    # use signature to determine predicate type\n    if signature == \"@-\":\n        # [@attribute] predicate\n        key = predicate[1]\n        def select(result):\n            for elem in result:\n                if elem.get(key) is not None:\n                    yield elem\n        return select\n    if signature == \"@-='\":\n        # [@attribute='value']\n        key = predicate[1]\n        value = predicate[-1]\n        def select(result):\n            for elem in result:\n                if elem.get(key) == value:\n                    yield elem\n        return select\n    if signature == \"-\" and not re.match(r\"-?\\d+$\", predicate[0]):\n        # [tag]\n        tag = predicate[0]\n        def select(result):\n            for elem in result:\n                for _ in elem.iterchildren(tag):\n                    yield elem\n                    break\n        return select\n    if signature == \".='\" or (signature == \"-='\" and not re.match(r\"-?\\d+$\", predicate[0])):\n        # [.='value'] or [tag='value']\n        tag = predicate[0]\n        value = predicate[-1]\n        if tag:\n            def select(result):\n                for elem in result:\n                    for e in elem.iterchildren(tag):\n                        if \"\".join(e.itertext()) == value:\n                            yield elem\n                            break\n        else:\n            def select(result):\n                for elem in result:\n                    if \"\".join(elem.itertext()) == value:\n                        yield elem\n        return select\n    if signature == \"-\" or signature == \"-()\" or signature == \"-()-\":\n        # [index] or [last()] or [last()-index]\n        if signature == \"-\":\n            # [index]\n            index = int(predicate[0]) - 1\n            if index < 0:\n                if index == -1:\n                    raise SyntaxError(\n                        \"indices in path predicates are 1-based, not 0-based\")\n                else:\n                    raise SyntaxError(\"path index >= 1 expected\")\n        else:\n            if predicate[0] != \"last\":\n                raise SyntaxError(\"unsupported function\")\n            if signature == \"-()-\":\n                try:\n                    index = int(predicate[2]) - 1\n                except ValueError:\n                    raise SyntaxError(\"unsupported expression\")\n            else:\n                index = -1\n        def select(result):\n            for elem in result:\n                parent = elem.getparent()\n                if parent is None:\n                    continue\n                try:\n                    # FIXME: what if the selector is \"*\" ?\n                    elems = list(parent.iterchildren(elem.tag))\n                    if elems[index] is elem:\n                        yield elem\n                except IndexError:\n                    pass\n        return select\n    raise SyntaxError(\"invalid predicate\")\n\nops = {\n    \"\": prepare_child,\n    \"*\": prepare_star,\n    \".\": prepare_self,\n    \"..\": prepare_parent,\n    \"//\": prepare_descendant,\n    \"[\": prepare_predicate,\n}\n\n\n# --------------------------------------------------------------------\n\n_cache = {}\n\n\ndef _build_path_iterator(path, namespaces):\n    \"\"\"compile selector pattern\"\"\"\n    if path[-1:] == \"/\":\n        path += \"*\"  # implicit all (FIXME: keep this?)\n\n    cache_key = (path,)\n    if namespaces:\n        # lxml originally used None for the default namespace but ElementTree uses the\n        # more convenient (all-strings-dict) empty string, so we support both here,\n        # preferring the more convenient '', as long as they aren't ambiguous.\n        if None in namespaces:\n            if '' in namespaces and namespaces[None] != namespaces['']:\n                raise ValueError(\"Ambiguous default namespace provided: %r versus %r\" % (\n                    namespaces[None], namespaces['']))\n            cache_key += (namespaces[None],) + tuple(sorted(\n                item for item in namespaces.items() if item[0] is not None))\n        else:\n            cache_key += tuple(sorted(namespaces.items()))\n\n    try:\n        return _cache[cache_key]\n    except KeyError:\n        pass\n    if len(_cache) > 100:\n        _cache.clear()\n\n    if path[:1] == \"/\":\n        raise SyntaxError(\"cannot use absolute path on element\")\n    stream = iter(xpath_tokenizer(path, namespaces))\n    try:\n        _next = stream.next\n    except AttributeError:\n        # Python 3\n        _next = stream.__next__\n    try:\n        token = _next()\n    except StopIteration:\n        raise SyntaxError(\"empty path expression\")\n    selector = []\n    while 1:\n        try:\n            selector.append(ops[token[0]](_next, token))\n        except StopIteration:\n            raise SyntaxError(\"invalid path\")\n        try:\n            token = _next()\n            if token[0] == \"/\":\n                token = _next()\n        except StopIteration:\n            break\n    _cache[cache_key] = selector\n    return selector\n\n\n##\n# Iterate over the matching nodes\n\ndef iterfind(elem, path, namespaces=None):\n    selector = _build_path_iterator(path, namespaces)\n    result = iter((elem,))\n    for select in selector:\n        result = select(result)\n    return result\n\n\n##\n# Find first matching object.\n\ndef find(elem, path, namespaces=None):\n    it = iterfind(elem, path, namespaces)\n    try:\n        return next(it)\n    except StopIteration:\n        return None\n\n\n##\n# Find all matching objects.\n\ndef findall(elem, path, namespaces=None):\n    return list(iterfind(elem, path, namespaces))\n\n\n##\n# Find text for first matching object.\n\ndef findtext(elem, path, default=None, namespaces=None):\n    el = find(elem, path, namespaces)\n    if el is None:\n        return default\n    else:\n        return el.text or ''\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/builder.py",
    "content": "# cython: language_level=2\n\n#\n# Element generator factory by Fredrik Lundh.\n#\n# Source:\n#    http://online.effbot.org/2006_11_01_archive.htm#et-builder\n#    http://effbot.python-hosting.com/file/stuff/sandbox/elementlib/builder.py\n#\n# --------------------------------------------------------------------\n# The ElementTree toolkit is\n#\n# Copyright (c) 1999-2004 by Fredrik Lundh\n#\n# By obtaining, using, and/or copying this software and/or its\n# associated documentation, you agree that you have read, understood,\n# and will comply with the following terms and conditions:\n#\n# Permission to use, copy, modify, and distribute this software and\n# its associated documentation for any purpose and without fee is\n# hereby granted, provided that the above copyright notice appears in\n# all copies, and that both that copyright notice and this permission\n# notice appear in supporting documentation, and that the name of\n# Secret Labs AB or the author not be used in advertising or publicity\n# pertaining to distribution of the software without specific, written\n# prior permission.\n#\n# SECRET LABS AB AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD\n# TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANT-\n# ABILITY AND FITNESS.  IN NO EVENT SHALL SECRET LABS AB OR THE AUTHOR\n# BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY\n# DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,\n# WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS\n# ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE\n# OF THIS SOFTWARE.\n# --------------------------------------------------------------------\n\n\"\"\"\nThe ``E`` Element factory for generating XML documents.\n\"\"\"\n\nfrom __future__ import absolute_import\n\nimport lxml.etree as ET\n\nfrom functools import partial\n\ntry:\n    basestring\nexcept NameError:\n    basestring = str\n\ntry:\n    unicode\nexcept NameError:\n    unicode = str\n\n\nclass ElementMaker(object):\n    \"\"\"Element generator factory.\n\n    Unlike the ordinary Element factory, the E factory allows you to pass in\n    more than just a tag and some optional attributes; you can also pass in\n    text and other elements.  The text is added as either text or tail\n    attributes, and elements are inserted at the right spot.  Some small\n    examples::\n\n        >>> from lxml import etree as ET\n        >>> from lxml.builder import E\n\n        >>> ET.tostring(E(\"tag\"))\n        '<tag/>'\n        >>> ET.tostring(E(\"tag\", \"text\"))\n        '<tag>text</tag>'\n        >>> ET.tostring(E(\"tag\", \"text\", key=\"value\"))\n        '<tag key=\"value\">text</tag>'\n        >>> ET.tostring(E(\"tag\", E(\"subtag\", \"text\"), \"tail\"))\n        '<tag><subtag>text</subtag>tail</tag>'\n\n    For simple tags, the factory also allows you to write ``E.tag(...)`` instead\n    of ``E('tag', ...)``::\n\n        >>> ET.tostring(E.tag())\n        '<tag/>'\n        >>> ET.tostring(E.tag(\"text\"))\n        '<tag>text</tag>'\n        >>> ET.tostring(E.tag(E.subtag(\"text\"), \"tail\"))\n        '<tag><subtag>text</subtag>tail</tag>'\n\n    Here's a somewhat larger example; this shows how to generate HTML\n    documents, using a mix of prepared factory functions for inline elements,\n    nested ``E.tag`` calls, and embedded XHTML fragments::\n\n        # some common inline elements\n        A = E.a\n        I = E.i\n        B = E.b\n\n        def CLASS(v):\n            # helper function, 'class' is a reserved word\n            return {'class': v}\n\n        page = (\n            E.html(\n                E.head(\n                    E.title(\"This is a sample document\")\n                ),\n                E.body(\n                    E.h1(\"Hello!\", CLASS(\"title\")),\n                    E.p(\"This is a paragraph with \", B(\"bold\"), \" text in it!\"),\n                    E.p(\"This is another paragraph, with a \",\n                        A(\"link\", href=\"http://www.python.org\"), \".\"),\n                    E.p(\"Here are some reserved characters: <spam&egg>.\"),\n                    ET.XML(\"<p>And finally, here is an embedded XHTML fragment.</p>\"),\n                )\n            )\n        )\n\n        print ET.tostring(page)\n\n    Here's a prettyprinted version of the output from the above script::\n\n        <html>\n          <head>\n            <title>This is a sample document</title>\n          </head>\n          <body>\n            <h1 class=\"title\">Hello!</h1>\n            <p>This is a paragraph with <b>bold</b> text in it!</p>\n            <p>This is another paragraph, with <a href=\"http://www.python.org\">link</a>.</p>\n            <p>Here are some reserved characters: &lt;spam&amp;egg&gt;.</p>\n            <p>And finally, here is an embedded XHTML fragment.</p>\n          </body>\n        </html>\n\n    For namespace support, you can pass a namespace map (``nsmap``)\n    and/or a specific target ``namespace`` to the ElementMaker class::\n\n        >>> E = ElementMaker(namespace=\"http://my.ns/\")\n        >>> print(ET.tostring( E.test ))\n        <test xmlns=\"http://my.ns/\"/>\n\n        >>> E = ElementMaker(namespace=\"http://my.ns/\", nsmap={'p':'http://my.ns/'})\n        >>> print(ET.tostring( E.test ))\n        <p:test xmlns:p=\"http://my.ns/\"/>\n    \"\"\"\n\n    def __init__(self, typemap=None,\n                 namespace=None, nsmap=None, makeelement=None):\n        if namespace is not None:\n            self._namespace = '{' + namespace + '}'\n        else:\n            self._namespace = None\n\n        if nsmap:\n            self._nsmap = dict(nsmap)\n        else:\n            self._nsmap = None\n\n        if makeelement is not None:\n            assert callable(makeelement)\n            self._makeelement = makeelement\n        else:\n            self._makeelement = ET.Element\n\n        # initialize type map for this element factory\n\n        if typemap:\n            typemap = dict(typemap)\n        else:\n            typemap = {}\n\n        def add_text(elem, item):\n            try:\n                elem[-1].tail = (elem[-1].tail or \"\") + item\n            except IndexError:\n                elem.text = (elem.text or \"\") + item\n\n        def add_cdata(elem, cdata):\n            if elem.text:\n                raise ValueError(\"Can't add a CDATA section. Element already has some text: %r\" % elem.text)\n            elem.text = cdata\n\n        if str not in typemap:\n            typemap[str] = add_text\n        if unicode not in typemap:\n            typemap[unicode] = add_text\n        if ET.CDATA not in typemap:\n            typemap[ET.CDATA] = add_cdata\n\n        def add_dict(elem, item):\n            attrib = elem.attrib\n            for k, v in item.items():\n                if isinstance(v, basestring):\n                    attrib[k] = v\n                else:\n                    attrib[k] = typemap[type(v)](None, v)\n        if dict not in typemap:\n            typemap[dict] = add_dict\n\n        self._typemap = typemap\n\n    def __call__(self, tag, *children, **attrib):\n        typemap = self._typemap\n\n        if self._namespace is not None and tag[0] != '{':\n            tag = self._namespace + tag\n        elem = self._makeelement(tag, nsmap=self._nsmap)\n        if attrib:\n            typemap[dict](elem, attrib)\n\n        for item in children:\n            if callable(item):\n                item = item()\n            t = typemap.get(type(item))\n            if t is None:\n                if ET.iselement(item):\n                    elem.append(item)\n                    continue\n                for basetype in type(item).__mro__:\n                    # See if the typemap knows of any of this type's bases.\n                    t = typemap.get(basetype)\n                    if t is not None:\n                        break\n                else:\n                    raise TypeError(\"bad argument type: %s(%r)\" %\n                                    (type(item).__name__, item))\n            v = t(elem, item)\n            if v:\n                typemap.get(type(v))(elem, v)\n\n        return elem\n\n    def __getattr__(self, tag):\n        return partial(self, tag)\n\n\n# create factory object\nE = ElementMaker()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/cssselect.py",
    "content": "\"\"\"CSS Selectors based on XPath.\n\nThis module supports selecting XML/HTML tags based on CSS selectors.\nSee the `CSSSelector` class for details.\n\nThis is a thin wrapper around cssselect 0.7 or later.\n\"\"\"\n\nfrom __future__ import absolute_import\n\nfrom . import etree\ntry:\n    import cssselect as external_cssselect\nexcept ImportError:\n    raise ImportError(\n        'cssselect does not seem to be installed. '\n        'See http://packages.python.org/cssselect/')\n\n\nSelectorSyntaxError = external_cssselect.SelectorSyntaxError\nExpressionError = external_cssselect.ExpressionError\nSelectorError = external_cssselect.SelectorError\n\n\n__all__ = ['SelectorSyntaxError', 'ExpressionError', 'SelectorError',\n           'CSSSelector']\n\n\nclass LxmlTranslator(external_cssselect.GenericTranslator):\n    \"\"\"\n    A custom CSS selector to XPath translator with lxml-specific extensions.\n    \"\"\"\n    def xpath_contains_function(self, xpath, function):\n        # Defined there, removed in later drafts:\n        # http://www.w3.org/TR/2001/CR-css3-selectors-20011113/#content-selectors\n        if function.argument_types() not in (['STRING'], ['IDENT']):\n            raise ExpressionError(\n                \"Expected a single string or ident for :contains(), got %r\"\n                % function.arguments)\n        value = function.arguments[0].value\n        return xpath.add_condition(\n            'contains(__lxml_internal_css:lower-case(string(.)), %s)'\n            % self.xpath_literal(value.lower()))\n\n\nclass LxmlHTMLTranslator(LxmlTranslator, external_cssselect.HTMLTranslator):\n    \"\"\"\n    lxml extensions + HTML support.\n    \"\"\"\n\n\ndef _make_lower_case(context, s):\n    return s.lower()\n\nns = etree.FunctionNamespace('http://codespeak.net/lxml/css/')\nns.prefix = '__lxml_internal_css'\nns['lower-case'] = _make_lower_case\n\n\nclass CSSSelector(etree.XPath):\n    \"\"\"A CSS selector.\n\n    Usage::\n\n        >>> from lxml import etree, cssselect\n        >>> select = cssselect.CSSSelector(\"a tag > child\")\n\n        >>> root = etree.XML(\"<a><b><c/><tag><child>TEXT</child></tag></b></a>\")\n        >>> [ el.tag for el in select(root) ]\n        ['child']\n\n    To use CSS namespaces, you need to pass a prefix-to-namespace\n    mapping as ``namespaces`` keyword argument::\n\n        >>> rdfns = 'http://www.w3.org/1999/02/22-rdf-syntax-ns#'\n        >>> select_ns = cssselect.CSSSelector('root > rdf|Description',\n        ...                                   namespaces={'rdf': rdfns})\n\n        >>> rdf = etree.XML((\n        ...     '<root xmlns:rdf=\"%s\">'\n        ...       '<rdf:Description>blah</rdf:Description>'\n        ...     '</root>') % rdfns)\n        >>> [(el.tag, el.text) for el in select_ns(rdf)]\n        [('{http://www.w3.org/1999/02/22-rdf-syntax-ns#}Description', 'blah')]\n\n    \"\"\"\n    def __init__(self, css, namespaces=None, translator='xml'):\n        if translator == 'xml':\n            translator = LxmlTranslator()\n        elif translator == 'html':\n            translator = LxmlHTMLTranslator()\n        elif translator == 'xhtml':\n            translator = LxmlHTMLTranslator(xhtml=True)\n        path = translator.css_to_xpath(css)\n        etree.XPath.__init__(self, path, namespaces=namespaces)\n        self.css = css\n\n    def __repr__(self):\n        return '<%s %s for %r>' % (\n            self.__class__.__name__,\n            hex(abs(id(self)))[2:],\n            self.css)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/doctestcompare.py",
    "content": "\"\"\"\nlxml-based doctest output comparison.\n\nNote: normally, you should just import the `lxml.usedoctest` and\n`lxml.html.usedoctest` modules from within a doctest, instead of this\none::\n\n    >>> import lxml.usedoctest # for XML output\n\n    >>> import lxml.html.usedoctest # for HTML output\n\nTo use this module directly, you must call ``lxmldoctest.install()``,\nwhich will cause doctest to use this in all subsequent calls.\n\nThis changes the way output is checked and comparisons are made for\nXML or HTML-like content.\n\nXML or HTML content is noticed because the example starts with ``<``\n(it's HTML if it starts with ``<html``).  You can also use the\n``PARSE_HTML`` and ``PARSE_XML`` flags to force parsing.\n\nSome rough wildcard-like things are allowed.  Whitespace is generally\nignored (except in attributes).  In text (attributes and text in the\nbody) you can use ``...`` as a wildcard.  In an example it also\nmatches any trailing tags in the element, though it does not match\nleading tags.  You may create a tag ``<any>`` or include an ``any``\nattribute in the tag.  An ``any`` tag matches any tag, while the\nattribute matches any and all attributes.\n\nWhen a match fails, the reformatted example and gotten text is\ndisplayed (indented), and a rough diff-like output is given.  Anything\nmarked with ``+`` is in the output but wasn't supposed to be, and\nsimilarly ``-`` means its in the example but wasn't in the output.\n\nYou can disable parsing on one line with ``# doctest:+NOPARSE_MARKUP``\n\"\"\"\n\nfrom lxml import etree\nimport sys\nimport re\nimport doctest\ntry:\n    from html import escape as html_escape\nexcept ImportError:\n    from cgi import escape as html_escape\n\n__all__ = ['PARSE_HTML', 'PARSE_XML', 'NOPARSE_MARKUP', 'LXMLOutputChecker',\n           'LHTMLOutputChecker', 'install', 'temp_install']\n\ntry:\n    _basestring = basestring\nexcept NameError:\n    _basestring = (str, bytes)\n\n_IS_PYTHON_3 = sys.version_info[0] >= 3\n\nPARSE_HTML = doctest.register_optionflag('PARSE_HTML')\nPARSE_XML = doctest.register_optionflag('PARSE_XML')\nNOPARSE_MARKUP = doctest.register_optionflag('NOPARSE_MARKUP')\n\nOutputChecker = doctest.OutputChecker\n\ndef strip(v):\n    if v is None:\n        return None\n    else:\n        return v.strip()\n\ndef norm_whitespace(v):\n    return _norm_whitespace_re.sub(' ', v)\n\n_html_parser = etree.HTMLParser(recover=False, remove_blank_text=True)\n\ndef html_fromstring(html):\n    return etree.fromstring(html, _html_parser)\n\n# We use this to distinguish repr()s from elements:\n_repr_re = re.compile(r'^<[^>]+ (at|object) ')\n_norm_whitespace_re = re.compile(r'[ \\t\\n][ \\t\\n]+')\n\nclass LXMLOutputChecker(OutputChecker):\n\n    empty_tags = (\n        'param', 'img', 'area', 'br', 'basefont', 'input',\n        'base', 'meta', 'link', 'col')\n\n    def get_default_parser(self):\n        return etree.XML\n\n    def check_output(self, want, got, optionflags):\n        alt_self = getattr(self, '_temp_override_self', None)\n        if alt_self is not None:\n            super_method = self._temp_call_super_check_output\n            self = alt_self\n        else:\n            super_method = OutputChecker.check_output\n        parser = self.get_parser(want, got, optionflags)\n        if not parser:\n            return super_method(\n                self, want, got, optionflags)\n        try:\n            want_doc = parser(want)\n        except etree.XMLSyntaxError:\n            return False\n        try:\n            got_doc = parser(got)\n        except etree.XMLSyntaxError:\n            return False\n        return self.compare_docs(want_doc, got_doc)\n\n    def get_parser(self, want, got, optionflags):\n        parser = None\n        if NOPARSE_MARKUP & optionflags:\n            return None\n        if PARSE_HTML & optionflags:\n            parser = html_fromstring\n        elif PARSE_XML & optionflags:\n            parser = etree.XML\n        elif (want.strip().lower().startswith('<html')\n              and got.strip().startswith('<html')):\n            parser = html_fromstring\n        elif (self._looks_like_markup(want)\n              and self._looks_like_markup(got)):\n            parser = self.get_default_parser()\n        return parser\n\n    def _looks_like_markup(self, s):\n        s = s.strip()\n        return (s.startswith('<')\n                and not _repr_re.search(s))\n\n    def compare_docs(self, want, got):\n        if not self.tag_compare(want.tag, got.tag):\n            return False\n        if not self.text_compare(want.text, got.text, True):\n            return False\n        if not self.text_compare(want.tail, got.tail, True):\n            return False\n        if 'any' not in want.attrib:\n            want_keys = sorted(want.attrib.keys())\n            got_keys = sorted(got.attrib.keys())\n            if want_keys != got_keys:\n                return False\n            for key in want_keys:\n                if not self.text_compare(want.attrib[key], got.attrib[key], False):\n                    return False\n        if want.text != '...' or len(want):\n            want_children = list(want)\n            got_children = list(got)\n            while want_children or got_children:\n                if not want_children or not got_children:\n                    return False\n                want_first = want_children.pop(0)\n                got_first = got_children.pop(0)\n                if not self.compare_docs(want_first, got_first):\n                    return False\n                if not got_children and want_first.tail == '...':\n                    break\n        return True\n\n    def text_compare(self, want, got, strip):\n        want = want or ''\n        got = got or ''\n        if strip:\n            want = norm_whitespace(want).strip()\n            got = norm_whitespace(got).strip()\n        want = '^%s$' % re.escape(want)\n        want = want.replace(r'\\.\\.\\.', '.*')\n        if re.search(want, got):\n            return True\n        else:\n            return False\n\n    def tag_compare(self, want, got):\n        if want == 'any':\n            return True\n        if (not isinstance(want, _basestring)\n            or not isinstance(got, _basestring)):\n            return want == got\n        want = want or ''\n        got = got or ''\n        if want.startswith('{...}'):\n            # Ellipsis on the namespace\n            return want.split('}')[-1] == got.split('}')[-1]\n        else:\n            return want == got\n\n    def output_difference(self, example, got, optionflags):\n        want = example.want\n        parser = self.get_parser(want, got, optionflags)\n        errors = []\n        if parser is not None:\n            try:\n                want_doc = parser(want)\n            except etree.XMLSyntaxError:\n                e = sys.exc_info()[1]\n                errors.append('In example: %s' % e)\n            try:\n                got_doc = parser(got)\n            except etree.XMLSyntaxError:\n                e = sys.exc_info()[1]\n                errors.append('In actual output: %s' % e)\n        if parser is None or errors:\n            value = OutputChecker.output_difference(\n                self, example, got, optionflags)\n            if errors:\n                errors.append(value)\n                return '\\n'.join(errors)\n            else:\n                return value\n        html = parser is html_fromstring\n        diff_parts = ['Expected:',\n                      self.format_doc(want_doc, html, 2),\n                      'Got:',\n                      self.format_doc(got_doc, html, 2),\n                      'Diff:',\n                      self.collect_diff(want_doc, got_doc, html, 2)]\n        return '\\n'.join(diff_parts)\n\n    def html_empty_tag(self, el, html=True):\n        if not html:\n            return False\n        if el.tag not in self.empty_tags:\n            return False\n        if el.text or len(el):\n            # This shouldn't happen (contents in an empty tag)\n            return False\n        return True\n\n    def format_doc(self, doc, html, indent, prefix=''):\n        parts = []\n        if not len(doc):\n            # No children...\n            parts.append(' '*indent)\n            parts.append(prefix)\n            parts.append(self.format_tag(doc))\n            if not self.html_empty_tag(doc, html):\n                if strip(doc.text):\n                    parts.append(self.format_text(doc.text))\n                parts.append(self.format_end_tag(doc))\n            if strip(doc.tail):\n                parts.append(self.format_text(doc.tail))\n            parts.append('\\n')\n            return ''.join(parts)\n        parts.append(' '*indent)\n        parts.append(prefix)\n        parts.append(self.format_tag(doc))\n        if not self.html_empty_tag(doc, html):\n            parts.append('\\n')\n            if strip(doc.text):\n                parts.append(' '*indent)\n                parts.append(self.format_text(doc.text))\n                parts.append('\\n')\n            for el in doc:\n                parts.append(self.format_doc(el, html, indent+2))\n            parts.append(' '*indent)\n            parts.append(self.format_end_tag(doc))\n            parts.append('\\n')\n        if strip(doc.tail):\n            parts.append(' '*indent)\n            parts.append(self.format_text(doc.tail))\n            parts.append('\\n')\n        return ''.join(parts)\n\n    def format_text(self, text, strip=True):\n        if text is None:\n            return ''\n        if strip:\n            text = text.strip()\n        return html_escape(text, 1)\n\n    def format_tag(self, el):\n        attrs = []\n        if isinstance(el, etree.CommentBase):\n            # FIXME: probably PIs should be handled specially too?\n            return '<!--'\n        for name, value in sorted(el.attrib.items()):\n            attrs.append('%s=\"%s\"' % (name, self.format_text(value, False)))\n        if not attrs:\n            return '<%s>' % el.tag\n        return '<%s %s>' % (el.tag, ' '.join(attrs))\n    \n    def format_end_tag(self, el):\n        if isinstance(el, etree.CommentBase):\n            # FIXME: probably PIs should be handled specially too?\n            return '-->'\n        return '</%s>' % el.tag\n\n    def collect_diff(self, want, got, html, indent):\n        parts = []\n        if not len(want) and not len(got):\n            parts.append(' '*indent)\n            parts.append(self.collect_diff_tag(want, got))\n            if not self.html_empty_tag(got, html):\n                parts.append(self.collect_diff_text(want.text, got.text))\n                parts.append(self.collect_diff_end_tag(want, got))\n            parts.append(self.collect_diff_text(want.tail, got.tail))\n            parts.append('\\n')\n            return ''.join(parts)\n        parts.append(' '*indent)\n        parts.append(self.collect_diff_tag(want, got))\n        parts.append('\\n')\n        if strip(want.text) or strip(got.text):\n            parts.append(' '*indent)\n            parts.append(self.collect_diff_text(want.text, got.text))\n            parts.append('\\n')\n        want_children = list(want)\n        got_children = list(got)\n        while want_children or got_children:\n            if not want_children:\n                parts.append(self.format_doc(got_children.pop(0), html, indent+2, '+'))\n                continue\n            if not got_children:\n                parts.append(self.format_doc(want_children.pop(0), html, indent+2, '-'))\n                continue\n            parts.append(self.collect_diff(\n                want_children.pop(0), got_children.pop(0), html, indent+2))\n        parts.append(' '*indent)\n        parts.append(self.collect_diff_end_tag(want, got))\n        parts.append('\\n')\n        if strip(want.tail) or strip(got.tail):\n            parts.append(' '*indent)\n            parts.append(self.collect_diff_text(want.tail, got.tail))\n            parts.append('\\n')\n        return ''.join(parts)\n\n    def collect_diff_tag(self, want, got):\n        if not self.tag_compare(want.tag, got.tag):\n            tag = '%s (got: %s)' % (want.tag, got.tag)\n        else:\n            tag = got.tag\n        attrs = []\n        any = want.tag == 'any' or 'any' in want.attrib\n        for name, value in sorted(got.attrib.items()):\n            if name not in want.attrib and not any:\n                attrs.append('+%s=\"%s\"' % (name, self.format_text(value, False)))\n            else:\n                if name in want.attrib:\n                    text = self.collect_diff_text(want.attrib[name], value, False)\n                else:\n                    text = self.format_text(value, False)\n                attrs.append('%s=\"%s\"' % (name, text))\n        if not any:\n            for name, value in sorted(want.attrib.items()):\n                if name in got.attrib:\n                    continue\n                attrs.append('-%s=\"%s\"' % (name, self.format_text(value, False)))\n        if attrs:\n            tag = '<%s %s>' % (tag, ' '.join(attrs))\n        else:\n            tag = '<%s>' % tag\n        return tag\n\n    def collect_diff_end_tag(self, want, got):\n        if want.tag != got.tag:\n            tag = '%s (got: %s)' % (want.tag, got.tag)\n        else:\n            tag = got.tag\n        return '</%s>' % tag\n\n    def collect_diff_text(self, want, got, strip=True):\n        if self.text_compare(want, got, strip):\n            if not got:\n                return ''\n            return self.format_text(got, strip)\n        text = '%s (got: %s)' % (want, got)\n        return self.format_text(text, strip)\n\nclass LHTMLOutputChecker(LXMLOutputChecker):\n    def get_default_parser(self):\n        return html_fromstring\n    \ndef install(html=False):\n    \"\"\"\n    Install doctestcompare for all future doctests.\n\n    If html is true, then by default the HTML parser will be used;\n    otherwise the XML parser is used.\n    \"\"\"\n    if html:\n        doctest.OutputChecker = LHTMLOutputChecker\n    else:\n        doctest.OutputChecker = LXMLOutputChecker\n\ndef temp_install(html=False, del_module=None):\n    \"\"\"\n    Use this *inside* a doctest to enable this checker for this\n    doctest only.\n\n    If html is true, then by default the HTML parser will be used;\n    otherwise the XML parser is used.\n    \"\"\"\n    if html:\n        Checker = LHTMLOutputChecker\n    else:\n        Checker = LXMLOutputChecker\n    frame = _find_doctest_frame()\n    dt_self = frame.f_locals['self']\n    checker = Checker()\n    old_checker = dt_self._checker\n    dt_self._checker = checker\n    # The unfortunate thing is that there is a local variable 'check'\n    # in the function that runs the doctests, that is a bound method\n    # into the output checker.  We have to update that.  We can't\n    # modify the frame, so we have to modify the object in place.  The\n    # only way to do this is to actually change the func_code\n    # attribute of the method.  We change it, and then wait for\n    # __record_outcome to be run, which signals the end of the __run\n    # method, at which point we restore the previous check_output\n    # implementation.\n    if _IS_PYTHON_3:\n        check_func = frame.f_locals['check'].__func__\n        checker_check_func = checker.check_output.__func__\n    else:\n        check_func = frame.f_locals['check'].im_func\n        checker_check_func = checker.check_output.im_func\n    # Because we can't patch up func_globals, this is the only global\n    # in check_output that we care about:\n    doctest.etree = etree\n    _RestoreChecker(dt_self, old_checker, checker,\n                    check_func, checker_check_func,\n                    del_module)\n\nclass _RestoreChecker(object):\n    def __init__(self, dt_self, old_checker, new_checker, check_func, clone_func,\n                 del_module):\n        self.dt_self = dt_self\n        self.checker = old_checker\n        self.checker._temp_call_super_check_output = self.call_super\n        self.checker._temp_override_self = new_checker\n        self.check_func = check_func\n        self.clone_func = clone_func\n        self.del_module = del_module\n        self.install_clone()\n        self.install_dt_self()\n    def install_clone(self):\n        if _IS_PYTHON_3:\n            self.func_code = self.check_func.__code__\n            self.func_globals = self.check_func.__globals__\n            self.check_func.__code__ = self.clone_func.__code__\n        else:\n            self.func_code = self.check_func.func_code\n            self.func_globals = self.check_func.func_globals\n            self.check_func.func_code = self.clone_func.func_code\n    def uninstall_clone(self):\n        if _IS_PYTHON_3:\n            self.check_func.__code__ = self.func_code\n        else:\n            self.check_func.func_code = self.func_code\n    def install_dt_self(self):\n        self.prev_func = self.dt_self._DocTestRunner__record_outcome\n        self.dt_self._DocTestRunner__record_outcome = self\n    def uninstall_dt_self(self):\n        self.dt_self._DocTestRunner__record_outcome = self.prev_func\n    def uninstall_module(self):\n        if self.del_module:\n            import sys\n            del sys.modules[self.del_module]\n            if '.' in self.del_module:\n                package, module = self.del_module.rsplit('.', 1)\n                package_mod = sys.modules[package]\n                delattr(package_mod, module)\n    def __call__(self, *args, **kw):\n        self.uninstall_clone()\n        self.uninstall_dt_self()\n        del self.checker._temp_override_self\n        del self.checker._temp_call_super_check_output\n        result = self.prev_func(*args, **kw)\n        self.uninstall_module()\n        return result\n    def call_super(self, *args, **kw):\n        self.uninstall_clone()\n        try:\n            return self.check_func(*args, **kw)\n        finally:\n            self.install_clone()\n            \ndef _find_doctest_frame():\n    import sys\n    frame = sys._getframe(1)\n    while frame:\n        l = frame.f_locals\n        if 'BOOM' in l:\n            # Sign of doctest\n            return frame\n        frame = frame.f_back\n    raise LookupError(\n        \"Could not find doctest (only use this function *inside* a doctest)\")\n    \n__test__ = {\n    'basic': '''\n    >>> temp_install()\n    >>> print \"\"\"<xml a=\"1\" b=\"2\">stuff</xml>\"\"\"\n    <xml b=\"2\" a=\"1\">...</xml>\n    >>> print \"\"\"<xml xmlns=\"http://example.com\"><tag   attr=\"bar\"   /></xml>\"\"\"\n    <xml xmlns=\"...\">\n      <tag attr=\"...\" />\n    </xml>\n    >>> print \"\"\"<xml>blahblahblah<foo /></xml>\"\"\" # doctest: +NOPARSE_MARKUP, +ELLIPSIS\n    <xml>...foo /></xml>\n    '''}\n\nif __name__ == '__main__':\n    import doctest\n    doctest.testmod()\n    \n    \n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/etree.h",
    "content": "/* Generated by Cython 0.29.13 */\n\n#ifndef __PYX_HAVE__lxml__etree\n#define __PYX_HAVE__lxml__etree\n\nstruct LxmlDocument;\nstruct LxmlElement;\nstruct LxmlElementTree;\nstruct LxmlElementTagMatcher;\nstruct LxmlElementIterator;\nstruct LxmlElementBase;\nstruct LxmlElementClassLookup;\nstruct LxmlFallbackElementClassLookup;\n\n/* \"lxml/etree.pyx\":322\n * \n * # type of a function that steps from node to node\n * ctypedef public xmlNode* (*_node_to_node_function)(xmlNode*)             # <<<<<<<<<<<<<<\n * \n * \n */\ntypedef xmlNode *(*_node_to_node_function)(xmlNode *);\n\n/* \"lxml/etree.pyx\":338\n * @cython.final\n * @cython.freelist(8)\n * cdef public class _Document [ type LxmlDocumentType, object LxmlDocument ]:             # <<<<<<<<<<<<<<\n *     u\"\"\"Internal base class to reference a libxml document.\n * \n */\nstruct LxmlDocument {\n  PyObject_HEAD\n  struct __pyx_vtabstruct_4lxml_5etree__Document *__pyx_vtab;\n  int _ns_counter;\n  PyObject *_prefix_tail;\n  xmlDoc *_c_doc;\n  struct __pyx_obj_4lxml_5etree__BaseParser *_parser;\n};\n\n/* \"lxml/etree.pyx\":687\n * \n * @cython.no_gc_clear\n * cdef public class _Element [ type LxmlElementType, object LxmlElement ]:             # <<<<<<<<<<<<<<\n *     u\"\"\"Element class.\n * \n */\nstruct LxmlElement {\n  PyObject_HEAD\n  struct LxmlDocument *_doc;\n  xmlNode *_c_node;\n  PyObject *_tag;\n};\n\n/* \"lxml/etree.pyx\":1853\n * \n * \n * cdef public class _ElementTree [ type LxmlElementTreeType,             # <<<<<<<<<<<<<<\n *                                  object LxmlElementTree ]:\n *     cdef _Document _doc\n */\nstruct LxmlElementTree {\n  PyObject_HEAD\n  struct __pyx_vtabstruct_4lxml_5etree__ElementTree *__pyx_vtab;\n  struct LxmlDocument *_doc;\n  struct LxmlElement *_context_node;\n};\n\n/* \"lxml/etree.pyx\":2597\n * \n * \n * cdef public class _ElementTagMatcher [ object LxmlElementTagMatcher,             # <<<<<<<<<<<<<<\n *                                        type LxmlElementTagMatcherType ]:\n *     \"\"\"\n */\nstruct LxmlElementTagMatcher {\n  PyObject_HEAD\n  struct __pyx_vtabstruct_4lxml_5etree__ElementTagMatcher *__pyx_vtab;\n  PyObject *_pystrings;\n  int _node_type;\n  char *_href;\n  char *_name;\n};\n\n/* \"lxml/etree.pyx\":2628\n *                 self._name = NULL\n * \n * cdef public class _ElementIterator(_ElementTagMatcher) [             # <<<<<<<<<<<<<<\n *     object LxmlElementIterator, type LxmlElementIteratorType ]:\n *     \"\"\"\n */\nstruct LxmlElementIterator {\n  struct LxmlElementTagMatcher __pyx_base;\n  struct LxmlElement *_node;\n  _node_to_node_function _next_element;\n};\n\n/* \"src/lxml/classlookup.pxi\":6\n * # Custom Element classes\n * \n * cdef public class ElementBase(_Element) [ type LxmlElementBaseType,             # <<<<<<<<<<<<<<\n *                                           object LxmlElementBase ]:\n *     u\"\"\"ElementBase(*children, attrib=None, nsmap=None, **_extra)\n */\nstruct LxmlElementBase {\n  struct LxmlElement __pyx_base;\n};\n\n/* \"src/lxml/classlookup.pxi\":210\n * # Element class lookup\n * \n * ctypedef public object (*_element_class_lookup_function)(object, _Document, xmlNode*)             # <<<<<<<<<<<<<<\n * \n * # class to store element class lookup functions\n */\ntypedef PyObject *(*_element_class_lookup_function)(PyObject *, struct LxmlDocument *, xmlNode *);\n\n/* \"src/lxml/classlookup.pxi\":213\n * \n * # class to store element class lookup functions\n * cdef public class ElementClassLookup [ type LxmlElementClassLookupType,             # <<<<<<<<<<<<<<\n *                                        object LxmlElementClassLookup ]:\n *     u\"\"\"ElementClassLookup(self)\n */\nstruct LxmlElementClassLookup {\n  PyObject_HEAD\n  _element_class_lookup_function _lookup_function;\n};\n\n/* \"src/lxml/classlookup.pxi\":221\n * \n * \n * cdef public class FallbackElementClassLookup(ElementClassLookup) \\             # <<<<<<<<<<<<<<\n *          [ type LxmlFallbackElementClassLookupType,\n *            object LxmlFallbackElementClassLookup ]:\n */\nstruct LxmlFallbackElementClassLookup {\n  struct LxmlElementClassLookup __pyx_base;\n  struct __pyx_vtabstruct_4lxml_5etree_FallbackElementClassLookup *__pyx_vtab;\n  struct LxmlElementClassLookup *fallback;\n  _element_class_lookup_function _fallback_function;\n};\n\n#ifndef __PYX_HAVE_API__lxml__etree\n\n#ifndef __PYX_EXTERN_C\n  #ifdef __cplusplus\n    #define __PYX_EXTERN_C extern \"C\"\n  #else\n    #define __PYX_EXTERN_C extern\n  #endif\n#endif\n\n#ifndef DL_IMPORT\n  #define DL_IMPORT(_T) _T\n#endif\n\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlDocumentType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlElementType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlElementTreeType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlElementTagMatcherType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlElementIteratorType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlElementBaseType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlElementClassLookupType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlFallbackElementClassLookupType;\n\n__PYX_EXTERN_C struct LxmlElement *deepcopyNodeToDocument(struct LxmlDocument *, xmlNode *);\n__PYX_EXTERN_C struct LxmlElementTree *elementTreeFactory(struct LxmlElement *);\n__PYX_EXTERN_C struct LxmlElementTree *newElementTree(struct LxmlElement *, PyObject *);\n__PYX_EXTERN_C struct LxmlElementTree *adoptExternalDocument(xmlDoc *, PyObject *, int);\n__PYX_EXTERN_C struct LxmlElement *elementFactory(struct LxmlDocument *, xmlNode *);\n__PYX_EXTERN_C struct LxmlElement *makeElement(PyObject *, struct LxmlDocument *, PyObject *, PyObject *, PyObject *, PyObject *, PyObject *);\n__PYX_EXTERN_C struct LxmlElement *makeSubElement(struct LxmlElement *, PyObject *, PyObject *, PyObject *, PyObject *, PyObject *);\n__PYX_EXTERN_C void setElementClassLookupFunction(_element_class_lookup_function, PyObject *);\n__PYX_EXTERN_C PyObject *lookupDefaultElementClass(PyObject *, PyObject *, xmlNode *);\n__PYX_EXTERN_C PyObject *lookupNamespaceElementClass(PyObject *, PyObject *, xmlNode *);\n__PYX_EXTERN_C PyObject *callLookupFallback(struct LxmlFallbackElementClassLookup *, struct LxmlDocument *, xmlNode *);\n__PYX_EXTERN_C int tagMatches(xmlNode *, const xmlChar *, const xmlChar *);\n__PYX_EXTERN_C struct LxmlDocument *documentOrRaise(PyObject *);\n__PYX_EXTERN_C struct LxmlElement *rootNodeOrRaise(PyObject *);\n__PYX_EXTERN_C int hasText(xmlNode *);\n__PYX_EXTERN_C int hasTail(xmlNode *);\n__PYX_EXTERN_C PyObject *textOf(xmlNode *);\n__PYX_EXTERN_C PyObject *tailOf(xmlNode *);\n__PYX_EXTERN_C int setNodeText(xmlNode *, PyObject *);\n__PYX_EXTERN_C int setTailText(xmlNode *, PyObject *);\n__PYX_EXTERN_C PyObject *attributeValue(xmlNode *, xmlAttr *);\n__PYX_EXTERN_C PyObject *attributeValueFromNsName(xmlNode *, const xmlChar *, const xmlChar *);\n__PYX_EXTERN_C PyObject *getAttributeValue(struct LxmlElement *, PyObject *, PyObject *);\n__PYX_EXTERN_C PyObject *iterattributes(struct LxmlElement *, int);\n__PYX_EXTERN_C PyObject *collectAttributes(xmlNode *, int);\n__PYX_EXTERN_C int setAttributeValue(struct LxmlElement *, PyObject *, PyObject *);\n__PYX_EXTERN_C int delAttribute(struct LxmlElement *, PyObject *);\n__PYX_EXTERN_C int delAttributeFromNsName(xmlNode *, const xmlChar *, const xmlChar *);\n__PYX_EXTERN_C int hasChild(xmlNode *);\n__PYX_EXTERN_C xmlNode *findChild(xmlNode *, Py_ssize_t);\n__PYX_EXTERN_C xmlNode *findChildForwards(xmlNode *, Py_ssize_t);\n__PYX_EXTERN_C xmlNode *findChildBackwards(xmlNode *, Py_ssize_t);\n__PYX_EXTERN_C xmlNode *nextElement(xmlNode *);\n__PYX_EXTERN_C xmlNode *previousElement(xmlNode *);\n__PYX_EXTERN_C void appendChild(struct LxmlElement *, struct LxmlElement *);\n__PYX_EXTERN_C int appendChildToElement(struct LxmlElement *, struct LxmlElement *);\n__PYX_EXTERN_C PyObject *pyunicode(const xmlChar *);\n__PYX_EXTERN_C PyObject *utf8(PyObject *);\n__PYX_EXTERN_C PyObject *getNsTag(PyObject *);\n__PYX_EXTERN_C PyObject *getNsTagWithEmptyNs(PyObject *);\n__PYX_EXTERN_C PyObject *namespacedName(xmlNode *);\n__PYX_EXTERN_C PyObject *namespacedNameFromNsName(const xmlChar *, const xmlChar *);\n__PYX_EXTERN_C void iteratorStoreNext(struct LxmlElementIterator *, struct LxmlElement *);\n__PYX_EXTERN_C void initTagMatch(struct LxmlElementTagMatcher *, PyObject *);\n__PYX_EXTERN_C xmlNs *findOrBuildNodeNsPrefix(struct LxmlDocument *, xmlNode *, const xmlChar *, const xmlChar *);\n\n#endif /* !__PYX_HAVE_API__lxml__etree */\n\n/* WARNING: the interface of the module init function changed in CPython 3.5. */\n/* It now returns a PyModuleDef instance instead of a PyModule instance. */\n\n#if PY_MAJOR_VERSION < 3\nPyMODINIT_FUNC initetree(void);\n#else\nPyMODINIT_FUNC PyInit_etree(void);\n#endif\n\n#endif /* !__PYX_HAVE__lxml__etree */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/etree_api.h",
    "content": "/* Generated by Cython 0.29.13 */\n\n#ifndef __PYX_HAVE_API__lxml__etree\n#define __PYX_HAVE_API__lxml__etree\n#ifdef __MINGW64__\n#define MS_WIN64\n#endif\n#include \"Python.h\"\n#include \"etree.h\"\n\nstatic struct LxmlElement *(*__pyx_api_f_4lxml_5etree_deepcopyNodeToDocument)(struct LxmlDocument *, xmlNode *) = 0;\n#define deepcopyNodeToDocument __pyx_api_f_4lxml_5etree_deepcopyNodeToDocument\nstatic struct LxmlElementTree *(*__pyx_api_f_4lxml_5etree_elementTreeFactory)(struct LxmlElement *) = 0;\n#define elementTreeFactory __pyx_api_f_4lxml_5etree_elementTreeFactory\nstatic struct LxmlElementTree *(*__pyx_api_f_4lxml_5etree_newElementTree)(struct LxmlElement *, PyObject *) = 0;\n#define newElementTree __pyx_api_f_4lxml_5etree_newElementTree\nstatic struct LxmlElementTree *(*__pyx_api_f_4lxml_5etree_adoptExternalDocument)(xmlDoc *, PyObject *, int) = 0;\n#define adoptExternalDocument __pyx_api_f_4lxml_5etree_adoptExternalDocument\nstatic struct LxmlElement *(*__pyx_api_f_4lxml_5etree_elementFactory)(struct LxmlDocument *, xmlNode *) = 0;\n#define elementFactory __pyx_api_f_4lxml_5etree_elementFactory\nstatic struct LxmlElement *(*__pyx_api_f_4lxml_5etree_makeElement)(PyObject *, struct LxmlDocument *, PyObject *, PyObject *, PyObject *, PyObject *, PyObject *) = 0;\n#define makeElement __pyx_api_f_4lxml_5etree_makeElement\nstatic struct LxmlElement *(*__pyx_api_f_4lxml_5etree_makeSubElement)(struct LxmlElement *, PyObject *, PyObject *, PyObject *, PyObject *, PyObject *) = 0;\n#define makeSubElement __pyx_api_f_4lxml_5etree_makeSubElement\nstatic void (*__pyx_api_f_4lxml_5etree_setElementClassLookupFunction)(_element_class_lookup_function, PyObject *) = 0;\n#define setElementClassLookupFunction __pyx_api_f_4lxml_5etree_setElementClassLookupFunction\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_lookupDefaultElementClass)(PyObject *, PyObject *, xmlNode *) = 0;\n#define lookupDefaultElementClass __pyx_api_f_4lxml_5etree_lookupDefaultElementClass\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_lookupNamespaceElementClass)(PyObject *, PyObject *, xmlNode *) = 0;\n#define lookupNamespaceElementClass __pyx_api_f_4lxml_5etree_lookupNamespaceElementClass\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_callLookupFallback)(struct LxmlFallbackElementClassLookup *, struct LxmlDocument *, xmlNode *) = 0;\n#define callLookupFallback __pyx_api_f_4lxml_5etree_callLookupFallback\nstatic int (*__pyx_api_f_4lxml_5etree_tagMatches)(xmlNode *, const xmlChar *, const xmlChar *) = 0;\n#define tagMatches __pyx_api_f_4lxml_5etree_tagMatches\nstatic struct LxmlDocument *(*__pyx_api_f_4lxml_5etree_documentOrRaise)(PyObject *) = 0;\n#define documentOrRaise __pyx_api_f_4lxml_5etree_documentOrRaise\nstatic struct LxmlElement *(*__pyx_api_f_4lxml_5etree_rootNodeOrRaise)(PyObject *) = 0;\n#define rootNodeOrRaise __pyx_api_f_4lxml_5etree_rootNodeOrRaise\nstatic int (*__pyx_api_f_4lxml_5etree_hasText)(xmlNode *) = 0;\n#define hasText __pyx_api_f_4lxml_5etree_hasText\nstatic int (*__pyx_api_f_4lxml_5etree_hasTail)(xmlNode *) = 0;\n#define hasTail __pyx_api_f_4lxml_5etree_hasTail\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_textOf)(xmlNode *) = 0;\n#define textOf __pyx_api_f_4lxml_5etree_textOf\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_tailOf)(xmlNode *) = 0;\n#define tailOf __pyx_api_f_4lxml_5etree_tailOf\nstatic int (*__pyx_api_f_4lxml_5etree_setNodeText)(xmlNode *, PyObject *) = 0;\n#define setNodeText __pyx_api_f_4lxml_5etree_setNodeText\nstatic int (*__pyx_api_f_4lxml_5etree_setTailText)(xmlNode *, PyObject *) = 0;\n#define setTailText __pyx_api_f_4lxml_5etree_setTailText\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_attributeValue)(xmlNode *, xmlAttr *) = 0;\n#define attributeValue __pyx_api_f_4lxml_5etree_attributeValue\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_attributeValueFromNsName)(xmlNode *, const xmlChar *, const xmlChar *) = 0;\n#define attributeValueFromNsName __pyx_api_f_4lxml_5etree_attributeValueFromNsName\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_getAttributeValue)(struct LxmlElement *, PyObject *, PyObject *) = 0;\n#define getAttributeValue __pyx_api_f_4lxml_5etree_getAttributeValue\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_iterattributes)(struct LxmlElement *, int) = 0;\n#define iterattributes __pyx_api_f_4lxml_5etree_iterattributes\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_collectAttributes)(xmlNode *, int) = 0;\n#define collectAttributes __pyx_api_f_4lxml_5etree_collectAttributes\nstatic int (*__pyx_api_f_4lxml_5etree_setAttributeValue)(struct LxmlElement *, PyObject *, PyObject *) = 0;\n#define setAttributeValue __pyx_api_f_4lxml_5etree_setAttributeValue\nstatic int (*__pyx_api_f_4lxml_5etree_delAttribute)(struct LxmlElement *, PyObject *) = 0;\n#define delAttribute __pyx_api_f_4lxml_5etree_delAttribute\nstatic int (*__pyx_api_f_4lxml_5etree_delAttributeFromNsName)(xmlNode *, const xmlChar *, const xmlChar *) = 0;\n#define delAttributeFromNsName __pyx_api_f_4lxml_5etree_delAttributeFromNsName\nstatic int (*__pyx_api_f_4lxml_5etree_hasChild)(xmlNode *) = 0;\n#define hasChild __pyx_api_f_4lxml_5etree_hasChild\nstatic xmlNode *(*__pyx_api_f_4lxml_5etree_findChild)(xmlNode *, Py_ssize_t) = 0;\n#define findChild __pyx_api_f_4lxml_5etree_findChild\nstatic xmlNode *(*__pyx_api_f_4lxml_5etree_findChildForwards)(xmlNode *, Py_ssize_t) = 0;\n#define findChildForwards __pyx_api_f_4lxml_5etree_findChildForwards\nstatic xmlNode *(*__pyx_api_f_4lxml_5etree_findChildBackwards)(xmlNode *, Py_ssize_t) = 0;\n#define findChildBackwards __pyx_api_f_4lxml_5etree_findChildBackwards\nstatic xmlNode *(*__pyx_api_f_4lxml_5etree_nextElement)(xmlNode *) = 0;\n#define nextElement __pyx_api_f_4lxml_5etree_nextElement\nstatic xmlNode *(*__pyx_api_f_4lxml_5etree_previousElement)(xmlNode *) = 0;\n#define previousElement __pyx_api_f_4lxml_5etree_previousElement\nstatic void (*__pyx_api_f_4lxml_5etree_appendChild)(struct LxmlElement *, struct LxmlElement *) = 0;\n#define appendChild __pyx_api_f_4lxml_5etree_appendChild\nstatic int (*__pyx_api_f_4lxml_5etree_appendChildToElement)(struct LxmlElement *, struct LxmlElement *) = 0;\n#define appendChildToElement __pyx_api_f_4lxml_5etree_appendChildToElement\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_pyunicode)(const xmlChar *) = 0;\n#define pyunicode __pyx_api_f_4lxml_5etree_pyunicode\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_utf8)(PyObject *) = 0;\n#define utf8 __pyx_api_f_4lxml_5etree_utf8\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_getNsTag)(PyObject *) = 0;\n#define getNsTag __pyx_api_f_4lxml_5etree_getNsTag\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_getNsTagWithEmptyNs)(PyObject *) = 0;\n#define getNsTagWithEmptyNs __pyx_api_f_4lxml_5etree_getNsTagWithEmptyNs\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_namespacedName)(xmlNode *) = 0;\n#define namespacedName __pyx_api_f_4lxml_5etree_namespacedName\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_namespacedNameFromNsName)(const xmlChar *, const xmlChar *) = 0;\n#define namespacedNameFromNsName __pyx_api_f_4lxml_5etree_namespacedNameFromNsName\nstatic void (*__pyx_api_f_4lxml_5etree_iteratorStoreNext)(struct LxmlElementIterator *, struct LxmlElement *) = 0;\n#define iteratorStoreNext __pyx_api_f_4lxml_5etree_iteratorStoreNext\nstatic void (*__pyx_api_f_4lxml_5etree_initTagMatch)(struct LxmlElementTagMatcher *, PyObject *) = 0;\n#define initTagMatch __pyx_api_f_4lxml_5etree_initTagMatch\nstatic xmlNs *(*__pyx_api_f_4lxml_5etree_findOrBuildNodeNsPrefix)(struct LxmlDocument *, xmlNode *, const xmlChar *, const xmlChar *) = 0;\n#define findOrBuildNodeNsPrefix __pyx_api_f_4lxml_5etree_findOrBuildNodeNsPrefix\n#if !defined(__Pyx_PyIdentifier_FromString)\n#if PY_MAJOR_VERSION < 3\n  #define __Pyx_PyIdentifier_FromString(s) PyString_FromString(s)\n#else\n  #define __Pyx_PyIdentifier_FromString(s) PyUnicode_FromString(s)\n#endif\n#endif\n\n#ifndef __PYX_HAVE_RT_ImportFunction\n#define __PYX_HAVE_RT_ImportFunction\nstatic int __Pyx_ImportFunction(PyObject *module, const char *funcname, void (**f)(void), const char *sig) {\n    PyObject *d = 0;\n    PyObject *cobj = 0;\n    union {\n        void (*fp)(void);\n        void *p;\n    } tmp;\n    d = PyObject_GetAttrString(module, (char *)\"__pyx_capi__\");\n    if (!d)\n        goto bad;\n    cobj = PyDict_GetItemString(d, funcname);\n    if (!cobj) {\n        PyErr_Format(PyExc_ImportError,\n            \"%.200s does not export expected C function %.200s\",\n                PyModule_GetName(module), funcname);\n        goto bad;\n    }\n#if PY_VERSION_HEX >= 0x02070000\n    if (!PyCapsule_IsValid(cobj, sig)) {\n        PyErr_Format(PyExc_TypeError,\n            \"C function %.200s.%.200s has wrong signature (expected %.500s, got %.500s)\",\n             PyModule_GetName(module), funcname, sig, PyCapsule_GetName(cobj));\n        goto bad;\n    }\n    tmp.p = PyCapsule_GetPointer(cobj, sig);\n#else\n    {const char *desc, *s1, *s2;\n    desc = (const char *)PyCObject_GetDesc(cobj);\n    if (!desc)\n        goto bad;\n    s1 = desc; s2 = sig;\n    while (*s1 != '\\0' && *s1 == *s2) { s1++; s2++; }\n    if (*s1 != *s2) {\n        PyErr_Format(PyExc_TypeError,\n            \"C function %.200s.%.200s has wrong signature (expected %.500s, got %.500s)\",\n             PyModule_GetName(module), funcname, sig, desc);\n        goto bad;\n    }\n    tmp.p = PyCObject_AsVoidPtr(cobj);}\n#endif\n    *f = tmp.fp;\n    if (!(*f))\n        goto bad;\n    Py_DECREF(d);\n    return 0;\nbad:\n    Py_XDECREF(d);\n    return -1;\n}\n#endif\n\n\nstatic int import_lxml__etree(void) {\n  PyObject *module = 0;\n  module = PyImport_ImportModule(\"lxml.etree\");\n  if (!module) goto bad;\n  if (__Pyx_ImportFunction(module, \"deepcopyNodeToDocument\", (void (**)(void))&__pyx_api_f_4lxml_5etree_deepcopyNodeToDocument, \"struct LxmlElement *(struct LxmlDocument *, xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"elementTreeFactory\", (void (**)(void))&__pyx_api_f_4lxml_5etree_elementTreeFactory, \"struct LxmlElementTree *(struct LxmlElement *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"newElementTree\", (void (**)(void))&__pyx_api_f_4lxml_5etree_newElementTree, \"struct LxmlElementTree *(struct LxmlElement *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"adoptExternalDocument\", (void (**)(void))&__pyx_api_f_4lxml_5etree_adoptExternalDocument, \"struct LxmlElementTree *(xmlDoc *, PyObject *, int)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"elementFactory\", (void (**)(void))&__pyx_api_f_4lxml_5etree_elementFactory, \"struct LxmlElement *(struct LxmlDocument *, xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"makeElement\", (void (**)(void))&__pyx_api_f_4lxml_5etree_makeElement, \"struct LxmlElement *(PyObject *, struct LxmlDocument *, PyObject *, PyObject *, PyObject *, PyObject *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"makeSubElement\", (void (**)(void))&__pyx_api_f_4lxml_5etree_makeSubElement, \"struct LxmlElement *(struct LxmlElement *, PyObject *, PyObject *, PyObject *, PyObject *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"setElementClassLookupFunction\", (void (**)(void))&__pyx_api_f_4lxml_5etree_setElementClassLookupFunction, \"void (_element_class_lookup_function, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"lookupDefaultElementClass\", (void (**)(void))&__pyx_api_f_4lxml_5etree_lookupDefaultElementClass, \"PyObject *(PyObject *, PyObject *, xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"lookupNamespaceElementClass\", (void (**)(void))&__pyx_api_f_4lxml_5etree_lookupNamespaceElementClass, \"PyObject *(PyObject *, PyObject *, xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"callLookupFallback\", (void (**)(void))&__pyx_api_f_4lxml_5etree_callLookupFallback, \"PyObject *(struct LxmlFallbackElementClassLookup *, struct LxmlDocument *, xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"tagMatches\", (void (**)(void))&__pyx_api_f_4lxml_5etree_tagMatches, \"int (xmlNode *, const xmlChar *, const xmlChar *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"documentOrRaise\", (void (**)(void))&__pyx_api_f_4lxml_5etree_documentOrRaise, \"struct LxmlDocument *(PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"rootNodeOrRaise\", (void (**)(void))&__pyx_api_f_4lxml_5etree_rootNodeOrRaise, \"struct LxmlElement *(PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"hasText\", (void (**)(void))&__pyx_api_f_4lxml_5etree_hasText, \"int (xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"hasTail\", (void (**)(void))&__pyx_api_f_4lxml_5etree_hasTail, \"int (xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"textOf\", (void (**)(void))&__pyx_api_f_4lxml_5etree_textOf, \"PyObject *(xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"tailOf\", (void (**)(void))&__pyx_api_f_4lxml_5etree_tailOf, \"PyObject *(xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"setNodeText\", (void (**)(void))&__pyx_api_f_4lxml_5etree_setNodeText, \"int (xmlNode *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"setTailText\", (void (**)(void))&__pyx_api_f_4lxml_5etree_setTailText, \"int (xmlNode *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"attributeValue\", (void (**)(void))&__pyx_api_f_4lxml_5etree_attributeValue, \"PyObject *(xmlNode *, xmlAttr *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"attributeValueFromNsName\", (void (**)(void))&__pyx_api_f_4lxml_5etree_attributeValueFromNsName, \"PyObject *(xmlNode *, const xmlChar *, const xmlChar *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"getAttributeValue\", (void (**)(void))&__pyx_api_f_4lxml_5etree_getAttributeValue, \"PyObject *(struct LxmlElement *, PyObject *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"iterattributes\", (void (**)(void))&__pyx_api_f_4lxml_5etree_iterattributes, \"PyObject *(struct LxmlElement *, int)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"collectAttributes\", (void (**)(void))&__pyx_api_f_4lxml_5etree_collectAttributes, \"PyObject *(xmlNode *, int)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"setAttributeValue\", (void (**)(void))&__pyx_api_f_4lxml_5etree_setAttributeValue, \"int (struct LxmlElement *, PyObject *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"delAttribute\", (void (**)(void))&__pyx_api_f_4lxml_5etree_delAttribute, \"int (struct LxmlElement *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"delAttributeFromNsName\", (void (**)(void))&__pyx_api_f_4lxml_5etree_delAttributeFromNsName, \"int (xmlNode *, const xmlChar *, const xmlChar *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"hasChild\", (void (**)(void))&__pyx_api_f_4lxml_5etree_hasChild, \"int (xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"findChild\", (void (**)(void))&__pyx_api_f_4lxml_5etree_findChild, \"xmlNode *(xmlNode *, Py_ssize_t)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"findChildForwards\", (void (**)(void))&__pyx_api_f_4lxml_5etree_findChildForwards, \"xmlNode *(xmlNode *, Py_ssize_t)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"findChildBackwards\", (void (**)(void))&__pyx_api_f_4lxml_5etree_findChildBackwards, \"xmlNode *(xmlNode *, Py_ssize_t)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"nextElement\", (void (**)(void))&__pyx_api_f_4lxml_5etree_nextElement, \"xmlNode *(xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"previousElement\", (void (**)(void))&__pyx_api_f_4lxml_5etree_previousElement, \"xmlNode *(xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"appendChild\", (void (**)(void))&__pyx_api_f_4lxml_5etree_appendChild, \"void (struct LxmlElement *, struct LxmlElement *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"appendChildToElement\", (void (**)(void))&__pyx_api_f_4lxml_5etree_appendChildToElement, \"int (struct LxmlElement *, struct LxmlElement *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"pyunicode\", (void (**)(void))&__pyx_api_f_4lxml_5etree_pyunicode, \"PyObject *(const xmlChar *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"utf8\", (void (**)(void))&__pyx_api_f_4lxml_5etree_utf8, \"PyObject *(PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"getNsTag\", (void (**)(void))&__pyx_api_f_4lxml_5etree_getNsTag, \"PyObject *(PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"getNsTagWithEmptyNs\", (void (**)(void))&__pyx_api_f_4lxml_5etree_getNsTagWithEmptyNs, \"PyObject *(PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"namespacedName\", (void (**)(void))&__pyx_api_f_4lxml_5etree_namespacedName, \"PyObject *(xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"namespacedNameFromNsName\", (void (**)(void))&__pyx_api_f_4lxml_5etree_namespacedNameFromNsName, \"PyObject *(const xmlChar *, const xmlChar *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"iteratorStoreNext\", (void (**)(void))&__pyx_api_f_4lxml_5etree_iteratorStoreNext, \"void (struct LxmlElementIterator *, struct LxmlElement *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"initTagMatch\", (void (**)(void))&__pyx_api_f_4lxml_5etree_initTagMatch, \"void (struct LxmlElementTagMatcher *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"findOrBuildNodeNsPrefix\", (void (**)(void))&__pyx_api_f_4lxml_5etree_findOrBuildNodeNsPrefix, \"xmlNs *(struct LxmlDocument *, xmlNode *, const xmlChar *, const xmlChar *)\") < 0) goto bad;\n  Py_DECREF(module); module = 0;\n  return 0;\n  bad:\n  Py_XDECREF(module);\n  return -1;\n}\n\n#endif /* !__PYX_HAVE_API__lxml__etree */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/ElementSoup.py",
    "content": "__doc__ = \"\"\"Legacy interface to the BeautifulSoup HTML parser.\n\"\"\"\n\n__all__ = [\"parse\", \"convert_tree\"]\n\nfrom soupparser import convert_tree, parse as _parse\n\ndef parse(file, beautifulsoup=None, makeelement=None):\n    root = _parse(file, beautifulsoup=beautifulsoup, makeelement=makeelement)\n    return root.getroot()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/__init__.py",
    "content": "# Copyright (c) 2004 Ian Bicking. All rights reserved.\n#\n# Redistribution and use in source and binary forms, with or without\n# modification, are permitted provided that the following conditions are\n# met:\n#\n# 1. Redistributions of source code must retain the above copyright\n# notice, this list of conditions and the following disclaimer.\n#\n# 2. Redistributions in binary form must reproduce the above copyright\n# notice, this list of conditions and the following disclaimer in\n# the documentation and/or other materials provided with the\n# distribution.\n#\n# 3. Neither the name of Ian Bicking nor the names of its contributors may\n# be used to endorse or promote products derived from this software\n# without specific prior written permission.\n#\n# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n# \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR\n# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL IAN BICKING OR\n# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,\n# EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,\n# PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR\n# PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF\n# LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING\n# NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\n# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n\"\"\"The ``lxml.html`` tool set for HTML handling.\n\"\"\"\n\nfrom __future__ import absolute_import\n\n__all__ = [\n    'document_fromstring', 'fragment_fromstring', 'fragments_fromstring', 'fromstring',\n    'tostring', 'Element', 'defs', 'open_in_browser', 'submit_form',\n    'find_rel_links', 'find_class', 'make_links_absolute',\n    'resolve_base_href', 'iterlinks', 'rewrite_links', 'open_in_browser', 'parse']\n\n\nimport copy\nimport sys\nimport re\nfrom functools import partial\n\ntry:\n    from collections.abc import MutableMapping, MutableSet\nexcept ImportError:\n    from collections import MutableMapping, MutableSet\n\nfrom .. import etree\nfrom . import defs\nfrom ._setmixin import SetMixin\n\ntry:\n    from urlparse import urljoin\nexcept ImportError:\n    # Python 3\n    from urllib.parse import urljoin\n\ntry:\n    unicode\nexcept NameError:\n    # Python 3\n    unicode = str\ntry:\n    basestring\nexcept NameError:\n    # Python 3\n    basestring = (str, bytes)\n\n\ndef __fix_docstring(s):\n    if not s:\n        return s\n    if sys.version_info[0] >= 3:\n        sub = re.compile(r\"^(\\s*)u'\", re.M).sub\n    else:\n        sub = re.compile(r\"^(\\s*)b'\", re.M).sub\n    return sub(r\"\\1'\", s)\n\n\nXHTML_NAMESPACE = \"http://www.w3.org/1999/xhtml\"\n\n_rel_links_xpath = etree.XPath(\"descendant-or-self::a[@rel]|descendant-or-self::x:a[@rel]\",\n                               namespaces={'x':XHTML_NAMESPACE})\n_options_xpath = etree.XPath(\"descendant-or-self::option|descendant-or-self::x:option\",\n                             namespaces={'x':XHTML_NAMESPACE})\n_forms_xpath = etree.XPath(\"descendant-or-self::form|descendant-or-self::x:form\",\n                           namespaces={'x':XHTML_NAMESPACE})\n#_class_xpath = etree.XPath(r\"descendant-or-self::*[regexp:match(@class, concat('\\b', $class_name, '\\b'))]\", {'regexp': 'http://exslt.org/regular-expressions'})\n_class_xpath = etree.XPath(\"descendant-or-self::*[@class and contains(concat(' ', normalize-space(@class), ' '), concat(' ', $class_name, ' '))]\")\n_id_xpath = etree.XPath(\"descendant-or-self::*[@id=$id]\")\n_collect_string_content = etree.XPath(\"string()\")\n_iter_css_urls = re.compile(r'url\\(('+'[\"][^\"]*[\"]|'+\"['][^']*[']|\"+r'[^)]*)\\)', re.I).finditer\n_iter_css_imports = re.compile(r'@import \"(.*?)\"').finditer\n_label_xpath = etree.XPath(\"//label[@for=$id]|//x:label[@for=$id]\",\n                           namespaces={'x':XHTML_NAMESPACE})\n_archive_re = re.compile(r'[^ ]+')\n_parse_meta_refresh_url = re.compile(\n    r'[^;=]*;\\s*(?:url\\s*=\\s*)?(?P<url>.*)$', re.I).search\n\n\ndef _unquote_match(s, pos):\n    if s[:1] == '\"' and s[-1:] == '\"' or s[:1] == \"'\" and s[-1:] == \"'\":\n        return s[1:-1], pos+1\n    else:\n        return s,pos\n\n\ndef _transform_result(typ, result):\n    \"\"\"Convert the result back into the input type.\n    \"\"\"\n    if issubclass(typ, bytes):\n        return tostring(result, encoding='utf-8')\n    elif issubclass(typ, unicode):\n        return tostring(result, encoding='unicode')\n    else:\n        return result\n\n\ndef _nons(tag):\n    if isinstance(tag, basestring):\n        if tag[0] == '{' and tag[1:len(XHTML_NAMESPACE)+1] == XHTML_NAMESPACE:\n            return tag.split('}')[-1]\n    return tag\n\n\nclass Classes(MutableSet):\n    \"\"\"Provides access to an element's class attribute as a set-like collection.\n    Usage::\n\n        >>> el = fromstring('<p class=\"hidden large\">Text</p>')\n        >>> classes = el.classes  # or: classes = Classes(el.attrib)\n        >>> classes |= ['block', 'paragraph']\n        >>> el.get('class')\n        'hidden large block paragraph'\n        >>> classes.toggle('hidden')\n        False\n        >>> el.get('class')\n        'large block paragraph'\n        >>> classes -= ('some', 'classes', 'block')\n        >>> el.get('class')\n        'large paragraph'\n    \"\"\"\n    def __init__(self, attributes):\n        self._attributes = attributes\n        self._get_class_value = partial(attributes.get, 'class', '')\n\n    def add(self, value):\n        \"\"\"\n        Add a class.\n\n        This has no effect if the class is already present.\n        \"\"\"\n        if not value or re.search(r'\\s', value):\n            raise ValueError(\"Invalid class name: %r\" % value)\n        classes = self._get_class_value().split()\n        if value in classes:\n            return\n        classes.append(value)\n        self._attributes['class'] = ' '.join(classes)\n\n    def discard(self, value):\n        \"\"\"\n        Remove a class if it is currently present.\n\n        If the class is not present, do nothing.\n        \"\"\"\n        if not value or re.search(r'\\s', value):\n            raise ValueError(\"Invalid class name: %r\" % value)\n        classes = [name for name in self._get_class_value().split()\n                   if name != value]\n        if classes:\n            self._attributes['class'] = ' '.join(classes)\n        elif 'class' in self._attributes:\n            del self._attributes['class']\n\n    def remove(self, value):\n        \"\"\"\n        Remove a class; it must currently be present.\n\n        If the class is not present, raise a KeyError.\n        \"\"\"\n        if not value or re.search(r'\\s', value):\n            raise ValueError(\"Invalid class name: %r\" % value)\n        super(Classes, self).remove(value)\n\n    def __contains__(self, name):\n        classes = self._get_class_value()\n        return name in classes and name in classes.split()\n\n    def __iter__(self):\n        return iter(self._get_class_value().split())\n\n    def __len__(self):\n        return len(self._get_class_value().split())\n\n    # non-standard methods\n\n    def update(self, values):\n        \"\"\"\n        Add all names from 'values'.\n        \"\"\"\n        classes = self._get_class_value().split()\n        extended = False\n        for value in values:\n            if value not in classes:\n                classes.append(value)\n                extended = True\n        if extended:\n            self._attributes['class'] = ' '.join(classes)\n\n    def toggle(self, value):\n        \"\"\"\n        Add a class name if it isn't there yet, or remove it if it exists.\n\n        Returns true if the class was added (and is now enabled) and\n        false if it was removed (and is now disabled).\n        \"\"\"\n        if not value or re.search(r'\\s', value):\n            raise ValueError(\"Invalid class name: %r\" % value)\n        classes = self._get_class_value().split()\n        try:\n            classes.remove(value)\n            enabled = False\n        except ValueError:\n            classes.append(value)\n            enabled = True\n        if classes:\n            self._attributes['class'] = ' '.join(classes)\n        else:\n            del self._attributes['class']\n        return enabled\n\n\nclass HtmlMixin(object):\n\n    def set(self, key, value=None):\n        \"\"\"set(self, key, value=None)\n\n        Sets an element attribute.  If no value is provided, or if the value is None,\n        creates a 'boolean' attribute without value, e.g. \"<form novalidate></form>\"\n        for ``form.set('novalidate')``.\n        \"\"\"\n        super(HtmlElement, self).set(key, value)\n\n    @property\n    def classes(self):\n        \"\"\"\n        A set-like wrapper around the 'class' attribute.\n        \"\"\"\n        return Classes(self.attrib)\n\n    @classes.setter\n    def classes(self, classes):\n        assert isinstance(classes, Classes)  # only allow \"el.classes |= ...\" etc.\n        value = classes._get_class_value()\n        if value:\n            self.set('class', value)\n        elif self.get('class') is not None:\n            del self.attrib['class']\n\n    @property\n    def base_url(self):\n        \"\"\"\n        Returns the base URL, given when the page was parsed.\n\n        Use with ``urlparse.urljoin(el.base_url, href)`` to get\n        absolute URLs.\n        \"\"\"\n        return self.getroottree().docinfo.URL\n\n    @property\n    def forms(self):\n        \"\"\"\n        Return a list of all the forms\n        \"\"\"\n        return _forms_xpath(self)\n\n    @property\n    def body(self):\n        \"\"\"\n        Return the <body> element.  Can be called from a child element\n        to get the document's head.\n        \"\"\"\n        return self.xpath('//body|//x:body', namespaces={'x':XHTML_NAMESPACE})[0]\n\n    @property\n    def head(self):\n        \"\"\"\n        Returns the <head> element.  Can be called from a child\n        element to get the document's head.\n        \"\"\"\n        return self.xpath('//head|//x:head', namespaces={'x':XHTML_NAMESPACE})[0]\n\n    @property\n    def label(self):\n        \"\"\"\n        Get or set any <label> element associated with this element.\n        \"\"\"\n        id = self.get('id')\n        if not id:\n            return None\n        result = _label_xpath(self, id=id)\n        if not result:\n            return None\n        else:\n            return result[0]\n\n    @label.setter\n    def label(self, label):\n        id = self.get('id')\n        if not id:\n            raise TypeError(\n                \"You cannot set a label for an element (%r) that has no id\"\n                % self)\n        if _nons(label.tag) != 'label':\n            raise TypeError(\n                \"You can only assign label to a label element (not %r)\"\n                % label)\n        label.set('for', id)\n\n    @label.deleter\n    def label(self):\n        label = self.label\n        if label is not None:\n            del label.attrib['for']\n\n    def drop_tree(self):\n        \"\"\"\n        Removes this element from the tree, including its children and\n        text.  The tail text is joined to the previous element or\n        parent.\n        \"\"\"\n        parent = self.getparent()\n        assert parent is not None\n        if self.tail:\n            previous = self.getprevious()\n            if previous is None:\n                parent.text = (parent.text or '') + self.tail\n            else:\n                previous.tail = (previous.tail or '') + self.tail\n        parent.remove(self)\n\n    def drop_tag(self):\n        \"\"\"\n        Remove the tag, but not its children or text.  The children and text\n        are merged into the parent.\n\n        Example::\n\n            >>> h = fragment_fromstring('<div>Hello <b>World!</b></div>')\n            >>> h.find('.//b').drop_tag()\n            >>> print(tostring(h, encoding='unicode'))\n            <div>Hello World!</div>\n        \"\"\"\n        parent = self.getparent()\n        assert parent is not None\n        previous = self.getprevious()\n        if self.text and isinstance(self.tag, basestring):\n            # not a Comment, etc.\n            if previous is None:\n                parent.text = (parent.text or '') + self.text\n            else:\n                previous.tail = (previous.tail or '') + self.text\n        if self.tail:\n            if len(self):\n                last = self[-1]\n                last.tail = (last.tail or '') + self.tail\n            elif previous is None:\n                parent.text = (parent.text or '') + self.tail\n            else:\n                previous.tail = (previous.tail or '') + self.tail\n        index = parent.index(self)\n        parent[index:index+1] = self[:]\n\n    def find_rel_links(self, rel):\n        \"\"\"\n        Find any links like ``<a rel=\"{rel}\">...</a>``; returns a list of elements.\n        \"\"\"\n        rel = rel.lower()\n        return [el for el in _rel_links_xpath(self)\n                if el.get('rel').lower() == rel]\n\n    def find_class(self, class_name):\n        \"\"\"\n        Find any elements with the given class name.\n        \"\"\"\n        return _class_xpath(self, class_name=class_name)\n\n    def get_element_by_id(self, id, *default):\n        \"\"\"\n        Get the first element in a document with the given id.  If none is\n        found, return the default argument if provided or raise KeyError\n        otherwise.\n\n        Note that there can be more than one element with the same id,\n        and this isn't uncommon in HTML documents found in the wild.\n        Browsers return only the first match, and this function does\n        the same.\n        \"\"\"\n        try:\n            # FIXME: should this check for multiple matches?\n            # browsers just return the first one\n            return _id_xpath(self, id=id)[0]\n        except IndexError:\n            if default:\n                return default[0]\n            else:\n                raise KeyError(id)\n\n    def text_content(self):\n        \"\"\"\n        Return the text content of the tag (and the text in any children).\n        \"\"\"\n        return _collect_string_content(self)\n\n    def cssselect(self, expr, translator='html'):\n        \"\"\"\n        Run the CSS expression on this element and its children,\n        returning a list of the results.\n\n        Equivalent to lxml.cssselect.CSSSelect(expr, translator='html')(self)\n        -- note that pre-compiling the expression can provide a substantial\n        speedup.\n        \"\"\"\n        # Do the import here to make the dependency optional.\n        from lxml.cssselect import CSSSelector\n        return CSSSelector(expr, translator=translator)(self)\n\n    ########################################\n    ## Link functions\n    ########################################\n\n    def make_links_absolute(self, base_url=None, resolve_base_href=True,\n                            handle_failures=None):\n        \"\"\"\n        Make all links in the document absolute, given the\n        ``base_url`` for the document (the full URL where the document\n        came from), or if no ``base_url`` is given, then the ``.base_url``\n        of the document.\n\n        If ``resolve_base_href`` is true, then any ``<base href>``\n        tags in the document are used *and* removed from the document.\n        If it is false then any such tag is ignored.\n\n        If ``handle_failures`` is None (default), a failure to process\n        a URL will abort the processing.  If set to 'ignore', errors\n        are ignored.  If set to 'discard', failing URLs will be removed.\n        \"\"\"\n        if base_url is None:\n            base_url = self.base_url\n            if base_url is None:\n                raise TypeError(\n                    \"No base_url given, and the document has no base_url\")\n        if resolve_base_href:\n            self.resolve_base_href()\n\n        if handle_failures == 'ignore':\n            def link_repl(href):\n                try:\n                    return urljoin(base_url, href)\n                except ValueError:\n                    return href\n        elif handle_failures == 'discard':\n            def link_repl(href):\n                try:\n                    return urljoin(base_url, href)\n                except ValueError:\n                    return None\n        elif handle_failures is None:\n            def link_repl(href):\n                return urljoin(base_url, href)\n        else:\n            raise ValueError(\n                \"unexpected value for handle_failures: %r\" % handle_failures)\n\n        self.rewrite_links(link_repl)\n\n    def resolve_base_href(self, handle_failures=None):\n        \"\"\"\n        Find any ``<base href>`` tag in the document, and apply its\n        values to all links found in the document.  Also remove the\n        tag once it has been applied.\n\n        If ``handle_failures`` is None (default), a failure to process\n        a URL will abort the processing.  If set to 'ignore', errors\n        are ignored.  If set to 'discard', failing URLs will be removed.\n        \"\"\"\n        base_href = None\n        basetags = self.xpath('//base[@href]|//x:base[@href]',\n                              namespaces={'x': XHTML_NAMESPACE})\n        for b in basetags:\n            base_href = b.get('href')\n            b.drop_tree()\n        if not base_href:\n            return\n        self.make_links_absolute(base_href, resolve_base_href=False,\n                                 handle_failures=handle_failures)\n\n    def iterlinks(self):\n        \"\"\"\n        Yield (element, attribute, link, pos), where attribute may be None\n        (indicating the link is in the text).  ``pos`` is the position\n        where the link occurs; often 0, but sometimes something else in\n        the case of links in stylesheets or style tags.\n\n        Note: <base href> is *not* taken into account in any way.  The\n        link you get is exactly the link in the document.\n\n        Note: multiple links inside of a single text string or\n        attribute value are returned in reversed order.  This makes it\n        possible to replace or delete them from the text string value\n        based on their reported text positions.  Otherwise, a\n        modification at one text position can change the positions of\n        links reported later on.\n        \"\"\"\n        link_attrs = defs.link_attrs\n        for el in self.iter(etree.Element):\n            attribs = el.attrib\n            tag = _nons(el.tag)\n            if tag == 'object':\n                codebase = None\n                ## <object> tags have attributes that are relative to\n                ## codebase\n                if 'codebase' in attribs:\n                    codebase = el.get('codebase')\n                    yield (el, 'codebase', codebase, 0)\n                for attrib in ('classid', 'data'):\n                    if attrib in attribs:\n                        value = el.get(attrib)\n                        if codebase is not None:\n                            value = urljoin(codebase, value)\n                        yield (el, attrib, value, 0)\n                if 'archive' in attribs:\n                    for match in _archive_re.finditer(el.get('archive')):\n                        value = match.group(0)\n                        if codebase is not None:\n                            value = urljoin(codebase, value)\n                        yield (el, 'archive', value, match.start())\n            else:\n                for attrib in link_attrs:\n                    if attrib in attribs:\n                        yield (el, attrib, attribs[attrib], 0)\n            if tag == 'meta':\n                http_equiv = attribs.get('http-equiv', '').lower()\n                if http_equiv == 'refresh':\n                    content = attribs.get('content', '')\n                    match = _parse_meta_refresh_url(content)\n                    url = (match.group('url') if match else content).strip()\n                    # unexpected content means the redirect won't work, but we might\n                    # as well be permissive and return the entire string.\n                    if url:\n                        url, pos = _unquote_match(\n                            url, match.start('url') if match else content.find(url))\n                        yield (el, 'content', url, pos)\n            elif tag == 'param':\n                valuetype = el.get('valuetype') or ''\n                if valuetype.lower() == 'ref':\n                    ## FIXME: while it's fine we *find* this link,\n                    ## according to the spec we aren't supposed to\n                    ## actually change the value, including resolving\n                    ## it.  It can also still be a link, even if it\n                    ## doesn't have a valuetype=\"ref\" (which seems to be the norm)\n                    ## http://www.w3.org/TR/html401/struct/objects.html#adef-valuetype\n                    yield (el, 'value', el.get('value'), 0)\n            elif tag == 'style' and el.text:\n                urls = [\n                    # (start_pos, url)\n                    _unquote_match(match.group(1), match.start(1))[::-1]\n                    for match in _iter_css_urls(el.text)\n                    ] + [\n                    (match.start(1), match.group(1))\n                    for match in _iter_css_imports(el.text)\n                    ]\n                if urls:\n                    # sort by start pos to bring both match sets back into order\n                    # and reverse the list to report correct positions despite\n                    # modifications\n                    urls.sort(reverse=True)\n                    for start, url in urls:\n                        yield (el, None, url, start)\n            if 'style' in attribs:\n                urls = list(_iter_css_urls(attribs['style']))\n                if urls:\n                    # return in reversed order to simplify in-place modifications\n                    for match in urls[::-1]:\n                        url, start = _unquote_match(match.group(1), match.start(1))\n                        yield (el, 'style', url, start)\n\n    def rewrite_links(self, link_repl_func, resolve_base_href=True,\n                      base_href=None):\n        \"\"\"\n        Rewrite all the links in the document.  For each link\n        ``link_repl_func(link)`` will be called, and the return value\n        will replace the old link.\n\n        Note that links may not be absolute (unless you first called\n        ``make_links_absolute()``), and may be internal (e.g.,\n        ``'#anchor'``).  They can also be values like\n        ``'mailto:email'`` or ``'javascript:expr'``.\n\n        If you give ``base_href`` then all links passed to\n        ``link_repl_func()`` will take that into account.\n\n        If the ``link_repl_func`` returns None, the attribute or\n        tag text will be removed completely.\n        \"\"\"\n        if base_href is not None:\n            # FIXME: this can be done in one pass with a wrapper\n            # around link_repl_func\n            self.make_links_absolute(\n                base_href, resolve_base_href=resolve_base_href)\n        elif resolve_base_href:\n            self.resolve_base_href()\n\n        for el, attrib, link, pos in self.iterlinks():\n            new_link = link_repl_func(link.strip())\n            if new_link == link:\n                continue\n            if new_link is None:\n                # Remove the attribute or element content\n                if attrib is None:\n                    el.text = ''\n                else:\n                    del el.attrib[attrib]\n                continue\n\n            if attrib is None:\n                new = el.text[:pos] + new_link + el.text[pos+len(link):]\n                el.text = new\n            else:\n                cur = el.get(attrib)\n                if not pos and len(cur) == len(link):\n                    new = new_link  # most common case\n                else:\n                    new = cur[:pos] + new_link + cur[pos+len(link):]\n                el.set(attrib, new)\n\n\nclass _MethodFunc(object):\n    \"\"\"\n    An object that represents a method on an element as a function;\n    the function takes either an element or an HTML string.  It\n    returns whatever the function normally returns, or if the function\n    works in-place (and so returns None) it returns a serialized form\n    of the resulting document.\n    \"\"\"\n    def __init__(self, name, copy=False, source_class=HtmlMixin):\n        self.name = name\n        self.copy = copy\n        self.__doc__ = getattr(source_class, self.name).__doc__\n    def __call__(self, doc, *args, **kw):\n        result_type = type(doc)\n        if isinstance(doc, basestring):\n            if 'copy' in kw:\n                raise TypeError(\n                    \"The keyword 'copy' can only be used with element inputs to %s, not a string input\" % self.name)\n            doc = fromstring(doc, **kw)\n        else:\n            if 'copy' in kw:\n                make_a_copy = kw.pop('copy')\n            else:\n                make_a_copy = self.copy\n            if make_a_copy:\n                doc = copy.deepcopy(doc)\n        meth = getattr(doc, self.name)\n        result = meth(*args, **kw)\n        # FIXME: this None test is a bit sloppy\n        if result is None:\n            # Then return what we got in\n            return _transform_result(result_type, doc)\n        else:\n            return result\n\n\nfind_rel_links = _MethodFunc('find_rel_links', copy=False)\nfind_class = _MethodFunc('find_class', copy=False)\nmake_links_absolute = _MethodFunc('make_links_absolute', copy=True)\nresolve_base_href = _MethodFunc('resolve_base_href', copy=True)\niterlinks = _MethodFunc('iterlinks', copy=False)\nrewrite_links = _MethodFunc('rewrite_links', copy=True)\n\n\nclass HtmlComment(etree.CommentBase, HtmlMixin):\n    pass\n\n\nclass HtmlElement(etree.ElementBase, HtmlMixin):\n    # Override etree.ElementBase.cssselect() and set(), despite the MRO (FIXME: change base order?)\n    cssselect = HtmlMixin.cssselect\n    set = HtmlMixin.set\n\n\nclass HtmlProcessingInstruction(etree.PIBase, HtmlMixin):\n    pass\n\n\nclass HtmlEntity(etree.EntityBase, HtmlMixin):\n    pass\n\n\nclass HtmlElementClassLookup(etree.CustomElementClassLookup):\n    \"\"\"A lookup scheme for HTML Element classes.\n\n    To create a lookup instance with different Element classes, pass a tag\n    name mapping of Element classes in the ``classes`` keyword argument and/or\n    a tag name mapping of Mixin classes in the ``mixins`` keyword argument.\n    The special key '*' denotes a Mixin class that should be mixed into all\n    Element classes.\n    \"\"\"\n    _default_element_classes = {}\n\n    def __init__(self, classes=None, mixins=None):\n        etree.CustomElementClassLookup.__init__(self)\n        if classes is None:\n            classes = self._default_element_classes.copy()\n        if mixins:\n            mixers = {}\n            for name, value in mixins:\n                if name == '*':\n                    for n in classes.keys():\n                        mixers.setdefault(n, []).append(value)\n                else:\n                    mixers.setdefault(name, []).append(value)\n            for name, mix_bases in mixers.items():\n                cur = classes.get(name, HtmlElement)\n                bases = tuple(mix_bases + [cur])\n                classes[name] = type(cur.__name__, bases, {})\n        self._element_classes = classes\n\n    def lookup(self, node_type, document, namespace, name):\n        if node_type == 'element':\n            return self._element_classes.get(name.lower(), HtmlElement)\n        elif node_type == 'comment':\n            return HtmlComment\n        elif node_type == 'PI':\n            return HtmlProcessingInstruction\n        elif node_type == 'entity':\n            return HtmlEntity\n        # Otherwise normal lookup\n        return None\n\n\n################################################################################\n# parsing\n################################################################################\n\n_looks_like_full_html_unicode = re.compile(\n    unicode(r'^\\s*<(?:html|!doctype)'), re.I).match\n_looks_like_full_html_bytes = re.compile(\n    r'^\\s*<(?:html|!doctype)'.encode('ascii'), re.I).match\n\n\ndef document_fromstring(html, parser=None, ensure_head_body=False, **kw):\n    if parser is None:\n        parser = html_parser\n    value = etree.fromstring(html, parser, **kw)\n    if value is None:\n        raise etree.ParserError(\n            \"Document is empty\")\n    if ensure_head_body and value.find('head') is None:\n        value.insert(0, Element('head'))\n    if ensure_head_body and value.find('body') is None:\n        value.append(Element('body'))\n    return value\n\n\ndef fragments_fromstring(html, no_leading_text=False, base_url=None,\n                         parser=None, **kw):\n    \"\"\"Parses several HTML elements, returning a list of elements.\n\n    The first item in the list may be a string.\n    If no_leading_text is true, then it will be an error if there is\n    leading text, and it will always be a list of only elements.\n\n    base_url will set the document's base_url attribute\n    (and the tree's docinfo.URL).\n    \"\"\"\n    if parser is None:\n        parser = html_parser\n    # FIXME: check what happens when you give html with a body, head, etc.\n    if isinstance(html, bytes):\n        if not _looks_like_full_html_bytes(html):\n            # can't use %-formatting in early Py3 versions\n            html = ('<html><body>'.encode('ascii') + html +\n                    '</body></html>'.encode('ascii'))\n    else:\n        if not _looks_like_full_html_unicode(html):\n            html = '<html><body>%s</body></html>' % html\n    doc = document_fromstring(html, parser=parser, base_url=base_url, **kw)\n    assert _nons(doc.tag) == 'html'\n    bodies = [e for e in doc if _nons(e.tag) == 'body']\n    assert len(bodies) == 1, (\"too many bodies: %r in %r\" % (bodies, html))\n    body = bodies[0]\n    elements = []\n    if no_leading_text and body.text and body.text.strip():\n        raise etree.ParserError(\n            \"There is leading text: %r\" % body.text)\n    if body.text and body.text.strip():\n        elements.append(body.text)\n    elements.extend(body)\n    # FIXME: removing the reference to the parent artificial document\n    # would be nice\n    return elements\n\n\ndef fragment_fromstring(html, create_parent=False, base_url=None,\n                        parser=None, **kw):\n    \"\"\"\n    Parses a single HTML element; it is an error if there is more than\n    one element, or if anything but whitespace precedes or follows the\n    element.\n\n    If ``create_parent`` is true (or is a tag name) then a parent node\n    will be created to encapsulate the HTML in a single element.  In this\n    case, leading or trailing text is also allowed, as are multiple elements\n    as result of the parsing.\n\n    Passing a ``base_url`` will set the document's ``base_url`` attribute\n    (and the tree's docinfo.URL).\n    \"\"\"\n    if parser is None:\n        parser = html_parser\n\n    accept_leading_text = bool(create_parent)\n\n    elements = fragments_fromstring(\n        html, parser=parser, no_leading_text=not accept_leading_text,\n        base_url=base_url, **kw)\n\n    if create_parent:\n        if not isinstance(create_parent, basestring):\n            create_parent = 'div'\n        new_root = Element(create_parent)\n        if elements:\n            if isinstance(elements[0], basestring):\n                new_root.text = elements[0]\n                del elements[0]\n            new_root.extend(elements)\n        return new_root\n\n    if not elements:\n        raise etree.ParserError('No elements found')\n    if len(elements) > 1:\n        raise etree.ParserError(\n            \"Multiple elements found (%s)\"\n            % ', '.join([_element_name(e) for e in elements]))\n    el = elements[0]\n    if el.tail and el.tail.strip():\n        raise etree.ParserError(\n            \"Element followed by text: %r\" % el.tail)\n    el.tail = None\n    return el\n\n\ndef fromstring(html, base_url=None, parser=None, **kw):\n    \"\"\"\n    Parse the html, returning a single element/document.\n\n    This tries to minimally parse the chunk of text, without knowing if it\n    is a fragment or a document.\n\n    base_url will set the document's base_url attribute (and the tree's docinfo.URL)\n    \"\"\"\n    if parser is None:\n        parser = html_parser\n    if isinstance(html, bytes):\n        is_full_html = _looks_like_full_html_bytes(html)\n    else:\n        is_full_html = _looks_like_full_html_unicode(html)\n    doc = document_fromstring(html, parser=parser, base_url=base_url, **kw)\n    if is_full_html:\n        return doc\n    # otherwise, lets parse it out...\n    bodies = doc.findall('body')\n    if not bodies:\n        bodies = doc.findall('{%s}body' % XHTML_NAMESPACE)\n    if bodies:\n        body = bodies[0]\n        if len(bodies) > 1:\n            # Somehow there are multiple bodies, which is bad, but just\n            # smash them into one body\n            for other_body in bodies[1:]:\n                if other_body.text:\n                    if len(body):\n                        body[-1].tail = (body[-1].tail or '') + other_body.text\n                    else:\n                        body.text = (body.text or '') + other_body.text\n                body.extend(other_body)\n                # We'll ignore tail\n                # I guess we are ignoring attributes too\n                other_body.drop_tree()\n    else:\n        body = None\n    heads = doc.findall('head')\n    if not heads:\n        heads = doc.findall('{%s}head' % XHTML_NAMESPACE)\n    if heads:\n        # Well, we have some sort of structure, so lets keep it all\n        head = heads[0]\n        if len(heads) > 1:\n            for other_head in heads[1:]:\n                head.extend(other_head)\n                # We don't care about text or tail in a head\n                other_head.drop_tree()\n        return doc\n    if body is None:\n        return doc\n    if (len(body) == 1 and (not body.text or not body.text.strip())\n        and (not body[-1].tail or not body[-1].tail.strip())):\n        # The body has just one element, so it was probably a single\n        # element passed in\n        return body[0]\n    # Now we have a body which represents a bunch of tags which have the\n    # content that was passed in.  We will create a fake container, which\n    # is the body tag, except <body> implies too much structure.\n    if _contains_block_level_tag(body):\n        body.tag = 'div'\n    else:\n        body.tag = 'span'\n    return body\n\n\ndef parse(filename_or_url, parser=None, base_url=None, **kw):\n    \"\"\"\n    Parse a filename, URL, or file-like object into an HTML document\n    tree.  Note: this returns a tree, not an element.  Use\n    ``parse(...).getroot()`` to get the document root.\n\n    You can override the base URL with the ``base_url`` keyword.  This\n    is most useful when parsing from a file-like object.\n    \"\"\"\n    if parser is None:\n        parser = html_parser\n    return etree.parse(filename_or_url, parser, base_url=base_url, **kw)\n\n\ndef _contains_block_level_tag(el):\n    # FIXME: I could do this with XPath, but would that just be\n    # unnecessarily slow?\n    for el in el.iter(etree.Element):\n        if _nons(el.tag) in defs.block_tags:\n            return True\n    return False\n\n\ndef _element_name(el):\n    if isinstance(el, etree.CommentBase):\n        return 'comment'\n    elif isinstance(el, basestring):\n        return 'string'\n    else:\n        return _nons(el.tag)\n\n\n################################################################################\n# form handling\n################################################################################\n\nclass FormElement(HtmlElement):\n    \"\"\"\n    Represents a <form> element.\n    \"\"\"\n\n    @property\n    def inputs(self):\n        \"\"\"\n        Returns an accessor for all the input elements in the form.\n\n        See `InputGetter` for more information about the object.\n        \"\"\"\n        return InputGetter(self)\n\n    @property\n    def fields(self):\n        \"\"\"\n        Dictionary-like object that represents all the fields in this\n        form.  You can set values in this dictionary to effect the\n        form.\n        \"\"\"\n        return FieldsDict(self.inputs)\n\n    @fields.setter\n    def fields(self, value):\n        fields = self.fields\n        prev_keys = fields.keys()\n        for key, value in value.items():\n            if key in prev_keys:\n                prev_keys.remove(key)\n            fields[key] = value\n        for key in prev_keys:\n            if key is None:\n                # Case of an unnamed input; these aren't really\n                # expressed in form_values() anyway.\n                continue\n            fields[key] = None\n\n    def _name(self):\n        if self.get('name'):\n            return self.get('name')\n        elif self.get('id'):\n            return '#' + self.get('id')\n        iter_tags = self.body.iter\n        forms = list(iter_tags('form'))\n        if not forms:\n            forms = list(iter_tags('{%s}form' % XHTML_NAMESPACE))\n        return str(forms.index(self))\n\n    def form_values(self):\n        \"\"\"\n        Return a list of tuples of the field values for the form.\n        This is suitable to be passed to ``urllib.urlencode()``.\n        \"\"\"\n        results = []\n        for el in self.inputs:\n            name = el.name\n            if not name or 'disabled' in el.attrib:\n                continue\n            tag = _nons(el.tag)\n            if tag == 'textarea':\n                results.append((name, el.value))\n            elif tag == 'select':\n                value = el.value\n                if el.multiple:\n                    for v in value:\n                        results.append((name, v))\n                elif value is not None:\n                    results.append((name, el.value))\n            else:\n                assert tag == 'input', (\n                    \"Unexpected tag: %r\" % el)\n                if el.checkable and not el.checked:\n                    continue\n                if el.type in ('submit', 'image', 'reset', 'file'):\n                    continue\n                value = el.value\n                if value is not None:\n                    results.append((name, el.value))\n        return results\n\n    @property\n    def action(self):\n        \"\"\"\n        Get/set the form's ``action`` attribute.\n        \"\"\"\n        base_url = self.base_url\n        action = self.get('action')\n        if base_url and action is not None:\n            return urljoin(base_url, action)\n        else:\n            return action\n\n    @action.setter\n    def action(self, value):\n        self.set('action', value)\n\n    @action.deleter\n    def action(self):\n        attrib = self.attrib\n        if 'action' in attrib:\n            del attrib['action']\n\n    @property\n    def method(self):\n        \"\"\"\n        Get/set the form's method.  Always returns a capitalized\n        string, and defaults to ``'GET'``\n        \"\"\"\n        return self.get('method', 'GET').upper()\n\n    @method.setter\n    def method(self, value):\n        self.set('method', value.upper())\n\n\nHtmlElementClassLookup._default_element_classes['form'] = FormElement\n\n\ndef submit_form(form, extra_values=None, open_http=None):\n    \"\"\"\n    Helper function to submit a form.  Returns a file-like object, as from\n    ``urllib.urlopen()``.  This object also has a ``.geturl()`` function,\n    which shows the URL if there were any redirects.\n\n    You can use this like::\n\n        form = doc.forms[0]\n        form.inputs['foo'].value = 'bar' # etc\n        response = form.submit()\n        doc = parse(response)\n        doc.make_links_absolute(response.geturl())\n\n    To change the HTTP requester, pass a function as ``open_http`` keyword\n    argument that opens the URL for you.  The function must have the following\n    signature::\n\n        open_http(method, URL, values)\n\n    The action is one of 'GET' or 'POST', the URL is the target URL as a\n    string, and the values are a sequence of ``(name, value)`` tuples with the\n    form data.\n    \"\"\"\n    values = form.form_values()\n    if extra_values:\n        if hasattr(extra_values, 'items'):\n            extra_values = extra_values.items()\n        values.extend(extra_values)\n    if open_http is None:\n        open_http = open_http_urllib\n    if form.action:\n        url = form.action\n    else:\n        url = form.base_url\n    return open_http(form.method, url, values)\n\n\ndef open_http_urllib(method, url, values):\n    if not url:\n        raise ValueError(\"cannot submit, no URL provided\")\n    ## FIXME: should test that it's not a relative URL or something\n    try:\n        from urllib import urlencode, urlopen\n    except ImportError: # Python 3\n        from urllib.request import urlopen\n        from urllib.parse import urlencode\n    if method == 'GET':\n        if '?' in url:\n            url += '&'\n        else:\n            url += '?'\n        url += urlencode(values)\n        data = None\n    else:\n        data = urlencode(values)\n        if not isinstance(data, bytes):\n            data = data.encode('ASCII')\n    return urlopen(url, data)\n\n\nclass FieldsDict(MutableMapping):\n\n    def __init__(self, inputs):\n        self.inputs = inputs\n    def __getitem__(self, item):\n        return self.inputs[item].value\n    def __setitem__(self, item, value):\n        self.inputs[item].value = value\n    def __delitem__(self, item):\n        raise KeyError(\n            \"You cannot remove keys from ElementDict\")\n    def keys(self):\n        return self.inputs.keys()\n    def __contains__(self, item):\n        return item in self.inputs\n    def __iter__(self):\n        return iter(self.inputs.keys())\n    def __len__(self):\n        return len(self.inputs)\n\n    def __repr__(self):\n        return '<%s for form %s>' % (\n            self.__class__.__name__,\n            self.inputs.form._name())\n\n\nclass InputGetter(object):\n\n    \"\"\"\n    An accessor that represents all the input fields in a form.\n\n    You can get fields by name from this, with\n    ``form.inputs['field_name']``.  If there are a set of checkboxes\n    with the same name, they are returned as a list (a `CheckboxGroup`\n    which also allows value setting).  Radio inputs are handled\n    similarly.\n\n    You can also iterate over this to get all input elements.  This\n    won't return the same thing as if you get all the names, as\n    checkboxes and radio elements are returned individually.\n    \"\"\"\n\n    _name_xpath = etree.XPath(\".//*[@name = $name and (local-name(.) = 'select' or local-name(.) = 'input' or local-name(.) = 'textarea')]\")\n    _all_xpath = etree.XPath(\".//*[local-name() = 'select' or local-name() = 'input' or local-name() = 'textarea']\")\n\n    def __init__(self, form):\n        self.form = form\n\n    def __repr__(self):\n        return '<%s for form %s>' % (\n            self.__class__.__name__,\n            self.form._name())\n\n    ## FIXME: there should be more methods, and it's unclear if this is\n    ## a dictionary-like object or list-like object\n\n    def __getitem__(self, name):\n        results = self._name_xpath(self.form, name=name)\n        if results:\n            type = results[0].get('type')\n            if type == 'radio' and len(results) > 1:\n                group = RadioGroup(results)\n                group.name = name\n                return group\n            elif type == 'checkbox' and len(results) > 1:\n                group = CheckboxGroup(results)\n                group.name = name\n                return group\n            else:\n                # I don't like throwing away elements like this\n                return results[0]\n        else:\n            raise KeyError(\n                \"No input element with the name %r\" % name)\n\n    def __contains__(self, name):\n        results = self._name_xpath(self.form, name=name)\n        return bool(results)\n\n    def keys(self):\n        names = set()\n        for el in self:\n            names.add(el.name)\n        if None in names:\n            names.remove(None)\n        return list(names)\n\n    def __iter__(self):\n        ## FIXME: kind of dumb to turn a list into an iterator, only\n        ## to have it likely turned back into a list again :(\n        return iter(self._all_xpath(self.form))\n\n\nclass InputMixin(object):\n    \"\"\"\n    Mix-in for all input elements (input, select, and textarea)\n    \"\"\"\n    @property\n    def name(self):\n        \"\"\"\n        Get/set the name of the element\n        \"\"\"\n        return self.get('name')\n\n    @name.setter\n    def name(self, value):\n        self.set('name', value)\n\n    @name.deleter\n    def name(self):\n        attrib = self.attrib\n        if 'name' in attrib:\n            del attrib['name']\n\n    def __repr__(self):\n        type_name = getattr(self, 'type', None)\n        if type_name:\n            type_name = ' type=%r' % type_name\n        else:\n            type_name = ''\n        return '<%s %x name=%r%s>' % (\n            self.__class__.__name__, id(self), self.name, type_name)\n\n\nclass TextareaElement(InputMixin, HtmlElement):\n    \"\"\"\n    ``<textarea>`` element.  You can get the name with ``.name`` and\n    get/set the value with ``.value``\n    \"\"\"\n    @property\n    def value(self):\n        \"\"\"\n        Get/set the value (which is the contents of this element)\n        \"\"\"\n        content = self.text or ''\n        if self.tag.startswith(\"{%s}\" % XHTML_NAMESPACE):\n            serialisation_method = 'xml'\n        else:\n            serialisation_method = 'html'\n        for el in self:\n            # it's rare that we actually get here, so let's not use ''.join()\n            content += etree.tostring(\n                el, method=serialisation_method, encoding='unicode')\n        return content\n\n    @value.setter\n    def value(self, value):\n        del self[:]\n        self.text = value\n\n    @value.deleter\n    def value(self):\n        self.text = ''\n        del self[:]\n\n\nHtmlElementClassLookup._default_element_classes['textarea'] = TextareaElement\n\n\nclass SelectElement(InputMixin, HtmlElement):\n    \"\"\"\n    ``<select>`` element.  You can get the name with ``.name``.\n\n    ``.value`` will be the value of the selected option, unless this\n    is a multi-select element (``<select multiple>``), in which case\n    it will be a set-like object.  In either case ``.value_options``\n    gives the possible values.\n\n    The boolean attribute ``.multiple`` shows if this is a\n    multi-select.\n    \"\"\"\n    @property\n    def value(self):\n        \"\"\"\n        Get/set the value of this select (the selected option).\n\n        If this is a multi-select, this is a set-like object that\n        represents all the selected options.\n        \"\"\"\n        if self.multiple:\n            return MultipleSelectOptions(self)\n        options = _options_xpath(self)\n\n        try:\n            selected_option = next(el for el in reversed(options) if el.get('selected') is not None)\n        except StopIteration:\n            try:\n                selected_option = next(el for el in options if el.get('disabled') is None)\n            except StopIteration:\n                return None\n        value = selected_option.get('value')\n        if value is None:\n            value = (selected_option.text or '').strip()\n        return value\n\n    @value.setter\n    def value(self, value):\n        if self.multiple:\n            if isinstance(value, basestring):\n                raise TypeError(\"You must pass in a sequence\")\n            values = self.value\n            values.clear()\n            values.update(value)\n            return\n        checked_option = None\n        if value is not None:\n            for el in _options_xpath(self):\n                opt_value = el.get('value')\n                if opt_value is None:\n                    opt_value = (el.text or '').strip()\n                if opt_value == value:\n                    checked_option = el\n                    break\n            else:\n                raise ValueError(\n                    \"There is no option with the value of %r\" % value)\n        for el in _options_xpath(self):\n            if 'selected' in el.attrib:\n                del el.attrib['selected']\n        if checked_option is not None:\n            checked_option.set('selected', '')\n\n    @value.deleter\n    def value(self):\n        # FIXME: should del be allowed at all?\n        if self.multiple:\n            self.value.clear()\n        else:\n            self.value = None\n\n    @property\n    def value_options(self):\n        \"\"\"\n        All the possible values this select can have (the ``value``\n        attribute of all the ``<option>`` elements.\n        \"\"\"\n        options = []\n        for el in _options_xpath(self):\n            value = el.get('value')\n            if value is None:\n                value = (el.text or '').strip()\n            options.append(value)\n        return options\n\n    @property\n    def multiple(self):\n        \"\"\"\n        Boolean attribute: is there a ``multiple`` attribute on this element.\n        \"\"\"\n        return 'multiple' in self.attrib\n\n    @multiple.setter\n    def multiple(self, value):\n        if value:\n            self.set('multiple', '')\n        elif 'multiple' in self.attrib:\n            del self.attrib['multiple']\n\n\nHtmlElementClassLookup._default_element_classes['select'] = SelectElement\n\n\nclass MultipleSelectOptions(SetMixin):\n    \"\"\"\n    Represents all the selected options in a ``<select multiple>`` element.\n\n    You can add to this set-like option to select an option, or remove\n    to unselect the option.\n    \"\"\"\n\n    def __init__(self, select):\n        self.select = select\n\n    @property\n    def options(self):\n        \"\"\"\n        Iterator of all the ``<option>`` elements.\n        \"\"\"\n        return iter(_options_xpath(self.select))\n\n    def __iter__(self):\n        for option in self.options:\n            if 'selected' in option.attrib:\n                opt_value = option.get('value')\n                if opt_value is None:\n                    opt_value = (option.text or '').strip()\n                yield opt_value\n\n    def add(self, item):\n        for option in self.options:\n            opt_value = option.get('value')\n            if opt_value is None:\n                opt_value = (option.text or '').strip()\n            if opt_value == item:\n                option.set('selected', '')\n                break\n        else:\n            raise ValueError(\n                \"There is no option with the value %r\" % item)\n\n    def remove(self, item):\n        for option in self.options:\n            opt_value = option.get('value')\n            if opt_value is None:\n                opt_value = (option.text or '').strip()\n            if opt_value == item:\n                if 'selected' in option.attrib:\n                    del option.attrib['selected']\n                else:\n                    raise ValueError(\n                        \"The option %r is not currently selected\" % item)\n                break\n        else:\n            raise ValueError(\n                \"There is not option with the value %r\" % item)\n\n    def __repr__(self):\n        return '<%s {%s} for select name=%r>' % (\n            self.__class__.__name__,\n            ', '.join([repr(v) for v in self]),\n            self.select.name)\n\n\nclass RadioGroup(list):\n    \"\"\"\n    This object represents several ``<input type=radio>`` elements\n    that have the same name.\n\n    You can use this like a list, but also use the property\n    ``.value`` to check/uncheck inputs.  Also you can use\n    ``.value_options`` to get the possible values.\n    \"\"\"\n    @property\n    def value(self):\n        \"\"\"\n        Get/set the value, which checks the radio with that value (and\n        unchecks any other value).\n        \"\"\"\n        for el in self:\n            if 'checked' in el.attrib:\n                return el.get('value')\n        return None\n\n    @value.setter\n    def value(self, value):\n        checked_option = None\n        if value is not None:\n            for el in self:\n                if el.get('value') == value:\n                    checked_option = el\n                    break\n            else:\n                raise ValueError(\"There is no radio input with the value %r\" % value)\n        for el in self:\n            if 'checked' in el.attrib:\n                del el.attrib['checked']\n        if checked_option is not None:\n            checked_option.set('checked', '')\n\n    @value.deleter\n    def value(self):\n        self.value = None\n\n    @property\n    def value_options(self):\n        \"\"\"\n        Returns a list of all the possible values.\n        \"\"\"\n        return [el.get('value') for el in self]\n\n    def __repr__(self):\n        return '%s(%s)' % (\n            self.__class__.__name__,\n            list.__repr__(self))\n\n\nclass CheckboxGroup(list):\n    \"\"\"\n    Represents a group of checkboxes (``<input type=checkbox>``) that\n    have the same name.\n\n    In addition to using this like a list, the ``.value`` attribute\n    returns a set-like object that you can add to or remove from to\n    check and uncheck checkboxes.  You can also use ``.value_options``\n    to get the possible values.\n    \"\"\"\n    @property\n    def value(self):\n        \"\"\"\n        Return a set-like object that can be modified to check or\n        uncheck individual checkboxes according to their value.\n        \"\"\"\n        return CheckboxValues(self)\n\n    @value.setter\n    def value(self, value):\n        values = self.value\n        values.clear()\n        if not hasattr(value, '__iter__'):\n            raise ValueError(\n                \"A CheckboxGroup (name=%r) must be set to a sequence (not %r)\"\n                % (self[0].name, value))\n        values.update(value)\n\n    @value.deleter\n    def value(self):\n        self.value.clear()\n\n    @property\n    def value_options(self):\n        \"\"\"\n        Returns a list of all the possible values.\n        \"\"\"\n        return [el.get('value') for el in self]\n\n    def __repr__(self):\n        return '%s(%s)' % (\n            self.__class__.__name__, list.__repr__(self))\n\n\nclass CheckboxValues(SetMixin):\n    \"\"\"\n    Represents the values of the checked checkboxes in a group of\n    checkboxes with the same name.\n    \"\"\"\n\n    def __init__(self, group):\n        self.group = group\n\n    def __iter__(self):\n        return iter([\n            el.get('value')\n            for el in self.group\n            if 'checked' in el.attrib])\n\n    def add(self, value):\n        for el in self.group:\n            if el.get('value') == value:\n                el.set('checked', '')\n                break\n        else:\n            raise KeyError(\"No checkbox with value %r\" % value)\n\n    def remove(self, value):\n        for el in self.group:\n            if el.get('value') == value:\n                if 'checked' in el.attrib:\n                    del el.attrib['checked']\n                else:\n                    raise KeyError(\n                        \"The checkbox with value %r was already unchecked\" % value)\n                break\n        else:\n            raise KeyError(\n                \"No checkbox with value %r\" % value)\n\n    def __repr__(self):\n        return '<%s {%s} for checkboxes name=%r>' % (\n            self.__class__.__name__,\n            ', '.join([repr(v) for v in self]),\n            self.group.name)\n\n\nclass InputElement(InputMixin, HtmlElement):\n    \"\"\"\n    Represents an ``<input>`` element.\n\n    You can get the type with ``.type`` (which is lower-cased and\n    defaults to ``'text'``).\n\n    Also you can get and set the value with ``.value``\n\n    Checkboxes and radios have the attribute ``input.checkable ==\n    True`` (for all others it is false) and a boolean attribute\n    ``.checked``.\n\n    \"\"\"\n\n    ## FIXME: I'm a little uncomfortable with the use of .checked\n    @property\n    def value(self):\n        \"\"\"\n        Get/set the value of this element, using the ``value`` attribute.\n\n        Also, if this is a checkbox and it has no value, this defaults\n        to ``'on'``.  If it is a checkbox or radio that is not\n        checked, this returns None.\n        \"\"\"\n        if self.checkable:\n            if self.checked:\n                return self.get('value') or 'on'\n            else:\n                return None\n        return self.get('value')\n\n    @value.setter\n    def value(self, value):\n        if self.checkable:\n            if not value:\n                self.checked = False\n            else:\n                self.checked = True\n                if isinstance(value, basestring):\n                    self.set('value', value)\n        else:\n            self.set('value', value)\n\n    @value.deleter\n    def value(self):\n        if self.checkable:\n            self.checked = False\n        else:\n            if 'value' in self.attrib:\n                del self.attrib['value']\n\n    @property\n    def type(self):\n        \"\"\"\n        Return the type of this element (using the type attribute).\n        \"\"\"\n        return self.get('type', 'text').lower()\n\n    @type.setter\n    def type(self, value):\n        self.set('type', value)\n\n    @property\n    def checkable(self):\n        \"\"\"\n        Boolean: can this element be checked?\n        \"\"\"\n        return self.type in ('checkbox', 'radio')\n\n    @property\n    def checked(self):\n        \"\"\"\n        Boolean attribute to get/set the presence of the ``checked``\n        attribute.\n\n        You can only use this on checkable input types.\n        \"\"\"\n        if not self.checkable:\n            raise AttributeError('Not a checkable input type')\n        return 'checked' in self.attrib\n\n    @checked.setter\n    def checked(self, value):\n        if not self.checkable:\n            raise AttributeError('Not a checkable input type')\n        if value:\n            self.set('checked', '')\n        else:\n            attrib = self.attrib\n            if 'checked' in attrib:\n                del attrib['checked']\n\n\nHtmlElementClassLookup._default_element_classes['input'] = InputElement\n\n\nclass LabelElement(HtmlElement):\n    \"\"\"\n    Represents a ``<label>`` element.\n\n    Label elements are linked to other elements with their ``for``\n    attribute.  You can access this element with ``label.for_element``.\n    \"\"\"\n    @property\n    def for_element(self):\n        \"\"\"\n        Get/set the element this label points to.  Return None if it\n        can't be found.\n        \"\"\"\n        id = self.get('for')\n        if not id:\n            return None\n        return self.body.get_element_by_id(id)\n\n    @for_element.setter\n    def for_element(self, other):\n        id = other.get('id')\n        if not id:\n            raise TypeError(\n                \"Element %r has no id attribute\" % other)\n        self.set('for', id)\n\n    @for_element.deleter\n    def for_element(self):\n        attrib = self.attrib\n        if 'id' in attrib:\n            del attrib['id']\n\n\nHtmlElementClassLookup._default_element_classes['label'] = LabelElement\n\n\n############################################################\n## Serialization\n############################################################\n\ndef html_to_xhtml(html):\n    \"\"\"Convert all tags in an HTML tree to XHTML by moving them to the\n    XHTML namespace.\n    \"\"\"\n    try:\n        html = html.getroot()\n    except AttributeError:\n        pass\n    prefix = \"{%s}\" % XHTML_NAMESPACE\n    for el in html.iter(etree.Element):\n        tag = el.tag\n        if tag[0] != '{':\n            el.tag = prefix + tag\n\n\ndef xhtml_to_html(xhtml):\n    \"\"\"Convert all tags in an XHTML tree to HTML by removing their\n    XHTML namespace.\n    \"\"\"\n    try:\n        xhtml = xhtml.getroot()\n    except AttributeError:\n        pass\n    prefix = \"{%s}\" % XHTML_NAMESPACE\n    prefix_len = len(prefix)\n    for el in xhtml.iter(prefix + \"*\"):\n        el.tag = el.tag[prefix_len:]\n\n\n# This isn't a general match, but it's a match for what libxml2\n# specifically serialises:\n__str_replace_meta_content_type = re.compile(\n    r'<meta http-equiv=\"Content-Type\"[^>]*>').sub\n__bytes_replace_meta_content_type = re.compile(\n    r'<meta http-equiv=\"Content-Type\"[^>]*>'.encode('ASCII')).sub\n\n\ndef tostring(doc, pretty_print=False, include_meta_content_type=False,\n             encoding=None, method=\"html\", with_tail=True, doctype=None):\n    \"\"\"Return an HTML string representation of the document.\n\n    Note: if include_meta_content_type is true this will create a\n    ``<meta http-equiv=\"Content-Type\" ...>`` tag in the head;\n    regardless of the value of include_meta_content_type any existing\n    ``<meta http-equiv=\"Content-Type\" ...>`` tag will be removed\n\n    The ``encoding`` argument controls the output encoding (defaults to\n    ASCII, with &#...; character references for any characters outside\n    of ASCII).  Note that you can pass the name ``'unicode'`` as\n    ``encoding`` argument to serialise to a Unicode string.\n\n    The ``method`` argument defines the output method.  It defaults to\n    'html', but can also be 'xml' for xhtml output, or 'text' to\n    serialise to plain text without markup.\n\n    To leave out the tail text of the top-level element that is being\n    serialised, pass ``with_tail=False``.\n\n    The ``doctype`` option allows passing in a plain string that will\n    be serialised before the XML tree.  Note that passing in non\n    well-formed content here will make the XML output non well-formed.\n    Also, an existing doctype in the document tree will not be removed\n    when serialising an ElementTree instance.\n\n    Example::\n\n        >>> from lxml import html\n        >>> root = html.fragment_fromstring('<p>Hello<br>world!</p>')\n\n        >>> html.tostring(root)\n        b'<p>Hello<br>world!</p>'\n        >>> html.tostring(root, method='html')\n        b'<p>Hello<br>world!</p>'\n\n        >>> html.tostring(root, method='xml')\n        b'<p>Hello<br/>world!</p>'\n\n        >>> html.tostring(root, method='text')\n        b'Helloworld!'\n\n        >>> html.tostring(root, method='text', encoding='unicode')\n        u'Helloworld!'\n\n        >>> root = html.fragment_fromstring('<div><p>Hello<br>world!</p>TAIL</div>')\n        >>> html.tostring(root[0], method='text', encoding='unicode')\n        u'Helloworld!TAIL'\n\n        >>> html.tostring(root[0], method='text', encoding='unicode', with_tail=False)\n        u'Helloworld!'\n\n        >>> doc = html.document_fromstring('<p>Hello<br>world!</p>')\n        >>> html.tostring(doc, method='html', encoding='unicode')\n        u'<html><body><p>Hello<br>world!</p></body></html>'\n\n        >>> print(html.tostring(doc, method='html', encoding='unicode',\n        ...          doctype='<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01//EN\"'\n        ...                  ' \"http://www.w3.org/TR/html4/strict.dtd\">'))\n        <!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01//EN\" \"http://www.w3.org/TR/html4/strict.dtd\">\n        <html><body><p>Hello<br>world!</p></body></html>\n    \"\"\"\n    html = etree.tostring(doc, method=method, pretty_print=pretty_print,\n                          encoding=encoding, with_tail=with_tail,\n                          doctype=doctype)\n    if method == 'html' and not include_meta_content_type:\n        if isinstance(html, str):\n            html = __str_replace_meta_content_type('', html)\n        else:\n            html = __bytes_replace_meta_content_type(bytes(), html)\n    return html\n\n\ntostring.__doc__ = __fix_docstring(tostring.__doc__)\n\n\ndef open_in_browser(doc, encoding=None):\n    \"\"\"\n    Open the HTML document in a web browser, saving it to a temporary\n    file to open it.  Note that this does not delete the file after\n    use.  This is mainly meant for debugging.\n    \"\"\"\n    import os\n    import webbrowser\n    import tempfile\n    if not isinstance(doc, etree._ElementTree):\n        doc = etree.ElementTree(doc)\n    handle, fn = tempfile.mkstemp(suffix='.html')\n    f = os.fdopen(handle, 'wb')\n    try:\n        doc.write(f, method=\"html\", encoding=encoding or doc.docinfo.encoding or \"UTF-8\")\n    finally:\n        # we leak the file itself here, but we should at least close it\n        f.close()\n    url = 'file://' + fn.replace(os.path.sep, '/')\n    print(url)\n    webbrowser.open(url)\n\n\n################################################################################\n# configure Element class lookup\n################################################################################\n\nclass HTMLParser(etree.HTMLParser):\n    \"\"\"An HTML parser that is configured to return lxml.html Element\n    objects.\n    \"\"\"\n    def __init__(self, **kwargs):\n        super(HTMLParser, self).__init__(**kwargs)\n        self.set_element_class_lookup(HtmlElementClassLookup())\n\n\nclass XHTMLParser(etree.XMLParser):\n    \"\"\"An XML parser that is configured to return lxml.html Element\n    objects.\n\n    Note that this parser is not really XHTML aware unless you let it\n    load a DTD that declares the HTML entities.  To do this, make sure\n    you have the XHTML DTDs installed in your catalogs, and create the\n    parser like this::\n\n        >>> parser = XHTMLParser(load_dtd=True)\n\n    If you additionally want to validate the document, use this::\n\n        >>> parser = XHTMLParser(dtd_validation=True)\n\n    For catalog support, see http://www.xmlsoft.org/catalog.html.\n    \"\"\"\n    def __init__(self, **kwargs):\n        super(XHTMLParser, self).__init__(**kwargs)\n        self.set_element_class_lookup(HtmlElementClassLookup())\n\n\ndef Element(*args, **kw):\n    \"\"\"Create a new HTML Element.\n\n    This can also be used for XHTML documents.\n    \"\"\"\n    v = html_parser.makeelement(*args, **kw)\n    return v\n\n\nhtml_parser = HTMLParser()\nxhtml_parser = XHTMLParser()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/_diffcommand.py",
    "content": "from __future__ import absolute_import\n\nimport optparse\nimport sys\nimport re\nimport os\nfrom .diff import htmldiff\n\ndescription = \"\"\"\\\n\"\"\"\n\nparser = optparse.OptionParser(\n    usage=\"%prog [OPTIONS] FILE1 FILE2\\n\"\n    \"%prog --annotate [OPTIONS] INFO1 FILE1 INFO2 FILE2 ...\",\n    description=description,\n    )\n\nparser.add_option(\n    '-o', '--output',\n    metavar=\"FILE\",\n    dest=\"output\",\n    default=\"-\",\n    help=\"File to write the difference to\",\n    )\n\nparser.add_option(\n    '-a', '--annotation',\n    action=\"store_true\",\n    dest=\"annotation\",\n    help=\"Do an annotation\")\n\ndef main(args=None):\n    if args is None:\n        args = sys.argv[1:]\n    options, args = parser.parse_args(args)\n    if options.annotation:\n        return annotate(options, args)\n    if len(args) != 2:\n        print('Error: you must give two files')\n        parser.print_help()\n        sys.exit(1)\n    file1, file2 = args\n    input1 = read_file(file1)\n    input2 = read_file(file2)\n    body1 = split_body(input1)[1]\n    pre, body2, post = split_body(input2)\n    result = htmldiff(body1, body2)\n    result = pre + result + post\n    if options.output == '-':\n        if not result.endswith('\\n'):\n            result += '\\n'\n        sys.stdout.write(result)\n    else:\n        with open(options.output, 'wb') as f:\n            f.write(result)\n\ndef read_file(filename):\n    if filename == '-':\n        c = sys.stdin.read()\n    elif not os.path.exists(filename):\n        raise OSError(\n            \"Input file %s does not exist\" % filename)\n    else:\n        with open(filename, 'rb') as f:\n            c = f.read()\n    return c\n\nbody_start_re = re.compile(\n    r\"<body.*?>\", re.I|re.S)\nbody_end_re = re.compile(\n    r\"</body.*?>\", re.I|re.S)\n    \ndef split_body(html):\n    pre = post = ''\n    match = body_start_re.search(html)\n    if match:\n        pre = html[:match.end()]\n        html = html[match.end():]\n    match = body_end_re.search(html)\n    if match:\n        post = html[match.start():]\n        html = html[:match.start()]\n    return pre, html, post\n\ndef annotate(options, args):\n    print(\"Not yet implemented\")\n    sys.exit(1)\n    \n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/_html5builder.py",
    "content": "\"\"\"\nLegacy module - don't use in new code!\n\nhtml5lib now has its own proper implementation.\n\nThis module implements a tree builder for html5lib that generates lxml\nhtml element trees.  This module uses camelCase as it follows the\nhtml5lib style guide.\n\"\"\"\n\nfrom html5lib.treebuilders import _base, etree as etree_builders\nfrom lxml import html, etree\n\n\nclass DocumentType(object):\n\n    def __init__(self, name, publicId, systemId):\n        self.name = name\n        self.publicId = publicId\n        self.systemId = systemId\n\nclass Document(object):\n\n    def __init__(self):\n        self._elementTree = None\n        self.childNodes = []\n\n    def appendChild(self, element):\n        self._elementTree.getroot().addnext(element._element)\n\n\nclass TreeBuilder(_base.TreeBuilder):\n    documentClass = Document\n    doctypeClass = DocumentType\n    elementClass = None\n    commentClass = None\n    fragmentClass = Document\n\n    def __init__(self, *args, **kwargs):\n        html_builder = etree_builders.getETreeModule(html, fullTree=False)\n        etree_builder = etree_builders.getETreeModule(etree, fullTree=False)\n        self.elementClass = html_builder.Element\n        self.commentClass = etree_builder.Comment\n        _base.TreeBuilder.__init__(self, *args, **kwargs)\n\n    def reset(self):\n        _base.TreeBuilder.reset(self)\n        self.rootInserted = False\n        self.initialComments = []\n        self.doctype = None\n\n    def getDocument(self):\n        return self.document._elementTree\n\n    def getFragment(self):\n        fragment = []\n        element = self.openElements[0]._element\n        if element.text:\n            fragment.append(element.text)\n        fragment.extend(element.getchildren())\n        if element.tail:\n            fragment.append(element.tail)\n        return fragment\n\n    def insertDoctype(self, name, publicId, systemId):\n        doctype = self.doctypeClass(name, publicId, systemId)\n        self.doctype = doctype\n\n    def insertComment(self, data, parent=None):\n        if not self.rootInserted:\n            self.initialComments.append(data)\n        else:\n            _base.TreeBuilder.insertComment(self, data, parent)\n\n    def insertRoot(self, name):\n        buf = []\n        if self.doctype and self.doctype.name:\n            buf.append('<!DOCTYPE %s' % self.doctype.name)\n            if self.doctype.publicId is not None or self.doctype.systemId is not None:\n                buf.append(' PUBLIC \"%s\" \"%s\"' % (self.doctype.publicId,\n                                                  self.doctype.systemId))\n            buf.append('>')\n        buf.append('<html></html>')\n        root = html.fromstring(''.join(buf))\n\n        # Append the initial comments:\n        for comment in self.initialComments:\n            root.addprevious(etree.Comment(comment))\n\n        # Create the root document and add the ElementTree to it\n        self.document = self.documentClass()\n        self.document._elementTree = root.getroottree()\n\n        # Add the root element to the internal child/open data structures\n        root_element = self.elementClass(name)\n        root_element._element = root\n        self.document.childNodes.append(root_element)\n        self.openElements.append(root_element)\n\n        self.rootInserted = True\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/_setmixin.py",
    "content": "try:\n    from collections.abc import MutableSet\nexcept ImportError:\n    from collections import MutableSet\n\n\nclass SetMixin(MutableSet):\n\n    \"\"\"\n    Mix-in for sets.  You must define __iter__, add, remove\n    \"\"\"\n\n    def __len__(self):\n        length = 0\n        for item in self:\n            length += 1\n        return length\n\n    def __contains__(self, item):\n        for has_item in self:\n            if item == has_item:\n                return True\n        return False\n\n    issubset = MutableSet.__le__\n    issuperset = MutableSet.__ge__\n\n    union = MutableSet.__or__\n    intersection = MutableSet.__and__\n    difference = MutableSet.__sub__\n    symmetric_difference = MutableSet.__xor__\n\n    def copy(self):\n        return set(self)\n\n    def update(self, other):\n        self |= other\n\n    def intersection_update(self, other):\n        self &= other\n\n    def difference_update(self, other):\n        self -= other\n\n    def symmetric_difference_update(self, other):\n        self ^= other\n\n    def discard(self, item):\n        try:\n            self.remove(item)\n        except KeyError:\n            pass\n\n    @classmethod\n    def _from_iterable(cls, it):\n        return set(it)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/builder.py",
    "content": "# --------------------------------------------------------------------\n# The ElementTree toolkit is\n# Copyright (c) 1999-2004 by Fredrik Lundh\n# --------------------------------------------------------------------\n\n\"\"\"\nA set of HTML generator tags for building HTML documents.\n\nUsage::\n\n    >>> from lxml.html.builder import *\n    >>> html = HTML(\n    ...            HEAD( TITLE(\"Hello World\") ),\n    ...            BODY( CLASS(\"main\"),\n    ...                  H1(\"Hello World !\")\n    ...            )\n    ...        )\n\n    >>> import lxml.etree\n    >>> print lxml.etree.tostring(html, pretty_print=True)\n    <html>\n      <head>\n        <title>Hello World</title>\n      </head>\n      <body class=\"main\">\n        <h1>Hello World !</h1>\n      </body>\n    </html>\n\n\"\"\"\n\nfrom lxml.builder import ElementMaker\nfrom lxml.html import html_parser\n\nE = ElementMaker(makeelement=html_parser.makeelement)\n\n# elements\nA = E.a # anchor\nABBR = E.abbr # abbreviated form (e.g., WWW, HTTP, etc.)\nACRONYM = E.acronym # \nADDRESS = E.address # information on author\nAPPLET = E.applet # Java applet (DEPRECATED)\nAREA = E.area # client-side image map area\nB = E.b # bold text style\nBASE = E.base # document base URI\nBASEFONT = E.basefont # base font size (DEPRECATED)\nBDO = E.bdo # I18N BiDi over-ride\nBIG = E.big # large text style\nBLOCKQUOTE = E.blockquote # long quotation\nBODY = E.body # document body\nBR = E.br # forced line break\nBUTTON = E.button # push button\nCAPTION = E.caption # table caption\nCENTER = E.center # shorthand for DIV align=center (DEPRECATED)\nCITE = E.cite # citation\nCODE = E.code # computer code fragment\nCOL = E.col # table column\nCOLGROUP = E.colgroup # table column group\nDD = E.dd # definition description\nDEL = getattr(E, 'del') # deleted text\nDFN = E.dfn # instance definition\nDIR = E.dir # directory list (DEPRECATED)\nDIV = E.div # generic language/style container\nDL = E.dl # definition list\nDT = E.dt # definition term\nEM = E.em # emphasis\nFIELDSET = E.fieldset # form control group\nFONT = E.font # local change to font (DEPRECATED)\nFORM = E.form # interactive form\nFRAME = E.frame # subwindow\nFRAMESET = E.frameset # window subdivision\nH1 = E.h1 # heading\nH2 = E.h2 # heading\nH3 = E.h3 # heading\nH4 = E.h4 # heading\nH5 = E.h5 # heading\nH6 = E.h6 # heading\nHEAD = E.head # document head\nHR = E.hr # horizontal rule\nHTML = E.html # document root element\nI = E.i # italic text style\nIFRAME = E.iframe # inline subwindow\nIMG = E.img # Embedded image\nINPUT = E.input # form control\nINS = E.ins # inserted text\nISINDEX = E.isindex # single line prompt (DEPRECATED)\nKBD = E.kbd # text to be entered by the user\nLABEL = E.label # form field label text\nLEGEND = E.legend # fieldset legend\nLI = E.li # list item\nLINK = E.link # a media-independent link\nMAP = E.map # client-side image map\nMENU = E.menu # menu list (DEPRECATED)\nMETA = E.meta # generic metainformation\nNOFRAMES = E.noframes # alternate content container for non frame-based rendering\nNOSCRIPT = E.noscript # alternate content container for non script-based rendering\nOBJECT = E.object # generic embedded object\nOL = E.ol # ordered list\nOPTGROUP = E.optgroup # option group\nOPTION = E.option # selectable choice\nP = E.p # paragraph\nPARAM = E.param # named property value\nPRE = E.pre # preformatted text\nQ = E.q # short inline quotation\nS = E.s # strike-through text style (DEPRECATED)\nSAMP = E.samp # sample program output, scripts, etc.\nSCRIPT = E.script # script statements\nSELECT = E.select # option selector\nSMALL = E.small # small text style\nSPAN = E.span # generic language/style container\nSTRIKE = E.strike # strike-through text (DEPRECATED)\nSTRONG = E.strong # strong emphasis\nSTYLE = E.style # style info\nSUB = E.sub # subscript\nSUP = E.sup # superscript\nTABLE = E.table # \nTBODY = E.tbody # table body\nTD = E.td # table data cell\nTEXTAREA = E.textarea # multi-line text field\nTFOOT = E.tfoot # table footer\nTH = E.th # table header cell\nTHEAD = E.thead # table header\nTITLE = E.title # document title\nTR = E.tr # table row\nTT = E.tt # teletype or monospaced text style\nU = E.u # underlined text style (DEPRECATED)\nUL = E.ul # unordered list\nVAR = E.var # instance of a variable or program argument\n\n# attributes (only reserved words are included here)\nATTR = dict\ndef CLASS(v): return {'class': v}\ndef FOR(v): return {'for': v}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/clean.py",
    "content": "# cython: language_level=2\n\n\"\"\"A cleanup tool for HTML.\n\nRemoves unwanted tags and content.  See the `Cleaner` class for\ndetails.\n\"\"\"\n\nfrom __future__ import absolute_import\n\nimport re\nimport copy\ntry:\n    from urlparse import urlsplit\n    from urllib import unquote_plus\nexcept ImportError:\n    # Python 3\n    from urllib.parse import urlsplit, unquote_plus\nfrom lxml import etree\nfrom lxml.html import defs\nfrom lxml.html import fromstring, XHTML_NAMESPACE\nfrom lxml.html import xhtml_to_html, _transform_result\n\ntry:\n    unichr\nexcept NameError:\n    # Python 3\n    unichr = chr\ntry:\n    unicode\nexcept NameError:\n    # Python 3\n    unicode = str\ntry:\n    basestring\nexcept NameError:\n    basestring = (str, bytes)\n\n\n__all__ = ['clean_html', 'clean', 'Cleaner', 'autolink', 'autolink_html',\n           'word_break', 'word_break_html']\n\n# Look at http://code.sixapart.com/trac/livejournal/browser/trunk/cgi-bin/cleanhtml.pl\n#   Particularly the CSS cleaning; most of the tag cleaning is integrated now\n# I have multiple kinds of schemes searched; but should schemes be\n#   whitelisted instead?\n# max height?\n# remove images?  Also in CSS?  background attribute?\n# Some way to whitelist object, iframe, etc (e.g., if you want to\n#   allow *just* embedded YouTube movies)\n# Log what was deleted and why?\n# style=\"behavior: ...\" might be bad in IE?\n# Should we have something for just <meta http-equiv>?  That's the worst of the\n#   metas.\n# UTF-7 detections?  Example:\n#     <HEAD><META HTTP-EQUIV=\"CONTENT-TYPE\" CONTENT=\"text/html; charset=UTF-7\"> </HEAD>+ADw-SCRIPT+AD4-alert('XSS');+ADw-/SCRIPT+AD4-\n#   you don't always have to have the charset set, if the page has no charset\n#   and there's UTF7-like code in it.\n# Look at these tests: http://htmlpurifier.org/live/smoketests/xssAttacks.php\n\n\n# This is an IE-specific construct you can have in a stylesheet to\n# run some Javascript:\n_css_javascript_re = re.compile(\n    r'expression\\s*\\(.*?\\)', re.S|re.I)\n\n# Do I have to worry about @\\nimport?\n_css_import_re = re.compile(\n    r'@\\s*import', re.I)\n\n# All kinds of schemes besides just javascript: that can cause\n# execution:\n_is_image_dataurl = re.compile(\n    r'^data:image/.+;base64', re.I).search\n_is_possibly_malicious_scheme = re.compile(\n    r'(?:javascript|jscript|livescript|vbscript|data|about|mocha):',\n    re.I).search\ndef _is_javascript_scheme(s):\n    if _is_image_dataurl(s):\n        return None\n    return _is_possibly_malicious_scheme(s)\n\n_substitute_whitespace = re.compile(r'[\\s\\x00-\\x08\\x0B\\x0C\\x0E-\\x19]+').sub\n# FIXME: should data: be blocked?\n\n# FIXME: check against: http://msdn2.microsoft.com/en-us/library/ms537512.aspx\n_conditional_comment_re = re.compile(\n    r'\\[if[\\s\\n\\r]+.*?][\\s\\n\\r]*>', re.I|re.S)\n\n_find_styled_elements = etree.XPath(\n    \"descendant-or-self::*[@style]\")\n\n_find_external_links = etree.XPath(\n    (\"descendant-or-self::a  [normalize-space(@href) and substring(normalize-space(@href),1,1) != '#'] |\"\n     \"descendant-or-self::x:a[normalize-space(@href) and substring(normalize-space(@href),1,1) != '#']\"),\n    namespaces={'x':XHTML_NAMESPACE})\n\n\nclass Cleaner(object):\n    \"\"\"\n    Instances cleans the document of each of the possible offending\n    elements.  The cleaning is controlled by attributes; you can\n    override attributes in a subclass, or set them in the constructor.\n\n    ``scripts``:\n        Removes any ``<script>`` tags.\n\n    ``javascript``:\n        Removes any Javascript, like an ``onclick`` attribute. Also removes stylesheets\n        as they could contain Javascript.\n\n    ``comments``:\n        Removes any comments.\n\n    ``style``:\n        Removes any style tags.\n\n    ``inline_style``\n        Removes any style attributes.  Defaults to the value of the ``style`` option.\n\n    ``links``:\n        Removes any ``<link>`` tags\n\n    ``meta``:\n        Removes any ``<meta>`` tags\n\n    ``page_structure``:\n        Structural parts of a page: ``<head>``, ``<html>``, ``<title>``.\n\n    ``processing_instructions``:\n        Removes any processing instructions.\n\n    ``embedded``:\n        Removes any embedded objects (flash, iframes)\n\n    ``frames``:\n        Removes any frame-related tags\n\n    ``forms``:\n        Removes any form tags\n\n    ``annoying_tags``:\n        Tags that aren't *wrong*, but are annoying.  ``<blink>`` and ``<marquee>``\n\n    ``remove_tags``:\n        A list of tags to remove.  Only the tags will be removed,\n        their content will get pulled up into the parent tag.\n\n    ``kill_tags``:\n        A list of tags to kill.  Killing also removes the tag's content,\n        i.e. the whole subtree, not just the tag itself.\n\n    ``allow_tags``:\n        A list of tags to include (default include all).\n\n    ``remove_unknown_tags``:\n        Remove any tags that aren't standard parts of HTML.\n\n    ``safe_attrs_only``:\n        If true, only include 'safe' attributes (specifically the list\n        from the feedparser HTML sanitisation web site).\n\n    ``safe_attrs``:\n        A set of attribute names to override the default list of attributes\n        considered 'safe' (when safe_attrs_only=True).\n\n    ``add_nofollow``:\n        If true, then any <a> tags will have ``rel=\"nofollow\"`` added to them.\n\n    ``host_whitelist``:\n        A list or set of hosts that you can use for embedded content\n        (for content like ``<object>``, ``<link rel=\"stylesheet\">``, etc).\n        You can also implement/override the method\n        ``allow_embedded_url(el, url)`` or ``allow_element(el)`` to\n        implement more complex rules for what can be embedded.\n        Anything that passes this test will be shown, regardless of\n        the value of (for instance) ``embedded``.\n\n        Note that this parameter might not work as intended if you do not\n        make the links absolute before doing the cleaning.\n\n        Note that you may also need to set ``whitelist_tags``.\n\n    ``whitelist_tags``:\n        A set of tags that can be included with ``host_whitelist``.\n        The default is ``iframe`` and ``embed``; you may wish to\n        include other tags like ``script``, or you may want to\n        implement ``allow_embedded_url`` for more control.  Set to None to\n        include all tags.\n\n    This modifies the document *in place*.\n    \"\"\"\n\n    scripts = True\n    javascript = True\n    comments = True\n    style = False\n    inline_style = None\n    links = True\n    meta = True\n    page_structure = True\n    processing_instructions = True\n    embedded = True\n    frames = True\n    forms = True\n    annoying_tags = True\n    remove_tags = None\n    allow_tags = None\n    kill_tags = None\n    remove_unknown_tags = True\n    safe_attrs_only = True\n    safe_attrs = defs.safe_attrs\n    add_nofollow = False\n    host_whitelist = ()\n    whitelist_tags = {'iframe', 'embed'}\n\n    def __init__(self, **kw):\n        for name, value in kw.items():\n            if not hasattr(self, name):\n                raise TypeError(\n                    \"Unknown parameter: %s=%r\" % (name, value))\n            setattr(self, name, value)\n        if self.inline_style is None and 'inline_style' not in kw:\n            self.inline_style = self.style\n\n    # Used to lookup the primary URL for a given tag that is up for\n    # removal:\n    _tag_link_attrs = dict(\n        script='src',\n        link='href',\n        # From: http://java.sun.com/j2se/1.4.2/docs/guide/misc/applet.html\n        # From what I can tell, both attributes can contain a link:\n        applet=['code', 'object'],\n        iframe='src',\n        embed='src',\n        layer='src',\n        # FIXME: there doesn't really seem like a general way to figure out what\n        # links an <object> tag uses; links often go in <param> tags with values\n        # that we don't really know.  You'd have to have knowledge about specific\n        # kinds of plugins (probably keyed off classid), and match against those.\n        ##object=?,\n        # FIXME: not looking at the action currently, because it is more complex\n        # than than -- if you keep the form, you should keep the form controls.\n        ##form='action',\n        a='href',\n        )\n\n    def __call__(self, doc):\n        \"\"\"\n        Cleans the document.\n        \"\"\"\n        if hasattr(doc, 'getroot'):\n            # ElementTree instance, instead of an element\n            doc = doc.getroot()\n        # convert XHTML to HTML\n        xhtml_to_html(doc)\n        # Normalize a case that IE treats <image> like <img>, and that\n        # can confuse either this step or later steps.\n        for el in doc.iter('image'):\n            el.tag = 'img'\n        if not self.comments:\n            # Of course, if we were going to kill comments anyway, we don't\n            # need to worry about this\n            self.kill_conditional_comments(doc)\n\n        kill_tags = set(self.kill_tags or ())\n        remove_tags = set(self.remove_tags or ())\n        allow_tags = set(self.allow_tags or ())\n\n        if self.scripts:\n            kill_tags.add('script')\n        if self.safe_attrs_only:\n            safe_attrs = set(self.safe_attrs)\n            for el in doc.iter(etree.Element):\n                attrib = el.attrib\n                for aname in attrib.keys():\n                    if aname not in safe_attrs:\n                        del attrib[aname]\n        if self.javascript:\n            if not (self.safe_attrs_only and\n                    self.safe_attrs == defs.safe_attrs):\n                # safe_attrs handles events attributes itself\n                for el in doc.iter(etree.Element):\n                    attrib = el.attrib\n                    for aname in attrib.keys():\n                        if aname.startswith('on'):\n                            del attrib[aname]\n            doc.rewrite_links(self._remove_javascript_link,\n                              resolve_base_href=False)\n            # If we're deleting style then we don't have to remove JS links\n            # from styles, otherwise...\n            if not self.inline_style:\n                for el in _find_styled_elements(doc):\n                    old = el.get('style')\n                    new = _css_javascript_re.sub('', old)\n                    new = _css_import_re.sub('', new)\n                    if self._has_sneaky_javascript(new):\n                        # Something tricky is going on...\n                        del el.attrib['style']\n                    elif new != old:\n                        el.set('style', new)\n            if not self.style:\n                for el in list(doc.iter('style')):\n                    if el.get('type', '').lower().strip() == 'text/javascript':\n                        el.drop_tree()\n                        continue\n                    old = el.text or ''\n                    new = _css_javascript_re.sub('', old)\n                    # The imported CSS can do anything; we just can't allow:\n                    new = _css_import_re.sub('', old)\n                    if self._has_sneaky_javascript(new):\n                        # Something tricky is going on...\n                        el.text = '/* deleted */'\n                    elif new != old:\n                        el.text = new\n        if self.comments or self.processing_instructions:\n            # FIXME: why either?  I feel like there's some obscure reason\n            # because you can put PIs in comments...?  But I've already\n            # forgotten it\n            kill_tags.add(etree.Comment)\n        if self.processing_instructions:\n            kill_tags.add(etree.ProcessingInstruction)\n        if self.style:\n            kill_tags.add('style')\n        if self.inline_style:\n            etree.strip_attributes(doc, 'style')\n        if self.links:\n            kill_tags.add('link')\n        elif self.style or self.javascript:\n            # We must get rid of included stylesheets if Javascript is not\n            # allowed, as you can put Javascript in them\n            for el in list(doc.iter('link')):\n                if 'stylesheet' in el.get('rel', '').lower():\n                    # Note this kills alternate stylesheets as well\n                    if not self.allow_element(el):\n                        el.drop_tree()\n        if self.meta:\n            kill_tags.add('meta')\n        if self.page_structure:\n            remove_tags.update(('head', 'html', 'title'))\n        if self.embedded:\n            # FIXME: is <layer> really embedded?\n            # We should get rid of any <param> tags not inside <applet>;\n            # These are not really valid anyway.\n            for el in list(doc.iter('param')):\n                found_parent = False\n                parent = el.getparent()\n                while parent is not None and parent.tag not in ('applet', 'object'):\n                    parent = parent.getparent()\n                if parent is None:\n                    el.drop_tree()\n            kill_tags.update(('applet',))\n            # The alternate contents that are in an iframe are a good fallback:\n            remove_tags.update(('iframe', 'embed', 'layer', 'object', 'param'))\n        if self.frames:\n            # FIXME: ideally we should look at the frame links, but\n            # generally frames don't mix properly with an HTML\n            # fragment anyway.\n            kill_tags.update(defs.frame_tags)\n        if self.forms:\n            remove_tags.add('form')\n            kill_tags.update(('button', 'input', 'select', 'textarea'))\n        if self.annoying_tags:\n            remove_tags.update(('blink', 'marquee'))\n\n        _remove = []\n        _kill = []\n        for el in doc.iter():\n            if el.tag in kill_tags:\n                if self.allow_element(el):\n                    continue\n                _kill.append(el)\n            elif el.tag in remove_tags:\n                if self.allow_element(el):\n                    continue\n                _remove.append(el)\n\n        if _remove and _remove[0] == doc:\n            # We have to drop the parent-most tag, which we can't\n            # do.  Instead we'll rewrite it:\n            el = _remove.pop(0)\n            el.tag = 'div'\n            el.attrib.clear()\n        elif _kill and _kill[0] == doc:\n            # We have to drop the parent-most element, which we can't\n            # do.  Instead we'll clear it:\n            el = _kill.pop(0)\n            if el.tag != 'html':\n                el.tag = 'div'\n            el.clear()\n\n        _kill.reverse() # start with innermost tags\n        for el in _kill:\n            el.drop_tree()\n        for el in _remove:\n            el.drop_tag()\n\n        if self.remove_unknown_tags:\n            if allow_tags:\n                raise ValueError(\n                    \"It does not make sense to pass in both allow_tags and remove_unknown_tags\")\n            allow_tags = set(defs.tags)\n        if allow_tags:\n            bad = []\n            for el in doc.iter():\n                if el.tag not in allow_tags:\n                    bad.append(el)\n            if bad:\n                if bad[0] is doc:\n                    el = bad.pop(0)\n                    el.tag = 'div'\n                    el.attrib.clear()\n                for el in bad:\n                    el.drop_tag()\n        if self.add_nofollow:\n            for el in _find_external_links(doc):\n                if not self.allow_follow(el):\n                    rel = el.get('rel')\n                    if rel:\n                        if ('nofollow' in rel\n                                and ' nofollow ' in (' %s ' % rel)):\n                            continue\n                        rel = '%s nofollow' % rel\n                    else:\n                        rel = 'nofollow'\n                    el.set('rel', rel)\n\n    def allow_follow(self, anchor):\n        \"\"\"\n        Override to suppress rel=\"nofollow\" on some anchors.\n        \"\"\"\n        return False\n\n    def allow_element(self, el):\n        if el.tag not in self._tag_link_attrs:\n            return False\n        attr = self._tag_link_attrs[el.tag]\n        if isinstance(attr, (list, tuple)):\n            for one_attr in attr:\n                url = el.get(one_attr)\n                if not url:\n                    return False\n                if not self.allow_embedded_url(el, url):\n                    return False\n            return True\n        else:\n            url = el.get(attr)\n            if not url:\n                return False\n            return self.allow_embedded_url(el, url)\n\n    def allow_embedded_url(self, el, url):\n        if (self.whitelist_tags is not None\n            and el.tag not in self.whitelist_tags):\n            return False\n        scheme, netloc, path, query, fragment = urlsplit(url)\n        netloc = netloc.lower().split(':', 1)[0]\n        if scheme not in ('http', 'https'):\n            return False\n        if netloc in self.host_whitelist:\n            return True\n        return False\n\n    def kill_conditional_comments(self, doc):\n        \"\"\"\n        IE conditional comments basically embed HTML that the parser\n        doesn't normally see.  We can't allow anything like that, so\n        we'll kill any comments that could be conditional.\n        \"\"\"\n        bad = []\n        self._kill_elements(\n            doc, lambda el: _conditional_comment_re.search(el.text),\n            etree.Comment)                \n\n    def _kill_elements(self, doc, condition, iterate=None):\n        bad = []\n        for el in doc.iter(iterate):\n            if condition(el):\n                bad.append(el)\n        for el in bad:\n            el.drop_tree()\n\n    def _remove_javascript_link(self, link):\n        # links like \"j a v a s c r i p t:\" might be interpreted in IE\n        new = _substitute_whitespace('', unquote_plus(link))\n        if _is_javascript_scheme(new):\n            # FIXME: should this be None to delete?\n            return ''\n        return link\n\n    _substitute_comments = re.compile(r'/\\*.*?\\*/', re.S).sub\n\n    def _has_sneaky_javascript(self, style):\n        \"\"\"\n        Depending on the browser, stuff like ``e x p r e s s i o n(...)``\n        can get interpreted, or ``expre/* stuff */ssion(...)``.  This\n        checks for attempt to do stuff like this.\n\n        Typically the response will be to kill the entire style; if you\n        have just a bit of Javascript in the style another rule will catch\n        that and remove only the Javascript from the style; this catches\n        more sneaky attempts.\n        \"\"\"\n        style = self._substitute_comments('', style)\n        style = style.replace('\\\\', '')\n        style = _substitute_whitespace('', style)\n        style = style.lower()\n        if 'javascript:' in style:\n            return True\n        if 'expression(' in style:\n            return True\n        return False\n\n    def clean_html(self, html):\n        result_type = type(html)\n        if isinstance(html, basestring):\n            doc = fromstring(html)\n        else:\n            doc = copy.deepcopy(html)\n        self(doc)\n        return _transform_result(result_type, doc)\n\nclean = Cleaner()\nclean_html = clean.clean_html\n\n############################################################\n## Autolinking\n############################################################\n\n_link_regexes = [\n    re.compile(r'(?P<body>https?://(?P<host>[a-z0-9._-]+)(?:/[/\\-_.,a-z0-9%&?;=~]*)?(?:\\([/\\-_.,a-z0-9%&?;=~]*\\))?)', re.I),\n    # This is conservative, but autolinking can be a bit conservative:\n    re.compile(r'mailto:(?P<body>[a-z0-9._-]+@(?P<host>[a-z0-9_.-]+[a-z]))', re.I),\n    ]\n\n_avoid_elements = ['textarea', 'pre', 'code', 'head', 'select', 'a']\n\n_avoid_hosts = [\n    re.compile(r'^localhost', re.I),\n    re.compile(r'\\bexample\\.(?:com|org|net)$', re.I),\n    re.compile(r'^127\\.0\\.0\\.1$'),\n    ]\n\n_avoid_classes = ['nolink']\n\ndef autolink(el, link_regexes=_link_regexes,\n             avoid_elements=_avoid_elements,\n             avoid_hosts=_avoid_hosts,\n             avoid_classes=_avoid_classes):\n    \"\"\"\n    Turn any URLs into links.\n\n    It will search for links identified by the given regular\n    expressions (by default mailto and http(s) links).\n\n    It won't link text in an element in avoid_elements, or an element\n    with a class in avoid_classes.  It won't link to anything with a\n    host that matches one of the regular expressions in avoid_hosts\n    (default localhost and 127.0.0.1).\n\n    If you pass in an element, the element's tail will not be\n    substituted, only the contents of the element.\n    \"\"\"\n    if el.tag in avoid_elements:\n        return\n    class_name = el.get('class')\n    if class_name:\n        class_name = class_name.split()\n        for match_class in avoid_classes:\n            if match_class in class_name:\n                return\n    for child in list(el):\n        autolink(child, link_regexes=link_regexes,\n                 avoid_elements=avoid_elements,\n                 avoid_hosts=avoid_hosts,\n                 avoid_classes=avoid_classes)\n        if child.tail:\n            text, tail_children = _link_text(\n                child.tail, link_regexes, avoid_hosts, factory=el.makeelement)\n            if tail_children:\n                child.tail = text\n                index = el.index(child)\n                el[index+1:index+1] = tail_children\n    if el.text:\n        text, pre_children = _link_text(\n            el.text, link_regexes, avoid_hosts, factory=el.makeelement)\n        if pre_children:\n            el.text = text\n            el[:0] = pre_children\n\ndef _link_text(text, link_regexes, avoid_hosts, factory):\n    leading_text = ''\n    links = []\n    last_pos = 0\n    while 1:\n        best_match, best_pos = None, None\n        for regex in link_regexes:\n            regex_pos = last_pos\n            while 1:\n                match = regex.search(text, pos=regex_pos)\n                if match is None:\n                    break\n                host = match.group('host')\n                for host_regex in avoid_hosts:\n                    if host_regex.search(host):\n                        regex_pos = match.end()\n                        break\n                else:\n                    break\n            if match is None:\n                continue\n            if best_pos is None or match.start() < best_pos:\n                best_match = match\n                best_pos = match.start()\n        if best_match is None:\n            # No more matches\n            if links:\n                assert not links[-1].tail\n                links[-1].tail = text\n            else:\n                assert not leading_text\n                leading_text = text\n            break\n        link = best_match.group(0)\n        end = best_match.end()\n        if link.endswith('.') or link.endswith(','):\n            # These punctuation marks shouldn't end a link\n            end -= 1\n            link = link[:-1]\n        prev_text = text[:best_match.start()]\n        if links:\n            assert not links[-1].tail\n            links[-1].tail = prev_text\n        else:\n            assert not leading_text\n            leading_text = prev_text\n        anchor = factory('a')\n        anchor.set('href', link)\n        body = best_match.group('body')\n        if not body:\n            body = link\n        if body.endswith('.') or body.endswith(','):\n            body = body[:-1]\n        anchor.text = body\n        links.append(anchor)\n        text = text[end:]\n    return leading_text, links\n                \ndef autolink_html(html, *args, **kw):\n    result_type = type(html)\n    if isinstance(html, basestring):\n        doc = fromstring(html)\n    else:\n        doc = copy.deepcopy(html)\n    autolink(doc, *args, **kw)\n    return _transform_result(result_type, doc)\n\nautolink_html.__doc__ = autolink.__doc__\n\n############################################################\n## Word wrapping\n############################################################\n\n_avoid_word_break_elements = ['pre', 'textarea', 'code']\n_avoid_word_break_classes = ['nobreak']\n\ndef word_break(el, max_width=40,\n               avoid_elements=_avoid_word_break_elements,\n               avoid_classes=_avoid_word_break_classes,\n               break_character=unichr(0x200b)):\n    \"\"\"\n    Breaks any long words found in the body of the text (not attributes).\n\n    Doesn't effect any of the tags in avoid_elements, by default\n    ``<textarea>`` and ``<pre>``\n\n    Breaks words by inserting &#8203;, which is a unicode character\n    for Zero Width Space character.  This generally takes up no space\n    in rendering, but does copy as a space, and in monospace contexts\n    usually takes up space.\n\n    See http://www.cs.tut.fi/~jkorpela/html/nobr.html for a discussion\n    \"\"\"\n    # Character suggestion of &#8203 comes from:\n    #   http://www.cs.tut.fi/~jkorpela/html/nobr.html\n    if el.tag in _avoid_word_break_elements:\n        return\n    class_name = el.get('class')\n    if class_name:\n        dont_break = False\n        class_name = class_name.split()\n        for avoid in avoid_classes:\n            if avoid in class_name:\n                dont_break = True\n                break\n        if dont_break:\n            return\n    if el.text:\n        el.text = _break_text(el.text, max_width, break_character)\n    for child in el:\n        word_break(child, max_width=max_width,\n                   avoid_elements=avoid_elements,\n                   avoid_classes=avoid_classes,\n                   break_character=break_character)\n        if child.tail:\n            child.tail = _break_text(child.tail, max_width, break_character)\n\ndef word_break_html(html, *args, **kw):\n    result_type = type(html)\n    doc = fromstring(html)\n    word_break(doc, *args, **kw)\n    return _transform_result(result_type, doc)\n\ndef _break_text(text, max_width, break_character):\n    words = text.split()\n    for word in words:\n        if len(word) > max_width:\n            replacement = _insert_break(word, max_width, break_character)\n            text = text.replace(word, replacement)\n    return text\n\n_break_prefer_re = re.compile(r'[^a-z]', re.I)\n\ndef _insert_break(word, width, break_character):\n    orig_word = word\n    result = ''\n    while len(word) > width:\n        start = word[:width]\n        breaks = list(_break_prefer_re.finditer(start))\n        if breaks:\n            last_break = breaks[-1]\n            # Only walk back up to 10 characters to find a nice break:\n            if last_break.end() > width-10:\n                # FIXME: should the break character be at the end of the\n                # chunk, or the beginning of the next chunk?\n                start = word[:last_break.end()]\n        result += start + break_character\n        word = word[len(start):]\n    result += word\n    return result\n    \n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/defs.py",
    "content": "# FIXME: this should all be confirmed against what a DTD says\n# (probably in a test; this may not match the DTD exactly, but we\n# should document just how it differs).\n\n# Data taken from http://www.w3.org/TR/html401/index/elements.html\n# and http://www.w3.org/community/webed/wiki/HTML/New_HTML5_Elements\n# for html5_tags.\n\nempty_tags = frozenset([\n    'area', 'base', 'basefont', 'br', 'col', 'frame', 'hr',\n    'img', 'input', 'isindex', 'link', 'meta', 'param', 'source', 'track'])\n\ndeprecated_tags = frozenset([\n    'applet', 'basefont', 'center', 'dir', 'font', 'isindex',\n    'menu', 's', 'strike', 'u'])\n\n# archive actually takes a space-separated list of URIs\nlink_attrs = frozenset([\n    'action', 'archive', 'background', 'cite', 'classid',\n    'codebase', 'data', 'href', 'longdesc', 'profile', 'src',\n    'usemap',\n    # Not standard:\n    'dynsrc', 'lowsrc',\n    ])\n\n# Not in the HTML 4 spec:\n# onerror, onresize\nevent_attrs = frozenset([\n    'onblur', 'onchange', 'onclick', 'ondblclick', 'onerror',\n    'onfocus', 'onkeydown', 'onkeypress', 'onkeyup', 'onload',\n    'onmousedown', 'onmousemove', 'onmouseout', 'onmouseover',\n    'onmouseup', 'onreset', 'onresize', 'onselect', 'onsubmit',\n    'onunload',\n    ])\n\nsafe_attrs = frozenset([\n    'abbr', 'accept', 'accept-charset', 'accesskey', 'action', 'align',\n    'alt', 'axis', 'border', 'cellpadding', 'cellspacing', 'char', 'charoff',\n    'charset', 'checked', 'cite', 'class', 'clear', 'cols', 'colspan',\n    'color', 'compact', 'coords', 'datetime', 'dir', 'disabled', 'enctype',\n    'for', 'frame', 'headers', 'height', 'href', 'hreflang', 'hspace', 'id',\n    'ismap', 'label', 'lang', 'longdesc', 'maxlength', 'media', 'method',\n    'multiple', 'name', 'nohref', 'noshade', 'nowrap', 'prompt', 'readonly',\n    'rel', 'rev', 'rows', 'rowspan', 'rules', 'scope', 'selected', 'shape',\n    'size', 'span', 'src', 'start', 'summary', 'tabindex', 'target', 'title',\n    'type', 'usemap', 'valign', 'value', 'vspace', 'width'])\n\n# From http://htmlhelp.com/reference/html40/olist.html\ntop_level_tags = frozenset([\n    'html', 'head', 'body', 'frameset',\n    ])\n\nhead_tags = frozenset([\n    'base', 'isindex', 'link', 'meta', 'script', 'style', 'title',\n    ])\n\ngeneral_block_tags = frozenset([\n    'address',\n    'blockquote',\n    'center',\n    'del',\n    'div',\n    'h1',\n    'h2',\n    'h3',\n    'h4',\n    'h5',\n    'h6',\n    'hr',\n    'ins',\n    'isindex',\n    'noscript',\n    'p',\n    'pre',\n    ])\n\nlist_tags = frozenset([\n    'dir', 'dl', 'dt', 'dd', 'li', 'menu', 'ol', 'ul',\n    ])\n\ntable_tags = frozenset([\n    'table', 'caption', 'colgroup', 'col',\n    'thead', 'tfoot', 'tbody', 'tr', 'td', 'th',\n    ])\n\n# just this one from\n# http://www.georgehernandez.com/h/XComputers/HTML/2BlockLevel.htm\nblock_tags = general_block_tags | list_tags | table_tags | frozenset([\n    # Partial form tags\n    'fieldset', 'form', 'legend', 'optgroup', 'option',\n    ])\n\nform_tags = frozenset([\n    'form', 'button', 'fieldset', 'legend', 'input', 'label',\n    'select', 'optgroup', 'option', 'textarea',\n    ])\n\nspecial_inline_tags = frozenset([\n    'a', 'applet', 'basefont', 'bdo', 'br', 'embed', 'font', 'iframe',\n    'img', 'map', 'area', 'object', 'param', 'q', 'script',\n    'span', 'sub', 'sup',\n    ])\n\nphrase_tags = frozenset([\n    'abbr', 'acronym', 'cite', 'code', 'del', 'dfn', 'em',\n    'ins', 'kbd', 'samp', 'strong', 'var',\n    ])\n\nfont_style_tags = frozenset([\n    'b', 'big', 'i', 's', 'small', 'strike', 'tt', 'u',\n    ])\n\nframe_tags = frozenset([\n    'frameset', 'frame', 'noframes',\n    ])\n    \nhtml5_tags = frozenset([\n    'article', 'aside', 'audio', 'canvas', 'command', 'datalist',\n    'details', 'embed', 'figcaption', 'figure', 'footer', 'header',\n    'hgroup', 'keygen', 'mark', 'math', 'meter', 'nav', 'output',\n    'progress', 'rp', 'rt', 'ruby', 'section', 'source', 'summary',\n    'svg', 'time', 'track', 'video', 'wbr'\n    ])\n\n# These tags aren't standard\nnonstandard_tags = frozenset(['blink', 'marquee'])\n\n\ntags = (top_level_tags | head_tags | general_block_tags | list_tags\n        | table_tags | form_tags | special_inline_tags | phrase_tags\n        | font_style_tags | nonstandard_tags | html5_tags)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/diff.py",
    "content": "# cython: language_level=3\n\nfrom __future__ import absolute_import\n\nimport difflib\nfrom lxml import etree\nfrom lxml.html import fragment_fromstring\nimport re\n\n__all__ = ['html_annotate', 'htmldiff']\n\ntry:\n    from html import escape as html_escape\nexcept ImportError:\n    from cgi import escape as html_escape\ntry:\n    _unicode = unicode\nexcept NameError:\n    # Python 3\n    _unicode = str\ntry:\n    basestring\nexcept NameError:\n    # Python 3\n    basestring = str\n\n############################################################\n## Annotation\n############################################################\n\ndef default_markup(text, version):\n    return '<span title=\"%s\">%s</span>' % (\n        html_escape(_unicode(version), 1), text)\n\ndef html_annotate(doclist, markup=default_markup):\n    \"\"\"\n    doclist should be ordered from oldest to newest, like::\n\n        >>> version1 = 'Hello World'\n        >>> version2 = 'Goodbye World'\n        >>> print(html_annotate([(version1, 'version 1'),\n        ...                      (version2, 'version 2')]))\n        <span title=\"version 2\">Goodbye</span> <span title=\"version 1\">World</span>\n\n    The documents must be *fragments* (str/UTF8 or unicode), not\n    complete documents\n\n    The markup argument is a function to markup the spans of words.\n    This function is called like markup('Hello', 'version 2'), and\n    returns HTML.  The first argument is text and never includes any\n    markup.  The default uses a span with a title:\n\n        >>> print(default_markup('Some Text', 'by Joe'))\n        <span title=\"by Joe\">Some Text</span>\n    \"\"\"\n    # The basic strategy we have is to split the documents up into\n    # logical tokens (which are words with attached markup).  We then\n    # do diffs of each of the versions to track when a token first\n    # appeared in the document; the annotation attached to the token\n    # is the version where it first appeared.\n    tokenlist = [tokenize_annotated(doc, version)\n                 for doc, version in doclist]\n    cur_tokens = tokenlist[0]\n    for tokens in tokenlist[1:]:\n        html_annotate_merge_annotations(cur_tokens, tokens)\n        cur_tokens = tokens\n\n    # After we've tracked all the tokens, we can combine spans of text\n    # that are adjacent and have the same annotation\n    cur_tokens = compress_tokens(cur_tokens)\n    # And finally add markup\n    result = markup_serialize_tokens(cur_tokens, markup)\n    return ''.join(result).strip()\n\ndef tokenize_annotated(doc, annotation): \n    \"\"\"Tokenize a document and add an annotation attribute to each token\n    \"\"\"\n    tokens = tokenize(doc, include_hrefs=False)\n    for tok in tokens: \n        tok.annotation = annotation\n    return tokens\n\ndef html_annotate_merge_annotations(tokens_old, tokens_new): \n    \"\"\"Merge the annotations from tokens_old into tokens_new, when the\n    tokens in the new document already existed in the old document.\n    \"\"\"\n    s = InsensitiveSequenceMatcher(a=tokens_old, b=tokens_new)\n    commands = s.get_opcodes()\n\n    for command, i1, i2, j1, j2 in commands:\n        if command == 'equal': \n            eq_old = tokens_old[i1:i2]\n            eq_new = tokens_new[j1:j2]\n            copy_annotations(eq_old, eq_new)\n\ndef copy_annotations(src, dest): \n    \"\"\"\n    Copy annotations from the tokens listed in src to the tokens in dest\n    \"\"\"\n    assert len(src) == len(dest)\n    for src_tok, dest_tok in zip(src, dest): \n        dest_tok.annotation = src_tok.annotation\n\ndef compress_tokens(tokens):\n    \"\"\"\n    Combine adjacent tokens when there is no HTML between the tokens, \n    and they share an annotation\n    \"\"\"\n    result = [tokens[0]] \n    for tok in tokens[1:]: \n        if (not result[-1].post_tags and \n            not tok.pre_tags and \n            result[-1].annotation == tok.annotation): \n            compress_merge_back(result, tok)\n        else: \n            result.append(tok)\n    return result\n\ndef compress_merge_back(tokens, tok): \n    \"\"\" Merge tok into the last element of tokens (modifying the list of\n    tokens in-place).  \"\"\"\n    last = tokens[-1]\n    if type(last) is not token or type(tok) is not token: \n        tokens.append(tok)\n    else:\n        text = _unicode(last)\n        if last.trailing_whitespace:\n            text += last.trailing_whitespace\n        text += tok\n        merged = token(text,\n                       pre_tags=last.pre_tags,\n                       post_tags=tok.post_tags,\n                       trailing_whitespace=tok.trailing_whitespace)\n        merged.annotation = last.annotation\n        tokens[-1] = merged\n    \ndef markup_serialize_tokens(tokens, markup_func):\n    \"\"\"\n    Serialize the list of tokens into a list of text chunks, calling\n    markup_func around text to add annotations.\n    \"\"\"\n    for token in tokens:\n        for pre in token.pre_tags:\n            yield pre\n        html = token.html()\n        html = markup_func(html, token.annotation)\n        if token.trailing_whitespace:\n            html += token.trailing_whitespace\n        yield html\n        for post in token.post_tags:\n            yield post\n\n\n############################################################\n## HTML Diffs\n############################################################\n\ndef htmldiff(old_html, new_html):\n    ## FIXME: this should take parsed documents too, and use their body\n    ## or other content.\n    \"\"\" Do a diff of the old and new document.  The documents are HTML\n    *fragments* (str/UTF8 or unicode), they are not complete documents\n    (i.e., no <html> tag).\n\n    Returns HTML with <ins> and <del> tags added around the\n    appropriate text.  \n\n    Markup is generally ignored, with the markup from new_html\n    preserved, and possibly some markup from old_html (though it is\n    considered acceptable to lose some of the old markup).  Only the\n    words in the HTML are diffed.  The exception is <img> tags, which\n    are treated like words, and the href attribute of <a> tags, which\n    are noted inside the tag itself when there are changes.\n    \"\"\" \n    old_html_tokens = tokenize(old_html)\n    new_html_tokens = tokenize(new_html)\n    result = htmldiff_tokens(old_html_tokens, new_html_tokens)\n    result = ''.join(result).strip()\n    return fixup_ins_del_tags(result)\n\ndef htmldiff_tokens(html1_tokens, html2_tokens):\n    \"\"\" Does a diff on the tokens themselves, returning a list of text\n    chunks (not tokens).\n    \"\"\"\n    # There are several passes as we do the differences.  The tokens\n    # isolate the portion of the content we care to diff; difflib does\n    # all the actual hard work at that point.  \n    #\n    # Then we must create a valid document from pieces of both the old\n    # document and the new document.  We generally prefer to take\n    # markup from the new document, and only do a best effort attempt\n    # to keep markup from the old document; anything that we can't\n    # resolve we throw away.  Also we try to put the deletes as close\n    # to the location where we think they would have been -- because\n    # we are only keeping the markup from the new document, it can be\n    # fuzzy where in the new document the old text would have gone.\n    # Again we just do a best effort attempt.\n    s = InsensitiveSequenceMatcher(a=html1_tokens, b=html2_tokens)\n    commands = s.get_opcodes()\n    result = []\n    for command, i1, i2, j1, j2 in commands:\n        if command == 'equal':\n            result.extend(expand_tokens(html2_tokens[j1:j2], equal=True))\n            continue\n        if command == 'insert' or command == 'replace':\n            ins_tokens = expand_tokens(html2_tokens[j1:j2])\n            merge_insert(ins_tokens, result)\n        if command == 'delete' or command == 'replace':\n            del_tokens = expand_tokens(html1_tokens[i1:i2])\n            merge_delete(del_tokens, result)\n    # If deletes were inserted directly as <del> then we'd have an\n    # invalid document at this point.  Instead we put in special\n    # markers, and when the complete diffed document has been created\n    # we try to move the deletes around and resolve any problems.\n    result = cleanup_delete(result)\n\n    return result\n\ndef expand_tokens(tokens, equal=False):\n    \"\"\"Given a list of tokens, return a generator of the chunks of\n    text for the data in the tokens.\n    \"\"\"\n    for token in tokens:\n        for pre in token.pre_tags:\n            yield pre\n        if not equal or not token.hide_when_equal:\n            if token.trailing_whitespace:\n                yield token.html() + token.trailing_whitespace\n            else:\n                yield token.html()\n        for post in token.post_tags:\n            yield post\n\ndef merge_insert(ins_chunks, doc):\n    \"\"\" doc is the already-handled document (as a list of text chunks);\n    here we add <ins>ins_chunks</ins> to the end of that.  \"\"\"\n    # Though we don't throw away unbalanced_start or unbalanced_end\n    # (we assume there is accompanying markup later or earlier in the\n    # document), we only put <ins> around the balanced portion.\n    unbalanced_start, balanced, unbalanced_end = split_unbalanced(ins_chunks)\n    doc.extend(unbalanced_start)\n    if doc and not doc[-1].endswith(' '):\n        # Fix up the case where the word before the insert didn't end with \n        # a space\n        doc[-1] += ' '\n    doc.append('<ins>')\n    if balanced and balanced[-1].endswith(' '):\n        # We move space outside of </ins>\n        balanced[-1] = balanced[-1][:-1]\n    doc.extend(balanced)\n    doc.append('</ins> ')\n    doc.extend(unbalanced_end)\n\n# These are sentinals to represent the start and end of a <del>\n# segment, until we do the cleanup phase to turn them into proper\n# markup:\nclass DEL_START:\n    pass\nclass DEL_END:\n    pass\n\nclass NoDeletes(Exception):\n    \"\"\" Raised when the document no longer contains any pending deletes\n    (DEL_START/DEL_END) \"\"\"\n\ndef merge_delete(del_chunks, doc):\n    \"\"\" Adds the text chunks in del_chunks to the document doc (another\n    list of text chunks) with marker to show it is a delete.\n    cleanup_delete later resolves these markers into <del> tags.\"\"\"\n    doc.append(DEL_START)\n    doc.extend(del_chunks)\n    doc.append(DEL_END)\n\ndef cleanup_delete(chunks):\n    \"\"\" Cleans up any DEL_START/DEL_END markers in the document, replacing\n    them with <del></del>.  To do this while keeping the document\n    valid, it may need to drop some tags (either start or end tags).\n\n    It may also move the del into adjacent tags to try to move it to a\n    similar location where it was originally located (e.g., moving a\n    delete into preceding <div> tag, if the del looks like (DEL_START,\n    'Text</div>', DEL_END)\"\"\"\n    while 1:\n        # Find a pending DEL_START/DEL_END, splitting the document\n        # into stuff-preceding-DEL_START, stuff-inside, and\n        # stuff-following-DEL_END\n        try:\n            pre_delete, delete, post_delete = split_delete(chunks)\n        except NoDeletes:\n            # Nothing found, we've cleaned up the entire doc\n            break\n        # The stuff-inside-DEL_START/END may not be well balanced\n        # markup.  First we figure out what unbalanced portions there are:\n        unbalanced_start, balanced, unbalanced_end = split_unbalanced(delete)\n        # Then we move the span forward and/or backward based on these\n        # unbalanced portions:\n        locate_unbalanced_start(unbalanced_start, pre_delete, post_delete)\n        locate_unbalanced_end(unbalanced_end, pre_delete, post_delete)\n        doc = pre_delete\n        if doc and not doc[-1].endswith(' '):\n            # Fix up case where the word before us didn't have a trailing space\n            doc[-1] += ' '\n        doc.append('<del>')\n        if balanced and balanced[-1].endswith(' '):\n            # We move space outside of </del>\n            balanced[-1] = balanced[-1][:-1]\n        doc.extend(balanced)\n        doc.append('</del> ')\n        doc.extend(post_delete)\n        chunks = doc\n    return chunks\n\ndef split_unbalanced(chunks):\n    \"\"\"Return (unbalanced_start, balanced, unbalanced_end), where each is\n    a list of text and tag chunks.\n\n    unbalanced_start is a list of all the tags that are opened, but\n    not closed in this span.  Similarly, unbalanced_end is a list of\n    tags that are closed but were not opened.  Extracting these might\n    mean some reordering of the chunks.\"\"\"\n    start = []\n    end = []\n    tag_stack = []\n    balanced = []\n    for chunk in chunks:\n        if not chunk.startswith('<'):\n            balanced.append(chunk)\n            continue\n        endtag = chunk[1] == '/'\n        name = chunk.split()[0].strip('<>/')\n        if name in empty_tags:\n            balanced.append(chunk)\n            continue\n        if endtag:\n            if tag_stack and tag_stack[-1][0] == name:\n                balanced.append(chunk)\n                name, pos, tag = tag_stack.pop()\n                balanced[pos] = tag\n            elif tag_stack:\n                start.extend([tag for name, pos, tag in tag_stack])\n                tag_stack = []\n                end.append(chunk)\n            else:\n                end.append(chunk)\n        else:\n            tag_stack.append((name, len(balanced), chunk))\n            balanced.append(None)\n    start.extend(\n        [chunk for name, pos, chunk in tag_stack])\n    balanced = [chunk for chunk in balanced if chunk is not None]\n    return start, balanced, end\n\ndef split_delete(chunks):\n    \"\"\" Returns (stuff_before_DEL_START, stuff_inside_DEL_START_END,\n    stuff_after_DEL_END).  Returns the first case found (there may be\n    more DEL_STARTs in stuff_after_DEL_END).  Raises NoDeletes if\n    there's no DEL_START found. \"\"\"\n    try:\n        pos = chunks.index(DEL_START)\n    except ValueError:\n        raise NoDeletes\n    pos2 = chunks.index(DEL_END)\n    return chunks[:pos], chunks[pos+1:pos2], chunks[pos2+1:]\n\ndef locate_unbalanced_start(unbalanced_start, pre_delete, post_delete):\n    \"\"\" pre_delete and post_delete implicitly point to a place in the\n    document (where the two were split).  This moves that point (by\n    popping items from one and pushing them onto the other).  It moves\n    the point to try to find a place where unbalanced_start applies.\n\n    As an example::\n\n        >>> unbalanced_start = ['<div>']\n        >>> doc = ['<p>', 'Text', '</p>', '<div>', 'More Text', '</div>']\n        >>> pre, post = doc[:3], doc[3:]\n        >>> pre, post\n        (['<p>', 'Text', '</p>'], ['<div>', 'More Text', '</div>'])\n        >>> locate_unbalanced_start(unbalanced_start, pre, post)\n        >>> pre, post\n        (['<p>', 'Text', '</p>', '<div>'], ['More Text', '</div>'])\n\n    As you can see, we moved the point so that the dangling <div> that\n    we found will be effectively replaced by the div in the original\n    document.  If this doesn't work out, we just throw away\n    unbalanced_start without doing anything.\n    \"\"\"\n    while 1:\n        if not unbalanced_start:\n            # We have totally succeeded in finding the position\n            break\n        finding = unbalanced_start[0]\n        finding_name = finding.split()[0].strip('<>')\n        if not post_delete:\n            break\n        next = post_delete[0]\n        if next is DEL_START or not next.startswith('<'):\n            # Reached a word, we can't move the delete text forward\n            break\n        if next[1] == '/':\n            # Reached a closing tag, can we go further?  Maybe not...\n            break\n        name = next.split()[0].strip('<>')\n        if name == 'ins':\n            # Can't move into an insert\n            break\n        assert name != 'del', (\n            \"Unexpected delete tag: %r\" % next)\n        if name == finding_name:\n            unbalanced_start.pop(0)\n            pre_delete.append(post_delete.pop(0))\n        else:\n            # Found a tag that doesn't match\n            break\n\ndef locate_unbalanced_end(unbalanced_end, pre_delete, post_delete):\n    \"\"\" like locate_unbalanced_start, except handling end tags and\n    possibly moving the point earlier in the document.  \"\"\"\n    while 1:\n        if not unbalanced_end:\n            # Success\n            break\n        finding = unbalanced_end[-1]\n        finding_name = finding.split()[0].strip('<>/')\n        if not pre_delete:\n            break\n        next = pre_delete[-1]\n        if next is DEL_END or not next.startswith('</'):\n            # A word or a start tag\n            break\n        name = next.split()[0].strip('<>/')\n        if name == 'ins' or name == 'del':\n            # Can't move into an insert or delete\n            break\n        if name == finding_name:\n            unbalanced_end.pop()\n            post_delete.insert(0, pre_delete.pop())\n        else:\n            # Found a tag that doesn't match\n            break\n\nclass token(_unicode):\n    \"\"\" Represents a diffable token, generally a word that is displayed to\n    the user.  Opening tags are attached to this token when they are\n    adjacent (pre_tags) and closing tags that follow the word\n    (post_tags).  Some exceptions occur when there are empty tags\n    adjacent to a word, so there may be close tags in pre_tags, or\n    open tags in post_tags.\n\n    We also keep track of whether the word was originally followed by\n    whitespace, even though we do not want to treat the word as\n    equivalent to a similar word that does not have a trailing\n    space.\"\"\"\n\n    # When this is true, the token will be eliminated from the\n    # displayed diff if no change has occurred:\n    hide_when_equal = False\n\n    def __new__(cls, text, pre_tags=None, post_tags=None, trailing_whitespace=\"\"):\n        obj = _unicode.__new__(cls, text)\n\n        if pre_tags is not None:\n            obj.pre_tags = pre_tags\n        else:\n            obj.pre_tags = []\n\n        if post_tags is not None:\n            obj.post_tags = post_tags\n        else:\n            obj.post_tags = []\n\n        obj.trailing_whitespace = trailing_whitespace\n\n        return obj\n\n    def __repr__(self):\n        return 'token(%s, %r, %r, %r)' % (_unicode.__repr__(self), self.pre_tags,\n                                          self.post_tags, self.trailing_whitespace)\n\n    def html(self):\n        return _unicode(self)\n\nclass tag_token(token):\n\n    \"\"\" Represents a token that is actually a tag.  Currently this is just\n    the <img> tag, which takes up visible space just like a word but\n    is only represented in a document by a tag.  \"\"\"\n\n    def __new__(cls, tag, data, html_repr, pre_tags=None, \n                post_tags=None, trailing_whitespace=\"\"):\n        obj = token.__new__(cls, \"%s: %s\" % (type, data), \n                            pre_tags=pre_tags, \n                            post_tags=post_tags, \n                            trailing_whitespace=trailing_whitespace)\n        obj.tag = tag\n        obj.data = data\n        obj.html_repr = html_repr\n        return obj\n\n    def __repr__(self):\n        return 'tag_token(%s, %s, html_repr=%s, post_tags=%r, pre_tags=%r, trailing_whitespace=%r)' % (\n            self.tag, \n            self.data, \n            self.html_repr, \n            self.pre_tags, \n            self.post_tags, \n            self.trailing_whitespace)\n    def html(self):\n        return self.html_repr\n\nclass href_token(token):\n\n    \"\"\" Represents the href in an anchor tag.  Unlike other words, we only\n    show the href when it changes.  \"\"\"\n\n    hide_when_equal = True\n\n    def html(self):\n        return ' Link: %s' % self\n\ndef tokenize(html, include_hrefs=True):\n    \"\"\"\n    Parse the given HTML and returns token objects (words with attached tags).\n\n    This parses only the content of a page; anything in the head is\n    ignored, and the <head> and <body> elements are themselves\n    optional.  The content is then parsed by lxml, which ensures the\n    validity of the resulting parsed document (though lxml may make\n    incorrect guesses when the markup is particular bad).\n\n    <ins> and <del> tags are also eliminated from the document, as\n    that gets confusing.\n\n    If include_hrefs is true, then the href attribute of <a> tags is\n    included as a special kind of diffable token.\"\"\"\n    if etree.iselement(html):\n        body_el = html\n    else:\n        body_el = parse_html(html, cleanup=True)\n    # Then we split the document into text chunks for each tag, word, and end tag:\n    chunks = flatten_el(body_el, skip_tag=True, include_hrefs=include_hrefs)\n    # Finally re-joining them into token objects:\n    return fixup_chunks(chunks)\n\ndef parse_html(html, cleanup=True):\n    \"\"\"\n    Parses an HTML fragment, returning an lxml element.  Note that the HTML will be\n    wrapped in a <div> tag that was not in the original document.\n\n    If cleanup is true, make sure there's no <head> or <body>, and get\n    rid of any <ins> and <del> tags.\n    \"\"\"\n    if cleanup:\n        # This removes any extra markup or structure like <head>:\n        html = cleanup_html(html)\n    return fragment_fromstring(html, create_parent=True)\n\n_body_re = re.compile(r'<body.*?>', re.I|re.S)\n_end_body_re = re.compile(r'</body.*?>', re.I|re.S)\n_ins_del_re = re.compile(r'</?(ins|del).*?>', re.I|re.S)\n\ndef cleanup_html(html):\n    \"\"\" This 'cleans' the HTML, meaning that any page structure is removed\n    (only the contents of <body> are used, if there is any <body).\n    Also <ins> and <del> tags are removed.  \"\"\"\n    match = _body_re.search(html)\n    if match:\n        html = html[match.end():]\n    match = _end_body_re.search(html)\n    if match:\n        html = html[:match.start()]\n    html = _ins_del_re.sub('', html)\n    return html\n    \n\nend_whitespace_re = re.compile(r'[ \\t\\n\\r]$')\n\ndef split_trailing_whitespace(word):\n    \"\"\"\n    This function takes a word, such as 'test\\n\\n' and returns ('test','\\n\\n')\n    \"\"\"\n    stripped_length = len(word.rstrip())\n    return word[0:stripped_length], word[stripped_length:]\n\n\ndef fixup_chunks(chunks):\n    \"\"\"\n    This function takes a list of chunks and produces a list of tokens.\n    \"\"\"\n    tag_accum = []\n    cur_word = None\n    result = []\n    for chunk in chunks:\n        if isinstance(chunk, tuple):\n            if chunk[0] == 'img':\n                src = chunk[1]\n                tag, trailing_whitespace = split_trailing_whitespace(chunk[2])\n                cur_word = tag_token('img', src, html_repr=tag,\n                                     pre_tags=tag_accum,\n                                     trailing_whitespace=trailing_whitespace)\n                tag_accum = []\n                result.append(cur_word)\n\n            elif chunk[0] == 'href':\n                href = chunk[1]\n                cur_word = href_token(href, pre_tags=tag_accum, trailing_whitespace=\" \")\n                tag_accum = []\n                result.append(cur_word)\n            continue\n\n        if is_word(chunk):\n            chunk, trailing_whitespace = split_trailing_whitespace(chunk)\n            cur_word = token(chunk, pre_tags=tag_accum, trailing_whitespace=trailing_whitespace)\n            tag_accum = []\n            result.append(cur_word)\n\n        elif is_start_tag(chunk):\n            tag_accum.append(chunk)\n\n        elif is_end_tag(chunk):\n            if tag_accum:\n                tag_accum.append(chunk)\n            else:\n                assert cur_word, (\n                    \"Weird state, cur_word=%r, result=%r, chunks=%r of %r\"\n                    % (cur_word, result, chunk, chunks))\n                cur_word.post_tags.append(chunk)\n        else:\n            assert False\n\n    if not result:\n        return [token('', pre_tags=tag_accum)]\n    else:\n        result[-1].post_tags.extend(tag_accum)\n\n    return result\n\n\n# All the tags in HTML that don't require end tags:\nempty_tags = (\n    'param', 'img', 'area', 'br', 'basefont', 'input',\n    'base', 'meta', 'link', 'col')\n\nblock_level_tags = (\n    'address',\n    'blockquote',\n    'center',\n    'dir',\n    'div',\n    'dl',\n    'fieldset',\n    'form',\n    'h1',\n    'h2',\n    'h3',\n    'h4',\n    'h5',\n    'h6',\n    'hr',\n    'isindex',\n    'menu',\n    'noframes',\n    'noscript',\n    'ol',\n    'p',\n    'pre',\n    'table',\n    'ul',\n    )\n\nblock_level_container_tags = (\n    'dd',\n    'dt',\n    'frameset',\n    'li',\n    'tbody',\n    'td',\n    'tfoot',\n    'th',\n    'thead',\n    'tr',\n    )\n\n\ndef flatten_el(el, include_hrefs, skip_tag=False):\n    \"\"\" Takes an lxml element el, and generates all the text chunks for\n    that tag.  Each start tag is a chunk, each word is a chunk, and each\n    end tag is a chunk.\n\n    If skip_tag is true, then the outermost container tag is\n    not returned (just its contents).\"\"\"\n    if not skip_tag:\n        if el.tag == 'img':\n            yield ('img', el.get('src'), start_tag(el))\n        else:\n            yield start_tag(el)\n    if el.tag in empty_tags and not el.text and not len(el) and not el.tail:\n        return\n    start_words = split_words(el.text)\n    for word in start_words:\n        yield html_escape(word)\n    for child in el:\n        for item in flatten_el(child, include_hrefs=include_hrefs):\n            yield item\n    if el.tag == 'a' and el.get('href') and include_hrefs:\n        yield ('href', el.get('href'))\n    if not skip_tag:\n        yield end_tag(el)\n        end_words = split_words(el.tail)\n        for word in end_words:\n            yield html_escape(word)\n\nsplit_words_re = re.compile(r'\\S+(?:\\s+|$)', re.U)\n\ndef split_words(text):\n    \"\"\" Splits some text into words. Includes trailing whitespace\n    on each word when appropriate.  \"\"\"\n    if not text or not text.strip():\n        return []\n\n    words = split_words_re.findall(text)\n    return words\n\nstart_whitespace_re = re.compile(r'^[ \\t\\n\\r]')\n\ndef start_tag(el):\n    \"\"\"\n    The text representation of the start tag for a tag.\n    \"\"\"\n    return '<%s%s>' % (\n        el.tag, ''.join([' %s=\"%s\"' % (name, html_escape(value, True))\n                         for name, value in el.attrib.items()]))\n\ndef end_tag(el):\n    \"\"\" The text representation of an end tag for a tag.  Includes\n    trailing whitespace when appropriate.  \"\"\"\n    if el.tail and start_whitespace_re.search(el.tail):\n        extra = ' '\n    else:\n        extra = ''\n    return '</%s>%s' % (el.tag, extra)\n\ndef is_word(tok):\n    return not tok.startswith('<')\n\ndef is_end_tag(tok):\n    return tok.startswith('</')\n\ndef is_start_tag(tok):\n    return tok.startswith('<') and not tok.startswith('</')\n\ndef fixup_ins_del_tags(html):\n    \"\"\" Given an html string, move any <ins> or <del> tags inside of any\n    block-level elements, e.g. transform <ins><p>word</p></ins> to\n    <p><ins>word</ins></p> \"\"\"\n    doc = parse_html(html, cleanup=False)\n    _fixup_ins_del_tags(doc)\n    html = serialize_html_fragment(doc, skip_outer=True)\n    return html\n\ndef serialize_html_fragment(el, skip_outer=False):\n    \"\"\" Serialize a single lxml element as HTML.  The serialized form\n    includes the elements tail.  \n\n    If skip_outer is true, then don't serialize the outermost tag\n    \"\"\"\n    assert not isinstance(el, basestring), (\n        \"You should pass in an element, not a string like %r\" % el)\n    html = etree.tostring(el, method=\"html\", encoding=_unicode)\n    if skip_outer:\n        # Get rid of the extra starting tag:\n        html = html[html.find('>')+1:]\n        # Get rid of the extra end tag:\n        html = html[:html.rfind('<')]\n        return html.strip()\n    else:\n        return html\n\ndef _fixup_ins_del_tags(doc):\n    \"\"\"fixup_ins_del_tags that works on an lxml document in-place\n    \"\"\"\n    for tag in ['ins', 'del']:\n        for el in doc.xpath('descendant-or-self::%s' % tag):\n            if not _contains_block_level_tag(el):\n                continue\n            _move_el_inside_block(el, tag=tag)\n            el.drop_tag()\n            #_merge_element_contents(el)\n\ndef _contains_block_level_tag(el):\n    \"\"\"True if the element contains any block-level elements, like <p>, <td>, etc.\n    \"\"\"\n    if el.tag in block_level_tags or el.tag in block_level_container_tags:\n        return True\n    for child in el:\n        if _contains_block_level_tag(child):\n            return True\n    return False\n\ndef _move_el_inside_block(el, tag):\n    \"\"\" helper for _fixup_ins_del_tags; actually takes the <ins> etc tags\n    and moves them inside any block-level tags.  \"\"\"\n    for child in el:\n        if _contains_block_level_tag(child):\n            break\n    else:\n        # No block-level tags in any child\n        children_tag = etree.Element(tag)\n        children_tag.text = el.text\n        el.text = None\n        children_tag.extend(list(el))\n        el[:] = [children_tag]\n        return\n    for child in list(el):\n        if _contains_block_level_tag(child):\n            _move_el_inside_block(child, tag)\n            if child.tail:\n                tail_tag = etree.Element(tag)\n                tail_tag.text = child.tail\n                child.tail = None\n                el.insert(el.index(child)+1, tail_tag)\n        else:\n            child_tag = etree.Element(tag)\n            el.replace(child, child_tag)\n            child_tag.append(child)\n    if el.text:\n        text_tag = etree.Element(tag)\n        text_tag.text = el.text\n        el.text = None\n        el.insert(0, text_tag)\n            \ndef _merge_element_contents(el):\n    \"\"\"\n    Removes an element, but merges its contents into its place, e.g.,\n    given <p>Hi <i>there!</i></p>, if you remove the <i> element you get\n    <p>Hi there!</p>\n    \"\"\"\n    parent = el.getparent()\n    text = el.text or ''\n    if el.tail:\n        if not len(el):\n            text += el.tail\n        else:\n            if el[-1].tail:\n                el[-1].tail += el.tail\n            else:\n                el[-1].tail = el.tail\n    index = parent.index(el)\n    if text:\n        if index == 0:\n            previous = None\n        else:\n            previous = parent[index-1]\n        if previous is None:\n            if parent.text:\n                parent.text += text\n            else:\n                parent.text = text\n        else:\n            if previous.tail:\n                previous.tail += text\n            else:\n                previous.tail = text\n    parent[index:index+1] = el.getchildren()\n\nclass InsensitiveSequenceMatcher(difflib.SequenceMatcher):\n    \"\"\"\n    Acts like SequenceMatcher, but tries not to find very small equal\n    blocks amidst large spans of changes\n    \"\"\"\n\n    threshold = 2\n    \n    def get_matching_blocks(self):\n        size = min(len(self.b), len(self.b))\n        threshold = min(self.threshold, size / 4)\n        actual = difflib.SequenceMatcher.get_matching_blocks(self)\n        return [item for item in actual\n                if item[2] > threshold\n                or not item[2]]\n\nif __name__ == '__main__':\n    from lxml.html import _diffcommand\n    _diffcommand.main()\n    \n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/formfill.py",
    "content": "from lxml.etree import XPath, ElementBase\nfrom lxml.html import fromstring, XHTML_NAMESPACE\nfrom lxml.html import _forms_xpath, _options_xpath, _nons, _transform_result\nfrom lxml.html import defs\nimport copy\n\ntry:\n    basestring\nexcept NameError:\n    # Python 3\n    basestring = str\n\n__all__ = ['FormNotFound', 'fill_form', 'fill_form_html',\n           'insert_errors', 'insert_errors_html',\n           'DefaultErrorCreator']\n\nclass FormNotFound(LookupError):\n    \"\"\"\n    Raised when no form can be found\n    \"\"\"\n\n_form_name_xpath = XPath('descendant-or-self::form[name=$name]|descendant-or-self::x:form[name=$name]', namespaces={'x':XHTML_NAMESPACE})\n_input_xpath = XPath('|'.join(['descendant-or-self::'+_tag for _tag in ('input','select','textarea','x:input','x:select','x:textarea')]),\n                               namespaces={'x':XHTML_NAMESPACE})\n_label_for_xpath = XPath('//label[@for=$for_id]|//x:label[@for=$for_id]',\n                               namespaces={'x':XHTML_NAMESPACE})\n_name_xpath = XPath('descendant-or-self::*[@name=$name]')\n\ndef fill_form(\n    el,\n    values,\n    form_id=None,\n    form_index=None,\n    ):\n    el = _find_form(el, form_id=form_id, form_index=form_index)\n    _fill_form(el, values)\n\ndef fill_form_html(html, values, form_id=None, form_index=None):\n    result_type = type(html)\n    if isinstance(html, basestring):\n        doc = fromstring(html)\n    else:\n        doc = copy.deepcopy(html)\n    fill_form(doc, values, form_id=form_id, form_index=form_index)\n    return _transform_result(result_type, doc)\n\ndef _fill_form(el, values):\n    counts = {}\n    if hasattr(values, 'mixed'):\n        # For Paste request parameters\n        values = values.mixed()\n    inputs = _input_xpath(el)\n    for input in inputs:\n        name = input.get('name')\n        if not name:\n            continue\n        if _takes_multiple(input):\n            value = values.get(name, [])\n            if not isinstance(value, (list, tuple)):\n                value = [value]\n            _fill_multiple(input, value)\n        elif name not in values:\n            continue\n        else:\n            index = counts.get(name, 0)\n            counts[name] = index + 1\n            value = values[name]\n            if isinstance(value, (list, tuple)):\n                try:\n                    value = value[index]\n                except IndexError:\n                    continue\n            elif index > 0:\n                continue\n            _fill_single(input, value)\n\ndef _takes_multiple(input):\n    if _nons(input.tag) == 'select' and input.get('multiple'):\n        # FIXME: multiple=\"0\"?\n        return True\n    type = input.get('type', '').lower()\n    if type in ('radio', 'checkbox'):\n        return True\n    return False\n\ndef _fill_multiple(input, value):\n    type = input.get('type', '').lower()\n    if type == 'checkbox':\n        v = input.get('value')\n        if v is None:\n            if not value:\n                result = False\n            else:\n                result = value[0]\n                if isinstance(value, basestring):\n                    # The only valid \"on\" value for an unnamed checkbox is 'on'\n                    result = result == 'on'\n            _check(input, result)\n        else:\n            _check(input, v in value)\n    elif type == 'radio':\n        v = input.get('value')\n        _check(input, v in value)\n    else:\n        assert _nons(input.tag) == 'select'\n        for option in _options_xpath(input):\n            v = option.get('value')\n            if v is None:\n                # This seems to be the default, at least on IE\n                # FIXME: but I'm not sure\n                v = option.text_content()\n            _select(option, v in value)\n\ndef _check(el, check):\n    if check:\n        el.set('checked', '')\n    else:\n        if 'checked' in el.attrib:\n            del el.attrib['checked']\n\ndef _select(el, select):\n    if select:\n        el.set('selected', '')\n    else:\n        if 'selected' in el.attrib:\n            del el.attrib['selected']\n\ndef _fill_single(input, value):\n    if _nons(input.tag) == 'textarea':\n        input.text = value\n    else:\n        input.set('value', value)\n\ndef _find_form(el, form_id=None, form_index=None):\n    if form_id is None and form_index is None:\n        forms = _forms_xpath(el)\n        for form in forms:\n            return form\n        raise FormNotFound(\n            \"No forms in page\")\n    if form_id is not None:\n        form = el.get_element_by_id(form_id)\n        if form is not None:\n            return form\n        forms = _form_name_xpath(el, name=form_id)\n        if forms:\n            return forms[0]\n        else:\n            raise FormNotFound(\n                \"No form with the name or id of %r (forms: %s)\"\n                % (id, ', '.join(_find_form_ids(el))))               \n    if form_index is not None:\n        forms = _forms_xpath(el)\n        try:\n            return forms[form_index]\n        except IndexError:\n            raise FormNotFound(\n                \"There is no form with the index %r (%i forms found)\"\n                % (form_index, len(forms)))\n\ndef _find_form_ids(el):\n    forms = _forms_xpath(el)\n    if not forms:\n        yield '(no forms)'\n        return\n    for index, form in enumerate(forms):\n        if form.get('id'):\n            if form.get('name'):\n                yield '%s or %s' % (form.get('id'),\n                                     form.get('name'))\n            else:\n                yield form.get('id')\n        elif form.get('name'):\n            yield form.get('name')\n        else:\n            yield '(unnamed form %s)' % index\n\n############################################################\n## Error filling\n############################################################\n\nclass DefaultErrorCreator(object):\n    insert_before = True\n    block_inside = True\n    error_container_tag = 'div'\n    error_message_class = 'error-message'\n    error_block_class = 'error-block'\n    default_message = \"Invalid\"\n\n    def __init__(self, **kw):\n        for name, value in kw.items():\n            if not hasattr(self, name):\n                raise TypeError(\n                    \"Unexpected keyword argument: %s\" % name)\n            setattr(self, name, value)\n\n    def __call__(self, el, is_block, message):\n        error_el = el.makeelement(self.error_container_tag)\n        if self.error_message_class:\n            error_el.set('class', self.error_message_class)\n        if is_block and self.error_block_class:\n            error_el.set('class', error_el.get('class', '')+' '+self.error_block_class)\n        if message is None or message == '':\n            message = self.default_message\n        if isinstance(message, ElementBase):\n            error_el.append(message)\n        else:\n            assert isinstance(message, basestring), (\n                \"Bad message; should be a string or element: %r\" % message)\n            error_el.text = message or self.default_message\n        if is_block and self.block_inside:\n            if self.insert_before:\n                error_el.tail = el.text\n                el.text = None\n                el.insert(0, error_el)\n            else:\n                el.append(error_el)\n        else:\n            parent = el.getparent()\n            pos = parent.index(el)\n            if self.insert_before:\n                parent.insert(pos, error_el)\n            else:\n                error_el.tail = el.tail\n                el.tail = None\n                parent.insert(pos+1, error_el)\n\ndefault_error_creator = DefaultErrorCreator()\n    \n\ndef insert_errors(\n    el,\n    errors,\n    form_id=None,\n    form_index=None,\n    error_class=\"error\",\n    error_creator=default_error_creator,\n    ):\n    el = _find_form(el, form_id=form_id, form_index=form_index)\n    for name, error in errors.items():\n        if error is None:\n            continue\n        for error_el, message in _find_elements_for_name(el, name, error):\n            assert isinstance(message, (basestring, type(None), ElementBase)), (\n                \"Bad message: %r\" % message)\n            _insert_error(error_el, message, error_class, error_creator)\n\ndef insert_errors_html(html, values, **kw):\n    result_type = type(html)\n    if isinstance(html, basestring):\n        doc = fromstring(html)\n    else:\n        doc = copy.deepcopy(html)\n    insert_errors(doc, values, **kw)\n    return _transform_result(result_type, doc)\n\ndef _insert_error(el, error, error_class, error_creator):\n    if _nons(el.tag) in defs.empty_tags or _nons(el.tag) == 'textarea':\n        is_block = False\n    else:\n        is_block = True\n    if _nons(el.tag) != 'form' and error_class:\n        _add_class(el, error_class)\n    if el.get('id'):\n        labels = _label_for_xpath(el, for_id=el.get('id'))\n        if labels:\n            for label in labels:\n                _add_class(label, error_class)\n    error_creator(el, is_block, error)\n\ndef _add_class(el, class_name):\n    if el.get('class'):\n        el.set('class', el.get('class')+' '+class_name)\n    else:\n        el.set('class', class_name)\n\ndef _find_elements_for_name(form, name, error):\n    if name is None:\n        # An error for the entire form\n        yield form, error\n        return\n    if name.startswith('#'):\n        # By id\n        el = form.get_element_by_id(name[1:])\n        if el is not None:\n            yield el, error\n        return\n    els = _name_xpath(form, name=name)\n    if not els:\n        # FIXME: should this raise an exception?\n        return\n    if not isinstance(error, (list, tuple)):\n        yield els[0], error\n        return\n    # FIXME: if error is longer than els, should it raise an error?\n    for el, err in zip(els, error):\n        if err is None:\n            continue\n        yield el, err\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/html5parser.py",
    "content": "\"\"\"\nAn interface to html5lib that mimics the lxml.html interface.\n\"\"\"\nimport sys\nimport string\n\nfrom html5lib import HTMLParser as _HTMLParser\nfrom html5lib.treebuilders.etree_lxml import TreeBuilder\nfrom lxml import etree\nfrom lxml.html import Element, XHTML_NAMESPACE, _contains_block_level_tag\n\n# python3 compatibility\ntry:\n    _strings = basestring\nexcept NameError:\n    _strings = (bytes, str)\ntry:\n    from urllib2 import urlopen\nexcept ImportError:\n    from urllib.request import urlopen\ntry:\n    from urlparse import urlparse\nexcept ImportError:\n    from urllib.parse import urlparse\n\n\nclass HTMLParser(_HTMLParser):\n    \"\"\"An html5lib HTML parser with lxml as tree.\"\"\"\n\n    def __init__(self, strict=False, **kwargs):\n        _HTMLParser.__init__(self, strict=strict, tree=TreeBuilder, **kwargs)\n\n\ntry:\n    from html5lib import XHTMLParser as _XHTMLParser\nexcept ImportError:\n    pass\nelse:\n    class XHTMLParser(_XHTMLParser):\n        \"\"\"An html5lib XHTML Parser with lxml as tree.\"\"\"\n\n        def __init__(self, strict=False, **kwargs):\n            _XHTMLParser.__init__(self, strict=strict, tree=TreeBuilder, **kwargs)\n\n    xhtml_parser = XHTMLParser()\n\n\ndef _find_tag(tree, tag):\n    elem = tree.find(tag)\n    if elem is not None:\n        return elem\n    return tree.find('{%s}%s' % (XHTML_NAMESPACE, tag))\n\n\ndef document_fromstring(html, guess_charset=None, parser=None):\n    \"\"\"\n    Parse a whole document into a string.\n\n    If `guess_charset` is true, or if the input is not Unicode but a\n    byte string, the `chardet` library will perform charset guessing\n    on the string.\n    \"\"\"\n    if not isinstance(html, _strings):\n        raise TypeError('string required')\n\n    if parser is None:\n        parser = html_parser\n\n    options = {}\n    if guess_charset is None and isinstance(html, bytes):\n        # html5lib does not accept useChardet as an argument, if it\n        # detected the html argument would produce unicode objects.\n        guess_charset = True\n    if guess_charset is not None:\n        options['useChardet'] = guess_charset\n    return parser.parse(html, **options).getroot()\n\n\ndef fragments_fromstring(html, no_leading_text=False,\n                         guess_charset=None, parser=None):\n    \"\"\"Parses several HTML elements, returning a list of elements.\n\n    The first item in the list may be a string.  If no_leading_text is true,\n    then it will be an error if there is leading text, and it will always be\n    a list of only elements.\n\n    If `guess_charset` is true, the `chardet` library will perform charset\n    guessing on the string.\n    \"\"\"\n    if not isinstance(html, _strings):\n        raise TypeError('string required')\n\n    if parser is None:\n        parser = html_parser\n\n    options = {}\n    if guess_charset is None and isinstance(html, bytes):\n        # html5lib does not accept useChardet as an argument, if it\n        # detected the html argument would produce unicode objects.\n        guess_charset = False\n    if guess_charset is not None:\n        options['useChardet'] = guess_charset\n    children = parser.parseFragment(html, 'div', **options)\n    if children and isinstance(children[0], _strings):\n        if no_leading_text:\n            if children[0].strip():\n                raise etree.ParserError('There is leading text: %r' %\n                                        children[0])\n            del children[0]\n    return children\n\n\ndef fragment_fromstring(html, create_parent=False,\n                        guess_charset=None, parser=None):\n    \"\"\"Parses a single HTML element; it is an error if there is more than\n    one element, or if anything but whitespace precedes or follows the\n    element.\n\n    If 'create_parent' is true (or is a tag name) then a parent node\n    will be created to encapsulate the HTML in a single element.  In\n    this case, leading or trailing text is allowed.\n\n    If `guess_charset` is true, the `chardet` library will perform charset\n    guessing on the string.\n    \"\"\"\n    if not isinstance(html, _strings):\n        raise TypeError('string required')\n\n    accept_leading_text = bool(create_parent)\n\n    elements = fragments_fromstring(\n        html, guess_charset=guess_charset, parser=parser,\n        no_leading_text=not accept_leading_text)\n\n    if create_parent:\n        if not isinstance(create_parent, _strings):\n            create_parent = 'div'\n        new_root = Element(create_parent)\n        if elements:\n            if isinstance(elements[0], _strings):\n                new_root.text = elements[0]\n                del elements[0]\n            new_root.extend(elements)\n        return new_root\n\n    if not elements:\n        raise etree.ParserError('No elements found')\n    if len(elements) > 1:\n        raise etree.ParserError('Multiple elements found')\n    result = elements[0]\n    if result.tail and result.tail.strip():\n        raise etree.ParserError('Element followed by text: %r' % result.tail)\n    result.tail = None\n    return result\n\n\ndef fromstring(html, guess_charset=None, parser=None):\n    \"\"\"Parse the html, returning a single element/document.\n\n    This tries to minimally parse the chunk of text, without knowing if it\n    is a fragment or a document.\n\n    'base_url' will set the document's base_url attribute (and the tree's\n    docinfo.URL)\n\n    If `guess_charset` is true, or if the input is not Unicode but a\n    byte string, the `chardet` library will perform charset guessing\n    on the string.\n    \"\"\"\n    if not isinstance(html, _strings):\n        raise TypeError('string required')\n    doc = document_fromstring(html, parser=parser,\n                              guess_charset=guess_charset)\n\n    # document starts with doctype or <html>, full document!\n    start = html[:50]\n    if isinstance(start, bytes):\n        # Allow text comparison in python3.\n        # Decode as ascii, that also covers latin-1 and utf-8 for the\n        # characters we need.\n        start = start.decode('ascii', 'replace')\n\n    start = start.lstrip().lower()\n    if start.startswith('<html') or start.startswith('<!doctype'):\n        return doc\n\n    head = _find_tag(doc, 'head')\n\n    # if the head is not empty we have a full document\n    if len(head):\n        return doc\n\n    body = _find_tag(doc, 'body')\n\n    # The body has just one element, so it was probably a single\n    # element passed in\n    if (len(body) == 1 and (not body.text or not body.text.strip())\n        and (not body[-1].tail or not body[-1].tail.strip())):\n        return body[0]\n\n    # Now we have a body which represents a bunch of tags which have the\n    # content that was passed in.  We will create a fake container, which\n    # is the body tag, except <body> implies too much structure.\n    if _contains_block_level_tag(body):\n        body.tag = 'div'\n    else:\n        body.tag = 'span'\n    return body\n\n\ndef parse(filename_url_or_file, guess_charset=None, parser=None):\n    \"\"\"Parse a filename, URL, or file-like object into an HTML document\n    tree.  Note: this returns a tree, not an element.  Use\n    ``parse(...).getroot()`` to get the document root.\n\n    If ``guess_charset`` is true, the ``useChardet`` option is passed into\n    html5lib to enable character detection.  This option is on by default\n    when parsing from URLs, off by default when parsing from file(-like)\n    objects (which tend to return Unicode more often than not), and on by\n    default when parsing from a file path (which is read in binary mode).\n    \"\"\"\n    if parser is None:\n        parser = html_parser\n    if not isinstance(filename_url_or_file, _strings):\n        fp = filename_url_or_file\n        if guess_charset is None:\n            # assume that file-like objects return Unicode more often than bytes\n            guess_charset = False\n    elif _looks_like_url(filename_url_or_file):\n        fp = urlopen(filename_url_or_file)\n        if guess_charset is None:\n            # assume that URLs return bytes\n            guess_charset = True\n    else:\n        fp = open(filename_url_or_file, 'rb')\n        if guess_charset is None:\n            guess_charset = True\n\n    options = {}\n    # html5lib does not accept useChardet as an argument, if it\n    # detected the html argument would produce unicode objects.\n    if guess_charset:\n        options['useChardet'] = guess_charset\n    return parser.parse(fp, **options)\n\n\ndef _looks_like_url(str):\n    scheme = urlparse(str)[0]\n    if not scheme:\n        return False\n    elif (sys.platform == 'win32' and\n            scheme in string.ascii_letters\n            and len(scheme) == 1):\n        # looks like a 'normal' absolute path\n        return False\n    else:\n        return True\n\n\nhtml_parser = HTMLParser()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/soupparser.py",
    "content": "\"\"\"External interface to the BeautifulSoup HTML parser.\n\"\"\"\n\n__all__ = [\"fromstring\", \"parse\", \"convert_tree\"]\n\nimport re\nfrom lxml import etree, html\n\ntry:\n    from bs4 import (\n        BeautifulSoup, Tag, Comment, ProcessingInstruction, NavigableString,\n        Declaration, Doctype)\n    _DECLARATION_OR_DOCTYPE = (Declaration, Doctype)\nexcept ImportError:\n    from BeautifulSoup import (\n        BeautifulSoup, Tag, Comment, ProcessingInstruction, NavigableString,\n        Declaration)\n    _DECLARATION_OR_DOCTYPE = Declaration\n\n\ndef fromstring(data, beautifulsoup=None, makeelement=None, **bsargs):\n    \"\"\"Parse a string of HTML data into an Element tree using the\n    BeautifulSoup parser.\n\n    Returns the root ``<html>`` Element of the tree.\n\n    You can pass a different BeautifulSoup parser through the\n    `beautifulsoup` keyword, and a diffent Element factory function\n    through the `makeelement` keyword.  By default, the standard\n    ``BeautifulSoup`` class and the default factory of `lxml.html` are\n    used.\n    \"\"\"\n    return _parse(data, beautifulsoup, makeelement, **bsargs)\n\n\ndef parse(file, beautifulsoup=None, makeelement=None, **bsargs):\n    \"\"\"Parse a file into an ElemenTree using the BeautifulSoup parser.\n\n    You can pass a different BeautifulSoup parser through the\n    `beautifulsoup` keyword, and a diffent Element factory function\n    through the `makeelement` keyword.  By default, the standard\n    ``BeautifulSoup`` class and the default factory of `lxml.html` are\n    used.\n    \"\"\"\n    if not hasattr(file, 'read'):\n        file = open(file)\n    root = _parse(file, beautifulsoup, makeelement, **bsargs)\n    return etree.ElementTree(root)\n\n\ndef convert_tree(beautiful_soup_tree, makeelement=None):\n    \"\"\"Convert a BeautifulSoup tree to a list of Element trees.\n\n    Returns a list instead of a single root Element to support\n    HTML-like soup with more than one root element.\n\n    You can pass a different Element factory through the `makeelement`\n    keyword.\n    \"\"\"\n    root = _convert_tree(beautiful_soup_tree, makeelement)\n    children = root.getchildren()\n    for child in children:\n        root.remove(child)\n    return children\n\n\n# helpers\n\ndef _parse(source, beautifulsoup, makeelement, **bsargs):\n    if beautifulsoup is None:\n        beautifulsoup = BeautifulSoup\n    if hasattr(beautifulsoup, \"HTML_ENTITIES\"):  # bs3\n        if 'convertEntities' not in bsargs:\n            bsargs['convertEntities'] = 'html'\n    if hasattr(beautifulsoup, \"DEFAULT_BUILDER_FEATURES\"):  # bs4\n        if 'features' not in bsargs:\n            bsargs['features'] = 'html.parser'  # use Python html parser\n    tree = beautifulsoup(source, **bsargs)\n    root = _convert_tree(tree, makeelement)\n    # from ET: wrap the document in a html root element, if necessary\n    if len(root) == 1 and root[0].tag == \"html\":\n        return root[0]\n    root.tag = \"html\"\n    return root\n\n\n_parse_doctype_declaration = re.compile(\n    r'(?:\\s|[<!])*DOCTYPE\\s*HTML'\n    r'(?:\\s+PUBLIC)?(?:\\s+(\\'[^\\']*\\'|\"[^\"]*\"))?'\n    r'(?:\\s+(\\'[^\\']*\\'|\"[^\"]*\"))?',\n    re.IGNORECASE).match\n\n\nclass _PseudoTag:\n    # Minimal imitation of BeautifulSoup.Tag\n    def __init__(self, contents):\n        self.name = 'html'\n        self.attrs = []\n        self.contents = contents\n\n    def __iter__(self):\n        return self.contents.__iter__()\n\n\ndef _convert_tree(beautiful_soup_tree, makeelement):\n    if makeelement is None:\n        makeelement = html.html_parser.makeelement\n\n    # Split the tree into three parts:\n    # i) everything before the root element: document type\n    # declaration, comments, processing instructions, whitespace\n    # ii) the root(s),\n    # iii) everything after the root: comments, processing\n    # instructions, whitespace\n    first_element_idx = last_element_idx = None\n    html_root = declaration = None\n    for i, e in enumerate(beautiful_soup_tree):\n        if isinstance(e, Tag):\n            if first_element_idx is None:\n                first_element_idx = i\n            last_element_idx = i\n            if html_root is None and e.name and e.name.lower() == 'html':\n                html_root = e\n        elif declaration is None and isinstance(e, _DECLARATION_OR_DOCTYPE):\n            declaration = e\n\n    # For a nice, well-formatted document, the variable roots below is\n    # a list consisting of a single <html> element. However, the document\n    # may be a soup like '<meta><head><title>Hello</head><body>Hi\n    # all<\\p>'. In this example roots is a list containing meta, head\n    # and body elements.\n    if first_element_idx is None:\n        pre_root = post_root = []\n        roots = beautiful_soup_tree.contents\n    else:\n        pre_root = beautiful_soup_tree.contents[:first_element_idx]\n        roots = beautiful_soup_tree.contents[first_element_idx:last_element_idx+1]\n        post_root = beautiful_soup_tree.contents[last_element_idx+1:]\n\n    # Reorganize so that there is one <html> root...\n    if html_root is not None:\n        # ... use existing one if possible, ...\n        i = roots.index(html_root)\n        html_root.contents = roots[:i] + html_root.contents + roots[i+1:]\n    else:\n        # ... otherwise create a new one.\n        html_root = _PseudoTag(roots)\n\n    convert_node = _init_node_converters(makeelement)\n\n    # Process pre_root\n    res_root = convert_node(html_root)\n    prev = res_root\n    for e in reversed(pre_root):\n        converted = convert_node(e)\n        if converted is not None:\n            prev.addprevious(converted)\n            prev = converted\n\n    # ditto for post_root\n    prev = res_root\n    for e in post_root:\n        converted = convert_node(e)\n        if converted is not None:\n            prev.addnext(converted)\n            prev = converted\n\n    if declaration is not None:\n        try:\n            # bs4 provides full Doctype string\n            doctype_string = declaration.output_ready()\n        except AttributeError:\n            doctype_string = declaration.string\n\n        match = _parse_doctype_declaration(doctype_string)\n        if not match:\n            # Something is wrong if we end up in here. Since soupparser should\n            # tolerate errors, do not raise Exception, just let it pass.\n            pass\n        else:\n            external_id, sys_uri = match.groups()\n            docinfo = res_root.getroottree().docinfo\n            # strip quotes and update DOCTYPE values (any of None, '', '...')\n            docinfo.public_id = external_id and external_id[1:-1]\n            docinfo.system_url = sys_uri and sys_uri[1:-1]\n\n    return res_root\n\n\ndef _init_node_converters(makeelement):\n    converters = {}\n    ordered_node_types = []\n\n    def converter(*types):\n        def add(handler):\n            for t in types:\n                converters[t] = handler\n                ordered_node_types.append(t)\n            return handler\n        return add\n\n    def find_best_converter(node):\n        for t in ordered_node_types:\n            if isinstance(node, t):\n                return converters[t]\n        return None\n\n    def convert_node(bs_node, parent=None):\n        # duplicated in convert_tag() below\n        try:\n            handler = converters[type(bs_node)]\n        except KeyError:\n            handler = converters[type(bs_node)] = find_best_converter(bs_node)\n        if handler is None:\n            return None\n        return handler(bs_node, parent)\n\n    def map_attrs(bs_attrs):\n        if isinstance(bs_attrs, dict):  # bs4\n            attribs = {}\n            for k, v in bs_attrs.items():\n                if isinstance(v, list):\n                    v = \" \".join(v)\n                attribs[k] = unescape(v)\n        else:\n            attribs = dict((k, unescape(v)) for k, v in bs_attrs)\n        return attribs\n\n    def append_text(parent, text):\n        if len(parent) == 0:\n            parent.text = (parent.text or '') + text\n        else:\n            parent[-1].tail = (parent[-1].tail or '') + text\n\n    # converters are tried in order of their definition\n\n    @converter(Tag, _PseudoTag)\n    def convert_tag(bs_node, parent):\n        attrs = bs_node.attrs\n        if parent is not None:\n            attribs = map_attrs(attrs) if attrs else None\n            res = etree.SubElement(parent, bs_node.name, attrib=attribs)\n        else:\n            attribs = map_attrs(attrs) if attrs else {}\n            res = makeelement(bs_node.name, attrib=attribs)\n\n        for child in bs_node:\n            # avoid double recursion by inlining convert_node(), see above\n            try:\n                handler = converters[type(child)]\n            except KeyError:\n                pass\n            else:\n                if handler is not None:\n                    handler(child, res)\n                continue\n            convert_node(child, res)\n        return res\n\n    @converter(Comment)\n    def convert_comment(bs_node, parent):\n        res = html.HtmlComment(bs_node)\n        if parent is not None:\n            parent.append(res)\n        return res\n\n    @converter(ProcessingInstruction)\n    def convert_pi(bs_node, parent):\n        if bs_node.endswith('?'):\n            # The PI is of XML style (<?as df?>) but BeautifulSoup\n            # interpreted it as being SGML style (<?as df>). Fix.\n            bs_node = bs_node[:-1]\n        res = etree.ProcessingInstruction(*bs_node.split(' ', 1))\n        if parent is not None:\n            parent.append(res)\n        return res\n\n    @converter(NavigableString)\n    def convert_text(bs_node, parent):\n        if parent is not None:\n            append_text(parent, unescape(bs_node))\n        return None\n\n    return convert_node\n\n\n# copied from ET's ElementSoup\n\ntry:\n    from html.entities import name2codepoint  # Python 3\nexcept ImportError:\n    from htmlentitydefs import name2codepoint\n\n\nhandle_entities = re.compile(r\"&(\\w+);\").sub\n\n\ntry:\n    unichr\nexcept NameError:\n    # Python 3\n    unichr = chr\n\n\ndef unescape(string):\n    if not string:\n        return ''\n    # work around oddities in BeautifulSoup's entity handling\n    def unescape_entity(m):\n        try:\n            return unichr(name2codepoint[m.group(1)])\n        except KeyError:\n            return m.group(0)  # use as is\n    return handle_entities(unescape_entity, string)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/html/usedoctest.py",
    "content": "\"\"\"Doctest module for HTML comparison.\n\nUsage::\n\n   >>> import lxml.html.usedoctest\n   >>> # now do your HTML doctests ...\n\nSee `lxml.doctestcompare`.\n\"\"\"\n\nfrom lxml import doctestcompare\n\ndoctestcompare.temp_install(html=True, del_module=__name__)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/__init__.pxd",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/c14n.pxd",
    "content": "from lxml.includes.tree cimport xmlDoc, xmlOutputBuffer, xmlChar\nfrom lxml.includes.xpath cimport xmlNodeSet\n\ncdef extern from \"libxml/c14n.h\":\n    cdef int xmlC14NDocDumpMemory(xmlDoc* doc,\n                                  xmlNodeSet* nodes,\n                                  int exclusive,\n                                  xmlChar** inclusive_ns_prefixes,\n                                  int with_comments,\n                                  xmlChar** doc_txt_ptr) nogil\n\n    cdef int xmlC14NDocSave(xmlDoc* doc,\n                            xmlNodeSet* nodes,\n                            int exclusive,\n                            xmlChar** inclusive_ns_prefixes,\n                            int with_comments,\n                            char* filename,\n                            int compression) nogil\n\n    cdef int xmlC14NDocSaveTo(xmlDoc* doc,\n                              xmlNodeSet* nodes,\n                              int exclusive,\n                              xmlChar** inclusive_ns_prefixes,\n                              int with_comments,\n                              xmlOutputBuffer* buffer) nogil\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/config.pxd",
    "content": "cdef extern from \"etree_defs.h\":\n    cdef bint ENABLE_THREADING\n    cdef bint ENABLE_SCHEMATRON\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/dtdvalid.pxd",
    "content": "from lxml.includes cimport tree\nfrom lxml.includes.tree cimport xmlDoc, xmlDtd\n\ncdef extern from \"libxml/valid.h\" nogil:\n    ctypedef void (*xmlValidityErrorFunc)(void * ctx, const char * msg, ...)\n    ctypedef void (*xmlValidityWarningFunc)(void * ctx, const char * msg, ...)\n\n    ctypedef struct xmlValidCtxt:\n        void *userData\n        xmlValidityErrorFunc error\n        xmlValidityWarningFunc warning\n\n    cdef xmlValidCtxt* xmlNewValidCtxt()\n    cdef void xmlFreeValidCtxt(xmlValidCtxt* cur)\n\n    cdef int xmlValidateDtd(xmlValidCtxt* ctxt, xmlDoc* doc, xmlDtd* dtd)\n    cdef tree.xmlElement* xmlGetDtdElementDesc(\n        xmlDtd* dtd, tree.const_xmlChar* name)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/etree_defs.h",
    "content": "#ifndef HAS_ETREE_DEFS_H\n#define HAS_ETREE_DEFS_H\n\n/* quick check for Python/libxml2/libxslt devel setup */\n#include \"Python.h\"\n#ifndef PY_VERSION_HEX\n#  error the development package of Python (header files etc.) is not installed correctly\n#else\n#  if PY_VERSION_HEX < 0x02070000 || PY_MAJOR_VERSION >= 3 && PY_VERSION_HEX < 0x03050000\n#  error this version of lxml requires Python 2.7, 3.5 or later\n#  endif\n#endif\n\n#include \"libxml/xmlversion.h\"\n#ifndef LIBXML_VERSION\n#  error the development package of libxml2 (header files etc.) is not installed correctly\n#else\n#if LIBXML_VERSION < 20700\n#  error minimum required version of libxml2 is 2.7.0\n#endif\n#endif\n\n#include \"libxslt/xsltconfig.h\"\n#ifndef LIBXSLT_VERSION\n#  error the development package of libxslt (header files etc.) is not installed correctly\n#else\n#if LIBXSLT_VERSION < 10123\n#  error minimum required version of libxslt is 1.1.23\n#endif\n#endif\n\n\n/* v_arg functions */\n#define va_int(ap)     va_arg(ap, int)\n#define va_charptr(ap) va_arg(ap, char *)\n\n#ifdef PYPY_VERSION\n#    define IS_PYPY 1\n#else\n#    define IS_PYPY 0\n#endif\n\n#if PY_MAJOR_VERSION >= 3\n#  define IS_PYTHON2 0  /* prefer for special casing Python 2.x */\n#  define IS_PYTHON3 1  /* avoid */\n#else\n#  define IS_PYTHON2 1\n#  define IS_PYTHON3 0\n#endif\n\n#if IS_PYTHON2\n#ifndef LXML_UNICODE_STRINGS\n#define LXML_UNICODE_STRINGS 0\n#endif\n#else\n#undef LXML_UNICODE_STRINGS\n#define LXML_UNICODE_STRINGS 1\n#endif\n\n#if !IS_PYPY\n#  define PyWeakref_LockObject(obj)          (NULL)\n#endif\n\n/* Threading is not currently supported by PyPy */\n#if IS_PYPY\n#  ifndef WITHOUT_THREADING\n#    define WITHOUT_THREADING\n#  endif\n#endif\n\n#if IS_PYPY\n#  undef PyFile_AsFile\n#  define PyFile_AsFile(o)                   (NULL)\n#  undef PyByteArray_Check\n#  define PyByteArray_Check(o)               (0)\n#elif !IS_PYTHON2\n   /* Python 3+ doesn't have PyFile_*() anymore */\n#  define PyFile_AsFile(o)                   (NULL)\n#endif\n\n#if PY_VERSION_HEX <= 0x03030000 && !(defined(CYTHON_PEP393_ENABLED) && CYTHON_PEP393_ENABLED)\n  #define PyUnicode_IS_READY(op)    (0)\n  #define PyUnicode_GET_LENGTH(u)   PyUnicode_GET_SIZE(u)\n  #define PyUnicode_KIND(u)         (sizeof(Py_UNICODE))\n  #define PyUnicode_DATA(u)         ((void*)PyUnicode_AS_UNICODE(u))\n#endif\n\n#if IS_PYPY\n#  ifndef PyUnicode_FromFormat\n#    define PyUnicode_FromFormat  PyString_FromFormat\n#  endif\n#  if !IS_PYTHON2 && !defined(PyBytes_FromFormat)\n#    ifdef PyString_FromFormat\n#      define PyBytes_FromFormat  PyString_FromFormat\n#    else\n#include <stdarg.h>\nstatic PyObject* PyBytes_FromFormat(const char* format, ...) {\n    PyObject *string;\n    va_list vargs;\n#ifdef HAVE_STDARG_PROTOTYPES\n    va_start(vargs, format);\n#else\n    va_start(vargs);\n#endif\n    string = PyUnicode_FromFormatV(format, vargs);\n    va_end(vargs);\n    if (string && PyUnicode_Check(string)) {\n        PyObject *bstring = PyUnicode_AsUTF8String(string);\n        Py_DECREF(string);\n        string = bstring;\n    }\n    if (string && !PyBytes_CheckExact(string)) {\n        Py_DECREF(string);\n        string = NULL;\n        PyErr_SetString(PyExc_TypeError, \"String formatting and encoding failed to return bytes object\");\n    }\n    return string;\n}\n#    endif\n#  endif\n#endif\n\n/* PySlice_GetIndicesEx() has wrong signature in Py<=3.1 */\n#if PY_VERSION_HEX >= 0x03020000\n#  define _lx_PySlice_GetIndicesEx(o, l, b, e, s, sl) PySlice_GetIndicesEx(o, l, b, e, s, sl)\n#else\n#  define _lx_PySlice_GetIndicesEx(o, l, b, e, s, sl) PySlice_GetIndicesEx(((PySliceObject*)o), l, b, e, s, sl)\n#endif\n\n#ifdef WITHOUT_THREADING\n#  undef PyEval_SaveThread\n#  define PyEval_SaveThread() (NULL)\n#  undef PyEval_RestoreThread\n#  define PyEval_RestoreThread(state)  if (state); else {}\n#  undef PyGILState_Ensure\n#  define PyGILState_Ensure() (PyGILState_UNLOCKED)\n#  undef PyGILState_Release\n#  define PyGILState_Release(state)  if (state); else {}\n#  undef  Py_UNBLOCK_THREADS\n#  define Py_UNBLOCK_THREADS  _save = NULL;\n#  undef  Py_BLOCK_THREADS\n#  define Py_BLOCK_THREADS  if (_save); else {}\n#endif\n\n#ifdef WITHOUT_THREADING\n#  define ENABLE_THREADING 0\n#else\n#  define ENABLE_THREADING 1\n#endif\n\n#if LIBXML_VERSION < 20704\n/* FIXME: hack to make new error reporting compile in old libxml2 versions */\n#  define xmlStructuredErrorContext NULL\n#  define xmlXIncludeProcessTreeFlagsData(n,o,d) xmlXIncludeProcessTreeFlags(n,o)\n#endif\n\n/* schematron was added in libxml2 2.6.21 */\n#ifdef LIBXML_SCHEMATRON_ENABLED\n#  define ENABLE_SCHEMATRON 1\n#else\n#  define ENABLE_SCHEMATRON 0\n#  define XML_SCHEMATRON_OUT_QUIET 0\n#  define XML_SCHEMATRON_OUT_XML 0\n#  define XML_SCHEMATRON_OUT_ERROR 0\n   typedef void xmlSchematron;\n   typedef void xmlSchematronParserCtxt;\n   typedef void xmlSchematronValidCtxt;\n#  define xmlSchematronNewDocParserCtxt(doc) NULL\n#  define xmlSchematronNewParserCtxt(file) NULL\n#  define xmlSchematronParse(ctxt) NULL\n#  define xmlSchematronFreeParserCtxt(ctxt)\n#  define xmlSchematronFree(schema)\n#  define xmlSchematronNewValidCtxt(schema, options) NULL\n#  define xmlSchematronValidateDoc(ctxt, doc) 0\n#  define xmlSchematronFreeValidCtxt(ctxt)\n#  define xmlSchematronSetValidStructuredErrors(ctxt, errorfunc, data)\n#endif\n\n#if LIBXML_VERSION < 20708\n#  define HTML_PARSE_NODEFDTD 4\n#endif\n#if LIBXML_VERSION < 20900\n#  define XML_PARSE_BIG_LINES 4194304\n#endif\n\n#include \"libxml/tree.h\"\n#ifndef LIBXML2_NEW_BUFFER\n   typedef xmlBuffer xmlBuf;\n#  define xmlBufContent(buf) xmlBufferContent(buf)\n#  define xmlBufUse(buf) xmlBufferLength(buf)\n#endif\n\n/* libexslt 1.1.25+ support EXSLT functions in XPath */\n#if LIBXSLT_VERSION < 10125\n#define exsltDateXpathCtxtRegister(ctxt, prefix)\n#define exsltSetsXpathCtxtRegister(ctxt, prefix)\n#define exsltMathXpathCtxtRegister(ctxt, prefix)\n#define exsltStrXpathCtxtRegister(ctxt, prefix)\n#endif\n\n#define LXML_GET_XSLT_ENCODING(result_var, style) XSLT_GET_IMPORT_PTR(result_var, style, encoding)\n\n/* work around MSDEV 6.0 */\n#if (_MSC_VER == 1200) && (WINVER < 0x0500)\nlong _ftol( double ); //defined by VC6 C libs\nlong _ftol2( double dblSource ) { return _ftol( dblSource ); }\n#endif\n\n#ifdef __GNUC__\n/* Test for GCC > 2.95 */\n#if __GNUC__ > 2 || (__GNUC__ == 2 && (__GNUC_MINOR__ > 95)) \n#define unlikely_condition(x) __builtin_expect((x), 0)\n#else /* __GNUC__ > 2 ... */\n#define unlikely_condition(x) (x)\n#endif /* __GNUC__ > 2 ... */\n#else /* __GNUC__ */\n#define unlikely_condition(x) (x)\n#endif /* __GNUC__ */\n\n#ifndef Py_TYPE\n  #define Py_TYPE(ob)   (((PyObject*)(ob))->ob_type)\n#endif\n\n#define PY_NEW(T) \\\n     (((PyTypeObject*)(T))->tp_new( \\\n             (PyTypeObject*)(T), __pyx_empty_tuple, NULL))\n\n#define _fqtypename(o)  ((Py_TYPE(o))->tp_name)\n\n#define lxml_malloc(count, item_size) \\\n    (unlikely_condition((size_t)(count) > (size_t) (PY_SSIZE_T_MAX / item_size)) ? NULL : \\\n     (PyMem_Malloc((count) * item_size)))\n\n#define lxml_realloc(mem, count, item_size) \\\n    (unlikely_condition((size_t)(count) > (size_t) (PY_SSIZE_T_MAX / item_size)) ? NULL : \\\n     (PyMem_Realloc(mem, (count) * item_size)))\n\n#define lxml_free(mem)  PyMem_Free(mem)\n\n#if PY_MAJOR_VERSION < 3\n#define _isString(obj)   (PyString_CheckExact(obj)  || \\\n                          PyUnicode_CheckExact(obj) || \\\n                          PyType_IsSubtype(Py_TYPE(obj), &PyBaseString_Type))\n#else\n/* builtin subtype type checks are almost as fast as exact checks in Py2.7+\n * and Unicode is more common in Py3 */\n#define _isString(obj)   (PyUnicode_Check(obj) || PyBytes_Check(obj))\n#endif\n\n#define _isElement(c_node) \\\n        (((c_node)->type == XML_ELEMENT_NODE) || \\\n         ((c_node)->type == XML_COMMENT_NODE) || \\\n         ((c_node)->type == XML_ENTITY_REF_NODE) || \\\n         ((c_node)->type == XML_PI_NODE))\n\n#define _isElementOrXInclude(c_node) \\\n        (_isElement(c_node)                     || \\\n         ((c_node)->type == XML_XINCLUDE_START) || \\\n         ((c_node)->type == XML_XINCLUDE_END))\n\n#define _getNs(c_node) \\\n        (((c_node)->ns == 0) ? 0 : ((c_node)->ns->href))\n\n\n#include \"string.h\"\nstatic void* lxml_unpack_xmldoc_capsule(PyObject* capsule, int* is_owned) {\n    xmlDoc *c_doc;\n    void *context;\n    *is_owned = 0;\n    if (unlikely_condition(!PyCapsule_IsValid(capsule, (const char*)\"libxml2:xmlDoc\"))) {\n        PyErr_SetString(\n                PyExc_TypeError,\n                \"Not a valid capsule. The capsule argument must be a capsule object with name libxml2:xmlDoc\");\n        return NULL;\n    }\n    c_doc = (xmlDoc*) PyCapsule_GetPointer(capsule, (const char*)\"libxml2:xmlDoc\");\n    if (unlikely_condition(!c_doc)) return NULL;\n\n    if (unlikely_condition(c_doc->type != XML_DOCUMENT_NODE && c_doc->type != XML_HTML_DOCUMENT_NODE)) {\n        PyErr_Format(\n            PyExc_ValueError,\n            \"Illegal document provided: expected XML or HTML, found %d\", (int)c_doc->type);\n        return NULL;\n    }\n\n    context = PyCapsule_GetContext(capsule);\n    if (unlikely_condition(!context && PyErr_Occurred())) return NULL;\n    if (context && strcmp((const char*) context, \"destructor:xmlFreeDoc\") == 0) {\n        /* take ownership by setting destructor to NULL */\n        if (PyCapsule_SetDestructor(capsule, NULL) == 0) {\n            /* ownership transferred => invalidate capsule by clearing its name */\n            if (unlikely_condition(PyCapsule_SetName(capsule, NULL))) {\n                /* this should never happen since everything above succeeded */\n                xmlFreeDoc(c_doc);\n                return NULL;\n            }\n            *is_owned = 1;\n        }\n    }\n    return c_doc;\n}\n\n/* Macro pair implementation of a depth first tree walker\n *\n * Calls the code block between the BEGIN and END macros for all elements\n * below c_tree_top (exclusively), starting at c_node (inclusively iff\n * 'inclusive' is 1).  The _ELEMENT_ variants will only stop on nodes\n * that match _isElement(), the normal variant will stop on every node\n * except text nodes.\n * \n * To traverse the node and all of its children and siblings in Pyrex, call\n *    cdef xmlNode* some_node\n *    BEGIN_FOR_EACH_ELEMENT_FROM(some_node.parent, some_node, 1)\n *    # do something with some_node\n *    END_FOR_EACH_ELEMENT_FROM(some_node)\n *\n * To traverse only the children and siblings of a node, call\n *    cdef xmlNode* some_node\n *    BEGIN_FOR_EACH_ELEMENT_FROM(some_node.parent, some_node, 0)\n *    # do something with some_node\n *    END_FOR_EACH_ELEMENT_FROM(some_node)\n *\n * To traverse only the children, do:\n *    cdef xmlNode* some_node\n *    some_node = parent_node.children\n *    BEGIN_FOR_EACH_ELEMENT_FROM(parent_node, some_node, 1)\n *    # do something with some_node\n *    END_FOR_EACH_ELEMENT_FROM(some_node)\n *\n * NOTE: 'some_node' MUST be a plain 'xmlNode*' !\n *\n * NOTE: parent modification during the walk can divert the iterator, but\n *       should not segfault !\n */\n\n#define _LX__ELEMENT_MATCH(c_node, only_elements)  \\\n    ((only_elements) ? (_isElement(c_node)) : 1)\n\n#define _LX__ADVANCE_TO_NEXT(c_node, only_elements)                        \\\n    while ((c_node != 0) && (!_LX__ELEMENT_MATCH(c_node, only_elements)))  \\\n        c_node = c_node->next;\n\n#define _LX__TRAVERSE_TO_NEXT(c_stop_node, c_node, only_elements)   \\\n{                                                                   \\\n    /* walk through children first */                               \\\n    xmlNode* _lx__next = c_node->children;\t\t            \\\n    if (_lx__next != 0) {                                           \\\n        if (c_node->type == XML_ENTITY_REF_NODE || c_node->type == XML_DTD_NODE) { \\\n            _lx__next = 0;                                          \\\n        } else {                                                    \\\n            _LX__ADVANCE_TO_NEXT(_lx__next, only_elements)\t    \\\n        }                                                           \\\n    }\t\t\t\t\t\t\t            \\\n    if ((_lx__next == 0) && (c_node != c_stop_node)) {              \\\n        /* try siblings */                                          \\\n        _lx__next = c_node->next;                                   \\\n        _LX__ADVANCE_TO_NEXT(_lx__next, only_elements)              \\\n        /* back off through parents */                              \\\n        while (_lx__next == 0) {                                    \\\n            c_node = c_node->parent;                                \\\n            if (c_node == 0)                                        \\\n                break;                                              \\\n            if (c_node == c_stop_node)                              \\\n                break;                                              \\\n            if ((only_elements) && !_isElement(c_node))\t            \\\n                break;                                              \\\n            /* we already traversed the parents -> siblings */      \\\n            _lx__next = c_node->next;                               \\\n            _LX__ADVANCE_TO_NEXT(_lx__next, only_elements)\t    \\\n        }                                                           \\\n    }                                                               \\\n    c_node = _lx__next;                                             \\\n}\n\n#define _LX__BEGIN_FOR_EACH_FROM(c_tree_top, c_node, inclusive, only_elements)     \\\n{\t\t\t\t\t\t\t\t\t      \\\n    if (c_node != 0) {\t\t\t\t\t\t\t      \\\n        const xmlNode* _lx__tree_top = (c_tree_top);                          \\\n        const int _lx__only_elements = (only_elements);                       \\\n        /* make sure we start at an element */                   \t      \\\n        if (!_LX__ELEMENT_MATCH(c_node, _lx__only_elements)) {\t\t      \\\n            /* we skip the node, so 'inclusive' is irrelevant */              \\\n            if (c_node == _lx__tree_top)                                      \\\n                c_node = 0; /* nothing to traverse */                         \\\n            else {                                                            \\\n                c_node = c_node->next;                                        \\\n                _LX__ADVANCE_TO_NEXT(c_node, _lx__only_elements)              \\\n            }                                                                 \\\n        } else if (! (inclusive)) {                                           \\\n            /* skip the first node */                                         \\\n            _LX__TRAVERSE_TO_NEXT(_lx__tree_top, c_node, _lx__only_elements)  \\\n        }                                                                     \\\n                                                                              \\\n        /* now run the user code on the elements we find */                   \\\n        while (c_node != 0) {                                                 \\\n            /* here goes the code to be run for each element */\n\n#define _LX__END_FOR_EACH_FROM(c_node)                                        \\\n            _LX__TRAVERSE_TO_NEXT(_lx__tree_top, c_node, _lx__only_elements)  \\\n        }                                                                     \\\n    }                                                                         \\\n}\n\n\n#define BEGIN_FOR_EACH_ELEMENT_FROM(c_tree_top, c_node, inclusive)   \\\n    _LX__BEGIN_FOR_EACH_FROM(c_tree_top, c_node, inclusive, 1)\n\n#define END_FOR_EACH_ELEMENT_FROM(c_node)   \\\n    _LX__END_FOR_EACH_FROM(c_node)\n\n#define BEGIN_FOR_EACH_FROM(c_tree_top, c_node, inclusive)   \\\n    _LX__BEGIN_FOR_EACH_FROM(c_tree_top, c_node, inclusive, 0)\n\n#define END_FOR_EACH_FROM(c_node)   \\\n    _LX__END_FOR_EACH_FROM(c_node)\n\n\n#endif /* HAS_ETREE_DEFS_H */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/etreepublic.pxd",
    "content": "# public Cython/C interface to lxml.etree\n\nfrom lxml.includes cimport tree\nfrom lxml.includes.tree cimport const_xmlChar\n\ncdef extern from \"lxml-version.h\":\n    cdef char* LXML_VERSION_STRING\n\ncdef extern from \"etree_defs.h\":\n    # test if c_node is considered an Element (i.e. Element, Comment, etc.)\n    cdef bint _isElement(tree.xmlNode* c_node) nogil\n\n    # return the namespace URI of the node or NULL\n    cdef const_xmlChar* _getNs(tree.xmlNode* node) nogil\n\n    # pair of macros for tree traversal\n    cdef void BEGIN_FOR_EACH_ELEMENT_FROM(tree.xmlNode* tree_top,\n                                          tree.xmlNode* start_node,\n                                          int start_node_inclusive) nogil\n    cdef void END_FOR_EACH_ELEMENT_FROM(tree.xmlNode* start_node) nogil\n\ncdef extern from \"etree_api.h\":\n\n    # first function to call!\n    cdef int import_lxml__etree() except -1\n\n    ##########################################################################\n    # public ElementTree API classes\n\n    cdef class lxml.etree._Document [ object LxmlDocument ]:\n        cdef tree.xmlDoc* _c_doc\n\n    cdef class lxml.etree._Element [ object LxmlElement ]:\n        cdef _Document _doc\n        cdef tree.xmlNode* _c_node\n\n    cdef class lxml.etree.ElementBase(_Element) [ object LxmlElementBase ]:\n        pass\n\n    cdef class lxml.etree._ElementTree [ object LxmlElementTree ]:\n        cdef _Document _doc\n        cdef _Element  _context_node\n\n    cdef class lxml.etree.ElementClassLookup [ object LxmlElementClassLookup ]:\n        cdef object (*_lookup_function)(object, _Document, tree.xmlNode*)\n\n    cdef class lxml.etree.FallbackElementClassLookup(ElementClassLookup) \\\n             [ object LxmlFallbackElementClassLookup ]:\n        cdef ElementClassLookup fallback\n        cdef object (*_fallback_function)(object, _Document, tree.xmlNode*)\n\n    ##########################################################################\n    # creating Element objects\n\n    # create an Element for a C-node in the Document\n    cdef _Element elementFactory(_Document doc, tree.xmlNode* c_node)\n\n    # create an ElementTree for an Element\n    cdef _ElementTree elementTreeFactory(_Element context_node)\n\n    # create an ElementTree subclass for an Element\n    cdef _ElementTree newElementTree(_Element context_node, object subclass)\n\n    # create an ElementTree from an external document\n    cdef _ElementTree adoptExternalDocument(tree.xmlDoc* c_doc, parser, bint is_owned)\n\n    # create a new Element for an existing or new document (doc = None)\n    # builds Python object after setting text, tail, namespaces and attributes\n    cdef _Element makeElement(tag, _Document doc, parser,\n                              text, tail, attrib, nsmap)\n\n    # create a new SubElement for an existing parent\n    # builds Python object after setting text, tail, namespaces and attributes\n    cdef _Element makeSubElement(_Element parent, tag, text, tail,\n                                 attrib, nsmap)\n\n    # deep copy a node to include it in the Document\n    cdef _Element deepcopyNodeToDocument(_Document doc, tree.xmlNode* c_root)\n\n    # set the internal lookup function for Element/Comment/PI classes\n    # use setElementClassLookupFunction(NULL, None) to reset it\n    # note that the lookup function *must always* return an _Element subclass!\n    cdef void setElementClassLookupFunction(\n         object (*function)(object, _Document, tree.xmlNode*), object state)\n\n    # lookup function that always returns the default Element class\n    # note that the first argument is expected to be None!\n    cdef object lookupDefaultElementClass(_1, _Document _2,\n                                          tree.xmlNode* c_node)\n\n    # lookup function for namespace/tag specific Element classes\n    # note that the first argument is expected to be None!\n    cdef object lookupNamespaceElementClass(_1, _Document _2,\n                                            tree.xmlNode* c_node)\n\n    # call the fallback lookup function of a FallbackElementClassLookup\n    cdef object callLookupFallback(FallbackElementClassLookup lookup,\n                                   _Document doc, tree.xmlNode* c_node)\n\n    ##########################################################################\n    # XML attribute access\n\n    # return an attribute value for a C attribute on a C element node\n    cdef object attributeValue(tree.xmlNode* c_element,\n                               tree.xmlAttr* c_attrib_node)\n\n    # return the value of the attribute with 'ns' and 'name' (or None)\n    cdef object attributeValueFromNsName(tree.xmlNode* c_element,\n                                         const_xmlChar* c_ns, const_xmlChar* c_name)\n\n    # return the value of attribute \"{ns}name\", or the default value\n    cdef object getAttributeValue(_Element element, key, default)\n\n    # return an iterator over attribute names (1), values (2) or items (3)\n    # attributes must not be removed during iteration!\n    cdef object iterattributes(_Element element, int keysvalues)\n\n    # return the list of all attribute names (1), values (2) or items (3)\n    cdef list collectAttributes(tree.xmlNode* c_element, int keysvalues)\n\n    # set an attribute value on an element\n    # on failure, sets an exception and returns -1\n    cdef int setAttributeValue(_Element element, key, value) except -1\n\n    # delete an attribute\n    # on failure, sets an exception and returns -1\n    cdef int delAttribute(_Element element, key) except -1\n\n    # delete an attribute based on name and namespace URI\n    # returns -1 if the attribute was not found (no exception)\n    cdef int delAttributeFromNsName(tree.xmlNode* c_element,\n                                    const_xmlChar* c_href, const_xmlChar* c_name)\n\n    ##########################################################################\n    # XML node helper functions\n\n    # check if the element has at least one child\n    cdef bint hasChild(tree.xmlNode* c_node) nogil\n\n    # find child element number 'index' (supports negative indexes)\n    cdef tree.xmlNode* findChild(tree.xmlNode* c_node,\n                                 Py_ssize_t index) nogil\n\n    # find child element number 'index' starting at first one\n    cdef tree.xmlNode* findChildForwards(tree.xmlNode* c_node,\n                                         Py_ssize_t index) nogil\n\n    # find child element number 'index' starting at last one\n    cdef tree.xmlNode* findChildBackwards(tree.xmlNode* c_node,\n                                          Py_ssize_t index) nogil\n\n    # return next/previous sibling element of the node\n    cdef tree.xmlNode* nextElement(tree.xmlNode* c_node) nogil\n    cdef tree.xmlNode* previousElement(tree.xmlNode* c_node) nogil\n\n    ##########################################################################\n    # iterators (DEPRECATED API, don't use in new code!)\n\n    cdef class lxml.etree._ElementTagMatcher [ object LxmlElementTagMatcher ]:\n        cdef char* _href\n        cdef char* _name\n\n    # store \"{ns}tag\" (or None) filter for this matcher or element iterator\n    # ** unless _href *and* _name are set up 'by hand', this function *must*\n    # ** be called when subclassing the iterator below!\n    cdef void initTagMatch(_ElementTagMatcher matcher, tag)\n\n    cdef class lxml.etree._ElementIterator(_ElementTagMatcher) [\n        object LxmlElementIterator ]:\n        cdef _Element _node\n        cdef tree.xmlNode* (*_next_element)(tree.xmlNode*)\n\n    # store the initial node of the iterator if it matches the required tag\n    # or its next matching sibling if not\n    cdef void iteratorStoreNext(_ElementIterator iterator, _Element node)\n\n    ##########################################################################\n    # other helper functions\n\n    # check if a C node matches a tag name and namespace\n    # (NULL allowed for each => always matches)\n    cdef int tagMatches(tree.xmlNode* c_node, const_xmlChar* c_href, const_xmlChar* c_name)\n\n    # convert a UTF-8 char* to a Python string or unicode string\n    cdef object pyunicode(const_xmlChar* s)\n\n    # convert the string to UTF-8 using the normal lxml.etree semantics\n    cdef bytes utf8(object s)\n\n    # split a tag into a (URI, name) tuple, return None as URI for '{}tag'\n    cdef tuple getNsTag(object tag)\n\n    # split a tag into a (URI, name) tuple, return b'' as URI for '{}tag'\n    cdef tuple getNsTagWithEmptyNs(object tag)\n\n    # get the \"{ns}tag\" string for a C node\n    cdef object namespacedName(tree.xmlNode* c_node)\n\n    # get the \"{ns}tag\" string for a href/tagname pair (c_ns may be NULL)\n    cdef object namespacedNameFromNsName(const_xmlChar* c_ns, const_xmlChar* c_tag)\n\n    # check if the node has a text value (which may be '')\n    cdef bint hasText(tree.xmlNode* c_node) nogil\n\n    # check if the node has a tail value (which may be '')\n    cdef bint hasTail(tree.xmlNode* c_node) nogil\n\n    # get the text content of an element (or None)\n    cdef object textOf(tree.xmlNode* c_node)\n\n    # get the tail content of an element (or None)\n    cdef object tailOf(tree.xmlNode* c_node)\n\n    # set the text value of an element\n    cdef int setNodeText(tree.xmlNode* c_node, text) except -1\n\n    # set the tail text value of an element\n    cdef int setTailText(tree.xmlNode* c_node, text) except -1\n\n    # append an element to the children of a parent element\n    # deprecated: don't use, does not propagate exceptions!\n    # use appendChildToElement() instead\n    cdef void appendChild(_Element parent, _Element child)\n\n    # added in lxml 3.3 as a safe replacement for appendChild()\n    # return -1 for exception, 0 for ok\n    cdef int appendChildToElement(_Element parent, _Element child) except -1\n\n    # recursively lookup a namespace in element or ancestors, or create it\n    cdef tree.xmlNs* findOrBuildNodeNsPrefix(\n        _Document doc, tree.xmlNode* c_node, const_xmlChar* href, const_xmlChar* prefix)\n\n    # find the Document of an Element, ElementTree or Document (itself!)\n    cdef _Document documentOrRaise(object input)\n\n    # find the root Element of an Element (itself!), ElementTree or Document\n    cdef _Element rootNodeOrRaise(object input)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/htmlparser.pxd",
    "content": "from libc.string cimport const_char\n\nfrom lxml.includes.tree cimport xmlDoc\nfrom lxml.includes.tree cimport xmlInputReadCallback, xmlInputCloseCallback\nfrom lxml.includes.xmlparser cimport xmlParserCtxt, xmlSAXHandler, xmlSAXHandlerV1\n\ncdef extern from \"libxml/HTMLparser.h\":\n    ctypedef enum htmlParserOption:\n        HTML_PARSE_NOERROR    # suppress error reports\n        HTML_PARSE_NOWARNING  # suppress warning reports\n        HTML_PARSE_PEDANTIC   # pedantic error reporting\n        HTML_PARSE_NOBLANKS   # remove blank nodes\n        HTML_PARSE_NONET      # Forbid network access\n        # libxml2 2.6.21+ only:\n        HTML_PARSE_RECOVER    # Relaxed parsing\n        HTML_PARSE_COMPACT    # compact small text nodes\n        # libxml2 2.7.7+ only:\n        HTML_PARSE_NOIMPLIED  # Do not add implied html/body... elements\n        # libxml2 2.7.8+ only:\n        HTML_PARSE_NODEFDTD   # do not default a doctype if not found\n        # libxml2 2.8.0+ only:\n        XML_PARSE_IGNORE_ENC  # ignore internal document encoding hint\n\n    xmlSAXHandlerV1 htmlDefaultSAXHandler\n\n    cdef xmlParserCtxt* htmlCreateMemoryParserCtxt(\n        char* buffer, int size) nogil\n    cdef xmlParserCtxt* htmlCreateFileParserCtxt(\n        char* filename, char* encoding) nogil\n    cdef xmlParserCtxt* htmlCreatePushParserCtxt(xmlSAXHandler* sax,\n                                                 void* user_data,\n                                                 char* chunk, int size,\n                                                 char* filename, int enc) nogil\n    cdef void htmlFreeParserCtxt(xmlParserCtxt* ctxt) nogil\n    cdef void htmlCtxtReset(xmlParserCtxt* ctxt) nogil\n    cdef int htmlCtxtUseOptions(xmlParserCtxt* ctxt, int options) nogil\n    cdef int htmlParseDocument(xmlParserCtxt* ctxt) nogil\n    cdef int htmlParseChunk(xmlParserCtxt* ctxt, \n                            char* chunk, int size, int terminate) nogil\n\n    cdef xmlDoc* htmlCtxtReadFile(xmlParserCtxt* ctxt,\n                                  char* filename, const_char* encoding,\n                                  int options) nogil\n    cdef xmlDoc* htmlCtxtReadDoc(xmlParserCtxt* ctxt,\n                                 char* buffer, char* URL, const_char* encoding,\n                                 int options) nogil\n    cdef xmlDoc* htmlCtxtReadIO(xmlParserCtxt* ctxt, \n                                xmlInputReadCallback ioread, \n                                xmlInputCloseCallback ioclose, \n                                void* ioctx,\n                                char* URL, const_char* encoding,\n                                int options) nogil\n    cdef xmlDoc* htmlCtxtReadMemory(xmlParserCtxt* ctxt,\n                                    char* buffer, int size,\n                                    char* filename, const_char* encoding,\n                                    int options) nogil\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libexslt/exslt.h",
    "content": "\n#ifndef __EXSLT_H__\n#define __EXSLT_H__\n\n#include <libxml/tree.h>\n#include <libxml/xpath.h>\n#include \"exsltexports.h\"\n#include <libexslt/exsltconfig.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nEXSLTPUBVAR const char *exsltLibraryVersion;\nEXSLTPUBVAR const int exsltLibexsltVersion;\nEXSLTPUBVAR const int exsltLibxsltVersion;\nEXSLTPUBVAR const int exsltLibxmlVersion;\n\n/**\n * EXSLT_COMMON_NAMESPACE:\n *\n * Namespace for EXSLT common functions\n */\n#define EXSLT_COMMON_NAMESPACE ((const xmlChar *) \"http://exslt.org/common\")\n/**\n * EXSLT_CRYPTO_NAMESPACE:\n *\n * Namespace for EXSLT crypto functions\n */\n#define EXSLT_CRYPTO_NAMESPACE ((const xmlChar *) \"http://exslt.org/crypto\")\n/**\n * EXSLT_MATH_NAMESPACE:\n *\n * Namespace for EXSLT math functions\n */\n#define EXSLT_MATH_NAMESPACE ((const xmlChar *) \"http://exslt.org/math\")\n/**\n * EXSLT_SETS_NAMESPACE:\n *\n * Namespace for EXSLT set functions\n */\n#define EXSLT_SETS_NAMESPACE ((const xmlChar *) \"http://exslt.org/sets\")\n/**\n * EXSLT_FUNCTIONS_NAMESPACE:\n *\n * Namespace for EXSLT functions extension functions\n */\n#define EXSLT_FUNCTIONS_NAMESPACE ((const xmlChar *) \"http://exslt.org/functions\")\n/**\n * EXSLT_STRINGS_NAMESPACE:\n *\n * Namespace for EXSLT strings functions\n */\n#define EXSLT_STRINGS_NAMESPACE ((const xmlChar *) \"http://exslt.org/strings\")\n/**\n * EXSLT_DATE_NAMESPACE:\n *\n * Namespace for EXSLT date functions\n */\n#define EXSLT_DATE_NAMESPACE ((const xmlChar *) \"http://exslt.org/dates-and-times\")\n/**\n * EXSLT_DYNAMIC_NAMESPACE:\n *\n * Namespace for EXSLT dynamic functions\n */\n#define EXSLT_DYNAMIC_NAMESPACE ((const xmlChar *) \"http://exslt.org/dynamic\")\n\n/**\n * SAXON_NAMESPACE:\n *\n * Namespace for SAXON extensions functions\n */\n#define SAXON_NAMESPACE ((const xmlChar *) \"http://icl.com/saxon\")\n\nEXSLTPUBFUN void EXSLTCALL exsltCommonRegister (void);\n#ifdef EXSLT_CRYPTO_ENABLED\nEXSLTPUBFUN void EXSLTCALL exsltCryptoRegister (void);\n#endif\nEXSLTPUBFUN void EXSLTCALL exsltMathRegister (void);\nEXSLTPUBFUN void EXSLTCALL exsltSetsRegister (void);\nEXSLTPUBFUN void EXSLTCALL exsltFuncRegister (void);\nEXSLTPUBFUN void EXSLTCALL exsltStrRegister (void);\nEXSLTPUBFUN void EXSLTCALL exsltDateRegister (void);\nEXSLTPUBFUN void EXSLTCALL exsltSaxonRegister (void);\nEXSLTPUBFUN void EXSLTCALL exsltDynRegister(void);\n\nEXSLTPUBFUN void EXSLTCALL exsltRegisterAll (void);\n\nEXSLTPUBFUN int EXSLTCALL exsltDateXpathCtxtRegister (xmlXPathContextPtr ctxt,\n                                                      const xmlChar *prefix);\nEXSLTPUBFUN int EXSLTCALL exsltMathXpathCtxtRegister (xmlXPathContextPtr ctxt,\n                                                      const xmlChar *prefix);\nEXSLTPUBFUN int EXSLTCALL exsltSetsXpathCtxtRegister (xmlXPathContextPtr ctxt,\n                                                      const xmlChar *prefix);\nEXSLTPUBFUN int EXSLTCALL exsltStrXpathCtxtRegister (xmlXPathContextPtr ctxt,\n                                                     const xmlChar *prefix);\n\n#ifdef __cplusplus\n}\n#endif\n#endif /* __EXSLT_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libexslt/exsltconfig.h",
    "content": "/*\n * exsltconfig.h: compile-time version information for the EXSLT library\n *\n * See Copyright for the status of this software.\n *\n * daniel@veillard.com\n */\n\n#ifndef __XML_EXSLTCONFIG_H__\n#define __XML_EXSLTCONFIG_H__\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * LIBEXSLT_DOTTED_VERSION:\n *\n * the version string like \"1.2.3\"\n */\n#define LIBEXSLT_DOTTED_VERSION \"1.1.33\"\n\n/**\n * LIBEXSLT_VERSION:\n *\n * the version number: 1.2.3 value is 10203\n */\n#define LIBEXSLT_VERSION 820\n\n/**\n * LIBEXSLT_VERSION_STRING:\n *\n * the version number string, 1.2.3 value is \"10203\"\n */\n#define LIBEXSLT_VERSION_STRING \"820\"\n\n/**\n * LIBEXSLT_VERSION_EXTRA:\n *\n * extra version information, used to show a CVS compilation\n */\n#define\tLIBEXSLT_VERSION_EXTRA \"\"\n\n/**\n * WITH_CRYPTO:\n *\n * Whether crypto support is configured into exslt\n */\n#if 0\n#define EXSLT_CRYPTO_ENABLED\n#endif\n\n/**\n * ATTRIBUTE_UNUSED:\n *\n * This macro is used to flag unused function parameters to GCC\n */\n#ifdef __GNUC__\n#ifdef HAVE_ANSIDECL_H\n#include <ansidecl.h>\n#endif\n#ifndef ATTRIBUTE_UNUSED\n#define ATTRIBUTE_UNUSED __attribute__((unused))\n#endif\n#else\n#define ATTRIBUTE_UNUSED\n#endif\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_EXSLTCONFIG_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libexslt/exsltexports.h",
    "content": "/*\n * exsltexports.h : macros for marking symbols as exportable/importable.\n *\n * See Copyright for the status of this software.\n *\n * igor@zlatkovic.com\n */\n\n#ifndef __EXSLT_EXPORTS_H__\n#define __EXSLT_EXPORTS_H__\n\n/**\n * EXSLTPUBFUN, EXSLTPUBVAR, EXSLTCALL\n *\n * Macros which declare an exportable function, an exportable variable and\n * the calling convention used for functions.\n *\n * Please use an extra block for every platform/compiler combination when\n * modifying this, rather than overlong #ifdef lines. This helps\n * readability as well as the fact that different compilers on the same\n * platform might need different definitions.\n */\n\n/**\n * EXSLTPUBFUN:\n *\n * Macros which declare an exportable function\n */\n#define EXSLTPUBFUN\n/**\n * EXSLTPUBVAR:\n *\n * Macros which declare an exportable variable\n */\n#define EXSLTPUBVAR extern\n/**\n * EXSLTCALL:\n *\n * Macros which declare the called convention for exported functions\n */\n#define EXSLTCALL\n\n/** DOC_DISABLE */\n\n/* Windows platform with MS compiler */\n#if defined(_WIN32) && defined(_MSC_VER)\n  #undef EXSLTPUBFUN\n  #undef EXSLTPUBVAR\n  #undef EXSLTCALL\n  #if defined(IN_LIBEXSLT) && !defined(LIBEXSLT_STATIC)\n    #define EXSLTPUBFUN __declspec(dllexport)\n    #define EXSLTPUBVAR __declspec(dllexport)\n  #else\n    #define EXSLTPUBFUN\n    #if !defined(LIBEXSLT_STATIC)\n      #define EXSLTPUBVAR __declspec(dllimport) extern\n    #else\n      #define EXSLTPUBVAR extern\n    #endif\n  #endif\n  #define EXSLTCALL __cdecl\n  #if !defined _REENTRANT\n    #define _REENTRANT\n  #endif\n#endif\n\n/* Windows platform with Borland compiler */\n#if defined(_WIN32) && defined(__BORLANDC__)\n  #undef EXSLTPUBFUN\n  #undef EXSLTPUBVAR\n  #undef EXSLTCALL\n  #if defined(IN_LIBEXSLT) && !defined(LIBEXSLT_STATIC)\n    #define EXSLTPUBFUN __declspec(dllexport)\n    #define EXSLTPUBVAR __declspec(dllexport) extern\n  #else\n    #define EXSLTPUBFUN\n    #if !defined(LIBEXSLT_STATIC)\n      #define EXSLTPUBVAR __declspec(dllimport) extern\n    #else\n      #define EXSLTPUBVAR extern\n    #endif\n  #endif\n  #define EXSLTCALL __cdecl\n  #if !defined _REENTRANT\n    #define _REENTRANT\n  #endif\n#endif\n\n/* Windows platform with GNU compiler (Mingw) */\n#if defined(_WIN32) && defined(__MINGW32__)\n  #undef EXSLTPUBFUN\n  #undef EXSLTPUBVAR\n  #undef EXSLTCALL\n/*\n  #if defined(IN_LIBEXSLT) && !defined(LIBEXSLT_STATIC)\n*/\n  #if !defined(LIBEXSLT_STATIC)\n    #define EXSLTPUBFUN __declspec(dllexport)\n    #define EXSLTPUBVAR __declspec(dllexport) extern\n  #else\n    #define EXSLTPUBFUN\n    #if !defined(LIBEXSLT_STATIC)\n      #define EXSLTPUBVAR __declspec(dllimport) extern\n    #else\n      #define EXSLTPUBVAR extern\n    #endif\n  #endif\n  #define EXSLTCALL __cdecl\n  #if !defined _REENTRANT\n    #define _REENTRANT\n  #endif\n#endif\n\n/* Cygwin platform (does not define _WIN32), GNU compiler */\n#if defined(__CYGWIN__)\n  #undef EXSLTPUBFUN\n  #undef EXSLTPUBVAR\n  #undef EXSLTCALL\n  #if defined(IN_LIBEXSLT) && !defined(LIBEXSLT_STATIC)\n    #define EXSLTPUBFUN __declspec(dllexport)\n    #define EXSLTPUBVAR __declspec(dllexport)\n  #else\n    #define EXSLTPUBFUN\n    #if !defined(LIBEXSLT_STATIC)\n      #define EXSLTPUBVAR __declspec(dllimport) extern\n    #else\n      #define EXSLTPUBVAR extern\n    #endif\n  #endif\n  #define EXSLTCALL __cdecl\n#endif\n\n/* Compatibility */\n#if !defined(LIBEXSLT_PUBLIC)\n#define LIBEXSLT_PUBLIC EXSLTPUBVAR\n#endif\n\n#endif /* __EXSLT_EXPORTS_H__ */\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/DOCBparser.h",
    "content": "/*\n * Summary: old DocBook SGML parser\n * Description: interface for a DocBook SGML non-verifying parser\n * This code is DEPRECATED, and should not be used anymore.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __DOCB_PARSER_H__\n#define __DOCB_PARSER_H__\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_DOCB_ENABLED\n\n#include <libxml/parser.h>\n#include <libxml/parserInternals.h>\n\n#ifndef IN_LIBXML\n#ifdef __GNUC__\n#warning \"The DOCBparser module has been deprecated in libxml2-2.6.0\"\n#endif\n#endif\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * Most of the back-end structures from XML and SGML are shared.\n */\ntypedef xmlParserCtxt docbParserCtxt;\ntypedef xmlParserCtxtPtr docbParserCtxtPtr;\ntypedef xmlSAXHandler docbSAXHandler;\ntypedef xmlSAXHandlerPtr docbSAXHandlerPtr;\ntypedef xmlParserInput docbParserInput;\ntypedef xmlParserInputPtr docbParserInputPtr;\ntypedef xmlDocPtr docbDocPtr;\n\n/*\n * There is only few public functions.\n */\nXMLPUBFUN int XMLCALL\n\t\t     docbEncodeEntities(unsigned char *out,\n                                        int *outlen,\n                                        const unsigned char *in,\n                                        int *inlen, int quoteChar);\n\nXMLPUBFUN docbDocPtr XMLCALL\n\t\t     docbSAXParseDoc   (xmlChar *cur,\n                                        const char *encoding,\n                                        docbSAXHandlerPtr sax,\n                                        void *userData);\nXMLPUBFUN docbDocPtr XMLCALL\n\t\t     docbParseDoc      (xmlChar *cur,\n                                        const char *encoding);\nXMLPUBFUN docbDocPtr XMLCALL\n\t\t     docbSAXParseFile  (const char *filename,\n                                        const char *encoding,\n                                        docbSAXHandlerPtr sax,\n                                        void *userData);\nXMLPUBFUN docbDocPtr XMLCALL\n\t\t     docbParseFile     (const char *filename,\n                                        const char *encoding);\n\n/**\n * Interfaces for the Push mode.\n */\nXMLPUBFUN void XMLCALL\n\t\t     docbFreeParserCtxt      (docbParserCtxtPtr ctxt);\nXMLPUBFUN docbParserCtxtPtr XMLCALL\n\t\t     docbCreatePushParserCtxt(docbSAXHandlerPtr sax,\n                                              void *user_data,\n                                              const char *chunk,\n                                              int size,\n                                              const char *filename,\n                                              xmlCharEncoding enc);\nXMLPUBFUN int XMLCALL\n\t\t     docbParseChunk          (docbParserCtxtPtr ctxt,\n                                              const char *chunk,\n                                              int size,\n                                              int terminate);\nXMLPUBFUN docbParserCtxtPtr XMLCALL\n\t\t     docbCreateFileParserCtxt(const char *filename,\n                                              const char *encoding);\nXMLPUBFUN int XMLCALL\n\t\t     docbParseDocument       (docbParserCtxtPtr ctxt);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_DOCB_ENABLED */\n\n#endif /* __DOCB_PARSER_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/HTMLparser.h",
    "content": "/*\n * Summary: interface for an HTML 4.0 non-verifying parser\n * Description: this module implements an HTML 4.0 non-verifying parser\n *              with API compatible with the XML parser ones. It should\n *              be able to parse \"real world\" HTML, even if severely\n *              broken from a specification point of view.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __HTML_PARSER_H__\n#define __HTML_PARSER_H__\n#include <libxml/xmlversion.h>\n#include <libxml/parser.h>\n\n#ifdef LIBXML_HTML_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * Most of the back-end structures from XML and HTML are shared.\n */\ntypedef xmlParserCtxt htmlParserCtxt;\ntypedef xmlParserCtxtPtr htmlParserCtxtPtr;\ntypedef xmlParserNodeInfo htmlParserNodeInfo;\ntypedef xmlSAXHandler htmlSAXHandler;\ntypedef xmlSAXHandlerPtr htmlSAXHandlerPtr;\ntypedef xmlParserInput htmlParserInput;\ntypedef xmlParserInputPtr htmlParserInputPtr;\ntypedef xmlDocPtr htmlDocPtr;\ntypedef xmlNodePtr htmlNodePtr;\n\n/*\n * Internal description of an HTML element, representing HTML 4.01\n * and XHTML 1.0 (which share the same structure).\n */\ntypedef struct _htmlElemDesc htmlElemDesc;\ntypedef htmlElemDesc *htmlElemDescPtr;\nstruct _htmlElemDesc {\n    const char *name;\t/* The tag name */\n    char startTag;      /* Whether the start tag can be implied */\n    char endTag;        /* Whether the end tag can be implied */\n    char saveEndTag;    /* Whether the end tag should be saved */\n    char empty;         /* Is this an empty element ? */\n    char depr;          /* Is this a deprecated element ? */\n    char dtd;           /* 1: only in Loose DTD, 2: only Frameset one */\n    char isinline;      /* is this a block 0 or inline 1 element */\n    const char *desc;   /* the description */\n\n/* NRK Jan.2003\n * New fields encapsulating HTML structure\n *\n * Bugs:\n *\tThis is a very limited representation.  It fails to tell us when\n *\tan element *requires* subelements (we only have whether they're\n *\tallowed or not), and it doesn't tell us where CDATA and PCDATA\n *\tare allowed.  Some element relationships are not fully represented:\n *\tthese are flagged with the word MODIFIER\n */\n    const char** subelts;\t\t/* allowed sub-elements of this element */\n    const char* defaultsubelt;\t/* subelement for suggested auto-repair\n\t\t\t\t\t   if necessary or NULL */\n    const char** attrs_opt;\t\t/* Optional Attributes */\n    const char** attrs_depr;\t\t/* Additional deprecated attributes */\n    const char** attrs_req;\t\t/* Required attributes */\n};\n\n/*\n * Internal description of an HTML entity.\n */\ntypedef struct _htmlEntityDesc htmlEntityDesc;\ntypedef htmlEntityDesc *htmlEntityDescPtr;\nstruct _htmlEntityDesc {\n    unsigned int value;\t/* the UNICODE value for the character */\n    const char *name;\t/* The entity name */\n    const char *desc;   /* the description */\n};\n\n/*\n * There is only few public functions.\n */\nXMLPUBFUN const htmlElemDesc * XMLCALL\n\t\t\thtmlTagLookup\t(const xmlChar *tag);\nXMLPUBFUN const htmlEntityDesc * XMLCALL\n\t\t\thtmlEntityLookup(const xmlChar *name);\nXMLPUBFUN const htmlEntityDesc * XMLCALL\n\t\t\thtmlEntityValueLookup(unsigned int value);\n\nXMLPUBFUN int XMLCALL\n\t\t\thtmlIsAutoClosed(htmlDocPtr doc,\n\t\t\t\t\t htmlNodePtr elem);\nXMLPUBFUN int XMLCALL\n\t\t\thtmlAutoCloseTag(htmlDocPtr doc,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t htmlNodePtr elem);\nXMLPUBFUN const htmlEntityDesc * XMLCALL\n\t\t\thtmlParseEntityRef(htmlParserCtxtPtr ctxt,\n\t\t\t\t\t const xmlChar **str);\nXMLPUBFUN int XMLCALL\n\t\t\thtmlParseCharRef(htmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\thtmlParseElement(htmlParserCtxtPtr ctxt);\n\nXMLPUBFUN htmlParserCtxtPtr XMLCALL\n\t\t\thtmlNewParserCtxt(void);\n\nXMLPUBFUN htmlParserCtxtPtr XMLCALL\n\t\t\thtmlCreateMemoryParserCtxt(const char *buffer,\n\t\t\t\t\t\t   int size);\n\nXMLPUBFUN int XMLCALL\n\t\t\thtmlParseDocument(htmlParserCtxtPtr ctxt);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\t\thtmlSAXParseDoc\t(const xmlChar *cur,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t htmlSAXHandlerPtr sax,\n\t\t\t\t\t void *userData);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\t\thtmlParseDoc\t(const xmlChar *cur,\n\t\t\t\t\t const char *encoding);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\t\thtmlSAXParseFile(const char *filename,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t htmlSAXHandlerPtr sax,\n\t\t\t\t\t void *userData);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\t\thtmlParseFile\t(const char *filename,\n\t\t\t\t\t const char *encoding);\nXMLPUBFUN int XMLCALL\n\t\t\tUTF8ToHtml\t(unsigned char *out,\n\t\t\t\t\t int *outlen,\n\t\t\t\t\t const unsigned char *in,\n\t\t\t\t\t int *inlen);\nXMLPUBFUN int XMLCALL\n\t\t\thtmlEncodeEntities(unsigned char *out,\n\t\t\t\t\t int *outlen,\n\t\t\t\t\t const unsigned char *in,\n\t\t\t\t\t int *inlen, int quoteChar);\nXMLPUBFUN int XMLCALL\n\t\t\thtmlIsScriptAttribute(const xmlChar *name);\nXMLPUBFUN int XMLCALL\n\t\t\thtmlHandleOmittedElem(int val);\n\n#ifdef LIBXML_PUSH_ENABLED\n/**\n * Interfaces for the Push mode.\n */\nXMLPUBFUN htmlParserCtxtPtr XMLCALL\n\t\t\thtmlCreatePushParserCtxt(htmlSAXHandlerPtr sax,\n\t\t\t\t\t\t void *user_data,\n\t\t\t\t\t\t const char *chunk,\n\t\t\t\t\t\t int size,\n\t\t\t\t\t\t const char *filename,\n\t\t\t\t\t\t xmlCharEncoding enc);\nXMLPUBFUN int XMLCALL\n\t\t\thtmlParseChunk\t\t(htmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t const char *chunk,\n\t\t\t\t\t\t int size,\n\t\t\t\t\t\t int terminate);\n#endif /* LIBXML_PUSH_ENABLED */\n\nXMLPUBFUN void XMLCALL\n\t\t\thtmlFreeParserCtxt\t(htmlParserCtxtPtr ctxt);\n\n/*\n * New set of simpler/more flexible APIs\n */\n/**\n * xmlParserOption:\n *\n * This is the set of XML parser options that can be passed down\n * to the xmlReadDoc() and similar calls.\n */\ntypedef enum {\n    HTML_PARSE_RECOVER  = 1<<0, /* Relaxed parsing */\n    HTML_PARSE_NODEFDTD = 1<<2, /* do not default a doctype if not found */\n    HTML_PARSE_NOERROR\t= 1<<5,\t/* suppress error reports */\n    HTML_PARSE_NOWARNING= 1<<6,\t/* suppress warning reports */\n    HTML_PARSE_PEDANTIC\t= 1<<7,\t/* pedantic error reporting */\n    HTML_PARSE_NOBLANKS\t= 1<<8,\t/* remove blank nodes */\n    HTML_PARSE_NONET\t= 1<<11,/* Forbid network access */\n    HTML_PARSE_NOIMPLIED= 1<<13,/* Do not add implied html/body... elements */\n    HTML_PARSE_COMPACT  = 1<<16,/* compact small text nodes */\n    HTML_PARSE_IGNORE_ENC=1<<21 /* ignore internal document encoding hint */\n} htmlParserOption;\n\nXMLPUBFUN void XMLCALL\n\t\thtmlCtxtReset\t\t(htmlParserCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\thtmlCtxtUseOptions\t(htmlParserCtxtPtr ctxt,\n\t\t\t\t\t int options);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\thtmlReadDoc\t\t(const xmlChar *cur,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\thtmlReadFile\t\t(const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\thtmlReadMemory\t\t(const char *buffer,\n\t\t\t\t\t int size,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\thtmlReadFd\t\t(int fd,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\thtmlReadIO\t\t(xmlInputReadCallback ioread,\n\t\t\t\t\t xmlInputCloseCallback ioclose,\n\t\t\t\t\t void *ioctx,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\thtmlCtxtReadDoc\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t const xmlChar *cur,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\thtmlCtxtReadFile\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t const char *filename,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\thtmlCtxtReadMemory\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t const char *buffer,\n\t\t\t\t\t int size,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\thtmlCtxtReadFd\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t int fd,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\thtmlCtxtReadIO\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t xmlInputReadCallback ioread,\n\t\t\t\t\t xmlInputCloseCallback ioclose,\n\t\t\t\t\t void *ioctx,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\n\n/* NRK/Jan2003: further knowledge of HTML structure\n */\ntypedef enum {\n  HTML_NA = 0 ,\t\t/* something we don't check at all */\n  HTML_INVALID = 0x1 ,\n  HTML_DEPRECATED = 0x2 ,\n  HTML_VALID = 0x4 ,\n  HTML_REQUIRED = 0xc /* VALID bit set so ( & HTML_VALID ) is TRUE */\n} htmlStatus ;\n\n/* Using htmlElemDesc rather than name here, to emphasise the fact\n   that otherwise there's a lookup overhead\n*/\nXMLPUBFUN htmlStatus XMLCALL htmlAttrAllowed(const htmlElemDesc*, const xmlChar*, int) ;\nXMLPUBFUN int XMLCALL htmlElementAllowedHere(const htmlElemDesc*, const xmlChar*) ;\nXMLPUBFUN htmlStatus XMLCALL htmlElementStatusHere(const htmlElemDesc*, const htmlElemDesc*) ;\nXMLPUBFUN htmlStatus XMLCALL htmlNodeStatus(const htmlNodePtr, int) ;\n/**\n * htmlDefaultSubelement:\n * @elt: HTML element\n *\n * Returns the default subelement for this element\n */\n#define htmlDefaultSubelement(elt) elt->defaultsubelt\n/**\n * htmlElementAllowedHereDesc:\n * @parent: HTML parent element\n * @elt: HTML element\n *\n * Checks whether an HTML element description may be a\n * direct child of the specified element.\n *\n * Returns 1 if allowed; 0 otherwise.\n */\n#define htmlElementAllowedHereDesc(parent,elt) \\\n\thtmlElementAllowedHere((parent), (elt)->name)\n/**\n * htmlRequiredAttrs:\n * @elt: HTML element\n *\n * Returns the attributes required for the specified element.\n */\n#define htmlRequiredAttrs(elt) (elt)->attrs_req\n\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_HTML_ENABLED */\n#endif /* __HTML_PARSER_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/HTMLtree.h",
    "content": "/*\n * Summary: specific APIs to process HTML tree, especially serialization\n * Description: this module implements a few function needed to process\n *              tree in an HTML specific way.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __HTML_TREE_H__\n#define __HTML_TREE_H__\n\n#include <stdio.h>\n#include <libxml/xmlversion.h>\n#include <libxml/tree.h>\n#include <libxml/HTMLparser.h>\n\n#ifdef LIBXML_HTML_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n\n/**\n * HTML_TEXT_NODE:\n *\n * Macro. A text node in a HTML document is really implemented\n * the same way as a text node in an XML document.\n */\n#define HTML_TEXT_NODE\t\tXML_TEXT_NODE\n/**\n * HTML_ENTITY_REF_NODE:\n *\n * Macro. An entity reference in a HTML document is really implemented\n * the same way as an entity reference in an XML document.\n */\n#define HTML_ENTITY_REF_NODE\tXML_ENTITY_REF_NODE\n/**\n * HTML_COMMENT_NODE:\n *\n * Macro. A comment in a HTML document is really implemented\n * the same way as a comment in an XML document.\n */\n#define HTML_COMMENT_NODE\tXML_COMMENT_NODE\n/**\n * HTML_PRESERVE_NODE:\n *\n * Macro. A preserved node in a HTML document is really implemented\n * the same way as a CDATA section in an XML document.\n */\n#define HTML_PRESERVE_NODE\tXML_CDATA_SECTION_NODE\n/**\n * HTML_PI_NODE:\n *\n * Macro. A processing instruction in a HTML document is really implemented\n * the same way as a processing instruction in an XML document.\n */\n#define HTML_PI_NODE\t\tXML_PI_NODE\n\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\thtmlNewDoc\t\t(const xmlChar *URI,\n\t\t\t\t\t const xmlChar *ExternalID);\nXMLPUBFUN htmlDocPtr XMLCALL\n\t\thtmlNewDocNoDtD\t\t(const xmlChar *URI,\n\t\t\t\t\t const xmlChar *ExternalID);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\thtmlGetMetaEncoding\t(htmlDocPtr doc);\nXMLPUBFUN int XMLCALL\n\t\thtmlSetMetaEncoding\t(htmlDocPtr doc,\n\t\t\t\t\t const xmlChar *encoding);\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN void XMLCALL\n\t\thtmlDocDumpMemory\t(xmlDocPtr cur,\n\t\t\t\t\t xmlChar **mem,\n\t\t\t\t\t int *size);\nXMLPUBFUN void XMLCALL\n\t\thtmlDocDumpMemoryFormat\t(xmlDocPtr cur,\n\t\t\t\t\t xmlChar **mem,\n\t\t\t\t\t int *size,\n\t\t\t\t\t int format);\nXMLPUBFUN int XMLCALL\n\t\thtmlDocDump\t\t(FILE *f,\n\t\t\t\t\t xmlDocPtr cur);\nXMLPUBFUN int XMLCALL\n\t\thtmlSaveFile\t\t(const char *filename,\n\t\t\t\t\t xmlDocPtr cur);\nXMLPUBFUN int XMLCALL\n\t\thtmlNodeDump\t\t(xmlBufferPtr buf,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr cur);\nXMLPUBFUN void XMLCALL\n\t\thtmlNodeDumpFile\t(FILE *out,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr cur);\nXMLPUBFUN int XMLCALL\n\t\thtmlNodeDumpFileFormat\t(FILE *out,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr cur,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int format);\nXMLPUBFUN int XMLCALL\n\t\thtmlSaveFileEnc\t\t(const char *filename,\n\t\t\t\t\t xmlDocPtr cur,\n\t\t\t\t\t const char *encoding);\nXMLPUBFUN int XMLCALL\n\t\thtmlSaveFileFormat\t(const char *filename,\n\t\t\t\t\t xmlDocPtr cur,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int format);\n\nXMLPUBFUN void XMLCALL\n\t\thtmlNodeDumpFormatOutput(xmlOutputBufferPtr buf,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr cur,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int format);\nXMLPUBFUN void XMLCALL\n\t\thtmlDocContentDumpOutput(xmlOutputBufferPtr buf,\n\t\t\t\t\t xmlDocPtr cur,\n\t\t\t\t\t const char *encoding);\nXMLPUBFUN void XMLCALL\n\t\thtmlDocContentDumpFormatOutput(xmlOutputBufferPtr buf,\n\t\t\t\t\t xmlDocPtr cur,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int format);\nXMLPUBFUN void XMLCALL\n\t\thtmlNodeDumpOutput\t(xmlOutputBufferPtr buf,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr cur,\n\t\t\t\t\t const char *encoding);\n\n#endif /* LIBXML_OUTPUT_ENABLED */\n\nXMLPUBFUN int XMLCALL\n\t\thtmlIsBooleanAttr\t(const xmlChar *name);\n\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_HTML_ENABLED */\n\n#endif /* __HTML_TREE_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/SAX.h",
    "content": "/*\n * Summary: Old SAX version 1 handler, deprecated\n * Description: DEPRECATED set of SAX version 1 interfaces used to\n *              build the DOM tree.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n\n#ifndef __XML_SAX_H__\n#define __XML_SAX_H__\n\n#include <stdio.h>\n#include <stdlib.h>\n#include <libxml/xmlversion.h>\n#include <libxml/parser.h>\n#include <libxml/xlink.h>\n\n#ifdef LIBXML_LEGACY_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\nXMLPUBFUN const xmlChar * XMLCALL\n\t\tgetPublicId\t\t\t(void *ctx);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\tgetSystemId\t\t\t(void *ctx);\nXMLPUBFUN void XMLCALL\n\t\tsetDocumentLocator\t\t(void *ctx,\n\t\t\t\t\t\t xmlSAXLocatorPtr loc);\n\nXMLPUBFUN int XMLCALL\n\t\tgetLineNumber\t\t\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\t\tgetColumnNumber\t\t\t(void *ctx);\n\nXMLPUBFUN int XMLCALL\n\t\tisStandalone\t\t\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\t\thasInternalSubset\t\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\t\thasExternalSubset\t\t(void *ctx);\n\nXMLPUBFUN void XMLCALL\n\t\tinternalSubset\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ExternalID,\n\t\t\t\t\t\t const xmlChar *SystemID);\nXMLPUBFUN void XMLCALL\n\t\texternalSubset\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ExternalID,\n\t\t\t\t\t\t const xmlChar *SystemID);\nXMLPUBFUN xmlEntityPtr XMLCALL\n\t\tgetEntity\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlEntityPtr XMLCALL\n\t\tgetParameterEntity\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlParserInputPtr XMLCALL\n\t\tresolveEntity\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *publicId,\n\t\t\t\t\t\t const xmlChar *systemId);\n\nXMLPUBFUN void XMLCALL\n\t\tentityDecl\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t int type,\n\t\t\t\t\t\t const xmlChar *publicId,\n\t\t\t\t\t\t const xmlChar *systemId,\n\t\t\t\t\t\t xmlChar *content);\nXMLPUBFUN void XMLCALL\n\t\tattributeDecl\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *elem,\n\t\t\t\t\t\t const xmlChar *fullname,\n\t\t\t\t\t\t int type,\n\t\t\t\t\t\t int def,\n\t\t\t\t\t\t const xmlChar *defaultValue,\n\t\t\t\t\t\t xmlEnumerationPtr tree);\nXMLPUBFUN void XMLCALL\n\t\telementDecl\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t int type,\n\t\t\t\t\t\t xmlElementContentPtr content);\nXMLPUBFUN void XMLCALL\n\t\tnotationDecl\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *publicId,\n\t\t\t\t\t\t const xmlChar *systemId);\nXMLPUBFUN void XMLCALL\n\t\tunparsedEntityDecl\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *publicId,\n\t\t\t\t\t\t const xmlChar *systemId,\n\t\t\t\t\t\t const xmlChar *notationName);\n\nXMLPUBFUN void XMLCALL\n\t\tstartDocument\t\t\t(void *ctx);\nXMLPUBFUN void XMLCALL\n\t\tendDocument\t\t\t(void *ctx);\nXMLPUBFUN void XMLCALL\n\t\tattribute\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *fullname,\n\t\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN void XMLCALL\n\t\tstartElement\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *fullname,\n\t\t\t\t\t\t const xmlChar **atts);\nXMLPUBFUN void XMLCALL\n\t\tendElement\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN void XMLCALL\n\t\treference\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN void XMLCALL\n\t\tcharacters\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *ch,\n\t\t\t\t\t\t int len);\nXMLPUBFUN void XMLCALL\n\t\tignorableWhitespace\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *ch,\n\t\t\t\t\t\t int len);\nXMLPUBFUN void XMLCALL\n\t\tprocessingInstruction\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *target,\n\t\t\t\t\t\t const xmlChar *data);\nXMLPUBFUN void XMLCALL\n\t\tglobalNamespace\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *href,\n\t\t\t\t\t\t const xmlChar *prefix);\nXMLPUBFUN void XMLCALL\n\t\tsetNamespace\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlNsPtr XMLCALL\n\t\tgetNamespace\t\t\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\t\tcheckNamespace\t\t\t(void *ctx,\n\t\t\t\t\t\t xmlChar *nameSpace);\nXMLPUBFUN void XMLCALL\n\t\tnamespaceDecl\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *href,\n\t\t\t\t\t\t const xmlChar *prefix);\nXMLPUBFUN void XMLCALL\n\t\tcomment\t\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN void XMLCALL\n\t\tcdataBlock\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *value,\n\t\t\t\t\t\t int len);\n\n#ifdef LIBXML_SAX1_ENABLED\nXMLPUBFUN void XMLCALL\n\t\tinitxmlDefaultSAXHandler\t(xmlSAXHandlerV1 *hdlr,\n\t\t\t\t\t\t int warning);\n#ifdef LIBXML_HTML_ENABLED\nXMLPUBFUN void XMLCALL\n\t\tinithtmlDefaultSAXHandler\t(xmlSAXHandlerV1 *hdlr);\n#endif\n#ifdef LIBXML_DOCB_ENABLED\nXMLPUBFUN void XMLCALL\n\t\tinitdocbDefaultSAXHandler\t(xmlSAXHandlerV1 *hdlr);\n#endif\n#endif /* LIBXML_SAX1_ENABLED */\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_LEGACY_ENABLED */\n\n#endif /* __XML_SAX_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/SAX2.h",
    "content": "/*\n * Summary: SAX2 parser interface used to build the DOM tree\n * Description: those are the default SAX2 interfaces used by\n *              the library when building DOM tree.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n\n#ifndef __XML_SAX2_H__\n#define __XML_SAX2_H__\n\n#include <stdio.h>\n#include <stdlib.h>\n#include <libxml/xmlversion.h>\n#include <libxml/parser.h>\n#include <libxml/xlink.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\nXMLPUBFUN const xmlChar * XMLCALL\n\t\txmlSAX2GetPublicId\t\t(void *ctx);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\txmlSAX2GetSystemId\t\t(void *ctx);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2SetDocumentLocator\t(void *ctx,\n\t\t\t\t\t\t xmlSAXLocatorPtr loc);\n\nXMLPUBFUN int XMLCALL\n\t\txmlSAX2GetLineNumber\t\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\t\txmlSAX2GetColumnNumber\t\t(void *ctx);\n\nXMLPUBFUN int XMLCALL\n\t\txmlSAX2IsStandalone\t\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\t\txmlSAX2HasInternalSubset\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\t\txmlSAX2HasExternalSubset\t(void *ctx);\n\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2InternalSubset\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ExternalID,\n\t\t\t\t\t\t const xmlChar *SystemID);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2ExternalSubset\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ExternalID,\n\t\t\t\t\t\t const xmlChar *SystemID);\nXMLPUBFUN xmlEntityPtr XMLCALL\n\t\txmlSAX2GetEntity\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlEntityPtr XMLCALL\n\t\txmlSAX2GetParameterEntity\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlParserInputPtr XMLCALL\n\t\txmlSAX2ResolveEntity\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *publicId,\n\t\t\t\t\t\t const xmlChar *systemId);\n\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2EntityDecl\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t int type,\n\t\t\t\t\t\t const xmlChar *publicId,\n\t\t\t\t\t\t const xmlChar *systemId,\n\t\t\t\t\t\t xmlChar *content);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2AttributeDecl\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *elem,\n\t\t\t\t\t\t const xmlChar *fullname,\n\t\t\t\t\t\t int type,\n\t\t\t\t\t\t int def,\n\t\t\t\t\t\t const xmlChar *defaultValue,\n\t\t\t\t\t\t xmlEnumerationPtr tree);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2ElementDecl\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t int type,\n\t\t\t\t\t\t xmlElementContentPtr content);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2NotationDecl\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *publicId,\n\t\t\t\t\t\t const xmlChar *systemId);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2UnparsedEntityDecl\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *publicId,\n\t\t\t\t\t\t const xmlChar *systemId,\n\t\t\t\t\t\t const xmlChar *notationName);\n\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2StartDocument\t\t(void *ctx);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2EndDocument\t\t(void *ctx);\n#if defined(LIBXML_SAX1_ENABLED) || defined(LIBXML_HTML_ENABLED) || \\\n    defined(LIBXML_WRITER_ENABLED) || defined(LIBXML_DOCB_ENABLED) || \\\n    defined(LIBXML_LEGACY_ENABLED)\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2StartElement\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *fullname,\n\t\t\t\t\t\t const xmlChar **atts);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2EndElement\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name);\n#endif /* LIBXML_SAX1_ENABLED or LIBXML_HTML_ENABLED or LIBXML_LEGACY_ENABLED */\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2StartElementNs\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *localname,\n\t\t\t\t\t\t const xmlChar *prefix,\n\t\t\t\t\t\t const xmlChar *URI,\n\t\t\t\t\t\t int nb_namespaces,\n\t\t\t\t\t\t const xmlChar **namespaces,\n\t\t\t\t\t\t int nb_attributes,\n\t\t\t\t\t\t int nb_defaulted,\n\t\t\t\t\t\t const xmlChar **attributes);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2EndElementNs\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *localname,\n\t\t\t\t\t\t const xmlChar *prefix,\n\t\t\t\t\t\t const xmlChar *URI);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2Reference\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2Characters\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *ch,\n\t\t\t\t\t\t int len);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2IgnorableWhitespace\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *ch,\n\t\t\t\t\t\t int len);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2ProcessingInstruction\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *target,\n\t\t\t\t\t\t const xmlChar *data);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2Comment\t\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2CDataBlock\t\t(void *ctx,\n\t\t\t\t\t\t const xmlChar *value,\n\t\t\t\t\t\t int len);\n\n#ifdef LIBXML_SAX1_ENABLED\nXMLPUBFUN int XMLCALL\n\t\txmlSAXDefaultVersion\t\t(int version);\n#endif /* LIBXML_SAX1_ENABLED */\n\nXMLPUBFUN int XMLCALL\n\t\txmlSAXVersion\t\t\t(xmlSAXHandler *hdlr,\n\t\t\t\t\t\t int version);\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2InitDefaultSAXHandler    (xmlSAXHandler *hdlr,\n\t\t\t\t\t\t int warning);\n#ifdef LIBXML_HTML_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2InitHtmlDefaultSAXHandler(xmlSAXHandler *hdlr);\nXMLPUBFUN void XMLCALL\n\t\thtmlDefaultSAXHandlerInit\t(void);\n#endif\n#ifdef LIBXML_DOCB_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlSAX2InitDocbDefaultSAXHandler(xmlSAXHandler *hdlr);\nXMLPUBFUN void XMLCALL\n\t\tdocbDefaultSAXHandlerInit\t(void);\n#endif\nXMLPUBFUN void XMLCALL\n\t\txmlDefaultSAXHandlerInit\t(void);\n#ifdef __cplusplus\n}\n#endif\n#endif /* __XML_SAX2_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/c14n.h",
    "content": "/*\n * Summary: Provide Canonical XML and Exclusive XML Canonicalization\n * Description: the c14n modules provides a\n *\n * \"Canonical XML\" implementation\n * http://www.w3.org/TR/xml-c14n\n *\n * and an\n *\n * \"Exclusive XML Canonicalization\" implementation\n * http://www.w3.org/TR/xml-exc-c14n\n\n * Copy: See Copyright for the status of this software.\n *\n * Author: Aleksey Sanin <aleksey@aleksey.com>\n */\n#ifndef __XML_C14N_H__\n#define __XML_C14N_H__\n#ifdef LIBXML_C14N_ENABLED\n#ifdef LIBXML_OUTPUT_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif /* __cplusplus */\n\n#include <libxml/xmlversion.h>\n#include <libxml/tree.h>\n#include <libxml/xpath.h>\n\n/*\n * XML Canonicazation\n * http://www.w3.org/TR/xml-c14n\n *\n * Exclusive XML Canonicazation\n * http://www.w3.org/TR/xml-exc-c14n\n *\n * Canonical form of an XML document could be created if and only if\n *  a) default attributes (if any) are added to all nodes\n *  b) all character and parsed entity references are resolved\n * In order to achive this in libxml2 the document MUST be loaded with\n * following global setings:\n *\n *    xmlLoadExtDtdDefaultValue = XML_DETECT_IDS | XML_COMPLETE_ATTRS;\n *    xmlSubstituteEntitiesDefault(1);\n *\n * or corresponding parser context setting:\n *    xmlParserCtxtPtr ctxt;\n *\n *    ...\n *    ctxt->loadsubset = XML_DETECT_IDS | XML_COMPLETE_ATTRS;\n *    ctxt->replaceEntities = 1;\n *    ...\n */\n\n/*\n * xmlC14NMode:\n *\n * Predefined values for C14N modes\n *\n */\ntypedef enum {\n    XML_C14N_1_0            = 0,    /* Origianal C14N 1.0 spec */\n    XML_C14N_EXCLUSIVE_1_0  = 1,    /* Exclusive C14N 1.0 spec */\n    XML_C14N_1_1            = 2     /* C14N 1.1 spec */\n} xmlC14NMode;\n\nXMLPUBFUN int XMLCALL\n\t\txmlC14NDocSaveTo\t(xmlDocPtr doc,\n\t\t\t\t\t xmlNodeSetPtr nodes,\n\t\t\t\t\t int mode, /* a xmlC14NMode */\n\t\t\t\t\t xmlChar **inclusive_ns_prefixes,\n\t\t\t\t\t int with_comments,\n\t\t\t\t\t xmlOutputBufferPtr buf);\n\nXMLPUBFUN int XMLCALL\n\t\txmlC14NDocDumpMemory\t(xmlDocPtr doc,\n\t\t\t\t\t xmlNodeSetPtr nodes,\n\t\t\t\t\t int mode, /* a xmlC14NMode */\n\t\t\t\t\t xmlChar **inclusive_ns_prefixes,\n\t\t\t\t\t int with_comments,\n\t\t\t\t\t xmlChar **doc_txt_ptr);\n\nXMLPUBFUN int XMLCALL\n\t\txmlC14NDocSave\t\t(xmlDocPtr doc,\n\t\t\t\t\t xmlNodeSetPtr nodes,\n\t\t\t\t\t int mode, /* a xmlC14NMode */\n\t\t\t\t\t xmlChar **inclusive_ns_prefixes,\n\t\t\t\t\t int with_comments,\n\t\t\t\t\t const char* filename,\n\t\t\t\t\t int compression);\n\n\n/**\n * This is the core C14N function\n */\n/**\n * xmlC14NIsVisibleCallback:\n * @user_data: user data\n * @node: the curent node\n * @parent: the parent node\n *\n * Signature for a C14N callback on visible nodes\n *\n * Returns 1 if the node should be included\n */\ntypedef int (*xmlC14NIsVisibleCallback)\t(void* user_data,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr parent);\n\nXMLPUBFUN int XMLCALL\n\t\txmlC14NExecute\t\t(xmlDocPtr doc,\n\t\t\t\t\t xmlC14NIsVisibleCallback is_visible_callback,\n\t\t\t\t\t void* user_data,\n\t\t\t\t\t int mode, /* a xmlC14NMode */\n\t\t\t\t\t xmlChar **inclusive_ns_prefixes,\n\t\t\t\t\t int with_comments,\n\t\t\t\t\t xmlOutputBufferPtr buf);\n\n#ifdef __cplusplus\n}\n#endif /* __cplusplus */\n\n#endif /* LIBXML_OUTPUT_ENABLED */\n#endif /* LIBXML_C14N_ENABLED */\n#endif /* __XML_C14N_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/catalog.h",
    "content": "/**\n * Summary: interfaces to the Catalog handling system\n * Description: the catalog module implements the support for\n * XML Catalogs and SGML catalogs\n *\n * SGML Open Technical Resolution TR9401:1997.\n * http://www.jclark.com/sp/catalog.htm\n *\n * XML Catalogs Working Draft 06 August 2001\n * http://www.oasis-open.org/committees/entity/spec-2001-08-06.html\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_CATALOG_H__\n#define __XML_CATALOG_H__\n\n#include <stdio.h>\n\n#include <libxml/xmlversion.h>\n#include <libxml/xmlstring.h>\n#include <libxml/tree.h>\n\n#ifdef LIBXML_CATALOG_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * XML_CATALOGS_NAMESPACE:\n *\n * The namespace for the XML Catalogs elements.\n */\n#define XML_CATALOGS_NAMESPACE\t\t\t\t\t\\\n    (const xmlChar *) \"urn:oasis:names:tc:entity:xmlns:xml:catalog\"\n/**\n * XML_CATALOG_PI:\n *\n * The specific XML Catalog Processing Instuction name.\n */\n#define XML_CATALOG_PI\t\t\t\t\t\t\\\n    (const xmlChar *) \"oasis-xml-catalog\"\n\n/*\n * The API is voluntarily limited to general cataloging.\n */\ntypedef enum {\n    XML_CATA_PREFER_NONE = 0,\n    XML_CATA_PREFER_PUBLIC = 1,\n    XML_CATA_PREFER_SYSTEM\n} xmlCatalogPrefer;\n\ntypedef enum {\n    XML_CATA_ALLOW_NONE = 0,\n    XML_CATA_ALLOW_GLOBAL = 1,\n    XML_CATA_ALLOW_DOCUMENT = 2,\n    XML_CATA_ALLOW_ALL = 3\n} xmlCatalogAllow;\n\ntypedef struct _xmlCatalog xmlCatalog;\ntypedef xmlCatalog *xmlCatalogPtr;\n\n/*\n * Operations on a given catalog.\n */\nXMLPUBFUN xmlCatalogPtr XMLCALL\n\t\txmlNewCatalog\t\t(int sgml);\nXMLPUBFUN xmlCatalogPtr XMLCALL\n\t\txmlLoadACatalog\t\t(const char *filename);\nXMLPUBFUN xmlCatalogPtr XMLCALL\n\t\txmlLoadSGMLSuperCatalog\t(const char *filename);\nXMLPUBFUN int XMLCALL\n\t\txmlConvertSGMLCatalog\t(xmlCatalogPtr catal);\nXMLPUBFUN int XMLCALL\n\t\txmlACatalogAdd\t\t(xmlCatalogPtr catal,\n\t\t\t\t\t const xmlChar *type,\n\t\t\t\t\t const xmlChar *orig,\n\t\t\t\t\t const xmlChar *replace);\nXMLPUBFUN int XMLCALL\n\t\txmlACatalogRemove\t(xmlCatalogPtr catal,\n\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlACatalogResolve\t(xmlCatalogPtr catal,\n\t\t\t\t\t const xmlChar *pubID,\n\t                                 const xmlChar *sysID);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlACatalogResolveSystem(xmlCatalogPtr catal,\n\t\t\t\t\t const xmlChar *sysID);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlACatalogResolvePublic(xmlCatalogPtr catal,\n\t\t\t\t\t const xmlChar *pubID);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlACatalogResolveURI\t(xmlCatalogPtr catal,\n\t\t\t\t\t const xmlChar *URI);\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlACatalogDump\t\t(xmlCatalogPtr catal,\n\t\t\t\t\t FILE *out);\n#endif /* LIBXML_OUTPUT_ENABLED */\nXMLPUBFUN void XMLCALL\n\t\txmlFreeCatalog\t\t(xmlCatalogPtr catal);\nXMLPUBFUN int XMLCALL\n\t\txmlCatalogIsEmpty\t(xmlCatalogPtr catal);\n\n/*\n * Global operations.\n */\nXMLPUBFUN void XMLCALL\n\t\txmlInitializeCatalog\t(void);\nXMLPUBFUN int XMLCALL\n\t\txmlLoadCatalog\t\t(const char *filename);\nXMLPUBFUN void XMLCALL\n\t\txmlLoadCatalogs\t\t(const char *paths);\nXMLPUBFUN void XMLCALL\n\t\txmlCatalogCleanup\t(void);\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlCatalogDump\t\t(FILE *out);\n#endif /* LIBXML_OUTPUT_ENABLED */\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlCatalogResolve\t(const xmlChar *pubID,\n\t                                 const xmlChar *sysID);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlCatalogResolveSystem\t(const xmlChar *sysID);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlCatalogResolvePublic\t(const xmlChar *pubID);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlCatalogResolveURI\t(const xmlChar *URI);\nXMLPUBFUN int XMLCALL\n\t\txmlCatalogAdd\t\t(const xmlChar *type,\n\t\t\t\t\t const xmlChar *orig,\n\t\t\t\t\t const xmlChar *replace);\nXMLPUBFUN int XMLCALL\n\t\txmlCatalogRemove\t(const xmlChar *value);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlParseCatalogFile\t(const char *filename);\nXMLPUBFUN int XMLCALL\n\t\txmlCatalogConvert\t(void);\n\n/*\n * Strictly minimal interfaces for per-document catalogs used\n * by the parser.\n */\nXMLPUBFUN void XMLCALL\n\t\txmlCatalogFreeLocal\t(void *catalogs);\nXMLPUBFUN void * XMLCALL\n\t\txmlCatalogAddLocal\t(void *catalogs,\n\t\t\t\t\t const xmlChar *URL);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlCatalogLocalResolve\t(void *catalogs,\n\t\t\t\t\t const xmlChar *pubID,\n\t                                 const xmlChar *sysID);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlCatalogLocalResolveURI(void *catalogs,\n\t\t\t\t\t const xmlChar *URI);\n/*\n * Preference settings.\n */\nXMLPUBFUN int XMLCALL\n\t\txmlCatalogSetDebug\t(int level);\nXMLPUBFUN xmlCatalogPrefer XMLCALL\n\t\txmlCatalogSetDefaultPrefer(xmlCatalogPrefer prefer);\nXMLPUBFUN void XMLCALL\n\t\txmlCatalogSetDefaults\t(xmlCatalogAllow allow);\nXMLPUBFUN xmlCatalogAllow XMLCALL\n\t\txmlCatalogGetDefaults\t(void);\n\n\n/* DEPRECATED interfaces */\nXMLPUBFUN const xmlChar * XMLCALL\n\t\txmlCatalogGetSystem\t(const xmlChar *sysID);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\txmlCatalogGetPublic\t(const xmlChar *pubID);\n\n#ifdef __cplusplus\n}\n#endif\n#endif /* LIBXML_CATALOG_ENABLED */\n#endif /* __XML_CATALOG_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/chvalid.h",
    "content": "/*\n * Summary: Unicode character range checking\n * Description: this module exports interfaces for the character\n *               range validation APIs\n *\n * This file is automatically generated from the cvs source\n * definition files using the genChRanges.py Python script\n *\n * Generation date: Mon Mar 27 11:09:48 2006\n * Sources: chvalid.def\n * Author: William Brack <wbrack@mmm.com.hk>\n */\n\n#ifndef __XML_CHVALID_H__\n#define __XML_CHVALID_H__\n\n#include <libxml/xmlversion.h>\n#include <libxml/xmlstring.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * Define our typedefs and structures\n *\n */\ntypedef struct _xmlChSRange xmlChSRange;\ntypedef xmlChSRange *xmlChSRangePtr;\nstruct _xmlChSRange {\n    unsigned short\tlow;\n    unsigned short\thigh;\n};\n\ntypedef struct _xmlChLRange xmlChLRange;\ntypedef xmlChLRange *xmlChLRangePtr;\nstruct _xmlChLRange {\n    unsigned int\tlow;\n    unsigned int\thigh;\n};\n\ntypedef struct _xmlChRangeGroup xmlChRangeGroup;\ntypedef xmlChRangeGroup *xmlChRangeGroupPtr;\nstruct _xmlChRangeGroup {\n    int\t\t\tnbShortRange;\n    int\t\t\tnbLongRange;\n    const xmlChSRange\t*shortRange;\t/* points to an array of ranges */\n    const xmlChLRange\t*longRange;\n};\n\n/**\n * Range checking routine\n */\nXMLPUBFUN int XMLCALL\n\t\txmlCharInRange(unsigned int val, const xmlChRangeGroup *group);\n\n\n/**\n * xmlIsBaseChar_ch:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsBaseChar_ch(c)\t(((0x41 <= (c)) && ((c) <= 0x5a)) || \\\n\t\t\t\t ((0x61 <= (c)) && ((c) <= 0x7a)) || \\\n\t\t\t\t ((0xc0 <= (c)) && ((c) <= 0xd6)) || \\\n\t\t\t\t ((0xd8 <= (c)) && ((c) <= 0xf6)) || \\\n\t\t\t\t  (0xf8 <= (c)))\n\n/**\n * xmlIsBaseCharQ:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsBaseCharQ(c)\t(((c) < 0x100) ? \\\n\t\t\t\t xmlIsBaseChar_ch((c)) : \\\n\t\t\t\t xmlCharInRange((c), &xmlIsBaseCharGroup))\n\nXMLPUBVAR const xmlChRangeGroup xmlIsBaseCharGroup;\n\n/**\n * xmlIsBlank_ch:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsBlank_ch(c)\t(((c) == 0x20) || \\\n\t\t\t\t ((0x9 <= (c)) && ((c) <= 0xa)) || \\\n\t\t\t\t ((c) == 0xd))\n\n/**\n * xmlIsBlankQ:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsBlankQ(c)\t\t(((c) < 0x100) ? \\\n\t\t\t\t xmlIsBlank_ch((c)) : 0)\n\n\n/**\n * xmlIsChar_ch:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsChar_ch(c)\t\t(((0x9 <= (c)) && ((c) <= 0xa)) || \\\n\t\t\t\t ((c) == 0xd) || \\\n\t\t\t\t  (0x20 <= (c)))\n\n/**\n * xmlIsCharQ:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsCharQ(c)\t\t(((c) < 0x100) ? \\\n\t\t\t\t xmlIsChar_ch((c)) :\\\n\t\t\t\t(((0x100 <= (c)) && ((c) <= 0xd7ff)) || \\\n\t\t\t\t ((0xe000 <= (c)) && ((c) <= 0xfffd)) || \\\n\t\t\t\t ((0x10000 <= (c)) && ((c) <= 0x10ffff))))\n\nXMLPUBVAR const xmlChRangeGroup xmlIsCharGroup;\n\n/**\n * xmlIsCombiningQ:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsCombiningQ(c)\t(((c) < 0x100) ? \\\n\t\t\t\t 0 : \\\n\t\t\t\t xmlCharInRange((c), &xmlIsCombiningGroup))\n\nXMLPUBVAR const xmlChRangeGroup xmlIsCombiningGroup;\n\n/**\n * xmlIsDigit_ch:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsDigit_ch(c)\t(((0x30 <= (c)) && ((c) <= 0x39)))\n\n/**\n * xmlIsDigitQ:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsDigitQ(c)\t\t(((c) < 0x100) ? \\\n\t\t\t\t xmlIsDigit_ch((c)) : \\\n\t\t\t\t xmlCharInRange((c), &xmlIsDigitGroup))\n\nXMLPUBVAR const xmlChRangeGroup xmlIsDigitGroup;\n\n/**\n * xmlIsExtender_ch:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsExtender_ch(c)\t(((c) == 0xb7))\n\n/**\n * xmlIsExtenderQ:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsExtenderQ(c)\t(((c) < 0x100) ? \\\n\t\t\t\t xmlIsExtender_ch((c)) : \\\n\t\t\t\t xmlCharInRange((c), &xmlIsExtenderGroup))\n\nXMLPUBVAR const xmlChRangeGroup xmlIsExtenderGroup;\n\n/**\n * xmlIsIdeographicQ:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsIdeographicQ(c)\t(((c) < 0x100) ? \\\n\t\t\t\t 0 :\\\n\t\t\t\t(((0x4e00 <= (c)) && ((c) <= 0x9fa5)) || \\\n\t\t\t\t ((c) == 0x3007) || \\\n\t\t\t\t ((0x3021 <= (c)) && ((c) <= 0x3029))))\n\nXMLPUBVAR const xmlChRangeGroup xmlIsIdeographicGroup;\nXMLPUBVAR const unsigned char xmlIsPubidChar_tab[256];\n\n/**\n * xmlIsPubidChar_ch:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsPubidChar_ch(c)\t(xmlIsPubidChar_tab[(c)])\n\n/**\n * xmlIsPubidCharQ:\n * @c: char to validate\n *\n * Automatically generated by genChRanges.py\n */\n#define xmlIsPubidCharQ(c)\t(((c) < 0x100) ? \\\n\t\t\t\t xmlIsPubidChar_ch((c)) : 0)\n\nXMLPUBFUN int XMLCALL\n\t\txmlIsBaseChar(unsigned int ch);\nXMLPUBFUN int XMLCALL\n\t\txmlIsBlank(unsigned int ch);\nXMLPUBFUN int XMLCALL\n\t\txmlIsChar(unsigned int ch);\nXMLPUBFUN int XMLCALL\n\t\txmlIsCombining(unsigned int ch);\nXMLPUBFUN int XMLCALL\n\t\txmlIsDigit(unsigned int ch);\nXMLPUBFUN int XMLCALL\n\t\txmlIsExtender(unsigned int ch);\nXMLPUBFUN int XMLCALL\n\t\txmlIsIdeographic(unsigned int ch);\nXMLPUBFUN int XMLCALL\n\t\txmlIsPubidChar(unsigned int ch);\n\n#ifdef __cplusplus\n}\n#endif\n#endif /* __XML_CHVALID_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/debugXML.h",
    "content": "/*\n * Summary: Tree debugging APIs\n * Description: Interfaces to a set of routines used for debugging the tree\n *              produced by the XML parser.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __DEBUG_XML__\n#define __DEBUG_XML__\n#include <stdio.h>\n#include <libxml/xmlversion.h>\n#include <libxml/tree.h>\n\n#ifdef LIBXML_DEBUG_ENABLED\n\n#include <libxml/xpath.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * The standard Dump routines.\n */\nXMLPUBFUN void XMLCALL\n\txmlDebugDumpString\t(FILE *output,\n\t\t\t\t const xmlChar *str);\nXMLPUBFUN void XMLCALL\n\txmlDebugDumpAttr\t(FILE *output,\n\t\t\t\t xmlAttrPtr attr,\n\t\t\t\t int depth);\nXMLPUBFUN void XMLCALL\n\txmlDebugDumpAttrList\t(FILE *output,\n\t\t\t\t xmlAttrPtr attr,\n\t\t\t\t int depth);\nXMLPUBFUN void XMLCALL\n\txmlDebugDumpOneNode\t(FILE *output,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t int depth);\nXMLPUBFUN void XMLCALL\n\txmlDebugDumpNode\t(FILE *output,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t int depth);\nXMLPUBFUN void XMLCALL\n\txmlDebugDumpNodeList\t(FILE *output,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t int depth);\nXMLPUBFUN void XMLCALL\n\txmlDebugDumpDocumentHead(FILE *output,\n\t\t\t\t xmlDocPtr doc);\nXMLPUBFUN void XMLCALL\n\txmlDebugDumpDocument\t(FILE *output,\n\t\t\t\t xmlDocPtr doc);\nXMLPUBFUN void XMLCALL\n\txmlDebugDumpDTD\t\t(FILE *output,\n\t\t\t\t xmlDtdPtr dtd);\nXMLPUBFUN void XMLCALL\n\txmlDebugDumpEntities\t(FILE *output,\n\t\t\t\t xmlDocPtr doc);\n\n/****************************************************************\n *\t\t\t\t\t\t\t\t*\n *\t\t\tChecking routines\t\t\t*\n *\t\t\t\t\t\t\t\t*\n ****************************************************************/\n\nXMLPUBFUN int XMLCALL\n\txmlDebugCheckDocument\t(FILE * output,\n\t\t\t\t xmlDocPtr doc);\n\n/****************************************************************\n *\t\t\t\t\t\t\t\t*\n *\t\t\tXML shell helpers\t\t\t*\n *\t\t\t\t\t\t\t\t*\n ****************************************************************/\n\nXMLPUBFUN void XMLCALL\n\txmlLsOneNode\t\t(FILE *output, xmlNodePtr node);\nXMLPUBFUN int XMLCALL\n\txmlLsCountNode\t\t(xmlNodePtr node);\n\nXMLPUBFUN const char * XMLCALL\n\txmlBoolToText\t\t(int boolval);\n\n/****************************************************************\n *\t\t\t\t\t\t\t\t*\n *\t The XML shell related structures and functions\t\t*\n *\t\t\t\t\t\t\t\t*\n ****************************************************************/\n\n#ifdef LIBXML_XPATH_ENABLED\n/**\n * xmlShellReadlineFunc:\n * @prompt:  a string prompt\n *\n * This is a generic signature for the XML shell input function.\n *\n * Returns a string which will be freed by the Shell.\n */\ntypedef char * (* xmlShellReadlineFunc)(char *prompt);\n\n/**\n * xmlShellCtxt:\n *\n * A debugging shell context.\n * TODO: add the defined function tables.\n */\ntypedef struct _xmlShellCtxt xmlShellCtxt;\ntypedef xmlShellCtxt *xmlShellCtxtPtr;\nstruct _xmlShellCtxt {\n    char *filename;\n    xmlDocPtr doc;\n    xmlNodePtr node;\n    xmlXPathContextPtr pctxt;\n    int loaded;\n    FILE *output;\n    xmlShellReadlineFunc input;\n};\n\n/**\n * xmlShellCmd:\n * @ctxt:  a shell context\n * @arg:  a string argument\n * @node:  a first node\n * @node2:  a second node\n *\n * This is a generic signature for the XML shell functions.\n *\n * Returns an int, negative returns indicating errors.\n */\ntypedef int (* xmlShellCmd) (xmlShellCtxtPtr ctxt,\n                             char *arg,\n\t\t\t     xmlNodePtr node,\n\t\t\t     xmlNodePtr node2);\n\nXMLPUBFUN void XMLCALL\n\txmlShellPrintXPathError\t(int errorType,\n\t\t\t\t const char *arg);\nXMLPUBFUN void XMLCALL\n\txmlShellPrintXPathResult(xmlXPathObjectPtr list);\nXMLPUBFUN int XMLCALL\n\txmlShellList\t\t(xmlShellCtxtPtr ctxt,\n\t\t\t\t char *arg,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t xmlNodePtr node2);\nXMLPUBFUN int XMLCALL\n\txmlShellBase\t\t(xmlShellCtxtPtr ctxt,\n\t\t\t\t char *arg,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t xmlNodePtr node2);\nXMLPUBFUN int XMLCALL\n\txmlShellDir\t\t(xmlShellCtxtPtr ctxt,\n\t\t\t\t char *arg,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t xmlNodePtr node2);\nXMLPUBFUN int XMLCALL\n\txmlShellLoad\t\t(xmlShellCtxtPtr ctxt,\n\t\t\t\t char *filename,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t xmlNodePtr node2);\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN void XMLCALL\n\txmlShellPrintNode\t(xmlNodePtr node);\nXMLPUBFUN int XMLCALL\n\txmlShellCat\t\t(xmlShellCtxtPtr ctxt,\n\t\t\t\t char *arg,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t xmlNodePtr node2);\nXMLPUBFUN int XMLCALL\n\txmlShellWrite\t\t(xmlShellCtxtPtr ctxt,\n\t\t\t\t char *filename,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t xmlNodePtr node2);\nXMLPUBFUN int XMLCALL\n\txmlShellSave\t\t(xmlShellCtxtPtr ctxt,\n\t\t\t\t char *filename,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t xmlNodePtr node2);\n#endif /* LIBXML_OUTPUT_ENABLED */\n#ifdef LIBXML_VALID_ENABLED\nXMLPUBFUN int XMLCALL\n\txmlShellValidate\t(xmlShellCtxtPtr ctxt,\n\t\t\t\t char *dtd,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t xmlNodePtr node2);\n#endif /* LIBXML_VALID_ENABLED */\nXMLPUBFUN int XMLCALL\n\txmlShellDu\t\t(xmlShellCtxtPtr ctxt,\n\t\t\t\t char *arg,\n\t\t\t\t xmlNodePtr tree,\n\t\t\t\t xmlNodePtr node2);\nXMLPUBFUN int XMLCALL\n\txmlShellPwd\t\t(xmlShellCtxtPtr ctxt,\n\t\t\t\t char *buffer,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t xmlNodePtr node2);\n\n/*\n * The Shell interface.\n */\nXMLPUBFUN void XMLCALL\n\txmlShell\t\t(xmlDocPtr doc,\n\t\t\t\t char *filename,\n\t\t\t\t xmlShellReadlineFunc input,\n\t\t\t\t FILE *output);\n\n#endif /* LIBXML_XPATH_ENABLED */\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_DEBUG_ENABLED */\n#endif /* __DEBUG_XML__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/dict.h",
    "content": "/*\n * Summary: string dictionary\n * Description: dictionary of reusable strings, just used to avoid allocation\n *         and freeing operations.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_DICT_H__\n#define __XML_DICT_H__\n\n#ifdef __cplusplus\n#define __XML_EXTERNC\textern \"C\"\n#else\n#define __XML_EXTERNC\n#endif\n\n/*\n * The dictionary.\n */\n__XML_EXTERNC typedef struct _xmlDict xmlDict;\n__XML_EXTERNC typedef xmlDict *xmlDictPtr;\n\n#include <limits.h>\n#include <libxml/xmlversion.h>\n#include <libxml/tree.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * Initializer\n */\nXMLPUBFUN int XMLCALL  xmlInitializeDict(void);\n\n/*\n * Constructor and destructor.\n */\nXMLPUBFUN xmlDictPtr XMLCALL\n\t\t\txmlDictCreate\t(void);\nXMLPUBFUN size_t XMLCALL\n\t\t\txmlDictSetLimit\t(xmlDictPtr dict,\n                                         size_t limit);\nXMLPUBFUN size_t XMLCALL\n\t\t\txmlDictGetUsage (xmlDictPtr dict);\nXMLPUBFUN xmlDictPtr XMLCALL\n\t\t\txmlDictCreateSub(xmlDictPtr sub);\nXMLPUBFUN int XMLCALL\n\t\t\txmlDictReference(xmlDictPtr dict);\nXMLPUBFUN void XMLCALL\n\t\t\txmlDictFree\t(xmlDictPtr dict);\n\n/*\n * Lookup of entry in the dictionary.\n */\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t\txmlDictLookup\t(xmlDictPtr dict,\n\t\t                         const xmlChar *name,\n\t\t                         int len);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t\txmlDictExists\t(xmlDictPtr dict,\n\t\t                         const xmlChar *name,\n\t\t                         int len);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t\txmlDictQLookup\t(xmlDictPtr dict,\n\t\t                         const xmlChar *prefix,\n\t\t                         const xmlChar *name);\nXMLPUBFUN int XMLCALL\n\t\t\txmlDictOwns\t(xmlDictPtr dict,\n\t\t\t\t\t const xmlChar *str);\nXMLPUBFUN int XMLCALL\n\t\t\txmlDictSize\t(xmlDictPtr dict);\n\n/*\n * Cleanup function\n */\nXMLPUBFUN void XMLCALL\n                        xmlDictCleanup  (void);\n\n#ifdef __cplusplus\n}\n#endif\n#endif /* ! __XML_DICT_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/encoding.h",
    "content": "/*\n * Summary: interface for the encoding conversion functions\n * Description: interface for the encoding conversion functions needed for\n *              XML basic encoding and iconv() support.\n *\n * Related specs are\n * rfc2044        (UTF-8 and UTF-16) F. Yergeau Alis Technologies\n * [ISO-10646]    UTF-8 and UTF-16 in Annexes\n * [ISO-8859-1]   ISO Latin-1 characters codes.\n * [UNICODE]      The Unicode Consortium, \"The Unicode Standard --\n *                Worldwide Character Encoding -- Version 1.0\", Addison-\n *                Wesley, Volume 1, 1991, Volume 2, 1992.  UTF-8 is\n *                described in Unicode Technical Report #4.\n * [US-ASCII]     Coded Character Set--7-bit American Standard Code for\n *                Information Interchange, ANSI X3.4-1986.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_CHAR_ENCODING_H__\n#define __XML_CHAR_ENCODING_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_ICONV_ENABLED\n#include <iconv.h>\n#endif\n#ifdef LIBXML_ICU_ENABLED\n#include <unicode/ucnv.h>\n#endif\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * xmlCharEncoding:\n *\n * Predefined values for some standard encodings.\n * Libxml does not do beforehand translation on UTF8 and ISOLatinX.\n * It also supports ASCII, ISO-8859-1, and UTF16 (LE and BE) by default.\n *\n * Anything else would have to be translated to UTF8 before being\n * given to the parser itself. The BOM for UTF16 and the encoding\n * declaration are looked at and a converter is looked for at that\n * point. If not found the parser stops here as asked by the XML REC. A\n * converter can be registered by the user using xmlRegisterCharEncodingHandler\n * but the current form doesn't allow stateful transcoding (a serious\n * problem agreed !). If iconv has been found it will be used\n * automatically and allow stateful transcoding, the simplest is then\n * to be sure to enable iconv and to provide iconv libs for the encoding\n * support needed.\n *\n * Note that the generic \"UTF-16\" is not a predefined value.  Instead, only\n * the specific UTF-16LE and UTF-16BE are present.\n */\ntypedef enum {\n    XML_CHAR_ENCODING_ERROR=   -1, /* No char encoding detected */\n    XML_CHAR_ENCODING_NONE=\t0, /* No char encoding detected */\n    XML_CHAR_ENCODING_UTF8=\t1, /* UTF-8 */\n    XML_CHAR_ENCODING_UTF16LE=\t2, /* UTF-16 little endian */\n    XML_CHAR_ENCODING_UTF16BE=\t3, /* UTF-16 big endian */\n    XML_CHAR_ENCODING_UCS4LE=\t4, /* UCS-4 little endian */\n    XML_CHAR_ENCODING_UCS4BE=\t5, /* UCS-4 big endian */\n    XML_CHAR_ENCODING_EBCDIC=\t6, /* EBCDIC uh! */\n    XML_CHAR_ENCODING_UCS4_2143=7, /* UCS-4 unusual ordering */\n    XML_CHAR_ENCODING_UCS4_3412=8, /* UCS-4 unusual ordering */\n    XML_CHAR_ENCODING_UCS2=\t9, /* UCS-2 */\n    XML_CHAR_ENCODING_8859_1=\t10,/* ISO-8859-1 ISO Latin 1 */\n    XML_CHAR_ENCODING_8859_2=\t11,/* ISO-8859-2 ISO Latin 2 */\n    XML_CHAR_ENCODING_8859_3=\t12,/* ISO-8859-3 */\n    XML_CHAR_ENCODING_8859_4=\t13,/* ISO-8859-4 */\n    XML_CHAR_ENCODING_8859_5=\t14,/* ISO-8859-5 */\n    XML_CHAR_ENCODING_8859_6=\t15,/* ISO-8859-6 */\n    XML_CHAR_ENCODING_8859_7=\t16,/* ISO-8859-7 */\n    XML_CHAR_ENCODING_8859_8=\t17,/* ISO-8859-8 */\n    XML_CHAR_ENCODING_8859_9=\t18,/* ISO-8859-9 */\n    XML_CHAR_ENCODING_2022_JP=  19,/* ISO-2022-JP */\n    XML_CHAR_ENCODING_SHIFT_JIS=20,/* Shift_JIS */\n    XML_CHAR_ENCODING_EUC_JP=   21,/* EUC-JP */\n    XML_CHAR_ENCODING_ASCII=    22 /* pure ASCII */\n} xmlCharEncoding;\n\n/**\n * xmlCharEncodingInputFunc:\n * @out:  a pointer to an array of bytes to store the UTF-8 result\n * @outlen:  the length of @out\n * @in:  a pointer to an array of chars in the original encoding\n * @inlen:  the length of @in\n *\n * Take a block of chars in the original encoding and try to convert\n * it to an UTF-8 block of chars out.\n *\n * Returns the number of bytes written, -1 if lack of space, or -2\n *     if the transcoding failed.\n * The value of @inlen after return is the number of octets consumed\n *     if the return value is positive, else unpredictiable.\n * The value of @outlen after return is the number of octets consumed.\n */\ntypedef int (* xmlCharEncodingInputFunc)(unsigned char *out, int *outlen,\n                                         const unsigned char *in, int *inlen);\n\n\n/**\n * xmlCharEncodingOutputFunc:\n * @out:  a pointer to an array of bytes to store the result\n * @outlen:  the length of @out\n * @in:  a pointer to an array of UTF-8 chars\n * @inlen:  the length of @in\n *\n * Take a block of UTF-8 chars in and try to convert it to another\n * encoding.\n * Note: a first call designed to produce heading info is called with\n * in = NULL. If stateful this should also initialize the encoder state.\n *\n * Returns the number of bytes written, -1 if lack of space, or -2\n *     if the transcoding failed.\n * The value of @inlen after return is the number of octets consumed\n *     if the return value is positive, else unpredictiable.\n * The value of @outlen after return is the number of octets produced.\n */\ntypedef int (* xmlCharEncodingOutputFunc)(unsigned char *out, int *outlen,\n                                          const unsigned char *in, int *inlen);\n\n\n/*\n * Block defining the handlers for non UTF-8 encodings.\n * If iconv is supported, there are two extra fields.\n */\n#ifdef LIBXML_ICU_ENABLED\n/* Size of pivot buffer, same as icu/source/common/ucnv.cpp CHUNK_SIZE */\n#define ICU_PIVOT_BUF_SIZE 1024\nstruct _uconv_t {\n  UConverter *uconv; /* for conversion between an encoding and UTF-16 */\n  UConverter *utf8; /* for conversion between UTF-8 and UTF-16 */\n  UChar      pivot_buf[ICU_PIVOT_BUF_SIZE];\n  UChar      *pivot_source;\n  UChar      *pivot_target;\n};\ntypedef struct _uconv_t uconv_t;\n#endif\n\ntypedef struct _xmlCharEncodingHandler xmlCharEncodingHandler;\ntypedef xmlCharEncodingHandler *xmlCharEncodingHandlerPtr;\nstruct _xmlCharEncodingHandler {\n    char                       *name;\n    xmlCharEncodingInputFunc   input;\n    xmlCharEncodingOutputFunc  output;\n#ifdef LIBXML_ICONV_ENABLED\n    iconv_t                    iconv_in;\n    iconv_t                    iconv_out;\n#endif /* LIBXML_ICONV_ENABLED */\n#ifdef LIBXML_ICU_ENABLED\n    uconv_t                    *uconv_in;\n    uconv_t                    *uconv_out;\n#endif /* LIBXML_ICU_ENABLED */\n};\n\n#ifdef __cplusplus\n}\n#endif\n#include <libxml/tree.h>\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * Interfaces for encoding handlers.\n */\nXMLPUBFUN void XMLCALL\n\txmlInitCharEncodingHandlers\t(void);\nXMLPUBFUN void XMLCALL\n\txmlCleanupCharEncodingHandlers\t(void);\nXMLPUBFUN void XMLCALL\n\txmlRegisterCharEncodingHandler\t(xmlCharEncodingHandlerPtr handler);\nXMLPUBFUN xmlCharEncodingHandlerPtr XMLCALL\n\txmlGetCharEncodingHandler\t(xmlCharEncoding enc);\nXMLPUBFUN xmlCharEncodingHandlerPtr XMLCALL\n\txmlFindCharEncodingHandler\t(const char *name);\nXMLPUBFUN xmlCharEncodingHandlerPtr XMLCALL\n\txmlNewCharEncodingHandler\t(const char *name,\n\t\t\t\t\t xmlCharEncodingInputFunc input,\n\t\t\t\t\t xmlCharEncodingOutputFunc output);\n\n/*\n * Interfaces for encoding names and aliases.\n */\nXMLPUBFUN int XMLCALL\n\txmlAddEncodingAlias\t\t(const char *name,\n\t\t\t\t\t const char *alias);\nXMLPUBFUN int XMLCALL\n\txmlDelEncodingAlias\t\t(const char *alias);\nXMLPUBFUN const char * XMLCALL\n\txmlGetEncodingAlias\t\t(const char *alias);\nXMLPUBFUN void XMLCALL\n\txmlCleanupEncodingAliases\t(void);\nXMLPUBFUN xmlCharEncoding XMLCALL\n\txmlParseCharEncoding\t\t(const char *name);\nXMLPUBFUN const char * XMLCALL\n\txmlGetCharEncodingName\t\t(xmlCharEncoding enc);\n\n/*\n * Interfaces directly used by the parsers.\n */\nXMLPUBFUN xmlCharEncoding XMLCALL\n\txmlDetectCharEncoding\t\t(const unsigned char *in,\n\t\t\t\t\t int len);\n\nXMLPUBFUN int XMLCALL\n\txmlCharEncOutFunc\t\t(xmlCharEncodingHandler *handler,\n\t\t\t\t\t xmlBufferPtr out,\n\t\t\t\t\t xmlBufferPtr in);\n\nXMLPUBFUN int XMLCALL\n\txmlCharEncInFunc\t\t(xmlCharEncodingHandler *handler,\n\t\t\t\t\t xmlBufferPtr out,\n\t\t\t\t\t xmlBufferPtr in);\nXMLPUBFUN int XMLCALL\n\txmlCharEncFirstLine\t\t(xmlCharEncodingHandler *handler,\n\t\t\t\t\t xmlBufferPtr out,\n\t\t\t\t\t xmlBufferPtr in);\nXMLPUBFUN int XMLCALL\n\txmlCharEncCloseFunc\t\t(xmlCharEncodingHandler *handler);\n\n/*\n * Export a few useful functions\n */\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN int XMLCALL\n\tUTF8Toisolat1\t\t\t(unsigned char *out,\n\t\t\t\t\t int *outlen,\n\t\t\t\t\t const unsigned char *in,\n\t\t\t\t\t int *inlen);\n#endif /* LIBXML_OUTPUT_ENABLED */\nXMLPUBFUN int XMLCALL\n\tisolat1ToUTF8\t\t\t(unsigned char *out,\n\t\t\t\t\t int *outlen,\n\t\t\t\t\t const unsigned char *in,\n\t\t\t\t\t int *inlen);\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_CHAR_ENCODING_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/entities.h",
    "content": "/*\n * Summary: interface for the XML entities handling\n * Description: this module provides some of the entity API needed\n *              for the parser and applications.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_ENTITIES_H__\n#define __XML_ENTITIES_H__\n\n#include <libxml/xmlversion.h>\n#include <libxml/tree.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * The different valid entity types.\n */\ntypedef enum {\n    XML_INTERNAL_GENERAL_ENTITY = 1,\n    XML_EXTERNAL_GENERAL_PARSED_ENTITY = 2,\n    XML_EXTERNAL_GENERAL_UNPARSED_ENTITY = 3,\n    XML_INTERNAL_PARAMETER_ENTITY = 4,\n    XML_EXTERNAL_PARAMETER_ENTITY = 5,\n    XML_INTERNAL_PREDEFINED_ENTITY = 6\n} xmlEntityType;\n\n/*\n * An unit of storage for an entity, contains the string, the value\n * and the linkind data needed for the linking in the hash table.\n */\n\nstruct _xmlEntity {\n    void           *_private;\t        /* application data */\n    xmlElementType          type;       /* XML_ENTITY_DECL, must be second ! */\n    const xmlChar          *name;\t/* Entity name */\n    struct _xmlNode    *children;\t/* First child link */\n    struct _xmlNode        *last;\t/* Last child link */\n    struct _xmlDtd       *parent;\t/* -> DTD */\n    struct _xmlNode        *next;\t/* next sibling link  */\n    struct _xmlNode        *prev;\t/* previous sibling link  */\n    struct _xmlDoc          *doc;       /* the containing document */\n\n    xmlChar                *orig;\t/* content without ref substitution */\n    xmlChar             *content;\t/* content or ndata if unparsed */\n    int                   length;\t/* the content length */\n    xmlEntityType          etype;\t/* The entity type */\n    const xmlChar    *ExternalID;\t/* External identifier for PUBLIC */\n    const xmlChar      *SystemID;\t/* URI for a SYSTEM or PUBLIC Entity */\n\n    struct _xmlEntity     *nexte;\t/* unused */\n    const xmlChar           *URI;\t/* the full URI as computed */\n    int                    owner;\t/* does the entity own the childrens */\n    int\t\t\t checked;\t/* was the entity content checked */\n\t\t\t\t\t/* this is also used to count entities\n\t\t\t\t\t * references done from that entity\n\t\t\t\t\t * and if it contains '<' */\n};\n\n/*\n * All entities are stored in an hash table.\n * There is 2 separate hash tables for global and parameter entities.\n */\n\ntypedef struct _xmlHashTable xmlEntitiesTable;\ntypedef xmlEntitiesTable *xmlEntitiesTablePtr;\n\n/*\n * External functions:\n */\n\n#ifdef LIBXML_LEGACY_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlInitializePredefinedEntities\t(void);\n#endif /* LIBXML_LEGACY_ENABLED */\n\nXMLPUBFUN xmlEntityPtr XMLCALL\n\t\t\txmlNewEntity\t\t(xmlDocPtr doc,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t int type,\n\t\t\t\t\t\t const xmlChar *ExternalID,\n\t\t\t\t\t\t const xmlChar *SystemID,\n\t\t\t\t\t\t const xmlChar *content);\nXMLPUBFUN xmlEntityPtr XMLCALL\n\t\t\txmlAddDocEntity\t\t(xmlDocPtr doc,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t int type,\n\t\t\t\t\t\t const xmlChar *ExternalID,\n\t\t\t\t\t\t const xmlChar *SystemID,\n\t\t\t\t\t\t const xmlChar *content);\nXMLPUBFUN xmlEntityPtr XMLCALL\n\t\t\txmlAddDtdEntity\t\t(xmlDocPtr doc,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t int type,\n\t\t\t\t\t\t const xmlChar *ExternalID,\n\t\t\t\t\t\t const xmlChar *SystemID,\n\t\t\t\t\t\t const xmlChar *content);\nXMLPUBFUN xmlEntityPtr XMLCALL\n\t\t\txmlGetPredefinedEntity\t(const xmlChar *name);\nXMLPUBFUN xmlEntityPtr XMLCALL\n\t\t\txmlGetDocEntity\t\t(const xmlDoc *doc,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlEntityPtr XMLCALL\n\t\t\txmlGetDtdEntity\t\t(xmlDocPtr doc,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlEntityPtr XMLCALL\n\t\t\txmlGetParameterEntity\t(xmlDocPtr doc,\n\t\t\t\t\t\t const xmlChar *name);\n#ifdef LIBXML_LEGACY_ENABLED\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t\txmlEncodeEntities\t(xmlDocPtr doc,\n\t\t\t\t\t\t const xmlChar *input);\n#endif /* LIBXML_LEGACY_ENABLED */\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlEncodeEntitiesReentrant(xmlDocPtr doc,\n\t\t\t\t\t\t const xmlChar *input);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlEncodeSpecialChars\t(const xmlDoc *doc,\n\t\t\t\t\t\t const xmlChar *input);\nXMLPUBFUN xmlEntitiesTablePtr XMLCALL\n\t\t\txmlCreateEntitiesTable\t(void);\n#ifdef LIBXML_TREE_ENABLED\nXMLPUBFUN xmlEntitiesTablePtr XMLCALL\n\t\t\txmlCopyEntitiesTable\t(xmlEntitiesTablePtr table);\n#endif /* LIBXML_TREE_ENABLED */\nXMLPUBFUN void XMLCALL\n\t\t\txmlFreeEntitiesTable\t(xmlEntitiesTablePtr table);\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN void XMLCALL\n\t\t\txmlDumpEntitiesTable\t(xmlBufferPtr buf,\n\t\t\t\t\t\t xmlEntitiesTablePtr table);\nXMLPUBFUN void XMLCALL\n\t\t\txmlDumpEntityDecl\t(xmlBufferPtr buf,\n\t\t\t\t\t\t xmlEntityPtr ent);\n#endif /* LIBXML_OUTPUT_ENABLED */\n#ifdef LIBXML_LEGACY_ENABLED\nXMLPUBFUN void XMLCALL\n\t\t\txmlCleanupPredefinedEntities(void);\n#endif /* LIBXML_LEGACY_ENABLED */\n\n\n#ifdef __cplusplus\n}\n#endif\n\n# endif /* __XML_ENTITIES_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/globals.h",
    "content": "/*\n * Summary: interface for all global variables of the library\n * Description: all the global variables and thread handling for\n *              those variables is handled by this module.\n *\n * The bottom of this file is automatically generated by build_glob.py\n * based on the description file global.data\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Gary Pennington <Gary.Pennington@uk.sun.com>, Daniel Veillard\n */\n\n#ifndef __XML_GLOBALS_H\n#define __XML_GLOBALS_H\n\n#include <libxml/xmlversion.h>\n#include <libxml/parser.h>\n#include <libxml/xmlerror.h>\n#include <libxml/SAX2.h>\n#include <libxml/xmlmemory.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nXMLPUBFUN void XMLCALL xmlInitGlobals(void);\nXMLPUBFUN void XMLCALL xmlCleanupGlobals(void);\n\n/**\n * xmlParserInputBufferCreateFilenameFunc:\n * @URI: the URI to read from\n * @enc: the requested source encoding\n *\n * Signature for the function doing the lookup for a suitable input method\n * corresponding to an URI.\n *\n * Returns the new xmlParserInputBufferPtr in case of success or NULL if no\n *         method was found.\n */\ntypedef xmlParserInputBufferPtr (*xmlParserInputBufferCreateFilenameFunc) (const char *URI,\n\t\t\t\t\t\t\t\t\t   xmlCharEncoding enc);\n\n\n/**\n * xmlOutputBufferCreateFilenameFunc:\n * @URI: the URI to write to\n * @enc: the requested target encoding\n *\n * Signature for the function doing the lookup for a suitable output method\n * corresponding to an URI.\n *\n * Returns the new xmlOutputBufferPtr in case of success or NULL if no\n *         method was found.\n */\ntypedef xmlOutputBufferPtr (*xmlOutputBufferCreateFilenameFunc) (const char *URI,\n\t\t\t\t\t\t\t\t xmlCharEncodingHandlerPtr encoder,\n\t\t\t\t\t\t\t\t int compression);\n\nXMLPUBFUN xmlParserInputBufferCreateFilenameFunc\nXMLCALL xmlParserInputBufferCreateFilenameDefault (xmlParserInputBufferCreateFilenameFunc func);\nXMLPUBFUN xmlOutputBufferCreateFilenameFunc\nXMLCALL xmlOutputBufferCreateFilenameDefault (xmlOutputBufferCreateFilenameFunc func);\n\n/*\n * Externally global symbols which need to be protected for backwards\n * compatibility support.\n */\n\n#undef\tdocbDefaultSAXHandler\n#undef\thtmlDefaultSAXHandler\n#undef\toldXMLWDcompatibility\n#undef\txmlBufferAllocScheme\n#undef\txmlDefaultBufferSize\n#undef\txmlDefaultSAXHandler\n#undef\txmlDefaultSAXLocator\n#undef\txmlDoValidityCheckingDefaultValue\n#undef\txmlFree\n#undef\txmlGenericError\n#undef\txmlStructuredError\n#undef\txmlGenericErrorContext\n#undef\txmlStructuredErrorContext\n#undef\txmlGetWarningsDefaultValue\n#undef\txmlIndentTreeOutput\n#undef  xmlTreeIndentString\n#undef\txmlKeepBlanksDefaultValue\n#undef\txmlLineNumbersDefaultValue\n#undef\txmlLoadExtDtdDefaultValue\n#undef\txmlMalloc\n#undef\txmlMallocAtomic\n#undef\txmlMemStrdup\n#undef\txmlParserDebugEntities\n#undef\txmlParserVersion\n#undef\txmlPedanticParserDefaultValue\n#undef\txmlRealloc\n#undef\txmlSaveNoEmptyTags\n#undef\txmlSubstituteEntitiesDefaultValue\n#undef  xmlRegisterNodeDefaultValue\n#undef  xmlDeregisterNodeDefaultValue\n#undef  xmlLastError\n#undef  xmlParserInputBufferCreateFilenameValue\n#undef  xmlOutputBufferCreateFilenameValue\n\n/**\n * xmlRegisterNodeFunc:\n * @node: the current node\n *\n * Signature for the registration callback of a created node\n */\ntypedef void (*xmlRegisterNodeFunc) (xmlNodePtr node);\n/**\n * xmlDeregisterNodeFunc:\n * @node: the current node\n *\n * Signature for the deregistration callback of a discarded node\n */\ntypedef void (*xmlDeregisterNodeFunc) (xmlNodePtr node);\n\ntypedef struct _xmlGlobalState xmlGlobalState;\ntypedef xmlGlobalState *xmlGlobalStatePtr;\nstruct _xmlGlobalState\n{\n\tconst char *xmlParserVersion;\n\n\txmlSAXLocator xmlDefaultSAXLocator;\n\txmlSAXHandlerV1 xmlDefaultSAXHandler;\n\txmlSAXHandlerV1 docbDefaultSAXHandler;\n\txmlSAXHandlerV1 htmlDefaultSAXHandler;\n\n\txmlFreeFunc xmlFree;\n\txmlMallocFunc xmlMalloc;\n\txmlStrdupFunc xmlMemStrdup;\n\txmlReallocFunc xmlRealloc;\n\n\txmlGenericErrorFunc xmlGenericError;\n\txmlStructuredErrorFunc xmlStructuredError;\n\tvoid *xmlGenericErrorContext;\n\n\tint oldXMLWDcompatibility;\n\n\txmlBufferAllocationScheme xmlBufferAllocScheme;\n\tint xmlDefaultBufferSize;\n\n\tint xmlSubstituteEntitiesDefaultValue;\n\tint xmlDoValidityCheckingDefaultValue;\n\tint xmlGetWarningsDefaultValue;\n\tint xmlKeepBlanksDefaultValue;\n\tint xmlLineNumbersDefaultValue;\n\tint xmlLoadExtDtdDefaultValue;\n\tint xmlParserDebugEntities;\n\tint xmlPedanticParserDefaultValue;\n\n\tint xmlSaveNoEmptyTags;\n\tint xmlIndentTreeOutput;\n\tconst char *xmlTreeIndentString;\n\n\txmlRegisterNodeFunc xmlRegisterNodeDefaultValue;\n\txmlDeregisterNodeFunc xmlDeregisterNodeDefaultValue;\n\n\txmlMallocFunc xmlMallocAtomic;\n\txmlError xmlLastError;\n\n\txmlParserInputBufferCreateFilenameFunc xmlParserInputBufferCreateFilenameValue;\n\txmlOutputBufferCreateFilenameFunc xmlOutputBufferCreateFilenameValue;\n\n\tvoid *xmlStructuredErrorContext;\n};\n\n#ifdef __cplusplus\n}\n#endif\n#include <libxml/threads.h>\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nXMLPUBFUN void XMLCALL\txmlInitializeGlobalState(xmlGlobalStatePtr gs);\n\nXMLPUBFUN void XMLCALL xmlThrDefSetGenericErrorFunc(void *ctx, xmlGenericErrorFunc handler);\n\nXMLPUBFUN void XMLCALL xmlThrDefSetStructuredErrorFunc(void *ctx, xmlStructuredErrorFunc handler);\n\nXMLPUBFUN xmlRegisterNodeFunc XMLCALL xmlRegisterNodeDefault(xmlRegisterNodeFunc func);\nXMLPUBFUN xmlRegisterNodeFunc XMLCALL xmlThrDefRegisterNodeDefault(xmlRegisterNodeFunc func);\nXMLPUBFUN xmlDeregisterNodeFunc XMLCALL xmlDeregisterNodeDefault(xmlDeregisterNodeFunc func);\nXMLPUBFUN xmlDeregisterNodeFunc XMLCALL xmlThrDefDeregisterNodeDefault(xmlDeregisterNodeFunc func);\n\nXMLPUBFUN xmlOutputBufferCreateFilenameFunc XMLCALL\n\txmlThrDefOutputBufferCreateFilenameDefault(xmlOutputBufferCreateFilenameFunc func);\nXMLPUBFUN xmlParserInputBufferCreateFilenameFunc XMLCALL\n\txmlThrDefParserInputBufferCreateFilenameDefault(\n\t\t\t\txmlParserInputBufferCreateFilenameFunc func);\n\n/** DOC_DISABLE */\n/*\n * In general the memory allocation entry points are not kept\n * thread specific but this can be overridden by LIBXML_THREAD_ALLOC_ENABLED\n *    - xmlMalloc\n *    - xmlMallocAtomic\n *    - xmlRealloc\n *    - xmlMemStrdup\n *    - xmlFree\n */\n\n#ifdef LIBXML_THREAD_ALLOC_ENABLED\n#ifdef LIBXML_THREAD_ENABLED\nXMLPUBFUN  xmlMallocFunc * XMLCALL __xmlMalloc(void);\n#define xmlMalloc \\\n(*(__xmlMalloc()))\n#else\nXMLPUBVAR xmlMallocFunc xmlMalloc;\n#endif\n\n#ifdef LIBXML_THREAD_ENABLED\nXMLPUBFUN  xmlMallocFunc * XMLCALL __xmlMallocAtomic(void);\n#define xmlMallocAtomic \\\n(*(__xmlMallocAtomic()))\n#else\nXMLPUBVAR xmlMallocFunc xmlMallocAtomic;\n#endif\n\n#ifdef LIBXML_THREAD_ENABLED\nXMLPUBFUN  xmlReallocFunc * XMLCALL __xmlRealloc(void);\n#define xmlRealloc \\\n(*(__xmlRealloc()))\n#else\nXMLPUBVAR xmlReallocFunc xmlRealloc;\n#endif\n\n#ifdef LIBXML_THREAD_ENABLED\nXMLPUBFUN  xmlFreeFunc * XMLCALL __xmlFree(void);\n#define xmlFree \\\n(*(__xmlFree()))\n#else\nXMLPUBVAR xmlFreeFunc xmlFree;\n#endif\n\n#ifdef LIBXML_THREAD_ENABLED\nXMLPUBFUN  xmlStrdupFunc * XMLCALL __xmlMemStrdup(void);\n#define xmlMemStrdup \\\n(*(__xmlMemStrdup()))\n#else\nXMLPUBVAR xmlStrdupFunc xmlMemStrdup;\n#endif\n\n#else /* !LIBXML_THREAD_ALLOC_ENABLED */\nXMLPUBVAR xmlMallocFunc xmlMalloc;\nXMLPUBVAR xmlMallocFunc xmlMallocAtomic;\nXMLPUBVAR xmlReallocFunc xmlRealloc;\nXMLPUBVAR xmlFreeFunc xmlFree;\nXMLPUBVAR xmlStrdupFunc xmlMemStrdup;\n#endif /* LIBXML_THREAD_ALLOC_ENABLED */\n\n#ifdef LIBXML_DOCB_ENABLED\nXMLPUBFUN  xmlSAXHandlerV1 * XMLCALL __docbDefaultSAXHandler(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define docbDefaultSAXHandler \\\n(*(__docbDefaultSAXHandler()))\n#else\nXMLPUBVAR xmlSAXHandlerV1 docbDefaultSAXHandler;\n#endif\n#endif\n\n#ifdef LIBXML_HTML_ENABLED\nXMLPUBFUN xmlSAXHandlerV1 * XMLCALL __htmlDefaultSAXHandler(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define htmlDefaultSAXHandler \\\n(*(__htmlDefaultSAXHandler()))\n#else\nXMLPUBVAR xmlSAXHandlerV1 htmlDefaultSAXHandler;\n#endif\n#endif\n\nXMLPUBFUN xmlError * XMLCALL __xmlLastError(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlLastError \\\n(*(__xmlLastError()))\n#else\nXMLPUBVAR xmlError xmlLastError;\n#endif\n\n/*\n * Everything starting from the line below is\n * Automatically generated by build_glob.py.\n * Do not modify the previous line.\n */\n\n\nXMLPUBFUN int * XMLCALL __oldXMLWDcompatibility(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define oldXMLWDcompatibility \\\n(*(__oldXMLWDcompatibility()))\n#else\nXMLPUBVAR int oldXMLWDcompatibility;\n#endif\n\nXMLPUBFUN xmlBufferAllocationScheme * XMLCALL __xmlBufferAllocScheme(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlBufferAllocScheme \\\n(*(__xmlBufferAllocScheme()))\n#else\nXMLPUBVAR xmlBufferAllocationScheme xmlBufferAllocScheme;\n#endif\nXMLPUBFUN xmlBufferAllocationScheme XMLCALL\n\txmlThrDefBufferAllocScheme(xmlBufferAllocationScheme v);\n\nXMLPUBFUN int * XMLCALL __xmlDefaultBufferSize(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlDefaultBufferSize \\\n(*(__xmlDefaultBufferSize()))\n#else\nXMLPUBVAR int xmlDefaultBufferSize;\n#endif\nXMLPUBFUN int XMLCALL xmlThrDefDefaultBufferSize(int v);\n\nXMLPUBFUN xmlSAXHandlerV1 * XMLCALL __xmlDefaultSAXHandler(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlDefaultSAXHandler \\\n(*(__xmlDefaultSAXHandler()))\n#else\nXMLPUBVAR xmlSAXHandlerV1 xmlDefaultSAXHandler;\n#endif\n\nXMLPUBFUN xmlSAXLocator * XMLCALL __xmlDefaultSAXLocator(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlDefaultSAXLocator \\\n(*(__xmlDefaultSAXLocator()))\n#else\nXMLPUBVAR xmlSAXLocator xmlDefaultSAXLocator;\n#endif\n\nXMLPUBFUN int * XMLCALL __xmlDoValidityCheckingDefaultValue(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlDoValidityCheckingDefaultValue \\\n(*(__xmlDoValidityCheckingDefaultValue()))\n#else\nXMLPUBVAR int xmlDoValidityCheckingDefaultValue;\n#endif\nXMLPUBFUN int XMLCALL xmlThrDefDoValidityCheckingDefaultValue(int v);\n\nXMLPUBFUN xmlGenericErrorFunc * XMLCALL __xmlGenericError(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlGenericError \\\n(*(__xmlGenericError()))\n#else\nXMLPUBVAR xmlGenericErrorFunc xmlGenericError;\n#endif\n\nXMLPUBFUN xmlStructuredErrorFunc * XMLCALL __xmlStructuredError(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlStructuredError \\\n(*(__xmlStructuredError()))\n#else\nXMLPUBVAR xmlStructuredErrorFunc xmlStructuredError;\n#endif\n\nXMLPUBFUN void * * XMLCALL __xmlGenericErrorContext(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlGenericErrorContext \\\n(*(__xmlGenericErrorContext()))\n#else\nXMLPUBVAR void * xmlGenericErrorContext;\n#endif\n\nXMLPUBFUN void * * XMLCALL __xmlStructuredErrorContext(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlStructuredErrorContext \\\n(*(__xmlStructuredErrorContext()))\n#else\nXMLPUBVAR void * xmlStructuredErrorContext;\n#endif\n\nXMLPUBFUN int * XMLCALL __xmlGetWarningsDefaultValue(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlGetWarningsDefaultValue \\\n(*(__xmlGetWarningsDefaultValue()))\n#else\nXMLPUBVAR int xmlGetWarningsDefaultValue;\n#endif\nXMLPUBFUN int XMLCALL xmlThrDefGetWarningsDefaultValue(int v);\n\nXMLPUBFUN int * XMLCALL __xmlIndentTreeOutput(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlIndentTreeOutput \\\n(*(__xmlIndentTreeOutput()))\n#else\nXMLPUBVAR int xmlIndentTreeOutput;\n#endif\nXMLPUBFUN int XMLCALL xmlThrDefIndentTreeOutput(int v);\n\nXMLPUBFUN const char * * XMLCALL __xmlTreeIndentString(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlTreeIndentString \\\n(*(__xmlTreeIndentString()))\n#else\nXMLPUBVAR const char * xmlTreeIndentString;\n#endif\nXMLPUBFUN const char * XMLCALL xmlThrDefTreeIndentString(const char * v);\n\nXMLPUBFUN int * XMLCALL __xmlKeepBlanksDefaultValue(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlKeepBlanksDefaultValue \\\n(*(__xmlKeepBlanksDefaultValue()))\n#else\nXMLPUBVAR int xmlKeepBlanksDefaultValue;\n#endif\nXMLPUBFUN int XMLCALL xmlThrDefKeepBlanksDefaultValue(int v);\n\nXMLPUBFUN int * XMLCALL __xmlLineNumbersDefaultValue(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlLineNumbersDefaultValue \\\n(*(__xmlLineNumbersDefaultValue()))\n#else\nXMLPUBVAR int xmlLineNumbersDefaultValue;\n#endif\nXMLPUBFUN int XMLCALL xmlThrDefLineNumbersDefaultValue(int v);\n\nXMLPUBFUN int * XMLCALL __xmlLoadExtDtdDefaultValue(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlLoadExtDtdDefaultValue \\\n(*(__xmlLoadExtDtdDefaultValue()))\n#else\nXMLPUBVAR int xmlLoadExtDtdDefaultValue;\n#endif\nXMLPUBFUN int XMLCALL xmlThrDefLoadExtDtdDefaultValue(int v);\n\nXMLPUBFUN int * XMLCALL __xmlParserDebugEntities(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlParserDebugEntities \\\n(*(__xmlParserDebugEntities()))\n#else\nXMLPUBVAR int xmlParserDebugEntities;\n#endif\nXMLPUBFUN int XMLCALL xmlThrDefParserDebugEntities(int v);\n\nXMLPUBFUN const char * * XMLCALL __xmlParserVersion(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlParserVersion \\\n(*(__xmlParserVersion()))\n#else\nXMLPUBVAR const char * xmlParserVersion;\n#endif\n\nXMLPUBFUN int * XMLCALL __xmlPedanticParserDefaultValue(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlPedanticParserDefaultValue \\\n(*(__xmlPedanticParserDefaultValue()))\n#else\nXMLPUBVAR int xmlPedanticParserDefaultValue;\n#endif\nXMLPUBFUN int XMLCALL xmlThrDefPedanticParserDefaultValue(int v);\n\nXMLPUBFUN int * XMLCALL __xmlSaveNoEmptyTags(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlSaveNoEmptyTags \\\n(*(__xmlSaveNoEmptyTags()))\n#else\nXMLPUBVAR int xmlSaveNoEmptyTags;\n#endif\nXMLPUBFUN int XMLCALL xmlThrDefSaveNoEmptyTags(int v);\n\nXMLPUBFUN int * XMLCALL __xmlSubstituteEntitiesDefaultValue(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlSubstituteEntitiesDefaultValue \\\n(*(__xmlSubstituteEntitiesDefaultValue()))\n#else\nXMLPUBVAR int xmlSubstituteEntitiesDefaultValue;\n#endif\nXMLPUBFUN int XMLCALL xmlThrDefSubstituteEntitiesDefaultValue(int v);\n\nXMLPUBFUN xmlRegisterNodeFunc * XMLCALL __xmlRegisterNodeDefaultValue(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlRegisterNodeDefaultValue \\\n(*(__xmlRegisterNodeDefaultValue()))\n#else\nXMLPUBVAR xmlRegisterNodeFunc xmlRegisterNodeDefaultValue;\n#endif\n\nXMLPUBFUN xmlDeregisterNodeFunc * XMLCALL __xmlDeregisterNodeDefaultValue(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlDeregisterNodeDefaultValue \\\n(*(__xmlDeregisterNodeDefaultValue()))\n#else\nXMLPUBVAR xmlDeregisterNodeFunc xmlDeregisterNodeDefaultValue;\n#endif\n\nXMLPUBFUN xmlParserInputBufferCreateFilenameFunc * XMLCALL \\\n\t\t\t\t__xmlParserInputBufferCreateFilenameValue(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlParserInputBufferCreateFilenameValue \\\n(*(__xmlParserInputBufferCreateFilenameValue()))\n#else\nXMLPUBVAR xmlParserInputBufferCreateFilenameFunc xmlParserInputBufferCreateFilenameValue;\n#endif\n\nXMLPUBFUN xmlOutputBufferCreateFilenameFunc * XMLCALL __xmlOutputBufferCreateFilenameValue(void);\n#ifdef LIBXML_THREAD_ENABLED\n#define xmlOutputBufferCreateFilenameValue \\\n(*(__xmlOutputBufferCreateFilenameValue()))\n#else\nXMLPUBVAR xmlOutputBufferCreateFilenameFunc xmlOutputBufferCreateFilenameValue;\n#endif\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_GLOBALS_H */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/hash.h",
    "content": "/*\n * Summary: Chained hash tables\n * Description: This module implements the hash table support used in\n *\t\tvarious places in the library.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Bjorn Reese <bjorn.reese@systematic.dk>\n */\n\n#ifndef __XML_HASH_H__\n#define __XML_HASH_H__\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * The hash table.\n */\ntypedef struct _xmlHashTable xmlHashTable;\ntypedef xmlHashTable *xmlHashTablePtr;\n\n#ifdef __cplusplus\n}\n#endif\n\n#include <libxml/xmlversion.h>\n#include <libxml/parser.h>\n#include <libxml/dict.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * Recent version of gcc produce a warning when a function pointer is assigned\n * to an object pointer, or vice versa.  The following macro is a dirty hack\n * to allow suppression of the warning.  If your architecture has function\n * pointers which are a different size than a void pointer, there may be some\n * serious trouble within the library.\n */\n/**\n * XML_CAST_FPTR:\n * @fptr:  pointer to a function\n *\n * Macro to do a casting from an object pointer to a\n * function pointer without encountering a warning from\n * gcc\n *\n * #define XML_CAST_FPTR(fptr) (*(void **)(&fptr))\n * This macro violated ISO C aliasing rules (gcc4 on s390 broke)\n * so it is disabled now\n */\n\n#define XML_CAST_FPTR(fptr) fptr\n\n\n/*\n * function types:\n */\n/**\n * xmlHashDeallocator:\n * @payload:  the data in the hash\n * @name:  the name associated\n *\n * Callback to free data from a hash.\n */\ntypedef void (*xmlHashDeallocator)(void *payload, const xmlChar *name);\n/**\n * xmlHashCopier:\n * @payload:  the data in the hash\n * @name:  the name associated\n *\n * Callback to copy data from a hash.\n *\n * Returns a copy of the data or NULL in case of error.\n */\ntypedef void *(*xmlHashCopier)(void *payload, const xmlChar *name);\n/**\n * xmlHashScanner:\n * @payload:  the data in the hash\n * @data:  extra scannner data\n * @name:  the name associated\n *\n * Callback when scanning data in a hash with the simple scanner.\n */\ntypedef void (*xmlHashScanner)(void *payload, void *data, const xmlChar *name);\n/**\n * xmlHashScannerFull:\n * @payload:  the data in the hash\n * @data:  extra scannner data\n * @name:  the name associated\n * @name2:  the second name associated\n * @name3:  the third name associated\n *\n * Callback when scanning data in a hash with the full scanner.\n */\ntypedef void (*xmlHashScannerFull)(void *payload, void *data,\n\t\t\t\t   const xmlChar *name, const xmlChar *name2,\n\t\t\t\t   const xmlChar *name3);\n\n/*\n * Constructor and destructor.\n */\nXMLPUBFUN xmlHashTablePtr XMLCALL\n\t\t\txmlHashCreate\t(int size);\nXMLPUBFUN xmlHashTablePtr XMLCALL\n\t\t\txmlHashCreateDict(int size,\n\t\t\t\t\t xmlDictPtr dict);\nXMLPUBFUN void XMLCALL\n\t\t\txmlHashFree\t(xmlHashTablePtr table,\n\t\t\t\t\t xmlHashDeallocator f);\nXMLPUBFUN void XMLCALL\n\t\t\txmlHashDefaultDeallocator(void *entry,\n\t\t\t\t\t const xmlChar *name);\n\n/*\n * Add a new entry to the hash table.\n */\nXMLPUBFUN int XMLCALL\n\t\t\txmlHashAddEntry\t(xmlHashTablePtr table,\n\t\t                         const xmlChar *name,\n\t\t                         void *userdata);\nXMLPUBFUN int XMLCALL\n\t\t\txmlHashUpdateEntry(xmlHashTablePtr table,\n\t\t                         const xmlChar *name,\n\t\t                         void *userdata,\n\t\t\t\t\t xmlHashDeallocator f);\nXMLPUBFUN int XMLCALL\n\t\t\txmlHashAddEntry2(xmlHashTablePtr table,\n\t\t                         const xmlChar *name,\n\t\t                         const xmlChar *name2,\n\t\t                         void *userdata);\nXMLPUBFUN int XMLCALL\n\t\t\txmlHashUpdateEntry2(xmlHashTablePtr table,\n\t\t                         const xmlChar *name,\n\t\t                         const xmlChar *name2,\n\t\t                         void *userdata,\n\t\t\t\t\t xmlHashDeallocator f);\nXMLPUBFUN int XMLCALL\n\t\t\txmlHashAddEntry3(xmlHashTablePtr table,\n\t\t                         const xmlChar *name,\n\t\t                         const xmlChar *name2,\n\t\t                         const xmlChar *name3,\n\t\t                         void *userdata);\nXMLPUBFUN int XMLCALL\n\t\t\txmlHashUpdateEntry3(xmlHashTablePtr table,\n\t\t                         const xmlChar *name,\n\t\t                         const xmlChar *name2,\n\t\t                         const xmlChar *name3,\n\t\t                         void *userdata,\n\t\t\t\t\t xmlHashDeallocator f);\n\n/*\n * Remove an entry from the hash table.\n */\nXMLPUBFUN int XMLCALL\n\t\t\txmlHashRemoveEntry(xmlHashTablePtr table, const xmlChar *name,\n                           xmlHashDeallocator f);\nXMLPUBFUN int XMLCALL\n\t\t\txmlHashRemoveEntry2(xmlHashTablePtr table, const xmlChar *name,\n                            const xmlChar *name2, xmlHashDeallocator f);\nXMLPUBFUN int  XMLCALL\n\t\t\txmlHashRemoveEntry3(xmlHashTablePtr table, const xmlChar *name,\n                            const xmlChar *name2, const xmlChar *name3,\n                            xmlHashDeallocator f);\n\n/*\n * Retrieve the userdata.\n */\nXMLPUBFUN void * XMLCALL\n\t\t\txmlHashLookup\t(xmlHashTablePtr table,\n\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN void * XMLCALL\n\t\t\txmlHashLookup2\t(xmlHashTablePtr table,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *name2);\nXMLPUBFUN void * XMLCALL\n\t\t\txmlHashLookup3\t(xmlHashTablePtr table,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *name2,\n\t\t\t\t\t const xmlChar *name3);\nXMLPUBFUN void * XMLCALL\n\t\t\txmlHashQLookup\t(xmlHashTablePtr table,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *prefix);\nXMLPUBFUN void * XMLCALL\n\t\t\txmlHashQLookup2\t(xmlHashTablePtr table,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *prefix,\n\t\t\t\t\t const xmlChar *name2,\n\t\t\t\t\t const xmlChar *prefix2);\nXMLPUBFUN void * XMLCALL\n\t\t\txmlHashQLookup3\t(xmlHashTablePtr table,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *prefix,\n\t\t\t\t\t const xmlChar *name2,\n\t\t\t\t\t const xmlChar *prefix2,\n\t\t\t\t\t const xmlChar *name3,\n\t\t\t\t\t const xmlChar *prefix3);\n\n/*\n * Helpers.\n */\nXMLPUBFUN xmlHashTablePtr XMLCALL\n\t\t\txmlHashCopy\t(xmlHashTablePtr table,\n\t\t\t\t\t xmlHashCopier f);\nXMLPUBFUN int XMLCALL\n\t\t\txmlHashSize\t(xmlHashTablePtr table);\nXMLPUBFUN void XMLCALL\n\t\t\txmlHashScan\t(xmlHashTablePtr table,\n\t\t\t\t\t xmlHashScanner f,\n\t\t\t\t\t void *data);\nXMLPUBFUN void XMLCALL\n\t\t\txmlHashScan3\t(xmlHashTablePtr table,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *name2,\n\t\t\t\t\t const xmlChar *name3,\n\t\t\t\t\t xmlHashScanner f,\n\t\t\t\t\t void *data);\nXMLPUBFUN void XMLCALL\n\t\t\txmlHashScanFull\t(xmlHashTablePtr table,\n\t\t\t\t\t xmlHashScannerFull f,\n\t\t\t\t\t void *data);\nXMLPUBFUN void XMLCALL\n\t\t\txmlHashScanFull3(xmlHashTablePtr table,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *name2,\n\t\t\t\t\t const xmlChar *name3,\n\t\t\t\t\t xmlHashScannerFull f,\n\t\t\t\t\t void *data);\n#ifdef __cplusplus\n}\n#endif\n#endif /* ! __XML_HASH_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/list.h",
    "content": "/*\n * Summary: lists interfaces\n * Description: this module implement the list support used in\n * various place in the library.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Gary Pennington <Gary.Pennington@uk.sun.com>\n */\n\n#ifndef __XML_LINK_INCLUDE__\n#define __XML_LINK_INCLUDE__\n\n#include <libxml/xmlversion.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\ntypedef struct _xmlLink xmlLink;\ntypedef xmlLink *xmlLinkPtr;\n\ntypedef struct _xmlList xmlList;\ntypedef xmlList *xmlListPtr;\n\n/**\n * xmlListDeallocator:\n * @lk:  the data to deallocate\n *\n * Callback function used to free data from a list.\n */\ntypedef void (*xmlListDeallocator) (xmlLinkPtr lk);\n/**\n * xmlListDataCompare:\n * @data0: the first data\n * @data1: the second data\n *\n * Callback function used to compare 2 data.\n *\n * Returns 0 is equality, -1 or 1 otherwise depending on the ordering.\n */\ntypedef int  (*xmlListDataCompare) (const void *data0, const void *data1);\n/**\n * xmlListWalker:\n * @data: the data found in the list\n * @user: extra user provided data to the walker\n *\n * Callback function used when walking a list with xmlListWalk().\n *\n * Returns 0 to stop walking the list, 1 otherwise.\n */\ntypedef int (*xmlListWalker) (const void *data, void *user);\n\n/* Creation/Deletion */\nXMLPUBFUN xmlListPtr XMLCALL\n\t\txmlListCreate\t\t(xmlListDeallocator deallocator,\n\t                                 xmlListDataCompare compare);\nXMLPUBFUN void XMLCALL\n\t\txmlListDelete\t\t(xmlListPtr l);\n\n/* Basic Operators */\nXMLPUBFUN void * XMLCALL\n\t\txmlListSearch\t\t(xmlListPtr l,\n\t\t\t\t\t void *data);\nXMLPUBFUN void * XMLCALL\n\t\txmlListReverseSearch\t(xmlListPtr l,\n\t\t\t\t\t void *data);\nXMLPUBFUN int XMLCALL\n\t\txmlListInsert\t\t(xmlListPtr l,\n\t\t\t\t\t void *data) ;\nXMLPUBFUN int XMLCALL\n\t\txmlListAppend\t\t(xmlListPtr l,\n\t\t\t\t\t void *data) ;\nXMLPUBFUN int XMLCALL\n\t\txmlListRemoveFirst\t(xmlListPtr l,\n\t\t\t\t\t void *data);\nXMLPUBFUN int XMLCALL\n\t\txmlListRemoveLast\t(xmlListPtr l,\n\t\t\t\t\t void *data);\nXMLPUBFUN int XMLCALL\n\t\txmlListRemoveAll\t(xmlListPtr l,\n\t\t\t\t\t void *data);\nXMLPUBFUN void XMLCALL\n\t\txmlListClear\t\t(xmlListPtr l);\nXMLPUBFUN int XMLCALL\n\t\txmlListEmpty\t\t(xmlListPtr l);\nXMLPUBFUN xmlLinkPtr XMLCALL\n\t\txmlListFront\t\t(xmlListPtr l);\nXMLPUBFUN xmlLinkPtr XMLCALL\n\t\txmlListEnd\t\t(xmlListPtr l);\nXMLPUBFUN int XMLCALL\n\t\txmlListSize\t\t(xmlListPtr l);\n\nXMLPUBFUN void XMLCALL\n\t\txmlListPopFront\t\t(xmlListPtr l);\nXMLPUBFUN void XMLCALL\n\t\txmlListPopBack\t\t(xmlListPtr l);\nXMLPUBFUN int XMLCALL\n\t\txmlListPushFront\t(xmlListPtr l,\n\t\t\t\t\t void *data);\nXMLPUBFUN int XMLCALL\n\t\txmlListPushBack\t\t(xmlListPtr l,\n\t\t\t\t\t void *data);\n\n/* Advanced Operators */\nXMLPUBFUN void XMLCALL\n\t\txmlListReverse\t\t(xmlListPtr l);\nXMLPUBFUN void XMLCALL\n\t\txmlListSort\t\t(xmlListPtr l);\nXMLPUBFUN void XMLCALL\n\t\txmlListWalk\t\t(xmlListPtr l,\n\t\t\t\t\t xmlListWalker walker,\n\t\t\t\t\t void *user);\nXMLPUBFUN void XMLCALL\n\t\txmlListReverseWalk\t(xmlListPtr l,\n\t\t\t\t\t xmlListWalker walker,\n\t\t\t\t\t void *user);\nXMLPUBFUN void XMLCALL\n\t\txmlListMerge\t\t(xmlListPtr l1,\n\t\t\t\t\t xmlListPtr l2);\nXMLPUBFUN xmlListPtr XMLCALL\n\t\txmlListDup\t\t(const xmlListPtr old);\nXMLPUBFUN int XMLCALL\n\t\txmlListCopy\t\t(xmlListPtr cur,\n\t\t\t\t\t const xmlListPtr old);\n/* Link operators */\nXMLPUBFUN void * XMLCALL\n\t\txmlLinkGetData          (xmlLinkPtr lk);\n\n/* xmlListUnique() */\n/* xmlListSwap */\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_LINK_INCLUDE__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/nanoftp.h",
    "content": "/*\n * Summary: minimal FTP implementation\n * Description: minimal FTP implementation allowing to fetch resources\n *              like external subset.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __NANO_FTP_H__\n#define __NANO_FTP_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_FTP_ENABLED\n\n/* Needed for portability to Windows 64 bits */\n#if defined(_WIN32) && !defined(__CYGWIN__)\n#include <winsock2.h>\n#else\n/**\n * SOCKET:\n *\n * macro used to provide portability of code to windows sockets\n */\n#define SOCKET int\n/**\n * INVALID_SOCKET:\n *\n * macro used to provide portability of code to windows sockets\n * the value to be used when the socket is not valid\n */\n#undef  INVALID_SOCKET\n#define INVALID_SOCKET (-1)\n#endif\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * ftpListCallback:\n * @userData:  user provided data for the callback\n * @filename:  the file name (including \"->\" when links are shown)\n * @attrib:  the attribute string\n * @owner:  the owner string\n * @group:  the group string\n * @size:  the file size\n * @links:  the link count\n * @year:  the year\n * @month:  the month\n * @day:  the day\n * @hour:  the hour\n * @minute:  the minute\n *\n * A callback for the xmlNanoFTPList command.\n * Note that only one of year and day:minute are specified.\n */\ntypedef void (*ftpListCallback) (void *userData,\n\t                         const char *filename, const char *attrib,\n\t                         const char *owner, const char *group,\n\t\t\t\t unsigned long size, int links, int year,\n\t\t\t\t const char *month, int day, int hour,\n\t\t\t\t int minute);\n/**\n * ftpDataCallback:\n * @userData: the user provided context\n * @data: the data received\n * @len: its size in bytes\n *\n * A callback for the xmlNanoFTPGet command.\n */\ntypedef void (*ftpDataCallback) (void *userData,\n\t\t\t\t const char *data,\n\t\t\t\t int len);\n\n/*\n * Init\n */\nXMLPUBFUN void XMLCALL\n\txmlNanoFTPInit\t\t(void);\nXMLPUBFUN void XMLCALL\n\txmlNanoFTPCleanup\t(void);\n\n/*\n * Creating/freeing contexts.\n */\nXMLPUBFUN void * XMLCALL\n\txmlNanoFTPNewCtxt\t(const char *URL);\nXMLPUBFUN void XMLCALL\n\txmlNanoFTPFreeCtxt\t(void * ctx);\nXMLPUBFUN void * XMLCALL\n\txmlNanoFTPConnectTo\t(const char *server,\n\t\t\t\t int port);\n/*\n * Opening/closing session connections.\n */\nXMLPUBFUN void * XMLCALL\n\txmlNanoFTPOpen\t\t(const char *URL);\nXMLPUBFUN int XMLCALL\n\txmlNanoFTPConnect\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\txmlNanoFTPClose\t\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\txmlNanoFTPQuit\t\t(void *ctx);\nXMLPUBFUN void XMLCALL\n\txmlNanoFTPScanProxy\t(const char *URL);\nXMLPUBFUN void XMLCALL\n\txmlNanoFTPProxy\t\t(const char *host,\n\t\t\t\t int port,\n\t\t\t\t const char *user,\n\t\t\t\t const char *passwd,\n\t\t\t\t int type);\nXMLPUBFUN int XMLCALL\n\txmlNanoFTPUpdateURL\t(void *ctx,\n\t\t\t\t const char *URL);\n\n/*\n * Rather internal commands.\n */\nXMLPUBFUN int XMLCALL\n\txmlNanoFTPGetResponse\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\txmlNanoFTPCheckResponse\t(void *ctx);\n\n/*\n * CD/DIR/GET handlers.\n */\nXMLPUBFUN int XMLCALL\n\txmlNanoFTPCwd\t\t(void *ctx,\n\t\t\t\t const char *directory);\nXMLPUBFUN int XMLCALL\n\txmlNanoFTPDele\t\t(void *ctx,\n\t\t\t\t const char *file);\n\nXMLPUBFUN SOCKET XMLCALL\n\txmlNanoFTPGetConnection\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\txmlNanoFTPCloseConnection(void *ctx);\nXMLPUBFUN int XMLCALL\n\txmlNanoFTPList\t\t(void *ctx,\n\t\t\t\t ftpListCallback callback,\n\t\t\t\t void *userData,\n\t\t\t\t const char *filename);\nXMLPUBFUN SOCKET XMLCALL\n\txmlNanoFTPGetSocket\t(void *ctx,\n\t\t\t\t const char *filename);\nXMLPUBFUN int XMLCALL\n\txmlNanoFTPGet\t\t(void *ctx,\n\t\t\t\t ftpDataCallback callback,\n\t\t\t\t void *userData,\n\t\t\t\t const char *filename);\nXMLPUBFUN int XMLCALL\n\txmlNanoFTPRead\t\t(void *ctx,\n\t\t\t\t void *dest,\n\t\t\t\t int len);\n\n#ifdef __cplusplus\n}\n#endif\n#endif /* LIBXML_FTP_ENABLED */\n#endif /* __NANO_FTP_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/nanohttp.h",
    "content": "/*\n * Summary: minimal HTTP implementation\n * Description: minimal HTTP implementation allowing to fetch resources\n *              like external subset.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __NANO_HTTP_H__\n#define __NANO_HTTP_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_HTTP_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\nXMLPUBFUN void XMLCALL\n\txmlNanoHTTPInit\t\t(void);\nXMLPUBFUN void XMLCALL\n\txmlNanoHTTPCleanup\t(void);\nXMLPUBFUN void XMLCALL\n\txmlNanoHTTPScanProxy\t(const char *URL);\nXMLPUBFUN int XMLCALL\n\txmlNanoHTTPFetch\t(const char *URL,\n\t\t\t\t const char *filename,\n\t\t\t\t char **contentType);\nXMLPUBFUN void * XMLCALL\n\txmlNanoHTTPMethod\t(const char *URL,\n\t\t\t\t const char *method,\n\t\t\t\t const char *input,\n\t\t\t\t char **contentType,\n\t\t\t\t const char *headers,\n\t\t\t\t int   ilen);\nXMLPUBFUN void * XMLCALL\n\txmlNanoHTTPMethodRedir\t(const char *URL,\n\t\t\t\t const char *method,\n\t\t\t\t const char *input,\n\t\t\t\t char **contentType,\n\t\t\t\t char **redir,\n\t\t\t\t const char *headers,\n\t\t\t\t int   ilen);\nXMLPUBFUN void * XMLCALL\n\txmlNanoHTTPOpen\t\t(const char *URL,\n\t\t\t\t char **contentType);\nXMLPUBFUN void * XMLCALL\n\txmlNanoHTTPOpenRedir\t(const char *URL,\n\t\t\t\t char **contentType,\n\t\t\t\t char **redir);\nXMLPUBFUN int XMLCALL\n\txmlNanoHTTPReturnCode\t(void *ctx);\nXMLPUBFUN const char * XMLCALL\n\txmlNanoHTTPAuthHeader\t(void *ctx);\nXMLPUBFUN const char * XMLCALL\n\txmlNanoHTTPRedir\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\txmlNanoHTTPContentLength( void * ctx );\nXMLPUBFUN const char * XMLCALL\n\txmlNanoHTTPEncoding\t(void *ctx);\nXMLPUBFUN const char * XMLCALL\n\txmlNanoHTTPMimeType\t(void *ctx);\nXMLPUBFUN int XMLCALL\n\txmlNanoHTTPRead\t\t(void *ctx,\n\t\t\t\t void *dest,\n\t\t\t\t int len);\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN int XMLCALL\n\txmlNanoHTTPSave\t\t(void *ctxt,\n\t\t\t\t const char *filename);\n#endif /* LIBXML_OUTPUT_ENABLED */\nXMLPUBFUN void XMLCALL\n\txmlNanoHTTPClose\t(void *ctx);\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_HTTP_ENABLED */\n#endif /* __NANO_HTTP_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/parser.h",
    "content": "/*\n * Summary: the core parser module\n * Description: Interfaces, constants and types related to the XML parser\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_PARSER_H__\n#define __XML_PARSER_H__\n\n#include <stdarg.h>\n\n#include <libxml/xmlversion.h>\n#include <libxml/tree.h>\n#include <libxml/dict.h>\n#include <libxml/hash.h>\n#include <libxml/valid.h>\n#include <libxml/entities.h>\n#include <libxml/xmlerror.h>\n#include <libxml/xmlstring.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * XML_DEFAULT_VERSION:\n *\n * The default version of XML used: 1.0\n */\n#define XML_DEFAULT_VERSION\t\"1.0\"\n\n/**\n * xmlParserInput:\n *\n * An xmlParserInput is an input flow for the XML processor.\n * Each entity parsed is associated an xmlParserInput (except the\n * few predefined ones). This is the case both for internal entities\n * - in which case the flow is already completely in memory - or\n * external entities - in which case we use the buf structure for\n * progressive reading and I18N conversions to the internal UTF-8 format.\n */\n\n/**\n * xmlParserInputDeallocate:\n * @str:  the string to deallocate\n *\n * Callback for freeing some parser input allocations.\n */\ntypedef void (* xmlParserInputDeallocate)(xmlChar *str);\n\nstruct _xmlParserInput {\n    /* Input buffer */\n    xmlParserInputBufferPtr buf;      /* UTF-8 encoded buffer */\n\n    const char *filename;             /* The file analyzed, if any */\n    const char *directory;            /* the directory/base of the file */\n    const xmlChar *base;              /* Base of the array to parse */\n    const xmlChar *cur;               /* Current char being parsed */\n    const xmlChar *end;               /* end of the array to parse */\n    int length;                       /* length if known */\n    int line;                         /* Current line */\n    int col;                          /* Current column */\n    /*\n     * NOTE: consumed is only tested for equality in the parser code,\n     *       so even if there is an overflow this should not give troubles\n     *       for parsing very large instances.\n     */\n    unsigned long consumed;           /* How many xmlChars already consumed */\n    xmlParserInputDeallocate free;    /* function to deallocate the base */\n    const xmlChar *encoding;          /* the encoding string for entity */\n    const xmlChar *version;           /* the version string for entity */\n    int standalone;                   /* Was that entity marked standalone */\n    int id;                           /* an unique identifier for the entity */\n};\n\n/**\n * xmlParserNodeInfo:\n *\n * The parser can be asked to collect Node informations, i.e. at what\n * place in the file they were detected.\n * NOTE: This is off by default and not very well tested.\n */\ntypedef struct _xmlParserNodeInfo xmlParserNodeInfo;\ntypedef xmlParserNodeInfo *xmlParserNodeInfoPtr;\n\nstruct _xmlParserNodeInfo {\n  const struct _xmlNode* node;\n  /* Position & line # that text that created the node begins & ends on */\n  unsigned long begin_pos;\n  unsigned long begin_line;\n  unsigned long end_pos;\n  unsigned long end_line;\n};\n\ntypedef struct _xmlParserNodeInfoSeq xmlParserNodeInfoSeq;\ntypedef xmlParserNodeInfoSeq *xmlParserNodeInfoSeqPtr;\nstruct _xmlParserNodeInfoSeq {\n  unsigned long maximum;\n  unsigned long length;\n  xmlParserNodeInfo* buffer;\n};\n\n/**\n * xmlParserInputState:\n *\n * The parser is now working also as a state based parser.\n * The recursive one use the state info for entities processing.\n */\ntypedef enum {\n    XML_PARSER_EOF = -1,\t/* nothing is to be parsed */\n    XML_PARSER_START = 0,\t/* nothing has been parsed */\n    XML_PARSER_MISC,\t\t/* Misc* before int subset */\n    XML_PARSER_PI,\t\t/* Within a processing instruction */\n    XML_PARSER_DTD,\t\t/* within some DTD content */\n    XML_PARSER_PROLOG,\t\t/* Misc* after internal subset */\n    XML_PARSER_COMMENT,\t\t/* within a comment */\n    XML_PARSER_START_TAG,\t/* within a start tag */\n    XML_PARSER_CONTENT,\t\t/* within the content */\n    XML_PARSER_CDATA_SECTION,\t/* within a CDATA section */\n    XML_PARSER_END_TAG,\t\t/* within a closing tag */\n    XML_PARSER_ENTITY_DECL,\t/* within an entity declaration */\n    XML_PARSER_ENTITY_VALUE,\t/* within an entity value in a decl */\n    XML_PARSER_ATTRIBUTE_VALUE,\t/* within an attribute value */\n    XML_PARSER_SYSTEM_LITERAL,\t/* within a SYSTEM value */\n    XML_PARSER_EPILOG,\t\t/* the Misc* after the last end tag */\n    XML_PARSER_IGNORE,\t\t/* within an IGNORED section */\n    XML_PARSER_PUBLIC_LITERAL\t/* within a PUBLIC value */\n} xmlParserInputState;\n\n/**\n * XML_DETECT_IDS:\n *\n * Bit in the loadsubset context field to tell to do ID/REFs lookups.\n * Use it to initialize xmlLoadExtDtdDefaultValue.\n */\n#define XML_DETECT_IDS\t\t2\n\n/**\n * XML_COMPLETE_ATTRS:\n *\n * Bit in the loadsubset context field to tell to do complete the\n * elements attributes lists with the ones defaulted from the DTDs.\n * Use it to initialize xmlLoadExtDtdDefaultValue.\n */\n#define XML_COMPLETE_ATTRS\t4\n\n/**\n * XML_SKIP_IDS:\n *\n * Bit in the loadsubset context field to tell to not do ID/REFs registration.\n * Used to initialize xmlLoadExtDtdDefaultValue in some special cases.\n */\n#define XML_SKIP_IDS\t\t8\n\n/**\n * xmlParserMode:\n *\n * A parser can operate in various modes\n */\ntypedef enum {\n    XML_PARSE_UNKNOWN = 0,\n    XML_PARSE_DOM = 1,\n    XML_PARSE_SAX = 2,\n    XML_PARSE_PUSH_DOM = 3,\n    XML_PARSE_PUSH_SAX = 4,\n    XML_PARSE_READER = 5\n} xmlParserMode;\n\n/**\n * xmlParserCtxt:\n *\n * The parser context.\n * NOTE This doesn't completely define the parser state, the (current ?)\n *      design of the parser uses recursive function calls since this allow\n *      and easy mapping from the production rules of the specification\n *      to the actual code. The drawback is that the actual function call\n *      also reflect the parser state. However most of the parsing routines\n *      takes as the only argument the parser context pointer, so migrating\n *      to a state based parser for progressive parsing shouldn't be too hard.\n */\nstruct _xmlParserCtxt {\n    struct _xmlSAXHandler *sax;       /* The SAX handler */\n    void            *userData;        /* For SAX interface only, used by DOM build */\n    xmlDocPtr           myDoc;        /* the document being built */\n    int            wellFormed;        /* is the document well formed */\n    int       replaceEntities;        /* shall we replace entities ? */\n    const xmlChar    *version;        /* the XML version string */\n    const xmlChar   *encoding;        /* the declared encoding, if any */\n    int            standalone;        /* standalone document */\n    int                  html;        /* an HTML(1)/Docbook(2) document\n                                       * 3 is HTML after <head>\n                                       * 10 is HTML after <body>\n                                       */\n\n    /* Input stream stack */\n    xmlParserInputPtr  input;         /* Current input stream */\n    int                inputNr;       /* Number of current input streams */\n    int                inputMax;      /* Max number of input streams */\n    xmlParserInputPtr *inputTab;      /* stack of inputs */\n\n    /* Node analysis stack only used for DOM building */\n    xmlNodePtr         node;          /* Current parsed Node */\n    int                nodeNr;        /* Depth of the parsing stack */\n    int                nodeMax;       /* Max depth of the parsing stack */\n    xmlNodePtr        *nodeTab;       /* array of nodes */\n\n    int record_info;                  /* Whether node info should be kept */\n    xmlParserNodeInfoSeq node_seq;    /* info about each node parsed */\n\n    int errNo;                        /* error code */\n\n    int     hasExternalSubset;        /* reference and external subset */\n    int             hasPErefs;        /* the internal subset has PE refs */\n    int              external;        /* are we parsing an external entity */\n\n    int                 valid;        /* is the document valid */\n    int              validate;        /* shall we try to validate ? */\n    xmlValidCtxt        vctxt;        /* The validity context */\n\n    xmlParserInputState instate;      /* current type of input */\n    int                 token;        /* next char look-ahead */\n\n    char           *directory;        /* the data directory */\n\n    /* Node name stack */\n    const xmlChar     *name;          /* Current parsed Node */\n    int                nameNr;        /* Depth of the parsing stack */\n    int                nameMax;       /* Max depth of the parsing stack */\n    const xmlChar *   *nameTab;       /* array of nodes */\n\n    long               nbChars;       /* number of xmlChar processed */\n    long            checkIndex;       /* used by progressive parsing lookup */\n    int             keepBlanks;       /* ugly but ... */\n    int             disableSAX;       /* SAX callbacks are disabled */\n    int               inSubset;       /* Parsing is in int 1/ext 2 subset */\n    const xmlChar *    intSubName;    /* name of subset */\n    xmlChar *          extSubURI;     /* URI of external subset */\n    xmlChar *          extSubSystem;  /* SYSTEM ID of external subset */\n\n    /* xml:space values */\n    int *              space;         /* Should the parser preserve spaces */\n    int                spaceNr;       /* Depth of the parsing stack */\n    int                spaceMax;      /* Max depth of the parsing stack */\n    int *              spaceTab;      /* array of space infos */\n\n    int                depth;         /* to prevent entity substitution loops */\n    xmlParserInputPtr  entity;        /* used to check entities boundaries */\n    int                charset;       /* encoding of the in-memory content\n\t\t\t\t         actually an xmlCharEncoding */\n    int                nodelen;       /* Those two fields are there to */\n    int                nodemem;       /* Speed up large node parsing */\n    int                pedantic;      /* signal pedantic warnings */\n    void              *_private;      /* For user data, libxml won't touch it */\n\n    int                loadsubset;    /* should the external subset be loaded */\n    int                linenumbers;   /* set line number in element content */\n    void              *catalogs;      /* document's own catalog */\n    int                recovery;      /* run in recovery mode */\n    int                progressive;   /* is this a progressive parsing */\n    xmlDictPtr         dict;          /* dictionary for the parser */\n    const xmlChar *   *atts;          /* array for the attributes callbacks */\n    int                maxatts;       /* the size of the array */\n    int                docdict;       /* use strings from dict to build tree */\n\n    /*\n     * pre-interned strings\n     */\n    const xmlChar *str_xml;\n    const xmlChar *str_xmlns;\n    const xmlChar *str_xml_ns;\n\n    /*\n     * Everything below is used only by the new SAX mode\n     */\n    int                sax2;          /* operating in the new SAX mode */\n    int                nsNr;          /* the number of inherited namespaces */\n    int                nsMax;         /* the size of the arrays */\n    const xmlChar *   *nsTab;         /* the array of prefix/namespace name */\n    int               *attallocs;     /* which attribute were allocated */\n    void *            *pushTab;       /* array of data for push */\n    xmlHashTablePtr    attsDefault;   /* defaulted attributes if any */\n    xmlHashTablePtr    attsSpecial;   /* non-CDATA attributes if any */\n    int                nsWellFormed;  /* is the document XML Nanespace okay */\n    int                options;       /* Extra options */\n\n    /*\n     * Those fields are needed only for treaming parsing so far\n     */\n    int               dictNames;    /* Use dictionary names for the tree */\n    int               freeElemsNr;  /* number of freed element nodes */\n    xmlNodePtr        freeElems;    /* List of freed element nodes */\n    int               freeAttrsNr;  /* number of freed attributes nodes */\n    xmlAttrPtr        freeAttrs;    /* List of freed attributes nodes */\n\n    /*\n     * the complete error informations for the last error.\n     */\n    xmlError          lastError;\n    xmlParserMode     parseMode;    /* the parser mode */\n    unsigned long    nbentities;    /* number of entities references */\n    unsigned long  sizeentities;    /* size of parsed entities */\n\n    /* for use by HTML non-recursive parser */\n    xmlParserNodeInfo *nodeInfo;      /* Current NodeInfo */\n    int                nodeInfoNr;    /* Depth of the parsing stack */\n    int                nodeInfoMax;   /* Max depth of the parsing stack */\n    xmlParserNodeInfo *nodeInfoTab;   /* array of nodeInfos */\n\n    int                input_id;      /* we need to label inputs */\n    unsigned long      sizeentcopy;   /* volume of entity copy */\n};\n\n/**\n * xmlSAXLocator:\n *\n * A SAX Locator.\n */\nstruct _xmlSAXLocator {\n    const xmlChar *(*getPublicId)(void *ctx);\n    const xmlChar *(*getSystemId)(void *ctx);\n    int (*getLineNumber)(void *ctx);\n    int (*getColumnNumber)(void *ctx);\n};\n\n/**\n * xmlSAXHandler:\n *\n * A SAX handler is bunch of callbacks called by the parser when processing\n * of the input generate data or structure informations.\n */\n\n/**\n * resolveEntitySAXFunc:\n * @ctx:  the user data (XML parser context)\n * @publicId: The public ID of the entity\n * @systemId: The system ID of the entity\n *\n * Callback:\n * The entity loader, to control the loading of external entities,\n * the application can either:\n *    - override this resolveEntity() callback in the SAX block\n *    - or better use the xmlSetExternalEntityLoader() function to\n *      set up it's own entity resolution routine\n *\n * Returns the xmlParserInputPtr if inlined or NULL for DOM behaviour.\n */\ntypedef xmlParserInputPtr (*resolveEntitySAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *publicId,\n\t\t\t\tconst xmlChar *systemId);\n/**\n * internalSubsetSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @name:  the root element name\n * @ExternalID:  the external ID\n * @SystemID:  the SYSTEM ID (e.g. filename or URL)\n *\n * Callback on internal subset declaration.\n */\ntypedef void (*internalSubsetSAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *name,\n\t\t\t\tconst xmlChar *ExternalID,\n\t\t\t\tconst xmlChar *SystemID);\n/**\n * externalSubsetSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @name:  the root element name\n * @ExternalID:  the external ID\n * @SystemID:  the SYSTEM ID (e.g. filename or URL)\n *\n * Callback on external subset declaration.\n */\ntypedef void (*externalSubsetSAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *name,\n\t\t\t\tconst xmlChar *ExternalID,\n\t\t\t\tconst xmlChar *SystemID);\n/**\n * getEntitySAXFunc:\n * @ctx:  the user data (XML parser context)\n * @name: The entity name\n *\n * Get an entity by name.\n *\n * Returns the xmlEntityPtr if found.\n */\ntypedef xmlEntityPtr (*getEntitySAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *name);\n/**\n * getParameterEntitySAXFunc:\n * @ctx:  the user data (XML parser context)\n * @name: The entity name\n *\n * Get a parameter entity by name.\n *\n * Returns the xmlEntityPtr if found.\n */\ntypedef xmlEntityPtr (*getParameterEntitySAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *name);\n/**\n * entityDeclSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @name:  the entity name\n * @type:  the entity type\n * @publicId: The public ID of the entity\n * @systemId: The system ID of the entity\n * @content: the entity value (without processing).\n *\n * An entity definition has been parsed.\n */\ntypedef void (*entityDeclSAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *name,\n\t\t\t\tint type,\n\t\t\t\tconst xmlChar *publicId,\n\t\t\t\tconst xmlChar *systemId,\n\t\t\t\txmlChar *content);\n/**\n * notationDeclSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @name: The name of the notation\n * @publicId: The public ID of the entity\n * @systemId: The system ID of the entity\n *\n * What to do when a notation declaration has been parsed.\n */\ntypedef void (*notationDeclSAXFunc)(void *ctx,\n\t\t\t\tconst xmlChar *name,\n\t\t\t\tconst xmlChar *publicId,\n\t\t\t\tconst xmlChar *systemId);\n/**\n * attributeDeclSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @elem:  the name of the element\n * @fullname:  the attribute name\n * @type:  the attribute type\n * @def:  the type of default value\n * @defaultValue: the attribute default value\n * @tree:  the tree of enumerated value set\n *\n * An attribute definition has been parsed.\n */\ntypedef void (*attributeDeclSAXFunc)(void *ctx,\n\t\t\t\tconst xmlChar *elem,\n\t\t\t\tconst xmlChar *fullname,\n\t\t\t\tint type,\n\t\t\t\tint def,\n\t\t\t\tconst xmlChar *defaultValue,\n\t\t\t\txmlEnumerationPtr tree);\n/**\n * elementDeclSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @name:  the element name\n * @type:  the element type\n * @content: the element value tree\n *\n * An element definition has been parsed.\n */\ntypedef void (*elementDeclSAXFunc)(void *ctx,\n\t\t\t\tconst xmlChar *name,\n\t\t\t\tint type,\n\t\t\t\txmlElementContentPtr content);\n/**\n * unparsedEntityDeclSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @name: The name of the entity\n * @publicId: The public ID of the entity\n * @systemId: The system ID of the entity\n * @notationName: the name of the notation\n *\n * What to do when an unparsed entity declaration is parsed.\n */\ntypedef void (*unparsedEntityDeclSAXFunc)(void *ctx,\n\t\t\t\tconst xmlChar *name,\n\t\t\t\tconst xmlChar *publicId,\n\t\t\t\tconst xmlChar *systemId,\n\t\t\t\tconst xmlChar *notationName);\n/**\n * setDocumentLocatorSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @loc: A SAX Locator\n *\n * Receive the document locator at startup, actually xmlDefaultSAXLocator.\n * Everything is available on the context, so this is useless in our case.\n */\ntypedef void (*setDocumentLocatorSAXFunc) (void *ctx,\n\t\t\t\txmlSAXLocatorPtr loc);\n/**\n * startDocumentSAXFunc:\n * @ctx:  the user data (XML parser context)\n *\n * Called when the document start being processed.\n */\ntypedef void (*startDocumentSAXFunc) (void *ctx);\n/**\n * endDocumentSAXFunc:\n * @ctx:  the user data (XML parser context)\n *\n * Called when the document end has been detected.\n */\ntypedef void (*endDocumentSAXFunc) (void *ctx);\n/**\n * startElementSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @name:  The element name, including namespace prefix\n * @atts:  An array of name/value attributes pairs, NULL terminated\n *\n * Called when an opening tag has been processed.\n */\ntypedef void (*startElementSAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *name,\n\t\t\t\tconst xmlChar **atts);\n/**\n * endElementSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @name:  The element name\n *\n * Called when the end of an element has been detected.\n */\ntypedef void (*endElementSAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *name);\n/**\n * attributeSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @name:  The attribute name, including namespace prefix\n * @value:  The attribute value\n *\n * Handle an attribute that has been read by the parser.\n * The default handling is to convert the attribute into an\n * DOM subtree and past it in a new xmlAttr element added to\n * the element.\n */\ntypedef void (*attributeSAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *name,\n\t\t\t\tconst xmlChar *value);\n/**\n * referenceSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @name:  The entity name\n *\n * Called when an entity reference is detected.\n */\ntypedef void (*referenceSAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *name);\n/**\n * charactersSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @ch:  a xmlChar string\n * @len: the number of xmlChar\n *\n * Receiving some chars from the parser.\n */\ntypedef void (*charactersSAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *ch,\n\t\t\t\tint len);\n/**\n * ignorableWhitespaceSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @ch:  a xmlChar string\n * @len: the number of xmlChar\n *\n * Receiving some ignorable whitespaces from the parser.\n * UNUSED: by default the DOM building will use characters.\n */\ntypedef void (*ignorableWhitespaceSAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *ch,\n\t\t\t\tint len);\n/**\n * processingInstructionSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @target:  the target name\n * @data: the PI data's\n *\n * A processing instruction has been parsed.\n */\ntypedef void (*processingInstructionSAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *target,\n\t\t\t\tconst xmlChar *data);\n/**\n * commentSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @value:  the comment content\n *\n * A comment has been parsed.\n */\ntypedef void (*commentSAXFunc) (void *ctx,\n\t\t\t\tconst xmlChar *value);\n/**\n * cdataBlockSAXFunc:\n * @ctx:  the user data (XML parser context)\n * @value:  The pcdata content\n * @len:  the block length\n *\n * Called when a pcdata block has been parsed.\n */\ntypedef void (*cdataBlockSAXFunc) (\n\t                        void *ctx,\n\t\t\t\tconst xmlChar *value,\n\t\t\t\tint len);\n/**\n * warningSAXFunc:\n * @ctx:  an XML parser context\n * @msg:  the message to display/transmit\n * @...:  extra parameters for the message display\n *\n * Display and format a warning messages, callback.\n */\ntypedef void (XMLCDECL *warningSAXFunc) (void *ctx,\n\t\t\t\tconst char *msg, ...) LIBXML_ATTR_FORMAT(2,3);\n/**\n * errorSAXFunc:\n * @ctx:  an XML parser context\n * @msg:  the message to display/transmit\n * @...:  extra parameters for the message display\n *\n * Display and format an error messages, callback.\n */\ntypedef void (XMLCDECL *errorSAXFunc) (void *ctx,\n\t\t\t\tconst char *msg, ...) LIBXML_ATTR_FORMAT(2,3);\n/**\n * fatalErrorSAXFunc:\n * @ctx:  an XML parser context\n * @msg:  the message to display/transmit\n * @...:  extra parameters for the message display\n *\n * Display and format fatal error messages, callback.\n * Note: so far fatalError() SAX callbacks are not used, error()\n *       get all the callbacks for errors.\n */\ntypedef void (XMLCDECL *fatalErrorSAXFunc) (void *ctx,\n\t\t\t\tconst char *msg, ...) LIBXML_ATTR_FORMAT(2,3);\n/**\n * isStandaloneSAXFunc:\n * @ctx:  the user data (XML parser context)\n *\n * Is this document tagged standalone?\n *\n * Returns 1 if true\n */\ntypedef int (*isStandaloneSAXFunc) (void *ctx);\n/**\n * hasInternalSubsetSAXFunc:\n * @ctx:  the user data (XML parser context)\n *\n * Does this document has an internal subset.\n *\n * Returns 1 if true\n */\ntypedef int (*hasInternalSubsetSAXFunc) (void *ctx);\n\n/**\n * hasExternalSubsetSAXFunc:\n * @ctx:  the user data (XML parser context)\n *\n * Does this document has an external subset?\n *\n * Returns 1 if true\n */\ntypedef int (*hasExternalSubsetSAXFunc) (void *ctx);\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n *\t\t\tThe SAX version 2 API extensions\t\t*\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\n/**\n * XML_SAX2_MAGIC:\n *\n * Special constant found in SAX2 blocks initialized fields\n */\n#define XML_SAX2_MAGIC 0xDEEDBEAF\n\n/**\n * startElementNsSAX2Func:\n * @ctx:  the user data (XML parser context)\n * @localname:  the local name of the element\n * @prefix:  the element namespace prefix if available\n * @URI:  the element namespace name if available\n * @nb_namespaces:  number of namespace definitions on that node\n * @namespaces:  pointer to the array of prefix/URI pairs namespace definitions\n * @nb_attributes:  the number of attributes on that node\n * @nb_defaulted:  the number of defaulted attributes. The defaulted\n *                  ones are at the end of the array\n * @attributes:  pointer to the array of (localname/prefix/URI/value/end)\n *               attribute values.\n *\n * SAX2 callback when an element start has been detected by the parser.\n * It provides the namespace informations for the element, as well as\n * the new namespace declarations on the element.\n */\n\ntypedef void (*startElementNsSAX2Func) (void *ctx,\n\t\t\t\t\tconst xmlChar *localname,\n\t\t\t\t\tconst xmlChar *prefix,\n\t\t\t\t\tconst xmlChar *URI,\n\t\t\t\t\tint nb_namespaces,\n\t\t\t\t\tconst xmlChar **namespaces,\n\t\t\t\t\tint nb_attributes,\n\t\t\t\t\tint nb_defaulted,\n\t\t\t\t\tconst xmlChar **attributes);\n\n/**\n * endElementNsSAX2Func:\n * @ctx:  the user data (XML parser context)\n * @localname:  the local name of the element\n * @prefix:  the element namespace prefix if available\n * @URI:  the element namespace name if available\n *\n * SAX2 callback when an element end has been detected by the parser.\n * It provides the namespace informations for the element.\n */\n\ntypedef void (*endElementNsSAX2Func)   (void *ctx,\n\t\t\t\t\tconst xmlChar *localname,\n\t\t\t\t\tconst xmlChar *prefix,\n\t\t\t\t\tconst xmlChar *URI);\n\n\nstruct _xmlSAXHandler {\n    internalSubsetSAXFunc internalSubset;\n    isStandaloneSAXFunc isStandalone;\n    hasInternalSubsetSAXFunc hasInternalSubset;\n    hasExternalSubsetSAXFunc hasExternalSubset;\n    resolveEntitySAXFunc resolveEntity;\n    getEntitySAXFunc getEntity;\n    entityDeclSAXFunc entityDecl;\n    notationDeclSAXFunc notationDecl;\n    attributeDeclSAXFunc attributeDecl;\n    elementDeclSAXFunc elementDecl;\n    unparsedEntityDeclSAXFunc unparsedEntityDecl;\n    setDocumentLocatorSAXFunc setDocumentLocator;\n    startDocumentSAXFunc startDocument;\n    endDocumentSAXFunc endDocument;\n    startElementSAXFunc startElement;\n    endElementSAXFunc endElement;\n    referenceSAXFunc reference;\n    charactersSAXFunc characters;\n    ignorableWhitespaceSAXFunc ignorableWhitespace;\n    processingInstructionSAXFunc processingInstruction;\n    commentSAXFunc comment;\n    warningSAXFunc warning;\n    errorSAXFunc error;\n    fatalErrorSAXFunc fatalError; /* unused error() get all the errors */\n    getParameterEntitySAXFunc getParameterEntity;\n    cdataBlockSAXFunc cdataBlock;\n    externalSubsetSAXFunc externalSubset;\n    unsigned int initialized;\n    /* The following fields are extensions available only on version 2 */\n    void *_private;\n    startElementNsSAX2Func startElementNs;\n    endElementNsSAX2Func endElementNs;\n    xmlStructuredErrorFunc serror;\n};\n\n/*\n * SAX Version 1\n */\ntypedef struct _xmlSAXHandlerV1 xmlSAXHandlerV1;\ntypedef xmlSAXHandlerV1 *xmlSAXHandlerV1Ptr;\nstruct _xmlSAXHandlerV1 {\n    internalSubsetSAXFunc internalSubset;\n    isStandaloneSAXFunc isStandalone;\n    hasInternalSubsetSAXFunc hasInternalSubset;\n    hasExternalSubsetSAXFunc hasExternalSubset;\n    resolveEntitySAXFunc resolveEntity;\n    getEntitySAXFunc getEntity;\n    entityDeclSAXFunc entityDecl;\n    notationDeclSAXFunc notationDecl;\n    attributeDeclSAXFunc attributeDecl;\n    elementDeclSAXFunc elementDecl;\n    unparsedEntityDeclSAXFunc unparsedEntityDecl;\n    setDocumentLocatorSAXFunc setDocumentLocator;\n    startDocumentSAXFunc startDocument;\n    endDocumentSAXFunc endDocument;\n    startElementSAXFunc startElement;\n    endElementSAXFunc endElement;\n    referenceSAXFunc reference;\n    charactersSAXFunc characters;\n    ignorableWhitespaceSAXFunc ignorableWhitespace;\n    processingInstructionSAXFunc processingInstruction;\n    commentSAXFunc comment;\n    warningSAXFunc warning;\n    errorSAXFunc error;\n    fatalErrorSAXFunc fatalError; /* unused error() get all the errors */\n    getParameterEntitySAXFunc getParameterEntity;\n    cdataBlockSAXFunc cdataBlock;\n    externalSubsetSAXFunc externalSubset;\n    unsigned int initialized;\n};\n\n\n/**\n * xmlExternalEntityLoader:\n * @URL: The System ID of the resource requested\n * @ID: The Public ID of the resource requested\n * @context: the XML parser context\n *\n * External entity loaders types.\n *\n * Returns the entity input parser.\n */\ntypedef xmlParserInputPtr (*xmlExternalEntityLoader) (const char *URL,\n\t\t\t\t\t const char *ID,\n\t\t\t\t\t xmlParserCtxtPtr context);\n\n#ifdef __cplusplus\n}\n#endif\n\n#include <libxml/encoding.h>\n#include <libxml/xmlIO.h>\n#include <libxml/globals.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n\n/*\n * Init/Cleanup\n */\nXMLPUBFUN void XMLCALL\n\t\txmlInitParser\t\t(void);\nXMLPUBFUN void XMLCALL\n\t\txmlCleanupParser\t(void);\n\n/*\n * Input functions\n */\nXMLPUBFUN int XMLCALL\n\t\txmlParserInputRead\t(xmlParserInputPtr in,\n\t\t\t\t\t int len);\nXMLPUBFUN int XMLCALL\n\t\txmlParserInputGrow\t(xmlParserInputPtr in,\n\t\t\t\t\t int len);\n\n/*\n * Basic parsing Interfaces\n */\n#ifdef LIBXML_SAX1_ENABLED\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlParseDoc\t\t(const xmlChar *cur);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlParseFile\t\t(const char *filename);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlParseMemory\t\t(const char *buffer,\n\t\t\t\t\t int size);\n#endif /* LIBXML_SAX1_ENABLED */\nXMLPUBFUN int XMLCALL\n\t\txmlSubstituteEntitiesDefault(int val);\nXMLPUBFUN int XMLCALL\n\t\txmlKeepBlanksDefault\t(int val);\nXMLPUBFUN void XMLCALL\n\t\txmlStopParser\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\txmlPedanticParserDefault(int val);\nXMLPUBFUN int XMLCALL\n\t\txmlLineNumbersDefault\t(int val);\n\n#ifdef LIBXML_SAX1_ENABLED\n/*\n * Recovery mode\n */\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlRecoverDoc\t\t(const xmlChar *cur);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlRecoverMemory\t(const char *buffer,\n\t\t\t\t\t int size);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlRecoverFile\t\t(const char *filename);\n#endif /* LIBXML_SAX1_ENABLED */\n\n/*\n * Less common routines and SAX interfaces\n */\nXMLPUBFUN int XMLCALL\n\t\txmlParseDocument\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\txmlParseExtParsedEnt\t(xmlParserCtxtPtr ctxt);\n#ifdef LIBXML_SAX1_ENABLED\nXMLPUBFUN int XMLCALL\n\t\txmlSAXUserParseFile\t(xmlSAXHandlerPtr sax,\n\t\t\t\t\t void *user_data,\n\t\t\t\t\t const char *filename);\nXMLPUBFUN int XMLCALL\n\t\txmlSAXUserParseMemory\t(xmlSAXHandlerPtr sax,\n\t\t\t\t\t void *user_data,\n\t\t\t\t\t const char *buffer,\n\t\t\t\t\t int size);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlSAXParseDoc\t\t(xmlSAXHandlerPtr sax,\n\t\t\t\t\t const xmlChar *cur,\n\t\t\t\t\t int recovery);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlSAXParseMemory\t(xmlSAXHandlerPtr sax,\n\t\t\t\t\t const char *buffer,\n\t\t\t\t\t int size,\n\t\t\t\t\t int recovery);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlSAXParseMemoryWithData (xmlSAXHandlerPtr sax,\n\t\t\t\t\t const char *buffer,\n\t\t\t\t\t int size,\n\t\t\t\t\t int recovery,\n\t\t\t\t\t void *data);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlSAXParseFile\t\t(xmlSAXHandlerPtr sax,\n\t\t\t\t\t const char *filename,\n\t\t\t\t\t int recovery);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlSAXParseFileWithData\t(xmlSAXHandlerPtr sax,\n\t\t\t\t\t const char *filename,\n\t\t\t\t\t int recovery,\n\t\t\t\t\t void *data);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlSAXParseEntity\t(xmlSAXHandlerPtr sax,\n\t\t\t\t\t const char *filename);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlParseEntity\t\t(const char *filename);\n#endif /* LIBXML_SAX1_ENABLED */\n\n#ifdef LIBXML_VALID_ENABLED\nXMLPUBFUN xmlDtdPtr XMLCALL\n\t\txmlSAXParseDTD\t\t(xmlSAXHandlerPtr sax,\n\t\t\t\t\t const xmlChar *ExternalID,\n\t\t\t\t\t const xmlChar *SystemID);\nXMLPUBFUN xmlDtdPtr XMLCALL\n\t\txmlParseDTD\t\t(const xmlChar *ExternalID,\n\t\t\t\t\t const xmlChar *SystemID);\nXMLPUBFUN xmlDtdPtr XMLCALL\n\t\txmlIOParseDTD\t\t(xmlSAXHandlerPtr sax,\n\t\t\t\t\t xmlParserInputBufferPtr input,\n\t\t\t\t\t xmlCharEncoding enc);\n#endif /* LIBXML_VALID_ENABLE */\n#ifdef LIBXML_SAX1_ENABLED\nXMLPUBFUN int XMLCALL\n\t\txmlParseBalancedChunkMemory(xmlDocPtr doc,\n\t\t\t\t\t xmlSAXHandlerPtr sax,\n\t\t\t\t\t void *user_data,\n\t\t\t\t\t int depth,\n\t\t\t\t\t const xmlChar *string,\n\t\t\t\t\t xmlNodePtr *lst);\n#endif /* LIBXML_SAX1_ENABLED */\nXMLPUBFUN xmlParserErrors XMLCALL\n\t\txmlParseInNodeContext\t(xmlNodePtr node,\n\t\t\t\t\t const char *data,\n\t\t\t\t\t int datalen,\n\t\t\t\t\t int options,\n\t\t\t\t\t xmlNodePtr *lst);\n#ifdef LIBXML_SAX1_ENABLED\nXMLPUBFUN int XMLCALL\n\t\txmlParseBalancedChunkMemoryRecover(xmlDocPtr doc,\n                     xmlSAXHandlerPtr sax,\n                     void *user_data,\n                     int depth,\n                     const xmlChar *string,\n                     xmlNodePtr *lst,\n                     int recover);\nXMLPUBFUN int XMLCALL\n\t\txmlParseExternalEntity\t(xmlDocPtr doc,\n\t\t\t\t\t xmlSAXHandlerPtr sax,\n\t\t\t\t\t void *user_data,\n\t\t\t\t\t int depth,\n\t\t\t\t\t const xmlChar *URL,\n\t\t\t\t\t const xmlChar *ID,\n\t\t\t\t\t xmlNodePtr *lst);\n#endif /* LIBXML_SAX1_ENABLED */\nXMLPUBFUN int XMLCALL\n\t\txmlParseCtxtExternalEntity(xmlParserCtxtPtr ctx,\n\t\t\t\t\t const xmlChar *URL,\n\t\t\t\t\t const xmlChar *ID,\n\t\t\t\t\t xmlNodePtr *lst);\n\n/*\n * Parser contexts handling.\n */\nXMLPUBFUN xmlParserCtxtPtr XMLCALL\n\t\txmlNewParserCtxt\t(void);\nXMLPUBFUN int XMLCALL\n\t\txmlInitParserCtxt\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\txmlClearParserCtxt\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeParserCtxt\t(xmlParserCtxtPtr ctxt);\n#ifdef LIBXML_SAX1_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlSetupParserForBuffer\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t const xmlChar* buffer,\n\t\t\t\t\t const char *filename);\n#endif /* LIBXML_SAX1_ENABLED */\nXMLPUBFUN xmlParserCtxtPtr XMLCALL\n\t\txmlCreateDocParserCtxt\t(const xmlChar *cur);\n\n#ifdef LIBXML_LEGACY_ENABLED\n/*\n * Reading/setting optional parsing features.\n */\nXMLPUBFUN int XMLCALL\n\t\txmlGetFeaturesList\t(int *len,\n\t\t\t\t\t const char **result);\nXMLPUBFUN int XMLCALL\n\t\txmlGetFeature\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t const char *name,\n\t\t\t\t\t void *result);\nXMLPUBFUN int XMLCALL\n\t\txmlSetFeature\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t const char *name,\n\t\t\t\t\t void *value);\n#endif /* LIBXML_LEGACY_ENABLED */\n\n#ifdef LIBXML_PUSH_ENABLED\n/*\n * Interfaces for the Push mode.\n */\nXMLPUBFUN xmlParserCtxtPtr XMLCALL\n\t\txmlCreatePushParserCtxt(xmlSAXHandlerPtr sax,\n\t\t\t\t\t void *user_data,\n\t\t\t\t\t const char *chunk,\n\t\t\t\t\t int size,\n\t\t\t\t\t const char *filename);\nXMLPUBFUN int XMLCALL\n\t\txmlParseChunk\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t const char *chunk,\n\t\t\t\t\t int size,\n\t\t\t\t\t int terminate);\n#endif /* LIBXML_PUSH_ENABLED */\n\n/*\n * Special I/O mode.\n */\n\nXMLPUBFUN xmlParserCtxtPtr XMLCALL\n\t\txmlCreateIOParserCtxt\t(xmlSAXHandlerPtr sax,\n\t\t\t\t\t void *user_data,\n\t\t\t\t\t xmlInputReadCallback   ioread,\n\t\t\t\t\t xmlInputCloseCallback  ioclose,\n\t\t\t\t\t void *ioctx,\n\t\t\t\t\t xmlCharEncoding enc);\n\nXMLPUBFUN xmlParserInputPtr XMLCALL\n\t\txmlNewIOInputStream\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t xmlParserInputBufferPtr input,\n\t\t\t\t\t xmlCharEncoding enc);\n\n/*\n * Node infos.\n */\nXMLPUBFUN const xmlParserNodeInfo* XMLCALL\n\t\txmlParserFindNodeInfo\t(const xmlParserCtxtPtr ctxt,\n\t\t\t\t         const xmlNodePtr node);\nXMLPUBFUN void XMLCALL\n\t\txmlInitNodeInfoSeq\t(xmlParserNodeInfoSeqPtr seq);\nXMLPUBFUN void XMLCALL\n\t\txmlClearNodeInfoSeq\t(xmlParserNodeInfoSeqPtr seq);\nXMLPUBFUN unsigned long XMLCALL\n\t\txmlParserFindNodeInfoIndex(const xmlParserNodeInfoSeqPtr seq,\n                                         const xmlNodePtr node);\nXMLPUBFUN void XMLCALL\n\t\txmlParserAddNodeInfo\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t const xmlParserNodeInfoPtr info);\n\n/*\n * External entities handling actually implemented in xmlIO.\n */\n\nXMLPUBFUN void XMLCALL\n\t\txmlSetExternalEntityLoader(xmlExternalEntityLoader f);\nXMLPUBFUN xmlExternalEntityLoader XMLCALL\n\t\txmlGetExternalEntityLoader(void);\nXMLPUBFUN xmlParserInputPtr XMLCALL\n\t\txmlLoadExternalEntity\t(const char *URL,\n\t\t\t\t\t const char *ID,\n\t\t\t\t\t xmlParserCtxtPtr ctxt);\n\n/*\n * Index lookup, actually implemented in the encoding module\n */\nXMLPUBFUN long XMLCALL\n\t\txmlByteConsumed\t\t(xmlParserCtxtPtr ctxt);\n\n/*\n * New set of simpler/more flexible APIs\n */\n/**\n * xmlParserOption:\n *\n * This is the set of XML parser options that can be passed down\n * to the xmlReadDoc() and similar calls.\n */\ntypedef enum {\n    XML_PARSE_RECOVER\t= 1<<0,\t/* recover on errors */\n    XML_PARSE_NOENT\t= 1<<1,\t/* substitute entities */\n    XML_PARSE_DTDLOAD\t= 1<<2,\t/* load the external subset */\n    XML_PARSE_DTDATTR\t= 1<<3,\t/* default DTD attributes */\n    XML_PARSE_DTDVALID\t= 1<<4,\t/* validate with the DTD */\n    XML_PARSE_NOERROR\t= 1<<5,\t/* suppress error reports */\n    XML_PARSE_NOWARNING\t= 1<<6,\t/* suppress warning reports */\n    XML_PARSE_PEDANTIC\t= 1<<7,\t/* pedantic error reporting */\n    XML_PARSE_NOBLANKS\t= 1<<8,\t/* remove blank nodes */\n    XML_PARSE_SAX1\t= 1<<9,\t/* use the SAX1 interface internally */\n    XML_PARSE_XINCLUDE\t= 1<<10,/* Implement XInclude substitition  */\n    XML_PARSE_NONET\t= 1<<11,/* Forbid network access */\n    XML_PARSE_NODICT\t= 1<<12,/* Do not reuse the context dictionary */\n    XML_PARSE_NSCLEAN\t= 1<<13,/* remove redundant namespaces declarations */\n    XML_PARSE_NOCDATA\t= 1<<14,/* merge CDATA as text nodes */\n    XML_PARSE_NOXINCNODE= 1<<15,/* do not generate XINCLUDE START/END nodes */\n    XML_PARSE_COMPACT   = 1<<16,/* compact small text nodes; no modification of\n                                   the tree allowed afterwards (will possibly\n\t\t\t\t   crash if you try to modify the tree) */\n    XML_PARSE_OLD10\t= 1<<17,/* parse using XML-1.0 before update 5 */\n    XML_PARSE_NOBASEFIX = 1<<18,/* do not fixup XINCLUDE xml:base uris */\n    XML_PARSE_HUGE      = 1<<19,/* relax any hardcoded limit from the parser */\n    XML_PARSE_OLDSAX    = 1<<20,/* parse using SAX2 interface before 2.7.0 */\n    XML_PARSE_IGNORE_ENC= 1<<21,/* ignore internal document encoding hint */\n    XML_PARSE_BIG_LINES = 1<<22 /* Store big lines numbers in text PSVI field */\n} xmlParserOption;\n\nXMLPUBFUN void XMLCALL\n\t\txmlCtxtReset\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\txmlCtxtResetPush\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t const char *chunk,\n\t\t\t\t\t int size,\n\t\t\t\t\t const char *filename,\n\t\t\t\t\t const char *encoding);\nXMLPUBFUN int XMLCALL\n\t\txmlCtxtUseOptions\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlReadDoc\t\t(const xmlChar *cur,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlReadFile\t\t(const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlReadMemory\t\t(const char *buffer,\n\t\t\t\t\t int size,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlReadFd\t\t(int fd,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlReadIO\t\t(xmlInputReadCallback ioread,\n\t\t\t\t\t xmlInputCloseCallback ioclose,\n\t\t\t\t\t void *ioctx,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlCtxtReadDoc\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t const xmlChar *cur,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlCtxtReadFile\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t const char *filename,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlCtxtReadMemory\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t const char *buffer,\n\t\t\t\t\t int size,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlCtxtReadFd\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t int fd,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlCtxtReadIO\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t xmlInputReadCallback ioread,\n\t\t\t\t\t xmlInputCloseCallback ioclose,\n\t\t\t\t\t void *ioctx,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\n\n/*\n * Library wide options\n */\n/**\n * xmlFeature:\n *\n * Used to examine the existance of features that can be enabled\n * or disabled at compile-time.\n * They used to be called XML_FEATURE_xxx but this clashed with Expat\n */\ntypedef enum {\n    XML_WITH_THREAD = 1,\n    XML_WITH_TREE = 2,\n    XML_WITH_OUTPUT = 3,\n    XML_WITH_PUSH = 4,\n    XML_WITH_READER = 5,\n    XML_WITH_PATTERN = 6,\n    XML_WITH_WRITER = 7,\n    XML_WITH_SAX1 = 8,\n    XML_WITH_FTP = 9,\n    XML_WITH_HTTP = 10,\n    XML_WITH_VALID = 11,\n    XML_WITH_HTML = 12,\n    XML_WITH_LEGACY = 13,\n    XML_WITH_C14N = 14,\n    XML_WITH_CATALOG = 15,\n    XML_WITH_XPATH = 16,\n    XML_WITH_XPTR = 17,\n    XML_WITH_XINCLUDE = 18,\n    XML_WITH_ICONV = 19,\n    XML_WITH_ISO8859X = 20,\n    XML_WITH_UNICODE = 21,\n    XML_WITH_REGEXP = 22,\n    XML_WITH_AUTOMATA = 23,\n    XML_WITH_EXPR = 24,\n    XML_WITH_SCHEMAS = 25,\n    XML_WITH_SCHEMATRON = 26,\n    XML_WITH_MODULES = 27,\n    XML_WITH_DEBUG = 28,\n    XML_WITH_DEBUG_MEM = 29,\n    XML_WITH_DEBUG_RUN = 30,\n    XML_WITH_ZLIB = 31,\n    XML_WITH_ICU = 32,\n    XML_WITH_LZMA = 33,\n    XML_WITH_NONE = 99999 /* just to be sure of allocation size */\n} xmlFeature;\n\nXMLPUBFUN int XMLCALL\n\t\txmlHasFeature\t\t(xmlFeature feature);\n\n#ifdef __cplusplus\n}\n#endif\n#endif /* __XML_PARSER_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/parserInternals.h",
    "content": "/*\n * Summary: internals routines and limits exported by the parser.\n * Description: this module exports a number of internal parsing routines\n *              they are not really all intended for applications but\n *              can prove useful doing low level processing.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_PARSER_INTERNALS_H__\n#define __XML_PARSER_INTERNALS_H__\n\n#include <libxml/xmlversion.h>\n#include <libxml/parser.h>\n#include <libxml/HTMLparser.h>\n#include <libxml/chvalid.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * xmlParserMaxDepth:\n *\n * arbitrary depth limit for the XML documents that we allow to\n * process. This is not a limitation of the parser but a safety\n * boundary feature, use XML_PARSE_HUGE option to override it.\n */\nXMLPUBVAR unsigned int xmlParserMaxDepth;\n\n/**\n * XML_MAX_TEXT_LENGTH:\n *\n * Maximum size allowed for a single text node when building a tree.\n * This is not a limitation of the parser but a safety boundary feature,\n * use XML_PARSE_HUGE option to override it.\n * Introduced in 2.9.0\n */\n#define XML_MAX_TEXT_LENGTH 10000000\n\n/**\n * XML_MAX_NAME_LENGTH:\n *\n * Maximum size allowed for a markup identitier\n * This is not a limitation of the parser but a safety boundary feature,\n * use XML_PARSE_HUGE option to override it.\n * Note that with the use of parsing dictionaries overriding the limit\n * may result in more runtime memory usage in face of \"unfriendly' content\n * Introduced in 2.9.0\n */\n#define XML_MAX_NAME_LENGTH 50000\n\n/**\n * XML_MAX_DICTIONARY_LIMIT:\n *\n * Maximum size allowed by the parser for a dictionary by default\n * This is not a limitation of the parser but a safety boundary feature,\n * use XML_PARSE_HUGE option to override it.\n * Introduced in 2.9.0\n */\n#define XML_MAX_DICTIONARY_LIMIT 10000000\n\n/**\n * XML_MAX_LOOKUP_LIMIT:\n *\n * Maximum size allowed by the parser for ahead lookup\n * This is an upper boundary enforced by the parser to avoid bad\n * behaviour on \"unfriendly' content\n * Introduced in 2.9.0\n */\n#define XML_MAX_LOOKUP_LIMIT 10000000\n\n/**\n * XML_MAX_NAMELEN:\n *\n * Identifiers can be longer, but this will be more costly\n * at runtime.\n */\n#define XML_MAX_NAMELEN 100\n\n/**\n * INPUT_CHUNK:\n *\n * The parser tries to always have that amount of input ready.\n * One of the point is providing context when reporting errors.\n */\n#define INPUT_CHUNK\t250\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n * UNICODE version of the macros.\t\t\t\t\t*\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\n/**\n * IS_BYTE_CHAR:\n * @c:  an byte value (int)\n *\n * Macro to check the following production in the XML spec:\n *\n * [2] Char ::= #x9 | #xA | #xD | [#x20...]\n * any byte character in the accepted range\n */\n#define IS_BYTE_CHAR(c)\t xmlIsChar_ch(c)\n\n/**\n * IS_CHAR:\n * @c:  an UNICODE value (int)\n *\n * Macro to check the following production in the XML spec:\n *\n * [2] Char ::= #x9 | #xA | #xD | [#x20-#xD7FF] | [#xE000-#xFFFD]\n *                  | [#x10000-#x10FFFF]\n * any Unicode character, excluding the surrogate blocks, FFFE, and FFFF.\n */\n#define IS_CHAR(c)   xmlIsCharQ(c)\n\n/**\n * IS_CHAR_CH:\n * @c: an xmlChar (usually an unsigned char)\n *\n * Behaves like IS_CHAR on single-byte value\n */\n#define IS_CHAR_CH(c)  xmlIsChar_ch(c)\n\n/**\n * IS_BLANK:\n * @c:  an UNICODE value (int)\n *\n * Macro to check the following production in the XML spec:\n *\n * [3] S ::= (#x20 | #x9 | #xD | #xA)+\n */\n#define IS_BLANK(c)  xmlIsBlankQ(c)\n\n/**\n * IS_BLANK_CH:\n * @c:  an xmlChar value (normally unsigned char)\n *\n * Behaviour same as IS_BLANK\n */\n#define IS_BLANK_CH(c)  xmlIsBlank_ch(c)\n\n/**\n * IS_BASECHAR:\n * @c:  an UNICODE value (int)\n *\n * Macro to check the following production in the XML spec:\n *\n * [85] BaseChar ::= ... long list see REC ...\n */\n#define IS_BASECHAR(c) xmlIsBaseCharQ(c)\n\n/**\n * IS_DIGIT:\n * @c:  an UNICODE value (int)\n *\n * Macro to check the following production in the XML spec:\n *\n * [88] Digit ::= ... long list see REC ...\n */\n#define IS_DIGIT(c) xmlIsDigitQ(c)\n\n/**\n * IS_DIGIT_CH:\n * @c:  an xmlChar value (usually an unsigned char)\n *\n * Behaves like IS_DIGIT but with a single byte argument\n */\n#define IS_DIGIT_CH(c)  xmlIsDigit_ch(c)\n\n/**\n * IS_COMBINING:\n * @c:  an UNICODE value (int)\n *\n * Macro to check the following production in the XML spec:\n *\n * [87] CombiningChar ::= ... long list see REC ...\n */\n#define IS_COMBINING(c) xmlIsCombiningQ(c)\n\n/**\n * IS_COMBINING_CH:\n * @c:  an xmlChar (usually an unsigned char)\n *\n * Always false (all combining chars > 0xff)\n */\n#define IS_COMBINING_CH(c) 0\n\n/**\n * IS_EXTENDER:\n * @c:  an UNICODE value (int)\n *\n * Macro to check the following production in the XML spec:\n *\n *\n * [89] Extender ::= #x00B7 | #x02D0 | #x02D1 | #x0387 | #x0640 |\n *                   #x0E46 | #x0EC6 | #x3005 | [#x3031-#x3035] |\n *                   [#x309D-#x309E] | [#x30FC-#x30FE]\n */\n#define IS_EXTENDER(c) xmlIsExtenderQ(c)\n\n/**\n * IS_EXTENDER_CH:\n * @c:  an xmlChar value (usually an unsigned char)\n *\n * Behaves like IS_EXTENDER but with a single-byte argument\n */\n#define IS_EXTENDER_CH(c)  xmlIsExtender_ch(c)\n\n/**\n * IS_IDEOGRAPHIC:\n * @c:  an UNICODE value (int)\n *\n * Macro to check the following production in the XML spec:\n *\n *\n * [86] Ideographic ::= [#x4E00-#x9FA5] | #x3007 | [#x3021-#x3029]\n */\n#define IS_IDEOGRAPHIC(c) xmlIsIdeographicQ(c)\n\n/**\n * IS_LETTER:\n * @c:  an UNICODE value (int)\n *\n * Macro to check the following production in the XML spec:\n *\n *\n * [84] Letter ::= BaseChar | Ideographic\n */\n#define IS_LETTER(c) (IS_BASECHAR(c) || IS_IDEOGRAPHIC(c))\n\n/**\n * IS_LETTER_CH:\n * @c:  an xmlChar value (normally unsigned char)\n *\n * Macro behaves like IS_LETTER, but only check base chars\n *\n */\n#define IS_LETTER_CH(c) xmlIsBaseChar_ch(c)\n\n/**\n * IS_ASCII_LETTER:\n * @c: an xmlChar value\n *\n * Macro to check [a-zA-Z]\n *\n */\n#define IS_ASCII_LETTER(c)\t(((0x41 <= (c)) && ((c) <= 0x5a)) || \\\n\t\t\t\t ((0x61 <= (c)) && ((c) <= 0x7a)))\n\n/**\n * IS_ASCII_DIGIT:\n * @c: an xmlChar value\n *\n * Macro to check [0-9]\n *\n */\n#define IS_ASCII_DIGIT(c)\t((0x30 <= (c)) && ((c) <= 0x39))\n\n/**\n * IS_PUBIDCHAR:\n * @c:  an UNICODE value (int)\n *\n * Macro to check the following production in the XML spec:\n *\n *\n * [13] PubidChar ::= #x20 | #xD | #xA | [a-zA-Z0-9] | [-'()+,./:=?;!*#@$_%]\n */\n#define IS_PUBIDCHAR(c)\txmlIsPubidCharQ(c)\n\n/**\n * IS_PUBIDCHAR_CH:\n * @c:  an xmlChar value (normally unsigned char)\n *\n * Same as IS_PUBIDCHAR but for single-byte value\n */\n#define IS_PUBIDCHAR_CH(c) xmlIsPubidChar_ch(c)\n\n/**\n * SKIP_EOL:\n * @p:  and UTF8 string pointer\n *\n * Skips the end of line chars.\n */\n#define SKIP_EOL(p)\t\t\t\t\t\t\t\\\n    if (*(p) == 0x13) { p++ ; if (*(p) == 0x10) p++; }\t\t\t\\\n    if (*(p) == 0x10) { p++ ; if (*(p) == 0x13) p++; }\n\n/**\n * MOVETO_ENDTAG:\n * @p:  and UTF8 string pointer\n *\n * Skips to the next '>' char.\n */\n#define MOVETO_ENDTAG(p)\t\t\t\t\t\t\\\n    while ((*p) && (*(p) != '>')) (p)++\n\n/**\n * MOVETO_STARTTAG:\n * @p:  and UTF8 string pointer\n *\n * Skips to the next '<' char.\n */\n#define MOVETO_STARTTAG(p)\t\t\t\t\t\t\\\n    while ((*p) && (*(p) != '<')) (p)++\n\n/**\n * Global variables used for predefined strings.\n */\nXMLPUBVAR const xmlChar xmlStringText[];\nXMLPUBVAR const xmlChar xmlStringTextNoenc[];\nXMLPUBVAR const xmlChar xmlStringComment[];\n\n/*\n * Function to finish the work of the macros where needed.\n */\nXMLPUBFUN int XMLCALL                   xmlIsLetter     (int c);\n\n/**\n * Parser context.\n */\nXMLPUBFUN xmlParserCtxtPtr XMLCALL\n\t\t\txmlCreateFileParserCtxt\t(const char *filename);\nXMLPUBFUN xmlParserCtxtPtr XMLCALL\n\t\t\txmlCreateURLParserCtxt\t(const char *filename,\n\t\t\t\t\t\t int options);\nXMLPUBFUN xmlParserCtxtPtr XMLCALL\n\t\t\txmlCreateMemoryParserCtxt(const char *buffer,\n\t\t\t\t\t\t int size);\nXMLPUBFUN xmlParserCtxtPtr XMLCALL\n\t\t\txmlCreateEntityParserCtxt(const xmlChar *URL,\n\t\t\t\t\t\t const xmlChar *ID,\n\t\t\t\t\t\t const xmlChar *base);\nXMLPUBFUN int XMLCALL\n\t\t\txmlSwitchEncoding\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlCharEncoding enc);\nXMLPUBFUN int XMLCALL\n\t\t\txmlSwitchToEncoding\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t xmlCharEncodingHandlerPtr handler);\nXMLPUBFUN int XMLCALL\n\t\t\txmlSwitchInputEncoding\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlParserInputPtr input,\n\t\t\t\t\t xmlCharEncodingHandlerPtr handler);\n\n#ifdef IN_LIBXML\n/* internal error reporting */\nXMLPUBFUN void XMLCALL\n\t\t\t__xmlErrEncoding\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlParserErrors xmlerr,\n\t\t\t\t\t\t const char *msg,\n\t\t\t\t\t\t const xmlChar * str1,\n\t\t\t\t\t\t const xmlChar * str2) LIBXML_ATTR_FORMAT(3,0);\n#endif\n\n/**\n * Input Streams.\n */\nXMLPUBFUN xmlParserInputPtr XMLCALL\n\t\t\txmlNewStringInputStream\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t const xmlChar *buffer);\nXMLPUBFUN xmlParserInputPtr XMLCALL\n\t\t\txmlNewEntityInputStream\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlEntityPtr entity);\nXMLPUBFUN int XMLCALL\n\t\t\txmlPushInput\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlParserInputPtr input);\nXMLPUBFUN xmlChar XMLCALL\n\t\t\txmlPopInput\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlFreeInputStream\t(xmlParserInputPtr input);\nXMLPUBFUN xmlParserInputPtr XMLCALL\n\t\t\txmlNewInputFromFile\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t const char *filename);\nXMLPUBFUN xmlParserInputPtr XMLCALL\n\t\t\txmlNewInputStream\t(xmlParserCtxtPtr ctxt);\n\n/**\n * Namespaces.\n */\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlSplitQName\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t xmlChar **prefix);\n\n/**\n * Generic production rules.\n */\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t\txmlParseName\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlParseNmtoken\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlParseEntityValue\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlChar **orig);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlParseAttValue\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlParseSystemLiteral\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlParsePubidLiteral\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseCharData\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t int cdata);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlParseExternalID\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlChar **publicID,\n\t\t\t\t\t\t int strict);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseComment\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t\txmlParsePITarget\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParsePI\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseNotationDecl\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseEntityDecl\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\t\txmlParseDefaultDecl\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlChar **value);\nXMLPUBFUN xmlEnumerationPtr XMLCALL\n\t\t\txmlParseNotationType\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlEnumerationPtr XMLCALL\n\t\t\txmlParseEnumerationType\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\t\txmlParseEnumeratedType\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlEnumerationPtr *tree);\nXMLPUBFUN int XMLCALL\n\t\t\txmlParseAttributeType\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlEnumerationPtr *tree);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseAttributeListDecl(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlElementContentPtr XMLCALL\n\t\t\txmlParseElementMixedContentDecl\n\t\t\t\t\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t int inputchk);\nXMLPUBFUN xmlElementContentPtr XMLCALL\n\t\t\txmlParseElementChildrenContentDecl\n\t\t\t\t\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t int inputchk);\nXMLPUBFUN int XMLCALL\n\t\t\txmlParseElementContentDecl(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t xmlElementContentPtr *result);\nXMLPUBFUN int XMLCALL\n\t\t\txmlParseElementDecl\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseMarkupDecl\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\t\txmlParseCharRef\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlEntityPtr XMLCALL\n\t\t\txmlParseEntityRef\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseReference\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParsePEReference\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseDocTypeDecl\t(xmlParserCtxtPtr ctxt);\n#ifdef LIBXML_SAX1_ENABLED\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t\txmlParseAttribute\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlChar **value);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t\txmlParseStartTag\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseEndTag\t\t(xmlParserCtxtPtr ctxt);\n#endif /* LIBXML_SAX1_ENABLED */\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseCDSect\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseContent\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseElement\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlParseVersionNum\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlParseVersionInfo\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlParseEncName\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t\txmlParseEncodingDecl\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\t\txmlParseSDDecl\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseXMLDecl\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseTextDecl\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseMisc\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t\txmlParseExternalSubset\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t const xmlChar *ExternalID,\n\t\t\t\t\t\t const xmlChar *SystemID);\n/**\n * XML_SUBSTITUTE_NONE:\n *\n * If no entities need to be substituted.\n */\n#define XML_SUBSTITUTE_NONE\t0\n/**\n * XML_SUBSTITUTE_REF:\n *\n * Whether general entities need to be substituted.\n */\n#define XML_SUBSTITUTE_REF\t1\n/**\n * XML_SUBSTITUTE_PEREF:\n *\n * Whether parameter entities need to be substituted.\n */\n#define XML_SUBSTITUTE_PEREF\t2\n/**\n * XML_SUBSTITUTE_BOTH:\n *\n * Both general and parameter entities need to be substituted.\n */\n#define XML_SUBSTITUTE_BOTH\t3\n\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlStringDecodeEntities\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t const xmlChar *str,\n\t\t\t\t\t\t int what,\n\t\t\t\t\t\t xmlChar end,\n\t\t\t\t\t\t xmlChar  end2,\n\t\t\t\t\t\t xmlChar end3);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlStringLenDecodeEntities\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t const xmlChar *str,\n\t\t\t\t\t\t int len,\n\t\t\t\t\t\t int what,\n\t\t\t\t\t\t xmlChar end,\n\t\t\t\t\t\t xmlChar  end2,\n\t\t\t\t\t\t xmlChar end3);\n\n/*\n * Generated by MACROS on top of parser.c c.f. PUSH_AND_POP.\n */\nXMLPUBFUN int XMLCALL\t\t\tnodePush\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr value);\nXMLPUBFUN xmlNodePtr XMLCALL\t\tnodePop\t\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\t\t\tinputPush\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlParserInputPtr value);\nXMLPUBFUN xmlParserInputPtr XMLCALL\tinputPop\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN const xmlChar * XMLCALL\tnamePop\t\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\t\t\tnamePush\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t const xmlChar *value);\n\n/*\n * other commodities shared between parser.c and parserInternals.\n */\nXMLPUBFUN int XMLCALL\t\t\txmlSkipBlankChars\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\t\t\txmlStringCurrentChar\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t const xmlChar *cur,\n\t\t\t\t\t\t int *len);\nXMLPUBFUN void XMLCALL\t\t\txmlParserHandlePEReference(xmlParserCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\t\t\txmlCheckLanguageID\t(const xmlChar *lang);\n\n/*\n * Really core function shared with HTML parser.\n */\nXMLPUBFUN int XMLCALL\t\t\txmlCurrentChar\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t int *len);\nXMLPUBFUN int XMLCALL\t\txmlCopyCharMultiByte\t(xmlChar *out,\n\t\t\t\t\t\t int val);\nXMLPUBFUN int XMLCALL\t\t\txmlCopyChar\t\t(int len,\n\t\t\t\t\t\t xmlChar *out,\n\t\t\t\t\t\t int val);\nXMLPUBFUN void XMLCALL\t\t\txmlNextChar\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\t\t\txmlParserInputShrink\t(xmlParserInputPtr in);\n\n#ifdef LIBXML_HTML_ENABLED\n/*\n * Actually comes from the HTML parser but launched from the init stuff.\n */\nXMLPUBFUN void XMLCALL\t\t\thtmlInitAutoClose\t(void);\nXMLPUBFUN htmlParserCtxtPtr XMLCALL\thtmlCreateFileParserCtxt(const char *filename,\n\t                                         const char *encoding);\n#endif\n\n/*\n * Specific function to keep track of entities references\n * and used by the XSLT debugger.\n */\n#ifdef LIBXML_LEGACY_ENABLED\n/**\n * xmlEntityReferenceFunc:\n * @ent: the entity\n * @firstNode:  the fist node in the chunk\n * @lastNode:  the last nod in the chunk\n *\n * Callback function used when one needs to be able to track back the\n * provenance of a chunk of nodes inherited from an entity replacement.\n */\ntypedef\tvoid\t(*xmlEntityReferenceFunc)\t(xmlEntityPtr ent,\n\t\t\t\t\t\t xmlNodePtr firstNode,\n\t\t\t\t\t\t xmlNodePtr lastNode);\n\nXMLPUBFUN void XMLCALL\t\txmlSetEntityReferenceFunc\t(xmlEntityReferenceFunc func);\n\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlParseQuotedString\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n                        xmlParseNamespace       (xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlNamespaceParseNSDef\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlScanName\t\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlNamespaceParseNCName\t(xmlParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\txmlParserHandleReference(xmlParserCtxtPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlNamespaceParseQName\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlChar **prefix);\n/**\n * Entities\n */\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlDecodeEntities\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t int len,\n\t\t\t\t\t\t int what,\n\t\t\t\t\t\t xmlChar end,\n\t\t\t\t\t\t xmlChar  end2,\n\t\t\t\t\t\t xmlChar end3);\nXMLPUBFUN void XMLCALL\n\t\t\txmlHandleEntity\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t\t xmlEntityPtr entity);\n\n#endif /* LIBXML_LEGACY_ENABLED */\n\n#ifdef IN_LIBXML\n/*\n * internal only\n */\nXMLPUBFUN void XMLCALL\n\txmlErrMemory\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t const char *extra);\n#endif\n\n#ifdef __cplusplus\n}\n#endif\n#endif /* __XML_PARSER_INTERNALS_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/relaxng.h",
    "content": "/*\n * Summary: implementation of the Relax-NG validation\n * Description: implementation of the Relax-NG validation\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_RELAX_NG__\n#define __XML_RELAX_NG__\n\n#include <libxml/xmlversion.h>\n#include <libxml/hash.h>\n#include <libxml/xmlstring.h>\n\n#ifdef LIBXML_SCHEMAS_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\ntypedef struct _xmlRelaxNG xmlRelaxNG;\ntypedef xmlRelaxNG *xmlRelaxNGPtr;\n\n\n/**\n * xmlRelaxNGValidityErrorFunc:\n * @ctx: the validation context\n * @msg: the message\n * @...: extra arguments\n *\n * Signature of an error callback from a Relax-NG validation\n */\ntypedef void (XMLCDECL *xmlRelaxNGValidityErrorFunc) (void *ctx,\n\t\t\t\t\t\t      const char *msg,\n\t\t\t\t\t\t      ...) LIBXML_ATTR_FORMAT(2,3);\n\n/**\n * xmlRelaxNGValidityWarningFunc:\n * @ctx: the validation context\n * @msg: the message\n * @...: extra arguments\n *\n * Signature of a warning callback from a Relax-NG validation\n */\ntypedef void (XMLCDECL *xmlRelaxNGValidityWarningFunc) (void *ctx,\n\t\t\t\t\t\t\tconst char *msg,\n\t\t\t\t\t\t\t...) LIBXML_ATTR_FORMAT(2,3);\n\n/**\n * A schemas validation context\n */\ntypedef struct _xmlRelaxNGParserCtxt xmlRelaxNGParserCtxt;\ntypedef xmlRelaxNGParserCtxt *xmlRelaxNGParserCtxtPtr;\n\ntypedef struct _xmlRelaxNGValidCtxt xmlRelaxNGValidCtxt;\ntypedef xmlRelaxNGValidCtxt *xmlRelaxNGValidCtxtPtr;\n\n/*\n * xmlRelaxNGValidErr:\n *\n * List of possible Relax NG validation errors\n */\ntypedef enum {\n    XML_RELAXNG_OK = 0,\n    XML_RELAXNG_ERR_MEMORY,\n    XML_RELAXNG_ERR_TYPE,\n    XML_RELAXNG_ERR_TYPEVAL,\n    XML_RELAXNG_ERR_DUPID,\n    XML_RELAXNG_ERR_TYPECMP,\n    XML_RELAXNG_ERR_NOSTATE,\n    XML_RELAXNG_ERR_NODEFINE,\n    XML_RELAXNG_ERR_LISTEXTRA,\n    XML_RELAXNG_ERR_LISTEMPTY,\n    XML_RELAXNG_ERR_INTERNODATA,\n    XML_RELAXNG_ERR_INTERSEQ,\n    XML_RELAXNG_ERR_INTEREXTRA,\n    XML_RELAXNG_ERR_ELEMNAME,\n    XML_RELAXNG_ERR_ATTRNAME,\n    XML_RELAXNG_ERR_ELEMNONS,\n    XML_RELAXNG_ERR_ATTRNONS,\n    XML_RELAXNG_ERR_ELEMWRONGNS,\n    XML_RELAXNG_ERR_ATTRWRONGNS,\n    XML_RELAXNG_ERR_ELEMEXTRANS,\n    XML_RELAXNG_ERR_ATTREXTRANS,\n    XML_RELAXNG_ERR_ELEMNOTEMPTY,\n    XML_RELAXNG_ERR_NOELEM,\n    XML_RELAXNG_ERR_NOTELEM,\n    XML_RELAXNG_ERR_ATTRVALID,\n    XML_RELAXNG_ERR_CONTENTVALID,\n    XML_RELAXNG_ERR_EXTRACONTENT,\n    XML_RELAXNG_ERR_INVALIDATTR,\n    XML_RELAXNG_ERR_DATAELEM,\n    XML_RELAXNG_ERR_VALELEM,\n    XML_RELAXNG_ERR_LISTELEM,\n    XML_RELAXNG_ERR_DATATYPE,\n    XML_RELAXNG_ERR_VALUE,\n    XML_RELAXNG_ERR_LIST,\n    XML_RELAXNG_ERR_NOGRAMMAR,\n    XML_RELAXNG_ERR_EXTRADATA,\n    XML_RELAXNG_ERR_LACKDATA,\n    XML_RELAXNG_ERR_INTERNAL,\n    XML_RELAXNG_ERR_ELEMWRONG,\n    XML_RELAXNG_ERR_TEXTWRONG\n} xmlRelaxNGValidErr;\n\n/*\n * xmlRelaxNGParserFlags:\n *\n * List of possible Relax NG Parser flags\n */\ntypedef enum {\n    XML_RELAXNGP_NONE = 0,\n    XML_RELAXNGP_FREE_DOC = 1,\n    XML_RELAXNGP_CRNG = 2\n} xmlRelaxNGParserFlag;\n\nXMLPUBFUN int XMLCALL\n\t\t    xmlRelaxNGInitTypes\t\t(void);\nXMLPUBFUN void XMLCALL\n\t\t    xmlRelaxNGCleanupTypes\t(void);\n\n/*\n * Interfaces for parsing.\n */\nXMLPUBFUN xmlRelaxNGParserCtxtPtr XMLCALL\n\t\t    xmlRelaxNGNewParserCtxt\t(const char *URL);\nXMLPUBFUN xmlRelaxNGParserCtxtPtr XMLCALL\n\t\t    xmlRelaxNGNewMemParserCtxt\t(const char *buffer,\n\t\t\t\t\t\t int size);\nXMLPUBFUN xmlRelaxNGParserCtxtPtr XMLCALL\n\t\t    xmlRelaxNGNewDocParserCtxt\t(xmlDocPtr doc);\n\nXMLPUBFUN int XMLCALL\n\t\t    xmlRelaxParserSetFlag\t(xmlRelaxNGParserCtxtPtr ctxt,\n\t\t\t\t\t\t int flag);\n\nXMLPUBFUN void XMLCALL\n\t\t    xmlRelaxNGFreeParserCtxt\t(xmlRelaxNGParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t    xmlRelaxNGSetParserErrors(xmlRelaxNGParserCtxtPtr ctxt,\n\t\t\t\t\t xmlRelaxNGValidityErrorFunc err,\n\t\t\t\t\t xmlRelaxNGValidityWarningFunc warn,\n\t\t\t\t\t void *ctx);\nXMLPUBFUN int XMLCALL\n\t\t    xmlRelaxNGGetParserErrors(xmlRelaxNGParserCtxtPtr ctxt,\n\t\t\t\t\t xmlRelaxNGValidityErrorFunc *err,\n\t\t\t\t\t xmlRelaxNGValidityWarningFunc *warn,\n\t\t\t\t\t void **ctx);\nXMLPUBFUN void XMLCALL\n\t\t    xmlRelaxNGSetParserStructuredErrors(\n\t\t\t\t\t xmlRelaxNGParserCtxtPtr ctxt,\n\t\t\t\t\t xmlStructuredErrorFunc serror,\n\t\t\t\t\t void *ctx);\nXMLPUBFUN xmlRelaxNGPtr XMLCALL\n\t\t    xmlRelaxNGParse\t\t(xmlRelaxNGParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t    xmlRelaxNGFree\t\t(xmlRelaxNGPtr schema);\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN void XMLCALL\n\t\t    xmlRelaxNGDump\t\t(FILE *output,\n\t\t\t\t\t xmlRelaxNGPtr schema);\nXMLPUBFUN void XMLCALL\n\t\t    xmlRelaxNGDumpTree\t(FILE * output,\n\t\t\t\t\t xmlRelaxNGPtr schema);\n#endif /* LIBXML_OUTPUT_ENABLED */\n/*\n * Interfaces for validating\n */\nXMLPUBFUN void XMLCALL\n\t\t    xmlRelaxNGSetValidErrors(xmlRelaxNGValidCtxtPtr ctxt,\n\t\t\t\t\t xmlRelaxNGValidityErrorFunc err,\n\t\t\t\t\t xmlRelaxNGValidityWarningFunc warn,\n\t\t\t\t\t void *ctx);\nXMLPUBFUN int XMLCALL\n\t\t    xmlRelaxNGGetValidErrors(xmlRelaxNGValidCtxtPtr ctxt,\n\t\t\t\t\t xmlRelaxNGValidityErrorFunc *err,\n\t\t\t\t\t xmlRelaxNGValidityWarningFunc *warn,\n\t\t\t\t\t void **ctx);\nXMLPUBFUN void XMLCALL\n\t\t\txmlRelaxNGSetValidStructuredErrors(xmlRelaxNGValidCtxtPtr ctxt,\n\t\t\t\t\t  xmlStructuredErrorFunc serror, void *ctx);\nXMLPUBFUN xmlRelaxNGValidCtxtPtr XMLCALL\n\t\t    xmlRelaxNGNewValidCtxt\t(xmlRelaxNGPtr schema);\nXMLPUBFUN void XMLCALL\n\t\t    xmlRelaxNGFreeValidCtxt\t(xmlRelaxNGValidCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\t    xmlRelaxNGValidateDoc\t(xmlRelaxNGValidCtxtPtr ctxt,\n\t\t\t\t\t\t xmlDocPtr doc);\n/*\n * Interfaces for progressive validation when possible\n */\nXMLPUBFUN int XMLCALL\n\t\t    xmlRelaxNGValidatePushElement\t(xmlRelaxNGValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr elem);\nXMLPUBFUN int XMLCALL\n\t\t    xmlRelaxNGValidatePushCData\t(xmlRelaxNGValidCtxtPtr ctxt,\n\t\t\t\t\t const xmlChar *data,\n\t\t\t\t\t int len);\nXMLPUBFUN int XMLCALL\n\t\t    xmlRelaxNGValidatePopElement\t(xmlRelaxNGValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr elem);\nXMLPUBFUN int XMLCALL\n\t\t    xmlRelaxNGValidateFullElement\t(xmlRelaxNGValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr elem);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_SCHEMAS_ENABLED */\n\n#endif /* __XML_RELAX_NG__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/schemasInternals.h",
    "content": "/*\n * Summary: internal interfaces for XML Schemas\n * Description: internal interfaces for the XML Schemas handling\n *              and schema validity checking\n *\t\tThe Schemas development is a Work In Progress.\n *              Some of those interfaces are not guaranteed to be API or ABI stable !\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n\n#ifndef __XML_SCHEMA_INTERNALS_H__\n#define __XML_SCHEMA_INTERNALS_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_SCHEMAS_ENABLED\n\n#include <libxml/xmlregexp.h>\n#include <libxml/hash.h>\n#include <libxml/dict.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\ntypedef enum {\n    XML_SCHEMAS_UNKNOWN = 0,\n    XML_SCHEMAS_STRING = 1,\n    XML_SCHEMAS_NORMSTRING = 2,\n    XML_SCHEMAS_DECIMAL = 3,\n    XML_SCHEMAS_TIME = 4,\n    XML_SCHEMAS_GDAY = 5,\n    XML_SCHEMAS_GMONTH = 6,\n    XML_SCHEMAS_GMONTHDAY = 7,\n    XML_SCHEMAS_GYEAR = 8,\n    XML_SCHEMAS_GYEARMONTH = 9,\n    XML_SCHEMAS_DATE = 10,\n    XML_SCHEMAS_DATETIME = 11,\n    XML_SCHEMAS_DURATION = 12,\n    XML_SCHEMAS_FLOAT = 13,\n    XML_SCHEMAS_DOUBLE = 14,\n    XML_SCHEMAS_BOOLEAN = 15,\n    XML_SCHEMAS_TOKEN = 16,\n    XML_SCHEMAS_LANGUAGE = 17,\n    XML_SCHEMAS_NMTOKEN = 18,\n    XML_SCHEMAS_NMTOKENS = 19,\n    XML_SCHEMAS_NAME = 20,\n    XML_SCHEMAS_QNAME = 21,\n    XML_SCHEMAS_NCNAME = 22,\n    XML_SCHEMAS_ID = 23,\n    XML_SCHEMAS_IDREF = 24,\n    XML_SCHEMAS_IDREFS = 25,\n    XML_SCHEMAS_ENTITY = 26,\n    XML_SCHEMAS_ENTITIES = 27,\n    XML_SCHEMAS_NOTATION = 28,\n    XML_SCHEMAS_ANYURI = 29,\n    XML_SCHEMAS_INTEGER = 30,\n    XML_SCHEMAS_NPINTEGER = 31,\n    XML_SCHEMAS_NINTEGER = 32,\n    XML_SCHEMAS_NNINTEGER = 33,\n    XML_SCHEMAS_PINTEGER = 34,\n    XML_SCHEMAS_INT = 35,\n    XML_SCHEMAS_UINT = 36,\n    XML_SCHEMAS_LONG = 37,\n    XML_SCHEMAS_ULONG = 38,\n    XML_SCHEMAS_SHORT = 39,\n    XML_SCHEMAS_USHORT = 40,\n    XML_SCHEMAS_BYTE = 41,\n    XML_SCHEMAS_UBYTE = 42,\n    XML_SCHEMAS_HEXBINARY = 43,\n    XML_SCHEMAS_BASE64BINARY = 44,\n    XML_SCHEMAS_ANYTYPE = 45,\n    XML_SCHEMAS_ANYSIMPLETYPE = 46\n} xmlSchemaValType;\n\n/*\n * XML Schemas defines multiple type of types.\n */\ntypedef enum {\n    XML_SCHEMA_TYPE_BASIC = 1, /* A built-in datatype */\n    XML_SCHEMA_TYPE_ANY,\n    XML_SCHEMA_TYPE_FACET,\n    XML_SCHEMA_TYPE_SIMPLE,\n    XML_SCHEMA_TYPE_COMPLEX,\n    XML_SCHEMA_TYPE_SEQUENCE = 6,\n    XML_SCHEMA_TYPE_CHOICE,\n    XML_SCHEMA_TYPE_ALL,\n    XML_SCHEMA_TYPE_SIMPLE_CONTENT,\n    XML_SCHEMA_TYPE_COMPLEX_CONTENT,\n    XML_SCHEMA_TYPE_UR,\n    XML_SCHEMA_TYPE_RESTRICTION,\n    XML_SCHEMA_TYPE_EXTENSION,\n    XML_SCHEMA_TYPE_ELEMENT,\n    XML_SCHEMA_TYPE_ATTRIBUTE,\n    XML_SCHEMA_TYPE_ATTRIBUTEGROUP,\n    XML_SCHEMA_TYPE_GROUP,\n    XML_SCHEMA_TYPE_NOTATION,\n    XML_SCHEMA_TYPE_LIST,\n    XML_SCHEMA_TYPE_UNION,\n    XML_SCHEMA_TYPE_ANY_ATTRIBUTE,\n    XML_SCHEMA_TYPE_IDC_UNIQUE,\n    XML_SCHEMA_TYPE_IDC_KEY,\n    XML_SCHEMA_TYPE_IDC_KEYREF,\n    XML_SCHEMA_TYPE_PARTICLE = 25,\n    XML_SCHEMA_TYPE_ATTRIBUTE_USE,\n    XML_SCHEMA_FACET_MININCLUSIVE = 1000,\n    XML_SCHEMA_FACET_MINEXCLUSIVE,\n    XML_SCHEMA_FACET_MAXINCLUSIVE,\n    XML_SCHEMA_FACET_MAXEXCLUSIVE,\n    XML_SCHEMA_FACET_TOTALDIGITS,\n    XML_SCHEMA_FACET_FRACTIONDIGITS,\n    XML_SCHEMA_FACET_PATTERN,\n    XML_SCHEMA_FACET_ENUMERATION,\n    XML_SCHEMA_FACET_WHITESPACE,\n    XML_SCHEMA_FACET_LENGTH,\n    XML_SCHEMA_FACET_MAXLENGTH,\n    XML_SCHEMA_FACET_MINLENGTH,\n    XML_SCHEMA_EXTRA_QNAMEREF = 2000,\n    XML_SCHEMA_EXTRA_ATTR_USE_PROHIB\n} xmlSchemaTypeType;\n\ntypedef enum {\n    XML_SCHEMA_CONTENT_UNKNOWN = 0,\n    XML_SCHEMA_CONTENT_EMPTY = 1,\n    XML_SCHEMA_CONTENT_ELEMENTS,\n    XML_SCHEMA_CONTENT_MIXED,\n    XML_SCHEMA_CONTENT_SIMPLE,\n    XML_SCHEMA_CONTENT_MIXED_OR_ELEMENTS, /* Obsolete */\n    XML_SCHEMA_CONTENT_BASIC,\n    XML_SCHEMA_CONTENT_ANY\n} xmlSchemaContentType;\n\ntypedef struct _xmlSchemaVal xmlSchemaVal;\ntypedef xmlSchemaVal *xmlSchemaValPtr;\n\ntypedef struct _xmlSchemaType xmlSchemaType;\ntypedef xmlSchemaType *xmlSchemaTypePtr;\n\ntypedef struct _xmlSchemaFacet xmlSchemaFacet;\ntypedef xmlSchemaFacet *xmlSchemaFacetPtr;\n\n/**\n * Annotation\n */\ntypedef struct _xmlSchemaAnnot xmlSchemaAnnot;\ntypedef xmlSchemaAnnot *xmlSchemaAnnotPtr;\nstruct _xmlSchemaAnnot {\n    struct _xmlSchemaAnnot *next;\n    xmlNodePtr content;         /* the annotation */\n};\n\n/**\n * XML_SCHEMAS_ANYATTR_SKIP:\n *\n * Skip unknown attribute from validation\n * Obsolete, not used anymore.\n */\n#define XML_SCHEMAS_ANYATTR_SKIP        1\n/**\n * XML_SCHEMAS_ANYATTR_LAX:\n *\n * Ignore validation non definition on attributes\n * Obsolete, not used anymore.\n */\n#define XML_SCHEMAS_ANYATTR_LAX                2\n/**\n * XML_SCHEMAS_ANYATTR_STRICT:\n *\n * Apply strict validation rules on attributes\n * Obsolete, not used anymore.\n */\n#define XML_SCHEMAS_ANYATTR_STRICT        3\n/**\n * XML_SCHEMAS_ANY_SKIP:\n *\n * Skip unknown attribute from validation\n */\n#define XML_SCHEMAS_ANY_SKIP        1\n/**\n * XML_SCHEMAS_ANY_LAX:\n *\n * Used by wildcards.\n * Validate if type found, don't worry if not found\n */\n#define XML_SCHEMAS_ANY_LAX                2\n/**\n * XML_SCHEMAS_ANY_STRICT:\n *\n * Used by wildcards.\n * Apply strict validation rules\n */\n#define XML_SCHEMAS_ANY_STRICT        3\n/**\n * XML_SCHEMAS_ATTR_USE_PROHIBITED:\n *\n * Used by wildcards.\n * The attribute is prohibited.\n */\n#define XML_SCHEMAS_ATTR_USE_PROHIBITED 0\n/**\n * XML_SCHEMAS_ATTR_USE_REQUIRED:\n *\n * The attribute is required.\n */\n#define XML_SCHEMAS_ATTR_USE_REQUIRED 1\n/**\n * XML_SCHEMAS_ATTR_USE_OPTIONAL:\n *\n * The attribute is optional.\n */\n#define XML_SCHEMAS_ATTR_USE_OPTIONAL 2\n/**\n * XML_SCHEMAS_ATTR_GLOBAL:\n *\n * allow elements in no namespace\n */\n#define XML_SCHEMAS_ATTR_GLOBAL        1 << 0\n/**\n * XML_SCHEMAS_ATTR_NSDEFAULT:\n *\n * allow elements in no namespace\n */\n#define XML_SCHEMAS_ATTR_NSDEFAULT        1 << 7\n/**\n * XML_SCHEMAS_ATTR_INTERNAL_RESOLVED:\n *\n * this is set when the \"type\" and \"ref\" references\n * have been resolved.\n */\n#define XML_SCHEMAS_ATTR_INTERNAL_RESOLVED        1 << 8\n/**\n * XML_SCHEMAS_ATTR_FIXED:\n *\n * the attribute has a fixed value\n */\n#define XML_SCHEMAS_ATTR_FIXED        1 << 9\n\n/**\n * xmlSchemaAttribute:\n * An attribute definition.\n */\n\ntypedef struct _xmlSchemaAttribute xmlSchemaAttribute;\ntypedef xmlSchemaAttribute *xmlSchemaAttributePtr;\nstruct _xmlSchemaAttribute {\n    xmlSchemaTypeType type;\n    struct _xmlSchemaAttribute *next; /* the next attribute (not used?) */\n    const xmlChar *name; /* the name of the declaration */\n    const xmlChar *id; /* Deprecated; not used */\n    const xmlChar *ref; /* Deprecated; not used */\n    const xmlChar *refNs; /* Deprecated; not used */\n    const xmlChar *typeName; /* the local name of the type definition */\n    const xmlChar *typeNs; /* the ns URI of the type definition */\n    xmlSchemaAnnotPtr annot;\n\n    xmlSchemaTypePtr base; /* Deprecated; not used */\n    int occurs; /* Deprecated; not used */\n    const xmlChar *defValue; /* The initial value of the value constraint */\n    xmlSchemaTypePtr subtypes; /* the type definition */\n    xmlNodePtr node;\n    const xmlChar *targetNamespace;\n    int flags;\n    const xmlChar *refPrefix; /* Deprecated; not used */\n    xmlSchemaValPtr defVal; /* The compiled value constraint */\n    xmlSchemaAttributePtr refDecl; /* Deprecated; not used */\n};\n\n/**\n * xmlSchemaAttributeLink:\n * Used to build a list of attribute uses on complexType definitions.\n * WARNING: Deprecated; not used.\n */\ntypedef struct _xmlSchemaAttributeLink xmlSchemaAttributeLink;\ntypedef xmlSchemaAttributeLink *xmlSchemaAttributeLinkPtr;\nstruct _xmlSchemaAttributeLink {\n    struct _xmlSchemaAttributeLink *next;/* the next attribute link ... */\n    struct _xmlSchemaAttribute *attr;/* the linked attribute */\n};\n\n/**\n * XML_SCHEMAS_WILDCARD_COMPLETE:\n *\n * If the wildcard is complete.\n */\n#define XML_SCHEMAS_WILDCARD_COMPLETE 1 << 0\n\n/**\n * xmlSchemaCharValueLink:\n * Used to build a list of namespaces on wildcards.\n */\ntypedef struct _xmlSchemaWildcardNs xmlSchemaWildcardNs;\ntypedef xmlSchemaWildcardNs *xmlSchemaWildcardNsPtr;\nstruct _xmlSchemaWildcardNs {\n    struct _xmlSchemaWildcardNs *next;/* the next constraint link ... */\n    const xmlChar *value;/* the value */\n};\n\n/**\n * xmlSchemaWildcard.\n * A wildcard.\n */\ntypedef struct _xmlSchemaWildcard xmlSchemaWildcard;\ntypedef xmlSchemaWildcard *xmlSchemaWildcardPtr;\nstruct _xmlSchemaWildcard {\n    xmlSchemaTypeType type;        /* The kind of type */\n    const xmlChar *id; /* Deprecated; not used */\n    xmlSchemaAnnotPtr annot;\n    xmlNodePtr node;\n    int minOccurs; /* Deprecated; not used */\n    int maxOccurs; /* Deprecated; not used */\n    int processContents;\n    int any; /* Indicates if the ns constraint is of ##any */\n    xmlSchemaWildcardNsPtr nsSet; /* The list of allowed namespaces */\n    xmlSchemaWildcardNsPtr negNsSet; /* The negated namespace */\n    int flags;\n};\n\n/**\n * XML_SCHEMAS_ATTRGROUP_WILDCARD_BUILDED:\n *\n * The attribute wildcard has been already builded.\n */\n#define XML_SCHEMAS_ATTRGROUP_WILDCARD_BUILDED 1 << 0\n/**\n * XML_SCHEMAS_ATTRGROUP_GLOBAL:\n *\n * The attribute wildcard has been already builded.\n */\n#define XML_SCHEMAS_ATTRGROUP_GLOBAL 1 << 1\n/**\n * XML_SCHEMAS_ATTRGROUP_MARKED:\n *\n * Marks the attr group as marked; used for circular checks.\n */\n#define XML_SCHEMAS_ATTRGROUP_MARKED 1 << 2\n\n/**\n * XML_SCHEMAS_ATTRGROUP_REDEFINED:\n *\n * The attr group was redefined.\n */\n#define XML_SCHEMAS_ATTRGROUP_REDEFINED 1 << 3\n/**\n * XML_SCHEMAS_ATTRGROUP_HAS_REFS:\n *\n * Whether this attr. group contains attr. group references.\n */\n#define XML_SCHEMAS_ATTRGROUP_HAS_REFS 1 << 4\n\n/**\n * An attribute group definition.\n *\n * xmlSchemaAttribute and xmlSchemaAttributeGroup start of structures\n * must be kept similar\n */\ntypedef struct _xmlSchemaAttributeGroup xmlSchemaAttributeGroup;\ntypedef xmlSchemaAttributeGroup *xmlSchemaAttributeGroupPtr;\nstruct _xmlSchemaAttributeGroup {\n    xmlSchemaTypeType type;        /* The kind of type */\n    struct _xmlSchemaAttribute *next;/* the next attribute if in a group ... */\n    const xmlChar *name;\n    const xmlChar *id;\n    const xmlChar *ref; /* Deprecated; not used */\n    const xmlChar *refNs; /* Deprecated; not used */\n    xmlSchemaAnnotPtr annot;\n\n    xmlSchemaAttributePtr attributes; /* Deprecated; not used */\n    xmlNodePtr node;\n    int flags;\n    xmlSchemaWildcardPtr attributeWildcard;\n    const xmlChar *refPrefix; /* Deprecated; not used */\n    xmlSchemaAttributeGroupPtr refItem; /* Deprecated; not used */\n    const xmlChar *targetNamespace;\n    void *attrUses;\n};\n\n/**\n * xmlSchemaTypeLink:\n * Used to build a list of types (e.g. member types of\n * simpleType with variety \"union\").\n */\ntypedef struct _xmlSchemaTypeLink xmlSchemaTypeLink;\ntypedef xmlSchemaTypeLink *xmlSchemaTypeLinkPtr;\nstruct _xmlSchemaTypeLink {\n    struct _xmlSchemaTypeLink *next;/* the next type link ... */\n    xmlSchemaTypePtr type;/* the linked type */\n};\n\n/**\n * xmlSchemaFacetLink:\n * Used to build a list of facets.\n */\ntypedef struct _xmlSchemaFacetLink xmlSchemaFacetLink;\ntypedef xmlSchemaFacetLink *xmlSchemaFacetLinkPtr;\nstruct _xmlSchemaFacetLink {\n    struct _xmlSchemaFacetLink *next;/* the next facet link ... */\n    xmlSchemaFacetPtr facet;/* the linked facet */\n};\n\n/**\n * XML_SCHEMAS_TYPE_MIXED:\n *\n * the element content type is mixed\n */\n#define XML_SCHEMAS_TYPE_MIXED                1 << 0\n/**\n * XML_SCHEMAS_TYPE_DERIVATION_METHOD_EXTENSION:\n *\n * the simple or complex type has a derivation method of \"extension\".\n */\n#define XML_SCHEMAS_TYPE_DERIVATION_METHOD_EXTENSION                1 << 1\n/**\n * XML_SCHEMAS_TYPE_DERIVATION_METHOD_RESTRICTION:\n *\n * the simple or complex type has a derivation method of \"restriction\".\n */\n#define XML_SCHEMAS_TYPE_DERIVATION_METHOD_RESTRICTION                1 << 2\n/**\n * XML_SCHEMAS_TYPE_GLOBAL:\n *\n * the type is global\n */\n#define XML_SCHEMAS_TYPE_GLOBAL                1 << 3\n/**\n * XML_SCHEMAS_TYPE_OWNED_ATTR_WILDCARD:\n *\n * the complexType owns an attribute wildcard, i.e.\n * it can be freed by the complexType\n */\n#define XML_SCHEMAS_TYPE_OWNED_ATTR_WILDCARD    1 << 4 /* Obsolete. */\n/**\n * XML_SCHEMAS_TYPE_VARIETY_ABSENT:\n *\n * the simpleType has a variety of \"absent\".\n * TODO: Actually not necessary :-/, since if\n * none of the variety flags occur then it's\n * automatically absent.\n */\n#define XML_SCHEMAS_TYPE_VARIETY_ABSENT    1 << 5\n/**\n * XML_SCHEMAS_TYPE_VARIETY_LIST:\n *\n * the simpleType has a variety of \"list\".\n */\n#define XML_SCHEMAS_TYPE_VARIETY_LIST    1 << 6\n/**\n * XML_SCHEMAS_TYPE_VARIETY_UNION:\n *\n * the simpleType has a variety of \"union\".\n */\n#define XML_SCHEMAS_TYPE_VARIETY_UNION    1 << 7\n/**\n * XML_SCHEMAS_TYPE_VARIETY_ATOMIC:\n *\n * the simpleType has a variety of \"union\".\n */\n#define XML_SCHEMAS_TYPE_VARIETY_ATOMIC    1 << 8\n/**\n * XML_SCHEMAS_TYPE_FINAL_EXTENSION:\n *\n * the complexType has a final of \"extension\".\n */\n#define XML_SCHEMAS_TYPE_FINAL_EXTENSION    1 << 9\n/**\n * XML_SCHEMAS_TYPE_FINAL_RESTRICTION:\n *\n * the simpleType/complexType has a final of \"restriction\".\n */\n#define XML_SCHEMAS_TYPE_FINAL_RESTRICTION    1 << 10\n/**\n * XML_SCHEMAS_TYPE_FINAL_LIST:\n *\n * the simpleType has a final of \"list\".\n */\n#define XML_SCHEMAS_TYPE_FINAL_LIST    1 << 11\n/**\n * XML_SCHEMAS_TYPE_FINAL_UNION:\n *\n * the simpleType has a final of \"union\".\n */\n#define XML_SCHEMAS_TYPE_FINAL_UNION    1 << 12\n/**\n * XML_SCHEMAS_TYPE_FINAL_DEFAULT:\n *\n * the simpleType has a final of \"default\".\n */\n#define XML_SCHEMAS_TYPE_FINAL_DEFAULT    1 << 13\n/**\n * XML_SCHEMAS_TYPE_BUILTIN_PRIMITIVE:\n *\n * Marks the item as a builtin primitive.\n */\n#define XML_SCHEMAS_TYPE_BUILTIN_PRIMITIVE    1 << 14\n/**\n * XML_SCHEMAS_TYPE_MARKED:\n *\n * Marks the item as marked; used for circular checks.\n */\n#define XML_SCHEMAS_TYPE_MARKED        1 << 16\n/**\n * XML_SCHEMAS_TYPE_BLOCK_DEFAULT:\n *\n * the complexType did not specify 'block' so use the default of the\n * <schema> item.\n */\n#define XML_SCHEMAS_TYPE_BLOCK_DEFAULT    1 << 17\n/**\n * XML_SCHEMAS_TYPE_BLOCK_EXTENSION:\n *\n * the complexType has a 'block' of \"extension\".\n */\n#define XML_SCHEMAS_TYPE_BLOCK_EXTENSION    1 << 18\n/**\n * XML_SCHEMAS_TYPE_BLOCK_RESTRICTION:\n *\n * the complexType has a 'block' of \"restriction\".\n */\n#define XML_SCHEMAS_TYPE_BLOCK_RESTRICTION    1 << 19\n/**\n * XML_SCHEMAS_TYPE_ABSTRACT:\n *\n * the simple/complexType is abstract.\n */\n#define XML_SCHEMAS_TYPE_ABSTRACT    1 << 20\n/**\n * XML_SCHEMAS_TYPE_FACETSNEEDVALUE:\n *\n * indicates if the facets need a computed value\n */\n#define XML_SCHEMAS_TYPE_FACETSNEEDVALUE    1 << 21\n/**\n * XML_SCHEMAS_TYPE_INTERNAL_RESOLVED:\n *\n * indicates that the type was typefixed\n */\n#define XML_SCHEMAS_TYPE_INTERNAL_RESOLVED    1 << 22\n/**\n * XML_SCHEMAS_TYPE_INTERNAL_INVALID:\n *\n * indicates that the type is invalid\n */\n#define XML_SCHEMAS_TYPE_INTERNAL_INVALID    1 << 23\n/**\n * XML_SCHEMAS_TYPE_WHITESPACE_PRESERVE:\n *\n * a whitespace-facet value of \"preserve\"\n */\n#define XML_SCHEMAS_TYPE_WHITESPACE_PRESERVE    1 << 24\n/**\n * XML_SCHEMAS_TYPE_WHITESPACE_REPLACE:\n *\n * a whitespace-facet value of \"replace\"\n */\n#define XML_SCHEMAS_TYPE_WHITESPACE_REPLACE    1 << 25\n/**\n * XML_SCHEMAS_TYPE_WHITESPACE_COLLAPSE:\n *\n * a whitespace-facet value of \"collapse\"\n */\n#define XML_SCHEMAS_TYPE_WHITESPACE_COLLAPSE    1 << 26\n/**\n * XML_SCHEMAS_TYPE_HAS_FACETS:\n *\n * has facets\n */\n#define XML_SCHEMAS_TYPE_HAS_FACETS    1 << 27\n/**\n * XML_SCHEMAS_TYPE_NORMVALUENEEDED:\n *\n * indicates if the facets (pattern) need a normalized value\n */\n#define XML_SCHEMAS_TYPE_NORMVALUENEEDED    1 << 28\n\n/**\n * XML_SCHEMAS_TYPE_FIXUP_1:\n *\n * First stage of fixup was done.\n */\n#define XML_SCHEMAS_TYPE_FIXUP_1    1 << 29\n\n/**\n * XML_SCHEMAS_TYPE_REDEFINED:\n *\n * The type was redefined.\n */\n#define XML_SCHEMAS_TYPE_REDEFINED    1 << 30\n/**\n * XML_SCHEMAS_TYPE_REDEFINING:\n *\n * The type redefines an other type.\n */\n/* #define XML_SCHEMAS_TYPE_REDEFINING    1 << 31 */\n\n/**\n * _xmlSchemaType:\n *\n * Schemas type definition.\n */\nstruct _xmlSchemaType {\n    xmlSchemaTypeType type; /* The kind of type */\n    struct _xmlSchemaType *next; /* the next type if in a sequence ... */\n    const xmlChar *name;\n    const xmlChar *id ; /* Deprecated; not used */\n    const xmlChar *ref; /* Deprecated; not used */\n    const xmlChar *refNs; /* Deprecated; not used */\n    xmlSchemaAnnotPtr annot;\n    xmlSchemaTypePtr subtypes;\n    xmlSchemaAttributePtr attributes; /* Deprecated; not used */\n    xmlNodePtr node;\n    int minOccurs; /* Deprecated; not used */\n    int maxOccurs; /* Deprecated; not used */\n\n    int flags;\n    xmlSchemaContentType contentType;\n    const xmlChar *base; /* Base type's local name */\n    const xmlChar *baseNs; /* Base type's target namespace */\n    xmlSchemaTypePtr baseType; /* The base type component */\n    xmlSchemaFacetPtr facets; /* Local facets */\n    struct _xmlSchemaType *redef; /* Deprecated; not used */\n    int recurse; /* Obsolete */\n    xmlSchemaAttributeLinkPtr *attributeUses; /* Deprecated; not used */\n    xmlSchemaWildcardPtr attributeWildcard;\n    int builtInType; /* Type of built-in types. */\n    xmlSchemaTypeLinkPtr memberTypes; /* member-types if a union type. */\n    xmlSchemaFacetLinkPtr facetSet; /* All facets (incl. inherited) */\n    const xmlChar *refPrefix; /* Deprecated; not used */\n    xmlSchemaTypePtr contentTypeDef; /* Used for the simple content of complex types.\n                                        Could we use @subtypes for this? */\n    xmlRegexpPtr contModel; /* Holds the automaton of the content model */\n    const xmlChar *targetNamespace;\n    void *attrUses;\n};\n\n/*\n * xmlSchemaElement:\n * An element definition.\n *\n * xmlSchemaType, xmlSchemaFacet and xmlSchemaElement start of\n * structures must be kept similar\n */\n/**\n * XML_SCHEMAS_ELEM_NILLABLE:\n *\n * the element is nillable\n */\n#define XML_SCHEMAS_ELEM_NILLABLE        1 << 0\n/**\n * XML_SCHEMAS_ELEM_GLOBAL:\n *\n * the element is global\n */\n#define XML_SCHEMAS_ELEM_GLOBAL                1 << 1\n/**\n * XML_SCHEMAS_ELEM_DEFAULT:\n *\n * the element has a default value\n */\n#define XML_SCHEMAS_ELEM_DEFAULT        1 << 2\n/**\n * XML_SCHEMAS_ELEM_FIXED:\n *\n * the element has a fixed value\n */\n#define XML_SCHEMAS_ELEM_FIXED                1 << 3\n/**\n * XML_SCHEMAS_ELEM_ABSTRACT:\n *\n * the element is abstract\n */\n#define XML_SCHEMAS_ELEM_ABSTRACT        1 << 4\n/**\n * XML_SCHEMAS_ELEM_TOPLEVEL:\n *\n * the element is top level\n * obsolete: use XML_SCHEMAS_ELEM_GLOBAL instead\n */\n#define XML_SCHEMAS_ELEM_TOPLEVEL        1 << 5\n/**\n * XML_SCHEMAS_ELEM_REF:\n *\n * the element is a reference to a type\n */\n#define XML_SCHEMAS_ELEM_REF                1 << 6\n/**\n * XML_SCHEMAS_ELEM_NSDEFAULT:\n *\n * allow elements in no namespace\n * Obsolete, not used anymore.\n */\n#define XML_SCHEMAS_ELEM_NSDEFAULT        1 << 7\n/**\n * XML_SCHEMAS_ELEM_INTERNAL_RESOLVED:\n *\n * this is set when \"type\", \"ref\", \"substitutionGroup\"\n * references have been resolved.\n */\n#define XML_SCHEMAS_ELEM_INTERNAL_RESOLVED        1 << 8\n /**\n * XML_SCHEMAS_ELEM_CIRCULAR:\n *\n * a helper flag for the search of circular references.\n */\n#define XML_SCHEMAS_ELEM_CIRCULAR        1 << 9\n/**\n * XML_SCHEMAS_ELEM_BLOCK_ABSENT:\n *\n * the \"block\" attribute is absent\n */\n#define XML_SCHEMAS_ELEM_BLOCK_ABSENT        1 << 10\n/**\n * XML_SCHEMAS_ELEM_BLOCK_EXTENSION:\n *\n * disallowed substitutions are absent\n */\n#define XML_SCHEMAS_ELEM_BLOCK_EXTENSION        1 << 11\n/**\n * XML_SCHEMAS_ELEM_BLOCK_RESTRICTION:\n *\n * disallowed substitutions: \"restriction\"\n */\n#define XML_SCHEMAS_ELEM_BLOCK_RESTRICTION        1 << 12\n/**\n * XML_SCHEMAS_ELEM_BLOCK_SUBSTITUTION:\n *\n * disallowed substitutions: \"substituion\"\n */\n#define XML_SCHEMAS_ELEM_BLOCK_SUBSTITUTION        1 << 13\n/**\n * XML_SCHEMAS_ELEM_FINAL_ABSENT:\n *\n * substitution group exclusions are absent\n */\n#define XML_SCHEMAS_ELEM_FINAL_ABSENT        1 << 14\n/**\n * XML_SCHEMAS_ELEM_FINAL_EXTENSION:\n *\n * substitution group exclusions: \"extension\"\n */\n#define XML_SCHEMAS_ELEM_FINAL_EXTENSION        1 << 15\n/**\n * XML_SCHEMAS_ELEM_FINAL_RESTRICTION:\n *\n * substitution group exclusions: \"restriction\"\n */\n#define XML_SCHEMAS_ELEM_FINAL_RESTRICTION        1 << 16\n/**\n * XML_SCHEMAS_ELEM_SUBST_GROUP_HEAD:\n *\n * the declaration is a substitution group head\n */\n#define XML_SCHEMAS_ELEM_SUBST_GROUP_HEAD        1 << 17\n/**\n * XML_SCHEMAS_ELEM_INTERNAL_CHECKED:\n *\n * this is set when the elem decl has been checked against\n * all constraints\n */\n#define XML_SCHEMAS_ELEM_INTERNAL_CHECKED        1 << 18\n\ntypedef struct _xmlSchemaElement xmlSchemaElement;\ntypedef xmlSchemaElement *xmlSchemaElementPtr;\nstruct _xmlSchemaElement {\n    xmlSchemaTypeType type; /* The kind of type */\n    struct _xmlSchemaType *next; /* Not used? */\n    const xmlChar *name;\n    const xmlChar *id; /* Deprecated; not used */\n    const xmlChar *ref; /* Deprecated; not used */\n    const xmlChar *refNs; /* Deprecated; not used */\n    xmlSchemaAnnotPtr annot;\n    xmlSchemaTypePtr subtypes; /* the type definition */\n    xmlSchemaAttributePtr attributes;\n    xmlNodePtr node;\n    int minOccurs; /* Deprecated; not used */\n    int maxOccurs; /* Deprecated; not used */\n\n    int flags;\n    const xmlChar *targetNamespace;\n    const xmlChar *namedType;\n    const xmlChar *namedTypeNs;\n    const xmlChar *substGroup;\n    const xmlChar *substGroupNs;\n    const xmlChar *scope;\n    const xmlChar *value; /* The original value of the value constraint. */\n    struct _xmlSchemaElement *refDecl; /* This will now be used for the\n                                          substitution group affiliation */\n    xmlRegexpPtr contModel; /* Obsolete for WXS, maybe used for RelaxNG */\n    xmlSchemaContentType contentType;\n    const xmlChar *refPrefix; /* Deprecated; not used */\n    xmlSchemaValPtr defVal; /* The compiled value contraint. */\n    void *idcs; /* The identity-constraint defs */\n};\n\n/*\n * XML_SCHEMAS_FACET_UNKNOWN:\n *\n * unknown facet handling\n */\n#define XML_SCHEMAS_FACET_UNKNOWN        0\n/*\n * XML_SCHEMAS_FACET_PRESERVE:\n *\n * preserve the type of the facet\n */\n#define XML_SCHEMAS_FACET_PRESERVE        1\n/*\n * XML_SCHEMAS_FACET_REPLACE:\n *\n * replace the type of the facet\n */\n#define XML_SCHEMAS_FACET_REPLACE        2\n/*\n * XML_SCHEMAS_FACET_COLLAPSE:\n *\n * collapse the types of the facet\n */\n#define XML_SCHEMAS_FACET_COLLAPSE        3\n/**\n * A facet definition.\n */\nstruct _xmlSchemaFacet {\n    xmlSchemaTypeType type;        /* The kind of type */\n    struct _xmlSchemaFacet *next;/* the next type if in a sequence ... */\n    const xmlChar *value; /* The original value */\n    const xmlChar *id; /* Obsolete */\n    xmlSchemaAnnotPtr annot;\n    xmlNodePtr node;\n    int fixed; /* XML_SCHEMAS_FACET_PRESERVE, etc. */\n    int whitespace;\n    xmlSchemaValPtr val; /* The compiled value */\n    xmlRegexpPtr    regexp; /* The regex for patterns */\n};\n\n/**\n * A notation definition.\n */\ntypedef struct _xmlSchemaNotation xmlSchemaNotation;\ntypedef xmlSchemaNotation *xmlSchemaNotationPtr;\nstruct _xmlSchemaNotation {\n    xmlSchemaTypeType type; /* The kind of type */\n    const xmlChar *name;\n    xmlSchemaAnnotPtr annot;\n    const xmlChar *identifier;\n    const xmlChar *targetNamespace;\n};\n\n/*\n* TODO: Actually all those flags used for the schema should sit\n* on the schema parser context, since they are used only\n* during parsing an XML schema document, and not available\n* on the component level as per spec.\n*/\n/**\n * XML_SCHEMAS_QUALIF_ELEM:\n *\n * Reflects elementFormDefault == qualified in\n * an XML schema document.\n */\n#define XML_SCHEMAS_QUALIF_ELEM                1 << 0\n/**\n * XML_SCHEMAS_QUALIF_ATTR:\n *\n * Reflects attributeFormDefault == qualified in\n * an XML schema document.\n */\n#define XML_SCHEMAS_QUALIF_ATTR            1 << 1\n/**\n * XML_SCHEMAS_FINAL_DEFAULT_EXTENSION:\n *\n * the schema has \"extension\" in the set of finalDefault.\n */\n#define XML_SCHEMAS_FINAL_DEFAULT_EXTENSION        1 << 2\n/**\n * XML_SCHEMAS_FINAL_DEFAULT_RESTRICTION:\n *\n * the schema has \"restriction\" in the set of finalDefault.\n */\n#define XML_SCHEMAS_FINAL_DEFAULT_RESTRICTION            1 << 3\n/**\n * XML_SCHEMAS_FINAL_DEFAULT_LIST:\n *\n * the cshema has \"list\" in the set of finalDefault.\n */\n#define XML_SCHEMAS_FINAL_DEFAULT_LIST            1 << 4\n/**\n * XML_SCHEMAS_FINAL_DEFAULT_UNION:\n *\n * the schema has \"union\" in the set of finalDefault.\n */\n#define XML_SCHEMAS_FINAL_DEFAULT_UNION            1 << 5\n/**\n * XML_SCHEMAS_BLOCK_DEFAULT_EXTENSION:\n *\n * the schema has \"extension\" in the set of blockDefault.\n */\n#define XML_SCHEMAS_BLOCK_DEFAULT_EXTENSION            1 << 6\n/**\n * XML_SCHEMAS_BLOCK_DEFAULT_RESTRICTION:\n *\n * the schema has \"restriction\" in the set of blockDefault.\n */\n#define XML_SCHEMAS_BLOCK_DEFAULT_RESTRICTION            1 << 7\n/**\n * XML_SCHEMAS_BLOCK_DEFAULT_SUBSTITUTION:\n *\n * the schema has \"substitution\" in the set of blockDefault.\n */\n#define XML_SCHEMAS_BLOCK_DEFAULT_SUBSTITUTION            1 << 8\n/**\n * XML_SCHEMAS_INCLUDING_CONVERT_NS:\n *\n * the schema is currently including an other schema with\n * no target namespace.\n */\n#define XML_SCHEMAS_INCLUDING_CONVERT_NS            1 << 9\n/**\n * _xmlSchema:\n *\n * A Schemas definition\n */\nstruct _xmlSchema {\n    const xmlChar *name; /* schema name */\n    const xmlChar *targetNamespace; /* the target namespace */\n    const xmlChar *version;\n    const xmlChar *id; /* Obsolete */\n    xmlDocPtr doc;\n    xmlSchemaAnnotPtr annot;\n    int flags;\n\n    xmlHashTablePtr typeDecl;\n    xmlHashTablePtr attrDecl;\n    xmlHashTablePtr attrgrpDecl;\n    xmlHashTablePtr elemDecl;\n    xmlHashTablePtr notaDecl;\n\n    xmlHashTablePtr schemasImports;\n\n    void *_private;        /* unused by the library for users or bindings */\n    xmlHashTablePtr groupDecl;\n    xmlDictPtr      dict;\n    void *includes;     /* the includes, this is opaque for now */\n    int preserve;        /* whether to free the document */\n    int counter; /* used to give ononymous components unique names */\n    xmlHashTablePtr idcDef; /* All identity-constraint defs. */\n    void *volatiles; /* Obsolete */\n};\n\nXMLPUBFUN void XMLCALL         xmlSchemaFreeType        (xmlSchemaTypePtr type);\nXMLPUBFUN void XMLCALL         xmlSchemaFreeWildcard(xmlSchemaWildcardPtr wildcard);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_SCHEMAS_ENABLED */\n#endif /* __XML_SCHEMA_INTERNALS_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/schematron.h",
    "content": "/*\n * Summary: XML Schemastron implementation\n * Description: interface to the XML Schematron validity checking.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n\n#ifndef __XML_SCHEMATRON_H__\n#define __XML_SCHEMATRON_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_SCHEMATRON_ENABLED\n\n#include <libxml/tree.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\ntypedef enum {\n    XML_SCHEMATRON_OUT_QUIET = 1 << 0,\t/* quiet no report */\n    XML_SCHEMATRON_OUT_TEXT = 1 << 1,\t/* build a textual report */\n    XML_SCHEMATRON_OUT_XML = 1 << 2,\t/* output SVRL */\n    XML_SCHEMATRON_OUT_ERROR = 1 << 3,  /* output via xmlStructuredErrorFunc */\n    XML_SCHEMATRON_OUT_FILE = 1 << 8,\t/* output to a file descriptor */\n    XML_SCHEMATRON_OUT_BUFFER = 1 << 9,\t/* output to a buffer */\n    XML_SCHEMATRON_OUT_IO = 1 << 10\t/* output to I/O mechanism */\n} xmlSchematronValidOptions;\n\n/**\n * The schemas related types are kept internal\n */\ntypedef struct _xmlSchematron xmlSchematron;\ntypedef xmlSchematron *xmlSchematronPtr;\n\n/**\n * xmlSchematronValidityErrorFunc:\n * @ctx: the validation context\n * @msg: the message\n * @...: extra arguments\n *\n * Signature of an error callback from a Schematron validation\n */\ntypedef void (*xmlSchematronValidityErrorFunc) (void *ctx, const char *msg, ...);\n\n/**\n * xmlSchematronValidityWarningFunc:\n * @ctx: the validation context\n * @msg: the message\n * @...: extra arguments\n *\n * Signature of a warning callback from a Schematron validation\n */\ntypedef void (*xmlSchematronValidityWarningFunc) (void *ctx, const char *msg, ...);\n\n/**\n * A schemas validation context\n */\ntypedef struct _xmlSchematronParserCtxt xmlSchematronParserCtxt;\ntypedef xmlSchematronParserCtxt *xmlSchematronParserCtxtPtr;\n\ntypedef struct _xmlSchematronValidCtxt xmlSchematronValidCtxt;\ntypedef xmlSchematronValidCtxt *xmlSchematronValidCtxtPtr;\n\n/*\n * Interfaces for parsing.\n */\nXMLPUBFUN xmlSchematronParserCtxtPtr XMLCALL\n\t    xmlSchematronNewParserCtxt\t(const char *URL);\nXMLPUBFUN xmlSchematronParserCtxtPtr XMLCALL\n\t    xmlSchematronNewMemParserCtxt(const char *buffer,\n\t\t\t\t\t int size);\nXMLPUBFUN xmlSchematronParserCtxtPtr XMLCALL\n\t    xmlSchematronNewDocParserCtxt(xmlDocPtr doc);\nXMLPUBFUN void XMLCALL\n\t    xmlSchematronFreeParserCtxt\t(xmlSchematronParserCtxtPtr ctxt);\n/*****\nXMLPUBFUN void XMLCALL\n\t    xmlSchematronSetParserErrors(xmlSchematronParserCtxtPtr ctxt,\n\t\t\t\t\t xmlSchematronValidityErrorFunc err,\n\t\t\t\t\t xmlSchematronValidityWarningFunc warn,\n\t\t\t\t\t void *ctx);\nXMLPUBFUN int XMLCALL\n\t\txmlSchematronGetParserErrors(xmlSchematronParserCtxtPtr ctxt,\n\t\t\t\t\txmlSchematronValidityErrorFunc * err,\n\t\t\t\t\txmlSchematronValidityWarningFunc * warn,\n\t\t\t\t\tvoid **ctx);\nXMLPUBFUN int XMLCALL\n\t\txmlSchematronIsValid\t(xmlSchematronValidCtxtPtr ctxt);\n *****/\nXMLPUBFUN xmlSchematronPtr XMLCALL\n\t    xmlSchematronParse\t\t(xmlSchematronParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t    xmlSchematronFree\t\t(xmlSchematronPtr schema);\n/*\n * Interfaces for validating\n */\nXMLPUBFUN void XMLCALL\n\t    xmlSchematronSetValidStructuredErrors(\n\t                                  xmlSchematronValidCtxtPtr ctxt,\n\t\t\t\t\t  xmlStructuredErrorFunc serror,\n\t\t\t\t\t  void *ctx);\n/******\nXMLPUBFUN void XMLCALL\n\t    xmlSchematronSetValidErrors\t(xmlSchematronValidCtxtPtr ctxt,\n\t\t\t\t\t xmlSchematronValidityErrorFunc err,\n\t\t\t\t\t xmlSchematronValidityWarningFunc warn,\n\t\t\t\t\t void *ctx);\nXMLPUBFUN int XMLCALL\n\t    xmlSchematronGetValidErrors\t(xmlSchematronValidCtxtPtr ctxt,\n\t\t\t\t\t xmlSchematronValidityErrorFunc *err,\n\t\t\t\t\t xmlSchematronValidityWarningFunc *warn,\n\t\t\t\t\t void **ctx);\nXMLPUBFUN int XMLCALL\n\t    xmlSchematronSetValidOptions(xmlSchematronValidCtxtPtr ctxt,\n\t\t\t\t\t int options);\nXMLPUBFUN int XMLCALL\n\t    xmlSchematronValidCtxtGetOptions(xmlSchematronValidCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n            xmlSchematronValidateOneElement (xmlSchematronValidCtxtPtr ctxt,\n\t\t\t                 xmlNodePtr elem);\n *******/\n\nXMLPUBFUN xmlSchematronValidCtxtPtr XMLCALL\n\t    xmlSchematronNewValidCtxt\t(xmlSchematronPtr schema,\n\t\t\t\t\t int options);\nXMLPUBFUN void XMLCALL\n\t    xmlSchematronFreeValidCtxt\t(xmlSchematronValidCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t    xmlSchematronValidateDoc\t(xmlSchematronValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr instance);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_SCHEMATRON_ENABLED */\n#endif /* __XML_SCHEMATRON_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/threads.h",
    "content": "/**\n * Summary: interfaces for thread handling\n * Description: set of generic threading related routines\n *              should work with pthreads, Windows native or TLS threads\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_THREADS_H__\n#define __XML_THREADS_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * xmlMutex are a simple mutual exception locks.\n */\ntypedef struct _xmlMutex xmlMutex;\ntypedef xmlMutex *xmlMutexPtr;\n\n/*\n * xmlRMutex are reentrant mutual exception locks.\n */\ntypedef struct _xmlRMutex xmlRMutex;\ntypedef xmlRMutex *xmlRMutexPtr;\n\n#ifdef __cplusplus\n}\n#endif\n#include <libxml/globals.h>\n#ifdef __cplusplus\nextern \"C\" {\n#endif\nXMLPUBFUN xmlMutexPtr XMLCALL\n\t\t\txmlNewMutex\t(void);\nXMLPUBFUN void XMLCALL\n\t\t\txmlMutexLock\t(xmlMutexPtr tok);\nXMLPUBFUN void XMLCALL\n\t\t\txmlMutexUnlock\t(xmlMutexPtr tok);\nXMLPUBFUN void XMLCALL\n\t\t\txmlFreeMutex\t(xmlMutexPtr tok);\n\nXMLPUBFUN xmlRMutexPtr XMLCALL\n\t\t\txmlNewRMutex\t(void);\nXMLPUBFUN void XMLCALL\n\t\t\txmlRMutexLock\t(xmlRMutexPtr tok);\nXMLPUBFUN void XMLCALL\n\t\t\txmlRMutexUnlock\t(xmlRMutexPtr tok);\nXMLPUBFUN void XMLCALL\n\t\t\txmlFreeRMutex\t(xmlRMutexPtr tok);\n\n/*\n * Library wide APIs.\n */\nXMLPUBFUN void XMLCALL\n\t\t\txmlInitThreads\t(void);\nXMLPUBFUN void XMLCALL\n\t\t\txmlLockLibrary\t(void);\nXMLPUBFUN void XMLCALL\n\t\t\txmlUnlockLibrary(void);\nXMLPUBFUN int XMLCALL\n\t\t\txmlGetThreadId\t(void);\nXMLPUBFUN int XMLCALL\n\t\t\txmlIsMainThread\t(void);\nXMLPUBFUN void XMLCALL\n\t\t\txmlCleanupThreads(void);\nXMLPUBFUN xmlGlobalStatePtr XMLCALL\n\t\t\txmlGetGlobalState(void);\n\n#ifdef HAVE_PTHREAD_H\n#elif defined(HAVE_WIN32_THREADS) && !defined(HAVE_COMPILER_TLS) && (!defined(LIBXML_STATIC) || defined(LIBXML_STATIC_FOR_DLL))\n#if defined(LIBXML_STATIC_FOR_DLL)\nint XMLCALL\nxmlDllMain(void *hinstDLL, unsigned long fdwReason,\n           void *lpvReserved);\n#endif\n#endif\n\n#ifdef __cplusplus\n}\n#endif\n\n\n#endif /* __XML_THREADS_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/tree.h",
    "content": "/*\n * Summary: interfaces for tree manipulation\n * Description: this module describes the structures found in an tree resulting\n *              from an XML or HTML parsing, as well as the API provided for\n *              various processing on that tree\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_TREE_H__\n#define __XML_TREE_H__\n\n#include <stdio.h>\n#include <limits.h>\n#include <libxml/xmlversion.h>\n#include <libxml/xmlstring.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * Some of the basic types pointer to structures:\n */\n/* xmlIO.h */\ntypedef struct _xmlParserInputBuffer xmlParserInputBuffer;\ntypedef xmlParserInputBuffer *xmlParserInputBufferPtr;\n\ntypedef struct _xmlOutputBuffer xmlOutputBuffer;\ntypedef xmlOutputBuffer *xmlOutputBufferPtr;\n\n/* parser.h */\ntypedef struct _xmlParserInput xmlParserInput;\ntypedef xmlParserInput *xmlParserInputPtr;\n\ntypedef struct _xmlParserCtxt xmlParserCtxt;\ntypedef xmlParserCtxt *xmlParserCtxtPtr;\n\ntypedef struct _xmlSAXLocator xmlSAXLocator;\ntypedef xmlSAXLocator *xmlSAXLocatorPtr;\n\ntypedef struct _xmlSAXHandler xmlSAXHandler;\ntypedef xmlSAXHandler *xmlSAXHandlerPtr;\n\n/* entities.h */\ntypedef struct _xmlEntity xmlEntity;\ntypedef xmlEntity *xmlEntityPtr;\n\n/**\n * BASE_BUFFER_SIZE:\n *\n * default buffer size 4000.\n */\n#define BASE_BUFFER_SIZE 4096\n\n/**\n * LIBXML_NAMESPACE_DICT:\n *\n * Defines experimental behaviour:\n * 1) xmlNs gets an additional field @context (a xmlDoc)\n * 2) when creating a tree, xmlNs->href is stored in the dict of xmlDoc.\n */\n/* #define LIBXML_NAMESPACE_DICT */\n\n/**\n * xmlBufferAllocationScheme:\n *\n * A buffer allocation scheme can be defined to either match exactly the\n * need or double it's allocated size each time it is found too small.\n */\n\ntypedef enum {\n    XML_BUFFER_ALLOC_DOUBLEIT,\t/* double each time one need to grow */\n    XML_BUFFER_ALLOC_EXACT,\t/* grow only to the minimal size */\n    XML_BUFFER_ALLOC_IMMUTABLE, /* immutable buffer */\n    XML_BUFFER_ALLOC_IO,\t/* special allocation scheme used for I/O */\n    XML_BUFFER_ALLOC_HYBRID,\t/* exact up to a threshold, and doubleit thereafter */\n    XML_BUFFER_ALLOC_BOUNDED\t/* limit the upper size of the buffer */\n} xmlBufferAllocationScheme;\n\n/**\n * xmlBuffer:\n *\n * A buffer structure, this old construct is limited to 2GB and\n * is being deprecated, use API with xmlBuf instead\n */\ntypedef struct _xmlBuffer xmlBuffer;\ntypedef xmlBuffer *xmlBufferPtr;\nstruct _xmlBuffer {\n    xmlChar *content;\t\t/* The buffer content UTF8 */\n    unsigned int use;\t\t/* The buffer size used */\n    unsigned int size;\t\t/* The buffer size */\n    xmlBufferAllocationScheme alloc; /* The realloc method */\n    xmlChar *contentIO;\t\t/* in IO mode we may have a different base */\n};\n\n/**\n * xmlBuf:\n *\n * A buffer structure, new one, the actual structure internals are not public\n */\n\ntypedef struct _xmlBuf xmlBuf;\n\n/**\n * xmlBufPtr:\n *\n * A pointer to a buffer structure, the actual structure internals are not\n * public\n */\n\ntypedef xmlBuf *xmlBufPtr;\n\n/*\n * A few public routines for xmlBuf. As those are expected to be used\n * mostly internally the bulk of the routines are internal in buf.h\n */\nXMLPUBFUN xmlChar* XMLCALL       xmlBufContent\t(const xmlBuf* buf);\nXMLPUBFUN xmlChar* XMLCALL       xmlBufEnd      (xmlBufPtr buf);\nXMLPUBFUN size_t XMLCALL         xmlBufUse      (const xmlBufPtr buf);\nXMLPUBFUN size_t XMLCALL         xmlBufShrink\t(xmlBufPtr buf, size_t len);\n\n/*\n * LIBXML2_NEW_BUFFER:\n *\n * Macro used to express that the API use the new buffers for\n * xmlParserInputBuffer and xmlOutputBuffer. The change was\n * introduced in 2.9.0.\n */\n#define LIBXML2_NEW_BUFFER\n\n/**\n * XML_XML_NAMESPACE:\n *\n * This is the namespace for the special xml: prefix predefined in the\n * XML Namespace specification.\n */\n#define XML_XML_NAMESPACE \\\n    (const xmlChar *) \"http://www.w3.org/XML/1998/namespace\"\n\n/**\n * XML_XML_ID:\n *\n * This is the name for the special xml:id attribute\n */\n#define XML_XML_ID (const xmlChar *) \"xml:id\"\n\n/*\n * The different element types carried by an XML tree.\n *\n * NOTE: This is synchronized with DOM Level1 values\n *       See http://www.w3.org/TR/REC-DOM-Level-1/\n *\n * Actually this had diverged a bit, and now XML_DOCUMENT_TYPE_NODE should\n * be deprecated to use an XML_DTD_NODE.\n */\ntypedef enum {\n    XML_ELEMENT_NODE=\t\t1,\n    XML_ATTRIBUTE_NODE=\t\t2,\n    XML_TEXT_NODE=\t\t3,\n    XML_CDATA_SECTION_NODE=\t4,\n    XML_ENTITY_REF_NODE=\t5,\n    XML_ENTITY_NODE=\t\t6,\n    XML_PI_NODE=\t\t7,\n    XML_COMMENT_NODE=\t\t8,\n    XML_DOCUMENT_NODE=\t\t9,\n    XML_DOCUMENT_TYPE_NODE=\t10,\n    XML_DOCUMENT_FRAG_NODE=\t11,\n    XML_NOTATION_NODE=\t\t12,\n    XML_HTML_DOCUMENT_NODE=\t13,\n    XML_DTD_NODE=\t\t14,\n    XML_ELEMENT_DECL=\t\t15,\n    XML_ATTRIBUTE_DECL=\t\t16,\n    XML_ENTITY_DECL=\t\t17,\n    XML_NAMESPACE_DECL=\t\t18,\n    XML_XINCLUDE_START=\t\t19,\n    XML_XINCLUDE_END=\t\t20\n#ifdef LIBXML_DOCB_ENABLED\n   ,XML_DOCB_DOCUMENT_NODE=\t21\n#endif\n} xmlElementType;\n\n\n/**\n * xmlNotation:\n *\n * A DTD Notation definition.\n */\n\ntypedef struct _xmlNotation xmlNotation;\ntypedef xmlNotation *xmlNotationPtr;\nstruct _xmlNotation {\n    const xmlChar               *name;\t        /* Notation name */\n    const xmlChar               *PublicID;\t/* Public identifier, if any */\n    const xmlChar               *SystemID;\t/* System identifier, if any */\n};\n\n/**\n * xmlAttributeType:\n *\n * A DTD Attribute type definition.\n */\n\ntypedef enum {\n    XML_ATTRIBUTE_CDATA = 1,\n    XML_ATTRIBUTE_ID,\n    XML_ATTRIBUTE_IDREF\t,\n    XML_ATTRIBUTE_IDREFS,\n    XML_ATTRIBUTE_ENTITY,\n    XML_ATTRIBUTE_ENTITIES,\n    XML_ATTRIBUTE_NMTOKEN,\n    XML_ATTRIBUTE_NMTOKENS,\n    XML_ATTRIBUTE_ENUMERATION,\n    XML_ATTRIBUTE_NOTATION\n} xmlAttributeType;\n\n/**\n * xmlAttributeDefault:\n *\n * A DTD Attribute default definition.\n */\n\ntypedef enum {\n    XML_ATTRIBUTE_NONE = 1,\n    XML_ATTRIBUTE_REQUIRED,\n    XML_ATTRIBUTE_IMPLIED,\n    XML_ATTRIBUTE_FIXED\n} xmlAttributeDefault;\n\n/**\n * xmlEnumeration:\n *\n * List structure used when there is an enumeration in DTDs.\n */\n\ntypedef struct _xmlEnumeration xmlEnumeration;\ntypedef xmlEnumeration *xmlEnumerationPtr;\nstruct _xmlEnumeration {\n    struct _xmlEnumeration    *next;\t/* next one */\n    const xmlChar            *name;\t/* Enumeration name */\n};\n\n/**\n * xmlAttribute:\n *\n * An Attribute declaration in a DTD.\n */\n\ntypedef struct _xmlAttribute xmlAttribute;\ntypedef xmlAttribute *xmlAttributePtr;\nstruct _xmlAttribute {\n    void           *_private;\t        /* application data */\n    xmlElementType          type;       /* XML_ATTRIBUTE_DECL, must be second ! */\n    const xmlChar          *name;\t/* Attribute name */\n    struct _xmlNode    *children;\t/* NULL */\n    struct _xmlNode        *last;\t/* NULL */\n    struct _xmlDtd       *parent;\t/* -> DTD */\n    struct _xmlNode        *next;\t/* next sibling link  */\n    struct _xmlNode        *prev;\t/* previous sibling link  */\n    struct _xmlDoc          *doc;       /* the containing document */\n\n    struct _xmlAttribute  *nexth;\t/* next in hash table */\n    xmlAttributeType       atype;\t/* The attribute type */\n    xmlAttributeDefault      def;\t/* the default */\n    const xmlChar  *defaultValue;\t/* or the default value */\n    xmlEnumerationPtr       tree;       /* or the enumeration tree if any */\n    const xmlChar        *prefix;\t/* the namespace prefix if any */\n    const xmlChar          *elem;\t/* Element holding the attribute */\n};\n\n/**\n * xmlElementContentType:\n *\n * Possible definitions of element content types.\n */\ntypedef enum {\n    XML_ELEMENT_CONTENT_PCDATA = 1,\n    XML_ELEMENT_CONTENT_ELEMENT,\n    XML_ELEMENT_CONTENT_SEQ,\n    XML_ELEMENT_CONTENT_OR\n} xmlElementContentType;\n\n/**\n * xmlElementContentOccur:\n *\n * Possible definitions of element content occurrences.\n */\ntypedef enum {\n    XML_ELEMENT_CONTENT_ONCE = 1,\n    XML_ELEMENT_CONTENT_OPT,\n    XML_ELEMENT_CONTENT_MULT,\n    XML_ELEMENT_CONTENT_PLUS\n} xmlElementContentOccur;\n\n/**\n * xmlElementContent:\n *\n * An XML Element content as stored after parsing an element definition\n * in a DTD.\n */\n\ntypedef struct _xmlElementContent xmlElementContent;\ntypedef xmlElementContent *xmlElementContentPtr;\nstruct _xmlElementContent {\n    xmlElementContentType     type;\t/* PCDATA, ELEMENT, SEQ or OR */\n    xmlElementContentOccur    ocur;\t/* ONCE, OPT, MULT or PLUS */\n    const xmlChar             *name;\t/* Element name */\n    struct _xmlElementContent *c1;\t/* first child */\n    struct _xmlElementContent *c2;\t/* second child */\n    struct _xmlElementContent *parent;\t/* parent */\n    const xmlChar             *prefix;\t/* Namespace prefix */\n};\n\n/**\n * xmlElementTypeVal:\n *\n * The different possibilities for an element content type.\n */\n\ntypedef enum {\n    XML_ELEMENT_TYPE_UNDEFINED = 0,\n    XML_ELEMENT_TYPE_EMPTY = 1,\n    XML_ELEMENT_TYPE_ANY,\n    XML_ELEMENT_TYPE_MIXED,\n    XML_ELEMENT_TYPE_ELEMENT\n} xmlElementTypeVal;\n\n#ifdef __cplusplus\n}\n#endif\n#include <libxml/xmlregexp.h>\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * xmlElement:\n *\n * An XML Element declaration from a DTD.\n */\n\ntypedef struct _xmlElement xmlElement;\ntypedef xmlElement *xmlElementPtr;\nstruct _xmlElement {\n    void           *_private;\t        /* application data */\n    xmlElementType          type;       /* XML_ELEMENT_DECL, must be second ! */\n    const xmlChar          *name;\t/* Element name */\n    struct _xmlNode    *children;\t/* NULL */\n    struct _xmlNode        *last;\t/* NULL */\n    struct _xmlDtd       *parent;\t/* -> DTD */\n    struct _xmlNode        *next;\t/* next sibling link  */\n    struct _xmlNode        *prev;\t/* previous sibling link  */\n    struct _xmlDoc          *doc;       /* the containing document */\n\n    xmlElementTypeVal      etype;\t/* The type */\n    xmlElementContentPtr content;\t/* the allowed element content */\n    xmlAttributePtr   attributes;\t/* List of the declared attributes */\n    const xmlChar        *prefix;\t/* the namespace prefix if any */\n#ifdef LIBXML_REGEXP_ENABLED\n    xmlRegexpPtr       contModel;\t/* the validating regexp */\n#else\n    void\t      *contModel;\n#endif\n};\n\n\n/**\n * XML_LOCAL_NAMESPACE:\n *\n * A namespace declaration node.\n */\n#define XML_LOCAL_NAMESPACE XML_NAMESPACE_DECL\ntypedef xmlElementType xmlNsType;\n\n/**\n * xmlNs:\n *\n * An XML namespace.\n * Note that prefix == NULL is valid, it defines the default namespace\n * within the subtree (until overridden).\n *\n * xmlNsType is unified with xmlElementType.\n */\n\ntypedef struct _xmlNs xmlNs;\ntypedef xmlNs *xmlNsPtr;\nstruct _xmlNs {\n    struct _xmlNs  *next;\t/* next Ns link for this node  */\n    xmlNsType      type;\t/* global or local */\n    const xmlChar *href;\t/* URL for the namespace */\n    const xmlChar *prefix;\t/* prefix for the namespace */\n    void           *_private;   /* application data */\n    struct _xmlDoc *context;\t\t/* normally an xmlDoc */\n};\n\n/**\n * xmlDtd:\n *\n * An XML DTD, as defined by <!DOCTYPE ... There is actually one for\n * the internal subset and for the external subset.\n */\ntypedef struct _xmlDtd xmlDtd;\ntypedef xmlDtd *xmlDtdPtr;\nstruct _xmlDtd {\n    void           *_private;\t/* application data */\n    xmlElementType  type;       /* XML_DTD_NODE, must be second ! */\n    const xmlChar *name;\t/* Name of the DTD */\n    struct _xmlNode *children;\t/* the value of the property link */\n    struct _xmlNode *last;\t/* last child link */\n    struct _xmlDoc  *parent;\t/* child->parent link */\n    struct _xmlNode *next;\t/* next sibling link  */\n    struct _xmlNode *prev;\t/* previous sibling link  */\n    struct _xmlDoc  *doc;\t/* the containing document */\n\n    /* End of common part */\n    void          *notations;   /* Hash table for notations if any */\n    void          *elements;    /* Hash table for elements if any */\n    void          *attributes;  /* Hash table for attributes if any */\n    void          *entities;    /* Hash table for entities if any */\n    const xmlChar *ExternalID;\t/* External identifier for PUBLIC DTD */\n    const xmlChar *SystemID;\t/* URI for a SYSTEM or PUBLIC DTD */\n    void          *pentities;   /* Hash table for param entities if any */\n};\n\n/**\n * xmlAttr:\n *\n * An attribute on an XML node.\n */\ntypedef struct _xmlAttr xmlAttr;\ntypedef xmlAttr *xmlAttrPtr;\nstruct _xmlAttr {\n    void           *_private;\t/* application data */\n    xmlElementType   type;      /* XML_ATTRIBUTE_NODE, must be second ! */\n    const xmlChar   *name;      /* the name of the property */\n    struct _xmlNode *children;\t/* the value of the property */\n    struct _xmlNode *last;\t/* NULL */\n    struct _xmlNode *parent;\t/* child->parent link */\n    struct _xmlAttr *next;\t/* next sibling link  */\n    struct _xmlAttr *prev;\t/* previous sibling link  */\n    struct _xmlDoc  *doc;\t/* the containing document */\n    xmlNs           *ns;        /* pointer to the associated namespace */\n    xmlAttributeType atype;     /* the attribute type if validating */\n    void            *psvi;\t/* for type/PSVI informations */\n};\n\n/**\n * xmlID:\n *\n * An XML ID instance.\n */\n\ntypedef struct _xmlID xmlID;\ntypedef xmlID *xmlIDPtr;\nstruct _xmlID {\n    struct _xmlID    *next;\t/* next ID */\n    const xmlChar    *value;\t/* The ID name */\n    xmlAttrPtr        attr;\t/* The attribute holding it */\n    const xmlChar    *name;\t/* The attribute if attr is not available */\n    int               lineno;\t/* The line number if attr is not available */\n    struct _xmlDoc   *doc;\t/* The document holding the ID */\n};\n\n/**\n * xmlRef:\n *\n * An XML IDREF instance.\n */\n\ntypedef struct _xmlRef xmlRef;\ntypedef xmlRef *xmlRefPtr;\nstruct _xmlRef {\n    struct _xmlRef    *next;\t/* next Ref */\n    const xmlChar     *value;\t/* The Ref name */\n    xmlAttrPtr        attr;\t/* The attribute holding it */\n    const xmlChar    *name;\t/* The attribute if attr is not available */\n    int               lineno;\t/* The line number if attr is not available */\n};\n\n/**\n * xmlNode:\n *\n * A node in an XML tree.\n */\ntypedef struct _xmlNode xmlNode;\ntypedef xmlNode *xmlNodePtr;\nstruct _xmlNode {\n    void           *_private;\t/* application data */\n    xmlElementType   type;\t/* type number, must be second ! */\n    const xmlChar   *name;      /* the name of the node, or the entity */\n    struct _xmlNode *children;\t/* parent->childs link */\n    struct _xmlNode *last;\t/* last child link */\n    struct _xmlNode *parent;\t/* child->parent link */\n    struct _xmlNode *next;\t/* next sibling link  */\n    struct _xmlNode *prev;\t/* previous sibling link  */\n    struct _xmlDoc  *doc;\t/* the containing document */\n\n    /* End of common part */\n    xmlNs           *ns;        /* pointer to the associated namespace */\n    xmlChar         *content;   /* the content */\n    struct _xmlAttr *properties;/* properties list */\n    xmlNs           *nsDef;     /* namespace definitions on this node */\n    void            *psvi;\t/* for type/PSVI informations */\n    unsigned short   line;\t/* line number */\n    unsigned short   extra;\t/* extra data for XPath/XSLT */\n};\n\n/**\n * XML_GET_CONTENT:\n *\n * Macro to extract the content pointer of a node.\n */\n#define XML_GET_CONTENT(n)\t\t\t\t\t\\\n    ((n)->type == XML_ELEMENT_NODE ? NULL : (n)->content)\n\n/**\n * XML_GET_LINE:\n *\n * Macro to extract the line number of an element node.\n */\n#define XML_GET_LINE(n)\t\t\t\t\t\t\\\n    (xmlGetLineNo(n))\n\n/**\n * xmlDocProperty\n *\n * Set of properties of the document as found by the parser\n * Some of them are linked to similary named xmlParserOption\n */\ntypedef enum {\n    XML_DOC_WELLFORMED\t\t= 1<<0, /* document is XML well formed */\n    XML_DOC_NSVALID\t\t= 1<<1, /* document is Namespace valid */\n    XML_DOC_OLD10\t\t= 1<<2, /* parsed with old XML-1.0 parser */\n    XML_DOC_DTDVALID\t\t= 1<<3, /* DTD validation was successful */\n    XML_DOC_XINCLUDE\t\t= 1<<4, /* XInclude substitution was done */\n    XML_DOC_USERBUILT\t\t= 1<<5, /* Document was built using the API\n                                           and not by parsing an instance */\n    XML_DOC_INTERNAL\t\t= 1<<6, /* built for internal processing */\n    XML_DOC_HTML\t\t= 1<<7  /* parsed or built HTML document */\n} xmlDocProperties;\n\n/**\n * xmlDoc:\n *\n * An XML document.\n */\ntypedef struct _xmlDoc xmlDoc;\ntypedef xmlDoc *xmlDocPtr;\nstruct _xmlDoc {\n    void           *_private;\t/* application data */\n    xmlElementType  type;       /* XML_DOCUMENT_NODE, must be second ! */\n    char           *name;\t/* name/filename/URI of the document */\n    struct _xmlNode *children;\t/* the document tree */\n    struct _xmlNode *last;\t/* last child link */\n    struct _xmlNode *parent;\t/* child->parent link */\n    struct _xmlNode *next;\t/* next sibling link  */\n    struct _xmlNode *prev;\t/* previous sibling link  */\n    struct _xmlDoc  *doc;\t/* autoreference to itself */\n\n    /* End of common part */\n    int             compression;/* level of zlib compression */\n    int             standalone; /* standalone document (no external refs)\n\t\t\t\t     1 if standalone=\"yes\"\n\t\t\t\t     0 if standalone=\"no\"\n\t\t\t\t    -1 if there is no XML declaration\n\t\t\t\t    -2 if there is an XML declaration, but no\n\t\t\t\t\tstandalone attribute was specified */\n    struct _xmlDtd  *intSubset;\t/* the document internal subset */\n    struct _xmlDtd  *extSubset;\t/* the document external subset */\n    struct _xmlNs   *oldNs;\t/* Global namespace, the old way */\n    const xmlChar  *version;\t/* the XML version string */\n    const xmlChar  *encoding;   /* external initial encoding, if any */\n    void           *ids;        /* Hash table for ID attributes if any */\n    void           *refs;       /* Hash table for IDREFs attributes if any */\n    const xmlChar  *URL;\t/* The URI for that document */\n    int             charset;    /* Internal flag for charset handling,\n\t\t\t\t   actually an xmlCharEncoding */\n    struct _xmlDict *dict;      /* dict used to allocate names or NULL */\n    void           *psvi;\t/* for type/PSVI informations */\n    int             parseFlags;\t/* set of xmlParserOption used to parse the\n\t\t\t\t   document */\n    int             properties;\t/* set of xmlDocProperties for this document\n\t\t\t\t   set at the end of parsing */\n};\n\n\ntypedef struct _xmlDOMWrapCtxt xmlDOMWrapCtxt;\ntypedef xmlDOMWrapCtxt *xmlDOMWrapCtxtPtr;\n\n/**\n * xmlDOMWrapAcquireNsFunction:\n * @ctxt:  a DOM wrapper context\n * @node:  the context node (element or attribute)\n * @nsName:  the requested namespace name\n * @nsPrefix:  the requested namespace prefix\n *\n * A function called to acquire namespaces (xmlNs) from the wrapper.\n *\n * Returns an xmlNsPtr or NULL in case of an error.\n */\ntypedef xmlNsPtr (*xmlDOMWrapAcquireNsFunction) (xmlDOMWrapCtxtPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t\t const xmlChar *nsName,\n\t\t\t\t\t\t const xmlChar *nsPrefix);\n\n/**\n * xmlDOMWrapCtxt:\n *\n * Context for DOM wrapper-operations.\n */\nstruct _xmlDOMWrapCtxt {\n    void * _private;\n    /*\n    * The type of this context, just in case we need specialized\n    * contexts in the future.\n    */\n    int type;\n    /*\n    * Internal namespace map used for various operations.\n    */\n    void * namespaceMap;\n    /*\n    * Use this one to acquire an xmlNsPtr intended for node->ns.\n    * (Note that this is not intended for elem->nsDef).\n    */\n    xmlDOMWrapAcquireNsFunction getNsForNodeFunc;\n};\n\n/**\n * xmlChildrenNode:\n *\n * Macro for compatibility naming layer with libxml1. Maps\n * to \"children.\"\n */\n#ifndef xmlChildrenNode\n#define xmlChildrenNode children\n#endif\n\n/**\n * xmlRootNode:\n *\n * Macro for compatibility naming layer with libxml1. Maps\n * to \"children\".\n */\n#ifndef xmlRootNode\n#define xmlRootNode children\n#endif\n\n/*\n * Variables.\n */\n\n/*\n * Some helper functions\n */\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_XPATH_ENABLED) || \\\n    defined(LIBXML_SCHEMAS_ENABLED) || defined(LIBXML_DEBUG_ENABLED) || \\\n    defined (LIBXML_HTML_ENABLED) || defined(LIBXML_SAX1_ENABLED) || \\\n    defined(LIBXML_HTML_ENABLED) || defined(LIBXML_WRITER_ENABLED) || \\\n    defined(LIBXML_DOCB_ENABLED) || defined(LIBXML_LEGACY_ENABLED)\nXMLPUBFUN int XMLCALL\n\t\txmlValidateNCName\t(const xmlChar *value,\n\t\t\t\t\t int space);\n#endif\n\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_SCHEMAS_ENABLED)\nXMLPUBFUN int XMLCALL\n\t\txmlValidateQName\t(const xmlChar *value,\n\t\t\t\t\t int space);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateName\t\t(const xmlChar *value,\n\t\t\t\t\t int space);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateNMToken\t(const xmlChar *value,\n\t\t\t\t\t int space);\n#endif\n\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlBuildQName\t\t(const xmlChar *ncname,\n\t\t\t\t\t const xmlChar *prefix,\n\t\t\t\t\t xmlChar *memory,\n\t\t\t\t\t int len);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlSplitQName2\t\t(const xmlChar *name,\n\t\t\t\t\t xmlChar **prefix);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\txmlSplitQName3\t\t(const xmlChar *name,\n\t\t\t\t\t int *len);\n\n/*\n * Handling Buffers, the old ones see @xmlBuf for the new ones.\n */\n\nXMLPUBFUN void XMLCALL\n\t\txmlSetBufferAllocationScheme(xmlBufferAllocationScheme scheme);\nXMLPUBFUN xmlBufferAllocationScheme XMLCALL\n\t\txmlGetBufferAllocationScheme(void);\n\nXMLPUBFUN xmlBufferPtr XMLCALL\n\t\txmlBufferCreate\t\t(void);\nXMLPUBFUN xmlBufferPtr XMLCALL\n\t\txmlBufferCreateSize\t(size_t size);\nXMLPUBFUN xmlBufferPtr XMLCALL\n\t\txmlBufferCreateStatic\t(void *mem,\n\t\t\t\t\t size_t size);\nXMLPUBFUN int XMLCALL\n\t\txmlBufferResize\t\t(xmlBufferPtr buf,\n\t\t\t\t\t unsigned int size);\nXMLPUBFUN void XMLCALL\n\t\txmlBufferFree\t\t(xmlBufferPtr buf);\nXMLPUBFUN int XMLCALL\n\t\txmlBufferDump\t\t(FILE *file,\n\t\t\t\t\t xmlBufferPtr buf);\nXMLPUBFUN int XMLCALL\n\t\txmlBufferAdd\t\t(xmlBufferPtr buf,\n\t\t\t\t\t const xmlChar *str,\n\t\t\t\t\t int len);\nXMLPUBFUN int XMLCALL\n\t\txmlBufferAddHead\t(xmlBufferPtr buf,\n\t\t\t\t\t const xmlChar *str,\n\t\t\t\t\t int len);\nXMLPUBFUN int XMLCALL\n\t\txmlBufferCat\t\t(xmlBufferPtr buf,\n\t\t\t\t\t const xmlChar *str);\nXMLPUBFUN int XMLCALL\n\t\txmlBufferCCat\t\t(xmlBufferPtr buf,\n\t\t\t\t\t const char *str);\nXMLPUBFUN int XMLCALL\n\t\txmlBufferShrink\t\t(xmlBufferPtr buf,\n\t\t\t\t\t unsigned int len);\nXMLPUBFUN int XMLCALL\n\t\txmlBufferGrow\t\t(xmlBufferPtr buf,\n\t\t\t\t\t unsigned int len);\nXMLPUBFUN void XMLCALL\n\t\txmlBufferEmpty\t\t(xmlBufferPtr buf);\nXMLPUBFUN const xmlChar* XMLCALL\n\t\txmlBufferContent\t(const xmlBuffer *buf);\nXMLPUBFUN xmlChar* XMLCALL\n\t\txmlBufferDetach         (xmlBufferPtr buf);\nXMLPUBFUN void XMLCALL\n\t\txmlBufferSetAllocationScheme(xmlBufferPtr buf,\n\t\t\t\t\t xmlBufferAllocationScheme scheme);\nXMLPUBFUN int XMLCALL\n\t\txmlBufferLength\t\t(const xmlBuffer *buf);\n\n/*\n * Creating/freeing new structures.\n */\nXMLPUBFUN xmlDtdPtr XMLCALL\n\t\txmlCreateIntSubset\t(xmlDocPtr doc,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *ExternalID,\n\t\t\t\t\t const xmlChar *SystemID);\nXMLPUBFUN xmlDtdPtr XMLCALL\n\t\txmlNewDtd\t\t(xmlDocPtr doc,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *ExternalID,\n\t\t\t\t\t const xmlChar *SystemID);\nXMLPUBFUN xmlDtdPtr XMLCALL\n\t\txmlGetIntSubset\t\t(const xmlDoc *doc);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeDtd\t\t(xmlDtdPtr cur);\n#ifdef LIBXML_LEGACY_ENABLED\nXMLPUBFUN xmlNsPtr XMLCALL\n\t\txmlNewGlobalNs\t\t(xmlDocPtr doc,\n\t\t\t\t\t const xmlChar *href,\n\t\t\t\t\t const xmlChar *prefix);\n#endif /* LIBXML_LEGACY_ENABLED */\nXMLPUBFUN xmlNsPtr XMLCALL\n\t\txmlNewNs\t\t(xmlNodePtr node,\n\t\t\t\t\t const xmlChar *href,\n\t\t\t\t\t const xmlChar *prefix);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeNs\t\t(xmlNsPtr cur);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeNsList\t\t(xmlNsPtr cur);\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlNewDoc\t\t(const xmlChar *version);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeDoc\t\t(xmlDocPtr cur);\nXMLPUBFUN xmlAttrPtr XMLCALL\n\t\txmlNewDocProp\t\t(xmlDocPtr doc,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *value);\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_HTML_ENABLED) || \\\n    defined(LIBXML_SCHEMAS_ENABLED)\nXMLPUBFUN xmlAttrPtr XMLCALL\n\t\txmlNewProp\t\t(xmlNodePtr node,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *value);\n#endif\nXMLPUBFUN xmlAttrPtr XMLCALL\n\t\txmlNewNsProp\t\t(xmlNodePtr node,\n\t\t\t\t\t xmlNsPtr ns,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN xmlAttrPtr XMLCALL\n\t\txmlNewNsPropEatName\t(xmlNodePtr node,\n\t\t\t\t\t xmlNsPtr ns,\n\t\t\t\t\t xmlChar *name,\n\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN void XMLCALL\n\t\txmlFreePropList\t\t(xmlAttrPtr cur);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeProp\t\t(xmlAttrPtr cur);\nXMLPUBFUN xmlAttrPtr XMLCALL\n\t\txmlCopyProp\t\t(xmlNodePtr target,\n\t\t\t\t\t xmlAttrPtr cur);\nXMLPUBFUN xmlAttrPtr XMLCALL\n\t\txmlCopyPropList\t\t(xmlNodePtr target,\n\t\t\t\t\t xmlAttrPtr cur);\n#ifdef LIBXML_TREE_ENABLED\nXMLPUBFUN xmlDtdPtr XMLCALL\n\t\txmlCopyDtd\t\t(xmlDtdPtr dtd);\n#endif /* LIBXML_TREE_ENABLED */\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_SCHEMAS_ENABLED)\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\txmlCopyDoc\t\t(xmlDocPtr doc,\n\t\t\t\t\t int recursive);\n#endif /* defined(LIBXML_TREE_ENABLED) || defined(LIBXML_SCHEMAS_ENABLED) */\n/*\n * Creating new nodes.\n */\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewDocNode\t\t(xmlDocPtr doc,\n\t\t\t\t\t xmlNsPtr ns,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *content);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewDocNodeEatName\t(xmlDocPtr doc,\n\t\t\t\t\t xmlNsPtr ns,\n\t\t\t\t\t xmlChar *name,\n\t\t\t\t\t const xmlChar *content);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewNode\t\t(xmlNsPtr ns,\n\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewNodeEatName\t(xmlNsPtr ns,\n\t\t\t\t\t xmlChar *name);\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_SCHEMAS_ENABLED)\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewChild\t\t(xmlNodePtr parent,\n\t\t\t\t\t xmlNsPtr ns,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *content);\n#endif\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewDocText\t\t(const xmlDoc *doc,\n\t\t\t\t\t const xmlChar *content);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewText\t\t(const xmlChar *content);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewDocPI\t\t(xmlDocPtr doc,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *content);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewPI\t\t(const xmlChar *name,\n\t\t\t\t\t const xmlChar *content);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewDocTextLen\t(xmlDocPtr doc,\n\t\t\t\t\t const xmlChar *content,\n\t\t\t\t\t int len);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewTextLen\t\t(const xmlChar *content,\n\t\t\t\t\t int len);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewDocComment\t(xmlDocPtr doc,\n\t\t\t\t\t const xmlChar *content);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewComment\t\t(const xmlChar *content);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewCDataBlock\t(xmlDocPtr doc,\n\t\t\t\t\t const xmlChar *content,\n\t\t\t\t\t int len);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewCharRef\t\t(xmlDocPtr doc,\n\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewReference\t\t(const xmlDoc *doc,\n\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlCopyNode\t\t(xmlNodePtr node,\n\t\t\t\t\t int recursive);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlDocCopyNode\t\t(xmlNodePtr node,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t int recursive);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlDocCopyNodeList\t(xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr node);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlCopyNodeList\t\t(xmlNodePtr node);\n#ifdef LIBXML_TREE_ENABLED\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewTextChild\t\t(xmlNodePtr parent,\n\t\t\t\t\t xmlNsPtr ns,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *content);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewDocRawNode\t(xmlDocPtr doc,\n\t\t\t\t\t xmlNsPtr ns,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *content);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlNewDocFragment\t(xmlDocPtr doc);\n#endif /* LIBXML_TREE_ENABLED */\n\n/*\n * Navigating.\n */\nXMLPUBFUN long XMLCALL\n\t\txmlGetLineNo\t\t(const xmlNode *node);\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_DEBUG_ENABLED)\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlGetNodePath\t\t(const xmlNode *node);\n#endif /* defined(LIBXML_TREE_ENABLED) || defined(LIBXML_DEBUG_ENABLED) */\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlDocGetRootElement\t(const xmlDoc *doc);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlGetLastChild\t\t(const xmlNode *parent);\nXMLPUBFUN int XMLCALL\n\t\txmlNodeIsText\t\t(const xmlNode *node);\nXMLPUBFUN int XMLCALL\n\t\txmlIsBlankNode\t\t(const xmlNode *node);\n\n/*\n * Changing the structure.\n */\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_WRITER_ENABLED)\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlDocSetRootElement\t(xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr root);\n#endif /* defined(LIBXML_TREE_ENABLED) || defined(LIBXML_WRITER_ENABLED) */\n#ifdef LIBXML_TREE_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlNodeSetName\t\t(xmlNodePtr cur,\n\t\t\t\t\t const xmlChar *name);\n#endif /* LIBXML_TREE_ENABLED */\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlAddChild\t\t(xmlNodePtr parent,\n\t\t\t\t\t xmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlAddChildList\t\t(xmlNodePtr parent,\n\t\t\t\t\t xmlNodePtr cur);\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_WRITER_ENABLED)\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlReplaceNode\t\t(xmlNodePtr old,\n\t\t\t\t\t xmlNodePtr cur);\n#endif /* defined(LIBXML_TREE_ENABLED) || defined(LIBXML_WRITER_ENABLED) */\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_HTML_ENABLED) || \\\n    defined(LIBXML_SCHEMAS_ENABLED) || defined(LIBXML_XINCLUDE_ENABLED)\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlAddPrevSibling\t(xmlNodePtr cur,\n\t\t\t\t\t xmlNodePtr elem);\n#endif /* LIBXML_TREE_ENABLED || LIBXML_HTML_ENABLED || LIBXML_SCHEMAS_ENABLED */\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlAddSibling\t\t(xmlNodePtr cur,\n\t\t\t\t\t xmlNodePtr elem);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlAddNextSibling\t(xmlNodePtr cur,\n\t\t\t\t\t xmlNodePtr elem);\nXMLPUBFUN void XMLCALL\n\t\txmlUnlinkNode\t\t(xmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlTextMerge\t\t(xmlNodePtr first,\n\t\t\t\t\t xmlNodePtr second);\nXMLPUBFUN int XMLCALL\n\t\txmlTextConcat\t\t(xmlNodePtr node,\n\t\t\t\t\t const xmlChar *content,\n\t\t\t\t\t int len);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeNodeList\t\t(xmlNodePtr cur);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeNode\t\t(xmlNodePtr cur);\nXMLPUBFUN void XMLCALL\n\t\txmlSetTreeDoc\t\t(xmlNodePtr tree,\n\t\t\t\t\t xmlDocPtr doc);\nXMLPUBFUN void XMLCALL\n\t\txmlSetListDoc\t\t(xmlNodePtr list,\n\t\t\t\t\t xmlDocPtr doc);\n/*\n * Namespaces.\n */\nXMLPUBFUN xmlNsPtr XMLCALL\n\t\txmlSearchNs\t\t(xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t const xmlChar *nameSpace);\nXMLPUBFUN xmlNsPtr XMLCALL\n\t\txmlSearchNsByHref\t(xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t const xmlChar *href);\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_XPATH_ENABLED) || \\\n    defined(LIBXML_SCHEMAS_ENABLED)\nXMLPUBFUN xmlNsPtr * XMLCALL\n\t\txmlGetNsList\t\t(const xmlDoc *doc,\n\t\t\t\t\t const xmlNode *node);\n#endif /* defined(LIBXML_TREE_ENABLED) || defined(LIBXML_XPATH_ENABLED) */\n\nXMLPUBFUN void XMLCALL\n\t\txmlSetNs\t\t(xmlNodePtr node,\n\t\t\t\t\t xmlNsPtr ns);\nXMLPUBFUN xmlNsPtr XMLCALL\n\t\txmlCopyNamespace\t(xmlNsPtr cur);\nXMLPUBFUN xmlNsPtr XMLCALL\n\t\txmlCopyNamespaceList\t(xmlNsPtr cur);\n\n/*\n * Changing the content.\n */\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_XINCLUDE_ENABLED) || \\\n    defined(LIBXML_SCHEMAS_ENABLED) || defined(LIBXML_HTML_ENABLED)\nXMLPUBFUN xmlAttrPtr XMLCALL\n\t\txmlSetProp\t\t(xmlNodePtr node,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN xmlAttrPtr XMLCALL\n\t\txmlSetNsProp\t\t(xmlNodePtr node,\n\t\t\t\t\t xmlNsPtr ns,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *value);\n#endif /* defined(LIBXML_TREE_ENABLED) || defined(LIBXML_XINCLUDE_ENABLED) || \\\n\t  defined(LIBXML_SCHEMAS_ENABLED) || defined(LIBXML_HTML_ENABLED) */\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlGetNoNsProp\t\t(const xmlNode *node,\n\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlGetProp\t\t(const xmlNode *node,\n\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlAttrPtr XMLCALL\n\t\txmlHasProp\t\t(const xmlNode *node,\n\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlAttrPtr XMLCALL\n\t\txmlHasNsProp\t\t(const xmlNode *node,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *nameSpace);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlGetNsProp\t\t(const xmlNode *node,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *nameSpace);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlStringGetNodeList\t(const xmlDoc *doc,\n\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\txmlStringLenGetNodeList\t(const xmlDoc *doc,\n\t\t\t\t\t const xmlChar *value,\n\t\t\t\t\t int len);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlNodeListGetString\t(xmlDocPtr doc,\n\t\t\t\t\t const xmlNode *list,\n\t\t\t\t\t int inLine);\n#ifdef LIBXML_TREE_ENABLED\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlNodeListGetRawString\t(const xmlDoc *doc,\n\t\t\t\t\t const xmlNode *list,\n\t\t\t\t\t int inLine);\n#endif /* LIBXML_TREE_ENABLED */\nXMLPUBFUN void XMLCALL\n\t\txmlNodeSetContent\t(xmlNodePtr cur,\n\t\t\t\t\t const xmlChar *content);\n#ifdef LIBXML_TREE_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlNodeSetContentLen\t(xmlNodePtr cur,\n\t\t\t\t\t const xmlChar *content,\n\t\t\t\t\t int len);\n#endif /* LIBXML_TREE_ENABLED */\nXMLPUBFUN void XMLCALL\n\t\txmlNodeAddContent\t(xmlNodePtr cur,\n\t\t\t\t\t const xmlChar *content);\nXMLPUBFUN void XMLCALL\n\t\txmlNodeAddContentLen\t(xmlNodePtr cur,\n\t\t\t\t\t const xmlChar *content,\n\t\t\t\t\t int len);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlNodeGetContent\t(const xmlNode *cur);\n\nXMLPUBFUN int XMLCALL\n\t\txmlNodeBufGetContent\t(xmlBufferPtr buffer,\n\t\t\t\t\t const xmlNode *cur);\nXMLPUBFUN int XMLCALL\n\t\txmlBufGetNodeContent\t(xmlBufPtr buf,\n\t\t\t\t\t const xmlNode *cur);\n\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlNodeGetLang\t\t(const xmlNode *cur);\nXMLPUBFUN int XMLCALL\n\t\txmlNodeGetSpacePreserve\t(const xmlNode *cur);\n#ifdef LIBXML_TREE_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlNodeSetLang\t\t(xmlNodePtr cur,\n\t\t\t\t\t const xmlChar *lang);\nXMLPUBFUN void XMLCALL\n\t\txmlNodeSetSpacePreserve (xmlNodePtr cur,\n\t\t\t\t\t int val);\n#endif /* LIBXML_TREE_ENABLED */\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlNodeGetBase\t\t(const xmlDoc *doc,\n\t\t\t\t\t const xmlNode *cur);\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_XINCLUDE_ENABLED)\nXMLPUBFUN void XMLCALL\n\t\txmlNodeSetBase\t\t(xmlNodePtr cur,\n\t\t\t\t\t const xmlChar *uri);\n#endif\n\n/*\n * Removing content.\n */\nXMLPUBFUN int XMLCALL\n\t\txmlRemoveProp\t\t(xmlAttrPtr cur);\n#if defined(LIBXML_TREE_ENABLED) || defined(LIBXML_SCHEMAS_ENABLED)\nXMLPUBFUN int XMLCALL\n\t\txmlUnsetNsProp\t\t(xmlNodePtr node,\n\t\t\t\t\t xmlNsPtr ns,\n\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN int XMLCALL\n\t\txmlUnsetProp\t\t(xmlNodePtr node,\n\t\t\t\t\t const xmlChar *name);\n#endif /* defined(LIBXML_TREE_ENABLED) || defined(LIBXML_SCHEMAS_ENABLED) */\n\n/*\n * Internal, don't use.\n */\nXMLPUBFUN void XMLCALL\n\t\txmlBufferWriteCHAR\t(xmlBufferPtr buf,\n\t\t\t\t\t const xmlChar *string);\nXMLPUBFUN void XMLCALL\n\t\txmlBufferWriteChar\t(xmlBufferPtr buf,\n\t\t\t\t\t const char *string);\nXMLPUBFUN void XMLCALL\n\t\txmlBufferWriteQuotedString(xmlBufferPtr buf,\n\t\t\t\t\t const xmlChar *string);\n\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN void xmlAttrSerializeTxtContent(xmlBufferPtr buf,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlAttrPtr attr,\n\t\t\t\t\t const xmlChar *string);\n#endif /* LIBXML_OUTPUT_ENABLED */\n\n#ifdef LIBXML_TREE_ENABLED\n/*\n * Namespace handling.\n */\nXMLPUBFUN int XMLCALL\n\t\txmlReconciliateNs\t(xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr tree);\n#endif\n\n#ifdef LIBXML_OUTPUT_ENABLED\n/*\n * Saving.\n */\nXMLPUBFUN void XMLCALL\n\t\txmlDocDumpFormatMemory\t(xmlDocPtr cur,\n\t\t\t\t\t xmlChar **mem,\n\t\t\t\t\t int *size,\n\t\t\t\t\t int format);\nXMLPUBFUN void XMLCALL\n\t\txmlDocDumpMemory\t(xmlDocPtr cur,\n\t\t\t\t\t xmlChar **mem,\n\t\t\t\t\t int *size);\nXMLPUBFUN void XMLCALL\n\t\txmlDocDumpMemoryEnc\t(xmlDocPtr out_doc,\n\t\t\t\t\t xmlChar **doc_txt_ptr,\n\t\t\t\t\t int * doc_txt_len,\n\t\t\t\t\t const char *txt_encoding);\nXMLPUBFUN void XMLCALL\n\t\txmlDocDumpFormatMemoryEnc(xmlDocPtr out_doc,\n\t\t\t\t\t xmlChar **doc_txt_ptr,\n\t\t\t\t\t int * doc_txt_len,\n\t\t\t\t\t const char *txt_encoding,\n\t\t\t\t\t int format);\nXMLPUBFUN int XMLCALL\n\t\txmlDocFormatDump\t(FILE *f,\n\t\t\t\t\t xmlDocPtr cur,\n\t\t\t\t\t int format);\nXMLPUBFUN int XMLCALL\n\t\txmlDocDump\t\t(FILE *f,\n\t\t\t\t\t xmlDocPtr cur);\nXMLPUBFUN void XMLCALL\n\t\txmlElemDump\t\t(FILE *f,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr cur);\nXMLPUBFUN int XMLCALL\n\t\txmlSaveFile\t\t(const char *filename,\n\t\t\t\t\t xmlDocPtr cur);\nXMLPUBFUN int XMLCALL\n\t\txmlSaveFormatFile\t(const char *filename,\n\t\t\t\t\t xmlDocPtr cur,\n\t\t\t\t\t int format);\nXMLPUBFUN size_t XMLCALL\n\t\txmlBufNodeDump\t\t(xmlBufPtr buf,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr cur,\n\t\t\t\t\t int level,\n\t\t\t\t\t int format);\nXMLPUBFUN int XMLCALL\n\t\txmlNodeDump\t\t(xmlBufferPtr buf,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr cur,\n\t\t\t\t\t int level,\n\t\t\t\t\t int format);\n\nXMLPUBFUN int XMLCALL\n\t\txmlSaveFileTo\t\t(xmlOutputBufferPtr buf,\n\t\t\t\t\t xmlDocPtr cur,\n\t\t\t\t\t const char *encoding);\nXMLPUBFUN int XMLCALL\n\t\txmlSaveFormatFileTo     (xmlOutputBufferPtr buf,\n\t\t\t\t\t xmlDocPtr cur,\n\t\t\t\t         const char *encoding,\n\t\t\t\t         int format);\nXMLPUBFUN void XMLCALL\n\t\txmlNodeDumpOutput\t(xmlOutputBufferPtr buf,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr cur,\n\t\t\t\t\t int level,\n\t\t\t\t\t int format,\n\t\t\t\t\t const char *encoding);\n\nXMLPUBFUN int XMLCALL\n\t\txmlSaveFormatFileEnc    (const char *filename,\n\t\t\t\t\t xmlDocPtr cur,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int format);\n\nXMLPUBFUN int XMLCALL\n\t\txmlSaveFileEnc\t\t(const char *filename,\n\t\t\t\t\t xmlDocPtr cur,\n\t\t\t\t\t const char *encoding);\n\n#endif /* LIBXML_OUTPUT_ENABLED */\n/*\n * XHTML\n */\nXMLPUBFUN int XMLCALL\n\t\txmlIsXHTML\t\t(const xmlChar *systemID,\n\t\t\t\t\t const xmlChar *publicID);\n\n/*\n * Compression.\n */\nXMLPUBFUN int XMLCALL\n\t\txmlGetDocCompressMode\t(const xmlDoc *doc);\nXMLPUBFUN void XMLCALL\n\t\txmlSetDocCompressMode\t(xmlDocPtr doc,\n\t\t\t\t\t int mode);\nXMLPUBFUN int XMLCALL\n\t\txmlGetCompressMode\t(void);\nXMLPUBFUN void XMLCALL\n\t\txmlSetCompressMode\t(int mode);\n\n/*\n* DOM-wrapper helper functions.\n*/\nXMLPUBFUN xmlDOMWrapCtxtPtr XMLCALL\n\t\txmlDOMWrapNewCtxt\t(void);\nXMLPUBFUN void XMLCALL\n\t\txmlDOMWrapFreeCtxt\t(xmlDOMWrapCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t    xmlDOMWrapReconcileNamespaces(xmlDOMWrapCtxtPtr ctxt,\n\t\t\t\t\t xmlNodePtr elem,\n\t\t\t\t\t int options);\nXMLPUBFUN int XMLCALL\n\t    xmlDOMWrapAdoptNode\t\t(xmlDOMWrapCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr sourceDoc,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t xmlDocPtr destDoc,\n\t\t\t\t\t xmlNodePtr destParent,\n\t\t\t\t\t int options);\nXMLPUBFUN int XMLCALL\n\t    xmlDOMWrapRemoveNode\t(xmlDOMWrapCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t int options);\nXMLPUBFUN int XMLCALL\n\t    xmlDOMWrapCloneNode\t\t(xmlDOMWrapCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr sourceDoc,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr *clonedNode,\n\t\t\t\t\t xmlDocPtr destDoc,\n\t\t\t\t\t xmlNodePtr destParent,\n\t\t\t\t\t int deep,\n\t\t\t\t\t int options);\n\n#ifdef LIBXML_TREE_ENABLED\n/*\n * 5 interfaces from DOM ElementTraversal, but different in entities\n * traversal.\n */\nXMLPUBFUN unsigned long XMLCALL\n            xmlChildElementCount        (xmlNodePtr parent);\nXMLPUBFUN xmlNodePtr XMLCALL\n            xmlNextElementSibling       (xmlNodePtr node);\nXMLPUBFUN xmlNodePtr XMLCALL\n            xmlFirstElementChild        (xmlNodePtr parent);\nXMLPUBFUN xmlNodePtr XMLCALL\n            xmlLastElementChild         (xmlNodePtr parent);\nXMLPUBFUN xmlNodePtr XMLCALL\n            xmlPreviousElementSibling   (xmlNodePtr node);\n#endif\n#ifdef __cplusplus\n}\n#endif\n#ifndef __XML_PARSER_H__\n#include <libxml/xmlmemory.h>\n#endif\n\n#endif /* __XML_TREE_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/uri.h",
    "content": "/**\n * Summary: library of generic URI related routines\n * Description: library of generic URI related routines\n *              Implements RFC 2396\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_URI_H__\n#define __XML_URI_H__\n\n#include <libxml/xmlversion.h>\n#include <libxml/tree.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * xmlURI:\n *\n * A parsed URI reference. This is a struct containing the various fields\n * as described in RFC 2396 but separated for further processing.\n *\n * Note: query is a deprecated field which is incorrectly unescaped.\n * query_raw takes precedence over query if the former is set.\n * See: http://mail.gnome.org/archives/xml/2007-April/thread.html#00127\n */\ntypedef struct _xmlURI xmlURI;\ntypedef xmlURI *xmlURIPtr;\nstruct _xmlURI {\n    char *scheme;\t/* the URI scheme */\n    char *opaque;\t/* opaque part */\n    char *authority;\t/* the authority part */\n    char *server;\t/* the server part */\n    char *user;\t\t/* the user part */\n    int port;\t\t/* the port number */\n    char *path;\t\t/* the path string */\n    char *query;\t/* the query string (deprecated - use with caution) */\n    char *fragment;\t/* the fragment identifier */\n    int  cleanup;\t/* parsing potentially unclean URI */\n    char *query_raw;\t/* the query string (as it appears in the URI) */\n};\n\n/*\n * This function is in tree.h:\n * xmlChar *\txmlNodeGetBase\t(xmlDocPtr doc,\n *                               xmlNodePtr cur);\n */\nXMLPUBFUN xmlURIPtr XMLCALL\n\t\txmlCreateURI\t\t(void);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlBuildURI\t\t(const xmlChar *URI,\n\t\t\t\t\t const xmlChar *base);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlBuildRelativeURI\t(const xmlChar *URI,\n\t\t\t\t\t const xmlChar *base);\nXMLPUBFUN xmlURIPtr XMLCALL\n\t\txmlParseURI\t\t(const char *str);\nXMLPUBFUN xmlURIPtr XMLCALL\n\t\txmlParseURIRaw\t\t(const char *str,\n\t\t\t\t\t int raw);\nXMLPUBFUN int XMLCALL\n\t\txmlParseURIReference\t(xmlURIPtr uri,\n\t\t\t\t\t const char *str);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlSaveUri\t\t(xmlURIPtr uri);\nXMLPUBFUN void XMLCALL\n\t\txmlPrintURI\t\t(FILE *stream,\n\t\t\t\t\t xmlURIPtr uri);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlURIEscapeStr         (const xmlChar *str,\n\t\t\t\t\t const xmlChar *list);\nXMLPUBFUN char * XMLCALL\n\t\txmlURIUnescapeString\t(const char *str,\n\t\t\t\t\t int len,\n\t\t\t\t\t char *target);\nXMLPUBFUN int XMLCALL\n\t\txmlNormalizeURIPath\t(char *path);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlURIEscape\t\t(const xmlChar *str);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeURI\t\t(xmlURIPtr uri);\nXMLPUBFUN xmlChar* XMLCALL\n\t\txmlCanonicPath\t\t(const xmlChar *path);\nXMLPUBFUN xmlChar* XMLCALL\n\t\txmlPathToURI\t\t(const xmlChar *path);\n\n#ifdef __cplusplus\n}\n#endif\n#endif /* __XML_URI_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/valid.h",
    "content": "/*\n * Summary: The DTD validation\n * Description: API for the DTD handling and the validity checking\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n\n#ifndef __XML_VALID_H__\n#define __XML_VALID_H__\n\n#include <libxml/xmlversion.h>\n#include <libxml/xmlerror.h>\n#include <libxml/tree.h>\n#include <libxml/list.h>\n#include <libxml/xmlautomata.h>\n#include <libxml/xmlregexp.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * Validation state added for non-determinist content model.\n */\ntypedef struct _xmlValidState xmlValidState;\ntypedef xmlValidState *xmlValidStatePtr;\n\n/**\n * xmlValidityErrorFunc:\n * @ctx:  usually an xmlValidCtxtPtr to a validity error context,\n *        but comes from ctxt->userData (which normally contains such\n *        a pointer); ctxt->userData can be changed by the user.\n * @msg:  the string to format *printf like vararg\n * @...:  remaining arguments to the format\n *\n * Callback called when a validity error is found. This is a message\n * oriented function similar to an *printf function.\n */\ntypedef void (XMLCDECL *xmlValidityErrorFunc) (void *ctx,\n\t\t\t     const char *msg,\n\t\t\t     ...) LIBXML_ATTR_FORMAT(2,3);\n\n/**\n * xmlValidityWarningFunc:\n * @ctx:  usually an xmlValidCtxtPtr to a validity error context,\n *        but comes from ctxt->userData (which normally contains such\n *        a pointer); ctxt->userData can be changed by the user.\n * @msg:  the string to format *printf like vararg\n * @...:  remaining arguments to the format\n *\n * Callback called when a validity warning is found. This is a message\n * oriented function similar to an *printf function.\n */\ntypedef void (XMLCDECL *xmlValidityWarningFunc) (void *ctx,\n\t\t\t       const char *msg,\n\t\t\t       ...) LIBXML_ATTR_FORMAT(2,3);\n\n#ifdef IN_LIBXML\n/**\n * XML_CTXT_FINISH_DTD_0:\n *\n * Special value for finishDtd field when embedded in an xmlParserCtxt\n */\n#define XML_CTXT_FINISH_DTD_0 0xabcd1234\n/**\n * XML_CTXT_FINISH_DTD_1:\n *\n * Special value for finishDtd field when embedded in an xmlParserCtxt\n */\n#define XML_CTXT_FINISH_DTD_1 0xabcd1235\n#endif\n\n/*\n * xmlValidCtxt:\n * An xmlValidCtxt is used for error reporting when validating.\n */\ntypedef struct _xmlValidCtxt xmlValidCtxt;\ntypedef xmlValidCtxt *xmlValidCtxtPtr;\nstruct _xmlValidCtxt {\n    void *userData;\t\t\t/* user specific data block */\n    xmlValidityErrorFunc error;\t\t/* the callback in case of errors */\n    xmlValidityWarningFunc warning;\t/* the callback in case of warning */\n\n    /* Node analysis stack used when validating within entities */\n    xmlNodePtr         node;          /* Current parsed Node */\n    int                nodeNr;        /* Depth of the parsing stack */\n    int                nodeMax;       /* Max depth of the parsing stack */\n    xmlNodePtr        *nodeTab;       /* array of nodes */\n\n    unsigned int     finishDtd;       /* finished validating the Dtd ? */\n    xmlDocPtr              doc;       /* the document */\n    int                  valid;       /* temporary validity check result */\n\n    /* state state used for non-determinist content validation */\n    xmlValidState     *vstate;        /* current state */\n    int                vstateNr;      /* Depth of the validation stack */\n    int                vstateMax;     /* Max depth of the validation stack */\n    xmlValidState     *vstateTab;     /* array of validation states */\n\n#ifdef LIBXML_REGEXP_ENABLED\n    xmlAutomataPtr            am;     /* the automata */\n    xmlAutomataStatePtr    state;     /* used to build the automata */\n#else\n    void                     *am;\n    void                  *state;\n#endif\n};\n\n/*\n * ALL notation declarations are stored in a table.\n * There is one table per DTD.\n */\n\ntypedef struct _xmlHashTable xmlNotationTable;\ntypedef xmlNotationTable *xmlNotationTablePtr;\n\n/*\n * ALL element declarations are stored in a table.\n * There is one table per DTD.\n */\n\ntypedef struct _xmlHashTable xmlElementTable;\ntypedef xmlElementTable *xmlElementTablePtr;\n\n/*\n * ALL attribute declarations are stored in a table.\n * There is one table per DTD.\n */\n\ntypedef struct _xmlHashTable xmlAttributeTable;\ntypedef xmlAttributeTable *xmlAttributeTablePtr;\n\n/*\n * ALL IDs attributes are stored in a table.\n * There is one table per document.\n */\n\ntypedef struct _xmlHashTable xmlIDTable;\ntypedef xmlIDTable *xmlIDTablePtr;\n\n/*\n * ALL Refs attributes are stored in a table.\n * There is one table per document.\n */\n\ntypedef struct _xmlHashTable xmlRefTable;\ntypedef xmlRefTable *xmlRefTablePtr;\n\n/* Notation */\nXMLPUBFUN xmlNotationPtr XMLCALL\n\t\txmlAddNotationDecl\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDtdPtr dtd,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *PublicID,\n\t\t\t\t\t const xmlChar *SystemID);\n#ifdef LIBXML_TREE_ENABLED\nXMLPUBFUN xmlNotationTablePtr XMLCALL\n\t\txmlCopyNotationTable\t(xmlNotationTablePtr table);\n#endif /* LIBXML_TREE_ENABLED */\nXMLPUBFUN void XMLCALL\n\t\txmlFreeNotationTable\t(xmlNotationTablePtr table);\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlDumpNotationDecl\t(xmlBufferPtr buf,\n\t\t\t\t\t xmlNotationPtr nota);\nXMLPUBFUN void XMLCALL\n\t\txmlDumpNotationTable\t(xmlBufferPtr buf,\n\t\t\t\t\t xmlNotationTablePtr table);\n#endif /* LIBXML_OUTPUT_ENABLED */\n\n/* Element Content */\n/* the non Doc version are being deprecated */\nXMLPUBFUN xmlElementContentPtr XMLCALL\n\t\txmlNewElementContent\t(const xmlChar *name,\n\t\t\t\t\t xmlElementContentType type);\nXMLPUBFUN xmlElementContentPtr XMLCALL\n\t\txmlCopyElementContent\t(xmlElementContentPtr content);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeElementContent\t(xmlElementContentPtr cur);\n/* the new versions with doc argument */\nXMLPUBFUN xmlElementContentPtr XMLCALL\n\t\txmlNewDocElementContent\t(xmlDocPtr doc,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t xmlElementContentType type);\nXMLPUBFUN xmlElementContentPtr XMLCALL\n\t\txmlCopyDocElementContent(xmlDocPtr doc,\n\t\t\t\t\t xmlElementContentPtr content);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeDocElementContent(xmlDocPtr doc,\n\t\t\t\t\t xmlElementContentPtr cur);\nXMLPUBFUN void XMLCALL\n\t\txmlSnprintfElementContent(char *buf,\n\t\t\t\t\t int size,\n\t                                 xmlElementContentPtr content,\n\t\t\t\t\t int englob);\n#ifdef LIBXML_OUTPUT_ENABLED\n/* DEPRECATED */\nXMLPUBFUN void XMLCALL\n\t\txmlSprintfElementContent(char *buf,\n\t                                 xmlElementContentPtr content,\n\t\t\t\t\t int englob);\n#endif /* LIBXML_OUTPUT_ENABLED */\n/* DEPRECATED */\n\n/* Element */\nXMLPUBFUN xmlElementPtr XMLCALL\n\t\txmlAddElementDecl\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDtdPtr dtd,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t xmlElementTypeVal type,\n\t\t\t\t\t xmlElementContentPtr content);\n#ifdef LIBXML_TREE_ENABLED\nXMLPUBFUN xmlElementTablePtr XMLCALL\n\t\txmlCopyElementTable\t(xmlElementTablePtr table);\n#endif /* LIBXML_TREE_ENABLED */\nXMLPUBFUN void XMLCALL\n\t\txmlFreeElementTable\t(xmlElementTablePtr table);\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlDumpElementTable\t(xmlBufferPtr buf,\n\t\t\t\t\t xmlElementTablePtr table);\nXMLPUBFUN void XMLCALL\n\t\txmlDumpElementDecl\t(xmlBufferPtr buf,\n\t\t\t\t\t xmlElementPtr elem);\n#endif /* LIBXML_OUTPUT_ENABLED */\n\n/* Enumeration */\nXMLPUBFUN xmlEnumerationPtr XMLCALL\n\t\txmlCreateEnumeration\t(const xmlChar *name);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeEnumeration\t(xmlEnumerationPtr cur);\n#ifdef LIBXML_TREE_ENABLED\nXMLPUBFUN xmlEnumerationPtr XMLCALL\n\t\txmlCopyEnumeration\t(xmlEnumerationPtr cur);\n#endif /* LIBXML_TREE_ENABLED */\n\n/* Attribute */\nXMLPUBFUN xmlAttributePtr XMLCALL\n\t\txmlAddAttributeDecl\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDtdPtr dtd,\n\t\t\t\t\t const xmlChar *elem,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *ns,\n\t\t\t\t\t xmlAttributeType type,\n\t\t\t\t\t xmlAttributeDefault def,\n\t\t\t\t\t const xmlChar *defaultValue,\n\t\t\t\t\t xmlEnumerationPtr tree);\n#ifdef LIBXML_TREE_ENABLED\nXMLPUBFUN xmlAttributeTablePtr XMLCALL\n\t\txmlCopyAttributeTable  (xmlAttributeTablePtr table);\n#endif /* LIBXML_TREE_ENABLED */\nXMLPUBFUN void XMLCALL\n\t\txmlFreeAttributeTable  (xmlAttributeTablePtr table);\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlDumpAttributeTable  (xmlBufferPtr buf,\n\t\t\t\t\txmlAttributeTablePtr table);\nXMLPUBFUN void XMLCALL\n\t\txmlDumpAttributeDecl   (xmlBufferPtr buf,\n\t\t\t\t\txmlAttributePtr attr);\n#endif /* LIBXML_OUTPUT_ENABLED */\n\n/* IDs */\nXMLPUBFUN xmlIDPtr XMLCALL\n\t\txmlAddID\t       (xmlValidCtxtPtr ctxt,\n\t\t\t\t\txmlDocPtr doc,\n\t\t\t\t\tconst xmlChar *value,\n\t\t\t\t\txmlAttrPtr attr);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeIDTable\t       (xmlIDTablePtr table);\nXMLPUBFUN xmlAttrPtr XMLCALL\n\t\txmlGetID\t       (xmlDocPtr doc,\n\t\t\t\t\tconst xmlChar *ID);\nXMLPUBFUN int XMLCALL\n\t\txmlIsID\t\t       (xmlDocPtr doc,\n\t\t\t\t\txmlNodePtr elem,\n\t\t\t\t\txmlAttrPtr attr);\nXMLPUBFUN int XMLCALL\n\t\txmlRemoveID\t       (xmlDocPtr doc,\n\t\t\t\t\txmlAttrPtr attr);\n\n/* IDREFs */\nXMLPUBFUN xmlRefPtr XMLCALL\n\t\txmlAddRef\t       (xmlValidCtxtPtr ctxt,\n\t\t\t\t\txmlDocPtr doc,\n\t\t\t\t\tconst xmlChar *value,\n\t\t\t\t\txmlAttrPtr attr);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeRefTable\t       (xmlRefTablePtr table);\nXMLPUBFUN int XMLCALL\n\t\txmlIsRef\t       (xmlDocPtr doc,\n\t\t\t\t\txmlNodePtr elem,\n\t\t\t\t\txmlAttrPtr attr);\nXMLPUBFUN int XMLCALL\n\t\txmlRemoveRef\t       (xmlDocPtr doc,\n\t\t\t\t\txmlAttrPtr attr);\nXMLPUBFUN xmlListPtr XMLCALL\n\t\txmlGetRefs\t       (xmlDocPtr doc,\n\t\t\t\t\tconst xmlChar *ID);\n\n/**\n * The public function calls related to validity checking.\n */\n#ifdef LIBXML_VALID_ENABLED\n/* Allocate/Release Validation Contexts */\nXMLPUBFUN xmlValidCtxtPtr XMLCALL\n\t\txmlNewValidCtxt(void);\nXMLPUBFUN void XMLCALL\n\t\txmlFreeValidCtxt(xmlValidCtxtPtr);\n\nXMLPUBFUN int XMLCALL\n\t\txmlValidateRoot\t\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateElementDecl\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t                         xmlElementPtr elem);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlValidNormalizeAttributeValue(xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr elem,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlValidCtxtNormalizeAttributeValue(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr elem,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateAttributeDecl(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t                         xmlAttributePtr attr);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateAttributeValue(xmlAttributeType type,\n\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateNotationDecl\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t                         xmlNotationPtr nota);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateDtd\t\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlDtdPtr dtd);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateDtdFinal\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateDocument\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateElement\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr elem);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateOneElement\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t                         xmlNodePtr elem);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateOneAttribute\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr\telem,\n\t\t\t\t\t xmlAttrPtr attr,\n\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateOneNamespace\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr elem,\n\t\t\t\t\t const xmlChar *prefix,\n\t\t\t\t\t xmlNsPtr ns,\n\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateDocumentFinal(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc);\n#endif /* LIBXML_VALID_ENABLED */\n\n#if defined(LIBXML_VALID_ENABLED) || defined(LIBXML_SCHEMAS_ENABLED)\nXMLPUBFUN int XMLCALL\n\t\txmlValidateNotationUse\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t const xmlChar *notationName);\n#endif /* LIBXML_VALID_ENABLED or LIBXML_SCHEMAS_ENABLED */\n\nXMLPUBFUN int XMLCALL\n\t\txmlIsMixedElement\t(xmlDocPtr doc,\n\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlAttributePtr XMLCALL\n\t\txmlGetDtdAttrDesc\t(xmlDtdPtr dtd,\n\t\t\t\t\t const xmlChar *elem,\n\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlAttributePtr XMLCALL\n\t\txmlGetDtdQAttrDesc\t(xmlDtdPtr dtd,\n\t\t\t\t\t const xmlChar *elem,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *prefix);\nXMLPUBFUN xmlNotationPtr XMLCALL\n\t\txmlGetDtdNotationDesc\t(xmlDtdPtr dtd,\n\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlElementPtr XMLCALL\n\t\txmlGetDtdQElementDesc\t(xmlDtdPtr dtd,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *prefix);\nXMLPUBFUN xmlElementPtr XMLCALL\n\t\txmlGetDtdElementDesc\t(xmlDtdPtr dtd,\n\t\t\t\t\t const xmlChar *name);\n\n#ifdef LIBXML_VALID_ENABLED\n\nXMLPUBFUN int XMLCALL\n\t\txmlValidGetPotentialChildren(xmlElementContent *ctree,\n\t\t\t\t\t const xmlChar **names,\n\t\t\t\t\t int *len,\n\t\t\t\t\t int max);\n\nXMLPUBFUN int XMLCALL\n\t\txmlValidGetValidElements(xmlNode *prev,\n\t\t\t\t\t xmlNode *next,\n\t\t\t\t\t const xmlChar **names,\n\t\t\t\t\t int max);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateNameValue\t(const xmlChar *value);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateNamesValue\t(const xmlChar *value);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateNmtokenValue\t(const xmlChar *value);\nXMLPUBFUN int XMLCALL\n\t\txmlValidateNmtokensValue(const xmlChar *value);\n\n#ifdef LIBXML_REGEXP_ENABLED\n/*\n * Validation based on the regexp support\n */\nXMLPUBFUN int XMLCALL\n\t\txmlValidBuildContentModel(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlElementPtr elem);\n\nXMLPUBFUN int XMLCALL\n\t\txmlValidatePushElement\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr elem,\n\t\t\t\t\t const xmlChar *qname);\nXMLPUBFUN int XMLCALL\n\t\txmlValidatePushCData\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t const xmlChar *data,\n\t\t\t\t\t int len);\nXMLPUBFUN int XMLCALL\n\t\txmlValidatePopElement\t(xmlValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr elem,\n\t\t\t\t\t const xmlChar *qname);\n#endif /* LIBXML_REGEXP_ENABLED */\n#endif /* LIBXML_VALID_ENABLED */\n#ifdef __cplusplus\n}\n#endif\n#endif /* __XML_VALID_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xinclude.h",
    "content": "/*\n * Summary: implementation of XInclude\n * Description: API to handle XInclude processing,\n * implements the\n * World Wide Web Consortium Last Call Working Draft 10 November 2003\n * http://www.w3.org/TR/2003/WD-xinclude-20031110\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XINCLUDE_H__\n#define __XML_XINCLUDE_H__\n\n#include <libxml/xmlversion.h>\n#include <libxml/tree.h>\n\n#ifdef LIBXML_XINCLUDE_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * XINCLUDE_NS:\n *\n * Macro defining the Xinclude namespace: http://www.w3.org/2003/XInclude\n */\n#define XINCLUDE_NS (const xmlChar *) \"http://www.w3.org/2003/XInclude\"\n/**\n * XINCLUDE_OLD_NS:\n *\n * Macro defining the draft Xinclude namespace: http://www.w3.org/2001/XInclude\n */\n#define XINCLUDE_OLD_NS (const xmlChar *) \"http://www.w3.org/2001/XInclude\"\n/**\n * XINCLUDE_NODE:\n *\n * Macro defining \"include\"\n */\n#define XINCLUDE_NODE (const xmlChar *) \"include\"\n/**\n * XINCLUDE_FALLBACK:\n *\n * Macro defining \"fallback\"\n */\n#define XINCLUDE_FALLBACK (const xmlChar *) \"fallback\"\n/**\n * XINCLUDE_HREF:\n *\n * Macro defining \"href\"\n */\n#define XINCLUDE_HREF (const xmlChar *) \"href\"\n/**\n * XINCLUDE_PARSE:\n *\n * Macro defining \"parse\"\n */\n#define XINCLUDE_PARSE (const xmlChar *) \"parse\"\n/**\n * XINCLUDE_PARSE_XML:\n *\n * Macro defining \"xml\"\n */\n#define XINCLUDE_PARSE_XML (const xmlChar *) \"xml\"\n/**\n * XINCLUDE_PARSE_TEXT:\n *\n * Macro defining \"text\"\n */\n#define XINCLUDE_PARSE_TEXT (const xmlChar *) \"text\"\n/**\n * XINCLUDE_PARSE_ENCODING:\n *\n * Macro defining \"encoding\"\n */\n#define XINCLUDE_PARSE_ENCODING (const xmlChar *) \"encoding\"\n/**\n * XINCLUDE_PARSE_XPOINTER:\n *\n * Macro defining \"xpointer\"\n */\n#define XINCLUDE_PARSE_XPOINTER (const xmlChar *) \"xpointer\"\n\ntypedef struct _xmlXIncludeCtxt xmlXIncludeCtxt;\ntypedef xmlXIncludeCtxt *xmlXIncludeCtxtPtr;\n\n/*\n * standalone processing\n */\nXMLPUBFUN int XMLCALL\n\t\txmlXIncludeProcess\t(xmlDocPtr doc);\nXMLPUBFUN int XMLCALL\n\t\txmlXIncludeProcessFlags\t(xmlDocPtr doc,\n\t\t\t\t\t int flags);\nXMLPUBFUN int XMLCALL\n\t\txmlXIncludeProcessFlagsData(xmlDocPtr doc,\n\t\t\t\t\t int flags,\n\t\t\t\t\t void *data);\nXMLPUBFUN int XMLCALL\n                xmlXIncludeProcessTreeFlagsData(xmlNodePtr tree,\n                                         int flags,\n                                         void *data);\nXMLPUBFUN int XMLCALL\n\t\txmlXIncludeProcessTree\t(xmlNodePtr tree);\nXMLPUBFUN int XMLCALL\n\t\txmlXIncludeProcessTreeFlags(xmlNodePtr tree,\n\t\t\t\t\t int flags);\n/*\n * contextual processing\n */\nXMLPUBFUN xmlXIncludeCtxtPtr XMLCALL\n\t\txmlXIncludeNewContext\t(xmlDocPtr doc);\nXMLPUBFUN int XMLCALL\n\t\txmlXIncludeSetFlags\t(xmlXIncludeCtxtPtr ctxt,\n\t\t\t\t\t int flags);\nXMLPUBFUN void XMLCALL\n\t\txmlXIncludeFreeContext\t(xmlXIncludeCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\txmlXIncludeProcessNode\t(xmlXIncludeCtxtPtr ctxt,\n\t\t\t\t\t xmlNodePtr tree);\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_XINCLUDE_ENABLED */\n\n#endif /* __XML_XINCLUDE_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xlink.h",
    "content": "/*\n * Summary: unfinished XLink detection module\n * Description: unfinished XLink detection module\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XLINK_H__\n#define __XML_XLINK_H__\n\n#include <libxml/xmlversion.h>\n#include <libxml/tree.h>\n\n#ifdef LIBXML_XPTR_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * Various defines for the various Link properties.\n *\n * NOTE: the link detection layer will try to resolve QName expansion\n *       of namespaces. If \"foo\" is the prefix for \"http://foo.com/\"\n *       then the link detection layer will expand role=\"foo:myrole\"\n *       to \"http://foo.com/:myrole\".\n * NOTE: the link detection layer will expand URI-Refences found on\n *       href attributes by using the base mechanism if found.\n */\ntypedef xmlChar *xlinkHRef;\ntypedef xmlChar *xlinkRole;\ntypedef xmlChar *xlinkTitle;\n\ntypedef enum {\n    XLINK_TYPE_NONE = 0,\n    XLINK_TYPE_SIMPLE,\n    XLINK_TYPE_EXTENDED,\n    XLINK_TYPE_EXTENDED_SET\n} xlinkType;\n\ntypedef enum {\n    XLINK_SHOW_NONE = 0,\n    XLINK_SHOW_NEW,\n    XLINK_SHOW_EMBED,\n    XLINK_SHOW_REPLACE\n} xlinkShow;\n\ntypedef enum {\n    XLINK_ACTUATE_NONE = 0,\n    XLINK_ACTUATE_AUTO,\n    XLINK_ACTUATE_ONREQUEST\n} xlinkActuate;\n\n/**\n * xlinkNodeDetectFunc:\n * @ctx:  user data pointer\n * @node:  the node to check\n *\n * This is the prototype for the link detection routine.\n * It calls the default link detection callbacks upon link detection.\n */\ntypedef void (*xlinkNodeDetectFunc) (void *ctx, xmlNodePtr node);\n\n/*\n * The link detection module interact with the upper layers using\n * a set of callback registered at parsing time.\n */\n\n/**\n * xlinkSimpleLinkFunk:\n * @ctx:  user data pointer\n * @node:  the node carrying the link\n * @href:  the target of the link\n * @role:  the role string\n * @title:  the link title\n *\n * This is the prototype for a simple link detection callback.\n */\ntypedef void\n(*xlinkSimpleLinkFunk)\t(void *ctx,\n\t\t\t xmlNodePtr node,\n\t\t\t const xlinkHRef href,\n\t\t\t const xlinkRole role,\n\t\t\t const xlinkTitle title);\n\n/**\n * xlinkExtendedLinkFunk:\n * @ctx:  user data pointer\n * @node:  the node carrying the link\n * @nbLocators: the number of locators detected on the link\n * @hrefs:  pointer to the array of locator hrefs\n * @roles:  pointer to the array of locator roles\n * @nbArcs: the number of arcs detected on the link\n * @from:  pointer to the array of source roles found on the arcs\n * @to:  pointer to the array of target roles found on the arcs\n * @show:  array of values for the show attributes found on the arcs\n * @actuate:  array of values for the actuate attributes found on the arcs\n * @nbTitles: the number of titles detected on the link\n * @title:  array of titles detected on the link\n * @langs:  array of xml:lang values for the titles\n *\n * This is the prototype for a extended link detection callback.\n */\ntypedef void\n(*xlinkExtendedLinkFunk)(void *ctx,\n\t\t\t xmlNodePtr node,\n\t\t\t int nbLocators,\n\t\t\t const xlinkHRef *hrefs,\n\t\t\t const xlinkRole *roles,\n\t\t\t int nbArcs,\n\t\t\t const xlinkRole *from,\n\t\t\t const xlinkRole *to,\n\t\t\t xlinkShow *show,\n\t\t\t xlinkActuate *actuate,\n\t\t\t int nbTitles,\n\t\t\t const xlinkTitle *titles,\n\t\t\t const xmlChar **langs);\n\n/**\n * xlinkExtendedLinkSetFunk:\n * @ctx:  user data pointer\n * @node:  the node carrying the link\n * @nbLocators: the number of locators detected on the link\n * @hrefs:  pointer to the array of locator hrefs\n * @roles:  pointer to the array of locator roles\n * @nbTitles: the number of titles detected on the link\n * @title:  array of titles detected on the link\n * @langs:  array of xml:lang values for the titles\n *\n * This is the prototype for a extended link set detection callback.\n */\ntypedef void\n(*xlinkExtendedLinkSetFunk)\t(void *ctx,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t int nbLocators,\n\t\t\t\t const xlinkHRef *hrefs,\n\t\t\t\t const xlinkRole *roles,\n\t\t\t\t int nbTitles,\n\t\t\t\t const xlinkTitle *titles,\n\t\t\t\t const xmlChar **langs);\n\n/**\n * This is the structure containing a set of Links detection callbacks.\n *\n * There is no default xlink callbacks, if one want to get link\n * recognition activated, those call backs must be provided before parsing.\n */\ntypedef struct _xlinkHandler xlinkHandler;\ntypedef xlinkHandler *xlinkHandlerPtr;\nstruct _xlinkHandler {\n    xlinkSimpleLinkFunk simple;\n    xlinkExtendedLinkFunk extended;\n    xlinkExtendedLinkSetFunk set;\n};\n\n/*\n * The default detection routine, can be overridden, they call the default\n * detection callbacks.\n */\n\nXMLPUBFUN xlinkNodeDetectFunc XMLCALL\n\t\txlinkGetDefaultDetect\t(void);\nXMLPUBFUN void XMLCALL\n\t\txlinkSetDefaultDetect\t(xlinkNodeDetectFunc func);\n\n/*\n * Routines to set/get the default handlers.\n */\nXMLPUBFUN xlinkHandlerPtr XMLCALL\n\t\txlinkGetDefaultHandler\t(void);\nXMLPUBFUN void XMLCALL\n\t\txlinkSetDefaultHandler\t(xlinkHandlerPtr handler);\n\n/*\n * Link detection module itself.\n */\nXMLPUBFUN xlinkType XMLCALL\n\t\txlinkIsLink\t\t(xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr node);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_XPTR_ENABLED */\n\n#endif /* __XML_XLINK_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlIO.h",
    "content": "/*\n * Summary: interface for the I/O interfaces used by the parser\n * Description: interface for the I/O interfaces used by the parser\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_IO_H__\n#define __XML_IO_H__\n\n#include <stdio.h>\n#include <libxml/xmlversion.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * Those are the functions and datatypes for the parser input\n * I/O structures.\n */\n\n/**\n * xmlInputMatchCallback:\n * @filename: the filename or URI\n *\n * Callback used in the I/O Input API to detect if the current handler\n * can provide input fonctionnalities for this resource.\n *\n * Returns 1 if yes and 0 if another Input module should be used\n */\ntypedef int (XMLCALL *xmlInputMatchCallback) (char const *filename);\n/**\n * xmlInputOpenCallback:\n * @filename: the filename or URI\n *\n * Callback used in the I/O Input API to open the resource\n *\n * Returns an Input context or NULL in case or error\n */\ntypedef void * (XMLCALL *xmlInputOpenCallback) (char const *filename);\n/**\n * xmlInputReadCallback:\n * @context:  an Input context\n * @buffer:  the buffer to store data read\n * @len:  the length of the buffer in bytes\n *\n * Callback used in the I/O Input API to read the resource\n *\n * Returns the number of bytes read or -1 in case of error\n */\ntypedef int (XMLCALL *xmlInputReadCallback) (void * context, char * buffer, int len);\n/**\n * xmlInputCloseCallback:\n * @context:  an Input context\n *\n * Callback used in the I/O Input API to close the resource\n *\n * Returns 0 or -1 in case of error\n */\ntypedef int (XMLCALL *xmlInputCloseCallback) (void * context);\n\n#ifdef LIBXML_OUTPUT_ENABLED\n/*\n * Those are the functions and datatypes for the library output\n * I/O structures.\n */\n\n/**\n * xmlOutputMatchCallback:\n * @filename: the filename or URI\n *\n * Callback used in the I/O Output API to detect if the current handler\n * can provide output fonctionnalities for this resource.\n *\n * Returns 1 if yes and 0 if another Output module should be used\n */\ntypedef int (XMLCALL *xmlOutputMatchCallback) (char const *filename);\n/**\n * xmlOutputOpenCallback:\n * @filename: the filename or URI\n *\n * Callback used in the I/O Output API to open the resource\n *\n * Returns an Output context or NULL in case or error\n */\ntypedef void * (XMLCALL *xmlOutputOpenCallback) (char const *filename);\n/**\n * xmlOutputWriteCallback:\n * @context:  an Output context\n * @buffer:  the buffer of data to write\n * @len:  the length of the buffer in bytes\n *\n * Callback used in the I/O Output API to write to the resource\n *\n * Returns the number of bytes written or -1 in case of error\n */\ntypedef int (XMLCALL *xmlOutputWriteCallback) (void * context, const char * buffer,\n                                       int len);\n/**\n * xmlOutputCloseCallback:\n * @context:  an Output context\n *\n * Callback used in the I/O Output API to close the resource\n *\n * Returns 0 or -1 in case of error\n */\ntypedef int (XMLCALL *xmlOutputCloseCallback) (void * context);\n#endif /* LIBXML_OUTPUT_ENABLED */\n\n#ifdef __cplusplus\n}\n#endif\n\n#include <libxml/globals.h>\n#include <libxml/tree.h>\n#include <libxml/parser.h>\n#include <libxml/encoding.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\nstruct _xmlParserInputBuffer {\n    void*                  context;\n    xmlInputReadCallback   readcallback;\n    xmlInputCloseCallback  closecallback;\n\n    xmlCharEncodingHandlerPtr encoder; /* I18N conversions to UTF-8 */\n\n    xmlBufPtr buffer;    /* Local buffer encoded in UTF-8 */\n    xmlBufPtr raw;       /* if encoder != NULL buffer for raw input */\n    int\tcompressed;\t    /* -1=unknown, 0=not compressed, 1=compressed */\n    int error;\n    unsigned long rawconsumed;/* amount consumed from raw */\n};\n\n\n#ifdef LIBXML_OUTPUT_ENABLED\nstruct _xmlOutputBuffer {\n    void*                   context;\n    xmlOutputWriteCallback  writecallback;\n    xmlOutputCloseCallback  closecallback;\n\n    xmlCharEncodingHandlerPtr encoder; /* I18N conversions to UTF-8 */\n\n    xmlBufPtr buffer;    /* Local buffer encoded in UTF-8 or ISOLatin */\n    xmlBufPtr conv;      /* if encoder != NULL buffer for output */\n    int written;            /* total number of byte written */\n    int error;\n};\n#endif /* LIBXML_OUTPUT_ENABLED */\n\n/*\n * Interfaces for input\n */\nXMLPUBFUN void XMLCALL\n\txmlCleanupInputCallbacks\t\t(void);\n\nXMLPUBFUN int XMLCALL\n\txmlPopInputCallbacks\t\t\t(void);\n\nXMLPUBFUN void XMLCALL\n\txmlRegisterDefaultInputCallbacks\t(void);\nXMLPUBFUN xmlParserInputBufferPtr XMLCALL\n\txmlAllocParserInputBuffer\t\t(xmlCharEncoding enc);\n\nXMLPUBFUN xmlParserInputBufferPtr XMLCALL\n\txmlParserInputBufferCreateFilename\t(const char *URI,\n                                                 xmlCharEncoding enc);\nXMLPUBFUN xmlParserInputBufferPtr XMLCALL\n\txmlParserInputBufferCreateFile\t\t(FILE *file,\n                                                 xmlCharEncoding enc);\nXMLPUBFUN xmlParserInputBufferPtr XMLCALL\n\txmlParserInputBufferCreateFd\t\t(int fd,\n\t                                         xmlCharEncoding enc);\nXMLPUBFUN xmlParserInputBufferPtr XMLCALL\n\txmlParserInputBufferCreateMem\t\t(const char *mem, int size,\n\t                                         xmlCharEncoding enc);\nXMLPUBFUN xmlParserInputBufferPtr XMLCALL\n\txmlParserInputBufferCreateStatic\t(const char *mem, int size,\n\t                                         xmlCharEncoding enc);\nXMLPUBFUN xmlParserInputBufferPtr XMLCALL\n\txmlParserInputBufferCreateIO\t\t(xmlInputReadCallback   ioread,\n\t\t\t\t\t\t xmlInputCloseCallback  ioclose,\n\t\t\t\t\t\t void *ioctx,\n\t                                         xmlCharEncoding enc);\nXMLPUBFUN int XMLCALL\n\txmlParserInputBufferRead\t\t(xmlParserInputBufferPtr in,\n\t\t\t\t\t\t int len);\nXMLPUBFUN int XMLCALL\n\txmlParserInputBufferGrow\t\t(xmlParserInputBufferPtr in,\n\t\t\t\t\t\t int len);\nXMLPUBFUN int XMLCALL\n\txmlParserInputBufferPush\t\t(xmlParserInputBufferPtr in,\n\t\t\t\t\t\t int len,\n\t\t\t\t\t\t const char *buf);\nXMLPUBFUN void XMLCALL\n\txmlFreeParserInputBuffer\t\t(xmlParserInputBufferPtr in);\nXMLPUBFUN char * XMLCALL\n\txmlParserGetDirectory\t\t\t(const char *filename);\n\nXMLPUBFUN int XMLCALL\n\txmlRegisterInputCallbacks\t\t(xmlInputMatchCallback matchFunc,\n\t\t\t\t\t\t xmlInputOpenCallback openFunc,\n\t\t\t\t\t\t xmlInputReadCallback readFunc,\n\t\t\t\t\t\t xmlInputCloseCallback closeFunc);\n\nxmlParserInputBufferPtr\n\t__xmlParserInputBufferCreateFilename(const char *URI,\n\t\t\t\t\t\txmlCharEncoding enc);\n\n#ifdef LIBXML_OUTPUT_ENABLED\n/*\n * Interfaces for output\n */\nXMLPUBFUN void XMLCALL\n\txmlCleanupOutputCallbacks\t\t(void);\nXMLPUBFUN void XMLCALL\n\txmlRegisterDefaultOutputCallbacks(void);\nXMLPUBFUN xmlOutputBufferPtr XMLCALL\n\txmlAllocOutputBuffer\t\t(xmlCharEncodingHandlerPtr encoder);\n\nXMLPUBFUN xmlOutputBufferPtr XMLCALL\n\txmlOutputBufferCreateFilename\t(const char *URI,\n\t\t\t\t\t xmlCharEncodingHandlerPtr encoder,\n\t\t\t\t\t int compression);\n\nXMLPUBFUN xmlOutputBufferPtr XMLCALL\n\txmlOutputBufferCreateFile\t(FILE *file,\n\t\t\t\t\t xmlCharEncodingHandlerPtr encoder);\n\nXMLPUBFUN xmlOutputBufferPtr XMLCALL\n\txmlOutputBufferCreateBuffer\t(xmlBufferPtr buffer,\n\t\t\t\t\t xmlCharEncodingHandlerPtr encoder);\n\nXMLPUBFUN xmlOutputBufferPtr XMLCALL\n\txmlOutputBufferCreateFd\t\t(int fd,\n\t\t\t\t\t xmlCharEncodingHandlerPtr encoder);\n\nXMLPUBFUN xmlOutputBufferPtr XMLCALL\n\txmlOutputBufferCreateIO\t\t(xmlOutputWriteCallback   iowrite,\n\t\t\t\t\t xmlOutputCloseCallback  ioclose,\n\t\t\t\t\t void *ioctx,\n\t\t\t\t\t xmlCharEncodingHandlerPtr encoder);\n\n/* Couple of APIs to get the output without digging into the buffers */\nXMLPUBFUN const xmlChar * XMLCALL\n        xmlOutputBufferGetContent       (xmlOutputBufferPtr out);\nXMLPUBFUN size_t XMLCALL\n        xmlOutputBufferGetSize          (xmlOutputBufferPtr out);\n\nXMLPUBFUN int XMLCALL\n\txmlOutputBufferWrite\t\t(xmlOutputBufferPtr out,\n\t\t\t\t\t int len,\n\t\t\t\t\t const char *buf);\nXMLPUBFUN int XMLCALL\n\txmlOutputBufferWriteString\t(xmlOutputBufferPtr out,\n\t\t\t\t\t const char *str);\nXMLPUBFUN int XMLCALL\n\txmlOutputBufferWriteEscape\t(xmlOutputBufferPtr out,\n\t\t\t\t\t const xmlChar *str,\n\t\t\t\t\t xmlCharEncodingOutputFunc escaping);\n\nXMLPUBFUN int XMLCALL\n\txmlOutputBufferFlush\t\t(xmlOutputBufferPtr out);\nXMLPUBFUN int XMLCALL\n\txmlOutputBufferClose\t\t(xmlOutputBufferPtr out);\n\nXMLPUBFUN int XMLCALL\n\txmlRegisterOutputCallbacks\t(xmlOutputMatchCallback matchFunc,\n\t\t\t\t\t xmlOutputOpenCallback openFunc,\n\t\t\t\t\t xmlOutputWriteCallback writeFunc,\n\t\t\t\t\t xmlOutputCloseCallback closeFunc);\n\nxmlOutputBufferPtr\n\t__xmlOutputBufferCreateFilename(const char *URI,\n                              xmlCharEncodingHandlerPtr encoder,\n                              int compression);\n\n#ifdef LIBXML_HTTP_ENABLED\n/*  This function only exists if HTTP support built into the library  */\nXMLPUBFUN void XMLCALL\n\txmlRegisterHTTPPostCallbacks\t(void );\n#endif /* LIBXML_HTTP_ENABLED */\n\n#endif /* LIBXML_OUTPUT_ENABLED */\n\nXMLPUBFUN xmlParserInputPtr XMLCALL\n\txmlCheckHTTPInput\t\t(xmlParserCtxtPtr ctxt,\n\t\t\t\t\t xmlParserInputPtr ret);\n\n/*\n * A predefined entity loader disabling network accesses\n */\nXMLPUBFUN xmlParserInputPtr XMLCALL\n\txmlNoNetExternalEntityLoader\t(const char *URL,\n\t\t\t\t\t const char *ID,\n\t\t\t\t\t xmlParserCtxtPtr ctxt);\n\n/*\n * xmlNormalizeWindowsPath is obsolete, don't use it.\n * Check xmlCanonicPath in uri.h for a better alternative.\n */\nXMLPUBFUN xmlChar * XMLCALL\n\txmlNormalizeWindowsPath\t\t(const xmlChar *path);\n\nXMLPUBFUN int XMLCALL\n\txmlCheckFilename\t\t(const char *path);\n/**\n * Default 'file://' protocol callbacks\n */\nXMLPUBFUN int XMLCALL\n\txmlFileMatch\t\t\t(const char *filename);\nXMLPUBFUN void * XMLCALL\n\txmlFileOpen\t\t\t(const char *filename);\nXMLPUBFUN int XMLCALL\n\txmlFileRead\t\t\t(void * context,\n\t\t\t\t\t char * buffer,\n\t\t\t\t\t int len);\nXMLPUBFUN int XMLCALL\n\txmlFileClose\t\t\t(void * context);\n\n/**\n * Default 'http://' protocol callbacks\n */\n#ifdef LIBXML_HTTP_ENABLED\nXMLPUBFUN int XMLCALL\n\txmlIOHTTPMatch\t\t\t(const char *filename);\nXMLPUBFUN void * XMLCALL\n\txmlIOHTTPOpen\t\t\t(const char *filename);\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN void * XMLCALL\n\txmlIOHTTPOpenW\t\t\t(const char * post_uri,\n\t\t\t\t\t int   compression );\n#endif /* LIBXML_OUTPUT_ENABLED */\nXMLPUBFUN int XMLCALL\n\txmlIOHTTPRead\t\t\t(void * context,\n\t\t\t\t\t char * buffer,\n\t\t\t\t\t int len);\nXMLPUBFUN int XMLCALL\n\txmlIOHTTPClose\t\t\t(void * context);\n#endif /* LIBXML_HTTP_ENABLED */\n\n/**\n * Default 'ftp://' protocol callbacks\n */\n#ifdef LIBXML_FTP_ENABLED\nXMLPUBFUN int XMLCALL\n\txmlIOFTPMatch\t\t\t(const char *filename);\nXMLPUBFUN void * XMLCALL\n\txmlIOFTPOpen\t\t\t(const char *filename);\nXMLPUBFUN int XMLCALL\n\txmlIOFTPRead\t\t\t(void * context,\n\t\t\t\t\t char * buffer,\n\t\t\t\t\t int len);\nXMLPUBFUN int XMLCALL\n\txmlIOFTPClose\t\t\t(void * context);\n#endif /* LIBXML_FTP_ENABLED */\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_IO_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlautomata.h",
    "content": "/*\n * Summary: API to build regexp automata\n * Description: the API to build regexp automata\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_AUTOMATA_H__\n#define __XML_AUTOMATA_H__\n\n#include <libxml/xmlversion.h>\n#include <libxml/tree.h>\n\n#ifdef LIBXML_REGEXP_ENABLED\n#ifdef LIBXML_AUTOMATA_ENABLED\n#include <libxml/xmlregexp.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * xmlAutomataPtr:\n *\n * A libxml automata description, It can be compiled into a regexp\n */\ntypedef struct _xmlAutomata xmlAutomata;\ntypedef xmlAutomata *xmlAutomataPtr;\n\n/**\n * xmlAutomataStatePtr:\n *\n * A state int the automata description,\n */\ntypedef struct _xmlAutomataState xmlAutomataState;\ntypedef xmlAutomataState *xmlAutomataStatePtr;\n\n/*\n * Building API\n */\nXMLPUBFUN xmlAutomataPtr XMLCALL\n\t\t    xmlNewAutomata\t\t(void);\nXMLPUBFUN void XMLCALL\n\t\t    xmlFreeAutomata\t\t(xmlAutomataPtr am);\n\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n\t\t    xmlAutomataGetInitState\t(xmlAutomataPtr am);\nXMLPUBFUN int XMLCALL\n\t\t    xmlAutomataSetFinalState\t(xmlAutomataPtr am,\n\t\t\t\t\t\t xmlAutomataStatePtr state);\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n\t\t    xmlAutomataNewState\t\t(xmlAutomataPtr am);\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n\t\t    xmlAutomataNewTransition\t(xmlAutomataPtr am,\n\t\t\t\t\t\t xmlAutomataStatePtr from,\n\t\t\t\t\t\t xmlAutomataStatePtr to,\n\t\t\t\t\t\t const xmlChar *token,\n\t\t\t\t\t\t void *data);\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n\t\t    xmlAutomataNewTransition2\t(xmlAutomataPtr am,\n\t\t\t\t\t\t xmlAutomataStatePtr from,\n\t\t\t\t\t\t xmlAutomataStatePtr to,\n\t\t\t\t\t\t const xmlChar *token,\n\t\t\t\t\t\t const xmlChar *token2,\n\t\t\t\t\t\t void *data);\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n                    xmlAutomataNewNegTrans\t(xmlAutomataPtr am,\n\t\t\t\t\t\t xmlAutomataStatePtr from,\n\t\t\t\t\t\t xmlAutomataStatePtr to,\n\t\t\t\t\t\t const xmlChar *token,\n\t\t\t\t\t\t const xmlChar *token2,\n\t\t\t\t\t\t void *data);\n\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n\t\t    xmlAutomataNewCountTrans\t(xmlAutomataPtr am,\n\t\t\t\t\t\t xmlAutomataStatePtr from,\n\t\t\t\t\t\t xmlAutomataStatePtr to,\n\t\t\t\t\t\t const xmlChar *token,\n\t\t\t\t\t\t int min,\n\t\t\t\t\t\t int max,\n\t\t\t\t\t\t void *data);\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n\t\t    xmlAutomataNewCountTrans2\t(xmlAutomataPtr am,\n\t\t\t\t\t\t xmlAutomataStatePtr from,\n\t\t\t\t\t\t xmlAutomataStatePtr to,\n\t\t\t\t\t\t const xmlChar *token,\n\t\t\t\t\t\t const xmlChar *token2,\n\t\t\t\t\t\t int min,\n\t\t\t\t\t\t int max,\n\t\t\t\t\t\t void *data);\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n\t\t    xmlAutomataNewOnceTrans\t(xmlAutomataPtr am,\n\t\t\t\t\t\t xmlAutomataStatePtr from,\n\t\t\t\t\t\t xmlAutomataStatePtr to,\n\t\t\t\t\t\t const xmlChar *token,\n\t\t\t\t\t\t int min,\n\t\t\t\t\t\t int max,\n\t\t\t\t\t\t void *data);\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n\t\t    xmlAutomataNewOnceTrans2\t(xmlAutomataPtr am,\n\t\t\t\t\t\t xmlAutomataStatePtr from,\n\t\t\t\t\t\t xmlAutomataStatePtr to,\n\t\t\t\t\t\t const xmlChar *token,\n\t\t\t\t\t\t const xmlChar *token2,\n\t\t\t\t\t\t int min,\n\t\t\t\t\t\t int max,\n\t\t\t\t\t\t void *data);\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n\t\t    xmlAutomataNewAllTrans\t(xmlAutomataPtr am,\n\t\t\t\t\t\t xmlAutomataStatePtr from,\n\t\t\t\t\t\t xmlAutomataStatePtr to,\n\t\t\t\t\t\t int lax);\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n\t\t    xmlAutomataNewEpsilon\t(xmlAutomataPtr am,\n\t\t\t\t\t\t xmlAutomataStatePtr from,\n\t\t\t\t\t\t xmlAutomataStatePtr to);\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n\t\t    xmlAutomataNewCountedTrans\t(xmlAutomataPtr am,\n\t\t\t\t\t\t xmlAutomataStatePtr from,\n\t\t\t\t\t\t xmlAutomataStatePtr to,\n\t\t\t\t\t\t int counter);\nXMLPUBFUN xmlAutomataStatePtr XMLCALL\n\t\t    xmlAutomataNewCounterTrans\t(xmlAutomataPtr am,\n\t\t\t\t\t\t xmlAutomataStatePtr from,\n\t\t\t\t\t\t xmlAutomataStatePtr to,\n\t\t\t\t\t\t int counter);\nXMLPUBFUN int XMLCALL\n\t\t    xmlAutomataNewCounter\t(xmlAutomataPtr am,\n\t\t\t\t\t\t int min,\n\t\t\t\t\t\t int max);\n\nXMLPUBFUN xmlRegexpPtr XMLCALL\n\t\t    xmlAutomataCompile\t\t(xmlAutomataPtr am);\nXMLPUBFUN int XMLCALL\n\t\t    xmlAutomataIsDeterminist\t(xmlAutomataPtr am);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_AUTOMATA_ENABLED */\n#endif /* LIBXML_REGEXP_ENABLED */\n\n#endif /* __XML_AUTOMATA_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlerror.h",
    "content": "/*\n * Summary: error handling\n * Description: the API used to report errors\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#include <libxml/parser.h>\n\n#ifndef __XML_ERROR_H__\n#define __XML_ERROR_H__\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * xmlErrorLevel:\n *\n * Indicates the level of an error\n */\ntypedef enum {\n    XML_ERR_NONE = 0,\n    XML_ERR_WARNING = 1,\t/* A simple warning */\n    XML_ERR_ERROR = 2,\t\t/* A recoverable error */\n    XML_ERR_FATAL = 3\t\t/* A fatal error */\n} xmlErrorLevel;\n\n/**\n * xmlErrorDomain:\n *\n * Indicates where an error may have come from\n */\ntypedef enum {\n    XML_FROM_NONE = 0,\n    XML_FROM_PARSER,\t/* The XML parser */\n    XML_FROM_TREE,\t/* The tree module */\n    XML_FROM_NAMESPACE,\t/* The XML Namespace module */\n    XML_FROM_DTD,\t/* The XML DTD validation with parser context*/\n    XML_FROM_HTML,\t/* The HTML parser */\n    XML_FROM_MEMORY,\t/* The memory allocator */\n    XML_FROM_OUTPUT,\t/* The serialization code */\n    XML_FROM_IO,\t/* The Input/Output stack */\n    XML_FROM_FTP,\t/* The FTP module */\n    XML_FROM_HTTP,\t/* The HTTP module */\n    XML_FROM_XINCLUDE,\t/* The XInclude processing */\n    XML_FROM_XPATH,\t/* The XPath module */\n    XML_FROM_XPOINTER,\t/* The XPointer module */\n    XML_FROM_REGEXP,\t/* The regular expressions module */\n    XML_FROM_DATATYPE,\t/* The W3C XML Schemas Datatype module */\n    XML_FROM_SCHEMASP,\t/* The W3C XML Schemas parser module */\n    XML_FROM_SCHEMASV,\t/* The W3C XML Schemas validation module */\n    XML_FROM_RELAXNGP,\t/* The Relax-NG parser module */\n    XML_FROM_RELAXNGV,\t/* The Relax-NG validator module */\n    XML_FROM_CATALOG,\t/* The Catalog module */\n    XML_FROM_C14N,\t/* The Canonicalization module */\n    XML_FROM_XSLT,\t/* The XSLT engine from libxslt */\n    XML_FROM_VALID,\t/* The XML DTD validation with valid context */\n    XML_FROM_CHECK,\t/* The error checking module */\n    XML_FROM_WRITER,\t/* The xmlwriter module */\n    XML_FROM_MODULE,\t/* The dynamically loaded module module*/\n    XML_FROM_I18N,\t/* The module handling character conversion */\n    XML_FROM_SCHEMATRONV,/* The Schematron validator module */\n    XML_FROM_BUFFER,    /* The buffers module */\n    XML_FROM_URI        /* The URI module */\n} xmlErrorDomain;\n\n/**\n * xmlError:\n *\n * An XML Error instance.\n */\n\ntypedef struct _xmlError xmlError;\ntypedef xmlError *xmlErrorPtr;\nstruct _xmlError {\n    int\t\tdomain;\t/* What part of the library raised this error */\n    int\t\tcode;\t/* The error code, e.g. an xmlParserError */\n    char       *message;/* human-readable informative error message */\n    xmlErrorLevel level;/* how consequent is the error */\n    char       *file;\t/* the filename */\n    int\t\tline;\t/* the line number if available */\n    char       *str1;\t/* extra string information */\n    char       *str2;\t/* extra string information */\n    char       *str3;\t/* extra string information */\n    int\t\tint1;\t/* extra number information */\n    int\t\tint2;\t/* error column # or 0 if N/A (todo: rename field when we would brk ABI) */\n    void       *ctxt;   /* the parser context if available */\n    void       *node;   /* the node in the tree */\n};\n\n/**\n * xmlParserError:\n *\n * This is an error that the XML (or HTML) parser can generate\n */\ntypedef enum {\n    XML_ERR_OK = 0,\n    XML_ERR_INTERNAL_ERROR, /* 1 */\n    XML_ERR_NO_MEMORY, /* 2 */\n    XML_ERR_DOCUMENT_START, /* 3 */\n    XML_ERR_DOCUMENT_EMPTY, /* 4 */\n    XML_ERR_DOCUMENT_END, /* 5 */\n    XML_ERR_INVALID_HEX_CHARREF, /* 6 */\n    XML_ERR_INVALID_DEC_CHARREF, /* 7 */\n    XML_ERR_INVALID_CHARREF, /* 8 */\n    XML_ERR_INVALID_CHAR, /* 9 */\n    XML_ERR_CHARREF_AT_EOF, /* 10 */\n    XML_ERR_CHARREF_IN_PROLOG, /* 11 */\n    XML_ERR_CHARREF_IN_EPILOG, /* 12 */\n    XML_ERR_CHARREF_IN_DTD, /* 13 */\n    XML_ERR_ENTITYREF_AT_EOF, /* 14 */\n    XML_ERR_ENTITYREF_IN_PROLOG, /* 15 */\n    XML_ERR_ENTITYREF_IN_EPILOG, /* 16 */\n    XML_ERR_ENTITYREF_IN_DTD, /* 17 */\n    XML_ERR_PEREF_AT_EOF, /* 18 */\n    XML_ERR_PEREF_IN_PROLOG, /* 19 */\n    XML_ERR_PEREF_IN_EPILOG, /* 20 */\n    XML_ERR_PEREF_IN_INT_SUBSET, /* 21 */\n    XML_ERR_ENTITYREF_NO_NAME, /* 22 */\n    XML_ERR_ENTITYREF_SEMICOL_MISSING, /* 23 */\n    XML_ERR_PEREF_NO_NAME, /* 24 */\n    XML_ERR_PEREF_SEMICOL_MISSING, /* 25 */\n    XML_ERR_UNDECLARED_ENTITY, /* 26 */\n    XML_WAR_UNDECLARED_ENTITY, /* 27 */\n    XML_ERR_UNPARSED_ENTITY, /* 28 */\n    XML_ERR_ENTITY_IS_EXTERNAL, /* 29 */\n    XML_ERR_ENTITY_IS_PARAMETER, /* 30 */\n    XML_ERR_UNKNOWN_ENCODING, /* 31 */\n    XML_ERR_UNSUPPORTED_ENCODING, /* 32 */\n    XML_ERR_STRING_NOT_STARTED, /* 33 */\n    XML_ERR_STRING_NOT_CLOSED, /* 34 */\n    XML_ERR_NS_DECL_ERROR, /* 35 */\n    XML_ERR_ENTITY_NOT_STARTED, /* 36 */\n    XML_ERR_ENTITY_NOT_FINISHED, /* 37 */\n    XML_ERR_LT_IN_ATTRIBUTE, /* 38 */\n    XML_ERR_ATTRIBUTE_NOT_STARTED, /* 39 */\n    XML_ERR_ATTRIBUTE_NOT_FINISHED, /* 40 */\n    XML_ERR_ATTRIBUTE_WITHOUT_VALUE, /* 41 */\n    XML_ERR_ATTRIBUTE_REDEFINED, /* 42 */\n    XML_ERR_LITERAL_NOT_STARTED, /* 43 */\n    XML_ERR_LITERAL_NOT_FINISHED, /* 44 */\n    XML_ERR_COMMENT_NOT_FINISHED, /* 45 */\n    XML_ERR_PI_NOT_STARTED, /* 46 */\n    XML_ERR_PI_NOT_FINISHED, /* 47 */\n    XML_ERR_NOTATION_NOT_STARTED, /* 48 */\n    XML_ERR_NOTATION_NOT_FINISHED, /* 49 */\n    XML_ERR_ATTLIST_NOT_STARTED, /* 50 */\n    XML_ERR_ATTLIST_NOT_FINISHED, /* 51 */\n    XML_ERR_MIXED_NOT_STARTED, /* 52 */\n    XML_ERR_MIXED_NOT_FINISHED, /* 53 */\n    XML_ERR_ELEMCONTENT_NOT_STARTED, /* 54 */\n    XML_ERR_ELEMCONTENT_NOT_FINISHED, /* 55 */\n    XML_ERR_XMLDECL_NOT_STARTED, /* 56 */\n    XML_ERR_XMLDECL_NOT_FINISHED, /* 57 */\n    XML_ERR_CONDSEC_NOT_STARTED, /* 58 */\n    XML_ERR_CONDSEC_NOT_FINISHED, /* 59 */\n    XML_ERR_EXT_SUBSET_NOT_FINISHED, /* 60 */\n    XML_ERR_DOCTYPE_NOT_FINISHED, /* 61 */\n    XML_ERR_MISPLACED_CDATA_END, /* 62 */\n    XML_ERR_CDATA_NOT_FINISHED, /* 63 */\n    XML_ERR_RESERVED_XML_NAME, /* 64 */\n    XML_ERR_SPACE_REQUIRED, /* 65 */\n    XML_ERR_SEPARATOR_REQUIRED, /* 66 */\n    XML_ERR_NMTOKEN_REQUIRED, /* 67 */\n    XML_ERR_NAME_REQUIRED, /* 68 */\n    XML_ERR_PCDATA_REQUIRED, /* 69 */\n    XML_ERR_URI_REQUIRED, /* 70 */\n    XML_ERR_PUBID_REQUIRED, /* 71 */\n    XML_ERR_LT_REQUIRED, /* 72 */\n    XML_ERR_GT_REQUIRED, /* 73 */\n    XML_ERR_LTSLASH_REQUIRED, /* 74 */\n    XML_ERR_EQUAL_REQUIRED, /* 75 */\n    XML_ERR_TAG_NAME_MISMATCH, /* 76 */\n    XML_ERR_TAG_NOT_FINISHED, /* 77 */\n    XML_ERR_STANDALONE_VALUE, /* 78 */\n    XML_ERR_ENCODING_NAME, /* 79 */\n    XML_ERR_HYPHEN_IN_COMMENT, /* 80 */\n    XML_ERR_INVALID_ENCODING, /* 81 */\n    XML_ERR_EXT_ENTITY_STANDALONE, /* 82 */\n    XML_ERR_CONDSEC_INVALID, /* 83 */\n    XML_ERR_VALUE_REQUIRED, /* 84 */\n    XML_ERR_NOT_WELL_BALANCED, /* 85 */\n    XML_ERR_EXTRA_CONTENT, /* 86 */\n    XML_ERR_ENTITY_CHAR_ERROR, /* 87 */\n    XML_ERR_ENTITY_PE_INTERNAL, /* 88 */\n    XML_ERR_ENTITY_LOOP, /* 89 */\n    XML_ERR_ENTITY_BOUNDARY, /* 90 */\n    XML_ERR_INVALID_URI, /* 91 */\n    XML_ERR_URI_FRAGMENT, /* 92 */\n    XML_WAR_CATALOG_PI, /* 93 */\n    XML_ERR_NO_DTD, /* 94 */\n    XML_ERR_CONDSEC_INVALID_KEYWORD, /* 95 */\n    XML_ERR_VERSION_MISSING, /* 96 */\n    XML_WAR_UNKNOWN_VERSION, /* 97 */\n    XML_WAR_LANG_VALUE, /* 98 */\n    XML_WAR_NS_URI, /* 99 */\n    XML_WAR_NS_URI_RELATIVE, /* 100 */\n    XML_ERR_MISSING_ENCODING, /* 101 */\n    XML_WAR_SPACE_VALUE, /* 102 */\n    XML_ERR_NOT_STANDALONE, /* 103 */\n    XML_ERR_ENTITY_PROCESSING, /* 104 */\n    XML_ERR_NOTATION_PROCESSING, /* 105 */\n    XML_WAR_NS_COLUMN, /* 106 */\n    XML_WAR_ENTITY_REDEFINED, /* 107 */\n    XML_ERR_UNKNOWN_VERSION, /* 108 */\n    XML_ERR_VERSION_MISMATCH, /* 109 */\n    XML_ERR_NAME_TOO_LONG, /* 110 */\n    XML_ERR_USER_STOP, /* 111 */\n    XML_NS_ERR_XML_NAMESPACE = 200,\n    XML_NS_ERR_UNDEFINED_NAMESPACE, /* 201 */\n    XML_NS_ERR_QNAME, /* 202 */\n    XML_NS_ERR_ATTRIBUTE_REDEFINED, /* 203 */\n    XML_NS_ERR_EMPTY, /* 204 */\n    XML_NS_ERR_COLON, /* 205 */\n    XML_DTD_ATTRIBUTE_DEFAULT = 500,\n    XML_DTD_ATTRIBUTE_REDEFINED, /* 501 */\n    XML_DTD_ATTRIBUTE_VALUE, /* 502 */\n    XML_DTD_CONTENT_ERROR, /* 503 */\n    XML_DTD_CONTENT_MODEL, /* 504 */\n    XML_DTD_CONTENT_NOT_DETERMINIST, /* 505 */\n    XML_DTD_DIFFERENT_PREFIX, /* 506 */\n    XML_DTD_ELEM_DEFAULT_NAMESPACE, /* 507 */\n    XML_DTD_ELEM_NAMESPACE, /* 508 */\n    XML_DTD_ELEM_REDEFINED, /* 509 */\n    XML_DTD_EMPTY_NOTATION, /* 510 */\n    XML_DTD_ENTITY_TYPE, /* 511 */\n    XML_DTD_ID_FIXED, /* 512 */\n    XML_DTD_ID_REDEFINED, /* 513 */\n    XML_DTD_ID_SUBSET, /* 514 */\n    XML_DTD_INVALID_CHILD, /* 515 */\n    XML_DTD_INVALID_DEFAULT, /* 516 */\n    XML_DTD_LOAD_ERROR, /* 517 */\n    XML_DTD_MISSING_ATTRIBUTE, /* 518 */\n    XML_DTD_MIXED_CORRUPT, /* 519 */\n    XML_DTD_MULTIPLE_ID, /* 520 */\n    XML_DTD_NO_DOC, /* 521 */\n    XML_DTD_NO_DTD, /* 522 */\n    XML_DTD_NO_ELEM_NAME, /* 523 */\n    XML_DTD_NO_PREFIX, /* 524 */\n    XML_DTD_NO_ROOT, /* 525 */\n    XML_DTD_NOTATION_REDEFINED, /* 526 */\n    XML_DTD_NOTATION_VALUE, /* 527 */\n    XML_DTD_NOT_EMPTY, /* 528 */\n    XML_DTD_NOT_PCDATA, /* 529 */\n    XML_DTD_NOT_STANDALONE, /* 530 */\n    XML_DTD_ROOT_NAME, /* 531 */\n    XML_DTD_STANDALONE_WHITE_SPACE, /* 532 */\n    XML_DTD_UNKNOWN_ATTRIBUTE, /* 533 */\n    XML_DTD_UNKNOWN_ELEM, /* 534 */\n    XML_DTD_UNKNOWN_ENTITY, /* 535 */\n    XML_DTD_UNKNOWN_ID, /* 536 */\n    XML_DTD_UNKNOWN_NOTATION, /* 537 */\n    XML_DTD_STANDALONE_DEFAULTED, /* 538 */\n    XML_DTD_XMLID_VALUE, /* 539 */\n    XML_DTD_XMLID_TYPE, /* 540 */\n    XML_DTD_DUP_TOKEN, /* 541 */\n    XML_HTML_STRUCURE_ERROR = 800,\n    XML_HTML_UNKNOWN_TAG, /* 801 */\n    XML_RNGP_ANYNAME_ATTR_ANCESTOR = 1000,\n    XML_RNGP_ATTR_CONFLICT, /* 1001 */\n    XML_RNGP_ATTRIBUTE_CHILDREN, /* 1002 */\n    XML_RNGP_ATTRIBUTE_CONTENT, /* 1003 */\n    XML_RNGP_ATTRIBUTE_EMPTY, /* 1004 */\n    XML_RNGP_ATTRIBUTE_NOOP, /* 1005 */\n    XML_RNGP_CHOICE_CONTENT, /* 1006 */\n    XML_RNGP_CHOICE_EMPTY, /* 1007 */\n    XML_RNGP_CREATE_FAILURE, /* 1008 */\n    XML_RNGP_DATA_CONTENT, /* 1009 */\n    XML_RNGP_DEF_CHOICE_AND_INTERLEAVE, /* 1010 */\n    XML_RNGP_DEFINE_CREATE_FAILED, /* 1011 */\n    XML_RNGP_DEFINE_EMPTY, /* 1012 */\n    XML_RNGP_DEFINE_MISSING, /* 1013 */\n    XML_RNGP_DEFINE_NAME_MISSING, /* 1014 */\n    XML_RNGP_ELEM_CONTENT_EMPTY, /* 1015 */\n    XML_RNGP_ELEM_CONTENT_ERROR, /* 1016 */\n    XML_RNGP_ELEMENT_EMPTY, /* 1017 */\n    XML_RNGP_ELEMENT_CONTENT, /* 1018 */\n    XML_RNGP_ELEMENT_NAME, /* 1019 */\n    XML_RNGP_ELEMENT_NO_CONTENT, /* 1020 */\n    XML_RNGP_ELEM_TEXT_CONFLICT, /* 1021 */\n    XML_RNGP_EMPTY, /* 1022 */\n    XML_RNGP_EMPTY_CONSTRUCT, /* 1023 */\n    XML_RNGP_EMPTY_CONTENT, /* 1024 */\n    XML_RNGP_EMPTY_NOT_EMPTY, /* 1025 */\n    XML_RNGP_ERROR_TYPE_LIB, /* 1026 */\n    XML_RNGP_EXCEPT_EMPTY, /* 1027 */\n    XML_RNGP_EXCEPT_MISSING, /* 1028 */\n    XML_RNGP_EXCEPT_MULTIPLE, /* 1029 */\n    XML_RNGP_EXCEPT_NO_CONTENT, /* 1030 */\n    XML_RNGP_EXTERNALREF_EMTPY, /* 1031 */\n    XML_RNGP_EXTERNAL_REF_FAILURE, /* 1032 */\n    XML_RNGP_EXTERNALREF_RECURSE, /* 1033 */\n    XML_RNGP_FORBIDDEN_ATTRIBUTE, /* 1034 */\n    XML_RNGP_FOREIGN_ELEMENT, /* 1035 */\n    XML_RNGP_GRAMMAR_CONTENT, /* 1036 */\n    XML_RNGP_GRAMMAR_EMPTY, /* 1037 */\n    XML_RNGP_GRAMMAR_MISSING, /* 1038 */\n    XML_RNGP_GRAMMAR_NO_START, /* 1039 */\n    XML_RNGP_GROUP_ATTR_CONFLICT, /* 1040 */\n    XML_RNGP_HREF_ERROR, /* 1041 */\n    XML_RNGP_INCLUDE_EMPTY, /* 1042 */\n    XML_RNGP_INCLUDE_FAILURE, /* 1043 */\n    XML_RNGP_INCLUDE_RECURSE, /* 1044 */\n    XML_RNGP_INTERLEAVE_ADD, /* 1045 */\n    XML_RNGP_INTERLEAVE_CREATE_FAILED, /* 1046 */\n    XML_RNGP_INTERLEAVE_EMPTY, /* 1047 */\n    XML_RNGP_INTERLEAVE_NO_CONTENT, /* 1048 */\n    XML_RNGP_INVALID_DEFINE_NAME, /* 1049 */\n    XML_RNGP_INVALID_URI, /* 1050 */\n    XML_RNGP_INVALID_VALUE, /* 1051 */\n    XML_RNGP_MISSING_HREF, /* 1052 */\n    XML_RNGP_NAME_MISSING, /* 1053 */\n    XML_RNGP_NEED_COMBINE, /* 1054 */\n    XML_RNGP_NOTALLOWED_NOT_EMPTY, /* 1055 */\n    XML_RNGP_NSNAME_ATTR_ANCESTOR, /* 1056 */\n    XML_RNGP_NSNAME_NO_NS, /* 1057 */\n    XML_RNGP_PARAM_FORBIDDEN, /* 1058 */\n    XML_RNGP_PARAM_NAME_MISSING, /* 1059 */\n    XML_RNGP_PARENTREF_CREATE_FAILED, /* 1060 */\n    XML_RNGP_PARENTREF_NAME_INVALID, /* 1061 */\n    XML_RNGP_PARENTREF_NO_NAME, /* 1062 */\n    XML_RNGP_PARENTREF_NO_PARENT, /* 1063 */\n    XML_RNGP_PARENTREF_NOT_EMPTY, /* 1064 */\n    XML_RNGP_PARSE_ERROR, /* 1065 */\n    XML_RNGP_PAT_ANYNAME_EXCEPT_ANYNAME, /* 1066 */\n    XML_RNGP_PAT_ATTR_ATTR, /* 1067 */\n    XML_RNGP_PAT_ATTR_ELEM, /* 1068 */\n    XML_RNGP_PAT_DATA_EXCEPT_ATTR, /* 1069 */\n    XML_RNGP_PAT_DATA_EXCEPT_ELEM, /* 1070 */\n    XML_RNGP_PAT_DATA_EXCEPT_EMPTY, /* 1071 */\n    XML_RNGP_PAT_DATA_EXCEPT_GROUP, /* 1072 */\n    XML_RNGP_PAT_DATA_EXCEPT_INTERLEAVE, /* 1073 */\n    XML_RNGP_PAT_DATA_EXCEPT_LIST, /* 1074 */\n    XML_RNGP_PAT_DATA_EXCEPT_ONEMORE, /* 1075 */\n    XML_RNGP_PAT_DATA_EXCEPT_REF, /* 1076 */\n    XML_RNGP_PAT_DATA_EXCEPT_TEXT, /* 1077 */\n    XML_RNGP_PAT_LIST_ATTR, /* 1078 */\n    XML_RNGP_PAT_LIST_ELEM, /* 1079 */\n    XML_RNGP_PAT_LIST_INTERLEAVE, /* 1080 */\n    XML_RNGP_PAT_LIST_LIST, /* 1081 */\n    XML_RNGP_PAT_LIST_REF, /* 1082 */\n    XML_RNGP_PAT_LIST_TEXT, /* 1083 */\n    XML_RNGP_PAT_NSNAME_EXCEPT_ANYNAME, /* 1084 */\n    XML_RNGP_PAT_NSNAME_EXCEPT_NSNAME, /* 1085 */\n    XML_RNGP_PAT_ONEMORE_GROUP_ATTR, /* 1086 */\n    XML_RNGP_PAT_ONEMORE_INTERLEAVE_ATTR, /* 1087 */\n    XML_RNGP_PAT_START_ATTR, /* 1088 */\n    XML_RNGP_PAT_START_DATA, /* 1089 */\n    XML_RNGP_PAT_START_EMPTY, /* 1090 */\n    XML_RNGP_PAT_START_GROUP, /* 1091 */\n    XML_RNGP_PAT_START_INTERLEAVE, /* 1092 */\n    XML_RNGP_PAT_START_LIST, /* 1093 */\n    XML_RNGP_PAT_START_ONEMORE, /* 1094 */\n    XML_RNGP_PAT_START_TEXT, /* 1095 */\n    XML_RNGP_PAT_START_VALUE, /* 1096 */\n    XML_RNGP_PREFIX_UNDEFINED, /* 1097 */\n    XML_RNGP_REF_CREATE_FAILED, /* 1098 */\n    XML_RNGP_REF_CYCLE, /* 1099 */\n    XML_RNGP_REF_NAME_INVALID, /* 1100 */\n    XML_RNGP_REF_NO_DEF, /* 1101 */\n    XML_RNGP_REF_NO_NAME, /* 1102 */\n    XML_RNGP_REF_NOT_EMPTY, /* 1103 */\n    XML_RNGP_START_CHOICE_AND_INTERLEAVE, /* 1104 */\n    XML_RNGP_START_CONTENT, /* 1105 */\n    XML_RNGP_START_EMPTY, /* 1106 */\n    XML_RNGP_START_MISSING, /* 1107 */\n    XML_RNGP_TEXT_EXPECTED, /* 1108 */\n    XML_RNGP_TEXT_HAS_CHILD, /* 1109 */\n    XML_RNGP_TYPE_MISSING, /* 1110 */\n    XML_RNGP_TYPE_NOT_FOUND, /* 1111 */\n    XML_RNGP_TYPE_VALUE, /* 1112 */\n    XML_RNGP_UNKNOWN_ATTRIBUTE, /* 1113 */\n    XML_RNGP_UNKNOWN_COMBINE, /* 1114 */\n    XML_RNGP_UNKNOWN_CONSTRUCT, /* 1115 */\n    XML_RNGP_UNKNOWN_TYPE_LIB, /* 1116 */\n    XML_RNGP_URI_FRAGMENT, /* 1117 */\n    XML_RNGP_URI_NOT_ABSOLUTE, /* 1118 */\n    XML_RNGP_VALUE_EMPTY, /* 1119 */\n    XML_RNGP_VALUE_NO_CONTENT, /* 1120 */\n    XML_RNGP_XMLNS_NAME, /* 1121 */\n    XML_RNGP_XML_NS, /* 1122 */\n    XML_XPATH_EXPRESSION_OK = 1200,\n    XML_XPATH_NUMBER_ERROR, /* 1201 */\n    XML_XPATH_UNFINISHED_LITERAL_ERROR, /* 1202 */\n    XML_XPATH_START_LITERAL_ERROR, /* 1203 */\n    XML_XPATH_VARIABLE_REF_ERROR, /* 1204 */\n    XML_XPATH_UNDEF_VARIABLE_ERROR, /* 1205 */\n    XML_XPATH_INVALID_PREDICATE_ERROR, /* 1206 */\n    XML_XPATH_EXPR_ERROR, /* 1207 */\n    XML_XPATH_UNCLOSED_ERROR, /* 1208 */\n    XML_XPATH_UNKNOWN_FUNC_ERROR, /* 1209 */\n    XML_XPATH_INVALID_OPERAND, /* 1210 */\n    XML_XPATH_INVALID_TYPE, /* 1211 */\n    XML_XPATH_INVALID_ARITY, /* 1212 */\n    XML_XPATH_INVALID_CTXT_SIZE, /* 1213 */\n    XML_XPATH_INVALID_CTXT_POSITION, /* 1214 */\n    XML_XPATH_MEMORY_ERROR, /* 1215 */\n    XML_XPTR_SYNTAX_ERROR, /* 1216 */\n    XML_XPTR_RESOURCE_ERROR, /* 1217 */\n    XML_XPTR_SUB_RESOURCE_ERROR, /* 1218 */\n    XML_XPATH_UNDEF_PREFIX_ERROR, /* 1219 */\n    XML_XPATH_ENCODING_ERROR, /* 1220 */\n    XML_XPATH_INVALID_CHAR_ERROR, /* 1221 */\n    XML_TREE_INVALID_HEX = 1300,\n    XML_TREE_INVALID_DEC, /* 1301 */\n    XML_TREE_UNTERMINATED_ENTITY, /* 1302 */\n    XML_TREE_NOT_UTF8, /* 1303 */\n    XML_SAVE_NOT_UTF8 = 1400,\n    XML_SAVE_CHAR_INVALID, /* 1401 */\n    XML_SAVE_NO_DOCTYPE, /* 1402 */\n    XML_SAVE_UNKNOWN_ENCODING, /* 1403 */\n    XML_REGEXP_COMPILE_ERROR = 1450,\n    XML_IO_UNKNOWN = 1500,\n    XML_IO_EACCES, /* 1501 */\n    XML_IO_EAGAIN, /* 1502 */\n    XML_IO_EBADF, /* 1503 */\n    XML_IO_EBADMSG, /* 1504 */\n    XML_IO_EBUSY, /* 1505 */\n    XML_IO_ECANCELED, /* 1506 */\n    XML_IO_ECHILD, /* 1507 */\n    XML_IO_EDEADLK, /* 1508 */\n    XML_IO_EDOM, /* 1509 */\n    XML_IO_EEXIST, /* 1510 */\n    XML_IO_EFAULT, /* 1511 */\n    XML_IO_EFBIG, /* 1512 */\n    XML_IO_EINPROGRESS, /* 1513 */\n    XML_IO_EINTR, /* 1514 */\n    XML_IO_EINVAL, /* 1515 */\n    XML_IO_EIO, /* 1516 */\n    XML_IO_EISDIR, /* 1517 */\n    XML_IO_EMFILE, /* 1518 */\n    XML_IO_EMLINK, /* 1519 */\n    XML_IO_EMSGSIZE, /* 1520 */\n    XML_IO_ENAMETOOLONG, /* 1521 */\n    XML_IO_ENFILE, /* 1522 */\n    XML_IO_ENODEV, /* 1523 */\n    XML_IO_ENOENT, /* 1524 */\n    XML_IO_ENOEXEC, /* 1525 */\n    XML_IO_ENOLCK, /* 1526 */\n    XML_IO_ENOMEM, /* 1527 */\n    XML_IO_ENOSPC, /* 1528 */\n    XML_IO_ENOSYS, /* 1529 */\n    XML_IO_ENOTDIR, /* 1530 */\n    XML_IO_ENOTEMPTY, /* 1531 */\n    XML_IO_ENOTSUP, /* 1532 */\n    XML_IO_ENOTTY, /* 1533 */\n    XML_IO_ENXIO, /* 1534 */\n    XML_IO_EPERM, /* 1535 */\n    XML_IO_EPIPE, /* 1536 */\n    XML_IO_ERANGE, /* 1537 */\n    XML_IO_EROFS, /* 1538 */\n    XML_IO_ESPIPE, /* 1539 */\n    XML_IO_ESRCH, /* 1540 */\n    XML_IO_ETIMEDOUT, /* 1541 */\n    XML_IO_EXDEV, /* 1542 */\n    XML_IO_NETWORK_ATTEMPT, /* 1543 */\n    XML_IO_ENCODER, /* 1544 */\n    XML_IO_FLUSH, /* 1545 */\n    XML_IO_WRITE, /* 1546 */\n    XML_IO_NO_INPUT, /* 1547 */\n    XML_IO_BUFFER_FULL, /* 1548 */\n    XML_IO_LOAD_ERROR, /* 1549 */\n    XML_IO_ENOTSOCK, /* 1550 */\n    XML_IO_EISCONN, /* 1551 */\n    XML_IO_ECONNREFUSED, /* 1552 */\n    XML_IO_ENETUNREACH, /* 1553 */\n    XML_IO_EADDRINUSE, /* 1554 */\n    XML_IO_EALREADY, /* 1555 */\n    XML_IO_EAFNOSUPPORT, /* 1556 */\n    XML_XINCLUDE_RECURSION=1600,\n    XML_XINCLUDE_PARSE_VALUE, /* 1601 */\n    XML_XINCLUDE_ENTITY_DEF_MISMATCH, /* 1602 */\n    XML_XINCLUDE_NO_HREF, /* 1603 */\n    XML_XINCLUDE_NO_FALLBACK, /* 1604 */\n    XML_XINCLUDE_HREF_URI, /* 1605 */\n    XML_XINCLUDE_TEXT_FRAGMENT, /* 1606 */\n    XML_XINCLUDE_TEXT_DOCUMENT, /* 1607 */\n    XML_XINCLUDE_INVALID_CHAR, /* 1608 */\n    XML_XINCLUDE_BUILD_FAILED, /* 1609 */\n    XML_XINCLUDE_UNKNOWN_ENCODING, /* 1610 */\n    XML_XINCLUDE_MULTIPLE_ROOT, /* 1611 */\n    XML_XINCLUDE_XPTR_FAILED, /* 1612 */\n    XML_XINCLUDE_XPTR_RESULT, /* 1613 */\n    XML_XINCLUDE_INCLUDE_IN_INCLUDE, /* 1614 */\n    XML_XINCLUDE_FALLBACKS_IN_INCLUDE, /* 1615 */\n    XML_XINCLUDE_FALLBACK_NOT_IN_INCLUDE, /* 1616 */\n    XML_XINCLUDE_DEPRECATED_NS, /* 1617 */\n    XML_XINCLUDE_FRAGMENT_ID, /* 1618 */\n    XML_CATALOG_MISSING_ATTR = 1650,\n    XML_CATALOG_ENTRY_BROKEN, /* 1651 */\n    XML_CATALOG_PREFER_VALUE, /* 1652 */\n    XML_CATALOG_NOT_CATALOG, /* 1653 */\n    XML_CATALOG_RECURSION, /* 1654 */\n    XML_SCHEMAP_PREFIX_UNDEFINED = 1700,\n    XML_SCHEMAP_ATTRFORMDEFAULT_VALUE, /* 1701 */\n    XML_SCHEMAP_ATTRGRP_NONAME_NOREF, /* 1702 */\n    XML_SCHEMAP_ATTR_NONAME_NOREF, /* 1703 */\n    XML_SCHEMAP_COMPLEXTYPE_NONAME_NOREF, /* 1704 */\n    XML_SCHEMAP_ELEMFORMDEFAULT_VALUE, /* 1705 */\n    XML_SCHEMAP_ELEM_NONAME_NOREF, /* 1706 */\n    XML_SCHEMAP_EXTENSION_NO_BASE, /* 1707 */\n    XML_SCHEMAP_FACET_NO_VALUE, /* 1708 */\n    XML_SCHEMAP_FAILED_BUILD_IMPORT, /* 1709 */\n    XML_SCHEMAP_GROUP_NONAME_NOREF, /* 1710 */\n    XML_SCHEMAP_IMPORT_NAMESPACE_NOT_URI, /* 1711 */\n    XML_SCHEMAP_IMPORT_REDEFINE_NSNAME, /* 1712 */\n    XML_SCHEMAP_IMPORT_SCHEMA_NOT_URI, /* 1713 */\n    XML_SCHEMAP_INVALID_BOOLEAN, /* 1714 */\n    XML_SCHEMAP_INVALID_ENUM, /* 1715 */\n    XML_SCHEMAP_INVALID_FACET, /* 1716 */\n    XML_SCHEMAP_INVALID_FACET_VALUE, /* 1717 */\n    XML_SCHEMAP_INVALID_MAXOCCURS, /* 1718 */\n    XML_SCHEMAP_INVALID_MINOCCURS, /* 1719 */\n    XML_SCHEMAP_INVALID_REF_AND_SUBTYPE, /* 1720 */\n    XML_SCHEMAP_INVALID_WHITE_SPACE, /* 1721 */\n    XML_SCHEMAP_NOATTR_NOREF, /* 1722 */\n    XML_SCHEMAP_NOTATION_NO_NAME, /* 1723 */\n    XML_SCHEMAP_NOTYPE_NOREF, /* 1724 */\n    XML_SCHEMAP_REF_AND_SUBTYPE, /* 1725 */\n    XML_SCHEMAP_RESTRICTION_NONAME_NOREF, /* 1726 */\n    XML_SCHEMAP_SIMPLETYPE_NONAME, /* 1727 */\n    XML_SCHEMAP_TYPE_AND_SUBTYPE, /* 1728 */\n    XML_SCHEMAP_UNKNOWN_ALL_CHILD, /* 1729 */\n    XML_SCHEMAP_UNKNOWN_ANYATTRIBUTE_CHILD, /* 1730 */\n    XML_SCHEMAP_UNKNOWN_ATTR_CHILD, /* 1731 */\n    XML_SCHEMAP_UNKNOWN_ATTRGRP_CHILD, /* 1732 */\n    XML_SCHEMAP_UNKNOWN_ATTRIBUTE_GROUP, /* 1733 */\n    XML_SCHEMAP_UNKNOWN_BASE_TYPE, /* 1734 */\n    XML_SCHEMAP_UNKNOWN_CHOICE_CHILD, /* 1735 */\n    XML_SCHEMAP_UNKNOWN_COMPLEXCONTENT_CHILD, /* 1736 */\n    XML_SCHEMAP_UNKNOWN_COMPLEXTYPE_CHILD, /* 1737 */\n    XML_SCHEMAP_UNKNOWN_ELEM_CHILD, /* 1738 */\n    XML_SCHEMAP_UNKNOWN_EXTENSION_CHILD, /* 1739 */\n    XML_SCHEMAP_UNKNOWN_FACET_CHILD, /* 1740 */\n    XML_SCHEMAP_UNKNOWN_FACET_TYPE, /* 1741 */\n    XML_SCHEMAP_UNKNOWN_GROUP_CHILD, /* 1742 */\n    XML_SCHEMAP_UNKNOWN_IMPORT_CHILD, /* 1743 */\n    XML_SCHEMAP_UNKNOWN_LIST_CHILD, /* 1744 */\n    XML_SCHEMAP_UNKNOWN_NOTATION_CHILD, /* 1745 */\n    XML_SCHEMAP_UNKNOWN_PROCESSCONTENT_CHILD, /* 1746 */\n    XML_SCHEMAP_UNKNOWN_REF, /* 1747 */\n    XML_SCHEMAP_UNKNOWN_RESTRICTION_CHILD, /* 1748 */\n    XML_SCHEMAP_UNKNOWN_SCHEMAS_CHILD, /* 1749 */\n    XML_SCHEMAP_UNKNOWN_SEQUENCE_CHILD, /* 1750 */\n    XML_SCHEMAP_UNKNOWN_SIMPLECONTENT_CHILD, /* 1751 */\n    XML_SCHEMAP_UNKNOWN_SIMPLETYPE_CHILD, /* 1752 */\n    XML_SCHEMAP_UNKNOWN_TYPE, /* 1753 */\n    XML_SCHEMAP_UNKNOWN_UNION_CHILD, /* 1754 */\n    XML_SCHEMAP_ELEM_DEFAULT_FIXED, /* 1755 */\n    XML_SCHEMAP_REGEXP_INVALID, /* 1756 */\n    XML_SCHEMAP_FAILED_LOAD, /* 1757 */\n    XML_SCHEMAP_NOTHING_TO_PARSE, /* 1758 */\n    XML_SCHEMAP_NOROOT, /* 1759 */\n    XML_SCHEMAP_REDEFINED_GROUP, /* 1760 */\n    XML_SCHEMAP_REDEFINED_TYPE, /* 1761 */\n    XML_SCHEMAP_REDEFINED_ELEMENT, /* 1762 */\n    XML_SCHEMAP_REDEFINED_ATTRGROUP, /* 1763 */\n    XML_SCHEMAP_REDEFINED_ATTR, /* 1764 */\n    XML_SCHEMAP_REDEFINED_NOTATION, /* 1765 */\n    XML_SCHEMAP_FAILED_PARSE, /* 1766 */\n    XML_SCHEMAP_UNKNOWN_PREFIX, /* 1767 */\n    XML_SCHEMAP_DEF_AND_PREFIX, /* 1768 */\n    XML_SCHEMAP_UNKNOWN_INCLUDE_CHILD, /* 1769 */\n    XML_SCHEMAP_INCLUDE_SCHEMA_NOT_URI, /* 1770 */\n    XML_SCHEMAP_INCLUDE_SCHEMA_NO_URI, /* 1771 */\n    XML_SCHEMAP_NOT_SCHEMA, /* 1772 */\n    XML_SCHEMAP_UNKNOWN_MEMBER_TYPE, /* 1773 */\n    XML_SCHEMAP_INVALID_ATTR_USE, /* 1774 */\n    XML_SCHEMAP_RECURSIVE, /* 1775 */\n    XML_SCHEMAP_SUPERNUMEROUS_LIST_ITEM_TYPE, /* 1776 */\n    XML_SCHEMAP_INVALID_ATTR_COMBINATION, /* 1777 */\n    XML_SCHEMAP_INVALID_ATTR_INLINE_COMBINATION, /* 1778 */\n    XML_SCHEMAP_MISSING_SIMPLETYPE_CHILD, /* 1779 */\n    XML_SCHEMAP_INVALID_ATTR_NAME, /* 1780 */\n    XML_SCHEMAP_REF_AND_CONTENT, /* 1781 */\n    XML_SCHEMAP_CT_PROPS_CORRECT_1, /* 1782 */\n    XML_SCHEMAP_CT_PROPS_CORRECT_2, /* 1783 */\n    XML_SCHEMAP_CT_PROPS_CORRECT_3, /* 1784 */\n    XML_SCHEMAP_CT_PROPS_CORRECT_4, /* 1785 */\n    XML_SCHEMAP_CT_PROPS_CORRECT_5, /* 1786 */\n    XML_SCHEMAP_DERIVATION_OK_RESTRICTION_1, /* 1787 */\n    XML_SCHEMAP_DERIVATION_OK_RESTRICTION_2_1_1, /* 1788 */\n    XML_SCHEMAP_DERIVATION_OK_RESTRICTION_2_1_2, /* 1789 */\n    XML_SCHEMAP_DERIVATION_OK_RESTRICTION_2_2, /* 1790 */\n    XML_SCHEMAP_DERIVATION_OK_RESTRICTION_3, /* 1791 */\n    XML_SCHEMAP_WILDCARD_INVALID_NS_MEMBER, /* 1792 */\n    XML_SCHEMAP_INTERSECTION_NOT_EXPRESSIBLE, /* 1793 */\n    XML_SCHEMAP_UNION_NOT_EXPRESSIBLE, /* 1794 */\n    XML_SCHEMAP_SRC_IMPORT_3_1, /* 1795 */\n    XML_SCHEMAP_SRC_IMPORT_3_2, /* 1796 */\n    XML_SCHEMAP_DERIVATION_OK_RESTRICTION_4_1, /* 1797 */\n    XML_SCHEMAP_DERIVATION_OK_RESTRICTION_4_2, /* 1798 */\n    XML_SCHEMAP_DERIVATION_OK_RESTRICTION_4_3, /* 1799 */\n    XML_SCHEMAP_COS_CT_EXTENDS_1_3, /* 1800 */\n    XML_SCHEMAV_NOROOT = 1801,\n    XML_SCHEMAV_UNDECLAREDELEM, /* 1802 */\n    XML_SCHEMAV_NOTTOPLEVEL, /* 1803 */\n    XML_SCHEMAV_MISSING, /* 1804 */\n    XML_SCHEMAV_WRONGELEM, /* 1805 */\n    XML_SCHEMAV_NOTYPE, /* 1806 */\n    XML_SCHEMAV_NOROLLBACK, /* 1807 */\n    XML_SCHEMAV_ISABSTRACT, /* 1808 */\n    XML_SCHEMAV_NOTEMPTY, /* 1809 */\n    XML_SCHEMAV_ELEMCONT, /* 1810 */\n    XML_SCHEMAV_HAVEDEFAULT, /* 1811 */\n    XML_SCHEMAV_NOTNILLABLE, /* 1812 */\n    XML_SCHEMAV_EXTRACONTENT, /* 1813 */\n    XML_SCHEMAV_INVALIDATTR, /* 1814 */\n    XML_SCHEMAV_INVALIDELEM, /* 1815 */\n    XML_SCHEMAV_NOTDETERMINIST, /* 1816 */\n    XML_SCHEMAV_CONSTRUCT, /* 1817 */\n    XML_SCHEMAV_INTERNAL, /* 1818 */\n    XML_SCHEMAV_NOTSIMPLE, /* 1819 */\n    XML_SCHEMAV_ATTRUNKNOWN, /* 1820 */\n    XML_SCHEMAV_ATTRINVALID, /* 1821 */\n    XML_SCHEMAV_VALUE, /* 1822 */\n    XML_SCHEMAV_FACET, /* 1823 */\n    XML_SCHEMAV_CVC_DATATYPE_VALID_1_2_1, /* 1824 */\n    XML_SCHEMAV_CVC_DATATYPE_VALID_1_2_2, /* 1825 */\n    XML_SCHEMAV_CVC_DATATYPE_VALID_1_2_3, /* 1826 */\n    XML_SCHEMAV_CVC_TYPE_3_1_1, /* 1827 */\n    XML_SCHEMAV_CVC_TYPE_3_1_2, /* 1828 */\n    XML_SCHEMAV_CVC_FACET_VALID, /* 1829 */\n    XML_SCHEMAV_CVC_LENGTH_VALID, /* 1830 */\n    XML_SCHEMAV_CVC_MINLENGTH_VALID, /* 1831 */\n    XML_SCHEMAV_CVC_MAXLENGTH_VALID, /* 1832 */\n    XML_SCHEMAV_CVC_MININCLUSIVE_VALID, /* 1833 */\n    XML_SCHEMAV_CVC_MAXINCLUSIVE_VALID, /* 1834 */\n    XML_SCHEMAV_CVC_MINEXCLUSIVE_VALID, /* 1835 */\n    XML_SCHEMAV_CVC_MAXEXCLUSIVE_VALID, /* 1836 */\n    XML_SCHEMAV_CVC_TOTALDIGITS_VALID, /* 1837 */\n    XML_SCHEMAV_CVC_FRACTIONDIGITS_VALID, /* 1838 */\n    XML_SCHEMAV_CVC_PATTERN_VALID, /* 1839 */\n    XML_SCHEMAV_CVC_ENUMERATION_VALID, /* 1840 */\n    XML_SCHEMAV_CVC_COMPLEX_TYPE_2_1, /* 1841 */\n    XML_SCHEMAV_CVC_COMPLEX_TYPE_2_2, /* 1842 */\n    XML_SCHEMAV_CVC_COMPLEX_TYPE_2_3, /* 1843 */\n    XML_SCHEMAV_CVC_COMPLEX_TYPE_2_4, /* 1844 */\n    XML_SCHEMAV_CVC_ELT_1, /* 1845 */\n    XML_SCHEMAV_CVC_ELT_2, /* 1846 */\n    XML_SCHEMAV_CVC_ELT_3_1, /* 1847 */\n    XML_SCHEMAV_CVC_ELT_3_2_1, /* 1848 */\n    XML_SCHEMAV_CVC_ELT_3_2_2, /* 1849 */\n    XML_SCHEMAV_CVC_ELT_4_1, /* 1850 */\n    XML_SCHEMAV_CVC_ELT_4_2, /* 1851 */\n    XML_SCHEMAV_CVC_ELT_4_3, /* 1852 */\n    XML_SCHEMAV_CVC_ELT_5_1_1, /* 1853 */\n    XML_SCHEMAV_CVC_ELT_5_1_2, /* 1854 */\n    XML_SCHEMAV_CVC_ELT_5_2_1, /* 1855 */\n    XML_SCHEMAV_CVC_ELT_5_2_2_1, /* 1856 */\n    XML_SCHEMAV_CVC_ELT_5_2_2_2_1, /* 1857 */\n    XML_SCHEMAV_CVC_ELT_5_2_2_2_2, /* 1858 */\n    XML_SCHEMAV_CVC_ELT_6, /* 1859 */\n    XML_SCHEMAV_CVC_ELT_7, /* 1860 */\n    XML_SCHEMAV_CVC_ATTRIBUTE_1, /* 1861 */\n    XML_SCHEMAV_CVC_ATTRIBUTE_2, /* 1862 */\n    XML_SCHEMAV_CVC_ATTRIBUTE_3, /* 1863 */\n    XML_SCHEMAV_CVC_ATTRIBUTE_4, /* 1864 */\n    XML_SCHEMAV_CVC_COMPLEX_TYPE_3_1, /* 1865 */\n    XML_SCHEMAV_CVC_COMPLEX_TYPE_3_2_1, /* 1866 */\n    XML_SCHEMAV_CVC_COMPLEX_TYPE_3_2_2, /* 1867 */\n    XML_SCHEMAV_CVC_COMPLEX_TYPE_4, /* 1868 */\n    XML_SCHEMAV_CVC_COMPLEX_TYPE_5_1, /* 1869 */\n    XML_SCHEMAV_CVC_COMPLEX_TYPE_5_2, /* 1870 */\n    XML_SCHEMAV_ELEMENT_CONTENT, /* 1871 */\n    XML_SCHEMAV_DOCUMENT_ELEMENT_MISSING, /* 1872 */\n    XML_SCHEMAV_CVC_COMPLEX_TYPE_1, /* 1873 */\n    XML_SCHEMAV_CVC_AU, /* 1874 */\n    XML_SCHEMAV_CVC_TYPE_1, /* 1875 */\n    XML_SCHEMAV_CVC_TYPE_2, /* 1876 */\n    XML_SCHEMAV_CVC_IDC, /* 1877 */\n    XML_SCHEMAV_CVC_WILDCARD, /* 1878 */\n    XML_SCHEMAV_MISC, /* 1879 */\n    XML_XPTR_UNKNOWN_SCHEME = 1900,\n    XML_XPTR_CHILDSEQ_START, /* 1901 */\n    XML_XPTR_EVAL_FAILED, /* 1902 */\n    XML_XPTR_EXTRA_OBJECTS, /* 1903 */\n    XML_C14N_CREATE_CTXT = 1950,\n    XML_C14N_REQUIRES_UTF8, /* 1951 */\n    XML_C14N_CREATE_STACK, /* 1952 */\n    XML_C14N_INVALID_NODE, /* 1953 */\n    XML_C14N_UNKNOW_NODE, /* 1954 */\n    XML_C14N_RELATIVE_NAMESPACE, /* 1955 */\n    XML_FTP_PASV_ANSWER = 2000,\n    XML_FTP_EPSV_ANSWER, /* 2001 */\n    XML_FTP_ACCNT, /* 2002 */\n    XML_FTP_URL_SYNTAX, /* 2003 */\n    XML_HTTP_URL_SYNTAX = 2020,\n    XML_HTTP_USE_IP, /* 2021 */\n    XML_HTTP_UNKNOWN_HOST, /* 2022 */\n    XML_SCHEMAP_SRC_SIMPLE_TYPE_1 = 3000,\n    XML_SCHEMAP_SRC_SIMPLE_TYPE_2, /* 3001 */\n    XML_SCHEMAP_SRC_SIMPLE_TYPE_3, /* 3002 */\n    XML_SCHEMAP_SRC_SIMPLE_TYPE_4, /* 3003 */\n    XML_SCHEMAP_SRC_RESOLVE, /* 3004 */\n    XML_SCHEMAP_SRC_RESTRICTION_BASE_OR_SIMPLETYPE, /* 3005 */\n    XML_SCHEMAP_SRC_LIST_ITEMTYPE_OR_SIMPLETYPE, /* 3006 */\n    XML_SCHEMAP_SRC_UNION_MEMBERTYPES_OR_SIMPLETYPES, /* 3007 */\n    XML_SCHEMAP_ST_PROPS_CORRECT_1, /* 3008 */\n    XML_SCHEMAP_ST_PROPS_CORRECT_2, /* 3009 */\n    XML_SCHEMAP_ST_PROPS_CORRECT_3, /* 3010 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_1_1, /* 3011 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_1_2, /* 3012 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_1_3_1, /* 3013 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_1_3_2, /* 3014 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_2_1, /* 3015 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_2_3_1_1, /* 3016 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_2_3_1_2, /* 3017 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_2_3_2_1, /* 3018 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_2_3_2_2, /* 3019 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_2_3_2_3, /* 3020 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_2_3_2_4, /* 3021 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_2_3_2_5, /* 3022 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_3_1, /* 3023 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_3_3_1, /* 3024 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_3_3_1_2, /* 3025 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_3_3_2_2, /* 3026 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_3_3_2_1, /* 3027 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_3_3_2_3, /* 3028 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_3_3_2_4, /* 3029 */\n    XML_SCHEMAP_COS_ST_RESTRICTS_3_3_2_5, /* 3030 */\n    XML_SCHEMAP_COS_ST_DERIVED_OK_2_1, /* 3031 */\n    XML_SCHEMAP_COS_ST_DERIVED_OK_2_2, /* 3032 */\n    XML_SCHEMAP_S4S_ELEM_NOT_ALLOWED, /* 3033 */\n    XML_SCHEMAP_S4S_ELEM_MISSING, /* 3034 */\n    XML_SCHEMAP_S4S_ATTR_NOT_ALLOWED, /* 3035 */\n    XML_SCHEMAP_S4S_ATTR_MISSING, /* 3036 */\n    XML_SCHEMAP_S4S_ATTR_INVALID_VALUE, /* 3037 */\n    XML_SCHEMAP_SRC_ELEMENT_1, /* 3038 */\n    XML_SCHEMAP_SRC_ELEMENT_2_1, /* 3039 */\n    XML_SCHEMAP_SRC_ELEMENT_2_2, /* 3040 */\n    XML_SCHEMAP_SRC_ELEMENT_3, /* 3041 */\n    XML_SCHEMAP_P_PROPS_CORRECT_1, /* 3042 */\n    XML_SCHEMAP_P_PROPS_CORRECT_2_1, /* 3043 */\n    XML_SCHEMAP_P_PROPS_CORRECT_2_2, /* 3044 */\n    XML_SCHEMAP_E_PROPS_CORRECT_2, /* 3045 */\n    XML_SCHEMAP_E_PROPS_CORRECT_3, /* 3046 */\n    XML_SCHEMAP_E_PROPS_CORRECT_4, /* 3047 */\n    XML_SCHEMAP_E_PROPS_CORRECT_5, /* 3048 */\n    XML_SCHEMAP_E_PROPS_CORRECT_6, /* 3049 */\n    XML_SCHEMAP_SRC_INCLUDE, /* 3050 */\n    XML_SCHEMAP_SRC_ATTRIBUTE_1, /* 3051 */\n    XML_SCHEMAP_SRC_ATTRIBUTE_2, /* 3052 */\n    XML_SCHEMAP_SRC_ATTRIBUTE_3_1, /* 3053 */\n    XML_SCHEMAP_SRC_ATTRIBUTE_3_2, /* 3054 */\n    XML_SCHEMAP_SRC_ATTRIBUTE_4, /* 3055 */\n    XML_SCHEMAP_NO_XMLNS, /* 3056 */\n    XML_SCHEMAP_NO_XSI, /* 3057 */\n    XML_SCHEMAP_COS_VALID_DEFAULT_1, /* 3058 */\n    XML_SCHEMAP_COS_VALID_DEFAULT_2_1, /* 3059 */\n    XML_SCHEMAP_COS_VALID_DEFAULT_2_2_1, /* 3060 */\n    XML_SCHEMAP_COS_VALID_DEFAULT_2_2_2, /* 3061 */\n    XML_SCHEMAP_CVC_SIMPLE_TYPE, /* 3062 */\n    XML_SCHEMAP_COS_CT_EXTENDS_1_1, /* 3063 */\n    XML_SCHEMAP_SRC_IMPORT_1_1, /* 3064 */\n    XML_SCHEMAP_SRC_IMPORT_1_2, /* 3065 */\n    XML_SCHEMAP_SRC_IMPORT_2, /* 3066 */\n    XML_SCHEMAP_SRC_IMPORT_2_1, /* 3067 */\n    XML_SCHEMAP_SRC_IMPORT_2_2, /* 3068 */\n    XML_SCHEMAP_INTERNAL, /* 3069 non-W3C */\n    XML_SCHEMAP_NOT_DETERMINISTIC, /* 3070 non-W3C */\n    XML_SCHEMAP_SRC_ATTRIBUTE_GROUP_1, /* 3071 */\n    XML_SCHEMAP_SRC_ATTRIBUTE_GROUP_2, /* 3072 */\n    XML_SCHEMAP_SRC_ATTRIBUTE_GROUP_3, /* 3073 */\n    XML_SCHEMAP_MG_PROPS_CORRECT_1, /* 3074 */\n    XML_SCHEMAP_MG_PROPS_CORRECT_2, /* 3075 */\n    XML_SCHEMAP_SRC_CT_1, /* 3076 */\n    XML_SCHEMAP_DERIVATION_OK_RESTRICTION_2_1_3, /* 3077 */\n    XML_SCHEMAP_AU_PROPS_CORRECT_2, /* 3078 */\n    XML_SCHEMAP_A_PROPS_CORRECT_2, /* 3079 */\n    XML_SCHEMAP_C_PROPS_CORRECT, /* 3080 */\n    XML_SCHEMAP_SRC_REDEFINE, /* 3081 */\n    XML_SCHEMAP_SRC_IMPORT, /* 3082 */\n    XML_SCHEMAP_WARN_SKIP_SCHEMA, /* 3083 */\n    XML_SCHEMAP_WARN_UNLOCATED_SCHEMA, /* 3084 */\n    XML_SCHEMAP_WARN_ATTR_REDECL_PROH, /* 3085 */\n    XML_SCHEMAP_WARN_ATTR_POINTLESS_PROH, /* 3085 */\n    XML_SCHEMAP_AG_PROPS_CORRECT, /* 3086 */\n    XML_SCHEMAP_COS_CT_EXTENDS_1_2, /* 3087 */\n    XML_SCHEMAP_AU_PROPS_CORRECT, /* 3088 */\n    XML_SCHEMAP_A_PROPS_CORRECT_3, /* 3089 */\n    XML_SCHEMAP_COS_ALL_LIMITED, /* 3090 */\n    XML_SCHEMATRONV_ASSERT = 4000, /* 4000 */\n    XML_SCHEMATRONV_REPORT,\n    XML_MODULE_OPEN = 4900, /* 4900 */\n    XML_MODULE_CLOSE, /* 4901 */\n    XML_CHECK_FOUND_ELEMENT = 5000,\n    XML_CHECK_FOUND_ATTRIBUTE, /* 5001 */\n    XML_CHECK_FOUND_TEXT, /* 5002 */\n    XML_CHECK_FOUND_CDATA, /* 5003 */\n    XML_CHECK_FOUND_ENTITYREF, /* 5004 */\n    XML_CHECK_FOUND_ENTITY, /* 5005 */\n    XML_CHECK_FOUND_PI, /* 5006 */\n    XML_CHECK_FOUND_COMMENT, /* 5007 */\n    XML_CHECK_FOUND_DOCTYPE, /* 5008 */\n    XML_CHECK_FOUND_FRAGMENT, /* 5009 */\n    XML_CHECK_FOUND_NOTATION, /* 5010 */\n    XML_CHECK_UNKNOWN_NODE, /* 5011 */\n    XML_CHECK_ENTITY_TYPE, /* 5012 */\n    XML_CHECK_NO_PARENT, /* 5013 */\n    XML_CHECK_NO_DOC, /* 5014 */\n    XML_CHECK_NO_NAME, /* 5015 */\n    XML_CHECK_NO_ELEM, /* 5016 */\n    XML_CHECK_WRONG_DOC, /* 5017 */\n    XML_CHECK_NO_PREV, /* 5018 */\n    XML_CHECK_WRONG_PREV, /* 5019 */\n    XML_CHECK_NO_NEXT, /* 5020 */\n    XML_CHECK_WRONG_NEXT, /* 5021 */\n    XML_CHECK_NOT_DTD, /* 5022 */\n    XML_CHECK_NOT_ATTR, /* 5023 */\n    XML_CHECK_NOT_ATTR_DECL, /* 5024 */\n    XML_CHECK_NOT_ELEM_DECL, /* 5025 */\n    XML_CHECK_NOT_ENTITY_DECL, /* 5026 */\n    XML_CHECK_NOT_NS_DECL, /* 5027 */\n    XML_CHECK_NO_HREF, /* 5028 */\n    XML_CHECK_WRONG_PARENT,/* 5029 */\n    XML_CHECK_NS_SCOPE, /* 5030 */\n    XML_CHECK_NS_ANCESTOR, /* 5031 */\n    XML_CHECK_NOT_UTF8, /* 5032 */\n    XML_CHECK_NO_DICT, /* 5033 */\n    XML_CHECK_NOT_NCNAME, /* 5034 */\n    XML_CHECK_OUTSIDE_DICT, /* 5035 */\n    XML_CHECK_WRONG_NAME, /* 5036 */\n    XML_CHECK_NAME_NOT_NULL, /* 5037 */\n    XML_I18N_NO_NAME = 6000,\n    XML_I18N_NO_HANDLER, /* 6001 */\n    XML_I18N_EXCESS_HANDLER, /* 6002 */\n    XML_I18N_CONV_FAILED, /* 6003 */\n    XML_I18N_NO_OUTPUT, /* 6004 */\n    XML_BUF_OVERFLOW = 7000\n} xmlParserErrors;\n\n/**\n * xmlGenericErrorFunc:\n * @ctx:  a parsing context\n * @msg:  the message\n * @...:  the extra arguments of the varags to format the message\n *\n * Signature of the function to use when there is an error and\n * no parsing or validity context available .\n */\ntypedef void (XMLCDECL *xmlGenericErrorFunc) (void *ctx,\n\t\t\t\t const char *msg,\n\t\t\t\t ...) LIBXML_ATTR_FORMAT(2,3);\n/**\n * xmlStructuredErrorFunc:\n * @userData:  user provided data for the error callback\n * @error:  the error being raised.\n *\n * Signature of the function to use when there is an error and\n * the module handles the new error reporting mechanism.\n */\ntypedef void (XMLCALL *xmlStructuredErrorFunc) (void *userData, xmlErrorPtr error);\n\n/*\n * Use the following function to reset the two global variables\n * xmlGenericError and xmlGenericErrorContext.\n */\nXMLPUBFUN void XMLCALL\n    xmlSetGenericErrorFunc\t(void *ctx,\n\t\t\t\t xmlGenericErrorFunc handler);\nXMLPUBFUN void XMLCALL\n    initGenericErrorDefaultFunc\t(xmlGenericErrorFunc *handler);\n\nXMLPUBFUN void XMLCALL\n    xmlSetStructuredErrorFunc\t(void *ctx,\n\t\t\t\t xmlStructuredErrorFunc handler);\n/*\n * Default message routines used by SAX and Valid context for error\n * and warning reporting.\n */\nXMLPUBFUN void XMLCDECL\n    xmlParserError\t\t(void *ctx,\n\t\t\t\t const char *msg,\n\t\t\t\t ...) LIBXML_ATTR_FORMAT(2,3);\nXMLPUBFUN void XMLCDECL\n    xmlParserWarning\t\t(void *ctx,\n\t\t\t\t const char *msg,\n\t\t\t\t ...) LIBXML_ATTR_FORMAT(2,3);\nXMLPUBFUN void XMLCDECL\n    xmlParserValidityError\t(void *ctx,\n\t\t\t\t const char *msg,\n\t\t\t\t ...) LIBXML_ATTR_FORMAT(2,3);\nXMLPUBFUN void XMLCDECL\n    xmlParserValidityWarning\t(void *ctx,\n\t\t\t\t const char *msg,\n\t\t\t\t ...) LIBXML_ATTR_FORMAT(2,3);\nXMLPUBFUN void XMLCALL\n    xmlParserPrintFileInfo\t(xmlParserInputPtr input);\nXMLPUBFUN void XMLCALL\n    xmlParserPrintFileContext\t(xmlParserInputPtr input);\n\n/*\n * Extended error information routines\n */\nXMLPUBFUN xmlErrorPtr XMLCALL\n    xmlGetLastError\t\t(void);\nXMLPUBFUN void XMLCALL\n    xmlResetLastError\t\t(void);\nXMLPUBFUN xmlErrorPtr XMLCALL\n    xmlCtxtGetLastError\t\t(void *ctx);\nXMLPUBFUN void XMLCALL\n    xmlCtxtResetLastError\t(void *ctx);\nXMLPUBFUN void XMLCALL\n    xmlResetError\t\t(xmlErrorPtr err);\nXMLPUBFUN int XMLCALL\n    xmlCopyError\t\t(xmlErrorPtr from,\n\t\t\t\t xmlErrorPtr to);\n\n#ifdef IN_LIBXML\n/*\n * Internal callback reporting routine\n */\nXMLPUBFUN void XMLCALL\n    __xmlRaiseError\t\t(xmlStructuredErrorFunc schannel,\n\t\t\t\t xmlGenericErrorFunc channel,\n\t\t\t\t void *data,\n                                 void *ctx,\n\t\t\t\t void *node,\n\t\t\t\t int domain,\n\t\t\t\t int code,\n\t\t\t\t xmlErrorLevel level,\n\t\t\t\t const char *file,\n\t\t\t\t int line,\n\t\t\t\t const char *str1,\n\t\t\t\t const char *str2,\n\t\t\t\t const char *str3,\n\t\t\t\t int int1,\n\t\t\t\t int col,\n\t\t\t\t const char *msg,\n\t\t\t\t ...) LIBXML_ATTR_FORMAT(16,17);\nXMLPUBFUN void XMLCALL\n    __xmlSimpleError\t\t(int domain,\n\t\t\t\t int code,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t const char *msg,\n\t\t\t\t const char *extra) LIBXML_ATTR_FORMAT(4,0);\n#endif\n#ifdef __cplusplus\n}\n#endif\n#endif /* __XML_ERROR_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlexports.h",
    "content": "/*\n * Summary: macros for marking symbols as exportable/importable.\n * Description: macros for marking symbols as exportable/importable.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Igor Zlatovic <igor@zlatkovic.com>\n */\n\n#ifndef __XML_EXPORTS_H__\n#define __XML_EXPORTS_H__\n\n/**\n * XMLPUBFUN, XMLPUBVAR, XMLCALL\n *\n * Macros which declare an exportable function, an exportable variable and\n * the calling convention used for functions.\n *\n * Please use an extra block for every platform/compiler combination when\n * modifying this, rather than overlong #ifdef lines. This helps\n * readability as well as the fact that different compilers on the same\n * platform might need different definitions.\n */\n\n/**\n * XMLPUBFUN:\n *\n * Macros which declare an exportable function\n */\n#define XMLPUBFUN\n/**\n * XMLPUBVAR:\n *\n * Macros which declare an exportable variable\n */\n#define XMLPUBVAR extern\n/**\n * XMLCALL:\n *\n * Macros which declare the called convention for exported functions\n */\n#define XMLCALL\n/**\n * XMLCDECL:\n *\n * Macro which declares the calling convention for exported functions that\n * use '...'.\n */\n#define XMLCDECL\n\n/** DOC_DISABLE */\n\n/* Windows platform with MS compiler */\n#if defined(_WIN32) && defined(_MSC_VER)\n  #undef XMLPUBFUN\n  #undef XMLPUBVAR\n  #undef XMLCALL\n  #undef XMLCDECL\n  #if defined(IN_LIBXML) && !defined(LIBXML_STATIC)\n    #define XMLPUBFUN __declspec(dllexport)\n    #define XMLPUBVAR __declspec(dllexport)\n  #else\n    #define XMLPUBFUN\n    #if !defined(LIBXML_STATIC)\n      #define XMLPUBVAR __declspec(dllimport) extern\n    #else\n      #define XMLPUBVAR extern\n    #endif\n  #endif\n  #if defined(LIBXML_FASTCALL)\n    #define XMLCALL __fastcall\n  #else\n    #define XMLCALL __cdecl\n  #endif\n  #define XMLCDECL __cdecl\n  #if !defined _REENTRANT\n    #define _REENTRANT\n  #endif\n#endif\n\n/* Windows platform with Borland compiler */\n#if defined(_WIN32) && defined(__BORLANDC__)\n  #undef XMLPUBFUN\n  #undef XMLPUBVAR\n  #undef XMLCALL\n  #undef XMLCDECL\n  #if defined(IN_LIBXML) && !defined(LIBXML_STATIC)\n    #define XMLPUBFUN __declspec(dllexport)\n    #define XMLPUBVAR __declspec(dllexport) extern\n  #else\n    #define XMLPUBFUN\n    #if !defined(LIBXML_STATIC)\n      #define XMLPUBVAR __declspec(dllimport) extern\n    #else\n      #define XMLPUBVAR extern\n    #endif\n  #endif\n  #define XMLCALL __cdecl\n  #define XMLCDECL __cdecl\n  #if !defined _REENTRANT\n    #define _REENTRANT\n  #endif\n#endif\n\n/* Windows platform with GNU compiler (Mingw) */\n#if defined(_WIN32) && defined(__MINGW32__)\n  #undef XMLPUBFUN\n  #undef XMLPUBVAR\n  #undef XMLCALL\n  #undef XMLCDECL\n  /*\n   * if defined(IN_LIBXML) this raises problems on mingw with msys\n   * _imp__xmlFree listed as missing. Try to workaround the problem\n   * by also making that declaration when compiling client code.\n   */\n  #if defined(IN_LIBXML) && !defined(LIBXML_STATIC)\n    #define XMLPUBFUN __declspec(dllexport)\n    #define XMLPUBVAR __declspec(dllexport) extern\n  #else\n    #define XMLPUBFUN\n    #if !defined(LIBXML_STATIC)\n      #define XMLPUBVAR __declspec(dllimport) extern\n    #else\n      #define XMLPUBVAR extern\n    #endif\n  #endif\n  #define XMLCALL __cdecl\n  #define XMLCDECL __cdecl\n  #if !defined _REENTRANT\n    #define _REENTRANT\n  #endif\n#endif\n\n/* Cygwin platform (does not define _WIN32), GNU compiler */\n#if defined(__CYGWIN__)\n  #undef XMLPUBFUN\n  #undef XMLPUBVAR\n  #undef XMLCALL\n  #undef XMLCDECL\n  #if defined(IN_LIBXML) && !defined(LIBXML_STATIC)\n    #define XMLPUBFUN __declspec(dllexport)\n    #define XMLPUBVAR __declspec(dllexport)\n  #else\n    #define XMLPUBFUN\n    #if !defined(LIBXML_STATIC)\n      #define XMLPUBVAR __declspec(dllimport) extern\n    #else\n      #define XMLPUBVAR extern\n    #endif\n  #endif\n  #define XMLCALL __cdecl\n  #define XMLCDECL __cdecl\n#endif\n\n/* Compatibility */\n#if !defined(LIBXML_DLL_IMPORT)\n#define LIBXML_DLL_IMPORT XMLPUBVAR\n#endif\n\n#endif /* __XML_EXPORTS_H__ */\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlmemory.h",
    "content": "/*\n * Summary: interface for the memory allocator\n * Description: provides interfaces for the memory allocator,\n *              including debugging capabilities.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n\n#ifndef __DEBUG_MEMORY_ALLOC__\n#define __DEBUG_MEMORY_ALLOC__\n\n#include <stdio.h>\n#include <libxml/xmlversion.h>\n\n/**\n * DEBUG_MEMORY:\n *\n * DEBUG_MEMORY replaces the allocator with a collect and debug\n * shell to the libc allocator.\n * DEBUG_MEMORY should only be activated when debugging\n * libxml i.e. if libxml has been configured with --with-debug-mem too.\n */\n/* #define DEBUG_MEMORY_FREED */\n/* #define DEBUG_MEMORY_LOCATION */\n\n#ifdef DEBUG\n#ifndef DEBUG_MEMORY\n#define DEBUG_MEMORY\n#endif\n#endif\n\n/**\n * DEBUG_MEMORY_LOCATION:\n *\n * DEBUG_MEMORY_LOCATION should be activated only when debugging\n * libxml i.e. if libxml has been configured with --with-debug-mem too.\n */\n#ifdef DEBUG_MEMORY_LOCATION\n#endif\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * The XML memory wrapper support 4 basic overloadable functions.\n */\n/**\n * xmlFreeFunc:\n * @mem: an already allocated block of memory\n *\n * Signature for a free() implementation.\n */\ntypedef void (XMLCALL *xmlFreeFunc)(void *mem);\n/**\n * xmlMallocFunc:\n * @size:  the size requested in bytes\n *\n * Signature for a malloc() implementation.\n *\n * Returns a pointer to the newly allocated block or NULL in case of error.\n */\ntypedef void *(LIBXML_ATTR_ALLOC_SIZE(1) XMLCALL *xmlMallocFunc)(size_t size);\n\n/**\n * xmlReallocFunc:\n * @mem: an already allocated block of memory\n * @size:  the new size requested in bytes\n *\n * Signature for a realloc() implementation.\n *\n * Returns a pointer to the newly reallocated block or NULL in case of error.\n */\ntypedef void *(XMLCALL *xmlReallocFunc)(void *mem, size_t size);\n\n/**\n * xmlStrdupFunc:\n * @str: a zero terminated string\n *\n * Signature for an strdup() implementation.\n *\n * Returns the copy of the string or NULL in case of error.\n */\ntypedef char *(XMLCALL *xmlStrdupFunc)(const char *str);\n\n/*\n * The 4 interfaces used for all memory handling within libxml.\nLIBXML_DLL_IMPORT xmlFreeFunc xmlFree;\nLIBXML_DLL_IMPORT xmlMallocFunc xmlMalloc;\nLIBXML_DLL_IMPORT xmlMallocFunc xmlMallocAtomic;\nLIBXML_DLL_IMPORT xmlReallocFunc xmlRealloc;\nLIBXML_DLL_IMPORT xmlStrdupFunc xmlMemStrdup;\n */\n\n/*\n * The way to overload the existing functions.\n * The xmlGc function have an extra entry for atomic block\n * allocations useful for garbage collected memory allocators\n */\nXMLPUBFUN int XMLCALL\n\txmlMemSetup\t(xmlFreeFunc freeFunc,\n\t\t\t xmlMallocFunc mallocFunc,\n\t\t\t xmlReallocFunc reallocFunc,\n\t\t\t xmlStrdupFunc strdupFunc);\nXMLPUBFUN int XMLCALL\n\txmlMemGet\t(xmlFreeFunc *freeFunc,\n\t\t\t xmlMallocFunc *mallocFunc,\n\t\t\t xmlReallocFunc *reallocFunc,\n\t\t\t xmlStrdupFunc *strdupFunc);\nXMLPUBFUN int XMLCALL\n\txmlGcMemSetup\t(xmlFreeFunc freeFunc,\n\t\t\t xmlMallocFunc mallocFunc,\n\t\t\t xmlMallocFunc mallocAtomicFunc,\n\t\t\t xmlReallocFunc reallocFunc,\n\t\t\t xmlStrdupFunc strdupFunc);\nXMLPUBFUN int XMLCALL\n\txmlGcMemGet\t(xmlFreeFunc *freeFunc,\n\t\t\t xmlMallocFunc *mallocFunc,\n\t\t\t xmlMallocFunc *mallocAtomicFunc,\n\t\t\t xmlReallocFunc *reallocFunc,\n\t\t\t xmlStrdupFunc *strdupFunc);\n\n/*\n * Initialization of the memory layer.\n */\nXMLPUBFUN int XMLCALL\n\txmlInitMemory\t(void);\n\n/*\n * Cleanup of the memory layer.\n */\nXMLPUBFUN void XMLCALL\n                xmlCleanupMemory        (void);\n/*\n * These are specific to the XML debug memory wrapper.\n */\nXMLPUBFUN int XMLCALL\n\txmlMemUsed\t(void);\nXMLPUBFUN int XMLCALL\n\txmlMemBlocks\t(void);\nXMLPUBFUN void XMLCALL\n\txmlMemDisplay\t(FILE *fp);\nXMLPUBFUN void XMLCALL\n\txmlMemDisplayLast(FILE *fp, long nbBytes);\nXMLPUBFUN void XMLCALL\n\txmlMemShow\t(FILE *fp, int nr);\nXMLPUBFUN void XMLCALL\n\txmlMemoryDump\t(void);\nXMLPUBFUN void * XMLCALL\n\txmlMemMalloc\t(size_t size) LIBXML_ATTR_ALLOC_SIZE(1);\nXMLPUBFUN void * XMLCALL\n\txmlMemRealloc\t(void *ptr,size_t size);\nXMLPUBFUN void XMLCALL\n\txmlMemFree\t(void *ptr);\nXMLPUBFUN char * XMLCALL\n\txmlMemoryStrdup\t(const char *str);\nXMLPUBFUN void * XMLCALL\n\txmlMallocLoc\t(size_t size, const char *file, int line) LIBXML_ATTR_ALLOC_SIZE(1);\nXMLPUBFUN void * XMLCALL\n\txmlReallocLoc\t(void *ptr, size_t size, const char *file, int line);\nXMLPUBFUN void * XMLCALL\n\txmlMallocAtomicLoc (size_t size, const char *file, int line) LIBXML_ATTR_ALLOC_SIZE(1);\nXMLPUBFUN char * XMLCALL\n\txmlMemStrdupLoc\t(const char *str, const char *file, int line);\n\n\n#ifdef DEBUG_MEMORY_LOCATION\n/**\n * xmlMalloc:\n * @size:  number of bytes to allocate\n *\n * Wrapper for the malloc() function used in the XML library.\n *\n * Returns the pointer to the allocated area or NULL in case of error.\n */\n#define xmlMalloc(size) xmlMallocLoc((size), __FILE__, __LINE__)\n/**\n * xmlMallocAtomic:\n * @size:  number of bytes to allocate\n *\n * Wrapper for the malloc() function used in the XML library for allocation\n * of block not containing pointers to other areas.\n *\n * Returns the pointer to the allocated area or NULL in case of error.\n */\n#define xmlMallocAtomic(size) xmlMallocAtomicLoc((size), __FILE__, __LINE__)\n/**\n * xmlRealloc:\n * @ptr:  pointer to the existing allocated area\n * @size:  number of bytes to allocate\n *\n * Wrapper for the realloc() function used in the XML library.\n *\n * Returns the pointer to the allocated area or NULL in case of error.\n */\n#define xmlRealloc(ptr, size) xmlReallocLoc((ptr), (size), __FILE__, __LINE__)\n/**\n * xmlMemStrdup:\n * @str:  pointer to the existing string\n *\n * Wrapper for the strdup() function, xmlStrdup() is usually preferred.\n *\n * Returns the pointer to the allocated area or NULL in case of error.\n */\n#define xmlMemStrdup(str) xmlMemStrdupLoc((str), __FILE__, __LINE__)\n\n#endif /* DEBUG_MEMORY_LOCATION */\n\n#ifdef __cplusplus\n}\n#endif /* __cplusplus */\n\n#ifndef __XML_GLOBALS_H\n#ifndef __XML_THREADS_H__\n#include <libxml/threads.h>\n#include <libxml/globals.h>\n#endif\n#endif\n\n#endif  /* __DEBUG_MEMORY_ALLOC__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlmodule.h",
    "content": "/*\n * Summary: dynamic module loading\n * Description: basic API for dynamic module loading, used by\n *              libexslt added in 2.6.17\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Joel W. Reed\n */\n\n#ifndef __XML_MODULE_H__\n#define __XML_MODULE_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_MODULES_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * xmlModulePtr:\n *\n * A handle to a dynamically loaded module\n */\ntypedef struct _xmlModule xmlModule;\ntypedef xmlModule *xmlModulePtr;\n\n/**\n * xmlModuleOption:\n *\n * enumeration of options that can be passed down to xmlModuleOpen()\n */\ntypedef enum {\n    XML_MODULE_LAZY = 1,\t/* lazy binding */\n    XML_MODULE_LOCAL= 2\t\t/* local binding */\n} xmlModuleOption;\n\nXMLPUBFUN xmlModulePtr XMLCALL xmlModuleOpen\t(const char *filename,\n\t\t\t\t\t\t int options);\n\nXMLPUBFUN int XMLCALL xmlModuleSymbol\t\t(xmlModulePtr module,\n\t\t\t\t\t\t const char* name,\n\t\t\t\t\t\t void **result);\n\nXMLPUBFUN int XMLCALL xmlModuleClose\t\t(xmlModulePtr module);\n\nXMLPUBFUN int XMLCALL xmlModuleFree\t\t(xmlModulePtr module);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_MODULES_ENABLED */\n\n#endif /*__XML_MODULE_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlreader.h",
    "content": "/*\n * Summary: the XMLReader implementation\n * Description: API of the XML streaming API based on C# interfaces.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XMLREADER_H__\n#define __XML_XMLREADER_H__\n\n#include <libxml/xmlversion.h>\n#include <libxml/tree.h>\n#include <libxml/xmlIO.h>\n#ifdef LIBXML_SCHEMAS_ENABLED\n#include <libxml/relaxng.h>\n#include <libxml/xmlschemas.h>\n#endif\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * xmlParserSeverities:\n *\n * How severe an error callback is when the per-reader error callback API\n * is used.\n */\ntypedef enum {\n    XML_PARSER_SEVERITY_VALIDITY_WARNING = 1,\n    XML_PARSER_SEVERITY_VALIDITY_ERROR = 2,\n    XML_PARSER_SEVERITY_WARNING = 3,\n    XML_PARSER_SEVERITY_ERROR = 4\n} xmlParserSeverities;\n\n#ifdef LIBXML_READER_ENABLED\n\n/**\n * xmlTextReaderMode:\n *\n * Internal state values for the reader.\n */\ntypedef enum {\n    XML_TEXTREADER_MODE_INITIAL = 0,\n    XML_TEXTREADER_MODE_INTERACTIVE = 1,\n    XML_TEXTREADER_MODE_ERROR = 2,\n    XML_TEXTREADER_MODE_EOF =3,\n    XML_TEXTREADER_MODE_CLOSED = 4,\n    XML_TEXTREADER_MODE_READING = 5\n} xmlTextReaderMode;\n\n/**\n * xmlParserProperties:\n *\n * Some common options to use with xmlTextReaderSetParserProp, but it\n * is better to use xmlParserOption and the xmlReaderNewxxx and\n * xmlReaderForxxx APIs now.\n */\ntypedef enum {\n    XML_PARSER_LOADDTD = 1,\n    XML_PARSER_DEFAULTATTRS = 2,\n    XML_PARSER_VALIDATE = 3,\n    XML_PARSER_SUBST_ENTITIES = 4\n} xmlParserProperties;\n\n/**\n * xmlReaderTypes:\n *\n * Predefined constants for the different types of nodes.\n */\ntypedef enum {\n    XML_READER_TYPE_NONE = 0,\n    XML_READER_TYPE_ELEMENT = 1,\n    XML_READER_TYPE_ATTRIBUTE = 2,\n    XML_READER_TYPE_TEXT = 3,\n    XML_READER_TYPE_CDATA = 4,\n    XML_READER_TYPE_ENTITY_REFERENCE = 5,\n    XML_READER_TYPE_ENTITY = 6,\n    XML_READER_TYPE_PROCESSING_INSTRUCTION = 7,\n    XML_READER_TYPE_COMMENT = 8,\n    XML_READER_TYPE_DOCUMENT = 9,\n    XML_READER_TYPE_DOCUMENT_TYPE = 10,\n    XML_READER_TYPE_DOCUMENT_FRAGMENT = 11,\n    XML_READER_TYPE_NOTATION = 12,\n    XML_READER_TYPE_WHITESPACE = 13,\n    XML_READER_TYPE_SIGNIFICANT_WHITESPACE = 14,\n    XML_READER_TYPE_END_ELEMENT = 15,\n    XML_READER_TYPE_END_ENTITY = 16,\n    XML_READER_TYPE_XML_DECLARATION = 17\n} xmlReaderTypes;\n\n/**\n * xmlTextReader:\n *\n * Structure for an xmlReader context.\n */\ntypedef struct _xmlTextReader xmlTextReader;\n\n/**\n * xmlTextReaderPtr:\n *\n * Pointer to an xmlReader context.\n */\ntypedef xmlTextReader *xmlTextReaderPtr;\n\n/*\n * Constructors & Destructor\n */\nXMLPUBFUN xmlTextReaderPtr XMLCALL\n\t\t\txmlNewTextReader\t(xmlParserInputBufferPtr input,\n\t                                         const char *URI);\nXMLPUBFUN xmlTextReaderPtr XMLCALL\n\t\t\txmlNewTextReaderFilename(const char *URI);\n\nXMLPUBFUN void XMLCALL\n\t\t\txmlFreeTextReader\t(xmlTextReaderPtr reader);\n\nXMLPUBFUN int XMLCALL\n            xmlTextReaderSetup(xmlTextReaderPtr reader,\n                   xmlParserInputBufferPtr input, const char *URL,\n                   const char *encoding, int options);\n\n/*\n * Iterators\n */\nXMLPUBFUN int XMLCALL\n\t\t\txmlTextReaderRead\t(xmlTextReaderPtr reader);\n\n#ifdef LIBXML_WRITER_ENABLED\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlTextReaderReadInnerXml(xmlTextReaderPtr reader);\n\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlTextReaderReadOuterXml(xmlTextReaderPtr reader);\n#endif\n\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlTextReaderReadString\t(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t\txmlTextReaderReadAttributeValue(xmlTextReaderPtr reader);\n\n/*\n * Attributes of the node\n */\nXMLPUBFUN int XMLCALL\n\t\t\txmlTextReaderAttributeCount(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t\txmlTextReaderDepth\t(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t\txmlTextReaderHasAttributes(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t\txmlTextReaderHasValue(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t\txmlTextReaderIsDefault\t(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t\txmlTextReaderIsEmptyElement(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t\txmlTextReaderNodeType\t(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t\txmlTextReaderQuoteChar\t(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t\txmlTextReaderReadState\t(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n                        xmlTextReaderIsNamespaceDecl(xmlTextReaderPtr reader);\n\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t    xmlTextReaderConstBaseUri\t(xmlTextReaderPtr reader);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t    xmlTextReaderConstLocalName\t(xmlTextReaderPtr reader);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t    xmlTextReaderConstName\t(xmlTextReaderPtr reader);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t    xmlTextReaderConstNamespaceUri(xmlTextReaderPtr reader);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t    xmlTextReaderConstPrefix\t(xmlTextReaderPtr reader);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t    xmlTextReaderConstXmlLang\t(xmlTextReaderPtr reader);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t    xmlTextReaderConstString\t(xmlTextReaderPtr reader,\n\t\t\t\t\t\t const xmlChar *str);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t    xmlTextReaderConstValue\t(xmlTextReaderPtr reader);\n\n/*\n * use the Const version of the routine for\n * better performance and simpler code\n */\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlTextReaderBaseUri\t(xmlTextReaderPtr reader);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlTextReaderLocalName\t(xmlTextReaderPtr reader);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlTextReaderName\t(xmlTextReaderPtr reader);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlTextReaderNamespaceUri(xmlTextReaderPtr reader);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlTextReaderPrefix\t(xmlTextReaderPtr reader);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlTextReaderXmlLang\t(xmlTextReaderPtr reader);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t\txmlTextReaderValue\t(xmlTextReaderPtr reader);\n\n/*\n * Methods of the XmlTextReader\n */\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderClose\t\t(xmlTextReaderPtr reader);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t    xmlTextReaderGetAttributeNo\t(xmlTextReaderPtr reader,\n\t\t\t\t\t\t int no);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t    xmlTextReaderGetAttribute\t(xmlTextReaderPtr reader,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t    xmlTextReaderGetAttributeNs\t(xmlTextReaderPtr reader,\n\t\t\t\t\t\t const xmlChar *localName,\n\t\t\t\t\t\t const xmlChar *namespaceURI);\nXMLPUBFUN xmlParserInputBufferPtr XMLCALL\n\t\t    xmlTextReaderGetRemainder\t(xmlTextReaderPtr reader);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t    xmlTextReaderLookupNamespace(xmlTextReaderPtr reader,\n\t\t\t\t\t\t const xmlChar *prefix);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderMoveToAttributeNo(xmlTextReaderPtr reader,\n\t\t\t\t\t\t int no);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderMoveToAttribute(xmlTextReaderPtr reader,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderMoveToAttributeNs(xmlTextReaderPtr reader,\n\t\t\t\t\t\t const xmlChar *localName,\n\t\t\t\t\t\t const xmlChar *namespaceURI);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderMoveToFirstAttribute(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderMoveToNextAttribute(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderMoveToElement\t(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderNormalization\t(xmlTextReaderPtr reader);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t    xmlTextReaderConstEncoding  (xmlTextReaderPtr reader);\n\n/*\n * Extensions\n */\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderSetParserProp\t(xmlTextReaderPtr reader,\n\t\t\t\t\t\t int prop,\n\t\t\t\t\t\t int value);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderGetParserProp\t(xmlTextReaderPtr reader,\n\t\t\t\t\t\t int prop);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\t    xmlTextReaderCurrentNode\t(xmlTextReaderPtr reader);\n\nXMLPUBFUN int XMLCALL\n            xmlTextReaderGetParserLineNumber(xmlTextReaderPtr reader);\n\nXMLPUBFUN int XMLCALL\n            xmlTextReaderGetParserColumnNumber(xmlTextReaderPtr reader);\n\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\t    xmlTextReaderPreserve\t(xmlTextReaderPtr reader);\n#ifdef LIBXML_PATTERN_ENABLED\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderPreservePattern(xmlTextReaderPtr reader,\n\t\t\t\t\t\t const xmlChar *pattern,\n\t\t\t\t\t\t const xmlChar **namespaces);\n#endif /* LIBXML_PATTERN_ENABLED */\nXMLPUBFUN xmlDocPtr XMLCALL\n\t\t    xmlTextReaderCurrentDoc\t(xmlTextReaderPtr reader);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\t    xmlTextReaderExpand\t\t(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderNext\t\t(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderNextSibling\t(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderIsValid\t(xmlTextReaderPtr reader);\n#ifdef LIBXML_SCHEMAS_ENABLED\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderRelaxNGValidate(xmlTextReaderPtr reader,\n\t\t\t\t\t\t const char *rng);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderRelaxNGValidateCtxt(xmlTextReaderPtr reader,\n\t\t\t\t\t\t xmlRelaxNGValidCtxtPtr ctxt,\n\t\t\t\t\t\t int options);\n\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderRelaxNGSetSchema(xmlTextReaderPtr reader,\n\t\t\t\t\t\t xmlRelaxNGPtr schema);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderSchemaValidate\t(xmlTextReaderPtr reader,\n\t\t\t\t\t\t const char *xsd);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderSchemaValidateCtxt(xmlTextReaderPtr reader,\n\t\t\t\t\t\t xmlSchemaValidCtxtPtr ctxt,\n\t\t\t\t\t\t int options);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderSetSchema\t(xmlTextReaderPtr reader,\n\t\t\t\t\t\t xmlSchemaPtr schema);\n#endif\nXMLPUBFUN const xmlChar * XMLCALL\n\t\t    xmlTextReaderConstXmlVersion(xmlTextReaderPtr reader);\nXMLPUBFUN int XMLCALL\n\t\t    xmlTextReaderStandalone     (xmlTextReaderPtr reader);\n\n\n/*\n * Index lookup\n */\nXMLPUBFUN long XMLCALL\n\t\txmlTextReaderByteConsumed\t(xmlTextReaderPtr reader);\n\n/*\n * New more complete APIs for simpler creation and reuse of readers\n */\nXMLPUBFUN xmlTextReaderPtr XMLCALL\n\t\txmlReaderWalker\t\t(xmlDocPtr doc);\nXMLPUBFUN xmlTextReaderPtr XMLCALL\n\t\txmlReaderForDoc\t\t(const xmlChar * cur,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlTextReaderPtr XMLCALL\n\t\txmlReaderForFile\t(const char *filename,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlTextReaderPtr XMLCALL\n\t\txmlReaderForMemory\t(const char *buffer,\n\t\t\t\t\t int size,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlTextReaderPtr XMLCALL\n\t\txmlReaderForFd\t\t(int fd,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlTextReaderPtr XMLCALL\n\t\txmlReaderForIO\t\t(xmlInputReadCallback ioread,\n\t\t\t\t\t xmlInputCloseCallback ioclose,\n\t\t\t\t\t void *ioctx,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\n\nXMLPUBFUN int XMLCALL\n\t\txmlReaderNewWalker\t(xmlTextReaderPtr reader,\n\t\t\t\t\t xmlDocPtr doc);\nXMLPUBFUN int XMLCALL\n\t\txmlReaderNewDoc\t\t(xmlTextReaderPtr reader,\n\t\t\t\t\t const xmlChar * cur,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN int XMLCALL\n\t\txmlReaderNewFile\t(xmlTextReaderPtr reader,\n\t\t\t\t\t const char *filename,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN int XMLCALL\n\t\txmlReaderNewMemory\t(xmlTextReaderPtr reader,\n\t\t\t\t\t const char *buffer,\n\t\t\t\t\t int size,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN int XMLCALL\n\t\txmlReaderNewFd\t\t(xmlTextReaderPtr reader,\n\t\t\t\t\t int fd,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN int XMLCALL\n\t\txmlReaderNewIO\t\t(xmlTextReaderPtr reader,\n\t\t\t\t\t xmlInputReadCallback ioread,\n\t\t\t\t\t xmlInputCloseCallback ioclose,\n\t\t\t\t\t void *ioctx,\n\t\t\t\t\t const char *URL,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\n/*\n * Error handling extensions\n */\ntypedef void *  xmlTextReaderLocatorPtr;\n\n/**\n * xmlTextReaderErrorFunc:\n * @arg: the user argument\n * @msg: the message\n * @severity: the severity of the error\n * @locator: a locator indicating where the error occurred\n *\n * Signature of an error callback from a reader parser\n */\ntypedef void (XMLCALL *xmlTextReaderErrorFunc)(void *arg,\n\t\t\t\t\t       const char *msg,\n\t\t\t\t\t       xmlParserSeverities severity,\n\t\t\t\t\t       xmlTextReaderLocatorPtr locator);\nXMLPUBFUN int XMLCALL\n\t    xmlTextReaderLocatorLineNumber(xmlTextReaderLocatorPtr locator);\nXMLPUBFUN xmlChar * XMLCALL\n\t    xmlTextReaderLocatorBaseURI (xmlTextReaderLocatorPtr locator);\nXMLPUBFUN void XMLCALL\n\t    xmlTextReaderSetErrorHandler(xmlTextReaderPtr reader,\n\t\t\t\t\t xmlTextReaderErrorFunc f,\n\t\t\t\t\t void *arg);\nXMLPUBFUN void XMLCALL\n\t    xmlTextReaderSetStructuredErrorHandler(xmlTextReaderPtr reader,\n\t\t\t\t\t\t   xmlStructuredErrorFunc f,\n\t\t\t\t\t\t   void *arg);\nXMLPUBFUN void XMLCALL\n\t    xmlTextReaderGetErrorHandler(xmlTextReaderPtr reader,\n\t\t\t\t\t xmlTextReaderErrorFunc *f,\n\t\t\t\t\t void **arg);\n\n#endif /* LIBXML_READER_ENABLED */\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XMLREADER_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlregexp.h",
    "content": "/*\n * Summary: regular expressions handling\n * Description: basic API for libxml regular expressions handling used\n *              for XML Schemas and validation.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_REGEXP_H__\n#define __XML_REGEXP_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_REGEXP_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * xmlRegexpPtr:\n *\n * A libxml regular expression, they can actually be far more complex\n * thank the POSIX regex expressions.\n */\ntypedef struct _xmlRegexp xmlRegexp;\ntypedef xmlRegexp *xmlRegexpPtr;\n\n/**\n * xmlRegExecCtxtPtr:\n *\n * A libxml progressive regular expression evaluation context\n */\ntypedef struct _xmlRegExecCtxt xmlRegExecCtxt;\ntypedef xmlRegExecCtxt *xmlRegExecCtxtPtr;\n\n#ifdef __cplusplus\n}\n#endif\n#include <libxml/tree.h>\n#include <libxml/dict.h>\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * The POSIX like API\n */\nXMLPUBFUN xmlRegexpPtr XMLCALL\n\t\t    xmlRegexpCompile\t(const xmlChar *regexp);\nXMLPUBFUN void XMLCALL\t\t\t xmlRegFreeRegexp(xmlRegexpPtr regexp);\nXMLPUBFUN int XMLCALL\n\t\t    xmlRegexpExec\t(xmlRegexpPtr comp,\n\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN void XMLCALL\n\t\t    xmlRegexpPrint\t(FILE *output,\n\t\t\t\t\t xmlRegexpPtr regexp);\nXMLPUBFUN int XMLCALL\n\t\t    xmlRegexpIsDeterminist(xmlRegexpPtr comp);\n\n/**\n * xmlRegExecCallbacks:\n * @exec: the regular expression context\n * @token: the current token string\n * @transdata: transition data\n * @inputdata: input data\n *\n * Callback function when doing a transition in the automata\n */\ntypedef void (*xmlRegExecCallbacks) (xmlRegExecCtxtPtr exec,\n\t                             const xmlChar *token,\n\t\t\t\t     void *transdata,\n\t\t\t\t     void *inputdata);\n\n/*\n * The progressive API\n */\nXMLPUBFUN xmlRegExecCtxtPtr XMLCALL\n\t\t    xmlRegNewExecCtxt\t(xmlRegexpPtr comp,\n\t\t\t\t\t xmlRegExecCallbacks callback,\n\t\t\t\t\t void *data);\nXMLPUBFUN void XMLCALL\n\t\t    xmlRegFreeExecCtxt\t(xmlRegExecCtxtPtr exec);\nXMLPUBFUN int XMLCALL\n\t\t    xmlRegExecPushString(xmlRegExecCtxtPtr exec,\n\t\t\t\t\t const xmlChar *value,\n\t\t\t\t\t void *data);\nXMLPUBFUN int XMLCALL\n\t\t    xmlRegExecPushString2(xmlRegExecCtxtPtr exec,\n\t\t\t\t\t const xmlChar *value,\n\t\t\t\t\t const xmlChar *value2,\n\t\t\t\t\t void *data);\n\nXMLPUBFUN int XMLCALL\n\t\t    xmlRegExecNextValues(xmlRegExecCtxtPtr exec,\n\t\t\t\t\t int *nbval,\n\t\t\t\t\t int *nbneg,\n\t\t\t\t\t xmlChar **values,\n\t\t\t\t\t int *terminal);\nXMLPUBFUN int XMLCALL\n\t\t    xmlRegExecErrInfo\t(xmlRegExecCtxtPtr exec,\n\t\t\t\t\t const xmlChar **string,\n\t\t\t\t\t int *nbval,\n\t\t\t\t\t int *nbneg,\n\t\t\t\t\t xmlChar **values,\n\t\t\t\t\t int *terminal);\n#ifdef LIBXML_EXPR_ENABLED\n/*\n * Formal regular expression handling\n * Its goal is to do some formal work on content models\n */\n\n/* expressions are used within a context */\ntypedef struct _xmlExpCtxt xmlExpCtxt;\ntypedef xmlExpCtxt *xmlExpCtxtPtr;\n\nXMLPUBFUN void XMLCALL\n\t\t\txmlExpFreeCtxt\t(xmlExpCtxtPtr ctxt);\nXMLPUBFUN xmlExpCtxtPtr XMLCALL\n\t\t\txmlExpNewCtxt\t(int maxNodes,\n\t\t\t\t\t xmlDictPtr dict);\n\nXMLPUBFUN int XMLCALL\n\t\t\txmlExpCtxtNbNodes(xmlExpCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\t\txmlExpCtxtNbCons(xmlExpCtxtPtr ctxt);\n\n/* Expressions are trees but the tree is opaque */\ntypedef struct _xmlExpNode xmlExpNode;\ntypedef xmlExpNode *xmlExpNodePtr;\n\ntypedef enum {\n    XML_EXP_EMPTY = 0,\n    XML_EXP_FORBID = 1,\n    XML_EXP_ATOM = 2,\n    XML_EXP_SEQ = 3,\n    XML_EXP_OR = 4,\n    XML_EXP_COUNT = 5\n} xmlExpNodeType;\n\n/*\n * 2 core expressions shared by all for the empty language set\n * and for the set with just the empty token\n */\nXMLPUBVAR xmlExpNodePtr forbiddenExp;\nXMLPUBVAR xmlExpNodePtr emptyExp;\n\n/*\n * Expressions are reference counted internally\n */\nXMLPUBFUN void XMLCALL\n\t\t\txmlExpFree\t(xmlExpCtxtPtr ctxt,\n\t\t\t\t\t xmlExpNodePtr expr);\nXMLPUBFUN void XMLCALL\n\t\t\txmlExpRef\t(xmlExpNodePtr expr);\n\n/*\n * constructors can be either manual or from a string\n */\nXMLPUBFUN xmlExpNodePtr XMLCALL\n\t\t\txmlExpParse\t(xmlExpCtxtPtr ctxt,\n\t\t\t\t\t const char *expr);\nXMLPUBFUN xmlExpNodePtr XMLCALL\n\t\t\txmlExpNewAtom\t(xmlExpCtxtPtr ctxt,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t int len);\nXMLPUBFUN xmlExpNodePtr XMLCALL\n\t\t\txmlExpNewOr\t(xmlExpCtxtPtr ctxt,\n\t\t\t\t\t xmlExpNodePtr left,\n\t\t\t\t\t xmlExpNodePtr right);\nXMLPUBFUN xmlExpNodePtr XMLCALL\n\t\t\txmlExpNewSeq\t(xmlExpCtxtPtr ctxt,\n\t\t\t\t\t xmlExpNodePtr left,\n\t\t\t\t\t xmlExpNodePtr right);\nXMLPUBFUN xmlExpNodePtr XMLCALL\n\t\t\txmlExpNewRange\t(xmlExpCtxtPtr ctxt,\n\t\t\t\t\t xmlExpNodePtr subset,\n\t\t\t\t\t int min,\n\t\t\t\t\t int max);\n/*\n * The really interesting APIs\n */\nXMLPUBFUN int XMLCALL\n\t\t\txmlExpIsNillable(xmlExpNodePtr expr);\nXMLPUBFUN int XMLCALL\n\t\t\txmlExpMaxToken\t(xmlExpNodePtr expr);\nXMLPUBFUN int XMLCALL\n\t\t\txmlExpGetLanguage(xmlExpCtxtPtr ctxt,\n\t\t\t\t\t xmlExpNodePtr expr,\n\t\t\t\t\t const xmlChar**langList,\n\t\t\t\t\t int len);\nXMLPUBFUN int XMLCALL\n\t\t\txmlExpGetStart\t(xmlExpCtxtPtr ctxt,\n\t\t\t\t\t xmlExpNodePtr expr,\n\t\t\t\t\t const xmlChar**tokList,\n\t\t\t\t\t int len);\nXMLPUBFUN xmlExpNodePtr XMLCALL\n\t\t\txmlExpStringDerive(xmlExpCtxtPtr ctxt,\n\t\t\t\t\t xmlExpNodePtr expr,\n\t\t\t\t\t const xmlChar *str,\n\t\t\t\t\t int len);\nXMLPUBFUN xmlExpNodePtr XMLCALL\n\t\t\txmlExpExpDerive\t(xmlExpCtxtPtr ctxt,\n\t\t\t\t\t xmlExpNodePtr expr,\n\t\t\t\t\t xmlExpNodePtr sub);\nXMLPUBFUN int XMLCALL\n\t\t\txmlExpSubsume\t(xmlExpCtxtPtr ctxt,\n\t\t\t\t\t xmlExpNodePtr expr,\n\t\t\t\t\t xmlExpNodePtr sub);\nXMLPUBFUN void XMLCALL\n\t\t\txmlExpDump\t(xmlBufferPtr buf,\n\t\t\t\t\t xmlExpNodePtr expr);\n#endif /* LIBXML_EXPR_ENABLED */\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_REGEXP_ENABLED */\n\n#endif /*__XML_REGEXP_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlsave.h",
    "content": "/*\n * Summary: the XML document serializer\n * Description: API to save document or subtree of document\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XMLSAVE_H__\n#define __XML_XMLSAVE_H__\n\n#include <libxml/xmlversion.h>\n#include <libxml/tree.h>\n#include <libxml/encoding.h>\n#include <libxml/xmlIO.h>\n\n#ifdef LIBXML_OUTPUT_ENABLED\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * xmlSaveOption:\n *\n * This is the set of XML save options that can be passed down\n * to the xmlSaveToFd() and similar calls.\n */\ntypedef enum {\n    XML_SAVE_FORMAT     = 1<<0,\t/* format save output */\n    XML_SAVE_NO_DECL    = 1<<1,\t/* drop the xml declaration */\n    XML_SAVE_NO_EMPTY\t= 1<<2, /* no empty tags */\n    XML_SAVE_NO_XHTML\t= 1<<3, /* disable XHTML1 specific rules */\n    XML_SAVE_XHTML\t= 1<<4, /* force XHTML1 specific rules */\n    XML_SAVE_AS_XML     = 1<<5, /* force XML serialization on HTML doc */\n    XML_SAVE_AS_HTML    = 1<<6, /* force HTML serialization on XML doc */\n    XML_SAVE_WSNONSIG   = 1<<7  /* format with non-significant whitespace */\n} xmlSaveOption;\n\n\ntypedef struct _xmlSaveCtxt xmlSaveCtxt;\ntypedef xmlSaveCtxt *xmlSaveCtxtPtr;\n\nXMLPUBFUN xmlSaveCtxtPtr XMLCALL\n\t\txmlSaveToFd\t\t(int fd,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\nXMLPUBFUN xmlSaveCtxtPtr XMLCALL\n\t\txmlSaveToFilename\t(const char *filename,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\n\nXMLPUBFUN xmlSaveCtxtPtr XMLCALL\n\t\txmlSaveToBuffer\t\t(xmlBufferPtr buffer,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\n\nXMLPUBFUN xmlSaveCtxtPtr XMLCALL\n\t\txmlSaveToIO\t\t(xmlOutputWriteCallback iowrite,\n\t\t\t\t\t xmlOutputCloseCallback ioclose,\n\t\t\t\t\t void *ioctx,\n\t\t\t\t\t const char *encoding,\n\t\t\t\t\t int options);\n\nXMLPUBFUN long XMLCALL\n\t\txmlSaveDoc\t\t(xmlSaveCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc);\nXMLPUBFUN long XMLCALL\n\t\txmlSaveTree\t\t(xmlSaveCtxtPtr ctxt,\n\t\t\t\t\t xmlNodePtr node);\n\nXMLPUBFUN int XMLCALL\n\t\txmlSaveFlush\t\t(xmlSaveCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\txmlSaveClose\t\t(xmlSaveCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\txmlSaveSetEscape\t(xmlSaveCtxtPtr ctxt,\n\t\t\t\t\t xmlCharEncodingOutputFunc escape);\nXMLPUBFUN int XMLCALL\n\t\txmlSaveSetAttrEscape\t(xmlSaveCtxtPtr ctxt,\n\t\t\t\t\t xmlCharEncodingOutputFunc escape);\n#ifdef __cplusplus\n}\n#endif\n#endif /* LIBXML_OUTPUT_ENABLED */\n#endif /* __XML_XMLSAVE_H__ */\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlschemas.h",
    "content": "/*\n * Summary: incomplete XML Schemas structure implementation\n * Description: interface to the XML Schemas handling and schema validity\n *              checking, it is incomplete right now.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n\n#ifndef __XML_SCHEMA_H__\n#define __XML_SCHEMA_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_SCHEMAS_ENABLED\n\n#include <libxml/tree.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * This error codes are obsolete; not used any more.\n */\ntypedef enum {\n    XML_SCHEMAS_ERR_OK\t\t= 0,\n    XML_SCHEMAS_ERR_NOROOT\t= 1,\n    XML_SCHEMAS_ERR_UNDECLAREDELEM,\n    XML_SCHEMAS_ERR_NOTTOPLEVEL,\n    XML_SCHEMAS_ERR_MISSING,\n    XML_SCHEMAS_ERR_WRONGELEM,\n    XML_SCHEMAS_ERR_NOTYPE,\n    XML_SCHEMAS_ERR_NOROLLBACK,\n    XML_SCHEMAS_ERR_ISABSTRACT,\n    XML_SCHEMAS_ERR_NOTEMPTY,\n    XML_SCHEMAS_ERR_ELEMCONT,\n    XML_SCHEMAS_ERR_HAVEDEFAULT,\n    XML_SCHEMAS_ERR_NOTNILLABLE,\n    XML_SCHEMAS_ERR_EXTRACONTENT,\n    XML_SCHEMAS_ERR_INVALIDATTR,\n    XML_SCHEMAS_ERR_INVALIDELEM,\n    XML_SCHEMAS_ERR_NOTDETERMINIST,\n    XML_SCHEMAS_ERR_CONSTRUCT,\n    XML_SCHEMAS_ERR_INTERNAL,\n    XML_SCHEMAS_ERR_NOTSIMPLE,\n    XML_SCHEMAS_ERR_ATTRUNKNOWN,\n    XML_SCHEMAS_ERR_ATTRINVALID,\n    XML_SCHEMAS_ERR_VALUE,\n    XML_SCHEMAS_ERR_FACET,\n    XML_SCHEMAS_ERR_,\n    XML_SCHEMAS_ERR_XXX\n} xmlSchemaValidError;\n\n/*\n* ATTENTION: Change xmlSchemaSetValidOptions's check\n* for invalid values, if adding to the validation\n* options below.\n*/\n/**\n * xmlSchemaValidOption:\n *\n * This is the set of XML Schema validation options.\n */\ntypedef enum {\n    XML_SCHEMA_VAL_VC_I_CREATE\t\t\t= 1<<0\n\t/* Default/fixed: create an attribute node\n\t* or an element's text node on the instance.\n\t*/\n} xmlSchemaValidOption;\n\n/*\n    XML_SCHEMA_VAL_XSI_ASSEMBLE\t\t\t= 1<<1,\n\t* assemble schemata using\n\t* xsi:schemaLocation and\n\t* xsi:noNamespaceSchemaLocation\n*/\n\n/**\n * The schemas related types are kept internal\n */\ntypedef struct _xmlSchema xmlSchema;\ntypedef xmlSchema *xmlSchemaPtr;\n\n/**\n * xmlSchemaValidityErrorFunc:\n * @ctx: the validation context\n * @msg: the message\n * @...: extra arguments\n *\n * Signature of an error callback from an XSD validation\n */\ntypedef void (XMLCDECL *xmlSchemaValidityErrorFunc)\n                 (void *ctx, const char *msg, ...) LIBXML_ATTR_FORMAT(2,3);\n\n/**\n * xmlSchemaValidityWarningFunc:\n * @ctx: the validation context\n * @msg: the message\n * @...: extra arguments\n *\n * Signature of a warning callback from an XSD validation\n */\ntypedef void (XMLCDECL *xmlSchemaValidityWarningFunc)\n                 (void *ctx, const char *msg, ...) LIBXML_ATTR_FORMAT(2,3);\n\n/**\n * A schemas validation context\n */\ntypedef struct _xmlSchemaParserCtxt xmlSchemaParserCtxt;\ntypedef xmlSchemaParserCtxt *xmlSchemaParserCtxtPtr;\n\ntypedef struct _xmlSchemaValidCtxt xmlSchemaValidCtxt;\ntypedef xmlSchemaValidCtxt *xmlSchemaValidCtxtPtr;\n\n/**\n * xmlSchemaValidityLocatorFunc:\n * @ctx: user provided context\n * @file: returned file information\n * @line: returned line information\n *\n * A schemas validation locator, a callback called by the validator.\n * This is used when file or node informations are not available\n * to find out what file and line number are affected\n *\n * Returns: 0 in case of success and -1 in case of error\n */\n\ntypedef int (XMLCDECL *xmlSchemaValidityLocatorFunc) (void *ctx,\n                           const char **file, unsigned long *line);\n\n/*\n * Interfaces for parsing.\n */\nXMLPUBFUN xmlSchemaParserCtxtPtr XMLCALL\n\t    xmlSchemaNewParserCtxt\t(const char *URL);\nXMLPUBFUN xmlSchemaParserCtxtPtr XMLCALL\n\t    xmlSchemaNewMemParserCtxt\t(const char *buffer,\n\t\t\t\t\t int size);\nXMLPUBFUN xmlSchemaParserCtxtPtr XMLCALL\n\t    xmlSchemaNewDocParserCtxt\t(xmlDocPtr doc);\nXMLPUBFUN void XMLCALL\n\t    xmlSchemaFreeParserCtxt\t(xmlSchemaParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t    xmlSchemaSetParserErrors\t(xmlSchemaParserCtxtPtr ctxt,\n\t\t\t\t\t xmlSchemaValidityErrorFunc err,\n\t\t\t\t\t xmlSchemaValidityWarningFunc warn,\n\t\t\t\t\t void *ctx);\nXMLPUBFUN void XMLCALL\n\t    xmlSchemaSetParserStructuredErrors(xmlSchemaParserCtxtPtr ctxt,\n\t\t\t\t\t xmlStructuredErrorFunc serror,\n\t\t\t\t\t void *ctx);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaGetParserErrors(xmlSchemaParserCtxtPtr ctxt,\n\t\t\t\t\txmlSchemaValidityErrorFunc * err,\n\t\t\t\t\txmlSchemaValidityWarningFunc * warn,\n\t\t\t\t\tvoid **ctx);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaIsValid\t(xmlSchemaValidCtxtPtr ctxt);\n\nXMLPUBFUN xmlSchemaPtr XMLCALL\n\t    xmlSchemaParse\t\t(xmlSchemaParserCtxtPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t    xmlSchemaFree\t\t(xmlSchemaPtr schema);\n#ifdef LIBXML_OUTPUT_ENABLED\nXMLPUBFUN void XMLCALL\n\t    xmlSchemaDump\t\t(FILE *output,\n\t\t\t\t\t xmlSchemaPtr schema);\n#endif /* LIBXML_OUTPUT_ENABLED */\n/*\n * Interfaces for validating\n */\nXMLPUBFUN void XMLCALL\n\t    xmlSchemaSetValidErrors\t(xmlSchemaValidCtxtPtr ctxt,\n\t\t\t\t\t xmlSchemaValidityErrorFunc err,\n\t\t\t\t\t xmlSchemaValidityWarningFunc warn,\n\t\t\t\t\t void *ctx);\nXMLPUBFUN void XMLCALL\n\t    xmlSchemaSetValidStructuredErrors(xmlSchemaValidCtxtPtr ctxt,\n\t\t\t\t\t xmlStructuredErrorFunc serror,\n\t\t\t\t\t void *ctx);\nXMLPUBFUN int XMLCALL\n\t    xmlSchemaGetValidErrors\t(xmlSchemaValidCtxtPtr ctxt,\n\t\t\t\t\t xmlSchemaValidityErrorFunc *err,\n\t\t\t\t\t xmlSchemaValidityWarningFunc *warn,\n\t\t\t\t\t void **ctx);\nXMLPUBFUN int XMLCALL\n\t    xmlSchemaSetValidOptions\t(xmlSchemaValidCtxtPtr ctxt,\n\t\t\t\t\t int options);\nXMLPUBFUN void XMLCALL\n            xmlSchemaValidateSetFilename(xmlSchemaValidCtxtPtr vctxt,\n\t                                 const char *filename);\nXMLPUBFUN int XMLCALL\n\t    xmlSchemaValidCtxtGetOptions(xmlSchemaValidCtxtPtr ctxt);\n\nXMLPUBFUN xmlSchemaValidCtxtPtr XMLCALL\n\t    xmlSchemaNewValidCtxt\t(xmlSchemaPtr schema);\nXMLPUBFUN void XMLCALL\n\t    xmlSchemaFreeValidCtxt\t(xmlSchemaValidCtxtPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t    xmlSchemaValidateDoc\t(xmlSchemaValidCtxtPtr ctxt,\n\t\t\t\t\t xmlDocPtr instance);\nXMLPUBFUN int XMLCALL\n            xmlSchemaValidateOneElement (xmlSchemaValidCtxtPtr ctxt,\n\t\t\t                 xmlNodePtr elem);\nXMLPUBFUN int XMLCALL\n\t    xmlSchemaValidateStream\t(xmlSchemaValidCtxtPtr ctxt,\n\t\t\t\t\t xmlParserInputBufferPtr input,\n\t\t\t\t\t xmlCharEncoding enc,\n\t\t\t\t\t xmlSAXHandlerPtr sax,\n\t\t\t\t\t void *user_data);\nXMLPUBFUN int XMLCALL\n\t    xmlSchemaValidateFile\t(xmlSchemaValidCtxtPtr ctxt,\n\t\t\t\t\t const char * filename,\n\t\t\t\t\t int options);\n\nXMLPUBFUN xmlParserCtxtPtr XMLCALL\n\t    xmlSchemaValidCtxtGetParserCtxt(xmlSchemaValidCtxtPtr ctxt);\n\n/*\n * Interface to insert Schemas SAX validation in a SAX stream\n */\ntypedef struct _xmlSchemaSAXPlug xmlSchemaSAXPlugStruct;\ntypedef xmlSchemaSAXPlugStruct *xmlSchemaSAXPlugPtr;\n\nXMLPUBFUN xmlSchemaSAXPlugPtr XMLCALL\n            xmlSchemaSAXPlug\t\t(xmlSchemaValidCtxtPtr ctxt,\n\t\t\t\t\t xmlSAXHandlerPtr *sax,\n\t\t\t\t\t void **user_data);\nXMLPUBFUN int XMLCALL\n            xmlSchemaSAXUnplug\t\t(xmlSchemaSAXPlugPtr plug);\n\n\nXMLPUBFUN void XMLCALL\n            xmlSchemaValidateSetLocator\t(xmlSchemaValidCtxtPtr vctxt,\n\t\t\t\t\t xmlSchemaValidityLocatorFunc f,\n\t\t\t\t\t void *ctxt);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_SCHEMAS_ENABLED */\n#endif /* __XML_SCHEMA_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlschemastypes.h",
    "content": "/*\n * Summary: implementation of XML Schema Datatypes\n * Description: module providing the XML Schema Datatypes implementation\n *              both definition and validity checking\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n\n#ifndef __XML_SCHEMA_TYPES_H__\n#define __XML_SCHEMA_TYPES_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_SCHEMAS_ENABLED\n\n#include <libxml/schemasInternals.h>\n#include <libxml/xmlschemas.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\ntypedef enum {\n    XML_SCHEMA_WHITESPACE_UNKNOWN = 0,\n    XML_SCHEMA_WHITESPACE_PRESERVE = 1,\n    XML_SCHEMA_WHITESPACE_REPLACE = 2,\n    XML_SCHEMA_WHITESPACE_COLLAPSE = 3\n} xmlSchemaWhitespaceValueType;\n\nXMLPUBFUN void XMLCALL\n\t\txmlSchemaInitTypes\t\t(void);\nXMLPUBFUN void XMLCALL\n\t\txmlSchemaCleanupTypes\t\t(void);\nXMLPUBFUN xmlSchemaTypePtr XMLCALL\n\t\txmlSchemaGetPredefinedType\t(const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ns);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaValidatePredefinedType\t(xmlSchemaTypePtr type,\n\t\t\t\t\t\t const xmlChar *value,\n\t\t\t\t\t\t xmlSchemaValPtr *val);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaValPredefTypeNode\t(xmlSchemaTypePtr type,\n\t\t\t\t\t\t const xmlChar *value,\n\t\t\t\t\t\t xmlSchemaValPtr *val,\n\t\t\t\t\t\t xmlNodePtr node);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaValidateFacet\t\t(xmlSchemaTypePtr base,\n\t\t\t\t\t\t xmlSchemaFacetPtr facet,\n\t\t\t\t\t\t const xmlChar *value,\n\t\t\t\t\t\t xmlSchemaValPtr val);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaValidateFacetWhtsp\t(xmlSchemaFacetPtr facet,\n\t\t\t\t\t\t xmlSchemaWhitespaceValueType fws,\n\t\t\t\t\t\t xmlSchemaValType valType,\n\t\t\t\t\t\t const xmlChar *value,\n\t\t\t\t\t\t xmlSchemaValPtr val,\n\t\t\t\t\t\t xmlSchemaWhitespaceValueType ws);\nXMLPUBFUN void XMLCALL\n\t\txmlSchemaFreeValue\t\t(xmlSchemaValPtr val);\nXMLPUBFUN xmlSchemaFacetPtr XMLCALL\n\t\txmlSchemaNewFacet\t\t(void);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaCheckFacet\t\t(xmlSchemaFacetPtr facet,\n\t\t\t\t\t\t xmlSchemaTypePtr typeDecl,\n\t\t\t\t\t\t xmlSchemaParserCtxtPtr ctxt,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN void XMLCALL\n\t\txmlSchemaFreeFacet\t\t(xmlSchemaFacetPtr facet);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaCompareValues\t\t(xmlSchemaValPtr x,\n\t\t\t\t\t\t xmlSchemaValPtr y);\nXMLPUBFUN xmlSchemaTypePtr XMLCALL\n    xmlSchemaGetBuiltInListSimpleTypeItemType\t(xmlSchemaTypePtr type);\nXMLPUBFUN int XMLCALL\n    xmlSchemaValidateListSimpleTypeFacet\t(xmlSchemaFacetPtr facet,\n\t\t\t\t\t\t const xmlChar *value,\n\t\t\t\t\t\t unsigned long actualLen,\n\t\t\t\t\t\t unsigned long *expectedLen);\nXMLPUBFUN xmlSchemaTypePtr XMLCALL\n\t\txmlSchemaGetBuiltInType\t\t(xmlSchemaValType type);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaIsBuiltInTypeFacet\t(xmlSchemaTypePtr type,\n\t\t\t\t\t\t int facetType);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlSchemaCollapseString\t\t(const xmlChar *value);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlSchemaWhiteSpaceReplace\t(const xmlChar *value);\nXMLPUBFUN unsigned long  XMLCALL\n\t\txmlSchemaGetFacetValueAsULong\t(xmlSchemaFacetPtr facet);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaValidateLengthFacet\t(xmlSchemaTypePtr type,\n\t\t\t\t\t\t xmlSchemaFacetPtr facet,\n\t\t\t\t\t\t const xmlChar *value,\n\t\t\t\t\t\t xmlSchemaValPtr val,\n\t\t\t\t\t\t unsigned long *length);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaValidateLengthFacetWhtsp(xmlSchemaFacetPtr facet,\n\t\t\t\t\t\t  xmlSchemaValType valType,\n\t\t\t\t\t\t  const xmlChar *value,\n\t\t\t\t\t\t  xmlSchemaValPtr val,\n\t\t\t\t\t\t  unsigned long *length,\n\t\t\t\t\t\t  xmlSchemaWhitespaceValueType ws);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaValPredefTypeNodeNoNorm(xmlSchemaTypePtr type,\n\t\t\t\t\t\t const xmlChar *value,\n\t\t\t\t\t\t xmlSchemaValPtr *val,\n\t\t\t\t\t\t xmlNodePtr node);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaGetCanonValue\t\t(xmlSchemaValPtr val,\n\t\t\t\t\t\t const xmlChar **retValue);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaGetCanonValueWhtsp\t(xmlSchemaValPtr val,\n\t\t\t\t\t\t const xmlChar **retValue,\n\t\t\t\t\t\t xmlSchemaWhitespaceValueType ws);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaValueAppend\t\t(xmlSchemaValPtr prev,\n\t\t\t\t\t\t xmlSchemaValPtr cur);\nXMLPUBFUN xmlSchemaValPtr XMLCALL\n\t\txmlSchemaValueGetNext\t\t(xmlSchemaValPtr cur);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\txmlSchemaValueGetAsString\t(xmlSchemaValPtr val);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaValueGetAsBoolean\t(xmlSchemaValPtr val);\nXMLPUBFUN xmlSchemaValPtr XMLCALL\n\t\txmlSchemaNewStringValue\t\t(xmlSchemaValType type,\n\t\t\t\t\t\t const xmlChar *value);\nXMLPUBFUN xmlSchemaValPtr XMLCALL\n\t\txmlSchemaNewNOTATIONValue\t(const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ns);\nXMLPUBFUN xmlSchemaValPtr XMLCALL\n\t\txmlSchemaNewQNameValue\t\t(const xmlChar *namespaceName,\n\t\t\t\t\t\t const xmlChar *localName);\nXMLPUBFUN int XMLCALL\n\t\txmlSchemaCompareValuesWhtsp\t(xmlSchemaValPtr x,\n\t\t\t\t\t\t xmlSchemaWhitespaceValueType xws,\n\t\t\t\t\t\t xmlSchemaValPtr y,\n\t\t\t\t\t\t xmlSchemaWhitespaceValueType yws);\nXMLPUBFUN xmlSchemaValPtr XMLCALL\n\t\txmlSchemaCopyValue\t\t(xmlSchemaValPtr val);\nXMLPUBFUN xmlSchemaValType XMLCALL\n\t\txmlSchemaGetValType\t\t(xmlSchemaValPtr val);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_SCHEMAS_ENABLED */\n#endif /* __XML_SCHEMA_TYPES_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlstring.h",
    "content": "/*\n * Summary: set of routines to process strings\n * Description: type and interfaces needed for the internal string handling\n *              of the library, especially UTF8 processing.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_STRING_H__\n#define __XML_STRING_H__\n\n#include <stdarg.h>\n#include <libxml/xmlversion.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * xmlChar:\n *\n * This is a basic byte in an UTF-8 encoded string.\n * It's unsigned allowing to pinpoint case where char * are assigned\n * to xmlChar * (possibly making serialization back impossible).\n */\ntypedef unsigned char xmlChar;\n\n/**\n * BAD_CAST:\n *\n * Macro to cast a string to an xmlChar * when one know its safe.\n */\n#define BAD_CAST (xmlChar *)\n\n/*\n * xmlChar handling\n */\nXMLPUBFUN xmlChar * XMLCALL\n                xmlStrdup                (const xmlChar *cur);\nXMLPUBFUN xmlChar * XMLCALL\n                xmlStrndup               (const xmlChar *cur,\n                                         int len);\nXMLPUBFUN xmlChar * XMLCALL\n                xmlCharStrndup           (const char *cur,\n                                         int len);\nXMLPUBFUN xmlChar * XMLCALL\n                xmlCharStrdup            (const char *cur);\nXMLPUBFUN xmlChar * XMLCALL\n                xmlStrsub                (const xmlChar *str,\n                                         int start,\n                                         int len);\nXMLPUBFUN const xmlChar * XMLCALL\n                xmlStrchr                (const xmlChar *str,\n                                         xmlChar val);\nXMLPUBFUN const xmlChar * XMLCALL\n                xmlStrstr                (const xmlChar *str,\n                                         const xmlChar *val);\nXMLPUBFUN const xmlChar * XMLCALL\n                xmlStrcasestr            (const xmlChar *str,\n                                         const xmlChar *val);\nXMLPUBFUN int XMLCALL\n                xmlStrcmp                (const xmlChar *str1,\n                                         const xmlChar *str2);\nXMLPUBFUN int XMLCALL\n                xmlStrncmp               (const xmlChar *str1,\n                                         const xmlChar *str2,\n                                         int len);\nXMLPUBFUN int XMLCALL\n                xmlStrcasecmp            (const xmlChar *str1,\n                                         const xmlChar *str2);\nXMLPUBFUN int XMLCALL\n                xmlStrncasecmp           (const xmlChar *str1,\n                                         const xmlChar *str2,\n                                         int len);\nXMLPUBFUN int XMLCALL\n                xmlStrEqual              (const xmlChar *str1,\n                                         const xmlChar *str2);\nXMLPUBFUN int XMLCALL\n                xmlStrQEqual             (const xmlChar *pref,\n                                         const xmlChar *name,\n                                         const xmlChar *str);\nXMLPUBFUN int XMLCALL\n                xmlStrlen                (const xmlChar *str);\nXMLPUBFUN xmlChar * XMLCALL\n                xmlStrcat                (xmlChar *cur,\n                                         const xmlChar *add);\nXMLPUBFUN xmlChar * XMLCALL\n                xmlStrncat               (xmlChar *cur,\n                                         const xmlChar *add,\n                                         int len);\nXMLPUBFUN xmlChar * XMLCALL\n                xmlStrncatNew            (const xmlChar *str1,\n                                         const xmlChar *str2,\n                                         int len);\nXMLPUBFUN int XMLCALL\n                xmlStrPrintf             (xmlChar *buf,\n                                         int len,\n                                         const char *msg,\n                                         ...) LIBXML_ATTR_FORMAT(3,4);\nXMLPUBFUN int XMLCALL\n                xmlStrVPrintf                (xmlChar *buf,\n                                         int len,\n                                         const char *msg,\n                                         va_list ap) LIBXML_ATTR_FORMAT(3,0);\n\nXMLPUBFUN int XMLCALL\n        xmlGetUTF8Char                   (const unsigned char *utf,\n                                         int *len);\nXMLPUBFUN int XMLCALL\n        xmlCheckUTF8                     (const unsigned char *utf);\nXMLPUBFUN int XMLCALL\n        xmlUTF8Strsize                   (const xmlChar *utf,\n                                         int len);\nXMLPUBFUN xmlChar * XMLCALL\n        xmlUTF8Strndup                   (const xmlChar *utf,\n                                         int len);\nXMLPUBFUN const xmlChar * XMLCALL\n        xmlUTF8Strpos                    (const xmlChar *utf,\n                                         int pos);\nXMLPUBFUN int XMLCALL\n        xmlUTF8Strloc                    (const xmlChar *utf,\n                                         const xmlChar *utfchar);\nXMLPUBFUN xmlChar * XMLCALL\n        xmlUTF8Strsub                    (const xmlChar *utf,\n                                         int start,\n                                         int len);\nXMLPUBFUN int XMLCALL\n        xmlUTF8Strlen                    (const xmlChar *utf);\nXMLPUBFUN int XMLCALL\n        xmlUTF8Size                      (const xmlChar *utf);\nXMLPUBFUN int XMLCALL\n        xmlUTF8Charcmp                   (const xmlChar *utf1,\n                                         const xmlChar *utf2);\n\n#ifdef __cplusplus\n}\n#endif\n#endif /* __XML_STRING_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlunicode.h",
    "content": "/*\n * Summary: Unicode character APIs\n * Description: API for the Unicode character APIs\n *\n * This file is automatically generated from the\n * UCS description files of the Unicode Character Database\n * http://www.unicode.org/Public/4.0-Update1/UCD-4.0.1.html\n * using the genUnicode.py Python script.\n *\n * Generation date: Mon Mar 27 11:09:52 2006\n * Sources: Blocks-4.0.1.txt UnicodeData-4.0.1.txt\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_UNICODE_H__\n#define __XML_UNICODE_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_UNICODE_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nXMLPUBFUN int XMLCALL xmlUCSIsAegeanNumbers\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsAlphabeticPresentationForms\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsArabic\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsArabicPresentationFormsA\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsArabicPresentationFormsB\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsArmenian\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsArrows\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsBasicLatin\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsBengali\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsBlockElements\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsBopomofo\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsBopomofoExtended\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsBoxDrawing\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsBraillePatterns\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsBuhid\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsByzantineMusicalSymbols\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCJKCompatibility\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCJKCompatibilityForms\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCJKCompatibilityIdeographs\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCJKCompatibilityIdeographsSupplement\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCJKRadicalsSupplement\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCJKSymbolsandPunctuation\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCJKUnifiedIdeographs\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCJKUnifiedIdeographsExtensionA\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCJKUnifiedIdeographsExtensionB\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCherokee\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCombiningDiacriticalMarks\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCombiningDiacriticalMarksforSymbols\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCombiningHalfMarks\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCombiningMarksforSymbols\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsControlPictures\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCurrencySymbols\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCypriotSyllabary\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCyrillic\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCyrillicSupplement\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsDeseret\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsDevanagari\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsDingbats\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsEnclosedAlphanumerics\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsEnclosedCJKLettersandMonths\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsEthiopic\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsGeneralPunctuation\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsGeometricShapes\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsGeorgian\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsGothic\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsGreek\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsGreekExtended\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsGreekandCoptic\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsGujarati\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsGurmukhi\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsHalfwidthandFullwidthForms\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsHangulCompatibilityJamo\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsHangulJamo\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsHangulSyllables\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsHanunoo\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsHebrew\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsHighPrivateUseSurrogates\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsHighSurrogates\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsHiragana\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsIPAExtensions\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsIdeographicDescriptionCharacters\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsKanbun\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsKangxiRadicals\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsKannada\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsKatakana\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsKatakanaPhoneticExtensions\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsKhmer\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsKhmerSymbols\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsLao\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsLatin1Supplement\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsLatinExtendedA\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsLatinExtendedB\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsLatinExtendedAdditional\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsLetterlikeSymbols\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsLimbu\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsLinearBIdeograms\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsLinearBSyllabary\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsLowSurrogates\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsMalayalam\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsMathematicalAlphanumericSymbols\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsMathematicalOperators\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsMiscellaneousMathematicalSymbolsA\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsMiscellaneousMathematicalSymbolsB\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsMiscellaneousSymbols\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsMiscellaneousSymbolsandArrows\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsMiscellaneousTechnical\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsMongolian\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsMusicalSymbols\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsMyanmar\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsNumberForms\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsOgham\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsOldItalic\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsOpticalCharacterRecognition\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsOriya\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsOsmanya\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsPhoneticExtensions\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsPrivateUse\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsPrivateUseArea\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsRunic\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsShavian\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsSinhala\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsSmallFormVariants\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsSpacingModifierLetters\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsSpecials\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsSuperscriptsandSubscripts\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsSupplementalArrowsA\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsSupplementalArrowsB\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsSupplementalMathematicalOperators\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsSupplementaryPrivateUseAreaA\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsSupplementaryPrivateUseAreaB\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsSyriac\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsTagalog\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsTagbanwa\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsTags\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsTaiLe\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsTaiXuanJingSymbols\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsTamil\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsTelugu\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsThaana\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsThai\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsTibetan\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsUgaritic\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsUnifiedCanadianAboriginalSyllabics\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsVariationSelectors\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsVariationSelectorsSupplement\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsYiRadicals\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsYiSyllables\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsYijingHexagramSymbols\t(int code);\n\nXMLPUBFUN int XMLCALL xmlUCSIsBlock\t(int code, const char *block);\n\nXMLPUBFUN int XMLCALL xmlUCSIsCatC\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatCc\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatCf\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatCo\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatCs\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatL\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatLl\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatLm\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatLo\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatLt\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatLu\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatM\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatMc\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatMe\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatMn\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatN\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatNd\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatNl\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatNo\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatP\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatPc\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatPd\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatPe\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatPf\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatPi\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatPo\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatPs\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatS\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatSc\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatSk\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatSm\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatSo\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatZ\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatZl\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatZp\t(int code);\nXMLPUBFUN int XMLCALL xmlUCSIsCatZs\t(int code);\n\nXMLPUBFUN int XMLCALL xmlUCSIsCat\t(int code, const char *cat);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_UNICODE_ENABLED */\n\n#endif /* __XML_UNICODE_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlversion.h",
    "content": "/*\n * Summary: compile-time version informations\n * Description: compile-time version informations for the XML library\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_VERSION_H__\n#define __XML_VERSION_H__\n\n#include <libxml/xmlexports.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * use those to be sure nothing nasty will happen if\n * your library and includes mismatch\n */\n#ifndef LIBXML2_COMPILING_MSCCDEF\nXMLPUBFUN void XMLCALL xmlCheckVersion(int version);\n#endif /* LIBXML2_COMPILING_MSCCDEF */\n\n/**\n * LIBXML_DOTTED_VERSION:\n *\n * the version string like \"1.2.3\"\n */\n#define LIBXML_DOTTED_VERSION \"2.9.9\"\n\n/**\n * LIBXML_VERSION:\n *\n * the version number: 1.2.3 value is 10203\n */\n#define LIBXML_VERSION 20909\n\n/**\n * LIBXML_VERSION_STRING:\n *\n * the version number string, 1.2.3 value is \"10203\"\n */\n#define LIBXML_VERSION_STRING \"20909\"\n\n/**\n * LIBXML_VERSION_EXTRA:\n *\n * extra version information, used to show a CVS compilation\n */\n#define LIBXML_VERSION_EXTRA \"\"\n\n/**\n * LIBXML_TEST_VERSION:\n *\n * Macro to check that the libxml version in use is compatible with\n * the version the software has been compiled against\n */\n#define LIBXML_TEST_VERSION xmlCheckVersion(20909);\n\n#ifndef VMS\n#if 0\n/**\n * WITH_TRIO:\n *\n * defined if the trio support need to be configured in\n */\n#define WITH_TRIO\n#else\n/**\n * WITHOUT_TRIO:\n *\n * defined if the trio support should not be configured in\n */\n#define WITHOUT_TRIO\n#endif\n#else /* VMS */\n/**\n * WITH_TRIO:\n *\n * defined if the trio support need to be configured in\n */\n#define WITH_TRIO 1\n#endif /* VMS */\n\n/**\n * LIBXML_THREAD_ENABLED:\n *\n * Whether the thread support is configured in\n */\n#if 1\n#if defined(_REENTRANT) || defined(__MT__) || \\\n    (defined(_POSIX_C_SOURCE) && (_POSIX_C_SOURCE - 0 >= 199506L))\n#define LIBXML_THREAD_ENABLED\n#endif\n#endif\n\n/**\n * LIBXML_THREAD_ALLOC_ENABLED:\n *\n * Whether the allocation hooks are per-thread\n */\n#if 0\n#define LIBXML_THREAD_ALLOC_ENABLED\n#endif\n\n/**\n * LIBXML_TREE_ENABLED:\n *\n * Whether the DOM like tree manipulation API support is configured in\n */\n#if 1\n#define LIBXML_TREE_ENABLED\n#endif\n\n/**\n * LIBXML_OUTPUT_ENABLED:\n *\n * Whether the serialization/saving support is configured in\n */\n#if 1\n#define LIBXML_OUTPUT_ENABLED\n#endif\n\n/**\n * LIBXML_PUSH_ENABLED:\n *\n * Whether the push parsing interfaces are configured in\n */\n#if 1\n#define LIBXML_PUSH_ENABLED\n#endif\n\n/**\n * LIBXML_READER_ENABLED:\n *\n * Whether the xmlReader parsing interface is configured in\n */\n#if 1\n#define LIBXML_READER_ENABLED\n#endif\n\n/**\n * LIBXML_PATTERN_ENABLED:\n *\n * Whether the xmlPattern node selection interface is configured in\n */\n#if 1\n#define LIBXML_PATTERN_ENABLED\n#endif\n\n/**\n * LIBXML_WRITER_ENABLED:\n *\n * Whether the xmlWriter saving interface is configured in\n */\n#if 1\n#define LIBXML_WRITER_ENABLED\n#endif\n\n/**\n * LIBXML_SAX1_ENABLED:\n *\n * Whether the older SAX1 interface is configured in\n */\n#if 1\n#define LIBXML_SAX1_ENABLED\n#endif\n\n/**\n * LIBXML_FTP_ENABLED:\n *\n * Whether the FTP support is configured in\n */\n#if 1\n#define LIBXML_FTP_ENABLED\n#endif\n\n/**\n * LIBXML_HTTP_ENABLED:\n *\n * Whether the HTTP support is configured in\n */\n#if 1\n#define LIBXML_HTTP_ENABLED\n#endif\n\n/**\n * LIBXML_VALID_ENABLED:\n *\n * Whether the DTD validation support is configured in\n */\n#if 1\n#define LIBXML_VALID_ENABLED\n#endif\n\n/**\n * LIBXML_HTML_ENABLED:\n *\n * Whether the HTML support is configured in\n */\n#if 1\n#define LIBXML_HTML_ENABLED\n#endif\n\n/**\n * LIBXML_LEGACY_ENABLED:\n *\n * Whether the deprecated APIs are compiled in for compatibility\n */\n#if 1\n#define LIBXML_LEGACY_ENABLED\n#endif\n\n/**\n * LIBXML_C14N_ENABLED:\n *\n * Whether the Canonicalization support is configured in\n */\n#if 1\n#define LIBXML_C14N_ENABLED\n#endif\n\n/**\n * LIBXML_CATALOG_ENABLED:\n *\n * Whether the Catalog support is configured in\n */\n#if 1\n#define LIBXML_CATALOG_ENABLED\n#endif\n\n/**\n * LIBXML_DOCB_ENABLED:\n *\n * Whether the SGML Docbook support is configured in\n */\n#if 1\n#define LIBXML_DOCB_ENABLED\n#endif\n\n/**\n * LIBXML_XPATH_ENABLED:\n *\n * Whether XPath is configured in\n */\n#if 1\n#define LIBXML_XPATH_ENABLED\n#endif\n\n/**\n * LIBXML_XPTR_ENABLED:\n *\n * Whether XPointer is configured in\n */\n#if 1\n#define LIBXML_XPTR_ENABLED\n#endif\n\n/**\n * LIBXML_XINCLUDE_ENABLED:\n *\n * Whether XInclude is configured in\n */\n#if 1\n#define LIBXML_XINCLUDE_ENABLED\n#endif\n\n/**\n * LIBXML_ICONV_ENABLED:\n *\n * Whether iconv support is available\n */\n#if 1\n#define LIBXML_ICONV_ENABLED\n#endif\n\n/**\n * LIBXML_ICU_ENABLED:\n *\n * Whether icu support is available\n */\n#if 0\n#define LIBXML_ICU_ENABLED\n#endif\n\n/**\n * LIBXML_ISO8859X_ENABLED:\n *\n * Whether ISO-8859-* support is made available in case iconv is not\n */\n#if 1\n#define LIBXML_ISO8859X_ENABLED\n#endif\n\n/**\n * LIBXML_DEBUG_ENABLED:\n *\n * Whether Debugging module is configured in\n */\n#if 1\n#define LIBXML_DEBUG_ENABLED\n#endif\n\n/**\n * DEBUG_MEMORY_LOCATION:\n *\n * Whether the memory debugging is configured in\n */\n#if 0\n#define DEBUG_MEMORY_LOCATION\n#endif\n\n/**\n * LIBXML_DEBUG_RUNTIME:\n *\n * Whether the runtime debugging is configured in\n */\n#if 0\n#define LIBXML_DEBUG_RUNTIME\n#endif\n\n/**\n * LIBXML_UNICODE_ENABLED:\n *\n * Whether the Unicode related interfaces are compiled in\n */\n#if 1\n#define LIBXML_UNICODE_ENABLED\n#endif\n\n/**\n * LIBXML_REGEXP_ENABLED:\n *\n * Whether the regular expressions interfaces are compiled in\n */\n#if 1\n#define LIBXML_REGEXP_ENABLED\n#endif\n\n/**\n * LIBXML_AUTOMATA_ENABLED:\n *\n * Whether the automata interfaces are compiled in\n */\n#if 1\n#define LIBXML_AUTOMATA_ENABLED\n#endif\n\n/**\n * LIBXML_EXPR_ENABLED:\n *\n * Whether the formal expressions interfaces are compiled in\n */\n#if 1\n#define LIBXML_EXPR_ENABLED\n#endif\n\n/**\n * LIBXML_SCHEMAS_ENABLED:\n *\n * Whether the Schemas validation interfaces are compiled in\n */\n#if 1\n#define LIBXML_SCHEMAS_ENABLED\n#endif\n\n/**\n * LIBXML_SCHEMATRON_ENABLED:\n *\n * Whether the Schematron validation interfaces are compiled in\n */\n#if 1\n#define LIBXML_SCHEMATRON_ENABLED\n#endif\n\n/**\n * LIBXML_MODULES_ENABLED:\n *\n * Whether the module interfaces are compiled in\n */\n#if 1\n#define LIBXML_MODULES_ENABLED\n/**\n * LIBXML_MODULE_EXTENSION:\n *\n * the string suffix used by dynamic modules (usually shared libraries)\n */\n#define LIBXML_MODULE_EXTENSION \".so\" \n#endif\n\n/**\n * LIBXML_ZLIB_ENABLED:\n *\n * Whether the Zlib support is compiled in\n */\n#if 1\n#define LIBXML_ZLIB_ENABLED\n#endif\n\n/**\n * LIBXML_LZMA_ENABLED:\n *\n * Whether the Lzma support is compiled in\n */\n#if 0\n#define LIBXML_LZMA_ENABLED\n#endif\n\n#ifdef __GNUC__\n\n/**\n * ATTRIBUTE_UNUSED:\n *\n * Macro used to signal to GCC unused function parameters\n */\n\n#ifndef ATTRIBUTE_UNUSED\n# if ((__GNUC__ > 2) || ((__GNUC__ == 2) && (__GNUC_MINOR__ >= 7)))\n#  define ATTRIBUTE_UNUSED __attribute__((unused))\n# else\n#  define ATTRIBUTE_UNUSED\n# endif\n#endif\n\n/**\n * LIBXML_ATTR_ALLOC_SIZE:\n *\n * Macro used to indicate to GCC this is an allocator function\n */\n\n#ifndef LIBXML_ATTR_ALLOC_SIZE\n# if (!defined(__clang__) && ((__GNUC__ > 4) || ((__GNUC__ == 4) && (__GNUC_MINOR__ >= 3))))\n#  define LIBXML_ATTR_ALLOC_SIZE(x) __attribute__((alloc_size(x)))\n# else\n#  define LIBXML_ATTR_ALLOC_SIZE(x)\n# endif\n#else\n# define LIBXML_ATTR_ALLOC_SIZE(x)\n#endif\n\n/**\n * LIBXML_ATTR_FORMAT:\n *\n * Macro used to indicate to GCC the parameter are printf like\n */\n\n#ifndef LIBXML_ATTR_FORMAT\n# if ((__GNUC__ > 3) || ((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)))\n#  define LIBXML_ATTR_FORMAT(fmt,args) __attribute__((__format__(__printf__,fmt,args)))\n# else\n#  define LIBXML_ATTR_FORMAT(fmt,args)\n# endif\n#else\n# define LIBXML_ATTR_FORMAT(fmt,args)\n#endif\n\n#else /* ! __GNUC__ */\n/**\n * ATTRIBUTE_UNUSED:\n *\n * Macro used to signal to GCC unused function parameters\n */\n#define ATTRIBUTE_UNUSED\n/**\n * LIBXML_ATTR_ALLOC_SIZE:\n *\n * Macro used to indicate to GCC this is an allocator function\n */\n#define LIBXML_ATTR_ALLOC_SIZE(x)\n/**\n * LIBXML_ATTR_FORMAT:\n *\n * Macro used to indicate to GCC the parameter are printf like\n */\n#define LIBXML_ATTR_FORMAT(fmt,args)\n#endif /* __GNUC__ */\n\n#ifdef __cplusplus\n}\n#endif /* __cplusplus */\n#endif\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xmlwriter.h",
    "content": "/*\n * Summary: text writing API for XML\n * Description: text writing API for XML\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Alfred Mickautsch <alfred@mickautsch.de>\n */\n\n#ifndef __XML_XMLWRITER_H__\n#define __XML_XMLWRITER_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_WRITER_ENABLED\n\n#include <stdarg.h>\n#include <libxml/xmlIO.h>\n#include <libxml/list.h>\n#include <libxml/xmlstring.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n    typedef struct _xmlTextWriter xmlTextWriter;\n    typedef xmlTextWriter *xmlTextWriterPtr;\n\n/*\n * Constructors & Destructor\n */\n    XMLPUBFUN xmlTextWriterPtr XMLCALL\n        xmlNewTextWriter(xmlOutputBufferPtr out);\n    XMLPUBFUN xmlTextWriterPtr XMLCALL\n        xmlNewTextWriterFilename(const char *uri, int compression);\n    XMLPUBFUN xmlTextWriterPtr XMLCALL\n        xmlNewTextWriterMemory(xmlBufferPtr buf, int compression);\n    XMLPUBFUN xmlTextWriterPtr XMLCALL\n        xmlNewTextWriterPushParser(xmlParserCtxtPtr ctxt, int compression);\n    XMLPUBFUN xmlTextWriterPtr XMLCALL\n        xmlNewTextWriterDoc(xmlDocPtr * doc, int compression);\n    XMLPUBFUN xmlTextWriterPtr XMLCALL\n        xmlNewTextWriterTree(xmlDocPtr doc, xmlNodePtr node,\n                             int compression);\n    XMLPUBFUN void XMLCALL xmlFreeTextWriter(xmlTextWriterPtr writer);\n\n/*\n * Functions\n */\n\n\n/*\n * Document\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterStartDocument(xmlTextWriterPtr writer,\n                                   const char *version,\n                                   const char *encoding,\n                                   const char *standalone);\n    XMLPUBFUN int XMLCALL xmlTextWriterEndDocument(xmlTextWriterPtr\n                                                   writer);\n\n/*\n * Comments\n */\n    XMLPUBFUN int XMLCALL xmlTextWriterStartComment(xmlTextWriterPtr\n                                                    writer);\n    XMLPUBFUN int XMLCALL xmlTextWriterEndComment(xmlTextWriterPtr writer);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteFormatComment(xmlTextWriterPtr writer,\n                                        const char *format, ...)\n\t\t\t\t\tLIBXML_ATTR_FORMAT(2,3);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteVFormatComment(xmlTextWriterPtr writer,\n                                         const char *format,\n                                         va_list argptr)\n\t\t\t\t\t LIBXML_ATTR_FORMAT(2,0);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteComment(xmlTextWriterPtr\n                                                    writer,\n                                                    const xmlChar *\n                                                    content);\n\n/*\n * Elements\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterStartElement(xmlTextWriterPtr writer,\n                                  const xmlChar * name);\n    XMLPUBFUN int XMLCALL xmlTextWriterStartElementNS(xmlTextWriterPtr\n                                                      writer,\n                                                      const xmlChar *\n                                                      prefix,\n                                                      const xmlChar * name,\n                                                      const xmlChar *\n                                                      namespaceURI);\n    XMLPUBFUN int XMLCALL xmlTextWriterEndElement(xmlTextWriterPtr writer);\n    XMLPUBFUN int XMLCALL xmlTextWriterFullEndElement(xmlTextWriterPtr\n                                                      writer);\n\n/*\n * Elements conveniency functions\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteFormatElement(xmlTextWriterPtr writer,\n                                        const xmlChar * name,\n                                        const char *format, ...)\n\t\t\t\t\tLIBXML_ATTR_FORMAT(3,4);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteVFormatElement(xmlTextWriterPtr writer,\n                                         const xmlChar * name,\n                                         const char *format,\n                                         va_list argptr)\n\t\t\t\t\t LIBXML_ATTR_FORMAT(3,0);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteElement(xmlTextWriterPtr\n                                                    writer,\n                                                    const xmlChar * name,\n                                                    const xmlChar *\n                                                    content);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteFormatElementNS(xmlTextWriterPtr writer,\n                                          const xmlChar * prefix,\n                                          const xmlChar * name,\n                                          const xmlChar * namespaceURI,\n                                          const char *format, ...)\n\t\t\t\t\t  LIBXML_ATTR_FORMAT(5,6);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteVFormatElementNS(xmlTextWriterPtr writer,\n                                           const xmlChar * prefix,\n                                           const xmlChar * name,\n                                           const xmlChar * namespaceURI,\n                                           const char *format,\n                                           va_list argptr)\n\t\t\t\t\t   LIBXML_ATTR_FORMAT(5,0);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteElementNS(xmlTextWriterPtr\n                                                      writer,\n                                                      const xmlChar *\n                                                      prefix,\n                                                      const xmlChar * name,\n                                                      const xmlChar *\n                                                      namespaceURI,\n                                                      const xmlChar *\n                                                      content);\n\n/*\n * Text\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteFormatRaw(xmlTextWriterPtr writer,\n                                    const char *format, ...)\n\t\t\t\t    LIBXML_ATTR_FORMAT(2,3);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteVFormatRaw(xmlTextWriterPtr writer,\n                                     const char *format, va_list argptr)\n\t\t\t\t     LIBXML_ATTR_FORMAT(2,0);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteRawLen(xmlTextWriterPtr writer,\n                                 const xmlChar * content, int len);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteRaw(xmlTextWriterPtr writer,\n                              const xmlChar * content);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteFormatString(xmlTextWriterPtr\n                                                         writer,\n                                                         const char\n                                                         *format, ...)\n\t\t\t\t\t\t\t LIBXML_ATTR_FORMAT(2,3);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteVFormatString(xmlTextWriterPtr\n                                                          writer,\n                                                          const char\n                                                          *format,\n                                                          va_list argptr)\n\t\t\t\t\t\t\t  LIBXML_ATTR_FORMAT(2,0);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteString(xmlTextWriterPtr writer,\n                                                   const xmlChar *\n                                                   content);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteBase64(xmlTextWriterPtr writer,\n                                                   const char *data,\n                                                   int start, int len);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteBinHex(xmlTextWriterPtr writer,\n                                                   const char *data,\n                                                   int start, int len);\n\n/*\n * Attributes\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterStartAttribute(xmlTextWriterPtr writer,\n                                    const xmlChar * name);\n    XMLPUBFUN int XMLCALL xmlTextWriterStartAttributeNS(xmlTextWriterPtr\n                                                        writer,\n                                                        const xmlChar *\n                                                        prefix,\n                                                        const xmlChar *\n                                                        name,\n                                                        const xmlChar *\n                                                        namespaceURI);\n    XMLPUBFUN int XMLCALL xmlTextWriterEndAttribute(xmlTextWriterPtr\n                                                    writer);\n\n/*\n * Attributes conveniency functions\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteFormatAttribute(xmlTextWriterPtr writer,\n                                          const xmlChar * name,\n                                          const char *format, ...)\n\t\t\t\t\t  LIBXML_ATTR_FORMAT(3,4);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteVFormatAttribute(xmlTextWriterPtr writer,\n                                           const xmlChar * name,\n                                           const char *format,\n                                           va_list argptr)\n\t\t\t\t\t   LIBXML_ATTR_FORMAT(3,0);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteAttribute(xmlTextWriterPtr\n                                                      writer,\n                                                      const xmlChar * name,\n                                                      const xmlChar *\n                                                      content);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteFormatAttributeNS(xmlTextWriterPtr writer,\n                                            const xmlChar * prefix,\n                                            const xmlChar * name,\n                                            const xmlChar * namespaceURI,\n                                            const char *format, ...)\n\t\t\t\t\t    LIBXML_ATTR_FORMAT(5,6);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteVFormatAttributeNS(xmlTextWriterPtr writer,\n                                             const xmlChar * prefix,\n                                             const xmlChar * name,\n                                             const xmlChar * namespaceURI,\n                                             const char *format,\n                                             va_list argptr)\n\t\t\t\t\t     LIBXML_ATTR_FORMAT(5,0);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteAttributeNS(xmlTextWriterPtr\n                                                        writer,\n                                                        const xmlChar *\n                                                        prefix,\n                                                        const xmlChar *\n                                                        name,\n                                                        const xmlChar *\n                                                        namespaceURI,\n                                                        const xmlChar *\n                                                        content);\n\n/*\n * PI's\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterStartPI(xmlTextWriterPtr writer,\n                             const xmlChar * target);\n    XMLPUBFUN int XMLCALL xmlTextWriterEndPI(xmlTextWriterPtr writer);\n\n/*\n * PI conveniency functions\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteFormatPI(xmlTextWriterPtr writer,\n                                   const xmlChar * target,\n                                   const char *format, ...)\n\t\t\t\t   LIBXML_ATTR_FORMAT(3,4);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteVFormatPI(xmlTextWriterPtr writer,\n                                    const xmlChar * target,\n                                    const char *format, va_list argptr)\n\t\t\t\t    LIBXML_ATTR_FORMAT(3,0);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWritePI(xmlTextWriterPtr writer,\n                             const xmlChar * target,\n                             const xmlChar * content);\n\n/**\n * xmlTextWriterWriteProcessingInstruction:\n *\n * This macro maps to xmlTextWriterWritePI\n */\n#define xmlTextWriterWriteProcessingInstruction xmlTextWriterWritePI\n\n/*\n * CDATA\n */\n    XMLPUBFUN int XMLCALL xmlTextWriterStartCDATA(xmlTextWriterPtr writer);\n    XMLPUBFUN int XMLCALL xmlTextWriterEndCDATA(xmlTextWriterPtr writer);\n\n/*\n * CDATA conveniency functions\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteFormatCDATA(xmlTextWriterPtr writer,\n                                      const char *format, ...)\n\t\t\t\t      LIBXML_ATTR_FORMAT(2,3);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteVFormatCDATA(xmlTextWriterPtr writer,\n                                       const char *format, va_list argptr)\n\t\t\t\t       LIBXML_ATTR_FORMAT(2,0);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteCDATA(xmlTextWriterPtr writer,\n                                const xmlChar * content);\n\n/*\n * DTD\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterStartDTD(xmlTextWriterPtr writer,\n                              const xmlChar * name,\n                              const xmlChar * pubid,\n                              const xmlChar * sysid);\n    XMLPUBFUN int XMLCALL xmlTextWriterEndDTD(xmlTextWriterPtr writer);\n\n/*\n * DTD conveniency functions\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteFormatDTD(xmlTextWriterPtr writer,\n                                    const xmlChar * name,\n                                    const xmlChar * pubid,\n                                    const xmlChar * sysid,\n                                    const char *format, ...)\n\t\t\t\t    LIBXML_ATTR_FORMAT(5,6);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteVFormatDTD(xmlTextWriterPtr writer,\n                                     const xmlChar * name,\n                                     const xmlChar * pubid,\n                                     const xmlChar * sysid,\n                                     const char *format, va_list argptr)\n\t\t\t\t     LIBXML_ATTR_FORMAT(5,0);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteDTD(xmlTextWriterPtr writer,\n                              const xmlChar * name,\n                              const xmlChar * pubid,\n                              const xmlChar * sysid,\n                              const xmlChar * subset);\n\n/**\n * xmlTextWriterWriteDocType:\n *\n * this macro maps to xmlTextWriterWriteDTD\n */\n#define xmlTextWriterWriteDocType xmlTextWriterWriteDTD\n\n/*\n * DTD element definition\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterStartDTDElement(xmlTextWriterPtr writer,\n                                     const xmlChar * name);\n    XMLPUBFUN int XMLCALL xmlTextWriterEndDTDElement(xmlTextWriterPtr\n                                                     writer);\n\n/*\n * DTD element definition conveniency functions\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteFormatDTDElement(xmlTextWriterPtr writer,\n                                           const xmlChar * name,\n                                           const char *format, ...)\n\t\t\t\t\t   LIBXML_ATTR_FORMAT(3,4);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteVFormatDTDElement(xmlTextWriterPtr writer,\n                                            const xmlChar * name,\n                                            const char *format,\n                                            va_list argptr)\n\t\t\t\t\t    LIBXML_ATTR_FORMAT(3,0);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteDTDElement(xmlTextWriterPtr\n                                                       writer,\n                                                       const xmlChar *\n                                                       name,\n                                                       const xmlChar *\n                                                       content);\n\n/*\n * DTD attribute list definition\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterStartDTDAttlist(xmlTextWriterPtr writer,\n                                     const xmlChar * name);\n    XMLPUBFUN int XMLCALL xmlTextWriterEndDTDAttlist(xmlTextWriterPtr\n                                                     writer);\n\n/*\n * DTD attribute list definition conveniency functions\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteFormatDTDAttlist(xmlTextWriterPtr writer,\n                                           const xmlChar * name,\n                                           const char *format, ...)\n\t\t\t\t\t   LIBXML_ATTR_FORMAT(3,4);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteVFormatDTDAttlist(xmlTextWriterPtr writer,\n                                            const xmlChar * name,\n                                            const char *format,\n                                            va_list argptr)\n\t\t\t\t\t    LIBXML_ATTR_FORMAT(3,0);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteDTDAttlist(xmlTextWriterPtr\n                                                       writer,\n                                                       const xmlChar *\n                                                       name,\n                                                       const xmlChar *\n                                                       content);\n\n/*\n * DTD entity definition\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterStartDTDEntity(xmlTextWriterPtr writer,\n                                    int pe, const xmlChar * name);\n    XMLPUBFUN int XMLCALL xmlTextWriterEndDTDEntity(xmlTextWriterPtr\n                                                    writer);\n\n/*\n * DTD entity definition conveniency functions\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteFormatDTDInternalEntity(xmlTextWriterPtr writer,\n                                                  int pe,\n                                                  const xmlChar * name,\n                                                  const char *format, ...)\n\t\t\t\t\t\t  LIBXML_ATTR_FORMAT(4,5);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteVFormatDTDInternalEntity(xmlTextWriterPtr writer,\n                                                   int pe,\n                                                   const xmlChar * name,\n                                                   const char *format,\n                                                   va_list argptr)\n\t\t\t\t\t\t   LIBXML_ATTR_FORMAT(4,0);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteDTDInternalEntity(xmlTextWriterPtr writer,\n                                            int pe,\n                                            const xmlChar * name,\n                                            const xmlChar * content);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteDTDExternalEntity(xmlTextWriterPtr writer,\n                                            int pe,\n                                            const xmlChar * name,\n                                            const xmlChar * pubid,\n                                            const xmlChar * sysid,\n                                            const xmlChar * ndataid);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteDTDExternalEntityContents(xmlTextWriterPtr\n                                                    writer,\n                                                    const xmlChar * pubid,\n                                                    const xmlChar * sysid,\n                                                    const xmlChar *\n                                                    ndataid);\n    XMLPUBFUN int XMLCALL xmlTextWriterWriteDTDEntity(xmlTextWriterPtr\n                                                      writer, int pe,\n                                                      const xmlChar * name,\n                                                      const xmlChar *\n                                                      pubid,\n                                                      const xmlChar *\n                                                      sysid,\n                                                      const xmlChar *\n                                                      ndataid,\n                                                      const xmlChar *\n                                                      content);\n\n/*\n * DTD notation definition\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterWriteDTDNotation(xmlTextWriterPtr writer,\n                                      const xmlChar * name,\n                                      const xmlChar * pubid,\n                                      const xmlChar * sysid);\n\n/*\n * Indentation\n */\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterSetIndent(xmlTextWriterPtr writer, int indent);\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterSetIndentString(xmlTextWriterPtr writer,\n                                     const xmlChar * str);\n\n    XMLPUBFUN int XMLCALL\n        xmlTextWriterSetQuoteChar(xmlTextWriterPtr writer, xmlChar quotechar);\n\n\n/*\n * misc\n */\n    XMLPUBFUN int XMLCALL xmlTextWriterFlush(xmlTextWriterPtr writer);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_WRITER_ENABLED */\n\n#endif                          /* __XML_XMLWRITER_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xpath.h",
    "content": "/*\n * Summary: XML Path Language implementation\n * Description: API for the XML Path Language implementation\n *\n * XML Path Language implementation\n * XPath is a language for addressing parts of an XML document,\n * designed to be used by both XSLT and XPointer\n *     http://www.w3.org/TR/xpath\n *\n * Implements\n * W3C Recommendation 16 November 1999\n *     http://www.w3.org/TR/1999/REC-xpath-19991116\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XPATH_H__\n#define __XML_XPATH_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_XPATH_ENABLED\n\n#include <libxml/xmlerror.h>\n#include <libxml/tree.h>\n#include <libxml/hash.h>\n#endif /* LIBXML_XPATH_ENABLED */\n\n#if defined(LIBXML_XPATH_ENABLED) || defined(LIBXML_SCHEMAS_ENABLED)\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n#endif /* LIBXML_XPATH_ENABLED or LIBXML_SCHEMAS_ENABLED */\n\n#ifdef LIBXML_XPATH_ENABLED\n\ntypedef struct _xmlXPathContext xmlXPathContext;\ntypedef xmlXPathContext *xmlXPathContextPtr;\ntypedef struct _xmlXPathParserContext xmlXPathParserContext;\ntypedef xmlXPathParserContext *xmlXPathParserContextPtr;\n\n/**\n * The set of XPath error codes.\n */\n\ntypedef enum {\n    XPATH_EXPRESSION_OK = 0,\n    XPATH_NUMBER_ERROR,\n    XPATH_UNFINISHED_LITERAL_ERROR,\n    XPATH_START_LITERAL_ERROR,\n    XPATH_VARIABLE_REF_ERROR,\n    XPATH_UNDEF_VARIABLE_ERROR,\n    XPATH_INVALID_PREDICATE_ERROR,\n    XPATH_EXPR_ERROR,\n    XPATH_UNCLOSED_ERROR,\n    XPATH_UNKNOWN_FUNC_ERROR,\n    XPATH_INVALID_OPERAND,\n    XPATH_INVALID_TYPE,\n    XPATH_INVALID_ARITY,\n    XPATH_INVALID_CTXT_SIZE,\n    XPATH_INVALID_CTXT_POSITION,\n    XPATH_MEMORY_ERROR,\n    XPTR_SYNTAX_ERROR,\n    XPTR_RESOURCE_ERROR,\n    XPTR_SUB_RESOURCE_ERROR,\n    XPATH_UNDEF_PREFIX_ERROR,\n    XPATH_ENCODING_ERROR,\n    XPATH_INVALID_CHAR_ERROR,\n    XPATH_INVALID_CTXT,\n    XPATH_STACK_ERROR,\n    XPATH_FORBID_VARIABLE_ERROR\n} xmlXPathError;\n\n/*\n * A node-set (an unordered collection of nodes without duplicates).\n */\ntypedef struct _xmlNodeSet xmlNodeSet;\ntypedef xmlNodeSet *xmlNodeSetPtr;\nstruct _xmlNodeSet {\n    int nodeNr;\t\t\t/* number of nodes in the set */\n    int nodeMax;\t\t/* size of the array as allocated */\n    xmlNodePtr *nodeTab;\t/* array of nodes in no particular order */\n    /* @@ with_ns to check wether namespace nodes should be looked at @@ */\n};\n\n/*\n * An expression is evaluated to yield an object, which\n * has one of the following four basic types:\n *   - node-set\n *   - boolean\n *   - number\n *   - string\n *\n * @@ XPointer will add more types !\n */\n\ntypedef enum {\n    XPATH_UNDEFINED = 0,\n    XPATH_NODESET = 1,\n    XPATH_BOOLEAN = 2,\n    XPATH_NUMBER = 3,\n    XPATH_STRING = 4,\n    XPATH_POINT = 5,\n    XPATH_RANGE = 6,\n    XPATH_LOCATIONSET = 7,\n    XPATH_USERS = 8,\n    XPATH_XSLT_TREE = 9  /* An XSLT value tree, non modifiable */\n} xmlXPathObjectType;\n\ntypedef struct _xmlXPathObject xmlXPathObject;\ntypedef xmlXPathObject *xmlXPathObjectPtr;\nstruct _xmlXPathObject {\n    xmlXPathObjectType type;\n    xmlNodeSetPtr nodesetval;\n    int boolval;\n    double floatval;\n    xmlChar *stringval;\n    void *user;\n    int index;\n    void *user2;\n    int index2;\n};\n\n/**\n * xmlXPathConvertFunc:\n * @obj:  an XPath object\n * @type:  the number of the target type\n *\n * A conversion function is associated to a type and used to cast\n * the new type to primitive values.\n *\n * Returns -1 in case of error, 0 otherwise\n */\ntypedef int (*xmlXPathConvertFunc) (xmlXPathObjectPtr obj, int type);\n\n/*\n * Extra type: a name and a conversion function.\n */\n\ntypedef struct _xmlXPathType xmlXPathType;\ntypedef xmlXPathType *xmlXPathTypePtr;\nstruct _xmlXPathType {\n    const xmlChar         *name;\t\t/* the type name */\n    xmlXPathConvertFunc func;\t\t/* the conversion function */\n};\n\n/*\n * Extra variable: a name and a value.\n */\n\ntypedef struct _xmlXPathVariable xmlXPathVariable;\ntypedef xmlXPathVariable *xmlXPathVariablePtr;\nstruct _xmlXPathVariable {\n    const xmlChar       *name;\t\t/* the variable name */\n    xmlXPathObjectPtr value;\t\t/* the value */\n};\n\n/**\n * xmlXPathEvalFunc:\n * @ctxt: an XPath parser context\n * @nargs: the number of arguments passed to the function\n *\n * An XPath evaluation function, the parameters are on the XPath context stack.\n */\n\ntypedef void (*xmlXPathEvalFunc)(xmlXPathParserContextPtr ctxt,\n\t                         int nargs);\n\n/*\n * Extra function: a name and a evaluation function.\n */\n\ntypedef struct _xmlXPathFunct xmlXPathFunct;\ntypedef xmlXPathFunct *xmlXPathFuncPtr;\nstruct _xmlXPathFunct {\n    const xmlChar      *name;\t\t/* the function name */\n    xmlXPathEvalFunc func;\t\t/* the evaluation function */\n};\n\n/**\n * xmlXPathAxisFunc:\n * @ctxt:  the XPath interpreter context\n * @cur:  the previous node being explored on that axis\n *\n * An axis traversal function. To traverse an axis, the engine calls\n * the first time with cur == NULL and repeat until the function returns\n * NULL indicating the end of the axis traversal.\n *\n * Returns the next node in that axis or NULL if at the end of the axis.\n */\n\ntypedef xmlXPathObjectPtr (*xmlXPathAxisFunc) (xmlXPathParserContextPtr ctxt,\n\t\t\t\t xmlXPathObjectPtr cur);\n\n/*\n * Extra axis: a name and an axis function.\n */\n\ntypedef struct _xmlXPathAxis xmlXPathAxis;\ntypedef xmlXPathAxis *xmlXPathAxisPtr;\nstruct _xmlXPathAxis {\n    const xmlChar      *name;\t\t/* the axis name */\n    xmlXPathAxisFunc func;\t\t/* the search function */\n};\n\n/**\n * xmlXPathFunction:\n * @ctxt:  the XPath interprestation context\n * @nargs:  the number of arguments\n *\n * An XPath function.\n * The arguments (if any) are popped out from the context stack\n * and the result is pushed on the stack.\n */\n\ntypedef void (*xmlXPathFunction) (xmlXPathParserContextPtr ctxt, int nargs);\n\n/*\n * Function and Variable Lookup.\n */\n\n/**\n * xmlXPathVariableLookupFunc:\n * @ctxt:  an XPath context\n * @name:  name of the variable\n * @ns_uri:  the namespace name hosting this variable\n *\n * Prototype for callbacks used to plug variable lookup in the XPath\n * engine.\n *\n * Returns the XPath object value or NULL if not found.\n */\ntypedef xmlXPathObjectPtr (*xmlXPathVariableLookupFunc) (void *ctxt,\n                                         const xmlChar *name,\n                                         const xmlChar *ns_uri);\n\n/**\n * xmlXPathFuncLookupFunc:\n * @ctxt:  an XPath context\n * @name:  name of the function\n * @ns_uri:  the namespace name hosting this function\n *\n * Prototype for callbacks used to plug function lookup in the XPath\n * engine.\n *\n * Returns the XPath function or NULL if not found.\n */\ntypedef xmlXPathFunction (*xmlXPathFuncLookupFunc) (void *ctxt,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *ns_uri);\n\n/**\n * xmlXPathFlags:\n * Flags for XPath engine compilation and runtime\n */\n/**\n * XML_XPATH_CHECKNS:\n *\n * check namespaces at compilation\n */\n#define XML_XPATH_CHECKNS (1<<0)\n/**\n * XML_XPATH_NOVAR:\n *\n * forbid variables in expression\n */\n#define XML_XPATH_NOVAR\t  (1<<1)\n\n/**\n * xmlXPathContext:\n *\n * Expression evaluation occurs with respect to a context.\n * he context consists of:\n *    - a node (the context node)\n *    - a node list (the context node list)\n *    - a set of variable bindings\n *    - a function library\n *    - the set of namespace declarations in scope for the expression\n * Following the switch to hash tables, this need to be trimmed up at\n * the next binary incompatible release.\n * The node may be modified when the context is passed to libxml2\n * for an XPath evaluation so you may need to initialize it again\n * before the next call.\n */\n\nstruct _xmlXPathContext {\n    xmlDocPtr doc;\t\t\t/* The current document */\n    xmlNodePtr node;\t\t\t/* The current node */\n\n    int nb_variables_unused;\t\t/* unused (hash table) */\n    int max_variables_unused;\t\t/* unused (hash table) */\n    xmlHashTablePtr varHash;\t\t/* Hash table of defined variables */\n\n    int nb_types;\t\t\t/* number of defined types */\n    int max_types;\t\t\t/* max number of types */\n    xmlXPathTypePtr types;\t\t/* Array of defined types */\n\n    int nb_funcs_unused;\t\t/* unused (hash table) */\n    int max_funcs_unused;\t\t/* unused (hash table) */\n    xmlHashTablePtr funcHash;\t\t/* Hash table of defined funcs */\n\n    int nb_axis;\t\t\t/* number of defined axis */\n    int max_axis;\t\t\t/* max number of axis */\n    xmlXPathAxisPtr axis;\t\t/* Array of defined axis */\n\n    /* the namespace nodes of the context node */\n    xmlNsPtr *namespaces;\t\t/* Array of namespaces */\n    int nsNr;\t\t\t\t/* number of namespace in scope */\n    void *user;\t\t\t\t/* function to free */\n\n    /* extra variables */\n    int contextSize;\t\t\t/* the context size */\n    int proximityPosition;\t\t/* the proximity position */\n\n    /* extra stuff for XPointer */\n    int xptr;\t\t\t\t/* is this an XPointer context? */\n    xmlNodePtr here;\t\t\t/* for here() */\n    xmlNodePtr origin;\t\t\t/* for origin() */\n\n    /* the set of namespace declarations in scope for the expression */\n    xmlHashTablePtr nsHash;\t\t/* The namespaces hash table */\n    xmlXPathVariableLookupFunc varLookupFunc;/* variable lookup func */\n    void *varLookupData;\t\t/* variable lookup data */\n\n    /* Possibility to link in an extra item */\n    void *extra;                        /* needed for XSLT */\n\n    /* The function name and URI when calling a function */\n    const xmlChar *function;\n    const xmlChar *functionURI;\n\n    /* function lookup function and data */\n    xmlXPathFuncLookupFunc funcLookupFunc;/* function lookup func */\n    void *funcLookupData;\t\t/* function lookup data */\n\n    /* temporary namespace lists kept for walking the namespace axis */\n    xmlNsPtr *tmpNsList;\t\t/* Array of namespaces */\n    int tmpNsNr;\t\t\t/* number of namespaces in scope */\n\n    /* error reporting mechanism */\n    void *userData;                     /* user specific data block */\n    xmlStructuredErrorFunc error;       /* the callback in case of errors */\n    xmlError lastError;\t\t\t/* the last error */\n    xmlNodePtr debugNode;\t\t/* the source node XSLT */\n\n    /* dictionary */\n    xmlDictPtr dict;\t\t\t/* dictionary if any */\n\n    int flags;\t\t\t\t/* flags to control compilation */\n\n    /* Cache for reusal of XPath objects */\n    void *cache;\n};\n\n/*\n * The structure of a compiled expression form is not public.\n */\n\ntypedef struct _xmlXPathCompExpr xmlXPathCompExpr;\ntypedef xmlXPathCompExpr *xmlXPathCompExprPtr;\n\n/**\n * xmlXPathParserContext:\n *\n * An XPath parser context. It contains pure parsing informations,\n * an xmlXPathContext, and the stack of objects.\n */\nstruct _xmlXPathParserContext {\n    const xmlChar *cur;\t\t\t/* the current char being parsed */\n    const xmlChar *base;\t\t\t/* the full expression */\n\n    int error;\t\t\t\t/* error code */\n\n    xmlXPathContextPtr  context;\t/* the evaluation context */\n    xmlXPathObjectPtr     value;\t/* the current value */\n    int                 valueNr;\t/* number of values stacked */\n    int                valueMax;\t/* max number of values stacked */\n    xmlXPathObjectPtr *valueTab;\t/* stack of values */\n\n    xmlXPathCompExprPtr comp;\t\t/* the precompiled expression */\n    int xptr;\t\t\t\t/* it this an XPointer expression */\n    xmlNodePtr         ancestor;\t/* used for walking preceding axis */\n\n    int              valueFrame;        /* used to limit Pop on the stack */\n};\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n *\t\t\tPublic API\t\t\t\t\t*\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\n\n/**\n * Objects and Nodesets handling\n */\n\nXMLPUBVAR double xmlXPathNAN;\nXMLPUBVAR double xmlXPathPINF;\nXMLPUBVAR double xmlXPathNINF;\n\n/* These macros may later turn into functions */\n/**\n * xmlXPathNodeSetGetLength:\n * @ns:  a node-set\n *\n * Implement a functionality similar to the DOM NodeList.length.\n *\n * Returns the number of nodes in the node-set.\n */\n#define xmlXPathNodeSetGetLength(ns) ((ns) ? (ns)->nodeNr : 0)\n/**\n * xmlXPathNodeSetItem:\n * @ns:  a node-set\n * @index:  index of a node in the set\n *\n * Implements a functionality similar to the DOM NodeList.item().\n *\n * Returns the xmlNodePtr at the given @index in @ns or NULL if\n *         @index is out of range (0 to length-1)\n */\n#define xmlXPathNodeSetItem(ns, index)\t\t\t\t\\\n\t\t((((ns) != NULL) &&\t\t\t\t\\\n\t\t  ((index) >= 0) && ((index) < (ns)->nodeNr)) ?\t\\\n\t\t (ns)->nodeTab[(index)]\t\t\t\t\\\n\t\t : NULL)\n/**\n * xmlXPathNodeSetIsEmpty:\n * @ns: a node-set\n *\n * Checks whether @ns is empty or not.\n *\n * Returns %TRUE if @ns is an empty node-set.\n */\n#define xmlXPathNodeSetIsEmpty(ns)                                      \\\n    (((ns) == NULL) || ((ns)->nodeNr == 0) || ((ns)->nodeTab == NULL))\n\n\nXMLPUBFUN void XMLCALL\n\t\t    xmlXPathFreeObject\t\t(xmlXPathObjectPtr obj);\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\t    xmlXPathNodeSetCreate\t(xmlNodePtr val);\nXMLPUBFUN void XMLCALL\n\t\t    xmlXPathFreeNodeSetList\t(xmlXPathObjectPtr obj);\nXMLPUBFUN void XMLCALL\n\t\t    xmlXPathFreeNodeSet\t\t(xmlNodeSetPtr obj);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPathObjectCopy\t\t(xmlXPathObjectPtr val);\nXMLPUBFUN int XMLCALL\n\t\t    xmlXPathCmpNodes\t\t(xmlNodePtr node1,\n\t\t\t\t\t\t xmlNodePtr node2);\n/**\n * Conversion functions to basic types.\n */\nXMLPUBFUN int XMLCALL\n\t\t    xmlXPathCastNumberToBoolean\t(double val);\nXMLPUBFUN int XMLCALL\n\t\t    xmlXPathCastStringToBoolean\t(const xmlChar * val);\nXMLPUBFUN int XMLCALL\n\t\t    xmlXPathCastNodeSetToBoolean(xmlNodeSetPtr ns);\nXMLPUBFUN int XMLCALL\n\t\t    xmlXPathCastToBoolean\t(xmlXPathObjectPtr val);\n\nXMLPUBFUN double XMLCALL\n\t\t    xmlXPathCastBooleanToNumber\t(int val);\nXMLPUBFUN double XMLCALL\n\t\t    xmlXPathCastStringToNumber\t(const xmlChar * val);\nXMLPUBFUN double XMLCALL\n\t\t    xmlXPathCastNodeToNumber\t(xmlNodePtr node);\nXMLPUBFUN double XMLCALL\n\t\t    xmlXPathCastNodeSetToNumber\t(xmlNodeSetPtr ns);\nXMLPUBFUN double XMLCALL\n\t\t    xmlXPathCastToNumber\t(xmlXPathObjectPtr val);\n\nXMLPUBFUN xmlChar * XMLCALL\n\t\t    xmlXPathCastBooleanToString\t(int val);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t    xmlXPathCastNumberToString\t(double val);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t    xmlXPathCastNodeToString\t(xmlNodePtr node);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t    xmlXPathCastNodeSetToString\t(xmlNodeSetPtr ns);\nXMLPUBFUN xmlChar * XMLCALL\n\t\t    xmlXPathCastToString\t(xmlXPathObjectPtr val);\n\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPathConvertBoolean\t(xmlXPathObjectPtr val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPathConvertNumber\t(xmlXPathObjectPtr val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPathConvertString\t(xmlXPathObjectPtr val);\n\n/**\n * Context handling.\n */\nXMLPUBFUN xmlXPathContextPtr XMLCALL\n\t\t    xmlXPathNewContext\t\t(xmlDocPtr doc);\nXMLPUBFUN void XMLCALL\n\t\t    xmlXPathFreeContext\t\t(xmlXPathContextPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\t    xmlXPathContextSetCache(xmlXPathContextPtr ctxt,\n\t\t\t\t            int active,\n\t\t\t\t\t    int value,\n\t\t\t\t\t    int options);\n/**\n * Evaluation functions.\n */\nXMLPUBFUN long XMLCALL\n\t\t    xmlXPathOrderDocElems\t(xmlDocPtr doc);\nXMLPUBFUN int XMLCALL\n\t\t    xmlXPathSetContextNode\t(xmlNodePtr node,\n\t\t\t\t\t\t xmlXPathContextPtr ctx);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPathNodeEval\t\t(xmlNodePtr node,\n\t\t\t\t\t\t const xmlChar *str,\n\t\t\t\t\t\t xmlXPathContextPtr ctx);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPathEval\t\t(const xmlChar *str,\n\t\t\t\t\t\t xmlXPathContextPtr ctx);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPathEvalExpression\t(const xmlChar *str,\n\t\t\t\t\t\t xmlXPathContextPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\t    xmlXPathEvalPredicate\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t\t xmlXPathObjectPtr res);\n/**\n * Separate compilation/evaluation entry points.\n */\nXMLPUBFUN xmlXPathCompExprPtr XMLCALL\n\t\t    xmlXPathCompile\t\t(const xmlChar *str);\nXMLPUBFUN xmlXPathCompExprPtr XMLCALL\n\t\t    xmlXPathCtxtCompile\t\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *str);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPathCompiledEval\t(xmlXPathCompExprPtr comp,\n\t\t\t\t\t\t xmlXPathContextPtr ctx);\nXMLPUBFUN int XMLCALL\n\t\t    xmlXPathCompiledEvalToBoolean(xmlXPathCompExprPtr comp,\n\t\t\t\t\t\t xmlXPathContextPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\t    xmlXPathFreeCompExpr\t(xmlXPathCompExprPtr comp);\n#endif /* LIBXML_XPATH_ENABLED */\n#if defined(LIBXML_XPATH_ENABLED) || defined(LIBXML_SCHEMAS_ENABLED)\nXMLPUBFUN void XMLCALL\n\t\t    xmlXPathInit\t\t(void);\nXMLPUBFUN int XMLCALL\n\t\txmlXPathIsNaN\t(double val);\nXMLPUBFUN int XMLCALL\n\t\txmlXPathIsInf\t(double val);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_XPATH_ENABLED or LIBXML_SCHEMAS_ENABLED*/\n#endif /* ! __XML_XPATH_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xpathInternals.h",
    "content": "/*\n * Summary: internal interfaces for XML Path Language implementation\n * Description: internal interfaces for XML Path Language implementation\n *              used to build new modules on top of XPath like XPointer and\n *              XSLT\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XPATH_INTERNALS_H__\n#define __XML_XPATH_INTERNALS_H__\n\n#include <libxml/xmlversion.h>\n#include <libxml/xpath.h>\n\n#ifdef LIBXML_XPATH_ENABLED\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n *\t\t\tHelpers\t\t\t\t\t\t*\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\n\n/*\n * Many of these macros may later turn into functions. They\n * shouldn't be used in #ifdef's preprocessor instructions.\n */\n/**\n * xmlXPathSetError:\n * @ctxt:  an XPath parser context\n * @err:  an xmlXPathError code\n *\n * Raises an error.\n */\n#define xmlXPathSetError(ctxt, err)\t\t\t\t\t\\\n    { xmlXPatherror((ctxt), __FILE__, __LINE__, (err));\t\t\t\\\n      if ((ctxt) != NULL) (ctxt)->error = (err); }\n\n/**\n * xmlXPathSetArityError:\n * @ctxt:  an XPath parser context\n *\n * Raises an XPATH_INVALID_ARITY error.\n */\n#define xmlXPathSetArityError(ctxt)\t\t\t\t\t\\\n    xmlXPathSetError((ctxt), XPATH_INVALID_ARITY)\n\n/**\n * xmlXPathSetTypeError:\n * @ctxt:  an XPath parser context\n *\n * Raises an XPATH_INVALID_TYPE error.\n */\n#define xmlXPathSetTypeError(ctxt)\t\t\t\t\t\\\n    xmlXPathSetError((ctxt), XPATH_INVALID_TYPE)\n\n/**\n * xmlXPathGetError:\n * @ctxt:  an XPath parser context\n *\n * Get the error code of an XPath context.\n *\n * Returns the context error.\n */\n#define xmlXPathGetError(ctxt)\t  ((ctxt)->error)\n\n/**\n * xmlXPathCheckError:\n * @ctxt:  an XPath parser context\n *\n * Check if an XPath error was raised.\n *\n * Returns true if an error has been raised, false otherwise.\n */\n#define xmlXPathCheckError(ctxt)  ((ctxt)->error != XPATH_EXPRESSION_OK)\n\n/**\n * xmlXPathGetDocument:\n * @ctxt:  an XPath parser context\n *\n * Get the document of an XPath context.\n *\n * Returns the context document.\n */\n#define xmlXPathGetDocument(ctxt)\t((ctxt)->context->doc)\n\n/**\n * xmlXPathGetContextNode:\n * @ctxt: an XPath parser context\n *\n * Get the context node of an XPath context.\n *\n * Returns the context node.\n */\n#define xmlXPathGetContextNode(ctxt)\t((ctxt)->context->node)\n\nXMLPUBFUN int XMLCALL\n\t\txmlXPathPopBoolean\t(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN double XMLCALL\n\t\txmlXPathPopNumber\t(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlXPathPopString\t(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathPopNodeSet\t(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN void * XMLCALL\n\t\txmlXPathPopExternal\t(xmlXPathParserContextPtr ctxt);\n\n/**\n * xmlXPathReturnBoolean:\n * @ctxt:  an XPath parser context\n * @val:  a boolean\n *\n * Pushes the boolean @val on the context stack.\n */\n#define xmlXPathReturnBoolean(ctxt, val)\t\t\t\t\\\n    valuePush((ctxt), xmlXPathNewBoolean(val))\n\n/**\n * xmlXPathReturnTrue:\n * @ctxt:  an XPath parser context\n *\n * Pushes true on the context stack.\n */\n#define xmlXPathReturnTrue(ctxt)   xmlXPathReturnBoolean((ctxt), 1)\n\n/**\n * xmlXPathReturnFalse:\n * @ctxt:  an XPath parser context\n *\n * Pushes false on the context stack.\n */\n#define xmlXPathReturnFalse(ctxt)  xmlXPathReturnBoolean((ctxt), 0)\n\n/**\n * xmlXPathReturnNumber:\n * @ctxt:  an XPath parser context\n * @val:  a double\n *\n * Pushes the double @val on the context stack.\n */\n#define xmlXPathReturnNumber(ctxt, val)\t\t\t\t\t\\\n    valuePush((ctxt), xmlXPathNewFloat(val))\n\n/**\n * xmlXPathReturnString:\n * @ctxt:  an XPath parser context\n * @str:  a string\n *\n * Pushes the string @str on the context stack.\n */\n#define xmlXPathReturnString(ctxt, str)\t\t\t\t\t\\\n    valuePush((ctxt), xmlXPathWrapString(str))\n\n/**\n * xmlXPathReturnEmptyString:\n * @ctxt:  an XPath parser context\n *\n * Pushes an empty string on the stack.\n */\n#define xmlXPathReturnEmptyString(ctxt)\t\t\t\t\t\\\n    valuePush((ctxt), xmlXPathNewCString(\"\"))\n\n/**\n * xmlXPathReturnNodeSet:\n * @ctxt:  an XPath parser context\n * @ns:  a node-set\n *\n * Pushes the node-set @ns on the context stack.\n */\n#define xmlXPathReturnNodeSet(ctxt, ns)\t\t\t\t\t\\\n    valuePush((ctxt), xmlXPathWrapNodeSet(ns))\n\n/**\n * xmlXPathReturnEmptyNodeSet:\n * @ctxt:  an XPath parser context\n *\n * Pushes an empty node-set on the context stack.\n */\n#define xmlXPathReturnEmptyNodeSet(ctxt)\t\t\t\t\\\n    valuePush((ctxt), xmlXPathNewNodeSet(NULL))\n\n/**\n * xmlXPathReturnExternal:\n * @ctxt:  an XPath parser context\n * @val:  user data\n *\n * Pushes user data on the context stack.\n */\n#define xmlXPathReturnExternal(ctxt, val)\t\t\t\t\\\n    valuePush((ctxt), xmlXPathWrapExternal(val))\n\n/**\n * xmlXPathStackIsNodeSet:\n * @ctxt: an XPath parser context\n *\n * Check if the current value on the XPath stack is a node set or\n * an XSLT value tree.\n *\n * Returns true if the current object on the stack is a node-set.\n */\n#define xmlXPathStackIsNodeSet(ctxt)\t\t\t\t\t\\\n    (((ctxt)->value != NULL)\t\t\t\t\t\t\\\n     && (((ctxt)->value->type == XPATH_NODESET)\t\t\t\t\\\n         || ((ctxt)->value->type == XPATH_XSLT_TREE)))\n\n/**\n * xmlXPathStackIsExternal:\n * @ctxt: an XPath parser context\n *\n * Checks if the current value on the XPath stack is an external\n * object.\n *\n * Returns true if the current object on the stack is an external\n * object.\n */\n#define xmlXPathStackIsExternal(ctxt)\t\t\t\t\t\\\n\t((ctxt->value != NULL) && (ctxt->value->type == XPATH_USERS))\n\n/**\n * xmlXPathEmptyNodeSet:\n * @ns:  a node-set\n *\n * Empties a node-set.\n */\n#define xmlXPathEmptyNodeSet(ns)\t\t\t\t\t\\\n    { while ((ns)->nodeNr > 0) (ns)->nodeTab[--(ns)->nodeNr] = NULL; }\n\n/**\n * CHECK_ERROR:\n *\n * Macro to return from the function if an XPath error was detected.\n */\n#define CHECK_ERROR\t\t\t\t\t\t\t\\\n    if (ctxt->error != XPATH_EXPRESSION_OK) return\n\n/**\n * CHECK_ERROR0:\n *\n * Macro to return 0 from the function if an XPath error was detected.\n */\n#define CHECK_ERROR0\t\t\t\t\t\t\t\\\n    if (ctxt->error != XPATH_EXPRESSION_OK) return(0)\n\n/**\n * XP_ERROR:\n * @X:  the error code\n *\n * Macro to raise an XPath error and return.\n */\n#define XP_ERROR(X)\t\t\t\t\t\t\t\\\n    { xmlXPathErr(ctxt, X); return; }\n\n/**\n * XP_ERROR0:\n * @X:  the error code\n *\n * Macro to raise an XPath error and return 0.\n */\n#define XP_ERROR0(X)\t\t\t\t\t\t\t\\\n    { xmlXPathErr(ctxt, X); return(0); }\n\n/**\n * CHECK_TYPE:\n * @typeval:  the XPath type\n *\n * Macro to check that the value on top of the XPath stack is of a given\n * type.\n */\n#define CHECK_TYPE(typeval)\t\t\t\t\t\t\\\n    if ((ctxt->value == NULL) || (ctxt->value->type != typeval))\t\\\n        XP_ERROR(XPATH_INVALID_TYPE)\n\n/**\n * CHECK_TYPE0:\n * @typeval:  the XPath type\n *\n * Macro to check that the value on top of the XPath stack is of a given\n * type. Return(0) in case of failure\n */\n#define CHECK_TYPE0(typeval)\t\t\t\t\t\t\\\n    if ((ctxt->value == NULL) || (ctxt->value->type != typeval))\t\\\n        XP_ERROR0(XPATH_INVALID_TYPE)\n\n/**\n * CHECK_ARITY:\n * @x:  the number of expected args\n *\n * Macro to check that the number of args passed to an XPath function matches.\n */\n#define CHECK_ARITY(x)\t\t\t\t\t\t\t\\\n    if (ctxt == NULL) return;\t\t\t\t\t\t\\\n    if (nargs != (x))\t\t\t\t\t\t\t\\\n        XP_ERROR(XPATH_INVALID_ARITY);\t\t\t\t\t\\\n    if (ctxt->valueNr < ctxt->valueFrame + (x))\t\t\t\t\\\n        XP_ERROR(XPATH_STACK_ERROR);\n\n/**\n * CAST_TO_STRING:\n *\n * Macro to try to cast the value on the top of the XPath stack to a string.\n */\n#define CAST_TO_STRING\t\t\t\t\t\t\t\\\n    if ((ctxt->value != NULL) && (ctxt->value->type != XPATH_STRING))\t\\\n        xmlXPathStringFunction(ctxt, 1);\n\n/**\n * CAST_TO_NUMBER:\n *\n * Macro to try to cast the value on the top of the XPath stack to a number.\n */\n#define CAST_TO_NUMBER\t\t\t\t\t\t\t\\\n    if ((ctxt->value != NULL) && (ctxt->value->type != XPATH_NUMBER))\t\\\n        xmlXPathNumberFunction(ctxt, 1);\n\n/**\n * CAST_TO_BOOLEAN:\n *\n * Macro to try to cast the value on the top of the XPath stack to a boolean.\n */\n#define CAST_TO_BOOLEAN\t\t\t\t\t\t\t\\\n    if ((ctxt->value != NULL) && (ctxt->value->type != XPATH_BOOLEAN))\t\\\n        xmlXPathBooleanFunction(ctxt, 1);\n\n/*\n * Variable Lookup forwarding.\n */\n\nXMLPUBFUN void XMLCALL\n\txmlXPathRegisterVariableLookup\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t xmlXPathVariableLookupFunc f,\n\t\t\t\t\t void *data);\n\n/*\n * Function Lookup forwarding.\n */\n\nXMLPUBFUN void XMLCALL\n\t    xmlXPathRegisterFuncLookup\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t xmlXPathFuncLookupFunc f,\n\t\t\t\t\t void *funcCtxt);\n\n/*\n * Error reporting.\n */\nXMLPUBFUN void XMLCALL\n\t\txmlXPatherror\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t const char *file,\n\t\t\t\t int line,\n\t\t\t\t int no);\n\nXMLPUBFUN void XMLCALL\n\t\txmlXPathErr\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t int error);\n\n#ifdef LIBXML_DEBUG_ENABLED\nXMLPUBFUN void XMLCALL\n\t\txmlXPathDebugDumpObject\t(FILE *output,\n\t\t\t\t\t xmlXPathObjectPtr cur,\n\t\t\t\t\t int depth);\nXMLPUBFUN void XMLCALL\n\t    xmlXPathDebugDumpCompExpr(FILE *output,\n\t\t\t\t\t xmlXPathCompExprPtr comp,\n\t\t\t\t\t int depth);\n#endif\n/**\n * NodeSet handling.\n */\nXMLPUBFUN int XMLCALL\n\t\txmlXPathNodeSetContains\t\t(xmlNodeSetPtr cur,\n\t\t\t\t\t\t xmlNodePtr val);\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathDifference\t\t(xmlNodeSetPtr nodes1,\n\t\t\t\t\t\t xmlNodeSetPtr nodes2);\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathIntersection\t\t(xmlNodeSetPtr nodes1,\n\t\t\t\t\t\t xmlNodeSetPtr nodes2);\n\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathDistinctSorted\t\t(xmlNodeSetPtr nodes);\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathDistinct\t\t(xmlNodeSetPtr nodes);\n\nXMLPUBFUN int XMLCALL\n\t\txmlXPathHasSameNodes\t\t(xmlNodeSetPtr nodes1,\n\t\t\t\t\t\t xmlNodeSetPtr nodes2);\n\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathNodeLeadingSorted\t(xmlNodeSetPtr nodes,\n\t\t\t\t\t\t xmlNodePtr node);\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathLeadingSorted\t\t(xmlNodeSetPtr nodes1,\n\t\t\t\t\t\t xmlNodeSetPtr nodes2);\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathNodeLeading\t\t(xmlNodeSetPtr nodes,\n\t\t\t\t\t\t xmlNodePtr node);\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathLeading\t\t\t(xmlNodeSetPtr nodes1,\n\t\t\t\t\t\t xmlNodeSetPtr nodes2);\n\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathNodeTrailingSorted\t(xmlNodeSetPtr nodes,\n\t\t\t\t\t\t xmlNodePtr node);\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathTrailingSorted\t\t(xmlNodeSetPtr nodes1,\n\t\t\t\t\t\t xmlNodeSetPtr nodes2);\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathNodeTrailing\t\t(xmlNodeSetPtr nodes,\n\t\t\t\t\t\t xmlNodePtr node);\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathTrailing\t\t(xmlNodeSetPtr nodes1,\n\t\t\t\t\t\t xmlNodeSetPtr nodes2);\n\n\n/**\n * Extending a context.\n */\n\nXMLPUBFUN int XMLCALL\n\t\txmlXPathRegisterNs\t\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *prefix,\n\t\t\t\t\t\t const xmlChar *ns_uri);\nXMLPUBFUN const xmlChar * XMLCALL\n\t\txmlXPathNsLookup\t\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *prefix);\nXMLPUBFUN void XMLCALL\n\t\txmlXPathRegisteredNsCleanup\t(xmlXPathContextPtr ctxt);\n\nXMLPUBFUN int XMLCALL\n\t\txmlXPathRegisterFunc\t\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t xmlXPathFunction f);\nXMLPUBFUN int XMLCALL\n\t\txmlXPathRegisterFuncNS\t\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ns_uri,\n\t\t\t\t\t\t xmlXPathFunction f);\nXMLPUBFUN int XMLCALL\n\t\txmlXPathRegisterVariable\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t xmlXPathObjectPtr value);\nXMLPUBFUN int XMLCALL\n\t\txmlXPathRegisterVariableNS\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ns_uri,\n\t\t\t\t\t\t xmlXPathObjectPtr value);\nXMLPUBFUN xmlXPathFunction XMLCALL\n\t\txmlXPathFunctionLookup\t\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlXPathFunction XMLCALL\n\t\txmlXPathFunctionLookupNS\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ns_uri);\nXMLPUBFUN void XMLCALL\n\t\txmlXPathRegisteredFuncsCleanup\t(xmlXPathContextPtr ctxt);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathVariableLookup\t\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *name);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathVariableLookupNS\t(xmlXPathContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ns_uri);\nXMLPUBFUN void XMLCALL\n\t\txmlXPathRegisteredVariablesCleanup(xmlXPathContextPtr ctxt);\n\n/**\n * Utilities to extend XPath.\n */\nXMLPUBFUN xmlXPathParserContextPtr XMLCALL\n\t\t  xmlXPathNewParserContext\t(const xmlChar *str,\n\t\t\t\t\t\t xmlXPathContextPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\txmlXPathFreeParserContext\t(xmlXPathParserContextPtr ctxt);\n\n/* TODO: remap to xmlXPathValuePop and Push. */\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\tvaluePop\t\t\t(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN int XMLCALL\n\t\tvaluePush\t\t\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t\t\t xmlXPathObjectPtr value);\n\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathNewString\t\t(const xmlChar *val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathNewCString\t\t(const char *val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathWrapString\t\t(xmlChar *val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathWrapCString\t\t(char * val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathNewFloat\t\t(double val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathNewBoolean\t\t(int val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathNewNodeSet\t\t(xmlNodePtr val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathNewValueTree\t\t(xmlNodePtr val);\nXMLPUBFUN int XMLCALL\n\t\txmlXPathNodeSetAdd\t\t(xmlNodeSetPtr cur,\n\t\t\t\t\t\t xmlNodePtr val);\nXMLPUBFUN int XMLCALL\n\t\txmlXPathNodeSetAddUnique\t(xmlNodeSetPtr cur,\n\t\t\t\t\t\t xmlNodePtr val);\nXMLPUBFUN int XMLCALL\n\t\txmlXPathNodeSetAddNs\t\t(xmlNodeSetPtr cur,\n\t\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t\t xmlNsPtr ns);\nXMLPUBFUN void XMLCALL\n\t\txmlXPathNodeSetSort\t\t(xmlNodeSetPtr set);\n\nXMLPUBFUN void XMLCALL\n\t\txmlXPathRoot\t\t\t(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN void XMLCALL\n\t\txmlXPathEvalExpr\t\t(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlXPathParseName\t\t(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN xmlChar * XMLCALL\n\t\txmlXPathParseNCName\t\t(xmlXPathParserContextPtr ctxt);\n\n/*\n * Existing functions.\n */\nXMLPUBFUN double XMLCALL\n\t\txmlXPathStringEvalNumber\t(const xmlChar *str);\nXMLPUBFUN int XMLCALL\n\t\txmlXPathEvaluatePredicateResult (xmlXPathParserContextPtr ctxt,\n\t\t\t\t\t\t xmlXPathObjectPtr res);\nXMLPUBFUN void XMLCALL\n\t\txmlXPathRegisterAllFunctions\t(xmlXPathContextPtr ctxt);\nXMLPUBFUN xmlNodeSetPtr XMLCALL\n\t\txmlXPathNodeSetMerge\t\t(xmlNodeSetPtr val1,\n\t\t\t\t\t\t xmlNodeSetPtr val2);\nXMLPUBFUN void XMLCALL\n\t\txmlXPathNodeSetDel\t\t(xmlNodeSetPtr cur,\n\t\t\t\t\t\t xmlNodePtr val);\nXMLPUBFUN void XMLCALL\n\t\txmlXPathNodeSetRemove\t\t(xmlNodeSetPtr cur,\n\t\t\t\t\t\t int val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathNewNodeSetList\t\t(xmlNodeSetPtr val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathWrapNodeSet\t\t(xmlNodeSetPtr val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\txmlXPathWrapExternal\t\t(void *val);\n\nXMLPUBFUN int XMLCALL xmlXPathEqualValues(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN int XMLCALL xmlXPathNotEqualValues(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN int XMLCALL xmlXPathCompareValues(xmlXPathParserContextPtr ctxt, int inf, int strict);\nXMLPUBFUN void XMLCALL xmlXPathValueFlipSign(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN void XMLCALL xmlXPathAddValues(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN void XMLCALL xmlXPathSubValues(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN void XMLCALL xmlXPathMultValues(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN void XMLCALL xmlXPathDivValues(xmlXPathParserContextPtr ctxt);\nXMLPUBFUN void XMLCALL xmlXPathModValues(xmlXPathParserContextPtr ctxt);\n\nXMLPUBFUN int XMLCALL xmlXPathIsNodeType(const xmlChar *name);\n\n/*\n * Some of the axis navigation routines.\n */\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextSelf(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextChild(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextDescendant(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextDescendantOrSelf(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextParent(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextAncestorOrSelf(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextFollowingSibling(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextFollowing(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextNamespace(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextAttribute(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextPreceding(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextAncestor(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\nXMLPUBFUN xmlNodePtr XMLCALL xmlXPathNextPrecedingSibling(xmlXPathParserContextPtr ctxt,\n\t\t\txmlNodePtr cur);\n/*\n * The official core of XPath functions.\n */\nXMLPUBFUN void XMLCALL xmlXPathLastFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathPositionFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathCountFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathIdFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathLocalNameFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathNamespaceURIFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathStringFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathStringLengthFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathConcatFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathContainsFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathStartsWithFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathSubstringFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathSubstringBeforeFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathSubstringAfterFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathNormalizeFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathTranslateFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathNotFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathTrueFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathFalseFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathLangFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathNumberFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathSumFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathFloorFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathCeilingFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathRoundFunction(xmlXPathParserContextPtr ctxt, int nargs);\nXMLPUBFUN void XMLCALL xmlXPathBooleanFunction(xmlXPathParserContextPtr ctxt, int nargs);\n\n/**\n * Really internal functions\n */\nXMLPUBFUN void XMLCALL xmlXPathNodeSetFreeNs(xmlNsPtr ns);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_XPATH_ENABLED */\n#endif /* ! __XML_XPATH_INTERNALS_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxml/xpointer.h",
    "content": "/*\n * Summary: API to handle XML Pointers\n * Description: API to handle XML Pointers\n * Base implementation was made accordingly to\n * W3C Candidate Recommendation 7 June 2000\n * http://www.w3.org/TR/2000/CR-xptr-20000607\n *\n * Added support for the element() scheme described in:\n * W3C Proposed Recommendation 13 November 2002\n * http://www.w3.org/TR/2002/PR-xptr-element-20021113/\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XPTR_H__\n#define __XML_XPTR_H__\n\n#include <libxml/xmlversion.h>\n\n#ifdef LIBXML_XPTR_ENABLED\n\n#include <libxml/tree.h>\n#include <libxml/xpath.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * A Location Set\n */\ntypedef struct _xmlLocationSet xmlLocationSet;\ntypedef xmlLocationSet *xmlLocationSetPtr;\nstruct _xmlLocationSet {\n    int locNr;\t\t      /* number of locations in the set */\n    int locMax;\t\t      /* size of the array as allocated */\n    xmlXPathObjectPtr *locTab;/* array of locations */\n};\n\n/*\n * Handling of location sets.\n */\n\nXMLPUBFUN xmlLocationSetPtr XMLCALL\n\t\t    xmlXPtrLocationSetCreate\t(xmlXPathObjectPtr val);\nXMLPUBFUN void XMLCALL\n\t\t    xmlXPtrFreeLocationSet\t(xmlLocationSetPtr obj);\nXMLPUBFUN xmlLocationSetPtr XMLCALL\n\t\t    xmlXPtrLocationSetMerge\t(xmlLocationSetPtr val1,\n\t\t\t\t\t\t xmlLocationSetPtr val2);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPtrNewRange\t\t(xmlNodePtr start,\n\t\t\t\t\t\t int startindex,\n\t\t\t\t\t\t xmlNodePtr end,\n\t\t\t\t\t\t int endindex);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPtrNewRangePoints\t(xmlXPathObjectPtr start,\n\t\t\t\t\t\t xmlXPathObjectPtr end);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPtrNewRangeNodePoint\t(xmlNodePtr start,\n\t\t\t\t\t\t xmlXPathObjectPtr end);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPtrNewRangePointNode\t(xmlXPathObjectPtr start,\n\t\t\t\t\t\t xmlNodePtr end);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPtrNewRangeNodes\t(xmlNodePtr start,\n\t\t\t\t\t\t xmlNodePtr end);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPtrNewLocationSetNodes\t(xmlNodePtr start,\n\t\t\t\t\t\t xmlNodePtr end);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPtrNewLocationSetNodeSet(xmlNodeSetPtr set);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPtrNewRangeNodeObject\t(xmlNodePtr start,\n\t\t\t\t\t\t xmlXPathObjectPtr end);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPtrNewCollapsedRange\t(xmlNodePtr start);\nXMLPUBFUN void XMLCALL\n\t\t    xmlXPtrLocationSetAdd\t(xmlLocationSetPtr cur,\n\t\t\t\t\t\t xmlXPathObjectPtr val);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPtrWrapLocationSet\t(xmlLocationSetPtr val);\nXMLPUBFUN void XMLCALL\n\t\t    xmlXPtrLocationSetDel\t(xmlLocationSetPtr cur,\n\t\t\t\t\t\t xmlXPathObjectPtr val);\nXMLPUBFUN void XMLCALL\n\t\t    xmlXPtrLocationSetRemove\t(xmlLocationSetPtr cur,\n\t\t\t\t\t\t int val);\n\n/*\n * Functions.\n */\nXMLPUBFUN xmlXPathContextPtr XMLCALL\n\t\t    xmlXPtrNewContext\t\t(xmlDocPtr doc,\n\t\t\t\t\t\t xmlNodePtr here,\n\t\t\t\t\t\t xmlNodePtr origin);\nXMLPUBFUN xmlXPathObjectPtr XMLCALL\n\t\t    xmlXPtrEval\t\t\t(const xmlChar *str,\n\t\t\t\t\t\t xmlXPathContextPtr ctx);\nXMLPUBFUN void XMLCALL\n\t\t    xmlXPtrRangeToFunction\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t\t\t int nargs);\nXMLPUBFUN xmlNodePtr XMLCALL\n\t\t    xmlXPtrBuildNodeList\t(xmlXPathObjectPtr obj);\nXMLPUBFUN void XMLCALL\n\t\t    xmlXPtrEvalRangePredicate\t(xmlXPathParserContextPtr ctxt);\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* LIBXML_XPTR_ENABLED */\n#endif /* __XML_XPTR_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/attributes.h",
    "content": "/*\n * Summary: interface for the XSLT attribute handling\n * Description: this module handles the specificities of attribute\n *              and attribute groups processing.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_ATTRIBUTES_H__\n#define __XML_XSLT_ATTRIBUTES_H__\n\n#include <libxml/tree.h>\n#include \"xsltexports.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nXSLTPUBFUN void XSLTCALL\n\txsltParseStylesheetAttributeSet\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlNodePtr cur);\nXSLTPUBFUN void XSLTCALL\n\txsltFreeAttributeSetsHashes\t(xsltStylesheetPtr style);\nXSLTPUBFUN void XSLTCALL\n\txsltApplyAttributeSet\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t const xmlChar *attributes);\nXSLTPUBFUN void XSLTCALL\n\txsltResolveStylesheetAttributeSet(xsltStylesheetPtr style);\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_ATTRIBUTES_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/documents.h",
    "content": "/*\n * Summary: interface for the document handling\n * Description: implements document loading and cache (multiple\n *              document() reference for the same resources must\n *              be equal.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_DOCUMENTS_H__\n#define __XML_XSLT_DOCUMENTS_H__\n\n#include <libxml/tree.h>\n#include \"xsltexports.h\"\n#include \"xsltInternals.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nXSLTPUBFUN xsltDocumentPtr XSLTCALL\n\t\txsltNewDocument\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc);\nXSLTPUBFUN xsltDocumentPtr XSLTCALL\n\t\txsltLoadDocument\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t const xmlChar *URI);\nXSLTPUBFUN xsltDocumentPtr XSLTCALL\n\t\txsltFindDocument\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlDocPtr doc);\nXSLTPUBFUN void XSLTCALL\n\t\txsltFreeDocuments\t(xsltTransformContextPtr ctxt);\n\nXSLTPUBFUN xsltDocumentPtr XSLTCALL\n\t\txsltLoadStyleDocument\t(xsltStylesheetPtr style,\n\t\t\t\t\t const xmlChar *URI);\nXSLTPUBFUN xsltDocumentPtr XSLTCALL\n\t\txsltNewStyleDocument\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlDocPtr doc);\nXSLTPUBFUN void XSLTCALL\n\t\txsltFreeStyleDocuments\t(xsltStylesheetPtr style);\n\n/*\n * Hooks for document loading\n */\n\n/**\n * xsltLoadType:\n *\n * Enum defining the kind of loader requirement.\n */\ntypedef enum {\n    XSLT_LOAD_START = 0,\t/* loading for a top stylesheet */\n    XSLT_LOAD_STYLESHEET = 1,\t/* loading for a stylesheet include/import */\n    XSLT_LOAD_DOCUMENT = 2\t/* loading document at transformation time */\n} xsltLoadType;\n\n/**\n * xsltDocLoaderFunc:\n * @URI: the URI of the document to load\n * @dict: the dictionary to use when parsing that document\n * @options: parsing options, a set of xmlParserOption\n * @ctxt: the context, either a stylesheet or a transformation context\n * @type: the xsltLoadType indicating the kind of loading required\n *\n * An xsltDocLoaderFunc is a signature for a function which can be\n * registered to load document not provided by the compilation or\n * transformation API themselve, for example when an xsl:import,\n * xsl:include is found at compilation time or when a document()\n * call is made at runtime.\n *\n * Returns the pointer to the document (which will be modified and\n * freed by the engine later), or NULL in case of error.\n */\ntypedef xmlDocPtr (*xsltDocLoaderFunc)\t\t(const xmlChar *URI,\n\t\t\t\t\t\t xmlDictPtr dict,\n\t\t\t\t\t\t int options,\n\t\t\t\t\t\t void *ctxt,\n\t\t\t\t\t\t xsltLoadType type);\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltSetLoaderFunc\t\t(xsltDocLoaderFunc f);\n\n/* the loader may be needed by extension libraries so it is exported */\nXSLTPUBVAR xsltDocLoaderFunc xsltDocDefaultLoader;\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_DOCUMENTS_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/extensions.h",
    "content": "/*\n * Summary: interface for the extension support\n * Description: This provide the API needed for simple and module\n *              extension support.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_EXTENSION_H__\n#define __XML_XSLT_EXTENSION_H__\n\n#include <libxml/xpath.h>\n#include \"xsltexports.h\"\n#include \"xsltInternals.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * Extension Modules API.\n */\n\n/**\n * xsltInitGlobals:\n *\n * Initialize the global variables for extensions\n *\n */\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltInitGlobals                 (void);\n\n/**\n * xsltStyleExtInitFunction:\n * @ctxt:  an XSLT stylesheet\n * @URI:  the namespace URI for the extension\n *\n * A function called at initialization time of an XSLT extension module.\n *\n * Returns a pointer to the module specific data for this transformation.\n */\ntypedef void * (*xsltStyleExtInitFunction)\t(xsltStylesheetPtr style,\n\t\t\t\t\t\t const xmlChar *URI);\n\n/**\n * xsltStyleExtShutdownFunction:\n * @ctxt:  an XSLT stylesheet\n * @URI:  the namespace URI for the extension\n * @data:  the data associated to this module\n *\n * A function called at shutdown time of an XSLT extension module.\n */\ntypedef void (*xsltStyleExtShutdownFunction)\t(xsltStylesheetPtr style,\n\t\t\t\t\t\t const xmlChar *URI,\n\t\t\t\t\t\t void *data);\n\n/**\n * xsltExtInitFunction:\n * @ctxt:  an XSLT transformation context\n * @URI:  the namespace URI for the extension\n *\n * A function called at initialization time of an XSLT extension module.\n *\n * Returns a pointer to the module specific data for this transformation.\n */\ntypedef void * (*xsltExtInitFunction)\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t const xmlChar *URI);\n\n/**\n * xsltExtShutdownFunction:\n * @ctxt:  an XSLT transformation context\n * @URI:  the namespace URI for the extension\n * @data:  the data associated to this module\n *\n * A function called at shutdown time of an XSLT extension module.\n */\ntypedef void (*xsltExtShutdownFunction) (xsltTransformContextPtr ctxt,\n\t\t\t\t\t const xmlChar *URI,\n\t\t\t\t\t void *data);\n\nXSLTPUBFUN int XSLTCALL\n\t\txsltRegisterExtModule\t(const xmlChar *URI,\n\t\t\t\t\t xsltExtInitFunction initFunc,\n\t\t\t\t\t xsltExtShutdownFunction shutdownFunc);\nXSLTPUBFUN int XSLTCALL\n\t\txsltRegisterExtModuleFull\n\t\t\t\t\t(const xmlChar * URI,\n\t\t\t\t\t xsltExtInitFunction initFunc,\n\t\t\t\t\t xsltExtShutdownFunction shutdownFunc,\n\t\t\t\t\t xsltStyleExtInitFunction styleInitFunc,\n\t\t\t\t\t xsltStyleExtShutdownFunction styleShutdownFunc);\n\nXSLTPUBFUN int XSLTCALL\n\t\txsltUnregisterExtModule\t(const xmlChar * URI);\n\nXSLTPUBFUN void * XSLTCALL\n\t\txsltGetExtData\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t const xmlChar *URI);\n\nXSLTPUBFUN void * XSLTCALL\n\t\txsltStyleGetExtData\t(xsltStylesheetPtr style,\n\t\t\t\t\t const xmlChar *URI);\n#ifdef XSLT_REFACTORED\nXSLTPUBFUN void * XSLTCALL\n\t\txsltStyleStylesheetLevelGetExtData(\n\t\t\t\t\t xsltStylesheetPtr style,\n\t\t\t\t\t const xmlChar * URI);\n#endif\nXSLTPUBFUN void XSLTCALL\n\t\txsltShutdownCtxtExts\t(xsltTransformContextPtr ctxt);\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltShutdownExts\t(xsltStylesheetPtr style);\n\nXSLTPUBFUN xsltTransformContextPtr XSLTCALL\n\t\txsltXPathGetTransformContext\n\t\t\t\t\t(xmlXPathParserContextPtr ctxt);\n\n/*\n * extension functions\n*/\nXSLTPUBFUN int XSLTCALL\n\t\txsltRegisterExtModuleFunction\n\t\t\t\t\t(const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI,\n\t\t\t\t\t xmlXPathFunction function);\nXSLTPUBFUN xmlXPathFunction XSLTCALL\n\txsltExtModuleFunctionLookup\t(const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI);\nXSLTPUBFUN int XSLTCALL\n\t\txsltUnregisterExtModuleFunction\n\t\t\t\t\t(const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI);\n\n/*\n * extension elements\n */\ntypedef xsltElemPreCompPtr (*xsltPreComputeFunction)\n\t\t\t\t\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltTransformFunction function);\n\nXSLTPUBFUN xsltElemPreCompPtr XSLTCALL\n\t\txsltNewElemPreComp\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltTransformFunction function);\nXSLTPUBFUN void XSLTCALL\n\t\txsltInitElemPreComp\t(xsltElemPreCompPtr comp,\n\t\t\t\t\t xsltStylesheetPtr style,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltTransformFunction function,\n\t\t\t\t\t xsltElemPreCompDeallocator freeFunc);\n\nXSLTPUBFUN int XSLTCALL\n\t\txsltRegisterExtModuleElement\n\t\t\t\t\t(const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI,\n\t\t\t\t\t xsltPreComputeFunction precomp,\n\t\t\t\t\t xsltTransformFunction transform);\nXSLTPUBFUN xsltTransformFunction XSLTCALL\n\t\txsltExtElementLookup\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI);\nXSLTPUBFUN xsltTransformFunction XSLTCALL\n\t\txsltExtModuleElementLookup\n\t\t\t\t\t(const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI);\nXSLTPUBFUN xsltPreComputeFunction XSLTCALL\n\t\txsltExtModuleElementPreComputeLookup\n\t\t\t\t\t(const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI);\nXSLTPUBFUN int XSLTCALL\n\t\txsltUnregisterExtModuleElement\n\t\t\t\t\t(const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI);\n\n/*\n * top-level elements\n */\ntypedef void (*xsltTopLevelFunction)\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlNodePtr inst);\n\nXSLTPUBFUN int XSLTCALL\n\t\txsltRegisterExtModuleTopLevel\n\t\t\t\t\t(const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI,\n\t\t\t\t\t xsltTopLevelFunction function);\nXSLTPUBFUN xsltTopLevelFunction XSLTCALL\n\t\txsltExtModuleTopLevelLookup\n\t\t\t\t\t(const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI);\nXSLTPUBFUN int XSLTCALL\n\t\txsltUnregisterExtModuleTopLevel\n\t\t\t\t\t(const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI);\n\n\n/* These 2 functions are deprecated for use within modules. */\nXSLTPUBFUN int XSLTCALL\n\t\txsltRegisterExtFunction\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI,\n\t\t\t\t\t xmlXPathFunction function);\nXSLTPUBFUN int XSLTCALL\n\t\txsltRegisterExtElement\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *URI,\n\t\t\t\t\t xsltTransformFunction function);\n\n/*\n * Extension Prefix handling API.\n * Those are used by the XSLT (pre)processor.\n */\n\nXSLTPUBFUN int XSLTCALL\n\t\txsltRegisterExtPrefix\t(xsltStylesheetPtr style,\n\t\t\t\t\t const xmlChar *prefix,\n\t\t\t\t\t const xmlChar *URI);\nXSLTPUBFUN int XSLTCALL\n\t\txsltCheckExtPrefix\t(xsltStylesheetPtr style,\n\t\t\t\t\t const xmlChar *URI);\nXSLTPUBFUN int XSLTCALL\n\t\txsltCheckExtURI\t\t(xsltStylesheetPtr style,\n\t\t\t\t\t const xmlChar *URI);\nXSLTPUBFUN int XSLTCALL\n\t\txsltInitCtxtExts\t(xsltTransformContextPtr ctxt);\nXSLTPUBFUN void XSLTCALL\n\t\txsltFreeCtxtExts\t(xsltTransformContextPtr ctxt);\nXSLTPUBFUN void XSLTCALL\n\t\txsltFreeExts\t\t(xsltStylesheetPtr style);\n\nXSLTPUBFUN xsltElemPreCompPtr XSLTCALL\n\t\txsltPreComputeExtModuleElement\n\t\t\t\t\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlNodePtr inst);\n/*\n * Extension Infos access.\n * Used by exslt initialisation\n */\n\nXSLTPUBFUN xmlHashTablePtr XSLTCALL\n\t\txsltGetExtInfo\t\t(xsltStylesheetPtr style,\n\t\t\t\t\t const xmlChar *URI);\n\n/**\n * Test module http://xmlsoft.org/XSLT/\n */\nXSLTPUBFUN void XSLTCALL\n\t\txsltRegisterTestModule\t(void);\nXSLTPUBFUN void XSLTCALL\n\t\txsltDebugDumpExtensions\t(FILE * output);\n\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_EXTENSION_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/extra.h",
    "content": "/*\n * Summary: interface for the non-standard features\n * Description: implement some extension outside the XSLT namespace\n *              but not EXSLT with is in a different library.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_EXTRA_H__\n#define __XML_XSLT_EXTRA_H__\n\n#include <libxml/xpath.h>\n#include \"xsltexports.h\"\n#include \"xsltInternals.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * XSLT_LIBXSLT_NAMESPACE:\n *\n * This is the libxslt namespace for specific extensions.\n */\n#define XSLT_LIBXSLT_NAMESPACE ((xmlChar *) \"http://xmlsoft.org/XSLT/namespace\")\n\n/**\n * XSLT_SAXON_NAMESPACE:\n *\n * This is Michael Kay's Saxon processor namespace for extensions.\n */\n#define XSLT_SAXON_NAMESPACE ((xmlChar *) \"http://icl.com/saxon\")\n\n/**\n * XSLT_XT_NAMESPACE:\n *\n * This is James Clark's XT processor namespace for extensions.\n */\n#define XSLT_XT_NAMESPACE ((xmlChar *) \"http://www.jclark.com/xt\")\n\n/**\n * XSLT_XALAN_NAMESPACE:\n *\n * This is the Apache project XALAN processor namespace for extensions.\n */\n#define XSLT_XALAN_NAMESPACE ((xmlChar *)\t\\\n\t                        \"org.apache.xalan.xslt.extensions.Redirect\")\n\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltFunctionNodeSet\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t\t int nargs);\nXSLTPUBFUN void XSLTCALL\n\t\txsltDebug\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\n\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltRegisterExtras\t(xsltTransformContextPtr ctxt);\nXSLTPUBFUN void XSLTCALL\n\t\txsltRegisterAllExtras\t(void);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_EXTRA_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/functions.h",
    "content": "/*\n * Summary: interface for the XSLT functions not from XPath\n * Description: a set of extra functions coming from XSLT but not in XPath\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard and Bjorn Reese <breese@users.sourceforge.net>\n */\n\n#ifndef __XML_XSLT_FUNCTIONS_H__\n#define __XML_XSLT_FUNCTIONS_H__\n\n#include <libxml/xpath.h>\n#include <libxml/xpathInternals.h>\n#include \"xsltexports.h\"\n#include \"xsltInternals.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * XSLT_REGISTER_FUNCTION_LOOKUP:\n *\n * Registering macro, not general purpose at all but used in different modules.\n */\n#define XSLT_REGISTER_FUNCTION_LOOKUP(ctxt)\t\t\t\\\n    xmlXPathRegisterFuncLookup((ctxt)->xpathCtxt,\t\t\\\n\txsltXPathFunctionLookup,\t\t\t\t\\\n\t(void *)(ctxt->xpathCtxt));\n\nXSLTPUBFUN xmlXPathFunction XSLTCALL\n\txsltXPathFunctionLookup\t\t(void *vctxt,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *ns_uri);\n\n/*\n * Interfaces for the functions implementations.\n */\n\nXSLTPUBFUN void XSLTCALL\n\txsltDocumentFunction\t\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t\t int nargs);\nXSLTPUBFUN void XSLTCALL\n\txsltKeyFunction\t\t\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t\t int nargs);\nXSLTPUBFUN void XSLTCALL\n\txsltUnparsedEntityURIFunction\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t\t int nargs);\nXSLTPUBFUN void XSLTCALL\n\txsltFormatNumberFunction\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t\t int nargs);\nXSLTPUBFUN void XSLTCALL\n\txsltGenerateIdFunction\t\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t\t int nargs);\nXSLTPUBFUN void XSLTCALL\n\txsltSystemPropertyFunction\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t\t int nargs);\nXSLTPUBFUN void XSLTCALL\n\txsltElementAvailableFunction\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t\t int nargs);\nXSLTPUBFUN void XSLTCALL\n\txsltFunctionAvailableFunction\t(xmlXPathParserContextPtr ctxt,\n\t\t\t\t\t int nargs);\n\n/*\n * And the registration\n */\n\nXSLTPUBFUN void XSLTCALL\n\txsltRegisterAllFunctions\t(xmlXPathContextPtr ctxt);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_FUNCTIONS_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/imports.h",
    "content": "/*\n * Summary: interface for the XSLT import support\n * Description: macros and fuctions needed to implement and\n *              access the import tree\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_IMPORTS_H__\n#define __XML_XSLT_IMPORTS_H__\n\n#include <libxml/tree.h>\n#include \"xsltexports.h\"\n#include \"xsltInternals.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * XSLT_GET_IMPORT_PTR:\n *\n * A macro to import pointers from the stylesheet cascading order.\n */\n#define XSLT_GET_IMPORT_PTR(res, style, name) {\t\t\t\\\n    xsltStylesheetPtr st = style;\t\t\t\t\\\n    res = NULL;\t\t\t\t\t\t\t\\\n    while (st != NULL) {\t\t\t\t\t\\\n\tif (st->name != NULL) { res = st->name; break; }\t\\\n\tst = xsltNextImport(st);\t\t\t\t\\\n    }}\n\n/**\n * XSLT_GET_IMPORT_INT:\n *\n * A macro to import intergers from the stylesheet cascading order.\n */\n#define XSLT_GET_IMPORT_INT(res, style, name) {\t\t\t\\\n    xsltStylesheetPtr st = style;\t\t\t\t\\\n    res = -1;\t\t\t\t\t\t\t\\\n    while (st != NULL) {\t\t\t\t\t\\\n\tif (st->name != -1) { res = st->name; break; }\t\\\n\tst = xsltNextImport(st);\t\t\t\t\\\n    }}\n\n/*\n * Module interfaces\n */\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltParseStylesheetImport(xsltStylesheetPtr style,\n\t\t\t\t\t\t  xmlNodePtr cur);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltParseStylesheetInclude\n\t\t\t\t\t\t (xsltStylesheetPtr style,\n\t\t\t\t\t\t  xmlNodePtr cur);\nXSLTPUBFUN xsltStylesheetPtr XSLTCALL\n\t\t\txsltNextImport\t\t (xsltStylesheetPtr style);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltNeedElemSpaceHandling(xsltTransformContextPtr ctxt);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltFindElemSpaceHandling(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t  xmlNodePtr node);\nXSLTPUBFUN xsltTemplatePtr XSLTCALL\n\t\t\txsltFindTemplate\t (xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t  const xmlChar *name,\n\t\t\t\t\t\t  const xmlChar *nameURI);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_IMPORTS_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/keys.h",
    "content": "/*\n * Summary:  interface for the key matching used in key() and template matches.\n * Description: implementation of the key mechanims.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_KEY_H__\n#define __XML_XSLT_KEY_H__\n\n#include <libxml/xpath.h>\n#include \"xsltexports.h\"\n#include \"xsltInternals.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * NODE_IS_KEYED:\n *\n * check for bit 15 set\n */\n#define NODE_IS_KEYED (1 >> 15)\n\nXSLTPUBFUN int XSLTCALL\n\t\txsltAddKey\t\t(xsltStylesheetPtr style,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *nameURI,\n\t\t\t\t\t const xmlChar *match,\n\t\t\t\t\t const xmlChar *use,\n\t\t\t\t\t xmlNodePtr inst);\nXSLTPUBFUN xmlNodeSetPtr XSLTCALL\n\t\txsltGetKey\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t const xmlChar *nameURI,\n\t\t\t\t\t const xmlChar *value);\nXSLTPUBFUN void XSLTCALL\n\t\txsltInitCtxtKeys\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xsltDocumentPtr doc);\nXSLTPUBFUN void XSLTCALL\n\t\txsltFreeKeys\t\t(xsltStylesheetPtr style);\nXSLTPUBFUN void XSLTCALL\n\t\txsltFreeDocumentKeys\t(xsltDocumentPtr doc);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/namespaces.h",
    "content": "/*\n * Summary: interface for the XSLT namespace handling\n * Description: set of function easing the processing and generation\n *              of namespace nodes in XSLT.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_NAMESPACES_H__\n#define __XML_XSLT_NAMESPACES_H__\n\n#include <libxml/tree.h>\n#include \"xsltexports.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * Used within nsAliases hashtable when the default namespace is required\n * but it's not been explicitly defined\n */\n/**\n * UNDEFINED_DEFAULT_NS:\n *\n * Special value for undefined namespace, internal\n */\n#define\tUNDEFINED_DEFAULT_NS\t(const xmlChar *) -1L\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltNamespaceAlias\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlNodePtr node);\nXSLTPUBFUN xmlNsPtr XSLTCALL\n\t\txsltGetNamespace\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr cur,\n\t\t\t\t\t xmlNsPtr ns,\n\t\t\t\t\t xmlNodePtr out);\nXSLTPUBFUN xmlNsPtr XSLTCALL\n\t\txsltGetPlainNamespace\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr cur,\n\t\t\t\t\t xmlNsPtr ns,\n\t\t\t\t\t xmlNodePtr out);\nXSLTPUBFUN xmlNsPtr XSLTCALL\n\t\txsltGetSpecialNamespace\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr cur,\n\t\t\t\t\t const xmlChar *URI,\n\t\t\t\t\t const xmlChar *prefix,\n\t\t\t\t\t xmlNodePtr out);\nXSLTPUBFUN xmlNsPtr XSLTCALL\n\t\txsltCopyNamespace\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr elem,\n\t\t\t\t\t xmlNsPtr ns);\nXSLTPUBFUN xmlNsPtr XSLTCALL\n\t\txsltCopyNamespaceList\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t xmlNsPtr cur);\nXSLTPUBFUN void XSLTCALL\n\t\txsltFreeNamespaceAliasHashes\n\t\t\t\t\t(xsltStylesheetPtr style);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_NAMESPACES_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/numbersInternals.h",
    "content": "/*\n * Summary: Implementation of the XSLT number functions\n * Description: Implementation of the XSLT number functions\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Bjorn Reese <breese@users.sourceforge.net> and Daniel Veillard\n */\n\n#ifndef __XML_XSLT_NUMBERSINTERNALS_H__\n#define __XML_XSLT_NUMBERSINTERNALS_H__\n\n#include <libxml/tree.h>\n#include \"xsltexports.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nstruct _xsltCompMatch;\n\n/**\n * xsltNumberData:\n *\n * This data structure is just a wrapper to pass xsl:number data in.\n */\ntypedef struct _xsltNumberData xsltNumberData;\ntypedef xsltNumberData *xsltNumberDataPtr;\n\nstruct _xsltNumberData {\n    const xmlChar *level;\n    const xmlChar *count;\n    const xmlChar *from;\n    const xmlChar *value;\n    const xmlChar *format;\n    int has_format;\n    int digitsPerGroup;\n    int groupingCharacter;\n    int groupingCharacterLen;\n    xmlDocPtr doc;\n    xmlNodePtr node;\n    struct _xsltCompMatch *countPat;\n    struct _xsltCompMatch *fromPat;\n\n    /*\n     * accelerators\n     */\n};\n\n/**\n * xsltFormatNumberInfo,:\n *\n * This data structure lists the various parameters needed to format numbers.\n */\ntypedef struct _xsltFormatNumberInfo xsltFormatNumberInfo;\ntypedef xsltFormatNumberInfo *xsltFormatNumberInfoPtr;\n\nstruct _xsltFormatNumberInfo {\n    int\t    integer_hash;\t/* Number of '#' in integer part */\n    int\t    integer_digits;\t/* Number of '0' in integer part */\n    int\t    frac_digits;\t/* Number of '0' in fractional part */\n    int\t    frac_hash;\t\t/* Number of '#' in fractional part */\n    int\t    group;\t\t/* Number of chars per display 'group' */\n    int     multiplier;\t\t/* Scaling for percent or permille */\n    char    add_decimal;\t/* Flag for whether decimal point appears in pattern */\n    char    is_multiplier_set;\t/* Flag to catch multiple occurences of percent/permille */\n    char    is_negative_pattern;/* Flag for processing -ve prefix/suffix */\n};\n\n#ifdef __cplusplus\n}\n#endif\n#endif /* __XML_XSLT_NUMBERSINTERNALS_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/pattern.h",
    "content": "/*\n * Summary: interface for the pattern matching used in template matches.\n * Description: the implementation of the lookup of the right template\n *              for a given node must be really fast in order to keep\n *              decent performances.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_PATTERN_H__\n#define __XML_XSLT_PATTERN_H__\n\n#include \"xsltInternals.h\"\n#include \"xsltexports.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * xsltCompMatch:\n *\n * Data structure used for the implementation of patterns.\n * It is kept private (in pattern.c).\n */\ntypedef struct _xsltCompMatch xsltCompMatch;\ntypedef xsltCompMatch *xsltCompMatchPtr;\n\n/*\n * Pattern related interfaces.\n */\n\nXSLTPUBFUN xsltCompMatchPtr XSLTCALL\n\t\txsltCompilePattern\t(const xmlChar *pattern,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t xsltStylesheetPtr style,\n\t\t\t\t\t xsltTransformContextPtr runtime);\nXSLTPUBFUN void XSLTCALL\n\t\txsltFreeCompMatchList\t(xsltCompMatchPtr comp);\nXSLTPUBFUN int XSLTCALL\n\t\txsltTestCompMatchList\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t xsltCompMatchPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltNormalizeCompSteps\t(void *payload,\n\t\t\t\t\t void *data,\n\t\t\t\t\t const xmlChar *name);\n\n/*\n * Template related interfaces.\n */\nXSLTPUBFUN int XSLTCALL\n\t\txsltAddTemplate\t\t(xsltStylesheetPtr style,\n\t\t\t\t\t xsltTemplatePtr cur,\n\t\t\t\t\t const xmlChar *mode,\n\t\t\t\t\t const xmlChar *modeURI);\nXSLTPUBFUN xsltTemplatePtr XSLTCALL\n\t\txsltGetTemplate\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t xsltStylesheetPtr style);\nXSLTPUBFUN void XSLTCALL\n\t\txsltFreeTemplateHashes\t(xsltStylesheetPtr style);\nXSLTPUBFUN void XSLTCALL\n\t\txsltCleanupTemplates\t(xsltStylesheetPtr style);\n\n#if 0\nint\t\txsltMatchPattern\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t const xmlChar *pattern,\n\t\t\t\t\t xmlDocPtr ctxtdoc,\n\t\t\t\t\t xmlNodePtr ctxtnode);\n#endif\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_PATTERN_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/preproc.h",
    "content": "/*\n * Summary: precomputing stylesheets\n * Description: this is the compilation phase, where most of the\n *              stylesheet is \"compiled\" into faster to use data.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_PRECOMP_H__\n#define __XML_XSLT_PRECOMP_H__\n\n#include <libxml/tree.h>\n#include \"xsltexports.h\"\n#include \"xsltInternals.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*\n * Interfaces\n */\nextern const xmlChar *xsltExtMarker;\n\nXSLTPUBFUN xsltElemPreCompPtr XSLTCALL\n\t\txsltDocumentComp\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltTransformFunction function);\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltStylePreCompute\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlNodePtr inst);\nXSLTPUBFUN void XSLTCALL\n\t\txsltFreeStylePreComps\t(xsltStylesheetPtr style);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_PRECOMP_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/security.h",
    "content": "/*\n * Summary: interface for the libxslt security framework\n * Description: the libxslt security framework allow to restrict\n *              the access to new resources (file or URL) from\n *              the stylesheet at runtime.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_SECURITY_H__\n#define __XML_XSLT_SECURITY_H__\n\n#include <libxml/tree.h>\n#include \"xsltexports.h\"\n#include \"xsltInternals.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * xsltSecurityPref:\n *\n * structure to indicate the preferences for security in the XSLT\n * transformation.\n */\ntypedef struct _xsltSecurityPrefs xsltSecurityPrefs;\ntypedef xsltSecurityPrefs *xsltSecurityPrefsPtr;\n\n/**\n * xsltSecurityOption:\n *\n * the set of option that can be configured\n */\ntypedef enum {\n    XSLT_SECPREF_READ_FILE = 1,\n    XSLT_SECPREF_WRITE_FILE,\n    XSLT_SECPREF_CREATE_DIRECTORY,\n    XSLT_SECPREF_READ_NETWORK,\n    XSLT_SECPREF_WRITE_NETWORK\n} xsltSecurityOption;\n\n/**\n * xsltSecurityCheck:\n *\n * User provided function to check the value of a string like a file\n * path or an URL ...\n */\ntypedef int (*xsltSecurityCheck)\t(xsltSecurityPrefsPtr sec,\n\t\t\t\t\t xsltTransformContextPtr ctxt,\n\t\t\t\t\t const char *value);\n\n/*\n * Module interfaces\n */\nXSLTPUBFUN xsltSecurityPrefsPtr XSLTCALL\n\t\t    xsltNewSecurityPrefs\t(void);\nXSLTPUBFUN void XSLTCALL\n\t\t    xsltFreeSecurityPrefs\t(xsltSecurityPrefsPtr sec);\nXSLTPUBFUN int XSLTCALL\n\t\t    xsltSetSecurityPrefs\t(xsltSecurityPrefsPtr sec,\n\t\t\t\t\t\t xsltSecurityOption option,\n\t\t\t\t\t\t xsltSecurityCheck func);\nXSLTPUBFUN xsltSecurityCheck XSLTCALL\n\t\t    xsltGetSecurityPrefs\t(xsltSecurityPrefsPtr sec,\n\t\t\t\t\t\t xsltSecurityOption option);\n\nXSLTPUBFUN void XSLTCALL\n\t\t    xsltSetDefaultSecurityPrefs\t(xsltSecurityPrefsPtr sec);\nXSLTPUBFUN xsltSecurityPrefsPtr XSLTCALL\n\t\t    xsltGetDefaultSecurityPrefs\t(void);\n\nXSLTPUBFUN int XSLTCALL\n\t\t    xsltSetCtxtSecurityPrefs\t(xsltSecurityPrefsPtr sec,\n\t\t\t\t\t\t xsltTransformContextPtr ctxt);\n\nXSLTPUBFUN int XSLTCALL\n\t\t    xsltSecurityAllow\t\t(xsltSecurityPrefsPtr sec,\n\t\t\t\t\t\t xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t const char *value);\nXSLTPUBFUN int XSLTCALL\n\t\t    xsltSecurityForbid\t\t(xsltSecurityPrefsPtr sec,\n\t\t\t\t\t\t xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t const char *value);\n/*\n * internal interfaces\n */\nXSLTPUBFUN int XSLTCALL\n\t\t    xsltCheckWrite\t\t(xsltSecurityPrefsPtr sec,\n\t\t\t\t\t\t xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *URL);\nXSLTPUBFUN int XSLTCALL\n\t\t    xsltCheckRead\t\t(xsltSecurityPrefsPtr sec,\n\t\t\t\t\t\t xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *URL);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_SECURITY_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/templates.h",
    "content": "/*\n * Summary: interface for the template processing\n * Description: This set of routine encapsulates XPath calls\n *              and Attribute Value Templates evaluation.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_TEMPLATES_H__\n#define __XML_XSLT_TEMPLATES_H__\n\n#include <libxml/xpath.h>\n#include <libxml/xpathInternals.h>\n#include \"xsltexports.h\"\n#include \"xsltInternals.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nXSLTPUBFUN int XSLTCALL\n\t\txsltEvalXPathPredicate\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlXPathCompExprPtr comp,\n\t\t                                 xmlNsPtr *nsList,\n\t\t\t\t\t\t int nsNr);\nXSLTPUBFUN xmlChar * XSLTCALL\n\t\txsltEvalTemplateString\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr contextNode,\n\t\t\t\t\t\t xmlNodePtr inst);\nXSLTPUBFUN xmlChar * XSLTCALL\n\t\txsltEvalAttrValueTemplate\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ns);\nXSLTPUBFUN const xmlChar * XSLTCALL\n\t\txsltEvalStaticAttrValueTemplate\t(xsltStylesheetPtr style,\n\t\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ns,\n\t\t\t\t\t\t int *found);\n\n/* TODO: this is obviously broken ... the namespaces should be passed too ! */\nXSLTPUBFUN xmlChar * XSLTCALL\n\t\txsltEvalXPathString\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlXPathCompExprPtr comp);\nXSLTPUBFUN xmlChar * XSLTCALL\n\t\txsltEvalXPathStringNs\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlXPathCompExprPtr comp,\n\t\t\t\t\t\t int nsNr,\n\t\t\t\t\t\t xmlNsPtr *nsList);\n\nXSLTPUBFUN xmlNodePtr * XSLTCALL\n\t\txsltTemplateProcess\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr node);\nXSLTPUBFUN xmlAttrPtr XSLTCALL\n\t\txsltAttrListTemplateProcess\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr target,\n\t\t\t\t\t\t xmlAttrPtr cur);\nXSLTPUBFUN xmlAttrPtr XSLTCALL\n\t\txsltAttrTemplateProcess\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr target,\n\t\t\t\t\t\t xmlAttrPtr attr);\nXSLTPUBFUN xmlChar * XSLTCALL\n\t\txsltAttrTemplateValueProcess\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar* attr);\nXSLTPUBFUN xmlChar * XSLTCALL\n\t\txsltAttrTemplateValueProcessNode(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar* str,\n\t\t\t\t\t\t xmlNodePtr node);\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_TEMPLATES_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/transform.h",
    "content": "/*\n * Summary: the XSLT engine transformation part.\n * Description: This module implements the bulk of the actual\n *              transformation processing. Most of the xsl: element\n *              constructs are implemented in this module.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_TRANSFORM_H__\n#define __XML_XSLT_TRANSFORM_H__\n\n#include <libxml/parser.h>\n#include <libxml/xmlIO.h>\n#include \"xsltexports.h\"\n#include <libxslt/xsltInternals.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * XInclude default processing.\n */\nXSLTPUBFUN void XSLTCALL\n\t\txsltSetXIncludeDefault\t(int xinclude);\nXSLTPUBFUN int XSLTCALL\n\t\txsltGetXIncludeDefault\t(void);\n\n/**\n * Export context to users.\n */\nXSLTPUBFUN xsltTransformContextPtr XSLTCALL\n\t\txsltNewTransformContext\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlDocPtr doc);\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltFreeTransformContext(xsltTransformContextPtr ctxt);\n\nXSLTPUBFUN xmlDocPtr XSLTCALL\n\t\txsltApplyStylesheetUser\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t const char **params,\n\t\t\t\t\t const char *output,\n\t\t\t\t\t FILE * profile,\n\t\t\t\t\t xsltTransformContextPtr userCtxt);\nXSLTPUBFUN void XSLTCALL\n                xsltProcessOneNode      (xsltTransformContextPtr ctxt,\n                                         xmlNodePtr node,\n                                         xsltStackElemPtr params);\n/**\n * Private Interfaces.\n */\nXSLTPUBFUN void XSLTCALL\n\t\txsltApplyStripSpaces\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr node);\nXSLTPUBFUN xmlDocPtr XSLTCALL\n\t\txsltApplyStylesheet\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t const char **params);\nXSLTPUBFUN xmlDocPtr XSLTCALL\n\t\txsltProfileStylesheet\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t const char **params,\n\t\t\t\t\t FILE * output);\nXSLTPUBFUN int XSLTCALL\n\t\txsltRunStylesheet\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t const char **params,\n\t\t\t\t\t const char *output,\n\t\t\t\t\t xmlSAXHandlerPtr SAX,\n\t\t\t\t\t xmlOutputBufferPtr IObuf);\nXSLTPUBFUN int XSLTCALL\n\t\txsltRunStylesheetUser\t(xsltStylesheetPtr style,\n\t\t\t\t\t xmlDocPtr doc,\n\t\t\t\t\t const char **params,\n\t\t\t\t\t const char *output,\n\t\t\t\t\t xmlSAXHandlerPtr SAX,\n\t\t\t\t\t xmlOutputBufferPtr IObuf,\n\t\t\t\t\t FILE * profile,\n\t\t\t\t\t xsltTransformContextPtr userCtxt);\nXSLTPUBFUN void XSLTCALL\n\t\txsltApplyOneTemplate\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr list,\n\t\t\t\t\t xsltTemplatePtr templ,\n\t\t\t\t\t xsltStackElemPtr params);\nXSLTPUBFUN void XSLTCALL\n\t\txsltDocumentElem\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltSort\t\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltCopy\t\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltText\t\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltElement\t\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltComment\t\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltAttribute\t\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltProcessingInstruction(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltCopyOf\t\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltValueOf\t\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltNumber\t\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltApplyImports\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltCallTemplate\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltApplyTemplates\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltChoose\t\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltIf\t\t\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltForEach\t\t(xsltTransformContextPtr ctxt,\n\t                                 xmlNodePtr node,\n\t\t\t\t\t xmlNodePtr inst,\n\t\t\t\t\t xsltElemPreCompPtr comp);\nXSLTPUBFUN void XSLTCALL\n\t\txsltRegisterAllElement\t(xsltTransformContextPtr ctxt);\n\nXSLTPUBFUN xmlNodePtr XSLTCALL\n\t\txsltCopyTextString\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xmlNodePtr target,\n\t\t\t\t\t const xmlChar *string,\n\t\t\t\t\t int noescape);\n\n/* Following 2 functions needed for libexslt/functions.c */\nXSLTPUBFUN void XSLTCALL\n\t\txsltLocalVariablePop\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t int limitNr,\n\t\t\t\t\t int level);\nXSLTPUBFUN int XSLTCALL\n\t\txsltLocalVariablePush\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t xsltStackElemPtr variable,\n\t\t\t\t\t int level);\n/*\n * Hook for the debugger if activated.\n */\nXSLTPUBFUN void XSLTCALL\n\t\txslHandleDebugger\t(xmlNodePtr cur,\n\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t xsltTemplatePtr templ,\n\t\t\t\t\t xsltTransformContextPtr ctxt);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_TRANSFORM_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/variables.h",
    "content": "/*\n * Summary: interface for the variable matching and lookup.\n * Description: interface for the variable matching and lookup.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_VARIABLES_H__\n#define __XML_XSLT_VARIABLES_H__\n\n#include <libxml/xpath.h>\n#include <libxml/xpathInternals.h>\n#include \"xsltexports.h\"\n#include \"xsltInternals.h\"\n#include \"functions.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n\n/**\n * XSLT_REGISTER_VARIABLE_LOOKUP:\n *\n * Registering macro, not general purpose at all but used in different modules.\n */\n\n#define XSLT_REGISTER_VARIABLE_LOOKUP(ctxt)\t\t\t\\\n    xmlXPathRegisterVariableLookup((ctxt)->xpathCtxt,\t\t\\\n\t       xsltXPathVariableLookup,\t(void *)(ctxt));\t\\\n    xsltRegisterAllFunctions((ctxt)->xpathCtxt);\t\t\\\n    xsltRegisterAllElement(ctxt);\t\t\t\t\\\n    (ctxt)->xpathCtxt->extra = ctxt\n\n/*\n * Flags for memory management of RVTs\n */\n\n/**\n * XSLT_RVT_LOCAL:\n *\n * RVT is destroyed after the current instructions ends.\n */\n#define XSLT_RVT_LOCAL       ((void *)1)\n\n/**\n * XSLT_RVT_FUNC_RESULT:\n *\n * RVT is part of results returned with func:result. The RVT won't be\n * destroyed after exiting a template and will be reset to XSLT_RVT_LOCAL or\n * XSLT_RVT_VARIABLE in the template that receives the return value.\n */\n#define XSLT_RVT_FUNC_RESULT ((void *)2)\n\n/**\n * XSLT_RVT_GLOBAL:\n *\n * RVT is part of a global variable.\n */\n#define XSLT_RVT_GLOBAL      ((void *)3)\n\n/*\n * Interfaces for the variable module.\n */\n\nXSLTPUBFUN int XSLTCALL\n\t\txsltEvalGlobalVariables\t\t(xsltTransformContextPtr ctxt);\nXSLTPUBFUN int XSLTCALL\n\t\txsltEvalUserParams\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t const char **params);\nXSLTPUBFUN int XSLTCALL\n\t\txsltQuoteUserParams\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t const char **params);\nXSLTPUBFUN int XSLTCALL\n\t\txsltEvalOneUserParam\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar * name,\n\t\t\t\t\t\t const xmlChar * value);\nXSLTPUBFUN int XSLTCALL\n\t\txsltQuoteOneUserParam\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar * name,\n\t\t\t\t\t\t const xmlChar * value);\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltParseGlobalVariable\t\t(xsltStylesheetPtr style,\n\t\t\t\t\t\t xmlNodePtr cur);\nXSLTPUBFUN void XSLTCALL\n\t\txsltParseGlobalParam\t\t(xsltStylesheetPtr style,\n\t\t\t\t\t\t xmlNodePtr cur);\nXSLTPUBFUN void XSLTCALL\n\t\txsltParseStylesheetVariable\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr cur);\nXSLTPUBFUN void XSLTCALL\n\t\txsltParseStylesheetParam\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr cur);\nXSLTPUBFUN xsltStackElemPtr XSLTCALL\n\t\txsltParseStylesheetCallerParam\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr cur);\nXSLTPUBFUN int XSLTCALL\n\t\txsltAddStackElemList\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xsltStackElemPtr elems);\nXSLTPUBFUN void XSLTCALL\n\t\txsltFreeGlobalVariables\t\t(xsltTransformContextPtr ctxt);\nXSLTPUBFUN xmlXPathObjectPtr XSLTCALL\n\t\txsltVariableLookup\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ns_uri);\nXSLTPUBFUN xmlXPathObjectPtr XSLTCALL\n\t\txsltXPathVariableLookup\t\t(void *ctxt,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar *ns_uri);\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_VARIABLES_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/xslt.h",
    "content": "/*\n * Summary: Interfaces, constants and types related to the XSLT engine\n * Description: Interfaces, constants and types related to the XSLT engine\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_H__\n#define __XML_XSLT_H__\n\n#include <libxml/tree.h>\n#include \"xsltexports.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * XSLT_DEFAULT_VERSION:\n *\n * The default version of XSLT supported.\n */\n#define XSLT_DEFAULT_VERSION     \"1.0\"\n\n/**\n * XSLT_DEFAULT_VENDOR:\n *\n * The XSLT \"vendor\" string for this processor.\n */\n#define XSLT_DEFAULT_VENDOR      \"libxslt\"\n\n/**\n * XSLT_DEFAULT_URL:\n *\n * The XSLT \"vendor\" URL for this processor.\n */\n#define XSLT_DEFAULT_URL         \"http://xmlsoft.org/XSLT/\"\n\n/**\n * XSLT_NAMESPACE:\n *\n * The XSLT specification namespace.\n */\n#define XSLT_NAMESPACE ((const xmlChar *)\"http://www.w3.org/1999/XSL/Transform\")\n\n/**\n * XSLT_PARSE_OPTIONS:\n *\n * The set of options to pass to an xmlReadxxx when loading files for\n * XSLT consumption.\n */\n#define XSLT_PARSE_OPTIONS \\\n XML_PARSE_NOENT | XML_PARSE_DTDLOAD | XML_PARSE_DTDATTR | XML_PARSE_NOCDATA\n\n/**\n * xsltMaxDepth:\n *\n * This value is used to detect templates loops.\n */\nXSLTPUBVAR int xsltMaxDepth;\n\n/**\n *  * xsltMaxVars:\n *   *\n *    * This value is used to detect templates loops.\n *     */\nXSLTPUBVAR int xsltMaxVars;\n\n/**\n * xsltEngineVersion:\n *\n * The version string for libxslt.\n */\nXSLTPUBVAR const char *xsltEngineVersion;\n\n/**\n * xsltLibxsltVersion:\n *\n * The version of libxslt compiled.\n */\nXSLTPUBVAR const int xsltLibxsltVersion;\n\n/**\n * xsltLibxmlVersion:\n *\n * The version of libxml libxslt was compiled against.\n */\nXSLTPUBVAR const int xsltLibxmlVersion;\n\n/*\n * Global initialization function.\n */\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltInit\t\t(void);\n\n/*\n * Global cleanup function.\n */\nXSLTPUBFUN void XSLTCALL\n\t\txsltCleanupGlobals\t(void);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/xsltInternals.h",
    "content": "/*\n * Summary: internal data structures, constants and functions\n * Description: Internal data structures, constants and functions used\n *              by the XSLT engine.\n *              They are not part of the API or ABI, i.e. they can change\n *              without prior notice, use carefully.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLT_INTERNALS_H__\n#define __XML_XSLT_INTERNALS_H__\n\n#include <libxml/tree.h>\n#include <libxml/hash.h>\n#include <libxml/xpath.h>\n#include <libxml/xmlerror.h>\n#include <libxml/dict.h>\n#include <libxml/xmlstring.h>\n#include <libxslt/xslt.h>\n#include \"xsltexports.h\"\n#include \"xsltlocale.h\"\n#include \"numbersInternals.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* #define XSLT_DEBUG_PROFILE_CACHE */\n\n/**\n * XSLT_IS_TEXT_NODE:\n *\n * check if the argument is a text node\n */\n#define XSLT_IS_TEXT_NODE(n) ((n != NULL) && \\\n    (((n)->type == XML_TEXT_NODE) || \\\n     ((n)->type == XML_CDATA_SECTION_NODE)))\n\n\n/**\n * XSLT_MARK_RES_TREE_FRAG:\n *\n * internal macro to set up tree fragments\n */\n#define XSLT_MARK_RES_TREE_FRAG(n) \\\n    (n)->name = (char *) xmlStrdup(BAD_CAST \" fake node libxslt\");\n\n/**\n * XSLT_IS_RES_TREE_FRAG:\n *\n * internal macro to test tree fragments\n */\n#define XSLT_IS_RES_TREE_FRAG(n) \\\n    ((n != NULL) && ((n)->type == XML_DOCUMENT_NODE) && \\\n     ((n)->name != NULL) && ((n)->name[0] == ' '))\n\n/**\n * XSLT_REFACTORED_KEYCOMP:\n *\n * Internal define to enable on-demand xsl:key computation.\n * That's the only mode now but the define is kept for compatibility\n */\n#define XSLT_REFACTORED_KEYCOMP\n\n/**\n * XSLT_FAST_IF:\n *\n * Internal define to enable usage of xmlXPathCompiledEvalToBoolean()\n * for XSLT \"tests\"; e.g. in <xsl:if test=\"/foo/bar\">\n */\n#define XSLT_FAST_IF\n\n/**\n * XSLT_REFACTORED:\n *\n * Internal define to enable the refactored parts of Libxslt.\n */\n/* #define XSLT_REFACTORED */\n/* ==================================================================== */\n\n/**\n * XSLT_REFACTORED_VARS:\n *\n * Internal define to enable the refactored variable part of libxslt\n */\n#define XSLT_REFACTORED_VARS\n\n#ifdef XSLT_REFACTORED\n\nextern const xmlChar *xsltXSLTAttrMarker;\n\n\n/* TODO: REMOVE: #define XSLT_REFACTORED_EXCLRESNS */\n\n/* TODO: REMOVE: #define XSLT_REFACTORED_NSALIAS */\n\n/**\n * XSLT_REFACTORED_XSLT_NSCOMP\n *\n * Internal define to enable the pointer-comparison of\n * namespaces of XSLT elements.\n */\n/* #define XSLT_REFACTORED_XSLT_NSCOMP */\n\n/**\n * XSLT_REFACTORED_XPATHCOMP:\n *\n * Internal define to enable the optimization of the\n * compilation of XPath expressions.\n */\n#define XSLT_REFACTORED_XPATHCOMP\n\n#ifdef XSLT_REFACTORED_XSLT_NSCOMP\n\nextern const xmlChar *xsltConstNamespaceNameXSLT;\n\n/**\n * IS_XSLT_ELEM_FAST:\n *\n * quick test to detect XSLT elements\n */\n#define IS_XSLT_ELEM_FAST(n) \\\n    (((n) != NULL) && ((n)->ns != NULL) && \\\n    ((n)->ns->href == xsltConstNamespaceNameXSLT))\n\n/**\n * IS_XSLT_ATTR_FAST:\n *\n * quick test to detect XSLT attributes\n */\n#define IS_XSLT_ATTR_FAST(a) \\\n    (((a) != NULL) && ((a)->ns != NULL) && \\\n    ((a)->ns->href == xsltConstNamespaceNameXSLT))\n\n/**\n * XSLT_HAS_INTERNAL_NSMAP:\n *\n * check for namespace mapping\n */\n#define XSLT_HAS_INTERNAL_NSMAP(s) \\\n    (((s) != NULL) && ((s)->principal) && \\\n     ((s)->principal->principalData) && \\\n     ((s)->principal->principalData->nsMap))\n\n/**\n * XSLT_GET_INTERNAL_NSMAP:\n *\n * get pointer to namespace map\n */\n#define XSLT_GET_INTERNAL_NSMAP(s) ((s)->principal->principalData->nsMap)\n\n#else /* XSLT_REFACTORED_XSLT_NSCOMP */\n\n/**\n * IS_XSLT_ELEM_FAST:\n *\n * quick check whether this is an xslt element\n */\n#define IS_XSLT_ELEM_FAST(n) \\\n    (((n) != NULL) && ((n)->ns != NULL) && \\\n     (xmlStrEqual((n)->ns->href, XSLT_NAMESPACE)))\n\n/**\n * IS_XSLT_ATTR_FAST:\n *\n * quick check for xslt namespace attribute\n */\n#define IS_XSLT_ATTR_FAST(a) \\\n    (((a) != NULL) && ((a)->ns != NULL) && \\\n     (xmlStrEqual((a)->ns->href, XSLT_NAMESPACE)))\n\n\n#endif /* XSLT_REFACTORED_XSLT_NSCOMP */\n\n\n/**\n * XSLT_REFACTORED_MANDATORY_VERSION:\n *\n * TODO: Currently disabled to surpress regression test failures, since\n *  the old behaviour was that a missing version attribute\n *  produced a only a warning and not an error, which was incerrect.\n *  So the regression tests need to be fixed if this is enabled.\n */\n/* #define XSLT_REFACTORED_MANDATORY_VERSION */\n\n/**\n * xsltPointerList:\n *\n * Pointer-list for various purposes.\n */\ntypedef struct _xsltPointerList xsltPointerList;\ntypedef xsltPointerList *xsltPointerListPtr;\nstruct _xsltPointerList {\n    void **items;\n    int number;\n    int size;\n};\n\n#endif\n\n/**\n * XSLT_REFACTORED_PARSING:\n *\n * Internal define to enable the refactored parts of Libxslt\n * related to parsing.\n */\n/* #define XSLT_REFACTORED_PARSING */\n\n/**\n * XSLT_MAX_SORT:\n *\n * Max number of specified xsl:sort on an element.\n */\n#define XSLT_MAX_SORT 15\n\n/**\n * XSLT_PAT_NO_PRIORITY:\n *\n * Specific value for pattern without priority expressed.\n */\n#define XSLT_PAT_NO_PRIORITY -12345789\n\n/**\n * xsltRuntimeExtra:\n *\n * Extra information added to the transformation context.\n */\ntypedef struct _xsltRuntimeExtra xsltRuntimeExtra;\ntypedef xsltRuntimeExtra *xsltRuntimeExtraPtr;\nstruct _xsltRuntimeExtra {\n    void       *info;\t\t/* pointer to the extra data */\n    xmlFreeFunc deallocate;\t/* pointer to the deallocation routine */\n    union {\t\t\t/* dual-purpose field */\n        void   *ptr;\t\t/* data not needing deallocation */\n\tint    ival;\t\t/* integer value storage */\n    } val;\n};\n\n/**\n * XSLT_RUNTIME_EXTRA_LST:\n * @ctxt: the transformation context\n * @nr: the index\n *\n * Macro used to access extra information stored in the context\n */\n#define XSLT_RUNTIME_EXTRA_LST(ctxt, nr) (ctxt)->extras[(nr)].info\n/**\n * XSLT_RUNTIME_EXTRA_FREE:\n * @ctxt: the transformation context\n * @nr: the index\n *\n * Macro used to free extra information stored in the context\n */\n#define XSLT_RUNTIME_EXTRA_FREE(ctxt, nr) (ctxt)->extras[(nr)].deallocate\n/**\n * XSLT_RUNTIME_EXTRA:\n * @ctxt: the transformation context\n * @nr: the index\n *\n * Macro used to define extra information stored in the context\n */\n#define\tXSLT_RUNTIME_EXTRA(ctxt, nr, typ) (ctxt)->extras[(nr)].val.typ\n\n/**\n * xsltTemplate:\n *\n * The in-memory structure corresponding to an XSLT Template.\n */\ntypedef struct _xsltTemplate xsltTemplate;\ntypedef xsltTemplate *xsltTemplatePtr;\nstruct _xsltTemplate {\n    struct _xsltTemplate *next;/* chained list sorted by priority */\n    struct _xsltStylesheet *style;/* the containing stylesheet */\n    xmlChar *match;\t/* the matching string */\n    float priority;\t/* as given from the stylesheet, not computed */\n    const xmlChar *name; /* the local part of the name QName */\n    const xmlChar *nameURI; /* the URI part of the name QName */\n    const xmlChar *mode;/* the local part of the mode QName */\n    const xmlChar *modeURI;/* the URI part of the mode QName */\n    xmlNodePtr content;\t/* the template replacement value */\n    xmlNodePtr elem;\t/* the source element */\n\n    /*\n    * TODO: @inheritedNsNr and @inheritedNs won't be used in the\n    *  refactored code.\n    */\n    int inheritedNsNr;  /* number of inherited namespaces */\n    xmlNsPtr *inheritedNs;/* inherited non-excluded namespaces */\n\n    /* Profiling information */\n    int nbCalls;        /* the number of time the template was called */\n    unsigned long time; /* the time spent in this template */\n    void *params;       /* xsl:param instructions */\n\n    int              templNr;\t\t/* Nb of templates in the stack */\n    int              templMax;\t\t/* Size of the templtes stack */\n    xsltTemplatePtr *templCalledTab;\t/* templates called */\n    int             *templCountTab;  /* .. and how often */\n};\n\n/**\n * xsltDecimalFormat:\n *\n * Data structure of decimal-format.\n */\ntypedef struct _xsltDecimalFormat xsltDecimalFormat;\ntypedef xsltDecimalFormat *xsltDecimalFormatPtr;\nstruct _xsltDecimalFormat {\n    struct _xsltDecimalFormat *next; /* chained list */\n    xmlChar *name;\n    /* Used for interpretation of pattern */\n    xmlChar *digit;\n    xmlChar *patternSeparator;\n    /* May appear in result */\n    xmlChar *minusSign;\n    xmlChar *infinity;\n    xmlChar *noNumber; /* Not-a-number */\n    /* Used for interpretation of pattern and may appear in result */\n    xmlChar *decimalPoint;\n    xmlChar *grouping;\n    xmlChar *percent;\n    xmlChar *permille;\n    xmlChar *zeroDigit;\n    const xmlChar *nsUri;\n};\n\n/**\n * xsltDocument:\n *\n * Data structure associated to a parsed document.\n */\ntypedef struct _xsltDocument xsltDocument;\ntypedef xsltDocument *xsltDocumentPtr;\nstruct _xsltDocument {\n    struct _xsltDocument *next;\t/* documents are kept in a chained list */\n    int main;\t\t\t/* is this the main document */\n    xmlDocPtr doc;\t\t/* the parsed document */\n    void *keys;\t\t\t/* key tables storage */\n    struct _xsltDocument *includes; /* subsidiary includes */\n    int preproc;\t\t/* pre-processing already done */\n    int nbKeysComputed;\n};\n\n/**\n * xsltKeyDef:\n *\n * Representation of an xsl:key.\n */\ntypedef struct _xsltKeyDef xsltKeyDef;\ntypedef xsltKeyDef *xsltKeyDefPtr;\nstruct _xsltKeyDef {\n    struct _xsltKeyDef *next;\n    xmlNodePtr inst;\n    xmlChar *name;\n    xmlChar *nameURI;\n    xmlChar *match;\n    xmlChar *use;\n    xmlXPathCompExprPtr comp;\n    xmlXPathCompExprPtr usecomp;\n    xmlNsPtr *nsList;           /* the namespaces in scope */\n    int nsNr;                   /* the number of namespaces in scope */\n};\n\n/**\n * xsltKeyTable:\n *\n * Holds the computed keys for key definitions of the same QName.\n * Is owned by an xsltDocument.\n */\ntypedef struct _xsltKeyTable xsltKeyTable;\ntypedef xsltKeyTable *xsltKeyTablePtr;\nstruct _xsltKeyTable {\n    struct _xsltKeyTable *next;\n    xmlChar *name;\n    xmlChar *nameURI;\n    xmlHashTablePtr keys;\n};\n\n/*\n * The in-memory structure corresponding to an XSLT Stylesheet.\n * NOTE: most of the content is simply linked from the doc tree\n *       structure, no specific allocation is made.\n */\ntypedef struct _xsltStylesheet xsltStylesheet;\ntypedef xsltStylesheet *xsltStylesheetPtr;\n\ntypedef struct _xsltTransformContext xsltTransformContext;\ntypedef xsltTransformContext *xsltTransformContextPtr;\n\n/**\n * xsltElemPreComp:\n *\n * The in-memory structure corresponding to element precomputed data,\n * designed to be extended by extension implementors.\n */\ntypedef struct _xsltElemPreComp xsltElemPreComp;\ntypedef xsltElemPreComp *xsltElemPreCompPtr;\n\n/**\n * xsltTransformFunction:\n * @ctxt: the XSLT transformation context\n * @node: the input node\n * @inst: the stylesheet node\n * @comp: the compiled information from the stylesheet\n *\n * Signature of the function associated to elements part of the\n * stylesheet language like xsl:if or xsl:apply-templates.\n */\ntypedef void (*xsltTransformFunction) (xsltTransformContextPtr ctxt,\n\t                               xmlNodePtr node,\n\t\t\t\t       xmlNodePtr inst,\n\t\t\t               xsltElemPreCompPtr comp);\n\n/**\n * xsltSortFunc:\n * @ctxt:    a transformation context\n * @sorts:   the node-set to sort\n * @nbsorts: the number of sorts\n *\n * Signature of the function to use during sorting\n */\ntypedef void (*xsltSortFunc) (xsltTransformContextPtr ctxt, xmlNodePtr *sorts,\n\t\t\t      int nbsorts);\n\ntypedef enum {\n    XSLT_FUNC_COPY=1,\n    XSLT_FUNC_SORT,\n    XSLT_FUNC_TEXT,\n    XSLT_FUNC_ELEMENT,\n    XSLT_FUNC_ATTRIBUTE,\n    XSLT_FUNC_COMMENT,\n    XSLT_FUNC_PI,\n    XSLT_FUNC_COPYOF,\n    XSLT_FUNC_VALUEOF,\n    XSLT_FUNC_NUMBER,\n    XSLT_FUNC_APPLYIMPORTS,\n    XSLT_FUNC_CALLTEMPLATE,\n    XSLT_FUNC_APPLYTEMPLATES,\n    XSLT_FUNC_CHOOSE,\n    XSLT_FUNC_IF,\n    XSLT_FUNC_FOREACH,\n    XSLT_FUNC_DOCUMENT,\n    XSLT_FUNC_WITHPARAM,\n    XSLT_FUNC_PARAM,\n    XSLT_FUNC_VARIABLE,\n    XSLT_FUNC_WHEN,\n    XSLT_FUNC_EXTENSION\n#ifdef XSLT_REFACTORED\n    ,\n    XSLT_FUNC_OTHERWISE,\n    XSLT_FUNC_FALLBACK,\n    XSLT_FUNC_MESSAGE,\n    XSLT_FUNC_INCLUDE,\n    XSLT_FUNC_ATTRSET,\n    XSLT_FUNC_LITERAL_RESULT_ELEMENT,\n    XSLT_FUNC_UNKOWN_FORWARDS_COMPAT\n#endif\n} xsltStyleType;\n\n/**\n * xsltElemPreCompDeallocator:\n * @comp:  the #xsltElemPreComp to free up\n *\n * Deallocates an #xsltElemPreComp structure.\n */\ntypedef void (*xsltElemPreCompDeallocator) (xsltElemPreCompPtr comp);\n\n/**\n * xsltElemPreComp:\n *\n * The basic structure for compiled items of the AST of the XSLT processor.\n * This structure is also intended to be extended by extension implementors.\n * TODO: This is somehow not nice, since it has a \"free\" field, which\n *   derived stylesheet-structs do not have.\n */\nstruct _xsltElemPreComp {\n    xsltElemPreCompPtr next;\t\t/* next item in the global chained\n\t\t\t\t\t   list hold by xsltStylesheet. */\n    xsltStyleType type;\t\t/* type of the element */\n    xsltTransformFunction func;\t/* handling function */\n    xmlNodePtr inst;\t\t\t/* the node in the stylesheet's tree\n\t\t\t\t\t   corresponding to this item */\n\n    /* end of common part */\n    xsltElemPreCompDeallocator free;\t/* the deallocator */\n};\n\n/**\n * xsltStylePreComp:\n *\n * The abstract basic structure for items of the XSLT processor.\n * This includes:\n * 1) compiled forms of XSLT instructions (xsl:if, xsl:attribute, etc.)\n * 2) compiled forms of literal result elements\n * 3) compiled forms of extension elements\n */\ntypedef struct _xsltStylePreComp xsltStylePreComp;\ntypedef xsltStylePreComp *xsltStylePreCompPtr;\n\n#ifdef XSLT_REFACTORED\n\n/*\n* Some pointer-list utility functions.\n*/\nXSLTPUBFUN xsltPointerListPtr XSLTCALL\n\t\txsltPointerListCreate\t\t(int initialSize);\nXSLTPUBFUN void XSLTCALL\n\t\txsltPointerListFree\t\t(xsltPointerListPtr list);\nXSLTPUBFUN void XSLTCALL\n\t\txsltPointerListClear\t\t(xsltPointerListPtr list);\nXSLTPUBFUN int XSLTCALL\n\t\txsltPointerListAddSize\t\t(xsltPointerListPtr list,\n\t\t\t\t\t\t void *item,\n\t\t\t\t\t\t int initialSize);\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n * Refactored structures                                                *\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\n\ntypedef struct _xsltNsListContainer xsltNsListContainer;\ntypedef xsltNsListContainer *xsltNsListContainerPtr;\nstruct _xsltNsListContainer {\n    xmlNsPtr *list;\n    int totalNumber;\n    int xpathNumber;\n};\n\n/**\n * XSLT_ITEM_COMPATIBILITY_FIELDS:\n *\n * Fields for API compatibility to the structure\n * _xsltElemPreComp which is used for extension functions.\n * Note that @next is used for storage; it does not reflect a next\n * sibling in the tree.\n * TODO: Evaluate if we really need such a compatibility.\n */\n#define XSLT_ITEM_COMPATIBILITY_FIELDS \\\n    xsltElemPreCompPtr next;\\\n    xsltStyleType type;\\\n    xsltTransformFunction func;\\\n    xmlNodePtr inst;\n\n/**\n * XSLT_ITEM_NAVIGATION_FIELDS:\n *\n * Currently empty.\n * TODO: It is intended to hold navigational fields in the future.\n */\n#define XSLT_ITEM_NAVIGATION_FIELDS\n/*\n    xsltStylePreCompPtr parent;\\\n    xsltStylePreCompPtr children;\\\n    xsltStylePreCompPtr nextItem;\n*/\n\n/**\n * XSLT_ITEM_NSINSCOPE_FIELDS:\n *\n * The in-scope namespaces.\n */\n#define XSLT_ITEM_NSINSCOPE_FIELDS xsltNsListContainerPtr inScopeNs;\n\n/**\n * XSLT_ITEM_COMMON_FIELDS:\n *\n * Common fields used for all items.\n */\n#define XSLT_ITEM_COMMON_FIELDS \\\n    XSLT_ITEM_COMPATIBILITY_FIELDS \\\n    XSLT_ITEM_NAVIGATION_FIELDS \\\n    XSLT_ITEM_NSINSCOPE_FIELDS\n\n/**\n * _xsltStylePreComp:\n *\n * The abstract basic structure for items of the XSLT processor.\n * This includes:\n * 1) compiled forms of XSLT instructions (e.g. xsl:if, xsl:attribute, etc.)\n * 2) compiled forms of literal result elements\n * 3) various properties for XSLT instructions (e.g. xsl:when,\n *    xsl:with-param)\n *\n * REVISIT TODO: Keep this structure equal to the fields\n *   defined by XSLT_ITEM_COMMON_FIELDS\n */\nstruct _xsltStylePreComp {\n    xsltElemPreCompPtr next;    /* next item in the global chained\n\t\t\t\t   list hold by xsltStylesheet */\n    xsltStyleType type;         /* type of the item */\n    xsltTransformFunction func; /* handling function */\n    xmlNodePtr inst;\t\t/* the node in the stylesheet's tree\n\t\t\t\t   corresponding to this item. */\n    /* Currently no navigational fields. */\n    xsltNsListContainerPtr inScopeNs;\n};\n\n/**\n * xsltStyleBasicEmptyItem:\n *\n * Abstract structure only used as a short-cut for\n * XSLT items with no extra fields.\n * NOTE that it is intended that this structure looks the same as\n *  _xsltStylePreComp.\n */\ntypedef struct _xsltStyleBasicEmptyItem xsltStyleBasicEmptyItem;\ntypedef xsltStyleBasicEmptyItem *xsltStyleBasicEmptyItemPtr;\n\nstruct _xsltStyleBasicEmptyItem {\n    XSLT_ITEM_COMMON_FIELDS\n};\n\n/**\n * xsltStyleBasicExpressionItem:\n *\n * Abstract structure only used as a short-cut for\n * XSLT items with just an expression.\n */\ntypedef struct _xsltStyleBasicExpressionItem xsltStyleBasicExpressionItem;\ntypedef xsltStyleBasicExpressionItem *xsltStyleBasicExpressionItemPtr;\n\nstruct _xsltStyleBasicExpressionItem {\n    XSLT_ITEM_COMMON_FIELDS\n\n    const xmlChar *select; /* TODO: Change this to \"expression\". */\n    xmlXPathCompExprPtr comp; /* TODO: Change this to compExpr. */\n};\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n * XSLT-instructions/declarations                                       *\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\n\n/**\n * xsltStyleItemElement:\n *\n * <!-- Category: instruction -->\n * <xsl:element\n *  name = { qname }\n *  namespace = { uri-reference }\n *  use-attribute-sets = qnames>\n *  <!-- Content: template -->\n * </xsl:element>\n */\ntypedef struct _xsltStyleItemElement xsltStyleItemElement;\ntypedef xsltStyleItemElement *xsltStyleItemElementPtr;\n\nstruct _xsltStyleItemElement {\n    XSLT_ITEM_COMMON_FIELDS\n\n    const xmlChar *use;\n    int      has_use;\n    const xmlChar *name;\n    int      has_name;\n    const xmlChar *ns;\n    const xmlChar *nsPrefix;\n    int      has_ns;\n};\n\n/**\n * xsltStyleItemAttribute:\n *\n * <!-- Category: instruction -->\n * <xsl:attribute\n *  name = { qname }\n *  namespace = { uri-reference }>\n *  <!-- Content: template -->\n * </xsl:attribute>\n */\ntypedef struct _xsltStyleItemAttribute xsltStyleItemAttribute;\ntypedef xsltStyleItemAttribute *xsltStyleItemAttributePtr;\n\nstruct _xsltStyleItemAttribute {\n    XSLT_ITEM_COMMON_FIELDS\n    const xmlChar *name;\n    int      has_name;\n    const xmlChar *ns;\n    const xmlChar *nsPrefix;\n    int      has_ns;\n};\n\n/**\n * xsltStyleItemText:\n *\n * <!-- Category: instruction -->\n * <xsl:text\n *  disable-output-escaping = \"yes\" | \"no\">\n *  <!-- Content: #PCDATA -->\n * </xsl:text>\n */\ntypedef struct _xsltStyleItemText xsltStyleItemText;\ntypedef xsltStyleItemText *xsltStyleItemTextPtr;\n\nstruct _xsltStyleItemText {\n    XSLT_ITEM_COMMON_FIELDS\n    int      noescape;\t\t/* text */\n};\n\n/**\n * xsltStyleItemComment:\n *\n * <!-- Category: instruction -->\n *  <xsl:comment>\n *  <!-- Content: template -->\n * </xsl:comment>\n */\ntypedef xsltStyleBasicEmptyItem xsltStyleItemComment;\ntypedef xsltStyleItemComment *xsltStyleItemCommentPtr;\n\n/**\n * xsltStyleItemPI:\n *\n * <!-- Category: instruction -->\n *  <xsl:processing-instruction\n *  name = { ncname }>\n *  <!-- Content: template -->\n * </xsl:processing-instruction>\n */\ntypedef struct _xsltStyleItemPI xsltStyleItemPI;\ntypedef xsltStyleItemPI *xsltStyleItemPIPtr;\n\nstruct _xsltStyleItemPI {\n    XSLT_ITEM_COMMON_FIELDS\n    const xmlChar *name;\n    int      has_name;\n};\n\n/**\n * xsltStyleItemApplyImports:\n *\n * <!-- Category: instruction -->\n * <xsl:apply-imports />\n */\ntypedef xsltStyleBasicEmptyItem xsltStyleItemApplyImports;\ntypedef xsltStyleItemApplyImports *xsltStyleItemApplyImportsPtr;\n\n/**\n * xsltStyleItemApplyTemplates:\n *\n * <!-- Category: instruction -->\n *  <xsl:apply-templates\n *  select = node-set-expression\n *  mode = qname>\n *  <!-- Content: (xsl:sort | xsl:with-param)* -->\n * </xsl:apply-templates>\n */\ntypedef struct _xsltStyleItemApplyTemplates xsltStyleItemApplyTemplates;\ntypedef xsltStyleItemApplyTemplates *xsltStyleItemApplyTemplatesPtr;\n\nstruct _xsltStyleItemApplyTemplates {\n    XSLT_ITEM_COMMON_FIELDS\n\n    const xmlChar *mode;\t/* apply-templates */\n    const xmlChar *modeURI;\t/* apply-templates */\n    const xmlChar *select;\t/* sort, copy-of, value-of, apply-templates */\n    xmlXPathCompExprPtr comp;\t/* a precompiled XPath expression */\n    /* TODO: with-params */\n};\n\n/**\n * xsltStyleItemCallTemplate:\n *\n * <!-- Category: instruction -->\n *  <xsl:call-template\n *  name = qname>\n *  <!-- Content: xsl:with-param* -->\n * </xsl:call-template>\n */\ntypedef struct _xsltStyleItemCallTemplate xsltStyleItemCallTemplate;\ntypedef xsltStyleItemCallTemplate *xsltStyleItemCallTemplatePtr;\n\nstruct _xsltStyleItemCallTemplate {\n    XSLT_ITEM_COMMON_FIELDS\n\n    xsltTemplatePtr templ;\t/* call-template */\n    const xmlChar *name;\t/* element, attribute, pi */\n    int      has_name;\t\t/* element, attribute, pi */\n    const xmlChar *ns;\t\t/* element */\n    int      has_ns;\t\t/* element */\n    /* TODO: with-params */\n};\n\n/**\n * xsltStyleItemCopy:\n *\n * <!-- Category: instruction -->\n * <xsl:copy\n *  use-attribute-sets = qnames>\n *  <!-- Content: template -->\n * </xsl:copy>\n */\ntypedef struct _xsltStyleItemCopy xsltStyleItemCopy;\ntypedef xsltStyleItemCopy *xsltStyleItemCopyPtr;\n\nstruct _xsltStyleItemCopy {\n   XSLT_ITEM_COMMON_FIELDS\n    const xmlChar *use;\t\t/* copy, element */\n    int      has_use;\t\t/* copy, element */\n};\n\n/**\n * xsltStyleItemIf:\n *\n * <!-- Category: instruction -->\n *  <xsl:if\n *  test = boolean-expression>\n *  <!-- Content: template -->\n * </xsl:if>\n */\ntypedef struct _xsltStyleItemIf xsltStyleItemIf;\ntypedef xsltStyleItemIf *xsltStyleItemIfPtr;\n\nstruct _xsltStyleItemIf {\n    XSLT_ITEM_COMMON_FIELDS\n\n    const xmlChar *test;\t/* if */\n    xmlXPathCompExprPtr comp;\t/* a precompiled XPath expression */\n};\n\n\n/**\n * xsltStyleItemCopyOf:\n *\n * <!-- Category: instruction -->\n * <xsl:copy-of\n *  select = expression />\n */\ntypedef xsltStyleBasicExpressionItem xsltStyleItemCopyOf;\ntypedef xsltStyleItemCopyOf *xsltStyleItemCopyOfPtr;\n\n/**\n * xsltStyleItemValueOf:\n *\n * <!-- Category: instruction -->\n * <xsl:value-of\n *  select = string-expression\n *  disable-output-escaping = \"yes\" | \"no\" />\n */\ntypedef struct _xsltStyleItemValueOf xsltStyleItemValueOf;\ntypedef xsltStyleItemValueOf *xsltStyleItemValueOfPtr;\n\nstruct _xsltStyleItemValueOf {\n    XSLT_ITEM_COMMON_FIELDS\n\n    const xmlChar *select;\n    xmlXPathCompExprPtr comp;\t/* a precompiled XPath expression */\n    int      noescape;\n};\n\n/**\n * xsltStyleItemNumber:\n *\n * <!-- Category: instruction -->\n *  <xsl:number\n *  level = \"single\" | \"multiple\" | \"any\"\n *  count = pattern\n *  from = pattern\n *  value = number-expression\n *  format = { string }\n *  lang = { nmtoken }\n *  letter-value = { \"alphabetic\" | \"traditional\" }\n *  grouping-separator = { char }\n *  grouping-size = { number } />\n */\ntypedef struct _xsltStyleItemNumber xsltStyleItemNumber;\ntypedef xsltStyleItemNumber *xsltStyleItemNumberPtr;\n\nstruct _xsltStyleItemNumber {\n    XSLT_ITEM_COMMON_FIELDS\n    xsltNumberData numdata;\t/* number */\n};\n\n/**\n * xsltStyleItemChoose:\n *\n * <!-- Category: instruction -->\n *  <xsl:choose>\n *  <!-- Content: (xsl:when+, xsl:otherwise?) -->\n * </xsl:choose>\n */\ntypedef xsltStyleBasicEmptyItem xsltStyleItemChoose;\ntypedef xsltStyleItemChoose *xsltStyleItemChoosePtr;\n\n/**\n * xsltStyleItemFallback:\n *\n * <!-- Category: instruction -->\n *  <xsl:fallback>\n *  <!-- Content: template -->\n * </xsl:fallback>\n */\ntypedef xsltStyleBasicEmptyItem xsltStyleItemFallback;\ntypedef xsltStyleItemFallback *xsltStyleItemFallbackPtr;\n\n/**\n * xsltStyleItemForEach:\n *\n * <!-- Category: instruction -->\n * <xsl:for-each\n *   select = node-set-expression>\n *   <!-- Content: (xsl:sort*, template) -->\n * </xsl:for-each>\n */\ntypedef xsltStyleBasicExpressionItem xsltStyleItemForEach;\ntypedef xsltStyleItemForEach *xsltStyleItemForEachPtr;\n\n/**\n * xsltStyleItemMessage:\n *\n * <!-- Category: instruction -->\n * <xsl:message\n *   terminate = \"yes\" | \"no\">\n *   <!-- Content: template -->\n * </xsl:message>\n */\ntypedef struct _xsltStyleItemMessage xsltStyleItemMessage;\ntypedef xsltStyleItemMessage *xsltStyleItemMessagePtr;\n\nstruct _xsltStyleItemMessage {\n    XSLT_ITEM_COMMON_FIELDS\n    int terminate;\n};\n\n/**\n * xsltStyleItemDocument:\n *\n * NOTE: This is not an instruction of XSLT 1.0.\n */\ntypedef struct _xsltStyleItemDocument xsltStyleItemDocument;\ntypedef xsltStyleItemDocument *xsltStyleItemDocumentPtr;\n\nstruct _xsltStyleItemDocument {\n    XSLT_ITEM_COMMON_FIELDS\n    int      ver11;\t\t/* assigned: in xsltDocumentComp;\n                                  read: nowhere;\n                                  TODO: Check if we need. */\n    const xmlChar *filename;\t/* document URL */\n    int has_filename;\n};\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n * Non-instructions (actually properties of instructions/declarations)  *\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\n\n/**\n * xsltStyleBasicItemVariable:\n *\n * Basic struct for xsl:variable, xsl:param and xsl:with-param.\n * It's currently important to have equal fields, since\n * xsltParseStylesheetCallerParam() is used with xsl:with-param from\n * the xslt side and with xsl:param from the exslt side (in\n * exsltFuncFunctionFunction()).\n *\n * FUTURE NOTE: In XSLT 2.0 xsl:param, xsl:variable and xsl:with-param\n *   have additional different fields.\n */\ntypedef struct _xsltStyleBasicItemVariable xsltStyleBasicItemVariable;\ntypedef xsltStyleBasicItemVariable *xsltStyleBasicItemVariablePtr;\n\nstruct _xsltStyleBasicItemVariable {\n    XSLT_ITEM_COMMON_FIELDS\n\n    const xmlChar *select;\n    xmlXPathCompExprPtr comp;\n\n    const xmlChar *name;\n    int      has_name;\n    const xmlChar *ns;\n    int      has_ns;\n};\n\n/**\n * xsltStyleItemVariable:\n *\n * <!-- Category: top-level-element -->\n * <xsl:param\n *   name = qname\n *   select = expression>\n *   <!-- Content: template -->\n * </xsl:param>\n */\ntypedef xsltStyleBasicItemVariable xsltStyleItemVariable;\ntypedef xsltStyleItemVariable *xsltStyleItemVariablePtr;\n\n/**\n * xsltStyleItemParam:\n *\n * <!-- Category: top-level-element -->\n * <xsl:param\n *   name = qname\n *   select = expression>\n *   <!-- Content: template -->\n * </xsl:param>\n */\ntypedef struct _xsltStyleItemParam xsltStyleItemParam;\ntypedef xsltStyleItemParam *xsltStyleItemParamPtr;\n\nstruct _xsltStyleItemParam {\n    XSLT_ITEM_COMMON_FIELDS\n\n    const xmlChar *select;\n    xmlXPathCompExprPtr comp;\n\n    const xmlChar *name;\n    int      has_name;\n    const xmlChar *ns;\n    int      has_ns;\n};\n\n/**\n * xsltStyleItemWithParam:\n *\n * <xsl:with-param\n *  name = qname\n *  select = expression>\n *  <!-- Content: template -->\n * </xsl:with-param>\n */\ntypedef xsltStyleBasicItemVariable xsltStyleItemWithParam;\ntypedef xsltStyleItemWithParam *xsltStyleItemWithParamPtr;\n\n/**\n * xsltStyleItemSort:\n *\n * Reflects the XSLT xsl:sort item.\n * Allowed parents: xsl:apply-templates, xsl:for-each\n * <xsl:sort\n *   select = string-expression\n *   lang = { nmtoken }\n *   data-type = { \"text\" | \"number\" | qname-but-not-ncname }\n *   order = { \"ascending\" | \"descending\" }\n *   case-order = { \"upper-first\" | \"lower-first\" } />\n */\ntypedef struct _xsltStyleItemSort xsltStyleItemSort;\ntypedef xsltStyleItemSort *xsltStyleItemSortPtr;\n\nstruct _xsltStyleItemSort {\n    XSLT_ITEM_COMMON_FIELDS\n\n    const xmlChar *stype;       /* sort */\n    int      has_stype;\t\t/* sort */\n    int      number;\t\t/* sort */\n    const xmlChar *order;\t/* sort */\n    int      has_order;\t\t/* sort */\n    int      descending;\t/* sort */\n    const xmlChar *lang;\t/* sort */\n    int      has_lang;\t\t/* sort */\n    xsltLocale locale;\t\t/* sort */\n    const xmlChar *case_order;\t/* sort */\n    int      lower_first;\t/* sort */\n\n    const xmlChar *use;\n    int      has_use;\n\n    const xmlChar *select;\t/* sort, copy-of, value-of, apply-templates */\n\n    xmlXPathCompExprPtr comp;\t/* a precompiled XPath expression */\n};\n\n\n/**\n * xsltStyleItemWhen:\n *\n * <xsl:when\n *   test = boolean-expression>\n *   <!-- Content: template -->\n * </xsl:when>\n * Allowed parent: xsl:choose\n */\ntypedef struct _xsltStyleItemWhen xsltStyleItemWhen;\ntypedef xsltStyleItemWhen *xsltStyleItemWhenPtr;\n\nstruct _xsltStyleItemWhen {\n    XSLT_ITEM_COMMON_FIELDS\n\n    const xmlChar *test;\n    xmlXPathCompExprPtr comp;\n};\n\n/**\n * xsltStyleItemOtherwise:\n *\n * Allowed parent: xsl:choose\n * <xsl:otherwise>\n *   <!-- Content: template -->\n * </xsl:otherwise>\n */\ntypedef struct _xsltStyleItemOtherwise xsltStyleItemOtherwise;\ntypedef xsltStyleItemOtherwise *xsltStyleItemOtherwisePtr;\n\nstruct _xsltStyleItemOtherwise {\n    XSLT_ITEM_COMMON_FIELDS\n};\n\ntypedef struct _xsltStyleItemInclude xsltStyleItemInclude;\ntypedef xsltStyleItemInclude *xsltStyleItemIncludePtr;\n\nstruct _xsltStyleItemInclude {\n    XSLT_ITEM_COMMON_FIELDS\n    xsltDocumentPtr include;\n};\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n *  XSLT elements in forwards-compatible mode                           *\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\n\ntypedef struct _xsltStyleItemUknown xsltStyleItemUknown;\ntypedef xsltStyleItemUknown *xsltStyleItemUknownPtr;\nstruct _xsltStyleItemUknown {\n    XSLT_ITEM_COMMON_FIELDS\n};\n\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n *  Extension elements                                                  *\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\n\n/*\n * xsltStyleItemExtElement:\n *\n * Reflects extension elements.\n *\n * NOTE: Due to the fact that the structure xsltElemPreComp is most\n * probably already heavily in use out there by users, so we cannot\n * easily change it, we'll create an intermediate structure which will\n * hold an xsltElemPreCompPtr.\n * BIG NOTE: The only problem I see here is that the user processes the\n *  content of the stylesheet tree, possibly he'll lookup the node->psvi\n *  fields in order to find subsequent extension functions.\n *  In this case, the user's code will break, since the node->psvi\n *  field will hold now the xsltStyleItemExtElementPtr and not\n *  the xsltElemPreCompPtr.\n *  However the place where the structure is anchored in the node-tree,\n *  namely node->psvi, has beed already once been moved from node->_private\n *  to node->psvi, so we have a precedent here, which, I think, should allow\n *  us to change such semantics without headaches.\n */\ntypedef struct _xsltStyleItemExtElement xsltStyleItemExtElement;\ntypedef xsltStyleItemExtElement *xsltStyleItemExtElementPtr;\nstruct _xsltStyleItemExtElement {\n    XSLT_ITEM_COMMON_FIELDS\n    xsltElemPreCompPtr item;\n};\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n *  Literal result elements                                             *\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\n\ntypedef struct _xsltEffectiveNs xsltEffectiveNs;\ntypedef xsltEffectiveNs *xsltEffectiveNsPtr;\nstruct _xsltEffectiveNs {\n    xsltEffectiveNsPtr nextInStore; /* storage next */\n    xsltEffectiveNsPtr next; /* next item in the list */\n    const xmlChar *prefix;\n    const xmlChar *nsName;\n    /*\n    * Indicates if eclared on the literal result element; dunno if really\n    * needed.\n    */\n    int holdByElem;\n};\n\n/*\n * Info for literal result elements.\n * This will be set on the elem->psvi field and will be\n * shared by literal result elements, which have the same\n * excluded result namespaces; i.e., this *won't* be created uniquely\n * for every literal result element.\n */\ntypedef struct _xsltStyleItemLRElementInfo xsltStyleItemLRElementInfo;\ntypedef xsltStyleItemLRElementInfo *xsltStyleItemLRElementInfoPtr;\nstruct _xsltStyleItemLRElementInfo {\n    XSLT_ITEM_COMMON_FIELDS\n    /*\n    * @effectiveNs is the set of effective ns-nodes\n    *  on the literal result element, which will be added to the result\n    *  element if not already existing in the result tree.\n    *  This means that excluded namespaces (via exclude-result-prefixes,\n    *  extension-element-prefixes and the XSLT namespace) not added\n    *  to the set.\n    *  Namespace-aliasing was applied on the @effectiveNs.\n    */\n    xsltEffectiveNsPtr effectiveNs;\n\n};\n\n#ifdef XSLT_REFACTORED\n\ntypedef struct _xsltNsAlias xsltNsAlias;\ntypedef xsltNsAlias *xsltNsAliasPtr;\nstruct _xsltNsAlias {\n    xsltNsAliasPtr next; /* next in the list */\n    xmlNsPtr literalNs;\n    xmlNsPtr targetNs;\n    xmlDocPtr docOfTargetNs;\n};\n#endif\n\n#ifdef XSLT_REFACTORED_XSLT_NSCOMP\n\ntypedef struct _xsltNsMap xsltNsMap;\ntypedef xsltNsMap *xsltNsMapPtr;\nstruct _xsltNsMap {\n    xsltNsMapPtr next; /* next in the list */\n    xmlDocPtr doc;\n    xmlNodePtr elem; /* the element holding the ns-decl */\n    xmlNsPtr ns; /* the xmlNs structure holding the XML namespace name */\n    const xmlChar *origNsName; /* the original XML namespace name */\n    const xmlChar *newNsName; /* the mapped XML namespace name */\n};\n#endif\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n *  Compile-time structures for *internal* use only                     *\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\n\ntypedef struct _xsltPrincipalStylesheetData xsltPrincipalStylesheetData;\ntypedef xsltPrincipalStylesheetData *xsltPrincipalStylesheetDataPtr;\n\ntypedef struct _xsltNsList xsltNsList;\ntypedef xsltNsList *xsltNsListPtr;\nstruct _xsltNsList {\n    xsltNsListPtr next; /* next in the list */\n    xmlNsPtr ns;\n};\n\n/*\n* xsltVarInfo:\n*\n* Used at compilation time for parameters and variables.\n*/\ntypedef struct _xsltVarInfo xsltVarInfo;\ntypedef xsltVarInfo *xsltVarInfoPtr;\nstruct _xsltVarInfo {\n    xsltVarInfoPtr next; /* next in the list */\n    xsltVarInfoPtr prev;\n    int depth; /* the depth in the tree */\n    const xmlChar *name;\n    const xmlChar *nsName;\n};\n\n/**\n * xsltCompilerNodeInfo:\n *\n * Per-node information during compile-time.\n */\ntypedef struct _xsltCompilerNodeInfo xsltCompilerNodeInfo;\ntypedef xsltCompilerNodeInfo *xsltCompilerNodeInfoPtr;\nstruct _xsltCompilerNodeInfo {\n    xsltCompilerNodeInfoPtr next;\n    xsltCompilerNodeInfoPtr prev;\n    xmlNodePtr node;\n    int depth;\n    xsltTemplatePtr templ;   /* The owning template */\n    int category;\t     /* XSLT element, LR-element or\n                                extension element */\n    xsltStyleType type;\n    xsltElemPreCompPtr item; /* The compiled information */\n    /* The current in-scope namespaces */\n    xsltNsListContainerPtr inScopeNs;\n    /* The current excluded result namespaces */\n    xsltPointerListPtr exclResultNs;\n    /* The current extension instruction namespaces */\n    xsltPointerListPtr extElemNs;\n\n    /* The current info for literal result elements. */\n    xsltStyleItemLRElementInfoPtr litResElemInfo;\n    /*\n    * Set to 1 if in-scope namespaces changed,\n    *  or excluded result namespaces changed,\n    *  or extension element namespaces changed.\n    * This will trigger creation of new infos\n    *  for literal result elements.\n    */\n    int nsChanged;\n    int preserveWhitespace;\n    int stripWhitespace;\n    int isRoot; /* whether this is the stylesheet's root node */\n    int forwardsCompat; /* whether forwards-compatible mode is enabled */\n    /* whether the content of an extension element was processed */\n    int extContentHandled;\n    /* the type of the current child */\n    xsltStyleType curChildType;\n};\n\n/**\n * XSLT_CCTXT:\n *\n * get pointer to compiler context\n */\n#define XSLT_CCTXT(style) ((xsltCompilerCtxtPtr) style->compCtxt)\n\ntypedef enum {\n    XSLT_ERROR_SEVERITY_ERROR = 0,\n    XSLT_ERROR_SEVERITY_WARNING\n} xsltErrorSeverityType;\n\ntypedef struct _xsltCompilerCtxt xsltCompilerCtxt;\ntypedef xsltCompilerCtxt *xsltCompilerCtxtPtr;\nstruct _xsltCompilerCtxt {\n    void *errorCtxt;            /* user specific error context */\n    /*\n    * used for error/warning reports; e.g. XSLT_ERROR_SEVERITY_WARNING */\n    xsltErrorSeverityType errSeverity;\n    int warnings;\t\t/* TODO: number of warnings found at\n                                   compilation */\n    int errors;\t\t\t/* TODO: number of errors found at\n                                   compilation */\n    xmlDictPtr dict;\n    xsltStylesheetPtr style;\n    int simplified; /* whether this is a simplified stylesheet */\n    /* TODO: structured/unstructured error contexts. */\n    int depth; /* Current depth of processing */\n\n    xsltCompilerNodeInfoPtr inode;\n    xsltCompilerNodeInfoPtr inodeList;\n    xsltCompilerNodeInfoPtr inodeLast;\n    xsltPointerListPtr tmpList; /* Used for various purposes */\n    /*\n    * The XSLT version as specified by the stylesheet's root element.\n    */\n    int isInclude;\n    int hasForwardsCompat; /* whether forwards-compatible mode was used\n\t\t\t     in a parsing episode */\n    int maxNodeInfos; /* TEMP TODO: just for the interest */\n    int maxLREs;  /* TEMP TODO: just for the interest */\n    /*\n    * In order to keep the old behaviour, applying strict rules of\n    * the spec can be turned off. This has effect only on special\n    * mechanisms like whitespace-stripping in the stylesheet.\n    */\n    int strict;\n    xsltPrincipalStylesheetDataPtr psData;\n#ifdef XSLT_REFACTORED_XPATHCOMP\n    xmlXPathContextPtr xpathCtxt;\n#endif\n    xsltStyleItemUknownPtr unknownItem;\n    int hasNsAliases; /* Indicator if there was an xsl:namespace-alias. */\n    xsltNsAliasPtr nsAliases;\n    xsltVarInfoPtr ivars; /* Storage of local in-scope variables/params. */\n    xsltVarInfoPtr ivar; /* topmost local variable/param. */\n};\n\n#else /* XSLT_REFACTORED */\n/*\n* The old structures before refactoring.\n*/\n\n/**\n * _xsltStylePreComp:\n *\n * The in-memory structure corresponding to XSLT stylesheet constructs\n * precomputed data.\n */\nstruct _xsltStylePreComp {\n    xsltElemPreCompPtr next;\t/* chained list */\n    xsltStyleType type;\t\t/* type of the element */\n    xsltTransformFunction func; /* handling function */\n    xmlNodePtr inst;\t\t/* the instruction */\n\n    /*\n     * Pre computed values.\n     */\n\n    const xmlChar *stype;       /* sort */\n    int      has_stype;\t\t/* sort */\n    int      number;\t\t/* sort */\n    const xmlChar *order;\t/* sort */\n    int      has_order;\t\t/* sort */\n    int      descending;\t/* sort */\n    const xmlChar *lang;\t/* sort */\n    int      has_lang;\t\t/* sort */\n    xsltLocale locale;\t\t/* sort */\n    const xmlChar *case_order;\t/* sort */\n    int      lower_first;\t/* sort */\n\n    const xmlChar *use;\t\t/* copy, element */\n    int      has_use;\t\t/* copy, element */\n\n    int      noescape;\t\t/* text */\n\n    const xmlChar *name;\t/* element, attribute, pi */\n    int      has_name;\t\t/* element, attribute, pi */\n    const xmlChar *ns;\t\t/* element */\n    int      has_ns;\t\t/* element */\n\n    const xmlChar *mode;\t/* apply-templates */\n    const xmlChar *modeURI;\t/* apply-templates */\n\n    const xmlChar *test;\t/* if */\n\n    xsltTemplatePtr templ;\t/* call-template */\n\n    const xmlChar *select;\t/* sort, copy-of, value-of, apply-templates */\n\n    int      ver11;\t\t/* document */\n    const xmlChar *filename;\t/* document URL */\n    int      has_filename;\t/* document */\n\n    xsltNumberData numdata;\t/* number */\n\n    xmlXPathCompExprPtr comp;\t/* a precompiled XPath expression */\n    xmlNsPtr *nsList;\t\t/* the namespaces in scope */\n    int nsNr;\t\t\t/* the number of namespaces in scope */\n};\n\n#endif /* XSLT_REFACTORED */\n\n\n/*\n * The in-memory structure corresponding to an XSLT Variable\n * or Param.\n */\ntypedef struct _xsltStackElem xsltStackElem;\ntypedef xsltStackElem *xsltStackElemPtr;\nstruct _xsltStackElem {\n    struct _xsltStackElem *next;/* chained list */\n    xsltStylePreCompPtr comp;   /* the compiled form */\n    int computed;\t\t/* was the evaluation done */\n    const xmlChar *name;\t/* the local part of the name QName */\n    const xmlChar *nameURI;\t/* the URI part of the name QName */\n    const xmlChar *select;\t/* the eval string */\n    xmlNodePtr tree;\t\t/* the sequence constructor if no eval\n\t\t\t\t    string or the location */\n    xmlXPathObjectPtr value;\t/* The value if computed */\n    xmlDocPtr fragment;\t\t/* The Result Tree Fragments (needed for XSLT 1.0)\n\t\t\t\t   which are bound to the variable's lifetime. */\n    int level;                  /* the depth in the tree;\n                                   -1 if persistent (e.g. a given xsl:with-param) */\n    xsltTransformContextPtr context; /* The transformation context; needed to cache\n                                        the variables */\n    int flags;\n};\n\n#ifdef XSLT_REFACTORED\n\nstruct _xsltPrincipalStylesheetData {\n    /*\n    * Namespace dictionary for ns-prefixes and ns-names:\n    * TODO: Shared between stylesheets, and XPath mechanisms.\n    *   Not used yet.\n    */\n    xmlDictPtr namespaceDict;\n    /*\n    * Global list of in-scope namespaces.\n    */\n    xsltPointerListPtr inScopeNamespaces;\n    /*\n    * Global list of information for [xsl:]excluded-result-prefixes.\n    */\n    xsltPointerListPtr exclResultNamespaces;\n    /*\n    * Global list of information for [xsl:]extension-element-prefixes.\n    */\n    xsltPointerListPtr extElemNamespaces;\n    xsltEffectiveNsPtr effectiveNs;\n#ifdef XSLT_REFACTORED_XSLT_NSCOMP\n    /*\n    * Namespace name map to get rid of string comparison of namespace names.\n    */\n    xsltNsMapPtr nsMap;\n#endif\n};\n\n\n#endif\n/*\n * Note that we added a @compCtxt field to anchor an stylesheet compilation\n * context, since, due to historical reasons, various compile-time function\n * take only the stylesheet as argument and not a compilation context.\n */\nstruct _xsltStylesheet {\n    /*\n     * The stylesheet import relation is kept as a tree.\n     */\n    struct _xsltStylesheet *parent;\n    struct _xsltStylesheet *next;\n    struct _xsltStylesheet *imports;\n\n    xsltDocumentPtr docList;\t\t/* the include document list */\n\n    /*\n     * General data on the style sheet document.\n     */\n    xmlDocPtr doc;\t\t/* the parsed XML stylesheet */\n    xmlHashTablePtr stripSpaces;/* the hash table of the strip-space and\n\t\t\t\t   preserve space elements */\n    int             stripAll;\t/* strip-space * (1) preserve-space * (-1) */\n    xmlHashTablePtr cdataSection;/* the hash table of the cdata-section */\n\n    /*\n     * Global variable or parameters.\n     */\n    xsltStackElemPtr variables; /* linked list of param and variables */\n\n    /*\n     * Template descriptions.\n     */\n    xsltTemplatePtr templates;\t/* the ordered list of templates */\n    void *templatesHash;\t/* hash table or wherever compiled templates\n\t\t\t\t   information is stored */\n    void *rootMatch;\t\t/* template based on / */\n    void *keyMatch;\t\t/* template based on key() */\n    void *elemMatch;\t\t/* template based on * */\n    void *attrMatch;\t\t/* template based on @* */\n    void *parentMatch;\t\t/* template based on .. */\n    void *textMatch;\t\t/* template based on text() */\n    void *piMatch;\t\t/* template based on processing-instruction() */\n    void *commentMatch;\t\t/* template based on comment() */\n\n    /*\n     * Namespace aliases.\n     * NOTE: Not used in the refactored code.\n     */\n    xmlHashTablePtr nsAliases;\t/* the namespace alias hash tables */\n\n    /*\n     * Attribute sets.\n     */\n    xmlHashTablePtr attributeSets;/* the attribute sets hash tables */\n\n    /*\n     * Namespaces.\n     * TODO: Eliminate this.\n     */\n    xmlHashTablePtr nsHash;     /* the set of namespaces in use:\n                                   ATTENTION: This is used for\n                                   execution of XPath expressions; unfortunately\n                                   it restricts the stylesheet to have distinct\n                                   prefixes.\n\t\t\t\t   TODO: We need to get rid of this.\n\t\t\t\t */\n    void           *nsDefs;     /* ATTENTION TODO: This is currently used to store\n\t\t\t\t   xsltExtDefPtr (in extensions.c) and\n                                   *not* xmlNsPtr.\n\t\t\t\t */\n\n    /*\n     * Key definitions.\n     */\n    void *keys;\t\t\t/* key definitions */\n\n    /*\n     * Output related stuff.\n     */\n    xmlChar *method;\t\t/* the output method */\n    xmlChar *methodURI;\t\t/* associated namespace if any */\n    xmlChar *version;\t\t/* version string */\n    xmlChar *encoding;\t\t/* encoding string */\n    int omitXmlDeclaration;     /* omit-xml-declaration = \"yes\" | \"no\" */\n\n    /*\n     * Number formatting.\n     */\n    xsltDecimalFormatPtr decimalFormat;\n    int standalone;             /* standalone = \"yes\" | \"no\" */\n    xmlChar *doctypePublic;     /* doctype-public string */\n    xmlChar *doctypeSystem;     /* doctype-system string */\n    int indent;\t\t\t/* should output being indented */\n    xmlChar *mediaType;\t\t/* media-type string */\n\n    /*\n     * Precomputed blocks.\n     */\n    xsltElemPreCompPtr preComps;/* list of precomputed blocks */\n    int warnings;\t\t/* number of warnings found at compilation */\n    int errors;\t\t\t/* number of errors found at compilation */\n\n    xmlChar  *exclPrefix;\t/* last excluded prefixes */\n    xmlChar **exclPrefixTab;\t/* array of excluded prefixes */\n    int       exclPrefixNr;\t/* number of excluded prefixes in scope */\n    int       exclPrefixMax;\t/* size of the array */\n\n    void     *_private;\t\t/* user defined data */\n\n    /*\n     * Extensions.\n     */\n    xmlHashTablePtr extInfos;\t/* the extension data */\n    int\t\t    extrasNr;\t/* the number of extras required */\n\n    /*\n     * For keeping track of nested includes\n     */\n    xsltDocumentPtr includes;\t/* points to last nested include */\n\n    /*\n     * dictionary: shared between stylesheet, context and documents.\n     */\n    xmlDictPtr dict;\n    /*\n     * precompiled attribute value templates.\n     */\n    void *attVTs;\n    /*\n     * if namespace-alias has an alias for the default stylesheet prefix\n     * NOTE: Not used in the refactored code.\n     */\n    const xmlChar *defaultAlias;\n    /*\n     * bypass pre-processing (already done) (used in imports)\n     */\n    int nopreproc;\n    /*\n     * all document text strings were internalized\n     */\n    int internalized;\n    /*\n     * Literal Result Element as Stylesheet c.f. section 2.3\n     */\n    int literal_result;\n    /*\n    * The principal stylesheet\n    */\n    xsltStylesheetPtr principal;\n#ifdef XSLT_REFACTORED\n    /*\n    * Compilation context used during compile-time.\n    */\n    xsltCompilerCtxtPtr compCtxt; /* TODO: Change this to (void *). */\n\n    xsltPrincipalStylesheetDataPtr principalData;\n#endif\n    /*\n     * Forwards-compatible processing\n     */\n    int forwards_compatible;\n\n    xmlHashTablePtr namedTemplates; /* hash table of named templates */\n};\n\ntypedef struct _xsltTransformCache xsltTransformCache;\ntypedef xsltTransformCache *xsltTransformCachePtr;\nstruct _xsltTransformCache {\n    xmlDocPtr RVT;\n    int nbRVT;\n    xsltStackElemPtr stackItems;\n    int nbStackItems;\n#ifdef XSLT_DEBUG_PROFILE_CACHE\n    int dbgCachedRVTs;\n    int dbgReusedRVTs;\n    int dbgCachedVars;\n    int dbgReusedVars;\n#endif\n};\n\n/*\n * The in-memory structure corresponding to an XSLT Transformation.\n */\ntypedef enum {\n    XSLT_OUTPUT_XML = 0,\n    XSLT_OUTPUT_HTML,\n    XSLT_OUTPUT_TEXT\n} xsltOutputType;\n\ntypedef enum {\n    XSLT_STATE_OK = 0,\n    XSLT_STATE_ERROR,\n    XSLT_STATE_STOPPED\n} xsltTransformState;\n\nstruct _xsltTransformContext {\n    xsltStylesheetPtr style;\t\t/* the stylesheet used */\n    xsltOutputType type;\t\t/* the type of output */\n\n    xsltTemplatePtr  templ;\t\t/* the current template */\n    int              templNr;\t\t/* Nb of templates in the stack */\n    int              templMax;\t\t/* Size of the templtes stack */\n    xsltTemplatePtr *templTab;\t\t/* the template stack */\n\n    xsltStackElemPtr  vars;\t\t/* the current variable list */\n    int               varsNr;\t\t/* Nb of variable list in the stack */\n    int               varsMax;\t\t/* Size of the variable list stack */\n    xsltStackElemPtr *varsTab;\t\t/* the variable list stack */\n    int               varsBase;\t\t/* the var base for current templ */\n\n    /*\n     * Extensions\n     */\n    xmlHashTablePtr   extFunctions;\t/* the extension functions */\n    xmlHashTablePtr   extElements;\t/* the extension elements */\n    xmlHashTablePtr   extInfos;\t\t/* the extension data */\n\n    const xmlChar *mode;\t\t/* the current mode */\n    const xmlChar *modeURI;\t\t/* the current mode URI */\n\n    xsltDocumentPtr docList;\t\t/* the document list */\n\n    xsltDocumentPtr document;\t\t/* the current source document; can be NULL if an RTF */\n    xmlNodePtr node;\t\t\t/* the current node being processed */\n    xmlNodeSetPtr nodeList;\t\t/* the current node list */\n    /* xmlNodePtr current;\t\t\tthe node */\n\n    xmlDocPtr output;\t\t\t/* the resulting document */\n    xmlNodePtr insert;\t\t\t/* the insertion node */\n\n    xmlXPathContextPtr xpathCtxt;\t/* the XPath context */\n    xsltTransformState state;\t\t/* the current state */\n\n    /*\n     * Global variables\n     */\n    xmlHashTablePtr   globalVars;\t/* the global variables and params */\n\n    xmlNodePtr inst;\t\t\t/* the instruction in the stylesheet */\n\n    int xinclude;\t\t\t/* should XInclude be processed */\n\n    const char *      outputFile;\t/* the output URI if known */\n\n    int profile;                        /* is this run profiled */\n    long             prof;\t\t/* the current profiled value */\n    int              profNr;\t\t/* Nb of templates in the stack */\n    int              profMax;\t\t/* Size of the templtaes stack */\n    long            *profTab;\t\t/* the profile template stack */\n\n    void            *_private;\t\t/* user defined data */\n\n    int              extrasNr;\t\t/* the number of extras used */\n    int              extrasMax;\t\t/* the number of extras allocated */\n    xsltRuntimeExtraPtr extras;\t\t/* extra per runtime information */\n\n    xsltDocumentPtr  styleList;\t\t/* the stylesheet docs list */\n    void                 * sec;\t\t/* the security preferences if any */\n\n    xmlGenericErrorFunc  error;\t\t/* a specific error handler */\n    void              * errctx;\t\t/* context for the error handler */\n\n    xsltSortFunc      sortfunc;\t\t/* a ctxt specific sort routine */\n\n    /*\n     * handling of temporary Result Value Tree\n     * (XSLT 1.0 term: \"Result Tree Fragment\")\n     */\n    xmlDocPtr       tmpRVT;\t\t/* list of RVT without persistance */\n    xmlDocPtr       persistRVT;\t\t/* list of persistant RVTs */\n    int             ctxtflags;          /* context processing flags */\n\n    /*\n     * Speed optimization when coalescing text nodes\n     */\n    const xmlChar  *lasttext;\t\t/* last text node content */\n    int             lasttsize;\t\t/* last text node size */\n    int             lasttuse;\t\t/* last text node use */\n    /*\n     * Per Context Debugging\n     */\n    int debugStatus;\t\t\t/* the context level debug status */\n    unsigned long* traceCode;\t\t/* pointer to the variable holding the mask */\n\n    int parserOptions;\t\t\t/* parser options xmlParserOption */\n\n    /*\n     * dictionary: shared between stylesheet, context and documents.\n     */\n    xmlDictPtr dict;\n    xmlDocPtr\t\ttmpDoc; /* Obsolete; not used in the library. */\n    /*\n     * all document text strings are internalized\n     */\n    int internalized;\n    int nbKeys;\n    int hasTemplKeyPatterns;\n    xsltTemplatePtr currentTemplateRule; /* the Current Template Rule */\n    xmlNodePtr initialContextNode;\n    xmlDocPtr initialContextDoc;\n    xsltTransformCachePtr cache;\n    void *contextVariable; /* the current variable item */\n    xmlDocPtr localRVT; /* list of local tree fragments; will be freed when\n\t\t\t   the instruction which created the fragment\n                           exits */\n    xmlDocPtr localRVTBase; /* Obsolete */\n    int keyInitLevel;   /* Needed to catch recursive keys issues */\n    int depth;          /* Needed to catch recursions */\n    int maxTemplateDepth;\n    int maxTemplateVars;\n};\n\n/**\n * CHECK_STOPPED:\n *\n * Macro to check if the XSLT processing should be stopped.\n * Will return from the function.\n */\n#define CHECK_STOPPED if (ctxt->state == XSLT_STATE_STOPPED) return;\n\n/**\n * CHECK_STOPPEDE:\n *\n * Macro to check if the XSLT processing should be stopped.\n * Will goto the error: label.\n */\n#define CHECK_STOPPEDE if (ctxt->state == XSLT_STATE_STOPPED) goto error;\n\n/**\n * CHECK_STOPPED0:\n *\n * Macro to check if the XSLT processing should be stopped.\n * Will return from the function with a 0 value.\n */\n#define CHECK_STOPPED0 if (ctxt->state == XSLT_STATE_STOPPED) return(0);\n\n/*\n * The macro XML_CAST_FPTR is a hack to avoid a gcc warning about\n * possible incompatibilities between function pointers and object\n * pointers.  It is defined in libxml/hash.h within recent versions\n * of libxml2, but is put here for compatibility.\n */\n#ifndef XML_CAST_FPTR\n/**\n * XML_CAST_FPTR:\n * @fptr:  pointer to a function\n *\n * Macro to do a casting from an object pointer to a\n * function pointer without encountering a warning from\n * gcc\n *\n * #define XML_CAST_FPTR(fptr) (*(void **)(&fptr))\n * This macro violated ISO C aliasing rules (gcc4 on s390 broke)\n * so it is disabled now\n */\n\n#define XML_CAST_FPTR(fptr) fptr\n#endif\n/*\n * Functions associated to the internal types\nxsltDecimalFormatPtr\txsltDecimalFormatGetByName(xsltStylesheetPtr sheet,\n\t\t\t\t\t\t   xmlChar *name);\n */\nXSLTPUBFUN xsltStylesheetPtr XSLTCALL\n\t\t\txsltNewStylesheet\t(void);\nXSLTPUBFUN xsltStylesheetPtr XSLTCALL\n\t\t\txsltParseStylesheetFile\t(const xmlChar* filename);\nXSLTPUBFUN void XSLTCALL\n\t\t\txsltFreeStylesheet\t(xsltStylesheetPtr style);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltIsBlank\t\t(xmlChar *str);\nXSLTPUBFUN void XSLTCALL\n\t\t\txsltFreeStackElemList\t(xsltStackElemPtr elem);\nXSLTPUBFUN xsltDecimalFormatPtr XSLTCALL\n\t\t\txsltDecimalFormatGetByName(xsltStylesheetPtr style,\n\t\t\t\t\t\t xmlChar *name);\nXSLTPUBFUN xsltDecimalFormatPtr XSLTCALL\n\t\t\txsltDecimalFormatGetByQName(xsltStylesheetPtr style,\n\t\t\t\t\t\t const xmlChar *nsUri,\n                                                 const xmlChar *name);\n\nXSLTPUBFUN xsltStylesheetPtr XSLTCALL\n\t\t\txsltParseStylesheetProcess(xsltStylesheetPtr ret,\n\t\t\t\t\t\t xmlDocPtr doc);\nXSLTPUBFUN void XSLTCALL\n\t\t\txsltParseStylesheetOutput(xsltStylesheetPtr style,\n\t\t\t\t\t\t xmlNodePtr cur);\nXSLTPUBFUN xsltStylesheetPtr XSLTCALL\n\t\t\txsltParseStylesheetDoc\t(xmlDocPtr doc);\nXSLTPUBFUN xsltStylesheetPtr XSLTCALL\n\t\t\txsltParseStylesheetImportedDoc(xmlDocPtr doc,\n\t\t\t\t\t\txsltStylesheetPtr style);\nXSLTPUBFUN xsltStylesheetPtr XSLTCALL\n\t\t\txsltLoadStylesheetPI\t(xmlDocPtr doc);\nXSLTPUBFUN void XSLTCALL\n\t\t\txsltNumberFormat\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xsltNumberDataPtr data,\n\t\t\t\t\t\t xmlNodePtr node);\nXSLTPUBFUN xmlXPathError XSLTCALL\n\t\t\txsltFormatNumberConversion(xsltDecimalFormatPtr self,\n\t\t\t\t\t\t xmlChar *format,\n\t\t\t\t\t\t double number,\n\t\t\t\t\t\t xmlChar **result);\n\nXSLTPUBFUN void XSLTCALL\n\t\t\txsltParseTemplateContent(xsltStylesheetPtr style,\n\t\t\t\t\t\t xmlNodePtr templ);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltAllocateExtra\t(xsltStylesheetPtr style);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltAllocateExtraCtxt\t(xsltTransformContextPtr ctxt);\n/*\n * Extra functions for Result Value Trees\n */\nXSLTPUBFUN xmlDocPtr XSLTCALL\n\t\t\txsltCreateRVT\t\t(xsltTransformContextPtr ctxt);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltRegisterTmpRVT\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlDocPtr RVT);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltRegisterLocalRVT\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlDocPtr RVT);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltRegisterPersistRVT\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlDocPtr RVT);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltExtensionInstructionResultRegister(\n\t\t\t\t\t\t xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlXPathObjectPtr obj);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltExtensionInstructionResultFinalize(\n\t\t\t\t\t\t xsltTransformContextPtr ctxt);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltFlagRVTs(\n\t\t\t\t\t\t xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlXPathObjectPtr obj,\n\t\t\t\t\t\t void *val);\nXSLTPUBFUN void XSLTCALL\n\t\t\txsltFreeRVTs\t\t(xsltTransformContextPtr ctxt);\nXSLTPUBFUN void XSLTCALL\n\t\t\txsltReleaseRVT\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlDocPtr RVT);\n/*\n * Extra functions for Attribute Value Templates\n */\nXSLTPUBFUN void XSLTCALL\n\t\t\txsltCompileAttr\t\t(xsltStylesheetPtr style,\n\t\t\t\t\t\t xmlAttrPtr attr);\nXSLTPUBFUN xmlChar * XSLTCALL\n\t\t\txsltEvalAVT\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t void *avt,\n\t\t\t\t\t\t xmlNodePtr node);\nXSLTPUBFUN void XSLTCALL\n\t\t\txsltFreeAVTList\t\t(void *avt);\n\n/*\n * Extra function for successful xsltCleanupGlobals / xsltInit sequence.\n */\n\nXSLTPUBFUN void XSLTCALL\n\t\t\txsltUninit\t\t(void);\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n *  Compile-time functions for *internal* use only                      *\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\n\n#ifdef XSLT_REFACTORED\nXSLTPUBFUN void XSLTCALL\n\t\t\txsltParseSequenceConstructor(\n\t\t\t\t\t\t xsltCompilerCtxtPtr cctxt,\n\t\t\t\t\t\t xmlNodePtr start);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltParseAnyXSLTElem\t(xsltCompilerCtxtPtr cctxt,\n\t\t\t\t\t\t xmlNodePtr elem);\n#ifdef XSLT_REFACTORED_XSLT_NSCOMP\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltRestoreDocumentNamespaces(\n\t\t\t\t\t\t xsltNsMapPtr ns,\n\t\t\t\t\t\t xmlDocPtr doc);\n#endif\n#endif /* XSLT_REFACTORED */\n\n/************************************************************************\n *\t\t\t\t\t\t\t\t\t*\n *  Transformation-time functions for *internal* use only               *\n *\t\t\t\t\t\t\t\t\t*\n ************************************************************************/\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltInitCtxtKey\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xsltDocumentPtr doc,\n\t\t\t\t\t\t xsltKeyDefPtr keyd);\nXSLTPUBFUN int XSLTCALL\n\t\t\txsltInitAllDocKeys\t(xsltTransformContextPtr ctxt);\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLT_H__ */\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/xsltconfig.h",
    "content": "/*\n * Summary: compile-time version information for the XSLT engine\n * Description: compile-time version information for the XSLT engine\n *              this module is autogenerated.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLTCONFIG_H__\n#define __XML_XSLTCONFIG_H__\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * LIBXSLT_DOTTED_VERSION:\n *\n * the version string like \"1.2.3\"\n */\n#define LIBXSLT_DOTTED_VERSION \"1.1.33\"\n\n/**\n * LIBXSLT_VERSION:\n *\n * the version number: 1.2.3 value is 10203\n */\n#define LIBXSLT_VERSION 10133\n\n/**\n * LIBXSLT_VERSION_STRING:\n *\n * the version number string, 1.2.3 value is \"10203\"\n */\n#define LIBXSLT_VERSION_STRING \"10133\"\n\n/**\n * LIBXSLT_VERSION_EXTRA:\n *\n * extra version information, used to show a CVS compilation\n */\n#define\tLIBXSLT_VERSION_EXTRA \"\"\n\n/**\n * WITH_XSLT_DEBUG:\n *\n * Activate the compilation of the debug reporting. Speed penalty\n * is insignifiant and being able to run xsltpoc -v is useful. On\n * by default unless --without-debug is passed to configure\n */\n#if 1\n#define WITH_XSLT_DEBUG\n#endif\n\n#if 0\n/**\n * DEBUG_MEMORY:\n *\n * should be activated only when debugging libxslt. It replaces the\n * allocator with a collect and debug shell to the libc allocator.\n * Use configure --with-mem-debug to activate it on both library\n */\n#define DEBUG_MEMORY\n\n/**\n * DEBUG_MEMORY_LOCATION:\n *\n * should be activated only when debugging libxslt.\n * DEBUG_MEMORY_LOCATION should be activated only when libxml has\n * been configured with --with-debug-mem too\n */\n#define DEBUG_MEMORY_LOCATION\n#endif\n\n/**\n * XSLT_NEED_TRIO:\n *\n * should be activated if the existing libc library lacks some of the\n * string formatting function, in that case reuse the Trio ones already\n * compiled in the libxml2 library.\n */\n\n#if 0\n#define XSLT_NEED_TRIO\n#endif\n#ifdef __VMS\n#define HAVE_MATH_H 1\n#define HAVE_SYS_STAT_H 1\n#ifndef XSLT_NEED_TRIO\n#define XSLT_NEED_TRIO\n#endif\n#endif\n\n#ifdef\tXSLT_NEED_TRIO\n#define\tTRIO_REPLACE_STDIO\n#endif\n\n/**\n * WITH_XSLT_DEBUGGER:\n *\n * Activate the compilation of the debugger support. Speed penalty\n * is insignifiant.\n * On by default unless --without-debugger is passed to configure\n */\n#if 1\n#ifndef WITH_DEBUGGER\n#define WITH_DEBUGGER\n#endif\n#endif\n\n/**\n * WITH_MODULES:\n *\n * Whether module support is configured into libxslt\n * Note: no default module path for win32 platforms\n */\n#if 0\n#ifndef WITH_MODULES\n#define WITH_MODULES\n#endif\n#define LIBXSLT_DEFAULT_PLUGINS_PATH() \"/tmp/pip-req-build-8wvhzb9p/build/tmp/libxml2/lib/libxslt-plugins\"\n#endif\n\n/**\n * ATTRIBUTE_UNUSED:\n *\n * This macro is used to flag unused function parameters to GCC\n */\n#ifdef __GNUC__\n#ifdef HAVE_ANSIDECL_H\n#include <ansidecl.h>\n#endif\n#ifndef ATTRIBUTE_UNUSED\n#define ATTRIBUTE_UNUSED __attribute__((unused))\n#endif\n#else\n#define ATTRIBUTE_UNUSED\n#endif\n\n/**\n * LIBXSLT_ATTR_FORMAT:\n *\n * This macro is used to indicate to GCC the parameters are printf-like\n */\n#ifdef __GNUC__\n#define LIBXSLT_ATTR_FORMAT(fmt,args) __attribute__((__format__(__printf__,fmt,args)))\n#else\n#define LIBXSLT_ATTR_FORMAT(fmt,args)\n#endif\n\n/**\n * LIBXSLT_PUBLIC:\n *\n * This macro is used to declare PUBLIC variables for Cygwin and for MSC on Windows\n */\n#if !defined LIBXSLT_PUBLIC\n#if (defined(__CYGWIN__) || defined _MSC_VER) && !defined IN_LIBXSLT && !defined LIBXSLT_STATIC\n#define LIBXSLT_PUBLIC __declspec(dllimport)\n#else\n#define LIBXSLT_PUBLIC\n#endif\n#endif\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLTCONFIG_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/xsltexports.h",
    "content": "/*\n * Summary: macros for marking symbols as exportable/importable.\n * Description: macros for marking symbols as exportable/importable.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Igor Zlatkovic <igor@zlatkovic.com>\n */\n\n#ifndef __XSLT_EXPORTS_H__\n#define __XSLT_EXPORTS_H__\n\n/**\n * XSLTPUBFUN:\n * XSLTPUBFUN, XSLTPUBVAR, XSLTCALL\n *\n * Macros which declare an exportable function, an exportable variable and\n * the calling convention used for functions.\n *\n * Please use an extra block for every platform/compiler combination when\n * modifying this, rather than overlong #ifdef lines. This helps\n * readability as well as the fact that different compilers on the same\n * platform might need different definitions.\n */\n\n/**\n * XSLTPUBFUN:\n *\n * Macros which declare an exportable function\n */\n#define XSLTPUBFUN\n/**\n * XSLTPUBVAR:\n *\n * Macros which declare an exportable variable\n */\n#define XSLTPUBVAR extern\n/**\n * XSLTCALL:\n *\n * Macros which declare the called convention for exported functions\n */\n#define XSLTCALL\n\n/** DOC_DISABLE */\n\n/* Windows platform with MS compiler */\n#if defined(_WIN32) && defined(_MSC_VER)\n  #undef XSLTPUBFUN\n  #undef XSLTPUBVAR\n  #undef XSLTCALL\n  #if defined(IN_LIBXSLT) && !defined(LIBXSLT_STATIC)\n    #define XSLTPUBFUN __declspec(dllexport)\n    #define XSLTPUBVAR __declspec(dllexport)\n  #else\n    #define XSLTPUBFUN\n    #if !defined(LIBXSLT_STATIC)\n      #define XSLTPUBVAR __declspec(dllimport) extern\n    #else\n      #define XSLTPUBVAR extern\n    #endif\n  #endif\n  #define XSLTCALL __cdecl\n  #if !defined _REENTRANT\n    #define _REENTRANT\n  #endif\n#endif\n\n/* Windows platform with Borland compiler */\n#if defined(_WIN32) && defined(__BORLANDC__)\n  #undef XSLTPUBFUN\n  #undef XSLTPUBVAR\n  #undef XSLTCALL\n  #if defined(IN_LIBXSLT) && !defined(LIBXSLT_STATIC)\n    #define XSLTPUBFUN __declspec(dllexport)\n    #define XSLTPUBVAR __declspec(dllexport) extern\n  #else\n    #define XSLTPUBFUN\n    #if !defined(LIBXSLT_STATIC)\n      #define XSLTPUBVAR __declspec(dllimport) extern\n    #else\n      #define XSLTPUBVAR extern\n    #endif\n  #endif\n  #define XSLTCALL __cdecl\n  #if !defined _REENTRANT\n    #define _REENTRANT\n  #endif\n#endif\n\n/* Windows platform with GNU compiler (Mingw) */\n#if defined(_WIN32) && defined(__MINGW32__)\n  #undef XSLTPUBFUN\n  #undef XSLTPUBVAR\n  #undef XSLTCALL\n/*\n  #if defined(IN_LIBXSLT) && !defined(LIBXSLT_STATIC)\n*/\n  #if !defined(LIBXSLT_STATIC)\n    #define XSLTPUBFUN __declspec(dllexport)\n    #define XSLTPUBVAR __declspec(dllexport) extern\n  #else\n    #define XSLTPUBFUN\n    #if !defined(LIBXSLT_STATIC)\n      #define XSLTPUBVAR __declspec(dllimport) extern\n    #else\n      #define XSLTPUBVAR extern\n    #endif\n  #endif\n  #define XSLTCALL __cdecl\n  #if !defined _REENTRANT\n    #define _REENTRANT\n  #endif\n#endif\n\n/* Cygwin platform (does not define _WIN32), GNU compiler */\n#if defined(__CYGWIN__)\n  #undef XSLTPUBFUN\n  #undef XSLTPUBVAR\n  #undef XSLTCALL\n  #if defined(IN_LIBXSLT) && !defined(LIBXSLT_STATIC)\n    #define XSLTPUBFUN __declspec(dllexport)\n    #define XSLTPUBVAR __declspec(dllexport)\n  #else\n    #define XSLTPUBFUN\n    #if !defined(LIBXSLT_STATIC)\n      #define XSLTPUBVAR __declspec(dllimport) extern\n    #else\n      #define XSLTPUBVAR extern\n    #endif\n  #endif\n  #define XSLTCALL __cdecl\n#endif\n\n/* Compatibility */\n#if !defined(LIBXSLT_PUBLIC)\n#define LIBXSLT_PUBLIC XSLTPUBVAR\n#endif\n\n#endif /* __XSLT_EXPORTS_H__ */\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/xsltlocale.h",
    "content": "/*\n * Summary: Locale handling\n * Description: Interfaces for locale handling. Needed for language dependent\n *              sorting.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Nick Wellnhofer\n */\n\n#ifndef __XML_XSLTLOCALE_H__\n#define __XML_XSLTLOCALE_H__\n\n#include <libxml/xmlstring.h>\n#include \"xsltexports.h\"\n\n#ifdef HAVE_STRXFRM_L\n\n/*\n * XSLT_LOCALE_POSIX:\n * Macro indicating to use POSIX locale extensions\n */\n#define XSLT_LOCALE_POSIX\n\n#ifdef HAVE_LOCALE_H\n#include <locale.h>\n#endif\n#ifdef HAVE_XLOCALE_H\n#include <xlocale.h>\n#endif\n\ntypedef locale_t xsltLocale;\ntypedef xmlChar xsltLocaleChar;\n\n#elif defined(_WIN32) && !defined(__CYGWIN__)\n\n/*\n * XSLT_LOCALE_WINAPI:\n * Macro indicating to use WinAPI for extended locale support\n */\n#define XSLT_LOCALE_WINAPI\n\n#include <windows.h>\n#include <winnls.h>\n\ntypedef LCID xsltLocale;\ntypedef wchar_t xsltLocaleChar;\n\n#else\n\n/*\n * XSLT_LOCALE_NONE:\n * Macro indicating that there's no extended locale support\n */\n#define XSLT_LOCALE_NONE\n\ntypedef void *xsltLocale;\ntypedef xmlChar xsltLocaleChar;\n\n#endif\n\nXSLTPUBFUN xsltLocale XSLTCALL\n\txsltNewLocale\t\t\t(const xmlChar *langName);\nXSLTPUBFUN void XSLTCALL\n\txsltFreeLocale\t\t\t(xsltLocale locale);\nXSLTPUBFUN xsltLocaleChar * XSLTCALL\n\txsltStrxfrm\t\t\t(xsltLocale locale,\n\t\t\t\t\t const xmlChar *string);\nXSLTPUBFUN int XSLTCALL\n\txsltLocaleStrcmp\t\t(xsltLocale locale,\n\t\t\t\t\t const xsltLocaleChar *str1,\n\t\t\t\t\t const xsltLocaleChar *str2);\nXSLTPUBFUN void XSLTCALL\n\txsltFreeLocales\t\t\t(void);\n\n#endif /* __XML_XSLTLOCALE_H__ */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/libxslt/xsltutils.h",
    "content": "/*\n * Summary: set of utilities for the XSLT engine\n * Description: interfaces for the utilities module of the XSLT engine.\n *              things like message handling, profiling, and other\n *              generally useful routines.\n *\n * Copy: See Copyright for the status of this software.\n *\n * Author: Daniel Veillard\n */\n\n#ifndef __XML_XSLTUTILS_H__\n#define __XML_XSLTUTILS_H__\n\n#include <libxslt/xsltconfig.h>\n#ifdef HAVE_STDARG_H\n#include <stdarg.h>\n#endif\n#include <libxml/xpath.h>\n#include <libxml/dict.h>\n#include <libxml/xmlerror.h>\n#include \"xsltexports.h\"\n#include \"xsltInternals.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * XSLT_TODO:\n *\n * Macro to flag unimplemented blocks.\n */\n#define XSLT_TODO\t\t\t\t\t\t\t\\\n    xsltGenericError(xsltGenericErrorContext,\t\t\t\t\\\n\t    \"Unimplemented block at %s:%d\\n\",\t\t\t\t\\\n            __FILE__, __LINE__);\n\n/**\n * XSLT_STRANGE:\n *\n * Macro to flag that a problem was detected internally.\n */\n#define XSLT_STRANGE\t\t\t\t\t\t\t\\\n    xsltGenericError(xsltGenericErrorContext,\t\t\t\t\\\n\t    \"Internal error at %s:%d\\n\",\t\t\t\t\\\n            __FILE__, __LINE__);\n\n/**\n * IS_XSLT_ELEM:\n *\n * Checks that the element pertains to XSLT namespace.\n */\n#define IS_XSLT_ELEM(n)\t\t\t\t\t\t\t\\\n    (((n) != NULL) && ((n)->type == XML_ELEMENT_NODE) &&                \\\n     ((n)->ns != NULL) && (xmlStrEqual((n)->ns->href, XSLT_NAMESPACE)))\n\n/**\n * IS_XSLT_NAME:\n *\n * Checks the value of an element in XSLT namespace.\n */\n#define IS_XSLT_NAME(n, val)\t\t\t\t\t\t\\\n    (xmlStrEqual((n)->name, (const xmlChar *) (val)))\n\n/**\n * IS_XSLT_REAL_NODE:\n *\n * Check that a node is a 'real' one: document, element, text or attribute.\n */\n#define IS_XSLT_REAL_NODE(n)\t\t\t\t\t\t\\\n    (((n) != NULL) &&\t\t\t\t\t\t\t\\\n     (((n)->type == XML_ELEMENT_NODE) ||\t\t\t\t\\\n      ((n)->type == XML_TEXT_NODE) ||\t\t\t\t\t\\\n      ((n)->type == XML_CDATA_SECTION_NODE) ||\t\t\t\t\\\n      ((n)->type == XML_ATTRIBUTE_NODE) ||\t\t\t\t\\\n      ((n)->type == XML_DOCUMENT_NODE) ||\t\t\t\t\\\n      ((n)->type == XML_HTML_DOCUMENT_NODE) ||\t\t\t\t\\\n      ((n)->type == XML_COMMENT_NODE) ||\t\t\t\t\\\n      ((n)->type == XML_PI_NODE)))\n\n/*\n * Our own version of namespaced atributes lookup.\n */\nXSLTPUBFUN xmlChar * XSLTCALL\n\t\txsltGetNsProp\t(xmlNodePtr node,\n\t\t\t\t const xmlChar *name,\n\t\t\t\t const xmlChar *nameSpace);\nXSLTPUBFUN const xmlChar * XSLTCALL\n\t\txsltGetCNsProp\t(xsltStylesheetPtr style,\n\t\t\t\t xmlNodePtr node,\n\t\t\t\t const xmlChar *name,\n\t\t\t\t const xmlChar *nameSpace);\nXSLTPUBFUN int XSLTCALL\n\t\txsltGetUTF8Char\t(const unsigned char *utf,\n\t\t\t\t int *len);\n\n/*\n * XSLT Debug Tracing Tracing Types\n */\ntypedef enum {\n\tXSLT_TRACE_ALL =\t\t-1,\n\tXSLT_TRACE_NONE =\t\t0,\n\tXSLT_TRACE_COPY_TEXT =\t\t1<<0,\n\tXSLT_TRACE_PROCESS_NODE =\t1<<1,\n\tXSLT_TRACE_APPLY_TEMPLATE =\t1<<2,\n\tXSLT_TRACE_COPY =\t\t1<<3,\n\tXSLT_TRACE_COMMENT =\t\t1<<4,\n\tXSLT_TRACE_PI =\t\t\t1<<5,\n\tXSLT_TRACE_COPY_OF =\t\t1<<6,\n\tXSLT_TRACE_VALUE_OF =\t\t1<<7,\n\tXSLT_TRACE_CALL_TEMPLATE =\t1<<8,\n\tXSLT_TRACE_APPLY_TEMPLATES =\t1<<9,\n\tXSLT_TRACE_CHOOSE =\t\t1<<10,\n\tXSLT_TRACE_IF =\t\t\t1<<11,\n\tXSLT_TRACE_FOR_EACH =\t\t1<<12,\n\tXSLT_TRACE_STRIP_SPACES =\t1<<13,\n\tXSLT_TRACE_TEMPLATES =\t\t1<<14,\n\tXSLT_TRACE_KEYS =\t\t1<<15,\n\tXSLT_TRACE_VARIABLES =\t\t1<<16\n} xsltDebugTraceCodes;\n\n/**\n * XSLT_TRACE:\n *\n * Control the type of xsl debugtrace messages emitted.\n */\n#define XSLT_TRACE(ctxt,code,call)\t\\\n\tif (ctxt->traceCode && (*(ctxt->traceCode) & code)) \\\n\t    call\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltDebugSetDefaultTrace(xsltDebugTraceCodes val);\nXSLTPUBFUN xsltDebugTraceCodes XSLTCALL\n\t\txsltDebugGetDefaultTrace(void);\n\n/*\n * XSLT specific error and debug reporting functions.\n */\nXSLTPUBVAR xmlGenericErrorFunc xsltGenericError;\nXSLTPUBVAR void *xsltGenericErrorContext;\nXSLTPUBVAR xmlGenericErrorFunc xsltGenericDebug;\nXSLTPUBVAR void *xsltGenericDebugContext;\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltPrintErrorContext\t\t(xsltTransformContextPtr ctxt,\n\t                                         xsltStylesheetPtr style,\n\t\t\t\t\t\t xmlNodePtr node);\nXSLTPUBFUN void XSLTCALL\n\t\txsltMessage\t\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t\t xmlNodePtr inst);\nXSLTPUBFUN void XSLTCALL\n\t\txsltSetGenericErrorFunc\t\t(void *ctx,\n\t\t\t\t\t\t xmlGenericErrorFunc handler);\nXSLTPUBFUN void XSLTCALL\n\t\txsltSetGenericDebugFunc\t\t(void *ctx,\n\t\t\t\t\t\t xmlGenericErrorFunc handler);\nXSLTPUBFUN void XSLTCALL\n\t\txsltSetTransformErrorFunc\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t void *ctx,\n\t\t\t\t\t\t xmlGenericErrorFunc handler);\nXSLTPUBFUN void XSLTCALL\n\t\txsltTransformError\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xsltStylesheetPtr style,\n\t\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t\t const char *msg,\n\t\t\t\t\t\t ...) LIBXSLT_ATTR_FORMAT(4,5);\n\nXSLTPUBFUN int XSLTCALL\n\t\txsltSetCtxtParseOptions\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t int options);\n/*\n * Sorting.\n */\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltDocumentSortFunction\t(xmlNodeSetPtr list);\nXSLTPUBFUN void XSLTCALL\n\t\txsltSetSortFunc\t\t\t(xsltSortFunc handler);\nXSLTPUBFUN void XSLTCALL\n\t\txsltSetCtxtSortFunc\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xsltSortFunc handler);\nXSLTPUBFUN void XSLTCALL\n\t\txsltDefaultSortFunction\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr *sorts,\n\t\t\t\t\t\t int nbsorts);\nXSLTPUBFUN void XSLTCALL\n\t\txsltDoSortFunction\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr * sorts,\n\t\t\t\t\t\t int nbsorts);\nXSLTPUBFUN xmlXPathObjectPtr * XSLTCALL\n\t\txsltComputeSortResult\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t xmlNodePtr sort);\n\n/*\n * QNames handling.\n */\n\nXSLTPUBFUN const xmlChar * XSLTCALL\n\t\txsltSplitQName\t\t\t(xmlDictPtr dict,\n\t\t\t\t\t\t const xmlChar *name,\n\t\t\t\t\t\t const xmlChar **prefix);\nXSLTPUBFUN const xmlChar * XSLTCALL\n\t\txsltGetQNameURI\t\t\t(xmlNodePtr node,\n\t\t\t\t\t\t xmlChar **name);\n\nXSLTPUBFUN const xmlChar * XSLTCALL\n\t\txsltGetQNameURI2\t\t(xsltStylesheetPtr style,\n\t\t\t\t\t\t xmlNodePtr node,\n\t\t\t\t\t\t const xmlChar **name);\n\n/*\n * Output, reuse libxml I/O buffers.\n */\nXSLTPUBFUN int XSLTCALL\n\t\txsltSaveResultTo\t\t(xmlOutputBufferPtr buf,\n\t\t\t\t\t\t xmlDocPtr result,\n\t\t\t\t\t\t xsltStylesheetPtr style);\nXSLTPUBFUN int XSLTCALL\n\t\txsltSaveResultToFilename\t(const char *URI,\n\t\t\t\t\t\t xmlDocPtr result,\n\t\t\t\t\t\t xsltStylesheetPtr style,\n\t\t\t\t\t\t int compression);\nXSLTPUBFUN int XSLTCALL\n\t\txsltSaveResultToFile\t\t(FILE *file,\n\t\t\t\t\t\t xmlDocPtr result,\n\t\t\t\t\t\t xsltStylesheetPtr style);\nXSLTPUBFUN int XSLTCALL\n\t\txsltSaveResultToFd\t\t(int fd,\n\t\t\t\t\t\t xmlDocPtr result,\n\t\t\t\t\t\t xsltStylesheetPtr style);\nXSLTPUBFUN int XSLTCALL\n\t\txsltSaveResultToString          (xmlChar **doc_txt_ptr,\n                                                 int * doc_txt_len,\n                                                 xmlDocPtr result,\n                                                 xsltStylesheetPtr style);\n\n/*\n * XPath interface\n */\nXSLTPUBFUN xmlXPathCompExprPtr XSLTCALL\n\t\txsltXPathCompile\t\t(xsltStylesheetPtr style,\n\t\t\t\t\t\t const xmlChar *str);\nXSLTPUBFUN xmlXPathCompExprPtr XSLTCALL\n\t\txsltXPathCompileFlags\t\t(xsltStylesheetPtr style,\n\t\t\t\t\t\t const xmlChar *str,\n\t\t\t\t\t\t int flags);\n\n/*\n * Profiling.\n */\nXSLTPUBFUN void XSLTCALL\n\t\txsltSaveProfiling\t\t(xsltTransformContextPtr ctxt,\n\t\t\t\t\t\t FILE *output);\nXSLTPUBFUN xmlDocPtr XSLTCALL\n\t\txsltGetProfileInformation\t(xsltTransformContextPtr ctxt);\n\nXSLTPUBFUN long XSLTCALL\n\t\txsltTimestamp\t\t\t(void);\nXSLTPUBFUN void XSLTCALL\n\t\txsltCalibrateAdjust\t\t(long delta);\n\n/**\n * XSLT_TIMESTAMP_TICS_PER_SEC:\n *\n * Sampling precision for profiling\n */\n#define XSLT_TIMESTAMP_TICS_PER_SEC 100000l\n\n/*\n * Hooks for the debugger.\n */\n\ntypedef enum {\n    XSLT_DEBUG_NONE = 0, /* no debugging allowed */\n    XSLT_DEBUG_INIT,\n    XSLT_DEBUG_STEP,\n    XSLT_DEBUG_STEPOUT,\n    XSLT_DEBUG_NEXT,\n    XSLT_DEBUG_STOP,\n    XSLT_DEBUG_CONT,\n    XSLT_DEBUG_RUN,\n    XSLT_DEBUG_RUN_RESTART,\n    XSLT_DEBUG_QUIT\n} xsltDebugStatusCodes;\n\nXSLTPUBVAR int xslDebugStatus;\n\ntypedef void (*xsltHandleDebuggerCallback) (xmlNodePtr cur, xmlNodePtr node,\n\t\t\txsltTemplatePtr templ, xsltTransformContextPtr ctxt);\ntypedef int (*xsltAddCallCallback) (xsltTemplatePtr templ, xmlNodePtr source);\ntypedef void (*xsltDropCallCallback) (void);\n\nXSLTPUBFUN void XSLTCALL\n\t\txsltSetDebuggerStatus\t\t(int value);\nXSLTPUBFUN int XSLTCALL\n\t\txsltGetDebuggerStatus\t\t(void);\nXSLTPUBFUN int XSLTCALL\n\t\txsltSetDebuggerCallbacks\t(int no, void *block);\nXSLTPUBFUN int XSLTCALL\n\t\txslAddCall\t\t\t(xsltTemplatePtr templ,\n\t\t\t\t\t\t xmlNodePtr source);\nXSLTPUBFUN void XSLTCALL\n\t\txslDropCall\t\t\t(void);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* __XML_XSLTUTILS_H__ */\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/lxml-version.h",
    "content": "#ifndef LXML_VERSION_STRING\n#define LXML_VERSION_STRING \"4.4.1\"\n#endif\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/relaxng.pxd",
    "content": "from lxml.includes.tree cimport xmlDoc\nfrom lxml.includes.xmlerror cimport xmlStructuredErrorFunc\n\ncdef extern from \"libxml/relaxng.h\":\n    ctypedef struct xmlRelaxNG\n    ctypedef struct xmlRelaxNGParserCtxt\n    \n    ctypedef struct xmlRelaxNGValidCtxt\n    \n    ctypedef enum xmlRelaxNGValidErr:\n        XML_RELAXNG_OK = 0\n        XML_RELAXNG_ERR_MEMORY = 1\n        XML_RELAXNG_ERR_TYPE = 2\n        XML_RELAXNG_ERR_TYPEVAL = 3\n        XML_RELAXNG_ERR_DUPID = 4\n        XML_RELAXNG_ERR_TYPECMP = 5\n        XML_RELAXNG_ERR_NOSTATE = 6\n        XML_RELAXNG_ERR_NODEFINE = 7\n        XML_RELAXNG_ERR_LISTEXTRA = 8\n        XML_RELAXNG_ERR_LISTEMPTY = 9\n        XML_RELAXNG_ERR_INTERNODATA = 10\n        XML_RELAXNG_ERR_INTERSEQ = 11\n        XML_RELAXNG_ERR_INTEREXTRA = 12\n        XML_RELAXNG_ERR_ELEMNAME = 13\n        XML_RELAXNG_ERR_ATTRNAME = 14\n        XML_RELAXNG_ERR_ELEMNONS = 15\n        XML_RELAXNG_ERR_ATTRNONS = 16\n        XML_RELAXNG_ERR_ELEMWRONGNS = 17\n        XML_RELAXNG_ERR_ATTRWRONGNS = 18\n        XML_RELAXNG_ERR_ELEMEXTRANS = 19\n        XML_RELAXNG_ERR_ATTREXTRANS = 20\n        XML_RELAXNG_ERR_ELEMNOTEMPTY = 21\n        XML_RELAXNG_ERR_NOELEM = 22\n        XML_RELAXNG_ERR_NOTELEM = 23\n        XML_RELAXNG_ERR_ATTRVALID = 24\n        XML_RELAXNG_ERR_CONTENTVALID = 25\n        XML_RELAXNG_ERR_EXTRACONTENT = 26\n        XML_RELAXNG_ERR_INVALIDATTR = 27\n        XML_RELAXNG_ERR_DATAELEM = 28\n        XML_RELAXNG_ERR_VALELEM = 29\n        XML_RELAXNG_ERR_LISTELEM = 30\n        XML_RELAXNG_ERR_DATATYPE = 31\n        XML_RELAXNG_ERR_VALUE = 32\n        XML_RELAXNG_ERR_LIST = 33\n        XML_RELAXNG_ERR_NOGRAMMAR = 34\n        XML_RELAXNG_ERR_EXTRADATA = 35\n        XML_RELAXNG_ERR_LACKDATA = 36\n        XML_RELAXNG_ERR_INTERNAL = 37\n        XML_RELAXNG_ERR_ELEMWRONG = 38\n        XML_RELAXNG_ERR_TEXTWRONG = 39\n        \n    cdef xmlRelaxNGValidCtxt* xmlRelaxNGNewValidCtxt(xmlRelaxNG* schema) nogil\n    cdef int xmlRelaxNGValidateDoc(xmlRelaxNGValidCtxt* ctxt, xmlDoc* doc) nogil\n    cdef xmlRelaxNG* xmlRelaxNGParse(xmlRelaxNGParserCtxt* ctxt) nogil\n    cdef xmlRelaxNGParserCtxt* xmlRelaxNGNewParserCtxt(char* URL) nogil\n    cdef xmlRelaxNGParserCtxt* xmlRelaxNGNewDocParserCtxt(xmlDoc* doc) nogil\n    cdef void xmlRelaxNGFree(xmlRelaxNG* schema) nogil\n    cdef void xmlRelaxNGFreeParserCtxt(xmlRelaxNGParserCtxt* ctxt) nogil\n    cdef void xmlRelaxNGFreeValidCtxt(xmlRelaxNGValidCtxt* ctxt) nogil\n\n    cdef void xmlRelaxNGSetValidStructuredErrors(\n        xmlRelaxNGValidCtxt* ctxt, xmlStructuredErrorFunc serror, void *ctx) nogil\n    cdef void xmlRelaxNGSetParserStructuredErrors(\n        xmlRelaxNGParserCtxt* ctxt, xmlStructuredErrorFunc serror, void *ctx) nogil\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/schematron.pxd",
    "content": "from lxml.includes cimport xmlerror\nfrom lxml.includes.tree cimport xmlDoc\n\ncdef extern from \"libxml/schematron.h\":\n    ctypedef struct xmlSchematron\n    ctypedef struct xmlSchematronParserCtxt\n    ctypedef struct xmlSchematronValidCtxt\n\n    ctypedef enum xmlSchematronValidOptions:\n        XML_SCHEMATRON_OUT_QUIET     =    1 # quiet no report\n        XML_SCHEMATRON_OUT_TEXT      =    2 # build a textual report\n        XML_SCHEMATRON_OUT_XML       =    4 # output SVRL\n        XML_SCHEMATRON_OUT_ERROR     =    8 # output via xmlStructuredErrorFunc\n        XML_SCHEMATRON_OUT_FILE      =  256 # output to a file descriptor\n        XML_SCHEMATRON_OUT_BUFFER    =  512 # output to a buffer\n        XML_SCHEMATRON_OUT_IO        = 1024 # output to I/O mechanism\n\n    cdef xmlSchematronParserCtxt* xmlSchematronNewDocParserCtxt(\n        xmlDoc* doc) nogil\n    cdef xmlSchematronParserCtxt* xmlSchematronNewParserCtxt(\n        char* filename) nogil\n    cdef xmlSchematronValidCtxt* xmlSchematronNewValidCtxt(\n        xmlSchematron* schema, int options) nogil\n\n    cdef xmlSchematron* xmlSchematronParse(xmlSchematronParserCtxt* ctxt) nogil\n    cdef int xmlSchematronValidateDoc(xmlSchematronValidCtxt* ctxt,\n                                      xmlDoc* instance) nogil\n\n    cdef void xmlSchematronFreeParserCtxt(xmlSchematronParserCtxt* ctxt) nogil\n    cdef void xmlSchematronFreeValidCtxt(xmlSchematronValidCtxt* ctxt) nogil\n    cdef void xmlSchematronFree(xmlSchematron* schema) nogil\n    cdef void xmlSchematronSetValidStructuredErrors(\n        xmlSchematronValidCtxt* ctxt,\n        xmlerror.xmlStructuredErrorFunc error_func, void *data)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/tree.pxd",
    "content": "from libc cimport stdio\nfrom libc.string cimport const_char, const_uchar\n\ncdef extern from \"lxml-version.h\":\n    # deprecated declaration, use etreepublic.pxd instead\n    cdef char* LXML_VERSION_STRING\n\ncdef extern from \"libxml/xmlversion.h\":\n    cdef const_char* xmlParserVersion\n    cdef int LIBXML_VERSION\n\ncdef extern from \"libxml/xmlstring.h\":\n    ctypedef unsigned char xmlChar\n    ctypedef const xmlChar const_xmlChar \"const xmlChar\"\n    cdef int xmlStrlen(const_xmlChar* str) nogil\n    cdef xmlChar* xmlStrdup(const_xmlChar* cur) nogil\n    cdef int xmlStrncmp(const_xmlChar* str1, const_xmlChar* str2, int length) nogil\n    cdef int xmlStrcmp(const_xmlChar* str1, const_xmlChar* str2) nogil\n    cdef int xmlStrcasecmp(const xmlChar *str1, const xmlChar *str2) nogil\n    cdef const_xmlChar* xmlStrstr(const_xmlChar* str1, const_xmlChar* str2) nogil\n    cdef const_xmlChar* xmlStrchr(const_xmlChar* str1, xmlChar ch) nogil\n    cdef const_xmlChar* _xcstr \"(const xmlChar*)PyBytes_AS_STRING\" (object s)\n\ncdef extern from \"libxml/encoding.h\":\n    ctypedef enum xmlCharEncoding:\n        XML_CHAR_ENCODING_ERROR = -1 # No char encoding detected\n        XML_CHAR_ENCODING_NONE = 0 # No char encoding detected\n        XML_CHAR_ENCODING_UTF8 = 1 # UTF-8\n        XML_CHAR_ENCODING_UTF16LE = 2 # UTF-16 little endian\n        XML_CHAR_ENCODING_UTF16BE = 3 # UTF-16 big endian\n        XML_CHAR_ENCODING_UCS4LE = 4 # UCS-4 little endian\n        XML_CHAR_ENCODING_UCS4BE = 5 # UCS-4 big endian\n        XML_CHAR_ENCODING_EBCDIC = 6 # EBCDIC uh!\n        XML_CHAR_ENCODING_UCS4_2143 = 7 # UCS-4 unusual ordering\n        XML_CHAR_ENCODING_UCS4_3412 = 8 # UCS-4 unusual ordering\n        XML_CHAR_ENCODING_UCS2 = 9 # UCS-2\n        XML_CHAR_ENCODING_8859_1 = 10 # ISO-8859-1 ISO Latin 1\n        XML_CHAR_ENCODING_8859_2 = 11 # ISO-8859-2 ISO Latin 2\n        XML_CHAR_ENCODING_8859_3 = 12 # ISO-8859-3\n        XML_CHAR_ENCODING_8859_4 = 13 # ISO-8859-4\n        XML_CHAR_ENCODING_8859_5 = 14 # ISO-8859-5\n        XML_CHAR_ENCODING_8859_6 = 15 # ISO-8859-6\n        XML_CHAR_ENCODING_8859_7 = 16 # ISO-8859-7\n        XML_CHAR_ENCODING_8859_8 = 17 # ISO-8859-8\n        XML_CHAR_ENCODING_8859_9 = 18 # ISO-8859-9\n        XML_CHAR_ENCODING_2022_JP = 19 # ISO-2022-JP\n        XML_CHAR_ENCODING_SHIFT_JIS = 20 # Shift_JIS\n        XML_CHAR_ENCODING_EUC_JP = 21 # EUC-JP\n        XML_CHAR_ENCODING_ASCII = 22 # pure ASCII\n\n    ctypedef struct xmlCharEncodingHandler\n    cdef xmlCharEncodingHandler* xmlFindCharEncodingHandler(char* name) nogil\n    cdef xmlCharEncodingHandler* xmlGetCharEncodingHandler(\n        xmlCharEncoding enc) nogil\n    cdef int xmlCharEncCloseFunc(xmlCharEncodingHandler* handler) nogil\n    cdef xmlCharEncoding xmlDetectCharEncoding(const_xmlChar* text, int len) nogil\n    cdef const_char* xmlGetCharEncodingName(xmlCharEncoding enc) nogil\n    cdef xmlCharEncoding xmlParseCharEncoding(char* name) nogil\n    ctypedef int (*xmlCharEncodingOutputFunc)(\n            unsigned char *out_buf, int *outlen, const_uchar *in_buf, int *inlen)\n\ncdef extern from \"libxml/chvalid.h\":\n    cdef int xmlIsChar_ch(char c) nogil\n    cdef int xmlIsCharQ(int ch) nogil\n\ncdef extern from \"libxml/hash.h\":\n    ctypedef struct xmlHashTable\n    ctypedef void (*xmlHashScanner)(void* payload, void* data, const_xmlChar* name) # may require GIL!\n    void xmlHashScan(xmlHashTable* table, xmlHashScanner f, void* data) nogil\n    void* xmlHashLookup(xmlHashTable* table, const_xmlChar* name) nogil\n    ctypedef void (*xmlHashDeallocator)(void *payload, xmlChar *name)\n    cdef xmlHashTable* xmlHashCreate(int size)\n    cdef xmlHashTable* xmlHashCreateDict(int size, xmlDict *dict)\n    cdef int xmlHashSize(xmlHashTable* table)\n    cdef void xmlHashFree(xmlHashTable* table, xmlHashDeallocator f)\n\ncdef extern from *: # actually \"libxml/dict.h\"\n    # libxml/dict.h appears to be broken to include in C\n    ctypedef struct xmlDict\n    cdef const_xmlChar* xmlDictLookup(xmlDict* dict, const_xmlChar* name, int len) nogil\n    cdef const_xmlChar* xmlDictExists(xmlDict* dict, const_xmlChar* name, int len) nogil\n    cdef int xmlDictOwns(xmlDict* dict, const_xmlChar* name) nogil\n    cdef size_t xmlDictSize(xmlDict* dict) nogil\n\ncdef extern from \"libxml/tree.h\":\n    ctypedef struct xmlDoc\n    ctypedef struct xmlAttr\n    ctypedef struct xmlNotationTable\n\n    ctypedef enum xmlElementType:\n        XML_ELEMENT_NODE=           1\n        XML_ATTRIBUTE_NODE=         2\n        XML_TEXT_NODE=              3\n        XML_CDATA_SECTION_NODE=     4\n        XML_ENTITY_REF_NODE=        5\n        XML_ENTITY_NODE=            6\n        XML_PI_NODE=                7\n        XML_COMMENT_NODE=           8\n        XML_DOCUMENT_NODE=          9\n        XML_DOCUMENT_TYPE_NODE=     10\n        XML_DOCUMENT_FRAG_NODE=     11\n        XML_NOTATION_NODE=          12\n        XML_HTML_DOCUMENT_NODE=     13\n        XML_DTD_NODE=               14\n        XML_ELEMENT_DECL=           15\n        XML_ATTRIBUTE_DECL=         16\n        XML_ENTITY_DECL=            17\n        XML_NAMESPACE_DECL=         18\n        XML_XINCLUDE_START=         19\n        XML_XINCLUDE_END=           20\n\n    ctypedef enum xmlElementTypeVal:\n        XML_ELEMENT_TYPE_UNDEFINED= 0\n        XML_ELEMENT_TYPE_EMPTY=     1\n        XML_ELEMENT_TYPE_ANY=       2\n        XML_ELEMENT_TYPE_MIXED=     3\n        XML_ELEMENT_TYPE_ELEMENT=   4\n\n    ctypedef enum xmlElementContentType:\n        XML_ELEMENT_CONTENT_PCDATA=  1\n        XML_ELEMENT_CONTENT_ELEMENT= 2\n        XML_ELEMENT_CONTENT_SEQ=     3\n        XML_ELEMENT_CONTENT_OR=      4\n\n    ctypedef enum xmlElementContentOccur:\n        XML_ELEMENT_CONTENT_ONCE= 1\n        XML_ELEMENT_CONTENT_OPT=  2\n        XML_ELEMENT_CONTENT_MULT= 3\n        XML_ELEMENT_CONTENT_PLUS= 4\n\n    ctypedef enum xmlAttributeType:\n        XML_ATTRIBUTE_CDATA =      1\n        XML_ATTRIBUTE_ID=          2\n        XML_ATTRIBUTE_IDREF=       3\n        XML_ATTRIBUTE_IDREFS=      4\n        XML_ATTRIBUTE_ENTITY=      5\n        XML_ATTRIBUTE_ENTITIES=    6\n        XML_ATTRIBUTE_NMTOKEN=     7\n        XML_ATTRIBUTE_NMTOKENS=    8\n        XML_ATTRIBUTE_ENUMERATION= 9\n        XML_ATTRIBUTE_NOTATION=    10\n    \n    ctypedef enum xmlAttributeDefault:\n        XML_ATTRIBUTE_NONE=     1\n        XML_ATTRIBUTE_REQUIRED= 2\n        XML_ATTRIBUTE_IMPLIED=  3\n        XML_ATTRIBUTE_FIXED=    4\n\n    ctypedef enum xmlEntityType:\n        XML_INTERNAL_GENERAL_ENTITY=          1\n        XML_EXTERNAL_GENERAL_PARSED_ENTITY=   2\n        XML_EXTERNAL_GENERAL_UNPARSED_ENTITY= 3\n        XML_INTERNAL_PARAMETER_ENTITY=        4\n        XML_EXTERNAL_PARAMETER_ENTITY=        5\n        XML_INTERNAL_PREDEFINED_ENTITY=       6\n\n    ctypedef struct xmlNs:\n        const_xmlChar* href\n        const_xmlChar* prefix\n        xmlNs* next\n\n    ctypedef struct xmlNode:\n        void* _private\n        xmlElementType   type\n        const_xmlChar* name\n        xmlNode* children\n        xmlNode* last\n        xmlNode* parent\n        xmlNode* next\n        xmlNode* prev\n        xmlDoc* doc\n        xmlChar* content\n        xmlAttr* properties\n        xmlNs* ns\n        xmlNs* nsDef\n        unsigned short line\n\n    ctypedef struct xmlElementContent:\n        xmlElementContentType type\n        xmlElementContentOccur ocur\n        const_xmlChar *name\n        xmlElementContent *c1\n        xmlElementContent *c2\n        xmlElementContent *parent\n        const_xmlChar *prefix\n\n    ctypedef struct xmlEnumeration:\n        xmlEnumeration *next\n        const_xmlChar *name\n\n    ctypedef struct xmlAttribute:\n        void* _private\n        xmlElementType type\n        const_xmlChar* name\n        xmlNode* children\n        xmlNode* last\n        xmlDtd* parent\n        xmlNode* next\n        xmlNode* prev\n        xmlDoc* doc\n        xmlAttribute* nexth\n        xmlAttributeType atype\n        xmlAttributeDefault def_ \"def\"\n        const_xmlChar* defaultValue\n        xmlEnumeration* tree\n        const_xmlChar* prefix\n        const_xmlChar* elem\n\n    ctypedef struct xmlElement:\n        void* _private\n        xmlElementType   type\n        const_xmlChar* name\n        xmlNode* children\n        xmlNode* last\n        xmlNode* parent\n        xmlNode* next\n        xmlNode* prev\n        xmlDoc* doc\n        xmlElementTypeVal etype\n        xmlElementContent* content\n        xmlAttribute* attributes\n        const_xmlChar* prefix\n        void *contModel\n\n    ctypedef struct xmlEntity:\n        void* _private\n        xmlElementType type\n        const_xmlChar* name\n        xmlNode* children\n        xmlNode* last\n        xmlDtd* parent\n        xmlNode* next\n        xmlNode* prev\n        xmlDoc* doc\n        xmlChar* orig\n        xmlChar* content\n        int length\n        xmlEntityType etype\n        const_xmlChar* ExternalID\n        const_xmlChar* SystemID\n        xmlEntity* nexte\n        const_xmlChar* URI\n        int owner\n        int checked\n\n    ctypedef struct xmlDtd:\n        const_xmlChar* name\n        const_xmlChar* ExternalID\n        const_xmlChar* SystemID\n        void* notations\n        void* entities\n        void* pentities\n        void* attributes\n        void* elements\n        xmlNode* children\n        xmlNode* last\n        xmlDoc* doc\n\n    ctypedef struct xmlDoc:\n        xmlElementType type\n        char* name\n        xmlNode* children\n        xmlNode* last\n        xmlNode* parent\n        xmlNode* next\n        xmlNode* prev\n        xmlDoc* doc\n        xmlDict* dict\n        xmlHashTable* ids\n        int standalone\n        const_xmlChar* version\n        const_xmlChar* encoding\n        const_xmlChar* URL\n        void* _private\n        xmlDtd* intSubset\n        xmlDtd* extSubset\n        \n    ctypedef struct xmlAttr:\n        void* _private\n        xmlElementType type\n        const_xmlChar* name\n        xmlNode* children\n        xmlNode* last\n        xmlNode* parent\n        xmlAttr* next\n        xmlAttr* prev\n        xmlDoc* doc\n        xmlNs* ns\n        xmlAttributeType atype\n\n    ctypedef struct xmlID:\n        const_xmlChar* value\n        const_xmlChar* name\n        xmlAttr* attr\n        xmlDoc* doc\n        \n    ctypedef struct xmlBuffer\n\n    ctypedef struct xmlBuf   # new in libxml2 2.9\n\n    ctypedef struct xmlOutputBuffer:\n        xmlBuf* buffer\n        xmlBuf* conv\n        int error\n\n    const_xmlChar* XML_XML_NAMESPACE\n        \n    cdef void xmlFreeDoc(xmlDoc* cur) nogil\n    cdef void xmlFreeDtd(xmlDtd* cur) nogil\n    cdef void xmlFreeNode(xmlNode* cur) nogil\n    cdef void xmlFreeNsList(xmlNs* ns) nogil\n    cdef void xmlFreeNs(xmlNs* ns) nogil\n    cdef void xmlFree(void* buf) nogil\n    \n    cdef xmlNode* xmlNewNode(xmlNs* ns, const_xmlChar* name) nogil\n    cdef xmlNode* xmlNewDocText(xmlDoc* doc, const_xmlChar* content) nogil\n    cdef xmlNode* xmlNewDocComment(xmlDoc* doc, const_xmlChar* content) nogil\n    cdef xmlNode* xmlNewDocPI(xmlDoc* doc, const_xmlChar* name, const_xmlChar* content) nogil\n    cdef xmlNode* xmlNewReference(xmlDoc* doc, const_xmlChar* name) nogil\n    cdef xmlNode* xmlNewCDataBlock(xmlDoc* doc, const_xmlChar* text, int len) nogil\n    cdef xmlNs* xmlNewNs(xmlNode* node, const_xmlChar* href, const_xmlChar* prefix) nogil\n    cdef xmlNode* xmlAddChild(xmlNode* parent, xmlNode* cur) nogil\n    cdef xmlNode* xmlReplaceNode(xmlNode* old, xmlNode* cur) nogil\n    cdef xmlNode* xmlAddPrevSibling(xmlNode* cur, xmlNode* elem) nogil\n    cdef xmlNode* xmlAddNextSibling(xmlNode* cur, xmlNode* elem) nogil\n    cdef xmlNode* xmlNewDocNode(xmlDoc* doc, xmlNs* ns,\n                                const_xmlChar* name, const_xmlChar* content) nogil\n    cdef xmlDoc* xmlNewDoc(const_xmlChar* version) nogil\n    cdef xmlAttr* xmlNewProp(xmlNode* node, const_xmlChar* name, const_xmlChar* value) nogil\n    cdef xmlAttr* xmlNewNsProp(xmlNode* node, xmlNs* ns,\n                               const_xmlChar* name, const_xmlChar* value) nogil\n    cdef xmlChar* xmlGetNoNsProp(xmlNode* node, const_xmlChar* name) nogil\n    cdef xmlChar* xmlGetNsProp(xmlNode* node, const_xmlChar* name, const_xmlChar* nameSpace) nogil\n    cdef void xmlSetNs(xmlNode* node, xmlNs* ns) nogil\n    cdef xmlAttr* xmlSetProp(xmlNode* node, const_xmlChar* name, const_xmlChar* value) nogil\n    cdef xmlAttr* xmlSetNsProp(xmlNode* node, xmlNs* ns,\n                               const_xmlChar* name, const_xmlChar* value) nogil\n    cdef int xmlRemoveID(xmlDoc* doc, xmlAttr* cur) nogil\n    cdef int xmlRemoveProp(xmlAttr* cur) nogil\n    cdef void xmlFreePropList(xmlAttr* cur) nogil\n    cdef xmlChar* xmlGetNodePath(xmlNode* node) nogil\n    cdef void xmlDocDumpMemory(xmlDoc* cur, char** mem, int* size) nogil\n    cdef void xmlDocDumpMemoryEnc(xmlDoc* cur, char** mem, int* size,\n                                  char* encoding) nogil\n    cdef int xmlSaveFileTo(xmlOutputBuffer* out, xmlDoc* cur,\n                           char* encoding) nogil\n\n    cdef void xmlUnlinkNode(xmlNode* cur) nogil\n    cdef xmlNode* xmlDocSetRootElement(xmlDoc* doc, xmlNode* root) nogil\n    cdef xmlNode* xmlDocGetRootElement(xmlDoc* doc) nogil\n    cdef void xmlSetTreeDoc(xmlNode* tree, xmlDoc* doc) nogil\n    cdef xmlAttr* xmlHasProp(xmlNode* node, const_xmlChar* name) nogil\n    cdef xmlAttr* xmlHasNsProp(xmlNode* node, const_xmlChar* name, const_xmlChar* nameSpace) nogil\n    cdef xmlChar* xmlNodeGetContent(xmlNode* cur) nogil\n    cdef int xmlNodeBufGetContent(xmlBuffer* buffer, xmlNode* cur) nogil\n    cdef xmlNs* xmlSearchNs(xmlDoc* doc, xmlNode* node, const_xmlChar* prefix) nogil\n    cdef xmlNs* xmlSearchNsByHref(xmlDoc* doc, xmlNode* node, const_xmlChar* href) nogil\n    cdef int xmlIsBlankNode(xmlNode* node) nogil\n    cdef long xmlGetLineNo(xmlNode* node) nogil\n    cdef void xmlElemDump(stdio.FILE* f, xmlDoc* doc, xmlNode* cur) nogil\n    cdef void xmlNodeDumpOutput(xmlOutputBuffer* buf,\n                                xmlDoc* doc, xmlNode* cur, int level,\n                                int format, const_char* encoding) nogil\n    cdef void xmlBufAttrSerializeTxtContent(xmlOutputBuffer *buf, xmlDoc *doc,\n                                xmlAttr *attr, const_xmlChar *string) nogil\n    cdef void xmlNodeSetName(xmlNode* cur, const_xmlChar* name) nogil\n    cdef void xmlNodeSetContent(xmlNode* cur, const_xmlChar* content) nogil\n    cdef xmlDtd* xmlCopyDtd(xmlDtd* dtd) nogil\n    cdef xmlDoc* xmlCopyDoc(xmlDoc* doc, int recursive) nogil\n    cdef xmlNode* xmlCopyNode(xmlNode* node, int extended) nogil\n    cdef xmlNode* xmlDocCopyNode(xmlNode* node, xmlDoc* doc, int extended) nogil\n    cdef int xmlReconciliateNs(xmlDoc* doc, xmlNode* tree) nogil\n    cdef xmlNs* xmlNewReconciliedNs(xmlDoc* doc, xmlNode* tree, xmlNs* ns) nogil\n    cdef xmlBuffer* xmlBufferCreate() nogil\n    cdef void xmlBufferWriteChar(xmlBuffer* buf, char* string) nogil\n    cdef void xmlBufferFree(xmlBuffer* buf) nogil\n    cdef const_xmlChar* xmlBufferContent(xmlBuffer* buf) nogil\n    cdef int xmlBufferLength(xmlBuffer* buf) nogil\n    cdef const_xmlChar* xmlBufContent(xmlBuf* buf) nogil # new in libxml2 2.9\n    cdef size_t xmlBufUse(xmlBuf* buf) nogil # new in libxml2 2.9\n    cdef int xmlKeepBlanksDefault(int val) nogil\n    cdef xmlChar* xmlNodeGetBase(xmlDoc* doc, xmlNode* node) nogil\n    cdef xmlDtd* xmlCreateIntSubset(xmlDoc* doc, const_xmlChar* name,\n                                    const_xmlChar* ExternalID, const_xmlChar* SystemID) nogil\n    cdef void xmlNodeSetBase(xmlNode* node, const_xmlChar* uri) nogil\n    cdef int xmlValidateNCName(const_xmlChar* value, int space) nogil\n\ncdef extern from \"libxml/uri.h\":\n    cdef const_xmlChar* xmlBuildURI(const_xmlChar* href, const_xmlChar* base) nogil\n\ncdef extern from \"libxml/HTMLtree.h\":\n    cdef void htmlNodeDumpFormatOutput(xmlOutputBuffer* buf,\n                                       xmlDoc* doc, xmlNode* cur,\n                                       char* encoding, int format) nogil\n    cdef xmlDoc* htmlNewDoc(const_xmlChar* uri, const_xmlChar* externalID) nogil\n\ncdef extern from \"libxml/valid.h\":\n    cdef xmlAttr* xmlGetID(xmlDoc* doc, const_xmlChar* ID) nogil\n    cdef void xmlDumpNotationTable(xmlBuffer* buffer,\n                                   xmlNotationTable* table) nogil\n    cdef int xmlValidateNameValue(const_xmlChar* value) nogil\n\ncdef extern from \"libxml/xmlIO.h\":\n    cdef int xmlOutputBufferWrite(xmlOutputBuffer* out,\n                                  int len, const_char* str) nogil\n    cdef int xmlOutputBufferWriteString(xmlOutputBuffer* out, const_char* str) nogil\n    cdef int xmlOutputBufferWriteEscape(xmlOutputBuffer* out,\n                                        const_xmlChar* str,\n                                        xmlCharEncodingOutputFunc escapefunc) nogil\n    cdef int xmlOutputBufferFlush(xmlOutputBuffer* out) nogil\n    cdef int xmlOutputBufferClose(xmlOutputBuffer* out) nogil\n\n    ctypedef int (*xmlInputReadCallback)(void* context,\n                                         char* buffer, int len)\n    ctypedef int (*xmlInputCloseCallback)(void* context)\n\n    ctypedef int (*xmlOutputWriteCallback)(void* context,\n                                           char* buffer, int len)\n    ctypedef int (*xmlOutputCloseCallback)(void* context)\n\n    cdef xmlOutputBuffer* xmlAllocOutputBuffer(\n        xmlCharEncodingHandler* encoder) nogil\n    cdef xmlOutputBuffer* xmlOutputBufferCreateIO(\n        xmlOutputWriteCallback iowrite,\n        xmlOutputCloseCallback ioclose,\n        void * ioctx, \n        xmlCharEncodingHandler* encoder) nogil\n    cdef xmlOutputBuffer* xmlOutputBufferCreateFile(\n        stdio.FILE* file, xmlCharEncodingHandler* encoder) nogil\n    cdef xmlOutputBuffer* xmlOutputBufferCreateFilename(\n        char* URI, xmlCharEncodingHandler* encoder, int compression) nogil\n\ncdef extern from \"libxml/xmlsave.h\":\n    ctypedef struct xmlSaveCtxt\n\n    ctypedef enum xmlSaveOption:\n        XML_SAVE_FORMAT   = 1   # format save output            (2.6.17)\n        XML_SAVE_NO_DECL  = 2   # drop the xml declaration      (2.6.21)\n        XML_SAVE_NO_EMPTY = 4   # no empty tags                 (2.6.22)\n        XML_SAVE_NO_XHTML = 8   # disable XHTML1 specific rules (2.6.22)\n        XML_SAVE_XHTML = 16     # force XHTML1 specific rules         (2.7.2)\n        XML_SAVE_AS_XML = 32    # force XML serialization on HTML doc (2.7.2)\n        XML_SAVE_AS_HTML = 64   # force HTML serialization on XML doc (2.7.2)\n\n    cdef xmlSaveCtxt* xmlSaveToFilename(char* filename, char* encoding,\n                                        int options) nogil\n    cdef xmlSaveCtxt* xmlSaveToBuffer(xmlBuffer* buffer, char* encoding,\n                                      int options) nogil # libxml2 2.6.23\n    cdef long xmlSaveDoc(xmlSaveCtxt* ctxt, xmlDoc* doc) nogil\n    cdef long xmlSaveTree(xmlSaveCtxt* ctxt, xmlNode* node) nogil\n    cdef int xmlSaveClose(xmlSaveCtxt* ctxt) nogil\n    cdef int xmlSaveFlush(xmlSaveCtxt* ctxt) nogil\n    cdef int xmlSaveSetAttrEscape(xmlSaveCtxt* ctxt, void* escape_func) nogil\n    cdef int xmlSaveSetEscape(xmlSaveCtxt* ctxt, void* escape_func) nogil\n\ncdef extern from \"libxml/globals.h\":\n    cdef int xmlThrDefKeepBlanksDefaultValue(int onoff) nogil\n    cdef int xmlThrDefLineNumbersDefaultValue(int onoff) nogil\n    cdef int xmlThrDefIndentTreeOutput(int onoff) nogil\n    \ncdef extern from \"libxml/xmlmemory.h\" nogil:\n    cdef void* xmlMalloc(size_t size)\n    cdef int xmlMemBlocks()\n    cdef int xmlMemUsed()\n    cdef void xmlMemDisplay(stdio.FILE* file)\n    cdef void xmlMemDisplayLast(stdio.FILE* file, long num_bytes)\n    cdef void xmlMemShow(stdio.FILE* file, int count)\n\ncdef extern from \"etree_defs.h\":\n    cdef bint _isElement(xmlNode* node) nogil\n    cdef bint _isElementOrXInclude(xmlNode* node) nogil\n    cdef const_xmlChar* _getNs(xmlNode* node) nogil\n    cdef void BEGIN_FOR_EACH_ELEMENT_FROM(xmlNode* tree_top,\n                                          xmlNode* start_node,\n                                          bint inclusive) nogil\n    cdef void END_FOR_EACH_ELEMENT_FROM(xmlNode* start_node) nogil\n    cdef void BEGIN_FOR_EACH_FROM(xmlNode* tree_top,\n                                  xmlNode* start_node,\n                                  bint inclusive) nogil\n    cdef void END_FOR_EACH_FROM(xmlNode* start_node) nogil\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/uri.pxd",
    "content": "cdef extern from \"libxml/uri.h\":\n    ctypedef struct xmlURI\n\n    cdef xmlURI* xmlParseURI(char* str)\n    cdef void xmlFreeURI(xmlURI* uri)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/xinclude.pxd",
    "content": "from lxml.includes.tree cimport xmlDoc, xmlNode\n\ncdef extern from \"libxml/xinclude.h\":\n\n    ctypedef struct xmlXIncludeCtxt\n\n    cdef int xmlXIncludeProcess(xmlDoc* doc) nogil\n    cdef int xmlXIncludeProcessFlags(xmlDoc* doc, int parser_opts) nogil\n    cdef int xmlXIncludeProcessTree(xmlNode* doc) nogil\n    cdef int xmlXIncludeProcessTreeFlags(xmlNode* doc, int parser_opts) nogil\n\n    # libxml2 >= 2.7.4\n    cdef int xmlXIncludeProcessTreeFlagsData(\n            xmlNode* doc, int parser_opts, void* data) nogil\n\n    cdef xmlXIncludeCtxt* xmlXIncludeNewContext(xmlDoc* doc) nogil\n    cdef int xmlXIncludeProcessNode(xmlXIncludeCtxt* ctxt, xmlNode* node) nogil\n    cdef int xmlXIncludeSetFlags(xmlXIncludeCtxt* ctxt, int flags) nogil\n\n    # libxml2 >= 2.6.27\n    cdef int xmlXIncludeProcessFlagsData(\n        xmlDoc* doc, int flags, void* data) nogil\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/xmlerror.pxd",
    "content": "\n# --- BEGIN: GENERATED CONSTANTS ---\n\n# This section is generated by the script 'update-error-constants.py'.\n\ncdef extern from \"libxml/xmlerror.h\":\n    ctypedef enum xmlErrorLevel:\n        XML_ERR_NONE                                       =       0\n        XML_ERR_WARNING                                    =       1 # A simple warning\n        XML_ERR_ERROR                                      =       2 # A recoverable error\n        XML_ERR_FATAL                                      =       3 # A fatal error\n\n    ctypedef enum xmlErrorDomain:\n        XML_FROM_NONE                                      =       0\n        XML_FROM_PARSER                                    =       1 # The XML parser\n        XML_FROM_TREE                                      =       2 # The tree module\n        XML_FROM_NAMESPACE                                 =       3 # The XML Namespace module\n        XML_FROM_DTD                                       =       4 # The XML DTD validation with parser contex\n        XML_FROM_HTML                                      =       5 # The HTML parser\n        XML_FROM_MEMORY                                    =       6 # The memory allocator\n        XML_FROM_OUTPUT                                    =       7 # The serialization code\n        XML_FROM_IO                                        =       8 # The Input/Output stack\n        XML_FROM_FTP                                       =       9 # The FTP module\n        XML_FROM_HTTP                                      =      10 # The HTTP module\n        XML_FROM_XINCLUDE                                  =      11 # The XInclude processing\n        XML_FROM_XPATH                                     =      12 # The XPath module\n        XML_FROM_XPOINTER                                  =      13 # The XPointer module\n        XML_FROM_REGEXP                                    =      14 # The regular expressions module\n        XML_FROM_DATATYPE                                  =      15 # The W3C XML Schemas Datatype module\n        XML_FROM_SCHEMASP                                  =      16 # The W3C XML Schemas parser module\n        XML_FROM_SCHEMASV                                  =      17 # The W3C XML Schemas validation module\n        XML_FROM_RELAXNGP                                  =      18 # The Relax-NG parser module\n        XML_FROM_RELAXNGV                                  =      19 # The Relax-NG validator module\n        XML_FROM_CATALOG                                   =      20 # The Catalog module\n        XML_FROM_C14N                                      =      21 # The Canonicalization module\n        XML_FROM_XSLT                                      =      22 # The XSLT engine from libxslt\n        XML_FROM_VALID                                     =      23 # The XML DTD validation with valid context\n        XML_FROM_CHECK                                     =      24 # The error checking module\n        XML_FROM_WRITER                                    =      25 # The xmlwriter module\n        XML_FROM_MODULE                                    =      26 # The dynamically loaded module modul\n        XML_FROM_I18N                                      =      27 # The module handling character conversion\n        XML_FROM_SCHEMATRONV                               =      28 # The Schematron validator module\n        XML_FROM_BUFFER                                    =      29 # The buffers module\n        XML_FROM_URI                                       =      30 # The URI module\n\n    ctypedef enum xmlParserErrors:\n        XML_ERR_OK                                         =       0\n        XML_ERR_INTERNAL_ERROR                             =       1\n        XML_ERR_NO_MEMORY                                  =       2\n        XML_ERR_DOCUMENT_START                             =       3\n        XML_ERR_DOCUMENT_EMPTY                             =       4\n        XML_ERR_DOCUMENT_END                               =       5\n        XML_ERR_INVALID_HEX_CHARREF                        =       6\n        XML_ERR_INVALID_DEC_CHARREF                        =       7\n        XML_ERR_INVALID_CHARREF                            =       8\n        XML_ERR_INVALID_CHAR                               =       9\n        XML_ERR_CHARREF_AT_EOF                             =      10\n        XML_ERR_CHARREF_IN_PROLOG                          =      11\n        XML_ERR_CHARREF_IN_EPILOG                          =      12\n        XML_ERR_CHARREF_IN_DTD                             =      13\n        XML_ERR_ENTITYREF_AT_EOF                           =      14\n        XML_ERR_ENTITYREF_IN_PROLOG                        =      15\n        XML_ERR_ENTITYREF_IN_EPILOG                        =      16\n        XML_ERR_ENTITYREF_IN_DTD                           =      17\n        XML_ERR_PEREF_AT_EOF                               =      18\n        XML_ERR_PEREF_IN_PROLOG                            =      19\n        XML_ERR_PEREF_IN_EPILOG                            =      20\n        XML_ERR_PEREF_IN_INT_SUBSET                        =      21\n        XML_ERR_ENTITYREF_NO_NAME                          =      22\n        XML_ERR_ENTITYREF_SEMICOL_MISSING                  =      23\n        XML_ERR_PEREF_NO_NAME                              =      24\n        XML_ERR_PEREF_SEMICOL_MISSING                      =      25\n        XML_ERR_UNDECLARED_ENTITY                          =      26\n        XML_WAR_UNDECLARED_ENTITY                          =      27\n        XML_ERR_UNPARSED_ENTITY                            =      28\n        XML_ERR_ENTITY_IS_EXTERNAL                         =      29\n        XML_ERR_ENTITY_IS_PARAMETER                        =      30\n        XML_ERR_UNKNOWN_ENCODING                           =      31\n        XML_ERR_UNSUPPORTED_ENCODING                       =      32\n        XML_ERR_STRING_NOT_STARTED                         =      33\n        XML_ERR_STRING_NOT_CLOSED                          =      34\n        XML_ERR_NS_DECL_ERROR                              =      35\n        XML_ERR_ENTITY_NOT_STARTED                         =      36\n        XML_ERR_ENTITY_NOT_FINISHED                        =      37\n        XML_ERR_LT_IN_ATTRIBUTE                            =      38\n        XML_ERR_ATTRIBUTE_NOT_STARTED                      =      39\n        XML_ERR_ATTRIBUTE_NOT_FINISHED                     =      40\n        XML_ERR_ATTRIBUTE_WITHOUT_VALUE                    =      41\n        XML_ERR_ATTRIBUTE_REDEFINED                        =      42\n        XML_ERR_LITERAL_NOT_STARTED                        =      43\n        XML_ERR_LITERAL_NOT_FINISHED                       =      44\n        XML_ERR_COMMENT_NOT_FINISHED                       =      45\n        XML_ERR_PI_NOT_STARTED                             =      46\n        XML_ERR_PI_NOT_FINISHED                            =      47\n        XML_ERR_NOTATION_NOT_STARTED                       =      48\n        XML_ERR_NOTATION_NOT_FINISHED                      =      49\n        XML_ERR_ATTLIST_NOT_STARTED                        =      50\n        XML_ERR_ATTLIST_NOT_FINISHED                       =      51\n        XML_ERR_MIXED_NOT_STARTED                          =      52\n        XML_ERR_MIXED_NOT_FINISHED                         =      53\n        XML_ERR_ELEMCONTENT_NOT_STARTED                    =      54\n        XML_ERR_ELEMCONTENT_NOT_FINISHED                   =      55\n        XML_ERR_XMLDECL_NOT_STARTED                        =      56\n        XML_ERR_XMLDECL_NOT_FINISHED                       =      57\n        XML_ERR_CONDSEC_NOT_STARTED                        =      58\n        XML_ERR_CONDSEC_NOT_FINISHED                       =      59\n        XML_ERR_EXT_SUBSET_NOT_FINISHED                    =      60\n        XML_ERR_DOCTYPE_NOT_FINISHED                       =      61\n        XML_ERR_MISPLACED_CDATA_END                        =      62\n        XML_ERR_CDATA_NOT_FINISHED                         =      63\n        XML_ERR_RESERVED_XML_NAME                          =      64\n        XML_ERR_SPACE_REQUIRED                             =      65\n        XML_ERR_SEPARATOR_REQUIRED                         =      66\n        XML_ERR_NMTOKEN_REQUIRED                           =      67\n        XML_ERR_NAME_REQUIRED                              =      68\n        XML_ERR_PCDATA_REQUIRED                            =      69\n        XML_ERR_URI_REQUIRED                               =      70\n        XML_ERR_PUBID_REQUIRED                             =      71\n        XML_ERR_LT_REQUIRED                                =      72\n        XML_ERR_GT_REQUIRED                                =      73\n        XML_ERR_LTSLASH_REQUIRED                           =      74\n        XML_ERR_EQUAL_REQUIRED                             =      75\n        XML_ERR_TAG_NAME_MISMATCH                          =      76\n        XML_ERR_TAG_NOT_FINISHED                           =      77\n        XML_ERR_STANDALONE_VALUE                           =      78\n        XML_ERR_ENCODING_NAME                              =      79\n        XML_ERR_HYPHEN_IN_COMMENT                          =      80\n        XML_ERR_INVALID_ENCODING                           =      81\n        XML_ERR_EXT_ENTITY_STANDALONE                      =      82\n        XML_ERR_CONDSEC_INVALID                            =      83\n        XML_ERR_VALUE_REQUIRED                             =      84\n        XML_ERR_NOT_WELL_BALANCED                          =      85\n        XML_ERR_EXTRA_CONTENT                              =      86\n        XML_ERR_ENTITY_CHAR_ERROR                          =      87\n        XML_ERR_ENTITY_PE_INTERNAL                         =      88\n        XML_ERR_ENTITY_LOOP                                =      89\n        XML_ERR_ENTITY_BOUNDARY                            =      90\n        XML_ERR_INVALID_URI                                =      91\n        XML_ERR_URI_FRAGMENT                               =      92\n        XML_WAR_CATALOG_PI                                 =      93\n        XML_ERR_NO_DTD                                     =      94\n        XML_ERR_CONDSEC_INVALID_KEYWORD                    =      95\n        XML_ERR_VERSION_MISSING                            =      96\n        XML_WAR_UNKNOWN_VERSION                            =      97\n        XML_WAR_LANG_VALUE                                 =      98\n        XML_WAR_NS_URI                                     =      99\n        XML_WAR_NS_URI_RELATIVE                            =     100\n        XML_ERR_MISSING_ENCODING                           =     101\n        XML_WAR_SPACE_VALUE                                =     102\n        XML_ERR_NOT_STANDALONE                             =     103\n        XML_ERR_ENTITY_PROCESSING                          =     104\n        XML_ERR_NOTATION_PROCESSING                        =     105\n        XML_WAR_NS_COLUMN                                  =     106\n        XML_WAR_ENTITY_REDEFINED                           =     107\n        XML_ERR_UNKNOWN_VERSION                            =     108\n        XML_ERR_VERSION_MISMATCH                           =     109\n        XML_ERR_NAME_TOO_LONG                              =     110\n        XML_ERR_USER_STOP                                  =     111\n        XML_NS_ERR_XML_NAMESPACE                           =     200\n        XML_NS_ERR_UNDEFINED_NAMESPACE                     =     201\n        XML_NS_ERR_QNAME                                   =     202\n        XML_NS_ERR_ATTRIBUTE_REDEFINED                     =     203\n        XML_NS_ERR_EMPTY                                   =     204\n        XML_NS_ERR_COLON                                   =     205\n        XML_DTD_ATTRIBUTE_DEFAULT                          =     500\n        XML_DTD_ATTRIBUTE_REDEFINED                        =     501\n        XML_DTD_ATTRIBUTE_VALUE                            =     502\n        XML_DTD_CONTENT_ERROR                              =     503\n        XML_DTD_CONTENT_MODEL                              =     504\n        XML_DTD_CONTENT_NOT_DETERMINIST                    =     505\n        XML_DTD_DIFFERENT_PREFIX                           =     506\n        XML_DTD_ELEM_DEFAULT_NAMESPACE                     =     507\n        XML_DTD_ELEM_NAMESPACE                             =     508\n        XML_DTD_ELEM_REDEFINED                             =     509\n        XML_DTD_EMPTY_NOTATION                             =     510\n        XML_DTD_ENTITY_TYPE                                =     511\n        XML_DTD_ID_FIXED                                   =     512\n        XML_DTD_ID_REDEFINED                               =     513\n        XML_DTD_ID_SUBSET                                  =     514\n        XML_DTD_INVALID_CHILD                              =     515\n        XML_DTD_INVALID_DEFAULT                            =     516\n        XML_DTD_LOAD_ERROR                                 =     517\n        XML_DTD_MISSING_ATTRIBUTE                          =     518\n        XML_DTD_MIXED_CORRUPT                              =     519\n        XML_DTD_MULTIPLE_ID                                =     520\n        XML_DTD_NO_DOC                                     =     521\n        XML_DTD_NO_DTD                                     =     522\n        XML_DTD_NO_ELEM_NAME                               =     523\n        XML_DTD_NO_PREFIX                                  =     524\n        XML_DTD_NO_ROOT                                    =     525\n        XML_DTD_NOTATION_REDEFINED                         =     526\n        XML_DTD_NOTATION_VALUE                             =     527\n        XML_DTD_NOT_EMPTY                                  =     528\n        XML_DTD_NOT_PCDATA                                 =     529\n        XML_DTD_NOT_STANDALONE                             =     530\n        XML_DTD_ROOT_NAME                                  =     531\n        XML_DTD_STANDALONE_WHITE_SPACE                     =     532\n        XML_DTD_UNKNOWN_ATTRIBUTE                          =     533\n        XML_DTD_UNKNOWN_ELEM                               =     534\n        XML_DTD_UNKNOWN_ENTITY                             =     535\n        XML_DTD_UNKNOWN_ID                                 =     536\n        XML_DTD_UNKNOWN_NOTATION                           =     537\n        XML_DTD_STANDALONE_DEFAULTED                       =     538\n        XML_DTD_XMLID_VALUE                                =     539\n        XML_DTD_XMLID_TYPE                                 =     540\n        XML_DTD_DUP_TOKEN                                  =     541\n        XML_HTML_STRUCURE_ERROR                            =     800\n        XML_HTML_UNKNOWN_TAG                               =     801\n        XML_RNGP_ANYNAME_ATTR_ANCESTOR                     =    1000\n        XML_RNGP_ATTR_CONFLICT                             =    1001\n        XML_RNGP_ATTRIBUTE_CHILDREN                        =    1002\n        XML_RNGP_ATTRIBUTE_CONTENT                         =    1003\n        XML_RNGP_ATTRIBUTE_EMPTY                           =    1004\n        XML_RNGP_ATTRIBUTE_NOOP                            =    1005\n        XML_RNGP_CHOICE_CONTENT                            =    1006\n        XML_RNGP_CHOICE_EMPTY                              =    1007\n        XML_RNGP_CREATE_FAILURE                            =    1008\n        XML_RNGP_DATA_CONTENT                              =    1009\n        XML_RNGP_DEF_CHOICE_AND_INTERLEAVE                 =    1010\n        XML_RNGP_DEFINE_CREATE_FAILED                      =    1011\n        XML_RNGP_DEFINE_EMPTY                              =    1012\n        XML_RNGP_DEFINE_MISSING                            =    1013\n        XML_RNGP_DEFINE_NAME_MISSING                       =    1014\n        XML_RNGP_ELEM_CONTENT_EMPTY                        =    1015\n        XML_RNGP_ELEM_CONTENT_ERROR                        =    1016\n        XML_RNGP_ELEMENT_EMPTY                             =    1017\n        XML_RNGP_ELEMENT_CONTENT                           =    1018\n        XML_RNGP_ELEMENT_NAME                              =    1019\n        XML_RNGP_ELEMENT_NO_CONTENT                        =    1020\n        XML_RNGP_ELEM_TEXT_CONFLICT                        =    1021\n        XML_RNGP_EMPTY                                     =    1022\n        XML_RNGP_EMPTY_CONSTRUCT                           =    1023\n        XML_RNGP_EMPTY_CONTENT                             =    1024\n        XML_RNGP_EMPTY_NOT_EMPTY                           =    1025\n        XML_RNGP_ERROR_TYPE_LIB                            =    1026\n        XML_RNGP_EXCEPT_EMPTY                              =    1027\n        XML_RNGP_EXCEPT_MISSING                            =    1028\n        XML_RNGP_EXCEPT_MULTIPLE                           =    1029\n        XML_RNGP_EXCEPT_NO_CONTENT                         =    1030\n        XML_RNGP_EXTERNALREF_EMTPY                         =    1031\n        XML_RNGP_EXTERNAL_REF_FAILURE                      =    1032\n        XML_RNGP_EXTERNALREF_RECURSE                       =    1033\n        XML_RNGP_FORBIDDEN_ATTRIBUTE                       =    1034\n        XML_RNGP_FOREIGN_ELEMENT                           =    1035\n        XML_RNGP_GRAMMAR_CONTENT                           =    1036\n        XML_RNGP_GRAMMAR_EMPTY                             =    1037\n        XML_RNGP_GRAMMAR_MISSING                           =    1038\n        XML_RNGP_GRAMMAR_NO_START                          =    1039\n        XML_RNGP_GROUP_ATTR_CONFLICT                       =    1040\n        XML_RNGP_HREF_ERROR                                =    1041\n        XML_RNGP_INCLUDE_EMPTY                             =    1042\n        XML_RNGP_INCLUDE_FAILURE                           =    1043\n        XML_RNGP_INCLUDE_RECURSE                           =    1044\n        XML_RNGP_INTERLEAVE_ADD                            =    1045\n        XML_RNGP_INTERLEAVE_CREATE_FAILED                  =    1046\n        XML_RNGP_INTERLEAVE_EMPTY                          =    1047\n        XML_RNGP_INTERLEAVE_NO_CONTENT                     =    1048\n        XML_RNGP_INVALID_DEFINE_NAME                       =    1049\n        XML_RNGP_INVALID_URI                               =    1050\n        XML_RNGP_INVALID_VALUE                             =    1051\n        XML_RNGP_MISSING_HREF                              =    1052\n        XML_RNGP_NAME_MISSING                              =    1053\n        XML_RNGP_NEED_COMBINE                              =    1054\n        XML_RNGP_NOTALLOWED_NOT_EMPTY                      =    1055\n        XML_RNGP_NSNAME_ATTR_ANCESTOR                      =    1056\n        XML_RNGP_NSNAME_NO_NS                              =    1057\n        XML_RNGP_PARAM_FORBIDDEN                           =    1058\n        XML_RNGP_PARAM_NAME_MISSING                        =    1059\n        XML_RNGP_PARENTREF_CREATE_FAILED                   =    1060\n        XML_RNGP_PARENTREF_NAME_INVALID                    =    1061\n        XML_RNGP_PARENTREF_NO_NAME                         =    1062\n        XML_RNGP_PARENTREF_NO_PARENT                       =    1063\n        XML_RNGP_PARENTREF_NOT_EMPTY                       =    1064\n        XML_RNGP_PARSE_ERROR                               =    1065\n        XML_RNGP_PAT_ANYNAME_EXCEPT_ANYNAME                =    1066\n        XML_RNGP_PAT_ATTR_ATTR                             =    1067\n        XML_RNGP_PAT_ATTR_ELEM                             =    1068\n        XML_RNGP_PAT_DATA_EXCEPT_ATTR                      =    1069\n        XML_RNGP_PAT_DATA_EXCEPT_ELEM                      =    1070\n        XML_RNGP_PAT_DATA_EXCEPT_EMPTY                     =    1071\n        XML_RNGP_PAT_DATA_EXCEPT_GROUP                     =    1072\n        XML_RNGP_PAT_DATA_EXCEPT_INTERLEAVE                =    1073\n        XML_RNGP_PAT_DATA_EXCEPT_LIST                      =    1074\n        XML_RNGP_PAT_DATA_EXCEPT_ONEMORE                   =    1075\n        XML_RNGP_PAT_DATA_EXCEPT_REF                       =    1076\n        XML_RNGP_PAT_DATA_EXCEPT_TEXT                      =    1077\n        XML_RNGP_PAT_LIST_ATTR                             =    1078\n        XML_RNGP_PAT_LIST_ELEM                             =    1079\n        XML_RNGP_PAT_LIST_INTERLEAVE                       =    1080\n        XML_RNGP_PAT_LIST_LIST                             =    1081\n        XML_RNGP_PAT_LIST_REF                              =    1082\n        XML_RNGP_PAT_LIST_TEXT                             =    1083\n        XML_RNGP_PAT_NSNAME_EXCEPT_ANYNAME                 =    1084\n        XML_RNGP_PAT_NSNAME_EXCEPT_NSNAME                  =    1085\n        XML_RNGP_PAT_ONEMORE_GROUP_ATTR                    =    1086\n        XML_RNGP_PAT_ONEMORE_INTERLEAVE_ATTR               =    1087\n        XML_RNGP_PAT_START_ATTR                            =    1088\n        XML_RNGP_PAT_START_DATA                            =    1089\n        XML_RNGP_PAT_START_EMPTY                           =    1090\n        XML_RNGP_PAT_START_GROUP                           =    1091\n        XML_RNGP_PAT_START_INTERLEAVE                      =    1092\n        XML_RNGP_PAT_START_LIST                            =    1093\n        XML_RNGP_PAT_START_ONEMORE                         =    1094\n        XML_RNGP_PAT_START_TEXT                            =    1095\n        XML_RNGP_PAT_START_VALUE                           =    1096\n        XML_RNGP_PREFIX_UNDEFINED                          =    1097\n        XML_RNGP_REF_CREATE_FAILED                         =    1098\n        XML_RNGP_REF_CYCLE                                 =    1099\n        XML_RNGP_REF_NAME_INVALID                          =    1100\n        XML_RNGP_REF_NO_DEF                                =    1101\n        XML_RNGP_REF_NO_NAME                               =    1102\n        XML_RNGP_REF_NOT_EMPTY                             =    1103\n        XML_RNGP_START_CHOICE_AND_INTERLEAVE               =    1104\n        XML_RNGP_START_CONTENT                             =    1105\n        XML_RNGP_START_EMPTY                               =    1106\n        XML_RNGP_START_MISSING                             =    1107\n        XML_RNGP_TEXT_EXPECTED                             =    1108\n        XML_RNGP_TEXT_HAS_CHILD                            =    1109\n        XML_RNGP_TYPE_MISSING                              =    1110\n        XML_RNGP_TYPE_NOT_FOUND                            =    1111\n        XML_RNGP_TYPE_VALUE                                =    1112\n        XML_RNGP_UNKNOWN_ATTRIBUTE                         =    1113\n        XML_RNGP_UNKNOWN_COMBINE                           =    1114\n        XML_RNGP_UNKNOWN_CONSTRUCT                         =    1115\n        XML_RNGP_UNKNOWN_TYPE_LIB                          =    1116\n        XML_RNGP_URI_FRAGMENT                              =    1117\n        XML_RNGP_URI_NOT_ABSOLUTE                          =    1118\n        XML_RNGP_VALUE_EMPTY                               =    1119\n        XML_RNGP_VALUE_NO_CONTENT                          =    1120\n        XML_RNGP_XMLNS_NAME                                =    1121\n        XML_RNGP_XML_NS                                    =    1122\n        XML_XPATH_EXPRESSION_OK                            =    1200\n        XML_XPATH_NUMBER_ERROR                             =    1201\n        XML_XPATH_UNFINISHED_LITERAL_ERROR                 =    1202\n        XML_XPATH_START_LITERAL_ERROR                      =    1203\n        XML_XPATH_VARIABLE_REF_ERROR                       =    1204\n        XML_XPATH_UNDEF_VARIABLE_ERROR                     =    1205\n        XML_XPATH_INVALID_PREDICATE_ERROR                  =    1206\n        XML_XPATH_EXPR_ERROR                               =    1207\n        XML_XPATH_UNCLOSED_ERROR                           =    1208\n        XML_XPATH_UNKNOWN_FUNC_ERROR                       =    1209\n        XML_XPATH_INVALID_OPERAND                          =    1210\n        XML_XPATH_INVALID_TYPE                             =    1211\n        XML_XPATH_INVALID_ARITY                            =    1212\n        XML_XPATH_INVALID_CTXT_SIZE                        =    1213\n        XML_XPATH_INVALID_CTXT_POSITION                    =    1214\n        XML_XPATH_MEMORY_ERROR                             =    1215\n        XML_XPTR_SYNTAX_ERROR                              =    1216\n        XML_XPTR_RESOURCE_ERROR                            =    1217\n        XML_XPTR_SUB_RESOURCE_ERROR                        =    1218\n        XML_XPATH_UNDEF_PREFIX_ERROR                       =    1219\n        XML_XPATH_ENCODING_ERROR                           =    1220\n        XML_XPATH_INVALID_CHAR_ERROR                       =    1221\n        XML_TREE_INVALID_HEX                               =    1300\n        XML_TREE_INVALID_DEC                               =    1301\n        XML_TREE_UNTERMINATED_ENTITY                       =    1302\n        XML_TREE_NOT_UTF8                                  =    1303\n        XML_SAVE_NOT_UTF8                                  =    1400\n        XML_SAVE_CHAR_INVALID                              =    1401\n        XML_SAVE_NO_DOCTYPE                                =    1402\n        XML_SAVE_UNKNOWN_ENCODING                          =    1403\n        XML_REGEXP_COMPILE_ERROR                           =    1450\n        XML_IO_UNKNOWN                                     =    1500\n        XML_IO_EACCES                                      =    1501\n        XML_IO_EAGAIN                                      =    1502\n        XML_IO_EBADF                                       =    1503\n        XML_IO_EBADMSG                                     =    1504\n        XML_IO_EBUSY                                       =    1505\n        XML_IO_ECANCELED                                   =    1506\n        XML_IO_ECHILD                                      =    1507\n        XML_IO_EDEADLK                                     =    1508\n        XML_IO_EDOM                                        =    1509\n        XML_IO_EEXIST                                      =    1510\n        XML_IO_EFAULT                                      =    1511\n        XML_IO_EFBIG                                       =    1512\n        XML_IO_EINPROGRESS                                 =    1513\n        XML_IO_EINTR                                       =    1514\n        XML_IO_EINVAL                                      =    1515\n        XML_IO_EIO                                         =    1516\n        XML_IO_EISDIR                                      =    1517\n        XML_IO_EMFILE                                      =    1518\n        XML_IO_EMLINK                                      =    1519\n        XML_IO_EMSGSIZE                                    =    1520\n        XML_IO_ENAMETOOLONG                                =    1521\n        XML_IO_ENFILE                                      =    1522\n        XML_IO_ENODEV                                      =    1523\n        XML_IO_ENOENT                                      =    1524\n        XML_IO_ENOEXEC                                     =    1525\n        XML_IO_ENOLCK                                      =    1526\n        XML_IO_ENOMEM                                      =    1527\n        XML_IO_ENOSPC                                      =    1528\n        XML_IO_ENOSYS                                      =    1529\n        XML_IO_ENOTDIR                                     =    1530\n        XML_IO_ENOTEMPTY                                   =    1531\n        XML_IO_ENOTSUP                                     =    1532\n        XML_IO_ENOTTY                                      =    1533\n        XML_IO_ENXIO                                       =    1534\n        XML_IO_EPERM                                       =    1535\n        XML_IO_EPIPE                                       =    1536\n        XML_IO_ERANGE                                      =    1537\n        XML_IO_EROFS                                       =    1538\n        XML_IO_ESPIPE                                      =    1539\n        XML_IO_ESRCH                                       =    1540\n        XML_IO_ETIMEDOUT                                   =    1541\n        XML_IO_EXDEV                                       =    1542\n        XML_IO_NETWORK_ATTEMPT                             =    1543\n        XML_IO_ENCODER                                     =    1544\n        XML_IO_FLUSH                                       =    1545\n        XML_IO_WRITE                                       =    1546\n        XML_IO_NO_INPUT                                    =    1547\n        XML_IO_BUFFER_FULL                                 =    1548\n        XML_IO_LOAD_ERROR                                  =    1549\n        XML_IO_ENOTSOCK                                    =    1550\n        XML_IO_EISCONN                                     =    1551\n        XML_IO_ECONNREFUSED                                =    1552\n        XML_IO_ENETUNREACH                                 =    1553\n        XML_IO_EADDRINUSE                                  =    1554\n        XML_IO_EALREADY                                    =    1555\n        XML_IO_EAFNOSUPPORT                                =    1556\n        XML_XINCLUDE_RECURSION                             =    1600\n        XML_XINCLUDE_PARSE_VALUE                           =    1601\n        XML_XINCLUDE_ENTITY_DEF_MISMATCH                   =    1602\n        XML_XINCLUDE_NO_HREF                               =    1603\n        XML_XINCLUDE_NO_FALLBACK                           =    1604\n        XML_XINCLUDE_HREF_URI                              =    1605\n        XML_XINCLUDE_TEXT_FRAGMENT                         =    1606\n        XML_XINCLUDE_TEXT_DOCUMENT                         =    1607\n        XML_XINCLUDE_INVALID_CHAR                          =    1608\n        XML_XINCLUDE_BUILD_FAILED                          =    1609\n        XML_XINCLUDE_UNKNOWN_ENCODING                      =    1610\n        XML_XINCLUDE_MULTIPLE_ROOT                         =    1611\n        XML_XINCLUDE_XPTR_FAILED                           =    1612\n        XML_XINCLUDE_XPTR_RESULT                           =    1613\n        XML_XINCLUDE_INCLUDE_IN_INCLUDE                    =    1614\n        XML_XINCLUDE_FALLBACKS_IN_INCLUDE                  =    1615\n        XML_XINCLUDE_FALLBACK_NOT_IN_INCLUDE               =    1616\n        XML_XINCLUDE_DEPRECATED_NS                         =    1617\n        XML_XINCLUDE_FRAGMENT_ID                           =    1618\n        XML_CATALOG_MISSING_ATTR                           =    1650\n        XML_CATALOG_ENTRY_BROKEN                           =    1651\n        XML_CATALOG_PREFER_VALUE                           =    1652\n        XML_CATALOG_NOT_CATALOG                            =    1653\n        XML_CATALOG_RECURSION                              =    1654\n        XML_SCHEMAP_PREFIX_UNDEFINED                       =    1700\n        XML_SCHEMAP_ATTRFORMDEFAULT_VALUE                  =    1701\n        XML_SCHEMAP_ATTRGRP_NONAME_NOREF                   =    1702\n        XML_SCHEMAP_ATTR_NONAME_NOREF                      =    1703\n        XML_SCHEMAP_COMPLEXTYPE_NONAME_NOREF               =    1704\n        XML_SCHEMAP_ELEMFORMDEFAULT_VALUE                  =    1705\n        XML_SCHEMAP_ELEM_NONAME_NOREF                      =    1706\n        XML_SCHEMAP_EXTENSION_NO_BASE                      =    1707\n        XML_SCHEMAP_FACET_NO_VALUE                         =    1708\n        XML_SCHEMAP_FAILED_BUILD_IMPORT                    =    1709\n        XML_SCHEMAP_GROUP_NONAME_NOREF                     =    1710\n        XML_SCHEMAP_IMPORT_NAMESPACE_NOT_URI               =    1711\n        XML_SCHEMAP_IMPORT_REDEFINE_NSNAME                 =    1712\n        XML_SCHEMAP_IMPORT_SCHEMA_NOT_URI                  =    1713\n        XML_SCHEMAP_INVALID_BOOLEAN                        =    1714\n        XML_SCHEMAP_INVALID_ENUM                           =    1715\n        XML_SCHEMAP_INVALID_FACET                          =    1716\n        XML_SCHEMAP_INVALID_FACET_VALUE                    =    1717\n        XML_SCHEMAP_INVALID_MAXOCCURS                      =    1718\n        XML_SCHEMAP_INVALID_MINOCCURS                      =    1719\n        XML_SCHEMAP_INVALID_REF_AND_SUBTYPE                =    1720\n        XML_SCHEMAP_INVALID_WHITE_SPACE                    =    1721\n        XML_SCHEMAP_NOATTR_NOREF                           =    1722\n        XML_SCHEMAP_NOTATION_NO_NAME                       =    1723\n        XML_SCHEMAP_NOTYPE_NOREF                           =    1724\n        XML_SCHEMAP_REF_AND_SUBTYPE                        =    1725\n        XML_SCHEMAP_RESTRICTION_NONAME_NOREF               =    1726\n        XML_SCHEMAP_SIMPLETYPE_NONAME                      =    1727\n        XML_SCHEMAP_TYPE_AND_SUBTYPE                       =    1728\n        XML_SCHEMAP_UNKNOWN_ALL_CHILD                      =    1729\n        XML_SCHEMAP_UNKNOWN_ANYATTRIBUTE_CHILD             =    1730\n        XML_SCHEMAP_UNKNOWN_ATTR_CHILD                     =    1731\n        XML_SCHEMAP_UNKNOWN_ATTRGRP_CHILD                  =    1732\n        XML_SCHEMAP_UNKNOWN_ATTRIBUTE_GROUP                =    1733\n        XML_SCHEMAP_UNKNOWN_BASE_TYPE                      =    1734\n        XML_SCHEMAP_UNKNOWN_CHOICE_CHILD                   =    1735\n        XML_SCHEMAP_UNKNOWN_COMPLEXCONTENT_CHILD           =    1736\n        XML_SCHEMAP_UNKNOWN_COMPLEXTYPE_CHILD              =    1737\n        XML_SCHEMAP_UNKNOWN_ELEM_CHILD                     =    1738\n        XML_SCHEMAP_UNKNOWN_EXTENSION_CHILD                =    1739\n        XML_SCHEMAP_UNKNOWN_FACET_CHILD                    =    1740\n        XML_SCHEMAP_UNKNOWN_FACET_TYPE                     =    1741\n        XML_SCHEMAP_UNKNOWN_GROUP_CHILD                    =    1742\n        XML_SCHEMAP_UNKNOWN_IMPORT_CHILD                   =    1743\n        XML_SCHEMAP_UNKNOWN_LIST_CHILD                     =    1744\n        XML_SCHEMAP_UNKNOWN_NOTATION_CHILD                 =    1745\n        XML_SCHEMAP_UNKNOWN_PROCESSCONTENT_CHILD           =    1746\n        XML_SCHEMAP_UNKNOWN_REF                            =    1747\n        XML_SCHEMAP_UNKNOWN_RESTRICTION_CHILD              =    1748\n        XML_SCHEMAP_UNKNOWN_SCHEMAS_CHILD                  =    1749\n        XML_SCHEMAP_UNKNOWN_SEQUENCE_CHILD                 =    1750\n        XML_SCHEMAP_UNKNOWN_SIMPLECONTENT_CHILD            =    1751\n        XML_SCHEMAP_UNKNOWN_SIMPLETYPE_CHILD               =    1752\n        XML_SCHEMAP_UNKNOWN_TYPE                           =    1753\n        XML_SCHEMAP_UNKNOWN_UNION_CHILD                    =    1754\n        XML_SCHEMAP_ELEM_DEFAULT_FIXED                     =    1755\n        XML_SCHEMAP_REGEXP_INVALID                         =    1756\n        XML_SCHEMAP_FAILED_LOAD                            =    1757\n        XML_SCHEMAP_NOTHING_TO_PARSE                       =    1758\n        XML_SCHEMAP_NOROOT                                 =    1759\n        XML_SCHEMAP_REDEFINED_GROUP                        =    1760\n        XML_SCHEMAP_REDEFINED_TYPE                         =    1761\n        XML_SCHEMAP_REDEFINED_ELEMENT                      =    1762\n        XML_SCHEMAP_REDEFINED_ATTRGROUP                    =    1763\n        XML_SCHEMAP_REDEFINED_ATTR                         =    1764\n        XML_SCHEMAP_REDEFINED_NOTATION                     =    1765\n        XML_SCHEMAP_FAILED_PARSE                           =    1766\n        XML_SCHEMAP_UNKNOWN_PREFIX                         =    1767\n        XML_SCHEMAP_DEF_AND_PREFIX                         =    1768\n        XML_SCHEMAP_UNKNOWN_INCLUDE_CHILD                  =    1769\n        XML_SCHEMAP_INCLUDE_SCHEMA_NOT_URI                 =    1770\n        XML_SCHEMAP_INCLUDE_SCHEMA_NO_URI                  =    1771\n        XML_SCHEMAP_NOT_SCHEMA                             =    1772\n        XML_SCHEMAP_UNKNOWN_MEMBER_TYPE                    =    1773\n        XML_SCHEMAP_INVALID_ATTR_USE                       =    1774\n        XML_SCHEMAP_RECURSIVE                              =    1775\n        XML_SCHEMAP_SUPERNUMEROUS_LIST_ITEM_TYPE           =    1776\n        XML_SCHEMAP_INVALID_ATTR_COMBINATION               =    1777\n        XML_SCHEMAP_INVALID_ATTR_INLINE_COMBINATION        =    1778\n        XML_SCHEMAP_MISSING_SIMPLETYPE_CHILD               =    1779\n        XML_SCHEMAP_INVALID_ATTR_NAME                      =    1780\n        XML_SCHEMAP_REF_AND_CONTENT                        =    1781\n        XML_SCHEMAP_CT_PROPS_CORRECT_1                     =    1782\n        XML_SCHEMAP_CT_PROPS_CORRECT_2                     =    1783\n        XML_SCHEMAP_CT_PROPS_CORRECT_3                     =    1784\n        XML_SCHEMAP_CT_PROPS_CORRECT_4                     =    1785\n        XML_SCHEMAP_CT_PROPS_CORRECT_5                     =    1786\n        XML_SCHEMAP_DERIVATION_OK_RESTRICTION_1            =    1787\n        XML_SCHEMAP_DERIVATION_OK_RESTRICTION_2_1_1        =    1788\n        XML_SCHEMAP_DERIVATION_OK_RESTRICTION_2_1_2        =    1789\n        XML_SCHEMAP_DERIVATION_OK_RESTRICTION_2_2          =    1790\n        XML_SCHEMAP_DERIVATION_OK_RESTRICTION_3            =    1791\n        XML_SCHEMAP_WILDCARD_INVALID_NS_MEMBER             =    1792\n        XML_SCHEMAP_INTERSECTION_NOT_EXPRESSIBLE           =    1793\n        XML_SCHEMAP_UNION_NOT_EXPRESSIBLE                  =    1794\n        XML_SCHEMAP_SRC_IMPORT_3_1                         =    1795\n        XML_SCHEMAP_SRC_IMPORT_3_2                         =    1796\n        XML_SCHEMAP_DERIVATION_OK_RESTRICTION_4_1          =    1797\n        XML_SCHEMAP_DERIVATION_OK_RESTRICTION_4_2          =    1798\n        XML_SCHEMAP_DERIVATION_OK_RESTRICTION_4_3          =    1799\n        XML_SCHEMAP_COS_CT_EXTENDS_1_3                     =    1800\n        XML_SCHEMAV_NOROOT                                 =    1801\n        XML_SCHEMAV_UNDECLAREDELEM                         =    1802\n        XML_SCHEMAV_NOTTOPLEVEL                            =    1803\n        XML_SCHEMAV_MISSING                                =    1804\n        XML_SCHEMAV_WRONGELEM                              =    1805\n        XML_SCHEMAV_NOTYPE                                 =    1806\n        XML_SCHEMAV_NOROLLBACK                             =    1807\n        XML_SCHEMAV_ISABSTRACT                             =    1808\n        XML_SCHEMAV_NOTEMPTY                               =    1809\n        XML_SCHEMAV_ELEMCONT                               =    1810\n        XML_SCHEMAV_HAVEDEFAULT                            =    1811\n        XML_SCHEMAV_NOTNILLABLE                            =    1812\n        XML_SCHEMAV_EXTRACONTENT                           =    1813\n        XML_SCHEMAV_INVALIDATTR                            =    1814\n        XML_SCHEMAV_INVALIDELEM                            =    1815\n        XML_SCHEMAV_NOTDETERMINIST                         =    1816\n        XML_SCHEMAV_CONSTRUCT                              =    1817\n        XML_SCHEMAV_INTERNAL                               =    1818\n        XML_SCHEMAV_NOTSIMPLE                              =    1819\n        XML_SCHEMAV_ATTRUNKNOWN                            =    1820\n        XML_SCHEMAV_ATTRINVALID                            =    1821\n        XML_SCHEMAV_VALUE                                  =    1822\n        XML_SCHEMAV_FACET                                  =    1823\n        XML_SCHEMAV_CVC_DATATYPE_VALID_1_2_1               =    1824\n        XML_SCHEMAV_CVC_DATATYPE_VALID_1_2_2               =    1825\n        XML_SCHEMAV_CVC_DATATYPE_VALID_1_2_3               =    1826\n        XML_SCHEMAV_CVC_TYPE_3_1_1                         =    1827\n        XML_SCHEMAV_CVC_TYPE_3_1_2                         =    1828\n        XML_SCHEMAV_CVC_FACET_VALID                        =    1829\n        XML_SCHEMAV_CVC_LENGTH_VALID                       =    1830\n        XML_SCHEMAV_CVC_MINLENGTH_VALID                    =    1831\n        XML_SCHEMAV_CVC_MAXLENGTH_VALID                    =    1832\n        XML_SCHEMAV_CVC_MININCLUSIVE_VALID                 =    1833\n        XML_SCHEMAV_CVC_MAXINCLUSIVE_VALID                 =    1834\n        XML_SCHEMAV_CVC_MINEXCLUSIVE_VALID                 =    1835\n        XML_SCHEMAV_CVC_MAXEXCLUSIVE_VALID                 =    1836\n        XML_SCHEMAV_CVC_TOTALDIGITS_VALID                  =    1837\n        XML_SCHEMAV_CVC_FRACTIONDIGITS_VALID               =    1838\n        XML_SCHEMAV_CVC_PATTERN_VALID                      =    1839\n        XML_SCHEMAV_CVC_ENUMERATION_VALID                  =    1840\n        XML_SCHEMAV_CVC_COMPLEX_TYPE_2_1                   =    1841\n        XML_SCHEMAV_CVC_COMPLEX_TYPE_2_2                   =    1842\n        XML_SCHEMAV_CVC_COMPLEX_TYPE_2_3                   =    1843\n        XML_SCHEMAV_CVC_COMPLEX_TYPE_2_4                   =    1844\n        XML_SCHEMAV_CVC_ELT_1                              =    1845\n        XML_SCHEMAV_CVC_ELT_2                              =    1846\n        XML_SCHEMAV_CVC_ELT_3_1                            =    1847\n        XML_SCHEMAV_CVC_ELT_3_2_1                          =    1848\n        XML_SCHEMAV_CVC_ELT_3_2_2                          =    1849\n        XML_SCHEMAV_CVC_ELT_4_1                            =    1850\n        XML_SCHEMAV_CVC_ELT_4_2                            =    1851\n        XML_SCHEMAV_CVC_ELT_4_3                            =    1852\n        XML_SCHEMAV_CVC_ELT_5_1_1                          =    1853\n        XML_SCHEMAV_CVC_ELT_5_1_2                          =    1854\n        XML_SCHEMAV_CVC_ELT_5_2_1                          =    1855\n        XML_SCHEMAV_CVC_ELT_5_2_2_1                        =    1856\n        XML_SCHEMAV_CVC_ELT_5_2_2_2_1                      =    1857\n        XML_SCHEMAV_CVC_ELT_5_2_2_2_2                      =    1858\n        XML_SCHEMAV_CVC_ELT_6                              =    1859\n        XML_SCHEMAV_CVC_ELT_7                              =    1860\n        XML_SCHEMAV_CVC_ATTRIBUTE_1                        =    1861\n        XML_SCHEMAV_CVC_ATTRIBUTE_2                        =    1862\n        XML_SCHEMAV_CVC_ATTRIBUTE_3                        =    1863\n        XML_SCHEMAV_CVC_ATTRIBUTE_4                        =    1864\n        XML_SCHEMAV_CVC_COMPLEX_TYPE_3_1                   =    1865\n        XML_SCHEMAV_CVC_COMPLEX_TYPE_3_2_1                 =    1866\n        XML_SCHEMAV_CVC_COMPLEX_TYPE_3_2_2                 =    1867\n        XML_SCHEMAV_CVC_COMPLEX_TYPE_4                     =    1868\n        XML_SCHEMAV_CVC_COMPLEX_TYPE_5_1                   =    1869\n        XML_SCHEMAV_CVC_COMPLEX_TYPE_5_2                   =    1870\n        XML_SCHEMAV_ELEMENT_CONTENT                        =    1871\n        XML_SCHEMAV_DOCUMENT_ELEMENT_MISSING               =    1872\n        XML_SCHEMAV_CVC_COMPLEX_TYPE_1                     =    1873\n        XML_SCHEMAV_CVC_AU                                 =    1874\n        XML_SCHEMAV_CVC_TYPE_1                             =    1875\n        XML_SCHEMAV_CVC_TYPE_2                             =    1876\n        XML_SCHEMAV_CVC_IDC                                =    1877\n        XML_SCHEMAV_CVC_WILDCARD                           =    1878\n        XML_SCHEMAV_MISC                                   =    1879\n        XML_XPTR_UNKNOWN_SCHEME                            =    1900\n        XML_XPTR_CHILDSEQ_START                            =    1901\n        XML_XPTR_EVAL_FAILED                               =    1902\n        XML_XPTR_EXTRA_OBJECTS                             =    1903\n        XML_C14N_CREATE_CTXT                               =    1950\n        XML_C14N_REQUIRES_UTF8                             =    1951\n        XML_C14N_CREATE_STACK                              =    1952\n        XML_C14N_INVALID_NODE                              =    1953\n        XML_C14N_UNKNOW_NODE                               =    1954\n        XML_C14N_RELATIVE_NAMESPACE                        =    1955\n        XML_FTP_PASV_ANSWER                                =    2000\n        XML_FTP_EPSV_ANSWER                                =    2001\n        XML_FTP_ACCNT                                      =    2002\n        XML_FTP_URL_SYNTAX                                 =    2003\n        XML_HTTP_URL_SYNTAX                                =    2020\n        XML_HTTP_USE_IP                                    =    2021\n        XML_HTTP_UNKNOWN_HOST                              =    2022\n        XML_SCHEMAP_SRC_SIMPLE_TYPE_1                      =    3000\n        XML_SCHEMAP_SRC_SIMPLE_TYPE_2                      =    3001\n        XML_SCHEMAP_SRC_SIMPLE_TYPE_3                      =    3002\n        XML_SCHEMAP_SRC_SIMPLE_TYPE_4                      =    3003\n        XML_SCHEMAP_SRC_RESOLVE                            =    3004\n        XML_SCHEMAP_SRC_RESTRICTION_BASE_OR_SIMPLETYPE     =    3005\n        XML_SCHEMAP_SRC_LIST_ITEMTYPE_OR_SIMPLETYPE        =    3006\n        XML_SCHEMAP_SRC_UNION_MEMBERTYPES_OR_SIMPLETYPES   =    3007\n        XML_SCHEMAP_ST_PROPS_CORRECT_1                     =    3008\n        XML_SCHEMAP_ST_PROPS_CORRECT_2                     =    3009\n        XML_SCHEMAP_ST_PROPS_CORRECT_3                     =    3010\n        XML_SCHEMAP_COS_ST_RESTRICTS_1_1                   =    3011\n        XML_SCHEMAP_COS_ST_RESTRICTS_1_2                   =    3012\n        XML_SCHEMAP_COS_ST_RESTRICTS_1_3_1                 =    3013\n        XML_SCHEMAP_COS_ST_RESTRICTS_1_3_2                 =    3014\n        XML_SCHEMAP_COS_ST_RESTRICTS_2_1                   =    3015\n        XML_SCHEMAP_COS_ST_RESTRICTS_2_3_1_1               =    3016\n        XML_SCHEMAP_COS_ST_RESTRICTS_2_3_1_2               =    3017\n        XML_SCHEMAP_COS_ST_RESTRICTS_2_3_2_1               =    3018\n        XML_SCHEMAP_COS_ST_RESTRICTS_2_3_2_2               =    3019\n        XML_SCHEMAP_COS_ST_RESTRICTS_2_3_2_3               =    3020\n        XML_SCHEMAP_COS_ST_RESTRICTS_2_3_2_4               =    3021\n        XML_SCHEMAP_COS_ST_RESTRICTS_2_3_2_5               =    3022\n        XML_SCHEMAP_COS_ST_RESTRICTS_3_1                   =    3023\n        XML_SCHEMAP_COS_ST_RESTRICTS_3_3_1                 =    3024\n        XML_SCHEMAP_COS_ST_RESTRICTS_3_3_1_2               =    3025\n        XML_SCHEMAP_COS_ST_RESTRICTS_3_3_2_2               =    3026\n        XML_SCHEMAP_COS_ST_RESTRICTS_3_3_2_1               =    3027\n        XML_SCHEMAP_COS_ST_RESTRICTS_3_3_2_3               =    3028\n        XML_SCHEMAP_COS_ST_RESTRICTS_3_3_2_4               =    3029\n        XML_SCHEMAP_COS_ST_RESTRICTS_3_3_2_5               =    3030\n        XML_SCHEMAP_COS_ST_DERIVED_OK_2_1                  =    3031\n        XML_SCHEMAP_COS_ST_DERIVED_OK_2_2                  =    3032\n        XML_SCHEMAP_S4S_ELEM_NOT_ALLOWED                   =    3033\n        XML_SCHEMAP_S4S_ELEM_MISSING                       =    3034\n        XML_SCHEMAP_S4S_ATTR_NOT_ALLOWED                   =    3035\n        XML_SCHEMAP_S4S_ATTR_MISSING                       =    3036\n        XML_SCHEMAP_S4S_ATTR_INVALID_VALUE                 =    3037\n        XML_SCHEMAP_SRC_ELEMENT_1                          =    3038\n        XML_SCHEMAP_SRC_ELEMENT_2_1                        =    3039\n        XML_SCHEMAP_SRC_ELEMENT_2_2                        =    3040\n        XML_SCHEMAP_SRC_ELEMENT_3                          =    3041\n        XML_SCHEMAP_P_PROPS_CORRECT_1                      =    3042\n        XML_SCHEMAP_P_PROPS_CORRECT_2_1                    =    3043\n        XML_SCHEMAP_P_PROPS_CORRECT_2_2                    =    3044\n        XML_SCHEMAP_E_PROPS_CORRECT_2                      =    3045\n        XML_SCHEMAP_E_PROPS_CORRECT_3                      =    3046\n        XML_SCHEMAP_E_PROPS_CORRECT_4                      =    3047\n        XML_SCHEMAP_E_PROPS_CORRECT_5                      =    3048\n        XML_SCHEMAP_E_PROPS_CORRECT_6                      =    3049\n        XML_SCHEMAP_SRC_INCLUDE                            =    3050\n        XML_SCHEMAP_SRC_ATTRIBUTE_1                        =    3051\n        XML_SCHEMAP_SRC_ATTRIBUTE_2                        =    3052\n        XML_SCHEMAP_SRC_ATTRIBUTE_3_1                      =    3053\n        XML_SCHEMAP_SRC_ATTRIBUTE_3_2                      =    3054\n        XML_SCHEMAP_SRC_ATTRIBUTE_4                        =    3055\n        XML_SCHEMAP_NO_XMLNS                               =    3056\n        XML_SCHEMAP_NO_XSI                                 =    3057\n        XML_SCHEMAP_COS_VALID_DEFAULT_1                    =    3058\n        XML_SCHEMAP_COS_VALID_DEFAULT_2_1                  =    3059\n        XML_SCHEMAP_COS_VALID_DEFAULT_2_2_1                =    3060\n        XML_SCHEMAP_COS_VALID_DEFAULT_2_2_2                =    3061\n        XML_SCHEMAP_CVC_SIMPLE_TYPE                        =    3062\n        XML_SCHEMAP_COS_CT_EXTENDS_1_1                     =    3063\n        XML_SCHEMAP_SRC_IMPORT_1_1                         =    3064\n        XML_SCHEMAP_SRC_IMPORT_1_2                         =    3065\n        XML_SCHEMAP_SRC_IMPORT_2                           =    3066\n        XML_SCHEMAP_SRC_IMPORT_2_1                         =    3067\n        XML_SCHEMAP_SRC_IMPORT_2_2                         =    3068\n        XML_SCHEMAP_INTERNAL                               =    3069 # 3069 non-W3C\n        XML_SCHEMAP_NOT_DETERMINISTIC                      =    3070 # 3070 non-W3C\n        XML_SCHEMAP_SRC_ATTRIBUTE_GROUP_1                  =    3071\n        XML_SCHEMAP_SRC_ATTRIBUTE_GROUP_2                  =    3072\n        XML_SCHEMAP_SRC_ATTRIBUTE_GROUP_3                  =    3073\n        XML_SCHEMAP_MG_PROPS_CORRECT_1                     =    3074\n        XML_SCHEMAP_MG_PROPS_CORRECT_2                     =    3075\n        XML_SCHEMAP_SRC_CT_1                               =    3076\n        XML_SCHEMAP_DERIVATION_OK_RESTRICTION_2_1_3        =    3077\n        XML_SCHEMAP_AU_PROPS_CORRECT_2                     =    3078\n        XML_SCHEMAP_A_PROPS_CORRECT_2                      =    3079\n        XML_SCHEMAP_C_PROPS_CORRECT                        =    3080\n        XML_SCHEMAP_SRC_REDEFINE                           =    3081\n        XML_SCHEMAP_SRC_IMPORT                             =    3082\n        XML_SCHEMAP_WARN_SKIP_SCHEMA                       =    3083\n        XML_SCHEMAP_WARN_UNLOCATED_SCHEMA                  =    3084\n        XML_SCHEMAP_WARN_ATTR_REDECL_PROH                  =    3085\n        XML_SCHEMAP_WARN_ATTR_POINTLESS_PROH               =    3086 # 3085\n        XML_SCHEMAP_AG_PROPS_CORRECT                       =    3087 # 3086\n        XML_SCHEMAP_COS_CT_EXTENDS_1_2                     =    3088 # 3087\n        XML_SCHEMAP_AU_PROPS_CORRECT                       =    3089 # 3088\n        XML_SCHEMAP_A_PROPS_CORRECT_3                      =    3090 # 3089\n        XML_SCHEMAP_COS_ALL_LIMITED                        =    3091 # 3090\n        XML_SCHEMATRONV_ASSERT                             =    4000\n        XML_SCHEMATRONV_REPORT                             =    4001\n        XML_MODULE_OPEN                                    =    4900\n        XML_MODULE_CLOSE                                   =    4901\n        XML_CHECK_FOUND_ELEMENT                            =    5000\n        XML_CHECK_FOUND_ATTRIBUTE                          =    5001\n        XML_CHECK_FOUND_TEXT                               =    5002\n        XML_CHECK_FOUND_CDATA                              =    5003\n        XML_CHECK_FOUND_ENTITYREF                          =    5004\n        XML_CHECK_FOUND_ENTITY                             =    5005\n        XML_CHECK_FOUND_PI                                 =    5006\n        XML_CHECK_FOUND_COMMENT                            =    5007\n        XML_CHECK_FOUND_DOCTYPE                            =    5008\n        XML_CHECK_FOUND_FRAGMENT                           =    5009\n        XML_CHECK_FOUND_NOTATION                           =    5010\n        XML_CHECK_UNKNOWN_NODE                             =    5011\n        XML_CHECK_ENTITY_TYPE                              =    5012\n        XML_CHECK_NO_PARENT                                =    5013\n        XML_CHECK_NO_DOC                                   =    5014\n        XML_CHECK_NO_NAME                                  =    5015\n        XML_CHECK_NO_ELEM                                  =    5016\n        XML_CHECK_WRONG_DOC                                =    5017\n        XML_CHECK_NO_PREV                                  =    5018\n        XML_CHECK_WRONG_PREV                               =    5019\n        XML_CHECK_NO_NEXT                                  =    5020\n        XML_CHECK_WRONG_NEXT                               =    5021\n        XML_CHECK_NOT_DTD                                  =    5022\n        XML_CHECK_NOT_ATTR                                 =    5023\n        XML_CHECK_NOT_ATTR_DECL                            =    5024\n        XML_CHECK_NOT_ELEM_DECL                            =    5025\n        XML_CHECK_NOT_ENTITY_DECL                          =    5026\n        XML_CHECK_NOT_NS_DECL                              =    5027\n        XML_CHECK_NO_HREF                                  =    5028\n        XML_CHECK_WRONG_PARENT                             =    5029\n        XML_CHECK_NS_SCOPE                                 =    5030\n        XML_CHECK_NS_ANCESTOR                              =    5031\n        XML_CHECK_NOT_UTF8                                 =    5032\n        XML_CHECK_NO_DICT                                  =    5033\n        XML_CHECK_NOT_NCNAME                               =    5034\n        XML_CHECK_OUTSIDE_DICT                             =    5035\n        XML_CHECK_WRONG_NAME                               =    5036\n        XML_CHECK_NAME_NOT_NULL                            =    5037\n        XML_I18N_NO_NAME                                   =    6000\n        XML_I18N_NO_HANDLER                                =    6001\n        XML_I18N_EXCESS_HANDLER                            =    6002\n        XML_I18N_CONV_FAILED                               =    6003\n        XML_I18N_NO_OUTPUT                                 =    6004\n        XML_BUF_OVERFLOW                                   =    7000\n\n    ctypedef enum xmlRelaxNGValidErr:\n        XML_RELAXNG_OK                                     =       0\n        XML_RELAXNG_ERR_MEMORY                             =       1\n        XML_RELAXNG_ERR_TYPE                               =       2\n        XML_RELAXNG_ERR_TYPEVAL                            =       3\n        XML_RELAXNG_ERR_DUPID                              =       4\n        XML_RELAXNG_ERR_TYPECMP                            =       5\n        XML_RELAXNG_ERR_NOSTATE                            =       6\n        XML_RELAXNG_ERR_NODEFINE                           =       7\n        XML_RELAXNG_ERR_LISTEXTRA                          =       8\n        XML_RELAXNG_ERR_LISTEMPTY                          =       9\n        XML_RELAXNG_ERR_INTERNODATA                        =      10\n        XML_RELAXNG_ERR_INTERSEQ                           =      11\n        XML_RELAXNG_ERR_INTEREXTRA                         =      12\n        XML_RELAXNG_ERR_ELEMNAME                           =      13\n        XML_RELAXNG_ERR_ATTRNAME                           =      14\n        XML_RELAXNG_ERR_ELEMNONS                           =      15\n        XML_RELAXNG_ERR_ATTRNONS                           =      16\n        XML_RELAXNG_ERR_ELEMWRONGNS                        =      17\n        XML_RELAXNG_ERR_ATTRWRONGNS                        =      18\n        XML_RELAXNG_ERR_ELEMEXTRANS                        =      19\n        XML_RELAXNG_ERR_ATTREXTRANS                        =      20\n        XML_RELAXNG_ERR_ELEMNOTEMPTY                       =      21\n        XML_RELAXNG_ERR_NOELEM                             =      22\n        XML_RELAXNG_ERR_NOTELEM                            =      23\n        XML_RELAXNG_ERR_ATTRVALID                          =      24\n        XML_RELAXNG_ERR_CONTENTVALID                       =      25\n        XML_RELAXNG_ERR_EXTRACONTENT                       =      26\n        XML_RELAXNG_ERR_INVALIDATTR                        =      27\n        XML_RELAXNG_ERR_DATAELEM                           =      28\n        XML_RELAXNG_ERR_VALELEM                            =      29\n        XML_RELAXNG_ERR_LISTELEM                           =      30\n        XML_RELAXNG_ERR_DATATYPE                           =      31\n        XML_RELAXNG_ERR_VALUE                              =      32\n        XML_RELAXNG_ERR_LIST                               =      33\n        XML_RELAXNG_ERR_NOGRAMMAR                          =      34\n        XML_RELAXNG_ERR_EXTRADATA                          =      35\n        XML_RELAXNG_ERR_LACKDATA                           =      36\n        XML_RELAXNG_ERR_INTERNAL                           =      37\n        XML_RELAXNG_ERR_ELEMWRONG                          =      38\n        XML_RELAXNG_ERR_TEXTWRONG                          =      39\n# --- END: GENERATED CONSTANTS ---\n\ncdef extern from \"libxml/xmlerror.h\":\n    ctypedef struct xmlError:\n        int domain\n        int code\n        char* message\n        xmlErrorLevel level\n        char* file\n        char* str1\n        char* str2\n        char* str3\n        int line\n        int int1\n        int int2\n        void* node\n\n    ctypedef void (*xmlGenericErrorFunc)(void* ctxt, char* msg, ...) nogil\n    ctypedef void (*xmlStructuredErrorFunc)(void* userData,\n                                            xmlError* error) nogil\n\n    cdef void xmlSetGenericErrorFunc(\n        void* ctxt, xmlGenericErrorFunc func) nogil\n    cdef void xmlSetStructuredErrorFunc(\n        void* ctxt, xmlStructuredErrorFunc func) nogil\n\ncdef extern from \"libxml/globals.h\":\n    cdef xmlStructuredErrorFunc xmlStructuredError\n    cdef void* xmlStructuredErrorContext\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/xmlparser.pxd",
    "content": "from libc.string cimport const_char\n\nfrom lxml.includes.tree cimport (\n    xmlDoc, xmlNode, xmlDict, xmlDtd, xmlChar, const_xmlChar)\nfrom lxml.includes.tree cimport xmlInputReadCallback, xmlInputCloseCallback\nfrom lxml.includes.xmlerror cimport xmlError, xmlStructuredErrorFunc\n\n\ncdef extern from \"libxml/parser.h\":\n    ctypedef void (*startElementNsSAX2Func)(void* ctx,\n                                            const_xmlChar* localname,\n                                            const_xmlChar* prefix,\n                                            const_xmlChar* URI,\n                                            int nb_namespaces,\n                                            const_xmlChar** namespaces,\n                                            int nb_attributes,\n                                            int nb_defaulted,\n                                            const_xmlChar** attributes)\n\n    ctypedef void (*endElementNsSAX2Func)(void* ctx,\n                                          const_xmlChar* localname,\n                                          const_xmlChar* prefix,\n                                          const_xmlChar* URI)\n\n    ctypedef void (*startElementSAXFunc)(void* ctx, const_xmlChar* name, const_xmlChar** atts)\n\n    ctypedef void (*endElementSAXFunc)(void* ctx, const_xmlChar* name)\n\n    ctypedef void (*charactersSAXFunc)(void* ctx, const_xmlChar* ch, int len)\n\n    ctypedef void (*cdataBlockSAXFunc)(void* ctx, const_xmlChar* value, int len)\n\n    ctypedef void (*commentSAXFunc)(void* ctx, const_xmlChar* value)\n\n    ctypedef void (*processingInstructionSAXFunc)(void* ctx, \n                                                  const_xmlChar* target,\n                                                  const_xmlChar* data)\n\n    ctypedef void (*internalSubsetSAXFunc)(void* ctx, \n                                            const_xmlChar* name,\n                                            const_xmlChar* externalID,\n                                            const_xmlChar* systemID)\n\n    ctypedef void (*endDocumentSAXFunc)(void* ctx)\n\n    ctypedef void (*startDocumentSAXFunc)(void* ctx)\n\n    ctypedef void (*referenceSAXFunc)(void * ctx, const_xmlChar* name)\n\n    cdef int XML_SAX2_MAGIC\n\ncdef extern from \"libxml/tree.h\":\n    ctypedef struct xmlParserInput:\n        int line\n        int length\n        const_xmlChar* base\n        const_xmlChar* cur\n        const_xmlChar* end\n        const_char *filename\n\n    ctypedef struct xmlParserInputBuffer:\n        void* context\n        xmlInputReadCallback  readcallback\n        xmlInputCloseCallback closecallback\n\n    ctypedef struct xmlSAXHandlerV1:\n        # same as xmlSAXHandler, but without namespaces\n        pass\n\n    ctypedef struct xmlSAXHandler:\n        internalSubsetSAXFunc           internalSubset\n        startElementNsSAX2Func          startElementNs\n        endElementNsSAX2Func            endElementNs\n        startElementSAXFunc             startElement\n        endElementSAXFunc               endElement\n        charactersSAXFunc               characters\n        cdataBlockSAXFunc               cdataBlock\n        referenceSAXFunc                reference\n        commentSAXFunc                  comment\n        processingInstructionSAXFunc\tprocessingInstruction\n        startDocumentSAXFunc            startDocument\n        endDocumentSAXFunc              endDocument\n        int                             initialized\n        xmlStructuredErrorFunc          serror\n        void*                           _private\n\n\ncdef extern from \"libxml/SAX2.h\" nogil:\n    cdef void xmlSAX2StartDocument(void* ctxt)\n\n\ncdef extern from \"libxml/xmlIO.h\" nogil:\n    cdef xmlParserInputBuffer* xmlAllocParserInputBuffer(int enc)\n\n\ncdef extern from \"libxml/parser.h\":\n\n    cdef xmlDict* xmlDictCreate() nogil\n    cdef xmlDict* xmlDictCreateSub(xmlDict* subdict) nogil\n    cdef void xmlDictFree(xmlDict* sub) nogil\n    cdef int xmlDictReference(xmlDict* dict) nogil\n    \n    cdef int XML_COMPLETE_ATTRS  # SAX option for adding DTD default attributes\n    cdef int XML_SKIP_IDS        # SAX option for not building an XML ID dict\n\n    ctypedef enum xmlParserInputState:\n        XML_PARSER_EOF = -1  # nothing is to be parsed\n        XML_PARSER_START = 0  # nothing has been parsed\n        XML_PARSER_MISC = 1  # Misc* before int subset\n        XML_PARSER_PI = 2  # Within a processing instruction\n        XML_PARSER_DTD = 3  # within some DTD content\n        XML_PARSER_PROLOG = 4  # Misc* after internal subset\n        XML_PARSER_COMMENT = 5  # within a comment\n        XML_PARSER_START_TAG = 6  # within a start tag\n        XML_PARSER_CONTENT = 7  # within the content\n        XML_PARSER_CDATA_SECTION = 8  # within a CDATA section\n        XML_PARSER_END_TAG = 9  # within a closing tag\n        XML_PARSER_ENTITY_DECL = 10  # within an entity declaration\n        XML_PARSER_ENTITY_VALUE = 11  # within an entity value in a decl\n        XML_PARSER_ATTRIBUTE_VALUE = 12  # within an attribute value\n        XML_PARSER_SYSTEM_LITERAL = 13  # within a SYSTEM value\n        XML_PARSER_EPILOG = 14  # the Misc* after the last end tag\n        XML_PARSER_IGNORE = 15  # within an IGNORED section\n        XML_PARSER_PUBLIC_LITERAL = 16  # within a PUBLIC value\n\n\n    ctypedef struct xmlParserCtxt:\n        xmlDoc* myDoc\n        xmlDict* dict\n        int dictNames\n        void* _private\n        bint wellFormed\n        bint recovery\n        int options\n        bint disableSAX\n        int errNo\n        xmlParserInputState instate\n        bint replaceEntities\n        int loadsubset  # != 0 if enabled, int value == why\n        bint validate\n        xmlError lastError\n        xmlNode* node\n        xmlSAXHandler* sax\n        void* userData\n        int* spaceTab\n        int spaceMax\n        bint html\n        bint progressive\n        int inSubset\n        int charset\n        xmlParserInput* input\n\n    ctypedef enum xmlParserOption:\n        XML_PARSE_RECOVER = 1 # recover on errors\n        XML_PARSE_NOENT = 2 # substitute entities\n        XML_PARSE_DTDLOAD = 4 # load the external subset\n        XML_PARSE_DTDATTR = 8 # default DTD attributes\n        XML_PARSE_DTDVALID = 16 # validate with the DTD\n        XML_PARSE_NOERROR = 32 # suppress error reports\n        XML_PARSE_NOWARNING = 64 # suppress warning reports\n        XML_PARSE_PEDANTIC = 128 # pedantic error reporting\n        XML_PARSE_NOBLANKS = 256 # remove blank nodes\n        XML_PARSE_SAX1 = 512 # use the SAX1 interface internally\n        XML_PARSE_XINCLUDE = 1024 # Implement XInclude substitution\n        XML_PARSE_NONET = 2048 # Forbid network access\n        XML_PARSE_NODICT = 4096 # Do not reuse the context dictionary\n        XML_PARSE_NSCLEAN = 8192 # remove redundant namespaces declarations\n        XML_PARSE_NOCDATA = 16384 # merge CDATA as text nodes\n        XML_PARSE_NOXINCNODE = 32768 # do not generate XINCLUDE START/END nodes\n        # libxml2 2.6.21+ only:\n        XML_PARSE_COMPACT = 65536 # compact small text nodes\n        # libxml2 2.7.0+ only:\n        XML_PARSE_OLD10 = 131072 # parse using XML-1.0 before update 5\n        XML_PARSE_NOBASEFIX = 262144 # do not fixup XINCLUDE xml:base uris\n        XML_PARSE_HUGE = 524288 # relax any hardcoded limit from the parser\n        # libxml2 2.7.3+ only:\n        XML_PARSE_OLDSAX = 1048576 # parse using SAX2 interface before 2.7.0\n        # libxml2 2.8.0+ only:\n        XML_PARSE_IGNORE_ENC = 2097152 # ignore internal document encoding hint\n        # libxml2 2.9.0+ only:\n        XML_PARSE_BIG_LINES = 4194304 # Store big lines numbers in text PSVI field\n\n    cdef void xmlInitParser() nogil\n    cdef void xmlCleanupParser() nogil\n\n    cdef int xmlLineNumbersDefault(int onoff) nogil\n    cdef xmlParserCtxt* xmlNewParserCtxt() nogil\n    cdef xmlParserInput* xmlNewIOInputStream(xmlParserCtxt* ctxt,\n                                             xmlParserInputBuffer* input,\n                                             int enc) nogil\n    cdef int xmlCtxtUseOptions(xmlParserCtxt* ctxt, int options) nogil\n    cdef void xmlFreeParserCtxt(xmlParserCtxt* ctxt) nogil\n    cdef void xmlCtxtReset(xmlParserCtxt* ctxt) nogil\n    cdef void xmlClearParserCtxt(xmlParserCtxt* ctxt) nogil\n    cdef int xmlParseChunk(xmlParserCtxt* ctxt,\n                           char* chunk, int size, int terminate) nogil\n    cdef xmlDoc* xmlCtxtReadDoc(xmlParserCtxt* ctxt,\n                                char* cur, char* URL, char* encoding,\n                                int options) nogil\n    cdef xmlDoc* xmlCtxtReadFile(xmlParserCtxt* ctxt,\n                                 char* filename, char* encoding,\n                                 int options) nogil\n    cdef xmlDoc* xmlCtxtReadIO(xmlParserCtxt* ctxt, \n                               xmlInputReadCallback ioread, \n                               xmlInputCloseCallback ioclose, \n                               void* ioctx,\n                               char* URL, char* encoding,\n                               int options) nogil\n    cdef xmlDoc* xmlCtxtReadMemory(xmlParserCtxt* ctxt,\n                                   char* buffer, int size,\n                                   char* filename, const_char* encoding,\n                                   int options) nogil\n\n# iterparse:\n\n    cdef xmlParserCtxt* xmlCreatePushParserCtxt(xmlSAXHandler* sax,\n                                                void* user_data,\n                                                char* chunk,\n                                                int size,\n                                                char* filename) nogil\n\n    cdef int xmlCtxtResetPush(xmlParserCtxt* ctxt,\n                              char* chunk,\n                              int size,\n                              char* filename,\n                              char* encoding) nogil\n\n# entity loaders:\n\n    ctypedef xmlParserInput* (*xmlExternalEntityLoader)(\n        const_char * URL, const_char * ID, xmlParserCtxt* context) nogil\n    cdef xmlExternalEntityLoader xmlGetExternalEntityLoader() nogil\n    cdef void xmlSetExternalEntityLoader(xmlExternalEntityLoader f) nogil\n\n# DTDs:\n\n    cdef xmlDtd* xmlParseDTD(const_xmlChar* ExternalID, const_xmlChar* SystemID) nogil\n    cdef xmlDtd* xmlIOParseDTD(xmlSAXHandler* sax,\n                               xmlParserInputBuffer* input,\n                               int enc) nogil\n\ncdef extern from \"libxml/parserInternals.h\":\n    cdef xmlParserInput* xmlNewInputStream(xmlParserCtxt* ctxt)\n    cdef xmlParserInput* xmlNewStringInputStream(xmlParserCtxt* ctxt, \n                                                 char* buffer) nogil\n    cdef xmlParserInput* xmlNewInputFromFile(xmlParserCtxt* ctxt, \n                                             char* filename) nogil\n    cdef void xmlFreeInputStream(xmlParserInput* input) nogil\n    cdef int xmlSwitchEncoding(xmlParserCtxt* ctxt, int enc) nogil\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/xmlschema.pxd",
    "content": "from lxml.includes.tree cimport xmlDoc\nfrom lxml.includes.xmlparser cimport xmlSAXHandler\nfrom lxml.includes.xmlerror cimport xmlStructuredErrorFunc\n\ncdef extern from \"libxml/xmlschemas.h\":\n    ctypedef struct xmlSchema\n    ctypedef struct xmlSchemaParserCtxt\n\n    ctypedef struct xmlSchemaSAXPlugStruct\n    ctypedef struct xmlSchemaValidCtxt\n\n    ctypedef enum xmlSchemaValidOption:\n        XML_SCHEMA_VAL_VC_I_CREATE = 1\n\n    cdef xmlSchemaValidCtxt* xmlSchemaNewValidCtxt(xmlSchema* schema) nogil\n    cdef void xmlSchemaSetParserStructuredErrors(xmlSchemaParserCtxt* ctxt,\n        xmlStructuredErrorFunc serror, void *ctx)\n    cdef void xmlSchemaSetValidStructuredErrors(xmlSchemaValidCtxt* ctxt,\n        xmlStructuredErrorFunc serror, void *ctx)\n\n    cdef int xmlSchemaValidateDoc(xmlSchemaValidCtxt* ctxt, xmlDoc* doc) nogil\n    cdef xmlSchema* xmlSchemaParse(xmlSchemaParserCtxt* ctxt) nogil\n    cdef xmlSchemaParserCtxt* xmlSchemaNewParserCtxt(char* URL) nogil\n    cdef xmlSchemaParserCtxt* xmlSchemaNewDocParserCtxt(xmlDoc* doc) nogil\n    cdef void xmlSchemaFree(xmlSchema* schema) nogil\n    cdef void xmlSchemaFreeParserCtxt(xmlSchemaParserCtxt* ctxt) nogil\n    cdef void xmlSchemaFreeValidCtxt(xmlSchemaValidCtxt* ctxt) nogil\n    cdef int xmlSchemaSetValidOptions(xmlSchemaValidCtxt* ctxt,\n                                      int options) nogil\n\n    cdef xmlSchemaSAXPlugStruct* xmlSchemaSAXPlug(xmlSchemaValidCtxt* ctxt,\n                                                  xmlSAXHandler** sax,\n                                                  void** data) nogil\n    cdef int xmlSchemaSAXUnplug(xmlSchemaSAXPlugStruct* sax_plug)\n    cdef int xmlSchemaIsValid(xmlSchemaValidCtxt* ctxt)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/xpath.pxd",
    "content": "from lxml.includes cimport tree\nfrom lxml.includes cimport xmlerror\n\nfrom libc.string cimport const_char\nfrom lxml.includes.tree cimport xmlChar, const_xmlChar\n\ncdef extern from \"libxml/xpath.h\":\n    ctypedef enum xmlXPathObjectType:\n        XPATH_UNDEFINED = 0\n        XPATH_NODESET = 1\n        XPATH_BOOLEAN = 2\n        XPATH_NUMBER = 3\n        XPATH_STRING = 4\n        XPATH_POINT = 5\n        XPATH_RANGE = 6\n        XPATH_LOCATIONSET = 7\n        XPATH_USERS = 8\n        XPATH_XSLT_TREE = 9\n\n    ctypedef enum xmlXPathError:\n        XPATH_EXPRESSION_OK = 0\n        XPATH_NUMBER_ERROR = 1\n        XPATH_UNFINISHED_LITERAL_ERROR = 2\n        XPATH_START_LITERAL_ERROR = 3\n        XPATH_VARIABLE_REF_ERROR = 4\n        XPATH_UNDEF_VARIABLE_ERROR = 5\n        XPATH_INVALID_PREDICATE_ERROR = 6\n        XPATH_EXPR_ERROR = 7\n        XPATH_UNCLOSED_ERROR = 8\n        XPATH_UNKNOWN_FUNC_ERROR = 9\n        XPATH_INVALID_OPERAND = 10\n        XPATH_INVALID_TYPE = 11\n        XPATH_INVALID_ARITY = 12\n        XPATH_INVALID_CTXT_SIZE = 13\n        XPATH_INVALID_CTXT_POSITION = 14\n        XPATH_MEMORY_ERROR = 15\n        XPTR_SYNTAX_ERROR = 16\n        XPTR_RESOURCE_ERROR = 17\n        XPTR_SUB_RESOURCE_ERROR = 18\n        XPATH_UNDEF_PREFIX_ERROR = 19\n        XPATH_ENCODING_ERROR = 20\n        XPATH_INVALID_CHAR_ERROR = 21\n        XPATH_INVALID_CTXT = 22\n\n    ctypedef struct xmlNodeSet:\n        int nodeNr\n        int nodeMax\n        tree.xmlNode** nodeTab\n        \n    ctypedef struct xmlXPathObject:\n        xmlXPathObjectType type\n        xmlNodeSet* nodesetval\n        bint boolval\n        double floatval\n        xmlChar* stringval\n\n    ctypedef struct xmlXPathContext:\n        tree.xmlDoc* doc\n        tree.xmlNode* node\n        tree.xmlDict* dict\n        tree.xmlHashTable* nsHash\n        const_xmlChar* function\n        const_xmlChar* functionURI\n        xmlerror.xmlStructuredErrorFunc error\n        xmlerror.xmlError lastError\n        void* userData\n\n    ctypedef struct xmlXPathParserContext:\n        xmlXPathContext* context\n        xmlXPathObject* value\n        tree.xmlNode* ancestor\n        int error\n\n    ctypedef struct xmlXPathCompExpr\n\n    ctypedef void (*xmlXPathFunction)(xmlXPathParserContext* ctxt, int nargs) nogil\n    ctypedef xmlXPathFunction (*xmlXPathFuncLookupFunc)(void* ctxt,\n                                                        const_xmlChar* name,\n                                                        const_xmlChar* ns_uri) nogil\n    \n    cdef xmlXPathContext* xmlXPathNewContext(tree.xmlDoc* doc) nogil\n    cdef xmlXPathObject* xmlXPathEvalExpression(const_xmlChar* str,\n                                                xmlXPathContext* ctxt) nogil\n    cdef xmlXPathObject* xmlXPathCompiledEval(xmlXPathCompExpr* comp,\n                                              xmlXPathContext* ctxt) nogil\n    cdef xmlXPathCompExpr* xmlXPathCompile(const_xmlChar* str) nogil\n    cdef xmlXPathCompExpr* xmlXPathCtxtCompile(xmlXPathContext* ctxt,\n                                               const_xmlChar* str) nogil\n    cdef void xmlXPathFreeContext(xmlXPathContext* ctxt) nogil\n    cdef void xmlXPathFreeCompExpr(xmlXPathCompExpr* comp) nogil\n    cdef void xmlXPathFreeObject(xmlXPathObject* obj) nogil\n    cdef int xmlXPathRegisterNs(xmlXPathContext* ctxt,\n                                const_xmlChar* prefix, const_xmlChar* ns_uri) nogil\n    \n    cdef xmlNodeSet* xmlXPathNodeSetCreate(tree.xmlNode* val) nogil\n    cdef void xmlXPathFreeNodeSet(xmlNodeSet* val) nogil\n\n\ncdef extern from \"libxml/xpathInternals.h\":\n    cdef int xmlXPathRegisterFunc(xmlXPathContext* ctxt,\n                                  const_xmlChar* name,\n                                  xmlXPathFunction f) nogil\n    cdef int xmlXPathRegisterFuncNS(xmlXPathContext* ctxt,\n                                    const_xmlChar* name,\n                                    const_xmlChar* ns_uri,\n                                    xmlXPathFunction f) nogil\n    cdef void xmlXPathRegisterFuncLookup(xmlXPathContext *ctxt,\n                                         xmlXPathFuncLookupFunc f,\n                                         void *funcCtxt) nogil\n    cdef int xmlXPathRegisterVariable(xmlXPathContext *ctxt, \n                                      const_xmlChar* name,\n                                      xmlXPathObject* value) nogil\n    cdef int xmlXPathRegisterVariableNS(xmlXPathContext *ctxt, \n                                        const_xmlChar* name,\n                                        const_xmlChar* ns_uri,\n                                        xmlXPathObject* value) nogil\n    cdef void xmlXPathRegisteredVariablesCleanup(xmlXPathContext *ctxt) nogil\n    cdef void xmlXPathRegisteredNsCleanup(xmlXPathContext *ctxt) nogil\n    cdef xmlXPathObject* valuePop (xmlXPathParserContext *ctxt) nogil\n    cdef int valuePush(xmlXPathParserContext* ctxt, xmlXPathObject *value) nogil\n    \n    cdef xmlXPathObject* xmlXPathNewCString(const_char *val) nogil\n    cdef xmlXPathObject* xmlXPathWrapCString(const_char * val) nogil\n    cdef xmlXPathObject* xmlXPathNewString(const_xmlChar *val) nogil\n    cdef xmlXPathObject* xmlXPathWrapString(const_xmlChar * val) nogil\n    cdef xmlXPathObject* xmlXPathNewFloat(double val) nogil\n    cdef xmlXPathObject* xmlXPathNewBoolean(int val) nogil\n    cdef xmlXPathObject* xmlXPathNewNodeSet(tree.xmlNode* val) nogil\n    cdef xmlXPathObject* xmlXPathNewValueTree(tree.xmlNode* val) nogil\n    cdef void xmlXPathNodeSetAdd(xmlNodeSet* cur,\n                                  tree.xmlNode* val) nogil\n    cdef void xmlXPathNodeSetAddUnique(xmlNodeSet* cur,\n                                        tree.xmlNode* val) nogil\n    cdef xmlXPathObject* xmlXPathWrapNodeSet(xmlNodeSet* val) nogil\n    cdef void xmlXPathErr(xmlXPathParserContext* ctxt, int error) nogil\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/includes/xslt.pxd",
    "content": "from lxml.includes.tree cimport xmlDoc, xmlNode, xmlDict, xmlChar, const_xmlChar, xmlOutputBuffer\nfrom lxml.includes.xmlerror cimport xmlGenericErrorFunc\nfrom lxml.includes.xpath cimport xmlXPathContext, xmlXPathFunction\n\nfrom libc.string cimport const_char\n\ncdef extern from \"libxslt/xslt.h\":\n    cdef int xsltLibxsltVersion\n    cdef int xsltMaxDepth\n\ncdef extern from \"libxslt/xsltconfig.h\":\n    cdef int LIBXSLT_VERSION\n\ncdef extern from \"libxslt/xsltInternals.h\":\n    ctypedef enum xsltTransformState:\n        XSLT_STATE_OK       # 0\n        XSLT_STATE_ERROR    # 1\n        XSLT_STATE_STOPPED  # 2\n\n    ctypedef struct xsltDocument:\n        xmlDoc* doc\n\n    ctypedef struct xsltStylesheet:\n        xmlChar* encoding\n        xmlDoc* doc\n        int errors\n\n    ctypedef struct xsltTransformContext:\n        xsltStylesheet* style\n        xmlXPathContext* xpathCtxt\n        xsltDocument* document\n        void* _private\n        xmlDict* dict\n        int profile\n        xmlNode* node\n        xmlDoc* output\n        xmlNode* insert\n        xmlNode* inst\n        xsltTransformState state\n\n    ctypedef struct xsltStackElem\n\n    ctypedef struct xsltTemplate\n\n    cdef xsltStylesheet* xsltParseStylesheetDoc(xmlDoc* doc) nogil\n    cdef void xsltFreeStylesheet(xsltStylesheet* sheet) nogil\n\ncdef extern from \"libxslt/imports.h\":\n    # actually defined in \"etree_defs.h\"\n    cdef void LXML_GET_XSLT_ENCODING(const_xmlChar* result_var, xsltStylesheet* style)\n\ncdef extern from \"libxslt/extensions.h\":\n    ctypedef void (*xsltTransformFunction)(xsltTransformContext* ctxt,\n                                           xmlNode* context_node,\n                                           xmlNode* inst,\n                                           void* precomp_unused) nogil\n\n    cdef int xsltRegisterExtFunction(xsltTransformContext* ctxt,\n                                     const_xmlChar* name,\n                                     const_xmlChar* URI,\n                                     xmlXPathFunction function) nogil\n    cdef int xsltRegisterExtModuleFunction(const_xmlChar* name, const_xmlChar* URI,\n                                           xmlXPathFunction function) nogil\n    cdef int xsltUnregisterExtModuleFunction(const_xmlChar* name, const_xmlChar* URI)\n    cdef xmlXPathFunction xsltExtModuleFunctionLookup(\n        const_xmlChar* name, const_xmlChar* URI) nogil\n    cdef int xsltRegisterExtPrefix(xsltStylesheet* style, \n                                   const_xmlChar* prefix, const_xmlChar* URI) nogil\n    cdef int xsltRegisterExtElement(xsltTransformContext* ctxt,\n                                    const_xmlChar* name, const_xmlChar* URI,\n                                    xsltTransformFunction function) nogil\n\ncdef extern from \"libxslt/documents.h\":\n    ctypedef enum xsltLoadType:\n        XSLT_LOAD_START\n        XSLT_LOAD_STYLESHEET\n        XSLT_LOAD_DOCUMENT\n\n    ctypedef xmlDoc* (*xsltDocLoaderFunc)(const_xmlChar* URI, xmlDict* dict,\n                                          int options,\n                                          void* ctxt,\n                                          xsltLoadType type) nogil\n    cdef xsltDocLoaderFunc xsltDocDefaultLoader\n    cdef void xsltSetLoaderFunc(xsltDocLoaderFunc f) nogil\n\ncdef extern from \"libxslt/transform.h\":\n    cdef xmlDoc* xsltApplyStylesheet(xsltStylesheet* style, xmlDoc* doc,\n                                     const_char** params) nogil\n    cdef xmlDoc* xsltApplyStylesheetUser(xsltStylesheet* style, xmlDoc* doc,\n                                         const_char** params, const_char* output,\n                                         void* profile,\n                                         xsltTransformContext* context) nogil\n    cdef void xsltProcessOneNode(xsltTransformContext* ctxt,\n                                 xmlNode* contextNode,\n                                 xsltStackElem* params) nogil\n    cdef xsltTransformContext* xsltNewTransformContext(xsltStylesheet* style,\n                                                       xmlDoc* doc) nogil\n    cdef void xsltFreeTransformContext(xsltTransformContext* context) nogil\n    cdef void xsltApplyOneTemplate(xsltTransformContext* ctxt,\n                                   xmlNode* contextNode, xmlNode* list,\n                                   xsltTemplate* templ,\n                                   xsltStackElem* params) nogil\n\n\ncdef extern from \"libxslt/xsltutils.h\":\n    cdef int xsltSaveResultToString(xmlChar** doc_txt_ptr,\n                                    int* doc_txt_len,\n                                    xmlDoc* result,\n                                    xsltStylesheet* style) nogil\n    cdef int xsltSaveResultToFilename(const_char *URL,\n                                      xmlDoc* result,\n                                      xsltStylesheet* style,\n                                      int compression) nogil\n    cdef int xsltSaveResultTo(xmlOutputBuffer* buf,\n                              xmlDoc* result,\n                              xsltStylesheet* style) nogil\n    cdef xmlGenericErrorFunc xsltGenericError\n    cdef void *xsltGenericErrorContext\n    cdef void xsltSetGenericErrorFunc(\n        void* ctxt, void (*handler)(void* ctxt, char* msg, ...)) nogil\n    cdef void xsltSetTransformErrorFunc(\n        xsltTransformContext*, void* ctxt,\n        void (*handler)(void* ctxt, char* msg, ...) nogil) nogil\n    cdef void xsltTransformError(xsltTransformContext* ctxt, \n                                 xsltStylesheet* style, \n                                 xmlNode* node, char* msg, ...)\n    cdef void xsltSetCtxtParseOptions(\n        xsltTransformContext* ctxt, int options)\n\n\ncdef extern from \"libxslt/security.h\":\n    ctypedef struct xsltSecurityPrefs\n    ctypedef enum xsltSecurityOption:\n        XSLT_SECPREF_READ_FILE = 1\n        XSLT_SECPREF_WRITE_FILE = 2\n        XSLT_SECPREF_CREATE_DIRECTORY = 3\n        XSLT_SECPREF_READ_NETWORK = 4\n        XSLT_SECPREF_WRITE_NETWORK = 5\n\n    ctypedef int (*xsltSecurityCheck)(xsltSecurityPrefs* sec,\n                                      xsltTransformContext* ctxt,\n                                      char* value) nogil\n\n    cdef xsltSecurityPrefs* xsltNewSecurityPrefs() nogil\n    cdef void xsltFreeSecurityPrefs(xsltSecurityPrefs* sec) nogil\n    cdef int xsltSecurityForbid(xsltSecurityPrefs* sec,\n                                xsltTransformContext* ctxt,\n                                char* value) nogil\n    cdef int xsltSecurityAllow(xsltSecurityPrefs* sec,\n                                xsltTransformContext* ctxt,\n                                char* value) nogil\n    cdef int xsltSetSecurityPrefs(xsltSecurityPrefs* sec,\n                                  xsltSecurityOption option,\n                                  xsltSecurityCheck func) nogil\n    cdef xsltSecurityCheck xsltGetSecurityPrefs(\n        xsltSecurityPrefs* sec,\n        xsltSecurityOption option) nogil\n    cdef int xsltSetCtxtSecurityPrefs(xsltSecurityPrefs* sec,\n                                      xsltTransformContext* ctxt) nogil\n    cdef xmlDoc* xsltGetProfileInformation(xsltTransformContext* ctxt) nogil\n\ncdef extern from \"libxslt/variables.h\":\n    cdef int xsltQuoteUserParams(xsltTransformContext* ctxt,\n                                 const_char** params)\n    cdef int xsltQuoteOneUserParam(xsltTransformContext* ctxt,\n                                   const_xmlChar* name,\n                                   const_xmlChar* value)\n\ncdef extern from \"libxslt/extra.h\":\n    const_xmlChar* XSLT_LIBXSLT_NAMESPACE\n    const_xmlChar* XSLT_XALAN_NAMESPACE\n    const_xmlChar* XSLT_SAXON_NAMESPACE\n    const_xmlChar* XSLT_XT_NAMESPACE\n\n    cdef xmlXPathFunction xsltFunctionNodeSet\n    cdef void xsltRegisterAllExtras() nogil\n\ncdef extern from \"libexslt/exslt.h\":\n    cdef void exsltRegisterAll() nogil\n\n    # libexslt 1.1.25+\n    const_xmlChar* EXSLT_DATE_NAMESPACE\n    const_xmlChar* EXSLT_SETS_NAMESPACE\n    const_xmlChar* EXSLT_MATH_NAMESPACE\n    const_xmlChar* EXSLT_STRINGS_NAMESPACE\n\n    cdef int exsltDateXpathCtxtRegister(xmlXPathContext* ctxt, const_xmlChar* prefix)\n    cdef int exsltSetsXpathCtxtRegister(xmlXPathContext* ctxt, const_xmlChar* prefix)\n    cdef int exsltMathXpathCtxtRegister(xmlXPathContext* ctxt, const_xmlChar* prefix)\n    cdef int exsltStrXpathCtxtRegister(xmlXPathContext* ctxt, const_xmlChar* prefix)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/isoschematron/__init__.py",
    "content": "\"\"\"The ``lxml.isoschematron`` package implements ISO Schematron support on top\nof the pure-xslt 'skeleton' implementation.\n\"\"\"\n\nimport sys\nimport os.path\nfrom lxml import etree as _etree # due to validator __init__ signature\n\n\n# some compat stuff, borrowed from lxml.html\ntry:\n    unicode\nexcept NameError:\n    # Python 3\n    unicode = str\ntry:\n    basestring\nexcept NameError:\n    # Python 3\n    basestring = str\n\n\n__all__ = ['extract_xsd', 'extract_rng', 'iso_dsdl_include',\n           'iso_abstract_expand', 'iso_svrl_for_xslt1',\n           'svrl_validation_errors', 'schematron_schema_valid',\n           'stylesheet_params', 'Schematron']\n\n\n# some namespaces\n#FIXME: Maybe lxml should provide a dedicated place for common namespace\n#FIXME: definitions?\nXML_SCHEMA_NS = \"http://www.w3.org/2001/XMLSchema\"\nRELAXNG_NS = \"http://relaxng.org/ns/structure/1.0\"\nSCHEMATRON_NS = \"http://purl.oclc.org/dsdl/schematron\"\nSVRL_NS = \"http://purl.oclc.org/dsdl/svrl\"\n\n\n# some helpers\n_schematron_root = '{%s}schema' % SCHEMATRON_NS\n_xml_schema_root = '{%s}schema' % XML_SCHEMA_NS\n_resources_dir = os.path.join(os.path.dirname(__file__), 'resources')\n\n\n# the iso-schematron skeleton implementation steps aka xsl transformations\nextract_xsd = _etree.XSLT(_etree.parse(\n    os.path.join(_resources_dir, 'xsl', 'XSD2Schtrn.xsl')))\nextract_rng = _etree.XSLT(_etree.parse(\n    os.path.join(_resources_dir, 'xsl', 'RNG2Schtrn.xsl')))\niso_dsdl_include = _etree.XSLT(_etree.parse(\n    os.path.join(_resources_dir, 'xsl', 'iso-schematron-xslt1',\n                 'iso_dsdl_include.xsl')))\niso_abstract_expand = _etree.XSLT(_etree.parse(\n    os.path.join(_resources_dir, 'xsl', 'iso-schematron-xslt1',\n                 'iso_abstract_expand.xsl')))\niso_svrl_for_xslt1 = _etree.XSLT(_etree.parse(\n    os.path.join(_resources_dir,\n                 'xsl', 'iso-schematron-xslt1', 'iso_svrl_for_xslt1.xsl')))\n\n\n# svrl result accessors\nsvrl_validation_errors = _etree.XPath(\n    '//svrl:failed-assert', namespaces={'svrl': SVRL_NS})\n\n\n# RelaxNG validator for schematron schemas\nschematron_schema_valid = _etree.RelaxNG(\n    file=os.path.join(_resources_dir, 'rng', 'iso-schematron.rng'))\n\n\ndef stylesheet_params(**kwargs):\n    \"\"\"Convert keyword args to a dictionary of stylesheet parameters.\n    XSL stylesheet parameters must be XPath expressions, i.e.:\n\n    * string expressions, like \"'5'\"\n    * simple (number) expressions, like \"5\"\n    * valid XPath expressions, like \"/a/b/text()\"\n\n    This function converts native Python keyword arguments to stylesheet\n    parameters following these rules:\n    If an arg is a string wrap it with XSLT.strparam().\n    If an arg is an XPath object use its path string.\n    If arg is None raise TypeError.\n    Else convert arg to string.\n    \"\"\"\n    result = {}\n    for key, val in kwargs.items():\n        if isinstance(val, basestring):\n            val = _etree.XSLT.strparam(val)\n        elif val is None:\n            raise TypeError('None not allowed as a stylesheet parameter')\n        elif not isinstance(val, _etree.XPath):\n            val = unicode(val)\n        result[key] = val\n    return result\n\n\n# helper function for use in Schematron __init__\ndef _stylesheet_param_dict(paramsDict, kwargsDict):\n    \"\"\"Return a copy of paramsDict, updated with kwargsDict entries, wrapped as\n    stylesheet arguments.\n    kwargsDict entries with a value of None are ignored.\n    \"\"\"\n    # beware of changing mutable default arg\n    paramsDict = dict(paramsDict)\n    for k, v in kwargsDict.items():\n        if v is not None: # None values do not override\n            paramsDict[k] = v\n    paramsDict = stylesheet_params(**paramsDict)\n    return paramsDict\n\n\nclass Schematron(_etree._Validator):\n    \"\"\"An ISO Schematron validator.\n\n    Pass a root Element or an ElementTree to turn it into a validator.\n    Alternatively, pass a filename as keyword argument 'file' to parse from\n    the file system.\n\n    Schematron is a less well known, but very powerful schema language.\n    The main idea is to use the capabilities of XPath to put restrictions on\n    the structure and the content of XML documents.\n\n    The standard behaviour is to fail on ``failed-assert`` findings only\n    (``ASSERTS_ONLY``).  To change this, you can either pass a report filter\n    function to the ``error_finder`` parameter (e.g. ``ASSERTS_AND_REPORTS``\n    or a custom ``XPath`` object), or subclass isoschematron.Schematron for\n    complete control of the validation process.\n\n    Built on the Schematron language 'reference' skeleton pure-xslt\n    implementation, the validator is created as an XSLT 1.0 stylesheet using\n    these steps:\n\n     0) (Extract from XML Schema or RelaxNG schema)\n     1) Process inclusions\n     2) Process abstract patterns\n     3) Compile the schematron schema to XSLT\n\n    The ``include`` and ``expand`` keyword arguments can be used to switch off\n    steps 1) and 2).\n    To set parameters for steps 1), 2) and 3) hand parameter dictionaries to the\n    keyword arguments ``include_params``, ``expand_params`` or\n    ``compile_params``.\n    For convenience, the compile-step parameter ``phase`` is also exposed as a\n    keyword argument ``phase``. This takes precedence if the parameter is also\n    given in the parameter dictionary.\n\n    If ``store_schematron`` is set to True, the (included-and-expanded)\n    schematron document tree is stored and available through the ``schematron``\n    property.\n    If ``store_xslt`` is set to True, the validation XSLT document tree will be\n    stored and can be retrieved through the ``validator_xslt`` property.\n    With ``store_report`` set to True (default: False), the resulting validation\n    report document gets stored and can be accessed as the ``validation_report``\n    property.\n\n    Here is a usage example::\n\n      >>> from lxml import etree\n      >>> from lxml.isoschematron import Schematron\n\n      >>> schematron = Schematron(etree.XML('''\n      ... <schema xmlns=\"http://purl.oclc.org/dsdl/schematron\" >\n      ...   <pattern id=\"id_only_attribute\">\n      ...     <title>id is the only permitted attribute name</title>\n      ...     <rule context=\"*\">\n      ...       <report test=\"@*[not(name()='id')]\">Attribute\n      ...         <name path=\"@*[not(name()='id')]\"/> is forbidden<name/>\n      ...       </report>\n      ...     </rule>\n      ...   </pattern>\n      ... </schema>'''),\n      ... error_finder=Schematron.ASSERTS_AND_REPORTS)\n\n      >>> xml = etree.XML('''\n      ... <AAA name=\"aaa\">\n      ...   <BBB id=\"bbb\"/>\n      ...   <CCC color=\"ccc\"/>\n      ... </AAA>\n      ... ''')\n\n      >>> schematron.validate(xml)\n      False\n\n      >>> xml = etree.XML('''\n      ... <AAA id=\"aaa\">\n      ...   <BBB id=\"bbb\"/>\n      ...   <CCC/>\n      ... </AAA>\n      ... ''')\n\n      >>> schematron.validate(xml)\n      True\n    \"\"\"\n\n    # libxml2 error categorization for validation errors\n    _domain = _etree.ErrorDomains.SCHEMATRONV\n    _level = _etree.ErrorLevels.ERROR\n    _error_type = _etree.ErrorTypes.SCHEMATRONV_ASSERT\n\n    # convenience definitions for common behaviours\n    ASSERTS_ONLY = svrl_validation_errors  # Default\n    ASSERTS_AND_REPORTS = _etree.XPath(\n        '//svrl:failed-assert | //svrl:successful-report',\n        namespaces={'svrl': SVRL_NS})\n\n    def _extract(self, element):\n        \"\"\"Extract embedded schematron schema from non-schematron host schema.\n        This method will only be called by __init__ if the given schema document\n        is not a schematron schema by itself.\n        Must return a schematron schema document tree or None.\n        \"\"\"\n        schematron = None\n        if element.tag == _xml_schema_root:\n            schematron = self._extract_xsd(element)\n        elif element.nsmap[element.prefix] == RELAXNG_NS:\n            # RelaxNG does not have a single unique root element\n            schematron = self._extract_rng(element)\n        return schematron\n\n    # customization points\n    # etree.XSLT objects that provide the extract, include, expand, compile\n    # steps\n    _extract_xsd = extract_xsd\n    _extract_rng = extract_rng\n    _include = iso_dsdl_include\n    _expand = iso_abstract_expand\n    _compile = iso_svrl_for_xslt1\n\n    # etree.xpath object that determines input document validity when applied to\n    # the svrl result report; must return a list of result elements (empty if\n    # valid)\n    _validation_errors = ASSERTS_ONLY\n\n    def __init__(self, etree=None, file=None, include=True, expand=True,\n                 include_params={}, expand_params={}, compile_params={},\n                 store_schematron=False, store_xslt=False, store_report=False,\n                 phase=None, error_finder=ASSERTS_ONLY):\n        super(Schematron, self).__init__()\n\n        self._store_report = store_report\n        self._schematron = None\n        self._validator_xslt = None\n        self._validation_report = None\n        if error_finder is not self.ASSERTS_ONLY:\n            self._validation_errors = error_finder\n\n        # parse schema document, may be a schematron schema or an XML Schema or\n        # a RelaxNG schema with embedded schematron rules\n        root = None\n        try:\n            if etree is not None:\n                if _etree.iselement(etree):\n                    root = etree\n                else:\n                    root = etree.getroot()\n            elif file is not None:\n                root = _etree.parse(file).getroot()\n        except Exception:\n            raise _etree.SchematronParseError(\n                \"No tree or file given: %s\" % sys.exc_info()[1])\n        if root is None:\n            raise ValueError(\"Empty tree\")\n        if root.tag == _schematron_root:\n            schematron = root\n        else:\n            schematron = self._extract(root)\n        if schematron is None:\n            raise _etree.SchematronParseError(\n                \"Document is not a schematron schema or schematron-extractable\")\n        # perform the iso-schematron skeleton implementation steps to get a\n        # validating xslt\n        if include:\n            schematron = self._include(schematron, **include_params)\n        if expand:\n            schematron = self._expand(schematron, **expand_params)\n        if not schematron_schema_valid(schematron):\n            raise _etree.SchematronParseError(\n                \"invalid schematron schema: %s\" %\n                schematron_schema_valid.error_log)\n        if store_schematron:\n            self._schematron = schematron\n        # add new compile keyword args here if exposing them\n        compile_kwargs = {'phase': phase}\n        compile_params = _stylesheet_param_dict(compile_params, compile_kwargs)\n        validator_xslt = self._compile(schematron, **compile_params)\n        if store_xslt:\n            self._validator_xslt = validator_xslt\n        self._validator = _etree.XSLT(validator_xslt)\n\n    def __call__(self, etree):\n        \"\"\"Validate doc using Schematron.\n\n        Returns true if document is valid, false if not.\n        \"\"\"\n        self._clear_error_log()\n        result = self._validator(etree)\n        if self._store_report:\n            self._validation_report = result\n        errors = self._validation_errors(result)\n        if errors:\n            if _etree.iselement(etree):\n                fname = etree.getroottree().docinfo.URL or '<file>'\n            else:\n                fname = etree.docinfo.URL or '<file>'\n            for error in errors:\n                # Does svrl report the line number, anywhere? Don't think so.\n                self._append_log_message(\n                    domain=self._domain, type=self._error_type,\n                    level=self._level, line=0,\n                    message=_etree.tostring(error, encoding='unicode'),\n                    filename=fname)\n            return False\n        return True\n\n    @property\n    def schematron(self):\n        \"\"\"ISO-schematron schema document (None if object has been initialized\n        with store_schematron=False).\n        \"\"\"\n        return self._schematron\n\n    @property\n    def validator_xslt(self):\n        \"\"\"ISO-schematron skeleton implementation XSLT validator document (None\n        if object has been initialized with store_xslt=False).\n        \"\"\"\n        return self._validator_xslt\n\n    @property\n    def validation_report(self):\n        \"\"\"ISO-schematron validation result report (None if result-storing has\n        been turned off).\n        \"\"\"\n        return self._validation_report\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/isoschematron/resources/rng/iso-schematron.rng",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!-- Copyright © ISO/IEC 2015 -->\n<!--\n  The following permission notice and disclaimer shall be included in all\n  copies of this XML schema (\"the Schema\"), and derivations of the Schema:\n  \n  Permission is hereby granted, free of charge in perpetuity, to any\n  person obtaining a copy of the Schema, to use, copy, modify, merge and\n  distribute free of charge, copies of the Schema for the purposes of\n  developing, implementing, installing and using software based on the\n  Schema, and to permit persons to whom the Schema is furnished to do so,\n  subject to the following conditions:\n  \n  THE SCHEMA IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL\n  THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR\n  OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,\n  ARISING FROM, OUT OF OR IN CONNECTION WITH THE SCHEMA OR THE USE OR\n  OTHER DEALINGS IN THE SCHEMA.\n  \n  In addition, any modified copy of the Schema shall include the following\n  notice:\n  \n  \"THIS SCHEMA HAS BEEN MODIFIED FROM THE SCHEMA DEFINED IN ISO/IEC 19757-3,\n  AND SHOULD NOT BE INTERPRETED AS COMPLYING WITH THAT STANDARD\".\n-->\n<grammar ns=\"http://purl.oclc.org/dsdl/schematron\" xmlns=\"http://relaxng.org/ns/structure/1.0\" datatypeLibrary=\"http://www.w3.org/2001/XMLSchema-datatypes\">\n  <start>\n    <ref name=\"schema\"/>\n  </start>\n  <!-- Element declarations -->\n  <define name=\"schema\">\n    <element name=\"schema\">\n      <optional>\n        <attribute name=\"id\">\n          <data type=\"ID\"/>\n        </attribute>\n      </optional>\n      <ref name=\"rich\"/>\n      <optional>\n        <attribute name=\"schemaVersion\">\n          <ref name=\"non-empty-string\"/>\n        </attribute>\n      </optional>\n      <optional>\n        <attribute name=\"defaultPhase\">\n          <data type=\"IDREF\"/>\n        </attribute>\n      </optional>\n      <optional>\n        <attribute name=\"queryBinding\">\n          <ref name=\"non-empty-string\"/>\n        </attribute>\n      </optional>\n      <interleave>\n        <ref name=\"foreign\"/>\n        <zeroOrMore>\n          <ref name=\"inclusion\"/>\n        </zeroOrMore>\n        <group>\n          <optional>\n            <ref name=\"title\"/>\n          </optional>\n          <zeroOrMore>\n            <ref name=\"ns\"/>\n          </zeroOrMore>\n          <zeroOrMore>\n            <ref name=\"p\"/>\n          </zeroOrMore>\n          <zeroOrMore>\n            <ref name=\"let\"/>\n          </zeroOrMore>\n          <zeroOrMore>\n            <ref name=\"phase\"/>\n          </zeroOrMore>\n          <oneOrMore>\n            <ref name=\"pattern\"/>\n          </oneOrMore>\n          <zeroOrMore>\n            <ref name=\"p\"/>\n          </zeroOrMore>\n          <optional>\n            <ref name=\"diagnostics\"/>\n          </optional>\n          <optional>\n            <!-- edited (lxml): required in standard, optional here (since it can be empty anyway) -->\n            <ref name=\"properties\"/>\n          </optional>\n        </group>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"active\">\n    <element name=\"active\">\n      <attribute name=\"pattern\">\n        <data type=\"IDREF\"/>\n      </attribute>\n      <interleave>\n        <ref name=\"foreign\"/>\n        <zeroOrMore>\n          <choice>\n            <text/>\n            <ref name=\"dir\"/>\n            <ref name=\"emph\"/>\n            <ref name=\"span\"/>\n          </choice>\n        </zeroOrMore>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"assert\">\n    <element name=\"assert\">\n      <attribute name=\"test\">\n        <ref name=\"exprValue\"/>\n      </attribute>\n      <optional>\n        <attribute name=\"flag\">\n          <ref name=\"flagValue\"/>\n        </attribute>\n      </optional>\n      <optional>\n        <attribute name=\"id\">\n          <data type=\"ID\"/>\n        </attribute>\n      </optional>\n      <optional>\n        <attribute name=\"diagnostics\">\n          <data type=\"IDREFS\"/>\n        </attribute>\n      </optional>\n      <optional>\n        <attribute name=\"properties\">\n          <data type=\"IDREFS\"/>\n        </attribute>\n      </optional>\n      <ref name=\"rich\"/>\n      <ref name=\"linkable\"/>\n      <interleave>\n        <ref name=\"foreign\"/>\n        <zeroOrMore>\n          <choice>\n            <text/>\n            <ref name=\"name\"/>\n            <ref name=\"value-of\"/>\n            <ref name=\"emph\"/>\n            <ref name=\"dir\"/>\n            <ref name=\"span\"/>\n          </choice>\n        </zeroOrMore>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"diagnostic\">\n    <element name=\"diagnostic\">\n      <attribute name=\"id\">\n        <data type=\"ID\"/>\n      </attribute>\n      <ref name=\"rich\"/>\n      <interleave>\n        <ref name=\"foreign\"/>\n        <zeroOrMore>\n          <choice>\n            <text/>\n            <ref name=\"value-of\"/>\n            <ref name=\"emph\"/>\n            <ref name=\"dir\"/>\n            <ref name=\"span\"/>\n          </choice>\n        </zeroOrMore>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"diagnostics\">\n    <element name=\"diagnostics\">\n      <interleave>\n        <ref name=\"foreign\"/>\n        <zeroOrMore>\n          <ref name=\"inclusion\"/>\n        </zeroOrMore>\n        <zeroOrMore>\n          <ref name=\"diagnostic\"/>\n        </zeroOrMore>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"dir\">\n    <element name=\"dir\">\n      <optional>\n        <attribute name=\"value\">\n          <choice>\n            <value>ltr</value>\n            <value>rtl</value>\n          </choice>\n        </attribute>\n      </optional>\n      <interleave>\n        <ref name=\"foreign\"/>\n        <text/>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"emph\">\n    <element name=\"emph\">\n      <text/>\n    </element>\n  </define>\n  <define name=\"extends\">\n    <element name=\"extends\">\n      <choice>\n        <attribute name=\"rule\">\n          <data type=\"IDREF\"/>\n        </attribute>\n        <attribute name=\"href\">\n          <ref name=\"uriValue\"/>\n        </attribute>\n      </choice>\n      <ref name=\"foreign-empty\"/>\n    </element>\n  </define>\n  <define name=\"let\">\n    <element name=\"let\">\n      <attribute name=\"name\">\n        <ref name=\"nameValue\"/>\n      </attribute>\n      <choice>\n        <attribute name=\"value\">\n          <data type=\"string\" datatypeLibrary=\"\"/>\n        </attribute>\n        <oneOrMore>\n          <ref name=\"foreign-element\"/>\n        </oneOrMore>\n      </choice>\n    </element>\n  </define>\n  <define name=\"name\">\n    <element name=\"name\">\n      <optional>\n        <attribute name=\"path\">\n          <ref name=\"pathValue\"/>\n        </attribute>\n      </optional>\n      <ref name=\"foreign-empty\"/>\n    </element>\n  </define>\n  <define name=\"ns\">\n    <element name=\"ns\">\n      <attribute name=\"uri\">\n        <ref name=\"uriValue\"/>\n      </attribute>\n      <attribute name=\"prefix\">\n        <ref name=\"nameValue\"/>\n      </attribute>\n      <ref name=\"foreign-empty\"/>\n    </element>\n  </define>\n  <define name=\"p\">\n    <element name=\"p\">\n      <optional>\n        <attribute name=\"id\">\n          <data type=\"ID\"/>\n        </attribute>\n      </optional>\n      <optional>\n        <attribute name=\"class\">\n          <ref name=\"classValue\"/>\n        </attribute>\n      </optional>\n      <optional>\n        <attribute name=\"icon\">\n          <ref name=\"uriValue\"/>\n        </attribute>\n      </optional>\n      <interleave>\n        <ref name=\"foreign\"/>\n        <zeroOrMore>\n          <choice>\n            <text/>\n            <ref name=\"dir\"/>\n            <ref name=\"emph\"/>\n            <ref name=\"span\"/>\n          </choice>\n        </zeroOrMore>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"param\">\n    <element name=\"param\">\n      <attribute name=\"name\">\n        <ref name=\"nameValue\"/>\n      </attribute>\n      <attribute name=\"value\">\n        <ref name=\"non-empty-string\"/>\n      </attribute>\n    </element>\n  </define>\n  <define name=\"pattern\">\n    <element name=\"pattern\">\n      <optional>\n        <attribute name=\"documents\">\n          <ref name=\"pathValue\"/>\n        </attribute>\n      </optional>\n      <ref name=\"rich\"/>\n      <interleave>\n        <ref name=\"foreign\"/>\n        <zeroOrMore>\n          <ref name=\"inclusion\"/>\n        </zeroOrMore>\n        <choice>\n          <group>\n            <attribute name=\"abstract\">\n              <value>true</value>\n            </attribute>\n            <attribute name=\"id\">\n              <data type=\"ID\"/>\n            </attribute>\n            <optional>\n              <ref name=\"title\"/>\n            </optional>\n            <group>\n              <zeroOrMore>\n                <ref name=\"p\"/>\n              </zeroOrMore>\n              <zeroOrMore>\n                <ref name=\"let\"/>\n              </zeroOrMore>\n              <zeroOrMore>\n                <ref name=\"rule\"/>\n              </zeroOrMore>\n            </group>\n          </group>\n          <group>\n            <optional>\n              <attribute name=\"abstract\">\n                <value>false</value>\n              </attribute>\n            </optional>\n            <optional>\n              <attribute name=\"id\">\n                <data type=\"ID\"/>\n              </attribute>\n            </optional>\n            <optional>\n              <ref name=\"title\"/>\n            </optional>\n            <group>\n              <zeroOrMore>\n                <ref name=\"p\"/>\n              </zeroOrMore>\n              <zeroOrMore>\n                <ref name=\"let\"/>\n              </zeroOrMore>\n              <zeroOrMore>\n                <ref name=\"rule\"/>\n              </zeroOrMore>\n            </group>\n          </group>\n          <group>\n            <optional>\n              <attribute name=\"abstract\">\n                <value>false</value>\n              </attribute>\n            </optional>\n            <attribute name=\"is-a\">\n              <data type=\"IDREF\"/>\n            </attribute>\n            <optional>\n              <attribute name=\"id\">\n                <data type=\"ID\"/>\n              </attribute>\n            </optional>\n            <optional>\n              <ref name=\"title\"/>\n            </optional>\n            <group>\n              <zeroOrMore>\n                <ref name=\"p\"/>\n              </zeroOrMore>\n              <zeroOrMore>\n                <ref name=\"param\"/>\n              </zeroOrMore>\n            </group>\n          </group>\n        </choice>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"phase\">\n    <element name=\"phase\">\n      <attribute name=\"id\">\n        <data type=\"ID\"/>\n      </attribute>\n      <ref name=\"rich\"/>\n      <interleave>\n        <ref name=\"foreign\"/>\n        <zeroOrMore>\n          <ref name=\"inclusion\"/>\n        </zeroOrMore>\n        <group>\n          <zeroOrMore>\n            <ref name=\"p\"/>\n          </zeroOrMore>\n          <zeroOrMore>\n            <ref name=\"let\"/>\n          </zeroOrMore>\n          <zeroOrMore>\n            <ref name=\"active\"/>\n          </zeroOrMore>\n        </group>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"properties\">\n    <element name=\"properties\">\n      <zeroOrMore>\n        <ref name=\"property\"/>\n      </zeroOrMore>\n    </element>\n  </define>\n  <define name=\"property\">\n    <element name=\"property\">\n      <attribute name=\"id\">\n        <data type=\"ID\"/>\n      </attribute>\n      <optional>\n        <attribute name=\"role\">\n          <ref name=\"roleValue\"/>\n        </attribute>\n      </optional>\n      <optional>\n        <attribute name=\"scheme\"/>\n      </optional>\n      <interleave>\n        <ref name=\"foreign\"/>\n        <zeroOrMore>\n          <choice>\n            <text/>\n            <ref name=\"name\"/>\n            <ref name=\"value-of\"/>\n            <ref name=\"emph\"/>\n            <ref name=\"dir\"/>\n            <ref name=\"span\"/>\n          </choice>\n        </zeroOrMore>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"report\">\n    <element name=\"report\">\n      <attribute name=\"test\">\n        <ref name=\"exprValue\"/>\n      </attribute>\n      <optional>\n        <attribute name=\"flag\">\n          <ref name=\"flagValue\"/>\n        </attribute>\n      </optional>\n      <optional>\n        <attribute name=\"id\">\n          <data type=\"ID\"/>\n        </attribute>\n      </optional>\n      <optional>\n        <attribute name=\"diagnostics\">\n          <data type=\"IDREFS\"/>\n        </attribute>\n      </optional>\n      <optional>\n        <attribute name=\"properties\">\n          <data type=\"IDREFS\"/>\n        </attribute>\n      </optional>\n      <ref name=\"rich\"/>\n      <ref name=\"linkable\"/>\n      <interleave>\n        <ref name=\"foreign\"/>\n        <zeroOrMore>\n          <choice>\n            <text/>\n            <ref name=\"name\"/>\n            <ref name=\"value-of\"/>\n            <ref name=\"emph\"/>\n            <ref name=\"dir\"/>\n            <ref name=\"span\"/>\n          </choice>\n        </zeroOrMore>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"rule\">\n    <element name=\"rule\">\n      <optional>\n        <attribute name=\"flag\">\n          <ref name=\"flagValue\"/>\n        </attribute>\n      </optional>\n      <ref name=\"rich\"/>\n      <ref name=\"linkable\"/>\n      <interleave>\n        <ref name=\"foreign\"/>\n        <zeroOrMore>\n          <ref name=\"inclusion\"/>\n        </zeroOrMore>\n        <choice>\n          <group>\n            <attribute name=\"abstract\">\n              <value>true</value>\n            </attribute>\n            <attribute name=\"id\">\n              <data type=\"ID\"/>\n            </attribute>\n            <zeroOrMore>\n              <ref name=\"let\"/>\n            </zeroOrMore>\n            <oneOrMore>\n              <choice>\n                <ref name=\"assert\"/>\n                <ref name=\"report\"/>\n                <ref name=\"extends\"/>\n                <ref name=\"p\"/>\n              </choice>\n            </oneOrMore>\n          </group>\n          <group>\n            <attribute name=\"context\">\n              <ref name=\"pathValue\"/>\n            </attribute>\n            <optional>\n              <attribute name=\"id\">\n                <data type=\"ID\"/>\n              </attribute>\n            </optional>\n            <optional>\n              <attribute name=\"abstract\">\n                <value>false</value>\n              </attribute>\n            </optional>\n            <zeroOrMore>\n              <ref name=\"let\"/>\n            </zeroOrMore>\n            <oneOrMore>\n              <choice>\n                <ref name=\"assert\"/>\n                <ref name=\"report\"/>\n                <ref name=\"extends\"/>\n                <ref name=\"p\"/>\n              </choice>\n            </oneOrMore>\n          </group>\n        </choice>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"span\">\n    <element name=\"span\">\n      <attribute name=\"class\">\n        <ref name=\"classValue\"/>\n      </attribute>\n      <interleave>\n        <ref name=\"foreign\"/>\n        <text/>\n      </interleave>\n    </element>\n  </define>\n  <define name=\"title\">\n    <element name=\"title\">\n      <zeroOrMore>\n        <choice>\n          <text/>\n          <ref name=\"dir\"/>\n        </choice>\n      </zeroOrMore>\n    </element>\n  </define>\n  <define name=\"value-of\">\n    <element name=\"value-of\">\n      <attribute name=\"select\">\n        <ref name=\"pathValue\"/>\n      </attribute>\n      <ref name=\"foreign-empty\"/>\n    </element>\n  </define>\n  <!-- common declarations -->\n  <define name=\"inclusion\">\n    <element name=\"include\">\n      <attribute name=\"href\">\n        <ref name=\"uriValue\"/>\n      </attribute>\n      <ref name=\"foreign-empty\"/>\n    </element>\n  </define>\n  <define name=\"rich\">\n    <optional>\n      <attribute name=\"icon\">\n        <ref name=\"uriValue\"/>\n      </attribute>\n    </optional>\n    <optional>\n      <attribute name=\"see\">\n        <ref name=\"uriValue\"/>\n      </attribute>\n    </optional>\n    <optional>\n      <attribute name=\"fpi\">\n        <ref name=\"fpiValue\"/>\n      </attribute>\n    </optional>\n    <optional>\n      <attribute name=\"xml:lang\">\n        <ref name=\"langValue\"/>\n      </attribute>\n    </optional>\n    <optional>\n      <attribute name=\"xml:space\">\n        <choice>\n          <value>preserve</value>\n          <value>default</value>\n        </choice>\n      </attribute>\n    </optional>\n  </define>\n  <define name=\"linkable\">\n    <optional>\n      <attribute name=\"role\">\n        <ref name=\"roleValue\"/>\n      </attribute>\n    </optional>\n    <optional>\n      <attribute name=\"subject\">\n        <ref name=\"pathValue\"/>\n      </attribute>\n    </optional>\n  </define>\n  <define name=\"foreign\">\n    <ref name=\"foreign-attributes\"/>\n    <zeroOrMore>\n      <ref name=\"foreign-element\"/>\n    </zeroOrMore>\n  </define>\n  <define name=\"foreign-empty\">\n    <ref name=\"foreign-attributes\"/>\n  </define>\n  <define name=\"foreign-attributes\">\n    <zeroOrMore>\n      <attribute>\n        <anyName>\n          <except>\n            <nsName ns=\"\"/>\n            <nsName ns=\"http://www.w3.org/XML/1998/namespace\"/>\n          </except>\n        </anyName>\n      </attribute>\n    </zeroOrMore>\n  </define>\n  <define name=\"foreign-element\">\n    <element>\n      <anyName>\n        <except>\n          <nsName/>\n        </except>\n      </anyName>\n      <zeroOrMore>\n        <choice>\n          <attribute>\n            <anyName/>\n          </attribute>\n          <ref name=\"foreign-element\"/>\n          <ref name=\"schema\"/>\n          <text/>\n        </choice>\n      </zeroOrMore>\n    </element>\n  </define>\n  <!-- Data types -->\n  <define name=\"uriValue\">\n    <data type=\"anyURI\"/>\n  </define>\n  <define name=\"pathValue\">\n    <data type=\"string\" datatypeLibrary=\"\"/>\n  </define>\n  <define name=\"exprValue\">\n    <data type=\"string\" datatypeLibrary=\"\"/>\n  </define>\n  <define name=\"fpiValue\">\n    <data type=\"string\" datatypeLibrary=\"\"/>\n  </define>\n  <define name=\"langValue\">\n    <data type=\"language\"/>\n  </define>\n  <define name=\"roleValue\">\n    <data type=\"string\" datatypeLibrary=\"\"/>\n  </define>\n  <define name=\"flagValue\">\n    <data type=\"string\" datatypeLibrary=\"\"/>\n  </define>\n  <define name=\"nameValue\">\n    <data type=\"string\" datatypeLibrary=\"\"/>\n  </define>\n  <!-- In the default query language binding, xsd:NCNAME -->\n  <define name=\"classValue\">\n    <data type=\"string\" datatypeLibrary=\"\"/>\n  </define>\n  <define name=\"non-empty-string\">\n    <data type=\"token\">\n      <param name=\"minLength\">1</param>\n    </data>\n  </define>\n</grammar>\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/isoschematron/resources/xsl/RNG2Schtrn.xsl",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!--\n\tStylesheet for extracting Schematron information from a RELAX-NG schema.\n\tBased on the stylesheet for extracting Schematron information from W3C XML Schema.\n\tCreated by Eddie Robertsson 2002/06/01\n        2009/12/10      hj: changed Schematron namespace to ISO URI (Holger Joukl)\n-->\n<xsl:transform version=\"1.0\" xmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\" \nxmlns:sch=\"http://purl.oclc.org/dsdl/schematron\" xmlns:rng=\"http://relaxng.org/ns/structure/1.0\">\n\t<!-- Set the output to be XML with an XML declaration and use indentation -->\n\t<xsl:output method=\"xml\" omit-xml-declaration=\"no\" indent=\"yes\" standalone=\"yes\"/>\n\t<!-- -->\n\t<!-- match schema and call recursive template to extract included schemas -->\n\t<!-- -->\n\t<xsl:template match=\"/rng:grammar | /rng:element\">\n\t\t<!-- call the schema definition template ... -->\n\t\t<xsl:call-template name=\"gatherSchema\">\n\t\t\t<!-- ... with current node as the $schemas parameter ... -->\n\t\t\t<xsl:with-param name=\"schemas\" select=\".\"/>\n\t\t\t<!-- ... and any includes in the $include parameter -->\n\t\t\t<xsl:with-param name=\"includes\" select=\"document(/rng:grammar/rng:include/@href\n| //rng:externalRef/@href)\"/>\n\t\t</xsl:call-template>\n\t</xsl:template>\n\t<!-- -->\n\t<!-- gather all included schemas into a single parameter variable -->\n\t<!-- -->\n\t<xsl:template name=\"gatherSchema\">\n\t\t<xsl:param name=\"schemas\"/>\n\t\t<xsl:param name=\"includes\"/>\n\t\t<xsl:choose>\n\t\t\t<xsl:when test=\"count($schemas) &lt; count($schemas | $includes)\">\n\t\t\t\t<!-- when $includes includes something new, recurse ... -->\n\t\t\t\t<xsl:call-template name=\"gatherSchema\">\n\t\t\t\t\t<!-- ... with current $includes added to the $schemas parameter ... -->\n\t\t\t\t\t<xsl:with-param name=\"schemas\" select=\"$schemas | $includes\"/>\n\t\t\t\t\t<!-- ... and any *new* includes in the $include parameter -->\n\t\t\t\t\t<xsl:with-param name=\"includes\" select=\"document($includes/rng:grammar/rng:include/@href\n| $includes//rng:externalRef/@href)\"/>\n\t\t\t\t</xsl:call-template>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise>\n\t\t\t\t<!-- we have the complete set of included schemas, so now let's output the embedded schematron -->\n\t\t\t\t<xsl:call-template name=\"output\">\n\t\t\t\t\t<xsl:with-param name=\"schemas\" select=\"$schemas\"/>\n\t\t\t\t</xsl:call-template>\n\t\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\t</xsl:template>\n\t<!-- -->\n\t<!-- output the schematron information -->\n\t<!-- -->\n\t<xsl:template name=\"output\">\n\t\t<xsl:param name=\"schemas\"/>\n\t\t<!-- -->\n\t\t<sch:schema>\n\t\t\t<!-- get header-type elements - eg title and especially ns -->\n\t\t\t<!-- title (just one) -->\n\t\t\t<xsl:copy-of select=\"$schemas//sch:title[1]\"/>\n\t\t\t<!-- get remaining schematron schema children -->\n\t\t\t<!-- get non-blank namespace elements, dropping duplicates -->\n\t\t\t<xsl:for-each select=\"$schemas//sch:ns\">\n\t\t\t\t<xsl:if test=\"generate-id(.) = generate-id($schemas//sch:ns[@prefix = current()/@prefix][1])\">\n\t\t\t\t\t<xsl:copy-of select=\".\"/>\n\t\t\t\t</xsl:if>\n\t\t\t</xsl:for-each>\n\t\t\t<xsl:copy-of select=\"$schemas//sch:phase\"/>\n\t\t\t<xsl:copy-of select=\"$schemas//sch:pattern\"/>\n\t\t\t<sch:diagnostics>\n\t\t\t\t<xsl:copy-of select=\"$schemas//sch:diagnostics/*\"/>\n\t\t\t</sch:diagnostics>\n\t\t</sch:schema>\n\t</xsl:template>\n\t<!-- -->\n</xsl:transform>\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/isoschematron/resources/xsl/XSD2Schtrn.xsl",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\r\n<!--\r\n        based on an original transform by Eddie Robertsson\r\n        2001/04/21      fn: added support for included schemas\r\n        2001/06/27      er: changed XMl Schema prefix from xsd: to xs: and changed to the Rec namespace\r\n        2009/12/10      hj: changed Schematron namespace to ISO URI (Holger Joukl)\r\n-->\r\n<xsl:transform version=\"1.0\" xmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\" \r\nxmlns:sch=\"http://purl.oclc.org/dsdl/schematron\" xmlns:xs=\"http://www.w3.org/2001/XMLSchema\">\r\n        <!-- Set the output to be XML with an XML declaration and use indentation -->\r\n        <xsl:output method=\"xml\" omit-xml-declaration=\"no\" indent=\"yes\" standalone=\"yes\"/>\r\n        <!-- -->\r\n        <!-- match schema and call recursive template to extract included schemas -->\r\n        <!-- -->\r\n        <xsl:template match=\"xs:schema\">\r\n                <!-- call the schema definition template ... -->\r\n                <xsl:call-template name=\"gatherSchema\">\r\n                        <!-- ... with current current root as the $schemas parameter ... -->\r\n                        <xsl:with-param name=\"schemas\" select=\"/\"/>\r\n                        <!-- ... and any includes in the $include parameter -->\r\n                        <xsl:with-param name=\"includes\" \r\n\t\t\t\t\t\tselect=\"document(/xs:schema/xs:*[self::xs:include or self::xs:import or self::xs:redefine]/@schemaLocation)\"/>\r\n                </xsl:call-template>\r\n        </xsl:template>\r\n        <!-- -->\r\n        <!-- gather all included schemas into a single parameter variable -->\r\n        <!-- -->\r\n        <xsl:template name=\"gatherSchema\">\r\n                <xsl:param name=\"schemas\"/>\r\n                <xsl:param name=\"includes\"/>\r\n                <xsl:choose>\r\n                        <xsl:when test=\"count($schemas) &lt; count($schemas | $includes)\">\r\n                                <!-- when $includes includes something new, recurse ... -->\r\n                                <xsl:call-template name=\"gatherSchema\">\r\n                                        <!-- ... with current $includes added to the $schemas parameter ... -->\r\n                                        <xsl:with-param name=\"schemas\" select=\"$schemas | $includes\"/>\r\n                                        <!-- ... and any *new* includes in the $include parameter -->\r\n                                        <xsl:with-param name=\"includes\" \r\n\t\t\t\t\t\t\t\t\t\tselect=\"document($includes/xs:schema/xs:*[self::xs:include or self::xs:import or self::xs:redefine]/@schemaLocation)\"/>\r\n                                </xsl:call-template>\r\n                        </xsl:when>\r\n                        <xsl:otherwise>\r\n                                <!-- we have the complete set of included schemas, \r\n\t\t\t\t\t\t\t\tso now let's output the embedded schematron -->\r\n                                <xsl:call-template name=\"output\">\r\n                                        <xsl:with-param name=\"schemas\" select=\"$schemas\"/>\r\n                                </xsl:call-template>\r\n                        </xsl:otherwise>\r\n                </xsl:choose>\r\n        </xsl:template>\r\n        <!-- -->\r\n        <!-- output the schematron information -->\r\n        <!-- -->\r\n        <xsl:template name=\"output\">\r\n                <xsl:param name=\"schemas\"/>\r\n                <!-- -->\r\n                <sch:schema>\r\n                        <!-- get header-type elements - eg title and especially ns -->\r\n                        <!-- title (just one) -->\r\n                        <xsl:copy-of select=\"$schemas//xs:appinfo/sch:title[1]\"/>\r\n                        <!-- get remaining schematron schema children -->\r\n                        <!-- get non-blank namespace elements, dropping duplicates -->\r\n                        <xsl:for-each select=\"$schemas//xs:appinfo/sch:ns\">\r\n                                <xsl:if test=\"generate-id(.) = \r\n\t\t\t\t\t\t\t\tgenerate-id($schemas//xs:appinfo/sch:ns[@prefix = current()/@prefix][1])\">\r\n                                        <xsl:copy-of select=\".\"/>\r\n                                </xsl:if>\r\n                        </xsl:for-each>\r\n                        <xsl:copy-of select=\"$schemas//xs:appinfo/sch:phase\"/>\r\n                        <xsl:copy-of select=\"$schemas//xs:appinfo/sch:pattern\"/>\r\n                        <sch:diagnostics>\r\n                                <xsl:copy-of select=\"$schemas//xs:appinfo/sch:diagnostics/*\"/>\r\n                        </sch:diagnostics>\r\n                </sch:schema>\r\n        </xsl:template>\r\n        <!-- -->\r\n</xsl:transform>\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/isoschematron/resources/xsl/iso-schematron-xslt1/iso_abstract_expand.xsl",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?><?xar XSLT?>\n\n<!-- \n     OVERVIEW - iso_abstract_expand.xsl\n     \n\t    This is a preprocessor for ISO Schematron, which implements abstract patterns. \n\t    It also \n\t       \t* extracts a particular schema using an ID, where there are multiple \n             schemas, such as when they are embedded in the same NVDL script \n           * allows parameter substitution inside @context, @test, @select, @path\n\t    \t   * experimentally, allows parameter recognition and substitution inside\n             text (NOTE: to be removed, for compataibility with other implementations,   \n             please do not use this) \n\t\t\n\t\tThis should be used after iso-dsdl-include.xsl and before the skeleton or\n\t\tmeta-stylesheet (e.g. iso-svrl.xsl) . It only requires XSLT 1.\n\t\t \n\t\tEach kind of inclusion can be turned off (or on) on the command line.\n\t\t \n-->\n\n<!--\nOpen Source Initiative OSI - The MIT License:Licensing\n[OSI Approved License]\n\nThis source code was previously available under the zlib/libpng license. \nAttribution is polite.\n\nThe MIT License\n\nCopyright (c) 2004-2010  Rick Jellife and Academia Sinica Computing Centre, Taiwan\n\nPermission is hereby granted, free of charge, to any person obtaining a copy\nof this software and associated documentation files (the \"Software\"), to deal\nin the Software without restriction, including without limitation the rights\nto use, copy, modify, merge, publish, distribute, sublicense, and/or sell\ncopies of the Software, and to permit persons to whom the Software is\nfurnished to do so, subject to the following conditions:\n\nThe above copyright notice and this permission notice shall be included in\nall copies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\nIMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\nFITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\nAUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\nLIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\nOUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN\nTHE SOFTWARE.\n-->\n\n<!--\nVERSION INFORMATION\n  2013-09-19 RJ\n     * Allow macro expansion in  @path attributes, eg. for   sch:name/@path\n\n  2010-07-10 RJ\n  \t\t* Move to MIT license\n  \t\t\n  2008-09-18 RJ\n  \t\t* move out param test from iso:schema template  to work with XSLT 1. (Noah Fontes)\n  \t\t\n  2008-07-29 RJ \n  \t\t* Create.  Pull out as distinct XSL in its own namespace from old iso_pre_pro.xsl\n  \t\t* Put everything in private namespace\n  \t\t* Rewrite replace_substring named template so that copyright is clear\n  \t\n  2008-07-24 RJ\n       * correct abstract patterns so for correct names: param/@name and\n     param/@value\n    \n  2007-01-12  RJ \n     * Use ISO namespace\n     * Use pattern/@id not  pattern/@name \n     * Add Oliver Becker's suggests from old Schematron-love-in list for <copy> \n     * Add XT -ism?\n  2003 RJ\n     * Original written for old namespace\n     * http://www.topologi.com/resources/iso-pre-pro.xsl\n-->\t\n<xslt:stylesheet version=\"1.0\" xmlns:xslt=\"http://www.w3.org/1999/XSL/Transform\" \n\txmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\" \n    xmlns:iso=\"http://purl.oclc.org/dsdl/schematron\"  \n    xmlns:nvdl=\"http://purl.oclc.org/dsdl/nvdl\"  \n    \n    xmlns:iae=\"http://www.schematron.com/namespace/iae\" \n     \n      >\n\t\n\t<xslt:param name=\"schema-id\"></xslt:param>\n\t\n\t\n\t<!-- Driver for the mode -->\n\t<xsl:template match=\"/\">\n  \t\t<xsl:apply-templates select=\".\" mode=\"iae:go\" />\n\t</xsl:template> \n\t\n\t\n\t<!-- ================================================================================== -->\n\t<!-- Normal processing rules                                                            -->\n\t<!-- ================================================================================== -->\n\t<!-- Output only the selected schema --> \n\t<xslt:template match=\"iso:schema\" >\n\t    <xsl:if test=\"string-length($schema-id) =0 or @id= $schema-id \">\n\t    \t<xslt:copy>\n\t\t\t\t<xslt:copy-of select=\"@*\" />\n\t\t\t\t<xslt:apply-templates  mode=\"iae:go\" /> \n\t\t\t</xslt:copy>\n\t\t</xsl:if>\n\t</xslt:template>\n\t\n \n\t<!-- Strip out any foreign elements above the Schematron schema .\n\t\t-->\n\t<xslt:template match=\"*[not(ancestor-or-self::iso:*)]\"     mode=\"iae:go\"  >\n\t   <xslt:apply-templates  mode=\"iae:go\" />\n\t</xslt:template>\n\t   \n\t\n\t<!-- ================================================================================== -->\n\t<!-- Handle Schematron abstract pattern preprocessing                                   -->\n\t<!-- abstract-to-real calls\n\t\t\tdo-pattern calls \n\t\t\t\tmacro-expand calls \n\t\t\t\t\tmulti-macro-expand\n\t\t\t\t\t\treplace-substring                                                   -->\n\t<!-- ================================================================================== -->\n\t\n\t<!--\n\t\tAbstract patterns allow you to say, for example\n\t\t\n\t\t<pattern name=\"htmlTable\" is-a=\"table\">\n\t\t\t<param name=\"row\" value=\"html:tr\"/>\n\t\t\t<param name=\"cell\" value=\"html:td\" />\n\t\t\t<param name=\"table\" value=\"html:table\" />\n\t\t</pattern>\n\t\t\n\t\tFor a good introduction, see Uche Ogbujii's article for IBM DeveloperWorks\n\t\t\"Discover the flexibility of Schematron abstract patterns\"\n\t\t  http://www-128.ibm.com/developerworks/xml/library/x-stron.html\n\t\tHowever, note that ISO Schematron uses @name and @value attributes on\n\t\tthe iso:param element, and @id not @name on the pattern element.\n\t\t\n\t-->\n\t\n\t<!-- Suppress declarations of abstract patterns -->\n\t<xslt:template match=\"iso:pattern[@abstract='true']\"  mode=\"iae:go\"  >\n\t\t<xslt:comment>Suppressed abstract pattern <xslt:value-of select=\"@id\"/> was here</xslt:comment>\t\n\t</xslt:template> \n\t\n\t\n\t<!-- Suppress uses of abstract patterns -->\n\t<xslt:template match=\"iso:pattern[@is-a]\"  mode=\"iae:go\" >\n\t\t\t\n\t\t<xslt:comment>Start pattern based on abstract <xslt:value-of select=\"@is-a\"/></xslt:comment>\n\t\t\n\t\t<xslt:call-template name=\"iae:abstract-to-real\" >\n\t\t\t<xslt:with-param name=\"caller\" select=\"@id\" />\n\t\t\t<xslt:with-param name=\"is-a\" select=\"@is-a\" />\n\t\t</xslt:call-template>\n\t\t\t\n\t</xslt:template>\n\t \n\t \n\t\n\t<!-- output everything else unchanged -->\n\t<xslt:template match=\"*\" priority=\"-1\"  mode=\"iae:go\" >\n\t    <xslt:copy>\n\t\t\t<xslt:copy-of select=\"@*\" />\n\t\t\t<xslt:apply-templates mode=\"iae:go\"/> \n\t\t</xslt:copy>\n\t</xslt:template>\n\t\n\t<!-- Templates for macro expansion of abstract patterns -->\n\t<!-- Sets up the initial conditions for the recursive call -->\n\t<xslt:template name=\"iae:macro-expand\">\n\t\t<xslt:param name=\"caller\"/>\n\t\t<xslt:param name=\"text\" />\n\t\t<xslt:call-template name=\"iae:multi-macro-expand\">\n\t\t\t<xslt:with-param name=\"caller\" select=\"$caller\"/>\n\t\t\t<xslt:with-param name=\"text\" select=\"$text\"/>\n\t\t\t<xslt:with-param name=\"paramNumber\" select=\"1\"/>\n\t\t</xslt:call-template>\n\t\t\n\t</xslt:template>\n\t\n\t<!-- Template to replace the current parameter and then\n\t   recurse to replace subsequent parameters. -->\n\t    \n\t<xslt:template name=\"iae:multi-macro-expand\">\n\t\t<xslt:param name=\"caller\"/>\n\t\t<xslt:param name=\"text\" />\n\t\t<xslt:param name=\"paramNumber\" />\n\n\t\t\n\t\t<xslt:choose>\n\t\t\t<xslt:when test=\"//iso:pattern[@id=$caller]/iso:param[ $paramNumber]\">\n\n\t\t\t\t<xslt:call-template name=\"iae:multi-macro-expand\">\n\t\t\t\t\t<xslt:with-param name=\"caller\" select=\"$caller\"/>\t\n\t\t\t\t\t<xslt:with-param name=\"paramNumber\" select=\"$paramNumber + 1\"/>\t\t\n\t\t\t\t\t<xslt:with-param name=\"text\" >\n\t\t\t\t\t\t<xslt:call-template name=\"iae:replace-substring\">\n\t\t\t\t\t\t\t<xslt:with-param name=\"original\" select=\"$text\"/>\n\t\t\t\t\t\t\t<xslt:with-param name=\"substring\"\n\t\t\t\t\t\t\tselect=\"concat('$', //iso:pattern[@id=$caller]/iso:param[ $paramNumber ]/@name)\"/>\n\t\t\t\t\t\t\t<xslt:with-param name=\"replacement\"\n\t\t\t\t\t\t\t\tselect=\"//iso:pattern[@id=$caller]/iso:param[ $paramNumber ]/@value\"/>\t\t\t\n\t\t\t\t\t\t</xslt:call-template>\n\t\t\t\t\t</xslt:with-param>\t\t\t\t\t\t\n\t\t\t\t</xslt:call-template>\n\t\t\t</xslt:when>\n\t\t\t<xslt:otherwise><xslt:value-of select=\"$text\" /></xslt:otherwise>\t\t\n\t\t\n\t\t</xslt:choose>\n\t</xslt:template>\n\t\n\t\n\t<!-- generate the real pattern from an abstract pattern + parameters-->\n\t<xslt:template name=\"iae:abstract-to-real\" >\n\t\t<xslt:param name=\"caller\"/>\n\t\t<xslt:param name=\"is-a\" />\n\t\t<xslt:for-each select=\"//iso:pattern[@id= $is-a]\">\n\t\t<xslt:copy>\n\t\t\n\t\t    <xslt:choose>\n\t\t      <xslt:when test=\" string-length( $caller ) = 0\">\n\t\t      <xslt:attribute name=\"id\"><xslt:value-of select=\"concat( generate-id(.) , $is-a)\" /></xslt:attribute>\n\t\t      </xslt:when>\n\t\t      <xslt:otherwise>\n\t\t\t\t<xslt:attribute name=\"id\"><xslt:value-of select=\"$caller\" /></xslt:attribute>\n\t\t      </xslt:otherwise>\n\t\t    </xslt:choose> \n\t\t\t\n\t\t\t<xslt:apply-templates select=\"*|text()\" mode=\"iae:do-pattern\"    >\n\t\t\t\t<xslt:with-param name=\"caller\"><xslt:value-of select=\"$caller\"/></xslt:with-param>\n\t\t\t</xslt:apply-templates>\t\n\t\t\t\n\t\t</xslt:copy>\n\t\t</xslt:for-each>\n\t</xslt:template>\n\t\t\n\t\n\t<!-- Generate a non-abstract pattern -->\n\t<xslt:template mode=\"iae:do-pattern\" match=\"*\">\n\t\t<xslt:param name=\"caller\"/>\n\t\t<xslt:copy>\n\t\t\t<xslt:for-each select=\"@*[name()='test' or name()='context' or name()='select'   or name()='path'  ]\">\n\t\t\t\t<xslt:attribute name=\"{name()}\">\n\t\t\t\t<xslt:call-template name=\"iae:macro-expand\">\n\t\t\t\t\t\t<xslt:with-param name=\"text\"><xslt:value-of select=\".\"/></xslt:with-param>\n\t\t\t\t\t\t<xslt:with-param name=\"caller\"><xslt:value-of select=\"$caller\"/></xslt:with-param>\n\t\t\t\t\t</xslt:call-template>\n\t\t\t\t</xslt:attribute>\n\t\t\t</xslt:for-each>\t\n\t\t\t<xslt:copy-of select=\"@*[name()!='test'][name()!='context'][name()!='select'][name()!='path']\" />\n\t\t\t<xsl:for-each select=\"node()\">\n\t\t\t\t<xsl:choose>\n\t\t\t\t    <!-- Experiment: replace macros in text as well, to allow parameterized assertions\n\t\t\t\t        and so on, without having to have spurious <iso:value-of> calls and multiple\n\t\t\t\t        delimiting.\n                NOTE: THIS FUNCTIONALITY WILL BE REMOVED IN THE FUTURE    -->\n\t\t\t\t\t<xsl:when test=\"self::text()\">\t\n\t\t\t\t\t\t<xslt:call-template name=\"iae:macro-expand\">\n\t\t\t\t\t\t\t<xslt:with-param name=\"text\"><xslt:value-of select=\".\"/></xslt:with-param>\n\t\t\t\t\t\t\t<xslt:with-param name=\"caller\"><xslt:value-of select=\"$caller\"/></xslt:with-param>\n\t\t\t\t\t\t</xslt:call-template>\n\t\t\t\t\t</xsl:when>\n\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t<xslt:apply-templates select=\".\" mode=\"iae:do-pattern\">\n\t\t\t\t\t\t\t<xslt:with-param name=\"caller\"><xslt:value-of select=\"$caller\"/></xslt:with-param>\n\t\t\t\t\t\t</xslt:apply-templates>\t\t\n\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t</xsl:choose>\n\t\t\t</xsl:for-each>\t\t\t\n\t\t</xslt:copy>\n\t</xslt:template>\n\t\n\t<!-- UTILITIES --> \n\t<!-- Simple version of replace-substring function -->\n\t<xslt:template name=\"iae:replace-substring\">\n\t\t<xslt:param name=\"original\" />    \n\t\t<xslt:param name=\"substring\" />   \n\t\t<xslt:param name=\"replacement\" select=\"''\"/>\n\t\t\n  <xsl:choose>\n    <xsl:when test=\"not($original)\" /> \n    <xsl:when test=\"not(string($substring))\">\n      <xsl:value-of select=\"$original\" />\n    </xsl:when> \n        <xsl:when test=\"contains($original, $substring)\">\n          <xsl:variable name=\"before\" select=\"substring-before($original, $substring)\" />\n          <xsl:variable name=\"after\" select=\"substring-after($original, $substring)\" />\n          \n          <xsl:value-of select=\"$before\" />\n          <xsl:value-of select=\"$replacement\" />\n          <!-- recursion -->\n          <xsl:call-template name=\"iae:replace-substring\">\n            <xsl:with-param name=\"original\" select=\"$after\" />\n            <xsl:with-param name=\"substring\" select=\"$substring\" />\n            <xsl:with-param name=\"replacement\" select=\"$replacement\" /> \n            </xsl:call-template>\n        </xsl:when>\n        <xsl:otherwise>\n        \t<!-- no substitution -->\n        \t<xsl:value-of select=\"$original\" />\n        </xsl:otherwise>\n      </xsl:choose> \n</xslt:template>\n\n\n\n</xslt:stylesheet>"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/isoschematron/resources/xsl/iso-schematron-xslt1/iso_dsdl_include.xsl",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?><?xar XSLT?>\n\n<!-- \n     OVERVIEW : iso_dsdl_include.xsl\n     \n\t    This is an inclusion preprocessor for the non-smart text inclusions\n\t    of ISO DSDL. It handles \n\t    \t<relax:extRef> for ISO RELAX NG\n\t    \t<sch:include>  for ISO Schematron and Schematron 1.n\n\t    \t<sch:extends>  for 2009 draft ISO Schematron\n\t    \t<xi:xinclude>  simple W3C XIncludes for ISO NVRL and DSRL \n\t    \t<crdl:ref>     for draft ISO CRDL\n\t    \t<dtll:include> for draft ISO DTLL\n\t    \t<* @xlink:href> for simple W3C XLink 1.1 embedded links\n\t    \t\n\t\t \n\t\tThis should be the first in any chain of processing. It only requires\n\t\tXSLT 1. Each kind of inclusion can be turned off (or on) on the command line.\n\t\t\n\t\tIds in fragment identifiers or xpointers will be sought in the following\n\t\torder:\n\t\t    * @xml:id\n\t\t    * id() for typed schemas (e.g. from DTD) [NOTE: XInclude does not support this]\n\t\t    * untyped @id \n\t\t    \n\tThe proposed behaviour for the update to ISO Schematron has been implemented. If an\n\tinclude points to an element with the same name as the parent, then that element's\n\tcontents will be included. This supports the merge style of inclusion.    \n\t\n\tWhen an inclusion is made, it is preceded by a PI with target DSDL_INCLUDE_START\n\tand the href and closed by a PI with target DSDL_INCLUDE_START and the href. This is\n\tto allow better location of problems, though only to the file level. \n\t\n\tLimitations:\n\t* No rebasing: relative paths will be interpreted based on the initial document's\n\tpath, not the including document. (Severe limitation!)\n\t* No checking for circular references\n\t* Not full xpointers: only ID matching\n\t* <relax:include> not implemented \n\t* XInclude handling of xml:base and xml:lang not implemented   \n-->\n<!-- \n  VERSION INFORMATION\n\t2009-02-25 \n\t* Update DSDL namespace to use schematron.com\n\t* Tested with SAXON9, Xalan 2.7.1, IE7, \n\t* IE does not like multiple variables in same template with same name: rename.   \n\t2008-09-18\n\t* Remove new behaviour for include, because it conflicts with existing usage [KH]\n\t* Add extends[@href] element with that merge functionality\n\t* Generate PIs to notate source of inclusions for potential better diagnostics\n\t\n\t2008-09-16\n\t* Fix for XSLT1\n\t\n\t2008-08-28\n\t* New behaviour for schematron includes: if the pointed to element is the same as the current,\n\tinclude the children.\n\t\n\t2008-08-20\n\t* Fix bug: in XSLT1 cannot do $document/id('x') but need to use for-each\n\t\n\t2008-08-04\n\t* Add support for inclusions in old namespace  \n\t\n\t2008-08-03\n\t* Fix wrong param name include-relaxng & include-crdl (KH, PH)\n\t* Allow inclusion of XSLT and XHTML (KH)\n\t* Fix inclusion of fragments (KH)\n\t\n\t2008-07-25\n\t* Add selectable input parameter\n\t\n\t2008-07-24  \n\t* RJ New\n-->\n<!--\n\tLEGAL INFORMATION\n\t\n\tCopyright (c) 2008 Rick Jelliffe \n\t\n\tThis software is provided 'as-is', without any express or implied warranty. \n\tIn no event will the authors be held liable for any damages arising from \n\tthe use of this software.\n\t\n\tPermission is granted to anyone to use this software for any purpose, \n\tincluding commercial applications, and to alter it and redistribute it freely,\n\tsubject to the following restrictions:\n\t\n\t1. The origin of this software must not be misrepresented; you must not claim\n\tthat you wrote the original software. If you use this software in a product, \n\tan acknowledgment in the product documentation would be appreciated but is \n\tnot required.\n\t\n\t2. Altered source versions must be plainly marked as such, and must not be \n\tmisrepresented as being the original software.\n\t\n\t3. This notice may not be removed or altered from any source distribution.\n-->\n<xslt:stylesheet version=\"1.0\"\n\txmlns:xslt=\"http://www.w3.org/1999/XSL/Transform\"\n\txmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\"\n\txmlns:iso=\"http://purl.oclc.org/dsdl/schematron\"\n\txmlns:nvdl=\"http://purl.oclc.org/dsdl/nvdl\"\n\txmlns:xhtml=\"http://www.w3.org/1999/xhtml\"\n\txmlns:schold=\"http://www.ascc.net/xml/schematron\"\n\txmlns:crdl=\"http://purl.oclc.org/dsdl/crepdl/ns/structure/1.0\"\n\txmlns:xi=\"http://www.w3.org/2001/XInclude\"\n\txmlns:dtll=\"http://www.jenitennison.com/datatypes\"\n\txmlns:dsdl=\"http://www.schematron.com/namespace/dsdl\"\n\txmlns:relax=\"http://relaxng.org/ns/structure/1.0\"\n\txmlns:xlink=\"http://www.w3.org/1999/xlink\">\n\t<!-- Note: The URL for the dsdl namespace is not official -->\n\n\n\t<xsl:param name=\"include-schematron\">true</xsl:param>\n\t<xsl:param name=\"include-crdl\">true</xsl:param>\n\t<xsl:param name=\"include-xinclude\">true</xsl:param>\n\t<xsl:param name=\"include-dtll\">true</xsl:param>\n\t<xsl:param name=\"include-relaxng\">true</xsl:param>\n\t<xsl:param name=\"include-xlink\">true</xsl:param>\n\n\t<xsl:template match=\"/\">\n\t\t<xsl:apply-templates select=\".\" mode=\"dsdl:go\" />\n\t</xsl:template>\n\n\t<!-- output everything else unchanged -->\n\t<xslt:template match=\"node()\" priority=\"-1\" mode=\"dsdl:go\">\n\t\t<xslt:copy>\n\t\t\t<xslt:copy-of select=\"@*\" />\n\t\t\t<xslt:apply-templates mode=\"dsdl:go\" />\n\t\t</xslt:copy>\n\t</xslt:template>\n\n\n\n\t<!-- =========================================================== -->\n\t<!-- ISO/IEC 19757 - DSDL Document Schema Definition Languages   -->\n\t<!-- Part 2 - Regular grammar-based validation - RELAX NG        -->\n\t<!-- This only implements relax:extRef not relax:include which   -->\n\t<!-- is complex.                                                 -->\n\t<!-- =========================================================== -->\n\t<xslt:template match=\"relax:extRef\" mode=\"dsdl:go\">\n\n\n\t\t<!-- Insert subschema -->\n\n\t\t<xsl:variable name=\"document-uri\"\n\t\t\tselect=\"substring-before(concat(@href,'#'), '#')\" />\n\t\t<xsl:variable name=\"fragment-id\"\n\t\t\tselect=\"substring-after(@href, '#')\" />\n\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_START\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\t\t<xsl:choose>\n\t\t\t<xsl:when test=\"not( $include-relaxng = 'true' )\">\n\t\t\t\t<xslt:copy>\n\t\t\t\t\t<xslt:copy-of select=\"@*\" />\n\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\" />\n\t\t\t\t</xslt:copy>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise>\n\n\t\t\t\t<xsl:choose>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0 and string-length( $fragment-id ) = 0\">\n\t\t\t\t\t\t<xsl:message>\n\t\t\t\t\t\t\tError: Impossible URL in RELAX NG extRef\n\t\t\t\t\t\t\tinclude\n\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<!-- this case is when there is in embedded schema in the same document elsewhere -->\n\t\t\t\t\t<xslt:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0\">\n\t\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\"\n\t\t\t\t\t\t\tselect=\"//*[@xml:id= $fragment-id ] | id( $fragment-id) | //*[@id= $fragment-id ]\" />\n\t\t\t\t\t</xslt:when>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $fragment-id ) &gt; 0\">\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_1\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_1)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<!-- use a for-each so that the id() function works correctly on the external document -->\n\t\t\t\t\t\t<xsl:for-each select=\"$theDocument_1\">\n\t\t\t\t\t\t\t<xsl:variable name=\"theFragment_1\"\n\t\t\t\t\t\t\t\tselect=\"$theDocument_1//*[@xml:id= $fragment-id ]        \n                  |  id( $fragment-id)          \n              | $theDocument_1//*[@id= $fragment-id ]\" />\n\t\t\t\t\t\t\t<xsl:if test=\"not($theFragment_1)\">\n\t\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t\t<xsl:apply-templates\n\t\t\t\t\t\t\t\tselect=\" $theFragment_1[1]\" mode=\"dsdl:go\" />\n\t\t\t\t\t\t</xsl:for-each>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_2\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:variable name=\"theFragment_2\"\n\t\t\t\t\t\t\tselect=\"$theDocument_2/*\" />\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_2)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\n\t\t\t\t\t\t<xsl:if test=\"not($theFragment_2)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<xsl:apply-templates select=\"$theFragment_2 \"\n\t\t\t\t\t\t\tmode=\"dsdl:go\" />\n\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t</xsl:choose>\n\n\t\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_END\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\t</xslt:template>\n\n\n\n\t<!-- =========================================================== -->\n\t<!-- ISO/IEC 19757 - DSDL Document Schema Definition Languages   -->\n\t<!-- Part 3 - Rule-based validation - Schematron                 -->\n\t<!-- =========================================================== -->\n\n\n\t<!-- Extend the URI syntax to allow # references -->\n\t<!-- Add experimental support for simple containers like  /xxx:xxx/iso:pattern to allow better includes -->\n\t<xsl:template match=\"iso:include\" mode=\"dsdl:go\">\n\n\t\t<xsl:variable name=\"document-uri\"\n\t\t\tselect=\"substring-before(concat(@href,'#'), '#')\" />\n\t\t<xsl:variable name=\"fragment-id\"\n\t\t\tselect=\"substring-after(@href, '#')\" />\n\n\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_START\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\n\t\t<xsl:choose>\n\t\t\t<xsl:when test=\"not( $include-schematron = 'true' )\">\n\t\t\t\t<xslt:copy>\n\t\t\t\t\t<xslt:copy-of select=\"@*\" />\n\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\" />\n\t\t\t\t</xslt:copy>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise>\n\n\t\t\t\t<xsl:choose>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0 and string-length( $fragment-id ) = 0\">\n\t\t\t\t\t\t<xsl:message>\n\t\t\t\t\t\t\tError: Impossible URL in Schematron include\n\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<!-- this case is when there is in embedded schema in the same document elsewhere -->\n\t\t\t\t\t<xslt:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0\">\n\t\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\"\n\t\t\t\t\t\t\tselect=\"//iso:*[@xml:id= $fragment-id ] \n              \t |id( $fragment-id)\n              \t | //iso:*[@id= $fragment-id ]\" />\n\t\t\t\t\t</xslt:when>\n\n\t\t\t\t\t<!-- case where there is a fragment in another document (should be an iso: element) -->\n\t\t\t\t\t<!-- There are three cases for includes with fragment:\n\t\t\t\t\t\t0) No href file or no matching id - error!\n\t\t\t\t\t\t1) REMOVED\n\t\t\t\t\t\t\n\t\t\t\t\t\t2) The linked-to element is sch:schema however the parent of the include\n\t\t\t\t\t\tis not a schema. In this case, it is an error. (Actually, it should\n\t\t\t\t\t\tbe an error for other kinds of containment problems, but we won't\n\t\t\t\t\t\tcheck for them in this version.)\n\t\t\t\t\t\t\n\t\t\t\t\t\t3) Otherwise, include the pointed-to element\n\t\t\t\t\t-->\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $fragment-id ) &gt; 0\">\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_1\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:variable name=\"originalParent\" select=\"..\" />\n\n\t\t\t\t\t\t<!-- case 0 -->\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_1)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<!-- use for-each to rebase id() to external document -->\n\t\t\t\t\t\t<xsl:for-each select=\"$theDocument_1\">\n\t\t\t\t\t\t\t<xsl:variable name=\"theFragment_1\"\n\t\t\t\t\t\t\t\tselect=\" $theDocument_1//iso:*[@xml:id= $fragment-id ] |\n              \t \t\tid($fragment-id) |\n              \t\t\t$theDocument_1//iso:*[@id= $fragment-id ]\" />\n\n\n\t\t\t\t\t\t\t<xsl:choose>\n\t\t\t\t\t\t\t\t<!-- case 0 -->\n\t\t\t\t\t\t\t\t<xsl:when test=\"not($theFragment_1)\">\n\t\t\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t\t</xsl:when>\n\n\n\t\t\t\t\t\t\t\t<!-- case 1 REMOVED -->\n\n\t\t\t\t\t\t\t\t<!-- case 2 -->\n\t\t\t\t\t\t\t\t<xsl:when\n\t\t\t\t\t\t\t\t\ttest=\" $theFragment_1/self::iso:schema \">\n\t\t\t\t\t\t\t\t\t<xsl:message>\n\t\t\t\t\t\t\t\t\t\tSchema error: Use include to\n\t\t\t\t\t\t\t\t\t\tinclude fragments, not a whole\n\t\t\t\t\t\t\t\t\t\tschema\n\t\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t\t\t\t<!-- case 3 -->\n\t\t\t\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t\t\t\t<xsl:apply-templates\n\t\t\t\t\t\t\t\t\t\tselect=\" $theFragment_1[1]\" mode=\"dsdl:go\" />\n\t\t\t\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t\t\t\t</xsl:choose>\n\t\t\t\t\t\t</xsl:for-each>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<!-- Case where there is no ID so we include the whole document -->\n\t\t\t\t\t<!-- Experimental addition: include fragments of children -->\n\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_2\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:variable name=\"theFragment_2\"\n\t\t\t\t\t\t\tselect=\"$theDocument_2/iso:*\" />\n\t\t\t\t\t\t<xsl:variable name=\"theContainedFragments\"\n\t\t\t\t\t\t\tselect=\"$theDocument_2/*/iso:* | $theDocument_2/*/xsl:* | $theDocument_2/*/xhtml:*\" />\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_2)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\n\t\t\t\t\t\t<!-- There are three cases for includes:\n\t\t\t\t\t\t\t0) No text specified- error!\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t1) REMOVED\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t2) The linked-to element is sch:schema however the parent of the include\n\t\t\t\t\t\t\tis not a schema. In this case, it is an error. (Actually, it should\n\t\t\t\t\t\t\tbe an error for other kinds of containment problems, but we won't\n\t\t\t\t\t\t\tcheck for them in this version.)\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t3) Otherwise, include the pointed-to element\n\t\t\t\t\t\t-->\n\t\t\t\t\t\t<xsl:choose>\n\t\t\t\t\t\t\t<!-- case 0 -->\n\t\t\t\t\t\t\t<xsl:when\n\t\t\t\t\t\t\t\ttest=\"not($theFragment_2) and not ($theContainedFragments)\">\n\t\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t\t\t<!-- case 1 removed -->\n\n\t\t\t\t\t\t\t<!-- case 2 -->\n\t\t\t\t\t\t\t<xsl:when\n\t\t\t\t\t\t\t\ttest=\" $theFragment_2/self::iso:schema or $theContainedFragments/self::iso:schema\">\n\t\t\t\t\t\t\t\t<xsl:message>\n\t\t\t\t\t\t\t\t\tSchema error: Use include to include\n\t\t\t\t\t\t\t\t\tfragments, not a whole schema\n\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t\t\t<!-- If this were XLST 2, we could use  \n\t\t\t\t\t\t\t\tif ($theFragment) then $theFragment else $theContainedFragments\n\t\t\t\t\t\t\t\there (thanks to KN)\n\t\t\t\t\t\t\t-->\n\t\t\t\t\t\t\t<!-- case 3 -->\n\t\t\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t\t\t<xsl:apply-templates\n\t\t\t\t\t\t\t\t\tselect=\"$theFragment_2 \" mode=\"dsdl:go\" />\n\t\t\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t\t\t</xsl:choose>\n\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t</xsl:choose>\n\t\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_END\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\t</xsl:template>\n\n\n\t<!-- WARNING   sch:extends[@href] is experimental and non standard  -->\n\t<!-- Basically, it adds the children of the selected element, not the element itself.  -->\n\t<xsl:template match=\"iso:extends[@href]\" mode=\"dsdl:go\">\n\n\t\t<xsl:variable name=\"document-uri\"\n\t\t\tselect=\"substring-before(concat(@href,'#'), '#')\" />\n\t\t<xsl:variable name=\"fragment-id\"\n\t\t\tselect=\"substring-after(@href, '#')\" />\n\n\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_START\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\n\t\t<xsl:choose>\n\t\t\t<xsl:when test=\"not( $include-schematron = 'true' )\">\n\t\t\t\t<xslt:copy>\n\t\t\t\t\t<xslt:copy-of select=\"@*\" />\n\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\" />\n\t\t\t\t</xslt:copy>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise>\n\n\t\t\t\t<xsl:choose>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0 and string-length( $fragment-id ) = 0\">\n\t\t\t\t\t\t<xsl:message>\n\t\t\t\t\t\t\tError: Impossible URL in Schematron include\n\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<!-- this case is when there is in embedded schema in the same document elsewhere -->\n\t\t\t\t\t<xslt:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0\">\n\t\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\"\n\t\t\t\t\t\t\tselect=\"//iso:*[@xml:id= $fragment-id ]/* \n              \t |id( $fragment-id)/*\n              \t | //iso:*[@id= $fragment-id ]/*\" />\n\t\t\t\t\t</xslt:when>\n\n\t\t\t\t\t<!-- case where there is a fragment in another document (should be an iso: element) -->\n\t\t\t\t\t<!-- There are three cases for includes with fragment:\n\t\t\t\t\t\t0) No href file or no matching id - error!\n\t\t\t\t\t\t1) REMOVED\n\t\t\t\t\t\t\n\t\t\t\t\t\t2) REMOVED\n\t\t\t\t\t\t\n\t\t\t\t\t\t3) Otherwise, include the pointed-to element\n\t\t\t\t\t-->\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $fragment-id ) &gt; 0\">\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_1\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:variable name=\"originalParent\" select=\"..\" />\n\n\t\t\t\t\t\t<!-- case 0 -->\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_1)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<!-- use for-each to rebase id() to external document -->\n\t\t\t\t\t\t<xsl:for-each select=\"$theDocument_1\">\n\t\t\t\t\t\t\t<xsl:variable name=\"theFragment_1\"\n\t\t\t\t\t\t\t\tselect=\" $theDocument_1//iso:*[@xml:id= $fragment-id ] |\n              \t \t\tid($fragment-id) |\n              \t\t\t$theDocument_1//iso:*[@id= $fragment-id ]\" />\n\n\n\t\t\t\t\t\t\t<xsl:choose>\n\t\t\t\t\t\t\t\t<!-- case 0 -->\n\t\t\t\t\t\t\t\t<xsl:when test=\"not($theFragment_1)\">\n\t\t\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t\t</xsl:when>\n\n\n\t\t\t\t\t\t\t\t<!-- case 1 REMOVED -->\n\n\t\t\t\t\t\t\t\t<!-- case 2 REMOVED -->\n\n\n\t\t\t\t\t\t\t\t<!-- case 3 -->\n\t\t\t\t\t\t\t\t<xsl:otherwise>\n\n\t\t\t\t\t\t\t\t\t<xsl:apply-templates\n\t\t\t\t\t\t\t\t\t\tselect=\" $theFragment_1[1]/*\" mode=\"dsdl:go\" />\n\t\t\t\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t\t\t\t</xsl:choose>\n\t\t\t\t\t\t</xsl:for-each>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<!-- Case where there is no ID so we include the whole document -->\n\t\t\t\t\t<!-- Experimental addition: include fragments of children -->\n\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_2\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:variable name=\"theFragment_2\"\n\t\t\t\t\t\t\tselect=\"$theDocument_2/iso:*\" />\n\t\t\t\t\t\t<xsl:variable name=\"theContainedFragments\"\n\t\t\t\t\t\t\tselect=\"$theDocument_2/*/iso:* | $theDocument_2/*/xsl:* | $theDocument_2/*/xhtml:*\" />\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_2)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\n\t\t\t\t\t\t<!-- There are three cases for includes:\n\t\t\t\t\t\t\t0) No text specified- error!\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t1) REMOVED\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t2) REMOVED\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t3) Otherwise, include the pointed-to element\n\t\t\t\t\t\t-->\n\t\t\t\t\t\t<xsl:choose>\n\t\t\t\t\t\t\t<!-- case 0 -->\n\t\t\t\t\t\t\t<xsl:when\n\t\t\t\t\t\t\t\ttest=\"not($theFragment_2) and not ($theContainedFragments)\">\n\t\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t\t\t<!-- case 1 removed -->\n\n\t\t\t\t\t\t\t<!-- case 2 removed -->\n\n\t\t\t\t\t\t\t<!-- If this were XLST 2, we could use  \n\t\t\t\t\t\t\t\tif ($theFragment) then $theFragment else $theContainedFragments\n\t\t\t\t\t\t\t\there (thanks to KN)\n\t\t\t\t\t\t\t-->\n\t\t\t\t\t\t\t<!-- case 3 -->\n\t\t\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t\t\t<xsl:apply-templates\n\t\t\t\t\t\t\t\t\tselect=\"$theFragment_2/* \" mode=\"dsdl:go\" />\n\t\t\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t\t\t</xsl:choose>\n\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t</xsl:choose>\n\t\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_END\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\t</xsl:template>\n\n\n\n\t<!-- =========================================================== -->\n\t<!-- Handle Schematron 1.6 inclusions: clone of ISO code above   -->\n\t<!-- =========================================================== -->\n\n\n\t<!-- Extend the URI syntax to allow # references -->\n\t<!-- Add experimental support for simple containers like  /xxx:xxx/schold:pattern to allow better includes -->\n\t<xsl:template match=\"schold:include\" mode=\"dsdl:go\">\n\t\t<xsl:variable name=\"document-uri\"\n\t\t\tselect=\"substring-before(concat(@href,'#'), '#')\" />\n\t\t<xsl:variable name=\"fragment-id\"\n\t\t\tselect=\"substring-after(@href, '#')\" />\n\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_START\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\n\t\t<xsl:choose>\n\t\t\t<xsl:when test=\"not( $include-schematron = 'true' )\">\n\t\t\t\t<xslt:copy>\n\t\t\t\t\t<xslt:copy-of select=\"@*\" />\n\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\" />\n\t\t\t\t</xslt:copy>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise>\n\t\t\t\t<xsl:choose>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0 and string-length( $fragment-id ) = 0\">\n\t\t\t\t\t\t<xsl:message>\n\t\t\t\t\t\t\tError: Impossible URL in Schematron include\n\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<!-- this case is when there is in embedded schema in the same document elsewhere -->\n\t\t\t\t\t<xslt:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0\">\n\t\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\"\n\t\t\t\t\t\t\tselect=\"//schold:*[@xml:id= $fragment-id ] \n              \t |id( $fragment-id)\n              \t | //schold:*[@id= $fragment-id ]\" />\n\t\t\t\t\t</xslt:when>\n\n\t\t\t\t\t<!-- case where there is a fragment in another document (should be an iso: element) -->\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $fragment-id ) &gt; 0\">\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_1\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_1)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<!-- use for-each to rebase id() to $theDocument -->\n\t\t\t\t\t\t<xsl:for-each select=\"$theDocument_1\">\n\t\t\t\t\t\t\t<xsl:variable name=\"theFragment_1\"\n\t\t\t\t\t\t\t\tselect=\" $theDocument_1//schold:*[@xml:id= $fragment-id ] |\n              \tid($fragment-id) |\n              \t$theDocument_1//schold:*[@id= $fragment-id ]\" />\n\t\t\t\t\t\t\t<xsl:if\n\t\t\t\t\t\t\t\ttest=\" $theFragment_1/self::schold:schema \">\n\t\t\t\t\t\t\t\t<xsl:message>\n\t\t\t\t\t\t\t\t\tSchema error: Use include to include\n\t\t\t\t\t\t\t\t\tfragments, not a whole schema\n\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t\t<xsl:if test=\"not($theFragment_1)\">\n\t\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t\t<xsl:apply-templates\n\t\t\t\t\t\t\t\tselect=\" $theFragment_1[1]\" mode=\"dsdl:go\" />\n\t\t\t\t\t\t</xsl:for-each>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<!-- Case where there is no ID so we include the whole document -->\n\t\t\t\t\t<!-- Experimental addition: include fragments of children -->\n\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_2\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:variable name=\"theFragment_2\"\n\t\t\t\t\t\t\tselect=\"$theDocument_2/iso:*\" />\n\t\t\t\t\t\t<xsl:variable name=\"theContainedFragments\"\n\t\t\t\t\t\t\tselect=\"$theDocument_2/*/schold:* | $theDocument_2/*/xsl:* | $theDocument_2/*/xhtml:*\" />\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_2)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\n\t\t\t\t\t\t<xsl:if\n\t\t\t\t\t\t\ttest=\" $theFragment_2/self::schold:schema or $theContainedFragments/self::schold:schema\">\n\t\t\t\t\t\t\t<xsl:message>\n\t\t\t\t\t\t\t\tSchema error: Use include to include\n\t\t\t\t\t\t\t\tfragments, not a whole schema\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<xsl:if\n\t\t\t\t\t\t\ttest=\"not($theFragment_2) and not ($theContainedFragments)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<!-- If this were XLST 2, we could use  \n\t\t\t\t\t\t\tif ($theFragment) then $theFragment else $theContainedFragments\n\t\t\t\t\t\t\there (thanks to KN)\n\t\t\t\t\t\t-->\n\t\t\t\t\t\t<xsl:choose>\n\t\t\t\t\t\t\t<xsl:when test=\" $theFragment_2 \">\n\t\t\t\t\t\t\t\t<xsl:apply-templates\n\t\t\t\t\t\t\t\t\tselect=\"$theFragment_2 \" mode=\"dsdl:go\" />\n\t\t\t\t\t\t\t</xsl:when>\n\t\t\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t\t\t<!-- WARNING!  EXPERIMENTAL! Use at your own risk. This may be discontinued! -->\n\t\t\t\t\t\t\t\t<xsl:apply-templates\n\t\t\t\t\t\t\t\t\tselect=\"  $theContainedFragments \" mode=\"dsdl:go\" />\n\t\t\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t\t\t</xsl:choose>\n\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t</xsl:choose>\n\n\t\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_END\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\t</xsl:template>\n\t<!-- =========================================================== -->\n\t<!-- ISO/IEC 19757 - DSDL Document Schema Definition Languages   -->\n\t<!-- Part 5 - DataType Library Language - DTLL                   -->\n\t<!-- Committee Draft  Experimental support only                  -->\n\t<!-- The <include> element may well be replaced by XInclude in   -->\n\t<!-- any final version.                                          -->\n\t<!-- =========================================================== -->\n\t<xslt:template match=\"dtll:include\" mode=\"dsdl:go\">\n\t\t<!-- Insert subschema -->\n\n\t\t<xsl:variable name=\"document-uri\"\n\t\t\tselect=\"substring-before(concat(@href,'#'), '#')\" />\n\t\t<xsl:variable name=\"fragment-id\"\n\t\t\tselect=\"substring-after(@href, '#')\" />\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_START\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\t\t<xsl:choose>\n\t\t\t<xsl:when test=\"not( $include-dtll = 'true' )\">\n\t\t\t\t<xslt:copy>\n\t\t\t\t\t<xslt:copy-of select=\"@*\" />\n\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\" />\n\t\t\t\t</xslt:copy>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise>\n\t\t\t\t<xsl:choose>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0 and string-length( $fragment-id ) = 0\">\n\t\t\t\t\t\t<xsl:message>\n\t\t\t\t\t\t\tError: Impossible URL in DTLL include\n\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<!-- this case is when there is in embedded schema in the same document elsewhere -->\n\t\t\t\t\t<xslt:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0\">\n\t\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\"\n\t\t\t\t\t\t\tselect=\"//*[@xml:id= $fragment-id ] | id( $fragment-id) \n              \t| //*[@id= $fragment-id ]\" />\n\t\t\t\t\t</xslt:when>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $fragment-id ) &gt; 0\">\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_1\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_1)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<!-- use for-each to rebase id() to $theDocument -->\n\t\t\t\t\t\t<xsl:for-each select=\"$theDocument_1\">\n\t\t\t\t\t\t\t<xsl:variable name=\"theFragment_1\"\n\t\t\t\t\t\t\t\tselect=\"$theDocument_1//*[@xml:id= $fragment-id ]\n               | id( $fragment-id ) \n               | $theDocument_1//*[@id= $fragment-id ]\" />\n\t\t\t\t\t\t\t<xsl:if test=\"not($theFragment_1)\">\n\t\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t\t<xsl:apply-templates\n\t\t\t\t\t\t\t\tselect=\" $theFragment_1[1]\" mode=\"dsdl:go\" />\n\t\t\t\t\t\t</xsl:for-each>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_2\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:variable name=\"theFragment_2\"\n\t\t\t\t\t\t\tselect=\"$theDocument_2/*\" />\n\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_2)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\n\t\t\t\t\t\t<xsl:if test=\"not($theFragment_2)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<xsl:apply-templates select=\"$theFragment_2 \"\n\t\t\t\t\t\t\tmode=\"dsdl:go\" />\n\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t</xsl:choose>\n\n\t\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_END\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\t</xslt:template>\n\n\t<!-- =========================================================== -->\n\t<!-- ISO/IEC 19757 - DSDL Document Schema Definition Languages   -->\n\t<!-- Part 7 - Character Repertoire Description Language - CRDL   -->\n\t<!-- Final Committee Draft 2008-01-11 Experimental support only  -->\n\t<!-- =========================================================== -->\n\t<xslt:template match=\"crdl:ref\" mode=\"dsdl:go\">\n\t\t<!-- Insert subschema -->\n\n\t\t<xsl:variable name=\"document-uri\"\n\t\t\tselect=\"substring-before(concat(@href,'#'), '#')\" />\n\t\t<xsl:variable name=\"fragment-id\"\n\t\t\tselect=\"substring-after(@href, '#')\" />\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_START\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\t\t<xsl:choose>\n\t\t\t<xsl:when test=\"not( $include-crdl = 'true' )\">\n\t\t\t\t<xslt:copy>\n\t\t\t\t\t<xslt:copy-of select=\"@*\" />\n\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\" />\n\t\t\t\t</xslt:copy>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise>\n\t\t\t\t<xsl:choose>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0 and string-length( $fragment-id ) = 0\">\n\t\t\t\t\t\t<xsl:message>\n\t\t\t\t\t\t\tError: Impossible URL in CRDL include\n\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<!-- this case is when there is in embedded schema in the same document elsewhere -->\n\t\t\t\t\t<xslt:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0\">\n\n\t\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\"\n\t\t\t\t\t\t\tselect=\"//*[@xml:id= $fragment-id ] | id( $fragment-id)\n              \t| //*[@id= $fragment-id ]\" />\n\t\t\t\t\t</xslt:when>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $fragment-id ) &gt; 0\">\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_1\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_1)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<!-- use for-each to rebase id() to $theDocument -->\n\t\t\t\t\t\t<xsl:for-each select=\"$theDocument_1\">\n\t\t\t\t\t\t\t<xsl:variable name=\"theFragment_1\"\n\t\t\t\t\t\t\t\tselect=\"$theDocument_1//*[@xml:id= $fragment-id ]\n               | id( $fragment-id )\n               | $theDocument_1//*[@id= $fragment-id ]\" />\n\n\t\t\t\t\t\t\t<xsl:if test=\"not($theFragment_1)\">\n\t\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t\t<xsl:apply-templates select=\" $theFragment_1 \"\n\t\t\t\t\t\t\t\tmode=\"dsdl:go\" />\n\t\t\t\t\t\t</xsl:for-each>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_2\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:variable name=\"theFragment_2\"\n\t\t\t\t\t\t\tselect=\"$theDocument_2/*\" />\n\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_2)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<xsl:if test=\"not($theFragment_2)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\n\t\t\t\t\t\t<xsl:apply-templates select=\"$theFragment_2\"\n\t\t\t\t\t\t\tmode=\"dsdl:go\" />\n\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t</xsl:choose>\n\n\t\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_END\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\t</xslt:template>\n\n\n\t<!-- =========================================================== -->\n\t<!-- ISO/IEC 19757 - DSDL Document Schema Definition Languages   -->\n\t<!-- Part 4 - Namespace-based Validation Dispatching Language - NVDL -->\n\t<!-- Note: This does not include schemas referenced for          -->\n\t<!-- validation, it merely handles any simple XIncludes          -->\n\t<!-- =========================================================== -->\n\t<!-- ISO/IEC 19757 - DSDL Document Schema Definition Languages   -->\n\t<!-- Part 8 - Document Schema Renaming Language - DSRL           -->\n\t<!-- Note: Final? Committee Draft   Experimental support only    -->\n\t<!-- =========================================================== -->\n\t<!-- XInclude support for id based references only, with 1 level -->\n\t<!-- of fallback.                                                -->\n\t<!-- =========================================================== -->\n\n\t<xslt:template mode=\"dsdl:go\"\n\t\tmatch=\"xi:include[@href][not(@parseType) or @parseType ='xml']\">\n\t\t<!-- Simple inclusions only here -->\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_START\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\t\t<xsl:choose>\n\t\t\t<xsl:when test=\"not( $include-xinclude = 'true' )\">\n\t\t\t\t<xslt:copy>\n\t\t\t\t\t<xslt:copy-of select=\"@*\" />\n\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\" />\n\t\t\t\t</xslt:copy>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise>\n\t\t\t\t<xsl:choose>\n\n\t\t\t\t\t<xsl:when test=\"contains( @href, '#')\">\n\t\t\t\t\t\t<xsl:message terminate=\"yes\">\n\t\t\t\t\t\t\tFatal error: Xinclude href contains fragment\n\t\t\t\t\t\t\tidentifier #\n\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t</xsl:when>\n\n\n\t\t\t\t\t<xsl:when test=\"contains( @xpointer, '(')\">\n\t\t\t\t\t\t<xsl:message terminate=\"yes\">\n\t\t\t\t\t\t\tFatal error: Sorry, this software only\n\t\t\t\t\t\t\tsupports simple ids in XInclude xpointers\n\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( @href ) = 0 and string-length( @xpointer ) = 0\">\n\n\t\t\t\t\t\t<xsl:message terminate=\"yes\">\n\t\t\t\t\t\t\tFatal Error: Impossible URL in XInclude\n\t\t\t\t\t\t\tinclude\n\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<!-- this case is when there is in embedded schema in the same document elsewhere -->\n\t\t\t\t\t<xslt:when test=\"string-length( @href ) = 0\">\n\n\t\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\"\n\t\t\t\t\t\t\tselect=\"//*[@xml:id= current()/@xpointer  ] | id( @xpointer)\n              \t| //*[@id= current()/@xpointer  ]\" />\n\t\t\t\t\t</xslt:when>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( @xpointer ) &gt; 0\">\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_1\"\n\t\t\t\t\t\t\tselect=\"document( @href,/ )\" />\n\t\t\t\t\t\t<xsl:variable name=\"theFragment_1\"\n\t\t\t\t\t\t\tselect=\"$theDocument_1//*[@xml:id= current()/@xpointer  ]\n             \n              | $theDocument_1//*[@id= current()/@xpointer  ]\" />\n\t\t\t\t\t\t<!-- removed\n\t\t\t\t\t\t\t| $theDocument_1/id( @xpointer)\n\t\t\t\t\t\t\tbecause it requires rebasing in XSLT1 and that would mess up the use of current()\n\t\t\t\t\t\t-->\n\n\n\t\t\t\t\t\t<!-- Allow one level of fallback, to another XInclude -->\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_1)\">\n\t\t\t\t\t\t\t<xsl:choose>\n\t\t\t\t\t\t\t\t<xsl:when test=\"xi:fallback\">\n\t\t\t\t\t\t\t\t\t<xsl:variable name=\"theDocument_2\"\n\t\t\t\t\t\t\t\t\t\tselect=\"document( xi:fallback[1]/xi:include[not(@parseType)\n                    \t or @parseType='xml']/@href,/ )\" />\n\t\t\t\t\t\t\t\t\t<xsl:variable name=\"theFragment_2\"\n\t\t\t\t\t\t\t\t\t\tselect=\"$theDocument_2//*[@xml:id= current()/xi:fallback[1]/xi:include/@xpointer  ]\n              \t\t\t\t| $theDocument_2//*[@id= current()/xi:fallback[1]/xi:include/@xpointer  ]\" />\n\t\t\t\t\t\t\t\t\t<!-- removed \n\t\t\t\t\t\t\t\t\t\t| $theDocument_2/id( xi:fallback[1]/xi:include/@xpointer)\n\t\t\t\t\t\t\t\t\t\tbecause it id() would need rebasing in XSLT1 and that would mess up use of current()\n\t\t\t\t\t\t\t\t\t-->\n\n\t\t\t\t\t\t\t\t\t<xsl:if\n\t\t\t\t\t\t\t\t\t\ttest=\"not($theDocument_2)\">\n\n\t\t\t\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file and fallback\n\t\t\t\t\t\t\t\t\tfile: </xsl:text>\n\t\t\t\t\t\t\t\t\t\t\t<xsl:value-of\n\t\t\t\t\t\t\t\t\t\t\t\tselect=\"@href\" />\n\t\t\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t\t\t</xsl:when>\n\t\t\t\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t\t\t\t</xsl:choose>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<xsl:apply-templates select=\" $theFragment_1\"\n\t\t\t\t\t\t\tmode=\"dsdl:go\" />\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<!-- Document but no fragment specified -->\n\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_3\"\n\t\t\t\t\t\t\tselect=\"document( @href,/ )\" />\n\t\t\t\t\t\t<xsl:variable name=\"theFragment_3\"\n\t\t\t\t\t\t\tselect=\"$theDocument_3/*\" />\n\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_3)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\n\t\t\t\t\t\t<xsl:apply-templates select=\"$theFragment_3 \"\n\t\t\t\t\t\t\tmode=\"dsdl:go\" />\n\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t</xsl:choose>\n\n\t\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_END\">\n\t\t\t<xsl:value-of select=\"@href\" />\n\t\t</xsl:processing-instruction>\n\t</xslt:template>\n\n\t<!-- =========================================================== -->\n\t<!-- W3C XLink 1.1 embedded simple links                        -->\n\t<!-- =========================================================== -->\n\t<xslt:template\n\t\tmatch=\"*[@xlink:href][not(parent::*[@xlink:type='complex'])]\n\t           [not(@xlink:type) or (@xlink:type='simple')]\n\t           [@xlink:show='embed']\n\t           [not(@xlink:actuate) or (@xlink:actuate='onLoad')]\"\n\t\tmode=\"dsdl:go\" priority=\"1\">\n\n\t\t<xsl:variable name=\"document-uri\"\n\t\t\tselect=\"substring-before(concat(@xlink:href,'#'), '#')\" />\n\t\t<xsl:variable name=\"fragment-id\"\n\t\t\tselect=\"substring-after(@xlink:href, '#')\" />\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_START\">\n\t\t\t<xsl:value-of select=\"@xlink:href\" />\n\t\t</xsl:processing-instruction>\n\t\t<xsl:choose>\n\t\t\t<xsl:when test=\"not( $include-xlink = 'true' )\">\n\t\t\t\t<xslt:copy>\n\t\t\t\t\t<xslt:copy-of select=\"@*\" />\n\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\" />\n\t\t\t\t</xslt:copy>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise>\n\t\t\t\t<xsl:choose>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0 and string-length( $fragment-id ) = 0\">\n\t\t\t\t\t\t<xsl:message>\n\t\t\t\t\t\t\tError: Impossible URL in XLink embedding\n\t\t\t\t\t\t\tlink\n\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<!-- this case is when there is in embedded schema in the same document elsewhere -->\n\t\t\t\t\t<xslt:when\n\t\t\t\t\t\ttest=\"string-length( $document-uri ) = 0\">\n\t\t\t\t\t\t<xslt:apply-templates mode=\"dsdl:go\"\n\t\t\t\t\t\t\tselect=\"//*[@xml:id= $fragment-id ] | id( $fragment-id) \n              \t| //*[@id= $fragment-id ]\" />\n\t\t\t\t\t</xslt:when>\n\n\t\t\t\t\t<xsl:when\n\t\t\t\t\t\ttest=\"string-length( $fragment-id ) &gt; 0\">\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_1\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_1)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@xlink:href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<!-- use for-each to rebase id() to $theDocument -->\n\t\t\t\t\t\t<xsl:for-each select=\"$theDocument_1\">\n\t\t\t\t\t\t\t<xsl:variable name=\"theFragment_1\"\n\t\t\t\t\t\t\t\tselect=\"$theDocument_1//*[@xml:id= $fragment-id ]\n               | id( $fragment-id ) \n               | $theDocument_1//*[@id= $fragment-id ]\" />\n\t\t\t\t\t\t\t<xsl:if test=\"not($theFragment_1)\">\n\t\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t\t<xsl:value-of select=\"@xlink:href\" />\n\t\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t\t<xsl:apply-templates\n\t\t\t\t\t\t\t\tselect=\" $theFragment_1[1]\" mode=\"dsdl:go\" />\n\t\t\t\t\t\t</xsl:for-each>\n\t\t\t\t\t</xsl:when>\n\n\t\t\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t<xsl:variable name=\"theDocument_2\"\n\t\t\t\t\t\t\tselect=\"document( $document-uri,/ )\" />\n\t\t\t\t\t\t<xsl:variable name=\"theFragment_2\"\n\t\t\t\t\t\t\tselect=\"$theDocument_2/*\" />\n\n\t\t\t\t\t\t<xsl:if test=\"not($theDocument_2)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to open referenced included file: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@xlink:href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\n\t\t\t\t\t\t<xsl:if test=\"not($theFragment_2)\">\n\t\t\t\t\t\t\t<xsl:message terminate=\"no\">\n\t\t\t\t\t\t\t\t<xsl:text>Unable to locate id attribute: </xsl:text>\n\t\t\t\t\t\t\t\t<xsl:value-of select=\"@xlink:href\" />\n\t\t\t\t\t\t\t</xsl:message>\n\t\t\t\t\t\t</xsl:if>\n\t\t\t\t\t\t<xsl:apply-templates select=\"$theFragment_2 \"\n\t\t\t\t\t\t\tmode=\"dsdl:go\" />\n\t\t\t\t\t</xsl:otherwise>\n\t\t\t\t</xsl:choose>\n\n\t\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\n\t\t<xsl:processing-instruction name=\"DSDL_INCLUDE_END\">\n\t\t\t<xsl:value-of select=\"@xlink:href\" />\n\t\t</xsl:processing-instruction>\n\t</xslt:template>\n\n\n</xslt:stylesheet>"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/isoschematron/resources/xsl/iso-schematron-xslt1/iso_schematron_message.xsl",
    "content": "<?xml version=\"1.0\" ?><?xar XSLT?>\n<!-- Implmentation for the Schematron XML Schema Language.\n\thttp://www.ascc.net/xml/resource/schematron/schematron.html\n \n Copyright (c) 2000,2001 Rick Jelliffe and Academia Sinica Computing Center, Taiwan\n\n This software is provided 'as-is', without any express or implied warranty. \n In no event will the authors be held liable for any damages arising from \n the use of this software.\n\n Permission is granted to anyone to use this software for any purpose, \n including commercial applications, and to alter it and redistribute it freely,\n subject to the following restrictions:\n\n 1. The origin of this software must not be misrepresented; you must not claim\n that you wrote the original software. If you use this software in a product, \n an acknowledgment in the product documentation would be appreciated but is \n not required.\n\n 2. Altered source versions must be plainly marked as such, and must not be \n misrepresented as being the original software.\n\n 3. This notice may not be removed or altered from any source distribution.\n-->\n\n<!-- Schematron message -->\n\n<xsl:stylesheet\n   version=\"1.0\"\n   xmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\"\n   xmlns:axsl=\"http://www.w3.org/1999/XSL/TransformAlias\">\n\n<xsl:import href=\"iso_schematron_skeleton_for_xslt1.xsl\"/>\n\n<xsl:template name=\"process-prolog\">\n   <axsl:output method=\"text\" />\n</xsl:template>\n\n<!-- use default rule for process-root:  copy contens / ignore title -->\n<!-- use default rule for process-pattern: ignore name and see -->\n<!-- use default rule for process-name:  output name -->\n<!-- use default rule for process-assert and process-report:\n     call process-message -->\n\n<xsl:template name=\"process-message\">\n   <xsl:param name=\"pattern\" />\n   <xsl:param name=\"role\" />\n   <axsl:message>\n      <xsl:apply-templates mode=\"text\"  \n      /> (<xsl:value-of select=\"$pattern\" />\n      <xsl:if test=\"$role\"> / <xsl:value-of select=\"$role\" />\n      </xsl:if>)</axsl:message>\n</xsl:template>\n\n</xsl:stylesheet>"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/isoschematron/resources/xsl/iso-schematron-xslt1/iso_schematron_skeleton_for_xslt1.xsl",
    "content": "<?xml version=\"1.0\"?><?xar XSLT?>\n\n<!-- \n   OVERVIEW\n   \n   ASCC/Schematron.com Skeleton Module for ISO Schematron (for XSLT1 systems)\n   \n   ISO Schematron is a language for making assertion about the presence or absence\n   of patterns in XML documents. It is typically used for as a schema language, or\n   to augment existing schema languages, and to check business rules. It is very\n   powerful, yet quite simple: a developer only need know XPath and about five other\n   elements.\n   \n   This is an open source implementation of ISO Schematron in XSLT. Although ISO does\n   not allow reference implementations which might compete with the text of the\n   standard, this code has been compiled by Rick Jelliffe, inventor of Schematron\n   and editor of the ISO standard; so developers can certainly use it as an \n   unofficial reference implementation for clarification. \n   \n   This implementation is based on one by Oliver Becker. API documentation is \n   available separately; try www.schematron.com for this. Funding for this\n   stylesheet over the years has come from Topologi Pty. Ltd., Geotempo Ltd.,\n   and ASCC, Tapei.\n   \n   There are two versions of this skeleton: one is tailored for XSLT1 processors\n   and the other is tailored for XSLT2 processors. Future versions of the\n   XSLT2 skeleton may support more features than that the XSLT 1 skeleton.\n-->\n<!--\n   TIPS\n      \n   A tip for new users of Schematron: make your assertions contain positive messages\n   about what is expected, rather than error messages. For example, use the form\n   \"An X should have a Y, because Z\". \n   \n   Another tip is that Schematron provides an\n   element <sch:ns> for declaring the namespaces and prefixes used in Xpaths in \n   attribute values; it does not extend the XML Namespaces mechanism: if a name\n   in an XPath has a prefix, there must be an <sch:ns> element for that prefix; if\n   a name in an XPath does not have a prefix, it is always in no namespace.\n   \n   A tip for implementers of Schematron, either using this API or re-implementing it:\n   make the value of the diagnostics, flags and richer features available if possible;\n   Schematron has many of the optional richer features which, if implemented, provide\n   a compelling alternative approach to validation and business-rules checking compared\n   to other schema languages and programs. \n   \n   If you create your own meta-stylesheet to override this one, it is a\n   good idea to have both in the same directory and to run the stylesheet\n   from that directory, as many XSLT implementations have ideosyncratic\n   handling of URLs: keep it simple.\n-->\n \n\n<!--\n  INVOCATION INFORMATION\n  \n  The following parameters are available\n  \n    phase           NMTOKEN | \"#ALL\" (default) Select the phase for validation\n    allow-foreign   \"true\" | \"false\" (default)   Pass non-Schematron elements to the generated stylesheet\n    sch.exslt.imports semi-colon delimited string of filenames for some EXSLT implementations  \n    message-newline \"true\" (default) | \"false\"   Generate an extra newline at the end of messages\n    optimize        \"visit-no-attributes\"     \n    debug\t    \"true\" | \"false\" (default)  Debug mode lets compilation continue despite problems\n    attributes \"true\" | \"false\"  (Autodetecting) Use only when the schema has no attributes as the context nodes\n    only-child-elements \"true\" | \"false\" (Autodetecting) Use only when the schema has no comments\n    or PI  as the context nodes\n    \n  The following parameters can be specified as Schematron variables in diagnostics, assertions and so on.\n    fileNameParameter string\t  \n    fileDirParameter string\t\t\t\t\n    archiveNameParameter string\t  In case of ZIP files\n    archiveDirParameter string\t  In case of ZIP files\t\n    output-encoding\t\t\t\t  Use when outputting to XML\n \n Experimental: USE AT YOUR OWN RISK   \n    visit-text \"true\" \"false\"   Also visist text nodes for context. WARNING: NON_STARDARD.\n    select-contents '' | 'key' | '//'   Select different implementation strategies\n \n Conventions: Meta-stylesheets that override this may use the following parameters\n    generate-paths=true|false   generate the @location attribute with XPaths\n    diagnose= yes | no    Add the diagnostics to the assertion test in reports\n    terminate= yes | no   Terminate on the first failed assertion or successful report\n-->\n\n<!-- \n  XSLT VERSION SUPPORT\n\n  XSLT 1:\n     A schema using the standard XSLT 1 query binding will have a /schema/@queryBinding='xslt' or \n     nothing.\n\n       * Note: XT does not implement key() and will die if given it. \n       * Add all formal parameters to default templates\n       * Fix missing apply-templates from process-ns and add params back\n\n  EXSLT:  Experimental support\n     A schema using the EXSLT query binding will have a /schema/@queryBinding='exslt'.\n     It is built on XSLT 1. After experience is gained, this binding is expected to be \n     formalized as part of ISO Schematron, which currently reserves the \"exslt\" name for this purpose.\n\n     Some EXSLT engines have the extra functions built-in. For these, there is no need to\n     provide library locations. For engines that require the functions, either hard code\n     them in this script or provide them on the command-line argument.\n \n-->\n<!--\n   PROCESS INFORMATION\n   \n   This stylesheet compiles a Schematron schema (*.sch) into XSLT code (*.xsl). \n   The generated XSLT code can then be run against an XML file (*.xml, etc) and\n   will produce validation results.\n   \n   The output of validation results is performed using named templates (process-*). \n   These can be overridden easily by making a new XSLT stylesheet that imports this \n   stylesheet but has its own version of the relevant process-* templates. Several\n   of these invoking stylesheets are available: \"iso_svrl.xsl\", for example generates\n   ISO Schematron Validation Report Language format results.\n   \n   In this version of the stylesheet, the ISO feature called \"abstract patterns\" is\n   implemented using macro processing: a prior XSLT stage to which converts uses\n   of abstract patterns into normal patterns. If you do not use abstract patterns,\n   it is not necessary to preprocess the schema.\n   \n   To summarize, a basic process flow for some commandline processor is like this:\n     XSLT -input=xxx.sch  -output=xxx.xsl  -stylesheet=iso_schematron_skeleton.xsl\n     XSLT -input=document.xml  -output=xxx-document.results  -stylesheet=xxx.xsl\n   \n   iso_svrl.xslt is an implementation of Schematron that can use this skeleton and\n   generate ISO SVRL reports. A process flow for some commandline processor would\n   be like this:\n     XSLT -input=xxx.sch  -output=xxx.xsl  -stylesheet=iso_svrl.xsl\n     XSLT -input=document.xml  -output=xxx-document.results  -stylesheet=xxx.xsl\n     \n   It is not impossible that ultimately a third stage, to handle macro-preprocessing\n   and inclusion, might be necessary. (The trade-off is in making this XSLT more\n   complex compared to making the outer process more complex.)\n             \n  This version has so far been tested with\n     Saxon 8\n     MSXML 4 (or 6?)   \n\n Please note that if you are using SAXON and JAXP, then you should use \n  System.setProperty(\"javax.xml.transform.TransformerFactory\",\n                          \"net.sf.saxon.TransformerFactoryImpl\");\n rather than \n  System.setProperty(\"javax.xml.xpath.TransformerFactory\",\n                           \"net.sf.saxon.TransformerFactoryImpl\");\n which is does not work, at least for the versions of SAXON we tried.\n-->\n<!--\n LEGAL INFORMATION\n \n Copyright (c) 2000-2008 Rick Jelliffe and Academia Sinica Computing Center, Taiwan\n\n This software is provided 'as-is', without any express or implied warranty. \n In no event will the authors be held liable for any damages arising from \n the use of this software.\n\n Permission is granted to anyone to use this software for any purpose, \n including commercial applications, and to alter it and redistribute it freely,\n subject to the following restrictions:\n\n 1. The origin of this software must not be misrepresented; you must not claim\n that you wrote the original software. If you use this software in a product, \n an acknowledgment in the product documentation would be appreciated but is \n not required.\n\n 2. Altered source versions must be plainly marked as such, and must not be \n misrepresented as being the original software.\n\n 3. This notice may not be removed or altered from any source distribution.\n-->\n<!--\n  NOTE: Compared to the iso_schematron_skeleton_for_saxon.xsl code, this version is currently missing\n     1) localization\n     2) properties\n     3) pattern/@documents\n\n  VERSION INFORMATION \n   2009-02-25 RJ\n        * Fix up variable names so none are used twice in same template\n        * Tested on SAXON 9, Xalan 2.7.1. Partly tested MSXML.  \n   2008-09-19 RJ\n        * Add mode schematron-select-full-path and param full-path-notation \n   \n   2008-08-11\n   \t\t* TT report/@flag was missing\n   2008-08-06\n   \t\t* TT Top-level lets need to be implemented using xsl:param not xsl:variable\n   \t\t* TT xsl:param/@select must have XPath or not be specified\n   \t\t\n    Version: 2008-07-28\n   \t\t* KH schematron-get-full-path-3 has [index] even on top step\n   \t\t* RJ fix schematron-get-full-path to have namespace predicate, I don't know why this was removed\n   \t\t\n   Version: 2008-07-24\n   \t\t* RJ clean out commented out namespace handling code\n   \t\t* RJ add support for experimental non-standard attribute report/@action\n   \t\tand assert/@action, and add parameter not in the published API (should\n   \t\tnot break anything, it is XSLT1)\n   \t\t* RJ Remove remaining XSLT2 code for ease of reading\n   \t\t\n   Version: 2008-07-14 minor update for inclusion experiments\n   \t* RJ Clean up zero-length fragment test on include\n   \t* RJ Add experimental support for include containers \n   \t* RJ For path generation, test for //iso:schema not just /iso:schema, for potential embedded Schematron support   \n   \t* RJ Don't generate double error messages for old namespace elements\n   \t* RJ Experimental iso:rule/iso:title just kept as comment (bigger request Uche Ogbuji)\n   \t* RJ Remove spurious debug messages\n   \t* RJ Fix bug that prevented including patterns in this (report Roger\n   \tCostello)\n  \n   Version: 2007-10-17\n     From this version on I am forking XSLT2 support to a different version of the script.\n     This is due to the increasingly horrible state of the namespace handling code as well\n     as other inconsistencies between the major implementations of different versions.\n     The intent is that future versions of this will have XSLT2 isms removed and be simplified\n     to cope with only XSLT1 and EXLST. Note that though this version is called\n     iso_schematron_skeleton_for_xslt1, the various meta-stylesheets will continue to just call\n     iso_schematron_skeleton: it is up to you to rename the stylesheet to the one you want to\n     use.\n\n       * RJ fix FULL-PATH problem with attribute names\n\n\n   Version: 2007-07-19\n     Accept most changes in David Carlisle's fork, but continue as XSLT1 script: \n    \thttp://dpcarlisle.blogspot.com/search/label/schematron\n    \t* DPC Remove \"optimize\" parameter\n    \t* DPC Add autodetecting optimize parameter attribute to skip checking attribute\n    \tcontext\n    \t* DPC Add autodetecting optimize parameter only-child-elements turn off checking for \n    \tcomments and PIs\n    \t* DPC (Experimental: NON_STANDARD DANGER!) Add param visit-text to viist text\n    \tnodes too for context \n    \t* DPC Fix inclusion syntax to allow #\n    \t* DPC Priorities count up from 1000 not down from 4000 to allow more rules\n        * RJ Add new template for titles of schemas, with existing behaviour.  \n        Override process-schema-title for custom processing of title\n    \t\t\n    \n   Version: 2007-04-04\n   \t* RJ debug mode param\n\t* RJ alter mixed test to only test mixed branches, so the same document\n\tcould have old and new namespaces schemas in it, but each schema must\n\tbe distinct, just so as not to overconstrain things.\n   \t* KH zero-length include/@href is fatal error, but allow debug mode\n\t* SB add hint on SAXON and JAXP\n\t* DC generate-full-path-1 generates XLST1 code by default\n   Version: 2007-03-05\n      \t* AS Typo for EXSLT randome, improve comment\n      \t* KH get-schematron-full-path-2 needs to apply to attributes too\n      \t* DP document policy on extensions better\n      \t* DC use copy-of not copy for foreign elements\n      \t* DC add generate-path-2\n      \t* DC don't try to apply templates to attribute axis on attribute nodes, to\n      \tstop SAXON warning.\n      \t* RJ improve reporting of typos \n   \n   Version: 2007-02-08\n   \t\t* KH Schematron fullpath implementation: @* handled twice and / missing\n   \t\t* KH Change stylesheetbody from named template to mode to allow implementers more flexibility.\n   \t\t  Move process-ns to outside the stylesheet body.\n   \t\t* DP, FG, fix handling of xslt:key\n   \t\t* FG no iso:title/@class\n   \t\t* Experimental optimization 'visit-no-attributes'\n   \t\t* KH Experimental added schematron-get-full-path-2 which gives prefixed version for humans\n \t\t* DC Move stylesheet/@version generation to after namespace handling\n \t\t* DC, FG EXSLT namespace handling code\n \t\t* FG add ref and commented code from FG's page on namespaces\n \t\t* Start adding normalize-space() to parameter code\n \t\t* Add a space between diagnostics\n   \t\t   \t\t \n   Version: 2007-01-22\n   \t* DP change = ($start) to = $start and =($phase) to =$phase \n   \tto run under Saxon 8.8j\n\t* FG better title section using ( @id | sch:title)[last()]\n\t* Default query language binding is \"xslt\" not \"xslt1\"\n  \n   Version: 2007-01-19\n   \t\t* Simplify message newline code\n   \t\t* Remove termination and xpath appending to message options: \n   \t\t   factor out as  iso_schematron_terminator.xsl\n   \t\t* Comment out XSLT2 namespace fix temporarily\n  \n   Version: 2007-01-18 (First beta candidate for comment)\n          * DC remove xml:space=\"preserve\"\n          * FG improve comment on import statement\n          * DC improve comments on invocation section\n          * Add exploratory support for sch:schema[@queryBinding='xpath']\n             by allowing it and warning as lets are found\n          * Be strict about queryBinding spelling errors\n          * Extra comments on the different queryBindings\n          * KH Add option \"message-paths\" to generate XPath from output \n          * KH Add option \"terminate\" to halt with an error after the first assertion\n          * KH refactor paths in schematron-full-path\n          * Improve (?) namespace handling: no dummy attributes for prefix \"xsl\" generated\n   \n   Version: 2007-01-15\n          * FG fix for calling templates\n          * Add formal parameters to default templates: may help XSLT 2\n          * Fix get-schematron-full-path\n          * Include skeleton1-6 is commented out by default\n\n   Version:2007-01-12 (Pre-beta release to Schematron-love-in maillist)\n           * Add many extra parameters to the process-* calls, so that almost\n           all the information in the schema can be provided to client programs.\n           Also, rearrange the parameters to fit in with the ISO schema, which\n           has \"rich\" and \"linkable\" attribute groups.\n           * Warn on diagnostics with no ID once only\n           * Improved path reporting, to handle for namespaces\n           * Add process-title dummy template for API\n           * Add command-line parameter allow-foreign (true|false) to suppress\n            warnings one foreign elements and pass them through to the generated\n            stylesheet\n           * remove legacy templates for the old ASCC namespace and no namespace, \n              and use an import statement instead. Much cleaner now!\n           * patterns use @id not @name\n           * titles can contain sub-elements\n           * start change sch:rule to allow attributes, PIs and comments \n           * the default process-* for inline elements add a leading and trailing \n             space, to reduce the chance of concatenation.\n           * add comments to make the generated code clearer\n           \n   Version:2006-11-07 (ISO: first release private to schematron-love-in maillist for review)\n           * Duplicate pattern templates, for handling ISO namespace\n           * Add priority onto default and paragraph templates\n           * Add namespace checks\n           * Handle key in xsl namespace not iso\n           * Add include\n           * Improve namespace handling\n           * Preliminary XSLT2 and EXSLT support\n\t       * Refactor iso:schema for clarity\n\n    Version: 2003-05-26 \n    \t    * Fix bug with key \n    Version: 2003-04-16\n    \t   * handle 1.6 let expressions\n    \t   * make key use XSLT names, and allow anywhere\n    Version: 2001-06-13\n           * same skeleton now supports namespace or no namespace\n           * parameters to handlers updated for all 1.5 attributes \n           * diagnostic hints supported: command-line option diagnose=yes|no\n           * phases supported: command-line option phase=#ALL|...\n           * abstract rules\n           * compile-time error messages  \n\t   * add utility routine generate-id-from-path\n          \n    Contributors: Rick Jelliffe (original), Oliver Becker (architecture, XSLT2), \n             Miloslav Nic (diagnostic, phase, options), Ludwig Svenonius (abstract)\n             Uche Ogbuji (misc. bug fixes), Jim Ancona (SAXON workaround),\n\t \t     Francis Norton (generate-id-from-path), Robert Leftwich, Bryan Rasmussen,\n             Dave Pawson (include, fallback), Florent Georges (namespaces, exslt, attribute\n             context), Benoit Maisonny (attribute context), John Dumps (process-message newline),\n             Cliff Stanford (diagnostics and other newlines)\n\n    \n    KNOWN TYPICAL LIMITATIONS:\n      * Don't use <sch:ns prefix=\"xsl\" .../> with a namespace other than the standard\n      XSLT one. This would be a bizarre thing to do anyway. \n      * Don't use other prefixes for the XSLT namespace either; some implementations will\n      not handle it correctly.\n     \n     EXTENSIONS:\n      ISO Schematron is designed as a framework with some standard query language\n      bindings. If you need to support other features, please do so safely by making\n      up your own @queryLanguage name: this makes it clear that your schema requires\n      special features. For example, default ISO Schematron does not support user\n      defined functions; so if you want to use the user defined function feature\n      in XSLT, you need to have a schema with some queryBinding attribute name like\n      \"XSLT-with-my-functions\" or whatever.\n-->\n\n\n\n\n<xsl:stylesheet version=\"1.0\" \n\txmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\" \n\txmlns:axsl=\"http://www.w3.org/1999/XSL/TransformAlias\" \n\txmlns:sch=\"http://www.ascc.net/xml/schematron\"\n    xmlns:iso=\"http://purl.oclc.org/dsdl/schematron\" \n    xmlns:exsl=\"http://exslt.org/common\"\n    xmlns:msxsl=\"urn:schemas-microsoft-com:xslt\"\n    extension-element-prefixes=\"exsl  msxsl\"\n\t >\n<!-- This program implements ISO Schematron, except for abstract patterns which require a preprocess. -->\n  \n\n<xsl:namespace-alias stylesheet-prefix=\"axsl\" result-prefix=\"xsl\"/>\n\n\n<!-- Category: top-level-element -->\n<xsl:output method=\"xml\" omit-xml-declaration=\"no\" standalone=\"yes\"  indent=\"yes\"/>\n\n\n<xsl:param name=\"phase\">\n  <xsl:choose>\n    <xsl:when test=\"//sch:schema/@defaultPhase\">\n      <xsl:value-of select=\"//sch:schema/@defaultPhase\"/>\n    </xsl:when>   \n    <xsl:when test=\"//iso:schema/@defaultPhase\">\n      <xsl:value-of select=\"//iso:schema/@defaultPhase\"/>\n    </xsl:when>\n    <xsl:otherwise>#ALL</xsl:otherwise>\n  </xsl:choose>\n</xsl:param>\n\n<xsl:param name=\"allow-foreign\">false</xsl:param>\n\n<xsl:param name=\"message-newline\">true</xsl:param>\n\n<!-- DPC set to true if contexts should be checked on attribute nodes\n         defaults to true if there is any possibility that a context could match an attribute,\n         err on the side if caution, a context of *[.='@'] would cause this param to defualt to true\n         even though @ is in a string\n-->\n<xsl:param name=\"attributes\">\n  <xsl:choose>\n    <xsl:when test=\"//iso:rule[contains(@context,'@') or contains(@context,'attribute')]\">true</xsl:when>\n    <xsl:otherwise>false</xsl:otherwise>\n  </xsl:choose>\n</xsl:param>\n\n<!-- DPC set to true if contexts should be checked on just elements in the child axis\n         defaults to true if there is any possibility that a context could match an comment or PI\n         err on the side if caution, a context of *[.='('] would cause this param to defualt to true\n         even though ( is in a string, but node() comment() and processing-instruction()  all have a (\n-->\n<xsl:param name=\"only-child-elements\">\n  <xsl:choose>\n    <xsl:when test=\"//iso:rule[contains(@context,'(')]\">true</xsl:when>\n    <xsl:otherwise>false</xsl:otherwise>\n  </xsl:choose>\n</xsl:param>\n\n<!-- DPC set to true if contexts should be checked on text nodes nodes (if only-child-elements is false)\n         THIS IS NON CONFORMANT BEHAVIOUR JUST FOR DISCUSSION OF A POSSIBLE CHANGE TO THE\n         SPECIFICATION. THIS PARAM SHOULD GO IF THE FINAL DECISION IS THAT THE SPEC DOES NOT CHANGE.\n\t Always defaults to false\n-->\n<xsl:param name=\"visit-text\" select=\"'false'\"/>\n\n<!-- DPC\n  When selecting contexts the specified behaviour is\n    @*|node()[not(self::text())]\n    The automatic settings may use\n      node()[not(self::text())]\n      @*|*\n      *\n  instead for schema for which they are equivalent.\n  If the params are set explictly the above may be used, and also either if\n      @*\n      @*|node()\n   in all cases the result may not be equivalent, for example if you specify no attributes and the schema \n   does have attribute contexts they will be silently ignored.\n\n  after testing it turns out that\n  node()[not(self::text())] is slower in saxon than *|comment()|processing-instruction() \n  which I find a bit surprising but anyway I'll use the longr faster version.\n-->\n<xsl:variable name=\"context-xpath\">\n  <xsl:if test=\"$attributes='true'\">@*|</xsl:if>\n  <xsl:choose>\n    <xsl:when test=\"$only-child-elements='true'\">*</xsl:when>\n    <xsl:when test=\"$visit-text='true'\">node()</xsl:when>\n    <xsl:otherwise>*|comment()|processing-instruction()</xsl:otherwise>\n  </xsl:choose>\n</xsl:variable>\n\n<!-- DPC if this is set to \n    '' use recursive templates to iterate over document tree,\n    'key' select  all contexts with a key rather than walking the tree explictly in each mode\n    '//' select all contexts with // a key rather than walking the tree explictly in each mode (XSLT2 only)\n-->\n<xsl:param name=\"select-contexts\" select=\"''\"/>\n\n\n<xsl:param name=\"output-encoding\"/>\n<!-- e.g. saxon file.xml file.xsl \"sch.exslt.imports=.../string.xsl;.../math.xsl\" -->\n<xsl:param name=\"sch.exslt.imports\"/>\n\n<!-- Set the language code for messages -->\n<xsl:param name=\"langCode\">default</xsl:param>\n\n<xsl:param name=\"debug\">false</xsl:param>\n\n\n<!-- Set the default for schematron-select-full-path, i.e. the notation for svrl's @location-->\n<xsl:param name=\"full-path-notation\">1</xsl:param>\n\n<!-- Simple namespace check -->\n<xsl:template match=\"/\">\n    <xsl:if  test=\"//sch:*[ancestor::iso:* or descendant::iso:*]\">\n\t<xsl:message>Schema error: Schematron elements in old and new namespaces found</xsl:message>\n\t<xsl:if test=\" $debug = 'false' \" />\n    </xsl:if>\n\n    <xsl:apply-templates />\n</xsl:template>\n\n\n<!-- ============================================================== -->\n<!-- ISO SCHEMATRON SCHEMA ELEMENT  -->\n<!-- Not handled: Abstract patterns. A pre-processor is assumed. -->\n<!-- ============================================================== -->\n\n<!-- SCHEMA -->\n<!-- Default uses XSLT 1 -->\n<xsl:template match=\"iso:schema[not(@queryBinding) or @queryBinding='xslt' \n     or @queryBinding='xslt1' or @queryBinding='XSLT' or @queryBinding='XSLT1'\n     or @queryBinding='xpath']\">\n     <xsl:if test=\"\n\t     @queryBinding='xslt1' or @queryBinding='XSLT' or @queryBinding='XSLT1'\">\n\t     <xsl:message>Schema error: in the queryBinding attribute, use 'xslt'</xsl:message>\n\t</xsl:if>\n\t<axsl:stylesheet>\n\t    <xsl:apply-templates select=\"iso:ns\"/>\n\t    <!-- Handle the namespaces before the version attribute: reported to help SAXON -->\n\t    <xsl:attribute name=\"version\">1.0</xsl:attribute>\n\t    \n\t\t<xsl:apply-templates select=\".\" mode=\"stylesheetbody\"/>\n\t\t<!-- was xsl:call-template name=\"stylesheetbody\"/ -->\n\t</axsl:stylesheet>\n</xsl:template>\n\n<!-- Using EXSLT with all modeles (except function module: not applicable) -->\n<xsl:template match=\"iso:schema[@queryBinding='exslt']\" priority=\"10\">\n    <xsl:comment>This XSLT was automatically generated from a Schematron schema.</xsl:comment>\n\t<axsl:stylesheet\n \t  \txmlns:date=\"http://exslt.org/dates-and-times\"\n \t  \txmlns:dyn=\"http://exslt.org/dynamic\"\n\t\txmlns:exsl=\"http://exslt.org/common\"\n\t\txmlns:math=\"http://exslt.org/math\"\n   \t\txmlns:random=\"http://exslt.org/random\"\n  \t\txmlns:regexp=\"http://exslt.org/regular-expressions\"\n   \t\txmlns:set=\"http://exslt.org/sets\"\n   \t\txmlns:str=\"http://exslt.org/strings\"\n   \t\textension-element-prefixes=\"date dyn exsl math random regexp set str\" >\n\t\n        <xsl:apply-templates select=\"iso:ns\"/>\n\t    <!-- Handle the namespaces before the version attribute: reported to help SAXON -->\n\t    <xsl:attribute name=\"version\">1.0</xsl:attribute>\n\t    \n\t    <xsl:apply-templates select=\".\" mode=\"stylesheetbody\"/>\n\t\t<!-- was xsl:call-template name=\"stylesheetbody\"/ -->\n\t</axsl:stylesheet>\n</xsl:template>\n\n\n<!-- Default uses XSLT 1 -->\n<xsl:template match=\"iso:schema\" priority=\"-1\">\n\t<xsl:message terminate=\"yes\" >Fail: This implementation of ISO Schematron does not work with \n\tschemas using the \"<xsl:value-of select=\"@queryBinding\"/>\" query language.</xsl:message>        \n</xsl:template>\n\n<xsl:template match=\"*\" mode=\"stylesheetbody\">\n\t<!--xsl:template name=\"stylesheetbody\"-->\n    <xsl:comment>Implementers: please note that overriding process-prolog or process-root is \n    the preferred method for meta-stylesheets to use where possible. </xsl:comment><xsl:text>&#10;</xsl:text>\n\n   <!-- These parameters may contain strings with the name and directory of the file being\n   validated. For convenience, if the caller only has the information in a single string,\n   that string could be put in fileDirParameter. The archives parameters are available\n   for ZIP archives.\n\t-->\n\n\t<axsl:param name=\"archiveDirParameter\" />\n\t<axsl:param name=\"archiveNameParameter\" />\n\t<axsl:param name=\"fileNameParameter\" />\n\t<axsl:param name=\"fileDirParameter\" />\n\n    <xsl:call-template name=\"iso:exslt.add.imports\" />\n    <xsl:text>&#10;&#10;</xsl:text><xsl:comment>PHASES</xsl:comment><xsl:text>&#10;</xsl:text>\n\t<xsl:call-template name=\"handle-phase\"/>\n    <xsl:text>&#10;&#10;</xsl:text><xsl:comment>PROLOG</xsl:comment><xsl:text>&#10;</xsl:text>\n\t<xsl:call-template name=\"process-prolog\"/>\n    <xsl:text>&#10;&#10;</xsl:text><xsl:comment>KEYS</xsl:comment><xsl:text>&#10;</xsl:text>\n\t<xsl:apply-templates mode=\"do-keys\"   select=\"xsl:key  \"/>\n    <xsl:text>&#10;&#10;</xsl:text><xsl:comment>DEFAULT RULES</xsl:comment><xsl:text>&#10;</xsl:text>\n    <xsl:call-template name=\"generate-default-rules\" />\n    <xsl:text>&#10;&#10;</xsl:text><xsl:comment>SCHEMA METADATA</xsl:comment><xsl:text>&#10;</xsl:text>\n    <xsl:call-template name=\"handle-root\"/>\n    <xsl:text>&#10;&#10;</xsl:text><xsl:comment>SCHEMATRON PATTERNS</xsl:comment><xsl:text>&#10;</xsl:text>\n \n\t<xsl:apply-templates select=\"*[not(self::iso:ns)] \" />\n</xsl:template>\n \n    <xsl:template name=\"iso:exslt.add.imports\">\n      <xsl:param name=\"imports\" select=\"$sch.exslt.imports\"/>\n      <xsl:choose>\n        <xsl:when test=\"contains($imports, ';')\">\n          <axsl:import href=\"{ substring-before($imports, ';') }\"/>\n          <xsl:call-template name=\"iso:exslt.add.imports\">\n            <xsl:with-param name=\"imports\"  select=\"substring-after($imports, ';')\"/>\n          </xsl:call-template>\n        </xsl:when>\n        <xsl:when test=\"$imports\">\n          <axsl:import href=\"{ $imports }\"/>\n        </xsl:when>\n      </xsl:choose>\n    </xsl:template>\n\n<xsl:template name=\"handle-phase\" >\n\t<xsl:if test=\"not(normalize-space( $phase ) = '#ALL')\">\n\t  <xsl:if test=\"not(iso:phase[@id = normalize-space( $phase )])\">\n\t\t  <xsl:message>Phase Error: no phase with name <xsl:value-of select=\"normalize-space( $phase )\"\n\t\t  /> has been defined.</xsl:message>\n\t  </xsl:if>\n     </xsl:if>\n</xsl:template>\n\n<xsl:template name=\"generate-default-rules\">\n\t\t<xsl:text>&#10;&#10;</xsl:text>\n\t\t<xsl:comment>MODE: SCHEMATRON-SELECT-FULL-PATH</xsl:comment><xsl:text>&#10;</xsl:text>\n\t\t<xsl:comment>This mode can be used to generate an ugly though full XPath for locators</xsl:comment><xsl:text>&#10;</xsl:text>\n   \t\t<axsl:template match=\"*\" mode=\"schematron-select-full-path\">\n   \t\t\t<xsl:choose>\n   \t\t\t\t<xsl:when test=\" $full-path-notation = '1' \">\n   \t\t\t\t\t<!-- Use for computers, but rather unreadable for humans -->\n\t\t\t\t\t<axsl:apply-templates select=\".\" mode=\"schematron-get-full-path\"/>\n\t\t\t\t</xsl:when>\n   \t\t\t\t<xsl:when test=\" $full-path-notation = '2' \">\n   \t\t\t\t\t<!-- Use for humans, but no good for paths unless namespaces are known out-of-band -->\n\t\t\t\t\t<axsl:apply-templates select=\".\" mode=\"schematron-get-full-path-2\"/>\n\t\t\t\t</xsl:when>\n   \t\t\t\t<xsl:when test=\" $full-path-notation = '3' \"> \n   \t\t\t\t\t<!-- Obsolescent. Use for humans, but no good for paths unless namespaces are known out-of-band -->\n\t\t\t\t\t<axsl:apply-templates select=\".\" mode=\"schematron-get-full-path-3\"/>\n\t\t\t\t</xsl:when>\n\n                   <xsl:otherwise >\n                       <!-- Use for computers, but rather unreadable for humans -->\n                    <axsl:apply-templates select=\".\" mode=\"schematron-get-full-path\"/>\n                </xsl:otherwise>\n\t\t\t</xsl:choose>\n\t\t</axsl:template>\n\t\n\n\t\t<xsl:text>&#10;&#10;</xsl:text>\n\t\t<xsl:comment>MODE: SCHEMATRON-FULL-PATH</xsl:comment><xsl:text>&#10;</xsl:text>\n\t\t<xsl:comment>This mode can be used to generate an ugly though full XPath for locators</xsl:comment><xsl:text>&#10;</xsl:text>\n   \t\t<axsl:template match=\"*\" mode=\"schematron-get-full-path\">\n\t\t\t<axsl:apply-templates select=\"parent::*\" mode=\"schematron-get-full-path\"/>\n\t\t\t\n\t\t\t<!-- XSLT1 syntax -->\n\n\t\t\t<axsl:text>/</axsl:text>\n\t\t\t<axsl:choose>\n\t\t\t<axsl:when test=\"namespace-uri()=''\">\n\t\t\t<axsl:value-of select=\"name()\"/>\n\t\t\t<axsl:variable name=\"p_1\" select=\"1+\n\t\t\tcount(preceding-sibling::*[name()=name(current())])\" />\n\t\t<axsl:if test=\"$p_1&gt;1 or following-sibling::*[name()=name(current())]\">\n\t\t  <xsl:text/>[<axsl:value-of select=\"$p_1\"/>]<xsl:text/>\n\t\t</axsl:if>\n\t\t</axsl:when>\n\t\t<axsl:otherwise>\n\t\t<axsl:text>*[local-name()='</axsl:text>\n\t\t<axsl:value-of select=\"local-name()\"/><axsl:text>' and namespace-uri()='</axsl:text>\n\t\t<axsl:value-of select=\"namespace-uri()\"/>\n\t\t<axsl:text>']</axsl:text>\n\t\t<axsl:variable name=\"p_2\" select=\"1+\n\t\tcount(preceding-sibling::*[local-name()=local-name(current())])\" />\n\t\t<axsl:if test=\"$p_2&gt;1 or following-sibling::*[local-name()=local-name(current())]\">\n\t\t  <xsl:text/>[<axsl:value-of select=\"$p_2\"/>]<xsl:text/>\n\t\t</axsl:if>\n\t\t</axsl:otherwise>\n\t\t</axsl:choose> \n       \t \t</axsl:template>\n       \t \t\n       \t \t\n\t\t<axsl:template match=\"@*\" mode=\"schematron-get-full-path\">\n\t\t\n\t\t\t<!-- XSLT1 syntax -->\n\t\t<axsl:text>/</axsl:text>\n\t\t<axsl:choose>\n\t\t<axsl:when test=\"namespace-uri()=''\">@<axsl:value-of\n\t\tselect=\"name()\"/></axsl:when>\n\t\t<axsl:otherwise>\n\t\t<axsl:text>@*[local-name()='</axsl:text>\n\t\t<axsl:value-of select=\"local-name()\"/>\n\t\t<axsl:text>' and namespace-uri()='</axsl:text>\n\t\t<axsl:value-of select=\"namespace-uri()\"/>\n\t\t<axsl:text>']</axsl:text>\n\t\t</axsl:otherwise>\n\t\t</axsl:choose>   \n\n\t\t</axsl:template>\n\t\n\t\n\t<xsl:text>&#10;&#10;</xsl:text>\n\t\n\t<xsl:comment>MODE: SCHEMATRON-FULL-PATH-2</xsl:comment>\n\t<xsl:text>&#10;</xsl:text>\n\t<xsl:comment>This mode can be used to generate prefixed XPath for humans</xsl:comment>\n\t<xsl:text>&#10;</xsl:text>\n\t<!--simplify the error messages by using the namespace prefixes of the\n     instance rather than the generic namespace-uri-styled qualification-->\n\t<axsl:template match=\"node() | @*\" mode=\"schematron-get-full-path-2\">\n\t<!--report the element hierarchy-->\n\t\t<axsl:for-each select=\"ancestor-or-self::*\">\n\t\t\t<axsl:text>/</axsl:text>\n\t\t\t<axsl:value-of select=\"name(.)\"/>\n\t\t\t<axsl:if test=\"preceding-sibling::*[name(.)=name(current())]\">\n\t\t\t\t<axsl:text>[</axsl:text>\n\t\t\t\t<axsl:value-of\n\t\t\t\t\tselect=\"count(preceding-sibling::*[name(.)=name(current())])+1\"/>\n\t\t\t\t<axsl:text>]</axsl:text>\n\t\t\t</axsl:if>\n\t\t</axsl:for-each>\n\t\t<!--report the attribute-->\n\t\t<axsl:if test=\"not(self::*)\">\n\t\t\t<axsl:text/>/@<axsl:value-of select=\"name(.)\"/>\n\t\t</axsl:if>\n\t</axsl:template>\n\n\t\t<xsl:text>&#10;&#10;</xsl:text>\n\t\t<xsl:comment>MODE: GENERATE-ID-FROM-PATH </xsl:comment><xsl:text>&#10;</xsl:text>\n\t\t<!-- repeatable-id maker derived from Francis Norton's. -->\n\t\t<!-- use this if you need generate ids in separate passes,\n\t\t     because generate-id() is not guaranteed to produce the same\n\t\t     results each time. These ids are not XML names but closer to paths. -->\n\t\t<axsl:template match=\"/\" mode=\"generate-id-from-path\"/>\n\t\t<axsl:template match=\"text()\" mode=\"generate-id-from-path\">\n\t\t\t<axsl:apply-templates select=\"parent::*\" mode=\"generate-id-from-path\"/>\n\t\t\t<axsl:value-of select=\"concat('.text-', 1+count(preceding-sibling::text()), '-')\"/>\n\t\t</axsl:template>\n\t\t<axsl:template match=\"comment()\" mode=\"generate-id-from-path\">\n\t\t\t<axsl:apply-templates select=\"parent::*\" mode=\"generate-id-from-path\"/>\n\t\t\t<axsl:value-of select=\"concat('.comment-', 1+count(preceding-sibling::comment()), '-')\"/>\n\t\t</axsl:template>\n\t\t<axsl:template match=\"processing-instruction()\" mode=\"generate-id-from-path\">\n\t\t\t<axsl:apply-templates select=\"parent::*\" mode=\"generate-id-from-path\"/>\n\t\t\t<axsl:value-of \n\t\t\tselect=\"concat('.processing-instruction-', 1+count(preceding-sibling::processing-instruction()), '-')\"/>\n\t\t</axsl:template>\n\t\t<axsl:template match=\"@*\" mode=\"generate-id-from-path\">\n\t\t\t<axsl:apply-templates select=\"parent::*\" mode=\"generate-id-from-path\"/>\n\t\t\t<axsl:value-of select=\"concat('.@', name())\"/>\n\t\t</axsl:template>\n\t\t<axsl:template match=\"*\" mode=\"generate-id-from-path\" priority=\"-0.5\">\n\t\t\t<axsl:apply-templates select=\"parent::*\" mode=\"generate-id-from-path\"/>\n\t\t\t<axsl:text>.</axsl:text>\n<!--\n\t\t\t<axsl:choose>\n\t\t\t\t<axsl:when test=\"count(. | ../namespace::*) = count(../namespace::*)\">\n\t\t\t\t\t<axsl:value-of select=\"concat('.namespace::-',1+count(namespace::*),'-')\"/>\n\t\t\t\t</axsl:when>\n\t\t\t\t<axsl:otherwise>\n-->\n\t\t\t\t<axsl:value-of \n\t\t\t\tselect=\"concat('.',name(),'-',1+count(preceding-sibling::*[name()=name(current())]),'-')\"/>\n<!--\n\t\t\t\t</axsl:otherwise>\n\t\t\t</axsl:choose>\n-->\n\t\t</axsl:template>\n\t\t\n\t\t\n\t<xsl:comment>MODE: SCHEMATRON-FULL-PATH-3</xsl:comment>\n\t\n\t<xsl:text>&#10;</xsl:text>\n\t<xsl:comment>This mode can be used to generate prefixed XPath for humans \n\t(Top-level element has index)</xsl:comment>\n\t<xsl:text>&#10;</xsl:text>\n\t<!--simplify the error messages by using the namespace prefixes of the\n     instance rather than the generic namespace-uri-styled qualification-->\n\t<axsl:template match=\"node() | @*\" mode=\"schematron-get-full-path-3\">\n\t<!--report the element hierarchy-->\n\t\t<axsl:for-each select=\"ancestor-or-self::*\">\n\t\t\t<axsl:text>/</axsl:text>\n\t\t\t<axsl:value-of select=\"name(.)\"/>\n\t\t\t<axsl:if test=\"parent::*\">\n\t\t\t\t<axsl:text>[</axsl:text>\n\t\t\t\t<axsl:value-of\n\t\t\t\t\tselect=\"count(preceding-sibling::*[name(.)=name(current())])+1\"/>\n\t\t\t\t<axsl:text>]</axsl:text>\n\t\t\t</axsl:if>\n\t\t</axsl:for-each>\n\t\t<!--report the attribute-->\n\t\t<axsl:if test=\"not(self::*)\">\n\t\t\t<axsl:text/>/@<axsl:value-of select=\"name(.)\"/>\n\t\t</axsl:if>\n\t</axsl:template>\n\n\t\t<xsl:text>&#10;&#10;</xsl:text>\n\t\t<xsl:comment>MODE: GENERATE-ID-2 </xsl:comment><xsl:text>&#10;</xsl:text>\n\t\t<!-- repeatable-id maker from David Carlisle. -->\n\t\t<!-- use this if you need generate IDs in separate passes,\n\t\t     because generate-id() is not guaranteed to produce the same\n\t\t     results each time. These IDs are well-formed XML NMTOKENS -->\n\t<axsl:template match=\"/\" mode=\"generate-id-2\">U</axsl:template>\n\n\t<axsl:template match=\"*\" mode=\"generate-id-2\" priority=\"2\">\n\t\t<axsl:text>U</axsl:text>\n\t\t<axsl:number level=\"multiple\" count=\"*\"/>\n\t</axsl:template>\n\n\t<axsl:template match=\"node()\" mode=\"generate-id-2\">\n\t\t<axsl:text>U.</axsl:text>\n\t\t<axsl:number level=\"multiple\" count=\"*\"/>\n\t\t<axsl:text>n</axsl:text>\n\t\t<axsl:number count=\"node()\"/>\n\t</axsl:template>\n\n\t<axsl:template match=\"@*\" mode=\"generate-id-2\">\n\t\t<axsl:text>U.</axsl:text>\n\t\t<axsl:number level=\"multiple\" count=\"*\"/>\n\t\t<axsl:text>_</axsl:text>\n\t\t<axsl:value-of select=\"string-length(local-name(.))\"/>\n\t\t<axsl:text>_</axsl:text>\n\t\t<axsl:value-of select=\"translate(name(),':','.')\"/>\n\t</axsl:template> \n\n\n\t\t<xsl:comment>Strip characters</xsl:comment>\n\t\t<axsl:template match=\"text()\" priority=\"-1\" />\n\t\t\t\n  </xsl:template>\n\n <xsl:template name=\"handle-root\">\n\t\t<!-- Process the top-level element -->\n\t\t<axsl:template match=\"/\">\n\t\t\t<xsl:call-template name=\"process-root\">\n\t\t\t\t<xsl:with-param \t\n\t\t\t\tname=\"title\" select=\"(@id | iso:title)[last()]\"/>\n\t\t\t\t<xsl:with-param name=\"version\" select=\"'iso'\" />\n\t\t\t\t<xsl:with-param name=\"schemaVersion\" select=\"@schemaVersion\" />\n\t\t\t\t<xsl:with-param name=\"queryBinding\" select=\"@queryBinding\" />\n\t\t\t\t<xsl:with-param name=\"contents\">\n\t\t\t\t\t<xsl:apply-templates mode=\"do-all-patterns\"/>\n\t\t\t\t</xsl:with-param>\n\t\t\t\t\n\t\t\t\t<!-- \"Rich\" properties -->\n\t\t\t\t<xsl:with-param name=\"fpi\" select=\"@fpi\"/>\n\t\t\t\t<xsl:with-param name=\"icon\" select=\"@icon\"/>\n\t\t\t\t<xsl:with-param name=\"id\" select=\"@id\"/>\n\t\t\t\t<xsl:with-param name=\"lang\" select=\"@xml:lang\"/>\n\t\t\t\t<xsl:with-param name=\"see\" select=\"@see\" />\n\t\t\t\t<xsl:with-param name=\"space\" select=\"@xml:space\" />\n\t\t\t\t\n\t\t\t\t\n\t\t\t\t<!-- Non-standard extensions not part of the API yet -->\n\t\t\t\t<xsl:with-param name=\"action\" select=\"@action\" />\n\t\t\t</xsl:call-template>\n\t\t</axsl:template>\n \n      \n</xsl:template>\n\n<!-- ============================================================== -->\n<!-- ISO SCHEMATRON ELEMENTS -->\n<!-- ============================================================== -->\n\n\t<!-- ISO ACTIVE -->\n\t<xsl:template match=\"iso:active\">\n                <xsl:if test=\"not(@pattern)\">\n                    <xsl:message>Markup Error: no pattern attribute in &lt;active></xsl:message>\n                </xsl:if>\n\n                <xsl:if test=\"not(../../iso:pattern[@id = current()/@pattern])\n                and not(../../iso:include)\">\n                           <xsl:message>Reference Error: the pattern  \"<xsl:value-of select=\"@pattern\"\n\t\t\t\t\t\t   />\" has been activated but is not declared</xsl:message>\n                </xsl:if>\n        </xsl:template>\n\n\t<!-- ISO ASSERT and REPORT -->\n\t<xsl:template match=\"iso:assert\">\n  \n                <xsl:if test=\"not(@test)\">\n                    <xsl:message>Markup Error: no test attribute in &lt;assert</xsl:message>\n                </xsl:if>\n        <xsl:text>&#10;&#10;\t\t</xsl:text>\n\t\t<xsl:comment>ASSERT <xsl:value-of select=\"@role\" /> </xsl:comment><xsl:text>&#10;</xsl:text>      \n\t\n\t\t<axsl:choose>\n\t\t\t<axsl:when test=\"{@test}\"/>\n\t\t\t<axsl:otherwise>\n\t\t\t\t<xsl:call-template name=\"process-assert\">\n\t\t\t\t\t<xsl:with-param name=\"test\" select=\"normalize-space(@test)\" />\n\t\t\t\t\t<xsl:with-param name=\"diagnostics\" select=\"@diagnostics\"/>\n\t\t\t\t\t<xsl:with-param name=\"flag\" select=\"@flag\"/>\n\t\t\t\t\t\n\t\t\t\t\t<!-- \"Rich\" properties -->\n\t\t\t\t\t<xsl:with-param name=\"fpi\" select=\"@fpi\"/>\n\t\t\t\t\t<xsl:with-param name=\"icon\" select=\"@icon\"/>\n\t\t\t\t\t<xsl:with-param name=\"id\" select=\"@id\"/>\n\t\t\t\t\t<xsl:with-param name=\"lang\" select=\"@xml:lang\"/>\n\t\t\t\t\t<xsl:with-param name=\"see\" select=\"@see\" />\n\t\t\t\t\t<xsl:with-param name=\"space\" select=\"@xml:space\" />\n\t\t\t\t\t\n\t\t\t\t\t<!-- \"Linking\" properties -->\n\t\t\t\t\t<xsl:with-param name=\"role\" select=\"@role\" />\n\t\t\t\t\t<xsl:with-param name=\"subject\" select=\"@subject\" />\n\t\t\t\t</xsl:call-template>\n \t\t\t\n\t\t\t</axsl:otherwise>\n\t\t</axsl:choose>\n\t</xsl:template>\n\t<xsl:template match=\"iso:report\">\n\t\t \n                <xsl:if test=\"not(@test)\">\n                    <xsl:message>Markup Error: no test attribute in &lt;report></xsl:message>\n                </xsl:if>\n                \n        <xsl:text>&#10;&#10;\t\t</xsl:text>\n\t\t<xsl:comment>REPORT <xsl:value-of select=\"@role\" /> </xsl:comment><xsl:text>&#10;</xsl:text>      \n\t\n\t\t<axsl:if test=\"{@test}\">\n\t\t\n\t\t\t<xsl:call-template name=\"process-report\">\n\t\t\t\t<xsl:with-param name=\"test\" select=\"normalize-space(@test)\" />\n\t\t\t\t<xsl:with-param name=\"diagnostics\" select=\"@diagnostics\"/>\n\t\t\t\t\t<xsl:with-param name=\"flag\" select=\"@flag\"/>\n\t\t\t\t\t\n\t\t\t\t\t<!-- \"Rich\" properties -->\n\t\t\t\t\t<xsl:with-param name=\"fpi\" select=\"@fpi\"/>\n\t\t\t\t\t<xsl:with-param name=\"icon\" select=\"@icon\"/>\n\t\t\t\t\t<xsl:with-param name=\"id\" select=\"@id\"/>\n\t\t\t\t\t<xsl:with-param name=\"lang\" select=\"@xml:lang\"/>\n\t\t\t\t\t<xsl:with-param name=\"see\" select=\"@see\" />\n\t\t\t\t\t<xsl:with-param name=\"space\" select=\"@xml:space\" />\n\t\t\t\t\t\n\t\t\t\t\t<!-- \"Linking\" properties -->\n\t\t\t\t\t<xsl:with-param name=\"role\" select=\"@role\" />\n\t\t\t\t\t<xsl:with-param name=\"subject\" select=\"@subject\" />\n\t\t\t</xsl:call-template>\n\t\t\t\t\n\t\t</axsl:if>\n\t</xsl:template>\n\n\n\t<!-- ISO DIAGNOSTIC -->\n\t<!-- We use a mode here to maintain backwards compatability, instead of adding it\n\t     to the other mode.\n\t-->\n\t<xsl:template match=\"iso:diagnostic\" mode=\"check-diagnostics\">\n              <xsl:if test=\"not(@id)\">\n                    <xsl:message>Markup Error: no id attribute in &lt;diagnostic></xsl:message>\n               </xsl:if>\n    </xsl:template>\n    \n    <xsl:template match=\"iso:diagnostic\"  >\n                <xsl:call-template name=\"process-diagnostic\">\n                \n\t\t\t\t\t<!-- \"Rich\" properties -->\n\t\t\t\t\t<xsl:with-param name=\"fpi\" select=\"@fpi\"/>\n\t\t\t\t\t<xsl:with-param name=\"icon\" select=\"@icon\"/>\n\t\t\t\t\t<xsl:with-param name=\"id\" select=\"@id\"/>\n\t\t\t\t\t<xsl:with-param name=\"lang\" select=\"@xml:lang\"/>\n\t\t\t\t\t<xsl:with-param name=\"see\" select=\"@see\" />\n\t\t\t\t\t<xsl:with-param name=\"space\" select=\"@xml:space\" />\n               </xsl:call-template>\n        </xsl:template>\n\n\t<!-- ISO DIAGNOSTICS -->\n\t<xsl:template match=\"iso:diagnostics\" >\n\t\t<xsl:apply-templates mode=\"check-diagnostics\" select=\"*\" />\n\t</xsl:template>\n\n\t<!-- ISO DIR -->\n\t<xsl:template match=\"iso:dir\"  mode=\"text\" >\n\t\t<xsl:call-template name=\"process-dir\">\n\t\t\t<xsl:with-param name=\"value\" select=\"@value\"/>\n\t\t</xsl:call-template>\n\t</xsl:template>\n\n\t<!-- ISO EMPH -->\n\t<xsl:template match=\"iso:emph\"  mode=\"text\">\n\t \n\t\t<xsl:call-template name=\"process-emph\"/> \n\n\t</xsl:template>\n\n\t<!-- ISO EXTENDS -->\n\t<xsl:template match=\"iso:extends\">\n\t\t<xsl:if test=\"not(@rule)\">\n                   <xsl:message>Markup Error: no rule attribute in &lt;extends></xsl:message>\n                </xsl:if>\n     \t\t<xsl:if test=\"not(//iso:rule[@abstract='true'][@id= current()/@rule] )\">\n                    <xsl:message>Reference Error: the abstract rule  \"<xsl:value-of select=\"@rule\"\n\t\t\t\t\t/>\" has been referenced but is not declared</xsl:message>\n                </xsl:if>\n\t        <xsl:call-template name=\"IamEmpty\" />\n\n  \t\t<xsl:if test=\"//iso:rule[@id=current()/@rule]\">\n    \t\t\t<xsl:apply-templates select=\"//iso:rule[@id=current()/@rule]\"\n\t\t\t\tmode=\"extends\"/>\n  \t\t</xsl:if>\n\n\t</xsl:template>\n\n\t<!-- KEY: ISO has no KEY -->\n\t<!-- NOTE: \n\t     Key has had a checkered history. Schematron 1.0 allowed it in certain places, but\n\t     users came up with a different location, which has now been adopted. \n\t     \n\t     XT, the early XSLT processor, did not implement key and died when it was present. \n\t     So there are some versions of the Schematron skeleton for XT that strip out all\n\t     key elements.\n\t     \n\t     Xalan (e.g. Xalan4C 1.0 and a Xalan4J) also had a funny. A fix involved making \n\t     a top-level parameter called $hiddenKey and then using that instead of matching\n\t     \"key\". This has been removed.\n\t-->\n\t<xsl:template  match=\"xsl:key\" mode=\"do-keys\" >\n\t     <xsl:if test=\"not(@name)\">\n              <xsl:message>Markup Error: no name attribute in &lt;key></xsl:message>\n         </xsl:if>\n                <xsl:if test=\"not(@path) and not(@use)\">\n                    <xsl:message>Markup Error: no path or use attribute in &lt;key></xsl:message>\n                </xsl:if>         \n\t     <xsl:choose>\n\t     \t<xsl:when test=\"parent::iso:rule \">\n\t        <xsl:call-template name=\"IamEmpty\" />\n\t       <xsl:choose>\n\t       \t<xsl:when test=\"@path\">\n\t\t\t\t<axsl:key match=\"{../@context}\" name=\"{@name}\" use=\"{@path}\"/>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise>\n\t\t\t\t\t\t\t<axsl:key match=\"{../@context}\" name=\"{@name}\" use=\"{@use}\"/>\n\t\t\t</xsl:otherwise>\n\t\t\t</xsl:choose>\t\n\t\t</xsl:when>\n\t\t<xsl:otherwise>\n                <xsl:if test=\"not(@match) \">\n                    <xsl:message>Markup Error: no path or use attribute in &lt;key></xsl:message>\n                </xsl:if>   \t\t\n\t\t\t<axsl:key>\n      \t\t\t<xsl:copy-of select=\"@*\"/>\n    \t\t</axsl:key>\t\n\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\t</xsl:template>\n\n\t<xsl:template match=\"xsl:key \"  /><!-- swallow -->\n\n\t<xsl:template match=\"iso:key \"  >\n\t\t<xsl:message>Schema error: The key element is not in the ISO Schematron namespace. Use the XSLT namespace.</xsl:message>\n    </xsl:template>\n\n   <!-- ISO INCLUDE -->\n   <!-- This is only a fallback. Include really needs to have been done before this as a separate pass.-->\n\n   <xsl:template match=\"iso:include[not(normalize-space(@href))]\"\n\t   priority=\"1\">\n\t<xsl:if test=\" $debug = 'false' \">\n\t\t<xsl:message terminate=\"yes\">Schema error: Empty href= attribute for include directive.</xsl:message>\n\t</xsl:if>\n\n   </xsl:template>\n\n   <!-- Extend the URI syntax to allow # refererences -->\n   <!-- Add experimental support for simple containers like  /xxx:xxx/iso:pattern to allow better includes -->\n   <xsl:template match=\"iso:include\">\n       <xsl:variable name=\"document-uri\" select=\"substring-before(concat(@href,'#'), '#')\"/>\n       <xsl:variable name=\"fragment-id\" select=\"substring-after(@href, '#')\"/>\n       \n       <xsl:choose> \n          \n          <xsl:when test=\"string-length( $document-uri ) = 0 and string-length( $fragment-id ) = 0\" >\n          \t<xsl:message>Error: Impossible URL in Schematron include</xsl:message>\n          </xsl:when> \n          \n          <xsl:when test=\"string-length( $fragment-id ) &gt; 0\">\n              <xsl:variable name=\"theDocument_1\" select=\"document( $document-uri,/ )\" />\n              <xsl:variable name=\"theFragment_1\" select=\"$theDocument_1//iso:*[@id= $fragment-id ]\" />\n              <xsl:if test=\" $theFragment_1/self::iso:schema \">\n                 <xsl:message>Schema error: Use include to include fragments, not a whole schema</xsl:message>\n              </xsl:if>\n              <xsl:apply-templates select=\" $theFragment_1\"/>\n\t\t   </xsl:when>\n\t\t  \n\t\t   <xsl:otherwise>\n              <xsl:variable name=\"theDocument_2\" select=\"document( $document-uri,/ )\" />\n              <xsl:variable name=\"theFragment_2\" select=\"$theDocument_2/iso:*\" />\n              <xsl:variable name=\"theContainedFragments\" select=\"$theDocument_2/*/iso:*\" />\n              <xsl:if test=\" $theFragment_2/self::iso:schema or $theContainedFragments/self::iso:schema\">\n                 <xsl:message>Schema error: Use include to include fragments, not a whole schema</xsl:message>\n              </xsl:if>\n       \t\t<xsl:apply-templates select=\"$theFragment_2 | $theContainedFragments \"/>\n       \t   </xsl:otherwise>\n       </xsl:choose>\n   </xsl:template>\n\n   <!-- This is to handle the particular case of including patterns -->  \n   <xsl:template match=\"iso:include\" mode=\"do-all-patterns\">\n       <xsl:variable name=\"document-uri\" select=\"substring-before(concat(@href,'#'), '#')\"/>\n       <xsl:variable name=\"fragment-id\" select=\"substring-after(@href, '#')\"/>\n \n       <xsl:choose> \n          \n          <xsl:when test=\"string-length( $document-uri ) = 0 and string-length( $fragment-id ) = 0\" >\n          \t<xsl:message>Error: Impossible URL in Schematron include</xsl:message>\n          </xsl:when> \n          \n          <xsl:when test=\"string-length( $fragment-id ) &gt; 0\">\n              <xsl:variable name=\"theDocument_1\" select=\"document( $document-uri,/ )\" />\n              <xsl:variable name=\"theFragment_1\" select=\"$theDocument_1//iso:*[@id= $fragment-id ]\" />\n              <xsl:if test=\" $theFragment_1/self::iso:schema \">\n                 <xsl:message>Schema error: Use include to include fragments, not a whole schema</xsl:message>\n              </xsl:if>\n              <xsl:apply-templates select=\" $theFragment_1\" mode=\"do-all-patterns\"/>\n\t\t   </xsl:when>\n\t\t  \n\t\t   <xsl:otherwise>\n\t\t   \t  <!-- Import the top-level element if it is in schematron namespace,\n\t\t   \t  or its children otherwise, to allow a simple containment mechanism. -->\n              <xsl:variable name=\"theDocument_2\" select=\"document( $document-uri,/ )\" />\n              <xsl:variable name=\"theFragment_2\" select=\"$theDocument_2/iso:*\" />\n              <xsl:variable name=\"theContainedFragments\" select=\"$theDocument_2/*/iso:*\" />\n              <xsl:if test=\" $theFragment_2/self::iso:schema or $theContainedFragments/self::iso:schema\">\n                 <xsl:message>Schema error: Use include to include fragments, not a whole schema</xsl:message>\n              </xsl:if>\n       \t\t<xsl:apply-templates select=\"$theFragment_2 | $theContainedFragments \"\n       \t\tmode=\"do-all-patterns\" />\n       \t   </xsl:otherwise>\n       </xsl:choose>\n   </xsl:template>\n   \n\t<!-- ISO LET -->\n\t<xsl:template match=\"iso:let\" >\n\t  <xsl:if test=\"ancestor::iso:schema[@queryBinding='xpath']\">\n                    <xsl:message>Warning: Variables should not be used with the \"xpath\" query language binding.</xsl:message>\n       </xsl:if>\n\t\t\n       <!-- lets at the top-level are implemented as parameters -->\n \n       \t<xsl:choose>\n       \t\t<xsl:when test=\"parent::iso:schema\">\n       \t\t\t<!-- it is an error to have an empty param/@select because an XPath is expected -->\n\t      \t\t <axsl:param name=\"{@name}\" select=\"{@value}\">\n\t      \t\t \t\t<xsl:if test=\"string-length(@value) &gt; 0\">\n\t      \t\t \t\t\t<xsl:attribute name=\"select\"><xsl:value-of select=\"@value\"/></xsl:attribute>\n\t      \t\t \t\t</xsl:if>\n\t      \t\t </axsl:param> \n       \t\t</xsl:when>\n       \t\t<xsl:otherwise>\n\t\t\t\t<axsl:variable name=\"{@name}\" select=\"{@value}\"/>\n\t\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\t\t  \n\t</xsl:template>\t\n\n\t<!-- ISO NAME -->\n\t<xsl:template match=\"iso:name\" mode=\"text\">\n\t\n\t\t<xsl:if test=\"@path\">\n\t\t\t<xsl:call-template name=\"process-name\">\n\t\t\t\t<xsl:with-param name=\"name\" select=\"concat('name(',@path,')')\"/>\n\t\t\t</xsl:call-template>\n\t\t</xsl:if>\n\t\t<xsl:if test=\"not(@path)\">\n\t\t\t<xsl:call-template name=\"process-name\">\n\t\t\t\t<xsl:with-param name=\"name\" select=\"'name(.)'\"/>\n\t\t\t</xsl:call-template>\n\t\t</xsl:if>\n\t    <xsl:call-template name=\"IamEmpty\" />\n\t</xsl:template>\n\n\t<!-- ISO NS -->\n\t<!-- Namespace handling is XSLT is quite tricky and implementation dependent -->\n\t<xsl:template match=\"iso:ns\">\n \t\t<xsl:call-template name=\"handle-namespace\" />\n\t</xsl:template>\n\n    <!-- This template is just to provide the API hook -->\n\t<xsl:template match=\"iso:ns\"  mode=\"do-all-patterns\" >\n               <xsl:if test=\"not(@uri)\">\n                    <xsl:message>Markup Error: no uri attribute in &lt;ns></xsl:message>\n                </xsl:if>\n               <xsl:if test=\"not(@prefix)\">\n                    <xsl:message>Markup Error: no prefix attribute in &lt;ns></xsl:message>\n                </xsl:if>\n\t        <xsl:call-template name=\"IamEmpty\" />\n\t\t<xsl:call-template name=\"process-ns\" >\n\t\t\t<xsl:with-param name=\"prefix\" select=\"@prefix\"/>\n\t\t\t<xsl:with-param name=\"uri\" select=\"@uri\"/>\n\t\t</xsl:call-template>\n\t</xsl:template>\n\n\t<!-- ISO P -->\n\t<xsl:template match=\"iso:schema/iso:p \" mode=\"do-schema-p\" >\n\t\t<xsl:call-template name=\"process-p\">\n\t\t\t<xsl:with-param name=\"class\" select=\"@class\"/>\n\t\t\t<xsl:with-param name=\"icon\" select=\"@icon\"/>\n\t\t\t<xsl:with-param name=\"id\" select=\"@id\"/>\n\t\t\t<xsl:with-param name=\"lang\" select=\"@xml:lang\"/>\n\t\t</xsl:call-template>\n\t</xsl:template>\n\t<xsl:template match=\"iso:pattern/iso:p \" mode=\"do-pattern-p\" >\n\t\t<xsl:call-template name=\"process-p\">\n\t\t\t<xsl:with-param name=\"class\" select=\"@class\"/>\n\t\t\t<xsl:with-param name=\"icon\" select=\"@icon\"/>\n\t\t\t<xsl:with-param name=\"id\" select=\"@id\"/>\n\t\t\t<xsl:with-param name=\"lang\" select=\"@xml:lang\"/>\n\t\t</xsl:call-template>\n\t</xsl:template>\n\t\n    <!-- Currently, iso:p in other position are not passed through to the API -->\n\t<xsl:template match=\"iso:phase/iso:p\" />\n\t<xsl:template match=\"iso:p \" priority=\"-1\" />\n\n\t<!-- ISO PATTERN -->\n\t<xsl:template match=\"iso:pattern\" mode=\"do-all-patterns\">\n\t<xsl:if test=\"($phase = '#ALL') \n\tor (../iso:phase[@id= $phase]/iso:active[@pattern= current()/@id])\">\n\t\t<xsl:call-template name=\"process-pattern\">\n\t\t\t<!-- the following select statement assumes that\n\t\t\t@id | sch:title returns node-set in document order:\n\t\t\twe want the title if it is there, otherwise the @id attribute -->\n\t\t\t<xsl:with-param name=\"name\" select=\"(@id | iso:title )[last()]\"/>\n\t\t\t<xsl:with-param name=\"is-a\" select=\"''\"/>\n\t\t\t\n\t\t\t\t\t<!-- \"Rich\" properties -->\n\t\t\t\t\t<xsl:with-param name=\"fpi\" select=\"@fpi\"/>\n\t\t\t\t\t<xsl:with-param name=\"icon\" select=\"@icon\"/>\n\t\t\t\t\t<xsl:with-param name=\"id\" select=\"@id\"/>\n\t\t\t\t\t<xsl:with-param name=\"lang\" select=\"@xml:lang\"/>\n\t\t\t\t\t<xsl:with-param name=\"see\" select=\"@see\" />\n\t\t\t\t\t<xsl:with-param name=\"space\" select=\"@xml:space\" />\n\t\t</xsl:call-template>\n\t\t<xsl:choose>\n\t\t  <xsl:when test=\"$select-contexts='key'\">\n\t\t    <axsl:apply-templates select=\"key('M','M{count(preceding-sibling::*)}')\" mode=\"M{count(preceding-sibling::*)}\"/>\n\t\t  </xsl:when>\n\t\t  <xsl:when test=\"$select-contexts='//'\">\n\t\t    <axsl:apply-templates mode=\"M{count(preceding-sibling::*)}\">\n\t\t      <xsl:attribute name=\"select\">\n\t\t\t<xsl:text>//(</xsl:text>\n\t\t\t<xsl:for-each select=\"iso:rule/@context\">\n\t\t\t  <xsl:text>(</xsl:text>\n\t\t\t  <xsl:value-of select=\".\"/>\n\t\t\t  <xsl:text>)</xsl:text>\n\t\t\t  <xsl:if test=\"position()!=last()\">|</xsl:if>\n\t\t\t</xsl:for-each>\n\t\t\t<xsl:text>)</xsl:text>\n\t\t\t<xsl:if test=\"$visit-text='false'\">[not(self::text())]</xsl:if>\n\t\t      </xsl:attribute>\n\t\t    </axsl:apply-templates>\n\t\t  </xsl:when>\n\t\t  <xsl:otherwise>\n\t\t    <axsl:apply-templates select=\"/\" mode=\"M{count(preceding-sibling::*)}\"/>\n\t\t  </xsl:otherwise>\n\t\t</xsl:choose>\n        </xsl:if>\n\t</xsl:template>\n\t\n\t<xsl:template match=\"iso:pattern[@abstract='true']\">\n    \n             <xsl:message>Schema implementation error: This schema has abstract patterns, yet they are supposed to be preprocessed out already\n             </xsl:message>\n    </xsl:template>\n\n    <!-- Here is the template for the normal case of patterns -->\n\t<xsl:template match=\"iso:pattern[not(@abstract='true')]\">\n     \n      <xsl:if test=\"($phase = '#ALL') \n\t          or (../iso:phase[@id= $phase]/iso:active[@pattern= current()/@id])\">\n \n\t\t<xsl:text>&#10;&#10;</xsl:text>\n\t\t<xsl:comment>PATTERN <xsl:value-of select=\"@id\" /> <xsl:value-of select=\"iso:title\" /> </xsl:comment><xsl:text>&#10;</xsl:text>      \n\t\t<xsl:apply-templates />\n\t\t\n\t\t<!-- DPC select-contexts test -->\n\t\t<xsl:if test=\"not($select-contexts)\">\n\t\t  <axsl:template match=\"text()\" priority=\"-1\" mode=\"M{count(preceding-sibling::*)}\">\n\t\t    <!-- strip characters -->\n\t\t  </axsl:template>\n\t\t  \n\t\t  <!-- DPC introduce context-xpath variable -->\n\t\t  <axsl:template match=\"@*|node()\"\n\t\t\t\t priority=\"-2\"\n\t\t\t\t mode=\"M{ count(preceding-sibling::*) }\">\n\t\t    <axsl:apply-templates select=\"{$context-xpath}\" mode=\"M{count(preceding-sibling::*)}\"/>\n\t\t  </axsl:template>\n\t\t</xsl:if>\n      </xsl:if>\n\t</xsl:template>\n\n\t<!-- ISO PHASE -->\n\t<xsl:template match=\"iso:phase\" >\n                <xsl:if test=\"not(@id)\">\n                    <xsl:message>Markup Error: no id attribute in &lt;phase></xsl:message>\n                </xsl:if>\n\t\t  <xsl:apply-templates/>\n\t</xsl:template>\n\n\t<!-- ISO RULE -->\n\t<xsl:template match=\"iso:rule[not(@abstract='true')] \">\n                <xsl:if test=\"not(@context)\">\n                    <xsl:message>Markup Error: no context attribute in &lt;rule></xsl:message>\n                </xsl:if>\n        <xsl:text>&#10;&#10;\t</xsl:text>\n\t\t<xsl:comment>RULE <xsl:value-of select=\"@id\" /> </xsl:comment><xsl:text>&#10;</xsl:text>   \n        <xsl:if test=\"iso:title\">\n\t\t    <xsl:comment><xsl:value-of select=\"iso:title\" /></xsl:comment>\n\t\t  </xsl:if>\n\t\t<!-- DPC select-contexts -->\n\t\t<xsl:if test=\"$select-contexts='key'\">\n\t\t    <axsl:key name=\"M\"\n\t\t\t      match=\"{@context}\" \n\t\t\t      use=\"'M{count(../preceding-sibling::*)}'\"/>\n\t\t</xsl:if>\n   \n\t\n<!-- DPC priorities count up from 1000 not down from 4000 (templates in same priority order as before) -->\n\t\t<axsl:template match=\"{@context}\"\n\t\tpriority=\"{1000 + count(following-sibling::*)}\" mode=\"M{count(../preceding-sibling::*)}\">\n\t\t\t<xsl:call-template name=\"process-rule\">\n\t\t\t\t<xsl:with-param name=\"context\" select=\"@context\"/>\n\t\t\t\t\n\t\t\t\t\t<!-- \"Rich\" properties -->\n\t\t\t\t\t<xsl:with-param name=\"fpi\" select=\"@fpi\"/>\n\t\t\t\t\t<xsl:with-param name=\"icon\" select=\"@icon\"/>\n\t\t\t\t\t<xsl:with-param name=\"id\" select=\"@id\"/>\n\t\t\t\t\t<xsl:with-param name=\"lang\" select=\"@xml:lang\"/>\n\t\t\t\t\t<xsl:with-param name=\"see\" select=\"@see\" />\n\t\t\t\t\t<xsl:with-param name=\"space\" select=\"@xml:space\" />\n\t\t\t\t\t\n\t\t\t\t\t<!-- \"Linking\" properties -->\n\t\t\t\t\t<xsl:with-param name=\"role\" select=\"@role\" />\n\t\t\t\t\t<xsl:with-param name=\"subject\" select=\"@subject\" />\n\t\t\t</xsl:call-template>\n\t\t\t<xsl:apply-templates/>\n\t\t\t<!-- DPC introduce context-xpath and select-contexts variables -->\n\t\t\t<xsl:if test=\"not($select-contexts)\">\n\t\t\t  <axsl:apply-templates select=\"{$context-xpath}\" mode=\"M{count(../preceding-sibling::*)}\"/>\n\t\t\t</xsl:if>\n\t\t</axsl:template>\n\t</xsl:template>\n\n\n\t<!-- ISO ABSTRACT RULE -->\n\t<xsl:template match=\"iso:rule[@abstract='true'] \" >\n\t\t<xsl:if test=\" not(@id)\">\n                    <xsl:message>Markup Error: no id attribute on abstract &lt;rule></xsl:message>\n                </xsl:if>\n \t\t<xsl:if test=\"@context\">\n                    <xsl:message>Markup Error: (2) context attribute on abstract &lt;rule></xsl:message>\n                </xsl:if>\n\t</xsl:template>\n\n\t<xsl:template match=\"iso:rule[@abstract='true']\"\n\t\tmode=\"extends\" >\n                <xsl:if test=\"@context\">\n                    <xsl:message>Markup Error: context attribute on abstract &lt;rule></xsl:message>\n                </xsl:if>\n\t\t\t<xsl:apply-templates/>\n\t</xsl:template>\n\n\t<!-- ISO SPAN -->\n\t<xsl:template match=\"iso:span\" mode=\"text\">\n\t\t<xsl:call-template name=\"process-span\">\n\t\t\t<xsl:with-param name=\"class\" select=\"@class\"/>\n\t\t</xsl:call-template>\n\t</xsl:template>\n\n\t<!-- ISO TITLE -->\n\t\n\t<xsl:template match=\"iso:schema/iso:title\"  priority=\"1\">\n\t     <xsl:call-template name=\"process-schema-title\" />\n\t</xsl:template>\n \n\t\n\t<xsl:template match=\"iso:title\" >\n\t     <xsl:call-template name=\"process-title\" />\n\t</xsl:template>\n \n\n\t<!-- ISO VALUE-OF -->\n\t<xsl:template match=\"iso:value-of\" mode=\"text\" >\n        <xsl:if test=\"not(@select)\">\n            <xsl:message>Markup Error: no select attribute in &lt;value-of></xsl:message>\n        </xsl:if>\n\t    <xsl:call-template name=\"IamEmpty\" />\n\t         \n\t\t<xsl:choose>\n\t\t\t<xsl:when test=\"@select\">\n\t\t\t\t<xsl:call-template name=\"process-value-of\">\n\t\t\t\t\t<xsl:with-param name=\"select\" select=\"@select\"/>  \n\t\t\t\t</xsl:call-template>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise >\n\t\t\t\t<xsl:call-template name=\"process-value-of\">\n\t\t\t\t\t<xsl:with-param name=\"select\" select=\"'.'\"/>\n\t\t\t\t</xsl:call-template>\n\t\t\t</xsl:otherwise>\n        </xsl:choose> \n        \n\t</xsl:template>\n\n\n<!-- ============================================================== -->\n<!-- DEFAULT TEXT HANDLING  -->\n<!-- ============================================================== -->\n\t<xsl:template match=\"text()\" priority=\"-1\" mode=\"do-keys\">\n\t\t<!-- strip characters -->\n\t</xsl:template>\n\t<xsl:template match=\"text()\" priority=\"-1\" mode=\"do-all-patterns\">\n\t\t<!-- strip characters -->\n\t</xsl:template>\n        <xsl:template match=\"text()\" priority=\"-1\" mode=\"do-schema-p\">\n\t\t<!-- strip characters -->\n\t</xsl:template>\n        <xsl:template match=\"text()\" priority=\"-1\" mode=\"do-pattern-p\">\n\t\t<!-- strip characters -->\n\t</xsl:template>\n\t\n\t<xsl:template match=\"text()\" priority=\"-1\">\n\t\t<!-- Strip characters -->\n\t</xsl:template>\n\t\n\t<xsl:template match=\"text()\" mode=\"text\">\n\t\t<xsl:value-of select=\".\"/>\n\t</xsl:template>\n\n\t<xsl:template match=\"text()\" mode=\"inline-text\">\n\t\t<xsl:value-of select=\".\"/>\n\t</xsl:template>\n\n<!-- ============================================================== -->\n<!-- UTILITY TEMPLATES -->\n<!-- ============================================================== -->\n<xsl:template name=\"IamEmpty\">\n\t<xsl:if test=\"count( * )\">\n\t\t<xsl:message>\n\t\t\t<xsl:text>Warning: </xsl:text>\n\t\t\t<xsl:value-of select=\"name(.)\"/>\n\t\t\t<xsl:text> must not contain any child elements</xsl:text>\n\t\t</xsl:message>\n\t</xsl:if>\n</xsl:template>\n\n<xsl:template name=\"diagnosticsSplit\">\n  <!-- Process at the current point the first of the <diagnostic> elements\n       referred to parameter str, and then recurse -->\n  <xsl:param name=\"str\"/>\n  <xsl:variable name=\"start\">\n    <xsl:choose>\n      <xsl:when test=\"contains($str,' ')\">\n\t<xsl:value-of  select=\"substring-before($str,' ')\"/>\n      </xsl:when>\n      <xsl:otherwise><xsl:value-of select=\"$str\"/></xsl:otherwise>\n    </xsl:choose>\n  </xsl:variable>\n\n  <xsl:variable name=\"end\">\n    <xsl:if test=\"contains($str,' ')\">\n      <xsl:value-of select=\"substring-after($str,' ')\"/>\n    </xsl:if>\n  </xsl:variable>\n\n  <!-- This works with all namespaces -->\n  <xsl:if test=\"not(string-length(normalize-space($start)) = 0)\n  \t\tand not(//iso:diagnostic[@id = $start])\n\t\tand not(//sch:diagnostic[@id = $start]) \n\t\tand not(//diagnostic[@id = $start])\">\n\t<xsl:message>Reference error: A diagnostic \"<xsl:value-of select=\"string($start)\"\n\t/>\" has been referenced but is not declared</xsl:message>\n  </xsl:if>\n\n  <xsl:if test=\"string-length(normalize-space($start)) > 0\">\n     <xsl:text> </xsl:text>\n     <xsl:apply-templates \n        select=\"//iso:diagnostic[@id = $start ]\n        \t| //sch:diagnostic[@id = $start ] \n            | //diagnostic[@id= $start ]\"/>\n  </xsl:if>\n\n  <xsl:if test=\"not($end='')\">\n    <xsl:call-template name=\"diagnosticsSplit\">\n      <xsl:with-param name=\"str\" select=\"$end\"/>\n    </xsl:call-template>\n  </xsl:if>\n</xsl:template>\n\n<!-- It would be nice to use this but xsl:namespace does not\n  allow a fallback -->\n<!--xsl:template name=\"handle-namespace\" version=\"2.0\">\n   <xsl:namespace name=\"{@prefix}\" select=\"@uri\">\n</xsl:template-->\n\n<xsl:template name=\"handle-namespace\">\n       <!-- experimental code from http://eccnet.eccnet.com/pipermail/schematron-love-in/2006-June/000104.html -->\n       <!-- Handle namespaces differently for exslt systems, msxml, and default, only using XSLT1 syntax -->\n       <!-- For more info see  http://fgeorges.blogspot.com/2007/01/creating-namespace-nodes-in-xslt-10.html -->\n       <xsl:choose>\n          <!-- The following code works for XSLT1 -->\n        <xsl:when test=\"function-available('exsl:node-set')\">\n           <xsl:variable name=\"ns-dummy-elements\">\n             <xsl:element name=\"{@prefix}:dummy\" namespace=\"{@uri}\"/>\n           </xsl:variable>\n       \t   <xsl:variable name=\"p\" select=\"@prefix\"/>\n           <xsl:copy-of select=\"exsl:node-set($ns-dummy-elements)\n                                  /*/namespace::*[local-name()=$p]\"/>\n         </xsl:when>        \n\n   \t\t\t<!-- End XSLT1  code -->\n  \n        <!-- Not tested yet       \n    \t<xsl:when test=\"function-available('msxsl:node-set')\">\n      \t\t<xsl:variable name=\"ns-dummy-elements\">\n        \t\t<xsl:element name=\"{ $prefix }:e\" namespace=\"{ $uri }\"/>\n      \t\t</xsl:variable>\n      \t\t<xsl:copy-of select=\"msxsl:node-set($ns-dummy-elements)/*/namespace::*\"/>\n    \t</xsl:when>\n        -->\n        \n        <xsl:when test=\"@prefix = 'xsl' \">\n           <!-- Do not generate dummy attributes with the xsl: prefix, as these\n                are errors against XSLT, because we presume that the output\n                stylesheet uses the xsl prefix. In any case, there would already\n                be a namespace declaration for the XSLT namespace generated\n                automatically, presumably using \"xsl:\".\n           -->\n        </xsl:when>\n        \n        <xsl:when test=\"@uri = 'http://www.w3.org/1999/XSL/Transform'\">\n          <xsl:message terminate=\"yes\">\n            <xsl:text>Using the XSLT namespace with a prefix other than \"xsl\" in </xsl:text>\n            <xsl:text>Schematron rules is not supported </xsl:text>\n            <xsl:text>in this processor: </xsl:text>\n            <xsl:value-of select=\"system-property('xsl:vendor')\"/>\n          </xsl:message>\n        </xsl:when>\n\n        <xsl:otherwise>\n          <xsl:attribute name=\"{concat(@prefix,':dummy-for-xmlns')}\" namespace=\"{@uri}\" />\n           \n        </xsl:otherwise>\n      </xsl:choose>\n\n\n</xsl:template>\n\n<!-- ============================================================== -->\n<!-- UNEXPECTED ELEMENTS -->\n<!-- ============================================================== -->\n\n\t<xsl:template match=\"iso:*\"  priority=\"-2\">\n\t   <xsl:message>\n\t\t\t<xsl:text>Error: unrecognized element in ISO Schematron namespace: check spelling\n\t\t\tand capitalization</xsl:text>\n\t\t\t<xsl:value-of select=\"name(.)\"/>\n\t\t</xsl:message>\n\t</xsl:template>\n\t\n\t\n\t<!-- Swallow old namespace elements: there is an upfront test for them elsewhere -->\n\t<xsl:template match=\"sch:*\"  priority=\"-2\" />\n\t\n\t<xsl:template match=\"*\"  priority=\"-3\">\n\t    <xsl:choose>\n\t       <xsl:when test=\" $allow-foreign = 'false' \">\n\t\t\t\t<xsl:message>\n\t\t\t\t\t<xsl:text>Warning: unrecognized element </xsl:text>\n\t\t\t\t\t<xsl:value-of select=\"name(.)\"/>\n\t\t\t\t</xsl:message>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise>\n\t\t\t\t<xsl:copy-of select=\".\" />\n\t\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\t</xsl:template>\n\t\n\t<xsl:template match=\"iso:*\" mode=\"text\" priority=\"-2\" />\n\t<xsl:template match=\"*\" mode=\"text\" priority=\"-3\">\n\t    <xsl:choose>\n\t       <xsl:when test=\" $allow-foreign = 'false' \">\n\t\t\t\t<xsl:message>\n\t\t\t\t\t<xsl:text>Warning: unrecognized element </xsl:text>\n\t\t\t\t\t<xsl:value-of select=\"name(.)\"/>\n\t\t\t\t</xsl:message>\n\t\t\t</xsl:when>\n\t\t\t<xsl:otherwise>\n\t\t\t\t<xsl:copy-of select=\".\" />\n\t\t\t</xsl:otherwise>\n\t\t</xsl:choose>\n\t</xsl:template>\n\n<!-- ============================================================== -->\n<!-- DEFAULT NAMED TEMPLATES -->\n<!-- These are the actions that are performed unless overridden -->\n<!-- ============================================================== -->\n \n\t<xsl:template name=\"process-prolog\"/>\n\t<!-- no params -->\n\n\t<xsl:template name=\"process-root\">\n\t\t<xsl:param name=\"contents\"/>\n\t\t<xsl:param name=\"id\" />\n\t\t<xsl:param name=\"version\" />\n\t\t<xsl:param name=\"schemaVersion\" />\n\t\t<xsl:param name=\"queryBinding\" />\n\t\t<xsl:param name=\"title\" />\n\n\n\t\t<!-- \"Rich\" parameters -->\n\t\t<xsl:param name=\"fpi\" />\n\t\t<xsl:param name=\"icon\" />\n\t\t<xsl:param name=\"lang\" />\n\t\t<xsl:param name=\"see\" />\n\t\t<xsl:param name=\"space\" />\n\n\t\t<xsl:copy-of select=\"$contents\"/>\n\t</xsl:template>\n\n\t<xsl:template name=\"process-assert\">\n\n\t\t<xsl:param name=\"test\"/>\n\t\t<xsl:param name=\"diagnostics\" />\n\t\t<xsl:param name=\"id\" />\n\t\t<xsl:param name=\"flag\" />\n\n           \t<!-- \"Linkable\" parameters -->\n\t\t<xsl:param name=\"role\"/>\n\t\t<xsl:param name=\"subject\"/>\n\n\t\t<!-- \"Rich\" parameters -->\n\t\t<xsl:param name=\"fpi\" />\n\t\t<xsl:param name=\"icon\" />\n\t\t<xsl:param name=\"lang\" />\n\t\t<xsl:param name=\"see\" />\n\t\t<xsl:param name=\"space\" />\n\n\n\t\t<xsl:call-template name=\"process-message\">\n\t\t\t<xsl:with-param name=\"pattern\" select=\"$test\"/>\n\t\t\t<xsl:with-param name=\"role\" select=\"$role\"/>\n\t\t</xsl:call-template>\n\t\t\n\t\t\n\t</xsl:template>\n\n\t<xsl:template name=\"process-report\">\n\t\t<xsl:param name=\"test\"/>\n\t\t<xsl:param name=\"diagnostics\" />\n\t\t<xsl:param name=\"id\" />\n\t\t<xsl:param name=\"flag\" />\n\n           \t<!-- \"Linkable\" parameters -->\n\t\t<xsl:param name=\"role\"/>\n\t\t<xsl:param name=\"subject\"/>\n\n\t\t<!-- \"Rich\" parameters -->\n\t\t<xsl:param name=\"fpi\" />\n\t\t<xsl:param name=\"icon\" /> \n\t\t<xsl:param name=\"lang\" />\n\t\t<xsl:param name=\"see\" />\n\t\t<xsl:param name=\"space\" />\n\n\t\t<xsl:call-template name=\"process-message\">\n\t\t\t<xsl:with-param name=\"pattern\" select=\"$test\"/>\n\t\t\t<xsl:with-param name=\"role\" select=\"$role\"/>\n\t\t</xsl:call-template>\n\t</xsl:template>\n\n\t<xsl:template name=\"process-diagnostic\">\n\t\t<xsl:param name=\"id\" />\n\n\t\t<!-- \"Rich\" parameters -->\n\t\t<xsl:param name=\"fpi\" />\n\t\t<xsl:param name=\"icon\" />\n\t\t<xsl:param name=\"lang\" />\n\t\t<xsl:param name=\"see\" />\n\t\t<xsl:param name=\"space\" />\n\t\t\n\t    <!-- We generate too much whitespace rather than risking concatenation -->\n\t\t<axsl:text> </axsl:text>\n\t\t<xsl:apply-templates mode=\"text\"/>\n\t\t<axsl:text> </axsl:text>\n\t</xsl:template>\n\n\t<xsl:template name=\"process-dir\">\n      \t<xsl:param name=\"value\" />\n\n\t    <!-- We generate too much whitespace rather than risking concatenation -->\n\t\t<axsl:text> </axsl:text>\n\t\t<xsl:apply-templates mode=\"inline-text\"/>\n\t\t<axsl:text> </axsl:text>\n\t</xsl:template>\n\n\t<xsl:template name=\"process-emph\"> \n\t    <!-- We generate too much whitespace rather than risking concatenation -->\n\t\t<axsl:text> </axsl:text>\n\t\t<xsl:apply-templates mode=\"inline-text\"/>\n\t\t<axsl:text> </axsl:text>\n\t</xsl:template>\n\t\n\t<xsl:template name=\"process-name\">\n\t\t<xsl:param name=\"name\"/>\n\t\t\n\t\t<!-- We generate too much whitespace rather than risking concatenation -->\n\t\t<axsl:text> </axsl:text>\n\t\t<axsl:value-of select=\"{$name}\"/>\n\t\t<axsl:text> </axsl:text>\n\t\t\n    </xsl:template>\n\n\t<xsl:template name=\"process-ns\" >\n\t<!-- Note that process-ns is for reporting. The sch:ns elements are \n\t     independently used in the sch:schema template to provide namespace bindings -->\n\t\t<xsl:param name=\"prefix\"/>\n\t\t<xsl:param name=\"uri\" />\n      </xsl:template>\n\n\t<xsl:template name=\"process-p\">\n\t\t<xsl:param name=\"id\" />\n\t\t<xsl:param name=\"class\" />\n\t\t<xsl:param name=\"icon\" />\n\t\t<xsl:param name=\"lang\" />\n      </xsl:template>\n\n\t<xsl:template name=\"process-pattern\">\n\t\t<xsl:param name=\"id\" />\n\t\t<xsl:param name=\"name\" />\n\t\t<xsl:param name=\"is-a\" />\n\n\t\t<!-- \"Rich\" parameters -->\n\t\t<xsl:param name=\"fpi\" />\n\t\t<xsl:param name=\"icon\" />\n\t\t<xsl:param name=\"lang\" />\n\t\t<xsl:param name=\"see\" />\n\t\t<xsl:param name=\"space\" />\n      </xsl:template>\n      \n\n\t<xsl:template name=\"process-rule\">\n\t\t<xsl:param name=\"context\" />\n\n\t\t<xsl:param name=\"id\" />\n\t\t<xsl:param name=\"flag\" />\n\n           \t<!-- \"Linkable\" parameters -->\n\t\t<xsl:param name=\"role\"/>\n\t\t<xsl:param name=\"subject\"/>\n  \n\t\t<!-- \"Rich\" parameters -->\n\t\t<xsl:param name=\"fpi\" />\n\t\t<xsl:param name=\"icon\" />\n\t\t<xsl:param name=\"lang\" />\n\t\t<xsl:param name=\"see\" />\n\t\t<xsl:param name=\"space\" />\n      </xsl:template>\n\n\t<xsl:template name=\"process-span\" >\n\t\t<xsl:param name=\"class\" />\n\n\t    <!-- We generate too much whitespace rather than risking concatenation -->\n\t\t<axsl:text> </axsl:text>\n\t\t<xsl:apply-templates mode=\"inline-text\"/>\n\t\t<axsl:text> </axsl:text>\t\t\n\t</xsl:template>\n\n\t<xsl:template name=\"process-title\" >\n\t\t<xsl:param name=\"class\" />\n\t   <xsl:call-template name=\"process-p\">\n\t      <xsl:with-param  name=\"class\">title</xsl:with-param>\n\t   </xsl:call-template>\n\t</xsl:template>\n\t\t\n\t<xsl:template name=\"process-schema-title\" >\n\t\t<xsl:param name=\"class\" />\n\t   <xsl:call-template name=\"process-title\">\n\t      <xsl:with-param  name=\"class\">schema-title</xsl:with-param>\n\t   </xsl:call-template>\n\t</xsl:template>\n\n\t<xsl:template name=\"process-value-of\">\n\t\t<xsl:param name=\"select\"/>\n\t\t\n\t    <!-- We generate too much whitespace rather than risking concatenation -->\n\t\t<axsl:text> </axsl:text>\n\t\t<axsl:value-of select=\"{$select}\"/>\n\t\t<axsl:text> </axsl:text>\n\t</xsl:template>\n\n\t<!-- default output action: the simplest customization is to just override this -->\n\t<xsl:template name=\"process-message\">\n\t\t<xsl:param name=\"pattern\" />\n            <xsl:param name=\"role\" />\n\n\t\t<xsl:apply-templates mode=\"text\"/>\t\n\t\t <xsl:if test=\" $message-newline = 'true'\" >\n\t\t\t<axsl:value-of  select=\"string('&#10;')\"/>\n\t\t</xsl:if>\n\t\t\n\t</xsl:template>\n</xsl:stylesheet>\n\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/isoschematron/resources/xsl/iso-schematron-xslt1/iso_svrl_for_xslt1.xsl",
    "content": "<?xml version=\"1.0\" ?>\n<!-- \n   ISO_SVRL.xsl   \n\n   Implementation of Schematron Validation Report Language from ISO Schematron\n   ISO/IEC 19757 Document Schema Definition Languages (DSDL) \n     Part 3: Rule-based validation  Schematron \n     Annex D: Schematron Validation Report Language \n\n  This ISO Standard is available free as a Publicly Available Specification in PDF from ISO.\n  Also see www.schematron.com for drafts and other information.\n\n  This implementation of SVRL is designed to run with the \"Skeleton\" implementation \n  of Schematron which Oliver Becker devised. The skeleton code provides a \n  Schematron implementation but with named templates for handling all output; \n  the skeleton provides basic templates for output using this API, but client\n  validators can be written to import the skeleton and override the default output\n  templates as required. (In order to understand this, you must understand that\n  a named template such as \"process-assert\" in this XSLT stylesheet overrides and\n  replaces any template with the same name in the imported skeleton XSLT file.)\n\n  The other important thing to understand in this code is that there are different\n  versions of the Schematron skeleton. These track the development of Schematron through\n  Schematron 1.5, Schematron 1.6 and now ISO Schematron. One only skeleton must be\n  imported. The code has templates for the different skeletons commented out for \n  convenience. ISO Schematron has a different namespace than Schematron 1.5 and 1.6;\n  so the ISO Schematron skeleton has been written itself with an optional import\n  statement to in turn import the Schematron 1.6 skeleton. This will allow you to \n  validate with schemas from either namespace.\n  \n\n  History:  \n    2009-03-18\n    \t* Fix atrribute with space \"see \" which generates wrong name in some processors\n    2008-08-11\n   \t\t* RJ Fix attribute/@select which saxon allows  in XSLT 1\n   2008-08-07\n    \t* RJ Add output-encoding attribute to specify final encoding to use\n    \t* Alter allow-foreign functionality so that Schematron span, emph and dir elements make \n    \t  it to the output, for better formatting and because span can be used to mark up\n    \t  semantically interesting information embedded in diagnostics, which reduces the\n    \t  need to extend SVRL itself\n    \t* Diagnostic-reference had an invalid attribute @id that duplicated @diagnostic: removed\n  \t2008-08-06\n    \t* RJ Fix invalid output:  svrl:diagnostic-reference is not contained in an svrl:text\n    \t* Output comment to SVRL file giving filename if available (from command-line parameter)\n  \t2008-08-04\n  \t\t* RJ move sch: prefix to schold: prefix to prevent confusion (we want people to\n  \t\tbe able to switch from old namespace to new namespace without changing the\n  \t\tsch: prefix, so it is better to keep that prefix completely out of the XSLT)\n  \t\t* Extra signature fixes (PH)\n    2008-08-03\n    \t* Repair missing class parameter on process-p\n    2008-07-31\n    \t* Update skeleton names\n    2007-04-03 \n    \t* Add option generate-fired-rule (RG)\n    2007-02-07\n    \t* Prefer true|false for parameters. But allow yes|no on some old for compatability\n    \t* DP Diagnostics output to svrl:text. Diagnosis put out after assertion text.\n      \t* Removed non-SVRL elements and attributes: better handled as an extra layer that invokes this one\n      \t* Add more formal parameters\n      \t* Correct confusion between $schemaVersion and $queryBinding\n     \t* Indent\n     \t* Validate against RNC schemas for XSLT 1 and 2 (with regex tests removed)\n     \t* Validate output with UniversalTest.sch against RNC schema for ISO SVRL\n    \t\n    2007-02-01\n       \t* DP. Update formal parameters of overriding named templates to handle more attributes.\n       \t* DP. Refactor handling of rich and linkable parameters to a named template.\n\n    2007-01-22\n    \t* DP change svrl:ns to svrl:ns-in-attribute-value\n\t\t* Change default when no queryBinding from \"unknown\" to \"xslt\"\n\t\n    2007-01-18:\n     \t* Improve documentation\n     \t* KH Add command-line options to generate paths or not \n       \t* Use axsl:attribute rather than xsl:attribute to shut XSLT2 up\n       \t* Add extra command-line options to pass to the iso_schematron_skeleton\n  \n    2006-12-01: iso_svrl.xsl Rick Jelliffe, \n          * update namespace, \n          * update phase handling,\n          * add flag param to process-assert and process-report & @ flag on output\n  \n    2001: Conformance1-5.xsl Rick Jelliffe, \n          * Created, using the skeleton code contributed by Oliver Becker\n-->\n<!--\n Derived from Conformance1-5.xsl.\n\n Copyright (c) 2001, 2006 Rick Jelliffe and Academia Sinica Computing Center, Taiwan\n\n This software is provided 'as-is', without any express or implied warranty. \n In no event will the authors be held liable for any damages arising from \n the use of this software.\n\n Permission is granted to anyone to use this software for any purpose, \n including commercial applications, and to alter it and redistribute it freely,\n subject to the following restrictions:\n\n 1. The origin of this software must not be misrepresented; you must not claim\n that you wrote the original software. If you use this software in a product, \n an acknowledgment in the product documentation would be appreciated but is \n not required.\n\n 2. Altered source versions must be plainly marked as such, and must not be \n misrepresented as being the original software.\n\n 3. This notice may not be removed or altered from any source distribution.\n-->\n\n<!-- Ideas nabbed from schematrons by Francis N., Miloslav N. and David C. -->\n\n<!-- The command-line parameters are:\n  \t\t\tphase           NMTOKEN | \"#ALL\" (default) Select the phase for validation\n    \t\tallow-foreign   \"true\" | \"false\" (default)   Pass non-Schematron elements  and rich markup  to the generated stylesheet\n            diagnose= true | false|yes|no    Add the diagnostics to the assertion test in reports (yes|no are obsolete)\n            generate-paths=true|false|yes|no   generate the @location attribute with XPaths (yes|no are obsolete)\n            sch.exslt.imports semi-colon delimited string of filenames for some EXSLT implementations          \n   \t\t optimize        \"visit-no-attributes\"     Use only when the schema has no attributes as the context nodes\n\t\t generate-fired-rule \"true\"(default) | \"false\"  Generate fired-rule elements\n            \n-->\n\n<xsl:stylesheet\n   version=\"1.0\"\n   xmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\"\n\txmlns:xs=\"http://www.w3.org/2001/XMLSchema\"\n   xmlns:axsl=\"http://www.w3.org/1999/XSL/TransformAlias\"\n   xmlns:schold=\"http://www.ascc.net/xml/schematron\" \n   xmlns:iso=\"http://purl.oclc.org/dsdl/schematron\"\n   xmlns:svrl=\"http://purl.oclc.org/dsdl/svrl\" \n>\n\n<!-- Select the import statement and adjust the path as \n   necessary for your system.\n   If not XSLT2 then also remove svrl:active-pattern/@document=\"{document-uri()}\" from process-pattern()\n-->\n<!--\n<xsl:import href=\"iso_schematron_skeleton_for_saxon.xsl\"/>\n--> \n  \n<xsl:import href=\"iso_schematron_skeleton_for_xslt1.xsl\"/>\n <!--\n<xsl:import href=\"iso_schematron_skeleton.xsl\"/>\n<xsl:import href=\"skeleton1-5.xsl\"/>\n<xsl:import href=\"skeleton1-6.xsl\"/>\n-->\n\n<xsl:param name=\"diagnose\" >true</xsl:param>\n<xsl:param name=\"phase\" >\n\t<xsl:choose>\n\t\t<!-- Handle Schematron 1.5 and 1.6 phases -->\n\t\t<xsl:when test=\"//schold:schema/@defaultPhase\">\n\t\t\t<xsl:value-of select=\"//schold:schema/@defaultPhase\"/>\n\t\t</xsl:when>\n\t\t<!-- Handle ISO Schematron phases -->\n\t\t<xsl:when test=\"//iso:schema/@defaultPhase\">\n\t\t\t<xsl:value-of select=\"//iso:schema/@defaultPhase\"/>\n\t\t</xsl:when>\n\t\t<xsl:otherwise>#ALL</xsl:otherwise>\n\t</xsl:choose>\n</xsl:param>\n<xsl:param name=\"allow-foreign\" >false</xsl:param>\n<xsl:param name=\"generate-paths\" >true</xsl:param>\n<xsl:param name=\"generate-fired-rule\" >true</xsl:param>\n<xsl:param name=\"optimize\"/>\n\n<xsl:param name=\"output-encoding\" ></xsl:param>\n\n<!-- e.g. saxon file.xml file.xsl \"sch.exslt.imports=.../string.xsl;.../math.xsl\" -->\n<xsl:param name=\"sch.exslt.imports\" />\n\n\n\n<!-- Experimental: If this file called, then must be generating svrl -->\n<xsl:variable name=\"svrlTest\" select=\"true()\" />\n\n  \n \n<!-- ================================================================ -->\n\n<xsl:template name=\"process-prolog\">\n\t<axsl:output method=\"xml\" omit-xml-declaration=\"no\" standalone=\"yes\"\n\t\tindent=\"yes\">\n\t\t<xsl:if test=\" string-length($output-encoding) &gt; 0\">\n\t\t\t<xsl:attribute name=\"encoding\"><xsl:value-of select=\" $output-encoding\" /></xsl:attribute>\n\t\t</xsl:if>\n    </axsl:output>\n     \n</xsl:template>\n\n<!-- Overrides skeleton.xsl -->\n<xsl:template name=\"process-root\">\n\t<xsl:param name=\"title\"/>\n\t<xsl:param name=\"contents\" />\n\t<xsl:param name=\"queryBinding\" >xslt1</xsl:param>\n\t<xsl:param name=\"schemaVersion\" />\n\t<xsl:param name=\"id\" />\n\t<xsl:param name=\"version\"/>\n\t<!-- \"Rich\" parameters -->\n\t<xsl:param name=\"fpi\" />\n\t<xsl:param name=\"icon\" />\n\t<xsl:param name=\"lang\" />\n\t<xsl:param name=\"see\" />\n\t<xsl:param name=\"space\" />\n\t\n\t<svrl:schematron-output title=\"{$title}\" schemaVersion=\"{$schemaVersion}\" >\n\t\t<xsl:if test=\" string-length( normalize-space( $phase )) &gt; 0 and \n\t\tnot( normalize-space( $phase ) = '#ALL') \">\n\t\t\t<axsl:attribute name=\"phase\">\n\t\t\t\t<xsl:value-of select=\" $phase \" />\n\t\t\t</axsl:attribute>\n\t\t</xsl:if>\n\t\t<xsl:if test=\" $allow-foreign = 'true'\">\n\t\t</xsl:if>\n\t\t  <xsl:if  test=\" $allow-foreign = 'true'\">\n\t\n\t\t<xsl:call-template name='richParms'>\n\t\t\t<xsl:with-param name=\"fpi\" select=\"$fpi\" />\n\t\t\t<xsl:with-param name=\"icon\" select=\"$icon\"/>\n\t\t\t<xsl:with-param name=\"lang\" select=\"$lang\"/>\n\t\t\t<xsl:with-param name=\"see\"  select=\"$see\" />\n\t\t\t<xsl:with-param name=\"space\"  select=\"$space\" />\n\t\t</xsl:call-template>\n\t</xsl:if>\n\t\t \n\t\t <axsl:comment><axsl:value-of select=\"$archiveDirParameter\"/>  &#xA0;\n\t\t <axsl:value-of select=\"$archiveNameParameter\"/> &#xA0;\n\t\t <axsl:value-of select=\"$fileNameParameter\"/> &#xA0;\n\t\t <axsl:value-of select=\"$fileDirParameter\"/></axsl:comment> \n\t\t \n\t\t\n\t\t<xsl:apply-templates mode=\"do-schema-p\" />\n\t\t<xsl:copy-of select=\"$contents\" />\n\t</svrl:schematron-output>\n</xsl:template>\n\n\n<xsl:template name=\"process-assert\">\n\t<xsl:param name=\"test\"/>\n\t<xsl:param name=\"diagnostics\" />\n\t<xsl:param name=\"id\" />\n\t<xsl:param name=\"flag\" />\n\t<!-- \"Linkable\" parameters -->\n\t<xsl:param name=\"role\"/>\n\t<xsl:param name=\"subject\"/>\n\t<!-- \"Rich\" parameters -->\n\t<xsl:param name=\"fpi\" />\n\t<xsl:param name=\"icon\" />\n\t<xsl:param name=\"lang\" />\n\t<xsl:param name=\"see\" />\n\t<xsl:param name=\"space\" />\n\t<svrl:failed-assert test=\"{$test}\" >\n\t\t<xsl:if test=\"string-length( $id ) &gt; 0\">\n\t\t\t<axsl:attribute name=\"id\">\n\t\t\t\t<xsl:value-of select=\" $id \" />\n\t\t\t</axsl:attribute>\n\t\t</xsl:if>\n\t\t<xsl:if test=\" string-length( $flag ) &gt; 0\">\n\t\t\t<axsl:attribute name=\"flag\">\n\t\t\t\t<xsl:value-of select=\" $flag \" />\n\t\t\t</axsl:attribute>\n\t\t</xsl:if>\n\t\t<!-- Process rich attributes.  -->\n\t\t<xsl:call-template name=\"richParms\">\n\t\t\t<xsl:with-param name=\"fpi\" select=\"$fpi\"/>\n\t\t\t<xsl:with-param name=\"icon\" select=\"$icon\"/>\n\t\t\t<xsl:with-param name=\"lang\" select=\"$lang\"/>\n\t\t\t<xsl:with-param name=\"see\" select=\"$see\" />\n\t\t\t<xsl:with-param name=\"space\" select=\"$space\" />\n\t\t</xsl:call-template>\n\t\t<xsl:call-template name='linkableParms'>\n\t\t\t<xsl:with-param name=\"role\" select=\"$role\" />\n\t\t\t<xsl:with-param name=\"subject\" select=\"$subject\"/>\n\t\t</xsl:call-template>\n\t\t<xsl:if test=\" $generate-paths = 'true' or $generate-paths= 'yes' \">\n\t\t\t<!-- true/false is the new way -->\n\t\t\t<axsl:attribute name=\"location\">\n\t\t\t\t<axsl:apply-templates select=\".\" mode=\"schematron-get-full-path\"/>\n\t\t\t</axsl:attribute>\n\t\t</xsl:if>\n\t\t  \n\t\t<svrl:text>\n\t\t\t<xsl:apply-templates mode=\"text\" />\n\t\n\t\t</svrl:text>\n\t\t    <xsl:if test=\"$diagnose = 'yes' or $diagnose= 'true' \">\n\t\t\t<!-- true/false is the new way -->\n\t\t\t\t<xsl:call-template name=\"diagnosticsSplit\">\n\t\t\t\t\t<xsl:with-param name=\"str\" select=\"$diagnostics\"/>\n\t\t\t\t</xsl:call-template>\n\t\t\t</xsl:if>\n\t</svrl:failed-assert>\n</xsl:template>\n\n<xsl:template name=\"process-report\">\n\t<xsl:param name=\"id\"/>\n\t<xsl:param name=\"test\"/>\n\t<xsl:param name=\"diagnostics\"/>\n\t<xsl:param name=\"flag\" />\n\t<!-- \"Linkable\" parameters -->\n\t<xsl:param name=\"role\"/>\n\t<xsl:param name=\"subject\"/>\n\t<!-- \"Rich\" parameters -->\n\t<xsl:param name=\"fpi\" />\n\t<xsl:param name=\"icon\" />\n\t<xsl:param name=\"lang\" />\n\t<xsl:param name=\"see\" />\n\t<xsl:param name=\"space\" />\n\t<svrl:successful-report test=\"{$test}\" >\n\t\t<xsl:if test=\" string-length( $id ) &gt; 0\">\n\t\t\t<axsl:attribute name=\"id\">\n\t\t\t\t<xsl:value-of select=\" $id \" />\n\t\t\t</axsl:attribute>\n\t\t</xsl:if>\n\t\t<xsl:if test=\" string-length( $flag ) &gt; 0\">\n\t\t\t<axsl:attribute name=\"flag\">\n\t\t\t\t<xsl:value-of select=\" $flag \" />\n\t\t\t</axsl:attribute>\n\t\t</xsl:if>\n\t\t\n\t\t<!-- Process rich attributes.  -->\n\t\t<xsl:call-template name=\"richParms\">\n\t\t\t<xsl:with-param name=\"fpi\" select=\"$fpi\"/>\n\t\t\t<xsl:with-param name=\"icon\" select=\"$icon\"/>\n\t\t\t<xsl:with-param name=\"lang\" select=\"$lang\"/>\n\t\t\t<xsl:with-param name=\"see\" select=\"$see\" />\n\t\t\t<xsl:with-param name=\"space\" select=\"$space\" />\n\t\t</xsl:call-template>\n\t\t<xsl:call-template name='linkableParms'>\n\t\t\t<xsl:with-param name=\"role\" select=\"$role\" />\n\t\t\t<xsl:with-param name=\"subject\" select=\"$subject\"/>\n\t\t</xsl:call-template>\n\t\t<xsl:if test=\" $generate-paths = 'yes' or $generate-paths = 'true' \">\n\t\t\t<!-- true/false is the new way -->\n\t\t\t<axsl:attribute name=\"location\">\n\t\t\t\t<axsl:apply-templates select=\".\" mode=\"schematron-get-full-path\"/>\n\t\t\t</axsl:attribute>\n\t\t</xsl:if>\n\t \n\t\t<svrl:text>\n\t\t\t<xsl:apply-templates mode=\"text\" />\n\n\t\t</svrl:text>\n\t\t\t<xsl:if test=\"$diagnose = 'yes' or $diagnose='true' \">\n\t\t\t<!-- true/false is the new way -->\n\t\t\t\t<xsl:call-template name=\"diagnosticsSplit\">\n\t\t\t\t\t<xsl:with-param name=\"str\" select=\"$diagnostics\"/>\n\t\t\t\t</xsl:call-template>\n\t\t\t</xsl:if>\n\t</svrl:successful-report>\n</xsl:template>\n\n\n    <!-- Overrides skeleton -->\n\t<xsl:template name=\"process-dir\" >\n\t\t<xsl:param name=\"value\" />\n        <xsl:choose>\n        \t<xsl:when test=\" $allow-foreign = 'true'\">\n        \t\t<xsl:copy-of select=\".\"/>\n        \t</xsl:when>\n       \n        <xsl:otherwise>\n\t    <!-- We generate too much whitespace rather than risking concatenation -->\n\t\t<axsl:text> </axsl:text>\n\t\t<xsl:apply-templates mode=\"inline-text\"/>\n\t\t<axsl:text> </axsl:text>\n\t\t</xsl:otherwise>\n\t\t </xsl:choose>\t\t\n\t</xsl:template>\n\n<xsl:template name=\"process-diagnostic\">\n\t<xsl:param name=\"id\"/>\n\t<!-- Rich parameters -->\n\t<xsl:param name=\"fpi\" />\n\t<xsl:param name=\"icon\" />\n\t<xsl:param name=\"lang\" />\n\t<xsl:param name=\"see\" />\n\t<xsl:param name=\"space\" />\n\t<svrl:diagnostic-reference diagnostic=\"{$id}\" >\n\t  \n\t\t<xsl:call-template name=\"richParms\">\n\t\t\t<xsl:with-param name=\"fpi\" select=\"$fpi\"/>\n\t\t\t<xsl:with-param name=\"icon\" select=\"$icon\"/>\n\t\t\t<xsl:with-param name=\"lang\" select=\"$lang\"/>\n\t\t\t<xsl:with-param name=\"see\" select=\"$see\" />\n\t\t\t<xsl:with-param name=\"space\" select=\"$space\" />\n\t\t</xsl:call-template> \n<xsl:text>\n</xsl:text>\n \n\t\t<xsl:apply-templates mode=\"text\"/>\n\t\t \n\t</svrl:diagnostic-reference>\n</xsl:template>\n\n\n    <!-- Overrides skeleton -->\n\t<xsl:template name=\"process-emph\" >\n\t\t<xsl:param name=\"class\" />\n        <xsl:choose>\n        \t<xsl:when test=\" $allow-foreign = 'true'\">\n        \t\t<xsl:copy-of select=\".\"/>\n        \t</xsl:when> \n        <xsl:otherwise>\n\t    <!-- We generate too much whitespace rather than risking concatenation -->\n\t\t<axsl:text> </axsl:text>\n\t\t<xsl:apply-templates mode=\"inline-text\"/>\n\t\t<axsl:text> </axsl:text>\n\t\t</xsl:otherwise>\n\t \t</xsl:choose>\t\n\t</xsl:template>\n\n<xsl:template name=\"process-rule\">\n\t<xsl:param name=\"id\"/>\n\t<xsl:param name=\"context\"/>\n\t<xsl:param name=\"flag\"/>\n\t<!-- \"Linkable\" parameters -->\n\t<xsl:param name=\"role\"/>\n\t<xsl:param name=\"subject\"/>\n\t<!-- \"Rich\" parameters -->\n\t<xsl:param name=\"fpi\" />\n\t<xsl:param name=\"icon\" />\n\t<xsl:param name=\"lang\" />\n\t<xsl:param name=\"see\" />\n\t<xsl:param name=\"space\" />\n\t<xsl:if test=\" $generate-fired-rule = 'true'\">\n\t<svrl:fired-rule context=\"{$context}\" >\n\t\t<!-- Process rich attributes.  -->\n\t\t<xsl:call-template name=\"richParms\">\n\t\t\t<xsl:with-param name=\"fpi\" select=\"$fpi\"/>\n\t\t\t<xsl:with-param name=\"icon\" select=\"$icon\"/>\n\t\t\t<xsl:with-param name=\"lang\" select=\"$lang\"/>\n\t\t\t<xsl:with-param name=\"see\" select=\"$see\" />\n\t\t\t<xsl:with-param name=\"space\" select=\"$space\" />\n\t\t</xsl:call-template>\n\t\t<xsl:if test=\" string( $id )\">\n\t\t\t<xsl:attribute name=\"id\">\n\t\t\t\t<xsl:value-of select=\" $id \" />\n\t\t\t</xsl:attribute>\n\t\t</xsl:if>\n\t\t<xsl:if test=\" string-length( $role ) &gt; 0\">\n\t\t\t<xsl:attribute name=\"role\">\n\t\t\t\t<xsl:value-of select=\" $role \" />\n\t\t\t</xsl:attribute>\n\t\t</xsl:if> \n\t</svrl:fired-rule>\n</xsl:if>\n</xsl:template>\n\n<xsl:template name=\"process-ns\">\n\t<xsl:param name=\"prefix\"/>\n\t<xsl:param name=\"uri\"/>\n\t<svrl:ns-prefix-in-attribute-values uri=\"{$uri}\" prefix=\"{$prefix}\" />\n</xsl:template>\n\n<xsl:template name=\"process-p\"> \n\t<xsl:param name=\"icon\"/>\n\t<xsl:param name=\"class\"/>\n\t<xsl:param name=\"id\"/>\n\t<xsl:param name=\"lang\"/>\n\t \n\t<svrl:text> \n\t\t<xsl:apply-templates mode=\"text\"/>\n\t</svrl:text>\n</xsl:template>\n\n<xsl:template name=\"process-pattern\">\n\t<xsl:param name=\"name\"/>\n\t<xsl:param name=\"id\"/>\n\t<xsl:param name=\"is-a\"/>\n\t\n\t<!-- \"Rich\" parameters -->\n\t<xsl:param name=\"fpi\" />\n\t<xsl:param name=\"icon\" />\n\t<xsl:param name=\"lang\" />\n\t<xsl:param name=\"see\" />\n\t<xsl:param name=\"space\" />\n\t<svrl:active-pattern > \n\t\t<xsl:if test=\" string( $id )\">\n\t\t\t<axsl:attribute name=\"id\">\n\t\t\t\t<xsl:value-of select=\" $id \" />\n\t\t\t</axsl:attribute>\n\t\t</xsl:if>\n\t\t<xsl:if test=\" string( $name )\">\n\t\t\t<axsl:attribute name=\"name\">\n\t\t\t\t<xsl:value-of select=\" $name \" />\n\t\t\t</axsl:attribute>\n\t\t</xsl:if> \n\t\t \n\t\t<xsl:call-template name='richParms'>\n\t\t\t<xsl:with-param name=\"fpi\" select=\"$fpi\"/>\n\t\t\t<xsl:with-param name=\"icon\" select=\"$icon\"/>\n\t\t\t<xsl:with-param name=\"lang\" select=\"$lang\"/>\n\t\t\t<xsl:with-param name=\"see\" select=\"$see\" />\n\t\t\t<xsl:with-param name=\"space\" select=\"$space\" />\n\t\t</xsl:call-template>\n\t\t\n\t\t<!-- ?? report that this screws up iso:title processing  -->\n\t\t<xsl:apply-templates mode=\"do-pattern-p\"/>\n\t\t<!-- ?? Seems that this apply-templates is never triggered DP -->\n\t\t<axsl:apply-templates />\n\t</svrl:active-pattern>\n</xsl:template>\n\n<!-- Overrides skeleton -->\n<xsl:template name=\"process-message\" > \n\t<xsl:param name=\"pattern\"/>\n\t<xsl:param name=\"role\"/>\n</xsl:template>\n\n\n    <!-- Overrides skeleton -->\n\t<xsl:template name=\"process-span\" >\n\t\t<xsl:param name=\"class\" />\n        <xsl:choose>\n        \t<xsl:when test=\" $allow-foreign = 'true'\">\n        \t\t<xsl:copy-of select=\".\"/>\n        \t</xsl:when> \n        <xsl:otherwise>\n\t    <!-- We generate too much whitespace rather than risking concatenation -->\n\t\t<axsl:text> </axsl:text>\n\t\t<xsl:apply-templates mode=\"inline-text\"/>\n\t\t<axsl:text> </axsl:text>\n\t\t</xsl:otherwise>\n\t \t</xsl:choose>\t\n\t</xsl:template>\n\n<!-- =========================================================================== -->\n<!-- processing rich parameters. -->\n<xsl:template name='richParms'>\n\t<!-- \"Rich\" parameters -->\n\t<xsl:param name=\"fpi\" />\n\t<xsl:param name=\"icon\" />\n\t<xsl:param name=\"lang\" />\n\t<xsl:param name=\"see\" />\n\t<xsl:param name=\"space\" />\n\t<!-- Process rich attributes.  -->\n\t<xsl:if  test=\" $allow-foreign = 'true'\">\n\t<xsl:if test=\"string($fpi)\"> \n\t\t<axsl:attribute name=\"fpi\">\n\t\t\t<xsl:value-of select=\"$fpi\"/>\n\t\t</axsl:attribute>\n\t</xsl:if>\n\t<xsl:if test=\"string($icon)\"> \n\t\t<axsl:attribute name=\"icon\">\n\t\t\t<xsl:value-of select=\"$icon\"/>\n\t\t</axsl:attribute>\n\t</xsl:if>\n\t<xsl:if test=\"string($see)\"> \n\t\t<axsl:attribute name=\"see\">\n\t\t\t<xsl:value-of select=\"$see\"/>\n\t\t</axsl:attribute>\n\t</xsl:if>\n\t</xsl:if>\n\t<xsl:if test=\"string($space)\">\n\t\t<axsl:attribute name=\"xml:space\">\n\t\t\t<xsl:value-of select=\"$space\"/>\n\t\t</axsl:attribute>\n\t</xsl:if>\n\t<xsl:if test=\"string($lang)\">\n\t\t<axsl:attribute name=\"xml:lang\">\n\t\t\t<xsl:value-of select=\"$lang\"/>\n\t\t</axsl:attribute>\n\t</xsl:if>\n</xsl:template>\n\n<!-- processing linkable parameters. -->\n<xsl:template name='linkableParms'>\n\t<xsl:param name=\"role\"/>\n\t<xsl:param name=\"subject\"/>\n\t\n\t<!-- ISO SVRL has a role attribute to match the Schematron role attribute -->\n\t<xsl:if test=\" string($role )\">\n\t\t<axsl:attribute name=\"role\">\n\t\t\t<xsl:value-of select=\" $role \" />\n\t\t</axsl:attribute>\n\t</xsl:if>\n\t<!-- ISO SVRL does not have a subject attribute to match the Schematron subject attribute.\n       Instead, the Schematron subject attribute is folded into the location attribute -->\n</xsl:template>\n   \n\n</xsl:stylesheet>\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/isoschematron/resources/xsl/iso-schematron-xslt1/readme.txt",
    "content": "ISO SCHEMATRON 2010\r\n\r\nXSLT implementation by Rick Jelliffe with assistance from members of Schematron-love-in maillist.\r\n\r\n2010-04-21\r\n\r\nTwo distributions are available. One is for XSLT1 engines. \r\nThe other is for XSLT2 engines, such as SAXON 9.\r\n\r\n\r\nThis version of Schematron splits the process into a pipeline of several different XSLT stages.\r\n\r\n1) First, preprocess your Schematron schema with iso_dsdl_include.xsl.  \r\nThis is a macro processor to assemble the schema from various parts. \r\nIf your schema is not in separate parts, you can skip this stage.\r\nThis stage also generates error messages for some common XPath syntax problems.\r\n\r\n2) Second, preprocess the output from stage 1 with iso_abstract_expand.xsl.  \r\nThis is a macro processor to convert abstract patterns to real patterns. \r\nIf your schema does not use abstract patterns, you can skip this\r\nstage.\r\n\r\n3) Third, compile the Schematron schema into an XSLT script. \r\nThis will typically use iso_svrl_for_xslt1.xsl or iso_svrl_for_xslt2.xsl \r\n(which in turn invoke iso_schematron_skeleton_for_xslt1.xsl or iso_schematron_skeleton_for_saxon.xsl)\r\nHowever, other \"meta-stylesheets\" are also in common use; the principle of operation is the same.\r\nIf your schema uses Schematron phases, supply these as command line/invocation parameters\r\nto this process.\r\n\r\n4) Fourth, run the script generated by stage 3 against the document being validated.\r\nIf you are using the SVRL script, then the output of validation will be an XML document.\r\nIf your schema uses Schematron parameters, supply these as command line/invocation parameters\r\nto this process. \r\n\r\n\r\nThe XSLT2 distribution also features several next generation features, \r\nsuch as validating multiple documents. See the source code for details.\r\n\r\nSchematron assertions can be written in any language, of course; the file\r\nsch-messages-en.xhtml contains the diagnostics messages from the XSLT2 skeleton\r\nin English, and this can be used as template to localize the skeleton's\r\nerror messages. Note that typically programming errors in Schematron are XPath\r\nerrors, which requires localized messages from the XSLT engine.\r\n\r\nANT\r\n---\r\nTo give an example of how to process a document, here is a sample ANT task.\r\n\r\n<target  name=\"schematron-compile-test\" >\r\n\r\n\t   <!-- expand inclusions -->\r\n\t   <xslt basedir=\"test/schematron\"\r\n\t   \t\tstyle=\"iso_dsdl_include.xsl\" in=\"test.sch\"  out=\"test1.sch\"> \r\n\t   \t\t\t\t<classpath>\r\n\t   \t\t\t\t\t<pathelement location=\"${lib.dir}/saxon9.jar\"/>\r\n\t   \t\t\t\t</classpath>\r\n\t   </xslt>\r\n\r\n\t   <!-- expand abstract patterns -->\r\n\t   <xslt basedir=\"test/schematron\"\r\n\t   \t\tstyle=\"iso_abstract_expand.xsl\" in=\"test1.sch\"  out=\"test2.sch\"> \r\n\t   \t\t\t\t<classpath>\r\n\t   \t\t\t\t\t<pathelement location=\"${lib.dir}/saxon9.jar\"/>\r\n\t   \t\t\t\t</classpath>\r\n\t   </xslt>\r\n\r\n\r\n\r\n\t   <!-- compile it -->\r\n\t   <xslt basedir=\"test/schematron\"\r\n\t   \t\tstyle=\"iso_svrl_for_xslt2.xsl\" in=\"test2.sch\"  out=\"test.xsl\"> \r\n\t   \t\t\t\t<classpath>\r\n\t   \t\t\t\t\t<pathelement location=\"${lib.dir}/saxon9.jar\"/>\r\n\t   \t\t\t\t</classpath>\r\n\t   </xslt>\r\n\t   \r\n\t   <!-- validate -->\r\n\t   <xslt basedir=\"test/schematron\"\r\n\t\t   \t\tstyle=\"test.xsl\" in=\"instance.xml\"  out=\"instance.svrlt\"> \r\n\t\t   \t\t\t\t<classpath>\r\n\t\t   \t\t\t\t\t<pathelement location=\"${lib.dir}/saxon9.jar\"/>\r\n\t\t   \t\t\t\t</classpath>\r\n\t</xslt>\r\n\t\t</target>\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/lxml.etree.h",
    "content": "/* Generated by Cython 0.29.13 */\n\n#ifndef __PYX_HAVE__lxml__etree\n#define __PYX_HAVE__lxml__etree\n\nstruct LxmlDocument;\nstruct LxmlElement;\nstruct LxmlElementTree;\nstruct LxmlElementTagMatcher;\nstruct LxmlElementIterator;\nstruct LxmlElementBase;\nstruct LxmlElementClassLookup;\nstruct LxmlFallbackElementClassLookup;\n\n/* \"lxml/etree.pyx\":322\n * \n * # type of a function that steps from node to node\n * ctypedef public xmlNode* (*_node_to_node_function)(xmlNode*)             # <<<<<<<<<<<<<<\n * \n * \n */\ntypedef xmlNode *(*_node_to_node_function)(xmlNode *);\n\n/* \"lxml/etree.pyx\":338\n * @cython.final\n * @cython.freelist(8)\n * cdef public class _Document [ type LxmlDocumentType, object LxmlDocument ]:             # <<<<<<<<<<<<<<\n *     u\"\"\"Internal base class to reference a libxml document.\n * \n */\nstruct LxmlDocument {\n  PyObject_HEAD\n  struct __pyx_vtabstruct_4lxml_5etree__Document *__pyx_vtab;\n  int _ns_counter;\n  PyObject *_prefix_tail;\n  xmlDoc *_c_doc;\n  struct __pyx_obj_4lxml_5etree__BaseParser *_parser;\n};\n\n/* \"lxml/etree.pyx\":687\n * \n * @cython.no_gc_clear\n * cdef public class _Element [ type LxmlElementType, object LxmlElement ]:             # <<<<<<<<<<<<<<\n *     u\"\"\"Element class.\n * \n */\nstruct LxmlElement {\n  PyObject_HEAD\n  struct LxmlDocument *_doc;\n  xmlNode *_c_node;\n  PyObject *_tag;\n};\n\n/* \"lxml/etree.pyx\":1853\n * \n * \n * cdef public class _ElementTree [ type LxmlElementTreeType,             # <<<<<<<<<<<<<<\n *                                  object LxmlElementTree ]:\n *     cdef _Document _doc\n */\nstruct LxmlElementTree {\n  PyObject_HEAD\n  struct __pyx_vtabstruct_4lxml_5etree__ElementTree *__pyx_vtab;\n  struct LxmlDocument *_doc;\n  struct LxmlElement *_context_node;\n};\n\n/* \"lxml/etree.pyx\":2597\n * \n * \n * cdef public class _ElementTagMatcher [ object LxmlElementTagMatcher,             # <<<<<<<<<<<<<<\n *                                        type LxmlElementTagMatcherType ]:\n *     \"\"\"\n */\nstruct LxmlElementTagMatcher {\n  PyObject_HEAD\n  struct __pyx_vtabstruct_4lxml_5etree__ElementTagMatcher *__pyx_vtab;\n  PyObject *_pystrings;\n  int _node_type;\n  char *_href;\n  char *_name;\n};\n\n/* \"lxml/etree.pyx\":2628\n *                 self._name = NULL\n * \n * cdef public class _ElementIterator(_ElementTagMatcher) [             # <<<<<<<<<<<<<<\n *     object LxmlElementIterator, type LxmlElementIteratorType ]:\n *     \"\"\"\n */\nstruct LxmlElementIterator {\n  struct LxmlElementTagMatcher __pyx_base;\n  struct LxmlElement *_node;\n  _node_to_node_function _next_element;\n};\n\n/* \"src/lxml/classlookup.pxi\":6\n * # Custom Element classes\n * \n * cdef public class ElementBase(_Element) [ type LxmlElementBaseType,             # <<<<<<<<<<<<<<\n *                                           object LxmlElementBase ]:\n *     u\"\"\"ElementBase(*children, attrib=None, nsmap=None, **_extra)\n */\nstruct LxmlElementBase {\n  struct LxmlElement __pyx_base;\n};\n\n/* \"src/lxml/classlookup.pxi\":210\n * # Element class lookup\n * \n * ctypedef public object (*_element_class_lookup_function)(object, _Document, xmlNode*)             # <<<<<<<<<<<<<<\n * \n * # class to store element class lookup functions\n */\ntypedef PyObject *(*_element_class_lookup_function)(PyObject *, struct LxmlDocument *, xmlNode *);\n\n/* \"src/lxml/classlookup.pxi\":213\n * \n * # class to store element class lookup functions\n * cdef public class ElementClassLookup [ type LxmlElementClassLookupType,             # <<<<<<<<<<<<<<\n *                                        object LxmlElementClassLookup ]:\n *     u\"\"\"ElementClassLookup(self)\n */\nstruct LxmlElementClassLookup {\n  PyObject_HEAD\n  _element_class_lookup_function _lookup_function;\n};\n\n/* \"src/lxml/classlookup.pxi\":221\n * \n * \n * cdef public class FallbackElementClassLookup(ElementClassLookup) \\             # <<<<<<<<<<<<<<\n *          [ type LxmlFallbackElementClassLookupType,\n *            object LxmlFallbackElementClassLookup ]:\n */\nstruct LxmlFallbackElementClassLookup {\n  struct LxmlElementClassLookup __pyx_base;\n  struct __pyx_vtabstruct_4lxml_5etree_FallbackElementClassLookup *__pyx_vtab;\n  struct LxmlElementClassLookup *fallback;\n  _element_class_lookup_function _fallback_function;\n};\n\n#ifndef __PYX_HAVE_API__lxml__etree\n\n#ifndef __PYX_EXTERN_C\n  #ifdef __cplusplus\n    #define __PYX_EXTERN_C extern \"C\"\n  #else\n    #define __PYX_EXTERN_C extern\n  #endif\n#endif\n\n#ifndef DL_IMPORT\n  #define DL_IMPORT(_T) _T\n#endif\n\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlDocumentType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlElementType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlElementTreeType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlElementTagMatcherType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlElementIteratorType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlElementBaseType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlElementClassLookupType;\n__PYX_EXTERN_C DL_IMPORT(PyTypeObject) LxmlFallbackElementClassLookupType;\n\n__PYX_EXTERN_C struct LxmlElement *deepcopyNodeToDocument(struct LxmlDocument *, xmlNode *);\n__PYX_EXTERN_C struct LxmlElementTree *elementTreeFactory(struct LxmlElement *);\n__PYX_EXTERN_C struct LxmlElementTree *newElementTree(struct LxmlElement *, PyObject *);\n__PYX_EXTERN_C struct LxmlElementTree *adoptExternalDocument(xmlDoc *, PyObject *, int);\n__PYX_EXTERN_C struct LxmlElement *elementFactory(struct LxmlDocument *, xmlNode *);\n__PYX_EXTERN_C struct LxmlElement *makeElement(PyObject *, struct LxmlDocument *, PyObject *, PyObject *, PyObject *, PyObject *, PyObject *);\n__PYX_EXTERN_C struct LxmlElement *makeSubElement(struct LxmlElement *, PyObject *, PyObject *, PyObject *, PyObject *, PyObject *);\n__PYX_EXTERN_C void setElementClassLookupFunction(_element_class_lookup_function, PyObject *);\n__PYX_EXTERN_C PyObject *lookupDefaultElementClass(PyObject *, PyObject *, xmlNode *);\n__PYX_EXTERN_C PyObject *lookupNamespaceElementClass(PyObject *, PyObject *, xmlNode *);\n__PYX_EXTERN_C PyObject *callLookupFallback(struct LxmlFallbackElementClassLookup *, struct LxmlDocument *, xmlNode *);\n__PYX_EXTERN_C int tagMatches(xmlNode *, const xmlChar *, const xmlChar *);\n__PYX_EXTERN_C struct LxmlDocument *documentOrRaise(PyObject *);\n__PYX_EXTERN_C struct LxmlElement *rootNodeOrRaise(PyObject *);\n__PYX_EXTERN_C int hasText(xmlNode *);\n__PYX_EXTERN_C int hasTail(xmlNode *);\n__PYX_EXTERN_C PyObject *textOf(xmlNode *);\n__PYX_EXTERN_C PyObject *tailOf(xmlNode *);\n__PYX_EXTERN_C int setNodeText(xmlNode *, PyObject *);\n__PYX_EXTERN_C int setTailText(xmlNode *, PyObject *);\n__PYX_EXTERN_C PyObject *attributeValue(xmlNode *, xmlAttr *);\n__PYX_EXTERN_C PyObject *attributeValueFromNsName(xmlNode *, const xmlChar *, const xmlChar *);\n__PYX_EXTERN_C PyObject *getAttributeValue(struct LxmlElement *, PyObject *, PyObject *);\n__PYX_EXTERN_C PyObject *iterattributes(struct LxmlElement *, int);\n__PYX_EXTERN_C PyObject *collectAttributes(xmlNode *, int);\n__PYX_EXTERN_C int setAttributeValue(struct LxmlElement *, PyObject *, PyObject *);\n__PYX_EXTERN_C int delAttribute(struct LxmlElement *, PyObject *);\n__PYX_EXTERN_C int delAttributeFromNsName(xmlNode *, const xmlChar *, const xmlChar *);\n__PYX_EXTERN_C int hasChild(xmlNode *);\n__PYX_EXTERN_C xmlNode *findChild(xmlNode *, Py_ssize_t);\n__PYX_EXTERN_C xmlNode *findChildForwards(xmlNode *, Py_ssize_t);\n__PYX_EXTERN_C xmlNode *findChildBackwards(xmlNode *, Py_ssize_t);\n__PYX_EXTERN_C xmlNode *nextElement(xmlNode *);\n__PYX_EXTERN_C xmlNode *previousElement(xmlNode *);\n__PYX_EXTERN_C void appendChild(struct LxmlElement *, struct LxmlElement *);\n__PYX_EXTERN_C int appendChildToElement(struct LxmlElement *, struct LxmlElement *);\n__PYX_EXTERN_C PyObject *pyunicode(const xmlChar *);\n__PYX_EXTERN_C PyObject *utf8(PyObject *);\n__PYX_EXTERN_C PyObject *getNsTag(PyObject *);\n__PYX_EXTERN_C PyObject *getNsTagWithEmptyNs(PyObject *);\n__PYX_EXTERN_C PyObject *namespacedName(xmlNode *);\n__PYX_EXTERN_C PyObject *namespacedNameFromNsName(const xmlChar *, const xmlChar *);\n__PYX_EXTERN_C void iteratorStoreNext(struct LxmlElementIterator *, struct LxmlElement *);\n__PYX_EXTERN_C void initTagMatch(struct LxmlElementTagMatcher *, PyObject *);\n__PYX_EXTERN_C xmlNs *findOrBuildNodeNsPrefix(struct LxmlDocument *, xmlNode *, const xmlChar *, const xmlChar *);\n\n#endif /* !__PYX_HAVE_API__lxml__etree */\n\n/* WARNING: the interface of the module init function changed in CPython 3.5. */\n/* It now returns a PyModuleDef instance instead of a PyModule instance. */\n\n#if PY_MAJOR_VERSION < 3\nPyMODINIT_FUNC initetree(void);\n#else\nPyMODINIT_FUNC PyInit_etree(void);\n#endif\n\n#endif /* !__PYX_HAVE__lxml__etree */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/lxml.etree_api.h",
    "content": "/* Generated by Cython 0.29.13 */\n\n#ifndef __PYX_HAVE_API__lxml__etree\n#define __PYX_HAVE_API__lxml__etree\n#ifdef __MINGW64__\n#define MS_WIN64\n#endif\n#include \"Python.h\"\n#include \"lxml.etree.h\"\n\nstatic struct LxmlElement *(*__pyx_api_f_4lxml_5etree_deepcopyNodeToDocument)(struct LxmlDocument *, xmlNode *) = 0;\n#define deepcopyNodeToDocument __pyx_api_f_4lxml_5etree_deepcopyNodeToDocument\nstatic struct LxmlElementTree *(*__pyx_api_f_4lxml_5etree_elementTreeFactory)(struct LxmlElement *) = 0;\n#define elementTreeFactory __pyx_api_f_4lxml_5etree_elementTreeFactory\nstatic struct LxmlElementTree *(*__pyx_api_f_4lxml_5etree_newElementTree)(struct LxmlElement *, PyObject *) = 0;\n#define newElementTree __pyx_api_f_4lxml_5etree_newElementTree\nstatic struct LxmlElementTree *(*__pyx_api_f_4lxml_5etree_adoptExternalDocument)(xmlDoc *, PyObject *, int) = 0;\n#define adoptExternalDocument __pyx_api_f_4lxml_5etree_adoptExternalDocument\nstatic struct LxmlElement *(*__pyx_api_f_4lxml_5etree_elementFactory)(struct LxmlDocument *, xmlNode *) = 0;\n#define elementFactory __pyx_api_f_4lxml_5etree_elementFactory\nstatic struct LxmlElement *(*__pyx_api_f_4lxml_5etree_makeElement)(PyObject *, struct LxmlDocument *, PyObject *, PyObject *, PyObject *, PyObject *, PyObject *) = 0;\n#define makeElement __pyx_api_f_4lxml_5etree_makeElement\nstatic struct LxmlElement *(*__pyx_api_f_4lxml_5etree_makeSubElement)(struct LxmlElement *, PyObject *, PyObject *, PyObject *, PyObject *, PyObject *) = 0;\n#define makeSubElement __pyx_api_f_4lxml_5etree_makeSubElement\nstatic void (*__pyx_api_f_4lxml_5etree_setElementClassLookupFunction)(_element_class_lookup_function, PyObject *) = 0;\n#define setElementClassLookupFunction __pyx_api_f_4lxml_5etree_setElementClassLookupFunction\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_lookupDefaultElementClass)(PyObject *, PyObject *, xmlNode *) = 0;\n#define lookupDefaultElementClass __pyx_api_f_4lxml_5etree_lookupDefaultElementClass\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_lookupNamespaceElementClass)(PyObject *, PyObject *, xmlNode *) = 0;\n#define lookupNamespaceElementClass __pyx_api_f_4lxml_5etree_lookupNamespaceElementClass\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_callLookupFallback)(struct LxmlFallbackElementClassLookup *, struct LxmlDocument *, xmlNode *) = 0;\n#define callLookupFallback __pyx_api_f_4lxml_5etree_callLookupFallback\nstatic int (*__pyx_api_f_4lxml_5etree_tagMatches)(xmlNode *, const xmlChar *, const xmlChar *) = 0;\n#define tagMatches __pyx_api_f_4lxml_5etree_tagMatches\nstatic struct LxmlDocument *(*__pyx_api_f_4lxml_5etree_documentOrRaise)(PyObject *) = 0;\n#define documentOrRaise __pyx_api_f_4lxml_5etree_documentOrRaise\nstatic struct LxmlElement *(*__pyx_api_f_4lxml_5etree_rootNodeOrRaise)(PyObject *) = 0;\n#define rootNodeOrRaise __pyx_api_f_4lxml_5etree_rootNodeOrRaise\nstatic int (*__pyx_api_f_4lxml_5etree_hasText)(xmlNode *) = 0;\n#define hasText __pyx_api_f_4lxml_5etree_hasText\nstatic int (*__pyx_api_f_4lxml_5etree_hasTail)(xmlNode *) = 0;\n#define hasTail __pyx_api_f_4lxml_5etree_hasTail\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_textOf)(xmlNode *) = 0;\n#define textOf __pyx_api_f_4lxml_5etree_textOf\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_tailOf)(xmlNode *) = 0;\n#define tailOf __pyx_api_f_4lxml_5etree_tailOf\nstatic int (*__pyx_api_f_4lxml_5etree_setNodeText)(xmlNode *, PyObject *) = 0;\n#define setNodeText __pyx_api_f_4lxml_5etree_setNodeText\nstatic int (*__pyx_api_f_4lxml_5etree_setTailText)(xmlNode *, PyObject *) = 0;\n#define setTailText __pyx_api_f_4lxml_5etree_setTailText\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_attributeValue)(xmlNode *, xmlAttr *) = 0;\n#define attributeValue __pyx_api_f_4lxml_5etree_attributeValue\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_attributeValueFromNsName)(xmlNode *, const xmlChar *, const xmlChar *) = 0;\n#define attributeValueFromNsName __pyx_api_f_4lxml_5etree_attributeValueFromNsName\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_getAttributeValue)(struct LxmlElement *, PyObject *, PyObject *) = 0;\n#define getAttributeValue __pyx_api_f_4lxml_5etree_getAttributeValue\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_iterattributes)(struct LxmlElement *, int) = 0;\n#define iterattributes __pyx_api_f_4lxml_5etree_iterattributes\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_collectAttributes)(xmlNode *, int) = 0;\n#define collectAttributes __pyx_api_f_4lxml_5etree_collectAttributes\nstatic int (*__pyx_api_f_4lxml_5etree_setAttributeValue)(struct LxmlElement *, PyObject *, PyObject *) = 0;\n#define setAttributeValue __pyx_api_f_4lxml_5etree_setAttributeValue\nstatic int (*__pyx_api_f_4lxml_5etree_delAttribute)(struct LxmlElement *, PyObject *) = 0;\n#define delAttribute __pyx_api_f_4lxml_5etree_delAttribute\nstatic int (*__pyx_api_f_4lxml_5etree_delAttributeFromNsName)(xmlNode *, const xmlChar *, const xmlChar *) = 0;\n#define delAttributeFromNsName __pyx_api_f_4lxml_5etree_delAttributeFromNsName\nstatic int (*__pyx_api_f_4lxml_5etree_hasChild)(xmlNode *) = 0;\n#define hasChild __pyx_api_f_4lxml_5etree_hasChild\nstatic xmlNode *(*__pyx_api_f_4lxml_5etree_findChild)(xmlNode *, Py_ssize_t) = 0;\n#define findChild __pyx_api_f_4lxml_5etree_findChild\nstatic xmlNode *(*__pyx_api_f_4lxml_5etree_findChildForwards)(xmlNode *, Py_ssize_t) = 0;\n#define findChildForwards __pyx_api_f_4lxml_5etree_findChildForwards\nstatic xmlNode *(*__pyx_api_f_4lxml_5etree_findChildBackwards)(xmlNode *, Py_ssize_t) = 0;\n#define findChildBackwards __pyx_api_f_4lxml_5etree_findChildBackwards\nstatic xmlNode *(*__pyx_api_f_4lxml_5etree_nextElement)(xmlNode *) = 0;\n#define nextElement __pyx_api_f_4lxml_5etree_nextElement\nstatic xmlNode *(*__pyx_api_f_4lxml_5etree_previousElement)(xmlNode *) = 0;\n#define previousElement __pyx_api_f_4lxml_5etree_previousElement\nstatic void (*__pyx_api_f_4lxml_5etree_appendChild)(struct LxmlElement *, struct LxmlElement *) = 0;\n#define appendChild __pyx_api_f_4lxml_5etree_appendChild\nstatic int (*__pyx_api_f_4lxml_5etree_appendChildToElement)(struct LxmlElement *, struct LxmlElement *) = 0;\n#define appendChildToElement __pyx_api_f_4lxml_5etree_appendChildToElement\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_pyunicode)(const xmlChar *) = 0;\n#define pyunicode __pyx_api_f_4lxml_5etree_pyunicode\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_utf8)(PyObject *) = 0;\n#define utf8 __pyx_api_f_4lxml_5etree_utf8\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_getNsTag)(PyObject *) = 0;\n#define getNsTag __pyx_api_f_4lxml_5etree_getNsTag\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_getNsTagWithEmptyNs)(PyObject *) = 0;\n#define getNsTagWithEmptyNs __pyx_api_f_4lxml_5etree_getNsTagWithEmptyNs\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_namespacedName)(xmlNode *) = 0;\n#define namespacedName __pyx_api_f_4lxml_5etree_namespacedName\nstatic PyObject *(*__pyx_api_f_4lxml_5etree_namespacedNameFromNsName)(const xmlChar *, const xmlChar *) = 0;\n#define namespacedNameFromNsName __pyx_api_f_4lxml_5etree_namespacedNameFromNsName\nstatic void (*__pyx_api_f_4lxml_5etree_iteratorStoreNext)(struct LxmlElementIterator *, struct LxmlElement *) = 0;\n#define iteratorStoreNext __pyx_api_f_4lxml_5etree_iteratorStoreNext\nstatic void (*__pyx_api_f_4lxml_5etree_initTagMatch)(struct LxmlElementTagMatcher *, PyObject *) = 0;\n#define initTagMatch __pyx_api_f_4lxml_5etree_initTagMatch\nstatic xmlNs *(*__pyx_api_f_4lxml_5etree_findOrBuildNodeNsPrefix)(struct LxmlDocument *, xmlNode *, const xmlChar *, const xmlChar *) = 0;\n#define findOrBuildNodeNsPrefix __pyx_api_f_4lxml_5etree_findOrBuildNodeNsPrefix\n#if !defined(__Pyx_PyIdentifier_FromString)\n#if PY_MAJOR_VERSION < 3\n  #define __Pyx_PyIdentifier_FromString(s) PyString_FromString(s)\n#else\n  #define __Pyx_PyIdentifier_FromString(s) PyUnicode_FromString(s)\n#endif\n#endif\n\n#ifndef __PYX_HAVE_RT_ImportFunction\n#define __PYX_HAVE_RT_ImportFunction\nstatic int __Pyx_ImportFunction(PyObject *module, const char *funcname, void (**f)(void), const char *sig) {\n    PyObject *d = 0;\n    PyObject *cobj = 0;\n    union {\n        void (*fp)(void);\n        void *p;\n    } tmp;\n    d = PyObject_GetAttrString(module, (char *)\"__pyx_capi__\");\n    if (!d)\n        goto bad;\n    cobj = PyDict_GetItemString(d, funcname);\n    if (!cobj) {\n        PyErr_Format(PyExc_ImportError,\n            \"%.200s does not export expected C function %.200s\",\n                PyModule_GetName(module), funcname);\n        goto bad;\n    }\n#if PY_VERSION_HEX >= 0x02070000\n    if (!PyCapsule_IsValid(cobj, sig)) {\n        PyErr_Format(PyExc_TypeError,\n            \"C function %.200s.%.200s has wrong signature (expected %.500s, got %.500s)\",\n             PyModule_GetName(module), funcname, sig, PyCapsule_GetName(cobj));\n        goto bad;\n    }\n    tmp.p = PyCapsule_GetPointer(cobj, sig);\n#else\n    {const char *desc, *s1, *s2;\n    desc = (const char *)PyCObject_GetDesc(cobj);\n    if (!desc)\n        goto bad;\n    s1 = desc; s2 = sig;\n    while (*s1 != '\\0' && *s1 == *s2) { s1++; s2++; }\n    if (*s1 != *s2) {\n        PyErr_Format(PyExc_TypeError,\n            \"C function %.200s.%.200s has wrong signature (expected %.500s, got %.500s)\",\n             PyModule_GetName(module), funcname, sig, desc);\n        goto bad;\n    }\n    tmp.p = PyCObject_AsVoidPtr(cobj);}\n#endif\n    *f = tmp.fp;\n    if (!(*f))\n        goto bad;\n    Py_DECREF(d);\n    return 0;\nbad:\n    Py_XDECREF(d);\n    return -1;\n}\n#endif\n\n\nstatic int import_lxml__etree(void) {\n  PyObject *module = 0;\n  module = PyImport_ImportModule(\"lxml.etree\");\n  if (!module) goto bad;\n  if (__Pyx_ImportFunction(module, \"deepcopyNodeToDocument\", (void (**)(void))&__pyx_api_f_4lxml_5etree_deepcopyNodeToDocument, \"struct LxmlElement *(struct LxmlDocument *, xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"elementTreeFactory\", (void (**)(void))&__pyx_api_f_4lxml_5etree_elementTreeFactory, \"struct LxmlElementTree *(struct LxmlElement *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"newElementTree\", (void (**)(void))&__pyx_api_f_4lxml_5etree_newElementTree, \"struct LxmlElementTree *(struct LxmlElement *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"adoptExternalDocument\", (void (**)(void))&__pyx_api_f_4lxml_5etree_adoptExternalDocument, \"struct LxmlElementTree *(xmlDoc *, PyObject *, int)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"elementFactory\", (void (**)(void))&__pyx_api_f_4lxml_5etree_elementFactory, \"struct LxmlElement *(struct LxmlDocument *, xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"makeElement\", (void (**)(void))&__pyx_api_f_4lxml_5etree_makeElement, \"struct LxmlElement *(PyObject *, struct LxmlDocument *, PyObject *, PyObject *, PyObject *, PyObject *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"makeSubElement\", (void (**)(void))&__pyx_api_f_4lxml_5etree_makeSubElement, \"struct LxmlElement *(struct LxmlElement *, PyObject *, PyObject *, PyObject *, PyObject *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"setElementClassLookupFunction\", (void (**)(void))&__pyx_api_f_4lxml_5etree_setElementClassLookupFunction, \"void (_element_class_lookup_function, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"lookupDefaultElementClass\", (void (**)(void))&__pyx_api_f_4lxml_5etree_lookupDefaultElementClass, \"PyObject *(PyObject *, PyObject *, xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"lookupNamespaceElementClass\", (void (**)(void))&__pyx_api_f_4lxml_5etree_lookupNamespaceElementClass, \"PyObject *(PyObject *, PyObject *, xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"callLookupFallback\", (void (**)(void))&__pyx_api_f_4lxml_5etree_callLookupFallback, \"PyObject *(struct LxmlFallbackElementClassLookup *, struct LxmlDocument *, xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"tagMatches\", (void (**)(void))&__pyx_api_f_4lxml_5etree_tagMatches, \"int (xmlNode *, const xmlChar *, const xmlChar *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"documentOrRaise\", (void (**)(void))&__pyx_api_f_4lxml_5etree_documentOrRaise, \"struct LxmlDocument *(PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"rootNodeOrRaise\", (void (**)(void))&__pyx_api_f_4lxml_5etree_rootNodeOrRaise, \"struct LxmlElement *(PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"hasText\", (void (**)(void))&__pyx_api_f_4lxml_5etree_hasText, \"int (xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"hasTail\", (void (**)(void))&__pyx_api_f_4lxml_5etree_hasTail, \"int (xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"textOf\", (void (**)(void))&__pyx_api_f_4lxml_5etree_textOf, \"PyObject *(xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"tailOf\", (void (**)(void))&__pyx_api_f_4lxml_5etree_tailOf, \"PyObject *(xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"setNodeText\", (void (**)(void))&__pyx_api_f_4lxml_5etree_setNodeText, \"int (xmlNode *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"setTailText\", (void (**)(void))&__pyx_api_f_4lxml_5etree_setTailText, \"int (xmlNode *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"attributeValue\", (void (**)(void))&__pyx_api_f_4lxml_5etree_attributeValue, \"PyObject *(xmlNode *, xmlAttr *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"attributeValueFromNsName\", (void (**)(void))&__pyx_api_f_4lxml_5etree_attributeValueFromNsName, \"PyObject *(xmlNode *, const xmlChar *, const xmlChar *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"getAttributeValue\", (void (**)(void))&__pyx_api_f_4lxml_5etree_getAttributeValue, \"PyObject *(struct LxmlElement *, PyObject *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"iterattributes\", (void (**)(void))&__pyx_api_f_4lxml_5etree_iterattributes, \"PyObject *(struct LxmlElement *, int)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"collectAttributes\", (void (**)(void))&__pyx_api_f_4lxml_5etree_collectAttributes, \"PyObject *(xmlNode *, int)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"setAttributeValue\", (void (**)(void))&__pyx_api_f_4lxml_5etree_setAttributeValue, \"int (struct LxmlElement *, PyObject *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"delAttribute\", (void (**)(void))&__pyx_api_f_4lxml_5etree_delAttribute, \"int (struct LxmlElement *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"delAttributeFromNsName\", (void (**)(void))&__pyx_api_f_4lxml_5etree_delAttributeFromNsName, \"int (xmlNode *, const xmlChar *, const xmlChar *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"hasChild\", (void (**)(void))&__pyx_api_f_4lxml_5etree_hasChild, \"int (xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"findChild\", (void (**)(void))&__pyx_api_f_4lxml_5etree_findChild, \"xmlNode *(xmlNode *, Py_ssize_t)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"findChildForwards\", (void (**)(void))&__pyx_api_f_4lxml_5etree_findChildForwards, \"xmlNode *(xmlNode *, Py_ssize_t)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"findChildBackwards\", (void (**)(void))&__pyx_api_f_4lxml_5etree_findChildBackwards, \"xmlNode *(xmlNode *, Py_ssize_t)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"nextElement\", (void (**)(void))&__pyx_api_f_4lxml_5etree_nextElement, \"xmlNode *(xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"previousElement\", (void (**)(void))&__pyx_api_f_4lxml_5etree_previousElement, \"xmlNode *(xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"appendChild\", (void (**)(void))&__pyx_api_f_4lxml_5etree_appendChild, \"void (struct LxmlElement *, struct LxmlElement *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"appendChildToElement\", (void (**)(void))&__pyx_api_f_4lxml_5etree_appendChildToElement, \"int (struct LxmlElement *, struct LxmlElement *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"pyunicode\", (void (**)(void))&__pyx_api_f_4lxml_5etree_pyunicode, \"PyObject *(const xmlChar *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"utf8\", (void (**)(void))&__pyx_api_f_4lxml_5etree_utf8, \"PyObject *(PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"getNsTag\", (void (**)(void))&__pyx_api_f_4lxml_5etree_getNsTag, \"PyObject *(PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"getNsTagWithEmptyNs\", (void (**)(void))&__pyx_api_f_4lxml_5etree_getNsTagWithEmptyNs, \"PyObject *(PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"namespacedName\", (void (**)(void))&__pyx_api_f_4lxml_5etree_namespacedName, \"PyObject *(xmlNode *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"namespacedNameFromNsName\", (void (**)(void))&__pyx_api_f_4lxml_5etree_namespacedNameFromNsName, \"PyObject *(const xmlChar *, const xmlChar *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"iteratorStoreNext\", (void (**)(void))&__pyx_api_f_4lxml_5etree_iteratorStoreNext, \"void (struct LxmlElementIterator *, struct LxmlElement *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"initTagMatch\", (void (**)(void))&__pyx_api_f_4lxml_5etree_initTagMatch, \"void (struct LxmlElementTagMatcher *, PyObject *)\") < 0) goto bad;\n  if (__Pyx_ImportFunction(module, \"findOrBuildNodeNsPrefix\", (void (**)(void))&__pyx_api_f_4lxml_5etree_findOrBuildNodeNsPrefix, \"xmlNs *(struct LxmlDocument *, xmlNode *, const xmlChar *, const xmlChar *)\") < 0) goto bad;\n  Py_DECREF(module); module = 0;\n  return 0;\n  bad:\n  Py_XDECREF(module);\n  return -1;\n}\n\n#endif /* !__PYX_HAVE_API__lxml__etree */\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/pyclasslookup.py",
    "content": "# dummy module for backwards compatibility\n\nfrom lxml.etree import PythonElementClassLookup\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/sax.py",
    "content": "# cython: language_level=2\n\n\"\"\"\nSAX-based adapter to copy trees from/to the Python standard library.\n\nUse the `ElementTreeContentHandler` class to build an ElementTree from\nSAX events.\n\nUse the `ElementTreeProducer` class or the `saxify()` function to fire\nthe SAX events of an ElementTree against a SAX ContentHandler.\n\nSee http://codespeak.net/lxml/sax.html\n\"\"\"\n\nfrom __future__ import absolute_import\n\nfrom xml.sax.handler import ContentHandler\nfrom lxml import etree\nfrom lxml.etree import ElementTree, SubElement\nfrom lxml.etree import Comment, ProcessingInstruction\n\n\nclass SaxError(etree.LxmlError):\n    \"\"\"General SAX error.\n    \"\"\"\n\n\ndef _getNsTag(tag):\n    if tag[0] == '{':\n        return tuple(tag[1:].split('}', 1))\n    else:\n        return None, tag\n\n\nclass ElementTreeContentHandler(ContentHandler):\n    \"\"\"Build an lxml ElementTree from SAX events.\n    \"\"\"\n    def __init__(self, makeelement=None):\n        ContentHandler.__init__(self)\n        self._root = None\n        self._root_siblings = []\n        self._element_stack = []\n        self._default_ns = None\n        self._ns_mapping = { None : [None] }\n        self._new_mappings = {}\n        if makeelement is None:\n            makeelement = etree.Element\n        self._makeelement = makeelement\n\n    def _get_etree(self):\n        \"Contains the generated ElementTree after parsing is finished.\"\n        return ElementTree(self._root)\n\n    etree = property(_get_etree, doc=_get_etree.__doc__)\n\n    def setDocumentLocator(self, locator):\n        pass\n\n    def startDocument(self):\n        pass\n\n    def endDocument(self):\n        pass\n\n    def startPrefixMapping(self, prefix, uri):\n        self._new_mappings[prefix] = uri\n        try:\n            self._ns_mapping[prefix].append(uri)\n        except KeyError:\n            self._ns_mapping[prefix] = [uri]\n        if prefix is None:\n            self._default_ns = uri\n\n    def endPrefixMapping(self, prefix):\n        ns_uri_list = self._ns_mapping[prefix]\n        ns_uri_list.pop()\n        if prefix is None:\n            self._default_ns = ns_uri_list[-1]\n\n    def _buildTag(self, ns_name_tuple):\n        ns_uri, local_name = ns_name_tuple\n        if ns_uri:\n            el_tag = \"{%s}%s\" % ns_name_tuple\n        elif self._default_ns:\n            el_tag = \"{%s}%s\" % (self._default_ns, local_name)\n        else:\n            el_tag = local_name\n        return el_tag\n\n    def startElementNS(self, ns_name, qname, attributes=None):\n        el_name = self._buildTag(ns_name)\n        if attributes:\n            attrs = {}\n            try:\n                iter_attributes = attributes.iteritems()\n            except AttributeError:\n                iter_attributes = attributes.items()\n\n            for name_tuple, value in iter_attributes:\n                if name_tuple[0]:\n                    attr_name = \"{%s}%s\" % name_tuple\n                else:\n                    attr_name = name_tuple[1]\n                attrs[attr_name] = value\n        else:\n            attrs = None\n\n        element_stack = self._element_stack\n        if self._root is None:\n            element = self._root = \\\n                      self._makeelement(el_name, attrs, self._new_mappings)\n            if self._root_siblings and hasattr(element, 'addprevious'):\n                for sibling in self._root_siblings:\n                    element.addprevious(sibling)\n            del self._root_siblings[:]\n        else:\n            element = SubElement(element_stack[-1], el_name,\n                                 attrs, self._new_mappings)\n        element_stack.append(element)\n\n        self._new_mappings.clear()\n\n    def processingInstruction(self, target, data):\n        pi = ProcessingInstruction(target, data)\n        if self._root is None:\n            self._root_siblings.append(pi)\n        else:\n            self._element_stack[-1].append(pi)\n\n    def endElementNS(self, ns_name, qname):\n        element = self._element_stack.pop()\n        el_tag = self._buildTag(ns_name)\n        if el_tag != element.tag:\n            raise SaxError(\"Unexpected element closed: \" + el_tag)\n\n    def startElement(self, name, attributes=None):\n        if attributes:\n            attributes = dict(\n                    [((None, k), v) for k, v in attributes.items()]\n                )\n        self.startElementNS((None, name), name, attributes)\n\n    def endElement(self, name):\n        self.endElementNS((None, name), name)\n\n    def characters(self, data):\n        last_element = self._element_stack[-1]\n        try:\n            # if there already is a child element, we must append to its tail\n            last_element = last_element[-1]\n            last_element.tail = (last_element.tail or '') + data\n        except IndexError:\n            # otherwise: append to the text\n            last_element.text = (last_element.text or '') + data\n\n    ignorableWhitespace = characters\n\n\nclass ElementTreeProducer(object):\n    \"\"\"Produces SAX events for an element and children.\n    \"\"\"\n    def __init__(self, element_or_tree, content_handler):\n        try:\n            element = element_or_tree.getroot()\n        except AttributeError:\n            element = element_or_tree\n        self._element = element\n        self._content_handler = content_handler\n        from xml.sax.xmlreader import AttributesNSImpl as attr_class\n        self._attr_class = attr_class\n        self._empty_attributes = attr_class({}, {})\n\n    def saxify(self):\n        self._content_handler.startDocument()\n\n        element = self._element\n        if hasattr(element, 'getprevious'):\n            siblings = []\n            sibling = element.getprevious()\n            while getattr(sibling, 'tag', None) is ProcessingInstruction:\n                siblings.append(sibling)\n                sibling = sibling.getprevious()\n            for sibling in siblings[::-1]:\n                self._recursive_saxify(sibling, {})\n\n        self._recursive_saxify(element, {})\n\n        if hasattr(element, 'getnext'):\n            sibling = element.getnext()\n            while getattr(sibling, 'tag', None) is ProcessingInstruction:\n                self._recursive_saxify(sibling, {})\n                sibling = sibling.getnext()\n\n        self._content_handler.endDocument()\n\n    def _recursive_saxify(self, element, parent_nsmap):\n        content_handler = self._content_handler\n        tag = element.tag\n        if tag is Comment or tag is ProcessingInstruction:\n            if tag is ProcessingInstruction:\n                content_handler.processingInstruction(\n                    element.target, element.text)\n            tail = element.tail\n            if tail:\n                content_handler.characters(tail)\n            return\n\n        element_nsmap = element.nsmap\n        new_prefixes = []\n        if element_nsmap != parent_nsmap:\n            # There have been updates to the namespace\n            for prefix, ns_uri in element_nsmap.items():\n                if parent_nsmap.get(prefix) != ns_uri:\n                    new_prefixes.append( (prefix, ns_uri) )\n\n        attribs = element.items()\n        if attribs:\n            attr_values = {}\n            attr_qnames = {}\n            for attr_ns_name, value in attribs:\n                attr_ns_tuple = _getNsTag(attr_ns_name)\n                attr_values[attr_ns_tuple] = value\n                attr_qnames[attr_ns_tuple] = self._build_qname(\n                    attr_ns_tuple[0], attr_ns_tuple[1], element_nsmap,\n                    preferred_prefix=None, is_attribute=True)\n            sax_attributes = self._attr_class(attr_values, attr_qnames)\n        else:\n            sax_attributes = self._empty_attributes\n\n        ns_uri, local_name = _getNsTag(tag)\n        qname = self._build_qname(\n            ns_uri, local_name, element_nsmap, element.prefix, is_attribute=False)\n\n        for prefix, uri in new_prefixes:\n            content_handler.startPrefixMapping(prefix, uri)\n        content_handler.startElementNS(\n            (ns_uri, local_name), qname, sax_attributes)\n        text = element.text\n        if text:\n            content_handler.characters(text)\n        for child in element:\n            self._recursive_saxify(child, element_nsmap)\n        content_handler.endElementNS((ns_uri, local_name), qname)\n        for prefix, uri in new_prefixes:\n            content_handler.endPrefixMapping(prefix)\n        tail = element.tail\n        if tail:\n            content_handler.characters(tail)\n\n    def _build_qname(self, ns_uri, local_name, nsmap, preferred_prefix, is_attribute):\n        if ns_uri is None:\n            return local_name\n\n        if not is_attribute and nsmap.get(preferred_prefix) == ns_uri:\n            prefix = preferred_prefix\n        else:\n            # Pick the first matching prefix, in alphabetical order.\n            candidates = [\n                pfx for (pfx, uri) in nsmap.items()\n                if pfx is not None and uri == ns_uri\n            ]\n            prefix = (\n                candidates[0] if len(candidates) == 1\n                else min(candidates) if candidates\n                else None\n            )\n\n        if prefix is None:\n            # Default namespace\n            return local_name\n        return prefix + ':' + local_name\n\n\ndef saxify(element_or_tree, content_handler):\n    \"\"\"One-shot helper to generate SAX events from an XML tree and fire\n    them against a SAX ContentHandler.\n    \"\"\"\n    return ElementTreeProducer(element_or_tree, content_handler).saxify()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml/usedoctest.py",
    "content": "\"\"\"Doctest module for XML comparison.\n\nUsage::\n\n   >>> import lxml.usedoctest\n   >>> # now do your XML doctests ...\n\nSee `lxml.doctestcompare`\n\"\"\"\n\nfrom lxml import doctestcompare\n\ndoctestcompare.temp_install(del_module=__name__)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml-4.4.1.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml-4.4.1.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: lxml\nVersion: 4.4.1\nSummary: Powerful and Pythonic XML processing library combining libxml2/libxslt with the ElementTree API.\nHome-page: http://lxml.de/\nAuthor: lxml dev team\nAuthor-email: lxml-dev@lxml.de\nMaintainer: lxml dev team\nMaintainer-email: lxml-dev@lxml.de\nLicense: BSD\nPlatform: UNKNOWN\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Intended Audience :: Developers\nClassifier: Intended Audience :: Information Technology\nClassifier: License :: OSI Approved :: BSD License\nClassifier: Programming Language :: Cython\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nClassifier: Programming Language :: C\nClassifier: Operating System :: OS Independent\nClassifier: Topic :: Text Processing :: Markup :: HTML\nClassifier: Topic :: Text Processing :: Markup :: XML\nClassifier: Topic :: Software Development :: Libraries :: Python Modules\nRequires-Python: >=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, != 3.4.*\nProvides-Extra: cssselect\nProvides-Extra: html5\nProvides-Extra: htmlsoup\nProvides-Extra: source\nProvides-Extra: cssselect\nRequires-Dist: cssselect (>=0.7); extra == 'cssselect'\nProvides-Extra: html5\nRequires-Dist: html5lib; extra == 'html5'\nProvides-Extra: htmlsoup\nRequires-Dist: BeautifulSoup4; extra == 'htmlsoup'\nProvides-Extra: source\nRequires-Dist: Cython (>=0.29.7); extra == 'source'\n\nlxml is a Pythonic, mature binding for the libxml2 and libxslt libraries.  It\nprovides safe and convenient access to these libraries using the ElementTree\nAPI.\n\nIt extends the ElementTree API significantly to offer support for XPath,\nRelaxNG, XML Schema, XSLT, C14N and much more.\n\nTo contact the project, go to the `project home page\n<http://lxml.de/>`_ or see our bug tracker at\nhttps://launchpad.net/lxml\n\nIn case you want to use the current in-development version of lxml,\nyou can get it from the github repository at\nhttps://github.com/lxml/lxml .  Note that this requires Cython to\nbuild the sources, see the build instructions on the project home\npage.  To the same end, running ``easy_install lxml==dev`` will\ninstall lxml from\nhttps://github.com/lxml/lxml/tarball/master#egg=lxml-dev if you have\nan appropriate version of Cython installed.\n\n\nAfter an official release of a new stable series, bug fixes may become\navailable at\nhttps://github.com/lxml/lxml/tree/lxml-4.4 .\nRunning ``easy_install lxml==4.4bugfix`` will install\nthe unreleased branch state from\nhttps://github.com/lxml/lxml/tarball/lxml-4.4#egg=lxml-4.4bugfix\nas soon as a maintenance branch has been established.  Note that this\nrequires Cython to be installed at an appropriate version for the build.\n\n4.4.1 (2019-08-11)\n==================\n\nBugs fixed\n----------\n\n* LP#1838252: The order of an OrderedDict was lost in 4.4.0 when passing it as\n  attrib mapping during element creation.\n\n* LP#1838521: The package metadata now lists the supported Python versions.\n\n\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml-4.4.1.dist-info/RECORD",
    "content": "lxml-4.4.1.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nlxml-4.4.1.dist-info/METADATA,sha256=a22r0w1l_2nSnf0QdzRhHY7fA2qbyVZ07KoY1iwB7bQ,3141\r\nlxml-4.4.1.dist-info/RECORD,,\r\nlxml-4.4.1.dist-info/WHEEL,sha256=d2ILPScH-y2UwGxsW1PeA2TT-KW0Git4AJ6LeOK8sQo,109\r\nlxml-4.4.1.dist-info/top_level.txt,sha256=NjD988wqaKq512nshNdLt-uDxsjkp4Bh51m6N-dhUrk,5\r\nlxml/ElementInclude.py,sha256=BXdowSt8EyZThmV-XjcitqFrleu0f5hWcnI3NnV4xug,8591\r\nlxml/__init__.py,sha256=lYLRn8M0_xdnN2bhEnZ2L7mlY5zM3gwz1kgLILLxC34,551\r\nlxml/__pycache__/ElementInclude.cpython-36.pyc,,\r\nlxml/__pycache__/__init__.cpython-36.pyc,,\r\nlxml/__pycache__/_elementpath.cpython-36.pyc,,\r\nlxml/__pycache__/builder.cpython-36.pyc,,\r\nlxml/__pycache__/cssselect.cpython-36.pyc,,\r\nlxml/__pycache__/doctestcompare.cpython-36.pyc,,\r\nlxml/__pycache__/pyclasslookup.cpython-36.pyc,,\r\nlxml/__pycache__/sax.cpython-36.pyc,,\r\nlxml/__pycache__/usedoctest.cpython-36.pyc,,\r\nlxml/_elementpath.cpython-36m-x86_64-linux-gnu.so,sha256=N0CyYEP_CxEWH0h7D8HmEPgkRDB9EWHQYs0kBeY8dUo,311585\r\nlxml/_elementpath.py,sha256=wo6_CnGtKSkadI-krW8gbEZ1fVPTnIJINNwrdRfT_fw,10742\r\nlxml/builder.cpython-36m-x86_64-linux-gnu.so,sha256=TT-WMNmWj0wjTmahIIV18dKkh0zIU1sezV9cLhOjeks,145183\r\nlxml/builder.py,sha256=R5WsHI0bCOHYehskKXENvBkuarviL5rNJsmnh6cZGUA,7975\r\nlxml/cssselect.py,sha256=ADTqox2BUhZI_28K26Dnd-rPqvwL1A7KpXwDetXZLfA,3366\r\nlxml/doctestcompare.py,sha256=dAjqNzMGJuDsxY0xOXwOWzEsq7gSfQf-6uuxZZwaNXM,18339\r\nlxml/etree.cpython-36m-x86_64-linux-gnu.so,sha256=YKb9eGz-L5f46lLqTpXqWUWPxsIlzTOtK8uiS8W-dFM,6880029\r\nlxml/etree.h,sha256=ovyaRkrRJRkTtHo0YoPvopYLhrcOVUvYhuio6iTmF58,8555\r\nlxml/etree_api.h,sha256=ctFt9PRo6JEtPZYPmZhWs6dDQwgtc_OuPjNQFp2io-U,17467\r\nlxml/html/ElementSoup.py,sha256=9NQNksJmEr0M2DqzaKhXWdALLo0btwVwjgTHnkfGfvk,319\r\nlxml/html/__init__.py,sha256=vFxnC3XWddHuM3pR8pYE7cRxdl1TgtJF0twoUVDTzUk,64806\r\nlxml/html/__pycache__/ElementSoup.cpython-36.pyc,,\r\nlxml/html/__pycache__/__init__.cpython-36.pyc,,\r\nlxml/html/__pycache__/_diffcommand.cpython-36.pyc,,\r\nlxml/html/__pycache__/_html5builder.cpython-36.pyc,,\r\nlxml/html/__pycache__/_setmixin.cpython-36.pyc,,\r\nlxml/html/__pycache__/builder.cpython-36.pyc,,\r\nlxml/html/__pycache__/clean.cpython-36.pyc,,\r\nlxml/html/__pycache__/defs.cpython-36.pyc,,\r\nlxml/html/__pycache__/diff.cpython-36.pyc,,\r\nlxml/html/__pycache__/formfill.cpython-36.pyc,,\r\nlxml/html/__pycache__/html5parser.cpython-36.pyc,,\r\nlxml/html/__pycache__/soupparser.cpython-36.pyc,,\r\nlxml/html/__pycache__/usedoctest.cpython-36.pyc,,\r\nlxml/html/_diffcommand.py,sha256=7-tz3udrgg0unGPAI8pa_uN4e7vW0MmgOXE43kKPdw8,2121\r\nlxml/html/_html5builder.py,sha256=cASxN0Tks3_vqCA_sXa1oCx_McyRL6VpuRLA1T-B58o,3246\r\nlxml/html/_setmixin.py,sha256=uVCgBUC4SJ7N9GotmlKHrhH7R4Kk7wGU3u1WmEJKGeM,1184\r\nlxml/html/builder.py,sha256=1NuLqKPSaat75wCGufVuv1jIeBLuQCWsJVA_T2XjjUI,4310\r\nlxml/html/clean.cpython-36m-x86_64-linux-gnu.so,sha256=pUyu-5nzzYpbGCP8l8xkGXAGc8C-IFuUJO1XdvnspIg,387009\r\nlxml/html/clean.py,sha256=7LoNhrkhE25j3wgjEVBgONk38TlIwUlaj44B0wVX-24,26422\r\nlxml/html/defs.py,sha256=ohRO7uinvxWwLZb59FsYdzr6UcIvCjuSWnnYwev6c9M,4192\r\nlxml/html/diff.cpython-36m-x86_64-linux-gnu.so,sha256=GYoV6i8rcINOtNQgmfH9_V4BHpvhhAheFsBJsMOJYlQ,527379\r\nlxml/html/diff.py,sha256=F1A1vYO3dQdYfGDkI46zj5GN6UzaGMQt7ezqV5i324Q,30553\r\nlxml/html/formfill.py,sha256=9lnv7BnrQS0HOBY8ToeP1408xMN1wnltpsY-0CTGBpQ,9689\r\nlxml/html/html5parser.py,sha256=dnyC4cqHxywjZSzk0mu2L7THTZjxhg4yF4pncjusa_w,8634\r\nlxml/html/soupparser.py,sha256=tfdraMayPbMBCd2kGxUoTvNkhKUclfP3LmV9R85WKI4,10203\r\nlxml/html/usedoctest.py,sha256=tPlmVz4KK1GRKV5DJLrdVECeqsT9PlDzSqqTodVi5s0,249\r\nlxml/includes/__init__.pxd,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0\r\nlxml/includes/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0\r\nlxml/includes/__pycache__/__init__.cpython-36.pyc,,\r\nlxml/includes/c14n.pxd,sha256=pGf910mVH9IdBb7r_aE-J59axIQcqFH4Sx_Tm0PA1m0,1123\r\nlxml/includes/config.pxd,sha256=H6Mrl8It21hzRI2hzMId9W48QqkYYkoLT4dniLNmdTw,96\r\nlxml/includes/dtdvalid.pxd,sha256=Rf2vRBbM4O1AOiIsUk_5M7pV3Dz309sS7Ccd2zGFHT0,671\r\nlxml/includes/etree_defs.h,sha256=e8Nlc-wG74xRyK3EqonkWx02LGzq7pl6bmLYzuWO9_Q,15559\r\nlxml/includes/etreepublic.pxd,sha256=3cdjIVlfkeZWYUav4y_T2uHwAo8yUCTlCvNLEvsZ_aI,10122\r\nlxml/includes/htmlparser.pxd,sha256=Va2qbs5zVokERn57HbDY__CiBQOoCS4uI9wEfCnT6zk,2868\r\nlxml/includes/libexslt/exslt.h,sha256=Z91WbHADa4o5-kJufstf6Y100qBTMqBiK1aZsxcp_Ao,3018\r\nlxml/includes/libexslt/exsltconfig.h,sha256=oSMQTfbUeZRxZOO7FW6ijRJTlzUUjTL6FlWWcqNruNs,1217\r\nlxml/includes/libexslt/exsltexports.h,sha256=QQ8XCrP1vKIkdXlmDBgVP239S-1zBftHCK1RKBFPnRQ,3396\r\nlxml/includes/libxml/DOCBparser.h,sha256=QCzfpD-a5w-3T9fbCLhJI12H_iN5LVtOiWu3L21eyJo,3157\r\nlxml/includes/libxml/HTMLparser.h,sha256=3LY9MRXs5ZCMbF91gTQol33ceRpambWVY0ciEPu6otI,9410\r\nlxml/includes/libxml/HTMLtree.h,sha256=-i37-IqS_LU9jei_9yUi6Fs80ZErlrCGZWwaTHIg9p8,3646\r\nlxml/includes/libxml/SAX.h,sha256=EgEjbXP_0OtfSYEb6FHHnWmPEgnQYZ5IaX8Ehh7YvVg,4341\r\nlxml/includes/libxml/SAX2.h,sha256=9Z6vTKhysqsnLMv63aJTcyRLh6Qm8Base48qRZWMQ0M,4949\r\nlxml/includes/libxml/c14n.h,sha256=yJO-_m0HOgTfbBiv_j-P02LftZ8_ofzIpJEonBPyULY,3109\r\nlxml/includes/libxml/catalog.h,sha256=ugBmcsBjZefAsAE8vs7OwMZonYVBzDj2rNyWVF4YK3I,4905\r\nlxml/includes/libxml/chvalid.h,sha256=H9_NIeLyDhdKDZg9euK_5b5QmeXWWNq4KTENFkcUUtA,5159\r\nlxml/includes/libxml/debugXML.h,sha256=eatflryQfcmuAgmyz_f3JoSpTmvDA26mrcUjd7vwSLY,5152\r\nlxml/includes/libxml/dict.h,sha256=o36P53gHvahFTU4K-RMkeqy5oJzXza_akJ069CmdorE,1955\r\nlxml/includes/libxml/encoding.h,sha256=bzmHUnU-pUjQIqMOqrEml5KapMOmZ8MeoNO5VIro0ck,8507\r\nlxml/includes/libxml/entities.h,sha256=uJ8I3voqfwMEw8MQJveLtS0mOanjzzREreKrSs8_018,4712\r\nlxml/includes/libxml/globals.h,sha256=bjkOtarZpUFFa5QYE5gN3t0RtRIsXHQQJg8ulxQHAKQ,14670\r\nlxml/includes/libxml/hash.h,sha256=81Gch4yaE4oXlKhM-jwPpVkf7zig2kH5b-wdrCkINpY,6603\r\nlxml/includes/libxml/list.h,sha256=b7h42wGsDQTVWXsRutjNe1n00_zXfDIXr-iBOHvSThg,3348\r\nlxml/includes/libxml/nanoftp.h,sha256=HOW15FcLYD7A7hvdcqz3JxGYVBraqjiTodtx-pBqQ5g,3758\r\nlxml/includes/libxml/nanohttp.h,sha256=LLgN_JcupVO24_Oki895yVKsJzFe5mcF2vH8Ekymq_I,2005\r\nlxml/includes/libxml/parser.h,sha256=fAvfRpely07ySdKS8MJRCwcyOoZpM-h5y6tPhXCZaNs,39717\r\nlxml/includes/libxml/parserInternals.h,sha256=2c5f6anmOJaYlqJhAky-mtn6CNBFFy1COvPXHtDkb2I,17418\r\nlxml/includes/libxml/relaxng.h,sha256=D1ufdqizDSPx8wOL_ZsjuIl--nK52cWMiZwIdEIbhSc,5996\r\nlxml/includes/libxml/schemasInternals.h,sha256=I1VSv5fO7wDHdgSoR2xrcUSGL1UEeOgabpnZT5wXayo,26243\r\nlxml/includes/libxml/schematron.h,sha256=lNOe9oFbhBqk1GVv4nJ4eZR3tieJVuw-gqbrmPtG3K4,4371\r\nlxml/includes/libxml/threads.h,sha256=4OopyFEmDIicmsj7cYzzlpEswbXSiHHM5LJakZ9Vw5Y,1958\r\nlxml/includes/libxml/tree.h,sha256=Vbh95HbDdJ8MmJyt-y2fDUMBl8unhC2xau7Rw3Ypkxk,38107\r\nlxml/includes/libxml/uri.h,sha256=nGU1MVe2zr7e3jReDYKCMPQkTkQRN-iNlLewkpP9cLo,2664\r\nlxml/includes/libxml/valid.h,sha256=__oCp9iK1nJc7s2iRZqtz8iHu6--9-XI_MWLXIBq_C0,13622\r\nlxml/includes/libxml/xinclude.h,sha256=iL_sqfaWIhThheHWBbEUQt59_sd-jnExhxaYeXxInqk,2967\r\nlxml/includes/libxml/xlink.h,sha256=hV-cvCxIJ_F1VdWcMYZ3w2jkGwWyLc9SZ8PdnUZxYNs,5040\r\nlxml/includes/libxml/xmlIO.h,sha256=-5MYRiCCuO81Y23ldZJU7Uh_my3U7yyg9rMfahcVans,10611\r\nlxml/includes/libxml/xmlautomata.h,sha256=rIJxLWBGZrfkFYDXdJZBoAhygp93vFBO_WI6nUCxBN4,3956\r\nlxml/includes/libxml/xmlerror.h,sha256=I7xskOqrTkctmlL76j2-_VMmMB_RPcXTglE1jHRXa5g,36808\r\nlxml/includes/libxml/xmlexports.h,sha256=STps2gtHl-dNVoWDBdsg1liYi88JYJYTjBp30KEeOYc,3933\r\nlxml/includes/libxml/xmlmemory.h,sha256=Z6y0IQCIKXfVnYOPiGoFwc5Hq4rUdZ5AJwKJeav0TNw,5945\r\nlxml/includes/libxml/xmlmodule.h,sha256=c5vXusZj46FsM9UPHGt8g9gdPhTVOH1rJEFf2pJ8K4c,1170\r\nlxml/includes/libxml/xmlreader.h,sha256=mAAVz-ZYrOt56fzLds-ytusW7UqEGS5L9BGi5kzpTv4,12607\r\nlxml/includes/libxml/xmlregexp.h,sha256=UHbZDD3CZVn4NDiaHB64Aa-90pxzSsconMqneCp1ZDc,5458\r\nlxml/includes/libxml/xmlsave.h,sha256=8QlBKC6tuZ7lFQr_KJDTAxp4gmXtZWg-KGmLMkD7TCw,2337\r\nlxml/includes/libxml/xmlschemas.h,sha256=mvK9-OmM-FxfAPSpfkte4R-EWdkwvY6WFX6JmUeF3_U,7069\r\nlxml/includes/libxml/xmlschemastypes.h,sha256=alMLzZOds02Ksbv7K86owr0_IXjFPQ2Kk99rGhniZPE,4841\r\nlxml/includes/libxml/xmlstring.h,sha256=P_40FyEE40e_8h8Tlk9TSNze1zrJygFgsxkFydPnnPs,5511\r\nlxml/includes/libxml/xmlunicode.h,sha256=TpTZ8Bf313Rs9m-ww1cBCHwvW-uHj9tQ125iQfaDorU,9993\r\nlxml/includes/libxml/xmlversion.h,sha256=QfvdigZn28-v7eoo5cout_QssMYibltZVz-FiWsMp34,8092\r\nlxml/includes/libxml/xmlwriter.h,sha256=ddjdRh9PBH-FynmNgjkRg1JFBRzlZBPyyh7FX3JX1lY,21265\r\nlxml/includes/libxml/xpath.h,sha256=zo45KZIebdrOgK-Zu7kWQMm9yAs4pt_5b5QGnDApMc0,16398\r\nlxml/includes/libxml/xpathInternals.h,sha256=EWeEX1yCVHsUUeDxxOe-4jO25LBEDoM564CoPc1YNGU,19353\r\nlxml/includes/libxml/xpointer.h,sha256=6MQwhGyIy3PKp9yWaXRg0LAdL-bR2jjFNYUxUSkc6lk,3359\r\nlxml/includes/libxslt/attributes.h,sha256=vwJCNwOWLxNtoTh4Zqf9jhlxOjYJ-2e6KbaDEM7sEHY,930\r\nlxml/includes/libxslt/documents.h,sha256=kBihgH5pqRvFalhm_fOFHtJTFhTpBcm681yT5dxgwfw,2704\r\nlxml/includes/libxslt/extensions.h,sha256=bTyuv5_mj-RdPFhpT89LIM-iaMJ5dZtJFJkq0sbfaxE,6903\r\nlxml/includes/libxslt/extra.h,sha256=6X3Wu3NdPtrlqz-Koo7dB-rccnnszi6j3zg599gTByg,1640\r\nlxml/includes/libxslt/functions.h,sha256=fc4CZj-9KeBHzO9-WWU_bNqmaEZAz3n7NNwClIBXk14,1972\r\nlxml/includes/libxslt/imports.h,sha256=18kIjoGqdFXR63Ce3ZtzxsTiYV3XGKpchYakMUPDuUI,1840\r\nlxml/includes/libxslt/keys.h,sha256=16v25VEluS7jYhgg6gYFwVxgGMn-1ctnlhhWWT4RcBY,1155\r\nlxml/includes/libxslt/namespaces.h,sha256=VofSn2Kkn-a5JyRKCmY3jPp7amQy3n09vzy0KUQt4q0,1666\r\nlxml/includes/libxslt/numbersInternals.h,sha256=Eg5gYZ5p3h0_e5wyI61S-0E6_ArVJzv0yr63j6BU2fc,2019\r\nlxml/includes/libxslt/pattern.h,sha256=guN--02T1BimNNZxySofWFs91rRwIfqVOkbnr5vkAuY,1998\r\nlxml/includes/libxslt/preproc.h,sha256=-19NH8t3q1NGsG6OsnctVHkk43tfNgbp1ei5glt_jNU,892\r\nlxml/includes/libxslt/security.h,sha256=fUD1cy_WxFCTvTNAF0WOQIU4p5CNWn1LHFyZJd-Fx5U,2652\r\nlxml/includes/libxslt/templates.h,sha256=bnt6Jqui6KU5pNUdMNPbQZkZ5d-VTWqC0TMGkOlVoIo,2268\r\nlxml/includes/libxslt/transform.h,sha256=ICT7meUV0OTAx27WaKVrKj-aUmR9LSpTNaOAJd2UStg,6311\r\nlxml/includes/libxslt/variables.h,sha256=NmypiBFTCM7u-2kUg_yZxFwq2oTEG1EFjYG4zbfGs44,3173\r\nlxml/includes/libxslt/xslt.h,sha256=wmFx2Q31Pd8Iq2phAQpY9J3QQatb8lWg3gABtqKFgEw,1964\r\nlxml/includes/libxslt/xsltInternals.h,sha256=a0BMdTHXL-s5LOhP9TztNqNA02GbWsueTkp4Tbkc83Q,57355\r\nlxml/includes/libxslt/xsltconfig.h,sha256=EApe02TD-3znFWSuzYX607MwPAGeSyl0Qu6M1Aqnq6s,3529\r\nlxml/includes/libxslt/xsltexports.h,sha256=0fj02WOCn4uL36ZuZEkGEb5UW1_tt-QC-ih12xvgscI,3439\r\nlxml/includes/libxslt/xsltlocale.h,sha256=yOkJGQNiD39fwBYus1TpgSmb1mEJstXcHx3O_Q03d_w,1549\r\nlxml/includes/libxslt/xsltutils.h,sha256=D2Gqop4cieJiOsQtLWTJezGea9kONcUFxeykLjGRI_E,8297\r\nlxml/includes/lxml-version.h,sha256=hnqux2tJVMv46Pk5v0BaConsfK5bKtukOQrdLavlUM0,71\r\nlxml/includes/relaxng.pxd,sha256=12yapjqDZLF_HTlcuSXSoQpPGK1NU7fj7gzS1EF8kZw,2669\r\nlxml/includes/schematron.pxd,sha256=5_PUpLHTzzYZ_d-8d2OjKLdwtLIdOm7C20HFUAX8hD4,1640\r\nlxml/includes/tree.pxd,sha256=dtnXNbEfxV3-5kOwWYkYoCE8HT5zvFVNdKFaIBuNXBc,20091\r\nlxml/includes/uri.pxd,sha256=5wPtpGU1JtdmpZMTzR8EswazihP3dxkns6Fgo9NWOt8,139\r\nlxml/includes/xinclude.pxd,sha256=onXD71LVdAbXjUj82_SDtSixNsNh8xbu6Nd9x0V3bmM,852\r\nlxml/includes/xmlerror.pxd,sha256=rV-nzG4TwgnNjuw7w68abmGDk_c8LGm4Y8f5oPw8OVc,57935\r\nlxml/includes/xmlparser.pxd,sha256=v-G3Y11eR4C1e2ImWLmGZpuTA90Y9N_uy-8H0-zwJY8,10852\r\nlxml/includes/xmlschema.pxd,sha256=yYQFrIKAQ_feenENV24X2AZyBIYGBltRDm9qB7CYMww,1696\r\nlxml/includes/xpath.pxd,sha256=tKYAcwpbSRq8qrsZ2ISVYvEaLnCV9GadNC5o_f8Ua_g,5794\r\nlxml/includes/xslt.pxd,sha256=qBU-0dLhIMQFv58I4q1XkBq9QJpJzKEAK9qBFPXBj_g,8341\r\nlxml/isoschematron/__init__.py,sha256=NUoI0bb87VB2XePzFcMtwUasrUAQACfb3Z9dPaMz6Fs,12399\r\nlxml/isoschematron/__pycache__/__init__.cpython-36.pyc,,\r\nlxml/isoschematron/resources/rng/iso-schematron.rng,sha256=VsWxPyi3iViJDDbjJJw0wWkEHkLrz9zoCA8zJLor9N4,18337\r\nlxml/isoschematron/resources/xsl/RNG2Schtrn.xsl,sha256=ObebsB8Wt-d3uIA_U5NU85TpnQ3PxPX38TdOAqosMac,3172\r\nlxml/isoschematron/resources/xsl/XSD2Schtrn.xsl,sha256=QweRrIIM-zFcgg98GXA2CaWfIbgVE0XKEeYSfvv67A0,4563\r\nlxml/isoschematron/resources/xsl/iso-schematron-xslt1/iso_abstract_expand.xsl,sha256=xSZ_Ekq_I-62ZpiE5AqYYHwFW_qh855zt9V4_s7rbkY,11703\r\nlxml/isoschematron/resources/xsl/iso-schematron-xslt1/iso_dsdl_include.xsl,sha256=x42QJ-dxQ1waPzydsCoQnp2Xj15y53nW43O7BuoDRHk,39957\r\nlxml/isoschematron/resources/xsl/iso-schematron-xslt1/iso_schematron_message.xsl,sha256=Tr9BnO6pzjVWwhqJfm10UlvAy95EgfSCz2iMlrVGT6Q,2015\r\nlxml/isoschematron/resources/xsl/iso-schematron-xslt1/iso_schematron_skeleton_for_xslt1.xsl,sha256=ue8q_88X4e_jsJizo31GRNBxNhdxkEE9fY20oq0Iqwk,71764\r\nlxml/isoschematron/resources/xsl/iso-schematron-xslt1/iso_svrl_for_xslt1.xsl,sha256=BBAdsVSi5zAzeGepuN6gS1saQINDqITXKplmmj4dTWg,20382\r\nlxml/isoschematron/resources/xsl/iso-schematron-xslt1/readme.txt,sha256=OGLiFswuLJEW5EPYKOeoauuCJFEtVa6jyzBE1OcJI98,3310\r\nlxml/lxml.etree.h,sha256=ovyaRkrRJRkTtHo0YoPvopYLhrcOVUvYhuio6iTmF58,8555\r\nlxml/lxml.etree_api.h,sha256=u2Wcjg8drM-DKurVac7acEb4PDblJex3p9zKdjf-i48,17472\r\nlxml/objectify.cpython-36m-x86_64-linux-gnu.so,sha256=CqBFuXPiUiMxyjPyHzP_gi8q8OkkPSiid0TrQQ9HS_E,3767730\r\nlxml/pyclasslookup.py,sha256=gLD1HM2HtITYYiGzjEOewSwbB7XkVx_NZv_quCt79Oc,92\r\nlxml/sax.cpython-36m-x86_64-linux-gnu.so,sha256=D5odEL_UHMhMWGGTh0twQ4LQEIEZGbor7Xp22g5O7lo,251290\r\nlxml/sax.py,sha256=xwHH7zbL6Vzp26fm50o2Jw1OkdualIcN4QoccYWRbqM,9406\r\nlxml/usedoctest.py,sha256=qRgZKQVcAZcl-zN0AIXVJnOsETUXz2nPXkxuzs1lGgk,230\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml-4.4.1.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.31.1)\nRoot-Is-Purelib: false\nTag: cp36-cp36m-manylinux1_x86_64\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/lxml-4.4.1.dist-info/top_level.txt",
    "content": "lxml\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/parsel/__init__.py",
    "content": "\"\"\"\nParsel lets you extract text from XML/HTML documents using XPath\nor CSS selectors\n\"\"\"\n\n__author__ = 'Scrapy project'\n__email__ = 'info@scrapy.org'\n__version__ = '1.5.2'\n\nfrom parsel.selector import Selector, SelectorList  # NOQA\nfrom parsel.csstranslator import css2xpath  # NOQA\nfrom parsel import xpathfuncs # NOQA\n\nxpathfuncs.setup()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/parsel/csstranslator.py",
    "content": "import six\n\nif six.PY2:\n    from functools32 import lru_cache\nelse:\n    from functools import lru_cache\n\nfrom cssselect import GenericTranslator as OriginalGenericTranslator\nfrom cssselect import HTMLTranslator as OriginalHTMLTranslator\nfrom cssselect.xpath import XPathExpr as OriginalXPathExpr\nfrom cssselect.xpath import _unicode_safe_getattr, ExpressionError\nfrom cssselect.parser import parse, FunctionalPseudoElement\n\n\nclass XPathExpr(OriginalXPathExpr):\n\n    textnode = False\n    attribute = None\n\n    @classmethod\n    def from_xpath(cls, xpath, textnode=False, attribute=None):\n        x = cls(path=xpath.path, element=xpath.element, condition=xpath.condition)\n        x.textnode = textnode\n        x.attribute = attribute\n        return x\n\n    def __str__(self):\n        path = super(XPathExpr, self).__str__()\n        if self.textnode:\n            if path == '*':\n                path = 'text()'\n            elif path.endswith('::*/*'):\n                path = path[:-3] + 'text()'\n            else:\n                path += '/text()'\n\n        if self.attribute is not None:\n            if path.endswith('::*/*'):\n                path = path[:-2]\n            path += '/@%s' % self.attribute\n\n        return path\n\n    def join(self, combiner, other):\n        super(XPathExpr, self).join(combiner, other)\n        self.textnode = other.textnode\n        self.attribute = other.attribute\n        return self\n\n\nclass TranslatorMixin(object):\n    \"\"\"This mixin adds support to CSS pseudo elements via dynamic dispatch.\n\n    Currently supported pseudo-elements are ``::text`` and ``::attr(ATTR_NAME)``.\n    \"\"\"\n\n    def xpath_element(self, selector):\n        xpath = super(TranslatorMixin, self).xpath_element(selector)\n        return XPathExpr.from_xpath(xpath)\n\n    def xpath_pseudo_element(self, xpath, pseudo_element):\n        \"\"\"\n        Dispatch method that transforms XPath to support pseudo-element\n        \"\"\"\n        if isinstance(pseudo_element, FunctionalPseudoElement):\n            method = 'xpath_%s_functional_pseudo_element' % (\n                pseudo_element.name.replace('-', '_'))\n            method = _unicode_safe_getattr(self, method, None)\n            if not method:\n                raise ExpressionError(\n                    \"The functional pseudo-element ::%s() is unknown\"\n                    % pseudo_element.name)\n            xpath = method(xpath, pseudo_element)\n        else:\n            method = 'xpath_%s_simple_pseudo_element' % (\n                pseudo_element.replace('-', '_'))\n            method = _unicode_safe_getattr(self, method, None)\n            if not method:\n                raise ExpressionError(\n                    \"The pseudo-element ::%s is unknown\"\n                    % pseudo_element)\n            xpath = method(xpath)\n        return xpath\n\n    def xpath_attr_functional_pseudo_element(self, xpath, function):\n        \"\"\"Support selecting attribute values using ::attr() pseudo-element\n        \"\"\"\n        if function.argument_types() not in (['STRING'], ['IDENT']):\n            raise ExpressionError(\n                \"Expected a single string or ident for ::attr(), got %r\"\n                % function.arguments)\n        return XPathExpr.from_xpath(xpath,\n                                    attribute=function.arguments[0].value)\n\n    def xpath_text_simple_pseudo_element(self, xpath):\n        \"\"\"Support selecting text nodes using ::text pseudo-element\"\"\"\n        return XPathExpr.from_xpath(xpath, textnode=True)\n\n\nclass GenericTranslator(TranslatorMixin, OriginalGenericTranslator):\n    @lru_cache(maxsize=256)\n    def css_to_xpath(self, css, prefix='descendant-or-self::'):\n        return super(GenericTranslator, self).css_to_xpath(css, prefix)\n\n\nclass HTMLTranslator(TranslatorMixin, OriginalHTMLTranslator):\n    @lru_cache(maxsize=256)\n    def css_to_xpath(self, css, prefix='descendant-or-self::'):\n        return super(HTMLTranslator, self).css_to_xpath(css, prefix)\n\n\n_translator = HTMLTranslator()\n\n\ndef css2xpath(query):\n    \"Return translated XPath version of a given CSS query\"\n    return _translator.css_to_xpath(query)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/parsel/selector.py",
    "content": "\"\"\"\nXPath selectors based on lxml\n\"\"\"\n\nimport sys\n\nimport six\nfrom lxml import etree, html\n\nfrom .utils import flatten, iflatten, extract_regex, shorten\nfrom .csstranslator import HTMLTranslator, GenericTranslator\n\n\nclass SafeXMLParser(etree.XMLParser):\n    def __init__(self, *args, **kwargs):\n        kwargs.setdefault('resolve_entities', False)\n        super(SafeXMLParser, self).__init__(*args, **kwargs)\n\n_ctgroup = {\n    'html': {'_parser': html.HTMLParser,\n             '_csstranslator': HTMLTranslator(),\n             '_tostring_method': 'html'},\n    'xml': {'_parser': SafeXMLParser,\n            '_csstranslator': GenericTranslator(),\n            '_tostring_method': 'xml'},\n}\n\n\ndef _st(st):\n    if st is None:\n        return 'html'\n    elif st in _ctgroup:\n        return st\n    else:\n        raise ValueError('Invalid type: %s' % st)\n\n\ndef create_root_node(text, parser_cls, base_url=None):\n    \"\"\"Create root node for text using given parser class.\n    \"\"\"\n    body = text.strip().replace('\\x00', '').encode('utf8') or b'<html/>'\n    parser = parser_cls(recover=True, encoding='utf8')\n    root = etree.fromstring(body, parser=parser, base_url=base_url)\n    if root is None:\n        root = etree.fromstring(b'<html/>', parser=parser, base_url=base_url)\n    return root\n\n\nclass SelectorList(list):\n    \"\"\"\n    The :class:`SelectorList` class is a subclass of the builtin ``list``\n    class, which provides a few additional methods.\n    \"\"\"\n\n    # __getslice__ is deprecated but `list` builtin implements it only in Py2\n    def __getslice__(self, i, j):\n        o = super(SelectorList, self).__getslice__(i, j)\n        return self.__class__(o)\n\n    def __getitem__(self, pos):\n        o = super(SelectorList, self).__getitem__(pos)\n        return self.__class__(o) if isinstance(pos, slice) else o\n\n    def __getstate__(self):\n        raise TypeError(\"can't pickle SelectorList objects\")\n\n    def xpath(self, xpath, namespaces=None, **kwargs):\n        \"\"\"\n        Call the ``.xpath()`` method for each element in this list and return\n        their results flattened as another :class:`SelectorList`.\n\n        ``query`` is the same argument as the one in :meth:`Selector.xpath`\n\n        ``namespaces`` is an optional ``prefix: namespace-uri`` mapping (dict)\n        for additional prefixes to those registered with ``register_namespace(prefix, uri)``.\n        Contrary to ``register_namespace()``, these prefixes are not\n        saved for future calls.\n\n        Any additional named arguments can be used to pass values for XPath\n        variables in the XPath expression, e.g.::\n\n            selector.xpath('//a[href=$url]', url=\"http://www.example.com\")\n        \"\"\"\n        return self.__class__(flatten([x.xpath(xpath, namespaces=namespaces, **kwargs) for x in self]))\n\n    def css(self, query):\n        \"\"\"\n        Call the ``.css()`` method for each element in this list and return\n        their results flattened as another :class:`SelectorList`.\n\n        ``query`` is the same argument as the one in :meth:`Selector.css`\n        \"\"\"\n        return self.__class__(flatten([x.css(query) for x in self]))\n\n    def re(self, regex, replace_entities=True):\n        \"\"\"\n        Call the ``.re()`` method for each element in this list and return\n        their results flattened, as a list of unicode strings.\n\n        By default, character entity references are replaced by their\n        corresponding character (except for ``&amp;`` and ``&lt;``.\n        Passing ``replace_entities`` as ``False`` switches off these\n        replacements.\n        \"\"\"\n        return flatten([x.re(regex, replace_entities=replace_entities) for x in self])\n\n    def re_first(self, regex, default=None, replace_entities=True):\n        \"\"\"\n        Call the ``.re()`` method for the first element in this list and\n        return the result in an unicode string. If the list is empty or the\n        regex doesn't match anything, return the default value (``None`` if\n        the argument is not provided).\n\n        By default, character entity references are replaced by their\n        corresponding character (except for ``&amp;`` and ``&lt;``.\n        Passing ``replace_entities`` as ``False`` switches off these\n        replacements.\n        \"\"\"\n        for el in iflatten(x.re(regex, replace_entities=replace_entities) for x in self):\n            return el\n        else:\n            return default\n\n    def getall(self):\n        \"\"\"\n        Call the ``.get()`` method for each element is this list and return\n        their results flattened, as a list of unicode strings.\n        \"\"\"\n        return [x.get() for x in self]\n    extract = getall\n\n    def get(self, default=None):\n        \"\"\"\n        Return the result of ``.get()`` for the first element in this list.\n        If the list is empty, return the default value.\n        \"\"\"\n        for x in self:\n            return x.get()\n        else:\n            return default\n    extract_first = get\n\n    @property\n    def attrib(self):\n        \"\"\"Return the attributes dictionary for the first element.\n        If the list is empty, return an empty dict.\n        \"\"\"\n        for x in self:\n            return x.attrib\n        else:\n            return {}\n\n\nclass Selector(object):\n    \"\"\"\n    :class:`Selector` allows you to select parts of an XML or HTML text using CSS\n    or XPath expressions and extract data from it.\n\n    ``text`` is a ``unicode`` object in Python 2 or a ``str`` object in Python 3\n\n    ``type`` defines the selector type, it can be ``\"html\"``, ``\"xml\"`` or ``None`` (default).\n    If ``type`` is ``None``, the selector defaults to ``\"html\"``.\n    \"\"\"\n\n    __slots__ = ['text', 'namespaces', 'type', '_expr', 'root',\n                 '__weakref__', '_parser', '_csstranslator', '_tostring_method']\n\n    _default_type = None\n    _default_namespaces = {\n        \"re\": \"http://exslt.org/regular-expressions\",\n\n        # supported in libxslt:\n        # set:difference\n        # set:has-same-node\n        # set:intersection\n        # set:leading\n        # set:trailing\n        \"set\": \"http://exslt.org/sets\"\n    }\n    _lxml_smart_strings = False\n    selectorlist_cls = SelectorList\n\n    def __init__(self, text=None, type=None, namespaces=None, root=None,\n                 base_url=None, _expr=None):\n        self.type = st = _st(type or self._default_type)\n        self._parser = _ctgroup[st]['_parser']\n        self._csstranslator = _ctgroup[st]['_csstranslator']\n        self._tostring_method = _ctgroup[st]['_tostring_method']\n\n        if text is not None:\n            if not isinstance(text, six.text_type):\n                raise TypeError(\"text argument should be of type %s\" % six.text_type)\n            root = self._get_root(text, base_url)\n        elif root is None:\n            raise ValueError(\"Selector needs either text or root argument\")\n\n        self.namespaces = dict(self._default_namespaces)\n        if namespaces is not None:\n            self.namespaces.update(namespaces)\n        self.root = root\n        self._expr = _expr\n\n    def __getstate__(self):\n        raise TypeError(\"can't pickle Selector objects\")\n\n    def _get_root(self, text, base_url=None):\n        return create_root_node(text, self._parser, base_url=base_url)\n\n    def xpath(self, query, namespaces=None, **kwargs):\n        \"\"\"\n        Find nodes matching the xpath ``query`` and return the result as a\n        :class:`SelectorList` instance with all elements flattened. List\n        elements implement :class:`Selector` interface too.\n\n        ``query`` is a string containing the XPATH query to apply.\n\n        ``namespaces`` is an optional ``prefix: namespace-uri`` mapping (dict)\n        for additional prefixes to those registered with ``register_namespace(prefix, uri)``.\n        Contrary to ``register_namespace()``, these prefixes are not\n        saved for future calls.\n\n        Any additional named arguments can be used to pass values for XPath\n        variables in the XPath expression, e.g.::\n\n            selector.xpath('//a[href=$url]', url=\"http://www.example.com\")\n        \"\"\"\n        try:\n            xpathev = self.root.xpath\n        except AttributeError:\n            return self.selectorlist_cls([])\n\n        nsp = dict(self.namespaces)\n        if namespaces is not None:\n            nsp.update(namespaces)\n        try:\n            result = xpathev(query, namespaces=nsp,\n                             smart_strings=self._lxml_smart_strings,\n                             **kwargs)\n        except etree.XPathError as exc:\n            msg = u\"XPath error: %s in %s\" % (exc, query)\n            msg = msg if six.PY3 else msg.encode('unicode_escape')\n            six.reraise(ValueError, ValueError(msg), sys.exc_info()[2])\n\n        if type(result) is not list:\n            result = [result]\n\n        result = [self.__class__(root=x, _expr=query,\n                                 namespaces=self.namespaces,\n                                 type=self.type)\n                  for x in result]\n        return self.selectorlist_cls(result)\n\n    def css(self, query):\n        \"\"\"\n        Apply the given CSS selector and return a :class:`SelectorList` instance.\n\n        ``query`` is a string containing the CSS selector to apply.\n\n        In the background, CSS queries are translated into XPath queries using\n        `cssselect`_ library and run ``.xpath()`` method.\n        \n        .. _cssselect: https://pypi.python.org/pypi/cssselect/\n        \"\"\"\n        return self.xpath(self._css2xpath(query))\n\n    def _css2xpath(self, query):\n        return self._csstranslator.css_to_xpath(query)\n\n    def re(self, regex, replace_entities=True):\n        \"\"\"\n        Apply the given regex and return a list of unicode strings with the\n        matches.\n\n        ``regex`` can be either a compiled regular expression or a string which\n        will be compiled to a regular expression using ``re.compile(regex)``.\n\n        By default, character entity references are replaced by their\n        corresponding character (except for ``&amp;`` and ``&lt;``).\n        Passing ``replace_entities`` as ``False`` switches off these\n        replacements.\n        \"\"\"\n        return extract_regex(regex, self.get(), replace_entities=replace_entities)\n\n    def re_first(self, regex, default=None, replace_entities=True):\n        \"\"\"\n        Apply the given regex and return the first unicode string which\n        matches. If there is no match, return the default value (``None`` if\n        the argument is not provided).\n\n        By default, character entity references are replaced by their\n        corresponding character (except for ``&amp;`` and ``&lt;``).\n        Passing ``replace_entities`` as ``False`` switches off these\n        replacements.\n        \"\"\"\n        return next(iflatten(self.re(regex, replace_entities=replace_entities)), default)\n\n    def get(self):\n        \"\"\"\n        Serialize and return the matched nodes in a single unicode string.\n        Percent encoded content is unquoted.\n        \"\"\"\n        try:\n            return etree.tostring(self.root,\n                                  method=self._tostring_method,\n                                  encoding='unicode',\n                                  with_tail=False)\n        except (AttributeError, TypeError):\n            if self.root is True:\n                return u'1'\n            elif self.root is False:\n                return u'0'\n            else:\n                return six.text_type(self.root)\n    extract = get\n\n    def getall(self):\n        \"\"\"\n        Serialize and return the matched node in a 1-element list of unicode strings.\n        \"\"\"\n        return [self.get()]\n\n    def register_namespace(self, prefix, uri):\n        \"\"\"\n        Register the given namespace to be used in this :class:`Selector`.\n        Without registering namespaces you can't select or extract data from\n        non-standard namespaces. See :ref:`selector-examples-xml`.\n        \"\"\"\n        self.namespaces[prefix] = uri\n\n    def remove_namespaces(self):\n        \"\"\"\n        Remove all namespaces, allowing to traverse the document using\n        namespace-less xpaths. See :ref:`removing-namespaces`.\n        \"\"\"\n        for el in self.root.iter('*'):\n            if el.tag.startswith('{'):\n                el.tag = el.tag.split('}', 1)[1]\n            # loop on element attributes also\n            for an in el.attrib.keys():\n                if an.startswith('{'):\n                    el.attrib[an.split('}', 1)[1]] = el.attrib.pop(an)\n        # remove namespace declarations\n        etree.cleanup_namespaces(self.root)\n\n    @property\n    def attrib(self):\n        \"\"\"Return the attributes dictionary for underlying element.\n        \"\"\"\n        return dict(self.root.attrib)\n\n    def __bool__(self):\n        \"\"\"\n        Return ``True`` if there is any real content selected or ``False``\n        otherwise.  In other words, the boolean value of a :class:`Selector` is\n        given by the contents it selects.\n        \"\"\"\n        return bool(self.get())\n    __nonzero__ = __bool__\n\n    def __str__(self):\n        data = repr(shorten(self.get(), width=40))\n        return \"<%s xpath=%r data=%s>\" % (type(self).__name__, self._expr, data)\n    __repr__ = __str__\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/parsel/utils.py",
    "content": "import re\nimport six\nfrom w3lib.html import replace_entities as w3lib_replace_entities\n\n\ndef flatten(x):\n    \"\"\"flatten(sequence) -> list\n    Returns a single, flat list which contains all elements retrieved\n    from the sequence and all recursively contained sub-sequences\n    (iterables).\n    Examples:\n    >>> [1, 2, [3,4], (5,6)]\n    [1, 2, [3, 4], (5, 6)]\n    >>> flatten([[[1,2,3], (42,None)], [4,5], [6], 7, (8,9,10)])\n    [1, 2, 3, 42, None, 4, 5, 6, 7, 8, 9, 10]\n    >>> flatten([\"foo\", \"bar\"])\n    ['foo', 'bar']\n    >>> flatten([\"foo\", [\"baz\", 42], \"bar\"])\n    ['foo', 'baz', 42, 'bar']\n    \"\"\"\n    return list(iflatten(x))\n\n\ndef iflatten(x):\n    \"\"\"iflatten(sequence) -> iterator\n    Similar to ``.flatten()``, but returns iterator instead\"\"\"\n    for el in x:\n        if _is_listlike(el):\n            for el_ in flatten(el):\n                yield el_\n        else:\n            yield el\n\n\ndef _is_listlike(x):\n    \"\"\"\n    >>> _is_listlike(\"foo\")\n    False\n    >>> _is_listlike(5)\n    False\n    >>> _is_listlike(b\"foo\")\n    False\n    >>> _is_listlike([b\"foo\"])\n    True\n    >>> _is_listlike((b\"foo\",))\n    True\n    >>> _is_listlike({})\n    True\n    >>> _is_listlike(set())\n    True\n    >>> _is_listlike((x for x in range(3)))\n    True\n    >>> _is_listlike(six.moves.xrange(5))\n    True\n    \"\"\"\n    return hasattr(x, \"__iter__\") and not isinstance(x, (six.text_type, bytes))\n\n\ndef extract_regex(regex, text, replace_entities=True):\n    \"\"\"Extract a list of unicode strings from the given text/encoding using the following policies:\n    * if the regex contains a named group called \"extract\" that will be returned\n    * if the regex contains multiple numbered groups, all those will be returned (flattened)\n    * if the regex doesn't contain any group the entire regex matching is returned\n    \"\"\"\n    if isinstance(regex, six.string_types):\n        regex = re.compile(regex, re.UNICODE)\n\n    if 'extract' in regex.groupindex:\n        # named group\n        try:\n            extracted = regex.search(text).group('extract')\n        except AttributeError:\n            strings = []\n        else:\n            strings = [extracted] if extracted is not None else []\n    else:\n        # full regex or numbered groups\n        strings = regex.findall(text)\n\n    strings = flatten(strings)\n    if not replace_entities:\n        return strings\n    return [w3lib_replace_entities(s, keep=['lt', 'amp']) for s in strings]\n\n\ndef shorten(text, width, suffix='...'):\n    \"\"\"Truncate the given text to fit in the given width.\"\"\"\n    if len(text) <= width:\n        return text\n    if width > len(suffix):\n        return text[:width-len(suffix)] + suffix\n    if width >= 0:\n        return suffix[len(suffix)-width:]\n    raise ValueError('width must be equal or greater than 0')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/parsel/xpathfuncs.py",
    "content": "import re\nfrom lxml import etree\n\nfrom six import string_types\n\nfrom w3lib.html import HTML5_WHITESPACE\n\nregex = '[{}]+'.format(HTML5_WHITESPACE)\nreplace_html5_whitespaces = re.compile(regex).sub\n\n\ndef set_xpathfunc(fname, func):\n    \"\"\"Register a custom extension function to use in XPath expressions.\n\n    The function ``func`` registered under ``fname`` identifier will be called\n    for every matching node, being passed a ``context`` parameter as well as\n    any parameters passed from the corresponding XPath expression.\n\n    If ``func`` is ``None``, the extension function will be removed.\n\n    See more `in lxml documentation`_.\n\n    .. _`in lxml documentation`: http://lxml.de/extensions.html#xpath-extension-functions\n\n    \"\"\"\n    ns_fns = etree.FunctionNamespace(None)\n    if func is not None:\n        ns_fns[fname] = func\n    else:\n        del ns_fns[fname]\n\n\ndef setup():\n    set_xpathfunc('has-class', has_class)\n\n\ndef has_class(context, *classes):\n    \"\"\"has-class function.\n\n    Return True if all ``classes`` are present in element's class attr.\n\n    \"\"\"\n    if not context.eval_context.get('args_checked'):\n        if not classes:\n            raise ValueError(\n                'XPath error: has-class must have at least 1 argument')\n        for c in classes:\n            if not isinstance(c, string_types):\n                raise ValueError(\n                    'XPath error: has-class arguments must be strings')\n        context.eval_context['args_checked'] = True\n\n    node_cls = context.context_node.get('class')\n    if node_cls is None:\n        return False\n    node_cls = ' ' + node_cls + ' '\n    node_cls = replace_html5_whitespaces(' ', node_cls)\n    for cls in classes:\n        if ' ' + cls + ' ' not in node_cls:\n            return False\n    return True\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/parsel-1.5.2.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/parsel-1.5.2.dist-info/LICENSE",
    "content": "Copyright (c) Scrapy developers.\nAll rights reserved.\n\nRedistribution and use in source and binary forms, with or without modification,\nare permitted provided that the following conditions are met:\n\n    1. Redistributions of source code must retain the above copyright notice, \n       this list of conditions and the following disclaimer.\n    \n    2. Redistributions in binary form must reproduce the above copyright \n       notice, this list of conditions and the following disclaimer in the\n       documentation and/or other materials provided with the distribution.\n\n    3. Neither the name of Scrapy nor the names of its contributors may be used\n       to endorse or promote products derived from this software without\n       specific prior written permission.\n\nTHIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\" AND\nANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\nWARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\nDISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR\nANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\nLOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON\nANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\nSOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/parsel-1.5.2.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: parsel\nVersion: 1.5.2\nSummary: Parsel is a library to extract data from HTML and XML using XPath and CSS selectors\nHome-page: https://github.com/scrapy/parsel\nAuthor: Scrapy project\nAuthor-email: info@scrapy.org\nLicense: BSD\nKeywords: parsel\nPlatform: UNKNOWN\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: BSD License\nClassifier: Natural Language :: English\nClassifier: Topic :: Text Processing :: Markup\nClassifier: Topic :: Text Processing :: Markup :: HTML\nClassifier: Topic :: Text Processing :: Markup :: XML\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nClassifier: Programming Language :: Python :: Implementation :: CPython\nClassifier: Programming Language :: Python :: Implementation :: PyPy\nRequires-Dist: w3lib (>=1.19.0)\nRequires-Dist: six (>=1.5.2)\nRequires-Dist: cssselect (>=0.9)\nRequires-Dist: lxml ; python_version != \"3.4\"\nRequires-Dist: lxml (<=4.3.5) ; python_version == \"3.4\"\nRequires-Dist: functools32 ; python_version<'3.0'\n\n===============================\nParsel\n===============================\n\n.. image:: https://img.shields.io/travis/scrapy/parsel/master.svg\n   :target: https://travis-ci.org/scrapy/parsel\n   :alt: Build Status\n\n.. image:: https://img.shields.io/pypi/v/parsel.svg\n   :target: https://pypi.python.org/pypi/parsel\n   :alt: PyPI Version\n\n.. image:: https://img.shields.io/codecov/c/github/scrapy/parsel/master.svg\n   :target: http://codecov.io/github/scrapy/parsel?branch=master\n   :alt: Coverage report\n\n\nParsel is a library to extract data from HTML and XML using XPath and CSS selectors\n\n* Free software: BSD license\n* Documentation: https://parsel.readthedocs.org.\n\nFeatures\n--------\n\n* Extract text using CSS or XPath selectors\n* Regular expression helper methods\n\nExample::\n\n    >>> from parsel import Selector\n    >>> sel = Selector(text=u\"\"\"<html>\n            <body>\n                <h1>Hello, Parsel!</h1>\n                <ul>\n                    <li><a href=\"http://example.com\">Link 1</a></li>\n                    <li><a href=\"http://scrapy.org\">Link 2</a></li>\n                </ul>\n            </body>\n            </html>\"\"\")\n    >>>\n    >>> sel.css('h1::text').get()\n    'Hello, Parsel!'\n    >>>\n    >>> sel.css('h1::text').re('\\w+')\n    ['Hello', 'Parsel']\n    >>>\n    >>> for e in sel.css('ul > li'):\n    ...     print(e.xpath('.//a/@href').get())\n    http://example.com\n    http://scrapy.org\n\n\n\n\nHistory\n-------\n\n1.5.2 (2019-08-09)\n~~~~~~~~~~~~~~~~~~\n\n* ``Selector.remove_namespaces`` received a significant performance improvement\n* The value of ``data`` within the printable representation of a selector\n  (``repr(selector)``) now ends in ``...`` when truncated, to make the\n  truncation obvious.\n* Minor documentation improvements.\n\n\n1.5.1 (2018-10-25)\n~~~~~~~~~~~~~~~~~~\n\n* ``has-class`` XPath function handles newlines and other separators\n  in class names properly;\n* fixed parsing of HTML documents with null bytes;\n* documentation improvements;\n* Python 3.7 tests are run on CI; other test improvements.\n\n\n1.5.0 (2018-07-04)\n~~~~~~~~~~~~~~~~~~\n\n* New ``Selector.attrib`` and ``SelectorList.attrib`` properties which make\n  it easier to get attributes of HTML elements.\n* CSS selectors became faster: compilation results are cached\n  (LRU cache is used for ``css2xpath``), so there is\n  less overhead when the same CSS expression is used several times.\n* ``.get()`` and ``.getall()`` selector methods are documented and recommended\n  over ``.extract_first()`` and ``.extract()``.\n* Various documentation tweaks and improvements.\n\nOne more change is that ``.extract()`` and  ``.extract_first()`` methods\nare now implemented using ``.get()`` and ``.getall()``, not the other\nway around, and instead of calling ``Selector.extract`` all other methods\nnow call ``Selector.get`` internally. It can be **backwards incompatible**\nin case of custom Selector subclasses which override ``Selector.extract``\nwithout doing the same for ``Selector.get``. If you have such Selector\nsubclass, make sure ``get`` method is also overridden. For example, this::\n\n    class MySelector(parsel.Selector):\n        def extract(self):\n            return super().extract() + \" foo\"\n\nshould be changed to this::\n\n    class MySelector(parsel.Selector):\n        def get(self):\n            return super().get() + \" foo\"\n        extract = get\n\n\n1.4.0 (2018-02-08)\n~~~~~~~~~~~~~~~~~~\n\n* ``Selector`` and ``SelectorList`` can't be pickled because\n  pickling/unpickling doesn't work for ``lxml.html.HtmlElement``;\n  parsel now raises TypeError explicitly instead of allowing pickle to\n  silently produce wrong output. This is technically backwards-incompatible\n  if you're using Python < 3.6.\n\n\n1.3.1 (2017-12-28)\n~~~~~~~~~~~~~~~~~~\n\n* Fix artifact uploads to pypi.\n\n\n1.3.0 (2017-12-28)\n~~~~~~~~~~~~~~~~~~\n\n* ``has-class`` XPath extension function;\n* ``parsel.xpathfuncs.set_xpathfunc`` is a simplified way to register\n  XPath extensions;\n* ``Selector.remove_namespaces`` now removes namespace declarations;\n* Python 3.3 support is dropped;\n* ``make htmlview`` command for easier Parsel docs development.\n* CI: PyPy installation is fixed; parsel now runs tests for PyPy3 as well.\n\n\n1.2.0 (2017-05-17)\n~~~~~~~~~~~~~~~~~~\n\n* Add ``SelectorList.get`` and ``SelectorList.getall``\n  methods as aliases for ``SelectorList.extract_first``\n  and ``SelectorList.extract`` respectively\n* Add default value parameter to ``SelectorList.re_first`` method\n* Add ``Selector.re_first`` method\n* Add ``replace_entities`` argument on ``.re()`` and ``.re_first()``\n  to turn off replacing of character entity references\n* Bug fix: detect ``None`` result from lxml parsing and fallback with an empty document\n* Rearrange XML/HTML examples in the selectors usage docs\n* Travis CI:\n\n  * Test against Python 3.6\n  * Test against PyPy using \"Portable PyPy for Linux\" distribution\n\n\n1.1.0 (2016-11-22)\n~~~~~~~~~~~~~~~~~~\n\n* Change default HTML parser to `lxml.html.HTMLParser <http://lxml.de/api/lxml.html.HTMLParser-class.html>`_,\n  which makes easier to use some HTML specific features\n* Add css2xpath function to translate CSS to XPath\n* Add support for ad-hoc namespaces declarations\n* Add support for XPath variables\n* Documentation improvements and updates\n\n\n1.0.3 (2016-07-29)\n~~~~~~~~~~~~~~~~~~\n\n* Add BSD-3-Clause license file\n* Re-enable PyPy tests\n* Integrate py.test runs with setuptools (needed for Debian packaging)\n* Changelog is now called ``NEWS``\n\n\n1.0.2 (2016-04-26)\n~~~~~~~~~~~~~~~~~~\n\n* Fix bug in exception handling causing original traceback to be lost\n* Added docstrings and other doc fixes\n\n\n1.0.1 (2015-08-24)\n~~~~~~~~~~~~~~~~~~\n\n* Updated PyPI classifiers\n* Added docstrings for csstranslator module and other doc fixes\n\n\n1.0.0 (2015-08-22)\n~~~~~~~~~~~~~~~~~~\n\n* Documentation fixes\n\n\n0.9.6 (2015-08-14)\n~~~~~~~~~~~~~~~~~~\n\n* Updated documentation\n* Extended test coverage\n\n\n0.9.5 (2015-08-11)\n~~~~~~~~~~~~~~~~~~\n\n* Support for extending SelectorList\n\n\n0.9.4 (2015-08-10)\n~~~~~~~~~~~~~~~~~~\n\n* Try workaround for travis-ci/dpl#253\n\n\n0.9.3 (2015-08-07)\n~~~~~~~~~~~~~~~~~~\n\n* Add base_url argument\n\n\n0.9.2 (2015-08-07)\n~~~~~~~~~~~~~~~~~~\n\n* Rename module unified -> selector and promoted root attribute\n* Add create_root_node function\n\n\n0.9.1 (2015-08-04)\n~~~~~~~~~~~~~~~~~~\n\n* Setup Sphinx build and docs structure\n* Build universal wheels\n* Rename some leftovers from package extraction\n\n\n0.9.0 (2015-07-30)\n~~~~~~~~~~~~~~~~~~\n\n* First release on PyPI.\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/parsel-1.5.2.dist-info/RECORD",
    "content": "parsel-1.5.2.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nparsel-1.5.2.dist-info/LICENSE,sha256=EjilxoEoVqJpatBTDtrSSV7AMEicPmPB-JD5VBZyrZc,1521\r\nparsel-1.5.2.dist-info/METADATA,sha256=9r-PGZ7PNak-uRFVrl8ECS6h7fFkmg0Mzp7ky3SwDFk,7809\r\nparsel-1.5.2.dist-info/RECORD,,\r\nparsel-1.5.2.dist-info/WHEEL,sha256=h_aVn5OB2IERUjMbi2pucmR_zzWJtk303YXvhh60NJ8,110\r\nparsel-1.5.2.dist-info/top_level.txt,sha256=djxZw3B9hpuDSWmC-9A8vEn2YaYMBNgv8v4sBhivK7A,7\r\nparsel/__init__.py,sha256=d-1RH-VBII6Smo_FW3GLP2cHrryNrdg6EPxt1t86xG4,341\r\nparsel/__pycache__/__init__.cpython-36.pyc,,\r\nparsel/__pycache__/csstranslator.cpython-36.pyc,,\r\nparsel/__pycache__/selector.cpython-36.pyc,,\r\nparsel/__pycache__/utils.cpython-36.pyc,,\r\nparsel/__pycache__/xpathfuncs.cpython-36.pyc,,\r\nparsel/csstranslator.py,sha256=90dBQZRwDaJd381xXrvqjeGktK-Cl7A-DQYm93yLdpw,4089\r\nparsel/selector.py,sha256=i2h3zx5VaMpyUC2MZlbCfxh1EBbTxeQ8hBkq9xlOALg,13158\r\nparsel/utils.py,sha256=FI6tqVrLJY0-vJfVqRS8ZYApwML65t4ywBYgfcqmFYI,2765\r\nparsel/xpathfuncs.py,sha256=s3j_ER11RYe9Eco7L6Yg52JsBST5de04oSs1lWwDd6M,1780\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/parsel-1.5.2.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.33.4)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/parsel-1.5.2.dist-info/top_level.txt",
    "content": "parsel\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/EGG-INFO/PKG-INFO",
    "content": "Metadata-Version: 1.2\nName: pip\nVersion: 19.0.3\nSummary: The PyPA recommended tool for installing Python packages.\nHome-page: https://pip.pypa.io/\nAuthor: The pip developers\nAuthor-email: pypa-dev@groups.google.com\nLicense: MIT\nDescription: pip - The Python Package Installer\n        ==================================\n        \n        .. image:: https://img.shields.io/pypi/v/pip.svg\n           :target: https://pypi.org/project/pip/\n        \n        .. image:: https://readthedocs.org/projects/pip/badge/?version=latest\n           :target: https://pip.pypa.io/en/latest\n        \n        pip is the `package installer`_ for Python. You can use pip to install packages from the `Python Package Index`_ and other indexes.\n        \n        Please take a look at our documentation for how to install and use pip:\n        \n        * `Installation`_\n        * `Usage`_\n        * `Release notes`_\n        \n        If you find bugs, need help, or want to talk to the developers please use our mailing lists or chat rooms:\n        \n        * `Issue tracking`_\n        * `Discourse channel`_\n        * `User IRC`_\n        \n        If you want to get involved head over to GitHub to get the source code and feel free to jump on the developer mailing lists and chat rooms:\n        \n        * `GitHub page`_\n        * `Dev mailing list`_\n        * `Dev IRC`_\n        \n        Code of Conduct\n        ---------------\n        \n        Everyone interacting in the pip project's codebases, issue trackers, chat\n        rooms, and mailing lists is expected to follow the `PyPA Code of Conduct`_.\n        \n        .. _package installer: https://packaging.python.org/en/latest/current/\n        .. _Python Package Index: https://pypi.org\n        .. _Installation: https://pip.pypa.io/en/stable/installing.html\n        .. _Usage: https://pip.pypa.io/en/stable/\n        .. _Release notes: https://pip.pypa.io/en/stable/news.html\n        .. _GitHub page: https://github.com/pypa/pip\n        .. _Issue tracking: https://github.com/pypa/pip/issues\n        .. _Discourse channel: https://discuss.python.org/c/packaging\n        .. _Dev mailing list: https://groups.google.com/forum/#!forum/pypa-dev\n        .. _User IRC: https://webchat.freenode.net/?channels=%23pypa\n        .. _Dev IRC: https://webchat.freenode.net/?channels=%23pypa-dev\n        .. _PyPA Code of Conduct: https://www.pypa.io/en/latest/code-of-conduct/\n        \nKeywords: distutils easy_install egg setuptools wheel virtualenv\nPlatform: UNKNOWN\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: MIT License\nClassifier: Topic :: Software Development :: Build Tools\nClassifier: Programming Language :: Python\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nClassifier: Programming Language :: Python :: Implementation :: CPython\nClassifier: Programming Language :: Python :: Implementation :: PyPy\nRequires-Python: >=2.7,!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/EGG-INFO/SOURCES.txt",
    "content": "AUTHORS.txt\nLICENSE.txt\nMANIFEST.in\nNEWS.rst\nREADME.rst\npyproject.toml\nsetup.cfg\nsetup.py\ndocs/pip_sphinxext.py\ndocs/html/conf.py\ndocs/html/cookbook.rst\ndocs/html/index.rst\ndocs/html/installing.rst\ndocs/html/logic.rst\ndocs/html/news.rst\ndocs/html/quickstart.rst\ndocs/html/usage.rst\ndocs/html/user_guide.rst\ndocs/html/development/configuration.rst\ndocs/html/development/contributing.rst\ndocs/html/development/getting-started.rst\ndocs/html/development/index.rst\ndocs/html/development/release-process.rst\ndocs/html/development/vendoring-policy.rst\ndocs/html/reference/index.rst\ndocs/html/reference/pip.rst\ndocs/html/reference/pip_check.rst\ndocs/html/reference/pip_config.rst\ndocs/html/reference/pip_download.rst\ndocs/html/reference/pip_freeze.rst\ndocs/html/reference/pip_hash.rst\ndocs/html/reference/pip_install.rst\ndocs/html/reference/pip_list.rst\ndocs/html/reference/pip_search.rst\ndocs/html/reference/pip_show.rst\ndocs/html/reference/pip_uninstall.rst\ndocs/html/reference/pip_wheel.rst\ndocs/man/index.rst\ndocs/man/commands/check.rst\ndocs/man/commands/config.rst\ndocs/man/commands/download.rst\ndocs/man/commands/freeze.rst\ndocs/man/commands/hash.rst\ndocs/man/commands/help.rst\ndocs/man/commands/install.rst\ndocs/man/commands/list.rst\ndocs/man/commands/search.rst\ndocs/man/commands/show.rst\ndocs/man/commands/uninstall.rst\ndocs/man/commands/wheel.rst\nsrc/pip/__init__.py\nsrc/pip/__main__.py\nsrc/pip.egg-info/PKG-INFO\nsrc/pip.egg-info/SOURCES.txt\nsrc/pip.egg-info/dependency_links.txt\nsrc/pip.egg-info/entry_points.txt\nsrc/pip.egg-info/not-zip-safe\nsrc/pip.egg-info/top_level.txt\nsrc/pip/_internal/__init__.py\nsrc/pip/_internal/build_env.py\nsrc/pip/_internal/cache.py\nsrc/pip/_internal/configuration.py\nsrc/pip/_internal/download.py\nsrc/pip/_internal/exceptions.py\nsrc/pip/_internal/index.py\nsrc/pip/_internal/locations.py\nsrc/pip/_internal/pep425tags.py\nsrc/pip/_internal/pyproject.py\nsrc/pip/_internal/resolve.py\nsrc/pip/_internal/wheel.py\nsrc/pip/_internal/cli/__init__.py\nsrc/pip/_internal/cli/autocompletion.py\nsrc/pip/_internal/cli/base_command.py\nsrc/pip/_internal/cli/cmdoptions.py\nsrc/pip/_internal/cli/main_parser.py\nsrc/pip/_internal/cli/parser.py\nsrc/pip/_internal/cli/status_codes.py\nsrc/pip/_internal/commands/__init__.py\nsrc/pip/_internal/commands/check.py\nsrc/pip/_internal/commands/completion.py\nsrc/pip/_internal/commands/configuration.py\nsrc/pip/_internal/commands/download.py\nsrc/pip/_internal/commands/freeze.py\nsrc/pip/_internal/commands/hash.py\nsrc/pip/_internal/commands/help.py\nsrc/pip/_internal/commands/install.py\nsrc/pip/_internal/commands/list.py\nsrc/pip/_internal/commands/search.py\nsrc/pip/_internal/commands/show.py\nsrc/pip/_internal/commands/uninstall.py\nsrc/pip/_internal/commands/wheel.py\nsrc/pip/_internal/models/__init__.py\nsrc/pip/_internal/models/candidate.py\nsrc/pip/_internal/models/format_control.py\nsrc/pip/_internal/models/index.py\nsrc/pip/_internal/models/link.py\nsrc/pip/_internal/operations/__init__.py\nsrc/pip/_internal/operations/check.py\nsrc/pip/_internal/operations/freeze.py\nsrc/pip/_internal/operations/prepare.py\nsrc/pip/_internal/req/__init__.py\nsrc/pip/_internal/req/constructors.py\nsrc/pip/_internal/req/req_file.py\nsrc/pip/_internal/req/req_install.py\nsrc/pip/_internal/req/req_set.py\nsrc/pip/_internal/req/req_tracker.py\nsrc/pip/_internal/req/req_uninstall.py\nsrc/pip/_internal/utils/__init__.py\nsrc/pip/_internal/utils/appdirs.py\nsrc/pip/_internal/utils/compat.py\nsrc/pip/_internal/utils/deprecation.py\nsrc/pip/_internal/utils/encoding.py\nsrc/pip/_internal/utils/filesystem.py\nsrc/pip/_internal/utils/glibc.py\nsrc/pip/_internal/utils/hashes.py\nsrc/pip/_internal/utils/logging.py\nsrc/pip/_internal/utils/misc.py\nsrc/pip/_internal/utils/models.py\nsrc/pip/_internal/utils/outdated.py\nsrc/pip/_internal/utils/packaging.py\nsrc/pip/_internal/utils/setuptools_build.py\nsrc/pip/_internal/utils/temp_dir.py\nsrc/pip/_internal/utils/typing.py\nsrc/pip/_internal/utils/ui.py\nsrc/pip/_internal/vcs/__init__.py\nsrc/pip/_internal/vcs/bazaar.py\nsrc/pip/_internal/vcs/git.py\nsrc/pip/_internal/vcs/mercurial.py\nsrc/pip/_internal/vcs/subversion.py\nsrc/pip/_vendor/README.rst\nsrc/pip/_vendor/__init__.py\nsrc/pip/_vendor/appdirs.LICENSE.txt\nsrc/pip/_vendor/appdirs.py\nsrc/pip/_vendor/distro.LICENSE\nsrc/pip/_vendor/distro.py\nsrc/pip/_vendor/ipaddress.LICENSE\nsrc/pip/_vendor/ipaddress.py\nsrc/pip/_vendor/pyparsing.LICENSE\nsrc/pip/_vendor/pyparsing.py\nsrc/pip/_vendor/retrying.LICENSE\nsrc/pip/_vendor/retrying.py\nsrc/pip/_vendor/six.LICENSE\nsrc/pip/_vendor/six.py\nsrc/pip/_vendor/vendor.txt\nsrc/pip/_vendor/cachecontrol/LICENSE.txt\nsrc/pip/_vendor/cachecontrol/__init__.py\nsrc/pip/_vendor/cachecontrol/_cmd.py\nsrc/pip/_vendor/cachecontrol/adapter.py\nsrc/pip/_vendor/cachecontrol/cache.py\nsrc/pip/_vendor/cachecontrol/compat.py\nsrc/pip/_vendor/cachecontrol/controller.py\nsrc/pip/_vendor/cachecontrol/filewrapper.py\nsrc/pip/_vendor/cachecontrol/heuristics.py\nsrc/pip/_vendor/cachecontrol/serialize.py\nsrc/pip/_vendor/cachecontrol/wrapper.py\nsrc/pip/_vendor/cachecontrol/caches/__init__.py\nsrc/pip/_vendor/cachecontrol/caches/file_cache.py\nsrc/pip/_vendor/cachecontrol/caches/redis_cache.py\nsrc/pip/_vendor/certifi/LICENSE\nsrc/pip/_vendor/certifi/__init__.py\nsrc/pip/_vendor/certifi/__main__.py\nsrc/pip/_vendor/certifi/cacert.pem\nsrc/pip/_vendor/certifi/core.py\nsrc/pip/_vendor/chardet/LICENSE\nsrc/pip/_vendor/chardet/__init__.py\nsrc/pip/_vendor/chardet/big5freq.py\nsrc/pip/_vendor/chardet/big5prober.py\nsrc/pip/_vendor/chardet/chardistribution.py\nsrc/pip/_vendor/chardet/charsetgroupprober.py\nsrc/pip/_vendor/chardet/charsetprober.py\nsrc/pip/_vendor/chardet/codingstatemachine.py\nsrc/pip/_vendor/chardet/compat.py\nsrc/pip/_vendor/chardet/cp949prober.py\nsrc/pip/_vendor/chardet/enums.py\nsrc/pip/_vendor/chardet/escprober.py\nsrc/pip/_vendor/chardet/escsm.py\nsrc/pip/_vendor/chardet/eucjpprober.py\nsrc/pip/_vendor/chardet/euckrfreq.py\nsrc/pip/_vendor/chardet/euckrprober.py\nsrc/pip/_vendor/chardet/euctwfreq.py\nsrc/pip/_vendor/chardet/euctwprober.py\nsrc/pip/_vendor/chardet/gb2312freq.py\nsrc/pip/_vendor/chardet/gb2312prober.py\nsrc/pip/_vendor/chardet/hebrewprober.py\nsrc/pip/_vendor/chardet/jisfreq.py\nsrc/pip/_vendor/chardet/jpcntx.py\nsrc/pip/_vendor/chardet/langbulgarianmodel.py\nsrc/pip/_vendor/chardet/langcyrillicmodel.py\nsrc/pip/_vendor/chardet/langgreekmodel.py\nsrc/pip/_vendor/chardet/langhebrewmodel.py\nsrc/pip/_vendor/chardet/langhungarianmodel.py\nsrc/pip/_vendor/chardet/langthaimodel.py\nsrc/pip/_vendor/chardet/langturkishmodel.py\nsrc/pip/_vendor/chardet/latin1prober.py\nsrc/pip/_vendor/chardet/mbcharsetprober.py\nsrc/pip/_vendor/chardet/mbcsgroupprober.py\nsrc/pip/_vendor/chardet/mbcssm.py\nsrc/pip/_vendor/chardet/sbcharsetprober.py\nsrc/pip/_vendor/chardet/sbcsgroupprober.py\nsrc/pip/_vendor/chardet/sjisprober.py\nsrc/pip/_vendor/chardet/universaldetector.py\nsrc/pip/_vendor/chardet/utf8prober.py\nsrc/pip/_vendor/chardet/version.py\nsrc/pip/_vendor/chardet/cli/__init__.py\nsrc/pip/_vendor/chardet/cli/chardetect.py\nsrc/pip/_vendor/colorama/LICENSE.txt\nsrc/pip/_vendor/colorama/__init__.py\nsrc/pip/_vendor/colorama/ansi.py\nsrc/pip/_vendor/colorama/ansitowin32.py\nsrc/pip/_vendor/colorama/initialise.py\nsrc/pip/_vendor/colorama/win32.py\nsrc/pip/_vendor/colorama/winterm.py\nsrc/pip/_vendor/distlib/LICENSE.txt\nsrc/pip/_vendor/distlib/__init__.py\nsrc/pip/_vendor/distlib/compat.py\nsrc/pip/_vendor/distlib/database.py\nsrc/pip/_vendor/distlib/index.py\nsrc/pip/_vendor/distlib/locators.py\nsrc/pip/_vendor/distlib/manifest.py\nsrc/pip/_vendor/distlib/markers.py\nsrc/pip/_vendor/distlib/metadata.py\nsrc/pip/_vendor/distlib/resources.py\nsrc/pip/_vendor/distlib/scripts.py\nsrc/pip/_vendor/distlib/t32.exe\nsrc/pip/_vendor/distlib/t64.exe\nsrc/pip/_vendor/distlib/util.py\nsrc/pip/_vendor/distlib/version.py\nsrc/pip/_vendor/distlib/w32.exe\nsrc/pip/_vendor/distlib/w64.exe\nsrc/pip/_vendor/distlib/wheel.py\nsrc/pip/_vendor/distlib/_backport/__init__.py\nsrc/pip/_vendor/distlib/_backport/misc.py\nsrc/pip/_vendor/distlib/_backport/shutil.py\nsrc/pip/_vendor/distlib/_backport/sysconfig.cfg\nsrc/pip/_vendor/distlib/_backport/sysconfig.py\nsrc/pip/_vendor/distlib/_backport/tarfile.py\nsrc/pip/_vendor/html5lib/LICENSE\nsrc/pip/_vendor/html5lib/__init__.py\nsrc/pip/_vendor/html5lib/_ihatexml.py\nsrc/pip/_vendor/html5lib/_inputstream.py\nsrc/pip/_vendor/html5lib/_tokenizer.py\nsrc/pip/_vendor/html5lib/_utils.py\nsrc/pip/_vendor/html5lib/constants.py\nsrc/pip/_vendor/html5lib/html5parser.py\nsrc/pip/_vendor/html5lib/serializer.py\nsrc/pip/_vendor/html5lib/_trie/__init__.py\nsrc/pip/_vendor/html5lib/_trie/_base.py\nsrc/pip/_vendor/html5lib/_trie/datrie.py\nsrc/pip/_vendor/html5lib/_trie/py.py\nsrc/pip/_vendor/html5lib/filters/__init__.py\nsrc/pip/_vendor/html5lib/filters/alphabeticalattributes.py\nsrc/pip/_vendor/html5lib/filters/base.py\nsrc/pip/_vendor/html5lib/filters/inject_meta_charset.py\nsrc/pip/_vendor/html5lib/filters/lint.py\nsrc/pip/_vendor/html5lib/filters/optionaltags.py\nsrc/pip/_vendor/html5lib/filters/sanitizer.py\nsrc/pip/_vendor/html5lib/filters/whitespace.py\nsrc/pip/_vendor/html5lib/treeadapters/__init__.py\nsrc/pip/_vendor/html5lib/treeadapters/genshi.py\nsrc/pip/_vendor/html5lib/treeadapters/sax.py\nsrc/pip/_vendor/html5lib/treebuilders/__init__.py\nsrc/pip/_vendor/html5lib/treebuilders/base.py\nsrc/pip/_vendor/html5lib/treebuilders/dom.py\nsrc/pip/_vendor/html5lib/treebuilders/etree.py\nsrc/pip/_vendor/html5lib/treebuilders/etree_lxml.py\nsrc/pip/_vendor/html5lib/treewalkers/__init__.py\nsrc/pip/_vendor/html5lib/treewalkers/base.py\nsrc/pip/_vendor/html5lib/treewalkers/dom.py\nsrc/pip/_vendor/html5lib/treewalkers/etree.py\nsrc/pip/_vendor/html5lib/treewalkers/etree_lxml.py\nsrc/pip/_vendor/html5lib/treewalkers/genshi.py\nsrc/pip/_vendor/idna/LICENSE.rst\nsrc/pip/_vendor/idna/__init__.py\nsrc/pip/_vendor/idna/codec.py\nsrc/pip/_vendor/idna/compat.py\nsrc/pip/_vendor/idna/core.py\nsrc/pip/_vendor/idna/idnadata.py\nsrc/pip/_vendor/idna/intranges.py\nsrc/pip/_vendor/idna/package_data.py\nsrc/pip/_vendor/idna/uts46data.py\nsrc/pip/_vendor/lockfile/LICENSE\nsrc/pip/_vendor/lockfile/__init__.py\nsrc/pip/_vendor/lockfile/linklockfile.py\nsrc/pip/_vendor/lockfile/mkdirlockfile.py\nsrc/pip/_vendor/lockfile/pidlockfile.py\nsrc/pip/_vendor/lockfile/sqlitelockfile.py\nsrc/pip/_vendor/lockfile/symlinklockfile.py\nsrc/pip/_vendor/msgpack/COPYING\nsrc/pip/_vendor/msgpack/__init__.py\nsrc/pip/_vendor/msgpack/_version.py\nsrc/pip/_vendor/msgpack/exceptions.py\nsrc/pip/_vendor/msgpack/fallback.py\nsrc/pip/_vendor/packaging/LICENSE\nsrc/pip/_vendor/packaging/LICENSE.APACHE\nsrc/pip/_vendor/packaging/LICENSE.BSD\nsrc/pip/_vendor/packaging/__about__.py\nsrc/pip/_vendor/packaging/__init__.py\nsrc/pip/_vendor/packaging/_compat.py\nsrc/pip/_vendor/packaging/_structures.py\nsrc/pip/_vendor/packaging/markers.py\nsrc/pip/_vendor/packaging/requirements.py\nsrc/pip/_vendor/packaging/specifiers.py\nsrc/pip/_vendor/packaging/utils.py\nsrc/pip/_vendor/packaging/version.py\nsrc/pip/_vendor/pep517/LICENSE\nsrc/pip/_vendor/pep517/__init__.py\nsrc/pip/_vendor/pep517/_in_process.py\nsrc/pip/_vendor/pep517/build.py\nsrc/pip/_vendor/pep517/check.py\nsrc/pip/_vendor/pep517/colorlog.py\nsrc/pip/_vendor/pep517/compat.py\nsrc/pip/_vendor/pep517/envbuild.py\nsrc/pip/_vendor/pep517/wrappers.py\nsrc/pip/_vendor/pkg_resources/LICENSE\nsrc/pip/_vendor/pkg_resources/__init__.py\nsrc/pip/_vendor/pkg_resources/py31compat.py\nsrc/pip/_vendor/progress/LICENSE\nsrc/pip/_vendor/progress/__init__.py\nsrc/pip/_vendor/progress/bar.py\nsrc/pip/_vendor/progress/counter.py\nsrc/pip/_vendor/progress/helpers.py\nsrc/pip/_vendor/progress/spinner.py\nsrc/pip/_vendor/pytoml/LICENSE\nsrc/pip/_vendor/pytoml/__init__.py\nsrc/pip/_vendor/pytoml/core.py\nsrc/pip/_vendor/pytoml/parser.py\nsrc/pip/_vendor/pytoml/test.py\nsrc/pip/_vendor/pytoml/utils.py\nsrc/pip/_vendor/pytoml/writer.py\nsrc/pip/_vendor/requests/LICENSE\nsrc/pip/_vendor/requests/__init__.py\nsrc/pip/_vendor/requests/__version__.py\nsrc/pip/_vendor/requests/_internal_utils.py\nsrc/pip/_vendor/requests/adapters.py\nsrc/pip/_vendor/requests/api.py\nsrc/pip/_vendor/requests/auth.py\nsrc/pip/_vendor/requests/certs.py\nsrc/pip/_vendor/requests/compat.py\nsrc/pip/_vendor/requests/cookies.py\nsrc/pip/_vendor/requests/exceptions.py\nsrc/pip/_vendor/requests/help.py\nsrc/pip/_vendor/requests/hooks.py\nsrc/pip/_vendor/requests/models.py\nsrc/pip/_vendor/requests/packages.py\nsrc/pip/_vendor/requests/sessions.py\nsrc/pip/_vendor/requests/status_codes.py\nsrc/pip/_vendor/requests/structures.py\nsrc/pip/_vendor/requests/utils.py\nsrc/pip/_vendor/urllib3/LICENSE.txt\nsrc/pip/_vendor/urllib3/__init__.py\nsrc/pip/_vendor/urllib3/_collections.py\nsrc/pip/_vendor/urllib3/connection.py\nsrc/pip/_vendor/urllib3/connectionpool.py\nsrc/pip/_vendor/urllib3/exceptions.py\nsrc/pip/_vendor/urllib3/fields.py\nsrc/pip/_vendor/urllib3/filepost.py\nsrc/pip/_vendor/urllib3/poolmanager.py\nsrc/pip/_vendor/urllib3/request.py\nsrc/pip/_vendor/urllib3/response.py\nsrc/pip/_vendor/urllib3/contrib/__init__.py\nsrc/pip/_vendor/urllib3/contrib/_appengine_environ.py\nsrc/pip/_vendor/urllib3/contrib/appengine.py\nsrc/pip/_vendor/urllib3/contrib/ntlmpool.py\nsrc/pip/_vendor/urllib3/contrib/pyopenssl.py\nsrc/pip/_vendor/urllib3/contrib/securetransport.py\nsrc/pip/_vendor/urllib3/contrib/socks.py\nsrc/pip/_vendor/urllib3/contrib/_securetransport/__init__.py\nsrc/pip/_vendor/urllib3/contrib/_securetransport/bindings.py\nsrc/pip/_vendor/urllib3/contrib/_securetransport/low_level.py\nsrc/pip/_vendor/urllib3/packages/__init__.py\nsrc/pip/_vendor/urllib3/packages/six.py\nsrc/pip/_vendor/urllib3/packages/backports/__init__.py\nsrc/pip/_vendor/urllib3/packages/backports/makefile.py\nsrc/pip/_vendor/urllib3/packages/ssl_match_hostname/__init__.py\nsrc/pip/_vendor/urllib3/packages/ssl_match_hostname/_implementation.py\nsrc/pip/_vendor/urllib3/util/__init__.py\nsrc/pip/_vendor/urllib3/util/connection.py\nsrc/pip/_vendor/urllib3/util/queue.py\nsrc/pip/_vendor/urllib3/util/request.py\nsrc/pip/_vendor/urllib3/util/response.py\nsrc/pip/_vendor/urllib3/util/retry.py\nsrc/pip/_vendor/urllib3/util/ssl_.py\nsrc/pip/_vendor/urllib3/util/timeout.py\nsrc/pip/_vendor/urllib3/util/url.py\nsrc/pip/_vendor/urllib3/util/wait.py\nsrc/pip/_vendor/webencodings/LICENSE\nsrc/pip/_vendor/webencodings/__init__.py\nsrc/pip/_vendor/webencodings/labels.py\nsrc/pip/_vendor/webencodings/mklabels.py\nsrc/pip/_vendor/webencodings/tests.py\nsrc/pip/_vendor/webencodings/x_user_defined.py"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/EGG-INFO/dependency_links.txt",
    "content": "\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/EGG-INFO/entry_points.txt",
    "content": "[console_scripts]\npip = pip._internal:main\npip3 = pip._internal:main\npip3.6 = pip._internal:main\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/EGG-INFO/not-zip-safe",
    "content": "\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/EGG-INFO/top_level.txt",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/__init__.py",
    "content": "__version__ = \"19.0.3\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/__main__.py",
    "content": "from __future__ import absolute_import\n\nimport os\nimport sys\n\n# If we are running from a wheel, add the wheel to sys.path\n# This allows the usage python pip-*.whl/pip install pip-*.whl\nif __package__ == '':\n    # __file__ is pip-*.whl/pip/__main__.py\n    # first dirname call strips of '/__main__.py', second strips off '/pip'\n    # Resulting path is the name of the wheel itself\n    # Add that to sys.path so we can import pip\n    path = os.path.dirname(os.path.dirname(__file__))\n    sys.path.insert(0, path)\n\nfrom pip._internal import main as _main  # isort:skip # noqa\n\nif __name__ == '__main__':\n    sys.exit(_main())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/__init__.py",
    "content": "#!/usr/bin/env python\nfrom __future__ import absolute_import\n\nimport locale\nimport logging\nimport os\nimport warnings\n\nimport sys\n\n# 2016-06-17 barry@debian.org: urllib3 1.14 added optional support for socks,\n# but if invoked (i.e. imported), it will issue a warning to stderr if socks\n# isn't available.  requests unconditionally imports urllib3's socks contrib\n# module, triggering this warning.  The warning breaks DEP-8 tests (because of\n# the stderr output) and is just plain annoying in normal usage.  I don't want\n# to add socks as yet another dependency for pip, nor do I want to allow-stder\n# in the DEP-8 tests, so just suppress the warning.  pdb tells me this has to\n# be done before the import of pip.vcs.\nfrom pip._vendor.urllib3.exceptions import DependencyWarning\nwarnings.filterwarnings(\"ignore\", category=DependencyWarning)  # noqa\n\n# We want to inject the use of SecureTransport as early as possible so that any\n# references or sessions or what have you are ensured to have it, however we\n# only want to do this in the case that we're running on macOS and the linked\n# OpenSSL is too old to handle TLSv1.2\ntry:\n    import ssl\nexcept ImportError:\n    pass\nelse:\n    # Checks for OpenSSL 1.0.1 on MacOS\n    if sys.platform == \"darwin\" and ssl.OPENSSL_VERSION_NUMBER < 0x1000100f:\n        try:\n            from pip._vendor.urllib3.contrib import securetransport\n        except (ImportError, OSError):\n            pass\n        else:\n            securetransport.inject_into_urllib3()\n\nfrom pip._internal.cli.autocompletion import autocomplete\nfrom pip._internal.cli.main_parser import parse_command\nfrom pip._internal.commands import commands_dict\nfrom pip._internal.exceptions import PipError\nfrom pip._internal.utils import deprecation\nfrom pip._internal.vcs import git, mercurial, subversion, bazaar  # noqa\nfrom pip._vendor.urllib3.exceptions import InsecureRequestWarning\n\nlogger = logging.getLogger(__name__)\n\n# Hide the InsecureRequestWarning from urllib3\nwarnings.filterwarnings(\"ignore\", category=InsecureRequestWarning)\n\n\ndef main(args=None):\n    if args is None:\n        args = sys.argv[1:]\n\n    # Configure our deprecation warnings to be sent through loggers\n    deprecation.install_warning_logger()\n\n    autocomplete()\n\n    try:\n        cmd_name, cmd_args = parse_command(args)\n    except PipError as exc:\n        sys.stderr.write(\"ERROR: %s\" % exc)\n        sys.stderr.write(os.linesep)\n        sys.exit(1)\n\n    # Needed for locale.getpreferredencoding(False) to work\n    # in pip._internal.utils.encoding.auto_decode\n    try:\n        locale.setlocale(locale.LC_ALL, '')\n    except locale.Error as e:\n        # setlocale can apparently crash if locale are uninitialized\n        logger.debug(\"Ignoring error %s when setting locale\", e)\n    command = commands_dict[cmd_name](isolated=(\"--isolated\" in cmd_args))\n    return command.main(cmd_args)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/build_env.py",
    "content": "\"\"\"Build Environment used for isolation during sdist building\n\"\"\"\n\nimport logging\nimport os\nimport sys\nimport textwrap\nfrom collections import OrderedDict\nfrom distutils.sysconfig import get_python_lib\nfrom sysconfig import get_paths\n\nfrom pip._vendor.pkg_resources import Requirement, VersionConflict, WorkingSet\n\nfrom pip import __file__ as pip_location\nfrom pip._internal.utils.misc import call_subprocess\nfrom pip._internal.utils.temp_dir import TempDirectory\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\nfrom pip._internal.utils.ui import open_spinner\n\nif MYPY_CHECK_RUNNING:\n    from typing import Tuple, Set, Iterable, Optional, List  # noqa: F401\n    from pip._internal.index import PackageFinder  # noqa: F401\n\nlogger = logging.getLogger(__name__)\n\n\nclass _Prefix:\n\n    def __init__(self, path):\n        # type: (str) -> None\n        self.path = path\n        self.setup = False\n        self.bin_dir = get_paths(\n            'nt' if os.name == 'nt' else 'posix_prefix',\n            vars={'base': path, 'platbase': path}\n        )['scripts']\n        # Note: prefer distutils' sysconfig to get the\n        # library paths so PyPy is correctly supported.\n        purelib = get_python_lib(plat_specific=False, prefix=path)\n        platlib = get_python_lib(plat_specific=True, prefix=path)\n        if purelib == platlib:\n            self.lib_dirs = [purelib]\n        else:\n            self.lib_dirs = [purelib, platlib]\n\n\nclass BuildEnvironment(object):\n    \"\"\"Creates and manages an isolated environment to install build deps\n    \"\"\"\n\n    def __init__(self):\n        # type: () -> None\n        self._temp_dir = TempDirectory(kind=\"build-env\")\n        self._temp_dir.create()\n\n        self._prefixes = OrderedDict((\n            (name, _Prefix(os.path.join(self._temp_dir.path, name)))\n            for name in ('normal', 'overlay')\n        ))\n\n        self._bin_dirs = []  # type: List[str]\n        self._lib_dirs = []  # type: List[str]\n        for prefix in reversed(list(self._prefixes.values())):\n            self._bin_dirs.append(prefix.bin_dir)\n            self._lib_dirs.extend(prefix.lib_dirs)\n\n        # Customize site to:\n        # - ensure .pth files are honored\n        # - prevent access to system site packages\n        system_sites = {\n            os.path.normcase(site) for site in (\n                get_python_lib(plat_specific=False),\n                get_python_lib(plat_specific=True),\n            )\n        }\n        self._site_dir = os.path.join(self._temp_dir.path, 'site')\n        if not os.path.exists(self._site_dir):\n            os.mkdir(self._site_dir)\n        with open(os.path.join(self._site_dir, 'sitecustomize.py'), 'w') as fp:\n            fp.write(textwrap.dedent(\n                '''\n                import os, site, sys\n\n                # First, drop system-sites related paths.\n                original_sys_path = sys.path[:]\n                known_paths = set()\n                for path in {system_sites!r}:\n                    site.addsitedir(path, known_paths=known_paths)\n                system_paths = set(\n                    os.path.normcase(path)\n                    for path in sys.path[len(original_sys_path):]\n                )\n                original_sys_path = [\n                    path for path in original_sys_path\n                    if os.path.normcase(path) not in system_paths\n                ]\n                sys.path = original_sys_path\n\n                # Second, add lib directories.\n                # ensuring .pth file are processed.\n                for path in {lib_dirs!r}:\n                    assert not path in sys.path\n                    site.addsitedir(path)\n                '''\n            ).format(system_sites=system_sites, lib_dirs=self._lib_dirs))\n\n    def __enter__(self):\n        self._save_env = {\n            name: os.environ.get(name, None)\n            for name in ('PATH', 'PYTHONNOUSERSITE', 'PYTHONPATH')\n        }\n\n        path = self._bin_dirs[:]\n        old_path = self._save_env['PATH']\n        if old_path:\n            path.extend(old_path.split(os.pathsep))\n\n        pythonpath = [self._site_dir]\n\n        os.environ.update({\n            'PATH': os.pathsep.join(path),\n            'PYTHONNOUSERSITE': '1',\n            'PYTHONPATH': os.pathsep.join(pythonpath),\n        })\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        for varname, old_value in self._save_env.items():\n            if old_value is None:\n                os.environ.pop(varname, None)\n            else:\n                os.environ[varname] = old_value\n\n    def cleanup(self):\n        # type: () -> None\n        self._temp_dir.cleanup()\n\n    def check_requirements(self, reqs):\n        # type: (Iterable[str]) -> Tuple[Set[Tuple[str, str]], Set[str]]\n        \"\"\"Return 2 sets:\n            - conflicting requirements: set of (installed, wanted) reqs tuples\n            - missing requirements: set of reqs\n        \"\"\"\n        missing = set()\n        conflicting = set()\n        if reqs:\n            ws = WorkingSet(self._lib_dirs)\n            for req in reqs:\n                try:\n                    if ws.find(Requirement.parse(req)) is None:\n                        missing.add(req)\n                except VersionConflict as e:\n                    conflicting.add((str(e.args[0].as_requirement()),\n                                     str(e.args[1])))\n        return conflicting, missing\n\n    def install_requirements(\n        self,\n        finder,  # type: PackageFinder\n        requirements,  # type: Iterable[str]\n        prefix_as_string,  # type: str\n        message  # type: Optional[str]\n    ):\n        # type: (...) -> None\n        prefix = self._prefixes[prefix_as_string]\n        assert not prefix.setup\n        prefix.setup = True\n        if not requirements:\n            return\n        args = [\n            sys.executable, os.path.dirname(pip_location), 'install',\n            '--ignore-installed', '--no-user', '--prefix', prefix.path,\n            '--no-warn-script-location',\n        ]  # type: List[str]\n        if logger.getEffectiveLevel() <= logging.DEBUG:\n            args.append('-v')\n        for format_control in ('no_binary', 'only_binary'):\n            formats = getattr(finder.format_control, format_control)\n            args.extend(('--' + format_control.replace('_', '-'),\n                         ','.join(sorted(formats or {':none:'}))))\n        if finder.index_urls:\n            args.extend(['-i', finder.index_urls[0]])\n            for extra_index in finder.index_urls[1:]:\n                args.extend(['--extra-index-url', extra_index])\n        else:\n            args.append('--no-index')\n        for link in finder.find_links:\n            args.extend(['--find-links', link])\n        for _, host, _ in finder.secure_origins:\n            args.extend(['--trusted-host', host])\n        if finder.allow_all_prereleases:\n            args.append('--pre')\n        args.append('--')\n        args.extend(requirements)\n        with open_spinner(message) as spinner:\n            call_subprocess(args, show_stdout=False, spinner=spinner)\n\n\nclass NoOpBuildEnvironment(BuildEnvironment):\n    \"\"\"A no-op drop-in replacement for BuildEnvironment\n    \"\"\"\n\n    def __init__(self):\n        pass\n\n    def __enter__(self):\n        pass\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        pass\n\n    def cleanup(self):\n        pass\n\n    def install_requirements(self, finder, requirements, prefix, message):\n        raise NotImplementedError()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/cache.py",
    "content": "\"\"\"Cache Management\n\"\"\"\n\nimport errno\nimport hashlib\nimport logging\nimport os\n\nfrom pip._vendor.packaging.utils import canonicalize_name\n\nfrom pip._internal.download import path_to_url\nfrom pip._internal.models.link import Link\nfrom pip._internal.utils.compat import expanduser\nfrom pip._internal.utils.temp_dir import TempDirectory\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\nfrom pip._internal.wheel import InvalidWheelFilename, Wheel\n\nif MYPY_CHECK_RUNNING:\n    from typing import Optional, Set, List, Any  # noqa: F401\n    from pip._internal.index import FormatControl  # noqa: F401\n\nlogger = logging.getLogger(__name__)\n\n\nclass Cache(object):\n    \"\"\"An abstract class - provides cache directories for data from links\n\n\n        :param cache_dir: The root of the cache.\n        :param format_control: An object of FormatControl class to limit\n            binaries being read from the cache.\n        :param allowed_formats: which formats of files the cache should store.\n            ('binary' and 'source' are the only allowed values)\n    \"\"\"\n\n    def __init__(self, cache_dir, format_control, allowed_formats):\n        # type: (str, FormatControl, Set[str]) -> None\n        super(Cache, self).__init__()\n        self.cache_dir = expanduser(cache_dir) if cache_dir else None\n        self.format_control = format_control\n        self.allowed_formats = allowed_formats\n\n        _valid_formats = {\"source\", \"binary\"}\n        assert self.allowed_formats.union(_valid_formats) == _valid_formats\n\n    def _get_cache_path_parts(self, link):\n        # type: (Link) -> List[str]\n        \"\"\"Get parts of part that must be os.path.joined with cache_dir\n        \"\"\"\n\n        # We want to generate an url to use as our cache key, we don't want to\n        # just re-use the URL because it might have other items in the fragment\n        # and we don't care about those.\n        key_parts = [link.url_without_fragment]\n        if link.hash_name is not None and link.hash is not None:\n            key_parts.append(\"=\".join([link.hash_name, link.hash]))\n        key_url = \"#\".join(key_parts)\n\n        # Encode our key url with sha224, we'll use this because it has similar\n        # security properties to sha256, but with a shorter total output (and\n        # thus less secure). However the differences don't make a lot of\n        # difference for our use case here.\n        hashed = hashlib.sha224(key_url.encode()).hexdigest()\n\n        # We want to nest the directories some to prevent having a ton of top\n        # level directories where we might run out of sub directories on some\n        # FS.\n        parts = [hashed[:2], hashed[2:4], hashed[4:6], hashed[6:]]\n\n        return parts\n\n    def _get_candidates(self, link, package_name):\n        # type: (Link, Optional[str]) -> List[Any]\n        can_not_cache = (\n            not self.cache_dir or\n            not package_name or\n            not link\n        )\n        if can_not_cache:\n            return []\n\n        canonical_name = canonicalize_name(package_name)\n        formats = self.format_control.get_allowed_formats(\n            canonical_name\n        )\n        if not self.allowed_formats.intersection(formats):\n            return []\n\n        root = self.get_path_for_link(link)\n        try:\n            return os.listdir(root)\n        except OSError as err:\n            if err.errno in {errno.ENOENT, errno.ENOTDIR}:\n                return []\n            raise\n\n    def get_path_for_link(self, link):\n        # type: (Link) -> str\n        \"\"\"Return a directory to store cached items in for link.\n        \"\"\"\n        raise NotImplementedError()\n\n    def get(self, link, package_name):\n        # type: (Link, Optional[str]) -> Link\n        \"\"\"Returns a link to a cached item if it exists, otherwise returns the\n        passed link.\n        \"\"\"\n        raise NotImplementedError()\n\n    def _link_for_candidate(self, link, candidate):\n        # type: (Link, str) -> Link\n        root = self.get_path_for_link(link)\n        path = os.path.join(root, candidate)\n\n        return Link(path_to_url(path))\n\n    def cleanup(self):\n        # type: () -> None\n        pass\n\n\nclass SimpleWheelCache(Cache):\n    \"\"\"A cache of wheels for future installs.\n    \"\"\"\n\n    def __init__(self, cache_dir, format_control):\n        # type: (str, FormatControl) -> None\n        super(SimpleWheelCache, self).__init__(\n            cache_dir, format_control, {\"binary\"}\n        )\n\n    def get_path_for_link(self, link):\n        # type: (Link) -> str\n        \"\"\"Return a directory to store cached wheels for link\n\n        Because there are M wheels for any one sdist, we provide a directory\n        to cache them in, and then consult that directory when looking up\n        cache hits.\n\n        We only insert things into the cache if they have plausible version\n        numbers, so that we don't contaminate the cache with things that were\n        not unique. E.g. ./package might have dozens of installs done for it\n        and build a version of 0.0...and if we built and cached a wheel, we'd\n        end up using the same wheel even if the source has been edited.\n\n        :param link: The link of the sdist for which this will cache wheels.\n        \"\"\"\n        parts = self._get_cache_path_parts(link)\n\n        # Store wheels within the root cache_dir\n        return os.path.join(self.cache_dir, \"wheels\", *parts)\n\n    def get(self, link, package_name):\n        # type: (Link, Optional[str]) -> Link\n        candidates = []\n\n        for wheel_name in self._get_candidates(link, package_name):\n            try:\n                wheel = Wheel(wheel_name)\n            except InvalidWheelFilename:\n                continue\n            if not wheel.supported():\n                # Built for a different python/arch/etc\n                continue\n            candidates.append((wheel.support_index_min(), wheel_name))\n\n        if not candidates:\n            return link\n\n        return self._link_for_candidate(link, min(candidates)[1])\n\n\nclass EphemWheelCache(SimpleWheelCache):\n    \"\"\"A SimpleWheelCache that creates it's own temporary cache directory\n    \"\"\"\n\n    def __init__(self, format_control):\n        # type: (FormatControl) -> None\n        self._temp_dir = TempDirectory(kind=\"ephem-wheel-cache\")\n        self._temp_dir.create()\n\n        super(EphemWheelCache, self).__init__(\n            self._temp_dir.path, format_control\n        )\n\n    def cleanup(self):\n        # type: () -> None\n        self._temp_dir.cleanup()\n\n\nclass WheelCache(Cache):\n    \"\"\"Wraps EphemWheelCache and SimpleWheelCache into a single Cache\n\n    This Cache allows for gracefully degradation, using the ephem wheel cache\n    when a certain link is not found in the simple wheel cache first.\n    \"\"\"\n\n    def __init__(self, cache_dir, format_control):\n        # type: (str, FormatControl) -> None\n        super(WheelCache, self).__init__(\n            cache_dir, format_control, {'binary'}\n        )\n        self._wheel_cache = SimpleWheelCache(cache_dir, format_control)\n        self._ephem_cache = EphemWheelCache(format_control)\n\n    def get_path_for_link(self, link):\n        # type: (Link) -> str\n        return self._wheel_cache.get_path_for_link(link)\n\n    def get_ephem_path_for_link(self, link):\n        # type: (Link) -> str\n        return self._ephem_cache.get_path_for_link(link)\n\n    def get(self, link, package_name):\n        # type: (Link, Optional[str]) -> Link\n        retval = self._wheel_cache.get(link, package_name)\n        if retval is link:\n            retval = self._ephem_cache.get(link, package_name)\n        return retval\n\n    def cleanup(self):\n        # type: () -> None\n        self._wheel_cache.cleanup()\n        self._ephem_cache.cleanup()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/cli/__init__.py",
    "content": "\"\"\"Subpackage containing all of pip's command line interface related code\n\"\"\"\n\n# This file intentionally does not import submodules\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/cli/autocompletion.py",
    "content": "\"\"\"Logic that powers autocompletion installed by ``pip completion``.\n\"\"\"\n\nimport optparse\nimport os\nimport sys\n\nfrom pip._internal.cli.main_parser import create_main_parser\nfrom pip._internal.commands import commands_dict, get_summaries\nfrom pip._internal.utils.misc import get_installed_distributions\n\n\ndef autocomplete():\n    \"\"\"Entry Point for completion of main and subcommand options.\n    \"\"\"\n    # Don't complete if user hasn't sourced bash_completion file.\n    if 'PIP_AUTO_COMPLETE' not in os.environ:\n        return\n    cwords = os.environ['COMP_WORDS'].split()[1:]\n    cword = int(os.environ['COMP_CWORD'])\n    try:\n        current = cwords[cword - 1]\n    except IndexError:\n        current = ''\n\n    subcommands = [cmd for cmd, summary in get_summaries()]\n    options = []\n    # subcommand\n    try:\n        subcommand_name = [w for w in cwords if w in subcommands][0]\n    except IndexError:\n        subcommand_name = None\n\n    parser = create_main_parser()\n    # subcommand options\n    if subcommand_name:\n        # special case: 'help' subcommand has no options\n        if subcommand_name == 'help':\n            sys.exit(1)\n        # special case: list locally installed dists for show and uninstall\n        should_list_installed = (\n            subcommand_name in ['show', 'uninstall'] and\n            not current.startswith('-')\n        )\n        if should_list_installed:\n            installed = []\n            lc = current.lower()\n            for dist in get_installed_distributions(local_only=True):\n                if dist.key.startswith(lc) and dist.key not in cwords[1:]:\n                    installed.append(dist.key)\n            # if there are no dists installed, fall back to option completion\n            if installed:\n                for dist in installed:\n                    print(dist)\n                sys.exit(1)\n\n        subcommand = commands_dict[subcommand_name]()\n\n        for opt in subcommand.parser.option_list_all:\n            if opt.help != optparse.SUPPRESS_HELP:\n                for opt_str in opt._long_opts + opt._short_opts:\n                    options.append((opt_str, opt.nargs))\n\n        # filter out previously specified options from available options\n        prev_opts = [x.split('=')[0] for x in cwords[1:cword - 1]]\n        options = [(x, v) for (x, v) in options if x not in prev_opts]\n        # filter options by current input\n        options = [(k, v) for k, v in options if k.startswith(current)]\n        # get completion type given cwords and available subcommand options\n        completion_type = get_path_completion_type(\n            cwords, cword, subcommand.parser.option_list_all,\n        )\n        # get completion files and directories if ``completion_type`` is\n        # ``<file>``, ``<dir>`` or ``<path>``\n        if completion_type:\n            options = auto_complete_paths(current, completion_type)\n            options = ((opt, 0) for opt in options)\n        for option in options:\n            opt_label = option[0]\n            # append '=' to options which require args\n            if option[1] and option[0][:2] == \"--\":\n                opt_label += '='\n            print(opt_label)\n    else:\n        # show main parser options only when necessary\n\n        opts = [i.option_list for i in parser.option_groups]\n        opts.append(parser.option_list)\n        opts = (o for it in opts for o in it)\n        if current.startswith('-'):\n            for opt in opts:\n                if opt.help != optparse.SUPPRESS_HELP:\n                    subcommands += opt._long_opts + opt._short_opts\n        else:\n            # get completion type given cwords and all available options\n            completion_type = get_path_completion_type(cwords, cword, opts)\n            if completion_type:\n                subcommands = auto_complete_paths(current, completion_type)\n\n        print(' '.join([x for x in subcommands if x.startswith(current)]))\n    sys.exit(1)\n\n\ndef get_path_completion_type(cwords, cword, opts):\n    \"\"\"Get the type of path completion (``file``, ``dir``, ``path`` or None)\n\n    :param cwords: same as the environmental variable ``COMP_WORDS``\n    :param cword: same as the environmental variable ``COMP_CWORD``\n    :param opts: The available options to check\n    :return: path completion type (``file``, ``dir``, ``path`` or None)\n    \"\"\"\n    if cword < 2 or not cwords[cword - 2].startswith('-'):\n        return\n    for opt in opts:\n        if opt.help == optparse.SUPPRESS_HELP:\n            continue\n        for o in str(opt).split('/'):\n            if cwords[cword - 2].split('=')[0] == o:\n                if not opt.metavar or any(\n                        x in ('path', 'file', 'dir')\n                        for x in opt.metavar.split('/')):\n                    return opt.metavar\n\n\ndef auto_complete_paths(current, completion_type):\n    \"\"\"If ``completion_type`` is ``file`` or ``path``, list all regular files\n    and directories starting with ``current``; otherwise only list directories\n    starting with ``current``.\n\n    :param current: The word to be completed\n    :param completion_type: path completion type(`file`, `path` or `dir`)i\n    :return: A generator of regular files and/or directories\n    \"\"\"\n    directory, filename = os.path.split(current)\n    current_path = os.path.abspath(directory)\n    # Don't complete paths if they can't be accessed\n    if not os.access(current_path, os.R_OK):\n        return\n    filename = os.path.normcase(filename)\n    # list all files that start with ``filename``\n    file_list = (x for x in os.listdir(current_path)\n                 if os.path.normcase(x).startswith(filename))\n    for f in file_list:\n        opt = os.path.join(current_path, f)\n        comp_file = os.path.normcase(os.path.join(directory, f))\n        # complete regular files when there is not ``<dir>`` after option\n        # complete directories when there is ``<file>``, ``<path>`` or\n        # ``<dir>``after option\n        if completion_type != 'dir' and os.path.isfile(opt):\n            yield comp_file\n        elif os.path.isdir(opt):\n            yield os.path.join(comp_file, '')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/cli/base_command.py",
    "content": "\"\"\"Base Command class, and related routines\"\"\"\nfrom __future__ import absolute_import, print_function\n\nimport logging\nimport logging.config\nimport optparse\nimport os\nimport platform\nimport sys\nimport traceback\n\nfrom pip._internal.cli import cmdoptions\nfrom pip._internal.cli.parser import (\n    ConfigOptionParser, UpdatingDefaultsHelpFormatter,\n)\nfrom pip._internal.cli.status_codes import (\n    ERROR, PREVIOUS_BUILD_DIR_ERROR, SUCCESS, UNKNOWN_ERROR,\n    VIRTUALENV_NOT_FOUND,\n)\nfrom pip._internal.download import PipSession\nfrom pip._internal.exceptions import (\n    BadCommand, CommandError, InstallationError, PreviousBuildDirError,\n    UninstallationError,\n)\nfrom pip._internal.index import PackageFinder\nfrom pip._internal.locations import running_under_virtualenv\nfrom pip._internal.req.constructors import (\n    install_req_from_editable, install_req_from_line,\n)\nfrom pip._internal.req.req_file import parse_requirements\nfrom pip._internal.utils.deprecation import deprecated\nfrom pip._internal.utils.logging import BrokenStdoutLoggingError, setup_logging\nfrom pip._internal.utils.misc import (\n    get_prog, normalize_path, redact_password_from_url,\n)\nfrom pip._internal.utils.outdated import pip_version_check\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Optional, List, Tuple, Any  # noqa: F401\n    from optparse import Values  # noqa: F401\n    from pip._internal.cache import WheelCache  # noqa: F401\n    from pip._internal.req.req_set import RequirementSet  # noqa: F401\n\n__all__ = ['Command']\n\nlogger = logging.getLogger(__name__)\n\n\nclass Command(object):\n    name = None  # type: Optional[str]\n    usage = None  # type: Optional[str]\n    hidden = False  # type: bool\n    ignore_require_venv = False  # type: bool\n\n    def __init__(self, isolated=False):\n        # type: (bool) -> None\n        parser_kw = {\n            'usage': self.usage,\n            'prog': '%s %s' % (get_prog(), self.name),\n            'formatter': UpdatingDefaultsHelpFormatter(),\n            'add_help_option': False,\n            'name': self.name,\n            'description': self.__doc__,\n            'isolated': isolated,\n        }\n\n        self.parser = ConfigOptionParser(**parser_kw)\n\n        # Commands should add options to this option group\n        optgroup_name = '%s Options' % self.name.capitalize()\n        self.cmd_opts = optparse.OptionGroup(self.parser, optgroup_name)\n\n        # Add the general options\n        gen_opts = cmdoptions.make_option_group(\n            cmdoptions.general_group,\n            self.parser,\n        )\n        self.parser.add_option_group(gen_opts)\n\n    def run(self, options, args):\n        # type: (Values, List[Any]) -> Any\n        raise NotImplementedError\n\n    def _build_session(self, options, retries=None, timeout=None):\n        # type: (Values, Optional[int], Optional[int]) -> PipSession\n        session = PipSession(\n            cache=(\n                normalize_path(os.path.join(options.cache_dir, \"http\"))\n                if options.cache_dir else None\n            ),\n            retries=retries if retries is not None else options.retries,\n            insecure_hosts=options.trusted_hosts,\n        )\n\n        # Handle custom ca-bundles from the user\n        if options.cert:\n            session.verify = options.cert\n\n        # Handle SSL client certificate\n        if options.client_cert:\n            session.cert = options.client_cert\n\n        # Handle timeouts\n        if options.timeout or timeout:\n            session.timeout = (\n                timeout if timeout is not None else options.timeout\n            )\n\n        # Handle configured proxies\n        if options.proxy:\n            session.proxies = {\n                \"http\": options.proxy,\n                \"https\": options.proxy,\n            }\n\n        # Determine if we can prompt the user for authentication or not\n        session.auth.prompting = not options.no_input\n\n        return session\n\n    def parse_args(self, args):\n        # type: (List[str]) -> Tuple\n        # factored out for testability\n        return self.parser.parse_args(args)\n\n    def main(self, args):\n        # type: (List[str]) -> int\n        options, args = self.parse_args(args)\n\n        # Set verbosity so that it can be used elsewhere.\n        self.verbosity = options.verbose - options.quiet\n\n        level_number = setup_logging(\n            verbosity=self.verbosity,\n            no_color=options.no_color,\n            user_log_file=options.log,\n        )\n\n        if sys.version_info[:2] == (3, 4):\n            deprecated(\n                \"Python 3.4 support has been deprecated. pip 19.1 will be the \"\n                \"last one supporting it. Please upgrade your Python as Python \"\n                \"3.4 won't be maintained after March 2019 (cf PEP 429).\",\n                replacement=None,\n                gone_in='19.2',\n            )\n        elif sys.version_info[:2] == (2, 7):\n            message = (\n                \"A future version of pip will drop support for Python 2.7.\"\n            )\n            if platform.python_implementation() == \"CPython\":\n                message = (\n                    \"Python 2.7 will reach the end of its life on January \"\n                    \"1st, 2020. Please upgrade your Python as Python 2.7 \"\n                    \"won't be maintained after that date. \"\n                ) + message\n            deprecated(message, replacement=None, gone_in=None)\n\n        # TODO: Try to get these passing down from the command?\n        #       without resorting to os.environ to hold these.\n        #       This also affects isolated builds and it should.\n\n        if options.no_input:\n            os.environ['PIP_NO_INPUT'] = '1'\n\n        if options.exists_action:\n            os.environ['PIP_EXISTS_ACTION'] = ' '.join(options.exists_action)\n\n        if options.require_venv and not self.ignore_require_venv:\n            # If a venv is required check if it can really be found\n            if not running_under_virtualenv():\n                logger.critical(\n                    'Could not find an activated virtualenv (required).'\n                )\n                sys.exit(VIRTUALENV_NOT_FOUND)\n\n        try:\n            status = self.run(options, args)\n            # FIXME: all commands should return an exit status\n            # and when it is done, isinstance is not needed anymore\n            if isinstance(status, int):\n                return status\n        except PreviousBuildDirError as exc:\n            logger.critical(str(exc))\n            logger.debug('Exception information:', exc_info=True)\n\n            return PREVIOUS_BUILD_DIR_ERROR\n        except (InstallationError, UninstallationError, BadCommand) as exc:\n            logger.critical(str(exc))\n            logger.debug('Exception information:', exc_info=True)\n\n            return ERROR\n        except CommandError as exc:\n            logger.critical('ERROR: %s', exc)\n            logger.debug('Exception information:', exc_info=True)\n\n            return ERROR\n        except BrokenStdoutLoggingError:\n            # Bypass our logger and write any remaining messages to stderr\n            # because stdout no longer works.\n            print('ERROR: Pipe to stdout was broken', file=sys.stderr)\n            if level_number <= logging.DEBUG:\n                traceback.print_exc(file=sys.stderr)\n\n            return ERROR\n        except KeyboardInterrupt:\n            logger.critical('Operation cancelled by user')\n            logger.debug('Exception information:', exc_info=True)\n\n            return ERROR\n        except BaseException:\n            logger.critical('Exception:', exc_info=True)\n\n            return UNKNOWN_ERROR\n        finally:\n            allow_version_check = (\n                # Does this command have the index_group options?\n                hasattr(options, \"no_index\") and\n                # Is this command allowed to perform this check?\n                not (options.disable_pip_version_check or options.no_index)\n            )\n            # Check if we're using the latest version of pip available\n            if allow_version_check:\n                session = self._build_session(\n                    options,\n                    retries=0,\n                    timeout=min(5, options.timeout)\n                )\n                with session:\n                    pip_version_check(session, options)\n\n            # Shutdown the logging module\n            logging.shutdown()\n\n        return SUCCESS\n\n\nclass RequirementCommand(Command):\n\n    @staticmethod\n    def populate_requirement_set(requirement_set,  # type: RequirementSet\n                                 args,             # type: List[str]\n                                 options,          # type: Values\n                                 finder,           # type: PackageFinder\n                                 session,          # type: PipSession\n                                 name,             # type: str\n                                 wheel_cache       # type: Optional[WheelCache]\n                                 ):\n        # type: (...) -> None\n        \"\"\"\n        Marshal cmd line args into a requirement set.\n        \"\"\"\n        # NOTE: As a side-effect, options.require_hashes and\n        #       requirement_set.require_hashes may be updated\n\n        for filename in options.constraints:\n            for req_to_add in parse_requirements(\n                    filename,\n                    constraint=True, finder=finder, options=options,\n                    session=session, wheel_cache=wheel_cache):\n                req_to_add.is_direct = True\n                requirement_set.add_requirement(req_to_add)\n\n        for req in args:\n            req_to_add = install_req_from_line(\n                req, None, isolated=options.isolated_mode,\n                use_pep517=options.use_pep517,\n                wheel_cache=wheel_cache\n            )\n            req_to_add.is_direct = True\n            requirement_set.add_requirement(req_to_add)\n\n        for req in options.editables:\n            req_to_add = install_req_from_editable(\n                req,\n                isolated=options.isolated_mode,\n                use_pep517=options.use_pep517,\n                wheel_cache=wheel_cache\n            )\n            req_to_add.is_direct = True\n            requirement_set.add_requirement(req_to_add)\n\n        for filename in options.requirements:\n            for req_to_add in parse_requirements(\n                    filename,\n                    finder=finder, options=options, session=session,\n                    wheel_cache=wheel_cache,\n                    use_pep517=options.use_pep517):\n                req_to_add.is_direct = True\n                requirement_set.add_requirement(req_to_add)\n        # If --require-hashes was a line in a requirements file, tell\n        # RequirementSet about it:\n        requirement_set.require_hashes = options.require_hashes\n\n        if not (args or options.editables or options.requirements):\n            opts = {'name': name}\n            if options.find_links:\n                raise CommandError(\n                    'You must give at least one requirement to %(name)s '\n                    '(maybe you meant \"pip %(name)s %(links)s\"?)' %\n                    dict(opts, links=' '.join(options.find_links)))\n            else:\n                raise CommandError(\n                    'You must give at least one requirement to %(name)s '\n                    '(see \"pip help %(name)s\")' % opts)\n\n    def _build_package_finder(\n        self,\n        options,               # type: Values\n        session,               # type: PipSession\n        platform=None,         # type: Optional[str]\n        python_versions=None,  # type: Optional[List[str]]\n        abi=None,              # type: Optional[str]\n        implementation=None    # type: Optional[str]\n    ):\n        # type: (...) -> PackageFinder\n        \"\"\"\n        Create a package finder appropriate to this requirement command.\n        \"\"\"\n        index_urls = [options.index_url] + options.extra_index_urls\n        if options.no_index:\n            logger.debug(\n                'Ignoring indexes: %s',\n                ','.join(redact_password_from_url(url) for url in index_urls),\n            )\n            index_urls = []\n\n        return PackageFinder(\n            find_links=options.find_links,\n            format_control=options.format_control,\n            index_urls=index_urls,\n            trusted_hosts=options.trusted_hosts,\n            allow_all_prereleases=options.pre,\n            session=session,\n            platform=platform,\n            versions=python_versions,\n            abi=abi,\n            implementation=implementation,\n            prefer_binary=options.prefer_binary,\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/cli/cmdoptions.py",
    "content": "\"\"\"\nshared options and groups\n\nThe principle here is to define options once, but *not* instantiate them\nglobally. One reason being that options with action='append' can carry state\nbetween parses. pip parses general options twice internally, and shouldn't\npass on state. To be consistent, all options will follow this design.\n\n\"\"\"\nfrom __future__ import absolute_import\n\nimport textwrap\nimport warnings\nfrom distutils.util import strtobool\nfrom functools import partial\nfrom optparse import SUPPRESS_HELP, Option, OptionGroup\n\nfrom pip._internal.exceptions import CommandError\nfrom pip._internal.locations import USER_CACHE_DIR, src_prefix\nfrom pip._internal.models.format_control import FormatControl\nfrom pip._internal.models.index import PyPI\nfrom pip._internal.utils.hashes import STRONG_HASHES\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\nfrom pip._internal.utils.ui import BAR_TYPES\n\nif MYPY_CHECK_RUNNING:\n    from typing import Any, Callable, Dict, List, Optional, Union  # noqa: F401\n    from optparse import OptionParser, Values  # noqa: F401\n    from pip._internal.cli.parser import ConfigOptionParser  # noqa: F401\n\n\ndef raise_option_error(parser, option, msg):\n    \"\"\"\n    Raise an option parsing error using parser.error().\n\n    Args:\n      parser: an OptionParser instance.\n      option: an Option instance.\n      msg: the error text.\n    \"\"\"\n    msg = '{} error: {}'.format(option, msg)\n    msg = textwrap.fill(' '.join(msg.split()))\n    parser.error(msg)\n\n\ndef make_option_group(group, parser):\n    # type: (Dict[str, Any], ConfigOptionParser) -> OptionGroup\n    \"\"\"\n    Return an OptionGroup object\n    group  -- assumed to be dict with 'name' and 'options' keys\n    parser -- an optparse Parser\n    \"\"\"\n    option_group = OptionGroup(parser, group['name'])\n    for option in group['options']:\n        option_group.add_option(option())\n    return option_group\n\n\ndef check_install_build_global(options, check_options=None):\n    # type: (Values, Optional[Values]) -> None\n    \"\"\"Disable wheels if per-setup.py call options are set.\n\n    :param options: The OptionParser options to update.\n    :param check_options: The options to check, if not supplied defaults to\n        options.\n    \"\"\"\n    if check_options is None:\n        check_options = options\n\n    def getname(n):\n        return getattr(check_options, n, None)\n    names = [\"build_options\", \"global_options\", \"install_options\"]\n    if any(map(getname, names)):\n        control = options.format_control\n        control.disallow_binaries()\n        warnings.warn(\n            'Disabling all use of wheels due to the use of --build-options '\n            '/ --global-options / --install-options.', stacklevel=2,\n        )\n\n\ndef check_dist_restriction(options, check_target=False):\n    # type: (Values, bool) -> None\n    \"\"\"Function for determining if custom platform options are allowed.\n\n    :param options: The OptionParser options.\n    :param check_target: Whether or not to check if --target is being used.\n    \"\"\"\n    dist_restriction_set = any([\n        options.python_version,\n        options.platform,\n        options.abi,\n        options.implementation,\n    ])\n\n    binary_only = FormatControl(set(), {':all:'})\n    sdist_dependencies_allowed = (\n        options.format_control != binary_only and\n        not options.ignore_dependencies\n    )\n\n    # Installations or downloads using dist restrictions must not combine\n    # source distributions and dist-specific wheels, as they are not\n    # gauranteed to be locally compatible.\n    if dist_restriction_set and sdist_dependencies_allowed:\n        raise CommandError(\n            \"When restricting platform and interpreter constraints using \"\n            \"--python-version, --platform, --abi, or --implementation, \"\n            \"either --no-deps must be set, or --only-binary=:all: must be \"\n            \"set and --no-binary must not be set (or must be set to \"\n            \":none:).\"\n        )\n\n    if check_target:\n        if dist_restriction_set and not options.target_dir:\n            raise CommandError(\n                \"Can not use any platform or abi specific options unless \"\n                \"installing via '--target'\"\n            )\n\n\n###########\n# options #\n###########\n\nhelp_ = partial(\n    Option,\n    '-h', '--help',\n    dest='help',\n    action='help',\n    help='Show help.',\n)  # type: Callable[..., Option]\n\nisolated_mode = partial(\n    Option,\n    \"--isolated\",\n    dest=\"isolated_mode\",\n    action=\"store_true\",\n    default=False,\n    help=(\n        \"Run pip in an isolated mode, ignoring environment variables and user \"\n        \"configuration.\"\n    ),\n)  # type: Callable[..., Option]\n\nrequire_virtualenv = partial(\n    Option,\n    # Run only if inside a virtualenv, bail if not.\n    '--require-virtualenv', '--require-venv',\n    dest='require_venv',\n    action='store_true',\n    default=False,\n    help=SUPPRESS_HELP\n)  # type: Callable[..., Option]\n\nverbose = partial(\n    Option,\n    '-v', '--verbose',\n    dest='verbose',\n    action='count',\n    default=0,\n    help='Give more output. Option is additive, and can be used up to 3 times.'\n)  # type: Callable[..., Option]\n\nno_color = partial(\n    Option,\n    '--no-color',\n    dest='no_color',\n    action='store_true',\n    default=False,\n    help=\"Suppress colored output\",\n)  # type: Callable[..., Option]\n\nversion = partial(\n    Option,\n    '-V', '--version',\n    dest='version',\n    action='store_true',\n    help='Show version and exit.',\n)  # type: Callable[..., Option]\n\nquiet = partial(\n    Option,\n    '-q', '--quiet',\n    dest='quiet',\n    action='count',\n    default=0,\n    help=(\n        'Give less output. Option is additive, and can be used up to 3'\n        ' times (corresponding to WARNING, ERROR, and CRITICAL logging'\n        ' levels).'\n    ),\n)  # type: Callable[..., Option]\n\nprogress_bar = partial(\n    Option,\n    '--progress-bar',\n    dest='progress_bar',\n    type='choice',\n    choices=list(BAR_TYPES.keys()),\n    default='on',\n    help=(\n        'Specify type of progress to be displayed [' +\n        '|'.join(BAR_TYPES.keys()) + '] (default: %default)'\n    ),\n)  # type: Callable[..., Option]\n\nlog = partial(\n    Option,\n    \"--log\", \"--log-file\", \"--local-log\",\n    dest=\"log\",\n    metavar=\"path\",\n    help=\"Path to a verbose appending log.\"\n)  # type: Callable[..., Option]\n\nno_input = partial(\n    Option,\n    # Don't ask for input\n    '--no-input',\n    dest='no_input',\n    action='store_true',\n    default=False,\n    help=SUPPRESS_HELP\n)  # type: Callable[..., Option]\n\nproxy = partial(\n    Option,\n    '--proxy',\n    dest='proxy',\n    type='str',\n    default='',\n    help=\"Specify a proxy in the form [user:passwd@]proxy.server:port.\"\n)  # type: Callable[..., Option]\n\nretries = partial(\n    Option,\n    '--retries',\n    dest='retries',\n    type='int',\n    default=5,\n    help=\"Maximum number of retries each connection should attempt \"\n         \"(default %default times).\",\n)  # type: Callable[..., Option]\n\ntimeout = partial(\n    Option,\n    '--timeout', '--default-timeout',\n    metavar='sec',\n    dest='timeout',\n    type='float',\n    default=15,\n    help='Set the socket timeout (default %default seconds).',\n)  # type: Callable[..., Option]\n\nskip_requirements_regex = partial(\n    Option,\n    # A regex to be used to skip requirements\n    '--skip-requirements-regex',\n    dest='skip_requirements_regex',\n    type='str',\n    default='',\n    help=SUPPRESS_HELP,\n)  # type: Callable[..., Option]\n\n\ndef exists_action():\n    # type: () -> Option\n    return Option(\n        # Option when path already exist\n        '--exists-action',\n        dest='exists_action',\n        type='choice',\n        choices=['s', 'i', 'w', 'b', 'a'],\n        default=[],\n        action='append',\n        metavar='action',\n        help=\"Default action when a path already exists: \"\n             \"(s)witch, (i)gnore, (w)ipe, (b)ackup, (a)bort).\",\n    )\n\n\ncert = partial(\n    Option,\n    '--cert',\n    dest='cert',\n    type='str',\n    metavar='path',\n    help=\"Path to alternate CA bundle.\",\n)  # type: Callable[..., Option]\n\nclient_cert = partial(\n    Option,\n    '--client-cert',\n    dest='client_cert',\n    type='str',\n    default=None,\n    metavar='path',\n    help=\"Path to SSL client certificate, a single file containing the \"\n         \"private key and the certificate in PEM format.\",\n)  # type: Callable[..., Option]\n\nindex_url = partial(\n    Option,\n    '-i', '--index-url', '--pypi-url',\n    dest='index_url',\n    metavar='URL',\n    default=PyPI.simple_url,\n    help=\"Base URL of Python Package Index (default %default). \"\n         \"This should point to a repository compliant with PEP 503 \"\n         \"(the simple repository API) or a local directory laid out \"\n         \"in the same format.\",\n)  # type: Callable[..., Option]\n\n\ndef extra_index_url():\n    return Option(\n        '--extra-index-url',\n        dest='extra_index_urls',\n        metavar='URL',\n        action='append',\n        default=[],\n        help=\"Extra URLs of package indexes to use in addition to \"\n             \"--index-url. Should follow the same rules as \"\n             \"--index-url.\",\n    )\n\n\nno_index = partial(\n    Option,\n    '--no-index',\n    dest='no_index',\n    action='store_true',\n    default=False,\n    help='Ignore package index (only looking at --find-links URLs instead).',\n)  # type: Callable[..., Option]\n\n\ndef find_links():\n    # type: () -> Option\n    return Option(\n        '-f', '--find-links',\n        dest='find_links',\n        action='append',\n        default=[],\n        metavar='url',\n        help=\"If a url or path to an html file, then parse for links to \"\n             \"archives. If a local path or file:// url that's a directory, \"\n             \"then look for archives in the directory listing.\",\n    )\n\n\ndef trusted_host():\n    # type: () -> Option\n    return Option(\n        \"--trusted-host\",\n        dest=\"trusted_hosts\",\n        action=\"append\",\n        metavar=\"HOSTNAME\",\n        default=[],\n        help=\"Mark this host as trusted, even though it does not have valid \"\n             \"or any HTTPS.\",\n    )\n\n\ndef constraints():\n    # type: () -> Option\n    return Option(\n        '-c', '--constraint',\n        dest='constraints',\n        action='append',\n        default=[],\n        metavar='file',\n        help='Constrain versions using the given constraints file. '\n        'This option can be used multiple times.'\n    )\n\n\ndef requirements():\n    # type: () -> Option\n    return Option(\n        '-r', '--requirement',\n        dest='requirements',\n        action='append',\n        default=[],\n        metavar='file',\n        help='Install from the given requirements file. '\n        'This option can be used multiple times.'\n    )\n\n\ndef editable():\n    # type: () -> Option\n    return Option(\n        '-e', '--editable',\n        dest='editables',\n        action='append',\n        default=[],\n        metavar='path/url',\n        help=('Install a project in editable mode (i.e. setuptools '\n              '\"develop mode\") from a local project path or a VCS url.'),\n    )\n\n\nsrc = partial(\n    Option,\n    '--src', '--source', '--source-dir', '--source-directory',\n    dest='src_dir',\n    metavar='dir',\n    default=src_prefix,\n    help='Directory to check out editable projects into. '\n    'The default in a virtualenv is \"<venv path>/src\". '\n    'The default for global installs is \"<current dir>/src\".'\n)  # type: Callable[..., Option]\n\n\ndef _get_format_control(values, option):\n    # type: (Values, Option) -> Any\n    \"\"\"Get a format_control object.\"\"\"\n    return getattr(values, option.dest)\n\n\ndef _handle_no_binary(option, opt_str, value, parser):\n    # type: (Option, str, str, OptionParser) -> None\n    existing = _get_format_control(parser.values, option)\n    FormatControl.handle_mutual_excludes(\n        value, existing.no_binary, existing.only_binary,\n    )\n\n\ndef _handle_only_binary(option, opt_str, value, parser):\n    # type: (Option, str, str, OptionParser) -> None\n    existing = _get_format_control(parser.values, option)\n    FormatControl.handle_mutual_excludes(\n        value, existing.only_binary, existing.no_binary,\n    )\n\n\ndef no_binary():\n    # type: () -> Option\n    format_control = FormatControl(set(), set())\n    return Option(\n        \"--no-binary\", dest=\"format_control\", action=\"callback\",\n        callback=_handle_no_binary, type=\"str\",\n        default=format_control,\n        help=\"Do not use binary packages. Can be supplied multiple times, and \"\n             \"each time adds to the existing value. Accepts either :all: to \"\n             \"disable all binary packages, :none: to empty the set, or one or \"\n             \"more package names with commas between them. Note that some \"\n             \"packages are tricky to compile and may fail to install when \"\n             \"this option is used on them.\",\n    )\n\n\ndef only_binary():\n    # type: () -> Option\n    format_control = FormatControl(set(), set())\n    return Option(\n        \"--only-binary\", dest=\"format_control\", action=\"callback\",\n        callback=_handle_only_binary, type=\"str\",\n        default=format_control,\n        help=\"Do not use source packages. Can be supplied multiple times, and \"\n             \"each time adds to the existing value. Accepts either :all: to \"\n             \"disable all source packages, :none: to empty the set, or one or \"\n             \"more package names with commas between them. Packages without \"\n             \"binary distributions will fail to install when this option is \"\n             \"used on them.\",\n    )\n\n\nplatform = partial(\n    Option,\n    '--platform',\n    dest='platform',\n    metavar='platform',\n    default=None,\n    help=(\"Only use wheels compatible with <platform>. \"\n          \"Defaults to the platform of the running system.\"),\n)  # type: Callable[..., Option]\n\n\npython_version = partial(\n    Option,\n    '--python-version',\n    dest='python_version',\n    metavar='python_version',\n    default=None,\n    help=(\"Only use wheels compatible with Python \"\n          \"interpreter version <version>. If not specified, then the \"\n          \"current system interpreter minor version is used. A major \"\n          \"version (e.g. '2') can be specified to match all \"\n          \"minor revs of that major version.  A minor version \"\n          \"(e.g. '34') can also be specified.\"),\n)  # type: Callable[..., Option]\n\n\nimplementation = partial(\n    Option,\n    '--implementation',\n    dest='implementation',\n    metavar='implementation',\n    default=None,\n    help=(\"Only use wheels compatible with Python \"\n          \"implementation <implementation>, e.g. 'pp', 'jy', 'cp', \"\n          \" or 'ip'. If not specified, then the current \"\n          \"interpreter implementation is used.  Use 'py' to force \"\n          \"implementation-agnostic wheels.\"),\n)  # type: Callable[..., Option]\n\n\nabi = partial(\n    Option,\n    '--abi',\n    dest='abi',\n    metavar='abi',\n    default=None,\n    help=(\"Only use wheels compatible with Python \"\n          \"abi <abi>, e.g. 'pypy_41'.  If not specified, then the \"\n          \"current interpreter abi tag is used.  Generally \"\n          \"you will need to specify --implementation, \"\n          \"--platform, and --python-version when using \"\n          \"this option.\"),\n)  # type: Callable[..., Option]\n\n\ndef prefer_binary():\n    # type: () -> Option\n    return Option(\n        \"--prefer-binary\",\n        dest=\"prefer_binary\",\n        action=\"store_true\",\n        default=False,\n        help=\"Prefer older binary packages over newer source packages.\"\n    )\n\n\ncache_dir = partial(\n    Option,\n    \"--cache-dir\",\n    dest=\"cache_dir\",\n    default=USER_CACHE_DIR,\n    metavar=\"dir\",\n    help=\"Store the cache data in <dir>.\"\n)  # type: Callable[..., Option]\n\n\ndef no_cache_dir_callback(option, opt, value, parser):\n    \"\"\"\n    Process a value provided for the --no-cache-dir option.\n\n    This is an optparse.Option callback for the --no-cache-dir option.\n    \"\"\"\n    # The value argument will be None if --no-cache-dir is passed via the\n    # command-line, since the option doesn't accept arguments.  However,\n    # the value can be non-None if the option is triggered e.g. by an\n    # environment variable, like PIP_NO_CACHE_DIR=true.\n    if value is not None:\n        # Then parse the string value to get argument error-checking.\n        try:\n            strtobool(value)\n        except ValueError as exc:\n            raise_option_error(parser, option=option, msg=str(exc))\n\n    # Originally, setting PIP_NO_CACHE_DIR to a value that strtobool()\n    # converted to 0 (like \"false\" or \"no\") caused cache_dir to be disabled\n    # rather than enabled (logic would say the latter).  Thus, we disable\n    # the cache directory not just on values that parse to True, but (for\n    # backwards compatibility reasons) also on values that parse to False.\n    # In other words, always set it to False if the option is provided in\n    # some (valid) form.\n    parser.values.cache_dir = False\n\n\nno_cache = partial(\n    Option,\n    \"--no-cache-dir\",\n    dest=\"cache_dir\",\n    action=\"callback\",\n    callback=no_cache_dir_callback,\n    help=\"Disable the cache.\",\n)  # type: Callable[..., Option]\n\nno_deps = partial(\n    Option,\n    '--no-deps', '--no-dependencies',\n    dest='ignore_dependencies',\n    action='store_true',\n    default=False,\n    help=\"Don't install package dependencies.\",\n)  # type: Callable[..., Option]\n\nbuild_dir = partial(\n    Option,\n    '-b', '--build', '--build-dir', '--build-directory',\n    dest='build_dir',\n    metavar='dir',\n    help='Directory to unpack packages into and build in. Note that '\n         'an initial build still takes place in a temporary directory. '\n         'The location of temporary directories can be controlled by setting '\n         'the TMPDIR environment variable (TEMP on Windows) appropriately. '\n         'When passed, build directories are not cleaned in case of failures.'\n)  # type: Callable[..., Option]\n\nignore_requires_python = partial(\n    Option,\n    '--ignore-requires-python',\n    dest='ignore_requires_python',\n    action='store_true',\n    help='Ignore the Requires-Python information.'\n)  # type: Callable[..., Option]\n\nno_build_isolation = partial(\n    Option,\n    '--no-build-isolation',\n    dest='build_isolation',\n    action='store_false',\n    default=True,\n    help='Disable isolation when building a modern source distribution. '\n         'Build dependencies specified by PEP 518 must be already installed '\n         'if this option is used.'\n)  # type: Callable[..., Option]\n\n\ndef no_use_pep517_callback(option, opt, value, parser):\n    \"\"\"\n    Process a value provided for the --no-use-pep517 option.\n\n    This is an optparse.Option callback for the no_use_pep517 option.\n    \"\"\"\n    # Since --no-use-pep517 doesn't accept arguments, the value argument\n    # will be None if --no-use-pep517 is passed via the command-line.\n    # However, the value can be non-None if the option is triggered e.g.\n    # by an environment variable, for example \"PIP_NO_USE_PEP517=true\".\n    if value is not None:\n        msg = \"\"\"A value was passed for --no-use-pep517,\n        probably using either the PIP_NO_USE_PEP517 environment variable\n        or the \"no-use-pep517\" config file option. Use an appropriate value\n        of the PIP_USE_PEP517 environment variable or the \"use-pep517\"\n        config file option instead.\n        \"\"\"\n        raise_option_error(parser, option=option, msg=msg)\n\n    # Otherwise, --no-use-pep517 was passed via the command-line.\n    parser.values.use_pep517 = False\n\n\nuse_pep517 = partial(\n    Option,\n    '--use-pep517',\n    dest='use_pep517',\n    action='store_true',\n    default=None,\n    help='Use PEP 517 for building source distributions '\n         '(use --no-use-pep517 to force legacy behaviour).'\n)  # type: Any\n\nno_use_pep517 = partial(\n    Option,\n    '--no-use-pep517',\n    dest='use_pep517',\n    action='callback',\n    callback=no_use_pep517_callback,\n    default=None,\n    help=SUPPRESS_HELP\n)  # type: Any\n\ninstall_options = partial(\n    Option,\n    '--install-option',\n    dest='install_options',\n    action='append',\n    metavar='options',\n    help=\"Extra arguments to be supplied to the setup.py install \"\n         \"command (use like --install-option=\\\"--install-scripts=/usr/local/\"\n         \"bin\\\"). Use multiple --install-option options to pass multiple \"\n         \"options to setup.py install. If you are using an option with a \"\n         \"directory path, be sure to use absolute path.\",\n)  # type: Callable[..., Option]\n\nglobal_options = partial(\n    Option,\n    '--global-option',\n    dest='global_options',\n    action='append',\n    metavar='options',\n    help=\"Extra global options to be supplied to the setup.py \"\n         \"call before the install command.\",\n)  # type: Callable[..., Option]\n\nno_clean = partial(\n    Option,\n    '--no-clean',\n    action='store_true',\n    default=False,\n    help=\"Don't clean up build directories.\"\n)  # type: Callable[..., Option]\n\npre = partial(\n    Option,\n    '--pre',\n    action='store_true',\n    default=False,\n    help=\"Include pre-release and development versions. By default, \"\n         \"pip only finds stable versions.\",\n)  # type: Callable[..., Option]\n\ndisable_pip_version_check = partial(\n    Option,\n    \"--disable-pip-version-check\",\n    dest=\"disable_pip_version_check\",\n    action=\"store_true\",\n    default=False,\n    help=\"Don't periodically check PyPI to determine whether a new version \"\n         \"of pip is available for download. Implied with --no-index.\",\n)  # type: Callable[..., Option]\n\n\n# Deprecated, Remove later\nalways_unzip = partial(\n    Option,\n    '-Z', '--always-unzip',\n    dest='always_unzip',\n    action='store_true',\n    help=SUPPRESS_HELP,\n)  # type: Callable[..., Option]\n\n\ndef _merge_hash(option, opt_str, value, parser):\n    # type: (Option, str, str, OptionParser) -> None\n    \"\"\"Given a value spelled \"algo:digest\", append the digest to a list\n    pointed to in a dict by the algo name.\"\"\"\n    if not parser.values.hashes:\n        parser.values.hashes = {}  # type: ignore\n    try:\n        algo, digest = value.split(':', 1)\n    except ValueError:\n        parser.error('Arguments to %s must be a hash name '\n                     'followed by a value, like --hash=sha256:abcde...' %\n                     opt_str)\n    if algo not in STRONG_HASHES:\n        parser.error('Allowed hash algorithms for %s are %s.' %\n                     (opt_str, ', '.join(STRONG_HASHES)))\n    parser.values.hashes.setdefault(algo, []).append(digest)\n\n\nhash = partial(\n    Option,\n    '--hash',\n    # Hash values eventually end up in InstallRequirement.hashes due to\n    # __dict__ copying in process_line().\n    dest='hashes',\n    action='callback',\n    callback=_merge_hash,\n    type='string',\n    help=\"Verify that the package's archive matches this \"\n         'hash before installing. Example: --hash=sha256:abcdef...',\n)  # type: Callable[..., Option]\n\n\nrequire_hashes = partial(\n    Option,\n    '--require-hashes',\n    dest='require_hashes',\n    action='store_true',\n    default=False,\n    help='Require a hash to check each requirement against, for '\n         'repeatable installs. This option is implied when any package in a '\n         'requirements file has a --hash option.',\n)  # type: Callable[..., Option]\n\n\n##########\n# groups #\n##########\n\ngeneral_group = {\n    'name': 'General Options',\n    'options': [\n        help_,\n        isolated_mode,\n        require_virtualenv,\n        verbose,\n        version,\n        quiet,\n        log,\n        no_input,\n        proxy,\n        retries,\n        timeout,\n        skip_requirements_regex,\n        exists_action,\n        trusted_host,\n        cert,\n        client_cert,\n        cache_dir,\n        no_cache,\n        disable_pip_version_check,\n        no_color,\n    ]\n}  # type: Dict[str, Any]\n\nindex_group = {\n    'name': 'Package Index Options',\n    'options': [\n        index_url,\n        extra_index_url,\n        no_index,\n        find_links,\n    ]\n}  # type: Dict[str, Any]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/cli/main_parser.py",
    "content": "\"\"\"A single place for constructing and exposing the main parser\n\"\"\"\n\nimport os\nimport sys\n\nfrom pip import __version__\nfrom pip._internal.cli import cmdoptions\nfrom pip._internal.cli.parser import (\n    ConfigOptionParser, UpdatingDefaultsHelpFormatter,\n)\nfrom pip._internal.commands import (\n    commands_dict, get_similar_commands, get_summaries,\n)\nfrom pip._internal.exceptions import CommandError\nfrom pip._internal.utils.misc import get_prog\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Tuple, List  # noqa: F401\n\n\n__all__ = [\"create_main_parser\", \"parse_command\"]\n\n\ndef create_main_parser():\n    # type: () -> ConfigOptionParser\n    \"\"\"Creates and returns the main parser for pip's CLI\n    \"\"\"\n\n    parser_kw = {\n        'usage': '\\n%prog <command> [options]',\n        'add_help_option': False,\n        'formatter': UpdatingDefaultsHelpFormatter(),\n        'name': 'global',\n        'prog': get_prog(),\n    }\n\n    parser = ConfigOptionParser(**parser_kw)\n    parser.disable_interspersed_args()\n\n    pip_pkg_dir = os.path.abspath(os.path.join(\n        os.path.dirname(__file__), \"..\", \"..\",\n    ))\n    parser.version = 'pip %s from %s (python %s)' % (\n        __version__, pip_pkg_dir, sys.version[:3],\n    )\n\n    # add the general options\n    gen_opts = cmdoptions.make_option_group(cmdoptions.general_group, parser)\n    parser.add_option_group(gen_opts)\n\n    # so the help formatter knows\n    parser.main = True  # type: ignore\n\n    # create command listing for description\n    command_summaries = get_summaries()\n    description = [''] + ['%-27s %s' % (i, j) for i, j in command_summaries]\n    parser.description = '\\n'.join(description)\n\n    return parser\n\n\ndef parse_command(args):\n    # type: (List[str]) -> Tuple[str, List[str]]\n    parser = create_main_parser()\n\n    # Note: parser calls disable_interspersed_args(), so the result of this\n    # call is to split the initial args into the general options before the\n    # subcommand and everything else.\n    # For example:\n    #  args: ['--timeout=5', 'install', '--user', 'INITools']\n    #  general_options: ['--timeout==5']\n    #  args_else: ['install', '--user', 'INITools']\n    general_options, args_else = parser.parse_args(args)\n\n    # --version\n    if general_options.version:\n        sys.stdout.write(parser.version)  # type: ignore\n        sys.stdout.write(os.linesep)\n        sys.exit()\n\n    # pip || pip help -> print_help()\n    if not args_else or (args_else[0] == 'help' and len(args_else) == 1):\n        parser.print_help()\n        sys.exit()\n\n    # the subcommand name\n    cmd_name = args_else[0]\n\n    if cmd_name not in commands_dict:\n        guess = get_similar_commands(cmd_name)\n\n        msg = ['unknown command \"%s\"' % cmd_name]\n        if guess:\n            msg.append('maybe you meant \"%s\"' % guess)\n\n        raise CommandError(' - '.join(msg))\n\n    # all the args without the subcommand\n    cmd_args = args[:]\n    cmd_args.remove(cmd_name)\n\n    return cmd_name, cmd_args\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/cli/parser.py",
    "content": "\"\"\"Base option parser setup\"\"\"\nfrom __future__ import absolute_import\n\nimport logging\nimport optparse\nimport sys\nimport textwrap\nfrom distutils.util import strtobool\n\nfrom pip._vendor.six import string_types\n\nfrom pip._internal.cli.status_codes import UNKNOWN_ERROR\nfrom pip._internal.configuration import Configuration, ConfigurationError\nfrom pip._internal.utils.compat import get_terminal_size\n\nlogger = logging.getLogger(__name__)\n\n\nclass PrettyHelpFormatter(optparse.IndentedHelpFormatter):\n    \"\"\"A prettier/less verbose help formatter for optparse.\"\"\"\n\n    def __init__(self, *args, **kwargs):\n        # help position must be aligned with __init__.parseopts.description\n        kwargs['max_help_position'] = 30\n        kwargs['indent_increment'] = 1\n        kwargs['width'] = get_terminal_size()[0] - 2\n        optparse.IndentedHelpFormatter.__init__(self, *args, **kwargs)\n\n    def format_option_strings(self, option):\n        return self._format_option_strings(option, ' <%s>', ', ')\n\n    def _format_option_strings(self, option, mvarfmt=' <%s>', optsep=', '):\n        \"\"\"\n        Return a comma-separated list of option strings and metavars.\n\n        :param option:  tuple of (short opt, long opt), e.g: ('-f', '--format')\n        :param mvarfmt: metavar format string - evaluated as mvarfmt % metavar\n        :param optsep:  separator\n        \"\"\"\n        opts = []\n\n        if option._short_opts:\n            opts.append(option._short_opts[0])\n        if option._long_opts:\n            opts.append(option._long_opts[0])\n        if len(opts) > 1:\n            opts.insert(1, optsep)\n\n        if option.takes_value():\n            metavar = option.metavar or option.dest.lower()\n            opts.append(mvarfmt % metavar.lower())\n\n        return ''.join(opts)\n\n    def format_heading(self, heading):\n        if heading == 'Options':\n            return ''\n        return heading + ':\\n'\n\n    def format_usage(self, usage):\n        \"\"\"\n        Ensure there is only one newline between usage and the first heading\n        if there is no description.\n        \"\"\"\n        msg = '\\nUsage: %s\\n' % self.indent_lines(textwrap.dedent(usage), \"  \")\n        return msg\n\n    def format_description(self, description):\n        # leave full control over description to us\n        if description:\n            if hasattr(self.parser, 'main'):\n                label = 'Commands'\n            else:\n                label = 'Description'\n            # some doc strings have initial newlines, some don't\n            description = description.lstrip('\\n')\n            # some doc strings have final newlines and spaces, some don't\n            description = description.rstrip()\n            # dedent, then reindent\n            description = self.indent_lines(textwrap.dedent(description), \"  \")\n            description = '%s:\\n%s\\n' % (label, description)\n            return description\n        else:\n            return ''\n\n    def format_epilog(self, epilog):\n        # leave full control over epilog to us\n        if epilog:\n            return epilog\n        else:\n            return ''\n\n    def indent_lines(self, text, indent):\n        new_lines = [indent + line for line in text.split('\\n')]\n        return \"\\n\".join(new_lines)\n\n\nclass UpdatingDefaultsHelpFormatter(PrettyHelpFormatter):\n    \"\"\"Custom help formatter for use in ConfigOptionParser.\n\n    This is updates the defaults before expanding them, allowing\n    them to show up correctly in the help listing.\n    \"\"\"\n\n    def expand_default(self, option):\n        if self.parser is not None:\n            self.parser._update_defaults(self.parser.defaults)\n        return optparse.IndentedHelpFormatter.expand_default(self, option)\n\n\nclass CustomOptionParser(optparse.OptionParser):\n\n    def insert_option_group(self, idx, *args, **kwargs):\n        \"\"\"Insert an OptionGroup at a given position.\"\"\"\n        group = self.add_option_group(*args, **kwargs)\n\n        self.option_groups.pop()\n        self.option_groups.insert(idx, group)\n\n        return group\n\n    @property\n    def option_list_all(self):\n        \"\"\"Get a list of all options, including those in option groups.\"\"\"\n        res = self.option_list[:]\n        for i in self.option_groups:\n            res.extend(i.option_list)\n\n        return res\n\n\nclass ConfigOptionParser(CustomOptionParser):\n    \"\"\"Custom option parser which updates its defaults by checking the\n    configuration files and environmental variables\"\"\"\n\n    def __init__(self, *args, **kwargs):\n        self.name = kwargs.pop('name')\n\n        isolated = kwargs.pop(\"isolated\", False)\n        self.config = Configuration(isolated)\n\n        assert self.name\n        optparse.OptionParser.__init__(self, *args, **kwargs)\n\n    def check_default(self, option, key, val):\n        try:\n            return option.check_value(key, val)\n        except optparse.OptionValueError as exc:\n            print(\"An error occurred during configuration: %s\" % exc)\n            sys.exit(3)\n\n    def _get_ordered_configuration_items(self):\n        # Configuration gives keys in an unordered manner. Order them.\n        override_order = [\"global\", self.name, \":env:\"]\n\n        # Pool the options into different groups\n        section_items = {name: [] for name in override_order}\n        for section_key, val in self.config.items():\n            # ignore empty values\n            if not val:\n                logger.debug(\n                    \"Ignoring configuration key '%s' as it's value is empty.\",\n                    section_key\n                )\n                continue\n\n            section, key = section_key.split(\".\", 1)\n            if section in override_order:\n                section_items[section].append((key, val))\n\n        # Yield each group in their override order\n        for section in override_order:\n            for key, val in section_items[section]:\n                yield key, val\n\n    def _update_defaults(self, defaults):\n        \"\"\"Updates the given defaults with values from the config files and\n        the environ. Does a little special handling for certain types of\n        options (lists).\"\"\"\n\n        # Accumulate complex default state.\n        self.values = optparse.Values(self.defaults)\n        late_eval = set()\n        # Then set the options with those values\n        for key, val in self._get_ordered_configuration_items():\n            # '--' because configuration supports only long names\n            option = self.get_option('--' + key)\n\n            # Ignore options not present in this parser. E.g. non-globals put\n            # in [global] by users that want them to apply to all applicable\n            # commands.\n            if option is None:\n                continue\n\n            if option.action in ('store_true', 'store_false', 'count'):\n                try:\n                    val = strtobool(val)\n                except ValueError:\n                    error_msg = invalid_config_error_message(\n                        option.action, key, val\n                    )\n                    self.error(error_msg)\n\n            elif option.action == 'append':\n                val = val.split()\n                val = [self.check_default(option, key, v) for v in val]\n            elif option.action == 'callback':\n                late_eval.add(option.dest)\n                opt_str = option.get_opt_string()\n                val = option.convert_value(opt_str, val)\n                # From take_action\n                args = option.callback_args or ()\n                kwargs = option.callback_kwargs or {}\n                option.callback(option, opt_str, val, self, *args, **kwargs)\n            else:\n                val = self.check_default(option, key, val)\n\n            defaults[option.dest] = val\n\n        for key in late_eval:\n            defaults[key] = getattr(self.values, key)\n        self.values = None\n        return defaults\n\n    def get_default_values(self):\n        \"\"\"Overriding to make updating the defaults after instantiation of\n        the option parser possible, _update_defaults() does the dirty work.\"\"\"\n        if not self.process_default_values:\n            # Old, pre-Optik 1.5 behaviour.\n            return optparse.Values(self.defaults)\n\n        # Load the configuration, or error out in case of an error\n        try:\n            self.config.load()\n        except ConfigurationError as err:\n            self.exit(UNKNOWN_ERROR, str(err))\n\n        defaults = self._update_defaults(self.defaults.copy())  # ours\n        for option in self._get_all_options():\n            default = defaults.get(option.dest)\n            if isinstance(default, string_types):\n                opt_str = option.get_opt_string()\n                defaults[option.dest] = option.check_value(opt_str, default)\n        return optparse.Values(defaults)\n\n    def error(self, msg):\n        self.print_usage(sys.stderr)\n        self.exit(UNKNOWN_ERROR, \"%s\\n\" % msg)\n\n\ndef invalid_config_error_message(action, key, val):\n    \"\"\"Returns a better error message when invalid configuration option\n    is provided.\"\"\"\n    if action in ('store_true', 'store_false'):\n        return (\"{0} is not a valid value for {1} option, \"\n                \"please specify a boolean value like yes/no, \"\n                \"true/false or 1/0 instead.\").format(val, key)\n\n    return (\"{0} is not a valid value for {1} option, \"\n            \"please specify a numerical value like 1/0 \"\n            \"instead.\").format(val, key)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/cli/status_codes.py",
    "content": "from __future__ import absolute_import\n\nSUCCESS = 0\nERROR = 1\nUNKNOWN_ERROR = 2\nVIRTUALENV_NOT_FOUND = 3\nPREVIOUS_BUILD_DIR_ERROR = 4\nNO_MATCHES_FOUND = 23\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/__init__.py",
    "content": "\"\"\"\nPackage containing all pip commands\n\"\"\"\nfrom __future__ import absolute_import\n\nfrom pip._internal.commands.completion import CompletionCommand\nfrom pip._internal.commands.configuration import ConfigurationCommand\nfrom pip._internal.commands.download import DownloadCommand\nfrom pip._internal.commands.freeze import FreezeCommand\nfrom pip._internal.commands.hash import HashCommand\nfrom pip._internal.commands.help import HelpCommand\nfrom pip._internal.commands.list import ListCommand\nfrom pip._internal.commands.check import CheckCommand\nfrom pip._internal.commands.search import SearchCommand\nfrom pip._internal.commands.show import ShowCommand\nfrom pip._internal.commands.install import InstallCommand\nfrom pip._internal.commands.uninstall import UninstallCommand\nfrom pip._internal.commands.wheel import WheelCommand\n\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import List, Type  # noqa: F401\n    from pip._internal.cli.base_command import Command  # noqa: F401\n\ncommands_order = [\n    InstallCommand,\n    DownloadCommand,\n    UninstallCommand,\n    FreezeCommand,\n    ListCommand,\n    ShowCommand,\n    CheckCommand,\n    ConfigurationCommand,\n    SearchCommand,\n    WheelCommand,\n    HashCommand,\n    CompletionCommand,\n    HelpCommand,\n]  # type: List[Type[Command]]\n\ncommands_dict = {c.name: c for c in commands_order}\n\n\ndef get_summaries(ordered=True):\n    \"\"\"Yields sorted (command name, command summary) tuples.\"\"\"\n\n    if ordered:\n        cmditems = _sort_commands(commands_dict, commands_order)\n    else:\n        cmditems = commands_dict.items()\n\n    for name, command_class in cmditems:\n        yield (name, command_class.summary)\n\n\ndef get_similar_commands(name):\n    \"\"\"Command name auto-correct.\"\"\"\n    from difflib import get_close_matches\n\n    name = name.lower()\n\n    close_commands = get_close_matches(name, commands_dict.keys())\n\n    if close_commands:\n        return close_commands[0]\n    else:\n        return False\n\n\ndef _sort_commands(cmddict, order):\n    def keyfn(key):\n        try:\n            return order.index(key[1])\n        except ValueError:\n            # unordered items should come last\n            return 0xff\n\n    return sorted(cmddict.items(), key=keyfn)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/check.py",
    "content": "import logging\n\nfrom pip._internal.cli.base_command import Command\nfrom pip._internal.operations.check import (\n    check_package_set, create_package_set_from_installed,\n)\n\nlogger = logging.getLogger(__name__)\n\n\nclass CheckCommand(Command):\n    \"\"\"Verify installed packages have compatible dependencies.\"\"\"\n    name = 'check'\n    usage = \"\"\"\n      %prog [options]\"\"\"\n    summary = 'Verify installed packages have compatible dependencies.'\n\n    def run(self, options, args):\n        package_set, parsing_probs = create_package_set_from_installed()\n        missing, conflicting = check_package_set(package_set)\n\n        for project_name in missing:\n            version = package_set[project_name].version\n            for dependency in missing[project_name]:\n                logger.info(\n                    \"%s %s requires %s, which is not installed.\",\n                    project_name, version, dependency[0],\n                )\n\n        for project_name in conflicting:\n            version = package_set[project_name].version\n            for dep_name, dep_version, req in conflicting[project_name]:\n                logger.info(\n                    \"%s %s has requirement %s, but you have %s %s.\",\n                    project_name, version, req, dep_name, dep_version,\n                )\n\n        if missing or conflicting or parsing_probs:\n            return 1\n        else:\n            logger.info(\"No broken requirements found.\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/completion.py",
    "content": "from __future__ import absolute_import\n\nimport sys\nimport textwrap\n\nfrom pip._internal.cli.base_command import Command\nfrom pip._internal.utils.misc import get_prog\n\nBASE_COMPLETION = \"\"\"\n# pip %(shell)s completion start%(script)s# pip %(shell)s completion end\n\"\"\"\n\nCOMPLETION_SCRIPTS = {\n    'bash': \"\"\"\n        _pip_completion()\n        {\n            COMPREPLY=( $( COMP_WORDS=\"${COMP_WORDS[*]}\" \\\\\n                           COMP_CWORD=$COMP_CWORD \\\\\n                           PIP_AUTO_COMPLETE=1 $1 ) )\n        }\n        complete -o default -F _pip_completion %(prog)s\n    \"\"\",\n    'zsh': \"\"\"\n        function _pip_completion {\n          local words cword\n          read -Ac words\n          read -cn cword\n          reply=( $( COMP_WORDS=\"$words[*]\" \\\\\n                     COMP_CWORD=$(( cword-1 )) \\\\\n                     PIP_AUTO_COMPLETE=1 $words[1] ) )\n        }\n        compctl -K _pip_completion %(prog)s\n    \"\"\",\n    'fish': \"\"\"\n        function __fish_complete_pip\n            set -lx COMP_WORDS (commandline -o) \"\"\n            set -lx COMP_CWORD ( \\\\\n                math (contains -i -- (commandline -t) $COMP_WORDS)-1 \\\\\n            )\n            set -lx PIP_AUTO_COMPLETE 1\n            string split \\\\  -- (eval $COMP_WORDS[1])\n        end\n        complete -fa \"(__fish_complete_pip)\" -c %(prog)s\n    \"\"\",\n}\n\n\nclass CompletionCommand(Command):\n    \"\"\"A helper command to be used for command completion.\"\"\"\n    name = 'completion'\n    summary = 'A helper command used for command completion.'\n    ignore_require_venv = True\n\n    def __init__(self, *args, **kw):\n        super(CompletionCommand, self).__init__(*args, **kw)\n\n        cmd_opts = self.cmd_opts\n\n        cmd_opts.add_option(\n            '--bash', '-b',\n            action='store_const',\n            const='bash',\n            dest='shell',\n            help='Emit completion code for bash')\n        cmd_opts.add_option(\n            '--zsh', '-z',\n            action='store_const',\n            const='zsh',\n            dest='shell',\n            help='Emit completion code for zsh')\n        cmd_opts.add_option(\n            '--fish', '-f',\n            action='store_const',\n            const='fish',\n            dest='shell',\n            help='Emit completion code for fish')\n\n        self.parser.insert_option_group(0, cmd_opts)\n\n    def run(self, options, args):\n        \"\"\"Prints the completion code of the given shell\"\"\"\n        shells = COMPLETION_SCRIPTS.keys()\n        shell_options = ['--' + shell for shell in sorted(shells)]\n        if options.shell in shells:\n            script = textwrap.dedent(\n                COMPLETION_SCRIPTS.get(options.shell, '') % {\n                    'prog': get_prog(),\n                }\n            )\n            print(BASE_COMPLETION % {'script': script, 'shell': options.shell})\n        else:\n            sys.stderr.write(\n                'ERROR: You must pass %s\\n' % ' or '.join(shell_options)\n            )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/configuration.py",
    "content": "import logging\nimport os\nimport subprocess\n\nfrom pip._internal.cli.base_command import Command\nfrom pip._internal.cli.status_codes import ERROR, SUCCESS\nfrom pip._internal.configuration import Configuration, kinds\nfrom pip._internal.exceptions import PipError\nfrom pip._internal.locations import venv_config_file\nfrom pip._internal.utils.misc import get_prog\n\nlogger = logging.getLogger(__name__)\n\n\nclass ConfigurationCommand(Command):\n    \"\"\"Manage local and global configuration.\n\n        Subcommands:\n\n        list: List the active configuration (or from the file specified)\n        edit: Edit the configuration file in an editor\n        get: Get the value associated with name\n        set: Set the name=value\n        unset: Unset the value associated with name\n\n        If none of --user, --global and --venv are passed, a virtual\n        environment configuration file is used if one is active and the file\n        exists. Otherwise, all modifications happen on the to the user file by\n        default.\n    \"\"\"\n\n    name = 'config'\n    usage = \"\"\"\n        %prog [<file-option>] list\n        %prog [<file-option>] [--editor <editor-path>] edit\n\n        %prog [<file-option>] get name\n        %prog [<file-option>] set name value\n        %prog [<file-option>] unset name\n    \"\"\"\n\n    summary = \"Manage local and global configuration.\"\n\n    def __init__(self, *args, **kwargs):\n        super(ConfigurationCommand, self).__init__(*args, **kwargs)\n\n        self.configuration = None\n\n        self.cmd_opts.add_option(\n            '--editor',\n            dest='editor',\n            action='store',\n            default=None,\n            help=(\n                'Editor to use to edit the file. Uses VISUAL or EDITOR '\n                'environment variables if not provided.'\n            )\n        )\n\n        self.cmd_opts.add_option(\n            '--global',\n            dest='global_file',\n            action='store_true',\n            default=False,\n            help='Use the system-wide configuration file only'\n        )\n\n        self.cmd_opts.add_option(\n            '--user',\n            dest='user_file',\n            action='store_true',\n            default=False,\n            help='Use the user configuration file only'\n        )\n\n        self.cmd_opts.add_option(\n            '--venv',\n            dest='venv_file',\n            action='store_true',\n            default=False,\n            help='Use the virtualenv configuration file only'\n        )\n\n        self.parser.insert_option_group(0, self.cmd_opts)\n\n    def run(self, options, args):\n        handlers = {\n            \"list\": self.list_values,\n            \"edit\": self.open_in_editor,\n            \"get\": self.get_name,\n            \"set\": self.set_name_value,\n            \"unset\": self.unset_name\n        }\n\n        # Determine action\n        if not args or args[0] not in handlers:\n            logger.error(\"Need an action ({}) to perform.\".format(\n                \", \".join(sorted(handlers)))\n            )\n            return ERROR\n\n        action = args[0]\n\n        # Determine which configuration files are to be loaded\n        #    Depends on whether the command is modifying.\n        try:\n            load_only = self._determine_file(\n                options, need_value=(action in [\"get\", \"set\", \"unset\", \"edit\"])\n            )\n        except PipError as e:\n            logger.error(e.args[0])\n            return ERROR\n\n        # Load a new configuration\n        self.configuration = Configuration(\n            isolated=options.isolated_mode, load_only=load_only\n        )\n        self.configuration.load()\n\n        # Error handling happens here, not in the action-handlers.\n        try:\n            handlers[action](options, args[1:])\n        except PipError as e:\n            logger.error(e.args[0])\n            return ERROR\n\n        return SUCCESS\n\n    def _determine_file(self, options, need_value):\n        file_options = {\n            kinds.USER: options.user_file,\n            kinds.GLOBAL: options.global_file,\n            kinds.VENV: options.venv_file\n        }\n\n        if sum(file_options.values()) == 0:\n            if not need_value:\n                return None\n            # Default to user, unless there's a virtualenv file.\n            elif os.path.exists(venv_config_file):\n                return kinds.VENV\n            else:\n                return kinds.USER\n        elif sum(file_options.values()) == 1:\n            # There's probably a better expression for this.\n            return [key for key in file_options if file_options[key]][0]\n\n        raise PipError(\n            \"Need exactly one file to operate upon \"\n            \"(--user, --venv, --global) to perform.\"\n        )\n\n    def list_values(self, options, args):\n        self._get_n_args(args, \"list\", n=0)\n\n        for key, value in sorted(self.configuration.items()):\n            logger.info(\"%s=%r\", key, value)\n\n    def get_name(self, options, args):\n        key = self._get_n_args(args, \"get [name]\", n=1)\n        value = self.configuration.get_value(key)\n\n        logger.info(\"%s\", value)\n\n    def set_name_value(self, options, args):\n        key, value = self._get_n_args(args, \"set [name] [value]\", n=2)\n        self.configuration.set_value(key, value)\n\n        self._save_configuration()\n\n    def unset_name(self, options, args):\n        key = self._get_n_args(args, \"unset [name]\", n=1)\n        self.configuration.unset_value(key)\n\n        self._save_configuration()\n\n    def open_in_editor(self, options, args):\n        editor = self._determine_editor(options)\n\n        fname = self.configuration.get_file_to_edit()\n        if fname is None:\n            raise PipError(\"Could not determine appropriate file.\")\n\n        try:\n            subprocess.check_call([editor, fname])\n        except subprocess.CalledProcessError as e:\n            raise PipError(\n                \"Editor Subprocess exited with exit code {}\"\n                .format(e.returncode)\n            )\n\n    def _get_n_args(self, args, example, n):\n        \"\"\"Helper to make sure the command got the right number of arguments\n        \"\"\"\n        if len(args) != n:\n            msg = (\n                'Got unexpected number of arguments, expected {}. '\n                '(example: \"{} config {}\")'\n            ).format(n, get_prog(), example)\n            raise PipError(msg)\n\n        if n == 1:\n            return args[0]\n        else:\n            return args\n\n    def _save_configuration(self):\n        # We successfully ran a modifying command. Need to save the\n        # configuration.\n        try:\n            self.configuration.save()\n        except Exception:\n            logger.error(\n                \"Unable to save configuration. Please report this as a bug.\",\n                exc_info=1\n            )\n            raise PipError(\"Internal Error.\")\n\n    def _determine_editor(self, options):\n        if options.editor is not None:\n            return options.editor\n        elif \"VISUAL\" in os.environ:\n            return os.environ[\"VISUAL\"]\n        elif \"EDITOR\" in os.environ:\n            return os.environ[\"EDITOR\"]\n        else:\n            raise PipError(\"Could not determine editor to use.\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/download.py",
    "content": "from __future__ import absolute_import\n\nimport logging\nimport os\n\nfrom pip._internal.cli import cmdoptions\nfrom pip._internal.cli.base_command import RequirementCommand\nfrom pip._internal.operations.prepare import RequirementPreparer\nfrom pip._internal.req import RequirementSet\nfrom pip._internal.req.req_tracker import RequirementTracker\nfrom pip._internal.resolve import Resolver\nfrom pip._internal.utils.filesystem import check_path_owner\nfrom pip._internal.utils.misc import ensure_dir, normalize_path\nfrom pip._internal.utils.temp_dir import TempDirectory\n\nlogger = logging.getLogger(__name__)\n\n\nclass DownloadCommand(RequirementCommand):\n    \"\"\"\n    Download packages from:\n\n    - PyPI (and other indexes) using requirement specifiers.\n    - VCS project urls.\n    - Local project directories.\n    - Local or remote source archives.\n\n    pip also supports downloading from \"requirements files\", which provide\n    an easy way to specify a whole environment to be downloaded.\n    \"\"\"\n    name = 'download'\n\n    usage = \"\"\"\n      %prog [options] <requirement specifier> [package-index-options] ...\n      %prog [options] -r <requirements file> [package-index-options] ...\n      %prog [options] <vcs project url> ...\n      %prog [options] <local project path> ...\n      %prog [options] <archive url/path> ...\"\"\"\n\n    summary = 'Download packages.'\n\n    def __init__(self, *args, **kw):\n        super(DownloadCommand, self).__init__(*args, **kw)\n\n        cmd_opts = self.cmd_opts\n\n        cmd_opts.add_option(cmdoptions.constraints())\n        cmd_opts.add_option(cmdoptions.requirements())\n        cmd_opts.add_option(cmdoptions.build_dir())\n        cmd_opts.add_option(cmdoptions.no_deps())\n        cmd_opts.add_option(cmdoptions.global_options())\n        cmd_opts.add_option(cmdoptions.no_binary())\n        cmd_opts.add_option(cmdoptions.only_binary())\n        cmd_opts.add_option(cmdoptions.prefer_binary())\n        cmd_opts.add_option(cmdoptions.src())\n        cmd_opts.add_option(cmdoptions.pre())\n        cmd_opts.add_option(cmdoptions.no_clean())\n        cmd_opts.add_option(cmdoptions.require_hashes())\n        cmd_opts.add_option(cmdoptions.progress_bar())\n        cmd_opts.add_option(cmdoptions.no_build_isolation())\n        cmd_opts.add_option(cmdoptions.use_pep517())\n        cmd_opts.add_option(cmdoptions.no_use_pep517())\n\n        cmd_opts.add_option(\n            '-d', '--dest', '--destination-dir', '--destination-directory',\n            dest='download_dir',\n            metavar='dir',\n            default=os.curdir,\n            help=(\"Download packages into <dir>.\"),\n        )\n\n        cmd_opts.add_option(cmdoptions.platform())\n        cmd_opts.add_option(cmdoptions.python_version())\n        cmd_opts.add_option(cmdoptions.implementation())\n        cmd_opts.add_option(cmdoptions.abi())\n\n        index_opts = cmdoptions.make_option_group(\n            cmdoptions.index_group,\n            self.parser,\n        )\n\n        self.parser.insert_option_group(0, index_opts)\n        self.parser.insert_option_group(0, cmd_opts)\n\n    def run(self, options, args):\n        options.ignore_installed = True\n        # editable doesn't really make sense for `pip download`, but the bowels\n        # of the RequirementSet code require that property.\n        options.editables = []\n\n        if options.python_version:\n            python_versions = [options.python_version]\n        else:\n            python_versions = None\n\n        cmdoptions.check_dist_restriction(options)\n\n        options.src_dir = os.path.abspath(options.src_dir)\n        options.download_dir = normalize_path(options.download_dir)\n\n        ensure_dir(options.download_dir)\n\n        with self._build_session(options) as session:\n            finder = self._build_package_finder(\n                options=options,\n                session=session,\n                platform=options.platform,\n                python_versions=python_versions,\n                abi=options.abi,\n                implementation=options.implementation,\n            )\n            build_delete = (not (options.no_clean or options.build_dir))\n            if options.cache_dir and not check_path_owner(options.cache_dir):\n                logger.warning(\n                    \"The directory '%s' or its parent directory is not owned \"\n                    \"by the current user and caching wheels has been \"\n                    \"disabled. check the permissions and owner of that \"\n                    \"directory. If executing pip with sudo, you may want \"\n                    \"sudo's -H flag.\",\n                    options.cache_dir,\n                )\n                options.cache_dir = None\n\n            with RequirementTracker() as req_tracker, TempDirectory(\n                options.build_dir, delete=build_delete, kind=\"download\"\n            ) as directory:\n\n                requirement_set = RequirementSet(\n                    require_hashes=options.require_hashes,\n                )\n                self.populate_requirement_set(\n                    requirement_set,\n                    args,\n                    options,\n                    finder,\n                    session,\n                    self.name,\n                    None\n                )\n\n                preparer = RequirementPreparer(\n                    build_dir=directory.path,\n                    src_dir=options.src_dir,\n                    download_dir=options.download_dir,\n                    wheel_download_dir=None,\n                    progress_bar=options.progress_bar,\n                    build_isolation=options.build_isolation,\n                    req_tracker=req_tracker,\n                )\n\n                resolver = Resolver(\n                    preparer=preparer,\n                    finder=finder,\n                    session=session,\n                    wheel_cache=None,\n                    use_user_site=False,\n                    upgrade_strategy=\"to-satisfy-only\",\n                    force_reinstall=False,\n                    ignore_dependencies=options.ignore_dependencies,\n                    ignore_requires_python=False,\n                    ignore_installed=True,\n                    isolated=options.isolated_mode,\n                )\n                resolver.resolve(requirement_set)\n\n                downloaded = ' '.join([\n                    req.name for req in requirement_set.successfully_downloaded\n                ])\n                if downloaded:\n                    logger.info('Successfully downloaded %s', downloaded)\n\n                # Clean up\n                if not options.no_clean:\n                    requirement_set.cleanup_files()\n\n        return requirement_set\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/freeze.py",
    "content": "from __future__ import absolute_import\n\nimport sys\n\nfrom pip._internal.cache import WheelCache\nfrom pip._internal.cli.base_command import Command\nfrom pip._internal.models.format_control import FormatControl\nfrom pip._internal.operations.freeze import freeze\nfrom pip._internal.utils.compat import stdlib_pkgs\n\nDEV_PKGS = {'pip', 'setuptools', 'distribute', 'wheel'}\n\n\nclass FreezeCommand(Command):\n    \"\"\"\n    Output installed packages in requirements format.\n\n    packages are listed in a case-insensitive sorted order.\n    \"\"\"\n    name = 'freeze'\n    usage = \"\"\"\n      %prog [options]\"\"\"\n    summary = 'Output installed packages in requirements format.'\n    log_streams = (\"ext://sys.stderr\", \"ext://sys.stderr\")\n\n    def __init__(self, *args, **kw):\n        super(FreezeCommand, self).__init__(*args, **kw)\n\n        self.cmd_opts.add_option(\n            '-r', '--requirement',\n            dest='requirements',\n            action='append',\n            default=[],\n            metavar='file',\n            help=\"Use the order in the given requirements file and its \"\n                 \"comments when generating output. This option can be \"\n                 \"used multiple times.\")\n        self.cmd_opts.add_option(\n            '-f', '--find-links',\n            dest='find_links',\n            action='append',\n            default=[],\n            metavar='URL',\n            help='URL for finding packages, which will be added to the '\n                 'output.')\n        self.cmd_opts.add_option(\n            '-l', '--local',\n            dest='local',\n            action='store_true',\n            default=False,\n            help='If in a virtualenv that has global access, do not output '\n                 'globally-installed packages.')\n        self.cmd_opts.add_option(\n            '--user',\n            dest='user',\n            action='store_true',\n            default=False,\n            help='Only output packages installed in user-site.')\n        self.cmd_opts.add_option(\n            '--all',\n            dest='freeze_all',\n            action='store_true',\n            help='Do not skip these packages in the output:'\n                 ' %s' % ', '.join(DEV_PKGS))\n        self.cmd_opts.add_option(\n            '--exclude-editable',\n            dest='exclude_editable',\n            action='store_true',\n            help='Exclude editable package from output.')\n\n        self.parser.insert_option_group(0, self.cmd_opts)\n\n    def run(self, options, args):\n        format_control = FormatControl(set(), set())\n        wheel_cache = WheelCache(options.cache_dir, format_control)\n        skip = set(stdlib_pkgs)\n        if not options.freeze_all:\n            skip.update(DEV_PKGS)\n\n        freeze_kwargs = dict(\n            requirement=options.requirements,\n            find_links=options.find_links,\n            local_only=options.local,\n            user_only=options.user,\n            skip_regex=options.skip_requirements_regex,\n            isolated=options.isolated_mode,\n            wheel_cache=wheel_cache,\n            skip=skip,\n            exclude_editable=options.exclude_editable,\n        )\n\n        try:\n            for line in freeze(**freeze_kwargs):\n                sys.stdout.write(line + '\\n')\n        finally:\n            wheel_cache.cleanup()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/hash.py",
    "content": "from __future__ import absolute_import\n\nimport hashlib\nimport logging\nimport sys\n\nfrom pip._internal.cli.base_command import Command\nfrom pip._internal.cli.status_codes import ERROR\nfrom pip._internal.utils.hashes import FAVORITE_HASH, STRONG_HASHES\nfrom pip._internal.utils.misc import read_chunks\n\nlogger = logging.getLogger(__name__)\n\n\nclass HashCommand(Command):\n    \"\"\"\n    Compute a hash of a local package archive.\n\n    These can be used with --hash in a requirements file to do repeatable\n    installs.\n\n    \"\"\"\n    name = 'hash'\n    usage = '%prog [options] <file> ...'\n    summary = 'Compute hashes of package archives.'\n    ignore_require_venv = True\n\n    def __init__(self, *args, **kw):\n        super(HashCommand, self).__init__(*args, **kw)\n        self.cmd_opts.add_option(\n            '-a', '--algorithm',\n            dest='algorithm',\n            choices=STRONG_HASHES,\n            action='store',\n            default=FAVORITE_HASH,\n            help='The hash algorithm to use: one of %s' %\n                 ', '.join(STRONG_HASHES))\n        self.parser.insert_option_group(0, self.cmd_opts)\n\n    def run(self, options, args):\n        if not args:\n            self.parser.print_usage(sys.stderr)\n            return ERROR\n\n        algorithm = options.algorithm\n        for path in args:\n            logger.info('%s:\\n--hash=%s:%s',\n                        path, algorithm, _hash_of_file(path, algorithm))\n\n\ndef _hash_of_file(path, algorithm):\n    \"\"\"Return the hash digest of a file.\"\"\"\n    with open(path, 'rb') as archive:\n        hash = hashlib.new(algorithm)\n        for chunk in read_chunks(archive):\n            hash.update(chunk)\n    return hash.hexdigest()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/help.py",
    "content": "from __future__ import absolute_import\n\nfrom pip._internal.cli.base_command import Command\nfrom pip._internal.cli.status_codes import SUCCESS\nfrom pip._internal.exceptions import CommandError\n\n\nclass HelpCommand(Command):\n    \"\"\"Show help for commands\"\"\"\n    name = 'help'\n    usage = \"\"\"\n      %prog <command>\"\"\"\n    summary = 'Show help for commands.'\n    ignore_require_venv = True\n\n    def run(self, options, args):\n        from pip._internal.commands import commands_dict, get_similar_commands\n\n        try:\n            # 'pip help' with no args is handled by pip.__init__.parseopt()\n            cmd_name = args[0]  # the command we need help for\n        except IndexError:\n            return SUCCESS\n\n        if cmd_name not in commands_dict:\n            guess = get_similar_commands(cmd_name)\n\n            msg = ['unknown command \"%s\"' % cmd_name]\n            if guess:\n                msg.append('maybe you meant \"%s\"' % guess)\n\n            raise CommandError(' - '.join(msg))\n\n        command = commands_dict[cmd_name]()\n        command.parser.print_help()\n\n        return SUCCESS\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/install.py",
    "content": "from __future__ import absolute_import\n\nimport errno\nimport logging\nimport operator\nimport os\nimport shutil\nfrom optparse import SUPPRESS_HELP\n\nfrom pip._vendor import pkg_resources\n\nfrom pip._internal.cache import WheelCache\nfrom pip._internal.cli import cmdoptions\nfrom pip._internal.cli.base_command import RequirementCommand\nfrom pip._internal.cli.status_codes import ERROR\nfrom pip._internal.exceptions import (\n    CommandError, InstallationError, PreviousBuildDirError,\n)\nfrom pip._internal.locations import distutils_scheme, virtualenv_no_global\nfrom pip._internal.operations.check import check_install_conflicts\nfrom pip._internal.operations.prepare import RequirementPreparer\nfrom pip._internal.req import RequirementSet, install_given_reqs\nfrom pip._internal.req.req_tracker import RequirementTracker\nfrom pip._internal.resolve import Resolver\nfrom pip._internal.utils.filesystem import check_path_owner\nfrom pip._internal.utils.misc import (\n    ensure_dir, get_installed_version,\n    protect_pip_from_modification_on_windows,\n)\nfrom pip._internal.utils.temp_dir import TempDirectory\nfrom pip._internal.wheel import WheelBuilder\n\nlogger = logging.getLogger(__name__)\n\n\nclass InstallCommand(RequirementCommand):\n    \"\"\"\n    Install packages from:\n\n    - PyPI (and other indexes) using requirement specifiers.\n    - VCS project urls.\n    - Local project directories.\n    - Local or remote source archives.\n\n    pip also supports installing from \"requirements files\", which provide\n    an easy way to specify a whole environment to be installed.\n    \"\"\"\n    name = 'install'\n\n    usage = \"\"\"\n      %prog [options] <requirement specifier> [package-index-options] ...\n      %prog [options] -r <requirements file> [package-index-options] ...\n      %prog [options] [-e] <vcs project url> ...\n      %prog [options] [-e] <local project path> ...\n      %prog [options] <archive url/path> ...\"\"\"\n\n    summary = 'Install packages.'\n\n    def __init__(self, *args, **kw):\n        super(InstallCommand, self).__init__(*args, **kw)\n\n        cmd_opts = self.cmd_opts\n\n        cmd_opts.add_option(cmdoptions.requirements())\n        cmd_opts.add_option(cmdoptions.constraints())\n        cmd_opts.add_option(cmdoptions.no_deps())\n        cmd_opts.add_option(cmdoptions.pre())\n\n        cmd_opts.add_option(cmdoptions.editable())\n        cmd_opts.add_option(\n            '-t', '--target',\n            dest='target_dir',\n            metavar='dir',\n            default=None,\n            help='Install packages into <dir>. '\n                 'By default this will not replace existing files/folders in '\n                 '<dir>. Use --upgrade to replace existing packages in <dir> '\n                 'with new versions.'\n        )\n        cmd_opts.add_option(cmdoptions.platform())\n        cmd_opts.add_option(cmdoptions.python_version())\n        cmd_opts.add_option(cmdoptions.implementation())\n        cmd_opts.add_option(cmdoptions.abi())\n\n        cmd_opts.add_option(\n            '--user',\n            dest='use_user_site',\n            action='store_true',\n            help=\"Install to the Python user install directory for your \"\n                 \"platform. Typically ~/.local/, or %APPDATA%\\\\Python on \"\n                 \"Windows. (See the Python documentation for site.USER_BASE \"\n                 \"for full details.)\")\n        cmd_opts.add_option(\n            '--no-user',\n            dest='use_user_site',\n            action='store_false',\n            help=SUPPRESS_HELP)\n        cmd_opts.add_option(\n            '--root',\n            dest='root_path',\n            metavar='dir',\n            default=None,\n            help=\"Install everything relative to this alternate root \"\n                 \"directory.\")\n        cmd_opts.add_option(\n            '--prefix',\n            dest='prefix_path',\n            metavar='dir',\n            default=None,\n            help=\"Installation prefix where lib, bin and other top-level \"\n                 \"folders are placed\")\n\n        cmd_opts.add_option(cmdoptions.build_dir())\n\n        cmd_opts.add_option(cmdoptions.src())\n\n        cmd_opts.add_option(\n            '-U', '--upgrade',\n            dest='upgrade',\n            action='store_true',\n            help='Upgrade all specified packages to the newest available '\n                 'version. The handling of dependencies depends on the '\n                 'upgrade-strategy used.'\n        )\n\n        cmd_opts.add_option(\n            '--upgrade-strategy',\n            dest='upgrade_strategy',\n            default='only-if-needed',\n            choices=['only-if-needed', 'eager'],\n            help='Determines how dependency upgrading should be handled '\n                 '[default: %default]. '\n                 '\"eager\" - dependencies are upgraded regardless of '\n                 'whether the currently installed version satisfies the '\n                 'requirements of the upgraded package(s). '\n                 '\"only-if-needed\" -  are upgraded only when they do not '\n                 'satisfy the requirements of the upgraded package(s).'\n        )\n\n        cmd_opts.add_option(\n            '--force-reinstall',\n            dest='force_reinstall',\n            action='store_true',\n            help='Reinstall all packages even if they are already '\n                 'up-to-date.')\n\n        cmd_opts.add_option(\n            '-I', '--ignore-installed',\n            dest='ignore_installed',\n            action='store_true',\n            help='Ignore the installed packages (reinstalling instead).')\n\n        cmd_opts.add_option(cmdoptions.ignore_requires_python())\n        cmd_opts.add_option(cmdoptions.no_build_isolation())\n        cmd_opts.add_option(cmdoptions.use_pep517())\n        cmd_opts.add_option(cmdoptions.no_use_pep517())\n\n        cmd_opts.add_option(cmdoptions.install_options())\n        cmd_opts.add_option(cmdoptions.global_options())\n\n        cmd_opts.add_option(\n            \"--compile\",\n            action=\"store_true\",\n            dest=\"compile\",\n            default=True,\n            help=\"Compile Python source files to bytecode\",\n        )\n\n        cmd_opts.add_option(\n            \"--no-compile\",\n            action=\"store_false\",\n            dest=\"compile\",\n            help=\"Do not compile Python source files to bytecode\",\n        )\n\n        cmd_opts.add_option(\n            \"--no-warn-script-location\",\n            action=\"store_false\",\n            dest=\"warn_script_location\",\n            default=True,\n            help=\"Do not warn when installing scripts outside PATH\",\n        )\n        cmd_opts.add_option(\n            \"--no-warn-conflicts\",\n            action=\"store_false\",\n            dest=\"warn_about_conflicts\",\n            default=True,\n            help=\"Do not warn about broken dependencies\",\n        )\n\n        cmd_opts.add_option(cmdoptions.no_binary())\n        cmd_opts.add_option(cmdoptions.only_binary())\n        cmd_opts.add_option(cmdoptions.prefer_binary())\n        cmd_opts.add_option(cmdoptions.no_clean())\n        cmd_opts.add_option(cmdoptions.require_hashes())\n        cmd_opts.add_option(cmdoptions.progress_bar())\n\n        index_opts = cmdoptions.make_option_group(\n            cmdoptions.index_group,\n            self.parser,\n        )\n\n        self.parser.insert_option_group(0, index_opts)\n        self.parser.insert_option_group(0, cmd_opts)\n\n    def run(self, options, args):\n        cmdoptions.check_install_build_global(options)\n        upgrade_strategy = \"to-satisfy-only\"\n        if options.upgrade:\n            upgrade_strategy = options.upgrade_strategy\n\n        if options.build_dir:\n            options.build_dir = os.path.abspath(options.build_dir)\n\n        cmdoptions.check_dist_restriction(options, check_target=True)\n\n        if options.python_version:\n            python_versions = [options.python_version]\n        else:\n            python_versions = None\n\n        options.src_dir = os.path.abspath(options.src_dir)\n        install_options = options.install_options or []\n        if options.use_user_site:\n            if options.prefix_path:\n                raise CommandError(\n                    \"Can not combine '--user' and '--prefix' as they imply \"\n                    \"different installation locations\"\n                )\n            if virtualenv_no_global():\n                raise InstallationError(\n                    \"Can not perform a '--user' install. User site-packages \"\n                    \"are not visible in this virtualenv.\"\n                )\n            install_options.append('--user')\n            install_options.append('--prefix=')\n\n        target_temp_dir = TempDirectory(kind=\"target\")\n        if options.target_dir:\n            options.ignore_installed = True\n            options.target_dir = os.path.abspath(options.target_dir)\n            if (os.path.exists(options.target_dir) and not\n                    os.path.isdir(options.target_dir)):\n                raise CommandError(\n                    \"Target path exists but is not a directory, will not \"\n                    \"continue.\"\n                )\n\n            # Create a target directory for using with the target option\n            target_temp_dir.create()\n            install_options.append('--home=' + target_temp_dir.path)\n\n        global_options = options.global_options or []\n\n        with self._build_session(options) as session:\n            finder = self._build_package_finder(\n                options=options,\n                session=session,\n                platform=options.platform,\n                python_versions=python_versions,\n                abi=options.abi,\n                implementation=options.implementation,\n            )\n            build_delete = (not (options.no_clean or options.build_dir))\n            wheel_cache = WheelCache(options.cache_dir, options.format_control)\n\n            if options.cache_dir and not check_path_owner(options.cache_dir):\n                logger.warning(\n                    \"The directory '%s' or its parent directory is not owned \"\n                    \"by the current user and caching wheels has been \"\n                    \"disabled. check the permissions and owner of that \"\n                    \"directory. If executing pip with sudo, you may want \"\n                    \"sudo's -H flag.\",\n                    options.cache_dir,\n                )\n                options.cache_dir = None\n\n            with RequirementTracker() as req_tracker, TempDirectory(\n                options.build_dir, delete=build_delete, kind=\"install\"\n            ) as directory:\n                requirement_set = RequirementSet(\n                    require_hashes=options.require_hashes,\n                    check_supported_wheels=not options.target_dir,\n                )\n\n                try:\n                    self.populate_requirement_set(\n                        requirement_set, args, options, finder, session,\n                        self.name, wheel_cache\n                    )\n                    preparer = RequirementPreparer(\n                        build_dir=directory.path,\n                        src_dir=options.src_dir,\n                        download_dir=None,\n                        wheel_download_dir=None,\n                        progress_bar=options.progress_bar,\n                        build_isolation=options.build_isolation,\n                        req_tracker=req_tracker,\n                    )\n\n                    resolver = Resolver(\n                        preparer=preparer,\n                        finder=finder,\n                        session=session,\n                        wheel_cache=wheel_cache,\n                        use_user_site=options.use_user_site,\n                        upgrade_strategy=upgrade_strategy,\n                        force_reinstall=options.force_reinstall,\n                        ignore_dependencies=options.ignore_dependencies,\n                        ignore_requires_python=options.ignore_requires_python,\n                        ignore_installed=options.ignore_installed,\n                        isolated=options.isolated_mode,\n                        use_pep517=options.use_pep517\n                    )\n                    resolver.resolve(requirement_set)\n\n                    protect_pip_from_modification_on_windows(\n                        modifying_pip=requirement_set.has_requirement(\"pip\")\n                    )\n\n                    # Consider legacy and PEP517-using requirements separately\n                    legacy_requirements = []\n                    pep517_requirements = []\n                    for req in requirement_set.requirements.values():\n                        if req.use_pep517:\n                            pep517_requirements.append(req)\n                        else:\n                            legacy_requirements.append(req)\n\n                    # We don't build wheels for legacy requirements if we\n                    # don't have wheel installed or we don't have a cache dir\n                    try:\n                        import wheel  # noqa: F401\n                        build_legacy = bool(options.cache_dir)\n                    except ImportError:\n                        build_legacy = False\n\n                    wb = WheelBuilder(\n                        finder, preparer, wheel_cache,\n                        build_options=[], global_options=[],\n                    )\n\n                    # Always build PEP 517 requirements\n                    build_failures = wb.build(\n                        pep517_requirements,\n                        session=session, autobuilding=True\n                    )\n\n                    if build_legacy:\n                        # We don't care about failures building legacy\n                        # requirements, as we'll fall through to a direct\n                        # install for those.\n                        wb.build(\n                            legacy_requirements,\n                            session=session, autobuilding=True\n                        )\n\n                    # If we're using PEP 517, we cannot do a direct install\n                    # so we fail here.\n                    if build_failures:\n                        raise InstallationError(\n                            \"Could not build wheels for {} which use\"\n                            \" PEP 517 and cannot be installed directly\".format(\n                                \", \".join(r.name for r in build_failures)))\n\n                    to_install = resolver.get_installation_order(\n                        requirement_set\n                    )\n\n                    # Consistency Checking of the package set we're installing.\n                    should_warn_about_conflicts = (\n                        not options.ignore_dependencies and\n                        options.warn_about_conflicts\n                    )\n                    if should_warn_about_conflicts:\n                        self._warn_about_conflicts(to_install)\n\n                    # Don't warn about script install locations if\n                    # --target has been specified\n                    warn_script_location = options.warn_script_location\n                    if options.target_dir:\n                        warn_script_location = False\n\n                    installed = install_given_reqs(\n                        to_install,\n                        install_options,\n                        global_options,\n                        root=options.root_path,\n                        home=target_temp_dir.path,\n                        prefix=options.prefix_path,\n                        pycompile=options.compile,\n                        warn_script_location=warn_script_location,\n                        use_user_site=options.use_user_site,\n                    )\n\n                    lib_locations = get_lib_location_guesses(\n                        user=options.use_user_site,\n                        home=target_temp_dir.path,\n                        root=options.root_path,\n                        prefix=options.prefix_path,\n                        isolated=options.isolated_mode,\n                    )\n                    working_set = pkg_resources.WorkingSet(lib_locations)\n\n                    reqs = sorted(installed, key=operator.attrgetter('name'))\n                    items = []\n                    for req in reqs:\n                        item = req.name\n                        try:\n                            installed_version = get_installed_version(\n                                req.name, working_set=working_set\n                            )\n                            if installed_version:\n                                item += '-' + installed_version\n                        except Exception:\n                            pass\n                        items.append(item)\n                    installed = ' '.join(items)\n                    if installed:\n                        logger.info('Successfully installed %s', installed)\n                except EnvironmentError as error:\n                    show_traceback = (self.verbosity >= 1)\n\n                    message = create_env_error_message(\n                        error, show_traceback, options.use_user_site,\n                    )\n                    logger.error(message, exc_info=show_traceback)\n\n                    return ERROR\n                except PreviousBuildDirError:\n                    options.no_clean = True\n                    raise\n                finally:\n                    # Clean up\n                    if not options.no_clean:\n                        requirement_set.cleanup_files()\n                        wheel_cache.cleanup()\n\n        if options.target_dir:\n            self._handle_target_dir(\n                options.target_dir, target_temp_dir, options.upgrade\n            )\n        return requirement_set\n\n    def _handle_target_dir(self, target_dir, target_temp_dir, upgrade):\n        ensure_dir(target_dir)\n\n        # Checking both purelib and platlib directories for installed\n        # packages to be moved to target directory\n        lib_dir_list = []\n\n        with target_temp_dir:\n            # Checking both purelib and platlib directories for installed\n            # packages to be moved to target directory\n            scheme = distutils_scheme('', home=target_temp_dir.path)\n            purelib_dir = scheme['purelib']\n            platlib_dir = scheme['platlib']\n            data_dir = scheme['data']\n\n            if os.path.exists(purelib_dir):\n                lib_dir_list.append(purelib_dir)\n            if os.path.exists(platlib_dir) and platlib_dir != purelib_dir:\n                lib_dir_list.append(platlib_dir)\n            if os.path.exists(data_dir):\n                lib_dir_list.append(data_dir)\n\n            for lib_dir in lib_dir_list:\n                for item in os.listdir(lib_dir):\n                    if lib_dir == data_dir:\n                        ddir = os.path.join(data_dir, item)\n                        if any(s.startswith(ddir) for s in lib_dir_list[:-1]):\n                            continue\n                    target_item_dir = os.path.join(target_dir, item)\n                    if os.path.exists(target_item_dir):\n                        if not upgrade:\n                            logger.warning(\n                                'Target directory %s already exists. Specify '\n                                '--upgrade to force replacement.',\n                                target_item_dir\n                            )\n                            continue\n                        if os.path.islink(target_item_dir):\n                            logger.warning(\n                                'Target directory %s already exists and is '\n                                'a link. Pip will not automatically replace '\n                                'links, please remove if replacement is '\n                                'desired.',\n                                target_item_dir\n                            )\n                            continue\n                        if os.path.isdir(target_item_dir):\n                            shutil.rmtree(target_item_dir)\n                        else:\n                            os.remove(target_item_dir)\n\n                    shutil.move(\n                        os.path.join(lib_dir, item),\n                        target_item_dir\n                    )\n\n    def _warn_about_conflicts(self, to_install):\n        try:\n            package_set, _dep_info = check_install_conflicts(to_install)\n        except Exception:\n            logger.error(\"Error checking for conflicts.\", exc_info=True)\n            return\n        missing, conflicting = _dep_info\n\n        # NOTE: There is some duplication here from pip check\n        for project_name in missing:\n            version = package_set[project_name][0]\n            for dependency in missing[project_name]:\n                logger.critical(\n                    \"%s %s requires %s, which is not installed.\",\n                    project_name, version, dependency[1],\n                )\n\n        for project_name in conflicting:\n            version = package_set[project_name][0]\n            for dep_name, dep_version, req in conflicting[project_name]:\n                logger.critical(\n                    \"%s %s has requirement %s, but you'll have %s %s which is \"\n                    \"incompatible.\",\n                    project_name, version, req, dep_name, dep_version,\n                )\n\n\ndef get_lib_location_guesses(*args, **kwargs):\n    scheme = distutils_scheme('', *args, **kwargs)\n    return [scheme['purelib'], scheme['platlib']]\n\n\ndef create_env_error_message(error, show_traceback, using_user_site):\n    \"\"\"Format an error message for an EnvironmentError\n\n    It may occur anytime during the execution of the install command.\n    \"\"\"\n    parts = []\n\n    # Mention the error if we are not going to show a traceback\n    parts.append(\"Could not install packages due to an EnvironmentError\")\n    if not show_traceback:\n        parts.append(\": \")\n        parts.append(str(error))\n    else:\n        parts.append(\".\")\n\n    # Spilt the error indication from a helper message (if any)\n    parts[-1] += \"\\n\"\n\n    # Suggest useful actions to the user:\n    #  (1) using user site-packages or (2) verifying the permissions\n    if error.errno == errno.EACCES:\n        user_option_part = \"Consider using the `--user` option\"\n        permissions_part = \"Check the permissions\"\n\n        if not using_user_site:\n            parts.extend([\n                user_option_part, \" or \",\n                permissions_part.lower(),\n            ])\n        else:\n            parts.append(permissions_part)\n        parts.append(\".\\n\")\n\n    return \"\".join(parts).strip() + \"\\n\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/list.py",
    "content": "from __future__ import absolute_import\n\nimport json\nimport logging\n\nfrom pip._vendor import six\nfrom pip._vendor.six.moves import zip_longest\n\nfrom pip._internal.cli import cmdoptions\nfrom pip._internal.cli.base_command import Command\nfrom pip._internal.exceptions import CommandError\nfrom pip._internal.index import PackageFinder\nfrom pip._internal.utils.misc import (\n    dist_is_editable, get_installed_distributions,\n)\nfrom pip._internal.utils.packaging import get_installer\n\nlogger = logging.getLogger(__name__)\n\n\nclass ListCommand(Command):\n    \"\"\"\n    List installed packages, including editables.\n\n    Packages are listed in a case-insensitive sorted order.\n    \"\"\"\n    name = 'list'\n    usage = \"\"\"\n      %prog [options]\"\"\"\n    summary = 'List installed packages.'\n\n    def __init__(self, *args, **kw):\n        super(ListCommand, self).__init__(*args, **kw)\n\n        cmd_opts = self.cmd_opts\n\n        cmd_opts.add_option(\n            '-o', '--outdated',\n            action='store_true',\n            default=False,\n            help='List outdated packages')\n        cmd_opts.add_option(\n            '-u', '--uptodate',\n            action='store_true',\n            default=False,\n            help='List uptodate packages')\n        cmd_opts.add_option(\n            '-e', '--editable',\n            action='store_true',\n            default=False,\n            help='List editable projects.')\n        cmd_opts.add_option(\n            '-l', '--local',\n            action='store_true',\n            default=False,\n            help=('If in a virtualenv that has global access, do not list '\n                  'globally-installed packages.'),\n        )\n        self.cmd_opts.add_option(\n            '--user',\n            dest='user',\n            action='store_true',\n            default=False,\n            help='Only output packages installed in user-site.')\n\n        cmd_opts.add_option(\n            '--pre',\n            action='store_true',\n            default=False,\n            help=(\"Include pre-release and development versions. By default, \"\n                  \"pip only finds stable versions.\"),\n        )\n\n        cmd_opts.add_option(\n            '--format',\n            action='store',\n            dest='list_format',\n            default=\"columns\",\n            choices=('columns', 'freeze', 'json'),\n            help=\"Select the output format among: columns (default), freeze, \"\n                 \"or json\",\n        )\n\n        cmd_opts.add_option(\n            '--not-required',\n            action='store_true',\n            dest='not_required',\n            help=\"List packages that are not dependencies of \"\n                 \"installed packages.\",\n        )\n\n        cmd_opts.add_option(\n            '--exclude-editable',\n            action='store_false',\n            dest='include_editable',\n            help='Exclude editable package from output.',\n        )\n        cmd_opts.add_option(\n            '--include-editable',\n            action='store_true',\n            dest='include_editable',\n            help='Include editable package from output.',\n            default=True,\n        )\n        index_opts = cmdoptions.make_option_group(\n            cmdoptions.index_group, self.parser\n        )\n\n        self.parser.insert_option_group(0, index_opts)\n        self.parser.insert_option_group(0, cmd_opts)\n\n    def _build_package_finder(self, options, index_urls, session):\n        \"\"\"\n        Create a package finder appropriate to this list command.\n        \"\"\"\n        return PackageFinder(\n            find_links=options.find_links,\n            index_urls=index_urls,\n            allow_all_prereleases=options.pre,\n            trusted_hosts=options.trusted_hosts,\n            session=session,\n        )\n\n    def run(self, options, args):\n        if options.outdated and options.uptodate:\n            raise CommandError(\n                \"Options --outdated and --uptodate cannot be combined.\")\n\n        packages = get_installed_distributions(\n            local_only=options.local,\n            user_only=options.user,\n            editables_only=options.editable,\n            include_editables=options.include_editable,\n        )\n\n        # get_not_required must be called firstly in order to find and\n        # filter out all dependencies correctly. Otherwise a package\n        # can't be identified as requirement because some parent packages\n        # could be filtered out before.\n        if options.not_required:\n            packages = self.get_not_required(packages, options)\n\n        if options.outdated:\n            packages = self.get_outdated(packages, options)\n        elif options.uptodate:\n            packages = self.get_uptodate(packages, options)\n\n        self.output_package_listing(packages, options)\n\n    def get_outdated(self, packages, options):\n        return [\n            dist for dist in self.iter_packages_latest_infos(packages, options)\n            if dist.latest_version > dist.parsed_version\n        ]\n\n    def get_uptodate(self, packages, options):\n        return [\n            dist for dist in self.iter_packages_latest_infos(packages, options)\n            if dist.latest_version == dist.parsed_version\n        ]\n\n    def get_not_required(self, packages, options):\n        dep_keys = set()\n        for dist in packages:\n            dep_keys.update(requirement.key for requirement in dist.requires())\n        return {pkg for pkg in packages if pkg.key not in dep_keys}\n\n    def iter_packages_latest_infos(self, packages, options):\n        index_urls = [options.index_url] + options.extra_index_urls\n        if options.no_index:\n            logger.debug('Ignoring indexes: %s', ','.join(index_urls))\n            index_urls = []\n\n        with self._build_session(options) as session:\n            finder = self._build_package_finder(options, index_urls, session)\n\n            for dist in packages:\n                typ = 'unknown'\n                all_candidates = finder.find_all_candidates(dist.key)\n                if not options.pre:\n                    # Remove prereleases\n                    all_candidates = [candidate for candidate in all_candidates\n                                      if not candidate.version.is_prerelease]\n\n                if not all_candidates:\n                    continue\n                best_candidate = max(all_candidates,\n                                     key=finder._candidate_sort_key)\n                remote_version = best_candidate.version\n                if best_candidate.location.is_wheel:\n                    typ = 'wheel'\n                else:\n                    typ = 'sdist'\n                # This is dirty but makes the rest of the code much cleaner\n                dist.latest_version = remote_version\n                dist.latest_filetype = typ\n                yield dist\n\n    def output_package_listing(self, packages, options):\n        packages = sorted(\n            packages,\n            key=lambda dist: dist.project_name.lower(),\n        )\n        if options.list_format == 'columns' and packages:\n            data, header = format_for_columns(packages, options)\n            self.output_package_listing_columns(data, header)\n        elif options.list_format == 'freeze':\n            for dist in packages:\n                if options.verbose >= 1:\n                    logger.info(\"%s==%s (%s)\", dist.project_name,\n                                dist.version, dist.location)\n                else:\n                    logger.info(\"%s==%s\", dist.project_name, dist.version)\n        elif options.list_format == 'json':\n            logger.info(format_for_json(packages, options))\n\n    def output_package_listing_columns(self, data, header):\n        # insert the header first: we need to know the size of column names\n        if len(data) > 0:\n            data.insert(0, header)\n\n        pkg_strings, sizes = tabulate(data)\n\n        # Create and add a separator.\n        if len(data) > 0:\n            pkg_strings.insert(1, \" \".join(map(lambda x: '-' * x, sizes)))\n\n        for val in pkg_strings:\n            logger.info(val)\n\n\ndef tabulate(vals):\n    # From pfmoore on GitHub:\n    # https://github.com/pypa/pip/issues/3651#issuecomment-216932564\n    assert len(vals) > 0\n\n    sizes = [0] * max(len(x) for x in vals)\n    for row in vals:\n        sizes = [max(s, len(str(c))) for s, c in zip_longest(sizes, row)]\n\n    result = []\n    for row in vals:\n        display = \" \".join([str(c).ljust(s) if c is not None else ''\n                            for s, c in zip_longest(sizes, row)])\n        result.append(display)\n\n    return result, sizes\n\n\ndef format_for_columns(pkgs, options):\n    \"\"\"\n    Convert the package data into something usable\n    by output_package_listing_columns.\n    \"\"\"\n    running_outdated = options.outdated\n    # Adjust the header for the `pip list --outdated` case.\n    if running_outdated:\n        header = [\"Package\", \"Version\", \"Latest\", \"Type\"]\n    else:\n        header = [\"Package\", \"Version\"]\n\n    data = []\n    if options.verbose >= 1 or any(dist_is_editable(x) for x in pkgs):\n        header.append(\"Location\")\n    if options.verbose >= 1:\n        header.append(\"Installer\")\n\n    for proj in pkgs:\n        # if we're working on the 'outdated' list, separate out the\n        # latest_version and type\n        row = [proj.project_name, proj.version]\n\n        if running_outdated:\n            row.append(proj.latest_version)\n            row.append(proj.latest_filetype)\n\n        if options.verbose >= 1 or dist_is_editable(proj):\n            row.append(proj.location)\n        if options.verbose >= 1:\n            row.append(get_installer(proj))\n\n        data.append(row)\n\n    return data, header\n\n\ndef format_for_json(packages, options):\n    data = []\n    for dist in packages:\n        info = {\n            'name': dist.project_name,\n            'version': six.text_type(dist.version),\n        }\n        if options.verbose >= 1:\n            info['location'] = dist.location\n            info['installer'] = get_installer(dist)\n        if options.outdated:\n            info['latest_version'] = six.text_type(dist.latest_version)\n            info['latest_filetype'] = dist.latest_filetype\n        data.append(info)\n    return json.dumps(data)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/search.py",
    "content": "from __future__ import absolute_import\n\nimport logging\nimport sys\nimport textwrap\nfrom collections import OrderedDict\n\nfrom pip._vendor import pkg_resources\nfrom pip._vendor.packaging.version import parse as parse_version\n# NOTE: XMLRPC Client is not annotated in typeshed as on 2017-07-17, which is\n#       why we ignore the type on this import\nfrom pip._vendor.six.moves import xmlrpc_client  # type: ignore\n\nfrom pip._internal.cli.base_command import Command\nfrom pip._internal.cli.status_codes import NO_MATCHES_FOUND, SUCCESS\nfrom pip._internal.download import PipXmlrpcTransport\nfrom pip._internal.exceptions import CommandError\nfrom pip._internal.models.index import PyPI\nfrom pip._internal.utils.compat import get_terminal_size\nfrom pip._internal.utils.logging import indent_log\n\nlogger = logging.getLogger(__name__)\n\n\nclass SearchCommand(Command):\n    \"\"\"Search for PyPI packages whose name or summary contains <query>.\"\"\"\n    name = 'search'\n    usage = \"\"\"\n      %prog [options] <query>\"\"\"\n    summary = 'Search PyPI for packages.'\n    ignore_require_venv = True\n\n    def __init__(self, *args, **kw):\n        super(SearchCommand, self).__init__(*args, **kw)\n        self.cmd_opts.add_option(\n            '-i', '--index',\n            dest='index',\n            metavar='URL',\n            default=PyPI.pypi_url,\n            help='Base URL of Python Package Index (default %default)')\n\n        self.parser.insert_option_group(0, self.cmd_opts)\n\n    def run(self, options, args):\n        if not args:\n            raise CommandError('Missing required argument (search query).')\n        query = args\n        pypi_hits = self.search(query, options)\n        hits = transform_hits(pypi_hits)\n\n        terminal_width = None\n        if sys.stdout.isatty():\n            terminal_width = get_terminal_size()[0]\n\n        print_results(hits, terminal_width=terminal_width)\n        if pypi_hits:\n            return SUCCESS\n        return NO_MATCHES_FOUND\n\n    def search(self, query, options):\n        index_url = options.index\n        with self._build_session(options) as session:\n            transport = PipXmlrpcTransport(index_url, session)\n            pypi = xmlrpc_client.ServerProxy(index_url, transport)\n            hits = pypi.search({'name': query, 'summary': query}, 'or')\n            return hits\n\n\ndef transform_hits(hits):\n    \"\"\"\n    The list from pypi is really a list of versions. We want a list of\n    packages with the list of versions stored inline. This converts the\n    list from pypi into one we can use.\n    \"\"\"\n    packages = OrderedDict()\n    for hit in hits:\n        name = hit['name']\n        summary = hit['summary']\n        version = hit['version']\n\n        if name not in packages.keys():\n            packages[name] = {\n                'name': name,\n                'summary': summary,\n                'versions': [version],\n            }\n        else:\n            packages[name]['versions'].append(version)\n\n            # if this is the highest version, replace summary and score\n            if version == highest_version(packages[name]['versions']):\n                packages[name]['summary'] = summary\n\n    return list(packages.values())\n\n\ndef print_results(hits, name_column_width=None, terminal_width=None):\n    if not hits:\n        return\n    if name_column_width is None:\n        name_column_width = max([\n            len(hit['name']) + len(highest_version(hit.get('versions', ['-'])))\n            for hit in hits\n        ]) + 4\n\n    installed_packages = [p.project_name for p in pkg_resources.working_set]\n    for hit in hits:\n        name = hit['name']\n        summary = hit['summary'] or ''\n        latest = highest_version(hit.get('versions', ['-']))\n        if terminal_width is not None:\n            target_width = terminal_width - name_column_width - 5\n            if target_width > 10:\n                # wrap and indent summary to fit terminal\n                summary = textwrap.wrap(summary, target_width)\n                summary = ('\\n' + ' ' * (name_column_width + 3)).join(summary)\n\n        line = '%-*s - %s' % (name_column_width,\n                              '%s (%s)' % (name, latest), summary)\n        try:\n            logger.info(line)\n            if name in installed_packages:\n                dist = pkg_resources.get_distribution(name)\n                with indent_log():\n                    if dist.version == latest:\n                        logger.info('INSTALLED: %s (latest)', dist.version)\n                    else:\n                        logger.info('INSTALLED: %s', dist.version)\n                        logger.info('LATEST:    %s', latest)\n        except UnicodeEncodeError:\n            pass\n\n\ndef highest_version(versions):\n    return max(versions, key=parse_version)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/show.py",
    "content": "from __future__ import absolute_import\n\nimport logging\nimport os\nfrom email.parser import FeedParser  # type: ignore\n\nfrom pip._vendor import pkg_resources\nfrom pip._vendor.packaging.utils import canonicalize_name\n\nfrom pip._internal.cli.base_command import Command\nfrom pip._internal.cli.status_codes import ERROR, SUCCESS\n\nlogger = logging.getLogger(__name__)\n\n\nclass ShowCommand(Command):\n    \"\"\"\n    Show information about one or more installed packages.\n\n    The output is in RFC-compliant mail header format.\n    \"\"\"\n    name = 'show'\n    usage = \"\"\"\n      %prog [options] <package> ...\"\"\"\n    summary = 'Show information about installed packages.'\n    ignore_require_venv = True\n\n    def __init__(self, *args, **kw):\n        super(ShowCommand, self).__init__(*args, **kw)\n        self.cmd_opts.add_option(\n            '-f', '--files',\n            dest='files',\n            action='store_true',\n            default=False,\n            help='Show the full list of installed files for each package.')\n\n        self.parser.insert_option_group(0, self.cmd_opts)\n\n    def run(self, options, args):\n        if not args:\n            logger.warning('ERROR: Please provide a package name or names.')\n            return ERROR\n        query = args\n\n        results = search_packages_info(query)\n        if not print_results(\n                results, list_files=options.files, verbose=options.verbose):\n            return ERROR\n        return SUCCESS\n\n\ndef search_packages_info(query):\n    \"\"\"\n    Gather details from installed distributions. Print distribution name,\n    version, location, and installed files. Installed files requires a\n    pip generated 'installed-files.txt' in the distributions '.egg-info'\n    directory.\n    \"\"\"\n    installed = {}\n    for p in pkg_resources.working_set:\n        installed[canonicalize_name(p.project_name)] = p\n\n    query_names = [canonicalize_name(name) for name in query]\n\n    for dist in [installed[pkg] for pkg in query_names if pkg in installed]:\n        package = {\n            'name': dist.project_name,\n            'version': dist.version,\n            'location': dist.location,\n            'requires': [dep.project_name for dep in dist.requires()],\n        }\n        file_list = None\n        metadata = None\n        if isinstance(dist, pkg_resources.DistInfoDistribution):\n            # RECORDs should be part of .dist-info metadatas\n            if dist.has_metadata('RECORD'):\n                lines = dist.get_metadata_lines('RECORD')\n                paths = [l.split(',')[0] for l in lines]\n                paths = [os.path.join(dist.location, p) for p in paths]\n                file_list = [os.path.relpath(p, dist.location) for p in paths]\n\n            if dist.has_metadata('METADATA'):\n                metadata = dist.get_metadata('METADATA')\n        else:\n            # Otherwise use pip's log for .egg-info's\n            if dist.has_metadata('installed-files.txt'):\n                paths = dist.get_metadata_lines('installed-files.txt')\n                paths = [os.path.join(dist.egg_info, p) for p in paths]\n                file_list = [os.path.relpath(p, dist.location) for p in paths]\n\n            if dist.has_metadata('PKG-INFO'):\n                metadata = dist.get_metadata('PKG-INFO')\n\n        if dist.has_metadata('entry_points.txt'):\n            entry_points = dist.get_metadata_lines('entry_points.txt')\n            package['entry_points'] = entry_points\n\n        if dist.has_metadata('INSTALLER'):\n            for line in dist.get_metadata_lines('INSTALLER'):\n                if line.strip():\n                    package['installer'] = line.strip()\n                    break\n\n        # @todo: Should pkg_resources.Distribution have a\n        # `get_pkg_info` method?\n        feed_parser = FeedParser()\n        feed_parser.feed(metadata)\n        pkg_info_dict = feed_parser.close()\n        for key in ('metadata-version', 'summary',\n                    'home-page', 'author', 'author-email', 'license'):\n            package[key] = pkg_info_dict.get(key)\n\n        # It looks like FeedParser cannot deal with repeated headers\n        classifiers = []\n        for line in metadata.splitlines():\n            if line.startswith('Classifier: '):\n                classifiers.append(line[len('Classifier: '):])\n        package['classifiers'] = classifiers\n\n        if file_list:\n            package['files'] = sorted(file_list)\n        yield package\n\n\ndef print_results(distributions, list_files=False, verbose=False):\n    \"\"\"\n    Print the informations from installed distributions found.\n    \"\"\"\n    results_printed = False\n    for i, dist in enumerate(distributions):\n        results_printed = True\n        if i > 0:\n            logger.info(\"---\")\n\n        name = dist.get('name', '')\n        required_by = [\n            pkg.project_name for pkg in pkg_resources.working_set\n            if name in [required.name for required in pkg.requires()]\n        ]\n\n        logger.info(\"Name: %s\", name)\n        logger.info(\"Version: %s\", dist.get('version', ''))\n        logger.info(\"Summary: %s\", dist.get('summary', ''))\n        logger.info(\"Home-page: %s\", dist.get('home-page', ''))\n        logger.info(\"Author: %s\", dist.get('author', ''))\n        logger.info(\"Author-email: %s\", dist.get('author-email', ''))\n        logger.info(\"License: %s\", dist.get('license', ''))\n        logger.info(\"Location: %s\", dist.get('location', ''))\n        logger.info(\"Requires: %s\", ', '.join(dist.get('requires', [])))\n        logger.info(\"Required-by: %s\", ', '.join(required_by))\n\n        if verbose:\n            logger.info(\"Metadata-Version: %s\",\n                        dist.get('metadata-version', ''))\n            logger.info(\"Installer: %s\", dist.get('installer', ''))\n            logger.info(\"Classifiers:\")\n            for classifier in dist.get('classifiers', []):\n                logger.info(\"  %s\", classifier)\n            logger.info(\"Entry-points:\")\n            for entry in dist.get('entry_points', []):\n                logger.info(\"  %s\", entry.strip())\n        if list_files:\n            logger.info(\"Files:\")\n            for line in dist.get('files', []):\n                logger.info(\"  %s\", line.strip())\n            if \"files\" not in dist:\n                logger.info(\"Cannot locate installed-files.txt\")\n    return results_printed\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/uninstall.py",
    "content": "from __future__ import absolute_import\n\nfrom pip._vendor.packaging.utils import canonicalize_name\n\nfrom pip._internal.cli.base_command import Command\nfrom pip._internal.exceptions import InstallationError\nfrom pip._internal.req import parse_requirements\nfrom pip._internal.req.constructors import install_req_from_line\nfrom pip._internal.utils.misc import protect_pip_from_modification_on_windows\n\n\nclass UninstallCommand(Command):\n    \"\"\"\n    Uninstall packages.\n\n    pip is able to uninstall most installed packages. Known exceptions are:\n\n    - Pure distutils packages installed with ``python setup.py install``, which\n      leave behind no metadata to determine what files were installed.\n    - Script wrappers installed by ``python setup.py develop``.\n    \"\"\"\n    name = 'uninstall'\n    usage = \"\"\"\n      %prog [options] <package> ...\n      %prog [options] -r <requirements file> ...\"\"\"\n    summary = 'Uninstall packages.'\n\n    def __init__(self, *args, **kw):\n        super(UninstallCommand, self).__init__(*args, **kw)\n        self.cmd_opts.add_option(\n            '-r', '--requirement',\n            dest='requirements',\n            action='append',\n            default=[],\n            metavar='file',\n            help='Uninstall all the packages listed in the given requirements '\n                 'file.  This option can be used multiple times.',\n        )\n        self.cmd_opts.add_option(\n            '-y', '--yes',\n            dest='yes',\n            action='store_true',\n            help=\"Don't ask for confirmation of uninstall deletions.\")\n\n        self.parser.insert_option_group(0, self.cmd_opts)\n\n    def run(self, options, args):\n        with self._build_session(options) as session:\n            reqs_to_uninstall = {}\n            for name in args:\n                req = install_req_from_line(\n                    name, isolated=options.isolated_mode,\n                )\n                if req.name:\n                    reqs_to_uninstall[canonicalize_name(req.name)] = req\n            for filename in options.requirements:\n                for req in parse_requirements(\n                        filename,\n                        options=options,\n                        session=session):\n                    if req.name:\n                        reqs_to_uninstall[canonicalize_name(req.name)] = req\n            if not reqs_to_uninstall:\n                raise InstallationError(\n                    'You must give at least one requirement to %(name)s (see '\n                    '\"pip help %(name)s\")' % dict(name=self.name)\n                )\n\n            protect_pip_from_modification_on_windows(\n                modifying_pip=\"pip\" in reqs_to_uninstall\n            )\n\n            for req in reqs_to_uninstall.values():\n                uninstall_pathset = req.uninstall(\n                    auto_confirm=options.yes, verbose=self.verbosity > 0,\n                )\n                if uninstall_pathset:\n                    uninstall_pathset.commit()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/commands/wheel.py",
    "content": "# -*- coding: utf-8 -*-\nfrom __future__ import absolute_import\n\nimport logging\nimport os\n\nfrom pip._internal.cache import WheelCache\nfrom pip._internal.cli import cmdoptions\nfrom pip._internal.cli.base_command import RequirementCommand\nfrom pip._internal.exceptions import CommandError, PreviousBuildDirError\nfrom pip._internal.operations.prepare import RequirementPreparer\nfrom pip._internal.req import RequirementSet\nfrom pip._internal.req.req_tracker import RequirementTracker\nfrom pip._internal.resolve import Resolver\nfrom pip._internal.utils.temp_dir import TempDirectory\nfrom pip._internal.wheel import WheelBuilder\n\nlogger = logging.getLogger(__name__)\n\n\nclass WheelCommand(RequirementCommand):\n    \"\"\"\n    Build Wheel archives for your requirements and dependencies.\n\n    Wheel is a built-package format, and offers the advantage of not\n    recompiling your software during every install. For more details, see the\n    wheel docs: https://wheel.readthedocs.io/en/latest/\n\n    Requirements: setuptools>=0.8, and wheel.\n\n    'pip wheel' uses the bdist_wheel setuptools extension from the wheel\n    package to build individual wheels.\n\n    \"\"\"\n\n    name = 'wheel'\n    usage = \"\"\"\n      %prog [options] <requirement specifier> ...\n      %prog [options] -r <requirements file> ...\n      %prog [options] [-e] <vcs project url> ...\n      %prog [options] [-e] <local project path> ...\n      %prog [options] <archive url/path> ...\"\"\"\n\n    summary = 'Build wheels from your requirements.'\n\n    def __init__(self, *args, **kw):\n        super(WheelCommand, self).__init__(*args, **kw)\n\n        cmd_opts = self.cmd_opts\n\n        cmd_opts.add_option(\n            '-w', '--wheel-dir',\n            dest='wheel_dir',\n            metavar='dir',\n            default=os.curdir,\n            help=(\"Build wheels into <dir>, where the default is the \"\n                  \"current working directory.\"),\n        )\n        cmd_opts.add_option(cmdoptions.no_binary())\n        cmd_opts.add_option(cmdoptions.only_binary())\n        cmd_opts.add_option(cmdoptions.prefer_binary())\n        cmd_opts.add_option(\n            '--build-option',\n            dest='build_options',\n            metavar='options',\n            action='append',\n            help=\"Extra arguments to be supplied to 'setup.py bdist_wheel'.\",\n        )\n        cmd_opts.add_option(cmdoptions.no_build_isolation())\n        cmd_opts.add_option(cmdoptions.use_pep517())\n        cmd_opts.add_option(cmdoptions.no_use_pep517())\n        cmd_opts.add_option(cmdoptions.constraints())\n        cmd_opts.add_option(cmdoptions.editable())\n        cmd_opts.add_option(cmdoptions.requirements())\n        cmd_opts.add_option(cmdoptions.src())\n        cmd_opts.add_option(cmdoptions.ignore_requires_python())\n        cmd_opts.add_option(cmdoptions.no_deps())\n        cmd_opts.add_option(cmdoptions.build_dir())\n        cmd_opts.add_option(cmdoptions.progress_bar())\n\n        cmd_opts.add_option(\n            '--global-option',\n            dest='global_options',\n            action='append',\n            metavar='options',\n            help=\"Extra global options to be supplied to the setup.py \"\n            \"call before the 'bdist_wheel' command.\")\n\n        cmd_opts.add_option(\n            '--pre',\n            action='store_true',\n            default=False,\n            help=(\"Include pre-release and development versions. By default, \"\n                  \"pip only finds stable versions.\"),\n        )\n\n        cmd_opts.add_option(cmdoptions.no_clean())\n        cmd_opts.add_option(cmdoptions.require_hashes())\n\n        index_opts = cmdoptions.make_option_group(\n            cmdoptions.index_group,\n            self.parser,\n        )\n\n        self.parser.insert_option_group(0, index_opts)\n        self.parser.insert_option_group(0, cmd_opts)\n\n    def run(self, options, args):\n        cmdoptions.check_install_build_global(options)\n\n        index_urls = [options.index_url] + options.extra_index_urls\n        if options.no_index:\n            logger.debug('Ignoring indexes: %s', ','.join(index_urls))\n            index_urls = []\n\n        if options.build_dir:\n            options.build_dir = os.path.abspath(options.build_dir)\n\n        options.src_dir = os.path.abspath(options.src_dir)\n\n        with self._build_session(options) as session:\n            finder = self._build_package_finder(options, session)\n            build_delete = (not (options.no_clean or options.build_dir))\n            wheel_cache = WheelCache(options.cache_dir, options.format_control)\n\n            with RequirementTracker() as req_tracker, TempDirectory(\n                options.build_dir, delete=build_delete, kind=\"wheel\"\n            ) as directory:\n\n                requirement_set = RequirementSet(\n                    require_hashes=options.require_hashes,\n                )\n\n                try:\n                    self.populate_requirement_set(\n                        requirement_set, args, options, finder, session,\n                        self.name, wheel_cache\n                    )\n\n                    preparer = RequirementPreparer(\n                        build_dir=directory.path,\n                        src_dir=options.src_dir,\n                        download_dir=None,\n                        wheel_download_dir=options.wheel_dir,\n                        progress_bar=options.progress_bar,\n                        build_isolation=options.build_isolation,\n                        req_tracker=req_tracker,\n                    )\n\n                    resolver = Resolver(\n                        preparer=preparer,\n                        finder=finder,\n                        session=session,\n                        wheel_cache=wheel_cache,\n                        use_user_site=False,\n                        upgrade_strategy=\"to-satisfy-only\",\n                        force_reinstall=False,\n                        ignore_dependencies=options.ignore_dependencies,\n                        ignore_requires_python=options.ignore_requires_python,\n                        ignore_installed=True,\n                        isolated=options.isolated_mode,\n                        use_pep517=options.use_pep517\n                    )\n                    resolver.resolve(requirement_set)\n\n                    # build wheels\n                    wb = WheelBuilder(\n                        finder, preparer, wheel_cache,\n                        build_options=options.build_options or [],\n                        global_options=options.global_options or [],\n                        no_clean=options.no_clean,\n                    )\n                    build_failures = wb.build(\n                        requirement_set.requirements.values(), session=session,\n                    )\n                    if len(build_failures) != 0:\n                        raise CommandError(\n                            \"Failed to build one or more wheels\"\n                        )\n                except PreviousBuildDirError:\n                    options.no_clean = True\n                    raise\n                finally:\n                    if not options.no_clean:\n                        requirement_set.cleanup_files()\n                        wheel_cache.cleanup()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/configuration.py",
    "content": "\"\"\"Configuration management setup\n\nSome terminology:\n- name\n  As written in config files.\n- value\n  Value associated with a name\n- key\n  Name combined with it's section (section.name)\n- variant\n  A single word describing where the configuration key-value pair came from\n\"\"\"\n\nimport locale\nimport logging\nimport os\n\nfrom pip._vendor import six\nfrom pip._vendor.six.moves import configparser\n\nfrom pip._internal.exceptions import (\n    ConfigurationError, ConfigurationFileCouldNotBeLoaded,\n)\nfrom pip._internal.locations import (\n    legacy_config_file, new_config_file, running_under_virtualenv,\n    site_config_files, venv_config_file,\n)\nfrom pip._internal.utils.misc import ensure_dir, enum\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import (  # noqa: F401\n        Any, Dict, Iterable, List, NewType, Optional, Tuple\n    )\n\n    RawConfigParser = configparser.RawConfigParser  # Shorthand\n    Kind = NewType(\"Kind\", str)\n\nlogger = logging.getLogger(__name__)\n\n\n# NOTE: Maybe use the optionx attribute to normalize keynames.\ndef _normalize_name(name):\n    # type: (str) -> str\n    \"\"\"Make a name consistent regardless of source (environment or file)\n    \"\"\"\n    name = name.lower().replace('_', '-')\n    if name.startswith('--'):\n        name = name[2:]  # only prefer long opts\n    return name\n\n\ndef _disassemble_key(name):\n    # type: (str) -> List[str]\n    return name.split(\".\", 1)\n\n\n# The kinds of configurations there are.\nkinds = enum(\n    USER=\"user\",        # User Specific\n    GLOBAL=\"global\",    # System Wide\n    VENV=\"venv\",        # Virtual Environment Specific\n    ENV=\"env\",          # from PIP_CONFIG_FILE\n    ENV_VAR=\"env-var\",  # from Environment Variables\n)\n\n\nclass Configuration(object):\n    \"\"\"Handles management of configuration.\n\n    Provides an interface to accessing and managing configuration files.\n\n    This class converts provides an API that takes \"section.key-name\" style\n    keys and stores the value associated with it as \"key-name\" under the\n    section \"section\".\n\n    This allows for a clean interface wherein the both the section and the\n    key-name are preserved in an easy to manage form in the configuration files\n    and the data stored is also nice.\n    \"\"\"\n\n    def __init__(self, isolated, load_only=None):\n        # type: (bool, Kind) -> None\n        super(Configuration, self).__init__()\n\n        _valid_load_only = [kinds.USER, kinds.GLOBAL, kinds.VENV, None]\n        if load_only not in _valid_load_only:\n            raise ConfigurationError(\n                \"Got invalid value for load_only - should be one of {}\".format(\n                    \", \".join(map(repr, _valid_load_only[:-1]))\n                )\n            )\n        self.isolated = isolated  # type: bool\n        self.load_only = load_only  # type: Optional[Kind]\n\n        # The order here determines the override order.\n        self._override_order = [\n            kinds.GLOBAL, kinds.USER, kinds.VENV, kinds.ENV, kinds.ENV_VAR\n        ]\n\n        self._ignore_env_names = [\"version\", \"help\"]\n\n        # Because we keep track of where we got the data from\n        self._parsers = {\n            variant: [] for variant in self._override_order\n        }  # type: Dict[Kind, List[Tuple[str, RawConfigParser]]]\n        self._config = {\n            variant: {} for variant in self._override_order\n        }  # type: Dict[Kind, Dict[str, Any]]\n        self._modified_parsers = []  # type: List[Tuple[str, RawConfigParser]]\n\n    def load(self):\n        # type: () -> None\n        \"\"\"Loads configuration from configuration files and environment\n        \"\"\"\n        self._load_config_files()\n        if not self.isolated:\n            self._load_environment_vars()\n\n    def get_file_to_edit(self):\n        # type: () -> Optional[str]\n        \"\"\"Returns the file with highest priority in configuration\n        \"\"\"\n        assert self.load_only is not None, \\\n            \"Need to be specified a file to be editing\"\n\n        try:\n            return self._get_parser_to_modify()[0]\n        except IndexError:\n            return None\n\n    def items(self):\n        # type: () -> Iterable[Tuple[str, Any]]\n        \"\"\"Returns key-value pairs like dict.items() representing the loaded\n        configuration\n        \"\"\"\n        return self._dictionary.items()\n\n    def get_value(self, key):\n        # type: (str) -> Any\n        \"\"\"Get a value from the configuration.\n        \"\"\"\n        try:\n            return self._dictionary[key]\n        except KeyError:\n            raise ConfigurationError(\"No such key - {}\".format(key))\n\n    def set_value(self, key, value):\n        # type: (str, Any) -> None\n        \"\"\"Modify a value in the configuration.\n        \"\"\"\n        self._ensure_have_load_only()\n\n        fname, parser = self._get_parser_to_modify()\n\n        if parser is not None:\n            section, name = _disassemble_key(key)\n\n            # Modify the parser and the configuration\n            if not parser.has_section(section):\n                parser.add_section(section)\n            parser.set(section, name, value)\n\n        self._config[self.load_only][key] = value\n        self._mark_as_modified(fname, parser)\n\n    def unset_value(self, key):\n        # type: (str) -> None\n        \"\"\"Unset a value in the configuration.\n        \"\"\"\n        self._ensure_have_load_only()\n\n        if key not in self._config[self.load_only]:\n            raise ConfigurationError(\"No such key - {}\".format(key))\n\n        fname, parser = self._get_parser_to_modify()\n\n        if parser is not None:\n            section, name = _disassemble_key(key)\n\n            # Remove the key in the parser\n            modified_something = False\n            if parser.has_section(section):\n                # Returns whether the option was removed or not\n                modified_something = parser.remove_option(section, name)\n\n            if modified_something:\n                # name removed from parser, section may now be empty\n                section_iter = iter(parser.items(section))\n                try:\n                    val = six.next(section_iter)\n                except StopIteration:\n                    val = None\n\n                if val is None:\n                    parser.remove_section(section)\n\n                self._mark_as_modified(fname, parser)\n            else:\n                raise ConfigurationError(\n                    \"Fatal Internal error [id=1]. Please report as a bug.\"\n                )\n\n        del self._config[self.load_only][key]\n\n    def save(self):\n        # type: () -> None\n        \"\"\"Save the currentin-memory state.\n        \"\"\"\n        self._ensure_have_load_only()\n\n        for fname, parser in self._modified_parsers:\n            logger.info(\"Writing to %s\", fname)\n\n            # Ensure directory exists.\n            ensure_dir(os.path.dirname(fname))\n\n            with open(fname, \"w\") as f:\n                parser.write(f)  # type: ignore\n\n    #\n    # Private routines\n    #\n\n    def _ensure_have_load_only(self):\n        # type: () -> None\n        if self.load_only is None:\n            raise ConfigurationError(\"Needed a specific file to be modifying.\")\n        logger.debug(\"Will be working with %s variant only\", self.load_only)\n\n    @property\n    def _dictionary(self):\n        # type: () -> Dict[str, Any]\n        \"\"\"A dictionary representing the loaded configuration.\n        \"\"\"\n        # NOTE: Dictionaries are not populated if not loaded. So, conditionals\n        #       are not needed here.\n        retval = {}\n\n        for variant in self._override_order:\n            retval.update(self._config[variant])\n\n        return retval\n\n    def _load_config_files(self):\n        # type: () -> None\n        \"\"\"Loads configuration from configuration files\n        \"\"\"\n        config_files = dict(self._iter_config_files())\n        if config_files[kinds.ENV][0:1] == [os.devnull]:\n            logger.debug(\n                \"Skipping loading configuration files due to \"\n                \"environment's PIP_CONFIG_FILE being os.devnull\"\n            )\n            return\n\n        for variant, files in config_files.items():\n            for fname in files:\n                # If there's specific variant set in `load_only`, load only\n                # that variant, not the others.\n                if self.load_only is not None and variant != self.load_only:\n                    logger.debug(\n                        \"Skipping file '%s' (variant: %s)\", fname, variant\n                    )\n                    continue\n\n                parser = self._load_file(variant, fname)\n\n                # Keeping track of the parsers used\n                self._parsers[variant].append((fname, parser))\n\n    def _load_file(self, variant, fname):\n        # type: (Kind, str) -> RawConfigParser\n        logger.debug(\"For variant '%s', will try loading '%s'\", variant, fname)\n        parser = self._construct_parser(fname)\n\n        for section in parser.sections():\n            items = parser.items(section)\n            self._config[variant].update(self._normalized_keys(section, items))\n\n        return parser\n\n    def _construct_parser(self, fname):\n        # type: (str) -> RawConfigParser\n        parser = configparser.RawConfigParser()\n        # If there is no such file, don't bother reading it but create the\n        # parser anyway, to hold the data.\n        # Doing this is useful when modifying and saving files, where we don't\n        # need to construct a parser.\n        if os.path.exists(fname):\n            try:\n                parser.read(fname)\n            except UnicodeDecodeError:\n                # See https://github.com/pypa/pip/issues/4963\n                raise ConfigurationFileCouldNotBeLoaded(\n                    reason=\"contains invalid {} characters\".format(\n                        locale.getpreferredencoding(False)\n                    ),\n                    fname=fname,\n                )\n            except configparser.Error as error:\n                # See https://github.com/pypa/pip/issues/4893\n                raise ConfigurationFileCouldNotBeLoaded(error=error)\n        return parser\n\n    def _load_environment_vars(self):\n        # type: () -> None\n        \"\"\"Loads configuration from environment variables\n        \"\"\"\n        self._config[kinds.ENV_VAR].update(\n            self._normalized_keys(\":env:\", self._get_environ_vars())\n        )\n\n    def _normalized_keys(self, section, items):\n        # type: (str, Iterable[Tuple[str, Any]]) -> Dict[str, Any]\n        \"\"\"Normalizes items to construct a dictionary with normalized keys.\n\n        This routine is where the names become keys and are made the same\n        regardless of source - configuration files or environment.\n        \"\"\"\n        normalized = {}\n        for name, val in items:\n            key = section + \".\" + _normalize_name(name)\n            normalized[key] = val\n        return normalized\n\n    def _get_environ_vars(self):\n        # type: () -> Iterable[Tuple[str, str]]\n        \"\"\"Returns a generator with all environmental vars with prefix PIP_\"\"\"\n        for key, val in os.environ.items():\n            should_be_yielded = (\n                key.startswith(\"PIP_\") and\n                key[4:].lower() not in self._ignore_env_names\n            )\n            if should_be_yielded:\n                yield key[4:].lower(), val\n\n    # XXX: This is patched in the tests.\n    def _iter_config_files(self):\n        # type: () -> Iterable[Tuple[Kind, List[str]]]\n        \"\"\"Yields variant and configuration files associated with it.\n\n        This should be treated like items of a dictionary.\n        \"\"\"\n        # SMELL: Move the conditions out of this function\n\n        # environment variables have the lowest priority\n        config_file = os.environ.get('PIP_CONFIG_FILE', None)\n        if config_file is not None:\n            yield kinds.ENV, [config_file]\n        else:\n            yield kinds.ENV, []\n\n        # at the base we have any global configuration\n        yield kinds.GLOBAL, list(site_config_files)\n\n        # per-user configuration next\n        should_load_user_config = not self.isolated and not (\n            config_file and os.path.exists(config_file)\n        )\n        if should_load_user_config:\n            # The legacy config file is overridden by the new config file\n            yield kinds.USER, [legacy_config_file, new_config_file]\n\n        # finally virtualenv configuration first trumping others\n        if running_under_virtualenv():\n            yield kinds.VENV, [venv_config_file]\n\n    def _get_parser_to_modify(self):\n        # type: () -> Tuple[str, RawConfigParser]\n        # Determine which parser to modify\n        parsers = self._parsers[self.load_only]\n        if not parsers:\n            # This should not happen if everything works correctly.\n            raise ConfigurationError(\n                \"Fatal Internal error [id=2]. Please report as a bug.\"\n            )\n\n        # Use the highest priority parser.\n        return parsers[-1]\n\n    # XXX: This is patched in the tests.\n    def _mark_as_modified(self, fname, parser):\n        # type: (str, RawConfigParser) -> None\n        file_parser_tuple = (fname, parser)\n        if file_parser_tuple not in self._modified_parsers:\n            self._modified_parsers.append(file_parser_tuple)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/download.py",
    "content": "from __future__ import absolute_import\n\nimport cgi\nimport email.utils\nimport getpass\nimport json\nimport logging\nimport mimetypes\nimport os\nimport platform\nimport re\nimport shutil\nimport sys\n\nfrom pip._vendor import requests, six, urllib3\nfrom pip._vendor.cachecontrol import CacheControlAdapter\nfrom pip._vendor.cachecontrol.caches import FileCache\nfrom pip._vendor.lockfile import LockError\nfrom pip._vendor.requests.adapters import BaseAdapter, HTTPAdapter\nfrom pip._vendor.requests.auth import AuthBase, HTTPBasicAuth\nfrom pip._vendor.requests.models import CONTENT_CHUNK_SIZE, Response\nfrom pip._vendor.requests.structures import CaseInsensitiveDict\nfrom pip._vendor.requests.utils import get_netrc_auth\n# NOTE: XMLRPC Client is not annotated in typeshed as on 2017-07-17, which is\n#       why we ignore the type on this import\nfrom pip._vendor.six.moves import xmlrpc_client  # type: ignore\nfrom pip._vendor.six.moves.urllib import parse as urllib_parse\nfrom pip._vendor.six.moves.urllib import request as urllib_request\nfrom pip._vendor.urllib3.util import IS_PYOPENSSL\n\nimport pip\nfrom pip._internal.exceptions import HashMismatch, InstallationError\nfrom pip._internal.locations import write_delete_marker_file\nfrom pip._internal.models.index import PyPI\nfrom pip._internal.utils.encoding import auto_decode\nfrom pip._internal.utils.filesystem import check_path_owner\nfrom pip._internal.utils.glibc import libc_ver\nfrom pip._internal.utils.logging import indent_log\nfrom pip._internal.utils.misc import (\n    ARCHIVE_EXTENSIONS, ask_path_exists, backup_dir, call_subprocess, consume,\n    display_path, format_size, get_installed_version, rmtree,\n    split_auth_from_netloc, splitext, unpack_file,\n)\nfrom pip._internal.utils.setuptools_build import SETUPTOOLS_SHIM\nfrom pip._internal.utils.temp_dir import TempDirectory\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\nfrom pip._internal.utils.ui import DownloadProgressProvider\nfrom pip._internal.vcs import vcs\n\nif MYPY_CHECK_RUNNING:\n    from typing import (  # noqa: F401\n        Optional, Tuple, Dict, IO, Text, Union\n    )\n    from pip._internal.models.link import Link  # noqa: F401\n    from pip._internal.utils.hashes import Hashes  # noqa: F401\n    from pip._internal.vcs import AuthInfo  # noqa: F401\n\ntry:\n    import ssl  # noqa\nexcept ImportError:\n    ssl = None\n\nHAS_TLS = (ssl is not None) or IS_PYOPENSSL\n\n__all__ = ['get_file_content',\n           'is_url', 'url_to_path', 'path_to_url',\n           'is_archive_file', 'unpack_vcs_link',\n           'unpack_file_url', 'is_vcs_url', 'is_file_url',\n           'unpack_http_url', 'unpack_url']\n\n\nlogger = logging.getLogger(__name__)\n\n\ndef user_agent():\n    \"\"\"\n    Return a string representing the user agent.\n    \"\"\"\n    data = {\n        \"installer\": {\"name\": \"pip\", \"version\": pip.__version__},\n        \"python\": platform.python_version(),\n        \"implementation\": {\n            \"name\": platform.python_implementation(),\n        },\n    }\n\n    if data[\"implementation\"][\"name\"] == 'CPython':\n        data[\"implementation\"][\"version\"] = platform.python_version()\n    elif data[\"implementation\"][\"name\"] == 'PyPy':\n        if sys.pypy_version_info.releaselevel == 'final':\n            pypy_version_info = sys.pypy_version_info[:3]\n        else:\n            pypy_version_info = sys.pypy_version_info\n        data[\"implementation\"][\"version\"] = \".\".join(\n            [str(x) for x in pypy_version_info]\n        )\n    elif data[\"implementation\"][\"name\"] == 'Jython':\n        # Complete Guess\n        data[\"implementation\"][\"version\"] = platform.python_version()\n    elif data[\"implementation\"][\"name\"] == 'IronPython':\n        # Complete Guess\n        data[\"implementation\"][\"version\"] = platform.python_version()\n\n    if sys.platform.startswith(\"linux\"):\n        from pip._vendor import distro\n        distro_infos = dict(filter(\n            lambda x: x[1],\n            zip([\"name\", \"version\", \"id\"], distro.linux_distribution()),\n        ))\n        libc = dict(filter(\n            lambda x: x[1],\n            zip([\"lib\", \"version\"], libc_ver()),\n        ))\n        if libc:\n            distro_infos[\"libc\"] = libc\n        if distro_infos:\n            data[\"distro\"] = distro_infos\n\n    if sys.platform.startswith(\"darwin\") and platform.mac_ver()[0]:\n        data[\"distro\"] = {\"name\": \"macOS\", \"version\": platform.mac_ver()[0]}\n\n    if platform.system():\n        data.setdefault(\"system\", {})[\"name\"] = platform.system()\n\n    if platform.release():\n        data.setdefault(\"system\", {})[\"release\"] = platform.release()\n\n    if platform.machine():\n        data[\"cpu\"] = platform.machine()\n\n    if HAS_TLS:\n        data[\"openssl_version\"] = ssl.OPENSSL_VERSION\n\n    setuptools_version = get_installed_version(\"setuptools\")\n    if setuptools_version is not None:\n        data[\"setuptools_version\"] = setuptools_version\n\n    return \"{data[installer][name]}/{data[installer][version]} {json}\".format(\n        data=data,\n        json=json.dumps(data, separators=(\",\", \":\"), sort_keys=True),\n    )\n\n\nclass MultiDomainBasicAuth(AuthBase):\n\n    def __init__(self, prompting=True):\n        # type: (bool) -> None\n        self.prompting = prompting\n        self.passwords = {}  # type: Dict[str, AuthInfo]\n\n    def __call__(self, req):\n        parsed = urllib_parse.urlparse(req.url)\n\n        # Split the credentials from the netloc.\n        netloc, url_user_password = split_auth_from_netloc(parsed.netloc)\n\n        # Set the url of the request to the url without any credentials\n        req.url = urllib_parse.urlunparse(parsed[:1] + (netloc,) + parsed[2:])\n\n        # Use any stored credentials that we have for this netloc\n        username, password = self.passwords.get(netloc, (None, None))\n\n        # Use the credentials embedded in the url if we have none stored\n        if username is None:\n            username, password = url_user_password\n\n        # Get creds from netrc if we still don't have them\n        if username is None and password is None:\n            netrc_auth = get_netrc_auth(req.url)\n            username, password = netrc_auth if netrc_auth else (None, None)\n\n        if username or password:\n            # Store the username and password\n            self.passwords[netloc] = (username, password)\n\n            # Send the basic auth with this request\n            req = HTTPBasicAuth(username or \"\", password or \"\")(req)\n\n        # Attach a hook to handle 401 responses\n        req.register_hook(\"response\", self.handle_401)\n\n        return req\n\n    def handle_401(self, resp, **kwargs):\n        # We only care about 401 responses, anything else we want to just\n        #   pass through the actual response\n        if resp.status_code != 401:\n            return resp\n\n        # We are not able to prompt the user so simply return the response\n        if not self.prompting:\n            return resp\n\n        parsed = urllib_parse.urlparse(resp.url)\n\n        # Prompt the user for a new username and password\n        username = six.moves.input(\"User for %s: \" % parsed.netloc)\n        password = getpass.getpass(\"Password: \")\n\n        # Store the new username and password to use for future requests\n        if username or password:\n            self.passwords[parsed.netloc] = (username, password)\n\n        # Consume content and release the original connection to allow our new\n        #   request to reuse the same one.\n        resp.content\n        resp.raw.release_conn()\n\n        # Add our new username and password to the request\n        req = HTTPBasicAuth(username or \"\", password or \"\")(resp.request)\n        req.register_hook(\"response\", self.warn_on_401)\n\n        # Send our new request\n        new_resp = resp.connection.send(req, **kwargs)\n        new_resp.history.append(resp)\n\n        return new_resp\n\n    def warn_on_401(self, resp, **kwargs):\n        # warn user that they provided incorrect credentials\n        if resp.status_code == 401:\n            logger.warning('401 Error, Credentials not correct for %s',\n                           resp.request.url)\n\n\nclass LocalFSAdapter(BaseAdapter):\n\n    def send(self, request, stream=None, timeout=None, verify=None, cert=None,\n             proxies=None):\n        pathname = url_to_path(request.url)\n\n        resp = Response()\n        resp.status_code = 200\n        resp.url = request.url\n\n        try:\n            stats = os.stat(pathname)\n        except OSError as exc:\n            resp.status_code = 404\n            resp.raw = exc\n        else:\n            modified = email.utils.formatdate(stats.st_mtime, usegmt=True)\n            content_type = mimetypes.guess_type(pathname)[0] or \"text/plain\"\n            resp.headers = CaseInsensitiveDict({\n                \"Content-Type\": content_type,\n                \"Content-Length\": stats.st_size,\n                \"Last-Modified\": modified,\n            })\n\n            resp.raw = open(pathname, \"rb\")\n            resp.close = resp.raw.close\n\n        return resp\n\n    def close(self):\n        pass\n\n\nclass SafeFileCache(FileCache):\n    \"\"\"\n    A file based cache which is safe to use even when the target directory may\n    not be accessible or writable.\n    \"\"\"\n\n    def __init__(self, *args, **kwargs):\n        super(SafeFileCache, self).__init__(*args, **kwargs)\n\n        # Check to ensure that the directory containing our cache directory\n        # is owned by the user current executing pip. If it does not exist\n        # we will check the parent directory until we find one that does exist.\n        # If it is not owned by the user executing pip then we will disable\n        # the cache and log a warning.\n        if not check_path_owner(self.directory):\n            logger.warning(\n                \"The directory '%s' or its parent directory is not owned by \"\n                \"the current user and the cache has been disabled. Please \"\n                \"check the permissions and owner of that directory. If \"\n                \"executing pip with sudo, you may want sudo's -H flag.\",\n                self.directory,\n            )\n\n            # Set our directory to None to disable the Cache\n            self.directory = None\n\n    def get(self, *args, **kwargs):\n        # If we don't have a directory, then the cache should be a no-op.\n        if self.directory is None:\n            return\n\n        try:\n            return super(SafeFileCache, self).get(*args, **kwargs)\n        except (LockError, OSError, IOError):\n            # We intentionally silence this error, if we can't access the cache\n            # then we can just skip caching and process the request as if\n            # caching wasn't enabled.\n            pass\n\n    def set(self, *args, **kwargs):\n        # If we don't have a directory, then the cache should be a no-op.\n        if self.directory is None:\n            return\n\n        try:\n            return super(SafeFileCache, self).set(*args, **kwargs)\n        except (LockError, OSError, IOError):\n            # We intentionally silence this error, if we can't access the cache\n            # then we can just skip caching and process the request as if\n            # caching wasn't enabled.\n            pass\n\n    def delete(self, *args, **kwargs):\n        # If we don't have a directory, then the cache should be a no-op.\n        if self.directory is None:\n            return\n\n        try:\n            return super(SafeFileCache, self).delete(*args, **kwargs)\n        except (LockError, OSError, IOError):\n            # We intentionally silence this error, if we can't access the cache\n            # then we can just skip caching and process the request as if\n            # caching wasn't enabled.\n            pass\n\n\nclass InsecureHTTPAdapter(HTTPAdapter):\n\n    def cert_verify(self, conn, url, verify, cert):\n        conn.cert_reqs = 'CERT_NONE'\n        conn.ca_certs = None\n\n\nclass PipSession(requests.Session):\n\n    timeout = None  # type: Optional[int]\n\n    def __init__(self, *args, **kwargs):\n        retries = kwargs.pop(\"retries\", 0)\n        cache = kwargs.pop(\"cache\", None)\n        insecure_hosts = kwargs.pop(\"insecure_hosts\", [])\n\n        super(PipSession, self).__init__(*args, **kwargs)\n\n        # Attach our User Agent to the request\n        self.headers[\"User-Agent\"] = user_agent()\n\n        # Attach our Authentication handler to the session\n        self.auth = MultiDomainBasicAuth()\n\n        # Create our urllib3.Retry instance which will allow us to customize\n        # how we handle retries.\n        retries = urllib3.Retry(\n            # Set the total number of retries that a particular request can\n            # have.\n            total=retries,\n\n            # A 503 error from PyPI typically means that the Fastly -> Origin\n            # connection got interrupted in some way. A 503 error in general\n            # is typically considered a transient error so we'll go ahead and\n            # retry it.\n            # A 500 may indicate transient error in Amazon S3\n            # A 520 or 527 - may indicate transient error in CloudFlare\n            status_forcelist=[500, 503, 520, 527],\n\n            # Add a small amount of back off between failed requests in\n            # order to prevent hammering the service.\n            backoff_factor=0.25,\n        )\n\n        # We want to _only_ cache responses on securely fetched origins. We do\n        # this because we can't validate the response of an insecurely fetched\n        # origin, and we don't want someone to be able to poison the cache and\n        # require manual eviction from the cache to fix it.\n        if cache:\n            secure_adapter = CacheControlAdapter(\n                cache=SafeFileCache(cache, use_dir_lock=True),\n                max_retries=retries,\n            )\n        else:\n            secure_adapter = HTTPAdapter(max_retries=retries)\n\n        # Our Insecure HTTPAdapter disables HTTPS validation. It does not\n        # support caching (see above) so we'll use it for all http:// URLs as\n        # well as any https:// host that we've marked as ignoring TLS errors\n        # for.\n        insecure_adapter = InsecureHTTPAdapter(max_retries=retries)\n\n        self.mount(\"https://\", secure_adapter)\n        self.mount(\"http://\", insecure_adapter)\n\n        # Enable file:// urls\n        self.mount(\"file://\", LocalFSAdapter())\n\n        # We want to use a non-validating adapter for any requests which are\n        # deemed insecure.\n        for host in insecure_hosts:\n            self.mount(\"https://{}/\".format(host), insecure_adapter)\n\n    def request(self, method, url, *args, **kwargs):\n        # Allow setting a default timeout on a session\n        kwargs.setdefault(\"timeout\", self.timeout)\n\n        # Dispatch the actual request\n        return super(PipSession, self).request(method, url, *args, **kwargs)\n\n\ndef get_file_content(url, comes_from=None, session=None):\n    # type: (str, Optional[str], Optional[PipSession]) -> Tuple[str, Text]\n    \"\"\"Gets the content of a file; it may be a filename, file: URL, or\n    http: URL.  Returns (location, content).  Content is unicode.\n\n    :param url:         File path or url.\n    :param comes_from:  Origin description of requirements.\n    :param session:     Instance of pip.download.PipSession.\n    \"\"\"\n    if session is None:\n        raise TypeError(\n            \"get_file_content() missing 1 required keyword argument: 'session'\"\n        )\n\n    match = _scheme_re.search(url)\n    if match:\n        scheme = match.group(1).lower()\n        if (scheme == 'file' and comes_from and\n                comes_from.startswith('http')):\n            raise InstallationError(\n                'Requirements file %s references URL %s, which is local'\n                % (comes_from, url))\n        if scheme == 'file':\n            path = url.split(':', 1)[1]\n            path = path.replace('\\\\', '/')\n            match = _url_slash_drive_re.match(path)\n            if match:\n                path = match.group(1) + ':' + path.split('|', 1)[1]\n            path = urllib_parse.unquote(path)\n            if path.startswith('/'):\n                path = '/' + path.lstrip('/')\n            url = path\n        else:\n            # FIXME: catch some errors\n            resp = session.get(url)\n            resp.raise_for_status()\n            return resp.url, resp.text\n    try:\n        with open(url, 'rb') as f:\n            content = auto_decode(f.read())\n    except IOError as exc:\n        raise InstallationError(\n            'Could not open requirements file: %s' % str(exc)\n        )\n    return url, content\n\n\n_scheme_re = re.compile(r'^(http|https|file):', re.I)\n_url_slash_drive_re = re.compile(r'/*([a-z])\\|', re.I)\n\n\ndef is_url(name):\n    # type: (Union[str, Text]) -> bool\n    \"\"\"Returns true if the name looks like a URL\"\"\"\n    if ':' not in name:\n        return False\n    scheme = name.split(':', 1)[0].lower()\n    return scheme in ['http', 'https', 'file', 'ftp'] + vcs.all_schemes\n\n\ndef url_to_path(url):\n    # type: (str) -> str\n    \"\"\"\n    Convert a file: URL to a path.\n    \"\"\"\n    assert url.startswith('file:'), (\n        \"You can only turn file: urls into filenames (not %r)\" % url)\n\n    _, netloc, path, _, _ = urllib_parse.urlsplit(url)\n\n    # if we have a UNC path, prepend UNC share notation\n    if netloc:\n        netloc = '\\\\\\\\' + netloc\n\n    path = urllib_request.url2pathname(netloc + path)\n    return path\n\n\ndef path_to_url(path):\n    # type: (Union[str, Text]) -> str\n    \"\"\"\n    Convert a path to a file: URL.  The path will be made absolute and have\n    quoted path parts.\n    \"\"\"\n    path = os.path.normpath(os.path.abspath(path))\n    url = urllib_parse.urljoin('file:', urllib_request.pathname2url(path))\n    return url\n\n\ndef is_archive_file(name):\n    # type: (str) -> bool\n    \"\"\"Return True if `name` is a considered as an archive file.\"\"\"\n    ext = splitext(name)[1].lower()\n    if ext in ARCHIVE_EXTENSIONS:\n        return True\n    return False\n\n\ndef unpack_vcs_link(link, location):\n    vcs_backend = _get_used_vcs_backend(link)\n    vcs_backend.unpack(location)\n\n\ndef _get_used_vcs_backend(link):\n    for backend in vcs.backends:\n        if link.scheme in backend.schemes:\n            vcs_backend = backend(link.url)\n            return vcs_backend\n\n\ndef is_vcs_url(link):\n    # type: (Link) -> bool\n    return bool(_get_used_vcs_backend(link))\n\n\ndef is_file_url(link):\n    # type: (Link) -> bool\n    return link.url.lower().startswith('file:')\n\n\ndef is_dir_url(link):\n    # type: (Link) -> bool\n    \"\"\"Return whether a file:// Link points to a directory.\n\n    ``link`` must not have any other scheme but file://. Call is_file_url()\n    first.\n\n    \"\"\"\n    link_path = url_to_path(link.url_without_fragment)\n    return os.path.isdir(link_path)\n\n\ndef _progress_indicator(iterable, *args, **kwargs):\n    return iterable\n\n\ndef _download_url(\n    resp,  # type: Response\n    link,  # type: Link\n    content_file,  # type: IO\n    hashes,  # type: Hashes\n    progress_bar  # type: str\n):\n    # type: (...) -> None\n    try:\n        total_length = int(resp.headers['content-length'])\n    except (ValueError, KeyError, TypeError):\n        total_length = 0\n\n    cached_resp = getattr(resp, \"from_cache\", False)\n    if logger.getEffectiveLevel() > logging.INFO:\n        show_progress = False\n    elif cached_resp:\n        show_progress = False\n    elif total_length > (40 * 1000):\n        show_progress = True\n    elif not total_length:\n        show_progress = True\n    else:\n        show_progress = False\n\n    show_url = link.show_url\n\n    def resp_read(chunk_size):\n        try:\n            # Special case for urllib3.\n            for chunk in resp.raw.stream(\n                    chunk_size,\n                    # We use decode_content=False here because we don't\n                    # want urllib3 to mess with the raw bytes we get\n                    # from the server. If we decompress inside of\n                    # urllib3 then we cannot verify the checksum\n                    # because the checksum will be of the compressed\n                    # file. This breakage will only occur if the\n                    # server adds a Content-Encoding header, which\n                    # depends on how the server was configured:\n                    # - Some servers will notice that the file isn't a\n                    #   compressible file and will leave the file alone\n                    #   and with an empty Content-Encoding\n                    # - Some servers will notice that the file is\n                    #   already compressed and will leave the file\n                    #   alone and will add a Content-Encoding: gzip\n                    #   header\n                    # - Some servers won't notice anything at all and\n                    #   will take a file that's already been compressed\n                    #   and compress it again and set the\n                    #   Content-Encoding: gzip header\n                    #\n                    # By setting this not to decode automatically we\n                    # hope to eliminate problems with the second case.\n                    decode_content=False):\n                yield chunk\n        except AttributeError:\n            # Standard file-like object.\n            while True:\n                chunk = resp.raw.read(chunk_size)\n                if not chunk:\n                    break\n                yield chunk\n\n    def written_chunks(chunks):\n        for chunk in chunks:\n            content_file.write(chunk)\n            yield chunk\n\n    progress_indicator = _progress_indicator\n\n    if link.netloc == PyPI.netloc:\n        url = show_url\n    else:\n        url = link.url_without_fragment\n\n    if show_progress:  # We don't show progress on cached responses\n        progress_indicator = DownloadProgressProvider(progress_bar,\n                                                      max=total_length)\n        if total_length:\n            logger.info(\"Downloading %s (%s)\", url, format_size(total_length))\n        else:\n            logger.info(\"Downloading %s\", url)\n    elif cached_resp:\n        logger.info(\"Using cached %s\", url)\n    else:\n        logger.info(\"Downloading %s\", url)\n\n    logger.debug('Downloading from URL %s', link)\n\n    downloaded_chunks = written_chunks(\n        progress_indicator(\n            resp_read(CONTENT_CHUNK_SIZE),\n            CONTENT_CHUNK_SIZE\n        )\n    )\n    if hashes:\n        hashes.check_against_chunks(downloaded_chunks)\n    else:\n        consume(downloaded_chunks)\n\n\ndef _copy_file(filename, location, link):\n    copy = True\n    download_location = os.path.join(location, link.filename)\n    if os.path.exists(download_location):\n        response = ask_path_exists(\n            'The file %s exists. (i)gnore, (w)ipe, (b)ackup, (a)abort' %\n            display_path(download_location), ('i', 'w', 'b', 'a'))\n        if response == 'i':\n            copy = False\n        elif response == 'w':\n            logger.warning('Deleting %s', display_path(download_location))\n            os.remove(download_location)\n        elif response == 'b':\n            dest_file = backup_dir(download_location)\n            logger.warning(\n                'Backing up %s to %s',\n                display_path(download_location),\n                display_path(dest_file),\n            )\n            shutil.move(download_location, dest_file)\n        elif response == 'a':\n            sys.exit(-1)\n    if copy:\n        shutil.copy(filename, download_location)\n        logger.info('Saved %s', display_path(download_location))\n\n\ndef unpack_http_url(\n    link,  # type: Link\n    location,  # type: str\n    download_dir=None,  # type: Optional[str]\n    session=None,  # type: Optional[PipSession]\n    hashes=None,  # type: Optional[Hashes]\n    progress_bar=\"on\"  # type: str\n):\n    # type: (...) -> None\n    if session is None:\n        raise TypeError(\n            \"unpack_http_url() missing 1 required keyword argument: 'session'\"\n        )\n\n    with TempDirectory(kind=\"unpack\") as temp_dir:\n        # If a download dir is specified, is the file already downloaded there?\n        already_downloaded_path = None\n        if download_dir:\n            already_downloaded_path = _check_download_dir(link,\n                                                          download_dir,\n                                                          hashes)\n\n        if already_downloaded_path:\n            from_path = already_downloaded_path\n            content_type = mimetypes.guess_type(from_path)[0]\n        else:\n            # let's download to a tmp dir\n            from_path, content_type = _download_http_url(link,\n                                                         session,\n                                                         temp_dir.path,\n                                                         hashes,\n                                                         progress_bar)\n\n        # unpack the archive to the build dir location. even when only\n        # downloading archives, they have to be unpacked to parse dependencies\n        unpack_file(from_path, location, content_type, link)\n\n        # a download dir is specified; let's copy the archive there\n        if download_dir and not already_downloaded_path:\n            _copy_file(from_path, download_dir, link)\n\n        if not already_downloaded_path:\n            os.unlink(from_path)\n\n\ndef unpack_file_url(\n    link,  # type: Link\n    location,  # type: str\n    download_dir=None,  # type: Optional[str]\n    hashes=None  # type: Optional[Hashes]\n):\n    # type: (...) -> None\n    \"\"\"Unpack link into location.\n\n    If download_dir is provided and link points to a file, make a copy\n    of the link file inside download_dir.\n    \"\"\"\n    link_path = url_to_path(link.url_without_fragment)\n\n    # If it's a url to a local directory\n    if is_dir_url(link):\n        if os.path.isdir(location):\n            rmtree(location)\n        shutil.copytree(link_path, location, symlinks=True)\n        if download_dir:\n            logger.info('Link is a directory, ignoring download_dir')\n        return\n\n    # If --require-hashes is off, `hashes` is either empty, the\n    # link's embedded hash, or MissingHashes; it is required to\n    # match. If --require-hashes is on, we are satisfied by any\n    # hash in `hashes` matching: a URL-based or an option-based\n    # one; no internet-sourced hash will be in `hashes`.\n    if hashes:\n        hashes.check_against_path(link_path)\n\n    # If a download dir is specified, is the file already there and valid?\n    already_downloaded_path = None\n    if download_dir:\n        already_downloaded_path = _check_download_dir(link,\n                                                      download_dir,\n                                                      hashes)\n\n    if already_downloaded_path:\n        from_path = already_downloaded_path\n    else:\n        from_path = link_path\n\n    content_type = mimetypes.guess_type(from_path)[0]\n\n    # unpack the archive to the build dir location. even when only downloading\n    # archives, they have to be unpacked to parse dependencies\n    unpack_file(from_path, location, content_type, link)\n\n    # a download dir is specified and not already downloaded\n    if download_dir and not already_downloaded_path:\n        _copy_file(from_path, download_dir, link)\n\n\ndef _copy_dist_from_dir(link_path, location):\n    \"\"\"Copy distribution files in `link_path` to `location`.\n\n    Invoked when user requests to install a local directory. E.g.:\n\n        pip install .\n        pip install ~/dev/git-repos/python-prompt-toolkit\n\n    \"\"\"\n\n    # Note: This is currently VERY SLOW if you have a lot of data in the\n    # directory, because it copies everything with `shutil.copytree`.\n    # What it should really do is build an sdist and install that.\n    # See https://github.com/pypa/pip/issues/2195\n\n    if os.path.isdir(location):\n        rmtree(location)\n\n    # build an sdist\n    setup_py = 'setup.py'\n    sdist_args = [sys.executable]\n    sdist_args.append('-c')\n    sdist_args.append(SETUPTOOLS_SHIM % setup_py)\n    sdist_args.append('sdist')\n    sdist_args += ['--dist-dir', location]\n    logger.info('Running setup.py sdist for %s', link_path)\n\n    with indent_log():\n        call_subprocess(sdist_args, cwd=link_path, show_stdout=False)\n\n    # unpack sdist into `location`\n    sdist = os.path.join(location, os.listdir(location)[0])\n    logger.info('Unpacking sdist %s into %s', sdist, location)\n    unpack_file(sdist, location, content_type=None, link=None)\n\n\nclass PipXmlrpcTransport(xmlrpc_client.Transport):\n    \"\"\"Provide a `xmlrpclib.Transport` implementation via a `PipSession`\n    object.\n    \"\"\"\n\n    def __init__(self, index_url, session, use_datetime=False):\n        xmlrpc_client.Transport.__init__(self, use_datetime)\n        index_parts = urllib_parse.urlparse(index_url)\n        self._scheme = index_parts.scheme\n        self._session = session\n\n    def request(self, host, handler, request_body, verbose=False):\n        parts = (self._scheme, host, handler, None, None, None)\n        url = urllib_parse.urlunparse(parts)\n        try:\n            headers = {'Content-Type': 'text/xml'}\n            response = self._session.post(url, data=request_body,\n                                          headers=headers, stream=True)\n            response.raise_for_status()\n            self.verbose = verbose\n            return self.parse_response(response.raw)\n        except requests.HTTPError as exc:\n            logger.critical(\n                \"HTTP error %s while getting %s\",\n                exc.response.status_code, url,\n            )\n            raise\n\n\ndef unpack_url(\n    link,  # type: Optional[Link]\n    location,  # type: Optional[str]\n    download_dir=None,  # type: Optional[str]\n    only_download=False,  # type: bool\n    session=None,  # type: Optional[PipSession]\n    hashes=None,  # type: Optional[Hashes]\n    progress_bar=\"on\"  # type: str\n):\n    # type: (...) -> None\n    \"\"\"Unpack link.\n       If link is a VCS link:\n         if only_download, export into download_dir and ignore location\n          else unpack into location\n       for other types of link:\n         - unpack into location\n         - if download_dir, copy the file into download_dir\n         - if only_download, mark location for deletion\n\n    :param hashes: A Hashes object, one of whose embedded hashes must match,\n        or HashMismatch will be raised. If the Hashes is empty, no matches are\n        required, and unhashable types of requirements (like VCS ones, which\n        would ordinarily raise HashUnsupported) are allowed.\n    \"\"\"\n    # non-editable vcs urls\n    if is_vcs_url(link):\n        unpack_vcs_link(link, location)\n\n    # file urls\n    elif is_file_url(link):\n        unpack_file_url(link, location, download_dir, hashes=hashes)\n\n    # http urls\n    else:\n        if session is None:\n            session = PipSession()\n\n        unpack_http_url(\n            link,\n            location,\n            download_dir,\n            session,\n            hashes=hashes,\n            progress_bar=progress_bar\n        )\n    if only_download:\n        write_delete_marker_file(location)\n\n\ndef _download_http_url(\n    link,  # type: Link\n    session,  # type: PipSession\n    temp_dir,  # type: str\n    hashes,  # type: Hashes\n    progress_bar  # type: str\n):\n    # type: (...) -> Tuple[str, str]\n    \"\"\"Download link url into temp_dir using provided session\"\"\"\n    target_url = link.url.split('#', 1)[0]\n    try:\n        resp = session.get(\n            target_url,\n            # We use Accept-Encoding: identity here because requests\n            # defaults to accepting compressed responses. This breaks in\n            # a variety of ways depending on how the server is configured.\n            # - Some servers will notice that the file isn't a compressible\n            #   file and will leave the file alone and with an empty\n            #   Content-Encoding\n            # - Some servers will notice that the file is already\n            #   compressed and will leave the file alone and will add a\n            #   Content-Encoding: gzip header\n            # - Some servers won't notice anything at all and will take\n            #   a file that's already been compressed and compress it again\n            #   and set the Content-Encoding: gzip header\n            # By setting this to request only the identity encoding We're\n            # hoping to eliminate the third case. Hopefully there does not\n            # exist a server which when given a file will notice it is\n            # already compressed and that you're not asking for a\n            # compressed file and will then decompress it before sending\n            # because if that's the case I don't think it'll ever be\n            # possible to make this work.\n            headers={\"Accept-Encoding\": \"identity\"},\n            stream=True,\n        )\n        resp.raise_for_status()\n    except requests.HTTPError as exc:\n        logger.critical(\n            \"HTTP error %s while getting %s\", exc.response.status_code, link,\n        )\n        raise\n\n    content_type = resp.headers.get('content-type', '')\n    filename = link.filename  # fallback\n    # Have a look at the Content-Disposition header for a better guess\n    content_disposition = resp.headers.get('content-disposition')\n    if content_disposition:\n        type, params = cgi.parse_header(content_disposition)\n        # We use ``or`` here because we don't want to use an \"empty\" value\n        # from the filename param.\n        filename = params.get('filename') or filename\n    ext = splitext(filename)[1]\n    if not ext:\n        ext = mimetypes.guess_extension(content_type)\n        if ext:\n            filename += ext\n    if not ext and link.url != resp.url:\n        ext = os.path.splitext(resp.url)[1]\n        if ext:\n            filename += ext\n    file_path = os.path.join(temp_dir, filename)\n    with open(file_path, 'wb') as content_file:\n        _download_url(resp, link, content_file, hashes, progress_bar)\n    return file_path, content_type\n\n\ndef _check_download_dir(link, download_dir, hashes):\n    # type: (Link, str, Hashes) -> Optional[str]\n    \"\"\" Check download_dir for previously downloaded file with correct hash\n        If a correct file is found return its path else None\n    \"\"\"\n    download_path = os.path.join(download_dir, link.filename)\n    if os.path.exists(download_path):\n        # If already downloaded, does its hash match?\n        logger.info('File was already downloaded %s', download_path)\n        if hashes:\n            try:\n                hashes.check_against_path(download_path)\n            except HashMismatch:\n                logger.warning(\n                    'Previously-downloaded file %s has bad hash. '\n                    'Re-downloading.',\n                    download_path\n                )\n                os.unlink(download_path)\n                return None\n        return download_path\n    return None\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/exceptions.py",
    "content": "\"\"\"Exceptions used throughout package\"\"\"\nfrom __future__ import absolute_import\n\nfrom itertools import chain, groupby, repeat\n\nfrom pip._vendor.six import iteritems\n\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Optional  # noqa: F401\n    from pip._internal.req.req_install import InstallRequirement  # noqa: F401\n\n\nclass PipError(Exception):\n    \"\"\"Base pip exception\"\"\"\n\n\nclass ConfigurationError(PipError):\n    \"\"\"General exception in configuration\"\"\"\n\n\nclass InstallationError(PipError):\n    \"\"\"General exception during installation\"\"\"\n\n\nclass UninstallationError(PipError):\n    \"\"\"General exception during uninstallation\"\"\"\n\n\nclass DistributionNotFound(InstallationError):\n    \"\"\"Raised when a distribution cannot be found to satisfy a requirement\"\"\"\n\n\nclass RequirementsFileParseError(InstallationError):\n    \"\"\"Raised when a general error occurs parsing a requirements file line.\"\"\"\n\n\nclass BestVersionAlreadyInstalled(PipError):\n    \"\"\"Raised when the most up-to-date version of a package is already\n    installed.\"\"\"\n\n\nclass BadCommand(PipError):\n    \"\"\"Raised when virtualenv or a command is not found\"\"\"\n\n\nclass CommandError(PipError):\n    \"\"\"Raised when there is an error in command-line arguments\"\"\"\n\n\nclass PreviousBuildDirError(PipError):\n    \"\"\"Raised when there's a previous conflicting build directory\"\"\"\n\n\nclass InvalidWheelFilename(InstallationError):\n    \"\"\"Invalid wheel filename.\"\"\"\n\n\nclass UnsupportedWheel(InstallationError):\n    \"\"\"Unsupported wheel.\"\"\"\n\n\nclass HashErrors(InstallationError):\n    \"\"\"Multiple HashError instances rolled into one for reporting\"\"\"\n\n    def __init__(self):\n        self.errors = []\n\n    def append(self, error):\n        self.errors.append(error)\n\n    def __str__(self):\n        lines = []\n        self.errors.sort(key=lambda e: e.order)\n        for cls, errors_of_cls in groupby(self.errors, lambda e: e.__class__):\n            lines.append(cls.head)\n            lines.extend(e.body() for e in errors_of_cls)\n        if lines:\n            return '\\n'.join(lines)\n\n    def __nonzero__(self):\n        return bool(self.errors)\n\n    def __bool__(self):\n        return self.__nonzero__()\n\n\nclass HashError(InstallationError):\n    \"\"\"\n    A failure to verify a package against known-good hashes\n\n    :cvar order: An int sorting hash exception classes by difficulty of\n        recovery (lower being harder), so the user doesn't bother fretting\n        about unpinned packages when he has deeper issues, like VCS\n        dependencies, to deal with. Also keeps error reports in a\n        deterministic order.\n    :cvar head: A section heading for display above potentially many\n        exceptions of this kind\n    :ivar req: The InstallRequirement that triggered this error. This is\n        pasted on after the exception is instantiated, because it's not\n        typically available earlier.\n\n    \"\"\"\n    req = None  # type: Optional[InstallRequirement]\n    head = ''\n\n    def body(self):\n        \"\"\"Return a summary of me for display under the heading.\n\n        This default implementation simply prints a description of the\n        triggering requirement.\n\n        :param req: The InstallRequirement that provoked this error, with\n            populate_link() having already been called\n\n        \"\"\"\n        return '    %s' % self._requirement_name()\n\n    def __str__(self):\n        return '%s\\n%s' % (self.head, self.body())\n\n    def _requirement_name(self):\n        \"\"\"Return a description of the requirement that triggered me.\n\n        This default implementation returns long description of the req, with\n        line numbers\n\n        \"\"\"\n        return str(self.req) if self.req else 'unknown package'\n\n\nclass VcsHashUnsupported(HashError):\n    \"\"\"A hash was provided for a version-control-system-based requirement, but\n    we don't have a method for hashing those.\"\"\"\n\n    order = 0\n    head = (\"Can't verify hashes for these requirements because we don't \"\n            \"have a way to hash version control repositories:\")\n\n\nclass DirectoryUrlHashUnsupported(HashError):\n    \"\"\"A hash was provided for a version-control-system-based requirement, but\n    we don't have a method for hashing those.\"\"\"\n\n    order = 1\n    head = (\"Can't verify hashes for these file:// requirements because they \"\n            \"point to directories:\")\n\n\nclass HashMissing(HashError):\n    \"\"\"A hash was needed for a requirement but is absent.\"\"\"\n\n    order = 2\n    head = ('Hashes are required in --require-hashes mode, but they are '\n            'missing from some requirements. Here is a list of those '\n            'requirements along with the hashes their downloaded archives '\n            'actually had. Add lines like these to your requirements files to '\n            'prevent tampering. (If you did not enable --require-hashes '\n            'manually, note that it turns on automatically when any package '\n            'has a hash.)')\n\n    def __init__(self, gotten_hash):\n        \"\"\"\n        :param gotten_hash: The hash of the (possibly malicious) archive we\n            just downloaded\n        \"\"\"\n        self.gotten_hash = gotten_hash\n\n    def body(self):\n        # Dodge circular import.\n        from pip._internal.utils.hashes import FAVORITE_HASH\n\n        package = None\n        if self.req:\n            # In the case of URL-based requirements, display the original URL\n            # seen in the requirements file rather than the package name,\n            # so the output can be directly copied into the requirements file.\n            package = (self.req.original_link if self.req.original_link\n                       # In case someone feeds something downright stupid\n                       # to InstallRequirement's constructor.\n                       else getattr(self.req, 'req', None))\n        return '    %s --hash=%s:%s' % (package or 'unknown package',\n                                        FAVORITE_HASH,\n                                        self.gotten_hash)\n\n\nclass HashUnpinned(HashError):\n    \"\"\"A requirement had a hash specified but was not pinned to a specific\n    version.\"\"\"\n\n    order = 3\n    head = ('In --require-hashes mode, all requirements must have their '\n            'versions pinned with ==. These do not:')\n\n\nclass HashMismatch(HashError):\n    \"\"\"\n    Distribution file hash values don't match.\n\n    :ivar package_name: The name of the package that triggered the hash\n        mismatch. Feel free to write to this after the exception is raise to\n        improve its error message.\n\n    \"\"\"\n    order = 4\n    head = ('THESE PACKAGES DO NOT MATCH THE HASHES FROM THE REQUIREMENTS '\n            'FILE. If you have updated the package versions, please update '\n            'the hashes. Otherwise, examine the package contents carefully; '\n            'someone may have tampered with them.')\n\n    def __init__(self, allowed, gots):\n        \"\"\"\n        :param allowed: A dict of algorithm names pointing to lists of allowed\n            hex digests\n        :param gots: A dict of algorithm names pointing to hashes we\n            actually got from the files under suspicion\n        \"\"\"\n        self.allowed = allowed\n        self.gots = gots\n\n    def body(self):\n        return '    %s:\\n%s' % (self._requirement_name(),\n                                self._hash_comparison())\n\n    def _hash_comparison(self):\n        \"\"\"\n        Return a comparison of actual and expected hash values.\n\n        Example::\n\n               Expected sha256 abcdeabcdeabcdeabcdeabcdeabcdeabcdeabcdeabcde\n                            or 123451234512345123451234512345123451234512345\n                    Got        bcdefbcdefbcdefbcdefbcdefbcdefbcdefbcdefbcdef\n\n        \"\"\"\n        def hash_then_or(hash_name):\n            # For now, all the decent hashes have 6-char names, so we can get\n            # away with hard-coding space literals.\n            return chain([hash_name], repeat('    or'))\n\n        lines = []\n        for hash_name, expecteds in iteritems(self.allowed):\n            prefix = hash_then_or(hash_name)\n            lines.extend(('        Expected %s %s' % (next(prefix), e))\n                         for e in expecteds)\n            lines.append('             Got        %s\\n' %\n                         self.gots[hash_name].hexdigest())\n            prefix = '    or'\n        return '\\n'.join(lines)\n\n\nclass UnsupportedPythonVersion(InstallationError):\n    \"\"\"Unsupported python version according to Requires-Python package\n    metadata.\"\"\"\n\n\nclass ConfigurationFileCouldNotBeLoaded(ConfigurationError):\n    \"\"\"When there are errors while loading a configuration file\n    \"\"\"\n\n    def __init__(self, reason=\"could not be loaded\", fname=None, error=None):\n        super(ConfigurationFileCouldNotBeLoaded, self).__init__(error)\n        self.reason = reason\n        self.fname = fname\n        self.error = error\n\n    def __str__(self):\n        if self.fname is not None:\n            message_part = \" in {}.\".format(self.fname)\n        else:\n            assert self.error is not None\n            message_part = \".\\n{}\\n\".format(self.error.message)\n        return \"Configuration file {}{}\".format(self.reason, message_part)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/index.py",
    "content": "\"\"\"Routines related to PyPI, indexes\"\"\"\nfrom __future__ import absolute_import\n\nimport cgi\nimport itertools\nimport logging\nimport mimetypes\nimport os\nimport posixpath\nimport re\nimport sys\nfrom collections import namedtuple\n\nfrom pip._vendor import html5lib, requests, six\nfrom pip._vendor.distlib.compat import unescape\nfrom pip._vendor.packaging import specifiers\nfrom pip._vendor.packaging.utils import canonicalize_name\nfrom pip._vendor.packaging.version import parse as parse_version\nfrom pip._vendor.requests.exceptions import RetryError, SSLError\nfrom pip._vendor.six.moves.urllib import parse as urllib_parse\nfrom pip._vendor.six.moves.urllib import request as urllib_request\n\nfrom pip._internal.download import HAS_TLS, is_url, path_to_url, url_to_path\nfrom pip._internal.exceptions import (\n    BestVersionAlreadyInstalled, DistributionNotFound, InvalidWheelFilename,\n    UnsupportedWheel,\n)\nfrom pip._internal.models.candidate import InstallationCandidate\nfrom pip._internal.models.format_control import FormatControl\nfrom pip._internal.models.index import PyPI\nfrom pip._internal.models.link import Link\nfrom pip._internal.pep425tags import get_supported\nfrom pip._internal.utils.compat import ipaddress\nfrom pip._internal.utils.logging import indent_log\nfrom pip._internal.utils.misc import (\n    ARCHIVE_EXTENSIONS, SUPPORTED_EXTENSIONS, WHEEL_EXTENSION, normalize_path,\n    redact_password_from_url,\n)\nfrom pip._internal.utils.packaging import check_requires_python\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\nfrom pip._internal.wheel import Wheel\n\nif MYPY_CHECK_RUNNING:\n    from logging import Logger  # noqa: F401\n    from typing import (  # noqa: F401\n        Tuple, Optional, Any, List, Union, Callable, Set, Sequence,\n        Iterable, MutableMapping\n    )\n    from pip._vendor.packaging.version import _BaseVersion  # noqa: F401\n    from pip._vendor.requests import Response  # noqa: F401\n    from pip._internal.req import InstallRequirement  # noqa: F401\n    from pip._internal.download import PipSession  # noqa: F401\n\n    SecureOrigin = Tuple[str, str, Optional[str]]\n    BuildTag = Tuple[Any, ...]  # either emply tuple or Tuple[int, str]\n    CandidateSortingKey = Tuple[int, _BaseVersion, BuildTag, Optional[int]]\n\n__all__ = ['FormatControl', 'PackageFinder']\n\n\nSECURE_ORIGINS = [\n    # protocol, hostname, port\n    # Taken from Chrome's list of secure origins (See: http://bit.ly/1qrySKC)\n    (\"https\", \"*\", \"*\"),\n    (\"*\", \"localhost\", \"*\"),\n    (\"*\", \"127.0.0.0/8\", \"*\"),\n    (\"*\", \"::1/128\", \"*\"),\n    (\"file\", \"*\", None),\n    # ssh is always secure.\n    (\"ssh\", \"*\", \"*\"),\n]  # type: List[SecureOrigin]\n\n\nlogger = logging.getLogger(__name__)\n\n\ndef _match_vcs_scheme(url):\n    # type: (str) -> Optional[str]\n    \"\"\"Look for VCS schemes in the URL.\n\n    Returns the matched VCS scheme, or None if there's no match.\n    \"\"\"\n    from pip._internal.vcs import VcsSupport\n    for scheme in VcsSupport.schemes:\n        if url.lower().startswith(scheme) and url[len(scheme)] in '+:':\n            return scheme\n    return None\n\n\ndef _is_url_like_archive(url):\n    # type: (str) -> bool\n    \"\"\"Return whether the URL looks like an archive.\n    \"\"\"\n    filename = Link(url).filename\n    for bad_ext in ARCHIVE_EXTENSIONS:\n        if filename.endswith(bad_ext):\n            return True\n    return False\n\n\nclass _NotHTML(Exception):\n    def __init__(self, content_type, request_desc):\n        # type: (str, str) -> None\n        super(_NotHTML, self).__init__(content_type, request_desc)\n        self.content_type = content_type\n        self.request_desc = request_desc\n\n\ndef _ensure_html_header(response):\n    # type: (Response) -> None\n    \"\"\"Check the Content-Type header to ensure the response contains HTML.\n\n    Raises `_NotHTML` if the content type is not text/html.\n    \"\"\"\n    content_type = response.headers.get(\"Content-Type\", \"\")\n    if not content_type.lower().startswith(\"text/html\"):\n        raise _NotHTML(content_type, response.request.method)\n\n\nclass _NotHTTP(Exception):\n    pass\n\n\ndef _ensure_html_response(url, session):\n    # type: (str, PipSession) -> None\n    \"\"\"Send a HEAD request to the URL, and ensure the response contains HTML.\n\n    Raises `_NotHTTP` if the URL is not available for a HEAD request, or\n    `_NotHTML` if the content type is not text/html.\n    \"\"\"\n    scheme, netloc, path, query, fragment = urllib_parse.urlsplit(url)\n    if scheme not in {'http', 'https'}:\n        raise _NotHTTP()\n\n    resp = session.head(url, allow_redirects=True)\n    resp.raise_for_status()\n\n    _ensure_html_header(resp)\n\n\ndef _get_html_response(url, session):\n    # type: (str, PipSession) -> Response\n    \"\"\"Access an HTML page with GET, and return the response.\n\n    This consists of three parts:\n\n    1. If the URL looks suspiciously like an archive, send a HEAD first to\n       check the Content-Type is HTML, to avoid downloading a large file.\n       Raise `_NotHTTP` if the content type cannot be determined, or\n       `_NotHTML` if it is not HTML.\n    2. Actually perform the request. Raise HTTP exceptions on network failures.\n    3. Check the Content-Type header to make sure we got HTML, and raise\n       `_NotHTML` otherwise.\n    \"\"\"\n    if _is_url_like_archive(url):\n        _ensure_html_response(url, session=session)\n\n    logger.debug('Getting page %s', url)\n\n    resp = session.get(\n        url,\n        headers={\n            \"Accept\": \"text/html\",\n            # We don't want to blindly returned cached data for\n            # /simple/, because authors generally expecting that\n            # twine upload && pip install will function, but if\n            # they've done a pip install in the last ~10 minutes\n            # it won't. Thus by setting this to zero we will not\n            # blindly use any cached data, however the benefit of\n            # using max-age=0 instead of no-cache, is that we will\n            # still support conditional requests, so we will still\n            # minimize traffic sent in cases where the page hasn't\n            # changed at all, we will just always incur the round\n            # trip for the conditional GET now instead of only\n            # once per 10 minutes.\n            # For more information, please see pypa/pip#5670.\n            \"Cache-Control\": \"max-age=0\",\n        },\n    )\n    resp.raise_for_status()\n\n    # The check for archives above only works if the url ends with\n    # something that looks like an archive. However that is not a\n    # requirement of an url. Unless we issue a HEAD request on every\n    # url we cannot know ahead of time for sure if something is HTML\n    # or not. However we can check after we've downloaded it.\n    _ensure_html_header(resp)\n\n    return resp\n\n\ndef _handle_get_page_fail(\n    link,  # type: Link\n    reason,  # type: Union[str, Exception]\n    meth=None  # type: Optional[Callable[..., None]]\n):\n    # type: (...) -> None\n    if meth is None:\n        meth = logger.debug\n    meth(\"Could not fetch URL %s: %s - skipping\", link, reason)\n\n\ndef _get_html_page(link, session=None):\n    # type: (Link, Optional[PipSession]) -> Optional[HTMLPage]\n    if session is None:\n        raise TypeError(\n            \"_get_html_page() missing 1 required keyword argument: 'session'\"\n        )\n\n    url = link.url.split('#', 1)[0]\n\n    # Check for VCS schemes that do not support lookup as web pages.\n    vcs_scheme = _match_vcs_scheme(url)\n    if vcs_scheme:\n        logger.debug('Cannot look at %s URL %s', vcs_scheme, link)\n        return None\n\n    # Tack index.html onto file:// URLs that point to directories\n    scheme, _, path, _, _, _ = urllib_parse.urlparse(url)\n    if (scheme == 'file' and os.path.isdir(urllib_request.url2pathname(path))):\n        # add trailing slash if not present so urljoin doesn't trim\n        # final segment\n        if not url.endswith('/'):\n            url += '/'\n        url = urllib_parse.urljoin(url, 'index.html')\n        logger.debug(' file: URL is directory, getting %s', url)\n\n    try:\n        resp = _get_html_response(url, session=session)\n    except _NotHTTP as exc:\n        logger.debug(\n            'Skipping page %s because it looks like an archive, and cannot '\n            'be checked by HEAD.', link,\n        )\n    except _NotHTML as exc:\n        logger.debug(\n            'Skipping page %s because the %s request got Content-Type: %s',\n            link, exc.request_desc, exc.content_type,\n        )\n    except requests.HTTPError as exc:\n        _handle_get_page_fail(link, exc)\n    except RetryError as exc:\n        _handle_get_page_fail(link, exc)\n    except SSLError as exc:\n        reason = \"There was a problem confirming the ssl certificate: \"\n        reason += str(exc)\n        _handle_get_page_fail(link, reason, meth=logger.info)\n    except requests.ConnectionError as exc:\n        _handle_get_page_fail(link, \"connection error: %s\" % exc)\n    except requests.Timeout:\n        _handle_get_page_fail(link, \"timed out\")\n    else:\n        return HTMLPage(resp.content, resp.url, resp.headers)\n    return None\n\n\nclass PackageFinder(object):\n    \"\"\"This finds packages.\n\n    This is meant to match easy_install's technique for looking for\n    packages, by reading pages and looking for appropriate links.\n    \"\"\"\n\n    def __init__(\n        self,\n        find_links,  # type: List[str]\n        index_urls,  # type: List[str]\n        allow_all_prereleases=False,  # type: bool\n        trusted_hosts=None,  # type: Optional[Iterable[str]]\n        session=None,  # type: Optional[PipSession]\n        format_control=None,  # type: Optional[FormatControl]\n        platform=None,  # type: Optional[str]\n        versions=None,  # type: Optional[List[str]]\n        abi=None,  # type: Optional[str]\n        implementation=None,  # type: Optional[str]\n        prefer_binary=False  # type: bool\n    ):\n        # type: (...) -> None\n        \"\"\"Create a PackageFinder.\n\n        :param format_control: A FormatControl object or None. Used to control\n            the selection of source packages / binary packages when consulting\n            the index and links.\n        :param platform: A string or None. If None, searches for packages\n            that are supported by the current system. Otherwise, will find\n            packages that can be built on the platform passed in. These\n            packages will only be downloaded for distribution: they will\n            not be built locally.\n        :param versions: A list of strings or None. This is passed directly\n            to pep425tags.py in the get_supported() method.\n        :param abi: A string or None. This is passed directly\n            to pep425tags.py in the get_supported() method.\n        :param implementation: A string or None. This is passed directly\n            to pep425tags.py in the get_supported() method.\n        \"\"\"\n        if session is None:\n            raise TypeError(\n                \"PackageFinder() missing 1 required keyword argument: \"\n                \"'session'\"\n            )\n\n        # Build find_links. If an argument starts with ~, it may be\n        # a local file relative to a home directory. So try normalizing\n        # it and if it exists, use the normalized version.\n        # This is deliberately conservative - it might be fine just to\n        # blindly normalize anything starting with a ~...\n        self.find_links = []  # type: List[str]\n        for link in find_links:\n            if link.startswith('~'):\n                new_link = normalize_path(link)\n                if os.path.exists(new_link):\n                    link = new_link\n            self.find_links.append(link)\n\n        self.index_urls = index_urls\n\n        # These are boring links that have already been logged somehow:\n        self.logged_links = set()  # type: Set[Link]\n\n        self.format_control = format_control or FormatControl(set(), set())\n\n        # Domains that we won't emit warnings for when not using HTTPS\n        self.secure_origins = [\n            (\"*\", host, \"*\")\n            for host in (trusted_hosts if trusted_hosts else [])\n        ]  # type: List[SecureOrigin]\n\n        # Do we want to allow _all_ pre-releases?\n        self.allow_all_prereleases = allow_all_prereleases\n\n        # The Session we'll use to make requests\n        self.session = session\n\n        # The valid tags to check potential found wheel candidates against\n        self.valid_tags = get_supported(\n            versions=versions,\n            platform=platform,\n            abi=abi,\n            impl=implementation,\n        )\n\n        # Do we prefer old, but valid, binary dist over new source dist\n        self.prefer_binary = prefer_binary\n\n        # If we don't have TLS enabled, then WARN if anyplace we're looking\n        # relies on TLS.\n        if not HAS_TLS:\n            for link in itertools.chain(self.index_urls, self.find_links):\n                parsed = urllib_parse.urlparse(link)\n                if parsed.scheme == \"https\":\n                    logger.warning(\n                        \"pip is configured with locations that require \"\n                        \"TLS/SSL, however the ssl module in Python is not \"\n                        \"available.\"\n                    )\n                    break\n\n    def get_formatted_locations(self):\n        # type: () -> str\n        lines = []\n        if self.index_urls and self.index_urls != [PyPI.simple_url]:\n            lines.append(\n                \"Looking in indexes: {}\".format(\", \".join(\n                    redact_password_from_url(url) for url in self.index_urls))\n            )\n        if self.find_links:\n            lines.append(\n                \"Looking in links: {}\".format(\", \".join(self.find_links))\n            )\n        return \"\\n\".join(lines)\n\n    @staticmethod\n    def _sort_locations(locations, expand_dir=False):\n        # type: (Sequence[str], bool) -> Tuple[List[str], List[str]]\n        \"\"\"\n        Sort locations into \"files\" (archives) and \"urls\", and return\n        a pair of lists (files,urls)\n        \"\"\"\n        files = []\n        urls = []\n\n        # puts the url for the given file path into the appropriate list\n        def sort_path(path):\n            url = path_to_url(path)\n            if mimetypes.guess_type(url, strict=False)[0] == 'text/html':\n                urls.append(url)\n            else:\n                files.append(url)\n\n        for url in locations:\n\n            is_local_path = os.path.exists(url)\n            is_file_url = url.startswith('file:')\n\n            if is_local_path or is_file_url:\n                if is_local_path:\n                    path = url\n                else:\n                    path = url_to_path(url)\n                if os.path.isdir(path):\n                    if expand_dir:\n                        path = os.path.realpath(path)\n                        for item in os.listdir(path):\n                            sort_path(os.path.join(path, item))\n                    elif is_file_url:\n                        urls.append(url)\n                    else:\n                        logger.warning(\n                            \"Path '{0}' is ignored: \"\n                            \"it is a directory.\".format(path),\n                        )\n                elif os.path.isfile(path):\n                    sort_path(path)\n                else:\n                    logger.warning(\n                        \"Url '%s' is ignored: it is neither a file \"\n                        \"nor a directory.\", url,\n                    )\n            elif is_url(url):\n                # Only add url with clear scheme\n                urls.append(url)\n            else:\n                logger.warning(\n                    \"Url '%s' is ignored. It is either a non-existing \"\n                    \"path or lacks a specific scheme.\", url,\n                )\n\n        return files, urls\n\n    def _candidate_sort_key(self, candidate):\n        # type: (InstallationCandidate) -> CandidateSortingKey\n        \"\"\"\n        Function used to generate link sort key for link tuples.\n        The greater the return value, the more preferred it is.\n        If not finding wheels, then sorted by version only.\n        If finding wheels, then the sort order is by version, then:\n          1. existing installs\n          2. wheels ordered via Wheel.support_index_min(self.valid_tags)\n          3. source archives\n        If prefer_binary was set, then all wheels are sorted above sources.\n        Note: it was considered to embed this logic into the Link\n              comparison operators, but then different sdist links\n              with the same version, would have to be considered equal\n        \"\"\"\n        support_num = len(self.valid_tags)\n        build_tag = tuple()  # type: BuildTag\n        binary_preference = 0\n        if candidate.location.is_wheel:\n            # can raise InvalidWheelFilename\n            wheel = Wheel(candidate.location.filename)\n            if not wheel.supported(self.valid_tags):\n                raise UnsupportedWheel(\n                    \"%s is not a supported wheel for this platform. It \"\n                    \"can't be sorted.\" % wheel.filename\n                )\n            if self.prefer_binary:\n                binary_preference = 1\n            pri = -(wheel.support_index_min(self.valid_tags))\n            if wheel.build_tag is not None:\n                match = re.match(r'^(\\d+)(.*)$', wheel.build_tag)\n                build_tag_groups = match.groups()\n                build_tag = (int(build_tag_groups[0]), build_tag_groups[1])\n        else:  # sdist\n            pri = -(support_num)\n        return (binary_preference, candidate.version, build_tag, pri)\n\n    def _validate_secure_origin(self, logger, location):\n        # type: (Logger, Link) -> bool\n        # Determine if this url used a secure transport mechanism\n        parsed = urllib_parse.urlparse(str(location))\n        origin = (parsed.scheme, parsed.hostname, parsed.port)\n\n        # The protocol to use to see if the protocol matches.\n        # Don't count the repository type as part of the protocol: in\n        # cases such as \"git+ssh\", only use \"ssh\". (I.e., Only verify against\n        # the last scheme.)\n        protocol = origin[0].rsplit('+', 1)[-1]\n\n        # Determine if our origin is a secure origin by looking through our\n        # hardcoded list of secure origins, as well as any additional ones\n        # configured on this PackageFinder instance.\n        for secure_origin in (SECURE_ORIGINS + self.secure_origins):\n            if protocol != secure_origin[0] and secure_origin[0] != \"*\":\n                continue\n\n            try:\n                # We need to do this decode dance to ensure that we have a\n                # unicode object, even on Python 2.x.\n                addr = ipaddress.ip_address(\n                    origin[1]\n                    if (\n                        isinstance(origin[1], six.text_type) or\n                        origin[1] is None\n                    )\n                    else origin[1].decode(\"utf8\")\n                )\n                network = ipaddress.ip_network(\n                    secure_origin[1]\n                    if isinstance(secure_origin[1], six.text_type)\n                    # setting secure_origin[1] to proper Union[bytes, str]\n                    # creates problems in other places\n                    else secure_origin[1].decode(\"utf8\")  # type: ignore\n                )\n            except ValueError:\n                # We don't have both a valid address or a valid network, so\n                # we'll check this origin against hostnames.\n                if (origin[1] and\n                        origin[1].lower() != secure_origin[1].lower() and\n                        secure_origin[1] != \"*\"):\n                    continue\n            else:\n                # We have a valid address and network, so see if the address\n                # is contained within the network.\n                if addr not in network:\n                    continue\n\n            # Check to see if the port patches\n            if (origin[2] != secure_origin[2] and\n                    secure_origin[2] != \"*\" and\n                    secure_origin[2] is not None):\n                continue\n\n            # If we've gotten here, then this origin matches the current\n            # secure origin and we should return True\n            return True\n\n        # If we've gotten to this point, then the origin isn't secure and we\n        # will not accept it as a valid location to search. We will however\n        # log a warning that we are ignoring it.\n        logger.warning(\n            \"The repository located at %s is not a trusted or secure host and \"\n            \"is being ignored. If this repository is available via HTTPS we \"\n            \"recommend you use HTTPS instead, otherwise you may silence \"\n            \"this warning and allow it anyway with '--trusted-host %s'.\",\n            parsed.hostname,\n            parsed.hostname,\n        )\n\n        return False\n\n    def _get_index_urls_locations(self, project_name):\n        # type: (str) -> List[str]\n        \"\"\"Returns the locations found via self.index_urls\n\n        Checks the url_name on the main (first in the list) index and\n        use this url_name to produce all locations\n        \"\"\"\n\n        def mkurl_pypi_url(url):\n            loc = posixpath.join(\n                url,\n                urllib_parse.quote(canonicalize_name(project_name)))\n            # For maximum compatibility with easy_install, ensure the path\n            # ends in a trailing slash.  Although this isn't in the spec\n            # (and PyPI can handle it without the slash) some other index\n            # implementations might break if they relied on easy_install's\n            # behavior.\n            if not loc.endswith('/'):\n                loc = loc + '/'\n            return loc\n\n        return [mkurl_pypi_url(url) for url in self.index_urls]\n\n    def find_all_candidates(self, project_name):\n        # type: (str) -> List[Optional[InstallationCandidate]]\n        \"\"\"Find all available InstallationCandidate for project_name\n\n        This checks index_urls and find_links.\n        All versions found are returned as an InstallationCandidate list.\n\n        See _link_package_versions for details on which files are accepted\n        \"\"\"\n        index_locations = self._get_index_urls_locations(project_name)\n        index_file_loc, index_url_loc = self._sort_locations(index_locations)\n        fl_file_loc, fl_url_loc = self._sort_locations(\n            self.find_links, expand_dir=True,\n        )\n\n        file_locations = (Link(url) for url in itertools.chain(\n            index_file_loc, fl_file_loc,\n        ))\n\n        # We trust every url that the user has given us whether it was given\n        #   via --index-url or --find-links.\n        # We want to filter out any thing which does not have a secure origin.\n        url_locations = [\n            link for link in itertools.chain(\n                (Link(url) for url in index_url_loc),\n                (Link(url) for url in fl_url_loc),\n            )\n            if self._validate_secure_origin(logger, link)\n        ]\n\n        logger.debug('%d location(s) to search for versions of %s:',\n                     len(url_locations), project_name)\n\n        for location in url_locations:\n            logger.debug('* %s', location)\n\n        canonical_name = canonicalize_name(project_name)\n        formats = self.format_control.get_allowed_formats(canonical_name)\n        search = Search(project_name, canonical_name, formats)\n        find_links_versions = self._package_versions(\n            # We trust every directly linked archive in find_links\n            (Link(url, '-f') for url in self.find_links),\n            search\n        )\n\n        page_versions = []\n        for page in self._get_pages(url_locations, project_name):\n            logger.debug('Analyzing links from page %s', page.url)\n            with indent_log():\n                page_versions.extend(\n                    self._package_versions(page.iter_links(), search)\n                )\n\n        file_versions = self._package_versions(file_locations, search)\n        if file_versions:\n            file_versions.sort(reverse=True)\n            logger.debug(\n                'Local files found: %s',\n                ', '.join([\n                    url_to_path(candidate.location.url)\n                    for candidate in file_versions\n                ])\n            )\n\n        # This is an intentional priority ordering\n        return file_versions + find_links_versions + page_versions\n\n    def find_requirement(self, req, upgrade):\n        # type: (InstallRequirement, bool) -> Optional[Link]\n        \"\"\"Try to find a Link matching req\n\n        Expects req, an InstallRequirement and upgrade, a boolean\n        Returns a Link if found,\n        Raises DistributionNotFound or BestVersionAlreadyInstalled otherwise\n        \"\"\"\n        all_candidates = self.find_all_candidates(req.name)\n\n        # Filter out anything which doesn't match our specifier\n        compatible_versions = set(\n            req.specifier.filter(\n                # We turn the version object into a str here because otherwise\n                # when we're debundled but setuptools isn't, Python will see\n                # packaging.version.Version and\n                # pkg_resources._vendor.packaging.version.Version as different\n                # types. This way we'll use a str as a common data interchange\n                # format. If we stop using the pkg_resources provided specifier\n                # and start using our own, we can drop the cast to str().\n                [str(c.version) for c in all_candidates],\n                prereleases=(\n                    self.allow_all_prereleases\n                    if self.allow_all_prereleases else None\n                ),\n            )\n        )\n        applicable_candidates = [\n            # Again, converting to str to deal with debundling.\n            c for c in all_candidates if str(c.version) in compatible_versions\n        ]\n\n        if applicable_candidates:\n            best_candidate = max(applicable_candidates,\n                                 key=self._candidate_sort_key)\n        else:\n            best_candidate = None\n\n        if req.satisfied_by is not None:\n            installed_version = parse_version(req.satisfied_by.version)\n        else:\n            installed_version = None\n\n        if installed_version is None and best_candidate is None:\n            logger.critical(\n                'Could not find a version that satisfies the requirement %s '\n                '(from versions: %s)',\n                req,\n                ', '.join(\n                    sorted(\n                        {str(c.version) for c in all_candidates},\n                        key=parse_version,\n                    )\n                )\n            )\n\n            raise DistributionNotFound(\n                'No matching distribution found for %s' % req\n            )\n\n        best_installed = False\n        if installed_version and (\n                best_candidate is None or\n                best_candidate.version <= installed_version):\n            best_installed = True\n\n        if not upgrade and installed_version is not None:\n            if best_installed:\n                logger.debug(\n                    'Existing installed version (%s) is most up-to-date and '\n                    'satisfies requirement',\n                    installed_version,\n                )\n            else:\n                logger.debug(\n                    'Existing installed version (%s) satisfies requirement '\n                    '(most up-to-date version is %s)',\n                    installed_version,\n                    best_candidate.version,\n                )\n            return None\n\n        if best_installed:\n            # We have an existing version, and its the best version\n            logger.debug(\n                'Installed version (%s) is most up-to-date (past versions: '\n                '%s)',\n                installed_version,\n                ', '.join(sorted(compatible_versions, key=parse_version)) or\n                \"none\",\n            )\n            raise BestVersionAlreadyInstalled\n\n        logger.debug(\n            'Using version %s (newest of versions: %s)',\n            best_candidate.version,\n            ', '.join(sorted(compatible_versions, key=parse_version))\n        )\n        return best_candidate.location\n\n    def _get_pages(self, locations, project_name):\n        # type: (Iterable[Link], str) -> Iterable[HTMLPage]\n        \"\"\"\n        Yields (page, page_url) from the given locations, skipping\n        locations that have errors.\n        \"\"\"\n        seen = set()  # type: Set[Link]\n        for location in locations:\n            if location in seen:\n                continue\n            seen.add(location)\n\n            page = _get_html_page(location, session=self.session)\n            if page is None:\n                continue\n\n            yield page\n\n    _py_version_re = re.compile(r'-py([123]\\.?[0-9]?)$')\n\n    def _sort_links(self, links):\n        # type: (Iterable[Link]) -> List[Link]\n        \"\"\"\n        Returns elements of links in order, non-egg links first, egg links\n        second, while eliminating duplicates\n        \"\"\"\n        eggs, no_eggs = [], []\n        seen = set()  # type: Set[Link]\n        for link in links:\n            if link not in seen:\n                seen.add(link)\n                if link.egg_fragment:\n                    eggs.append(link)\n                else:\n                    no_eggs.append(link)\n        return no_eggs + eggs\n\n    def _package_versions(\n        self,\n        links,  # type: Iterable[Link]\n        search  # type: Search\n    ):\n        # type: (...) -> List[Optional[InstallationCandidate]]\n        result = []\n        for link in self._sort_links(links):\n            v = self._link_package_versions(link, search)\n            if v is not None:\n                result.append(v)\n        return result\n\n    def _log_skipped_link(self, link, reason):\n        # type: (Link, str) -> None\n        if link not in self.logged_links:\n            logger.debug('Skipping link %s; %s', link, reason)\n            self.logged_links.add(link)\n\n    def _link_package_versions(self, link, search):\n        # type: (Link, Search) -> Optional[InstallationCandidate]\n        \"\"\"Return an InstallationCandidate or None\"\"\"\n        version = None\n        if link.egg_fragment:\n            egg_info = link.egg_fragment\n            ext = link.ext\n        else:\n            egg_info, ext = link.splitext()\n            if not ext:\n                self._log_skipped_link(link, 'not a file')\n                return None\n            if ext not in SUPPORTED_EXTENSIONS:\n                self._log_skipped_link(\n                    link, 'unsupported archive format: %s' % ext,\n                )\n                return None\n            if \"binary\" not in search.formats and ext == WHEEL_EXTENSION:\n                self._log_skipped_link(\n                    link, 'No binaries permitted for %s' % search.supplied,\n                )\n                return None\n            if \"macosx10\" in link.path and ext == '.zip':\n                self._log_skipped_link(link, 'macosx10 one')\n                return None\n            if ext == WHEEL_EXTENSION:\n                try:\n                    wheel = Wheel(link.filename)\n                except InvalidWheelFilename:\n                    self._log_skipped_link(link, 'invalid wheel filename')\n                    return None\n                if canonicalize_name(wheel.name) != search.canonical:\n                    self._log_skipped_link(\n                        link, 'wrong project name (not %s)' % search.supplied)\n                    return None\n\n                if not wheel.supported(self.valid_tags):\n                    self._log_skipped_link(\n                        link, 'it is not compatible with this Python')\n                    return None\n\n                version = wheel.version\n\n        # This should be up by the search.ok_binary check, but see issue 2700.\n        if \"source\" not in search.formats and ext != WHEEL_EXTENSION:\n            self._log_skipped_link(\n                link, 'No sources permitted for %s' % search.supplied,\n            )\n            return None\n\n        if not version:\n            version = _egg_info_matches(egg_info, search.canonical)\n        if not version:\n            self._log_skipped_link(\n                link, 'Missing project version for %s' % search.supplied)\n            return None\n\n        match = self._py_version_re.search(version)\n        if match:\n            version = version[:match.start()]\n            py_version = match.group(1)\n            if py_version != sys.version[:3]:\n                self._log_skipped_link(\n                    link, 'Python version is incorrect')\n                return None\n        try:\n            support_this_python = check_requires_python(link.requires_python)\n        except specifiers.InvalidSpecifier:\n            logger.debug(\"Package %s has an invalid Requires-Python entry: %s\",\n                         link.filename, link.requires_python)\n            support_this_python = True\n\n        if not support_this_python:\n            logger.debug(\"The package %s is incompatible with the python \"\n                         \"version in use. Acceptable python versions are: %s\",\n                         link, link.requires_python)\n            return None\n        logger.debug('Found link %s, version: %s', link, version)\n\n        return InstallationCandidate(search.supplied, version, link)\n\n\ndef _find_name_version_sep(egg_info, canonical_name):\n    # type: (str, str) -> int\n    \"\"\"Find the separator's index based on the package's canonical name.\n\n    `egg_info` must be an egg info string for the given package, and\n    `canonical_name` must be the package's canonical name.\n\n    This function is needed since the canonicalized name does not necessarily\n    have the same length as the egg info's name part. An example::\n\n    >>> egg_info = 'foo__bar-1.0'\n    >>> canonical_name = 'foo-bar'\n    >>> _find_name_version_sep(egg_info, canonical_name)\n    8\n    \"\"\"\n    # Project name and version must be separated by one single dash. Find all\n    # occurrences of dashes; if the string in front of it matches the canonical\n    # name, this is the one separating the name and version parts.\n    for i, c in enumerate(egg_info):\n        if c != \"-\":\n            continue\n        if canonicalize_name(egg_info[:i]) == canonical_name:\n            return i\n    raise ValueError(\"{} does not match {}\".format(egg_info, canonical_name))\n\n\ndef _egg_info_matches(egg_info, canonical_name):\n    # type: (str, str) -> Optional[str]\n    \"\"\"Pull the version part out of a string.\n\n    :param egg_info: The string to parse. E.g. foo-2.1\n    :param canonical_name: The canonicalized name of the package this\n        belongs to.\n    \"\"\"\n    try:\n        version_start = _find_name_version_sep(egg_info, canonical_name) + 1\n    except ValueError:\n        return None\n    version = egg_info[version_start:]\n    if not version:\n        return None\n    return version\n\n\ndef _determine_base_url(document, page_url):\n    \"\"\"Determine the HTML document's base URL.\n\n    This looks for a ``<base>`` tag in the HTML document. If present, its href\n    attribute denotes the base URL of anchor tags in the document. If there is\n    no such tag (or if it does not have a valid href attribute), the HTML\n    file's URL is used as the base URL.\n\n    :param document: An HTML document representation. The current\n        implementation expects the result of ``html5lib.parse()``.\n    :param page_url: The URL of the HTML document.\n    \"\"\"\n    for base in document.findall(\".//base\"):\n        href = base.get(\"href\")\n        if href is not None:\n            return href\n    return page_url\n\n\ndef _get_encoding_from_headers(headers):\n    \"\"\"Determine if we have any encoding information in our headers.\n    \"\"\"\n    if headers and \"Content-Type\" in headers:\n        content_type, params = cgi.parse_header(headers[\"Content-Type\"])\n        if \"charset\" in params:\n            return params['charset']\n    return None\n\n\n_CLEAN_LINK_RE = re.compile(r'[^a-z0-9$&+,/:;=?@.#%_\\\\|-]', re.I)\n\n\ndef _clean_link(url):\n    # type: (str) -> str\n    \"\"\"Makes sure a link is fully encoded.  That is, if a ' ' shows up in\n    the link, it will be rewritten to %20 (while not over-quoting\n    % or other characters).\"\"\"\n    return _CLEAN_LINK_RE.sub(lambda match: '%%%2x' % ord(match.group(0)), url)\n\n\nclass HTMLPage(object):\n    \"\"\"Represents one page, along with its URL\"\"\"\n\n    def __init__(self, content, url, headers=None):\n        # type: (bytes, str, MutableMapping[str, str]) -> None\n        self.content = content\n        self.url = url\n        self.headers = headers\n\n    def __str__(self):\n        return redact_password_from_url(self.url)\n\n    def iter_links(self):\n        # type: () -> Iterable[Link]\n        \"\"\"Yields all links in the page\"\"\"\n        document = html5lib.parse(\n            self.content,\n            transport_encoding=_get_encoding_from_headers(self.headers),\n            namespaceHTMLElements=False,\n        )\n        base_url = _determine_base_url(document, self.url)\n        for anchor in document.findall(\".//a\"):\n            if anchor.get(\"href\"):\n                href = anchor.get(\"href\")\n                url = _clean_link(urllib_parse.urljoin(base_url, href))\n                pyrequire = anchor.get('data-requires-python')\n                pyrequire = unescape(pyrequire) if pyrequire else None\n                yield Link(url, self.url, requires_python=pyrequire)\n\n\nSearch = namedtuple('Search', 'supplied canonical formats')\n\"\"\"Capture key aspects of a search.\n\n:attribute supplied: The user supplied package.\n:attribute canonical: The canonical package name.\n:attribute formats: The formats allowed for this package. Should be a set\n    with 'binary' or 'source' or both in it.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/locations.py",
    "content": "\"\"\"Locations where we look for configs, install stuff, etc\"\"\"\nfrom __future__ import absolute_import\n\nimport os\nimport os.path\nimport platform\nimport site\nimport sys\nimport sysconfig\nfrom distutils import sysconfig as distutils_sysconfig\nfrom distutils.command.install import SCHEME_KEYS  # type: ignore\n\nfrom pip._internal.utils import appdirs\nfrom pip._internal.utils.compat import WINDOWS, expanduser\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Any, Union, Dict, List, Optional  # noqa: F401\n\n\n# Application Directories\nUSER_CACHE_DIR = appdirs.user_cache_dir(\"pip\")\n\n\nDELETE_MARKER_MESSAGE = '''\\\nThis file is placed here by pip to indicate the source was put\nhere by pip.\n\nOnce this package is successfully installed this source code will be\ndeleted (unless you remove this file).\n'''\nPIP_DELETE_MARKER_FILENAME = 'pip-delete-this-directory.txt'\n\n\ndef write_delete_marker_file(directory):\n    # type: (str) -> None\n    \"\"\"\n    Write the pip delete marker file into this directory.\n    \"\"\"\n    filepath = os.path.join(directory, PIP_DELETE_MARKER_FILENAME)\n    with open(filepath, 'w') as marker_fp:\n        marker_fp.write(DELETE_MARKER_MESSAGE)\n\n\ndef running_under_virtualenv():\n    # type: () -> bool\n    \"\"\"\n    Return True if we're running inside a virtualenv, False otherwise.\n\n    \"\"\"\n    if hasattr(sys, 'real_prefix'):\n        return True\n    elif sys.prefix != getattr(sys, \"base_prefix\", sys.prefix):\n        return True\n\n    return False\n\n\ndef virtualenv_no_global():\n    # type: () -> bool\n    \"\"\"\n    Return True if in a venv and no system site packages.\n    \"\"\"\n    # this mirrors the logic in virtualenv.py for locating the\n    # no-global-site-packages.txt file\n    site_mod_dir = os.path.dirname(os.path.abspath(site.__file__))\n    no_global_file = os.path.join(site_mod_dir, 'no-global-site-packages.txt')\n    if running_under_virtualenv() and os.path.isfile(no_global_file):\n        return True\n    else:\n        return False\n\n\nif running_under_virtualenv():\n    src_prefix = os.path.join(sys.prefix, 'src')\nelse:\n    # FIXME: keep src in cwd for now (it is not a temporary folder)\n    try:\n        src_prefix = os.path.join(os.getcwd(), 'src')\n    except OSError:\n        # In case the current working directory has been renamed or deleted\n        sys.exit(\n            \"The folder you are executing pip from can no longer be found.\"\n        )\n\n# under macOS + virtualenv sys.prefix is not properly resolved\n# it is something like /path/to/python/bin/..\n# Note: using realpath due to tmp dirs on OSX being symlinks\nsrc_prefix = os.path.abspath(src_prefix)\n\n# FIXME doesn't account for venv linked to global site-packages\n\nsite_packages = sysconfig.get_path(\"purelib\")  # type: Optional[str]\n\n# This is because of a bug in PyPy's sysconfig module, see\n# https://bitbucket.org/pypy/pypy/issues/2506/sysconfig-returns-incorrect-paths\n# for more information.\nif platform.python_implementation().lower() == \"pypy\":\n    site_packages = distutils_sysconfig.get_python_lib()\ntry:\n    # Use getusersitepackages if this is present, as it ensures that the\n    # value is initialised properly.\n    user_site = site.getusersitepackages()\nexcept AttributeError:\n    user_site = site.USER_SITE\nuser_dir = expanduser('~')\nif WINDOWS:\n    bin_py = os.path.join(sys.prefix, 'Scripts')\n    bin_user = os.path.join(user_site, 'Scripts')\n    # buildout uses 'bin' on Windows too?\n    if not os.path.exists(bin_py):\n        bin_py = os.path.join(sys.prefix, 'bin')\n        bin_user = os.path.join(user_site, 'bin')\n\n    config_basename = 'pip.ini'\n\n    legacy_storage_dir = os.path.join(user_dir, 'pip')\n    legacy_config_file = os.path.join(\n        legacy_storage_dir,\n        config_basename,\n    )\nelse:\n    bin_py = os.path.join(sys.prefix, 'bin')\n    bin_user = os.path.join(user_site, 'bin')\n\n    config_basename = 'pip.conf'\n\n    legacy_storage_dir = os.path.join(user_dir, '.pip')\n    legacy_config_file = os.path.join(\n        legacy_storage_dir,\n        config_basename,\n    )\n    # Forcing to use /usr/local/bin for standard macOS framework installs\n    # Also log to ~/Library/Logs/ for use with the Console.app log viewer\n    if sys.platform[:6] == 'darwin' and sys.prefix[:16] == '/System/Library/':\n        bin_py = '/usr/local/bin'\n\nsite_config_files = [\n    os.path.join(path, config_basename)\n    for path in appdirs.site_config_dirs('pip')\n]\n\nvenv_config_file = os.path.join(sys.prefix, config_basename)\nnew_config_file = os.path.join(appdirs.user_config_dir(\"pip\"), config_basename)\n\n\ndef distutils_scheme(dist_name, user=False, home=None, root=None,\n                     isolated=False, prefix=None):\n    # type:(str, bool, str, str, bool, str) -> dict\n    \"\"\"\n    Return a distutils install scheme\n    \"\"\"\n    from distutils.dist import Distribution\n\n    scheme = {}\n\n    if isolated:\n        extra_dist_args = {\"script_args\": [\"--no-user-cfg\"]}\n    else:\n        extra_dist_args = {}\n    dist_args = {'name': dist_name}  # type: Dict[str, Union[str, List[str]]]\n    dist_args.update(extra_dist_args)\n\n    d = Distribution(dist_args)\n    # Ignoring, typeshed issue reported python/typeshed/issues/2567\n    d.parse_config_files()\n    # NOTE: Ignoring type since mypy can't find attributes on 'Command'\n    i = d.get_command_obj('install', create=True)  # type: Any\n    assert i is not None\n    # NOTE: setting user or home has the side-effect of creating the home dir\n    # or user base for installations during finalize_options()\n    # ideally, we'd prefer a scheme class that has no side-effects.\n    assert not (user and prefix), \"user={} prefix={}\".format(user, prefix)\n    i.user = user or i.user\n    if user:\n        i.prefix = \"\"\n    i.prefix = prefix or i.prefix\n    i.home = home or i.home\n    i.root = root or i.root\n    i.finalize_options()\n    for key in SCHEME_KEYS:\n        scheme[key] = getattr(i, 'install_' + key)\n\n    # install_lib specified in setup.cfg should install *everything*\n    # into there (i.e. it takes precedence over both purelib and\n    # platlib).  Note, i.install_lib is *always* set after\n    # finalize_options(); we only want to override here if the user\n    # has explicitly requested it hence going back to the config\n\n    # Ignoring, typeshed issue reported python/typeshed/issues/2567\n    if 'install_lib' in d.get_option_dict('install'):  # type: ignore\n        scheme.update(dict(purelib=i.install_lib, platlib=i.install_lib))\n\n    if running_under_virtualenv():\n        scheme['headers'] = os.path.join(\n            sys.prefix,\n            'include',\n            'site',\n            'python' + sys.version[:3],\n            dist_name,\n        )\n\n        if root is not None:\n            path_no_drive = os.path.splitdrive(\n                os.path.abspath(scheme[\"headers\"]))[1]\n            scheme[\"headers\"] = os.path.join(\n                root,\n                path_no_drive[1:],\n            )\n\n    return scheme\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/models/__init__.py",
    "content": "\"\"\"A package that contains models that represent entities.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/models/candidate.py",
    "content": "from pip._vendor.packaging.version import parse as parse_version\n\nfrom pip._internal.utils.models import KeyBasedCompareMixin\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from pip._vendor.packaging.version import _BaseVersion  # noqa: F401\n    from pip._internal.models.link import Link  # noqa: F401\n    from typing import Any, Union  # noqa: F401\n\n\nclass InstallationCandidate(KeyBasedCompareMixin):\n    \"\"\"Represents a potential \"candidate\" for installation.\n    \"\"\"\n\n    def __init__(self, project, version, location):\n        # type: (Any, str, Link) -> None\n        self.project = project\n        self.version = parse_version(version)  # type: _BaseVersion\n        self.location = location\n\n        super(InstallationCandidate, self).__init__(\n            key=(self.project, self.version, self.location),\n            defining_class=InstallationCandidate\n        )\n\n    def __repr__(self):\n        # type: () -> str\n        return \"<InstallationCandidate({!r}, {!r}, {!r})>\".format(\n            self.project, self.version, self.location,\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/models/format_control.py",
    "content": "from pip._vendor.packaging.utils import canonicalize_name\n\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Optional, Set, FrozenSet  # noqa: F401\n\n\nclass FormatControl(object):\n    \"\"\"Helper for managing formats from which a package can be installed.\n    \"\"\"\n\n    def __init__(self, no_binary=None, only_binary=None):\n        # type: (Optional[Set], Optional[Set]) -> None\n        if no_binary is None:\n            no_binary = set()\n        if only_binary is None:\n            only_binary = set()\n\n        self.no_binary = no_binary\n        self.only_binary = only_binary\n\n    def __eq__(self, other):\n        return self.__dict__ == other.__dict__\n\n    def __ne__(self, other):\n        return not self.__eq__(other)\n\n    def __repr__(self):\n        return \"{}({}, {})\".format(\n            self.__class__.__name__,\n            self.no_binary,\n            self.only_binary\n        )\n\n    @staticmethod\n    def handle_mutual_excludes(value, target, other):\n        # type: (str, Optional[Set], Optional[Set]) -> None\n        new = value.split(',')\n        while ':all:' in new:\n            other.clear()\n            target.clear()\n            target.add(':all:')\n            del new[:new.index(':all:') + 1]\n            # Without a none, we want to discard everything as :all: covers it\n            if ':none:' not in new:\n                return\n        for name in new:\n            if name == ':none:':\n                target.clear()\n                continue\n            name = canonicalize_name(name)\n            other.discard(name)\n            target.add(name)\n\n    def get_allowed_formats(self, canonical_name):\n        # type: (str) -> FrozenSet\n        result = {\"binary\", \"source\"}\n        if canonical_name in self.only_binary:\n            result.discard('source')\n        elif canonical_name in self.no_binary:\n            result.discard('binary')\n        elif ':all:' in self.only_binary:\n            result.discard('source')\n        elif ':all:' in self.no_binary:\n            result.discard('binary')\n        return frozenset(result)\n\n    def disallow_binaries(self):\n        # type: () -> None\n        self.handle_mutual_excludes(\n            ':all:', self.no_binary, self.only_binary,\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/models/index.py",
    "content": "from pip._vendor.six.moves.urllib import parse as urllib_parse\n\n\nclass PackageIndex(object):\n    \"\"\"Represents a Package Index and provides easier access to endpoints\n    \"\"\"\n\n    def __init__(self, url, file_storage_domain):\n        # type: (str, str) -> None\n        super(PackageIndex, self).__init__()\n        self.url = url\n        self.netloc = urllib_parse.urlsplit(url).netloc\n        self.simple_url = self._url_for_path('simple')\n        self.pypi_url = self._url_for_path('pypi')\n\n        # This is part of a temporary hack used to block installs of PyPI\n        # packages which depend on external urls only necessary until PyPI can\n        # block such packages themselves\n        self.file_storage_domain = file_storage_domain\n\n    def _url_for_path(self, path):\n        # type: (str) -> str\n        return urllib_parse.urljoin(self.url, path)\n\n\nPyPI = PackageIndex(\n    'https://pypi.org/', file_storage_domain='files.pythonhosted.org'\n)\nTestPyPI = PackageIndex(\n    'https://test.pypi.org/', file_storage_domain='test-files.pythonhosted.org'\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/models/link.py",
    "content": "import posixpath\nimport re\n\nfrom pip._vendor.six.moves.urllib import parse as urllib_parse\n\nfrom pip._internal.download import path_to_url\nfrom pip._internal.utils.misc import (\n    WHEEL_EXTENSION, redact_password_from_url, splitext,\n)\nfrom pip._internal.utils.models import KeyBasedCompareMixin\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Optional, Tuple, Union, Text  # noqa: F401\n    from pip._internal.index import HTMLPage  # noqa: F401\n\n\nclass Link(KeyBasedCompareMixin):\n    \"\"\"Represents a parsed link from a Package Index's simple URL\n    \"\"\"\n\n    def __init__(self, url, comes_from=None, requires_python=None):\n        # type: (str, Optional[Union[str, HTMLPage]], Optional[str]) -> None\n        \"\"\"\n        url:\n            url of the resource pointed to (href of the link)\n        comes_from:\n            instance of HTMLPage where the link was found, or string.\n        requires_python:\n            String containing the `Requires-Python` metadata field, specified\n            in PEP 345. This may be specified by a data-requires-python\n            attribute in the HTML link tag, as described in PEP 503.\n        \"\"\"\n\n        # url can be a UNC windows share\n        if url.startswith('\\\\\\\\'):\n            url = path_to_url(url)\n\n        self.url = url\n        self.comes_from = comes_from\n        self.requires_python = requires_python if requires_python else None\n\n        super(Link, self).__init__(\n            key=(self.url),\n            defining_class=Link\n        )\n\n    def __str__(self):\n        if self.requires_python:\n            rp = ' (requires-python:%s)' % self.requires_python\n        else:\n            rp = ''\n        if self.comes_from:\n            return '%s (from %s)%s' % (redact_password_from_url(self.url),\n                                       self.comes_from, rp)\n        else:\n            return redact_password_from_url(str(self.url))\n\n    def __repr__(self):\n        return '<Link %s>' % self\n\n    @property\n    def filename(self):\n        # type: () -> str\n        _, netloc, path, _, _ = urllib_parse.urlsplit(self.url)\n        name = posixpath.basename(path.rstrip('/')) or netloc\n        name = urllib_parse.unquote(name)\n        assert name, ('URL %r produced no filename' % self.url)\n        return name\n\n    @property\n    def scheme(self):\n        # type: () -> str\n        return urllib_parse.urlsplit(self.url)[0]\n\n    @property\n    def netloc(self):\n        # type: () -> str\n        return urllib_parse.urlsplit(self.url)[1]\n\n    @property\n    def path(self):\n        # type: () -> str\n        return urllib_parse.unquote(urllib_parse.urlsplit(self.url)[2])\n\n    def splitext(self):\n        # type: () -> Tuple[str, str]\n        return splitext(posixpath.basename(self.path.rstrip('/')))\n\n    @property\n    def ext(self):\n        # type: () -> str\n        return self.splitext()[1]\n\n    @property\n    def url_without_fragment(self):\n        # type: () -> str\n        scheme, netloc, path, query, fragment = urllib_parse.urlsplit(self.url)\n        return urllib_parse.urlunsplit((scheme, netloc, path, query, None))\n\n    _egg_fragment_re = re.compile(r'[#&]egg=([^&]*)')\n\n    @property\n    def egg_fragment(self):\n        # type: () -> Optional[str]\n        match = self._egg_fragment_re.search(self.url)\n        if not match:\n            return None\n        return match.group(1)\n\n    _subdirectory_fragment_re = re.compile(r'[#&]subdirectory=([^&]*)')\n\n    @property\n    def subdirectory_fragment(self):\n        # type: () -> Optional[str]\n        match = self._subdirectory_fragment_re.search(self.url)\n        if not match:\n            return None\n        return match.group(1)\n\n    _hash_re = re.compile(\n        r'(sha1|sha224|sha384|sha256|sha512|md5)=([a-f0-9]+)'\n    )\n\n    @property\n    def hash(self):\n        # type: () -> Optional[str]\n        match = self._hash_re.search(self.url)\n        if match:\n            return match.group(2)\n        return None\n\n    @property\n    def hash_name(self):\n        # type: () -> Optional[str]\n        match = self._hash_re.search(self.url)\n        if match:\n            return match.group(1)\n        return None\n\n    @property\n    def show_url(self):\n        # type: () -> Optional[str]\n        return posixpath.basename(self.url.split('#', 1)[0].split('?', 1)[0])\n\n    @property\n    def is_wheel(self):\n        # type: () -> bool\n        return self.ext == WHEEL_EXTENSION\n\n    @property\n    def is_artifact(self):\n        # type: () -> bool\n        \"\"\"\n        Determines if this points to an actual artifact (e.g. a tarball) or if\n        it points to an \"abstract\" thing like a path or a VCS location.\n        \"\"\"\n        from pip._internal.vcs import vcs\n\n        if self.scheme in vcs.all_schemes:\n            return False\n\n        return True\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/operations/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/operations/check.py",
    "content": "\"\"\"Validation of dependencies of packages\n\"\"\"\n\nimport logging\nfrom collections import namedtuple\n\nfrom pip._vendor.packaging.utils import canonicalize_name\nfrom pip._vendor.pkg_resources import RequirementParseError\n\nfrom pip._internal.operations.prepare import make_abstract_dist\nfrom pip._internal.utils.misc import get_installed_distributions\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nlogger = logging.getLogger(__name__)\n\nif MYPY_CHECK_RUNNING:\n    from pip._internal.req.req_install import InstallRequirement  # noqa: F401\n    from typing import (  # noqa: F401\n        Any, Callable, Dict, Optional, Set, Tuple, List\n    )\n\n    # Shorthands\n    PackageSet = Dict[str, 'PackageDetails']\n    Missing = Tuple[str, Any]\n    Conflicting = Tuple[str, str, Any]\n\n    MissingDict = Dict[str, List[Missing]]\n    ConflictingDict = Dict[str, List[Conflicting]]\n    CheckResult = Tuple[MissingDict, ConflictingDict]\n\nPackageDetails = namedtuple('PackageDetails', ['version', 'requires'])\n\n\ndef create_package_set_from_installed(**kwargs):\n    # type: (**Any) -> Tuple[PackageSet, bool]\n    \"\"\"Converts a list of distributions into a PackageSet.\n    \"\"\"\n    # Default to using all packages installed on the system\n    if kwargs == {}:\n        kwargs = {\"local_only\": False, \"skip\": ()}\n\n    package_set = {}\n    problems = False\n    for dist in get_installed_distributions(**kwargs):\n        name = canonicalize_name(dist.project_name)\n        try:\n            package_set[name] = PackageDetails(dist.version, dist.requires())\n        except RequirementParseError as e:\n            # Don't crash on broken metadata\n            logging.warning(\"Error parsing requirements for %s: %s\", name, e)\n            problems = True\n    return package_set, problems\n\n\ndef check_package_set(package_set, should_ignore=None):\n    # type: (PackageSet, Optional[Callable[[str], bool]]) -> CheckResult\n    \"\"\"Check if a package set is consistent\n\n    If should_ignore is passed, it should be a callable that takes a\n    package name and returns a boolean.\n    \"\"\"\n    if should_ignore is None:\n        def should_ignore(name):\n            return False\n\n    missing = dict()\n    conflicting = dict()\n\n    for package_name in package_set:\n        # Info about dependencies of package_name\n        missing_deps = set()  # type: Set[Missing]\n        conflicting_deps = set()  # type: Set[Conflicting]\n\n        if should_ignore(package_name):\n            continue\n\n        for req in package_set[package_name].requires:\n            name = canonicalize_name(req.project_name)  # type: str\n\n            # Check if it's missing\n            if name not in package_set:\n                missed = True\n                if req.marker is not None:\n                    missed = req.marker.evaluate()\n                if missed:\n                    missing_deps.add((name, req))\n                continue\n\n            # Check if there's a conflict\n            version = package_set[name].version  # type: str\n            if not req.specifier.contains(version, prereleases=True):\n                conflicting_deps.add((name, version, req))\n\n        if missing_deps:\n            missing[package_name] = sorted(missing_deps, key=str)\n        if conflicting_deps:\n            conflicting[package_name] = sorted(conflicting_deps, key=str)\n\n    return missing, conflicting\n\n\ndef check_install_conflicts(to_install):\n    # type: (List[InstallRequirement]) -> Tuple[PackageSet, CheckResult]\n    \"\"\"For checking if the dependency graph would be consistent after \\\n    installing given requirements\n    \"\"\"\n    # Start from the current state\n    package_set, _ = create_package_set_from_installed()\n    # Install packages\n    would_be_installed = _simulate_installation_of(to_install, package_set)\n\n    # Only warn about directly-dependent packages; create a whitelist of them\n    whitelist = _create_whitelist(would_be_installed, package_set)\n\n    return (\n        package_set,\n        check_package_set(\n            package_set, should_ignore=lambda name: name not in whitelist\n        )\n    )\n\n\ndef _simulate_installation_of(to_install, package_set):\n    # type: (List[InstallRequirement], PackageSet) -> Set[str]\n    \"\"\"Computes the version of packages after installing to_install.\n    \"\"\"\n\n    # Keep track of packages that were installed\n    installed = set()\n\n    # Modify it as installing requirement_set would (assuming no errors)\n    for inst_req in to_install:\n        dist = make_abstract_dist(inst_req).dist()\n        name = canonicalize_name(dist.key)\n        package_set[name] = PackageDetails(dist.version, dist.requires())\n\n        installed.add(name)\n\n    return installed\n\n\ndef _create_whitelist(would_be_installed, package_set):\n    # type: (Set[str], PackageSet) -> Set[str]\n    packages_affected = set(would_be_installed)\n\n    for package_name in package_set:\n        if package_name in packages_affected:\n            continue\n\n        for req in package_set[package_name].requires:\n            if canonicalize_name(req.name) in packages_affected:\n                packages_affected.add(package_name)\n                break\n\n    return packages_affected\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/operations/freeze.py",
    "content": "from __future__ import absolute_import\n\nimport collections\nimport logging\nimport os\nimport re\n\nfrom pip._vendor import six\nfrom pip._vendor.packaging.utils import canonicalize_name\nfrom pip._vendor.pkg_resources import RequirementParseError\n\nfrom pip._internal.exceptions import BadCommand, InstallationError\nfrom pip._internal.req.constructors import (\n    install_req_from_editable, install_req_from_line,\n)\nfrom pip._internal.req.req_file import COMMENT_RE\nfrom pip._internal.utils.misc import (\n    dist_is_editable, get_installed_distributions,\n)\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import (  # noqa: F401\n        Iterator, Optional, List, Container, Set, Dict, Tuple, Iterable, Union\n    )\n    from pip._internal.cache import WheelCache  # noqa: F401\n    from pip._vendor.pkg_resources import (  # noqa: F401\n        Distribution, Requirement\n    )\n\n    RequirementInfo = Tuple[Optional[Union[str, Requirement]], bool, List[str]]\n\n\nlogger = logging.getLogger(__name__)\n\n\ndef freeze(\n    requirement=None,  # type: Optional[List[str]]\n    find_links=None,  # type: Optional[List[str]]\n    local_only=None,  # type: Optional[bool]\n    user_only=None,  # type: Optional[bool]\n    skip_regex=None,  # type: Optional[str]\n    isolated=False,  # type: bool\n    wheel_cache=None,  # type: Optional[WheelCache]\n    exclude_editable=False,  # type: bool\n    skip=()  # type: Container[str]\n):\n    # type: (...) -> Iterator[str]\n    find_links = find_links or []\n    skip_match = None\n\n    if skip_regex:\n        skip_match = re.compile(skip_regex).search\n\n    for link in find_links:\n        yield '-f %s' % link\n    installations = {}  # type: Dict[str, FrozenRequirement]\n    for dist in get_installed_distributions(local_only=local_only,\n                                            skip=(),\n                                            user_only=user_only):\n        try:\n            req = FrozenRequirement.from_dist(dist)\n        except RequirementParseError:\n            logger.warning(\n                \"Could not parse requirement: %s\",\n                dist.project_name\n            )\n            continue\n        if exclude_editable and req.editable:\n            continue\n        installations[req.name] = req\n\n    if requirement:\n        # the options that don't get turned into an InstallRequirement\n        # should only be emitted once, even if the same option is in multiple\n        # requirements files, so we need to keep track of what has been emitted\n        # so that we don't emit it again if it's seen again\n        emitted_options = set()  # type: Set[str]\n        # keep track of which files a requirement is in so that we can\n        # give an accurate warning if a requirement appears multiple times.\n        req_files = collections.defaultdict(list)  # type: Dict[str, List[str]]\n        for req_file_path in requirement:\n            with open(req_file_path) as req_file:\n                for line in req_file:\n                    if (not line.strip() or\n                            line.strip().startswith('#') or\n                            (skip_match and skip_match(line)) or\n                            line.startswith((\n                                '-r', '--requirement',\n                                '-Z', '--always-unzip',\n                                '-f', '--find-links',\n                                '-i', '--index-url',\n                                '--pre',\n                                '--trusted-host',\n                                '--process-dependency-links',\n                                '--extra-index-url'))):\n                        line = line.rstrip()\n                        if line not in emitted_options:\n                            emitted_options.add(line)\n                            yield line\n                        continue\n\n                    if line.startswith('-e') or line.startswith('--editable'):\n                        if line.startswith('-e'):\n                            line = line[2:].strip()\n                        else:\n                            line = line[len('--editable'):].strip().lstrip('=')\n                        line_req = install_req_from_editable(\n                            line,\n                            isolated=isolated,\n                            wheel_cache=wheel_cache,\n                        )\n                    else:\n                        line_req = install_req_from_line(\n                            COMMENT_RE.sub('', line).strip(),\n                            isolated=isolated,\n                            wheel_cache=wheel_cache,\n                        )\n\n                    if not line_req.name:\n                        logger.info(\n                            \"Skipping line in requirement file [%s] because \"\n                            \"it's not clear what it would install: %s\",\n                            req_file_path, line.strip(),\n                        )\n                        logger.info(\n                            \"  (add #egg=PackageName to the URL to avoid\"\n                            \" this warning)\"\n                        )\n                    elif line_req.name not in installations:\n                        # either it's not installed, or it is installed\n                        # but has been processed already\n                        if not req_files[line_req.name]:\n                            logger.warning(\n                                \"Requirement file [%s] contains %s, but \"\n                                \"package %r is not installed\",\n                                req_file_path,\n                                COMMENT_RE.sub('', line).strip(), line_req.name\n                            )\n                        else:\n                            req_files[line_req.name].append(req_file_path)\n                    else:\n                        yield str(installations[line_req.name]).rstrip()\n                        del installations[line_req.name]\n                        req_files[line_req.name].append(req_file_path)\n\n        # Warn about requirements that were included multiple times (in a\n        # single requirements file or in different requirements files).\n        for name, files in six.iteritems(req_files):\n            if len(files) > 1:\n                logger.warning(\"Requirement %s included multiple times [%s]\",\n                               name, ', '.join(sorted(set(files))))\n\n        yield(\n            '## The following requirements were added by '\n            'pip freeze:'\n        )\n    for installation in sorted(\n            installations.values(), key=lambda x: x.name.lower()):\n        if canonicalize_name(installation.name) not in skip:\n            yield str(installation).rstrip()\n\n\ndef get_requirement_info(dist):\n    # type: (Distribution) -> RequirementInfo\n    \"\"\"\n    Compute and return values (req, editable, comments) for use in\n    FrozenRequirement.from_dist().\n    \"\"\"\n    if not dist_is_editable(dist):\n        return (None, False, [])\n\n    location = os.path.normcase(os.path.abspath(dist.location))\n\n    from pip._internal.vcs import vcs, RemoteNotFoundError\n    vc_type = vcs.get_backend_type(location)\n\n    if not vc_type:\n        req = dist.as_requirement()\n        logger.debug(\n            'No VCS found for editable requirement {!r} in: {!r}', req,\n            location,\n        )\n        comments = [\n            '# Editable install with no version control ({})'.format(req)\n        ]\n        return (location, True, comments)\n\n    try:\n        req = vc_type.get_src_requirement(location, dist.project_name)\n    except RemoteNotFoundError:\n        req = dist.as_requirement()\n        comments = [\n            '# Editable {} install with no remote ({})'.format(\n                vc_type.__name__, req,\n            )\n        ]\n        return (location, True, comments)\n\n    except BadCommand:\n        logger.warning(\n            'cannot determine version of editable source in %s '\n            '(%s command not found in path)',\n            location,\n            vc_type.name,\n        )\n        return (None, True, [])\n\n    except InstallationError as exc:\n        logger.warning(\n            \"Error when trying to get requirement for VCS system %s, \"\n            \"falling back to uneditable format\", exc\n        )\n    else:\n        if req is not None:\n            return (req, True, [])\n\n    logger.warning(\n        'Could not determine repository location of %s', location\n    )\n    comments = ['## !! Could not determine repository location']\n\n    return (None, False, comments)\n\n\nclass FrozenRequirement(object):\n    def __init__(self, name, req, editable, comments=()):\n        # type: (str, Union[str, Requirement], bool, Iterable[str]) -> None\n        self.name = name\n        self.req = req\n        self.editable = editable\n        self.comments = comments\n\n    @classmethod\n    def from_dist(cls, dist):\n        # type: (Distribution) -> FrozenRequirement\n        req, editable, comments = get_requirement_info(dist)\n        if req is None:\n            req = dist.as_requirement()\n\n        return cls(dist.project_name, req, editable, comments=comments)\n\n    def __str__(self):\n        req = self.req\n        if self.editable:\n            req = '-e %s' % req\n        return '\\n'.join(list(self.comments) + [str(req)]) + '\\n'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/operations/prepare.py",
    "content": "\"\"\"Prepares a distribution for installation\n\"\"\"\n\nimport logging\nimport os\n\nfrom pip._vendor import pkg_resources, requests\n\nfrom pip._internal.build_env import BuildEnvironment\nfrom pip._internal.download import (\n    is_dir_url, is_file_url, is_vcs_url, unpack_url, url_to_path,\n)\nfrom pip._internal.exceptions import (\n    DirectoryUrlHashUnsupported, HashUnpinned, InstallationError,\n    PreviousBuildDirError, VcsHashUnsupported,\n)\nfrom pip._internal.utils.compat import expanduser\nfrom pip._internal.utils.hashes import MissingHashes\nfrom pip._internal.utils.logging import indent_log\nfrom pip._internal.utils.misc import display_path, normalize_path\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\nfrom pip._internal.vcs import vcs\n\nif MYPY_CHECK_RUNNING:\n    from typing import Any, Optional  # noqa: F401\n    from pip._internal.req.req_install import InstallRequirement  # noqa: F401\n    from pip._internal.index import PackageFinder  # noqa: F401\n    from pip._internal.download import PipSession  # noqa: F401\n    from pip._internal.req.req_tracker import RequirementTracker  # noqa: F401\n\nlogger = logging.getLogger(__name__)\n\n\ndef make_abstract_dist(req):\n    # type: (InstallRequirement) -> DistAbstraction\n    \"\"\"Factory to make an abstract dist object.\n\n    Preconditions: Either an editable req with a source_dir, or satisfied_by or\n    a wheel link, or a non-editable req with a source_dir.\n\n    :return: A concrete DistAbstraction.\n    \"\"\"\n    if req.editable:\n        return IsSDist(req)\n    elif req.link and req.link.is_wheel:\n        return IsWheel(req)\n    else:\n        return IsSDist(req)\n\n\nclass DistAbstraction(object):\n    \"\"\"Abstracts out the wheel vs non-wheel Resolver.resolve() logic.\n\n    The requirements for anything installable are as follows:\n     - we must be able to determine the requirement name\n       (or we can't correctly handle the non-upgrade case).\n     - we must be able to generate a list of run-time dependencies\n       without installing any additional packages (or we would\n       have to either burn time by doing temporary isolated installs\n       or alternatively violate pips 'don't start installing unless\n       all requirements are available' rule - neither of which are\n       desirable).\n     - for packages with setup requirements, we must also be able\n       to determine their requirements without installing additional\n       packages (for the same reason as run-time dependencies)\n     - we must be able to create a Distribution object exposing the\n       above metadata.\n    \"\"\"\n\n    def __init__(self, req):\n        # type: (InstallRequirement) -> None\n        self.req = req  # type: InstallRequirement\n\n    def dist(self):\n        # type: () -> Any\n        \"\"\"Return a setuptools Dist object.\"\"\"\n        raise NotImplementedError\n\n    def prep_for_dist(self, finder, build_isolation):\n        # type: (PackageFinder, bool) -> Any\n        \"\"\"Ensure that we can get a Dist for this requirement.\"\"\"\n        raise NotImplementedError\n\n\nclass IsWheel(DistAbstraction):\n\n    def dist(self):\n        # type: () -> pkg_resources.Distribution\n        return list(pkg_resources.find_distributions(\n            self.req.source_dir))[0]\n\n    def prep_for_dist(self, finder, build_isolation):\n        # type: (PackageFinder, bool) -> Any\n        # FIXME:https://github.com/pypa/pip/issues/1112\n        pass\n\n\nclass IsSDist(DistAbstraction):\n\n    def dist(self):\n        return self.req.get_dist()\n\n    def prep_for_dist(self, finder, build_isolation):\n        # type: (PackageFinder, bool) -> None\n        # Prepare for building. We need to:\n        #   1. Load pyproject.toml (if it exists)\n        #   2. Set up the build environment\n\n        self.req.load_pyproject_toml()\n        should_isolate = self.req.use_pep517 and build_isolation\n\n        def _raise_conflicts(conflicting_with, conflicting_reqs):\n            raise InstallationError(\n                \"Some build dependencies for %s conflict with %s: %s.\" % (\n                    self.req, conflicting_with, ', '.join(\n                        '%s is incompatible with %s' % (installed, wanted)\n                        for installed, wanted in sorted(conflicting))))\n\n        if should_isolate:\n            # Isolate in a BuildEnvironment and install the build-time\n            # requirements.\n            self.req.build_env = BuildEnvironment()\n            self.req.build_env.install_requirements(\n                finder, self.req.pyproject_requires, 'overlay',\n                \"Installing build dependencies\"\n            )\n            conflicting, missing = self.req.build_env.check_requirements(\n                self.req.requirements_to_check\n            )\n            if conflicting:\n                _raise_conflicts(\"PEP 517/518 supported requirements\",\n                                 conflicting)\n            if missing:\n                logger.warning(\n                    \"Missing build requirements in pyproject.toml for %s.\",\n                    self.req,\n                )\n                logger.warning(\n                    \"The project does not specify a build backend, and \"\n                    \"pip cannot fall back to setuptools without %s.\",\n                    \" and \".join(map(repr, sorted(missing)))\n                )\n            # Install any extra build dependencies that the backend requests.\n            # This must be done in a second pass, as the pyproject.toml\n            # dependencies must be installed before we can call the backend.\n            with self.req.build_env:\n                # We need to have the env active when calling the hook.\n                self.req.spin_message = \"Getting requirements to build wheel\"\n                reqs = self.req.pep517_backend.get_requires_for_build_wheel()\n            conflicting, missing = self.req.build_env.check_requirements(reqs)\n            if conflicting:\n                _raise_conflicts(\"the backend dependencies\", conflicting)\n            self.req.build_env.install_requirements(\n                finder, missing, 'normal',\n                \"Installing backend dependencies\"\n            )\n\n        self.req.prepare_metadata()\n        self.req.assert_source_matches_version()\n\n\nclass Installed(DistAbstraction):\n\n    def dist(self):\n        # type: () -> pkg_resources.Distribution\n        return self.req.satisfied_by\n\n    def prep_for_dist(self, finder, build_isolation):\n        # type: (PackageFinder, bool) -> Any\n        pass\n\n\nclass RequirementPreparer(object):\n    \"\"\"Prepares a Requirement\n    \"\"\"\n\n    def __init__(\n        self,\n        build_dir,  # type: str\n        download_dir,  # type: Optional[str]\n        src_dir,  # type: str\n        wheel_download_dir,  # type: Optional[str]\n        progress_bar,  # type: str\n        build_isolation,  # type: bool\n        req_tracker  # type: RequirementTracker\n    ):\n        # type: (...) -> None\n        super(RequirementPreparer, self).__init__()\n\n        self.src_dir = src_dir\n        self.build_dir = build_dir\n        self.req_tracker = req_tracker\n\n        # Where still packed archives should be written to. If None, they are\n        # not saved, and are deleted immediately after unpacking.\n        self.download_dir = download_dir\n\n        # Where still-packed .whl files should be written to. If None, they are\n        # written to the download_dir parameter. Separate to download_dir to\n        # permit only keeping wheel archives for pip wheel.\n        if wheel_download_dir:\n            wheel_download_dir = normalize_path(wheel_download_dir)\n        self.wheel_download_dir = wheel_download_dir\n\n        # NOTE\n        # download_dir and wheel_download_dir overlap semantically and may\n        # be combined if we're willing to have non-wheel archives present in\n        # the wheelhouse output by 'pip wheel'.\n\n        self.progress_bar = progress_bar\n\n        # Is build isolation allowed?\n        self.build_isolation = build_isolation\n\n    @property\n    def _download_should_save(self):\n        # type: () -> bool\n        # TODO: Modify to reduce indentation needed\n        if self.download_dir:\n            self.download_dir = expanduser(self.download_dir)\n            if os.path.exists(self.download_dir):\n                return True\n            else:\n                logger.critical('Could not find download directory')\n                raise InstallationError(\n                    \"Could not find or access download directory '%s'\"\n                    % display_path(self.download_dir))\n        return False\n\n    def prepare_linked_requirement(\n        self,\n        req,  # type: InstallRequirement\n        session,  # type: PipSession\n        finder,  # type: PackageFinder\n        upgrade_allowed,  # type: bool\n        require_hashes  # type: bool\n    ):\n        # type: (...) -> DistAbstraction\n        \"\"\"Prepare a requirement that would be obtained from req.link\n        \"\"\"\n        # TODO: Breakup into smaller functions\n        if req.link and req.link.scheme == 'file':\n            path = url_to_path(req.link.url)\n            logger.info('Processing %s', display_path(path))\n        else:\n            logger.info('Collecting %s', req)\n\n        with indent_log():\n            # @@ if filesystem packages are not marked\n            # editable in a req, a non deterministic error\n            # occurs when the script attempts to unpack the\n            # build directory\n            req.ensure_has_source_dir(self.build_dir)\n            # If a checkout exists, it's unwise to keep going.  version\n            # inconsistencies are logged later, but do not fail the\n            # installation.\n            # FIXME: this won't upgrade when there's an existing\n            # package unpacked in `req.source_dir`\n            # package unpacked in `req.source_dir`\n            if os.path.exists(os.path.join(req.source_dir, 'setup.py')):\n                raise PreviousBuildDirError(\n                    \"pip can't proceed with requirements '%s' due to a\"\n                    \" pre-existing build directory (%s). This is \"\n                    \"likely due to a previous installation that failed\"\n                    \". pip is being responsible and not assuming it \"\n                    \"can delete this. Please delete it and try again.\"\n                    % (req, req.source_dir)\n                )\n            req.populate_link(finder, upgrade_allowed, require_hashes)\n\n            # We can't hit this spot and have populate_link return None.\n            # req.satisfied_by is None here (because we're\n            # guarded) and upgrade has no impact except when satisfied_by\n            # is not None.\n            # Then inside find_requirement existing_applicable -> False\n            # If no new versions are found, DistributionNotFound is raised,\n            # otherwise a result is guaranteed.\n            assert req.link\n            link = req.link\n\n            # Now that we have the real link, we can tell what kind of\n            # requirements we have and raise some more informative errors\n            # than otherwise. (For example, we can raise VcsHashUnsupported\n            # for a VCS URL rather than HashMissing.)\n            if require_hashes:\n                # We could check these first 2 conditions inside\n                # unpack_url and save repetition of conditions, but then\n                # we would report less-useful error messages for\n                # unhashable requirements, complaining that there's no\n                # hash provided.\n                if is_vcs_url(link):\n                    raise VcsHashUnsupported()\n                elif is_file_url(link) and is_dir_url(link):\n                    raise DirectoryUrlHashUnsupported()\n                if not req.original_link and not req.is_pinned:\n                    # Unpinned packages are asking for trouble when a new\n                    # version is uploaded. This isn't a security check, but\n                    # it saves users a surprising hash mismatch in the\n                    # future.\n                    #\n                    # file:/// URLs aren't pinnable, so don't complain\n                    # about them not being pinned.\n                    raise HashUnpinned()\n\n            hashes = req.hashes(trust_internet=not require_hashes)\n            if require_hashes and not hashes:\n                # Known-good hashes are missing for this requirement, so\n                # shim it with a facade object that will provoke hash\n                # computation and then raise a HashMissing exception\n                # showing the user what the hash should be.\n                hashes = MissingHashes()\n\n            try:\n                download_dir = self.download_dir\n                # We always delete unpacked sdists after pip ran.\n                autodelete_unpacked = True\n                if req.link.is_wheel and self.wheel_download_dir:\n                    # when doing 'pip wheel` we download wheels to a\n                    # dedicated dir.\n                    download_dir = self.wheel_download_dir\n                if req.link.is_wheel:\n                    if download_dir:\n                        # When downloading, we only unpack wheels to get\n                        # metadata.\n                        autodelete_unpacked = True\n                    else:\n                        # When installing a wheel, we use the unpacked\n                        # wheel.\n                        autodelete_unpacked = False\n                unpack_url(\n                    req.link, req.source_dir,\n                    download_dir, autodelete_unpacked,\n                    session=session, hashes=hashes,\n                    progress_bar=self.progress_bar\n                )\n            except requests.HTTPError as exc:\n                logger.critical(\n                    'Could not install requirement %s because of error %s',\n                    req,\n                    exc,\n                )\n                raise InstallationError(\n                    'Could not install requirement %s because of HTTP '\n                    'error %s for URL %s' %\n                    (req, exc, req.link)\n                )\n            abstract_dist = make_abstract_dist(req)\n            with self.req_tracker.track(req):\n                abstract_dist.prep_for_dist(finder, self.build_isolation)\n            if self._download_should_save:\n                # Make a .zip of the source_dir we already created.\n                if req.link.scheme in vcs.all_schemes:\n                    req.archive(self.download_dir)\n        return abstract_dist\n\n    def prepare_editable_requirement(\n        self,\n        req,  # type: InstallRequirement\n        require_hashes,  # type: bool\n        use_user_site,  # type: bool\n        finder  # type: PackageFinder\n    ):\n        # type: (...) -> DistAbstraction\n        \"\"\"Prepare an editable requirement\n        \"\"\"\n        assert req.editable, \"cannot prepare a non-editable req as editable\"\n\n        logger.info('Obtaining %s', req)\n\n        with indent_log():\n            if require_hashes:\n                raise InstallationError(\n                    'The editable requirement %s cannot be installed when '\n                    'requiring hashes, because there is no single file to '\n                    'hash.' % req\n                )\n            req.ensure_has_source_dir(self.src_dir)\n            req.update_editable(not self._download_should_save)\n\n            abstract_dist = make_abstract_dist(req)\n            with self.req_tracker.track(req):\n                abstract_dist.prep_for_dist(finder, self.build_isolation)\n\n            if self._download_should_save:\n                req.archive(self.download_dir)\n            req.check_if_exists(use_user_site)\n\n        return abstract_dist\n\n    def prepare_installed_requirement(self, req, require_hashes, skip_reason):\n        # type: (InstallRequirement, bool, Optional[str]) -> DistAbstraction\n        \"\"\"Prepare an already-installed requirement\n        \"\"\"\n        assert req.satisfied_by, \"req should have been satisfied but isn't\"\n        assert skip_reason is not None, (\n            \"did not get skip reason skipped but req.satisfied_by \"\n            \"is set to %r\" % (req.satisfied_by,)\n        )\n        logger.info(\n            'Requirement %s: %s (%s)',\n            skip_reason, req, req.satisfied_by.version\n        )\n        with indent_log():\n            if require_hashes:\n                logger.debug(\n                    'Since it is already installed, we are trusting this '\n                    'package without checking its hash. To ensure a '\n                    'completely repeatable environment, install into an '\n                    'empty virtualenv.'\n                )\n            abstract_dist = Installed(req)\n\n        return abstract_dist\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/pep425tags.py",
    "content": "\"\"\"Generate and work with PEP 425 Compatibility Tags.\"\"\"\nfrom __future__ import absolute_import\n\nimport distutils.util\nimport logging\nimport platform\nimport re\nimport sys\nimport sysconfig\nimport warnings\nfrom collections import OrderedDict\n\nimport pip._internal.utils.glibc\nfrom pip._internal.utils.compat import get_extension_suffixes\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import (  # noqa: F401\n        Tuple, Callable, List, Optional, Union, Dict\n    )\n\n    Pep425Tag = Tuple[str, str, str]\n\nlogger = logging.getLogger(__name__)\n\n_osx_arch_pat = re.compile(r'(.+)_(\\d+)_(\\d+)_(.+)')\n\n\ndef get_config_var(var):\n    # type: (str) -> Optional[str]\n    try:\n        return sysconfig.get_config_var(var)\n    except IOError as e:  # Issue #1074\n        warnings.warn(\"{}\".format(e), RuntimeWarning)\n        return None\n\n\ndef get_abbr_impl():\n    # type: () -> str\n    \"\"\"Return abbreviated implementation name.\"\"\"\n    if hasattr(sys, 'pypy_version_info'):\n        pyimpl = 'pp'\n    elif sys.platform.startswith('java'):\n        pyimpl = 'jy'\n    elif sys.platform == 'cli':\n        pyimpl = 'ip'\n    else:\n        pyimpl = 'cp'\n    return pyimpl\n\n\ndef get_impl_ver():\n    # type: () -> str\n    \"\"\"Return implementation version.\"\"\"\n    impl_ver = get_config_var(\"py_version_nodot\")\n    if not impl_ver or get_abbr_impl() == 'pp':\n        impl_ver = ''.join(map(str, get_impl_version_info()))\n    return impl_ver\n\n\ndef get_impl_version_info():\n    # type: () -> Tuple[int, ...]\n    \"\"\"Return sys.version_info-like tuple for use in decrementing the minor\n    version.\"\"\"\n    if get_abbr_impl() == 'pp':\n        # as per https://github.com/pypa/pip/issues/2882\n        # attrs exist only on pypy\n        return (sys.version_info[0],\n                sys.pypy_version_info.major,  # type: ignore\n                sys.pypy_version_info.minor)  # type: ignore\n    else:\n        return sys.version_info[0], sys.version_info[1]\n\n\ndef get_impl_tag():\n    # type: () -> str\n    \"\"\"\n    Returns the Tag for this specific implementation.\n    \"\"\"\n    return \"{}{}\".format(get_abbr_impl(), get_impl_ver())\n\n\ndef get_flag(var, fallback, expected=True, warn=True):\n    # type: (str, Callable[..., bool], Union[bool, int], bool) -> bool\n    \"\"\"Use a fallback method for determining SOABI flags if the needed config\n    var is unset or unavailable.\"\"\"\n    val = get_config_var(var)\n    if val is None:\n        if warn:\n            logger.debug(\"Config variable '%s' is unset, Python ABI tag may \"\n                         \"be incorrect\", var)\n        return fallback()\n    return val == expected\n\n\ndef get_abi_tag():\n    # type: () -> Optional[str]\n    \"\"\"Return the ABI tag based on SOABI (if available) or emulate SOABI\n    (CPython 2, PyPy).\"\"\"\n    soabi = get_config_var('SOABI')\n    impl = get_abbr_impl()\n    if not soabi and impl in {'cp', 'pp'} and hasattr(sys, 'maxunicode'):\n        d = ''\n        m = ''\n        u = ''\n        if get_flag('Py_DEBUG',\n                    lambda: hasattr(sys, 'gettotalrefcount'),\n                    warn=(impl == 'cp')):\n            d = 'd'\n        if get_flag('WITH_PYMALLOC',\n                    lambda: impl == 'cp',\n                    warn=(impl == 'cp')):\n            m = 'm'\n        if get_flag('Py_UNICODE_SIZE',\n                    lambda: sys.maxunicode == 0x10ffff,\n                    expected=4,\n                    warn=(impl == 'cp' and\n                          sys.version_info < (3, 3))) \\\n                and sys.version_info < (3, 3):\n            u = 'u'\n        abi = '%s%s%s%s%s' % (impl, get_impl_ver(), d, m, u)\n    elif soabi and soabi.startswith('cpython-'):\n        abi = 'cp' + soabi.split('-')[1]\n    elif soabi:\n        abi = soabi.replace('.', '_').replace('-', '_')\n    else:\n        abi = None\n    return abi\n\n\ndef _is_running_32bit():\n    # type: () -> bool\n    return sys.maxsize == 2147483647\n\n\ndef get_platform():\n    # type: () -> str\n    \"\"\"Return our platform name 'win32', 'linux_x86_64'\"\"\"\n    if sys.platform == 'darwin':\n        # distutils.util.get_platform() returns the release based on the value\n        # of MACOSX_DEPLOYMENT_TARGET on which Python was built, which may\n        # be significantly older than the user's current machine.\n        release, _, machine = platform.mac_ver()\n        split_ver = release.split('.')\n\n        if machine == \"x86_64\" and _is_running_32bit():\n            machine = \"i386\"\n        elif machine == \"ppc64\" and _is_running_32bit():\n            machine = \"ppc\"\n\n        return 'macosx_{}_{}_{}'.format(split_ver[0], split_ver[1], machine)\n\n    # XXX remove distutils dependency\n    result = distutils.util.get_platform().replace('.', '_').replace('-', '_')\n    if result == \"linux_x86_64\" and _is_running_32bit():\n        # 32 bit Python program (running on a 64 bit Linux): pip should only\n        # install and run 32 bit compiled extensions in that case.\n        result = \"linux_i686\"\n\n    return result\n\n\ndef is_manylinux1_compatible():\n    # type: () -> bool\n    # Only Linux, and only x86-64 / i686\n    if get_platform() not in {\"linux_x86_64\", \"linux_i686\"}:\n        return False\n\n    # Check for presence of _manylinux module\n    try:\n        import _manylinux\n        return bool(_manylinux.manylinux1_compatible)\n    except (ImportError, AttributeError):\n        # Fall through to heuristic check below\n        pass\n\n    # Check glibc version. CentOS 5 uses glibc 2.5.\n    return pip._internal.utils.glibc.have_compatible_glibc(2, 5)\n\n\ndef is_manylinux2010_compatible():\n    # type: () -> bool\n    # Only Linux, and only x86-64 / i686\n    if get_platform() not in {\"linux_x86_64\", \"linux_i686\"}:\n        return False\n\n    # Check for presence of _manylinux module\n    try:\n        import _manylinux\n        return bool(_manylinux.manylinux2010_compatible)\n    except (ImportError, AttributeError):\n        # Fall through to heuristic check below\n        pass\n\n    # Check glibc version. CentOS 6 uses glibc 2.12.\n    return pip._internal.utils.glibc.have_compatible_glibc(2, 12)\n\n\ndef get_darwin_arches(major, minor, machine):\n    # type: (int, int, str) -> List[str]\n    \"\"\"Return a list of supported arches (including group arches) for\n    the given major, minor and machine architecture of an macOS machine.\n    \"\"\"\n    arches = []\n\n    def _supports_arch(major, minor, arch):\n        # type: (int, int, str) -> bool\n        # Looking at the application support for macOS versions in the chart\n        # provided by https://en.wikipedia.org/wiki/OS_X#Versions it appears\n        # our timeline looks roughly like:\n        #\n        # 10.0 - Introduces ppc support.\n        # 10.4 - Introduces ppc64, i386, and x86_64 support, however the ppc64\n        #        and x86_64 support is CLI only, and cannot be used for GUI\n        #        applications.\n        # 10.5 - Extends ppc64 and x86_64 support to cover GUI applications.\n        # 10.6 - Drops support for ppc64\n        # 10.7 - Drops support for ppc\n        #\n        # Given that we do not know if we're installing a CLI or a GUI\n        # application, we must be conservative and assume it might be a GUI\n        # application and behave as if ppc64 and x86_64 support did not occur\n        # until 10.5.\n        #\n        # Note: The above information is taken from the \"Application support\"\n        #       column in the chart not the \"Processor support\" since I believe\n        #       that we care about what instruction sets an application can use\n        #       not which processors the OS supports.\n        if arch == 'ppc':\n            return (major, minor) <= (10, 5)\n        if arch == 'ppc64':\n            return (major, minor) == (10, 5)\n        if arch == 'i386':\n            return (major, minor) >= (10, 4)\n        if arch == 'x86_64':\n            return (major, minor) >= (10, 5)\n        if arch in groups:\n            for garch in groups[arch]:\n                if _supports_arch(major, minor, garch):\n                    return True\n        return False\n\n    groups = OrderedDict([\n        (\"fat\", (\"i386\", \"ppc\")),\n        (\"intel\", (\"x86_64\", \"i386\")),\n        (\"fat64\", (\"x86_64\", \"ppc64\")),\n        (\"fat32\", (\"x86_64\", \"i386\", \"ppc\")),\n    ])  # type: Dict[str, Tuple[str, ...]]\n\n    if _supports_arch(major, minor, machine):\n        arches.append(machine)\n\n    for garch in groups:\n        if machine in groups[garch] and _supports_arch(major, minor, garch):\n            arches.append(garch)\n\n    arches.append('universal')\n\n    return arches\n\n\ndef get_all_minor_versions_as_strings(version_info):\n    # type: (Tuple[int, ...]) -> List[str]\n    versions = []\n    major = version_info[:-1]\n    # Support all previous minor Python versions.\n    for minor in range(version_info[-1], -1, -1):\n        versions.append(''.join(map(str, major + (minor,))))\n    return versions\n\n\ndef get_supported(\n    versions=None,  # type: Optional[List[str]]\n    noarch=False,  # type: bool\n    platform=None,  # type: Optional[str]\n    impl=None,  # type: Optional[str]\n    abi=None  # type: Optional[str]\n):\n    # type: (...) -> List[Pep425Tag]\n    \"\"\"Return a list of supported tags for each version specified in\n    `versions`.\n\n    :param versions: a list of string versions, of the form [\"33\", \"32\"],\n        or None. The first version will be assumed to support our ABI.\n    :param platform: specify the exact platform you want valid\n        tags for, or None. If None, use the local system platform.\n    :param impl: specify the exact implementation you want valid\n        tags for, or None. If None, use the local interpreter impl.\n    :param abi: specify the exact abi you want valid\n        tags for, or None. If None, use the local interpreter abi.\n    \"\"\"\n    supported = []\n\n    # Versions must be given with respect to the preference\n    if versions is None:\n        version_info = get_impl_version_info()\n        versions = get_all_minor_versions_as_strings(version_info)\n\n    impl = impl or get_abbr_impl()\n\n    abis = []  # type: List[str]\n\n    abi = abi or get_abi_tag()\n    if abi:\n        abis[0:0] = [abi]\n\n    abi3s = set()\n    for suffix in get_extension_suffixes():\n        if suffix.startswith('.abi'):\n            abi3s.add(suffix.split('.', 2)[1])\n\n    abis.extend(sorted(list(abi3s)))\n\n    abis.append('none')\n\n    if not noarch:\n        arch = platform or get_platform()\n        arch_prefix, arch_sep, arch_suffix = arch.partition('_')\n        if arch.startswith('macosx'):\n            # support macosx-10.6-intel on macosx-10.9-x86_64\n            match = _osx_arch_pat.match(arch)\n            if match:\n                name, major, minor, actual_arch = match.groups()\n                tpl = '{}_{}_%i_%s'.format(name, major)\n                arches = []\n                for m in reversed(range(int(minor) + 1)):\n                    for a in get_darwin_arches(int(major), m, actual_arch):\n                        arches.append(tpl % (m, a))\n            else:\n                # arch pattern didn't match (?!)\n                arches = [arch]\n        elif arch_prefix == 'manylinux2010':\n            # manylinux1 wheels run on most manylinux2010 systems with the\n            # exception of wheels depending on ncurses. PEP 571 states\n            # manylinux1 wheels should be considered manylinux2010 wheels:\n            # https://www.python.org/dev/peps/pep-0571/#backwards-compatibility-with-manylinux1-wheels\n            arches = [arch, 'manylinux1' + arch_sep + arch_suffix]\n        elif platform is None:\n            arches = []\n            if is_manylinux2010_compatible():\n                arches.append('manylinux2010' + arch_sep + arch_suffix)\n            if is_manylinux1_compatible():\n                arches.append('manylinux1' + arch_sep + arch_suffix)\n            arches.append(arch)\n        else:\n            arches = [arch]\n\n        # Current version, current API (built specifically for our Python):\n        for abi in abis:\n            for arch in arches:\n                supported.append(('%s%s' % (impl, versions[0]), abi, arch))\n\n        # abi3 modules compatible with older version of Python\n        for version in versions[1:]:\n            # abi3 was introduced in Python 3.2\n            if version in {'31', '30'}:\n                break\n            for abi in abi3s:   # empty set if not Python 3\n                for arch in arches:\n                    supported.append((\"%s%s\" % (impl, version), abi, arch))\n\n        # Has binaries, does not use the Python API:\n        for arch in arches:\n            supported.append(('py%s' % (versions[0][0]), 'none', arch))\n\n    # No abi / arch, but requires our implementation:\n    supported.append(('%s%s' % (impl, versions[0]), 'none', 'any'))\n    # Tagged specifically as being cross-version compatible\n    # (with just the major version specified)\n    supported.append(('%s%s' % (impl, versions[0][0]), 'none', 'any'))\n\n    # No abi / arch, generic Python\n    for i, version in enumerate(versions):\n        supported.append(('py%s' % (version,), 'none', 'any'))\n        if i == 0:\n            supported.append(('py%s' % (version[0]), 'none', 'any'))\n\n    return supported\n\n\nimplementation_tag = get_impl_tag()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/pyproject.py",
    "content": "from __future__ import absolute_import\n\nimport io\nimport os\nimport sys\n\nfrom pip._vendor import pytoml, six\n\nfrom pip._internal.exceptions import InstallationError\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Any, Tuple, Optional, List  # noqa: F401\n\n\ndef _is_list_of_str(obj):\n    # type: (Any) -> bool\n    return (\n        isinstance(obj, list) and\n        all(isinstance(item, six.string_types) for item in obj)\n    )\n\n\ndef make_pyproject_path(setup_py_dir):\n    # type: (str) -> str\n    path = os.path.join(setup_py_dir, 'pyproject.toml')\n\n    # Python2 __file__ should not be unicode\n    if six.PY2 and isinstance(path, six.text_type):\n        path = path.encode(sys.getfilesystemencoding())\n\n    return path\n\n\ndef load_pyproject_toml(\n    use_pep517,  # type: Optional[bool]\n    pyproject_toml,  # type: str\n    setup_py,  # type: str\n    req_name  # type: str\n):\n    # type: (...) -> Optional[Tuple[List[str], str, List[str]]]\n    \"\"\"Load the pyproject.toml file.\n\n    Parameters:\n        use_pep517 - Has the user requested PEP 517 processing? None\n                     means the user hasn't explicitly specified.\n        pyproject_toml - Location of the project's pyproject.toml file\n        setup_py - Location of the project's setup.py file\n        req_name - The name of the requirement we're processing (for\n                   error reporting)\n\n    Returns:\n        None if we should use the legacy code path, otherwise a tuple\n        (\n            requirements from pyproject.toml,\n            name of PEP 517 backend,\n            requirements we should check are installed after setting\n                up the build environment\n        )\n    \"\"\"\n    has_pyproject = os.path.isfile(pyproject_toml)\n    has_setup = os.path.isfile(setup_py)\n\n    if has_pyproject:\n        with io.open(pyproject_toml, encoding=\"utf-8\") as f:\n            pp_toml = pytoml.load(f)\n        build_system = pp_toml.get(\"build-system\")\n    else:\n        build_system = None\n\n    # The following cases must use PEP 517\n    # We check for use_pep517 being non-None and falsey because that means\n    # the user explicitly requested --no-use-pep517.  The value 0 as\n    # opposed to False can occur when the value is provided via an\n    # environment variable or config file option (due to the quirk of\n    # strtobool() returning an integer in pip's configuration code).\n    if has_pyproject and not has_setup:\n        if use_pep517 is not None and not use_pep517:\n            raise InstallationError(\n                \"Disabling PEP 517 processing is invalid: \"\n                \"project does not have a setup.py\"\n            )\n        use_pep517 = True\n    elif build_system and \"build-backend\" in build_system:\n        if use_pep517 is not None and not use_pep517:\n            raise InstallationError(\n                \"Disabling PEP 517 processing is invalid: \"\n                \"project specifies a build backend of {} \"\n                \"in pyproject.toml\".format(\n                    build_system[\"build-backend\"]\n                )\n            )\n        use_pep517 = True\n\n    # If we haven't worked out whether to use PEP 517 yet,\n    # and the user hasn't explicitly stated a preference,\n    # we do so if the project has a pyproject.toml file.\n    elif use_pep517 is None:\n        use_pep517 = has_pyproject\n\n    # At this point, we know whether we're going to use PEP 517.\n    assert use_pep517 is not None\n\n    # If we're using the legacy code path, there is nothing further\n    # for us to do here.\n    if not use_pep517:\n        return None\n\n    if build_system is None:\n        # Either the user has a pyproject.toml with no build-system\n        # section, or the user has no pyproject.toml, but has opted in\n        # explicitly via --use-pep517.\n        # In the absence of any explicit backend specification, we\n        # assume the setuptools backend that most closely emulates the\n        # traditional direct setup.py execution, and require wheel and\n        # a version of setuptools that supports that backend.\n\n        build_system = {\n            \"requires\": [\"setuptools>=40.8.0\", \"wheel\"],\n            \"build-backend\": \"setuptools.build_meta:__legacy__\",\n        }\n\n    # If we're using PEP 517, we have build system information (either\n    # from pyproject.toml, or defaulted by the code above).\n    # Note that at this point, we do not know if the user has actually\n    # specified a backend, though.\n    assert build_system is not None\n\n    # Ensure that the build-system section in pyproject.toml conforms\n    # to PEP 518.\n    error_template = (\n        \"{package} has a pyproject.toml file that does not comply \"\n        \"with PEP 518: {reason}\"\n    )\n\n    # Specifying the build-system table but not the requires key is invalid\n    if \"requires\" not in build_system:\n        raise InstallationError(\n            error_template.format(package=req_name, reason=(\n                \"it has a 'build-system' table but not \"\n                \"'build-system.requires' which is mandatory in the table\"\n            ))\n        )\n\n    # Error out if requires is not a list of strings\n    requires = build_system[\"requires\"]\n    if not _is_list_of_str(requires):\n        raise InstallationError(error_template.format(\n            package=req_name,\n            reason=\"'build-system.requires' is not a list of strings.\",\n        ))\n\n    backend = build_system.get(\"build-backend\")\n    check = []  # type: List[str]\n    if backend is None:\n        # If the user didn't specify a backend, we assume they want to use\n        # the setuptools backend. But we can't be sure they have included\n        # a version of setuptools which supplies the backend, or wheel\n        # (which is needed by the backend) in their requirements. So we\n        # make a note to check that those requirements are present once\n        # we have set up the environment.\n        # This is quite a lot of work to check for a very specific case. But\n        # the problem is, that case is potentially quite common - projects that\n        # adopted PEP 518 early for the ability to specify requirements to\n        # execute setup.py, but never considered needing to mention the build\n        # tools themselves. The original PEP 518 code had a similar check (but\n        # implemented in a different way).\n        backend = \"setuptools.build_meta:__legacy__\"\n        check = [\"setuptools>=40.8.0\", \"wheel\"]\n\n    return (requires, backend, check)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/req/__init__.py",
    "content": "from __future__ import absolute_import\n\nimport logging\n\nfrom .req_install import InstallRequirement\nfrom .req_set import RequirementSet\nfrom .req_file import parse_requirements\nfrom pip._internal.utils.logging import indent_log\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import List, Sequence  # noqa: F401\n\n__all__ = [\n    \"RequirementSet\", \"InstallRequirement\",\n    \"parse_requirements\", \"install_given_reqs\",\n]\n\nlogger = logging.getLogger(__name__)\n\n\ndef install_given_reqs(\n    to_install,  # type: List[InstallRequirement]\n    install_options,  # type: List[str]\n    global_options=(),  # type: Sequence[str]\n    *args, **kwargs\n):\n    # type: (...) -> List[InstallRequirement]\n    \"\"\"\n    Install everything in the given list.\n\n    (to be called after having downloaded and unpacked the packages)\n    \"\"\"\n\n    if to_install:\n        logger.info(\n            'Installing collected packages: %s',\n            ', '.join([req.name for req in to_install]),\n        )\n\n    with indent_log():\n        for requirement in to_install:\n            if requirement.conflicts_with:\n                logger.info(\n                    'Found existing installation: %s',\n                    requirement.conflicts_with,\n                )\n                with indent_log():\n                    uninstalled_pathset = requirement.uninstall(\n                        auto_confirm=True\n                    )\n            try:\n                requirement.install(\n                    install_options,\n                    global_options,\n                    *args,\n                    **kwargs\n                )\n            except Exception:\n                should_rollback = (\n                    requirement.conflicts_with and\n                    not requirement.install_succeeded\n                )\n                # if install did not succeed, rollback previous uninstall\n                if should_rollback:\n                    uninstalled_pathset.rollback()\n                raise\n            else:\n                should_commit = (\n                    requirement.conflicts_with and\n                    requirement.install_succeeded\n                )\n                if should_commit:\n                    uninstalled_pathset.commit()\n            requirement.remove_temporary_source()\n\n    return to_install\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/req/constructors.py",
    "content": "\"\"\"Backing implementation for InstallRequirement's various constructors\n\nThe idea here is that these formed a major chunk of InstallRequirement's size\nso, moving them and support code dedicated to them outside of that class\nhelps creates for better understandability for the rest of the code.\n\nThese are meant to be used elsewhere within pip to create instances of\nInstallRequirement.\n\"\"\"\n\nimport logging\nimport os\nimport re\n\nfrom pip._vendor.packaging.markers import Marker\nfrom pip._vendor.packaging.requirements import InvalidRequirement, Requirement\nfrom pip._vendor.packaging.specifiers import Specifier\nfrom pip._vendor.pkg_resources import RequirementParseError, parse_requirements\n\nfrom pip._internal.download import (\n    is_archive_file, is_url, path_to_url, url_to_path,\n)\nfrom pip._internal.exceptions import InstallationError\nfrom pip._internal.models.index import PyPI, TestPyPI\nfrom pip._internal.models.link import Link\nfrom pip._internal.pyproject import make_pyproject_path\nfrom pip._internal.req.req_install import InstallRequirement\nfrom pip._internal.utils.misc import is_installable_dir\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\nfrom pip._internal.vcs import vcs\nfrom pip._internal.wheel import Wheel\n\nif MYPY_CHECK_RUNNING:\n    from typing import (   # noqa: F401\n        Optional, Tuple, Set, Any, Union, Text, Dict,\n    )\n    from pip._internal.cache import WheelCache  # noqa: F401\n\n\n__all__ = [\n    \"install_req_from_editable\", \"install_req_from_line\",\n    \"parse_editable\"\n]\n\nlogger = logging.getLogger(__name__)\noperators = Specifier._operators.keys()\n\n\ndef _strip_extras(path):\n    # type: (str) -> Tuple[str, Optional[str]]\n    m = re.match(r'^(.+)(\\[[^\\]]+\\])$', path)\n    extras = None\n    if m:\n        path_no_extras = m.group(1)\n        extras = m.group(2)\n    else:\n        path_no_extras = path\n\n    return path_no_extras, extras\n\n\ndef parse_editable(editable_req):\n    # type: (str) -> Tuple[Optional[str], str, Optional[Set[str]]]\n    \"\"\"Parses an editable requirement into:\n        - a requirement name\n        - an URL\n        - extras\n        - editable options\n    Accepted requirements:\n        svn+http://blahblah@rev#egg=Foobar[baz]&subdirectory=version_subdir\n        .[some_extra]\n    \"\"\"\n\n    url = editable_req\n\n    # If a file path is specified with extras, strip off the extras.\n    url_no_extras, extras = _strip_extras(url)\n\n    if os.path.isdir(url_no_extras):\n        if not os.path.exists(os.path.join(url_no_extras, 'setup.py')):\n            msg = (\n                'File \"setup.py\" not found. Directory cannot be installed '\n                'in editable mode: {}'.format(os.path.abspath(url_no_extras))\n            )\n            pyproject_path = make_pyproject_path(url_no_extras)\n            if os.path.isfile(pyproject_path):\n                msg += (\n                    '\\n(A \"pyproject.toml\" file was found, but editable '\n                    'mode currently requires a setup.py based build.)'\n                )\n            raise InstallationError(msg)\n\n        # Treating it as code that has already been checked out\n        url_no_extras = path_to_url(url_no_extras)\n\n    if url_no_extras.lower().startswith('file:'):\n        package_name = Link(url_no_extras).egg_fragment\n        if extras:\n            return (\n                package_name,\n                url_no_extras,\n                Requirement(\"placeholder\" + extras.lower()).extras,\n            )\n        else:\n            return package_name, url_no_extras, None\n\n    for version_control in vcs:\n        if url.lower().startswith('%s:' % version_control):\n            url = '%s+%s' % (version_control, url)\n            break\n\n    if '+' not in url:\n        raise InstallationError(\n            '%s should either be a path to a local project or a VCS url '\n            'beginning with svn+, git+, hg+, or bzr+' %\n            editable_req\n        )\n\n    vc_type = url.split('+', 1)[0].lower()\n\n    if not vcs.get_backend(vc_type):\n        error_message = 'For --editable=%s only ' % editable_req + \\\n            ', '.join([backend.name + '+URL' for backend in vcs.backends]) + \\\n            ' is currently supported'\n        raise InstallationError(error_message)\n\n    package_name = Link(url).egg_fragment\n    if not package_name:\n        raise InstallationError(\n            \"Could not detect requirement name for '%s', please specify one \"\n            \"with #egg=your_package_name\" % editable_req\n        )\n    return package_name, url, None\n\n\ndef deduce_helpful_msg(req):\n    # type: (str) -> str\n    \"\"\"Returns helpful msg in case requirements file does not exist,\n    or cannot be parsed.\n\n    :params req: Requirements file path\n    \"\"\"\n    msg = \"\"\n    if os.path.exists(req):\n        msg = \" It does exist.\"\n        # Try to parse and check if it is a requirements file.\n        try:\n            with open(req, 'r') as fp:\n                # parse first line only\n                next(parse_requirements(fp.read()))\n                msg += \" The argument you provided \" + \\\n                    \"(%s) appears to be a\" % (req) + \\\n                    \" requirements file. If that is the\" + \\\n                    \" case, use the '-r' flag to install\" + \\\n                    \" the packages specified within it.\"\n        except RequirementParseError:\n            logger.debug(\"Cannot parse '%s' as requirements \\\n            file\" % (req), exc_info=True)\n    else:\n        msg += \" File '%s' does not exist.\" % (req)\n    return msg\n\n\n# ---- The actual constructors follow ----\n\n\ndef install_req_from_editable(\n    editable_req,  # type: str\n    comes_from=None,  # type: Optional[str]\n    use_pep517=None,  # type: Optional[bool]\n    isolated=False,  # type: bool\n    options=None,  # type: Optional[Dict[str, Any]]\n    wheel_cache=None,  # type: Optional[WheelCache]\n    constraint=False  # type: bool\n):\n    # type: (...) -> InstallRequirement\n    name, url, extras_override = parse_editable(editable_req)\n    if url.startswith('file:'):\n        source_dir = url_to_path(url)\n    else:\n        source_dir = None\n\n    if name is not None:\n        try:\n            req = Requirement(name)\n        except InvalidRequirement:\n            raise InstallationError(\"Invalid requirement: '%s'\" % name)\n    else:\n        req = None\n    return InstallRequirement(\n        req, comes_from, source_dir=source_dir,\n        editable=True,\n        link=Link(url),\n        constraint=constraint,\n        use_pep517=use_pep517,\n        isolated=isolated,\n        options=options if options else {},\n        wheel_cache=wheel_cache,\n        extras=extras_override or (),\n    )\n\n\ndef install_req_from_line(\n    name,  # type: str\n    comes_from=None,  # type: Optional[Union[str, InstallRequirement]]\n    use_pep517=None,  # type: Optional[bool]\n    isolated=False,  # type: bool\n    options=None,  # type: Optional[Dict[str, Any]]\n    wheel_cache=None,  # type: Optional[WheelCache]\n    constraint=False  # type: bool\n):\n    # type: (...) -> InstallRequirement\n    \"\"\"Creates an InstallRequirement from a name, which might be a\n    requirement, directory containing 'setup.py', filename, or URL.\n    \"\"\"\n    if is_url(name):\n        marker_sep = '; '\n    else:\n        marker_sep = ';'\n    if marker_sep in name:\n        name, markers_as_string = name.split(marker_sep, 1)\n        markers_as_string = markers_as_string.strip()\n        if not markers_as_string:\n            markers = None\n        else:\n            markers = Marker(markers_as_string)\n    else:\n        markers = None\n    name = name.strip()\n    req_as_string = None\n    path = os.path.normpath(os.path.abspath(name))\n    link = None\n    extras_as_string = None\n\n    if is_url(name):\n        link = Link(name)\n    else:\n        p, extras_as_string = _strip_extras(path)\n        looks_like_dir = os.path.isdir(p) and (\n            os.path.sep in name or\n            (os.path.altsep is not None and os.path.altsep in name) or\n            name.startswith('.')\n        )\n        if looks_like_dir:\n            if not is_installable_dir(p):\n                raise InstallationError(\n                    \"Directory %r is not installable. Neither 'setup.py' \"\n                    \"nor 'pyproject.toml' found.\" % name\n                )\n            link = Link(path_to_url(p))\n        elif is_archive_file(p):\n            if not os.path.isfile(p):\n                logger.warning(\n                    'Requirement %r looks like a filename, but the '\n                    'file does not exist',\n                    name\n                )\n            link = Link(path_to_url(p))\n\n    # it's a local file, dir, or url\n    if link:\n        # Handle relative file URLs\n        if link.scheme == 'file' and re.search(r'\\.\\./', link.url):\n            link = Link(\n                path_to_url(os.path.normpath(os.path.abspath(link.path))))\n        # wheel file\n        if link.is_wheel:\n            wheel = Wheel(link.filename)  # can raise InvalidWheelFilename\n            req_as_string = \"%s==%s\" % (wheel.name, wheel.version)\n        else:\n            # set the req to the egg fragment.  when it's not there, this\n            # will become an 'unnamed' requirement\n            req_as_string = link.egg_fragment\n\n    # a requirement specifier\n    else:\n        req_as_string = name\n\n    if extras_as_string:\n        extras = Requirement(\"placeholder\" + extras_as_string.lower()).extras\n    else:\n        extras = ()\n    if req_as_string is not None:\n        try:\n            req = Requirement(req_as_string)\n        except InvalidRequirement:\n            if os.path.sep in req_as_string:\n                add_msg = \"It looks like a path.\"\n                add_msg += deduce_helpful_msg(req_as_string)\n            elif ('=' in req_as_string and\n                  not any(op in req_as_string for op in operators)):\n                add_msg = \"= is not a valid operator. Did you mean == ?\"\n            else:\n                add_msg = \"\"\n            raise InstallationError(\n                \"Invalid requirement: '%s'\\n%s\" % (req_as_string, add_msg)\n            )\n    else:\n        req = None\n\n    return InstallRequirement(\n        req, comes_from, link=link, markers=markers,\n        use_pep517=use_pep517, isolated=isolated,\n        options=options if options else {},\n        wheel_cache=wheel_cache,\n        constraint=constraint,\n        extras=extras,\n    )\n\n\ndef install_req_from_req_string(\n    req_string,  # type: str\n    comes_from=None,  # type: Optional[InstallRequirement]\n    isolated=False,  # type: bool\n    wheel_cache=None,  # type: Optional[WheelCache]\n    use_pep517=None  # type: Optional[bool]\n):\n    # type: (...) -> InstallRequirement\n    try:\n        req = Requirement(req_string)\n    except InvalidRequirement:\n        raise InstallationError(\"Invalid requirement: '%s'\" % req)\n\n    domains_not_allowed = [\n        PyPI.file_storage_domain,\n        TestPyPI.file_storage_domain,\n    ]\n    if req.url and comes_from.link.netloc in domains_not_allowed:\n        # Explicitly disallow pypi packages that depend on external urls\n        raise InstallationError(\n            \"Packages installed from PyPI cannot depend on packages \"\n            \"which are not also hosted on PyPI.\\n\"\n            \"%s depends on %s \" % (comes_from.name, req)\n        )\n\n    return InstallRequirement(\n        req, comes_from, isolated=isolated, wheel_cache=wheel_cache,\n        use_pep517=use_pep517\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/req/req_file.py",
    "content": "\"\"\"\nRequirements file parsing\n\"\"\"\n\nfrom __future__ import absolute_import\n\nimport optparse\nimport os\nimport re\nimport shlex\nimport sys\n\nfrom pip._vendor.six.moves import filterfalse\nfrom pip._vendor.six.moves.urllib import parse as urllib_parse\n\nfrom pip._internal.cli import cmdoptions\nfrom pip._internal.download import get_file_content\nfrom pip._internal.exceptions import RequirementsFileParseError\nfrom pip._internal.req.constructors import (\n    install_req_from_editable, install_req_from_line,\n)\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import (  # noqa: F401\n        Iterator, Tuple, Optional, List, Callable, Text\n    )\n    from pip._internal.req import InstallRequirement  # noqa: F401\n    from pip._internal.cache import WheelCache  # noqa: F401\n    from pip._internal.index import PackageFinder  # noqa: F401\n    from pip._internal.download import PipSession  # noqa: F401\n\n    ReqFileLines = Iterator[Tuple[int, Text]]\n\n__all__ = ['parse_requirements']\n\nSCHEME_RE = re.compile(r'^(http|https|file):', re.I)\nCOMMENT_RE = re.compile(r'(^|\\s)+#.*$')\n\n# Matches environment variable-style values in '${MY_VARIABLE_1}' with the\n# variable name consisting of only uppercase letters, digits or the '_'\n# (underscore). This follows the POSIX standard defined in IEEE Std 1003.1,\n# 2013 Edition.\nENV_VAR_RE = re.compile(r'(?P<var>\\$\\{(?P<name>[A-Z0-9_]+)\\})')\n\nSUPPORTED_OPTIONS = [\n    cmdoptions.constraints,\n    cmdoptions.editable,\n    cmdoptions.requirements,\n    cmdoptions.no_index,\n    cmdoptions.index_url,\n    cmdoptions.find_links,\n    cmdoptions.extra_index_url,\n    cmdoptions.always_unzip,\n    cmdoptions.no_binary,\n    cmdoptions.only_binary,\n    cmdoptions.pre,\n    cmdoptions.trusted_host,\n    cmdoptions.require_hashes,\n]  # type: List[Callable[..., optparse.Option]]\n\n# options to be passed to requirements\nSUPPORTED_OPTIONS_REQ = [\n    cmdoptions.install_options,\n    cmdoptions.global_options,\n    cmdoptions.hash,\n]  # type: List[Callable[..., optparse.Option]]\n\n# the 'dest' string values\nSUPPORTED_OPTIONS_REQ_DEST = [str(o().dest) for o in SUPPORTED_OPTIONS_REQ]\n\n\ndef parse_requirements(\n    filename,  # type: str\n    finder=None,  # type: Optional[PackageFinder]\n    comes_from=None,  # type: Optional[str]\n    options=None,  # type: Optional[optparse.Values]\n    session=None,  # type: Optional[PipSession]\n    constraint=False,  # type: bool\n    wheel_cache=None,  # type: Optional[WheelCache]\n    use_pep517=None  # type: Optional[bool]\n):\n    # type: (...) -> Iterator[InstallRequirement]\n    \"\"\"Parse a requirements file and yield InstallRequirement instances.\n\n    :param filename:    Path or url of requirements file.\n    :param finder:      Instance of pip.index.PackageFinder.\n    :param comes_from:  Origin description of requirements.\n    :param options:     cli options.\n    :param session:     Instance of pip.download.PipSession.\n    :param constraint:  If true, parsing a constraint file rather than\n        requirements file.\n    :param wheel_cache: Instance of pip.wheel.WheelCache\n    :param use_pep517:  Value of the --use-pep517 option.\n    \"\"\"\n    if session is None:\n        raise TypeError(\n            \"parse_requirements() missing 1 required keyword argument: \"\n            \"'session'\"\n        )\n\n    _, content = get_file_content(\n        filename, comes_from=comes_from, session=session\n    )\n\n    lines_enum = preprocess(content, options)\n\n    for line_number, line in lines_enum:\n        req_iter = process_line(line, filename, line_number, finder,\n                                comes_from, options, session, wheel_cache,\n                                use_pep517=use_pep517, constraint=constraint)\n        for req in req_iter:\n            yield req\n\n\ndef preprocess(content, options):\n    # type: (Text, Optional[optparse.Values]) -> ReqFileLines\n    \"\"\"Split, filter, and join lines, and return a line iterator\n\n    :param content: the content of the requirements file\n    :param options: cli options\n    \"\"\"\n    lines_enum = enumerate(content.splitlines(), start=1)  # type: ReqFileLines\n    lines_enum = join_lines(lines_enum)\n    lines_enum = ignore_comments(lines_enum)\n    lines_enum = skip_regex(lines_enum, options)\n    lines_enum = expand_env_variables(lines_enum)\n    return lines_enum\n\n\ndef process_line(\n    line,  # type: Text\n    filename,  # type: str\n    line_number,  # type: int\n    finder=None,  # type: Optional[PackageFinder]\n    comes_from=None,  # type: Optional[str]\n    options=None,  # type: Optional[optparse.Values]\n    session=None,  # type: Optional[PipSession]\n    wheel_cache=None,  # type: Optional[WheelCache]\n    use_pep517=None,  # type: Optional[bool]\n    constraint=False  # type: bool\n):\n    # type: (...) -> Iterator[InstallRequirement]\n    \"\"\"Process a single requirements line; This can result in creating/yielding\n    requirements, or updating the finder.\n\n    For lines that contain requirements, the only options that have an effect\n    are from SUPPORTED_OPTIONS_REQ, and they are scoped to the\n    requirement. Other options from SUPPORTED_OPTIONS may be present, but are\n    ignored.\n\n    For lines that do not contain requirements, the only options that have an\n    effect are from SUPPORTED_OPTIONS. Options from SUPPORTED_OPTIONS_REQ may\n    be present, but are ignored. These lines may contain multiple options\n    (although our docs imply only one is supported), and all our parsed and\n    affect the finder.\n\n    :param constraint: If True, parsing a constraints file.\n    :param options: OptionParser options that we may update\n    \"\"\"\n    parser = build_parser(line)\n    defaults = parser.get_default_values()\n    defaults.index_url = None\n    if finder:\n        defaults.format_control = finder.format_control\n    args_str, options_str = break_args_options(line)\n    # Prior to 2.7.3, shlex cannot deal with unicode entries\n    if sys.version_info < (2, 7, 3):\n        # https://github.com/python/mypy/issues/1174\n        options_str = options_str.encode('utf8')  # type: ignore\n    # https://github.com/python/mypy/issues/1174\n    opts, _ = parser.parse_args(\n        shlex.split(options_str), defaults)  # type: ignore\n\n    # preserve for the nested code path\n    line_comes_from = '%s %s (line %s)' % (\n        '-c' if constraint else '-r', filename, line_number,\n    )\n\n    # yield a line requirement\n    if args_str:\n        isolated = options.isolated_mode if options else False\n        if options:\n            cmdoptions.check_install_build_global(options, opts)\n        # get the options that apply to requirements\n        req_options = {}\n        for dest in SUPPORTED_OPTIONS_REQ_DEST:\n            if dest in opts.__dict__ and opts.__dict__[dest]:\n                req_options[dest] = opts.__dict__[dest]\n        yield install_req_from_line(\n            args_str, line_comes_from, constraint=constraint,\n            use_pep517=use_pep517,\n            isolated=isolated, options=req_options, wheel_cache=wheel_cache\n        )\n\n    # yield an editable requirement\n    elif opts.editables:\n        isolated = options.isolated_mode if options else False\n        yield install_req_from_editable(\n            opts.editables[0], comes_from=line_comes_from,\n            use_pep517=use_pep517,\n            constraint=constraint, isolated=isolated, wheel_cache=wheel_cache\n        )\n\n    # parse a nested requirements file\n    elif opts.requirements or opts.constraints:\n        if opts.requirements:\n            req_path = opts.requirements[0]\n            nested_constraint = False\n        else:\n            req_path = opts.constraints[0]\n            nested_constraint = True\n        # original file is over http\n        if SCHEME_RE.search(filename):\n            # do a url join so relative paths work\n            req_path = urllib_parse.urljoin(filename, req_path)\n        # original file and nested file are paths\n        elif not SCHEME_RE.search(req_path):\n            # do a join so relative paths work\n            req_path = os.path.join(os.path.dirname(filename), req_path)\n        # TODO: Why not use `comes_from='-r {} (line {})'` here as well?\n        parsed_reqs = parse_requirements(\n            req_path, finder, comes_from, options, session,\n            constraint=nested_constraint, wheel_cache=wheel_cache\n        )\n        for req in parsed_reqs:\n            yield req\n\n    # percolate hash-checking option upward\n    elif opts.require_hashes:\n        options.require_hashes = opts.require_hashes\n\n    # set finder options\n    elif finder:\n        if opts.index_url:\n            finder.index_urls = [opts.index_url]\n        if opts.no_index is True:\n            finder.index_urls = []\n        if opts.extra_index_urls:\n            finder.index_urls.extend(opts.extra_index_urls)\n        if opts.find_links:\n            # FIXME: it would be nice to keep track of the source\n            # of the find_links: support a find-links local path\n            # relative to a requirements file.\n            value = opts.find_links[0]\n            req_dir = os.path.dirname(os.path.abspath(filename))\n            relative_to_reqs_file = os.path.join(req_dir, value)\n            if os.path.exists(relative_to_reqs_file):\n                value = relative_to_reqs_file\n            finder.find_links.append(value)\n        if opts.pre:\n            finder.allow_all_prereleases = True\n        if opts.trusted_hosts:\n            finder.secure_origins.extend(\n                (\"*\", host, \"*\") for host in opts.trusted_hosts)\n\n\ndef break_args_options(line):\n    # type: (Text) -> Tuple[str, Text]\n    \"\"\"Break up the line into an args and options string.  We only want to shlex\n    (and then optparse) the options, not the args.  args can contain markers\n    which are corrupted by shlex.\n    \"\"\"\n    tokens = line.split(' ')\n    args = []\n    options = tokens[:]\n    for token in tokens:\n        if token.startswith('-') or token.startswith('--'):\n            break\n        else:\n            args.append(token)\n            options.pop(0)\n    return ' '.join(args), ' '.join(options)  # type: ignore\n\n\ndef build_parser(line):\n    # type: (Text) -> optparse.OptionParser\n    \"\"\"\n    Return a parser for parsing requirement lines\n    \"\"\"\n    parser = optparse.OptionParser(add_help_option=False)\n\n    option_factories = SUPPORTED_OPTIONS + SUPPORTED_OPTIONS_REQ\n    for option_factory in option_factories:\n        option = option_factory()\n        parser.add_option(option)\n\n    # By default optparse sys.exits on parsing errors. We want to wrap\n    # that in our own exception.\n    def parser_exit(self, msg):\n        # add offending line\n        msg = 'Invalid requirement: %s\\n%s' % (line, msg)\n        raise RequirementsFileParseError(msg)\n    # NOTE: mypy disallows assigning to a method\n    #       https://github.com/python/mypy/issues/2427\n    parser.exit = parser_exit  # type: ignore\n\n    return parser\n\n\ndef join_lines(lines_enum):\n    # type: (ReqFileLines) -> ReqFileLines\n    \"\"\"Joins a line ending in '\\' with the previous line (except when following\n    comments).  The joined line takes on the index of the first line.\n    \"\"\"\n    primary_line_number = None\n    new_line = []  # type: List[Text]\n    for line_number, line in lines_enum:\n        if not line.endswith('\\\\') or COMMENT_RE.match(line):\n            if COMMENT_RE.match(line):\n                # this ensures comments are always matched later\n                line = ' ' + line\n            if new_line:\n                new_line.append(line)\n                yield primary_line_number, ''.join(new_line)\n                new_line = []\n            else:\n                yield line_number, line\n        else:\n            if not new_line:\n                primary_line_number = line_number\n            new_line.append(line.strip('\\\\'))\n\n    # last line contains \\\n    if new_line:\n        yield primary_line_number, ''.join(new_line)\n\n    # TODO: handle space after '\\'.\n\n\ndef ignore_comments(lines_enum):\n    # type: (ReqFileLines) -> ReqFileLines\n    \"\"\"\n    Strips comments and filter empty lines.\n    \"\"\"\n    for line_number, line in lines_enum:\n        line = COMMENT_RE.sub('', line)\n        line = line.strip()\n        if line:\n            yield line_number, line\n\n\ndef skip_regex(lines_enum, options):\n    # type: (ReqFileLines, Optional[optparse.Values]) -> ReqFileLines\n    \"\"\"\n    Skip lines that match '--skip-requirements-regex' pattern\n\n    Note: the regex pattern is only built once\n    \"\"\"\n    skip_regex = options.skip_requirements_regex if options else None\n    if skip_regex:\n        pattern = re.compile(skip_regex)\n        lines_enum = filterfalse(lambda e: pattern.search(e[1]), lines_enum)\n    return lines_enum\n\n\ndef expand_env_variables(lines_enum):\n    # type: (ReqFileLines) -> ReqFileLines\n    \"\"\"Replace all environment variables that can be retrieved via `os.getenv`.\n\n    The only allowed format for environment variables defined in the\n    requirement file is `${MY_VARIABLE_1}` to ensure two things:\n\n    1. Strings that contain a `$` aren't accidentally (partially) expanded.\n    2. Ensure consistency across platforms for requirement files.\n\n    These points are the result of a discusssion on the `github pull\n    request #3514 <https://github.com/pypa/pip/pull/3514>`_.\n\n    Valid characters in variable names follow the `POSIX standard\n    <http://pubs.opengroup.org/onlinepubs/9699919799/>`_ and are limited\n    to uppercase letter, digits and the `_` (underscore).\n    \"\"\"\n    for line_number, line in lines_enum:\n        for env_var, var_name in ENV_VAR_RE.findall(line):\n            value = os.getenv(var_name)\n            if not value:\n                continue\n\n            line = line.replace(env_var, value)\n\n        yield line_number, line\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/req/req_install.py",
    "content": "from __future__ import absolute_import\n\nimport logging\nimport os\nimport shutil\nimport sys\nimport sysconfig\nimport zipfile\nfrom distutils.util import change_root\n\nfrom pip._vendor import pkg_resources, six\nfrom pip._vendor.packaging.requirements import Requirement\nfrom pip._vendor.packaging.utils import canonicalize_name\nfrom pip._vendor.packaging.version import Version\nfrom pip._vendor.packaging.version import parse as parse_version\nfrom pip._vendor.pep517.wrappers import Pep517HookCaller\n\nfrom pip._internal import wheel\nfrom pip._internal.build_env import NoOpBuildEnvironment\nfrom pip._internal.exceptions import InstallationError\nfrom pip._internal.locations import (\n    PIP_DELETE_MARKER_FILENAME, running_under_virtualenv,\n)\nfrom pip._internal.models.link import Link\nfrom pip._internal.pyproject import load_pyproject_toml, make_pyproject_path\nfrom pip._internal.req.req_uninstall import UninstallPathSet\nfrom pip._internal.utils.compat import native_str\nfrom pip._internal.utils.hashes import Hashes\nfrom pip._internal.utils.logging import indent_log\nfrom pip._internal.utils.misc import (\n    _make_build_dir, ask_path_exists, backup_dir, call_subprocess,\n    display_path, dist_in_site_packages, dist_in_usersite, ensure_dir,\n    get_installed_version, redact_password_from_url, rmtree,\n)\nfrom pip._internal.utils.packaging import get_metadata\nfrom pip._internal.utils.setuptools_build import SETUPTOOLS_SHIM\nfrom pip._internal.utils.temp_dir import TempDirectory\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\nfrom pip._internal.utils.ui import open_spinner\nfrom pip._internal.vcs import vcs\nfrom pip._internal.wheel import move_wheel_files\n\nif MYPY_CHECK_RUNNING:\n    from typing import (  # noqa: F401\n        Optional, Iterable, List, Union, Any, Text, Sequence, Dict\n    )\n    from pip._internal.build_env import BuildEnvironment  # noqa: F401\n    from pip._internal.cache import WheelCache  # noqa: F401\n    from pip._internal.index import PackageFinder  # noqa: F401\n    from pip._vendor.pkg_resources import Distribution  # noqa: F401\n    from pip._vendor.packaging.specifiers import SpecifierSet  # noqa: F401\n    from pip._vendor.packaging.markers import Marker  # noqa: F401\n\n\nlogger = logging.getLogger(__name__)\n\n\nclass InstallRequirement(object):\n    \"\"\"\n    Represents something that may be installed later on, may have information\n    about where to fetch the relavant requirement and also contains logic for\n    installing the said requirement.\n    \"\"\"\n\n    def __init__(\n        self,\n        req,  # type: Optional[Requirement]\n        comes_from,  # type: Optional[Union[str, InstallRequirement]]\n        source_dir=None,  # type: Optional[str]\n        editable=False,  # type: bool\n        link=None,  # type: Optional[Link]\n        update=True,  # type: bool\n        markers=None,  # type: Optional[Marker]\n        use_pep517=None,  # type: Optional[bool]\n        isolated=False,  # type: bool\n        options=None,  # type: Optional[Dict[str, Any]]\n        wheel_cache=None,  # type: Optional[WheelCache]\n        constraint=False,  # type: bool\n        extras=()  # type: Iterable[str]\n    ):\n        # type: (...) -> None\n        assert req is None or isinstance(req, Requirement), req\n        self.req = req\n        self.comes_from = comes_from\n        self.constraint = constraint\n        if source_dir is not None:\n            self.source_dir = os.path.normpath(os.path.abspath(source_dir))\n        else:\n            self.source_dir = None\n        self.editable = editable\n\n        self._wheel_cache = wheel_cache\n        if link is None and req and req.url:\n            # PEP 508 URL requirement\n            link = Link(req.url)\n        self.link = self.original_link = link\n\n        if extras:\n            self.extras = extras\n        elif req:\n            self.extras = {\n                pkg_resources.safe_extra(extra) for extra in req.extras\n            }\n        else:\n            self.extras = set()\n        if markers is None and req:\n            markers = req.marker\n        self.markers = markers\n\n        self._egg_info_path = None  # type: Optional[str]\n        # This holds the pkg_resources.Distribution object if this requirement\n        # is already available:\n        self.satisfied_by = None\n        # This hold the pkg_resources.Distribution object if this requirement\n        # conflicts with another installed distribution:\n        self.conflicts_with = None\n        # Temporary build location\n        self._temp_build_dir = TempDirectory(kind=\"req-build\")\n        # Used to store the global directory where the _temp_build_dir should\n        # have been created. Cf _correct_build_location method.\n        self._ideal_build_dir = None  # type: Optional[str]\n        # True if the editable should be updated:\n        self.update = update\n        # Set to True after successful installation\n        self.install_succeeded = None  # type: Optional[bool]\n        # UninstallPathSet of uninstalled distribution (for possible rollback)\n        self.uninstalled_pathset = None\n        self.options = options if options else {}\n        # Set to True after successful preparation of this requirement\n        self.prepared = False\n        self.is_direct = False\n\n        self.isolated = isolated\n        self.build_env = NoOpBuildEnvironment()  # type: BuildEnvironment\n\n        # For PEP 517, the directory where we request the project metadata\n        # gets stored. We need this to pass to build_wheel, so the backend\n        # can ensure that the wheel matches the metadata (see the PEP for\n        # details).\n        self.metadata_directory = None  # type: Optional[str]\n\n        # The static build requirements (from pyproject.toml)\n        self.pyproject_requires = None  # type: Optional[List[str]]\n\n        # Build requirements that we will check are available\n        self.requirements_to_check = []  # type: List[str]\n\n        # The PEP 517 backend we should use to build the project\n        self.pep517_backend = None  # type: Optional[Pep517HookCaller]\n\n        # Are we using PEP 517 for this requirement?\n        # After pyproject.toml has been loaded, the only valid values are True\n        # and False. Before loading, None is valid (meaning \"use the default\").\n        # Setting an explicit value before loading pyproject.toml is supported,\n        # but after loading this flag should be treated as read only.\n        self.use_pep517 = use_pep517\n\n    def __str__(self):\n        if self.req:\n            s = str(self.req)\n            if self.link:\n                s += ' from %s' % redact_password_from_url(self.link.url)\n        elif self.link:\n            s = redact_password_from_url(self.link.url)\n        else:\n            s = '<InstallRequirement>'\n        if self.satisfied_by is not None:\n            s += ' in %s' % display_path(self.satisfied_by.location)\n        if self.comes_from:\n            if isinstance(self.comes_from, six.string_types):\n                comes_from = self.comes_from\n            else:\n                comes_from = self.comes_from.from_path()\n            if comes_from:\n                s += ' (from %s)' % comes_from\n        return s\n\n    def __repr__(self):\n        return '<%s object: %s editable=%r>' % (\n            self.__class__.__name__, str(self), self.editable)\n\n    def populate_link(self, finder, upgrade, require_hashes):\n        # type: (PackageFinder, bool, bool) -> None\n        \"\"\"Ensure that if a link can be found for this, that it is found.\n\n        Note that self.link may still be None - if Upgrade is False and the\n        requirement is already installed.\n\n        If require_hashes is True, don't use the wheel cache, because cached\n        wheels, always built locally, have different hashes than the files\n        downloaded from the index server and thus throw false hash mismatches.\n        Furthermore, cached wheels at present have undeterministic contents due\n        to file modification times.\n        \"\"\"\n        if self.link is None:\n            self.link = finder.find_requirement(self, upgrade)\n        if self._wheel_cache is not None and not require_hashes:\n            old_link = self.link\n            self.link = self._wheel_cache.get(self.link, self.name)\n            if old_link != self.link:\n                logger.debug('Using cached wheel link: %s', self.link)\n\n    # Things that are valid for all kinds of requirements?\n    @property\n    def name(self):\n        # type: () -> Optional[str]\n        if self.req is None:\n            return None\n        return native_str(pkg_resources.safe_name(self.req.name))\n\n    @property\n    def specifier(self):\n        # type: () -> SpecifierSet\n        return self.req.specifier\n\n    @property\n    def is_pinned(self):\n        # type: () -> bool\n        \"\"\"Return whether I am pinned to an exact version.\n\n        For example, some-package==1.2 is pinned; some-package>1.2 is not.\n        \"\"\"\n        specifiers = self.specifier\n        return (len(specifiers) == 1 and\n                next(iter(specifiers)).operator in {'==', '==='})\n\n    @property\n    def installed_version(self):\n        return get_installed_version(self.name)\n\n    def match_markers(self, extras_requested=None):\n        # type: (Optional[Iterable[str]]) -> bool\n        if not extras_requested:\n            # Provide an extra to safely evaluate the markers\n            # without matching any extra\n            extras_requested = ('',)\n        if self.markers is not None:\n            return any(\n                self.markers.evaluate({'extra': extra})\n                for extra in extras_requested)\n        else:\n            return True\n\n    @property\n    def has_hash_options(self):\n        # type: () -> bool\n        \"\"\"Return whether any known-good hashes are specified as options.\n\n        These activate --require-hashes mode; hashes specified as part of a\n        URL do not.\n\n        \"\"\"\n        return bool(self.options.get('hashes', {}))\n\n    def hashes(self, trust_internet=True):\n        # type: (bool) -> Hashes\n        \"\"\"Return a hash-comparer that considers my option- and URL-based\n        hashes to be known-good.\n\n        Hashes in URLs--ones embedded in the requirements file, not ones\n        downloaded from an index server--are almost peers with ones from\n        flags. They satisfy --require-hashes (whether it was implicitly or\n        explicitly activated) but do not activate it. md5 and sha224 are not\n        allowed in flags, which should nudge people toward good algos. We\n        always OR all hashes together, even ones from URLs.\n\n        :param trust_internet: Whether to trust URL-based (#md5=...) hashes\n            downloaded from the internet, as by populate_link()\n\n        \"\"\"\n        good_hashes = self.options.get('hashes', {}).copy()\n        link = self.link if trust_internet else self.original_link\n        if link and link.hash:\n            good_hashes.setdefault(link.hash_name, []).append(link.hash)\n        return Hashes(good_hashes)\n\n    def from_path(self):\n        # type: () -> Optional[str]\n        \"\"\"Format a nice indicator to show where this \"comes from\"\n        \"\"\"\n        if self.req is None:\n            return None\n        s = str(self.req)\n        if self.comes_from:\n            if isinstance(self.comes_from, six.string_types):\n                comes_from = self.comes_from\n            else:\n                comes_from = self.comes_from.from_path()\n            if comes_from:\n                s += '->' + comes_from\n        return s\n\n    def build_location(self, build_dir):\n        # type: (str) -> Optional[str]\n        assert build_dir is not None\n        if self._temp_build_dir.path is not None:\n            return self._temp_build_dir.path\n        if self.req is None:\n            # for requirement via a path to a directory: the name of the\n            # package is not available yet so we create a temp directory\n            # Once run_egg_info will have run, we'll be able\n            # to fix it via _correct_build_location\n            # Some systems have /tmp as a symlink which confuses custom\n            # builds (such as numpy). Thus, we ensure that the real path\n            # is returned.\n            self._temp_build_dir.create()\n            self._ideal_build_dir = build_dir\n\n            return self._temp_build_dir.path\n        if self.editable:\n            name = self.name.lower()\n        else:\n            name = self.name\n        # FIXME: Is there a better place to create the build_dir? (hg and bzr\n        # need this)\n        if not os.path.exists(build_dir):\n            logger.debug('Creating directory %s', build_dir)\n            _make_build_dir(build_dir)\n        return os.path.join(build_dir, name)\n\n    def _correct_build_location(self):\n        # type: () -> None\n        \"\"\"Move self._temp_build_dir to self._ideal_build_dir/self.req.name\n\n        For some requirements (e.g. a path to a directory), the name of the\n        package is not available until we run egg_info, so the build_location\n        will return a temporary directory and store the _ideal_build_dir.\n\n        This is only called by self.run_egg_info to fix the temporary build\n        directory.\n        \"\"\"\n        if self.source_dir is not None:\n            return\n        assert self.req is not None\n        assert self._temp_build_dir.path\n        assert (self._ideal_build_dir is not None and\n                self._ideal_build_dir.path)  # type: ignore\n        old_location = self._temp_build_dir.path\n        self._temp_build_dir.path = None\n\n        new_location = self.build_location(self._ideal_build_dir)\n        if os.path.exists(new_location):\n            raise InstallationError(\n                'A package already exists in %s; please remove it to continue'\n                % display_path(new_location))\n        logger.debug(\n            'Moving package %s from %s to new location %s',\n            self, display_path(old_location), display_path(new_location),\n        )\n        shutil.move(old_location, new_location)\n        self._temp_build_dir.path = new_location\n        self._ideal_build_dir = None\n        self.source_dir = os.path.normpath(os.path.abspath(new_location))\n        self._egg_info_path = None\n\n        # Correct the metadata directory, if it exists\n        if self.metadata_directory:\n            old_meta = self.metadata_directory\n            rel = os.path.relpath(old_meta, start=old_location)\n            new_meta = os.path.join(new_location, rel)\n            new_meta = os.path.normpath(os.path.abspath(new_meta))\n            self.metadata_directory = new_meta\n\n    def remove_temporary_source(self):\n        # type: () -> None\n        \"\"\"Remove the source files from this requirement, if they are marked\n        for deletion\"\"\"\n        if self.source_dir and os.path.exists(\n                os.path.join(self.source_dir, PIP_DELETE_MARKER_FILENAME)):\n            logger.debug('Removing source in %s', self.source_dir)\n            rmtree(self.source_dir)\n        self.source_dir = None\n        self._temp_build_dir.cleanup()\n        self.build_env.cleanup()\n\n    def check_if_exists(self, use_user_site):\n        # type: (bool) -> bool\n        \"\"\"Find an installed distribution that satisfies or conflicts\n        with this requirement, and set self.satisfied_by or\n        self.conflicts_with appropriately.\n        \"\"\"\n        if self.req is None:\n            return False\n        try:\n            # get_distribution() will resolve the entire list of requirements\n            # anyway, and we've already determined that we need the requirement\n            # in question, so strip the marker so that we don't try to\n            # evaluate it.\n            no_marker = Requirement(str(self.req))\n            no_marker.marker = None\n            self.satisfied_by = pkg_resources.get_distribution(str(no_marker))\n            if self.editable and self.satisfied_by:\n                self.conflicts_with = self.satisfied_by\n                # when installing editables, nothing pre-existing should ever\n                # satisfy\n                self.satisfied_by = None\n                return True\n        except pkg_resources.DistributionNotFound:\n            return False\n        except pkg_resources.VersionConflict:\n            existing_dist = pkg_resources.get_distribution(\n                self.req.name\n            )\n            if use_user_site:\n                if dist_in_usersite(existing_dist):\n                    self.conflicts_with = existing_dist\n                elif (running_under_virtualenv() and\n                        dist_in_site_packages(existing_dist)):\n                    raise InstallationError(\n                        \"Will not install to the user site because it will \"\n                        \"lack sys.path precedence to %s in %s\" %\n                        (existing_dist.project_name, existing_dist.location)\n                    )\n            else:\n                self.conflicts_with = existing_dist\n        return True\n\n    # Things valid for wheels\n    @property\n    def is_wheel(self):\n        # type: () -> bool\n        if not self.link:\n            return False\n        return self.link.is_wheel\n\n    def move_wheel_files(\n        self,\n        wheeldir,  # type: str\n        root=None,  # type: Optional[str]\n        home=None,  # type: Optional[str]\n        prefix=None,  # type: Optional[str]\n        warn_script_location=True,  # type: bool\n        use_user_site=False,  # type: bool\n        pycompile=True  # type: bool\n    ):\n        # type: (...) -> None\n        move_wheel_files(\n            self.name, self.req, wheeldir,\n            user=use_user_site,\n            home=home,\n            root=root,\n            prefix=prefix,\n            pycompile=pycompile,\n            isolated=self.isolated,\n            warn_script_location=warn_script_location,\n        )\n\n    # Things valid for sdists\n    @property\n    def setup_py_dir(self):\n        # type: () -> str\n        return os.path.join(\n            self.source_dir,\n            self.link and self.link.subdirectory_fragment or '')\n\n    @property\n    def setup_py(self):\n        # type: () -> str\n        assert self.source_dir, \"No source dir for %s\" % self\n\n        setup_py = os.path.join(self.setup_py_dir, 'setup.py')\n\n        # Python2 __file__ should not be unicode\n        if six.PY2 and isinstance(setup_py, six.text_type):\n            setup_py = setup_py.encode(sys.getfilesystemencoding())\n\n        return setup_py\n\n    @property\n    def pyproject_toml(self):\n        # type: () -> str\n        assert self.source_dir, \"No source dir for %s\" % self\n\n        return make_pyproject_path(self.setup_py_dir)\n\n    def load_pyproject_toml(self):\n        # type: () -> None\n        \"\"\"Load the pyproject.toml file.\n\n        After calling this routine, all of the attributes related to PEP 517\n        processing for this requirement have been set. In particular, the\n        use_pep517 attribute can be used to determine whether we should\n        follow the PEP 517 or legacy (setup.py) code path.\n        \"\"\"\n        pep517_data = load_pyproject_toml(\n            self.use_pep517,\n            self.pyproject_toml,\n            self.setup_py,\n            str(self)\n        )\n\n        if pep517_data is None:\n            self.use_pep517 = False\n        else:\n            self.use_pep517 = True\n            requires, backend, check = pep517_data\n            self.requirements_to_check = check\n            self.pyproject_requires = requires\n            self.pep517_backend = Pep517HookCaller(self.setup_py_dir, backend)\n\n            # Use a custom function to call subprocesses\n            self.spin_message = \"\"\n\n            def runner(cmd, cwd=None, extra_environ=None):\n                with open_spinner(self.spin_message) as spinner:\n                    call_subprocess(\n                        cmd,\n                        cwd=cwd,\n                        extra_environ=extra_environ,\n                        show_stdout=False,\n                        spinner=spinner\n                    )\n                self.spin_message = \"\"\n\n            self.pep517_backend._subprocess_runner = runner\n\n    def prepare_metadata(self):\n        # type: () -> None\n        \"\"\"Ensure that project metadata is available.\n\n        Under PEP 517, call the backend hook to prepare the metadata.\n        Under legacy processing, call setup.py egg-info.\n        \"\"\"\n        assert self.source_dir\n\n        with indent_log():\n            if self.use_pep517:\n                self.prepare_pep517_metadata()\n            else:\n                self.run_egg_info()\n\n        if not self.req:\n            if isinstance(parse_version(self.metadata[\"Version\"]), Version):\n                op = \"==\"\n            else:\n                op = \"===\"\n            self.req = Requirement(\n                \"\".join([\n                    self.metadata[\"Name\"],\n                    op,\n                    self.metadata[\"Version\"],\n                ])\n            )\n            self._correct_build_location()\n        else:\n            metadata_name = canonicalize_name(self.metadata[\"Name\"])\n            if canonicalize_name(self.req.name) != metadata_name:\n                logger.warning(\n                    'Generating metadata for package %s '\n                    'produced metadata for project name %s. Fix your '\n                    '#egg=%s fragments.',\n                    self.name, metadata_name, self.name\n                )\n                self.req = Requirement(metadata_name)\n\n    def prepare_pep517_metadata(self):\n        # type: () -> None\n        assert self.pep517_backend is not None\n\n        metadata_dir = os.path.join(\n            self.setup_py_dir,\n            'pip-wheel-metadata'\n        )\n        ensure_dir(metadata_dir)\n\n        with self.build_env:\n            # Note that Pep517HookCaller implements a fallback for\n            # prepare_metadata_for_build_wheel, so we don't have to\n            # consider the possibility that this hook doesn't exist.\n            backend = self.pep517_backend\n            self.spin_message = \"Preparing wheel metadata\"\n            distinfo_dir = backend.prepare_metadata_for_build_wheel(\n                metadata_dir\n            )\n\n        self.metadata_directory = os.path.join(metadata_dir, distinfo_dir)\n\n    def run_egg_info(self):\n        # type: () -> None\n        if self.name:\n            logger.debug(\n                'Running setup.py (path:%s) egg_info for package %s',\n                self.setup_py, self.name,\n            )\n        else:\n            logger.debug(\n                'Running setup.py (path:%s) egg_info for package from %s',\n                self.setup_py, self.link,\n            )\n        script = SETUPTOOLS_SHIM % self.setup_py\n        base_cmd = [sys.executable, '-c', script]\n        if self.isolated:\n            base_cmd += [\"--no-user-cfg\"]\n        egg_info_cmd = base_cmd + ['egg_info']\n        # We can't put the .egg-info files at the root, because then the\n        # source code will be mistaken for an installed egg, causing\n        # problems\n        if self.editable:\n            egg_base_option = []  # type: List[str]\n        else:\n            egg_info_dir = os.path.join(self.setup_py_dir, 'pip-egg-info')\n            ensure_dir(egg_info_dir)\n            egg_base_option = ['--egg-base', 'pip-egg-info']\n        with self.build_env:\n            call_subprocess(\n                egg_info_cmd + egg_base_option,\n                cwd=self.setup_py_dir,\n                show_stdout=False,\n                command_desc='python setup.py egg_info')\n\n    @property\n    def egg_info_path(self):\n        # type: () -> str\n        if self._egg_info_path is None:\n            if self.editable:\n                base = self.source_dir\n            else:\n                base = os.path.join(self.setup_py_dir, 'pip-egg-info')\n            filenames = os.listdir(base)\n            if self.editable:\n                filenames = []\n                for root, dirs, files in os.walk(base):\n                    for dir in vcs.dirnames:\n                        if dir in dirs:\n                            dirs.remove(dir)\n                    # Iterate over a copy of ``dirs``, since mutating\n                    # a list while iterating over it can cause trouble.\n                    # (See https://github.com/pypa/pip/pull/462.)\n                    for dir in list(dirs):\n                        # Don't search in anything that looks like a virtualenv\n                        # environment\n                        if (\n                                os.path.lexists(\n                                    os.path.join(root, dir, 'bin', 'python')\n                                ) or\n                                os.path.exists(\n                                    os.path.join(\n                                        root, dir, 'Scripts', 'Python.exe'\n                                    )\n                                )):\n                            dirs.remove(dir)\n                        # Also don't search through tests\n                        elif dir == 'test' or dir == 'tests':\n                            dirs.remove(dir)\n                    filenames.extend([os.path.join(root, dir)\n                                      for dir in dirs])\n                filenames = [f for f in filenames if f.endswith('.egg-info')]\n\n            if not filenames:\n                raise InstallationError(\n                    \"Files/directories not found in %s\" % base\n                )\n            # if we have more than one match, we pick the toplevel one.  This\n            # can easily be the case if there is a dist folder which contains\n            # an extracted tarball for testing purposes.\n            if len(filenames) > 1:\n                filenames.sort(\n                    key=lambda x: x.count(os.path.sep) +\n                    (os.path.altsep and x.count(os.path.altsep) or 0)\n                )\n            self._egg_info_path = os.path.join(base, filenames[0])\n        return self._egg_info_path\n\n    @property\n    def metadata(self):\n        if not hasattr(self, '_metadata'):\n            self._metadata = get_metadata(self.get_dist())\n\n        return self._metadata\n\n    def get_dist(self):\n        # type: () -> Distribution\n        \"\"\"Return a pkg_resources.Distribution for this requirement\"\"\"\n        if self.metadata_directory:\n            base_dir, distinfo = os.path.split(self.metadata_directory)\n            metadata = pkg_resources.PathMetadata(\n                base_dir, self.metadata_directory\n            )\n            dist_name = os.path.splitext(distinfo)[0]\n            typ = pkg_resources.DistInfoDistribution\n        else:\n            egg_info = self.egg_info_path.rstrip(os.path.sep)\n            base_dir = os.path.dirname(egg_info)\n            metadata = pkg_resources.PathMetadata(base_dir, egg_info)\n            dist_name = os.path.splitext(os.path.basename(egg_info))[0]\n            # https://github.com/python/mypy/issues/1174\n            typ = pkg_resources.Distribution  # type: ignore\n\n        return typ(\n            base_dir,\n            project_name=dist_name,\n            metadata=metadata,\n        )\n\n    def assert_source_matches_version(self):\n        # type: () -> None\n        assert self.source_dir\n        version = self.metadata['version']\n        if self.req.specifier and version not in self.req.specifier:\n            logger.warning(\n                'Requested %s, but installing version %s',\n                self,\n                version,\n            )\n        else:\n            logger.debug(\n                'Source in %s has version %s, which satisfies requirement %s',\n                display_path(self.source_dir),\n                version,\n                self,\n            )\n\n    # For both source distributions and editables\n    def ensure_has_source_dir(self, parent_dir):\n        # type: (str) -> str\n        \"\"\"Ensure that a source_dir is set.\n\n        This will create a temporary build dir if the name of the requirement\n        isn't known yet.\n\n        :param parent_dir: The ideal pip parent_dir for the source_dir.\n            Generally src_dir for editables and build_dir for sdists.\n        :return: self.source_dir\n        \"\"\"\n        if self.source_dir is None:\n            self.source_dir = self.build_location(parent_dir)\n        return self.source_dir\n\n    # For editable installations\n    def install_editable(\n        self,\n        install_options,  # type: List[str]\n        global_options=(),  # type: Sequence[str]\n        prefix=None  # type: Optional[str]\n    ):\n        # type: (...) -> None\n        logger.info('Running setup.py develop for %s', self.name)\n\n        if self.isolated:\n            global_options = list(global_options) + [\"--no-user-cfg\"]\n\n        if prefix:\n            prefix_param = ['--prefix={}'.format(prefix)]\n            install_options = list(install_options) + prefix_param\n\n        with indent_log():\n            # FIXME: should we do --install-headers here too?\n            with self.build_env:\n                call_subprocess(\n                    [\n                        sys.executable,\n                        '-c',\n                        SETUPTOOLS_SHIM % self.setup_py\n                    ] +\n                    list(global_options) +\n                    ['develop', '--no-deps'] +\n                    list(install_options),\n\n                    cwd=self.setup_py_dir,\n                    show_stdout=False,\n                )\n\n        self.install_succeeded = True\n\n    def update_editable(self, obtain=True):\n        # type: (bool) -> None\n        if not self.link:\n            logger.debug(\n                \"Cannot update repository at %s; repository location is \"\n                \"unknown\",\n                self.source_dir,\n            )\n            return\n        assert self.editable\n        assert self.source_dir\n        if self.link.scheme == 'file':\n            # Static paths don't get updated\n            return\n        assert '+' in self.link.url, \"bad url: %r\" % self.link.url\n        if not self.update:\n            return\n        vc_type, url = self.link.url.split('+', 1)\n        backend = vcs.get_backend(vc_type)\n        if backend:\n            vcs_backend = backend(self.link.url)\n            if obtain:\n                vcs_backend.obtain(self.source_dir)\n            else:\n                vcs_backend.export(self.source_dir)\n        else:\n            assert 0, (\n                'Unexpected version control type (in %s): %s'\n                % (self.link, vc_type))\n\n    # Top-level Actions\n    def uninstall(self, auto_confirm=False, verbose=False,\n                  use_user_site=False):\n        # type: (bool, bool, bool) -> Optional[UninstallPathSet]\n        \"\"\"\n        Uninstall the distribution currently satisfying this requirement.\n\n        Prompts before removing or modifying files unless\n        ``auto_confirm`` is True.\n\n        Refuses to delete or modify files outside of ``sys.prefix`` -\n        thus uninstallation within a virtual environment can only\n        modify that virtual environment, even if the virtualenv is\n        linked to global site-packages.\n\n        \"\"\"\n        if not self.check_if_exists(use_user_site):\n            logger.warning(\"Skipping %s as it is not installed.\", self.name)\n            return None\n        dist = self.satisfied_by or self.conflicts_with\n\n        uninstalled_pathset = UninstallPathSet.from_dist(dist)\n        uninstalled_pathset.remove(auto_confirm, verbose)\n        return uninstalled_pathset\n\n    def _clean_zip_name(self, name, prefix):  # only used by archive.\n        assert name.startswith(prefix + os.path.sep), (\n            \"name %r doesn't start with prefix %r\" % (name, prefix)\n        )\n        name = name[len(prefix) + 1:]\n        name = name.replace(os.path.sep, '/')\n        return name\n\n    def _get_archive_name(self, path, parentdir, rootdir):\n        # type: (str, str, str) -> str\n        path = os.path.join(parentdir, path)\n        name = self._clean_zip_name(path, rootdir)\n        return self.name + '/' + name\n\n    # TODO: Investigate if this should be kept in InstallRequirement\n    #       Seems to be used only when VCS + downloads\n    def archive(self, build_dir):\n        # type: (str) -> None\n        assert self.source_dir\n        create_archive = True\n        archive_name = '%s-%s.zip' % (self.name, self.metadata[\"version\"])\n        archive_path = os.path.join(build_dir, archive_name)\n        if os.path.exists(archive_path):\n            response = ask_path_exists(\n                'The file %s exists. (i)gnore, (w)ipe, (b)ackup, (a)bort ' %\n                display_path(archive_path), ('i', 'w', 'b', 'a'))\n            if response == 'i':\n                create_archive = False\n            elif response == 'w':\n                logger.warning('Deleting %s', display_path(archive_path))\n                os.remove(archive_path)\n            elif response == 'b':\n                dest_file = backup_dir(archive_path)\n                logger.warning(\n                    'Backing up %s to %s',\n                    display_path(archive_path),\n                    display_path(dest_file),\n                )\n                shutil.move(archive_path, dest_file)\n            elif response == 'a':\n                sys.exit(-1)\n        if create_archive:\n            zip = zipfile.ZipFile(\n                archive_path, 'w', zipfile.ZIP_DEFLATED,\n                allowZip64=True\n            )\n            dir = os.path.normcase(os.path.abspath(self.setup_py_dir))\n            for dirpath, dirnames, filenames in os.walk(dir):\n                if 'pip-egg-info' in dirnames:\n                    dirnames.remove('pip-egg-info')\n                for dirname in dirnames:\n                    dir_arcname = self._get_archive_name(dirname,\n                                                         parentdir=dirpath,\n                                                         rootdir=dir)\n                    zipdir = zipfile.ZipInfo(dir_arcname + '/')\n                    zipdir.external_attr = 0x1ED << 16  # 0o755\n                    zip.writestr(zipdir, '')\n                for filename in filenames:\n                    if filename == PIP_DELETE_MARKER_FILENAME:\n                        continue\n                    file_arcname = self._get_archive_name(filename,\n                                                          parentdir=dirpath,\n                                                          rootdir=dir)\n                    filename = os.path.join(dirpath, filename)\n                    zip.write(filename, file_arcname)\n            zip.close()\n            logger.info('Saved %s', display_path(archive_path))\n\n    def install(\n        self,\n        install_options,  # type: List[str]\n        global_options=None,  # type: Optional[Sequence[str]]\n        root=None,  # type: Optional[str]\n        home=None,  # type: Optional[str]\n        prefix=None,  # type: Optional[str]\n        warn_script_location=True,  # type: bool\n        use_user_site=False,  # type: bool\n        pycompile=True  # type: bool\n    ):\n        # type: (...) -> None\n        global_options = global_options if global_options is not None else []\n        if self.editable:\n            self.install_editable(\n                install_options, global_options, prefix=prefix,\n            )\n            return\n        if self.is_wheel:\n            version = wheel.wheel_version(self.source_dir)\n            wheel.check_compatibility(version, self.name)\n\n            self.move_wheel_files(\n                self.source_dir, root=root, prefix=prefix, home=home,\n                warn_script_location=warn_script_location,\n                use_user_site=use_user_site, pycompile=pycompile,\n            )\n            self.install_succeeded = True\n            return\n\n        # Extend the list of global and install options passed on to\n        # the setup.py call with the ones from the requirements file.\n        # Options specified in requirements file override those\n        # specified on the command line, since the last option given\n        # to setup.py is the one that is used.\n        global_options = list(global_options) + \\\n            self.options.get('global_options', [])\n        install_options = list(install_options) + \\\n            self.options.get('install_options', [])\n\n        if self.isolated:\n            # https://github.com/python/mypy/issues/1174\n            global_options = global_options + [\"--no-user-cfg\"]  # type: ignore\n\n        with TempDirectory(kind=\"record\") as temp_dir:\n            record_filename = os.path.join(temp_dir.path, 'install-record.txt')\n            install_args = self.get_install_args(\n                global_options, record_filename, root, prefix, pycompile,\n            )\n            msg = 'Running setup.py install for %s' % (self.name,)\n            with open_spinner(msg) as spinner:\n                with indent_log():\n                    with self.build_env:\n                        call_subprocess(\n                            install_args + install_options,\n                            cwd=self.setup_py_dir,\n                            show_stdout=False,\n                            spinner=spinner,\n                        )\n\n            if not os.path.exists(record_filename):\n                logger.debug('Record file %s not found', record_filename)\n                return\n            self.install_succeeded = True\n\n            def prepend_root(path):\n                if root is None or not os.path.isabs(path):\n                    return path\n                else:\n                    return change_root(root, path)\n\n            with open(record_filename) as f:\n                for line in f:\n                    directory = os.path.dirname(line)\n                    if directory.endswith('.egg-info'):\n                        egg_info_dir = prepend_root(directory)\n                        break\n                else:\n                    logger.warning(\n                        'Could not find .egg-info directory in install record'\n                        ' for %s',\n                        self,\n                    )\n                    # FIXME: put the record somewhere\n                    # FIXME: should this be an error?\n                    return\n            new_lines = []\n            with open(record_filename) as f:\n                for line in f:\n                    filename = line.strip()\n                    if os.path.isdir(filename):\n                        filename += os.path.sep\n                    new_lines.append(\n                        os.path.relpath(prepend_root(filename), egg_info_dir)\n                    )\n            new_lines.sort()\n            ensure_dir(egg_info_dir)\n            inst_files_path = os.path.join(egg_info_dir, 'installed-files.txt')\n            with open(inst_files_path, 'w') as f:\n                f.write('\\n'.join(new_lines) + '\\n')\n\n    def get_install_args(\n        self,\n        global_options,  # type: Sequence[str]\n        record_filename,  # type: str\n        root,  # type: Optional[str]\n        prefix,  # type: Optional[str]\n        pycompile  # type: bool\n    ):\n        # type: (...) -> List[str]\n        install_args = [sys.executable, \"-u\"]\n        install_args.append('-c')\n        install_args.append(SETUPTOOLS_SHIM % self.setup_py)\n        install_args += list(global_options) + \\\n            ['install', '--record', record_filename]\n        install_args += ['--single-version-externally-managed']\n\n        if root is not None:\n            install_args += ['--root', root]\n        if prefix is not None:\n            install_args += ['--prefix', prefix]\n\n        if pycompile:\n            install_args += [\"--compile\"]\n        else:\n            install_args += [\"--no-compile\"]\n\n        if running_under_virtualenv():\n            py_ver_str = 'python' + sysconfig.get_python_version()\n            install_args += ['--install-headers',\n                             os.path.join(sys.prefix, 'include', 'site',\n                                          py_ver_str, self.name)]\n\n        return install_args\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/req/req_set.py",
    "content": "from __future__ import absolute_import\n\nimport logging\nfrom collections import OrderedDict\n\nfrom pip._internal.exceptions import InstallationError\nfrom pip._internal.utils.logging import indent_log\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\nfrom pip._internal.wheel import Wheel\n\nif MYPY_CHECK_RUNNING:\n    from typing import Optional, List, Tuple, Dict, Iterable  # noqa: F401\n    from pip._internal.req.req_install import InstallRequirement  # noqa: F401\n\n\nlogger = logging.getLogger(__name__)\n\n\nclass RequirementSet(object):\n\n    def __init__(self, require_hashes=False, check_supported_wheels=True):\n        # type: (bool, bool) -> None\n        \"\"\"Create a RequirementSet.\n        \"\"\"\n\n        self.requirements = OrderedDict()  # type: Dict[str, InstallRequirement]  # noqa: E501\n        self.require_hashes = require_hashes\n        self.check_supported_wheels = check_supported_wheels\n\n        # Mapping of alias: real_name\n        self.requirement_aliases = {}  # type: Dict[str, str]\n        self.unnamed_requirements = []  # type: List[InstallRequirement]\n        self.successfully_downloaded = []  # type: List[InstallRequirement]\n        self.reqs_to_cleanup = []  # type: List[InstallRequirement]\n\n    def __str__(self):\n        reqs = [req for req in self.requirements.values()\n                if not req.comes_from]\n        reqs.sort(key=lambda req: req.name.lower())\n        return ' '.join([str(req.req) for req in reqs])\n\n    def __repr__(self):\n        reqs = [req for req in self.requirements.values()]\n        reqs.sort(key=lambda req: req.name.lower())\n        reqs_str = ', '.join([str(req.req) for req in reqs])\n        return ('<%s object; %d requirement(s): %s>'\n                % (self.__class__.__name__, len(reqs), reqs_str))\n\n    def add_requirement(\n        self,\n        install_req,  # type: InstallRequirement\n        parent_req_name=None,  # type: Optional[str]\n        extras_requested=None  # type: Optional[Iterable[str]]\n    ):\n        # type: (...) -> Tuple[List[InstallRequirement], Optional[InstallRequirement]]  # noqa: E501\n        \"\"\"Add install_req as a requirement to install.\n\n        :param parent_req_name: The name of the requirement that needed this\n            added. The name is used because when multiple unnamed requirements\n            resolve to the same name, we could otherwise end up with dependency\n            links that point outside the Requirements set. parent_req must\n            already be added. Note that None implies that this is a user\n            supplied requirement, vs an inferred one.\n        :param extras_requested: an iterable of extras used to evaluate the\n            environment markers.\n        :return: Additional requirements to scan. That is either [] if\n            the requirement is not applicable, or [install_req] if the\n            requirement is applicable and has just been added.\n        \"\"\"\n        name = install_req.name\n\n        # If the markers do not match, ignore this requirement.\n        if not install_req.match_markers(extras_requested):\n            logger.info(\n                \"Ignoring %s: markers '%s' don't match your environment\",\n                name, install_req.markers,\n            )\n            return [], None\n\n        # If the wheel is not supported, raise an error.\n        # Should check this after filtering out based on environment markers to\n        # allow specifying different wheels based on the environment/OS, in a\n        # single requirements file.\n        if install_req.link and install_req.link.is_wheel:\n            wheel = Wheel(install_req.link.filename)\n            if self.check_supported_wheels and not wheel.supported():\n                raise InstallationError(\n                    \"%s is not a supported wheel on this platform.\" %\n                    wheel.filename\n                )\n\n        # This next bit is really a sanity check.\n        assert install_req.is_direct == (parent_req_name is None), (\n            \"a direct req shouldn't have a parent and also, \"\n            \"a non direct req should have a parent\"\n        )\n\n        # Unnamed requirements are scanned again and the requirement won't be\n        # added as a dependency until after scanning.\n        if not name:\n            # url or path requirement w/o an egg fragment\n            self.unnamed_requirements.append(install_req)\n            return [install_req], None\n\n        try:\n            existing_req = self.get_requirement(name)\n        except KeyError:\n            existing_req = None\n\n        has_conflicting_requirement = (\n            parent_req_name is None and\n            existing_req and\n            not existing_req.constraint and\n            existing_req.extras == install_req.extras and\n            existing_req.req.specifier != install_req.req.specifier\n        )\n        if has_conflicting_requirement:\n            raise InstallationError(\n                \"Double requirement given: %s (already in %s, name=%r)\"\n                % (install_req, existing_req, name)\n            )\n\n        # When no existing requirement exists, add the requirement as a\n        # dependency and it will be scanned again after.\n        if not existing_req:\n            self.requirements[name] = install_req\n            # FIXME: what about other normalizations?  E.g., _ vs. -?\n            if name.lower() != name:\n                self.requirement_aliases[name.lower()] = name\n            # We'd want to rescan this requirements later\n            return [install_req], install_req\n\n        # Assume there's no need to scan, and that we've already\n        # encountered this for scanning.\n        if install_req.constraint or not existing_req.constraint:\n            return [], existing_req\n\n        does_not_satisfy_constraint = (\n            install_req.link and\n            not (\n                existing_req.link and\n                install_req.link.path == existing_req.link.path\n            )\n        )\n        if does_not_satisfy_constraint:\n            self.reqs_to_cleanup.append(install_req)\n            raise InstallationError(\n                \"Could not satisfy constraints for '%s': \"\n                \"installation from path or url cannot be \"\n                \"constrained to a version\" % name,\n            )\n        # If we're now installing a constraint, mark the existing\n        # object for real installation.\n        existing_req.constraint = False\n        existing_req.extras = tuple(sorted(\n            set(existing_req.extras) | set(install_req.extras)\n        ))\n        logger.debug(\n            \"Setting %s extras to: %s\",\n            existing_req, existing_req.extras,\n        )\n        # Return the existing requirement for addition to the parent and\n        # scanning again.\n        return [existing_req], existing_req\n\n    def has_requirement(self, project_name):\n        # type: (str) -> bool\n        name = project_name.lower()\n        if (name in self.requirements and\n           not self.requirements[name].constraint or\n           name in self.requirement_aliases and\n           not self.requirements[self.requirement_aliases[name]].constraint):\n            return True\n        return False\n\n    @property\n    def has_requirements(self):\n        # type: () -> List[InstallRequirement]\n        return list(req for req in self.requirements.values() if not\n                    req.constraint) or self.unnamed_requirements\n\n    def get_requirement(self, project_name):\n        # type: (str) -> InstallRequirement\n        for name in project_name, project_name.lower():\n            if name in self.requirements:\n                return self.requirements[name]\n            if name in self.requirement_aliases:\n                return self.requirements[self.requirement_aliases[name]]\n        raise KeyError(\"No project with the name %r\" % project_name)\n\n    def cleanup_files(self):\n        # type: () -> None\n        \"\"\"Clean up files, remove builds.\"\"\"\n        logger.debug('Cleaning up...')\n        with indent_log():\n            for req in self.reqs_to_cleanup:\n                req.remove_temporary_source()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/req/req_tracker.py",
    "content": "from __future__ import absolute_import\n\nimport contextlib\nimport errno\nimport hashlib\nimport logging\nimport os\n\nfrom pip._internal.utils.temp_dir import TempDirectory\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Set, Iterator  # noqa: F401\n    from pip._internal.req.req_install import InstallRequirement  # noqa: F401\n    from pip._internal.models.link import Link  # noqa: F401\n\nlogger = logging.getLogger(__name__)\n\n\nclass RequirementTracker(object):\n\n    def __init__(self):\n        # type: () -> None\n        self._root = os.environ.get('PIP_REQ_TRACKER')\n        if self._root is None:\n            self._temp_dir = TempDirectory(delete=False, kind='req-tracker')\n            self._temp_dir.create()\n            self._root = os.environ['PIP_REQ_TRACKER'] = self._temp_dir.path\n            logger.debug('Created requirements tracker %r', self._root)\n        else:\n            self._temp_dir = None\n            logger.debug('Re-using requirements tracker %r', self._root)\n        self._entries = set()  # type: Set[InstallRequirement]\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        self.cleanup()\n\n    def _entry_path(self, link):\n        # type: (Link) -> str\n        hashed = hashlib.sha224(link.url_without_fragment.encode()).hexdigest()\n        return os.path.join(self._root, hashed)\n\n    def add(self, req):\n        # type: (InstallRequirement) -> None\n        link = req.link\n        info = str(req)\n        entry_path = self._entry_path(link)\n        try:\n            with open(entry_path) as fp:\n                # Error, these's already a build in progress.\n                raise LookupError('%s is already being built: %s'\n                                  % (link, fp.read()))\n        except IOError as e:\n            if e.errno != errno.ENOENT:\n                raise\n            assert req not in self._entries\n            with open(entry_path, 'w') as fp:\n                fp.write(info)\n            self._entries.add(req)\n            logger.debug('Added %s to build tracker %r', req, self._root)\n\n    def remove(self, req):\n        # type: (InstallRequirement) -> None\n        link = req.link\n        self._entries.remove(req)\n        os.unlink(self._entry_path(link))\n        logger.debug('Removed %s from build tracker %r', req, self._root)\n\n    def cleanup(self):\n        # type: () -> None\n        for req in set(self._entries):\n            self.remove(req)\n        remove = self._temp_dir is not None\n        if remove:\n            self._temp_dir.cleanup()\n        logger.debug('%s build tracker %r',\n                     'Removed' if remove else 'Cleaned',\n                     self._root)\n\n    @contextlib.contextmanager\n    def track(self, req):\n        # type: (InstallRequirement) -> Iterator[None]\n        self.add(req)\n        yield\n        self.remove(req)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/req/req_uninstall.py",
    "content": "from __future__ import absolute_import\n\nimport csv\nimport functools\nimport logging\nimport os\nimport sys\nimport sysconfig\n\nfrom pip._vendor import pkg_resources\n\nfrom pip._internal.exceptions import UninstallationError\nfrom pip._internal.locations import bin_py, bin_user\nfrom pip._internal.utils.compat import WINDOWS, cache_from_source, uses_pycache\nfrom pip._internal.utils.logging import indent_log\nfrom pip._internal.utils.misc import (\n    FakeFile, ask, dist_in_usersite, dist_is_local, egg_link_path, is_local,\n    normalize_path, renames, rmtree,\n)\nfrom pip._internal.utils.temp_dir import AdjacentTempDirectory, TempDirectory\n\nlogger = logging.getLogger(__name__)\n\n\ndef _script_names(dist, script_name, is_gui):\n    \"\"\"Create the fully qualified name of the files created by\n    {console,gui}_scripts for the given ``dist``.\n    Returns the list of file names\n    \"\"\"\n    if dist_in_usersite(dist):\n        bin_dir = bin_user\n    else:\n        bin_dir = bin_py\n    exe_name = os.path.join(bin_dir, script_name)\n    paths_to_remove = [exe_name]\n    if WINDOWS:\n        paths_to_remove.append(exe_name + '.exe')\n        paths_to_remove.append(exe_name + '.exe.manifest')\n        if is_gui:\n            paths_to_remove.append(exe_name + '-script.pyw')\n        else:\n            paths_to_remove.append(exe_name + '-script.py')\n    return paths_to_remove\n\n\ndef _unique(fn):\n    @functools.wraps(fn)\n    def unique(*args, **kw):\n        seen = set()\n        for item in fn(*args, **kw):\n            if item not in seen:\n                seen.add(item)\n                yield item\n    return unique\n\n\n@_unique\ndef uninstallation_paths(dist):\n    \"\"\"\n    Yield all the uninstallation paths for dist based on RECORD-without-.py[co]\n\n    Yield paths to all the files in RECORD. For each .py file in RECORD, add\n    the .pyc and .pyo in the same directory.\n\n    UninstallPathSet.add() takes care of the __pycache__ .py[co].\n    \"\"\"\n    r = csv.reader(FakeFile(dist.get_metadata_lines('RECORD')))\n    for row in r:\n        path = os.path.join(dist.location, row[0])\n        yield path\n        if path.endswith('.py'):\n            dn, fn = os.path.split(path)\n            base = fn[:-3]\n            path = os.path.join(dn, base + '.pyc')\n            yield path\n            path = os.path.join(dn, base + '.pyo')\n            yield path\n\n\ndef compact(paths):\n    \"\"\"Compact a path set to contain the minimal number of paths\n    necessary to contain all paths in the set. If /a/path/ and\n    /a/path/to/a/file.txt are both in the set, leave only the\n    shorter path.\"\"\"\n\n    sep = os.path.sep\n    short_paths = set()\n    for path in sorted(paths, key=len):\n        should_skip = any(\n            path.startswith(shortpath.rstrip(\"*\")) and\n            path[len(shortpath.rstrip(\"*\").rstrip(sep))] == sep\n            for shortpath in short_paths\n        )\n        if not should_skip:\n            short_paths.add(path)\n    return short_paths\n\n\ndef compress_for_rename(paths):\n    \"\"\"Returns a set containing the paths that need to be renamed.\n\n    This set may include directories when the original sequence of paths\n    included every file on disk.\n    \"\"\"\n    case_map = dict((os.path.normcase(p), p) for p in paths)\n    remaining = set(case_map)\n    unchecked = sorted(set(os.path.split(p)[0]\n                           for p in case_map.values()), key=len)\n    wildcards = set()\n\n    def norm_join(*a):\n        return os.path.normcase(os.path.join(*a))\n\n    for root in unchecked:\n        if any(os.path.normcase(root).startswith(w)\n               for w in wildcards):\n            # This directory has already been handled.\n            continue\n\n        all_files = set()\n        all_subdirs = set()\n        for dirname, subdirs, files in os.walk(root):\n            all_subdirs.update(norm_join(root, dirname, d)\n                               for d in subdirs)\n            all_files.update(norm_join(root, dirname, f)\n                             for f in files)\n        # If all the files we found are in our remaining set of files to\n        # remove, then remove them from the latter set and add a wildcard\n        # for the directory.\n        if not (all_files - remaining):\n            remaining.difference_update(all_files)\n            wildcards.add(root + os.sep)\n\n    return set(map(case_map.__getitem__, remaining)) | wildcards\n\n\ndef compress_for_output_listing(paths):\n    \"\"\"Returns a tuple of 2 sets of which paths to display to user\n\n    The first set contains paths that would be deleted. Files of a package\n    are not added and the top-level directory of the package has a '*' added\n    at the end - to signify that all it's contents are removed.\n\n    The second set contains files that would have been skipped in the above\n    folders.\n    \"\"\"\n\n    will_remove = list(paths)\n    will_skip = set()\n\n    # Determine folders and files\n    folders = set()\n    files = set()\n    for path in will_remove:\n        if path.endswith(\".pyc\"):\n            continue\n        if path.endswith(\"__init__.py\") or \".dist-info\" in path:\n            folders.add(os.path.dirname(path))\n        files.add(path)\n\n    _normcased_files = set(map(os.path.normcase, files))\n\n    folders = compact(folders)\n\n    # This walks the tree using os.walk to not miss extra folders\n    # that might get added.\n    for folder in folders:\n        for dirpath, _, dirfiles in os.walk(folder):\n            for fname in dirfiles:\n                if fname.endswith(\".pyc\"):\n                    continue\n\n                file_ = os.path.join(dirpath, fname)\n                if (os.path.isfile(file_) and\n                        os.path.normcase(file_) not in _normcased_files):\n                    # We are skipping this file. Add it to the set.\n                    will_skip.add(file_)\n\n    will_remove = files | {\n        os.path.join(folder, \"*\") for folder in folders\n    }\n\n    return will_remove, will_skip\n\n\nclass StashedUninstallPathSet(object):\n    \"\"\"A set of file rename operations to stash files while\n    tentatively uninstalling them.\"\"\"\n    def __init__(self):\n        # Mapping from source file root to [Adjacent]TempDirectory\n        # for files under that directory.\n        self._save_dirs = {}\n        # (old path, new path) tuples for each move that may need\n        # to be undone.\n        self._moves = []\n\n    def _get_directory_stash(self, path):\n        \"\"\"Stashes a directory.\n\n        Directories are stashed adjacent to their original location if\n        possible, or else moved/copied into the user's temp dir.\"\"\"\n\n        try:\n            save_dir = AdjacentTempDirectory(path)\n            save_dir.create()\n        except OSError:\n            save_dir = TempDirectory(kind=\"uninstall\")\n            save_dir.create()\n        self._save_dirs[os.path.normcase(path)] = save_dir\n\n        return save_dir.path\n\n    def _get_file_stash(self, path):\n        \"\"\"Stashes a file.\n\n        If no root has been provided, one will be created for the directory\n        in the user's temp directory.\"\"\"\n        path = os.path.normcase(path)\n        head, old_head = os.path.dirname(path), None\n        save_dir = None\n\n        while head != old_head:\n            try:\n                save_dir = self._save_dirs[head]\n                break\n            except KeyError:\n                pass\n            head, old_head = os.path.dirname(head), head\n        else:\n            # Did not find any suitable root\n            head = os.path.dirname(path)\n            save_dir = TempDirectory(kind='uninstall')\n            save_dir.create()\n            self._save_dirs[head] = save_dir\n\n        relpath = os.path.relpath(path, head)\n        if relpath and relpath != os.path.curdir:\n            return os.path.join(save_dir.path, relpath)\n        return save_dir.path\n\n    def stash(self, path):\n        \"\"\"Stashes the directory or file and returns its new location.\n        \"\"\"\n        if os.path.isdir(path):\n            new_path = self._get_directory_stash(path)\n        else:\n            new_path = self._get_file_stash(path)\n\n        self._moves.append((path, new_path))\n        if os.path.isdir(path) and os.path.isdir(new_path):\n            # If we're moving a directory, we need to\n            # remove the destination first or else it will be\n            # moved to inside the existing directory.\n            # We just created new_path ourselves, so it will\n            # be removable.\n            os.rmdir(new_path)\n        renames(path, new_path)\n        return new_path\n\n    def commit(self):\n        \"\"\"Commits the uninstall by removing stashed files.\"\"\"\n        for _, save_dir in self._save_dirs.items():\n            save_dir.cleanup()\n        self._moves = []\n        self._save_dirs = {}\n\n    def rollback(self):\n        \"\"\"Undoes the uninstall by moving stashed files back.\"\"\"\n        for p in self._moves:\n            logging.info(\"Moving to %s\\n from %s\", *p)\n\n        for new_path, path in self._moves:\n            try:\n                logger.debug('Replacing %s from %s', new_path, path)\n                if os.path.isfile(new_path):\n                    os.unlink(new_path)\n                elif os.path.isdir(new_path):\n                    rmtree(new_path)\n                renames(path, new_path)\n            except OSError as ex:\n                logger.error(\"Failed to restore %s\", new_path)\n                logger.debug(\"Exception: %s\", ex)\n\n        self.commit()\n\n    @property\n    def can_rollback(self):\n        return bool(self._moves)\n\n\nclass UninstallPathSet(object):\n    \"\"\"A set of file paths to be removed in the uninstallation of a\n    requirement.\"\"\"\n    def __init__(self, dist):\n        self.paths = set()\n        self._refuse = set()\n        self.pth = {}\n        self.dist = dist\n        self._moved_paths = StashedUninstallPathSet()\n\n    def _permitted(self, path):\n        \"\"\"\n        Return True if the given path is one we are permitted to\n        remove/modify, False otherwise.\n\n        \"\"\"\n        return is_local(path)\n\n    def add(self, path):\n        head, tail = os.path.split(path)\n\n        # we normalize the head to resolve parent directory symlinks, but not\n        # the tail, since we only want to uninstall symlinks, not their targets\n        path = os.path.join(normalize_path(head), os.path.normcase(tail))\n\n        if not os.path.exists(path):\n            return\n        if self._permitted(path):\n            self.paths.add(path)\n        else:\n            self._refuse.add(path)\n\n        # __pycache__ files can show up after 'installed-files.txt' is created,\n        # due to imports\n        if os.path.splitext(path)[1] == '.py' and uses_pycache:\n            self.add(cache_from_source(path))\n\n    def add_pth(self, pth_file, entry):\n        pth_file = normalize_path(pth_file)\n        if self._permitted(pth_file):\n            if pth_file not in self.pth:\n                self.pth[pth_file] = UninstallPthEntries(pth_file)\n            self.pth[pth_file].add(entry)\n        else:\n            self._refuse.add(pth_file)\n\n    def remove(self, auto_confirm=False, verbose=False):\n        \"\"\"Remove paths in ``self.paths`` with confirmation (unless\n        ``auto_confirm`` is True).\"\"\"\n\n        if not self.paths:\n            logger.info(\n                \"Can't uninstall '%s'. No files were found to uninstall.\",\n                self.dist.project_name,\n            )\n            return\n\n        dist_name_version = (\n            self.dist.project_name + \"-\" + self.dist.version\n        )\n        logger.info('Uninstalling %s:', dist_name_version)\n\n        with indent_log():\n            if auto_confirm or self._allowed_to_proceed(verbose):\n                moved = self._moved_paths\n\n                for_rename = compress_for_rename(self.paths)\n\n                for path in sorted(compact(for_rename)):\n                    moved.stash(path)\n                    logger.debug('Removing file or directory %s', path)\n\n                for pth in self.pth.values():\n                    pth.remove()\n\n                logger.info('Successfully uninstalled %s', dist_name_version)\n\n    def _allowed_to_proceed(self, verbose):\n        \"\"\"Display which files would be deleted and prompt for confirmation\n        \"\"\"\n\n        def _display(msg, paths):\n            if not paths:\n                return\n\n            logger.info(msg)\n            with indent_log():\n                for path in sorted(compact(paths)):\n                    logger.info(path)\n\n        if not verbose:\n            will_remove, will_skip = compress_for_output_listing(self.paths)\n        else:\n            # In verbose mode, display all the files that are going to be\n            # deleted.\n            will_remove = list(self.paths)\n            will_skip = set()\n\n        _display('Would remove:', will_remove)\n        _display('Would not remove (might be manually added):', will_skip)\n        _display('Would not remove (outside of prefix):', self._refuse)\n        if verbose:\n            _display('Will actually move:', compress_for_rename(self.paths))\n\n        return ask('Proceed (y/n)? ', ('y', 'n')) == 'y'\n\n    def rollback(self):\n        \"\"\"Rollback the changes previously made by remove().\"\"\"\n        if not self._moved_paths.can_rollback:\n            logger.error(\n                \"Can't roll back %s; was not uninstalled\",\n                self.dist.project_name,\n            )\n            return False\n        logger.info('Rolling back uninstall of %s', self.dist.project_name)\n        self._moved_paths.rollback()\n        for pth in self.pth.values():\n            pth.rollback()\n\n    def commit(self):\n        \"\"\"Remove temporary save dir: rollback will no longer be possible.\"\"\"\n        self._moved_paths.commit()\n\n    @classmethod\n    def from_dist(cls, dist):\n        dist_path = normalize_path(dist.location)\n        if not dist_is_local(dist):\n            logger.info(\n                \"Not uninstalling %s at %s, outside environment %s\",\n                dist.key,\n                dist_path,\n                sys.prefix,\n            )\n            return cls(dist)\n\n        if dist_path in {p for p in {sysconfig.get_path(\"stdlib\"),\n                                     sysconfig.get_path(\"platstdlib\")}\n                         if p}:\n            logger.info(\n                \"Not uninstalling %s at %s, as it is in the standard library.\",\n                dist.key,\n                dist_path,\n            )\n            return cls(dist)\n\n        paths_to_remove = cls(dist)\n        develop_egg_link = egg_link_path(dist)\n        develop_egg_link_egg_info = '{}.egg-info'.format(\n            pkg_resources.to_filename(dist.project_name))\n        egg_info_exists = dist.egg_info and os.path.exists(dist.egg_info)\n        # Special case for distutils installed package\n        distutils_egg_info = getattr(dist._provider, 'path', None)\n\n        # Uninstall cases order do matter as in the case of 2 installs of the\n        # same package, pip needs to uninstall the currently detected version\n        if (egg_info_exists and dist.egg_info.endswith('.egg-info') and\n                not dist.egg_info.endswith(develop_egg_link_egg_info)):\n            # if dist.egg_info.endswith(develop_egg_link_egg_info), we\n            # are in fact in the develop_egg_link case\n            paths_to_remove.add(dist.egg_info)\n            if dist.has_metadata('installed-files.txt'):\n                for installed_file in dist.get_metadata(\n                        'installed-files.txt').splitlines():\n                    path = os.path.normpath(\n                        os.path.join(dist.egg_info, installed_file)\n                    )\n                    paths_to_remove.add(path)\n            # FIXME: need a test for this elif block\n            # occurs with --single-version-externally-managed/--record outside\n            # of pip\n            elif dist.has_metadata('top_level.txt'):\n                if dist.has_metadata('namespace_packages.txt'):\n                    namespaces = dist.get_metadata('namespace_packages.txt')\n                else:\n                    namespaces = []\n                for top_level_pkg in [\n                        p for p\n                        in dist.get_metadata('top_level.txt').splitlines()\n                        if p and p not in namespaces]:\n                    path = os.path.join(dist.location, top_level_pkg)\n                    paths_to_remove.add(path)\n                    paths_to_remove.add(path + '.py')\n                    paths_to_remove.add(path + '.pyc')\n                    paths_to_remove.add(path + '.pyo')\n\n        elif distutils_egg_info:\n            raise UninstallationError(\n                \"Cannot uninstall {!r}. It is a distutils installed project \"\n                \"and thus we cannot accurately determine which files belong \"\n                \"to it which would lead to only a partial uninstall.\".format(\n                    dist.project_name,\n                )\n            )\n\n        elif dist.location.endswith('.egg'):\n            # package installed by easy_install\n            # We cannot match on dist.egg_name because it can slightly vary\n            # i.e. setuptools-0.6c11-py2.6.egg vs setuptools-0.6rc11-py2.6.egg\n            paths_to_remove.add(dist.location)\n            easy_install_egg = os.path.split(dist.location)[1]\n            easy_install_pth = os.path.join(os.path.dirname(dist.location),\n                                            'easy-install.pth')\n            paths_to_remove.add_pth(easy_install_pth, './' + easy_install_egg)\n\n        elif egg_info_exists and dist.egg_info.endswith('.dist-info'):\n            for path in uninstallation_paths(dist):\n                paths_to_remove.add(path)\n\n        elif develop_egg_link:\n            # develop egg\n            with open(develop_egg_link, 'r') as fh:\n                link_pointer = os.path.normcase(fh.readline().strip())\n            assert (link_pointer == dist.location), (\n                'Egg-link %s does not match installed location of %s '\n                '(at %s)' % (link_pointer, dist.project_name, dist.location)\n            )\n            paths_to_remove.add(develop_egg_link)\n            easy_install_pth = os.path.join(os.path.dirname(develop_egg_link),\n                                            'easy-install.pth')\n            paths_to_remove.add_pth(easy_install_pth, dist.location)\n\n        else:\n            logger.debug(\n                'Not sure how to uninstall: %s - Check: %s',\n                dist, dist.location,\n            )\n\n        # find distutils scripts= scripts\n        if dist.has_metadata('scripts') and dist.metadata_isdir('scripts'):\n            for script in dist.metadata_listdir('scripts'):\n                if dist_in_usersite(dist):\n                    bin_dir = bin_user\n                else:\n                    bin_dir = bin_py\n                paths_to_remove.add(os.path.join(bin_dir, script))\n                if WINDOWS:\n                    paths_to_remove.add(os.path.join(bin_dir, script) + '.bat')\n\n        # find console_scripts\n        _scripts_to_remove = []\n        console_scripts = dist.get_entry_map(group='console_scripts')\n        for name in console_scripts.keys():\n            _scripts_to_remove.extend(_script_names(dist, name, False))\n        # find gui_scripts\n        gui_scripts = dist.get_entry_map(group='gui_scripts')\n        for name in gui_scripts.keys():\n            _scripts_to_remove.extend(_script_names(dist, name, True))\n\n        for s in _scripts_to_remove:\n            paths_to_remove.add(s)\n\n        return paths_to_remove\n\n\nclass UninstallPthEntries(object):\n    def __init__(self, pth_file):\n        if not os.path.isfile(pth_file):\n            raise UninstallationError(\n                \"Cannot remove entries from nonexistent file %s\" % pth_file\n            )\n        self.file = pth_file\n        self.entries = set()\n        self._saved_lines = None\n\n    def add(self, entry):\n        entry = os.path.normcase(entry)\n        # On Windows, os.path.normcase converts the entry to use\n        # backslashes.  This is correct for entries that describe absolute\n        # paths outside of site-packages, but all the others use forward\n        # slashes.\n        if WINDOWS and not os.path.splitdrive(entry)[0]:\n            entry = entry.replace('\\\\', '/')\n        self.entries.add(entry)\n\n    def remove(self):\n        logger.debug('Removing pth entries from %s:', self.file)\n        with open(self.file, 'rb') as fh:\n            # windows uses '\\r\\n' with py3k, but uses '\\n' with py2.x\n            lines = fh.readlines()\n            self._saved_lines = lines\n        if any(b'\\r\\n' in line for line in lines):\n            endline = '\\r\\n'\n        else:\n            endline = '\\n'\n        # handle missing trailing newline\n        if lines and not lines[-1].endswith(endline.encode(\"utf-8\")):\n            lines[-1] = lines[-1] + endline.encode(\"utf-8\")\n        for entry in self.entries:\n            try:\n                logger.debug('Removing entry: %s', entry)\n                lines.remove((entry + endline).encode(\"utf-8\"))\n            except ValueError:\n                pass\n        with open(self.file, 'wb') as fh:\n            fh.writelines(lines)\n\n    def rollback(self):\n        if self._saved_lines is None:\n            logger.error(\n                'Cannot roll back changes to %s, none were made', self.file\n            )\n            return False\n        logger.debug('Rolling %s back to previous state', self.file)\n        with open(self.file, 'wb') as fh:\n            fh.writelines(self._saved_lines)\n        return True\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/resolve.py",
    "content": "\"\"\"Dependency Resolution\n\nThe dependency resolution in pip is performed as follows:\n\nfor top-level requirements:\n    a. only one spec allowed per project, regardless of conflicts or not.\n       otherwise a \"double requirement\" exception is raised\n    b. they override sub-dependency requirements.\nfor sub-dependencies\n    a. \"first found, wins\" (where the order is breadth first)\n\"\"\"\n\nimport logging\nfrom collections import defaultdict\nfrom itertools import chain\n\nfrom pip._internal.exceptions import (\n    BestVersionAlreadyInstalled, DistributionNotFound, HashError, HashErrors,\n    UnsupportedPythonVersion,\n)\nfrom pip._internal.req.constructors import install_req_from_req_string\nfrom pip._internal.utils.logging import indent_log\nfrom pip._internal.utils.misc import dist_in_usersite, ensure_dir\nfrom pip._internal.utils.packaging import check_dist_requires_python\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Optional, DefaultDict, List, Set  # noqa: F401\n    from pip._internal.download import PipSession  # noqa: F401\n    from pip._internal.req.req_install import InstallRequirement  # noqa: F401\n    from pip._internal.index import PackageFinder  # noqa: F401\n    from pip._internal.req.req_set import RequirementSet  # noqa: F401\n    from pip._internal.operations.prepare import (  # noqa: F401\n        DistAbstraction, RequirementPreparer\n    )\n    from pip._internal.cache import WheelCache  # noqa: F401\n\nlogger = logging.getLogger(__name__)\n\n\nclass Resolver(object):\n    \"\"\"Resolves which packages need to be installed/uninstalled to perform \\\n    the requested operation without breaking the requirements of any package.\n    \"\"\"\n\n    _allowed_strategies = {\"eager\", \"only-if-needed\", \"to-satisfy-only\"}\n\n    def __init__(\n        self,\n        preparer,  # type: RequirementPreparer\n        session,  # type: PipSession\n        finder,  # type: PackageFinder\n        wheel_cache,  # type: Optional[WheelCache]\n        use_user_site,  # type: bool\n        ignore_dependencies,  # type: bool\n        ignore_installed,  # type: bool\n        ignore_requires_python,  # type: bool\n        force_reinstall,  # type: bool\n        isolated,  # type: bool\n        upgrade_strategy,  # type: str\n        use_pep517=None  # type: Optional[bool]\n    ):\n        # type: (...) -> None\n        super(Resolver, self).__init__()\n        assert upgrade_strategy in self._allowed_strategies\n\n        self.preparer = preparer\n        self.finder = finder\n        self.session = session\n\n        # NOTE: This would eventually be replaced with a cache that can give\n        #       information about both sdist and wheels transparently.\n        self.wheel_cache = wheel_cache\n\n        # This is set in resolve\n        self.require_hashes = None  # type: Optional[bool]\n\n        self.upgrade_strategy = upgrade_strategy\n        self.force_reinstall = force_reinstall\n        self.isolated = isolated\n        self.ignore_dependencies = ignore_dependencies\n        self.ignore_installed = ignore_installed\n        self.ignore_requires_python = ignore_requires_python\n        self.use_user_site = use_user_site\n        self.use_pep517 = use_pep517\n\n        self._discovered_dependencies = \\\n            defaultdict(list)  # type: DefaultDict[str, List]\n\n    def resolve(self, requirement_set):\n        # type: (RequirementSet) -> None\n        \"\"\"Resolve what operations need to be done\n\n        As a side-effect of this method, the packages (and their dependencies)\n        are downloaded, unpacked and prepared for installation. This\n        preparation is done by ``pip.operations.prepare``.\n\n        Once PyPI has static dependency metadata available, it would be\n        possible to move the preparation to become a step separated from\n        dependency resolution.\n        \"\"\"\n        # make the wheelhouse\n        if self.preparer.wheel_download_dir:\n            ensure_dir(self.preparer.wheel_download_dir)\n\n        # If any top-level requirement has a hash specified, enter\n        # hash-checking mode, which requires hashes from all.\n        root_reqs = (\n            requirement_set.unnamed_requirements +\n            list(requirement_set.requirements.values())\n        )\n        self.require_hashes = (\n            requirement_set.require_hashes or\n            any(req.has_hash_options for req in root_reqs)\n        )\n\n        # Display where finder is looking for packages\n        locations = self.finder.get_formatted_locations()\n        if locations:\n            logger.info(locations)\n\n        # Actually prepare the files, and collect any exceptions. Most hash\n        # exceptions cannot be checked ahead of time, because\n        # req.populate_link() needs to be called before we can make decisions\n        # based on link type.\n        discovered_reqs = []  # type: List[InstallRequirement]\n        hash_errors = HashErrors()\n        for req in chain(root_reqs, discovered_reqs):\n            try:\n                discovered_reqs.extend(\n                    self._resolve_one(requirement_set, req)\n                )\n            except HashError as exc:\n                exc.req = req\n                hash_errors.append(exc)\n\n        if hash_errors:\n            raise hash_errors\n\n    def _is_upgrade_allowed(self, req):\n        # type: (InstallRequirement) -> bool\n        if self.upgrade_strategy == \"to-satisfy-only\":\n            return False\n        elif self.upgrade_strategy == \"eager\":\n            return True\n        else:\n            assert self.upgrade_strategy == \"only-if-needed\"\n            return req.is_direct\n\n    def _set_req_to_reinstall(self, req):\n        # type: (InstallRequirement) -> None\n        \"\"\"\n        Set a requirement to be installed.\n        \"\"\"\n        # Don't uninstall the conflict if doing a user install and the\n        # conflict is not a user install.\n        if not self.use_user_site or dist_in_usersite(req.satisfied_by):\n            req.conflicts_with = req.satisfied_by\n        req.satisfied_by = None\n\n    # XXX: Stop passing requirement_set for options\n    def _check_skip_installed(self, req_to_install):\n        # type: (InstallRequirement) -> Optional[str]\n        \"\"\"Check if req_to_install should be skipped.\n\n        This will check if the req is installed, and whether we should upgrade\n        or reinstall it, taking into account all the relevant user options.\n\n        After calling this req_to_install will only have satisfied_by set to\n        None if the req_to_install is to be upgraded/reinstalled etc. Any\n        other value will be a dist recording the current thing installed that\n        satisfies the requirement.\n\n        Note that for vcs urls and the like we can't assess skipping in this\n        routine - we simply identify that we need to pull the thing down,\n        then later on it is pulled down and introspected to assess upgrade/\n        reinstalls etc.\n\n        :return: A text reason for why it was skipped, or None.\n        \"\"\"\n        if self.ignore_installed:\n            return None\n\n        req_to_install.check_if_exists(self.use_user_site)\n        if not req_to_install.satisfied_by:\n            return None\n\n        if self.force_reinstall:\n            self._set_req_to_reinstall(req_to_install)\n            return None\n\n        if not self._is_upgrade_allowed(req_to_install):\n            if self.upgrade_strategy == \"only-if-needed\":\n                return 'already satisfied, skipping upgrade'\n            return 'already satisfied'\n\n        # Check for the possibility of an upgrade.  For link-based\n        # requirements we have to pull the tree down and inspect to assess\n        # the version #, so it's handled way down.\n        if not req_to_install.link:\n            try:\n                self.finder.find_requirement(req_to_install, upgrade=True)\n            except BestVersionAlreadyInstalled:\n                # Then the best version is installed.\n                return 'already up-to-date'\n            except DistributionNotFound:\n                # No distribution found, so we squash the error.  It will\n                # be raised later when we re-try later to do the install.\n                # Why don't we just raise here?\n                pass\n\n        self._set_req_to_reinstall(req_to_install)\n        return None\n\n    def _get_abstract_dist_for(self, req):\n        # type: (InstallRequirement) -> DistAbstraction\n        \"\"\"Takes a InstallRequirement and returns a single AbstractDist \\\n        representing a prepared variant of the same.\n        \"\"\"\n        assert self.require_hashes is not None, (\n            \"require_hashes should have been set in Resolver.resolve()\"\n        )\n\n        if req.editable:\n            return self.preparer.prepare_editable_requirement(\n                req, self.require_hashes, self.use_user_site, self.finder,\n            )\n\n        # satisfied_by is only evaluated by calling _check_skip_installed,\n        # so it must be None here.\n        assert req.satisfied_by is None\n        skip_reason = self._check_skip_installed(req)\n\n        if req.satisfied_by:\n            return self.preparer.prepare_installed_requirement(\n                req, self.require_hashes, skip_reason\n            )\n\n        upgrade_allowed = self._is_upgrade_allowed(req)\n        abstract_dist = self.preparer.prepare_linked_requirement(\n            req, self.session, self.finder, upgrade_allowed,\n            self.require_hashes\n        )\n\n        # NOTE\n        # The following portion is for determining if a certain package is\n        # going to be re-installed/upgraded or not and reporting to the user.\n        # This should probably get cleaned up in a future refactor.\n\n        # req.req is only avail after unpack for URL\n        # pkgs repeat check_if_exists to uninstall-on-upgrade\n        # (#14)\n        if not self.ignore_installed:\n            req.check_if_exists(self.use_user_site)\n\n        if req.satisfied_by:\n            should_modify = (\n                self.upgrade_strategy != \"to-satisfy-only\" or\n                self.force_reinstall or\n                self.ignore_installed or\n                req.link.scheme == 'file'\n            )\n            if should_modify:\n                self._set_req_to_reinstall(req)\n            else:\n                logger.info(\n                    'Requirement already satisfied (use --upgrade to upgrade):'\n                    ' %s', req,\n                )\n\n        return abstract_dist\n\n    def _resolve_one(\n        self,\n        requirement_set,  # type: RequirementSet\n        req_to_install  # type: InstallRequirement\n    ):\n        # type: (...) -> List[InstallRequirement]\n        \"\"\"Prepare a single requirements file.\n\n        :return: A list of additional InstallRequirements to also install.\n        \"\"\"\n        # Tell user what we are doing for this requirement:\n        # obtain (editable), skipping, processing (local url), collecting\n        # (remote url or package name)\n        if req_to_install.constraint or req_to_install.prepared:\n            return []\n\n        req_to_install.prepared = True\n\n        # register tmp src for cleanup in case something goes wrong\n        requirement_set.reqs_to_cleanup.append(req_to_install)\n\n        abstract_dist = self._get_abstract_dist_for(req_to_install)\n\n        # Parse and return dependencies\n        dist = abstract_dist.dist()\n        try:\n            check_dist_requires_python(dist)\n        except UnsupportedPythonVersion as err:\n            if self.ignore_requires_python:\n                logger.warning(err.args[0])\n            else:\n                raise\n\n        more_reqs = []  # type: List[InstallRequirement]\n\n        def add_req(subreq, extras_requested):\n            sub_install_req = install_req_from_req_string(\n                str(subreq),\n                req_to_install,\n                isolated=self.isolated,\n                wheel_cache=self.wheel_cache,\n                use_pep517=self.use_pep517\n            )\n            parent_req_name = req_to_install.name\n            to_scan_again, add_to_parent = requirement_set.add_requirement(\n                sub_install_req,\n                parent_req_name=parent_req_name,\n                extras_requested=extras_requested,\n            )\n            if parent_req_name and add_to_parent:\n                self._discovered_dependencies[parent_req_name].append(\n                    add_to_parent\n                )\n            more_reqs.extend(to_scan_again)\n\n        with indent_log():\n            # We add req_to_install before its dependencies, so that we\n            # can refer to it when adding dependencies.\n            if not requirement_set.has_requirement(req_to_install.name):\n                # 'unnamed' requirements will get added here\n                req_to_install.is_direct = True\n                requirement_set.add_requirement(\n                    req_to_install, parent_req_name=None,\n                )\n\n            if not self.ignore_dependencies:\n                if req_to_install.extras:\n                    logger.debug(\n                        \"Installing extra requirements: %r\",\n                        ','.join(req_to_install.extras),\n                    )\n                missing_requested = sorted(\n                    set(req_to_install.extras) - set(dist.extras)\n                )\n                for missing in missing_requested:\n                    logger.warning(\n                        '%s does not provide the extra \\'%s\\'',\n                        dist, missing\n                    )\n\n                available_requested = sorted(\n                    set(dist.extras) & set(req_to_install.extras)\n                )\n                for subreq in dist.requires(available_requested):\n                    add_req(subreq, extras_requested=available_requested)\n\n            if not req_to_install.editable and not req_to_install.satisfied_by:\n                # XXX: --no-install leads this to report 'Successfully\n                # downloaded' for only non-editable reqs, even though we took\n                # action on them.\n                requirement_set.successfully_downloaded.append(req_to_install)\n\n        return more_reqs\n\n    def get_installation_order(self, req_set):\n        # type: (RequirementSet) -> List[InstallRequirement]\n        \"\"\"Create the installation order.\n\n        The installation order is topological - requirements are installed\n        before the requiring thing. We break cycles at an arbitrary point,\n        and make no other guarantees.\n        \"\"\"\n        # The current implementation, which we may change at any point\n        # installs the user specified things in the order given, except when\n        # dependencies must come earlier to achieve topological order.\n        order = []\n        ordered_reqs = set()  # type: Set[InstallRequirement]\n\n        def schedule(req):\n            if req.satisfied_by or req in ordered_reqs:\n                return\n            if req.constraint:\n                return\n            ordered_reqs.add(req)\n            for dep in self._discovered_dependencies[req.name]:\n                schedule(dep)\n            order.append(req)\n\n        for install_req in req_set.requirements.values():\n            schedule(install_req)\n        return order\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/appdirs.py",
    "content": "\"\"\"\nThis code was taken from https://github.com/ActiveState/appdirs and modified\nto suit our purposes.\n\"\"\"\nfrom __future__ import absolute_import\n\nimport os\nimport sys\n\nfrom pip._vendor.six import PY2, text_type\n\nfrom pip._internal.utils.compat import WINDOWS, expanduser\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import (  # noqa: F401\n        List, Union\n    )\n\n\ndef user_cache_dir(appname):\n    # type: (str) -> str\n    r\"\"\"\n    Return full path to the user-specific cache dir for this application.\n\n        \"appname\" is the name of application.\n\n    Typical user cache directories are:\n        macOS:      ~/Library/Caches/<AppName>\n        Unix:       ~/.cache/<AppName> (XDG default)\n        Windows:    C:\\Users\\<username>\\AppData\\Local\\<AppName>\\Cache\n\n    On Windows the only suggestion in the MSDN docs is that local settings go\n    in the `CSIDL_LOCAL_APPDATA` directory. This is identical to the\n    non-roaming app data dir (the default returned by `user_data_dir`). Apps\n    typically put cache data somewhere *under* the given dir here. Some\n    examples:\n        ...\\Mozilla\\Firefox\\Profiles\\<ProfileName>\\Cache\n        ...\\Acme\\SuperApp\\Cache\\1.0\n\n    OPINION: This function appends \"Cache\" to the `CSIDL_LOCAL_APPDATA` value.\n    \"\"\"\n    if WINDOWS:\n        # Get the base path\n        path = os.path.normpath(_get_win_folder(\"CSIDL_LOCAL_APPDATA\"))\n\n        # When using Python 2, return paths as bytes on Windows like we do on\n        # other operating systems. See helper function docs for more details.\n        if PY2 and isinstance(path, text_type):\n            path = _win_path_to_bytes(path)\n\n        # Add our app name and Cache directory to it\n        path = os.path.join(path, appname, \"Cache\")\n    elif sys.platform == \"darwin\":\n        # Get the base path\n        path = expanduser(\"~/Library/Caches\")\n\n        # Add our app name to it\n        path = os.path.join(path, appname)\n    else:\n        # Get the base path\n        path = os.getenv(\"XDG_CACHE_HOME\", expanduser(\"~/.cache\"))\n\n        # Add our app name to it\n        path = os.path.join(path, appname)\n\n    return path\n\n\ndef user_data_dir(appname, roaming=False):\n    # type: (str, bool) -> str\n    r\"\"\"\n    Return full path to the user-specific data dir for this application.\n\n        \"appname\" is the name of application.\n            If None, just the system directory is returned.\n        \"roaming\" (boolean, default False) can be set True to use the Windows\n            roaming appdata directory. That means that for users on a Windows\n            network setup for roaming profiles, this user data will be\n            sync'd on login. See\n            <http://technet.microsoft.com/en-us/library/cc766489(WS.10).aspx>\n            for a discussion of issues.\n\n    Typical user data directories are:\n        macOS:                  ~/Library/Application Support/<AppName>\n                                if it exists, else ~/.config/<AppName>\n        Unix:                   ~/.local/share/<AppName>    # or in\n                                $XDG_DATA_HOME, if defined\n        Win XP (not roaming):   C:\\Documents and Settings\\<username>\\ ...\n                                ...Application Data\\<AppName>\n        Win XP (roaming):       C:\\Documents and Settings\\<username>\\Local ...\n                                ...Settings\\Application Data\\<AppName>\n        Win 7  (not roaming):   C:\\\\Users\\<username>\\AppData\\Local\\<AppName>\n        Win 7  (roaming):       C:\\\\Users\\<username>\\AppData\\Roaming\\<AppName>\n\n    For Unix, we follow the XDG spec and support $XDG_DATA_HOME.\n    That means, by default \"~/.local/share/<AppName>\".\n    \"\"\"\n    if WINDOWS:\n        const = roaming and \"CSIDL_APPDATA\" or \"CSIDL_LOCAL_APPDATA\"\n        path = os.path.join(os.path.normpath(_get_win_folder(const)), appname)\n    elif sys.platform == \"darwin\":\n        path = os.path.join(\n            expanduser('~/Library/Application Support/'),\n            appname,\n        ) if os.path.isdir(os.path.join(\n            expanduser('~/Library/Application Support/'),\n            appname,\n        )\n        ) else os.path.join(\n            expanduser('~/.config/'),\n            appname,\n        )\n    else:\n        path = os.path.join(\n            os.getenv('XDG_DATA_HOME', expanduser(\"~/.local/share\")),\n            appname,\n        )\n\n    return path\n\n\ndef user_config_dir(appname, roaming=True):\n    # type: (str, bool) -> str\n    \"\"\"Return full path to the user-specific config dir for this application.\n\n        \"appname\" is the name of application.\n            If None, just the system directory is returned.\n        \"roaming\" (boolean, default True) can be set False to not use the\n            Windows roaming appdata directory. That means that for users on a\n            Windows network setup for roaming profiles, this user data will be\n            sync'd on login. See\n            <http://technet.microsoft.com/en-us/library/cc766489(WS.10).aspx>\n            for a discussion of issues.\n\n    Typical user data directories are:\n        macOS:                  same as user_data_dir\n        Unix:                   ~/.config/<AppName>\n        Win *:                  same as user_data_dir\n\n    For Unix, we follow the XDG spec and support $XDG_CONFIG_HOME.\n    That means, by default \"~/.config/<AppName>\".\n    \"\"\"\n    if WINDOWS:\n        path = user_data_dir(appname, roaming=roaming)\n    elif sys.platform == \"darwin\":\n        path = user_data_dir(appname)\n    else:\n        path = os.getenv('XDG_CONFIG_HOME', expanduser(\"~/.config\"))\n        path = os.path.join(path, appname)\n\n    return path\n\n\n# for the discussion regarding site_config_dirs locations\n# see <https://github.com/pypa/pip/issues/1733>\ndef site_config_dirs(appname):\n    # type: (str) -> List[str]\n    r\"\"\"Return a list of potential user-shared config dirs for this application.\n\n        \"appname\" is the name of application.\n\n    Typical user config directories are:\n        macOS:      /Library/Application Support/<AppName>/\n        Unix:       /etc or $XDG_CONFIG_DIRS[i]/<AppName>/ for each value in\n                    $XDG_CONFIG_DIRS\n        Win XP:     C:\\Documents and Settings\\All Users\\Application ...\n                    ...Data\\<AppName>\\\n        Vista:      (Fail! \"C:\\ProgramData\" is a hidden *system* directory\n                    on Vista.)\n        Win 7:      Hidden, but writeable on Win 7:\n                    C:\\ProgramData\\<AppName>\\\n    \"\"\"\n    if WINDOWS:\n        path = os.path.normpath(_get_win_folder(\"CSIDL_COMMON_APPDATA\"))\n        pathlist = [os.path.join(path, appname)]\n    elif sys.platform == 'darwin':\n        pathlist = [os.path.join('/Library/Application Support', appname)]\n    else:\n        # try looking in $XDG_CONFIG_DIRS\n        xdg_config_dirs = os.getenv('XDG_CONFIG_DIRS', '/etc/xdg')\n        if xdg_config_dirs:\n            pathlist = [\n                os.path.join(expanduser(x), appname)\n                for x in xdg_config_dirs.split(os.pathsep)\n            ]\n        else:\n            pathlist = []\n\n        # always look in /etc directly as well\n        pathlist.append('/etc')\n\n    return pathlist\n\n\n# -- Windows support functions --\n\ndef _get_win_folder_from_registry(csidl_name):\n    # type: (str) -> str\n    \"\"\"\n    This is a fallback technique at best. I'm not sure if using the\n    registry for this guarantees us the correct answer for all CSIDL_*\n    names.\n    \"\"\"\n    import _winreg\n\n    shell_folder_name = {\n        \"CSIDL_APPDATA\": \"AppData\",\n        \"CSIDL_COMMON_APPDATA\": \"Common AppData\",\n        \"CSIDL_LOCAL_APPDATA\": \"Local AppData\",\n    }[csidl_name]\n\n    key = _winreg.OpenKey(\n        _winreg.HKEY_CURRENT_USER,\n        r\"Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\Shell Folders\"\n    )\n    directory, _type = _winreg.QueryValueEx(key, shell_folder_name)\n    return directory\n\n\ndef _get_win_folder_with_ctypes(csidl_name):\n    # type: (str) -> str\n    csidl_const = {\n        \"CSIDL_APPDATA\": 26,\n        \"CSIDL_COMMON_APPDATA\": 35,\n        \"CSIDL_LOCAL_APPDATA\": 28,\n    }[csidl_name]\n\n    buf = ctypes.create_unicode_buffer(1024)\n    ctypes.windll.shell32.SHGetFolderPathW(None, csidl_const, None, 0, buf)\n\n    # Downgrade to short path name if have highbit chars. See\n    # <http://bugs.activestate.com/show_bug.cgi?id=85099>.\n    has_high_char = False\n    for c in buf:\n        if ord(c) > 255:\n            has_high_char = True\n            break\n    if has_high_char:\n        buf2 = ctypes.create_unicode_buffer(1024)\n        if ctypes.windll.kernel32.GetShortPathNameW(buf.value, buf2, 1024):\n            buf = buf2\n\n    return buf.value\n\n\nif WINDOWS:\n    try:\n        import ctypes\n        _get_win_folder = _get_win_folder_with_ctypes\n    except ImportError:\n        _get_win_folder = _get_win_folder_from_registry\n\n\ndef _win_path_to_bytes(path):\n    \"\"\"Encode Windows paths to bytes. Only used on Python 2.\n\n    Motivation is to be consistent with other operating systems where paths\n    are also returned as bytes. This avoids problems mixing bytes and Unicode\n    elsewhere in the codebase. For more details and discussion see\n    <https://github.com/pypa/pip/issues/3463>.\n\n    If encoding using ASCII and MBCS fails, return the original Unicode path.\n    \"\"\"\n    for encoding in ('ASCII', 'MBCS'):\n        try:\n            return path.encode(encoding)\n        except (UnicodeEncodeError, LookupError):\n            pass\n    return path\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/compat.py",
    "content": "\"\"\"Stuff that differs in different Python versions and platform\ndistributions.\"\"\"\nfrom __future__ import absolute_import, division\n\nimport codecs\nimport locale\nimport logging\nimport os\nimport shutil\nimport sys\n\nfrom pip._vendor.six import text_type\n\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Tuple, Text  # noqa: F401\n\ntry:\n    import ipaddress\nexcept ImportError:\n    try:\n        from pip._vendor import ipaddress  # type: ignore\n    except ImportError:\n        import ipaddr as ipaddress  # type: ignore\n        ipaddress.ip_address = ipaddress.IPAddress  # type: ignore\n        ipaddress.ip_network = ipaddress.IPNetwork  # type: ignore\n\n\n__all__ = [\n    \"ipaddress\", \"uses_pycache\", \"console_to_str\", \"native_str\",\n    \"get_path_uid\", \"stdlib_pkgs\", \"WINDOWS\", \"samefile\", \"get_terminal_size\",\n    \"get_extension_suffixes\",\n]\n\n\nlogger = logging.getLogger(__name__)\n\nif sys.version_info >= (3, 4):\n    uses_pycache = True\n    from importlib.util import cache_from_source\nelse:\n    import imp\n\n    try:\n        cache_from_source = imp.cache_from_source  # type: ignore\n    except AttributeError:\n        # does not use __pycache__\n        cache_from_source = None\n\n    uses_pycache = cache_from_source is not None\n\n\nif sys.version_info >= (3, 5):\n    backslashreplace_decode = \"backslashreplace\"\nelse:\n    # In version 3.4 and older, backslashreplace exists\n    # but does not support use for decoding.\n    # We implement our own replace handler for this\n    # situation, so that we can consistently use\n    # backslash replacement for all versions.\n    def backslashreplace_decode_fn(err):\n        raw_bytes = (err.object[i] for i in range(err.start, err.end))\n        if sys.version_info[0] == 2:\n            # Python 2 gave us characters - convert to numeric bytes\n            raw_bytes = (ord(b) for b in raw_bytes)\n        return u\"\".join(u\"\\\\x%x\" % c for c in raw_bytes), err.end\n    codecs.register_error(\n        \"backslashreplace_decode\",\n        backslashreplace_decode_fn,\n    )\n    backslashreplace_decode = \"backslashreplace_decode\"\n\n\ndef console_to_str(data):\n    # type: (bytes) -> Text\n    \"\"\"Return a string, safe for output, of subprocess output.\n\n    We assume the data is in the locale preferred encoding.\n    If it won't decode properly, we warn the user but decode as\n    best we can.\n\n    We also ensure that the output can be safely written to\n    standard output without encoding errors.\n    \"\"\"\n\n    # First, get the encoding we assume. This is the preferred\n    # encoding for the locale, unless that is not found, or\n    # it is ASCII, in which case assume UTF-8\n    encoding = locale.getpreferredencoding()\n    if (not encoding) or codecs.lookup(encoding).name == \"ascii\":\n        encoding = \"utf-8\"\n\n    # Now try to decode the data - if we fail, warn the user and\n    # decode with replacement.\n    try:\n        decoded_data = data.decode(encoding)\n    except UnicodeDecodeError:\n        logger.warning(\n            \"Subprocess output does not appear to be encoded as %s\",\n            encoding,\n        )\n        decoded_data = data.decode(encoding, errors=backslashreplace_decode)\n\n    # Make sure we can print the output, by encoding it to the output\n    # encoding with replacement of unencodable characters, and then\n    # decoding again.\n    # We use stderr's encoding because it's less likely to be\n    # redirected and if we don't find an encoding we skip this\n    # step (on the assumption that output is wrapped by something\n    # that won't fail).\n    # The double getattr is to deal with the possibility that we're\n    # being called in a situation where sys.__stderr__ doesn't exist,\n    # or doesn't have an encoding attribute. Neither of these cases\n    # should occur in normal pip use, but there's no harm in checking\n    # in case people use pip in (unsupported) unusual situations.\n    output_encoding = getattr(getattr(sys, \"__stderr__\", None),\n                              \"encoding\", None)\n\n    if output_encoding:\n        output_encoded = decoded_data.encode(\n            output_encoding,\n            errors=\"backslashreplace\"\n        )\n        decoded_data = output_encoded.decode(output_encoding)\n\n    return decoded_data\n\n\nif sys.version_info >= (3,):\n    def native_str(s, replace=False):\n        # type: (str, bool) -> str\n        if isinstance(s, bytes):\n            return s.decode('utf-8', 'replace' if replace else 'strict')\n        return s\n\nelse:\n    def native_str(s, replace=False):\n        # type: (str, bool) -> str\n        # Replace is ignored -- unicode to UTF-8 can't fail\n        if isinstance(s, text_type):\n            return s.encode('utf-8')\n        return s\n\n\ndef get_path_uid(path):\n    # type: (str) -> int\n    \"\"\"\n    Return path's uid.\n\n    Does not follow symlinks:\n        https://github.com/pypa/pip/pull/935#discussion_r5307003\n\n    Placed this function in compat due to differences on AIX and\n    Jython, that should eventually go away.\n\n    :raises OSError: When path is a symlink or can't be read.\n    \"\"\"\n    if hasattr(os, 'O_NOFOLLOW'):\n        fd = os.open(path, os.O_RDONLY | os.O_NOFOLLOW)\n        file_uid = os.fstat(fd).st_uid\n        os.close(fd)\n    else:  # AIX and Jython\n        # WARNING: time of check vulnerability, but best we can do w/o NOFOLLOW\n        if not os.path.islink(path):\n            # older versions of Jython don't have `os.fstat`\n            file_uid = os.stat(path).st_uid\n        else:\n            # raise OSError for parity with os.O_NOFOLLOW above\n            raise OSError(\n                \"%s is a symlink; Will not return uid for symlinks\" % path\n            )\n    return file_uid\n\n\nif sys.version_info >= (3, 4):\n    from importlib.machinery import EXTENSION_SUFFIXES\n\n    def get_extension_suffixes():\n        return EXTENSION_SUFFIXES\nelse:\n    from imp import get_suffixes\n\n    def get_extension_suffixes():\n        return [suffix[0] for suffix in get_suffixes()]\n\n\ndef expanduser(path):\n    # type: (str) -> str\n    \"\"\"\n    Expand ~ and ~user constructions.\n\n    Includes a workaround for https://bugs.python.org/issue14768\n    \"\"\"\n    expanded = os.path.expanduser(path)\n    if path.startswith('~/') and expanded.startswith('//'):\n        expanded = expanded[1:]\n    return expanded\n\n\n# packages in the stdlib that may have installation metadata, but should not be\n# considered 'installed'.  this theoretically could be determined based on\n# dist.location (py27:`sysconfig.get_paths()['stdlib']`,\n# py26:sysconfig.get_config_vars('LIBDEST')), but fear platform variation may\n# make this ineffective, so hard-coding\nstdlib_pkgs = {\"python\", \"wsgiref\", \"argparse\"}\n\n\n# windows detection, covers cpython and ironpython\nWINDOWS = (sys.platform.startswith(\"win\") or\n           (sys.platform == 'cli' and os.name == 'nt'))\n\n\ndef samefile(file1, file2):\n    # type: (str, str) -> bool\n    \"\"\"Provide an alternative for os.path.samefile on Windows/Python2\"\"\"\n    if hasattr(os.path, 'samefile'):\n        return os.path.samefile(file1, file2)\n    else:\n        path1 = os.path.normcase(os.path.abspath(file1))\n        path2 = os.path.normcase(os.path.abspath(file2))\n        return path1 == path2\n\n\nif hasattr(shutil, 'get_terminal_size'):\n    def get_terminal_size():\n        # type: () -> Tuple[int, int]\n        \"\"\"\n        Returns a tuple (x, y) representing the width(x) and the height(y)\n        in characters of the terminal window.\n        \"\"\"\n        return tuple(shutil.get_terminal_size())  # type: ignore\nelse:\n    def get_terminal_size():\n        # type: () -> Tuple[int, int]\n        \"\"\"\n        Returns a tuple (x, y) representing the width(x) and the height(y)\n        in characters of the terminal window.\n        \"\"\"\n        def ioctl_GWINSZ(fd):\n            try:\n                import fcntl\n                import termios\n                import struct\n                cr = struct.unpack_from(\n                    'hh',\n                    fcntl.ioctl(fd, termios.TIOCGWINSZ, '12345678')\n                )\n            except Exception:\n                return None\n            if cr == (0, 0):\n                return None\n            return cr\n        cr = ioctl_GWINSZ(0) or ioctl_GWINSZ(1) or ioctl_GWINSZ(2)\n        if not cr:\n            try:\n                fd = os.open(os.ctermid(), os.O_RDONLY)\n                cr = ioctl_GWINSZ(fd)\n                os.close(fd)\n            except Exception:\n                pass\n        if not cr:\n            cr = (os.environ.get('LINES', 25), os.environ.get('COLUMNS', 80))\n        return int(cr[1]), int(cr[0])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/deprecation.py",
    "content": "\"\"\"\nA module that implements tooling to enable easy warnings about deprecations.\n\"\"\"\nfrom __future__ import absolute_import\n\nimport logging\nimport warnings\n\nfrom pip._vendor.packaging.version import parse\n\nfrom pip import __version__ as current_version\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Any, Optional  # noqa: F401\n\n\nclass PipDeprecationWarning(Warning):\n    pass\n\n\n_original_showwarning = None  # type: Any\n\n\n# Warnings <-> Logging Integration\ndef _showwarning(message, category, filename, lineno, file=None, line=None):\n    if file is not None:\n        if _original_showwarning is not None:\n            _original_showwarning(\n                message, category, filename, lineno, file, line,\n            )\n    elif issubclass(category, PipDeprecationWarning):\n        # We use a specially named logger which will handle all of the\n        # deprecation messages for pip.\n        logger = logging.getLogger(\"pip._internal.deprecations\")\n        logger.warning(message)\n    else:\n        _original_showwarning(\n            message, category, filename, lineno, file, line,\n        )\n\n\ndef install_warning_logger():\n    # type: () -> None\n    # Enable our Deprecation Warnings\n    warnings.simplefilter(\"default\", PipDeprecationWarning, append=True)\n\n    global _original_showwarning\n\n    if _original_showwarning is None:\n        _original_showwarning = warnings.showwarning\n        warnings.showwarning = _showwarning\n\n\ndef deprecated(reason, replacement, gone_in, issue=None):\n    # type: (str, Optional[str], Optional[str], Optional[int]) -> None\n    \"\"\"Helper to deprecate existing functionality.\n\n    reason:\n        Textual reason shown to the user about why this functionality has\n        been deprecated.\n    replacement:\n        Textual suggestion shown to the user about what alternative\n        functionality they can use.\n    gone_in:\n        The version of pip does this functionality should get removed in.\n        Raises errors if pip's current version is greater than or equal to\n        this.\n    issue:\n        Issue number on the tracker that would serve as a useful place for\n        users to find related discussion and provide feedback.\n\n    Always pass replacement, gone_in and issue as keyword arguments for clarity\n    at the call site.\n    \"\"\"\n\n    # Construct a nice message.\n    # This is purposely eagerly formatted as we want it to appear as if someone\n    # typed this entire message out.\n    message = \"DEPRECATION: \" + reason\n    if replacement is not None:\n        message += \" A possible replacement is {}.\".format(replacement)\n    if issue is not None:\n        url = \"https://github.com/pypa/pip/issues/\" + str(issue)\n        message += \" You can find discussion regarding this at {}.\".format(url)\n\n    # Raise as an error if it has to be removed.\n    if gone_in is not None and parse(current_version) >= parse(gone_in):\n        raise PipDeprecationWarning(message)\n    warnings.warn(message, category=PipDeprecationWarning, stacklevel=2)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/encoding.py",
    "content": "import codecs\nimport locale\nimport re\nimport sys\n\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import List, Tuple, Text  # noqa: F401\n\nBOMS = [\n    (codecs.BOM_UTF8, 'utf8'),\n    (codecs.BOM_UTF16, 'utf16'),\n    (codecs.BOM_UTF16_BE, 'utf16-be'),\n    (codecs.BOM_UTF16_LE, 'utf16-le'),\n    (codecs.BOM_UTF32, 'utf32'),\n    (codecs.BOM_UTF32_BE, 'utf32-be'),\n    (codecs.BOM_UTF32_LE, 'utf32-le'),\n]  # type: List[Tuple[bytes, Text]]\n\nENCODING_RE = re.compile(br'coding[:=]\\s*([-\\w.]+)')\n\n\ndef auto_decode(data):\n    # type: (bytes) -> Text\n    \"\"\"Check a bytes string for a BOM to correctly detect the encoding\n\n    Fallback to locale.getpreferredencoding(False) like open() on Python3\"\"\"\n    for bom, encoding in BOMS:\n        if data.startswith(bom):\n            return data[len(bom):].decode(encoding)\n    # Lets check the first two lines as in PEP263\n    for line in data.split(b'\\n')[:2]:\n        if line[0:1] == b'#' and ENCODING_RE.search(line):\n            encoding = ENCODING_RE.search(line).groups()[0].decode('ascii')\n            return data.decode(encoding)\n    return data.decode(\n        locale.getpreferredencoding(False) or sys.getdefaultencoding(),\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/filesystem.py",
    "content": "import os\nimport os.path\n\nfrom pip._internal.utils.compat import get_path_uid\n\n\ndef check_path_owner(path):\n    # type: (str) -> bool\n    # If we don't have a way to check the effective uid of this process, then\n    # we'll just assume that we own the directory.\n    if not hasattr(os, \"geteuid\"):\n        return True\n\n    previous = None\n    while path != previous:\n        if os.path.lexists(path):\n            # Check if path is writable by current user.\n            if os.geteuid() == 0:\n                # Special handling for root user in order to handle properly\n                # cases where users use sudo without -H flag.\n                try:\n                    path_uid = get_path_uid(path)\n                except OSError:\n                    return False\n                return path_uid == 0\n            else:\n                return os.access(path, os.W_OK)\n        else:\n            previous, path = path, os.path.dirname(path)\n    return False  # assume we don't own the path\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/glibc.py",
    "content": "from __future__ import absolute_import\n\nimport ctypes\nimport re\nimport warnings\n\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Optional, Tuple  # noqa: F401\n\n\ndef glibc_version_string():\n    # type: () -> Optional[str]\n    \"Returns glibc version string, or None if not using glibc.\"\n\n    # ctypes.CDLL(None) internally calls dlopen(NULL), and as the dlopen\n    # manpage says, \"If filename is NULL, then the returned handle is for the\n    # main program\". This way we can let the linker do the work to figure out\n    # which libc our process is actually using.\n    process_namespace = ctypes.CDLL(None)\n    try:\n        gnu_get_libc_version = process_namespace.gnu_get_libc_version\n    except AttributeError:\n        # Symbol doesn't exist -> therefore, we are not linked to\n        # glibc.\n        return None\n\n    # Call gnu_get_libc_version, which returns a string like \"2.5\"\n    gnu_get_libc_version.restype = ctypes.c_char_p\n    version_str = gnu_get_libc_version()\n    # py2 / py3 compatibility:\n    if not isinstance(version_str, str):\n        version_str = version_str.decode(\"ascii\")\n\n    return version_str\n\n\n# Separated out from have_compatible_glibc for easier unit testing\ndef check_glibc_version(version_str, required_major, minimum_minor):\n    # type: (str, int, int) -> bool\n    # Parse string and check against requested version.\n    #\n    # We use a regexp instead of str.split because we want to discard any\n    # random junk that might come after the minor version -- this might happen\n    # in patched/forked versions of glibc (e.g. Linaro's version of glibc\n    # uses version strings like \"2.20-2014.11\"). See gh-3588.\n    m = re.match(r\"(?P<major>[0-9]+)\\.(?P<minor>[0-9]+)\", version_str)\n    if not m:\n        warnings.warn(\"Expected glibc version with 2 components major.minor,\"\n                      \" got: %s\" % version_str, RuntimeWarning)\n        return False\n    return (int(m.group(\"major\")) == required_major and\n            int(m.group(\"minor\")) >= minimum_minor)\n\n\ndef have_compatible_glibc(required_major, minimum_minor):\n    # type: (int, int) -> bool\n    version_str = glibc_version_string()  # type: Optional[str]\n    if version_str is None:\n        return False\n    return check_glibc_version(version_str, required_major, minimum_minor)\n\n\n# platform.libc_ver regularly returns completely nonsensical glibc\n# versions. E.g. on my computer, platform says:\n#\n#   ~$ python2.7 -c 'import platform; print(platform.libc_ver())'\n#   ('glibc', '2.7')\n#   ~$ python3.5 -c 'import platform; print(platform.libc_ver())'\n#   ('glibc', '2.9')\n#\n# But the truth is:\n#\n#   ~$ ldd --version\n#   ldd (Debian GLIBC 2.22-11) 2.22\n#\n# This is unfortunate, because it means that the linehaul data on libc\n# versions that was generated by pip 8.1.2 and earlier is useless and\n# misleading. Solution: instead of using platform, use our code that actually\n# works.\ndef libc_ver():\n    # type: () -> Tuple[str, str]\n    \"\"\"Try to determine the glibc version\n\n    Returns a tuple of strings (lib, version) which default to empty strings\n    in case the lookup fails.\n    \"\"\"\n    glibc_version = glibc_version_string()\n    if glibc_version is None:\n        return (\"\", \"\")\n    else:\n        return (\"glibc\", glibc_version)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/hashes.py",
    "content": "from __future__ import absolute_import\n\nimport hashlib\n\nfrom pip._vendor.six import iteritems, iterkeys, itervalues\n\nfrom pip._internal.exceptions import (\n    HashMismatch, HashMissing, InstallationError,\n)\nfrom pip._internal.utils.misc import read_chunks\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import (  # noqa: F401\n        Dict, List, BinaryIO, NoReturn, Iterator\n    )\n    from pip._vendor.six import PY3\n    if PY3:\n        from hashlib import _Hash  # noqa: F401\n    else:\n        from hashlib import _hash as _Hash  # noqa: F401\n\n\n# The recommended hash algo of the moment. Change this whenever the state of\n# the art changes; it won't hurt backward compatibility.\nFAVORITE_HASH = 'sha256'\n\n\n# Names of hashlib algorithms allowed by the --hash option and ``pip hash``\n# Currently, those are the ones at least as collision-resistant as sha256.\nSTRONG_HASHES = ['sha256', 'sha384', 'sha512']\n\n\nclass Hashes(object):\n    \"\"\"A wrapper that builds multiple hashes at once and checks them against\n    known-good values\n\n    \"\"\"\n    def __init__(self, hashes=None):\n        # type: (Dict[str, List[str]]) -> None\n        \"\"\"\n        :param hashes: A dict of algorithm names pointing to lists of allowed\n            hex digests\n        \"\"\"\n        self._allowed = {} if hashes is None else hashes\n\n    def check_against_chunks(self, chunks):\n        # type: (Iterator[bytes]) -> None\n        \"\"\"Check good hashes against ones built from iterable of chunks of\n        data.\n\n        Raise HashMismatch if none match.\n\n        \"\"\"\n        gots = {}\n        for hash_name in iterkeys(self._allowed):\n            try:\n                gots[hash_name] = hashlib.new(hash_name)\n            except (ValueError, TypeError):\n                raise InstallationError('Unknown hash name: %s' % hash_name)\n\n        for chunk in chunks:\n            for hash in itervalues(gots):\n                hash.update(chunk)\n\n        for hash_name, got in iteritems(gots):\n            if got.hexdigest() in self._allowed[hash_name]:\n                return\n        self._raise(gots)\n\n    def _raise(self, gots):\n        # type: (Dict[str, _Hash]) -> NoReturn\n        raise HashMismatch(self._allowed, gots)\n\n    def check_against_file(self, file):\n        # type: (BinaryIO) -> None\n        \"\"\"Check good hashes against a file-like object\n\n        Raise HashMismatch if none match.\n\n        \"\"\"\n        return self.check_against_chunks(read_chunks(file))\n\n    def check_against_path(self, path):\n        # type: (str) -> None\n        with open(path, 'rb') as file:\n            return self.check_against_file(file)\n\n    def __nonzero__(self):\n        # type: () -> bool\n        \"\"\"Return whether I know any known-good hashes.\"\"\"\n        return bool(self._allowed)\n\n    def __bool__(self):\n        # type: () -> bool\n        return self.__nonzero__()\n\n\nclass MissingHashes(Hashes):\n    \"\"\"A workalike for Hashes used when we're missing a hash for a requirement\n\n    It computes the actual hash of the requirement and raises a HashMissing\n    exception showing it to the user.\n\n    \"\"\"\n    def __init__(self):\n        # type: () -> None\n        \"\"\"Don't offer the ``hashes`` kwarg.\"\"\"\n        # Pass our favorite hash in to generate a \"gotten hash\". With the\n        # empty list, it will never match, so an error will always raise.\n        super(MissingHashes, self).__init__(hashes={FAVORITE_HASH: []})\n\n    def _raise(self, gots):\n        # type: (Dict[str, _Hash]) -> NoReturn\n        raise HashMissing(gots[FAVORITE_HASH].hexdigest())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/logging.py",
    "content": "from __future__ import absolute_import\n\nimport contextlib\nimport errno\nimport logging\nimport logging.handlers\nimport os\nimport sys\n\nfrom pip._vendor.six import PY2\n\nfrom pip._internal.utils.compat import WINDOWS\nfrom pip._internal.utils.misc import ensure_dir\n\ntry:\n    import threading\nexcept ImportError:\n    import dummy_threading as threading  # type: ignore\n\n\ntry:\n    from pip._vendor import colorama\n# Lots of different errors can come from this, including SystemError and\n# ImportError.\nexcept Exception:\n    colorama = None\n\n\n_log_state = threading.local()\n_log_state.indentation = 0\n\n\nclass BrokenStdoutLoggingError(Exception):\n    \"\"\"\n    Raised if BrokenPipeError occurs for the stdout stream while logging.\n    \"\"\"\n    pass\n\n\n# BrokenPipeError does not exist in Python 2 and, in addition, manifests\n# differently in Windows and non-Windows.\nif WINDOWS:\n    # In Windows, a broken pipe can show up as EINVAL rather than EPIPE:\n    # https://bugs.python.org/issue19612\n    # https://bugs.python.org/issue30418\n    if PY2:\n        def _is_broken_pipe_error(exc_class, exc):\n            \"\"\"See the docstring for non-Windows Python 3 below.\"\"\"\n            return (exc_class is IOError and\n                    exc.errno in (errno.EINVAL, errno.EPIPE))\n    else:\n        # In Windows, a broken pipe IOError became OSError in Python 3.\n        def _is_broken_pipe_error(exc_class, exc):\n            \"\"\"See the docstring for non-Windows Python 3 below.\"\"\"\n            return ((exc_class is BrokenPipeError) or  # noqa: F821\n                    (exc_class is OSError and\n                     exc.errno in (errno.EINVAL, errno.EPIPE)))\nelif PY2:\n    def _is_broken_pipe_error(exc_class, exc):\n        \"\"\"See the docstring for non-Windows Python 3 below.\"\"\"\n        return (exc_class is IOError and exc.errno == errno.EPIPE)\nelse:\n    # Then we are in the non-Windows Python 3 case.\n    def _is_broken_pipe_error(exc_class, exc):\n        \"\"\"\n        Return whether an exception is a broken pipe error.\n\n        Args:\n          exc_class: an exception class.\n          exc: an exception instance.\n        \"\"\"\n        return (exc_class is BrokenPipeError)  # noqa: F821\n\n\n@contextlib.contextmanager\ndef indent_log(num=2):\n    \"\"\"\n    A context manager which will cause the log output to be indented for any\n    log messages emitted inside it.\n    \"\"\"\n    _log_state.indentation += num\n    try:\n        yield\n    finally:\n        _log_state.indentation -= num\n\n\ndef get_indentation():\n    return getattr(_log_state, 'indentation', 0)\n\n\nclass IndentingFormatter(logging.Formatter):\n    def __init__(self, *args, **kwargs):\n        \"\"\"\n        A logging.Formatter obeying containing indent_log contexts.\n\n        :param add_timestamp: A bool indicating output lines should be prefixed\n            with their record's timestamp.\n        \"\"\"\n        self.add_timestamp = kwargs.pop(\"add_timestamp\", False)\n        super(IndentingFormatter, self).__init__(*args, **kwargs)\n\n    def format(self, record):\n        \"\"\"\n        Calls the standard formatter, but will indent all of the log messages\n        by our current indentation level.\n        \"\"\"\n        formatted = super(IndentingFormatter, self).format(record)\n        prefix = ''\n        if self.add_timestamp:\n            prefix = self.formatTime(record, \"%Y-%m-%dT%H:%M:%S \")\n        prefix += \" \" * get_indentation()\n        formatted = \"\".join([\n            prefix + line\n            for line in formatted.splitlines(True)\n        ])\n        return formatted\n\n\ndef _color_wrap(*colors):\n    def wrapped(inp):\n        return \"\".join(list(colors) + [inp, colorama.Style.RESET_ALL])\n    return wrapped\n\n\nclass ColorizedStreamHandler(logging.StreamHandler):\n\n    # Don't build up a list of colors if we don't have colorama\n    if colorama:\n        COLORS = [\n            # This needs to be in order from highest logging level to lowest.\n            (logging.ERROR, _color_wrap(colorama.Fore.RED)),\n            (logging.WARNING, _color_wrap(colorama.Fore.YELLOW)),\n        ]\n    else:\n        COLORS = []\n\n    def __init__(self, stream=None, no_color=None):\n        logging.StreamHandler.__init__(self, stream)\n        self._no_color = no_color\n\n        if WINDOWS and colorama:\n            self.stream = colorama.AnsiToWin32(self.stream)\n\n    def _using_stdout(self):\n        \"\"\"\n        Return whether the handler is using sys.stdout.\n        \"\"\"\n        if WINDOWS and colorama:\n            # Then self.stream is an AnsiToWin32 object.\n            return self.stream.wrapped is sys.stdout\n\n        return self.stream is sys.stdout\n\n    def should_color(self):\n        # Don't colorize things if we do not have colorama or if told not to\n        if not colorama or self._no_color:\n            return False\n\n        real_stream = (\n            self.stream if not isinstance(self.stream, colorama.AnsiToWin32)\n            else self.stream.wrapped\n        )\n\n        # If the stream is a tty we should color it\n        if hasattr(real_stream, \"isatty\") and real_stream.isatty():\n            return True\n\n        # If we have an ANSI term we should color it\n        if os.environ.get(\"TERM\") == \"ANSI\":\n            return True\n\n        # If anything else we should not color it\n        return False\n\n    def format(self, record):\n        msg = logging.StreamHandler.format(self, record)\n\n        if self.should_color():\n            for level, color in self.COLORS:\n                if record.levelno >= level:\n                    msg = color(msg)\n                    break\n\n        return msg\n\n    # The logging module says handleError() can be customized.\n    def handleError(self, record):\n        exc_class, exc = sys.exc_info()[:2]\n        # If a broken pipe occurred while calling write() or flush() on the\n        # stdout stream in logging's Handler.emit(), then raise our special\n        # exception so we can handle it in main() instead of logging the\n        # broken pipe error and continuing.\n        if (exc_class and self._using_stdout() and\n                _is_broken_pipe_error(exc_class, exc)):\n            raise BrokenStdoutLoggingError()\n\n        return super(ColorizedStreamHandler, self).handleError(record)\n\n\nclass BetterRotatingFileHandler(logging.handlers.RotatingFileHandler):\n\n    def _open(self):\n        ensure_dir(os.path.dirname(self.baseFilename))\n        return logging.handlers.RotatingFileHandler._open(self)\n\n\nclass MaxLevelFilter(logging.Filter):\n\n    def __init__(self, level):\n        self.level = level\n\n    def filter(self, record):\n        return record.levelno < self.level\n\n\ndef setup_logging(verbosity, no_color, user_log_file):\n    \"\"\"Configures and sets up all of the logging\n\n    Returns the requested logging level, as its integer value.\n    \"\"\"\n\n    # Determine the level to be logging at.\n    if verbosity >= 1:\n        level = \"DEBUG\"\n    elif verbosity == -1:\n        level = \"WARNING\"\n    elif verbosity == -2:\n        level = \"ERROR\"\n    elif verbosity <= -3:\n        level = \"CRITICAL\"\n    else:\n        level = \"INFO\"\n\n    level_number = getattr(logging, level)\n\n    # The \"root\" logger should match the \"console\" level *unless* we also need\n    # to log to a user log file.\n    include_user_log = user_log_file is not None\n    if include_user_log:\n        additional_log_file = user_log_file\n        root_level = \"DEBUG\"\n    else:\n        additional_log_file = \"/dev/null\"\n        root_level = level\n\n    # Disable any logging besides WARNING unless we have DEBUG level logging\n    # enabled for vendored libraries.\n    vendored_log_level = \"WARNING\" if level in [\"INFO\", \"ERROR\"] else \"DEBUG\"\n\n    # Shorthands for clarity\n    log_streams = {\n        \"stdout\": \"ext://sys.stdout\",\n        \"stderr\": \"ext://sys.stderr\",\n    }\n    handler_classes = {\n        \"stream\": \"pip._internal.utils.logging.ColorizedStreamHandler\",\n        \"file\": \"pip._internal.utils.logging.BetterRotatingFileHandler\",\n    }\n\n    logging.config.dictConfig({\n        \"version\": 1,\n        \"disable_existing_loggers\": False,\n        \"filters\": {\n            \"exclude_warnings\": {\n                \"()\": \"pip._internal.utils.logging.MaxLevelFilter\",\n                \"level\": logging.WARNING,\n            },\n        },\n        \"formatters\": {\n            \"indent\": {\n                \"()\": IndentingFormatter,\n                \"format\": \"%(message)s\",\n            },\n            \"indent_with_timestamp\": {\n                \"()\": IndentingFormatter,\n                \"format\": \"%(message)s\",\n                \"add_timestamp\": True,\n            },\n        },\n        \"handlers\": {\n            \"console\": {\n                \"level\": level,\n                \"class\": handler_classes[\"stream\"],\n                \"no_color\": no_color,\n                \"stream\": log_streams[\"stdout\"],\n                \"filters\": [\"exclude_warnings\"],\n                \"formatter\": \"indent\",\n            },\n            \"console_errors\": {\n                \"level\": \"WARNING\",\n                \"class\": handler_classes[\"stream\"],\n                \"no_color\": no_color,\n                \"stream\": log_streams[\"stderr\"],\n                \"formatter\": \"indent\",\n            },\n            \"user_log\": {\n                \"level\": \"DEBUG\",\n                \"class\": handler_classes[\"file\"],\n                \"filename\": additional_log_file,\n                \"delay\": True,\n                \"formatter\": \"indent_with_timestamp\",\n            },\n        },\n        \"root\": {\n            \"level\": root_level,\n            \"handlers\": [\"console\", \"console_errors\"] + (\n                [\"user_log\"] if include_user_log else []\n            ),\n        },\n        \"loggers\": {\n            \"pip._vendor\": {\n                \"level\": vendored_log_level\n            }\n        },\n    })\n\n    return level_number\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/misc.py",
    "content": "from __future__ import absolute_import\n\nimport contextlib\nimport errno\nimport io\nimport locale\n# we have a submodule named 'logging' which would shadow this if we used the\n# regular name:\nimport logging as std_logging\nimport os\nimport posixpath\nimport re\nimport shutil\nimport stat\nimport subprocess\nimport sys\nimport tarfile\nimport zipfile\nfrom collections import deque\n\nfrom pip._vendor import pkg_resources\n# NOTE: retrying is not annotated in typeshed as on 2017-07-17, which is\n#       why we ignore the type on this import.\nfrom pip._vendor.retrying import retry  # type: ignore\nfrom pip._vendor.six import PY2\nfrom pip._vendor.six.moves import input\nfrom pip._vendor.six.moves.urllib import parse as urllib_parse\nfrom pip._vendor.six.moves.urllib.parse import unquote as urllib_unquote\n\nfrom pip._internal.exceptions import CommandError, InstallationError\nfrom pip._internal.locations import (\n    running_under_virtualenv, site_packages, user_site, virtualenv_no_global,\n    write_delete_marker_file,\n)\nfrom pip._internal.utils.compat import (\n    WINDOWS, console_to_str, expanduser, stdlib_pkgs,\n)\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif PY2:\n    from io import BytesIO as StringIO\nelse:\n    from io import StringIO\n\nif MYPY_CHECK_RUNNING:\n    from typing import (  # noqa: F401\n        Optional, Tuple, Iterable, List, Match, Union, Any, Mapping, Text,\n        AnyStr, Container\n    )\n    from pip._vendor.pkg_resources import Distribution  # noqa: F401\n    from pip._internal.models.link import Link  # noqa: F401\n    from pip._internal.utils.ui import SpinnerInterface  # noqa: F401\n\n\n__all__ = ['rmtree', 'display_path', 'backup_dir',\n           'ask', 'splitext',\n           'format_size', 'is_installable_dir',\n           'is_svn_page', 'file_contents',\n           'split_leading_dir', 'has_leading_dir',\n           'normalize_path',\n           'renames', 'get_prog',\n           'unzip_file', 'untar_file', 'unpack_file', 'call_subprocess',\n           'captured_stdout', 'ensure_dir',\n           'ARCHIVE_EXTENSIONS', 'SUPPORTED_EXTENSIONS', 'WHEEL_EXTENSION',\n           'get_installed_version', 'remove_auth_from_url']\n\n\nlogger = std_logging.getLogger(__name__)\n\nWHEEL_EXTENSION = '.whl'\nBZ2_EXTENSIONS = ('.tar.bz2', '.tbz')\nXZ_EXTENSIONS = ('.tar.xz', '.txz', '.tlz', '.tar.lz', '.tar.lzma')\nZIP_EXTENSIONS = ('.zip', WHEEL_EXTENSION)\nTAR_EXTENSIONS = ('.tar.gz', '.tgz', '.tar')\nARCHIVE_EXTENSIONS = (\n    ZIP_EXTENSIONS + BZ2_EXTENSIONS + TAR_EXTENSIONS + XZ_EXTENSIONS)\nSUPPORTED_EXTENSIONS = ZIP_EXTENSIONS + TAR_EXTENSIONS\n\ntry:\n    import bz2  # noqa\n    SUPPORTED_EXTENSIONS += BZ2_EXTENSIONS\nexcept ImportError:\n    logger.debug('bz2 module is not available')\n\ntry:\n    # Only for Python 3.3+\n    import lzma  # noqa\n    SUPPORTED_EXTENSIONS += XZ_EXTENSIONS\nexcept ImportError:\n    logger.debug('lzma module is not available')\n\n\ndef ensure_dir(path):\n    # type: (AnyStr) -> None\n    \"\"\"os.path.makedirs without EEXIST.\"\"\"\n    try:\n        os.makedirs(path)\n    except OSError as e:\n        if e.errno != errno.EEXIST:\n            raise\n\n\ndef get_prog():\n    # type: () -> str\n    try:\n        prog = os.path.basename(sys.argv[0])\n        if prog in ('__main__.py', '-c'):\n            return \"%s -m pip\" % sys.executable\n        else:\n            return prog\n    except (AttributeError, TypeError, IndexError):\n        pass\n    return 'pip'\n\n\n# Retry every half second for up to 3 seconds\n@retry(stop_max_delay=3000, wait_fixed=500)\ndef rmtree(dir, ignore_errors=False):\n    # type: (str, bool) -> None\n    shutil.rmtree(dir, ignore_errors=ignore_errors,\n                  onerror=rmtree_errorhandler)\n\n\ndef rmtree_errorhandler(func, path, exc_info):\n    \"\"\"On Windows, the files in .svn are read-only, so when rmtree() tries to\n    remove them, an exception is thrown.  We catch that here, remove the\n    read-only attribute, and hopefully continue without problems.\"\"\"\n    # if file type currently read only\n    if os.stat(path).st_mode & stat.S_IREAD:\n        # convert to read/write\n        os.chmod(path, stat.S_IWRITE)\n        # use the original function to repeat the operation\n        func(path)\n        return\n    else:\n        raise\n\n\ndef display_path(path):\n    # type: (Union[str, Text]) -> str\n    \"\"\"Gives the display value for a given path, making it relative to cwd\n    if possible.\"\"\"\n    path = os.path.normcase(os.path.abspath(path))\n    if sys.version_info[0] == 2:\n        path = path.decode(sys.getfilesystemencoding(), 'replace')\n        path = path.encode(sys.getdefaultencoding(), 'replace')\n    if path.startswith(os.getcwd() + os.path.sep):\n        path = '.' + path[len(os.getcwd()):]\n    return path\n\n\ndef backup_dir(dir, ext='.bak'):\n    # type: (str, str) -> str\n    \"\"\"Figure out the name of a directory to back up the given dir to\n    (adding .bak, .bak2, etc)\"\"\"\n    n = 1\n    extension = ext\n    while os.path.exists(dir + extension):\n        n += 1\n        extension = ext + str(n)\n    return dir + extension\n\n\ndef ask_path_exists(message, options):\n    # type: (str, Iterable[str]) -> str\n    for action in os.environ.get('PIP_EXISTS_ACTION', '').split():\n        if action in options:\n            return action\n    return ask(message, options)\n\n\ndef ask(message, options):\n    # type: (str, Iterable[str]) -> str\n    \"\"\"Ask the message interactively, with the given possible responses\"\"\"\n    while 1:\n        if os.environ.get('PIP_NO_INPUT'):\n            raise Exception(\n                'No input was expected ($PIP_NO_INPUT set); question: %s' %\n                message\n            )\n        response = input(message)\n        response = response.strip().lower()\n        if response not in options:\n            print(\n                'Your response (%r) was not one of the expected responses: '\n                '%s' % (response, ', '.join(options))\n            )\n        else:\n            return response\n\n\ndef format_size(bytes):\n    # type: (float) -> str\n    if bytes > 1000 * 1000:\n        return '%.1fMB' % (bytes / 1000.0 / 1000)\n    elif bytes > 10 * 1000:\n        return '%ikB' % (bytes / 1000)\n    elif bytes > 1000:\n        return '%.1fkB' % (bytes / 1000.0)\n    else:\n        return '%ibytes' % bytes\n\n\ndef is_installable_dir(path):\n    # type: (str) -> bool\n    \"\"\"Is path is a directory containing setup.py or pyproject.toml?\n    \"\"\"\n    if not os.path.isdir(path):\n        return False\n    setup_py = os.path.join(path, 'setup.py')\n    if os.path.isfile(setup_py):\n        return True\n    pyproject_toml = os.path.join(path, 'pyproject.toml')\n    if os.path.isfile(pyproject_toml):\n        return True\n    return False\n\n\ndef is_svn_page(html):\n    # type: (Union[str, Text]) -> Optional[Match[Union[str, Text]]]\n    \"\"\"\n    Returns true if the page appears to be the index page of an svn repository\n    \"\"\"\n    return (re.search(r'<title>[^<]*Revision \\d+:', html) and\n            re.search(r'Powered by (?:<a[^>]*?>)?Subversion', html, re.I))\n\n\ndef file_contents(filename):\n    # type: (str) -> Text\n    with open(filename, 'rb') as fp:\n        return fp.read().decode('utf-8')\n\n\ndef read_chunks(file, size=io.DEFAULT_BUFFER_SIZE):\n    \"\"\"Yield pieces of data from a file-like object until EOF.\"\"\"\n    while True:\n        chunk = file.read(size)\n        if not chunk:\n            break\n        yield chunk\n\n\ndef split_leading_dir(path):\n    # type: (Union[str, Text]) -> List[Union[str, Text]]\n    path = path.lstrip('/').lstrip('\\\\')\n    if '/' in path and (('\\\\' in path and path.find('/') < path.find('\\\\')) or\n                        '\\\\' not in path):\n        return path.split('/', 1)\n    elif '\\\\' in path:\n        return path.split('\\\\', 1)\n    else:\n        return [path, '']\n\n\ndef has_leading_dir(paths):\n    # type: (Iterable[Union[str, Text]]) -> bool\n    \"\"\"Returns true if all the paths have the same leading path name\n    (i.e., everything is in one subdirectory in an archive)\"\"\"\n    common_prefix = None\n    for path in paths:\n        prefix, rest = split_leading_dir(path)\n        if not prefix:\n            return False\n        elif common_prefix is None:\n            common_prefix = prefix\n        elif prefix != common_prefix:\n            return False\n    return True\n\n\ndef normalize_path(path, resolve_symlinks=True):\n    # type: (str, bool) -> str\n    \"\"\"\n    Convert a path to its canonical, case-normalized, absolute version.\n\n    \"\"\"\n    path = expanduser(path)\n    if resolve_symlinks:\n        path = os.path.realpath(path)\n    else:\n        path = os.path.abspath(path)\n    return os.path.normcase(path)\n\n\ndef splitext(path):\n    # type: (str) -> Tuple[str, str]\n    \"\"\"Like os.path.splitext, but take off .tar too\"\"\"\n    base, ext = posixpath.splitext(path)\n    if base.lower().endswith('.tar'):\n        ext = base[-4:] + ext\n        base = base[:-4]\n    return base, ext\n\n\ndef renames(old, new):\n    # type: (str, str) -> None\n    \"\"\"Like os.renames(), but handles renaming across devices.\"\"\"\n    # Implementation borrowed from os.renames().\n    head, tail = os.path.split(new)\n    if head and tail and not os.path.exists(head):\n        os.makedirs(head)\n\n    shutil.move(old, new)\n\n    head, tail = os.path.split(old)\n    if head and tail:\n        try:\n            os.removedirs(head)\n        except OSError:\n            pass\n\n\ndef is_local(path):\n    # type: (str) -> bool\n    \"\"\"\n    Return True if path is within sys.prefix, if we're running in a virtualenv.\n\n    If we're not in a virtualenv, all paths are considered \"local.\"\n\n    \"\"\"\n    if not running_under_virtualenv():\n        return True\n    return normalize_path(path).startswith(normalize_path(sys.prefix))\n\n\ndef dist_is_local(dist):\n    # type: (Distribution) -> bool\n    \"\"\"\n    Return True if given Distribution object is installed locally\n    (i.e. within current virtualenv).\n\n    Always True if we're not in a virtualenv.\n\n    \"\"\"\n    return is_local(dist_location(dist))\n\n\ndef dist_in_usersite(dist):\n    # type: (Distribution) -> bool\n    \"\"\"\n    Return True if given Distribution is installed in user site.\n    \"\"\"\n    norm_path = normalize_path(dist_location(dist))\n    return norm_path.startswith(normalize_path(user_site))\n\n\ndef dist_in_site_packages(dist):\n    # type: (Distribution) -> bool\n    \"\"\"\n    Return True if given Distribution is installed in\n    sysconfig.get_python_lib().\n    \"\"\"\n    return normalize_path(\n        dist_location(dist)\n    ).startswith(normalize_path(site_packages))\n\n\ndef dist_is_editable(dist):\n    # type: (Distribution) -> bool\n    \"\"\"\n    Return True if given Distribution is an editable install.\n    \"\"\"\n    for path_item in sys.path:\n        egg_link = os.path.join(path_item, dist.project_name + '.egg-link')\n        if os.path.isfile(egg_link):\n            return True\n    return False\n\n\ndef get_installed_distributions(local_only=True,\n                                skip=stdlib_pkgs,\n                                include_editables=True,\n                                editables_only=False,\n                                user_only=False):\n    # type: (bool, Container[str], bool, bool, bool) -> List[Distribution]\n    \"\"\"\n    Return a list of installed Distribution objects.\n\n    If ``local_only`` is True (default), only return installations\n    local to the current virtualenv, if in a virtualenv.\n\n    ``skip`` argument is an iterable of lower-case project names to\n    ignore; defaults to stdlib_pkgs\n\n    If ``include_editables`` is False, don't report editables.\n\n    If ``editables_only`` is True , only report editables.\n\n    If ``user_only`` is True , only report installations in the user\n    site directory.\n\n    \"\"\"\n    if local_only:\n        local_test = dist_is_local\n    else:\n        def local_test(d):\n            return True\n\n    if include_editables:\n        def editable_test(d):\n            return True\n    else:\n        def editable_test(d):\n            return not dist_is_editable(d)\n\n    if editables_only:\n        def editables_only_test(d):\n            return dist_is_editable(d)\n    else:\n        def editables_only_test(d):\n            return True\n\n    if user_only:\n        user_test = dist_in_usersite\n    else:\n        def user_test(d):\n            return True\n\n    # because of pkg_resources vendoring, mypy cannot find stub in typeshed\n    return [d for d in pkg_resources.working_set  # type: ignore\n            if local_test(d) and\n            d.key not in skip and\n            editable_test(d) and\n            editables_only_test(d) and\n            user_test(d)\n            ]\n\n\ndef egg_link_path(dist):\n    # type: (Distribution) -> Optional[str]\n    \"\"\"\n    Return the path for the .egg-link file if it exists, otherwise, None.\n\n    There's 3 scenarios:\n    1) not in a virtualenv\n       try to find in site.USER_SITE, then site_packages\n    2) in a no-global virtualenv\n       try to find in site_packages\n    3) in a yes-global virtualenv\n       try to find in site_packages, then site.USER_SITE\n       (don't look in global location)\n\n    For #1 and #3, there could be odd cases, where there's an egg-link in 2\n    locations.\n\n    This method will just return the first one found.\n    \"\"\"\n    sites = []\n    if running_under_virtualenv():\n        if virtualenv_no_global():\n            sites.append(site_packages)\n        else:\n            sites.append(site_packages)\n            if user_site:\n                sites.append(user_site)\n    else:\n        if user_site:\n            sites.append(user_site)\n        sites.append(site_packages)\n\n    for site in sites:\n        egglink = os.path.join(site, dist.project_name) + '.egg-link'\n        if os.path.isfile(egglink):\n            return egglink\n    return None\n\n\ndef dist_location(dist):\n    # type: (Distribution) -> str\n    \"\"\"\n    Get the site-packages location of this distribution. Generally\n    this is dist.location, except in the case of develop-installed\n    packages, where dist.location is the source code location, and we\n    want to know where the egg-link file is.\n\n    \"\"\"\n    egg_link = egg_link_path(dist)\n    if egg_link:\n        return egg_link\n    return dist.location\n\n\ndef current_umask():\n    \"\"\"Get the current umask which involves having to set it temporarily.\"\"\"\n    mask = os.umask(0)\n    os.umask(mask)\n    return mask\n\n\ndef unzip_file(filename, location, flatten=True):\n    # type: (str, str, bool) -> None\n    \"\"\"\n    Unzip the file (with path `filename`) to the destination `location`.  All\n    files are written based on system defaults and umask (i.e. permissions are\n    not preserved), except that regular file members with any execute\n    permissions (user, group, or world) have \"chmod +x\" applied after being\n    written. Note that for windows, any execute changes using os.chmod are\n    no-ops per the python docs.\n    \"\"\"\n    ensure_dir(location)\n    zipfp = open(filename, 'rb')\n    try:\n        zip = zipfile.ZipFile(zipfp, allowZip64=True)\n        leading = has_leading_dir(zip.namelist()) and flatten\n        for info in zip.infolist():\n            name = info.filename\n            fn = name\n            if leading:\n                fn = split_leading_dir(name)[1]\n            fn = os.path.join(location, fn)\n            dir = os.path.dirname(fn)\n            if fn.endswith('/') or fn.endswith('\\\\'):\n                # A directory\n                ensure_dir(fn)\n            else:\n                ensure_dir(dir)\n                # Don't use read() to avoid allocating an arbitrarily large\n                # chunk of memory for the file's content\n                fp = zip.open(name)\n                try:\n                    with open(fn, 'wb') as destfp:\n                        shutil.copyfileobj(fp, destfp)\n                finally:\n                    fp.close()\n                    mode = info.external_attr >> 16\n                    # if mode and regular file and any execute permissions for\n                    # user/group/world?\n                    if mode and stat.S_ISREG(mode) and mode & 0o111:\n                        # make dest file have execute for user/group/world\n                        # (chmod +x) no-op on windows per python docs\n                        os.chmod(fn, (0o777 - current_umask() | 0o111))\n    finally:\n        zipfp.close()\n\n\ndef untar_file(filename, location):\n    # type: (str, str) -> None\n    \"\"\"\n    Untar the file (with path `filename`) to the destination `location`.\n    All files are written based on system defaults and umask (i.e. permissions\n    are not preserved), except that regular file members with any execute\n    permissions (user, group, or world) have \"chmod +x\" applied after being\n    written.  Note that for windows, any execute changes using os.chmod are\n    no-ops per the python docs.\n    \"\"\"\n    ensure_dir(location)\n    if filename.lower().endswith('.gz') or filename.lower().endswith('.tgz'):\n        mode = 'r:gz'\n    elif filename.lower().endswith(BZ2_EXTENSIONS):\n        mode = 'r:bz2'\n    elif filename.lower().endswith(XZ_EXTENSIONS):\n        mode = 'r:xz'\n    elif filename.lower().endswith('.tar'):\n        mode = 'r'\n    else:\n        logger.warning(\n            'Cannot determine compression type for file %s', filename,\n        )\n        mode = 'r:*'\n    tar = tarfile.open(filename, mode)\n    try:\n        leading = has_leading_dir([\n            member.name for member in tar.getmembers()\n        ])\n        for member in tar.getmembers():\n            fn = member.name\n            if leading:\n                # https://github.com/python/mypy/issues/1174\n                fn = split_leading_dir(fn)[1]  # type: ignore\n            path = os.path.join(location, fn)\n            if member.isdir():\n                ensure_dir(path)\n            elif member.issym():\n                try:\n                    # https://github.com/python/typeshed/issues/2673\n                    tar._extract_member(member, path)  # type: ignore\n                except Exception as exc:\n                    # Some corrupt tar files seem to produce this\n                    # (specifically bad symlinks)\n                    logger.warning(\n                        'In the tar file %s the member %s is invalid: %s',\n                        filename, member.name, exc,\n                    )\n                    continue\n            else:\n                try:\n                    fp = tar.extractfile(member)\n                except (KeyError, AttributeError) as exc:\n                    # Some corrupt tar files seem to produce this\n                    # (specifically bad symlinks)\n                    logger.warning(\n                        'In the tar file %s the member %s is invalid: %s',\n                        filename, member.name, exc,\n                    )\n                    continue\n                ensure_dir(os.path.dirname(path))\n                with open(path, 'wb') as destfp:\n                    shutil.copyfileobj(fp, destfp)\n                fp.close()\n                # Update the timestamp (useful for cython compiled files)\n                # https://github.com/python/typeshed/issues/2673\n                tar.utime(member, path)  # type: ignore\n                # member have any execute permissions for user/group/world?\n                if member.mode & 0o111:\n                    # make dest file have execute for user/group/world\n                    # no-op on windows per python docs\n                    os.chmod(path, (0o777 - current_umask() | 0o111))\n    finally:\n        tar.close()\n\n\ndef unpack_file(\n    filename,  # type: str\n    location,  # type: str\n    content_type,  # type: Optional[str]\n    link  # type: Optional[Link]\n):\n    # type: (...) -> None\n    filename = os.path.realpath(filename)\n    if (content_type == 'application/zip' or\n            filename.lower().endswith(ZIP_EXTENSIONS) or\n            zipfile.is_zipfile(filename)):\n        unzip_file(\n            filename,\n            location,\n            flatten=not filename.endswith('.whl')\n        )\n    elif (content_type == 'application/x-gzip' or\n            tarfile.is_tarfile(filename) or\n            filename.lower().endswith(\n                TAR_EXTENSIONS + BZ2_EXTENSIONS + XZ_EXTENSIONS)):\n        untar_file(filename, location)\n    elif (content_type and content_type.startswith('text/html') and\n            is_svn_page(file_contents(filename))):\n        # We don't really care about this\n        from pip._internal.vcs.subversion import Subversion\n        Subversion('svn+' + link.url).unpack(location)\n    else:\n        # FIXME: handle?\n        # FIXME: magic signatures?\n        logger.critical(\n            'Cannot unpack file %s (downloaded from %s, content-type: %s); '\n            'cannot detect archive format',\n            filename, location, content_type,\n        )\n        raise InstallationError(\n            'Cannot determine archive format of %s' % location\n        )\n\n\ndef call_subprocess(\n    cmd,  # type: List[str]\n    show_stdout=True,  # type: bool\n    cwd=None,  # type: Optional[str]\n    on_returncode='raise',  # type: str\n    extra_ok_returncodes=None,  # type: Optional[Iterable[int]]\n    command_desc=None,  # type: Optional[str]\n    extra_environ=None,  # type: Optional[Mapping[str, Any]]\n    unset_environ=None,  # type: Optional[Iterable[str]]\n    spinner=None  # type: Optional[SpinnerInterface]\n):\n    # type: (...) -> Optional[Text]\n    \"\"\"\n    Args:\n      extra_ok_returncodes: an iterable of integer return codes that are\n        acceptable, in addition to 0. Defaults to None, which means [].\n      unset_environ: an iterable of environment variable names to unset\n        prior to calling subprocess.Popen().\n    \"\"\"\n    if extra_ok_returncodes is None:\n        extra_ok_returncodes = []\n    if unset_environ is None:\n        unset_environ = []\n    # This function's handling of subprocess output is confusing and I\n    # previously broke it terribly, so as penance I will write a long comment\n    # explaining things.\n    #\n    # The obvious thing that affects output is the show_stdout=\n    # kwarg. show_stdout=True means, let the subprocess write directly to our\n    # stdout. Even though it is nominally the default, it is almost never used\n    # inside pip (and should not be used in new code without a very good\n    # reason); as of 2016-02-22 it is only used in a few places inside the VCS\n    # wrapper code. Ideally we should get rid of it entirely, because it\n    # creates a lot of complexity here for a rarely used feature.\n    #\n    # Most places in pip set show_stdout=False. What this means is:\n    # - We connect the child stdout to a pipe, which we read.\n    # - By default, we hide the output but show a spinner -- unless the\n    #   subprocess exits with an error, in which case we show the output.\n    # - If the --verbose option was passed (= loglevel is DEBUG), then we show\n    #   the output unconditionally. (But in this case we don't want to show\n    #   the output a second time if it turns out that there was an error.)\n    #\n    # stderr is always merged with stdout (even if show_stdout=True).\n    if show_stdout:\n        stdout = None\n    else:\n        stdout = subprocess.PIPE\n    if command_desc is None:\n        cmd_parts = []\n        for part in cmd:\n            if ' ' in part or '\\n' in part or '\"' in part or \"'\" in part:\n                part = '\"%s\"' % part.replace('\"', '\\\\\"')\n            cmd_parts.append(part)\n        command_desc = ' '.join(cmd_parts)\n    logger.debug(\"Running command %s\", command_desc)\n    env = os.environ.copy()\n    if extra_environ:\n        env.update(extra_environ)\n    for name in unset_environ:\n        env.pop(name, None)\n    try:\n        proc = subprocess.Popen(\n            cmd, stderr=subprocess.STDOUT, stdin=subprocess.PIPE,\n            stdout=stdout, cwd=cwd, env=env,\n        )\n        proc.stdin.close()\n    except Exception as exc:\n        logger.critical(\n            \"Error %s while executing command %s\", exc, command_desc,\n        )\n        raise\n    all_output = []\n    if stdout is not None:\n        while True:\n            line = console_to_str(proc.stdout.readline())\n            if not line:\n                break\n            line = line.rstrip()\n            all_output.append(line + '\\n')\n            if logger.getEffectiveLevel() <= std_logging.DEBUG:\n                # Show the line immediately\n                logger.debug(line)\n            else:\n                # Update the spinner\n                if spinner is not None:\n                    spinner.spin()\n    try:\n        proc.wait()\n    finally:\n        if proc.stdout:\n            proc.stdout.close()\n    if spinner is not None:\n        if proc.returncode:\n            spinner.finish(\"error\")\n        else:\n            spinner.finish(\"done\")\n    if proc.returncode and proc.returncode not in extra_ok_returncodes:\n        if on_returncode == 'raise':\n            if (logger.getEffectiveLevel() > std_logging.DEBUG and\n                    not show_stdout):\n                logger.info(\n                    'Complete output from command %s:', command_desc,\n                )\n                logger.info(\n                    ''.join(all_output) +\n                    '\\n----------------------------------------'\n                )\n            raise InstallationError(\n                'Command \"%s\" failed with error code %s in %s'\n                % (command_desc, proc.returncode, cwd))\n        elif on_returncode == 'warn':\n            logger.warning(\n                'Command \"%s\" had error code %s in %s',\n                command_desc, proc.returncode, cwd,\n            )\n        elif on_returncode == 'ignore':\n            pass\n        else:\n            raise ValueError('Invalid value: on_returncode=%s' %\n                             repr(on_returncode))\n    if not show_stdout:\n        return ''.join(all_output)\n    return None\n\n\ndef read_text_file(filename):\n    # type: (str) -> str\n    \"\"\"Return the contents of *filename*.\n\n    Try to decode the file contents with utf-8, the preferred system encoding\n    (e.g., cp1252 on some Windows machines), and latin1, in that order.\n    Decoding a byte string with latin1 will never raise an error. In the worst\n    case, the returned string will contain some garbage characters.\n\n    \"\"\"\n    with open(filename, 'rb') as fp:\n        data = fp.read()\n\n    encodings = ['utf-8', locale.getpreferredencoding(False), 'latin1']\n    for enc in encodings:\n        try:\n            # https://github.com/python/mypy/issues/1174\n            data = data.decode(enc)  # type: ignore\n        except UnicodeDecodeError:\n            continue\n        break\n\n    assert not isinstance(data, bytes)  # Latin1 should have worked.\n    return data\n\n\ndef _make_build_dir(build_dir):\n    os.makedirs(build_dir)\n    write_delete_marker_file(build_dir)\n\n\nclass FakeFile(object):\n    \"\"\"Wrap a list of lines in an object with readline() to make\n    ConfigParser happy.\"\"\"\n    def __init__(self, lines):\n        self._gen = (l for l in lines)\n\n    def readline(self):\n        try:\n            try:\n                return next(self._gen)\n            except NameError:\n                return self._gen.next()\n        except StopIteration:\n            return ''\n\n    def __iter__(self):\n        return self._gen\n\n\nclass StreamWrapper(StringIO):\n\n    @classmethod\n    def from_stream(cls, orig_stream):\n        cls.orig_stream = orig_stream\n        return cls()\n\n    # compileall.compile_dir() needs stdout.encoding to print to stdout\n    @property\n    def encoding(self):\n        return self.orig_stream.encoding\n\n\n@contextlib.contextmanager\ndef captured_output(stream_name):\n    \"\"\"Return a context manager used by captured_stdout/stdin/stderr\n    that temporarily replaces the sys stream *stream_name* with a StringIO.\n\n    Taken from Lib/support/__init__.py in the CPython repo.\n    \"\"\"\n    orig_stdout = getattr(sys, stream_name)\n    setattr(sys, stream_name, StreamWrapper.from_stream(orig_stdout))\n    try:\n        yield getattr(sys, stream_name)\n    finally:\n        setattr(sys, stream_name, orig_stdout)\n\n\ndef captured_stdout():\n    \"\"\"Capture the output of sys.stdout:\n\n       with captured_stdout() as stdout:\n           print('hello')\n       self.assertEqual(stdout.getvalue(), 'hello\\n')\n\n    Taken from Lib/support/__init__.py in the CPython repo.\n    \"\"\"\n    return captured_output('stdout')\n\n\ndef captured_stderr():\n    \"\"\"\n    See captured_stdout().\n    \"\"\"\n    return captured_output('stderr')\n\n\nclass cached_property(object):\n    \"\"\"A property that is only computed once per instance and then replaces\n       itself with an ordinary attribute. Deleting the attribute resets the\n       property.\n\n       Source: https://github.com/bottlepy/bottle/blob/0.11.5/bottle.py#L175\n    \"\"\"\n\n    def __init__(self, func):\n        self.__doc__ = getattr(func, '__doc__')\n        self.func = func\n\n    def __get__(self, obj, cls):\n        if obj is None:\n            # We're being accessed from the class itself, not from an object\n            return self\n        value = obj.__dict__[self.func.__name__] = self.func(obj)\n        return value\n\n\ndef get_installed_version(dist_name, working_set=None):\n    \"\"\"Get the installed version of dist_name avoiding pkg_resources cache\"\"\"\n    # Create a requirement that we'll look for inside of setuptools.\n    req = pkg_resources.Requirement.parse(dist_name)\n\n    if working_set is None:\n        # We want to avoid having this cached, so we need to construct a new\n        # working set each time.\n        working_set = pkg_resources.WorkingSet()\n\n    # Get the installed distribution from our working set\n    dist = working_set.find(req)\n\n    # Check to see if we got an installed distribution or not, if we did\n    # we want to return it's version.\n    return dist.version if dist else None\n\n\ndef consume(iterator):\n    \"\"\"Consume an iterable at C speed.\"\"\"\n    deque(iterator, maxlen=0)\n\n\n# Simulates an enum\ndef enum(*sequential, **named):\n    enums = dict(zip(sequential, range(len(sequential))), **named)\n    reverse = {value: key for key, value in enums.items()}\n    enums['reverse_mapping'] = reverse\n    return type('Enum', (), enums)\n\n\ndef make_vcs_requirement_url(repo_url, rev, project_name, subdir=None):\n    \"\"\"\n    Return the URL for a VCS requirement.\n\n    Args:\n      repo_url: the remote VCS url, with any needed VCS prefix (e.g. \"git+\").\n      project_name: the (unescaped) project name.\n    \"\"\"\n    egg_project_name = pkg_resources.to_filename(project_name)\n    req = '{}@{}#egg={}'.format(repo_url, rev, egg_project_name)\n    if subdir:\n        req += '&subdirectory={}'.format(subdir)\n\n    return req\n\n\ndef split_auth_from_netloc(netloc):\n    \"\"\"\n    Parse out and remove the auth information from a netloc.\n\n    Returns: (netloc, (username, password)).\n    \"\"\"\n    if '@' not in netloc:\n        return netloc, (None, None)\n\n    # Split from the right because that's how urllib.parse.urlsplit()\n    # behaves if more than one @ is present (which can be checked using\n    # the password attribute of urlsplit()'s return value).\n    auth, netloc = netloc.rsplit('@', 1)\n    if ':' in auth:\n        # Split from the left because that's how urllib.parse.urlsplit()\n        # behaves if more than one : is present (which again can be checked\n        # using the password attribute of the return value)\n        user_pass = auth.split(':', 1)\n    else:\n        user_pass = auth, None\n\n    user_pass = tuple(\n        None if x is None else urllib_unquote(x) for x in user_pass\n    )\n\n    return netloc, user_pass\n\n\ndef redact_netloc(netloc):\n    # type: (str) -> str\n    \"\"\"\n    Replace the password in a netloc with \"****\", if it exists.\n\n    For example, \"user:pass@example.com\" returns \"user:****@example.com\".\n    \"\"\"\n    netloc, (user, password) = split_auth_from_netloc(netloc)\n    if user is None:\n        return netloc\n    password = '' if password is None else ':****'\n    return '{user}{password}@{netloc}'.format(user=urllib_parse.quote(user),\n                                              password=password,\n                                              netloc=netloc)\n\n\ndef _transform_url(url, transform_netloc):\n    purl = urllib_parse.urlsplit(url)\n    netloc = transform_netloc(purl.netloc)\n    # stripped url\n    url_pieces = (\n        purl.scheme, netloc, purl.path, purl.query, purl.fragment\n    )\n    surl = urllib_parse.urlunsplit(url_pieces)\n    return surl\n\n\ndef _get_netloc(netloc):\n    return split_auth_from_netloc(netloc)[0]\n\n\ndef remove_auth_from_url(url):\n    # type: (str) -> str\n    # Return a copy of url with 'username:password@' removed.\n    # username/pass params are passed to subversion through flags\n    # and are not recognized in the url.\n    return _transform_url(url, _get_netloc)\n\n\ndef redact_password_from_url(url):\n    # type: (str) -> str\n    \"\"\"Replace the password in a given url with ****.\"\"\"\n    return _transform_url(url, redact_netloc)\n\n\ndef protect_pip_from_modification_on_windows(modifying_pip):\n    \"\"\"Protection of pip.exe from modification on Windows\n\n    On Windows, any operation modifying pip should be run as:\n        python -m pip ...\n    \"\"\"\n    pip_names = [\n        \"pip.exe\",\n        \"pip{}.exe\".format(sys.version_info[0]),\n        \"pip{}.{}.exe\".format(*sys.version_info[:2])\n    ]\n\n    # See https://github.com/pypa/pip/issues/1299 for more discussion\n    should_show_use_python_msg = (\n        modifying_pip and\n        WINDOWS and\n        os.path.basename(sys.argv[0]) in pip_names\n    )\n\n    if should_show_use_python_msg:\n        new_command = [\n            sys.executable, \"-m\", \"pip\"\n        ] + sys.argv[1:]\n        raise CommandError(\n            'To modify pip, please run the following command:\\n{}'\n            .format(\" \".join(new_command))\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/models.py",
    "content": "\"\"\"Utilities for defining models\n\"\"\"\n\nimport operator\n\n\nclass KeyBasedCompareMixin(object):\n    \"\"\"Provides comparision capabilities that is based on a key\n    \"\"\"\n\n    def __init__(self, key, defining_class):\n        self._compare_key = key\n        self._defining_class = defining_class\n\n    def __hash__(self):\n        return hash(self._compare_key)\n\n    def __lt__(self, other):\n        return self._compare(other, operator.__lt__)\n\n    def __le__(self, other):\n        return self._compare(other, operator.__le__)\n\n    def __gt__(self, other):\n        return self._compare(other, operator.__gt__)\n\n    def __ge__(self, other):\n        return self._compare(other, operator.__ge__)\n\n    def __eq__(self, other):\n        return self._compare(other, operator.__eq__)\n\n    def __ne__(self, other):\n        return self._compare(other, operator.__ne__)\n\n    def _compare(self, other, method):\n        if not isinstance(other, self._defining_class):\n            return NotImplemented\n\n        return method(self._compare_key, other._compare_key)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/outdated.py",
    "content": "from __future__ import absolute_import\n\nimport datetime\nimport json\nimport logging\nimport os.path\nimport sys\n\nfrom pip._vendor import lockfile, pkg_resources\nfrom pip._vendor.packaging import version as packaging_version\n\nfrom pip._internal.index import PackageFinder\nfrom pip._internal.utils.compat import WINDOWS\nfrom pip._internal.utils.filesystem import check_path_owner\nfrom pip._internal.utils.misc import ensure_dir, get_installed_version\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    import optparse  # noqa: F401\n    from typing import Any, Dict  # noqa: F401\n    from pip._internal.download import PipSession  # noqa: F401\n\n\nSELFCHECK_DATE_FMT = \"%Y-%m-%dT%H:%M:%SZ\"\n\n\nlogger = logging.getLogger(__name__)\n\n\nclass SelfCheckState(object):\n    def __init__(self, cache_dir):\n        # type: (str) -> None\n        self.state = {}  # type: Dict[str, Any]\n        self.statefile_path = None\n\n        # Try to load the existing state\n        if cache_dir:\n            self.statefile_path = os.path.join(cache_dir, \"selfcheck.json\")\n            try:\n                with open(self.statefile_path) as statefile:\n                    self.state = json.load(statefile)[sys.prefix]\n            except (IOError, ValueError, KeyError):\n                # Explicitly suppressing exceptions, since we don't want to\n                # error out if the cache file is invalid.\n                pass\n\n    def save(self, pypi_version, current_time):\n        # type: (str, datetime.datetime) -> None\n        # If we do not have a path to cache in, don't bother saving.\n        if not self.statefile_path:\n            return\n\n        # Check to make sure that we own the directory\n        if not check_path_owner(os.path.dirname(self.statefile_path)):\n            return\n\n        # Now that we've ensured the directory is owned by this user, we'll go\n        # ahead and make sure that all our directories are created.\n        ensure_dir(os.path.dirname(self.statefile_path))\n\n        # Attempt to write out our version check file\n        with lockfile.LockFile(self.statefile_path):\n            if os.path.exists(self.statefile_path):\n                with open(self.statefile_path) as statefile:\n                    state = json.load(statefile)\n            else:\n                state = {}\n\n            state[sys.prefix] = {\n                \"last_check\": current_time.strftime(SELFCHECK_DATE_FMT),\n                \"pypi_version\": pypi_version,\n            }\n\n            with open(self.statefile_path, \"w\") as statefile:\n                json.dump(state, statefile, sort_keys=True,\n                          separators=(\",\", \":\"))\n\n\ndef was_installed_by_pip(pkg):\n    # type: (str) -> bool\n    \"\"\"Checks whether pkg was installed by pip\n\n    This is used not to display the upgrade message when pip is in fact\n    installed by system package manager, such as dnf on Fedora.\n    \"\"\"\n    try:\n        dist = pkg_resources.get_distribution(pkg)\n        return (dist.has_metadata('INSTALLER') and\n                'pip' in dist.get_metadata_lines('INSTALLER'))\n    except pkg_resources.DistributionNotFound:\n        return False\n\n\ndef pip_version_check(session, options):\n    # type: (PipSession, optparse.Values) -> None\n    \"\"\"Check for an update for pip.\n\n    Limit the frequency of checks to once per week. State is stored either in\n    the active virtualenv or in the user's USER_CACHE_DIR keyed off the prefix\n    of the pip script path.\n    \"\"\"\n    installed_version = get_installed_version(\"pip\")\n    if not installed_version:\n        return\n\n    pip_version = packaging_version.parse(installed_version)\n    pypi_version = None\n\n    try:\n        state = SelfCheckState(cache_dir=options.cache_dir)\n\n        current_time = datetime.datetime.utcnow()\n        # Determine if we need to refresh the state\n        if \"last_check\" in state.state and \"pypi_version\" in state.state:\n            last_check = datetime.datetime.strptime(\n                state.state[\"last_check\"],\n                SELFCHECK_DATE_FMT\n            )\n            if (current_time - last_check).total_seconds() < 7 * 24 * 60 * 60:\n                pypi_version = state.state[\"pypi_version\"]\n\n        # Refresh the version if we need to or just see if we need to warn\n        if pypi_version is None:\n            # Lets use PackageFinder to see what the latest pip version is\n            finder = PackageFinder(\n                find_links=options.find_links,\n                index_urls=[options.index_url] + options.extra_index_urls,\n                allow_all_prereleases=False,  # Explicitly set to False\n                trusted_hosts=options.trusted_hosts,\n                session=session,\n            )\n            all_candidates = finder.find_all_candidates(\"pip\")\n            if not all_candidates:\n                return\n            pypi_version = str(\n                max(all_candidates, key=lambda c: c.version).version\n            )\n\n            # save that we've performed a check\n            state.save(pypi_version, current_time)\n\n        remote_version = packaging_version.parse(pypi_version)\n\n        # Determine if our pypi_version is older\n        if (pip_version < remote_version and\n                pip_version.base_version != remote_version.base_version and\n                was_installed_by_pip('pip')):\n            # Advise \"python -m pip\" on Windows to avoid issues\n            # with overwriting pip.exe.\n            if WINDOWS:\n                pip_cmd = \"python -m pip\"\n            else:\n                pip_cmd = \"pip\"\n            logger.warning(\n                \"You are using pip version %s, however version %s is \"\n                \"available.\\nYou should consider upgrading via the \"\n                \"'%s install --upgrade pip' command.\",\n                pip_version, pypi_version, pip_cmd\n            )\n    except Exception:\n        logger.debug(\n            \"There was an error checking the latest version of pip\",\n            exc_info=True,\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/packaging.py",
    "content": "from __future__ import absolute_import\n\nimport logging\nimport sys\nfrom email.parser import FeedParser\n\nfrom pip._vendor import pkg_resources\nfrom pip._vendor.packaging import specifiers, version\n\nfrom pip._internal import exceptions\nfrom pip._internal.utils.misc import display_path\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Optional  # noqa: F401\n    from email.message import Message  # noqa: F401\n    from pip._vendor.pkg_resources import Distribution  # noqa: F401\n\n\nlogger = logging.getLogger(__name__)\n\n\ndef check_requires_python(requires_python):\n    # type: (Optional[str]) -> bool\n    \"\"\"\n    Check if the python version in use match the `requires_python` specifier.\n\n    Returns `True` if the version of python in use matches the requirement.\n    Returns `False` if the version of python in use does not matches the\n    requirement.\n\n    Raises an InvalidSpecifier if `requires_python` have an invalid format.\n    \"\"\"\n    if requires_python is None:\n        # The package provides no information\n        return True\n    requires_python_specifier = specifiers.SpecifierSet(requires_python)\n\n    # We only use major.minor.micro\n    python_version = version.parse('.'.join(map(str, sys.version_info[:3])))\n    return python_version in requires_python_specifier\n\n\ndef get_metadata(dist):\n    # type: (Distribution) -> Message\n    if (isinstance(dist, pkg_resources.DistInfoDistribution) and\n            dist.has_metadata('METADATA')):\n        metadata = dist.get_metadata('METADATA')\n    elif dist.has_metadata('PKG-INFO'):\n        metadata = dist.get_metadata('PKG-INFO')\n    else:\n        logger.warning(\"No metadata found in %s\", display_path(dist.location))\n        metadata = ''\n\n    feed_parser = FeedParser()\n    feed_parser.feed(metadata)\n    return feed_parser.close()\n\n\ndef check_dist_requires_python(dist):\n    pkg_info_dict = get_metadata(dist)\n    requires_python = pkg_info_dict.get('Requires-Python')\n    try:\n        if not check_requires_python(requires_python):\n            raise exceptions.UnsupportedPythonVersion(\n                \"%s requires Python '%s' but the running Python is %s\" % (\n                    dist.project_name,\n                    requires_python,\n                    '.'.join(map(str, sys.version_info[:3])),)\n            )\n    except specifiers.InvalidSpecifier as e:\n        logger.warning(\n            \"Package %s has an invalid Requires-Python entry %s - %s\",\n            dist.project_name, requires_python, e,\n        )\n        return\n\n\ndef get_installer(dist):\n    # type: (Distribution) -> str\n    if dist.has_metadata('INSTALLER'):\n        for line in dist.get_metadata_lines('INSTALLER'):\n            if line.strip():\n                return line.strip()\n    return ''\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/setuptools_build.py",
    "content": "# Shim to wrap setup.py invocation with setuptools\nSETUPTOOLS_SHIM = (\n    \"import setuptools, tokenize;__file__=%r;\"\n    \"f=getattr(tokenize, 'open', open)(__file__);\"\n    \"code=f.read().replace('\\\\r\\\\n', '\\\\n');\"\n    \"f.close();\"\n    \"exec(compile(code, __file__, 'exec'))\"\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/temp_dir.py",
    "content": "from __future__ import absolute_import\n\nimport errno\nimport itertools\nimport logging\nimport os.path\nimport tempfile\n\nfrom pip._internal.utils.misc import rmtree\n\nlogger = logging.getLogger(__name__)\n\n\nclass TempDirectory(object):\n    \"\"\"Helper class that owns and cleans up a temporary directory.\n\n    This class can be used as a context manager or as an OO representation of a\n    temporary directory.\n\n    Attributes:\n        path\n            Location to the created temporary directory or None\n        delete\n            Whether the directory should be deleted when exiting\n            (when used as a contextmanager)\n\n    Methods:\n        create()\n            Creates a temporary directory and stores its path in the path\n            attribute.\n        cleanup()\n            Deletes the temporary directory and sets path attribute to None\n\n    When used as a context manager, a temporary directory is created on\n    entering the context and, if the delete attribute is True, on exiting the\n    context the created directory is deleted.\n    \"\"\"\n\n    def __init__(self, path=None, delete=None, kind=\"temp\"):\n        super(TempDirectory, self).__init__()\n\n        if path is None and delete is None:\n            # If we were not given an explicit directory, and we were not given\n            # an explicit delete option, then we'll default to deleting.\n            delete = True\n\n        self.path = path\n        self.delete = delete\n        self.kind = kind\n\n    def __repr__(self):\n        return \"<{} {!r}>\".format(self.__class__.__name__, self.path)\n\n    def __enter__(self):\n        self.create()\n        return self\n\n    def __exit__(self, exc, value, tb):\n        if self.delete:\n            self.cleanup()\n\n    def create(self):\n        \"\"\"Create a temporary directory and store its path in self.path\n        \"\"\"\n        if self.path is not None:\n            logger.debug(\n                \"Skipped creation of temporary directory: {}\".format(self.path)\n            )\n            return\n        # We realpath here because some systems have their default tmpdir\n        # symlinked to another directory.  This tends to confuse build\n        # scripts, so we canonicalize the path by traversing potential\n        # symlinks here.\n        self.path = os.path.realpath(\n            tempfile.mkdtemp(prefix=\"pip-{}-\".format(self.kind))\n        )\n        logger.debug(\"Created temporary directory: {}\".format(self.path))\n\n    def cleanup(self):\n        \"\"\"Remove the temporary directory created and reset state\n        \"\"\"\n        if self.path is not None and os.path.exists(self.path):\n            rmtree(self.path)\n        self.path = None\n\n\nclass AdjacentTempDirectory(TempDirectory):\n    \"\"\"Helper class that creates a temporary directory adjacent to a real one.\n\n    Attributes:\n        original\n            The original directory to create a temp directory for.\n        path\n            After calling create() or entering, contains the full\n            path to the temporary directory.\n        delete\n            Whether the directory should be deleted when exiting\n            (when used as a contextmanager)\n\n    \"\"\"\n    # The characters that may be used to name the temp directory\n    # We always prepend a ~ and then rotate through these until\n    # a usable name is found.\n    # pkg_resources raises a different error for .dist-info folder\n    # with leading '-' and invalid metadata\n    LEADING_CHARS = \"-~.=%0123456789\"\n\n    def __init__(self, original, delete=None):\n        super(AdjacentTempDirectory, self).__init__(delete=delete)\n        self.original = original.rstrip('/\\\\')\n\n    @classmethod\n    def _generate_names(cls, name):\n        \"\"\"Generates a series of temporary names.\n\n        The algorithm replaces the leading characters in the name\n        with ones that are valid filesystem characters, but are not\n        valid package names (for both Python and pip definitions of\n        package).\n        \"\"\"\n        for i in range(1, len(name)):\n            for candidate in itertools.combinations_with_replacement(\n                    cls.LEADING_CHARS, i - 1):\n                new_name = '~' + ''.join(candidate) + name[i:]\n                if new_name != name:\n                    yield new_name\n\n        # If we make it this far, we will have to make a longer name\n        for i in range(len(cls.LEADING_CHARS)):\n            for candidate in itertools.combinations_with_replacement(\n                    cls.LEADING_CHARS, i):\n                new_name = '~' + ''.join(candidate) + name\n                if new_name != name:\n                    yield new_name\n\n    def create(self):\n        root, name = os.path.split(self.original)\n        for candidate in self._generate_names(name):\n            path = os.path.join(root, candidate)\n            try:\n                os.mkdir(path)\n            except OSError as ex:\n                # Continue if the name exists already\n                if ex.errno != errno.EEXIST:\n                    raise\n            else:\n                self.path = os.path.realpath(path)\n                break\n\n        if not self.path:\n            # Final fallback on the default behavior.\n            self.path = os.path.realpath(\n                tempfile.mkdtemp(prefix=\"pip-{}-\".format(self.kind))\n            )\n        logger.debug(\"Created temporary directory: {}\".format(self.path))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/typing.py",
    "content": "\"\"\"For neatly implementing static typing in pip.\n\n`mypy` - the static type analysis tool we use - uses the `typing` module, which\nprovides core functionality fundamental to mypy's functioning.\n\nGenerally, `typing` would be imported at runtime and used in that fashion -\nit acts as a no-op at runtime and does not have any run-time overhead by\ndesign.\n\nAs it turns out, `typing` is not vendorable - it uses separate sources for\nPython 2/Python 3. Thus, this codebase can not expect it to be present.\nTo work around this, mypy allows the typing import to be behind a False-y\noptional to prevent it from running at runtime and type-comments can be used\nto remove the need for the types to be accessible directly during runtime.\n\nThis module provides the False-y guard in a nicely named fashion so that a\ncurious maintainer can reach here to read this.\n\nIn pip, all static-typing related imports should be guarded as follows:\n\n    from pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\n    if MYPY_CHECK_RUNNING:\n        from typing import ...  # noqa: F401\n\nRef: https://github.com/python/mypy/issues/3216\n\"\"\"\n\nMYPY_CHECK_RUNNING = False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/utils/ui.py",
    "content": "from __future__ import absolute_import, division\n\nimport contextlib\nimport itertools\nimport logging\nimport sys\nimport time\nfrom signal import SIGINT, default_int_handler, signal\n\nfrom pip._vendor import six\nfrom pip._vendor.progress.bar import (\n    Bar, ChargingBar, FillingCirclesBar, FillingSquaresBar, IncrementalBar,\n    ShadyBar,\n)\nfrom pip._vendor.progress.helpers import HIDE_CURSOR, SHOW_CURSOR, WritelnMixin\nfrom pip._vendor.progress.spinner import Spinner\n\nfrom pip._internal.utils.compat import WINDOWS\nfrom pip._internal.utils.logging import get_indentation\nfrom pip._internal.utils.misc import format_size\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import Any, Iterator, IO  # noqa: F401\n\ntry:\n    from pip._vendor import colorama\n# Lots of different errors can come from this, including SystemError and\n# ImportError.\nexcept Exception:\n    colorama = None\n\nlogger = logging.getLogger(__name__)\n\n\ndef _select_progress_class(preferred, fallback):\n    encoding = getattr(preferred.file, \"encoding\", None)\n\n    # If we don't know what encoding this file is in, then we'll just assume\n    # that it doesn't support unicode and use the ASCII bar.\n    if not encoding:\n        return fallback\n\n    # Collect all of the possible characters we want to use with the preferred\n    # bar.\n    characters = [\n        getattr(preferred, \"empty_fill\", six.text_type()),\n        getattr(preferred, \"fill\", six.text_type()),\n    ]\n    characters += list(getattr(preferred, \"phases\", []))\n\n    # Try to decode the characters we're using for the bar using the encoding\n    # of the given file, if this works then we'll assume that we can use the\n    # fancier bar and if not we'll fall back to the plaintext bar.\n    try:\n        six.text_type().join(characters).encode(encoding)\n    except UnicodeEncodeError:\n        return fallback\n    else:\n        return preferred\n\n\n_BaseBar = _select_progress_class(IncrementalBar, Bar)  # type: Any\n\n\nclass InterruptibleMixin(object):\n    \"\"\"\n    Helper to ensure that self.finish() gets called on keyboard interrupt.\n\n    This allows downloads to be interrupted without leaving temporary state\n    (like hidden cursors) behind.\n\n    This class is similar to the progress library's existing SigIntMixin\n    helper, but as of version 1.2, that helper has the following problems:\n\n    1. It calls sys.exit().\n    2. It discards the existing SIGINT handler completely.\n    3. It leaves its own handler in place even after an uninterrupted finish,\n       which will have unexpected delayed effects if the user triggers an\n       unrelated keyboard interrupt some time after a progress-displaying\n       download has already completed, for example.\n    \"\"\"\n\n    def __init__(self, *args, **kwargs):\n        \"\"\"\n        Save the original SIGINT handler for later.\n        \"\"\"\n        super(InterruptibleMixin, self).__init__(*args, **kwargs)\n\n        self.original_handler = signal(SIGINT, self.handle_sigint)\n\n        # If signal() returns None, the previous handler was not installed from\n        # Python, and we cannot restore it. This probably should not happen,\n        # but if it does, we must restore something sensible instead, at least.\n        # The least bad option should be Python's default SIGINT handler, which\n        # just raises KeyboardInterrupt.\n        if self.original_handler is None:\n            self.original_handler = default_int_handler\n\n    def finish(self):\n        \"\"\"\n        Restore the original SIGINT handler after finishing.\n\n        This should happen regardless of whether the progress display finishes\n        normally, or gets interrupted.\n        \"\"\"\n        super(InterruptibleMixin, self).finish()\n        signal(SIGINT, self.original_handler)\n\n    def handle_sigint(self, signum, frame):\n        \"\"\"\n        Call self.finish() before delegating to the original SIGINT handler.\n\n        This handler should only be in place while the progress display is\n        active.\n        \"\"\"\n        self.finish()\n        self.original_handler(signum, frame)\n\n\nclass SilentBar(Bar):\n\n    def update(self):\n        pass\n\n\nclass BlueEmojiBar(IncrementalBar):\n\n    suffix = \"%(percent)d%%\"\n    bar_prefix = \" \"\n    bar_suffix = \" \"\n    phases = (u\"\\U0001F539\", u\"\\U0001F537\", u\"\\U0001F535\")  # type: Any\n\n\nclass DownloadProgressMixin(object):\n\n    def __init__(self, *args, **kwargs):\n        super(DownloadProgressMixin, self).__init__(*args, **kwargs)\n        self.message = (\" \" * (get_indentation() + 2)) + self.message\n\n    @property\n    def downloaded(self):\n        return format_size(self.index)\n\n    @property\n    def download_speed(self):\n        # Avoid zero division errors...\n        if self.avg == 0.0:\n            return \"...\"\n        return format_size(1 / self.avg) + \"/s\"\n\n    @property\n    def pretty_eta(self):\n        if self.eta:\n            return \"eta %s\" % self.eta_td\n        return \"\"\n\n    def iter(self, it, n=1):\n        for x in it:\n            yield x\n            self.next(n)\n        self.finish()\n\n\nclass WindowsMixin(object):\n\n    def __init__(self, *args, **kwargs):\n        # The Windows terminal does not support the hide/show cursor ANSI codes\n        # even with colorama. So we'll ensure that hide_cursor is False on\n        # Windows.\n        # This call neds to go before the super() call, so that hide_cursor\n        # is set in time. The base progress bar class writes the \"hide cursor\"\n        # code to the terminal in its init, so if we don't set this soon\n        # enough, we get a \"hide\" with no corresponding \"show\"...\n        if WINDOWS and self.hide_cursor:\n            self.hide_cursor = False\n\n        super(WindowsMixin, self).__init__(*args, **kwargs)\n\n        # Check if we are running on Windows and we have the colorama module,\n        # if we do then wrap our file with it.\n        if WINDOWS and colorama:\n            self.file = colorama.AnsiToWin32(self.file)\n            # The progress code expects to be able to call self.file.isatty()\n            # but the colorama.AnsiToWin32() object doesn't have that, so we'll\n            # add it.\n            self.file.isatty = lambda: self.file.wrapped.isatty()\n            # The progress code expects to be able to call self.file.flush()\n            # but the colorama.AnsiToWin32() object doesn't have that, so we'll\n            # add it.\n            self.file.flush = lambda: self.file.wrapped.flush()\n\n\nclass BaseDownloadProgressBar(WindowsMixin, InterruptibleMixin,\n                              DownloadProgressMixin):\n\n    file = sys.stdout\n    message = \"%(percent)d%%\"\n    suffix = \"%(downloaded)s %(download_speed)s %(pretty_eta)s\"\n\n# NOTE: The \"type: ignore\" comments on the following classes are there to\n#       work around https://github.com/python/typing/issues/241\n\n\nclass DefaultDownloadProgressBar(BaseDownloadProgressBar,\n                                 _BaseBar):\n    pass\n\n\nclass DownloadSilentBar(BaseDownloadProgressBar, SilentBar):  # type: ignore\n    pass\n\n\nclass DownloadIncrementalBar(BaseDownloadProgressBar,  # type: ignore\n                             IncrementalBar):\n    pass\n\n\nclass DownloadChargingBar(BaseDownloadProgressBar,  # type: ignore\n                          ChargingBar):\n    pass\n\n\nclass DownloadShadyBar(BaseDownloadProgressBar, ShadyBar):  # type: ignore\n    pass\n\n\nclass DownloadFillingSquaresBar(BaseDownloadProgressBar,  # type: ignore\n                                FillingSquaresBar):\n    pass\n\n\nclass DownloadFillingCirclesBar(BaseDownloadProgressBar,  # type: ignore\n                                FillingCirclesBar):\n    pass\n\n\nclass DownloadBlueEmojiProgressBar(BaseDownloadProgressBar,  # type: ignore\n                                   BlueEmojiBar):\n    pass\n\n\nclass DownloadProgressSpinner(WindowsMixin, InterruptibleMixin,\n                              DownloadProgressMixin, WritelnMixin, Spinner):\n\n    file = sys.stdout\n    suffix = \"%(downloaded)s %(download_speed)s\"\n\n    def next_phase(self):\n        if not hasattr(self, \"_phaser\"):\n            self._phaser = itertools.cycle(self.phases)\n        return next(self._phaser)\n\n    def update(self):\n        message = self.message % self\n        phase = self.next_phase()\n        suffix = self.suffix % self\n        line = ''.join([\n            message,\n            \" \" if message else \"\",\n            phase,\n            \" \" if suffix else \"\",\n            suffix,\n        ])\n\n        self.writeln(line)\n\n\nBAR_TYPES = {\n    \"off\": (DownloadSilentBar, DownloadSilentBar),\n    \"on\": (DefaultDownloadProgressBar, DownloadProgressSpinner),\n    \"ascii\": (DownloadIncrementalBar, DownloadProgressSpinner),\n    \"pretty\": (DownloadFillingCirclesBar, DownloadProgressSpinner),\n    \"emoji\": (DownloadBlueEmojiProgressBar, DownloadProgressSpinner)\n}\n\n\ndef DownloadProgressProvider(progress_bar, max=None):\n    if max is None or max == 0:\n        return BAR_TYPES[progress_bar][1]().iter\n    else:\n        return BAR_TYPES[progress_bar][0](max=max).iter\n\n\n################################################################\n# Generic \"something is happening\" spinners\n#\n# We don't even try using progress.spinner.Spinner here because it's actually\n# simpler to reimplement from scratch than to coerce their code into doing\n# what we need.\n################################################################\n\n@contextlib.contextmanager\ndef hidden_cursor(file):\n    # type: (IO) -> Iterator[None]\n    # The Windows terminal does not support the hide/show cursor ANSI codes,\n    # even via colorama. So don't even try.\n    if WINDOWS:\n        yield\n    # We don't want to clutter the output with control characters if we're\n    # writing to a file, or if the user is running with --quiet.\n    # See https://github.com/pypa/pip/issues/3418\n    elif not file.isatty() or logger.getEffectiveLevel() > logging.INFO:\n        yield\n    else:\n        file.write(HIDE_CURSOR)\n        try:\n            yield\n        finally:\n            file.write(SHOW_CURSOR)\n\n\nclass RateLimiter(object):\n    def __init__(self, min_update_interval_seconds):\n        # type: (float) -> None\n        self._min_update_interval_seconds = min_update_interval_seconds\n        self._last_update = 0  # type: float\n\n    def ready(self):\n        # type: () -> bool\n        now = time.time()\n        delta = now - self._last_update\n        return delta >= self._min_update_interval_seconds\n\n    def reset(self):\n        # type: () -> None\n        self._last_update = time.time()\n\n\nclass SpinnerInterface(object):\n    def spin(self):\n        # type: () -> None\n        raise NotImplementedError()\n\n    def finish(self, final_status):\n        # type: (str) -> None\n        raise NotImplementedError()\n\n\nclass InteractiveSpinner(SpinnerInterface):\n    def __init__(self, message, file=None, spin_chars=\"-\\\\|/\",\n                 # Empirically, 8 updates/second looks nice\n                 min_update_interval_seconds=0.125):\n        self._message = message\n        if file is None:\n            file = sys.stdout\n        self._file = file\n        self._rate_limiter = RateLimiter(min_update_interval_seconds)\n        self._finished = False\n\n        self._spin_cycle = itertools.cycle(spin_chars)\n\n        self._file.write(\" \" * get_indentation() + self._message + \" ... \")\n        self._width = 0\n\n    def _write(self, status):\n        assert not self._finished\n        # Erase what we wrote before by backspacing to the beginning, writing\n        # spaces to overwrite the old text, and then backspacing again\n        backup = \"\\b\" * self._width\n        self._file.write(backup + \" \" * self._width + backup)\n        # Now we have a blank slate to add our status\n        self._file.write(status)\n        self._width = len(status)\n        self._file.flush()\n        self._rate_limiter.reset()\n\n    def spin(self):\n        # type: () -> None\n        if self._finished:\n            return\n        if not self._rate_limiter.ready():\n            return\n        self._write(next(self._spin_cycle))\n\n    def finish(self, final_status):\n        # type: (str) -> None\n        if self._finished:\n            return\n        self._write(final_status)\n        self._file.write(\"\\n\")\n        self._file.flush()\n        self._finished = True\n\n\n# Used for dumb terminals, non-interactive installs (no tty), etc.\n# We still print updates occasionally (once every 60 seconds by default) to\n# act as a keep-alive for systems like Travis-CI that take lack-of-output as\n# an indication that a task has frozen.\nclass NonInteractiveSpinner(SpinnerInterface):\n    def __init__(self, message, min_update_interval_seconds=60):\n        # type: (str, float) -> None\n        self._message = message\n        self._finished = False\n        self._rate_limiter = RateLimiter(min_update_interval_seconds)\n        self._update(\"started\")\n\n    def _update(self, status):\n        assert not self._finished\n        self._rate_limiter.reset()\n        logger.info(\"%s: %s\", self._message, status)\n\n    def spin(self):\n        # type: () -> None\n        if self._finished:\n            return\n        if not self._rate_limiter.ready():\n            return\n        self._update(\"still running...\")\n\n    def finish(self, final_status):\n        # type: (str) -> None\n        if self._finished:\n            return\n        self._update(\"finished with status '%s'\" % (final_status,))\n        self._finished = True\n\n\n@contextlib.contextmanager\ndef open_spinner(message):\n    # type: (str) -> Iterator[SpinnerInterface]\n    # Interactive spinner goes directly to sys.stdout rather than being routed\n    # through the logging system, but it acts like it has level INFO,\n    # i.e. it's only displayed if we're at level INFO or better.\n    # Non-interactive spinner goes through the logging system, so it is always\n    # in sync with logging configuration.\n    if sys.stdout.isatty() and logger.getEffectiveLevel() <= logging.INFO:\n        spinner = InteractiveSpinner(message)  # type: SpinnerInterface\n    else:\n        spinner = NonInteractiveSpinner(message)\n    try:\n        with hidden_cursor(sys.stdout):\n            yield spinner\n    except KeyboardInterrupt:\n        spinner.finish(\"canceled\")\n        raise\n    except Exception:\n        spinner.finish(\"error\")\n        raise\n    else:\n        spinner.finish(\"done\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/vcs/__init__.py",
    "content": "\"\"\"Handles all VCS (version control) support\"\"\"\nfrom __future__ import absolute_import\n\nimport errno\nimport logging\nimport os\nimport shutil\nimport sys\n\nfrom pip._vendor.six.moves.urllib import parse as urllib_parse\n\nfrom pip._internal.exceptions import BadCommand\nfrom pip._internal.utils.misc import (\n    display_path, backup_dir, call_subprocess, rmtree, ask_path_exists,\n)\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\n\nif MYPY_CHECK_RUNNING:\n    from typing import (  # noqa: F401\n        Any, Dict, Iterable, List, Mapping, Optional, Text, Tuple, Type\n    )\n    from pip._internal.utils.ui import SpinnerInterface  # noqa: F401\n\n    AuthInfo = Tuple[Optional[str], Optional[str]]\n\n__all__ = ['vcs']\n\n\nlogger = logging.getLogger(__name__)\n\n\nclass RemoteNotFoundError(Exception):\n    pass\n\n\nclass RevOptions(object):\n\n    \"\"\"\n    Encapsulates a VCS-specific revision to install, along with any VCS\n    install options.\n\n    Instances of this class should be treated as if immutable.\n    \"\"\"\n\n    def __init__(self, vcs, rev=None, extra_args=None):\n        # type: (VersionControl, Optional[str], Optional[List[str]]) -> None\n        \"\"\"\n        Args:\n          vcs: a VersionControl object.\n          rev: the name of the revision to install.\n          extra_args: a list of extra options.\n        \"\"\"\n        if extra_args is None:\n            extra_args = []\n\n        self.extra_args = extra_args\n        self.rev = rev\n        self.vcs = vcs\n\n    def __repr__(self):\n        return '<RevOptions {}: rev={!r}>'.format(self.vcs.name, self.rev)\n\n    @property\n    def arg_rev(self):\n        # type: () -> Optional[str]\n        if self.rev is None:\n            return self.vcs.default_arg_rev\n\n        return self.rev\n\n    def to_args(self):\n        # type: () -> List[str]\n        \"\"\"\n        Return the VCS-specific command arguments.\n        \"\"\"\n        args = []  # type: List[str]\n        rev = self.arg_rev\n        if rev is not None:\n            args += self.vcs.get_base_rev_args(rev)\n        args += self.extra_args\n\n        return args\n\n    def to_display(self):\n        # type: () -> str\n        if not self.rev:\n            return ''\n\n        return ' (to revision {})'.format(self.rev)\n\n    def make_new(self, rev):\n        # type: (str) -> RevOptions\n        \"\"\"\n        Make a copy of the current instance, but with a new rev.\n\n        Args:\n          rev: the name of the revision for the new object.\n        \"\"\"\n        return self.vcs.make_rev_options(rev, extra_args=self.extra_args)\n\n\nclass VcsSupport(object):\n    _registry = {}  # type: Dict[str, Type[VersionControl]]\n    schemes = ['ssh', 'git', 'hg', 'bzr', 'sftp', 'svn']\n\n    def __init__(self):\n        # type: () -> None\n        # Register more schemes with urlparse for various version control\n        # systems\n        urllib_parse.uses_netloc.extend(self.schemes)\n        # Python >= 2.7.4, 3.3 doesn't have uses_fragment\n        if getattr(urllib_parse, 'uses_fragment', None):\n            urllib_parse.uses_fragment.extend(self.schemes)\n        super(VcsSupport, self).__init__()\n\n    def __iter__(self):\n        return self._registry.__iter__()\n\n    @property\n    def backends(self):\n        # type: () -> List[Type[VersionControl]]\n        return list(self._registry.values())\n\n    @property\n    def dirnames(self):\n        # type: () -> List[str]\n        return [backend.dirname for backend in self.backends]\n\n    @property\n    def all_schemes(self):\n        # type: () -> List[str]\n        schemes = []  # type: List[str]\n        for backend in self.backends:\n            schemes.extend(backend.schemes)\n        return schemes\n\n    def register(self, cls):\n        # type: (Type[VersionControl]) -> None\n        if not hasattr(cls, 'name'):\n            logger.warning('Cannot register VCS %s', cls.__name__)\n            return\n        if cls.name not in self._registry:\n            self._registry[cls.name] = cls\n            logger.debug('Registered VCS backend: %s', cls.name)\n\n    def unregister(self, cls=None, name=None):\n        # type: (Optional[Type[VersionControl]], Optional[str]) -> None\n        if name in self._registry:\n            del self._registry[name]\n        elif cls in self._registry.values():\n            del self._registry[cls.name]\n        else:\n            logger.warning('Cannot unregister because no class or name given')\n\n    def get_backend_type(self, location):\n        # type: (str) -> Optional[Type[VersionControl]]\n        \"\"\"\n        Return the type of the version control backend if found at given\n        location, e.g. vcs.get_backend_type('/path/to/vcs/checkout')\n        \"\"\"\n        for vc_type in self._registry.values():\n            if vc_type.controls_location(location):\n                logger.debug('Determine that %s uses VCS: %s',\n                             location, vc_type.name)\n                return vc_type\n        return None\n\n    def get_backend(self, name):\n        # type: (str) -> Optional[Type[VersionControl]]\n        name = name.lower()\n        if name in self._registry:\n            return self._registry[name]\n        return None\n\n\nvcs = VcsSupport()\n\n\nclass VersionControl(object):\n    name = ''\n    dirname = ''\n    repo_name = ''\n    # List of supported schemes for this Version Control\n    schemes = ()  # type: Tuple[str, ...]\n    # Iterable of environment variable names to pass to call_subprocess().\n    unset_environ = ()  # type: Tuple[str, ...]\n    default_arg_rev = None  # type: Optional[str]\n\n    def __init__(self, url=None, *args, **kwargs):\n        self.url = url\n        super(VersionControl, self).__init__(*args, **kwargs)\n\n    def get_base_rev_args(self, rev):\n        \"\"\"\n        Return the base revision arguments for a vcs command.\n\n        Args:\n          rev: the name of a revision to install.  Cannot be None.\n        \"\"\"\n        raise NotImplementedError\n\n    def make_rev_options(self, rev=None, extra_args=None):\n        # type: (Optional[str], Optional[List[str]]) -> RevOptions\n        \"\"\"\n        Return a RevOptions object.\n\n        Args:\n          rev: the name of a revision to install.\n          extra_args: a list of extra options.\n        \"\"\"\n        return RevOptions(self, rev, extra_args=extra_args)\n\n    @classmethod\n    def _is_local_repository(cls, repo):\n        # type: (str) -> bool\n        \"\"\"\n           posix absolute paths start with os.path.sep,\n           win32 ones start with drive (like c:\\\\folder)\n        \"\"\"\n        drive, tail = os.path.splitdrive(repo)\n        return repo.startswith(os.path.sep) or bool(drive)\n\n    def export(self, location):\n        \"\"\"\n        Export the repository at the url to the destination location\n        i.e. only download the files, without vcs informations\n        \"\"\"\n        raise NotImplementedError\n\n    def get_netloc_and_auth(self, netloc, scheme):\n        \"\"\"\n        Parse the repository URL's netloc, and return the new netloc to use\n        along with auth information.\n\n        Args:\n          netloc: the original repository URL netloc.\n          scheme: the repository URL's scheme without the vcs prefix.\n\n        This is mainly for the Subversion class to override, so that auth\n        information can be provided via the --username and --password options\n        instead of through the URL.  For other subclasses like Git without\n        such an option, auth information must stay in the URL.\n\n        Returns: (netloc, (username, password)).\n        \"\"\"\n        return netloc, (None, None)\n\n    def get_url_rev_and_auth(self, url):\n        # type: (str) -> Tuple[str, Optional[str], AuthInfo]\n        \"\"\"\n        Parse the repository URL to use, and return the URL, revision,\n        and auth info to use.\n\n        Returns: (url, rev, (username, password)).\n        \"\"\"\n        scheme, netloc, path, query, frag = urllib_parse.urlsplit(url)\n        if '+' not in scheme:\n            raise ValueError(\n                \"Sorry, {!r} is a malformed VCS url. \"\n                \"The format is <vcs>+<protocol>://<url>, \"\n                \"e.g. svn+http://myrepo/svn/MyApp#egg=MyApp\".format(url)\n            )\n        # Remove the vcs prefix.\n        scheme = scheme.split('+', 1)[1]\n        netloc, user_pass = self.get_netloc_and_auth(netloc, scheme)\n        rev = None\n        if '@' in path:\n            path, rev = path.rsplit('@', 1)\n        url = urllib_parse.urlunsplit((scheme, netloc, path, query, ''))\n        return url, rev, user_pass\n\n    def make_rev_args(self, username, password):\n        \"\"\"\n        Return the RevOptions \"extra arguments\" to use in obtain().\n        \"\"\"\n        return []\n\n    def get_url_rev_options(self, url):\n        # type: (str) -> Tuple[str, RevOptions]\n        \"\"\"\n        Return the URL and RevOptions object to use in obtain() and in\n        some cases export(), as a tuple (url, rev_options).\n        \"\"\"\n        url, rev, user_pass = self.get_url_rev_and_auth(url)\n        username, password = user_pass\n        extra_args = self.make_rev_args(username, password)\n        rev_options = self.make_rev_options(rev, extra_args=extra_args)\n\n        return url, rev_options\n\n    def normalize_url(self, url):\n        # type: (str) -> str\n        \"\"\"\n        Normalize a URL for comparison by unquoting it and removing any\n        trailing slash.\n        \"\"\"\n        return urllib_parse.unquote(url).rstrip('/')\n\n    def compare_urls(self, url1, url2):\n        # type: (str, str) -> bool\n        \"\"\"\n        Compare two repo URLs for identity, ignoring incidental differences.\n        \"\"\"\n        return (self.normalize_url(url1) == self.normalize_url(url2))\n\n    def fetch_new(self, dest, url, rev_options):\n        \"\"\"\n        Fetch a revision from a repository, in the case that this is the\n        first fetch from the repository.\n\n        Args:\n          dest: the directory to fetch the repository to.\n          rev_options: a RevOptions object.\n        \"\"\"\n        raise NotImplementedError\n\n    def switch(self, dest, url, rev_options):\n        \"\"\"\n        Switch the repo at ``dest`` to point to ``URL``.\n\n        Args:\n          rev_options: a RevOptions object.\n        \"\"\"\n        raise NotImplementedError\n\n    def update(self, dest, url, rev_options):\n        \"\"\"\n        Update an already-existing repo to the given ``rev_options``.\n\n        Args:\n          rev_options: a RevOptions object.\n        \"\"\"\n        raise NotImplementedError\n\n    def is_commit_id_equal(self, dest, name):\n        \"\"\"\n        Return whether the id of the current commit equals the given name.\n\n        Args:\n          dest: the repository directory.\n          name: a string name.\n        \"\"\"\n        raise NotImplementedError\n\n    def obtain(self, dest):\n        # type: (str) -> None\n        \"\"\"\n        Install or update in editable mode the package represented by this\n        VersionControl object.\n\n        Args:\n          dest: the repository directory in which to install or update.\n        \"\"\"\n        url, rev_options = self.get_url_rev_options(self.url)\n\n        if not os.path.exists(dest):\n            self.fetch_new(dest, url, rev_options)\n            return\n\n        rev_display = rev_options.to_display()\n        if self.is_repository_directory(dest):\n            existing_url = self.get_remote_url(dest)\n            if self.compare_urls(existing_url, url):\n                logger.debug(\n                    '%s in %s exists, and has correct URL (%s)',\n                    self.repo_name.title(),\n                    display_path(dest),\n                    url,\n                )\n                if not self.is_commit_id_equal(dest, rev_options.rev):\n                    logger.info(\n                        'Updating %s %s%s',\n                        display_path(dest),\n                        self.repo_name,\n                        rev_display,\n                    )\n                    self.update(dest, url, rev_options)\n                else:\n                    logger.info('Skipping because already up-to-date.')\n                return\n\n            logger.warning(\n                '%s %s in %s exists with URL %s',\n                self.name,\n                self.repo_name,\n                display_path(dest),\n                existing_url,\n            )\n            prompt = ('(s)witch, (i)gnore, (w)ipe, (b)ackup ',\n                      ('s', 'i', 'w', 'b'))\n        else:\n            logger.warning(\n                'Directory %s already exists, and is not a %s %s.',\n                dest,\n                self.name,\n                self.repo_name,\n            )\n            # https://github.com/python/mypy/issues/1174\n            prompt = ('(i)gnore, (w)ipe, (b)ackup ',  # type: ignore\n                      ('i', 'w', 'b'))\n\n        logger.warning(\n            'The plan is to install the %s repository %s',\n            self.name,\n            url,\n        )\n        response = ask_path_exists('What to do?  %s' % prompt[0], prompt[1])\n\n        if response == 'a':\n            sys.exit(-1)\n\n        if response == 'w':\n            logger.warning('Deleting %s', display_path(dest))\n            rmtree(dest)\n            self.fetch_new(dest, url, rev_options)\n            return\n\n        if response == 'b':\n            dest_dir = backup_dir(dest)\n            logger.warning(\n                'Backing up %s to %s', display_path(dest), dest_dir,\n            )\n            shutil.move(dest, dest_dir)\n            self.fetch_new(dest, url, rev_options)\n            return\n\n        # Do nothing if the response is \"i\".\n        if response == 's':\n            logger.info(\n                'Switching %s %s to %s%s',\n                self.repo_name,\n                display_path(dest),\n                url,\n                rev_display,\n            )\n            self.switch(dest, url, rev_options)\n\n    def unpack(self, location):\n        # type: (str) -> None\n        \"\"\"\n        Clean up current location and download the url repository\n        (and vcs infos) into location\n        \"\"\"\n        if os.path.exists(location):\n            rmtree(location)\n        self.obtain(location)\n\n    @classmethod\n    def get_src_requirement(cls, location, project_name):\n        \"\"\"\n        Return a string representing the requirement needed to\n        redownload the files currently present in location, something\n        like:\n          {repository_url}@{revision}#egg={project_name}-{version_identifier}\n        \"\"\"\n        raise NotImplementedError\n\n    @classmethod\n    def get_remote_url(cls, location):\n        \"\"\"\n        Return the url used at location\n\n        Raises RemoteNotFoundError if the repository does not have a remote\n        url configured.\n        \"\"\"\n        raise NotImplementedError\n\n    @classmethod\n    def get_revision(cls, location):\n        \"\"\"\n        Return the current commit id of the files at the given location.\n        \"\"\"\n        raise NotImplementedError\n\n    @classmethod\n    def run_command(\n        cls,\n        cmd,  # type: List[str]\n        show_stdout=True,  # type: bool\n        cwd=None,  # type: Optional[str]\n        on_returncode='raise',  # type: str\n        extra_ok_returncodes=None,  # type: Optional[Iterable[int]]\n        command_desc=None,  # type: Optional[str]\n        extra_environ=None,  # type: Optional[Mapping[str, Any]]\n        spinner=None  # type: Optional[SpinnerInterface]\n    ):\n        # type: (...) -> Optional[Text]\n        \"\"\"\n        Run a VCS subcommand\n        This is simply a wrapper around call_subprocess that adds the VCS\n        command name, and checks that the VCS is available\n        \"\"\"\n        cmd = [cls.name] + cmd\n        try:\n            return call_subprocess(cmd, show_stdout, cwd,\n                                   on_returncode=on_returncode,\n                                   extra_ok_returncodes=extra_ok_returncodes,\n                                   command_desc=command_desc,\n                                   extra_environ=extra_environ,\n                                   unset_environ=cls.unset_environ,\n                                   spinner=spinner)\n        except OSError as e:\n            # errno.ENOENT = no such file or directory\n            # In other words, the VCS executable isn't available\n            if e.errno == errno.ENOENT:\n                raise BadCommand(\n                    'Cannot find command %r - do you have '\n                    '%r installed and in your '\n                    'PATH?' % (cls.name, cls.name))\n            else:\n                raise  # re-raise exception if a different error occurred\n\n    @classmethod\n    def is_repository_directory(cls, path):\n        # type: (str) -> bool\n        \"\"\"\n        Return whether a directory path is a repository directory.\n        \"\"\"\n        logger.debug('Checking in %s for %s (%s)...',\n                     path, cls.dirname, cls.name)\n        return os.path.exists(os.path.join(path, cls.dirname))\n\n    @classmethod\n    def controls_location(cls, location):\n        # type: (str) -> bool\n        \"\"\"\n        Check if a location is controlled by the vcs.\n        It is meant to be overridden to implement smarter detection\n        mechanisms for specific vcs.\n\n        This can do more than is_repository_directory() alone.  For example,\n        the Git override checks that Git is actually available.\n        \"\"\"\n        return cls.is_repository_directory(location)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/vcs/bazaar.py",
    "content": "from __future__ import absolute_import\n\nimport logging\nimport os\n\nfrom pip._vendor.six.moves.urllib import parse as urllib_parse\n\nfrom pip._internal.download import path_to_url\nfrom pip._internal.utils.misc import (\n    display_path, make_vcs_requirement_url, rmtree,\n)\nfrom pip._internal.utils.temp_dir import TempDirectory\nfrom pip._internal.vcs import VersionControl, vcs\n\nlogger = logging.getLogger(__name__)\n\n\nclass Bazaar(VersionControl):\n    name = 'bzr'\n    dirname = '.bzr'\n    repo_name = 'branch'\n    schemes = (\n        'bzr', 'bzr+http', 'bzr+https', 'bzr+ssh', 'bzr+sftp', 'bzr+ftp',\n        'bzr+lp',\n    )\n\n    def __init__(self, url=None, *args, **kwargs):\n        super(Bazaar, self).__init__(url, *args, **kwargs)\n        # This is only needed for python <2.7.5\n        # Register lp but do not expose as a scheme to support bzr+lp.\n        if getattr(urllib_parse, 'uses_fragment', None):\n            urllib_parse.uses_fragment.extend(['lp'])\n\n    def get_base_rev_args(self, rev):\n        return ['-r', rev]\n\n    def export(self, location):\n        \"\"\"\n        Export the Bazaar repository at the url to the destination location\n        \"\"\"\n        # Remove the location to make sure Bazaar can export it correctly\n        if os.path.exists(location):\n            rmtree(location)\n\n        with TempDirectory(kind=\"export\") as temp_dir:\n            self.unpack(temp_dir.path)\n\n            self.run_command(\n                ['export', location],\n                cwd=temp_dir.path, show_stdout=False,\n            )\n\n    def fetch_new(self, dest, url, rev_options):\n        rev_display = rev_options.to_display()\n        logger.info(\n            'Checking out %s%s to %s',\n            url,\n            rev_display,\n            display_path(dest),\n        )\n        cmd_args = ['branch', '-q'] + rev_options.to_args() + [url, dest]\n        self.run_command(cmd_args)\n\n    def switch(self, dest, url, rev_options):\n        self.run_command(['switch', url], cwd=dest)\n\n    def update(self, dest, url, rev_options):\n        cmd_args = ['pull', '-q'] + rev_options.to_args()\n        self.run_command(cmd_args, cwd=dest)\n\n    def get_url_rev_and_auth(self, url):\n        # hotfix the URL scheme after removing bzr+ from bzr+ssh:// readd it\n        url, rev, user_pass = super(Bazaar, self).get_url_rev_and_auth(url)\n        if url.startswith('ssh://'):\n            url = 'bzr+' + url\n        return url, rev, user_pass\n\n    @classmethod\n    def get_remote_url(cls, location):\n        urls = cls.run_command(['info'], show_stdout=False, cwd=location)\n        for line in urls.splitlines():\n            line = line.strip()\n            for x in ('checkout of branch: ',\n                      'parent branch: '):\n                if line.startswith(x):\n                    repo = line.split(x)[1]\n                    if cls._is_local_repository(repo):\n                        return path_to_url(repo)\n                    return repo\n        return None\n\n    @classmethod\n    def get_revision(cls, location):\n        revision = cls.run_command(\n            ['revno'], show_stdout=False, cwd=location,\n        )\n        return revision.splitlines()[-1]\n\n    @classmethod\n    def get_src_requirement(cls, location, project_name):\n        repo = cls.get_remote_url(location)\n        if not repo:\n            return None\n        if not repo.lower().startswith('bzr:'):\n            repo = 'bzr+' + repo\n        current_rev = cls.get_revision(location)\n        return make_vcs_requirement_url(repo, current_rev, project_name)\n\n    def is_commit_id_equal(self, dest, name):\n        \"\"\"Always assume the versions don't match\"\"\"\n        return False\n\n\nvcs.register(Bazaar)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/vcs/git.py",
    "content": "from __future__ import absolute_import\n\nimport logging\nimport os.path\nimport re\n\nfrom pip._vendor.packaging.version import parse as parse_version\nfrom pip._vendor.six.moves.urllib import parse as urllib_parse\nfrom pip._vendor.six.moves.urllib import request as urllib_request\n\nfrom pip._internal.exceptions import BadCommand\nfrom pip._internal.utils.compat import samefile\nfrom pip._internal.utils.misc import (\n    display_path, make_vcs_requirement_url, redact_password_from_url,\n)\nfrom pip._internal.utils.temp_dir import TempDirectory\nfrom pip._internal.vcs import RemoteNotFoundError, VersionControl, vcs\n\nurlsplit = urllib_parse.urlsplit\nurlunsplit = urllib_parse.urlunsplit\n\n\nlogger = logging.getLogger(__name__)\n\n\nHASH_REGEX = re.compile('[a-fA-F0-9]{40}')\n\n\ndef looks_like_hash(sha):\n    return bool(HASH_REGEX.match(sha))\n\n\nclass Git(VersionControl):\n    name = 'git'\n    dirname = '.git'\n    repo_name = 'clone'\n    schemes = (\n        'git', 'git+http', 'git+https', 'git+ssh', 'git+git', 'git+file',\n    )\n    # Prevent the user's environment variables from interfering with pip:\n    # https://github.com/pypa/pip/issues/1130\n    unset_environ = ('GIT_DIR', 'GIT_WORK_TREE')\n    default_arg_rev = 'HEAD'\n\n    def __init__(self, url=None, *args, **kwargs):\n\n        # Works around an apparent Git bug\n        # (see https://article.gmane.org/gmane.comp.version-control.git/146500)\n        if url:\n            scheme, netloc, path, query, fragment = urlsplit(url)\n            if scheme.endswith('file'):\n                initial_slashes = path[:-len(path.lstrip('/'))]\n                newpath = (\n                    initial_slashes +\n                    urllib_request.url2pathname(path)\n                    .replace('\\\\', '/').lstrip('/')\n                )\n                url = urlunsplit((scheme, netloc, newpath, query, fragment))\n                after_plus = scheme.find('+') + 1\n                url = scheme[:after_plus] + urlunsplit(\n                    (scheme[after_plus:], netloc, newpath, query, fragment),\n                )\n\n        super(Git, self).__init__(url, *args, **kwargs)\n\n    def get_base_rev_args(self, rev):\n        return [rev]\n\n    def get_git_version(self):\n        VERSION_PFX = 'git version '\n        version = self.run_command(['version'], show_stdout=False)\n        if version.startswith(VERSION_PFX):\n            version = version[len(VERSION_PFX):].split()[0]\n        else:\n            version = ''\n        # get first 3 positions of the git version becasue\n        # on windows it is x.y.z.windows.t, and this parses as\n        # LegacyVersion which always smaller than a Version.\n        version = '.'.join(version.split('.')[:3])\n        return parse_version(version)\n\n    def get_current_branch(self, location):\n        \"\"\"\n        Return the current branch, or None if HEAD isn't at a branch\n        (e.g. detached HEAD).\n        \"\"\"\n        # git-symbolic-ref exits with empty stdout if \"HEAD\" is a detached\n        # HEAD rather than a symbolic ref.  In addition, the -q causes the\n        # command to exit with status code 1 instead of 128 in this case\n        # and to suppress the message to stderr.\n        args = ['symbolic-ref', '-q', 'HEAD']\n        output = self.run_command(\n            args, extra_ok_returncodes=(1, ), show_stdout=False, cwd=location,\n        )\n        ref = output.strip()\n\n        if ref.startswith('refs/heads/'):\n            return ref[len('refs/heads/'):]\n\n        return None\n\n    def export(self, location):\n        \"\"\"Export the Git repository at the url to the destination location\"\"\"\n        if not location.endswith('/'):\n            location = location + '/'\n\n        with TempDirectory(kind=\"export\") as temp_dir:\n            self.unpack(temp_dir.path)\n            self.run_command(\n                ['checkout-index', '-a', '-f', '--prefix', location],\n                show_stdout=False, cwd=temp_dir.path\n            )\n\n    def get_revision_sha(self, dest, rev):\n        \"\"\"\n        Return (sha_or_none, is_branch), where sha_or_none is a commit hash\n        if the revision names a remote branch or tag, otherwise None.\n\n        Args:\n          dest: the repository directory.\n          rev: the revision name.\n        \"\"\"\n        # Pass rev to pre-filter the list.\n        output = self.run_command(['show-ref', rev], cwd=dest,\n                                  show_stdout=False, on_returncode='ignore')\n        refs = {}\n        for line in output.strip().splitlines():\n            try:\n                sha, ref = line.split()\n            except ValueError:\n                # Include the offending line to simplify troubleshooting if\n                # this error ever occurs.\n                raise ValueError('unexpected show-ref line: {!r}'.format(line))\n\n            refs[ref] = sha\n\n        branch_ref = 'refs/remotes/origin/{}'.format(rev)\n        tag_ref = 'refs/tags/{}'.format(rev)\n\n        sha = refs.get(branch_ref)\n        if sha is not None:\n            return (sha, True)\n\n        sha = refs.get(tag_ref)\n\n        return (sha, False)\n\n    def resolve_revision(self, dest, url, rev_options):\n        \"\"\"\n        Resolve a revision to a new RevOptions object with the SHA1 of the\n        branch, tag, or ref if found.\n\n        Args:\n          rev_options: a RevOptions object.\n        \"\"\"\n        rev = rev_options.arg_rev\n        sha, is_branch = self.get_revision_sha(dest, rev)\n\n        if sha is not None:\n            rev_options = rev_options.make_new(sha)\n            rev_options.branch_name = rev if is_branch else None\n\n            return rev_options\n\n        # Do not show a warning for the common case of something that has\n        # the form of a Git commit hash.\n        if not looks_like_hash(rev):\n            logger.warning(\n                \"Did not find branch or tag '%s', assuming revision or ref.\",\n                rev,\n            )\n\n        if not rev.startswith('refs/'):\n            return rev_options\n\n        # If it looks like a ref, we have to fetch it explicitly.\n        self.run_command(\n            ['fetch', '-q', url] + rev_options.to_args(),\n            cwd=dest,\n        )\n        # Change the revision to the SHA of the ref we fetched\n        sha = self.get_revision(dest, rev='FETCH_HEAD')\n        rev_options = rev_options.make_new(sha)\n\n        return rev_options\n\n    def is_commit_id_equal(self, dest, name):\n        \"\"\"\n        Return whether the current commit hash equals the given name.\n\n        Args:\n          dest: the repository directory.\n          name: a string name.\n        \"\"\"\n        if not name:\n            # Then avoid an unnecessary subprocess call.\n            return False\n\n        return self.get_revision(dest) == name\n\n    def fetch_new(self, dest, url, rev_options):\n        rev_display = rev_options.to_display()\n        logger.info(\n            'Cloning %s%s to %s', redact_password_from_url(url),\n            rev_display, display_path(dest),\n        )\n        self.run_command(['clone', '-q', url, dest])\n\n        if rev_options.rev:\n            # Then a specific revision was requested.\n            rev_options = self.resolve_revision(dest, url, rev_options)\n            branch_name = getattr(rev_options, 'branch_name', None)\n            if branch_name is None:\n                # Only do a checkout if the current commit id doesn't match\n                # the requested revision.\n                if not self.is_commit_id_equal(dest, rev_options.rev):\n                    cmd_args = ['checkout', '-q'] + rev_options.to_args()\n                    self.run_command(cmd_args, cwd=dest)\n            elif self.get_current_branch(dest) != branch_name:\n                # Then a specific branch was requested, and that branch\n                # is not yet checked out.\n                track_branch = 'origin/{}'.format(branch_name)\n                cmd_args = [\n                    'checkout', '-b', branch_name, '--track', track_branch,\n                ]\n                self.run_command(cmd_args, cwd=dest)\n\n        #: repo may contain submodules\n        self.update_submodules(dest)\n\n    def switch(self, dest, url, rev_options):\n        self.run_command(['config', 'remote.origin.url', url], cwd=dest)\n        cmd_args = ['checkout', '-q'] + rev_options.to_args()\n        self.run_command(cmd_args, cwd=dest)\n\n        self.update_submodules(dest)\n\n    def update(self, dest, url, rev_options):\n        # First fetch changes from the default remote\n        if self.get_git_version() >= parse_version('1.9.0'):\n            # fetch tags in addition to everything else\n            self.run_command(['fetch', '-q', '--tags'], cwd=dest)\n        else:\n            self.run_command(['fetch', '-q'], cwd=dest)\n        # Then reset to wanted revision (maybe even origin/master)\n        rev_options = self.resolve_revision(dest, url, rev_options)\n        cmd_args = ['reset', '--hard', '-q'] + rev_options.to_args()\n        self.run_command(cmd_args, cwd=dest)\n        #: update submodules\n        self.update_submodules(dest)\n\n    @classmethod\n    def get_remote_url(cls, location):\n        \"\"\"\n        Return URL of the first remote encountered.\n\n        Raises RemoteNotFoundError if the repository does not have a remote\n        url configured.\n        \"\"\"\n        # We need to pass 1 for extra_ok_returncodes since the command\n        # exits with return code 1 if there are no matching lines.\n        stdout = cls.run_command(\n            ['config', '--get-regexp', r'remote\\..*\\.url'],\n            extra_ok_returncodes=(1, ), show_stdout=False, cwd=location,\n        )\n        remotes = stdout.splitlines()\n        try:\n            found_remote = remotes[0]\n        except IndexError:\n            raise RemoteNotFoundError\n\n        for remote in remotes:\n            if remote.startswith('remote.origin.url '):\n                found_remote = remote\n                break\n        url = found_remote.split(' ')[1]\n        return url.strip()\n\n    @classmethod\n    def get_revision(cls, location, rev=None):\n        if rev is None:\n            rev = 'HEAD'\n        current_rev = cls.run_command(\n            ['rev-parse', rev], show_stdout=False, cwd=location,\n        )\n        return current_rev.strip()\n\n    @classmethod\n    def _get_subdirectory(cls, location):\n        \"\"\"Return the relative path of setup.py to the git repo root.\"\"\"\n        # find the repo root\n        git_dir = cls.run_command(['rev-parse', '--git-dir'],\n                                  show_stdout=False, cwd=location).strip()\n        if not os.path.isabs(git_dir):\n            git_dir = os.path.join(location, git_dir)\n        root_dir = os.path.join(git_dir, '..')\n        # find setup.py\n        orig_location = location\n        while not os.path.exists(os.path.join(location, 'setup.py')):\n            last_location = location\n            location = os.path.dirname(location)\n            if location == last_location:\n                # We've traversed up to the root of the filesystem without\n                # finding setup.py\n                logger.warning(\n                    \"Could not find setup.py for directory %s (tried all \"\n                    \"parent directories)\",\n                    orig_location,\n                )\n                return None\n        # relative path of setup.py to repo root\n        if samefile(root_dir, location):\n            return None\n        return os.path.relpath(location, root_dir)\n\n    @classmethod\n    def get_src_requirement(cls, location, project_name):\n        repo = cls.get_remote_url(location)\n        if not repo.lower().startswith('git:'):\n            repo = 'git+' + repo\n        current_rev = cls.get_revision(location)\n        subdir = cls._get_subdirectory(location)\n        req = make_vcs_requirement_url(repo, current_rev, project_name,\n                                       subdir=subdir)\n\n        return req\n\n    def get_url_rev_and_auth(self, url):\n        \"\"\"\n        Prefixes stub URLs like 'user@hostname:user/repo.git' with 'ssh://'.\n        That's required because although they use SSH they sometimes don't\n        work with a ssh:// scheme (e.g. GitHub). But we need a scheme for\n        parsing. Hence we remove it again afterwards and return it as a stub.\n        \"\"\"\n        if '://' not in url:\n            assert 'file:' not in url\n            url = url.replace('git+', 'git+ssh://')\n            url, rev, user_pass = super(Git, self).get_url_rev_and_auth(url)\n            url = url.replace('ssh://', '')\n        else:\n            url, rev, user_pass = super(Git, self).get_url_rev_and_auth(url)\n\n        return url, rev, user_pass\n\n    def update_submodules(self, location):\n        if not os.path.exists(os.path.join(location, '.gitmodules')):\n            return\n        self.run_command(\n            ['submodule', 'update', '--init', '--recursive', '-q'],\n            cwd=location,\n        )\n\n    @classmethod\n    def controls_location(cls, location):\n        if super(Git, cls).controls_location(location):\n            return True\n        try:\n            r = cls.run_command(['rev-parse'],\n                                cwd=location,\n                                show_stdout=False,\n                                on_returncode='ignore')\n            return not r\n        except BadCommand:\n            logger.debug(\"could not determine if %s is under git control \"\n                         \"because git is not available\", location)\n            return False\n\n\nvcs.register(Git)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/vcs/mercurial.py",
    "content": "from __future__ import absolute_import\n\nimport logging\nimport os\n\nfrom pip._vendor.six.moves import configparser\n\nfrom pip._internal.download import path_to_url\nfrom pip._internal.utils.misc import display_path, make_vcs_requirement_url\nfrom pip._internal.utils.temp_dir import TempDirectory\nfrom pip._internal.vcs import VersionControl, vcs\n\nlogger = logging.getLogger(__name__)\n\n\nclass Mercurial(VersionControl):\n    name = 'hg'\n    dirname = '.hg'\n    repo_name = 'clone'\n    schemes = ('hg', 'hg+http', 'hg+https', 'hg+ssh', 'hg+static-http')\n\n    def get_base_rev_args(self, rev):\n        return [rev]\n\n    def export(self, location):\n        \"\"\"Export the Hg repository at the url to the destination location\"\"\"\n        with TempDirectory(kind=\"export\") as temp_dir:\n            self.unpack(temp_dir.path)\n\n            self.run_command(\n                ['archive', location], show_stdout=False, cwd=temp_dir.path\n            )\n\n    def fetch_new(self, dest, url, rev_options):\n        rev_display = rev_options.to_display()\n        logger.info(\n            'Cloning hg %s%s to %s',\n            url,\n            rev_display,\n            display_path(dest),\n        )\n        self.run_command(['clone', '--noupdate', '-q', url, dest])\n        cmd_args = ['update', '-q'] + rev_options.to_args()\n        self.run_command(cmd_args, cwd=dest)\n\n    def switch(self, dest, url, rev_options):\n        repo_config = os.path.join(dest, self.dirname, 'hgrc')\n        config = configparser.SafeConfigParser()\n        try:\n            config.read(repo_config)\n            config.set('paths', 'default', url)\n            with open(repo_config, 'w') as config_file:\n                config.write(config_file)\n        except (OSError, configparser.NoSectionError) as exc:\n            logger.warning(\n                'Could not switch Mercurial repository to %s: %s', url, exc,\n            )\n        else:\n            cmd_args = ['update', '-q'] + rev_options.to_args()\n            self.run_command(cmd_args, cwd=dest)\n\n    def update(self, dest, url, rev_options):\n        self.run_command(['pull', '-q'], cwd=dest)\n        cmd_args = ['update', '-q'] + rev_options.to_args()\n        self.run_command(cmd_args, cwd=dest)\n\n    @classmethod\n    def get_remote_url(cls, location):\n        url = cls.run_command(\n            ['showconfig', 'paths.default'],\n            show_stdout=False, cwd=location).strip()\n        if cls._is_local_repository(url):\n            url = path_to_url(url)\n        return url.strip()\n\n    @classmethod\n    def get_revision(cls, location):\n        current_revision = cls.run_command(\n            ['parents', '--template={rev}'],\n            show_stdout=False, cwd=location).strip()\n        return current_revision\n\n    @classmethod\n    def get_revision_hash(cls, location):\n        current_rev_hash = cls.run_command(\n            ['parents', '--template={node}'],\n            show_stdout=False, cwd=location).strip()\n        return current_rev_hash\n\n    @classmethod\n    def get_src_requirement(cls, location, project_name):\n        repo = cls.get_remote_url(location)\n        if not repo.lower().startswith('hg:'):\n            repo = 'hg+' + repo\n        current_rev_hash = cls.get_revision_hash(location)\n        return make_vcs_requirement_url(repo, current_rev_hash, project_name)\n\n    def is_commit_id_equal(self, dest, name):\n        \"\"\"Always assume the versions don't match\"\"\"\n        return False\n\n\nvcs.register(Mercurial)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/vcs/subversion.py",
    "content": "from __future__ import absolute_import\n\nimport logging\nimport os\nimport re\n\nfrom pip._internal.utils.logging import indent_log\nfrom pip._internal.utils.misc import (\n    display_path, make_vcs_requirement_url, rmtree, split_auth_from_netloc,\n)\nfrom pip._internal.vcs import VersionControl, vcs\n\n_svn_xml_url_re = re.compile('url=\"([^\"]+)\"')\n_svn_rev_re = re.compile(r'committed-rev=\"(\\d+)\"')\n_svn_info_xml_rev_re = re.compile(r'\\s*revision=\"(\\d+)\"')\n_svn_info_xml_url_re = re.compile(r'<url>(.*)</url>')\n\n\nlogger = logging.getLogger(__name__)\n\n\nclass Subversion(VersionControl):\n    name = 'svn'\n    dirname = '.svn'\n    repo_name = 'checkout'\n    schemes = ('svn', 'svn+ssh', 'svn+http', 'svn+https', 'svn+svn')\n\n    def get_base_rev_args(self, rev):\n        return ['-r', rev]\n\n    def export(self, location):\n        \"\"\"Export the svn repository at the url to the destination location\"\"\"\n        url, rev_options = self.get_url_rev_options(self.url)\n\n        logger.info('Exporting svn repository %s to %s', url, location)\n        with indent_log():\n            if os.path.exists(location):\n                # Subversion doesn't like to check out over an existing\n                # directory --force fixes this, but was only added in svn 1.5\n                rmtree(location)\n            cmd_args = ['export'] + rev_options.to_args() + [url, location]\n            self.run_command(cmd_args, show_stdout=False)\n\n    def fetch_new(self, dest, url, rev_options):\n        rev_display = rev_options.to_display()\n        logger.info(\n            'Checking out %s%s to %s',\n            url,\n            rev_display,\n            display_path(dest),\n        )\n        cmd_args = ['checkout', '-q'] + rev_options.to_args() + [url, dest]\n        self.run_command(cmd_args)\n\n    def switch(self, dest, url, rev_options):\n        cmd_args = ['switch'] + rev_options.to_args() + [url, dest]\n        self.run_command(cmd_args)\n\n    def update(self, dest, url, rev_options):\n        cmd_args = ['update'] + rev_options.to_args() + [dest]\n        self.run_command(cmd_args)\n\n    @classmethod\n    def get_revision(cls, location):\n        \"\"\"\n        Return the maximum revision for all files under a given location\n        \"\"\"\n        # Note: taken from setuptools.command.egg_info\n        revision = 0\n\n        for base, dirs, files in os.walk(location):\n            if cls.dirname not in dirs:\n                dirs[:] = []\n                continue    # no sense walking uncontrolled subdirs\n            dirs.remove(cls.dirname)\n            entries_fn = os.path.join(base, cls.dirname, 'entries')\n            if not os.path.exists(entries_fn):\n                # FIXME: should we warn?\n                continue\n\n            dirurl, localrev = cls._get_svn_url_rev(base)\n\n            if base == location:\n                base = dirurl + '/'   # save the root url\n            elif not dirurl or not dirurl.startswith(base):\n                dirs[:] = []\n                continue    # not part of the same svn tree, skip it\n            revision = max(revision, localrev)\n        return revision\n\n    def get_netloc_and_auth(self, netloc, scheme):\n        \"\"\"\n        This override allows the auth information to be passed to svn via the\n        --username and --password options instead of via the URL.\n        \"\"\"\n        if scheme == 'ssh':\n            # The --username and --password options can't be used for\n            # svn+ssh URLs, so keep the auth information in the URL.\n            return super(Subversion, self).get_netloc_and_auth(\n                netloc, scheme)\n\n        return split_auth_from_netloc(netloc)\n\n    def get_url_rev_and_auth(self, url):\n        # hotfix the URL scheme after removing svn+ from svn+ssh:// readd it\n        url, rev, user_pass = super(Subversion, self).get_url_rev_and_auth(url)\n        if url.startswith('ssh://'):\n            url = 'svn+' + url\n        return url, rev, user_pass\n\n    def make_rev_args(self, username, password):\n        extra_args = []\n        if username:\n            extra_args += ['--username', username]\n        if password:\n            extra_args += ['--password', password]\n\n        return extra_args\n\n    @classmethod\n    def get_remote_url(cls, location):\n        # In cases where the source is in a subdirectory, not alongside\n        # setup.py we have to look up in the location until we find a real\n        # setup.py\n        orig_location = location\n        while not os.path.exists(os.path.join(location, 'setup.py')):\n            last_location = location\n            location = os.path.dirname(location)\n            if location == last_location:\n                # We've traversed up to the root of the filesystem without\n                # finding setup.py\n                logger.warning(\n                    \"Could not find setup.py for directory %s (tried all \"\n                    \"parent directories)\",\n                    orig_location,\n                )\n                return None\n\n        return cls._get_svn_url_rev(location)[0]\n\n    @classmethod\n    def _get_svn_url_rev(cls, location):\n        from pip._internal.exceptions import InstallationError\n\n        entries_path = os.path.join(location, cls.dirname, 'entries')\n        if os.path.exists(entries_path):\n            with open(entries_path) as f:\n                data = f.read()\n        else:  # subversion >= 1.7 does not have the 'entries' file\n            data = ''\n\n        if (data.startswith('8') or\n                data.startswith('9') or\n                data.startswith('10')):\n            data = list(map(str.splitlines, data.split('\\n\\x0c\\n')))\n            del data[0][0]  # get rid of the '8'\n            url = data[0][3]\n            revs = [int(d[9]) for d in data if len(d) > 9 and d[9]] + [0]\n        elif data.startswith('<?xml'):\n            match = _svn_xml_url_re.search(data)\n            if not match:\n                raise ValueError('Badly formatted data: %r' % data)\n            url = match.group(1)    # get repository URL\n            revs = [int(m.group(1)) for m in _svn_rev_re.finditer(data)] + [0]\n        else:\n            try:\n                # subversion >= 1.7\n                xml = cls.run_command(\n                    ['info', '--xml', location],\n                    show_stdout=False,\n                )\n                url = _svn_info_xml_url_re.search(xml).group(1)\n                revs = [\n                    int(m.group(1)) for m in _svn_info_xml_rev_re.finditer(xml)\n                ]\n            except InstallationError:\n                url, revs = None, []\n\n        if revs:\n            rev = max(revs)\n        else:\n            rev = 0\n\n        return url, rev\n\n    @classmethod\n    def get_src_requirement(cls, location, project_name):\n        repo = cls.get_remote_url(location)\n        if repo is None:\n            return None\n        repo = 'svn+' + repo\n        rev = cls.get_revision(location)\n        return make_vcs_requirement_url(repo, rev, project_name)\n\n    def is_commit_id_equal(self, dest, name):\n        \"\"\"Always assume the versions don't match\"\"\"\n        return False\n\n\nvcs.register(Subversion)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_internal/wheel.py",
    "content": "\"\"\"\nSupport for installing and building the \"wheel\" binary package format.\n\"\"\"\nfrom __future__ import absolute_import\n\nimport collections\nimport compileall\nimport csv\nimport hashlib\nimport logging\nimport os.path\nimport re\nimport shutil\nimport stat\nimport sys\nimport warnings\nfrom base64 import urlsafe_b64encode\nfrom email.parser import Parser\n\nfrom pip._vendor import pkg_resources\nfrom pip._vendor.distlib.scripts import ScriptMaker\nfrom pip._vendor.packaging.utils import canonicalize_name\nfrom pip._vendor.six import StringIO\n\nfrom pip._internal import pep425tags\nfrom pip._internal.download import path_to_url, unpack_url\nfrom pip._internal.exceptions import (\n    InstallationError, InvalidWheelFilename, UnsupportedWheel,\n)\nfrom pip._internal.locations import (\n    PIP_DELETE_MARKER_FILENAME, distutils_scheme,\n)\nfrom pip._internal.models.link import Link\nfrom pip._internal.utils.logging import indent_log\nfrom pip._internal.utils.misc import (\n    call_subprocess, captured_stdout, ensure_dir, read_chunks,\n)\nfrom pip._internal.utils.setuptools_build import SETUPTOOLS_SHIM\nfrom pip._internal.utils.temp_dir import TempDirectory\nfrom pip._internal.utils.typing import MYPY_CHECK_RUNNING\nfrom pip._internal.utils.ui import open_spinner\n\nif MYPY_CHECK_RUNNING:\n    from typing import (  # noqa: F401\n        Dict, List, Optional, Sequence, Mapping, Tuple, IO, Text, Any,\n        Union, Iterable\n    )\n    from pip._vendor.packaging.requirements import Requirement  # noqa: F401\n    from pip._internal.req.req_install import InstallRequirement  # noqa: F401\n    from pip._internal.download import PipSession  # noqa: F401\n    from pip._internal.index import FormatControl, PackageFinder  # noqa: F401\n    from pip._internal.operations.prepare import (  # noqa: F401\n        RequirementPreparer\n    )\n    from pip._internal.cache import WheelCache  # noqa: F401\n    from pip._internal.pep425tags import Pep425Tag  # noqa: F401\n\n    InstalledCSVRow = Tuple[str, ...]\n\n\nVERSION_COMPATIBLE = (1, 0)\n\n\nlogger = logging.getLogger(__name__)\n\n\ndef normpath(src, p):\n    return os.path.relpath(src, p).replace(os.path.sep, '/')\n\n\ndef rehash(path, blocksize=1 << 20):\n    # type: (str, int) -> Tuple[str, str]\n    \"\"\"Return (hash, length) for path using hashlib.sha256()\"\"\"\n    h = hashlib.sha256()\n    length = 0\n    with open(path, 'rb') as f:\n        for block in read_chunks(f, size=blocksize):\n            length += len(block)\n            h.update(block)\n    digest = 'sha256=' + urlsafe_b64encode(\n        h.digest()\n    ).decode('latin1').rstrip('=')\n    # unicode/str python2 issues\n    return (digest, str(length))  # type: ignore\n\n\ndef open_for_csv(name, mode):\n    # type: (str, Text) -> IO\n    if sys.version_info[0] < 3:\n        nl = {}  # type: Dict[str, Any]\n        bin = 'b'\n    else:\n        nl = {'newline': ''}  # type: Dict[str, Any]\n        bin = ''\n    return open(name, mode + bin, **nl)\n\n\ndef replace_python_tag(wheelname, new_tag):\n    # type: (str, str) -> str\n    \"\"\"Replace the Python tag in a wheel file name with a new value.\n    \"\"\"\n    parts = wheelname.split('-')\n    parts[-3] = new_tag\n    return '-'.join(parts)\n\n\ndef fix_script(path):\n    # type: (str) -> Optional[bool]\n    \"\"\"Replace #!python with #!/path/to/python\n    Return True if file was changed.\"\"\"\n    # XXX RECORD hashes will need to be updated\n    if os.path.isfile(path):\n        with open(path, 'rb') as script:\n            firstline = script.readline()\n            if not firstline.startswith(b'#!python'):\n                return False\n            exename = sys.executable.encode(sys.getfilesystemencoding())\n            firstline = b'#!' + exename + os.linesep.encode(\"ascii\")\n            rest = script.read()\n        with open(path, 'wb') as script:\n            script.write(firstline)\n            script.write(rest)\n        return True\n    return None\n\n\ndist_info_re = re.compile(r\"\"\"^(?P<namever>(?P<name>.+?)(-(?P<ver>.+?))?)\n                                \\.dist-info$\"\"\", re.VERBOSE)\n\n\ndef root_is_purelib(name, wheeldir):\n    # type: (str, str) -> bool\n    \"\"\"\n    Return True if the extracted wheel in wheeldir should go into purelib.\n    \"\"\"\n    name_folded = name.replace(\"-\", \"_\")\n    for item in os.listdir(wheeldir):\n        match = dist_info_re.match(item)\n        if match and match.group('name') == name_folded:\n            with open(os.path.join(wheeldir, item, 'WHEEL')) as wheel:\n                for line in wheel:\n                    line = line.lower().rstrip()\n                    if line == \"root-is-purelib: true\":\n                        return True\n    return False\n\n\ndef get_entrypoints(filename):\n    # type: (str) -> Tuple[Dict[str, str], Dict[str, str]]\n    if not os.path.exists(filename):\n        return {}, {}\n\n    # This is done because you can pass a string to entry_points wrappers which\n    # means that they may or may not be valid INI files. The attempt here is to\n    # strip leading and trailing whitespace in order to make them valid INI\n    # files.\n    with open(filename) as fp:\n        data = StringIO()\n        for line in fp:\n            data.write(line.strip())\n            data.write(\"\\n\")\n        data.seek(0)\n\n    # get the entry points and then the script names\n    entry_points = pkg_resources.EntryPoint.parse_map(data)\n    console = entry_points.get('console_scripts', {})\n    gui = entry_points.get('gui_scripts', {})\n\n    def _split_ep(s):\n        \"\"\"get the string representation of EntryPoint, remove space and split\n        on '='\"\"\"\n        return str(s).replace(\" \", \"\").split(\"=\")\n\n    # convert the EntryPoint objects into strings with module:function\n    console = dict(_split_ep(v) for v in console.values())\n    gui = dict(_split_ep(v) for v in gui.values())\n    return console, gui\n\n\ndef message_about_scripts_not_on_PATH(scripts):\n    # type: (Sequence[str]) -> Optional[str]\n    \"\"\"Determine if any scripts are not on PATH and format a warning.\n\n    Returns a warning message if one or more scripts are not on PATH,\n    otherwise None.\n    \"\"\"\n    if not scripts:\n        return None\n\n    # Group scripts by the path they were installed in\n    grouped_by_dir = collections.defaultdict(set)  # type: Dict[str, set]\n    for destfile in scripts:\n        parent_dir = os.path.dirname(destfile)\n        script_name = os.path.basename(destfile)\n        grouped_by_dir[parent_dir].add(script_name)\n\n    # We don't want to warn for directories that are on PATH.\n    not_warn_dirs = [\n        os.path.normcase(i).rstrip(os.sep) for i in\n        os.environ.get(\"PATH\", \"\").split(os.pathsep)\n    ]\n    # If an executable sits with sys.executable, we don't warn for it.\n    #     This covers the case of venv invocations without activating the venv.\n    not_warn_dirs.append(os.path.normcase(os.path.dirname(sys.executable)))\n    warn_for = {\n        parent_dir: scripts for parent_dir, scripts in grouped_by_dir.items()\n        if os.path.normcase(parent_dir) not in not_warn_dirs\n    }\n    if not warn_for:\n        return None\n\n    # Format a message\n    msg_lines = []\n    for parent_dir, scripts in warn_for.items():\n        scripts = sorted(scripts)\n        if len(scripts) == 1:\n            start_text = \"script {} is\".format(scripts[0])\n        else:\n            start_text = \"scripts {} are\".format(\n                \", \".join(scripts[:-1]) + \" and \" + scripts[-1]\n            )\n\n        msg_lines.append(\n            \"The {} installed in '{}' which is not on PATH.\"\n            .format(start_text, parent_dir)\n        )\n\n    last_line_fmt = (\n        \"Consider adding {} to PATH or, if you prefer \"\n        \"to suppress this warning, use --no-warn-script-location.\"\n    )\n    if len(msg_lines) == 1:\n        msg_lines.append(last_line_fmt.format(\"this directory\"))\n    else:\n        msg_lines.append(last_line_fmt.format(\"these directories\"))\n\n    # Returns the formatted multiline message\n    return \"\\n\".join(msg_lines)\n\n\ndef sorted_outrows(outrows):\n    # type: (Iterable[InstalledCSVRow]) -> List[InstalledCSVRow]\n    \"\"\"\n    Return the given rows of a RECORD file in sorted order.\n\n    Each row is a 3-tuple (path, hash, size) and corresponds to a record of\n    a RECORD file (see PEP 376 and PEP 427 for details).  For the rows\n    passed to this function, the size can be an integer as an int or string,\n    or the empty string.\n    \"\"\"\n    # Normally, there should only be one row per path, in which case the\n    # second and third elements don't come into play when sorting.\n    # However, in cases in the wild where a path might happen to occur twice,\n    # we don't want the sort operation to trigger an error (but still want\n    # determinism).  Since the third element can be an int or string, we\n    # coerce each element to a string to avoid a TypeError in this case.\n    # For additional background, see--\n    # https://github.com/pypa/pip/issues/5868\n    return sorted(outrows, key=lambda row: tuple(str(x) for x in row))\n\n\ndef get_csv_rows_for_installed(\n    old_csv_rows,  # type: Iterable[List[str]]\n    installed,  # type: Dict[str, str]\n    changed,  # type: set\n    generated,  # type: List[str]\n    lib_dir,  # type: str\n):\n    # type: (...) -> List[InstalledCSVRow]\n    \"\"\"\n    :param installed: A map from archive RECORD path to installation RECORD\n        path.\n    \"\"\"\n    installed_rows = []  # type: List[InstalledCSVRow]\n    for row in old_csv_rows:\n        if len(row) > 3:\n            logger.warning(\n                'RECORD line has more than three elements: {}'.format(row)\n            )\n        # Make a copy because we are mutating the row.\n        row = list(row)\n        old_path = row[0]\n        new_path = installed.pop(old_path, old_path)\n        row[0] = new_path\n        if new_path in changed:\n            digest, length = rehash(new_path)\n            row[1] = digest\n            row[2] = length\n        installed_rows.append(tuple(row))\n    for f in generated:\n        digest, length = rehash(f)\n        installed_rows.append((normpath(f, lib_dir), digest, str(length)))\n    for f in installed:\n        installed_rows.append((installed[f], '', ''))\n    return installed_rows\n\n\ndef move_wheel_files(\n    name,  # type: str\n    req,  # type: Requirement\n    wheeldir,  # type: str\n    user=False,  # type: bool\n    home=None,  # type: Optional[str]\n    root=None,  # type: Optional[str]\n    pycompile=True,  # type: bool\n    scheme=None,  # type: Optional[Mapping[str, str]]\n    isolated=False,  # type: bool\n    prefix=None,  # type: Optional[str]\n    warn_script_location=True  # type: bool\n):\n    # type: (...) -> None\n    \"\"\"Install a wheel\"\"\"\n    # TODO: Investigate and break this up.\n    # TODO: Look into moving this into a dedicated class for representing an\n    #       installation.\n\n    if not scheme:\n        scheme = distutils_scheme(\n            name, user=user, home=home, root=root, isolated=isolated,\n            prefix=prefix,\n        )\n\n    if root_is_purelib(name, wheeldir):\n        lib_dir = scheme['purelib']\n    else:\n        lib_dir = scheme['platlib']\n\n    info_dir = []  # type: List[str]\n    data_dirs = []\n    source = wheeldir.rstrip(os.path.sep) + os.path.sep\n\n    # Record details of the files moved\n    #   installed = files copied from the wheel to the destination\n    #   changed = files changed while installing (scripts #! line typically)\n    #   generated = files newly generated during the install (script wrappers)\n    installed = {}  # type: Dict[str, str]\n    changed = set()\n    generated = []  # type: List[str]\n\n    # Compile all of the pyc files that we're going to be installing\n    if pycompile:\n        with captured_stdout() as stdout:\n            with warnings.catch_warnings():\n                warnings.filterwarnings('ignore')\n                compileall.compile_dir(source, force=True, quiet=True)\n        logger.debug(stdout.getvalue())\n\n    def record_installed(srcfile, destfile, modified=False):\n        \"\"\"Map archive RECORD paths to installation RECORD paths.\"\"\"\n        oldpath = normpath(srcfile, wheeldir)\n        newpath = normpath(destfile, lib_dir)\n        installed[oldpath] = newpath\n        if modified:\n            changed.add(destfile)\n\n    def clobber(source, dest, is_base, fixer=None, filter=None):\n        ensure_dir(dest)  # common for the 'include' path\n\n        for dir, subdirs, files in os.walk(source):\n            basedir = dir[len(source):].lstrip(os.path.sep)\n            destdir = os.path.join(dest, basedir)\n            if is_base and basedir.split(os.path.sep, 1)[0].endswith('.data'):\n                continue\n            for s in subdirs:\n                destsubdir = os.path.join(dest, basedir, s)\n                if is_base and basedir == '' and destsubdir.endswith('.data'):\n                    data_dirs.append(s)\n                    continue\n                elif (is_base and\n                        s.endswith('.dist-info') and\n                        canonicalize_name(s).startswith(\n                            canonicalize_name(req.name))):\n                    assert not info_dir, ('Multiple .dist-info directories: ' +\n                                          destsubdir + ', ' +\n                                          ', '.join(info_dir))\n                    info_dir.append(destsubdir)\n            for f in files:\n                # Skip unwanted files\n                if filter and filter(f):\n                    continue\n                srcfile = os.path.join(dir, f)\n                destfile = os.path.join(dest, basedir, f)\n                # directory creation is lazy and after the file filtering above\n                # to ensure we don't install empty dirs; empty dirs can't be\n                # uninstalled.\n                ensure_dir(destdir)\n\n                # copyfile (called below) truncates the destination if it\n                # exists and then writes the new contents. This is fine in most\n                # cases, but can cause a segfault if pip has loaded a shared\n                # object (e.g. from pyopenssl through its vendored urllib3)\n                # Since the shared object is mmap'd an attempt to call a\n                # symbol in it will then cause a segfault. Unlinking the file\n                # allows writing of new contents while allowing the process to\n                # continue to use the old copy.\n                if os.path.exists(destfile):\n                    os.unlink(destfile)\n\n                # We use copyfile (not move, copy, or copy2) to be extra sure\n                # that we are not moving directories over (copyfile fails for\n                # directories) as well as to ensure that we are not copying\n                # over any metadata because we want more control over what\n                # metadata we actually copy over.\n                shutil.copyfile(srcfile, destfile)\n\n                # Copy over the metadata for the file, currently this only\n                # includes the atime and mtime.\n                st = os.stat(srcfile)\n                if hasattr(os, \"utime\"):\n                    os.utime(destfile, (st.st_atime, st.st_mtime))\n\n                # If our file is executable, then make our destination file\n                # executable.\n                if os.access(srcfile, os.X_OK):\n                    st = os.stat(srcfile)\n                    permissions = (\n                        st.st_mode | stat.S_IXUSR | stat.S_IXGRP | stat.S_IXOTH\n                    )\n                    os.chmod(destfile, permissions)\n\n                changed = False\n                if fixer:\n                    changed = fixer(destfile)\n                record_installed(srcfile, destfile, changed)\n\n    clobber(source, lib_dir, True)\n\n    assert info_dir, \"%s .dist-info directory not found\" % req\n\n    # Get the defined entry points\n    ep_file = os.path.join(info_dir[0], 'entry_points.txt')\n    console, gui = get_entrypoints(ep_file)\n\n    def is_entrypoint_wrapper(name):\n        # EP, EP.exe and EP-script.py are scripts generated for\n        # entry point EP by setuptools\n        if name.lower().endswith('.exe'):\n            matchname = name[:-4]\n        elif name.lower().endswith('-script.py'):\n            matchname = name[:-10]\n        elif name.lower().endswith(\".pya\"):\n            matchname = name[:-4]\n        else:\n            matchname = name\n        # Ignore setuptools-generated scripts\n        return (matchname in console or matchname in gui)\n\n    for datadir in data_dirs:\n        fixer = None\n        filter = None\n        for subdir in os.listdir(os.path.join(wheeldir, datadir)):\n            fixer = None\n            if subdir == 'scripts':\n                fixer = fix_script\n                filter = is_entrypoint_wrapper\n            source = os.path.join(wheeldir, datadir, subdir)\n            dest = scheme[subdir]\n            clobber(source, dest, False, fixer=fixer, filter=filter)\n\n    maker = ScriptMaker(None, scheme['scripts'])\n\n    # Ensure old scripts are overwritten.\n    # See https://github.com/pypa/pip/issues/1800\n    maker.clobber = True\n\n    # Ensure we don't generate any variants for scripts because this is almost\n    # never what somebody wants.\n    # See https://bitbucket.org/pypa/distlib/issue/35/\n    maker.variants = {''}\n\n    # This is required because otherwise distlib creates scripts that are not\n    # executable.\n    # See https://bitbucket.org/pypa/distlib/issue/32/\n    maker.set_mode = True\n\n    # Simplify the script and fix the fact that the default script swallows\n    # every single stack trace.\n    # See https://bitbucket.org/pypa/distlib/issue/34/\n    # See https://bitbucket.org/pypa/distlib/issue/33/\n    def _get_script_text(entry):\n        if entry.suffix is None:\n            raise InstallationError(\n                \"Invalid script entry point: %s for req: %s - A callable \"\n                \"suffix is required. Cf https://packaging.python.org/en/\"\n                \"latest/distributing.html#console-scripts for more \"\n                \"information.\" % (entry, req)\n            )\n        return maker.script_template % {\n            \"module\": entry.prefix,\n            \"import_name\": entry.suffix.split(\".\")[0],\n            \"func\": entry.suffix,\n        }\n    # ignore type, because mypy disallows assigning to a method,\n    # see https://github.com/python/mypy/issues/2427\n    maker._get_script_text = _get_script_text  # type: ignore\n    maker.script_template = r\"\"\"# -*- coding: utf-8 -*-\nimport re\nimport sys\n\nfrom %(module)s import %(import_name)s\n\nif __name__ == '__main__':\n    sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n    sys.exit(%(func)s())\n\"\"\"\n\n    # Special case pip and setuptools to generate versioned wrappers\n    #\n    # The issue is that some projects (specifically, pip and setuptools) use\n    # code in setup.py to create \"versioned\" entry points - pip2.7 on Python\n    # 2.7, pip3.3 on Python 3.3, etc. But these entry points are baked into\n    # the wheel metadata at build time, and so if the wheel is installed with\n    # a *different* version of Python the entry points will be wrong. The\n    # correct fix for this is to enhance the metadata to be able to describe\n    # such versioned entry points, but that won't happen till Metadata 2.0 is\n    # available.\n    # In the meantime, projects using versioned entry points will either have\n    # incorrect versioned entry points, or they will not be able to distribute\n    # \"universal\" wheels (i.e., they will need a wheel per Python version).\n    #\n    # Because setuptools and pip are bundled with _ensurepip and virtualenv,\n    # we need to use universal wheels. So, as a stopgap until Metadata 2.0, we\n    # override the versioned entry points in the wheel and generate the\n    # correct ones. This code is purely a short-term measure until Metadata 2.0\n    # is available.\n    #\n    # To add the level of hack in this section of code, in order to support\n    # ensurepip this code will look for an ``ENSUREPIP_OPTIONS`` environment\n    # variable which will control which version scripts get installed.\n    #\n    # ENSUREPIP_OPTIONS=altinstall\n    #   - Only pipX.Y and easy_install-X.Y will be generated and installed\n    # ENSUREPIP_OPTIONS=install\n    #   - pipX.Y, pipX, easy_install-X.Y will be generated and installed. Note\n    #     that this option is technically if ENSUREPIP_OPTIONS is set and is\n    #     not altinstall\n    # DEFAULT\n    #   - The default behavior is to install pip, pipX, pipX.Y, easy_install\n    #     and easy_install-X.Y.\n    pip_script = console.pop('pip', None)\n    if pip_script:\n        if \"ENSUREPIP_OPTIONS\" not in os.environ:\n            spec = 'pip = ' + pip_script\n            generated.extend(maker.make(spec))\n\n        if os.environ.get(\"ENSUREPIP_OPTIONS\", \"\") != \"altinstall\":\n            spec = 'pip%s = %s' % (sys.version[:1], pip_script)\n            generated.extend(maker.make(spec))\n\n        spec = 'pip%s = %s' % (sys.version[:3], pip_script)\n        generated.extend(maker.make(spec))\n        # Delete any other versioned pip entry points\n        pip_ep = [k for k in console if re.match(r'pip(\\d(\\.\\d)?)?$', k)]\n        for k in pip_ep:\n            del console[k]\n    easy_install_script = console.pop('easy_install', None)\n    if easy_install_script:\n        if \"ENSUREPIP_OPTIONS\" not in os.environ:\n            spec = 'easy_install = ' + easy_install_script\n            generated.extend(maker.make(spec))\n\n        spec = 'easy_install-%s = %s' % (sys.version[:3], easy_install_script)\n        generated.extend(maker.make(spec))\n        # Delete any other versioned easy_install entry points\n        easy_install_ep = [\n            k for k in console if re.match(r'easy_install(-\\d\\.\\d)?$', k)\n        ]\n        for k in easy_install_ep:\n            del console[k]\n\n    # Generate the console and GUI entry points specified in the wheel\n    if len(console) > 0:\n        generated_console_scripts = maker.make_multiple(\n            ['%s = %s' % kv for kv in console.items()]\n        )\n        generated.extend(generated_console_scripts)\n\n        if warn_script_location:\n            msg = message_about_scripts_not_on_PATH(generated_console_scripts)\n            if msg is not None:\n                logger.warning(msg)\n\n    if len(gui) > 0:\n        generated.extend(\n            maker.make_multiple(\n                ['%s = %s' % kv for kv in gui.items()],\n                {'gui': True}\n            )\n        )\n\n    # Record pip as the installer\n    installer = os.path.join(info_dir[0], 'INSTALLER')\n    temp_installer = os.path.join(info_dir[0], 'INSTALLER.pip')\n    with open(temp_installer, 'wb') as installer_file:\n        installer_file.write(b'pip\\n')\n    shutil.move(temp_installer, installer)\n    generated.append(installer)\n\n    # Record details of all files installed\n    record = os.path.join(info_dir[0], 'RECORD')\n    temp_record = os.path.join(info_dir[0], 'RECORD.pip')\n    with open_for_csv(record, 'r') as record_in:\n        with open_for_csv(temp_record, 'w+') as record_out:\n            reader = csv.reader(record_in)\n            outrows = get_csv_rows_for_installed(\n                reader, installed=installed, changed=changed,\n                generated=generated, lib_dir=lib_dir,\n            )\n            writer = csv.writer(record_out)\n            # Sort to simplify testing.\n            for row in sorted_outrows(outrows):\n                writer.writerow(row)\n    shutil.move(temp_record, record)\n\n\ndef wheel_version(source_dir):\n    # type: (Optional[str]) -> Optional[Tuple[int, ...]]\n    \"\"\"\n    Return the Wheel-Version of an extracted wheel, if possible.\n\n    Otherwise, return None if we couldn't parse / extract it.\n    \"\"\"\n    try:\n        dist = [d for d in pkg_resources.find_on_path(None, source_dir)][0]\n\n        wheel_data = dist.get_metadata('WHEEL')\n        wheel_data = Parser().parsestr(wheel_data)\n\n        version = wheel_data['Wheel-Version'].strip()\n        version = tuple(map(int, version.split('.')))\n        return version\n    except Exception:\n        return None\n\n\ndef check_compatibility(version, name):\n    # type: (Optional[Tuple[int, ...]], str) -> None\n    \"\"\"\n    Raises errors or warns if called with an incompatible Wheel-Version.\n\n    Pip should refuse to install a Wheel-Version that's a major series\n    ahead of what it's compatible with (e.g 2.0 > 1.1); and warn when\n    installing a version only minor version ahead (e.g 1.2 > 1.1).\n\n    version: a 2-tuple representing a Wheel-Version (Major, Minor)\n    name: name of wheel or package to raise exception about\n\n    :raises UnsupportedWheel: when an incompatible Wheel-Version is given\n    \"\"\"\n    if not version:\n        raise UnsupportedWheel(\n            \"%s is in an unsupported or invalid wheel\" % name\n        )\n    if version[0] > VERSION_COMPATIBLE[0]:\n        raise UnsupportedWheel(\n            \"%s's Wheel-Version (%s) is not compatible with this version \"\n            \"of pip\" % (name, '.'.join(map(str, version)))\n        )\n    elif version > VERSION_COMPATIBLE:\n        logger.warning(\n            'Installing from a newer Wheel-Version (%s)',\n            '.'.join(map(str, version)),\n        )\n\n\nclass Wheel(object):\n    \"\"\"A wheel file\"\"\"\n\n    # TODO: Maybe move the class into the models sub-package\n    # TODO: Maybe move the install code into this class\n\n    wheel_file_re = re.compile(\n        r\"\"\"^(?P<namever>(?P<name>.+?)-(?P<ver>.*?))\n        ((-(?P<build>\\d[^-]*?))?-(?P<pyver>.+?)-(?P<abi>.+?)-(?P<plat>.+?)\n        \\.whl|\\.dist-info)$\"\"\",\n        re.VERBOSE\n    )\n\n    def __init__(self, filename):\n        # type: (str) -> None\n        \"\"\"\n        :raises InvalidWheelFilename: when the filename is invalid for a wheel\n        \"\"\"\n        wheel_info = self.wheel_file_re.match(filename)\n        if not wheel_info:\n            raise InvalidWheelFilename(\n                \"%s is not a valid wheel filename.\" % filename\n            )\n        self.filename = filename\n        self.name = wheel_info.group('name').replace('_', '-')\n        # we'll assume \"_\" means \"-\" due to wheel naming scheme\n        # (https://github.com/pypa/pip/issues/1150)\n        self.version = wheel_info.group('ver').replace('_', '-')\n        self.build_tag = wheel_info.group('build')\n        self.pyversions = wheel_info.group('pyver').split('.')\n        self.abis = wheel_info.group('abi').split('.')\n        self.plats = wheel_info.group('plat').split('.')\n\n        # All the tag combinations from this file\n        self.file_tags = {\n            (x, y, z) for x in self.pyversions\n            for y in self.abis for z in self.plats\n        }\n\n    def support_index_min(self, tags=None):\n        # type: (Optional[List[Pep425Tag]]) -> Optional[int]\n        \"\"\"\n        Return the lowest index that one of the wheel's file_tag combinations\n        achieves in the supported_tags list e.g. if there are 8 supported tags,\n        and one of the file tags is first in the list, then return 0.  Returns\n        None is the wheel is not supported.\n        \"\"\"\n        if tags is None:  # for mock\n            tags = pep425tags.get_supported()\n        indexes = [tags.index(c) for c in self.file_tags if c in tags]\n        return min(indexes) if indexes else None\n\n    def supported(self, tags=None):\n        # type: (Optional[List[Pep425Tag]]) -> bool\n        \"\"\"Is this wheel supported on this system?\"\"\"\n        if tags is None:  # for mock\n            tags = pep425tags.get_supported()\n        return bool(set(tags).intersection(self.file_tags))\n\n\ndef _contains_egg_info(\n        s, _egg_info_re=re.compile(r'([a-z0-9_.]+)-([a-z0-9_.!+-]+)', re.I)):\n    \"\"\"Determine whether the string looks like an egg_info.\n\n    :param s: The string to parse. E.g. foo-2.1\n    \"\"\"\n    return bool(_egg_info_re.search(s))\n\n\ndef should_use_ephemeral_cache(\n    req,  # type: InstallRequirement\n    format_control,  # type: FormatControl\n    autobuilding,  # type: bool\n    cache_available  # type: bool\n):\n    # type: (...) -> Optional[bool]\n    \"\"\"\n    Return whether to build an InstallRequirement object using the\n    ephemeral cache.\n\n    :param cache_available: whether a cache directory is available for the\n        autobuilding=True case.\n\n    :return: True or False to build the requirement with ephem_cache=True\n        or False, respectively; or None not to build the requirement.\n    \"\"\"\n    if req.constraint:\n        return None\n    if req.is_wheel:\n        if not autobuilding:\n            logger.info(\n                'Skipping %s, due to already being wheel.', req.name,\n            )\n        return None\n    if not autobuilding:\n        return False\n\n    if req.editable or not req.source_dir:\n        return None\n\n    if req.link and not req.link.is_artifact:\n        # VCS checkout. Build wheel just for this run.\n        return True\n\n    if \"binary\" not in format_control.get_allowed_formats(\n            canonicalize_name(req.name)):\n        logger.info(\n            \"Skipping bdist_wheel for %s, due to binaries \"\n            \"being disabled for it.\", req.name,\n        )\n        return None\n\n    link = req.link\n    base, ext = link.splitext()\n    if cache_available and _contains_egg_info(base):\n        return False\n\n    # Otherwise, build the wheel just for this run using the ephemeral\n    # cache since we are either in the case of e.g. a local directory, or\n    # no cache directory is available to use.\n    return True\n\n\ndef format_command(\n    command_args,  # type: List[str]\n    command_output,  # type: str\n):\n    # type: (...) -> str\n    \"\"\"\n    Format command information for logging.\n    \"\"\"\n    text = 'Command arguments: {}\\n'.format(command_args)\n\n    if not command_output:\n        text += 'Command output: None'\n    elif logger.getEffectiveLevel() > logging.DEBUG:\n        text += 'Command output: [use --verbose to show]'\n    else:\n        if not command_output.endswith('\\n'):\n            command_output += '\\n'\n        text += (\n            'Command output:\\n{}'\n            '-----------------------------------------'\n        ).format(command_output)\n\n    return text\n\n\ndef get_legacy_build_wheel_path(\n    names,  # type: List[str]\n    temp_dir,  # type: str\n    req,  # type: InstallRequirement\n    command_args,  # type: List[str]\n    command_output,  # type: str\n):\n    # type: (...) -> Optional[str]\n    \"\"\"\n    Return the path to the wheel in the temporary build directory.\n    \"\"\"\n    # Sort for determinism.\n    names = sorted(names)\n    if not names:\n        msg = (\n            'Legacy build of wheel for {!r} created no files.\\n'\n        ).format(req.name)\n        msg += format_command(command_args, command_output)\n        logger.warning(msg)\n        return None\n\n    if len(names) > 1:\n        msg = (\n            'Legacy build of wheel for {!r} created more than one file.\\n'\n            'Filenames (choosing first): {}\\n'\n        ).format(req.name, names)\n        msg += format_command(command_args, command_output)\n        logger.warning(msg)\n\n    return os.path.join(temp_dir, names[0])\n\n\nclass WheelBuilder(object):\n    \"\"\"Build wheels from a RequirementSet.\"\"\"\n\n    def __init__(\n        self,\n        finder,  # type: PackageFinder\n        preparer,  # type: RequirementPreparer\n        wheel_cache,  # type: WheelCache\n        build_options=None,  # type: Optional[List[str]]\n        global_options=None,  # type: Optional[List[str]]\n        no_clean=False  # type: bool\n    ):\n        # type: (...) -> None\n        self.finder = finder\n        self.preparer = preparer\n        self.wheel_cache = wheel_cache\n\n        self._wheel_dir = preparer.wheel_download_dir\n\n        self.build_options = build_options or []\n        self.global_options = global_options or []\n        self.no_clean = no_clean\n\n    def _build_one(self, req, output_dir, python_tag=None):\n        \"\"\"Build one wheel.\n\n        :return: The filename of the built wheel, or None if the build failed.\n        \"\"\"\n        # Install build deps into temporary directory (PEP 518)\n        with req.build_env:\n            return self._build_one_inside_env(req, output_dir,\n                                              python_tag=python_tag)\n\n    def _build_one_inside_env(self, req, output_dir, python_tag=None):\n        with TempDirectory(kind=\"wheel\") as temp_dir:\n            if req.use_pep517:\n                builder = self._build_one_pep517\n            else:\n                builder = self._build_one_legacy\n            wheel_path = builder(req, temp_dir.path, python_tag=python_tag)\n            if wheel_path is not None:\n                wheel_name = os.path.basename(wheel_path)\n                dest_path = os.path.join(output_dir, wheel_name)\n                try:\n                    shutil.move(wheel_path, dest_path)\n                    logger.info('Stored in directory: %s', output_dir)\n                    return dest_path\n                except Exception:\n                    pass\n            # Ignore return, we can't do anything else useful.\n            self._clean_one(req)\n            return None\n\n    def _base_setup_args(self, req):\n        # NOTE: Eventually, we'd want to also -S to the flags here, when we're\n        # isolating. Currently, it breaks Python in virtualenvs, because it\n        # relies on site.py to find parts of the standard library outside the\n        # virtualenv.\n        return [\n            sys.executable, '-u', '-c',\n            SETUPTOOLS_SHIM % req.setup_py\n        ] + list(self.global_options)\n\n    def _build_one_pep517(self, req, tempd, python_tag=None):\n        \"\"\"Build one InstallRequirement using the PEP 517 build process.\n\n        Returns path to wheel if successfully built. Otherwise, returns None.\n        \"\"\"\n        assert req.metadata_directory is not None\n        try:\n            req.spin_message = 'Building wheel for %s (PEP 517)' % (req.name,)\n            logger.debug('Destination directory: %s', tempd)\n            wheel_name = req.pep517_backend.build_wheel(\n                tempd,\n                metadata_directory=req.metadata_directory\n            )\n            if python_tag:\n                # General PEP 517 backends don't necessarily support\n                # a \"--python-tag\" option, so we rename the wheel\n                # file directly.\n                new_name = replace_python_tag(wheel_name, python_tag)\n                os.rename(\n                    os.path.join(tempd, wheel_name),\n                    os.path.join(tempd, new_name)\n                )\n                # Reassign to simplify the return at the end of function\n                wheel_name = new_name\n        except Exception:\n            logger.error('Failed building wheel for %s', req.name)\n            return None\n        return os.path.join(tempd, wheel_name)\n\n    def _build_one_legacy(self, req, tempd, python_tag=None):\n        \"\"\"Build one InstallRequirement using the \"legacy\" build process.\n\n        Returns path to wheel if successfully built. Otherwise, returns None.\n        \"\"\"\n        base_args = self._base_setup_args(req)\n\n        spin_message = 'Building wheel for %s (setup.py)' % (req.name,)\n        with open_spinner(spin_message) as spinner:\n            logger.debug('Destination directory: %s', tempd)\n            wheel_args = base_args + ['bdist_wheel', '-d', tempd] \\\n                + self.build_options\n\n            if python_tag is not None:\n                wheel_args += [\"--python-tag\", python_tag]\n\n            try:\n                output = call_subprocess(wheel_args, cwd=req.setup_py_dir,\n                                         show_stdout=False, spinner=spinner)\n            except Exception:\n                spinner.finish(\"error\")\n                logger.error('Failed building wheel for %s', req.name)\n                return None\n            names = os.listdir(tempd)\n            wheel_path = get_legacy_build_wheel_path(\n                names=names,\n                temp_dir=tempd,\n                req=req,\n                command_args=wheel_args,\n                command_output=output,\n            )\n            return wheel_path\n\n    def _clean_one(self, req):\n        base_args = self._base_setup_args(req)\n\n        logger.info('Running setup.py clean for %s', req.name)\n        clean_args = base_args + ['clean', '--all']\n        try:\n            call_subprocess(clean_args, cwd=req.source_dir, show_stdout=False)\n            return True\n        except Exception:\n            logger.error('Failed cleaning build dir for %s', req.name)\n            return False\n\n    def build(\n        self,\n        requirements,  # type: Iterable[InstallRequirement]\n        session,  # type: PipSession\n        autobuilding=False  # type: bool\n    ):\n        # type: (...) -> List[InstallRequirement]\n        \"\"\"Build wheels.\n\n        :param unpack: If True, replace the sdist we built from with the\n            newly built wheel, in preparation for installation.\n        :return: True if all the wheels built correctly.\n        \"\"\"\n        buildset = []\n        format_control = self.finder.format_control\n        # Whether a cache directory is available for autobuilding=True.\n        cache_available = bool(self._wheel_dir or self.wheel_cache.cache_dir)\n\n        for req in requirements:\n            ephem_cache = should_use_ephemeral_cache(\n                req, format_control=format_control, autobuilding=autobuilding,\n                cache_available=cache_available,\n            )\n            if ephem_cache is None:\n                continue\n\n            buildset.append((req, ephem_cache))\n\n        if not buildset:\n            return []\n\n        # Is any wheel build not using the ephemeral cache?\n        if any(not ephem_cache for _, ephem_cache in buildset):\n            have_directory_for_build = self._wheel_dir or (\n                autobuilding and self.wheel_cache.cache_dir\n            )\n            assert have_directory_for_build\n\n        # TODO by @pradyunsg\n        # Should break up this method into 2 separate methods.\n\n        # Build the wheels.\n        logger.info(\n            'Building wheels for collected packages: %s',\n            ', '.join([req.name for (req, _) in buildset]),\n        )\n        _cache = self.wheel_cache  # shorter name\n        with indent_log():\n            build_success, build_failure = [], []\n            for req, ephem in buildset:\n                python_tag = None\n                if autobuilding:\n                    python_tag = pep425tags.implementation_tag\n                    if ephem:\n                        output_dir = _cache.get_ephem_path_for_link(req.link)\n                    else:\n                        output_dir = _cache.get_path_for_link(req.link)\n                    try:\n                        ensure_dir(output_dir)\n                    except OSError as e:\n                        logger.warning(\"Building wheel for %s failed: %s\",\n                                       req.name, e)\n                        build_failure.append(req)\n                        continue\n                else:\n                    output_dir = self._wheel_dir\n                wheel_file = self._build_one(\n                    req, output_dir,\n                    python_tag=python_tag,\n                )\n                if wheel_file:\n                    build_success.append(req)\n                    if autobuilding:\n                        # XXX: This is mildly duplicative with prepare_files,\n                        # but not close enough to pull out to a single common\n                        # method.\n                        # The code below assumes temporary source dirs -\n                        # prevent it doing bad things.\n                        if req.source_dir and not os.path.exists(os.path.join(\n                                req.source_dir, PIP_DELETE_MARKER_FILENAME)):\n                            raise AssertionError(\n                                \"bad source dir - missing marker\")\n                        # Delete the source we built the wheel from\n                        req.remove_temporary_source()\n                        # set the build directory again - name is known from\n                        # the work prepare_files did.\n                        req.source_dir = req.build_location(\n                            self.preparer.build_dir\n                        )\n                        # Update the link for this.\n                        req.link = Link(path_to_url(wheel_file))\n                        assert req.link.is_wheel\n                        # extract the wheel into the dir\n                        unpack_url(\n                            req.link, req.source_dir, None, False,\n                            session=session,\n                        )\n                else:\n                    build_failure.append(req)\n\n        # notify success/failure\n        if build_success:\n            logger.info(\n                'Successfully built %s',\n                ' '.join([req.name for req in build_success]),\n            )\n        if build_failure:\n            logger.info(\n                'Failed to build %s',\n                ' '.join([req.name for req in build_failure]),\n            )\n        # Return a list of requirements that failed to build\n        return build_failure\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/__init__.py",
    "content": "\"\"\"\npip._vendor is for vendoring dependencies of pip to prevent needing pip to\ndepend on something external.\n\nFiles inside of pip._vendor should be considered immutable and should only be\nupdated to versions from upstream.\n\"\"\"\nfrom __future__ import absolute_import\n\nimport glob\nimport os.path\nimport sys\n\n# Downstream redistributors which have debundled our dependencies should also\n# patch this value to be true. This will trigger the additional patching\n# to cause things like \"six\" to be available as pip.\nDEBUNDLED = False\n\n# By default, look in this directory for a bunch of .whl files which we will\n# add to the beginning of sys.path before attempting to import anything. This\n# is done to support downstream re-distributors like Debian and Fedora who\n# wish to create their own Wheels for our dependencies to aid in debundling.\nWHEEL_DIR = os.path.abspath(os.path.dirname(__file__))\n\n\n# Define a small helper function to alias our vendored modules to the real ones\n# if the vendored ones do not exist. This idea of this was taken from\n# https://github.com/kennethreitz/requests/pull/2567.\ndef vendored(modulename):\n    vendored_name = \"{0}.{1}\".format(__name__, modulename)\n\n    try:\n        __import__(vendored_name, globals(), locals(), level=0)\n    except ImportError:\n        try:\n            __import__(modulename, globals(), locals(), level=0)\n        except ImportError:\n            # We can just silently allow import failures to pass here. If we\n            # got to this point it means that ``import pip._vendor.whatever``\n            # failed and so did ``import whatever``. Since we're importing this\n            # upfront in an attempt to alias imports, not erroring here will\n            # just mean we get a regular import error whenever pip *actually*\n            # tries to import one of these modules to use it, which actually\n            # gives us a better error message than we would have otherwise\n            # gotten.\n            pass\n        else:\n            sys.modules[vendored_name] = sys.modules[modulename]\n            base, head = vendored_name.rsplit(\".\", 1)\n            setattr(sys.modules[base], head, sys.modules[modulename])\n\n\n# If we're operating in a debundled setup, then we want to go ahead and trigger\n# the aliasing of our vendored libraries as well as looking for wheels to add\n# to our sys.path. This will cause all of this code to be a no-op typically\n# however downstream redistributors can enable it in a consistent way across\n# all platforms.\nif DEBUNDLED:\n    # Actually look inside of WHEEL_DIR to find .whl files and add them to the\n    # front of our sys.path.\n    sys.path[:] = glob.glob(os.path.join(WHEEL_DIR, \"*.whl\")) + sys.path\n\n    # Actually alias all of our vendored dependencies.\n    vendored(\"cachecontrol\")\n    vendored(\"colorama\")\n    vendored(\"distlib\")\n    vendored(\"distro\")\n    vendored(\"html5lib\")\n    vendored(\"lockfile\")\n    vendored(\"six\")\n    vendored(\"six.moves\")\n    vendored(\"six.moves.urllib\")\n    vendored(\"six.moves.urllib.parse\")\n    vendored(\"packaging\")\n    vendored(\"packaging.version\")\n    vendored(\"packaging.specifiers\")\n    vendored(\"pep517\")\n    vendored(\"pkg_resources\")\n    vendored(\"progress\")\n    vendored(\"pytoml\")\n    vendored(\"retrying\")\n    vendored(\"requests\")\n    vendored(\"requests.packages\")\n    vendored(\"requests.packages.urllib3\")\n    vendored(\"requests.packages.urllib3._collections\")\n    vendored(\"requests.packages.urllib3.connection\")\n    vendored(\"requests.packages.urllib3.connectionpool\")\n    vendored(\"requests.packages.urllib3.contrib\")\n    vendored(\"requests.packages.urllib3.contrib.ntlmpool\")\n    vendored(\"requests.packages.urllib3.contrib.pyopenssl\")\n    vendored(\"requests.packages.urllib3.exceptions\")\n    vendored(\"requests.packages.urllib3.fields\")\n    vendored(\"requests.packages.urllib3.filepost\")\n    vendored(\"requests.packages.urllib3.packages\")\n    vendored(\"requests.packages.urllib3.packages.ordered_dict\")\n    vendored(\"requests.packages.urllib3.packages.six\")\n    vendored(\"requests.packages.urllib3.packages.ssl_match_hostname\")\n    vendored(\"requests.packages.urllib3.packages.ssl_match_hostname.\"\n             \"_implementation\")\n    vendored(\"requests.packages.urllib3.poolmanager\")\n    vendored(\"requests.packages.urllib3.request\")\n    vendored(\"requests.packages.urllib3.response\")\n    vendored(\"requests.packages.urllib3.util\")\n    vendored(\"requests.packages.urllib3.util.connection\")\n    vendored(\"requests.packages.urllib3.util.request\")\n    vendored(\"requests.packages.urllib3.util.response\")\n    vendored(\"requests.packages.urllib3.util.retry\")\n    vendored(\"requests.packages.urllib3.util.ssl_\")\n    vendored(\"requests.packages.urllib3.util.timeout\")\n    vendored(\"requests.packages.urllib3.util.url\")\n    vendored(\"urllib3\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/appdirs.py",
    "content": "#!/usr/bin/env python\n# -*- coding: utf-8 -*-\n# Copyright (c) 2005-2010 ActiveState Software Inc.\n# Copyright (c) 2013 Eddy Petrișor\n\n\"\"\"Utilities for determining application-specific dirs.\n\nSee <http://github.com/ActiveState/appdirs> for details and usage.\n\"\"\"\n# Dev Notes:\n# - MSDN on where to store app data files:\n#   http://support.microsoft.com/default.aspx?scid=kb;en-us;310294#XSLTH3194121123120121120120\n# - Mac OS X: http://developer.apple.com/documentation/MacOSX/Conceptual/BPFileSystem/index.html\n# - XDG spec for Un*x: http://standards.freedesktop.org/basedir-spec/basedir-spec-latest.html\n\n__version_info__ = (1, 4, 3)\n__version__ = '.'.join(map(str, __version_info__))\n\n\nimport sys\nimport os\n\nPY3 = sys.version_info[0] == 3\n\nif PY3:\n    unicode = str\n\nif sys.platform.startswith('java'):\n    import platform\n    os_name = platform.java_ver()[3][0]\n    if os_name.startswith('Windows'): # \"Windows XP\", \"Windows 7\", etc.\n        system = 'win32'\n    elif os_name.startswith('Mac'): # \"Mac OS X\", etc.\n        system = 'darwin'\n    else: # \"Linux\", \"SunOS\", \"FreeBSD\", etc.\n        # Setting this to \"linux2\" is not ideal, but only Windows or Mac\n        # are actually checked for and the rest of the module expects\n        # *sys.platform* style strings.\n        system = 'linux2'\nelse:\n    system = sys.platform\n\n\n\ndef user_data_dir(appname=None, appauthor=None, version=None, roaming=False):\n    r\"\"\"Return full path to the user-specific data dir for this application.\n\n        \"appname\" is the name of application.\n            If None, just the system directory is returned.\n        \"appauthor\" (only used on Windows) is the name of the\n            appauthor or distributing body for this application. Typically\n            it is the owning company name. This falls back to appname. You may\n            pass False to disable it.\n        \"version\" is an optional version path element to append to the\n            path. You might want to use this if you want multiple versions\n            of your app to be able to run independently. If used, this\n            would typically be \"<major>.<minor>\".\n            Only applied when appname is present.\n        \"roaming\" (boolean, default False) can be set True to use the Windows\n            roaming appdata directory. That means that for users on a Windows\n            network setup for roaming profiles, this user data will be\n            sync'd on login. See\n            <http://technet.microsoft.com/en-us/library/cc766489(WS.10).aspx>\n            for a discussion of issues.\n\n    Typical user data directories are:\n        Mac OS X:               ~/Library/Application Support/<AppName>\n        Unix:                   ~/.local/share/<AppName>    # or in $XDG_DATA_HOME, if defined\n        Win XP (not roaming):   C:\\Documents and Settings\\<username>\\Application Data\\<AppAuthor>\\<AppName>\n        Win XP (roaming):       C:\\Documents and Settings\\<username>\\Local Settings\\Application Data\\<AppAuthor>\\<AppName>\n        Win 7  (not roaming):   C:\\Users\\<username>\\AppData\\Local\\<AppAuthor>\\<AppName>\n        Win 7  (roaming):       C:\\Users\\<username>\\AppData\\Roaming\\<AppAuthor>\\<AppName>\n\n    For Unix, we follow the XDG spec and support $XDG_DATA_HOME.\n    That means, by default \"~/.local/share/<AppName>\".\n    \"\"\"\n    if system == \"win32\":\n        if appauthor is None:\n            appauthor = appname\n        const = roaming and \"CSIDL_APPDATA\" or \"CSIDL_LOCAL_APPDATA\"\n        path = os.path.normpath(_get_win_folder(const))\n        if appname:\n            if appauthor is not False:\n                path = os.path.join(path, appauthor, appname)\n            else:\n                path = os.path.join(path, appname)\n    elif system == 'darwin':\n        path = os.path.expanduser('~/Library/Application Support/')\n        if appname:\n            path = os.path.join(path, appname)\n    else:\n        path = os.getenv('XDG_DATA_HOME', os.path.expanduser(\"~/.local/share\"))\n        if appname:\n            path = os.path.join(path, appname)\n    if appname and version:\n        path = os.path.join(path, version)\n    return path\n\n\ndef site_data_dir(appname=None, appauthor=None, version=None, multipath=False):\n    r\"\"\"Return full path to the user-shared data dir for this application.\n\n        \"appname\" is the name of application.\n            If None, just the system directory is returned.\n        \"appauthor\" (only used on Windows) is the name of the\n            appauthor or distributing body for this application. Typically\n            it is the owning company name. This falls back to appname. You may\n            pass False to disable it.\n        \"version\" is an optional version path element to append to the\n            path. You might want to use this if you want multiple versions\n            of your app to be able to run independently. If used, this\n            would typically be \"<major>.<minor>\".\n            Only applied when appname is present.\n        \"multipath\" is an optional parameter only applicable to *nix\n            which indicates that the entire list of data dirs should be\n            returned. By default, the first item from XDG_DATA_DIRS is\n            returned, or '/usr/local/share/<AppName>',\n            if XDG_DATA_DIRS is not set\n\n    Typical site data directories are:\n        Mac OS X:   /Library/Application Support/<AppName>\n        Unix:       /usr/local/share/<AppName> or /usr/share/<AppName>\n        Win XP:     C:\\Documents and Settings\\All Users\\Application Data\\<AppAuthor>\\<AppName>\n        Vista:      (Fail! \"C:\\ProgramData\" is a hidden *system* directory on Vista.)\n        Win 7:      C:\\ProgramData\\<AppAuthor>\\<AppName>   # Hidden, but writeable on Win 7.\n\n    For Unix, this is using the $XDG_DATA_DIRS[0] default.\n\n    WARNING: Do not use this on Windows. See the Vista-Fail note above for why.\n    \"\"\"\n    if system == \"win32\":\n        if appauthor is None:\n            appauthor = appname\n        path = os.path.normpath(_get_win_folder(\"CSIDL_COMMON_APPDATA\"))\n        if appname:\n            if appauthor is not False:\n                path = os.path.join(path, appauthor, appname)\n            else:\n                path = os.path.join(path, appname)\n    elif system == 'darwin':\n        path = os.path.expanduser('/Library/Application Support')\n        if appname:\n            path = os.path.join(path, appname)\n    else:\n        # XDG default for $XDG_DATA_DIRS\n        # only first, if multipath is False\n        path = os.getenv('XDG_DATA_DIRS',\n                         os.pathsep.join(['/usr/local/share', '/usr/share']))\n        pathlist = [os.path.expanduser(x.rstrip(os.sep)) for x in path.split(os.pathsep)]\n        if appname:\n            if version:\n                appname = os.path.join(appname, version)\n            pathlist = [os.sep.join([x, appname]) for x in pathlist]\n\n        if multipath:\n            path = os.pathsep.join(pathlist)\n        else:\n            path = pathlist[0]\n        return path\n\n    if appname and version:\n        path = os.path.join(path, version)\n    return path\n\n\ndef user_config_dir(appname=None, appauthor=None, version=None, roaming=False):\n    r\"\"\"Return full path to the user-specific config dir for this application.\n\n        \"appname\" is the name of application.\n            If None, just the system directory is returned.\n        \"appauthor\" (only used on Windows) is the name of the\n            appauthor or distributing body for this application. Typically\n            it is the owning company name. This falls back to appname. You may\n            pass False to disable it.\n        \"version\" is an optional version path element to append to the\n            path. You might want to use this if you want multiple versions\n            of your app to be able to run independently. If used, this\n            would typically be \"<major>.<minor>\".\n            Only applied when appname is present.\n        \"roaming\" (boolean, default False) can be set True to use the Windows\n            roaming appdata directory. That means that for users on a Windows\n            network setup for roaming profiles, this user data will be\n            sync'd on login. See\n            <http://technet.microsoft.com/en-us/library/cc766489(WS.10).aspx>\n            for a discussion of issues.\n\n    Typical user config directories are:\n        Mac OS X:               same as user_data_dir\n        Unix:                   ~/.config/<AppName>     # or in $XDG_CONFIG_HOME, if defined\n        Win *:                  same as user_data_dir\n\n    For Unix, we follow the XDG spec and support $XDG_CONFIG_HOME.\n    That means, by default \"~/.config/<AppName>\".\n    \"\"\"\n    if system in [\"win32\", \"darwin\"]:\n        path = user_data_dir(appname, appauthor, None, roaming)\n    else:\n        path = os.getenv('XDG_CONFIG_HOME', os.path.expanduser(\"~/.config\"))\n        if appname:\n            path = os.path.join(path, appname)\n    if appname and version:\n        path = os.path.join(path, version)\n    return path\n\n\ndef site_config_dir(appname=None, appauthor=None, version=None, multipath=False):\n    r\"\"\"Return full path to the user-shared data dir for this application.\n\n        \"appname\" is the name of application.\n            If None, just the system directory is returned.\n        \"appauthor\" (only used on Windows) is the name of the\n            appauthor or distributing body for this application. Typically\n            it is the owning company name. This falls back to appname. You may\n            pass False to disable it.\n        \"version\" is an optional version path element to append to the\n            path. You might want to use this if you want multiple versions\n            of your app to be able to run independently. If used, this\n            would typically be \"<major>.<minor>\".\n            Only applied when appname is present.\n        \"multipath\" is an optional parameter only applicable to *nix\n            which indicates that the entire list of config dirs should be\n            returned. By default, the first item from XDG_CONFIG_DIRS is\n            returned, or '/etc/xdg/<AppName>', if XDG_CONFIG_DIRS is not set\n\n    Typical site config directories are:\n        Mac OS X:   same as site_data_dir\n        Unix:       /etc/xdg/<AppName> or $XDG_CONFIG_DIRS[i]/<AppName> for each value in\n                    $XDG_CONFIG_DIRS\n        Win *:      same as site_data_dir\n        Vista:      (Fail! \"C:\\ProgramData\" is a hidden *system* directory on Vista.)\n\n    For Unix, this is using the $XDG_CONFIG_DIRS[0] default, if multipath=False\n\n    WARNING: Do not use this on Windows. See the Vista-Fail note above for why.\n    \"\"\"\n    if system in [\"win32\", \"darwin\"]:\n        path = site_data_dir(appname, appauthor)\n        if appname and version:\n            path = os.path.join(path, version)\n    else:\n        # XDG default for $XDG_CONFIG_DIRS\n        # only first, if multipath is False\n        path = os.getenv('XDG_CONFIG_DIRS', '/etc/xdg')\n        pathlist = [os.path.expanduser(x.rstrip(os.sep)) for x in path.split(os.pathsep)]\n        if appname:\n            if version:\n                appname = os.path.join(appname, version)\n            pathlist = [os.sep.join([x, appname]) for x in pathlist]\n\n        if multipath:\n            path = os.pathsep.join(pathlist)\n        else:\n            path = pathlist[0]\n    return path\n\n\ndef user_cache_dir(appname=None, appauthor=None, version=None, opinion=True):\n    r\"\"\"Return full path to the user-specific cache dir for this application.\n\n        \"appname\" is the name of application.\n            If None, just the system directory is returned.\n        \"appauthor\" (only used on Windows) is the name of the\n            appauthor or distributing body for this application. Typically\n            it is the owning company name. This falls back to appname. You may\n            pass False to disable it.\n        \"version\" is an optional version path element to append to the\n            path. You might want to use this if you want multiple versions\n            of your app to be able to run independently. If used, this\n            would typically be \"<major>.<minor>\".\n            Only applied when appname is present.\n        \"opinion\" (boolean) can be False to disable the appending of\n            \"Cache\" to the base app data dir for Windows. See\n            discussion below.\n\n    Typical user cache directories are:\n        Mac OS X:   ~/Library/Caches/<AppName>\n        Unix:       ~/.cache/<AppName> (XDG default)\n        Win XP:     C:\\Documents and Settings\\<username>\\Local Settings\\Application Data\\<AppAuthor>\\<AppName>\\Cache\n        Vista:      C:\\Users\\<username>\\AppData\\Local\\<AppAuthor>\\<AppName>\\Cache\n\n    On Windows the only suggestion in the MSDN docs is that local settings go in\n    the `CSIDL_LOCAL_APPDATA` directory. This is identical to the non-roaming\n    app data dir (the default returned by `user_data_dir` above). Apps typically\n    put cache data somewhere *under* the given dir here. Some examples:\n        ...\\Mozilla\\Firefox\\Profiles\\<ProfileName>\\Cache\n        ...\\Acme\\SuperApp\\Cache\\1.0\n    OPINION: This function appends \"Cache\" to the `CSIDL_LOCAL_APPDATA` value.\n    This can be disabled with the `opinion=False` option.\n    \"\"\"\n    if system == \"win32\":\n        if appauthor is None:\n            appauthor = appname\n        path = os.path.normpath(_get_win_folder(\"CSIDL_LOCAL_APPDATA\"))\n        if appname:\n            if appauthor is not False:\n                path = os.path.join(path, appauthor, appname)\n            else:\n                path = os.path.join(path, appname)\n            if opinion:\n                path = os.path.join(path, \"Cache\")\n    elif system == 'darwin':\n        path = os.path.expanduser('~/Library/Caches')\n        if appname:\n            path = os.path.join(path, appname)\n    else:\n        path = os.getenv('XDG_CACHE_HOME', os.path.expanduser('~/.cache'))\n        if appname:\n            path = os.path.join(path, appname)\n    if appname and version:\n        path = os.path.join(path, version)\n    return path\n\n\ndef user_state_dir(appname=None, appauthor=None, version=None, roaming=False):\n    r\"\"\"Return full path to the user-specific state dir for this application.\n\n        \"appname\" is the name of application.\n            If None, just the system directory is returned.\n        \"appauthor\" (only used on Windows) is the name of the\n            appauthor or distributing body for this application. Typically\n            it is the owning company name. This falls back to appname. You may\n            pass False to disable it.\n        \"version\" is an optional version path element to append to the\n            path. You might want to use this if you want multiple versions\n            of your app to be able to run independently. If used, this\n            would typically be \"<major>.<minor>\".\n            Only applied when appname is present.\n        \"roaming\" (boolean, default False) can be set True to use the Windows\n            roaming appdata directory. That means that for users on a Windows\n            network setup for roaming profiles, this user data will be\n            sync'd on login. See\n            <http://technet.microsoft.com/en-us/library/cc766489(WS.10).aspx>\n            for a discussion of issues.\n\n    Typical user state directories are:\n        Mac OS X:  same as user_data_dir\n        Unix:      ~/.local/state/<AppName>   # or in $XDG_STATE_HOME, if defined\n        Win *:     same as user_data_dir\n\n    For Unix, we follow this Debian proposal <https://wiki.debian.org/XDGBaseDirectorySpecification#state>\n    to extend the XDG spec and support $XDG_STATE_HOME.\n\n    That means, by default \"~/.local/state/<AppName>\".\n    \"\"\"\n    if system in [\"win32\", \"darwin\"]:\n        path = user_data_dir(appname, appauthor, None, roaming)\n    else:\n        path = os.getenv('XDG_STATE_HOME', os.path.expanduser(\"~/.local/state\"))\n        if appname:\n            path = os.path.join(path, appname)\n    if appname and version:\n        path = os.path.join(path, version)\n    return path\n\n\ndef user_log_dir(appname=None, appauthor=None, version=None, opinion=True):\n    r\"\"\"Return full path to the user-specific log dir for this application.\n\n        \"appname\" is the name of application.\n            If None, just the system directory is returned.\n        \"appauthor\" (only used on Windows) is the name of the\n            appauthor or distributing body for this application. Typically\n            it is the owning company name. This falls back to appname. You may\n            pass False to disable it.\n        \"version\" is an optional version path element to append to the\n            path. You might want to use this if you want multiple versions\n            of your app to be able to run independently. If used, this\n            would typically be \"<major>.<minor>\".\n            Only applied when appname is present.\n        \"opinion\" (boolean) can be False to disable the appending of\n            \"Logs\" to the base app data dir for Windows, and \"log\" to the\n            base cache dir for Unix. See discussion below.\n\n    Typical user log directories are:\n        Mac OS X:   ~/Library/Logs/<AppName>\n        Unix:       ~/.cache/<AppName>/log  # or under $XDG_CACHE_HOME if defined\n        Win XP:     C:\\Documents and Settings\\<username>\\Local Settings\\Application Data\\<AppAuthor>\\<AppName>\\Logs\n        Vista:      C:\\Users\\<username>\\AppData\\Local\\<AppAuthor>\\<AppName>\\Logs\n\n    On Windows the only suggestion in the MSDN docs is that local settings\n    go in the `CSIDL_LOCAL_APPDATA` directory. (Note: I'm interested in\n    examples of what some windows apps use for a logs dir.)\n\n    OPINION: This function appends \"Logs\" to the `CSIDL_LOCAL_APPDATA`\n    value for Windows and appends \"log\" to the user cache dir for Unix.\n    This can be disabled with the `opinion=False` option.\n    \"\"\"\n    if system == \"darwin\":\n        path = os.path.join(\n            os.path.expanduser('~/Library/Logs'),\n            appname)\n    elif system == \"win32\":\n        path = user_data_dir(appname, appauthor, version)\n        version = False\n        if opinion:\n            path = os.path.join(path, \"Logs\")\n    else:\n        path = user_cache_dir(appname, appauthor, version)\n        version = False\n        if opinion:\n            path = os.path.join(path, \"log\")\n    if appname and version:\n        path = os.path.join(path, version)\n    return path\n\n\nclass AppDirs(object):\n    \"\"\"Convenience wrapper for getting application dirs.\"\"\"\n    def __init__(self, appname=None, appauthor=None, version=None,\n            roaming=False, multipath=False):\n        self.appname = appname\n        self.appauthor = appauthor\n        self.version = version\n        self.roaming = roaming\n        self.multipath = multipath\n\n    @property\n    def user_data_dir(self):\n        return user_data_dir(self.appname, self.appauthor,\n                             version=self.version, roaming=self.roaming)\n\n    @property\n    def site_data_dir(self):\n        return site_data_dir(self.appname, self.appauthor,\n                             version=self.version, multipath=self.multipath)\n\n    @property\n    def user_config_dir(self):\n        return user_config_dir(self.appname, self.appauthor,\n                               version=self.version, roaming=self.roaming)\n\n    @property\n    def site_config_dir(self):\n        return site_config_dir(self.appname, self.appauthor,\n                             version=self.version, multipath=self.multipath)\n\n    @property\n    def user_cache_dir(self):\n        return user_cache_dir(self.appname, self.appauthor,\n                              version=self.version)\n\n    @property\n    def user_state_dir(self):\n        return user_state_dir(self.appname, self.appauthor,\n                              version=self.version)\n\n    @property\n    def user_log_dir(self):\n        return user_log_dir(self.appname, self.appauthor,\n                            version=self.version)\n\n\n#---- internal support stuff\n\ndef _get_win_folder_from_registry(csidl_name):\n    \"\"\"This is a fallback technique at best. I'm not sure if using the\n    registry for this guarantees us the correct answer for all CSIDL_*\n    names.\n    \"\"\"\n    if PY3:\n      import winreg as _winreg\n    else:\n      import _winreg\n\n    shell_folder_name = {\n        \"CSIDL_APPDATA\": \"AppData\",\n        \"CSIDL_COMMON_APPDATA\": \"Common AppData\",\n        \"CSIDL_LOCAL_APPDATA\": \"Local AppData\",\n    }[csidl_name]\n\n    key = _winreg.OpenKey(\n        _winreg.HKEY_CURRENT_USER,\n        r\"Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\Shell Folders\"\n    )\n    dir, type = _winreg.QueryValueEx(key, shell_folder_name)\n    return dir\n\n\ndef _get_win_folder_with_pywin32(csidl_name):\n    from win32com.shell import shellcon, shell\n    dir = shell.SHGetFolderPath(0, getattr(shellcon, csidl_name), 0, 0)\n    # Try to make this a unicode path because SHGetFolderPath does\n    # not return unicode strings when there is unicode data in the\n    # path.\n    try:\n        dir = unicode(dir)\n\n        # Downgrade to short path name if have highbit chars. See\n        # <http://bugs.activestate.com/show_bug.cgi?id=85099>.\n        has_high_char = False\n        for c in dir:\n            if ord(c) > 255:\n                has_high_char = True\n                break\n        if has_high_char:\n            try:\n                import win32api\n                dir = win32api.GetShortPathName(dir)\n            except ImportError:\n                pass\n    except UnicodeError:\n        pass\n    return dir\n\n\ndef _get_win_folder_with_ctypes(csidl_name):\n    import ctypes\n\n    csidl_const = {\n        \"CSIDL_APPDATA\": 26,\n        \"CSIDL_COMMON_APPDATA\": 35,\n        \"CSIDL_LOCAL_APPDATA\": 28,\n    }[csidl_name]\n\n    buf = ctypes.create_unicode_buffer(1024)\n    ctypes.windll.shell32.SHGetFolderPathW(None, csidl_const, None, 0, buf)\n\n    # Downgrade to short path name if have highbit chars. See\n    # <http://bugs.activestate.com/show_bug.cgi?id=85099>.\n    has_high_char = False\n    for c in buf:\n        if ord(c) > 255:\n            has_high_char = True\n            break\n    if has_high_char:\n        buf2 = ctypes.create_unicode_buffer(1024)\n        if ctypes.windll.kernel32.GetShortPathNameW(buf.value, buf2, 1024):\n            buf = buf2\n\n    return buf.value\n\ndef _get_win_folder_with_jna(csidl_name):\n    import array\n    from com.sun import jna\n    from com.sun.jna.platform import win32\n\n    buf_size = win32.WinDef.MAX_PATH * 2\n    buf = array.zeros('c', buf_size)\n    shell = win32.Shell32.INSTANCE\n    shell.SHGetFolderPath(None, getattr(win32.ShlObj, csidl_name), None, win32.ShlObj.SHGFP_TYPE_CURRENT, buf)\n    dir = jna.Native.toString(buf.tostring()).rstrip(\"\\0\")\n\n    # Downgrade to short path name if have highbit chars. See\n    # <http://bugs.activestate.com/show_bug.cgi?id=85099>.\n    has_high_char = False\n    for c in dir:\n        if ord(c) > 255:\n            has_high_char = True\n            break\n    if has_high_char:\n        buf = array.zeros('c', buf_size)\n        kernel = win32.Kernel32.INSTANCE\n        if kernel.GetShortPathName(dir, buf, buf_size):\n            dir = jna.Native.toString(buf.tostring()).rstrip(\"\\0\")\n\n    return dir\n\nif system == \"win32\":\n    try:\n        from ctypes import windll\n        _get_win_folder = _get_win_folder_with_ctypes\n    except ImportError:\n        try:\n            import com.sun.jna\n            _get_win_folder = _get_win_folder_with_jna\n        except ImportError:\n            _get_win_folder = _get_win_folder_from_registry\n\n\n#---- self test code\n\nif __name__ == \"__main__\":\n    appname = \"MyApp\"\n    appauthor = \"MyCompany\"\n\n    props = (\"user_data_dir\",\n             \"user_config_dir\",\n             \"user_cache_dir\",\n             \"user_state_dir\",\n             \"user_log_dir\",\n             \"site_data_dir\",\n             \"site_config_dir\")\n\n    print(\"-- app dirs %s --\" % __version__)\n\n    print(\"-- app dirs (with optional 'version')\")\n    dirs = AppDirs(appname, appauthor, version=\"1.0\")\n    for prop in props:\n        print(\"%s: %s\" % (prop, getattr(dirs, prop)))\n\n    print(\"\\n-- app dirs (without optional 'version')\")\n    dirs = AppDirs(appname, appauthor)\n    for prop in props:\n        print(\"%s: %s\" % (prop, getattr(dirs, prop)))\n\n    print(\"\\n-- app dirs (without optional 'appauthor')\")\n    dirs = AppDirs(appname)\n    for prop in props:\n        print(\"%s: %s\" % (prop, getattr(dirs, prop)))\n\n    print(\"\\n-- app dirs (with disabled 'appauthor')\")\n    dirs = AppDirs(appname, appauthor=False)\n    for prop in props:\n        print(\"%s: %s\" % (prop, getattr(dirs, prop)))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/__init__.py",
    "content": "\"\"\"CacheControl import Interface.\n\nMake it easy to import from cachecontrol without long namespaces.\n\"\"\"\n__author__ = \"Eric Larson\"\n__email__ = \"eric@ionrock.org\"\n__version__ = \"0.12.5\"\n\nfrom .wrapper import CacheControl\nfrom .adapter import CacheControlAdapter\nfrom .controller import CacheController\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/_cmd.py",
    "content": "import logging\n\nfrom pip._vendor import requests\n\nfrom pip._vendor.cachecontrol.adapter import CacheControlAdapter\nfrom pip._vendor.cachecontrol.cache import DictCache\nfrom pip._vendor.cachecontrol.controller import logger\n\nfrom argparse import ArgumentParser\n\n\ndef setup_logging():\n    logger.setLevel(logging.DEBUG)\n    handler = logging.StreamHandler()\n    logger.addHandler(handler)\n\n\ndef get_session():\n    adapter = CacheControlAdapter(\n        DictCache(), cache_etags=True, serializer=None, heuristic=None\n    )\n    sess = requests.Session()\n    sess.mount(\"http://\", adapter)\n    sess.mount(\"https://\", adapter)\n\n    sess.cache_controller = adapter.controller\n    return sess\n\n\ndef get_args():\n    parser = ArgumentParser()\n    parser.add_argument(\"url\", help=\"The URL to try and cache\")\n    return parser.parse_args()\n\n\ndef main(args=None):\n    args = get_args()\n    sess = get_session()\n\n    # Make a request to get a response\n    resp = sess.get(args.url)\n\n    # Turn on logging\n    setup_logging()\n\n    # try setting the cache\n    sess.cache_controller.cache_response(resp.request, resp.raw)\n\n    # Now try to get it\n    if sess.cache_controller.cached_request(resp.request):\n        print(\"Cached!\")\n    else:\n        print(\"Not cached :(\")\n\n\nif __name__ == \"__main__\":\n    main()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/adapter.py",
    "content": "import types\nimport functools\nimport zlib\n\nfrom pip._vendor.requests.adapters import HTTPAdapter\n\nfrom .controller import CacheController\nfrom .cache import DictCache\nfrom .filewrapper import CallbackFileWrapper\n\n\nclass CacheControlAdapter(HTTPAdapter):\n    invalidating_methods = {\"PUT\", \"DELETE\"}\n\n    def __init__(\n        self,\n        cache=None,\n        cache_etags=True,\n        controller_class=None,\n        serializer=None,\n        heuristic=None,\n        cacheable_methods=None,\n        *args,\n        **kw\n    ):\n        super(CacheControlAdapter, self).__init__(*args, **kw)\n        self.cache = cache or DictCache()\n        self.heuristic = heuristic\n        self.cacheable_methods = cacheable_methods or (\"GET\",)\n\n        controller_factory = controller_class or CacheController\n        self.controller = controller_factory(\n            self.cache, cache_etags=cache_etags, serializer=serializer\n        )\n\n    def send(self, request, cacheable_methods=None, **kw):\n        \"\"\"\n        Send a request. Use the request information to see if it\n        exists in the cache and cache the response if we need to and can.\n        \"\"\"\n        cacheable = cacheable_methods or self.cacheable_methods\n        if request.method in cacheable:\n            try:\n                cached_response = self.controller.cached_request(request)\n            except zlib.error:\n                cached_response = None\n            if cached_response:\n                return self.build_response(request, cached_response, from_cache=True)\n\n            # check for etags and add headers if appropriate\n            request.headers.update(self.controller.conditional_headers(request))\n\n        resp = super(CacheControlAdapter, self).send(request, **kw)\n\n        return resp\n\n    def build_response(\n        self, request, response, from_cache=False, cacheable_methods=None\n    ):\n        \"\"\"\n        Build a response by making a request or using the cache.\n\n        This will end up calling send and returning a potentially\n        cached response\n        \"\"\"\n        cacheable = cacheable_methods or self.cacheable_methods\n        if not from_cache and request.method in cacheable:\n            # Check for any heuristics that might update headers\n            # before trying to cache.\n            if self.heuristic:\n                response = self.heuristic.apply(response)\n\n            # apply any expiration heuristics\n            if response.status == 304:\n                # We must have sent an ETag request. This could mean\n                # that we've been expired already or that we simply\n                # have an etag. In either case, we want to try and\n                # update the cache if that is the case.\n                cached_response = self.controller.update_cached_response(\n                    request, response\n                )\n\n                if cached_response is not response:\n                    from_cache = True\n\n                # We are done with the server response, read a\n                # possible response body (compliant servers will\n                # not return one, but we cannot be 100% sure) and\n                # release the connection back to the pool.\n                response.read(decode_content=False)\n                response.release_conn()\n\n                response = cached_response\n\n            # We always cache the 301 responses\n            elif response.status == 301:\n                self.controller.cache_response(request, response)\n            else:\n                # Wrap the response file with a wrapper that will cache the\n                #   response when the stream has been consumed.\n                response._fp = CallbackFileWrapper(\n                    response._fp,\n                    functools.partial(\n                        self.controller.cache_response, request, response\n                    ),\n                )\n                if response.chunked:\n                    super_update_chunk_length = response._update_chunk_length\n\n                    def _update_chunk_length(self):\n                        super_update_chunk_length()\n                        if self.chunk_left == 0:\n                            self._fp._close()\n\n                    response._update_chunk_length = types.MethodType(\n                        _update_chunk_length, response\n                    )\n\n        resp = super(CacheControlAdapter, self).build_response(request, response)\n\n        # See if we should invalidate the cache.\n        if request.method in self.invalidating_methods and resp.ok:\n            cache_url = self.controller.cache_url(request.url)\n            self.cache.delete(cache_url)\n\n        # Give the request a from_cache attr to let people use it\n        resp.from_cache = from_cache\n\n        return resp\n\n    def close(self):\n        self.cache.close()\n        super(CacheControlAdapter, self).close()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/cache.py",
    "content": "\"\"\"\nThe cache object API for implementing caches. The default is a thread\nsafe in-memory dictionary.\n\"\"\"\nfrom threading import Lock\n\n\nclass BaseCache(object):\n\n    def get(self, key):\n        raise NotImplementedError()\n\n    def set(self, key, value):\n        raise NotImplementedError()\n\n    def delete(self, key):\n        raise NotImplementedError()\n\n    def close(self):\n        pass\n\n\nclass DictCache(BaseCache):\n\n    def __init__(self, init_dict=None):\n        self.lock = Lock()\n        self.data = init_dict or {}\n\n    def get(self, key):\n        return self.data.get(key, None)\n\n    def set(self, key, value):\n        with self.lock:\n            self.data.update({key: value})\n\n    def delete(self, key):\n        with self.lock:\n            if key in self.data:\n                self.data.pop(key)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/caches/__init__.py",
    "content": "from .file_cache import FileCache  # noqa\nfrom .redis_cache import RedisCache  # noqa\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/caches/file_cache.py",
    "content": "import hashlib\nimport os\nfrom textwrap import dedent\n\nfrom ..cache import BaseCache\nfrom ..controller import CacheController\n\ntry:\n    FileNotFoundError\nexcept NameError:\n    # py2.X\n    FileNotFoundError = (IOError, OSError)\n\n\ndef _secure_open_write(filename, fmode):\n    # We only want to write to this file, so open it in write only mode\n    flags = os.O_WRONLY\n\n    # os.O_CREAT | os.O_EXCL will fail if the file already exists, so we only\n    #  will open *new* files.\n    # We specify this because we want to ensure that the mode we pass is the\n    # mode of the file.\n    flags |= os.O_CREAT | os.O_EXCL\n\n    # Do not follow symlinks to prevent someone from making a symlink that\n    # we follow and insecurely open a cache file.\n    if hasattr(os, \"O_NOFOLLOW\"):\n        flags |= os.O_NOFOLLOW\n\n    # On Windows we'll mark this file as binary\n    if hasattr(os, \"O_BINARY\"):\n        flags |= os.O_BINARY\n\n    # Before we open our file, we want to delete any existing file that is\n    # there\n    try:\n        os.remove(filename)\n    except (IOError, OSError):\n        # The file must not exist already, so we can just skip ahead to opening\n        pass\n\n    # Open our file, the use of os.O_CREAT | os.O_EXCL will ensure that if a\n    # race condition happens between the os.remove and this line, that an\n    # error will be raised. Because we utilize a lockfile this should only\n    # happen if someone is attempting to attack us.\n    fd = os.open(filename, flags, fmode)\n    try:\n        return os.fdopen(fd, \"wb\")\n\n    except:\n        # An error occurred wrapping our FD in a file object\n        os.close(fd)\n        raise\n\n\nclass FileCache(BaseCache):\n\n    def __init__(\n        self,\n        directory,\n        forever=False,\n        filemode=0o0600,\n        dirmode=0o0700,\n        use_dir_lock=None,\n        lock_class=None,\n    ):\n\n        if use_dir_lock is not None and lock_class is not None:\n            raise ValueError(\"Cannot use use_dir_lock and lock_class together\")\n\n        try:\n            from pip._vendor.lockfile import LockFile\n            from pip._vendor.lockfile.mkdirlockfile import MkdirLockFile\n        except ImportError:\n            notice = dedent(\n                \"\"\"\n            NOTE: In order to use the FileCache you must have\n            lockfile installed. You can install it via pip:\n              pip install lockfile\n            \"\"\"\n            )\n            raise ImportError(notice)\n\n        else:\n            if use_dir_lock:\n                lock_class = MkdirLockFile\n\n            elif lock_class is None:\n                lock_class = LockFile\n\n        self.directory = directory\n        self.forever = forever\n        self.filemode = filemode\n        self.dirmode = dirmode\n        self.lock_class = lock_class\n\n    @staticmethod\n    def encode(x):\n        return hashlib.sha224(x.encode()).hexdigest()\n\n    def _fn(self, name):\n        # NOTE: This method should not change as some may depend on it.\n        #       See: https://github.com/ionrock/cachecontrol/issues/63\n        hashed = self.encode(name)\n        parts = list(hashed[:5]) + [hashed]\n        return os.path.join(self.directory, *parts)\n\n    def get(self, key):\n        name = self._fn(key)\n        try:\n            with open(name, \"rb\") as fh:\n                return fh.read()\n\n        except FileNotFoundError:\n            return None\n\n    def set(self, key, value):\n        name = self._fn(key)\n\n        # Make sure the directory exists\n        try:\n            os.makedirs(os.path.dirname(name), self.dirmode)\n        except (IOError, OSError):\n            pass\n\n        with self.lock_class(name) as lock:\n            # Write our actual file\n            with _secure_open_write(lock.path, self.filemode) as fh:\n                fh.write(value)\n\n    def delete(self, key):\n        name = self._fn(key)\n        if not self.forever:\n            try:\n                os.remove(name)\n            except FileNotFoundError:\n                pass\n\n\ndef url_to_file_path(url, filecache):\n    \"\"\"Return the file cache path based on the URL.\n\n    This does not ensure the file exists!\n    \"\"\"\n    key = CacheController.cache_url(url)\n    return filecache._fn(key)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/caches/redis_cache.py",
    "content": "from __future__ import division\n\nfrom datetime import datetime\nfrom pip._vendor.cachecontrol.cache import BaseCache\n\n\nclass RedisCache(BaseCache):\n\n    def __init__(self, conn):\n        self.conn = conn\n\n    def get(self, key):\n        return self.conn.get(key)\n\n    def set(self, key, value, expires=None):\n        if not expires:\n            self.conn.set(key, value)\n        else:\n            expires = expires - datetime.utcnow()\n            self.conn.setex(key, int(expires.total_seconds()), value)\n\n    def delete(self, key):\n        self.conn.delete(key)\n\n    def clear(self):\n        \"\"\"Helper for clearing all the keys in a database. Use with\n        caution!\"\"\"\n        for key in self.conn.keys():\n            self.conn.delete(key)\n\n    def close(self):\n        \"\"\"Redis uses connection pooling, no need to close the connection.\"\"\"\n        pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/compat.py",
    "content": "try:\n    from urllib.parse import urljoin\nexcept ImportError:\n    from urlparse import urljoin\n\n\ntry:\n    import cPickle as pickle\nexcept ImportError:\n    import pickle\n\n\n# Handle the case where the requests module has been patched to not have\n# urllib3 bundled as part of its source.\ntry:\n    from pip._vendor.requests.packages.urllib3.response import HTTPResponse\nexcept ImportError:\n    from pip._vendor.urllib3.response import HTTPResponse\n\ntry:\n    from pip._vendor.requests.packages.urllib3.util import is_fp_closed\nexcept ImportError:\n    from pip._vendor.urllib3.util import is_fp_closed\n\n# Replicate some six behaviour\ntry:\n    text_type = unicode\nexcept NameError:\n    text_type = str\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/controller.py",
    "content": "\"\"\"\nThe httplib2 algorithms ported for use with requests.\n\"\"\"\nimport logging\nimport re\nimport calendar\nimport time\nfrom email.utils import parsedate_tz\n\nfrom pip._vendor.requests.structures import CaseInsensitiveDict\n\nfrom .cache import DictCache\nfrom .serialize import Serializer\n\n\nlogger = logging.getLogger(__name__)\n\nURI = re.compile(r\"^(([^:/?#]+):)?(//([^/?#]*))?([^?#]*)(\\?([^#]*))?(#(.*))?\")\n\n\ndef parse_uri(uri):\n    \"\"\"Parses a URI using the regex given in Appendix B of RFC 3986.\n\n        (scheme, authority, path, query, fragment) = parse_uri(uri)\n    \"\"\"\n    groups = URI.match(uri).groups()\n    return (groups[1], groups[3], groups[4], groups[6], groups[8])\n\n\nclass CacheController(object):\n    \"\"\"An interface to see if request should cached or not.\n    \"\"\"\n\n    def __init__(\n        self, cache=None, cache_etags=True, serializer=None, status_codes=None\n    ):\n        self.cache = cache or DictCache()\n        self.cache_etags = cache_etags\n        self.serializer = serializer or Serializer()\n        self.cacheable_status_codes = status_codes or (200, 203, 300, 301)\n\n    @classmethod\n    def _urlnorm(cls, uri):\n        \"\"\"Normalize the URL to create a safe key for the cache\"\"\"\n        (scheme, authority, path, query, fragment) = parse_uri(uri)\n        if not scheme or not authority:\n            raise Exception(\"Only absolute URIs are allowed. uri = %s\" % uri)\n\n        scheme = scheme.lower()\n        authority = authority.lower()\n\n        if not path:\n            path = \"/\"\n\n        # Could do syntax based normalization of the URI before\n        # computing the digest. See Section 6.2.2 of Std 66.\n        request_uri = query and \"?\".join([path, query]) or path\n        defrag_uri = scheme + \"://\" + authority + request_uri\n\n        return defrag_uri\n\n    @classmethod\n    def cache_url(cls, uri):\n        return cls._urlnorm(uri)\n\n    def parse_cache_control(self, headers):\n        known_directives = {\n            # https://tools.ietf.org/html/rfc7234#section-5.2\n            \"max-age\": (int, True),\n            \"max-stale\": (int, False),\n            \"min-fresh\": (int, True),\n            \"no-cache\": (None, False),\n            \"no-store\": (None, False),\n            \"no-transform\": (None, False),\n            \"only-if-cached\": (None, False),\n            \"must-revalidate\": (None, False),\n            \"public\": (None, False),\n            \"private\": (None, False),\n            \"proxy-revalidate\": (None, False),\n            \"s-maxage\": (int, True),\n        }\n\n        cc_headers = headers.get(\"cache-control\", headers.get(\"Cache-Control\", \"\"))\n\n        retval = {}\n\n        for cc_directive in cc_headers.split(\",\"):\n            if not cc_directive.strip():\n                continue\n\n            parts = cc_directive.split(\"=\", 1)\n            directive = parts[0].strip()\n\n            try:\n                typ, required = known_directives[directive]\n            except KeyError:\n                logger.debug(\"Ignoring unknown cache-control directive: %s\", directive)\n                continue\n\n            if not typ or not required:\n                retval[directive] = None\n            if typ:\n                try:\n                    retval[directive] = typ(parts[1].strip())\n                except IndexError:\n                    if required:\n                        logger.debug(\n                            \"Missing value for cache-control \" \"directive: %s\",\n                            directive,\n                        )\n                except ValueError:\n                    logger.debug(\n                        \"Invalid value for cache-control directive \" \"%s, must be %s\",\n                        directive,\n                        typ.__name__,\n                    )\n\n        return retval\n\n    def cached_request(self, request):\n        \"\"\"\n        Return a cached response if it exists in the cache, otherwise\n        return False.\n        \"\"\"\n        cache_url = self.cache_url(request.url)\n        logger.debug('Looking up \"%s\" in the cache', cache_url)\n        cc = self.parse_cache_control(request.headers)\n\n        # Bail out if the request insists on fresh data\n        if \"no-cache\" in cc:\n            logger.debug('Request header has \"no-cache\", cache bypassed')\n            return False\n\n        if \"max-age\" in cc and cc[\"max-age\"] == 0:\n            logger.debug('Request header has \"max_age\" as 0, cache bypassed')\n            return False\n\n        # Request allows serving from the cache, let's see if we find something\n        cache_data = self.cache.get(cache_url)\n        if cache_data is None:\n            logger.debug(\"No cache entry available\")\n            return False\n\n        # Check whether it can be deserialized\n        resp = self.serializer.loads(request, cache_data)\n        if not resp:\n            logger.warning(\"Cache entry deserialization failed, entry ignored\")\n            return False\n\n        # If we have a cached 301, return it immediately. We don't\n        # need to test our response for other headers b/c it is\n        # intrinsically \"cacheable\" as it is Permanent.\n        # See:\n        #   https://tools.ietf.org/html/rfc7231#section-6.4.2\n        #\n        # Client can try to refresh the value by repeating the request\n        # with cache busting headers as usual (ie no-cache).\n        if resp.status == 301:\n            msg = (\n                'Returning cached \"301 Moved Permanently\" response '\n                \"(ignoring date and etag information)\"\n            )\n            logger.debug(msg)\n            return resp\n\n        headers = CaseInsensitiveDict(resp.headers)\n        if not headers or \"date\" not in headers:\n            if \"etag\" not in headers:\n                # Without date or etag, the cached response can never be used\n                # and should be deleted.\n                logger.debug(\"Purging cached response: no date or etag\")\n                self.cache.delete(cache_url)\n            logger.debug(\"Ignoring cached response: no date\")\n            return False\n\n        now = time.time()\n        date = calendar.timegm(parsedate_tz(headers[\"date\"]))\n        current_age = max(0, now - date)\n        logger.debug(\"Current age based on date: %i\", current_age)\n\n        # TODO: There is an assumption that the result will be a\n        #       urllib3 response object. This may not be best since we\n        #       could probably avoid instantiating or constructing the\n        #       response until we know we need it.\n        resp_cc = self.parse_cache_control(headers)\n\n        # determine freshness\n        freshness_lifetime = 0\n\n        # Check the max-age pragma in the cache control header\n        if \"max-age\" in resp_cc:\n            freshness_lifetime = resp_cc[\"max-age\"]\n            logger.debug(\"Freshness lifetime from max-age: %i\", freshness_lifetime)\n\n        # If there isn't a max-age, check for an expires header\n        elif \"expires\" in headers:\n            expires = parsedate_tz(headers[\"expires\"])\n            if expires is not None:\n                expire_time = calendar.timegm(expires) - date\n                freshness_lifetime = max(0, expire_time)\n                logger.debug(\"Freshness lifetime from expires: %i\", freshness_lifetime)\n\n        # Determine if we are setting freshness limit in the\n        # request. Note, this overrides what was in the response.\n        if \"max-age\" in cc:\n            freshness_lifetime = cc[\"max-age\"]\n            logger.debug(\n                \"Freshness lifetime from request max-age: %i\", freshness_lifetime\n            )\n\n        if \"min-fresh\" in cc:\n            min_fresh = cc[\"min-fresh\"]\n            # adjust our current age by our min fresh\n            current_age += min_fresh\n            logger.debug(\"Adjusted current age from min-fresh: %i\", current_age)\n\n        # Return entry if it is fresh enough\n        if freshness_lifetime > current_age:\n            logger.debug('The response is \"fresh\", returning cached response')\n            logger.debug(\"%i > %i\", freshness_lifetime, current_age)\n            return resp\n\n        # we're not fresh. If we don't have an Etag, clear it out\n        if \"etag\" not in headers:\n            logger.debug('The cached response is \"stale\" with no etag, purging')\n            self.cache.delete(cache_url)\n\n        # return the original handler\n        return False\n\n    def conditional_headers(self, request):\n        cache_url = self.cache_url(request.url)\n        resp = self.serializer.loads(request, self.cache.get(cache_url))\n        new_headers = {}\n\n        if resp:\n            headers = CaseInsensitiveDict(resp.headers)\n\n            if \"etag\" in headers:\n                new_headers[\"If-None-Match\"] = headers[\"ETag\"]\n\n            if \"last-modified\" in headers:\n                new_headers[\"If-Modified-Since\"] = headers[\"Last-Modified\"]\n\n        return new_headers\n\n    def cache_response(self, request, response, body=None, status_codes=None):\n        \"\"\"\n        Algorithm for caching requests.\n\n        This assumes a requests Response object.\n        \"\"\"\n        # From httplib2: Don't cache 206's since we aren't going to\n        #                handle byte range requests\n        cacheable_status_codes = status_codes or self.cacheable_status_codes\n        if response.status not in cacheable_status_codes:\n            logger.debug(\n                \"Status code %s not in %s\", response.status, cacheable_status_codes\n            )\n            return\n\n        response_headers = CaseInsensitiveDict(response.headers)\n\n        # If we've been given a body, our response has a Content-Length, that\n        # Content-Length is valid then we can check to see if the body we've\n        # been given matches the expected size, and if it doesn't we'll just\n        # skip trying to cache it.\n        if (\n            body is not None\n            and \"content-length\" in response_headers\n            and response_headers[\"content-length\"].isdigit()\n            and int(response_headers[\"content-length\"]) != len(body)\n        ):\n            return\n\n        cc_req = self.parse_cache_control(request.headers)\n        cc = self.parse_cache_control(response_headers)\n\n        cache_url = self.cache_url(request.url)\n        logger.debug('Updating cache with response from \"%s\"', cache_url)\n\n        # Delete it from the cache if we happen to have it stored there\n        no_store = False\n        if \"no-store\" in cc:\n            no_store = True\n            logger.debug('Response header has \"no-store\"')\n        if \"no-store\" in cc_req:\n            no_store = True\n            logger.debug('Request header has \"no-store\"')\n        if no_store and self.cache.get(cache_url):\n            logger.debug('Purging existing cache entry to honor \"no-store\"')\n            self.cache.delete(cache_url)\n        if no_store:\n            return\n\n        # If we've been given an etag, then keep the response\n        if self.cache_etags and \"etag\" in response_headers:\n            logger.debug(\"Caching due to etag\")\n            self.cache.set(\n                cache_url, self.serializer.dumps(request, response, body=body)\n            )\n\n        # Add to the cache any 301s. We do this before looking that\n        # the Date headers.\n        elif response.status == 301:\n            logger.debug(\"Caching permanant redirect\")\n            self.cache.set(cache_url, self.serializer.dumps(request, response))\n\n        # Add to the cache if the response headers demand it. If there\n        # is no date header then we can't do anything about expiring\n        # the cache.\n        elif \"date\" in response_headers:\n            # cache when there is a max-age > 0\n            if \"max-age\" in cc and cc[\"max-age\"] > 0:\n                logger.debug(\"Caching b/c date exists and max-age > 0\")\n                self.cache.set(\n                    cache_url, self.serializer.dumps(request, response, body=body)\n                )\n\n            # If the request can expire, it means we should cache it\n            # in the meantime.\n            elif \"expires\" in response_headers:\n                if response_headers[\"expires\"]:\n                    logger.debug(\"Caching b/c of expires header\")\n                    self.cache.set(\n                        cache_url, self.serializer.dumps(request, response, body=body)\n                    )\n\n    def update_cached_response(self, request, response):\n        \"\"\"On a 304 we will get a new set of headers that we want to\n        update our cached value with, assuming we have one.\n\n        This should only ever be called when we've sent an ETag and\n        gotten a 304 as the response.\n        \"\"\"\n        cache_url = self.cache_url(request.url)\n\n        cached_response = self.serializer.loads(request, self.cache.get(cache_url))\n\n        if not cached_response:\n            # we didn't have a cached response\n            return response\n\n        # Lets update our headers with the headers from the new request:\n        # http://tools.ietf.org/html/draft-ietf-httpbis-p4-conditional-26#section-4.1\n        #\n        # The server isn't supposed to send headers that would make\n        # the cached body invalid. But... just in case, we'll be sure\n        # to strip out ones we know that might be problmatic due to\n        # typical assumptions.\n        excluded_headers = [\"content-length\"]\n\n        cached_response.headers.update(\n            dict(\n                (k, v)\n                for k, v in response.headers.items()\n                if k.lower() not in excluded_headers\n            )\n        )\n\n        # we want a 200 b/c we have content via the cache\n        cached_response.status = 200\n\n        # update our cache\n        self.cache.set(cache_url, self.serializer.dumps(request, cached_response))\n\n        return cached_response\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/filewrapper.py",
    "content": "from io import BytesIO\n\n\nclass CallbackFileWrapper(object):\n    \"\"\"\n    Small wrapper around a fp object which will tee everything read into a\n    buffer, and when that file is closed it will execute a callback with the\n    contents of that buffer.\n\n    All attributes are proxied to the underlying file object.\n\n    This class uses members with a double underscore (__) leading prefix so as\n    not to accidentally shadow an attribute.\n    \"\"\"\n\n    def __init__(self, fp, callback):\n        self.__buf = BytesIO()\n        self.__fp = fp\n        self.__callback = callback\n\n    def __getattr__(self, name):\n        # The vaguaries of garbage collection means that self.__fp is\n        # not always set.  By using __getattribute__ and the private\n        # name[0] allows looking up the attribute value and raising an\n        # AttributeError when it doesn't exist. This stop thigns from\n        # infinitely recursing calls to getattr in the case where\n        # self.__fp hasn't been set.\n        #\n        # [0] https://docs.python.org/2/reference/expressions.html#atom-identifiers\n        fp = self.__getattribute__(\"_CallbackFileWrapper__fp\")\n        return getattr(fp, name)\n\n    def __is_fp_closed(self):\n        try:\n            return self.__fp.fp is None\n\n        except AttributeError:\n            pass\n\n        try:\n            return self.__fp.closed\n\n        except AttributeError:\n            pass\n\n        # We just don't cache it then.\n        # TODO: Add some logging here...\n        return False\n\n    def _close(self):\n        if self.__callback:\n            self.__callback(self.__buf.getvalue())\n\n        # We assign this to None here, because otherwise we can get into\n        # really tricky problems where the CPython interpreter dead locks\n        # because the callback is holding a reference to something which\n        # has a __del__ method. Setting this to None breaks the cycle\n        # and allows the garbage collector to do it's thing normally.\n        self.__callback = None\n\n    def read(self, amt=None):\n        data = self.__fp.read(amt)\n        self.__buf.write(data)\n        if self.__is_fp_closed():\n            self._close()\n\n        return data\n\n    def _safe_read(self, amt):\n        data = self.__fp._safe_read(amt)\n        if amt == 2 and data == b\"\\r\\n\":\n            # urllib executes this read to toss the CRLF at the end\n            # of the chunk.\n            return data\n\n        self.__buf.write(data)\n        if self.__is_fp_closed():\n            self._close()\n\n        return data\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/heuristics.py",
    "content": "import calendar\nimport time\n\nfrom email.utils import formatdate, parsedate, parsedate_tz\n\nfrom datetime import datetime, timedelta\n\nTIME_FMT = \"%a, %d %b %Y %H:%M:%S GMT\"\n\n\ndef expire_after(delta, date=None):\n    date = date or datetime.utcnow()\n    return date + delta\n\n\ndef datetime_to_header(dt):\n    return formatdate(calendar.timegm(dt.timetuple()))\n\n\nclass BaseHeuristic(object):\n\n    def warning(self, response):\n        \"\"\"\n        Return a valid 1xx warning header value describing the cache\n        adjustments.\n\n        The response is provided too allow warnings like 113\n        http://tools.ietf.org/html/rfc7234#section-5.5.4 where we need\n        to explicitly say response is over 24 hours old.\n        \"\"\"\n        return '110 - \"Response is Stale\"'\n\n    def update_headers(self, response):\n        \"\"\"Update the response headers with any new headers.\n\n        NOTE: This SHOULD always include some Warning header to\n              signify that the response was cached by the client, not\n              by way of the provided headers.\n        \"\"\"\n        return {}\n\n    def apply(self, response):\n        updated_headers = self.update_headers(response)\n\n        if updated_headers:\n            response.headers.update(updated_headers)\n            warning_header_value = self.warning(response)\n            if warning_header_value is not None:\n                response.headers.update({\"Warning\": warning_header_value})\n\n        return response\n\n\nclass OneDayCache(BaseHeuristic):\n    \"\"\"\n    Cache the response by providing an expires 1 day in the\n    future.\n    \"\"\"\n\n    def update_headers(self, response):\n        headers = {}\n\n        if \"expires\" not in response.headers:\n            date = parsedate(response.headers[\"date\"])\n            expires = expire_after(timedelta(days=1), date=datetime(*date[:6]))\n            headers[\"expires\"] = datetime_to_header(expires)\n            headers[\"cache-control\"] = \"public\"\n        return headers\n\n\nclass ExpiresAfter(BaseHeuristic):\n    \"\"\"\n    Cache **all** requests for a defined time period.\n    \"\"\"\n\n    def __init__(self, **kw):\n        self.delta = timedelta(**kw)\n\n    def update_headers(self, response):\n        expires = expire_after(self.delta)\n        return {\"expires\": datetime_to_header(expires), \"cache-control\": \"public\"}\n\n    def warning(self, response):\n        tmpl = \"110 - Automatically cached for %s. Response might be stale\"\n        return tmpl % self.delta\n\n\nclass LastModified(BaseHeuristic):\n    \"\"\"\n    If there is no Expires header already, fall back on Last-Modified\n    using the heuristic from\n    http://tools.ietf.org/html/rfc7234#section-4.2.2\n    to calculate a reasonable value.\n\n    Firefox also does something like this per\n    https://developer.mozilla.org/en-US/docs/Web/HTTP/Caching_FAQ\n    http://lxr.mozilla.org/mozilla-release/source/netwerk/protocol/http/nsHttpResponseHead.cpp#397\n    Unlike mozilla we limit this to 24-hr.\n    \"\"\"\n    cacheable_by_default_statuses = {\n        200, 203, 204, 206, 300, 301, 404, 405, 410, 414, 501\n    }\n\n    def update_headers(self, resp):\n        headers = resp.headers\n\n        if \"expires\" in headers:\n            return {}\n\n        if \"cache-control\" in headers and headers[\"cache-control\"] != \"public\":\n            return {}\n\n        if resp.status not in self.cacheable_by_default_statuses:\n            return {}\n\n        if \"date\" not in headers or \"last-modified\" not in headers:\n            return {}\n\n        date = calendar.timegm(parsedate_tz(headers[\"date\"]))\n        last_modified = parsedate(headers[\"last-modified\"])\n        if date is None or last_modified is None:\n            return {}\n\n        now = time.time()\n        current_age = max(0, now - date)\n        delta = date - calendar.timegm(last_modified)\n        freshness_lifetime = max(0, min(delta / 10, 24 * 3600))\n        if freshness_lifetime <= current_age:\n            return {}\n\n        expires = date + freshness_lifetime\n        return {\"expires\": time.strftime(TIME_FMT, time.gmtime(expires))}\n\n    def warning(self, resp):\n        return None\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/serialize.py",
    "content": "import base64\nimport io\nimport json\nimport zlib\n\nfrom pip._vendor import msgpack\nfrom pip._vendor.requests.structures import CaseInsensitiveDict\n\nfrom .compat import HTTPResponse, pickle, text_type\n\n\ndef _b64_decode_bytes(b):\n    return base64.b64decode(b.encode(\"ascii\"))\n\n\ndef _b64_decode_str(s):\n    return _b64_decode_bytes(s).decode(\"utf8\")\n\n\nclass Serializer(object):\n\n    def dumps(self, request, response, body=None):\n        response_headers = CaseInsensitiveDict(response.headers)\n\n        if body is None:\n            body = response.read(decode_content=False)\n\n            # NOTE: 99% sure this is dead code. I'm only leaving it\n            #       here b/c I don't have a test yet to prove\n            #       it. Basically, before using\n            #       `cachecontrol.filewrapper.CallbackFileWrapper`,\n            #       this made an effort to reset the file handle. The\n            #       `CallbackFileWrapper` short circuits this code by\n            #       setting the body as the content is consumed, the\n            #       result being a `body` argument is *always* passed\n            #       into cache_response, and in turn,\n            #       `Serializer.dump`.\n            response._fp = io.BytesIO(body)\n\n        # NOTE: This is all a bit weird, but it's really important that on\n        #       Python 2.x these objects are unicode and not str, even when\n        #       they contain only ascii. The problem here is that msgpack\n        #       understands the difference between unicode and bytes and we\n        #       have it set to differentiate between them, however Python 2\n        #       doesn't know the difference. Forcing these to unicode will be\n        #       enough to have msgpack know the difference.\n        data = {\n            u\"response\": {\n                u\"body\": body,\n                u\"headers\": dict(\n                    (text_type(k), text_type(v)) for k, v in response.headers.items()\n                ),\n                u\"status\": response.status,\n                u\"version\": response.version,\n                u\"reason\": text_type(response.reason),\n                u\"strict\": response.strict,\n                u\"decode_content\": response.decode_content,\n            }\n        }\n\n        # Construct our vary headers\n        data[u\"vary\"] = {}\n        if u\"vary\" in response_headers:\n            varied_headers = response_headers[u\"vary\"].split(\",\")\n            for header in varied_headers:\n                header = text_type(header).strip()\n                header_value = request.headers.get(header, None)\n                if header_value is not None:\n                    header_value = text_type(header_value)\n                data[u\"vary\"][header] = header_value\n\n        return b\",\".join([b\"cc=4\", msgpack.dumps(data, use_bin_type=True)])\n\n    def loads(self, request, data):\n        # Short circuit if we've been given an empty set of data\n        if not data:\n            return\n\n        # Determine what version of the serializer the data was serialized\n        # with\n        try:\n            ver, data = data.split(b\",\", 1)\n        except ValueError:\n            ver = b\"cc=0\"\n\n        # Make sure that our \"ver\" is actually a version and isn't a false\n        # positive from a , being in the data stream.\n        if ver[:3] != b\"cc=\":\n            data = ver + data\n            ver = b\"cc=0\"\n\n        # Get the version number out of the cc=N\n        ver = ver.split(b\"=\", 1)[-1].decode(\"ascii\")\n\n        # Dispatch to the actual load method for the given version\n        try:\n            return getattr(self, \"_loads_v{}\".format(ver))(request, data)\n\n        except AttributeError:\n            # This is a version we don't have a loads function for, so we'll\n            # just treat it as a miss and return None\n            return\n\n    def prepare_response(self, request, cached):\n        \"\"\"Verify our vary headers match and construct a real urllib3\n        HTTPResponse object.\n        \"\"\"\n        # Special case the '*' Vary value as it means we cannot actually\n        # determine if the cached response is suitable for this request.\n        if \"*\" in cached.get(\"vary\", {}):\n            return\n\n        # Ensure that the Vary headers for the cached response match our\n        # request\n        for header, value in cached.get(\"vary\", {}).items():\n            if request.headers.get(header, None) != value:\n                return\n\n        body_raw = cached[\"response\"].pop(\"body\")\n\n        headers = CaseInsensitiveDict(data=cached[\"response\"][\"headers\"])\n        if headers.get(\"transfer-encoding\", \"\") == \"chunked\":\n            headers.pop(\"transfer-encoding\")\n\n        cached[\"response\"][\"headers\"] = headers\n\n        try:\n            body = io.BytesIO(body_raw)\n        except TypeError:\n            # This can happen if cachecontrol serialized to v1 format (pickle)\n            # using Python 2. A Python 2 str(byte string) will be unpickled as\n            # a Python 3 str (unicode string), which will cause the above to\n            # fail with:\n            #\n            #     TypeError: 'str' does not support the buffer interface\n            body = io.BytesIO(body_raw.encode(\"utf8\"))\n\n        return HTTPResponse(body=body, preload_content=False, **cached[\"response\"])\n\n    def _loads_v0(self, request, data):\n        # The original legacy cache data. This doesn't contain enough\n        # information to construct everything we need, so we'll treat this as\n        # a miss.\n        return\n\n    def _loads_v1(self, request, data):\n        try:\n            cached = pickle.loads(data)\n        except ValueError:\n            return\n\n        return self.prepare_response(request, cached)\n\n    def _loads_v2(self, request, data):\n        try:\n            cached = json.loads(zlib.decompress(data).decode(\"utf8\"))\n        except (ValueError, zlib.error):\n            return\n\n        # We need to decode the items that we've base64 encoded\n        cached[\"response\"][\"body\"] = _b64_decode_bytes(cached[\"response\"][\"body\"])\n        cached[\"response\"][\"headers\"] = dict(\n            (_b64_decode_str(k), _b64_decode_str(v))\n            for k, v in cached[\"response\"][\"headers\"].items()\n        )\n        cached[\"response\"][\"reason\"] = _b64_decode_str(cached[\"response\"][\"reason\"])\n        cached[\"vary\"] = dict(\n            (_b64_decode_str(k), _b64_decode_str(v) if v is not None else v)\n            for k, v in cached[\"vary\"].items()\n        )\n\n        return self.prepare_response(request, cached)\n\n    def _loads_v3(self, request, data):\n        # Due to Python 2 encoding issues, it's impossible to know for sure\n        # exactly how to load v3 entries, thus we'll treat these as a miss so\n        # that they get rewritten out as v4 entries.\n        return\n\n    def _loads_v4(self, request, data):\n        try:\n            cached = msgpack.loads(data, encoding=\"utf-8\")\n        except ValueError:\n            return\n\n        return self.prepare_response(request, cached)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/cachecontrol/wrapper.py",
    "content": "from .adapter import CacheControlAdapter\nfrom .cache import DictCache\n\n\ndef CacheControl(\n    sess,\n    cache=None,\n    cache_etags=True,\n    serializer=None,\n    heuristic=None,\n    controller_class=None,\n    adapter_class=None,\n    cacheable_methods=None,\n):\n\n    cache = cache or DictCache()\n    adapter_class = adapter_class or CacheControlAdapter\n    adapter = adapter_class(\n        cache,\n        cache_etags=cache_etags,\n        serializer=serializer,\n        heuristic=heuristic,\n        controller_class=controller_class,\n        cacheable_methods=cacheable_methods,\n    )\n    sess.mount(\"http://\", adapter)\n    sess.mount(\"https://\", adapter)\n\n    return sess\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/certifi/__init__.py",
    "content": "from .core import where\n\n__version__ = \"2018.11.29\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/certifi/__main__.py",
    "content": "from pip._vendor.certifi import where\nprint(where())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/certifi/cacert.pem",
    "content": "\n# Issuer: CN=GlobalSign Root CA O=GlobalSign nv-sa OU=Root CA\n# Subject: CN=GlobalSign Root CA O=GlobalSign nv-sa OU=Root CA\n# Label: \"GlobalSign Root CA\"\n# Serial: 4835703278459707669005204\n# MD5 Fingerprint: 3e:45:52:15:09:51:92:e1:b7:5d:37:9f:b1:87:29:8a\n# SHA1 Fingerprint: b1:bc:96:8b:d4:f4:9d:62:2a:a8:9a:81:f2:15:01:52:a4:1d:82:9c\n# SHA256 Fingerprint: eb:d4:10:40:e4:bb:3e:c7:42:c9:e3:81:d3:1e:f2:a4:1a:48:b6:68:5c:96:e7:ce:f3:c1:df:6c:d4:33:1c:99\n-----BEGIN CERTIFICATE-----\nMIIDdTCCAl2gAwIBAgILBAAAAAABFUtaw5QwDQYJKoZIhvcNAQEFBQAwVzELMAkG\nA1UEBhMCQkUxGTAXBgNVBAoTEEdsb2JhbFNpZ24gbnYtc2ExEDAOBgNVBAsTB1Jv\nb3QgQ0ExGzAZBgNVBAMTEkdsb2JhbFNpZ24gUm9vdCBDQTAeFw05ODA5MDExMjAw\nMDBaFw0yODAxMjgxMjAwMDBaMFcxCzAJBgNVBAYTAkJFMRkwFwYDVQQKExBHbG9i\nYWxTaWduIG52LXNhMRAwDgYDVQQLEwdSb290IENBMRswGQYDVQQDExJHbG9iYWxT\naWduIFJvb3QgQ0EwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDaDuaZ\njc6j40+Kfvvxi4Mla+pIH/EqsLmVEQS98GPR4mdmzxzdzxtIK+6NiY6arymAZavp\nxy0Sy6scTHAHoT0KMM0VjU/43dSMUBUc71DuxC73/OlS8pF94G3VNTCOXkNz8kHp\n1Wrjsok6Vjk4bwY8iGlbKk3Fp1S4bInMm/k8yuX9ifUSPJJ4ltbcdG6TRGHRjcdG\nsnUOhugZitVtbNV4FpWi6cgKOOvyJBNPc1STE4U6G7weNLWLBYy5d4ux2x8gkasJ\nU26Qzns3dLlwR5EiUWMWea6xrkEmCMgZK9FGqkjWZCrXgzT/LCrBbBlDSgeF59N8\n9iFo7+ryUp9/k5DPAgMBAAGjQjBAMA4GA1UdDwEB/wQEAwIBBjAPBgNVHRMBAf8E\nBTADAQH/MB0GA1UdDgQWBBRge2YaRQ2XyolQL30EzTSo//z9SzANBgkqhkiG9w0B\nAQUFAAOCAQEA1nPnfE920I2/7LqivjTFKDK1fPxsnCwrvQmeU79rXqoRSLblCKOz\nyj1hTdNGCbM+w6DjY1Ub8rrvrTnhQ7k4o+YviiY776BQVvnGCv04zcQLcFGUl5gE\n38NflNUVyRRBnMRddWQVDf9VMOyGj/8N7yy5Y0b2qvzfvGn9LhJIZJrglfCm7ymP\nAbEVtQwdpf5pLGkkeB6zpxxxYu7KyJesF12KwvhHhm4qxFYxldBniYUr+WymXUad\nDKqC5JlR3XC321Y9YeRq4VzW9v493kHMB65jUr9TU/Qr6cf9tveCX4XSQRjbgbME\nHMUfpIBvFSDJ3gyICh3WZlXi/EjJKSZp4A==\n-----END CERTIFICATE-----\n\n# Issuer: CN=GlobalSign O=GlobalSign OU=GlobalSign Root CA - R2\n# Subject: CN=GlobalSign O=GlobalSign OU=GlobalSign Root CA - R2\n# Label: \"GlobalSign Root CA - R2\"\n# Serial: 4835703278459682885658125\n# MD5 Fingerprint: 94:14:77:7e:3e:5e:fd:8f:30:bd:41:b0:cf:e7:d0:30\n# SHA1 Fingerprint: 75:e0:ab:b6:13:85:12:27:1c:04:f8:5f:dd:de:38:e4:b7:24:2e:fe\n# SHA256 Fingerprint: ca:42:dd:41:74:5f:d0:b8:1e:b9:02:36:2c:f9:d8:bf:71:9d:a1:bd:1b:1e:fc:94:6f:5b:4c:99:f4:2c:1b:9e\n-----BEGIN CERTIFICATE-----\nMIIDujCCAqKgAwIBAgILBAAAAAABD4Ym5g0wDQYJKoZIhvcNAQEFBQAwTDEgMB4G\nA1UECxMXR2xvYmFsU2lnbiBSb290IENBIC0gUjIxEzARBgNVBAoTCkdsb2JhbFNp\nZ24xEzARBgNVBAMTCkdsb2JhbFNpZ24wHhcNMDYxMjE1MDgwMDAwWhcNMjExMjE1\nMDgwMDAwWjBMMSAwHgYDVQQLExdHbG9iYWxTaWduIFJvb3QgQ0EgLSBSMjETMBEG\nA1UEChMKR2xvYmFsU2lnbjETMBEGA1UEAxMKR2xvYmFsU2lnbjCCASIwDQYJKoZI\nhvcNAQEBBQADggEPADCCAQoCggEBAKbPJA6+Lm8omUVCxKs+IVSbC9N/hHD6ErPL\nv4dfxn+G07IwXNb9rfF73OX4YJYJkhD10FPe+3t+c4isUoh7SqbKSaZeqKeMWhG8\neoLrvozps6yWJQeXSpkqBy+0Hne/ig+1AnwblrjFuTosvNYSuetZfeLQBoZfXklq\ntTleiDTsvHgMCJiEbKjNS7SgfQx5TfC4LcshytVsW33hoCmEofnTlEnLJGKRILzd\nC9XZzPnqJworc5HGnRusyMvo4KD0L5CLTfuwNhv2GXqF4G3yYROIXJ/gkwpRl4pa\nzq+r1feqCapgvdzZX99yqWATXgAByUr6P6TqBwMhAo6CygPCm48CAwEAAaOBnDCB\nmTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQUm+IH\nV2ccHsBqBt5ZtJot39wZhi4wNgYDVR0fBC8wLTAroCmgJ4YlaHR0cDovL2NybC5n\nbG9iYWxzaWduLm5ldC9yb290LXIyLmNybDAfBgNVHSMEGDAWgBSb4gdXZxwewGoG\n3lm0mi3f3BmGLjANBgkqhkiG9w0BAQUFAAOCAQEAmYFThxxol4aR7OBKuEQLq4Gs\nJ0/WwbgcQ3izDJr86iw8bmEbTUsp9Z8FHSbBuOmDAGJFtqkIk7mpM0sYmsL4h4hO\n291xNBrBVNpGP+DTKqttVCL1OmLNIG+6KYnX3ZHu01yiPqFbQfXf5WRDLenVOavS\not+3i9DAgBkcRcAtjOj4LaR0VknFBbVPFd5uRHg5h6h+u/N5GJG79G+dwfCMNYxd\nAfvDbbnvRG15RjF+Cv6pgsH/76tuIMRQyV+dTZsXjAzlAcmgQWpzU/qlULRuJQ/7\nTBj0/VLZjmmx6BEP3ojY+x1J96relc8geMJgEtslQIxq/H5COEBkEveegeGTLg==\n-----END CERTIFICATE-----\n\n# Issuer: CN=VeriSign Class 3 Public Primary Certification Authority - G3 O=VeriSign, Inc. OU=VeriSign Trust Network/(c) 1999 VeriSign, Inc. - For authorized use only\n# Subject: CN=VeriSign Class 3 Public Primary Certification Authority - G3 O=VeriSign, Inc. OU=VeriSign Trust Network/(c) 1999 VeriSign, Inc. - For authorized use only\n# Label: \"Verisign Class 3 Public Primary Certification Authority - G3\"\n# Serial: 206684696279472310254277870180966723415\n# MD5 Fingerprint: cd:68:b6:a7:c7:c4:ce:75:e0:1d:4f:57:44:61:92:09\n# SHA1 Fingerprint: 13:2d:0d:45:53:4b:69:97:cd:b2:d5:c3:39:e2:55:76:60:9b:5c:c6\n# SHA256 Fingerprint: eb:04:cf:5e:b1:f3:9a:fa:76:2f:2b:b1:20:f2:96:cb:a5:20:c1:b9:7d:b1:58:95:65:b8:1c:b9:a1:7b:72:44\n-----BEGIN CERTIFICATE-----\nMIIEGjCCAwICEQCbfgZJoz5iudXukEhxKe9XMA0GCSqGSIb3DQEBBQUAMIHKMQsw\nCQYDVQQGEwJVUzEXMBUGA1UEChMOVmVyaVNpZ24sIEluYy4xHzAdBgNVBAsTFlZl\ncmlTaWduIFRydXN0IE5ldHdvcmsxOjA4BgNVBAsTMShjKSAxOTk5IFZlcmlTaWdu\nLCBJbmMuIC0gRm9yIGF1dGhvcml6ZWQgdXNlIG9ubHkxRTBDBgNVBAMTPFZlcmlT\naWduIENsYXNzIDMgUHVibGljIFByaW1hcnkgQ2VydGlmaWNhdGlvbiBBdXRob3Jp\ndHkgLSBHMzAeFw05OTEwMDEwMDAwMDBaFw0zNjA3MTYyMzU5NTlaMIHKMQswCQYD\nVQQGEwJVUzEXMBUGA1UEChMOVmVyaVNpZ24sIEluYy4xHzAdBgNVBAsTFlZlcmlT\naWduIFRydXN0IE5ldHdvcmsxOjA4BgNVBAsTMShjKSAxOTk5IFZlcmlTaWduLCBJ\nbmMuIC0gRm9yIGF1dGhvcml6ZWQgdXNlIG9ubHkxRTBDBgNVBAMTPFZlcmlTaWdu\nIENsYXNzIDMgUHVibGljIFByaW1hcnkgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkg\nLSBHMzCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMu6nFL8eB8aHm8b\nN3O9+MlrlBIwT/A2R/XQkQr1F8ilYcEWQE37imGQ5XYgwREGfassbqb1EUGO+i2t\nKmFZpGcmTNDovFJbcCAEWNF6yaRpvIMXZK0Fi7zQWM6NjPXr8EJJC52XJ2cybuGu\nkxUccLwgTS8Y3pKI6GyFVxEa6X7jJhFUokWWVYPKMIno3Nij7SqAP395ZVc+FSBm\nCC+Vk7+qRy+oRpfwEuL+wgorUeZ25rdGt+INpsyow0xZVYnm6FNcHOqd8GIWC6fJ\nXwzw3sJ2zq/3avL6QaaiMxTJ5Xpj055iN9WFZZ4O5lMkdBteHRJTW8cs54NJOxWu\nimi5V5cCAwEAATANBgkqhkiG9w0BAQUFAAOCAQEAERSWwauSCPc/L8my/uRan2Te\n2yFPhpk0djZX3dAVL8WtfxUfN2JzPtTnX84XA9s1+ivbrmAJXx5fj267Cz3qWhMe\nDGBvtcC1IyIuBwvLqXTLR7sdwdela8wv0kL9Sd2nic9TutoAWii/gt/4uhMdUIaC\n/Y4wjylGsB49Ndo4YhYYSq3mtlFs3q9i6wHQHiT+eo8SGhJouPtmmRQURVyu565p\nF4ErWjfJXir0xuKhXFSbplQAz/DxwceYMBo7Nhbbo27q/a2ywtrvAkcTisDxszGt\nTxzhT5yvDwyd93gN2PQ1VoDat20Xj50egWTh/sVFuq1ruQp6Tk9LhO5L8X3dEQ==\n-----END CERTIFICATE-----\n\n# Issuer: CN=Entrust.net Certification Authority (2048) O=Entrust.net OU=www.entrust.net/CPS_2048 incorp. by ref. (limits liab.)/(c) 1999 Entrust.net Limited\n# Subject: CN=Entrust.net Certification Authority (2048) O=Entrust.net OU=www.entrust.net/CPS_2048 incorp. by ref. (limits liab.)/(c) 1999 Entrust.net Limited\n# Label: \"Entrust.net Premium 2048 Secure Server CA\"\n# Serial: 946069240\n# MD5 Fingerprint: ee:29:31:bc:32:7e:9a:e6:e8:b5:f7:51:b4:34:71:90\n# SHA1 Fingerprint: 50:30:06:09:1d:97:d4:f5:ae:39:f7:cb:e7:92:7d:7d:65:2d:34:31\n# SHA256 Fingerprint: 6d:c4:71:72:e0:1c:bc:b0:bf:62:58:0d:89:5f:e2:b8:ac:9a:d4:f8:73:80:1e:0c:10:b9:c8:37:d2:1e:b1:77\n-----BEGIN CERTIFICATE-----\nMIIEKjCCAxKgAwIBAgIEOGPe+DANBgkqhkiG9w0BAQUFADCBtDEUMBIGA1UEChML\nRW50cnVzdC5uZXQxQDA+BgNVBAsUN3d3dy5lbnRydXN0Lm5ldC9DUFNfMjA0OCBp\nbmNvcnAuIGJ5IHJlZi4gKGxpbWl0cyBsaWFiLikxJTAjBgNVBAsTHChjKSAxOTk5\nIEVudHJ1c3QubmV0IExpbWl0ZWQxMzAxBgNVBAMTKkVudHJ1c3QubmV0IENlcnRp\nZmljYXRpb24gQXV0aG9yaXR5ICgyMDQ4KTAeFw05OTEyMjQxNzUwNTFaFw0yOTA3\nMjQxNDE1MTJaMIG0MRQwEgYDVQQKEwtFbnRydXN0Lm5ldDFAMD4GA1UECxQ3d3d3\nLmVudHJ1c3QubmV0L0NQU18yMDQ4IGluY29ycC4gYnkgcmVmLiAobGltaXRzIGxp\nYWIuKTElMCMGA1UECxMcKGMpIDE5OTkgRW50cnVzdC5uZXQgTGltaXRlZDEzMDEG\nA1UEAxMqRW50cnVzdC5uZXQgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkgKDIwNDgp\nMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEArU1LqRKGsuqjIAcVFmQq\nK0vRvwtKTY7tgHalZ7d4QMBzQshowNtTK91euHaYNZOLGp18EzoOH1u3Hs/lJBQe\nsYGpjX24zGtLA/ECDNyrpUAkAH90lKGdCCmziAv1h3edVc3kw37XamSrhRSGlVuX\nMlBvPci6Zgzj/L24ScF2iUkZ/cCovYmjZy/Gn7xxGWC4LeksyZB2ZnuU4q941mVT\nXTzWnLLPKQP5L6RQstRIzgUyVYr9smRMDuSYB3Xbf9+5CFVghTAp+XtIpGmG4zU/\nHoZdenoVve8AjhUiVBcAkCaTvA5JaJG/+EfTnZVCwQ5N328mz8MYIWJmQ3DW1cAH\n4QIDAQABo0IwQDAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zAdBgNV\nHQ4EFgQUVeSB0RGAvtiJuQijMfmhJAkWuXAwDQYJKoZIhvcNAQEFBQADggEBADub\nj1abMOdTmXx6eadNl9cZlZD7Bh/KM3xGY4+WZiT6QBshJ8rmcnPyT/4xmf3IDExo\nU8aAghOY+rat2l098c5u9hURlIIM7j+VrxGrD9cv3h8Dj1csHsm7mhpElesYT6Yf\nzX1XEC+bBAlahLVu2B064dae0Wx5XnkcFMXj0EyTO2U87d89vqbllRrDtRnDvV5b\nu/8j72gZyxKTJ1wDLW8w0B62GqzeWvfRqqgnpv55gcR5mTNXuhKwqeBCbJPKVt7+\nbYQLCIt+jerXmCHG8+c8eS9enNFMFY3h7CI3zJpDC5fcgJCNs2ebb0gIFVbPv/Er\nfF6adulZkMV8gzURZVE=\n-----END CERTIFICATE-----\n\n# Issuer: CN=Baltimore CyberTrust Root O=Baltimore OU=CyberTrust\n# Subject: CN=Baltimore CyberTrust Root O=Baltimore OU=CyberTrust\n# Label: \"Baltimore CyberTrust Root\"\n# Serial: 33554617\n# MD5 Fingerprint: ac:b6:94:a5:9c:17:e0:d7:91:52:9b:b1:97:06:a6:e4\n# SHA1 Fingerprint: d4:de:20:d0:5e:66:fc:53:fe:1a:50:88:2c:78:db:28:52:ca:e4:74\n# SHA256 Fingerprint: 16:af:57:a9:f6:76:b0:ab:12:60:95:aa:5e:ba:de:f2:2a:b3:11:19:d6:44:ac:95:cd:4b:93:db:f3:f2:6a:eb\n-----BEGIN CERTIFICATE-----\nMIIDdzCCAl+gAwIBAgIEAgAAuTANBgkqhkiG9w0BAQUFADBaMQswCQYDVQQGEwJJ\nRTESMBAGA1UEChMJQmFsdGltb3JlMRMwEQYDVQQLEwpDeWJlclRydXN0MSIwIAYD\nVQQDExlCYWx0aW1vcmUgQ3liZXJUcnVzdCBSb290MB4XDTAwMDUxMjE4NDYwMFoX\nDTI1MDUxMjIzNTkwMFowWjELMAkGA1UEBhMCSUUxEjAQBgNVBAoTCUJhbHRpbW9y\nZTETMBEGA1UECxMKQ3liZXJUcnVzdDEiMCAGA1UEAxMZQmFsdGltb3JlIEN5YmVy\nVHJ1c3QgUm9vdDCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAKMEuyKr\nmD1X6CZymrV51Cni4eiVgLGw41uOKymaZN+hXe2wCQVt2yguzmKiYv60iNoS6zjr\nIZ3AQSsBUnuId9Mcj8e6uYi1agnnc+gRQKfRzMpijS3ljwumUNKoUMMo6vWrJYeK\nmpYcqWe4PwzV9/lSEy/CG9VwcPCPwBLKBsua4dnKM3p31vjsufFoREJIE9LAwqSu\nXmD+tqYF/LTdB1kC1FkYmGP1pWPgkAx9XbIGevOF6uvUA65ehD5f/xXtabz5OTZy\ndc93Uk3zyZAsuT3lySNTPx8kmCFcB5kpvcY67Oduhjprl3RjM71oGDHweI12v/ye\njl0qhqdNkNwnGjkCAwEAAaNFMEMwHQYDVR0OBBYEFOWdWTCCR1jMrPoIVDaGezq1\nBE3wMBIGA1UdEwEB/wQIMAYBAf8CAQMwDgYDVR0PAQH/BAQDAgEGMA0GCSqGSIb3\nDQEBBQUAA4IBAQCFDF2O5G9RaEIFoN27TyclhAO992T9Ldcw46QQF+vaKSm2eT92\n9hkTI7gQCvlYpNRhcL0EYWoSihfVCr3FvDB81ukMJY2GQE/szKN+OMY3EU/t3Wgx\njkzSswF07r51XgdIGn9w/xZchMB5hbgF/X++ZRGjD8ACtPhSNzkE1akxehi/oCr0\nEpn3o0WC4zxe9Z2etciefC7IpJ5OCBRLbf1wbWsaY71k5h+3zvDyny67G7fyUIhz\nksLi4xaNmjICq44Y3ekQEe5+NauQrz4wlHrQMz2nZQ/1/I6eYs9HRCwBXbsdtTLS\nR9I4LtD+gdwyah617jzV/OeBHRnDJELqYzmp\n-----END CERTIFICATE-----\n\n# Issuer: CN=AddTrust External CA Root O=AddTrust AB OU=AddTrust External TTP Network\n# Subject: CN=AddTrust External CA Root O=AddTrust AB OU=AddTrust External TTP Network\n# Label: \"AddTrust External Root\"\n# Serial: 1\n# MD5 Fingerprint: 1d:35:54:04:85:78:b0:3f:42:42:4d:bf:20:73:0a:3f\n# SHA1 Fingerprint: 02:fa:f3:e2:91:43:54:68:60:78:57:69:4d:f5:e4:5b:68:85:18:68\n# SHA256 Fingerprint: 68:7f:a4:51:38:22:78:ff:f0:c8:b1:1f:8d:43:d5:76:67:1c:6e:b2:bc:ea:b4:13:fb:83:d9:65:d0:6d:2f:f2\n-----BEGIN CERTIFICATE-----\nMIIENjCCAx6gAwIBAgIBATANBgkqhkiG9w0BAQUFADBvMQswCQYDVQQGEwJTRTEU\nMBIGA1UEChMLQWRkVHJ1c3QgQUIxJjAkBgNVBAsTHUFkZFRydXN0IEV4dGVybmFs\nIFRUUCBOZXR3b3JrMSIwIAYDVQQDExlBZGRUcnVzdCBFeHRlcm5hbCBDQSBSb290\nMB4XDTAwMDUzMDEwNDgzOFoXDTIwMDUzMDEwNDgzOFowbzELMAkGA1UEBhMCU0Ux\nFDASBgNVBAoTC0FkZFRydXN0IEFCMSYwJAYDVQQLEx1BZGRUcnVzdCBFeHRlcm5h\nbCBUVFAgTmV0d29yazEiMCAGA1UEAxMZQWRkVHJ1c3QgRXh0ZXJuYWwgQ0EgUm9v\ndDCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALf3GjPm8gAELTngTlvt\nH7xsD821+iO2zt6bETOXpClMfZOfvUq8k+0DGuOPz+VtUFrWlymUWoCwSXrbLpX9\nuMq/NzgtHj6RQa1wVsfwTz/oMp50ysiQVOnGXw94nZpAPA6sYapeFI+eh6FqUNzX\nmk6vBbOmcZSccbNQYArHE504B4YCqOmoaSYYkKtMsE8jqzpPhNjfzp/haW+710LX\na0Tkx63ubUFfclpxCDezeWWkWaCUN/cALw3CknLa0Dhy2xSoRcRdKn23tNbE7qzN\nE0S3ySvdQwAl+mG5aWpYIxG3pzOPVnVZ9c0p10a3CitlttNCbxWyuHv77+ldU9U0\nWicCAwEAAaOB3DCB2TAdBgNVHQ4EFgQUrb2YejS0Jvf6xCZU7wO94CTLVBowCwYD\nVR0PBAQDAgEGMA8GA1UdEwEB/wQFMAMBAf8wgZkGA1UdIwSBkTCBjoAUrb2YejS0\nJvf6xCZU7wO94CTLVBqhc6RxMG8xCzAJBgNVBAYTAlNFMRQwEgYDVQQKEwtBZGRU\ncnVzdCBBQjEmMCQGA1UECxMdQWRkVHJ1c3QgRXh0ZXJuYWwgVFRQIE5ldHdvcmsx\nIjAgBgNVBAMTGUFkZFRydXN0IEV4dGVybmFsIENBIFJvb3SCAQEwDQYJKoZIhvcN\nAQEFBQADggEBALCb4IUlwtYj4g+WBpKdQZic2YR5gdkeWxQHIzZlj7DYd7usQWxH\nYINRsPkyPef89iYTx4AWpb9a/IfPeHmJIZriTAcKhjW88t5RxNKWt9x+Tu5w/Rw5\n6wwCURQtjr0W4MHfRnXnJK3s9EK0hZNwEGe6nQY1ShjTK3rMUUKhemPR5ruhxSvC\nNr4TDea9Y355e6cJDUCrat2PisP29owaQgVR1EX1n6diIWgVIEM8med8vSTYqZEX\nc4g/VhsxOBi0cQ+azcgOno4uG+GMmIPLHzHxREzGBHNJdmAPx/i9F4BrLunMTA5a\nmnkPIAou1Z5jJh5VkpTYghdae9C8x49OhgQ=\n-----END CERTIFICATE-----\n\n# Issuer: CN=Entrust Root Certification Authority O=Entrust, Inc. OU=www.entrust.net/CPS is incorporated by reference/(c) 2006 Entrust, Inc.\n# Subject: CN=Entrust Root Certification Authority O=Entrust, Inc. OU=www.entrust.net/CPS is incorporated by reference/(c) 2006 Entrust, Inc.\n# Label: \"Entrust Root Certification Authority\"\n# Serial: 1164660820\n# MD5 Fingerprint: d6:a5:c3:ed:5d:dd:3e:00:c1:3d:87:92:1f:1d:3f:e4\n# SHA1 Fingerprint: b3:1e:b1:b7:40:e3:6c:84:02:da:dc:37:d4:4d:f5:d4:67:49:52:f9\n# SHA256 Fingerprint: 73:c1:76:43:4f:1b:c6:d5:ad:f4:5b:0e:76:e7:27:28:7c:8d:e5:76:16:c1:e6:e6:14:1a:2b:2c:bc:7d:8e:4c\n-----BEGIN CERTIFICATE-----\nMIIEkTCCA3mgAwIBAgIERWtQVDANBgkqhkiG9w0BAQUFADCBsDELMAkGA1UEBhMC\nVVMxFjAUBgNVBAoTDUVudHJ1c3QsIEluYy4xOTA3BgNVBAsTMHd3dy5lbnRydXN0\nLm5ldC9DUFMgaXMgaW5jb3Jwb3JhdGVkIGJ5IHJlZmVyZW5jZTEfMB0GA1UECxMW\nKGMpIDIwMDYgRW50cnVzdCwgSW5jLjEtMCsGA1UEAxMkRW50cnVzdCBSb290IENl\ncnRpZmljYXRpb24gQXV0aG9yaXR5MB4XDTA2MTEyNzIwMjM0MloXDTI2MTEyNzIw\nNTM0MlowgbAxCzAJBgNVBAYTAlVTMRYwFAYDVQQKEw1FbnRydXN0LCBJbmMuMTkw\nNwYDVQQLEzB3d3cuZW50cnVzdC5uZXQvQ1BTIGlzIGluY29ycG9yYXRlZCBieSBy\nZWZlcmVuY2UxHzAdBgNVBAsTFihjKSAyMDA2IEVudHJ1c3QsIEluYy4xLTArBgNV\nBAMTJEVudHJ1c3QgUm9vdCBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0eTCCASIwDQYJ\nKoZIhvcNAQEBBQADggEPADCCAQoCggEBALaVtkNC+sZtKm9I35RMOVcF7sN5EUFo\nNu3s/poBj6E4KPz3EEZmLk0eGrEaTsbRwJWIsMn/MYszA9u3g3s+IIRe7bJWKKf4\n4LlAcTfFy0cOlypowCKVYhXbR9n10Cv/gkvJrT7eTNuQgFA/CYqEAOwwCj0Yzfv9\nKlmaI5UXLEWeH25DeW0MXJj+SKfFI0dcXv1u5x609mhF0YaDW6KKjbHjKYD+JXGI\nrb68j6xSlkuqUY3kEzEZ6E5Nn9uss2rVvDlUccp6en+Q3X0dgNmBu1kmwhH+5pPi\n94DkZfs0Nw4pgHBNrziGLp5/V6+eF67rHMsoIV+2HNjnogQi+dPa2MsCAwEAAaOB\nsDCBrTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zArBgNVHRAEJDAi\ngA8yMDA2MTEyNzIwMjM0MlqBDzIwMjYxMTI3MjA1MzQyWjAfBgNVHSMEGDAWgBRo\nkORnpKZTgMeGZqTx90tD+4S9bTAdBgNVHQ4EFgQUaJDkZ6SmU4DHhmak8fdLQ/uE\nvW0wHQYJKoZIhvZ9B0EABBAwDhsIVjcuMTo0LjADAgSQMA0GCSqGSIb3DQEBBQUA\nA4IBAQCT1DCw1wMgKtD5Y+iRDAUgqV8ZyntyTtSx29CW+1RaGSwMCPeyvIWonX9t\nO1KzKtvn1ISMY/YPyyYBkVBs9F8U4pN0wBOeMDpQ47RgxRzwIkSNcUesyBrJ6Zua\nAGAT/3B+XxFNSRuzFVJ7yVTav52Vr2ua2J7p8eRDjeIRRDq/r72DQnNSi6q7pynP\n9WQcCk3RvKqsnyrQ/39/2n3qse0wJcGE2jTSW3iDVuycNsMm4hH2Z0kdkquM++v/\neu6FSqdQgPCnXEqULl8FmTxSQeDNtGPPAUO6nIPcj2A781q0tHuu2guQOHXvgR1m\n0vdXcDazv/wor3ElhVsT/h5/WrQ8\n-----END CERTIFICATE-----\n\n# Issuer: CN=GeoTrust Global CA O=GeoTrust Inc.\n# Subject: CN=GeoTrust Global CA O=GeoTrust Inc.\n# Label: \"GeoTrust Global CA\"\n# Serial: 144470\n# MD5 Fingerprint: f7:75:ab:29:fb:51:4e:b7:77:5e:ff:05:3c:99:8e:f5\n# SHA1 Fingerprint: de:28:f4:a4:ff:e5:b9:2f:a3:c5:03:d1:a3:49:a7:f9:96:2a:82:12\n# SHA256 Fingerprint: ff:85:6a:2d:25:1d:cd:88:d3:66:56:f4:50:12:67:98:cf:ab:aa:de:40:79:9c:72:2d:e4:d2:b5:db:36:a7:3a\n-----BEGIN CERTIFICATE-----\nMIIDVDCCAjygAwIBAgIDAjRWMA0GCSqGSIb3DQEBBQUAMEIxCzAJBgNVBAYTAlVT\nMRYwFAYDVQQKEw1HZW9UcnVzdCBJbmMuMRswGQYDVQQDExJHZW9UcnVzdCBHbG9i\nYWwgQ0EwHhcNMDIwNTIxMDQwMDAwWhcNMjIwNTIxMDQwMDAwWjBCMQswCQYDVQQG\nEwJVUzEWMBQGA1UEChMNR2VvVHJ1c3QgSW5jLjEbMBkGA1UEAxMSR2VvVHJ1c3Qg\nR2xvYmFsIENBMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA2swYYzD9\n9BcjGlZ+W988bDjkcbd4kdS8odhM+KhDtgPpTSEHCIjaWC9mOSm9BXiLnTjoBbdq\nfnGk5sRgprDvgOSJKA+eJdbtg/OtppHHmMlCGDUUna2YRpIuT8rxh0PBFpVXLVDv\niS2Aelet8u5fa9IAjbkU+BQVNdnARqN7csiRv8lVK83Qlz6cJmTM386DGXHKTubU\n1XupGc1V3sjs0l44U+VcT4wt/lAjNvxm5suOpDkZALeVAjmRCw7+OC7RHQWa9k0+\nbw8HHa8sHo9gOeL6NlMTOdReJivbPagUvTLrGAMoUgRx5aszPeE4uwc2hGKceeoW\nMPRfwCvocWvk+QIDAQABo1MwUTAPBgNVHRMBAf8EBTADAQH/MB0GA1UdDgQWBBTA\nephojYn7qwVkDBF9qn1luMrMTjAfBgNVHSMEGDAWgBTAephojYn7qwVkDBF9qn1l\nuMrMTjANBgkqhkiG9w0BAQUFAAOCAQEANeMpauUvXVSOKVCUn5kaFOSPeCpilKIn\nZ57QzxpeR+nBsqTP3UEaBU6bS+5Kb1VSsyShNwrrZHYqLizz/Tt1kL/6cdjHPTfS\ntQWVYrmm3ok9Nns4d0iXrKYgjy6myQzCsplFAMfOEVEiIuCl6rYVSAlk6l5PdPcF\nPseKUgzbFbS9bZvlxrFUaKnjaZC2mqUPuLk/IH2uSrW4nOQdtqvmlKXBx4Ot2/Un\nhw4EbNX/3aBd7YdStysVAq45pmp06drE57xNNB6pXE0zX5IJL4hmXXeXxx12E6nV\n5fEWCRE11azbJHFwLJhWC9kXtNHjUStedejV0NxPNO3CBWaAocvmMw==\n-----END CERTIFICATE-----\n\n# Issuer: CN=GeoTrust Universal CA O=GeoTrust Inc.\n# Subject: CN=GeoTrust Universal CA O=GeoTrust Inc.\n# Label: \"GeoTrust Universal CA\"\n# Serial: 1\n# MD5 Fingerprint: 92:65:58:8b:a2:1a:31:72:73:68:5c:b4:a5:7a:07:48\n# SHA1 Fingerprint: e6:21:f3:35:43:79:05:9a:4b:68:30:9d:8a:2f:74:22:15:87:ec:79\n# SHA256 Fingerprint: a0:45:9b:9f:63:b2:25:59:f5:fa:5d:4c:6d:b3:f9:f7:2f:f1:93:42:03:35:78:f0:73:bf:1d:1b:46:cb:b9:12\n-----BEGIN CERTIFICATE-----\nMIIFaDCCA1CgAwIBAgIBATANBgkqhkiG9w0BAQUFADBFMQswCQYDVQQGEwJVUzEW\nMBQGA1UEChMNR2VvVHJ1c3QgSW5jLjEeMBwGA1UEAxMVR2VvVHJ1c3QgVW5pdmVy\nc2FsIENBMB4XDTA0MDMwNDA1MDAwMFoXDTI5MDMwNDA1MDAwMFowRTELMAkGA1UE\nBhMCVVMxFjAUBgNVBAoTDUdlb1RydXN0IEluYy4xHjAcBgNVBAMTFUdlb1RydXN0\nIFVuaXZlcnNhbCBDQTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBAKYV\nVaCjxuAfjJ0hUNfBvitbtaSeodlyWL0AG0y/YckUHUWCq8YdgNY96xCcOq9tJPi8\ncQGeBvV8Xx7BDlXKg5pZMK4ZyzBIle0iN430SppyZj6tlcDgFgDgEB8rMQ7XlFTT\nQjOgNB0eRXbdT8oYN+yFFXoZCPzVx5zw8qkuEKmS5j1YPakWaDwvdSEYfyh3peFh\nF7em6fgemdtzbvQKoiFs7tqqhZJmr/Z6a4LauiIINQ/PQvE1+mrufislzDoR5G2v\nc7J2Ha3QsnhnGqQ5HFELZ1aD/ThdDc7d8Lsrlh/eezJS/R27tQahsiFepdaVaH/w\nmZ7cRQg+59IJDTWU3YBOU5fXtQlEIGQWFwMCTFMNaN7VqnJNk22CDtucvc+081xd\nVHppCZbW2xHBjXWotM85yM48vCR85mLK4b19p71XZQvk/iXttmkQ3CgaRr0BHdCX\nteGYO8A3ZNY9lO4L4fUorgtWv3GLIylBjobFS1J72HGrH4oVpjuDWtdYAVHGTEHZ\nf9hBZ3KiKN9gg6meyHv8U3NyWfWTehd2Ds735VzZC1U0oqpbtWpU5xPKV+yXbfRe\nBi9Fi1jUIxaS5BZuKGNZMN9QAZxjiRqf2xeUgnA3wySemkfWWspOqGmJch+RbNt+\nnhutxx9z3SxPGWX9f5NAEC7S8O08ni4oPmkmM8V7AgMBAAGjYzBhMA8GA1UdEwEB\n/wQFMAMBAf8wHQYDVR0OBBYEFNq7LqqwDLiIJlF0XG0D08DYj3rWMB8GA1UdIwQY\nMBaAFNq7LqqwDLiIJlF0XG0D08DYj3rWMA4GA1UdDwEB/wQEAwIBhjANBgkqhkiG\n9w0BAQUFAAOCAgEAMXjmx7XfuJRAyXHEqDXsRh3ChfMoWIawC/yOsjmPRFWrZIRc\naanQmjg8+uUfNeVE44B5lGiku8SfPeE0zTBGi1QrlaXv9z+ZhP015s8xxtxqv6fX\nIwjhmF7DWgh2qaavdy+3YL1ERmrvl/9zlcGO6JP7/TG37FcREUWbMPEaiDnBTzyn\nANXH/KttgCJwpQzgXQQpAvvLoJHRfNbDflDVnVi+QTjruXU8FdmbyUqDWcDaU/0z\nuzYYm4UPFd3uLax2k7nZAY1IEKj79TiG8dsKxr2EoyNB3tZ3b4XUhRxQ4K5RirqN\nPnbiucon8l+f725ZDQbYKxek0nxru18UGkiPGkzns0ccjkxFKyDuSN/n3QmOGKja\nQI2SJhFTYXNd673nxE0pN2HrrDktZy4W1vUAg4WhzH92xH3kt0tm7wNFYGm2DFKW\nkoRepqO1pD4r2czYG0eq8kTaT/kD6PAUyz/zg97QwVTjt+gKN02LIFkDMBmhLMi9\nER/frslKxfMnZmaGrGiR/9nmUxwPi1xpZQomyB40w11Re9epnAahNt3ViZS82eQt\nDF4JbAiXfKM9fJP/P6EUp8+1Xevb2xzEdt+Iub1FBZUbrvxGakyvSOPOrg/Sfuvm\nbJxPgWp6ZKy7PtXny3YuxadIwVyQD8vIP/rmMuGNG2+k5o7Y+SlIis5z/iw=\n-----END CERTIFICATE-----\n\n# Issuer: CN=GeoTrust Universal CA 2 O=GeoTrust Inc.\n# Subject: CN=GeoTrust Universal CA 2 O=GeoTrust Inc.\n# Label: \"GeoTrust Universal CA 2\"\n# Serial: 1\n# MD5 Fingerprint: 34:fc:b8:d0:36:db:9e:14:b3:c2:f2:db:8f:e4:94:c7\n# SHA1 Fingerprint: 37:9a:19:7b:41:85:45:35:0c:a6:03:69:f3:3c:2e:af:47:4f:20:79\n# SHA256 Fingerprint: a0:23:4f:3b:c8:52:7c:a5:62:8e:ec:81:ad:5d:69:89:5d:a5:68:0d:c9:1d:1c:b8:47:7f:33:f8:78:b9:5b:0b\n-----BEGIN CERTIFICATE-----\nMIIFbDCCA1SgAwIBAgIBATANBgkqhkiG9w0BAQUFADBHMQswCQYDVQQGEwJVUzEW\nMBQGA1UEChMNR2VvVHJ1c3QgSW5jLjEgMB4GA1UEAxMXR2VvVHJ1c3QgVW5pdmVy\nc2FsIENBIDIwHhcNMDQwMzA0MDUwMDAwWhcNMjkwMzA0MDUwMDAwWjBHMQswCQYD\nVQQGEwJVUzEWMBQGA1UEChMNR2VvVHJ1c3QgSW5jLjEgMB4GA1UEAxMXR2VvVHJ1\nc3QgVW5pdmVyc2FsIENBIDIwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoIC\nAQCzVFLByT7y2dyxUxpZKeexw0Uo5dfR7cXFS6GqdHtXr0om/Nj1XqduGdt0DE81\nWzILAePb63p3NeqqWuDW6KFXlPCQo3RWlEQwAx5cTiuFJnSCegx2oG9NzkEtoBUG\nFF+3Qs17j1hhNNwqCPkuwwGmIkQcTAeC5lvO0Ep8BNMZcyfwqph/Lq9O64ceJHdq\nXbboW0W63MOhBW9Wjo8QJqVJwy7XQYci4E+GymC16qFjwAGXEHm9ADwSbSsVsaxL\nse4YuU6W3Nx2/zu+z18DwPw76L5GG//aQMJS9/7jOvdqdzXQ2o3rXhhqMcceujwb\nKNZrVMaqW9eiLBsZzKIC9ptZvTdrhrVtgrrY6slWvKk2WP0+GfPtDCapkzj4T8Fd\nIgbQl+rhrcZV4IErKIM6+vR7IVEAvlI4zs1meaj0gVbi0IMJR1FbUGrP20gaXT73\ny/Zl92zxlfgCOzJWgjl6W70viRu/obTo/3+NjN8D8WBOWBFM66M/ECuDmgFz2ZRt\nhAAnZqzwcEAJQpKtT5MNYQlRJNiS1QuUYbKHsu3/mjX/hVTK7URDrBs8FmtISgoc\nQIgfksILAAX/8sgCSqSqqcyZlpwvWOB94b67B9xfBHJcMTTD7F8t4D1kkCLm0ey4\nLt1ZrtmhN79UNdxzMk+MBB4zsslG8dhcyFVQyWi9qLo2CQIDAQABo2MwYTAPBgNV\nHRMBAf8EBTADAQH/MB0GA1UdDgQWBBR281Xh+qQ2+/CfXGJx7Tz0RzgQKzAfBgNV\nHSMEGDAWgBR281Xh+qQ2+/CfXGJx7Tz0RzgQKzAOBgNVHQ8BAf8EBAMCAYYwDQYJ\nKoZIhvcNAQEFBQADggIBAGbBxiPz2eAubl/oz66wsCVNK/g7WJtAJDday6sWSf+z\ndXkzoS9tcBc0kf5nfo/sm+VegqlVHy/c1FEHEv6sFj4sNcZj/NwQ6w2jqtB8zNHQ\nL1EuxBRa3ugZ4T7GzKQp5y6EqgYweHZUcyiYWTjgAA1i00J9IZ+uPTqM1fp3DRgr\nFg5fNuH8KrUwJM/gYwx7WBr+mbpCErGR9Hxo4sjoryzqyX6uuyo9DRXcNJW2GHSo\nag/HtPQTxORb7QrSpJdMKu0vbBKJPfEncKpqA1Ihn0CoZ1Dy81of398j9tx4TuaY\nT1U6U+Pv8vSfx3zYWK8pIpe44L2RLrB27FcRz+8pRPPphXpgY+RdM4kX2TGq2tbz\nGDVyz4crL2MjhF2EjD9XoIj8mZEoJmmZ1I+XRL6O1UixpCgp8RW04eWe3fiPpm8m\n1wk8OhwRDqZsN/etRIcsKMfYdIKz0G9KV7s1KSegi+ghp4dkNl3M2Basx7InQJJV\nOCiNUW7dFGdTbHFcJoRNdVq2fmBWqU2t+5sel/MN2dKXVHfaPRK34B7vCAas+YWH\n6aLcr34YEoP9VhdBLtUpgn2Z9DH2canPLAEnpQW5qrJITirvn5NSUZU8UnOOVkwX\nQMAJKOSLakhT2+zNVVXxxvjpoixMptEmX36vWkzaH6byHCx+rgIW0lbQL1dTR+iS\n-----END CERTIFICATE-----\n\n# Issuer: CN=AAA Certificate Services O=Comodo CA Limited\n# Subject: CN=AAA Certificate Services O=Comodo CA Limited\n# Label: \"Comodo AAA Services root\"\n# Serial: 1\n# MD5 Fingerprint: 49:79:04:b0:eb:87:19:ac:47:b0:bc:11:51:9b:74:d0\n# SHA1 Fingerprint: d1:eb:23:a4:6d:17:d6:8f:d9:25:64:c2:f1:f1:60:17:64:d8:e3:49\n# SHA256 Fingerprint: d7:a7:a0:fb:5d:7e:27:31:d7:71:e9:48:4e:bc:de:f7:1d:5f:0c:3e:0a:29:48:78:2b:c8:3e:e0:ea:69:9e:f4\n-----BEGIN CERTIFICATE-----\nMIIEMjCCAxqgAwIBAgIBATANBgkqhkiG9w0BAQUFADB7MQswCQYDVQQGEwJHQjEb\nMBkGA1UECAwSR3JlYXRlciBNYW5jaGVzdGVyMRAwDgYDVQQHDAdTYWxmb3JkMRow\nGAYDVQQKDBFDb21vZG8gQ0EgTGltaXRlZDEhMB8GA1UEAwwYQUFBIENlcnRpZmlj\nYXRlIFNlcnZpY2VzMB4XDTA0MDEwMTAwMDAwMFoXDTI4MTIzMTIzNTk1OVowezEL\nMAkGA1UEBhMCR0IxGzAZBgNVBAgMEkdyZWF0ZXIgTWFuY2hlc3RlcjEQMA4GA1UE\nBwwHU2FsZm9yZDEaMBgGA1UECgwRQ29tb2RvIENBIExpbWl0ZWQxITAfBgNVBAMM\nGEFBQSBDZXJ0aWZpY2F0ZSBTZXJ2aWNlczCCASIwDQYJKoZIhvcNAQEBBQADggEP\nADCCAQoCggEBAL5AnfRu4ep2hxxNRUSOvkbIgwadwSr+GB+O5AL686tdUIoWMQua\nBtDFcCLNSS1UY8y2bmhGC1Pqy0wkwLxyTurxFa70VJoSCsN6sjNg4tqJVfMiWPPe\n3M/vg4aijJRPn2jymJBGhCfHdr/jzDUsi14HZGWCwEiwqJH5YZ92IFCokcdmtet4\nYgNW8IoaE+oxox6gmf049vYnMlhvB/VruPsUK6+3qszWY19zjNoFmag4qMsXeDZR\nrOme9Hg6jc8P2ULimAyrL58OAd7vn5lJ8S3frHRNG5i1R8XlKdH5kBjHYpy+g8cm\nez6KJcfA3Z3mNWgQIJ2P2N7Sw4ScDV7oL8kCAwEAAaOBwDCBvTAdBgNVHQ4EFgQU\noBEKIz6W8Qfs4q8p74Klf9AwpLQwDgYDVR0PAQH/BAQDAgEGMA8GA1UdEwEB/wQF\nMAMBAf8wewYDVR0fBHQwcjA4oDagNIYyaHR0cDovL2NybC5jb21vZG9jYS5jb20v\nQUFBQ2VydGlmaWNhdGVTZXJ2aWNlcy5jcmwwNqA0oDKGMGh0dHA6Ly9jcmwuY29t\nb2RvLm5ldC9BQUFDZXJ0aWZpY2F0ZVNlcnZpY2VzLmNybDANBgkqhkiG9w0BAQUF\nAAOCAQEACFb8AvCb6P+k+tZ7xkSAzk/ExfYAWMymtrwUSWgEdujm7l3sAg9g1o1Q\nGE8mTgHj5rCl7r+8dFRBv/38ErjHT1r0iWAFf2C3BUrz9vHCv8S5dIa2LX1rzNLz\nRt0vxuBqw8M0Ayx9lt1awg6nCpnBBYurDC/zXDrPbDdVCYfeU0BsWO/8tqtlbgT2\nG9w84FoVxp7Z8VlIMCFlA2zs6SFz7JsDoeA3raAVGI/6ugLOpyypEBMs1OUIJqsi\nl2D4kF501KKaU73yqWjgom7C12yxow+ev+to51byrvLjKzg6CYG1a4XXvi3tPxq3\nsmPi9WIsgtRqAEFQ8TmDn5XpNpaYbg==\n-----END CERTIFICATE-----\n\n# Issuer: CN=QuoVadis Root Certification Authority O=QuoVadis Limited OU=Root Certification Authority\n# Subject: CN=QuoVadis Root Certification Authority O=QuoVadis Limited OU=Root Certification Authority\n# Label: \"QuoVadis Root CA\"\n# Serial: 985026699\n# MD5 Fingerprint: 27:de:36:fe:72:b7:00:03:00:9d:f4:f0:1e:6c:04:24\n# SHA1 Fingerprint: de:3f:40:bd:50:93:d3:9b:6c:60:f6:da:bc:07:62:01:00:89:76:c9\n# SHA256 Fingerprint: a4:5e:de:3b:bb:f0:9c:8a:e1:5c:72:ef:c0:72:68:d6:93:a2:1c:99:6f:d5:1e:67:ca:07:94:60:fd:6d:88:73\n-----BEGIN CERTIFICATE-----\nMIIF0DCCBLigAwIBAgIEOrZQizANBgkqhkiG9w0BAQUFADB/MQswCQYDVQQGEwJC\nTTEZMBcGA1UEChMQUXVvVmFkaXMgTGltaXRlZDElMCMGA1UECxMcUm9vdCBDZXJ0\naWZpY2F0aW9uIEF1dGhvcml0eTEuMCwGA1UEAxMlUXVvVmFkaXMgUm9vdCBDZXJ0\naWZpY2F0aW9uIEF1dGhvcml0eTAeFw0wMTAzMTkxODMzMzNaFw0yMTAzMTcxODMz\nMzNaMH8xCzAJBgNVBAYTAkJNMRkwFwYDVQQKExBRdW9WYWRpcyBMaW1pdGVkMSUw\nIwYDVQQLExxSb290IENlcnRpZmljYXRpb24gQXV0aG9yaXR5MS4wLAYDVQQDEyVR\ndW9WYWRpcyBSb290IENlcnRpZmljYXRpb24gQXV0aG9yaXR5MIIBIjANBgkqhkiG\n9w0BAQEFAAOCAQ8AMIIBCgKCAQEAv2G1lVO6V/z68mcLOhrfEYBklbTRvM16z/Yp\nli4kVEAkOPcahdxYTMukJ0KX0J+DisPkBgNbAKVRHnAEdOLB1Dqr1607BxgFjv2D\nrOpm2RgbaIr1VxqYuvXtdj182d6UajtLF8HVj71lODqV0D1VNk7feVcxKh7YWWVJ\nWCCYfqtffp/p1k3sg3Spx2zY7ilKhSoGFPlU5tPaZQeLYzcS19Dsw3sgQUSj7cug\nF+FxZc4dZjH3dgEZyH0DWLaVSR2mEiboxgx24ONmy+pdpibu5cxfvWenAScOospU\nxbF6lR1xHkopigPcakXBpBlebzbNw6Kwt/5cOOJSvPhEQ+aQuwIDAQABo4ICUjCC\nAk4wPQYIKwYBBQUHAQEEMTAvMC0GCCsGAQUFBzABhiFodHRwczovL29jc3AucXVv\ndmFkaXNvZmZzaG9yZS5jb20wDwYDVR0TAQH/BAUwAwEB/zCCARoGA1UdIASCAREw\nggENMIIBCQYJKwYBBAG+WAABMIH7MIHUBggrBgEFBQcCAjCBxxqBxFJlbGlhbmNl\nIG9uIHRoZSBRdW9WYWRpcyBSb290IENlcnRpZmljYXRlIGJ5IGFueSBwYXJ0eSBh\nc3N1bWVzIGFjY2VwdGFuY2Ugb2YgdGhlIHRoZW4gYXBwbGljYWJsZSBzdGFuZGFy\nZCB0ZXJtcyBhbmQgY29uZGl0aW9ucyBvZiB1c2UsIGNlcnRpZmljYXRpb24gcHJh\nY3RpY2VzLCBhbmQgdGhlIFF1b1ZhZGlzIENlcnRpZmljYXRlIFBvbGljeS4wIgYI\nKwYBBQUHAgEWFmh0dHA6Ly93d3cucXVvdmFkaXMuYm0wHQYDVR0OBBYEFItLbe3T\nKbkGGew5Oanwl4Rqy+/fMIGuBgNVHSMEgaYwgaOAFItLbe3TKbkGGew5Oanwl4Rq\ny+/foYGEpIGBMH8xCzAJBgNVBAYTAkJNMRkwFwYDVQQKExBRdW9WYWRpcyBMaW1p\ndGVkMSUwIwYDVQQLExxSb290IENlcnRpZmljYXRpb24gQXV0aG9yaXR5MS4wLAYD\nVQQDEyVRdW9WYWRpcyBSb290IENlcnRpZmljYXRpb24gQXV0aG9yaXR5ggQ6tlCL\nMA4GA1UdDwEB/wQEAwIBBjANBgkqhkiG9w0BAQUFAAOCAQEAitQUtf70mpKnGdSk\nfnIYj9lofFIk3WdvOXrEql494liwTXCYhGHoG+NpGA7O+0dQoE7/8CQfvbLO9Sf8\n7C9TqnN7Az10buYWnuulLsS/VidQK2K6vkscPFVcQR0kvoIgR13VRH56FmjffU1R\ncHhXHTMe/QKZnAzNCgVPx7uOpHX6Sm2xgI4JVrmcGmD+XcHXetwReNDWXcG31a0y\nmQM6isxUJTkxgXsTIlG6Rmyhu576BGxJJnSP0nPrzDCi5upZIof4l/UO/erMkqQW\nxFIY6iHOsfHmhIHluqmGKPJDWl0Snawe2ajlCmqnf6CHKc/yiU3U7MXi5nrQNiOK\nSnQ2+Q==\n-----END CERTIFICATE-----\n\n# Issuer: CN=QuoVadis Root CA 2 O=QuoVadis Limited\n# Subject: CN=QuoVadis Root CA 2 O=QuoVadis Limited\n# Label: \"QuoVadis Root CA 2\"\n# Serial: 1289\n# MD5 Fingerprint: 5e:39:7b:dd:f8:ba:ec:82:e9:ac:62:ba:0c:54:00:2b\n# SHA1 Fingerprint: ca:3a:fb:cf:12:40:36:4b:44:b2:16:20:88:80:48:39:19:93:7c:f7\n# SHA256 Fingerprint: 85:a0:dd:7d:d7:20:ad:b7:ff:05:f8:3d:54:2b:20:9d:c7:ff:45:28:f7:d6:77:b1:83:89:fe:a5:e5:c4:9e:86\n-----BEGIN CERTIFICATE-----\nMIIFtzCCA5+gAwIBAgICBQkwDQYJKoZIhvcNAQEFBQAwRTELMAkGA1UEBhMCQk0x\nGTAXBgNVBAoTEFF1b1ZhZGlzIExpbWl0ZWQxGzAZBgNVBAMTElF1b1ZhZGlzIFJv\nb3QgQ0EgMjAeFw0wNjExMjQxODI3MDBaFw0zMTExMjQxODIzMzNaMEUxCzAJBgNV\nBAYTAkJNMRkwFwYDVQQKExBRdW9WYWRpcyBMaW1pdGVkMRswGQYDVQQDExJRdW9W\nYWRpcyBSb290IENBIDIwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQCa\nGMpLlA0ALa8DKYrwD4HIrkwZhR0In6spRIXzL4GtMh6QRr+jhiYaHv5+HBg6XJxg\nFyo6dIMzMH1hVBHL7avg5tKifvVrbxi3Cgst/ek+7wrGsxDp3MJGF/hd/aTa/55J\nWpzmM+Yklvc/ulsrHHo1wtZn/qtmUIttKGAr79dgw8eTvI02kfN/+NsRE8Scd3bB\nrrcCaoF6qUWD4gXmuVbBlDePSHFjIuwXZQeVikvfj8ZaCuWw419eaxGrDPmF60Tp\n+ARz8un+XJiM9XOva7R+zdRcAitMOeGylZUtQofX1bOQQ7dsE/He3fbE+Ik/0XX1\nksOR1YqI0JDs3G3eicJlcZaLDQP9nL9bFqyS2+r+eXyt66/3FsvbzSUr5R/7mp/i\nUcw6UwxI5g69ybR2BlLmEROFcmMDBOAENisgGQLodKcftslWZvB1JdxnwQ5hYIiz\nPtGo/KPaHbDRsSNU30R2be1B2MGyIrZTHN81Hdyhdyox5C315eXbyOD/5YDXC2Og\n/zOhD7osFRXql7PSorW+8oyWHhqPHWykYTe5hnMz15eWniN9gqRMgeKh0bpnX5UH\noycR7hYQe7xFSkyyBNKr79X9DFHOUGoIMfmR2gyPZFwDwzqLID9ujWc9Otb+fVuI\nyV77zGHcizN300QyNQliBJIWENieJ0f7OyHj+OsdWwIDAQABo4GwMIGtMA8GA1Ud\nEwEB/wQFMAMBAf8wCwYDVR0PBAQDAgEGMB0GA1UdDgQWBBQahGK8SEwzJQTU7tD2\nA8QZRtGUazBuBgNVHSMEZzBlgBQahGK8SEwzJQTU7tD2A8QZRtGUa6FJpEcwRTEL\nMAkGA1UEBhMCQk0xGTAXBgNVBAoTEFF1b1ZhZGlzIExpbWl0ZWQxGzAZBgNVBAMT\nElF1b1ZhZGlzIFJvb3QgQ0EgMoICBQkwDQYJKoZIhvcNAQEFBQADggIBAD4KFk2f\nBluornFdLwUvZ+YTRYPENvbzwCYMDbVHZF34tHLJRqUDGCdViXh9duqWNIAXINzn\ng/iN/Ae42l9NLmeyhP3ZRPx3UIHmfLTJDQtyU/h2BwdBR5YM++CCJpNVjP4iH2Bl\nfF/nJrP3MpCYUNQ3cVX2kiF495V5+vgtJodmVjB3pjd4M1IQWK4/YY7yarHvGH5K\nWWPKjaJW1acvvFYfzznB4vsKqBUsfU16Y8Zsl0Q80m/DShcK+JDSV6IZUaUtl0Ha\nB0+pUNqQjZRG4T7wlP0QADj1O+hA4bRuVhogzG9Yje0uRY/W6ZM/57Es3zrWIozc\nhLsib9D45MY56QSIPMO661V6bYCZJPVsAfv4l7CUW+v90m/xd2gNNWQjrLhVoQPR\nTUIZ3Ph1WVaj+ahJefivDrkRoHy3au000LYmYjgahwz46P0u05B/B5EqHdZ+XIWD\nmbA4CD/pXvk1B+TJYm5Xf6dQlfe6yJvmjqIBxdZmv3lh8zwc4bmCXF2gw+nYSL0Z\nohEUGW6yhhtoPkg3Goi3XZZenMfvJ2II4pEZXNLxId26F0KCl3GBUzGpn/Z9Yr9y\n4aOTHcyKJloJONDO1w2AFrR4pTqHTI2KpdVGl/IsELm8VCLAAVBpQ570su9t+Oza\n8eOx79+Rj1QqCyXBJhnEUhAFZdWCEOrCMc0u\n-----END CERTIFICATE-----\n\n# Issuer: CN=QuoVadis Root CA 3 O=QuoVadis Limited\n# Subject: CN=QuoVadis Root CA 3 O=QuoVadis Limited\n# Label: \"QuoVadis Root CA 3\"\n# Serial: 1478\n# MD5 Fingerprint: 31:85:3c:62:94:97:63:b9:aa:fd:89:4e:af:6f:e0:cf\n# SHA1 Fingerprint: 1f:49:14:f7:d8:74:95:1d:dd:ae:02:c0:be:fd:3a:2d:82:75:51:85\n# SHA256 Fingerprint: 18:f1:fc:7f:20:5d:f8:ad:dd:eb:7f:e0:07:dd:57:e3:af:37:5a:9c:4d:8d:73:54:6b:f4:f1:fe:d1:e1:8d:35\n-----BEGIN CERTIFICATE-----\nMIIGnTCCBIWgAwIBAgICBcYwDQYJKoZIhvcNAQEFBQAwRTELMAkGA1UEBhMCQk0x\nGTAXBgNVBAoTEFF1b1ZhZGlzIExpbWl0ZWQxGzAZBgNVBAMTElF1b1ZhZGlzIFJv\nb3QgQ0EgMzAeFw0wNjExMjQxOTExMjNaFw0zMTExMjQxOTA2NDRaMEUxCzAJBgNV\nBAYTAkJNMRkwFwYDVQQKExBRdW9WYWRpcyBMaW1pdGVkMRswGQYDVQQDExJRdW9W\nYWRpcyBSb290IENBIDMwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQDM\nV0IWVJzmmNPTTe7+7cefQzlKZbPoFog02w1ZkXTPkrgEQK0CSzGrvI2RaNggDhoB\n4hp7Thdd4oq3P5kazethq8Jlph+3t723j/z9cI8LoGe+AaJZz3HmDyl2/7FWeUUr\nH556VOijKTVopAFPD6QuN+8bv+OPEKhyq1hX51SGyMnzW9os2l2ObjyjPtr7guXd\n8lyyBTNvijbO0BNO/79KDDRMpsMhvVAEVeuxu537RR5kFd5VAYwCdrXLoT9Cabwv\nvWhDFlaJKjdhkf2mrk7AyxRllDdLkgbvBNDInIjbC3uBr7E9KsRlOni27tyAsdLT\nmZw67mtaa7ONt9XOnMK+pUsvFrGeaDsGb659n/je7Mwpp5ijJUMv7/FfJuGITfhe\nbtfZFG4ZM2mnO4SJk8RTVROhUXhA+LjJou57ulJCg54U7QVSWllWp5f8nT8KKdjc\nT5EOE7zelaTfi5m+rJsziO+1ga8bxiJTyPbH7pcUsMV8eFLI8M5ud2CEpukqdiDt\nWAEXMJPpGovgc2PZapKUSU60rUqFxKMiMPwJ7Wgic6aIDFUhWMXhOp8q3crhkODZ\nc6tsgLjoC2SToJyMGf+z0gzskSaHirOi4XCPLArlzW1oUevaPwV/izLmE1xr/l9A\n4iLItLRkT9a6fUg+qGkM17uGcclzuD87nSVL2v9A6wIDAQABo4IBlTCCAZEwDwYD\nVR0TAQH/BAUwAwEB/zCB4QYDVR0gBIHZMIHWMIHTBgkrBgEEAb5YAAMwgcUwgZMG\nCCsGAQUFBwICMIGGGoGDQW55IHVzZSBvZiB0aGlzIENlcnRpZmljYXRlIGNvbnN0\naXR1dGVzIGFjY2VwdGFuY2Ugb2YgdGhlIFF1b1ZhZGlzIFJvb3QgQ0EgMyBDZXJ0\naWZpY2F0ZSBQb2xpY3kgLyBDZXJ0aWZpY2F0aW9uIFByYWN0aWNlIFN0YXRlbWVu\ndC4wLQYIKwYBBQUHAgEWIWh0dHA6Ly93d3cucXVvdmFkaXNnbG9iYWwuY29tL2Nw\nczALBgNVHQ8EBAMCAQYwHQYDVR0OBBYEFPLAE+CCQz777i9nMpY1XNu4ywLQMG4G\nA1UdIwRnMGWAFPLAE+CCQz777i9nMpY1XNu4ywLQoUmkRzBFMQswCQYDVQQGEwJC\nTTEZMBcGA1UEChMQUXVvVmFkaXMgTGltaXRlZDEbMBkGA1UEAxMSUXVvVmFkaXMg\nUm9vdCBDQSAzggIFxjANBgkqhkiG9w0BAQUFAAOCAgEAT62gLEz6wPJv92ZVqyM0\n7ucp2sNbtrCD2dDQ4iH782CnO11gUyeim/YIIirnv6By5ZwkajGxkHon24QRiSem\nd1o417+shvzuXYO8BsbRd2sPbSQvS3pspweWyuOEn62Iix2rFo1bZhfZFvSLgNLd\n+LJ2w/w4E6oM3kJpK27zPOuAJ9v1pkQNn1pVWQvVDVJIxa6f8i+AxeoyUDUSly7B\n4f/xI4hROJ/yZlZ25w9Rl6VSDE1JUZU2Pb+iSwwQHYaZTKrzchGT5Or2m9qoXadN\nt54CrnMAyNojA+j56hl0YgCUyyIgvpSnWbWCar6ZeXqp8kokUvd0/bpO5qgdAm6x\nDYBEwa7TIzdfu4V8K5Iu6H6li92Z4b8nby1dqnuH/grdS/yO9SbkbnBCbjPsMZ57\nk8HkyWkaPcBrTiJt7qtYTcbQQcEr6k8Sh17rRdhs9ZgC06DYVYoGmRmioHfRMJ6s\nzHXug/WwYjnPbFfiTNKRCw51KBuav/0aQ/HKd/s7j2G4aSgWQgRecCocIdiP4b0j\nWy10QJLZYxkNc91pvGJHvOB0K7Lrfb5BG7XARsWhIstfTsEokt4YutUqKLsRixeT\nmJlglFwjz1onl14LBQaTNx47aTbrqZ5hHY8y2o4M1nQ+ewkk2gF3R8Q7zTSMmfXK\n4SVhM7JZG+Ju1zdXtg2pEto=\n-----END CERTIFICATE-----\n\n# Issuer: O=SECOM Trust.net OU=Security Communication RootCA1\n# Subject: O=SECOM Trust.net OU=Security Communication RootCA1\n# Label: \"Security Communication Root CA\"\n# Serial: 0\n# MD5 Fingerprint: f1:bc:63:6a:54:e0:b5:27:f5:cd:e7:1a:e3:4d:6e:4a\n# SHA1 Fingerprint: 36:b1:2b:49:f9:81:9e:d7:4c:9e:bc:38:0f:c6:56:8f:5d:ac:b2:f7\n# SHA256 Fingerprint: e7:5e:72:ed:9f:56:0e:ec:6e:b4:80:00:73:a4:3f:c3:ad:19:19:5a:39:22:82:01:78:95:97:4a:99:02:6b:6c\n-----BEGIN CERTIFICATE-----\nMIIDWjCCAkKgAwIBAgIBADANBgkqhkiG9w0BAQUFADBQMQswCQYDVQQGEwJKUDEY\nMBYGA1UEChMPU0VDT00gVHJ1c3QubmV0MScwJQYDVQQLEx5TZWN1cml0eSBDb21t\ndW5pY2F0aW9uIFJvb3RDQTEwHhcNMDMwOTMwMDQyMDQ5WhcNMjMwOTMwMDQyMDQ5\nWjBQMQswCQYDVQQGEwJKUDEYMBYGA1UEChMPU0VDT00gVHJ1c3QubmV0MScwJQYD\nVQQLEx5TZWN1cml0eSBDb21tdW5pY2F0aW9uIFJvb3RDQTEwggEiMA0GCSqGSIb3\nDQEBAQUAA4IBDwAwggEKAoIBAQCzs/5/022x7xZ8V6UMbXaKL0u/ZPtM7orw8yl8\n9f/uKuDp6bpbZCKamm8sOiZpUQWZJtzVHGpxxpp9Hp3dfGzGjGdnSj74cbAZJ6kJ\nDKaVv0uMDPpVmDvY6CKhS3E4eayXkmmziX7qIWgGmBSWh9JhNrxtJ1aeV+7AwFb9\nMs+k2Y7CI9eNqPPYJayX5HA49LY6tJ07lyZDo6G8SVlyTCMwhwFY9k6+HGhWZq/N\nQV3Is00qVUarH9oe4kA92819uZKAnDfdDJZkndwi92SL32HeFZRSFaB9UslLqCHJ\nxrHty8OVYNEP8Ktw+N/LTX7s1vqr2b1/VPKl6Xn62dZ2JChzAgMBAAGjPzA9MB0G\nA1UdDgQWBBSgc0mZaNyFW2XjmygvV5+9M7wHSDALBgNVHQ8EBAMCAQYwDwYDVR0T\nAQH/BAUwAwEB/zANBgkqhkiG9w0BAQUFAAOCAQEAaECpqLvkT115swW1F7NgE+vG\nkl3g0dNq/vu+m22/xwVtWSDEHPC32oRYAmP6SBbvT6UL90qY8j+eG61Ha2POCEfr\nUj94nK9NrvjVT8+amCoQQTlSxN3Zmw7vkwGusi7KaEIkQmywszo+zenaSMQVy+n5\nBw+SUEmK3TGXX8npN6o7WWWXlDLJs58+OmJYxUmtYg5xpTKqL8aJdkNAExNnPaJU\nJRDL8Try2frbSVa7pv6nQTXD4IhhyYjH3zYQIphZ6rBK+1YWc26sTfcioU+tHXot\nRSflMMFe8toTyyVCUZVHA4xsIcx0Qu1T/zOLjw9XARYvz6buyXAiFL39vmwLAw==\n-----END CERTIFICATE-----\n\n# Issuer: CN=Sonera Class2 CA O=Sonera\n# Subject: CN=Sonera Class2 CA O=Sonera\n# Label: \"Sonera Class 2 Root CA\"\n# Serial: 29\n# MD5 Fingerprint: a3:ec:75:0f:2e:88:df:fa:48:01:4e:0b:5c:48:6f:fb\n# SHA1 Fingerprint: 37:f7:6d:e6:07:7c:90:c5:b1:3e:93:1a:b7:41:10:b4:f2:e4:9a:27\n# SHA256 Fingerprint: 79:08:b4:03:14:c1:38:10:0b:51:8d:07:35:80:7f:fb:fc:f8:51:8a:00:95:33:71:05:ba:38:6b:15:3d:d9:27\n-----BEGIN CERTIFICATE-----\nMIIDIDCCAgigAwIBAgIBHTANBgkqhkiG9w0BAQUFADA5MQswCQYDVQQGEwJGSTEP\nMA0GA1UEChMGU29uZXJhMRkwFwYDVQQDExBTb25lcmEgQ2xhc3MyIENBMB4XDTAx\nMDQwNjA3Mjk0MFoXDTIxMDQwNjA3Mjk0MFowOTELMAkGA1UEBhMCRkkxDzANBgNV\nBAoTBlNvbmVyYTEZMBcGA1UEAxMQU29uZXJhIENsYXNzMiBDQTCCASIwDQYJKoZI\nhvcNAQEBBQADggEPADCCAQoCggEBAJAXSjWdyvANlsdE+hY3/Ei9vX+ALTU74W+o\nZ6m/AxxNjG8yR9VBaKQTBME1DJqEQ/xcHf+Js+gXGM2RX/uJ4+q/Tl18GybTdXnt\n5oTjV+WtKcT0OijnpXuENmmz/V52vaMtmdOQTiMofRhj8VQ7Jp12W5dCsv+u8E7s\n3TmVToMGf+dJQMjFAbJUWmYdPfz56TwKnoG4cPABi+QjVHzIrviQHgCWctRUz2Ej\nvOr7nQKV0ba5cTppCD8PtOFCx4j1P5iop7oc4HFx71hXgVB6XGt0Rg6DA5jDjqhu\n8nYybieDwnPz3BjotJPqdURrBGAgcVeHnfO+oJAjPYok4doh28MCAwEAAaMzMDEw\nDwYDVR0TAQH/BAUwAwEB/zARBgNVHQ4ECgQISqCqWITTXjwwCwYDVR0PBAQDAgEG\nMA0GCSqGSIb3DQEBBQUAA4IBAQBazof5FnIVV0sd2ZvnoiYw7JNn39Yt0jSv9zil\nzqsWuasvfDXLrNAPtEwr/IDva4yRXzZ299uzGxnq9LIR/WFxRL8oszodv7ND6J+/\n3DEIcbCdjdY0RzKQxmUk96BKfARzjzlvF4xytb1LyHr4e4PDKE6cCepnP7JnBBvD\nFNr450kkkdAdavphOe9r5yF1BgfYErQhIHBCcYHaPJo2vqZbDWpsmh+Re/n570K6\nTk6ezAyNlNzZRZxe7EJQY670XcSxEtzKO6gunRRaBXW37Ndj4ro1tgQIkejanZz2\nZrUYrAqmVCY0M9IbwdR/GjqOC6oybtv8TyWf2TLHllpwrN9M\n-----END CERTIFICATE-----\n\n# Issuer: CN=XRamp Global Certification Authority O=XRamp Security Services Inc OU=www.xrampsecurity.com\n# Subject: CN=XRamp Global Certification Authority O=XRamp Security Services Inc OU=www.xrampsecurity.com\n# Label: \"XRamp Global CA Root\"\n# Serial: 107108908803651509692980124233745014957\n# MD5 Fingerprint: a1:0b:44:b3:ca:10:d8:00:6e:9d:0f:d8:0f:92:0a:d1\n# SHA1 Fingerprint: b8:01:86:d1:eb:9c:86:a5:41:04:cf:30:54:f3:4c:52:b7:e5:58:c6\n# SHA256 Fingerprint: ce:cd:dc:90:50:99:d8:da:df:c5:b1:d2:09:b7:37:cb:e2:c1:8c:fb:2c:10:c0:ff:0b:cf:0d:32:86:fc:1a:a2\n-----BEGIN CERTIFICATE-----\nMIIEMDCCAxigAwIBAgIQUJRs7Bjq1ZxN1ZfvdY+grTANBgkqhkiG9w0BAQUFADCB\ngjELMAkGA1UEBhMCVVMxHjAcBgNVBAsTFXd3dy54cmFtcHNlY3VyaXR5LmNvbTEk\nMCIGA1UEChMbWFJhbXAgU2VjdXJpdHkgU2VydmljZXMgSW5jMS0wKwYDVQQDEyRY\nUmFtcCBHbG9iYWwgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkwHhcNMDQxMTAxMTcx\nNDA0WhcNMzUwMTAxMDUzNzE5WjCBgjELMAkGA1UEBhMCVVMxHjAcBgNVBAsTFXd3\ndy54cmFtcHNlY3VyaXR5LmNvbTEkMCIGA1UEChMbWFJhbXAgU2VjdXJpdHkgU2Vy\ndmljZXMgSW5jMS0wKwYDVQQDEyRYUmFtcCBHbG9iYWwgQ2VydGlmaWNhdGlvbiBB\ndXRob3JpdHkwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCYJB69FbS6\n38eMpSe2OAtp87ZOqCwuIR1cRN8hXX4jdP5efrRKt6atH67gBhbim1vZZ3RrXYCP\nKZ2GG9mcDZhtdhAoWORlsH9KmHmf4MMxfoArtYzAQDsRhtDLooY2YKTVMIJt2W7Q\nDxIEM5dfT2Fa8OT5kavnHTu86M/0ay00fOJIYRyO82FEzG+gSqmUsE3a56k0enI4\nqEHMPJQRfevIpoy3hsvKMzvZPTeL+3o+hiznc9cKV6xkmxnr9A8ECIqsAxcZZPRa\nJSKNNCyy9mgdEm3Tih4U2sSPpuIjhdV6Db1q4Ons7Be7QhtnqiXtRYMh/MHJfNVi\nPvryxS3T/dRlAgMBAAGjgZ8wgZwwEwYJKwYBBAGCNxQCBAYeBABDAEEwCwYDVR0P\nBAQDAgGGMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFMZPoj0GY4QJnM5i5ASs\njVy16bYbMDYGA1UdHwQvMC0wK6ApoCeGJWh0dHA6Ly9jcmwueHJhbXBzZWN1cml0\neS5jb20vWEdDQS5jcmwwEAYJKwYBBAGCNxUBBAMCAQEwDQYJKoZIhvcNAQEFBQAD\nggEBAJEVOQMBG2f7Shz5CmBbodpNl2L5JFMn14JkTpAuw0kbK5rc/Kh4ZzXxHfAR\nvbdI4xD2Dd8/0sm2qlWkSLoC295ZLhVbO50WfUfXN+pfTXYSNrsf16GBBEYgoyxt\nqZ4Bfj8pzgCT3/3JknOJiWSe5yvkHJEs0rnOfc5vMZnT5r7SHpDwCRR5XCOrTdLa\nIR9NmXmd4c8nnxCbHIgNsIpkQTG4DmyQJKSbXHGPurt+HBvbaoAPIbzp26a3QPSy\ni6mx5O+aGtA9aZnuqCij4Tyz8LIRnM98QObd50N9otg6tamN8jSZxNQQ4Qb9CYQQ\nO+7ETPTsJ3xCwnR8gooJybQDJbw=\n-----END CERTIFICATE-----\n\n# Issuer: O=The Go Daddy Group, Inc. OU=Go Daddy Class 2 Certification Authority\n# Subject: O=The Go Daddy Group, Inc. OU=Go Daddy Class 2 Certification Authority\n# Label: \"Go Daddy Class 2 CA\"\n# Serial: 0\n# MD5 Fingerprint: 91:de:06:25:ab:da:fd:32:17:0c:bb:25:17:2a:84:67\n# SHA1 Fingerprint: 27:96:ba:e6:3f:18:01:e2:77:26:1b:a0:d7:77:70:02:8f:20:ee:e4\n# SHA256 Fingerprint: c3:84:6b:f2:4b:9e:93:ca:64:27:4c:0e:c6:7c:1e:cc:5e:02:4f:fc:ac:d2:d7:40:19:35:0e:81:fe:54:6a:e4\n-----BEGIN CERTIFICATE-----\nMIIEADCCAuigAwIBAgIBADANBgkqhkiG9w0BAQUFADBjMQswCQYDVQQGEwJVUzEh\nMB8GA1UEChMYVGhlIEdvIERhZGR5IEdyb3VwLCBJbmMuMTEwLwYDVQQLEyhHbyBE\nYWRkeSBDbGFzcyAyIENlcnRpZmljYXRpb24gQXV0aG9yaXR5MB4XDTA0MDYyOTE3\nMDYyMFoXDTM0MDYyOTE3MDYyMFowYzELMAkGA1UEBhMCVVMxITAfBgNVBAoTGFRo\nZSBHbyBEYWRkeSBHcm91cCwgSW5jLjExMC8GA1UECxMoR28gRGFkZHkgQ2xhc3Mg\nMiBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0eTCCASAwDQYJKoZIhvcNAQEBBQADggEN\nADCCAQgCggEBAN6d1+pXGEmhW+vXX0iG6r7d/+TvZxz0ZWizV3GgXne77ZtJ6XCA\nPVYYYwhv2vLM0D9/AlQiVBDYsoHUwHU9S3/Hd8M+eKsaA7Ugay9qK7HFiH7Eux6w\nwdhFJ2+qN1j3hybX2C32qRe3H3I2TqYXP2WYktsqbl2i/ojgC95/5Y0V4evLOtXi\nEqITLdiOr18SPaAIBQi2XKVlOARFmR6jYGB0xUGlcmIbYsUfb18aQr4CUWWoriMY\navx4A6lNf4DD+qta/KFApMoZFv6yyO9ecw3ud72a9nmYvLEHZ6IVDd2gWMZEewo+\nYihfukEHU1jPEX44dMX4/7VpkI+EdOqXG68CAQOjgcAwgb0wHQYDVR0OBBYEFNLE\nsNKR1EwRcbNhyz2h/t2oatTjMIGNBgNVHSMEgYUwgYKAFNLEsNKR1EwRcbNhyz2h\n/t2oatTjoWekZTBjMQswCQYDVQQGEwJVUzEhMB8GA1UEChMYVGhlIEdvIERhZGR5\nIEdyb3VwLCBJbmMuMTEwLwYDVQQLEyhHbyBEYWRkeSBDbGFzcyAyIENlcnRpZmlj\nYXRpb24gQXV0aG9yaXR5ggEAMAwGA1UdEwQFMAMBAf8wDQYJKoZIhvcNAQEFBQAD\nggEBADJL87LKPpH8EsahB4yOd6AzBhRckB4Y9wimPQoZ+YeAEW5p5JYXMP80kWNy\nOO7MHAGjHZQopDH2esRU1/blMVgDoszOYtuURXO1v0XJJLXVggKtI3lpjbi2Tc7P\nTMozI+gciKqdi0FuFskg5YmezTvacPd+mSYgFFQlq25zheabIZ0KbIIOqPjCDPoQ\nHmyW74cNxA9hi63ugyuV+I6ShHI56yDqg+2DzZduCLzrTia2cyvk0/ZM/iZx4mER\ndEr/VxqHD3VILs9RaRegAhJhldXRQLIQTO7ErBBDpqWeCtWVYpoNz4iCxTIM5Cuf\nReYNnyicsbkqWletNw+vHX/bvZ8=\n-----END CERTIFICATE-----\n\n# Issuer: O=Starfield Technologies, Inc. OU=Starfield Class 2 Certification Authority\n# Subject: O=Starfield Technologies, Inc. OU=Starfield Class 2 Certification Authority\n# Label: \"Starfield Class 2 CA\"\n# Serial: 0\n# MD5 Fingerprint: 32:4a:4b:bb:c8:63:69:9b:be:74:9a:c6:dd:1d:46:24\n# SHA1 Fingerprint: ad:7e:1c:28:b0:64:ef:8f:60:03:40:20:14:c3:d0:e3:37:0e:b5:8a\n# SHA256 Fingerprint: 14:65:fa:20:53:97:b8:76:fa:a6:f0:a9:95:8e:55:90:e4:0f:cc:7f:aa:4f:b7:c2:c8:67:75:21:fb:5f:b6:58\n-----BEGIN CERTIFICATE-----\nMIIEDzCCAvegAwIBAgIBADANBgkqhkiG9w0BAQUFADBoMQswCQYDVQQGEwJVUzEl\nMCMGA1UEChMcU3RhcmZpZWxkIFRlY2hub2xvZ2llcywgSW5jLjEyMDAGA1UECxMp\nU3RhcmZpZWxkIENsYXNzIDIgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkwHhcNMDQw\nNjI5MTczOTE2WhcNMzQwNjI5MTczOTE2WjBoMQswCQYDVQQGEwJVUzElMCMGA1UE\nChMcU3RhcmZpZWxkIFRlY2hub2xvZ2llcywgSW5jLjEyMDAGA1UECxMpU3RhcmZp\nZWxkIENsYXNzIDIgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkwggEgMA0GCSqGSIb3\nDQEBAQUAA4IBDQAwggEIAoIBAQC3Msj+6XGmBIWtDBFk385N78gDGIc/oav7PKaf\n8MOh2tTYbitTkPskpD6E8J7oX+zlJ0T1KKY/e97gKvDIr1MvnsoFAZMej2YcOadN\n+lq2cwQlZut3f+dZxkqZJRRU6ybH838Z1TBwj6+wRir/resp7defqgSHo9T5iaU0\nX9tDkYI22WY8sbi5gv2cOj4QyDvvBmVmepsZGD3/cVE8MC5fvj13c7JdBmzDI1aa\nK4UmkhynArPkPw2vCHmCuDY96pzTNbO8acr1zJ3o/WSNF4Azbl5KXZnJHoe0nRrA\n1W4TNSNe35tfPe/W93bC6j67eA0cQmdrBNj41tpvi/JEoAGrAgEDo4HFMIHCMB0G\nA1UdDgQWBBS/X7fRzt0fhvRbVazc1xDCDqmI5zCBkgYDVR0jBIGKMIGHgBS/X7fR\nzt0fhvRbVazc1xDCDqmI56FspGowaDELMAkGA1UEBhMCVVMxJTAjBgNVBAoTHFN0\nYXJmaWVsZCBUZWNobm9sb2dpZXMsIEluYy4xMjAwBgNVBAsTKVN0YXJmaWVsZCBD\nbGFzcyAyIENlcnRpZmljYXRpb24gQXV0aG9yaXR5ggEAMAwGA1UdEwQFMAMBAf8w\nDQYJKoZIhvcNAQEFBQADggEBAAWdP4id0ckaVaGsafPzWdqbAYcaT1epoXkJKtv3\nL7IezMdeatiDh6GX70k1PncGQVhiv45YuApnP+yz3SFmH8lU+nLMPUxA2IGvd56D\neruix/U0F47ZEUD0/CwqTRV/p2JdLiXTAAsgGh1o+Re49L2L7ShZ3U0WixeDyLJl\nxy16paq8U4Zt3VekyvggQQto8PT7dL5WXXp59fkdheMtlb71cZBDzI0fmgAKhynp\nVSJYACPq4xJDKVtHCN2MQWplBqjlIapBtJUhlbl90TSrE9atvNziPTnNvT51cKEY\nWQPJIrSPnNVeKtelttQKbfi3QBFGmh95DmK/D5fs4C8fF5Q=\n-----END CERTIFICATE-----\n\n# Issuer: O=Government Root Certification Authority\n# Subject: O=Government Root Certification Authority\n# Label: \"Taiwan GRCA\"\n# Serial: 42023070807708724159991140556527066870\n# MD5 Fingerprint: 37:85:44:53:32:45:1f:20:f0:f3:95:e1:25:c4:43:4e\n# SHA1 Fingerprint: f4:8b:11:bf:de:ab:be:94:54:20:71:e6:41:de:6b:be:88:2b:40:b9\n# SHA256 Fingerprint: 76:00:29:5e:ef:e8:5b:9e:1f:d6:24:db:76:06:2a:aa:ae:59:81:8a:54:d2:77:4c:d4:c0:b2:c0:11:31:e1:b3\n-----BEGIN CERTIFICATE-----\nMIIFcjCCA1qgAwIBAgIQH51ZWtcvwgZEpYAIaeNe9jANBgkqhkiG9w0BAQUFADA/\nMQswCQYDVQQGEwJUVzEwMC4GA1UECgwnR292ZXJubWVudCBSb290IENlcnRpZmlj\nYXRpb24gQXV0aG9yaXR5MB4XDTAyMTIwNTEzMjMzM1oXDTMyMTIwNTEzMjMzM1ow\nPzELMAkGA1UEBhMCVFcxMDAuBgNVBAoMJ0dvdmVybm1lbnQgUm9vdCBDZXJ0aWZp\nY2F0aW9uIEF1dGhvcml0eTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIB\nAJoluOzMonWoe/fOW1mKydGGEghU7Jzy50b2iPN86aXfTEc2pBsBHH8eV4qNw8XR\nIePaJD9IK/ufLqGU5ywck9G/GwGHU5nOp/UKIXZ3/6m3xnOUT0b3EEk3+qhZSV1q\ngQdW8or5BtD3cCJNtLdBuTK4sfCxw5w/cP1T3YGq2GN49thTbqGsaoQkclSGxtKy\nyhwOeYHWtXBiCAEuTk8O1RGvqa/lmr/czIdtJuTJV6L7lvnM4T9TjGxMfptTCAts\nF/tnyMKtsc2AtJfcdgEWFelq16TheEfOhtX7MfP6Mb40qij7cEwdScevLJ1tZqa2\njWR+tSBqnTuBto9AAGdLiYa4zGX+FVPpBMHWXx1E1wovJ5pGfaENda1UhhXcSTvx\nls4Pm6Dso3pdvtUqdULle96ltqqvKKyskKw4t9VoNSZ63Pc78/1Fm9G7Q3hub/FC\nVGqY8A2tl+lSXunVanLeavcbYBT0peS2cWeqH+riTcFCQP5nRhc4L0c/cZyu5SHK\nYS1tB6iEfC3uUSXxY5Ce/eFXiGvviiNtsea9P63RPZYLhY3Naye7twWb7LuRqQoH\nEgKXTiCQ8P8NHuJBO9NAOueNXdpm5AKwB1KYXA6OM5zCppX7VRluTI6uSw+9wThN\nXo+EHWbNxWCWtFJaBYmOlXqYwZE8lSOyDvR5tMl8wUohAgMBAAGjajBoMB0GA1Ud\nDgQWBBTMzO/MKWCkO7GStjz6MmKPrCUVOzAMBgNVHRMEBTADAQH/MDkGBGcqBwAE\nMTAvMC0CAQAwCQYFKw4DAhoFADAHBgVnKgMAAAQUA5vwIhP/lSg209yewDL7MTqK\nUWUwDQYJKoZIhvcNAQEFBQADggIBAECASvomyc5eMN1PhnR2WPWus4MzeKR6dBcZ\nTulStbngCnRiqmjKeKBMmo4sIy7VahIkv9Ro04rQ2JyftB8M3jh+Vzj8jeJPXgyf\nqzvS/3WXy6TjZwj/5cAWtUgBfen5Cv8b5Wppv3ghqMKnI6mGq3ZW6A4M9hPdKmaK\nZEk9GhiHkASfQlK3T8v+R0F2Ne//AHY2RTKbxkaFXeIksB7jSJaYV0eUVXoPQbFE\nJPPB/hprv4j9wabak2BegUqZIJxIZhm1AHlUD7gsL0u8qV1bYH+Mh6XgUmMqvtg7\nhUAV/h62ZT/FS9p+tXo1KaMuephgIqP0fSdOLeq0dDzpD6QzDxARvBMB1uUO07+1\nEqLhRSPAzAhuYbeJq4PjJB7mXQfnHyA+z2fI56wwbSdLaG5LKlwCCDTb+HbkZ6Mm\nnD+iMsJKxYEYMRBWqoTvLQr/uB930r+lWKBi5NdLkXWNiYCYfm3LU05er/ayl4WX\nudpVBrkk7tfGOB5jGxI7leFYrPLfhNVfmS8NVVvmONsuP3LpSIXLuykTjx44Vbnz\nssQwmSNOXfJIoRIM3BKQCZBUkQM8R+XVyWXgt0t97EfTsws+rZ7QdAAO671RrcDe\nLMDDav7v3Aun+kbfYNucpllQdSNpc5Oy+fwC00fmcc4QAu4njIT/rEUNE1yDMuAl\npYYsfPQS\n-----END CERTIFICATE-----\n\n# Issuer: CN=DigiCert Assured ID Root CA O=DigiCert Inc OU=www.digicert.com\n# Subject: CN=DigiCert Assured ID Root CA O=DigiCert Inc OU=www.digicert.com\n# Label: \"DigiCert Assured ID Root CA\"\n# Serial: 17154717934120587862167794914071425081\n# MD5 Fingerprint: 87:ce:0b:7b:2a:0e:49:00:e1:58:71:9b:37:a8:93:72\n# SHA1 Fingerprint: 05:63:b8:63:0d:62:d7:5a:bb:c8:ab:1e:4b:df:b5:a8:99:b2:4d:43\n# SHA256 Fingerprint: 3e:90:99:b5:01:5e:8f:48:6c:00:bc:ea:9d:11:1e:e7:21:fa:ba:35:5a:89:bc:f1:df:69:56:1e:3d:c6:32:5c\n-----BEGIN CERTIFICATE-----\nMIIDtzCCAp+gAwIBAgIQDOfg5RfYRv6P5WD8G/AwOTANBgkqhkiG9w0BAQUFADBl\nMQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3\nd3cuZGlnaWNlcnQuY29tMSQwIgYDVQQDExtEaWdpQ2VydCBBc3N1cmVkIElEIFJv\nb3QgQ0EwHhcNMDYxMTEwMDAwMDAwWhcNMzExMTEwMDAwMDAwWjBlMQswCQYDVQQG\nEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3d3cuZGlnaWNl\ncnQuY29tMSQwIgYDVQQDExtEaWdpQ2VydCBBc3N1cmVkIElEIFJvb3QgQ0EwggEi\nMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCtDhXO5EOAXLGH87dg+XESpa7c\nJpSIqvTO9SA5KFhgDPiA2qkVlTJhPLWxKISKityfCgyDF3qPkKyK53lTXDGEKvYP\nmDI2dsze3Tyoou9q+yHyUmHfnyDXH+Kx2f4YZNISW1/5WBg1vEfNoTb5a3/UsDg+\nwRvDjDPZ2C8Y/igPs6eD1sNuRMBhNZYW/lmci3Zt1/GiSw0r/wty2p5g0I6QNcZ4\nVYcgoc/lbQrISXwxmDNsIumH0DJaoroTghHtORedmTpyoeb6pNnVFzF1roV9Iq4/\nAUaG9ih5yLHa5FcXxH4cDrC0kqZWs72yl+2qp/C3xag/lRbQ/6GW6whfGHdPAgMB\nAAGjYzBhMA4GA1UdDwEB/wQEAwIBhjAPBgNVHRMBAf8EBTADAQH/MB0GA1UdDgQW\nBBRF66Kv9JLLgjEtUYunpyGd823IDzAfBgNVHSMEGDAWgBRF66Kv9JLLgjEtUYun\npyGd823IDzANBgkqhkiG9w0BAQUFAAOCAQEAog683+Lt8ONyc3pklL/3cmbYMuRC\ndWKuh+vy1dneVrOfzM4UKLkNl2BcEkxY5NM9g0lFWJc1aRqoR+pWxnmrEthngYTf\nfwk8lOa4JiwgvT2zKIn3X/8i4peEH+ll74fg38FnSbNd67IJKusm7Xi+fT8r87cm\nNW1fiQG2SVufAQWbqz0lwcy2f8Lxb4bG+mRo64EtlOtCt/qMHt1i8b5QZ7dsvfPx\nH2sMNgcWfzd8qVttevESRmCD1ycEvkvOl77DZypoEd+A5wwzZr8TDRRu838fYxAe\n+o0bJW1sj6W3YQGx0qMmoRBxna3iw/nDmVG3KwcIzi7mULKn+gpFL6Lw8g==\n-----END CERTIFICATE-----\n\n# Issuer: CN=DigiCert Global Root CA O=DigiCert Inc OU=www.digicert.com\n# Subject: CN=DigiCert Global Root CA O=DigiCert Inc OU=www.digicert.com\n# Label: \"DigiCert Global Root CA\"\n# Serial: 10944719598952040374951832963794454346\n# MD5 Fingerprint: 79:e4:a9:84:0d:7d:3a:96:d7:c0:4f:e2:43:4c:89:2e\n# SHA1 Fingerprint: a8:98:5d:3a:65:e5:e5:c4:b2:d7:d6:6d:40:c6:dd:2f:b1:9c:54:36\n# SHA256 Fingerprint: 43:48:a0:e9:44:4c:78:cb:26:5e:05:8d:5e:89:44:b4:d8:4f:96:62:bd:26:db:25:7f:89:34:a4:43:c7:01:61\n-----BEGIN CERTIFICATE-----\nMIIDrzCCApegAwIBAgIQCDvgVpBCRrGhdWrJWZHHSjANBgkqhkiG9w0BAQUFADBh\nMQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3\nd3cuZGlnaWNlcnQuY29tMSAwHgYDVQQDExdEaWdpQ2VydCBHbG9iYWwgUm9vdCBD\nQTAeFw0wNjExMTAwMDAwMDBaFw0zMTExMTAwMDAwMDBaMGExCzAJBgNVBAYTAlVT\nMRUwEwYDVQQKEwxEaWdpQ2VydCBJbmMxGTAXBgNVBAsTEHd3dy5kaWdpY2VydC5j\nb20xIDAeBgNVBAMTF0RpZ2lDZXJ0IEdsb2JhbCBSb290IENBMIIBIjANBgkqhkiG\n9w0BAQEFAAOCAQ8AMIIBCgKCAQEA4jvhEXLeqKTTo1eqUKKPC3eQyaKl7hLOllsB\nCSDMAZOnTjC3U/dDxGkAV53ijSLdhwZAAIEJzs4bg7/fzTtxRuLWZscFs3YnFo97\nnh6Vfe63SKMI2tavegw5BmV/Sl0fvBf4q77uKNd0f3p4mVmFaG5cIzJLv07A6Fpt\n43C/dxC//AH2hdmoRBBYMql1GNXRor5H4idq9Joz+EkIYIvUX7Q6hL+hqkpMfT7P\nT19sdl6gSzeRntwi5m3OFBqOasv+zbMUZBfHWymeMr/y7vrTC0LUq7dBMtoM1O/4\ngdW7jVg/tRvoSSiicNoxBN33shbyTApOB6jtSj1etX+jkMOvJwIDAQABo2MwYTAO\nBgNVHQ8BAf8EBAMCAYYwDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQUA95QNVbR\nTLtm8KPiGxvDl7I90VUwHwYDVR0jBBgwFoAUA95QNVbRTLtm8KPiGxvDl7I90VUw\nDQYJKoZIhvcNAQEFBQADggEBAMucN6pIExIK+t1EnE9SsPTfrgT1eXkIoyQY/Esr\nhMAtudXH/vTBH1jLuG2cenTnmCmrEbXjcKChzUyImZOMkXDiqw8cvpOp/2PV5Adg\n06O/nVsJ8dWO41P0jmP6P6fbtGbfYmbW0W5BjfIttep3Sp+dWOIrWcBAI+0tKIJF\nPnlUkiaY4IBIqDfv8NZ5YBberOgOzW6sRBc4L0na4UU+Krk2U886UAb3LujEV0ls\nYSEY1QSteDwsOoBrp+uvFRTp2InBuThs4pFsiv9kuXclVzDAGySj4dzp30d8tbQk\nCAUw7C29C79Fv1C5qfPrmAESrciIxpg0X40KPMbp1ZWVbd4=\n-----END CERTIFICATE-----\n\n# Issuer: CN=DigiCert High Assurance EV Root CA O=DigiCert Inc OU=www.digicert.com\n# Subject: CN=DigiCert High Assurance EV Root CA O=DigiCert Inc OU=www.digicert.com\n# Label: \"DigiCert High Assurance EV Root CA\"\n# Serial: 3553400076410547919724730734378100087\n# MD5 Fingerprint: d4:74:de:57:5c:39:b2:d3:9c:85:83:c5:c0:65:49:8a\n# SHA1 Fingerprint: 5f:b7:ee:06:33:e2:59:db:ad:0c:4c:9a:e6:d3:8f:1a:61:c7:dc:25\n# SHA256 Fingerprint: 74:31:e5:f4:c3:c1:ce:46:90:77:4f:0b:61:e0:54:40:88:3b:a9:a0:1e:d0:0b:a6:ab:d7:80:6e:d3:b1:18:cf\n-----BEGIN CERTIFICATE-----\nMIIDxTCCAq2gAwIBAgIQAqxcJmoLQJuPC3nyrkYldzANBgkqhkiG9w0BAQUFADBs\nMQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3\nd3cuZGlnaWNlcnQuY29tMSswKQYDVQQDEyJEaWdpQ2VydCBIaWdoIEFzc3VyYW5j\nZSBFViBSb290IENBMB4XDTA2MTExMDAwMDAwMFoXDTMxMTExMDAwMDAwMFowbDEL\nMAkGA1UEBhMCVVMxFTATBgNVBAoTDERpZ2lDZXJ0IEluYzEZMBcGA1UECxMQd3d3\nLmRpZ2ljZXJ0LmNvbTErMCkGA1UEAxMiRGlnaUNlcnQgSGlnaCBBc3N1cmFuY2Ug\nRVYgUm9vdCBDQTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMbM5XPm\n+9S75S0tMqbf5YE/yc0lSbZxKsPVlDRnogocsF9ppkCxxLeyj9CYpKlBWTrT3JTW\nPNt0OKRKzE0lgvdKpVMSOO7zSW1xkX5jtqumX8OkhPhPYlG++MXs2ziS4wblCJEM\nxChBVfvLWokVfnHoNb9Ncgk9vjo4UFt3MRuNs8ckRZqnrG0AFFoEt7oT61EKmEFB\nIk5lYYeBQVCmeVyJ3hlKV9Uu5l0cUyx+mM0aBhakaHPQNAQTXKFx01p8VdteZOE3\nhzBWBOURtCmAEvF5OYiiAhF8J2a3iLd48soKqDirCmTCv2ZdlYTBoSUeh10aUAsg\nEsxBu24LUTi4S8sCAwEAAaNjMGEwDgYDVR0PAQH/BAQDAgGGMA8GA1UdEwEB/wQF\nMAMBAf8wHQYDVR0OBBYEFLE+w2kD+L9HAdSYJhoIAu9jZCvDMB8GA1UdIwQYMBaA\nFLE+w2kD+L9HAdSYJhoIAu9jZCvDMA0GCSqGSIb3DQEBBQUAA4IBAQAcGgaX3Nec\nnzyIZgYIVyHbIUf4KmeqvxgydkAQV8GK83rZEWWONfqe/EW1ntlMMUu4kehDLI6z\neM7b41N5cdblIZQB2lWHmiRk9opmzN6cN82oNLFpmyPInngiK3BD41VHMWEZ71jF\nhS9OMPagMRYjyOfiZRYzy78aG6A9+MpeizGLYAiJLQwGXFK3xPkKmNEVX58Svnw2\nYzi9RKR/5CYrCsSXaQ3pjOLAEFe4yHYSkVXySGnYvCoCWw9E1CAx2/S6cCZdkGCe\nvEsXCS+0yx5DaMkHJ8HSXPfqIbloEpw8nL+e/IBcm2PN7EeqJSdnoDfzAIJ9VNep\n+OkuE6N36B9K\n-----END CERTIFICATE-----\n\n# Issuer: CN=Class 2 Primary CA O=Certplus\n# Subject: CN=Class 2 Primary CA O=Certplus\n# Label: \"Certplus Class 2 Primary CA\"\n# Serial: 177770208045934040241468760488327595043\n# MD5 Fingerprint: 88:2c:8c:52:b8:a2:3c:f3:f7:bb:03:ea:ae:ac:42:0b\n# SHA1 Fingerprint: 74:20:74:41:72:9c:dd:92:ec:79:31:d8:23:10:8d:c2:81:92:e2:bb\n# SHA256 Fingerprint: 0f:99:3c:8a:ef:97:ba:af:56:87:14:0e:d5:9a:d1:82:1b:b4:af:ac:f0:aa:9a:58:b5:d5:7a:33:8a:3a:fb:cb\n-----BEGIN CERTIFICATE-----\nMIIDkjCCAnqgAwIBAgIRAIW9S/PY2uNp9pTXX8OlRCMwDQYJKoZIhvcNAQEFBQAw\nPTELMAkGA1UEBhMCRlIxETAPBgNVBAoTCENlcnRwbHVzMRswGQYDVQQDExJDbGFz\ncyAyIFByaW1hcnkgQ0EwHhcNOTkwNzA3MTcwNTAwWhcNMTkwNzA2MjM1OTU5WjA9\nMQswCQYDVQQGEwJGUjERMA8GA1UEChMIQ2VydHBsdXMxGzAZBgNVBAMTEkNsYXNz\nIDIgUHJpbWFyeSBDQTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBANxQ\nltAS+DXSCHh6tlJw/W/uz7kRy1134ezpfgSN1sxvc0NXYKwzCkTsA18cgCSR5aiR\nVhKC9+Ar9NuuYS6JEI1rbLqzAr3VNsVINyPi8Fo3UjMXEuLRYE2+L0ER4/YXJQyL\nkcAbmXuZVg2v7tK8R1fjeUl7NIknJITesezpWE7+Tt9avkGtrAjFGA7v0lPubNCd\nEgETjdyAYveVqUSISnFOYFWe2yMZeVYHDD9jC1yw4r5+FfyUM1hBOHTE4Y+L3yas\nH7WLO7dDWWuwJKZtkIvEcupdM5i3y95ee++U8Rs+yskhwcWYAqqi9lt3m/V+llU0\nHGdpwPFC40es/CgcZlUCAwEAAaOBjDCBiTAPBgNVHRMECDAGAQH/AgEKMAsGA1Ud\nDwQEAwIBBjAdBgNVHQ4EFgQU43Mt38sOKAze3bOkynm4jrvoMIkwEQYJYIZIAYb4\nQgEBBAQDAgEGMDcGA1UdHwQwMC4wLKAqoCiGJmh0dHA6Ly93d3cuY2VydHBsdXMu\nY29tL0NSTC9jbGFzczIuY3JsMA0GCSqGSIb3DQEBBQUAA4IBAQCnVM+IRBnL39R/\nAN9WM2K191EBkOvDP9GIROkkXe/nFL0gt5o8AP5tn9uQ3Nf0YtaLcF3n5QRIqWh8\nyfFC82x/xXp8HVGIutIKPidd3i1RTtMTZGnkLuPT55sJmabglZvOGtd/vjzOUrMR\nFcEPF80Du5wlFbqidon8BvEY0JNLDnyCt6X09l/+7UCmnYR0ObncHoUW2ikbhiMA\nybuJfm6AiB4vFLQDJKgybwOaRywwvlbGp0ICcBvqQNi6BQNwB6SW//1IMwrh3KWB\nkJtN3X3n57LNXMhqlfil9o3EXXgIvnsG1knPGTZQIy4I5p4FTUcY1Rbpsda2ENW7\nl7+ijrRU\n-----END CERTIFICATE-----\n\n# Issuer: CN=DST Root CA X3 O=Digital Signature Trust Co.\n# Subject: CN=DST Root CA X3 O=Digital Signature Trust Co.\n# Label: \"DST Root CA X3\"\n# Serial: 91299735575339953335919266965803778155\n# MD5 Fingerprint: 41:03:52:dc:0f:f7:50:1b:16:f0:02:8e:ba:6f:45:c5\n# SHA1 Fingerprint: da:c9:02:4f:54:d8:f6:df:94:93:5f:b1:73:26:38:ca:6a:d7:7c:13\n# SHA256 Fingerprint: 06:87:26:03:31:a7:24:03:d9:09:f1:05:e6:9b:cf:0d:32:e1:bd:24:93:ff:c6:d9:20:6d:11:bc:d6:77:07:39\n-----BEGIN CERTIFICATE-----\nMIIDSjCCAjKgAwIBAgIQRK+wgNajJ7qJMDmGLvhAazANBgkqhkiG9w0BAQUFADA/\nMSQwIgYDVQQKExtEaWdpdGFsIFNpZ25hdHVyZSBUcnVzdCBDby4xFzAVBgNVBAMT\nDkRTVCBSb290IENBIFgzMB4XDTAwMDkzMDIxMTIxOVoXDTIxMDkzMDE0MDExNVow\nPzEkMCIGA1UEChMbRGlnaXRhbCBTaWduYXR1cmUgVHJ1c3QgQ28uMRcwFQYDVQQD\nEw5EU1QgUm9vdCBDQSBYMzCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEB\nAN+v6ZdQCINXtMxiZfaQguzH0yxrMMpb7NnDfcdAwRgUi+DoM3ZJKuM/IUmTrE4O\nrz5Iy2Xu/NMhD2XSKtkyj4zl93ewEnu1lcCJo6m67XMuegwGMoOifooUMM0RoOEq\nOLl5CjH9UL2AZd+3UWODyOKIYepLYYHsUmu5ouJLGiifSKOeDNoJjj4XLh7dIN9b\nxiqKqy69cK3FCxolkHRyxXtqqzTWMIn/5WgTe1QLyNau7Fqckh49ZLOMxt+/yUFw\n7BZy1SbsOFU5Q9D8/RhcQPGX69Wam40dutolucbY38EVAjqr2m7xPi71XAicPNaD\naeQQmxkqtilX4+U9m5/wAl0CAwEAAaNCMEAwDwYDVR0TAQH/BAUwAwEB/zAOBgNV\nHQ8BAf8EBAMCAQYwHQYDVR0OBBYEFMSnsaR7LHH62+FLkHX/xBVghYkQMA0GCSqG\nSIb3DQEBBQUAA4IBAQCjGiybFwBcqR7uKGY3Or+Dxz9LwwmglSBd49lZRNI+DT69\nikugdB/OEIKcdBodfpga3csTS7MgROSR6cz8faXbauX+5v3gTt23ADq1cEmv8uXr\nAvHRAosZy5Q6XkjEGB5YGV8eAlrwDPGxrancWYaLbumR9YbK+rlmM6pZW87ipxZz\nR8srzJmwN0jP41ZL9c8PDHIyh8bwRLtTcm1D9SZImlJnt1ir/md2cXjbDaJWFBM5\nJDGFoqgCWjBH4d1QB7wCCZAA62RjYJsWvIjJEubSfZGL+T0yjWW06XyxV3bqxbYo\nOb8VZRzI9neWagqNdwvYkQsEjgfbKbYK7p2CNTUQ\n-----END CERTIFICATE-----\n\n# Issuer: CN=SwissSign Gold CA - G2 O=SwissSign AG\n# Subject: CN=SwissSign Gold CA - G2 O=SwissSign AG\n# Label: \"SwissSign Gold CA - G2\"\n# Serial: 13492815561806991280\n# MD5 Fingerprint: 24:77:d9:a8:91:d1:3b:fa:88:2d:c2:ff:f8:cd:33:93\n# SHA1 Fingerprint: d8:c5:38:8a:b7:30:1b:1b:6e:d4:7a:e6:45:25:3a:6f:9f:1a:27:61\n# SHA256 Fingerprint: 62:dd:0b:e9:b9:f5:0a:16:3e:a0:f8:e7:5c:05:3b:1e:ca:57:ea:55:c8:68:8f:64:7c:68:81:f2:c8:35:7b:95\n-----BEGIN CERTIFICATE-----\nMIIFujCCA6KgAwIBAgIJALtAHEP1Xk+wMA0GCSqGSIb3DQEBBQUAMEUxCzAJBgNV\nBAYTAkNIMRUwEwYDVQQKEwxTd2lzc1NpZ24gQUcxHzAdBgNVBAMTFlN3aXNzU2ln\nbiBHb2xkIENBIC0gRzIwHhcNMDYxMDI1MDgzMDM1WhcNMzYxMDI1MDgzMDM1WjBF\nMQswCQYDVQQGEwJDSDEVMBMGA1UEChMMU3dpc3NTaWduIEFHMR8wHQYDVQQDExZT\nd2lzc1NpZ24gR29sZCBDQSAtIEcyMIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIIC\nCgKCAgEAr+TufoskDhJuqVAtFkQ7kpJcyrhdhJJCEyq8ZVeCQD5XJM1QiyUqt2/8\n76LQwB8CJEoTlo8jE+YoWACjR8cGp4QjK7u9lit/VcyLwVcfDmJlD909Vopz2q5+\nbbqBHH5CjCA12UNNhPqE21Is8w4ndwtrvxEvcnifLtg+5hg3Wipy+dpikJKVyh+c\n6bM8K8vzARO/Ws/BtQpgvd21mWRTuKCWs2/iJneRjOBiEAKfNA+k1ZIzUd6+jbqE\nemA8atufK+ze3gE/bk3lUIbLtK/tREDFylqM2tIrfKjuvqblCqoOpd8FUrdVxyJd\nMmqXl2MT28nbeTZ7hTpKxVKJ+STnnXepgv9VHKVxaSvRAiTysybUa9oEVeXBCsdt\nMDeQKuSeFDNeFhdVxVu1yzSJkvGdJo+hB9TGsnhQ2wwMC3wLjEHXuendjIj3o02y\nMszYF9rNt85mndT9Xv+9lz4pded+p2JYryU0pUHHPbwNUMoDAw8IWh+Vc3hiv69y\nFGkOpeUDDniOJihC8AcLYiAQZzlG+qkDzAQ4embvIIO1jEpWjpEA/I5cgt6IoMPi\naG59je883WX0XaxR7ySArqpWl2/5rX3aYT+YdzylkbYcjCbaZaIJbcHiVOO5ykxM\ngI93e2CaHt+28kgeDrpOVG2Y4OGiGqJ3UM/EY5LsRxmd6+ZrzsECAwEAAaOBrDCB\nqTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQUWyV7\nlqRlUX64OfPAeGZe6Drn8O4wHwYDVR0jBBgwFoAUWyV7lqRlUX64OfPAeGZe6Drn\n8O4wRgYDVR0gBD8wPTA7BglghXQBWQECAQEwLjAsBggrBgEFBQcCARYgaHR0cDov\nL3JlcG9zaXRvcnkuc3dpc3NzaWduLmNvbS8wDQYJKoZIhvcNAQEFBQADggIBACe6\n45R88a7A3hfm5djV9VSwg/S7zV4Fe0+fdWavPOhWfvxyeDgD2StiGwC5+OlgzczO\nUYrHUDFu4Up+GC9pWbY9ZIEr44OE5iKHjn3g7gKZYbge9LgriBIWhMIxkziWMaa5\nO1M/wySTVltpkuzFwbs4AOPsF6m43Md8AYOfMke6UiI0HTJ6CVanfCU2qT1L2sCC\nbwq7EsiHSycR+R4tx5M/nttfJmtS2S6K8RTGRI0Vqbe/vd6mGu6uLftIdxf+u+yv\nGPUqUfA5hJeVbG4bwyvEdGB5JbAKJ9/fXtI5z0V9QkvfsywexcZdylU6oJxpmo/a\n77KwPJ+HbBIrZXAVUjEaJM9vMSNQH4xPjyPDdEFjHFWoFN0+4FFQz/EbMFYOkrCC\nhdiDyyJkvC24JdVUorgG6q2SpCSgwYa1ShNqR88uC1aVVMvOmttqtKay20EIhid3\n92qgQmwLOM7XdVAyksLfKzAiSNDVQTglXaTpXZ/GlHXQRf0wl0OPkKsKx4ZzYEpp\nLd6leNcG2mqeSz53OiATIgHQv2ieY2BrNU0LbbqhPcCT4H8js1WtciVORvnSFu+w\nZMEBnunKoGqYDs/YYPIvSbjkQuE4NRb0yG5P94FW6LqjviOvrv1vA+ACOzB2+htt\nQc8Bsem4yWb02ybzOqR08kkkW8mw0FfB+j564ZfJ\n-----END CERTIFICATE-----\n\n# Issuer: CN=SwissSign Silver CA - G2 O=SwissSign AG\n# Subject: CN=SwissSign Silver CA - G2 O=SwissSign AG\n# Label: \"SwissSign Silver CA - G2\"\n# Serial: 5700383053117599563\n# MD5 Fingerprint: e0:06:a1:c9:7d:cf:c9:fc:0d:c0:56:75:96:d8:62:13\n# SHA1 Fingerprint: 9b:aa:e5:9f:56:ee:21:cb:43:5a:be:25:93:df:a7:f0:40:d1:1d:cb\n# SHA256 Fingerprint: be:6c:4d:a2:bb:b9:ba:59:b6:f3:93:97:68:37:42:46:c3:c0:05:99:3f:a9:8f:02:0d:1d:ed:be:d4:8a:81:d5\n-----BEGIN CERTIFICATE-----\nMIIFvTCCA6WgAwIBAgIITxvUL1S7L0swDQYJKoZIhvcNAQEFBQAwRzELMAkGA1UE\nBhMCQ0gxFTATBgNVBAoTDFN3aXNzU2lnbiBBRzEhMB8GA1UEAxMYU3dpc3NTaWdu\nIFNpbHZlciBDQSAtIEcyMB4XDTA2MTAyNTA4MzI0NloXDTM2MTAyNTA4MzI0Nlow\nRzELMAkGA1UEBhMCQ0gxFTATBgNVBAoTDFN3aXNzU2lnbiBBRzEhMB8GA1UEAxMY\nU3dpc3NTaWduIFNpbHZlciBDQSAtIEcyMIICIjANBgkqhkiG9w0BAQEFAAOCAg8A\nMIICCgKCAgEAxPGHf9N4Mfc4yfjDmUO8x/e8N+dOcbpLj6VzHVxumK4DV644N0Mv\nFz0fyM5oEMF4rhkDKxD6LHmD9ui5aLlV8gREpzn5/ASLHvGiTSf5YXu6t+WiE7br\nYT7QbNHm+/pe7R20nqA1W6GSy/BJkv6FCgU+5tkL4k+73JU3/JHpMjUi0R86TieF\nnbAVlDLaYQ1HTWBCrpJH6INaUFjpiou5XaHc3ZlKHzZnu0jkg7Y360g6rw9njxcH\n6ATK72oxh9TAtvmUcXtnZLi2kUpCe2UuMGoM9ZDulebyzYLs2aFK7PayS+VFheZt\neJMELpyCbTapxDFkH4aDCyr0NQp4yVXPQbBH6TCfmb5hqAaEuSh6XzjZG6k4sIN/\nc8HDO0gqgg8hm7jMqDXDhBuDsz6+pJVpATqJAHgE2cn0mRmrVn5bi4Y5FZGkECwJ\nMoBgs5PAKrYYC51+jUnyEEp/+dVGLxmSo5mnJqy7jDzmDrxHB9xzUfFwZC8I+bRH\nHTBsROopN4WSaGa8gzj+ezku01DwH/teYLappvonQfGbGHLy9YR0SslnxFSuSGTf\njNFusB3hB48IHpmccelM2KX3RxIfdNFRnobzwqIjQAtz20um53MGjMGg6cFZrEb6\n5i/4z3GcRm25xBWNOHkDRUjvxF3XCO6HOSKGsg0PWEP3calILv3q1h8CAwEAAaOB\nrDCBqTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQU\nF6DNweRBtjpbO8tFnb0cwpj6hlgwHwYDVR0jBBgwFoAUF6DNweRBtjpbO8tFnb0c\nwpj6hlgwRgYDVR0gBD8wPTA7BglghXQBWQEDAQEwLjAsBggrBgEFBQcCARYgaHR0\ncDovL3JlcG9zaXRvcnkuc3dpc3NzaWduLmNvbS8wDQYJKoZIhvcNAQEFBQADggIB\nAHPGgeAn0i0P4JUw4ppBf1AsX19iYamGamkYDHRJ1l2E6kFSGG9YrVBWIGrGvShp\nWJHckRE1qTodvBqlYJ7YH39FkWnZfrt4csEGDyrOj4VwYaygzQu4OSlWhDJOhrs9\nxCrZ1x9y7v5RoSJBsXECYxqCsGKrXlcSH9/L3XWgwF15kIwb4FDm3jH+mHtwX6WQ\n2K34ArZv02DdQEsixT2tOnqfGhpHkXkzuoLcMmkDlm4fS/Bx/uNncqCxv1yL5PqZ\nIseEuRuNI5c/7SXgz2W79WEE790eslpBIlqhn10s6FvJbakMDHiqYMZWjwFaDGi8\naRl5xB9+lwW/xekkUV7U1UtT7dkjWjYDZaPBA61BMPNGG4WQr2W11bHkFlt4dR2X\nem1ZqSqPe97Dh4kQmUlzeMg9vVE1dCrV8X5pGyq7O70luJpaPXJhkGaH7gzWTdQR\ndAtq/gsD/KNVV4n+SsuuWxcFyPKNIzFTONItaj+CuY0IavdeQXRuwxF+B6wpYJE/\nOMpXEA29MC/HpeZBoNquBYeaoKRlbEwJDIm6uNO5wJOKMPqN5ZprFQFOZ6raYlY+\nhAhm0sQ2fac+EPyI4NSA5QC9qvNOBqN6avlicuMJT+ubDgEj8Z+7fNzcbBGXJbLy\ntGMU0gYqZ4yD9c7qB9iaah7s5Aq7KkzrCWA5zspi2C5u\n-----END CERTIFICATE-----\n\n# Issuer: CN=GeoTrust Primary Certification Authority O=GeoTrust Inc.\n# Subject: CN=GeoTrust Primary Certification Authority O=GeoTrust Inc.\n# Label: \"GeoTrust Primary Certification Authority\"\n# Serial: 32798226551256963324313806436981982369\n# MD5 Fingerprint: 02:26:c3:01:5e:08:30:37:43:a9:d0:7d:cf:37:e6:bf\n# SHA1 Fingerprint: 32:3c:11:8e:1b:f7:b8:b6:52:54:e2:e2:10:0d:d6:02:90:37:f0:96\n# SHA256 Fingerprint: 37:d5:10:06:c5:12:ea:ab:62:64:21:f1:ec:8c:92:01:3f:c5:f8:2a:e9:8e:e5:33:eb:46:19:b8:de:b4:d0:6c\n-----BEGIN CERTIFICATE-----\nMIIDfDCCAmSgAwIBAgIQGKy1av1pthU6Y2yv2vrEoTANBgkqhkiG9w0BAQUFADBY\nMQswCQYDVQQGEwJVUzEWMBQGA1UEChMNR2VvVHJ1c3QgSW5jLjExMC8GA1UEAxMo\nR2VvVHJ1c3QgUHJpbWFyeSBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0eTAeFw0wNjEx\nMjcwMDAwMDBaFw0zNjA3MTYyMzU5NTlaMFgxCzAJBgNVBAYTAlVTMRYwFAYDVQQK\nEw1HZW9UcnVzdCBJbmMuMTEwLwYDVQQDEyhHZW9UcnVzdCBQcmltYXJ5IENlcnRp\nZmljYXRpb24gQXV0aG9yaXR5MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKC\nAQEAvrgVe//UfH1nrYNke8hCUy3f9oQIIGHWAVlqnEQRr+92/ZV+zmEwu3qDXwK9\nAWbK7hWNb6EwnL2hhZ6UOvNWiAAxz9juapYC2e0DjPt1befquFUWBRaa9OBesYjA\nZIVcFU2Ix7e64HXprQU9nceJSOC7KMgD4TCTZF5SwFlwIjVXiIrxlQqD17wxcwE0\n7e9GceBrAqg1cmuXm2bgyxx5X9gaBGgeRwLmnWDiNpcB3841kt++Z8dtd1k7j53W\nkBWUvEI0EME5+bEnPn7WinXFsq+W06Lem+SYvn3h6YGttm/81w7a4DSwDRp35+MI\nmO9Y+pyEtzavwt+s0vQQBnBxNQIDAQABo0IwQDAPBgNVHRMBAf8EBTADAQH/MA4G\nA1UdDwEB/wQEAwIBBjAdBgNVHQ4EFgQULNVQQZcVi/CPNmFbSvtr2ZnJM5IwDQYJ\nKoZIhvcNAQEFBQADggEBAFpwfyzdtzRP9YZRqSa+S7iq8XEN3GHHoOo0Hnp3DwQ1\n6CePbJC/kRYkRj5KTs4rFtULUh38H2eiAkUxT87z+gOneZ1TatnaYzr4gNfTmeGl\n4b7UVXGYNTq+k+qurUKykG/g/CFNNWMziUnWm07Kx+dOCQD32sfvmWKZd7aVIl6K\noKv0uHiYyjgZmclynnjNS6yvGaBzEi38wkG6gZHaFloxt/m0cYASSJlyc1pZU8Fj\nUjPtp8nSOQJw+uCxQmYpqptR7TBUIhRf2asdweSU8Pj1K/fqynhG1riR/aYNKxoU\nAT6A8EKglQdebc3MS6RFjasS6LPeWuWgfOgPIh1a6Vk=\n-----END CERTIFICATE-----\n\n# Issuer: CN=thawte Primary Root CA O=thawte, Inc. OU=Certification Services Division/(c) 2006 thawte, Inc. - For authorized use only\n# Subject: CN=thawte Primary Root CA O=thawte, Inc. OU=Certification Services Division/(c) 2006 thawte, Inc. - For authorized use only\n# Label: \"thawte Primary Root CA\"\n# Serial: 69529181992039203566298953787712940909\n# MD5 Fingerprint: 8c:ca:dc:0b:22:ce:f5:be:72:ac:41:1a:11:a8:d8:12\n# SHA1 Fingerprint: 91:c6:d6:ee:3e:8a:c8:63:84:e5:48:c2:99:29:5c:75:6c:81:7b:81\n# SHA256 Fingerprint: 8d:72:2f:81:a9:c1:13:c0:79:1d:f1:36:a2:96:6d:b2:6c:95:0a:97:1d:b4:6b:41:99:f4:ea:54:b7:8b:fb:9f\n-----BEGIN CERTIFICATE-----\nMIIEIDCCAwigAwIBAgIQNE7VVyDV7exJ9C/ON9srbTANBgkqhkiG9w0BAQUFADCB\nqTELMAkGA1UEBhMCVVMxFTATBgNVBAoTDHRoYXd0ZSwgSW5jLjEoMCYGA1UECxMf\nQ2VydGlmaWNhdGlvbiBTZXJ2aWNlcyBEaXZpc2lvbjE4MDYGA1UECxMvKGMpIDIw\nMDYgdGhhd3RlLCBJbmMuIC0gRm9yIGF1dGhvcml6ZWQgdXNlIG9ubHkxHzAdBgNV\nBAMTFnRoYXd0ZSBQcmltYXJ5IFJvb3QgQ0EwHhcNMDYxMTE3MDAwMDAwWhcNMzYw\nNzE2MjM1OTU5WjCBqTELMAkGA1UEBhMCVVMxFTATBgNVBAoTDHRoYXd0ZSwgSW5j\nLjEoMCYGA1UECxMfQ2VydGlmaWNhdGlvbiBTZXJ2aWNlcyBEaXZpc2lvbjE4MDYG\nA1UECxMvKGMpIDIwMDYgdGhhd3RlLCBJbmMuIC0gRm9yIGF1dGhvcml6ZWQgdXNl\nIG9ubHkxHzAdBgNVBAMTFnRoYXd0ZSBQcmltYXJ5IFJvb3QgQ0EwggEiMA0GCSqG\nSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCsoPD7gFnUnMekz52hWXMJEEUMDSxuaPFs\nW0hoSVk3/AszGcJ3f8wQLZU0HObrTQmnHNK4yZc2AreJ1CRfBsDMRJSUjQJib+ta\n3RGNKJpchJAQeg29dGYvajig4tVUROsdB58Hum/u6f1OCyn1PoSgAfGcq/gcfomk\n6KHYcWUNo1F77rzSImANuVud37r8UVsLr5iy6S7pBOhih94ryNdOwUxkHt3Ph1i6\nSk/KaAcdHJ1KxtUvkcx8cXIcxcBn6zL9yZJclNqFwJu/U30rCfSMnZEfl2pSy94J\nNqR32HuHUETVPm4pafs5SSYeCaWAe0At6+gnhcn+Yf1+5nyXHdWdAgMBAAGjQjBA\nMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgEGMB0GA1UdDgQWBBR7W0XP\nr87Lev0xkhpqtvNG61dIUDANBgkqhkiG9w0BAQUFAAOCAQEAeRHAS7ORtvzw6WfU\nDW5FvlXok9LOAz/t2iWwHVfLHjp2oEzsUHboZHIMpKnxuIvW1oeEuzLlQRHAd9mz\nYJ3rG9XRbkREqaYB7FViHXe4XI5ISXycO1cRrK1zN44veFyQaEfZYGDm/Ac9IiAX\nxPcW6cTYcvnIc3zfFi8VqT79aie2oetaupgf1eNNZAqdE8hhuvU5HIe6uL17In/2\n/qxAeeWsEG89jxt5dovEN7MhGITlNgDrYyCZuen+MwS7QcjBAvlEYyCegc5C09Y/\nLHbTY5xZ3Y+m4Q6gLkH3LpVHz7z9M/P2C2F+fpErgUfCJzDupxBdN49cOSvkBPB7\njVaMaA==\n-----END CERTIFICATE-----\n\n# Issuer: CN=VeriSign Class 3 Public Primary Certification Authority - G5 O=VeriSign, Inc. OU=VeriSign Trust Network/(c) 2006 VeriSign, Inc. - For authorized use only\n# Subject: CN=VeriSign Class 3 Public Primary Certification Authority - G5 O=VeriSign, Inc. OU=VeriSign Trust Network/(c) 2006 VeriSign, Inc. - For authorized use only\n# Label: \"VeriSign Class 3 Public Primary Certification Authority - G5\"\n# Serial: 33037644167568058970164719475676101450\n# MD5 Fingerprint: cb:17:e4:31:67:3e:e2:09:fe:45:57:93:f3:0a:fa:1c\n# SHA1 Fingerprint: 4e:b6:d5:78:49:9b:1c:cf:5f:58:1e:ad:56:be:3d:9b:67:44:a5:e5\n# SHA256 Fingerprint: 9a:cf:ab:7e:43:c8:d8:80:d0:6b:26:2a:94:de:ee:e4:b4:65:99:89:c3:d0:ca:f1:9b:af:64:05:e4:1a:b7:df\n-----BEGIN CERTIFICATE-----\nMIIE0zCCA7ugAwIBAgIQGNrRniZ96LtKIVjNzGs7SjANBgkqhkiG9w0BAQUFADCB\nyjELMAkGA1UEBhMCVVMxFzAVBgNVBAoTDlZlcmlTaWduLCBJbmMuMR8wHQYDVQQL\nExZWZXJpU2lnbiBUcnVzdCBOZXR3b3JrMTowOAYDVQQLEzEoYykgMjAwNiBWZXJp\nU2lnbiwgSW5jLiAtIEZvciBhdXRob3JpemVkIHVzZSBvbmx5MUUwQwYDVQQDEzxW\nZXJpU2lnbiBDbGFzcyAzIFB1YmxpYyBQcmltYXJ5IENlcnRpZmljYXRpb24gQXV0\naG9yaXR5IC0gRzUwHhcNMDYxMTA4MDAwMDAwWhcNMzYwNzE2MjM1OTU5WjCByjEL\nMAkGA1UEBhMCVVMxFzAVBgNVBAoTDlZlcmlTaWduLCBJbmMuMR8wHQYDVQQLExZW\nZXJpU2lnbiBUcnVzdCBOZXR3b3JrMTowOAYDVQQLEzEoYykgMjAwNiBWZXJpU2ln\nbiwgSW5jLiAtIEZvciBhdXRob3JpemVkIHVzZSBvbmx5MUUwQwYDVQQDEzxWZXJp\nU2lnbiBDbGFzcyAzIFB1YmxpYyBQcmltYXJ5IENlcnRpZmljYXRpb24gQXV0aG9y\naXR5IC0gRzUwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCvJAgIKXo1\nnmAMqudLO07cfLw8RRy7K+D+KQL5VwijZIUVJ/XxrcgxiV0i6CqqpkKzj/i5Vbex\nt0uz/o9+B1fs70PbZmIVYc9gDaTY3vjgw2IIPVQT60nKWVSFJuUrjxuf6/WhkcIz\nSdhDY2pSS9KP6HBRTdGJaXvHcPaz3BJ023tdS1bTlr8Vd6Gw9KIl8q8ckmcY5fQG\nBO+QueQA5N06tRn/Arr0PO7gi+s3i+z016zy9vA9r911kTMZHRxAy3QkGSGT2RT+\nrCpSx4/VBEnkjWNHiDxpg8v+R70rfk/Fla4OndTRQ8Bnc+MUCH7lP59zuDMKz10/\nNIeWiu5T6CUVAgMBAAGjgbIwga8wDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8E\nBAMCAQYwbQYIKwYBBQUHAQwEYTBfoV2gWzBZMFcwVRYJaW1hZ2UvZ2lmMCEwHzAH\nBgUrDgMCGgQUj+XTGoasjY5rw8+AatRIGCx7GS4wJRYjaHR0cDovL2xvZ28udmVy\naXNpZ24uY29tL3ZzbG9nby5naWYwHQYDVR0OBBYEFH/TZafC3ey78DAJ80M5+gKv\nMzEzMA0GCSqGSIb3DQEBBQUAA4IBAQCTJEowX2LP2BqYLz3q3JktvXf2pXkiOOzE\np6B4Eq1iDkVwZMXnl2YtmAl+X6/WzChl8gGqCBpH3vn5fJJaCGkgDdk+bW48DW7Y\n5gaRQBi5+MHt39tBquCWIMnNZBU4gcmU7qKEKQsTb47bDN0lAtukixlE0kF6BWlK\nWE9gyn6CagsCqiUXObXbf+eEZSqVir2G3l6BFoMtEMze/aiCKm0oHw0LxOXnGiYZ\n4fQRbxC1lfznQgUy286dUV4otp6F01vvpX1FQHKOtw5rDgb7MzVIcbidJ4vEZV8N\nhnacRHr2lVz2XTIIM6RUthg/aFzyQkqFOFSDX9HoLPKsEdao7WNq\n-----END CERTIFICATE-----\n\n# Issuer: CN=SecureTrust CA O=SecureTrust Corporation\n# Subject: CN=SecureTrust CA O=SecureTrust Corporation\n# Label: \"SecureTrust CA\"\n# Serial: 17199774589125277788362757014266862032\n# MD5 Fingerprint: dc:32:c3:a7:6d:25:57:c7:68:09:9d:ea:2d:a9:a2:d1\n# SHA1 Fingerprint: 87:82:c6:c3:04:35:3b:cf:d2:96:92:d2:59:3e:7d:44:d9:34:ff:11\n# SHA256 Fingerprint: f1:c1:b5:0a:e5:a2:0d:d8:03:0e:c9:f6:bc:24:82:3d:d3:67:b5:25:57:59:b4:e7:1b:61:fc:e9:f7:37:5d:73\n-----BEGIN CERTIFICATE-----\nMIIDuDCCAqCgAwIBAgIQDPCOXAgWpa1Cf/DrJxhZ0DANBgkqhkiG9w0BAQUFADBI\nMQswCQYDVQQGEwJVUzEgMB4GA1UEChMXU2VjdXJlVHJ1c3QgQ29ycG9yYXRpb24x\nFzAVBgNVBAMTDlNlY3VyZVRydXN0IENBMB4XDTA2MTEwNzE5MzExOFoXDTI5MTIz\nMTE5NDA1NVowSDELMAkGA1UEBhMCVVMxIDAeBgNVBAoTF1NlY3VyZVRydXN0IENv\ncnBvcmF0aW9uMRcwFQYDVQQDEw5TZWN1cmVUcnVzdCBDQTCCASIwDQYJKoZIhvcN\nAQEBBQADggEPADCCAQoCggEBAKukgeWVzfX2FI7CT8rU4niVWJxB4Q2ZQCQXOZEz\nZum+4YOvYlyJ0fwkW2Gz4BERQRwdbvC4u/jep4G6pkjGnx29vo6pQT64lO0pGtSO\n0gMdA+9tDWccV9cGrcrI9f4Or2YlSASWC12juhbDCE/RRvgUXPLIXgGZbf2IzIao\nwW8xQmxSPmjL8xk037uHGFaAJsTQ3MBv396gwpEWoGQRS0S8Hvbn+mPeZqx2pHGj\n7DaUaHp3pLHnDi+BeuK1cobvomuL8A/b01k/unK8RCSc43Oz969XL0Imnal0ugBS\n8kvNU3xHCzaFDmapCJcWNFfBZveA4+1wVMeT4C4oFVmHursCAwEAAaOBnTCBmjAT\nBgkrBgEEAYI3FAIEBh4EAEMAQTALBgNVHQ8EBAMCAYYwDwYDVR0TAQH/BAUwAwEB\n/zAdBgNVHQ4EFgQUQjK2FvoE/f5dS3rD/fdMQB1aQ68wNAYDVR0fBC0wKzApoCeg\nJYYjaHR0cDovL2NybC5zZWN1cmV0cnVzdC5jb20vU1RDQS5jcmwwEAYJKwYBBAGC\nNxUBBAMCAQAwDQYJKoZIhvcNAQEFBQADggEBADDtT0rhWDpSclu1pqNlGKa7UTt3\n6Z3q059c4EVlew3KW+JwULKUBRSuSceNQQcSc5R+DCMh/bwQf2AQWnL1mA6s7Ll/\n3XpvXdMc9P+IBWlCqQVxyLesJugutIxq/3HcuLHfmbx8IVQr5Fiiu1cprp6poxkm\nD5kuCLDv/WnPmRoJjeOnnyvJNjR7JLN4TJUXpAYmHrZkUjZfYGfZnMUFdAvnZyPS\nCPyI6a6Lf+Ew9Dd+/cYy2i2eRDAwbO4H3tI0/NL/QPZL9GZGBlSm8jIKYyYwa5vR\n3ItHuuG51WLQoqD0ZwV4KWMabwTW+MZMo5qxN7SN5ShLHZ4swrhovO0C7jE=\n-----END CERTIFICATE-----\n\n# Issuer: CN=Secure Global CA O=SecureTrust Corporation\n# Subject: CN=Secure Global CA O=SecureTrust Corporation\n# Label: \"Secure Global CA\"\n# Serial: 9751836167731051554232119481456978597\n# MD5 Fingerprint: cf:f4:27:0d:d4:ed:dc:65:16:49:6d:3d:da:bf:6e:de\n# SHA1 Fingerprint: 3a:44:73:5a:e5:81:90:1f:24:86:61:46:1e:3b:9c:c4:5f:f5:3a:1b\n# SHA256 Fingerprint: 42:00:f5:04:3a:c8:59:0e:bb:52:7d:20:9e:d1:50:30:29:fb:cb:d4:1c:a1:b5:06:ec:27:f1:5a:de:7d:ac:69\n-----BEGIN CERTIFICATE-----\nMIIDvDCCAqSgAwIBAgIQB1YipOjUiolN9BPI8PjqpTANBgkqhkiG9w0BAQUFADBK\nMQswCQYDVQQGEwJVUzEgMB4GA1UEChMXU2VjdXJlVHJ1c3QgQ29ycG9yYXRpb24x\nGTAXBgNVBAMTEFNlY3VyZSBHbG9iYWwgQ0EwHhcNMDYxMTA3MTk0MjI4WhcNMjkx\nMjMxMTk1MjA2WjBKMQswCQYDVQQGEwJVUzEgMB4GA1UEChMXU2VjdXJlVHJ1c3Qg\nQ29ycG9yYXRpb24xGTAXBgNVBAMTEFNlY3VyZSBHbG9iYWwgQ0EwggEiMA0GCSqG\nSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCvNS7YrGxVaQZx5RNoJLNP2MwhR/jxYDiJ\niQPpvepeRlMJ3Fz1Wuj3RSoC6zFh1ykzTM7HfAo3fg+6MpjhHZevj8fcyTiW89sa\n/FHtaMbQbqR8JNGuQsiWUGMu4P51/pinX0kuleM5M2SOHqRfkNJnPLLZ/kG5VacJ\njnIFHovdRIWCQtBJwB1g8NEXLJXr9qXBkqPFwqcIYA1gBBCWeZ4WNOaptvolRTnI\nHmX5k/Wq8VLcmZg9pYYaDDUz+kulBAYVHDGA76oYa8J719rO+TMg1fW9ajMtgQT7\nsFzUnKPiXB3jqUJ1XnvUd+85VLrJChgbEplJL4hL/VBi0XPnj3pDAgMBAAGjgZ0w\ngZowEwYJKwYBBAGCNxQCBAYeBABDAEEwCwYDVR0PBAQDAgGGMA8GA1UdEwEB/wQF\nMAMBAf8wHQYDVR0OBBYEFK9EBMJBfkiD2045AuzshHrmzsmkMDQGA1UdHwQtMCsw\nKaAnoCWGI2h0dHA6Ly9jcmwuc2VjdXJldHJ1c3QuY29tL1NHQ0EuY3JsMBAGCSsG\nAQQBgjcVAQQDAgEAMA0GCSqGSIb3DQEBBQUAA4IBAQBjGghAfaReUw132HquHw0L\nURYD7xh8yOOvaliTFGCRsoTciE6+OYo68+aCiV0BN7OrJKQVDpI1WkpEXk5X+nXO\nH0jOZvQ8QCaSmGwb7iRGDBezUqXbpZGRzzfTb+cnCDpOGR86p1hcF895P4vkp9Mm\nI50mD1hp/Ed+stCNi5O/KU9DaXR2Z0vPB4zmAve14bRDtUstFJ/53CYNv6ZHdAbY\niNE6KTCEztI5gGIbqMdXSbxqVVFnFUq+NQfk1XWYN3kwFNspnWzFacxHVaIw98xc\nf8LDmBxrThaA63p4ZUWiABqvDA1VZDRIuJK58bRQKfJPIx/abKwfROHdI3hRW8cW\n-----END CERTIFICATE-----\n\n# Issuer: CN=COMODO Certification Authority O=COMODO CA Limited\n# Subject: CN=COMODO Certification Authority O=COMODO CA Limited\n# Label: \"COMODO Certification Authority\"\n# Serial: 104350513648249232941998508985834464573\n# MD5 Fingerprint: 5c:48:dc:f7:42:72:ec:56:94:6d:1c:cc:71:35:80:75\n# SHA1 Fingerprint: 66:31:bf:9e:f7:4f:9e:b6:c9:d5:a6:0c:ba:6a:be:d1:f7:bd:ef:7b\n# SHA256 Fingerprint: 0c:2c:d6:3d:f7:80:6f:a3:99:ed:e8:09:11:6b:57:5b:f8:79:89:f0:65:18:f9:80:8c:86:05:03:17:8b:af:66\n-----BEGIN CERTIFICATE-----\nMIIEHTCCAwWgAwIBAgIQToEtioJl4AsC7j41AkblPTANBgkqhkiG9w0BAQUFADCB\ngTELMAkGA1UEBhMCR0IxGzAZBgNVBAgTEkdyZWF0ZXIgTWFuY2hlc3RlcjEQMA4G\nA1UEBxMHU2FsZm9yZDEaMBgGA1UEChMRQ09NT0RPIENBIExpbWl0ZWQxJzAlBgNV\nBAMTHkNPTU9ETyBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0eTAeFw0wNjEyMDEwMDAw\nMDBaFw0yOTEyMzEyMzU5NTlaMIGBMQswCQYDVQQGEwJHQjEbMBkGA1UECBMSR3Jl\nYXRlciBNYW5jaGVzdGVyMRAwDgYDVQQHEwdTYWxmb3JkMRowGAYDVQQKExFDT01P\nRE8gQ0EgTGltaXRlZDEnMCUGA1UEAxMeQ09NT0RPIENlcnRpZmljYXRpb24gQXV0\naG9yaXR5MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA0ECLi3LjkRv3\nUcEbVASY06m/weaKXTuH+7uIzg3jLz8GlvCiKVCZrts7oVewdFFxze1CkU1B/qnI\n2GqGd0S7WWaXUF601CxwRM/aN5VCaTwwxHGzUvAhTaHYujl8HJ6jJJ3ygxaYqhZ8\nQ5sVW7euNJH+1GImGEaaP+vB+fGQV+useg2L23IwambV4EajcNxo2f8ESIl33rXp\n+2dtQem8Ob0y2WIC8bGoPW43nOIv4tOiJovGuFVDiOEjPqXSJDlqR6sA1KGzqSX+\nDT+nHbrTUcELpNqsOO9VUCQFZUaTNE8tja3G1CEZ0o7KBWFxB3NH5YoZEr0ETc5O\nnKVIrLsm9wIDAQABo4GOMIGLMB0GA1UdDgQWBBQLWOWLxkwVN6RAqTCpIb5HNlpW\n/zAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zBJBgNVHR8EQjBAMD6g\nPKA6hjhodHRwOi8vY3JsLmNvbW9kb2NhLmNvbS9DT01PRE9DZXJ0aWZpY2F0aW9u\nQXV0aG9yaXR5LmNybDANBgkqhkiG9w0BAQUFAAOCAQEAPpiem/Yb6dc5t3iuHXIY\nSdOH5EOC6z/JqvWote9VfCFSZfnVDeFs9D6Mk3ORLgLETgdxb8CPOGEIqB6BCsAv\nIC9Bi5HcSEW88cbeunZrM8gALTFGTO3nnc+IlP8zwFboJIYmuNg4ON8qa90SzMc/\nRxdMosIGlgnW2/4/PEZB31jiVg88O8EckzXZOFKs7sjsLjBOlDW0JB9LeGna8gI4\nzJVSk/BwJVmcIGfE7vmLV2H0knZ9P4SNVbfo5azV8fUZVqZa+5Acr5Pr5RzUZ5dd\nBA6+C4OmF4O5MBKgxTMVBbkN+8cFduPYSo38NBejxiEovjBFMR7HeL5YYTisO+IB\nZQ==\n-----END CERTIFICATE-----\n\n# Issuer: CN=Network Solutions Certificate Authority O=Network Solutions L.L.C.\n# Subject: CN=Network Solutions Certificate Authority O=Network Solutions L.L.C.\n# Label: \"Network Solutions Certificate Authority\"\n# Serial: 116697915152937497490437556386812487904\n# MD5 Fingerprint: d3:f3:a6:16:c0:fa:6b:1d:59:b1:2d:96:4d:0e:11:2e\n# SHA1 Fingerprint: 74:f8:a3:c3:ef:e7:b3:90:06:4b:83:90:3c:21:64:60:20:e5:df:ce\n# SHA256 Fingerprint: 15:f0:ba:00:a3:ac:7a:f3:ac:88:4c:07:2b:10:11:a0:77:bd:77:c0:97:f4:01:64:b2:f8:59:8a:bd:83:86:0c\n-----BEGIN CERTIFICATE-----\nMIID5jCCAs6gAwIBAgIQV8szb8JcFuZHFhfjkDFo4DANBgkqhkiG9w0BAQUFADBi\nMQswCQYDVQQGEwJVUzEhMB8GA1UEChMYTmV0d29yayBTb2x1dGlvbnMgTC5MLkMu\nMTAwLgYDVQQDEydOZXR3b3JrIFNvbHV0aW9ucyBDZXJ0aWZpY2F0ZSBBdXRob3Jp\ndHkwHhcNMDYxMjAxMDAwMDAwWhcNMjkxMjMxMjM1OTU5WjBiMQswCQYDVQQGEwJV\nUzEhMB8GA1UEChMYTmV0d29yayBTb2x1dGlvbnMgTC5MLkMuMTAwLgYDVQQDEydO\nZXR3b3JrIFNvbHV0aW9ucyBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkwggEiMA0GCSqG\nSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDkvH6SMG3G2I4rC7xGzuAnlt7e+foS0zwz\nc7MEL7xxjOWftiJgPl9dzgn/ggwbmlFQGiaJ3dVhXRncEg8tCqJDXRfQNJIg6nPP\nOCwGJgl6cvf6UDL4wpPTaaIjzkGxzOTVHzbRijr4jGPiFFlp7Q3Tf2vouAPlT2rl\nmGNpSAW+Lv8ztumXWWn4Zxmuk2GWRBXTcrA/vGp97Eh/jcOrqnErU2lBUzS1sLnF\nBgrEsEX1QV1uiUV7PTsmjHTC5dLRfbIR1PtYMiKagMnc/Qzpf14Dl847ABSHJ3A4\nqY5usyd2mFHgBeMhqxrVhSI8KbWaFsWAqPS7azCPL0YCorEMIuDTAgMBAAGjgZcw\ngZQwHQYDVR0OBBYEFCEwyfsA106Y2oeqKtCnLrFAMadMMA4GA1UdDwEB/wQEAwIB\nBjAPBgNVHRMBAf8EBTADAQH/MFIGA1UdHwRLMEkwR6BFoEOGQWh0dHA6Ly9jcmwu\nbmV0c29sc3NsLmNvbS9OZXR3b3JrU29sdXRpb25zQ2VydGlmaWNhdGVBdXRob3Jp\ndHkuY3JsMA0GCSqGSIb3DQEBBQUAA4IBAQC7rkvnt1frf6ott3NHhWrB5KUd5Oc8\n6fRZZXe1eltajSU24HqXLjjAV2CDmAaDn7l2em5Q4LqILPxFzBiwmZVRDuwduIj/\nh1AcgsLj4DKAv6ALR8jDMe+ZZzKATxcheQxpXN5eNK4CtSbqUN9/GGUsyfJj4akH\n/nxxH2szJGoeBfcFaMBqEssuXmHLrijTfsK0ZpEmXzwuJF/LWA/rKOyvEZbz3Htv\nwKeI8lN3s2Berq4o2jUsbzRF0ybh3uxbTydrFny9RAQYgrOJeRcQcT16ohZO9QHN\npGxlaKFJdlxDydi8NmdspZS11My5vWo1ViHe2MPr+8ukYEywVaCge1ey\n-----END CERTIFICATE-----\n\n# Issuer: CN=COMODO ECC Certification Authority O=COMODO CA Limited\n# Subject: CN=COMODO ECC Certification Authority O=COMODO CA Limited\n# Label: \"COMODO ECC Certification Authority\"\n# Serial: 41578283867086692638256921589707938090\n# MD5 Fingerprint: 7c:62:ff:74:9d:31:53:5e:68:4a:d5:78:aa:1e:bf:23\n# SHA1 Fingerprint: 9f:74:4e:9f:2b:4d:ba:ec:0f:31:2c:50:b6:56:3b:8e:2d:93:c3:11\n# SHA256 Fingerprint: 17:93:92:7a:06:14:54:97:89:ad:ce:2f:8f:34:f7:f0:b6:6d:0f:3a:e3:a3:b8:4d:21:ec:15:db:ba:4f:ad:c7\n-----BEGIN CERTIFICATE-----\nMIICiTCCAg+gAwIBAgIQH0evqmIAcFBUTAGem2OZKjAKBggqhkjOPQQDAzCBhTEL\nMAkGA1UEBhMCR0IxGzAZBgNVBAgTEkdyZWF0ZXIgTWFuY2hlc3RlcjEQMA4GA1UE\nBxMHU2FsZm9yZDEaMBgGA1UEChMRQ09NT0RPIENBIExpbWl0ZWQxKzApBgNVBAMT\nIkNPTU9ETyBFQ0MgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkwHhcNMDgwMzA2MDAw\nMDAwWhcNMzgwMTE4MjM1OTU5WjCBhTELMAkGA1UEBhMCR0IxGzAZBgNVBAgTEkdy\nZWF0ZXIgTWFuY2hlc3RlcjEQMA4GA1UEBxMHU2FsZm9yZDEaMBgGA1UEChMRQ09N\nT0RPIENBIExpbWl0ZWQxKzApBgNVBAMTIkNPTU9ETyBFQ0MgQ2VydGlmaWNhdGlv\nbiBBdXRob3JpdHkwdjAQBgcqhkjOPQIBBgUrgQQAIgNiAAQDR3svdcmCFYX7deSR\nFtSrYpn1PlILBs5BAH+X4QokPB0BBO490o0JlwzgdeT6+3eKKvUDYEs2ixYjFq0J\ncfRK9ChQtP6IHG4/bC8vCVlbpVsLM5niwz2J+Wos77LTBumjQjBAMB0GA1UdDgQW\nBBR1cacZSBm8nZ3qQUfflMRId5nTeTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/\nBAUwAwEB/zAKBggqhkjOPQQDAwNoADBlAjEA7wNbeqy3eApyt4jf/7VGFAkK+qDm\nfQjGGoe9GKhzvSbKYAydzpmfz1wPMOG+FDHqAjAU9JM8SaczepBGR7NjfRObTrdv\nGDeAU/7dIOA1mjbRxwG55tzd8/8dLDoWV9mSOdY=\n-----END CERTIFICATE-----\n\n# Issuer: CN=OISTE WISeKey Global Root GA CA O=WISeKey OU=Copyright (c) 2005/OISTE Foundation Endorsed\n# Subject: CN=OISTE WISeKey Global Root GA CA O=WISeKey OU=Copyright (c) 2005/OISTE Foundation Endorsed\n# Label: \"OISTE WISeKey Global Root GA CA\"\n# Serial: 86718877871133159090080555911823548314\n# MD5 Fingerprint: bc:6c:51:33:a7:e9:d3:66:63:54:15:72:1b:21:92:93\n# SHA1 Fingerprint: 59:22:a1:e1:5a:ea:16:35:21:f8:98:39:6a:46:46:b0:44:1b:0f:a9\n# SHA256 Fingerprint: 41:c9:23:86:6a:b4:ca:d6:b7:ad:57:80:81:58:2e:02:07:97:a6:cb:df:4f:ff:78:ce:83:96:b3:89:37:d7:f5\n-----BEGIN CERTIFICATE-----\nMIID8TCCAtmgAwIBAgIQQT1yx/RrH4FDffHSKFTfmjANBgkqhkiG9w0BAQUFADCB\nijELMAkGA1UEBhMCQ0gxEDAOBgNVBAoTB1dJU2VLZXkxGzAZBgNVBAsTEkNvcHly\naWdodCAoYykgMjAwNTEiMCAGA1UECxMZT0lTVEUgRm91bmRhdGlvbiBFbmRvcnNl\nZDEoMCYGA1UEAxMfT0lTVEUgV0lTZUtleSBHbG9iYWwgUm9vdCBHQSBDQTAeFw0w\nNTEyMTExNjAzNDRaFw0zNzEyMTExNjA5NTFaMIGKMQswCQYDVQQGEwJDSDEQMA4G\nA1UEChMHV0lTZUtleTEbMBkGA1UECxMSQ29weXJpZ2h0IChjKSAyMDA1MSIwIAYD\nVQQLExlPSVNURSBGb3VuZGF0aW9uIEVuZG9yc2VkMSgwJgYDVQQDEx9PSVNURSBX\nSVNlS2V5IEdsb2JhbCBSb290IEdBIENBMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8A\nMIIBCgKCAQEAy0+zAJs9Nt350UlqaxBJH+zYK7LG+DKBKUOVTJoZIyEVRd7jyBxR\nVVuuk+g3/ytr6dTqvirdqFEr12bDYVxgAsj1znJ7O7jyTmUIms2kahnBAbtzptf2\nw93NvKSLtZlhuAGio9RN1AU9ka34tAhxZK9w8RxrfvbDd50kc3vkDIzh2TbhmYsF\nmQvtRTEJysIA2/dyoJaqlYfQjse2YXMNdmaM3Bu0Y6Kff5MTMPGhJ9vZ/yxViJGg\n4E8HsChWjBgbl0SOid3gF27nKu+POQoxhILYQBRJLnpB5Kf+42TMwVlxSywhp1t9\n4B3RLoGbw9ho972WG6xwsRYUC9tguSYBBQIDAQABo1EwTzALBgNVHQ8EBAMCAYYw\nDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQUswN+rja8sHnR3JQmthG+IbJphpQw\nEAYJKwYBBAGCNxUBBAMCAQAwDQYJKoZIhvcNAQEFBQADggEBAEuh/wuHbrP5wUOx\nSPMowB0uyQlB+pQAHKSkq0lPjz0e701vvbyk9vImMMkQyh2I+3QZH4VFvbBsUfk2\nftv1TDI6QU9bR8/oCy22xBmddMVHxjtqD6wU2zz0c5ypBd8A3HR4+vg1YFkCExh8\nvPtNsCBtQ7tgMHpnM1zFmdH4LTlSc/uMqpclXHLZCB6rTjzjgTGfA6b7wP4piFXa\nhNVQA7bihKOmNqoROgHhGEvWRGizPflTdISzRpFGlgC3gCy24eMQ4tui5yiPAZZi\nFj4A4xylNoEYokxSdsARo27mHbrjWr42U8U+dY+GaSlYU7Wcu2+fXMUY7N0v4ZjJ\n/L7fCg0=\n-----END CERTIFICATE-----\n\n# Issuer: CN=Certigna O=Dhimyotis\n# Subject: CN=Certigna O=Dhimyotis\n# Label: \"Certigna\"\n# Serial: 18364802974209362175\n# MD5 Fingerprint: ab:57:a6:5b:7d:42:82:19:b5:d8:58:26:28:5e:fd:ff\n# SHA1 Fingerprint: b1:2e:13:63:45:86:a4:6f:1a:b2:60:68:37:58:2d:c4:ac:fd:94:97\n# SHA256 Fingerprint: e3:b6:a2:db:2e:d7:ce:48:84:2f:7a:c5:32:41:c7:b7:1d:54:14:4b:fb:40:c1:1f:3f:1d:0b:42:f5:ee:a1:2d\n-----BEGIN CERTIFICATE-----\nMIIDqDCCApCgAwIBAgIJAP7c4wEPyUj/MA0GCSqGSIb3DQEBBQUAMDQxCzAJBgNV\nBAYTAkZSMRIwEAYDVQQKDAlEaGlteW90aXMxETAPBgNVBAMMCENlcnRpZ25hMB4X\nDTA3MDYyOTE1MTMwNVoXDTI3MDYyOTE1MTMwNVowNDELMAkGA1UEBhMCRlIxEjAQ\nBgNVBAoMCURoaW15b3RpczERMA8GA1UEAwwIQ2VydGlnbmEwggEiMA0GCSqGSIb3\nDQEBAQUAA4IBDwAwggEKAoIBAQDIaPHJ1tazNHUmgh7stL7qXOEm7RFHYeGifBZ4\nQCHkYJ5ayGPhxLGWkv8YbWkj4Sti993iNi+RB7lIzw7sebYs5zRLcAglozyHGxny\ngQcPOJAZ0xH+hrTy0V4eHpbNgGzOOzGTtvKg0KmVEn2lmsxryIRWijOp5yIVUxbw\nzBfsV1/pogqYCd7jX5xv3EjjhQsVWqa6n6xI4wmy9/Qy3l40vhx4XUJbzg4ij02Q\n130yGLMLLGq/jj8UEYkgDncUtT2UCIf3JR7VsmAA7G8qKCVuKj4YYxclPz5EIBb2\nJsglrgVKtOdjLPOMFlN+XPsRGgjBRmKfIrjxwo1p3Po6WAbfAgMBAAGjgbwwgbkw\nDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQUGu3+QTmQtCRZvgHyUtVF9lo53BEw\nZAYDVR0jBF0wW4AUGu3+QTmQtCRZvgHyUtVF9lo53BGhOKQ2MDQxCzAJBgNVBAYT\nAkZSMRIwEAYDVQQKDAlEaGlteW90aXMxETAPBgNVBAMMCENlcnRpZ25hggkA/tzj\nAQ/JSP8wDgYDVR0PAQH/BAQDAgEGMBEGCWCGSAGG+EIBAQQEAwIABzANBgkqhkiG\n9w0BAQUFAAOCAQEAhQMeknH2Qq/ho2Ge6/PAD/Kl1NqV5ta+aDY9fm4fTIrv0Q8h\nbV6lUmPOEvjvKtpv6zf+EwLHyzs+ImvaYS5/1HI93TDhHkxAGYwP15zRgzB7mFnc\nfca5DClMoTOi62c6ZYTTluLtdkVwj7Ur3vkj1kluPBS1xp81HlDQwY9qcEQCYsuu\nHWhBp6pX6FOqB9IG9tUUBguRA3UsbHK1YZWaDYu5Def131TN3ubY1gkIl2PlwS6w\nt0QmwCbAr1UwnjvVNioZBPRcHv/PLLf/0P2HQBHVESO7SMAhqaQoLf0V+LBOK/Qw\nWyH8EZE0vkHve52Xdf+XlcCWWC/qu0bXu+TZLg==\n-----END CERTIFICATE-----\n\n# Issuer: CN=Deutsche Telekom Root CA 2 O=Deutsche Telekom AG OU=T-TeleSec Trust Center\n# Subject: CN=Deutsche Telekom Root CA 2 O=Deutsche Telekom AG OU=T-TeleSec Trust Center\n# Label: \"Deutsche Telekom Root CA 2\"\n# Serial: 38\n# MD5 Fingerprint: 74:01:4a:91:b1:08:c4:58:ce:47:cd:f0:dd:11:53:08\n# SHA1 Fingerprint: 85:a4:08:c0:9c:19:3e:5d:51:58:7d:cd:d6:13:30:fd:8c:de:37:bf\n# SHA256 Fingerprint: b6:19:1a:50:d0:c3:97:7f:7d:a9:9b:cd:aa:c8:6a:22:7d:ae:b9:67:9e:c7:0b:a3:b0:c9:d9:22:71:c1:70:d3\n-----BEGIN CERTIFICATE-----\nMIIDnzCCAoegAwIBAgIBJjANBgkqhkiG9w0BAQUFADBxMQswCQYDVQQGEwJERTEc\nMBoGA1UEChMTRGV1dHNjaGUgVGVsZWtvbSBBRzEfMB0GA1UECxMWVC1UZWxlU2Vj\nIFRydXN0IENlbnRlcjEjMCEGA1UEAxMaRGV1dHNjaGUgVGVsZWtvbSBSb290IENB\nIDIwHhcNOTkwNzA5MTIxMTAwWhcNMTkwNzA5MjM1OTAwWjBxMQswCQYDVQQGEwJE\nRTEcMBoGA1UEChMTRGV1dHNjaGUgVGVsZWtvbSBBRzEfMB0GA1UECxMWVC1UZWxl\nU2VjIFRydXN0IENlbnRlcjEjMCEGA1UEAxMaRGV1dHNjaGUgVGVsZWtvbSBSb290\nIENBIDIwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCrC6M14IspFLEU\nha88EOQ5bzVdSq7d6mGNlUn0b2SjGmBmpKlAIoTZ1KXleJMOaAGtuU1cOs7TuKhC\nQN/Po7qCWWqSG6wcmtoIKyUn+WkjR/Hg6yx6m/UTAtB+NHzCnjwAWav12gz1Mjwr\nrFDa1sPeg5TKqAyZMg4ISFZbavva4VhYAUlfckE8FQYBjl2tqriTtM2e66foai1S\nNNs671x1Udrb8zH57nGYMsRUFUQM+ZtV7a3fGAigo4aKSe5TBY8ZTNXeWHmb0moc\nQqvF1afPaA+W5OFhmHZhyJF81j4A4pFQh+GdCuatl9Idxjp9y7zaAzTVjlsB9WoH\ntxa2bkp/AgMBAAGjQjBAMB0GA1UdDgQWBBQxw3kbuvVT1xfgiXotF2wKsyudMzAP\nBgNVHRMECDAGAQH/AgEFMA4GA1UdDwEB/wQEAwIBBjANBgkqhkiG9w0BAQUFAAOC\nAQEAlGRZrTlk5ynrE/5aw4sTV8gEJPB0d8Bg42f76Ymmg7+Wgnxu1MM9756Abrsp\ntJh6sTtU6zkXR34ajgv8HzFZMQSyzhfzLMdiNlXiItiJVbSYSKpk+tYcNthEeFpa\nIzpXl/V6ME+un2pMSyuOoAPjPuCp1NJ70rOo4nI8rZ7/gFnkm0W09juwzTkZmDLl\n6iFhkOQxIY40sfcvNUqFENrnijchvllj4PKFiDFT1FQUhXB59C4Gdyd1Lx+4ivn+\nxbrYNuSD7Odlt79jWvNGr4GUN9RBjNYj1h7P9WgbRGOiWrqnNVmh5XAFmw4jV5mU\nCm26OWMohpLzGITY+9HPBVZkVw==\n-----END CERTIFICATE-----\n\n# Issuer: CN=Cybertrust Global Root O=Cybertrust, Inc\n# Subject: CN=Cybertrust Global Root O=Cybertrust, Inc\n# Label: \"Cybertrust Global Root\"\n# Serial: 4835703278459682877484360\n# MD5 Fingerprint: 72:e4:4a:87:e3:69:40:80:77:ea:bc:e3:f4:ff:f0:e1\n# SHA1 Fingerprint: 5f:43:e5:b1:bf:f8:78:8c:ac:1c:c7:ca:4a:9a:c6:22:2b:cc:34:c6\n# SHA256 Fingerprint: 96:0a:df:00:63:e9:63:56:75:0c:29:65:dd:0a:08:67:da:0b:9c:bd:6e:77:71:4a:ea:fb:23:49:ab:39:3d:a3\n-----BEGIN CERTIFICATE-----\nMIIDoTCCAomgAwIBAgILBAAAAAABD4WqLUgwDQYJKoZIhvcNAQEFBQAwOzEYMBYG\nA1UEChMPQ3liZXJ0cnVzdCwgSW5jMR8wHQYDVQQDExZDeWJlcnRydXN0IEdsb2Jh\nbCBSb290MB4XDTA2MTIxNTA4MDAwMFoXDTIxMTIxNTA4MDAwMFowOzEYMBYGA1UE\nChMPQ3liZXJ0cnVzdCwgSW5jMR8wHQYDVQQDExZDeWJlcnRydXN0IEdsb2JhbCBS\nb290MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA+Mi8vRRQZhP/8NN5\n7CPytxrHjoXxEnOmGaoQ25yiZXRadz5RfVb23CO21O1fWLE3TdVJDm71aofW0ozS\nJ8bi/zafmGWgE07GKmSb1ZASzxQG9Dvj1Ci+6A74q05IlG2OlTEQXO2iLb3VOm2y\nHLtgwEZLAfVJrn5GitB0jaEMAs7u/OePuGtm839EAL9mJRQr3RAwHQeWP032a7iP\nt3sMpTjr3kfb1V05/Iin89cqdPHoWqI7n1C6poxFNcJQZZXcY4Lv3b93TZxiyWNz\nFtApD0mpSPCzqrdsxacwOUBdrsTiXSZT8M4cIwhhqJQZugRiQOwfOHB3EgZxpzAY\nXSUnpQIDAQABo4GlMIGiMA4GA1UdDwEB/wQEAwIBBjAPBgNVHRMBAf8EBTADAQH/\nMB0GA1UdDgQWBBS2CHsNesysIEyGVjJez6tuhS1wVzA/BgNVHR8EODA2MDSgMqAw\nhi5odHRwOi8vd3d3Mi5wdWJsaWMtdHJ1c3QuY29tL2NybC9jdC9jdHJvb3QuY3Js\nMB8GA1UdIwQYMBaAFLYIew16zKwgTIZWMl7Pq26FLXBXMA0GCSqGSIb3DQEBBQUA\nA4IBAQBW7wojoFROlZfJ+InaRcHUowAl9B8Tq7ejhVhpwjCt2BWKLePJzYFa+HMj\nWqd8BfP9IjsO0QbE2zZMcwSO5bAi5MXzLqXZI+O4Tkogp24CJJ8iYGd7ix1yCcUx\nXOl5n4BHPa2hCwcUPUf/A2kaDAtE52Mlp3+yybh2hO0j9n0Hq0V+09+zv+mKts2o\nomcrUtW3ZfA5TGOgkXmTUg9U3YO7n9GPp1Nzw8v/MOx8BLjYRB+TX3EJIrduPuoc\nA06dGiBh+4E37F78CkWr1+cXVdCg6mCbpvbjjFspwgZgFJ0tl0ypkxWdYcQBX0jW\nWL1WMRJOEcgh4LMRkWXbtKaIOM5V\n-----END CERTIFICATE-----\n\n# Issuer: O=Chunghwa Telecom Co., Ltd. OU=ePKI Root Certification Authority\n# Subject: O=Chunghwa Telecom Co., Ltd. OU=ePKI Root Certification Authority\n# Label: \"ePKI Root Certification Authority\"\n# Serial: 28956088682735189655030529057352760477\n# MD5 Fingerprint: 1b:2e:00:ca:26:06:90:3d:ad:fe:6f:15:68:d3:6b:b3\n# SHA1 Fingerprint: 67:65:0d:f1:7e:8e:7e:5b:82:40:a4:f4:56:4b:cf:e2:3d:69:c6:f0\n# SHA256 Fingerprint: c0:a6:f4:dc:63:a2:4b:fd:cf:54:ef:2a:6a:08:2a:0a:72:de:35:80:3e:2f:f5:ff:52:7a:e5:d8:72:06:df:d5\n-----BEGIN CERTIFICATE-----\nMIIFsDCCA5igAwIBAgIQFci9ZUdcr7iXAF7kBtK8nTANBgkqhkiG9w0BAQUFADBe\nMQswCQYDVQQGEwJUVzEjMCEGA1UECgwaQ2h1bmdod2EgVGVsZWNvbSBDby4sIEx0\nZC4xKjAoBgNVBAsMIWVQS0kgUm9vdCBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0eTAe\nFw0wNDEyMjAwMjMxMjdaFw0zNDEyMjAwMjMxMjdaMF4xCzAJBgNVBAYTAlRXMSMw\nIQYDVQQKDBpDaHVuZ2h3YSBUZWxlY29tIENvLiwgTHRkLjEqMCgGA1UECwwhZVBL\nSSBSb290IENlcnRpZmljYXRpb24gQXV0aG9yaXR5MIICIjANBgkqhkiG9w0BAQEF\nAAOCAg8AMIICCgKCAgEA4SUP7o3biDN1Z82tH306Tm2d0y8U82N0ywEhajfqhFAH\nSyZbCUNsIZ5qyNUD9WBpj8zwIuQf5/dqIjG3LBXy4P4AakP/h2XGtRrBp0xtInAh\nijHyl3SJCRImHJ7K2RKilTza6We/CKBk49ZCt0Xvl/T29de1ShUCWH2YWEtgvM3X\nDZoTM1PRYfl61dd4s5oz9wCGzh1NlDivqOx4UXCKXBCDUSH3ET00hl7lSM2XgYI1\nTBnsZfZrxQWh7kcT1rMhJ5QQCtkkO7q+RBNGMD+XPNjX12ruOzjjK9SXDrkb5wdJ\nfzcq+Xd4z1TtW0ado4AOkUPB1ltfFLqfpo0kR0BZv3I4sjZsN/+Z0V0OWQqraffA\nsgRFelQArr5T9rXn4fg8ozHSqf4hUmTFpmfwdQcGlBSBVcYn5AGPF8Fqcde+S/uU\nWH1+ETOxQvdibBjWzwloPn9s9h6PYq2lY9sJpx8iQkEeb5mKPtf5P0B6ebClAZLS\nnT0IFaUQAS2zMnaolQ2zepr7BxB4EW/hj8e6DyUadCrlHJhBmd8hh+iVBmoKs2pH\ndmX2Os+PYhcZewoozRrSgx4hxyy/vv9haLdnG7t4TY3OZ+XkwY63I2binZB1NJip\nNiuKmpS5nezMirH4JYlcWrYvjB9teSSnUmjDhDXiZo1jDiVN1Rmy5nk3pyKdVDEC\nAwEAAaNqMGgwHQYDVR0OBBYEFB4M97Zn8uGSJglFwFU5Lnc/QkqiMAwGA1UdEwQF\nMAMBAf8wOQYEZyoHAAQxMC8wLQIBADAJBgUrDgMCGgUAMAcGBWcqAwAABBRFsMLH\nClZ87lt4DJX5GFPBphzYEDANBgkqhkiG9w0BAQUFAAOCAgEACbODU1kBPpVJufGB\nuvl2ICO1J2B01GqZNF5sAFPZn/KmsSQHRGoqxqWOeBLoR9lYGxMqXnmbnwoqZ6Yl\nPwZpVnPDimZI+ymBV3QGypzqKOg4ZyYr8dW1P2WT+DZdjo2NQCCHGervJ8A9tDkP\nJXtoUHRVnAxZfVo9QZQlUgjgRywVMRnVvwdVxrsStZf0X4OFunHB2WyBEXYKCrC/\ngpf36j36+uwtqSiUO1bd0lEursC9CBWMd1I0ltabrNMdjmEPNXubrjlpC2JgQCA2\nj6/7Nu4tCEoduL+bXPjqpRugc6bY+G7gMwRfaKonh+3ZwZCc7b3jajWvY9+rGNm6\n5ulK6lCKD2GTHuItGeIwlDWSXQ62B68ZgI9HkFFLLk3dheLSClIKF5r8GrBQAuUB\no2M3IUxExJtRmREOc5wGj1QupyheRDmHVi03vYVElOEMSyycw5KFNGHLD7ibSkNS\n/jQ6fbjpKdx2qcgw+BRxgMYeNkh0IkFch4LoGHGLQYlE535YW6i4jRPpp2zDR+2z\nGp1iro2C6pSe3VkQw63d4k3jMdXH7OjysP6SHhYKGvzZ8/gntsm+HbRsZJB/9OTE\nW9c3rkIO3aQab3yIVMUWbuF6aC74Or8NpDyJO3inTmODBCEIZ43ygknQW/2xzQ+D\nhNQ+IIX3Sj0rnP0qCglN6oH4EZw=\n-----END CERTIFICATE-----\n\n# Issuer: O=certSIGN OU=certSIGN ROOT CA\n# Subject: O=certSIGN OU=certSIGN ROOT CA\n# Label: \"certSIGN ROOT CA\"\n# Serial: 35210227249154\n# MD5 Fingerprint: 18:98:c0:d6:e9:3a:fc:f9:b0:f5:0c:f7:4b:01:44:17\n# SHA1 Fingerprint: fa:b7:ee:36:97:26:62:fb:2d:b0:2a:f6:bf:03:fd:e8:7c:4b:2f:9b\n# SHA256 Fingerprint: ea:a9:62:c4:fa:4a:6b:af:eb:e4:15:19:6d:35:1c:cd:88:8d:4f:53:f3:fa:8a:e6:d7:c4:66:a9:4e:60:42:bb\n-----BEGIN CERTIFICATE-----\nMIIDODCCAiCgAwIBAgIGIAYFFnACMA0GCSqGSIb3DQEBBQUAMDsxCzAJBgNVBAYT\nAlJPMREwDwYDVQQKEwhjZXJ0U0lHTjEZMBcGA1UECxMQY2VydFNJR04gUk9PVCBD\nQTAeFw0wNjA3MDQxNzIwMDRaFw0zMTA3MDQxNzIwMDRaMDsxCzAJBgNVBAYTAlJP\nMREwDwYDVQQKEwhjZXJ0U0lHTjEZMBcGA1UECxMQY2VydFNJR04gUk9PVCBDQTCC\nASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALczuX7IJUqOtdu0KBuqV5Do\n0SLTZLrTk+jUrIZhQGpgV2hUhE28alQCBf/fm5oqrl0Hj0rDKH/v+yv6efHHrfAQ\nUySQi2bJqIirr1qjAOm+ukbuW3N7LBeCgV5iLKECZbO9xSsAfsT8AzNXDe3i+s5d\nRdY4zTW2ssHQnIFKquSyAVwdj1+ZxLGt24gh65AIgoDzMKND5pCCrlUoSe1b16kQ\nOA7+j0xbm0bqQfWwCHTD0IgztnzXdN/chNFDDnU5oSVAKOp4yw4sLjmdjItuFhwv\nJoIQ4uNllAoEwF73XVv4EOLQunpL+943AAAaWyjj0pxzPjKHmKHJUS/X3qwzs08C\nAwEAAaNCMEAwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAcYwHQYDVR0O\nBBYEFOCMm9slSbPxfIbWskKHC9BroNnkMA0GCSqGSIb3DQEBBQUAA4IBAQA+0hyJ\nLjX8+HXd5n9liPRyTMks1zJO890ZeUe9jjtbkw9QSSQTaxQGcu8J06Gh40CEyecY\nMnQ8SG4Pn0vU9x7Tk4ZkVJdjclDVVc/6IJMCopvDI5NOFlV2oHB5bc0hH88vLbwZ\n44gx+FkagQnIl6Z0x2DEW8xXjrJ1/RsCCdtZb3KTafcxQdaIOL+Hsr0Wefmq5L6I\nJd1hJyMctTEHBDa0GpC9oHRxUIltvBTjD4au8as+x6AJzKNI0eDbZOeStc+vckNw\ni/nDhDwTqn6Sm1dTk/pwwpEOMfmbZ13pljheX7NzTogVZ96edhBiIL5VaZVDADlN\n9u6wWk5JRFRYX0KD\n-----END CERTIFICATE-----\n\n# Issuer: CN=GeoTrust Primary Certification Authority - G3 O=GeoTrust Inc. OU=(c) 2008 GeoTrust Inc. - For authorized use only\n# Subject: CN=GeoTrust Primary Certification Authority - G3 O=GeoTrust Inc. OU=(c) 2008 GeoTrust Inc. - For authorized use only\n# Label: \"GeoTrust Primary Certification Authority - G3\"\n# Serial: 28809105769928564313984085209975885599\n# MD5 Fingerprint: b5:e8:34:36:c9:10:44:58:48:70:6d:2e:83:d4:b8:05\n# SHA1 Fingerprint: 03:9e:ed:b8:0b:e7:a0:3c:69:53:89:3b:20:d2:d9:32:3a:4c:2a:fd\n# SHA256 Fingerprint: b4:78:b8:12:25:0d:f8:78:63:5c:2a:a7:ec:7d:15:5e:aa:62:5e:e8:29:16:e2:cd:29:43:61:88:6c:d1:fb:d4\n-----BEGIN CERTIFICATE-----\nMIID/jCCAuagAwIBAgIQFaxulBmyeUtB9iepwxgPHzANBgkqhkiG9w0BAQsFADCB\nmDELMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUdlb1RydXN0IEluYy4xOTA3BgNVBAsT\nMChjKSAyMDA4IEdlb1RydXN0IEluYy4gLSBGb3IgYXV0aG9yaXplZCB1c2Ugb25s\neTE2MDQGA1UEAxMtR2VvVHJ1c3QgUHJpbWFyeSBDZXJ0aWZpY2F0aW9uIEF1dGhv\ncml0eSAtIEczMB4XDTA4MDQwMjAwMDAwMFoXDTM3MTIwMTIzNTk1OVowgZgxCzAJ\nBgNVBAYTAlVTMRYwFAYDVQQKEw1HZW9UcnVzdCBJbmMuMTkwNwYDVQQLEzAoYykg\nMjAwOCBHZW9UcnVzdCBJbmMuIC0gRm9yIGF1dGhvcml6ZWQgdXNlIG9ubHkxNjA0\nBgNVBAMTLUdlb1RydXN0IFByaW1hcnkgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkg\nLSBHMzCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBANziXmJYHTNXOTIz\n+uvLh4yn1ErdBojqZI4xmKU4kB6Yzy5jK/BGvESyiaHAKAxJcCGVn2TAppMSAmUm\nhsalifD614SgcK9PGpc/BkTVyetyEH3kMSj7HGHmKAdEc5IiaacDiGydY8hS2pgn\n5whMcD60yRLBxWeDXTPzAxHsatBT4tG6NmCUgLthY2xbF37fQJQeqw3CIShwiP/W\nJmxsYAQlTlV+fe+/lEjetx3dcI0FX4ilm/LC7urRQEFtYjgdVgbFA0dRIBn8exAL\nDmKudlW/X3e+PkkBUz2YJQN2JFodtNuJ6nnltrM7P7pMKEF/BqxqjsHQ9gUdfeZC\nhuOl1UcCAwEAAaNCMEAwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYw\nHQYDVR0OBBYEFMR5yo6hTgMdHNxr2zFblD4/MH8tMA0GCSqGSIb3DQEBCwUAA4IB\nAQAtxRPPVoB7eni9n64smefv2t+UXglpp+duaIy9cr5HqQ6XErhK8WTTOd8lNNTB\nzU6B8A8ExCSzNJbGpqow32hhc9f5joWJ7w5elShKKiePEI4ufIbEAp7aDHdlDkQN\nkv39sxY2+hENHYwOB4lqKVb3cvTdFZx3NWZXqxNT2I7BQMXXExZacse3aQHEerGD\nAWh9jUGhlBjBJVz88P6DAod8DQ3PLghcSkANPuyBYeYk28rgDi0Hsj5W3I31QYUH\nSJsMC8tJP33st/3LjWeJGqvtux6jAAgIFyqCXDFdRootD4abdNlF+9RAsXqqaC2G\nspki4cErx5z481+oghLrGREt\n-----END CERTIFICATE-----\n\n# Issuer: CN=thawte Primary Root CA - G2 O=thawte, Inc. OU=(c) 2007 thawte, Inc. - For authorized use only\n# Subject: CN=thawte Primary Root CA - G2 O=thawte, Inc. OU=(c) 2007 thawte, Inc. - For authorized use only\n# Label: \"thawte Primary Root CA - G2\"\n# Serial: 71758320672825410020661621085256472406\n# MD5 Fingerprint: 74:9d:ea:60:24:c4:fd:22:53:3e:cc:3a:72:d9:29:4f\n# SHA1 Fingerprint: aa:db:bc:22:23:8f:c4:01:a1:27:bb:38:dd:f4:1d:db:08:9e:f0:12\n# SHA256 Fingerprint: a4:31:0d:50:af:18:a6:44:71:90:37:2a:86:af:af:8b:95:1f:fb:43:1d:83:7f:1e:56:88:b4:59:71:ed:15:57\n-----BEGIN CERTIFICATE-----\nMIICiDCCAg2gAwIBAgIQNfwmXNmET8k9Jj1Xm67XVjAKBggqhkjOPQQDAzCBhDEL\nMAkGA1UEBhMCVVMxFTATBgNVBAoTDHRoYXd0ZSwgSW5jLjE4MDYGA1UECxMvKGMp\nIDIwMDcgdGhhd3RlLCBJbmMuIC0gRm9yIGF1dGhvcml6ZWQgdXNlIG9ubHkxJDAi\nBgNVBAMTG3RoYXd0ZSBQcmltYXJ5IFJvb3QgQ0EgLSBHMjAeFw0wNzExMDUwMDAw\nMDBaFw0zODAxMTgyMzU5NTlaMIGEMQswCQYDVQQGEwJVUzEVMBMGA1UEChMMdGhh\nd3RlLCBJbmMuMTgwNgYDVQQLEy8oYykgMjAwNyB0aGF3dGUsIEluYy4gLSBGb3Ig\nYXV0aG9yaXplZCB1c2Ugb25seTEkMCIGA1UEAxMbdGhhd3RlIFByaW1hcnkgUm9v\ndCBDQSAtIEcyMHYwEAYHKoZIzj0CAQYFK4EEACIDYgAEotWcgnuVnfFSeIf+iha/\nBebfowJPDQfGAFG6DAJSLSKkQjnE/o/qycG+1E3/n3qe4rF8mq2nhglzh9HnmuN6\npapu+7qzcMBniKI11KOasf2twu8x+qi58/sIxpHR+ymVo0IwQDAPBgNVHRMBAf8E\nBTADAQH/MA4GA1UdDwEB/wQEAwIBBjAdBgNVHQ4EFgQUmtgAMADna3+FGO6Lts6K\nDPgR4bswCgYIKoZIzj0EAwMDaQAwZgIxAN344FdHW6fmCsO99YCKlzUNG4k8VIZ3\nKMqh9HneteY4sPBlcIx/AlTCv//YoT7ZzwIxAMSNlPzcU9LcnXgWHxUzI1NS41ox\nXZ3Krr0TKUQNJ1uo52icEvdYPy5yAlejj6EULg==\n-----END CERTIFICATE-----\n\n# Issuer: CN=thawte Primary Root CA - G3 O=thawte, Inc. OU=Certification Services Division/(c) 2008 thawte, Inc. - For authorized use only\n# Subject: CN=thawte Primary Root CA - G3 O=thawte, Inc. OU=Certification Services Division/(c) 2008 thawte, Inc. - For authorized use only\n# Label: \"thawte Primary Root CA - G3\"\n# Serial: 127614157056681299805556476275995414779\n# MD5 Fingerprint: fb:1b:5d:43:8a:94:cd:44:c6:76:f2:43:4b:47:e7:31\n# SHA1 Fingerprint: f1:8b:53:8d:1b:e9:03:b6:a6:f0:56:43:5b:17:15:89:ca:f3:6b:f2\n# SHA256 Fingerprint: 4b:03:f4:58:07:ad:70:f2:1b:fc:2c:ae:71:c9:fd:e4:60:4c:06:4c:f5:ff:b6:86:ba:e5:db:aa:d7:fd:d3:4c\n-----BEGIN CERTIFICATE-----\nMIIEKjCCAxKgAwIBAgIQYAGXt0an6rS0mtZLL/eQ+zANBgkqhkiG9w0BAQsFADCB\nrjELMAkGA1UEBhMCVVMxFTATBgNVBAoTDHRoYXd0ZSwgSW5jLjEoMCYGA1UECxMf\nQ2VydGlmaWNhdGlvbiBTZXJ2aWNlcyBEaXZpc2lvbjE4MDYGA1UECxMvKGMpIDIw\nMDggdGhhd3RlLCBJbmMuIC0gRm9yIGF1dGhvcml6ZWQgdXNlIG9ubHkxJDAiBgNV\nBAMTG3RoYXd0ZSBQcmltYXJ5IFJvb3QgQ0EgLSBHMzAeFw0wODA0MDIwMDAwMDBa\nFw0zNzEyMDEyMzU5NTlaMIGuMQswCQYDVQQGEwJVUzEVMBMGA1UEChMMdGhhd3Rl\nLCBJbmMuMSgwJgYDVQQLEx9DZXJ0aWZpY2F0aW9uIFNlcnZpY2VzIERpdmlzaW9u\nMTgwNgYDVQQLEy8oYykgMjAwOCB0aGF3dGUsIEluYy4gLSBGb3IgYXV0aG9yaXpl\nZCB1c2Ugb25seTEkMCIGA1UEAxMbdGhhd3RlIFByaW1hcnkgUm9vdCBDQSAtIEcz\nMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAsr8nLPvb2FvdeHsbnndm\ngcs+vHyu86YnmjSjaDFxODNi5PNxZnmxqWWjpYvVj2AtP0LMqmsywCPLLEHd5N/8\nYZzic7IilRFDGF/Eth9XbAoFWCLINkw6fKXRz4aviKdEAhN0cXMKQlkC+BsUa0Lf\nb1+6a4KinVvnSr0eAXLbS3ToO39/fR8EtCab4LRarEc9VbjXsCZSKAExQGbY2SS9\n9irY7CFJXJv2eul/VTV+lmuNk5Mny5K76qxAwJ/C+IDPXfRa3M50hqY+bAtTyr2S\nzhkGcuYMXDhpxwTWvGzOW/b3aJzcJRVIiKHpqfiYnODz1TEoYRFsZ5aNOZnLwkUk\nOQIDAQABo0IwQDAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIBBjAdBgNV\nHQ4EFgQUrWyqlGCc7eT/+j4KdCtjA/e2Wb8wDQYJKoZIhvcNAQELBQADggEBABpA\n2JVlrAmSicY59BDlqQ5mU1143vokkbvnRFHfxhY0Cu9qRFHqKweKA3rD6z8KLFIW\noCtDuSWQP3CpMyVtRRooOyfPqsMpQhvfO0zAMzRbQYi/aytlryjvsvXDqmbOe1bu\nt8jLZ8HJnBoYuMTDSQPxYA5QzUbF83d597YV4Djbxy8ooAw/dyZ02SUS2jHaGh7c\nKUGRIjxpp7sC8rZcJwOJ9Abqm+RyguOhCcHpABnTPtRwa7pxpqpYrvS76Wy274fM\nm7v/OeZWYdMKp8RcTGB7BXcmer/YB1IsYvdwY9k5vG8cwnncdimvzsUsZAReiDZu\nMdRAGmI0Nj81Aa6sY6A=\n-----END CERTIFICATE-----\n\n# Issuer: CN=GeoTrust Primary Certification Authority - G2 O=GeoTrust Inc. OU=(c) 2007 GeoTrust Inc. - For authorized use only\n# Subject: CN=GeoTrust Primary Certification Authority - G2 O=GeoTrust Inc. OU=(c) 2007 GeoTrust Inc. - For authorized use only\n# Label: \"GeoTrust Primary Certification Authority - G2\"\n# Serial: 80682863203381065782177908751794619243\n# MD5 Fingerprint: 01:5e:d8:6b:bd:6f:3d:8e:a1:31:f8:12:e0:98:73:6a\n# SHA1 Fingerprint: 8d:17:84:d5:37:f3:03:7d:ec:70:fe:57:8b:51:9a:99:e6:10:d7:b0\n# SHA256 Fingerprint: 5e:db:7a:c4:3b:82:a0:6a:87:61:e8:d7:be:49:79:eb:f2:61:1f:7d:d7:9b:f9:1c:1c:6b:56:6a:21:9e:d7:66\n-----BEGIN CERTIFICATE-----\nMIICrjCCAjWgAwIBAgIQPLL0SAoA4v7rJDteYD7DazAKBggqhkjOPQQDAzCBmDEL\nMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUdlb1RydXN0IEluYy4xOTA3BgNVBAsTMChj\nKSAyMDA3IEdlb1RydXN0IEluYy4gLSBGb3IgYXV0aG9yaXplZCB1c2Ugb25seTE2\nMDQGA1UEAxMtR2VvVHJ1c3QgUHJpbWFyeSBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0\neSAtIEcyMB4XDTA3MTEwNTAwMDAwMFoXDTM4MDExODIzNTk1OVowgZgxCzAJBgNV\nBAYTAlVTMRYwFAYDVQQKEw1HZW9UcnVzdCBJbmMuMTkwNwYDVQQLEzAoYykgMjAw\nNyBHZW9UcnVzdCBJbmMuIC0gRm9yIGF1dGhvcml6ZWQgdXNlIG9ubHkxNjA0BgNV\nBAMTLUdlb1RydXN0IFByaW1hcnkgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkgLSBH\nMjB2MBAGByqGSM49AgEGBSuBBAAiA2IABBWx6P0DFUPlrOuHNxFi79KDNlJ9RVcL\nSo17VDs6bl8VAsBQps8lL33KSLjHUGMcKiEIfJo22Av+0SbFWDEwKCXzXV2juLal\ntJLtbCyf691DiaI8S0iRHVDsJt/WYC69IaNCMEAwDwYDVR0TAQH/BAUwAwEB/zAO\nBgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYEFBVfNVdRVfslsq0DafwBo/q+EVXVMAoG\nCCqGSM49BAMDA2cAMGQCMGSWWaboCd6LuvpaiIjwH5HTRqjySkwCY/tsXzjbLkGT\nqQ7mndwxHLKgpxgceeHHNgIwOlavmnRs9vuD4DPTCF+hnMJbn0bWtsuRBmOiBucz\nrD6ogRLQy7rQkgu2npaqBA+K\n-----END CERTIFICATE-----\n\n# Issuer: CN=VeriSign Universal Root Certification Authority O=VeriSign, Inc. OU=VeriSign Trust Network/(c) 2008 VeriSign, Inc. - For authorized use only\n# Subject: CN=VeriSign Universal Root Certification Authority O=VeriSign, Inc. OU=VeriSign Trust Network/(c) 2008 VeriSign, Inc. - For authorized use only\n# Label: \"VeriSign Universal Root Certification Authority\"\n# Serial: 85209574734084581917763752644031726877\n# MD5 Fingerprint: 8e:ad:b5:01:aa:4d:81:e4:8c:1d:d1:e1:14:00:95:19\n# SHA1 Fingerprint: 36:79:ca:35:66:87:72:30:4d:30:a5:fb:87:3b:0f:a7:7b:b7:0d:54\n# SHA256 Fingerprint: 23:99:56:11:27:a5:71:25:de:8c:ef:ea:61:0d:df:2f:a0:78:b5:c8:06:7f:4e:82:82:90:bf:b8:60:e8:4b:3c\n-----BEGIN CERTIFICATE-----\nMIIEuTCCA6GgAwIBAgIQQBrEZCGzEyEDDrvkEhrFHTANBgkqhkiG9w0BAQsFADCB\nvTELMAkGA1UEBhMCVVMxFzAVBgNVBAoTDlZlcmlTaWduLCBJbmMuMR8wHQYDVQQL\nExZWZXJpU2lnbiBUcnVzdCBOZXR3b3JrMTowOAYDVQQLEzEoYykgMjAwOCBWZXJp\nU2lnbiwgSW5jLiAtIEZvciBhdXRob3JpemVkIHVzZSBvbmx5MTgwNgYDVQQDEy9W\nZXJpU2lnbiBVbml2ZXJzYWwgUm9vdCBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0eTAe\nFw0wODA0MDIwMDAwMDBaFw0zNzEyMDEyMzU5NTlaMIG9MQswCQYDVQQGEwJVUzEX\nMBUGA1UEChMOVmVyaVNpZ24sIEluYy4xHzAdBgNVBAsTFlZlcmlTaWduIFRydXN0\nIE5ldHdvcmsxOjA4BgNVBAsTMShjKSAyMDA4IFZlcmlTaWduLCBJbmMuIC0gRm9y\nIGF1dGhvcml6ZWQgdXNlIG9ubHkxODA2BgNVBAMTL1ZlcmlTaWduIFVuaXZlcnNh\nbCBSb290IENlcnRpZmljYXRpb24gQXV0aG9yaXR5MIIBIjANBgkqhkiG9w0BAQEF\nAAOCAQ8AMIIBCgKCAQEAx2E3XrEBNNti1xWb/1hajCMj1mCOkdeQmIN65lgZOIzF\n9uVkhbSicfvtvbnazU0AtMgtc6XHaXGVHzk8skQHnOgO+k1KxCHfKWGPMiJhgsWH\nH26MfF8WIFFE0XBPV+rjHOPMee5Y2A7Cs0WTwCznmhcrewA3ekEzeOEz4vMQGn+H\nLL729fdC4uW/h2KJXwBL38Xd5HVEMkE6HnFuacsLdUYI0crSK5XQz/u5QGtkjFdN\n/BMReYTtXlT2NJ8IAfMQJQYXStrxHXpma5hgZqTZ79IugvHw7wnqRMkVauIDbjPT\nrJ9VAMf2CGqUuV/c4DPxhGD5WycRtPwW8rtWaoAljQIDAQABo4GyMIGvMA8GA1Ud\nEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgEGMG0GCCsGAQUFBwEMBGEwX6FdoFsw\nWTBXMFUWCWltYWdlL2dpZjAhMB8wBwYFKw4DAhoEFI/l0xqGrI2Oa8PPgGrUSBgs\nexkuMCUWI2h0dHA6Ly9sb2dvLnZlcmlzaWduLmNvbS92c2xvZ28uZ2lmMB0GA1Ud\nDgQWBBS2d/ppSEefUxLVwuoHMnYH0ZcHGTANBgkqhkiG9w0BAQsFAAOCAQEASvj4\nsAPmLGd75JR3Y8xuTPl9Dg3cyLk1uXBPY/ok+myDjEedO2Pzmvl2MpWRsXe8rJq+\nseQxIcaBlVZaDrHC1LGmWazxY8u4TB1ZkErvkBYoH1quEPuBUDgMbMzxPcP1Y+Oz\n4yHJJDnp/RVmRvQbEdBNc6N9Rvk97ahfYtTxP/jgdFcrGJ2BtMQo2pSXpXDrrB2+\nBxHw1dvd5Yzw1TKwg+ZX4o+/vqGqvz0dtdQ46tewXDpPaj+PwGZsY6rp2aQW9IHR\nlRQOfc2VNNnSj3BzgXucfr2YYdhFh5iQxeuGMMY1v/D/w1WIg0vvBZIGcfK4mJO3\n7M2CYfE45k+XmCpajQ==\n-----END CERTIFICATE-----\n\n# Issuer: CN=VeriSign Class 3 Public Primary Certification Authority - G4 O=VeriSign, Inc. OU=VeriSign Trust Network/(c) 2007 VeriSign, Inc. - For authorized use only\n# Subject: CN=VeriSign Class 3 Public Primary Certification Authority - G4 O=VeriSign, Inc. OU=VeriSign Trust Network/(c) 2007 VeriSign, Inc. - For authorized use only\n# Label: \"VeriSign Class 3 Public Primary Certification Authority - G4\"\n# Serial: 63143484348153506665311985501458640051\n# MD5 Fingerprint: 3a:52:e1:e7:fd:6f:3a:e3:6f:f3:6f:99:1b:f9:22:41\n# SHA1 Fingerprint: 22:d5:d8:df:8f:02:31:d1:8d:f7:9d:b7:cf:8a:2d:64:c9:3f:6c:3a\n# SHA256 Fingerprint: 69:dd:d7:ea:90:bb:57:c9:3e:13:5d:c8:5e:a6:fc:d5:48:0b:60:32:39:bd:c4:54:fc:75:8b:2a:26:cf:7f:79\n-----BEGIN CERTIFICATE-----\nMIIDhDCCAwqgAwIBAgIQL4D+I4wOIg9IZxIokYesszAKBggqhkjOPQQDAzCByjEL\nMAkGA1UEBhMCVVMxFzAVBgNVBAoTDlZlcmlTaWduLCBJbmMuMR8wHQYDVQQLExZW\nZXJpU2lnbiBUcnVzdCBOZXR3b3JrMTowOAYDVQQLEzEoYykgMjAwNyBWZXJpU2ln\nbiwgSW5jLiAtIEZvciBhdXRob3JpemVkIHVzZSBvbmx5MUUwQwYDVQQDEzxWZXJp\nU2lnbiBDbGFzcyAzIFB1YmxpYyBQcmltYXJ5IENlcnRpZmljYXRpb24gQXV0aG9y\naXR5IC0gRzQwHhcNMDcxMTA1MDAwMDAwWhcNMzgwMTE4MjM1OTU5WjCByjELMAkG\nA1UEBhMCVVMxFzAVBgNVBAoTDlZlcmlTaWduLCBJbmMuMR8wHQYDVQQLExZWZXJp\nU2lnbiBUcnVzdCBOZXR3b3JrMTowOAYDVQQLEzEoYykgMjAwNyBWZXJpU2lnbiwg\nSW5jLiAtIEZvciBhdXRob3JpemVkIHVzZSBvbmx5MUUwQwYDVQQDEzxWZXJpU2ln\nbiBDbGFzcyAzIFB1YmxpYyBQcmltYXJ5IENlcnRpZmljYXRpb24gQXV0aG9yaXR5\nIC0gRzQwdjAQBgcqhkjOPQIBBgUrgQQAIgNiAASnVnp8Utpkmw4tXNherJI9/gHm\nGUo9FANL+mAnINmDiWn6VMaaGF5VKmTeBvaNSjutEDxlPZCIBIngMGGzrl0Bp3ve\nfLK+ymVhAIau2o970ImtTR1ZmkGxvEeA3J5iw/mjgbIwga8wDwYDVR0TAQH/BAUw\nAwEB/zAOBgNVHQ8BAf8EBAMCAQYwbQYIKwYBBQUHAQwEYTBfoV2gWzBZMFcwVRYJ\naW1hZ2UvZ2lmMCEwHzAHBgUrDgMCGgQUj+XTGoasjY5rw8+AatRIGCx7GS4wJRYj\naHR0cDovL2xvZ28udmVyaXNpZ24uY29tL3ZzbG9nby5naWYwHQYDVR0OBBYEFLMW\nkf3upm7ktS5Jj4d4gYDs5bG1MAoGCCqGSM49BAMDA2gAMGUCMGYhDBgmYFo4e1ZC\n4Kf8NoRRkSAsdk1DPcQdhCPQrNZ8NQbOzWm9kA3bbEhCHQ6qQgIxAJw9SDkjOVga\nFRJZap7v1VmyHVIsmXHNxynfGyphe3HR3vPA5Q06Sqotp9iGKt0uEA==\n-----END CERTIFICATE-----\n\n# Issuer: CN=NetLock Arany (Class Gold) F\\u0151tan\\xfas\\xedtv\\xe1ny O=NetLock Kft. OU=Tan\\xfas\\xedtv\\xe1nykiad\\xf3k (Certification Services)\n# Subject: CN=NetLock Arany (Class Gold) F\\u0151tan\\xfas\\xedtv\\xe1ny O=NetLock Kft. OU=Tan\\xfas\\xedtv\\xe1nykiad\\xf3k (Certification Services)\n# Label: \"NetLock Arany (Class Gold) F\\u0151tan\\xfas\\xedtv\\xe1ny\"\n# Serial: 80544274841616\n# MD5 Fingerprint: c5:a1:b7:ff:73:dd:d6:d7:34:32:18:df:fc:3c:ad:88\n# SHA1 Fingerprint: 06:08:3f:59:3f:15:a1:04:a0:69:a4:6b:a9:03:d0:06:b7:97:09:91\n# SHA256 Fingerprint: 6c:61:da:c3:a2:de:f0:31:50:6b:e0:36:d2:a6:fe:40:19:94:fb:d1:3d:f9:c8:d4:66:59:92:74:c4:46:ec:98\n-----BEGIN CERTIFICATE-----\nMIIEFTCCAv2gAwIBAgIGSUEs5AAQMA0GCSqGSIb3DQEBCwUAMIGnMQswCQYDVQQG\nEwJIVTERMA8GA1UEBwwIQnVkYXBlc3QxFTATBgNVBAoMDE5ldExvY2sgS2Z0LjE3\nMDUGA1UECwwuVGFuw7pzw610dsOhbnlraWFkw7NrIChDZXJ0aWZpY2F0aW9uIFNl\ncnZpY2VzKTE1MDMGA1UEAwwsTmV0TG9jayBBcmFueSAoQ2xhc3MgR29sZCkgRsWR\ndGFuw7pzw610dsOhbnkwHhcNMDgxMjExMTUwODIxWhcNMjgxMjA2MTUwODIxWjCB\npzELMAkGA1UEBhMCSFUxETAPBgNVBAcMCEJ1ZGFwZXN0MRUwEwYDVQQKDAxOZXRM\nb2NrIEtmdC4xNzA1BgNVBAsMLlRhbsO6c8OtdHbDoW55a2lhZMOzayAoQ2VydGlm\naWNhdGlvbiBTZXJ2aWNlcykxNTAzBgNVBAMMLE5ldExvY2sgQXJhbnkgKENsYXNz\nIEdvbGQpIEbFkXRhbsO6c8OtdHbDoW55MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8A\nMIIBCgKCAQEAxCRec75LbRTDofTjl5Bu0jBFHjzuZ9lk4BqKf8owyoPjIMHj9DrT\nlF8afFttvzBPhCf2nx9JvMaZCpDyD/V/Q4Q3Y1GLeqVw/HpYzY6b7cNGbIRwXdrz\nAZAj/E4wqX7hJ2Pn7WQ8oLjJM2P+FpD/sLj916jAwJRDC7bVWaaeVtAkH3B5r9s5\nVA1lddkVQZQBr17s9o3x/61k/iCa11zr/qYfCGSji3ZVrR47KGAuhyXoqq8fxmRG\nILdwfzzeSNuWU7c5d+Qa4scWhHaXWy+7GRWF+GmF9ZmnqfI0p6m2pgP8b4Y9VHx2\nBJtr+UBdADTHLpl1neWIA6pN+APSQnbAGwIDAKiLo0UwQzASBgNVHRMBAf8ECDAG\nAQH/AgEEMA4GA1UdDwEB/wQEAwIBBjAdBgNVHQ4EFgQUzPpnk/C2uNClwB7zU/2M\nU9+D15YwDQYJKoZIhvcNAQELBQADggEBAKt/7hwWqZw8UQCgwBEIBaeZ5m8BiFRh\nbvG5GK1Krf6BQCOUL/t1fC8oS2IkgYIL9WHxHG64YTjrgfpioTtaYtOUZcTh5m2C\n+C8lcLIhJsFyUR+MLMOEkMNaj7rP9KdlpeuY0fsFskZ1FSNqb4VjMIDw1Z4fKRzC\nbLBQWV2QWzuoDTDPv31/zvGdg73JRm4gpvlhUbohL3u+pRVjodSVh/GeufOJ8z2F\nuLjbvrW5KfnaNwUASZQDhETnv0Mxz3WLJdH0pmT1kvarBes96aULNmLazAZfNou2\nXjG4Kvte9nHfRCaexOYNkbQudZWAUWpLMKawYqGT8ZvYzsRjdT9ZR7E=\n-----END CERTIFICATE-----\n\n# Issuer: CN=Staat der Nederlanden Root CA - G2 O=Staat der Nederlanden\n# Subject: CN=Staat der Nederlanden Root CA - G2 O=Staat der Nederlanden\n# Label: \"Staat der Nederlanden Root CA - G2\"\n# Serial: 10000012\n# MD5 Fingerprint: 7c:a5:0f:f8:5b:9a:7d:6d:30:ae:54:5a:e3:42:a2:8a\n# SHA1 Fingerprint: 59:af:82:79:91:86:c7:b4:75:07:cb:cf:03:57:46:eb:04:dd:b7:16\n# SHA256 Fingerprint: 66:8c:83:94:7d:a6:3b:72:4b:ec:e1:74:3c:31:a0:e6:ae:d0:db:8e:c5:b3:1b:e3:77:bb:78:4f:91:b6:71:6f\n-----BEGIN CERTIFICATE-----\nMIIFyjCCA7KgAwIBAgIEAJiWjDANBgkqhkiG9w0BAQsFADBaMQswCQYDVQQGEwJO\nTDEeMBwGA1UECgwVU3RhYXQgZGVyIE5lZGVybGFuZGVuMSswKQYDVQQDDCJTdGFh\ndCBkZXIgTmVkZXJsYW5kZW4gUm9vdCBDQSAtIEcyMB4XDTA4MDMyNjExMTgxN1oX\nDTIwMDMyNTExMDMxMFowWjELMAkGA1UEBhMCTkwxHjAcBgNVBAoMFVN0YWF0IGRl\nciBOZWRlcmxhbmRlbjErMCkGA1UEAwwiU3RhYXQgZGVyIE5lZGVybGFuZGVuIFJv\nb3QgQ0EgLSBHMjCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBAMVZ5291\nqj5LnLW4rJ4L5PnZyqtdj7U5EILXr1HgO+EASGrP2uEGQxGZqhQlEq0i6ABtQ8Sp\nuOUfiUtnvWFI7/3S4GCI5bkYYCjDdyutsDeqN95kWSpGV+RLufg3fNU254DBtvPU\nZ5uW6M7XxgpT0GtJlvOjCwV3SPcl5XCsMBQgJeN/dVrlSPhOewMHBPqCYYdu8DvE\npMfQ9XQ+pV0aCPKbJdL2rAQmPlU6Yiile7Iwr/g3wtG61jj99O9JMDeZJiFIhQGp\n5Rbn3JBV3w/oOM2ZNyFPXfUib2rFEhZgF1XyZWampzCROME4HYYEhLoaJXhena/M\nUGDWE4dS7WMfbWV9whUYdMrhfmQpjHLYFhN9C0lK8SgbIHRrxT3dsKpICT0ugpTN\nGmXZK4iambwYfp/ufWZ8Pr2UuIHOzZgweMFvZ9C+X+Bo7d7iscksWXiSqt8rYGPy\n5V6548r6f1CGPqI0GAwJaCgRHOThuVw+R7oyPxjMW4T182t0xHJ04eOLoEq9jWYv\n6q012iDTiIJh8BIitrzQ1aTsr1SIJSQ8p22xcik/Plemf1WvbibG/ufMQFxRRIEK\neN5KzlW/HdXZt1bv8Hb/C3m1r737qWmRRpdogBQ2HbN/uymYNqUg+oJgYjOk7Na6\nB6duxc8UpufWkjTYgfX8HV2qXB72o007uPc5AgMBAAGjgZcwgZQwDwYDVR0TAQH/\nBAUwAwEB/zBSBgNVHSAESzBJMEcGBFUdIAAwPzA9BggrBgEFBQcCARYxaHR0cDov\nL3d3dy5wa2lvdmVyaGVpZC5ubC9wb2xpY2llcy9yb290LXBvbGljeS1HMjAOBgNV\nHQ8BAf8EBAMCAQYwHQYDVR0OBBYEFJFoMocVHYnitfGsNig0jQt8YojrMA0GCSqG\nSIb3DQEBCwUAA4ICAQCoQUpnKpKBglBu4dfYszk78wIVCVBR7y29JHuIhjv5tLyS\nCZa59sCrI2AGeYwRTlHSeYAz+51IvuxBQ4EffkdAHOV6CMqqi3WtFMTC6GY8ggen\n5ieCWxjmD27ZUD6KQhgpxrRW/FYQoAUXvQwjf/ST7ZwaUb7dRUG/kSS0H4zpX897\nIZmflZ85OkYcbPnNe5yQzSipx6lVu6xiNGI1E0sUOlWDuYaNkqbG9AclVMwWVxJK\ngnjIFNkXgiYtXSAfea7+1HAWFpWD2DU5/1JddRwWxRNVz0fMdWVSSt7wsKfkCpYL\n+63C4iWEst3kvX5ZbJvw8NjnyvLplzh+ib7M+zkXYT9y2zqR2GUBGR2tUKRXCnxL\nvJxxcypFURmFzI79R6d0lR2o0a9OF7FpJsKqeFdbxU2n5Z4FF5TKsl+gSRiNNOkm\nbEgeqmiSBeGCc1qb3AdbCG19ndeNIdn8FCCqwkXfP+cAslHkwvgFuXkajDTznlvk\nN1trSt8sV4pAWja63XVECDdCcAz+3F4hoKOKwJCcaNpQ5kUQR3i2TtJlycM33+FC\nY7BXN0Ute4qcvwXqZVUz9zkQxSgqIXobisQk+T8VyJoVIPVVYpbtbZNQvOSqeK3Z\nywplh6ZmwcSBo3c6WB4L7oOLnR7SUqTMHW+wmG2UMbX4cQrcufx9MmDm66+KAQ==\n-----END CERTIFICATE-----\n\n# Issuer: CN=Hongkong Post Root CA 1 O=Hongkong Post\n# Subject: CN=Hongkong Post Root CA 1 O=Hongkong Post\n# Label: \"Hongkong Post Root CA 1\"\n# Serial: 1000\n# MD5 Fingerprint: a8:0d:6f:39:78:b9:43:6d:77:42:6d:98:5a:cc:23:ca\n# SHA1 Fingerprint: d6:da:a8:20:8d:09:d2:15:4d:24:b5:2f:cb:34:6e:b2:58:b2:8a:58\n# SHA256 Fingerprint: f9:e6:7d:33:6c:51:00:2a:c0:54:c6:32:02:2d:66:dd:a2:e7:e3:ff:f1:0a:d0:61:ed:31:d8:bb:b4:10:cf:b2\n-----BEGIN CERTIFICATE-----\nMIIDMDCCAhigAwIBAgICA+gwDQYJKoZIhvcNAQEFBQAwRzELMAkGA1UEBhMCSEsx\nFjAUBgNVBAoTDUhvbmdrb25nIFBvc3QxIDAeBgNVBAMTF0hvbmdrb25nIFBvc3Qg\nUm9vdCBDQSAxMB4XDTAzMDUxNTA1MTMxNFoXDTIzMDUxNTA0NTIyOVowRzELMAkG\nA1UEBhMCSEsxFjAUBgNVBAoTDUhvbmdrb25nIFBvc3QxIDAeBgNVBAMTF0hvbmdr\nb25nIFBvc3QgUm9vdCBDQSAxMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKC\nAQEArP84tulmAknjorThkPlAj3n54r15/gK97iSSHSL22oVyaf7XPwnU3ZG1ApzQ\njVrhVcNQhrkpJsLj2aDxaQMoIIBFIi1WpztUlVYiWR8o3x8gPW2iNr4joLFutbEn\nPzlTCeqrauh0ssJlXI6/fMN4hM2eFvz1Lk8gKgifd/PFHsSaUmYeSF7jEAaPIpjh\nZY4bXSNmO7ilMlHIhqqhqZ5/dpTCpmy3QfDVyAY45tQM4vM7TG1QjMSDJ8EThFk9\nnnV0ttgCXjqQesBCNnLsak3c78QA3xMYV18meMjWCnl3v/evt3a5pQuEF10Q6m/h\nq5URX208o1xNg1vysxmKgIsLhwIDAQABoyYwJDASBgNVHRMBAf8ECDAGAQH/AgED\nMA4GA1UdDwEB/wQEAwIBxjANBgkqhkiG9w0BAQUFAAOCAQEADkbVPK7ih9legYsC\nmEEIjEy82tvuJxuC52pF7BaLT4Wg87JwvVqWuspube5Gi27nKi6Wsxkz67SfqLI3\n7piol7Yutmcn1KZJ/RyTZXaeQi/cImyaT/JaFTmxcdcrUehtHJjA2Sr0oYJ71clB\noiMBdDhViw+5LmeiIAQ32pwL0xch4I+XeTRvhEgCIDMb5jREn5Fw9IBehEPCKdJs\nEhTkYY2sEJCehFC78JZvRZ+K88psT/oROhUVRsPNH4NbLUES7VBnQRM9IauUiqpO\nfMGx+6fWtScvl6tu4B3i0RwsH0Ti/L6RoZz71ilTc4afU9hDDl3WY4JxHYB0yvbi\nAmvZWg==\n-----END CERTIFICATE-----\n\n# Issuer: CN=SecureSign RootCA11 O=Japan Certification Services, Inc.\n# Subject: CN=SecureSign RootCA11 O=Japan Certification Services, Inc.\n# Label: \"SecureSign RootCA11\"\n# Serial: 1\n# MD5 Fingerprint: b7:52:74:e2:92:b4:80:93:f2:75:e4:cc:d7:f2:ea:26\n# SHA1 Fingerprint: 3b:c4:9f:48:f8:f3:73:a0:9c:1e:bd:f8:5b:b1:c3:65:c7:d8:11:b3\n# SHA256 Fingerprint: bf:0f:ee:fb:9e:3a:58:1a:d5:f9:e9:db:75:89:98:57:43:d2:61:08:5c:4d:31:4f:6f:5d:72:59:aa:42:16:12\n-----BEGIN CERTIFICATE-----\nMIIDbTCCAlWgAwIBAgIBATANBgkqhkiG9w0BAQUFADBYMQswCQYDVQQGEwJKUDEr\nMCkGA1UEChMiSmFwYW4gQ2VydGlmaWNhdGlvbiBTZXJ2aWNlcywgSW5jLjEcMBoG\nA1UEAxMTU2VjdXJlU2lnbiBSb290Q0ExMTAeFw0wOTA0MDgwNDU2NDdaFw0yOTA0\nMDgwNDU2NDdaMFgxCzAJBgNVBAYTAkpQMSswKQYDVQQKEyJKYXBhbiBDZXJ0aWZp\nY2F0aW9uIFNlcnZpY2VzLCBJbmMuMRwwGgYDVQQDExNTZWN1cmVTaWduIFJvb3RD\nQTExMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA/XeqpRyQBTvLTJsz\ni1oURaTnkBbR31fSIRCkF/3frNYfp+TbfPfs37gD2pRY/V1yfIw/XwFndBWW4wI8\nh9uuywGOwvNmxoVF9ALGOrVisq/6nL+k5tSAMJjzDbaTj6nU2DbysPyKyiyhFTOV\nMdrAG/LuYpmGYz+/3ZMqg6h2uRMft85OQoWPIucuGvKVCbIFtUROd6EgvanyTgp9\nUK31BQ1FT0Zx/Sg+U/sE2C3XZR1KG/rPO7AxmjVuyIsG0wCR8pQIZUyxNAYAeoni\n8McDWc/V1uinMrPmmECGxc0nEovMe863ETxiYAcjPitAbpSACW22s293bzUIUPsC\nh8U+iQIDAQABo0IwQDAdBgNVHQ4EFgQUW/hNT7KlhtQ60vFjmqC+CfZXt94wDgYD\nVR0PAQH/BAQDAgEGMA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZIhvcNAQEFBQADggEB\nAKChOBZmLqdWHyGcBvod7bkixTgm2E5P7KN/ed5GIaGHd48HCJqypMWvDzKYC3xm\nKbabfSVSSUOrTC4rbnpwrxYO4wJs+0LmGJ1F2FXI6Dvd5+H0LgscNFxsWEr7jIhQ\nX5Ucv+2rIrVls4W6ng+4reV6G4pQOh29Dbx7VFALuUKvVaAYga1lme++5Jy/xIWr\nQbJUb9wlze144o4MjQlJ3WN7WmmWAiGovVJZ6X01y8hSyn+B/tlr0/cR7SXf+Of5\npPpyl4RTDaXQMhhRdlkUbA/r7F+AjHVDg8OFmP9Mni0N5HeDk061lgeLKBObjBmN\nQSdJQO7e5iNEOdyhIta6A/I=\n-----END CERTIFICATE-----\n\n# Issuer: CN=Microsec e-Szigno Root CA 2009 O=Microsec Ltd.\n# Subject: CN=Microsec e-Szigno Root CA 2009 O=Microsec Ltd.\n# Label: \"Microsec e-Szigno Root CA 2009\"\n# Serial: 14014712776195784473\n# MD5 Fingerprint: f8:49:f4:03:bc:44:2d:83:be:48:69:7d:29:64:fc:b1\n# SHA1 Fingerprint: 89:df:74:fe:5c:f4:0f:4a:80:f9:e3:37:7d:54:da:91:e1:01:31:8e\n# SHA256 Fingerprint: 3c:5f:81:fe:a5:fa:b8:2c:64:bf:a2:ea:ec:af:cd:e8:e0:77:fc:86:20:a7:ca:e5:37:16:3d:f3:6e:db:f3:78\n-----BEGIN CERTIFICATE-----\nMIIECjCCAvKgAwIBAgIJAMJ+QwRORz8ZMA0GCSqGSIb3DQEBCwUAMIGCMQswCQYD\nVQQGEwJIVTERMA8GA1UEBwwIQnVkYXBlc3QxFjAUBgNVBAoMDU1pY3Jvc2VjIEx0\nZC4xJzAlBgNVBAMMHk1pY3Jvc2VjIGUtU3ppZ25vIFJvb3QgQ0EgMjAwOTEfMB0G\nCSqGSIb3DQEJARYQaW5mb0BlLXN6aWduby5odTAeFw0wOTA2MTYxMTMwMThaFw0y\nOTEyMzAxMTMwMThaMIGCMQswCQYDVQQGEwJIVTERMA8GA1UEBwwIQnVkYXBlc3Qx\nFjAUBgNVBAoMDU1pY3Jvc2VjIEx0ZC4xJzAlBgNVBAMMHk1pY3Jvc2VjIGUtU3pp\nZ25vIFJvb3QgQ0EgMjAwOTEfMB0GCSqGSIb3DQEJARYQaW5mb0BlLXN6aWduby5o\ndTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAOn4j/NjrdqG2KfgQvvP\nkd6mJviZpWNwrZuuyjNAfW2WbqEORO7hE52UQlKavXWFdCyoDh2Tthi3jCyoz/tc\ncbna7P7ofo/kLx2yqHWH2Leh5TvPmUpG0IMZfcChEhyVbUr02MelTTMuhTlAdX4U\nfIASmFDHQWe4oIBhVKZsTh/gnQ4H6cm6M+f+wFUoLAKApxn1ntxVUwOXewdI/5n7\nN4okxFnMUBBjjqqpGrCEGob5X7uxUG6k0QrM1XF+H6cbfPVTbiJfyyvm1HxdrtbC\nxkzlBQHZ7Vf8wSN5/PrIJIOV87VqUQHQd9bpEqH5GoP7ghu5sJf0dgYzQ0mg/wu1\n+rUCAwEAAaOBgDB+MA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgEGMB0G\nA1UdDgQWBBTLD8bfQkPMPcu1SCOhGnqmKrs0aDAfBgNVHSMEGDAWgBTLD8bfQkPM\nPcu1SCOhGnqmKrs0aDAbBgNVHREEFDASgRBpbmZvQGUtc3ppZ25vLmh1MA0GCSqG\nSIb3DQEBCwUAA4IBAQDJ0Q5eLtXMs3w+y/w9/w0olZMEyL/azXm4Q5DwpL7v8u8h\nmLzU1F0G9u5C7DBsoKqpyvGvivo/C3NqPuouQH4frlRheesuCDfXI/OMn74dseGk\nddug4lQUsbocKaQY9hK6ohQU4zE1yED/t+AFdlfBHFny+L/k7SViXITwfn4fs775\ntyERzAMBVnCnEJIeGzSBHq2cGsMEPO0CYdYeBvNfOofyK/FFh+U9rNHHV4S9a67c\n2Pm2G2JwCz02yULyMtd6YebS2z3PyKnJm9zbWETXbzivf3jTo60adbocwTZ8jx5t\nHMN1Rq41Bab2XD0h7lbwyYIiLXpUq3DDfSJlgnCW\n-----END CERTIFICATE-----\n\n# Issuer: CN=GlobalSign O=GlobalSign OU=GlobalSign Root CA - R3\n# Subject: CN=GlobalSign O=GlobalSign OU=GlobalSign Root CA - R3\n# Label: \"GlobalSign Root CA - R3\"\n# Serial: 4835703278459759426209954\n# MD5 Fingerprint: c5:df:b8:49:ca:05:13:55:ee:2d:ba:1a:c3:3e:b0:28\n# SHA1 Fingerprint: d6:9b:56:11:48:f0:1c:77:c5:45:78:c1:09:26:df:5b:85:69:76:ad\n# SHA256 Fingerprint: cb:b5:22:d7:b7:f1:27:ad:6a:01:13:86:5b:df:1c:d4:10:2e:7d:07:59:af:63:5a:7c:f4:72:0d:c9:63:c5:3b\n-----BEGIN CERTIFICATE-----\nMIIDXzCCAkegAwIBAgILBAAAAAABIVhTCKIwDQYJKoZIhvcNAQELBQAwTDEgMB4G\nA1UECxMXR2xvYmFsU2lnbiBSb290IENBIC0gUjMxEzARBgNVBAoTCkdsb2JhbFNp\nZ24xEzARBgNVBAMTCkdsb2JhbFNpZ24wHhcNMDkwMzE4MTAwMDAwWhcNMjkwMzE4\nMTAwMDAwWjBMMSAwHgYDVQQLExdHbG9iYWxTaWduIFJvb3QgQ0EgLSBSMzETMBEG\nA1UEChMKR2xvYmFsU2lnbjETMBEGA1UEAxMKR2xvYmFsU2lnbjCCASIwDQYJKoZI\nhvcNAQEBBQADggEPADCCAQoCggEBAMwldpB5BngiFvXAg7aEyiie/QV2EcWtiHL8\nRgJDx7KKnQRfJMsuS+FggkbhUqsMgUdwbN1k0ev1LKMPgj0MK66X17YUhhB5uzsT\ngHeMCOFJ0mpiLx9e+pZo34knlTifBtc+ycsmWQ1z3rDI6SYOgxXG71uL0gRgykmm\nKPZpO/bLyCiR5Z2KYVc3rHQU3HTgOu5yLy6c+9C7v/U9AOEGM+iCK65TpjoWc4zd\nQQ4gOsC0p6Hpsk+QLjJg6VfLuQSSaGjlOCZgdbKfd/+RFO+uIEn8rUAVSNECMWEZ\nXriX7613t2Saer9fwRPvm2L7DWzgVGkWqQPabumDk3F2xmmFghcCAwEAAaNCMEAw\nDgYDVR0PAQH/BAQDAgEGMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFI/wS3+o\nLkUkrk1Q+mOai97i3Ru8MA0GCSqGSIb3DQEBCwUAA4IBAQBLQNvAUKr+yAzv95ZU\nRUm7lgAJQayzE4aGKAczymvmdLm6AC2upArT9fHxD4q/c2dKg8dEe3jgr25sbwMp\njjM5RcOO5LlXbKr8EpbsU8Yt5CRsuZRj+9xTaGdWPoO4zzUhw8lo/s7awlOqzJCK\n6fBdRoyV3XpYKBovHd7NADdBj+1EbddTKJd+82cEHhXXipa0095MJ6RMG3NzdvQX\nmcIfeg7jLQitChws/zyrVQ4PkX4268NXSb7hLi18YIvDQVETI53O9zJrlAGomecs\nMx86OyXShkDOOyyGeMlhLxS67ttVb9+E7gUJTb0o2HLO02JQZR7rkpeDMdmztcpH\nWD9f\n-----END CERTIFICATE-----\n\n# Issuer: CN=Autoridad de Certificacion Firmaprofesional CIF A62634068\n# Subject: CN=Autoridad de Certificacion Firmaprofesional CIF A62634068\n# Label: \"Autoridad de Certificacion Firmaprofesional CIF A62634068\"\n# Serial: 6047274297262753887\n# MD5 Fingerprint: 73:3a:74:7a:ec:bb:a3:96:a6:c2:e4:e2:c8:9b:c0:c3\n# SHA1 Fingerprint: ae:c5:fb:3f:c8:e1:bf:c4:e5:4f:03:07:5a:9a:e8:00:b7:f7:b6:fa\n# SHA256 Fingerprint: 04:04:80:28:bf:1f:28:64:d4:8f:9a:d4:d8:32:94:36:6a:82:88:56:55:3f:3b:14:30:3f:90:14:7f:5d:40:ef\n-----BEGIN CERTIFICATE-----\nMIIGFDCCA/ygAwIBAgIIU+w77vuySF8wDQYJKoZIhvcNAQEFBQAwUTELMAkGA1UE\nBhMCRVMxQjBABgNVBAMMOUF1dG9yaWRhZCBkZSBDZXJ0aWZpY2FjaW9uIEZpcm1h\ncHJvZmVzaW9uYWwgQ0lGIEE2MjYzNDA2ODAeFw0wOTA1MjAwODM4MTVaFw0zMDEy\nMzEwODM4MTVaMFExCzAJBgNVBAYTAkVTMUIwQAYDVQQDDDlBdXRvcmlkYWQgZGUg\nQ2VydGlmaWNhY2lvbiBGaXJtYXByb2Zlc2lvbmFsIENJRiBBNjI2MzQwNjgwggIi\nMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQDKlmuO6vj78aI14H9M2uDDUtd9\nthDIAl6zQyrET2qyyhxdKJp4ERppWVevtSBC5IsP5t9bpgOSL/UR5GLXMnE42QQM\ncas9UX4PB99jBVzpv5RvwSmCwLTaUbDBPLutN0pcyvFLNg4kq7/DhHf9qFD0sefG\nL9ItWY16Ck6WaVICqjaY7Pz6FIMMNx/Jkjd/14Et5cS54D40/mf0PmbR0/RAz15i\nNA9wBj4gGFrO93IbJWyTdBSTo3OxDqqHECNZXyAFGUftaI6SEspd/NYrspI8IM/h\nX68gvqB2f3bl7BqGYTM+53u0P6APjqK5am+5hyZvQWyIplD9amML9ZMWGxmPsu2b\nm8mQ9QEM3xk9Dz44I8kvjwzRAv4bVdZO0I08r0+k8/6vKtMFnXkIoctXMbScyJCy\nZ/QYFpM6/EfY0XiWMR+6KwxfXZmtY4laJCB22N/9q06mIqqdXuYnin1oKaPnirja\nEbsXLZmdEyRG98Xi2J+Of8ePdG1asuhy9azuJBCtLxTa/y2aRnFHvkLfuwHb9H/T\nKI8xWVvTyQKmtFLKbpf7Q8UIJm+K9Lv9nyiqDdVF8xM6HdjAeI9BZzwelGSuewvF\n6NkBiDkal4ZkQdU7hwxu+g/GvUgUvzlN1J5Bto+WHWOWk9mVBngxaJ43BjuAiUVh\nOSPHG0SjFeUc+JIwuwIDAQABo4HvMIHsMBIGA1UdEwEB/wQIMAYBAf8CAQEwDgYD\nVR0PAQH/BAQDAgEGMB0GA1UdDgQWBBRlzeurNR4APn7VdMActHNHDhpkLzCBpgYD\nVR0gBIGeMIGbMIGYBgRVHSAAMIGPMC8GCCsGAQUFBwIBFiNodHRwOi8vd3d3LmZp\ncm1hcHJvZmVzaW9uYWwuY29tL2NwczBcBggrBgEFBQcCAjBQHk4AUABhAHMAZQBv\nACAAZABlACAAbABhACAAQgBvAG4AYQBuAG8AdgBhACAANAA3ACAAQgBhAHIAYwBl\nAGwAbwBuAGEAIAAwADgAMAAxADcwDQYJKoZIhvcNAQEFBQADggIBABd9oPm03cXF\n661LJLWhAqvdpYhKsg9VSytXjDvlMd3+xDLx51tkljYyGOylMnfX40S2wBEqgLk9\nam58m9Ot/MPWo+ZkKXzR4Tgegiv/J2Wv+xYVxC5xhOW1//qkR71kMrv2JYSiJ0L1\nILDCExARzRAVukKQKtJE4ZYm6zFIEv0q2skGz3QeqUvVhyj5eTSSPi5E6PaPT481\nPyWzOdxjKpBrIF/EUhJOlywqrJ2X3kjyo2bbwtKDlaZmp54lD+kLM5FlClrD2VQS\n3a/DTg4fJl4N3LON7NWBcN7STyQF82xO9UxJZo3R/9ILJUFI/lGExkKvgATP0H5k\nSeTy36LssUzAKh3ntLFlosS88Zj0qnAHY7S42jtM+kAiMFsRpvAFDsYCA0irhpuF\n3dvd6qJ2gHN99ZwExEWN57kci57q13XRcrHedUTnQn3iV2t93Jm8PYMo6oCTjcVM\nZcFwgbg4/EMxsvYDNEeyrPsiBsse3RdHHF9mudMaotoRsaS8I8nkvof/uZS2+F0g\nStRf571oe2XyFR7SOqkt6dhrJKyXWERHrVkY8SFlcN7ONGCoQPHzPKTDKCOM/icz\nQ0CgFzzr6juwcqajuUpLXhZI9LK8yIySxZ2frHI2vDSANGupi5LAuBft7HZT9SQB\njLMi6Et8Vcad+qMUu2WFbm5PEn4KPJ2V\n-----END CERTIFICATE-----\n\n# Issuer: CN=Izenpe.com O=IZENPE S.A.\n# Subject: CN=Izenpe.com O=IZENPE S.A.\n# Label: \"Izenpe.com\"\n# Serial: 917563065490389241595536686991402621\n# MD5 Fingerprint: a6:b0:cd:85:80:da:5c:50:34:a3:39:90:2f:55:67:73\n# SHA1 Fingerprint: 2f:78:3d:25:52:18:a7:4a:65:39:71:b5:2c:a2:9c:45:15:6f:e9:19\n# SHA256 Fingerprint: 25:30:cc:8e:98:32:15:02:ba:d9:6f:9b:1f:ba:1b:09:9e:2d:29:9e:0f:45:48:bb:91:4f:36:3b:c0:d4:53:1f\n-----BEGIN CERTIFICATE-----\nMIIF8TCCA9mgAwIBAgIQALC3WhZIX7/hy/WL1xnmfTANBgkqhkiG9w0BAQsFADA4\nMQswCQYDVQQGEwJFUzEUMBIGA1UECgwLSVpFTlBFIFMuQS4xEzARBgNVBAMMCkl6\nZW5wZS5jb20wHhcNMDcxMjEzMTMwODI4WhcNMzcxMjEzMDgyNzI1WjA4MQswCQYD\nVQQGEwJFUzEUMBIGA1UECgwLSVpFTlBFIFMuQS4xEzARBgNVBAMMCkl6ZW5wZS5j\nb20wggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQDJ03rKDx6sp4boFmVq\nscIbRTJxldn+EFvMr+eleQGPicPK8lVx93e+d5TzcqQsRNiekpsUOqHnJJAKClaO\nxdgmlOHZSOEtPtoKct2jmRXagaKH9HtuJneJWK3W6wyyQXpzbm3benhB6QiIEn6H\nLmYRY2xU+zydcsC8Lv/Ct90NduM61/e0aL6i9eOBbsFGb12N4E3GVFWJGjMxCrFX\nuaOKmMPsOzTFlUFpfnXCPCDFYbpRR6AgkJOhkEvzTnyFRVSa0QUmQbC1TR0zvsQD\nyCV8wXDbO/QJLVQnSKwv4cSsPsjLkkxTOTcj7NMB+eAJRE1NZMDhDVqHIrytG6P+\nJrUV86f8hBnp7KGItERphIPzidF0BqnMC9bC3ieFUCbKF7jJeodWLBoBHmy+E60Q\nrLUk9TiRodZL2vG70t5HtfG8gfZZa88ZU+mNFctKy6lvROUbQc/hhqfK0GqfvEyN\nBjNaooXlkDWgYlwWTvDjovoDGrQscbNYLN57C9saD+veIR8GdwYDsMnvmfzAuU8L\nhij+0rnq49qlw0dpEuDb8PYZi+17cNcC1u2HGCgsBCRMd+RIihrGO5rUD8r6ddIB\nQFqNeb+Lz0vPqhbBleStTIo+F5HUsWLlguWABKQDfo2/2n+iD5dPDNMN+9fR5XJ+\nHMh3/1uaD7euBUbl8agW7EekFwIDAQABo4H2MIHzMIGwBgNVHREEgagwgaWBD2lu\nZm9AaXplbnBlLmNvbaSBkTCBjjFHMEUGA1UECgw+SVpFTlBFIFMuQS4gLSBDSUYg\nQTAxMzM3MjYwLVJNZXJjLlZpdG9yaWEtR2FzdGVpeiBUMTA1NSBGNjIgUzgxQzBB\nBgNVBAkMOkF2ZGEgZGVsIE1lZGl0ZXJyYW5lbyBFdG9yYmlkZWEgMTQgLSAwMTAx\nMCBWaXRvcmlhLUdhc3RlaXowDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMC\nAQYwHQYDVR0OBBYEFB0cZQ6o8iV7tJHP5LGx5r1VdGwFMA0GCSqGSIb3DQEBCwUA\nA4ICAQB4pgwWSp9MiDrAyw6lFn2fuUhfGI8NYjb2zRlrrKvV9pF9rnHzP7MOeIWb\nlaQnIUdCSnxIOvVFfLMMjlF4rJUT3sb9fbgakEyrkgPH7UIBzg/YsfqikuFgba56\nawmqxinuaElnMIAkejEWOVt+8Rwu3WwJrfIxwYJOubv5vr8qhT/AQKM6WfxZSzwo\nJNu0FXWuDYi6LnPAvViH5ULy617uHjAimcs30cQhbIHsvm0m5hzkQiCeR7Csg1lw\nLDXWrzY0tM07+DKo7+N4ifuNRSzanLh+QBxh5z6ikixL8s36mLYp//Pye6kfLqCT\nVyvehQP5aTfLnnhqBbTFMXiJ7HqnheG5ezzevh55hM6fcA5ZwjUukCox2eRFekGk\nLhObNA5me0mrZJfQRsN5nXJQY6aYWwa9SG3YOYNw6DXwBdGqvOPbyALqfP2C2sJb\nUjWumDqtujWTI6cfSN01RpiyEGjkpTHCClguGYEQyVB1/OpaFs4R1+7vUIgtYf8/\nQnMFlEPVjjxOAToZpR9GTnfQXeWBIiGH/pR9hNiTrdZoQ0iy2+tzJOeRf1SktoA+\nnaM8THLCV8Sg1Mw4J87VBp6iSNnpn86CcDaTmjvfliHjWbcM2pE38P1ZWrOZyGls\nQyYBNWNgVYkDOnXYukrZVP/u3oDYLdE41V4tC5h9Pmzb/CaIxw==\n-----END CERTIFICATE-----\n\n# Issuer: CN=Chambers of Commerce Root - 2008 O=AC Camerfirma S.A.\n# Subject: CN=Chambers of Commerce Root - 2008 O=AC Camerfirma S.A.\n# Label: \"Chambers of Commerce Root - 2008\"\n# Serial: 11806822484801597146\n# MD5 Fingerprint: 5e:80:9e:84:5a:0e:65:0b:17:02:f3:55:18:2a:3e:d7\n# SHA1 Fingerprint: 78:6a:74:ac:76:ab:14:7f:9c:6a:30:50:ba:9e:a8:7e:fe:9a:ce:3c\n# SHA256 Fingerprint: 06:3e:4a:fa:c4:91:df:d3:32:f3:08:9b:85:42:e9:46:17:d8:93:d7:fe:94:4e:10:a7:93:7e:e2:9d:96:93:c0\n-----BEGIN CERTIFICATE-----\nMIIHTzCCBTegAwIBAgIJAKPaQn6ksa7aMA0GCSqGSIb3DQEBBQUAMIGuMQswCQYD\nVQQGEwJFVTFDMEEGA1UEBxM6TWFkcmlkIChzZWUgY3VycmVudCBhZGRyZXNzIGF0\nIHd3dy5jYW1lcmZpcm1hLmNvbS9hZGRyZXNzKTESMBAGA1UEBRMJQTgyNzQzMjg3\nMRswGQYDVQQKExJBQyBDYW1lcmZpcm1hIFMuQS4xKTAnBgNVBAMTIENoYW1iZXJz\nIG9mIENvbW1lcmNlIFJvb3QgLSAyMDA4MB4XDTA4MDgwMTEyMjk1MFoXDTM4MDcz\nMTEyMjk1MFowga4xCzAJBgNVBAYTAkVVMUMwQQYDVQQHEzpNYWRyaWQgKHNlZSBj\ndXJyZW50IGFkZHJlc3MgYXQgd3d3LmNhbWVyZmlybWEuY29tL2FkZHJlc3MpMRIw\nEAYDVQQFEwlBODI3NDMyODcxGzAZBgNVBAoTEkFDIENhbWVyZmlybWEgUy5BLjEp\nMCcGA1UEAxMgQ2hhbWJlcnMgb2YgQ29tbWVyY2UgUm9vdCAtIDIwMDgwggIiMA0G\nCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQCvAMtwNyuAWko6bHiUfaN/Gh/2NdW9\n28sNRHI+JrKQUrpjOyhYb6WzbZSm891kDFX29ufyIiKAXuFixrYp4YFs8r/lfTJq\nVKAyGVn+H4vXPWCGhSRv4xGzdz4gljUha7MI2XAuZPeEklPWDrCQiorjh40G072Q\nDuKZoRuGDtqaCrsLYVAGUvGef3bsyw/QHg3PmTA9HMRFEFis1tPo1+XqxQEHd9ZR\n5gN/ikilTWh1uem8nk4ZcfUyS5xtYBkL+8ydddy/Js2Pk3g5eXNeJQ7KXOt3EgfL\nZEFHcpOrUMPrCXZkNNI5t3YRCQ12RcSprj1qr7V9ZS+UWBDsXHyvfuK2GNnQm05a\nSd+pZgvMPMZ4fKecHePOjlO+Bd5gD2vlGts/4+EhySnB8esHnFIbAURRPHsl18Tl\nUlRdJQfKFiC4reRB7noI/plvg6aRArBsNlVq5331lubKgdaX8ZSD6e2wsWsSaR6s\n+12pxZjptFtYer49okQ6Y1nUCyXeG0+95QGezdIp1Z8XGQpvvwyQ0wlf2eOKNcx5\nWk0ZN5K3xMGtr/R5JJqyAQuxr1yW84Ay+1w9mPGgP0revq+ULtlVmhduYJ1jbLhj\nya6BXBg14JC7vjxPNyK5fuvPnnchpj04gftI2jE9K+OJ9dC1vX7gUMQSibMjmhAx\nhduub+84Mxh2EQIDAQABo4IBbDCCAWgwEgYDVR0TAQH/BAgwBgEB/wIBDDAdBgNV\nHQ4EFgQU+SSsD7K1+HnA+mCIG8TZTQKeFxkwgeMGA1UdIwSB2zCB2IAU+SSsD7K1\n+HnA+mCIG8TZTQKeFxmhgbSkgbEwga4xCzAJBgNVBAYTAkVVMUMwQQYDVQQHEzpN\nYWRyaWQgKHNlZSBjdXJyZW50IGFkZHJlc3MgYXQgd3d3LmNhbWVyZmlybWEuY29t\nL2FkZHJlc3MpMRIwEAYDVQQFEwlBODI3NDMyODcxGzAZBgNVBAoTEkFDIENhbWVy\nZmlybWEgUy5BLjEpMCcGA1UEAxMgQ2hhbWJlcnMgb2YgQ29tbWVyY2UgUm9vdCAt\nIDIwMDiCCQCj2kJ+pLGu2jAOBgNVHQ8BAf8EBAMCAQYwPQYDVR0gBDYwNDAyBgRV\nHSAAMCowKAYIKwYBBQUHAgEWHGh0dHA6Ly9wb2xpY3kuY2FtZXJmaXJtYS5jb20w\nDQYJKoZIhvcNAQEFBQADggIBAJASryI1wqM58C7e6bXpeHxIvj99RZJe6dqxGfwW\nPJ+0W2aeaufDuV2I6A+tzyMP3iU6XsxPpcG1Lawk0lgH3qLPaYRgM+gQDROpI9CF\n5Y57pp49chNyM/WqfcZjHwj0/gF/JM8rLFQJ3uIrbZLGOU8W6jx+ekbURWpGqOt1\nglanq6B8aBMz9p0w8G8nOSQjKpD9kCk18pPfNKXG9/jvjA9iSnyu0/VU+I22mlaH\nFoI6M6taIgj3grrqLuBHmrS1RaMFO9ncLkVAO+rcf+g769HsJtg1pDDFOqxXnrN2\npSB7+R5KBWIBpih1YJeSDW4+TTdDDZIVnBgizVGZoCkaPF+KMjNbMMeJL0eYD6MD\nxvbxrN8y8NmBGuScvfaAFPDRLLmF9dijscilIeUcE5fuDr3fKanvNFNb0+RqE4QG\ntjICxFKuItLcsiFCGtpA8CnJ7AoMXOLQusxI0zcKzBIKinmwPQN/aUv0NCB9szTq\njktk9T79syNnFQ0EuPAtwQlRPLJsFfClI9eDdOTlLsn+mCdCxqvGnrDQWzilm1De\nfhiYtUU79nm06PcaewaD+9CL2rvHvRirCG88gGtAPxkZumWK5r7VXNM21+9AUiRg\nOGcEMeyP84LG3rlV8zsxkVrctQgVrXYlCg17LofiDKYGvCYQbTed7N14jHyAxfDZ\nd0jQ\n-----END CERTIFICATE-----\n\n# Issuer: CN=Global Chambersign Root - 2008 O=AC Camerfirma S.A.\n# Subject: CN=Global Chambersign Root - 2008 O=AC Camerfirma S.A.\n# Label: \"Global Chambersign Root - 2008\"\n# Serial: 14541511773111788494\n# MD5 Fingerprint: 9e:80:ff:78:01:0c:2e:c1:36:bd:fe:96:90:6e:08:f3\n# SHA1 Fingerprint: 4a:bd:ee:ec:95:0d:35:9c:89:ae:c7:52:a1:2c:5b:29:f6:d6:aa:0c\n# SHA256 Fingerprint: 13:63:35:43:93:34:a7:69:80:16:a0:d3:24:de:72:28:4e:07:9d:7b:52:20:bb:8f:bd:74:78:16:ee:be:ba:ca\n-----BEGIN CERTIFICATE-----\nMIIHSTCCBTGgAwIBAgIJAMnN0+nVfSPOMA0GCSqGSIb3DQEBBQUAMIGsMQswCQYD\nVQQGEwJFVTFDMEEGA1UEBxM6TWFkcmlkIChzZWUgY3VycmVudCBhZGRyZXNzIGF0\nIHd3dy5jYW1lcmZpcm1hLmNvbS9hZGRyZXNzKTESMBAGA1UEBRMJQTgyNzQzMjg3\nMRswGQYDVQQKExJBQyBDYW1lcmZpcm1hIFMuQS4xJzAlBgNVBAMTHkdsb2JhbCBD\naGFtYmVyc2lnbiBSb290IC0gMjAwODAeFw0wODA4MDExMjMxNDBaFw0zODA3MzEx\nMjMxNDBaMIGsMQswCQYDVQQGEwJFVTFDMEEGA1UEBxM6TWFkcmlkIChzZWUgY3Vy\ncmVudCBhZGRyZXNzIGF0IHd3dy5jYW1lcmZpcm1hLmNvbS9hZGRyZXNzKTESMBAG\nA1UEBRMJQTgyNzQzMjg3MRswGQYDVQQKExJBQyBDYW1lcmZpcm1hIFMuQS4xJzAl\nBgNVBAMTHkdsb2JhbCBDaGFtYmVyc2lnbiBSb290IC0gMjAwODCCAiIwDQYJKoZI\nhvcNAQEBBQADggIPADCCAgoCggIBAMDfVtPkOpt2RbQT2//BthmLN0EYlVJH6xed\nKYiONWwGMi5HYvNJBL99RDaxccy9Wglz1dmFRP+RVyXfXjaOcNFccUMd2drvXNL7\nG706tcuto8xEpw2uIRU/uXpbknXYpBI4iRmKt4DS4jJvVpyR1ogQC7N0ZJJ0YPP2\nzxhPYLIj0Mc7zmFLmY/CDNBAspjcDahOo7kKrmCgrUVSY7pmvWjg+b4aqIG7HkF4\nddPB/gBVsIdU6CeQNR1MM62X/JcumIS/LMmjv9GYERTtY/jKmIhYF5ntRQOXfjyG\nHoiMvvKRhI9lNNgATH23MRdaKXoKGCQwoze1eqkBfSbW+Q6OWfH9GzO1KTsXO0G2\nId3UwD2ln58fQ1DJu7xsepeY7s2MH/ucUa6LcL0nn3HAa6x9kGbo1106DbDVwo3V\nyJ2dwW3Q0L9R5OP4wzg2rtandeavhENdk5IMagfeOx2YItaswTXbo6Al/3K1dh3e\nbeksZixShNBFks4c5eUzHdwHU1SjqoI7mjcv3N2gZOnm3b2u/GSFHTynyQbehP9r\n6GsaPMWis0L7iwk+XwhSx2LE1AVxv8Rk5Pihg+g+EpuoHtQ2TS9x9o0o9oOpE9Jh\nwZG7SMA0j0GMS0zbaRL/UJScIINZc+18ofLx/d33SdNDWKBWY8o9PeU1VlnpDsog\nzCtLkykPAgMBAAGjggFqMIIBZjASBgNVHRMBAf8ECDAGAQH/AgEMMB0GA1UdDgQW\nBBS5CcqcHtvTbDprru1U8VuTBjUuXjCB4QYDVR0jBIHZMIHWgBS5CcqcHtvTbDpr\nru1U8VuTBjUuXqGBsqSBrzCBrDELMAkGA1UEBhMCRVUxQzBBBgNVBAcTOk1hZHJp\nZCAoc2VlIGN1cnJlbnQgYWRkcmVzcyBhdCB3d3cuY2FtZXJmaXJtYS5jb20vYWRk\ncmVzcykxEjAQBgNVBAUTCUE4Mjc0MzI4NzEbMBkGA1UEChMSQUMgQ2FtZXJmaXJt\nYSBTLkEuMScwJQYDVQQDEx5HbG9iYWwgQ2hhbWJlcnNpZ24gUm9vdCAtIDIwMDiC\nCQDJzdPp1X0jzjAOBgNVHQ8BAf8EBAMCAQYwPQYDVR0gBDYwNDAyBgRVHSAAMCow\nKAYIKwYBBQUHAgEWHGh0dHA6Ly9wb2xpY3kuY2FtZXJmaXJtYS5jb20wDQYJKoZI\nhvcNAQEFBQADggIBAICIf3DekijZBZRG/5BXqfEv3xoNa/p8DhxJJHkn2EaqbylZ\nUohwEurdPfWbU1Rv4WCiqAm57OtZfMY18dwY6fFn5a+6ReAJ3spED8IXDneRRXoz\nX1+WLGiLwUePmJs9wOzL9dWCkoQ10b42OFZyMVtHLaoXpGNR6woBrX/sdZ7LoR/x\nfxKxueRkf2fWIyr0uDldmOghp+G9PUIadJpwr2hsUF1Jz//7Dl3mLEfXgTpZALVz\na2Mg9jFFCDkO9HB+QHBaP9BrQql0PSgvAm11cpUJjUhjxsYjV5KTXjXBjfkK9yyd\nYhz2rXzdpjEetrHHfoUm+qRqtdpjMNHvkzeyZi99Bffnt0uYlDXA2TopwZ2yUDMd\nSqlapskD7+3056huirRXhOukP9DuqqqHW2Pok+JrqNS4cnhrG+055F3Lm6qH1U9O\nAP7Zap88MQ8oAgF9mOinsKJknnn4SPIVqczmyETrP3iZ8ntxPjzxmKfFGBI/5rso\nM0LpRQp8bfKGeS/Fghl9CYl8slR2iK7ewfPM4W7bMdaTrpmg7yVqc5iJWzouE4ge\nv8CSlDQb4ye3ix5vQv/n6TebUB0tovkC7stYWDpxvGjjqsGvHCgfotwjZT+B6q6Z\n09gwzxMNTxXJhLynSC34MCN32EZLeW32jO06f2ARePTpm67VVMB0gNELQp/B\n-----END CERTIFICATE-----\n\n# Issuer: CN=Go Daddy Root Certificate Authority - G2 O=GoDaddy.com, Inc.\n# Subject: CN=Go Daddy Root Certificate Authority - G2 O=GoDaddy.com, Inc.\n# Label: \"Go Daddy Root Certificate Authority - G2\"\n# Serial: 0\n# MD5 Fingerprint: 80:3a:bc:22:c1:e6:fb:8d:9b:3b:27:4a:32:1b:9a:01\n# SHA1 Fingerprint: 47:be:ab:c9:22:ea:e8:0e:78:78:34:62:a7:9f:45:c2:54:fd:e6:8b\n# SHA256 Fingerprint: 45:14:0b:32:47:eb:9c:c8:c5:b4:f0:d7:b5:30:91:f7:32:92:08:9e:6e:5a:63:e2:74:9d:d3:ac:a9:19:8e:da\n-----BEGIN CERTIFICATE-----\nMIIDxTCCAq2gAwIBAgIBADANBgkqhkiG9w0BAQsFADCBgzELMAkGA1UEBhMCVVMx\nEDAOBgNVBAgTB0FyaXpvbmExEzARBgNVBAcTClNjb3R0c2RhbGUxGjAYBgNVBAoT\nEUdvRGFkZHkuY29tLCBJbmMuMTEwLwYDVQQDEyhHbyBEYWRkeSBSb290IENlcnRp\nZmljYXRlIEF1dGhvcml0eSAtIEcyMB4XDTA5MDkwMTAwMDAwMFoXDTM3MTIzMTIz\nNTk1OVowgYMxCzAJBgNVBAYTAlVTMRAwDgYDVQQIEwdBcml6b25hMRMwEQYDVQQH\nEwpTY290dHNkYWxlMRowGAYDVQQKExFHb0RhZGR5LmNvbSwgSW5jLjExMC8GA1UE\nAxMoR28gRGFkZHkgUm9vdCBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkgLSBHMjCCASIw\nDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAL9xYgjx+lk09xvJGKP3gElY6SKD\nE6bFIEMBO4Tx5oVJnyfq9oQbTqC023CYxzIBsQU+B07u9PpPL1kwIuerGVZr4oAH\n/PMWdYA5UXvl+TW2dE6pjYIT5LY/qQOD+qK+ihVqf94Lw7YZFAXK6sOoBJQ7Rnwy\nDfMAZiLIjWltNowRGLfTshxgtDj6AozO091GB94KPutdfMh8+7ArU6SSYmlRJQVh\nGkSBjCypQ5Yj36w6gZoOKcUcqeldHraenjAKOc7xiID7S13MMuyFYkMlNAJWJwGR\ntDtwKj9useiciAF9n9T521NtYJ2/LOdYq7hfRvzOxBsDPAnrSTFcaUaz4EcCAwEA\nAaNCMEAwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYE\nFDqahQcQZyi27/a9BUFuIMGU2g/eMA0GCSqGSIb3DQEBCwUAA4IBAQCZ21151fmX\nWWcDYfF+OwYxdS2hII5PZYe096acvNjpL9DbWu7PdIxztDhC2gV7+AJ1uP2lsdeu\n9tfeE8tTEH6KRtGX+rcuKxGrkLAngPnon1rpN5+r5N9ss4UXnT3ZJE95kTXWXwTr\ngIOrmgIttRD02JDHBHNA7XIloKmf7J6raBKZV8aPEjoJpL1E/QYVN8Gb5DKj7Tjo\n2GTzLH4U/ALqn83/B2gX2yKQOC16jdFU8WnjXzPKej17CuPKf1855eJ1usV2GDPO\nLPAvTK33sefOT6jEm0pUBsV/fdUID+Ic/n4XuKxe9tQWskMJDE32p2u0mYRlynqI\n4uJEvlz36hz1\n-----END CERTIFICATE-----\n\n# Issuer: CN=Starfield Root Certificate Authority - G2 O=Starfield Technologies, Inc.\n# Subject: CN=Starfield Root Certificate Authority - G2 O=Starfield Technologies, Inc.\n# Label: \"Starfield Root Certificate Authority - G2\"\n# Serial: 0\n# MD5 Fingerprint: d6:39:81:c6:52:7e:96:69:fc:fc:ca:66:ed:05:f2:96\n# SHA1 Fingerprint: b5:1c:06:7c:ee:2b:0c:3d:f8:55:ab:2d:92:f4:fe:39:d4:e7:0f:0e\n# SHA256 Fingerprint: 2c:e1:cb:0b:f9:d2:f9:e1:02:99:3f:be:21:51:52:c3:b2:dd:0c:ab:de:1c:68:e5:31:9b:83:91:54:db:b7:f5\n-----BEGIN CERTIFICATE-----\nMIID3TCCAsWgAwIBAgIBADANBgkqhkiG9w0BAQsFADCBjzELMAkGA1UEBhMCVVMx\nEDAOBgNVBAgTB0FyaXpvbmExEzARBgNVBAcTClNjb3R0c2RhbGUxJTAjBgNVBAoT\nHFN0YXJmaWVsZCBUZWNobm9sb2dpZXMsIEluYy4xMjAwBgNVBAMTKVN0YXJmaWVs\nZCBSb290IENlcnRpZmljYXRlIEF1dGhvcml0eSAtIEcyMB4XDTA5MDkwMTAwMDAw\nMFoXDTM3MTIzMTIzNTk1OVowgY8xCzAJBgNVBAYTAlVTMRAwDgYDVQQIEwdBcml6\nb25hMRMwEQYDVQQHEwpTY290dHNkYWxlMSUwIwYDVQQKExxTdGFyZmllbGQgVGVj\naG5vbG9naWVzLCBJbmMuMTIwMAYDVQQDEylTdGFyZmllbGQgUm9vdCBDZXJ0aWZp\nY2F0ZSBBdXRob3JpdHkgLSBHMjCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoC\nggEBAL3twQP89o/8ArFvW59I2Z154qK3A2FWGMNHttfKPTUuiUP3oWmb3ooa/RMg\nnLRJdzIpVv257IzdIvpy3Cdhl+72WoTsbhm5iSzchFvVdPtrX8WJpRBSiUZV9Lh1\nHOZ/5FSuS/hVclcCGfgXcVnrHigHdMWdSL5stPSksPNkN3mSwOxGXn/hbVNMYq/N\nHwtjuzqd+/x5AJhhdM8mgkBj87JyahkNmcrUDnXMN/uLicFZ8WJ/X7NfZTD4p7dN\ndloedl40wOiWVpmKs/B/pM293DIxfJHP4F8R+GuqSVzRmZTRouNjWwl2tVZi4Ut0\nHZbUJtQIBFnQmA4O5t78w+wfkPECAwEAAaNCMEAwDwYDVR0TAQH/BAUwAwEB/zAO\nBgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYEFHwMMh+n2TB/xH1oo2Kooc6rB1snMA0G\nCSqGSIb3DQEBCwUAA4IBAQARWfolTwNvlJk7mh+ChTnUdgWUXuEok21iXQnCoKjU\nsHU48TRqneSfioYmUeYs0cYtbpUgSpIB7LiKZ3sx4mcujJUDJi5DnUox9g61DLu3\n4jd/IroAow57UvtruzvE03lRTs2Q9GcHGcg8RnoNAX3FWOdt5oUwF5okxBDgBPfg\n8n/Uqgr/Qh037ZTlZFkSIHc40zI+OIF1lnP6aI+xy84fxez6nH7PfrHxBy22/L/K\npL/QlwVKvOoYKAKQvVR4CSFx09F9HdkWsKlhPdAKACL8x3vLCWRFCztAgfd9fDL1\nmMpYjn0q7pBZc2T5NnReJaH1ZgUufzkVqSr7UIuOhWn0\n-----END CERTIFICATE-----\n\n# Issuer: CN=Starfield Services Root Certificate Authority - G2 O=Starfield Technologies, Inc.\n# Subject: CN=Starfield Services Root Certificate Authority - G2 O=Starfield Technologies, Inc.\n# Label: \"Starfield Services Root Certificate Authority - G2\"\n# Serial: 0\n# MD5 Fingerprint: 17:35:74:af:7b:61:1c:eb:f4:f9:3c:e2:ee:40:f9:a2\n# SHA1 Fingerprint: 92:5a:8f:8d:2c:6d:04:e0:66:5f:59:6a:ff:22:d8:63:e8:25:6f:3f\n# SHA256 Fingerprint: 56:8d:69:05:a2:c8:87:08:a4:b3:02:51:90:ed:cf:ed:b1:97:4a:60:6a:13:c6:e5:29:0f:cb:2a:e6:3e:da:b5\n-----BEGIN CERTIFICATE-----\nMIID7zCCAtegAwIBAgIBADANBgkqhkiG9w0BAQsFADCBmDELMAkGA1UEBhMCVVMx\nEDAOBgNVBAgTB0FyaXpvbmExEzARBgNVBAcTClNjb3R0c2RhbGUxJTAjBgNVBAoT\nHFN0YXJmaWVsZCBUZWNobm9sb2dpZXMsIEluYy4xOzA5BgNVBAMTMlN0YXJmaWVs\nZCBTZXJ2aWNlcyBSb290IENlcnRpZmljYXRlIEF1dGhvcml0eSAtIEcyMB4XDTA5\nMDkwMTAwMDAwMFoXDTM3MTIzMTIzNTk1OVowgZgxCzAJBgNVBAYTAlVTMRAwDgYD\nVQQIEwdBcml6b25hMRMwEQYDVQQHEwpTY290dHNkYWxlMSUwIwYDVQQKExxTdGFy\nZmllbGQgVGVjaG5vbG9naWVzLCBJbmMuMTswOQYDVQQDEzJTdGFyZmllbGQgU2Vy\ndmljZXMgUm9vdCBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkgLSBHMjCCASIwDQYJKoZI\nhvcNAQEBBQADggEPADCCAQoCggEBANUMOsQq+U7i9b4Zl1+OiFOxHz/Lz58gE20p\nOsgPfTz3a3Y4Y9k2YKibXlwAgLIvWX/2h/klQ4bnaRtSmpDhcePYLQ1Ob/bISdm2\n8xpWriu2dBTrz/sm4xq6HZYuajtYlIlHVv8loJNwU4PahHQUw2eeBGg6345AWh1K\nTs9DkTvnVtYAcMtS7nt9rjrnvDH5RfbCYM8TWQIrgMw0R9+53pBlbQLPLJGmpufe\nhRhJfGZOozptqbXuNC66DQO4M99H67FrjSXZm86B0UVGMpZwh94CDklDhbZsc7tk\n6mFBrMnUVN+HL8cisibMn1lUaJ/8viovxFUcdUBgF4UCVTmLfwUCAwEAAaNCMEAw\nDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYEFJxfAN+q\nAdcwKziIorhtSpzyEZGDMA0GCSqGSIb3DQEBCwUAA4IBAQBLNqaEd2ndOxmfZyMI\nbw5hyf2E3F/YNoHN2BtBLZ9g3ccaaNnRbobhiCPPE95Dz+I0swSdHynVv/heyNXB\nve6SbzJ08pGCL72CQnqtKrcgfU28elUSwhXqvfdqlS5sdJ/PHLTyxQGjhdByPq1z\nqwubdQxtRbeOlKyWN7Wg0I8VRw7j6IPdj/3vQQF3zCepYoUz8jcI73HPdwbeyBkd\niEDPfUYd/x7H4c7/I9vG+o1VTqkC50cRRj70/b17KSa7qWFiNyi2LSr2EIZkyXCn\n0q23KXB56jzaYyWf/Wi3MOxw+3WKt21gZ7IeyLnp2KhvAotnDU0mV3HaIPzBSlCN\nsSi6\n-----END CERTIFICATE-----\n\n# Issuer: CN=AffirmTrust Commercial O=AffirmTrust\n# Subject: CN=AffirmTrust Commercial O=AffirmTrust\n# Label: \"AffirmTrust Commercial\"\n# Serial: 8608355977964138876\n# MD5 Fingerprint: 82:92:ba:5b:ef:cd:8a:6f:a6:3d:55:f9:84:f6:d6:b7\n# SHA1 Fingerprint: f9:b5:b6:32:45:5f:9c:be:ec:57:5f:80:dc:e9:6e:2c:c7:b2:78:b7\n# SHA256 Fingerprint: 03:76:ab:1d:54:c5:f9:80:3c:e4:b2:e2:01:a0:ee:7e:ef:7b:57:b6:36:e8:a9:3c:9b:8d:48:60:c9:6f:5f:a7\n-----BEGIN CERTIFICATE-----\nMIIDTDCCAjSgAwIBAgIId3cGJyapsXwwDQYJKoZIhvcNAQELBQAwRDELMAkGA1UE\nBhMCVVMxFDASBgNVBAoMC0FmZmlybVRydXN0MR8wHQYDVQQDDBZBZmZpcm1UcnVz\ndCBDb21tZXJjaWFsMB4XDTEwMDEyOTE0MDYwNloXDTMwMTIzMTE0MDYwNlowRDEL\nMAkGA1UEBhMCVVMxFDASBgNVBAoMC0FmZmlybVRydXN0MR8wHQYDVQQDDBZBZmZp\ncm1UcnVzdCBDb21tZXJjaWFsMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKC\nAQEA9htPZwcroRX1BiLLHwGy43NFBkRJLLtJJRTWzsO3qyxPxkEylFf6EqdbDuKP\nHx6GGaeqtS25Xw2Kwq+FNXkyLbscYjfysVtKPcrNcV/pQr6U6Mje+SJIZMblq8Yr\nba0F8PrVC8+a5fBQpIs7R6UjW3p6+DM/uO+Zl+MgwdYoic+U+7lF7eNAFxHUdPAL\nMeIrJmqbTFeurCA+ukV6BfO9m2kVrn1OIGPENXY6BwLJN/3HR+7o8XYdcxXyl6S1\nyHp52UKqK39c/s4mT6NmgTWvRLpUHhwwMmWd5jyTXlBOeuM61G7MGvv50jeuJCqr\nVwMiKA1JdX+3KNp1v47j3A55MQIDAQABo0IwQDAdBgNVHQ4EFgQUnZPGU4teyq8/\nnx4P5ZmVvCT2lI8wDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwDQYJ\nKoZIhvcNAQELBQADggEBAFis9AQOzcAN/wr91LoWXym9e2iZWEnStB03TX8nfUYG\nXUPGhi4+c7ImfU+TqbbEKpqrIZcUsd6M06uJFdhrJNTxFq7YpFzUf1GO7RgBsZNj\nvbz4YYCanrHOQnDiqX0GJX0nof5v7LMeJNrjS1UaADs1tDvZ110w/YETifLCBivt\nZ8SOyUOyXGsViQK8YvxO8rUzqrJv0wqiUOP2O+guRMLbZjipM1ZI8W0bM40NjD9g\nN53Tym1+NH4Nn3J2ixufcv1SNUFFApYvHLKac0khsUlHRUe072o0EclNmsxZt9YC\nnlpOZbWUrhvfKbAW8b8Angc6F2S1BLUjIZkKlTuXfO8=\n-----END CERTIFICATE-----\n\n# Issuer: CN=AffirmTrust Networking O=AffirmTrust\n# Subject: CN=AffirmTrust Networking O=AffirmTrust\n# Label: \"AffirmTrust Networking\"\n# Serial: 8957382827206547757\n# MD5 Fingerprint: 42:65:ca:be:01:9a:9a:4c:a9:8c:41:49:cd:c0:d5:7f\n# SHA1 Fingerprint: 29:36:21:02:8b:20:ed:02:f5:66:c5:32:d1:d6:ed:90:9f:45:00:2f\n# SHA256 Fingerprint: 0a:81:ec:5a:92:97:77:f1:45:90:4a:f3:8d:5d:50:9f:66:b5:e2:c5:8f:cd:b5:31:05:8b:0e:17:f3:f0:b4:1b\n-----BEGIN CERTIFICATE-----\nMIIDTDCCAjSgAwIBAgIIfE8EORzUmS0wDQYJKoZIhvcNAQEFBQAwRDELMAkGA1UE\nBhMCVVMxFDASBgNVBAoMC0FmZmlybVRydXN0MR8wHQYDVQQDDBZBZmZpcm1UcnVz\ndCBOZXR3b3JraW5nMB4XDTEwMDEyOTE0MDgyNFoXDTMwMTIzMTE0MDgyNFowRDEL\nMAkGA1UEBhMCVVMxFDASBgNVBAoMC0FmZmlybVRydXN0MR8wHQYDVQQDDBZBZmZp\ncm1UcnVzdCBOZXR3b3JraW5nMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKC\nAQEAtITMMxcua5Rsa2FSoOujz3mUTOWUgJnLVWREZY9nZOIG41w3SfYvm4SEHi3y\nYJ0wTsyEheIszx6e/jarM3c1RNg1lho9Nuh6DtjVR6FqaYvZ/Ls6rnla1fTWcbua\nkCNrmreIdIcMHl+5ni36q1Mr3Lt2PpNMCAiMHqIjHNRqrSK6mQEubWXLviRmVSRL\nQESxG9fhwoXA3hA/Pe24/PHxI1Pcv2WXb9n5QHGNfb2V1M6+oF4nI979ptAmDgAp\n6zxG8D1gvz9Q0twmQVGeFDdCBKNwV6gbh+0t+nvujArjqWaJGctB+d1ENmHP4ndG\nyH329JKBNv3bNPFyfvMMFr20FQIDAQABo0IwQDAdBgNVHQ4EFgQUBx/S55zawm6i\nQLSwelAQUHTEyL0wDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwDQYJ\nKoZIhvcNAQEFBQADggEBAIlXshZ6qML91tmbmzTCnLQyFE2npN/svqe++EPbkTfO\ntDIuUFUaNU52Q3Eg75N3ThVwLofDwR1t3Mu1J9QsVtFSUzpE0nPIxBsFZVpikpzu\nQY0x2+c06lkh1QF612S4ZDnNye2v7UsDSKegmQGA3GWjNq5lWUhPgkvIZfFXHeVZ\nLgo/bNjR9eUJtGxUAArgFU2HdW23WJZa3W3SAKD0m0i+wzekujbgfIeFlxoVot4u\nolu9rxj5kFDNcFn4J2dHy8egBzp90SxdbBk6ZrV9/ZFvgrG+CJPbFEfxojfHRZ48\nx3evZKiT3/Zpg4Jg8klCNO1aAFSFHBY2kgxc+qatv9s=\n-----END CERTIFICATE-----\n\n# Issuer: CN=AffirmTrust Premium O=AffirmTrust\n# Subject: CN=AffirmTrust Premium O=AffirmTrust\n# Label: \"AffirmTrust Premium\"\n# Serial: 7893706540734352110\n# MD5 Fingerprint: c4:5d:0e:48:b6:ac:28:30:4e:0a:bc:f9:38:16:87:57\n# SHA1 Fingerprint: d8:a6:33:2c:e0:03:6f:b1:85:f6:63:4f:7d:6a:06:65:26:32:28:27\n# SHA256 Fingerprint: 70:a7:3f:7f:37:6b:60:07:42:48:90:45:34:b1:14:82:d5:bf:0e:69:8e:cc:49:8d:f5:25:77:eb:f2:e9:3b:9a\n-----BEGIN CERTIFICATE-----\nMIIFRjCCAy6gAwIBAgIIbYwURrGmCu4wDQYJKoZIhvcNAQEMBQAwQTELMAkGA1UE\nBhMCVVMxFDASBgNVBAoMC0FmZmlybVRydXN0MRwwGgYDVQQDDBNBZmZpcm1UcnVz\ndCBQcmVtaXVtMB4XDTEwMDEyOTE0MTAzNloXDTQwMTIzMTE0MTAzNlowQTELMAkG\nA1UEBhMCVVMxFDASBgNVBAoMC0FmZmlybVRydXN0MRwwGgYDVQQDDBNBZmZpcm1U\ncnVzdCBQcmVtaXVtMIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAxBLf\nqV/+Qd3d9Z+K4/as4Tx4mrzY8H96oDMq3I0gW64tb+eT2TZwamjPjlGjhVtnBKAQ\nJG9dKILBl1fYSCkTtuG+kU3fhQxTGJoeJKJPj/CihQvL9Cl/0qRY7iZNyaqoe5rZ\n+jjeRFcV5fiMyNlI4g0WJx0eyIOFJbe6qlVBzAMiSy2RjYvmia9mx+n/K+k8rNrS\ns8PhaJyJ+HoAVt70VZVs+7pk3WKL3wt3MutizCaam7uqYoNMtAZ6MMgpv+0GTZe5\nHMQxK9VfvFMSF5yZVylmd2EhMQcuJUmdGPLu8ytxjLW6OQdJd/zvLpKQBY0tL3d7\n70O/Nbua2Plzpyzy0FfuKE4mX4+QaAkvuPjcBukumj5Rp9EixAqnOEhss/n/fauG\nV+O61oV4d7pD6kh/9ti+I20ev9E2bFhc8e6kGVQa9QPSdubhjL08s9NIS+LI+H+S\nqHZGnEJlPqQewQcDWkYtuJfzt9WyVSHvutxMAJf7FJUnM7/oQ0dG0giZFmA7mn7S\n5u046uwBHjxIVkkJx0w3AJ6IDsBz4W9m6XJHMD4Q5QsDyZpCAGzFlH5hxIrff4Ia\nC1nEWTJ3s7xgaVY5/bQGeyzWZDbZvUjthB9+pSKPKrhC9IK31FOQeE4tGv2Bb0TX\nOwF0lkLgAOIua+rF7nKsu7/+6qqo+Nz2snmKtmcCAwEAAaNCMEAwHQYDVR0OBBYE\nFJ3AZ6YMItkm9UWrpmVSESfYRaxjMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/\nBAQDAgEGMA0GCSqGSIb3DQEBDAUAA4ICAQCzV00QYk465KzquByvMiPIs0laUZx2\nKI15qldGF9X1Uva3ROgIRL8YhNILgM3FEv0AVQVhh0HctSSePMTYyPtwni94loMg\nNt58D2kTiKV1NpgIpsbfrM7jWNa3Pt668+s0QNiigfV4Py/VpfzZotReBA4Xrf5B\n8OWycvpEgjNC6C1Y91aMYj+6QrCcDFx+LmUmXFNPALJ4fqENmS2NuB2OosSw/WDQ\nMKSOyARiqcTtNd56l+0OOF6SL5Nwpamcb6d9Ex1+xghIsV5n61EIJenmJWtSKZGc\n0jlzCFfemQa0W50QBuHCAKi4HEoCChTQwUHK+4w1IX2COPKpVJEZNZOUbWo6xbLQ\nu4mGk+ibyQ86p3q4ofB4Rvr8Ny/lioTz3/4E2aFooC8k4gmVBtWVyuEklut89pMF\nu+1z6S3RdTnX5yTb2E5fQ4+e0BQ5v1VwSJlXMbSc7kqYA5YwH2AG7hsj/oFgIxpH\nYoWlzBk0gG+zrBrjn/B7SK3VAdlntqlyk+otZrWyuOQ9PLLvTIzq6we/qzWaVYa8\nGKa1qF60g2xraUDTn9zxw2lrueFtCfTxqlB2Cnp9ehehVZZCmTEJ3WARjQUwfuaO\nRtGdFNrHF+QFlozEJLUbzxQHskD4o55BhrwE0GuWyCqANP2/7waj3VjFhT0+j/6e\nKeC2uAloGRwYQw==\n-----END CERTIFICATE-----\n\n# Issuer: CN=AffirmTrust Premium ECC O=AffirmTrust\n# Subject: CN=AffirmTrust Premium ECC O=AffirmTrust\n# Label: \"AffirmTrust Premium ECC\"\n# Serial: 8401224907861490260\n# MD5 Fingerprint: 64:b0:09:55:cf:b1:d5:99:e2:be:13:ab:a6:5d:ea:4d\n# SHA1 Fingerprint: b8:23:6b:00:2f:1d:16:86:53:01:55:6c:11:a4:37:ca:eb:ff:c3:bb\n# SHA256 Fingerprint: bd:71:fd:f6:da:97:e4:cf:62:d1:64:7a:dd:25:81:b0:7d:79:ad:f8:39:7e:b4:ec:ba:9c:5e:84:88:82:14:23\n-----BEGIN CERTIFICATE-----\nMIIB/jCCAYWgAwIBAgIIdJclisc/elQwCgYIKoZIzj0EAwMwRTELMAkGA1UEBhMC\nVVMxFDASBgNVBAoMC0FmZmlybVRydXN0MSAwHgYDVQQDDBdBZmZpcm1UcnVzdCBQ\ncmVtaXVtIEVDQzAeFw0xMDAxMjkxNDIwMjRaFw00MDEyMzExNDIwMjRaMEUxCzAJ\nBgNVBAYTAlVTMRQwEgYDVQQKDAtBZmZpcm1UcnVzdDEgMB4GA1UEAwwXQWZmaXJt\nVHJ1c3QgUHJlbWl1bSBFQ0MwdjAQBgcqhkjOPQIBBgUrgQQAIgNiAAQNMF4bFZ0D\n0KF5Nbc6PJJ6yhUczWLznCZcBz3lVPqj1swS6vQUX+iOGasvLkjmrBhDeKzQN8O9\nss0s5kfiGuZjuD0uL3jET9v0D6RoTFVya5UdThhClXjMNzyR4ptlKymjQjBAMB0G\nA1UdDgQWBBSaryl6wBE1NSZRMADDav5A1a7WPDAPBgNVHRMBAf8EBTADAQH/MA4G\nA1UdDwEB/wQEAwIBBjAKBggqhkjOPQQDAwNnADBkAjAXCfOHiFBar8jAQr9HX/Vs\naobgxCd05DhT1wV/GzTjxi+zygk8N53X57hG8f2h4nECMEJZh0PUUd+60wkyWs6I\nflc9nF9Ca/UHLbXwgpP5WW+uZPpY5Yse42O+tYHNbwKMeQ==\n-----END CERTIFICATE-----\n\n# Issuer: CN=Certum Trusted Network CA O=Unizeto Technologies S.A. OU=Certum Certification Authority\n# Subject: CN=Certum Trusted Network CA O=Unizeto Technologies S.A. OU=Certum Certification Authority\n# Label: \"Certum Trusted Network CA\"\n# Serial: 279744\n# MD5 Fingerprint: d5:e9:81:40:c5:18:69:fc:46:2c:89:75:62:0f:aa:78\n# SHA1 Fingerprint: 07:e0:32:e0:20:b7:2c:3f:19:2f:06:28:a2:59:3a:19:a7:0f:06:9e\n# SHA256 Fingerprint: 5c:58:46:8d:55:f5:8e:49:7e:74:39:82:d2:b5:00:10:b6:d1:65:37:4a:cf:83:a7:d4:a3:2d:b7:68:c4:40:8e\n-----BEGIN CERTIFICATE-----\nMIIDuzCCAqOgAwIBAgIDBETAMA0GCSqGSIb3DQEBBQUAMH4xCzAJBgNVBAYTAlBM\nMSIwIAYDVQQKExlVbml6ZXRvIFRlY2hub2xvZ2llcyBTLkEuMScwJQYDVQQLEx5D\nZXJ0dW0gQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkxIjAgBgNVBAMTGUNlcnR1bSBU\ncnVzdGVkIE5ldHdvcmsgQ0EwHhcNMDgxMDIyMTIwNzM3WhcNMjkxMjMxMTIwNzM3\nWjB+MQswCQYDVQQGEwJQTDEiMCAGA1UEChMZVW5pemV0byBUZWNobm9sb2dpZXMg\nUy5BLjEnMCUGA1UECxMeQ2VydHVtIENlcnRpZmljYXRpb24gQXV0aG9yaXR5MSIw\nIAYDVQQDExlDZXJ0dW0gVHJ1c3RlZCBOZXR3b3JrIENBMIIBIjANBgkqhkiG9w0B\nAQEFAAOCAQ8AMIIBCgKCAQEA4/t9o3K6wvDJFIf1awFO4W5AB7ptJ11/91sts1rH\nUV+rpDKmYYe2bg+G0jACl/jXaVehGDldamR5xgFZrDwxSjh80gTSSyjoIF87B6LM\nTXPb865Px1bVWqeWifrzq2jUI4ZZJ88JJ7ysbnKDHDBy3+Ci6dLhdHUZvSqeexVU\nBBvXQzmtVSjF4hq79MDkrjhJM8x2hZ85RdKknvISjFH4fOQtf/WsX+sWn7Et0brM\nkUJ3TCXJkDhv2/DM+44el1k+1WBO5gUo7Ul5E0u6SNsv+XLTOcr+H9g0cvW0QM8x\nAcPs3hEtF10fuFDRXhmnad4HMyjKUJX5p1TLVIZQRan5SQIDAQABo0IwQDAPBgNV\nHRMBAf8EBTADAQH/MB0GA1UdDgQWBBQIds3LB/8k9sXN7buQvOKEN0Z19zAOBgNV\nHQ8BAf8EBAMCAQYwDQYJKoZIhvcNAQEFBQADggEBAKaorSLOAT2mo/9i0Eidi15y\nsHhE49wcrwn9I0j6vSrEuVUEtRCjjSfeC4Jj0O7eDDd5QVsisrCaQVymcODU0HfL\nI9MA4GxWL+FpDQ3Zqr8hgVDZBqWo/5U30Kr+4rP1mS1FhIrlQgnXdAIv94nYmem8\nJ9RHjboNRhx3zxSkHLmkMcScKHQDNP8zGSal6Q10tz6XxnboJ5ajZt3hrvJBW8qY\nVoNzcOSGGtIxQbovvi0TWnZvTuhOgQ4/WwMioBK+ZlgRSssDxLQqKi2WF+A5VLxI\n03YnnZotBqbJ7DnSq9ufmgsnAjUpsUCV5/nonFWIGUbWtzT1fs45mtk48VH3Tyw=\n-----END CERTIFICATE-----\n\n# Issuer: CN=TWCA Root Certification Authority O=TAIWAN-CA OU=Root CA\n# Subject: CN=TWCA Root Certification Authority O=TAIWAN-CA OU=Root CA\n# Label: \"TWCA Root Certification Authority\"\n# Serial: 1\n# MD5 Fingerprint: aa:08:8f:f6:f9:7b:b7:f2:b1:a7:1e:9b:ea:ea:bd:79\n# SHA1 Fingerprint: cf:9e:87:6d:d3:eb:fc:42:26:97:a3:b5:a3:7a:a0:76:a9:06:23:48\n# SHA256 Fingerprint: bf:d8:8f:e1:10:1c:41:ae:3e:80:1b:f8:be:56:35:0e:e9:ba:d1:a6:b9:bd:51:5e:dc:5c:6d:5b:87:11:ac:44\n-----BEGIN CERTIFICATE-----\nMIIDezCCAmOgAwIBAgIBATANBgkqhkiG9w0BAQUFADBfMQswCQYDVQQGEwJUVzES\nMBAGA1UECgwJVEFJV0FOLUNBMRAwDgYDVQQLDAdSb290IENBMSowKAYDVQQDDCFU\nV0NBIFJvb3QgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkwHhcNMDgwODI4MDcyNDMz\nWhcNMzAxMjMxMTU1OTU5WjBfMQswCQYDVQQGEwJUVzESMBAGA1UECgwJVEFJV0FO\nLUNBMRAwDgYDVQQLDAdSb290IENBMSowKAYDVQQDDCFUV0NBIFJvb3QgQ2VydGlm\naWNhdGlvbiBBdXRob3JpdHkwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIB\nAQCwfnK4pAOU5qfeCTiRShFAh6d8WWQUe7UREN3+v9XAu1bihSX0NXIP+FPQQeFE\nAcK0HMMxQhZHhTMidrIKbw/lJVBPhYa+v5guEGcevhEFhgWQxFnQfHgQsIBct+HH\nK3XLfJ+utdGdIzdjp9xCoi2SBBtQwXu4PhvJVgSLL1KbralW6cH/ralYhzC2gfeX\nRfwZVzsrb+RH9JlF/h3x+JejiB03HFyP4HYlmlD4oFT/RJB2I9IyxsOrBr/8+7/z\nrX2SYgJbKdM1o5OaQ2RgXbL6Mv87BK9NQGr5x+PvI/1ry+UPizgN7gr8/g+YnzAx\n3WxSZfmLgb4i4RxYA7qRG4kHAgMBAAGjQjBAMA4GA1UdDwEB/wQEAwIBBjAPBgNV\nHRMBAf8EBTADAQH/MB0GA1UdDgQWBBRqOFsmjd6LWvJPelSDGRjjCDWmujANBgkq\nhkiG9w0BAQUFAAOCAQEAPNV3PdrfibqHDAhUaiBQkr6wQT25JmSDCi/oQMCXKCeC\nMErJk/9q56YAf4lCmtYR5VPOL8zy2gXE/uJQxDqGfczafhAJO5I1KlOy/usrBdls\nXebQ79NqZp4VKIV66IIArB6nCWlWQtNoURi+VJq/REG6Sb4gumlc7rh3zc5sH62D\nlhh9DrUUOYTxKOkto557HnpyWoOzeW/vtPzQCqVYT0bf+215WfKEIlKuD8z7fDvn\naspHYcN6+NOSBB+4IIThNlQWx0DeO4pz3N/GCUzf7Nr/1FNCocnyYh0igzyXxfkZ\nYiesZSLX0zzG5Y6yU8xJzrww/nsOM5D77dIUkR8Hrw==\n-----END CERTIFICATE-----\n\n# Issuer: O=SECOM Trust Systems CO.,LTD. OU=Security Communication RootCA2\n# Subject: O=SECOM Trust Systems CO.,LTD. OU=Security Communication RootCA2\n# Label: \"Security Communication RootCA2\"\n# Serial: 0\n# MD5 Fingerprint: 6c:39:7d:a4:0e:55:59:b2:3f:d6:41:b1:12:50:de:43\n# SHA1 Fingerprint: 5f:3b:8c:f2:f8:10:b3:7d:78:b4:ce:ec:19:19:c3:73:34:b9:c7:74\n# SHA256 Fingerprint: 51:3b:2c:ec:b8:10:d4:cd:e5:dd:85:39:1a:df:c6:c2:dd:60:d8:7b:b7:36:d2:b5:21:48:4a:a4:7a:0e:be:f6\n-----BEGIN CERTIFICATE-----\nMIIDdzCCAl+gAwIBAgIBADANBgkqhkiG9w0BAQsFADBdMQswCQYDVQQGEwJKUDEl\nMCMGA1UEChMcU0VDT00gVHJ1c3QgU3lzdGVtcyBDTy4sTFRELjEnMCUGA1UECxMe\nU2VjdXJpdHkgQ29tbXVuaWNhdGlvbiBSb290Q0EyMB4XDTA5MDUyOTA1MDAzOVoX\nDTI5MDUyOTA1MDAzOVowXTELMAkGA1UEBhMCSlAxJTAjBgNVBAoTHFNFQ09NIFRy\ndXN0IFN5c3RlbXMgQ08uLExURC4xJzAlBgNVBAsTHlNlY3VyaXR5IENvbW11bmlj\nYXRpb24gUm9vdENBMjCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBANAV\nOVKxUrO6xVmCxF1SrjpDZYBLx/KWvNs2l9amZIyoXvDjChz335c9S672XewhtUGr\nzbl+dp+++T42NKA7wfYxEUV0kz1XgMX5iZnK5atq1LXaQZAQwdbWQonCv/Q4EpVM\nVAX3NuRFg3sUZdbcDE3R3n4MqzvEFb46VqZab3ZpUql6ucjrappdUtAtCms1FgkQ\nhNBqyjoGADdH5H5XTz+L62e4iKrFvlNVspHEfbmwhRkGeC7bYRr6hfVKkaHnFtWO\nojnflLhwHyg/i/xAXmODPIMqGplrz95Zajv8bxbXH/1KEOtOghY6rCcMU/Gt1SSw\nawNQwS08Ft1ENCcadfsCAwEAAaNCMEAwHQYDVR0OBBYEFAqFqXdlBZh8QIH4D5cs\nOPEK7DzPMA4GA1UdDwEB/wQEAwIBBjAPBgNVHRMBAf8EBTADAQH/MA0GCSqGSIb3\nDQEBCwUAA4IBAQBMOqNErLlFsceTfsgLCkLfZOoc7llsCLqJX2rKSpWeeo8HxdpF\ncoJxDjrSzG+ntKEju/Ykn8sX/oymzsLS28yN/HH8AynBbF0zX2S2ZTuJbxh2ePXc\nokgfGT+Ok+vx+hfuzU7jBBJV1uXk3fs+BXziHV7Gp7yXT2g69ekuCkO2r1dcYmh8\nt/2jioSgrGK+KwmHNPBqAbubKVY8/gA3zyNs8U6qtnRGEmyR7jTV7JqR50S+kDFy\n1UkC9gLl9B/rfNmWVan/7Ir5mUf/NVoCqgTLiluHcSmRvaS0eg29mvVXIwAHIRc/\nSjnRBUkLp7Y3gaVdjKozXoEofKd9J+sAro03\n-----END CERTIFICATE-----\n\n# Issuer: CN=Hellenic Academic and Research Institutions RootCA 2011 O=Hellenic Academic and Research Institutions Cert. Authority\n# Subject: CN=Hellenic Academic and Research Institutions RootCA 2011 O=Hellenic Academic and Research Institutions Cert. Authority\n# Label: \"Hellenic Academic and Research Institutions RootCA 2011\"\n# Serial: 0\n# MD5 Fingerprint: 73:9f:4c:4b:73:5b:79:e9:fa:ba:1c:ef:6e:cb:d5:c9\n# SHA1 Fingerprint: fe:45:65:9b:79:03:5b:98:a1:61:b5:51:2e:ac:da:58:09:48:22:4d\n# SHA256 Fingerprint: bc:10:4f:15:a4:8b:e7:09:dc:a5:42:a7:e1:d4:b9:df:6f:05:45:27:e8:02:ea:a9:2d:59:54:44:25:8a:fe:71\n-----BEGIN CERTIFICATE-----\nMIIEMTCCAxmgAwIBAgIBADANBgkqhkiG9w0BAQUFADCBlTELMAkGA1UEBhMCR1Ix\nRDBCBgNVBAoTO0hlbGxlbmljIEFjYWRlbWljIGFuZCBSZXNlYXJjaCBJbnN0aXR1\ndGlvbnMgQ2VydC4gQXV0aG9yaXR5MUAwPgYDVQQDEzdIZWxsZW5pYyBBY2FkZW1p\nYyBhbmQgUmVzZWFyY2ggSW5zdGl0dXRpb25zIFJvb3RDQSAyMDExMB4XDTExMTIw\nNjEzNDk1MloXDTMxMTIwMTEzNDk1MlowgZUxCzAJBgNVBAYTAkdSMUQwQgYDVQQK\nEztIZWxsZW5pYyBBY2FkZW1pYyBhbmQgUmVzZWFyY2ggSW5zdGl0dXRpb25zIENl\ncnQuIEF1dGhvcml0eTFAMD4GA1UEAxM3SGVsbGVuaWMgQWNhZGVtaWMgYW5kIFJl\nc2VhcmNoIEluc3RpdHV0aW9ucyBSb290Q0EgMjAxMTCCASIwDQYJKoZIhvcNAQEB\nBQADggEPADCCAQoCggEBAKlTAOMupvaO+mDYLZU++CwqVE7NuYRhlFhPjz2L5EPz\ndYmNUeTDN9KKiE15HrcS3UN4SoqS5tdI1Q+kOilENbgH9mgdVc04UfCMJDGFr4PJ\nfel3r+0ae50X+bOdOFAPplp5kYCvN66m0zH7tSYJnTxa71HFK9+WXesyHgLacEns\nbgzImjeN9/E2YEsmLIKe0HjzDQ9jpFEw4fkrJxIH2Oq9GGKYsFk3fb7u8yBRQlqD\n75O6aRXxYp2fmTmCobd0LovUxQt7L/DICto9eQqakxylKHJzkUOap9FNhYS5qXSP\nFEDH3N6sQWRstBmbAmNtJGSPRLIl6s5ddAxjMlyNh+UCAwEAAaOBiTCBhjAPBgNV\nHRMBAf8EBTADAQH/MAsGA1UdDwQEAwIBBjAdBgNVHQ4EFgQUppFC/RNhSiOeCKQp\n5dgTBCPuQSUwRwYDVR0eBEAwPqA8MAWCAy5ncjAFggMuZXUwBoIELmVkdTAGggQu\nb3JnMAWBAy5ncjAFgQMuZXUwBoEELmVkdTAGgQQub3JnMA0GCSqGSIb3DQEBBQUA\nA4IBAQAf73lB4XtuP7KMhjdCSk4cNx6NZrokgclPEg8hwAOXhiVtXdMiKahsog2p\n6z0GW5k6x8zDmjR/qw7IThzh+uTczQ2+vyT+bOdrwg3IBp5OjWEopmr95fZi6hg8\nTqBTnbI6nOulnJEWtk2C4AwFSKls9cz4y51JtPACpf1wA+2KIaWuE4ZJwzNzvoc7\ndIsXRSZMFpGD/md9zU1jZ/rzAxKWeAaNsWftjj++n08C9bMJL/NMh98qy5V8Acys\nNnq/onN694/BtZqhFLKPM58N7yLcZnuEvUUXBj08yrl3NI/K6s8/MT7jiOOASSXI\nl7WdmplNsDz4SgCbZN2fOUvRJ9e4\n-----END CERTIFICATE-----\n\n# Issuer: CN=Actalis Authentication Root CA O=Actalis S.p.A./03358520967\n# Subject: CN=Actalis Authentication Root CA O=Actalis S.p.A./03358520967\n# Label: \"Actalis Authentication Root CA\"\n# Serial: 6271844772424770508\n# MD5 Fingerprint: 69:c1:0d:4f:07:a3:1b:c3:fe:56:3d:04:bc:11:f6:a6\n# SHA1 Fingerprint: f3:73:b3:87:06:5a:28:84:8a:f2:f3:4a:ce:19:2b:dd:c7:8e:9c:ac\n# SHA256 Fingerprint: 55:92:60:84:ec:96:3a:64:b9:6e:2a:be:01:ce:0b:a8:6a:64:fb:fe:bc:c7:aa:b5:af:c1:55:b3:7f:d7:60:66\n-----BEGIN CERTIFICATE-----\nMIIFuzCCA6OgAwIBAgIIVwoRl0LE48wwDQYJKoZIhvcNAQELBQAwazELMAkGA1UE\nBhMCSVQxDjAMBgNVBAcMBU1pbGFuMSMwIQYDVQQKDBpBY3RhbGlzIFMucC5BLi8w\nMzM1ODUyMDk2NzEnMCUGA1UEAwweQWN0YWxpcyBBdXRoZW50aWNhdGlvbiBSb290\nIENBMB4XDTExMDkyMjExMjIwMloXDTMwMDkyMjExMjIwMlowazELMAkGA1UEBhMC\nSVQxDjAMBgNVBAcMBU1pbGFuMSMwIQYDVQQKDBpBY3RhbGlzIFMucC5BLi8wMzM1\nODUyMDk2NzEnMCUGA1UEAwweQWN0YWxpcyBBdXRoZW50aWNhdGlvbiBSb290IENB\nMIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAp8bEpSmkLO/lGMWwUKNv\nUTufClrJwkg4CsIcoBh/kbWHuUA/3R1oHwiD1S0eiKD4j1aPbZkCkpAW1V8IbInX\n4ay8IMKx4INRimlNAJZaby/ARH6jDuSRzVju3PvHHkVH3Se5CAGfpiEd9UEtL0z9\nKK3giq0itFZljoZUj5NDKd45RnijMCO6zfB9E1fAXdKDa0hMxKufgFpbOr3JpyI/\ngCczWw63igxdBzcIy2zSekciRDXFzMwujt0q7bd9Zg1fYVEiVRvjRuPjPdA1Yprb\nrxTIW6HMiRvhMCb8oJsfgadHHwTrozmSBp+Z07/T6k9QnBn+locePGX2oxgkg4YQ\n51Q+qDp2JE+BIcXjDwL4k5RHILv+1A7TaLndxHqEguNTVHnd25zS8gebLra8Pu2F\nbe8lEfKXGkJh90qX6IuxEAf6ZYGyojnP9zz/GPvG8VqLWeICrHuS0E4UT1lF9gxe\nKF+w6D9Fz8+vm2/7hNN3WpVvrJSEnu68wEqPSpP4RCHiMUVhUE4Q2OM1fEwZtN4F\nv6MGn8i1zeQf1xcGDXqVdFUNaBr8EBtiZJ1t4JWgw5QHVw0U5r0F+7if5t+L4sbn\nfpb2U8WANFAoWPASUHEXMLrmeGO89LKtmyuy/uE5jF66CyCU3nuDuP/jVo23Eek7\njPKxwV2dpAtMK9myGPW1n0sCAwEAAaNjMGEwHQYDVR0OBBYEFFLYiDrIn3hm7Ynz\nezhwlMkCAjbQMA8GA1UdEwEB/wQFMAMBAf8wHwYDVR0jBBgwFoAUUtiIOsifeGbt\nifN7OHCUyQICNtAwDgYDVR0PAQH/BAQDAgEGMA0GCSqGSIb3DQEBCwUAA4ICAQAL\ne3KHwGCmSUyIWOYdiPcUZEim2FgKDk8TNd81HdTtBjHIgT5q1d07GjLukD0R0i70\njsNjLiNmsGe+b7bAEzlgqqI0JZN1Ut6nna0Oh4lScWoWPBkdg/iaKWW+9D+a2fDz\nWochcYBNy+A4mz+7+uAwTc+G02UQGRjRlwKxK3JCaKygvU5a2hi/a5iB0P2avl4V\nSM0RFbnAKVy06Ij3Pjaut2L9HmLecHgQHEhb2rykOLpn7VU+Xlff1ANATIGk0k9j\npwlCCRT8AKnCgHNPLsBA2RF7SOp6AsDT6ygBJlh0wcBzIm2Tlf05fbsq4/aC4yyX\nX04fkZT6/iyj2HYauE2yOE+b+h1IYHkm4vP9qdCa6HCPSXrW5b0KDtst842/6+Ok\nfcvHlXHo2qN8xcL4dJIEG4aspCJTQLas/kx2z/uUMsA1n3Y/buWQbqCmJqK4LL7R\nK4X9p2jIugErsWx0Hbhzlefut8cl8ABMALJ+tguLHPPAUJ4lueAI3jZm/zel0btU\nZCzJJ7VLkn5l/9Mt4blOvH+kQSGQQXemOR/qnuOf0GZvBeyqdn6/axag67XH/JJU\nLysRJyU3eExRarDzzFhdFPFqSBX/wge2sY0PjlxQRrM9vwGYT7JZVEc+NHt4bVaT\nLnPqZih4zR0Uv6CPLy64Lo7yFIrM6bV8+2ydDKXhlg==\n-----END CERTIFICATE-----\n\n# Issuer: O=Trustis Limited OU=Trustis FPS Root CA\n# Subject: O=Trustis Limited OU=Trustis FPS Root CA\n# Label: \"Trustis FPS Root CA\"\n# Serial: 36053640375399034304724988975563710553\n# MD5 Fingerprint: 30:c9:e7:1e:6b:e6:14:eb:65:b2:16:69:20:31:67:4d\n# SHA1 Fingerprint: 3b:c0:38:0b:33:c3:f6:a6:0c:86:15:22:93:d9:df:f5:4b:81:c0:04\n# SHA256 Fingerprint: c1:b4:82:99:ab:a5:20:8f:e9:63:0a:ce:55:ca:68:a0:3e:da:5a:51:9c:88:02:a0:d3:a6:73:be:8f:8e:55:7d\n-----BEGIN CERTIFICATE-----\nMIIDZzCCAk+gAwIBAgIQGx+ttiD5JNM2a/fH8YygWTANBgkqhkiG9w0BAQUFADBF\nMQswCQYDVQQGEwJHQjEYMBYGA1UEChMPVHJ1c3RpcyBMaW1pdGVkMRwwGgYDVQQL\nExNUcnVzdGlzIEZQUyBSb290IENBMB4XDTAzMTIyMzEyMTQwNloXDTI0MDEyMTEx\nMzY1NFowRTELMAkGA1UEBhMCR0IxGDAWBgNVBAoTD1RydXN0aXMgTGltaXRlZDEc\nMBoGA1UECxMTVHJ1c3RpcyBGUFMgUm9vdCBDQTCCASIwDQYJKoZIhvcNAQEBBQAD\nggEPADCCAQoCggEBAMVQe547NdDfxIzNjpvto8A2mfRC6qc+gIMPpqdZh8mQRUN+\nAOqGeSoDvT03mYlmt+WKVoaTnGhLaASMk5MCPjDSNzoiYYkchU59j9WvezX2fihH\niTHcDnlkH5nSW7r+f2C/revnPDgpai/lkQtV/+xvWNUtyd5MZnGPDNcE2gfmHhjj\nvSkCqPoc4Vu5g6hBSLwacY3nYuUtsuvffM/bq1rKMfFMIvMFE/eC+XN5DL7XSxzA\n0RU8k0Fk0ea+IxciAIleH2ulrG6nS4zto3Lmr2NNL4XSFDWaLk6M6jKYKIahkQlB\nOrTh4/L68MkKokHdqeMDx4gVOxzUGpTXn2RZEm0CAwEAAaNTMFEwDwYDVR0TAQH/\nBAUwAwEB/zAfBgNVHSMEGDAWgBS6+nEleYtXQSUhhgtx67JkDoshZzAdBgNVHQ4E\nFgQUuvpxJXmLV0ElIYYLceuyZA6LIWcwDQYJKoZIhvcNAQEFBQADggEBAH5Y//01\nGX2cGE+esCu8jowU/yyg2kdbw++BLa8F6nRIW/M+TgfHbcWzk88iNVy2P3UnXwmW\nzaD+vkAMXBJV+JOCyinpXj9WV4s4NvdFGkwozZ5BuO1WTISkQMi4sKUraXAEasP4\n1BIy+Q7DsdwyhEQsb8tGD+pmQQ9P8Vilpg0ND2HepZ5dfWWhPBfnqFVO76DH7cZE\nf1T1o+CP8HxVIo8ptoGj4W1OLBuAZ+ytIJ8MYmHVl/9D7S3B2l0pKoU/rGXuhg8F\njZBf3+6f9L/uHfuY5H+QK4R4EA5sSVPvFVtlRkpdr7r7OnIdzfYliB6XzCGcKQEN\nZetX2fNXlrtIzYE=\n-----END CERTIFICATE-----\n\n# Issuer: CN=Buypass Class 2 Root CA O=Buypass AS-983163327\n# Subject: CN=Buypass Class 2 Root CA O=Buypass AS-983163327\n# Label: \"Buypass Class 2 Root CA\"\n# Serial: 2\n# MD5 Fingerprint: 46:a7:d2:fe:45:fb:64:5a:a8:59:90:9b:78:44:9b:29\n# SHA1 Fingerprint: 49:0a:75:74:de:87:0a:47:fe:58:ee:f6:c7:6b:eb:c6:0b:12:40:99\n# SHA256 Fingerprint: 9a:11:40:25:19:7c:5b:b9:5d:94:e6:3d:55:cd:43:79:08:47:b6:46:b2:3c:df:11:ad:a4:a0:0e:ff:15:fb:48\n-----BEGIN CERTIFICATE-----\nMIIFWTCCA0GgAwIBAgIBAjANBgkqhkiG9w0BAQsFADBOMQswCQYDVQQGEwJOTzEd\nMBsGA1UECgwUQnV5cGFzcyBBUy05ODMxNjMzMjcxIDAeBgNVBAMMF0J1eXBhc3Mg\nQ2xhc3MgMiBSb290IENBMB4XDTEwMTAyNjA4MzgwM1oXDTQwMTAyNjA4MzgwM1ow\nTjELMAkGA1UEBhMCTk8xHTAbBgNVBAoMFEJ1eXBhc3MgQVMtOTgzMTYzMzI3MSAw\nHgYDVQQDDBdCdXlwYXNzIENsYXNzIDIgUm9vdCBDQTCCAiIwDQYJKoZIhvcNAQEB\nBQADggIPADCCAgoCggIBANfHXvfBB9R3+0Mh9PT1aeTuMgHbo4Yf5FkNuud1g1Lr\n6hxhFUi7HQfKjK6w3Jad6sNgkoaCKHOcVgb/S2TwDCo3SbXlzwx87vFKu3MwZfPV\nL4O2fuPn9Z6rYPnT8Z2SdIrkHJasW4DptfQxh6NR/Md+oW+OU3fUl8FVM5I+GC91\n1K2GScuVr1QGbNgGE41b/+EmGVnAJLqBcXmQRFBoJJRfuLMR8SlBYaNByyM21cHx\nMlAQTn/0hpPshNOOvEu/XAFOBz3cFIqUCqTqc/sLUegTBxj6DvEr0VQVfTzh97QZ\nQmdiXnfgolXsttlpF9U6r0TtSsWe5HonfOV116rLJeffawrbD02TTqigzXsu8lkB\narcNuAeBfos4GzjmCleZPe4h6KP1DBbdi+w0jpwqHAAVF41og9JwnxgIzRFo1clr\nUs3ERo/ctfPYV3Me6ZQ5BL/T3jjetFPsaRyifsSP5BtwrfKi+fv3FmRmaZ9JUaLi\nFRhnBkp/1Wy1TbMz4GHrXb7pmA8y1x1LPC5aAVKRCfLf6o3YBkBjqhHk/sM3nhRS\nP/TizPJhk9H9Z2vXUq6/aKtAQ6BXNVN48FP4YUIHZMbXb5tMOA1jrGKvNouicwoN\n9SG9dKpN6nIDSdvHXx1iY8f93ZHsM+71bbRuMGjeyNYmsHVee7QHIJihdjK4TWxP\nAgMBAAGjQjBAMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFMmAd+BikoL1Rpzz\nuvdMw964o605MA4GA1UdDwEB/wQEAwIBBjANBgkqhkiG9w0BAQsFAAOCAgEAU18h\n9bqwOlI5LJKwbADJ784g7wbylp7ppHR/ehb8t/W2+xUbP6umwHJdELFx7rxP462s\nA20ucS6vxOOto70MEae0/0qyexAQH6dXQbLArvQsWdZHEIjzIVEpMMpghq9Gqx3t\nOluwlN5E40EIosHsHdb9T7bWR9AUC8rmyrV7d35BH16Dx7aMOZawP5aBQW9gkOLo\n+fsicdl9sz1Gv7SEr5AcD48Saq/v7h56rgJKihcrdv6sVIkkLE8/trKnToyokZf7\nKcZ7XC25y2a2t6hbElGFtQl+Ynhw/qlqYLYdDnkM/crqJIByw5c/8nerQyIKx+u2\nDISCLIBrQYoIwOula9+ZEsuK1V6ADJHgJgg2SMX6OBE1/yWDLfJ6v9r9jv6ly0Us\nH8SIU653DtmadsWOLB2jutXsMq7Aqqz30XpN69QH4kj3Io6wpJ9qzo6ysmD0oyLQ\nI+uUWnpp3Q+/QFesa1lQ2aOZ4W7+jQF5JyMV3pKdewlNWudLSDBaGOYKbeaP4NK7\n5t98biGCwWg5TbSYWGZizEqQXsP6JwSxeRV0mcy+rSDeJmAc61ZRpqPq5KM/p/9h\n3PFaTWwyI0PurKju7koSCTxdccK+efrCh2gdC/1cacwG0Jp9VJkqyTkaGa9LKkPz\nY11aWOIv4x3kqdbQCtCev9eBCfHJxyYNrJgWVqA=\n-----END CERTIFICATE-----\n\n# Issuer: CN=Buypass Class 3 Root CA O=Buypass AS-983163327\n# Subject: CN=Buypass Class 3 Root CA O=Buypass AS-983163327\n# Label: \"Buypass Class 3 Root CA\"\n# Serial: 2\n# MD5 Fingerprint: 3d:3b:18:9e:2c:64:5a:e8:d5:88:ce:0e:f9:37:c2:ec\n# SHA1 Fingerprint: da:fa:f7:fa:66:84:ec:06:8f:14:50:bd:c7:c2:81:a5:bc:a9:64:57\n# SHA256 Fingerprint: ed:f7:eb:bc:a2:7a:2a:38:4d:38:7b:7d:40:10:c6:66:e2:ed:b4:84:3e:4c:29:b4:ae:1d:5b:93:32:e6:b2:4d\n-----BEGIN CERTIFICATE-----\nMIIFWTCCA0GgAwIBAgIBAjANBgkqhkiG9w0BAQsFADBOMQswCQYDVQQGEwJOTzEd\nMBsGA1UECgwUQnV5cGFzcyBBUy05ODMxNjMzMjcxIDAeBgNVBAMMF0J1eXBhc3Mg\nQ2xhc3MgMyBSb290IENBMB4XDTEwMTAyNjA4Mjg1OFoXDTQwMTAyNjA4Mjg1OFow\nTjELMAkGA1UEBhMCTk8xHTAbBgNVBAoMFEJ1eXBhc3MgQVMtOTgzMTYzMzI3MSAw\nHgYDVQQDDBdCdXlwYXNzIENsYXNzIDMgUm9vdCBDQTCCAiIwDQYJKoZIhvcNAQEB\nBQADggIPADCCAgoCggIBAKXaCpUWUOOV8l6ddjEGMnqb8RB2uACatVI2zSRHsJ8Y\nZLya9vrVediQYkwiL944PdbgqOkcLNt4EemOaFEVcsfzM4fkoF0LXOBXByow9c3E\nN3coTRiR5r/VUv1xLXA+58bEiuPwKAv0dpihi4dVsjoT/Lc+JzeOIuOoTyrvYLs9\ntznDDgFHmV0ST9tD+leh7fmdvhFHJlsTmKtdFoqwNxxXnUX/iJY2v7vKB3tvh2PX\n0DJq1l1sDPGzbjniazEuOQAnFN44wOwZZoYS6J1yFhNkUsepNxz9gjDthBgd9K5c\n/3ATAOux9TN6S9ZV+AWNS2mw9bMoNlwUxFFzTWsL8TQH2xc519woe2v1n/MuwU8X\nKhDzzMro6/1rqy6any2CbgTUUgGTLT2G/H783+9CHaZr77kgxve9oKeV/afmiSTY\nzIw0bOIjL9kSGiG5VZFvC5F5GQytQIgLcOJ60g7YaEi7ghM5EFjp2CoHxhLbWNvS\nO1UQRwUVZ2J+GGOmRj8JDlQyXr8NYnon74Do29lLBlo3WiXQCBJ31G8JUJc9yB3D\n34xFMFbG02SrZvPAXpacw8Tvw3xrizp5f7NJzz3iiZ+gMEuFuZyUJHmPfWupRWgP\nK9Dx2hzLabjKSWJtyNBjYt1gD1iqj6G8BaVmos8bdrKEZLFMOVLAMLrwjEsCsLa3\nAgMBAAGjQjBAMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFEe4zf/lb+74suwv\nTg75JbCOPGvDMA4GA1UdDwEB/wQEAwIBBjANBgkqhkiG9w0BAQsFAAOCAgEAACAj\nQTUEkMJAYmDv4jVM1z+s4jSQuKFvdvoWFqRINyzpkMLyPPgKn9iB5btb2iUspKdV\ncSQy9sgL8rxq+JOssgfCX5/bzMiKqr5qb+FJEMwx14C7u8jYog5kV+qi9cKpMRXS\nIGrs/CIBKM+GuIAeqcwRpTzyFrNHnfzSgCHEy9BHcEGhyoMZCCxt8l13nIoUE9Q2\nHJLw5QY33KbmkJs4j1xrG0aGQ0JfPgEHU1RdZX33inOhmlRaHylDFCfChQ+1iHsa\nO5S3HWCntZznKWlXWpuTekMwGwPXYshApqr8ZORK15FTAaggiG6cX0S5y2CBNOxv\n033aSF/rtJC8LakcC6wc1aJoIIAE1vyxjy+7SjENSoYc6+I2KSb12tjE8nVhz36u\ndmNKekBlk4f4HoCMhuWG1o8O/FMsYOgWYRqiPkN7zTlgVGr18okmAWiDSKIz6MkE\nkbIRNBE+6tBDGR8Dk5AM/1E9V/RBbuHLoL7ryWPNbczk+DaqaJ3tvV2XcEQNtg41\n3OEMXbugUZTLfhbrES+jkkXITHHZvMmZUldGL1DPvTVp9D0VzgalLA8+9oG6lLvD\nu79leNKGef9JOxqDDPDeeOzI8k1MGt6CKfjBWtrt7uYnXuhF0J0cUahoq0Tj0Itq\n4/g7u9xN12TyUb7mqqta6THuBrxzvxNiCp/HuZc=\n-----END CERTIFICATE-----\n\n# Issuer: CN=T-TeleSec GlobalRoot Class 3 O=T-Systems Enterprise Services GmbH OU=T-Systems Trust Center\n# Subject: CN=T-TeleSec GlobalRoot Class 3 O=T-Systems Enterprise Services GmbH OU=T-Systems Trust Center\n# Label: \"T-TeleSec GlobalRoot Class 3\"\n# Serial: 1\n# MD5 Fingerprint: ca:fb:40:a8:4e:39:92:8a:1d:fe:8e:2f:c4:27:ea:ef\n# SHA1 Fingerprint: 55:a6:72:3e:cb:f2:ec:cd:c3:23:74:70:19:9d:2a:be:11:e3:81:d1\n# SHA256 Fingerprint: fd:73:da:d3:1c:64:4f:f1:b4:3b:ef:0c:cd:da:96:71:0b:9c:d9:87:5e:ca:7e:31:70:7a:f3:e9:6d:52:2b:bd\n-----BEGIN CERTIFICATE-----\nMIIDwzCCAqugAwIBAgIBATANBgkqhkiG9w0BAQsFADCBgjELMAkGA1UEBhMCREUx\nKzApBgNVBAoMIlQtU3lzdGVtcyBFbnRlcnByaXNlIFNlcnZpY2VzIEdtYkgxHzAd\nBgNVBAsMFlQtU3lzdGVtcyBUcnVzdCBDZW50ZXIxJTAjBgNVBAMMHFQtVGVsZVNl\nYyBHbG9iYWxSb290IENsYXNzIDMwHhcNMDgxMDAxMTAyOTU2WhcNMzMxMDAxMjM1\nOTU5WjCBgjELMAkGA1UEBhMCREUxKzApBgNVBAoMIlQtU3lzdGVtcyBFbnRlcnBy\naXNlIFNlcnZpY2VzIEdtYkgxHzAdBgNVBAsMFlQtU3lzdGVtcyBUcnVzdCBDZW50\nZXIxJTAjBgNVBAMMHFQtVGVsZVNlYyBHbG9iYWxSb290IENsYXNzIDMwggEiMA0G\nCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQC9dZPwYiJvJK7genasfb3ZJNW4t/zN\n8ELg63iIVl6bmlQdTQyK9tPPcPRStdiTBONGhnFBSivwKixVA9ZIw+A5OO3yXDw/\nRLyTPWGrTs0NvvAgJ1gORH8EGoel15YUNpDQSXuhdfsaa3Ox+M6pCSzyU9XDFES4\nhqX2iys52qMzVNn6chr3IhUciJFrf2blw2qAsCTz34ZFiP0Zf3WHHx+xGwpzJFu5\nZeAsVMhg02YXP+HMVDNzkQI6pn97djmiH5a2OK61yJN0HZ65tOVgnS9W0eDrXltM\nEnAMbEQgqxHY9Bn20pxSN+f6tsIxO0rUFJmtxxr1XV/6B7h8DR/Wgx6zAgMBAAGj\nQjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgEGMB0GA1UdDgQWBBS1\nA/d2O2GCahKqGFPrAyGUv/7OyjANBgkqhkiG9w0BAQsFAAOCAQEAVj3vlNW92nOy\nWL6ukK2YJ5f+AbGwUgC4TeQbIXQbfsDuXmkqJa9c1h3a0nnJ85cp4IaH3gRZD/FZ\n1GSFS5mvJQQeyUapl96Cshtwn5z2r3Ex3XsFpSzTucpH9sry9uetuUg/vBa3wW30\n6gmv7PO15wWeph6KU1HWk4HMdJP2udqmJQV0eVp+QD6CSyYRMG7hP0HHRwA11fXT\n91Q+gT3aSWqas+8QPebrb9HIIkfLzM8BMZLZGOMivgkeGj5asuRrDFR6fUNOuIml\ne9eiPZaGzPImNC1qkp2aGtAw4l1OBLBfiyB+d8E9lYLRRpo7PHi4b6HQDWSieB4p\nTpPDpFQUWw==\n-----END CERTIFICATE-----\n\n# Issuer: CN=EE Certification Centre Root CA O=AS Sertifitseerimiskeskus\n# Subject: CN=EE Certification Centre Root CA O=AS Sertifitseerimiskeskus\n# Label: \"EE Certification Centre Root CA\"\n# Serial: 112324828676200291871926431888494945866\n# MD5 Fingerprint: 43:5e:88:d4:7d:1a:4a:7e:fd:84:2e:52:eb:01:d4:6f\n# SHA1 Fingerprint: c9:a8:b9:e7:55:80:5e:58:e3:53:77:a7:25:eb:af:c3:7b:27:cc:d7\n# SHA256 Fingerprint: 3e:84:ba:43:42:90:85:16:e7:75:73:c0:99:2f:09:79:ca:08:4e:46:85:68:1f:f1:95:cc:ba:8a:22:9b:8a:76\n-----BEGIN CERTIFICATE-----\nMIIEAzCCAuugAwIBAgIQVID5oHPtPwBMyonY43HmSjANBgkqhkiG9w0BAQUFADB1\nMQswCQYDVQQGEwJFRTEiMCAGA1UECgwZQVMgU2VydGlmaXRzZWVyaW1pc2tlc2t1\nczEoMCYGA1UEAwwfRUUgQ2VydGlmaWNhdGlvbiBDZW50cmUgUm9vdCBDQTEYMBYG\nCSqGSIb3DQEJARYJcGtpQHNrLmVlMCIYDzIwMTAxMDMwMTAxMDMwWhgPMjAzMDEy\nMTcyMzU5NTlaMHUxCzAJBgNVBAYTAkVFMSIwIAYDVQQKDBlBUyBTZXJ0aWZpdHNl\nZXJpbWlza2Vza3VzMSgwJgYDVQQDDB9FRSBDZXJ0aWZpY2F0aW9uIENlbnRyZSBS\nb290IENBMRgwFgYJKoZIhvcNAQkBFglwa2lAc2suZWUwggEiMA0GCSqGSIb3DQEB\nAQUAA4IBDwAwggEKAoIBAQDIIMDs4MVLqwd4lfNE7vsLDP90jmG7sWLqI9iroWUy\neuuOF0+W2Ap7kaJjbMeMTC55v6kF/GlclY1i+blw7cNRfdCT5mzrMEvhvH2/UpvO\nbntl8jixwKIy72KyaOBhU8E2lf/slLo2rpwcpzIP5Xy0xm90/XsY6KxX7QYgSzIw\nWFv9zajmofxwvI6Sc9uXp3whrj3B9UiHbCe9nyV0gVWw93X2PaRka9ZP585ArQ/d\nMtO8ihJTmMmJ+xAdTX7Nfh9WDSFwhfYggx/2uh8Ej+p3iDXE/+pOoYtNP2MbRMNE\n1CV2yreN1x5KZmTNXMWcg+HCCIia7E6j8T4cLNlsHaFLAgMBAAGjgYowgYcwDwYD\nVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYEFBLyWj7qVhy/\nzQas8fElyalL1BSZMEUGA1UdJQQ+MDwGCCsGAQUFBwMCBggrBgEFBQcDAQYIKwYB\nBQUHAwMGCCsGAQUFBwMEBggrBgEFBQcDCAYIKwYBBQUHAwkwDQYJKoZIhvcNAQEF\nBQADggEBAHv25MANqhlHt01Xo/6tu7Fq1Q+e2+RjxY6hUFaTlrg4wCQiZrxTFGGV\nv9DHKpY5P30osxBAIWrEr7BSdxjhlthWXePdNl4dp1BUoMUq5KqMlIpPnTX/dqQG\nE5Gion0ARD9V04I8GtVbvFZMIi5GQ4okQC3zErg7cBqklrkar4dBGmoYDQZPxz5u\nuSlNDUmJEYcyW+ZLBMjkXOZ0c5RdFpgTlf7727FE5TpwrDdr5rMzcijJs1eg9gIW\niAYLtqZLICjU3j2LrTcFU3T+bsy8QxdxXvnFzBqpYe73dgzzcvRyrc9yAjYHR8/v\nGVCJYMzpJJUPwssd8m92kMfMdcGWxZ0=\n-----END CERTIFICATE-----\n\n# Issuer: CN=D-TRUST Root Class 3 CA 2 2009 O=D-Trust GmbH\n# Subject: CN=D-TRUST Root Class 3 CA 2 2009 O=D-Trust GmbH\n# Label: \"D-TRUST Root Class 3 CA 2 2009\"\n# Serial: 623603\n# MD5 Fingerprint: cd:e0:25:69:8d:47:ac:9c:89:35:90:f7:fd:51:3d:2f\n# SHA1 Fingerprint: 58:e8:ab:b0:36:15:33:fb:80:f7:9b:1b:6d:29:d3:ff:8d:5f:00:f0\n# SHA256 Fingerprint: 49:e7:a4:42:ac:f0:ea:62:87:05:00:54:b5:25:64:b6:50:e4:f4:9e:42:e3:48:d6:aa:38:e0:39:e9:57:b1:c1\n-----BEGIN CERTIFICATE-----\nMIIEMzCCAxugAwIBAgIDCYPzMA0GCSqGSIb3DQEBCwUAME0xCzAJBgNVBAYTAkRF\nMRUwEwYDVQQKDAxELVRydXN0IEdtYkgxJzAlBgNVBAMMHkQtVFJVU1QgUm9vdCBD\nbGFzcyAzIENBIDIgMjAwOTAeFw0wOTExMDUwODM1NThaFw0yOTExMDUwODM1NTha\nME0xCzAJBgNVBAYTAkRFMRUwEwYDVQQKDAxELVRydXN0IEdtYkgxJzAlBgNVBAMM\nHkQtVFJVU1QgUm9vdCBDbGFzcyAzIENBIDIgMjAwOTCCASIwDQYJKoZIhvcNAQEB\nBQADggEPADCCAQoCggEBANOySs96R+91myP6Oi/WUEWJNTrGa9v+2wBoqOADER03\nUAifTUpolDWzU9GUY6cgVq/eUXjsKj3zSEhQPgrfRlWLJ23DEE0NkVJD2IfgXU42\ntSHKXzlABF9bfsyjxiupQB7ZNoTWSPOSHjRGICTBpFGOShrvUD9pXRl/RcPHAY9R\nySPocq60vFYJfxLLHLGvKZAKyVXMD9O0Gu1HNVpK7ZxzBCHQqr0ME7UAyiZsxGsM\nlFqVlNpQmvH/pStmMaTJOKDfHR+4CS7zp+hnUquVH+BGPtikw8paxTGA6Eian5Rp\n/hnd2HN8gcqW3o7tszIFZYQ05ub9VxC1X3a/L7AQDcUCAwEAAaOCARowggEWMA8G\nA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFP3aFMSfMN4hvR5COfyrYyNJ4PGEMA4G\nA1UdDwEB/wQEAwIBBjCB0wYDVR0fBIHLMIHIMIGAoH6gfIZ6bGRhcDovL2RpcmVj\ndG9yeS5kLXRydXN0Lm5ldC9DTj1ELVRSVVNUJTIwUm9vdCUyMENsYXNzJTIwMyUy\nMENBJTIwMiUyMDIwMDksTz1ELVRydXN0JTIwR21iSCxDPURFP2NlcnRpZmljYXRl\ncmV2b2NhdGlvbmxpc3QwQ6BBoD+GPWh0dHA6Ly93d3cuZC10cnVzdC5uZXQvY3Js\nL2QtdHJ1c3Rfcm9vdF9jbGFzc18zX2NhXzJfMjAwOS5jcmwwDQYJKoZIhvcNAQEL\nBQADggEBAH+X2zDI36ScfSF6gHDOFBJpiBSVYEQBrLLpME+bUMJm2H6NMLVwMeni\nacfzcNsgFYbQDfC+rAF1hM5+n02/t2A7nPPKHeJeaNijnZflQGDSNiH+0LS4F9p0\no3/U37CYAqxva2ssJSRyoWXuJVrl5jLn8t+rSfrzkGkj2wTZ51xY/GXUl77M/C4K\nzCUqNQT4YJEVdT1B/yMfGchs64JTBKbkTCJNjYy6zltz7GRUUG3RnFX7acM2w4y8\nPIWmawomDeCTmGCufsYkl4phX5GOZpIJhzbNi5stPvZR1FDUWSi9g/LMKHtThm3Y\nJohw1+qRzT65ysCQblrGXnRl11z+o+I=\n-----END CERTIFICATE-----\n\n# Issuer: CN=D-TRUST Root Class 3 CA 2 EV 2009 O=D-Trust GmbH\n# Subject: CN=D-TRUST Root Class 3 CA 2 EV 2009 O=D-Trust GmbH\n# Label: \"D-TRUST Root Class 3 CA 2 EV 2009\"\n# Serial: 623604\n# MD5 Fingerprint: aa:c6:43:2c:5e:2d:cd:c4:34:c0:50:4f:11:02:4f:b6\n# SHA1 Fingerprint: 96:c9:1b:0b:95:b4:10:98:42:fa:d0:d8:22:79:fe:60:fa:b9:16:83\n# SHA256 Fingerprint: ee:c5:49:6b:98:8c:e9:86:25:b9:34:09:2e:ec:29:08:be:d0:b0:f3:16:c2:d4:73:0c:84:ea:f1:f3:d3:48:81\n-----BEGIN CERTIFICATE-----\nMIIEQzCCAyugAwIBAgIDCYP0MA0GCSqGSIb3DQEBCwUAMFAxCzAJBgNVBAYTAkRF\nMRUwEwYDVQQKDAxELVRydXN0IEdtYkgxKjAoBgNVBAMMIUQtVFJVU1QgUm9vdCBD\nbGFzcyAzIENBIDIgRVYgMjAwOTAeFw0wOTExMDUwODUwNDZaFw0yOTExMDUwODUw\nNDZaMFAxCzAJBgNVBAYTAkRFMRUwEwYDVQQKDAxELVRydXN0IEdtYkgxKjAoBgNV\nBAMMIUQtVFJVU1QgUm9vdCBDbGFzcyAzIENBIDIgRVYgMjAwOTCCASIwDQYJKoZI\nhvcNAQEBBQADggEPADCCAQoCggEBAJnxhDRwui+3MKCOvXwEz75ivJn9gpfSegpn\nljgJ9hBOlSJzmY3aFS3nBfwZcyK3jpgAvDw9rKFs+9Z5JUut8Mxk2og+KbgPCdM0\n3TP1YtHhzRnp7hhPTFiu4h7WDFsVWtg6uMQYZB7jM7K1iXdODL/ZlGsTl28So/6Z\nqQTMFexgaDbtCHu39b+T7WYxg4zGcTSHThfqr4uRjRxWQa4iN1438h3Z0S0NL2lR\np75mpoo6Kr3HGrHhFPC+Oh25z1uxav60sUYgovseO3Dvk5h9jHOW8sXvhXCtKSb8\nHgQ+HKDYD8tSg2J87otTlZCpV6LqYQXY+U3EJ/pure3511H3a6UCAwEAAaOCASQw\nggEgMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFNOUikxiEyoZLsyvcop9Ntea\nHNxnMA4GA1UdDwEB/wQEAwIBBjCB3QYDVR0fBIHVMIHSMIGHoIGEoIGBhn9sZGFw\nOi8vZGlyZWN0b3J5LmQtdHJ1c3QubmV0L0NOPUQtVFJVU1QlMjBSb290JTIwQ2xh\nc3MlMjAzJTIwQ0ElMjAyJTIwRVYlMjAyMDA5LE89RC1UcnVzdCUyMEdtYkgsQz1E\nRT9jZXJ0aWZpY2F0ZXJldm9jYXRpb25saXN0MEagRKBChkBodHRwOi8vd3d3LmQt\ndHJ1c3QubmV0L2NybC9kLXRydXN0X3Jvb3RfY2xhc3NfM19jYV8yX2V2XzIwMDku\nY3JsMA0GCSqGSIb3DQEBCwUAA4IBAQA07XtaPKSUiO8aEXUHL7P+PPoeUSbrh/Yp\n3uDx1MYkCenBz1UbtDDZzhr+BlGmFaQt77JLvyAoJUnRpjZ3NOhk31KxEcdzes05\nnsKtjHEh8lprr988TlWvsoRlFIm5d8sqMb7Po23Pb0iUMkZv53GMoKaEGTcH8gNF\nCSuGdXzfX2lXANtu2KZyIktQ1HWYVt+3GP9DQ1CuekR78HlR10M9p9OB0/DJT7na\nxpeG0ILD5EJt/rDiZE4OJudANCa1CInXCGNjOCd1HjPqbqjdn5lPdE2BiYBL3ZqX\nKVwvvoFBuYz/6n1gBp7N1z3TLqMVvKjmJuVvw9y4AyHqnxbxLFS1\n-----END CERTIFICATE-----\n\n# Issuer: CN=CA Disig Root R2 O=Disig a.s.\n# Subject: CN=CA Disig Root R2 O=Disig a.s.\n# Label: \"CA Disig Root R2\"\n# Serial: 10572350602393338211\n# MD5 Fingerprint: 26:01:fb:d8:27:a7:17:9a:45:54:38:1a:43:01:3b:03\n# SHA1 Fingerprint: b5:61:eb:ea:a4:de:e4:25:4b:69:1a:98:a5:57:47:c2:34:c7:d9:71\n# SHA256 Fingerprint: e2:3d:4a:03:6d:7b:70:e9:f5:95:b1:42:20:79:d2:b9:1e:df:bb:1f:b6:51:a0:63:3e:aa:8a:9d:c5:f8:07:03\n-----BEGIN CERTIFICATE-----\nMIIFaTCCA1GgAwIBAgIJAJK4iNuwisFjMA0GCSqGSIb3DQEBCwUAMFIxCzAJBgNV\nBAYTAlNLMRMwEQYDVQQHEwpCcmF0aXNsYXZhMRMwEQYDVQQKEwpEaXNpZyBhLnMu\nMRkwFwYDVQQDExBDQSBEaXNpZyBSb290IFIyMB4XDTEyMDcxOTA5MTUzMFoXDTQy\nMDcxOTA5MTUzMFowUjELMAkGA1UEBhMCU0sxEzARBgNVBAcTCkJyYXRpc2xhdmEx\nEzARBgNVBAoTCkRpc2lnIGEucy4xGTAXBgNVBAMTEENBIERpc2lnIFJvb3QgUjIw\nggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQCio8QACdaFXS1tFPbCw3Oe\nNcJxVX6B+6tGUODBfEl45qt5WDza/3wcn9iXAng+a0EE6UG9vgMsRfYvZNSrXaNH\nPWSb6WiaxswbP7q+sos0Ai6YVRn8jG+qX9pMzk0DIaPY0jSTVpbLTAwAFjxfGs3I\nx2ymrdMxp7zo5eFm1tL7A7RBZckQrg4FY8aAamkw/dLukO8NJ9+flXP04SXabBbe\nQTg06ov80egEFGEtQX6sx3dOy1FU+16SGBsEWmjGycT6txOgmLcRK7fWV8x8nhfR\nyyX+hk4kLlYMeE2eARKmK6cBZW58Yh2EhN/qwGu1pSqVg8NTEQxzHQuyRpDRQjrO\nQG6Vrf/GlK1ul4SOfW+eioANSW1z4nuSHsPzwfPrLgVv2RvPN3YEyLRa5Beny912\nH9AZdugsBbPWnDTYltxhh5EF5EQIM8HauQhl1K6yNg3ruji6DOWbnuuNZt2Zz9aJ\nQfYEkoopKW1rOhzndX0CcQ7zwOe9yxndnWCywmZgtrEE7snmhrmaZkCo5xHtgUUD\ni/ZnWejBBhG93c+AAk9lQHhcR1DIm+YfgXvkRKhbhZri3lrVx/k6RGZL5DJUfORs\nnLMOPReisjQS1n6yqEm70XooQL6iFh/f5DcfEXP7kAplQ6INfPgGAVUzfbANuPT1\nrqVCV3w2EYx7XsQDnYx5nQIDAQABo0IwQDAPBgNVHRMBAf8EBTADAQH/MA4GA1Ud\nDwEB/wQEAwIBBjAdBgNVHQ4EFgQUtZn4r7CU9eMg1gqtzk5WpC5uQu0wDQYJKoZI\nhvcNAQELBQADggIBACYGXnDnZTPIgm7ZnBc6G3pmsgH2eDtpXi/q/075KMOYKmFM\ntCQSin1tERT3nLXK5ryeJ45MGcipvXrA1zYObYVybqjGom32+nNjf7xueQgcnYqf\nGopTpti72TVVsRHFqQOzVju5hJMiXn7B9hJSi+osZ7z+Nkz1uM/Rs0mSO9MpDpkb\nlvdhuDvEK7Z4bLQjb/D907JedR+Zlais9trhxTF7+9FGs9K8Z7RiVLoJ92Owk6Ka\n+elSLotgEqv89WBW7xBci8QaQtyDW2QOy7W81k/BfDxujRNt+3vrMNDcTa/F1bal\nTFtxyegxvug4BkihGuLq0t4SOVga/4AOgnXmt8kHbA7v/zjxmHHEt38OFdAlab0i\nnSvtBfZGR6ztwPDUO+Ls7pZbkBNOHlY667DvlruWIxG68kOGdGSVyCh13x01utI3\ngzhTODY7z2zp+WsO0PsE6E9312UBeIYMej4hYvF/Y3EMyZ9E26gnonW+boE+18Dr\nG5gPcFw0sorMwIUY6256s/daoQe/qUKS82Ail+QUoQebTnbAjn39pCXHR+3/H3Os\nzMOl6W8KjptlwlCFtaOgUxLMVYdh84GuEEZhvUQhuMI9dM9+JDX6HAcOmz0iyu8x\nL4ysEr3vQCj8KWefshNPZiTEUxnpHikV7+ZtsH8tZ/3zbBt1RqPlShfppNcL\n-----END CERTIFICATE-----\n\n# Issuer: CN=ACCVRAIZ1 O=ACCV OU=PKIACCV\n# Subject: CN=ACCVRAIZ1 O=ACCV OU=PKIACCV\n# Label: \"ACCVRAIZ1\"\n# Serial: 6828503384748696800\n# MD5 Fingerprint: d0:a0:5a:ee:05:b6:09:94:21:a1:7d:f1:b2:29:82:02\n# SHA1 Fingerprint: 93:05:7a:88:15:c6:4f:ce:88:2f:fa:91:16:52:28:78:bc:53:64:17\n# SHA256 Fingerprint: 9a:6e:c0:12:e1:a7:da:9d:be:34:19:4d:47:8a:d7:c0:db:18:22:fb:07:1d:f1:29:81:49:6e:d1:04:38:41:13\n-----BEGIN CERTIFICATE-----\nMIIH0zCCBbugAwIBAgIIXsO3pkN/pOAwDQYJKoZIhvcNAQEFBQAwQjESMBAGA1UE\nAwwJQUNDVlJBSVoxMRAwDgYDVQQLDAdQS0lBQ0NWMQ0wCwYDVQQKDARBQ0NWMQsw\nCQYDVQQGEwJFUzAeFw0xMTA1MDUwOTM3MzdaFw0zMDEyMzEwOTM3MzdaMEIxEjAQ\nBgNVBAMMCUFDQ1ZSQUlaMTEQMA4GA1UECwwHUEtJQUNDVjENMAsGA1UECgwEQUND\nVjELMAkGA1UEBhMCRVMwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQCb\nqau/YUqXry+XZpp0X9DZlv3P4uRm7x8fRzPCRKPfmt4ftVTdFXxpNRFvu8gMjmoY\nHtiP2Ra8EEg2XPBjs5BaXCQ316PWywlxufEBcoSwfdtNgM3802/J+Nq2DoLSRYWo\nG2ioPej0RGy9ocLLA76MPhMAhN9KSMDjIgro6TenGEyxCQ0jVn8ETdkXhBilyNpA\nlHPrzg5XPAOBOp0KoVdDaaxXbXmQeOW1tDvYvEyNKKGno6e6Ak4l0Squ7a4DIrhr\nIA8wKFSVf+DuzgpmndFALW4ir50awQUZ0m/A8p/4e7MCQvtQqR0tkw8jq8bBD5L/\n0KIV9VMJcRz/RROE5iZe+OCIHAr8Fraocwa48GOEAqDGWuzndN9wrqODJerWx5eH\nk6fGioozl2A3ED6XPm4pFdahD9GILBKfb6qkxkLrQaLjlUPTAYVtjrs78yM2x/47\n4KElB0iryYl0/wiPgL/AlmXz7uxLaL2diMMxs0Dx6M/2OLuc5NF/1OVYm3z61PMO\nm3WR5LpSLhl+0fXNWhn8ugb2+1KoS5kE3fj5tItQo05iifCHJPqDQsGH+tUtKSpa\ncXpkatcnYGMN285J9Y0fkIkyF/hzQ7jSWpOGYdbhdQrqeWZ2iE9x6wQl1gpaepPl\nuUsXQA+xtrn13k/c4LOsOxFwYIRKQ26ZIMApcQrAZQIDAQABo4ICyzCCAscwfQYI\nKwYBBQUHAQEEcTBvMEwGCCsGAQUFBzAChkBodHRwOi8vd3d3LmFjY3YuZXMvZmls\nZWFkbWluL0FyY2hpdm9zL2NlcnRpZmljYWRvcy9yYWl6YWNjdjEuY3J0MB8GCCsG\nAQUFBzABhhNodHRwOi8vb2NzcC5hY2N2LmVzMB0GA1UdDgQWBBTSh7Tj3zcnk1X2\nVuqB5TbMjB4/vTAPBgNVHRMBAf8EBTADAQH/MB8GA1UdIwQYMBaAFNKHtOPfNyeT\nVfZW6oHlNsyMHj+9MIIBcwYDVR0gBIIBajCCAWYwggFiBgRVHSAAMIIBWDCCASIG\nCCsGAQUFBwICMIIBFB6CARAAQQB1AHQAbwByAGkAZABhAGQAIABkAGUAIABDAGUA\ncgB0AGkAZgBpAGMAYQBjAGkA8wBuACAAUgBhAO0AegAgAGQAZQAgAGwAYQAgAEEA\nQwBDAFYAIAAoAEEAZwBlAG4AYwBpAGEAIABkAGUAIABUAGUAYwBuAG8AbABvAGcA\n7QBhACAAeQAgAEMAZQByAHQAaQBmAGkAYwBhAGMAaQDzAG4AIABFAGwAZQBjAHQA\ncgDzAG4AaQBjAGEALAAgAEMASQBGACAAUQA0ADYAMAAxADEANQA2AEUAKQAuACAA\nQwBQAFMAIABlAG4AIABoAHQAdABwADoALwAvAHcAdwB3AC4AYQBjAGMAdgAuAGUA\nczAwBggrBgEFBQcCARYkaHR0cDovL3d3dy5hY2N2LmVzL2xlZ2lzbGFjaW9uX2Mu\naHRtMFUGA1UdHwROMEwwSqBIoEaGRGh0dHA6Ly93d3cuYWNjdi5lcy9maWxlYWRt\naW4vQXJjaGl2b3MvY2VydGlmaWNhZG9zL3JhaXphY2N2MV9kZXIuY3JsMA4GA1Ud\nDwEB/wQEAwIBBjAXBgNVHREEEDAOgQxhY2N2QGFjY3YuZXMwDQYJKoZIhvcNAQEF\nBQADggIBAJcxAp/n/UNnSEQU5CmH7UwoZtCPNdpNYbdKl02125DgBS4OxnnQ8pdp\nD70ER9m+27Up2pvZrqmZ1dM8MJP1jaGo/AaNRPTKFpV8M9xii6g3+CfYCS0b78gU\nJyCpZET/LtZ1qmxNYEAZSUNUY9rizLpm5U9EelvZaoErQNV/+QEnWCzI7UiRfD+m\nAM/EKXMRNt6GGT6d7hmKG9Ww7Y49nCrADdg9ZuM8Db3VlFzi4qc1GwQA9j9ajepD\nvV+JHanBsMyZ4k0ACtrJJ1vnE5Bc5PUzolVt3OAJTS+xJlsndQAJxGJ3KQhfnlms\ntn6tn1QwIgPBHnFk/vk4CpYY3QIUrCPLBhwepH2NDd4nQeit2hW3sCPdK6jT2iWH\n7ehVRE2I9DZ+hJp4rPcOVkkO1jMl1oRQQmwgEh0q1b688nCBpHBgvgW1m54ERL5h\nI6zppSSMEYCUWqKiuUnSwdzRp+0xESyeGabu4VXhwOrPDYTkF7eifKXeVSUG7szA\nh1xA2syVP1XgNce4hL60Xc16gwFy7ofmXx2utYXGJt/mwZrpHgJHnyqobalbz+xF\nd3+YJ5oyXSrjhO7FmGYvliAd3djDJ9ew+f7Zfc3Qn48LFFhRny+Lwzgt3uiP1o2H\npPVWQxaZLPSkVrQ0uGE3ycJYgBugl6H8WY3pEfbRD0tVNEYqi4Y7\n-----END CERTIFICATE-----\n\n# Issuer: CN=TWCA Global Root CA O=TAIWAN-CA OU=Root CA\n# Subject: CN=TWCA Global Root CA O=TAIWAN-CA OU=Root CA\n# Label: \"TWCA Global Root CA\"\n# Serial: 3262\n# MD5 Fingerprint: f9:03:7e:cf:e6:9e:3c:73:7a:2a:90:07:69:ff:2b:96\n# SHA1 Fingerprint: 9c:bb:48:53:f6:a4:f6:d3:52:a4:e8:32:52:55:60:13:f5:ad:af:65\n# SHA256 Fingerprint: 59:76:90:07:f7:68:5d:0f:cd:50:87:2f:9f:95:d5:75:5a:5b:2b:45:7d:81:f3:69:2b:61:0a:98:67:2f:0e:1b\n-----BEGIN CERTIFICATE-----\nMIIFQTCCAymgAwIBAgICDL4wDQYJKoZIhvcNAQELBQAwUTELMAkGA1UEBhMCVFcx\nEjAQBgNVBAoTCVRBSVdBTi1DQTEQMA4GA1UECxMHUm9vdCBDQTEcMBoGA1UEAxMT\nVFdDQSBHbG9iYWwgUm9vdCBDQTAeFw0xMjA2MjcwNjI4MzNaFw0zMDEyMzExNTU5\nNTlaMFExCzAJBgNVBAYTAlRXMRIwEAYDVQQKEwlUQUlXQU4tQ0ExEDAOBgNVBAsT\nB1Jvb3QgQ0ExHDAaBgNVBAMTE1RXQ0EgR2xvYmFsIFJvb3QgQ0EwggIiMA0GCSqG\nSIb3DQEBAQUAA4ICDwAwggIKAoICAQCwBdvI64zEbooh745NnHEKH1Jw7W2CnJfF\n10xORUnLQEK1EjRsGcJ0pDFfhQKX7EMzClPSnIyOt7h52yvVavKOZsTuKwEHktSz\n0ALfUPZVr2YOy+BHYC8rMjk1Ujoog/h7FsYYuGLWRyWRzvAZEk2tY/XTP3VfKfCh\nMBwqoJimFb3u/Rk28OKRQ4/6ytYQJ0lM793B8YVwm8rqqFpD/G2Gb3PpN0Wp8DbH\nzIh1HrtsBv+baz4X7GGqcXzGHaL3SekVtTzWoWH1EfcFbx39Eb7QMAfCKbAJTibc\n46KokWofwpFFiFzlmLhxpRUZyXx1EcxwdE8tmx2RRP1WKKD+u4ZqyPpcC1jcxkt2\nyKsi2XMPpfRaAok/T54igu6idFMqPVMnaR1sjjIsZAAmY2E2TqNGtz99sy2sbZCi\nlaLOz9qC5wc0GZbpuCGqKX6mOL6OKUohZnkfs8O1CWfe1tQHRvMq2uYiN2DLgbYP\noA/pyJV/v1WRBXrPPRXAb94JlAGD1zQbzECl8LibZ9WYkTunhHiVJqRaCPgrdLQA\nBDzfuBSO6N+pjWxnkjMdwLfS7JLIvgm/LCkFbwJrnu+8vyq8W8BQj0FwcYeyTbcE\nqYSjMq+u7msXi7Kx/mzhkIyIqJdIzshNy/MGz19qCkKxHh53L46g5pIOBvwFItIm\n4TFRfTLcDwIDAQABoyMwITAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB\n/zANBgkqhkiG9w0BAQsFAAOCAgEAXzSBdu+WHdXltdkCY4QWwa6gcFGn90xHNcgL\n1yg9iXHZqjNB6hQbbCEAwGxCGX6faVsgQt+i0trEfJdLjbDorMjupWkEmQqSpqsn\nLhpNgb+E1HAerUf+/UqdM+DyucRFCCEK2mlpc3INvjT+lIutwx4116KD7+U4x6WF\nH6vPNOw/KP4M8VeGTslV9xzU2KV9Bnpv1d8Q34FOIWWxtuEXeZVFBs5fzNxGiWNo\nRI2T9GRwoD2dKAXDOXC4Ynsg/eTb6QihuJ49CcdP+yz4k3ZB3lLg4VfSnQO8d57+\nnile98FRYB/e2guyLXW3Q0iT5/Z5xoRdgFlglPx4mI88k1HtQJAH32RjJMtOcQWh\n15QaiDLxInQirqWm2BJpTGCjAu4r7NRjkgtevi92a6O2JryPA9gK8kxkRr05YuWW\n6zRjESjMlfGt7+/cgFhI6Uu46mWs6fyAtbXIRfmswZ/ZuepiiI7E8UuDEq3mi4TW\nnsLrgxifarsbJGAzcMzs9zLzXNl5fe+epP7JI8Mk7hWSsT2RTyaGvWZzJBPqpK5j\nwa19hAM8EHiGG3njxPPyBJUgriOCxLM6AGK/5jYk4Ve6xx6QddVfP5VhK8E7zeWz\naGHQRiapIVJpLesux+t3zqY6tQMzT3bR51xUAV3LePTJDL/PEo4XLSNolOer/qmy\nKwbQBM0=\n-----END CERTIFICATE-----\n\n# Issuer: CN=TeliaSonera Root CA v1 O=TeliaSonera\n# Subject: CN=TeliaSonera Root CA v1 O=TeliaSonera\n# Label: \"TeliaSonera Root CA v1\"\n# Serial: 199041966741090107964904287217786801558\n# MD5 Fingerprint: 37:41:49:1b:18:56:9a:26:f5:ad:c2:66:fb:40:a5:4c\n# SHA1 Fingerprint: 43:13:bb:96:f1:d5:86:9b:c1:4e:6a:92:f6:cf:f6:34:69:87:82:37\n# SHA256 Fingerprint: dd:69:36:fe:21:f8:f0:77:c1:23:a1:a5:21:c1:22:24:f7:22:55:b7:3e:03:a7:26:06:93:e8:a2:4b:0f:a3:89\n-----BEGIN CERTIFICATE-----\nMIIFODCCAyCgAwIBAgIRAJW+FqD3LkbxezmCcvqLzZYwDQYJKoZIhvcNAQEFBQAw\nNzEUMBIGA1UECgwLVGVsaWFTb25lcmExHzAdBgNVBAMMFlRlbGlhU29uZXJhIFJv\nb3QgQ0EgdjEwHhcNMDcxMDE4MTIwMDUwWhcNMzIxMDE4MTIwMDUwWjA3MRQwEgYD\nVQQKDAtUZWxpYVNvbmVyYTEfMB0GA1UEAwwWVGVsaWFTb25lcmEgUm9vdCBDQSB2\nMTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBAMK+6yfwIaPzaSZVfp3F\nVRaRXP3vIb9TgHot0pGMYzHw7CTww6XScnwQbfQ3t+XmfHnqjLWCi65ItqwA3GV1\n7CpNX8GH9SBlK4GoRz6JI5UwFpB/6FcHSOcZrr9FZ7E3GwYq/t75rH2D+1665I+X\nZ75Ljo1kB1c4VWk0Nj0TSO9P4tNmHqTPGrdeNjPUtAa9GAH9d4RQAEX1jF3oI7x+\n/jXh7VB7qTCNGdMJjmhnXb88lxhTuylixcpecsHHltTbLaC0H2kD7OriUPEMPPCs\n81Mt8Bz17Ww5OXOAFshSsCPN4D7c3TxHoLs1iuKYaIu+5b9y7tL6pe0S7fyYGKkm\ndtwoSxAgHNN/Fnct7W+A90m7UwW7XWjH1Mh1Fj+JWov3F0fUTPHSiXk+TT2YqGHe\nOh7S+F4D4MHJHIzTjU3TlTazN19jY5szFPAtJmtTfImMMsJu7D0hADnJoWjiUIMu\nsDor8zagrC/kb2HCUQk5PotTubtn2txTuXZZNp1D5SDgPTJghSJRt8czu90VL6R4\npgd7gUY2BIbdeTXHlSw7sKMXNeVzH7RcWe/a6hBle3rQf5+ztCo3O3CLm1u5K7fs\nslESl1MpWtTwEhDcTwK7EpIvYtQ/aUN8Ddb8WHUBiJ1YFkveupD/RwGJBmr2X7KQ\narMCpgKIv7NHfirZ1fpoeDVNAgMBAAGjPzA9MA8GA1UdEwEB/wQFMAMBAf8wCwYD\nVR0PBAQDAgEGMB0GA1UdDgQWBBTwj1k4ALP1j5qWDNXr+nuqF+gTEjANBgkqhkiG\n9w0BAQUFAAOCAgEAvuRcYk4k9AwI//DTDGjkk0kiP0Qnb7tt3oNmzqjMDfz1mgbl\ndxSR651Be5kqhOX//CHBXfDkH1e3damhXwIm/9fH907eT/j3HEbAek9ALCI18Bmx\n0GtnLLCo4MBANzX2hFxc469CeP6nyQ1Q6g2EdvZR74NTxnr/DlZJLo961gzmJ1Tj\nTQpgcmLNkQfWpb/ImWvtxBnmq0wROMVvMeJuScg/doAmAyYp4Db29iBT4xdwNBed\nY2gea+zDTYa4EzAvXUYNR0PVG6pZDrlcjQZIrXSHX8f8MVRBE+LHIQ6e4B4N4cB7\nQ4WQxYpYxmUKeFfyxiMPAdkgS94P+5KFdSpcc41teyWRyu5FrgZLAMzTsVlQ2jqI\nOylDRl6XK1TOU2+NSueW+r9xDkKLfP0ooNBIytrEgUy7onOTJsjrDNYmiLbAJM+7\nvVvrdX3pCI6GMyx5dwlppYn8s3CQh3aP0yK7Qs69cwsgJirQmz1wHiRszYd2qReW\nt88NkvuOGKmYSdGe/mBEciG5Ge3C9THxOUiIkCR1VBatzvT4aRRkOfujuLpwQMcn\nHL/EVlP6Y2XQ8xwOFvVrhlhNGNTkDY6lnVuR3HYkUD/GKvvZt5y11ubQ2egZixVx\nSK236thZiNSQvxaz2emsWWFUyBy6ysHK4bkgTI86k4mloMy/0/Z1pHWWbVY=\n-----END CERTIFICATE-----\n\n# Issuer: CN=E-Tugra Certification Authority O=E-Tu\\u011fra EBG Bili\\u015fim Teknolojileri ve Hizmetleri A.\\u015e. OU=E-Tugra Sertifikasyon Merkezi\n# Subject: CN=E-Tugra Certification Authority O=E-Tu\\u011fra EBG Bili\\u015fim Teknolojileri ve Hizmetleri A.\\u015e. OU=E-Tugra Sertifikasyon Merkezi\n# Label: \"E-Tugra Certification Authority\"\n# Serial: 7667447206703254355\n# MD5 Fingerprint: b8:a1:03:63:b0:bd:21:71:70:8a:6f:13:3a:bb:79:49\n# SHA1 Fingerprint: 51:c6:e7:08:49:06:6e:f3:92:d4:5c:a0:0d:6d:a3:62:8f:c3:52:39\n# SHA256 Fingerprint: b0:bf:d5:2b:b0:d7:d9:bd:92:bf:5d:4d:c1:3d:a2:55:c0:2c:54:2f:37:83:65:ea:89:39:11:f5:5e:55:f2:3c\n-----BEGIN CERTIFICATE-----\nMIIGSzCCBDOgAwIBAgIIamg+nFGby1MwDQYJKoZIhvcNAQELBQAwgbIxCzAJBgNV\nBAYTAlRSMQ8wDQYDVQQHDAZBbmthcmExQDA+BgNVBAoMN0UtVHXEn3JhIEVCRyBC\naWxpxZ9pbSBUZWtub2xvamlsZXJpIHZlIEhpem1ldGxlcmkgQS7Fni4xJjAkBgNV\nBAsMHUUtVHVncmEgU2VydGlmaWthc3lvbiBNZXJrZXppMSgwJgYDVQQDDB9FLVR1\nZ3JhIENlcnRpZmljYXRpb24gQXV0aG9yaXR5MB4XDTEzMDMwNTEyMDk0OFoXDTIz\nMDMwMzEyMDk0OFowgbIxCzAJBgNVBAYTAlRSMQ8wDQYDVQQHDAZBbmthcmExQDA+\nBgNVBAoMN0UtVHXEn3JhIEVCRyBCaWxpxZ9pbSBUZWtub2xvamlsZXJpIHZlIEhp\nem1ldGxlcmkgQS7Fni4xJjAkBgNVBAsMHUUtVHVncmEgU2VydGlmaWthc3lvbiBN\nZXJrZXppMSgwJgYDVQQDDB9FLVR1Z3JhIENlcnRpZmljYXRpb24gQXV0aG9yaXR5\nMIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEA4vU/kwVRHoViVF56C/UY\nB4Oufq9899SKa6VjQzm5S/fDxmSJPZQuVIBSOTkHS0vdhQd2h8y/L5VMzH2nPbxH\nD5hw+IyFHnSOkm0bQNGZDbt1bsipa5rAhDGvykPL6ys06I+XawGb1Q5KCKpbknSF\nQ9OArqGIW66z6l7LFpp3RMih9lRozt6Plyu6W0ACDGQXwLWTzeHxE2bODHnv0ZEo\nq1+gElIwcxmOj+GMB6LDu0rw6h8VqO4lzKRG+Bsi77MOQ7osJLjFLFzUHPhdZL3D\nk14opz8n8Y4e0ypQBaNV2cvnOVPAmJ6MVGKLJrD3fY185MaeZkJVgkfnsliNZvcH\nfC425lAcP9tDJMW/hkd5s3kc91r0E+xs+D/iWR+V7kI+ua2oMoVJl0b+SzGPWsut\ndEcf6ZG33ygEIqDUD13ieU/qbIWGvaimzuT6w+Gzrt48Ue7LE3wBf4QOXVGUnhMM\nti6lTPk5cDZvlsouDERVxcr6XQKj39ZkjFqzAQqptQpHF//vkUAqjqFGOjGY5RH8\nzLtJVor8udBhmm9lbObDyz51Sf6Pp+KJxWfXnUYTTjF2OySznhFlhqt/7x3U+Lzn\nrFpct1pHXFXOVbQicVtbC/DP3KBhZOqp12gKY6fgDT+gr9Oq0n7vUaDmUStVkhUX\nU8u3Zg5mTPj5dUyQ5xJwx0UCAwEAAaNjMGEwHQYDVR0OBBYEFC7j27JJ0JxUeVz6\nJyr+zE7S6E5UMA8GA1UdEwEB/wQFMAMBAf8wHwYDVR0jBBgwFoAULuPbsknQnFR5\nXPonKv7MTtLoTlQwDgYDVR0PAQH/BAQDAgEGMA0GCSqGSIb3DQEBCwUAA4ICAQAF\nNzr0TbdF4kV1JI+2d1LoHNgQk2Xz8lkGpD4eKexd0dCrfOAKkEh47U6YA5n+KGCR\nHTAduGN8qOY1tfrTYXbm1gdLymmasoR6d5NFFxWfJNCYExL/u6Au/U5Mh/jOXKqY\nGwXgAEZKgoClM4so3O0409/lPun++1ndYYRP0lSWE2ETPo+Aab6TR7U1Q9Jauz1c\n77NCR807VRMGsAnb/WP2OogKmW9+4c4bU2pEZiNRCHu8W1Ki/QY3OEBhj0qWuJA3\n+GbHeJAAFS6LrVE1Uweoa2iu+U48BybNCAVwzDk/dr2l02cmAYamU9JgO3xDf1WK\nvJUawSg5TB9D0pH0clmKuVb8P7Sd2nCcdlqMQ1DujjByTd//SffGqWfZbawCEeI6\nFiWnWAjLb1NBnEg4R2gz0dfHj9R0IdTDBZB6/86WiLEVKV0jq9BgoRJP3vQXzTLl\nyb/IQ639Lo7xr+L0mPoSHyDYwKcMhcWQ9DstliaxLL5Mq+ux0orJ23gTDx4JnW2P\nAJ8C2sH6H3p6CcRK5ogql5+Ji/03X186zjhZhkuvcQu02PJwT58yE+Owp1fl2tpD\ny4Q08ijE6m30Ku/Ba3ba+367hTzSU8JNvnHhRdH9I2cNE3X7z2VnIp2usAnRCf8d\nNL/+I5c30jn6PQ0GC7TbO6Orb1wdtn7os4I07QZcJA==\n-----END CERTIFICATE-----\n\n# Issuer: CN=T-TeleSec GlobalRoot Class 2 O=T-Systems Enterprise Services GmbH OU=T-Systems Trust Center\n# Subject: CN=T-TeleSec GlobalRoot Class 2 O=T-Systems Enterprise Services GmbH OU=T-Systems Trust Center\n# Label: \"T-TeleSec GlobalRoot Class 2\"\n# Serial: 1\n# MD5 Fingerprint: 2b:9b:9e:e4:7b:6c:1f:00:72:1a:cc:c1:77:79:df:6a\n# SHA1 Fingerprint: 59:0d:2d:7d:88:4f:40:2e:61:7e:a5:62:32:17:65:cf:17:d8:94:e9\n# SHA256 Fingerprint: 91:e2:f5:78:8d:58:10:eb:a7:ba:58:73:7d:e1:54:8a:8e:ca:cd:01:45:98:bc:0b:14:3e:04:1b:17:05:25:52\n-----BEGIN CERTIFICATE-----\nMIIDwzCCAqugAwIBAgIBATANBgkqhkiG9w0BAQsFADCBgjELMAkGA1UEBhMCREUx\nKzApBgNVBAoMIlQtU3lzdGVtcyBFbnRlcnByaXNlIFNlcnZpY2VzIEdtYkgxHzAd\nBgNVBAsMFlQtU3lzdGVtcyBUcnVzdCBDZW50ZXIxJTAjBgNVBAMMHFQtVGVsZVNl\nYyBHbG9iYWxSb290IENsYXNzIDIwHhcNMDgxMDAxMTA0MDE0WhcNMzMxMDAxMjM1\nOTU5WjCBgjELMAkGA1UEBhMCREUxKzApBgNVBAoMIlQtU3lzdGVtcyBFbnRlcnBy\naXNlIFNlcnZpY2VzIEdtYkgxHzAdBgNVBAsMFlQtU3lzdGVtcyBUcnVzdCBDZW50\nZXIxJTAjBgNVBAMMHFQtVGVsZVNlYyBHbG9iYWxSb290IENsYXNzIDIwggEiMA0G\nCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCqX9obX+hzkeXaXPSi5kfl82hVYAUd\nAqSzm1nzHoqvNK38DcLZSBnuaY/JIPwhqgcZ7bBcrGXHX+0CfHt8LRvWurmAwhiC\nFoT6ZrAIxlQjgeTNuUk/9k9uN0goOA/FvudocP05l03Sx5iRUKrERLMjfTlH6VJi\n1hKTXrcxlkIF+3anHqP1wvzpesVsqXFP6st4vGCvx9702cu+fjOlbpSD8DT6Iavq\njnKgP6TeMFvvhk1qlVtDRKgQFRzlAVfFmPHmBiiRqiDFt1MmUUOyCxGVWOHAD3bZ\nwI18gfNycJ5v/hqO2V81xrJvNHy+SE/iWjnX2J14np+GPgNeGYtEotXHAgMBAAGj\nQjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgEGMB0GA1UdDgQWBBS/\nWSA2AHmgoCJrjNXyYdK4LMuCSjANBgkqhkiG9w0BAQsFAAOCAQEAMQOiYQsfdOhy\nNsZt+U2e+iKo4YFWz827n+qrkRk4r6p8FU3ztqONpfSO9kSpp+ghla0+AGIWiPAC\nuvxhI+YzmzB6azZie60EI4RYZeLbK4rnJVM3YlNfvNoBYimipidx5joifsFvHZVw\nIEoHNN/q/xWA5brXethbdXwFeilHfkCoMRN3zUA7tFFHei4R40cR3p1m0IvVVGb6\ng1XqfMIpiRvpb7PO4gWEyS8+eIVibslfwXhjdFjASBgMmTnrpMwatXlajRWc2BQN\n9noHV8cigwUtPJslJj0Ys6lDfMjIq2SPDqO/nBudMNva0Bkuqjzx+zOAduTNrRlP\nBSeOE6Fuwg==\n-----END CERTIFICATE-----\n\n# Issuer: CN=Atos TrustedRoot 2011 O=Atos\n# Subject: CN=Atos TrustedRoot 2011 O=Atos\n# Label: \"Atos TrustedRoot 2011\"\n# Serial: 6643877497813316402\n# MD5 Fingerprint: ae:b9:c4:32:4b:ac:7f:5d:66:cc:77:94:bb:2a:77:56\n# SHA1 Fingerprint: 2b:b1:f5:3e:55:0c:1d:c5:f1:d4:e6:b7:6a:46:4b:55:06:02:ac:21\n# SHA256 Fingerprint: f3:56:be:a2:44:b7:a9:1e:b3:5d:53:ca:9a:d7:86:4a:ce:01:8e:2d:35:d5:f8:f9:6d:df:68:a6:f4:1a:a4:74\n-----BEGIN CERTIFICATE-----\nMIIDdzCCAl+gAwIBAgIIXDPLYixfszIwDQYJKoZIhvcNAQELBQAwPDEeMBwGA1UE\nAwwVQXRvcyBUcnVzdGVkUm9vdCAyMDExMQ0wCwYDVQQKDARBdG9zMQswCQYDVQQG\nEwJERTAeFw0xMTA3MDcxNDU4MzBaFw0zMDEyMzEyMzU5NTlaMDwxHjAcBgNVBAMM\nFUF0b3MgVHJ1c3RlZFJvb3QgMjAxMTENMAsGA1UECgwEQXRvczELMAkGA1UEBhMC\nREUwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCVhTuXbyo7LjvPpvMp\nNb7PGKw+qtn4TaA+Gke5vJrf8v7MPkfoepbCJI419KkM/IL9bcFyYie96mvr54rM\nVD6QUM+A1JX76LWC1BTFtqlVJVfbsVD2sGBkWXppzwO3bw2+yj5vdHLqqjAqc2K+\nSZFhyBH+DgMq92og3AIVDV4VavzjgsG1xZ1kCWyjWZgHJ8cblithdHFsQ/H3NYkQ\n4J7sVaE3IqKHBAUsR320HLliKWYoyrfhk/WklAOZuXCFteZI6o1Q/NnezG8HDt0L\ncp2AMBYHlT8oDv3FdU9T1nSatCQujgKRz3bFmx5VdJx4IbHwLfELn8LVlhgf8FQi\neowHAgMBAAGjfTB7MB0GA1UdDgQWBBSnpQaxLKYJYO7Rl+lwrrw7GWzbITAPBgNV\nHRMBAf8EBTADAQH/MB8GA1UdIwQYMBaAFKelBrEspglg7tGX6XCuvDsZbNshMBgG\nA1UdIAQRMA8wDQYLKwYBBAGwLQMEAQEwDgYDVR0PAQH/BAQDAgGGMA0GCSqGSIb3\nDQEBCwUAA4IBAQAmdzTblEiGKkGdLD4GkGDEjKwLVLgfuXvTBznk+j57sj1O7Z8j\nvZfza1zv7v1Apt+hk6EKhqzvINB5Ab149xnYJDE0BAGmuhWawyfc2E8PzBhj/5kP\nDpFrdRbhIfzYJsdHt6bPWHJxfrrhTZVHO8mvbaG0weyJ9rQPOLXiZNwlz6bb65pc\nmaHFCN795trV1lpFDMS3wrUU77QR/w4VtfX128a961qn8FYiqTxlVMYVqL2Gns2D\nlmh6cYGJ4Qvh6hEbaAjMaZ7snkGeRDImeuKHCnE96+RapNLbxc3G3mB/ufNPRJLv\nKrcYPqcZ2Qt9sTdBQrC6YB3y/gkRsPCHe6ed\n-----END CERTIFICATE-----\n\n# Issuer: CN=QuoVadis Root CA 1 G3 O=QuoVadis Limited\n# Subject: CN=QuoVadis Root CA 1 G3 O=QuoVadis Limited\n# Label: \"QuoVadis Root CA 1 G3\"\n# Serial: 687049649626669250736271037606554624078720034195\n# MD5 Fingerprint: a4:bc:5b:3f:fe:37:9a:fa:64:f0:e2:fa:05:3d:0b:ab\n# SHA1 Fingerprint: 1b:8e:ea:57:96:29:1a:c9:39:ea:b8:0a:81:1a:73:73:c0:93:79:67\n# SHA256 Fingerprint: 8a:86:6f:d1:b2:76:b5:7e:57:8e:92:1c:65:82:8a:2b:ed:58:e9:f2:f2:88:05:41:34:b7:f1:f4:bf:c9:cc:74\n-----BEGIN CERTIFICATE-----\nMIIFYDCCA0igAwIBAgIUeFhfLq0sGUvjNwc1NBMotZbUZZMwDQYJKoZIhvcNAQEL\nBQAwSDELMAkGA1UEBhMCQk0xGTAXBgNVBAoTEFF1b1ZhZGlzIExpbWl0ZWQxHjAc\nBgNVBAMTFVF1b1ZhZGlzIFJvb3QgQ0EgMSBHMzAeFw0xMjAxMTIxNzI3NDRaFw00\nMjAxMTIxNzI3NDRaMEgxCzAJBgNVBAYTAkJNMRkwFwYDVQQKExBRdW9WYWRpcyBM\naW1pdGVkMR4wHAYDVQQDExVRdW9WYWRpcyBSb290IENBIDEgRzMwggIiMA0GCSqG\nSIb3DQEBAQUAA4ICDwAwggIKAoICAQCgvlAQjunybEC0BJyFuTHK3C3kEakEPBtV\nwedYMB0ktMPvhd6MLOHBPd+C5k+tR4ds7FtJwUrVu4/sh6x/gpqG7D0DmVIB0jWe\nrNrwU8lmPNSsAgHaJNM7qAJGr6Qc4/hzWHa39g6QDbXwz8z6+cZM5cOGMAqNF341\n68Xfuw6cwI2H44g4hWf6Pser4BOcBRiYz5P1sZK0/CPTz9XEJ0ngnjybCKOLXSoh\n4Pw5qlPafX7PGglTvF0FBM+hSo+LdoINofjSxxR3W5A2B4GbPgb6Ul5jxaYA/qXp\nUhtStZI5cgMJYr2wYBZupt0lwgNm3fME0UDiTouG9G/lg6AnhF4EwfWQvTA9xO+o\nabw4m6SkltFi2mnAAZauy8RRNOoMqv8hjlmPSlzkYZqn0ukqeI1RPToV7qJZjqlc\n3sX5kCLliEVx3ZGZbHqfPT2YfF72vhZooF6uCyP8Wg+qInYtyaEQHeTTRCOQiJ/G\nKubX9ZqzWB4vMIkIG1SitZgj7Ah3HJVdYdHLiZxfokqRmu8hqkkWCKi9YSgxyXSt\nhfbZxbGL0eUQMk1fiyA6PEkfM4VZDdvLCXVDaXP7a3F98N/ETH3Goy7IlXnLc6KO\nTk0k+17kBL5yG6YnLUlamXrXXAkgt3+UuU/xDRxeiEIbEbfnkduebPRq34wGmAOt\nzCjvpUfzUwIDAQABo0IwQDAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIB\nBjAdBgNVHQ4EFgQUo5fW816iEOGrRZ88F2Q87gFwnMwwDQYJKoZIhvcNAQELBQAD\nggIBABj6W3X8PnrHX3fHyt/PX8MSxEBd1DKquGrX1RUVRpgjpeaQWxiZTOOtQqOC\nMTaIzen7xASWSIsBx40Bz1szBpZGZnQdT+3Btrm0DWHMY37XLneMlhwqI2hrhVd2\ncDMT/uFPpiN3GPoajOi9ZcnPP/TJF9zrx7zABC4tRi9pZsMbj/7sPtPKlL92CiUN\nqXsCHKnQO18LwIE6PWThv6ctTr1NxNgpxiIY0MWscgKCP6o6ojoilzHdCGPDdRS5\nYCgtW2jgFqlmgiNR9etT2DGbe+m3nUvriBbP+V04ikkwj+3x6xn0dxoxGE1nVGwv\nb2X52z3sIexe9PSLymBlVNFxZPT5pqOBMzYzcfCkeF9OrYMh3jRJjehZrJ3ydlo2\n8hP0r+AJx2EqbPfgna67hkooby7utHnNkDPDs3b69fBsnQGQ+p6Q9pxyz0fawx/k\nNSBT8lTR32GDpgLiJTjehTItXnOQUl1CxM49S+H5GYQd1aJQzEH7QRTDvdbJWqNj\nZgKAvQU6O0ec7AAmTPWIUb+oI38YB7AL7YsmoWTTYUrrXJ/es69nA7Mf3W1daWhp\nq1467HxpvMc7hU6eFbm0FU/DlXpY18ls6Wy58yljXrQs8C097Vpl4KlbQMJImYFt\nnh8GKjwStIsPm6Ik8KaN1nrgS7ZklmOVhMJKzRwuJIczYOXD\n-----END CERTIFICATE-----\n\n# Issuer: CN=QuoVadis Root CA 2 G3 O=QuoVadis Limited\n# Subject: CN=QuoVadis Root CA 2 G3 O=QuoVadis Limited\n# Label: \"QuoVadis Root CA 2 G3\"\n# Serial: 390156079458959257446133169266079962026824725800\n# MD5 Fingerprint: af:0c:86:6e:bf:40:2d:7f:0b:3e:12:50:ba:12:3d:06\n# SHA1 Fingerprint: 09:3c:61:f3:8b:8b:dc:7d:55:df:75:38:02:05:00:e1:25:f5:c8:36\n# SHA256 Fingerprint: 8f:e4:fb:0a:f9:3a:4d:0d:67:db:0b:eb:b2:3e:37:c7:1b:f3:25:dc:bc:dd:24:0e:a0:4d:af:58:b4:7e:18:40\n-----BEGIN CERTIFICATE-----\nMIIFYDCCA0igAwIBAgIURFc0JFuBiZs18s64KztbpybwdSgwDQYJKoZIhvcNAQEL\nBQAwSDELMAkGA1UEBhMCQk0xGTAXBgNVBAoTEFF1b1ZhZGlzIExpbWl0ZWQxHjAc\nBgNVBAMTFVF1b1ZhZGlzIFJvb3QgQ0EgMiBHMzAeFw0xMjAxMTIxODU5MzJaFw00\nMjAxMTIxODU5MzJaMEgxCzAJBgNVBAYTAkJNMRkwFwYDVQQKExBRdW9WYWRpcyBM\naW1pdGVkMR4wHAYDVQQDExVRdW9WYWRpcyBSb290IENBIDIgRzMwggIiMA0GCSqG\nSIb3DQEBAQUAA4ICDwAwggIKAoICAQChriWyARjcV4g/Ruv5r+LrI3HimtFhZiFf\nqq8nUeVuGxbULX1QsFN3vXg6YOJkApt8hpvWGo6t/x8Vf9WVHhLL5hSEBMHfNrMW\nn4rjyduYNM7YMxcoRvynyfDStNVNCXJJ+fKH46nafaF9a7I6JaltUkSs+L5u+9ym\nc5GQYaYDFCDy54ejiK2toIz/pgslUiXnFgHVy7g1gQyjO/Dh4fxaXc6AcW34Sas+\nO7q414AB+6XrW7PFXmAqMaCvN+ggOp+oMiwMzAkd056OXbxMmO7FGmh77FOm6RQ1\no9/NgJ8MSPsc9PG/Srj61YxxSscfrf5BmrODXfKEVu+lV0POKa2Mq1W/xPtbAd0j\nIaFYAI7D0GoT7RPjEiuA3GfmlbLNHiJuKvhB1PLKFAeNilUSxmn1uIZoL1NesNKq\nIcGY5jDjZ1XHm26sGahVpkUG0CM62+tlXSoREfA7T8pt9DTEceT/AFr2XK4jYIVz\n8eQQsSWu1ZK7E8EM4DnatDlXtas1qnIhO4M15zHfeiFuuDIIfR0ykRVKYnLP43eh\nvNURG3YBZwjgQQvD6xVu+KQZ2aKrr+InUlYrAoosFCT5v0ICvybIxo/gbjh9Uy3l\n7ZizlWNof/k19N+IxWA1ksB8aRxhlRbQ694Lrz4EEEVlWFA4r0jyWbYW8jwNkALG\ncC4BrTwV1wIDAQABo0IwQDAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIB\nBjAdBgNVHQ4EFgQU7edvdlq/YOxJW8ald7tyFnGbxD0wDQYJKoZIhvcNAQELBQAD\nggIBAJHfgD9DCX5xwvfrs4iP4VGyvD11+ShdyLyZm3tdquXK4Qr36LLTn91nMX66\nAarHakE7kNQIXLJgapDwyM4DYvmL7ftuKtwGTTwpD4kWilhMSA/ohGHqPHKmd+RC\nroijQ1h5fq7KpVMNqT1wvSAZYaRsOPxDMuHBR//47PERIjKWnML2W2mWeyAMQ0Ga\nW/ZZGYjeVYg3UQt4XAoeo0L9x52ID8DyeAIkVJOviYeIyUqAHerQbj5hLja7NQ4n\nlv1mNDthcnPxFlxHBlRJAHpYErAK74X9sbgzdWqTHBLmYF5vHX/JHyPLhGGfHoJE\n+V+tYlUkmlKY7VHnoX6XOuYvHxHaU4AshZ6rNRDbIl9qxV6XU/IyAgkwo1jwDQHV\ncsaxfGl7w/U2Rcxhbl5MlMVerugOXou/983g7aEOGzPuVBj+D77vfoRrQ+NwmNtd\ndbINWQeFFSM51vHfqSYP1kjHs6Yi9TM3WpVHn3u6GBVv/9YUZINJ0gpnIdsPNWNg\nKCLjsZWDzYWm3S8P52dSbrsvhXz1SnPnxT7AvSESBT/8twNJAlvIJebiVDj1eYeM\nHVOyToV7BjjHLPj4sHKNJeV3UvQDHEimUF+IIDBu8oJDqz2XhOdT+yHBTw8imoa4\nWSr2Rz0ZiC3oheGe7IUIarFsNMkd7EgrO3jtZsSOeWmD3n+M\n-----END CERTIFICATE-----\n\n# Issuer: CN=QuoVadis Root CA 3 G3 O=QuoVadis Limited\n# Subject: CN=QuoVadis Root CA 3 G3 O=QuoVadis Limited\n# Label: \"QuoVadis Root CA 3 G3\"\n# Serial: 268090761170461462463995952157327242137089239581\n# MD5 Fingerprint: df:7d:b9:ad:54:6f:68:a1:df:89:57:03:97:43:b0:d7\n# SHA1 Fingerprint: 48:12:bd:92:3c:a8:c4:39:06:e7:30:6d:27:96:e6:a4:cf:22:2e:7d\n# SHA256 Fingerprint: 88:ef:81:de:20:2e:b0:18:45:2e:43:f8:64:72:5c:ea:5f:bd:1f:c2:d9:d2:05:73:07:09:c5:d8:b8:69:0f:46\n-----BEGIN CERTIFICATE-----\nMIIFYDCCA0igAwIBAgIULvWbAiin23r/1aOp7r0DoM8Sah0wDQYJKoZIhvcNAQEL\nBQAwSDELMAkGA1UEBhMCQk0xGTAXBgNVBAoTEFF1b1ZhZGlzIExpbWl0ZWQxHjAc\nBgNVBAMTFVF1b1ZhZGlzIFJvb3QgQ0EgMyBHMzAeFw0xMjAxMTIyMDI2MzJaFw00\nMjAxMTIyMDI2MzJaMEgxCzAJBgNVBAYTAkJNMRkwFwYDVQQKExBRdW9WYWRpcyBM\naW1pdGVkMR4wHAYDVQQDExVRdW9WYWRpcyBSb290IENBIDMgRzMwggIiMA0GCSqG\nSIb3DQEBAQUAA4ICDwAwggIKAoICAQCzyw4QZ47qFJenMioKVjZ/aEzHs286IxSR\n/xl/pcqs7rN2nXrpixurazHb+gtTTK/FpRp5PIpM/6zfJd5O2YIyC0TeytuMrKNu\nFoM7pmRLMon7FhY4futD4tN0SsJiCnMK3UmzV9KwCoWdcTzeo8vAMvMBOSBDGzXR\nU7Ox7sWTaYI+FrUoRqHe6okJ7UO4BUaKhvVZR74bbwEhELn9qdIoyhA5CcoTNs+c\nra1AdHkrAj80//ogaX3T7mH1urPnMNA3I4ZyYUUpSFlob3emLoG+B01vr87ERROR\nFHAGjx+f+IdpsQ7vw4kZ6+ocYfx6bIrc1gMLnia6Et3UVDmrJqMz6nWB2i3ND0/k\nA9HvFZcba5DFApCTZgIhsUfei5pKgLlVj7WiL8DWM2fafsSntARE60f75li59wzw\neyuxwHApw0BiLTtIadwjPEjrewl5qW3aqDCYz4ByA4imW0aucnl8CAMhZa634Ryl\nsSqiMd5mBPfAdOhx3v89WcyWJhKLhZVXGqtrdQtEPREoPHtht+KPZ0/l7DxMYIBp\nVzgeAVuNVejH38DMdyM0SXV89pgR6y3e7UEuFAUCf+D+IOs15xGsIs5XPd7JMG0Q\nA4XN8f+MFrXBsj6IbGB/kE+V9/YtrQE5BwT6dYB9v0lQ7e/JxHwc64B+27bQ3RP+\nydOc17KXqQIDAQABo0IwQDAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIB\nBjAdBgNVHQ4EFgQUxhfQvKjqAkPyGwaZXSuQILnXnOQwDQYJKoZIhvcNAQELBQAD\nggIBADRh2Va1EodVTd2jNTFGu6QHcrxfYWLopfsLN7E8trP6KZ1/AvWkyaiTt3px\nKGmPc+FSkNrVvjrlt3ZqVoAh313m6Tqe5T72omnHKgqwGEfcIHB9UqM+WXzBusnI\nFUBhynLWcKzSt/Ac5IYp8M7vaGPQtSCKFWGafoaYtMnCdvvMujAWzKNhxnQT5Wvv\noxXqA/4Ti2Tk08HS6IT7SdEQTXlm66r99I0xHnAUrdzeZxNMgRVhvLfZkXdxGYFg\nu/BYpbWcC/ePIlUnwEsBbTuZDdQdm2NnL9DuDcpmvJRPpq3t/O5jrFc/ZSXPsoaP\n0Aj/uHYUbt7lJ+yreLVTubY/6CD50qi+YUbKh4yE8/nxoGibIh6BJpsQBJFxwAYf\n3KDTuVan45gtf4Od34wrnDKOMpTwATwiKp9Dwi7DmDkHOHv8XgBCH/MyJnmDhPbl\n8MFREsALHgQjDFSlTC9JxUrRtm5gDWv8a4uFJGS3iQ6rJUdbPM9+Sb3H6QrG2vd+\nDhcI00iX0HGS8A85PjRqHH3Y8iKuu2n0M7SmSFXRDw4m6Oy2Cy2nhTXN/VnIn9HN\nPlopNLk9hM6xZdRZkZFWdSHBd575euFgndOtBBj0fOtek49TSiIp+EgrPk2GrFt/\nywaZWWDYWGWVjUTR939+J399roD1B0y2PpxxVJkES/1Y+Zj0\n-----END CERTIFICATE-----\n\n# Issuer: CN=DigiCert Assured ID Root G2 O=DigiCert Inc OU=www.digicert.com\n# Subject: CN=DigiCert Assured ID Root G2 O=DigiCert Inc OU=www.digicert.com\n# Label: \"DigiCert Assured ID Root G2\"\n# Serial: 15385348160840213938643033620894905419\n# MD5 Fingerprint: 92:38:b9:f8:63:24:82:65:2c:57:33:e6:fe:81:8f:9d\n# SHA1 Fingerprint: a1:4b:48:d9:43:ee:0a:0e:40:90:4f:3c:e0:a4:c0:91:93:51:5d:3f\n# SHA256 Fingerprint: 7d:05:eb:b6:82:33:9f:8c:94:51:ee:09:4e:eb:fe:fa:79:53:a1:14:ed:b2:f4:49:49:45:2f:ab:7d:2f:c1:85\n-----BEGIN CERTIFICATE-----\nMIIDljCCAn6gAwIBAgIQC5McOtY5Z+pnI7/Dr5r0SzANBgkqhkiG9w0BAQsFADBl\nMQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3\nd3cuZGlnaWNlcnQuY29tMSQwIgYDVQQDExtEaWdpQ2VydCBBc3N1cmVkIElEIFJv\nb3QgRzIwHhcNMTMwODAxMTIwMDAwWhcNMzgwMTE1MTIwMDAwWjBlMQswCQYDVQQG\nEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3d3cuZGlnaWNl\ncnQuY29tMSQwIgYDVQQDExtEaWdpQ2VydCBBc3N1cmVkIElEIFJvb3QgRzIwggEi\nMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDZ5ygvUj82ckmIkzTz+GoeMVSA\nn61UQbVH35ao1K+ALbkKz3X9iaV9JPrjIgwrvJUXCzO/GU1BBpAAvQxNEP4Htecc\nbiJVMWWXvdMX0h5i89vqbFCMP4QMls+3ywPgym2hFEwbid3tALBSfK+RbLE4E9Hp\nEgjAALAcKxHad3A2m67OeYfcgnDmCXRwVWmvo2ifv922ebPynXApVfSr/5Vh88lA\nbx3RvpO704gqu52/clpWcTs/1PPRCv4o76Pu2ZmvA9OPYLfykqGxvYmJHzDNw6Yu\nYjOuFgJ3RFrngQo8p0Quebg/BLxcoIfhG69Rjs3sLPr4/m3wOnyqi+RnlTGNAgMB\nAAGjQjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgGGMB0GA1UdDgQW\nBBTOw0q5mVXyuNtgv6l+vVa1lzan1jANBgkqhkiG9w0BAQsFAAOCAQEAyqVVjOPI\nQW5pJ6d1Ee88hjZv0p3GeDgdaZaikmkuOGybfQTUiaWxMTeKySHMq2zNixya1r9I\n0jJmwYrA8y8678Dj1JGG0VDjA9tzd29KOVPt3ibHtX2vK0LRdWLjSisCx1BL4Gni\nlmwORGYQRI+tBev4eaymG+g3NJ1TyWGqolKvSnAWhsI6yLETcDbYz+70CjTVW0z9\nB5yiutkBclzzTcHdDrEcDcRjvq30FPuJ7KJBDkzMyFdA0G4Dqs0MjomZmWzwPDCv\nON9vvKO+KSAnq3T/EyJ43pdSVR6DtVQgA+6uwE9W3jfMw3+qBCe703e4YtsXfJwo\nIhNzbM8m9Yop5w==\n-----END CERTIFICATE-----\n\n# Issuer: CN=DigiCert Assured ID Root G3 O=DigiCert Inc OU=www.digicert.com\n# Subject: CN=DigiCert Assured ID Root G3 O=DigiCert Inc OU=www.digicert.com\n# Label: \"DigiCert Assured ID Root G3\"\n# Serial: 15459312981008553731928384953135426796\n# MD5 Fingerprint: 7c:7f:65:31:0c:81:df:8d:ba:3e:99:e2:5c:ad:6e:fb\n# SHA1 Fingerprint: f5:17:a2:4f:9a:48:c6:c9:f8:a2:00:26:9f:dc:0f:48:2c:ab:30:89\n# SHA256 Fingerprint: 7e:37:cb:8b:4c:47:09:0c:ab:36:55:1b:a6:f4:5d:b8:40:68:0f:ba:16:6a:95:2d:b1:00:71:7f:43:05:3f:c2\n-----BEGIN CERTIFICATE-----\nMIICRjCCAc2gAwIBAgIQC6Fa+h3foLVJRK/NJKBs7DAKBggqhkjOPQQDAzBlMQsw\nCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3d3cu\nZGlnaWNlcnQuY29tMSQwIgYDVQQDExtEaWdpQ2VydCBBc3N1cmVkIElEIFJvb3Qg\nRzMwHhcNMTMwODAxMTIwMDAwWhcNMzgwMTE1MTIwMDAwWjBlMQswCQYDVQQGEwJV\nUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3d3cuZGlnaWNlcnQu\nY29tMSQwIgYDVQQDExtEaWdpQ2VydCBBc3N1cmVkIElEIFJvb3QgRzMwdjAQBgcq\nhkjOPQIBBgUrgQQAIgNiAAQZ57ysRGXtzbg/WPuNsVepRC0FFfLvC/8QdJ+1YlJf\nZn4f5dwbRXkLzMZTCp2NXQLZqVneAlr2lSoOjThKiknGvMYDOAdfVdp+CW7if17Q\nRSAPWXYQ1qAk8C3eNvJsKTmjQjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/\nBAQDAgGGMB0GA1UdDgQWBBTL0L2p4ZgFUaFNN6KDec6NHSrkhDAKBggqhkjOPQQD\nAwNnADBkAjAlpIFFAmsSS3V0T8gj43DydXLefInwz5FyYZ5eEJJZVrmDxxDnOOlY\nJjZ91eQ0hjkCMHw2U/Aw5WJjOpnitqM7mzT6HtoQknFekROn3aRukswy1vUhZscv\n6pZjamVFkpUBtA==\n-----END CERTIFICATE-----\n\n# Issuer: CN=DigiCert Global Root G2 O=DigiCert Inc OU=www.digicert.com\n# Subject: CN=DigiCert Global Root G2 O=DigiCert Inc OU=www.digicert.com\n# Label: \"DigiCert Global Root G2\"\n# Serial: 4293743540046975378534879503202253541\n# MD5 Fingerprint: e4:a6:8a:c8:54:ac:52:42:46:0a:fd:72:48:1b:2a:44\n# SHA1 Fingerprint: df:3c:24:f9:bf:d6:66:76:1b:26:80:73:fe:06:d1:cc:8d:4f:82:a4\n# SHA256 Fingerprint: cb:3c:cb:b7:60:31:e5:e0:13:8f:8d:d3:9a:23:f9:de:47:ff:c3:5e:43:c1:14:4c:ea:27:d4:6a:5a:b1:cb:5f\n-----BEGIN CERTIFICATE-----\nMIIDjjCCAnagAwIBAgIQAzrx5qcRqaC7KGSxHQn65TANBgkqhkiG9w0BAQsFADBh\nMQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3\nd3cuZGlnaWNlcnQuY29tMSAwHgYDVQQDExdEaWdpQ2VydCBHbG9iYWwgUm9vdCBH\nMjAeFw0xMzA4MDExMjAwMDBaFw0zODAxMTUxMjAwMDBaMGExCzAJBgNVBAYTAlVT\nMRUwEwYDVQQKEwxEaWdpQ2VydCBJbmMxGTAXBgNVBAsTEHd3dy5kaWdpY2VydC5j\nb20xIDAeBgNVBAMTF0RpZ2lDZXJ0IEdsb2JhbCBSb290IEcyMIIBIjANBgkqhkiG\n9w0BAQEFAAOCAQ8AMIIBCgKCAQEAuzfNNNx7a8myaJCtSnX/RrohCgiN9RlUyfuI\n2/Ou8jqJkTx65qsGGmvPrC3oXgkkRLpimn7Wo6h+4FR1IAWsULecYxpsMNzaHxmx\n1x7e/dfgy5SDN67sH0NO3Xss0r0upS/kqbitOtSZpLYl6ZtrAGCSYP9PIUkY92eQ\nq2EGnI/yuum06ZIya7XzV+hdG82MHauVBJVJ8zUtluNJbd134/tJS7SsVQepj5Wz\ntCO7TG1F8PapspUwtP1MVYwnSlcUfIKdzXOS0xZKBgyMUNGPHgm+F6HmIcr9g+UQ\nvIOlCsRnKPZzFBQ9RnbDhxSJITRNrw9FDKZJobq7nMWxM4MphQIDAQABo0IwQDAP\nBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIBhjAdBgNVHQ4EFgQUTiJUIBiV\n5uNu5g/6+rkS7QYXjzkwDQYJKoZIhvcNAQELBQADggEBAGBnKJRvDkhj6zHd6mcY\n1Yl9PMWLSn/pvtsrF9+wX3N3KjITOYFnQoQj8kVnNeyIv/iPsGEMNKSuIEyExtv4\nNeF22d+mQrvHRAiGfzZ0JFrabA0UWTW98kndth/Jsw1HKj2ZL7tcu7XUIOGZX1NG\nFdtom/DzMNU+MeKNhJ7jitralj41E6Vf8PlwUHBHQRFXGU7Aj64GxJUTFy8bJZ91\n8rGOmaFvE7FBcf6IKshPECBV1/MUReXgRPTqh5Uykw7+U0b6LJ3/iyK5S9kJRaTe\npLiaWN0bfVKfjllDiIGknibVb63dDcY3fe0Dkhvld1927jyNxF1WW6LZZm6zNTfl\nMrY=\n-----END CERTIFICATE-----\n\n# Issuer: CN=DigiCert Global Root G3 O=DigiCert Inc OU=www.digicert.com\n# Subject: CN=DigiCert Global Root G3 O=DigiCert Inc OU=www.digicert.com\n# Label: \"DigiCert Global Root G3\"\n# Serial: 7089244469030293291760083333884364146\n# MD5 Fingerprint: f5:5d:a4:50:a5:fb:28:7e:1e:0f:0d:cc:96:57:56:ca\n# SHA1 Fingerprint: 7e:04:de:89:6a:3e:66:6d:00:e6:87:d3:3f:fa:d9:3b:e8:3d:34:9e\n# SHA256 Fingerprint: 31:ad:66:48:f8:10:41:38:c7:38:f3:9e:a4:32:01:33:39:3e:3a:18:cc:02:29:6e:f9:7c:2a:c9:ef:67:31:d0\n-----BEGIN CERTIFICATE-----\nMIICPzCCAcWgAwIBAgIQBVVWvPJepDU1w6QP1atFcjAKBggqhkjOPQQDAzBhMQsw\nCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3d3cu\nZGlnaWNlcnQuY29tMSAwHgYDVQQDExdEaWdpQ2VydCBHbG9iYWwgUm9vdCBHMzAe\nFw0xMzA4MDExMjAwMDBaFw0zODAxMTUxMjAwMDBaMGExCzAJBgNVBAYTAlVTMRUw\nEwYDVQQKEwxEaWdpQ2VydCBJbmMxGTAXBgNVBAsTEHd3dy5kaWdpY2VydC5jb20x\nIDAeBgNVBAMTF0RpZ2lDZXJ0IEdsb2JhbCBSb290IEczMHYwEAYHKoZIzj0CAQYF\nK4EEACIDYgAE3afZu4q4C/sLfyHS8L6+c/MzXRq8NOrexpu80JX28MzQC7phW1FG\nfp4tn+6OYwwX7Adw9c+ELkCDnOg/QW07rdOkFFk2eJ0DQ+4QE2xy3q6Ip6FrtUPO\nZ9wj/wMco+I+o0IwQDAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIBhjAd\nBgNVHQ4EFgQUs9tIpPmhxdiuNkHMEWNpYim8S8YwCgYIKoZIzj0EAwMDaAAwZQIx\nAK288mw/EkrRLTnDCgmXc/SINoyIJ7vmiI1Qhadj+Z4y3maTD/HMsQmP3Wyr+mt/\noAIwOWZbwmSNuJ5Q3KjVSaLtx9zRSX8XAbjIho9OjIgrqJqpisXRAL34VOKa5Vt8\nsycX\n-----END CERTIFICATE-----\n\n# Issuer: CN=DigiCert Trusted Root G4 O=DigiCert Inc OU=www.digicert.com\n# Subject: CN=DigiCert Trusted Root G4 O=DigiCert Inc OU=www.digicert.com\n# Label: \"DigiCert Trusted Root G4\"\n# Serial: 7451500558977370777930084869016614236\n# MD5 Fingerprint: 78:f2:fc:aa:60:1f:2f:b4:eb:c9:37:ba:53:2e:75:49\n# SHA1 Fingerprint: dd:fb:16:cd:49:31:c9:73:a2:03:7d:3f:c8:3a:4d:7d:77:5d:05:e4\n# SHA256 Fingerprint: 55:2f:7b:dc:f1:a7:af:9e:6c:e6:72:01:7f:4f:12:ab:f7:72:40:c7:8e:76:1a:c2:03:d1:d9:d2:0a:c8:99:88\n-----BEGIN CERTIFICATE-----\nMIIFkDCCA3igAwIBAgIQBZsbV56OITLiOQe9p3d1XDANBgkqhkiG9w0BAQwFADBi\nMQswCQYDVQQGEwJVUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3\nd3cuZGlnaWNlcnQuY29tMSEwHwYDVQQDExhEaWdpQ2VydCBUcnVzdGVkIFJvb3Qg\nRzQwHhcNMTMwODAxMTIwMDAwWhcNMzgwMTE1MTIwMDAwWjBiMQswCQYDVQQGEwJV\nUzEVMBMGA1UEChMMRGlnaUNlcnQgSW5jMRkwFwYDVQQLExB3d3cuZGlnaWNlcnQu\nY29tMSEwHwYDVQQDExhEaWdpQ2VydCBUcnVzdGVkIFJvb3QgRzQwggIiMA0GCSqG\nSIb3DQEBAQUAA4ICDwAwggIKAoICAQC/5pBzaN675F1KPDAiMGkz7MKnJS7JIT3y\nithZwuEppz1Yq3aaza57G4QNxDAf8xukOBbrVsaXbR2rsnnyyhHS5F/WBTxSD1If\nxp4VpX6+n6lXFllVcq9ok3DCsrp1mWpzMpTREEQQLt+C8weE5nQ7bXHiLQwb7iDV\nySAdYyktzuxeTsiT+CFhmzTrBcZe7FsavOvJz82sNEBfsXpm7nfISKhmV1efVFiO\nDCu3T6cw2Vbuyntd463JT17lNecxy9qTXtyOj4DatpGYQJB5w3jHtrHEtWoYOAMQ\njdjUN6QuBX2I9YI+EJFwq1WCQTLX2wRzKm6RAXwhTNS8rhsDdV14Ztk6MUSaM0C/\nCNdaSaTC5qmgZ92kJ7yhTzm1EVgX9yRcRo9k98FpiHaYdj1ZXUJ2h4mXaXpI8OCi\nEhtmmnTK3kse5w5jrubU75KSOp493ADkRSWJtppEGSt+wJS00mFt6zPZxd9LBADM\nfRyVw4/3IbKyEbe7f/LVjHAsQWCqsWMYRJUadmJ+9oCw++hkpjPRiQfhvbfmQ6QY\nuKZ3AeEPlAwhHbJUKSWJbOUOUlFHdL4mrLZBdd56rF+NP8m800ERElvlEFDrMcXK\nchYiCd98THU/Y+whX8QgUWtvsauGi0/C1kVfnSD8oR7FwI+isX4KJpn15GkvmB0t\n9dmpsh3lGwIDAQABo0IwQDAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIB\nhjAdBgNVHQ4EFgQU7NfjgtJxXWRM3y5nP+e6mK4cD08wDQYJKoZIhvcNAQEMBQAD\nggIBALth2X2pbL4XxJEbw6GiAI3jZGgPVs93rnD5/ZpKmbnJeFwMDF/k5hQpVgs2\nSV1EY+CtnJYYZhsjDT156W1r1lT40jzBQ0CuHVD1UvyQO7uYmWlrx8GnqGikJ9yd\n+SeuMIW59mdNOj6PWTkiU0TryF0Dyu1Qen1iIQqAyHNm0aAFYF/opbSnr6j3bTWc\nfFqK1qI4mfN4i/RN0iAL3gTujJtHgXINwBQy7zBZLq7gcfJW5GqXb5JQbZaNaHqa\nsjYUegbyJLkJEVDXCLG4iXqEI2FCKeWjzaIgQdfRnGTZ6iahixTXTBmyUEFxPT9N\ncCOGDErcgdLMMpSEDQgJlxxPwO5rIHQw0uA5NBCFIRUBCOhVMt5xSdkoF1BN5r5N\n0XWs0Mr7QbhDparTwwVETyw2m+L64kW4I1NsBm9nVX9GtUw/bihaeSbSpKhil9Ie\n4u1Ki7wb/UdKDd9nZn6yW0HQO+T0O/QEY+nvwlQAUaCKKsnOeMzV6ocEGLPOr0mI\nr/OSmbaz5mEP0oUA51Aa5BuVnRmhuZyxm7EAHu/QD09CbMkKvO5D+jpxpchNJqU1\n/YldvIViHTLSoCtU7ZpXwdv6EM8Zt4tKG48BtieVU+i2iW1bvGjUI+iLUaJW+fCm\ngKDWHrO8Dw9TdSmq6hN35N6MgSGtBxBHEa2HPQfRdbzP82Z+\n-----END CERTIFICATE-----\n\n# Issuer: CN=COMODO RSA Certification Authority O=COMODO CA Limited\n# Subject: CN=COMODO RSA Certification Authority O=COMODO CA Limited\n# Label: \"COMODO RSA Certification Authority\"\n# Serial: 101909084537582093308941363524873193117\n# MD5 Fingerprint: 1b:31:b0:71:40:36:cc:14:36:91:ad:c4:3e:fd:ec:18\n# SHA1 Fingerprint: af:e5:d2:44:a8:d1:19:42:30:ff:47:9f:e2:f8:97:bb:cd:7a:8c:b4\n# SHA256 Fingerprint: 52:f0:e1:c4:e5:8e:c6:29:29:1b:60:31:7f:07:46:71:b8:5d:7e:a8:0d:5b:07:27:34:63:53:4b:32:b4:02:34\n-----BEGIN CERTIFICATE-----\nMIIF2DCCA8CgAwIBAgIQTKr5yttjb+Af907YWwOGnTANBgkqhkiG9w0BAQwFADCB\nhTELMAkGA1UEBhMCR0IxGzAZBgNVBAgTEkdyZWF0ZXIgTWFuY2hlc3RlcjEQMA4G\nA1UEBxMHU2FsZm9yZDEaMBgGA1UEChMRQ09NT0RPIENBIExpbWl0ZWQxKzApBgNV\nBAMTIkNPTU9ETyBSU0EgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkwHhcNMTAwMTE5\nMDAwMDAwWhcNMzgwMTE4MjM1OTU5WjCBhTELMAkGA1UEBhMCR0IxGzAZBgNVBAgT\nEkdyZWF0ZXIgTWFuY2hlc3RlcjEQMA4GA1UEBxMHU2FsZm9yZDEaMBgGA1UEChMR\nQ09NT0RPIENBIExpbWl0ZWQxKzApBgNVBAMTIkNPTU9ETyBSU0EgQ2VydGlmaWNh\ndGlvbiBBdXRob3JpdHkwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQCR\n6FSS0gpWsawNJN3Fz0RndJkrN6N9I3AAcbxT38T6KhKPS38QVr2fcHK3YX/JSw8X\npz3jsARh7v8Rl8f0hj4K+j5c+ZPmNHrZFGvnnLOFoIJ6dq9xkNfs/Q36nGz637CC\n9BR++b7Epi9Pf5l/tfxnQ3K9DADWietrLNPtj5gcFKt+5eNu/Nio5JIk2kNrYrhV\n/erBvGy2i/MOjZrkm2xpmfh4SDBF1a3hDTxFYPwyllEnvGfDyi62a+pGx8cgoLEf\nZd5ICLqkTqnyg0Y3hOvozIFIQ2dOciqbXL1MGyiKXCJ7tKuY2e7gUYPDCUZObT6Z\n+pUX2nwzV0E8jVHtC7ZcryxjGt9XyD+86V3Em69FmeKjWiS0uqlWPc9vqv9JWL7w\nqP/0uK3pN/u6uPQLOvnoQ0IeidiEyxPx2bvhiWC4jChWrBQdnArncevPDt09qZah\nSL0896+1DSJMwBGB7FY79tOi4lu3sgQiUpWAk2nojkxl8ZEDLXB0AuqLZxUpaVIC\nu9ffUGpVRr+goyhhf3DQw6KqLCGqR84onAZFdr+CGCe01a60y1Dma/RMhnEw6abf\nFobg2P9A3fvQQoh/ozM6LlweQRGBY84YcWsr7KaKtzFcOmpH4MN5WdYgGq/yapiq\ncrxXStJLnbsQ/LBMQeXtHT1eKJ2czL+zUdqnR+WEUwIDAQABo0IwQDAdBgNVHQ4E\nFgQUu69+Aj36pvE8hI6t7jiY7NkyMtQwDgYDVR0PAQH/BAQDAgEGMA8GA1UdEwEB\n/wQFMAMBAf8wDQYJKoZIhvcNAQEMBQADggIBAArx1UaEt65Ru2yyTUEUAJNMnMvl\nwFTPoCWOAvn9sKIN9SCYPBMtrFaisNZ+EZLpLrqeLppysb0ZRGxhNaKatBYSaVqM\n4dc+pBroLwP0rmEdEBsqpIt6xf4FpuHA1sj+nq6PK7o9mfjYcwlYRm6mnPTXJ9OV\n2jeDchzTc+CiR5kDOF3VSXkAKRzH7JsgHAckaVd4sjn8OoSgtZx8jb8uk2Intzna\nFxiuvTwJaP+EmzzV1gsD41eeFPfR60/IvYcjt7ZJQ3mFXLrrkguhxuhoqEwWsRqZ\nCuhTLJK7oQkYdQxlqHvLI7cawiiFwxv/0Cti76R7CZGYZ4wUAc1oBmpjIXUDgIiK\nboHGhfKppC3n9KUkEEeDys30jXlYsQab5xoq2Z0B15R97QNKyvDb6KkBPvVWmcke\njkk9u+UJueBPSZI9FoJAzMxZxuY67RIuaTxslbH9qh17f4a+Hg4yRvv7E491f0yL\nS0Zj/gA0QHDBw7mh3aZw4gSzQbzpgJHqZJx64SIDqZxubw5lT2yHh17zbqD5daWb\nQOhTsiedSrnAdyGN/4fy3ryM7xfft0kL0fJuMAsaDk527RH89elWsn2/x20Kk4yl\n0MC2Hb46TpSi125sC8KKfPog88Tk5c0NqMuRkrF8hey1FGlmDoLnzc7ILaZRfyHB\nNVOFBkpdn627G190\n-----END CERTIFICATE-----\n\n# Issuer: CN=USERTrust RSA Certification Authority O=The USERTRUST Network\n# Subject: CN=USERTrust RSA Certification Authority O=The USERTRUST Network\n# Label: \"USERTrust RSA Certification Authority\"\n# Serial: 2645093764781058787591871645665788717\n# MD5 Fingerprint: 1b:fe:69:d1:91:b7:19:33:a3:72:a8:0f:e1:55:e5:b5\n# SHA1 Fingerprint: 2b:8f:1b:57:33:0d:bb:a2:d0:7a:6c:51:f7:0e:e9:0d:da:b9:ad:8e\n# SHA256 Fingerprint: e7:93:c9:b0:2f:d8:aa:13:e2:1c:31:22:8a:cc:b0:81:19:64:3b:74:9c:89:89:64:b1:74:6d:46:c3:d4:cb:d2\n-----BEGIN CERTIFICATE-----\nMIIF3jCCA8agAwIBAgIQAf1tMPyjylGoG7xkDjUDLTANBgkqhkiG9w0BAQwFADCB\niDELMAkGA1UEBhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFDASBgNVBAcTC0pl\ncnNleSBDaXR5MR4wHAYDVQQKExVUaGUgVVNFUlRSVVNUIE5ldHdvcmsxLjAsBgNV\nBAMTJVVTRVJUcnVzdCBSU0EgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkwHhcNMTAw\nMjAxMDAwMDAwWhcNMzgwMTE4MjM1OTU5WjCBiDELMAkGA1UEBhMCVVMxEzARBgNV\nBAgTCk5ldyBKZXJzZXkxFDASBgNVBAcTC0plcnNleSBDaXR5MR4wHAYDVQQKExVU\naGUgVVNFUlRSVVNUIE5ldHdvcmsxLjAsBgNVBAMTJVVTRVJUcnVzdCBSU0EgQ2Vy\ndGlmaWNhdGlvbiBBdXRob3JpdHkwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIK\nAoICAQCAEmUXNg7D2wiz0KxXDXbtzSfTTK1Qg2HiqiBNCS1kCdzOiZ/MPans9s/B\n3PHTsdZ7NygRK0faOca8Ohm0X6a9fZ2jY0K2dvKpOyuR+OJv0OwWIJAJPuLodMkY\ntJHUYmTbf6MG8YgYapAiPLz+E/CHFHv25B+O1ORRxhFnRghRy4YUVD+8M/5+bJz/\nFp0YvVGONaanZshyZ9shZrHUm3gDwFA66Mzw3LyeTP6vBZY1H1dat//O+T23LLb2\nVN3I5xI6Ta5MirdcmrS3ID3KfyI0rn47aGYBROcBTkZTmzNg95S+UzeQc0PzMsNT\n79uq/nROacdrjGCT3sTHDN/hMq7MkztReJVni+49Vv4M0GkPGw/zJSZrM233bkf6\nc0Plfg6lZrEpfDKEY1WJxA3Bk1QwGROs0303p+tdOmw1XNtB1xLaqUkL39iAigmT\nYo61Zs8liM2EuLE/pDkP2QKe6xJMlXzzawWpXhaDzLhn4ugTncxbgtNMs+1b/97l\nc6wjOy0AvzVVdAlJ2ElYGn+SNuZRkg7zJn0cTRe8yexDJtC/QV9AqURE9JnnV4ee\nUB9XVKg+/XRjL7FQZQnmWEIuQxpMtPAlR1n6BB6T1CZGSlCBst6+eLf8ZxXhyVeE\nHg9j1uliutZfVS7qXMYoCAQlObgOK6nyTJccBz8NUvXt7y+CDwIDAQABo0IwQDAd\nBgNVHQ4EFgQUU3m/WqorSs9UgOHYm8Cd8rIDZsswDgYDVR0PAQH/BAQDAgEGMA8G\nA1UdEwEB/wQFMAMBAf8wDQYJKoZIhvcNAQEMBQADggIBAFzUfA3P9wF9QZllDHPF\nUp/L+M+ZBn8b2kMVn54CVVeWFPFSPCeHlCjtHzoBN6J2/FNQwISbxmtOuowhT6KO\nVWKR82kV2LyI48SqC/3vqOlLVSoGIG1VeCkZ7l8wXEskEVX/JJpuXior7gtNn3/3\nATiUFJVDBwn7YKnuHKsSjKCaXqeYalltiz8I+8jRRa8YFWSQEg9zKC7F4iRO/Fjs\n8PRF/iKz6y+O0tlFYQXBl2+odnKPi4w2r78NBc5xjeambx9spnFixdjQg3IM8WcR\niQycE0xyNN+81XHfqnHd4blsjDwSXWXavVcStkNr/+XeTWYRUc+ZruwXtuhxkYze\nSf7dNXGiFSeUHM9h4ya7b6NnJSFd5t0dCy5oGzuCr+yDZ4XUmFF0sbmZgIn/f3gZ\nXHlKYC6SQK5MNyosycdiyA5d9zZbyuAlJQG03RoHnHcAP9Dc1ew91Pq7P8yF1m9/\nqS3fuQL39ZeatTXaw2ewh0qpKJ4jjv9cJ2vhsE/zB+4ALtRZh8tSQZXq9EfX7mRB\nVXyNWQKV3WKdwrnuWih0hKWbt5DHDAff9Yk2dDLWKMGwsAvgnEzDHNb842m1R0aB\nL6KCq9NjRHDEjf8tM7qtj3u1cIiuPhnPQCjY/MiQu12ZIvVS5ljFH4gxQ+6IHdfG\njjxDah2nGN59PRbxYvnKkKj9\n-----END CERTIFICATE-----\n\n# Issuer: CN=USERTrust ECC Certification Authority O=The USERTRUST Network\n# Subject: CN=USERTrust ECC Certification Authority O=The USERTRUST Network\n# Label: \"USERTrust ECC Certification Authority\"\n# Serial: 123013823720199481456569720443997572134\n# MD5 Fingerprint: fa:68:bc:d9:b5:7f:ad:fd:c9:1d:06:83:28:cc:24:c1\n# SHA1 Fingerprint: d1:cb:ca:5d:b2:d5:2a:7f:69:3b:67:4d:e5:f0:5a:1d:0c:95:7d:f0\n# SHA256 Fingerprint: 4f:f4:60:d5:4b:9c:86:da:bf:bc:fc:57:12:e0:40:0d:2b:ed:3f:bc:4d:4f:bd:aa:86:e0:6a:dc:d2:a9:ad:7a\n-----BEGIN CERTIFICATE-----\nMIICjzCCAhWgAwIBAgIQXIuZxVqUxdJxVt7NiYDMJjAKBggqhkjOPQQDAzCBiDEL\nMAkGA1UEBhMCVVMxEzARBgNVBAgTCk5ldyBKZXJzZXkxFDASBgNVBAcTC0plcnNl\neSBDaXR5MR4wHAYDVQQKExVUaGUgVVNFUlRSVVNUIE5ldHdvcmsxLjAsBgNVBAMT\nJVVTRVJUcnVzdCBFQ0MgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkwHhcNMTAwMjAx\nMDAwMDAwWhcNMzgwMTE4MjM1OTU5WjCBiDELMAkGA1UEBhMCVVMxEzARBgNVBAgT\nCk5ldyBKZXJzZXkxFDASBgNVBAcTC0plcnNleSBDaXR5MR4wHAYDVQQKExVUaGUg\nVVNFUlRSVVNUIE5ldHdvcmsxLjAsBgNVBAMTJVVTRVJUcnVzdCBFQ0MgQ2VydGlm\naWNhdGlvbiBBdXRob3JpdHkwdjAQBgcqhkjOPQIBBgUrgQQAIgNiAAQarFRaqflo\nI+d61SRvU8Za2EurxtW20eZzca7dnNYMYf3boIkDuAUU7FfO7l0/4iGzzvfUinng\no4N+LZfQYcTxmdwlkWOrfzCjtHDix6EznPO/LlxTsV+zfTJ/ijTjeXmjQjBAMB0G\nA1UdDgQWBBQ64QmG1M8ZwpZ2dEl23OA1xmNjmjAOBgNVHQ8BAf8EBAMCAQYwDwYD\nVR0TAQH/BAUwAwEB/zAKBggqhkjOPQQDAwNoADBlAjA2Z6EWCNzklwBBHU6+4WMB\nzzuqQhFkoJ2UOQIReVx7Hfpkue4WQrO/isIJxOzksU0CMQDpKmFHjFJKS04YcPbW\nRNZu9YO6bVi9JNlWSOrvxKJGgYhqOkbRqZtNyWHa0V1Xahg=\n-----END CERTIFICATE-----\n\n# Issuer: CN=GlobalSign O=GlobalSign OU=GlobalSign ECC Root CA - R4\n# Subject: CN=GlobalSign O=GlobalSign OU=GlobalSign ECC Root CA - R4\n# Label: \"GlobalSign ECC Root CA - R4\"\n# Serial: 14367148294922964480859022125800977897474\n# MD5 Fingerprint: 20:f0:27:68:d1:7e:a0:9d:0e:e6:2a:ca:df:5c:89:8e\n# SHA1 Fingerprint: 69:69:56:2e:40:80:f4:24:a1:e7:19:9f:14:ba:f3:ee:58:ab:6a:bb\n# SHA256 Fingerprint: be:c9:49:11:c2:95:56:76:db:6c:0a:55:09:86:d7:6e:3b:a0:05:66:7c:44:2c:97:62:b4:fb:b7:73:de:22:8c\n-----BEGIN CERTIFICATE-----\nMIIB4TCCAYegAwIBAgIRKjikHJYKBN5CsiilC+g0mAIwCgYIKoZIzj0EAwIwUDEk\nMCIGA1UECxMbR2xvYmFsU2lnbiBFQ0MgUm9vdCBDQSAtIFI0MRMwEQYDVQQKEwpH\nbG9iYWxTaWduMRMwEQYDVQQDEwpHbG9iYWxTaWduMB4XDTEyMTExMzAwMDAwMFoX\nDTM4MDExOTAzMTQwN1owUDEkMCIGA1UECxMbR2xvYmFsU2lnbiBFQ0MgUm9vdCBD\nQSAtIFI0MRMwEQYDVQQKEwpHbG9iYWxTaWduMRMwEQYDVQQDEwpHbG9iYWxTaWdu\nMFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEuMZ5049sJQ6fLjkZHAOkrprlOQcJ\nFspjsbmG+IpXwVfOQvpzofdlQv8ewQCybnMO/8ch5RikqtlxP6jUuc6MHaNCMEAw\nDgYDVR0PAQH/BAQDAgEGMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFFSwe61F\nuOJAf/sKbvu+M8k8o4TVMAoGCCqGSM49BAMCA0gAMEUCIQDckqGgE6bPA7DmxCGX\nkPoUVy0D7O48027KqGx2vKLeuwIgJ6iFJzWbVsaj8kfSt24bAgAXqmemFZHe+pTs\newv4n4Q=\n-----END CERTIFICATE-----\n\n# Issuer: CN=GlobalSign O=GlobalSign OU=GlobalSign ECC Root CA - R5\n# Subject: CN=GlobalSign O=GlobalSign OU=GlobalSign ECC Root CA - R5\n# Label: \"GlobalSign ECC Root CA - R5\"\n# Serial: 32785792099990507226680698011560947931244\n# MD5 Fingerprint: 9f:ad:3b:1c:02:1e:8a:ba:17:74:38:81:0c:a2:bc:08\n# SHA1 Fingerprint: 1f:24:c6:30:cd:a4:18:ef:20:69:ff:ad:4f:dd:5f:46:3a:1b:69:aa\n# SHA256 Fingerprint: 17:9f:bc:14:8a:3d:d0:0f:d2:4e:a1:34:58:cc:43:bf:a7:f5:9c:81:82:d7:83:a5:13:f6:eb:ec:10:0c:89:24\n-----BEGIN CERTIFICATE-----\nMIICHjCCAaSgAwIBAgIRYFlJ4CYuu1X5CneKcflK2GwwCgYIKoZIzj0EAwMwUDEk\nMCIGA1UECxMbR2xvYmFsU2lnbiBFQ0MgUm9vdCBDQSAtIFI1MRMwEQYDVQQKEwpH\nbG9iYWxTaWduMRMwEQYDVQQDEwpHbG9iYWxTaWduMB4XDTEyMTExMzAwMDAwMFoX\nDTM4MDExOTAzMTQwN1owUDEkMCIGA1UECxMbR2xvYmFsU2lnbiBFQ0MgUm9vdCBD\nQSAtIFI1MRMwEQYDVQQKEwpHbG9iYWxTaWduMRMwEQYDVQQDEwpHbG9iYWxTaWdu\nMHYwEAYHKoZIzj0CAQYFK4EEACIDYgAER0UOlvt9Xb/pOdEh+J8LttV7HpI6SFkc\n8GIxLcB6KP4ap1yztsyX50XUWPrRd21DosCHZTQKH3rd6zwzocWdTaRvQZU4f8ke\nhOvRnkmSh5SHDDqFSmafnVmTTZdhBoZKo0IwQDAOBgNVHQ8BAf8EBAMCAQYwDwYD\nVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQUPeYpSJvqB8ohREom3m7e0oPQn1kwCgYI\nKoZIzj0EAwMDaAAwZQIxAOVpEslu28YxuglB4Zf4+/2a4n0Sye18ZNPLBSWLVtmg\n515dTguDnFt2KaAJJiFqYgIwcdK1j1zqO+F4CYWodZI7yFz9SO8NdCKoCOJuxUnO\nxwy8p2Fp8fc74SrL+SvzZpA3\n-----END CERTIFICATE-----\n\n# Issuer: CN=Staat der Nederlanden Root CA - G3 O=Staat der Nederlanden\n# Subject: CN=Staat der Nederlanden Root CA - G3 O=Staat der Nederlanden\n# Label: \"Staat der Nederlanden Root CA - G3\"\n# Serial: 10003001\n# MD5 Fingerprint: 0b:46:67:07:db:10:2f:19:8c:35:50:60:d1:0b:f4:37\n# SHA1 Fingerprint: d8:eb:6b:41:51:92:59:e0:f3:e7:85:00:c0:3d:b6:88:97:c9:ee:fc\n# SHA256 Fingerprint: 3c:4f:b0:b9:5a:b8:b3:00:32:f4:32:b8:6f:53:5f:e1:72:c1:85:d0:fd:39:86:58:37:cf:36:18:7f:a6:f4:28\n-----BEGIN CERTIFICATE-----\nMIIFdDCCA1ygAwIBAgIEAJiiOTANBgkqhkiG9w0BAQsFADBaMQswCQYDVQQGEwJO\nTDEeMBwGA1UECgwVU3RhYXQgZGVyIE5lZGVybGFuZGVuMSswKQYDVQQDDCJTdGFh\ndCBkZXIgTmVkZXJsYW5kZW4gUm9vdCBDQSAtIEczMB4XDTEzMTExNDExMjg0MloX\nDTI4MTExMzIzMDAwMFowWjELMAkGA1UEBhMCTkwxHjAcBgNVBAoMFVN0YWF0IGRl\nciBOZWRlcmxhbmRlbjErMCkGA1UEAwwiU3RhYXQgZGVyIE5lZGVybGFuZGVuIFJv\nb3QgQ0EgLSBHMzCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBAL4yolQP\ncPssXFnrbMSkUeiFKrPMSjTysF/zDsccPVMeiAho2G89rcKezIJnByeHaHE6n3WW\nIkYFsO2tx1ueKt6c/DrGlaf1F2cY5y9JCAxcz+bMNO14+1Cx3Gsy8KL+tjzk7FqX\nxz8ecAgwoNzFs21v0IJyEavSgWhZghe3eJJg+szeP4TrjTgzkApyI/o1zCZxMdFy\nKJLZWyNtZrVtB0LrpjPOktvA9mxjeM3KTj215VKb8b475lRgsGYeCasH/lSJEULR\n9yS6YHgamPfJEf0WwTUaVHXvQ9Plrk7O53vDxk5hUUurmkVLoR9BvUhTFXFkC4az\n5S6+zqQbwSmEorXLCCN2QyIkHxcE1G6cxvx/K2Ya7Irl1s9N9WMJtxU51nus6+N8\n6U78dULI7ViVDAZCopz35HCz33JvWjdAidiFpNfxC95DGdRKWCyMijmev4SH8RY7\nNgzp07TKbBlBUgmhHbBqv4LvcFEhMtwFdozL92TkA1CvjJFnq8Xy7ljY3r735zHP\nbMk7ccHViLVlvMDoFxcHErVc0qsgk7TmgoNwNsXNo42ti+yjwUOH5kPiNL6VizXt\nBznaqB16nzaeErAMZRKQFWDZJkBE41ZgpRDUajz9QdwOWke275dhdU/Z/seyHdTt\nXUmzqWrLZoQT1Vyg3N9udwbRcXXIV2+vD3dbAgMBAAGjQjBAMA8GA1UdEwEB/wQF\nMAMBAf8wDgYDVR0PAQH/BAQDAgEGMB0GA1UdDgQWBBRUrfrHkleuyjWcLhL75Lpd\nINyUVzANBgkqhkiG9w0BAQsFAAOCAgEAMJmdBTLIXg47mAE6iqTnB/d6+Oea31BD\nU5cqPco8R5gu4RV78ZLzYdqQJRZlwJ9UXQ4DO1t3ApyEtg2YXzTdO2PCwyiBwpwp\nLiniyMMB8jPqKqrMCQj3ZWfGzd/TtiunvczRDnBfuCPRy5FOCvTIeuXZYzbB1N/8\nIpf3YF3qKS9Ysr1YvY2WTxB1v0h7PVGHoTx0IsL8B3+A3MSs/mrBcDCw6Y5p4ixp\ngZQJut3+TcCDjJRYwEYgr5wfAvg1VUkvRtTA8KCWAg8zxXHzniN9lLf9OtMJgwYh\n/WA9rjLA0u6NpvDntIJ8CsxwyXmA+P5M9zWEGYox+wrZ13+b8KKaa8MFSu1BYBQw\n0aoRQm7TIwIEC8Zl3d1Sd9qBa7Ko+gE4uZbqKmxnl4mUnrzhVNXkanjvSr0rmj1A\nfsbAddJu+2gw7OyLnflJNZoaLNmzlTnVHpL3prllL+U9bTpITAjc5CgSKL59NVzq\n4BZ+Extq1z7XnvwtdbLBFNUjA9tbbws+eC8N3jONFrdI54OagQ97wUNNVQQXOEpR\n1VmiiXTTn74eS9fGbbeIJG9gkaSChVtWQbzQRKtqE77RLFi3EjNYsjdj3BP1lB0/\nQFH1T/U67cjF68IeHRaVesd+QnGTbksVtzDfqu1XhUisHWrdOWnk4Xl4vs4Fv6EM\n94B7IWcnMFk=\n-----END CERTIFICATE-----\n\n# Issuer: CN=Staat der Nederlanden EV Root CA O=Staat der Nederlanden\n# Subject: CN=Staat der Nederlanden EV Root CA O=Staat der Nederlanden\n# Label: \"Staat der Nederlanden EV Root CA\"\n# Serial: 10000013\n# MD5 Fingerprint: fc:06:af:7b:e8:1a:f1:9a:b4:e8:d2:70:1f:c0:f5:ba\n# SHA1 Fingerprint: 76:e2:7e:c1:4f:db:82:c1:c0:a6:75:b5:05:be:3d:29:b4:ed:db:bb\n# SHA256 Fingerprint: 4d:24:91:41:4c:fe:95:67:46:ec:4c:ef:a6:cf:6f:72:e2:8a:13:29:43:2f:9d:8a:90:7a:c4:cb:5d:ad:c1:5a\n-----BEGIN CERTIFICATE-----\nMIIFcDCCA1igAwIBAgIEAJiWjTANBgkqhkiG9w0BAQsFADBYMQswCQYDVQQGEwJO\nTDEeMBwGA1UECgwVU3RhYXQgZGVyIE5lZGVybGFuZGVuMSkwJwYDVQQDDCBTdGFh\ndCBkZXIgTmVkZXJsYW5kZW4gRVYgUm9vdCBDQTAeFw0xMDEyMDgxMTE5MjlaFw0y\nMjEyMDgxMTEwMjhaMFgxCzAJBgNVBAYTAk5MMR4wHAYDVQQKDBVTdGFhdCBkZXIg\nTmVkZXJsYW5kZW4xKTAnBgNVBAMMIFN0YWF0IGRlciBOZWRlcmxhbmRlbiBFViBS\nb290IENBMIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEA48d+ifkkSzrS\nM4M1LGns3Amk41GoJSt5uAg94JG6hIXGhaTK5skuU6TJJB79VWZxXSzFYGgEt9nC\nUiY4iKTWO0Cmws0/zZiTs1QUWJZV1VD+hq2kY39ch/aO5ieSZxeSAgMs3NZmdO3d\nZ//BYY1jTw+bbRcwJu+r0h8QoPnFfxZpgQNH7R5ojXKhTbImxrpsX23Wr9GxE46p\nrfNeaXUmGD5BKyF/7otdBwadQ8QpCiv8Kj6GyzyDOvnJDdrFmeK8eEEzduG/L13l\npJhQDBXd4Pqcfzho0LKmeqfRMb1+ilgnQ7O6M5HTp5gVXJrm0w912fxBmJc+qiXb\nj5IusHsMX/FjqTf5m3VpTCgmJdrV8hJwRVXj33NeN/UhbJCONVrJ0yPr08C+eKxC\nKFhmpUZtcALXEPlLVPxdhkqHz3/KRawRWrUgUY0viEeXOcDPusBCAUCZSCELa6fS\n/ZbV0b5GnUngC6agIk440ME8MLxwjyx1zNDFjFE7PZQIZCZhfbnDZY8UnCHQqv0X\ncgOPvZuM5l5Tnrmd74K74bzickFbIZTTRTeU0d8JOV3nI6qaHcptqAqGhYqCvkIH\n1vI4gnPah1vlPNOePqc7nvQDs/nxfRN0Av+7oeX6AHkcpmZBiFxgV6YuCcS6/ZrP\npx9Aw7vMWgpVSzs4dlG4Y4uElBbmVvMCAwEAAaNCMEAwDwYDVR0TAQH/BAUwAwEB\n/zAOBgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYEFP6rAJCYniT8qcwaivsnuL8wbqg7\nMA0GCSqGSIb3DQEBCwUAA4ICAQDPdyxuVr5Os7aEAJSrR8kN0nbHhp8dB9O2tLsI\neK9p0gtJ3jPFrK3CiAJ9Brc1AsFgyb/E6JTe1NOpEyVa/m6irn0F3H3zbPB+po3u\n2dfOWBfoqSmuc0iH55vKbimhZF8ZE/euBhD/UcabTVUlT5OZEAFTdfETzsemQUHS\nv4ilf0X8rLiltTMMgsT7B/Zq5SWEXwbKwYY5EdtYzXc7LMJMD16a4/CrPmEbUCTC\nwPTxGfARKbalGAKb12NMcIxHowNDXLldRqANb/9Zjr7dn3LDWyvfjFvO5QxGbJKy\nCqNMVEIYFRIYvdr8unRu/8G2oGTYqV9Vrp9canaW2HNnh/tNf1zuacpzEPuKqf2e\nvTY4SUmH9A4U8OmHuD+nT3pajnnUk+S7aFKErGzp85hwVXIy+TSrK0m1zSBi5Dp6\nZ2Orltxtrpfs/J92VoguZs9btsmksNcFuuEnL5O7Jiqik7Ab846+HUCjuTaPPoIa\nGl6I6lD4WeKDRikL40Rc4ZW2aZCaFG+XroHPaO+Zmr615+F/+PoTRxZMzG0IQOeL\neG9QgkRQP2YGiqtDhFZKDyAthg710tvSeopLzaXoTvFeJiUBWSOgftL2fiFX1ye8\nFVdMpEbB4IMeDExNH08GGeL5qPQ6gqGyeUN51q1veieQA6TqJIc/2b3Z6fJfUEkc\n7uzXLg==\n-----END CERTIFICATE-----\n\n# Issuer: CN=IdenTrust Commercial Root CA 1 O=IdenTrust\n# Subject: CN=IdenTrust Commercial Root CA 1 O=IdenTrust\n# Label: \"IdenTrust Commercial Root CA 1\"\n# Serial: 13298821034946342390520003877796839426\n# MD5 Fingerprint: b3:3e:77:73:75:ee:a0:d3:e3:7e:49:63:49:59:bb:c7\n# SHA1 Fingerprint: df:71:7e:aa:4a:d9:4e:c9:55:84:99:60:2d:48:de:5f:bc:f0:3a:25\n# SHA256 Fingerprint: 5d:56:49:9b:e4:d2:e0:8b:cf:ca:d0:8a:3e:38:72:3d:50:50:3b:de:70:69:48:e4:2f:55:60:30:19:e5:28:ae\n-----BEGIN CERTIFICATE-----\nMIIFYDCCA0igAwIBAgIQCgFCgAAAAUUjyES1AAAAAjANBgkqhkiG9w0BAQsFADBK\nMQswCQYDVQQGEwJVUzESMBAGA1UEChMJSWRlblRydXN0MScwJQYDVQQDEx5JZGVu\nVHJ1c3QgQ29tbWVyY2lhbCBSb290IENBIDEwHhcNMTQwMTE2MTgxMjIzWhcNMzQw\nMTE2MTgxMjIzWjBKMQswCQYDVQQGEwJVUzESMBAGA1UEChMJSWRlblRydXN0MScw\nJQYDVQQDEx5JZGVuVHJ1c3QgQ29tbWVyY2lhbCBSb290IENBIDEwggIiMA0GCSqG\nSIb3DQEBAQUAA4ICDwAwggIKAoICAQCnUBneP5k91DNG8W9RYYKyqU+PZ4ldhNlT\n3Qwo2dfw/66VQ3KZ+bVdfIrBQuExUHTRgQ18zZshq0PirK1ehm7zCYofWjK9ouuU\n+ehcCuz/mNKvcbO0U59Oh++SvL3sTzIwiEsXXlfEU8L2ApeN2WIrvyQfYo3fw7gp\nS0l4PJNgiCL8mdo2yMKi1CxUAGc1bnO/AljwpN3lsKImesrgNqUZFvX9t++uP0D1\nbVoE/c40yiTcdCMbXTMTEl3EASX2MN0CXZ/g1Ue9tOsbobtJSdifWwLziuQkkORi\nT0/Br4sOdBeo0XKIanoBScy0RnnGF7HamB4HWfp1IYVl3ZBWzvurpWCdxJ35UrCL\nvYf5jysjCiN2O/cz4ckA82n5S6LgTrx+kzmEB/dEcH7+B1rlsazRGMzyNeVJSQjK\nVsk9+w8YfYs7wRPCTY/JTw436R+hDmrfYi7LNQZReSzIJTj0+kuniVyc0uMNOYZK\ndHzVWYfCP04MXFL0PfdSgvHqo6z9STQaKPNBiDoT7uje/5kdX7rL6B7yuVBgwDHT\nc+XvvqDtMwt0viAgxGds8AgDelWAf0ZOlqf0Hj7h9tgJ4TNkK2PXMl6f+cB7D3hv\nl7yTmvmcEpB4eoCHFddydJxVdHixuuFucAS6T6C6aMN7/zHwcz09lCqxC0EOoP5N\niGVreTO01wIDAQABo0IwQDAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB\n/zAdBgNVHQ4EFgQU7UQZwNPwBovupHu+QucmVMiONnYwDQYJKoZIhvcNAQELBQAD\nggIBAA2ukDL2pkt8RHYZYR4nKM1eVO8lvOMIkPkp165oCOGUAFjvLi5+U1KMtlwH\n6oi6mYtQlNeCgN9hCQCTrQ0U5s7B8jeUeLBfnLOic7iPBZM4zY0+sLj7wM+x8uwt\nLRvM7Kqas6pgghstO8OEPVeKlh6cdbjTMM1gCIOQ045U8U1mwF10A0Cj7oV+wh93\nnAbowacYXVKV7cndJZ5t+qntozo00Fl72u1Q8zW/7esUTTHHYPTa8Yec4kjixsU3\n+wYQ+nVZZjFHKdp2mhzpgq7vmrlR94gjmmmVYjzlVYA211QC//G5Xc7UI2/YRYRK\nW2XviQzdFKcgyxilJbQN+QHwotL0AMh0jqEqSI5l2xPE4iUXfeu+h1sXIFRRk0pT\nAwvsXcoz7WL9RccvW9xYoIA55vrX/hMUpu09lEpCdNTDd1lzzY9GvlU47/rokTLq\nl1gEIt44w8y8bckzOmoKaT+gyOpyj4xjhiO9bTyWnpXgSUyqorkqG5w2gXjtw+hG\n4iZZRHUe2XWJUc0QhJ1hYMtd+ZciTY6Y5uN/9lu7rs3KSoFrXgvzUeF0K+l+J6fZ\nmUlO+KWA2yUPHGNiiskzZ2s8EIPGrd6ozRaOjfAHN3Gf8qv8QfXBi+wAN10J5U6A\n7/qxXDgGpRtK4dw4LTzcqx+QGtVKnO7RcGzM7vRX+Bi6hG6H\n-----END CERTIFICATE-----\n\n# Issuer: CN=IdenTrust Public Sector Root CA 1 O=IdenTrust\n# Subject: CN=IdenTrust Public Sector Root CA 1 O=IdenTrust\n# Label: \"IdenTrust Public Sector Root CA 1\"\n# Serial: 13298821034946342390521976156843933698\n# MD5 Fingerprint: 37:06:a5:b0:fc:89:9d:ba:f4:6b:8c:1a:64:cd:d5:ba\n# SHA1 Fingerprint: ba:29:41:60:77:98:3f:f4:f3:ef:f2:31:05:3b:2e:ea:6d:4d:45:fd\n# SHA256 Fingerprint: 30:d0:89:5a:9a:44:8a:26:20:91:63:55:22:d1:f5:20:10:b5:86:7a:ca:e1:2c:78:ef:95:8f:d4:f4:38:9f:2f\n-----BEGIN CERTIFICATE-----\nMIIFZjCCA06gAwIBAgIQCgFCgAAAAUUjz0Z8AAAAAjANBgkqhkiG9w0BAQsFADBN\nMQswCQYDVQQGEwJVUzESMBAGA1UEChMJSWRlblRydXN0MSowKAYDVQQDEyFJZGVu\nVHJ1c3QgUHVibGljIFNlY3RvciBSb290IENBIDEwHhcNMTQwMTE2MTc1MzMyWhcN\nMzQwMTE2MTc1MzMyWjBNMQswCQYDVQQGEwJVUzESMBAGA1UEChMJSWRlblRydXN0\nMSowKAYDVQQDEyFJZGVuVHJ1c3QgUHVibGljIFNlY3RvciBSb290IENBIDEwggIi\nMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQC2IpT8pEiv6EdrCvsnduTyP4o7\nekosMSqMjbCpwzFrqHd2hCa2rIFCDQjrVVi7evi8ZX3yoG2LqEfpYnYeEe4IFNGy\nRBb06tD6Hi9e28tzQa68ALBKK0CyrOE7S8ItneShm+waOh7wCLPQ5CQ1B5+ctMlS\nbdsHyo+1W/CD80/HLaXIrcuVIKQxKFdYWuSNG5qrng0M8gozOSI5Cpcu81N3uURF\n/YTLNiCBWS2ab21ISGHKTN9T0a9SvESfqy9rg3LvdYDaBjMbXcjaY8ZNzaxmMc3R\n3j6HEDbhuaR672BQssvKplbgN6+rNBM5Jeg5ZuSYeqoSmJxZZoY+rfGwyj4GD3vw\nEUs3oERte8uojHH01bWRNszwFcYr3lEXsZdMUD2xlVl8BX0tIdUAvwFnol57plzy\n9yLxkA2T26pEUWbMfXYD62qoKjgZl3YNa4ph+bz27nb9cCvdKTz4Ch5bQhyLVi9V\nGxyhLrXHFub4qjySjmm2AcG1hp2JDws4lFTo6tyePSW8Uybt1as5qsVATFSrsrTZ\n2fjXctscvG29ZV/viDUqZi/u9rNl8DONfJhBaUYPQxxp+pu10GFqzcpL2UyQRqsV\nWaFHVCkugyhfHMKiq3IXAAaOReyL4jM9f9oZRORicsPfIsbyVtTdX5Vy7W1f90gD\nW/3FKqD2cyOEEBsB5wIDAQABo0IwQDAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/\nBAUwAwEB/zAdBgNVHQ4EFgQU43HgntinQtnbcZFrlJPrw6PRFKMwDQYJKoZIhvcN\nAQELBQADggIBAEf63QqwEZE4rU1d9+UOl1QZgkiHVIyqZJnYWv6IAcVYpZmxI1Qj\nt2odIFflAWJBF9MJ23XLblSQdf4an4EKwt3X9wnQW3IV5B4Jaj0z8yGa5hV+rVHV\nDRDtfULAj+7AmgjVQdZcDiFpboBhDhXAuM/FSRJSzL46zNQuOAXeNf0fb7iAaJg9\nTaDKQGXSc3z1i9kKlT/YPyNtGtEqJBnZhbMX73huqVjRI9PHE+1yJX9dsXNw0H8G\nlwmEKYBhHfpe/3OsoOOJuBxxFcbeMX8S3OFtm6/n6J91eEyrRjuazr8FGF1NFTwW\nmhlQBJqymm9li1JfPFgEKCXAZmExfrngdbkaqIHWchezxQMxNRF4eKLg6TCMf4Df\nWN88uieW4oA0beOY02QnrEh+KHdcxiVhJfiFDGX6xDIvpZgF5PgLZxYWxoK4Mhn5\n+bl53B/N66+rDt0b20XkeucC4pVd/GnwU2lhlXV5C15V5jgclKlZM57IcXR5f1GJ\ntshquDDIajjDbp7hNxbqBWJMWxJH7ae0s1hWx0nzfxJoCTFx8G34Tkf71oXuxVhA\nGaQdp/lLQzfcaFpPz+vCZHTetBXZ9FRUGi8c15dxVJCO2SCdUyt/q4/i6jC8UDfv\n8Ue1fXwsBOxonbRJRBD0ckscZOf85muQ3Wl9af0AVqW3rLatt8o+Ae+c\n-----END CERTIFICATE-----\n\n# Issuer: CN=Entrust Root Certification Authority - G2 O=Entrust, Inc. OU=See www.entrust.net/legal-terms/(c) 2009 Entrust, Inc. - for authorized use only\n# Subject: CN=Entrust Root Certification Authority - G2 O=Entrust, Inc. OU=See www.entrust.net/legal-terms/(c) 2009 Entrust, Inc. - for authorized use only\n# Label: \"Entrust Root Certification Authority - G2\"\n# Serial: 1246989352\n# MD5 Fingerprint: 4b:e2:c9:91:96:65:0c:f4:0e:5a:93:92:a0:0a:fe:b2\n# SHA1 Fingerprint: 8c:f4:27:fd:79:0c:3a:d1:66:06:8d:e8:1e:57:ef:bb:93:22:72:d4\n# SHA256 Fingerprint: 43:df:57:74:b0:3e:7f:ef:5f:e4:0d:93:1a:7b:ed:f1:bb:2e:6b:42:73:8c:4e:6d:38:41:10:3d:3a:a7:f3:39\n-----BEGIN CERTIFICATE-----\nMIIEPjCCAyagAwIBAgIESlOMKDANBgkqhkiG9w0BAQsFADCBvjELMAkGA1UEBhMC\nVVMxFjAUBgNVBAoTDUVudHJ1c3QsIEluYy4xKDAmBgNVBAsTH1NlZSB3d3cuZW50\ncnVzdC5uZXQvbGVnYWwtdGVybXMxOTA3BgNVBAsTMChjKSAyMDA5IEVudHJ1c3Qs\nIEluYy4gLSBmb3IgYXV0aG9yaXplZCB1c2Ugb25seTEyMDAGA1UEAxMpRW50cnVz\ndCBSb290IENlcnRpZmljYXRpb24gQXV0aG9yaXR5IC0gRzIwHhcNMDkwNzA3MTcy\nNTU0WhcNMzAxMjA3MTc1NTU0WjCBvjELMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUVu\ndHJ1c3QsIEluYy4xKDAmBgNVBAsTH1NlZSB3d3cuZW50cnVzdC5uZXQvbGVnYWwt\ndGVybXMxOTA3BgNVBAsTMChjKSAyMDA5IEVudHJ1c3QsIEluYy4gLSBmb3IgYXV0\naG9yaXplZCB1c2Ugb25seTEyMDAGA1UEAxMpRW50cnVzdCBSb290IENlcnRpZmlj\nYXRpb24gQXV0aG9yaXR5IC0gRzIwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEK\nAoIBAQC6hLZy254Ma+KZ6TABp3bqMriVQRrJ2mFOWHLP/vaCeb9zYQYKpSfYs1/T\nRU4cctZOMvJyig/3gxnQaoCAAEUesMfnmr8SVycco2gvCoe9amsOXmXzHHfV1IWN\ncCG0szLni6LVhjkCsbjSR87kyUnEO6fe+1R9V77w6G7CebI6C1XiUJgWMhNcL3hW\nwcKUs/Ja5CeanyTXxuzQmyWC48zCxEXFjJd6BmsqEZ+pCm5IO2/b1BEZQvePB7/1\nU1+cPvQXLOZprE4yTGJ36rfo5bs0vBmLrpxR57d+tVOxMyLlbc9wPBr64ptntoP0\njaWvYkxN4FisZDQSA/i2jZRjJKRxAgMBAAGjQjBAMA4GA1UdDwEB/wQEAwIBBjAP\nBgNVHRMBAf8EBTADAQH/MB0GA1UdDgQWBBRqciZ60B7vfec7aVHUbI2fkBJmqzAN\nBgkqhkiG9w0BAQsFAAOCAQEAeZ8dlsa2eT8ijYfThwMEYGprmi5ZiXMRrEPR9RP/\njTkrwPK9T3CMqS/qF8QLVJ7UG5aYMzyorWKiAHarWWluBh1+xLlEjZivEtRh2woZ\nRkfz6/djwUAFQKXSt/S1mja/qYh2iARVBCuch38aNzx+LaUa2NSJXsq9rD1s2G2v\n1fN2D807iDginWyTmsQ9v4IbZT+mD12q/OWyFcq1rca8PdCE6OoGcrBNOTJ4vz4R\nnAuknZoh8/CbCzB428Hch0P+vGOaysXCHMnHjf87ElgI5rY97HosTvuDls4MPGmH\nVHOkc8KT/1EQrBVUAdj8BbGJoX90g5pJ19xOe4pIb4tF9g==\n-----END CERTIFICATE-----\n\n# Issuer: CN=Entrust Root Certification Authority - EC1 O=Entrust, Inc. OU=See www.entrust.net/legal-terms/(c) 2012 Entrust, Inc. - for authorized use only\n# Subject: CN=Entrust Root Certification Authority - EC1 O=Entrust, Inc. OU=See www.entrust.net/legal-terms/(c) 2012 Entrust, Inc. - for authorized use only\n# Label: \"Entrust Root Certification Authority - EC1\"\n# Serial: 51543124481930649114116133369\n# MD5 Fingerprint: b6:7e:1d:f0:58:c5:49:6c:24:3b:3d:ed:98:18:ed:bc\n# SHA1 Fingerprint: 20:d8:06:40:df:9b:25:f5:12:25:3a:11:ea:f7:59:8a:eb:14:b5:47\n# SHA256 Fingerprint: 02:ed:0e:b2:8c:14:da:45:16:5c:56:67:91:70:0d:64:51:d7:fb:56:f0:b2:ab:1d:3b:8e:b0:70:e5:6e:df:f5\n-----BEGIN CERTIFICATE-----\nMIIC+TCCAoCgAwIBAgINAKaLeSkAAAAAUNCR+TAKBggqhkjOPQQDAzCBvzELMAkG\nA1UEBhMCVVMxFjAUBgNVBAoTDUVudHJ1c3QsIEluYy4xKDAmBgNVBAsTH1NlZSB3\nd3cuZW50cnVzdC5uZXQvbGVnYWwtdGVybXMxOTA3BgNVBAsTMChjKSAyMDEyIEVu\ndHJ1c3QsIEluYy4gLSBmb3IgYXV0aG9yaXplZCB1c2Ugb25seTEzMDEGA1UEAxMq\nRW50cnVzdCBSb290IENlcnRpZmljYXRpb24gQXV0aG9yaXR5IC0gRUMxMB4XDTEy\nMTIxODE1MjUzNloXDTM3MTIxODE1NTUzNlowgb8xCzAJBgNVBAYTAlVTMRYwFAYD\nVQQKEw1FbnRydXN0LCBJbmMuMSgwJgYDVQQLEx9TZWUgd3d3LmVudHJ1c3QubmV0\nL2xlZ2FsLXRlcm1zMTkwNwYDVQQLEzAoYykgMjAxMiBFbnRydXN0LCBJbmMuIC0g\nZm9yIGF1dGhvcml6ZWQgdXNlIG9ubHkxMzAxBgNVBAMTKkVudHJ1c3QgUm9vdCBD\nZXJ0aWZpY2F0aW9uIEF1dGhvcml0eSAtIEVDMTB2MBAGByqGSM49AgEGBSuBBAAi\nA2IABIQTydC6bUF74mzQ61VfZgIaJPRbiWlH47jCffHyAsWfoPZb1YsGGYZPUxBt\nByQnoaD41UcZYUx9ypMn6nQM72+WCf5j7HBdNq1nd67JnXxVRDqiY1Ef9eNi1KlH\nBz7MIKNCMEAwDgYDVR0PAQH/BAQDAgEGMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0O\nBBYEFLdj5xrdjekIplWDpOBqUEFlEUJJMAoGCCqGSM49BAMDA2cAMGQCMGF52OVC\nR98crlOZF7ZvHH3hvxGU0QOIdeSNiaSKd0bebWHvAvX7td/M/k7//qnmpwIwW5nX\nhTcGtXsI/esni0qU+eH6p44mCOh8kmhtc9hvJqwhAriZtyZBWyVgrtBIGu4G\n-----END CERTIFICATE-----\n\n# Issuer: CN=CFCA EV ROOT O=China Financial Certification Authority\n# Subject: CN=CFCA EV ROOT O=China Financial Certification Authority\n# Label: \"CFCA EV ROOT\"\n# Serial: 407555286\n# MD5 Fingerprint: 74:e1:b6:ed:26:7a:7a:44:30:33:94:ab:7b:27:81:30\n# SHA1 Fingerprint: e2:b8:29:4b:55:84:ab:6b:58:c2:90:46:6c:ac:3f:b8:39:8f:84:83\n# SHA256 Fingerprint: 5c:c3:d7:8e:4e:1d:5e:45:54:7a:04:e6:87:3e:64:f9:0c:f9:53:6d:1c:cc:2e:f8:00:f3:55:c4:c5:fd:70:fd\n-----BEGIN CERTIFICATE-----\nMIIFjTCCA3WgAwIBAgIEGErM1jANBgkqhkiG9w0BAQsFADBWMQswCQYDVQQGEwJD\nTjEwMC4GA1UECgwnQ2hpbmEgRmluYW5jaWFsIENlcnRpZmljYXRpb24gQXV0aG9y\naXR5MRUwEwYDVQQDDAxDRkNBIEVWIFJPT1QwHhcNMTIwODA4MDMwNzAxWhcNMjkx\nMjMxMDMwNzAxWjBWMQswCQYDVQQGEwJDTjEwMC4GA1UECgwnQ2hpbmEgRmluYW5j\naWFsIENlcnRpZmljYXRpb24gQXV0aG9yaXR5MRUwEwYDVQQDDAxDRkNBIEVWIFJP\nT1QwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQDXXWvNED8fBVnVBU03\nsQ7smCuOFR36k0sXgiFxEFLXUWRwFsJVaU2OFW2fvwwbwuCjZ9YMrM8irq93VCpL\nTIpTUnrD7i7es3ElweldPe6hL6P3KjzJIx1qqx2hp/Hz7KDVRM8Vz3IvHWOX6Jn5\n/ZOkVIBMUtRSqy5J35DNuF++P96hyk0g1CXohClTt7GIH//62pCfCqktQT+x8Rgp\n7hZZLDRJGqgG16iI0gNyejLi6mhNbiyWZXvKWfry4t3uMCz7zEasxGPrb382KzRz\nEpR/38wmnvFyXVBlWY9ps4deMm/DGIq1lY+wejfeWkU7xzbh72fROdOXW3NiGUgt\nhxwG+3SYIElz8AXSG7Ggo7cbcNOIabla1jj0Ytwli3i/+Oh+uFzJlU9fpy25IGvP\na931DfSCt/SyZi4QKPaXWnuWFo8BGS1sbn85WAZkgwGDg8NNkt0yxoekN+kWzqot\naK8KgWU6cMGbrU1tVMoqLUuFG7OA5nBFDWteNfB/O7ic5ARwiRIlk9oKmSJgamNg\nTnYGmE69g60dWIolhdLHZR4tjsbftsbhf4oEIRUpdPA+nJCdDC7xij5aqgwJHsfV\nPKPtl8MeNPo4+QgO48BdK4PRVmrJtqhUUy54Mmc9gn900PvhtgVguXDbjgv5E1hv\ncWAQUhC5wUEJ73IfZzF4/5YFjQIDAQABo2MwYTAfBgNVHSMEGDAWgBTj/i39KNAL\ntbq2osS/BqoFjJP7LzAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIBBjAd\nBgNVHQ4EFgQU4/4t/SjQC7W6tqLEvwaqBYyT+y8wDQYJKoZIhvcNAQELBQADggIB\nACXGumvrh8vegjmWPfBEp2uEcwPenStPuiB/vHiyz5ewG5zz13ku9Ui20vsXiObT\nej/tUxPQ4i9qecsAIyjmHjdXNYmEwnZPNDatZ8POQQaIxffu2Bq41gt/UP+TqhdL\njOztUmCypAbqTuv0axn96/Ua4CUqmtzHQTb3yHQFhDmVOdYLO6Qn+gjYXB74BGBS\nESgoA//vU2YApUo0FmZ8/Qmkrp5nGm9BC2sGE5uPhnEFtC+NiWYzKXZUmhH4J/qy\nP5Hgzg0b8zAarb8iXRvTvyUFTeGSGn+ZnzxEk8rUQElsgIfXBDrDMlI1Dlb4pd19\nxIsNER9Tyx6yF7Zod1rg1MvIB671Oi6ON7fQAUtDKXeMOZePglr4UeWJoBjnaH9d\nCi77o0cOPaYjesYBx4/IXr9tgFa+iiS6M+qf4TIRnvHST4D2G0CvOJ4RUHlzEhLN\n5mydLIhyPDCBBpEi6lmt2hkuIsKNuYyH4Ga8cyNfIWRjgEj1oDwYPZTISEEdQLpe\n/v5WOaHIz16eGWRGENoXkbcFgKyLmZJ956LYBws2J+dIeWCKw9cTXPhyQN9Ky8+Z\nAAoACxGV2lZFA4gKn2fQ1XmxqI1AbQ3CekD6819kR5LLU7m7Wc5P/dAVUwHY3+vZ\n5nbv0CO7O6l5s9UCKc2Jo5YPSjXnTkLAdc0Hz+Ys63su\n-----END CERTIFICATE-----\n\n# Issuer: CN=Certinomis - Root CA O=Certinomis OU=0002 433998903\n# Subject: CN=Certinomis - Root CA O=Certinomis OU=0002 433998903\n# Label: \"Certinomis - Root CA\"\n# Serial: 1\n# MD5 Fingerprint: 14:0a:fd:8d:a8:28:b5:38:69:db:56:7e:61:22:03:3f\n# SHA1 Fingerprint: 9d:70:bb:01:a5:a4:a0:18:11:2e:f7:1c:01:b9:32:c5:34:e7:88:a8\n# SHA256 Fingerprint: 2a:99:f5:bc:11:74:b7:3c:bb:1d:62:08:84:e0:1c:34:e5:1c:cb:39:78:da:12:5f:0e:33:26:88:83:bf:41:58\n-----BEGIN CERTIFICATE-----\nMIIFkjCCA3qgAwIBAgIBATANBgkqhkiG9w0BAQsFADBaMQswCQYDVQQGEwJGUjET\nMBEGA1UEChMKQ2VydGlub21pczEXMBUGA1UECxMOMDAwMiA0MzM5OTg5MDMxHTAb\nBgNVBAMTFENlcnRpbm9taXMgLSBSb290IENBMB4XDTEzMTAyMTA5MTcxOFoXDTMz\nMTAyMTA5MTcxOFowWjELMAkGA1UEBhMCRlIxEzARBgNVBAoTCkNlcnRpbm9taXMx\nFzAVBgNVBAsTDjAwMDIgNDMzOTk4OTAzMR0wGwYDVQQDExRDZXJ0aW5vbWlzIC0g\nUm9vdCBDQTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBANTMCQosP5L2\nfxSeC5yaah1AMGT9qt8OHgZbn1CF6s2Nq0Nn3rD6foCWnoR4kkjW4znuzuRZWJfl\nLieY6pOod5tK8O90gC3rMB+12ceAnGInkYjwSond3IjmFPnVAy//ldu9n+ws+hQV\nWZUKxkd8aRi5pwP5ynapz8dvtF4F/u7BUrJ1Mofs7SlmO/NKFoL21prbcpjp3vDF\nTKWrteoB4owuZH9kb/2jJZOLyKIOSY008B/sWEUuNKqEUL3nskoTuLAPrjhdsKkb\n5nPJWqHZZkCqqU2mNAKthH6yI8H7KsZn9DS2sJVqM09xRLWtwHkziOC/7aOgFLSc\nCbAK42C++PhmiM1b8XcF4LVzbsF9Ri6OSyemzTUK/eVNfaoqoynHWmgE6OXWk6Ri\nwsXm9E/G+Z8ajYJJGYrKWUM66A0ywfRMEwNvbqY/kXPLynNvEiCL7sCCeN5LLsJJ\nwx3tFvYk9CcbXFcx3FXuqB5vbKziRcxXV4p1VxngtViZSTYxPDMBbRZKzbgqg4SG\nm/lg0h9tkQPTYKbVPZrdd5A9NaSfD171UkRpucC63M9933zZxKyGIjK8e2uR73r4\nF2iw4lNVYC2vPsKD2NkJK/DAZNuHi5HMkesE/Xa0lZrmFAYb1TQdvtj/dBxThZng\nWVJKYe2InmtJiUZ+IFrZ50rlau7SZRFDAgMBAAGjYzBhMA4GA1UdDwEB/wQEAwIB\nBjAPBgNVHRMBAf8EBTADAQH/MB0GA1UdDgQWBBTvkUz1pcMw6C8I6tNxIqSSaHh0\n2TAfBgNVHSMEGDAWgBTvkUz1pcMw6C8I6tNxIqSSaHh02TANBgkqhkiG9w0BAQsF\nAAOCAgEAfj1U2iJdGlg+O1QnurrMyOMaauo++RLrVl89UM7g6kgmJs95Vn6RHJk/\n0KGRHCwPT5iVWVO90CLYiF2cN/z7ZMF4jIuaYAnq1fohX9B0ZedQxb8uuQsLrbWw\nF6YSjNRieOpWauwK0kDDPAUwPk2Ut59KA9N9J0u2/kTO+hkzGm2kQtHdzMjI1xZS\ng081lLMSVX3l4kLr5JyTCcBMWwerx20RoFAXlCOotQqSD7J6wWAsOMwaplv/8gzj\nqh8c3LigkyfeY+N/IZ865Z764BNqdeuWXGKRlI5nU7aJ+BIJy29SWwNyhlCVCNSN\nh4YVH5Uk2KRvms6knZtt0rJ2BobGVgjF6wnaNsIbW0G+YSrjcOa4pvi2WsS9Iff/\nql+hbHY5ZtbqTFXhADObE5hjyW/QASAJN1LnDE8+zbz1X5YnpyACleAu6AdBBR8V\nbtaw5BngDwKTACdyxYvRVB9dSsNAl35VpnzBMwQUAR1JIGkLGZOdblgi90AMRgwj\nY/M50n92Uaf0yKHxDHYiI0ZSKS3io0EHVmmY0gUJvGnHWmHNj4FgFU2A3ZDifcRQ\n8ow7bkrHxuaAKzyBvBGAFhAn1/DNP3nMcyrDflOR1m749fPH0FFNjkulW+YZFzvW\ngQncItzujrnEj1PhZ7szuIgVRs/taTX/dQ1G885x4cVrhkIGuUE=\n-----END CERTIFICATE-----\n\n# Issuer: CN=OISTE WISeKey Global Root GB CA O=WISeKey OU=OISTE Foundation Endorsed\n# Subject: CN=OISTE WISeKey Global Root GB CA O=WISeKey OU=OISTE Foundation Endorsed\n# Label: \"OISTE WISeKey Global Root GB CA\"\n# Serial: 157768595616588414422159278966750757568\n# MD5 Fingerprint: a4:eb:b9:61:28:2e:b7:2f:98:b0:35:26:90:99:51:1d\n# SHA1 Fingerprint: 0f:f9:40:76:18:d3:d7:6a:4b:98:f0:a8:35:9e:0c:fd:27:ac:cc:ed\n# SHA256 Fingerprint: 6b:9c:08:e8:6e:b0:f7:67:cf:ad:65:cd:98:b6:21:49:e5:49:4a:67:f5:84:5e:7b:d1:ed:01:9f:27:b8:6b:d6\n-----BEGIN CERTIFICATE-----\nMIIDtTCCAp2gAwIBAgIQdrEgUnTwhYdGs/gjGvbCwDANBgkqhkiG9w0BAQsFADBt\nMQswCQYDVQQGEwJDSDEQMA4GA1UEChMHV0lTZUtleTEiMCAGA1UECxMZT0lTVEUg\nRm91bmRhdGlvbiBFbmRvcnNlZDEoMCYGA1UEAxMfT0lTVEUgV0lTZUtleSBHbG9i\nYWwgUm9vdCBHQiBDQTAeFw0xNDEyMDExNTAwMzJaFw0zOTEyMDExNTEwMzFaMG0x\nCzAJBgNVBAYTAkNIMRAwDgYDVQQKEwdXSVNlS2V5MSIwIAYDVQQLExlPSVNURSBG\nb3VuZGF0aW9uIEVuZG9yc2VkMSgwJgYDVQQDEx9PSVNURSBXSVNlS2V5IEdsb2Jh\nbCBSb290IEdCIENBMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA2Be3\nHEokKtaXscriHvt9OO+Y9bI5mE4nuBFde9IllIiCFSZqGzG7qFshISvYD06fWvGx\nWuR51jIjK+FTzJlFXHtPrby/h0oLS5daqPZI7H17Dc0hBt+eFf1Biki3IPShehtX\n1F1Q/7pn2COZH8g/497/b1t3sWtuuMlk9+HKQUYOKXHQuSP8yYFfTvdv37+ErXNk\nu7dCjmn21HYdfp2nuFeKUWdy19SouJVUQHMD9ur06/4oQnc/nSMbsrY9gBQHTC5P\n99UKFg29ZkM3fiNDecNAhvVMKdqOmq0NpQSHiB6F4+lT1ZvIiwNjeOvgGUpuuy9r\nM2RYk61pv48b74JIxwIDAQABo1EwTzALBgNVHQ8EBAMCAYYwDwYDVR0TAQH/BAUw\nAwEB/zAdBgNVHQ4EFgQUNQ/INmNe4qPs+TtmFc5RUuORmj0wEAYJKwYBBAGCNxUB\nBAMCAQAwDQYJKoZIhvcNAQELBQADggEBAEBM+4eymYGQfp3FsLAmzYh7KzKNbrgh\ncViXfa43FK8+5/ea4n32cZiZBKpDdHij40lhPnOMTZTg+XHEthYOU3gf1qKHLwI5\ngSk8rxWYITD+KJAAjNHhy/peyP34EEY7onhCkRd0VQreUGdNZtGn//3ZwLWoo4rO\nZvUPQ82nK1d7Y0Zqqi5S2PTt4W2tKZB4SLrhI6qjiey1q5bAtEuiHZeeevJuQHHf\naPFlTc58Bd9TZaml8LGXBHAVRgOY1NK/VLSgWH1Sb9pWJmLU2NuJMW8c8CLC02Ic\nNc1MaRVUGpCY3useX8p3x8uOPUNpnJpY0CQ73xtAln41rYHHTnG6iBM=\n-----END CERTIFICATE-----\n\n# Issuer: CN=SZAFIR ROOT CA2 O=Krajowa Izba Rozliczeniowa S.A.\n# Subject: CN=SZAFIR ROOT CA2 O=Krajowa Izba Rozliczeniowa S.A.\n# Label: \"SZAFIR ROOT CA2\"\n# Serial: 357043034767186914217277344587386743377558296292\n# MD5 Fingerprint: 11:64:c1:89:b0:24:b1:8c:b1:07:7e:89:9e:51:9e:99\n# SHA1 Fingerprint: e2:52:fa:95:3f:ed:db:24:60:bd:6e:28:f3:9c:cc:cf:5e:b3:3f:de\n# SHA256 Fingerprint: a1:33:9d:33:28:1a:0b:56:e5:57:d3:d3:2b:1c:e7:f9:36:7e:b0:94:bd:5f:a7:2a:7e:50:04:c8:de:d7:ca:fe\n-----BEGIN CERTIFICATE-----\nMIIDcjCCAlqgAwIBAgIUPopdB+xV0jLVt+O2XwHrLdzk1uQwDQYJKoZIhvcNAQEL\nBQAwUTELMAkGA1UEBhMCUEwxKDAmBgNVBAoMH0tyYWpvd2EgSXpiYSBSb3psaWN6\nZW5pb3dhIFMuQS4xGDAWBgNVBAMMD1NaQUZJUiBST09UIENBMjAeFw0xNTEwMTkw\nNzQzMzBaFw0zNTEwMTkwNzQzMzBaMFExCzAJBgNVBAYTAlBMMSgwJgYDVQQKDB9L\ncmFqb3dhIEl6YmEgUm96bGljemVuaW93YSBTLkEuMRgwFgYDVQQDDA9TWkFGSVIg\nUk9PVCBDQTIwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQC3vD5QqEvN\nQLXOYeeWyrSh2gwisPq1e3YAd4wLz32ohswmUeQgPYUM1ljj5/QqGJ3a0a4m7utT\n3PSQ1hNKDJA8w/Ta0o4NkjrcsbH/ON7Dui1fgLkCvUqdGw+0w8LBZwPd3BucPbOw\n3gAeqDRHu5rr/gsUvTaE2g0gv/pby6kWIK05YO4vdbbnl5z5Pv1+TW9NL++IDWr6\n3fE9biCloBK0TXC5ztdyO4mTp4CEHCdJckm1/zuVnsHMyAHs6A6KCpbns6aH5db5\nBSsNl0BwPLqsdVqc1U2dAgrSS5tmS0YHF2Wtn2yIANwiieDhZNRnvDF5YTy7ykHN\nXGoAyDw4jlivAgMBAAGjQjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQD\nAgEGMB0GA1UdDgQWBBQuFqlKGLXLzPVvUPMjX/hd56zwyDANBgkqhkiG9w0BAQsF\nAAOCAQEAtXP4A9xZWx126aMqe5Aosk3AM0+qmrHUuOQn/6mWmc5G4G18TKI4pAZw\n8PRBEew/R40/cof5O/2kbytTAOD/OblqBw7rHRz2onKQy4I9EYKL0rufKq8h5mOG\nnXkZ7/e7DDWQw4rtTw/1zBLZpD67oPwglV9PJi8RI4NOdQcPv5vRtB3pEAT+ymCP\noky4rc/hkA/NrgrHXXu3UNLUYfrVFdvXn4dRVOul4+vJhaAlIDf7js4MNIThPIGy\nd05DpYhfhmehPea0XGG2Ptv+tyjFogeutcrKjSoS75ftwjCkySp6+/NNIxuZMzSg\nLvWpCz/UXeHPhJ/iGcJfitYgHuNztw==\n-----END CERTIFICATE-----\n\n# Issuer: CN=Certum Trusted Network CA 2 O=Unizeto Technologies S.A. OU=Certum Certification Authority\n# Subject: CN=Certum Trusted Network CA 2 O=Unizeto Technologies S.A. OU=Certum Certification Authority\n# Label: \"Certum Trusted Network CA 2\"\n# Serial: 44979900017204383099463764357512596969\n# MD5 Fingerprint: 6d:46:9e:d9:25:6d:08:23:5b:5e:74:7d:1e:27:db:f2\n# SHA1 Fingerprint: d3:dd:48:3e:2b:bf:4c:05:e8:af:10:f5:fa:76:26:cf:d3:dc:30:92\n# SHA256 Fingerprint: b6:76:f2:ed:da:e8:77:5c:d3:6c:b0:f6:3c:d1:d4:60:39:61:f4:9e:62:65:ba:01:3a:2f:03:07:b6:d0:b8:04\n-----BEGIN CERTIFICATE-----\nMIIF0jCCA7qgAwIBAgIQIdbQSk8lD8kyN/yqXhKN6TANBgkqhkiG9w0BAQ0FADCB\ngDELMAkGA1UEBhMCUEwxIjAgBgNVBAoTGVVuaXpldG8gVGVjaG5vbG9naWVzIFMu\nQS4xJzAlBgNVBAsTHkNlcnR1bSBDZXJ0aWZpY2F0aW9uIEF1dGhvcml0eTEkMCIG\nA1UEAxMbQ2VydHVtIFRydXN0ZWQgTmV0d29yayBDQSAyMCIYDzIwMTExMDA2MDgz\nOTU2WhgPMjA0NjEwMDYwODM5NTZaMIGAMQswCQYDVQQGEwJQTDEiMCAGA1UEChMZ\nVW5pemV0byBUZWNobm9sb2dpZXMgUy5BLjEnMCUGA1UECxMeQ2VydHVtIENlcnRp\nZmljYXRpb24gQXV0aG9yaXR5MSQwIgYDVQQDExtDZXJ0dW0gVHJ1c3RlZCBOZXR3\nb3JrIENBIDIwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQC9+Xj45tWA\nDGSdhhuWZGc/IjoedQF97/tcZ4zJzFxrqZHmuULlIEub2pt7uZld2ZuAS9eEQCsn\n0+i6MLs+CRqnSZXvK0AkwpfHp+6bJe+oCgCXhVqqndwpyeI1B+twTUrWwbNWuKFB\nOJvR+zF/j+Bf4bE/D44WSWDXBo0Y+aomEKsq09DRZ40bRr5HMNUuctHFY9rnY3lE\nfktjJImGLjQ/KUxSiyqnwOKRKIm5wFv5HdnnJ63/mgKXwcZQkpsCLL2puTRZCr+E\nSv/f/rOf69me4Jgj7KZrdxYq28ytOxykh9xGc14ZYmhFV+SQgkK7QtbwYeDBoz1m\no130GO6IyY0XRSmZMnUCMe4pJshrAua1YkV/NxVaI2iJ1D7eTiew8EAMvE0Xy02i\nsx7QBlrd9pPPV3WZ9fqGGmd4s7+W/jTcvedSVuWz5XV710GRBdxdaeOVDUO5/IOW\nOZV7bIBaTxNyxtd9KXpEulKkKtVBRgkg/iKgtlswjbyJDNXXcPiHUv3a76xRLgez\nTv7QCdpw75j6VuZt27VXS9zlLCUVyJ4ueE742pyehizKV/Ma5ciSixqClnrDvFAS\nadgOWkaLOusm+iPJtrCBvkIApPjW/jAux9JG9uWOdf3yzLnQh1vMBhBgu4M1t15n\n3kfsmUjxpKEV/q2MYo45VU85FrmxY53/twIDAQABo0IwQDAPBgNVHRMBAf8EBTAD\nAQH/MB0GA1UdDgQWBBS2oVQ5AsOgP46KvPrU+Bym0ToO/TAOBgNVHQ8BAf8EBAMC\nAQYwDQYJKoZIhvcNAQENBQADggIBAHGlDs7k6b8/ONWJWsQCYftMxRQXLYtPU2sQ\nF/xlhMcQSZDe28cmk4gmb3DWAl45oPePq5a1pRNcgRRtDoGCERuKTsZPpd1iHkTf\nCVn0W3cLN+mLIMb4Ck4uWBzrM9DPhmDJ2vuAL55MYIR4PSFk1vtBHxgP58l1cb29\nXN40hz5BsA72udY/CROWFC/emh1auVbONTqwX3BNXuMp8SMoclm2q8KMZiYcdywm\ndjWLKKdpoPk79SPdhRB0yZADVpHnr7pH1BKXESLjokmUbOe3lEu6LaTaM4tMpkT/\nWjzGHWTYtTHkpjx6qFcL2+1hGsvxznN3Y6SHb0xRONbkX8eftoEq5IVIeVheO/jb\nAoJnwTnbw3RLPTYe+SmTiGhbqEQZIfCn6IENLOiTNrQ3ssqwGyZ6miUfmpqAnksq\nP/ujmv5zMnHCnsZy4YpoJ/HkD7TETKVhk/iXEAcqMCWpuchxuO9ozC1+9eB+D4Ko\nb7a6bINDd82Kkhehnlt4Fj1F4jNy3eFmypnTycUm/Q1oBEauttmbjL4ZvrHG8hnj\nXALKLNhvSgfZyTXaQHXyxKcZb55CEJh15pWLYLztxRLXis7VmFxWlgPF7ncGNf/P\n5O4/E2Hu29othfDNrp2yGAlFw5Khchf8R7agCyzxxN5DaAhqXzvwdmP7zAYspsbi\nDrW5viSP\n-----END CERTIFICATE-----\n\n# Issuer: CN=Hellenic Academic and Research Institutions RootCA 2015 O=Hellenic Academic and Research Institutions Cert. Authority\n# Subject: CN=Hellenic Academic and Research Institutions RootCA 2015 O=Hellenic Academic and Research Institutions Cert. Authority\n# Label: \"Hellenic Academic and Research Institutions RootCA 2015\"\n# Serial: 0\n# MD5 Fingerprint: ca:ff:e2:db:03:d9:cb:4b:e9:0f:ad:84:fd:7b:18:ce\n# SHA1 Fingerprint: 01:0c:06:95:a6:98:19:14:ff:bf:5f:c6:b0:b6:95:ea:29:e9:12:a6\n# SHA256 Fingerprint: a0:40:92:9a:02:ce:53:b4:ac:f4:f2:ff:c6:98:1c:e4:49:6f:75:5e:6d:45:fe:0b:2a:69:2b:cd:52:52:3f:36\n-----BEGIN CERTIFICATE-----\nMIIGCzCCA/OgAwIBAgIBADANBgkqhkiG9w0BAQsFADCBpjELMAkGA1UEBhMCR1Ix\nDzANBgNVBAcTBkF0aGVuczFEMEIGA1UEChM7SGVsbGVuaWMgQWNhZGVtaWMgYW5k\nIFJlc2VhcmNoIEluc3RpdHV0aW9ucyBDZXJ0LiBBdXRob3JpdHkxQDA+BgNVBAMT\nN0hlbGxlbmljIEFjYWRlbWljIGFuZCBSZXNlYXJjaCBJbnN0aXR1dGlvbnMgUm9v\ndENBIDIwMTUwHhcNMTUwNzA3MTAxMTIxWhcNNDAwNjMwMTAxMTIxWjCBpjELMAkG\nA1UEBhMCR1IxDzANBgNVBAcTBkF0aGVuczFEMEIGA1UEChM7SGVsbGVuaWMgQWNh\nZGVtaWMgYW5kIFJlc2VhcmNoIEluc3RpdHV0aW9ucyBDZXJ0LiBBdXRob3JpdHkx\nQDA+BgNVBAMTN0hlbGxlbmljIEFjYWRlbWljIGFuZCBSZXNlYXJjaCBJbnN0aXR1\ndGlvbnMgUm9vdENBIDIwMTUwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoIC\nAQDC+Kk/G4n8PDwEXT2QNrCROnk8ZlrvbTkBSRq0t89/TSNTt5AA4xMqKKYx8ZEA\n4yjsriFBzh/a/X0SWwGDD7mwX5nh8hKDgE0GPt+sr+ehiGsxr/CL0BgzuNtFajT0\nAoAkKAoCFZVedioNmToUW/bLy1O8E00BiDeUJRtCvCLYjqOWXjrZMts+6PAQZe10\n4S+nfK8nNLspfZu2zwnI5dMK/IhlZXQK3HMcXM1AsRzUtoSMTFDPaI6oWa7CJ06C\nojXdFPQf/7J31Ycvqm59JCfnxssm5uX+Zwdj2EUN3TpZZTlYepKZcj2chF6IIbjV\n9Cz82XBST3i4vTwri5WY9bPRaM8gFH5MXF/ni+X1NYEZN9cRCLdmvtNKzoNXADrD\ngfgXy5I2XdGj2HUb4Ysn6npIQf1FGQatJ5lOwXBH3bWfgVMS5bGMSF0xQxfjjMZ6\nY5ZLKTBOhE5iGV48zpeQpX8B653g+IuJ3SWYPZK2fu/Z8VFRfS0myGlZYeCsargq\nNhEEelC9MoS+L9xy1dcdFkfkR2YgP/SWxa+OAXqlD3pk9Q0Yh9muiNX6hME6wGko\nLfINaFGq46V3xqSQDqE3izEjR8EJCOtu93ib14L8hCCZSRm2Ekax+0VVFqmjZayc\nBw/qa9wfLgZy7IaIEuQt218FL+TwA9MmM+eAws1CoRc0CwIDAQABo0IwQDAPBgNV\nHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIBBjAdBgNVHQ4EFgQUcRVnyMjJvXVd\nctA4GGqd83EkVAswDQYJKoZIhvcNAQELBQADggIBAHW7bVRLqhBYRjTyYtcWNl0I\nXtVsyIe9tC5G8jH4fOpCtZMWVdyhDBKg2mF+D1hYc2Ryx+hFjtyp8iY/xnmMsVMI\nM4GwVhO+5lFc2JsKT0ucVlMC6U/2DWDqTUJV6HwbISHTGzrMd/K4kPFox/la/vot\n9L/J9UUbzjgQKjeKeaO04wlshYaT/4mWJ3iBj2fjRnRUjtkNaeJK9E10A/+yd+2V\nZ5fkscWrv2oj6NSU4kQoYsRL4vDY4ilrGnB+JGGTe08DMiUNRSQrlrRGar9KC/ea\nj8GsGsVn82800vpzY4zvFrCopEYq+OsS7HK07/grfoxSwIuEVPkvPuNVqNxmsdnh\nX9izjFk0WaSrT2y7HxjbdavYy5LNlDhhDgcGH0tGEPEVvo2FXDtKK4F5D7Rpn0lQ\nl033DlZdwJVqwjbDG2jJ9SrcR5q+ss7FJej6A7na+RZukYT1HCjI/CbM1xyQVqdf\nbzoEvM14iQuODy+jqk+iGxI9FghAD/FGTNeqewjBCvVtJ94Cj8rDtSvK6evIIVM4\npcw72Hc3MKJP2W/R8kCtQXoXxdZKNYm3QdV8hn9VTYNKpXMgwDqvkPGaJI7ZjnHK\ne7iG2rKPmT4dEw0SEe7Uq/DpFXYC5ODfqiAeW2GFZECpkJcNrVPSWh2HagCXZWK0\nvm9qp/UsQu0yrbYhnr68\n-----END CERTIFICATE-----\n\n# Issuer: CN=Hellenic Academic and Research Institutions ECC RootCA 2015 O=Hellenic Academic and Research Institutions Cert. Authority\n# Subject: CN=Hellenic Academic and Research Institutions ECC RootCA 2015 O=Hellenic Academic and Research Institutions Cert. Authority\n# Label: \"Hellenic Academic and Research Institutions ECC RootCA 2015\"\n# Serial: 0\n# MD5 Fingerprint: 81:e5:b4:17:eb:c2:f5:e1:4b:0d:41:7b:49:92:fe:ef\n# SHA1 Fingerprint: 9f:f1:71:8d:92:d5:9a:f3:7d:74:97:b4:bc:6f:84:68:0b:ba:b6:66\n# SHA256 Fingerprint: 44:b5:45:aa:8a:25:e6:5a:73:ca:15:dc:27:fc:36:d2:4c:1c:b9:95:3a:06:65:39:b1:15:82:dc:48:7b:48:33\n-----BEGIN CERTIFICATE-----\nMIICwzCCAkqgAwIBAgIBADAKBggqhkjOPQQDAjCBqjELMAkGA1UEBhMCR1IxDzAN\nBgNVBAcTBkF0aGVuczFEMEIGA1UEChM7SGVsbGVuaWMgQWNhZGVtaWMgYW5kIFJl\nc2VhcmNoIEluc3RpdHV0aW9ucyBDZXJ0LiBBdXRob3JpdHkxRDBCBgNVBAMTO0hl\nbGxlbmljIEFjYWRlbWljIGFuZCBSZXNlYXJjaCBJbnN0aXR1dGlvbnMgRUNDIFJv\nb3RDQSAyMDE1MB4XDTE1MDcwNzEwMzcxMloXDTQwMDYzMDEwMzcxMlowgaoxCzAJ\nBgNVBAYTAkdSMQ8wDQYDVQQHEwZBdGhlbnMxRDBCBgNVBAoTO0hlbGxlbmljIEFj\nYWRlbWljIGFuZCBSZXNlYXJjaCBJbnN0aXR1dGlvbnMgQ2VydC4gQXV0aG9yaXR5\nMUQwQgYDVQQDEztIZWxsZW5pYyBBY2FkZW1pYyBhbmQgUmVzZWFyY2ggSW5zdGl0\ndXRpb25zIEVDQyBSb290Q0EgMjAxNTB2MBAGByqGSM49AgEGBSuBBAAiA2IABJKg\nQehLgoRc4vgxEZmGZE4JJS+dQS8KrjVPdJWyUWRrjWvmP3CV8AVER6ZyOFB2lQJa\njq4onvktTpnvLEhvTCUp6NFxW98dwXU3tNf6e3pCnGoKVlp8aQuqgAkkbH7BRqNC\nMEAwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYEFLQi\nC4KZJAEOnLvkDv2/+5cgk5kqMAoGCCqGSM49BAMCA2cAMGQCMGfOFmI4oqxiRaep\nlSTAGiecMjvAwNW6qef4BENThe5SId6d9SWDPp5YSy/XZxMOIQIwBeF1Ad5o7Sof\nTUwJCA3sS61kFyjndc5FZXIhF8siQQ6ME5g4mlRtm8rifOoCWCKR\n-----END CERTIFICATE-----\n\n# Issuer: CN=ISRG Root X1 O=Internet Security Research Group\n# Subject: CN=ISRG Root X1 O=Internet Security Research Group\n# Label: \"ISRG Root X1\"\n# Serial: 172886928669790476064670243504169061120\n# MD5 Fingerprint: 0c:d2:f9:e0:da:17:73:e9:ed:86:4d:a5:e3:70:e7:4e\n# SHA1 Fingerprint: ca:bd:2a:79:a1:07:6a:31:f2:1d:25:36:35:cb:03:9d:43:29:a5:e8\n# SHA256 Fingerprint: 96:bc:ec:06:26:49:76:f3:74:60:77:9a:cf:28:c5:a7:cf:e8:a3:c0:aa:e1:1a:8f:fc:ee:05:c0:bd:df:08:c6\n-----BEGIN CERTIFICATE-----\nMIIFazCCA1OgAwIBAgIRAIIQz7DSQONZRGPgu2OCiwAwDQYJKoZIhvcNAQELBQAw\nTzELMAkGA1UEBhMCVVMxKTAnBgNVBAoTIEludGVybmV0IFNlY3VyaXR5IFJlc2Vh\ncmNoIEdyb3VwMRUwEwYDVQQDEwxJU1JHIFJvb3QgWDEwHhcNMTUwNjA0MTEwNDM4\nWhcNMzUwNjA0MTEwNDM4WjBPMQswCQYDVQQGEwJVUzEpMCcGA1UEChMgSW50ZXJu\nZXQgU2VjdXJpdHkgUmVzZWFyY2ggR3JvdXAxFTATBgNVBAMTDElTUkcgUm9vdCBY\nMTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBAK3oJHP0FDfzm54rVygc\nh77ct984kIxuPOZXoHj3dcKi/vVqbvYATyjb3miGbESTtrFj/RQSa78f0uoxmyF+\n0TM8ukj13Xnfs7j/EvEhmkvBioZxaUpmZmyPfjxwv60pIgbz5MDmgK7iS4+3mX6U\nA5/TR5d8mUgjU+g4rk8Kb4Mu0UlXjIB0ttov0DiNewNwIRt18jA8+o+u3dpjq+sW\nT8KOEUt+zwvo/7V3LvSye0rgTBIlDHCNAymg4VMk7BPZ7hm/ELNKjD+Jo2FR3qyH\nB5T0Y3HsLuJvW5iB4YlcNHlsdu87kGJ55tukmi8mxdAQ4Q7e2RCOFvu396j3x+UC\nB5iPNgiV5+I3lg02dZ77DnKxHZu8A/lJBdiB3QW0KtZB6awBdpUKD9jf1b0SHzUv\nKBds0pjBqAlkd25HN7rOrFleaJ1/ctaJxQZBKT5ZPt0m9STJEadao0xAH0ahmbWn\nOlFuhjuefXKnEgV4We0+UXgVCwOPjdAvBbI+e0ocS3MFEvzG6uBQE3xDk3SzynTn\njh8BCNAw1FtxNrQHusEwMFxIt4I7mKZ9YIqioymCzLq9gwQbooMDQaHWBfEbwrbw\nqHyGO0aoSCqI3Haadr8faqU9GY/rOPNk3sgrDQoo//fb4hVC1CLQJ13hef4Y53CI\nrU7m2Ys6xt0nUW7/vGT1M0NPAgMBAAGjQjBAMA4GA1UdDwEB/wQEAwIBBjAPBgNV\nHRMBAf8EBTADAQH/MB0GA1UdDgQWBBR5tFnme7bl5AFzgAiIyBpY9umbbjANBgkq\nhkiG9w0BAQsFAAOCAgEAVR9YqbyyqFDQDLHYGmkgJykIrGF1XIpu+ILlaS/V9lZL\nubhzEFnTIZd+50xx+7LSYK05qAvqFyFWhfFQDlnrzuBZ6brJFe+GnY+EgPbk6ZGQ\n3BebYhtF8GaV0nxvwuo77x/Py9auJ/GpsMiu/X1+mvoiBOv/2X/qkSsisRcOj/KK\nNFtY2PwByVS5uCbMiogziUwthDyC3+6WVwW6LLv3xLfHTjuCvjHIInNzktHCgKQ5\nORAzI4JMPJ+GslWYHb4phowim57iaztXOoJwTdwJx4nLCgdNbOhdjsnvzqvHu7Ur\nTkXWStAmzOVyyghqpZXjFaH3pO3JLF+l+/+sKAIuvtd7u+Nxe5AW0wdeRlN8NwdC\njNPElpzVmbUq4JUagEiuTDkHzsxHpFKVK7q4+63SM1N95R1NbdWhscdCb+ZAJzVc\noyi3B43njTOQ5yOf+1CceWxG1bQVs5ZufpsMljq4Ui0/1lvh+wjChP4kqKOJ2qxq\n4RgqsahDYVvTH9w7jXbyLeiNdd8XM2w9U/t7y0Ff/9yi0GE44Za4rF2LN9d11TPA\nmRGunUHBcnWEvgJBQl9nJEiU0Zsnvgc/ubhPgXRR4Xq37Z0j4r7g1SgEEzwxA57d\nemyPxgcYxn/eR44/KJ4EBs+lVDR3veyJm+kXQ99b21/+jh5Xos1AnX5iItreGCc=\n-----END CERTIFICATE-----\n\n# Issuer: O=FNMT-RCM OU=AC RAIZ FNMT-RCM\n# Subject: O=FNMT-RCM OU=AC RAIZ FNMT-RCM\n# Label: \"AC RAIZ FNMT-RCM\"\n# Serial: 485876308206448804701554682760554759\n# MD5 Fingerprint: e2:09:04:b4:d3:bd:d1:a0:14:fd:1a:d2:47:c4:57:1d\n# SHA1 Fingerprint: ec:50:35:07:b2:15:c4:95:62:19:e2:a8:9a:5b:42:99:2c:4c:2c:20\n# SHA256 Fingerprint: eb:c5:57:0c:29:01:8c:4d:67:b1:aa:12:7b:af:12:f7:03:b4:61:1e:bc:17:b7:da:b5:57:38:94:17:9b:93:fa\n-----BEGIN CERTIFICATE-----\nMIIFgzCCA2ugAwIBAgIPXZONMGc2yAYdGsdUhGkHMA0GCSqGSIb3DQEBCwUAMDsx\nCzAJBgNVBAYTAkVTMREwDwYDVQQKDAhGTk1ULVJDTTEZMBcGA1UECwwQQUMgUkFJ\nWiBGTk1ULVJDTTAeFw0wODEwMjkxNTU5NTZaFw0zMDAxMDEwMDAwMDBaMDsxCzAJ\nBgNVBAYTAkVTMREwDwYDVQQKDAhGTk1ULVJDTTEZMBcGA1UECwwQQUMgUkFJWiBG\nTk1ULVJDTTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBALpxgHpMhm5/\nyBNtwMZ9HACXjywMI7sQmkCpGreHiPibVmr75nuOi5KOpyVdWRHbNi63URcfqQgf\nBBckWKo3Shjf5TnUV/3XwSyRAZHiItQDwFj8d0fsjz50Q7qsNI1NOHZnjrDIbzAz\nWHFctPVrbtQBULgTfmxKo0nRIBnuvMApGGWn3v7v3QqQIecaZ5JCEJhfTzC8PhxF\ntBDXaEAUwED653cXeuYLj2VbPNmaUtu1vZ5Gzz3rkQUCwJaydkxNEJY7kvqcfw+Z\n374jNUUeAlz+taibmSXaXvMiwzn15Cou08YfxGyqxRxqAQVKL9LFwag0Jl1mpdIC\nIfkYtwb1TplvqKtMUejPUBjFd8g5CSxJkjKZqLsXF3mwWsXmo8RZZUc1g16p6DUL\nmbvkzSDGm0oGObVo/CK67lWMK07q87Hj/LaZmtVC+nFNCM+HHmpxffnTtOmlcYF7\nwk5HlqX2doWjKI/pgG6BU6VtX7hI+cL5NqYuSf+4lsKMB7ObiFj86xsc3i1w4peS\nMKGJ47xVqCfWS+2QrYv6YyVZLag13cqXM7zlzced0ezvXg5KkAYmY6252TUtB7p2\nZSysV4999AeU14ECll2jB0nVetBX+RvnU0Z1qrB5QstocQjpYL05ac70r8NWQMet\nUqIJ5G+GR4of6ygnXYMgrwTJbFaai0b1AgMBAAGjgYMwgYAwDwYDVR0TAQH/BAUw\nAwEB/zAOBgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYEFPd9xf3E6Jobd2Sn9R2gzL+H\nYJptMD4GA1UdIAQ3MDUwMwYEVR0gADArMCkGCCsGAQUFBwIBFh1odHRwOi8vd3d3\nLmNlcnQuZm5tdC5lcy9kcGNzLzANBgkqhkiG9w0BAQsFAAOCAgEAB5BK3/MjTvDD\nnFFlm5wioooMhfNzKWtN/gHiqQxjAb8EZ6WdmF/9ARP67Jpi6Yb+tmLSbkyU+8B1\nRXxlDPiyN8+sD8+Nb/kZ94/sHvJwnvDKuO+3/3Y3dlv2bojzr2IyIpMNOmqOFGYM\nLVN0V2Ue1bLdI4E7pWYjJ2cJj+F3qkPNZVEI7VFY/uY5+ctHhKQV8Xa7pO6kO8Rf\n77IzlhEYt8llvhjho6Tc+hj507wTmzl6NLrTQfv6MooqtyuGC2mDOL7Nii4LcK2N\nJpLuHvUBKwrZ1pebbuCoGRw6IYsMHkCtA+fdZn71uSANA+iW+YJF1DngoABd15jm\nfZ5nc8OaKveri6E6FO80vFIOiZiaBECEHX5FaZNXzuvO+FB8TxxuBEOb+dY7Ixjp\n6o7RTUaN8Tvkasq6+yO3m/qZASlaWFot4/nUbQ4mrcFuNLwy+AwF+mWj2zs3gyLp\n1txyM/1d8iC9djwj2ij3+RvrWWTV3F9yfiD8zYm1kGdNYno/Tq0dwzn+evQoFt9B\n9kiABdcPUXmsEKvU7ANm5mqwujGSQkBqvjrTcuFqN1W8rB2Vt2lh8kORdOag0wok\nRqEIr9baRRmW1FMdW4R58MD3R++Lj8UGrp1MYp3/RgT408m2ECVAdf4WqslKYIYv\nuu8wd+RU4riEmViAqhOLUTpPSPaLtrM=\n-----END CERTIFICATE-----\n\n# Issuer: CN=Amazon Root CA 1 O=Amazon\n# Subject: CN=Amazon Root CA 1 O=Amazon\n# Label: \"Amazon Root CA 1\"\n# Serial: 143266978916655856878034712317230054538369994\n# MD5 Fingerprint: 43:c6:bf:ae:ec:fe:ad:2f:18:c6:88:68:30:fc:c8:e6\n# SHA1 Fingerprint: 8d:a7:f9:65:ec:5e:fc:37:91:0f:1c:6e:59:fd:c1:cc:6a:6e:de:16\n# SHA256 Fingerprint: 8e:cd:e6:88:4f:3d:87:b1:12:5b:a3:1a:c3:fc:b1:3d:70:16:de:7f:57:cc:90:4f:e1:cb:97:c6:ae:98:19:6e\n-----BEGIN CERTIFICATE-----\nMIIDQTCCAimgAwIBAgITBmyfz5m/jAo54vB4ikPmljZbyjANBgkqhkiG9w0BAQsF\nADA5MQswCQYDVQQGEwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6\nb24gUm9vdCBDQSAxMB4XDTE1MDUyNjAwMDAwMFoXDTM4MDExNzAwMDAwMFowOTEL\nMAkGA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpvbjEZMBcGA1UEAxMQQW1hem9uIFJv\nb3QgQ0EgMTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALJ4gHHKeNXj\nca9HgFB0fW7Y14h29Jlo91ghYPl0hAEvrAIthtOgQ3pOsqTQNroBvo3bSMgHFzZM\n9O6II8c+6zf1tRn4SWiw3te5djgdYZ6k/oI2peVKVuRF4fn9tBb6dNqcmzU5L/qw\nIFAGbHrQgLKm+a/sRxmPUDgH3KKHOVj4utWp+UhnMJbulHheb4mjUcAwhmahRWa6\nVOujw5H5SNz/0egwLX0tdHA114gk957EWW67c4cX8jJGKLhD+rcdqsq08p8kDi1L\n93FcXmn/6pUCyziKrlA4b9v7LWIbxcceVOF34GfID5yHI9Y/QCB/IIDEgEw+OyQm\njgSubJrIqg0CAwEAAaNCMEAwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMC\nAYYwHQYDVR0OBBYEFIQYzIU07LwMlJQuCFmcx7IQTgoIMA0GCSqGSIb3DQEBCwUA\nA4IBAQCY8jdaQZChGsV2USggNiMOruYou6r4lK5IpDB/G/wkjUu0yKGX9rbxenDI\nU5PMCCjjmCXPI6T53iHTfIUJrU6adTrCC2qJeHZERxhlbI1Bjjt/msv0tadQ1wUs\nN+gDS63pYaACbvXy8MWy7Vu33PqUXHeeE6V/Uq2V8viTO96LXFvKWlJbYK8U90vv\no/ufQJVtMVT8QtPHRh8jrdkPSHCa2XV4cdFyQzR1bldZwgJcJmApzyMZFo6IQ6XU\n5MsI+yMRQ+hDKXJioaldXgjUkK642M4UwtBV8ob2xJNDd2ZhwLnoQdeXeGADbkpy\nrqXRfboQnoZsG4q5WTP468SQvvG5\n-----END CERTIFICATE-----\n\n# Issuer: CN=Amazon Root CA 2 O=Amazon\n# Subject: CN=Amazon Root CA 2 O=Amazon\n# Label: \"Amazon Root CA 2\"\n# Serial: 143266982885963551818349160658925006970653239\n# MD5 Fingerprint: c8:e5:8d:ce:a8:42:e2:7a:c0:2a:5c:7c:9e:26:bf:66\n# SHA1 Fingerprint: 5a:8c:ef:45:d7:a6:98:59:76:7a:8c:8b:44:96:b5:78:cf:47:4b:1a\n# SHA256 Fingerprint: 1b:a5:b2:aa:8c:65:40:1a:82:96:01:18:f8:0b:ec:4f:62:30:4d:83:ce:c4:71:3a:19:c3:9c:01:1e:a4:6d:b4\n-----BEGIN CERTIFICATE-----\nMIIFQTCCAymgAwIBAgITBmyf0pY1hp8KD+WGePhbJruKNzANBgkqhkiG9w0BAQwF\nADA5MQswCQYDVQQGEwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6\nb24gUm9vdCBDQSAyMB4XDTE1MDUyNjAwMDAwMFoXDTQwMDUyNjAwMDAwMFowOTEL\nMAkGA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpvbjEZMBcGA1UEAxMQQW1hem9uIFJv\nb3QgQ0EgMjCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBAK2Wny2cSkxK\ngXlRmeyKy2tgURO8TW0G/LAIjd0ZEGrHJgw12MBvIITplLGbhQPDW9tK6Mj4kHbZ\nW0/jTOgGNk3Mmqw9DJArktQGGWCsN0R5hYGCrVo34A3MnaZMUnbqQ523BNFQ9lXg\n1dKmSYXpN+nKfq5clU1Imj+uIFptiJXZNLhSGkOQsL9sBbm2eLfq0OQ6PBJTYv9K\n8nu+NQWpEjTj82R0Yiw9AElaKP4yRLuH3WUnAnE72kr3H9rN9yFVkE8P7K6C4Z9r\n2UXTu/Bfh+08LDmG2j/e7HJV63mjrdvdfLC6HM783k81ds8P+HgfajZRRidhW+me\nz/CiVX18JYpvL7TFz4QuK/0NURBs+18bvBt+xa47mAExkv8LV/SasrlX6avvDXbR\n8O70zoan4G7ptGmh32n2M8ZpLpcTnqWHsFcQgTfJU7O7f/aS0ZzQGPSSbtqDT6Zj\nmUyl+17vIWR6IF9sZIUVyzfpYgwLKhbcAS4y2j5L9Z469hdAlO+ekQiG+r5jqFoz\n7Mt0Q5X5bGlSNscpb/xVA1wf+5+9R+vnSUeVC06JIglJ4PVhHvG/LopyboBZ/1c6\n+XUyo05f7O0oYtlNc/LMgRdg7c3r3NunysV+Ar3yVAhU/bQtCSwXVEqY0VThUWcI\n0u1ufm8/0i2BWSlmy5A5lREedCf+3euvAgMBAAGjQjBAMA8GA1UdEwEB/wQFMAMB\nAf8wDgYDVR0PAQH/BAQDAgGGMB0GA1UdDgQWBBSwDPBMMPQFWAJI/TPlUq9LhONm\nUjANBgkqhkiG9w0BAQwFAAOCAgEAqqiAjw54o+Ci1M3m9Zh6O+oAA7CXDpO8Wqj2\nLIxyh6mx/H9z/WNxeKWHWc8w4Q0QshNabYL1auaAn6AFC2jkR2vHat+2/XcycuUY\n+gn0oJMsXdKMdYV2ZZAMA3m3MSNjrXiDCYZohMr/+c8mmpJ5581LxedhpxfL86kS\nk5Nrp+gvU5LEYFiwzAJRGFuFjWJZY7attN6a+yb3ACfAXVU3dJnJUH/jWS5E4ywl\n7uxMMne0nxrpS10gxdr9HIcWxkPo1LsmmkVwXqkLN1PiRnsn/eBG8om3zEK2yygm\nbtmlyTrIQRNg91CMFa6ybRoVGld45pIq2WWQgj9sAq+uEjonljYE1x2igGOpm/Hl\nurR8FLBOybEfdF849lHqm/osohHUqS0nGkWxr7JOcQ3AWEbWaQbLU8uz/mtBzUF+\nfUwPfHJ5elnNXkoOrJupmHN5fLT0zLm4BwyydFy4x2+IoZCn9Kr5v2c69BoVYh63\nn749sSmvZ6ES8lgQGVMDMBu4Gon2nL2XA46jCfMdiyHxtN/kHNGfZQIG6lzWE7OE\n76KlXIx3KadowGuuQNKotOrN8I1LOJwZmhsoVLiJkO/KdYE+HvJkJMcYr07/R54H\n9jVlpNMKVv/1F2Rs76giJUmTtt8AF9pYfl3uxRuw0dFfIRDH+fO6AgonB8Xx1sfT\n4PsJYGw=\n-----END CERTIFICATE-----\n\n# Issuer: CN=Amazon Root CA 3 O=Amazon\n# Subject: CN=Amazon Root CA 3 O=Amazon\n# Label: \"Amazon Root CA 3\"\n# Serial: 143266986699090766294700635381230934788665930\n# MD5 Fingerprint: a0:d4:ef:0b:f7:b5:d8:49:95:2a:ec:f5:c4:fc:81:87\n# SHA1 Fingerprint: 0d:44:dd:8c:3c:8c:1a:1a:58:75:64:81:e9:0f:2e:2a:ff:b3:d2:6e\n# SHA256 Fingerprint: 18:ce:6c:fe:7b:f1:4e:60:b2:e3:47:b8:df:e8:68:cb:31:d0:2e:bb:3a:da:27:15:69:f5:03:43:b4:6d:b3:a4\n-----BEGIN CERTIFICATE-----\nMIIBtjCCAVugAwIBAgITBmyf1XSXNmY/Owua2eiedgPySjAKBggqhkjOPQQDAjA5\nMQswCQYDVQQGEwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6b24g\nUm9vdCBDQSAzMB4XDTE1MDUyNjAwMDAwMFoXDTQwMDUyNjAwMDAwMFowOTELMAkG\nA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpvbjEZMBcGA1UEAxMQQW1hem9uIFJvb3Qg\nQ0EgMzBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABCmXp8ZBf8ANm+gBG1bG8lKl\nui2yEujSLtf6ycXYqm0fc4E7O5hrOXwzpcVOho6AF2hiRVd9RFgdszflZwjrZt6j\nQjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgGGMB0GA1UdDgQWBBSr\nttvXBp43rDCGB5Fwx5zEGbF4wDAKBggqhkjOPQQDAgNJADBGAiEA4IWSoxe3jfkr\nBqWTrBqYaGFy+uGh0PsceGCmQ5nFuMQCIQCcAu/xlJyzlvnrxir4tiz+OpAUFteM\nYyRIHN8wfdVoOw==\n-----END CERTIFICATE-----\n\n# Issuer: CN=Amazon Root CA 4 O=Amazon\n# Subject: CN=Amazon Root CA 4 O=Amazon\n# Label: \"Amazon Root CA 4\"\n# Serial: 143266989758080763974105200630763877849284878\n# MD5 Fingerprint: 89:bc:27:d5:eb:17:8d:06:6a:69:d5:fd:89:47:b4:cd\n# SHA1 Fingerprint: f6:10:84:07:d6:f8:bb:67:98:0c:c2:e2:44:c2:eb:ae:1c:ef:63:be\n# SHA256 Fingerprint: e3:5d:28:41:9e:d0:20:25:cf:a6:90:38:cd:62:39:62:45:8d:a5:c6:95:fb:de:a3:c2:2b:0b:fb:25:89:70:92\n-----BEGIN CERTIFICATE-----\nMIIB8jCCAXigAwIBAgITBmyf18G7EEwpQ+Vxe3ssyBrBDjAKBggqhkjOPQQDAzA5\nMQswCQYDVQQGEwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6b24g\nUm9vdCBDQSA0MB4XDTE1MDUyNjAwMDAwMFoXDTQwMDUyNjAwMDAwMFowOTELMAkG\nA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpvbjEZMBcGA1UEAxMQQW1hem9uIFJvb3Qg\nQ0EgNDB2MBAGByqGSM49AgEGBSuBBAAiA2IABNKrijdPo1MN/sGKe0uoe0ZLY7Bi\n9i0b2whxIdIA6GO9mif78DluXeo9pcmBqqNbIJhFXRbb/egQbeOc4OO9X4Ri83Bk\nM6DLJC9wuoihKqB1+IGuYgbEgds5bimwHvouXKNCMEAwDwYDVR0TAQH/BAUwAwEB\n/zAOBgNVHQ8BAf8EBAMCAYYwHQYDVR0OBBYEFNPsxzplbszh2naaVvuc84ZtV+WB\nMAoGCCqGSM49BAMDA2gAMGUCMDqLIfG9fhGt0O9Yli/W651+kI0rz2ZVwyzjKKlw\nCkcO8DdZEv8tmZQoTipPNU0zWgIxAOp1AE47xDqUEpHJWEadIRNyp4iciuRMStuW\n1KyLa2tJElMzrdfkviT8tQp21KW8EA==\n-----END CERTIFICATE-----\n\n# Issuer: CN=LuxTrust Global Root 2 O=LuxTrust S.A.\n# Subject: CN=LuxTrust Global Root 2 O=LuxTrust S.A.\n# Label: \"LuxTrust Global Root 2\"\n# Serial: 59914338225734147123941058376788110305822489521\n# MD5 Fingerprint: b2:e1:09:00:61:af:f7:f1:91:6f:c4:ad:8d:5e:3b:7c\n# SHA1 Fingerprint: 1e:0e:56:19:0a:d1:8b:25:98:b2:04:44:ff:66:8a:04:17:99:5f:3f\n# SHA256 Fingerprint: 54:45:5f:71:29:c2:0b:14:47:c4:18:f9:97:16:8f:24:c5:8f:c5:02:3b:f5:da:5b:e2:eb:6e:1d:d8:90:2e:d5\n-----BEGIN CERTIFICATE-----\nMIIFwzCCA6ugAwIBAgIUCn6m30tEntpqJIWe5rgV0xZ/u7EwDQYJKoZIhvcNAQEL\nBQAwRjELMAkGA1UEBhMCTFUxFjAUBgNVBAoMDUx1eFRydXN0IFMuQS4xHzAdBgNV\nBAMMFkx1eFRydXN0IEdsb2JhbCBSb290IDIwHhcNMTUwMzA1MTMyMTU3WhcNMzUw\nMzA1MTMyMTU3WjBGMQswCQYDVQQGEwJMVTEWMBQGA1UECgwNTHV4VHJ1c3QgUy5B\nLjEfMB0GA1UEAwwWTHV4VHJ1c3QgR2xvYmFsIFJvb3QgMjCCAiIwDQYJKoZIhvcN\nAQEBBQADggIPADCCAgoCggIBANeFl78RmOnwYoNMPIf5U2o3C/IPPIfOb9wmKb3F\nibrJgz337spbxm1Jc7TJRqMbNBM/wYlFV/TZsfs2ZUv7COJIcRHIbjuend+JZTem\nhfY7RBi2xjcwYkSSl2l9QjAk5A0MiWtj3sXh306pFGxT4GHO9hcvHTy95iJMHZP1\nEMShduxq3sVs35a0VkBCwGKSMKEtFZSg0iAGCW5qbeXrt77U8PEVfIvmTroTzEsn\nXpk8F12PgX8zPU/TPxvsXD/wPEx1bvKm1Z3aLQdjAsZy6ZS8TEmVT4hSyNvoaYL4\nzDRbIvCGp4m9SAptZoFtyMhk+wHh9OHe2Z7d21vUKpkmFRseTJIpgp7VkoGSQXAZ\n96Tlk0u8d2cx3Rz9MXANF5kM+Qw5GSoXtTBxVdUPrljhPS80m8+f9niFwpN6cj5m\nj5wWEWCPnolvZ77gR1o7DJpni89Gxq44o/KnvObWhWszJHAiS8sIm7vI+AIpHb4g\nDEa/a4ebsypmQjVGbKq6rfmYe+lQVRQxv7HaLe2ArWgk+2mr2HETMOZns4dA/Yl+\n8kPREd8vZS9kzl8UubG/Mb2HeFpZZYiq/FkySIbWTLkpS5XTdvN3JW1CHDiDTf2j\nX5t/Lax5Gw5CMZdjpPuKadUiDTSQMC6otOBttpSsvItO13D8xTiOZCXhTTmQzsmH\nhFhxAgMBAAGjgagwgaUwDwYDVR0TAQH/BAUwAwEB/zBCBgNVHSAEOzA5MDcGByuB\nKwEBAQowLDAqBggrBgEFBQcCARYeaHR0cHM6Ly9yZXBvc2l0b3J5Lmx1eHRydXN0\nLmx1MA4GA1UdDwEB/wQEAwIBBjAfBgNVHSMEGDAWgBT/GCh2+UgFLKGu8SsbK7JT\n+Et8szAdBgNVHQ4EFgQU/xgodvlIBSyhrvErGyuyU/hLfLMwDQYJKoZIhvcNAQEL\nBQADggIBAGoZFO1uecEsh9QNcH7X9njJCwROxLHOk3D+sFTAMs2ZMGQXvw/l4jP9\nBzZAcg4atmpZ1gDlaCDdLnINH2pkMSCEfUmmWjfrRcmF9dTHF5kH5ptV5AzoqbTO\njFu1EVzPig4N1qx3gf4ynCSecs5U89BvolbW7MM3LGVYvlcAGvI1+ut7MV3CwRI9\nloGIlonBWVx65n9wNOeD4rHh4bhY79SV5GCc8JaXcozrhAIuZY+kt9J/Z93I055c\nqqmkoCUUBpvsT34tC38ddfEz2O3OuHVtPlu5mB0xDVbYQw8wkbIEa91WvpWAVWe+\n2M2D2RjuLg+GLZKecBPs3lHJQ3gCpU3I+V/EkVhGFndadKpAvAefMLmx9xIX3eP/\nJEAdemrRTxgKqpAd60Ae36EeRJIQmvKN4dFLRp7oRUKX6kWZ8+xm1QL68qZKJKre\nzrnK+T+Tb/mjuuqlPpmt/f97mfVl7vBZKGfXkJWkE4SphMHozs51k2MavDzq1WQf\nLSoSOcbDWjLtR5EWDrw4wVDej8oqkDQc7kGUnF4ZLvhFSZl0kbAEb+MEWrGrKqv+\nx9CWttrhSmQGbmBNvUJO/3jaJMobtNeWOWyu8Q6qp31IiyBMz2TWuJdGsE7RKlY6\noJO9r4Ak4Ap+58rVyuiFVdw2KuGUaJPHZnJED4AhMmwlxyOAgwrr\n-----END CERTIFICATE-----\n\n# Issuer: CN=TUBITAK Kamu SM SSL Kok Sertifikasi - Surum 1 O=Turkiye Bilimsel ve Teknolojik Arastirma Kurumu - TUBITAK OU=Kamu Sertifikasyon Merkezi - Kamu SM\n# Subject: CN=TUBITAK Kamu SM SSL Kok Sertifikasi - Surum 1 O=Turkiye Bilimsel ve Teknolojik Arastirma Kurumu - TUBITAK OU=Kamu Sertifikasyon Merkezi - Kamu SM\n# Label: \"TUBITAK Kamu SM SSL Kok Sertifikasi - Surum 1\"\n# Serial: 1\n# MD5 Fingerprint: dc:00:81:dc:69:2f:3e:2f:b0:3b:f6:3d:5a:91:8e:49\n# SHA1 Fingerprint: 31:43:64:9b:ec:ce:27:ec:ed:3a:3f:0b:8f:0d:e4:e8:91:dd:ee:ca\n# SHA256 Fingerprint: 46:ed:c3:68:90:46:d5:3a:45:3f:b3:10:4a:b8:0d:ca:ec:65:8b:26:60:ea:16:29:dd:7e:86:79:90:64:87:16\n-----BEGIN CERTIFICATE-----\nMIIEYzCCA0ugAwIBAgIBATANBgkqhkiG9w0BAQsFADCB0jELMAkGA1UEBhMCVFIx\nGDAWBgNVBAcTD0dlYnplIC0gS29jYWVsaTFCMEAGA1UEChM5VHVya2l5ZSBCaWxp\nbXNlbCB2ZSBUZWtub2xvamlrIEFyYXN0aXJtYSBLdXJ1bXUgLSBUVUJJVEFLMS0w\nKwYDVQQLEyRLYW11IFNlcnRpZmlrYXN5b24gTWVya2V6aSAtIEthbXUgU00xNjA0\nBgNVBAMTLVRVQklUQUsgS2FtdSBTTSBTU0wgS29rIFNlcnRpZmlrYXNpIC0gU3Vy\ndW0gMTAeFw0xMzExMjUwODI1NTVaFw00MzEwMjUwODI1NTVaMIHSMQswCQYDVQQG\nEwJUUjEYMBYGA1UEBxMPR2ViemUgLSBLb2NhZWxpMUIwQAYDVQQKEzlUdXJraXll\nIEJpbGltc2VsIHZlIFRla25vbG9qaWsgQXJhc3Rpcm1hIEt1cnVtdSAtIFRVQklU\nQUsxLTArBgNVBAsTJEthbXUgU2VydGlmaWthc3lvbiBNZXJrZXppIC0gS2FtdSBT\nTTE2MDQGA1UEAxMtVFVCSVRBSyBLYW11IFNNIFNTTCBLb2sgU2VydGlmaWthc2kg\nLSBTdXJ1bSAxMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAr3UwM6q7\na9OZLBI3hNmNe5eA027n/5tQlT6QlVZC1xl8JoSNkvoBHToP4mQ4t4y86Ij5iySr\nLqP1N+RAjhgleYN1Hzv/bKjFxlb4tO2KRKOrbEz8HdDc72i9z+SqzvBV96I01INr\nN3wcwv61A+xXzry0tcXtAA9TNypN9E8Mg/uGz8v+jE69h/mniyFXnHrfA2eJLJ2X\nYacQuFWQfw4tJzh03+f92k4S400VIgLI4OD8D62K18lUUMw7D8oWgITQUVbDjlZ/\niSIzL+aFCr2lqBs23tPcLG07xxO9WSMs5uWk99gL7eqQQESolbuT1dCANLZGeA4f\nAJNG4e7p+exPFwIDAQABo0IwQDAdBgNVHQ4EFgQUZT/HiobGPN08VFw1+DrtUgxH\nV8gwDgYDVR0PAQH/BAQDAgEGMA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZIhvcNAQEL\nBQADggEBACo/4fEyjq7hmFxLXs9rHmoJ0iKpEsdeV31zVmSAhHqT5Am5EM2fKifh\nAHe+SMg1qIGf5LgsyX8OsNJLN13qudULXjS99HMpw+0mFZx+CFOKWI3QSyjfwbPf\nIPP54+M638yclNhOT8NrF7f3cuitZjO1JVOr4PhMqZ398g26rrnZqsZr+ZO7rqu4\nlzwDGrpDxpa5RXI4s6ehlj2Re37AIVNMh+3yC1SVUZPVIqUNivGTDj5UDrDYyU7c\n8jEyVupk+eq1nRZmQnLzf9OxMUP8pI4X8W0jq5Rm+K37DwhuJi1/FwcJsoz7UMCf\nlo3Ptv0AnVoUmr8CRPXBwp8iXqIPoeM=\n-----END CERTIFICATE-----\n\n# Issuer: CN=GDCA TrustAUTH R5 ROOT O=GUANG DONG CERTIFICATE AUTHORITY CO.,LTD.\n# Subject: CN=GDCA TrustAUTH R5 ROOT O=GUANG DONG CERTIFICATE AUTHORITY CO.,LTD.\n# Label: \"GDCA TrustAUTH R5 ROOT\"\n# Serial: 9009899650740120186\n# MD5 Fingerprint: 63:cc:d9:3d:34:35:5c:6f:53:a3:e2:08:70:48:1f:b4\n# SHA1 Fingerprint: 0f:36:38:5b:81:1a:25:c3:9b:31:4e:83:ca:e9:34:66:70:cc:74:b4\n# SHA256 Fingerprint: bf:ff:8f:d0:44:33:48:7d:6a:8a:a6:0c:1a:29:76:7a:9f:c2:bb:b0:5e:42:0f:71:3a:13:b9:92:89:1d:38:93\n-----BEGIN CERTIFICATE-----\nMIIFiDCCA3CgAwIBAgIIfQmX/vBH6nowDQYJKoZIhvcNAQELBQAwYjELMAkGA1UE\nBhMCQ04xMjAwBgNVBAoMKUdVQU5HIERPTkcgQ0VSVElGSUNBVEUgQVVUSE9SSVRZ\nIENPLixMVEQuMR8wHQYDVQQDDBZHRENBIFRydXN0QVVUSCBSNSBST09UMB4XDTE0\nMTEyNjA1MTMxNVoXDTQwMTIzMTE1NTk1OVowYjELMAkGA1UEBhMCQ04xMjAwBgNV\nBAoMKUdVQU5HIERPTkcgQ0VSVElGSUNBVEUgQVVUSE9SSVRZIENPLixMVEQuMR8w\nHQYDVQQDDBZHRENBIFRydXN0QVVUSCBSNSBST09UMIICIjANBgkqhkiG9w0BAQEF\nAAOCAg8AMIICCgKCAgEA2aMW8Mh0dHeb7zMNOwZ+Vfy1YI92hhJCfVZmPoiC7XJj\nDp6L3TQsAlFRwxn9WVSEyfFrs0yw6ehGXTjGoqcuEVe6ghWinI9tsJlKCvLriXBj\nTnnEt1u9ol2x8kECK62pOqPseQrsXzrj/e+APK00mxqriCZ7VqKChh/rNYmDf1+u\nKU49tm7srsHwJ5uu4/Ts765/94Y9cnrrpftZTqfrlYwiOXnhLQiPzLyRuEH3FMEj\nqcOtmkVEs7LXLM3GKeJQEK5cy4KOFxg2fZfmiJqwTTQJ9Cy5WmYqsBebnh52nUpm\nMUHfP/vFBu8btn4aRjb3ZGM74zkYI+dndRTVdVeSN72+ahsmUPI2JgaQxXABZG12\nZuGR224HwGGALrIuL4xwp9E7PLOR5G62xDtw8mySlwnNR30YwPO7ng/Wi64HtloP\nzgsMR6flPri9fcebNaBhlzpBdRfMK5Z3KpIhHtmVdiBnaM8Nvd/WHwlqmuLMc3Gk\nL30SgLdTMEZeS1SZD2fJpcjyIMGC7J0R38IC+xo70e0gmu9lZJIQDSri3nDxGGeC\njGHeuLzRL5z7D9Ar7Rt2ueQ5Vfj4oR24qoAATILnsn8JuLwwoC8N9VKejveSswoA\nHQBUlwbgsQfZxw9cZX08bVlX5O2ljelAU58VS6Bx9hoh49pwBiFYFIeFd3mqgnkC\nAwEAAaNCMEAwHQYDVR0OBBYEFOLJQJ9NzuiaoXzPDj9lxSmIahlRMA8GA1UdEwEB\n/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgGGMA0GCSqGSIb3DQEBCwUAA4ICAQDRSVfg\np8xoWLoBDysZzY2wYUWsEe1jUGn4H3++Fo/9nesLqjJHdtJnJO29fDMylyrHBYZm\nDRd9FBUb1Ov9H5r2XpdptxolpAqzkT9fNqyL7FeoPueBihhXOYV0GkLH6VsTX4/5\nCOmSdI31R9KrO9b7eGZONn356ZLpBN79SWP8bfsUcZNnL0dKt7n/HipzcEYwv1ry\nL3ml4Y0M2fmyYzeMN2WFcGpcWwlyua1jPLHd+PwyvzeG5LuOmCd+uh8W4XAR8gPf\nJWIyJyYYMoSf/wA6E7qaTfRPuBRwIrHKK5DOKcFw9C+df/KQHtZa37dG/OaG+svg\nIHZ6uqbL9XzeYqWxi+7egmaKTjowHz+Ay60nugxe19CxVsp3cbK1daFQqUBDF8Io\n2c9Si1vIY9RCPqAzekYu9wogRlR+ak8x8YF+QnQ4ZXMn7sZ8uI7XpTrXmKGcjBBV\n09tL7ECQ8s1uV9JiDnxXk7Gnbc2dg7sq5+W2O3FYrf3RRbxake5TFW/TRQl1brqQ\nXR4EzzffHqhmsYzmIGrv/EhOdJhCrylvLmrH+33RZjEizIYAfmaDDEL0vTSSwxrq\nT8p+ck0LcIymSLumoRT2+1hEmRSuqguTaaApJUqlyyvdimYHFngVV3Eb7PVHhPOe\nMTd61X8kreS8/f3MboPoDKi3QWwH3b08hpcv0g==\n-----END CERTIFICATE-----\n\n# Issuer: CN=TrustCor RootCert CA-1 O=TrustCor Systems S. de R.L. OU=TrustCor Certificate Authority\n# Subject: CN=TrustCor RootCert CA-1 O=TrustCor Systems S. de R.L. OU=TrustCor Certificate Authority\n# Label: \"TrustCor RootCert CA-1\"\n# Serial: 15752444095811006489\n# MD5 Fingerprint: 6e:85:f1:dc:1a:00:d3:22:d5:b2:b2:ac:6b:37:05:45\n# SHA1 Fingerprint: ff:bd:cd:e7:82:c8:43:5e:3c:6f:26:86:5c:ca:a8:3a:45:5b:c3:0a\n# SHA256 Fingerprint: d4:0e:9c:86:cd:8f:e4:68:c1:77:69:59:f4:9e:a7:74:fa:54:86:84:b6:c4:06:f3:90:92:61:f4:dc:e2:57:5c\n-----BEGIN CERTIFICATE-----\nMIIEMDCCAxigAwIBAgIJANqb7HHzA7AZMA0GCSqGSIb3DQEBCwUAMIGkMQswCQYD\nVQQGEwJQQTEPMA0GA1UECAwGUGFuYW1hMRQwEgYDVQQHDAtQYW5hbWEgQ2l0eTEk\nMCIGA1UECgwbVHJ1c3RDb3IgU3lzdGVtcyBTLiBkZSBSLkwuMScwJQYDVQQLDB5U\ncnVzdENvciBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkxHzAdBgNVBAMMFlRydXN0Q29y\nIFJvb3RDZXJ0IENBLTEwHhcNMTYwMjA0MTIzMjE2WhcNMjkxMjMxMTcyMzE2WjCB\npDELMAkGA1UEBhMCUEExDzANBgNVBAgMBlBhbmFtYTEUMBIGA1UEBwwLUGFuYW1h\nIENpdHkxJDAiBgNVBAoMG1RydXN0Q29yIFN5c3RlbXMgUy4gZGUgUi5MLjEnMCUG\nA1UECwweVHJ1c3RDb3IgQ2VydGlmaWNhdGUgQXV0aG9yaXR5MR8wHQYDVQQDDBZU\ncnVzdENvciBSb290Q2VydCBDQS0xMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIB\nCgKCAQEAv463leLCJhJrMxnHQFgKq1mqjQCj/IDHUHuO1CAmujIS2CNUSSUQIpid\nRtLByZ5OGy4sDjjzGiVoHKZaBeYei0i/mJZ0PmnK6bV4pQa81QBeCQryJ3pS/C3V\nseq0iWEk8xoT26nPUu0MJLq5nux+AHT6k61sKZKuUbS701e/s/OojZz0JEsq1pme\n9J7+wH5COucLlVPat2gOkEz7cD+PSiyU8ybdY2mplNgQTsVHCJCZGxdNuWxu72CV\nEY4hgLW9oHPY0LJ3xEXqWib7ZnZ2+AYfYW0PVcWDtxBWcgYHpfOxGgMFZA6dWorW\nhnAbJN7+KIor0Gqw/Hqi3LJ5DotlDwIDAQABo2MwYTAdBgNVHQ4EFgQU7mtJPHo/\nDeOxCbeKyKsZn3MzUOcwHwYDVR0jBBgwFoAU7mtJPHo/DeOxCbeKyKsZn3MzUOcw\nDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAYYwDQYJKoZIhvcNAQELBQAD\nggEBACUY1JGPE+6PHh0RU9otRCkZoB5rMZ5NDp6tPVxBb5UrJKF5mDo4Nvu7Zp5I\n/5CQ7z3UuJu0h3U/IJvOcs+hVcFNZKIZBqEHMwwLKeXx6quj7LUKdJDHfXLy11yf\nke+Ri7fc7Waiz45mO7yfOgLgJ90WmMCV1Aqk5IGadZQ1nJBfiDcGrVmVCrDRZ9MZ\nyonnMlo2HD6CqFqTvsbQZJG2z9m2GM/bftJlo6bEjhcxwft+dtvTheNYsnd6djts\nL1Ac59v2Z3kf9YKVmgenFK+P3CghZwnS1k1aHBkcjndcw5QkPTJrS37UeJSDvjdN\nzl/HHk484IkzlQsPpTLWPFp5LBk=\n-----END CERTIFICATE-----\n\n# Issuer: CN=TrustCor RootCert CA-2 O=TrustCor Systems S. de R.L. OU=TrustCor Certificate Authority\n# Subject: CN=TrustCor RootCert CA-2 O=TrustCor Systems S. de R.L. OU=TrustCor Certificate Authority\n# Label: \"TrustCor RootCert CA-2\"\n# Serial: 2711694510199101698\n# MD5 Fingerprint: a2:e1:f8:18:0b:ba:45:d5:c7:41:2a:bb:37:52:45:64\n# SHA1 Fingerprint: b8:be:6d:cb:56:f1:55:b9:63:d4:12:ca:4e:06:34:c7:94:b2:1c:c0\n# SHA256 Fingerprint: 07:53:e9:40:37:8c:1b:d5:e3:83:6e:39:5d:ae:a5:cb:83:9e:50:46:f1:bd:0e:ae:19:51:cf:10:fe:c7:c9:65\n-----BEGIN CERTIFICATE-----\nMIIGLzCCBBegAwIBAgIIJaHfyjPLWQIwDQYJKoZIhvcNAQELBQAwgaQxCzAJBgNV\nBAYTAlBBMQ8wDQYDVQQIDAZQYW5hbWExFDASBgNVBAcMC1BhbmFtYSBDaXR5MSQw\nIgYDVQQKDBtUcnVzdENvciBTeXN0ZW1zIFMuIGRlIFIuTC4xJzAlBgNVBAsMHlRy\ndXN0Q29yIENlcnRpZmljYXRlIEF1dGhvcml0eTEfMB0GA1UEAwwWVHJ1c3RDb3Ig\nUm9vdENlcnQgQ0EtMjAeFw0xNjAyMDQxMjMyMjNaFw0zNDEyMzExNzI2MzlaMIGk\nMQswCQYDVQQGEwJQQTEPMA0GA1UECAwGUGFuYW1hMRQwEgYDVQQHDAtQYW5hbWEg\nQ2l0eTEkMCIGA1UECgwbVHJ1c3RDb3IgU3lzdGVtcyBTLiBkZSBSLkwuMScwJQYD\nVQQLDB5UcnVzdENvciBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkxHzAdBgNVBAMMFlRy\ndXN0Q29yIFJvb3RDZXJ0IENBLTIwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIK\nAoICAQCnIG7CKqJiJJWQdsg4foDSq8GbZQWU9MEKENUCrO2fk8eHyLAnK0IMPQo+\nQVqedd2NyuCb7GgypGmSaIwLgQ5WoD4a3SwlFIIvl9NkRvRUqdw6VC0xK5mC8tkq\n1+9xALgxpL56JAfDQiDyitSSBBtlVkxs1Pu2YVpHI7TYabS3OtB0PAx1oYxOdqHp\n2yqlO/rOsP9+aij9JxzIsekp8VduZLTQwRVtDr4uDkbIXvRR/u8OYzo7cbrPb1nK\nDOObXUm4TOJXsZiKQlecdu/vvdFoqNL0Cbt3Nb4lggjEFixEIFapRBF37120Hape\naz6LMvYHL1cEksr1/p3C6eizjkxLAjHZ5DxIgif3GIJ2SDpxsROhOdUuxTTCHWKF\n3wP+TfSvPd9cW436cOGlfifHhi5qjxLGhF5DUVCcGZt45vz27Ud+ez1m7xMTiF88\noWP7+ayHNZ/zgp6kPwqcMWmLmaSISo5uZk3vFsQPeSghYA2FFn3XVDjxklb9tTNM\ng9zXEJ9L/cb4Qr26fHMC4P99zVvh1Kxhe1fVSntb1IVYJ12/+CtgrKAmrhQhJ8Z3\nmjOAPF5GP/fDsaOGM8boXg25NSyqRsGFAnWAoOsk+xWq5Gd/bnc/9ASKL3x74xdh\n8N0JqSDIvgmk0H5Ew7IwSjiqqewYmgeCK9u4nBit2uBGF6zPXQIDAQABo2MwYTAd\nBgNVHQ4EFgQU2f4hQG6UnrybPZx9mCAZ5YwwYrIwHwYDVR0jBBgwFoAU2f4hQG6U\nnrybPZx9mCAZ5YwwYrIwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAYYw\nDQYJKoZIhvcNAQELBQADggIBAJ5Fngw7tu/hOsh80QA9z+LqBrWyOrsGS2h60COX\ndKcs8AjYeVrXWoSK2BKaG9l9XE1wxaX5q+WjiYndAfrs3fnpkpfbsEZC89NiqpX+\nMWcUaViQCqoL7jcjx1BRtPV+nuN79+TMQjItSQzL/0kMmx40/W5ulop5A7Zv2wnL\n/V9lFDfhOPXzYRZY5LVtDQsEGz9QLX+zx3oaFoBg+Iof6Rsqxvm6ARppv9JYx1RX\nCI/hOWB3S6xZhBqI8d3LT3jX5+EzLfzuQfogsL7L9ziUwOHQhQ+77Sxzq+3+knYa\nZH9bDTMJBzN7Bj8RpFxwPIXAz+OQqIN3+tvmxYxoZxBnpVIt8MSZj3+/0WvitUfW\n2dCFmU2Umw9Lje4AWkcdEQOsQRivh7dvDDqPys/cA8GiCcjl/YBeyGBCARsaU1q7\nN6a3vLqE6R5sGtRk2tRD/pOLS/IseRYQ1JMLiI+h2IYURpFHmygk71dSTlxCnKr3\nSewn6EAes6aJInKc9Q0ztFijMDvd1GpUk74aTfOTlPf8hAs/hCBcNANExdqtvArB\nAs8e5ZTZ845b2EzwnexhF7sUMlQMAimTHpKG9n/v55IFDlndmQguLvqcAFLTxWYp\n5KeXRKQOKIETNcX2b2TmQcTVL8w0RSXPQQCWPUouwpaYT05KnJe32x+SMsj/D1Fu\n1uwJ\n-----END CERTIFICATE-----\n\n# Issuer: CN=TrustCor ECA-1 O=TrustCor Systems S. de R.L. OU=TrustCor Certificate Authority\n# Subject: CN=TrustCor ECA-1 O=TrustCor Systems S. de R.L. OU=TrustCor Certificate Authority\n# Label: \"TrustCor ECA-1\"\n# Serial: 9548242946988625984\n# MD5 Fingerprint: 27:92:23:1d:0a:f5:40:7c:e9:e6:6b:9d:d8:f5:e7:6c\n# SHA1 Fingerprint: 58:d1:df:95:95:67:6b:63:c0:f0:5b:1c:17:4d:8b:84:0b:c8:78:bd\n# SHA256 Fingerprint: 5a:88:5d:b1:9c:01:d9:12:c5:75:93:88:93:8c:af:bb:df:03:1a:b2:d4:8e:91:ee:15:58:9b:42:97:1d:03:9c\n-----BEGIN CERTIFICATE-----\nMIIEIDCCAwigAwIBAgIJAISCLF8cYtBAMA0GCSqGSIb3DQEBCwUAMIGcMQswCQYD\nVQQGEwJQQTEPMA0GA1UECAwGUGFuYW1hMRQwEgYDVQQHDAtQYW5hbWEgQ2l0eTEk\nMCIGA1UECgwbVHJ1c3RDb3IgU3lzdGVtcyBTLiBkZSBSLkwuMScwJQYDVQQLDB5U\ncnVzdENvciBDZXJ0aWZpY2F0ZSBBdXRob3JpdHkxFzAVBgNVBAMMDlRydXN0Q29y\nIEVDQS0xMB4XDTE2MDIwNDEyMzIzM1oXDTI5MTIzMTE3MjgwN1owgZwxCzAJBgNV\nBAYTAlBBMQ8wDQYDVQQIDAZQYW5hbWExFDASBgNVBAcMC1BhbmFtYSBDaXR5MSQw\nIgYDVQQKDBtUcnVzdENvciBTeXN0ZW1zIFMuIGRlIFIuTC4xJzAlBgNVBAsMHlRy\ndXN0Q29yIENlcnRpZmljYXRlIEF1dGhvcml0eTEXMBUGA1UEAwwOVHJ1c3RDb3Ig\nRUNBLTEwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDPj+ARtZ+odnbb\n3w9U73NjKYKtR8aja+3+XzP4Q1HpGjORMRegdMTUpwHmspI+ap3tDvl0mEDTPwOA\nBoJA6LHip1GnHYMma6ve+heRK9jGrB6xnhkB1Zem6g23xFUfJ3zSCNV2HykVh0A5\n3ThFEXXQmqc04L/NyFIduUd+Dbi7xgz2c1cWWn5DkR9VOsZtRASqnKmcp0yJF4Ou\nowReUoCLHhIlERnXDH19MURB6tuvsBzvgdAsxZohmz3tQjtQJvLsznFhBmIhVE5/\nwZ0+fyCMgMsq2JdiyIMzkX2woloPV+g7zPIlstR8L+xNxqE6FXrntl019fZISjZF\nZtS6mFjBAgMBAAGjYzBhMB0GA1UdDgQWBBREnkj1zG1I1KBLf/5ZJC+Dl5mahjAf\nBgNVHSMEGDAWgBREnkj1zG1I1KBLf/5ZJC+Dl5mahjAPBgNVHRMBAf8EBTADAQH/\nMA4GA1UdDwEB/wQEAwIBhjANBgkqhkiG9w0BAQsFAAOCAQEABT41XBVwm8nHc2Fv\ncivUwo/yQ10CzsSUuZQRg2dd4mdsdXa/uwyqNsatR5Nj3B5+1t4u/ukZMjgDfxT2\nAHMsWbEhBuH7rBiVDKP/mZb3Kyeb1STMHd3BOuCYRLDE5D53sXOpZCz2HAF8P11F\nhcCF5yWPldwX8zyfGm6wyuMdKulMY/okYWLW2n62HGz1Ah3UKt1VkOsqEUc8Ll50\nsoIipX1TH0XsJ5F95yIW6MBoNtjG8U+ARDL54dHRHareqKucBK+tIA5kmE2la8BI\nWJZpTdwHjFGTot+fDz2LYLSCjaoITmJF4PkL0uDgPFveXHEnJcLmA4GLEFPjx1Wi\ntJ/X5g==\n-----END CERTIFICATE-----\n\n# Issuer: CN=SSL.com Root Certification Authority RSA O=SSL Corporation\n# Subject: CN=SSL.com Root Certification Authority RSA O=SSL Corporation\n# Label: \"SSL.com Root Certification Authority RSA\"\n# Serial: 8875640296558310041\n# MD5 Fingerprint: 86:69:12:c0:70:f1:ec:ac:ac:c2:d5:bc:a5:5b:a1:29\n# SHA1 Fingerprint: b7:ab:33:08:d1:ea:44:77:ba:14:80:12:5a:6f:bd:a9:36:49:0c:bb\n# SHA256 Fingerprint: 85:66:6a:56:2e:e0:be:5c:e9:25:c1:d8:89:0a:6f:76:a8:7e:c1:6d:4d:7d:5f:29:ea:74:19:cf:20:12:3b:69\n-----BEGIN CERTIFICATE-----\nMIIF3TCCA8WgAwIBAgIIeyyb0xaAMpkwDQYJKoZIhvcNAQELBQAwfDELMAkGA1UE\nBhMCVVMxDjAMBgNVBAgMBVRleGFzMRAwDgYDVQQHDAdIb3VzdG9uMRgwFgYDVQQK\nDA9TU0wgQ29ycG9yYXRpb24xMTAvBgNVBAMMKFNTTC5jb20gUm9vdCBDZXJ0aWZp\nY2F0aW9uIEF1dGhvcml0eSBSU0EwHhcNMTYwMjEyMTczOTM5WhcNNDEwMjEyMTcz\nOTM5WjB8MQswCQYDVQQGEwJVUzEOMAwGA1UECAwFVGV4YXMxEDAOBgNVBAcMB0hv\ndXN0b24xGDAWBgNVBAoMD1NTTCBDb3Jwb3JhdGlvbjExMC8GA1UEAwwoU1NMLmNv\nbSBSb290IENlcnRpZmljYXRpb24gQXV0aG9yaXR5IFJTQTCCAiIwDQYJKoZIhvcN\nAQEBBQADggIPADCCAgoCggIBAPkP3aMrfcvQKv7sZ4Wm5y4bunfh4/WvpOz6Sl2R\nxFdHaxh3a3by/ZPkPQ/CFp4LZsNWlJ4Xg4XOVu/yFv0AYvUiCVToZRdOQbngT0aX\nqhvIuG5iXmmxX9sqAn78bMrzQdjt0Oj8P2FI7bADFB0QDksZ4LtO7IZl/zbzXmcC\nC52GVWH9ejjt/uIZALdvoVBidXQ8oPrIJZK0bnoix/geoeOy3ZExqysdBP+lSgQ3\n6YWkMyv94tZVNHwZpEpox7Ko07fKoZOI68GXvIz5HdkihCR0xwQ9aqkpk8zruFvh\n/l8lqjRYyMEjVJ0bmBHDOJx+PYZspQ9AhnwC9FwCTyjLrnGfDzrIM/4RJTXq/LrF\nYD3ZfBjVsqnTdXgDciLKOsMf7yzlLqn6niy2UUb9rwPW6mBo6oUWNmuF6R7As93E\nJNyAKoFBbZQ+yODJgUEAnl6/f8UImKIYLEJAs/lvOCdLToD0PYFH4Ih86hzOtXVc\nUS4cK38acijnALXRdMbX5J+tB5O2UzU1/Dfkw/ZdFr4hc96SCvigY2q8lpJqPvi8\nZVWb3vUNiSYE/CUapiVpy8JtynziWV+XrOvvLsi81xtZPCvM8hnIk2snYxnP/Okm\n+Mpxm3+T/jRnhE6Z6/yzeAkzcLpmpnbtG3PrGqUNxCITIJRWCk4sbE6x/c+cCbqi\nM+2HAgMBAAGjYzBhMB0GA1UdDgQWBBTdBAkHovV6fVJTEpKV7jiAJQ2mWTAPBgNV\nHRMBAf8EBTADAQH/MB8GA1UdIwQYMBaAFN0ECQei9Xp9UlMSkpXuOIAlDaZZMA4G\nA1UdDwEB/wQEAwIBhjANBgkqhkiG9w0BAQsFAAOCAgEAIBgRlCn7Jp0cHh5wYfGV\ncpNxJK1ok1iOMq8bs3AD/CUrdIWQPXhq9LmLpZc7tRiRux6n+UBbkflVma8eEdBc\nHadm47GUBwwyOabqG7B52B2ccETjit3E+ZUfijhDPwGFpUenPUayvOUiaPd7nNgs\nPgohyC0zrL/FgZkxdMF1ccW+sfAjRfSda/wZY52jvATGGAslu1OJD7OAUN5F7kR/\nq5R4ZJjT9ijdh9hwZXT7DrkT66cPYakylszeu+1jTBi7qUD3oFRuIIhxdRjqerQ0\ncuAjJ3dctpDqhiVAq+8zD8ufgr6iIPv2tS0a5sKFsXQP+8hlAqRSAUfdSSLBv9jr\na6x+3uxjMxW3IwiPxg+NQVrdjsW5j+VFP3jbutIbQLH+cU0/4IGiul607BXgk90I\nH37hVZkLId6Tngr75qNJvTYw/ud3sqB1l7UtgYgXZSD32pAAn8lSzDLKNXz1PQ/Y\nK9f1JmzJBjSWFupwWRoyeXkLtoh/D1JIPb9s2KJELtFOt3JY04kTlf5Eq/jXixtu\nnLwsoFvVagCvXzfh1foQC5ichucmj87w7G6KVwuA406ywKBjYZC6VWg3dGq2ktuf\noYYitmUnDuy2n0Jg5GfCtdpBC8TTi2EbvPofkSvXRAdeuims2cXp71NIWuuA8ShY\nIc2wBlX7Jz9TkHCpBB5XJ7k=\n-----END CERTIFICATE-----\n\n# Issuer: CN=SSL.com Root Certification Authority ECC O=SSL Corporation\n# Subject: CN=SSL.com Root Certification Authority ECC O=SSL Corporation\n# Label: \"SSL.com Root Certification Authority ECC\"\n# Serial: 8495723813297216424\n# MD5 Fingerprint: 2e:da:e4:39:7f:9c:8f:37:d1:70:9f:26:17:51:3a:8e\n# SHA1 Fingerprint: c3:19:7c:39:24:e6:54:af:1b:c4:ab:20:95:7a:e2:c3:0e:13:02:6a\n# SHA256 Fingerprint: 34:17:bb:06:cc:60:07:da:1b:96:1c:92:0b:8a:b4:ce:3f:ad:82:0e:4a:a3:0b:9a:cb:c4:a7:4e:bd:ce:bc:65\n-----BEGIN CERTIFICATE-----\nMIICjTCCAhSgAwIBAgIIdebfy8FoW6gwCgYIKoZIzj0EAwIwfDELMAkGA1UEBhMC\nVVMxDjAMBgNVBAgMBVRleGFzMRAwDgYDVQQHDAdIb3VzdG9uMRgwFgYDVQQKDA9T\nU0wgQ29ycG9yYXRpb24xMTAvBgNVBAMMKFNTTC5jb20gUm9vdCBDZXJ0aWZpY2F0\naW9uIEF1dGhvcml0eSBFQ0MwHhcNMTYwMjEyMTgxNDAzWhcNNDEwMjEyMTgxNDAz\nWjB8MQswCQYDVQQGEwJVUzEOMAwGA1UECAwFVGV4YXMxEDAOBgNVBAcMB0hvdXN0\nb24xGDAWBgNVBAoMD1NTTCBDb3Jwb3JhdGlvbjExMC8GA1UEAwwoU1NMLmNvbSBS\nb290IENlcnRpZmljYXRpb24gQXV0aG9yaXR5IEVDQzB2MBAGByqGSM49AgEGBSuB\nBAAiA2IABEVuqVDEpiM2nl8ojRfLliJkP9x6jh3MCLOicSS6jkm5BBtHllirLZXI\n7Z4INcgn64mMU1jrYor+8FsPazFSY0E7ic3s7LaNGdM0B9y7xgZ/wkWV7Mt/qCPg\nCemB+vNH06NjMGEwHQYDVR0OBBYEFILRhXMw5zUE044CkvvlpNHEIejNMA8GA1Ud\nEwEB/wQFMAMBAf8wHwYDVR0jBBgwFoAUgtGFczDnNQTTjgKS++Wk0cQh6M0wDgYD\nVR0PAQH/BAQDAgGGMAoGCCqGSM49BAMCA2cAMGQCMG/n61kRpGDPYbCWe+0F+S8T\nkdzt5fxQaxFGRrMcIQBiu77D5+jNB5n5DQtdcj7EqgIwH7y6C+IwJPt8bYBVCpk+\ngA0z5Wajs6O7pdWLjwkspl1+4vAHCGht0nxpbl/f5Wpl\n-----END CERTIFICATE-----\n\n# Issuer: CN=SSL.com EV Root Certification Authority RSA R2 O=SSL Corporation\n# Subject: CN=SSL.com EV Root Certification Authority RSA R2 O=SSL Corporation\n# Label: \"SSL.com EV Root Certification Authority RSA R2\"\n# Serial: 6248227494352943350\n# MD5 Fingerprint: e1:1e:31:58:1a:ae:54:53:02:f6:17:6a:11:7b:4d:95\n# SHA1 Fingerprint: 74:3a:f0:52:9b:d0:32:a0:f4:4a:83:cd:d4:ba:a9:7b:7c:2e:c4:9a\n# SHA256 Fingerprint: 2e:7b:f1:6c:c2:24:85:a7:bb:e2:aa:86:96:75:07:61:b0:ae:39:be:3b:2f:e9:d0:cc:6d:4e:f7:34:91:42:5c\n-----BEGIN CERTIFICATE-----\nMIIF6zCCA9OgAwIBAgIIVrYpzTS8ePYwDQYJKoZIhvcNAQELBQAwgYIxCzAJBgNV\nBAYTAlVTMQ4wDAYDVQQIDAVUZXhhczEQMA4GA1UEBwwHSG91c3RvbjEYMBYGA1UE\nCgwPU1NMIENvcnBvcmF0aW9uMTcwNQYDVQQDDC5TU0wuY29tIEVWIFJvb3QgQ2Vy\ndGlmaWNhdGlvbiBBdXRob3JpdHkgUlNBIFIyMB4XDTE3MDUzMTE4MTQzN1oXDTQy\nMDUzMDE4MTQzN1owgYIxCzAJBgNVBAYTAlVTMQ4wDAYDVQQIDAVUZXhhczEQMA4G\nA1UEBwwHSG91c3RvbjEYMBYGA1UECgwPU1NMIENvcnBvcmF0aW9uMTcwNQYDVQQD\nDC5TU0wuY29tIEVWIFJvb3QgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkgUlNBIFIy\nMIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAjzZlQOHWTcDXtOlG2mvq\nM0fNTPl9fb69LT3w23jhhqXZuglXaO1XPqDQCEGD5yhBJB/jchXQARr7XnAjssuf\nOePPxU7Gkm0mxnu7s9onnQqG6YE3Bf7wcXHswxzpY6IXFJ3vG2fThVUCAtZJycxa\n4bH3bzKfydQ7iEGonL3Lq9ttewkfokxykNorCPzPPFTOZw+oz12WGQvE43LrrdF9\nHSfvkusQv1vrO6/PgN3B0pYEW3p+pKk8OHakYo6gOV7qd89dAFmPZiw+B6KjBSYR\naZfqhbcPlgtLyEDhULouisv3D5oi53+aNxPN8k0TayHRwMwi8qFG9kRpnMphNQcA\nb9ZhCBHqurj26bNg5U257J8UZslXWNvNh2n4ioYSA0e/ZhN2rHd9NCSFg83XqpyQ\nGp8hLH94t2S42Oim9HizVcuE0jLEeK6jj2HdzghTreyI/BXkmg3mnxp3zkyPuBQV\nPWKchjgGAGYS5Fl2WlPAApiiECtoRHuOec4zSnaqW4EWG7WK2NAAe15itAnWhmMO\npgWVSbooi4iTsjQc2KRVbrcc0N6ZVTsj9CLg+SlmJuwgUHfbSguPvuUCYHBBXtSu\nUDkiFCbLsjtzdFVHB3mBOagwE0TlBIqulhMlQg+5U8Sb/M3kHN48+qvWBkofZ6aY\nMBzdLNvcGJVXZsb/XItW9XcCAwEAAaNjMGEwDwYDVR0TAQH/BAUwAwEB/zAfBgNV\nHSMEGDAWgBT5YLvU49U09rj1BoAlp3PbRmmonjAdBgNVHQ4EFgQU+WC71OPVNPa4\n9QaAJadz20ZpqJ4wDgYDVR0PAQH/BAQDAgGGMA0GCSqGSIb3DQEBCwUAA4ICAQBW\ns47LCp1Jjr+kxJG7ZhcFUZh1++VQLHqe8RT6q9OKPv+RKY9ji9i0qVQBDb6Thi/5\nSm3HXvVX+cpVHBK+Rw82xd9qt9t1wkclf7nxY/hoLVUE0fKNsKTPvDxeH3jnpaAg\ncLAExbf3cqfeIg29MyVGjGSSJuM+LmOW2puMPfgYCdcDzH2GguDKBAdRUNf/ktUM\n79qGn5nX67evaOI5JpS6aLe/g9Pqemc9YmeuJeVy6OLk7K4S9ksrPJ/psEDzOFSz\n/bdoyNrGj1E8svuR3Bznm53htw1yj+KkxKl4+esUrMZDBcJlOSgYAsOCsp0FvmXt\nll9ldDz7CTUue5wT/RsPXcdtgTpWD8w74a8CLyKsRspGPKAcTNZEtF4uXBVmCeEm\nKf7GUmG6sXP/wwyc5WxqlD8UykAWlYTzWamsX0xhk23RO8yilQwipmdnRC652dKK\nQbNmC1r7fSOl8hqw/96bg5Qu0T/fkreRrwU7ZcegbLHNYhLDkBvjJc40vG93drEQ\nw/cFGsDWr3RiSBd3kmmQYRzelYB0VI8YHMPzA9C/pEN1hlMYegouCRw2n5H9gooi\nS9EOUCXdywMMF8mDAAhONU2Ki+3wApRmLER/y5UnlhetCTCstnEXbosX9hwJ1C07\nmKVx01QT2WDz9UtmT/rx7iASjbSsV7FFY6GsdqnC+w==\n-----END CERTIFICATE-----\n\n# Issuer: CN=SSL.com EV Root Certification Authority ECC O=SSL Corporation\n# Subject: CN=SSL.com EV Root Certification Authority ECC O=SSL Corporation\n# Label: \"SSL.com EV Root Certification Authority ECC\"\n# Serial: 3182246526754555285\n# MD5 Fingerprint: 59:53:22:65:83:42:01:54:c0:ce:42:b9:5a:7c:f2:90\n# SHA1 Fingerprint: 4c:dd:51:a3:d1:f5:20:32:14:b0:c6:c5:32:23:03:91:c7:46:42:6d\n# SHA256 Fingerprint: 22:a2:c1:f7:bd:ed:70:4c:c1:e7:01:b5:f4:08:c3:10:88:0f:e9:56:b5:de:2a:4a:44:f9:9c:87:3a:25:a7:c8\n-----BEGIN CERTIFICATE-----\nMIIClDCCAhqgAwIBAgIILCmcWxbtBZUwCgYIKoZIzj0EAwIwfzELMAkGA1UEBhMC\nVVMxDjAMBgNVBAgMBVRleGFzMRAwDgYDVQQHDAdIb3VzdG9uMRgwFgYDVQQKDA9T\nU0wgQ29ycG9yYXRpb24xNDAyBgNVBAMMK1NTTC5jb20gRVYgUm9vdCBDZXJ0aWZp\nY2F0aW9uIEF1dGhvcml0eSBFQ0MwHhcNMTYwMjEyMTgxNTIzWhcNNDEwMjEyMTgx\nNTIzWjB/MQswCQYDVQQGEwJVUzEOMAwGA1UECAwFVGV4YXMxEDAOBgNVBAcMB0hv\ndXN0b24xGDAWBgNVBAoMD1NTTCBDb3Jwb3JhdGlvbjE0MDIGA1UEAwwrU1NMLmNv\nbSBFViBSb290IENlcnRpZmljYXRpb24gQXV0aG9yaXR5IEVDQzB2MBAGByqGSM49\nAgEGBSuBBAAiA2IABKoSR5CYG/vvw0AHgyBO8TCCogbR8pKGYfL2IWjKAMTH6kMA\nVIbc/R/fALhBYlzccBYy3h+Z1MzFB8gIH2EWB1E9fVwHU+M1OIzfzZ/ZLg1Kthku\nWnBaBu2+8KGwytAJKaNjMGEwHQYDVR0OBBYEFFvKXuXe0oGqzagtZFG22XKbl+ZP\nMA8GA1UdEwEB/wQFMAMBAf8wHwYDVR0jBBgwFoAUW8pe5d7SgarNqC1kUbbZcpuX\n5k8wDgYDVR0PAQH/BAQDAgGGMAoGCCqGSM49BAMCA2gAMGUCMQCK5kCJN+vp1RPZ\nytRrJPOwPYdGWBrssd9v+1a6cGvHOMzosYxPD/fxZ3YOg9AeUY8CMD32IygmTMZg\nh5Mmm7I1HrrW9zzRHM76JTymGoEVW/MSD2zuZYrJh6j5B+BimoxcSg==\n-----END CERTIFICATE-----\n\n# Issuer: CN=GlobalSign O=GlobalSign OU=GlobalSign Root CA - R6\n# Subject: CN=GlobalSign O=GlobalSign OU=GlobalSign Root CA - R6\n# Label: \"GlobalSign Root CA - R6\"\n# Serial: 1417766617973444989252670301619537\n# MD5 Fingerprint: 4f:dd:07:e4:d4:22:64:39:1e:0c:37:42:ea:d1:c6:ae\n# SHA1 Fingerprint: 80:94:64:0e:b5:a7:a1:ca:11:9c:1f:dd:d5:9f:81:02:63:a7:fb:d1\n# SHA256 Fingerprint: 2c:ab:ea:fe:37:d0:6c:a2:2a:ba:73:91:c0:03:3d:25:98:29:52:c4:53:64:73:49:76:3a:3a:b5:ad:6c:cf:69\n-----BEGIN CERTIFICATE-----\nMIIFgzCCA2ugAwIBAgIORea7A4Mzw4VlSOb/RVEwDQYJKoZIhvcNAQEMBQAwTDEg\nMB4GA1UECxMXR2xvYmFsU2lnbiBSb290IENBIC0gUjYxEzARBgNVBAoTCkdsb2Jh\nbFNpZ24xEzARBgNVBAMTCkdsb2JhbFNpZ24wHhcNMTQxMjEwMDAwMDAwWhcNMzQx\nMjEwMDAwMDAwWjBMMSAwHgYDVQQLExdHbG9iYWxTaWduIFJvb3QgQ0EgLSBSNjET\nMBEGA1UEChMKR2xvYmFsU2lnbjETMBEGA1UEAxMKR2xvYmFsU2lnbjCCAiIwDQYJ\nKoZIhvcNAQEBBQADggIPADCCAgoCggIBAJUH6HPKZvnsFMp7PPcNCPG0RQssgrRI\nxutbPK6DuEGSMxSkb3/pKszGsIhrxbaJ0cay/xTOURQh7ErdG1rG1ofuTToVBu1k\nZguSgMpE3nOUTvOniX9PeGMIyBJQbUJmL025eShNUhqKGoC3GYEOfsSKvGRMIRxD\naNc9PIrFsmbVkJq3MQbFvuJtMgamHvm566qjuL++gmNQ0PAYid/kD3n16qIfKtJw\nLnvnvJO7bVPiSHyMEAc4/2ayd2F+4OqMPKq0pPbzlUoSB239jLKJz9CgYXfIWHSw\n1CM69106yqLbnQneXUQtkPGBzVeS+n68UARjNN9rkxi+azayOeSsJDa38O+2HBNX\nk7besvjihbdzorg1qkXy4J02oW9UivFyVm4uiMVRQkQVlO6jxTiWm05OWgtH8wY2\nSXcwvHE35absIQh1/OZhFj931dmRl4QKbNQCTXTAFO39OfuD8l4UoQSwC+n+7o/h\nbguyCLNhZglqsQY6ZZZZwPA1/cnaKI0aEYdwgQqomnUdnjqGBQCe24DWJfncBZ4n\nWUx2OVvq+aWh2IMP0f/fMBH5hc8zSPXKbWQULHpYT9NLCEnFlWQaYw55PfWzjMpY\nrZxCRXluDocZXFSxZba/jJvcE+kNb7gu3GduyYsRtYQUigAZcIN5kZeR1Bonvzce\nMgfYFGM8KEyvAgMBAAGjYzBhMA4GA1UdDwEB/wQEAwIBBjAPBgNVHRMBAf8EBTAD\nAQH/MB0GA1UdDgQWBBSubAWjkxPioufi1xzWx/B/yGdToDAfBgNVHSMEGDAWgBSu\nbAWjkxPioufi1xzWx/B/yGdToDANBgkqhkiG9w0BAQwFAAOCAgEAgyXt6NH9lVLN\nnsAEoJFp5lzQhN7craJP6Ed41mWYqVuoPId8AorRbrcWc+ZfwFSY1XS+wc3iEZGt\nIxg93eFyRJa0lV7Ae46ZeBZDE1ZXs6KzO7V33EByrKPrmzU+sQghoefEQzd5Mr61\n55wsTLxDKZmOMNOsIeDjHfrYBzN2VAAiKrlNIC5waNrlU/yDXNOd8v9EDERm8tLj\nvUYAGm0CuiVdjaExUd1URhxN25mW7xocBFymFe944Hn+Xds+qkxV/ZoVqW/hpvvf\ncDDpw+5CRu3CkwWJ+n1jez/QcYF8AOiYrg54NMMl+68KnyBr3TsTjxKM4kEaSHpz\noHdpx7Zcf4LIHv5YGygrqGytXm3ABdJ7t+uA/iU3/gKbaKxCXcPu9czc8FB10jZp\nnOZ7BN9uBmm23goJSFmH63sUYHpkqmlD75HHTOwY3WzvUy2MmeFe8nI+z1TIvWfs\npA9MRf/TuTAjB0yPEL+GltmZWrSZVxykzLsViVO6LAUP5MSeGbEYNNVMnbrt9x+v\nJJUEeKgDu+6B5dpffItKoZB0JaezPkvILFa9x8jvOOJckvB595yEunQtYQEgfn7R\n8k8HWV+LLUNS60YMlOH1Zkd5d9VUWx+tJDfLRVpOoERIyNiwmcUVhAn21klJwGW4\n5hpxbqCo8YLoRT5s1gLXCmeDBVrJpBA=\n-----END CERTIFICATE-----\n\n# Issuer: CN=OISTE WISeKey Global Root GC CA O=WISeKey OU=OISTE Foundation Endorsed\n# Subject: CN=OISTE WISeKey Global Root GC CA O=WISeKey OU=OISTE Foundation Endorsed\n# Label: \"OISTE WISeKey Global Root GC CA\"\n# Serial: 44084345621038548146064804565436152554\n# MD5 Fingerprint: a9:d6:b9:2d:2f:93:64:f8:a5:69:ca:91:e9:68:07:23\n# SHA1 Fingerprint: e0:11:84:5e:34:de:be:88:81:b9:9c:f6:16:26:d1:96:1f:c3:b9:31\n# SHA256 Fingerprint: 85:60:f9:1c:36:24:da:ba:95:70:b5:fe:a0:db:e3:6f:f1:1a:83:23:be:94:86:85:4f:b3:f3:4a:55:71:19:8d\n-----BEGIN CERTIFICATE-----\nMIICaTCCAe+gAwIBAgIQISpWDK7aDKtARb8roi066jAKBggqhkjOPQQDAzBtMQsw\nCQYDVQQGEwJDSDEQMA4GA1UEChMHV0lTZUtleTEiMCAGA1UECxMZT0lTVEUgRm91\nbmRhdGlvbiBFbmRvcnNlZDEoMCYGA1UEAxMfT0lTVEUgV0lTZUtleSBHbG9iYWwg\nUm9vdCBHQyBDQTAeFw0xNzA1MDkwOTQ4MzRaFw00MjA1MDkwOTU4MzNaMG0xCzAJ\nBgNVBAYTAkNIMRAwDgYDVQQKEwdXSVNlS2V5MSIwIAYDVQQLExlPSVNURSBGb3Vu\nZGF0aW9uIEVuZG9yc2VkMSgwJgYDVQQDEx9PSVNURSBXSVNlS2V5IEdsb2JhbCBS\nb290IEdDIENBMHYwEAYHKoZIzj0CAQYFK4EEACIDYgAETOlQwMYPchi82PG6s4ni\neUqjFqdrVCTbUf/q9Akkwwsin8tqJ4KBDdLArzHkdIJuyiXZjHWd8dvQmqJLIX4W\np2OQ0jnUsYd4XxiWD1AbNTcPasbc2RNNpI6QN+a9WzGRo1QwUjAOBgNVHQ8BAf8E\nBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zAdBgNVHQ4EFgQUSIcUrOPDnpBgOtfKie7T\nrYy0UGYwEAYJKwYBBAGCNxUBBAMCAQAwCgYIKoZIzj0EAwMDaAAwZQIwJsdpW9zV\n57LnyAyMjMPdeYwbY9XJUpROTYJKcx6ygISpJcBMWm1JKWB4E+J+SOtkAjEA2zQg\nMgj/mkkCtojeFK9dbJlxjRo/i9fgojaGHAeCOnZT/cKi7e97sIBPWA9LUzm9\n-----END CERTIFICATE-----\n\n# Issuer: CN=GTS Root R1 O=Google Trust Services LLC\n# Subject: CN=GTS Root R1 O=Google Trust Services LLC\n# Label: \"GTS Root R1\"\n# Serial: 146587175971765017618439757810265552097\n# MD5 Fingerprint: 82:1a:ef:d4:d2:4a:f2:9f:e2:3d:97:06:14:70:72:85\n# SHA1 Fingerprint: e1:c9:50:e6:ef:22:f8:4c:56:45:72:8b:92:20:60:d7:d5:a7:a3:e8\n# SHA256 Fingerprint: 2a:57:54:71:e3:13:40:bc:21:58:1c:bd:2c:f1:3e:15:84:63:20:3e:ce:94:bc:f9:d3:cc:19:6b:f0:9a:54:72\n-----BEGIN CERTIFICATE-----\nMIIFWjCCA0KgAwIBAgIQbkepxUtHDA3sM9CJuRz04TANBgkqhkiG9w0BAQwFADBH\nMQswCQYDVQQGEwJVUzEiMCAGA1UEChMZR29vZ2xlIFRydXN0IFNlcnZpY2VzIExM\nQzEUMBIGA1UEAxMLR1RTIFJvb3QgUjEwHhcNMTYwNjIyMDAwMDAwWhcNMzYwNjIy\nMDAwMDAwWjBHMQswCQYDVQQGEwJVUzEiMCAGA1UEChMZR29vZ2xlIFRydXN0IFNl\ncnZpY2VzIExMQzEUMBIGA1UEAxMLR1RTIFJvb3QgUjEwggIiMA0GCSqGSIb3DQEB\nAQUAA4ICDwAwggIKAoICAQC2EQKLHuOhd5s73L+UPreVp0A8of2C+X0yBoJx9vaM\nf/vo27xqLpeXo4xL+Sv2sfnOhB2x+cWX3u+58qPpvBKJXqeqUqv4IyfLpLGcY9vX\nmX7wCl7raKb0xlpHDU0QM+NOsROjyBhsS+z8CZDfnWQpJSMHobTSPS5g4M/SCYe7\nzUjwTcLCeoiKu7rPWRnWr4+wB7CeMfGCwcDfLqZtbBkOtdh+JhpFAz2weaSUKK0P\nfyblqAj+lug8aJRT7oM6iCsVlgmy4HqMLnXWnOunVmSPlk9orj2XwoSPwLxAwAtc\nvfaHszVsrBhQf4TgTM2S0yDpM7xSma8ytSmzJSq0SPly4cpk9+aCEI3oncKKiPo4\nZor8Y/kB+Xj9e1x3+naH+uzfsQ55lVe0vSbv1gHR6xYKu44LtcXFilWr06zqkUsp\nzBmkMiVOKvFlRNACzqrOSbTqn3yDsEB750Orp2yjj32JgfpMpf/VjsPOS+C12LOO\nRc92wO1AK/1TD7Cn1TsNsYqiA94xrcx36m97PtbfkSIS5r762DL8EGMUUXLeXdYW\nk70paDPvOmbsB4om3xPXV2V4J95eSRQAogB/mqghtqmxlbCluQ0WEdrHbEg8QOB+\nDVrNVjzRlwW5y0vtOUucxD/SVRNuJLDWcfr0wbrM7Rv1/oFB2ACYPTrIrnqYNxgF\nlQIDAQABo0IwQDAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zAdBgNV\nHQ4EFgQU5K8rJnEaK0gnhS9SZizv8IkTcT4wDQYJKoZIhvcNAQEMBQADggIBADiW\nCu49tJYeX++dnAsznyvgyv3SjgofQXSlfKqE1OXyHuY3UjKcC9FhHb8owbZEKTV1\nd5iyfNm9dKyKaOOpMQkpAWBz40d8U6iQSifvS9efk+eCNs6aaAyC58/UEBZvXw6Z\nXPYfcX3v73svfuo21pdwCxXu11xWajOl40k4DLh9+42FpLFZXvRq4d2h9mREruZR\ngyFmxhE+885H7pwoHyXa/6xmld01D1zvICxi/ZG6qcz8WpyTgYMpl0p8WnK0OdC3\nd8t5/Wk6kjftbjhlRn7pYL15iJdfOBL07q9bgsiG1eGZbYwE8na6SfZu6W0eX6Dv\nJ4J2QPim01hcDyxC2kLGe4g0x8HYRZvBPsVhHdljUEn2NIVq4BjFbkerQUIpm/Zg\nDdIx02OYI5NaAIFItO/Nis3Jz5nu2Z6qNuFoS3FJFDYoOj0dzpqPJeaAcWErtXvM\n+SUWgeExX6GjfhaknBZqlxi9dnKlC54dNuYvoS++cJEPqOba+MSSQGwlfnuzCdyy\nF62ARPBopY+Udf90WuioAnwMCeKpSwughQtiue+hMZL77/ZRBIls6Kl0obsXs7X9\nSQ98POyDGCBDTtWTurQ0sR8WNh8M5mQ5Fkzc4P4dyKliPUDqysU0ArSuiYgzNdws\nE3PYJ/HQcu51OyLemGhmW/HGY0dVHLqlCFF1pkgl\n-----END CERTIFICATE-----\n\n# Issuer: CN=GTS Root R2 O=Google Trust Services LLC\n# Subject: CN=GTS Root R2 O=Google Trust Services LLC\n# Label: \"GTS Root R2\"\n# Serial: 146587176055767053814479386953112547951\n# MD5 Fingerprint: 44:ed:9a:0e:a4:09:3b:00:f2:ae:4c:a3:c6:61:b0:8b\n# SHA1 Fingerprint: d2:73:96:2a:2a:5e:39:9f:73:3f:e1:c7:1e:64:3f:03:38:34:fc:4d\n# SHA256 Fingerprint: c4:5d:7b:b0:8e:6d:67:e6:2e:42:35:11:0b:56:4e:5f:78:fd:92:ef:05:8c:84:0a:ea:4e:64:55:d7:58:5c:60\n-----BEGIN CERTIFICATE-----\nMIIFWjCCA0KgAwIBAgIQbkepxlqz5yDFMJo/aFLybzANBgkqhkiG9w0BAQwFADBH\nMQswCQYDVQQGEwJVUzEiMCAGA1UEChMZR29vZ2xlIFRydXN0IFNlcnZpY2VzIExM\nQzEUMBIGA1UEAxMLR1RTIFJvb3QgUjIwHhcNMTYwNjIyMDAwMDAwWhcNMzYwNjIy\nMDAwMDAwWjBHMQswCQYDVQQGEwJVUzEiMCAGA1UEChMZR29vZ2xlIFRydXN0IFNl\ncnZpY2VzIExMQzEUMBIGA1UEAxMLR1RTIFJvb3QgUjIwggIiMA0GCSqGSIb3DQEB\nAQUAA4ICDwAwggIKAoICAQDO3v2m++zsFDQ8BwZabFn3GTXd98GdVarTzTukk3Lv\nCvptnfbwhYBboUhSnznFt+4orO/LdmgUud+tAWyZH8QiHZ/+cnfgLFuv5AS/T3Kg\nGjSY6Dlo7JUle3ah5mm5hRm9iYz+re026nO8/4Piy33B0s5Ks40FnotJk9/BW9Bu\nXvAuMC6C/Pq8tBcKSOWIm8Wba96wyrQD8Nr0kLhlZPdcTK3ofmZemde4wj7I0BOd\nre7kRXuJVfeKH2JShBKzwkCX44ofR5GmdFrS+LFjKBC4swm4VndAoiaYecb+3yXu\nPuWgf9RhD1FLPD+M2uFwdNjCaKH5wQzpoeJ/u1U8dgbuak7MkogwTZq9TwtImoS1\nmKPV+3PBV2HdKFZ1E66HjucMUQkQdYhMvI35ezzUIkgfKtzra7tEscszcTJGr61K\n8YzodDqs5xoic4DSMPclQsciOzsSrZYuxsN2B6ogtzVJV+mSSeh2FnIxZyuWfoqj\nx5RWIr9qS34BIbIjMt/kmkRtWVtd9QCgHJvGeJeNkP+byKq0rxFROV7Z+2et1VsR\nnTKaG73VululycslaVNVJ1zgyjbLiGH7HrfQy+4W+9OmTN6SpdTi3/UGVN4unUu0\nkzCqgc7dGtxRcw1PcOnlthYhGXmy5okLdWTK1au8CcEYof/UVKGFPP0UJAOyh9Ok\ntwIDAQABo0IwQDAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/BAUwAwEB/zAdBgNV\nHQ4EFgQUu//KjiOfT5nK2+JopqUVJxce2Q4wDQYJKoZIhvcNAQEMBQADggIBALZp\n8KZ3/p7uC4Gt4cCpx/k1HUCCq+YEtN/L9x0Pg/B+E02NjO7jMyLDOfxA325BS0JT\nvhaI8dI4XsRomRyYUpOM52jtG2pzegVATX9lO9ZY8c6DR2Dj/5epnGB3GFW1fgiT\nz9D2PGcDFWEJ+YF59exTpJ/JjwGLc8R3dtyDovUMSRqodt6Sm2T4syzFJ9MHwAiA\npJiS4wGWAqoC7o87xdFtCjMwc3i5T1QWvwsHoaRc5svJXISPD+AVdyx+Jn7axEvb\npxZ3B7DNdehyQtaVhJ2Gg/LkkM0JR9SLA3DaWsYDQvTtN6LwG1BUSw7YhN4ZKJmB\nR64JGz9I0cNv4rBgF/XuIwKl2gBbbZCr7qLpGzvpx0QnRY5rn/WkhLx3+WuXrD5R\nRaIRpsyF7gpo8j5QOHokYh4XIDdtak23CZvJ/KRY9bb7nE4Yu5UC56GtmwfuNmsk\n0jmGwZODUNKBRqhfYlcsu2xkiAhu7xNUX90txGdj08+JN7+dIPT7eoOboB6BAFDC\n5AwiWVIQ7UNWhwD4FFKnHYuTjKJNRn8nxnGbJN7k2oaLDX5rIMHAnuFl2GqjpuiF\nizoHCBy69Y9Vmhh1fuXsgWbRIXOhNUQLgD1bnF5vKheW0YMjiGZt5obicDIvUiLn\nyOd/xCxgXS/Dr55FBcOEArf9LAhST4Ldo/DUhgkC\n-----END CERTIFICATE-----\n\n# Issuer: CN=GTS Root R3 O=Google Trust Services LLC\n# Subject: CN=GTS Root R3 O=Google Trust Services LLC\n# Label: \"GTS Root R3\"\n# Serial: 146587176140553309517047991083707763997\n# MD5 Fingerprint: 1a:79:5b:6b:04:52:9c:5d:c7:74:33:1b:25:9a:f9:25\n# SHA1 Fingerprint: 30:d4:24:6f:07:ff:db:91:89:8a:0b:e9:49:66:11:eb:8c:5e:46:e5\n# SHA256 Fingerprint: 15:d5:b8:77:46:19:ea:7d:54:ce:1c:a6:d0:b0:c4:03:e0:37:a9:17:f1:31:e8:a0:4e:1e:6b:7a:71:ba:bc:e5\n-----BEGIN CERTIFICATE-----\nMIICDDCCAZGgAwIBAgIQbkepx2ypcyRAiQ8DVd2NHTAKBggqhkjOPQQDAzBHMQsw\nCQYDVQQGEwJVUzEiMCAGA1UEChMZR29vZ2xlIFRydXN0IFNlcnZpY2VzIExMQzEU\nMBIGA1UEAxMLR1RTIFJvb3QgUjMwHhcNMTYwNjIyMDAwMDAwWhcNMzYwNjIyMDAw\nMDAwWjBHMQswCQYDVQQGEwJVUzEiMCAGA1UEChMZR29vZ2xlIFRydXN0IFNlcnZp\nY2VzIExMQzEUMBIGA1UEAxMLR1RTIFJvb3QgUjMwdjAQBgcqhkjOPQIBBgUrgQQA\nIgNiAAQfTzOHMymKoYTey8chWEGJ6ladK0uFxh1MJ7x/JlFyb+Kf1qPKzEUURout\n736GjOyxfi//qXGdGIRFBEFVbivqJn+7kAHjSxm65FSWRQmx1WyRRK2EE46ajA2A\nDDL24CejQjBAMA4GA1UdDwEB/wQEAwIBBjAPBgNVHRMBAf8EBTADAQH/MB0GA1Ud\nDgQWBBTB8Sa6oC2uhYHP0/EqEr24Cmf9vDAKBggqhkjOPQQDAwNpADBmAjEAgFuk\nfCPAlaUs3L6JbyO5o91lAFJekazInXJ0glMLfalAvWhgxeG4VDvBNhcl2MG9AjEA\nnjWSdIUlUfUk7GRSJFClH9voy8l27OyCbvWFGFPouOOaKaqW04MjyaR7YbPMAuhd\n-----END CERTIFICATE-----\n\n# Issuer: CN=GTS Root R4 O=Google Trust Services LLC\n# Subject: CN=GTS Root R4 O=Google Trust Services LLC\n# Label: \"GTS Root R4\"\n# Serial: 146587176229350439916519468929765261721\n# MD5 Fingerprint: 5d:b6:6a:c4:60:17:24:6a:1a:99:a8:4b:ee:5e:b4:26\n# SHA1 Fingerprint: 2a:1d:60:27:d9:4a:b1:0a:1c:4d:91:5c:cd:33:a0:cb:3e:2d:54:cb\n# SHA256 Fingerprint: 71:cc:a5:39:1f:9e:79:4b:04:80:25:30:b3:63:e1:21:da:8a:30:43:bb:26:66:2f:ea:4d:ca:7f:c9:51:a4:bd\n-----BEGIN CERTIFICATE-----\nMIICCjCCAZGgAwIBAgIQbkepyIuUtui7OyrYorLBmTAKBggqhkjOPQQDAzBHMQsw\nCQYDVQQGEwJVUzEiMCAGA1UEChMZR29vZ2xlIFRydXN0IFNlcnZpY2VzIExMQzEU\nMBIGA1UEAxMLR1RTIFJvb3QgUjQwHhcNMTYwNjIyMDAwMDAwWhcNMzYwNjIyMDAw\nMDAwWjBHMQswCQYDVQQGEwJVUzEiMCAGA1UEChMZR29vZ2xlIFRydXN0IFNlcnZp\nY2VzIExMQzEUMBIGA1UEAxMLR1RTIFJvb3QgUjQwdjAQBgcqhkjOPQIBBgUrgQQA\nIgNiAATzdHOnaItgrkO4NcWBMHtLSZ37wWHO5t5GvWvVYRg1rkDdc/eJkTBa6zzu\nhXyiQHY7qca4R9gq55KRanPpsXI5nymfopjTX15YhmUPoYRlBtHci8nHc8iMai/l\nxKvRHYqjQjBAMA4GA1UdDwEB/wQEAwIBBjAPBgNVHRMBAf8EBTADAQH/MB0GA1Ud\nDgQWBBSATNbrdP9JNqPV2Py1PsVq8JQdjDAKBggqhkjOPQQDAwNnADBkAjBqUFJ0\nCMRw3J5QdCHojXohw0+WbhXRIjVhLfoIN+4Zba3bssx9BzT1YBkstTTZbyACMANx\nsbqjYAuG7ZoIapVon+Kz4ZNkfF6Tpt95LY2F45TPI11xzPKwTdb+mciUqXWi4w==\n-----END CERTIFICATE-----\n\n# Issuer: CN=UCA Global G2 Root O=UniTrust\n# Subject: CN=UCA Global G2 Root O=UniTrust\n# Label: \"UCA Global G2 Root\"\n# Serial: 124779693093741543919145257850076631279\n# MD5 Fingerprint: 80:fe:f0:c4:4a:f0:5c:62:32:9f:1c:ba:78:a9:50:f8\n# SHA1 Fingerprint: 28:f9:78:16:19:7a:ff:18:25:18:aa:44:fe:c1:a0:ce:5c:b6:4c:8a\n# SHA256 Fingerprint: 9b:ea:11:c9:76:fe:01:47:64:c1:be:56:a6:f9:14:b5:a5:60:31:7a:bd:99:88:39:33:82:e5:16:1a:a0:49:3c\n-----BEGIN CERTIFICATE-----\nMIIFRjCCAy6gAwIBAgIQXd+x2lqj7V2+WmUgZQOQ7zANBgkqhkiG9w0BAQsFADA9\nMQswCQYDVQQGEwJDTjERMA8GA1UECgwIVW5pVHJ1c3QxGzAZBgNVBAMMElVDQSBH\nbG9iYWwgRzIgUm9vdDAeFw0xNjAzMTEwMDAwMDBaFw00MDEyMzEwMDAwMDBaMD0x\nCzAJBgNVBAYTAkNOMREwDwYDVQQKDAhVbmlUcnVzdDEbMBkGA1UEAwwSVUNBIEds\nb2JhbCBHMiBSb290MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAxeYr\nb3zvJgUno4Ek2m/LAfmZmqkywiKHYUGRO8vDaBsGxUypK8FnFyIdK+35KYmToni9\nkmugow2ifsqTs6bRjDXVdfkX9s9FxeV67HeToI8jrg4aA3++1NDtLnurRiNb/yzm\nVHqUwCoV8MmNsHo7JOHXaOIxPAYzRrZUEaalLyJUKlgNAQLx+hVRZ2zA+te2G3/R\nVogvGjqNO7uCEeBHANBSh6v7hn4PJGtAnTRnvI3HLYZveT6OqTwXS3+wmeOwcWDc\nC/Vkw85DvG1xudLeJ1uK6NjGruFZfc8oLTW4lVYa8bJYS7cSN8h8s+1LgOGN+jIj\ntm+3SJUIsUROhYw6AlQgL9+/V087OpAh18EmNVQg7Mc/R+zvWr9LesGtOxdQXGLY\nD0tK3Cv6brxzks3sx1DoQZbXqX5t2Okdj4q1uViSukqSKwxW/YDrCPBeKW4bHAyv\nj5OJrdu9o54hyokZ7N+1wxrrFv54NkzWbtA+FxyQF2smuvt6L78RHBgOLXMDj6Dl\nNaBa4kx1HXHhOThTeEDMg5PXCp6dW4+K5OXgSORIskfNTip1KnvyIvbJvgmRlld6\niIis7nCs+dwp4wwcOxJORNanTrAmyPPZGpeRaOrvjUYG0lZFWJo8DA+DuAUlwznP\nO6Q0ibd5Ei9Hxeepl2n8pndntd978XplFeRhVmUCAwEAAaNCMEAwDgYDVR0PAQH/\nBAQDAgEGMA8GA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFIHEjMz15DD/pQwIX4wV\nZyF0Ad/fMA0GCSqGSIb3DQEBCwUAA4ICAQATZSL1jiutROTL/7lo5sOASD0Ee/oj\nL3rtNtqyzm325p7lX1iPyzcyochltq44PTUbPrw7tgTQvPlJ9Zv3hcU2tsu8+Mg5\n1eRfB70VVJd0ysrtT7q6ZHafgbiERUlMjW+i67HM0cOU2kTC5uLqGOiiHycFutfl\n1qnN3e92mI0ADs0b+gO3joBYDic/UvuUospeZcnWhNq5NXHzJsBPd+aBJ9J3O5oU\nb3n09tDh05S60FdRvScFDcH9yBIw7m+NESsIndTUv4BFFJqIRNow6rSn4+7vW4LV\nPtateJLbXDzz2K36uGt/xDYotgIVilQsnLAXc47QN6MUPJiVAAwpBVueSUmxX8fj\ny88nZY41F7dXyDDZQVu5FLbowg+UMaeUmMxq67XhJ/UQqAHojhJi6IjMtX9Gl8Cb\nEGY4GjZGXyJoPd/JxhMnq1MGrKI8hgZlb7F+sSlEmqO6SWkoaY/X5V+tBIZkbxqg\nDMUIYs6Ao9Dz7GjevjPHF1t/gMRMTLGmhIrDO7gJzRSBuhjjVFc2/tsvfEehOjPI\n+Vg7RE+xygKJBJYoaMVLuCaJu9YzL1DV/pqJuhgyklTGW+Cd+V7lDSKb9triyCGy\nYiGqhkCyLmTTX8jjfhFnRR8F/uOi77Oos/N9j/gMHyIfLXC0uAE0djAA5SN4p1bX\nUB+K+wb1whnw0A==\n-----END CERTIFICATE-----\n\n# Issuer: CN=UCA Extended Validation Root O=UniTrust\n# Subject: CN=UCA Extended Validation Root O=UniTrust\n# Label: \"UCA Extended Validation Root\"\n# Serial: 106100277556486529736699587978573607008\n# MD5 Fingerprint: a1:f3:5f:43:c6:34:9b:da:bf:8c:7e:05:53:ad:96:e2\n# SHA1 Fingerprint: a3:a1:b0:6f:24:61:23:4a:e3:36:a5:c2:37:fc:a6:ff:dd:f0:d7:3a\n# SHA256 Fingerprint: d4:3a:f9:b3:54:73:75:5c:96:84:fc:06:d7:d8:cb:70:ee:5c:28:e7:73:fb:29:4e:b4:1e:e7:17:22:92:4d:24\n-----BEGIN CERTIFICATE-----\nMIIFWjCCA0KgAwIBAgIQT9Irj/VkyDOeTzRYZiNwYDANBgkqhkiG9w0BAQsFADBH\nMQswCQYDVQQGEwJDTjERMA8GA1UECgwIVW5pVHJ1c3QxJTAjBgNVBAMMHFVDQSBF\neHRlbmRlZCBWYWxpZGF0aW9uIFJvb3QwHhcNMTUwMzEzMDAwMDAwWhcNMzgxMjMx\nMDAwMDAwWjBHMQswCQYDVQQGEwJDTjERMA8GA1UECgwIVW5pVHJ1c3QxJTAjBgNV\nBAMMHFVDQSBFeHRlbmRlZCBWYWxpZGF0aW9uIFJvb3QwggIiMA0GCSqGSIb3DQEB\nAQUAA4ICDwAwggIKAoICAQCpCQcoEwKwmeBkqh5DFnpzsZGgdT6o+uM4AHrsiWog\nD4vFsJszA1qGxliG1cGFu0/GnEBNyr7uaZa4rYEwmnySBesFK5pI0Lh2PpbIILvS\nsPGP2KxFRv+qZ2C0d35qHzwaUnoEPQc8hQ2E0B92CvdqFN9y4zR8V05WAT558aop\nO2z6+I9tTcg1367r3CTueUWnhbYFiN6IXSV8l2RnCdm/WhUFhvMJHuxYMjMR83dk\nsHYf5BA1FxvyDrFspCqjc/wJHx4yGVMR59mzLC52LqGj3n5qiAno8geK+LLNEOfi\nc0CTuwjRP+H8C5SzJe98ptfRr5//lpr1kXuYC3fUfugH0mK1lTnj8/FtDw5lhIpj\nVMWAtuCeS31HJqcBCF3RiJ7XwzJE+oJKCmhUfzhTA8ykADNkUVkLo4KRel7sFsLz\nKuZi2irbWWIQJUoqgQtHB0MGcIfS+pMRKXpITeuUx3BNr2fVUbGAIAEBtHoIppB/\nTuDvB0GHr2qlXov7z1CymlSvw4m6WC31MJixNnI5fkkE/SmnTHnkBVfblLkWU41G\nsx2VYVdWf6/wFlthWG82UBEL2KwrlRYaDh8IzTY0ZRBiZtWAXxQgXy0MoHgKaNYs\n1+lvK9JKBZP8nm9rZ/+I8U6laUpSNwXqxhaN0sSZ0YIrO7o1dfdRUVjzyAfd5LQD\nfwIDAQABo0IwQDAdBgNVHQ4EFgQU2XQ65DA9DfcS3H5aBZ8eNJr34RQwDwYDVR0T\nAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAYYwDQYJKoZIhvcNAQELBQADggIBADaN\nl8xCFWQpN5smLNb7rhVpLGsaGvdftvkHTFnq88nIua7Mui563MD1sC3AO6+fcAUR\nap8lTwEpcOPlDOHqWnzcSbvBHiqB9RZLcpHIojG5qtr8nR/zXUACE/xOHAbKsxSQ\nVBcZEhrxH9cMaVr2cXj0lH2RC47skFSOvG+hTKv8dGT9cZr4QQehzZHkPJrgmzI5\nc6sq1WnIeJEmMX3ixzDx/BR4dxIOE/TdFpS/S2d7cFOFyrC78zhNLJA5wA3CXWvp\n4uXViI3WLL+rG761KIcSF3Ru/H38j9CHJrAb+7lsq+KePRXBOy5nAliRn+/4Qh8s\nt2j1da3Ptfb/EX3C8CSlrdP6oDyp+l3cpaDvRKS+1ujl5BOWF3sGPjLtx7dCvHaj\n2GU4Kzg1USEODm8uNBNA4StnDG1KQTAYI1oyVZnJF+A83vbsea0rWBmirSwiGpWO\nvpaQXUJXxPkUAzUrHC1RVwinOt4/5Mi0A3PCwSaAuwtCH60NryZy2sy+s6ODWA2C\nxR9GUeOcGMyNm43sSet1UNWMKFnKdDTajAshqx7qG+XH/RU+wBeq+yNuJkbL+vmx\ncmtpzyKEC2IPrNkZAJSidjzULZrtBJ4tBmIQN1IchXIbJ+XMxjHsN+xjWZsLHXbM\nfjKaiJUINlK73nZfdklJrX+9ZSCyycErdhh2n1ax\n-----END CERTIFICATE-----\n\n# Issuer: CN=Certigna Root CA O=Dhimyotis OU=0002 48146308100036\n# Subject: CN=Certigna Root CA O=Dhimyotis OU=0002 48146308100036\n# Label: \"Certigna Root CA\"\n# Serial: 269714418870597844693661054334862075617\n# MD5 Fingerprint: 0e:5c:30:62:27:eb:5b:bc:d7:ae:62:ba:e9:d5:df:77\n# SHA1 Fingerprint: 2d:0d:52:14:ff:9e:ad:99:24:01:74:20:47:6e:6c:85:27:27:f5:43\n# SHA256 Fingerprint: d4:8d:3d:23:ee:db:50:a4:59:e5:51:97:60:1c:27:77:4b:9d:7b:18:c9:4d:5a:05:95:11:a1:02:50:b9:31:68\n-----BEGIN CERTIFICATE-----\nMIIGWzCCBEOgAwIBAgIRAMrpG4nxVQMNo+ZBbcTjpuEwDQYJKoZIhvcNAQELBQAw\nWjELMAkGA1UEBhMCRlIxEjAQBgNVBAoMCURoaW15b3RpczEcMBoGA1UECwwTMDAw\nMiA0ODE0NjMwODEwMDAzNjEZMBcGA1UEAwwQQ2VydGlnbmEgUm9vdCBDQTAeFw0x\nMzEwMDEwODMyMjdaFw0zMzEwMDEwODMyMjdaMFoxCzAJBgNVBAYTAkZSMRIwEAYD\nVQQKDAlEaGlteW90aXMxHDAaBgNVBAsMEzAwMDIgNDgxNDYzMDgxMDAwMzYxGTAX\nBgNVBAMMEENlcnRpZ25hIFJvb3QgQ0EwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAw\nggIKAoICAQDNGDllGlmx6mQWDoyUJJV8g9PFOSbcDO8WV43X2KyjQn+Cyu3NW9sO\nty3tRQgXstmzy9YXUnIo245Onoq2C/mehJpNdt4iKVzSs9IGPjA5qXSjklYcoW9M\nCiBtnyN6tMbaLOQdLNyzKNAT8kxOAkmhVECe5uUFoC2EyP+YbNDrihqECB63aCPu\nI9Vwzm1RaRDuoXrC0SIxwoKF0vJVdlB8JXrJhFwLrN1CTivngqIkicuQstDuI7pm\nTLtipPlTWmR7fJj6o0ieD5Wupxj0auwuA0Wv8HT4Ks16XdG+RCYyKfHx9WzMfgIh\nC59vpD++nVPiz32pLHxYGpfhPTc3GGYo0kDFUYqMwy3OU4gkWGQwFsWq4NYKpkDf\nePb1BHxpE4S80dGnBs8B92jAqFe7OmGtBIyT46388NtEbVncSVmurJqZNjBBe3Yz\nIoejwpKGbvlw7q6Hh5UbxHq9MfPU0uWZ/75I7HX1eBYdpnDBfzwboZL7z8g81sWT\nCo/1VTp2lc5ZmIoJlXcymoO6LAQ6l73UL77XbJuiyn1tJslV1c/DeVIICZkHJC1k\nJWumIWmbat10TWuXekG9qxf5kBdIjzb5LdXF2+6qhUVB+s06RbFo5jZMm5BX7CO5\nhwjCxAnxl4YqKE3idMDaxIzb3+KhF1nOJFl0Mdp//TBt2dzhauH8XwIDAQABo4IB\nGjCCARYwDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAQYwHQYDVR0OBBYE\nFBiHVuBud+4kNTxOc5of1uHieX4rMB8GA1UdIwQYMBaAFBiHVuBud+4kNTxOc5of\n1uHieX4rMEQGA1UdIAQ9MDswOQYEVR0gADAxMC8GCCsGAQUFBwIBFiNodHRwczov\nL3d3d3cuY2VydGlnbmEuZnIvYXV0b3JpdGVzLzBtBgNVHR8EZjBkMC+gLaArhilo\ndHRwOi8vY3JsLmNlcnRpZ25hLmZyL2NlcnRpZ25hcm9vdGNhLmNybDAxoC+gLYYr\naHR0cDovL2NybC5kaGlteW90aXMuY29tL2NlcnRpZ25hcm9vdGNhLmNybDANBgkq\nhkiG9w0BAQsFAAOCAgEAlLieT/DjlQgi581oQfccVdV8AOItOoldaDgvUSILSo3L\n6btdPrtcPbEo/uRTVRPPoZAbAh1fZkYJMyjhDSSXcNMQH+pkV5a7XdrnxIxPTGRG\nHVyH41neQtGbqH6mid2PHMkwgu07nM3A6RngatgCdTer9zQoKJHyBApPNeNgJgH6\n0BGM+RFq7q89w1DTj18zeTyGqHNFkIwgtnJzFyO+B2XleJINugHA64wcZr+shncB\nlA2c5uk5jR+mUYyZDDl34bSb+hxnV29qao6pK0xXeXpXIs/NX2NGjVxZOob4Mkdi\no2cNGJHc+6Zr9UhhcyNZjgKnvETq9Emd8VRY+WCv2hikLyhF3HqgiIZd8zvn/yk1\ngPxkQ5Tm4xxvvq0OKmOZK8l+hfZx6AYDlf7ej0gcWtSS6Cvu5zHbugRqh5jnxV/v\nfaci9wHYTfmJ0A6aBVmknpjZbyvKcL5kwlWj9Omvw5Ip3IgWJJk8jSaYtlu3zM63\nNwf9JtmYhST/WSMDmu2dnajkXjjO11INb9I/bbEFa0nOipFGc/T2L/Coc3cOZayh\njWZSaX5LaAzHHjcng6WMxwLkFM1JAbBzs/3GkDpv0mztO+7skb6iQ12LAEpmJURw\n3kAP+HwV96LOPNdeE4yBFxgX0b3xdxA61GU5wSesVywlVP+i2k+KYTlerj1KjL0=\n-----END CERTIFICATE-----\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/certifi/core.py",
    "content": "#!/usr/bin/env python\n# -*- coding: utf-8 -*-\n\n\"\"\"\ncertifi.py\n~~~~~~~~~~\n\nThis module returns the installation location of cacert.pem.\n\"\"\"\nimport os\n\n\ndef where():\n    f = os.path.dirname(__file__)\n\n    return os.path.join(f, 'cacert.pem')\n\n\nif __name__ == '__main__':\n    print(where())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/__init__.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n\nfrom .compat import PY2, PY3\nfrom .universaldetector import UniversalDetector\nfrom .version import __version__, VERSION\n\n\ndef detect(byte_str):\n    \"\"\"\n    Detect the encoding of the given byte string.\n\n    :param byte_str:     The byte sequence to examine.\n    :type byte_str:      ``bytes`` or ``bytearray``\n    \"\"\"\n    if not isinstance(byte_str, bytearray):\n        if not isinstance(byte_str, bytes):\n            raise TypeError('Expected object of type bytes or bytearray, got: '\n                            '{0}'.format(type(byte_str)))\n        else:\n            byte_str = bytearray(byte_str)\n    detector = UniversalDetector()\n    detector.feed(byte_str)\n    return detector.close()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/big5freq.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n# Big5 frequency table\n# by Taiwan's Mandarin Promotion Council\n# <http://www.edu.tw:81/mandr/>\n#\n# 128  --> 0.42261\n# 256  --> 0.57851\n# 512  --> 0.74851\n# 1024 --> 0.89384\n# 2048 --> 0.97583\n#\n# Ideal Distribution Ratio = 0.74851/(1-0.74851) =2.98\n# Random Distribution Ration = 512/(5401-512)=0.105\n#\n# Typical Distribution Ratio about 25% of Ideal one, still much higher than RDR\n\nBIG5_TYPICAL_DISTRIBUTION_RATIO = 0.75\n\n#Char to FreqOrder table\nBIG5_TABLE_SIZE = 5376\n\nBIG5_CHAR_TO_FREQ_ORDER = (\n   1,1801,1506, 255,1431, 198,   9,  82,   6,5008, 177, 202,3681,1256,2821, 110, #   16\n3814,  33,3274, 261,  76,  44,2114,  16,2946,2187,1176, 659,3971,  26,3451,2653, #   32\n1198,3972,3350,4202, 410,2215, 302, 590, 361,1964,   8, 204,  58,4510,5009,1932, #   48\n  63,5010,5011, 317,1614,  75, 222, 159,4203,2417,1480,5012,3555,3091, 224,2822, #   64\n3682,   3,  10,3973,1471,  29,2787,1135,2866,1940, 873, 130,3275,1123, 312,5013, #   80\n4511,2052, 507, 252, 682,5014, 142,1915, 124, 206,2947,  34,3556,3204,  64, 604, #   96\n5015,2501,1977,1978, 155,1991, 645, 641,1606,5016,3452, 337,  72, 406,5017,  80, #  112\n 630, 238,3205,1509, 263, 939,1092,2654, 756,1440,1094,3453, 449,  69,2987, 591, #  128\n 179,2096, 471, 115,2035,1844,  60,  50,2988, 134, 806,1869, 734,2036,3454, 180, #  144\n 995,1607, 156, 537,2907, 688,5018, 319,1305, 779,2145, 514,2379, 298,4512, 359, #  160\n2502,  90,2716,1338, 663,  11, 906,1099,2553,  20,2441, 182, 532,1716,5019, 732, #  176\n1376,4204,1311,1420,3206,  25,2317,1056, 113, 399, 382,1950, 242,3455,2474, 529, #  192\n3276, 475,1447,3683,5020, 117,  21, 656, 810,1297,2300,2334,3557,5021, 126,4205, #  208\n 706, 456, 150, 613,4513,  71,1118,2037,4206, 145,3092,  85, 835, 486,2115,1246, #  224\n1426, 428, 727,1285,1015, 800, 106, 623, 303,1281,5022,2128,2359, 347,3815, 221, #  240\n3558,3135,5023,1956,1153,4207,  83, 296,1199,3093, 192, 624,  93,5024, 822,1898, #  256\n2823,3136, 795,2065, 991,1554,1542,1592,  27,  43,2867, 859, 139,1456, 860,4514, #  272\n 437, 712,3974, 164,2397,3137, 695, 211,3037,2097, 195,3975,1608,3559,3560,3684, #  288\n3976, 234, 811,2989,2098,3977,2233,1441,3561,1615,2380, 668,2077,1638, 305, 228, #  304\n1664,4515, 467, 415,5025, 262,2099,1593, 239, 108, 300, 200,1033, 512,1247,2078, #  320\n5026,5027,2176,3207,3685,2682, 593, 845,1062,3277,  88,1723,2038,3978,1951, 212, #  336\n 266, 152, 149, 468,1899,4208,4516,  77, 187,5028,3038,  37,   5,2990,5029,3979, #  352\n5030,5031,  39,2524,4517,2908,3208,2079,  55, 148,  74,4518, 545, 483,1474,1029, #  368\n1665, 217,1870,1531,3138,1104,2655,4209,  24, 172,3562, 900,3980,3563,3564,4519, #  384\n  32,1408,2824,1312, 329, 487,2360,2251,2717, 784,2683,   4,3039,3351,1427,1789, #  400\n 188, 109, 499,5032,3686,1717,1790, 888,1217,3040,4520,5033,3565,5034,3352,1520, #  416\n3687,3981, 196,1034, 775,5035,5036, 929,1816, 249, 439,  38,5037,1063,5038, 794, #  432\n3982,1435,2301,  46, 178,3278,2066,5039,2381,5040, 214,1709,4521, 804,  35, 707, #  448\n 324,3688,1601,2554, 140, 459,4210,5041,5042,1365, 839, 272, 978,2262,2580,3456, #  464\n2129,1363,3689,1423, 697, 100,3094,  48,  70,1231, 495,3139,2196,5043,1294,5044, #  480\n2080, 462, 586,1042,3279, 853, 256, 988, 185,2382,3457,1698, 434,1084,5045,3458, #  496\n 314,2625,2788,4522,2335,2336, 569,2285, 637,1817,2525, 757,1162,1879,1616,3459, #  512\n 287,1577,2116, 768,4523,1671,2868,3566,2526,1321,3816, 909,2418,5046,4211, 933, #  528\n3817,4212,2053,2361,1222,4524, 765,2419,1322, 786,4525,5047,1920,1462,1677,2909, #  544\n1699,5048,4526,1424,2442,3140,3690,2600,3353,1775,1941,3460,3983,4213, 309,1369, #  560\n1130,2825, 364,2234,1653,1299,3984,3567,3985,3986,2656, 525,1085,3041, 902,2001, #  576\n1475, 964,4527, 421,1845,1415,1057,2286, 940,1364,3141, 376,4528,4529,1381,   7, #  592\n2527, 983,2383, 336,1710,2684,1846, 321,3461, 559,1131,3042,2752,1809,1132,1313, #  608\n 265,1481,1858,5049, 352,1203,2826,3280, 167,1089, 420,2827, 776, 792,1724,3568, #  624\n4214,2443,3281,5050,4215,5051, 446, 229, 333,2753, 901,3818,1200,1557,4530,2657, #  640\n1921, 395,2754,2685,3819,4216,1836, 125, 916,3209,2626,4531,5052,5053,3820,5054, #  656\n5055,5056,4532,3142,3691,1133,2555,1757,3462,1510,2318,1409,3569,5057,2146, 438, #  672\n2601,2910,2384,3354,1068, 958,3043, 461, 311,2869,2686,4217,1916,3210,4218,1979, #  688\n 383, 750,2755,2627,4219, 274, 539, 385,1278,1442,5058,1154,1965, 384, 561, 210, #  704\n  98,1295,2556,3570,5059,1711,2420,1482,3463,3987,2911,1257, 129,5060,3821, 642, #  720\n 523,2789,2790,2658,5061, 141,2235,1333,  68, 176, 441, 876, 907,4220, 603,2602, #  736\n 710, 171,3464, 404, 549,  18,3143,2398,1410,3692,1666,5062,3571,4533,2912,4534, #  752\n5063,2991, 368,5064, 146, 366,  99, 871,3693,1543, 748, 807,1586,1185,  22,2263, #  768\n 379,3822,3211,5065,3212, 505,1942,2628,1992,1382,2319,5066, 380,2362, 218, 702, #  784\n1818,1248,3465,3044,3572,3355,3282,5067,2992,3694, 930,3283,3823,5068,  59,5069, #  800\n 585, 601,4221, 497,3466,1112,1314,4535,1802,5070,1223,1472,2177,5071, 749,1837, #  816\n 690,1900,3824,1773,3988,1476, 429,1043,1791,2236,2117, 917,4222, 447,1086,1629, #  832\n5072, 556,5073,5074,2021,1654, 844,1090, 105, 550, 966,1758,2828,1008,1783, 686, #  848\n1095,5075,2287, 793,1602,5076,3573,2603,4536,4223,2948,2302,4537,3825, 980,2503, #  864\n 544, 353, 527,4538, 908,2687,2913,5077, 381,2629,1943,1348,5078,1341,1252, 560, #  880\n3095,5079,3467,2870,5080,2054, 973, 886,2081, 143,4539,5081,5082, 157,3989, 496, #  896\n4224,  57, 840, 540,2039,4540,4541,3468,2118,1445, 970,2264,1748,1966,2082,4225, #  912\n3144,1234,1776,3284,2829,3695, 773,1206,2130,1066,2040,1326,3990,1738,1725,4226, #  928\n 279,3145,  51,1544,2604, 423,1578,2131,2067, 173,4542,1880,5083,5084,1583, 264, #  944\n 610,3696,4543,2444, 280, 154,5085,5086,5087,1739, 338,1282,3096, 693,2871,1411, #  960\n1074,3826,2445,5088,4544,5089,5090,1240, 952,2399,5091,2914,1538,2688, 685,1483, #  976\n4227,2475,1436, 953,4228,2055,4545, 671,2400,  79,4229,2446,3285, 608, 567,2689, #  992\n3469,4230,4231,1691, 393,1261,1792,2401,5092,4546,5093,5094,5095,5096,1383,1672, # 1008\n3827,3213,1464, 522,1119, 661,1150, 216, 675,4547,3991,1432,3574, 609,4548,2690, # 1024\n2402,5097,5098,5099,4232,3045,   0,5100,2476, 315, 231,2447, 301,3356,4549,2385, # 1040\n5101, 233,4233,3697,1819,4550,4551,5102,  96,1777,1315,2083,5103, 257,5104,1810, # 1056\n3698,2718,1139,1820,4234,2022,1124,2164,2791,1778,2659,5105,3097, 363,1655,3214, # 1072\n5106,2993,5107,5108,5109,3992,1567,3993, 718, 103,3215, 849,1443, 341,3357,2949, # 1088\n1484,5110,1712, 127,  67, 339,4235,2403, 679,1412, 821,5111,5112, 834, 738, 351, # 1104\n2994,2147, 846, 235,1497,1881, 418,1993,3828,2719, 186,1100,2148,2756,3575,1545, # 1120\n1355,2950,2872,1377, 583,3994,4236,2581,2995,5113,1298,3699,1078,2557,3700,2363, # 1136\n  78,3829,3830, 267,1289,2100,2002,1594,4237, 348, 369,1274,2197,2178,1838,4552, # 1152\n1821,2830,3701,2757,2288,2003,4553,2951,2758, 144,3358, 882,4554,3995,2759,3470, # 1168\n4555,2915,5114,4238,1726, 320,5115,3996,3046, 788,2996,5116,2831,1774,1327,2873, # 1184\n3997,2832,5117,1306,4556,2004,1700,3831,3576,2364,2660, 787,2023, 506, 824,3702, # 1200\n 534, 323,4557,1044,3359,2024,1901, 946,3471,5118,1779,1500,1678,5119,1882,4558, # 1216\n 165, 243,4559,3703,2528, 123, 683,4239, 764,4560,  36,3998,1793, 589,2916, 816, # 1232\n 626,1667,3047,2237,1639,1555,1622,3832,3999,5120,4000,2874,1370,1228,1933, 891, # 1248\n2084,2917, 304,4240,5121, 292,2997,2720,3577, 691,2101,4241,1115,4561, 118, 662, # 1264\n5122, 611,1156, 854,2386,1316,2875,   2, 386, 515,2918,5123,5124,3286, 868,2238, # 1280\n1486, 855,2661, 785,2216,3048,5125,1040,3216,3578,5126,3146, 448,5127,1525,5128, # 1296\n2165,4562,5129,3833,5130,4242,2833,3579,3147, 503, 818,4001,3148,1568, 814, 676, # 1312\n1444, 306,1749,5131,3834,1416,1030, 197,1428, 805,2834,1501,4563,5132,5133,5134, # 1328\n1994,5135,4564,5136,5137,2198,  13,2792,3704,2998,3149,1229,1917,5138,3835,2132, # 1344\n5139,4243,4565,2404,3580,5140,2217,1511,1727,1120,5141,5142, 646,3836,2448, 307, # 1360\n5143,5144,1595,3217,5145,5146,5147,3705,1113,1356,4002,1465,2529,2530,5148, 519, # 1376\n5149, 128,2133,  92,2289,1980,5150,4003,1512, 342,3150,2199,5151,2793,2218,1981, # 1392\n3360,4244, 290,1656,1317, 789, 827,2365,5152,3837,4566, 562, 581,4004,5153, 401, # 1408\n4567,2252,  94,4568,5154,1399,2794,5155,1463,2025,4569,3218,1944,5156, 828,1105, # 1424\n4245,1262,1394,5157,4246, 605,4570,5158,1784,2876,5159,2835, 819,2102, 578,2200, # 1440\n2952,5160,1502, 436,3287,4247,3288,2836,4005,2919,3472,3473,5161,2721,2320,5162, # 1456\n5163,2337,2068,  23,4571, 193, 826,3838,2103, 699,1630,4248,3098, 390,1794,1064, # 1472\n3581,5164,1579,3099,3100,1400,5165,4249,1839,1640,2877,5166,4572,4573, 137,4250, # 1488\n 598,3101,1967, 780, 104, 974,2953,5167, 278, 899, 253, 402, 572, 504, 493,1339, # 1504\n5168,4006,1275,4574,2582,2558,5169,3706,3049,3102,2253, 565,1334,2722, 863,  41, # 1520\n5170,5171,4575,5172,1657,2338,  19, 463,2760,4251, 606,5173,2999,3289,1087,2085, # 1536\n1323,2662,3000,5174,1631,1623,1750,4252,2691,5175,2878, 791,2723,2663,2339, 232, # 1552\n2421,5176,3001,1498,5177,2664,2630, 755,1366,3707,3290,3151,2026,1609, 119,1918, # 1568\n3474, 862,1026,4253,5178,4007,3839,4576,4008,4577,2265,1952,2477,5179,1125, 817, # 1584\n4254,4255,4009,1513,1766,2041,1487,4256,3050,3291,2837,3840,3152,5180,5181,1507, # 1600\n5182,2692, 733,  40,1632,1106,2879, 345,4257, 841,2531, 230,4578,3002,1847,3292, # 1616\n3475,5183,1263, 986,3476,5184, 735, 879, 254,1137, 857, 622,1300,1180,1388,1562, # 1632\n4010,4011,2954, 967,2761,2665,1349, 592,2134,1692,3361,3003,1995,4258,1679,4012, # 1648\n1902,2188,5185, 739,3708,2724,1296,1290,5186,4259,2201,2202,1922,1563,2605,2559, # 1664\n1871,2762,3004,5187, 435,5188, 343,1108, 596,  17,1751,4579,2239,3477,3709,5189, # 1680\n4580, 294,3582,2955,1693, 477, 979, 281,2042,3583, 643,2043,3710,2631,2795,2266, # 1696\n1031,2340,2135,2303,3584,4581, 367,1249,2560,5190,3585,5191,4582,1283,3362,2005, # 1712\n 240,1762,3363,4583,4584, 836,1069,3153, 474,5192,2149,2532, 268,3586,5193,3219, # 1728\n1521,1284,5194,1658,1546,4260,5195,3587,3588,5196,4261,3364,2693,1685,4262, 961, # 1744\n1673,2632, 190,2006,2203,3841,4585,4586,5197, 570,2504,3711,1490,5198,4587,2633, # 1760\n3293,1957,4588, 584,1514, 396,1045,1945,5199,4589,1968,2449,5200,5201,4590,4013, # 1776\n 619,5202,3154,3294, 215,2007,2796,2561,3220,4591,3221,4592, 763,4263,3842,4593, # 1792\n5203,5204,1958,1767,2956,3365,3712,1174, 452,1477,4594,3366,3155,5205,2838,1253, # 1808\n2387,2189,1091,2290,4264, 492,5206, 638,1169,1825,2136,1752,4014, 648, 926,1021, # 1824\n1324,4595, 520,4596, 997, 847,1007, 892,4597,3843,2267,1872,3713,2405,1785,4598, # 1840\n1953,2957,3103,3222,1728,4265,2044,3714,4599,2008,1701,3156,1551,  30,2268,4266, # 1856\n5207,2027,4600,3589,5208, 501,5209,4267, 594,3478,2166,1822,3590,3479,3591,3223, # 1872\n 829,2839,4268,5210,1680,3157,1225,4269,5211,3295,4601,4270,3158,2341,5212,4602, # 1888\n4271,5213,4015,4016,5214,1848,2388,2606,3367,5215,4603, 374,4017, 652,4272,4273, # 1904\n 375,1140, 798,5216,5217,5218,2366,4604,2269, 546,1659, 138,3051,2450,4605,5219, # 1920\n2254, 612,1849, 910, 796,3844,1740,1371, 825,3845,3846,5220,2920,2562,5221, 692, # 1936\n 444,3052,2634, 801,4606,4274,5222,1491, 244,1053,3053,4275,4276, 340,5223,4018, # 1952\n1041,3005, 293,1168,  87,1357,5224,1539, 959,5225,2240, 721, 694,4277,3847, 219, # 1968\n1478, 644,1417,3368,2666,1413,1401,1335,1389,4019,5226,5227,3006,2367,3159,1826, # 1984\n 730,1515, 184,2840,  66,4607,5228,1660,2958, 246,3369, 378,1457, 226,3480, 975, # 2000\n4020,2959,1264,3592, 674, 696,5229, 163,5230,1141,2422,2167, 713,3593,3370,4608, # 2016\n4021,5231,5232,1186,  15,5233,1079,1070,5234,1522,3224,3594, 276,1050,2725, 758, # 2032\n1126, 653,2960,3296,5235,2342, 889,3595,4022,3104,3007, 903,1250,4609,4023,3481, # 2048\n3596,1342,1681,1718, 766,3297, 286,  89,2961,3715,5236,1713,5237,2607,3371,3008, # 2064\n5238,2962,2219,3225,2880,5239,4610,2505,2533, 181, 387,1075,4024, 731,2190,3372, # 2080\n5240,3298, 310, 313,3482,2304, 770,4278,  54,3054, 189,4611,3105,3848,4025,5241, # 2096\n1230,1617,1850, 355,3597,4279,4612,3373, 111,4280,3716,1350,3160,3483,3055,4281, # 2112\n2150,3299,3598,5242,2797,4026,4027,3009, 722,2009,5243,1071, 247,1207,2343,2478, # 2128\n1378,4613,2010, 864,1437,1214,4614, 373,3849,1142,2220, 667,4615, 442,2763,2563, # 2144\n3850,4028,1969,4282,3300,1840, 837, 170,1107, 934,1336,1883,5244,5245,2119,4283, # 2160\n2841, 743,1569,5246,4616,4284, 582,2389,1418,3484,5247,1803,5248, 357,1395,1729, # 2176\n3717,3301,2423,1564,2241,5249,3106,3851,1633,4617,1114,2086,4285,1532,5250, 482, # 2192\n2451,4618,5251,5252,1492, 833,1466,5253,2726,3599,1641,2842,5254,1526,1272,3718, # 2208\n4286,1686,1795, 416,2564,1903,1954,1804,5255,3852,2798,3853,1159,2321,5256,2881, # 2224\n4619,1610,1584,3056,2424,2764, 443,3302,1163,3161,5257,5258,4029,5259,4287,2506, # 2240\n3057,4620,4030,3162,2104,1647,3600,2011,1873,4288,5260,4289, 431,3485,5261, 250, # 2256\n  97,  81,4290,5262,1648,1851,1558, 160, 848,5263, 866, 740,1694,5264,2204,2843, # 2272\n3226,4291,4621,3719,1687, 950,2479, 426, 469,3227,3720,3721,4031,5265,5266,1188, # 2288\n 424,1996, 861,3601,4292,3854,2205,2694, 168,1235,3602,4293,5267,2087,1674,4622, # 2304\n3374,3303, 220,2565,1009,5268,3855, 670,3010, 332,1208, 717,5269,5270,3603,2452, # 2320\n4032,3375,5271, 513,5272,1209,2882,3376,3163,4623,1080,5273,5274,5275,5276,2534, # 2336\n3722,3604, 815,1587,4033,4034,5277,3605,3486,3856,1254,4624,1328,3058,1390,4035, # 2352\n1741,4036,3857,4037,5278, 236,3858,2453,3304,5279,5280,3723,3859,1273,3860,4625, # 2368\n5281, 308,5282,4626, 245,4627,1852,2480,1307,2583, 430, 715,2137,2454,5283, 270, # 2384\n 199,2883,4038,5284,3606,2727,1753, 761,1754, 725,1661,1841,4628,3487,3724,5285, # 2400\n5286, 587,  14,3305, 227,2608, 326, 480,2270, 943,2765,3607, 291, 650,1884,5287, # 2416\n1702,1226, 102,1547,  62,3488, 904,4629,3489,1164,4294,5288,5289,1224,1548,2766, # 2432\n 391, 498,1493,5290,1386,1419,5291,2056,1177,4630, 813, 880,1081,2368, 566,1145, # 2448\n4631,2291,1001,1035,2566,2609,2242, 394,1286,5292,5293,2069,5294,  86,1494,1730, # 2464\n4039, 491,1588, 745, 897,2963, 843,3377,4040,2767,2884,3306,1768, 998,2221,2070, # 2480\n 397,1827,1195,1970,3725,3011,3378, 284,5295,3861,2507,2138,2120,1904,5296,4041, # 2496\n2151,4042,4295,1036,3490,1905, 114,2567,4296, 209,1527,5297,5298,2964,2844,2635, # 2512\n2390,2728,3164, 812,2568,5299,3307,5300,1559, 737,1885,3726,1210, 885,  28,2695, # 2528\n3608,3862,5301,4297,1004,1780,4632,5302, 346,1982,2222,2696,4633,3863,1742, 797, # 2544\n1642,4043,1934,1072,1384,2152, 896,4044,3308,3727,3228,2885,3609,5303,2569,1959, # 2560\n4634,2455,1786,5304,5305,5306,4045,4298,1005,1308,3728,4299,2729,4635,4636,1528, # 2576\n2610, 161,1178,4300,1983, 987,4637,1101,4301, 631,4046,1157,3229,2425,1343,1241, # 2592\n1016,2243,2570, 372, 877,2344,2508,1160, 555,1935, 911,4047,5307, 466,1170, 169, # 2608\n1051,2921,2697,3729,2481,3012,1182,2012,2571,1251,2636,5308, 992,2345,3491,1540, # 2624\n2730,1201,2071,2406,1997,2482,5309,4638, 528,1923,2191,1503,1874,1570,2369,3379, # 2640\n3309,5310, 557,1073,5311,1828,3492,2088,2271,3165,3059,3107, 767,3108,2799,4639, # 2656\n1006,4302,4640,2346,1267,2179,3730,3230, 778,4048,3231,2731,1597,2667,5312,4641, # 2672\n5313,3493,5314,5315,5316,3310,2698,1433,3311, 131,  95,1504,4049, 723,4303,3166, # 2688\n1842,3610,2768,2192,4050,2028,2105,3731,5317,3013,4051,1218,5318,3380,3232,4052, # 2704\n4304,2584, 248,1634,3864, 912,5319,2845,3732,3060,3865, 654,  53,5320,3014,5321, # 2720\n1688,4642, 777,3494,1032,4053,1425,5322, 191, 820,2121,2846, 971,4643, 931,3233, # 2736\n 135, 664, 783,3866,1998, 772,2922,1936,4054,3867,4644,2923,3234, 282,2732, 640, # 2752\n1372,3495,1127, 922, 325,3381,5323,5324, 711,2045,5325,5326,4055,2223,2800,1937, # 2768\n4056,3382,2224,2255,3868,2305,5327,4645,3869,1258,3312,4057,3235,2139,2965,4058, # 2784\n4059,5328,2225, 258,3236,4646, 101,1227,5329,3313,1755,5330,1391,3314,5331,2924, # 2800\n2057, 893,5332,5333,5334,1402,4305,2347,5335,5336,3237,3611,5337,5338, 878,1325, # 2816\n1781,2801,4647, 259,1385,2585, 744,1183,2272,4648,5339,4060,2509,5340, 684,1024, # 2832\n4306,5341, 472,3612,3496,1165,3315,4061,4062, 322,2153, 881, 455,1695,1152,1340, # 2848\n 660, 554,2154,4649,1058,4650,4307, 830,1065,3383,4063,4651,1924,5342,1703,1919, # 2864\n5343, 932,2273, 122,5344,4652, 947, 677,5345,3870,2637, 297,1906,1925,2274,4653, # 2880\n2322,3316,5346,5347,4308,5348,4309,  84,4310, 112, 989,5349, 547,1059,4064, 701, # 2896\n3613,1019,5350,4311,5351,3497, 942, 639, 457,2306,2456, 993,2966, 407, 851, 494, # 2912\n4654,3384, 927,5352,1237,5353,2426,3385, 573,4312, 680, 921,2925,1279,1875, 285, # 2928\n 790,1448,1984, 719,2168,5354,5355,4655,4065,4066,1649,5356,1541, 563,5357,1077, # 2944\n5358,3386,3061,3498, 511,3015,4067,4068,3733,4069,1268,2572,3387,3238,4656,4657, # 2960\n5359, 535,1048,1276,1189,2926,2029,3167,1438,1373,2847,2967,1134,2013,5360,4313, # 2976\n1238,2586,3109,1259,5361, 700,5362,2968,3168,3734,4314,5363,4315,1146,1876,1907, # 2992\n4658,2611,4070, 781,2427, 132,1589, 203, 147, 273,2802,2407, 898,1787,2155,4071, # 3008\n4072,5364,3871,2803,5365,5366,4659,4660,5367,3239,5368,1635,3872, 965,5369,1805, # 3024\n2699,1516,3614,1121,1082,1329,3317,4073,1449,3873,  65,1128,2848,2927,2769,1590, # 3040\n3874,5370,5371,  12,2668,  45, 976,2587,3169,4661, 517,2535,1013,1037,3240,5372, # 3056\n3875,2849,5373,3876,5374,3499,5375,2612, 614,1999,2323,3877,3110,2733,2638,5376, # 3072\n2588,4316, 599,1269,5377,1811,3735,5378,2700,3111, 759,1060, 489,1806,3388,3318, # 3088\n1358,5379,5380,2391,1387,1215,2639,2256, 490,5381,5382,4317,1759,2392,2348,5383, # 3104\n4662,3878,1908,4074,2640,1807,3241,4663,3500,3319,2770,2349, 874,5384,5385,3501, # 3120\n3736,1859,  91,2928,3737,3062,3879,4664,5386,3170,4075,2669,5387,3502,1202,1403, # 3136\n3880,2969,2536,1517,2510,4665,3503,2511,5388,4666,5389,2701,1886,1495,1731,4076, # 3152\n2370,4667,5390,2030,5391,5392,4077,2702,1216, 237,2589,4318,2324,4078,3881,4668, # 3168\n4669,2703,3615,3504, 445,4670,5393,5394,5395,5396,2771,  61,4079,3738,1823,4080, # 3184\n5397, 687,2046, 935, 925, 405,2670, 703,1096,1860,2734,4671,4081,1877,1367,2704, # 3200\n3389, 918,2106,1782,2483, 334,3320,1611,1093,4672, 564,3171,3505,3739,3390, 945, # 3216\n2641,2058,4673,5398,1926, 872,4319,5399,3506,2705,3112, 349,4320,3740,4082,4674, # 3232\n3882,4321,3741,2156,4083,4675,4676,4322,4677,2408,2047, 782,4084, 400, 251,4323, # 3248\n1624,5400,5401, 277,3742, 299,1265, 476,1191,3883,2122,4324,4325,1109, 205,5402, # 3264\n2590,1000,2157,3616,1861,5403,5404,5405,4678,5406,4679,2573, 107,2484,2158,4085, # 3280\n3507,3172,5407,1533, 541,1301, 158, 753,4326,2886,3617,5408,1696, 370,1088,4327, # 3296\n4680,3618, 579, 327, 440, 162,2244, 269,1938,1374,3508, 968,3063,  56,1396,3113, # 3312\n2107,3321,3391,5409,1927,2159,4681,3016,5410,3619,5411,5412,3743,4682,2485,5413, # 3328\n2804,5414,1650,4683,5415,2613,5416,5417,4086,2671,3392,1149,3393,4087,3884,4088, # 3344\n5418,1076,  49,5419, 951,3242,3322,3323, 450,2850, 920,5420,1812,2805,2371,4328, # 3360\n1909,1138,2372,3885,3509,5421,3243,4684,1910,1147,1518,2428,4685,3886,5422,4686, # 3376\n2393,2614, 260,1796,3244,5423,5424,3887,3324, 708,5425,3620,1704,5426,3621,1351, # 3392\n1618,3394,3017,1887, 944,4329,3395,4330,3064,3396,4331,5427,3744, 422, 413,1714, # 3408\n3325, 500,2059,2350,4332,2486,5428,1344,1911, 954,5429,1668,5430,5431,4089,2409, # 3424\n4333,3622,3888,4334,5432,2307,1318,2512,3114, 133,3115,2887,4687, 629,  31,2851, # 3440\n2706,3889,4688, 850, 949,4689,4090,2970,1732,2089,4335,1496,1853,5433,4091, 620, # 3456\n3245, 981,1242,3745,3397,1619,3746,1643,3326,2140,2457,1971,1719,3510,2169,5434, # 3472\n3246,5435,5436,3398,1829,5437,1277,4690,1565,2048,5438,1636,3623,3116,5439, 869, # 3488\n2852, 655,3890,3891,3117,4092,3018,3892,1310,3624,4691,5440,5441,5442,1733, 558, # 3504\n4692,3747, 335,1549,3065,1756,4336,3748,1946,3511,1830,1291,1192, 470,2735,2108, # 3520\n2806, 913,1054,4093,5443,1027,5444,3066,4094,4693, 982,2672,3399,3173,3512,3247, # 3536\n3248,1947,2807,5445, 571,4694,5446,1831,5447,3625,2591,1523,2429,5448,2090, 984, # 3552\n4695,3749,1960,5449,3750, 852, 923,2808,3513,3751, 969,1519, 999,2049,2325,1705, # 3568\n5450,3118, 615,1662, 151, 597,4095,2410,2326,1049, 275,4696,3752,4337, 568,3753, # 3584\n3626,2487,4338,3754,5451,2430,2275, 409,3249,5452,1566,2888,3514,1002, 769,2853, # 3600\n 194,2091,3174,3755,2226,3327,4339, 628,1505,5453,5454,1763,2180,3019,4096, 521, # 3616\n1161,2592,1788,2206,2411,4697,4097,1625,4340,4341, 412,  42,3119, 464,5455,2642, # 3632\n4698,3400,1760,1571,2889,3515,2537,1219,2207,3893,2643,2141,2373,4699,4700,3328, # 3648\n1651,3401,3627,5456,5457,3628,2488,3516,5458,3756,5459,5460,2276,2092, 460,5461, # 3664\n4701,5462,3020, 962, 588,3629, 289,3250,2644,1116,  52,5463,3067,1797,5464,5465, # 3680\n5466,1467,5467,1598,1143,3757,4342,1985,1734,1067,4702,1280,3402, 465,4703,1572, # 3696\n 510,5468,1928,2245,1813,1644,3630,5469,4704,3758,5470,5471,2673,1573,1534,5472, # 3712\n5473, 536,1808,1761,3517,3894,3175,2645,5474,5475,5476,4705,3518,2929,1912,2809, # 3728\n5477,3329,1122, 377,3251,5478, 360,5479,5480,4343,1529, 551,5481,2060,3759,1769, # 3744\n2431,5482,2930,4344,3330,3120,2327,2109,2031,4706,1404, 136,1468,1479, 672,1171, # 3760\n3252,2308, 271,3176,5483,2772,5484,2050, 678,2736, 865,1948,4707,5485,2014,4098, # 3776\n2971,5486,2737,2227,1397,3068,3760,4708,4709,1735,2931,3403,3631,5487,3895, 509, # 3792\n2854,2458,2890,3896,5488,5489,3177,3178,4710,4345,2538,4711,2309,1166,1010, 552, # 3808\n 681,1888,5490,5491,2972,2973,4099,1287,1596,1862,3179, 358, 453, 736, 175, 478, # 3824\n1117, 905,1167,1097,5492,1854,1530,5493,1706,5494,2181,3519,2292,3761,3520,3632, # 3840\n4346,2093,4347,5495,3404,1193,2489,4348,1458,2193,2208,1863,1889,1421,3331,2932, # 3856\n3069,2182,3521, 595,2123,5496,4100,5497,5498,4349,1707,2646, 223,3762,1359, 751, # 3872\n3121, 183,3522,5499,2810,3021, 419,2374, 633, 704,3897,2394, 241,5500,5501,5502, # 3888\n 838,3022,3763,2277,2773,2459,3898,1939,2051,4101,1309,3122,2246,1181,5503,1136, # 3904\n2209,3899,2375,1446,4350,2310,4712,5504,5505,4351,1055,2615, 484,3764,5506,4102, # 3920\n 625,4352,2278,3405,1499,4353,4103,5507,4104,4354,3253,2279,2280,3523,5508,5509, # 3936\n2774, 808,2616,3765,3406,4105,4355,3123,2539, 526,3407,3900,4356, 955,5510,1620, # 3952\n4357,2647,2432,5511,1429,3766,1669,1832, 994, 928,5512,3633,1260,5513,5514,5515, # 3968\n1949,2293, 741,2933,1626,4358,2738,2460, 867,1184, 362,3408,1392,5516,5517,4106, # 3984\n4359,1770,1736,3254,2934,4713,4714,1929,2707,1459,1158,5518,3070,3409,2891,1292, # 4000\n1930,2513,2855,3767,1986,1187,2072,2015,2617,4360,5519,2574,2514,2170,3768,2490, # 4016\n3332,5520,3769,4715,5521,5522, 666,1003,3023,1022,3634,4361,5523,4716,1814,2257, # 4032\n 574,3901,1603, 295,1535, 705,3902,4362, 283, 858, 417,5524,5525,3255,4717,4718, # 4048\n3071,1220,1890,1046,2281,2461,4107,1393,1599, 689,2575, 388,4363,5526,2491, 802, # 4064\n5527,2811,3903,2061,1405,2258,5528,4719,3904,2110,1052,1345,3256,1585,5529, 809, # 4080\n5530,5531,5532, 575,2739,3524, 956,1552,1469,1144,2328,5533,2329,1560,2462,3635, # 4096\n3257,4108, 616,2210,4364,3180,2183,2294,5534,1833,5535,3525,4720,5536,1319,3770, # 4112\n3771,1211,3636,1023,3258,1293,2812,5537,5538,5539,3905, 607,2311,3906, 762,2892, # 4128\n1439,4365,1360,4721,1485,3072,5540,4722,1038,4366,1450,2062,2648,4367,1379,4723, # 4144\n2593,5541,5542,4368,1352,1414,2330,2935,1172,5543,5544,3907,3908,4724,1798,1451, # 4160\n5545,5546,5547,5548,2936,4109,4110,2492,2351, 411,4111,4112,3637,3333,3124,4725, # 4176\n1561,2674,1452,4113,1375,5549,5550,  47,2974, 316,5551,1406,1591,2937,3181,5552, # 4192\n1025,2142,3125,3182, 354,2740, 884,2228,4369,2412, 508,3772, 726,3638, 996,2433, # 4208\n3639, 729,5553, 392,2194,1453,4114,4726,3773,5554,5555,2463,3640,2618,1675,2813, # 4224\n 919,2352,2975,2353,1270,4727,4115,  73,5556,5557, 647,5558,3259,2856,2259,1550, # 4240\n1346,3024,5559,1332, 883,3526,5560,5561,5562,5563,3334,2775,5564,1212, 831,1347, # 4256\n4370,4728,2331,3909,1864,3073, 720,3910,4729,4730,3911,5565,4371,5566,5567,4731, # 4272\n5568,5569,1799,4732,3774,2619,4733,3641,1645,2376,4734,5570,2938, 669,2211,2675, # 4288\n2434,5571,2893,5572,5573,1028,3260,5574,4372,2413,5575,2260,1353,5576,5577,4735, # 4304\n3183, 518,5578,4116,5579,4373,1961,5580,2143,4374,5581,5582,3025,2354,2355,3912, # 4320\n 516,1834,1454,4117,2708,4375,4736,2229,2620,1972,1129,3642,5583,2776,5584,2976, # 4336\n1422, 577,1470,3026,1524,3410,5585,5586, 432,4376,3074,3527,5587,2594,1455,2515, # 4352\n2230,1973,1175,5588,1020,2741,4118,3528,4737,5589,2742,5590,1743,1361,3075,3529, # 4368\n2649,4119,4377,4738,2295, 895, 924,4378,2171, 331,2247,3076, 166,1627,3077,1098, # 4384\n5591,1232,2894,2231,3411,4739, 657, 403,1196,2377, 542,3775,3412,1600,4379,3530, # 4400\n5592,4740,2777,3261, 576, 530,1362,4741,4742,2540,2676,3776,4120,5593, 842,3913, # 4416\n5594,2814,2032,1014,4121, 213,2709,3413, 665, 621,4380,5595,3777,2939,2435,5596, # 4432\n2436,3335,3643,3414,4743,4381,2541,4382,4744,3644,1682,4383,3531,1380,5597, 724, # 4448\n2282, 600,1670,5598,1337,1233,4745,3126,2248,5599,1621,4746,5600, 651,4384,5601, # 4464\n1612,4385,2621,5602,2857,5603,2743,2312,3078,5604, 716,2464,3079, 174,1255,2710, # 4480\n4122,3645, 548,1320,1398, 728,4123,1574,5605,1891,1197,3080,4124,5606,3081,3082, # 4496\n3778,3646,3779, 747,5607, 635,4386,4747,5608,5609,5610,4387,5611,5612,4748,5613, # 4512\n3415,4749,2437, 451,5614,3780,2542,2073,4388,2744,4389,4125,5615,1764,4750,5616, # 4528\n4390, 350,4751,2283,2395,2493,5617,4391,4126,2249,1434,4127, 488,4752, 458,4392, # 4544\n4128,3781, 771,1330,2396,3914,2576,3184,2160,2414,1553,2677,3185,4393,5618,2494, # 4560\n2895,2622,1720,2711,4394,3416,4753,5619,2543,4395,5620,3262,4396,2778,5621,2016, # 4576\n2745,5622,1155,1017,3782,3915,5623,3336,2313, 201,1865,4397,1430,5624,4129,5625, # 4592\n5626,5627,5628,5629,4398,1604,5630, 414,1866, 371,2595,4754,4755,3532,2017,3127, # 4608\n4756,1708, 960,4399, 887, 389,2172,1536,1663,1721,5631,2232,4130,2356,2940,1580, # 4624\n5632,5633,1744,4757,2544,4758,4759,5634,4760,5635,2074,5636,4761,3647,3417,2896, # 4640\n4400,5637,4401,2650,3418,2815, 673,2712,2465, 709,3533,4131,3648,4402,5638,1148, # 4656\n 502, 634,5639,5640,1204,4762,3649,1575,4763,2623,3783,5641,3784,3128, 948,3263, # 4672\n 121,1745,3916,1110,5642,4403,3083,2516,3027,4132,3785,1151,1771,3917,1488,4133, # 4688\n1987,5643,2438,3534,5644,5645,2094,5646,4404,3918,1213,1407,2816, 531,2746,2545, # 4704\n3264,1011,1537,4764,2779,4405,3129,1061,5647,3786,3787,1867,2897,5648,2018, 120, # 4720\n4406,4407,2063,3650,3265,2314,3919,2678,3419,1955,4765,4134,5649,3535,1047,2713, # 4736\n1266,5650,1368,4766,2858, 649,3420,3920,2546,2747,1102,2859,2679,5651,5652,2000, # 4752\n5653,1111,3651,2977,5654,2495,3921,3652,2817,1855,3421,3788,5655,5656,3422,2415, # 4768\n2898,3337,3266,3653,5657,2577,5658,3654,2818,4135,1460, 856,5659,3655,5660,2899, # 4784\n2978,5661,2900,3922,5662,4408, 632,2517, 875,3923,1697,3924,2296,5663,5664,4767, # 4800\n3028,1239, 580,4768,4409,5665, 914, 936,2075,1190,4136,1039,2124,5666,5667,5668, # 4816\n5669,3423,1473,5670,1354,4410,3925,4769,2173,3084,4137, 915,3338,4411,4412,3339, # 4832\n1605,1835,5671,2748, 398,3656,4413,3926,4138, 328,1913,2860,4139,3927,1331,4414, # 4848\n3029, 937,4415,5672,3657,4140,4141,3424,2161,4770,3425, 524, 742, 538,3085,1012, # 4864\n5673,5674,3928,2466,5675, 658,1103, 225,3929,5676,5677,4771,5678,4772,5679,3267, # 4880\n1243,5680,4142, 963,2250,4773,5681,2714,3658,3186,5682,5683,2596,2332,5684,4774, # 4896\n5685,5686,5687,3536, 957,3426,2547,2033,1931,2941,2467, 870,2019,3659,1746,2780, # 4912\n2781,2439,2468,5688,3930,5689,3789,3130,3790,3537,3427,3791,5690,1179,3086,5691, # 4928\n3187,2378,4416,3792,2548,3188,3131,2749,4143,5692,3428,1556,2549,2297, 977,2901, # 4944\n2034,4144,1205,3429,5693,1765,3430,3189,2125,1271, 714,1689,4775,3538,5694,2333, # 4960\n3931, 533,4417,3660,2184, 617,5695,2469,3340,3539,2315,5696,5697,3190,5698,5699, # 4976\n3932,1988, 618, 427,2651,3540,3431,5700,5701,1244,1690,5702,2819,4418,4776,5703, # 4992\n3541,4777,5704,2284,1576, 473,3661,4419,3432, 972,5705,3662,5706,3087,5707,5708, # 5008\n4778,4779,5709,3793,4145,4146,5710, 153,4780, 356,5711,1892,2902,4420,2144, 408, # 5024\n 803,2357,5712,3933,5713,4421,1646,2578,2518,4781,4782,3934,5714,3935,4422,5715, # 5040\n2416,3433, 752,5716,5717,1962,3341,2979,5718, 746,3030,2470,4783,4423,3794, 698, # 5056\n4784,1893,4424,3663,2550,4785,3664,3936,5719,3191,3434,5720,1824,1302,4147,2715, # 5072\n3937,1974,4425,5721,4426,3192, 823,1303,1288,1236,2861,3542,4148,3435, 774,3938, # 5088\n5722,1581,4786,1304,2862,3939,4787,5723,2440,2162,1083,3268,4427,4149,4428, 344, # 5104\n1173, 288,2316, 454,1683,5724,5725,1461,4788,4150,2597,5726,5727,4789, 985, 894, # 5120\n5728,3436,3193,5729,1914,2942,3795,1989,5730,2111,1975,5731,4151,5732,2579,1194, # 5136\n 425,5733,4790,3194,1245,3796,4429,5734,5735,2863,5736, 636,4791,1856,3940, 760, # 5152\n1800,5737,4430,2212,1508,4792,4152,1894,1684,2298,5738,5739,4793,4431,4432,2213, # 5168\n 479,5740,5741, 832,5742,4153,2496,5743,2980,2497,3797, 990,3132, 627,1815,2652, # 5184\n4433,1582,4434,2126,2112,3543,4794,5744, 799,4435,3195,5745,4795,2113,1737,3031, # 5200\n1018, 543, 754,4436,3342,1676,4796,4797,4154,4798,1489,5746,3544,5747,2624,2903, # 5216\n4155,5748,5749,2981,5750,5751,5752,5753,3196,4799,4800,2185,1722,5754,3269,3270, # 5232\n1843,3665,1715, 481, 365,1976,1857,5755,5756,1963,2498,4801,5757,2127,3666,3271, # 5248\n 433,1895,2064,2076,5758, 602,2750,5759,5760,5761,5762,5763,3032,1628,3437,5764, # 5264\n3197,4802,4156,2904,4803,2519,5765,2551,2782,5766,5767,5768,3343,4804,2905,5769, # 5280\n4805,5770,2864,4806,4807,1221,2982,4157,2520,5771,5772,5773,1868,1990,5774,5775, # 5296\n5776,1896,5777,5778,4808,1897,4158, 318,5779,2095,4159,4437,5780,5781, 485,5782, # 5312\n 938,3941, 553,2680, 116,5783,3942,3667,5784,3545,2681,2783,3438,3344,2820,5785, # 5328\n3668,2943,4160,1747,2944,2983,5786,5787, 207,5788,4809,5789,4810,2521,5790,3033, # 5344\n 890,3669,3943,5791,1878,3798,3439,5792,2186,2358,3440,1652,5793,5794,5795, 941, # 5360\n2299, 208,3546,4161,2020, 330,4438,3944,2906,2499,3799,4439,4811,5796,5797,5798, # 5376\n)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/big5prober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .mbcharsetprober import MultiByteCharSetProber\nfrom .codingstatemachine import CodingStateMachine\nfrom .chardistribution import Big5DistributionAnalysis\nfrom .mbcssm import BIG5_SM_MODEL\n\n\nclass Big5Prober(MultiByteCharSetProber):\n    def __init__(self):\n        super(Big5Prober, self).__init__()\n        self.coding_sm = CodingStateMachine(BIG5_SM_MODEL)\n        self.distribution_analyzer = Big5DistributionAnalysis()\n        self.reset()\n\n    @property\n    def charset_name(self):\n        return \"Big5\"\n\n    @property\n    def language(self):\n        return \"Chinese\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/chardistribution.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .euctwfreq import (EUCTW_CHAR_TO_FREQ_ORDER, EUCTW_TABLE_SIZE,\n                        EUCTW_TYPICAL_DISTRIBUTION_RATIO)\nfrom .euckrfreq import (EUCKR_CHAR_TO_FREQ_ORDER, EUCKR_TABLE_SIZE,\n                        EUCKR_TYPICAL_DISTRIBUTION_RATIO)\nfrom .gb2312freq import (GB2312_CHAR_TO_FREQ_ORDER, GB2312_TABLE_SIZE,\n                         GB2312_TYPICAL_DISTRIBUTION_RATIO)\nfrom .big5freq import (BIG5_CHAR_TO_FREQ_ORDER, BIG5_TABLE_SIZE,\n                       BIG5_TYPICAL_DISTRIBUTION_RATIO)\nfrom .jisfreq import (JIS_CHAR_TO_FREQ_ORDER, JIS_TABLE_SIZE,\n                      JIS_TYPICAL_DISTRIBUTION_RATIO)\n\n\nclass CharDistributionAnalysis(object):\n    ENOUGH_DATA_THRESHOLD = 1024\n    SURE_YES = 0.99\n    SURE_NO = 0.01\n    MINIMUM_DATA_THRESHOLD = 3\n\n    def __init__(self):\n        # Mapping table to get frequency order from char order (get from\n        # GetOrder())\n        self._char_to_freq_order = None\n        self._table_size = None  # Size of above table\n        # This is a constant value which varies from language to language,\n        # used in calculating confidence.  See\n        # http://www.mozilla.org/projects/intl/UniversalCharsetDetection.html\n        # for further detail.\n        self.typical_distribution_ratio = None\n        self._done = None\n        self._total_chars = None\n        self._freq_chars = None\n        self.reset()\n\n    def reset(self):\n        \"\"\"reset analyser, clear any state\"\"\"\n        # If this flag is set to True, detection is done and conclusion has\n        # been made\n        self._done = False\n        self._total_chars = 0  # Total characters encountered\n        # The number of characters whose frequency order is less than 512\n        self._freq_chars = 0\n\n    def feed(self, char, char_len):\n        \"\"\"feed a character with known length\"\"\"\n        if char_len == 2:\n            # we only care about 2-bytes character in our distribution analysis\n            order = self.get_order(char)\n        else:\n            order = -1\n        if order >= 0:\n            self._total_chars += 1\n            # order is valid\n            if order < self._table_size:\n                if 512 > self._char_to_freq_order[order]:\n                    self._freq_chars += 1\n\n    def get_confidence(self):\n        \"\"\"return confidence based on existing data\"\"\"\n        # if we didn't receive any character in our consideration range,\n        # return negative answer\n        if self._total_chars <= 0 or self._freq_chars <= self.MINIMUM_DATA_THRESHOLD:\n            return self.SURE_NO\n\n        if self._total_chars != self._freq_chars:\n            r = (self._freq_chars / ((self._total_chars - self._freq_chars)\n                 * self.typical_distribution_ratio))\n            if r < self.SURE_YES:\n                return r\n\n        # normalize confidence (we don't want to be 100% sure)\n        return self.SURE_YES\n\n    def got_enough_data(self):\n        # It is not necessary to receive all data to draw conclusion.\n        # For charset detection, certain amount of data is enough\n        return self._total_chars > self.ENOUGH_DATA_THRESHOLD\n\n    def get_order(self, byte_str):\n        # We do not handle characters based on the original encoding string,\n        # but convert this encoding string to a number, here called order.\n        # This allows multiple encodings of a language to share one frequency\n        # table.\n        return -1\n\n\nclass EUCTWDistributionAnalysis(CharDistributionAnalysis):\n    def __init__(self):\n        super(EUCTWDistributionAnalysis, self).__init__()\n        self._char_to_freq_order = EUCTW_CHAR_TO_FREQ_ORDER\n        self._table_size = EUCTW_TABLE_SIZE\n        self.typical_distribution_ratio = EUCTW_TYPICAL_DISTRIBUTION_RATIO\n\n    def get_order(self, byte_str):\n        # for euc-TW encoding, we are interested\n        #   first  byte range: 0xc4 -- 0xfe\n        #   second byte range: 0xa1 -- 0xfe\n        # no validation needed here. State machine has done that\n        first_char = byte_str[0]\n        if first_char >= 0xC4:\n            return 94 * (first_char - 0xC4) + byte_str[1] - 0xA1\n        else:\n            return -1\n\n\nclass EUCKRDistributionAnalysis(CharDistributionAnalysis):\n    def __init__(self):\n        super(EUCKRDistributionAnalysis, self).__init__()\n        self._char_to_freq_order = EUCKR_CHAR_TO_FREQ_ORDER\n        self._table_size = EUCKR_TABLE_SIZE\n        self.typical_distribution_ratio = EUCKR_TYPICAL_DISTRIBUTION_RATIO\n\n    def get_order(self, byte_str):\n        # for euc-KR encoding, we are interested\n        #   first  byte range: 0xb0 -- 0xfe\n        #   second byte range: 0xa1 -- 0xfe\n        # no validation needed here. State machine has done that\n        first_char = byte_str[0]\n        if first_char >= 0xB0:\n            return 94 * (first_char - 0xB0) + byte_str[1] - 0xA1\n        else:\n            return -1\n\n\nclass GB2312DistributionAnalysis(CharDistributionAnalysis):\n    def __init__(self):\n        super(GB2312DistributionAnalysis, self).__init__()\n        self._char_to_freq_order = GB2312_CHAR_TO_FREQ_ORDER\n        self._table_size = GB2312_TABLE_SIZE\n        self.typical_distribution_ratio = GB2312_TYPICAL_DISTRIBUTION_RATIO\n\n    def get_order(self, byte_str):\n        # for GB2312 encoding, we are interested\n        #  first  byte range: 0xb0 -- 0xfe\n        #  second byte range: 0xa1 -- 0xfe\n        # no validation needed here. State machine has done that\n        first_char, second_char = byte_str[0], byte_str[1]\n        if (first_char >= 0xB0) and (second_char >= 0xA1):\n            return 94 * (first_char - 0xB0) + second_char - 0xA1\n        else:\n            return -1\n\n\nclass Big5DistributionAnalysis(CharDistributionAnalysis):\n    def __init__(self):\n        super(Big5DistributionAnalysis, self).__init__()\n        self._char_to_freq_order = BIG5_CHAR_TO_FREQ_ORDER\n        self._table_size = BIG5_TABLE_SIZE\n        self.typical_distribution_ratio = BIG5_TYPICAL_DISTRIBUTION_RATIO\n\n    def get_order(self, byte_str):\n        # for big5 encoding, we are interested\n        #   first  byte range: 0xa4 -- 0xfe\n        #   second byte range: 0x40 -- 0x7e , 0xa1 -- 0xfe\n        # no validation needed here. State machine has done that\n        first_char, second_char = byte_str[0], byte_str[1]\n        if first_char >= 0xA4:\n            if second_char >= 0xA1:\n                return 157 * (first_char - 0xA4) + second_char - 0xA1 + 63\n            else:\n                return 157 * (first_char - 0xA4) + second_char - 0x40\n        else:\n            return -1\n\n\nclass SJISDistributionAnalysis(CharDistributionAnalysis):\n    def __init__(self):\n        super(SJISDistributionAnalysis, self).__init__()\n        self._char_to_freq_order = JIS_CHAR_TO_FREQ_ORDER\n        self._table_size = JIS_TABLE_SIZE\n        self.typical_distribution_ratio = JIS_TYPICAL_DISTRIBUTION_RATIO\n\n    def get_order(self, byte_str):\n        # for sjis encoding, we are interested\n        #   first  byte range: 0x81 -- 0x9f , 0xe0 -- 0xfe\n        #   second byte range: 0x40 -- 0x7e,  0x81 -- oxfe\n        # no validation needed here. State machine has done that\n        first_char, second_char = byte_str[0], byte_str[1]\n        if (first_char >= 0x81) and (first_char <= 0x9F):\n            order = 188 * (first_char - 0x81)\n        elif (first_char >= 0xE0) and (first_char <= 0xEF):\n            order = 188 * (first_char - 0xE0 + 31)\n        else:\n            return -1\n        order = order + second_char - 0x40\n        if second_char > 0x7F:\n            order = -1\n        return order\n\n\nclass EUCJPDistributionAnalysis(CharDistributionAnalysis):\n    def __init__(self):\n        super(EUCJPDistributionAnalysis, self).__init__()\n        self._char_to_freq_order = JIS_CHAR_TO_FREQ_ORDER\n        self._table_size = JIS_TABLE_SIZE\n        self.typical_distribution_ratio = JIS_TYPICAL_DISTRIBUTION_RATIO\n\n    def get_order(self, byte_str):\n        # for euc-JP encoding, we are interested\n        #   first  byte range: 0xa0 -- 0xfe\n        #   second byte range: 0xa1 -- 0xfe\n        # no validation needed here. State machine has done that\n        char = byte_str[0]\n        if char >= 0xA0:\n            return 94 * (char - 0xA1) + byte_str[1] - 0xa1\n        else:\n            return -1\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/charsetgroupprober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .enums import ProbingState\nfrom .charsetprober import CharSetProber\n\n\nclass CharSetGroupProber(CharSetProber):\n    def __init__(self, lang_filter=None):\n        super(CharSetGroupProber, self).__init__(lang_filter=lang_filter)\n        self._active_num = 0\n        self.probers = []\n        self._best_guess_prober = None\n\n    def reset(self):\n        super(CharSetGroupProber, self).reset()\n        self._active_num = 0\n        for prober in self.probers:\n            if prober:\n                prober.reset()\n                prober.active = True\n                self._active_num += 1\n        self._best_guess_prober = None\n\n    @property\n    def charset_name(self):\n        if not self._best_guess_prober:\n            self.get_confidence()\n            if not self._best_guess_prober:\n                return None\n        return self._best_guess_prober.charset_name\n\n    @property\n    def language(self):\n        if not self._best_guess_prober:\n            self.get_confidence()\n            if not self._best_guess_prober:\n                return None\n        return self._best_guess_prober.language\n\n    def feed(self, byte_str):\n        for prober in self.probers:\n            if not prober:\n                continue\n            if not prober.active:\n                continue\n            state = prober.feed(byte_str)\n            if not state:\n                continue\n            if state == ProbingState.FOUND_IT:\n                self._best_guess_prober = prober\n                return self.state\n            elif state == ProbingState.NOT_ME:\n                prober.active = False\n                self._active_num -= 1\n                if self._active_num <= 0:\n                    self._state = ProbingState.NOT_ME\n                    return self.state\n        return self.state\n\n    def get_confidence(self):\n        state = self.state\n        if state == ProbingState.FOUND_IT:\n            return 0.99\n        elif state == ProbingState.NOT_ME:\n            return 0.01\n        best_conf = 0.0\n        self._best_guess_prober = None\n        for prober in self.probers:\n            if not prober:\n                continue\n            if not prober.active:\n                self.logger.debug('%s not active', prober.charset_name)\n                continue\n            conf = prober.get_confidence()\n            self.logger.debug('%s %s confidence = %s', prober.charset_name, prober.language, conf)\n            if best_conf < conf:\n                best_conf = conf\n                self._best_guess_prober = prober\n        if not self._best_guess_prober:\n            return 0.0\n        return best_conf\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/charsetprober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Universal charset detector code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 2001\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#   Shy Shalom - original C code\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nimport logging\nimport re\n\nfrom .enums import ProbingState\n\n\nclass CharSetProber(object):\n\n    SHORTCUT_THRESHOLD = 0.95\n\n    def __init__(self, lang_filter=None):\n        self._state = None\n        self.lang_filter = lang_filter\n        self.logger = logging.getLogger(__name__)\n\n    def reset(self):\n        self._state = ProbingState.DETECTING\n\n    @property\n    def charset_name(self):\n        return None\n\n    def feed(self, buf):\n        pass\n\n    @property\n    def state(self):\n        return self._state\n\n    def get_confidence(self):\n        return 0.0\n\n    @staticmethod\n    def filter_high_byte_only(buf):\n        buf = re.sub(b'([\\x00-\\x7F])+', b' ', buf)\n        return buf\n\n    @staticmethod\n    def filter_international_words(buf):\n        \"\"\"\n        We define three types of bytes:\n        alphabet: english alphabets [a-zA-Z]\n        international: international characters [\\x80-\\xFF]\n        marker: everything else [^a-zA-Z\\x80-\\xFF]\n\n        The input buffer can be thought to contain a series of words delimited\n        by markers. This function works to filter all words that contain at\n        least one international character. All contiguous sequences of markers\n        are replaced by a single space ascii character.\n\n        This filter applies to all scripts which do not use English characters.\n        \"\"\"\n        filtered = bytearray()\n\n        # This regex expression filters out only words that have at-least one\n        # international character. The word may include one marker character at\n        # the end.\n        words = re.findall(b'[a-zA-Z]*[\\x80-\\xFF]+[a-zA-Z]*[^a-zA-Z\\x80-\\xFF]?',\n                           buf)\n\n        for word in words:\n            filtered.extend(word[:-1])\n\n            # If the last character in the word is a marker, replace it with a\n            # space as markers shouldn't affect our analysis (they are used\n            # similarly across all languages and may thus have similar\n            # frequencies).\n            last_char = word[-1:]\n            if not last_char.isalpha() and last_char < b'\\x80':\n                last_char = b' '\n            filtered.extend(last_char)\n\n        return filtered\n\n    @staticmethod\n    def filter_with_english_letters(buf):\n        \"\"\"\n        Returns a copy of ``buf`` that retains only the sequences of English\n        alphabet and high byte characters that are not between <> characters.\n        Also retains English alphabet and high byte characters immediately\n        before occurrences of >.\n\n        This filter can be applied to all scripts which contain both English\n        characters and extended ASCII characters, but is currently only used by\n        ``Latin1Prober``.\n        \"\"\"\n        filtered = bytearray()\n        in_tag = False\n        prev = 0\n\n        for curr in range(len(buf)):\n            # Slice here to get bytes instead of an int with Python 3\n            buf_char = buf[curr:curr + 1]\n            # Check if we're coming out of or entering an HTML tag\n            if buf_char == b'>':\n                in_tag = False\n            elif buf_char == b'<':\n                in_tag = True\n\n            # If current character is not extended-ASCII and not alphabetic...\n            if buf_char < b'\\x80' and not buf_char.isalpha():\n                # ...and we're not in a tag\n                if curr > prev and not in_tag:\n                    # Keep everything after last non-extended-ASCII,\n                    # non-alphabetic character\n                    filtered.extend(buf[prev:curr])\n                    # Output a space to delimit stretch we kept\n                    filtered.extend(b' ')\n                prev = curr + 1\n\n        # If we're not in a tag...\n        if not in_tag:\n            # Keep everything after last non-extended-ASCII, non-alphabetic\n            # character\n            filtered.extend(buf[prev:])\n\n        return filtered\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/cli/__init__.py",
    "content": "\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/cli/chardetect.py",
    "content": "#!/usr/bin/env python\n\"\"\"\nScript which takes one or more file paths and reports on their detected\nencodings\n\nExample::\n\n    % chardetect somefile someotherfile\n    somefile: windows-1252 with confidence 0.5\n    someotherfile: ascii with confidence 1.0\n\nIf no paths are provided, it takes its input from stdin.\n\n\"\"\"\n\nfrom __future__ import absolute_import, print_function, unicode_literals\n\nimport argparse\nimport sys\n\nfrom pip._vendor.chardet import __version__\nfrom pip._vendor.chardet.compat import PY2\nfrom pip._vendor.chardet.universaldetector import UniversalDetector\n\n\ndef description_of(lines, name='stdin'):\n    \"\"\"\n    Return a string describing the probable encoding of a file or\n    list of strings.\n\n    :param lines: The lines to get the encoding of.\n    :type lines: Iterable of bytes\n    :param name: Name of file or collection of lines\n    :type name: str\n    \"\"\"\n    u = UniversalDetector()\n    for line in lines:\n        line = bytearray(line)\n        u.feed(line)\n        # shortcut out of the loop to save reading further - particularly useful if we read a BOM.\n        if u.done:\n            break\n    u.close()\n    result = u.result\n    if PY2:\n        name = name.decode(sys.getfilesystemencoding(), 'ignore')\n    if result['encoding']:\n        return '{0}: {1} with confidence {2}'.format(name, result['encoding'],\n                                                     result['confidence'])\n    else:\n        return '{0}: no result'.format(name)\n\n\ndef main(argv=None):\n    \"\"\"\n    Handles command line arguments and gets things started.\n\n    :param argv: List of arguments, as if specified on the command-line.\n                 If None, ``sys.argv[1:]`` is used instead.\n    :type argv: list of str\n    \"\"\"\n    # Get command line arguments\n    parser = argparse.ArgumentParser(\n        description=\"Takes one or more file paths and reports their detected \\\n                     encodings\")\n    parser.add_argument('input',\n                        help='File whose encoding we would like to determine. \\\n                              (default: stdin)',\n                        type=argparse.FileType('rb'), nargs='*',\n                        default=[sys.stdin if PY2 else sys.stdin.buffer])\n    parser.add_argument('--version', action='version',\n                        version='%(prog)s {0}'.format(__version__))\n    args = parser.parse_args(argv)\n\n    for f in args.input:\n        if f.isatty():\n            print(\"You are running chardetect interactively. Press \" +\n                  \"CTRL-D twice at the start of a blank line to signal the \" +\n                  \"end of your input. If you want help, run chardetect \" +\n                  \"--help\\n\", file=sys.stderr)\n        print(description_of(f, f.name))\n\n\nif __name__ == '__main__':\n    main()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/codingstatemachine.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is mozilla.org code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nimport logging\n\nfrom .enums import MachineState\n\n\nclass CodingStateMachine(object):\n    \"\"\"\n    A state machine to verify a byte sequence for a particular encoding. For\n    each byte the detector receives, it will feed that byte to every active\n    state machine available, one byte at a time. The state machine changes its\n    state based on its previous state and the byte it receives. There are 3\n    states in a state machine that are of interest to an auto-detector:\n\n    START state: This is the state to start with, or a legal byte sequence\n                 (i.e. a valid code point) for character has been identified.\n\n    ME state:  This indicates that the state machine identified a byte sequence\n               that is specific to the charset it is designed for and that\n               there is no other possible encoding which can contain this byte\n               sequence. This will to lead to an immediate positive answer for\n               the detector.\n\n    ERROR state: This indicates the state machine identified an illegal byte\n                 sequence for that encoding. This will lead to an immediate\n                 negative answer for this encoding. Detector will exclude this\n                 encoding from consideration from here on.\n    \"\"\"\n    def __init__(self, sm):\n        self._model = sm\n        self._curr_byte_pos = 0\n        self._curr_char_len = 0\n        self._curr_state = None\n        self.logger = logging.getLogger(__name__)\n        self.reset()\n\n    def reset(self):\n        self._curr_state = MachineState.START\n\n    def next_state(self, c):\n        # for each byte we get its class\n        # if it is first byte, we also get byte length\n        byte_class = self._model['class_table'][c]\n        if self._curr_state == MachineState.START:\n            self._curr_byte_pos = 0\n            self._curr_char_len = self._model['char_len_table'][byte_class]\n        # from byte's class and state_table, we get its next state\n        curr_state = (self._curr_state * self._model['class_factor']\n                      + byte_class)\n        self._curr_state = self._model['state_table'][curr_state]\n        self._curr_byte_pos += 1\n        return self._curr_state\n\n    def get_current_charlen(self):\n        return self._curr_char_len\n\n    def get_coding_state_machine(self):\n        return self._model['name']\n\n    @property\n    def language(self):\n        return self._model['language']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/compat.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# Contributor(s):\n#   Dan Blanchard\n#   Ian Cordasco\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nimport sys\n\n\nif sys.version_info < (3, 0):\n    PY2 = True\n    PY3 = False\n    base_str = (str, unicode)\n    text_type = unicode\nelse:\n    PY2 = False\n    PY3 = True\n    base_str = (bytes, str)\n    text_type = str\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/cp949prober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is mozilla.org code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .chardistribution import EUCKRDistributionAnalysis\nfrom .codingstatemachine import CodingStateMachine\nfrom .mbcharsetprober import MultiByteCharSetProber\nfrom .mbcssm import CP949_SM_MODEL\n\n\nclass CP949Prober(MultiByteCharSetProber):\n    def __init__(self):\n        super(CP949Prober, self).__init__()\n        self.coding_sm = CodingStateMachine(CP949_SM_MODEL)\n        # NOTE: CP949 is a superset of EUC-KR, so the distribution should be\n        #       not different.\n        self.distribution_analyzer = EUCKRDistributionAnalysis()\n        self.reset()\n\n    @property\n    def charset_name(self):\n        return \"CP949\"\n\n    @property\n    def language(self):\n        return \"Korean\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/enums.py",
    "content": "\"\"\"\nAll of the Enums that are used throughout the chardet package.\n\n:author: Dan Blanchard (dan.blanchard@gmail.com)\n\"\"\"\n\n\nclass InputState(object):\n    \"\"\"\n    This enum represents the different states a universal detector can be in.\n    \"\"\"\n    PURE_ASCII = 0\n    ESC_ASCII = 1\n    HIGH_BYTE = 2\n\n\nclass LanguageFilter(object):\n    \"\"\"\n    This enum represents the different language filters we can apply to a\n    ``UniversalDetector``.\n    \"\"\"\n    CHINESE_SIMPLIFIED = 0x01\n    CHINESE_TRADITIONAL = 0x02\n    JAPANESE = 0x04\n    KOREAN = 0x08\n    NON_CJK = 0x10\n    ALL = 0x1F\n    CHINESE = CHINESE_SIMPLIFIED | CHINESE_TRADITIONAL\n    CJK = CHINESE | JAPANESE | KOREAN\n\n\nclass ProbingState(object):\n    \"\"\"\n    This enum represents the different states a prober can be in.\n    \"\"\"\n    DETECTING = 0\n    FOUND_IT = 1\n    NOT_ME = 2\n\n\nclass MachineState(object):\n    \"\"\"\n    This enum represents the different states a state machine can be in.\n    \"\"\"\n    START = 0\n    ERROR = 1\n    ITS_ME = 2\n\n\nclass SequenceLikelihood(object):\n    \"\"\"\n    This enum represents the likelihood of a character following the previous one.\n    \"\"\"\n    NEGATIVE = 0\n    UNLIKELY = 1\n    LIKELY = 2\n    POSITIVE = 3\n\n    @classmethod\n    def get_num_categories(cls):\n        \"\"\":returns: The number of likelihood categories in the enum.\"\"\"\n        return 4\n\n\nclass CharacterCategory(object):\n    \"\"\"\n    This enum represents the different categories language models for\n    ``SingleByteCharsetProber`` put characters into.\n\n    Anything less than CONTROL is considered a letter.\n    \"\"\"\n    UNDEFINED = 255\n    LINE_BREAK = 254\n    SYMBOL = 253\n    DIGIT = 252\n    CONTROL = 251\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/escprober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is mozilla.org code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .charsetprober import CharSetProber\nfrom .codingstatemachine import CodingStateMachine\nfrom .enums import LanguageFilter, ProbingState, MachineState\nfrom .escsm import (HZ_SM_MODEL, ISO2022CN_SM_MODEL, ISO2022JP_SM_MODEL,\n                    ISO2022KR_SM_MODEL)\n\n\nclass EscCharSetProber(CharSetProber):\n    \"\"\"\n    This CharSetProber uses a \"code scheme\" approach for detecting encodings,\n    whereby easily recognizable escape or shift sequences are relied on to\n    identify these encodings.\n    \"\"\"\n\n    def __init__(self, lang_filter=None):\n        super(EscCharSetProber, self).__init__(lang_filter=lang_filter)\n        self.coding_sm = []\n        if self.lang_filter & LanguageFilter.CHINESE_SIMPLIFIED:\n            self.coding_sm.append(CodingStateMachine(HZ_SM_MODEL))\n            self.coding_sm.append(CodingStateMachine(ISO2022CN_SM_MODEL))\n        if self.lang_filter & LanguageFilter.JAPANESE:\n            self.coding_sm.append(CodingStateMachine(ISO2022JP_SM_MODEL))\n        if self.lang_filter & LanguageFilter.KOREAN:\n            self.coding_sm.append(CodingStateMachine(ISO2022KR_SM_MODEL))\n        self.active_sm_count = None\n        self._detected_charset = None\n        self._detected_language = None\n        self._state = None\n        self.reset()\n\n    def reset(self):\n        super(EscCharSetProber, self).reset()\n        for coding_sm in self.coding_sm:\n            if not coding_sm:\n                continue\n            coding_sm.active = True\n            coding_sm.reset()\n        self.active_sm_count = len(self.coding_sm)\n        self._detected_charset = None\n        self._detected_language = None\n\n    @property\n    def charset_name(self):\n        return self._detected_charset\n\n    @property\n    def language(self):\n        return self._detected_language\n\n    def get_confidence(self):\n        if self._detected_charset:\n            return 0.99\n        else:\n            return 0.00\n\n    def feed(self, byte_str):\n        for c in byte_str:\n            for coding_sm in self.coding_sm:\n                if not coding_sm or not coding_sm.active:\n                    continue\n                coding_state = coding_sm.next_state(c)\n                if coding_state == MachineState.ERROR:\n                    coding_sm.active = False\n                    self.active_sm_count -= 1\n                    if self.active_sm_count <= 0:\n                        self._state = ProbingState.NOT_ME\n                        return self.state\n                elif coding_state == MachineState.ITS_ME:\n                    self._state = ProbingState.FOUND_IT\n                    self._detected_charset = coding_sm.get_coding_state_machine()\n                    self._detected_language = coding_sm.language\n                    return self.state\n\n        return self.state\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/escsm.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is mozilla.org code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .enums import MachineState\n\nHZ_CLS = (\n1,0,0,0,0,0,0,0,  # 00 - 07\n0,0,0,0,0,0,0,0,  # 08 - 0f\n0,0,0,0,0,0,0,0,  # 10 - 17\n0,0,0,1,0,0,0,0,  # 18 - 1f\n0,0,0,0,0,0,0,0,  # 20 - 27\n0,0,0,0,0,0,0,0,  # 28 - 2f\n0,0,0,0,0,0,0,0,  # 30 - 37\n0,0,0,0,0,0,0,0,  # 38 - 3f\n0,0,0,0,0,0,0,0,  # 40 - 47\n0,0,0,0,0,0,0,0,  # 48 - 4f\n0,0,0,0,0,0,0,0,  # 50 - 57\n0,0,0,0,0,0,0,0,  # 58 - 5f\n0,0,0,0,0,0,0,0,  # 60 - 67\n0,0,0,0,0,0,0,0,  # 68 - 6f\n0,0,0,0,0,0,0,0,  # 70 - 77\n0,0,0,4,0,5,2,0,  # 78 - 7f\n1,1,1,1,1,1,1,1,  # 80 - 87\n1,1,1,1,1,1,1,1,  # 88 - 8f\n1,1,1,1,1,1,1,1,  # 90 - 97\n1,1,1,1,1,1,1,1,  # 98 - 9f\n1,1,1,1,1,1,1,1,  # a0 - a7\n1,1,1,1,1,1,1,1,  # a8 - af\n1,1,1,1,1,1,1,1,  # b0 - b7\n1,1,1,1,1,1,1,1,  # b8 - bf\n1,1,1,1,1,1,1,1,  # c0 - c7\n1,1,1,1,1,1,1,1,  # c8 - cf\n1,1,1,1,1,1,1,1,  # d0 - d7\n1,1,1,1,1,1,1,1,  # d8 - df\n1,1,1,1,1,1,1,1,  # e0 - e7\n1,1,1,1,1,1,1,1,  # e8 - ef\n1,1,1,1,1,1,1,1,  # f0 - f7\n1,1,1,1,1,1,1,1,  # f8 - ff\n)\n\nHZ_ST = (\nMachineState.START,MachineState.ERROR,     3,MachineState.START,MachineState.START,MachineState.START,MachineState.ERROR,MachineState.ERROR,# 00-07\nMachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,# 08-0f\nMachineState.ITS_ME,MachineState.ITS_ME,MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.START,     4,MachineState.ERROR,# 10-17\n     5,MachineState.ERROR,     6,MachineState.ERROR,     5,     5,     4,MachineState.ERROR,# 18-1f\n     4,MachineState.ERROR,     4,     4,     4,MachineState.ERROR,     4,MachineState.ERROR,# 20-27\n     4,MachineState.ITS_ME,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,# 28-2f\n)\n\nHZ_CHAR_LEN_TABLE = (0, 0, 0, 0, 0, 0)\n\nHZ_SM_MODEL = {'class_table': HZ_CLS,\n               'class_factor': 6,\n               'state_table': HZ_ST,\n               'char_len_table': HZ_CHAR_LEN_TABLE,\n               'name': \"HZ-GB-2312\",\n               'language': 'Chinese'}\n\nISO2022CN_CLS = (\n2,0,0,0,0,0,0,0,  # 00 - 07\n0,0,0,0,0,0,0,0,  # 08 - 0f\n0,0,0,0,0,0,0,0,  # 10 - 17\n0,0,0,1,0,0,0,0,  # 18 - 1f\n0,0,0,0,0,0,0,0,  # 20 - 27\n0,3,0,0,0,0,0,0,  # 28 - 2f\n0,0,0,0,0,0,0,0,  # 30 - 37\n0,0,0,0,0,0,0,0,  # 38 - 3f\n0,0,0,4,0,0,0,0,  # 40 - 47\n0,0,0,0,0,0,0,0,  # 48 - 4f\n0,0,0,0,0,0,0,0,  # 50 - 57\n0,0,0,0,0,0,0,0,  # 58 - 5f\n0,0,0,0,0,0,0,0,  # 60 - 67\n0,0,0,0,0,0,0,0,  # 68 - 6f\n0,0,0,0,0,0,0,0,  # 70 - 77\n0,0,0,0,0,0,0,0,  # 78 - 7f\n2,2,2,2,2,2,2,2,  # 80 - 87\n2,2,2,2,2,2,2,2,  # 88 - 8f\n2,2,2,2,2,2,2,2,  # 90 - 97\n2,2,2,2,2,2,2,2,  # 98 - 9f\n2,2,2,2,2,2,2,2,  # a0 - a7\n2,2,2,2,2,2,2,2,  # a8 - af\n2,2,2,2,2,2,2,2,  # b0 - b7\n2,2,2,2,2,2,2,2,  # b8 - bf\n2,2,2,2,2,2,2,2,  # c0 - c7\n2,2,2,2,2,2,2,2,  # c8 - cf\n2,2,2,2,2,2,2,2,  # d0 - d7\n2,2,2,2,2,2,2,2,  # d8 - df\n2,2,2,2,2,2,2,2,  # e0 - e7\n2,2,2,2,2,2,2,2,  # e8 - ef\n2,2,2,2,2,2,2,2,  # f0 - f7\n2,2,2,2,2,2,2,2,  # f8 - ff\n)\n\nISO2022CN_ST = (\nMachineState.START,     3,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,# 00-07\nMachineState.START,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,# 08-0f\nMachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,# 10-17\nMachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,     4,MachineState.ERROR,# 18-1f\nMachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,# 20-27\n     5,     6,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,# 28-2f\nMachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,# 30-37\nMachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ERROR,MachineState.START,# 38-3f\n)\n\nISO2022CN_CHAR_LEN_TABLE = (0, 0, 0, 0, 0, 0, 0, 0, 0)\n\nISO2022CN_SM_MODEL = {'class_table': ISO2022CN_CLS,\n                      'class_factor': 9,\n                      'state_table': ISO2022CN_ST,\n                      'char_len_table': ISO2022CN_CHAR_LEN_TABLE,\n                      'name': \"ISO-2022-CN\",\n                      'language': 'Chinese'}\n\nISO2022JP_CLS = (\n2,0,0,0,0,0,0,0,  # 00 - 07\n0,0,0,0,0,0,2,2,  # 08 - 0f\n0,0,0,0,0,0,0,0,  # 10 - 17\n0,0,0,1,0,0,0,0,  # 18 - 1f\n0,0,0,0,7,0,0,0,  # 20 - 27\n3,0,0,0,0,0,0,0,  # 28 - 2f\n0,0,0,0,0,0,0,0,  # 30 - 37\n0,0,0,0,0,0,0,0,  # 38 - 3f\n6,0,4,0,8,0,0,0,  # 40 - 47\n0,9,5,0,0,0,0,0,  # 48 - 4f\n0,0,0,0,0,0,0,0,  # 50 - 57\n0,0,0,0,0,0,0,0,  # 58 - 5f\n0,0,0,0,0,0,0,0,  # 60 - 67\n0,0,0,0,0,0,0,0,  # 68 - 6f\n0,0,0,0,0,0,0,0,  # 70 - 77\n0,0,0,0,0,0,0,0,  # 78 - 7f\n2,2,2,2,2,2,2,2,  # 80 - 87\n2,2,2,2,2,2,2,2,  # 88 - 8f\n2,2,2,2,2,2,2,2,  # 90 - 97\n2,2,2,2,2,2,2,2,  # 98 - 9f\n2,2,2,2,2,2,2,2,  # a0 - a7\n2,2,2,2,2,2,2,2,  # a8 - af\n2,2,2,2,2,2,2,2,  # b0 - b7\n2,2,2,2,2,2,2,2,  # b8 - bf\n2,2,2,2,2,2,2,2,  # c0 - c7\n2,2,2,2,2,2,2,2,  # c8 - cf\n2,2,2,2,2,2,2,2,  # d0 - d7\n2,2,2,2,2,2,2,2,  # d8 - df\n2,2,2,2,2,2,2,2,  # e0 - e7\n2,2,2,2,2,2,2,2,  # e8 - ef\n2,2,2,2,2,2,2,2,  # f0 - f7\n2,2,2,2,2,2,2,2,  # f8 - ff\n)\n\nISO2022JP_ST = (\nMachineState.START,     3,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,# 00-07\nMachineState.START,MachineState.START,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,# 08-0f\nMachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,# 10-17\nMachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ERROR,MachineState.ERROR,# 18-1f\nMachineState.ERROR,     5,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,     4,MachineState.ERROR,MachineState.ERROR,# 20-27\nMachineState.ERROR,MachineState.ERROR,MachineState.ERROR,     6,MachineState.ITS_ME,MachineState.ERROR,MachineState.ITS_ME,MachineState.ERROR,# 28-2f\nMachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ITS_ME,# 30-37\nMachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,# 38-3f\nMachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ERROR,MachineState.START,MachineState.START,# 40-47\n)\n\nISO2022JP_CHAR_LEN_TABLE = (0, 0, 0, 0, 0, 0, 0, 0, 0, 0)\n\nISO2022JP_SM_MODEL = {'class_table': ISO2022JP_CLS,\n                      'class_factor': 10,\n                      'state_table': ISO2022JP_ST,\n                      'char_len_table': ISO2022JP_CHAR_LEN_TABLE,\n                      'name': \"ISO-2022-JP\",\n                      'language': 'Japanese'}\n\nISO2022KR_CLS = (\n2,0,0,0,0,0,0,0,  # 00 - 07\n0,0,0,0,0,0,0,0,  # 08 - 0f\n0,0,0,0,0,0,0,0,  # 10 - 17\n0,0,0,1,0,0,0,0,  # 18 - 1f\n0,0,0,0,3,0,0,0,  # 20 - 27\n0,4,0,0,0,0,0,0,  # 28 - 2f\n0,0,0,0,0,0,0,0,  # 30 - 37\n0,0,0,0,0,0,0,0,  # 38 - 3f\n0,0,0,5,0,0,0,0,  # 40 - 47\n0,0,0,0,0,0,0,0,  # 48 - 4f\n0,0,0,0,0,0,0,0,  # 50 - 57\n0,0,0,0,0,0,0,0,  # 58 - 5f\n0,0,0,0,0,0,0,0,  # 60 - 67\n0,0,0,0,0,0,0,0,  # 68 - 6f\n0,0,0,0,0,0,0,0,  # 70 - 77\n0,0,0,0,0,0,0,0,  # 78 - 7f\n2,2,2,2,2,2,2,2,  # 80 - 87\n2,2,2,2,2,2,2,2,  # 88 - 8f\n2,2,2,2,2,2,2,2,  # 90 - 97\n2,2,2,2,2,2,2,2,  # 98 - 9f\n2,2,2,2,2,2,2,2,  # a0 - a7\n2,2,2,2,2,2,2,2,  # a8 - af\n2,2,2,2,2,2,2,2,  # b0 - b7\n2,2,2,2,2,2,2,2,  # b8 - bf\n2,2,2,2,2,2,2,2,  # c0 - c7\n2,2,2,2,2,2,2,2,  # c8 - cf\n2,2,2,2,2,2,2,2,  # d0 - d7\n2,2,2,2,2,2,2,2,  # d8 - df\n2,2,2,2,2,2,2,2,  # e0 - e7\n2,2,2,2,2,2,2,2,  # e8 - ef\n2,2,2,2,2,2,2,2,  # f0 - f7\n2,2,2,2,2,2,2,2,  # f8 - ff\n)\n\nISO2022KR_ST = (\nMachineState.START,     3,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.ERROR,MachineState.ERROR,# 00-07\nMachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,# 08-0f\nMachineState.ITS_ME,MachineState.ITS_ME,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,     4,MachineState.ERROR,MachineState.ERROR,# 10-17\nMachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,     5,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,# 18-1f\nMachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.START,MachineState.START,MachineState.START,MachineState.START,# 20-27\n)\n\nISO2022KR_CHAR_LEN_TABLE = (0, 0, 0, 0, 0, 0)\n\nISO2022KR_SM_MODEL = {'class_table': ISO2022KR_CLS,\n                      'class_factor': 6,\n                      'state_table': ISO2022KR_ST,\n                      'char_len_table': ISO2022KR_CHAR_LEN_TABLE,\n                      'name': \"ISO-2022-KR\",\n                      'language': 'Korean'}\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/eucjpprober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is mozilla.org code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .enums import ProbingState, MachineState\nfrom .mbcharsetprober import MultiByteCharSetProber\nfrom .codingstatemachine import CodingStateMachine\nfrom .chardistribution import EUCJPDistributionAnalysis\nfrom .jpcntx import EUCJPContextAnalysis\nfrom .mbcssm import EUCJP_SM_MODEL\n\n\nclass EUCJPProber(MultiByteCharSetProber):\n    def __init__(self):\n        super(EUCJPProber, self).__init__()\n        self.coding_sm = CodingStateMachine(EUCJP_SM_MODEL)\n        self.distribution_analyzer = EUCJPDistributionAnalysis()\n        self.context_analyzer = EUCJPContextAnalysis()\n        self.reset()\n\n    def reset(self):\n        super(EUCJPProber, self).reset()\n        self.context_analyzer.reset()\n\n    @property\n    def charset_name(self):\n        return \"EUC-JP\"\n\n    @property\n    def language(self):\n        return \"Japanese\"\n\n    def feed(self, byte_str):\n        for i in range(len(byte_str)):\n            # PY3K: byte_str is a byte array, so byte_str[i] is an int, not a byte\n            coding_state = self.coding_sm.next_state(byte_str[i])\n            if coding_state == MachineState.ERROR:\n                self.logger.debug('%s %s prober hit error at byte %s',\n                                  self.charset_name, self.language, i)\n                self._state = ProbingState.NOT_ME\n                break\n            elif coding_state == MachineState.ITS_ME:\n                self._state = ProbingState.FOUND_IT\n                break\n            elif coding_state == MachineState.START:\n                char_len = self.coding_sm.get_current_charlen()\n                if i == 0:\n                    self._last_char[1] = byte_str[0]\n                    self.context_analyzer.feed(self._last_char, char_len)\n                    self.distribution_analyzer.feed(self._last_char, char_len)\n                else:\n                    self.context_analyzer.feed(byte_str[i - 1:i + 1],\n                                                char_len)\n                    self.distribution_analyzer.feed(byte_str[i - 1:i + 1],\n                                                     char_len)\n\n        self._last_char[0] = byte_str[-1]\n\n        if self.state == ProbingState.DETECTING:\n            if (self.context_analyzer.got_enough_data() and\n               (self.get_confidence() > self.SHORTCUT_THRESHOLD)):\n                self._state = ProbingState.FOUND_IT\n\n        return self.state\n\n    def get_confidence(self):\n        context_conf = self.context_analyzer.get_confidence()\n        distrib_conf = self.distribution_analyzer.get_confidence()\n        return max(context_conf, distrib_conf)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/euckrfreq.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n# Sampling from about 20M text materials include literature and computer technology\n\n# 128  --> 0.79\n# 256  --> 0.92\n# 512  --> 0.986\n# 1024 --> 0.99944\n# 2048 --> 0.99999\n#\n# Idea Distribution Ratio = 0.98653 / (1-0.98653) = 73.24\n# Random Distribution Ration = 512 / (2350-512) = 0.279.\n#\n# Typical Distribution Ratio\n\nEUCKR_TYPICAL_DISTRIBUTION_RATIO = 6.0\n\nEUCKR_TABLE_SIZE = 2352\n\n# Char to FreqOrder table ,\nEUCKR_CHAR_TO_FREQ_ORDER = (\n  13, 130, 120,1396, 481,1719,1720, 328, 609, 212,1721, 707, 400, 299,1722,  87,\n1397,1723, 104, 536,1117,1203,1724,1267, 685,1268, 508,1725,1726,1727,1728,1398,\n1399,1729,1730,1731, 141, 621, 326,1057, 368,1732, 267, 488,  20,1733,1269,1734,\n 945,1400,1735,  47, 904,1270,1736,1737, 773, 248,1738, 409, 313, 786, 429,1739,\n 116, 987, 813,1401, 683,  75,1204, 145,1740,1741,1742,1743,  16, 847, 667, 622,\n 708,1744,1745,1746, 966, 787, 304, 129,1747,  60, 820, 123, 676,1748,1749,1750,\n1751, 617,1752, 626,1753,1754,1755,1756, 653,1757,1758,1759,1760,1761,1762, 856,\n 344,1763,1764,1765,1766,  89, 401, 418, 806, 905, 848,1767,1768,1769, 946,1205,\n 709,1770,1118,1771, 241,1772,1773,1774,1271,1775, 569,1776, 999,1777,1778,1779,\n1780, 337, 751,1058,  28, 628, 254,1781, 177, 906, 270, 349, 891,1079,1782,  19,\n1783, 379,1784, 315,1785, 629, 754,1402, 559,1786, 636, 203,1206,1787, 710, 567,\n1788, 935, 814,1789,1790,1207, 766, 528,1791,1792,1208,1793,1794,1795,1796,1797,\n1403,1798,1799, 533,1059,1404,1405,1156,1406, 936, 884,1080,1800, 351,1801,1802,\n1803,1804,1805, 801,1806,1807,1808,1119,1809,1157, 714, 474,1407,1810, 298, 899,\n 885,1811,1120, 802,1158,1812, 892,1813,1814,1408, 659,1815,1816,1121,1817,1818,\n1819,1820,1821,1822, 319,1823, 594, 545,1824, 815, 937,1209,1825,1826, 573,1409,\n1022,1827,1210,1828,1829,1830,1831,1832,1833, 556, 722, 807,1122,1060,1834, 697,\n1835, 900, 557, 715,1836,1410, 540,1411, 752,1159, 294, 597,1211, 976, 803, 770,\n1412,1837,1838,  39, 794,1413, 358,1839, 371, 925,1840, 453, 661, 788, 531, 723,\n 544,1023,1081, 869,  91,1841, 392, 430, 790, 602,1414, 677,1082, 457,1415,1416,\n1842,1843, 475, 327,1024,1417, 795, 121,1844, 733, 403,1418,1845,1846,1847, 300,\n 119, 711,1212, 627,1848,1272, 207,1849,1850, 796,1213, 382,1851, 519,1852,1083,\n 893,1853,1854,1855, 367, 809, 487, 671,1856, 663,1857,1858, 956, 471, 306, 857,\n1859,1860,1160,1084,1861,1862,1863,1864,1865,1061,1866,1867,1868,1869,1870,1871,\n 282,  96, 574,1872, 502,1085,1873,1214,1874, 907,1875,1876, 827, 977,1419,1420,\n1421, 268,1877,1422,1878,1879,1880, 308,1881,   2, 537,1882,1883,1215,1884,1885,\n 127, 791,1886,1273,1423,1887,  34, 336, 404, 643,1888, 571, 654, 894, 840,1889,\n   0, 886,1274, 122, 575, 260, 908, 938,1890,1275, 410, 316,1891,1892, 100,1893,\n1894,1123,  48,1161,1124,1025,1895, 633, 901,1276,1896,1897, 115, 816,1898, 317,\n1899, 694,1900, 909, 734,1424, 572, 866,1425, 691,  85, 524,1010, 543, 394, 841,\n1901,1902,1903,1026,1904,1905,1906,1907,1908,1909,  30, 451, 651, 988, 310,1910,\n1911,1426, 810,1216,  93,1912,1913,1277,1217,1914, 858, 759,  45,  58, 181, 610,\n 269,1915,1916, 131,1062, 551, 443,1000, 821,1427, 957, 895,1086,1917,1918, 375,\n1919, 359,1920, 687,1921, 822,1922, 293,1923,1924,  40, 662, 118, 692,  29, 939,\n 887, 640, 482, 174,1925,  69,1162, 728,1428, 910,1926,1278,1218,1279, 386, 870,\n 217, 854,1163, 823,1927,1928,1929,1930, 834,1931,  78,1932, 859,1933,1063,1934,\n1935,1936,1937, 438,1164, 208, 595,1938,1939,1940,1941,1219,1125,1942, 280, 888,\n1429,1430,1220,1431,1943,1944,1945,1946,1947,1280, 150, 510,1432,1948,1949,1950,\n1951,1952,1953,1954,1011,1087,1955,1433,1043,1956, 881,1957, 614, 958,1064,1065,\n1221,1958, 638,1001, 860, 967, 896,1434, 989, 492, 553,1281,1165,1959,1282,1002,\n1283,1222,1960,1961,1962,1963,  36, 383, 228, 753, 247, 454,1964, 876, 678,1965,\n1966,1284, 126, 464, 490, 835, 136, 672, 529, 940,1088,1435, 473,1967,1968, 467,\n  50, 390, 227, 587, 279, 378, 598, 792, 968, 240, 151, 160, 849, 882,1126,1285,\n 639,1044, 133, 140, 288, 360, 811, 563,1027, 561, 142, 523,1969,1970,1971,   7,\n 103, 296, 439, 407, 506, 634, 990,1972,1973,1974,1975, 645,1976,1977,1978,1979,\n1980,1981, 236,1982,1436,1983,1984,1089, 192, 828, 618, 518,1166, 333,1127,1985,\n 818,1223,1986,1987,1988,1989,1990,1991,1992,1993, 342,1128,1286, 746, 842,1994,\n1995, 560, 223,1287,  98,   8, 189, 650, 978,1288,1996,1437,1997,  17, 345, 250,\n 423, 277, 234, 512, 226,  97, 289,  42, 167,1998, 201,1999,2000, 843, 836, 824,\n 532, 338, 783,1090, 182, 576, 436,1438,1439, 527, 500,2001, 947, 889,2002,2003,\n2004,2005, 262, 600, 314, 447,2006, 547,2007, 693, 738,1129,2008,  71,1440, 745,\n 619, 688,2009, 829,2010,2011, 147,2012,  33, 948,2013,2014,  74, 224,2015,  61,\n 191, 918, 399, 637,2016,1028,1130, 257, 902,2017,2018,2019,2020,2021,2022,2023,\n2024,2025,2026, 837,2027,2028,2029,2030, 179, 874, 591,  52, 724, 246,2031,2032,\n2033,2034,1167, 969,2035,1289, 630, 605, 911,1091,1168,2036,2037,2038,1441, 912,\n2039, 623,2040,2041, 253,1169,1290,2042,1442, 146, 620, 611, 577, 433,2043,1224,\n 719,1170, 959, 440, 437, 534,  84, 388, 480,1131, 159, 220, 198, 679,2044,1012,\n 819,1066,1443, 113,1225, 194, 318,1003,1029,2045,2046,2047,2048,1067,2049,2050,\n2051,2052,2053,  59, 913, 112,2054, 632,2055, 455, 144, 739,1291,2056, 273, 681,\n 499,2057, 448,2058,2059, 760,2060,2061, 970, 384, 169, 245,1132,2062,2063, 414,\n1444,2064,2065,  41, 235,2066, 157, 252, 877, 568, 919, 789, 580,2067, 725,2068,\n2069,1292,2070,2071,1445,2072,1446,2073,2074,  55, 588,  66,1447, 271,1092,2075,\n1226,2076, 960,1013, 372,2077,2078,2079,2080,2081,1293,2082,2083,2084,2085, 850,\n2086,2087,2088,2089,2090, 186,2091,1068, 180,2092,2093,2094, 109,1227, 522, 606,\n2095, 867,1448,1093, 991,1171, 926, 353,1133,2096, 581,2097,2098,2099,1294,1449,\n1450,2100, 596,1172,1014,1228,2101,1451,1295,1173,1229,2102,2103,1296,1134,1452,\n 949,1135,2104,2105,1094,1453,1454,1455,2106,1095,2107,2108,2109,2110,2111,2112,\n2113,2114,2115,2116,2117, 804,2118,2119,1230,1231, 805,1456, 405,1136,2120,2121,\n2122,2123,2124, 720, 701,1297, 992,1457, 927,1004,2125,2126,2127,2128,2129,2130,\n  22, 417,2131, 303,2132, 385,2133, 971, 520, 513,2134,1174,  73,1096, 231, 274,\n 962,1458, 673,2135,1459,2136, 152,1137,2137,2138,2139,2140,1005,1138,1460,1139,\n2141,2142,2143,2144,  11, 374, 844,2145, 154,1232,  46,1461,2146, 838, 830, 721,\n1233, 106,2147,  90, 428, 462, 578, 566,1175, 352,2148,2149, 538,1234, 124,1298,\n2150,1462, 761, 565,2151, 686,2152, 649,2153,  72, 173,2154, 460, 415,2155,1463,\n2156,1235, 305,2157,2158,2159,2160,2161,2162, 579,2163,2164,2165,2166,2167, 747,\n2168,2169,2170,2171,1464, 669,2172,2173,2174,2175,2176,1465,2177,  23, 530, 285,\n2178, 335, 729,2179, 397,2180,2181,2182,1030,2183,2184, 698,2185,2186, 325,2187,\n2188, 369,2189, 799,1097,1015, 348,2190,1069, 680,2191, 851,1466,2192,2193,  10,\n2194, 613, 424,2195, 979, 108, 449, 589,  27, 172,  81,1031,  80, 774, 281, 350,\n1032, 525, 301, 582,1176,2196, 674,1045,2197,2198,1467, 730, 762,2199,2200,2201,\n2202,1468,2203, 993,2204,2205, 266,1070, 963,1140,2206,2207,2208, 664,1098, 972,\n2209,2210,2211,1177,1469,1470, 871,2212,2213,2214,2215,2216,1471,2217,2218,2219,\n2220,2221,2222,2223,2224,2225,2226,2227,1472,1236,2228,2229,2230,2231,2232,2233,\n2234,2235,1299,2236,2237, 200,2238, 477, 373,2239,2240, 731, 825, 777,2241,2242,\n2243, 521, 486, 548,2244,2245,2246,1473,1300,  53, 549, 137, 875,  76, 158,2247,\n1301,1474, 469, 396,1016, 278, 712,2248, 321, 442, 503, 767, 744, 941,1237,1178,\n1475,2249,  82, 178,1141,1179, 973,2250,1302,2251, 297,2252,2253, 570,2254,2255,\n2256,  18, 450, 206,2257, 290, 292,1142,2258, 511, 162,  99, 346, 164, 735,2259,\n1476,1477,   4, 554, 343, 798,1099,2260,1100,2261,  43, 171,1303, 139, 215,2262,\n2263, 717, 775,2264,1033, 322, 216,2265, 831,2266, 149,2267,1304,2268,2269, 702,\n1238, 135, 845, 347, 309,2270, 484,2271, 878, 655, 238,1006,1478,2272,  67,2273,\n 295,2274,2275, 461,2276, 478, 942, 412,2277,1034,2278,2279,2280, 265,2281, 541,\n2282,2283,2284,2285,2286,  70, 852,1071,2287,2288,2289,2290,  21,  56, 509, 117,\n 432,2291,2292, 331, 980, 552,1101, 148, 284, 105, 393,1180,1239, 755,2293, 187,\n2294,1046,1479,2295, 340,2296,  63,1047, 230,2297,2298,1305, 763,1306, 101, 800,\n 808, 494,2299,2300,2301, 903,2302,  37,1072,  14,   5,2303,  79, 675,2304, 312,\n2305,2306,2307,2308,2309,1480,   6,1307,2310,2311,2312,   1, 470,  35,  24, 229,\n2313, 695, 210,  86, 778,  15, 784, 592, 779,  32,  77, 855, 964,2314, 259,2315,\n 501, 380,2316,2317,  83, 981, 153, 689,1308,1481,1482,1483,2318,2319, 716,1484,\n2320,2321,2322,2323,2324,2325,1485,2326,2327, 128,  57,  68, 261,1048, 211, 170,\n1240,  31,2328,  51, 435, 742,2329,2330,2331, 635,2332, 264, 456,2333,2334,2335,\n 425,2336,1486, 143, 507, 263, 943,2337, 363, 920,1487, 256,1488,1102, 243, 601,\n1489,2338,2339,2340,2341,2342,2343,2344, 861,2345,2346,2347,2348,2349,2350, 395,\n2351,1490,1491,  62, 535, 166, 225,2352,2353, 668, 419,1241, 138, 604, 928,2354,\n1181,2355,1492,1493,2356,2357,2358,1143,2359, 696,2360, 387, 307,1309, 682, 476,\n2361,2362, 332,  12, 222, 156,2363, 232,2364, 641, 276, 656, 517,1494,1495,1035,\n 416, 736,1496,2365,1017, 586,2366,2367,2368,1497,2369, 242,2370,2371,2372,1498,\n2373, 965, 713,2374,2375,2376,2377, 740, 982,1499, 944,1500,1007,2378,2379,1310,\n1501,2380,2381,2382, 785, 329,2383,2384,1502,2385,2386,2387, 932,2388,1503,2389,\n2390,2391,2392,1242,2393,2394,2395,2396,2397, 994, 950,2398,2399,2400,2401,1504,\n1311,2402,2403,2404,2405,1049, 749,2406,2407, 853, 718,1144,1312,2408,1182,1505,\n2409,2410, 255, 516, 479, 564, 550, 214,1506,1507,1313, 413, 239, 444, 339,1145,\n1036,1508,1509,1314,1037,1510,1315,2411,1511,2412,2413,2414, 176, 703, 497, 624,\n 593, 921, 302,2415, 341, 165,1103,1512,2416,1513,2417,2418,2419, 376,2420, 700,\n2421,2422,2423, 258, 768,1316,2424,1183,2425, 995, 608,2426,2427,2428,2429, 221,\n2430,2431,2432,2433,2434,2435,2436,2437, 195, 323, 726, 188, 897, 983,1317, 377,\n 644,1050, 879,2438, 452,2439,2440,2441,2442,2443,2444, 914,2445,2446,2447,2448,\n 915, 489,2449,1514,1184,2450,2451, 515,  64, 427, 495,2452, 583,2453, 483, 485,\n1038, 562, 213,1515, 748, 666,2454,2455,2456,2457, 334,2458, 780, 996,1008, 705,\n1243,2459,2460,2461,2462,2463, 114,2464, 493,1146, 366, 163,1516, 961,1104,2465,\n 291,2466,1318,1105,2467,1517, 365,2468, 355, 951,1244,2469,1319,2470, 631,2471,\n2472, 218,1320, 364, 320, 756,1518,1519,1321,1520,1322,2473,2474,2475,2476, 997,\n2477,2478,2479,2480, 665,1185,2481, 916,1521,2482,2483,2484, 584, 684,2485,2486,\n 797,2487,1051,1186,2488,2489,2490,1522,2491,2492, 370,2493,1039,1187,  65,2494,\n 434, 205, 463,1188,2495, 125, 812, 391, 402, 826, 699, 286, 398, 155, 781, 771,\n 585,2496, 590, 505,1073,2497, 599, 244, 219, 917,1018, 952, 646,1523,2498,1323,\n2499,2500,  49, 984, 354, 741,2501, 625,2502,1324,2503,1019, 190, 357, 757, 491,\n  95, 782, 868,2504,2505,2506,2507,2508,2509, 134,1524,1074, 422,1525, 898,2510,\n 161,2511,2512,2513,2514, 769,2515,1526,2516,2517, 411,1325,2518, 472,1527,2519,\n2520,2521,2522,2523,2524, 985,2525,2526,2527,2528,2529,2530, 764,2531,1245,2532,\n2533,  25, 204, 311,2534, 496,2535,1052,2536,2537,2538,2539,2540,2541,2542, 199,\n 704, 504, 468, 758, 657,1528, 196,  44, 839,1246, 272, 750,2543, 765, 862,2544,\n2545,1326,2546, 132, 615, 933,2547, 732,2548,2549,2550,1189,1529,2551, 283,1247,\n1053, 607, 929,2552,2553,2554, 930, 183, 872, 616,1040,1147,2555,1148,1020, 441,\n 249,1075,2556,2557,2558, 466, 743,2559,2560,2561,  92, 514, 426, 420, 526,2562,\n2563,2564,2565,2566,2567,2568, 185,2569,2570,2571,2572, 776,1530, 658,2573, 362,\n2574, 361, 922,1076, 793,2575,2576,2577,2578,2579,2580,1531, 251,2581,2582,2583,\n2584,1532,  54, 612, 237,1327,2585,2586, 275, 408, 647, 111,2587,1533,1106, 465,\n   3, 458,   9,  38,2588, 107, 110, 890, 209,  26, 737, 498,2589,1534,2590, 431,\n 202,  88,1535, 356, 287,1107, 660,1149,2591, 381,1536, 986,1150, 445,1248,1151,\n 974,2592,2593, 846,2594, 446, 953, 184,1249,1250, 727,2595, 923, 193, 883,2596,\n2597,2598, 102, 324, 539, 817,2599, 421,1041,2600, 832,2601,  94, 175, 197, 406,\n2602, 459,2603,2604,2605,2606,2607, 330, 555,2608,2609,2610, 706,1108, 389,2611,\n2612,2613,2614, 233,2615, 833, 558, 931, 954,1251,2616,2617,1537, 546,2618,2619,\n1009,2620,2621,2622,1538, 690,1328,2623, 955,2624,1539,2625,2626, 772,2627,2628,\n2629,2630,2631, 924, 648, 863, 603,2632,2633, 934,1540, 864, 865,2634, 642,1042,\n 670,1190,2635,2636,2637,2638, 168,2639, 652, 873, 542,1054,1541,2640,2641,2642,  # 512, 256\n)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/euckrprober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is mozilla.org code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .mbcharsetprober import MultiByteCharSetProber\nfrom .codingstatemachine import CodingStateMachine\nfrom .chardistribution import EUCKRDistributionAnalysis\nfrom .mbcssm import EUCKR_SM_MODEL\n\n\nclass EUCKRProber(MultiByteCharSetProber):\n    def __init__(self):\n        super(EUCKRProber, self).__init__()\n        self.coding_sm = CodingStateMachine(EUCKR_SM_MODEL)\n        self.distribution_analyzer = EUCKRDistributionAnalysis()\n        self.reset()\n\n    @property\n    def charset_name(self):\n        return \"EUC-KR\"\n\n    @property\n    def language(self):\n        return \"Korean\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/euctwfreq.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n# EUCTW frequency table\n# Converted from big5 work\n# by Taiwan's Mandarin Promotion Council\n# <http:#www.edu.tw:81/mandr/>\n\n# 128  --> 0.42261\n# 256  --> 0.57851\n# 512  --> 0.74851\n# 1024 --> 0.89384\n# 2048 --> 0.97583\n#\n# Idea Distribution Ratio = 0.74851/(1-0.74851) =2.98\n# Random Distribution Ration = 512/(5401-512)=0.105\n#\n# Typical Distribution Ratio about 25% of Ideal one, still much higher than RDR\n\nEUCTW_TYPICAL_DISTRIBUTION_RATIO = 0.75\n\n# Char to FreqOrder table ,\nEUCTW_TABLE_SIZE = 5376\n\nEUCTW_CHAR_TO_FREQ_ORDER = (\n   1,1800,1506, 255,1431, 198,   9,  82,   6,7310, 177, 202,3615,1256,2808, 110,  # 2742\n3735,  33,3241, 261,  76,  44,2113,  16,2931,2184,1176, 659,3868,  26,3404,2643,  # 2758\n1198,3869,3313,4060, 410,2211, 302, 590, 361,1963,   8, 204,  58,4296,7311,1931,  # 2774\n  63,7312,7313, 317,1614,  75, 222, 159,4061,2412,1480,7314,3500,3068, 224,2809,  # 2790\n3616,   3,  10,3870,1471,  29,2774,1135,2852,1939, 873, 130,3242,1123, 312,7315,  # 2806\n4297,2051, 507, 252, 682,7316, 142,1914, 124, 206,2932,  34,3501,3173,  64, 604,  # 2822\n7317,2494,1976,1977, 155,1990, 645, 641,1606,7318,3405, 337,  72, 406,7319,  80,  # 2838\n 630, 238,3174,1509, 263, 939,1092,2644, 756,1440,1094,3406, 449,  69,2969, 591,  # 2854\n 179,2095, 471, 115,2034,1843,  60,  50,2970, 134, 806,1868, 734,2035,3407, 180,  # 2870\n 995,1607, 156, 537,2893, 688,7320, 319,1305, 779,2144, 514,2374, 298,4298, 359,  # 2886\n2495,  90,2707,1338, 663,  11, 906,1099,2545,  20,2436, 182, 532,1716,7321, 732,  # 2902\n1376,4062,1311,1420,3175,  25,2312,1056, 113, 399, 382,1949, 242,3408,2467, 529,  # 2918\n3243, 475,1447,3617,7322, 117,  21, 656, 810,1297,2295,2329,3502,7323, 126,4063,  # 2934\n 706, 456, 150, 613,4299,  71,1118,2036,4064, 145,3069,  85, 835, 486,2114,1246,  # 2950\n1426, 428, 727,1285,1015, 800, 106, 623, 303,1281,7324,2127,2354, 347,3736, 221,  # 2966\n3503,3110,7325,1955,1153,4065,  83, 296,1199,3070, 192, 624,  93,7326, 822,1897,  # 2982\n2810,3111, 795,2064, 991,1554,1542,1592,  27,  43,2853, 859, 139,1456, 860,4300,  # 2998\n 437, 712,3871, 164,2392,3112, 695, 211,3017,2096, 195,3872,1608,3504,3505,3618,  # 3014\n3873, 234, 811,2971,2097,3874,2229,1441,3506,1615,2375, 668,2076,1638, 305, 228,  # 3030\n1664,4301, 467, 415,7327, 262,2098,1593, 239, 108, 300, 200,1033, 512,1247,2077,  # 3046\n7328,7329,2173,3176,3619,2673, 593, 845,1062,3244,  88,1723,2037,3875,1950, 212,  # 3062\n 266, 152, 149, 468,1898,4066,4302,  77, 187,7330,3018,  37,   5,2972,7331,3876,  # 3078\n7332,7333,  39,2517,4303,2894,3177,2078,  55, 148,  74,4304, 545, 483,1474,1029,  # 3094\n1665, 217,1869,1531,3113,1104,2645,4067,  24, 172,3507, 900,3877,3508,3509,4305,  # 3110\n  32,1408,2811,1312, 329, 487,2355,2247,2708, 784,2674,   4,3019,3314,1427,1788,  # 3126\n 188, 109, 499,7334,3620,1717,1789, 888,1217,3020,4306,7335,3510,7336,3315,1520,  # 3142\n3621,3878, 196,1034, 775,7337,7338, 929,1815, 249, 439,  38,7339,1063,7340, 794,  # 3158\n3879,1435,2296,  46, 178,3245,2065,7341,2376,7342, 214,1709,4307, 804,  35, 707,  # 3174\n 324,3622,1601,2546, 140, 459,4068,7343,7344,1365, 839, 272, 978,2257,2572,3409,  # 3190\n2128,1363,3623,1423, 697, 100,3071,  48,  70,1231, 495,3114,2193,7345,1294,7346,  # 3206\n2079, 462, 586,1042,3246, 853, 256, 988, 185,2377,3410,1698, 434,1084,7347,3411,  # 3222\n 314,2615,2775,4308,2330,2331, 569,2280, 637,1816,2518, 757,1162,1878,1616,3412,  # 3238\n 287,1577,2115, 768,4309,1671,2854,3511,2519,1321,3737, 909,2413,7348,4069, 933,  # 3254\n3738,7349,2052,2356,1222,4310, 765,2414,1322, 786,4311,7350,1919,1462,1677,2895,  # 3270\n1699,7351,4312,1424,2437,3115,3624,2590,3316,1774,1940,3413,3880,4070, 309,1369,  # 3286\n1130,2812, 364,2230,1653,1299,3881,3512,3882,3883,2646, 525,1085,3021, 902,2000,  # 3302\n1475, 964,4313, 421,1844,1415,1057,2281, 940,1364,3116, 376,4314,4315,1381,   7,  # 3318\n2520, 983,2378, 336,1710,2675,1845, 321,3414, 559,1131,3022,2742,1808,1132,1313,  # 3334\n 265,1481,1857,7352, 352,1203,2813,3247, 167,1089, 420,2814, 776, 792,1724,3513,  # 3350\n4071,2438,3248,7353,4072,7354, 446, 229, 333,2743, 901,3739,1200,1557,4316,2647,  # 3366\n1920, 395,2744,2676,3740,4073,1835, 125, 916,3178,2616,4317,7355,7356,3741,7357,  # 3382\n7358,7359,4318,3117,3625,1133,2547,1757,3415,1510,2313,1409,3514,7360,2145, 438,  # 3398\n2591,2896,2379,3317,1068, 958,3023, 461, 311,2855,2677,4074,1915,3179,4075,1978,  # 3414\n 383, 750,2745,2617,4076, 274, 539, 385,1278,1442,7361,1154,1964, 384, 561, 210,  # 3430\n  98,1295,2548,3515,7362,1711,2415,1482,3416,3884,2897,1257, 129,7363,3742, 642,  # 3446\n 523,2776,2777,2648,7364, 141,2231,1333,  68, 176, 441, 876, 907,4077, 603,2592,  # 3462\n 710, 171,3417, 404, 549,  18,3118,2393,1410,3626,1666,7365,3516,4319,2898,4320,  # 3478\n7366,2973, 368,7367, 146, 366,  99, 871,3627,1543, 748, 807,1586,1185,  22,2258,  # 3494\n 379,3743,3180,7368,3181, 505,1941,2618,1991,1382,2314,7369, 380,2357, 218, 702,  # 3510\n1817,1248,3418,3024,3517,3318,3249,7370,2974,3628, 930,3250,3744,7371,  59,7372,  # 3526\n 585, 601,4078, 497,3419,1112,1314,4321,1801,7373,1223,1472,2174,7374, 749,1836,  # 3542\n 690,1899,3745,1772,3885,1476, 429,1043,1790,2232,2116, 917,4079, 447,1086,1629,  # 3558\n7375, 556,7376,7377,2020,1654, 844,1090, 105, 550, 966,1758,2815,1008,1782, 686,  # 3574\n1095,7378,2282, 793,1602,7379,3518,2593,4322,4080,2933,2297,4323,3746, 980,2496,  # 3590\n 544, 353, 527,4324, 908,2678,2899,7380, 381,2619,1942,1348,7381,1341,1252, 560,  # 3606\n3072,7382,3420,2856,7383,2053, 973, 886,2080, 143,4325,7384,7385, 157,3886, 496,  # 3622\n4081,  57, 840, 540,2038,4326,4327,3421,2117,1445, 970,2259,1748,1965,2081,4082,  # 3638\n3119,1234,1775,3251,2816,3629, 773,1206,2129,1066,2039,1326,3887,1738,1725,4083,  # 3654\n 279,3120,  51,1544,2594, 423,1578,2130,2066, 173,4328,1879,7386,7387,1583, 264,  # 3670\n 610,3630,4329,2439, 280, 154,7388,7389,7390,1739, 338,1282,3073, 693,2857,1411,  # 3686\n1074,3747,2440,7391,4330,7392,7393,1240, 952,2394,7394,2900,1538,2679, 685,1483,  # 3702\n4084,2468,1436, 953,4085,2054,4331, 671,2395,  79,4086,2441,3252, 608, 567,2680,  # 3718\n3422,4087,4088,1691, 393,1261,1791,2396,7395,4332,7396,7397,7398,7399,1383,1672,  # 3734\n3748,3182,1464, 522,1119, 661,1150, 216, 675,4333,3888,1432,3519, 609,4334,2681,  # 3750\n2397,7400,7401,7402,4089,3025,   0,7403,2469, 315, 231,2442, 301,3319,4335,2380,  # 3766\n7404, 233,4090,3631,1818,4336,4337,7405,  96,1776,1315,2082,7406, 257,7407,1809,  # 3782\n3632,2709,1139,1819,4091,2021,1124,2163,2778,1777,2649,7408,3074, 363,1655,3183,  # 3798\n7409,2975,7410,7411,7412,3889,1567,3890, 718, 103,3184, 849,1443, 341,3320,2934,  # 3814\n1484,7413,1712, 127,  67, 339,4092,2398, 679,1412, 821,7414,7415, 834, 738, 351,  # 3830\n2976,2146, 846, 235,1497,1880, 418,1992,3749,2710, 186,1100,2147,2746,3520,1545,  # 3846\n1355,2935,2858,1377, 583,3891,4093,2573,2977,7416,1298,3633,1078,2549,3634,2358,  # 3862\n  78,3750,3751, 267,1289,2099,2001,1594,4094, 348, 369,1274,2194,2175,1837,4338,  # 3878\n1820,2817,3635,2747,2283,2002,4339,2936,2748, 144,3321, 882,4340,3892,2749,3423,  # 3894\n4341,2901,7417,4095,1726, 320,7418,3893,3026, 788,2978,7419,2818,1773,1327,2859,  # 3910\n3894,2819,7420,1306,4342,2003,1700,3752,3521,2359,2650, 787,2022, 506, 824,3636,  # 3926\n 534, 323,4343,1044,3322,2023,1900, 946,3424,7421,1778,1500,1678,7422,1881,4344,  # 3942\n 165, 243,4345,3637,2521, 123, 683,4096, 764,4346,  36,3895,1792, 589,2902, 816,  # 3958\n 626,1667,3027,2233,1639,1555,1622,3753,3896,7423,3897,2860,1370,1228,1932, 891,  # 3974\n2083,2903, 304,4097,7424, 292,2979,2711,3522, 691,2100,4098,1115,4347, 118, 662,  # 3990\n7425, 611,1156, 854,2381,1316,2861,   2, 386, 515,2904,7426,7427,3253, 868,2234,  # 4006\n1486, 855,2651, 785,2212,3028,7428,1040,3185,3523,7429,3121, 448,7430,1525,7431,  # 4022\n2164,4348,7432,3754,7433,4099,2820,3524,3122, 503, 818,3898,3123,1568, 814, 676,  # 4038\n1444, 306,1749,7434,3755,1416,1030, 197,1428, 805,2821,1501,4349,7435,7436,7437,  # 4054\n1993,7438,4350,7439,7440,2195,  13,2779,3638,2980,3124,1229,1916,7441,3756,2131,  # 4070\n7442,4100,4351,2399,3525,7443,2213,1511,1727,1120,7444,7445, 646,3757,2443, 307,  # 4086\n7446,7447,1595,3186,7448,7449,7450,3639,1113,1356,3899,1465,2522,2523,7451, 519,  # 4102\n7452, 128,2132,  92,2284,1979,7453,3900,1512, 342,3125,2196,7454,2780,2214,1980,  # 4118\n3323,7455, 290,1656,1317, 789, 827,2360,7456,3758,4352, 562, 581,3901,7457, 401,  # 4134\n4353,2248,  94,4354,1399,2781,7458,1463,2024,4355,3187,1943,7459, 828,1105,4101,  # 4150\n1262,1394,7460,4102, 605,4356,7461,1783,2862,7462,2822, 819,2101, 578,2197,2937,  # 4166\n7463,1502, 436,3254,4103,3255,2823,3902,2905,3425,3426,7464,2712,2315,7465,7466,  # 4182\n2332,2067,  23,4357, 193, 826,3759,2102, 699,1630,4104,3075, 390,1793,1064,3526,  # 4198\n7467,1579,3076,3077,1400,7468,4105,1838,1640,2863,7469,4358,4359, 137,4106, 598,  # 4214\n3078,1966, 780, 104, 974,2938,7470, 278, 899, 253, 402, 572, 504, 493,1339,7471,  # 4230\n3903,1275,4360,2574,2550,7472,3640,3029,3079,2249, 565,1334,2713, 863,  41,7473,  # 4246\n7474,4361,7475,1657,2333,  19, 463,2750,4107, 606,7476,2981,3256,1087,2084,1323,  # 4262\n2652,2982,7477,1631,1623,1750,4108,2682,7478,2864, 791,2714,2653,2334, 232,2416,  # 4278\n7479,2983,1498,7480,2654,2620, 755,1366,3641,3257,3126,2025,1609, 119,1917,3427,  # 4294\n 862,1026,4109,7481,3904,3760,4362,3905,4363,2260,1951,2470,7482,1125, 817,4110,  # 4310\n4111,3906,1513,1766,2040,1487,4112,3030,3258,2824,3761,3127,7483,7484,1507,7485,  # 4326\n2683, 733,  40,1632,1106,2865, 345,4113, 841,2524, 230,4364,2984,1846,3259,3428,  # 4342\n7486,1263, 986,3429,7487, 735, 879, 254,1137, 857, 622,1300,1180,1388,1562,3907,  # 4358\n3908,2939, 967,2751,2655,1349, 592,2133,1692,3324,2985,1994,4114,1679,3909,1901,  # 4374\n2185,7488, 739,3642,2715,1296,1290,7489,4115,2198,2199,1921,1563,2595,2551,1870,  # 4390\n2752,2986,7490, 435,7491, 343,1108, 596,  17,1751,4365,2235,3430,3643,7492,4366,  # 4406\n 294,3527,2940,1693, 477, 979, 281,2041,3528, 643,2042,3644,2621,2782,2261,1031,  # 4422\n2335,2134,2298,3529,4367, 367,1249,2552,7493,3530,7494,4368,1283,3325,2004, 240,  # 4438\n1762,3326,4369,4370, 836,1069,3128, 474,7495,2148,2525, 268,3531,7496,3188,1521,  # 4454\n1284,7497,1658,1546,4116,7498,3532,3533,7499,4117,3327,2684,1685,4118, 961,1673,  # 4470\n2622, 190,2005,2200,3762,4371,4372,7500, 570,2497,3645,1490,7501,4373,2623,3260,  # 4486\n1956,4374, 584,1514, 396,1045,1944,7502,4375,1967,2444,7503,7504,4376,3910, 619,  # 4502\n7505,3129,3261, 215,2006,2783,2553,3189,4377,3190,4378, 763,4119,3763,4379,7506,  # 4518\n7507,1957,1767,2941,3328,3646,1174, 452,1477,4380,3329,3130,7508,2825,1253,2382,  # 4534\n2186,1091,2285,4120, 492,7509, 638,1169,1824,2135,1752,3911, 648, 926,1021,1324,  # 4550\n4381, 520,4382, 997, 847,1007, 892,4383,3764,2262,1871,3647,7510,2400,1784,4384,  # 4566\n1952,2942,3080,3191,1728,4121,2043,3648,4385,2007,1701,3131,1551,  30,2263,4122,  # 4582\n7511,2026,4386,3534,7512, 501,7513,4123, 594,3431,2165,1821,3535,3432,3536,3192,  # 4598\n 829,2826,4124,7514,1680,3132,1225,4125,7515,3262,4387,4126,3133,2336,7516,4388,  # 4614\n4127,7517,3912,3913,7518,1847,2383,2596,3330,7519,4389, 374,3914, 652,4128,4129,  # 4630\n 375,1140, 798,7520,7521,7522,2361,4390,2264, 546,1659, 138,3031,2445,4391,7523,  # 4646\n2250, 612,1848, 910, 796,3765,1740,1371, 825,3766,3767,7524,2906,2554,7525, 692,  # 4662\n 444,3032,2624, 801,4392,4130,7526,1491, 244,1053,3033,4131,4132, 340,7527,3915,  # 4678\n1041,2987, 293,1168,  87,1357,7528,1539, 959,7529,2236, 721, 694,4133,3768, 219,  # 4694\n1478, 644,1417,3331,2656,1413,1401,1335,1389,3916,7530,7531,2988,2362,3134,1825,  # 4710\n 730,1515, 184,2827,  66,4393,7532,1660,2943, 246,3332, 378,1457, 226,3433, 975,  # 4726\n3917,2944,1264,3537, 674, 696,7533, 163,7534,1141,2417,2166, 713,3538,3333,4394,  # 4742\n3918,7535,7536,1186,  15,7537,1079,1070,7538,1522,3193,3539, 276,1050,2716, 758,  # 4758\n1126, 653,2945,3263,7539,2337, 889,3540,3919,3081,2989, 903,1250,4395,3920,3434,  # 4774\n3541,1342,1681,1718, 766,3264, 286,  89,2946,3649,7540,1713,7541,2597,3334,2990,  # 4790\n7542,2947,2215,3194,2866,7543,4396,2498,2526, 181, 387,1075,3921, 731,2187,3335,  # 4806\n7544,3265, 310, 313,3435,2299, 770,4134,  54,3034, 189,4397,3082,3769,3922,7545,  # 4822\n1230,1617,1849, 355,3542,4135,4398,3336, 111,4136,3650,1350,3135,3436,3035,4137,  # 4838\n2149,3266,3543,7546,2784,3923,3924,2991, 722,2008,7547,1071, 247,1207,2338,2471,  # 4854\n1378,4399,2009, 864,1437,1214,4400, 373,3770,1142,2216, 667,4401, 442,2753,2555,  # 4870\n3771,3925,1968,4138,3267,1839, 837, 170,1107, 934,1336,1882,7548,7549,2118,4139,  # 4886\n2828, 743,1569,7550,4402,4140, 582,2384,1418,3437,7551,1802,7552, 357,1395,1729,  # 4902\n3651,3268,2418,1564,2237,7553,3083,3772,1633,4403,1114,2085,4141,1532,7554, 482,  # 4918\n2446,4404,7555,7556,1492, 833,1466,7557,2717,3544,1641,2829,7558,1526,1272,3652,  # 4934\n4142,1686,1794, 416,2556,1902,1953,1803,7559,3773,2785,3774,1159,2316,7560,2867,  # 4950\n4405,1610,1584,3036,2419,2754, 443,3269,1163,3136,7561,7562,3926,7563,4143,2499,  # 4966\n3037,4406,3927,3137,2103,1647,3545,2010,1872,4144,7564,4145, 431,3438,7565, 250,  # 4982\n  97,  81,4146,7566,1648,1850,1558, 160, 848,7567, 866, 740,1694,7568,2201,2830,  # 4998\n3195,4147,4407,3653,1687, 950,2472, 426, 469,3196,3654,3655,3928,7569,7570,1188,  # 5014\n 424,1995, 861,3546,4148,3775,2202,2685, 168,1235,3547,4149,7571,2086,1674,4408,  # 5030\n3337,3270, 220,2557,1009,7572,3776, 670,2992, 332,1208, 717,7573,7574,3548,2447,  # 5046\n3929,3338,7575, 513,7576,1209,2868,3339,3138,4409,1080,7577,7578,7579,7580,2527,  # 5062\n3656,3549, 815,1587,3930,3931,7581,3550,3439,3777,1254,4410,1328,3038,1390,3932,  # 5078\n1741,3933,3778,3934,7582, 236,3779,2448,3271,7583,7584,3657,3780,1273,3781,4411,  # 5094\n7585, 308,7586,4412, 245,4413,1851,2473,1307,2575, 430, 715,2136,2449,7587, 270,  # 5110\n 199,2869,3935,7588,3551,2718,1753, 761,1754, 725,1661,1840,4414,3440,3658,7589,  # 5126\n7590, 587,  14,3272, 227,2598, 326, 480,2265, 943,2755,3552, 291, 650,1883,7591,  # 5142\n1702,1226, 102,1547,  62,3441, 904,4415,3442,1164,4150,7592,7593,1224,1548,2756,  # 5158\n 391, 498,1493,7594,1386,1419,7595,2055,1177,4416, 813, 880,1081,2363, 566,1145,  # 5174\n4417,2286,1001,1035,2558,2599,2238, 394,1286,7596,7597,2068,7598,  86,1494,1730,  # 5190\n3936, 491,1588, 745, 897,2948, 843,3340,3937,2757,2870,3273,1768, 998,2217,2069,  # 5206\n 397,1826,1195,1969,3659,2993,3341, 284,7599,3782,2500,2137,2119,1903,7600,3938,  # 5222\n2150,3939,4151,1036,3443,1904, 114,2559,4152, 209,1527,7601,7602,2949,2831,2625,  # 5238\n2385,2719,3139, 812,2560,7603,3274,7604,1559, 737,1884,3660,1210, 885,  28,2686,  # 5254\n3553,3783,7605,4153,1004,1779,4418,7606, 346,1981,2218,2687,4419,3784,1742, 797,  # 5270\n1642,3940,1933,1072,1384,2151, 896,3941,3275,3661,3197,2871,3554,7607,2561,1958,  # 5286\n4420,2450,1785,7608,7609,7610,3942,4154,1005,1308,3662,4155,2720,4421,4422,1528,  # 5302\n2600, 161,1178,4156,1982, 987,4423,1101,4157, 631,3943,1157,3198,2420,1343,1241,  # 5318\n1016,2239,2562, 372, 877,2339,2501,1160, 555,1934, 911,3944,7611, 466,1170, 169,  # 5334\n1051,2907,2688,3663,2474,2994,1182,2011,2563,1251,2626,7612, 992,2340,3444,1540,  # 5350\n2721,1201,2070,2401,1996,2475,7613,4424, 528,1922,2188,1503,1873,1570,2364,3342,  # 5366\n3276,7614, 557,1073,7615,1827,3445,2087,2266,3140,3039,3084, 767,3085,2786,4425,  # 5382\n1006,4158,4426,2341,1267,2176,3664,3199, 778,3945,3200,2722,1597,2657,7616,4427,  # 5398\n7617,3446,7618,7619,7620,3277,2689,1433,3278, 131,  95,1504,3946, 723,4159,3141,  # 5414\n1841,3555,2758,2189,3947,2027,2104,3665,7621,2995,3948,1218,7622,3343,3201,3949,  # 5430\n4160,2576, 248,1634,3785, 912,7623,2832,3666,3040,3786, 654,  53,7624,2996,7625,  # 5446\n1688,4428, 777,3447,1032,3950,1425,7626, 191, 820,2120,2833, 971,4429, 931,3202,  # 5462\n 135, 664, 783,3787,1997, 772,2908,1935,3951,3788,4430,2909,3203, 282,2723, 640,  # 5478\n1372,3448,1127, 922, 325,3344,7627,7628, 711,2044,7629,7630,3952,2219,2787,1936,  # 5494\n3953,3345,2220,2251,3789,2300,7631,4431,3790,1258,3279,3954,3204,2138,2950,3955,  # 5510\n3956,7632,2221, 258,3205,4432, 101,1227,7633,3280,1755,7634,1391,3281,7635,2910,  # 5526\n2056, 893,7636,7637,7638,1402,4161,2342,7639,7640,3206,3556,7641,7642, 878,1325,  # 5542\n1780,2788,4433, 259,1385,2577, 744,1183,2267,4434,7643,3957,2502,7644, 684,1024,  # 5558\n4162,7645, 472,3557,3449,1165,3282,3958,3959, 322,2152, 881, 455,1695,1152,1340,  # 5574\n 660, 554,2153,4435,1058,4436,4163, 830,1065,3346,3960,4437,1923,7646,1703,1918,  # 5590\n7647, 932,2268, 122,7648,4438, 947, 677,7649,3791,2627, 297,1905,1924,2269,4439,  # 5606\n2317,3283,7650,7651,4164,7652,4165,  84,4166, 112, 989,7653, 547,1059,3961, 701,  # 5622\n3558,1019,7654,4167,7655,3450, 942, 639, 457,2301,2451, 993,2951, 407, 851, 494,  # 5638\n4440,3347, 927,7656,1237,7657,2421,3348, 573,4168, 680, 921,2911,1279,1874, 285,  # 5654\n 790,1448,1983, 719,2167,7658,7659,4441,3962,3963,1649,7660,1541, 563,7661,1077,  # 5670\n7662,3349,3041,3451, 511,2997,3964,3965,3667,3966,1268,2564,3350,3207,4442,4443,  # 5686\n7663, 535,1048,1276,1189,2912,2028,3142,1438,1373,2834,2952,1134,2012,7664,4169,  # 5702\n1238,2578,3086,1259,7665, 700,7666,2953,3143,3668,4170,7667,4171,1146,1875,1906,  # 5718\n4444,2601,3967, 781,2422, 132,1589, 203, 147, 273,2789,2402, 898,1786,2154,3968,  # 5734\n3969,7668,3792,2790,7669,7670,4445,4446,7671,3208,7672,1635,3793, 965,7673,1804,  # 5750\n2690,1516,3559,1121,1082,1329,3284,3970,1449,3794,  65,1128,2835,2913,2759,1590,  # 5766\n3795,7674,7675,  12,2658,  45, 976,2579,3144,4447, 517,2528,1013,1037,3209,7676,  # 5782\n3796,2836,7677,3797,7678,3452,7679,2602, 614,1998,2318,3798,3087,2724,2628,7680,  # 5798\n2580,4172, 599,1269,7681,1810,3669,7682,2691,3088, 759,1060, 489,1805,3351,3285,  # 5814\n1358,7683,7684,2386,1387,1215,2629,2252, 490,7685,7686,4173,1759,2387,2343,7687,  # 5830\n4448,3799,1907,3971,2630,1806,3210,4449,3453,3286,2760,2344, 874,7688,7689,3454,  # 5846\n3670,1858,  91,2914,3671,3042,3800,4450,7690,3145,3972,2659,7691,3455,1202,1403,  # 5862\n3801,2954,2529,1517,2503,4451,3456,2504,7692,4452,7693,2692,1885,1495,1731,3973,  # 5878\n2365,4453,7694,2029,7695,7696,3974,2693,1216, 237,2581,4174,2319,3975,3802,4454,  # 5894\n4455,2694,3560,3457, 445,4456,7697,7698,7699,7700,2761,  61,3976,3672,1822,3977,  # 5910\n7701, 687,2045, 935, 925, 405,2660, 703,1096,1859,2725,4457,3978,1876,1367,2695,  # 5926\n3352, 918,2105,1781,2476, 334,3287,1611,1093,4458, 564,3146,3458,3673,3353, 945,  # 5942\n2631,2057,4459,7702,1925, 872,4175,7703,3459,2696,3089, 349,4176,3674,3979,4460,  # 5958\n3803,4177,3675,2155,3980,4461,4462,4178,4463,2403,2046, 782,3981, 400, 251,4179,  # 5974\n1624,7704,7705, 277,3676, 299,1265, 476,1191,3804,2121,4180,4181,1109, 205,7706,  # 5990\n2582,1000,2156,3561,1860,7707,7708,7709,4464,7710,4465,2565, 107,2477,2157,3982,  # 6006\n3460,3147,7711,1533, 541,1301, 158, 753,4182,2872,3562,7712,1696, 370,1088,4183,  # 6022\n4466,3563, 579, 327, 440, 162,2240, 269,1937,1374,3461, 968,3043,  56,1396,3090,  # 6038\n2106,3288,3354,7713,1926,2158,4467,2998,7714,3564,7715,7716,3677,4468,2478,7717,  # 6054\n2791,7718,1650,4469,7719,2603,7720,7721,3983,2661,3355,1149,3356,3984,3805,3985,  # 6070\n7722,1076,  49,7723, 951,3211,3289,3290, 450,2837, 920,7724,1811,2792,2366,4184,  # 6086\n1908,1138,2367,3806,3462,7725,3212,4470,1909,1147,1518,2423,4471,3807,7726,4472,  # 6102\n2388,2604, 260,1795,3213,7727,7728,3808,3291, 708,7729,3565,1704,7730,3566,1351,  # 6118\n1618,3357,2999,1886, 944,4185,3358,4186,3044,3359,4187,7731,3678, 422, 413,1714,  # 6134\n3292, 500,2058,2345,4188,2479,7732,1344,1910, 954,7733,1668,7734,7735,3986,2404,  # 6150\n4189,3567,3809,4190,7736,2302,1318,2505,3091, 133,3092,2873,4473, 629,  31,2838,  # 6166\n2697,3810,4474, 850, 949,4475,3987,2955,1732,2088,4191,1496,1852,7737,3988, 620,  # 6182\n3214, 981,1242,3679,3360,1619,3680,1643,3293,2139,2452,1970,1719,3463,2168,7738,  # 6198\n3215,7739,7740,3361,1828,7741,1277,4476,1565,2047,7742,1636,3568,3093,7743, 869,  # 6214\n2839, 655,3811,3812,3094,3989,3000,3813,1310,3569,4477,7744,7745,7746,1733, 558,  # 6230\n4478,3681, 335,1549,3045,1756,4192,3682,1945,3464,1829,1291,1192, 470,2726,2107,  # 6246\n2793, 913,1054,3990,7747,1027,7748,3046,3991,4479, 982,2662,3362,3148,3465,3216,  # 6262\n3217,1946,2794,7749, 571,4480,7750,1830,7751,3570,2583,1523,2424,7752,2089, 984,  # 6278\n4481,3683,1959,7753,3684, 852, 923,2795,3466,3685, 969,1519, 999,2048,2320,1705,  # 6294\n7754,3095, 615,1662, 151, 597,3992,2405,2321,1049, 275,4482,3686,4193, 568,3687,  # 6310\n3571,2480,4194,3688,7755,2425,2270, 409,3218,7756,1566,2874,3467,1002, 769,2840,  # 6326\n 194,2090,3149,3689,2222,3294,4195, 628,1505,7757,7758,1763,2177,3001,3993, 521,  # 6342\n1161,2584,1787,2203,2406,4483,3994,1625,4196,4197, 412,  42,3096, 464,7759,2632,  # 6358\n4484,3363,1760,1571,2875,3468,2530,1219,2204,3814,2633,2140,2368,4485,4486,3295,  # 6374\n1651,3364,3572,7760,7761,3573,2481,3469,7762,3690,7763,7764,2271,2091, 460,7765,  # 6390\n4487,7766,3002, 962, 588,3574, 289,3219,2634,1116,  52,7767,3047,1796,7768,7769,  # 6406\n7770,1467,7771,1598,1143,3691,4198,1984,1734,1067,4488,1280,3365, 465,4489,1572,  # 6422\n 510,7772,1927,2241,1812,1644,3575,7773,4490,3692,7774,7775,2663,1573,1534,7776,  # 6438\n7777,4199, 536,1807,1761,3470,3815,3150,2635,7778,7779,7780,4491,3471,2915,1911,  # 6454\n2796,7781,3296,1122, 377,3220,7782, 360,7783,7784,4200,1529, 551,7785,2059,3693,  # 6470\n1769,2426,7786,2916,4201,3297,3097,2322,2108,2030,4492,1404, 136,1468,1479, 672,  # 6486\n1171,3221,2303, 271,3151,7787,2762,7788,2049, 678,2727, 865,1947,4493,7789,2013,  # 6502\n3995,2956,7790,2728,2223,1397,3048,3694,4494,4495,1735,2917,3366,3576,7791,3816,  # 6518\n 509,2841,2453,2876,3817,7792,7793,3152,3153,4496,4202,2531,4497,2304,1166,1010,  # 6534\n 552, 681,1887,7794,7795,2957,2958,3996,1287,1596,1861,3154, 358, 453, 736, 175,  # 6550\n 478,1117, 905,1167,1097,7796,1853,1530,7797,1706,7798,2178,3472,2287,3695,3473,  # 6566\n3577,4203,2092,4204,7799,3367,1193,2482,4205,1458,2190,2205,1862,1888,1421,3298,  # 6582\n2918,3049,2179,3474, 595,2122,7800,3997,7801,7802,4206,1707,2636, 223,3696,1359,  # 6598\n 751,3098, 183,3475,7803,2797,3003, 419,2369, 633, 704,3818,2389, 241,7804,7805,  # 6614\n7806, 838,3004,3697,2272,2763,2454,3819,1938,2050,3998,1309,3099,2242,1181,7807,  # 6630\n1136,2206,3820,2370,1446,4207,2305,4498,7808,7809,4208,1055,2605, 484,3698,7810,  # 6646\n3999, 625,4209,2273,3368,1499,4210,4000,7811,4001,4211,3222,2274,2275,3476,7812,  # 6662\n7813,2764, 808,2606,3699,3369,4002,4212,3100,2532, 526,3370,3821,4213, 955,7814,  # 6678\n1620,4214,2637,2427,7815,1429,3700,1669,1831, 994, 928,7816,3578,1260,7817,7818,  # 6694\n7819,1948,2288, 741,2919,1626,4215,2729,2455, 867,1184, 362,3371,1392,7820,7821,  # 6710\n4003,4216,1770,1736,3223,2920,4499,4500,1928,2698,1459,1158,7822,3050,3372,2877,  # 6726\n1292,1929,2506,2842,3701,1985,1187,2071,2014,2607,4217,7823,2566,2507,2169,3702,  # 6742\n2483,3299,7824,3703,4501,7825,7826, 666,1003,3005,1022,3579,4218,7827,4502,1813,  # 6758\n2253, 574,3822,1603, 295,1535, 705,3823,4219, 283, 858, 417,7828,7829,3224,4503,  # 6774\n4504,3051,1220,1889,1046,2276,2456,4004,1393,1599, 689,2567, 388,4220,7830,2484,  # 6790\n 802,7831,2798,3824,2060,1405,2254,7832,4505,3825,2109,1052,1345,3225,1585,7833,  # 6806\n 809,7834,7835,7836, 575,2730,3477, 956,1552,1469,1144,2323,7837,2324,1560,2457,  # 6822\n3580,3226,4005, 616,2207,3155,2180,2289,7838,1832,7839,3478,4506,7840,1319,3704,  # 6838\n3705,1211,3581,1023,3227,1293,2799,7841,7842,7843,3826, 607,2306,3827, 762,2878,  # 6854\n1439,4221,1360,7844,1485,3052,7845,4507,1038,4222,1450,2061,2638,4223,1379,4508,  # 6870\n2585,7846,7847,4224,1352,1414,2325,2921,1172,7848,7849,3828,3829,7850,1797,1451,  # 6886\n7851,7852,7853,7854,2922,4006,4007,2485,2346, 411,4008,4009,3582,3300,3101,4509,  # 6902\n1561,2664,1452,4010,1375,7855,7856,  47,2959, 316,7857,1406,1591,2923,3156,7858,  # 6918\n1025,2141,3102,3157, 354,2731, 884,2224,4225,2407, 508,3706, 726,3583, 996,2428,  # 6934\n3584, 729,7859, 392,2191,1453,4011,4510,3707,7860,7861,2458,3585,2608,1675,2800,  # 6950\n 919,2347,2960,2348,1270,4511,4012,  73,7862,7863, 647,7864,3228,2843,2255,1550,  # 6966\n1346,3006,7865,1332, 883,3479,7866,7867,7868,7869,3301,2765,7870,1212, 831,1347,  # 6982\n4226,4512,2326,3830,1863,3053, 720,3831,4513,4514,3832,7871,4227,7872,7873,4515,  # 6998\n7874,7875,1798,4516,3708,2609,4517,3586,1645,2371,7876,7877,2924, 669,2208,2665,  # 7014\n2429,7878,2879,7879,7880,1028,3229,7881,4228,2408,7882,2256,1353,7883,7884,4518,  # 7030\n3158, 518,7885,4013,7886,4229,1960,7887,2142,4230,7888,7889,3007,2349,2350,3833,  # 7046\n 516,1833,1454,4014,2699,4231,4519,2225,2610,1971,1129,3587,7890,2766,7891,2961,  # 7062\n1422, 577,1470,3008,1524,3373,7892,7893, 432,4232,3054,3480,7894,2586,1455,2508,  # 7078\n2226,1972,1175,7895,1020,2732,4015,3481,4520,7896,2733,7897,1743,1361,3055,3482,  # 7094\n2639,4016,4233,4521,2290, 895, 924,4234,2170, 331,2243,3056, 166,1627,3057,1098,  # 7110\n7898,1232,2880,2227,3374,4522, 657, 403,1196,2372, 542,3709,3375,1600,4235,3483,  # 7126\n7899,4523,2767,3230, 576, 530,1362,7900,4524,2533,2666,3710,4017,7901, 842,3834,  # 7142\n7902,2801,2031,1014,4018, 213,2700,3376, 665, 621,4236,7903,3711,2925,2430,7904,  # 7158\n2431,3302,3588,3377,7905,4237,2534,4238,4525,3589,1682,4239,3484,1380,7906, 724,  # 7174\n2277, 600,1670,7907,1337,1233,4526,3103,2244,7908,1621,4527,7909, 651,4240,7910,  # 7190\n1612,4241,2611,7911,2844,7912,2734,2307,3058,7913, 716,2459,3059, 174,1255,2701,  # 7206\n4019,3590, 548,1320,1398, 728,4020,1574,7914,1890,1197,3060,4021,7915,3061,3062,  # 7222\n3712,3591,3713, 747,7916, 635,4242,4528,7917,7918,7919,4243,7920,7921,4529,7922,  # 7238\n3378,4530,2432, 451,7923,3714,2535,2072,4244,2735,4245,4022,7924,1764,4531,7925,  # 7254\n4246, 350,7926,2278,2390,2486,7927,4247,4023,2245,1434,4024, 488,4532, 458,4248,  # 7270\n4025,3715, 771,1330,2391,3835,2568,3159,2159,2409,1553,2667,3160,4249,7928,2487,  # 7286\n2881,2612,1720,2702,4250,3379,4533,7929,2536,4251,7930,3231,4252,2768,7931,2015,  # 7302\n2736,7932,1155,1017,3716,3836,7933,3303,2308, 201,1864,4253,1430,7934,4026,7935,  # 7318\n7936,7937,7938,7939,4254,1604,7940, 414,1865, 371,2587,4534,4535,3485,2016,3104,  # 7334\n4536,1708, 960,4255, 887, 389,2171,1536,1663,1721,7941,2228,4027,2351,2926,1580,  # 7350\n7942,7943,7944,1744,7945,2537,4537,4538,7946,4539,7947,2073,7948,7949,3592,3380,  # 7366\n2882,4256,7950,4257,2640,3381,2802, 673,2703,2460, 709,3486,4028,3593,4258,7951,  # 7382\n1148, 502, 634,7952,7953,1204,4540,3594,1575,4541,2613,3717,7954,3718,3105, 948,  # 7398\n3232, 121,1745,3837,1110,7955,4259,3063,2509,3009,4029,3719,1151,1771,3838,1488,  # 7414\n4030,1986,7956,2433,3487,7957,7958,2093,7959,4260,3839,1213,1407,2803, 531,2737,  # 7430\n2538,3233,1011,1537,7960,2769,4261,3106,1061,7961,3720,3721,1866,2883,7962,2017,  # 7446\n 120,4262,4263,2062,3595,3234,2309,3840,2668,3382,1954,4542,7963,7964,3488,1047,  # 7462\n2704,1266,7965,1368,4543,2845, 649,3383,3841,2539,2738,1102,2846,2669,7966,7967,  # 7478\n1999,7968,1111,3596,2962,7969,2488,3842,3597,2804,1854,3384,3722,7970,7971,3385,  # 7494\n2410,2884,3304,3235,3598,7972,2569,7973,3599,2805,4031,1460, 856,7974,3600,7975,  # 7510\n2885,2963,7976,2886,3843,7977,4264, 632,2510, 875,3844,1697,3845,2291,7978,7979,  # 7526\n4544,3010,1239, 580,4545,4265,7980, 914, 936,2074,1190,4032,1039,2123,7981,7982,  # 7542\n7983,3386,1473,7984,1354,4266,3846,7985,2172,3064,4033, 915,3305,4267,4268,3306,  # 7558\n1605,1834,7986,2739, 398,3601,4269,3847,4034, 328,1912,2847,4035,3848,1331,4270,  # 7574\n3011, 937,4271,7987,3602,4036,4037,3387,2160,4546,3388, 524, 742, 538,3065,1012,  # 7590\n7988,7989,3849,2461,7990, 658,1103, 225,3850,7991,7992,4547,7993,4548,7994,3236,  # 7606\n1243,7995,4038, 963,2246,4549,7996,2705,3603,3161,7997,7998,2588,2327,7999,4550,  # 7622\n8000,8001,8002,3489,3307, 957,3389,2540,2032,1930,2927,2462, 870,2018,3604,1746,  # 7638\n2770,2771,2434,2463,8003,3851,8004,3723,3107,3724,3490,3390,3725,8005,1179,3066,  # 7654\n8006,3162,2373,4272,3726,2541,3163,3108,2740,4039,8007,3391,1556,2542,2292, 977,  # 7670\n2887,2033,4040,1205,3392,8008,1765,3393,3164,2124,1271,1689, 714,4551,3491,8009,  # 7686\n2328,3852, 533,4273,3605,2181, 617,8010,2464,3308,3492,2310,8011,8012,3165,8013,  # 7702\n8014,3853,1987, 618, 427,2641,3493,3394,8015,8016,1244,1690,8017,2806,4274,4552,  # 7718\n8018,3494,8019,8020,2279,1576, 473,3606,4275,3395, 972,8021,3607,8022,3067,8023,  # 7734\n8024,4553,4554,8025,3727,4041,4042,8026, 153,4555, 356,8027,1891,2888,4276,2143,  # 7750\n 408, 803,2352,8028,3854,8029,4277,1646,2570,2511,4556,4557,3855,8030,3856,4278,  # 7766\n8031,2411,3396, 752,8032,8033,1961,2964,8034, 746,3012,2465,8035,4279,3728, 698,  # 7782\n4558,1892,4280,3608,2543,4559,3609,3857,8036,3166,3397,8037,1823,1302,4043,2706,  # 7798\n3858,1973,4281,8038,4282,3167, 823,1303,1288,1236,2848,3495,4044,3398, 774,3859,  # 7814\n8039,1581,4560,1304,2849,3860,4561,8040,2435,2161,1083,3237,4283,4045,4284, 344,  # 7830\n1173, 288,2311, 454,1683,8041,8042,1461,4562,4046,2589,8043,8044,4563, 985, 894,  # 7846\n8045,3399,3168,8046,1913,2928,3729,1988,8047,2110,1974,8048,4047,8049,2571,1194,  # 7862\n 425,8050,4564,3169,1245,3730,4285,8051,8052,2850,8053, 636,4565,1855,3861, 760,  # 7878\n1799,8054,4286,2209,1508,4566,4048,1893,1684,2293,8055,8056,8057,4287,4288,2210,  # 7894\n 479,8058,8059, 832,8060,4049,2489,8061,2965,2490,3731, 990,3109, 627,1814,2642,  # 7910\n4289,1582,4290,2125,2111,3496,4567,8062, 799,4291,3170,8063,4568,2112,1737,3013,  # 7926\n1018, 543, 754,4292,3309,1676,4569,4570,4050,8064,1489,8065,3497,8066,2614,2889,  # 7942\n4051,8067,8068,2966,8069,8070,8071,8072,3171,4571,4572,2182,1722,8073,3238,3239,  # 7958\n1842,3610,1715, 481, 365,1975,1856,8074,8075,1962,2491,4573,8076,2126,3611,3240,  # 7974\n 433,1894,2063,2075,8077, 602,2741,8078,8079,8080,8081,8082,3014,1628,3400,8083,  # 7990\n3172,4574,4052,2890,4575,2512,8084,2544,2772,8085,8086,8087,3310,4576,2891,8088,  # 8006\n4577,8089,2851,4578,4579,1221,2967,4053,2513,8090,8091,8092,1867,1989,8093,8094,  # 8022\n8095,1895,8096,8097,4580,1896,4054, 318,8098,2094,4055,4293,8099,8100, 485,8101,  # 8038\n 938,3862, 553,2670, 116,8102,3863,3612,8103,3498,2671,2773,3401,3311,2807,8104,  # 8054\n3613,2929,4056,1747,2930,2968,8105,8106, 207,8107,8108,2672,4581,2514,8109,3015,  # 8070\n 890,3614,3864,8110,1877,3732,3402,8111,2183,2353,3403,1652,8112,8113,8114, 941,  # 8086\n2294, 208,3499,4057,2019, 330,4294,3865,2892,2492,3733,4295,8115,8116,8117,8118,  # 8102\n)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/euctwprober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is mozilla.org code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .mbcharsetprober import MultiByteCharSetProber\nfrom .codingstatemachine import CodingStateMachine\nfrom .chardistribution import EUCTWDistributionAnalysis\nfrom .mbcssm import EUCTW_SM_MODEL\n\nclass EUCTWProber(MultiByteCharSetProber):\n    def __init__(self):\n        super(EUCTWProber, self).__init__()\n        self.coding_sm = CodingStateMachine(EUCTW_SM_MODEL)\n        self.distribution_analyzer = EUCTWDistributionAnalysis()\n        self.reset()\n\n    @property\n    def charset_name(self):\n        return \"EUC-TW\"\n\n    @property\n    def language(self):\n        return \"Taiwan\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/gb2312freq.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n# GB2312 most frequently used character table\n#\n# Char to FreqOrder table , from hz6763\n\n# 512  --> 0.79  -- 0.79\n# 1024 --> 0.92  -- 0.13\n# 2048 --> 0.98  -- 0.06\n# 6768 --> 1.00  -- 0.02\n#\n# Ideal Distribution Ratio = 0.79135/(1-0.79135) = 3.79\n# Random Distribution Ration = 512 / (3755 - 512) = 0.157\n#\n# Typical Distribution Ratio about 25% of Ideal one, still much higher that RDR\n\nGB2312_TYPICAL_DISTRIBUTION_RATIO = 0.9\n\nGB2312_TABLE_SIZE = 3760\n\nGB2312_CHAR_TO_FREQ_ORDER = (\n1671, 749,1443,2364,3924,3807,2330,3921,1704,3463,2691,1511,1515, 572,3191,2205,\n2361, 224,2558, 479,1711, 963,3162, 440,4060,1905,2966,2947,3580,2647,3961,3842,\n2204, 869,4207, 970,2678,5626,2944,2956,1479,4048, 514,3595, 588,1346,2820,3409,\n 249,4088,1746,1873,2047,1774, 581,1813, 358,1174,3590,1014,1561,4844,2245, 670,\n1636,3112, 889,1286, 953, 556,2327,3060,1290,3141, 613, 185,3477,1367, 850,3820,\n1715,2428,2642,2303,2732,3041,2562,2648,3566,3946,1349, 388,3098,2091,1360,3585,\n 152,1687,1539, 738,1559,  59,1232,2925,2267,1388,1249,1741,1679,2960, 151,1566,\n1125,1352,4271, 924,4296, 385,3166,4459, 310,1245,2850,  70,3285,2729,3534,3575,\n2398,3298,3466,1960,2265, 217,3647, 864,1909,2084,4401,2773,1010,3269,5152, 853,\n3051,3121,1244,4251,1895, 364,1499,1540,2313,1180,3655,2268, 562, 715,2417,3061,\n 544, 336,3768,2380,1752,4075, 950, 280,2425,4382, 183,2759,3272, 333,4297,2155,\n1688,2356,1444,1039,4540, 736,1177,3349,2443,2368,2144,2225, 565, 196,1482,3406,\n 927,1335,4147, 692, 878,1311,1653,3911,3622,1378,4200,1840,2969,3149,2126,1816,\n2534,1546,2393,2760, 737,2494,  13, 447, 245,2747,  38,2765,2129,2589,1079, 606,\n 360, 471,3755,2890, 404, 848, 699,1785,1236, 370,2221,1023,3746,2074,2026,2023,\n2388,1581,2119, 812,1141,3091,2536,1519, 804,2053, 406,1596,1090, 784, 548,4414,\n1806,2264,2936,1100, 343,4114,5096, 622,3358, 743,3668,1510,1626,5020,3567,2513,\n3195,4115,5627,2489,2991,  24,2065,2697,1087,2719,  48,1634, 315,  68, 985,2052,\n 198,2239,1347,1107,1439, 597,2366,2172, 871,3307, 919,2487,2790,1867, 236,2570,\n1413,3794, 906,3365,3381,1701,1982,1818,1524,2924,1205, 616,2586,2072,2004, 575,\n 253,3099,  32,1365,1182, 197,1714,2454,1201, 554,3388,3224,2748, 756,2587, 250,\n2567,1507,1517,3529,1922,2761,2337,3416,1961,1677,2452,2238,3153, 615, 911,1506,\n1474,2495,1265,1906,2749,3756,3280,2161, 898,2714,1759,3450,2243,2444, 563,  26,\n3286,2266,3769,3344,2707,3677, 611,1402, 531,1028,2871,4548,1375, 261,2948, 835,\n1190,4134, 353, 840,2684,1900,3082,1435,2109,1207,1674, 329,1872,2781,4055,2686,\n2104, 608,3318,2423,2957,2768,1108,3739,3512,3271,3985,2203,1771,3520,1418,2054,\n1681,1153, 225,1627,2929, 162,2050,2511,3687,1954, 124,1859,2431,1684,3032,2894,\n 585,4805,3969,2869,2704,2088,2032,2095,3656,2635,4362,2209, 256, 518,2042,2105,\n3777,3657, 643,2298,1148,1779, 190, 989,3544, 414,  11,2135,2063,2979,1471, 403,\n3678, 126, 770,1563, 671,2499,3216,2877, 600,1179, 307,2805,4937,1268,1297,2694,\n 252,4032,1448,1494,1331,1394, 127,2256, 222,1647,1035,1481,3056,1915,1048, 873,\n3651, 210,  33,1608,2516, 200,1520, 415, 102,   0,3389,1287, 817,  91,3299,2940,\n 836,1814, 549,2197,1396,1669,2987,3582,2297,2848,4528,1070, 687,  20,1819, 121,\n1552,1364,1461,1968,2617,3540,2824,2083, 177, 948,4938,2291, 110,4549,2066, 648,\n3359,1755,2110,2114,4642,4845,1693,3937,3308,1257,1869,2123, 208,1804,3159,2992,\n2531,2549,3361,2418,1350,2347,2800,2568,1291,2036,2680,  72, 842,1990, 212,1233,\n1154,1586,  75,2027,3410,4900,1823,1337,2710,2676, 728,2810,1522,3026,4995, 157,\n 755,1050,4022, 710, 785,1936,2194,2085,1406,2777,2400, 150,1250,4049,1206, 807,\n1910, 534, 529,3309,1721,1660, 274,  39,2827, 661,2670,1578, 925,3248,3815,1094,\n4278,4901,4252,  41,1150,3747,2572,2227,4501,3658,4902,3813,3357,3617,2884,2258,\n 887, 538,4187,3199,1294,2439,3042,2329,2343,2497,1255, 107, 543,1527, 521,3478,\n3568, 194,5062,  15, 961,3870,1241,1192,2664,  66,5215,3260,2111,1295,1127,2152,\n3805,4135, 901,1164,1976, 398,1278, 530,1460, 748, 904,1054,1966,1426,  53,2909,\n 509, 523,2279,1534, 536,1019, 239,1685, 460,2353, 673,1065,2401,3600,4298,2272,\n1272,2363, 284,1753,3679,4064,1695,  81, 815,2677,2757,2731,1386, 859, 500,4221,\n2190,2566, 757,1006,2519,2068,1166,1455, 337,2654,3203,1863,1682,1914,3025,1252,\n1409,1366, 847, 714,2834,2038,3209, 964,2970,1901, 885,2553,1078,1756,3049, 301,\n1572,3326, 688,2130,1996,2429,1805,1648,2930,3421,2750,3652,3088, 262,1158,1254,\n 389,1641,1812, 526,1719, 923,2073,1073,1902, 468, 489,4625,1140, 857,2375,3070,\n3319,2863, 380, 116,1328,2693,1161,2244, 273,1212,1884,2769,3011,1775,1142, 461,\n3066,1200,2147,2212, 790, 702,2695,4222,1601,1058, 434,2338,5153,3640,  67,2360,\n4099,2502, 618,3472,1329, 416,1132, 830,2782,1807,2653,3211,3510,1662, 192,2124,\n 296,3979,1739,1611,3684,  23, 118, 324, 446,1239,1225, 293,2520,3814,3795,2535,\n3116,  17,1074, 467,2692,2201, 387,2922,  45,1326,3055,1645,3659,2817, 958, 243,\n1903,2320,1339,2825,1784,3289, 356, 576, 865,2315,2381,3377,3916,1088,3122,1713,\n1655, 935, 628,4689,1034,1327, 441, 800, 720, 894,1979,2183,1528,5289,2702,1071,\n4046,3572,2399,1571,3281,  79, 761,1103, 327, 134, 758,1899,1371,1615, 879, 442,\n 215,2605,2579, 173,2048,2485,1057,2975,3317,1097,2253,3801,4263,1403,1650,2946,\n 814,4968,3487,1548,2644,1567,1285,   2, 295,2636,  97, 946,3576, 832, 141,4257,\n3273, 760,3821,3521,3156,2607, 949,1024,1733,1516,1803,1920,2125,2283,2665,3180,\n1501,2064,3560,2171,1592, 803,3518,1416, 732,3897,4258,1363,1362,2458, 119,1427,\n 602,1525,2608,1605,1639,3175, 694,3064,  10, 465,  76,2000,4846,4208, 444,3781,\n1619,3353,2206,1273,3796, 740,2483, 320,1723,2377,3660,2619,1359,1137,1762,1724,\n2345,2842,1850,1862, 912, 821,1866, 612,2625,1735,2573,3369,1093, 844,  89, 937,\n 930,1424,3564,2413,2972,1004,3046,3019,2011, 711,3171,1452,4178, 428, 801,1943,\n 432, 445,2811, 206,4136,1472, 730, 349,  73, 397,2802,2547, 998,1637,1167, 789,\n 396,3217, 154,1218, 716,1120,1780,2819,4826,1931,3334,3762,2139,1215,2627, 552,\n3664,3628,3232,1405,2383,3111,1356,2652,3577,3320,3101,1703, 640,1045,1370,1246,\n4996, 371,1575,2436,1621,2210, 984,4033,1734,2638,  16,4529, 663,2755,3255,1451,\n3917,2257,1253,1955,2234,1263,2951, 214,1229, 617, 485, 359,1831,1969, 473,2310,\n 750,2058, 165,  80,2864,2419, 361,4344,2416,2479,1134, 796,3726,1266,2943, 860,\n2715, 938, 390,2734,1313,1384, 248, 202, 877,1064,2854, 522,3907, 279,1602, 297,\n2357, 395,3740, 137,2075, 944,4089,2584,1267,3802,  62,1533,2285, 178, 176, 780,\n2440, 201,3707, 590, 478,1560,4354,2117,1075,  30,  74,4643,4004,1635,1441,2745,\n 776,2596, 238,1077,1692,1912,2844, 605, 499,1742,3947, 241,3053, 980,1749, 936,\n2640,4511,2582, 515,1543,2162,5322,2892,2993, 890,2148,1924, 665,1827,3581,1032,\n 968,3163, 339,1044,1896, 270, 583,1791,1720,4367,1194,3488,3669,  43,2523,1657,\n 163,2167, 290,1209,1622,3378, 550, 634,2508,2510, 695,2634,2384,2512,1476,1414,\n 220,1469,2341,2138,2852,3183,2900,4939,2865,3502,1211,3680, 854,3227,1299,2976,\n3172, 186,2998,1459, 443,1067,3251,1495, 321,1932,3054, 909, 753,1410,1828, 436,\n2441,1119,1587,3164,2186,1258, 227, 231,1425,1890,3200,3942, 247, 959, 725,5254,\n2741, 577,2158,2079, 929, 120, 174, 838,2813, 591,1115, 417,2024,  40,3240,1536,\n1037, 291,4151,2354, 632,1298,2406,2500,3535,1825,1846,3451, 205,1171, 345,4238,\n  18,1163, 811, 685,2208,1217, 425,1312,1508,1175,4308,2552,1033, 587,1381,3059,\n2984,3482, 340,1316,4023,3972, 792,3176, 519, 777,4690, 918, 933,4130,2981,3741,\n  90,3360,2911,2200,5184,4550, 609,3079,2030, 272,3379,2736, 363,3881,1130,1447,\n 286, 779, 357,1169,3350,3137,1630,1220,2687,2391, 747,1277,3688,2618,2682,2601,\n1156,3196,5290,4034,3102,1689,3596,3128, 874, 219,2783, 798, 508,1843,2461, 269,\n1658,1776,1392,1913,2983,3287,2866,2159,2372, 829,4076,  46,4253,2873,1889,1894,\n 915,1834,1631,2181,2318, 298, 664,2818,3555,2735, 954,3228,3117, 527,3511,2173,\n 681,2712,3033,2247,2346,3467,1652, 155,2164,3382, 113,1994, 450, 899, 494, 994,\n1237,2958,1875,2336,1926,3727, 545,1577,1550, 633,3473, 204,1305,3072,2410,1956,\n2471, 707,2134, 841,2195,2196,2663,3843,1026,4940, 990,3252,4997, 368,1092, 437,\n3212,3258,1933,1829, 675,2977,2893, 412, 943,3723,4644,3294,3283,2230,2373,5154,\n2389,2241,2661,2323,1404,2524, 593, 787, 677,3008,1275,2059, 438,2709,2609,2240,\n2269,2246,1446,  36,1568,1373,3892,1574,2301,1456,3962, 693,2276,5216,2035,1143,\n2720,1919,1797,1811,2763,4137,2597,1830,1699,1488,1198,2090, 424,1694, 312,3634,\n3390,4179,3335,2252,1214, 561,1059,3243,2295,2561, 975,5155,2321,2751,3772, 472,\n1537,3282,3398,1047,2077,2348,2878,1323,3340,3076, 690,2906,  51, 369, 170,3541,\n1060,2187,2688,3670,2541,1083,1683, 928,3918, 459, 109,4427, 599,3744,4286, 143,\n2101,2730,2490,  82,1588,3036,2121, 281,1860, 477,4035,1238,2812,3020,2716,3312,\n1530,2188,2055,1317, 843, 636,1808,1173,3495, 649, 181,1002, 147,3641,1159,2414,\n3750,2289,2795, 813,3123,2610,1136,4368,   5,3391,4541,2174, 420, 429,1728, 754,\n1228,2115,2219, 347,2223,2733, 735,1518,3003,2355,3134,1764,3948,3329,1888,2424,\n1001,1234,1972,3321,3363,1672,1021,1450,1584, 226, 765, 655,2526,3404,3244,2302,\n3665, 731, 594,2184, 319,1576, 621, 658,2656,4299,2099,3864,1279,2071,2598,2739,\n 795,3086,3699,3908,1707,2352,2402,1382,3136,2475,1465,4847,3496,3865,1085,3004,\n2591,1084, 213,2287,1963,3565,2250, 822, 793,4574,3187,1772,1789,3050, 595,1484,\n1959,2770,1080,2650, 456, 422,2996, 940,3322,4328,4345,3092,2742, 965,2784, 739,\n4124, 952,1358,2498,2949,2565, 332,2698,2378, 660,2260,2473,4194,3856,2919, 535,\n1260,2651,1208,1428,1300,1949,1303,2942, 433,2455,2450,1251,1946, 614,1269, 641,\n1306,1810,2737,3078,2912, 564,2365,1419,1415,1497,4460,2367,2185,1379,3005,1307,\n3218,2175,1897,3063, 682,1157,4040,4005,1712,1160,1941,1399, 394, 402,2952,1573,\n1151,2986,2404, 862, 299,2033,1489,3006, 346, 171,2886,3401,1726,2932, 168,2533,\n  47,2507,1030,3735,1145,3370,1395,1318,1579,3609,4560,2857,4116,1457,2529,1965,\n 504,1036,2690,2988,2405, 745,5871, 849,2397,2056,3081, 863,2359,3857,2096,  99,\n1397,1769,2300,4428,1643,3455,1978,1757,3718,1440,  35,4879,3742,1296,4228,2280,\n 160,5063,1599,2013, 166, 520,3479,1646,3345,3012, 490,1937,1545,1264,2182,2505,\n1096,1188,1369,1436,2421,1667,2792,2460,1270,2122, 727,3167,2143, 806,1706,1012,\n1800,3037, 960,2218,1882, 805, 139,2456,1139,1521, 851,1052,3093,3089, 342,2039,\n 744,5097,1468,1502,1585,2087, 223, 939, 326,2140,2577, 892,2481,1623,4077, 982,\n3708, 135,2131,  87,2503,3114,2326,1106, 876,1616, 547,2997,2831,2093,3441,4530,\n4314,   9,3256,4229,4148, 659,1462,1986,1710,2046,2913,2231,4090,4880,5255,3392,\n3274,1368,3689,4645,1477, 705,3384,3635,1068,1529,2941,1458,3782,1509, 100,1656,\n2548, 718,2339, 408,1590,2780,3548,1838,4117,3719,1345,3530, 717,3442,2778,3220,\n2898,1892,4590,3614,3371,2043,1998,1224,3483, 891, 635, 584,2559,3355, 733,1766,\n1729,1172,3789,1891,2307, 781,2982,2271,1957,1580,5773,2633,2005,4195,3097,1535,\n3213,1189,1934,5693,3262, 586,3118,1324,1598, 517,1564,2217,1868,1893,4445,3728,\n2703,3139,1526,1787,1992,3882,2875,1549,1199,1056,2224,1904,2711,5098,4287, 338,\n1993,3129,3489,2689,1809,2815,1997, 957,1855,3898,2550,3275,3057,1105,1319, 627,\n1505,1911,1883,3526, 698,3629,3456,1833,1431, 746,  77,1261,2017,2296,1977,1885,\n 125,1334,1600, 525,1798,1109,2222,1470,1945, 559,2236,1186,3443,2476,1929,1411,\n2411,3135,1777,3372,2621,1841,1613,3229, 668,1430,1839,2643,2916, 195,1989,2671,\n2358,1387, 629,3205,2293,5256,4439, 123,1310, 888,1879,4300,3021,3605,1003,1162,\n3192,2910,2010, 140,2395,2859,  55,1082,2012,2901, 662, 419,2081,1438, 680,2774,\n4654,3912,1620,1731,1625,5035,4065,2328, 512,1344, 802,5443,2163,2311,2537, 524,\n3399,  98,1155,2103,1918,2606,3925,2816,1393,2465,1504,3773,2177,3963,1478,4346,\n 180,1113,4655,3461,2028,1698, 833,2696,1235,1322,1594,4408,3623,3013,3225,2040,\n3022, 541,2881, 607,3632,2029,1665,1219, 639,1385,1686,1099,2803,3231,1938,3188,\n2858, 427, 676,2772,1168,2025, 454,3253,2486,3556, 230,1950, 580, 791,1991,1280,\n1086,1974,2034, 630, 257,3338,2788,4903,1017,  86,4790, 966,2789,1995,1696,1131,\n 259,3095,4188,1308, 179,1463,5257, 289,4107,1248,  42,3413,1725,2288, 896,1947,\n 774,4474,4254, 604,3430,4264, 392,2514,2588, 452, 237,1408,3018, 988,4531,1970,\n3034,3310, 540,2370,1562,1288,2990, 502,4765,1147,   4,1853,2708, 207, 294,2814,\n4078,2902,2509, 684,  34,3105,3532,2551, 644, 709,2801,2344, 573,1727,3573,3557,\n2021,1081,3100,4315,2100,3681, 199,2263,1837,2385, 146,3484,1195,2776,3949, 997,\n1939,3973,1008,1091,1202,1962,1847,1149,4209,5444,1076, 493, 117,5400,2521, 972,\n1490,2934,1796,4542,2374,1512,2933,2657, 413,2888,1135,2762,2314,2156,1355,2369,\n 766,2007,2527,2170,3124,2491,2593,2632,4757,2437, 234,3125,3591,1898,1750,1376,\n1942,3468,3138, 570,2127,2145,3276,4131, 962, 132,1445,4196,  19, 941,3624,3480,\n3366,1973,1374,4461,3431,2629, 283,2415,2275, 808,2887,3620,2112,2563,1353,3610,\n 955,1089,3103,1053,  96,  88,4097, 823,3808,1583, 399, 292,4091,3313, 421,1128,\n 642,4006, 903,2539,1877,2082, 596,  29,4066,1790, 722,2157, 130, 995,1569, 769,\n1485, 464, 513,2213, 288,1923,1101,2453,4316, 133, 486,2445,  50, 625, 487,2207,\n  57, 423, 481,2962, 159,3729,1558, 491, 303, 482, 501, 240,2837, 112,3648,2392,\n1783, 362,   8,3433,3422, 610,2793,3277,1390,1284,1654,  21,3823, 734, 367, 623,\n 193, 287, 374,1009,1483, 816, 476, 313,2255,2340,1262,2150,2899,1146,2581, 782,\n2116,1659,2018,1880, 255,3586,3314,1110,2867,2137,2564, 986,2767,5185,2006, 650,\n 158, 926, 762, 881,3157,2717,2362,3587, 306,3690,3245,1542,3077,2427,1691,2478,\n2118,2985,3490,2438, 539,2305, 983, 129,1754, 355,4201,2386, 827,2923, 104,1773,\n2838,2771, 411,2905,3919, 376, 767, 122,1114, 828,2422,1817,3506, 266,3460,1007,\n1609,4998, 945,2612,4429,2274, 726,1247,1964,2914,2199,2070,4002,4108, 657,3323,\n1422, 579, 455,2764,4737,1222,2895,1670, 824,1223,1487,2525, 558, 861,3080, 598,\n2659,2515,1967, 752,2583,2376,2214,4180, 977, 704,2464,4999,2622,4109,1210,2961,\n 819,1541, 142,2284,  44, 418, 457,1126,3730,4347,4626,1644,1876,3671,1864, 302,\n1063,5694, 624, 723,1984,3745,1314,1676,2488,1610,1449,3558,3569,2166,2098, 409,\n1011,2325,3704,2306, 818,1732,1383,1824,1844,3757, 999,2705,3497,1216,1423,2683,\n2426,2954,2501,2726,2229,1475,2554,5064,1971,1794,1666,2014,1343, 783, 724, 191,\n2434,1354,2220,5065,1763,2752,2472,4152, 131, 175,2885,3434,  92,1466,4920,2616,\n3871,3872,3866, 128,1551,1632, 669,1854,3682,4691,4125,1230, 188,2973,3290,1302,\n1213, 560,3266, 917, 763,3909,3249,1760, 868,1958, 764,1782,2097, 145,2277,3774,\n4462,  64,1491,3062, 971,2132,3606,2442, 221,1226,1617, 218, 323,1185,3207,3147,\n 571, 619,1473,1005,1744,2281, 449,1887,2396,3685, 275, 375,3816,1743,3844,3731,\n 845,1983,2350,4210,1377, 773, 967,3499,3052,3743,2725,4007,1697,1022,3943,1464,\n3264,2855,2722,1952,1029,2839,2467,  84,4383,2215, 820,1391,2015,2448,3672, 377,\n1948,2168, 797,2545,3536,2578,2645,  94,2874,1678, 405,1259,3071, 771, 546,1315,\n 470,1243,3083, 895,2468, 981, 969,2037, 846,4181, 653,1276,2928,  14,2594, 557,\n3007,2474, 156, 902,1338,1740,2574, 537,2518, 973,2282,2216,2433,1928, 138,2903,\n1293,2631,1612, 646,3457, 839,2935, 111, 496,2191,2847, 589,3186, 149,3994,2060,\n4031,2641,4067,3145,1870,  37,3597,2136,1025,2051,3009,3383,3549,1121,1016,3261,\n1301, 251,2446,2599,2153, 872,3246, 637, 334,3705, 831, 884, 921,3065,3140,4092,\n2198,1944, 246,2964, 108,2045,1152,1921,2308,1031, 203,3173,4170,1907,3890, 810,\n1401,2003,1690, 506, 647,1242,2828,1761,1649,3208,2249,1589,3709,2931,5156,1708,\n 498, 666,2613, 834,3817,1231, 184,2851,1124, 883,3197,2261,3710,1765,1553,2658,\n1178,2639,2351,  93,1193, 942,2538,2141,4402, 235,1821, 870,1591,2192,1709,1871,\n3341,1618,4126,2595,2334, 603, 651,  69, 701, 268,2662,3411,2555,1380,1606, 503,\n 448, 254,2371,2646, 574,1187,2309,1770, 322,2235,1292,1801, 305, 566,1133, 229,\n2067,2057, 706, 167, 483,2002,2672,3295,1820,3561,3067, 316, 378,2746,3452,1112,\n 136,1981, 507,1651,2917,1117, 285,4591, 182,2580,3522,1304, 335,3303,1835,2504,\n1795,1792,2248, 674,1018,2106,2449,1857,2292,2845, 976,3047,1781,2600,2727,1389,\n1281,  52,3152, 153, 265,3950, 672,3485,3951,4463, 430,1183, 365, 278,2169,  27,\n1407,1336,2304, 209,1340,1730,2202,1852,2403,2883, 979,1737,1062, 631,2829,2542,\n3876,2592, 825,2086,2226,3048,3625, 352,1417,3724, 542, 991, 431,1351,3938,1861,\n2294, 826,1361,2927,3142,3503,1738, 463,2462,2723, 582,1916,1595,2808, 400,3845,\n3891,2868,3621,2254,  58,2492,1123, 910,2160,2614,1372,1603,1196,1072,3385,1700,\n3267,1980, 696, 480,2430, 920, 799,1570,2920,1951,2041,4047,2540,1321,4223,2469,\n3562,2228,1271,2602, 401,2833,3351,2575,5157, 907,2312,1256, 410, 263,3507,1582,\n 996, 678,1849,2316,1480, 908,3545,2237, 703,2322, 667,1826,2849,1531,2604,2999,\n2407,3146,2151,2630,1786,3711, 469,3542, 497,3899,2409, 858, 837,4446,3393,1274,\n 786, 620,1845,2001,3311, 484, 308,3367,1204,1815,3691,2332,1532,2557,1842,2020,\n2724,1927,2333,4440, 567,  22,1673,2728,4475,1987,1858,1144,1597, 101,1832,3601,\n  12, 974,3783,4391, 951,1412,   1,3720, 453,4608,4041, 528,1041,1027,3230,2628,\n1129, 875,1051,3291,1203,2262,1069,2860,2799,2149,2615,3278, 144,1758,3040,  31,\n 475,1680, 366,2685,3184, 311,1642,4008,2466,5036,1593,1493,2809, 216,1420,1668,\n 233, 304,2128,3284, 232,1429,1768,1040,2008,3407,2740,2967,2543, 242,2133, 778,\n1565,2022,2620, 505,2189,2756,1098,2273, 372,1614, 708, 553,2846,2094,2278, 169,\n3626,2835,4161, 228,2674,3165, 809,1454,1309, 466,1705,1095, 900,3423, 880,2667,\n3751,5258,2317,3109,2571,4317,2766,1503,1342, 866,4447,1118,  63,2076, 314,1881,\n1348,1061, 172, 978,3515,1747, 532, 511,3970,   6, 601, 905,2699,3300,1751, 276,\n1467,3725,2668,  65,4239,2544,2779,2556,1604, 578,2451,1802, 992,2331,2624,1320,\n3446, 713,1513,1013, 103,2786,2447,1661, 886,1702, 916, 654,3574,2031,1556, 751,\n2178,2821,2179,1498,1538,2176, 271, 914,2251,2080,1325, 638,1953,2937,3877,2432,\n2754,  95,3265,1716, 260,1227,4083, 775, 106,1357,3254, 426,1607, 555,2480, 772,\n1985, 244,2546, 474, 495,1046,2611,1851,2061,  71,2089,1675,2590, 742,3758,2843,\n3222,1433, 267,2180,2576,2826,2233,2092,3913,2435, 956,1745,3075, 856,2113,1116,\n 451,   3,1988,2896,1398, 993,2463,1878,2049,1341,2718,2721,2870,2108, 712,2904,\n4363,2753,2324, 277,2872,2349,2649, 384, 987, 435, 691,3000, 922, 164,3939, 652,\n1500,1184,4153,2482,3373,2165,4848,2335,3775,3508,3154,2806,2830,1554,2102,1664,\n2530,1434,2408, 893,1547,2623,3447,2832,2242,2532,3169,2856,3223,2078,  49,3770,\n3469, 462, 318, 656,2259,3250,3069, 679,1629,2758, 344,1138,1104,3120,1836,1283,\n3115,2154,1437,4448, 934, 759,1999, 794,2862,1038, 533,2560,1722,2342, 855,2626,\n1197,1663,4476,3127,  85,4240,2528,  25,1111,1181,3673, 407,3470,4561,2679,2713,\n 768,1925,2841,3986,1544,1165, 932, 373,1240,2146,1930,2673, 721,4766, 354,4333,\n 391,2963, 187,  61,3364,1442,1102, 330,1940,1767, 341,3809,4118, 393,2496,2062,\n2211, 105, 331, 300, 439, 913,1332, 626, 379,3304,1557, 328, 689,3952, 309,1555,\n 931, 317,2517,3027, 325, 569, 686,2107,3084,  60,1042,1333,2794, 264,3177,4014,\n1628, 258,3712,   7,4464,1176,1043,1778, 683, 114,1975,  78,1492, 383,1886, 510,\n 386, 645,5291,2891,2069,3305,4138,3867,2939,2603,2493,1935,1066,1848,3588,1015,\n1282,1289,4609, 697,1453,3044,2666,3611,1856,2412,  54, 719,1330, 568,3778,2459,\n1748, 788, 492, 551,1191,1000, 488,3394,3763, 282,1799, 348,2016,1523,3155,2390,\n1049, 382,2019,1788,1170, 729,2968,3523, 897,3926,2785,2938,3292, 350,2319,3238,\n1718,1717,2655,3453,3143,4465, 161,2889,2980,2009,1421,  56,1908,1640,2387,2232,\n1917,1874,2477,4921, 148,  83,3438, 592,4245,2882,1822,1055, 741, 115,1496,1624,\n 381,1638,4592,1020, 516,3214, 458, 947,4575,1432, 211,1514,2926,1865,2142, 189,\n 852,1221,1400,1486, 882,2299,4036, 351,  28,1122, 700,6479,6480,6481,6482,6483,  #last 512\n)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/gb2312prober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is mozilla.org code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .mbcharsetprober import MultiByteCharSetProber\nfrom .codingstatemachine import CodingStateMachine\nfrom .chardistribution import GB2312DistributionAnalysis\nfrom .mbcssm import GB2312_SM_MODEL\n\nclass GB2312Prober(MultiByteCharSetProber):\n    def __init__(self):\n        super(GB2312Prober, self).__init__()\n        self.coding_sm = CodingStateMachine(GB2312_SM_MODEL)\n        self.distribution_analyzer = GB2312DistributionAnalysis()\n        self.reset()\n\n    @property\n    def charset_name(self):\n        return \"GB2312\"\n\n    @property\n    def language(self):\n        return \"Chinese\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/hebrewprober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Universal charset detector code.\n#\n# The Initial Developer of the Original Code is\n#          Shy Shalom\n# Portions created by the Initial Developer are Copyright (C) 2005\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .charsetprober import CharSetProber\nfrom .enums import ProbingState\n\n# This prober doesn't actually recognize a language or a charset.\n# It is a helper prober for the use of the Hebrew model probers\n\n### General ideas of the Hebrew charset recognition ###\n#\n# Four main charsets exist in Hebrew:\n# \"ISO-8859-8\" - Visual Hebrew\n# \"windows-1255\" - Logical Hebrew\n# \"ISO-8859-8-I\" - Logical Hebrew\n# \"x-mac-hebrew\" - ?? Logical Hebrew ??\n#\n# Both \"ISO\" charsets use a completely identical set of code points, whereas\n# \"windows-1255\" and \"x-mac-hebrew\" are two different proper supersets of\n# these code points. windows-1255 defines additional characters in the range\n# 0x80-0x9F as some misc punctuation marks as well as some Hebrew-specific\n# diacritics and additional 'Yiddish' ligature letters in the range 0xc0-0xd6.\n# x-mac-hebrew defines similar additional code points but with a different\n# mapping.\n#\n# As far as an average Hebrew text with no diacritics is concerned, all four\n# charsets are identical with respect to code points. Meaning that for the\n# main Hebrew alphabet, all four map the same values to all 27 Hebrew letters\n# (including final letters).\n#\n# The dominant difference between these charsets is their directionality.\n# \"Visual\" directionality means that the text is ordered as if the renderer is\n# not aware of a BIDI rendering algorithm. The renderer sees the text and\n# draws it from left to right. The text itself when ordered naturally is read\n# backwards. A buffer of Visual Hebrew generally looks like so:\n# \"[last word of first line spelled backwards] [whole line ordered backwards\n# and spelled backwards] [first word of first line spelled backwards]\n# [end of line] [last word of second line] ... etc' \"\n# adding punctuation marks, numbers and English text to visual text is\n# naturally also \"visual\" and from left to right.\n#\n# \"Logical\" directionality means the text is ordered \"naturally\" according to\n# the order it is read. It is the responsibility of the renderer to display\n# the text from right to left. A BIDI algorithm is used to place general\n# punctuation marks, numbers and English text in the text.\n#\n# Texts in x-mac-hebrew are almost impossible to find on the Internet. From\n# what little evidence I could find, it seems that its general directionality\n# is Logical.\n#\n# To sum up all of the above, the Hebrew probing mechanism knows about two\n# charsets:\n# Visual Hebrew - \"ISO-8859-8\" - backwards text - Words and sentences are\n#    backwards while line order is natural. For charset recognition purposes\n#    the line order is unimportant (In fact, for this implementation, even\n#    word order is unimportant).\n# Logical Hebrew - \"windows-1255\" - normal, naturally ordered text.\n#\n# \"ISO-8859-8-I\" is a subset of windows-1255 and doesn't need to be\n#    specifically identified.\n# \"x-mac-hebrew\" is also identified as windows-1255. A text in x-mac-hebrew\n#    that contain special punctuation marks or diacritics is displayed with\n#    some unconverted characters showing as question marks. This problem might\n#    be corrected using another model prober for x-mac-hebrew. Due to the fact\n#    that x-mac-hebrew texts are so rare, writing another model prober isn't\n#    worth the effort and performance hit.\n#\n#### The Prober ####\n#\n# The prober is divided between two SBCharSetProbers and a HebrewProber,\n# all of which are managed, created, fed data, inquired and deleted by the\n# SBCSGroupProber. The two SBCharSetProbers identify that the text is in\n# fact some kind of Hebrew, Logical or Visual. The final decision about which\n# one is it is made by the HebrewProber by combining final-letter scores\n# with the scores of the two SBCharSetProbers to produce a final answer.\n#\n# The SBCSGroupProber is responsible for stripping the original text of HTML\n# tags, English characters, numbers, low-ASCII punctuation characters, spaces\n# and new lines. It reduces any sequence of such characters to a single space.\n# The buffer fed to each prober in the SBCS group prober is pure text in\n# high-ASCII.\n# The two SBCharSetProbers (model probers) share the same language model:\n# Win1255Model.\n# The first SBCharSetProber uses the model normally as any other\n# SBCharSetProber does, to recognize windows-1255, upon which this model was\n# built. The second SBCharSetProber is told to make the pair-of-letter\n# lookup in the language model backwards. This in practice exactly simulates\n# a visual Hebrew model using the windows-1255 logical Hebrew model.\n#\n# The HebrewProber is not using any language model. All it does is look for\n# final-letter evidence suggesting the text is either logical Hebrew or visual\n# Hebrew. Disjointed from the model probers, the results of the HebrewProber\n# alone are meaningless. HebrewProber always returns 0.00 as confidence\n# since it never identifies a charset by itself. Instead, the pointer to the\n# HebrewProber is passed to the model probers as a helper \"Name Prober\".\n# When the Group prober receives a positive identification from any prober,\n# it asks for the name of the charset identified. If the prober queried is a\n# Hebrew model prober, the model prober forwards the call to the\n# HebrewProber to make the final decision. In the HebrewProber, the\n# decision is made according to the final-letters scores maintained and Both\n# model probers scores. The answer is returned in the form of the name of the\n# charset identified, either \"windows-1255\" or \"ISO-8859-8\".\n\nclass HebrewProber(CharSetProber):\n    # windows-1255 / ISO-8859-8 code points of interest\n    FINAL_KAF = 0xea\n    NORMAL_KAF = 0xeb\n    FINAL_MEM = 0xed\n    NORMAL_MEM = 0xee\n    FINAL_NUN = 0xef\n    NORMAL_NUN = 0xf0\n    FINAL_PE = 0xf3\n    NORMAL_PE = 0xf4\n    FINAL_TSADI = 0xf5\n    NORMAL_TSADI = 0xf6\n\n    # Minimum Visual vs Logical final letter score difference.\n    # If the difference is below this, don't rely solely on the final letter score\n    # distance.\n    MIN_FINAL_CHAR_DISTANCE = 5\n\n    # Minimum Visual vs Logical model score difference.\n    # If the difference is below this, don't rely at all on the model score\n    # distance.\n    MIN_MODEL_DISTANCE = 0.01\n\n    VISUAL_HEBREW_NAME = \"ISO-8859-8\"\n    LOGICAL_HEBREW_NAME = \"windows-1255\"\n\n    def __init__(self):\n        super(HebrewProber, self).__init__()\n        self._final_char_logical_score = None\n        self._final_char_visual_score = None\n        self._prev = None\n        self._before_prev = None\n        self._logical_prober = None\n        self._visual_prober = None\n        self.reset()\n\n    def reset(self):\n        self._final_char_logical_score = 0\n        self._final_char_visual_score = 0\n        # The two last characters seen in the previous buffer,\n        # mPrev and mBeforePrev are initialized to space in order to simulate\n        # a word delimiter at the beginning of the data\n        self._prev = ' '\n        self._before_prev = ' '\n        # These probers are owned by the group prober.\n\n    def set_model_probers(self, logicalProber, visualProber):\n        self._logical_prober = logicalProber\n        self._visual_prober = visualProber\n\n    def is_final(self, c):\n        return c in [self.FINAL_KAF, self.FINAL_MEM, self.FINAL_NUN,\n                     self.FINAL_PE, self.FINAL_TSADI]\n\n    def is_non_final(self, c):\n        # The normal Tsadi is not a good Non-Final letter due to words like\n        # 'lechotet' (to chat) containing an apostrophe after the tsadi. This\n        # apostrophe is converted to a space in FilterWithoutEnglishLetters\n        # causing the Non-Final tsadi to appear at an end of a word even\n        # though this is not the case in the original text.\n        # The letters Pe and Kaf rarely display a related behavior of not being\n        # a good Non-Final letter. Words like 'Pop', 'Winamp' and 'Mubarak'\n        # for example legally end with a Non-Final Pe or Kaf. However, the\n        # benefit of these letters as Non-Final letters outweighs the damage\n        # since these words are quite rare.\n        return c in [self.NORMAL_KAF, self.NORMAL_MEM,\n                     self.NORMAL_NUN, self.NORMAL_PE]\n\n    def feed(self, byte_str):\n        # Final letter analysis for logical-visual decision.\n        # Look for evidence that the received buffer is either logical Hebrew\n        # or visual Hebrew.\n        # The following cases are checked:\n        # 1) A word longer than 1 letter, ending with a final letter. This is\n        #    an indication that the text is laid out \"naturally\" since the\n        #    final letter really appears at the end. +1 for logical score.\n        # 2) A word longer than 1 letter, ending with a Non-Final letter. In\n        #    normal Hebrew, words ending with Kaf, Mem, Nun, Pe or Tsadi,\n        #    should not end with the Non-Final form of that letter. Exceptions\n        #    to this rule are mentioned above in isNonFinal(). This is an\n        #    indication that the text is laid out backwards. +1 for visual\n        #    score\n        # 3) A word longer than 1 letter, starting with a final letter. Final\n        #    letters should not appear at the beginning of a word. This is an\n        #    indication that the text is laid out backwards. +1 for visual\n        #    score.\n        #\n        # The visual score and logical score are accumulated throughout the\n        # text and are finally checked against each other in GetCharSetName().\n        # No checking for final letters in the middle of words is done since\n        # that case is not an indication for either Logical or Visual text.\n        #\n        # We automatically filter out all 7-bit characters (replace them with\n        # spaces) so the word boundary detection works properly. [MAP]\n\n        if self.state == ProbingState.NOT_ME:\n            # Both model probers say it's not them. No reason to continue.\n            return ProbingState.NOT_ME\n\n        byte_str = self.filter_high_byte_only(byte_str)\n\n        for cur in byte_str:\n            if cur == ' ':\n                # We stand on a space - a word just ended\n                if self._before_prev != ' ':\n                    # next-to-last char was not a space so self._prev is not a\n                    # 1 letter word\n                    if self.is_final(self._prev):\n                        # case (1) [-2:not space][-1:final letter][cur:space]\n                        self._final_char_logical_score += 1\n                    elif self.is_non_final(self._prev):\n                        # case (2) [-2:not space][-1:Non-Final letter][\n                        #  cur:space]\n                        self._final_char_visual_score += 1\n            else:\n                # Not standing on a space\n                if ((self._before_prev == ' ') and\n                        (self.is_final(self._prev)) and (cur != ' ')):\n                    # case (3) [-2:space][-1:final letter][cur:not space]\n                    self._final_char_visual_score += 1\n            self._before_prev = self._prev\n            self._prev = cur\n\n        # Forever detecting, till the end or until both model probers return\n        # ProbingState.NOT_ME (handled above)\n        return ProbingState.DETECTING\n\n    @property\n    def charset_name(self):\n        # Make the decision: is it Logical or Visual?\n        # If the final letter score distance is dominant enough, rely on it.\n        finalsub = self._final_char_logical_score - self._final_char_visual_score\n        if finalsub >= self.MIN_FINAL_CHAR_DISTANCE:\n            return self.LOGICAL_HEBREW_NAME\n        if finalsub <= -self.MIN_FINAL_CHAR_DISTANCE:\n            return self.VISUAL_HEBREW_NAME\n\n        # It's not dominant enough, try to rely on the model scores instead.\n        modelsub = (self._logical_prober.get_confidence()\n                    - self._visual_prober.get_confidence())\n        if modelsub > self.MIN_MODEL_DISTANCE:\n            return self.LOGICAL_HEBREW_NAME\n        if modelsub < -self.MIN_MODEL_DISTANCE:\n            return self.VISUAL_HEBREW_NAME\n\n        # Still no good, back to final letter distance, maybe it'll save the\n        # day.\n        if finalsub < 0.0:\n            return self.VISUAL_HEBREW_NAME\n\n        # (finalsub > 0 - Logical) or (don't know what to do) default to\n        # Logical.\n        return self.LOGICAL_HEBREW_NAME\n\n    @property\n    def language(self):\n        return 'Hebrew'\n\n    @property\n    def state(self):\n        # Remain active as long as any of the model probers are active.\n        if (self._logical_prober.state == ProbingState.NOT_ME) and \\\n           (self._visual_prober.state == ProbingState.NOT_ME):\n            return ProbingState.NOT_ME\n        return ProbingState.DETECTING\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/jisfreq.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n# Sampling from about 20M text materials include literature and computer technology\n#\n# Japanese frequency table, applied to both S-JIS and EUC-JP\n# They are sorted in order.\n\n# 128  --> 0.77094\n# 256  --> 0.85710\n# 512  --> 0.92635\n# 1024 --> 0.97130\n# 2048 --> 0.99431\n#\n# Ideal Distribution Ratio = 0.92635 / (1-0.92635) = 12.58\n# Random Distribution Ration = 512 / (2965+62+83+86-512) = 0.191\n#\n# Typical Distribution Ratio, 25% of IDR\n\nJIS_TYPICAL_DISTRIBUTION_RATIO = 3.0\n\n# Char to FreqOrder table ,\nJIS_TABLE_SIZE = 4368\n\nJIS_CHAR_TO_FREQ_ORDER = (\n  40,   1,   6, 182, 152, 180, 295,2127, 285, 381,3295,4304,3068,4606,3165,3510, #   16\n3511,1822,2785,4607,1193,2226,5070,4608, 171,2996,1247,  18, 179,5071, 856,1661, #   32\n1262,5072, 619, 127,3431,3512,3230,1899,1700, 232, 228,1294,1298, 284, 283,2041, #   48\n2042,1061,1062,  48,  49,  44,  45, 433, 434,1040,1041, 996, 787,2997,1255,4305, #   64\n2108,4609,1684,1648,5073,5074,5075,5076,5077,5078,3687,5079,4610,5080,3927,3928, #   80\n5081,3296,3432, 290,2285,1471,2187,5082,2580,2825,1303,2140,1739,1445,2691,3375, #   96\n1691,3297,4306,4307,4611, 452,3376,1182,2713,3688,3069,4308,5083,5084,5085,5086, #  112\n5087,5088,5089,5090,5091,5092,5093,5094,5095,5096,5097,5098,5099,5100,5101,5102, #  128\n5103,5104,5105,5106,5107,5108,5109,5110,5111,5112,4097,5113,5114,5115,5116,5117, #  144\n5118,5119,5120,5121,5122,5123,5124,5125,5126,5127,5128,5129,5130,5131,5132,5133, #  160\n5134,5135,5136,5137,5138,5139,5140,5141,5142,5143,5144,5145,5146,5147,5148,5149, #  176\n5150,5151,5152,4612,5153,5154,5155,5156,5157,5158,5159,5160,5161,5162,5163,5164, #  192\n5165,5166,5167,5168,5169,5170,5171,5172,5173,5174,5175,1472, 598, 618, 820,1205, #  208\n1309,1412,1858,1307,1692,5176,5177,5178,5179,5180,5181,5182,1142,1452,1234,1172, #  224\n1875,2043,2149,1793,1382,2973, 925,2404,1067,1241, 960,1377,2935,1491, 919,1217, #  240\n1865,2030,1406,1499,2749,4098,5183,5184,5185,5186,5187,5188,2561,4099,3117,1804, #  256\n2049,3689,4309,3513,1663,5189,3166,3118,3298,1587,1561,3433,5190,3119,1625,2998, #  272\n3299,4613,1766,3690,2786,4614,5191,5192,5193,5194,2161,  26,3377,   2,3929,  20, #  288\n3691,  47,4100,  50,  17,  16,  35, 268,  27, 243,  42, 155,  24, 154,  29, 184, #  304\n   4,  91,  14,  92,  53, 396,  33, 289,   9,  37,  64, 620,  21,  39, 321,   5, #  320\n  12,  11,  52,  13,   3, 208, 138,   0,   7,  60, 526, 141, 151,1069, 181, 275, #  336\n1591,  83, 132,1475, 126, 331, 829,  15,  69, 160,  59,  22, 157,  55,1079, 312, #  352\n 109,  38,  23,  25,  10,  19,  79,5195,  61, 382,1124,   8,  30,5196,5197,5198, #  368\n5199,5200,5201,5202,5203,5204,5205,5206,  89,  62,  74,  34,2416, 112, 139, 196, #  384\n 271, 149,  84, 607, 131, 765,  46,  88, 153, 683,  76, 874, 101, 258,  57,  80, #  400\n  32, 364, 121,1508, 169,1547,  68, 235, 145,2999,  41, 360,3027,  70,  63,  31, #  416\n  43, 259, 262,1383,  99, 533, 194,  66,  93, 846, 217, 192,  56, 106,  58, 565, #  432\n 280, 272, 311, 256, 146,  82, 308,  71, 100, 128, 214, 655, 110, 261, 104,1140, #  448\n  54,  51,  36,  87,  67,3070, 185,2618,2936,2020,  28,1066,2390,2059,5207,5208, #  464\n5209,5210,5211,5212,5213,5214,5215,5216,4615,5217,5218,5219,5220,5221,5222,5223, #  480\n5224,5225,5226,5227,5228,5229,5230,5231,5232,5233,5234,5235,5236,3514,5237,5238, #  496\n5239,5240,5241,5242,5243,5244,2297,2031,4616,4310,3692,5245,3071,5246,3598,5247, #  512\n4617,3231,3515,5248,4101,4311,4618,3808,4312,4102,5249,4103,4104,3599,5250,5251, #  528\n5252,5253,5254,5255,5256,5257,5258,5259,5260,5261,5262,5263,5264,5265,5266,5267, #  544\n5268,5269,5270,5271,5272,5273,5274,5275,5276,5277,5278,5279,5280,5281,5282,5283, #  560\n5284,5285,5286,5287,5288,5289,5290,5291,5292,5293,5294,5295,5296,5297,5298,5299, #  576\n5300,5301,5302,5303,5304,5305,5306,5307,5308,5309,5310,5311,5312,5313,5314,5315, #  592\n5316,5317,5318,5319,5320,5321,5322,5323,5324,5325,5326,5327,5328,5329,5330,5331, #  608\n5332,5333,5334,5335,5336,5337,5338,5339,5340,5341,5342,5343,5344,5345,5346,5347, #  624\n5348,5349,5350,5351,5352,5353,5354,5355,5356,5357,5358,5359,5360,5361,5362,5363, #  640\n5364,5365,5366,5367,5368,5369,5370,5371,5372,5373,5374,5375,5376,5377,5378,5379, #  656\n5380,5381, 363, 642,2787,2878,2788,2789,2316,3232,2317,3434,2011, 165,1942,3930, #  672\n3931,3932,3933,5382,4619,5383,4620,5384,5385,5386,5387,5388,5389,5390,5391,5392, #  688\n5393,5394,5395,5396,5397,5398,5399,5400,5401,5402,5403,5404,5405,5406,5407,5408, #  704\n5409,5410,5411,5412,5413,5414,5415,5416,5417,5418,5419,5420,5421,5422,5423,5424, #  720\n5425,5426,5427,5428,5429,5430,5431,5432,5433,5434,5435,5436,5437,5438,5439,5440, #  736\n5441,5442,5443,5444,5445,5446,5447,5448,5449,5450,5451,5452,5453,5454,5455,5456, #  752\n5457,5458,5459,5460,5461,5462,5463,5464,5465,5466,5467,5468,5469,5470,5471,5472, #  768\n5473,5474,5475,5476,5477,5478,5479,5480,5481,5482,5483,5484,5485,5486,5487,5488, #  784\n5489,5490,5491,5492,5493,5494,5495,5496,5497,5498,5499,5500,5501,5502,5503,5504, #  800\n5505,5506,5507,5508,5509,5510,5511,5512,5513,5514,5515,5516,5517,5518,5519,5520, #  816\n5521,5522,5523,5524,5525,5526,5527,5528,5529,5530,5531,5532,5533,5534,5535,5536, #  832\n5537,5538,5539,5540,5541,5542,5543,5544,5545,5546,5547,5548,5549,5550,5551,5552, #  848\n5553,5554,5555,5556,5557,5558,5559,5560,5561,5562,5563,5564,5565,5566,5567,5568, #  864\n5569,5570,5571,5572,5573,5574,5575,5576,5577,5578,5579,5580,5581,5582,5583,5584, #  880\n5585,5586,5587,5588,5589,5590,5591,5592,5593,5594,5595,5596,5597,5598,5599,5600, #  896\n5601,5602,5603,5604,5605,5606,5607,5608,5609,5610,5611,5612,5613,5614,5615,5616, #  912\n5617,5618,5619,5620,5621,5622,5623,5624,5625,5626,5627,5628,5629,5630,5631,5632, #  928\n5633,5634,5635,5636,5637,5638,5639,5640,5641,5642,5643,5644,5645,5646,5647,5648, #  944\n5649,5650,5651,5652,5653,5654,5655,5656,5657,5658,5659,5660,5661,5662,5663,5664, #  960\n5665,5666,5667,5668,5669,5670,5671,5672,5673,5674,5675,5676,5677,5678,5679,5680, #  976\n5681,5682,5683,5684,5685,5686,5687,5688,5689,5690,5691,5692,5693,5694,5695,5696, #  992\n5697,5698,5699,5700,5701,5702,5703,5704,5705,5706,5707,5708,5709,5710,5711,5712, # 1008\n5713,5714,5715,5716,5717,5718,5719,5720,5721,5722,5723,5724,5725,5726,5727,5728, # 1024\n5729,5730,5731,5732,5733,5734,5735,5736,5737,5738,5739,5740,5741,5742,5743,5744, # 1040\n5745,5746,5747,5748,5749,5750,5751,5752,5753,5754,5755,5756,5757,5758,5759,5760, # 1056\n5761,5762,5763,5764,5765,5766,5767,5768,5769,5770,5771,5772,5773,5774,5775,5776, # 1072\n5777,5778,5779,5780,5781,5782,5783,5784,5785,5786,5787,5788,5789,5790,5791,5792, # 1088\n5793,5794,5795,5796,5797,5798,5799,5800,5801,5802,5803,5804,5805,5806,5807,5808, # 1104\n5809,5810,5811,5812,5813,5814,5815,5816,5817,5818,5819,5820,5821,5822,5823,5824, # 1120\n5825,5826,5827,5828,5829,5830,5831,5832,5833,5834,5835,5836,5837,5838,5839,5840, # 1136\n5841,5842,5843,5844,5845,5846,5847,5848,5849,5850,5851,5852,5853,5854,5855,5856, # 1152\n5857,5858,5859,5860,5861,5862,5863,5864,5865,5866,5867,5868,5869,5870,5871,5872, # 1168\n5873,5874,5875,5876,5877,5878,5879,5880,5881,5882,5883,5884,5885,5886,5887,5888, # 1184\n5889,5890,5891,5892,5893,5894,5895,5896,5897,5898,5899,5900,5901,5902,5903,5904, # 1200\n5905,5906,5907,5908,5909,5910,5911,5912,5913,5914,5915,5916,5917,5918,5919,5920, # 1216\n5921,5922,5923,5924,5925,5926,5927,5928,5929,5930,5931,5932,5933,5934,5935,5936, # 1232\n5937,5938,5939,5940,5941,5942,5943,5944,5945,5946,5947,5948,5949,5950,5951,5952, # 1248\n5953,5954,5955,5956,5957,5958,5959,5960,5961,5962,5963,5964,5965,5966,5967,5968, # 1264\n5969,5970,5971,5972,5973,5974,5975,5976,5977,5978,5979,5980,5981,5982,5983,5984, # 1280\n5985,5986,5987,5988,5989,5990,5991,5992,5993,5994,5995,5996,5997,5998,5999,6000, # 1296\n6001,6002,6003,6004,6005,6006,6007,6008,6009,6010,6011,6012,6013,6014,6015,6016, # 1312\n6017,6018,6019,6020,6021,6022,6023,6024,6025,6026,6027,6028,6029,6030,6031,6032, # 1328\n6033,6034,6035,6036,6037,6038,6039,6040,6041,6042,6043,6044,6045,6046,6047,6048, # 1344\n6049,6050,6051,6052,6053,6054,6055,6056,6057,6058,6059,6060,6061,6062,6063,6064, # 1360\n6065,6066,6067,6068,6069,6070,6071,6072,6073,6074,6075,6076,6077,6078,6079,6080, # 1376\n6081,6082,6083,6084,6085,6086,6087,6088,6089,6090,6091,6092,6093,6094,6095,6096, # 1392\n6097,6098,6099,6100,6101,6102,6103,6104,6105,6106,6107,6108,6109,6110,6111,6112, # 1408\n6113,6114,2044,2060,4621, 997,1235, 473,1186,4622, 920,3378,6115,6116, 379,1108, # 1424\n4313,2657,2735,3934,6117,3809, 636,3233, 573,1026,3693,3435,2974,3300,2298,4105, # 1440\n 854,2937,2463, 393,2581,2417, 539, 752,1280,2750,2480, 140,1161, 440, 708,1569, # 1456\n 665,2497,1746,1291,1523,3000, 164,1603, 847,1331, 537,1997, 486, 508,1693,2418, # 1472\n1970,2227, 878,1220, 299,1030, 969, 652,2751, 624,1137,3301,2619,  65,3302,2045, # 1488\n1761,1859,3120,1930,3694,3516, 663,1767, 852, 835,3695, 269, 767,2826,2339,1305, # 1504\n 896,1150, 770,1616,6118, 506,1502,2075,1012,2519, 775,2520,2975,2340,2938,4314, # 1520\n3028,2086,1224,1943,2286,6119,3072,4315,2240,1273,1987,3935,1557, 175, 597, 985, # 1536\n3517,2419,2521,1416,3029, 585, 938,1931,1007,1052,1932,1685,6120,3379,4316,4623, # 1552\n 804, 599,3121,1333,2128,2539,1159,1554,2032,3810, 687,2033,2904, 952, 675,1467, # 1568\n3436,6121,2241,1096,1786,2440,1543,1924, 980,1813,2228, 781,2692,1879, 728,1918, # 1584\n3696,4624, 548,1950,4625,1809,1088,1356,3303,2522,1944, 502, 972, 373, 513,2827, # 1600\n 586,2377,2391,1003,1976,1631,6122,2464,1084, 648,1776,4626,2141, 324, 962,2012, # 1616\n2177,2076,1384, 742,2178,1448,1173,1810, 222, 102, 301, 445, 125,2420, 662,2498, # 1632\n 277, 200,1476,1165,1068, 224,2562,1378,1446, 450,1880, 659, 791, 582,4627,2939, # 1648\n3936,1516,1274, 555,2099,3697,1020,1389,1526,3380,1762,1723,1787,2229, 412,2114, # 1664\n1900,2392,3518, 512,2597, 427,1925,2341,3122,1653,1686,2465,2499, 697, 330, 273, # 1680\n 380,2162, 951, 832, 780, 991,1301,3073, 965,2270,3519, 668,2523,2636,1286, 535, # 1696\n1407, 518, 671, 957,2658,2378, 267, 611,2197,3030,6123, 248,2299, 967,1799,2356, # 1712\n 850,1418,3437,1876,1256,1480,2828,1718,6124,6125,1755,1664,2405,6126,4628,2879, # 1728\n2829, 499,2179, 676,4629, 557,2329,2214,2090, 325,3234, 464, 811,3001, 992,2342, # 1744\n2481,1232,1469, 303,2242, 466,1070,2163, 603,1777,2091,4630,2752,4631,2714, 322, # 1760\n2659,1964,1768, 481,2188,1463,2330,2857,3600,2092,3031,2421,4632,2318,2070,1849, # 1776\n2598,4633,1302,2254,1668,1701,2422,3811,2905,3032,3123,2046,4106,1763,1694,4634, # 1792\n1604, 943,1724,1454, 917, 868,2215,1169,2940, 552,1145,1800,1228,1823,1955, 316, # 1808\n1080,2510, 361,1807,2830,4107,2660,3381,1346,1423,1134,4108,6127, 541,1263,1229, # 1824\n1148,2540, 545, 465,1833,2880,3438,1901,3074,2482, 816,3937, 713,1788,2500, 122, # 1840\n1575, 195,1451,2501,1111,6128, 859, 374,1225,2243,2483,4317, 390,1033,3439,3075, # 1856\n2524,1687, 266, 793,1440,2599, 946, 779, 802, 507, 897,1081, 528,2189,1292, 711, # 1872\n1866,1725,1167,1640, 753, 398,2661,1053, 246, 348,4318, 137,1024,3440,1600,2077, # 1888\n2129, 825,4319, 698, 238, 521, 187,2300,1157,2423,1641,1605,1464,1610,1097,2541, # 1904\n1260,1436, 759,2255,1814,2150, 705,3235, 409,2563,3304, 561,3033,2005,2564, 726, # 1920\n1956,2343,3698,4109, 949,3812,3813,3520,1669, 653,1379,2525, 881,2198, 632,2256, # 1936\n1027, 778,1074, 733,1957, 514,1481,2466, 554,2180, 702,3938,1606,1017,1398,6129, # 1952\n1380,3521, 921, 993,1313, 594, 449,1489,1617,1166, 768,1426,1360, 495,1794,3601, # 1968\n1177,3602,1170,4320,2344, 476, 425,3167,4635,3168,1424, 401,2662,1171,3382,1998, # 1984\n1089,4110, 477,3169, 474,6130,1909, 596,2831,1842, 494, 693,1051,1028,1207,3076, # 2000\n 606,2115, 727,2790,1473,1115, 743,3522, 630, 805,1532,4321,2021, 366,1057, 838, # 2016\n 684,1114,2142,4322,2050,1492,1892,1808,2271,3814,2424,1971,1447,1373,3305,1090, # 2032\n1536,3939,3523,3306,1455,2199, 336, 369,2331,1035, 584,2393, 902, 718,2600,6131, # 2048\n2753, 463,2151,1149,1611,2467, 715,1308,3124,1268, 343,1413,3236,1517,1347,2663, # 2064\n2093,3940,2022,1131,1553,2100,2941,1427,3441,2942,1323,2484,6132,1980, 872,2368, # 2080\n2441,2943, 320,2369,2116,1082, 679,1933,3941,2791,3815, 625,1143,2023, 422,2200, # 2096\n3816,6133, 730,1695, 356,2257,1626,2301,2858,2637,1627,1778, 937, 883,2906,2693, # 2112\n3002,1769,1086, 400,1063,1325,3307,2792,4111,3077, 456,2345,1046, 747,6134,1524, # 2128\n 884,1094,3383,1474,2164,1059, 974,1688,2181,2258,1047, 345,1665,1187, 358, 875, # 2144\n3170, 305, 660,3524,2190,1334,1135,3171,1540,1649,2542,1527, 927, 968,2793, 885, # 2160\n1972,1850, 482, 500,2638,1218,1109,1085,2543,1654,2034, 876,  78,2287,1482,1277, # 2176\n 861,1675,1083,1779, 724,2754, 454, 397,1132,1612,2332, 893, 672,1237, 257,2259, # 2192\n2370, 135,3384, 337,2244, 547, 352, 340, 709,2485,1400, 788,1138,2511, 540, 772, # 2208\n1682,2260,2272,2544,2013,1843,1902,4636,1999,1562,2288,4637,2201,1403,1533, 407, # 2224\n 576,3308,1254,2071, 978,3385, 170, 136,1201,3125,2664,3172,2394, 213, 912, 873, # 2240\n3603,1713,2202, 699,3604,3699, 813,3442, 493, 531,1054, 468,2907,1483, 304, 281, # 2256\n4112,1726,1252,2094, 339,2319,2130,2639, 756,1563,2944, 748, 571,2976,1588,2425, # 2272\n2715,1851,1460,2426,1528,1392,1973,3237, 288,3309, 685,3386, 296, 892,2716,2216, # 2288\n1570,2245, 722,1747,2217, 905,3238,1103,6135,1893,1441,1965, 251,1805,2371,3700, # 2304\n2601,1919,1078,  75,2182,1509,1592,1270,2640,4638,2152,6136,3310,3817, 524, 706, # 2320\n1075, 292,3818,1756,2602, 317,  98,3173,3605,3525,1844,2218,3819,2502, 814, 567, # 2336\n 385,2908,1534,6137, 534,1642,3239, 797,6138,1670,1529, 953,4323, 188,1071, 538, # 2352\n 178, 729,3240,2109,1226,1374,2000,2357,2977, 731,2468,1116,2014,2051,6139,1261, # 2368\n1593, 803,2859,2736,3443, 556, 682, 823,1541,6140,1369,2289,1706,2794, 845, 462, # 2384\n2603,2665,1361, 387, 162,2358,1740, 739,1770,1720,1304,1401,3241,1049, 627,1571, # 2400\n2427,3526,1877,3942,1852,1500, 431,1910,1503, 677, 297,2795, 286,1433,1038,1198, # 2416\n2290,1133,1596,4113,4639,2469,1510,1484,3943,6141,2442, 108, 712,4640,2372, 866, # 2432\n3701,2755,3242,1348, 834,1945,1408,3527,2395,3243,1811, 824, 994,1179,2110,1548, # 2448\n1453, 790,3003, 690,4324,4325,2832,2909,3820,1860,3821, 225,1748, 310, 346,1780, # 2464\n2470, 821,1993,2717,2796, 828, 877,3528,2860,2471,1702,2165,2910,2486,1789, 453, # 2480\n 359,2291,1676,  73,1164,1461,1127,3311, 421, 604, 314,1037, 589, 116,2487, 737, # 2496\n 837,1180, 111, 244, 735,6142,2261,1861,1362, 986, 523, 418, 581,2666,3822, 103, # 2512\n 855, 503,1414,1867,2488,1091, 657,1597, 979, 605,1316,4641,1021,2443,2078,2001, # 2528\n1209,  96, 587,2166,1032, 260,1072,2153, 173,  94, 226,3244, 819,2006,4642,4114, # 2544\n2203, 231,1744, 782,  97,2667, 786,3387, 887, 391, 442,2219,4326,1425,6143,2694, # 2560\n 633,1544,1202, 483,2015, 592,2052,1958,2472,1655, 419, 129,4327,3444,3312,1714, # 2576\n1257,3078,4328,1518,1098, 865,1310,1019,1885,1512,1734, 469,2444, 148, 773, 436, # 2592\n1815,1868,1128,1055,4329,1245,2756,3445,2154,1934,1039,4643, 579,1238, 932,2320, # 2608\n 353, 205, 801, 115,2428, 944,2321,1881, 399,2565,1211, 678, 766,3944, 335,2101, # 2624\n1459,1781,1402,3945,2737,2131,1010, 844, 981,1326,1013, 550,1816,1545,2620,1335, # 2640\n1008, 371,2881, 936,1419,1613,3529,1456,1395,2273,1834,2604,1317,2738,2503, 416, # 2656\n1643,4330, 806,1126, 229, 591,3946,1314,1981,1576,1837,1666, 347,1790, 977,3313, # 2672\n 764,2861,1853, 688,2429,1920,1462,  77, 595, 415,2002,3034, 798,1192,4115,6144, # 2688\n2978,4331,3035,2695,2582,2072,2566, 430,2430,1727, 842,1396,3947,3702, 613, 377, # 2704\n 278, 236,1417,3388,3314,3174, 757,1869, 107,3530,6145,1194, 623,2262, 207,1253, # 2720\n2167,3446,3948, 492,1117,1935, 536,1838,2757,1246,4332, 696,2095,2406,1393,1572, # 2736\n3175,1782, 583, 190, 253,1390,2230, 830,3126,3389, 934,3245,1703,1749,2979,1870, # 2752\n2545,1656,2204, 869,2346,4116,3176,1817, 496,1764,4644, 942,1504, 404,1903,1122, # 2768\n1580,3606,2945,1022, 515, 372,1735, 955,2431,3036,6146,2797,1110,2302,2798, 617, # 2784\n6147, 441, 762,1771,3447,3607,3608,1904, 840,3037,  86, 939,1385, 572,1370,2445, # 2800\n1336, 114,3703, 898, 294, 203,3315, 703,1583,2274, 429, 961,4333,1854,1951,3390, # 2816\n2373,3704,4334,1318,1381, 966,1911,2322,1006,1155, 309, 989, 458,2718,1795,1372, # 2832\n1203, 252,1689,1363,3177, 517,1936, 168,1490, 562, 193,3823,1042,4117,1835, 551, # 2848\n 470,4645, 395, 489,3448,1871,1465,2583,2641, 417,1493, 279,1295, 511,1236,1119, # 2864\n  72,1231,1982,1812,3004, 871,1564, 984,3449,1667,2696,2096,4646,2347,2833,1673, # 2880\n3609, 695,3246,2668, 807,1183,4647, 890, 388,2333,1801,1457,2911,1765,1477,1031, # 2896\n3316,3317,1278,3391,2799,2292,2526, 163,3450,4335,2669,1404,1802,6148,2323,2407, # 2912\n1584,1728,1494,1824,1269, 298, 909,3318,1034,1632, 375, 776,1683,2061, 291, 210, # 2928\n1123, 809,1249,1002,2642,3038, 206,1011,2132, 144, 975, 882,1565, 342, 667, 754, # 2944\n1442,2143,1299,2303,2062, 447, 626,2205,1221,2739,2912,1144,1214,2206,2584, 760, # 2960\n1715, 614, 950,1281,2670,2621, 810, 577,1287,2546,4648, 242,2168, 250,2643, 691, # 2976\n 123,2644, 647, 313,1029, 689,1357,2946,1650, 216, 771,1339,1306, 808,2063, 549, # 2992\n 913,1371,2913,2914,6149,1466,1092,1174,1196,1311,2605,2396,1783,1796,3079, 406, # 3008\n2671,2117,3949,4649, 487,1825,2220,6150,2915, 448,2348,1073,6151,2397,1707, 130, # 3024\n 900,1598, 329, 176,1959,2527,1620,6152,2275,4336,3319,1983,2191,3705,3610,2155, # 3040\n3706,1912,1513,1614,6153,1988, 646, 392,2304,1589,3320,3039,1826,1239,1352,1340, # 3056\n2916, 505,2567,1709,1437,2408,2547, 906,6154,2672, 384,1458,1594,1100,1329, 710, # 3072\n 423,3531,2064,2231,2622,1989,2673,1087,1882, 333, 841,3005,1296,2882,2379, 580, # 3088\n1937,1827,1293,2585, 601, 574, 249,1772,4118,2079,1120, 645, 901,1176,1690, 795, # 3104\n2207, 478,1434, 516,1190,1530, 761,2080, 930,1264, 355, 435,1552, 644,1791, 987, # 3120\n 220,1364,1163,1121,1538, 306,2169,1327,1222, 546,2645, 218, 241, 610,1704,3321, # 3136\n1984,1839,1966,2528, 451,6155,2586,3707,2568, 907,3178, 254,2947, 186,1845,4650, # 3152\n 745, 432,1757, 428,1633, 888,2246,2221,2489,3611,2118,1258,1265, 956,3127,1784, # 3168\n4337,2490, 319, 510, 119, 457,3612, 274,2035,2007,4651,1409,3128, 970,2758, 590, # 3184\n2800, 661,2247,4652,2008,3950,1420,1549,3080,3322,3951,1651,1375,2111, 485,2491, # 3200\n1429,1156,6156,2548,2183,1495, 831,1840,2529,2446, 501,1657, 307,1894,3247,1341, # 3216\n 666, 899,2156,1539,2549,1559, 886, 349,2208,3081,2305,1736,3824,2170,2759,1014, # 3232\n1913,1386, 542,1397,2948, 490, 368, 716, 362, 159, 282,2569,1129,1658,1288,1750, # 3248\n2674, 276, 649,2016, 751,1496, 658,1818,1284,1862,2209,2087,2512,3451, 622,2834, # 3264\n 376, 117,1060,2053,1208,1721,1101,1443, 247,1250,3179,1792,3952,2760,2398,3953, # 3280\n6157,2144,3708, 446,2432,1151,2570,3452,2447,2761,2835,1210,2448,3082, 424,2222, # 3296\n1251,2449,2119,2836, 504,1581,4338, 602, 817, 857,3825,2349,2306, 357,3826,1470, # 3312\n1883,2883, 255, 958, 929,2917,3248, 302,4653,1050,1271,1751,2307,1952,1430,2697, # 3328\n2719,2359, 354,3180, 777, 158,2036,4339,1659,4340,4654,2308,2949,2248,1146,2232, # 3344\n3532,2720,1696,2623,3827,6158,3129,1550,2698,1485,1297,1428, 637, 931,2721,2145, # 3360\n 914,2550,2587,  81,2450, 612, 827,2646,1242,4655,1118,2884, 472,1855,3181,3533, # 3376\n3534, 569,1353,2699,1244,1758,2588,4119,2009,2762,2171,3709,1312,1531,6159,1152, # 3392\n1938, 134,1830, 471,3710,2276,1112,1535,3323,3453,3535, 982,1337,2950, 488, 826, # 3408\n 674,1058,1628,4120,2017, 522,2399, 211, 568,1367,3454, 350, 293,1872,1139,3249, # 3424\n1399,1946,3006,1300,2360,3324, 588, 736,6160,2606, 744, 669,3536,3828,6161,1358, # 3440\n 199, 723, 848, 933, 851,1939,1505,1514,1338,1618,1831,4656,1634,3613, 443,2740, # 3456\n3829, 717,1947, 491,1914,6162,2551,1542,4121,1025,6163,1099,1223, 198,3040,2722, # 3472\n 370, 410,1905,2589, 998,1248,3182,2380, 519,1449,4122,1710, 947, 928,1153,4341, # 3488\n2277, 344,2624,1511, 615, 105, 161,1212,1076,1960,3130,2054,1926,1175,1906,2473, # 3504\n 414,1873,2801,6164,2309, 315,1319,3325, 318,2018,2146,2157, 963, 631, 223,4342, # 3520\n4343,2675, 479,3711,1197,2625,3712,2676,2361,6165,4344,4123,6166,2451,3183,1886, # 3536\n2184,1674,1330,1711,1635,1506, 799, 219,3250,3083,3954,1677,3713,3326,2081,3614, # 3552\n1652,2073,4657,1147,3041,1752, 643,1961, 147,1974,3955,6167,1716,2037, 918,3007, # 3568\n1994, 120,1537, 118, 609,3184,4345, 740,3455,1219, 332,1615,3830,6168,1621,2980, # 3584\n1582, 783, 212, 553,2350,3714,1349,2433,2082,4124, 889,6169,2310,1275,1410, 973, # 3600\n 166,1320,3456,1797,1215,3185,2885,1846,2590,2763,4658, 629, 822,3008, 763, 940, # 3616\n1990,2862, 439,2409,1566,1240,1622, 926,1282,1907,2764, 654,2210,1607, 327,1130, # 3632\n3956,1678,1623,6170,2434,2192, 686, 608,3831,3715, 903,3957,3042,6171,2741,1522, # 3648\n1915,1105,1555,2552,1359, 323,3251,4346,3457, 738,1354,2553,2311,2334,1828,2003, # 3664\n3832,1753,2351,1227,6172,1887,4125,1478,6173,2410,1874,1712,1847, 520,1204,2607, # 3680\n 264,4659, 836,2677,2102, 600,4660,3833,2278,3084,6174,4347,3615,1342, 640, 532, # 3696\n 543,2608,1888,2400,2591,1009,4348,1497, 341,1737,3616,2723,1394, 529,3252,1321, # 3712\n 983,4661,1515,2120, 971,2592, 924, 287,1662,3186,4349,2700,4350,1519, 908,1948, # 3728\n2452, 156, 796,1629,1486,2223,2055, 694,4126,1259,1036,3392,1213,2249,2742,1889, # 3744\n1230,3958,1015, 910, 408, 559,3617,4662, 746, 725, 935,4663,3959,3009,1289, 563, # 3760\n 867,4664,3960,1567,2981,2038,2626, 988,2263,2381,4351, 143,2374, 704,1895,6175, # 3776\n1188,3716,2088, 673,3085,2362,4352, 484,1608,1921,2765,2918, 215, 904,3618,3537, # 3792\n 894, 509, 976,3043,2701,3961,4353,2837,2982, 498,6176,6177,1102,3538,1332,3393, # 3808\n1487,1636,1637, 233, 245,3962, 383, 650, 995,3044, 460,1520,1206,2352, 749,3327, # 3824\n 530, 700, 389,1438,1560,1773,3963,2264, 719,2951,2724,3834, 870,1832,1644,1000, # 3840\n 839,2474,3717, 197,1630,3394, 365,2886,3964,1285,2133, 734, 922, 818,1106, 732, # 3856\n 480,2083,1774,3458, 923,2279,1350, 221,3086,  85,2233,2234,3835,1585,3010,2147, # 3872\n1387,1705,2382,1619,2475, 133, 239,2802,1991,1016,2084,2383, 411,2838,1113, 651, # 3888\n1985,1160,3328, 990,1863,3087,1048,1276,2647, 265,2627,1599,3253,2056, 150, 638, # 3904\n2019, 656, 853, 326,1479, 680,1439,4354,1001,1759, 413,3459,3395,2492,1431, 459, # 3920\n4355,1125,3329,2265,1953,1450,2065,2863, 849, 351,2678,3131,3254,3255,1104,1577, # 3936\n 227,1351,1645,2453,2193,1421,2887, 812,2121, 634,  95,2435, 201,2312,4665,1646, # 3952\n1671,2743,1601,2554,2702,2648,2280,1315,1366,2089,3132,1573,3718,3965,1729,1189, # 3968\n 328,2679,1077,1940,1136, 558,1283, 964,1195, 621,2074,1199,1743,3460,3619,1896, # 3984\n1916,1890,3836,2952,1154,2112,1064, 862, 378,3011,2066,2113,2803,1568,2839,6178, # 4000\n3088,2919,1941,1660,2004,1992,2194, 142, 707,1590,1708,1624,1922,1023,1836,1233, # 4016\n1004,2313, 789, 741,3620,6179,1609,2411,1200,4127,3719,3720,4666,2057,3721, 593, # 4032\n2840, 367,2920,1878,6180,3461,1521, 628,1168, 692,2211,2649, 300, 720,2067,2571, # 4048\n2953,3396, 959,2504,3966,3539,3462,1977, 701,6181, 954,1043, 800, 681, 183,3722, # 4064\n1803,1730,3540,4128,2103, 815,2314, 174, 467, 230,2454,1093,2134, 755,3541,3397, # 4080\n1141,1162,6182,1738,2039, 270,3256,2513,1005,1647,2185,3837, 858,1679,1897,1719, # 4096\n2954,2324,1806, 402, 670, 167,4129,1498,2158,2104, 750,6183, 915, 189,1680,1551, # 4112\n 455,4356,1501,2455, 405,1095,2955, 338,1586,1266,1819, 570, 641,1324, 237,1556, # 4128\n2650,1388,3723,6184,1368,2384,1343,1978,3089,2436, 879,3724, 792,1191, 758,3012, # 4144\n1411,2135,1322,4357, 240,4667,1848,3725,1574,6185, 420,3045,1546,1391, 714,4358, # 4160\n1967, 941,1864, 863, 664, 426, 560,1731,2680,1785,2864,1949,2363, 403,3330,1415, # 4176\n1279,2136,1697,2335, 204, 721,2097,3838,  90,6186,2085,2505, 191,3967, 124,2148, # 4192\n1376,1798,1178,1107,1898,1405, 860,4359,1243,1272,2375,2983,1558,2456,1638, 113, # 4208\n3621, 578,1923,2609, 880, 386,4130, 784,2186,2266,1422,2956,2172,1722, 497, 263, # 4224\n2514,1267,2412,2610, 177,2703,3542, 774,1927,1344, 616,1432,1595,1018, 172,4360, # 4240\n2325, 911,4361, 438,1468,3622, 794,3968,2024,2173,1681,1829,2957, 945, 895,3090, # 4256\n 575,2212,2476, 475,2401,2681, 785,2744,1745,2293,2555,1975,3133,2865, 394,4668, # 4272\n3839, 635,4131, 639, 202,1507,2195,2766,1345,1435,2572,3726,1908,1184,1181,2457, # 4288\n3727,3134,4362, 843,2611, 437, 916,4669, 234, 769,1884,3046,3047,3623, 833,6187, # 4304\n1639,2250,2402,1355,1185,2010,2047, 999, 525,1732,1290,1488,2612, 948,1578,3728, # 4320\n2413,2477,1216,2725,2159, 334,3840,1328,3624,2921,1525,4132, 564,1056, 891,4363, # 4336\n1444,1698,2385,2251,3729,1365,2281,2235,1717,6188, 864,3841,2515, 444, 527,2767, # 4352\n2922,3625, 544, 461,6189, 566, 209,2437,3398,2098,1065,2068,3331,3626,3257,2137, # 4368  #last 512\n)\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/jpcntx.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n\n# This is hiragana 2-char sequence table, the number in each cell represents its frequency category\njp2CharContext = (\n(0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1),\n(2,4,0,4,0,3,0,4,0,3,4,4,4,2,4,3,3,4,3,2,3,3,4,2,3,3,3,2,4,1,4,3,3,1,5,4,3,4,3,4,3,5,3,0,3,5,4,2,0,3,1,0,3,3,0,3,3,0,1,1,0,4,3,0,3,3,0,4,0,2,0,3,5,5,5,5,4,0,4,1,0,3,4),\n(0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2),\n(0,4,0,5,0,5,0,4,0,4,5,4,4,3,5,3,5,1,5,3,4,3,4,4,3,4,3,3,4,3,5,4,4,3,5,5,3,5,5,5,3,5,5,3,4,5,5,3,1,3,2,0,3,4,0,4,2,0,4,2,1,5,3,2,3,5,0,4,0,2,0,5,4,4,5,4,5,0,4,0,0,4,4),\n(0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0),\n(0,3,0,4,0,3,0,3,0,4,5,4,3,3,3,3,4,3,5,4,4,3,5,4,4,3,4,3,4,4,4,4,5,3,4,4,3,4,5,5,4,5,5,1,4,5,4,3,0,3,3,1,3,3,0,4,4,0,3,3,1,5,3,3,3,5,0,4,0,3,0,4,4,3,4,3,3,0,4,1,1,3,4),\n(0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0),\n(0,4,0,3,0,3,0,4,0,3,4,4,3,2,2,1,2,1,3,1,3,3,3,3,3,4,3,1,3,3,5,3,3,0,4,3,0,5,4,3,3,5,4,4,3,4,4,5,0,1,2,0,1,2,0,2,2,0,1,0,0,5,2,2,1,4,0,3,0,1,0,4,4,3,5,4,3,0,2,1,0,4,3),\n(0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0),\n(0,3,0,5,0,4,0,2,1,4,4,2,4,1,4,2,4,2,4,3,3,3,4,3,3,3,3,1,4,2,3,3,3,1,4,4,1,1,1,4,3,3,2,0,2,4,3,2,0,3,3,0,3,1,1,0,0,0,3,3,0,4,2,2,3,4,0,4,0,3,0,4,4,5,3,4,4,0,3,0,0,1,4),\n(1,4,0,4,0,4,0,4,0,3,5,4,4,3,4,3,5,4,3,3,4,3,5,4,4,4,4,3,4,2,4,3,3,1,5,4,3,2,4,5,4,5,5,4,4,5,4,4,0,3,2,2,3,3,0,4,3,1,3,2,1,4,3,3,4,5,0,3,0,2,0,4,5,5,4,5,4,0,4,0,0,5,4),\n(0,5,0,5,0,4,0,3,0,4,4,3,4,3,3,3,4,0,4,4,4,3,4,3,4,3,3,1,4,2,4,3,4,0,5,4,1,4,5,4,4,5,3,2,4,3,4,3,2,4,1,3,3,3,2,3,2,0,4,3,3,4,3,3,3,4,0,4,0,3,0,4,5,4,4,4,3,0,4,1,0,1,3),\n(0,3,1,4,0,3,0,2,0,3,4,4,3,1,4,2,3,3,4,3,4,3,4,3,4,4,3,2,3,1,5,4,4,1,4,4,3,5,4,4,3,5,5,4,3,4,4,3,1,2,3,1,2,2,0,3,2,0,3,1,0,5,3,3,3,4,3,3,3,3,4,4,4,4,5,4,2,0,3,3,2,4,3),\n(0,2,0,3,0,1,0,1,0,0,3,2,0,0,2,0,1,0,2,1,3,3,3,1,2,3,1,0,1,0,4,2,1,1,3,3,0,4,3,3,1,4,3,3,0,3,3,2,0,0,0,0,1,0,0,2,0,0,0,0,0,4,1,0,2,3,2,2,2,1,3,3,3,4,4,3,2,0,3,1,0,3,3),\n(0,4,0,4,0,3,0,3,0,4,4,4,3,3,3,3,3,3,4,3,4,2,4,3,4,3,3,2,4,3,4,5,4,1,4,5,3,5,4,5,3,5,4,0,3,5,5,3,1,3,3,2,2,3,0,3,4,1,3,3,2,4,3,3,3,4,0,4,0,3,0,4,5,4,4,5,3,0,4,1,0,3,4),\n(0,2,0,3,0,3,0,0,0,2,2,2,1,0,1,0,0,0,3,0,3,0,3,0,1,3,1,0,3,1,3,3,3,1,3,3,3,0,1,3,1,3,4,0,0,3,1,1,0,3,2,0,0,0,0,1,3,0,1,0,0,3,3,2,0,3,0,0,0,0,0,3,4,3,4,3,3,0,3,0,0,2,3),\n(2,3,0,3,0,2,0,1,0,3,3,4,3,1,3,1,1,1,3,1,4,3,4,3,3,3,0,0,3,1,5,4,3,1,4,3,2,5,5,4,4,4,4,3,3,4,4,4,0,2,1,1,3,2,0,1,2,0,0,1,0,4,1,3,3,3,0,3,0,1,0,4,4,4,5,5,3,0,2,0,0,4,4),\n(0,2,0,1,0,3,1,3,0,2,3,3,3,0,3,1,0,0,3,0,3,2,3,1,3,2,1,1,0,0,4,2,1,0,2,3,1,4,3,2,0,4,4,3,1,3,1,3,0,1,0,0,1,0,0,0,1,0,0,0,0,4,1,1,1,2,0,3,0,0,0,3,4,2,4,3,2,0,1,0,0,3,3),\n(0,1,0,4,0,5,0,4,0,2,4,4,2,3,3,2,3,3,5,3,3,3,4,3,4,2,3,0,4,3,3,3,4,1,4,3,2,1,5,5,3,4,5,1,3,5,4,2,0,3,3,0,1,3,0,4,2,0,1,3,1,4,3,3,3,3,0,3,0,1,0,3,4,4,4,5,5,0,3,0,1,4,5),\n(0,2,0,3,0,3,0,0,0,2,3,1,3,0,4,0,1,1,3,0,3,4,3,2,3,1,0,3,3,2,3,1,3,0,2,3,0,2,1,4,1,2,2,0,0,3,3,0,0,2,0,0,0,1,0,0,0,0,2,2,0,3,2,1,3,3,0,2,0,2,0,0,3,3,1,2,4,0,3,0,2,2,3),\n(2,4,0,5,0,4,0,4,0,2,4,4,4,3,4,3,3,3,1,2,4,3,4,3,4,4,5,0,3,3,3,3,2,0,4,3,1,4,3,4,1,4,4,3,3,4,4,3,1,2,3,0,4,2,0,4,1,0,3,3,0,4,3,3,3,4,0,4,0,2,0,3,5,3,4,5,2,0,3,0,0,4,5),\n(0,3,0,4,0,1,0,1,0,1,3,2,2,1,3,0,3,0,2,0,2,0,3,0,2,0,0,0,1,0,1,1,0,0,3,1,0,0,0,4,0,3,1,0,2,1,3,0,0,0,0,0,0,3,0,0,0,0,0,0,0,4,2,2,3,1,0,3,0,0,0,1,4,4,4,3,0,0,4,0,0,1,4),\n(1,4,1,5,0,3,0,3,0,4,5,4,4,3,5,3,3,4,4,3,4,1,3,3,3,3,2,1,4,1,5,4,3,1,4,4,3,5,4,4,3,5,4,3,3,4,4,4,0,3,3,1,2,3,0,3,1,0,3,3,0,5,4,4,4,4,4,4,3,3,5,4,4,3,3,5,4,0,3,2,0,4,4),\n(0,2,0,3,0,1,0,0,0,1,3,3,3,2,4,1,3,0,3,1,3,0,2,2,1,1,0,0,2,0,4,3,1,0,4,3,0,4,4,4,1,4,3,1,1,3,3,1,0,2,0,0,1,3,0,0,0,0,2,0,0,4,3,2,4,3,5,4,3,3,3,4,3,3,4,3,3,0,2,1,0,3,3),\n(0,2,0,4,0,3,0,2,0,2,5,5,3,4,4,4,4,1,4,3,3,0,4,3,4,3,1,3,3,2,4,3,0,3,4,3,0,3,4,4,2,4,4,0,4,5,3,3,2,2,1,1,1,2,0,1,5,0,3,3,2,4,3,3,3,4,0,3,0,2,0,4,4,3,5,5,0,0,3,0,2,3,3),\n(0,3,0,4,0,3,0,1,0,3,4,3,3,1,3,3,3,0,3,1,3,0,4,3,3,1,1,0,3,0,3,3,0,0,4,4,0,1,5,4,3,3,5,0,3,3,4,3,0,2,0,1,1,1,0,1,3,0,1,2,1,3,3,2,3,3,0,3,0,1,0,1,3,3,4,4,1,0,1,2,2,1,3),\n(0,1,0,4,0,4,0,3,0,1,3,3,3,2,3,1,1,0,3,0,3,3,4,3,2,4,2,0,1,0,4,3,2,0,4,3,0,5,3,3,2,4,4,4,3,3,3,4,0,1,3,0,0,1,0,0,1,0,0,0,0,4,2,3,3,3,0,3,0,0,0,4,4,4,5,3,2,0,3,3,0,3,5),\n(0,2,0,3,0,0,0,3,0,1,3,0,2,0,0,0,1,0,3,1,1,3,3,0,0,3,0,0,3,0,2,3,1,0,3,1,0,3,3,2,0,4,2,2,0,2,0,0,0,4,0,0,0,0,0,0,0,0,0,0,0,2,1,2,0,1,0,1,0,0,0,1,3,1,2,0,0,0,1,0,0,1,4),\n(0,3,0,3,0,5,0,1,0,2,4,3,1,3,3,2,1,1,5,2,1,0,5,1,2,0,0,0,3,3,2,2,3,2,4,3,0,0,3,3,1,3,3,0,2,5,3,4,0,3,3,0,1,2,0,2,2,0,3,2,0,2,2,3,3,3,0,2,0,1,0,3,4,4,2,5,4,0,3,0,0,3,5),\n(0,3,0,3,0,3,0,1,0,3,3,3,3,0,3,0,2,0,2,1,1,0,2,0,1,0,0,0,2,1,0,0,1,0,3,2,0,0,3,3,1,2,3,1,0,3,3,0,0,1,0,0,0,0,0,2,0,0,0,0,0,2,3,1,2,3,0,3,0,1,0,3,2,1,0,4,3,0,1,1,0,3,3),\n(0,4,0,5,0,3,0,3,0,4,5,5,4,3,5,3,4,3,5,3,3,2,5,3,4,4,4,3,4,3,4,5,5,3,4,4,3,4,4,5,4,4,4,3,4,5,5,4,2,3,4,2,3,4,0,3,3,1,4,3,2,4,3,3,5,5,0,3,0,3,0,5,5,5,5,4,4,0,4,0,1,4,4),\n(0,4,0,4,0,3,0,3,0,3,5,4,4,2,3,2,5,1,3,2,5,1,4,2,3,2,3,3,4,3,3,3,3,2,5,4,1,3,3,5,3,4,4,0,4,4,3,1,1,3,1,0,2,3,0,2,3,0,3,0,0,4,3,1,3,4,0,3,0,2,0,4,4,4,3,4,5,0,4,0,0,3,4),\n(0,3,0,3,0,3,1,2,0,3,4,4,3,3,3,0,2,2,4,3,3,1,3,3,3,1,1,0,3,1,4,3,2,3,4,4,2,4,4,4,3,4,4,3,2,4,4,3,1,3,3,1,3,3,0,4,1,0,2,2,1,4,3,2,3,3,5,4,3,3,5,4,4,3,3,0,4,0,3,2,2,4,4),\n(0,2,0,1,0,0,0,0,0,1,2,1,3,0,0,0,0,0,2,0,1,2,1,0,0,1,0,0,0,0,3,0,0,1,0,1,1,3,1,0,0,0,1,1,0,1,1,0,0,0,0,0,2,0,0,0,0,0,0,0,0,1,1,2,2,0,3,4,0,0,0,1,1,0,0,1,0,0,0,0,0,1,1),\n(0,1,0,0,0,1,0,0,0,0,4,0,4,1,4,0,3,0,4,0,3,0,4,0,3,0,3,0,4,1,5,1,4,0,0,3,0,5,0,5,2,0,1,0,0,0,2,1,4,0,1,3,0,0,3,0,0,3,1,1,4,1,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0),\n(1,4,0,5,0,3,0,2,0,3,5,4,4,3,4,3,5,3,4,3,3,0,4,3,3,3,3,3,3,2,4,4,3,1,3,4,4,5,4,4,3,4,4,1,3,5,4,3,3,3,1,2,2,3,3,1,3,1,3,3,3,5,3,3,4,5,0,3,0,3,0,3,4,3,4,4,3,0,3,0,2,4,3),\n(0,1,0,4,0,0,0,0,0,1,4,0,4,1,4,2,4,0,3,0,1,0,1,0,0,0,0,0,2,0,3,1,1,1,0,3,0,0,0,1,2,1,0,0,1,1,1,1,0,1,0,0,0,1,0,0,3,0,0,0,0,3,2,0,2,2,0,1,0,0,0,2,3,2,3,3,0,0,0,0,2,1,0),\n(0,5,1,5,0,3,0,3,0,5,4,4,5,1,5,3,3,0,4,3,4,3,5,3,4,3,3,2,4,3,4,3,3,0,3,3,1,4,4,3,4,4,4,3,4,5,5,3,2,3,1,1,3,3,1,3,1,1,3,3,2,4,5,3,3,5,0,4,0,3,0,4,4,3,5,3,3,0,3,4,0,4,3),\n(0,5,0,5,0,3,0,2,0,4,4,3,5,2,4,3,3,3,4,4,4,3,5,3,5,3,3,1,4,0,4,3,3,0,3,3,0,4,4,4,4,5,4,3,3,5,5,3,2,3,1,2,3,2,0,1,0,0,3,2,2,4,4,3,1,5,0,4,0,3,0,4,3,1,3,2,1,0,3,3,0,3,3),\n(0,4,0,5,0,5,0,4,0,4,5,5,5,3,4,3,3,2,5,4,4,3,5,3,5,3,4,0,4,3,4,4,3,2,4,4,3,4,5,4,4,5,5,0,3,5,5,4,1,3,3,2,3,3,1,3,1,0,4,3,1,4,4,3,4,5,0,4,0,2,0,4,3,4,4,3,3,0,4,0,0,5,5),\n(0,4,0,4,0,5,0,1,1,3,3,4,4,3,4,1,3,0,5,1,3,0,3,1,3,1,1,0,3,0,3,3,4,0,4,3,0,4,4,4,3,4,4,0,3,5,4,1,0,3,0,0,2,3,0,3,1,0,3,1,0,3,2,1,3,5,0,3,0,1,0,3,2,3,3,4,4,0,2,2,0,4,4),\n(2,4,0,5,0,4,0,3,0,4,5,5,4,3,5,3,5,3,5,3,5,2,5,3,4,3,3,4,3,4,5,3,2,1,5,4,3,2,3,4,5,3,4,1,2,5,4,3,0,3,3,0,3,2,0,2,3,0,4,1,0,3,4,3,3,5,0,3,0,1,0,4,5,5,5,4,3,0,4,2,0,3,5),\n(0,5,0,4,0,4,0,2,0,5,4,3,4,3,4,3,3,3,4,3,4,2,5,3,5,3,4,1,4,3,4,4,4,0,3,5,0,4,4,4,4,5,3,1,3,4,5,3,3,3,3,3,3,3,0,2,2,0,3,3,2,4,3,3,3,5,3,4,1,3,3,5,3,2,0,0,0,0,4,3,1,3,3),\n(0,1,0,3,0,3,0,1,0,1,3,3,3,2,3,3,3,0,3,0,0,0,3,1,3,0,0,0,2,2,2,3,0,0,3,2,0,1,2,4,1,3,3,0,0,3,3,3,0,1,0,0,2,1,0,0,3,0,3,1,0,3,0,0,1,3,0,2,0,1,0,3,3,1,3,3,0,0,1,1,0,3,3),\n(0,2,0,3,0,2,1,4,0,2,2,3,1,1,3,1,1,0,2,0,3,1,2,3,1,3,0,0,1,0,4,3,2,3,3,3,1,4,2,3,3,3,3,1,0,3,1,4,0,1,1,0,1,2,0,1,1,0,1,1,0,3,1,3,2,2,0,1,0,0,0,2,3,3,3,1,0,0,0,0,0,2,3),\n(0,5,0,4,0,5,0,2,0,4,5,5,3,3,4,3,3,1,5,4,4,2,4,4,4,3,4,2,4,3,5,5,4,3,3,4,3,3,5,5,4,5,5,1,3,4,5,3,1,4,3,1,3,3,0,3,3,1,4,3,1,4,5,3,3,5,0,4,0,3,0,5,3,3,1,4,3,0,4,0,1,5,3),\n(0,5,0,5,0,4,0,2,0,4,4,3,4,3,3,3,3,3,5,4,4,4,4,4,4,5,3,3,5,2,4,4,4,3,4,4,3,3,4,4,5,5,3,3,4,3,4,3,3,4,3,3,3,3,1,2,2,1,4,3,3,5,4,4,3,4,0,4,0,3,0,4,4,4,4,4,1,0,4,2,0,2,4),\n(0,4,0,4,0,3,0,1,0,3,5,2,3,0,3,0,2,1,4,2,3,3,4,1,4,3,3,2,4,1,3,3,3,0,3,3,0,0,3,3,3,5,3,3,3,3,3,2,0,2,0,0,2,0,0,2,0,0,1,0,0,3,1,2,2,3,0,3,0,2,0,4,4,3,3,4,1,0,3,0,0,2,4),\n(0,0,0,4,0,0,0,0,0,0,1,0,1,0,2,0,0,0,0,0,1,0,2,0,1,0,0,0,0,0,3,1,3,0,3,2,0,0,0,1,0,3,2,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,3,4,0,2,0,0,0,0,0,0,2),\n(0,2,1,3,0,2,0,2,0,3,3,3,3,1,3,1,3,3,3,3,3,3,4,2,2,1,2,1,4,0,4,3,1,3,3,3,2,4,3,5,4,3,3,3,3,3,3,3,0,1,3,0,2,0,0,1,0,0,1,0,0,4,2,0,2,3,0,3,3,0,3,3,4,2,3,1,4,0,1,2,0,2,3),\n(0,3,0,3,0,1,0,3,0,2,3,3,3,0,3,1,2,0,3,3,2,3,3,2,3,2,3,1,3,0,4,3,2,0,3,3,1,4,3,3,2,3,4,3,1,3,3,1,1,0,1,1,0,1,0,1,0,1,0,0,0,4,1,1,0,3,0,3,1,0,2,3,3,3,3,3,1,0,0,2,0,3,3),\n(0,0,0,0,0,0,0,0,0,0,3,0,2,0,3,0,0,0,0,0,0,0,3,0,0,0,0,0,0,0,3,0,3,0,3,1,0,1,0,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,3,0,2,0,2,3,0,0,0,0,0,0,0,0,3),\n(0,2,0,3,1,3,0,3,0,2,3,3,3,1,3,1,3,1,3,1,3,3,3,1,3,0,2,3,1,1,4,3,3,2,3,3,1,2,2,4,1,3,3,0,1,4,2,3,0,1,3,0,3,0,0,1,3,0,2,0,0,3,3,2,1,3,0,3,0,2,0,3,4,4,4,3,1,0,3,0,0,3,3),\n(0,2,0,1,0,2,0,0,0,1,3,2,2,1,3,0,1,1,3,0,3,2,3,1,2,0,2,0,1,1,3,3,3,0,3,3,1,1,2,3,2,3,3,1,2,3,2,0,0,1,0,0,0,0,0,0,3,0,1,0,0,2,1,2,1,3,0,3,0,0,0,3,4,4,4,3,2,0,2,0,0,2,4),\n(0,0,0,1,0,1,0,0,0,0,1,0,0,0,1,0,0,0,0,0,0,0,1,1,1,0,0,0,0,0,0,0,0,0,2,2,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,1,3,1,0,0,0,0,0,0,0,3),\n(0,3,0,3,0,2,0,3,0,3,3,3,2,3,2,2,2,0,3,1,3,3,3,2,3,3,0,0,3,0,3,2,2,0,2,3,1,4,3,4,3,3,2,3,1,5,4,4,0,3,1,2,1,3,0,3,1,1,2,0,2,3,1,3,1,3,0,3,0,1,0,3,3,4,4,2,1,0,2,1,0,2,4),\n(0,1,0,3,0,1,0,2,0,1,4,2,5,1,4,0,2,0,2,1,3,1,4,0,2,1,0,0,2,1,4,1,1,0,3,3,0,5,1,3,2,3,3,1,0,3,2,3,0,1,0,0,0,0,0,0,1,0,0,0,0,4,0,1,0,3,0,2,0,1,0,3,3,3,4,3,3,0,0,0,0,2,3),\n(0,0,0,1,0,0,0,0,0,0,2,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,3,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,1,0,0,1,0,0,0,0,0,3),\n(0,1,0,3,0,4,0,3,0,2,4,3,1,0,3,2,2,1,3,1,2,2,3,1,1,1,2,1,3,0,1,2,0,1,3,2,1,3,0,5,5,1,0,0,1,3,2,1,0,3,0,0,1,0,0,0,0,0,3,4,0,1,1,1,3,2,0,2,0,1,0,2,3,3,1,2,3,0,1,0,1,0,4),\n(0,0,0,1,0,3,0,3,0,2,2,1,0,0,4,0,3,0,3,1,3,0,3,0,3,0,1,0,3,0,3,1,3,0,3,3,0,0,1,2,1,1,1,0,1,2,0,0,0,1,0,0,1,0,0,0,0,0,0,0,0,2,2,1,2,0,0,2,0,0,0,0,2,3,3,3,3,0,0,0,0,1,4),\n(0,0,0,3,0,3,0,0,0,0,3,1,1,0,3,0,1,0,2,0,1,0,0,0,0,0,0,0,1,0,3,0,2,0,2,3,0,0,2,2,3,1,2,0,0,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,3,0,0,2,0,0,0,0,2,3),\n(2,4,0,5,0,5,0,4,0,3,4,3,3,3,4,3,3,3,4,3,4,4,5,4,5,5,5,2,3,0,5,5,4,1,5,4,3,1,5,4,3,4,4,3,3,4,3,3,0,3,2,0,2,3,0,3,0,0,3,3,0,5,3,2,3,3,0,3,0,3,0,3,4,5,4,5,3,0,4,3,0,3,4),\n(0,3,0,3,0,3,0,3,0,3,3,4,3,2,3,2,3,0,4,3,3,3,3,3,3,3,3,0,3,2,4,3,3,1,3,4,3,4,4,4,3,4,4,3,2,4,4,1,0,2,0,0,1,1,0,2,0,0,3,1,0,5,3,2,1,3,0,3,0,1,2,4,3,2,4,3,3,0,3,2,0,4,4),\n(0,3,0,3,0,1,0,0,0,1,4,3,3,2,3,1,3,1,4,2,3,2,4,2,3,4,3,0,2,2,3,3,3,0,3,3,3,0,3,4,1,3,3,0,3,4,3,3,0,1,1,0,1,0,0,0,4,0,3,0,0,3,1,2,1,3,0,4,0,1,0,4,3,3,4,3,3,0,2,0,0,3,3),\n(0,3,0,4,0,1,0,3,0,3,4,3,3,0,3,3,3,1,3,1,3,3,4,3,3,3,0,0,3,1,5,3,3,1,3,3,2,5,4,3,3,4,5,3,2,5,3,4,0,1,0,0,0,0,0,2,0,0,1,1,0,4,2,2,1,3,0,3,0,2,0,4,4,3,5,3,2,0,1,1,0,3,4),\n(0,5,0,4,0,5,0,2,0,4,4,3,3,2,3,3,3,1,4,3,4,1,5,3,4,3,4,0,4,2,4,3,4,1,5,4,0,4,4,4,4,5,4,1,3,5,4,2,1,4,1,1,3,2,0,3,1,0,3,2,1,4,3,3,3,4,0,4,0,3,0,4,4,4,3,3,3,0,4,2,0,3,4),\n(1,4,0,4,0,3,0,1,0,3,3,3,1,1,3,3,2,2,3,3,1,0,3,2,2,1,2,0,3,1,2,1,2,0,3,2,0,2,2,3,3,4,3,0,3,3,1,2,0,1,1,3,1,2,0,0,3,0,1,1,0,3,2,2,3,3,0,3,0,0,0,2,3,3,4,3,3,0,1,0,0,1,4),\n(0,4,0,4,0,4,0,0,0,3,4,4,3,1,4,2,3,2,3,3,3,1,4,3,4,0,3,0,4,2,3,3,2,2,5,4,2,1,3,4,3,4,3,1,3,3,4,2,0,2,1,0,3,3,0,0,2,0,3,1,0,4,4,3,4,3,0,4,0,1,0,2,4,4,4,4,4,0,3,2,0,3,3),\n(0,0,0,1,0,4,0,0,0,0,0,0,1,1,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,3,2,0,0,1,0,0,0,1,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,2),\n(0,2,0,3,0,4,0,4,0,1,3,3,3,0,4,0,2,1,2,1,1,1,2,0,3,1,1,0,1,0,3,1,0,0,3,3,2,0,1,1,0,0,0,0,0,1,0,2,0,2,2,0,3,1,0,0,1,0,1,1,0,1,2,0,3,0,0,0,0,1,0,0,3,3,4,3,1,0,1,0,3,0,2),\n(0,0,0,3,0,5,0,0,0,0,1,0,2,0,3,1,0,1,3,0,0,0,2,0,0,0,1,0,0,0,1,1,0,0,4,0,0,0,2,3,0,1,4,1,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,3,0,0,0,0,0,1,0,0,0,0,0,0,0,2,0,0,3,0,0,0,0,0,3),\n(0,2,0,5,0,5,0,1,0,2,4,3,3,2,5,1,3,2,3,3,3,0,4,1,2,0,3,0,4,0,2,2,1,1,5,3,0,0,1,4,2,3,2,0,3,3,3,2,0,2,4,1,1,2,0,1,1,0,3,1,0,1,3,1,2,3,0,2,0,0,0,1,3,5,4,4,4,0,3,0,0,1,3),\n(0,4,0,5,0,4,0,4,0,4,5,4,3,3,4,3,3,3,4,3,4,4,5,3,4,5,4,2,4,2,3,4,3,1,4,4,1,3,5,4,4,5,5,4,4,5,5,5,2,3,3,1,4,3,1,3,3,0,3,3,1,4,3,4,4,4,0,3,0,4,0,3,3,4,4,5,0,0,4,3,0,4,5),\n(0,4,0,4,0,3,0,3,0,3,4,4,4,3,3,2,4,3,4,3,4,3,5,3,4,3,2,1,4,2,4,4,3,1,3,4,2,4,5,5,3,4,5,4,1,5,4,3,0,3,2,2,3,2,1,3,1,0,3,3,3,5,3,3,3,5,4,4,2,3,3,4,3,3,3,2,1,0,3,2,1,4,3),\n(0,4,0,5,0,4,0,3,0,3,5,5,3,2,4,3,4,0,5,4,4,1,4,4,4,3,3,3,4,3,5,5,2,3,3,4,1,2,5,5,3,5,5,2,3,5,5,4,0,3,2,0,3,3,1,1,5,1,4,1,0,4,3,2,3,5,0,4,0,3,0,5,4,3,4,3,0,0,4,1,0,4,4),\n(1,3,0,4,0,2,0,2,0,2,5,5,3,3,3,3,3,0,4,2,3,4,4,4,3,4,0,0,3,4,5,4,3,3,3,3,2,5,5,4,5,5,5,4,3,5,5,5,1,3,1,0,1,0,0,3,2,0,4,2,0,5,2,3,2,4,1,3,0,3,0,4,5,4,5,4,3,0,4,2,0,5,4),\n(0,3,0,4,0,5,0,3,0,3,4,4,3,2,3,2,3,3,3,3,3,2,4,3,3,2,2,0,3,3,3,3,3,1,3,3,3,0,4,4,3,4,4,1,1,4,4,2,0,3,1,0,1,1,0,4,1,0,2,3,1,3,3,1,3,4,0,3,0,1,0,3,1,3,0,0,1,0,2,0,0,4,4),\n(0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0),\n(0,3,0,3,0,2,0,3,0,1,5,4,3,3,3,1,4,2,1,2,3,4,4,2,4,4,5,0,3,1,4,3,4,0,4,3,3,3,2,3,2,5,3,4,3,2,2,3,0,0,3,0,2,1,0,1,2,0,0,0,0,2,1,1,3,1,0,2,0,4,0,3,4,4,4,5,2,0,2,0,0,1,3),\n(0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,1,1,1,0,0,1,1,0,0,0,4,2,1,1,0,1,0,3,2,0,0,3,1,1,1,2,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,3,0,1,0,0,0,2,0,0,0,1,4,0,4,2,1,0,0,0,0,0,1),\n(0,0,0,0,0,0,0,0,0,1,0,1,0,0,0,0,1,0,0,0,0,0,0,1,0,1,0,0,0,0,3,1,0,0,0,2,0,2,1,0,0,1,2,1,0,1,1,0,0,3,0,0,0,0,0,0,0,0,0,0,0,1,3,1,0,0,0,0,0,1,0,0,2,1,0,0,0,0,0,0,0,0,2),\n(0,4,0,4,0,4,0,3,0,4,4,3,4,2,4,3,2,0,4,4,4,3,5,3,5,3,3,2,4,2,4,3,4,3,1,4,0,2,3,4,4,4,3,3,3,4,4,4,3,4,1,3,4,3,2,1,2,1,3,3,3,4,4,3,3,5,0,4,0,3,0,4,3,3,3,2,1,0,3,0,0,3,3),\n(0,4,0,3,0,3,0,3,0,3,5,5,3,3,3,3,4,3,4,3,3,3,4,4,4,3,3,3,3,4,3,5,3,3,1,3,2,4,5,5,5,5,4,3,4,5,5,3,2,2,3,3,3,3,2,3,3,1,2,3,2,4,3,3,3,4,0,4,0,2,0,4,3,2,2,1,2,0,3,0,0,4,1),\n)\n\nclass JapaneseContextAnalysis(object):\n    NUM_OF_CATEGORY = 6\n    DONT_KNOW = -1\n    ENOUGH_REL_THRESHOLD = 100\n    MAX_REL_THRESHOLD = 1000\n    MINIMUM_DATA_THRESHOLD = 4\n\n    def __init__(self):\n        self._total_rel = None\n        self._rel_sample = None\n        self._need_to_skip_char_num = None\n        self._last_char_order = None\n        self._done = None\n        self.reset()\n\n    def reset(self):\n        self._total_rel = 0  # total sequence received\n        # category counters, each integer counts sequence in its category\n        self._rel_sample = [0] * self.NUM_OF_CATEGORY\n        # if last byte in current buffer is not the last byte of a character,\n        # we need to know how many bytes to skip in next buffer\n        self._need_to_skip_char_num = 0\n        self._last_char_order = -1  # The order of previous char\n        # If this flag is set to True, detection is done and conclusion has\n        # been made\n        self._done = False\n\n    def feed(self, byte_str, num_bytes):\n        if self._done:\n            return\n\n        # The buffer we got is byte oriented, and a character may span in more than one\n        # buffers. In case the last one or two byte in last buffer is not\n        # complete, we record how many byte needed to complete that character\n        # and skip these bytes here.  We can choose to record those bytes as\n        # well and analyse the character once it is complete, but since a\n        # character will not make much difference, by simply skipping\n        # this character will simply our logic and improve performance.\n        i = self._need_to_skip_char_num\n        while i < num_bytes:\n            order, char_len = self.get_order(byte_str[i:i + 2])\n            i += char_len\n            if i > num_bytes:\n                self._need_to_skip_char_num = i - num_bytes\n                self._last_char_order = -1\n            else:\n                if (order != -1) and (self._last_char_order != -1):\n                    self._total_rel += 1\n                    if self._total_rel > self.MAX_REL_THRESHOLD:\n                        self._done = True\n                        break\n                    self._rel_sample[jp2CharContext[self._last_char_order][order]] += 1\n                self._last_char_order = order\n\n    def got_enough_data(self):\n        return self._total_rel > self.ENOUGH_REL_THRESHOLD\n\n    def get_confidence(self):\n        # This is just one way to calculate confidence. It works well for me.\n        if self._total_rel > self.MINIMUM_DATA_THRESHOLD:\n            return (self._total_rel - self._rel_sample[0]) / self._total_rel\n        else:\n            return self.DONT_KNOW\n\n    def get_order(self, byte_str):\n        return -1, 1\n\nclass SJISContextAnalysis(JapaneseContextAnalysis):\n    def __init__(self):\n        super(SJISContextAnalysis, self).__init__()\n        self._charset_name = \"SHIFT_JIS\"\n\n    @property\n    def charset_name(self):\n        return self._charset_name\n\n    def get_order(self, byte_str):\n        if not byte_str:\n            return -1, 1\n        # find out current char's byte length\n        first_char = byte_str[0]\n        if (0x81 <= first_char <= 0x9F) or (0xE0 <= first_char <= 0xFC):\n            char_len = 2\n            if (first_char == 0x87) or (0xFA <= first_char <= 0xFC):\n                self._charset_name = \"CP932\"\n        else:\n            char_len = 1\n\n        # return its order if it is hiragana\n        if len(byte_str) > 1:\n            second_char = byte_str[1]\n            if (first_char == 202) and (0x9F <= second_char <= 0xF1):\n                return second_char - 0x9F, char_len\n\n        return -1, char_len\n\nclass EUCJPContextAnalysis(JapaneseContextAnalysis):\n    def get_order(self, byte_str):\n        if not byte_str:\n            return -1, 1\n        # find out current char's byte length\n        first_char = byte_str[0]\n        if (first_char == 0x8E) or (0xA1 <= first_char <= 0xFE):\n            char_len = 2\n        elif first_char == 0x8F:\n            char_len = 3\n        else:\n            char_len = 1\n\n        # return its order if it is hiragana\n        if len(byte_str) > 1:\n            second_char = byte_str[1]\n            if (first_char == 0xA4) and (0xA1 <= second_char <= 0xF3):\n                return second_char - 0xA1, char_len\n\n        return -1, char_len\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/langbulgarianmodel.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n# 255: Control characters that usually does not exist in any text\n# 254: Carriage/Return\n# 253: symbol (punctuation) that does not belong to word\n# 252: 0 - 9\n\n# Character Mapping Table:\n# this table is modified base on win1251BulgarianCharToOrderMap, so\n# only number <64 is sure valid\n\nLatin5_BulgarianCharToOrderMap = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253, 77, 90, 99,100, 72,109,107,101, 79,185, 81,102, 76, 94, 82,  # 40\n110,186,108, 91, 74,119, 84, 96,111,187,115,253,253,253,253,253,  # 50\n253, 65, 69, 70, 66, 63, 68,112,103, 92,194,104, 95, 86, 87, 71,  # 60\n116,195, 85, 93, 97,113,196,197,198,199,200,253,253,253,253,253,  # 70\n194,195,196,197,198,199,200,201,202,203,204,205,206,207,208,209,  # 80\n210,211,212,213,214,215,216,217,218,219,220,221,222,223,224,225,  # 90\n 81,226,227,228,229,230,105,231,232,233,234,235,236, 45,237,238,  # a0\n 31, 32, 35, 43, 37, 44, 55, 47, 40, 59, 33, 46, 38, 36, 41, 30,  # b0\n 39, 28, 34, 51, 48, 49, 53, 50, 54, 57, 61,239, 67,240, 60, 56,  # c0\n  1, 18,  9, 20, 11,  3, 23, 15,  2, 26, 12, 10, 14,  6,  4, 13,  # d0\n  7,  8,  5, 19, 29, 25, 22, 21, 27, 24, 17, 75, 52,241, 42, 16,  # e0\n 62,242,243,244, 58,245, 98,246,247,248,249,250,251, 91,252,253,  # f0\n)\n\nwin1251BulgarianCharToOrderMap = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253, 77, 90, 99,100, 72,109,107,101, 79,185, 81,102, 76, 94, 82,  # 40\n110,186,108, 91, 74,119, 84, 96,111,187,115,253,253,253,253,253,  # 50\n253, 65, 69, 70, 66, 63, 68,112,103, 92,194,104, 95, 86, 87, 71,  # 60\n116,195, 85, 93, 97,113,196,197,198,199,200,253,253,253,253,253,  # 70\n206,207,208,209,210,211,212,213,120,214,215,216,217,218,219,220,  # 80\n221, 78, 64, 83,121, 98,117,105,222,223,224,225,226,227,228,229,  # 90\n 88,230,231,232,233,122, 89,106,234,235,236,237,238, 45,239,240,  # a0\n 73, 80,118,114,241,242,243,244,245, 62, 58,246,247,248,249,250,  # b0\n 31, 32, 35, 43, 37, 44, 55, 47, 40, 59, 33, 46, 38, 36, 41, 30,  # c0\n 39, 28, 34, 51, 48, 49, 53, 50, 54, 57, 61,251, 67,252, 60, 56,  # d0\n  1, 18,  9, 20, 11,  3, 23, 15,  2, 26, 12, 10, 14,  6,  4, 13,  # e0\n  7,  8,  5, 19, 29, 25, 22, 21, 27, 24, 17, 75, 52,253, 42, 16,  # f0\n)\n\n# Model Table:\n# total sequences: 100%\n# first 512 sequences: 96.9392%\n# first 1024 sequences:3.0618%\n# rest  sequences:     0.2992%\n# negative sequences:  0.0020%\nBulgarianLangModel = (\n0,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,3,3,3,3,3,3,3,3,2,3,3,3,3,3,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,0,3,3,3,2,2,3,2,2,1,2,2,\n3,1,3,3,2,3,3,3,3,3,3,3,3,3,3,3,3,0,3,3,3,3,3,3,3,3,3,3,0,3,0,1,\n0,0,0,0,0,0,0,0,0,0,1,0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,3,2,3,3,3,3,3,3,3,3,0,3,1,0,\n0,1,0,0,0,0,0,0,0,0,1,1,0,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n3,2,2,2,3,3,3,3,3,3,3,3,3,3,3,3,3,1,3,2,3,3,3,3,3,3,3,3,0,3,0,0,\n0,0,0,0,0,0,0,0,0,0,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,2,3,3,2,3,3,3,3,3,3,3,3,3,3,3,3,1,3,2,3,3,3,3,3,3,3,3,0,3,0,0,\n0,0,0,0,0,0,0,0,0,0,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,3,3,3,2,3,2,2,1,3,3,3,3,2,2,2,1,1,2,0,1,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,3,3,2,3,2,2,3,3,1,1,2,3,3,2,3,3,3,3,2,1,2,0,2,0,3,0,0,\n0,0,0,0,0,0,0,1,0,0,2,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,3,3,1,3,3,3,3,3,2,3,2,3,3,3,3,3,2,3,3,1,3,0,3,0,2,0,0,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,3,3,3,1,3,3,2,3,3,3,1,3,3,2,3,2,2,2,0,0,2,0,2,0,2,0,0,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,3,3,3,3,0,3,3,3,2,2,3,3,3,1,2,2,3,2,1,1,2,0,2,0,0,0,0,\n1,0,0,0,0,0,0,0,0,0,2,0,0,1,0,0,1,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,3,3,2,3,3,1,2,3,2,2,2,3,3,3,3,3,2,2,3,1,2,0,2,1,2,0,0,\n0,0,0,0,0,0,0,0,0,0,3,0,0,1,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,1,3,3,3,3,3,2,3,3,3,2,3,3,2,3,2,2,2,3,1,2,0,1,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,3,3,3,3,3,3,1,1,1,2,2,1,3,1,3,2,2,3,0,0,1,0,1,0,1,0,0,\n0,0,0,1,0,0,0,0,1,0,2,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,2,2,3,2,2,3,1,2,1,1,1,2,3,1,3,1,2,2,0,1,1,1,1,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,1,3,2,2,3,3,1,2,3,1,1,3,3,3,3,1,2,2,1,1,1,0,2,0,2,0,1,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,1,2,2,3,3,3,2,2,1,1,2,0,2,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,\n3,0,1,2,1,3,3,2,3,3,3,3,3,2,3,2,1,0,3,1,2,1,2,1,2,3,2,1,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,1,1,2,3,3,3,3,3,3,3,3,3,3,3,3,0,0,3,1,3,3,2,3,3,2,2,2,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,3,3,3,3,0,3,3,3,3,3,2,1,1,2,1,3,3,0,3,1,1,1,1,3,2,0,1,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,\n3,3,2,2,2,3,3,3,3,3,3,3,3,3,3,3,1,1,3,1,3,3,2,3,2,2,2,3,0,2,0,0,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,2,3,3,2,2,3,2,1,1,1,1,1,3,1,3,1,1,0,0,0,1,0,0,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,2,3,2,0,3,2,0,3,0,2,0,0,2,1,3,1,0,0,1,0,0,0,1,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,2,1,1,1,1,2,1,1,2,1,1,1,2,2,1,2,1,1,1,0,1,1,0,1,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,2,1,3,1,1,2,1,3,2,1,1,0,1,2,3,2,1,1,1,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,3,3,3,3,2,2,1,0,1,0,0,1,0,0,0,2,1,0,3,0,0,1,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,2,3,2,3,3,1,3,2,1,1,1,2,1,1,2,1,3,0,1,0,0,0,1,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,1,1,2,2,3,3,2,3,2,2,2,3,1,2,2,1,1,2,1,1,2,2,0,1,1,0,1,0,2,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,2,1,3,1,0,2,2,1,3,2,1,0,0,2,0,2,0,1,0,0,0,0,0,0,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,3,1,2,0,2,3,1,2,3,2,0,1,3,1,2,1,1,1,0,0,1,0,0,2,2,2,3,\n2,2,2,2,1,2,1,1,2,2,1,1,2,0,1,1,1,0,0,1,1,0,0,1,1,0,0,0,1,1,0,1,\n3,3,3,3,3,2,1,2,2,1,2,0,2,0,1,0,1,2,1,2,1,1,0,0,0,1,0,1,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,1,\n3,3,2,3,3,1,1,3,1,0,3,2,1,0,0,0,1,2,0,2,0,1,0,0,0,1,0,1,2,1,2,2,\n1,1,1,1,1,1,1,2,2,2,1,1,1,1,1,1,1,0,1,2,1,1,1,0,0,0,0,0,1,1,0,0,\n3,1,0,1,0,2,3,2,2,2,3,2,2,2,2,2,1,0,2,1,2,1,1,1,0,1,2,1,2,2,2,1,\n1,1,2,2,2,2,1,2,1,1,0,1,2,1,2,2,2,1,1,1,0,1,1,1,1,2,0,1,0,0,0,0,\n2,3,2,3,3,0,0,2,1,0,2,1,0,0,0,0,2,3,0,2,0,0,0,0,0,1,0,0,2,0,1,2,\n2,1,2,1,2,2,1,1,1,2,1,1,1,0,1,2,2,1,1,1,1,1,0,1,1,1,0,0,1,2,0,0,\n3,3,2,2,3,0,2,3,1,1,2,0,0,0,1,0,0,2,0,2,0,0,0,1,0,1,0,1,2,0,2,2,\n1,1,1,1,2,1,0,1,2,2,2,1,1,1,1,1,1,1,0,1,1,1,0,0,0,0,0,0,1,1,0,0,\n2,3,2,3,3,0,0,3,0,1,1,0,1,0,0,0,2,2,1,2,0,0,0,0,0,0,0,0,2,0,1,2,\n2,2,1,1,1,1,1,2,2,2,1,0,2,0,1,0,1,0,0,1,0,1,0,0,1,0,0,0,0,1,0,0,\n3,3,3,3,2,2,2,2,2,0,2,1,1,1,1,2,1,2,1,1,0,2,0,1,0,1,0,0,2,0,1,2,\n1,1,1,1,1,1,1,2,2,1,1,0,2,0,1,0,2,0,0,1,1,1,0,0,2,0,0,0,1,1,0,0,\n2,3,3,3,3,1,0,0,0,0,0,0,0,0,0,0,2,0,0,1,1,0,0,0,0,0,0,1,2,0,1,2,\n2,2,2,1,1,2,1,1,2,2,2,1,2,0,1,1,1,1,1,1,0,1,1,1,1,0,0,1,1,1,0,0,\n2,3,3,3,3,0,2,2,0,2,1,0,0,0,1,1,1,2,0,2,0,0,0,3,0,0,0,0,2,0,2,2,\n1,1,1,2,1,2,1,1,2,2,2,1,2,0,1,1,1,0,1,1,1,1,0,2,1,0,0,0,1,1,0,0,\n2,3,3,3,3,0,2,1,0,0,2,0,0,0,0,0,1,2,0,2,0,0,0,0,0,0,0,0,2,0,1,2,\n1,1,1,2,1,1,1,1,2,2,2,0,1,0,1,1,1,0,0,1,1,1,0,0,1,0,0,0,0,1,0,0,\n3,3,2,2,3,0,1,0,1,0,0,0,0,0,0,0,1,1,0,3,0,0,0,0,0,0,0,0,1,0,2,2,\n1,1,1,1,1,2,1,1,2,2,1,2,2,1,0,1,1,1,1,1,0,1,0,0,1,0,0,0,1,1,0,0,\n3,1,0,1,0,2,2,2,2,3,2,1,1,1,2,3,0,0,1,0,2,1,1,0,1,1,1,1,2,1,1,1,\n1,2,2,1,2,1,2,2,1,1,0,1,2,1,2,2,1,1,1,0,0,1,1,1,2,1,0,1,0,0,0,0,\n2,1,0,1,0,3,1,2,2,2,2,1,2,2,1,1,1,0,2,1,2,2,1,1,2,1,1,0,2,1,1,1,\n1,2,2,2,2,2,2,2,1,2,0,1,1,0,2,1,1,1,1,1,0,0,1,1,1,1,0,1,0,0,0,0,\n2,1,1,1,1,2,2,2,2,1,2,2,2,1,2,2,1,1,2,1,2,3,2,2,1,1,1,1,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,2,2,3,2,0,1,2,0,1,2,1,1,0,1,0,1,2,1,2,0,0,0,1,1,0,0,0,1,0,0,2,\n1,1,0,0,1,1,0,1,1,1,1,0,2,0,1,1,1,0,0,1,1,0,0,0,0,1,0,0,0,1,0,0,\n2,0,0,0,0,1,2,2,2,2,2,2,2,1,2,1,1,1,1,1,1,1,0,1,1,1,1,1,2,1,1,1,\n1,2,2,2,2,1,1,2,1,2,1,1,1,0,2,1,2,1,1,1,0,2,1,1,1,1,0,1,0,0,0,0,\n3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,1,0,\n1,1,0,1,0,1,1,1,1,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,2,2,3,2,0,0,0,0,1,0,0,0,0,0,0,1,1,0,2,0,0,0,0,0,0,0,0,1,0,1,2,\n1,1,1,1,1,1,0,0,2,2,2,2,2,0,1,1,0,1,1,1,1,1,0,0,1,0,0,0,1,1,0,1,\n2,3,1,2,1,0,1,1,0,2,2,2,0,0,1,0,0,1,1,1,1,0,0,0,0,0,0,0,1,0,1,2,\n1,1,1,1,2,1,1,1,1,1,1,1,1,0,1,1,0,1,0,1,0,1,0,0,1,0,0,0,0,1,0,0,\n2,2,2,2,2,0,0,2,0,0,2,0,0,0,0,0,0,1,0,1,0,0,0,0,0,0,0,0,2,0,2,2,\n1,1,1,1,1,0,0,1,2,1,1,0,1,0,1,0,0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,\n1,2,2,2,2,0,0,2,0,1,1,0,0,0,1,0,0,2,0,2,0,0,0,0,0,0,0,0,0,0,1,1,\n0,0,0,1,1,1,1,1,1,1,1,1,1,0,1,0,0,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,\n1,2,2,3,2,0,0,1,0,0,1,0,0,0,0,0,0,1,0,2,0,0,0,1,0,0,0,0,0,0,0,2,\n1,1,0,0,1,0,0,0,1,1,0,0,1,0,1,1,0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,\n2,1,2,2,2,1,2,1,2,2,1,1,2,1,1,1,0,1,1,1,1,2,0,1,0,1,1,1,1,0,1,1,\n1,1,2,1,1,1,1,1,1,0,0,1,2,1,1,1,1,1,1,0,0,1,1,1,0,0,0,0,0,0,0,0,\n1,0,0,1,3,1,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,2,2,2,1,0,0,1,0,2,0,0,0,0,0,1,1,1,0,1,0,0,0,0,0,0,0,0,2,0,0,1,\n0,2,0,1,0,0,1,1,2,0,1,0,1,0,1,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,\n1,2,2,2,2,0,1,1,0,2,1,0,1,1,1,0,0,1,0,2,0,1,0,0,0,0,0,0,0,0,0,1,\n0,1,0,0,1,0,0,0,1,1,0,0,1,0,0,1,0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,\n2,2,2,2,2,0,0,1,0,0,0,1,0,1,0,0,0,1,0,1,0,0,0,0,0,0,0,0,0,0,0,1,\n0,1,0,1,1,1,0,0,1,1,1,0,1,0,0,0,0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,\n2,0,1,0,0,1,2,1,1,1,1,1,1,2,2,1,0,0,1,0,1,0,0,0,0,1,1,1,1,0,0,0,\n1,1,2,1,1,1,1,0,0,0,1,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,2,1,2,1,0,0,1,0,0,0,0,0,0,0,0,1,1,0,1,0,0,0,0,0,0,0,0,0,0,0,1,\n0,0,0,0,0,0,0,0,1,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,0,0,1,2,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,0,0,0,\n0,1,1,0,1,1,1,0,0,1,0,0,1,0,1,0,0,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0,\n1,0,1,0,0,1,1,1,1,1,1,1,1,1,1,1,0,0,1,0,2,0,0,2,0,1,0,0,1,0,0,1,\n1,1,0,0,1,1,0,1,0,0,0,1,0,0,1,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,1,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,1,0,\n1,1,1,1,1,1,1,2,0,0,0,0,0,0,2,1,0,1,1,0,0,1,1,1,0,1,0,0,0,0,0,0,\n2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,0,0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,0,1,0,1,1,0,1,1,1,1,1,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n)\n\nLatin5BulgarianModel = {\n  'char_to_order_map': Latin5_BulgarianCharToOrderMap,\n  'precedence_matrix': BulgarianLangModel,\n  'typical_positive_ratio': 0.969392,\n  'keep_english_letter': False,\n  'charset_name': \"ISO-8859-5\",\n  'language': 'Bulgairan',\n}\n\nWin1251BulgarianModel = {\n  'char_to_order_map': win1251BulgarianCharToOrderMap,\n  'precedence_matrix': BulgarianLangModel,\n  'typical_positive_ratio': 0.969392,\n  'keep_english_letter': False,\n  'charset_name': \"windows-1251\",\n  'language': 'Bulgarian',\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/langcyrillicmodel.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n# KOI8-R language model\n# Character Mapping Table:\nKOI8R_char_to_order_map = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253,142,143,144,145,146,147,148,149,150,151,152, 74,153, 75,154,  # 40\n155,156,157,158,159,160,161,162,163,164,165,253,253,253,253,253,  # 50\n253, 71,172, 66,173, 65,174, 76,175, 64,176,177, 77, 72,178, 69,  # 60\n 67,179, 78, 73,180,181, 79,182,183,184,185,253,253,253,253,253,  # 70\n191,192,193,194,195,196,197,198,199,200,201,202,203,204,205,206,  # 80\n207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,  # 90\n223,224,225, 68,226,227,228,229,230,231,232,233,234,235,236,237,  # a0\n238,239,240,241,242,243,244,245,246,247,248,249,250,251,252,253,  # b0\n 27,  3, 21, 28, 13,  2, 39, 19, 26,  4, 23, 11,  8, 12,  5,  1,  # c0\n 15, 16,  9,  7,  6, 14, 24, 10, 17, 18, 20, 25, 30, 29, 22, 54,  # d0\n 59, 37, 44, 58, 41, 48, 53, 46, 55, 42, 60, 36, 49, 38, 31, 34,  # e0\n 35, 43, 45, 32, 40, 52, 56, 33, 61, 62, 51, 57, 47, 63, 50, 70,  # f0\n)\n\nwin1251_char_to_order_map = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253,142,143,144,145,146,147,148,149,150,151,152, 74,153, 75,154,  # 40\n155,156,157,158,159,160,161,162,163,164,165,253,253,253,253,253,  # 50\n253, 71,172, 66,173, 65,174, 76,175, 64,176,177, 77, 72,178, 69,  # 60\n 67,179, 78, 73,180,181, 79,182,183,184,185,253,253,253,253,253,  # 70\n191,192,193,194,195,196,197,198,199,200,201,202,203,204,205,206,\n207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,\n223,224,225,226,227,228,229,230,231,232,233,234,235,236,237,238,\n239,240,241,242,243,244,245,246, 68,247,248,249,250,251,252,253,\n 37, 44, 33, 46, 41, 48, 56, 51, 42, 60, 36, 49, 38, 31, 34, 35,\n 45, 32, 40, 52, 53, 55, 58, 50, 57, 63, 70, 62, 61, 47, 59, 43,\n  3, 21, 10, 19, 13,  2, 24, 20,  4, 23, 11,  8, 12,  5,  1, 15,\n  9,  7,  6, 14, 39, 26, 28, 22, 25, 29, 54, 18, 17, 30, 27, 16,\n)\n\nlatin5_char_to_order_map = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253,142,143,144,145,146,147,148,149,150,151,152, 74,153, 75,154,  # 40\n155,156,157,158,159,160,161,162,163,164,165,253,253,253,253,253,  # 50\n253, 71,172, 66,173, 65,174, 76,175, 64,176,177, 77, 72,178, 69,  # 60\n 67,179, 78, 73,180,181, 79,182,183,184,185,253,253,253,253,253,  # 70\n191,192,193,194,195,196,197,198,199,200,201,202,203,204,205,206,\n207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,\n223,224,225,226,227,228,229,230,231,232,233,234,235,236,237,238,\n 37, 44, 33, 46, 41, 48, 56, 51, 42, 60, 36, 49, 38, 31, 34, 35,\n 45, 32, 40, 52, 53, 55, 58, 50, 57, 63, 70, 62, 61, 47, 59, 43,\n  3, 21, 10, 19, 13,  2, 24, 20,  4, 23, 11,  8, 12,  5,  1, 15,\n  9,  7,  6, 14, 39, 26, 28, 22, 25, 29, 54, 18, 17, 30, 27, 16,\n239, 68,240,241,242,243,244,245,246,247,248,249,250,251,252,255,\n)\n\nmacCyrillic_char_to_order_map = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253,142,143,144,145,146,147,148,149,150,151,152, 74,153, 75,154,  # 40\n155,156,157,158,159,160,161,162,163,164,165,253,253,253,253,253,  # 50\n253, 71,172, 66,173, 65,174, 76,175, 64,176,177, 77, 72,178, 69,  # 60\n 67,179, 78, 73,180,181, 79,182,183,184,185,253,253,253,253,253,  # 70\n 37, 44, 33, 46, 41, 48, 56, 51, 42, 60, 36, 49, 38, 31, 34, 35,\n 45, 32, 40, 52, 53, 55, 58, 50, 57, 63, 70, 62, 61, 47, 59, 43,\n191,192,193,194,195,196,197,198,199,200,201,202,203,204,205,206,\n207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,\n223,224,225,226,227,228,229,230,231,232,233,234,235,236,237,238,\n239,240,241,242,243,244,245,246,247,248,249,250,251,252, 68, 16,\n  3, 21, 10, 19, 13,  2, 24, 20,  4, 23, 11,  8, 12,  5,  1, 15,\n  9,  7,  6, 14, 39, 26, 28, 22, 25, 29, 54, 18, 17, 30, 27,255,\n)\n\nIBM855_char_to_order_map = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253,142,143,144,145,146,147,148,149,150,151,152, 74,153, 75,154,  # 40\n155,156,157,158,159,160,161,162,163,164,165,253,253,253,253,253,  # 50\n253, 71,172, 66,173, 65,174, 76,175, 64,176,177, 77, 72,178, 69,  # 60\n 67,179, 78, 73,180,181, 79,182,183,184,185,253,253,253,253,253,  # 70\n191,192,193,194, 68,195,196,197,198,199,200,201,202,203,204,205,\n206,207,208,209,210,211,212,213,214,215,216,217, 27, 59, 54, 70,\n  3, 37, 21, 44, 28, 58, 13, 41,  2, 48, 39, 53, 19, 46,218,219,\n220,221,222,223,224, 26, 55,  4, 42,225,226,227,228, 23, 60,229,\n230,231,232,233,234,235, 11, 36,236,237,238,239,240,241,242,243,\n  8, 49, 12, 38,  5, 31,  1, 34, 15,244,245,246,247, 35, 16,248,\n 43,  9, 45,  7, 32,  6, 40, 14, 52, 24, 56, 10, 33, 17, 61,249,\n250, 18, 62, 20, 51, 25, 57, 30, 47, 29, 63, 22, 50,251,252,255,\n)\n\nIBM866_char_to_order_map = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253,142,143,144,145,146,147,148,149,150,151,152, 74,153, 75,154,  # 40\n155,156,157,158,159,160,161,162,163,164,165,253,253,253,253,253,  # 50\n253, 71,172, 66,173, 65,174, 76,175, 64,176,177, 77, 72,178, 69,  # 60\n 67,179, 78, 73,180,181, 79,182,183,184,185,253,253,253,253,253,  # 70\n 37, 44, 33, 46, 41, 48, 56, 51, 42, 60, 36, 49, 38, 31, 34, 35,\n 45, 32, 40, 52, 53, 55, 58, 50, 57, 63, 70, 62, 61, 47, 59, 43,\n  3, 21, 10, 19, 13,  2, 24, 20,  4, 23, 11,  8, 12,  5,  1, 15,\n191,192,193,194,195,196,197,198,199,200,201,202,203,204,205,206,\n207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,\n223,224,225,226,227,228,229,230,231,232,233,234,235,236,237,238,\n  9,  7,  6, 14, 39, 26, 28, 22, 25, 29, 54, 18, 17, 30, 27, 16,\n239, 68,240,241,242,243,244,245,246,247,248,249,250,251,252,255,\n)\n\n# Model Table:\n# total sequences: 100%\n# first 512 sequences: 97.6601%\n# first 1024 sequences: 2.3389%\n# rest  sequences:      0.1237%\n# negative sequences:   0.0009%\nRussianLangModel = (\n0,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,1,1,3,3,3,3,1,3,3,3,2,3,2,3,3,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,0,3,2,2,2,2,2,0,0,2,\n3,3,3,2,3,3,3,3,3,3,3,3,3,3,2,3,3,0,0,3,3,3,3,3,3,3,3,3,2,3,2,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,2,2,3,3,3,3,3,3,3,3,3,2,3,3,0,0,3,3,3,3,3,3,3,3,2,3,3,1,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,2,3,2,3,3,3,3,3,3,3,3,3,3,3,3,3,0,0,3,3,3,3,3,3,3,3,3,3,3,2,1,\n0,0,0,0,0,0,0,2,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,3,3,0,0,3,3,3,3,3,3,3,3,3,3,3,2,1,\n0,0,0,0,0,1,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,2,2,2,3,1,3,3,1,3,3,3,3,2,2,3,0,2,2,2,3,3,2,1,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,2,3,3,3,3,3,2,2,3,2,3,3,3,2,1,2,2,0,1,2,2,2,2,2,2,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,2,2,3,0,2,2,3,3,2,1,2,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,1,0,0,2,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,2,3,3,1,2,3,2,2,3,2,3,3,3,3,2,2,3,0,3,2,2,3,1,1,1,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,2,2,3,3,3,3,3,2,3,3,3,3,2,2,2,0,3,3,3,2,2,2,2,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,3,3,2,3,2,3,3,3,3,3,3,2,3,2,2,0,1,3,2,1,2,2,1,0,\n0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,3,3,3,2,1,1,3,0,1,1,1,1,2,1,1,0,2,2,2,1,2,0,1,0,\n0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,2,3,3,2,2,2,2,1,3,2,3,2,3,2,1,2,2,0,1,1,2,1,2,1,2,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,3,3,3,3,2,2,3,2,3,3,3,2,2,2,2,0,2,2,2,2,3,1,1,0,\n0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,\n3,2,3,2,2,3,3,3,3,3,3,3,3,3,1,3,2,0,0,3,3,3,3,2,3,3,3,3,2,3,2,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,3,3,3,3,3,2,2,3,3,0,2,1,0,3,2,3,2,3,0,0,1,2,0,0,1,0,1,2,1,1,0,\n0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,0,3,0,2,3,3,3,3,2,3,3,3,3,1,2,2,0,0,2,3,2,2,2,3,2,3,2,2,3,0,0,\n0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,2,3,0,2,3,2,3,0,1,2,3,3,2,0,2,3,0,0,2,3,2,2,0,1,3,1,3,2,2,1,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,1,3,0,2,3,3,3,3,3,3,3,3,2,1,3,2,0,0,2,2,3,3,3,2,3,3,0,2,2,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,2,2,3,3,2,2,2,3,3,0,0,1,1,1,1,1,2,0,0,1,1,1,1,0,1,0,\n0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,2,2,3,3,3,3,3,3,3,0,3,2,3,3,2,3,2,0,2,1,0,1,1,0,1,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,2,3,3,3,2,2,2,2,3,1,3,2,3,1,1,2,1,0,2,2,2,2,1,3,1,0,\n0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,\n2,2,3,3,3,3,3,1,2,2,1,3,1,0,3,0,0,3,0,0,0,1,1,0,1,2,1,0,0,0,0,0,\n0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,2,2,1,1,3,3,3,2,2,1,2,2,3,1,1,2,0,0,2,2,1,3,0,0,2,1,1,2,1,1,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,2,3,3,3,3,1,2,2,2,1,2,1,3,3,1,1,2,1,2,1,2,2,0,2,0,0,1,1,0,1,0,\n0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,3,3,3,3,3,2,1,3,2,2,3,2,0,3,2,0,3,0,1,0,1,1,0,0,1,1,1,1,0,1,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,2,3,3,3,2,2,2,3,3,1,2,1,2,1,0,1,0,1,1,0,1,0,0,2,1,1,1,0,1,0,\n0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,\n3,1,1,2,1,2,3,3,2,2,1,2,2,3,0,2,1,0,0,2,2,3,2,1,2,2,2,2,2,3,1,0,\n0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,1,1,0,1,1,2,2,1,1,3,0,0,1,3,1,1,1,0,0,0,1,0,1,1,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,1,3,3,3,2,0,0,0,2,1,0,1,0,2,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,0,1,0,0,2,3,2,2,2,1,2,2,2,1,2,1,0,0,1,1,1,0,2,0,1,1,1,0,0,1,1,\n1,0,0,0,0,0,1,2,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,\n2,3,3,3,3,0,0,0,0,1,0,0,0,0,3,0,1,2,1,0,0,0,0,0,0,0,1,1,0,0,1,1,\n1,0,1,0,1,2,0,0,1,1,2,1,0,1,1,1,1,0,1,1,1,1,0,1,0,0,1,0,0,1,1,0,\n2,2,3,2,2,2,3,1,2,2,2,2,2,2,2,2,1,1,1,1,1,1,1,0,1,0,1,1,1,0,2,1,\n1,1,1,1,1,1,1,1,2,1,1,1,1,1,1,1,1,1,1,0,1,0,1,1,0,1,1,1,0,1,1,0,\n3,3,3,2,2,2,2,3,2,2,1,1,2,2,2,2,1,1,3,1,2,1,2,0,0,1,1,0,1,0,2,1,\n1,1,1,1,1,2,1,0,1,1,1,1,0,1,0,0,1,1,0,0,1,0,1,0,0,1,0,0,0,1,1,0,\n2,0,0,1,0,3,2,2,2,2,1,2,1,2,1,2,0,0,0,2,1,2,2,1,1,2,2,0,1,1,0,2,\n1,1,1,1,1,0,1,1,1,2,1,1,1,2,1,0,1,2,1,1,1,1,0,1,1,1,0,0,1,0,0,1,\n1,3,2,2,2,1,1,1,2,3,0,0,0,0,2,0,2,2,1,0,0,0,0,0,0,1,0,0,0,0,1,1,\n1,0,1,1,0,1,0,1,1,0,1,1,0,2,0,0,1,1,0,0,1,0,0,0,0,0,0,0,0,1,1,0,\n2,3,2,3,2,1,2,2,2,2,1,0,0,0,2,0,0,1,1,0,0,0,0,0,0,0,1,1,0,0,2,1,\n1,1,2,1,0,2,0,0,1,0,1,0,0,1,0,0,1,1,0,1,1,0,0,0,0,0,1,0,0,0,0,0,\n3,0,0,1,0,2,2,2,3,2,2,2,2,2,2,2,0,0,0,2,1,2,1,1,1,2,2,0,0,0,1,2,\n1,1,1,1,1,0,1,2,1,1,1,1,1,1,1,0,1,1,1,1,1,1,0,1,1,1,1,1,1,0,0,1,\n2,3,2,3,3,2,0,1,1,1,0,0,1,0,2,0,1,1,3,1,0,0,0,0,0,0,0,1,0,0,2,1,\n1,1,1,1,1,1,1,0,1,0,1,1,1,1,0,1,1,1,0,0,1,1,0,1,0,0,0,0,0,0,1,0,\n2,3,3,3,3,1,2,2,2,2,0,1,1,0,2,1,1,1,2,1,0,1,1,0,0,1,0,1,0,0,2,0,\n0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,3,3,3,2,0,0,1,1,2,2,1,0,0,2,0,1,1,3,0,0,1,0,0,0,0,0,1,0,1,2,1,\n1,1,2,0,1,1,1,0,1,0,1,1,0,1,0,1,1,1,1,0,1,0,0,0,0,0,0,1,0,1,1,0,\n1,3,2,3,2,1,0,0,2,2,2,0,1,0,2,0,1,1,1,0,1,0,0,0,3,0,1,1,0,0,2,1,\n1,1,1,0,1,1,0,0,0,0,1,1,0,1,0,0,2,1,1,0,1,0,0,0,1,0,1,0,0,1,1,0,\n3,1,2,1,1,2,2,2,2,2,2,1,2,2,1,1,0,0,0,2,2,2,0,0,0,1,2,1,0,1,0,1,\n2,1,1,1,1,1,1,1,1,1,1,1,1,1,1,0,2,1,1,1,0,1,0,1,1,0,1,1,1,0,0,1,\n3,0,0,0,0,2,0,1,1,1,1,1,1,1,0,1,0,0,0,1,1,1,0,1,0,1,1,0,0,1,0,1,\n1,1,0,0,1,0,0,0,1,0,1,1,0,0,1,0,1,0,1,0,0,0,0,1,0,0,0,1,0,0,0,1,\n1,3,3,2,2,0,0,0,2,2,0,0,0,1,2,0,1,1,2,0,0,0,0,0,0,0,0,1,0,0,2,1,\n0,1,1,0,0,1,1,0,0,0,1,1,0,1,1,0,1,1,0,0,1,0,0,0,0,0,0,0,0,0,1,0,\n2,3,2,3,2,0,0,0,0,1,1,0,0,0,2,0,2,0,2,0,0,0,0,0,1,0,0,1,0,0,1,1,\n1,1,2,0,1,2,1,0,1,1,2,1,1,1,1,1,2,1,1,0,1,0,0,1,1,1,1,1,0,1,1,0,\n1,3,2,2,2,1,0,0,2,2,1,0,1,2,2,0,0,1,0,0,0,0,0,0,0,0,0,1,0,0,1,1,\n0,0,1,1,0,1,1,0,0,1,1,0,1,1,0,0,1,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,\n1,0,0,1,0,2,3,1,2,2,2,2,2,2,1,1,0,0,0,1,0,1,0,2,1,1,1,0,0,0,0,1,\n1,1,0,1,1,0,1,1,1,1,0,0,0,1,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,0,0,0,\n2,0,2,0,0,1,0,3,2,1,2,1,2,2,0,1,0,0,0,2,1,0,0,2,1,1,1,1,0,2,0,2,\n2,1,1,1,1,1,1,1,1,1,1,1,1,2,1,0,1,1,1,1,0,0,0,1,1,1,1,0,1,0,0,1,\n1,2,2,2,2,1,0,0,1,0,0,0,0,0,2,0,1,1,1,1,0,0,0,0,1,0,1,2,0,0,2,0,\n1,0,1,1,1,2,1,0,1,0,1,1,0,0,1,0,1,1,1,0,1,0,0,0,1,0,0,1,0,1,1,0,\n2,1,2,2,2,0,3,0,1,1,0,0,0,0,2,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n0,0,0,1,1,1,0,0,1,0,1,0,0,0,0,0,1,0,0,0,1,0,0,0,0,0,0,0,0,1,0,0,\n1,2,2,3,2,2,0,0,1,1,2,0,1,2,1,0,1,0,1,0,0,1,0,0,0,0,0,0,0,0,0,1,\n0,1,1,0,0,1,1,0,0,1,1,0,0,1,1,0,1,1,0,0,1,0,0,0,0,0,0,0,0,1,1,0,\n2,2,1,1,2,1,2,2,2,2,2,1,2,2,0,1,0,0,0,1,2,2,2,1,2,1,1,1,1,1,2,1,\n1,1,1,1,1,1,1,1,1,1,0,0,1,1,1,0,1,1,1,0,0,0,0,1,1,1,0,1,1,0,0,1,\n1,2,2,2,2,0,1,0,2,2,0,0,0,0,2,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,2,0,\n0,0,1,0,0,1,0,0,0,0,1,0,1,1,0,0,1,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,\n0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,2,2,2,2,0,0,0,2,2,2,0,1,0,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1,\n0,1,1,0,0,1,1,0,0,0,1,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,2,2,2,2,0,0,0,0,1,0,0,1,1,2,0,0,0,0,1,0,1,0,0,1,0,0,2,0,0,0,1,\n0,0,1,0,0,1,0,0,0,1,1,0,0,0,0,0,1,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,\n1,2,2,2,1,1,2,0,2,1,1,1,1,0,2,2,0,0,0,0,0,0,0,0,0,1,1,0,0,0,1,1,\n0,0,1,0,1,1,0,0,0,0,1,0,0,0,0,0,1,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,\n1,0,2,1,2,0,0,0,0,0,1,0,0,0,1,0,0,0,1,0,0,0,0,0,0,0,0,1,0,0,0,0,\n0,0,1,0,1,1,0,0,0,0,1,0,0,0,0,0,1,0,0,0,1,0,0,0,0,0,0,0,0,0,1,0,\n1,0,0,0,0,2,0,1,2,1,0,1,1,1,0,1,0,0,0,1,0,1,0,0,1,0,1,0,0,0,0,1,\n0,0,0,0,0,1,0,0,1,1,0,0,1,1,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,1,\n2,2,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n1,0,0,0,1,0,0,0,1,1,0,0,0,0,0,0,0,1,0,0,0,0,0,1,0,0,1,0,0,0,0,0,\n2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n1,1,1,0,1,0,1,0,0,1,1,1,1,0,0,0,1,0,0,0,0,1,0,0,0,1,0,1,0,0,0,0,\n1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n1,1,0,1,1,0,1,0,1,0,0,0,0,1,1,0,1,1,0,0,0,0,0,1,0,1,1,0,1,0,0,0,\n0,1,1,1,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,1,0,0,0,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,\n)\n\nKoi8rModel = {\n  'char_to_order_map': KOI8R_char_to_order_map,\n  'precedence_matrix': RussianLangModel,\n  'typical_positive_ratio': 0.976601,\n  'keep_english_letter': False,\n  'charset_name': \"KOI8-R\",\n  'language': 'Russian',\n}\n\nWin1251CyrillicModel = {\n  'char_to_order_map': win1251_char_to_order_map,\n  'precedence_matrix': RussianLangModel,\n  'typical_positive_ratio': 0.976601,\n  'keep_english_letter': False,\n  'charset_name': \"windows-1251\",\n  'language': 'Russian',\n}\n\nLatin5CyrillicModel = {\n  'char_to_order_map': latin5_char_to_order_map,\n  'precedence_matrix': RussianLangModel,\n  'typical_positive_ratio': 0.976601,\n  'keep_english_letter': False,\n  'charset_name': \"ISO-8859-5\",\n  'language': 'Russian',\n}\n\nMacCyrillicModel = {\n  'char_to_order_map': macCyrillic_char_to_order_map,\n  'precedence_matrix': RussianLangModel,\n  'typical_positive_ratio': 0.976601,\n  'keep_english_letter': False,\n  'charset_name': \"MacCyrillic\",\n  'language': 'Russian',\n}\n\nIbm866Model = {\n  'char_to_order_map': IBM866_char_to_order_map,\n  'precedence_matrix': RussianLangModel,\n  'typical_positive_ratio': 0.976601,\n  'keep_english_letter': False,\n  'charset_name': \"IBM866\",\n  'language': 'Russian',\n}\n\nIbm855Model = {\n  'char_to_order_map': IBM855_char_to_order_map,\n  'precedence_matrix': RussianLangModel,\n  'typical_positive_ratio': 0.976601,\n  'keep_english_letter': False,\n  'charset_name': \"IBM855\",\n  'language': 'Russian',\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/langgreekmodel.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n# 255: Control characters that usually does not exist in any text\n# 254: Carriage/Return\n# 253: symbol (punctuation) that does not belong to word\n# 252: 0 - 9\n\n# Character Mapping Table:\nLatin7_char_to_order_map = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253, 82,100,104, 94, 98,101,116,102,111,187,117, 92, 88,113, 85,  # 40\n 79,118,105, 83, 67,114,119, 95, 99,109,188,253,253,253,253,253,  # 50\n253, 72, 70, 80, 81, 60, 96, 93, 89, 68,120, 97, 77, 86, 69, 55,  # 60\n 78,115, 65, 66, 58, 76,106,103, 87,107,112,253,253,253,253,253,  # 70\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 80\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 90\n253,233, 90,253,253,253,253,253,253,253,253,253,253, 74,253,253,  # a0\n253,253,253,253,247,248, 61, 36, 46, 71, 73,253, 54,253,108,123,  # b0\n110, 31, 51, 43, 41, 34, 91, 40, 52, 47, 44, 53, 38, 49, 59, 39,  # c0\n 35, 48,250, 37, 33, 45, 56, 50, 84, 57,120,121, 17, 18, 22, 15,  # d0\n124,  1, 29, 20, 21,  3, 32, 13, 25,  5, 11, 16, 10,  6, 30,  4,  # e0\n  9,  8, 14,  7,  2, 12, 28, 23, 42, 24, 64, 75, 19, 26, 27,253,  # f0\n)\n\nwin1253_char_to_order_map = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253, 82,100,104, 94, 98,101,116,102,111,187,117, 92, 88,113, 85,  # 40\n 79,118,105, 83, 67,114,119, 95, 99,109,188,253,253,253,253,253,  # 50\n253, 72, 70, 80, 81, 60, 96, 93, 89, 68,120, 97, 77, 86, 69, 55,  # 60\n 78,115, 65, 66, 58, 76,106,103, 87,107,112,253,253,253,253,253,  # 70\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 80\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 90\n253,233, 61,253,253,253,253,253,253,253,253,253,253, 74,253,253,  # a0\n253,253,253,253,247,253,253, 36, 46, 71, 73,253, 54,253,108,123,  # b0\n110, 31, 51, 43, 41, 34, 91, 40, 52, 47, 44, 53, 38, 49, 59, 39,  # c0\n 35, 48,250, 37, 33, 45, 56, 50, 84, 57,120,121, 17, 18, 22, 15,  # d0\n124,  1, 29, 20, 21,  3, 32, 13, 25,  5, 11, 16, 10,  6, 30,  4,  # e0\n  9,  8, 14,  7,  2, 12, 28, 23, 42, 24, 64, 75, 19, 26, 27,253,  # f0\n)\n\n# Model Table:\n# total sequences: 100%\n# first 512 sequences: 98.2851%\n# first 1024 sequences:1.7001%\n# rest  sequences:     0.0359%\n# negative sequences:  0.0148%\nGreekLangModel = (\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,3,2,2,3,3,3,3,3,3,3,3,1,3,3,3,0,2,2,3,3,0,3,0,3,2,0,3,3,3,0,\n3,0,0,0,2,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,3,3,3,0,3,3,0,3,2,3,3,0,3,2,3,3,3,0,0,3,0,3,0,3,3,2,0,0,0,\n2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,\n0,2,3,2,2,3,3,3,3,3,3,3,3,0,3,3,3,3,0,2,3,3,0,3,3,3,3,2,3,3,3,0,\n2,0,0,0,2,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,2,3,3,2,3,3,3,3,3,3,3,3,3,3,3,3,0,2,1,3,3,3,3,2,3,3,2,3,3,2,0,\n0,0,0,0,2,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,3,3,0,3,3,3,3,3,3,0,3,3,0,3,3,3,3,3,3,3,3,3,3,0,3,2,3,3,0,\n2,0,1,0,2,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,\n0,3,3,3,3,3,2,3,0,0,0,0,3,3,0,3,1,3,3,3,0,3,3,0,3,3,3,3,0,0,0,0,\n2,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,3,3,3,0,3,0,3,3,3,3,3,0,3,2,2,2,3,0,2,3,3,3,3,3,2,3,3,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,3,3,3,3,2,2,2,3,3,3,3,0,3,1,3,3,3,3,2,3,3,3,3,3,3,3,2,2,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,3,3,3,2,0,3,0,0,0,3,3,2,3,3,3,3,3,0,0,3,2,3,0,2,3,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,0,3,3,3,3,0,0,3,3,0,2,3,0,3,0,3,3,3,0,0,3,0,3,0,2,2,3,3,0,0,\n0,0,1,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,3,3,3,2,0,3,2,3,3,3,3,0,3,3,3,3,3,0,3,3,2,3,2,3,3,2,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,2,3,2,3,3,3,3,3,3,0,2,3,2,3,2,2,2,3,2,3,3,2,3,0,2,2,2,3,0,\n2,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,3,0,0,0,3,3,3,2,3,3,0,0,3,0,3,0,0,0,3,2,0,3,0,3,0,0,2,0,2,0,\n0,0,0,0,2,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,3,3,0,3,3,3,3,3,3,0,3,3,0,3,0,0,0,3,3,0,3,3,3,0,0,1,2,3,0,\n3,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,3,3,3,2,0,0,3,2,2,3,3,0,3,3,3,3,3,2,1,3,0,3,2,3,3,2,1,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,3,3,0,2,3,3,3,3,3,3,0,0,3,0,3,0,0,0,3,3,0,3,2,3,0,0,3,3,3,0,\n3,0,0,0,2,0,0,0,0,0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,3,3,0,3,3,3,3,3,3,0,0,3,0,3,0,0,0,3,2,0,3,2,3,0,0,3,2,3,0,\n2,0,0,0,0,0,0,0,0,0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,3,1,2,2,3,3,3,3,3,3,0,2,3,0,3,0,0,0,3,3,0,3,0,2,0,0,2,3,1,0,\n2,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,0,3,3,3,3,0,3,0,3,3,2,3,0,3,3,3,3,3,3,0,3,3,3,0,2,3,0,0,3,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,0,3,3,3,0,0,3,0,0,0,3,3,0,3,0,2,3,3,0,0,3,0,3,0,3,3,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,3,0,0,0,3,3,3,3,3,3,0,0,3,0,2,0,0,0,3,3,0,3,0,3,0,0,2,0,2,0,\n0,0,0,0,1,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,3,3,3,3,0,3,0,2,0,3,2,0,3,2,3,2,3,0,0,3,2,3,2,3,3,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,3,0,0,2,3,3,3,3,3,0,0,0,3,0,2,1,0,0,3,2,2,2,0,3,0,0,2,2,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,0,3,3,3,2,0,3,0,3,0,3,3,0,2,1,2,3,3,0,0,3,0,3,0,3,3,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,2,3,3,3,0,3,3,3,3,3,3,0,2,3,0,3,0,0,0,2,1,0,2,2,3,0,0,2,2,2,0,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,3,0,0,2,3,3,3,2,3,0,0,1,3,0,2,0,0,0,0,3,0,1,0,2,0,0,1,1,1,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,3,3,3,1,0,3,0,0,0,3,2,0,3,2,3,3,3,0,0,3,0,3,2,2,2,1,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,0,3,3,3,0,0,3,0,0,0,0,2,0,2,3,3,2,2,2,2,3,0,2,0,2,2,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,3,3,3,2,0,0,0,0,0,0,2,3,0,2,0,2,3,2,0,0,3,0,3,0,3,1,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,3,2,3,3,2,2,3,0,2,0,3,0,0,0,2,0,0,0,0,1,2,0,2,0,2,0,\n0,2,0,2,0,2,2,0,0,1,0,2,2,2,0,2,2,2,0,2,2,2,0,0,2,0,0,1,0,0,0,0,\n0,2,0,3,3,2,0,0,0,0,0,0,1,3,0,2,0,2,2,2,0,0,2,0,3,0,0,2,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,0,2,3,2,0,2,2,0,2,0,2,2,0,2,0,2,2,2,0,0,0,0,0,0,2,3,0,0,0,2,\n0,1,2,0,0,0,0,2,2,0,0,0,2,1,0,2,2,0,0,0,0,0,0,1,0,2,0,0,0,0,0,0,\n0,0,2,1,0,2,3,2,2,3,2,3,2,0,0,3,3,3,0,0,3,2,0,0,0,1,1,0,2,0,2,2,\n0,2,0,2,0,2,2,0,0,2,0,2,2,2,0,2,2,2,2,0,0,2,0,0,0,2,0,1,0,0,0,0,\n0,3,0,3,3,2,2,0,3,0,0,0,2,2,0,2,2,2,1,2,0,0,1,2,2,0,0,3,0,0,0,2,\n0,1,2,0,0,0,1,2,0,0,0,0,0,0,0,2,2,0,1,0,0,2,0,0,0,2,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,2,3,3,2,2,0,0,0,2,0,2,3,3,0,2,0,0,0,0,0,0,2,2,2,0,2,2,0,2,0,2,\n0,2,2,0,0,2,2,2,2,1,0,0,2,2,0,2,0,0,2,0,0,0,0,0,0,2,0,0,0,0,0,0,\n0,2,0,3,2,3,0,0,0,3,0,0,2,2,0,2,0,2,2,2,0,0,2,0,0,0,0,0,0,0,0,2,\n0,0,2,2,0,0,2,2,2,0,0,0,0,0,0,2,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,2,0,0,3,2,0,2,2,2,2,2,0,0,0,2,0,0,0,0,2,0,1,0,0,2,0,1,0,0,0,\n0,2,2,2,0,2,2,0,1,2,0,2,2,2,0,2,2,2,2,1,2,2,0,0,2,0,0,0,0,0,0,0,\n0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,\n0,2,0,2,0,2,2,0,0,0,0,1,2,1,0,0,2,2,0,0,2,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,3,2,3,0,0,2,0,0,0,2,2,0,2,0,0,0,1,0,0,2,0,2,0,2,2,0,0,0,0,\n0,0,2,0,0,0,0,2,2,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,\n0,2,2,3,2,2,0,0,0,0,0,0,1,3,0,2,0,2,2,0,0,0,1,0,2,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,2,0,2,0,3,2,0,2,0,0,0,0,0,0,2,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n0,0,2,0,0,0,0,1,1,0,0,2,1,2,0,2,2,0,1,0,0,1,0,0,0,2,0,0,0,0,0,0,\n0,3,0,2,2,2,0,0,2,0,0,0,2,0,0,0,2,3,0,2,0,0,0,0,0,0,2,2,0,0,0,2,\n0,1,2,0,0,0,1,2,2,1,0,0,0,2,0,0,2,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,3,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,2,1,2,0,2,2,0,2,0,0,2,0,0,0,0,1,2,1,0,2,1,0,0,0,0,0,0,0,0,0,0,\n0,0,2,0,0,0,3,1,2,2,0,2,0,0,0,0,2,0,0,0,2,0,0,3,0,0,0,0,2,2,2,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,2,1,0,2,0,1,2,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,1,0,0,0,0,0,0,2,\n0,2,2,0,0,2,2,2,2,2,0,1,2,0,0,0,2,2,0,1,0,2,0,0,2,2,0,0,0,0,0,0,\n0,0,0,0,1,0,0,0,0,0,0,0,3,0,0,2,0,0,0,0,0,0,0,0,2,0,2,0,0,0,0,2,\n0,1,2,0,0,0,0,2,2,1,0,1,0,1,0,2,2,2,1,0,0,0,0,0,0,1,0,0,0,0,0,0,\n0,2,0,1,2,0,0,0,0,0,0,0,0,0,0,2,0,0,2,2,0,0,0,0,1,0,0,0,0,0,0,2,\n0,2,2,0,0,0,0,2,2,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,2,0,0,2,0,0,0,\n0,2,2,2,2,0,0,0,3,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,2,0,0,0,0,0,0,1,\n0,0,2,0,0,0,0,1,2,0,0,0,0,0,0,2,2,1,1,0,0,0,0,0,0,1,0,0,0,0,0,0,\n0,2,0,2,2,2,0,0,2,0,0,0,0,0,0,0,2,2,2,0,0,0,2,0,0,0,0,0,0,0,0,2,\n0,0,1,0,0,0,0,2,1,0,0,0,0,0,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,\n0,3,0,2,0,0,0,0,0,0,0,0,2,0,0,0,0,0,2,0,0,0,0,0,0,0,2,0,0,0,0,2,\n0,0,2,0,0,0,0,2,2,0,0,0,0,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,2,0,2,2,1,0,0,0,0,0,0,2,0,0,2,0,2,2,2,0,0,0,0,0,0,2,0,0,0,0,2,\n0,0,2,0,0,2,0,2,2,0,0,0,0,2,0,2,0,0,0,0,0,2,0,0,0,2,0,0,0,0,0,0,\n0,0,3,0,0,0,2,2,0,2,2,0,0,0,0,0,2,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,2,0,0,0,0,0,\n0,2,2,2,2,2,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1,0,0,0,1,\n0,0,0,0,0,0,0,2,1,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,2,2,0,0,0,0,0,2,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,\n0,2,0,0,0,2,0,0,0,0,0,1,0,0,0,0,2,2,0,0,0,1,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,1,0,2,0,0,0,\n0,2,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,1,0,0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,1,0,0,2,0,2,0,0,0,\n0,0,0,0,0,0,0,0,2,1,0,0,0,0,0,0,2,0,0,0,1,2,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n)\n\nLatin7GreekModel = {\n  'char_to_order_map': Latin7_char_to_order_map,\n  'precedence_matrix': GreekLangModel,\n  'typical_positive_ratio': 0.982851,\n  'keep_english_letter': False,\n  'charset_name': \"ISO-8859-7\",\n  'language': 'Greek',\n}\n\nWin1253GreekModel = {\n  'char_to_order_map': win1253_char_to_order_map,\n  'precedence_matrix': GreekLangModel,\n  'typical_positive_ratio': 0.982851,\n  'keep_english_letter': False,\n  'charset_name': \"windows-1253\",\n  'language': 'Greek',\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/langhebrewmodel.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Universal charset detector code.\n#\n# The Initial Developer of the Original Code is\n#          Simon Montagu\n# Portions created by the Initial Developer are Copyright (C) 2005\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#   Shy Shalom - original C code\n#   Shoshannah Forbes - original C code (?)\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n# 255: Control characters that usually does not exist in any text\n# 254: Carriage/Return\n# 253: symbol (punctuation) that does not belong to word\n# 252: 0 - 9\n\n# Windows-1255 language model\n# Character Mapping Table:\nWIN1255_CHAR_TO_ORDER_MAP = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253, 69, 91, 79, 80, 92, 89, 97, 90, 68,111,112, 82, 73, 95, 85,  # 40\n 78,121, 86, 71, 67,102,107, 84,114,103,115,253,253,253,253,253,  # 50\n253, 50, 74, 60, 61, 42, 76, 70, 64, 53,105, 93, 56, 65, 54, 49,  # 60\n 66,110, 51, 43, 44, 63, 81, 77, 98, 75,108,253,253,253,253,253,  # 70\n124,202,203,204,205, 40, 58,206,207,208,209,210,211,212,213,214,\n215, 83, 52, 47, 46, 72, 32, 94,216,113,217,109,218,219,220,221,\n 34,116,222,118,100,223,224,117,119,104,125,225,226, 87, 99,227,\n106,122,123,228, 55,229,230,101,231,232,120,233, 48, 39, 57,234,\n 30, 59, 41, 88, 33, 37, 36, 31, 29, 35,235, 62, 28,236,126,237,\n238, 38, 45,239,240,241,242,243,127,244,245,246,247,248,249,250,\n  9,  8, 20, 16,  3,  2, 24, 14, 22,  1, 25, 15,  4, 11,  6, 23,\n 12, 19, 13, 26, 18, 27, 21, 17,  7, 10,  5,251,252,128, 96,253,\n)\n\n# Model Table:\n# total sequences: 100%\n# first 512 sequences: 98.4004%\n# first 1024 sequences: 1.5981%\n# rest  sequences:      0.087%\n# negative sequences:   0.0015%\nHEBREW_LANG_MODEL = (\n0,3,3,3,3,3,3,3,3,3,3,2,3,3,3,3,3,3,3,3,3,3,3,2,3,2,1,2,0,1,0,0,\n3,0,3,1,0,0,1,3,2,0,1,1,2,0,2,2,2,1,1,1,1,2,1,1,1,2,0,0,2,2,0,1,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,2,2,2,\n1,2,1,2,1,2,0,0,2,0,0,0,0,0,1,0,1,0,0,0,0,0,0,1,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,2,2,\n1,2,1,3,1,1,0,0,2,0,0,0,1,0,1,0,1,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,1,0,1,2,2,1,3,\n1,2,1,1,2,2,0,0,2,2,0,0,0,0,1,0,1,0,0,0,1,0,0,0,0,0,0,1,0,1,1,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,3,3,2,2,2,2,3,2,\n1,2,1,2,2,2,0,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,3,3,2,3,2,2,3,2,2,2,1,2,2,2,2,\n1,2,1,1,2,2,0,1,2,0,0,0,0,0,0,0,1,0,0,0,1,0,0,0,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,0,2,2,2,2,2,\n0,2,0,2,2,2,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,3,0,2,2,2,\n0,2,1,2,2,2,0,0,2,1,0,0,0,0,1,0,1,0,0,0,0,0,0,2,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,3,3,3,3,3,2,3,3,3,3,3,3,3,3,3,3,3,3,3,2,1,2,3,2,2,2,\n1,2,1,2,2,2,0,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,1,0,0,0,0,0,1,1,0,\n3,3,3,3,3,3,3,3,3,2,3,3,3,2,3,3,3,3,3,3,3,3,3,3,3,3,3,1,0,2,0,2,\n0,2,1,2,2,2,0,0,1,2,0,0,0,0,1,0,1,0,0,0,0,0,0,1,0,0,0,2,0,0,1,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,3,2,3,2,2,3,2,1,2,1,1,1,\n0,1,1,1,1,1,3,0,1,0,0,0,0,2,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,\n3,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,0,1,1,0,1,1,0,0,1,0,0,1,0,0,0,0,\n0,0,1,0,0,0,0,0,2,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,2,2,2,2,2,2,\n0,2,0,1,2,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,3,3,3,2,3,3,3,2,1,2,3,3,2,3,3,3,3,2,3,2,1,2,0,2,1,2,\n0,2,0,2,2,2,0,0,1,2,0,0,0,0,1,0,1,0,0,0,0,0,0,0,0,0,0,1,0,0,1,0,\n3,3,3,3,3,3,3,3,3,2,3,3,3,1,2,2,3,3,2,3,2,3,2,2,3,1,2,2,0,2,2,2,\n0,2,1,2,2,2,0,0,1,2,0,0,0,0,1,0,0,0,0,0,1,0,0,1,0,0,0,1,0,0,1,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,2,3,3,3,2,3,3,2,2,2,3,3,3,3,1,3,2,2,2,\n0,2,0,1,2,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,2,3,3,3,2,3,2,2,2,1,2,2,0,2,2,2,2,\n0,2,0,2,2,2,0,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,3,3,3,3,3,2,3,3,3,1,3,2,3,3,2,3,3,2,2,1,2,2,2,2,2,2,\n0,2,1,2,1,2,0,0,1,0,0,0,0,0,1,0,0,0,0,0,1,0,0,1,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,2,3,2,3,3,2,3,3,3,3,2,3,2,3,3,3,3,3,2,2,2,2,2,2,2,1,\n0,2,0,1,2,1,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,3,3,3,2,1,2,3,3,3,3,3,3,3,2,3,2,3,2,1,2,3,0,2,1,2,2,\n0,2,1,1,2,1,0,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,2,0,\n3,3,3,3,3,3,3,3,3,2,3,3,3,3,2,1,3,1,2,2,2,1,2,3,3,1,2,1,2,2,2,2,\n0,1,1,1,1,1,0,0,0,0,0,0,0,0,1,0,0,0,0,0,1,0,0,2,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,3,3,0,2,3,3,3,1,3,3,3,1,2,2,2,2,1,1,2,2,2,2,2,2,\n0,2,0,1,1,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,2,3,3,3,2,2,3,3,3,2,1,2,3,2,3,2,2,2,2,1,2,1,1,1,2,2,\n0,2,1,1,1,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,\n3,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,0,1,0,0,0,1,0,0,0,0,0,\n1,0,1,0,0,0,0,0,2,0,0,0,0,0,1,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,2,3,3,2,3,1,2,2,2,2,3,2,3,1,1,2,2,1,2,2,1,1,0,2,2,2,2,\n0,1,0,1,2,2,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,1,0,\n3,0,0,1,1,0,1,0,0,1,1,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,2,0,\n0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,0,1,0,1,0,1,1,0,1,1,0,0,0,1,1,0,1,1,1,0,0,0,0,0,0,1,0,0,0,0,0,\n0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,0,0,0,1,1,0,1,0,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,\n3,2,2,1,2,2,2,2,2,2,2,1,2,2,1,2,2,1,1,1,1,1,1,1,1,2,1,1,0,3,3,3,\n0,3,0,2,2,2,2,0,0,1,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,\n2,2,2,3,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,1,2,2,1,2,2,2,1,1,1,2,0,1,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,2,2,2,2,2,2,2,2,2,2,1,2,2,2,2,2,2,2,2,2,2,2,0,2,2,0,0,0,0,0,0,\n0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,3,1,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,1,2,1,0,2,1,0,\n0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,1,1,1,1,1,1,1,1,1,1,0,0,1,1,1,1,0,1,1,1,1,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,\n0,3,1,1,2,2,2,2,2,1,2,2,2,1,1,2,2,2,2,2,2,2,1,2,2,1,0,1,1,1,1,0,\n0,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,2,1,1,1,1,2,1,1,2,1,0,1,1,1,1,1,1,1,1,1,1,1,0,1,0,0,0,0,0,0,0,\n0,0,2,0,0,0,0,0,0,0,0,1,1,0,0,0,0,1,1,0,0,1,1,0,0,0,0,0,0,1,0,0,\n2,1,1,2,2,2,2,2,2,2,2,2,2,2,1,2,2,2,2,2,1,2,1,2,1,1,1,1,0,0,0,0,\n0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,2,1,2,2,2,2,2,2,2,2,2,2,1,2,1,2,1,1,2,1,1,1,2,1,2,1,2,0,1,0,1,\n0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,3,1,2,2,2,1,2,2,2,2,2,2,2,2,1,2,1,1,1,1,1,1,2,1,2,1,1,0,1,0,1,\n0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,1,2,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,\n0,2,0,1,2,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,\n3,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,0,1,0,0,0,1,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,1,1,1,1,1,1,1,0,1,1,0,1,0,0,1,0,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,2,0,1,1,1,0,1,0,0,0,1,1,0,1,1,0,0,0,0,0,1,1,0,0,\n0,1,1,1,2,1,2,2,2,0,2,0,2,0,1,1,2,1,1,1,1,2,1,0,1,1,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,0,1,0,0,0,0,0,1,0,1,2,2,0,1,0,0,1,1,2,2,1,2,0,2,0,0,0,1,2,0,1,\n2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,2,0,2,1,2,0,2,0,0,1,1,1,1,1,1,0,1,0,0,0,1,0,0,1,\n2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,1,0,0,0,0,0,1,0,2,1,1,0,1,0,0,1,1,1,2,2,0,0,1,0,0,0,1,0,0,1,\n1,1,2,1,0,1,1,1,0,1,0,1,1,1,1,0,0,0,1,0,1,0,0,0,0,0,0,0,0,2,2,1,\n0,2,0,1,2,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,1,0,0,1,0,1,1,1,1,0,0,0,0,0,1,0,0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,1,1,1,1,1,1,1,1,2,1,0,1,1,1,1,1,1,1,1,1,1,1,0,1,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,1,1,1,0,0,0,0,1,1,1,0,1,1,0,1,0,0,0,1,1,0,1,\n2,0,1,0,1,0,1,0,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,1,0,1,1,1,0,1,0,0,1,1,2,1,1,2,0,1,0,0,0,1,1,0,1,\n1,0,0,1,0,0,1,0,0,0,1,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,1,0,1,1,2,0,1,0,0,0,0,2,1,1,2,0,2,0,0,0,1,1,0,1,\n1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,1,0,2,1,1,0,1,0,0,2,2,1,2,1,1,0,1,0,0,0,1,1,0,1,\n2,0,1,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,1,2,2,0,0,0,0,0,1,1,0,1,0,0,1,0,0,0,0,1,0,1,\n1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,1,2,2,0,0,0,0,2,1,1,1,0,2,1,1,0,0,0,2,1,0,1,\n1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,1,0,1,1,2,0,1,0,0,1,1,0,2,1,1,0,1,0,0,0,1,1,0,1,\n2,2,1,1,1,0,1,1,0,1,1,0,1,0,0,0,0,0,0,1,0,0,0,1,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,1,0,2,1,1,0,1,0,0,1,1,0,1,2,1,0,2,0,0,0,1,1,0,1,\n2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,\n0,1,0,0,2,0,2,1,1,0,1,0,1,0,0,1,0,0,0,0,1,0,0,0,1,0,0,0,0,0,1,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,0,0,1,0,0,1,0,0,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,1,0,1,1,2,0,1,0,0,1,1,1,0,1,0,0,1,0,0,0,1,0,0,1,\n1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,0,0,0,0,0,0,0,1,0,1,1,0,0,1,0,0,2,1,1,1,1,1,0,1,0,0,0,0,1,0,1,\n0,1,1,1,2,1,1,1,1,0,1,1,1,1,1,1,1,1,1,1,1,1,0,1,1,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,1,2,1,0,0,0,0,0,1,1,1,1,1,0,1,0,0,0,1,1,0,0,\n)\n\nWin1255HebrewModel = {\n  'char_to_order_map': WIN1255_CHAR_TO_ORDER_MAP,\n  'precedence_matrix': HEBREW_LANG_MODEL,\n  'typical_positive_ratio': 0.984004,\n  'keep_english_letter': False,\n  'charset_name': \"windows-1255\",\n  'language': 'Hebrew',\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/langhungarianmodel.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n# 255: Control characters that usually does not exist in any text\n# 254: Carriage/Return\n# 253: symbol (punctuation) that does not belong to word\n# 252: 0 - 9\n\n# Character Mapping Table:\nLatin2_HungarianCharToOrderMap = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253, 28, 40, 54, 45, 32, 50, 49, 38, 39, 53, 36, 41, 34, 35, 47,\n 46, 71, 43, 33, 37, 57, 48, 64, 68, 55, 52,253,253,253,253,253,\n253,  2, 18, 26, 17,  1, 27, 12, 20,  9, 22,  7,  6, 13,  4,  8,\n 23, 67, 10,  5,  3, 21, 19, 65, 62, 16, 11,253,253,253,253,253,\n159,160,161,162,163,164,165,166,167,168,169,170,171,172,173,174,\n175,176,177,178,179,180,181,182,183,184,185,186,187,188,189,190,\n191,192,193,194,195,196,197, 75,198,199,200,201,202,203,204,205,\n 79,206,207,208,209,210,211,212,213,214,215,216,217,218,219,220,\n221, 51, 81,222, 78,223,224,225,226, 44,227,228,229, 61,230,231,\n232,233,234, 58,235, 66, 59,236,237,238, 60, 69, 63,239,240,241,\n 82, 14, 74,242, 70, 80,243, 72,244, 15, 83, 77, 84, 30, 76, 85,\n245,246,247, 25, 73, 42, 24,248,249,250, 31, 56, 29,251,252,253,\n)\n\nwin1250HungarianCharToOrderMap = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253, 28, 40, 54, 45, 32, 50, 49, 38, 39, 53, 36, 41, 34, 35, 47,\n 46, 72, 43, 33, 37, 57, 48, 64, 68, 55, 52,253,253,253,253,253,\n253,  2, 18, 26, 17,  1, 27, 12, 20,  9, 22,  7,  6, 13,  4,  8,\n 23, 67, 10,  5,  3, 21, 19, 65, 62, 16, 11,253,253,253,253,253,\n161,162,163,164,165,166,167,168,169,170,171,172,173,174,175,176,\n177,178,179,180, 78,181, 69,182,183,184,185,186,187,188,189,190,\n191,192,193,194,195,196,197, 76,198,199,200,201,202,203,204,205,\n 81,206,207,208,209,210,211,212,213,214,215,216,217,218,219,220,\n221, 51, 83,222, 80,223,224,225,226, 44,227,228,229, 61,230,231,\n232,233,234, 58,235, 66, 59,236,237,238, 60, 70, 63,239,240,241,\n 84, 14, 75,242, 71, 82,243, 73,244, 15, 85, 79, 86, 30, 77, 87,\n245,246,247, 25, 74, 42, 24,248,249,250, 31, 56, 29,251,252,253,\n)\n\n# Model Table:\n# total sequences: 100%\n# first 512 sequences: 94.7368%\n# first 1024 sequences:5.2623%\n# rest  sequences:     0.8894%\n# negative sequences:  0.0009%\nHungarianLangModel = (\n0,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,1,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,\n3,3,3,3,3,3,3,3,3,3,2,3,3,3,3,3,3,3,3,2,2,3,3,1,1,2,2,2,2,2,1,2,\n3,2,2,3,3,3,3,3,2,3,3,3,3,3,3,1,2,3,3,3,3,2,3,3,1,1,3,3,0,1,1,1,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,\n3,2,1,3,3,3,3,3,2,3,3,3,3,3,1,1,2,3,3,3,3,3,3,3,1,1,3,2,0,1,1,1,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,3,3,3,3,3,1,1,2,3,3,3,1,3,3,3,3,3,1,3,3,2,2,0,3,2,3,\n0,0,0,0,0,0,0,0,0,0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,\n3,3,3,3,3,3,2,3,3,3,2,3,3,2,3,3,3,3,3,2,3,3,2,2,3,2,3,2,0,3,2,2,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,1,0,\n3,3,3,3,3,3,2,3,3,3,3,3,2,3,3,3,1,2,3,2,2,3,1,2,3,3,2,2,0,3,3,3,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,3,3,2,2,3,3,3,3,3,3,2,3,3,3,3,2,3,3,3,3,0,2,3,2,\n0,0,0,1,1,0,0,0,0,0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,3,3,3,1,1,1,3,3,2,1,3,2,2,3,2,1,3,2,2,1,0,3,3,1,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,\n3,2,2,3,3,3,3,3,1,2,3,3,3,3,1,2,1,3,3,3,3,2,2,3,1,1,3,2,0,1,1,1,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,\n3,3,3,3,3,3,3,3,2,2,3,3,3,3,3,2,1,3,3,3,3,3,2,2,1,3,3,3,0,1,1,2,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,1,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,2,3,3,3,2,3,3,2,3,3,3,2,0,3,2,3,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,1,0,\n3,3,3,3,3,3,2,3,3,3,2,3,2,3,3,3,1,3,2,2,2,3,1,1,3,3,1,1,0,3,3,2,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,2,3,3,3,2,3,2,3,3,3,2,3,3,3,3,3,1,2,3,2,2,0,2,2,2,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,\n3,3,3,2,2,2,3,1,3,3,2,2,1,3,3,3,1,1,3,1,2,3,2,3,2,2,2,1,0,2,2,2,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,\n3,1,1,3,3,3,3,3,1,2,3,3,3,3,1,2,1,3,3,3,2,2,3,2,1,0,3,2,0,1,1,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,1,1,3,3,3,3,3,1,2,3,3,3,3,1,1,0,3,3,3,3,0,2,3,0,0,2,1,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,2,2,3,3,2,2,2,2,3,3,0,1,2,3,2,3,2,2,3,2,1,2,0,2,2,2,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,\n3,3,3,3,3,3,1,2,3,3,3,2,1,2,3,3,2,2,2,3,2,3,3,1,3,3,1,1,0,2,3,2,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,\n3,3,3,1,2,2,2,2,3,3,3,1,1,1,3,3,1,1,3,1,1,3,2,1,2,3,1,1,0,2,2,2,\n0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,\n3,3,3,2,1,2,1,1,3,3,1,1,1,1,3,3,1,1,2,2,1,2,1,1,2,2,1,1,0,2,2,1,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,\n3,3,3,1,1,2,1,1,3,3,1,0,1,1,3,3,2,0,1,1,2,3,1,0,2,2,1,0,0,1,3,2,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,\n3,2,1,3,3,3,3,3,1,2,3,2,3,3,2,1,1,3,2,3,2,1,2,2,0,1,2,1,0,0,1,1,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,\n3,3,3,3,2,2,2,2,3,1,2,2,1,1,3,3,0,3,2,1,2,3,2,1,3,3,1,1,0,2,1,3,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,\n3,3,3,2,2,2,3,2,3,3,3,2,1,1,3,3,1,1,1,2,2,3,2,3,2,2,2,1,0,2,2,1,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,\n1,0,0,3,3,3,3,3,0,0,3,3,2,3,0,0,0,2,3,3,1,0,1,2,0,0,1,1,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,1,2,3,3,3,3,3,1,2,3,3,2,2,1,1,0,3,3,2,2,1,2,2,1,0,2,2,0,1,1,1,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,2,2,1,3,1,2,3,3,2,2,1,1,2,2,1,1,1,1,3,2,1,1,1,1,2,1,0,1,2,1,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,1,0,0,0,0,0,0,0,0,0,\n2,3,3,1,1,1,1,1,3,3,3,0,1,1,3,3,1,1,1,1,1,2,2,0,3,1,1,2,0,2,1,1,\n0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,\n3,1,0,1,2,1,2,2,0,1,2,3,1,2,0,0,0,2,1,1,1,1,1,2,0,0,1,1,0,0,0,0,\n1,2,1,2,2,2,1,2,1,2,0,2,0,2,2,1,1,2,1,1,2,1,1,1,0,1,0,0,0,1,1,0,\n1,1,1,2,3,2,3,3,0,1,2,2,3,1,0,1,0,2,1,2,2,0,1,1,0,0,1,1,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,0,0,3,3,2,2,1,0,0,3,2,3,2,0,0,0,1,1,3,0,0,1,1,0,0,2,1,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,1,1,2,2,3,3,1,0,1,3,2,3,1,1,1,0,1,1,1,1,1,3,1,0,0,2,2,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,1,1,1,2,2,2,1,0,1,2,3,3,2,0,0,0,2,1,1,1,2,1,1,1,0,1,1,1,0,0,0,\n1,2,2,2,2,2,1,1,1,2,0,2,1,1,1,1,1,2,1,1,1,1,1,1,0,1,1,1,0,0,1,1,\n3,2,2,1,0,0,1,1,2,2,0,3,0,1,2,1,1,0,0,1,1,1,0,1,1,1,1,0,2,1,1,1,\n2,2,1,1,1,2,1,2,1,1,1,1,1,1,1,2,1,1,1,2,3,1,1,1,1,1,1,1,1,1,0,1,\n2,3,3,0,1,0,0,0,3,3,1,0,0,1,2,2,1,0,0,0,0,2,0,0,1,1,1,0,2,1,1,1,\n2,1,1,1,1,1,1,2,1,1,0,1,1,0,1,1,1,0,1,2,1,1,0,1,1,1,1,1,1,1,0,1,\n2,3,3,0,1,0,0,0,2,2,0,0,0,0,1,2,2,0,0,0,0,1,0,0,1,1,0,0,2,0,1,0,\n2,1,1,1,1,2,1,1,1,1,1,1,1,2,1,1,1,1,1,1,1,1,1,2,0,1,1,1,1,1,0,1,\n3,2,2,0,1,0,1,0,2,3,2,0,0,1,2,2,1,0,0,1,1,1,0,0,2,1,0,1,2,2,1,1,\n2,1,1,1,1,1,1,2,1,1,1,1,1,1,0,2,1,0,1,1,0,1,1,1,0,1,1,2,1,1,0,1,\n2,2,2,0,0,1,0,0,2,2,1,1,0,0,2,1,1,0,0,0,1,2,0,0,2,1,0,0,2,1,1,1,\n2,1,1,1,1,2,1,2,1,1,1,2,2,1,1,2,1,1,1,2,1,1,1,1,1,1,1,1,1,1,0,1,\n1,2,3,0,0,0,1,0,3,2,1,0,0,1,2,1,1,0,0,0,0,2,1,0,1,1,0,0,2,1,2,1,\n1,1,0,0,0,1,0,1,1,1,1,1,2,0,0,1,0,0,0,2,0,0,1,1,1,1,1,1,1,1,0,1,\n3,0,0,2,1,2,2,1,0,0,2,1,2,2,0,0,0,2,1,1,1,0,1,1,0,0,1,1,2,0,0,0,\n1,2,1,2,2,1,1,2,1,2,0,1,1,1,1,1,1,1,1,1,2,1,1,0,0,1,1,1,1,0,0,1,\n1,3,2,0,0,0,1,0,2,2,2,0,0,0,2,2,1,0,0,0,0,3,1,1,1,1,0,0,2,1,1,1,\n2,1,0,1,1,1,0,1,1,1,1,1,1,1,0,2,1,0,0,1,0,1,1,0,1,1,1,1,1,1,0,1,\n2,3,2,0,0,0,1,0,2,2,0,0,0,0,2,1,1,0,0,0,0,2,1,0,1,1,0,0,2,1,1,0,\n2,1,1,1,1,2,1,2,1,2,0,1,1,1,0,2,1,1,1,2,1,1,1,1,0,1,1,1,1,1,0,1,\n3,1,1,2,2,2,3,2,1,1,2,2,1,1,0,1,0,2,2,1,1,1,1,1,0,0,1,1,0,1,1,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,2,2,0,0,0,0,0,2,2,0,0,0,0,2,2,1,0,0,0,1,1,0,0,1,2,0,0,2,1,1,1,\n2,2,1,1,1,2,1,2,1,1,0,1,1,1,1,2,1,1,1,2,1,1,1,1,0,1,2,1,1,1,0,1,\n1,0,0,1,2,3,2,1,0,0,2,0,1,1,0,0,0,1,1,1,1,0,1,1,0,0,1,0,0,0,0,0,\n1,2,1,2,1,2,1,1,1,2,0,2,1,1,1,0,1,2,0,0,1,1,1,0,0,0,0,0,0,0,0,0,\n2,3,2,0,0,0,0,0,1,1,2,1,0,0,1,1,1,0,0,0,0,2,0,0,1,1,0,0,2,1,1,1,\n2,1,1,1,1,1,1,2,1,0,1,1,1,1,0,2,1,1,1,1,1,1,0,1,0,1,1,1,1,1,0,1,\n1,2,2,0,1,1,1,0,2,2,2,0,0,0,3,2,1,0,0,0,1,1,0,0,1,1,0,1,1,1,0,0,\n1,1,0,1,1,1,1,1,1,1,1,2,1,1,1,1,1,1,1,2,1,1,1,0,0,1,1,1,0,1,0,1,\n2,1,0,2,1,1,2,2,1,1,2,1,1,1,0,0,0,1,1,0,1,1,1,1,0,0,1,1,1,0,0,0,\n1,2,2,2,2,2,1,1,1,2,0,2,1,1,1,1,1,1,1,1,1,1,1,1,0,1,1,0,0,0,1,0,\n1,2,3,0,0,0,1,0,2,2,0,0,0,0,2,2,0,0,0,0,0,1,0,0,1,0,0,0,2,0,1,0,\n2,1,1,1,1,1,0,2,0,0,0,1,2,1,1,1,1,0,1,2,0,1,0,1,0,1,1,1,0,1,0,1,\n2,2,2,0,0,0,1,0,2,1,2,0,0,0,1,1,2,0,0,0,0,1,0,0,1,1,0,0,2,1,0,1,\n2,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,2,0,1,1,1,1,1,0,1,\n1,2,2,0,0,0,1,0,2,2,2,0,0,0,1,1,0,0,0,0,0,1,1,0,2,0,0,1,1,1,0,1,\n1,0,1,1,1,1,1,1,0,1,1,1,1,0,0,1,0,0,1,1,0,1,0,1,1,1,1,1,0,0,0,1,\n1,0,0,1,0,1,2,1,0,0,1,1,1,2,0,0,0,1,1,0,1,0,1,1,0,0,1,0,0,0,0,0,\n0,2,1,2,1,1,1,1,1,2,0,2,0,1,1,0,1,2,1,0,1,1,1,0,0,0,0,0,0,1,0,0,\n2,1,1,0,1,2,0,0,1,1,1,0,0,0,1,1,0,0,0,0,0,1,0,0,1,0,0,0,2,1,0,1,\n2,2,1,1,1,1,1,2,1,1,0,1,1,1,1,2,1,1,1,2,1,1,0,1,0,1,1,1,1,1,0,1,\n1,2,2,0,0,0,0,0,1,1,0,0,0,0,2,1,0,0,0,0,0,2,0,0,2,2,0,0,2,0,0,1,\n2,1,1,1,1,1,1,1,0,1,1,0,1,1,0,1,0,0,0,1,1,1,1,0,0,1,1,1,1,0,0,1,\n1,1,2,0,0,3,1,0,2,1,1,1,0,0,1,1,1,0,0,0,1,1,0,0,0,1,0,0,1,0,1,0,\n1,2,1,0,1,1,1,2,1,1,0,1,1,1,1,1,0,0,0,1,1,1,1,1,0,1,0,0,0,1,0,0,\n2,1,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,1,0,1,0,0,0,1,0,0,0,0,2,0,0,0,\n2,1,1,1,1,1,1,1,1,1,0,1,1,1,1,1,1,1,1,1,2,1,1,0,0,1,1,1,1,1,0,1,\n2,1,1,1,2,1,1,1,0,1,1,2,1,0,0,0,0,1,1,1,1,0,1,0,0,0,0,1,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,1,0,1,1,1,1,1,0,0,1,1,2,1,0,0,0,1,1,0,0,0,1,1,0,0,1,0,1,0,0,0,\n1,2,1,1,1,1,1,1,1,1,0,1,0,1,1,1,1,1,1,0,1,1,1,0,0,0,0,0,0,1,0,0,\n2,0,0,0,1,1,1,1,0,0,1,1,0,0,0,0,0,1,1,1,2,0,0,1,0,0,1,0,1,0,0,0,\n0,1,1,1,1,1,1,1,1,2,0,1,1,1,1,0,1,1,1,0,1,1,1,0,0,0,0,0,0,0,0,0,\n1,0,0,1,1,1,1,1,0,0,2,1,0,1,0,0,0,1,0,1,0,0,0,0,0,0,1,0,0,0,0,0,\n0,1,1,1,1,1,1,0,1,1,0,1,0,1,1,0,1,1,0,0,1,1,1,0,0,0,0,0,0,0,0,0,\n1,0,0,1,1,1,0,0,0,0,1,0,2,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,\n0,1,1,1,1,1,0,0,1,1,0,1,0,1,0,0,1,1,1,0,1,1,1,0,0,0,0,0,0,0,0,0,\n0,0,0,1,0,0,0,0,0,0,1,1,2,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,1,1,1,0,1,0,0,1,1,0,1,0,1,1,0,1,1,1,0,1,1,1,0,0,0,0,0,0,0,0,0,\n2,1,1,1,1,1,1,1,1,1,1,0,0,1,1,1,0,0,1,0,0,1,0,1,0,1,1,1,0,0,1,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,0,0,1,1,1,1,0,0,0,1,1,1,0,0,0,0,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0,\n0,1,1,1,1,1,1,0,1,1,0,1,0,1,0,0,1,1,0,0,1,1,0,0,0,0,0,0,0,0,0,0,\n)\n\nLatin2HungarianModel = {\n  'char_to_order_map': Latin2_HungarianCharToOrderMap,\n  'precedence_matrix': HungarianLangModel,\n  'typical_positive_ratio': 0.947368,\n  'keep_english_letter': True,\n  'charset_name': \"ISO-8859-2\",\n  'language': 'Hungarian',\n}\n\nWin1250HungarianModel = {\n  'char_to_order_map': win1250HungarianCharToOrderMap,\n  'precedence_matrix': HungarianLangModel,\n  'typical_positive_ratio': 0.947368,\n  'keep_english_letter': True,\n  'charset_name': \"windows-1250\",\n  'language': 'Hungarian',\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/langthaimodel.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n# 255: Control characters that usually does not exist in any text\n# 254: Carriage/Return\n# 253: symbol (punctuation) that does not belong to word\n# 252: 0 - 9\n\n# The following result for thai was collected from a limited sample (1M).\n\n# Character Mapping Table:\nTIS620CharToOrderMap = (\n255,255,255,255,255,255,255,255,255,255,254,255,255,254,255,255,  # 00\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,  # 10\n253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,253,  # 20\n252,252,252,252,252,252,252,252,252,252,253,253,253,253,253,253,  # 30\n253,182,106,107,100,183,184,185,101, 94,186,187,108,109,110,111,  # 40\n188,189,190, 89, 95,112,113,191,192,193,194,253,253,253,253,253,  # 50\n253, 64, 72, 73,114, 74,115,116,102, 81,201,117, 90,103, 78, 82,  # 60\n 96,202, 91, 79, 84,104,105, 97, 98, 92,203,253,253,253,253,253,  # 70\n209,210,211,212,213, 88,214,215,216,217,218,219,220,118,221,222,\n223,224, 99, 85, 83,225,226,227,228,229,230,231,232,233,234,235,\n236,  5, 30,237, 24,238, 75,  8, 26, 52, 34, 51,119, 47, 58, 57,\n 49, 53, 55, 43, 20, 19, 44, 14, 48,  3, 17, 25, 39, 62, 31, 54,\n 45,  9, 16,  2, 61, 15,239, 12, 42, 46, 18, 21, 76,  4, 66, 63,\n 22, 10,  1, 36, 23, 13, 40, 27, 32, 35, 86,240,241,242,243,244,\n 11, 28, 41, 29, 33,245, 50, 37,  6,  7, 67, 77, 38, 93,246,247,\n 68, 56, 59, 65, 69, 60, 70, 80, 71, 87,248,249,250,251,252,253,\n)\n\n# Model Table:\n# total sequences: 100%\n# first 512 sequences: 92.6386%\n# first 1024 sequences:7.3177%\n# rest  sequences:     1.0230%\n# negative sequences:  0.0436%\nThaiLangModel = (\n0,1,3,3,3,3,0,0,3,3,0,3,3,0,3,3,3,3,3,3,3,3,0,0,3,3,3,0,3,3,3,3,\n0,3,3,0,0,0,1,3,0,3,3,2,3,3,0,1,2,3,3,3,3,0,2,0,2,0,0,3,2,1,2,2,\n3,0,3,3,2,3,0,0,3,3,0,3,3,0,3,3,3,3,3,3,3,3,3,0,3,2,3,0,2,2,2,3,\n0,2,3,0,0,0,0,1,0,1,2,3,1,1,3,2,2,0,1,1,0,0,1,0,0,0,0,0,0,0,1,1,\n3,3,3,2,3,3,3,3,3,3,3,3,3,3,3,2,2,2,2,2,2,2,3,3,2,3,2,3,3,2,2,2,\n3,1,2,3,0,3,3,2,2,1,2,3,3,1,2,0,1,3,0,1,0,0,1,0,0,0,0,0,0,0,1,1,\n3,3,2,2,3,3,3,3,1,2,3,3,3,3,3,2,2,2,2,3,3,2,2,3,3,2,2,3,2,3,2,2,\n3,3,1,2,3,1,2,2,3,3,1,0,2,1,0,0,3,1,2,1,0,0,1,0,0,0,0,0,0,1,0,1,\n3,3,3,3,3,3,2,2,3,3,3,3,2,3,2,2,3,3,2,2,3,2,2,2,2,1,1,3,1,2,1,1,\n3,2,1,0,2,1,0,1,0,1,1,0,1,1,0,0,1,0,1,0,0,0,1,0,0,0,0,0,0,0,0,0,\n3,3,3,2,3,2,3,3,2,2,3,2,3,3,2,3,1,1,2,3,2,2,2,3,2,2,2,2,2,1,2,1,\n2,2,1,1,3,3,2,1,0,1,2,2,0,1,3,0,0,0,1,1,0,0,0,0,0,2,3,0,0,2,1,1,\n3,3,2,3,3,2,0,0,3,3,0,3,3,0,2,2,3,1,2,2,1,1,1,0,2,2,2,0,2,2,1,1,\n0,2,1,0,2,0,0,2,0,1,0,0,1,0,0,0,1,1,1,1,0,0,0,0,0,0,0,0,0,0,1,0,\n3,3,2,3,3,2,0,0,3,3,0,2,3,0,2,1,2,2,2,2,1,2,0,0,2,2,2,0,2,2,1,1,\n0,2,1,0,2,0,0,2,0,1,1,0,1,0,0,0,0,0,0,1,0,0,1,0,0,0,0,0,0,0,0,0,\n3,3,2,3,2,3,2,0,2,2,1,3,2,1,3,2,1,2,3,2,2,3,0,2,3,2,2,1,2,2,2,2,\n1,2,2,0,0,0,0,2,0,1,2,0,1,1,1,0,1,0,3,1,1,0,0,0,0,0,0,0,0,0,1,0,\n3,3,2,3,3,2,3,2,2,2,3,2,2,3,2,2,1,2,3,2,2,3,1,3,2,2,2,3,2,2,2,3,\n3,2,1,3,0,1,1,1,0,2,1,1,1,1,1,0,1,0,1,1,0,0,0,0,0,0,0,0,0,2,0,0,\n1,0,0,3,0,3,3,3,3,3,0,0,3,0,2,2,3,3,3,3,3,0,0,0,1,1,3,0,0,0,0,2,\n0,0,1,0,0,0,0,0,0,0,2,3,0,0,0,3,0,2,0,0,0,0,0,3,0,0,0,0,0,0,0,0,\n2,0,3,3,3,3,0,0,2,3,0,0,3,0,3,3,2,3,3,3,3,3,0,0,3,3,3,0,0,0,3,3,\n0,0,3,0,0,0,0,2,0,0,2,1,1,3,0,0,1,0,0,2,3,0,1,0,0,0,0,0,0,0,1,0,\n3,3,3,3,2,3,3,3,3,3,3,3,1,2,1,3,3,2,2,1,2,2,2,3,1,1,2,0,2,1,2,1,\n2,2,1,0,0,0,1,1,0,1,0,1,1,0,0,0,0,0,1,1,0,0,1,0,0,0,0,0,0,0,0,0,\n3,0,2,1,2,3,3,3,0,2,0,2,2,0,2,1,3,2,2,1,2,1,0,0,2,2,1,0,2,1,2,2,\n0,1,1,0,0,0,0,1,0,1,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,2,1,3,3,1,1,3,0,2,3,1,1,3,2,1,1,2,0,2,2,3,2,1,1,1,1,1,2,\n3,0,0,1,3,1,2,1,2,0,3,0,0,0,1,0,3,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,\n3,3,1,1,3,2,3,3,3,1,3,2,1,3,2,1,3,2,2,2,2,1,3,3,1,2,1,3,1,2,3,0,\n2,1,1,3,2,2,2,1,2,1,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,\n3,3,2,3,2,3,3,2,3,2,3,2,3,3,2,1,0,3,2,2,2,1,2,2,2,1,2,2,1,2,1,1,\n2,2,2,3,0,1,3,1,1,1,1,0,1,1,0,2,1,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,2,3,2,2,1,1,3,2,3,2,3,2,0,3,2,2,1,2,0,2,2,2,1,2,2,2,2,1,\n3,2,1,2,2,1,0,2,0,1,0,0,1,1,0,0,0,0,0,1,1,0,1,0,0,0,0,0,0,0,0,1,\n3,3,3,3,3,2,3,1,2,3,3,2,2,3,0,1,1,2,0,3,3,2,2,3,0,1,1,3,0,0,0,0,\n3,1,0,3,3,0,2,0,2,1,0,0,3,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,2,3,2,3,3,0,1,3,1,1,2,1,2,1,1,3,1,1,0,2,3,1,1,1,1,1,1,1,1,\n3,1,1,2,2,2,2,1,1,1,0,0,2,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n3,2,2,1,1,2,1,3,3,2,3,2,2,3,2,2,3,1,2,2,1,2,0,3,2,1,2,2,2,2,2,1,\n3,2,1,2,2,2,1,1,1,1,0,0,1,1,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,1,3,3,0,2,1,0,3,2,0,0,3,1,0,1,1,0,1,0,0,0,0,0,1,\n1,0,0,1,0,3,2,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,0,2,2,2,3,0,0,1,3,0,3,2,0,3,2,2,3,3,3,3,3,1,0,2,2,2,0,2,2,1,2,\n0,2,3,0,0,0,0,1,0,1,0,0,1,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n3,0,2,3,1,3,3,2,3,3,0,3,3,0,3,2,2,3,2,3,3,3,0,0,2,2,3,0,1,1,1,3,\n0,0,3,0,0,0,2,2,0,1,3,0,1,2,2,2,3,0,0,0,0,0,1,0,0,0,0,0,0,0,0,1,\n3,2,3,3,2,0,3,3,2,2,3,1,3,2,1,3,2,0,1,2,2,0,2,3,2,1,0,3,0,0,0,0,\n3,0,0,2,3,1,3,0,0,3,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,1,3,2,2,2,1,2,0,1,3,1,1,3,1,3,0,0,2,1,1,1,1,2,1,1,1,0,2,1,0,1,\n1,2,0,0,0,3,1,1,0,0,0,0,1,0,1,0,0,1,0,1,0,0,0,0,0,3,1,0,0,0,1,0,\n3,3,3,3,2,2,2,2,2,1,3,1,1,1,2,0,1,1,2,1,2,1,3,2,0,0,3,1,1,1,1,1,\n3,1,0,2,3,0,0,0,3,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,2,3,0,3,3,0,2,0,0,0,0,0,0,0,3,0,0,1,0,0,0,0,0,0,0,0,0,0,0,\n0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,2,3,1,3,0,0,1,2,0,0,2,0,3,3,2,3,3,3,2,3,0,0,2,2,2,0,0,0,2,2,\n0,0,1,0,0,0,0,3,0,0,0,0,2,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,\n0,0,0,3,0,2,0,0,0,0,0,0,0,0,0,0,1,2,3,1,3,3,0,0,1,0,3,0,0,0,0,0,\n0,0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,1,2,3,1,2,3,1,0,3,0,2,2,1,0,2,1,1,2,0,1,0,0,1,1,1,1,0,1,0,0,\n1,0,0,0,0,1,1,0,3,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,2,1,0,1,1,1,3,1,2,2,2,2,2,2,1,1,1,1,0,3,1,0,1,3,1,1,1,1,\n1,1,0,2,0,1,3,1,1,0,0,1,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,2,0,1,\n3,0,2,2,1,3,3,2,3,3,0,1,1,0,2,2,1,2,1,3,3,1,0,0,3,2,0,0,0,0,2,1,\n0,1,0,0,0,0,1,2,0,1,1,3,1,1,2,2,1,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,\n0,0,3,0,0,1,0,0,0,3,0,0,3,0,3,1,0,1,1,1,3,2,0,0,0,3,0,0,0,0,2,0,\n0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,2,0,0,0,0,0,0,0,0,0,\n3,3,1,3,2,1,3,3,1,2,2,0,1,2,1,0,1,2,0,0,0,0,0,3,0,0,0,3,0,0,0,0,\n3,0,0,1,1,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,0,1,2,0,3,3,3,2,2,0,1,1,0,1,3,0,0,0,2,2,0,0,0,0,3,1,0,1,0,0,0,\n0,0,0,0,0,0,0,0,0,1,0,1,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,0,2,3,1,2,0,0,2,1,0,3,1,0,1,2,0,1,1,1,1,3,0,0,3,1,1,0,2,2,1,1,\n0,2,0,0,0,0,0,1,0,1,0,0,1,1,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,0,0,3,1,2,0,0,2,2,0,1,2,0,1,0,1,3,1,2,1,0,0,0,2,0,3,0,0,0,1,0,\n0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,0,1,1,2,2,0,0,0,2,0,2,1,0,1,1,0,1,1,1,2,1,0,0,1,1,1,0,2,1,1,1,\n0,1,1,0,0,0,0,0,0,1,0,0,1,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,1,0,1,\n0,0,0,2,0,1,3,1,1,1,1,0,0,0,0,3,2,0,1,0,0,0,1,2,0,0,0,1,0,0,0,0,\n0,0,0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,3,3,3,3,1,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,0,2,3,2,2,0,0,0,1,0,0,0,0,2,3,2,1,2,2,3,0,0,0,2,3,1,0,0,0,1,1,\n0,0,1,0,0,0,0,0,0,0,1,0,0,1,0,0,0,0,0,1,1,0,1,0,0,0,0,0,0,0,0,0,\n3,3,2,2,0,1,0,0,0,0,2,0,2,0,1,0,0,0,1,1,0,0,0,2,1,0,1,0,1,1,0,0,\n0,1,0,2,0,0,1,0,3,0,1,0,0,0,2,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,1,0,0,1,0,0,0,0,0,1,1,2,0,0,0,0,1,0,0,1,3,1,0,0,0,0,1,1,0,0,\n0,1,0,0,0,0,3,0,0,0,0,0,0,3,0,0,0,0,0,0,0,3,0,0,0,0,0,0,0,0,0,0,\n3,3,1,1,1,1,2,3,0,0,2,1,1,1,1,1,0,2,1,1,0,0,0,2,1,0,1,2,1,1,0,1,\n2,1,0,3,0,0,0,0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,3,1,0,0,0,0,0,0,0,3,0,0,0,3,0,0,0,0,0,0,0,0,1,1,0,0,0,0,0,0,1,\n0,0,0,2,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,2,0,0,0,0,0,0,1,2,1,0,1,1,0,2,0,0,1,0,0,2,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,2,0,0,0,1,3,0,1,0,0,0,2,0,0,0,0,0,0,0,1,2,0,0,0,0,0,\n3,3,0,0,1,1,2,0,0,1,2,1,0,1,1,1,0,1,1,0,0,2,1,1,0,1,0,0,1,1,1,0,\n0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,3,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,2,2,1,0,0,0,0,1,0,0,0,0,3,0,0,0,0,0,0,0,0,0,3,0,0,0,0,0,0,0,0,\n2,0,0,0,0,0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,3,0,0,1,1,0,0,0,2,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,1,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n1,1,0,1,2,0,1,2,0,0,1,1,0,2,0,1,0,0,1,0,0,0,0,1,0,0,0,2,0,0,0,0,\n1,0,0,1,0,1,1,0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,1,0,0,0,0,0,0,0,1,1,0,1,1,0,2,1,3,0,0,0,0,1,1,0,0,0,0,0,0,0,3,\n1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,0,1,0,1,0,0,2,0,0,2,0,0,1,1,2,0,0,1,1,0,0,0,1,0,0,0,1,1,0,0,0,\n1,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,\n1,0,0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,1,1,0,0,0,\n2,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,3,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,0,0,0,0,2,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,1,0,1,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,1,3,0,0,0,\n2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,1,0,0,0,0,\n1,0,0,0,0,0,0,0,0,1,0,0,0,0,2,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,1,1,0,0,2,1,0,0,1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n)\n\nTIS620ThaiModel = {\n  'char_to_order_map': TIS620CharToOrderMap,\n  'precedence_matrix': ThaiLangModel,\n  'typical_positive_ratio': 0.926386,\n  'keep_english_letter': False,\n  'charset_name': \"TIS-620\",\n  'language': 'Thai',\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/langturkishmodel.py",
    "content": "# -*- coding: utf-8 -*-\n######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Communicator client code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#   Özgür Baskın - Turkish Language Model\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\n# 255: Control characters that usually does not exist in any text\n# 254: Carriage/Return\n# 253: symbol (punctuation) that does not belong to word\n# 252: 0 - 9\n\n# Character Mapping Table:\nLatin5_TurkishCharToOrderMap = (\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,\n255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,255,\n255, 23, 37, 47, 39, 29, 52, 36, 45, 53, 60, 16, 49, 20, 46, 42,\n 48, 69, 44, 35, 31, 51, 38, 62, 65, 43, 56,255,255,255,255,255,\n255,  1, 21, 28, 12,  2, 18, 27, 25,  3, 24, 10,  5, 13,  4, 15,\n 26, 64,  7,  8,  9, 14, 32, 57, 58, 11, 22,255,255,255,255,255,\n180,179,178,177,176,175,174,173,172,171,170,169,168,167,166,165,\n164,163,162,161,160,159,101,158,157,156,155,154,153,152,151,106,\n150,149,148,147,146,145,144,100,143,142,141,140,139,138,137,136,\n 94, 80, 93,135,105,134,133, 63,132,131,130,129,128,127,126,125,\n124,104, 73, 99, 79, 85,123, 54,122, 98, 92,121,120, 91,103,119,\n 68,118,117, 97,116,115, 50, 90,114,113,112,111, 55, 41, 40, 86,\n 89, 70, 59, 78, 71, 82, 88, 33, 77, 66, 84, 83,110, 75, 61, 96,\n 30, 67,109, 74, 87,102, 34, 95, 81,108, 76, 72, 17,  6, 19,107,\n)\n\nTurkishLangModel = (\n3,2,3,3,3,1,3,3,3,3,3,3,3,3,2,1,1,3,3,1,3,3,0,3,3,3,3,3,0,3,1,3,\n3,2,1,0,0,1,1,0,0,0,1,0,0,1,1,1,1,0,0,0,0,0,0,0,2,2,0,0,1,0,0,1,\n3,2,2,3,3,0,3,3,3,3,3,3,3,2,3,1,0,3,3,1,3,3,0,3,3,3,3,3,0,3,0,3,\n3,1,1,0,1,0,1,0,0,0,0,0,0,1,1,1,1,0,0,0,0,0,0,0,2,2,0,0,0,1,0,1,\n3,3,2,3,3,0,3,3,3,3,3,3,3,2,3,1,1,3,3,0,3,3,1,2,3,3,3,3,0,3,0,3,\n3,1,1,0,0,0,1,0,0,0,0,1,1,0,1,2,1,0,0,0,1,0,0,0,0,2,0,0,0,0,0,1,\n3,3,3,3,3,3,2,3,3,3,3,3,3,3,3,1,3,3,2,0,3,2,1,2,2,1,3,3,0,0,0,2,\n2,2,0,1,0,0,1,0,0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,0,1,1,0,1,0,0,1,\n3,3,3,2,3,3,1,2,3,3,3,3,3,3,3,1,3,2,1,0,3,2,0,1,2,3,3,2,1,0,0,2,\n2,1,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,2,0,2,0,0,0,\n1,0,1,3,3,1,3,3,3,3,3,3,3,1,2,0,0,2,3,0,2,3,0,0,2,2,2,3,0,3,0,1,\n2,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,0,3,3,3,0,3,2,0,2,3,2,3,3,1,0,0,2,\n3,2,0,0,1,0,0,0,0,0,0,2,0,0,1,0,0,0,0,0,0,0,0,0,1,1,1,0,2,0,0,1,\n3,3,3,2,3,3,2,3,3,3,3,2,3,3,3,0,3,3,0,0,2,1,0,0,2,3,2,2,0,0,0,2,\n2,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1,0,0,0,1,0,1,0,2,0,0,1,\n3,3,3,2,3,3,3,3,3,3,3,2,3,3,3,0,3,2,0,1,3,2,1,1,3,2,3,2,1,0,0,2,\n2,2,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,1,0,0,0,0,0,\n3,3,3,2,3,3,3,3,3,3,3,2,3,3,3,0,3,2,2,0,2,3,0,0,2,2,2,2,0,0,0,2,\n3,3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,2,0,1,0,0,0,\n3,3,3,3,3,3,3,2,2,2,2,3,2,3,3,0,3,3,1,1,2,2,0,0,2,2,3,2,0,0,1,3,\n0,3,1,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,1,0,0,0,0,1,\n3,3,3,2,3,3,3,2,1,2,2,3,2,3,3,0,3,2,0,0,1,1,0,1,1,2,1,2,0,0,0,1,\n0,3,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,1,0,1,0,1,0,0,0,\n3,3,3,2,3,3,2,3,2,2,2,3,3,3,3,1,3,1,1,0,3,2,1,1,3,3,2,3,1,0,0,1,\n1,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,2,0,0,1,\n3,2,2,3,3,0,3,3,3,3,3,3,3,2,2,1,0,3,3,1,3,3,0,1,3,3,2,3,0,3,0,3,\n2,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,\n2,2,2,3,3,0,3,3,3,3,3,3,3,3,3,0,0,3,2,0,3,3,0,3,2,3,3,3,0,3,1,3,\n2,0,0,0,0,0,0,0,0,0,0,1,0,1,2,0,1,0,0,0,0,0,0,0,2,2,0,0,1,0,0,1,\n3,3,3,1,2,3,3,1,0,0,1,0,0,3,3,2,3,0,0,2,0,0,2,0,2,0,0,0,2,0,2,0,\n0,3,1,0,1,0,0,0,2,2,1,0,1,1,2,1,2,2,2,0,2,1,1,0,0,0,2,0,0,0,0,0,\n1,2,1,3,3,0,3,3,3,3,3,2,3,0,0,0,0,2,3,0,2,3,1,0,2,3,1,3,0,3,0,2,\n3,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,1,3,3,2,2,3,2,2,0,1,2,3,0,1,2,1,0,1,0,0,0,1,0,2,2,0,0,0,1,\n1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,1,1,0,0,1,0,0,0,\n3,3,3,1,3,3,1,1,3,3,1,1,3,3,1,0,2,1,2,0,2,1,0,0,1,1,2,1,0,0,0,2,\n2,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,1,0,2,1,3,0,0,2,0,0,3,3,0,3,0,0,1,0,1,2,0,0,1,1,2,2,0,1,0,\n0,1,2,1,1,0,1,0,1,1,1,1,1,0,1,1,1,2,2,1,2,0,1,0,0,0,0,0,0,1,0,0,\n3,3,3,2,3,2,3,3,0,2,2,2,3,3,3,0,3,0,0,0,2,2,0,1,2,1,1,1,0,0,0,1,\n0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,\n3,3,3,3,3,3,2,1,2,2,3,3,3,3,2,0,2,0,0,0,2,2,0,0,2,1,3,3,0,0,1,1,\n1,1,0,0,1,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,1,0,0,0,\n1,1,2,3,3,0,3,3,3,3,3,3,2,2,0,2,0,2,3,2,3,2,2,2,2,2,2,2,1,3,2,3,\n2,0,2,1,2,2,2,2,1,1,2,2,1,2,2,1,2,0,0,2,1,1,0,2,1,0,0,1,0,0,0,1,\n2,3,3,1,1,1,0,1,1,1,2,3,2,1,1,0,0,0,0,0,0,0,0,0,0,1,0,1,0,0,0,0,\n0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,2,2,2,3,2,3,2,2,1,3,3,3,0,2,1,2,0,2,1,0,0,1,1,1,1,1,0,0,1,\n2,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,2,0,1,0,0,0,\n3,3,3,2,3,3,3,3,3,2,3,1,2,3,3,1,2,0,0,0,0,0,0,0,3,2,1,1,0,0,0,0,\n2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,\n3,3,3,2,2,3,3,2,1,1,1,1,1,3,3,0,3,1,0,0,1,1,0,0,3,1,2,1,0,0,0,0,\n0,3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,\n3,3,3,2,2,3,2,2,2,3,2,1,1,3,3,0,3,0,0,0,0,1,0,0,3,1,1,2,0,0,0,1,\n1,0,0,1,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,\n1,1,1,3,3,0,3,3,3,3,3,2,2,2,1,2,0,2,1,2,2,1,1,0,1,2,2,2,2,2,2,2,\n0,0,2,1,2,1,2,1,0,1,1,3,1,2,1,1,2,0,0,2,0,1,0,1,0,1,0,0,0,1,0,1,\n3,3,3,1,3,3,3,0,1,1,0,2,2,3,1,0,3,0,0,0,1,0,0,0,1,0,0,1,0,1,0,0,\n1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,2,0,0,2,2,1,0,0,1,0,0,3,3,1,3,0,0,1,1,0,2,0,3,0,0,0,2,0,1,1,\n0,1,2,0,1,2,2,0,2,2,2,2,1,0,2,1,1,0,2,0,2,1,2,0,0,0,0,0,0,0,0,0,\n3,3,3,1,3,2,3,2,0,2,2,2,1,3,2,0,2,1,2,0,1,2,0,0,1,0,2,2,0,0,0,2,\n1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,1,0,1,0,0,0,\n3,3,3,0,3,3,1,1,2,3,1,0,3,2,3,0,3,0,0,0,1,0,0,0,1,0,1,0,0,0,0,0,\n1,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,3,3,0,3,3,2,3,3,2,2,0,0,0,0,1,2,0,1,3,0,0,0,3,1,1,0,3,0,2,\n2,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,1,2,2,1,0,3,1,1,1,1,3,3,2,3,0,0,1,0,1,2,0,2,2,0,2,2,0,2,1,\n0,2,2,1,1,1,1,0,2,1,1,0,1,1,1,1,2,1,2,1,2,0,1,0,1,0,0,0,0,0,0,0,\n3,3,3,0,1,1,3,0,0,1,1,0,0,2,2,0,3,0,0,1,1,0,1,0,0,0,0,0,2,0,0,0,\n0,3,1,0,1,0,1,0,2,0,0,1,0,1,0,1,1,1,2,1,1,0,2,0,0,0,0,0,0,0,0,0,\n3,3,3,0,2,0,2,0,1,1,1,0,0,3,3,0,2,0,0,1,0,0,2,1,1,0,1,0,1,0,1,0,\n0,2,0,1,2,0,2,0,2,1,1,0,1,0,2,1,1,0,2,1,1,0,1,0,0,0,1,1,0,0,0,0,\n3,2,3,0,1,0,0,0,0,0,0,0,0,1,2,0,1,0,0,1,0,0,1,0,0,0,0,0,2,0,0,0,\n0,0,1,1,0,0,1,0,1,0,0,1,0,0,0,2,1,0,1,0,2,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,0,0,2,3,0,0,1,0,1,0,2,3,2,3,0,0,1,3,0,2,1,0,0,0,0,2,0,1,0,\n0,2,1,0,0,1,1,0,2,1,0,0,1,0,0,1,1,0,1,1,2,0,1,0,0,0,0,1,0,0,0,0,\n3,2,2,0,0,1,1,0,0,0,0,0,0,3,1,1,1,0,0,0,0,0,1,0,0,0,0,0,2,0,1,0,\n0,1,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,1,0,1,0,0,0,0,0,0,0,0,0,\n0,0,0,3,3,0,2,3,2,2,1,2,2,1,1,2,0,1,3,2,2,2,0,0,2,2,0,0,0,1,2,1,\n3,0,2,1,1,0,1,1,1,0,1,2,2,2,1,1,2,0,0,0,0,1,0,1,1,0,0,0,0,0,0,0,\n0,1,1,2,3,0,3,3,3,2,2,2,2,1,0,1,0,1,0,1,2,2,0,0,2,2,1,3,1,1,2,1,\n0,0,1,1,2,0,1,1,0,0,1,2,0,2,1,1,2,0,0,1,0,0,0,1,0,1,0,1,0,0,0,0,\n3,3,2,0,0,3,1,0,0,0,0,0,0,3,2,1,2,0,0,1,0,0,2,0,0,0,0,0,2,0,1,0,\n0,2,1,1,0,0,1,0,1,2,0,0,1,1,0,0,2,1,1,1,1,0,2,0,0,0,0,0,0,0,0,0,\n3,3,2,0,0,1,0,0,0,0,1,0,0,3,3,2,2,0,0,1,0,0,2,0,1,0,0,0,2,0,1,0,\n0,0,1,1,0,0,2,0,2,1,0,0,1,1,2,1,2,0,2,1,2,1,1,1,0,0,1,1,0,0,0,0,\n3,3,2,0,0,2,2,0,0,0,1,1,0,2,2,1,3,1,0,1,0,1,2,0,0,0,0,0,1,0,1,0,\n0,1,1,0,0,0,0,0,1,0,0,1,0,0,0,1,1,0,1,0,1,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,2,0,0,0,1,0,0,1,0,0,2,3,1,2,0,0,1,0,0,2,0,0,0,1,0,2,0,2,0,\n0,1,1,2,2,1,2,0,2,1,1,0,0,1,1,0,1,1,1,1,2,1,1,0,0,0,0,0,0,0,0,0,\n3,3,3,0,2,1,2,1,0,0,1,1,0,3,3,1,2,0,0,1,0,0,2,0,2,0,1,1,2,0,0,0,\n0,0,1,1,1,1,2,0,1,1,0,1,1,1,1,0,0,0,1,1,1,0,1,0,0,0,1,0,0,0,0,0,\n3,3,3,0,2,2,3,2,0,0,1,0,0,2,3,1,0,0,0,0,0,0,2,0,2,0,0,0,2,0,0,0,\n0,1,1,0,0,0,1,0,0,1,0,1,1,0,1,0,1,1,1,0,1,0,0,0,0,0,0,0,0,0,0,0,\n3,2,3,0,0,0,0,0,0,0,1,0,0,2,2,2,2,0,0,1,0,0,2,0,0,0,0,0,2,0,1,0,\n0,0,2,1,1,0,1,0,2,1,1,0,0,1,1,2,1,0,2,0,2,0,1,0,0,0,2,0,0,0,0,0,\n0,0,0,2,2,0,2,1,1,1,1,2,2,0,0,1,0,1,0,0,1,3,0,0,0,0,1,0,0,2,1,0,\n0,0,1,0,1,0,0,0,0,0,2,1,0,1,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,\n2,0,0,2,3,0,2,3,1,2,2,0,2,0,0,2,0,2,1,1,1,2,1,0,0,1,2,1,1,2,1,0,\n1,0,2,0,1,0,1,1,0,0,2,2,1,2,1,1,2,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,\n3,3,3,0,2,1,2,0,0,0,1,0,0,3,2,0,1,0,0,1,0,0,2,0,0,0,1,2,1,0,1,0,\n0,0,0,0,1,0,1,0,0,1,0,0,0,0,1,0,1,0,1,1,1,0,1,0,0,0,0,0,0,0,0,0,\n0,0,0,2,2,0,2,2,1,1,0,1,1,1,1,1,0,0,1,2,1,1,1,0,1,0,0,0,1,1,1,1,\n0,0,2,1,0,1,1,1,0,1,1,2,1,2,1,1,2,0,1,1,2,1,0,2,0,0,0,0,0,0,0,0,\n3,2,2,0,0,2,0,0,0,0,0,0,0,2,2,0,2,0,0,1,0,0,2,0,0,0,0,0,2,0,0,0,\n0,2,1,0,0,0,0,0,1,0,0,0,0,0,0,0,1,0,0,0,1,0,1,0,0,0,0,0,0,0,0,0,\n0,0,0,3,2,0,2,2,0,1,1,0,1,0,0,1,0,0,0,1,0,1,0,0,0,0,0,1,0,0,0,0,\n2,0,1,0,1,0,1,1,0,0,1,2,0,1,0,1,1,0,0,1,0,1,0,2,0,0,0,0,0,0,0,0,\n2,2,2,0,1,1,0,0,0,1,0,0,0,1,2,0,1,0,0,1,0,0,1,0,0,0,0,1,2,0,1,0,\n0,0,1,0,0,0,1,0,0,1,0,0,0,0,0,0,1,0,1,0,2,0,0,0,0,0,0,0,0,0,0,0,\n2,2,2,2,1,0,1,1,1,0,0,0,0,1,2,0,0,1,0,0,0,1,0,0,1,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,\n1,1,2,0,1,0,0,0,1,0,1,0,0,0,1,0,0,1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,2,0,0,0,0,0,1,\n0,0,1,2,2,0,2,1,2,1,1,2,2,0,0,0,0,1,0,0,1,1,0,0,2,0,0,0,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,\n2,2,2,0,0,0,1,0,0,0,0,0,0,2,2,1,1,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,\n0,0,0,0,1,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,1,1,0,0,0,1,0,0,0,1,0,0,0,0,0,0,0,1,1,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n2,2,2,0,1,0,1,0,0,0,0,0,0,1,1,0,0,0,0,0,0,0,1,0,1,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,1,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,1,0,0,0,0,0,0,0,0,0,0,2,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,\n)\n\nLatin5TurkishModel = {\n  'char_to_order_map': Latin5_TurkishCharToOrderMap,\n  'precedence_matrix': TurkishLangModel,\n  'typical_positive_ratio': 0.970290,\n  'keep_english_letter': True,\n  'charset_name': \"ISO-8859-9\",\n  'language': 'Turkish',\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/latin1prober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Universal charset detector code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 2001\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#   Shy Shalom - original C code\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .charsetprober import CharSetProber\nfrom .enums import ProbingState\n\nFREQ_CAT_NUM = 4\n\nUDF = 0  # undefined\nOTH = 1  # other\nASC = 2  # ascii capital letter\nASS = 3  # ascii small letter\nACV = 4  # accent capital vowel\nACO = 5  # accent capital other\nASV = 6  # accent small vowel\nASO = 7  # accent small other\nCLASS_NUM = 8  # total classes\n\nLatin1_CharToClass = (\n    OTH, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # 00 - 07\n    OTH, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # 08 - 0F\n    OTH, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # 10 - 17\n    OTH, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # 18 - 1F\n    OTH, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # 20 - 27\n    OTH, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # 28 - 2F\n    OTH, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # 30 - 37\n    OTH, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # 38 - 3F\n    OTH, ASC, ASC, ASC, ASC, ASC, ASC, ASC,   # 40 - 47\n    ASC, ASC, ASC, ASC, ASC, ASC, ASC, ASC,   # 48 - 4F\n    ASC, ASC, ASC, ASC, ASC, ASC, ASC, ASC,   # 50 - 57\n    ASC, ASC, ASC, OTH, OTH, OTH, OTH, OTH,   # 58 - 5F\n    OTH, ASS, ASS, ASS, ASS, ASS, ASS, ASS,   # 60 - 67\n    ASS, ASS, ASS, ASS, ASS, ASS, ASS, ASS,   # 68 - 6F\n    ASS, ASS, ASS, ASS, ASS, ASS, ASS, ASS,   # 70 - 77\n    ASS, ASS, ASS, OTH, OTH, OTH, OTH, OTH,   # 78 - 7F\n    OTH, UDF, OTH, ASO, OTH, OTH, OTH, OTH,   # 80 - 87\n    OTH, OTH, ACO, OTH, ACO, UDF, ACO, UDF,   # 88 - 8F\n    UDF, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # 90 - 97\n    OTH, OTH, ASO, OTH, ASO, UDF, ASO, ACO,   # 98 - 9F\n    OTH, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # A0 - A7\n    OTH, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # A8 - AF\n    OTH, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # B0 - B7\n    OTH, OTH, OTH, OTH, OTH, OTH, OTH, OTH,   # B8 - BF\n    ACV, ACV, ACV, ACV, ACV, ACV, ACO, ACO,   # C0 - C7\n    ACV, ACV, ACV, ACV, ACV, ACV, ACV, ACV,   # C8 - CF\n    ACO, ACO, ACV, ACV, ACV, ACV, ACV, OTH,   # D0 - D7\n    ACV, ACV, ACV, ACV, ACV, ACO, ACO, ACO,   # D8 - DF\n    ASV, ASV, ASV, ASV, ASV, ASV, ASO, ASO,   # E0 - E7\n    ASV, ASV, ASV, ASV, ASV, ASV, ASV, ASV,   # E8 - EF\n    ASO, ASO, ASV, ASV, ASV, ASV, ASV, OTH,   # F0 - F7\n    ASV, ASV, ASV, ASV, ASV, ASO, ASO, ASO,   # F8 - FF\n)\n\n# 0 : illegal\n# 1 : very unlikely\n# 2 : normal\n# 3 : very likely\nLatin1ClassModel = (\n# UDF OTH ASC ASS ACV ACO ASV ASO\n    0,  0,  0,  0,  0,  0,  0,  0,  # UDF\n    0,  3,  3,  3,  3,  3,  3,  3,  # OTH\n    0,  3,  3,  3,  3,  3,  3,  3,  # ASC\n    0,  3,  3,  3,  1,  1,  3,  3,  # ASS\n    0,  3,  3,  3,  1,  2,  1,  2,  # ACV\n    0,  3,  3,  3,  3,  3,  3,  3,  # ACO\n    0,  3,  1,  3,  1,  1,  1,  3,  # ASV\n    0,  3,  1,  3,  1,  1,  3,  3,  # ASO\n)\n\n\nclass Latin1Prober(CharSetProber):\n    def __init__(self):\n        super(Latin1Prober, self).__init__()\n        self._last_char_class = None\n        self._freq_counter = None\n        self.reset()\n\n    def reset(self):\n        self._last_char_class = OTH\n        self._freq_counter = [0] * FREQ_CAT_NUM\n        CharSetProber.reset(self)\n\n    @property\n    def charset_name(self):\n        return \"ISO-8859-1\"\n\n    @property\n    def language(self):\n        return \"\"\n\n    def feed(self, byte_str):\n        byte_str = self.filter_with_english_letters(byte_str)\n        for c in byte_str:\n            char_class = Latin1_CharToClass[c]\n            freq = Latin1ClassModel[(self._last_char_class * CLASS_NUM)\n                                    + char_class]\n            if freq == 0:\n                self._state = ProbingState.NOT_ME\n                break\n            self._freq_counter[freq] += 1\n            self._last_char_class = char_class\n\n        return self.state\n\n    def get_confidence(self):\n        if self.state == ProbingState.NOT_ME:\n            return 0.01\n\n        total = sum(self._freq_counter)\n        if total < 0.01:\n            confidence = 0.0\n        else:\n            confidence = ((self._freq_counter[3] - self._freq_counter[1] * 20.0)\n                          / total)\n        if confidence < 0.0:\n            confidence = 0.0\n        # lower the confidence of latin1 so that other more accurate\n        # detector can take priority.\n        confidence = confidence * 0.73\n        return confidence\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/mbcharsetprober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Universal charset detector code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 2001\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#   Shy Shalom - original C code\n#   Proofpoint, Inc.\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .charsetprober import CharSetProber\nfrom .enums import ProbingState, MachineState\n\n\nclass MultiByteCharSetProber(CharSetProber):\n    \"\"\"\n    MultiByteCharSetProber\n    \"\"\"\n\n    def __init__(self, lang_filter=None):\n        super(MultiByteCharSetProber, self).__init__(lang_filter=lang_filter)\n        self.distribution_analyzer = None\n        self.coding_sm = None\n        self._last_char = [0, 0]\n\n    def reset(self):\n        super(MultiByteCharSetProber, self).reset()\n        if self.coding_sm:\n            self.coding_sm.reset()\n        if self.distribution_analyzer:\n            self.distribution_analyzer.reset()\n        self._last_char = [0, 0]\n\n    @property\n    def charset_name(self):\n        raise NotImplementedError\n\n    @property\n    def language(self):\n        raise NotImplementedError\n\n    def feed(self, byte_str):\n        for i in range(len(byte_str)):\n            coding_state = self.coding_sm.next_state(byte_str[i])\n            if coding_state == MachineState.ERROR:\n                self.logger.debug('%s %s prober hit error at byte %s',\n                                  self.charset_name, self.language, i)\n                self._state = ProbingState.NOT_ME\n                break\n            elif coding_state == MachineState.ITS_ME:\n                self._state = ProbingState.FOUND_IT\n                break\n            elif coding_state == MachineState.START:\n                char_len = self.coding_sm.get_current_charlen()\n                if i == 0:\n                    self._last_char[1] = byte_str[0]\n                    self.distribution_analyzer.feed(self._last_char, char_len)\n                else:\n                    self.distribution_analyzer.feed(byte_str[i - 1:i + 1],\n                                                    char_len)\n\n        self._last_char[0] = byte_str[-1]\n\n        if self.state == ProbingState.DETECTING:\n            if (self.distribution_analyzer.got_enough_data() and\n                    (self.get_confidence() > self.SHORTCUT_THRESHOLD)):\n                self._state = ProbingState.FOUND_IT\n\n        return self.state\n\n    def get_confidence(self):\n        return self.distribution_analyzer.get_confidence()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/mbcsgroupprober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Universal charset detector code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 2001\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#   Shy Shalom - original C code\n#   Proofpoint, Inc.\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .charsetgroupprober import CharSetGroupProber\nfrom .utf8prober import UTF8Prober\nfrom .sjisprober import SJISProber\nfrom .eucjpprober import EUCJPProber\nfrom .gb2312prober import GB2312Prober\nfrom .euckrprober import EUCKRProber\nfrom .cp949prober import CP949Prober\nfrom .big5prober import Big5Prober\nfrom .euctwprober import EUCTWProber\n\n\nclass MBCSGroupProber(CharSetGroupProber):\n    def __init__(self, lang_filter=None):\n        super(MBCSGroupProber, self).__init__(lang_filter=lang_filter)\n        self.probers = [\n            UTF8Prober(),\n            SJISProber(),\n            EUCJPProber(),\n            GB2312Prober(),\n            EUCKRProber(),\n            CP949Prober(),\n            Big5Prober(),\n            EUCTWProber()\n        ]\n        self.reset()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/mbcssm.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is mozilla.org code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .enums import MachineState\n\n# BIG5\n\nBIG5_CLS = (\n    1,1,1,1,1,1,1,1,  # 00 - 07    #allow 0x00 as legal value\n    1,1,1,1,1,1,0,0,  # 08 - 0f\n    1,1,1,1,1,1,1,1,  # 10 - 17\n    1,1,1,0,1,1,1,1,  # 18 - 1f\n    1,1,1,1,1,1,1,1,  # 20 - 27\n    1,1,1,1,1,1,1,1,  # 28 - 2f\n    1,1,1,1,1,1,1,1,  # 30 - 37\n    1,1,1,1,1,1,1,1,  # 38 - 3f\n    2,2,2,2,2,2,2,2,  # 40 - 47\n    2,2,2,2,2,2,2,2,  # 48 - 4f\n    2,2,2,2,2,2,2,2,  # 50 - 57\n    2,2,2,2,2,2,2,2,  # 58 - 5f\n    2,2,2,2,2,2,2,2,  # 60 - 67\n    2,2,2,2,2,2,2,2,  # 68 - 6f\n    2,2,2,2,2,2,2,2,  # 70 - 77\n    2,2,2,2,2,2,2,1,  # 78 - 7f\n    4,4,4,4,4,4,4,4,  # 80 - 87\n    4,4,4,4,4,4,4,4,  # 88 - 8f\n    4,4,4,4,4,4,4,4,  # 90 - 97\n    4,4,4,4,4,4,4,4,  # 98 - 9f\n    4,3,3,3,3,3,3,3,  # a0 - a7\n    3,3,3,3,3,3,3,3,  # a8 - af\n    3,3,3,3,3,3,3,3,  # b0 - b7\n    3,3,3,3,3,3,3,3,  # b8 - bf\n    3,3,3,3,3,3,3,3,  # c0 - c7\n    3,3,3,3,3,3,3,3,  # c8 - cf\n    3,3,3,3,3,3,3,3,  # d0 - d7\n    3,3,3,3,3,3,3,3,  # d8 - df\n    3,3,3,3,3,3,3,3,  # e0 - e7\n    3,3,3,3,3,3,3,3,  # e8 - ef\n    3,3,3,3,3,3,3,3,  # f0 - f7\n    3,3,3,3,3,3,3,0  # f8 - ff\n)\n\nBIG5_ST = (\n    MachineState.ERROR,MachineState.START,MachineState.START,     3,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#00-07\n    MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ERROR,#08-0f\n    MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START#10-17\n)\n\nBIG5_CHAR_LEN_TABLE = (0, 1, 1, 2, 0)\n\nBIG5_SM_MODEL = {'class_table': BIG5_CLS,\n                 'class_factor': 5,\n                 'state_table': BIG5_ST,\n                 'char_len_table': BIG5_CHAR_LEN_TABLE,\n                 'name': 'Big5'}\n\n# CP949\n\nCP949_CLS  = (\n    1,1,1,1,1,1,1,1, 1,1,1,1,1,1,0,0,  # 00 - 0f\n    1,1,1,1,1,1,1,1, 1,1,1,0,1,1,1,1,  # 10 - 1f\n    1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1,  # 20 - 2f\n    1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1,  # 30 - 3f\n    1,4,4,4,4,4,4,4, 4,4,4,4,4,4,4,4,  # 40 - 4f\n    4,4,5,5,5,5,5,5, 5,5,5,1,1,1,1,1,  # 50 - 5f\n    1,5,5,5,5,5,5,5, 5,5,5,5,5,5,5,5,  # 60 - 6f\n    5,5,5,5,5,5,5,5, 5,5,5,1,1,1,1,1,  # 70 - 7f\n    0,6,6,6,6,6,6,6, 6,6,6,6,6,6,6,6,  # 80 - 8f\n    6,6,6,6,6,6,6,6, 6,6,6,6,6,6,6,6,  # 90 - 9f\n    6,7,7,7,7,7,7,7, 7,7,7,7,7,8,8,8,  # a0 - af\n    7,7,7,7,7,7,7,7, 7,7,7,7,7,7,7,7,  # b0 - bf\n    7,7,7,7,7,7,9,2, 2,3,2,2,2,2,2,2,  # c0 - cf\n    2,2,2,2,2,2,2,2, 2,2,2,2,2,2,2,2,  # d0 - df\n    2,2,2,2,2,2,2,2, 2,2,2,2,2,2,2,2,  # e0 - ef\n    2,2,2,2,2,2,2,2, 2,2,2,2,2,2,2,0,  # f0 - ff\n)\n\nCP949_ST = (\n#cls=    0      1      2      3      4      5      6      7      8      9  # previous state =\n    MachineState.ERROR,MachineState.START,     3,MachineState.ERROR,MachineState.START,MachineState.START,     4,     5,MachineState.ERROR,     6, # MachineState.START\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR, # MachineState.ERROR\n    MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME, # MachineState.ITS_ME\n    MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START, # 3\n    MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START, # 4\n    MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START, # 5\n    MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START, # 6\n)\n\nCP949_CHAR_LEN_TABLE = (0, 1, 2, 0, 1, 1, 2, 2, 0, 2)\n\nCP949_SM_MODEL = {'class_table': CP949_CLS,\n                  'class_factor': 10,\n                  'state_table': CP949_ST,\n                  'char_len_table': CP949_CHAR_LEN_TABLE,\n                  'name': 'CP949'}\n\n# EUC-JP\n\nEUCJP_CLS = (\n    4,4,4,4,4,4,4,4,  # 00 - 07\n    4,4,4,4,4,4,5,5,  # 08 - 0f\n    4,4,4,4,4,4,4,4,  # 10 - 17\n    4,4,4,5,4,4,4,4,  # 18 - 1f\n    4,4,4,4,4,4,4,4,  # 20 - 27\n    4,4,4,4,4,4,4,4,  # 28 - 2f\n    4,4,4,4,4,4,4,4,  # 30 - 37\n    4,4,4,4,4,4,4,4,  # 38 - 3f\n    4,4,4,4,4,4,4,4,  # 40 - 47\n    4,4,4,4,4,4,4,4,  # 48 - 4f\n    4,4,4,4,4,4,4,4,  # 50 - 57\n    4,4,4,4,4,4,4,4,  # 58 - 5f\n    4,4,4,4,4,4,4,4,  # 60 - 67\n    4,4,4,4,4,4,4,4,  # 68 - 6f\n    4,4,4,4,4,4,4,4,  # 70 - 77\n    4,4,4,4,4,4,4,4,  # 78 - 7f\n    5,5,5,5,5,5,5,5,  # 80 - 87\n    5,5,5,5,5,5,1,3,  # 88 - 8f\n    5,5,5,5,5,5,5,5,  # 90 - 97\n    5,5,5,5,5,5,5,5,  # 98 - 9f\n    5,2,2,2,2,2,2,2,  # a0 - a7\n    2,2,2,2,2,2,2,2,  # a8 - af\n    2,2,2,2,2,2,2,2,  # b0 - b7\n    2,2,2,2,2,2,2,2,  # b8 - bf\n    2,2,2,2,2,2,2,2,  # c0 - c7\n    2,2,2,2,2,2,2,2,  # c8 - cf\n    2,2,2,2,2,2,2,2,  # d0 - d7\n    2,2,2,2,2,2,2,2,  # d8 - df\n    0,0,0,0,0,0,0,0,  # e0 - e7\n    0,0,0,0,0,0,0,0,  # e8 - ef\n    0,0,0,0,0,0,0,0,  # f0 - f7\n    0,0,0,0,0,0,0,5  # f8 - ff\n)\n\nEUCJP_ST = (\n          3,     4,     3,     5,MachineState.START,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#00-07\n     MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,#08-0f\n     MachineState.ITS_ME,MachineState.ITS_ME,MachineState.START,MachineState.ERROR,MachineState.START,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#10-17\n     MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,     3,MachineState.ERROR,#18-1f\n          3,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.START#20-27\n)\n\nEUCJP_CHAR_LEN_TABLE = (2, 2, 2, 3, 1, 0)\n\nEUCJP_SM_MODEL = {'class_table': EUCJP_CLS,\n                  'class_factor': 6,\n                  'state_table': EUCJP_ST,\n                  'char_len_table': EUCJP_CHAR_LEN_TABLE,\n                  'name': 'EUC-JP'}\n\n# EUC-KR\n\nEUCKR_CLS  = (\n    1,1,1,1,1,1,1,1,  # 00 - 07\n    1,1,1,1,1,1,0,0,  # 08 - 0f\n    1,1,1,1,1,1,1,1,  # 10 - 17\n    1,1,1,0,1,1,1,1,  # 18 - 1f\n    1,1,1,1,1,1,1,1,  # 20 - 27\n    1,1,1,1,1,1,1,1,  # 28 - 2f\n    1,1,1,1,1,1,1,1,  # 30 - 37\n    1,1,1,1,1,1,1,1,  # 38 - 3f\n    1,1,1,1,1,1,1,1,  # 40 - 47\n    1,1,1,1,1,1,1,1,  # 48 - 4f\n    1,1,1,1,1,1,1,1,  # 50 - 57\n    1,1,1,1,1,1,1,1,  # 58 - 5f\n    1,1,1,1,1,1,1,1,  # 60 - 67\n    1,1,1,1,1,1,1,1,  # 68 - 6f\n    1,1,1,1,1,1,1,1,  # 70 - 77\n    1,1,1,1,1,1,1,1,  # 78 - 7f\n    0,0,0,0,0,0,0,0,  # 80 - 87\n    0,0,0,0,0,0,0,0,  # 88 - 8f\n    0,0,0,0,0,0,0,0,  # 90 - 97\n    0,0,0,0,0,0,0,0,  # 98 - 9f\n    0,2,2,2,2,2,2,2,  # a0 - a7\n    2,2,2,2,2,3,3,3,  # a8 - af\n    2,2,2,2,2,2,2,2,  # b0 - b7\n    2,2,2,2,2,2,2,2,  # b8 - bf\n    2,2,2,2,2,2,2,2,  # c0 - c7\n    2,3,2,2,2,2,2,2,  # c8 - cf\n    2,2,2,2,2,2,2,2,  # d0 - d7\n    2,2,2,2,2,2,2,2,  # d8 - df\n    2,2,2,2,2,2,2,2,  # e0 - e7\n    2,2,2,2,2,2,2,2,  # e8 - ef\n    2,2,2,2,2,2,2,2,  # f0 - f7\n    2,2,2,2,2,2,2,0   # f8 - ff\n)\n\nEUCKR_ST = (\n    MachineState.ERROR,MachineState.START,     3,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#00-07\n    MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.START #08-0f\n)\n\nEUCKR_CHAR_LEN_TABLE = (0, 1, 2, 0)\n\nEUCKR_SM_MODEL = {'class_table': EUCKR_CLS,\n                'class_factor': 4,\n                'state_table': EUCKR_ST,\n                'char_len_table': EUCKR_CHAR_LEN_TABLE,\n                'name': 'EUC-KR'}\n\n# EUC-TW\n\nEUCTW_CLS = (\n    2,2,2,2,2,2,2,2,  # 00 - 07\n    2,2,2,2,2,2,0,0,  # 08 - 0f\n    2,2,2,2,2,2,2,2,  # 10 - 17\n    2,2,2,0,2,2,2,2,  # 18 - 1f\n    2,2,2,2,2,2,2,2,  # 20 - 27\n    2,2,2,2,2,2,2,2,  # 28 - 2f\n    2,2,2,2,2,2,2,2,  # 30 - 37\n    2,2,2,2,2,2,2,2,  # 38 - 3f\n    2,2,2,2,2,2,2,2,  # 40 - 47\n    2,2,2,2,2,2,2,2,  # 48 - 4f\n    2,2,2,2,2,2,2,2,  # 50 - 57\n    2,2,2,2,2,2,2,2,  # 58 - 5f\n    2,2,2,2,2,2,2,2,  # 60 - 67\n    2,2,2,2,2,2,2,2,  # 68 - 6f\n    2,2,2,2,2,2,2,2,  # 70 - 77\n    2,2,2,2,2,2,2,2,  # 78 - 7f\n    0,0,0,0,0,0,0,0,  # 80 - 87\n    0,0,0,0,0,0,6,0,  # 88 - 8f\n    0,0,0,0,0,0,0,0,  # 90 - 97\n    0,0,0,0,0,0,0,0,  # 98 - 9f\n    0,3,4,4,4,4,4,4,  # a0 - a7\n    5,5,1,1,1,1,1,1,  # a8 - af\n    1,1,1,1,1,1,1,1,  # b0 - b7\n    1,1,1,1,1,1,1,1,  # b8 - bf\n    1,1,3,1,3,3,3,3,  # c0 - c7\n    3,3,3,3,3,3,3,3,  # c8 - cf\n    3,3,3,3,3,3,3,3,  # d0 - d7\n    3,3,3,3,3,3,3,3,  # d8 - df\n    3,3,3,3,3,3,3,3,  # e0 - e7\n    3,3,3,3,3,3,3,3,  # e8 - ef\n    3,3,3,3,3,3,3,3,  # f0 - f7\n    3,3,3,3,3,3,3,0   # f8 - ff\n)\n\nEUCTW_ST = (\n    MachineState.ERROR,MachineState.ERROR,MachineState.START,     3,     3,     3,     4,MachineState.ERROR,#00-07\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ITS_ME,#08-0f\n    MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ERROR,MachineState.START,MachineState.ERROR,#10-17\n    MachineState.START,MachineState.START,MachineState.START,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#18-1f\n         5,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.ERROR,MachineState.START,MachineState.START,#20-27\n    MachineState.START,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START #28-2f\n)\n\nEUCTW_CHAR_LEN_TABLE = (0, 0, 1, 2, 2, 2, 3)\n\nEUCTW_SM_MODEL = {'class_table': EUCTW_CLS,\n                'class_factor': 7,\n                'state_table': EUCTW_ST,\n                'char_len_table': EUCTW_CHAR_LEN_TABLE,\n                'name': 'x-euc-tw'}\n\n# GB2312\n\nGB2312_CLS = (\n    1,1,1,1,1,1,1,1,  # 00 - 07\n    1,1,1,1,1,1,0,0,  # 08 - 0f\n    1,1,1,1,1,1,1,1,  # 10 - 17\n    1,1,1,0,1,1,1,1,  # 18 - 1f\n    1,1,1,1,1,1,1,1,  # 20 - 27\n    1,1,1,1,1,1,1,1,  # 28 - 2f\n    3,3,3,3,3,3,3,3,  # 30 - 37\n    3,3,1,1,1,1,1,1,  # 38 - 3f\n    2,2,2,2,2,2,2,2,  # 40 - 47\n    2,2,2,2,2,2,2,2,  # 48 - 4f\n    2,2,2,2,2,2,2,2,  # 50 - 57\n    2,2,2,2,2,2,2,2,  # 58 - 5f\n    2,2,2,2,2,2,2,2,  # 60 - 67\n    2,2,2,2,2,2,2,2,  # 68 - 6f\n    2,2,2,2,2,2,2,2,  # 70 - 77\n    2,2,2,2,2,2,2,4,  # 78 - 7f\n    5,6,6,6,6,6,6,6,  # 80 - 87\n    6,6,6,6,6,6,6,6,  # 88 - 8f\n    6,6,6,6,6,6,6,6,  # 90 - 97\n    6,6,6,6,6,6,6,6,  # 98 - 9f\n    6,6,6,6,6,6,6,6,  # a0 - a7\n    6,6,6,6,6,6,6,6,  # a8 - af\n    6,6,6,6,6,6,6,6,  # b0 - b7\n    6,6,6,6,6,6,6,6,  # b8 - bf\n    6,6,6,6,6,6,6,6,  # c0 - c7\n    6,6,6,6,6,6,6,6,  # c8 - cf\n    6,6,6,6,6,6,6,6,  # d0 - d7\n    6,6,6,6,6,6,6,6,  # d8 - df\n    6,6,6,6,6,6,6,6,  # e0 - e7\n    6,6,6,6,6,6,6,6,  # e8 - ef\n    6,6,6,6,6,6,6,6,  # f0 - f7\n    6,6,6,6,6,6,6,0   # f8 - ff\n)\n\nGB2312_ST = (\n    MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,     3,MachineState.ERROR,#00-07\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ITS_ME,#08-0f\n    MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ERROR,MachineState.ERROR,MachineState.START,#10-17\n         4,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#18-1f\n    MachineState.ERROR,MachineState.ERROR,     5,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ERROR,#20-27\n    MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.START #28-2f\n)\n\n# To be accurate, the length of class 6 can be either 2 or 4.\n# But it is not necessary to discriminate between the two since\n# it is used for frequency analysis only, and we are validating\n# each code range there as well. So it is safe to set it to be\n# 2 here.\nGB2312_CHAR_LEN_TABLE = (0, 1, 1, 1, 1, 1, 2)\n\nGB2312_SM_MODEL = {'class_table': GB2312_CLS,\n                   'class_factor': 7,\n                   'state_table': GB2312_ST,\n                   'char_len_table': GB2312_CHAR_LEN_TABLE,\n                   'name': 'GB2312'}\n\n# Shift_JIS\n\nSJIS_CLS = (\n    1,1,1,1,1,1,1,1,  # 00 - 07\n    1,1,1,1,1,1,0,0,  # 08 - 0f\n    1,1,1,1,1,1,1,1,  # 10 - 17\n    1,1,1,0,1,1,1,1,  # 18 - 1f\n    1,1,1,1,1,1,1,1,  # 20 - 27\n    1,1,1,1,1,1,1,1,  # 28 - 2f\n    1,1,1,1,1,1,1,1,  # 30 - 37\n    1,1,1,1,1,1,1,1,  # 38 - 3f\n    2,2,2,2,2,2,2,2,  # 40 - 47\n    2,2,2,2,2,2,2,2,  # 48 - 4f\n    2,2,2,2,2,2,2,2,  # 50 - 57\n    2,2,2,2,2,2,2,2,  # 58 - 5f\n    2,2,2,2,2,2,2,2,  # 60 - 67\n    2,2,2,2,2,2,2,2,  # 68 - 6f\n    2,2,2,2,2,2,2,2,  # 70 - 77\n    2,2,2,2,2,2,2,1,  # 78 - 7f\n    3,3,3,3,3,2,2,3,  # 80 - 87\n    3,3,3,3,3,3,3,3,  # 88 - 8f\n    3,3,3,3,3,3,3,3,  # 90 - 97\n    3,3,3,3,3,3,3,3,  # 98 - 9f\n    #0xa0 is illegal in sjis encoding, but some pages does\n    #contain such byte. We need to be more error forgiven.\n    2,2,2,2,2,2,2,2,  # a0 - a7\n    2,2,2,2,2,2,2,2,  # a8 - af\n    2,2,2,2,2,2,2,2,  # b0 - b7\n    2,2,2,2,2,2,2,2,  # b8 - bf\n    2,2,2,2,2,2,2,2,  # c0 - c7\n    2,2,2,2,2,2,2,2,  # c8 - cf\n    2,2,2,2,2,2,2,2,  # d0 - d7\n    2,2,2,2,2,2,2,2,  # d8 - df\n    3,3,3,3,3,3,3,3,  # e0 - e7\n    3,3,3,3,3,4,4,4,  # e8 - ef\n    3,3,3,3,3,3,3,3,  # f0 - f7\n    3,3,3,3,3,0,0,0)  # f8 - ff\n\n\nSJIS_ST = (\n    MachineState.ERROR,MachineState.START,MachineState.START,     3,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#00-07\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,#08-0f\n    MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.START #10-17\n)\n\nSJIS_CHAR_LEN_TABLE = (0, 1, 1, 2, 0, 0)\n\nSJIS_SM_MODEL = {'class_table': SJIS_CLS,\n               'class_factor': 6,\n               'state_table': SJIS_ST,\n               'char_len_table': SJIS_CHAR_LEN_TABLE,\n               'name': 'Shift_JIS'}\n\n# UCS2-BE\n\nUCS2BE_CLS = (\n    0,0,0,0,0,0,0,0,  # 00 - 07\n    0,0,1,0,0,2,0,0,  # 08 - 0f\n    0,0,0,0,0,0,0,0,  # 10 - 17\n    0,0,0,3,0,0,0,0,  # 18 - 1f\n    0,0,0,0,0,0,0,0,  # 20 - 27\n    0,3,3,3,3,3,0,0,  # 28 - 2f\n    0,0,0,0,0,0,0,0,  # 30 - 37\n    0,0,0,0,0,0,0,0,  # 38 - 3f\n    0,0,0,0,0,0,0,0,  # 40 - 47\n    0,0,0,0,0,0,0,0,  # 48 - 4f\n    0,0,0,0,0,0,0,0,  # 50 - 57\n    0,0,0,0,0,0,0,0,  # 58 - 5f\n    0,0,0,0,0,0,0,0,  # 60 - 67\n    0,0,0,0,0,0,0,0,  # 68 - 6f\n    0,0,0,0,0,0,0,0,  # 70 - 77\n    0,0,0,0,0,0,0,0,  # 78 - 7f\n    0,0,0,0,0,0,0,0,  # 80 - 87\n    0,0,0,0,0,0,0,0,  # 88 - 8f\n    0,0,0,0,0,0,0,0,  # 90 - 97\n    0,0,0,0,0,0,0,0,  # 98 - 9f\n    0,0,0,0,0,0,0,0,  # a0 - a7\n    0,0,0,0,0,0,0,0,  # a8 - af\n    0,0,0,0,0,0,0,0,  # b0 - b7\n    0,0,0,0,0,0,0,0,  # b8 - bf\n    0,0,0,0,0,0,0,0,  # c0 - c7\n    0,0,0,0,0,0,0,0,  # c8 - cf\n    0,0,0,0,0,0,0,0,  # d0 - d7\n    0,0,0,0,0,0,0,0,  # d8 - df\n    0,0,0,0,0,0,0,0,  # e0 - e7\n    0,0,0,0,0,0,0,0,  # e8 - ef\n    0,0,0,0,0,0,0,0,  # f0 - f7\n    0,0,0,0,0,0,4,5   # f8 - ff\n)\n\nUCS2BE_ST  = (\n          5,     7,     7,MachineState.ERROR,     4,     3,MachineState.ERROR,MachineState.ERROR,#00-07\n     MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,#08-0f\n     MachineState.ITS_ME,MachineState.ITS_ME,     6,     6,     6,     6,MachineState.ERROR,MachineState.ERROR,#10-17\n          6,     6,     6,     6,     6,MachineState.ITS_ME,     6,     6,#18-1f\n          6,     6,     6,     6,     5,     7,     7,MachineState.ERROR,#20-27\n          5,     8,     6,     6,MachineState.ERROR,     6,     6,     6,#28-2f\n          6,     6,     6,     6,MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.START #30-37\n)\n\nUCS2BE_CHAR_LEN_TABLE = (2, 2, 2, 0, 2, 2)\n\nUCS2BE_SM_MODEL = {'class_table': UCS2BE_CLS,\n                   'class_factor': 6,\n                   'state_table': UCS2BE_ST,\n                   'char_len_table': UCS2BE_CHAR_LEN_TABLE,\n                   'name': 'UTF-16BE'}\n\n# UCS2-LE\n\nUCS2LE_CLS = (\n    0,0,0,0,0,0,0,0,  # 00 - 07\n    0,0,1,0,0,2,0,0,  # 08 - 0f\n    0,0,0,0,0,0,0,0,  # 10 - 17\n    0,0,0,3,0,0,0,0,  # 18 - 1f\n    0,0,0,0,0,0,0,0,  # 20 - 27\n    0,3,3,3,3,3,0,0,  # 28 - 2f\n    0,0,0,0,0,0,0,0,  # 30 - 37\n    0,0,0,0,0,0,0,0,  # 38 - 3f\n    0,0,0,0,0,0,0,0,  # 40 - 47\n    0,0,0,0,0,0,0,0,  # 48 - 4f\n    0,0,0,0,0,0,0,0,  # 50 - 57\n    0,0,0,0,0,0,0,0,  # 58 - 5f\n    0,0,0,0,0,0,0,0,  # 60 - 67\n    0,0,0,0,0,0,0,0,  # 68 - 6f\n    0,0,0,0,0,0,0,0,  # 70 - 77\n    0,0,0,0,0,0,0,0,  # 78 - 7f\n    0,0,0,0,0,0,0,0,  # 80 - 87\n    0,0,0,0,0,0,0,0,  # 88 - 8f\n    0,0,0,0,0,0,0,0,  # 90 - 97\n    0,0,0,0,0,0,0,0,  # 98 - 9f\n    0,0,0,0,0,0,0,0,  # a0 - a7\n    0,0,0,0,0,0,0,0,  # a8 - af\n    0,0,0,0,0,0,0,0,  # b0 - b7\n    0,0,0,0,0,0,0,0,  # b8 - bf\n    0,0,0,0,0,0,0,0,  # c0 - c7\n    0,0,0,0,0,0,0,0,  # c8 - cf\n    0,0,0,0,0,0,0,0,  # d0 - d7\n    0,0,0,0,0,0,0,0,  # d8 - df\n    0,0,0,0,0,0,0,0,  # e0 - e7\n    0,0,0,0,0,0,0,0,  # e8 - ef\n    0,0,0,0,0,0,0,0,  # f0 - f7\n    0,0,0,0,0,0,4,5   # f8 - ff\n)\n\nUCS2LE_ST = (\n          6,     6,     7,     6,     4,     3,MachineState.ERROR,MachineState.ERROR,#00-07\n     MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,#08-0f\n     MachineState.ITS_ME,MachineState.ITS_ME,     5,     5,     5,MachineState.ERROR,MachineState.ITS_ME,MachineState.ERROR,#10-17\n          5,     5,     5,MachineState.ERROR,     5,MachineState.ERROR,     6,     6,#18-1f\n          7,     6,     8,     8,     5,     5,     5,MachineState.ERROR,#20-27\n          5,     5,     5,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,     5,     5,#28-2f\n          5,     5,     5,MachineState.ERROR,     5,MachineState.ERROR,MachineState.START,MachineState.START #30-37\n)\n\nUCS2LE_CHAR_LEN_TABLE = (2, 2, 2, 2, 2, 2)\n\nUCS2LE_SM_MODEL = {'class_table': UCS2LE_CLS,\n                 'class_factor': 6,\n                 'state_table': UCS2LE_ST,\n                 'char_len_table': UCS2LE_CHAR_LEN_TABLE,\n                 'name': 'UTF-16LE'}\n\n# UTF-8\n\nUTF8_CLS = (\n    1,1,1,1,1,1,1,1,  # 00 - 07  #allow 0x00 as a legal value\n    1,1,1,1,1,1,0,0,  # 08 - 0f\n    1,1,1,1,1,1,1,1,  # 10 - 17\n    1,1,1,0,1,1,1,1,  # 18 - 1f\n    1,1,1,1,1,1,1,1,  # 20 - 27\n    1,1,1,1,1,1,1,1,  # 28 - 2f\n    1,1,1,1,1,1,1,1,  # 30 - 37\n    1,1,1,1,1,1,1,1,  # 38 - 3f\n    1,1,1,1,1,1,1,1,  # 40 - 47\n    1,1,1,1,1,1,1,1,  # 48 - 4f\n    1,1,1,1,1,1,1,1,  # 50 - 57\n    1,1,1,1,1,1,1,1,  # 58 - 5f\n    1,1,1,1,1,1,1,1,  # 60 - 67\n    1,1,1,1,1,1,1,1,  # 68 - 6f\n    1,1,1,1,1,1,1,1,  # 70 - 77\n    1,1,1,1,1,1,1,1,  # 78 - 7f\n    2,2,2,2,3,3,3,3,  # 80 - 87\n    4,4,4,4,4,4,4,4,  # 88 - 8f\n    4,4,4,4,4,4,4,4,  # 90 - 97\n    4,4,4,4,4,4,4,4,  # 98 - 9f\n    5,5,5,5,5,5,5,5,  # a0 - a7\n    5,5,5,5,5,5,5,5,  # a8 - af\n    5,5,5,5,5,5,5,5,  # b0 - b7\n    5,5,5,5,5,5,5,5,  # b8 - bf\n    0,0,6,6,6,6,6,6,  # c0 - c7\n    6,6,6,6,6,6,6,6,  # c8 - cf\n    6,6,6,6,6,6,6,6,  # d0 - d7\n    6,6,6,6,6,6,6,6,  # d8 - df\n    7,8,8,8,8,8,8,8,  # e0 - e7\n    8,8,8,8,8,9,8,8,  # e8 - ef\n    10,11,11,11,11,11,11,11,  # f0 - f7\n    12,13,13,13,14,15,0,0    # f8 - ff\n)\n\nUTF8_ST = (\n    MachineState.ERROR,MachineState.START,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,     12,   10,#00-07\n         9,     11,     8,     7,     6,     5,     4,    3,#08-0f\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#10-17\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#18-1f\n    MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,#20-27\n    MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,MachineState.ITS_ME,#28-2f\n    MachineState.ERROR,MachineState.ERROR,     5,     5,     5,     5,MachineState.ERROR,MachineState.ERROR,#30-37\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#38-3f\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,     5,     5,     5,MachineState.ERROR,MachineState.ERROR,#40-47\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#48-4f\n    MachineState.ERROR,MachineState.ERROR,     7,     7,     7,     7,MachineState.ERROR,MachineState.ERROR,#50-57\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#58-5f\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,     7,     7,MachineState.ERROR,MachineState.ERROR,#60-67\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#68-6f\n    MachineState.ERROR,MachineState.ERROR,     9,     9,     9,     9,MachineState.ERROR,MachineState.ERROR,#70-77\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#78-7f\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,     9,MachineState.ERROR,MachineState.ERROR,#80-87\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#88-8f\n    MachineState.ERROR,MachineState.ERROR,    12,    12,    12,    12,MachineState.ERROR,MachineState.ERROR,#90-97\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#98-9f\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,    12,MachineState.ERROR,MachineState.ERROR,#a0-a7\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#a8-af\n    MachineState.ERROR,MachineState.ERROR,    12,    12,    12,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#b0-b7\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,#b8-bf\n    MachineState.ERROR,MachineState.ERROR,MachineState.START,MachineState.START,MachineState.START,MachineState.START,MachineState.ERROR,MachineState.ERROR,#c0-c7\n    MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR,MachineState.ERROR #c8-cf\n)\n\nUTF8_CHAR_LEN_TABLE = (0, 1, 0, 0, 0, 0, 2, 3, 3, 3, 4, 4, 5, 5, 6, 6)\n\nUTF8_SM_MODEL = {'class_table': UTF8_CLS,\n                 'class_factor': 16,\n                 'state_table': UTF8_ST,\n                 'char_len_table': UTF8_CHAR_LEN_TABLE,\n                 'name': 'UTF-8'}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/sbcharsetprober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Universal charset detector code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 2001\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#   Shy Shalom - original C code\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .charsetprober import CharSetProber\nfrom .enums import CharacterCategory, ProbingState, SequenceLikelihood\n\n\nclass SingleByteCharSetProber(CharSetProber):\n    SAMPLE_SIZE = 64\n    SB_ENOUGH_REL_THRESHOLD = 1024  #  0.25 * SAMPLE_SIZE^2\n    POSITIVE_SHORTCUT_THRESHOLD = 0.95\n    NEGATIVE_SHORTCUT_THRESHOLD = 0.05\n\n    def __init__(self, model, reversed=False, name_prober=None):\n        super(SingleByteCharSetProber, self).__init__()\n        self._model = model\n        # TRUE if we need to reverse every pair in the model lookup\n        self._reversed = reversed\n        # Optional auxiliary prober for name decision\n        self._name_prober = name_prober\n        self._last_order = None\n        self._seq_counters = None\n        self._total_seqs = None\n        self._total_char = None\n        self._freq_char = None\n        self.reset()\n\n    def reset(self):\n        super(SingleByteCharSetProber, self).reset()\n        # char order of last character\n        self._last_order = 255\n        self._seq_counters = [0] * SequenceLikelihood.get_num_categories()\n        self._total_seqs = 0\n        self._total_char = 0\n        # characters that fall in our sampling range\n        self._freq_char = 0\n\n    @property\n    def charset_name(self):\n        if self._name_prober:\n            return self._name_prober.charset_name\n        else:\n            return self._model['charset_name']\n\n    @property\n    def language(self):\n        if self._name_prober:\n            return self._name_prober.language\n        else:\n            return self._model.get('language')\n\n    def feed(self, byte_str):\n        if not self._model['keep_english_letter']:\n            byte_str = self.filter_international_words(byte_str)\n        if not byte_str:\n            return self.state\n        char_to_order_map = self._model['char_to_order_map']\n        for i, c in enumerate(byte_str):\n            # XXX: Order is in range 1-64, so one would think we want 0-63 here,\n            #      but that leads to 27 more test failures than before.\n            order = char_to_order_map[c]\n            # XXX: This was SYMBOL_CAT_ORDER before, with a value of 250, but\n            #      CharacterCategory.SYMBOL is actually 253, so we use CONTROL\n            #      to make it closer to the original intent. The only difference\n            #      is whether or not we count digits and control characters for\n            #      _total_char purposes.\n            if order < CharacterCategory.CONTROL:\n                self._total_char += 1\n            if order < self.SAMPLE_SIZE:\n                self._freq_char += 1\n                if self._last_order < self.SAMPLE_SIZE:\n                    self._total_seqs += 1\n                    if not self._reversed:\n                        i = (self._last_order * self.SAMPLE_SIZE) + order\n                        model = self._model['precedence_matrix'][i]\n                    else:  # reverse the order of the letters in the lookup\n                        i = (order * self.SAMPLE_SIZE) + self._last_order\n                        model = self._model['precedence_matrix'][i]\n                    self._seq_counters[model] += 1\n            self._last_order = order\n\n        charset_name = self._model['charset_name']\n        if self.state == ProbingState.DETECTING:\n            if self._total_seqs > self.SB_ENOUGH_REL_THRESHOLD:\n                confidence = self.get_confidence()\n                if confidence > self.POSITIVE_SHORTCUT_THRESHOLD:\n                    self.logger.debug('%s confidence = %s, we have a winner',\n                                      charset_name, confidence)\n                    self._state = ProbingState.FOUND_IT\n                elif confidence < self.NEGATIVE_SHORTCUT_THRESHOLD:\n                    self.logger.debug('%s confidence = %s, below negative '\n                                      'shortcut threshhold %s', charset_name,\n                                      confidence,\n                                      self.NEGATIVE_SHORTCUT_THRESHOLD)\n                    self._state = ProbingState.NOT_ME\n\n        return self.state\n\n    def get_confidence(self):\n        r = 0.01\n        if self._total_seqs > 0:\n            r = ((1.0 * self._seq_counters[SequenceLikelihood.POSITIVE]) /\n                 self._total_seqs / self._model['typical_positive_ratio'])\n            r = r * self._freq_char / self._total_char\n            if r >= 1.0:\n                r = 0.99\n        return r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/sbcsgroupprober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Universal charset detector code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 2001\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#   Shy Shalom - original C code\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .charsetgroupprober import CharSetGroupProber\nfrom .sbcharsetprober import SingleByteCharSetProber\nfrom .langcyrillicmodel import (Win1251CyrillicModel, Koi8rModel,\n                                Latin5CyrillicModel, MacCyrillicModel,\n                                Ibm866Model, Ibm855Model)\nfrom .langgreekmodel import Latin7GreekModel, Win1253GreekModel\nfrom .langbulgarianmodel import Latin5BulgarianModel, Win1251BulgarianModel\n# from .langhungarianmodel import Latin2HungarianModel, Win1250HungarianModel\nfrom .langthaimodel import TIS620ThaiModel\nfrom .langhebrewmodel import Win1255HebrewModel\nfrom .hebrewprober import HebrewProber\nfrom .langturkishmodel import Latin5TurkishModel\n\n\nclass SBCSGroupProber(CharSetGroupProber):\n    def __init__(self):\n        super(SBCSGroupProber, self).__init__()\n        self.probers = [\n            SingleByteCharSetProber(Win1251CyrillicModel),\n            SingleByteCharSetProber(Koi8rModel),\n            SingleByteCharSetProber(Latin5CyrillicModel),\n            SingleByteCharSetProber(MacCyrillicModel),\n            SingleByteCharSetProber(Ibm866Model),\n            SingleByteCharSetProber(Ibm855Model),\n            SingleByteCharSetProber(Latin7GreekModel),\n            SingleByteCharSetProber(Win1253GreekModel),\n            SingleByteCharSetProber(Latin5BulgarianModel),\n            SingleByteCharSetProber(Win1251BulgarianModel),\n            # TODO: Restore Hungarian encodings (iso-8859-2 and windows-1250)\n            #       after we retrain model.\n            # SingleByteCharSetProber(Latin2HungarianModel),\n            # SingleByteCharSetProber(Win1250HungarianModel),\n            SingleByteCharSetProber(TIS620ThaiModel),\n            SingleByteCharSetProber(Latin5TurkishModel),\n        ]\n        hebrew_prober = HebrewProber()\n        logical_hebrew_prober = SingleByteCharSetProber(Win1255HebrewModel,\n                                                        False, hebrew_prober)\n        visual_hebrew_prober = SingleByteCharSetProber(Win1255HebrewModel, True,\n                                                       hebrew_prober)\n        hebrew_prober.set_model_probers(logical_hebrew_prober, visual_hebrew_prober)\n        self.probers.extend([hebrew_prober, logical_hebrew_prober,\n                             visual_hebrew_prober])\n\n        self.reset()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/sjisprober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is mozilla.org code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .mbcharsetprober import MultiByteCharSetProber\nfrom .codingstatemachine import CodingStateMachine\nfrom .chardistribution import SJISDistributionAnalysis\nfrom .jpcntx import SJISContextAnalysis\nfrom .mbcssm import SJIS_SM_MODEL\nfrom .enums import ProbingState, MachineState\n\n\nclass SJISProber(MultiByteCharSetProber):\n    def __init__(self):\n        super(SJISProber, self).__init__()\n        self.coding_sm = CodingStateMachine(SJIS_SM_MODEL)\n        self.distribution_analyzer = SJISDistributionAnalysis()\n        self.context_analyzer = SJISContextAnalysis()\n        self.reset()\n\n    def reset(self):\n        super(SJISProber, self).reset()\n        self.context_analyzer.reset()\n\n    @property\n    def charset_name(self):\n        return self.context_analyzer.charset_name\n\n    @property\n    def language(self):\n        return \"Japanese\"\n\n    def feed(self, byte_str):\n        for i in range(len(byte_str)):\n            coding_state = self.coding_sm.next_state(byte_str[i])\n            if coding_state == MachineState.ERROR:\n                self.logger.debug('%s %s prober hit error at byte %s',\n                                  self.charset_name, self.language, i)\n                self._state = ProbingState.NOT_ME\n                break\n            elif coding_state == MachineState.ITS_ME:\n                self._state = ProbingState.FOUND_IT\n                break\n            elif coding_state == MachineState.START:\n                char_len = self.coding_sm.get_current_charlen()\n                if i == 0:\n                    self._last_char[1] = byte_str[0]\n                    self.context_analyzer.feed(self._last_char[2 - char_len:],\n                                               char_len)\n                    self.distribution_analyzer.feed(self._last_char, char_len)\n                else:\n                    self.context_analyzer.feed(byte_str[i + 1 - char_len:i + 3\n                                                        - char_len], char_len)\n                    self.distribution_analyzer.feed(byte_str[i - 1:i + 1],\n                                                    char_len)\n\n        self._last_char[0] = byte_str[-1]\n\n        if self.state == ProbingState.DETECTING:\n            if (self.context_analyzer.got_enough_data() and\n               (self.get_confidence() > self.SHORTCUT_THRESHOLD)):\n                self._state = ProbingState.FOUND_IT\n\n        return self.state\n\n    def get_confidence(self):\n        context_conf = self.context_analyzer.get_confidence()\n        distrib_conf = self.distribution_analyzer.get_confidence()\n        return max(context_conf, distrib_conf)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/universaldetector.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is Mozilla Universal charset detector code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 2001\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#   Shy Shalom - original C code\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\"\"\"\nModule containing the UniversalDetector detector class, which is the primary\nclass a user of ``chardet`` should use.\n\n:author: Mark Pilgrim (initial port to Python)\n:author: Shy Shalom (original C code)\n:author: Dan Blanchard (major refactoring for 3.0)\n:author: Ian Cordasco\n\"\"\"\n\n\nimport codecs\nimport logging\nimport re\n\nfrom .charsetgroupprober import CharSetGroupProber\nfrom .enums import InputState, LanguageFilter, ProbingState\nfrom .escprober import EscCharSetProber\nfrom .latin1prober import Latin1Prober\nfrom .mbcsgroupprober import MBCSGroupProber\nfrom .sbcsgroupprober import SBCSGroupProber\n\n\nclass UniversalDetector(object):\n    \"\"\"\n    The ``UniversalDetector`` class underlies the ``chardet.detect`` function\n    and coordinates all of the different charset probers.\n\n    To get a ``dict`` containing an encoding and its confidence, you can simply\n    run:\n\n    .. code::\n\n            u = UniversalDetector()\n            u.feed(some_bytes)\n            u.close()\n            detected = u.result\n\n    \"\"\"\n\n    MINIMUM_THRESHOLD = 0.20\n    HIGH_BYTE_DETECTOR = re.compile(b'[\\x80-\\xFF]')\n    ESC_DETECTOR = re.compile(b'(\\033|~{)')\n    WIN_BYTE_DETECTOR = re.compile(b'[\\x80-\\x9F]')\n    ISO_WIN_MAP = {'iso-8859-1': 'Windows-1252',\n                   'iso-8859-2': 'Windows-1250',\n                   'iso-8859-5': 'Windows-1251',\n                   'iso-8859-6': 'Windows-1256',\n                   'iso-8859-7': 'Windows-1253',\n                   'iso-8859-8': 'Windows-1255',\n                   'iso-8859-9': 'Windows-1254',\n                   'iso-8859-13': 'Windows-1257'}\n\n    def __init__(self, lang_filter=LanguageFilter.ALL):\n        self._esc_charset_prober = None\n        self._charset_probers = []\n        self.result = None\n        self.done = None\n        self._got_data = None\n        self._input_state = None\n        self._last_char = None\n        self.lang_filter = lang_filter\n        self.logger = logging.getLogger(__name__)\n        self._has_win_bytes = None\n        self.reset()\n\n    def reset(self):\n        \"\"\"\n        Reset the UniversalDetector and all of its probers back to their\n        initial states.  This is called by ``__init__``, so you only need to\n        call this directly in between analyses of different documents.\n        \"\"\"\n        self.result = {'encoding': None, 'confidence': 0.0, 'language': None}\n        self.done = False\n        self._got_data = False\n        self._has_win_bytes = False\n        self._input_state = InputState.PURE_ASCII\n        self._last_char = b''\n        if self._esc_charset_prober:\n            self._esc_charset_prober.reset()\n        for prober in self._charset_probers:\n            prober.reset()\n\n    def feed(self, byte_str):\n        \"\"\"\n        Takes a chunk of a document and feeds it through all of the relevant\n        charset probers.\n\n        After calling ``feed``, you can check the value of the ``done``\n        attribute to see if you need to continue feeding the\n        ``UniversalDetector`` more data, or if it has made a prediction\n        (in the ``result`` attribute).\n\n        .. note::\n           You should always call ``close`` when you're done feeding in your\n           document if ``done`` is not already ``True``.\n        \"\"\"\n        if self.done:\n            return\n\n        if not len(byte_str):\n            return\n\n        if not isinstance(byte_str, bytearray):\n            byte_str = bytearray(byte_str)\n\n        # First check for known BOMs, since these are guaranteed to be correct\n        if not self._got_data:\n            # If the data starts with BOM, we know it is UTF\n            if byte_str.startswith(codecs.BOM_UTF8):\n                # EF BB BF  UTF-8 with BOM\n                self.result = {'encoding': \"UTF-8-SIG\",\n                               'confidence': 1.0,\n                               'language': ''}\n            elif byte_str.startswith((codecs.BOM_UTF32_LE,\n                                      codecs.BOM_UTF32_BE)):\n                # FF FE 00 00  UTF-32, little-endian BOM\n                # 00 00 FE FF  UTF-32, big-endian BOM\n                self.result = {'encoding': \"UTF-32\",\n                               'confidence': 1.0,\n                               'language': ''}\n            elif byte_str.startswith(b'\\xFE\\xFF\\x00\\x00'):\n                # FE FF 00 00  UCS-4, unusual octet order BOM (3412)\n                self.result = {'encoding': \"X-ISO-10646-UCS-4-3412\",\n                               'confidence': 1.0,\n                               'language': ''}\n            elif byte_str.startswith(b'\\x00\\x00\\xFF\\xFE'):\n                # 00 00 FF FE  UCS-4, unusual octet order BOM (2143)\n                self.result = {'encoding': \"X-ISO-10646-UCS-4-2143\",\n                               'confidence': 1.0,\n                               'language': ''}\n            elif byte_str.startswith((codecs.BOM_LE, codecs.BOM_BE)):\n                # FF FE  UTF-16, little endian BOM\n                # FE FF  UTF-16, big endian BOM\n                self.result = {'encoding': \"UTF-16\",\n                               'confidence': 1.0,\n                               'language': ''}\n\n            self._got_data = True\n            if self.result['encoding'] is not None:\n                self.done = True\n                return\n\n        # If none of those matched and we've only see ASCII so far, check\n        # for high bytes and escape sequences\n        if self._input_state == InputState.PURE_ASCII:\n            if self.HIGH_BYTE_DETECTOR.search(byte_str):\n                self._input_state = InputState.HIGH_BYTE\n            elif self._input_state == InputState.PURE_ASCII and \\\n                    self.ESC_DETECTOR.search(self._last_char + byte_str):\n                self._input_state = InputState.ESC_ASCII\n\n        self._last_char = byte_str[-1:]\n\n        # If we've seen escape sequences, use the EscCharSetProber, which\n        # uses a simple state machine to check for known escape sequences in\n        # HZ and ISO-2022 encodings, since those are the only encodings that\n        # use such sequences.\n        if self._input_state == InputState.ESC_ASCII:\n            if not self._esc_charset_prober:\n                self._esc_charset_prober = EscCharSetProber(self.lang_filter)\n            if self._esc_charset_prober.feed(byte_str) == ProbingState.FOUND_IT:\n                self.result = {'encoding':\n                               self._esc_charset_prober.charset_name,\n                               'confidence':\n                               self._esc_charset_prober.get_confidence(),\n                               'language':\n                               self._esc_charset_prober.language}\n                self.done = True\n        # If we've seen high bytes (i.e., those with values greater than 127),\n        # we need to do more complicated checks using all our multi-byte and\n        # single-byte probers that are left.  The single-byte probers\n        # use character bigram distributions to determine the encoding, whereas\n        # the multi-byte probers use a combination of character unigram and\n        # bigram distributions.\n        elif self._input_state == InputState.HIGH_BYTE:\n            if not self._charset_probers:\n                self._charset_probers = [MBCSGroupProber(self.lang_filter)]\n                # If we're checking non-CJK encodings, use single-byte prober\n                if self.lang_filter & LanguageFilter.NON_CJK:\n                    self._charset_probers.append(SBCSGroupProber())\n                self._charset_probers.append(Latin1Prober())\n            for prober in self._charset_probers:\n                if prober.feed(byte_str) == ProbingState.FOUND_IT:\n                    self.result = {'encoding': prober.charset_name,\n                                   'confidence': prober.get_confidence(),\n                                   'language': prober.language}\n                    self.done = True\n                    break\n            if self.WIN_BYTE_DETECTOR.search(byte_str):\n                self._has_win_bytes = True\n\n    def close(self):\n        \"\"\"\n        Stop analyzing the current document and come up with a final\n        prediction.\n\n        :returns:  The ``result`` attribute, a ``dict`` with the keys\n                   `encoding`, `confidence`, and `language`.\n        \"\"\"\n        # Don't bother with checks if we're already done\n        if self.done:\n            return self.result\n        self.done = True\n\n        if not self._got_data:\n            self.logger.debug('no data received!')\n\n        # Default to ASCII if it is all we've seen so far\n        elif self._input_state == InputState.PURE_ASCII:\n            self.result = {'encoding': 'ascii',\n                           'confidence': 1.0,\n                           'language': ''}\n\n        # If we have seen non-ASCII, return the best that met MINIMUM_THRESHOLD\n        elif self._input_state == InputState.HIGH_BYTE:\n            prober_confidence = None\n            max_prober_confidence = 0.0\n            max_prober = None\n            for prober in self._charset_probers:\n                if not prober:\n                    continue\n                prober_confidence = prober.get_confidence()\n                if prober_confidence > max_prober_confidence:\n                    max_prober_confidence = prober_confidence\n                    max_prober = prober\n            if max_prober and (max_prober_confidence > self.MINIMUM_THRESHOLD):\n                charset_name = max_prober.charset_name\n                lower_charset_name = max_prober.charset_name.lower()\n                confidence = max_prober.get_confidence()\n                # Use Windows encoding name instead of ISO-8859 if we saw any\n                # extra Windows-specific bytes\n                if lower_charset_name.startswith('iso-8859'):\n                    if self._has_win_bytes:\n                        charset_name = self.ISO_WIN_MAP.get(lower_charset_name,\n                                                            charset_name)\n                self.result = {'encoding': charset_name,\n                               'confidence': confidence,\n                               'language': max_prober.language}\n\n        # Log all prober confidences if none met MINIMUM_THRESHOLD\n        if self.logger.getEffectiveLevel() == logging.DEBUG:\n            if self.result['encoding'] is None:\n                self.logger.debug('no probers hit minimum threshold')\n                for group_prober in self._charset_probers:\n                    if not group_prober:\n                        continue\n                    if isinstance(group_prober, CharSetGroupProber):\n                        for prober in group_prober.probers:\n                            self.logger.debug('%s %s confidence = %s',\n                                              prober.charset_name,\n                                              prober.language,\n                                              prober.get_confidence())\n                    else:\n                        self.logger.debug('%s %s confidence = %s',\n                                          prober.charset_name,\n                                          prober.language,\n                                          prober.get_confidence())\n        return self.result\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/utf8prober.py",
    "content": "######################## BEGIN LICENSE BLOCK ########################\n# The Original Code is mozilla.org code.\n#\n# The Initial Developer of the Original Code is\n# Netscape Communications Corporation.\n# Portions created by the Initial Developer are Copyright (C) 1998\n# the Initial Developer. All Rights Reserved.\n#\n# Contributor(s):\n#   Mark Pilgrim - port to Python\n#\n# This library is free software; you can redistribute it and/or\n# modify it under the terms of the GNU Lesser General Public\n# License as published by the Free Software Foundation; either\n# version 2.1 of the License, or (at your option) any later version.\n#\n# This library is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# Lesser General Public License for more details.\n#\n# You should have received a copy of the GNU Lesser General Public\n# License along with this library; if not, write to the Free Software\n# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA\n# 02110-1301  USA\n######################### END LICENSE BLOCK #########################\n\nfrom .charsetprober import CharSetProber\nfrom .enums import ProbingState, MachineState\nfrom .codingstatemachine import CodingStateMachine\nfrom .mbcssm import UTF8_SM_MODEL\n\n\n\nclass UTF8Prober(CharSetProber):\n    ONE_CHAR_PROB = 0.5\n\n    def __init__(self):\n        super(UTF8Prober, self).__init__()\n        self.coding_sm = CodingStateMachine(UTF8_SM_MODEL)\n        self._num_mb_chars = None\n        self.reset()\n\n    def reset(self):\n        super(UTF8Prober, self).reset()\n        self.coding_sm.reset()\n        self._num_mb_chars = 0\n\n    @property\n    def charset_name(self):\n        return \"utf-8\"\n\n    @property\n    def language(self):\n        return \"\"\n\n    def feed(self, byte_str):\n        for c in byte_str:\n            coding_state = self.coding_sm.next_state(c)\n            if coding_state == MachineState.ERROR:\n                self._state = ProbingState.NOT_ME\n                break\n            elif coding_state == MachineState.ITS_ME:\n                self._state = ProbingState.FOUND_IT\n                break\n            elif coding_state == MachineState.START:\n                if self.coding_sm.get_current_charlen() >= 2:\n                    self._num_mb_chars += 1\n\n        if self.state == ProbingState.DETECTING:\n            if self.get_confidence() > self.SHORTCUT_THRESHOLD:\n                self._state = ProbingState.FOUND_IT\n\n        return self.state\n\n    def get_confidence(self):\n        unlike = 0.99\n        if self._num_mb_chars < 6:\n            unlike *= self.ONE_CHAR_PROB ** self._num_mb_chars\n            return 1.0 - unlike\n        else:\n            return unlike\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/chardet/version.py",
    "content": "\"\"\"\nThis module exists only to simplify retrieving the version number of chardet\nfrom within setup.py and from chardet subpackages.\n\n:author: Dan Blanchard (dan.blanchard@gmail.com)\n\"\"\"\n\n__version__ = \"3.0.4\"\nVERSION = __version__.split('.')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/colorama/__init__.py",
    "content": "# Copyright Jonathan Hartley 2013. BSD 3-Clause license, see LICENSE file.\nfrom .initialise import init, deinit, reinit, colorama_text\nfrom .ansi import Fore, Back, Style, Cursor\nfrom .ansitowin32 import AnsiToWin32\n\n__version__ = '0.4.1'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/colorama/ansi.py",
    "content": "# Copyright Jonathan Hartley 2013. BSD 3-Clause license, see LICENSE file.\n'''\nThis module generates ANSI character codes to printing colors to terminals.\nSee: http://en.wikipedia.org/wiki/ANSI_escape_code\n'''\n\nCSI = '\\033['\nOSC = '\\033]'\nBEL = '\\007'\n\n\ndef code_to_chars(code):\n    return CSI + str(code) + 'm'\n\ndef set_title(title):\n    return OSC + '2;' + title + BEL\n\ndef clear_screen(mode=2):\n    return CSI + str(mode) + 'J'\n\ndef clear_line(mode=2):\n    return CSI + str(mode) + 'K'\n\n\nclass AnsiCodes(object):\n    def __init__(self):\n        # the subclasses declare class attributes which are numbers.\n        # Upon instantiation we define instance attributes, which are the same\n        # as the class attributes but wrapped with the ANSI escape sequence\n        for name in dir(self):\n            if not name.startswith('_'):\n                value = getattr(self, name)\n                setattr(self, name, code_to_chars(value))\n\n\nclass AnsiCursor(object):\n    def UP(self, n=1):\n        return CSI + str(n) + 'A'\n    def DOWN(self, n=1):\n        return CSI + str(n) + 'B'\n    def FORWARD(self, n=1):\n        return CSI + str(n) + 'C'\n    def BACK(self, n=1):\n        return CSI + str(n) + 'D'\n    def POS(self, x=1, y=1):\n        return CSI + str(y) + ';' + str(x) + 'H'\n\n\nclass AnsiFore(AnsiCodes):\n    BLACK           = 30\n    RED             = 31\n    GREEN           = 32\n    YELLOW          = 33\n    BLUE            = 34\n    MAGENTA         = 35\n    CYAN            = 36\n    WHITE           = 37\n    RESET           = 39\n\n    # These are fairly well supported, but not part of the standard.\n    LIGHTBLACK_EX   = 90\n    LIGHTRED_EX     = 91\n    LIGHTGREEN_EX   = 92\n    LIGHTYELLOW_EX  = 93\n    LIGHTBLUE_EX    = 94\n    LIGHTMAGENTA_EX = 95\n    LIGHTCYAN_EX    = 96\n    LIGHTWHITE_EX   = 97\n\n\nclass AnsiBack(AnsiCodes):\n    BLACK           = 40\n    RED             = 41\n    GREEN           = 42\n    YELLOW          = 43\n    BLUE            = 44\n    MAGENTA         = 45\n    CYAN            = 46\n    WHITE           = 47\n    RESET           = 49\n\n    # These are fairly well supported, but not part of the standard.\n    LIGHTBLACK_EX   = 100\n    LIGHTRED_EX     = 101\n    LIGHTGREEN_EX   = 102\n    LIGHTYELLOW_EX  = 103\n    LIGHTBLUE_EX    = 104\n    LIGHTMAGENTA_EX = 105\n    LIGHTCYAN_EX    = 106\n    LIGHTWHITE_EX   = 107\n\n\nclass AnsiStyle(AnsiCodes):\n    BRIGHT    = 1\n    DIM       = 2\n    NORMAL    = 22\n    RESET_ALL = 0\n\nFore   = AnsiFore()\nBack   = AnsiBack()\nStyle  = AnsiStyle()\nCursor = AnsiCursor()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/colorama/ansitowin32.py",
    "content": "# Copyright Jonathan Hartley 2013. BSD 3-Clause license, see LICENSE file.\nimport re\nimport sys\nimport os\n\nfrom .ansi import AnsiFore, AnsiBack, AnsiStyle, Style\nfrom .winterm import WinTerm, WinColor, WinStyle\nfrom .win32 import windll, winapi_test\n\n\nwinterm = None\nif windll is not None:\n    winterm = WinTerm()\n\n\nclass StreamWrapper(object):\n    '''\n    Wraps a stream (such as stdout), acting as a transparent proxy for all\n    attribute access apart from method 'write()', which is delegated to our\n    Converter instance.\n    '''\n    def __init__(self, wrapped, converter):\n        # double-underscore everything to prevent clashes with names of\n        # attributes on the wrapped stream object.\n        self.__wrapped = wrapped\n        self.__convertor = converter\n\n    def __getattr__(self, name):\n        return getattr(self.__wrapped, name)\n\n    def __enter__(self, *args, **kwargs):\n        # special method lookup bypasses __getattr__/__getattribute__, see\n        # https://stackoverflow.com/questions/12632894/why-doesnt-getattr-work-with-exit\n        # thus, contextlib magic methods are not proxied via __getattr__\n        return self.__wrapped.__enter__(*args, **kwargs)\n\n    def __exit__(self, *args, **kwargs):\n        return self.__wrapped.__exit__(*args, **kwargs)\n\n    def write(self, text):\n        self.__convertor.write(text)\n\n    def isatty(self):\n        stream = self.__wrapped\n        if 'PYCHARM_HOSTED' in os.environ:\n            if stream is not None and (stream is sys.__stdout__ or stream is sys.__stderr__):\n                return True\n        try:\n            stream_isatty = stream.isatty\n        except AttributeError:\n            return False\n        else:\n            return stream_isatty()\n\n    @property\n    def closed(self):\n        stream = self.__wrapped\n        try:\n            return stream.closed\n        except AttributeError:\n            return True\n\n\nclass AnsiToWin32(object):\n    '''\n    Implements a 'write()' method which, on Windows, will strip ANSI character\n    sequences from the text, and if outputting to a tty, will convert them into\n    win32 function calls.\n    '''\n    ANSI_CSI_RE = re.compile('\\001?\\033\\\\[((?:\\\\d|;)*)([a-zA-Z])\\002?')   # Control Sequence Introducer\n    ANSI_OSC_RE = re.compile('\\001?\\033\\\\]((?:.|;)*?)(\\x07)\\002?')        # Operating System Command\n\n    def __init__(self, wrapped, convert=None, strip=None, autoreset=False):\n        # The wrapped stream (normally sys.stdout or sys.stderr)\n        self.wrapped = wrapped\n\n        # should we reset colors to defaults after every .write()\n        self.autoreset = autoreset\n\n        # create the proxy wrapping our output stream\n        self.stream = StreamWrapper(wrapped, self)\n\n        on_windows = os.name == 'nt'\n        # We test if the WinAPI works, because even if we are on Windows\n        # we may be using a terminal that doesn't support the WinAPI\n        # (e.g. Cygwin Terminal). In this case it's up to the terminal\n        # to support the ANSI codes.\n        conversion_supported = on_windows and winapi_test()\n\n        # should we strip ANSI sequences from our output?\n        if strip is None:\n            strip = conversion_supported or (not self.stream.closed and not self.stream.isatty())\n        self.strip = strip\n\n        # should we should convert ANSI sequences into win32 calls?\n        if convert is None:\n            convert = conversion_supported and not self.stream.closed and self.stream.isatty()\n        self.convert = convert\n\n        # dict of ansi codes to win32 functions and parameters\n        self.win32_calls = self.get_win32_calls()\n\n        # are we wrapping stderr?\n        self.on_stderr = self.wrapped is sys.stderr\n\n    def should_wrap(self):\n        '''\n        True if this class is actually needed. If false, then the output\n        stream will not be affected, nor will win32 calls be issued, so\n        wrapping stdout is not actually required. This will generally be\n        False on non-Windows platforms, unless optional functionality like\n        autoreset has been requested using kwargs to init()\n        '''\n        return self.convert or self.strip or self.autoreset\n\n    def get_win32_calls(self):\n        if self.convert and winterm:\n            return {\n                AnsiStyle.RESET_ALL: (winterm.reset_all, ),\n                AnsiStyle.BRIGHT: (winterm.style, WinStyle.BRIGHT),\n                AnsiStyle.DIM: (winterm.style, WinStyle.NORMAL),\n                AnsiStyle.NORMAL: (winterm.style, WinStyle.NORMAL),\n                AnsiFore.BLACK: (winterm.fore, WinColor.BLACK),\n                AnsiFore.RED: (winterm.fore, WinColor.RED),\n                AnsiFore.GREEN: (winterm.fore, WinColor.GREEN),\n                AnsiFore.YELLOW: (winterm.fore, WinColor.YELLOW),\n                AnsiFore.BLUE: (winterm.fore, WinColor.BLUE),\n                AnsiFore.MAGENTA: (winterm.fore, WinColor.MAGENTA),\n                AnsiFore.CYAN: (winterm.fore, WinColor.CYAN),\n                AnsiFore.WHITE: (winterm.fore, WinColor.GREY),\n                AnsiFore.RESET: (winterm.fore, ),\n                AnsiFore.LIGHTBLACK_EX: (winterm.fore, WinColor.BLACK, True),\n                AnsiFore.LIGHTRED_EX: (winterm.fore, WinColor.RED, True),\n                AnsiFore.LIGHTGREEN_EX: (winterm.fore, WinColor.GREEN, True),\n                AnsiFore.LIGHTYELLOW_EX: (winterm.fore, WinColor.YELLOW, True),\n                AnsiFore.LIGHTBLUE_EX: (winterm.fore, WinColor.BLUE, True),\n                AnsiFore.LIGHTMAGENTA_EX: (winterm.fore, WinColor.MAGENTA, True),\n                AnsiFore.LIGHTCYAN_EX: (winterm.fore, WinColor.CYAN, True),\n                AnsiFore.LIGHTWHITE_EX: (winterm.fore, WinColor.GREY, True),\n                AnsiBack.BLACK: (winterm.back, WinColor.BLACK),\n                AnsiBack.RED: (winterm.back, WinColor.RED),\n                AnsiBack.GREEN: (winterm.back, WinColor.GREEN),\n                AnsiBack.YELLOW: (winterm.back, WinColor.YELLOW),\n                AnsiBack.BLUE: (winterm.back, WinColor.BLUE),\n                AnsiBack.MAGENTA: (winterm.back, WinColor.MAGENTA),\n                AnsiBack.CYAN: (winterm.back, WinColor.CYAN),\n                AnsiBack.WHITE: (winterm.back, WinColor.GREY),\n                AnsiBack.RESET: (winterm.back, ),\n                AnsiBack.LIGHTBLACK_EX: (winterm.back, WinColor.BLACK, True),\n                AnsiBack.LIGHTRED_EX: (winterm.back, WinColor.RED, True),\n                AnsiBack.LIGHTGREEN_EX: (winterm.back, WinColor.GREEN, True),\n                AnsiBack.LIGHTYELLOW_EX: (winterm.back, WinColor.YELLOW, True),\n                AnsiBack.LIGHTBLUE_EX: (winterm.back, WinColor.BLUE, True),\n                AnsiBack.LIGHTMAGENTA_EX: (winterm.back, WinColor.MAGENTA, True),\n                AnsiBack.LIGHTCYAN_EX: (winterm.back, WinColor.CYAN, True),\n                AnsiBack.LIGHTWHITE_EX: (winterm.back, WinColor.GREY, True),\n            }\n        return dict()\n\n    def write(self, text):\n        if self.strip or self.convert:\n            self.write_and_convert(text)\n        else:\n            self.wrapped.write(text)\n            self.wrapped.flush()\n        if self.autoreset:\n            self.reset_all()\n\n\n    def reset_all(self):\n        if self.convert:\n            self.call_win32('m', (0,))\n        elif not self.strip and not self.stream.closed:\n            self.wrapped.write(Style.RESET_ALL)\n\n\n    def write_and_convert(self, text):\n        '''\n        Write the given text to our wrapped stream, stripping any ANSI\n        sequences from the text, and optionally converting them into win32\n        calls.\n        '''\n        cursor = 0\n        text = self.convert_osc(text)\n        for match in self.ANSI_CSI_RE.finditer(text):\n            start, end = match.span()\n            self.write_plain_text(text, cursor, start)\n            self.convert_ansi(*match.groups())\n            cursor = end\n        self.write_plain_text(text, cursor, len(text))\n\n\n    def write_plain_text(self, text, start, end):\n        if start < end:\n            self.wrapped.write(text[start:end])\n            self.wrapped.flush()\n\n\n    def convert_ansi(self, paramstring, command):\n        if self.convert:\n            params = self.extract_params(command, paramstring)\n            self.call_win32(command, params)\n\n\n    def extract_params(self, command, paramstring):\n        if command in 'Hf':\n            params = tuple(int(p) if len(p) != 0 else 1 for p in paramstring.split(';'))\n            while len(params) < 2:\n                # defaults:\n                params = params + (1,)\n        else:\n            params = tuple(int(p) for p in paramstring.split(';') if len(p) != 0)\n            if len(params) == 0:\n                # defaults:\n                if command in 'JKm':\n                    params = (0,)\n                elif command in 'ABCD':\n                    params = (1,)\n\n        return params\n\n\n    def call_win32(self, command, params):\n        if command == 'm':\n            for param in params:\n                if param in self.win32_calls:\n                    func_args = self.win32_calls[param]\n                    func = func_args[0]\n                    args = func_args[1:]\n                    kwargs = dict(on_stderr=self.on_stderr)\n                    func(*args, **kwargs)\n        elif command in 'J':\n            winterm.erase_screen(params[0], on_stderr=self.on_stderr)\n        elif command in 'K':\n            winterm.erase_line(params[0], on_stderr=self.on_stderr)\n        elif command in 'Hf':     # cursor position - absolute\n            winterm.set_cursor_position(params, on_stderr=self.on_stderr)\n        elif command in 'ABCD':   # cursor position - relative\n            n = params[0]\n            # A - up, B - down, C - forward, D - back\n            x, y = {'A': (0, -n), 'B': (0, n), 'C': (n, 0), 'D': (-n, 0)}[command]\n            winterm.cursor_adjust(x, y, on_stderr=self.on_stderr)\n\n\n    def convert_osc(self, text):\n        for match in self.ANSI_OSC_RE.finditer(text):\n            start, end = match.span()\n            text = text[:start] + text[end:]\n            paramstring, command = match.groups()\n            if command in '\\x07':       # \\x07 = BEL\n                params = paramstring.split(\";\")\n                # 0 - change title and icon (we will only change title)\n                # 1 - change icon (we don't support this)\n                # 2 - change title\n                if params[0] in '02':\n                    winterm.set_title(params[1])\n        return text\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/colorama/initialise.py",
    "content": "# Copyright Jonathan Hartley 2013. BSD 3-Clause license, see LICENSE file.\nimport atexit\nimport contextlib\nimport sys\n\nfrom .ansitowin32 import AnsiToWin32\n\n\norig_stdout = None\norig_stderr = None\n\nwrapped_stdout = None\nwrapped_stderr = None\n\natexit_done = False\n\n\ndef reset_all():\n    if AnsiToWin32 is not None:    # Issue #74: objects might become None at exit\n        AnsiToWin32(orig_stdout).reset_all()\n\n\ndef init(autoreset=False, convert=None, strip=None, wrap=True):\n\n    if not wrap and any([autoreset, convert, strip]):\n        raise ValueError('wrap=False conflicts with any other arg=True')\n\n    global wrapped_stdout, wrapped_stderr\n    global orig_stdout, orig_stderr\n\n    orig_stdout = sys.stdout\n    orig_stderr = sys.stderr\n\n    if sys.stdout is None:\n        wrapped_stdout = None\n    else:\n        sys.stdout = wrapped_stdout = \\\n            wrap_stream(orig_stdout, convert, strip, autoreset, wrap)\n    if sys.stderr is None:\n        wrapped_stderr = None\n    else:\n        sys.stderr = wrapped_stderr = \\\n            wrap_stream(orig_stderr, convert, strip, autoreset, wrap)\n\n    global atexit_done\n    if not atexit_done:\n        atexit.register(reset_all)\n        atexit_done = True\n\n\ndef deinit():\n    if orig_stdout is not None:\n        sys.stdout = orig_stdout\n    if orig_stderr is not None:\n        sys.stderr = orig_stderr\n\n\n@contextlib.contextmanager\ndef colorama_text(*args, **kwargs):\n    init(*args, **kwargs)\n    try:\n        yield\n    finally:\n        deinit()\n\n\ndef reinit():\n    if wrapped_stdout is not None:\n        sys.stdout = wrapped_stdout\n    if wrapped_stderr is not None:\n        sys.stderr = wrapped_stderr\n\n\ndef wrap_stream(stream, convert, strip, autoreset, wrap):\n    if wrap:\n        wrapper = AnsiToWin32(stream,\n            convert=convert, strip=strip, autoreset=autoreset)\n        if wrapper.should_wrap():\n            stream = wrapper.stream\n    return stream\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/colorama/win32.py",
    "content": "# Copyright Jonathan Hartley 2013. BSD 3-Clause license, see LICENSE file.\n\n# from winbase.h\nSTDOUT = -11\nSTDERR = -12\n\ntry:\n    import ctypes\n    from ctypes import LibraryLoader\n    windll = LibraryLoader(ctypes.WinDLL)\n    from ctypes import wintypes\nexcept (AttributeError, ImportError):\n    windll = None\n    SetConsoleTextAttribute = lambda *_: None\n    winapi_test = lambda *_: None\nelse:\n    from ctypes import byref, Structure, c_char, POINTER\n\n    COORD = wintypes._COORD\n\n    class CONSOLE_SCREEN_BUFFER_INFO(Structure):\n        \"\"\"struct in wincon.h.\"\"\"\n        _fields_ = [\n            (\"dwSize\", COORD),\n            (\"dwCursorPosition\", COORD),\n            (\"wAttributes\", wintypes.WORD),\n            (\"srWindow\", wintypes.SMALL_RECT),\n            (\"dwMaximumWindowSize\", COORD),\n        ]\n        def __str__(self):\n            return '(%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d)' % (\n                self.dwSize.Y, self.dwSize.X\n                , self.dwCursorPosition.Y, self.dwCursorPosition.X\n                , self.wAttributes\n                , self.srWindow.Top, self.srWindow.Left, self.srWindow.Bottom, self.srWindow.Right\n                , self.dwMaximumWindowSize.Y, self.dwMaximumWindowSize.X\n            )\n\n    _GetStdHandle = windll.kernel32.GetStdHandle\n    _GetStdHandle.argtypes = [\n        wintypes.DWORD,\n    ]\n    _GetStdHandle.restype = wintypes.HANDLE\n\n    _GetConsoleScreenBufferInfo = windll.kernel32.GetConsoleScreenBufferInfo\n    _GetConsoleScreenBufferInfo.argtypes = [\n        wintypes.HANDLE,\n        POINTER(CONSOLE_SCREEN_BUFFER_INFO),\n    ]\n    _GetConsoleScreenBufferInfo.restype = wintypes.BOOL\n\n    _SetConsoleTextAttribute = windll.kernel32.SetConsoleTextAttribute\n    _SetConsoleTextAttribute.argtypes = [\n        wintypes.HANDLE,\n        wintypes.WORD,\n    ]\n    _SetConsoleTextAttribute.restype = wintypes.BOOL\n\n    _SetConsoleCursorPosition = windll.kernel32.SetConsoleCursorPosition\n    _SetConsoleCursorPosition.argtypes = [\n        wintypes.HANDLE,\n        COORD,\n    ]\n    _SetConsoleCursorPosition.restype = wintypes.BOOL\n\n    _FillConsoleOutputCharacterA = windll.kernel32.FillConsoleOutputCharacterA\n    _FillConsoleOutputCharacterA.argtypes = [\n        wintypes.HANDLE,\n        c_char,\n        wintypes.DWORD,\n        COORD,\n        POINTER(wintypes.DWORD),\n    ]\n    _FillConsoleOutputCharacterA.restype = wintypes.BOOL\n\n    _FillConsoleOutputAttribute = windll.kernel32.FillConsoleOutputAttribute\n    _FillConsoleOutputAttribute.argtypes = [\n        wintypes.HANDLE,\n        wintypes.WORD,\n        wintypes.DWORD,\n        COORD,\n        POINTER(wintypes.DWORD),\n    ]\n    _FillConsoleOutputAttribute.restype = wintypes.BOOL\n\n    _SetConsoleTitleW = windll.kernel32.SetConsoleTitleW\n    _SetConsoleTitleW.argtypes = [\n        wintypes.LPCWSTR\n    ]\n    _SetConsoleTitleW.restype = wintypes.BOOL\n\n    def _winapi_test(handle):\n        csbi = CONSOLE_SCREEN_BUFFER_INFO()\n        success = _GetConsoleScreenBufferInfo(\n            handle, byref(csbi))\n        return bool(success)\n\n    def winapi_test():\n        return any(_winapi_test(h) for h in\n                   (_GetStdHandle(STDOUT), _GetStdHandle(STDERR)))\n\n    def GetConsoleScreenBufferInfo(stream_id=STDOUT):\n        handle = _GetStdHandle(stream_id)\n        csbi = CONSOLE_SCREEN_BUFFER_INFO()\n        success = _GetConsoleScreenBufferInfo(\n            handle, byref(csbi))\n        return csbi\n\n    def SetConsoleTextAttribute(stream_id, attrs):\n        handle = _GetStdHandle(stream_id)\n        return _SetConsoleTextAttribute(handle, attrs)\n\n    def SetConsoleCursorPosition(stream_id, position, adjust=True):\n        position = COORD(*position)\n        # If the position is out of range, do nothing.\n        if position.Y <= 0 or position.X <= 0:\n            return\n        # Adjust for Windows' SetConsoleCursorPosition:\n        #    1. being 0-based, while ANSI is 1-based.\n        #    2. expecting (x,y), while ANSI uses (y,x).\n        adjusted_position = COORD(position.Y - 1, position.X - 1)\n        if adjust:\n            # Adjust for viewport's scroll position\n            sr = GetConsoleScreenBufferInfo(STDOUT).srWindow\n            adjusted_position.Y += sr.Top\n            adjusted_position.X += sr.Left\n        # Resume normal processing\n        handle = _GetStdHandle(stream_id)\n        return _SetConsoleCursorPosition(handle, adjusted_position)\n\n    def FillConsoleOutputCharacter(stream_id, char, length, start):\n        handle = _GetStdHandle(stream_id)\n        char = c_char(char.encode())\n        length = wintypes.DWORD(length)\n        num_written = wintypes.DWORD(0)\n        # Note that this is hard-coded for ANSI (vs wide) bytes.\n        success = _FillConsoleOutputCharacterA(\n            handle, char, length, start, byref(num_written))\n        return num_written.value\n\n    def FillConsoleOutputAttribute(stream_id, attr, length, start):\n        ''' FillConsoleOutputAttribute( hConsole, csbi.wAttributes, dwConSize, coordScreen, &cCharsWritten )'''\n        handle = _GetStdHandle(stream_id)\n        attribute = wintypes.WORD(attr)\n        length = wintypes.DWORD(length)\n        num_written = wintypes.DWORD(0)\n        # Note that this is hard-coded for ANSI (vs wide) bytes.\n        return _FillConsoleOutputAttribute(\n            handle, attribute, length, start, byref(num_written))\n\n    def SetConsoleTitle(title):\n        return _SetConsoleTitleW(title)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/colorama/winterm.py",
    "content": "# Copyright Jonathan Hartley 2013. BSD 3-Clause license, see LICENSE file.\nfrom . import win32\n\n\n# from wincon.h\nclass WinColor(object):\n    BLACK   = 0\n    BLUE    = 1\n    GREEN   = 2\n    CYAN    = 3\n    RED     = 4\n    MAGENTA = 5\n    YELLOW  = 6\n    GREY    = 7\n\n# from wincon.h\nclass WinStyle(object):\n    NORMAL              = 0x00 # dim text, dim background\n    BRIGHT              = 0x08 # bright text, dim background\n    BRIGHT_BACKGROUND   = 0x80 # dim text, bright background\n\nclass WinTerm(object):\n\n    def __init__(self):\n        self._default = win32.GetConsoleScreenBufferInfo(win32.STDOUT).wAttributes\n        self.set_attrs(self._default)\n        self._default_fore = self._fore\n        self._default_back = self._back\n        self._default_style = self._style\n        # In order to emulate LIGHT_EX in windows, we borrow the BRIGHT style.\n        # So that LIGHT_EX colors and BRIGHT style do not clobber each other,\n        # we track them separately, since LIGHT_EX is overwritten by Fore/Back\n        # and BRIGHT is overwritten by Style codes.\n        self._light = 0\n\n    def get_attrs(self):\n        return self._fore + self._back * 16 + (self._style | self._light)\n\n    def set_attrs(self, value):\n        self._fore = value & 7\n        self._back = (value >> 4) & 7\n        self._style = value & (WinStyle.BRIGHT | WinStyle.BRIGHT_BACKGROUND)\n\n    def reset_all(self, on_stderr=None):\n        self.set_attrs(self._default)\n        self.set_console(attrs=self._default)\n        self._light = 0\n\n    def fore(self, fore=None, light=False, on_stderr=False):\n        if fore is None:\n            fore = self._default_fore\n        self._fore = fore\n        # Emulate LIGHT_EX with BRIGHT Style\n        if light:\n            self._light |= WinStyle.BRIGHT\n        else:\n            self._light &= ~WinStyle.BRIGHT\n        self.set_console(on_stderr=on_stderr)\n\n    def back(self, back=None, light=False, on_stderr=False):\n        if back is None:\n            back = self._default_back\n        self._back = back\n        # Emulate LIGHT_EX with BRIGHT_BACKGROUND Style\n        if light:\n            self._light |= WinStyle.BRIGHT_BACKGROUND\n        else:\n            self._light &= ~WinStyle.BRIGHT_BACKGROUND\n        self.set_console(on_stderr=on_stderr)\n\n    def style(self, style=None, on_stderr=False):\n        if style is None:\n            style = self._default_style\n        self._style = style\n        self.set_console(on_stderr=on_stderr)\n\n    def set_console(self, attrs=None, on_stderr=False):\n        if attrs is None:\n            attrs = self.get_attrs()\n        handle = win32.STDOUT\n        if on_stderr:\n            handle = win32.STDERR\n        win32.SetConsoleTextAttribute(handle, attrs)\n\n    def get_position(self, handle):\n        position = win32.GetConsoleScreenBufferInfo(handle).dwCursorPosition\n        # Because Windows coordinates are 0-based,\n        # and win32.SetConsoleCursorPosition expects 1-based.\n        position.X += 1\n        position.Y += 1\n        return position\n\n    def set_cursor_position(self, position=None, on_stderr=False):\n        if position is None:\n            # I'm not currently tracking the position, so there is no default.\n            # position = self.get_position()\n            return\n        handle = win32.STDOUT\n        if on_stderr:\n            handle = win32.STDERR\n        win32.SetConsoleCursorPosition(handle, position)\n\n    def cursor_adjust(self, x, y, on_stderr=False):\n        handle = win32.STDOUT\n        if on_stderr:\n            handle = win32.STDERR\n        position = self.get_position(handle)\n        adjusted_position = (position.Y + y, position.X + x)\n        win32.SetConsoleCursorPosition(handle, adjusted_position, adjust=False)\n\n    def erase_screen(self, mode=0, on_stderr=False):\n        # 0 should clear from the cursor to the end of the screen.\n        # 1 should clear from the cursor to the beginning of the screen.\n        # 2 should clear the entire screen, and move cursor to (1,1)\n        handle = win32.STDOUT\n        if on_stderr:\n            handle = win32.STDERR\n        csbi = win32.GetConsoleScreenBufferInfo(handle)\n        # get the number of character cells in the current buffer\n        cells_in_screen = csbi.dwSize.X * csbi.dwSize.Y\n        # get number of character cells before current cursor position\n        cells_before_cursor = csbi.dwSize.X * csbi.dwCursorPosition.Y + csbi.dwCursorPosition.X\n        if mode == 0:\n            from_coord = csbi.dwCursorPosition\n            cells_to_erase = cells_in_screen - cells_before_cursor\n        elif mode == 1:\n            from_coord = win32.COORD(0, 0)\n            cells_to_erase = cells_before_cursor\n        elif mode == 2:\n            from_coord = win32.COORD(0, 0)\n            cells_to_erase = cells_in_screen\n        else:\n            # invalid mode\n            return\n        # fill the entire screen with blanks\n        win32.FillConsoleOutputCharacter(handle, ' ', cells_to_erase, from_coord)\n        # now set the buffer's attributes accordingly\n        win32.FillConsoleOutputAttribute(handle, self.get_attrs(), cells_to_erase, from_coord)\n        if mode == 2:\n            # put the cursor where needed\n            win32.SetConsoleCursorPosition(handle, (1, 1))\n\n    def erase_line(self, mode=0, on_stderr=False):\n        # 0 should clear from the cursor to the end of the line.\n        # 1 should clear from the cursor to the beginning of the line.\n        # 2 should clear the entire line.\n        handle = win32.STDOUT\n        if on_stderr:\n            handle = win32.STDERR\n        csbi = win32.GetConsoleScreenBufferInfo(handle)\n        if mode == 0:\n            from_coord = csbi.dwCursorPosition\n            cells_to_erase = csbi.dwSize.X - csbi.dwCursorPosition.X\n        elif mode == 1:\n            from_coord = win32.COORD(0, csbi.dwCursorPosition.Y)\n            cells_to_erase = csbi.dwCursorPosition.X\n        elif mode == 2:\n            from_coord = win32.COORD(0, csbi.dwCursorPosition.Y)\n            cells_to_erase = csbi.dwSize.X\n        else:\n            # invalid mode\n            return\n        # fill the entire screen with blanks\n        win32.FillConsoleOutputCharacter(handle, ' ', cells_to_erase, from_coord)\n        # now set the buffer's attributes accordingly\n        win32.FillConsoleOutputAttribute(handle, self.get_attrs(), cells_to_erase, from_coord)\n\n    def set_title(self, title):\n        win32.SetConsoleTitle(title)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/__init__.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2012-2017 Vinay Sajip.\n# Licensed to the Python Software Foundation under a contributor agreement.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\nimport logging\n\n__version__ = '0.2.8'\n\nclass DistlibException(Exception):\n    pass\n\ntry:\n    from logging import NullHandler\nexcept ImportError: # pragma: no cover\n    class NullHandler(logging.Handler):\n        def handle(self, record): pass\n        def emit(self, record): pass\n        def createLock(self): self.lock = None\n\nlogger = logging.getLogger(__name__)\nlogger.addHandler(NullHandler())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/_backport/__init__.py",
    "content": "\"\"\"Modules copied from Python 3 standard libraries, for internal use only.\n\nIndividual classes and functions are found in d2._backport.misc.  Intended\nusage is to always import things missing from 3.1 from that module: the\nbuilt-in/stdlib objects will be used if found.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/_backport/misc.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2012 The Python Software Foundation.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\n\"\"\"Backports for individual classes and functions.\"\"\"\n\nimport os\nimport sys\n\n__all__ = ['cache_from_source', 'callable', 'fsencode']\n\n\ntry:\n    from imp import cache_from_source\nexcept ImportError:\n    def cache_from_source(py_file, debug=__debug__):\n        ext = debug and 'c' or 'o'\n        return py_file + ext\n\n\ntry:\n    callable = callable\nexcept NameError:\n    from collections import Callable\n\n    def callable(obj):\n        return isinstance(obj, Callable)\n\n\ntry:\n    fsencode = os.fsencode\nexcept AttributeError:\n    def fsencode(filename):\n        if isinstance(filename, bytes):\n            return filename\n        elif isinstance(filename, str):\n            return filename.encode(sys.getfilesystemencoding())\n        else:\n            raise TypeError(\"expect bytes or str, not %s\" %\n                            type(filename).__name__)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/_backport/shutil.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2012 The Python Software Foundation.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\n\"\"\"Utility functions for copying and archiving files and directory trees.\n\nXXX The functions here don't copy the resource fork or other metadata on Mac.\n\n\"\"\"\n\nimport os\nimport sys\nimport stat\nfrom os.path import abspath\nimport fnmatch\nimport collections\nimport errno\nfrom . import tarfile\n\ntry:\n    import bz2\n    _BZ2_SUPPORTED = True\nexcept ImportError:\n    _BZ2_SUPPORTED = False\n\ntry:\n    from pwd import getpwnam\nexcept ImportError:\n    getpwnam = None\n\ntry:\n    from grp import getgrnam\nexcept ImportError:\n    getgrnam = None\n\n__all__ = [\"copyfileobj\", \"copyfile\", \"copymode\", \"copystat\", \"copy\", \"copy2\",\n           \"copytree\", \"move\", \"rmtree\", \"Error\", \"SpecialFileError\",\n           \"ExecError\", \"make_archive\", \"get_archive_formats\",\n           \"register_archive_format\", \"unregister_archive_format\",\n           \"get_unpack_formats\", \"register_unpack_format\",\n           \"unregister_unpack_format\", \"unpack_archive\", \"ignore_patterns\"]\n\nclass Error(EnvironmentError):\n    pass\n\nclass SpecialFileError(EnvironmentError):\n    \"\"\"Raised when trying to do a kind of operation (e.g. copying) which is\n    not supported on a special file (e.g. a named pipe)\"\"\"\n\nclass ExecError(EnvironmentError):\n    \"\"\"Raised when a command could not be executed\"\"\"\n\nclass ReadError(EnvironmentError):\n    \"\"\"Raised when an archive cannot be read\"\"\"\n\nclass RegistryError(Exception):\n    \"\"\"Raised when a registry operation with the archiving\n    and unpacking registries fails\"\"\"\n\n\ntry:\n    WindowsError\nexcept NameError:\n    WindowsError = None\n\ndef copyfileobj(fsrc, fdst, length=16*1024):\n    \"\"\"copy data from file-like object fsrc to file-like object fdst\"\"\"\n    while 1:\n        buf = fsrc.read(length)\n        if not buf:\n            break\n        fdst.write(buf)\n\ndef _samefile(src, dst):\n    # Macintosh, Unix.\n    if hasattr(os.path, 'samefile'):\n        try:\n            return os.path.samefile(src, dst)\n        except OSError:\n            return False\n\n    # All other platforms: check for same pathname.\n    return (os.path.normcase(os.path.abspath(src)) ==\n            os.path.normcase(os.path.abspath(dst)))\n\ndef copyfile(src, dst):\n    \"\"\"Copy data from src to dst\"\"\"\n    if _samefile(src, dst):\n        raise Error(\"`%s` and `%s` are the same file\" % (src, dst))\n\n    for fn in [src, dst]:\n        try:\n            st = os.stat(fn)\n        except OSError:\n            # File most likely does not exist\n            pass\n        else:\n            # XXX What about other special files? (sockets, devices...)\n            if stat.S_ISFIFO(st.st_mode):\n                raise SpecialFileError(\"`%s` is a named pipe\" % fn)\n\n    with open(src, 'rb') as fsrc:\n        with open(dst, 'wb') as fdst:\n            copyfileobj(fsrc, fdst)\n\ndef copymode(src, dst):\n    \"\"\"Copy mode bits from src to dst\"\"\"\n    if hasattr(os, 'chmod'):\n        st = os.stat(src)\n        mode = stat.S_IMODE(st.st_mode)\n        os.chmod(dst, mode)\n\ndef copystat(src, dst):\n    \"\"\"Copy all stat info (mode bits, atime, mtime, flags) from src to dst\"\"\"\n    st = os.stat(src)\n    mode = stat.S_IMODE(st.st_mode)\n    if hasattr(os, 'utime'):\n        os.utime(dst, (st.st_atime, st.st_mtime))\n    if hasattr(os, 'chmod'):\n        os.chmod(dst, mode)\n    if hasattr(os, 'chflags') and hasattr(st, 'st_flags'):\n        try:\n            os.chflags(dst, st.st_flags)\n        except OSError as why:\n            if (not hasattr(errno, 'EOPNOTSUPP') or\n                why.errno != errno.EOPNOTSUPP):\n                raise\n\ndef copy(src, dst):\n    \"\"\"Copy data and mode bits (\"cp src dst\").\n\n    The destination may be a directory.\n\n    \"\"\"\n    if os.path.isdir(dst):\n        dst = os.path.join(dst, os.path.basename(src))\n    copyfile(src, dst)\n    copymode(src, dst)\n\ndef copy2(src, dst):\n    \"\"\"Copy data and all stat info (\"cp -p src dst\").\n\n    The destination may be a directory.\n\n    \"\"\"\n    if os.path.isdir(dst):\n        dst = os.path.join(dst, os.path.basename(src))\n    copyfile(src, dst)\n    copystat(src, dst)\n\ndef ignore_patterns(*patterns):\n    \"\"\"Function that can be used as copytree() ignore parameter.\n\n    Patterns is a sequence of glob-style patterns\n    that are used to exclude files\"\"\"\n    def _ignore_patterns(path, names):\n        ignored_names = []\n        for pattern in patterns:\n            ignored_names.extend(fnmatch.filter(names, pattern))\n        return set(ignored_names)\n    return _ignore_patterns\n\ndef copytree(src, dst, symlinks=False, ignore=None, copy_function=copy2,\n             ignore_dangling_symlinks=False):\n    \"\"\"Recursively copy a directory tree.\n\n    The destination directory must not already exist.\n    If exception(s) occur, an Error is raised with a list of reasons.\n\n    If the optional symlinks flag is true, symbolic links in the\n    source tree result in symbolic links in the destination tree; if\n    it is false, the contents of the files pointed to by symbolic\n    links are copied. If the file pointed by the symlink doesn't\n    exist, an exception will be added in the list of errors raised in\n    an Error exception at the end of the copy process.\n\n    You can set the optional ignore_dangling_symlinks flag to true if you\n    want to silence this exception. Notice that this has no effect on\n    platforms that don't support os.symlink.\n\n    The optional ignore argument is a callable. If given, it\n    is called with the `src` parameter, which is the directory\n    being visited by copytree(), and `names` which is the list of\n    `src` contents, as returned by os.listdir():\n\n        callable(src, names) -> ignored_names\n\n    Since copytree() is called recursively, the callable will be\n    called once for each directory that is copied. It returns a\n    list of names relative to the `src` directory that should\n    not be copied.\n\n    The optional copy_function argument is a callable that will be used\n    to copy each file. It will be called with the source path and the\n    destination path as arguments. By default, copy2() is used, but any\n    function that supports the same signature (like copy()) can be used.\n\n    \"\"\"\n    names = os.listdir(src)\n    if ignore is not None:\n        ignored_names = ignore(src, names)\n    else:\n        ignored_names = set()\n\n    os.makedirs(dst)\n    errors = []\n    for name in names:\n        if name in ignored_names:\n            continue\n        srcname = os.path.join(src, name)\n        dstname = os.path.join(dst, name)\n        try:\n            if os.path.islink(srcname):\n                linkto = os.readlink(srcname)\n                if symlinks:\n                    os.symlink(linkto, dstname)\n                else:\n                    # ignore dangling symlink if the flag is on\n                    if not os.path.exists(linkto) and ignore_dangling_symlinks:\n                        continue\n                    # otherwise let the copy occurs. copy2 will raise an error\n                    copy_function(srcname, dstname)\n            elif os.path.isdir(srcname):\n                copytree(srcname, dstname, symlinks, ignore, copy_function)\n            else:\n                # Will raise a SpecialFileError for unsupported file types\n                copy_function(srcname, dstname)\n        # catch the Error from the recursive copytree so that we can\n        # continue with other files\n        except Error as err:\n            errors.extend(err.args[0])\n        except EnvironmentError as why:\n            errors.append((srcname, dstname, str(why)))\n    try:\n        copystat(src, dst)\n    except OSError as why:\n        if WindowsError is not None and isinstance(why, WindowsError):\n            # Copying file access times may fail on Windows\n            pass\n        else:\n            errors.extend((src, dst, str(why)))\n    if errors:\n        raise Error(errors)\n\ndef rmtree(path, ignore_errors=False, onerror=None):\n    \"\"\"Recursively delete a directory tree.\n\n    If ignore_errors is set, errors are ignored; otherwise, if onerror\n    is set, it is called to handle the error with arguments (func,\n    path, exc_info) where func is os.listdir, os.remove, or os.rmdir;\n    path is the argument to that function that caused it to fail; and\n    exc_info is a tuple returned by sys.exc_info().  If ignore_errors\n    is false and onerror is None, an exception is raised.\n\n    \"\"\"\n    if ignore_errors:\n        def onerror(*args):\n            pass\n    elif onerror is None:\n        def onerror(*args):\n            raise\n    try:\n        if os.path.islink(path):\n            # symlinks to directories are forbidden, see bug #1669\n            raise OSError(\"Cannot call rmtree on a symbolic link\")\n    except OSError:\n        onerror(os.path.islink, path, sys.exc_info())\n        # can't continue even if onerror hook returns\n        return\n    names = []\n    try:\n        names = os.listdir(path)\n    except os.error:\n        onerror(os.listdir, path, sys.exc_info())\n    for name in names:\n        fullname = os.path.join(path, name)\n        try:\n            mode = os.lstat(fullname).st_mode\n        except os.error:\n            mode = 0\n        if stat.S_ISDIR(mode):\n            rmtree(fullname, ignore_errors, onerror)\n        else:\n            try:\n                os.remove(fullname)\n            except os.error:\n                onerror(os.remove, fullname, sys.exc_info())\n    try:\n        os.rmdir(path)\n    except os.error:\n        onerror(os.rmdir, path, sys.exc_info())\n\n\ndef _basename(path):\n    # A basename() variant which first strips the trailing slash, if present.\n    # Thus we always get the last component of the path, even for directories.\n    return os.path.basename(path.rstrip(os.path.sep))\n\ndef move(src, dst):\n    \"\"\"Recursively move a file or directory to another location. This is\n    similar to the Unix \"mv\" command.\n\n    If the destination is a directory or a symlink to a directory, the source\n    is moved inside the directory. The destination path must not already\n    exist.\n\n    If the destination already exists but is not a directory, it may be\n    overwritten depending on os.rename() semantics.\n\n    If the destination is on our current filesystem, then rename() is used.\n    Otherwise, src is copied to the destination and then removed.\n    A lot more could be done here...  A look at a mv.c shows a lot of\n    the issues this implementation glosses over.\n\n    \"\"\"\n    real_dst = dst\n    if os.path.isdir(dst):\n        if _samefile(src, dst):\n            # We might be on a case insensitive filesystem,\n            # perform the rename anyway.\n            os.rename(src, dst)\n            return\n\n        real_dst = os.path.join(dst, _basename(src))\n        if os.path.exists(real_dst):\n            raise Error(\"Destination path '%s' already exists\" % real_dst)\n    try:\n        os.rename(src, real_dst)\n    except OSError:\n        if os.path.isdir(src):\n            if _destinsrc(src, dst):\n                raise Error(\"Cannot move a directory '%s' into itself '%s'.\" % (src, dst))\n            copytree(src, real_dst, symlinks=True)\n            rmtree(src)\n        else:\n            copy2(src, real_dst)\n            os.unlink(src)\n\ndef _destinsrc(src, dst):\n    src = abspath(src)\n    dst = abspath(dst)\n    if not src.endswith(os.path.sep):\n        src += os.path.sep\n    if not dst.endswith(os.path.sep):\n        dst += os.path.sep\n    return dst.startswith(src)\n\ndef _get_gid(name):\n    \"\"\"Returns a gid, given a group name.\"\"\"\n    if getgrnam is None or name is None:\n        return None\n    try:\n        result = getgrnam(name)\n    except KeyError:\n        result = None\n    if result is not None:\n        return result[2]\n    return None\n\ndef _get_uid(name):\n    \"\"\"Returns an uid, given a user name.\"\"\"\n    if getpwnam is None or name is None:\n        return None\n    try:\n        result = getpwnam(name)\n    except KeyError:\n        result = None\n    if result is not None:\n        return result[2]\n    return None\n\ndef _make_tarball(base_name, base_dir, compress=\"gzip\", verbose=0, dry_run=0,\n                  owner=None, group=None, logger=None):\n    \"\"\"Create a (possibly compressed) tar file from all the files under\n    'base_dir'.\n\n    'compress' must be \"gzip\" (the default), \"bzip2\", or None.\n\n    'owner' and 'group' can be used to define an owner and a group for the\n    archive that is being built. If not provided, the current owner and group\n    will be used.\n\n    The output tar file will be named 'base_name' +  \".tar\", possibly plus\n    the appropriate compression extension (\".gz\", or \".bz2\").\n\n    Returns the output filename.\n    \"\"\"\n    tar_compression = {'gzip': 'gz', None: ''}\n    compress_ext = {'gzip': '.gz'}\n\n    if _BZ2_SUPPORTED:\n        tar_compression['bzip2'] = 'bz2'\n        compress_ext['bzip2'] = '.bz2'\n\n    # flags for compression program, each element of list will be an argument\n    if compress is not None and compress not in compress_ext:\n        raise ValueError(\"bad value for 'compress', or compression format not \"\n                         \"supported : {0}\".format(compress))\n\n    archive_name = base_name + '.tar' + compress_ext.get(compress, '')\n    archive_dir = os.path.dirname(archive_name)\n\n    if not os.path.exists(archive_dir):\n        if logger is not None:\n            logger.info(\"creating %s\", archive_dir)\n        if not dry_run:\n            os.makedirs(archive_dir)\n\n    # creating the tarball\n    if logger is not None:\n        logger.info('Creating tar archive')\n\n    uid = _get_uid(owner)\n    gid = _get_gid(group)\n\n    def _set_uid_gid(tarinfo):\n        if gid is not None:\n            tarinfo.gid = gid\n            tarinfo.gname = group\n        if uid is not None:\n            tarinfo.uid = uid\n            tarinfo.uname = owner\n        return tarinfo\n\n    if not dry_run:\n        tar = tarfile.open(archive_name, 'w|%s' % tar_compression[compress])\n        try:\n            tar.add(base_dir, filter=_set_uid_gid)\n        finally:\n            tar.close()\n\n    return archive_name\n\ndef _call_external_zip(base_dir, zip_filename, verbose=False, dry_run=False):\n    # XXX see if we want to keep an external call here\n    if verbose:\n        zipoptions = \"-r\"\n    else:\n        zipoptions = \"-rq\"\n    from distutils.errors import DistutilsExecError\n    from distutils.spawn import spawn\n    try:\n        spawn([\"zip\", zipoptions, zip_filename, base_dir], dry_run=dry_run)\n    except DistutilsExecError:\n        # XXX really should distinguish between \"couldn't find\n        # external 'zip' command\" and \"zip failed\".\n        raise ExecError(\"unable to create zip file '%s': \"\n            \"could neither import the 'zipfile' module nor \"\n            \"find a standalone zip utility\") % zip_filename\n\ndef _make_zipfile(base_name, base_dir, verbose=0, dry_run=0, logger=None):\n    \"\"\"Create a zip file from all the files under 'base_dir'.\n\n    The output zip file will be named 'base_name' + \".zip\".  Uses either the\n    \"zipfile\" Python module (if available) or the InfoZIP \"zip\" utility\n    (if installed and found on the default search path).  If neither tool is\n    available, raises ExecError.  Returns the name of the output zip\n    file.\n    \"\"\"\n    zip_filename = base_name + \".zip\"\n    archive_dir = os.path.dirname(base_name)\n\n    if not os.path.exists(archive_dir):\n        if logger is not None:\n            logger.info(\"creating %s\", archive_dir)\n        if not dry_run:\n            os.makedirs(archive_dir)\n\n    # If zipfile module is not available, try spawning an external 'zip'\n    # command.\n    try:\n        import zipfile\n    except ImportError:\n        zipfile = None\n\n    if zipfile is None:\n        _call_external_zip(base_dir, zip_filename, verbose, dry_run)\n    else:\n        if logger is not None:\n            logger.info(\"creating '%s' and adding '%s' to it\",\n                        zip_filename, base_dir)\n\n        if not dry_run:\n            zip = zipfile.ZipFile(zip_filename, \"w\",\n                                  compression=zipfile.ZIP_DEFLATED)\n\n            for dirpath, dirnames, filenames in os.walk(base_dir):\n                for name in filenames:\n                    path = os.path.normpath(os.path.join(dirpath, name))\n                    if os.path.isfile(path):\n                        zip.write(path, path)\n                        if logger is not None:\n                            logger.info(\"adding '%s'\", path)\n            zip.close()\n\n    return zip_filename\n\n_ARCHIVE_FORMATS = {\n    'gztar': (_make_tarball, [('compress', 'gzip')], \"gzip'ed tar-file\"),\n    'bztar': (_make_tarball, [('compress', 'bzip2')], \"bzip2'ed tar-file\"),\n    'tar':   (_make_tarball, [('compress', None)], \"uncompressed tar file\"),\n    'zip':   (_make_zipfile, [], \"ZIP file\"),\n    }\n\nif _BZ2_SUPPORTED:\n    _ARCHIVE_FORMATS['bztar'] = (_make_tarball, [('compress', 'bzip2')],\n                                \"bzip2'ed tar-file\")\n\ndef get_archive_formats():\n    \"\"\"Returns a list of supported formats for archiving and unarchiving.\n\n    Each element of the returned sequence is a tuple (name, description)\n    \"\"\"\n    formats = [(name, registry[2]) for name, registry in\n               _ARCHIVE_FORMATS.items()]\n    formats.sort()\n    return formats\n\ndef register_archive_format(name, function, extra_args=None, description=''):\n    \"\"\"Registers an archive format.\n\n    name is the name of the format. function is the callable that will be\n    used to create archives. If provided, extra_args is a sequence of\n    (name, value) tuples that will be passed as arguments to the callable.\n    description can be provided to describe the format, and will be returned\n    by the get_archive_formats() function.\n    \"\"\"\n    if extra_args is None:\n        extra_args = []\n    if not isinstance(function, collections.Callable):\n        raise TypeError('The %s object is not callable' % function)\n    if not isinstance(extra_args, (tuple, list)):\n        raise TypeError('extra_args needs to be a sequence')\n    for element in extra_args:\n        if not isinstance(element, (tuple, list)) or len(element) !=2:\n            raise TypeError('extra_args elements are : (arg_name, value)')\n\n    _ARCHIVE_FORMATS[name] = (function, extra_args, description)\n\ndef unregister_archive_format(name):\n    del _ARCHIVE_FORMATS[name]\n\ndef make_archive(base_name, format, root_dir=None, base_dir=None, verbose=0,\n                 dry_run=0, owner=None, group=None, logger=None):\n    \"\"\"Create an archive file (eg. zip or tar).\n\n    'base_name' is the name of the file to create, minus any format-specific\n    extension; 'format' is the archive format: one of \"zip\", \"tar\", \"bztar\"\n    or \"gztar\".\n\n    'root_dir' is a directory that will be the root directory of the\n    archive; ie. we typically chdir into 'root_dir' before creating the\n    archive.  'base_dir' is the directory where we start archiving from;\n    ie. 'base_dir' will be the common prefix of all files and\n    directories in the archive.  'root_dir' and 'base_dir' both default\n    to the current directory.  Returns the name of the archive file.\n\n    'owner' and 'group' are used when creating a tar archive. By default,\n    uses the current owner and group.\n    \"\"\"\n    save_cwd = os.getcwd()\n    if root_dir is not None:\n        if logger is not None:\n            logger.debug(\"changing into '%s'\", root_dir)\n        base_name = os.path.abspath(base_name)\n        if not dry_run:\n            os.chdir(root_dir)\n\n    if base_dir is None:\n        base_dir = os.curdir\n\n    kwargs = {'dry_run': dry_run, 'logger': logger}\n\n    try:\n        format_info = _ARCHIVE_FORMATS[format]\n    except KeyError:\n        raise ValueError(\"unknown archive format '%s'\" % format)\n\n    func = format_info[0]\n    for arg, val in format_info[1]:\n        kwargs[arg] = val\n\n    if format != 'zip':\n        kwargs['owner'] = owner\n        kwargs['group'] = group\n\n    try:\n        filename = func(base_name, base_dir, **kwargs)\n    finally:\n        if root_dir is not None:\n            if logger is not None:\n                logger.debug(\"changing back to '%s'\", save_cwd)\n            os.chdir(save_cwd)\n\n    return filename\n\n\ndef get_unpack_formats():\n    \"\"\"Returns a list of supported formats for unpacking.\n\n    Each element of the returned sequence is a tuple\n    (name, extensions, description)\n    \"\"\"\n    formats = [(name, info[0], info[3]) for name, info in\n               _UNPACK_FORMATS.items()]\n    formats.sort()\n    return formats\n\ndef _check_unpack_options(extensions, function, extra_args):\n    \"\"\"Checks what gets registered as an unpacker.\"\"\"\n    # first make sure no other unpacker is registered for this extension\n    existing_extensions = {}\n    for name, info in _UNPACK_FORMATS.items():\n        for ext in info[0]:\n            existing_extensions[ext] = name\n\n    for extension in extensions:\n        if extension in existing_extensions:\n            msg = '%s is already registered for \"%s\"'\n            raise RegistryError(msg % (extension,\n                                       existing_extensions[extension]))\n\n    if not isinstance(function, collections.Callable):\n        raise TypeError('The registered function must be a callable')\n\n\ndef register_unpack_format(name, extensions, function, extra_args=None,\n                           description=''):\n    \"\"\"Registers an unpack format.\n\n    `name` is the name of the format. `extensions` is a list of extensions\n    corresponding to the format.\n\n    `function` is the callable that will be\n    used to unpack archives. The callable will receive archives to unpack.\n    If it's unable to handle an archive, it needs to raise a ReadError\n    exception.\n\n    If provided, `extra_args` is a sequence of\n    (name, value) tuples that will be passed as arguments to the callable.\n    description can be provided to describe the format, and will be returned\n    by the get_unpack_formats() function.\n    \"\"\"\n    if extra_args is None:\n        extra_args = []\n    _check_unpack_options(extensions, function, extra_args)\n    _UNPACK_FORMATS[name] = extensions, function, extra_args, description\n\ndef unregister_unpack_format(name):\n    \"\"\"Removes the pack format from the registry.\"\"\"\n    del _UNPACK_FORMATS[name]\n\ndef _ensure_directory(path):\n    \"\"\"Ensure that the parent directory of `path` exists\"\"\"\n    dirname = os.path.dirname(path)\n    if not os.path.isdir(dirname):\n        os.makedirs(dirname)\n\ndef _unpack_zipfile(filename, extract_dir):\n    \"\"\"Unpack zip `filename` to `extract_dir`\n    \"\"\"\n    try:\n        import zipfile\n    except ImportError:\n        raise ReadError('zlib not supported, cannot unpack this archive.')\n\n    if not zipfile.is_zipfile(filename):\n        raise ReadError(\"%s is not a zip file\" % filename)\n\n    zip = zipfile.ZipFile(filename)\n    try:\n        for info in zip.infolist():\n            name = info.filename\n\n            # don't extract absolute paths or ones with .. in them\n            if name.startswith('/') or '..' in name:\n                continue\n\n            target = os.path.join(extract_dir, *name.split('/'))\n            if not target:\n                continue\n\n            _ensure_directory(target)\n            if not name.endswith('/'):\n                # file\n                data = zip.read(info.filename)\n                f = open(target, 'wb')\n                try:\n                    f.write(data)\n                finally:\n                    f.close()\n                    del data\n    finally:\n        zip.close()\n\ndef _unpack_tarfile(filename, extract_dir):\n    \"\"\"Unpack tar/tar.gz/tar.bz2 `filename` to `extract_dir`\n    \"\"\"\n    try:\n        tarobj = tarfile.open(filename)\n    except tarfile.TarError:\n        raise ReadError(\n            \"%s is not a compressed or uncompressed tar file\" % filename)\n    try:\n        tarobj.extractall(extract_dir)\n    finally:\n        tarobj.close()\n\n_UNPACK_FORMATS = {\n    'gztar': (['.tar.gz', '.tgz'], _unpack_tarfile, [], \"gzip'ed tar-file\"),\n    'tar':   (['.tar'], _unpack_tarfile, [], \"uncompressed tar file\"),\n    'zip':   (['.zip'], _unpack_zipfile, [], \"ZIP file\")\n    }\n\nif _BZ2_SUPPORTED:\n    _UNPACK_FORMATS['bztar'] = (['.bz2'], _unpack_tarfile, [],\n                                \"bzip2'ed tar-file\")\n\ndef _find_unpack_format(filename):\n    for name, info in _UNPACK_FORMATS.items():\n        for extension in info[0]:\n            if filename.endswith(extension):\n                return name\n    return None\n\ndef unpack_archive(filename, extract_dir=None, format=None):\n    \"\"\"Unpack an archive.\n\n    `filename` is the name of the archive.\n\n    `extract_dir` is the name of the target directory, where the archive\n    is unpacked. If not provided, the current working directory is used.\n\n    `format` is the archive format: one of \"zip\", \"tar\", or \"gztar\". Or any\n    other registered format. If not provided, unpack_archive will use the\n    filename extension and see if an unpacker was registered for that\n    extension.\n\n    In case none is found, a ValueError is raised.\n    \"\"\"\n    if extract_dir is None:\n        extract_dir = os.getcwd()\n\n    if format is not None:\n        try:\n            format_info = _UNPACK_FORMATS[format]\n        except KeyError:\n            raise ValueError(\"Unknown unpack format '{0}'\".format(format))\n\n        func = format_info[1]\n        func(filename, extract_dir, **dict(format_info[2]))\n    else:\n        # we need to look at the registered unpackers supported extensions\n        format = _find_unpack_format(filename)\n        if format is None:\n            raise ReadError(\"Unknown archive format '{0}'\".format(filename))\n\n        func = _UNPACK_FORMATS[format][1]\n        kwargs = dict(_UNPACK_FORMATS[format][2])\n        func(filename, extract_dir, **kwargs)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/_backport/sysconfig.cfg",
    "content": "[posix_prefix]\n# Configuration directories.  Some of these come straight out of the\n# configure script.  They are for implementing the other variables, not to\n# be used directly in [resource_locations].\nconfdir = /etc\ndatadir = /usr/share\nlibdir = /usr/lib\nstatedir = /var\n# User resource directory\nlocal = ~/.local/{distribution.name}\n\nstdlib = {base}/lib/python{py_version_short}\nplatstdlib = {platbase}/lib/python{py_version_short}\npurelib = {base}/lib/python{py_version_short}/site-packages\nplatlib = {platbase}/lib/python{py_version_short}/site-packages\ninclude = {base}/include/python{py_version_short}{abiflags}\nplatinclude = {platbase}/include/python{py_version_short}{abiflags}\ndata = {base}\n\n[posix_home]\nstdlib = {base}/lib/python\nplatstdlib = {base}/lib/python\npurelib = {base}/lib/python\nplatlib = {base}/lib/python\ninclude = {base}/include/python\nplatinclude = {base}/include/python\nscripts = {base}/bin\ndata = {base}\n\n[nt]\nstdlib = {base}/Lib\nplatstdlib = {base}/Lib\npurelib = {base}/Lib/site-packages\nplatlib = {base}/Lib/site-packages\ninclude = {base}/Include\nplatinclude = {base}/Include\nscripts = {base}/Scripts\ndata = {base}\n\n[os2]\nstdlib = {base}/Lib\nplatstdlib = {base}/Lib\npurelib = {base}/Lib/site-packages\nplatlib = {base}/Lib/site-packages\ninclude = {base}/Include\nplatinclude = {base}/Include\nscripts = {base}/Scripts\ndata = {base}\n\n[os2_home]\nstdlib = {userbase}/lib/python{py_version_short}\nplatstdlib = {userbase}/lib/python{py_version_short}\npurelib = {userbase}/lib/python{py_version_short}/site-packages\nplatlib = {userbase}/lib/python{py_version_short}/site-packages\ninclude = {userbase}/include/python{py_version_short}\nscripts = {userbase}/bin\ndata = {userbase}\n\n[nt_user]\nstdlib = {userbase}/Python{py_version_nodot}\nplatstdlib = {userbase}/Python{py_version_nodot}\npurelib = {userbase}/Python{py_version_nodot}/site-packages\nplatlib = {userbase}/Python{py_version_nodot}/site-packages\ninclude = {userbase}/Python{py_version_nodot}/Include\nscripts = {userbase}/Scripts\ndata = {userbase}\n\n[posix_user]\nstdlib = {userbase}/lib/python{py_version_short}\nplatstdlib = {userbase}/lib/python{py_version_short}\npurelib = {userbase}/lib/python{py_version_short}/site-packages\nplatlib = {userbase}/lib/python{py_version_short}/site-packages\ninclude = {userbase}/include/python{py_version_short}\nscripts = {userbase}/bin\ndata = {userbase}\n\n[osx_framework_user]\nstdlib = {userbase}/lib/python\nplatstdlib = {userbase}/lib/python\npurelib = {userbase}/lib/python/site-packages\nplatlib = {userbase}/lib/python/site-packages\ninclude = {userbase}/include\nscripts = {userbase}/bin\ndata = {userbase}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/_backport/sysconfig.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2012 The Python Software Foundation.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\n\"\"\"Access to Python's configuration information.\"\"\"\n\nimport codecs\nimport os\nimport re\nimport sys\nfrom os.path import pardir, realpath\ntry:\n    import configparser\nexcept ImportError:\n    import ConfigParser as configparser\n\n\n__all__ = [\n    'get_config_h_filename',\n    'get_config_var',\n    'get_config_vars',\n    'get_makefile_filename',\n    'get_path',\n    'get_path_names',\n    'get_paths',\n    'get_platform',\n    'get_python_version',\n    'get_scheme_names',\n    'parse_config_h',\n]\n\n\ndef _safe_realpath(path):\n    try:\n        return realpath(path)\n    except OSError:\n        return path\n\n\nif sys.executable:\n    _PROJECT_BASE = os.path.dirname(_safe_realpath(sys.executable))\nelse:\n    # sys.executable can be empty if argv[0] has been changed and Python is\n    # unable to retrieve the real program name\n    _PROJECT_BASE = _safe_realpath(os.getcwd())\n\nif os.name == \"nt\" and \"pcbuild\" in _PROJECT_BASE[-8:].lower():\n    _PROJECT_BASE = _safe_realpath(os.path.join(_PROJECT_BASE, pardir))\n# PC/VS7.1\nif os.name == \"nt\" and \"\\\\pc\\\\v\" in _PROJECT_BASE[-10:].lower():\n    _PROJECT_BASE = _safe_realpath(os.path.join(_PROJECT_BASE, pardir, pardir))\n# PC/AMD64\nif os.name == \"nt\" and \"\\\\pcbuild\\\\amd64\" in _PROJECT_BASE[-14:].lower():\n    _PROJECT_BASE = _safe_realpath(os.path.join(_PROJECT_BASE, pardir, pardir))\n\n\ndef is_python_build():\n    for fn in (\"Setup.dist\", \"Setup.local\"):\n        if os.path.isfile(os.path.join(_PROJECT_BASE, \"Modules\", fn)):\n            return True\n    return False\n\n_PYTHON_BUILD = is_python_build()\n\n_cfg_read = False\n\ndef _ensure_cfg_read():\n    global _cfg_read\n    if not _cfg_read:\n        from ..resources import finder\n        backport_package = __name__.rsplit('.', 1)[0]\n        _finder = finder(backport_package)\n        _cfgfile = _finder.find('sysconfig.cfg')\n        assert _cfgfile, 'sysconfig.cfg exists'\n        with _cfgfile.as_stream() as s:\n            _SCHEMES.readfp(s)\n        if _PYTHON_BUILD:\n            for scheme in ('posix_prefix', 'posix_home'):\n                _SCHEMES.set(scheme, 'include', '{srcdir}/Include')\n                _SCHEMES.set(scheme, 'platinclude', '{projectbase}/.')\n\n        _cfg_read = True\n\n\n_SCHEMES = configparser.RawConfigParser()\n_VAR_REPL = re.compile(r'\\{([^{]*?)\\}')\n\ndef _expand_globals(config):\n    _ensure_cfg_read()\n    if config.has_section('globals'):\n        globals = config.items('globals')\n    else:\n        globals = tuple()\n\n    sections = config.sections()\n    for section in sections:\n        if section == 'globals':\n            continue\n        for option, value in globals:\n            if config.has_option(section, option):\n                continue\n            config.set(section, option, value)\n    config.remove_section('globals')\n\n    # now expanding local variables defined in the cfg file\n    #\n    for section in config.sections():\n        variables = dict(config.items(section))\n\n        def _replacer(matchobj):\n            name = matchobj.group(1)\n            if name in variables:\n                return variables[name]\n            return matchobj.group(0)\n\n        for option, value in config.items(section):\n            config.set(section, option, _VAR_REPL.sub(_replacer, value))\n\n#_expand_globals(_SCHEMES)\n\n # FIXME don't rely on sys.version here, its format is an implementation detail\n # of CPython, use sys.version_info or sys.hexversion\n_PY_VERSION = sys.version.split()[0]\n_PY_VERSION_SHORT = sys.version[:3]\n_PY_VERSION_SHORT_NO_DOT = _PY_VERSION[0] + _PY_VERSION[2]\n_PREFIX = os.path.normpath(sys.prefix)\n_EXEC_PREFIX = os.path.normpath(sys.exec_prefix)\n_CONFIG_VARS = None\n_USER_BASE = None\n\n\ndef _subst_vars(path, local_vars):\n    \"\"\"In the string `path`, replace tokens like {some.thing} with the\n    corresponding value from the map `local_vars`.\n\n    If there is no corresponding value, leave the token unchanged.\n    \"\"\"\n    def _replacer(matchobj):\n        name = matchobj.group(1)\n        if name in local_vars:\n            return local_vars[name]\n        elif name in os.environ:\n            return os.environ[name]\n        return matchobj.group(0)\n    return _VAR_REPL.sub(_replacer, path)\n\n\ndef _extend_dict(target_dict, other_dict):\n    target_keys = target_dict.keys()\n    for key, value in other_dict.items():\n        if key in target_keys:\n            continue\n        target_dict[key] = value\n\n\ndef _expand_vars(scheme, vars):\n    res = {}\n    if vars is None:\n        vars = {}\n    _extend_dict(vars, get_config_vars())\n\n    for key, value in _SCHEMES.items(scheme):\n        if os.name in ('posix', 'nt'):\n            value = os.path.expanduser(value)\n        res[key] = os.path.normpath(_subst_vars(value, vars))\n    return res\n\n\ndef format_value(value, vars):\n    def _replacer(matchobj):\n        name = matchobj.group(1)\n        if name in vars:\n            return vars[name]\n        return matchobj.group(0)\n    return _VAR_REPL.sub(_replacer, value)\n\n\ndef _get_default_scheme():\n    if os.name == 'posix':\n        # the default scheme for posix is posix_prefix\n        return 'posix_prefix'\n    return os.name\n\n\ndef _getuserbase():\n    env_base = os.environ.get(\"PYTHONUSERBASE\", None)\n\n    def joinuser(*args):\n        return os.path.expanduser(os.path.join(*args))\n\n    # what about 'os2emx', 'riscos' ?\n    if os.name == \"nt\":\n        base = os.environ.get(\"APPDATA\") or \"~\"\n        if env_base:\n            return env_base\n        else:\n            return joinuser(base, \"Python\")\n\n    if sys.platform == \"darwin\":\n        framework = get_config_var(\"PYTHONFRAMEWORK\")\n        if framework:\n            if env_base:\n                return env_base\n            else:\n                return joinuser(\"~\", \"Library\", framework, \"%d.%d\" %\n                                sys.version_info[:2])\n\n    if env_base:\n        return env_base\n    else:\n        return joinuser(\"~\", \".local\")\n\n\ndef _parse_makefile(filename, vars=None):\n    \"\"\"Parse a Makefile-style file.\n\n    A dictionary containing name/value pairs is returned.  If an\n    optional dictionary is passed in as the second argument, it is\n    used instead of a new dictionary.\n    \"\"\"\n    # Regexes needed for parsing Makefile (and similar syntaxes,\n    # like old-style Setup files).\n    _variable_rx = re.compile(r\"([a-zA-Z][a-zA-Z0-9_]+)\\s*=\\s*(.*)\")\n    _findvar1_rx = re.compile(r\"\\$\\(([A-Za-z][A-Za-z0-9_]*)\\)\")\n    _findvar2_rx = re.compile(r\"\\${([A-Za-z][A-Za-z0-9_]*)}\")\n\n    if vars is None:\n        vars = {}\n    done = {}\n    notdone = {}\n\n    with codecs.open(filename, encoding='utf-8', errors=\"surrogateescape\") as f:\n        lines = f.readlines()\n\n    for line in lines:\n        if line.startswith('#') or line.strip() == '':\n            continue\n        m = _variable_rx.match(line)\n        if m:\n            n, v = m.group(1, 2)\n            v = v.strip()\n            # `$$' is a literal `$' in make\n            tmpv = v.replace('$$', '')\n\n            if \"$\" in tmpv:\n                notdone[n] = v\n            else:\n                try:\n                    v = int(v)\n                except ValueError:\n                    # insert literal `$'\n                    done[n] = v.replace('$$', '$')\n                else:\n                    done[n] = v\n\n    # do variable interpolation here\n    variables = list(notdone.keys())\n\n    # Variables with a 'PY_' prefix in the makefile. These need to\n    # be made available without that prefix through sysconfig.\n    # Special care is needed to ensure that variable expansion works, even\n    # if the expansion uses the name without a prefix.\n    renamed_variables = ('CFLAGS', 'LDFLAGS', 'CPPFLAGS')\n\n    while len(variables) > 0:\n        for name in tuple(variables):\n            value = notdone[name]\n            m = _findvar1_rx.search(value) or _findvar2_rx.search(value)\n            if m is not None:\n                n = m.group(1)\n                found = True\n                if n in done:\n                    item = str(done[n])\n                elif n in notdone:\n                    # get it on a subsequent round\n                    found = False\n                elif n in os.environ:\n                    # do it like make: fall back to environment\n                    item = os.environ[n]\n\n                elif n in renamed_variables:\n                    if (name.startswith('PY_') and\n                        name[3:] in renamed_variables):\n                        item = \"\"\n\n                    elif 'PY_' + n in notdone:\n                        found = False\n\n                    else:\n                        item = str(done['PY_' + n])\n\n                else:\n                    done[n] = item = \"\"\n\n                if found:\n                    after = value[m.end():]\n                    value = value[:m.start()] + item + after\n                    if \"$\" in after:\n                        notdone[name] = value\n                    else:\n                        try:\n                            value = int(value)\n                        except ValueError:\n                            done[name] = value.strip()\n                        else:\n                            done[name] = value\n                        variables.remove(name)\n\n                        if (name.startswith('PY_') and\n                            name[3:] in renamed_variables):\n\n                            name = name[3:]\n                            if name not in done:\n                                done[name] = value\n\n            else:\n                # bogus variable reference (e.g. \"prefix=$/opt/python\");\n                # just drop it since we can't deal\n                done[name] = value\n                variables.remove(name)\n\n    # strip spurious spaces\n    for k, v in done.items():\n        if isinstance(v, str):\n            done[k] = v.strip()\n\n    # save the results in the global dictionary\n    vars.update(done)\n    return vars\n\n\ndef get_makefile_filename():\n    \"\"\"Return the path of the Makefile.\"\"\"\n    if _PYTHON_BUILD:\n        return os.path.join(_PROJECT_BASE, \"Makefile\")\n    if hasattr(sys, 'abiflags'):\n        config_dir_name = 'config-%s%s' % (_PY_VERSION_SHORT, sys.abiflags)\n    else:\n        config_dir_name = 'config'\n    return os.path.join(get_path('stdlib'), config_dir_name, 'Makefile')\n\n\ndef _init_posix(vars):\n    \"\"\"Initialize the module as appropriate for POSIX systems.\"\"\"\n    # load the installed Makefile:\n    makefile = get_makefile_filename()\n    try:\n        _parse_makefile(makefile, vars)\n    except IOError as e:\n        msg = \"invalid Python installation: unable to open %s\" % makefile\n        if hasattr(e, \"strerror\"):\n            msg = msg + \" (%s)\" % e.strerror\n        raise IOError(msg)\n    # load the installed pyconfig.h:\n    config_h = get_config_h_filename()\n    try:\n        with open(config_h) as f:\n            parse_config_h(f, vars)\n    except IOError as e:\n        msg = \"invalid Python installation: unable to open %s\" % config_h\n        if hasattr(e, \"strerror\"):\n            msg = msg + \" (%s)\" % e.strerror\n        raise IOError(msg)\n    # On AIX, there are wrong paths to the linker scripts in the Makefile\n    # -- these paths are relative to the Python source, but when installed\n    # the scripts are in another directory.\n    if _PYTHON_BUILD:\n        vars['LDSHARED'] = vars['BLDSHARED']\n\n\ndef _init_non_posix(vars):\n    \"\"\"Initialize the module as appropriate for NT\"\"\"\n    # set basic install directories\n    vars['LIBDEST'] = get_path('stdlib')\n    vars['BINLIBDEST'] = get_path('platstdlib')\n    vars['INCLUDEPY'] = get_path('include')\n    vars['SO'] = '.pyd'\n    vars['EXE'] = '.exe'\n    vars['VERSION'] = _PY_VERSION_SHORT_NO_DOT\n    vars['BINDIR'] = os.path.dirname(_safe_realpath(sys.executable))\n\n#\n# public APIs\n#\n\n\ndef parse_config_h(fp, vars=None):\n    \"\"\"Parse a config.h-style file.\n\n    A dictionary containing name/value pairs is returned.  If an\n    optional dictionary is passed in as the second argument, it is\n    used instead of a new dictionary.\n    \"\"\"\n    if vars is None:\n        vars = {}\n    define_rx = re.compile(\"#define ([A-Z][A-Za-z0-9_]+) (.*)\\n\")\n    undef_rx = re.compile(\"/[*] #undef ([A-Z][A-Za-z0-9_]+) [*]/\\n\")\n\n    while True:\n        line = fp.readline()\n        if not line:\n            break\n        m = define_rx.match(line)\n        if m:\n            n, v = m.group(1, 2)\n            try:\n                v = int(v)\n            except ValueError:\n                pass\n            vars[n] = v\n        else:\n            m = undef_rx.match(line)\n            if m:\n                vars[m.group(1)] = 0\n    return vars\n\n\ndef get_config_h_filename():\n    \"\"\"Return the path of pyconfig.h.\"\"\"\n    if _PYTHON_BUILD:\n        if os.name == \"nt\":\n            inc_dir = os.path.join(_PROJECT_BASE, \"PC\")\n        else:\n            inc_dir = _PROJECT_BASE\n    else:\n        inc_dir = get_path('platinclude')\n    return os.path.join(inc_dir, 'pyconfig.h')\n\n\ndef get_scheme_names():\n    \"\"\"Return a tuple containing the schemes names.\"\"\"\n    return tuple(sorted(_SCHEMES.sections()))\n\n\ndef get_path_names():\n    \"\"\"Return a tuple containing the paths names.\"\"\"\n    # xxx see if we want a static list\n    return _SCHEMES.options('posix_prefix')\n\n\ndef get_paths(scheme=_get_default_scheme(), vars=None, expand=True):\n    \"\"\"Return a mapping containing an install scheme.\n\n    ``scheme`` is the install scheme name. If not provided, it will\n    return the default scheme for the current platform.\n    \"\"\"\n    _ensure_cfg_read()\n    if expand:\n        return _expand_vars(scheme, vars)\n    else:\n        return dict(_SCHEMES.items(scheme))\n\n\ndef get_path(name, scheme=_get_default_scheme(), vars=None, expand=True):\n    \"\"\"Return a path corresponding to the scheme.\n\n    ``scheme`` is the install scheme name.\n    \"\"\"\n    return get_paths(scheme, vars, expand)[name]\n\n\ndef get_config_vars(*args):\n    \"\"\"With no arguments, return a dictionary of all configuration\n    variables relevant for the current platform.\n\n    On Unix, this means every variable defined in Python's installed Makefile;\n    On Windows and Mac OS it's a much smaller set.\n\n    With arguments, return a list of values that result from looking up\n    each argument in the configuration variable dictionary.\n    \"\"\"\n    global _CONFIG_VARS\n    if _CONFIG_VARS is None:\n        _CONFIG_VARS = {}\n        # Normalized versions of prefix and exec_prefix are handy to have;\n        # in fact, these are the standard versions used most places in the\n        # distutils2 module.\n        _CONFIG_VARS['prefix'] = _PREFIX\n        _CONFIG_VARS['exec_prefix'] = _EXEC_PREFIX\n        _CONFIG_VARS['py_version'] = _PY_VERSION\n        _CONFIG_VARS['py_version_short'] = _PY_VERSION_SHORT\n        _CONFIG_VARS['py_version_nodot'] = _PY_VERSION[0] + _PY_VERSION[2]\n        _CONFIG_VARS['base'] = _PREFIX\n        _CONFIG_VARS['platbase'] = _EXEC_PREFIX\n        _CONFIG_VARS['projectbase'] = _PROJECT_BASE\n        try:\n            _CONFIG_VARS['abiflags'] = sys.abiflags\n        except AttributeError:\n            # sys.abiflags may not be defined on all platforms.\n            _CONFIG_VARS['abiflags'] = ''\n\n        if os.name in ('nt', 'os2'):\n            _init_non_posix(_CONFIG_VARS)\n        if os.name == 'posix':\n            _init_posix(_CONFIG_VARS)\n        # Setting 'userbase' is done below the call to the\n        # init function to enable using 'get_config_var' in\n        # the init-function.\n        if sys.version >= '2.6':\n            _CONFIG_VARS['userbase'] = _getuserbase()\n\n        if 'srcdir' not in _CONFIG_VARS:\n            _CONFIG_VARS['srcdir'] = _PROJECT_BASE\n        else:\n            _CONFIG_VARS['srcdir'] = _safe_realpath(_CONFIG_VARS['srcdir'])\n\n        # Convert srcdir into an absolute path if it appears necessary.\n        # Normally it is relative to the build directory.  However, during\n        # testing, for example, we might be running a non-installed python\n        # from a different directory.\n        if _PYTHON_BUILD and os.name == \"posix\":\n            base = _PROJECT_BASE\n            try:\n                cwd = os.getcwd()\n            except OSError:\n                cwd = None\n            if (not os.path.isabs(_CONFIG_VARS['srcdir']) and\n                base != cwd):\n                # srcdir is relative and we are not in the same directory\n                # as the executable. Assume executable is in the build\n                # directory and make srcdir absolute.\n                srcdir = os.path.join(base, _CONFIG_VARS['srcdir'])\n                _CONFIG_VARS['srcdir'] = os.path.normpath(srcdir)\n\n        if sys.platform == 'darwin':\n            kernel_version = os.uname()[2]  # Kernel version (8.4.3)\n            major_version = int(kernel_version.split('.')[0])\n\n            if major_version < 8:\n                # On Mac OS X before 10.4, check if -arch and -isysroot\n                # are in CFLAGS or LDFLAGS and remove them if they are.\n                # This is needed when building extensions on a 10.3 system\n                # using a universal build of python.\n                for key in ('LDFLAGS', 'BASECFLAGS',\n                        # a number of derived variables. These need to be\n                        # patched up as well.\n                        'CFLAGS', 'PY_CFLAGS', 'BLDSHARED'):\n                    flags = _CONFIG_VARS[key]\n                    flags = re.sub(r'-arch\\s+\\w+\\s', ' ', flags)\n                    flags = re.sub('-isysroot [^ \\t]*', ' ', flags)\n                    _CONFIG_VARS[key] = flags\n            else:\n                # Allow the user to override the architecture flags using\n                # an environment variable.\n                # NOTE: This name was introduced by Apple in OSX 10.5 and\n                # is used by several scripting languages distributed with\n                # that OS release.\n                if 'ARCHFLAGS' in os.environ:\n                    arch = os.environ['ARCHFLAGS']\n                    for key in ('LDFLAGS', 'BASECFLAGS',\n                        # a number of derived variables. These need to be\n                        # patched up as well.\n                        'CFLAGS', 'PY_CFLAGS', 'BLDSHARED'):\n\n                        flags = _CONFIG_VARS[key]\n                        flags = re.sub(r'-arch\\s+\\w+\\s', ' ', flags)\n                        flags = flags + ' ' + arch\n                        _CONFIG_VARS[key] = flags\n\n                # If we're on OSX 10.5 or later and the user tries to\n                # compiles an extension using an SDK that is not present\n                # on the current machine it is better to not use an SDK\n                # than to fail.\n                #\n                # The major usecase for this is users using a Python.org\n                # binary installer  on OSX 10.6: that installer uses\n                # the 10.4u SDK, but that SDK is not installed by default\n                # when you install Xcode.\n                #\n                CFLAGS = _CONFIG_VARS.get('CFLAGS', '')\n                m = re.search(r'-isysroot\\s+(\\S+)', CFLAGS)\n                if m is not None:\n                    sdk = m.group(1)\n                    if not os.path.exists(sdk):\n                        for key in ('LDFLAGS', 'BASECFLAGS',\n                             # a number of derived variables. These need to be\n                             # patched up as well.\n                            'CFLAGS', 'PY_CFLAGS', 'BLDSHARED'):\n\n                            flags = _CONFIG_VARS[key]\n                            flags = re.sub(r'-isysroot\\s+\\S+(\\s|$)', ' ', flags)\n                            _CONFIG_VARS[key] = flags\n\n    if args:\n        vals = []\n        for name in args:\n            vals.append(_CONFIG_VARS.get(name))\n        return vals\n    else:\n        return _CONFIG_VARS\n\n\ndef get_config_var(name):\n    \"\"\"Return the value of a single variable using the dictionary returned by\n    'get_config_vars()'.\n\n    Equivalent to get_config_vars().get(name)\n    \"\"\"\n    return get_config_vars().get(name)\n\n\ndef get_platform():\n    \"\"\"Return a string that identifies the current platform.\n\n    This is used mainly to distinguish platform-specific build directories and\n    platform-specific built distributions.  Typically includes the OS name\n    and version and the architecture (as supplied by 'os.uname()'),\n    although the exact information included depends on the OS; eg. for IRIX\n    the architecture isn't particularly important (IRIX only runs on SGI\n    hardware), but for Linux the kernel version isn't particularly\n    important.\n\n    Examples of returned values:\n       linux-i586\n       linux-alpha (?)\n       solaris-2.6-sun4u\n       irix-5.3\n       irix64-6.2\n\n    Windows will return one of:\n       win-amd64 (64bit Windows on AMD64 (aka x86_64, Intel64, EM64T, etc)\n       win-ia64 (64bit Windows on Itanium)\n       win32 (all others - specifically, sys.platform is returned)\n\n    For other non-POSIX platforms, currently just returns 'sys.platform'.\n    \"\"\"\n    if os.name == 'nt':\n        # sniff sys.version for architecture.\n        prefix = \" bit (\"\n        i = sys.version.find(prefix)\n        if i == -1:\n            return sys.platform\n        j = sys.version.find(\")\", i)\n        look = sys.version[i+len(prefix):j].lower()\n        if look == 'amd64':\n            return 'win-amd64'\n        if look == 'itanium':\n            return 'win-ia64'\n        return sys.platform\n\n    if os.name != \"posix\" or not hasattr(os, 'uname'):\n        # XXX what about the architecture? NT is Intel or Alpha,\n        # Mac OS is M68k or PPC, etc.\n        return sys.platform\n\n    # Try to distinguish various flavours of Unix\n    osname, host, release, version, machine = os.uname()\n\n    # Convert the OS name to lowercase, remove '/' characters\n    # (to accommodate BSD/OS), and translate spaces (for \"Power Macintosh\")\n    osname = osname.lower().replace('/', '')\n    machine = machine.replace(' ', '_')\n    machine = machine.replace('/', '-')\n\n    if osname[:5] == \"linux\":\n        # At least on Linux/Intel, 'machine' is the processor --\n        # i386, etc.\n        # XXX what about Alpha, SPARC, etc?\n        return  \"%s-%s\" % (osname, machine)\n    elif osname[:5] == \"sunos\":\n        if release[0] >= \"5\":           # SunOS 5 == Solaris 2\n            osname = \"solaris\"\n            release = \"%d.%s\" % (int(release[0]) - 3, release[2:])\n        # fall through to standard osname-release-machine representation\n    elif osname[:4] == \"irix\":              # could be \"irix64\"!\n        return \"%s-%s\" % (osname, release)\n    elif osname[:3] == \"aix\":\n        return \"%s-%s.%s\" % (osname, version, release)\n    elif osname[:6] == \"cygwin\":\n        osname = \"cygwin\"\n        rel_re = re.compile(r'[\\d.]+')\n        m = rel_re.match(release)\n        if m:\n            release = m.group()\n    elif osname[:6] == \"darwin\":\n        #\n        # For our purposes, we'll assume that the system version from\n        # distutils' perspective is what MACOSX_DEPLOYMENT_TARGET is set\n        # to. This makes the compatibility story a bit more sane because the\n        # machine is going to compile and link as if it were\n        # MACOSX_DEPLOYMENT_TARGET.\n        cfgvars = get_config_vars()\n        macver = cfgvars.get('MACOSX_DEPLOYMENT_TARGET')\n\n        if True:\n            # Always calculate the release of the running machine,\n            # needed to determine if we can build fat binaries or not.\n\n            macrelease = macver\n            # Get the system version. Reading this plist is a documented\n            # way to get the system version (see the documentation for\n            # the Gestalt Manager)\n            try:\n                f = open('/System/Library/CoreServices/SystemVersion.plist')\n            except IOError:\n                # We're on a plain darwin box, fall back to the default\n                # behaviour.\n                pass\n            else:\n                try:\n                    m = re.search(r'<key>ProductUserVisibleVersion</key>\\s*'\n                                  r'<string>(.*?)</string>', f.read())\n                finally:\n                    f.close()\n                if m is not None:\n                    macrelease = '.'.join(m.group(1).split('.')[:2])\n                # else: fall back to the default behaviour\n\n        if not macver:\n            macver = macrelease\n\n        if macver:\n            release = macver\n            osname = \"macosx\"\n\n            if ((macrelease + '.') >= '10.4.' and\n                '-arch' in get_config_vars().get('CFLAGS', '').strip()):\n                # The universal build will build fat binaries, but not on\n                # systems before 10.4\n                #\n                # Try to detect 4-way universal builds, those have machine-type\n                # 'universal' instead of 'fat'.\n\n                machine = 'fat'\n                cflags = get_config_vars().get('CFLAGS')\n\n                archs = re.findall(r'-arch\\s+(\\S+)', cflags)\n                archs = tuple(sorted(set(archs)))\n\n                if len(archs) == 1:\n                    machine = archs[0]\n                elif archs == ('i386', 'ppc'):\n                    machine = 'fat'\n                elif archs == ('i386', 'x86_64'):\n                    machine = 'intel'\n                elif archs == ('i386', 'ppc', 'x86_64'):\n                    machine = 'fat3'\n                elif archs == ('ppc64', 'x86_64'):\n                    machine = 'fat64'\n                elif archs == ('i386', 'ppc', 'ppc64', 'x86_64'):\n                    machine = 'universal'\n                else:\n                    raise ValueError(\n                       \"Don't know machine value for archs=%r\" % (archs,))\n\n            elif machine == 'i386':\n                # On OSX the machine type returned by uname is always the\n                # 32-bit variant, even if the executable architecture is\n                # the 64-bit variant\n                if sys.maxsize >= 2**32:\n                    machine = 'x86_64'\n\n            elif machine in ('PowerPC', 'Power_Macintosh'):\n                # Pick a sane name for the PPC architecture.\n                # See 'i386' case\n                if sys.maxsize >= 2**32:\n                    machine = 'ppc64'\n                else:\n                    machine = 'ppc'\n\n    return \"%s-%s-%s\" % (osname, release, machine)\n\n\ndef get_python_version():\n    return _PY_VERSION_SHORT\n\n\ndef _print_dict(title, data):\n    for index, (key, value) in enumerate(sorted(data.items())):\n        if index == 0:\n            print('%s: ' % (title))\n        print('\\t%s = \"%s\"' % (key, value))\n\n\ndef _main():\n    \"\"\"Display all information sysconfig detains.\"\"\"\n    print('Platform: \"%s\"' % get_platform())\n    print('Python version: \"%s\"' % get_python_version())\n    print('Current installation scheme: \"%s\"' % _get_default_scheme())\n    print()\n    _print_dict('Paths', get_paths())\n    print()\n    _print_dict('Variables', get_config_vars())\n\n\nif __name__ == '__main__':\n    _main()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/_backport/tarfile.py",
    "content": "#-------------------------------------------------------------------\n# tarfile.py\n#-------------------------------------------------------------------\n# Copyright (C) 2002 Lars Gustaebel <lars@gustaebel.de>\n# All rights reserved.\n#\n# Permission  is  hereby granted,  free  of charge,  to  any person\n# obtaining a  copy of  this software  and associated documentation\n# files  (the  \"Software\"),  to   deal  in  the  Software   without\n# restriction,  including  without limitation  the  rights to  use,\n# copy, modify, merge, publish, distribute, sublicense, and/or sell\n# copies  of  the  Software,  and to  permit  persons  to  whom the\n# Software  is  furnished  to  do  so,  subject  to  the  following\n# conditions:\n#\n# The above copyright  notice and this  permission notice shall  be\n# included in all copies or substantial portions of the Software.\n#\n# THE SOFTWARE IS PROVIDED \"AS  IS\", WITHOUT WARRANTY OF ANY  KIND,\n# EXPRESS OR IMPLIED, INCLUDING  BUT NOT LIMITED TO  THE WARRANTIES\n# OF  MERCHANTABILITY,  FITNESS   FOR  A  PARTICULAR   PURPOSE  AND\n# NONINFRINGEMENT.  IN  NO  EVENT SHALL  THE  AUTHORS  OR COPYRIGHT\n# HOLDERS  BE LIABLE  FOR ANY  CLAIM, DAMAGES  OR OTHER  LIABILITY,\n# WHETHER  IN AN  ACTION OF  CONTRACT, TORT  OR OTHERWISE,  ARISING\n# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR\n# OTHER DEALINGS IN THE SOFTWARE.\n#\nfrom __future__ import print_function\n\n\"\"\"Read from and write to tar format archives.\n\"\"\"\n\n__version__ = \"$Revision$\"\n\nversion     = \"0.9.0\"\n__author__  = \"Lars Gust\\u00e4bel (lars@gustaebel.de)\"\n__date__    = \"$Date: 2011-02-25 17:42:01 +0200 (Fri, 25 Feb 2011) $\"\n__cvsid__   = \"$Id: tarfile.py 88586 2011-02-25 15:42:01Z marc-andre.lemburg $\"\n__credits__ = \"Gustavo Niemeyer, Niels Gust\\u00e4bel, Richard Townsend.\"\n\n#---------\n# Imports\n#---------\nimport sys\nimport os\nimport stat\nimport errno\nimport time\nimport struct\nimport copy\nimport re\n\ntry:\n    import grp, pwd\nexcept ImportError:\n    grp = pwd = None\n\n# os.symlink on Windows prior to 6.0 raises NotImplementedError\nsymlink_exception = (AttributeError, NotImplementedError)\ntry:\n    # WindowsError (1314) will be raised if the caller does not hold the\n    # SeCreateSymbolicLinkPrivilege privilege\n    symlink_exception += (WindowsError,)\nexcept NameError:\n    pass\n\n# from tarfile import *\n__all__ = [\"TarFile\", \"TarInfo\", \"is_tarfile\", \"TarError\"]\n\nif sys.version_info[0] < 3:\n    import __builtin__ as builtins\nelse:\n    import builtins\n\n_open = builtins.open   # Since 'open' is TarFile.open\n\n#---------------------------------------------------------\n# tar constants\n#---------------------------------------------------------\nNUL = b\"\\0\"                     # the null character\nBLOCKSIZE = 512                 # length of processing blocks\nRECORDSIZE = BLOCKSIZE * 20     # length of records\nGNU_MAGIC = b\"ustar  \\0\"        # magic gnu tar string\nPOSIX_MAGIC = b\"ustar\\x0000\"    # magic posix tar string\n\nLENGTH_NAME = 100               # maximum length of a filename\nLENGTH_LINK = 100               # maximum length of a linkname\nLENGTH_PREFIX = 155             # maximum length of the prefix field\n\nREGTYPE = b\"0\"                  # regular file\nAREGTYPE = b\"\\0\"                # regular file\nLNKTYPE = b\"1\"                  # link (inside tarfile)\nSYMTYPE = b\"2\"                  # symbolic link\nCHRTYPE = b\"3\"                  # character special device\nBLKTYPE = b\"4\"                  # block special device\nDIRTYPE = b\"5\"                  # directory\nFIFOTYPE = b\"6\"                 # fifo special device\nCONTTYPE = b\"7\"                 # contiguous file\n\nGNUTYPE_LONGNAME = b\"L\"         # GNU tar longname\nGNUTYPE_LONGLINK = b\"K\"         # GNU tar longlink\nGNUTYPE_SPARSE = b\"S\"           # GNU tar sparse file\n\nXHDTYPE = b\"x\"                  # POSIX.1-2001 extended header\nXGLTYPE = b\"g\"                  # POSIX.1-2001 global header\nSOLARIS_XHDTYPE = b\"X\"          # Solaris extended header\n\nUSTAR_FORMAT = 0                # POSIX.1-1988 (ustar) format\nGNU_FORMAT = 1                  # GNU tar format\nPAX_FORMAT = 2                  # POSIX.1-2001 (pax) format\nDEFAULT_FORMAT = GNU_FORMAT\n\n#---------------------------------------------------------\n# tarfile constants\n#---------------------------------------------------------\n# File types that tarfile supports:\nSUPPORTED_TYPES = (REGTYPE, AREGTYPE, LNKTYPE,\n                   SYMTYPE, DIRTYPE, FIFOTYPE,\n                   CONTTYPE, CHRTYPE, BLKTYPE,\n                   GNUTYPE_LONGNAME, GNUTYPE_LONGLINK,\n                   GNUTYPE_SPARSE)\n\n# File types that will be treated as a regular file.\nREGULAR_TYPES = (REGTYPE, AREGTYPE,\n                 CONTTYPE, GNUTYPE_SPARSE)\n\n# File types that are part of the GNU tar format.\nGNU_TYPES = (GNUTYPE_LONGNAME, GNUTYPE_LONGLINK,\n             GNUTYPE_SPARSE)\n\n# Fields from a pax header that override a TarInfo attribute.\nPAX_FIELDS = (\"path\", \"linkpath\", \"size\", \"mtime\",\n              \"uid\", \"gid\", \"uname\", \"gname\")\n\n# Fields from a pax header that are affected by hdrcharset.\nPAX_NAME_FIELDS = set((\"path\", \"linkpath\", \"uname\", \"gname\"))\n\n# Fields in a pax header that are numbers, all other fields\n# are treated as strings.\nPAX_NUMBER_FIELDS = {\n    \"atime\": float,\n    \"ctime\": float,\n    \"mtime\": float,\n    \"uid\": int,\n    \"gid\": int,\n    \"size\": int\n}\n\n#---------------------------------------------------------\n# Bits used in the mode field, values in octal.\n#---------------------------------------------------------\nS_IFLNK = 0o120000        # symbolic link\nS_IFREG = 0o100000        # regular file\nS_IFBLK = 0o060000        # block device\nS_IFDIR = 0o040000        # directory\nS_IFCHR = 0o020000        # character device\nS_IFIFO = 0o010000        # fifo\n\nTSUID   = 0o4000          # set UID on execution\nTSGID   = 0o2000          # set GID on execution\nTSVTX   = 0o1000          # reserved\n\nTUREAD  = 0o400           # read by owner\nTUWRITE = 0o200           # write by owner\nTUEXEC  = 0o100           # execute/search by owner\nTGREAD  = 0o040           # read by group\nTGWRITE = 0o020           # write by group\nTGEXEC  = 0o010           # execute/search by group\nTOREAD  = 0o004           # read by other\nTOWRITE = 0o002           # write by other\nTOEXEC  = 0o001           # execute/search by other\n\n#---------------------------------------------------------\n# initialization\n#---------------------------------------------------------\nif os.name in (\"nt\", \"ce\"):\n    ENCODING = \"utf-8\"\nelse:\n    ENCODING = sys.getfilesystemencoding()\n\n#---------------------------------------------------------\n# Some useful functions\n#---------------------------------------------------------\n\ndef stn(s, length, encoding, errors):\n    \"\"\"Convert a string to a null-terminated bytes object.\n    \"\"\"\n    s = s.encode(encoding, errors)\n    return s[:length] + (length - len(s)) * NUL\n\ndef nts(s, encoding, errors):\n    \"\"\"Convert a null-terminated bytes object to a string.\n    \"\"\"\n    p = s.find(b\"\\0\")\n    if p != -1:\n        s = s[:p]\n    return s.decode(encoding, errors)\n\ndef nti(s):\n    \"\"\"Convert a number field to a python number.\n    \"\"\"\n    # There are two possible encodings for a number field, see\n    # itn() below.\n    if s[0] != chr(0o200):\n        try:\n            n = int(nts(s, \"ascii\", \"strict\") or \"0\", 8)\n        except ValueError:\n            raise InvalidHeaderError(\"invalid header\")\n    else:\n        n = 0\n        for i in range(len(s) - 1):\n            n <<= 8\n            n += ord(s[i + 1])\n    return n\n\ndef itn(n, digits=8, format=DEFAULT_FORMAT):\n    \"\"\"Convert a python number to a number field.\n    \"\"\"\n    # POSIX 1003.1-1988 requires numbers to be encoded as a string of\n    # octal digits followed by a null-byte, this allows values up to\n    # (8**(digits-1))-1. GNU tar allows storing numbers greater than\n    # that if necessary. A leading 0o200 byte indicates this particular\n    # encoding, the following digits-1 bytes are a big-endian\n    # representation. This allows values up to (256**(digits-1))-1.\n    if 0 <= n < 8 ** (digits - 1):\n        s = (\"%0*o\" % (digits - 1, n)).encode(\"ascii\") + NUL\n    else:\n        if format != GNU_FORMAT or n >= 256 ** (digits - 1):\n            raise ValueError(\"overflow in number field\")\n\n        if n < 0:\n            # XXX We mimic GNU tar's behaviour with negative numbers,\n            # this could raise OverflowError.\n            n = struct.unpack(\"L\", struct.pack(\"l\", n))[0]\n\n        s = bytearray()\n        for i in range(digits - 1):\n            s.insert(0, n & 0o377)\n            n >>= 8\n        s.insert(0, 0o200)\n    return s\n\ndef calc_chksums(buf):\n    \"\"\"Calculate the checksum for a member's header by summing up all\n       characters except for the chksum field which is treated as if\n       it was filled with spaces. According to the GNU tar sources,\n       some tars (Sun and NeXT) calculate chksum with signed char,\n       which will be different if there are chars in the buffer with\n       the high bit set. So we calculate two checksums, unsigned and\n       signed.\n    \"\"\"\n    unsigned_chksum = 256 + sum(struct.unpack(\"148B\", buf[:148]) + struct.unpack(\"356B\", buf[156:512]))\n    signed_chksum = 256 + sum(struct.unpack(\"148b\", buf[:148]) + struct.unpack(\"356b\", buf[156:512]))\n    return unsigned_chksum, signed_chksum\n\ndef copyfileobj(src, dst, length=None):\n    \"\"\"Copy length bytes from fileobj src to fileobj dst.\n       If length is None, copy the entire content.\n    \"\"\"\n    if length == 0:\n        return\n    if length is None:\n        while True:\n            buf = src.read(16*1024)\n            if not buf:\n                break\n            dst.write(buf)\n        return\n\n    BUFSIZE = 16 * 1024\n    blocks, remainder = divmod(length, BUFSIZE)\n    for b in range(blocks):\n        buf = src.read(BUFSIZE)\n        if len(buf) < BUFSIZE:\n            raise IOError(\"end of file reached\")\n        dst.write(buf)\n\n    if remainder != 0:\n        buf = src.read(remainder)\n        if len(buf) < remainder:\n            raise IOError(\"end of file reached\")\n        dst.write(buf)\n    return\n\nfilemode_table = (\n    ((S_IFLNK,      \"l\"),\n     (S_IFREG,      \"-\"),\n     (S_IFBLK,      \"b\"),\n     (S_IFDIR,      \"d\"),\n     (S_IFCHR,      \"c\"),\n     (S_IFIFO,      \"p\")),\n\n    ((TUREAD,       \"r\"),),\n    ((TUWRITE,      \"w\"),),\n    ((TUEXEC|TSUID, \"s\"),\n     (TSUID,        \"S\"),\n     (TUEXEC,       \"x\")),\n\n    ((TGREAD,       \"r\"),),\n    ((TGWRITE,      \"w\"),),\n    ((TGEXEC|TSGID, \"s\"),\n     (TSGID,        \"S\"),\n     (TGEXEC,       \"x\")),\n\n    ((TOREAD,       \"r\"),),\n    ((TOWRITE,      \"w\"),),\n    ((TOEXEC|TSVTX, \"t\"),\n     (TSVTX,        \"T\"),\n     (TOEXEC,       \"x\"))\n)\n\ndef filemode(mode):\n    \"\"\"Convert a file's mode to a string of the form\n       -rwxrwxrwx.\n       Used by TarFile.list()\n    \"\"\"\n    perm = []\n    for table in filemode_table:\n        for bit, char in table:\n            if mode & bit == bit:\n                perm.append(char)\n                break\n        else:\n            perm.append(\"-\")\n    return \"\".join(perm)\n\nclass TarError(Exception):\n    \"\"\"Base exception.\"\"\"\n    pass\nclass ExtractError(TarError):\n    \"\"\"General exception for extract errors.\"\"\"\n    pass\nclass ReadError(TarError):\n    \"\"\"Exception for unreadable tar archives.\"\"\"\n    pass\nclass CompressionError(TarError):\n    \"\"\"Exception for unavailable compression methods.\"\"\"\n    pass\nclass StreamError(TarError):\n    \"\"\"Exception for unsupported operations on stream-like TarFiles.\"\"\"\n    pass\nclass HeaderError(TarError):\n    \"\"\"Base exception for header errors.\"\"\"\n    pass\nclass EmptyHeaderError(HeaderError):\n    \"\"\"Exception for empty headers.\"\"\"\n    pass\nclass TruncatedHeaderError(HeaderError):\n    \"\"\"Exception for truncated headers.\"\"\"\n    pass\nclass EOFHeaderError(HeaderError):\n    \"\"\"Exception for end of file headers.\"\"\"\n    pass\nclass InvalidHeaderError(HeaderError):\n    \"\"\"Exception for invalid headers.\"\"\"\n    pass\nclass SubsequentHeaderError(HeaderError):\n    \"\"\"Exception for missing and invalid extended headers.\"\"\"\n    pass\n\n#---------------------------\n# internal stream interface\n#---------------------------\nclass _LowLevelFile(object):\n    \"\"\"Low-level file object. Supports reading and writing.\n       It is used instead of a regular file object for streaming\n       access.\n    \"\"\"\n\n    def __init__(self, name, mode):\n        mode = {\n            \"r\": os.O_RDONLY,\n            \"w\": os.O_WRONLY | os.O_CREAT | os.O_TRUNC,\n        }[mode]\n        if hasattr(os, \"O_BINARY\"):\n            mode |= os.O_BINARY\n        self.fd = os.open(name, mode, 0o666)\n\n    def close(self):\n        os.close(self.fd)\n\n    def read(self, size):\n        return os.read(self.fd, size)\n\n    def write(self, s):\n        os.write(self.fd, s)\n\nclass _Stream(object):\n    \"\"\"Class that serves as an adapter between TarFile and\n       a stream-like object.  The stream-like object only\n       needs to have a read() or write() method and is accessed\n       blockwise.  Use of gzip or bzip2 compression is possible.\n       A stream-like object could be for example: sys.stdin,\n       sys.stdout, a socket, a tape device etc.\n\n       _Stream is intended to be used only internally.\n    \"\"\"\n\n    def __init__(self, name, mode, comptype, fileobj, bufsize):\n        \"\"\"Construct a _Stream object.\n        \"\"\"\n        self._extfileobj = True\n        if fileobj is None:\n            fileobj = _LowLevelFile(name, mode)\n            self._extfileobj = False\n\n        if comptype == '*':\n            # Enable transparent compression detection for the\n            # stream interface\n            fileobj = _StreamProxy(fileobj)\n            comptype = fileobj.getcomptype()\n\n        self.name     = name or \"\"\n        self.mode     = mode\n        self.comptype = comptype\n        self.fileobj  = fileobj\n        self.bufsize  = bufsize\n        self.buf      = b\"\"\n        self.pos      = 0\n        self.closed   = False\n\n        try:\n            if comptype == \"gz\":\n                try:\n                    import zlib\n                except ImportError:\n                    raise CompressionError(\"zlib module is not available\")\n                self.zlib = zlib\n                self.crc = zlib.crc32(b\"\")\n                if mode == \"r\":\n                    self._init_read_gz()\n                else:\n                    self._init_write_gz()\n\n            if comptype == \"bz2\":\n                try:\n                    import bz2\n                except ImportError:\n                    raise CompressionError(\"bz2 module is not available\")\n                if mode == \"r\":\n                    self.dbuf = b\"\"\n                    self.cmp = bz2.BZ2Decompressor()\n                else:\n                    self.cmp = bz2.BZ2Compressor()\n        except:\n            if not self._extfileobj:\n                self.fileobj.close()\n            self.closed = True\n            raise\n\n    def __del__(self):\n        if hasattr(self, \"closed\") and not self.closed:\n            self.close()\n\n    def _init_write_gz(self):\n        \"\"\"Initialize for writing with gzip compression.\n        \"\"\"\n        self.cmp = self.zlib.compressobj(9, self.zlib.DEFLATED,\n                                            -self.zlib.MAX_WBITS,\n                                            self.zlib.DEF_MEM_LEVEL,\n                                            0)\n        timestamp = struct.pack(\"<L\", int(time.time()))\n        self.__write(b\"\\037\\213\\010\\010\" + timestamp + b\"\\002\\377\")\n        if self.name.endswith(\".gz\"):\n            self.name = self.name[:-3]\n        # RFC1952 says we must use ISO-8859-1 for the FNAME field.\n        self.__write(self.name.encode(\"iso-8859-1\", \"replace\") + NUL)\n\n    def write(self, s):\n        \"\"\"Write string s to the stream.\n        \"\"\"\n        if self.comptype == \"gz\":\n            self.crc = self.zlib.crc32(s, self.crc)\n        self.pos += len(s)\n        if self.comptype != \"tar\":\n            s = self.cmp.compress(s)\n        self.__write(s)\n\n    def __write(self, s):\n        \"\"\"Write string s to the stream if a whole new block\n           is ready to be written.\n        \"\"\"\n        self.buf += s\n        while len(self.buf) > self.bufsize:\n            self.fileobj.write(self.buf[:self.bufsize])\n            self.buf = self.buf[self.bufsize:]\n\n    def close(self):\n        \"\"\"Close the _Stream object. No operation should be\n           done on it afterwards.\n        \"\"\"\n        if self.closed:\n            return\n\n        if self.mode == \"w\" and self.comptype != \"tar\":\n            self.buf += self.cmp.flush()\n\n        if self.mode == \"w\" and self.buf:\n            self.fileobj.write(self.buf)\n            self.buf = b\"\"\n            if self.comptype == \"gz\":\n                # The native zlib crc is an unsigned 32-bit integer, but\n                # the Python wrapper implicitly casts that to a signed C\n                # long.  So, on a 32-bit box self.crc may \"look negative\",\n                # while the same crc on a 64-bit box may \"look positive\".\n                # To avoid irksome warnings from the `struct` module, force\n                # it to look positive on all boxes.\n                self.fileobj.write(struct.pack(\"<L\", self.crc & 0xffffffff))\n                self.fileobj.write(struct.pack(\"<L\", self.pos & 0xffffFFFF))\n\n        if not self._extfileobj:\n            self.fileobj.close()\n\n        self.closed = True\n\n    def _init_read_gz(self):\n        \"\"\"Initialize for reading a gzip compressed fileobj.\n        \"\"\"\n        self.cmp = self.zlib.decompressobj(-self.zlib.MAX_WBITS)\n        self.dbuf = b\"\"\n\n        # taken from gzip.GzipFile with some alterations\n        if self.__read(2) != b\"\\037\\213\":\n            raise ReadError(\"not a gzip file\")\n        if self.__read(1) != b\"\\010\":\n            raise CompressionError(\"unsupported compression method\")\n\n        flag = ord(self.__read(1))\n        self.__read(6)\n\n        if flag & 4:\n            xlen = ord(self.__read(1)) + 256 * ord(self.__read(1))\n            self.read(xlen)\n        if flag & 8:\n            while True:\n                s = self.__read(1)\n                if not s or s == NUL:\n                    break\n        if flag & 16:\n            while True:\n                s = self.__read(1)\n                if not s or s == NUL:\n                    break\n        if flag & 2:\n            self.__read(2)\n\n    def tell(self):\n        \"\"\"Return the stream's file pointer position.\n        \"\"\"\n        return self.pos\n\n    def seek(self, pos=0):\n        \"\"\"Set the stream's file pointer to pos. Negative seeking\n           is forbidden.\n        \"\"\"\n        if pos - self.pos >= 0:\n            blocks, remainder = divmod(pos - self.pos, self.bufsize)\n            for i in range(blocks):\n                self.read(self.bufsize)\n            self.read(remainder)\n        else:\n            raise StreamError(\"seeking backwards is not allowed\")\n        return self.pos\n\n    def read(self, size=None):\n        \"\"\"Return the next size number of bytes from the stream.\n           If size is not defined, return all bytes of the stream\n           up to EOF.\n        \"\"\"\n        if size is None:\n            t = []\n            while True:\n                buf = self._read(self.bufsize)\n                if not buf:\n                    break\n                t.append(buf)\n            buf = \"\".join(t)\n        else:\n            buf = self._read(size)\n        self.pos += len(buf)\n        return buf\n\n    def _read(self, size):\n        \"\"\"Return size bytes from the stream.\n        \"\"\"\n        if self.comptype == \"tar\":\n            return self.__read(size)\n\n        c = len(self.dbuf)\n        while c < size:\n            buf = self.__read(self.bufsize)\n            if not buf:\n                break\n            try:\n                buf = self.cmp.decompress(buf)\n            except IOError:\n                raise ReadError(\"invalid compressed data\")\n            self.dbuf += buf\n            c += len(buf)\n        buf = self.dbuf[:size]\n        self.dbuf = self.dbuf[size:]\n        return buf\n\n    def __read(self, size):\n        \"\"\"Return size bytes from stream. If internal buffer is empty,\n           read another block from the stream.\n        \"\"\"\n        c = len(self.buf)\n        while c < size:\n            buf = self.fileobj.read(self.bufsize)\n            if not buf:\n                break\n            self.buf += buf\n            c += len(buf)\n        buf = self.buf[:size]\n        self.buf = self.buf[size:]\n        return buf\n# class _Stream\n\nclass _StreamProxy(object):\n    \"\"\"Small proxy class that enables transparent compression\n       detection for the Stream interface (mode 'r|*').\n    \"\"\"\n\n    def __init__(self, fileobj):\n        self.fileobj = fileobj\n        self.buf = self.fileobj.read(BLOCKSIZE)\n\n    def read(self, size):\n        self.read = self.fileobj.read\n        return self.buf\n\n    def getcomptype(self):\n        if self.buf.startswith(b\"\\037\\213\\010\"):\n            return \"gz\"\n        if self.buf.startswith(b\"BZh91\"):\n            return \"bz2\"\n        return \"tar\"\n\n    def close(self):\n        self.fileobj.close()\n# class StreamProxy\n\nclass _BZ2Proxy(object):\n    \"\"\"Small proxy class that enables external file object\n       support for \"r:bz2\" and \"w:bz2\" modes. This is actually\n       a workaround for a limitation in bz2 module's BZ2File\n       class which (unlike gzip.GzipFile) has no support for\n       a file object argument.\n    \"\"\"\n\n    blocksize = 16 * 1024\n\n    def __init__(self, fileobj, mode):\n        self.fileobj = fileobj\n        self.mode = mode\n        self.name = getattr(self.fileobj, \"name\", None)\n        self.init()\n\n    def init(self):\n        import bz2\n        self.pos = 0\n        if self.mode == \"r\":\n            self.bz2obj = bz2.BZ2Decompressor()\n            self.fileobj.seek(0)\n            self.buf = b\"\"\n        else:\n            self.bz2obj = bz2.BZ2Compressor()\n\n    def read(self, size):\n        x = len(self.buf)\n        while x < size:\n            raw = self.fileobj.read(self.blocksize)\n            if not raw:\n                break\n            data = self.bz2obj.decompress(raw)\n            self.buf += data\n            x += len(data)\n\n        buf = self.buf[:size]\n        self.buf = self.buf[size:]\n        self.pos += len(buf)\n        return buf\n\n    def seek(self, pos):\n        if pos < self.pos:\n            self.init()\n        self.read(pos - self.pos)\n\n    def tell(self):\n        return self.pos\n\n    def write(self, data):\n        self.pos += len(data)\n        raw = self.bz2obj.compress(data)\n        self.fileobj.write(raw)\n\n    def close(self):\n        if self.mode == \"w\":\n            raw = self.bz2obj.flush()\n            self.fileobj.write(raw)\n# class _BZ2Proxy\n\n#------------------------\n# Extraction file object\n#------------------------\nclass _FileInFile(object):\n    \"\"\"A thin wrapper around an existing file object that\n       provides a part of its data as an individual file\n       object.\n    \"\"\"\n\n    def __init__(self, fileobj, offset, size, blockinfo=None):\n        self.fileobj = fileobj\n        self.offset = offset\n        self.size = size\n        self.position = 0\n\n        if blockinfo is None:\n            blockinfo = [(0, size)]\n\n        # Construct a map with data and zero blocks.\n        self.map_index = 0\n        self.map = []\n        lastpos = 0\n        realpos = self.offset\n        for offset, size in blockinfo:\n            if offset > lastpos:\n                self.map.append((False, lastpos, offset, None))\n            self.map.append((True, offset, offset + size, realpos))\n            realpos += size\n            lastpos = offset + size\n        if lastpos < self.size:\n            self.map.append((False, lastpos, self.size, None))\n\n    def seekable(self):\n        if not hasattr(self.fileobj, \"seekable\"):\n            # XXX gzip.GzipFile and bz2.BZ2File\n            return True\n        return self.fileobj.seekable()\n\n    def tell(self):\n        \"\"\"Return the current file position.\n        \"\"\"\n        return self.position\n\n    def seek(self, position):\n        \"\"\"Seek to a position in the file.\n        \"\"\"\n        self.position = position\n\n    def read(self, size=None):\n        \"\"\"Read data from the file.\n        \"\"\"\n        if size is None:\n            size = self.size - self.position\n        else:\n            size = min(size, self.size - self.position)\n\n        buf = b\"\"\n        while size > 0:\n            while True:\n                data, start, stop, offset = self.map[self.map_index]\n                if start <= self.position < stop:\n                    break\n                else:\n                    self.map_index += 1\n                    if self.map_index == len(self.map):\n                        self.map_index = 0\n            length = min(size, stop - self.position)\n            if data:\n                self.fileobj.seek(offset + (self.position - start))\n                buf += self.fileobj.read(length)\n            else:\n                buf += NUL * length\n            size -= length\n            self.position += length\n        return buf\n#class _FileInFile\n\n\nclass ExFileObject(object):\n    \"\"\"File-like object for reading an archive member.\n       Is returned by TarFile.extractfile().\n    \"\"\"\n    blocksize = 1024\n\n    def __init__(self, tarfile, tarinfo):\n        self.fileobj = _FileInFile(tarfile.fileobj,\n                                   tarinfo.offset_data,\n                                   tarinfo.size,\n                                   tarinfo.sparse)\n        self.name = tarinfo.name\n        self.mode = \"r\"\n        self.closed = False\n        self.size = tarinfo.size\n\n        self.position = 0\n        self.buffer = b\"\"\n\n    def readable(self):\n        return True\n\n    def writable(self):\n        return False\n\n    def seekable(self):\n        return self.fileobj.seekable()\n\n    def read(self, size=None):\n        \"\"\"Read at most size bytes from the file. If size is not\n           present or None, read all data until EOF is reached.\n        \"\"\"\n        if self.closed:\n            raise ValueError(\"I/O operation on closed file\")\n\n        buf = b\"\"\n        if self.buffer:\n            if size is None:\n                buf = self.buffer\n                self.buffer = b\"\"\n            else:\n                buf = self.buffer[:size]\n                self.buffer = self.buffer[size:]\n\n        if size is None:\n            buf += self.fileobj.read()\n        else:\n            buf += self.fileobj.read(size - len(buf))\n\n        self.position += len(buf)\n        return buf\n\n    # XXX TextIOWrapper uses the read1() method.\n    read1 = read\n\n    def readline(self, size=-1):\n        \"\"\"Read one entire line from the file. If size is present\n           and non-negative, return a string with at most that\n           size, which may be an incomplete line.\n        \"\"\"\n        if self.closed:\n            raise ValueError(\"I/O operation on closed file\")\n\n        pos = self.buffer.find(b\"\\n\") + 1\n        if pos == 0:\n            # no newline found.\n            while True:\n                buf = self.fileobj.read(self.blocksize)\n                self.buffer += buf\n                if not buf or b\"\\n\" in buf:\n                    pos = self.buffer.find(b\"\\n\") + 1\n                    if pos == 0:\n                        # no newline found.\n                        pos = len(self.buffer)\n                    break\n\n        if size != -1:\n            pos = min(size, pos)\n\n        buf = self.buffer[:pos]\n        self.buffer = self.buffer[pos:]\n        self.position += len(buf)\n        return buf\n\n    def readlines(self):\n        \"\"\"Return a list with all remaining lines.\n        \"\"\"\n        result = []\n        while True:\n            line = self.readline()\n            if not line: break\n            result.append(line)\n        return result\n\n    def tell(self):\n        \"\"\"Return the current file position.\n        \"\"\"\n        if self.closed:\n            raise ValueError(\"I/O operation on closed file\")\n\n        return self.position\n\n    def seek(self, pos, whence=os.SEEK_SET):\n        \"\"\"Seek to a position in the file.\n        \"\"\"\n        if self.closed:\n            raise ValueError(\"I/O operation on closed file\")\n\n        if whence == os.SEEK_SET:\n            self.position = min(max(pos, 0), self.size)\n        elif whence == os.SEEK_CUR:\n            if pos < 0:\n                self.position = max(self.position + pos, 0)\n            else:\n                self.position = min(self.position + pos, self.size)\n        elif whence == os.SEEK_END:\n            self.position = max(min(self.size + pos, self.size), 0)\n        else:\n            raise ValueError(\"Invalid argument\")\n\n        self.buffer = b\"\"\n        self.fileobj.seek(self.position)\n\n    def close(self):\n        \"\"\"Close the file object.\n        \"\"\"\n        self.closed = True\n\n    def __iter__(self):\n        \"\"\"Get an iterator over the file's lines.\n        \"\"\"\n        while True:\n            line = self.readline()\n            if not line:\n                break\n            yield line\n#class ExFileObject\n\n#------------------\n# Exported Classes\n#------------------\nclass TarInfo(object):\n    \"\"\"Informational class which holds the details about an\n       archive member given by a tar header block.\n       TarInfo objects are returned by TarFile.getmember(),\n       TarFile.getmembers() and TarFile.gettarinfo() and are\n       usually created internally.\n    \"\"\"\n\n    __slots__ = (\"name\", \"mode\", \"uid\", \"gid\", \"size\", \"mtime\",\n                 \"chksum\", \"type\", \"linkname\", \"uname\", \"gname\",\n                 \"devmajor\", \"devminor\",\n                 \"offset\", \"offset_data\", \"pax_headers\", \"sparse\",\n                 \"tarfile\", \"_sparse_structs\", \"_link_target\")\n\n    def __init__(self, name=\"\"):\n        \"\"\"Construct a TarInfo object. name is the optional name\n           of the member.\n        \"\"\"\n        self.name = name        # member name\n        self.mode = 0o644       # file permissions\n        self.uid = 0            # user id\n        self.gid = 0            # group id\n        self.size = 0           # file size\n        self.mtime = 0          # modification time\n        self.chksum = 0         # header checksum\n        self.type = REGTYPE     # member type\n        self.linkname = \"\"      # link name\n        self.uname = \"\"         # user name\n        self.gname = \"\"         # group name\n        self.devmajor = 0       # device major number\n        self.devminor = 0       # device minor number\n\n        self.offset = 0         # the tar header starts here\n        self.offset_data = 0    # the file's data starts here\n\n        self.sparse = None      # sparse member information\n        self.pax_headers = {}   # pax header information\n\n    # In pax headers the \"name\" and \"linkname\" field are called\n    # \"path\" and \"linkpath\".\n    def _getpath(self):\n        return self.name\n    def _setpath(self, name):\n        self.name = name\n    path = property(_getpath, _setpath)\n\n    def _getlinkpath(self):\n        return self.linkname\n    def _setlinkpath(self, linkname):\n        self.linkname = linkname\n    linkpath = property(_getlinkpath, _setlinkpath)\n\n    def __repr__(self):\n        return \"<%s %r at %#x>\" % (self.__class__.__name__,self.name,id(self))\n\n    def get_info(self):\n        \"\"\"Return the TarInfo's attributes as a dictionary.\n        \"\"\"\n        info = {\n            \"name\":     self.name,\n            \"mode\":     self.mode & 0o7777,\n            \"uid\":      self.uid,\n            \"gid\":      self.gid,\n            \"size\":     self.size,\n            \"mtime\":    self.mtime,\n            \"chksum\":   self.chksum,\n            \"type\":     self.type,\n            \"linkname\": self.linkname,\n            \"uname\":    self.uname,\n            \"gname\":    self.gname,\n            \"devmajor\": self.devmajor,\n            \"devminor\": self.devminor\n        }\n\n        if info[\"type\"] == DIRTYPE and not info[\"name\"].endswith(\"/\"):\n            info[\"name\"] += \"/\"\n\n        return info\n\n    def tobuf(self, format=DEFAULT_FORMAT, encoding=ENCODING, errors=\"surrogateescape\"):\n        \"\"\"Return a tar header as a string of 512 byte blocks.\n        \"\"\"\n        info = self.get_info()\n\n        if format == USTAR_FORMAT:\n            return self.create_ustar_header(info, encoding, errors)\n        elif format == GNU_FORMAT:\n            return self.create_gnu_header(info, encoding, errors)\n        elif format == PAX_FORMAT:\n            return self.create_pax_header(info, encoding)\n        else:\n            raise ValueError(\"invalid format\")\n\n    def create_ustar_header(self, info, encoding, errors):\n        \"\"\"Return the object as a ustar header block.\n        \"\"\"\n        info[\"magic\"] = POSIX_MAGIC\n\n        if len(info[\"linkname\"]) > LENGTH_LINK:\n            raise ValueError(\"linkname is too long\")\n\n        if len(info[\"name\"]) > LENGTH_NAME:\n            info[\"prefix\"], info[\"name\"] = self._posix_split_name(info[\"name\"])\n\n        return self._create_header(info, USTAR_FORMAT, encoding, errors)\n\n    def create_gnu_header(self, info, encoding, errors):\n        \"\"\"Return the object as a GNU header block sequence.\n        \"\"\"\n        info[\"magic\"] = GNU_MAGIC\n\n        buf = b\"\"\n        if len(info[\"linkname\"]) > LENGTH_LINK:\n            buf += self._create_gnu_long_header(info[\"linkname\"], GNUTYPE_LONGLINK, encoding, errors)\n\n        if len(info[\"name\"]) > LENGTH_NAME:\n            buf += self._create_gnu_long_header(info[\"name\"], GNUTYPE_LONGNAME, encoding, errors)\n\n        return buf + self._create_header(info, GNU_FORMAT, encoding, errors)\n\n    def create_pax_header(self, info, encoding):\n        \"\"\"Return the object as a ustar header block. If it cannot be\n           represented this way, prepend a pax extended header sequence\n           with supplement information.\n        \"\"\"\n        info[\"magic\"] = POSIX_MAGIC\n        pax_headers = self.pax_headers.copy()\n\n        # Test string fields for values that exceed the field length or cannot\n        # be represented in ASCII encoding.\n        for name, hname, length in (\n                (\"name\", \"path\", LENGTH_NAME), (\"linkname\", \"linkpath\", LENGTH_LINK),\n                (\"uname\", \"uname\", 32), (\"gname\", \"gname\", 32)):\n\n            if hname in pax_headers:\n                # The pax header has priority.\n                continue\n\n            # Try to encode the string as ASCII.\n            try:\n                info[name].encode(\"ascii\", \"strict\")\n            except UnicodeEncodeError:\n                pax_headers[hname] = info[name]\n                continue\n\n            if len(info[name]) > length:\n                pax_headers[hname] = info[name]\n\n        # Test number fields for values that exceed the field limit or values\n        # that like to be stored as float.\n        for name, digits in ((\"uid\", 8), (\"gid\", 8), (\"size\", 12), (\"mtime\", 12)):\n            if name in pax_headers:\n                # The pax header has priority. Avoid overflow.\n                info[name] = 0\n                continue\n\n            val = info[name]\n            if not 0 <= val < 8 ** (digits - 1) or isinstance(val, float):\n                pax_headers[name] = str(val)\n                info[name] = 0\n\n        # Create a pax extended header if necessary.\n        if pax_headers:\n            buf = self._create_pax_generic_header(pax_headers, XHDTYPE, encoding)\n        else:\n            buf = b\"\"\n\n        return buf + self._create_header(info, USTAR_FORMAT, \"ascii\", \"replace\")\n\n    @classmethod\n    def create_pax_global_header(cls, pax_headers):\n        \"\"\"Return the object as a pax global header block sequence.\n        \"\"\"\n        return cls._create_pax_generic_header(pax_headers, XGLTYPE, \"utf8\")\n\n    def _posix_split_name(self, name):\n        \"\"\"Split a name longer than 100 chars into a prefix\n           and a name part.\n        \"\"\"\n        prefix = name[:LENGTH_PREFIX + 1]\n        while prefix and prefix[-1] != \"/\":\n            prefix = prefix[:-1]\n\n        name = name[len(prefix):]\n        prefix = prefix[:-1]\n\n        if not prefix or len(name) > LENGTH_NAME:\n            raise ValueError(\"name is too long\")\n        return prefix, name\n\n    @staticmethod\n    def _create_header(info, format, encoding, errors):\n        \"\"\"Return a header block. info is a dictionary with file\n           information, format must be one of the *_FORMAT constants.\n        \"\"\"\n        parts = [\n            stn(info.get(\"name\", \"\"), 100, encoding, errors),\n            itn(info.get(\"mode\", 0) & 0o7777, 8, format),\n            itn(info.get(\"uid\", 0), 8, format),\n            itn(info.get(\"gid\", 0), 8, format),\n            itn(info.get(\"size\", 0), 12, format),\n            itn(info.get(\"mtime\", 0), 12, format),\n            b\"        \", # checksum field\n            info.get(\"type\", REGTYPE),\n            stn(info.get(\"linkname\", \"\"), 100, encoding, errors),\n            info.get(\"magic\", POSIX_MAGIC),\n            stn(info.get(\"uname\", \"\"), 32, encoding, errors),\n            stn(info.get(\"gname\", \"\"), 32, encoding, errors),\n            itn(info.get(\"devmajor\", 0), 8, format),\n            itn(info.get(\"devminor\", 0), 8, format),\n            stn(info.get(\"prefix\", \"\"), 155, encoding, errors)\n        ]\n\n        buf = struct.pack(\"%ds\" % BLOCKSIZE, b\"\".join(parts))\n        chksum = calc_chksums(buf[-BLOCKSIZE:])[0]\n        buf = buf[:-364] + (\"%06o\\0\" % chksum).encode(\"ascii\") + buf[-357:]\n        return buf\n\n    @staticmethod\n    def _create_payload(payload):\n        \"\"\"Return the string payload filled with zero bytes\n           up to the next 512 byte border.\n        \"\"\"\n        blocks, remainder = divmod(len(payload), BLOCKSIZE)\n        if remainder > 0:\n            payload += (BLOCKSIZE - remainder) * NUL\n        return payload\n\n    @classmethod\n    def _create_gnu_long_header(cls, name, type, encoding, errors):\n        \"\"\"Return a GNUTYPE_LONGNAME or GNUTYPE_LONGLINK sequence\n           for name.\n        \"\"\"\n        name = name.encode(encoding, errors) + NUL\n\n        info = {}\n        info[\"name\"] = \"././@LongLink\"\n        info[\"type\"] = type\n        info[\"size\"] = len(name)\n        info[\"magic\"] = GNU_MAGIC\n\n        # create extended header + name blocks.\n        return cls._create_header(info, USTAR_FORMAT, encoding, errors) + \\\n                cls._create_payload(name)\n\n    @classmethod\n    def _create_pax_generic_header(cls, pax_headers, type, encoding):\n        \"\"\"Return a POSIX.1-2008 extended or global header sequence\n           that contains a list of keyword, value pairs. The values\n           must be strings.\n        \"\"\"\n        # Check if one of the fields contains surrogate characters and thereby\n        # forces hdrcharset=BINARY, see _proc_pax() for more information.\n        binary = False\n        for keyword, value in pax_headers.items():\n            try:\n                value.encode(\"utf8\", \"strict\")\n            except UnicodeEncodeError:\n                binary = True\n                break\n\n        records = b\"\"\n        if binary:\n            # Put the hdrcharset field at the beginning of the header.\n            records += b\"21 hdrcharset=BINARY\\n\"\n\n        for keyword, value in pax_headers.items():\n            keyword = keyword.encode(\"utf8\")\n            if binary:\n                # Try to restore the original byte representation of `value'.\n                # Needless to say, that the encoding must match the string.\n                value = value.encode(encoding, \"surrogateescape\")\n            else:\n                value = value.encode(\"utf8\")\n\n            l = len(keyword) + len(value) + 3   # ' ' + '=' + '\\n'\n            n = p = 0\n            while True:\n                n = l + len(str(p))\n                if n == p:\n                    break\n                p = n\n            records += bytes(str(p), \"ascii\") + b\" \" + keyword + b\"=\" + value + b\"\\n\"\n\n        # We use a hardcoded \"././@PaxHeader\" name like star does\n        # instead of the one that POSIX recommends.\n        info = {}\n        info[\"name\"] = \"././@PaxHeader\"\n        info[\"type\"] = type\n        info[\"size\"] = len(records)\n        info[\"magic\"] = POSIX_MAGIC\n\n        # Create pax header + record blocks.\n        return cls._create_header(info, USTAR_FORMAT, \"ascii\", \"replace\") + \\\n                cls._create_payload(records)\n\n    @classmethod\n    def frombuf(cls, buf, encoding, errors):\n        \"\"\"Construct a TarInfo object from a 512 byte bytes object.\n        \"\"\"\n        if len(buf) == 0:\n            raise EmptyHeaderError(\"empty header\")\n        if len(buf) != BLOCKSIZE:\n            raise TruncatedHeaderError(\"truncated header\")\n        if buf.count(NUL) == BLOCKSIZE:\n            raise EOFHeaderError(\"end of file header\")\n\n        chksum = nti(buf[148:156])\n        if chksum not in calc_chksums(buf):\n            raise InvalidHeaderError(\"bad checksum\")\n\n        obj = cls()\n        obj.name = nts(buf[0:100], encoding, errors)\n        obj.mode = nti(buf[100:108])\n        obj.uid = nti(buf[108:116])\n        obj.gid = nti(buf[116:124])\n        obj.size = nti(buf[124:136])\n        obj.mtime = nti(buf[136:148])\n        obj.chksum = chksum\n        obj.type = buf[156:157]\n        obj.linkname = nts(buf[157:257], encoding, errors)\n        obj.uname = nts(buf[265:297], encoding, errors)\n        obj.gname = nts(buf[297:329], encoding, errors)\n        obj.devmajor = nti(buf[329:337])\n        obj.devminor = nti(buf[337:345])\n        prefix = nts(buf[345:500], encoding, errors)\n\n        # Old V7 tar format represents a directory as a regular\n        # file with a trailing slash.\n        if obj.type == AREGTYPE and obj.name.endswith(\"/\"):\n            obj.type = DIRTYPE\n\n        # The old GNU sparse format occupies some of the unused\n        # space in the buffer for up to 4 sparse structures.\n        # Save the them for later processing in _proc_sparse().\n        if obj.type == GNUTYPE_SPARSE:\n            pos = 386\n            structs = []\n            for i in range(4):\n                try:\n                    offset = nti(buf[pos:pos + 12])\n                    numbytes = nti(buf[pos + 12:pos + 24])\n                except ValueError:\n                    break\n                structs.append((offset, numbytes))\n                pos += 24\n            isextended = bool(buf[482])\n            origsize = nti(buf[483:495])\n            obj._sparse_structs = (structs, isextended, origsize)\n\n        # Remove redundant slashes from directories.\n        if obj.isdir():\n            obj.name = obj.name.rstrip(\"/\")\n\n        # Reconstruct a ustar longname.\n        if prefix and obj.type not in GNU_TYPES:\n            obj.name = prefix + \"/\" + obj.name\n        return obj\n\n    @classmethod\n    def fromtarfile(cls, tarfile):\n        \"\"\"Return the next TarInfo object from TarFile object\n           tarfile.\n        \"\"\"\n        buf = tarfile.fileobj.read(BLOCKSIZE)\n        obj = cls.frombuf(buf, tarfile.encoding, tarfile.errors)\n        obj.offset = tarfile.fileobj.tell() - BLOCKSIZE\n        return obj._proc_member(tarfile)\n\n    #--------------------------------------------------------------------------\n    # The following are methods that are called depending on the type of a\n    # member. The entry point is _proc_member() which can be overridden in a\n    # subclass to add custom _proc_*() methods. A _proc_*() method MUST\n    # implement the following\n    # operations:\n    # 1. Set self.offset_data to the position where the data blocks begin,\n    #    if there is data that follows.\n    # 2. Set tarfile.offset to the position where the next member's header will\n    #    begin.\n    # 3. Return self or another valid TarInfo object.\n    def _proc_member(self, tarfile):\n        \"\"\"Choose the right processing method depending on\n           the type and call it.\n        \"\"\"\n        if self.type in (GNUTYPE_LONGNAME, GNUTYPE_LONGLINK):\n            return self._proc_gnulong(tarfile)\n        elif self.type == GNUTYPE_SPARSE:\n            return self._proc_sparse(tarfile)\n        elif self.type in (XHDTYPE, XGLTYPE, SOLARIS_XHDTYPE):\n            return self._proc_pax(tarfile)\n        else:\n            return self._proc_builtin(tarfile)\n\n    def _proc_builtin(self, tarfile):\n        \"\"\"Process a builtin type or an unknown type which\n           will be treated as a regular file.\n        \"\"\"\n        self.offset_data = tarfile.fileobj.tell()\n        offset = self.offset_data\n        if self.isreg() or self.type not in SUPPORTED_TYPES:\n            # Skip the following data blocks.\n            offset += self._block(self.size)\n        tarfile.offset = offset\n\n        # Patch the TarInfo object with saved global\n        # header information.\n        self._apply_pax_info(tarfile.pax_headers, tarfile.encoding, tarfile.errors)\n\n        return self\n\n    def _proc_gnulong(self, tarfile):\n        \"\"\"Process the blocks that hold a GNU longname\n           or longlink member.\n        \"\"\"\n        buf = tarfile.fileobj.read(self._block(self.size))\n\n        # Fetch the next header and process it.\n        try:\n            next = self.fromtarfile(tarfile)\n        except HeaderError:\n            raise SubsequentHeaderError(\"missing or bad subsequent header\")\n\n        # Patch the TarInfo object from the next header with\n        # the longname information.\n        next.offset = self.offset\n        if self.type == GNUTYPE_LONGNAME:\n            next.name = nts(buf, tarfile.encoding, tarfile.errors)\n        elif self.type == GNUTYPE_LONGLINK:\n            next.linkname = nts(buf, tarfile.encoding, tarfile.errors)\n\n        return next\n\n    def _proc_sparse(self, tarfile):\n        \"\"\"Process a GNU sparse header plus extra headers.\n        \"\"\"\n        # We already collected some sparse structures in frombuf().\n        structs, isextended, origsize = self._sparse_structs\n        del self._sparse_structs\n\n        # Collect sparse structures from extended header blocks.\n        while isextended:\n            buf = tarfile.fileobj.read(BLOCKSIZE)\n            pos = 0\n            for i in range(21):\n                try:\n                    offset = nti(buf[pos:pos + 12])\n                    numbytes = nti(buf[pos + 12:pos + 24])\n                except ValueError:\n                    break\n                if offset and numbytes:\n                    structs.append((offset, numbytes))\n                pos += 24\n            isextended = bool(buf[504])\n        self.sparse = structs\n\n        self.offset_data = tarfile.fileobj.tell()\n        tarfile.offset = self.offset_data + self._block(self.size)\n        self.size = origsize\n        return self\n\n    def _proc_pax(self, tarfile):\n        \"\"\"Process an extended or global header as described in\n           POSIX.1-2008.\n        \"\"\"\n        # Read the header information.\n        buf = tarfile.fileobj.read(self._block(self.size))\n\n        # A pax header stores supplemental information for either\n        # the following file (extended) or all following files\n        # (global).\n        if self.type == XGLTYPE:\n            pax_headers = tarfile.pax_headers\n        else:\n            pax_headers = tarfile.pax_headers.copy()\n\n        # Check if the pax header contains a hdrcharset field. This tells us\n        # the encoding of the path, linkpath, uname and gname fields. Normally,\n        # these fields are UTF-8 encoded but since POSIX.1-2008 tar\n        # implementations are allowed to store them as raw binary strings if\n        # the translation to UTF-8 fails.\n        match = re.search(br\"\\d+ hdrcharset=([^\\n]+)\\n\", buf)\n        if match is not None:\n            pax_headers[\"hdrcharset\"] = match.group(1).decode(\"utf8\")\n\n        # For the time being, we don't care about anything other than \"BINARY\".\n        # The only other value that is currently allowed by the standard is\n        # \"ISO-IR 10646 2000 UTF-8\" in other words UTF-8.\n        hdrcharset = pax_headers.get(\"hdrcharset\")\n        if hdrcharset == \"BINARY\":\n            encoding = tarfile.encoding\n        else:\n            encoding = \"utf8\"\n\n        # Parse pax header information. A record looks like that:\n        # \"%d %s=%s\\n\" % (length, keyword, value). length is the size\n        # of the complete record including the length field itself and\n        # the newline. keyword and value are both UTF-8 encoded strings.\n        regex = re.compile(br\"(\\d+) ([^=]+)=\")\n        pos = 0\n        while True:\n            match = regex.match(buf, pos)\n            if not match:\n                break\n\n            length, keyword = match.groups()\n            length = int(length)\n            value = buf[match.end(2) + 1:match.start(1) + length - 1]\n\n            # Normally, we could just use \"utf8\" as the encoding and \"strict\"\n            # as the error handler, but we better not take the risk. For\n            # example, GNU tar <= 1.23 is known to store filenames it cannot\n            # translate to UTF-8 as raw strings (unfortunately without a\n            # hdrcharset=BINARY header).\n            # We first try the strict standard encoding, and if that fails we\n            # fall back on the user's encoding and error handler.\n            keyword = self._decode_pax_field(keyword, \"utf8\", \"utf8\",\n                    tarfile.errors)\n            if keyword in PAX_NAME_FIELDS:\n                value = self._decode_pax_field(value, encoding, tarfile.encoding,\n                        tarfile.errors)\n            else:\n                value = self._decode_pax_field(value, \"utf8\", \"utf8\",\n                        tarfile.errors)\n\n            pax_headers[keyword] = value\n            pos += length\n\n        # Fetch the next header.\n        try:\n            next = self.fromtarfile(tarfile)\n        except HeaderError:\n            raise SubsequentHeaderError(\"missing or bad subsequent header\")\n\n        # Process GNU sparse information.\n        if \"GNU.sparse.map\" in pax_headers:\n            # GNU extended sparse format version 0.1.\n            self._proc_gnusparse_01(next, pax_headers)\n\n        elif \"GNU.sparse.size\" in pax_headers:\n            # GNU extended sparse format version 0.0.\n            self._proc_gnusparse_00(next, pax_headers, buf)\n\n        elif pax_headers.get(\"GNU.sparse.major\") == \"1\" and pax_headers.get(\"GNU.sparse.minor\") == \"0\":\n            # GNU extended sparse format version 1.0.\n            self._proc_gnusparse_10(next, pax_headers, tarfile)\n\n        if self.type in (XHDTYPE, SOLARIS_XHDTYPE):\n            # Patch the TarInfo object with the extended header info.\n            next._apply_pax_info(pax_headers, tarfile.encoding, tarfile.errors)\n            next.offset = self.offset\n\n            if \"size\" in pax_headers:\n                # If the extended header replaces the size field,\n                # we need to recalculate the offset where the next\n                # header starts.\n                offset = next.offset_data\n                if next.isreg() or next.type not in SUPPORTED_TYPES:\n                    offset += next._block(next.size)\n                tarfile.offset = offset\n\n        return next\n\n    def _proc_gnusparse_00(self, next, pax_headers, buf):\n        \"\"\"Process a GNU tar extended sparse header, version 0.0.\n        \"\"\"\n        offsets = []\n        for match in re.finditer(br\"\\d+ GNU.sparse.offset=(\\d+)\\n\", buf):\n            offsets.append(int(match.group(1)))\n        numbytes = []\n        for match in re.finditer(br\"\\d+ GNU.sparse.numbytes=(\\d+)\\n\", buf):\n            numbytes.append(int(match.group(1)))\n        next.sparse = list(zip(offsets, numbytes))\n\n    def _proc_gnusparse_01(self, next, pax_headers):\n        \"\"\"Process a GNU tar extended sparse header, version 0.1.\n        \"\"\"\n        sparse = [int(x) for x in pax_headers[\"GNU.sparse.map\"].split(\",\")]\n        next.sparse = list(zip(sparse[::2], sparse[1::2]))\n\n    def _proc_gnusparse_10(self, next, pax_headers, tarfile):\n        \"\"\"Process a GNU tar extended sparse header, version 1.0.\n        \"\"\"\n        fields = None\n        sparse = []\n        buf = tarfile.fileobj.read(BLOCKSIZE)\n        fields, buf = buf.split(b\"\\n\", 1)\n        fields = int(fields)\n        while len(sparse) < fields * 2:\n            if b\"\\n\" not in buf:\n                buf += tarfile.fileobj.read(BLOCKSIZE)\n            number, buf = buf.split(b\"\\n\", 1)\n            sparse.append(int(number))\n        next.offset_data = tarfile.fileobj.tell()\n        next.sparse = list(zip(sparse[::2], sparse[1::2]))\n\n    def _apply_pax_info(self, pax_headers, encoding, errors):\n        \"\"\"Replace fields with supplemental information from a previous\n           pax extended or global header.\n        \"\"\"\n        for keyword, value in pax_headers.items():\n            if keyword == \"GNU.sparse.name\":\n                setattr(self, \"path\", value)\n            elif keyword == \"GNU.sparse.size\":\n                setattr(self, \"size\", int(value))\n            elif keyword == \"GNU.sparse.realsize\":\n                setattr(self, \"size\", int(value))\n            elif keyword in PAX_FIELDS:\n                if keyword in PAX_NUMBER_FIELDS:\n                    try:\n                        value = PAX_NUMBER_FIELDS[keyword](value)\n                    except ValueError:\n                        value = 0\n                if keyword == \"path\":\n                    value = value.rstrip(\"/\")\n                setattr(self, keyword, value)\n\n        self.pax_headers = pax_headers.copy()\n\n    def _decode_pax_field(self, value, encoding, fallback_encoding, fallback_errors):\n        \"\"\"Decode a single field from a pax record.\n        \"\"\"\n        try:\n            return value.decode(encoding, \"strict\")\n        except UnicodeDecodeError:\n            return value.decode(fallback_encoding, fallback_errors)\n\n    def _block(self, count):\n        \"\"\"Round up a byte count by BLOCKSIZE and return it,\n           e.g. _block(834) => 1024.\n        \"\"\"\n        blocks, remainder = divmod(count, BLOCKSIZE)\n        if remainder:\n            blocks += 1\n        return blocks * BLOCKSIZE\n\n    def isreg(self):\n        return self.type in REGULAR_TYPES\n    def isfile(self):\n        return self.isreg()\n    def isdir(self):\n        return self.type == DIRTYPE\n    def issym(self):\n        return self.type == SYMTYPE\n    def islnk(self):\n        return self.type == LNKTYPE\n    def ischr(self):\n        return self.type == CHRTYPE\n    def isblk(self):\n        return self.type == BLKTYPE\n    def isfifo(self):\n        return self.type == FIFOTYPE\n    def issparse(self):\n        return self.sparse is not None\n    def isdev(self):\n        return self.type in (CHRTYPE, BLKTYPE, FIFOTYPE)\n# class TarInfo\n\nclass TarFile(object):\n    \"\"\"The TarFile Class provides an interface to tar archives.\n    \"\"\"\n\n    debug = 0                   # May be set from 0 (no msgs) to 3 (all msgs)\n\n    dereference = False         # If true, add content of linked file to the\n                                # tar file, else the link.\n\n    ignore_zeros = False        # If true, skips empty or invalid blocks and\n                                # continues processing.\n\n    errorlevel = 1              # If 0, fatal errors only appear in debug\n                                # messages (if debug >= 0). If > 0, errors\n                                # are passed to the caller as exceptions.\n\n    format = DEFAULT_FORMAT     # The format to use when creating an archive.\n\n    encoding = ENCODING         # Encoding for 8-bit character strings.\n\n    errors = None               # Error handler for unicode conversion.\n\n    tarinfo = TarInfo           # The default TarInfo class to use.\n\n    fileobject = ExFileObject   # The default ExFileObject class to use.\n\n    def __init__(self, name=None, mode=\"r\", fileobj=None, format=None,\n            tarinfo=None, dereference=None, ignore_zeros=None, encoding=None,\n            errors=\"surrogateescape\", pax_headers=None, debug=None, errorlevel=None):\n        \"\"\"Open an (uncompressed) tar archive `name'. `mode' is either 'r' to\n           read from an existing archive, 'a' to append data to an existing\n           file or 'w' to create a new file overwriting an existing one. `mode'\n           defaults to 'r'.\n           If `fileobj' is given, it is used for reading or writing data. If it\n           can be determined, `mode' is overridden by `fileobj's mode.\n           `fileobj' is not closed, when TarFile is closed.\n        \"\"\"\n        if len(mode) > 1 or mode not in \"raw\":\n            raise ValueError(\"mode must be 'r', 'a' or 'w'\")\n        self.mode = mode\n        self._mode = {\"r\": \"rb\", \"a\": \"r+b\", \"w\": \"wb\"}[mode]\n\n        if not fileobj:\n            if self.mode == \"a\" and not os.path.exists(name):\n                # Create nonexistent files in append mode.\n                self.mode = \"w\"\n                self._mode = \"wb\"\n            fileobj = bltn_open(name, self._mode)\n            self._extfileobj = False\n        else:\n            if name is None and hasattr(fileobj, \"name\"):\n                name = fileobj.name\n            if hasattr(fileobj, \"mode\"):\n                self._mode = fileobj.mode\n            self._extfileobj = True\n        self.name = os.path.abspath(name) if name else None\n        self.fileobj = fileobj\n\n        # Init attributes.\n        if format is not None:\n            self.format = format\n        if tarinfo is not None:\n            self.tarinfo = tarinfo\n        if dereference is not None:\n            self.dereference = dereference\n        if ignore_zeros is not None:\n            self.ignore_zeros = ignore_zeros\n        if encoding is not None:\n            self.encoding = encoding\n        self.errors = errors\n\n        if pax_headers is not None and self.format == PAX_FORMAT:\n            self.pax_headers = pax_headers\n        else:\n            self.pax_headers = {}\n\n        if debug is not None:\n            self.debug = debug\n        if errorlevel is not None:\n            self.errorlevel = errorlevel\n\n        # Init datastructures.\n        self.closed = False\n        self.members = []       # list of members as TarInfo objects\n        self._loaded = False    # flag if all members have been read\n        self.offset = self.fileobj.tell()\n                                # current position in the archive file\n        self.inodes = {}        # dictionary caching the inodes of\n                                # archive members already added\n\n        try:\n            if self.mode == \"r\":\n                self.firstmember = None\n                self.firstmember = self.next()\n\n            if self.mode == \"a\":\n                # Move to the end of the archive,\n                # before the first empty block.\n                while True:\n                    self.fileobj.seek(self.offset)\n                    try:\n                        tarinfo = self.tarinfo.fromtarfile(self)\n                        self.members.append(tarinfo)\n                    except EOFHeaderError:\n                        self.fileobj.seek(self.offset)\n                        break\n                    except HeaderError as e:\n                        raise ReadError(str(e))\n\n            if self.mode in \"aw\":\n                self._loaded = True\n\n                if self.pax_headers:\n                    buf = self.tarinfo.create_pax_global_header(self.pax_headers.copy())\n                    self.fileobj.write(buf)\n                    self.offset += len(buf)\n        except:\n            if not self._extfileobj:\n                self.fileobj.close()\n            self.closed = True\n            raise\n\n    #--------------------------------------------------------------------------\n    # Below are the classmethods which act as alternate constructors to the\n    # TarFile class. The open() method is the only one that is needed for\n    # public use; it is the \"super\"-constructor and is able to select an\n    # adequate \"sub\"-constructor for a particular compression using the mapping\n    # from OPEN_METH.\n    #\n    # This concept allows one to subclass TarFile without losing the comfort of\n    # the super-constructor. A sub-constructor is registered and made available\n    # by adding it to the mapping in OPEN_METH.\n\n    @classmethod\n    def open(cls, name=None, mode=\"r\", fileobj=None, bufsize=RECORDSIZE, **kwargs):\n        \"\"\"Open a tar archive for reading, writing or appending. Return\n           an appropriate TarFile class.\n\n           mode:\n           'r' or 'r:*' open for reading with transparent compression\n           'r:'         open for reading exclusively uncompressed\n           'r:gz'       open for reading with gzip compression\n           'r:bz2'      open for reading with bzip2 compression\n           'a' or 'a:'  open for appending, creating the file if necessary\n           'w' or 'w:'  open for writing without compression\n           'w:gz'       open for writing with gzip compression\n           'w:bz2'      open for writing with bzip2 compression\n\n           'r|*'        open a stream of tar blocks with transparent compression\n           'r|'         open an uncompressed stream of tar blocks for reading\n           'r|gz'       open a gzip compressed stream of tar blocks\n           'r|bz2'      open a bzip2 compressed stream of tar blocks\n           'w|'         open an uncompressed stream for writing\n           'w|gz'       open a gzip compressed stream for writing\n           'w|bz2'      open a bzip2 compressed stream for writing\n        \"\"\"\n\n        if not name and not fileobj:\n            raise ValueError(\"nothing to open\")\n\n        if mode in (\"r\", \"r:*\"):\n            # Find out which *open() is appropriate for opening the file.\n            for comptype in cls.OPEN_METH:\n                func = getattr(cls, cls.OPEN_METH[comptype])\n                if fileobj is not None:\n                    saved_pos = fileobj.tell()\n                try:\n                    return func(name, \"r\", fileobj, **kwargs)\n                except (ReadError, CompressionError) as e:\n                    if fileobj is not None:\n                        fileobj.seek(saved_pos)\n                    continue\n            raise ReadError(\"file could not be opened successfully\")\n\n        elif \":\" in mode:\n            filemode, comptype = mode.split(\":\", 1)\n            filemode = filemode or \"r\"\n            comptype = comptype or \"tar\"\n\n            # Select the *open() function according to\n            # given compression.\n            if comptype in cls.OPEN_METH:\n                func = getattr(cls, cls.OPEN_METH[comptype])\n            else:\n                raise CompressionError(\"unknown compression type %r\" % comptype)\n            return func(name, filemode, fileobj, **kwargs)\n\n        elif \"|\" in mode:\n            filemode, comptype = mode.split(\"|\", 1)\n            filemode = filemode or \"r\"\n            comptype = comptype or \"tar\"\n\n            if filemode not in \"rw\":\n                raise ValueError(\"mode must be 'r' or 'w'\")\n\n            stream = _Stream(name, filemode, comptype, fileobj, bufsize)\n            try:\n                t = cls(name, filemode, stream, **kwargs)\n            except:\n                stream.close()\n                raise\n            t._extfileobj = False\n            return t\n\n        elif mode in \"aw\":\n            return cls.taropen(name, mode, fileobj, **kwargs)\n\n        raise ValueError(\"undiscernible mode\")\n\n    @classmethod\n    def taropen(cls, name, mode=\"r\", fileobj=None, **kwargs):\n        \"\"\"Open uncompressed tar archive name for reading or writing.\n        \"\"\"\n        if len(mode) > 1 or mode not in \"raw\":\n            raise ValueError(\"mode must be 'r', 'a' or 'w'\")\n        return cls(name, mode, fileobj, **kwargs)\n\n    @classmethod\n    def gzopen(cls, name, mode=\"r\", fileobj=None, compresslevel=9, **kwargs):\n        \"\"\"Open gzip compressed tar archive name for reading or writing.\n           Appending is not allowed.\n        \"\"\"\n        if len(mode) > 1 or mode not in \"rw\":\n            raise ValueError(\"mode must be 'r' or 'w'\")\n\n        try:\n            import gzip\n            gzip.GzipFile\n        except (ImportError, AttributeError):\n            raise CompressionError(\"gzip module is not available\")\n\n        extfileobj = fileobj is not None\n        try:\n            fileobj = gzip.GzipFile(name, mode + \"b\", compresslevel, fileobj)\n            t = cls.taropen(name, mode, fileobj, **kwargs)\n        except IOError:\n            if not extfileobj and fileobj is not None:\n                fileobj.close()\n            if fileobj is None:\n                raise\n            raise ReadError(\"not a gzip file\")\n        except:\n            if not extfileobj and fileobj is not None:\n                fileobj.close()\n            raise\n        t._extfileobj = extfileobj\n        return t\n\n    @classmethod\n    def bz2open(cls, name, mode=\"r\", fileobj=None, compresslevel=9, **kwargs):\n        \"\"\"Open bzip2 compressed tar archive name for reading or writing.\n           Appending is not allowed.\n        \"\"\"\n        if len(mode) > 1 or mode not in \"rw\":\n            raise ValueError(\"mode must be 'r' or 'w'.\")\n\n        try:\n            import bz2\n        except ImportError:\n            raise CompressionError(\"bz2 module is not available\")\n\n        if fileobj is not None:\n            fileobj = _BZ2Proxy(fileobj, mode)\n        else:\n            fileobj = bz2.BZ2File(name, mode, compresslevel=compresslevel)\n\n        try:\n            t = cls.taropen(name, mode, fileobj, **kwargs)\n        except (IOError, EOFError):\n            fileobj.close()\n            raise ReadError(\"not a bzip2 file\")\n        t._extfileobj = False\n        return t\n\n    # All *open() methods are registered here.\n    OPEN_METH = {\n        \"tar\": \"taropen\",   # uncompressed tar\n        \"gz\":  \"gzopen\",    # gzip compressed tar\n        \"bz2\": \"bz2open\"    # bzip2 compressed tar\n    }\n\n    #--------------------------------------------------------------------------\n    # The public methods which TarFile provides:\n\n    def close(self):\n        \"\"\"Close the TarFile. In write-mode, two finishing zero blocks are\n           appended to the archive.\n        \"\"\"\n        if self.closed:\n            return\n\n        if self.mode in \"aw\":\n            self.fileobj.write(NUL * (BLOCKSIZE * 2))\n            self.offset += (BLOCKSIZE * 2)\n            # fill up the end with zero-blocks\n            # (like option -b20 for tar does)\n            blocks, remainder = divmod(self.offset, RECORDSIZE)\n            if remainder > 0:\n                self.fileobj.write(NUL * (RECORDSIZE - remainder))\n\n        if not self._extfileobj:\n            self.fileobj.close()\n        self.closed = True\n\n    def getmember(self, name):\n        \"\"\"Return a TarInfo object for member `name'. If `name' can not be\n           found in the archive, KeyError is raised. If a member occurs more\n           than once in the archive, its last occurrence is assumed to be the\n           most up-to-date version.\n        \"\"\"\n        tarinfo = self._getmember(name)\n        if tarinfo is None:\n            raise KeyError(\"filename %r not found\" % name)\n        return tarinfo\n\n    def getmembers(self):\n        \"\"\"Return the members of the archive as a list of TarInfo objects. The\n           list has the same order as the members in the archive.\n        \"\"\"\n        self._check()\n        if not self._loaded:    # if we want to obtain a list of\n            self._load()        # all members, we first have to\n                                # scan the whole archive.\n        return self.members\n\n    def getnames(self):\n        \"\"\"Return the members of the archive as a list of their names. It has\n           the same order as the list returned by getmembers().\n        \"\"\"\n        return [tarinfo.name for tarinfo in self.getmembers()]\n\n    def gettarinfo(self, name=None, arcname=None, fileobj=None):\n        \"\"\"Create a TarInfo object for either the file `name' or the file\n           object `fileobj' (using os.fstat on its file descriptor). You can\n           modify some of the TarInfo's attributes before you add it using\n           addfile(). If given, `arcname' specifies an alternative name for the\n           file in the archive.\n        \"\"\"\n        self._check(\"aw\")\n\n        # When fileobj is given, replace name by\n        # fileobj's real name.\n        if fileobj is not None:\n            name = fileobj.name\n\n        # Building the name of the member in the archive.\n        # Backward slashes are converted to forward slashes,\n        # Absolute paths are turned to relative paths.\n        if arcname is None:\n            arcname = name\n        drv, arcname = os.path.splitdrive(arcname)\n        arcname = arcname.replace(os.sep, \"/\")\n        arcname = arcname.lstrip(\"/\")\n\n        # Now, fill the TarInfo object with\n        # information specific for the file.\n        tarinfo = self.tarinfo()\n        tarinfo.tarfile = self\n\n        # Use os.stat or os.lstat, depending on platform\n        # and if symlinks shall be resolved.\n        if fileobj is None:\n            if hasattr(os, \"lstat\") and not self.dereference:\n                statres = os.lstat(name)\n            else:\n                statres = os.stat(name)\n        else:\n            statres = os.fstat(fileobj.fileno())\n        linkname = \"\"\n\n        stmd = statres.st_mode\n        if stat.S_ISREG(stmd):\n            inode = (statres.st_ino, statres.st_dev)\n            if not self.dereference and statres.st_nlink > 1 and \\\n                    inode in self.inodes and arcname != self.inodes[inode]:\n                # Is it a hardlink to an already\n                # archived file?\n                type = LNKTYPE\n                linkname = self.inodes[inode]\n            else:\n                # The inode is added only if its valid.\n                # For win32 it is always 0.\n                type = REGTYPE\n                if inode[0]:\n                    self.inodes[inode] = arcname\n        elif stat.S_ISDIR(stmd):\n            type = DIRTYPE\n        elif stat.S_ISFIFO(stmd):\n            type = FIFOTYPE\n        elif stat.S_ISLNK(stmd):\n            type = SYMTYPE\n            linkname = os.readlink(name)\n        elif stat.S_ISCHR(stmd):\n            type = CHRTYPE\n        elif stat.S_ISBLK(stmd):\n            type = BLKTYPE\n        else:\n            return None\n\n        # Fill the TarInfo object with all\n        # information we can get.\n        tarinfo.name = arcname\n        tarinfo.mode = stmd\n        tarinfo.uid = statres.st_uid\n        tarinfo.gid = statres.st_gid\n        if type == REGTYPE:\n            tarinfo.size = statres.st_size\n        else:\n            tarinfo.size = 0\n        tarinfo.mtime = statres.st_mtime\n        tarinfo.type = type\n        tarinfo.linkname = linkname\n        if pwd:\n            try:\n                tarinfo.uname = pwd.getpwuid(tarinfo.uid)[0]\n            except KeyError:\n                pass\n        if grp:\n            try:\n                tarinfo.gname = grp.getgrgid(tarinfo.gid)[0]\n            except KeyError:\n                pass\n\n        if type in (CHRTYPE, BLKTYPE):\n            if hasattr(os, \"major\") and hasattr(os, \"minor\"):\n                tarinfo.devmajor = os.major(statres.st_rdev)\n                tarinfo.devminor = os.minor(statres.st_rdev)\n        return tarinfo\n\n    def list(self, verbose=True):\n        \"\"\"Print a table of contents to sys.stdout. If `verbose' is False, only\n           the names of the members are printed. If it is True, an `ls -l'-like\n           output is produced.\n        \"\"\"\n        self._check()\n\n        for tarinfo in self:\n            if verbose:\n                print(filemode(tarinfo.mode), end=' ')\n                print(\"%s/%s\" % (tarinfo.uname or tarinfo.uid,\n                                 tarinfo.gname or tarinfo.gid), end=' ')\n                if tarinfo.ischr() or tarinfo.isblk():\n                    print(\"%10s\" % (\"%d,%d\" \\\n                                    % (tarinfo.devmajor, tarinfo.devminor)), end=' ')\n                else:\n                    print(\"%10d\" % tarinfo.size, end=' ')\n                print(\"%d-%02d-%02d %02d:%02d:%02d\" \\\n                      % time.localtime(tarinfo.mtime)[:6], end=' ')\n\n            print(tarinfo.name + (\"/\" if tarinfo.isdir() else \"\"), end=' ')\n\n            if verbose:\n                if tarinfo.issym():\n                    print(\"->\", tarinfo.linkname, end=' ')\n                if tarinfo.islnk():\n                    print(\"link to\", tarinfo.linkname, end=' ')\n            print()\n\n    def add(self, name, arcname=None, recursive=True, exclude=None, filter=None):\n        \"\"\"Add the file `name' to the archive. `name' may be any type of file\n           (directory, fifo, symbolic link, etc.). If given, `arcname'\n           specifies an alternative name for the file in the archive.\n           Directories are added recursively by default. This can be avoided by\n           setting `recursive' to False. `exclude' is a function that should\n           return True for each filename to be excluded. `filter' is a function\n           that expects a TarInfo object argument and returns the changed\n           TarInfo object, if it returns None the TarInfo object will be\n           excluded from the archive.\n        \"\"\"\n        self._check(\"aw\")\n\n        if arcname is None:\n            arcname = name\n\n        # Exclude pathnames.\n        if exclude is not None:\n            import warnings\n            warnings.warn(\"use the filter argument instead\",\n                    DeprecationWarning, 2)\n            if exclude(name):\n                self._dbg(2, \"tarfile: Excluded %r\" % name)\n                return\n\n        # Skip if somebody tries to archive the archive...\n        if self.name is not None and os.path.abspath(name) == self.name:\n            self._dbg(2, \"tarfile: Skipped %r\" % name)\n            return\n\n        self._dbg(1, name)\n\n        # Create a TarInfo object from the file.\n        tarinfo = self.gettarinfo(name, arcname)\n\n        if tarinfo is None:\n            self._dbg(1, \"tarfile: Unsupported type %r\" % name)\n            return\n\n        # Change or exclude the TarInfo object.\n        if filter is not None:\n            tarinfo = filter(tarinfo)\n            if tarinfo is None:\n                self._dbg(2, \"tarfile: Excluded %r\" % name)\n                return\n\n        # Append the tar header and data to the archive.\n        if tarinfo.isreg():\n            f = bltn_open(name, \"rb\")\n            self.addfile(tarinfo, f)\n            f.close()\n\n        elif tarinfo.isdir():\n            self.addfile(tarinfo)\n            if recursive:\n                for f in os.listdir(name):\n                    self.add(os.path.join(name, f), os.path.join(arcname, f),\n                            recursive, exclude, filter=filter)\n\n        else:\n            self.addfile(tarinfo)\n\n    def addfile(self, tarinfo, fileobj=None):\n        \"\"\"Add the TarInfo object `tarinfo' to the archive. If `fileobj' is\n           given, tarinfo.size bytes are read from it and added to the archive.\n           You can create TarInfo objects using gettarinfo().\n           On Windows platforms, `fileobj' should always be opened with mode\n           'rb' to avoid irritation about the file size.\n        \"\"\"\n        self._check(\"aw\")\n\n        tarinfo = copy.copy(tarinfo)\n\n        buf = tarinfo.tobuf(self.format, self.encoding, self.errors)\n        self.fileobj.write(buf)\n        self.offset += len(buf)\n\n        # If there's data to follow, append it.\n        if fileobj is not None:\n            copyfileobj(fileobj, self.fileobj, tarinfo.size)\n            blocks, remainder = divmod(tarinfo.size, BLOCKSIZE)\n            if remainder > 0:\n                self.fileobj.write(NUL * (BLOCKSIZE - remainder))\n                blocks += 1\n            self.offset += blocks * BLOCKSIZE\n\n        self.members.append(tarinfo)\n\n    def extractall(self, path=\".\", members=None):\n        \"\"\"Extract all members from the archive to the current working\n           directory and set owner, modification time and permissions on\n           directories afterwards. `path' specifies a different directory\n           to extract to. `members' is optional and must be a subset of the\n           list returned by getmembers().\n        \"\"\"\n        directories = []\n\n        if members is None:\n            members = self\n\n        for tarinfo in members:\n            if tarinfo.isdir():\n                # Extract directories with a safe mode.\n                directories.append(tarinfo)\n                tarinfo = copy.copy(tarinfo)\n                tarinfo.mode = 0o700\n            # Do not set_attrs directories, as we will do that further down\n            self.extract(tarinfo, path, set_attrs=not tarinfo.isdir())\n\n        # Reverse sort directories.\n        directories.sort(key=lambda a: a.name)\n        directories.reverse()\n\n        # Set correct owner, mtime and filemode on directories.\n        for tarinfo in directories:\n            dirpath = os.path.join(path, tarinfo.name)\n            try:\n                self.chown(tarinfo, dirpath)\n                self.utime(tarinfo, dirpath)\n                self.chmod(tarinfo, dirpath)\n            except ExtractError as e:\n                if self.errorlevel > 1:\n                    raise\n                else:\n                    self._dbg(1, \"tarfile: %s\" % e)\n\n    def extract(self, member, path=\"\", set_attrs=True):\n        \"\"\"Extract a member from the archive to the current working directory,\n           using its full name. Its file information is extracted as accurately\n           as possible. `member' may be a filename or a TarInfo object. You can\n           specify a different directory using `path'. File attributes (owner,\n           mtime, mode) are set unless `set_attrs' is False.\n        \"\"\"\n        self._check(\"r\")\n\n        if isinstance(member, str):\n            tarinfo = self.getmember(member)\n        else:\n            tarinfo = member\n\n        # Prepare the link target for makelink().\n        if tarinfo.islnk():\n            tarinfo._link_target = os.path.join(path, tarinfo.linkname)\n\n        try:\n            self._extract_member(tarinfo, os.path.join(path, tarinfo.name),\n                                 set_attrs=set_attrs)\n        except EnvironmentError as e:\n            if self.errorlevel > 0:\n                raise\n            else:\n                if e.filename is None:\n                    self._dbg(1, \"tarfile: %s\" % e.strerror)\n                else:\n                    self._dbg(1, \"tarfile: %s %r\" % (e.strerror, e.filename))\n        except ExtractError as e:\n            if self.errorlevel > 1:\n                raise\n            else:\n                self._dbg(1, \"tarfile: %s\" % e)\n\n    def extractfile(self, member):\n        \"\"\"Extract a member from the archive as a file object. `member' may be\n           a filename or a TarInfo object. If `member' is a regular file, a\n           file-like object is returned. If `member' is a link, a file-like\n           object is constructed from the link's target. If `member' is none of\n           the above, None is returned.\n           The file-like object is read-only and provides the following\n           methods: read(), readline(), readlines(), seek() and tell()\n        \"\"\"\n        self._check(\"r\")\n\n        if isinstance(member, str):\n            tarinfo = self.getmember(member)\n        else:\n            tarinfo = member\n\n        if tarinfo.isreg():\n            return self.fileobject(self, tarinfo)\n\n        elif tarinfo.type not in SUPPORTED_TYPES:\n            # If a member's type is unknown, it is treated as a\n            # regular file.\n            return self.fileobject(self, tarinfo)\n\n        elif tarinfo.islnk() or tarinfo.issym():\n            if isinstance(self.fileobj, _Stream):\n                # A small but ugly workaround for the case that someone tries\n                # to extract a (sym)link as a file-object from a non-seekable\n                # stream of tar blocks.\n                raise StreamError(\"cannot extract (sym)link as file object\")\n            else:\n                # A (sym)link's file object is its target's file object.\n                return self.extractfile(self._find_link_target(tarinfo))\n        else:\n            # If there's no data associated with the member (directory, chrdev,\n            # blkdev, etc.), return None instead of a file object.\n            return None\n\n    def _extract_member(self, tarinfo, targetpath, set_attrs=True):\n        \"\"\"Extract the TarInfo object tarinfo to a physical\n           file called targetpath.\n        \"\"\"\n        # Fetch the TarInfo object for the given name\n        # and build the destination pathname, replacing\n        # forward slashes to platform specific separators.\n        targetpath = targetpath.rstrip(\"/\")\n        targetpath = targetpath.replace(\"/\", os.sep)\n\n        # Create all upper directories.\n        upperdirs = os.path.dirname(targetpath)\n        if upperdirs and not os.path.exists(upperdirs):\n            # Create directories that are not part of the archive with\n            # default permissions.\n            os.makedirs(upperdirs)\n\n        if tarinfo.islnk() or tarinfo.issym():\n            self._dbg(1, \"%s -> %s\" % (tarinfo.name, tarinfo.linkname))\n        else:\n            self._dbg(1, tarinfo.name)\n\n        if tarinfo.isreg():\n            self.makefile(tarinfo, targetpath)\n        elif tarinfo.isdir():\n            self.makedir(tarinfo, targetpath)\n        elif tarinfo.isfifo():\n            self.makefifo(tarinfo, targetpath)\n        elif tarinfo.ischr() or tarinfo.isblk():\n            self.makedev(tarinfo, targetpath)\n        elif tarinfo.islnk() or tarinfo.issym():\n            self.makelink(tarinfo, targetpath)\n        elif tarinfo.type not in SUPPORTED_TYPES:\n            self.makeunknown(tarinfo, targetpath)\n        else:\n            self.makefile(tarinfo, targetpath)\n\n        if set_attrs:\n            self.chown(tarinfo, targetpath)\n            if not tarinfo.issym():\n                self.chmod(tarinfo, targetpath)\n                self.utime(tarinfo, targetpath)\n\n    #--------------------------------------------------------------------------\n    # Below are the different file methods. They are called via\n    # _extract_member() when extract() is called. They can be replaced in a\n    # subclass to implement other functionality.\n\n    def makedir(self, tarinfo, targetpath):\n        \"\"\"Make a directory called targetpath.\n        \"\"\"\n        try:\n            # Use a safe mode for the directory, the real mode is set\n            # later in _extract_member().\n            os.mkdir(targetpath, 0o700)\n        except EnvironmentError as e:\n            if e.errno != errno.EEXIST:\n                raise\n\n    def makefile(self, tarinfo, targetpath):\n        \"\"\"Make a file called targetpath.\n        \"\"\"\n        source = self.fileobj\n        source.seek(tarinfo.offset_data)\n        target = bltn_open(targetpath, \"wb\")\n        if tarinfo.sparse is not None:\n            for offset, size in tarinfo.sparse:\n                target.seek(offset)\n                copyfileobj(source, target, size)\n        else:\n            copyfileobj(source, target, tarinfo.size)\n        target.seek(tarinfo.size)\n        target.truncate()\n        target.close()\n\n    def makeunknown(self, tarinfo, targetpath):\n        \"\"\"Make a file from a TarInfo object with an unknown type\n           at targetpath.\n        \"\"\"\n        self.makefile(tarinfo, targetpath)\n        self._dbg(1, \"tarfile: Unknown file type %r, \" \\\n                     \"extracted as regular file.\" % tarinfo.type)\n\n    def makefifo(self, tarinfo, targetpath):\n        \"\"\"Make a fifo called targetpath.\n        \"\"\"\n        if hasattr(os, \"mkfifo\"):\n            os.mkfifo(targetpath)\n        else:\n            raise ExtractError(\"fifo not supported by system\")\n\n    def makedev(self, tarinfo, targetpath):\n        \"\"\"Make a character or block device called targetpath.\n        \"\"\"\n        if not hasattr(os, \"mknod\") or not hasattr(os, \"makedev\"):\n            raise ExtractError(\"special devices not supported by system\")\n\n        mode = tarinfo.mode\n        if tarinfo.isblk():\n            mode |= stat.S_IFBLK\n        else:\n            mode |= stat.S_IFCHR\n\n        os.mknod(targetpath, mode,\n                 os.makedev(tarinfo.devmajor, tarinfo.devminor))\n\n    def makelink(self, tarinfo, targetpath):\n        \"\"\"Make a (symbolic) link called targetpath. If it cannot be created\n          (platform limitation), we try to make a copy of the referenced file\n          instead of a link.\n        \"\"\"\n        try:\n            # For systems that support symbolic and hard links.\n            if tarinfo.issym():\n                os.symlink(tarinfo.linkname, targetpath)\n            else:\n                # See extract().\n                if os.path.exists(tarinfo._link_target):\n                    os.link(tarinfo._link_target, targetpath)\n                else:\n                    self._extract_member(self._find_link_target(tarinfo),\n                                         targetpath)\n        except symlink_exception:\n            if tarinfo.issym():\n                linkpath = os.path.join(os.path.dirname(tarinfo.name),\n                                        tarinfo.linkname)\n            else:\n                linkpath = tarinfo.linkname\n        else:\n            try:\n                self._extract_member(self._find_link_target(tarinfo),\n                                     targetpath)\n            except KeyError:\n                raise ExtractError(\"unable to resolve link inside archive\")\n\n    def chown(self, tarinfo, targetpath):\n        \"\"\"Set owner of targetpath according to tarinfo.\n        \"\"\"\n        if pwd and hasattr(os, \"geteuid\") and os.geteuid() == 0:\n            # We have to be root to do so.\n            try:\n                g = grp.getgrnam(tarinfo.gname)[2]\n            except KeyError:\n                g = tarinfo.gid\n            try:\n                u = pwd.getpwnam(tarinfo.uname)[2]\n            except KeyError:\n                u = tarinfo.uid\n            try:\n                if tarinfo.issym() and hasattr(os, \"lchown\"):\n                    os.lchown(targetpath, u, g)\n                else:\n                    if sys.platform != \"os2emx\":\n                        os.chown(targetpath, u, g)\n            except EnvironmentError as e:\n                raise ExtractError(\"could not change owner\")\n\n    def chmod(self, tarinfo, targetpath):\n        \"\"\"Set file permissions of targetpath according to tarinfo.\n        \"\"\"\n        if hasattr(os, 'chmod'):\n            try:\n                os.chmod(targetpath, tarinfo.mode)\n            except EnvironmentError as e:\n                raise ExtractError(\"could not change mode\")\n\n    def utime(self, tarinfo, targetpath):\n        \"\"\"Set modification time of targetpath according to tarinfo.\n        \"\"\"\n        if not hasattr(os, 'utime'):\n            return\n        try:\n            os.utime(targetpath, (tarinfo.mtime, tarinfo.mtime))\n        except EnvironmentError as e:\n            raise ExtractError(\"could not change modification time\")\n\n    #--------------------------------------------------------------------------\n    def next(self):\n        \"\"\"Return the next member of the archive as a TarInfo object, when\n           TarFile is opened for reading. Return None if there is no more\n           available.\n        \"\"\"\n        self._check(\"ra\")\n        if self.firstmember is not None:\n            m = self.firstmember\n            self.firstmember = None\n            return m\n\n        # Read the next block.\n        self.fileobj.seek(self.offset)\n        tarinfo = None\n        while True:\n            try:\n                tarinfo = self.tarinfo.fromtarfile(self)\n            except EOFHeaderError as e:\n                if self.ignore_zeros:\n                    self._dbg(2, \"0x%X: %s\" % (self.offset, e))\n                    self.offset += BLOCKSIZE\n                    continue\n            except InvalidHeaderError as e:\n                if self.ignore_zeros:\n                    self._dbg(2, \"0x%X: %s\" % (self.offset, e))\n                    self.offset += BLOCKSIZE\n                    continue\n                elif self.offset == 0:\n                    raise ReadError(str(e))\n            except EmptyHeaderError:\n                if self.offset == 0:\n                    raise ReadError(\"empty file\")\n            except TruncatedHeaderError as e:\n                if self.offset == 0:\n                    raise ReadError(str(e))\n            except SubsequentHeaderError as e:\n                raise ReadError(str(e))\n            break\n\n        if tarinfo is not None:\n            self.members.append(tarinfo)\n        else:\n            self._loaded = True\n\n        return tarinfo\n\n    #--------------------------------------------------------------------------\n    # Little helper methods:\n\n    def _getmember(self, name, tarinfo=None, normalize=False):\n        \"\"\"Find an archive member by name from bottom to top.\n           If tarinfo is given, it is used as the starting point.\n        \"\"\"\n        # Ensure that all members have been loaded.\n        members = self.getmembers()\n\n        # Limit the member search list up to tarinfo.\n        if tarinfo is not None:\n            members = members[:members.index(tarinfo)]\n\n        if normalize:\n            name = os.path.normpath(name)\n\n        for member in reversed(members):\n            if normalize:\n                member_name = os.path.normpath(member.name)\n            else:\n                member_name = member.name\n\n            if name == member_name:\n                return member\n\n    def _load(self):\n        \"\"\"Read through the entire archive file and look for readable\n           members.\n        \"\"\"\n        while True:\n            tarinfo = self.next()\n            if tarinfo is None:\n                break\n        self._loaded = True\n\n    def _check(self, mode=None):\n        \"\"\"Check if TarFile is still open, and if the operation's mode\n           corresponds to TarFile's mode.\n        \"\"\"\n        if self.closed:\n            raise IOError(\"%s is closed\" % self.__class__.__name__)\n        if mode is not None and self.mode not in mode:\n            raise IOError(\"bad operation for mode %r\" % self.mode)\n\n    def _find_link_target(self, tarinfo):\n        \"\"\"Find the target member of a symlink or hardlink member in the\n           archive.\n        \"\"\"\n        if tarinfo.issym():\n            # Always search the entire archive.\n            linkname = os.path.dirname(tarinfo.name) + \"/\" + tarinfo.linkname\n            limit = None\n        else:\n            # Search the archive before the link, because a hard link is\n            # just a reference to an already archived file.\n            linkname = tarinfo.linkname\n            limit = tarinfo\n\n        member = self._getmember(linkname, tarinfo=limit, normalize=True)\n        if member is None:\n            raise KeyError(\"linkname %r not found\" % linkname)\n        return member\n\n    def __iter__(self):\n        \"\"\"Provide an iterator object.\n        \"\"\"\n        if self._loaded:\n            return iter(self.members)\n        else:\n            return TarIter(self)\n\n    def _dbg(self, level, msg):\n        \"\"\"Write debugging output to sys.stderr.\n        \"\"\"\n        if level <= self.debug:\n            print(msg, file=sys.stderr)\n\n    def __enter__(self):\n        self._check()\n        return self\n\n    def __exit__(self, type, value, traceback):\n        if type is None:\n            self.close()\n        else:\n            # An exception occurred. We must not call close() because\n            # it would try to write end-of-archive blocks and padding.\n            if not self._extfileobj:\n                self.fileobj.close()\n            self.closed = True\n# class TarFile\n\nclass TarIter(object):\n    \"\"\"Iterator Class.\n\n       for tarinfo in TarFile(...):\n           suite...\n    \"\"\"\n\n    def __init__(self, tarfile):\n        \"\"\"Construct a TarIter object.\n        \"\"\"\n        self.tarfile = tarfile\n        self.index = 0\n    def __iter__(self):\n        \"\"\"Return iterator object.\n        \"\"\"\n        return self\n\n    def __next__(self):\n        \"\"\"Return the next item using TarFile's next() method.\n           When all members have been read, set TarFile as _loaded.\n        \"\"\"\n        # Fix for SF #1100429: Under rare circumstances it can\n        # happen that getmembers() is called during iteration,\n        # which will cause TarIter to stop prematurely.\n        if not self.tarfile._loaded:\n            tarinfo = self.tarfile.next()\n            if not tarinfo:\n                self.tarfile._loaded = True\n                raise StopIteration\n        else:\n            try:\n                tarinfo = self.tarfile.members[self.index]\n            except IndexError:\n                raise StopIteration\n        self.index += 1\n        return tarinfo\n\n    next = __next__ # for Python 2.x\n\n#--------------------\n# exported functions\n#--------------------\ndef is_tarfile(name):\n    \"\"\"Return True if name points to a tar archive that we\n       are able to handle, else return False.\n    \"\"\"\n    try:\n        t = open(name)\n        t.close()\n        return True\n    except TarError:\n        return False\n\nbltn_open = open\nopen = TarFile.open\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/compat.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2013-2017 Vinay Sajip.\n# Licensed to the Python Software Foundation under a contributor agreement.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\nfrom __future__ import absolute_import\n\nimport os\nimport re\nimport sys\n\ntry:\n    import ssl\nexcept ImportError:  # pragma: no cover\n    ssl = None\n\nif sys.version_info[0] < 3:  # pragma: no cover\n    from StringIO import StringIO\n    string_types = basestring,\n    text_type = unicode\n    from types import FileType as file_type\n    import __builtin__ as builtins\n    import ConfigParser as configparser\n    from ._backport import shutil\n    from urlparse import urlparse, urlunparse, urljoin, urlsplit, urlunsplit\n    from urllib import (urlretrieve, quote as _quote, unquote, url2pathname,\n                        pathname2url, ContentTooShortError, splittype)\n\n    def quote(s):\n        if isinstance(s, unicode):\n            s = s.encode('utf-8')\n        return _quote(s)\n\n    import urllib2\n    from urllib2 import (Request, urlopen, URLError, HTTPError,\n                         HTTPBasicAuthHandler, HTTPPasswordMgr,\n                         HTTPHandler, HTTPRedirectHandler,\n                         build_opener)\n    if ssl:\n        from urllib2 import HTTPSHandler\n    import httplib\n    import xmlrpclib\n    import Queue as queue\n    from HTMLParser import HTMLParser\n    import htmlentitydefs\n    raw_input = raw_input\n    from itertools import ifilter as filter\n    from itertools import ifilterfalse as filterfalse\n\n    _userprog = None\n    def splituser(host):\n        \"\"\"splituser('user[:passwd]@host[:port]') --> 'user[:passwd]', 'host[:port]'.\"\"\"\n        global _userprog\n        if _userprog is None:\n            import re\n            _userprog = re.compile('^(.*)@(.*)$')\n\n        match = _userprog.match(host)\n        if match: return match.group(1, 2)\n        return None, host\n\nelse:  # pragma: no cover\n    from io import StringIO\n    string_types = str,\n    text_type = str\n    from io import TextIOWrapper as file_type\n    import builtins\n    import configparser\n    import shutil\n    from urllib.parse import (urlparse, urlunparse, urljoin, splituser, quote,\n                              unquote, urlsplit, urlunsplit, splittype)\n    from urllib.request import (urlopen, urlretrieve, Request, url2pathname,\n                                pathname2url,\n                                HTTPBasicAuthHandler, HTTPPasswordMgr,\n                                HTTPHandler, HTTPRedirectHandler,\n                                build_opener)\n    if ssl:\n        from urllib.request import HTTPSHandler\n    from urllib.error import HTTPError, URLError, ContentTooShortError\n    import http.client as httplib\n    import urllib.request as urllib2\n    import xmlrpc.client as xmlrpclib\n    import queue\n    from html.parser import HTMLParser\n    import html.entities as htmlentitydefs\n    raw_input = input\n    from itertools import filterfalse\n    filter = filter\n\ntry:\n    from ssl import match_hostname, CertificateError\nexcept ImportError: # pragma: no cover\n    class CertificateError(ValueError):\n        pass\n\n\n    def _dnsname_match(dn, hostname, max_wildcards=1):\n        \"\"\"Matching according to RFC 6125, section 6.4.3\n\n        http://tools.ietf.org/html/rfc6125#section-6.4.3\n        \"\"\"\n        pats = []\n        if not dn:\n            return False\n\n        parts = dn.split('.')\n        leftmost, remainder = parts[0], parts[1:]\n\n        wildcards = leftmost.count('*')\n        if wildcards > max_wildcards:\n            # Issue #17980: avoid denials of service by refusing more\n            # than one wildcard per fragment.  A survey of established\n            # policy among SSL implementations showed it to be a\n            # reasonable choice.\n            raise CertificateError(\n                \"too many wildcards in certificate DNS name: \" + repr(dn))\n\n        # speed up common case w/o wildcards\n        if not wildcards:\n            return dn.lower() == hostname.lower()\n\n        # RFC 6125, section 6.4.3, subitem 1.\n        # The client SHOULD NOT attempt to match a presented identifier in which\n        # the wildcard character comprises a label other than the left-most label.\n        if leftmost == '*':\n            # When '*' is a fragment by itself, it matches a non-empty dotless\n            # fragment.\n            pats.append('[^.]+')\n        elif leftmost.startswith('xn--') or hostname.startswith('xn--'):\n            # RFC 6125, section 6.4.3, subitem 3.\n            # The client SHOULD NOT attempt to match a presented identifier\n            # where the wildcard character is embedded within an A-label or\n            # U-label of an internationalized domain name.\n            pats.append(re.escape(leftmost))\n        else:\n            # Otherwise, '*' matches any dotless string, e.g. www*\n            pats.append(re.escape(leftmost).replace(r'\\*', '[^.]*'))\n\n        # add the remaining fragments, ignore any wildcards\n        for frag in remainder:\n            pats.append(re.escape(frag))\n\n        pat = re.compile(r'\\A' + r'\\.'.join(pats) + r'\\Z', re.IGNORECASE)\n        return pat.match(hostname)\n\n\n    def match_hostname(cert, hostname):\n        \"\"\"Verify that *cert* (in decoded format as returned by\n        SSLSocket.getpeercert()) matches the *hostname*.  RFC 2818 and RFC 6125\n        rules are followed, but IP addresses are not accepted for *hostname*.\n\n        CertificateError is raised on failure. On success, the function\n        returns nothing.\n        \"\"\"\n        if not cert:\n            raise ValueError(\"empty or no certificate, match_hostname needs a \"\n                             \"SSL socket or SSL context with either \"\n                             \"CERT_OPTIONAL or CERT_REQUIRED\")\n        dnsnames = []\n        san = cert.get('subjectAltName', ())\n        for key, value in san:\n            if key == 'DNS':\n                if _dnsname_match(value, hostname):\n                    return\n                dnsnames.append(value)\n        if not dnsnames:\n            # The subject is only checked when there is no dNSName entry\n            # in subjectAltName\n            for sub in cert.get('subject', ()):\n                for key, value in sub:\n                    # XXX according to RFC 2818, the most specific Common Name\n                    # must be used.\n                    if key == 'commonName':\n                        if _dnsname_match(value, hostname):\n                            return\n                        dnsnames.append(value)\n        if len(dnsnames) > 1:\n            raise CertificateError(\"hostname %r \"\n                \"doesn't match either of %s\"\n                % (hostname, ', '.join(map(repr, dnsnames))))\n        elif len(dnsnames) == 1:\n            raise CertificateError(\"hostname %r \"\n                \"doesn't match %r\"\n                % (hostname, dnsnames[0]))\n        else:\n            raise CertificateError(\"no appropriate commonName or \"\n                \"subjectAltName fields were found\")\n\n\ntry:\n    from types import SimpleNamespace as Container\nexcept ImportError:  # pragma: no cover\n    class Container(object):\n        \"\"\"\n        A generic container for when multiple values need to be returned\n        \"\"\"\n        def __init__(self, **kwargs):\n            self.__dict__.update(kwargs)\n\n\ntry:\n    from shutil import which\nexcept ImportError:  # pragma: no cover\n    # Implementation from Python 3.3\n    def which(cmd, mode=os.F_OK | os.X_OK, path=None):\n        \"\"\"Given a command, mode, and a PATH string, return the path which\n        conforms to the given mode on the PATH, or None if there is no such\n        file.\n\n        `mode` defaults to os.F_OK | os.X_OK. `path` defaults to the result\n        of os.environ.get(\"PATH\"), or can be overridden with a custom search\n        path.\n\n        \"\"\"\n        # Check that a given file can be accessed with the correct mode.\n        # Additionally check that `file` is not a directory, as on Windows\n        # directories pass the os.access check.\n        def _access_check(fn, mode):\n            return (os.path.exists(fn) and os.access(fn, mode)\n                    and not os.path.isdir(fn))\n\n        # If we're given a path with a directory part, look it up directly rather\n        # than referring to PATH directories. This includes checking relative to the\n        # current directory, e.g. ./script\n        if os.path.dirname(cmd):\n            if _access_check(cmd, mode):\n                return cmd\n            return None\n\n        if path is None:\n            path = os.environ.get(\"PATH\", os.defpath)\n        if not path:\n            return None\n        path = path.split(os.pathsep)\n\n        if sys.platform == \"win32\":\n            # The current directory takes precedence on Windows.\n            if not os.curdir in path:\n                path.insert(0, os.curdir)\n\n            # PATHEXT is necessary to check on Windows.\n            pathext = os.environ.get(\"PATHEXT\", \"\").split(os.pathsep)\n            # See if the given file matches any of the expected path extensions.\n            # This will allow us to short circuit when given \"python.exe\".\n            # If it does match, only test that one, otherwise we have to try\n            # others.\n            if any(cmd.lower().endswith(ext.lower()) for ext in pathext):\n                files = [cmd]\n            else:\n                files = [cmd + ext for ext in pathext]\n        else:\n            # On other platforms you don't have things like PATHEXT to tell you\n            # what file suffixes are executable, so just pass on cmd as-is.\n            files = [cmd]\n\n        seen = set()\n        for dir in path:\n            normdir = os.path.normcase(dir)\n            if not normdir in seen:\n                seen.add(normdir)\n                for thefile in files:\n                    name = os.path.join(dir, thefile)\n                    if _access_check(name, mode):\n                        return name\n        return None\n\n\n# ZipFile is a context manager in 2.7, but not in 2.6\n\nfrom zipfile import ZipFile as BaseZipFile\n\nif hasattr(BaseZipFile, '__enter__'):  # pragma: no cover\n    ZipFile = BaseZipFile\nelse:  # pragma: no cover\n    from zipfile import ZipExtFile as BaseZipExtFile\n\n    class ZipExtFile(BaseZipExtFile):\n        def __init__(self, base):\n            self.__dict__.update(base.__dict__)\n\n        def __enter__(self):\n            return self\n\n        def __exit__(self, *exc_info):\n            self.close()\n            # return None, so if an exception occurred, it will propagate\n\n    class ZipFile(BaseZipFile):\n        def __enter__(self):\n            return self\n\n        def __exit__(self, *exc_info):\n            self.close()\n            # return None, so if an exception occurred, it will propagate\n\n        def open(self, *args, **kwargs):\n            base = BaseZipFile.open(self, *args, **kwargs)\n            return ZipExtFile(base)\n\ntry:\n    from platform import python_implementation\nexcept ImportError: # pragma: no cover\n    def python_implementation():\n        \"\"\"Return a string identifying the Python implementation.\"\"\"\n        if 'PyPy' in sys.version:\n            return 'PyPy'\n        if os.name == 'java':\n            return 'Jython'\n        if sys.version.startswith('IronPython'):\n            return 'IronPython'\n        return 'CPython'\n\ntry:\n    import sysconfig\nexcept ImportError: # pragma: no cover\n    from ._backport import sysconfig\n\ntry:\n    callable = callable\nexcept NameError:   # pragma: no cover\n    from collections import Callable\n\n    def callable(obj):\n        return isinstance(obj, Callable)\n\n\ntry:\n    fsencode = os.fsencode\n    fsdecode = os.fsdecode\nexcept AttributeError:  # pragma: no cover\n    # Issue #99: on some systems (e.g. containerised),\n    # sys.getfilesystemencoding() returns None, and we need a real value,\n    # so fall back to utf-8. From the CPython 2.7 docs relating to Unix and\n    # sys.getfilesystemencoding(): the return value is \"the user’s preference\n    # according to the result of nl_langinfo(CODESET), or None if the\n    # nl_langinfo(CODESET) failed.\"\n    _fsencoding = sys.getfilesystemencoding() or 'utf-8'\n    if _fsencoding == 'mbcs':\n        _fserrors = 'strict'\n    else:\n        _fserrors = 'surrogateescape'\n\n    def fsencode(filename):\n        if isinstance(filename, bytes):\n            return filename\n        elif isinstance(filename, text_type):\n            return filename.encode(_fsencoding, _fserrors)\n        else:\n            raise TypeError(\"expect bytes or str, not %s\" %\n                            type(filename).__name__)\n\n    def fsdecode(filename):\n        if isinstance(filename, text_type):\n            return filename\n        elif isinstance(filename, bytes):\n            return filename.decode(_fsencoding, _fserrors)\n        else:\n            raise TypeError(\"expect bytes or str, not %s\" %\n                            type(filename).__name__)\n\ntry:\n    from tokenize import detect_encoding\nexcept ImportError: # pragma: no cover\n    from codecs import BOM_UTF8, lookup\n    import re\n\n    cookie_re = re.compile(r\"coding[:=]\\s*([-\\w.]+)\")\n\n    def _get_normal_name(orig_enc):\n        \"\"\"Imitates get_normal_name in tokenizer.c.\"\"\"\n        # Only care about the first 12 characters.\n        enc = orig_enc[:12].lower().replace(\"_\", \"-\")\n        if enc == \"utf-8\" or enc.startswith(\"utf-8-\"):\n            return \"utf-8\"\n        if enc in (\"latin-1\", \"iso-8859-1\", \"iso-latin-1\") or \\\n           enc.startswith((\"latin-1-\", \"iso-8859-1-\", \"iso-latin-1-\")):\n            return \"iso-8859-1\"\n        return orig_enc\n\n    def detect_encoding(readline):\n        \"\"\"\n        The detect_encoding() function is used to detect the encoding that should\n        be used to decode a Python source file.  It requires one argument, readline,\n        in the same way as the tokenize() generator.\n\n        It will call readline a maximum of twice, and return the encoding used\n        (as a string) and a list of any lines (left as bytes) it has read in.\n\n        It detects the encoding from the presence of a utf-8 bom or an encoding\n        cookie as specified in pep-0263.  If both a bom and a cookie are present,\n        but disagree, a SyntaxError will be raised.  If the encoding cookie is an\n        invalid charset, raise a SyntaxError.  Note that if a utf-8 bom is found,\n        'utf-8-sig' is returned.\n\n        If no encoding is specified, then the default of 'utf-8' will be returned.\n        \"\"\"\n        try:\n            filename = readline.__self__.name\n        except AttributeError:\n            filename = None\n        bom_found = False\n        encoding = None\n        default = 'utf-8'\n        def read_or_stop():\n            try:\n                return readline()\n            except StopIteration:\n                return b''\n\n        def find_cookie(line):\n            try:\n                # Decode as UTF-8. Either the line is an encoding declaration,\n                # in which case it should be pure ASCII, or it must be UTF-8\n                # per default encoding.\n                line_string = line.decode('utf-8')\n            except UnicodeDecodeError:\n                msg = \"invalid or missing encoding declaration\"\n                if filename is not None:\n                    msg = '{} for {!r}'.format(msg, filename)\n                raise SyntaxError(msg)\n\n            matches = cookie_re.findall(line_string)\n            if not matches:\n                return None\n            encoding = _get_normal_name(matches[0])\n            try:\n                codec = lookup(encoding)\n            except LookupError:\n                # This behaviour mimics the Python interpreter\n                if filename is None:\n                    msg = \"unknown encoding: \" + encoding\n                else:\n                    msg = \"unknown encoding for {!r}: {}\".format(filename,\n                            encoding)\n                raise SyntaxError(msg)\n\n            if bom_found:\n                if codec.name != 'utf-8':\n                    # This behaviour mimics the Python interpreter\n                    if filename is None:\n                        msg = 'encoding problem: utf-8'\n                    else:\n                        msg = 'encoding problem for {!r}: utf-8'.format(filename)\n                    raise SyntaxError(msg)\n                encoding += '-sig'\n            return encoding\n\n        first = read_or_stop()\n        if first.startswith(BOM_UTF8):\n            bom_found = True\n            first = first[3:]\n            default = 'utf-8-sig'\n        if not first:\n            return default, []\n\n        encoding = find_cookie(first)\n        if encoding:\n            return encoding, [first]\n\n        second = read_or_stop()\n        if not second:\n            return default, [first]\n\n        encoding = find_cookie(second)\n        if encoding:\n            return encoding, [first, second]\n\n        return default, [first, second]\n\n# For converting & <-> &amp; etc.\ntry:\n    from html import escape\nexcept ImportError:\n    from cgi import escape\nif sys.version_info[:2] < (3, 4):\n    unescape = HTMLParser().unescape\nelse:\n    from html import unescape\n\ntry:\n    from collections import ChainMap\nexcept ImportError: # pragma: no cover\n    from collections import MutableMapping\n\n    try:\n        from reprlib import recursive_repr as _recursive_repr\n    except ImportError:\n        def _recursive_repr(fillvalue='...'):\n            '''\n            Decorator to make a repr function return fillvalue for a recursive\n            call\n            '''\n\n            def decorating_function(user_function):\n                repr_running = set()\n\n                def wrapper(self):\n                    key = id(self), get_ident()\n                    if key in repr_running:\n                        return fillvalue\n                    repr_running.add(key)\n                    try:\n                        result = user_function(self)\n                    finally:\n                        repr_running.discard(key)\n                    return result\n\n                # Can't use functools.wraps() here because of bootstrap issues\n                wrapper.__module__ = getattr(user_function, '__module__')\n                wrapper.__doc__ = getattr(user_function, '__doc__')\n                wrapper.__name__ = getattr(user_function, '__name__')\n                wrapper.__annotations__ = getattr(user_function, '__annotations__', {})\n                return wrapper\n\n            return decorating_function\n\n    class ChainMap(MutableMapping):\n        ''' A ChainMap groups multiple dicts (or other mappings) together\n        to create a single, updateable view.\n\n        The underlying mappings are stored in a list.  That list is public and can\n        accessed or updated using the *maps* attribute.  There is no other state.\n\n        Lookups search the underlying mappings successively until a key is found.\n        In contrast, writes, updates, and deletions only operate on the first\n        mapping.\n\n        '''\n\n        def __init__(self, *maps):\n            '''Initialize a ChainMap by setting *maps* to the given mappings.\n            If no mappings are provided, a single empty dictionary is used.\n\n            '''\n            self.maps = list(maps) or [{}]          # always at least one map\n\n        def __missing__(self, key):\n            raise KeyError(key)\n\n        def __getitem__(self, key):\n            for mapping in self.maps:\n                try:\n                    return mapping[key]             # can't use 'key in mapping' with defaultdict\n                except KeyError:\n                    pass\n            return self.__missing__(key)            # support subclasses that define __missing__\n\n        def get(self, key, default=None):\n            return self[key] if key in self else default\n\n        def __len__(self):\n            return len(set().union(*self.maps))     # reuses stored hash values if possible\n\n        def __iter__(self):\n            return iter(set().union(*self.maps))\n\n        def __contains__(self, key):\n            return any(key in m for m in self.maps)\n\n        def __bool__(self):\n            return any(self.maps)\n\n        @_recursive_repr()\n        def __repr__(self):\n            return '{0.__class__.__name__}({1})'.format(\n                self, ', '.join(map(repr, self.maps)))\n\n        @classmethod\n        def fromkeys(cls, iterable, *args):\n            'Create a ChainMap with a single dict created from the iterable.'\n            return cls(dict.fromkeys(iterable, *args))\n\n        def copy(self):\n            'New ChainMap or subclass with a new copy of maps[0] and refs to maps[1:]'\n            return self.__class__(self.maps[0].copy(), *self.maps[1:])\n\n        __copy__ = copy\n\n        def new_child(self):                        # like Django's Context.push()\n            'New ChainMap with a new dict followed by all previous maps.'\n            return self.__class__({}, *self.maps)\n\n        @property\n        def parents(self):                          # like Django's Context.pop()\n            'New ChainMap from maps[1:].'\n            return self.__class__(*self.maps[1:])\n\n        def __setitem__(self, key, value):\n            self.maps[0][key] = value\n\n        def __delitem__(self, key):\n            try:\n                del self.maps[0][key]\n            except KeyError:\n                raise KeyError('Key not found in the first mapping: {!r}'.format(key))\n\n        def popitem(self):\n            'Remove and return an item pair from maps[0]. Raise KeyError is maps[0] is empty.'\n            try:\n                return self.maps[0].popitem()\n            except KeyError:\n                raise KeyError('No keys found in the first mapping.')\n\n        def pop(self, key, *args):\n            'Remove *key* from maps[0] and return its value. Raise KeyError if *key* not in maps[0].'\n            try:\n                return self.maps[0].pop(key, *args)\n            except KeyError:\n                raise KeyError('Key not found in the first mapping: {!r}'.format(key))\n\n        def clear(self):\n            'Clear maps[0], leaving maps[1:] intact.'\n            self.maps[0].clear()\n\ntry:\n    from importlib.util import cache_from_source  # Python >= 3.4\nexcept ImportError:  # pragma: no cover\n    try:\n        from imp import cache_from_source\n    except ImportError:  # pragma: no cover\n        def cache_from_source(path, debug_override=None):\n            assert path.endswith('.py')\n            if debug_override is None:\n                debug_override = __debug__\n            if debug_override:\n                suffix = 'c'\n            else:\n                suffix = 'o'\n            return path + suffix\n\ntry:\n    from collections import OrderedDict\nexcept ImportError: # pragma: no cover\n## {{{ http://code.activestate.com/recipes/576693/ (r9)\n# Backport of OrderedDict() class that runs on Python 2.4, 2.5, 2.6, 2.7 and pypy.\n# Passes Python2.7's test suite and incorporates all the latest updates.\n    try:\n        from thread import get_ident as _get_ident\n    except ImportError:\n        from dummy_thread import get_ident as _get_ident\n\n    try:\n        from _abcoll import KeysView, ValuesView, ItemsView\n    except ImportError:\n        pass\n\n\n    class OrderedDict(dict):\n        'Dictionary that remembers insertion order'\n        # An inherited dict maps keys to values.\n        # The inherited dict provides __getitem__, __len__, __contains__, and get.\n        # The remaining methods are order-aware.\n        # Big-O running times for all methods are the same as for regular dictionaries.\n\n        # The internal self.__map dictionary maps keys to links in a doubly linked list.\n        # The circular doubly linked list starts and ends with a sentinel element.\n        # The sentinel element never gets deleted (this simplifies the algorithm).\n        # Each link is stored as a list of length three:  [PREV, NEXT, KEY].\n\n        def __init__(self, *args, **kwds):\n            '''Initialize an ordered dictionary.  Signature is the same as for\n            regular dictionaries, but keyword arguments are not recommended\n            because their insertion order is arbitrary.\n\n            '''\n            if len(args) > 1:\n                raise TypeError('expected at most 1 arguments, got %d' % len(args))\n            try:\n                self.__root\n            except AttributeError:\n                self.__root = root = []                     # sentinel node\n                root[:] = [root, root, None]\n                self.__map = {}\n            self.__update(*args, **kwds)\n\n        def __setitem__(self, key, value, dict_setitem=dict.__setitem__):\n            'od.__setitem__(i, y) <==> od[i]=y'\n            # Setting a new item creates a new link which goes at the end of the linked\n            # list, and the inherited dictionary is updated with the new key/value pair.\n            if key not in self:\n                root = self.__root\n                last = root[0]\n                last[1] = root[0] = self.__map[key] = [last, root, key]\n            dict_setitem(self, key, value)\n\n        def __delitem__(self, key, dict_delitem=dict.__delitem__):\n            'od.__delitem__(y) <==> del od[y]'\n            # Deleting an existing item uses self.__map to find the link which is\n            # then removed by updating the links in the predecessor and successor nodes.\n            dict_delitem(self, key)\n            link_prev, link_next, key = self.__map.pop(key)\n            link_prev[1] = link_next\n            link_next[0] = link_prev\n\n        def __iter__(self):\n            'od.__iter__() <==> iter(od)'\n            root = self.__root\n            curr = root[1]\n            while curr is not root:\n                yield curr[2]\n                curr = curr[1]\n\n        def __reversed__(self):\n            'od.__reversed__() <==> reversed(od)'\n            root = self.__root\n            curr = root[0]\n            while curr is not root:\n                yield curr[2]\n                curr = curr[0]\n\n        def clear(self):\n            'od.clear() -> None.  Remove all items from od.'\n            try:\n                for node in self.__map.itervalues():\n                    del node[:]\n                root = self.__root\n                root[:] = [root, root, None]\n                self.__map.clear()\n            except AttributeError:\n                pass\n            dict.clear(self)\n\n        def popitem(self, last=True):\n            '''od.popitem() -> (k, v), return and remove a (key, value) pair.\n            Pairs are returned in LIFO order if last is true or FIFO order if false.\n\n            '''\n            if not self:\n                raise KeyError('dictionary is empty')\n            root = self.__root\n            if last:\n                link = root[0]\n                link_prev = link[0]\n                link_prev[1] = root\n                root[0] = link_prev\n            else:\n                link = root[1]\n                link_next = link[1]\n                root[1] = link_next\n                link_next[0] = root\n            key = link[2]\n            del self.__map[key]\n            value = dict.pop(self, key)\n            return key, value\n\n        # -- the following methods do not depend on the internal structure --\n\n        def keys(self):\n            'od.keys() -> list of keys in od'\n            return list(self)\n\n        def values(self):\n            'od.values() -> list of values in od'\n            return [self[key] for key in self]\n\n        def items(self):\n            'od.items() -> list of (key, value) pairs in od'\n            return [(key, self[key]) for key in self]\n\n        def iterkeys(self):\n            'od.iterkeys() -> an iterator over the keys in od'\n            return iter(self)\n\n        def itervalues(self):\n            'od.itervalues -> an iterator over the values in od'\n            for k in self:\n                yield self[k]\n\n        def iteritems(self):\n            'od.iteritems -> an iterator over the (key, value) items in od'\n            for k in self:\n                yield (k, self[k])\n\n        def update(*args, **kwds):\n            '''od.update(E, **F) -> None.  Update od from dict/iterable E and F.\n\n            If E is a dict instance, does:           for k in E: od[k] = E[k]\n            If E has a .keys() method, does:         for k in E.keys(): od[k] = E[k]\n            Or if E is an iterable of items, does:   for k, v in E: od[k] = v\n            In either case, this is followed by:     for k, v in F.items(): od[k] = v\n\n            '''\n            if len(args) > 2:\n                raise TypeError('update() takes at most 2 positional '\n                                'arguments (%d given)' % (len(args),))\n            elif not args:\n                raise TypeError('update() takes at least 1 argument (0 given)')\n            self = args[0]\n            # Make progressively weaker assumptions about \"other\"\n            other = ()\n            if len(args) == 2:\n                other = args[1]\n            if isinstance(other, dict):\n                for key in other:\n                    self[key] = other[key]\n            elif hasattr(other, 'keys'):\n                for key in other.keys():\n                    self[key] = other[key]\n            else:\n                for key, value in other:\n                    self[key] = value\n            for key, value in kwds.items():\n                self[key] = value\n\n        __update = update  # let subclasses override update without breaking __init__\n\n        __marker = object()\n\n        def pop(self, key, default=__marker):\n            '''od.pop(k[,d]) -> v, remove specified key and return the corresponding value.\n            If key is not found, d is returned if given, otherwise KeyError is raised.\n\n            '''\n            if key in self:\n                result = self[key]\n                del self[key]\n                return result\n            if default is self.__marker:\n                raise KeyError(key)\n            return default\n\n        def setdefault(self, key, default=None):\n            'od.setdefault(k[,d]) -> od.get(k,d), also set od[k]=d if k not in od'\n            if key in self:\n                return self[key]\n            self[key] = default\n            return default\n\n        def __repr__(self, _repr_running=None):\n            'od.__repr__() <==> repr(od)'\n            if not _repr_running: _repr_running = {}\n            call_key = id(self), _get_ident()\n            if call_key in _repr_running:\n                return '...'\n            _repr_running[call_key] = 1\n            try:\n                if not self:\n                    return '%s()' % (self.__class__.__name__,)\n                return '%s(%r)' % (self.__class__.__name__, self.items())\n            finally:\n                del _repr_running[call_key]\n\n        def __reduce__(self):\n            'Return state information for pickling'\n            items = [[k, self[k]] for k in self]\n            inst_dict = vars(self).copy()\n            for k in vars(OrderedDict()):\n                inst_dict.pop(k, None)\n            if inst_dict:\n                return (self.__class__, (items,), inst_dict)\n            return self.__class__, (items,)\n\n        def copy(self):\n            'od.copy() -> a shallow copy of od'\n            return self.__class__(self)\n\n        @classmethod\n        def fromkeys(cls, iterable, value=None):\n            '''OD.fromkeys(S[, v]) -> New ordered dictionary with keys from S\n            and values equal to v (which defaults to None).\n\n            '''\n            d = cls()\n            for key in iterable:\n                d[key] = value\n            return d\n\n        def __eq__(self, other):\n            '''od.__eq__(y) <==> od==y.  Comparison to another OD is order-sensitive\n            while comparison to a regular mapping is order-insensitive.\n\n            '''\n            if isinstance(other, OrderedDict):\n                return len(self)==len(other) and self.items() == other.items()\n            return dict.__eq__(self, other)\n\n        def __ne__(self, other):\n            return not self == other\n\n        # -- the following methods are only used in Python 2.7 --\n\n        def viewkeys(self):\n            \"od.viewkeys() -> a set-like object providing a view on od's keys\"\n            return KeysView(self)\n\n        def viewvalues(self):\n            \"od.viewvalues() -> an object providing a view on od's values\"\n            return ValuesView(self)\n\n        def viewitems(self):\n            \"od.viewitems() -> a set-like object providing a view on od's items\"\n            return ItemsView(self)\n\ntry:\n    from logging.config import BaseConfigurator, valid_ident\nexcept ImportError: # pragma: no cover\n    IDENTIFIER = re.compile('^[a-z_][a-z0-9_]*$', re.I)\n\n\n    def valid_ident(s):\n        m = IDENTIFIER.match(s)\n        if not m:\n            raise ValueError('Not a valid Python identifier: %r' % s)\n        return True\n\n\n    # The ConvertingXXX classes are wrappers around standard Python containers,\n    # and they serve to convert any suitable values in the container. The\n    # conversion converts base dicts, lists and tuples to their wrapped\n    # equivalents, whereas strings which match a conversion format are converted\n    # appropriately.\n    #\n    # Each wrapper should have a configurator attribute holding the actual\n    # configurator to use for conversion.\n\n    class ConvertingDict(dict):\n        \"\"\"A converting dictionary wrapper.\"\"\"\n\n        def __getitem__(self, key):\n            value = dict.__getitem__(self, key)\n            result = self.configurator.convert(value)\n            #If the converted value is different, save for next time\n            if value is not result:\n                self[key] = result\n                if type(result) in (ConvertingDict, ConvertingList,\n                                    ConvertingTuple):\n                    result.parent = self\n                    result.key = key\n            return result\n\n        def get(self, key, default=None):\n            value = dict.get(self, key, default)\n            result = self.configurator.convert(value)\n            #If the converted value is different, save for next time\n            if value is not result:\n                self[key] = result\n                if type(result) in (ConvertingDict, ConvertingList,\n                                    ConvertingTuple):\n                    result.parent = self\n                    result.key = key\n            return result\n\n    def pop(self, key, default=None):\n        value = dict.pop(self, key, default)\n        result = self.configurator.convert(value)\n        if value is not result:\n            if type(result) in (ConvertingDict, ConvertingList,\n                                ConvertingTuple):\n                result.parent = self\n                result.key = key\n        return result\n\n    class ConvertingList(list):\n        \"\"\"A converting list wrapper.\"\"\"\n        def __getitem__(self, key):\n            value = list.__getitem__(self, key)\n            result = self.configurator.convert(value)\n            #If the converted value is different, save for next time\n            if value is not result:\n                self[key] = result\n                if type(result) in (ConvertingDict, ConvertingList,\n                                    ConvertingTuple):\n                    result.parent = self\n                    result.key = key\n            return result\n\n        def pop(self, idx=-1):\n            value = list.pop(self, idx)\n            result = self.configurator.convert(value)\n            if value is not result:\n                if type(result) in (ConvertingDict, ConvertingList,\n                                    ConvertingTuple):\n                    result.parent = self\n            return result\n\n    class ConvertingTuple(tuple):\n        \"\"\"A converting tuple wrapper.\"\"\"\n        def __getitem__(self, key):\n            value = tuple.__getitem__(self, key)\n            result = self.configurator.convert(value)\n            if value is not result:\n                if type(result) in (ConvertingDict, ConvertingList,\n                                    ConvertingTuple):\n                    result.parent = self\n                    result.key = key\n            return result\n\n    class BaseConfigurator(object):\n        \"\"\"\n        The configurator base class which defines some useful defaults.\n        \"\"\"\n\n        CONVERT_PATTERN = re.compile(r'^(?P<prefix>[a-z]+)://(?P<suffix>.*)$')\n\n        WORD_PATTERN = re.compile(r'^\\s*(\\w+)\\s*')\n        DOT_PATTERN = re.compile(r'^\\.\\s*(\\w+)\\s*')\n        INDEX_PATTERN = re.compile(r'^\\[\\s*(\\w+)\\s*\\]\\s*')\n        DIGIT_PATTERN = re.compile(r'^\\d+$')\n\n        value_converters = {\n            'ext' : 'ext_convert',\n            'cfg' : 'cfg_convert',\n        }\n\n        # We might want to use a different one, e.g. importlib\n        importer = staticmethod(__import__)\n\n        def __init__(self, config):\n            self.config = ConvertingDict(config)\n            self.config.configurator = self\n\n        def resolve(self, s):\n            \"\"\"\n            Resolve strings to objects using standard import and attribute\n            syntax.\n            \"\"\"\n            name = s.split('.')\n            used = name.pop(0)\n            try:\n                found = self.importer(used)\n                for frag in name:\n                    used += '.' + frag\n                    try:\n                        found = getattr(found, frag)\n                    except AttributeError:\n                        self.importer(used)\n                        found = getattr(found, frag)\n                return found\n            except ImportError:\n                e, tb = sys.exc_info()[1:]\n                v = ValueError('Cannot resolve %r: %s' % (s, e))\n                v.__cause__, v.__traceback__ = e, tb\n                raise v\n\n        def ext_convert(self, value):\n            \"\"\"Default converter for the ext:// protocol.\"\"\"\n            return self.resolve(value)\n\n        def cfg_convert(self, value):\n            \"\"\"Default converter for the cfg:// protocol.\"\"\"\n            rest = value\n            m = self.WORD_PATTERN.match(rest)\n            if m is None:\n                raise ValueError(\"Unable to convert %r\" % value)\n            else:\n                rest = rest[m.end():]\n                d = self.config[m.groups()[0]]\n                #print d, rest\n                while rest:\n                    m = self.DOT_PATTERN.match(rest)\n                    if m:\n                        d = d[m.groups()[0]]\n                    else:\n                        m = self.INDEX_PATTERN.match(rest)\n                        if m:\n                            idx = m.groups()[0]\n                            if not self.DIGIT_PATTERN.match(idx):\n                                d = d[idx]\n                            else:\n                                try:\n                                    n = int(idx) # try as number first (most likely)\n                                    d = d[n]\n                                except TypeError:\n                                    d = d[idx]\n                    if m:\n                        rest = rest[m.end():]\n                    else:\n                        raise ValueError('Unable to convert '\n                                         '%r at %r' % (value, rest))\n            #rest should be empty\n            return d\n\n        def convert(self, value):\n            \"\"\"\n            Convert values to an appropriate type. dicts, lists and tuples are\n            replaced by their converting alternatives. Strings are checked to\n            see if they have a conversion format and are converted if they do.\n            \"\"\"\n            if not isinstance(value, ConvertingDict) and isinstance(value, dict):\n                value = ConvertingDict(value)\n                value.configurator = self\n            elif not isinstance(value, ConvertingList) and isinstance(value, list):\n                value = ConvertingList(value)\n                value.configurator = self\n            elif not isinstance(value, ConvertingTuple) and\\\n                     isinstance(value, tuple):\n                value = ConvertingTuple(value)\n                value.configurator = self\n            elif isinstance(value, string_types):\n                m = self.CONVERT_PATTERN.match(value)\n                if m:\n                    d = m.groupdict()\n                    prefix = d['prefix']\n                    converter = self.value_converters.get(prefix, None)\n                    if converter:\n                        suffix = d['suffix']\n                        converter = getattr(self, converter)\n                        value = converter(suffix)\n            return value\n\n        def configure_custom(self, config):\n            \"\"\"Configure an object with a user-supplied factory.\"\"\"\n            c = config.pop('()')\n            if not callable(c):\n                c = self.resolve(c)\n            props = config.pop('.', None)\n            # Check for valid identifiers\n            kwargs = dict([(k, config[k]) for k in config if valid_ident(k)])\n            result = c(**kwargs)\n            if props:\n                for name, value in props.items():\n                    setattr(result, name, value)\n            return result\n\n        def as_tuple(self, value):\n            \"\"\"Utility function which converts lists to tuples.\"\"\"\n            if isinstance(value, list):\n                value = tuple(value)\n            return value\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/database.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2012-2017 The Python Software Foundation.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\n\"\"\"PEP 376 implementation.\"\"\"\n\nfrom __future__ import unicode_literals\n\nimport base64\nimport codecs\nimport contextlib\nimport hashlib\nimport logging\nimport os\nimport posixpath\nimport sys\nimport zipimport\n\nfrom . import DistlibException, resources\nfrom .compat import StringIO\nfrom .version import get_scheme, UnsupportedVersionError\nfrom .metadata import (Metadata, METADATA_FILENAME, WHEEL_METADATA_FILENAME,\n                       LEGACY_METADATA_FILENAME)\nfrom .util import (parse_requirement, cached_property, parse_name_and_version,\n                   read_exports, write_exports, CSVReader, CSVWriter)\n\n\n__all__ = ['Distribution', 'BaseInstalledDistribution',\n           'InstalledDistribution', 'EggInfoDistribution',\n           'DistributionPath']\n\n\nlogger = logging.getLogger(__name__)\n\nEXPORTS_FILENAME = 'pydist-exports.json'\nCOMMANDS_FILENAME = 'pydist-commands.json'\n\nDIST_FILES = ('INSTALLER', METADATA_FILENAME, 'RECORD', 'REQUESTED',\n              'RESOURCES', EXPORTS_FILENAME, 'SHARED')\n\nDISTINFO_EXT = '.dist-info'\n\n\nclass _Cache(object):\n    \"\"\"\n    A simple cache mapping names and .dist-info paths to distributions\n    \"\"\"\n    def __init__(self):\n        \"\"\"\n        Initialise an instance. There is normally one for each DistributionPath.\n        \"\"\"\n        self.name = {}\n        self.path = {}\n        self.generated = False\n\n    def clear(self):\n        \"\"\"\n        Clear the cache, setting it to its initial state.\n        \"\"\"\n        self.name.clear()\n        self.path.clear()\n        self.generated = False\n\n    def add(self, dist):\n        \"\"\"\n        Add a distribution to the cache.\n        :param dist: The distribution to add.\n        \"\"\"\n        if dist.path not in self.path:\n            self.path[dist.path] = dist\n            self.name.setdefault(dist.key, []).append(dist)\n\n\nclass DistributionPath(object):\n    \"\"\"\n    Represents a set of distributions installed on a path (typically sys.path).\n    \"\"\"\n    def __init__(self, path=None, include_egg=False):\n        \"\"\"\n        Create an instance from a path, optionally including legacy (distutils/\n        setuptools/distribute) distributions.\n        :param path: The path to use, as a list of directories. If not specified,\n                     sys.path is used.\n        :param include_egg: If True, this instance will look for and return legacy\n                            distributions as well as those based on PEP 376.\n        \"\"\"\n        if path is None:\n            path = sys.path\n        self.path = path\n        self._include_dist = True\n        self._include_egg = include_egg\n\n        self._cache = _Cache()\n        self._cache_egg = _Cache()\n        self._cache_enabled = True\n        self._scheme = get_scheme('default')\n\n    def _get_cache_enabled(self):\n        return self._cache_enabled\n\n    def _set_cache_enabled(self, value):\n        self._cache_enabled = value\n\n    cache_enabled = property(_get_cache_enabled, _set_cache_enabled)\n\n    def clear_cache(self):\n        \"\"\"\n        Clears the internal cache.\n        \"\"\"\n        self._cache.clear()\n        self._cache_egg.clear()\n\n\n    def _yield_distributions(self):\n        \"\"\"\n        Yield .dist-info and/or .egg(-info) distributions.\n        \"\"\"\n        # We need to check if we've seen some resources already, because on\n        # some Linux systems (e.g. some Debian/Ubuntu variants) there are\n        # symlinks which alias other files in the environment.\n        seen = set()\n        for path in self.path:\n            finder = resources.finder_for_path(path)\n            if finder is None:\n                continue\n            r = finder.find('')\n            if not r or not r.is_container:\n                continue\n            rset = sorted(r.resources)\n            for entry in rset:\n                r = finder.find(entry)\n                if not r or r.path in seen:\n                    continue\n                if self._include_dist and entry.endswith(DISTINFO_EXT):\n                    possible_filenames = [METADATA_FILENAME,\n                                          WHEEL_METADATA_FILENAME,\n                                          LEGACY_METADATA_FILENAME]\n                    for metadata_filename in possible_filenames:\n                        metadata_path = posixpath.join(entry, metadata_filename)\n                        pydist = finder.find(metadata_path)\n                        if pydist:\n                            break\n                    else:\n                        continue\n\n                    with contextlib.closing(pydist.as_stream()) as stream:\n                        metadata = Metadata(fileobj=stream, scheme='legacy')\n                    logger.debug('Found %s', r.path)\n                    seen.add(r.path)\n                    yield new_dist_class(r.path, metadata=metadata,\n                                         env=self)\n                elif self._include_egg and entry.endswith(('.egg-info',\n                                                          '.egg')):\n                    logger.debug('Found %s', r.path)\n                    seen.add(r.path)\n                    yield old_dist_class(r.path, self)\n\n    def _generate_cache(self):\n        \"\"\"\n        Scan the path for distributions and populate the cache with\n        those that are found.\n        \"\"\"\n        gen_dist = not self._cache.generated\n        gen_egg = self._include_egg and not self._cache_egg.generated\n        if gen_dist or gen_egg:\n            for dist in self._yield_distributions():\n                if isinstance(dist, InstalledDistribution):\n                    self._cache.add(dist)\n                else:\n                    self._cache_egg.add(dist)\n\n            if gen_dist:\n                self._cache.generated = True\n            if gen_egg:\n                self._cache_egg.generated = True\n\n    @classmethod\n    def distinfo_dirname(cls, name, version):\n        \"\"\"\n        The *name* and *version* parameters are converted into their\n        filename-escaped form, i.e. any ``'-'`` characters are replaced\n        with ``'_'`` other than the one in ``'dist-info'`` and the one\n        separating the name from the version number.\n\n        :parameter name: is converted to a standard distribution name by replacing\n                         any runs of non- alphanumeric characters with a single\n                         ``'-'``.\n        :type name: string\n        :parameter version: is converted to a standard version string. Spaces\n                            become dots, and all other non-alphanumeric characters\n                            (except dots) become dashes, with runs of multiple\n                            dashes condensed to a single dash.\n        :type version: string\n        :returns: directory name\n        :rtype: string\"\"\"\n        name = name.replace('-', '_')\n        return '-'.join([name, version]) + DISTINFO_EXT\n\n    def get_distributions(self):\n        \"\"\"\n        Provides an iterator that looks for distributions and returns\n        :class:`InstalledDistribution` or\n        :class:`EggInfoDistribution` instances for each one of them.\n\n        :rtype: iterator of :class:`InstalledDistribution` and\n                :class:`EggInfoDistribution` instances\n        \"\"\"\n        if not self._cache_enabled:\n            for dist in self._yield_distributions():\n                yield dist\n        else:\n            self._generate_cache()\n\n            for dist in self._cache.path.values():\n                yield dist\n\n            if self._include_egg:\n                for dist in self._cache_egg.path.values():\n                    yield dist\n\n    def get_distribution(self, name):\n        \"\"\"\n        Looks for a named distribution on the path.\n\n        This function only returns the first result found, as no more than one\n        value is expected. If nothing is found, ``None`` is returned.\n\n        :rtype: :class:`InstalledDistribution`, :class:`EggInfoDistribution`\n                or ``None``\n        \"\"\"\n        result = None\n        name = name.lower()\n        if not self._cache_enabled:\n            for dist in self._yield_distributions():\n                if dist.key == name:\n                    result = dist\n                    break\n        else:\n            self._generate_cache()\n\n            if name in self._cache.name:\n                result = self._cache.name[name][0]\n            elif self._include_egg and name in self._cache_egg.name:\n                result = self._cache_egg.name[name][0]\n        return result\n\n    def provides_distribution(self, name, version=None):\n        \"\"\"\n        Iterates over all distributions to find which distributions provide *name*.\n        If a *version* is provided, it will be used to filter the results.\n\n        This function only returns the first result found, since no more than\n        one values are expected. If the directory is not found, returns ``None``.\n\n        :parameter version: a version specifier that indicates the version\n                            required, conforming to the format in ``PEP-345``\n\n        :type name: string\n        :type version: string\n        \"\"\"\n        matcher = None\n        if version is not None:\n            try:\n                matcher = self._scheme.matcher('%s (%s)' % (name, version))\n            except ValueError:\n                raise DistlibException('invalid name or version: %r, %r' %\n                                      (name, version))\n\n        for dist in self.get_distributions():\n            # We hit a problem on Travis where enum34 was installed and doesn't\n            # have a provides attribute ...\n            if not hasattr(dist, 'provides'):\n                logger.debug('No \"provides\": %s', dist)\n            else:\n                provided = dist.provides\n\n                for p in provided:\n                    p_name, p_ver = parse_name_and_version(p)\n                    if matcher is None:\n                        if p_name == name:\n                            yield dist\n                            break\n                    else:\n                        if p_name == name and matcher.match(p_ver):\n                            yield dist\n                            break\n\n    def get_file_path(self, name, relative_path):\n        \"\"\"\n        Return the path to a resource file.\n        \"\"\"\n        dist = self.get_distribution(name)\n        if dist is None:\n            raise LookupError('no distribution named %r found' % name)\n        return dist.get_resource_path(relative_path)\n\n    def get_exported_entries(self, category, name=None):\n        \"\"\"\n        Return all of the exported entries in a particular category.\n\n        :param category: The category to search for entries.\n        :param name: If specified, only entries with that name are returned.\n        \"\"\"\n        for dist in self.get_distributions():\n            r = dist.exports\n            if category in r:\n                d = r[category]\n                if name is not None:\n                    if name in d:\n                        yield d[name]\n                else:\n                    for v in d.values():\n                        yield v\n\n\nclass Distribution(object):\n    \"\"\"\n    A base class for distributions, whether installed or from indexes.\n    Either way, it must have some metadata, so that's all that's needed\n    for construction.\n    \"\"\"\n\n    build_time_dependency = False\n    \"\"\"\n    Set to True if it's known to be only a build-time dependency (i.e.\n    not needed after installation).\n    \"\"\"\n\n    requested = False\n    \"\"\"A boolean that indicates whether the ``REQUESTED`` metadata file is\n    present (in other words, whether the package was installed by user\n    request or it was installed as a dependency).\"\"\"\n\n    def __init__(self, metadata):\n        \"\"\"\n        Initialise an instance.\n        :param metadata: The instance of :class:`Metadata` describing this\n        distribution.\n        \"\"\"\n        self.metadata = metadata\n        self.name = metadata.name\n        self.key = self.name.lower()    # for case-insensitive comparisons\n        self.version = metadata.version\n        self.locator = None\n        self.digest = None\n        self.extras = None      # additional features requested\n        self.context = None     # environment marker overrides\n        self.download_urls = set()\n        self.digests = {}\n\n    @property\n    def source_url(self):\n        \"\"\"\n        The source archive download URL for this distribution.\n        \"\"\"\n        return self.metadata.source_url\n\n    download_url = source_url   # Backward compatibility\n\n    @property\n    def name_and_version(self):\n        \"\"\"\n        A utility property which displays the name and version in parentheses.\n        \"\"\"\n        return '%s (%s)' % (self.name, self.version)\n\n    @property\n    def provides(self):\n        \"\"\"\n        A set of distribution names and versions provided by this distribution.\n        :return: A set of \"name (version)\" strings.\n        \"\"\"\n        plist = self.metadata.provides\n        s = '%s (%s)' % (self.name, self.version)\n        if s not in plist:\n            plist.append(s)\n        return plist\n\n    def _get_requirements(self, req_attr):\n        md = self.metadata\n        logger.debug('Getting requirements from metadata %r', md.todict())\n        reqts = getattr(md, req_attr)\n        return set(md.get_requirements(reqts, extras=self.extras,\n                                       env=self.context))\n\n    @property\n    def run_requires(self):\n        return self._get_requirements('run_requires')\n\n    @property\n    def meta_requires(self):\n        return self._get_requirements('meta_requires')\n\n    @property\n    def build_requires(self):\n        return self._get_requirements('build_requires')\n\n    @property\n    def test_requires(self):\n        return self._get_requirements('test_requires')\n\n    @property\n    def dev_requires(self):\n        return self._get_requirements('dev_requires')\n\n    def matches_requirement(self, req):\n        \"\"\"\n        Say if this instance matches (fulfills) a requirement.\n        :param req: The requirement to match.\n        :rtype req: str\n        :return: True if it matches, else False.\n        \"\"\"\n        # Requirement may contain extras - parse to lose those\n        # from what's passed to the matcher\n        r = parse_requirement(req)\n        scheme = get_scheme(self.metadata.scheme)\n        try:\n            matcher = scheme.matcher(r.requirement)\n        except UnsupportedVersionError:\n            # XXX compat-mode if cannot read the version\n            logger.warning('could not read version %r - using name only',\n                           req)\n            name = req.split()[0]\n            matcher = scheme.matcher(name)\n\n        name = matcher.key   # case-insensitive\n\n        result = False\n        for p in self.provides:\n            p_name, p_ver = parse_name_and_version(p)\n            if p_name != name:\n                continue\n            try:\n                result = matcher.match(p_ver)\n                break\n            except UnsupportedVersionError:\n                pass\n        return result\n\n    def __repr__(self):\n        \"\"\"\n        Return a textual representation of this instance,\n        \"\"\"\n        if self.source_url:\n            suffix = ' [%s]' % self.source_url\n        else:\n            suffix = ''\n        return '<Distribution %s (%s)%s>' % (self.name, self.version, suffix)\n\n    def __eq__(self, other):\n        \"\"\"\n        See if this distribution is the same as another.\n        :param other: The distribution to compare with. To be equal to one\n                      another. distributions must have the same type, name,\n                      version and source_url.\n        :return: True if it is the same, else False.\n        \"\"\"\n        if type(other) is not type(self):\n            result = False\n        else:\n            result = (self.name == other.name and\n                      self.version == other.version and\n                      self.source_url == other.source_url)\n        return result\n\n    def __hash__(self):\n        \"\"\"\n        Compute hash in a way which matches the equality test.\n        \"\"\"\n        return hash(self.name) + hash(self.version) + hash(self.source_url)\n\n\nclass BaseInstalledDistribution(Distribution):\n    \"\"\"\n    This is the base class for installed distributions (whether PEP 376 or\n    legacy).\n    \"\"\"\n\n    hasher = None\n\n    def __init__(self, metadata, path, env=None):\n        \"\"\"\n        Initialise an instance.\n        :param metadata: An instance of :class:`Metadata` which describes the\n                         distribution. This will normally have been initialised\n                         from a metadata file in the ``path``.\n        :param path:     The path of the ``.dist-info`` or ``.egg-info``\n                         directory for the distribution.\n        :param env:      This is normally the :class:`DistributionPath`\n                         instance where this distribution was found.\n        \"\"\"\n        super(BaseInstalledDistribution, self).__init__(metadata)\n        self.path = path\n        self.dist_path = env\n\n    def get_hash(self, data, hasher=None):\n        \"\"\"\n        Get the hash of some data, using a particular hash algorithm, if\n        specified.\n\n        :param data: The data to be hashed.\n        :type data: bytes\n        :param hasher: The name of a hash implementation, supported by hashlib,\n                       or ``None``. Examples of valid values are ``'sha1'``,\n                       ``'sha224'``, ``'sha384'``, '``sha256'``, ``'md5'`` and\n                       ``'sha512'``. If no hasher is specified, the ``hasher``\n                       attribute of the :class:`InstalledDistribution` instance\n                       is used. If the hasher is determined to be ``None``, MD5\n                       is used as the hashing algorithm.\n        :returns: The hash of the data. If a hasher was explicitly specified,\n                  the returned hash will be prefixed with the specified hasher\n                  followed by '='.\n        :rtype: str\n        \"\"\"\n        if hasher is None:\n            hasher = self.hasher\n        if hasher is None:\n            hasher = hashlib.md5\n            prefix = ''\n        else:\n            hasher = getattr(hashlib, hasher)\n            prefix = '%s=' % self.hasher\n        digest = hasher(data).digest()\n        digest = base64.urlsafe_b64encode(digest).rstrip(b'=').decode('ascii')\n        return '%s%s' % (prefix, digest)\n\n\nclass InstalledDistribution(BaseInstalledDistribution):\n    \"\"\"\n    Created with the *path* of the ``.dist-info`` directory provided to the\n    constructor. It reads the metadata contained in ``pydist.json`` when it is\n    instantiated., or uses a passed in Metadata instance (useful for when\n    dry-run mode is being used).\n    \"\"\"\n\n    hasher = 'sha256'\n\n    def __init__(self, path, metadata=None, env=None):\n        self.modules = []\n        self.finder = finder = resources.finder_for_path(path)\n        if finder is None:\n            raise ValueError('finder unavailable for %s' % path)\n        if env and env._cache_enabled and path in env._cache.path:\n            metadata = env._cache.path[path].metadata\n        elif metadata is None:\n            r = finder.find(METADATA_FILENAME)\n            # Temporary - for Wheel 0.23 support\n            if r is None:\n                r = finder.find(WHEEL_METADATA_FILENAME)\n            # Temporary - for legacy support\n            if r is None:\n                r = finder.find('METADATA')\n            if r is None:\n                raise ValueError('no %s found in %s' % (METADATA_FILENAME,\n                                                        path))\n            with contextlib.closing(r.as_stream()) as stream:\n                metadata = Metadata(fileobj=stream, scheme='legacy')\n\n        super(InstalledDistribution, self).__init__(metadata, path, env)\n\n        if env and env._cache_enabled:\n            env._cache.add(self)\n\n        r = finder.find('REQUESTED')\n        self.requested = r is not None\n        p  = os.path.join(path, 'top_level.txt')\n        if os.path.exists(p):\n            with open(p, 'rb') as f:\n                data = f.read()\n            self.modules = data.splitlines()\n\n    def __repr__(self):\n        return '<InstalledDistribution %r %s at %r>' % (\n            self.name, self.version, self.path)\n\n    def __str__(self):\n        return \"%s %s\" % (self.name, self.version)\n\n    def _get_records(self):\n        \"\"\"\n        Get the list of installed files for the distribution\n        :return: A list of tuples of path, hash and size. Note that hash and\n                 size might be ``None`` for some entries. The path is exactly\n                 as stored in the file (which is as in PEP 376).\n        \"\"\"\n        results = []\n        r = self.get_distinfo_resource('RECORD')\n        with contextlib.closing(r.as_stream()) as stream:\n            with CSVReader(stream=stream) as record_reader:\n                # Base location is parent dir of .dist-info dir\n                #base_location = os.path.dirname(self.path)\n                #base_location = os.path.abspath(base_location)\n                for row in record_reader:\n                    missing = [None for i in range(len(row), 3)]\n                    path, checksum, size = row + missing\n                    #if not os.path.isabs(path):\n                    #    path = path.replace('/', os.sep)\n                    #    path = os.path.join(base_location, path)\n                    results.append((path, checksum, size))\n        return results\n\n    @cached_property\n    def exports(self):\n        \"\"\"\n        Return the information exported by this distribution.\n        :return: A dictionary of exports, mapping an export category to a dict\n                 of :class:`ExportEntry` instances describing the individual\n                 export entries, and keyed by name.\n        \"\"\"\n        result = {}\n        r = self.get_distinfo_resource(EXPORTS_FILENAME)\n        if r:\n            result = self.read_exports()\n        return result\n\n    def read_exports(self):\n        \"\"\"\n        Read exports data from a file in .ini format.\n\n        :return: A dictionary of exports, mapping an export category to a list\n                 of :class:`ExportEntry` instances describing the individual\n                 export entries.\n        \"\"\"\n        result = {}\n        r = self.get_distinfo_resource(EXPORTS_FILENAME)\n        if r:\n            with contextlib.closing(r.as_stream()) as stream:\n                result = read_exports(stream)\n        return result\n\n    def write_exports(self, exports):\n        \"\"\"\n        Write a dictionary of exports to a file in .ini format.\n        :param exports: A dictionary of exports, mapping an export category to\n                        a list of :class:`ExportEntry` instances describing the\n                        individual export entries.\n        \"\"\"\n        rf = self.get_distinfo_file(EXPORTS_FILENAME)\n        with open(rf, 'w') as f:\n            write_exports(exports, f)\n\n    def get_resource_path(self, relative_path):\n        \"\"\"\n        NOTE: This API may change in the future.\n\n        Return the absolute path to a resource file with the given relative\n        path.\n\n        :param relative_path: The path, relative to .dist-info, of the resource\n                              of interest.\n        :return: The absolute path where the resource is to be found.\n        \"\"\"\n        r = self.get_distinfo_resource('RESOURCES')\n        with contextlib.closing(r.as_stream()) as stream:\n            with CSVReader(stream=stream) as resources_reader:\n                for relative, destination in resources_reader:\n                    if relative == relative_path:\n                        return destination\n        raise KeyError('no resource file with relative path %r '\n                       'is installed' % relative_path)\n\n    def list_installed_files(self):\n        \"\"\"\n        Iterates over the ``RECORD`` entries and returns a tuple\n        ``(path, hash, size)`` for each line.\n\n        :returns: iterator of (path, hash, size)\n        \"\"\"\n        for result in self._get_records():\n            yield result\n\n    def write_installed_files(self, paths, prefix, dry_run=False):\n        \"\"\"\n        Writes the ``RECORD`` file, using the ``paths`` iterable passed in. Any\n        existing ``RECORD`` file is silently overwritten.\n\n        prefix is used to determine when to write absolute paths.\n        \"\"\"\n        prefix = os.path.join(prefix, '')\n        base = os.path.dirname(self.path)\n        base_under_prefix = base.startswith(prefix)\n        base = os.path.join(base, '')\n        record_path = self.get_distinfo_file('RECORD')\n        logger.info('creating %s', record_path)\n        if dry_run:\n            return None\n        with CSVWriter(record_path) as writer:\n            for path in paths:\n                if os.path.isdir(path) or path.endswith(('.pyc', '.pyo')):\n                    # do not put size and hash, as in PEP-376\n                    hash_value = size = ''\n                else:\n                    size = '%d' % os.path.getsize(path)\n                    with open(path, 'rb') as fp:\n                        hash_value = self.get_hash(fp.read())\n                if path.startswith(base) or (base_under_prefix and\n                                             path.startswith(prefix)):\n                    path = os.path.relpath(path, base)\n                writer.writerow((path, hash_value, size))\n\n            # add the RECORD file itself\n            if record_path.startswith(base):\n                record_path = os.path.relpath(record_path, base)\n            writer.writerow((record_path, '', ''))\n        return record_path\n\n    def check_installed_files(self):\n        \"\"\"\n        Checks that the hashes and sizes of the files in ``RECORD`` are\n        matched by the files themselves. Returns a (possibly empty) list of\n        mismatches. Each entry in the mismatch list will be a tuple consisting\n        of the path, 'exists', 'size' or 'hash' according to what didn't match\n        (existence is checked first, then size, then hash), the expected\n        value and the actual value.\n        \"\"\"\n        mismatches = []\n        base = os.path.dirname(self.path)\n        record_path = self.get_distinfo_file('RECORD')\n        for path, hash_value, size in self.list_installed_files():\n            if not os.path.isabs(path):\n                path = os.path.join(base, path)\n            if path == record_path:\n                continue\n            if not os.path.exists(path):\n                mismatches.append((path, 'exists', True, False))\n            elif os.path.isfile(path):\n                actual_size = str(os.path.getsize(path))\n                if size and actual_size != size:\n                    mismatches.append((path, 'size', size, actual_size))\n                elif hash_value:\n                    if '=' in hash_value:\n                        hasher = hash_value.split('=', 1)[0]\n                    else:\n                        hasher = None\n\n                    with open(path, 'rb') as f:\n                        actual_hash = self.get_hash(f.read(), hasher)\n                        if actual_hash != hash_value:\n                            mismatches.append((path, 'hash', hash_value, actual_hash))\n        return mismatches\n\n    @cached_property\n    def shared_locations(self):\n        \"\"\"\n        A dictionary of shared locations whose keys are in the set 'prefix',\n        'purelib', 'platlib', 'scripts', 'headers', 'data' and 'namespace'.\n        The corresponding value is the absolute path of that category for\n        this distribution, and takes into account any paths selected by the\n        user at installation time (e.g. via command-line arguments). In the\n        case of the 'namespace' key, this would be a list of absolute paths\n        for the roots of namespace packages in this distribution.\n\n        The first time this property is accessed, the relevant information is\n        read from the SHARED file in the .dist-info directory.\n        \"\"\"\n        result = {}\n        shared_path = os.path.join(self.path, 'SHARED')\n        if os.path.isfile(shared_path):\n            with codecs.open(shared_path, 'r', encoding='utf-8') as f:\n                lines = f.read().splitlines()\n            for line in lines:\n                key, value = line.split('=', 1)\n                if key == 'namespace':\n                    result.setdefault(key, []).append(value)\n                else:\n                    result[key] = value\n        return result\n\n    def write_shared_locations(self, paths, dry_run=False):\n        \"\"\"\n        Write shared location information to the SHARED file in .dist-info.\n        :param paths: A dictionary as described in the documentation for\n        :meth:`shared_locations`.\n        :param dry_run: If True, the action is logged but no file is actually\n                        written.\n        :return: The path of the file written to.\n        \"\"\"\n        shared_path = os.path.join(self.path, 'SHARED')\n        logger.info('creating %s', shared_path)\n        if dry_run:\n            return None\n        lines = []\n        for key in ('prefix', 'lib', 'headers', 'scripts', 'data'):\n            path = paths[key]\n            if os.path.isdir(paths[key]):\n                lines.append('%s=%s' % (key,  path))\n        for ns in paths.get('namespace', ()):\n            lines.append('namespace=%s' % ns)\n\n        with codecs.open(shared_path, 'w', encoding='utf-8') as f:\n            f.write('\\n'.join(lines))\n        return shared_path\n\n    def get_distinfo_resource(self, path):\n        if path not in DIST_FILES:\n            raise DistlibException('invalid path for a dist-info file: '\n                                   '%r at %r' % (path, self.path))\n        finder = resources.finder_for_path(self.path)\n        if finder is None:\n            raise DistlibException('Unable to get a finder for %s' % self.path)\n        return finder.find(path)\n\n    def get_distinfo_file(self, path):\n        \"\"\"\n        Returns a path located under the ``.dist-info`` directory. Returns a\n        string representing the path.\n\n        :parameter path: a ``'/'``-separated path relative to the\n                         ``.dist-info`` directory or an absolute path;\n                         If *path* is an absolute path and doesn't start\n                         with the ``.dist-info`` directory path,\n                         a :class:`DistlibException` is raised\n        :type path: str\n        :rtype: str\n        \"\"\"\n        # Check if it is an absolute path  # XXX use relpath, add tests\n        if path.find(os.sep) >= 0:\n            # it's an absolute path?\n            distinfo_dirname, path = path.split(os.sep)[-2:]\n            if distinfo_dirname != self.path.split(os.sep)[-1]:\n                raise DistlibException(\n                    'dist-info file %r does not belong to the %r %s '\n                    'distribution' % (path, self.name, self.version))\n\n        # The file must be relative\n        if path not in DIST_FILES:\n            raise DistlibException('invalid path for a dist-info file: '\n                                   '%r at %r' % (path, self.path))\n\n        return os.path.join(self.path, path)\n\n    def list_distinfo_files(self):\n        \"\"\"\n        Iterates over the ``RECORD`` entries and returns paths for each line if\n        the path is pointing to a file located in the ``.dist-info`` directory\n        or one of its subdirectories.\n\n        :returns: iterator of paths\n        \"\"\"\n        base = os.path.dirname(self.path)\n        for path, checksum, size in self._get_records():\n            # XXX add separator or use real relpath algo\n            if not os.path.isabs(path):\n                path = os.path.join(base, path)\n            if path.startswith(self.path):\n                yield path\n\n    def __eq__(self, other):\n        return (isinstance(other, InstalledDistribution) and\n                self.path == other.path)\n\n    # See http://docs.python.org/reference/datamodel#object.__hash__\n    __hash__ = object.__hash__\n\n\nclass EggInfoDistribution(BaseInstalledDistribution):\n    \"\"\"Created with the *path* of the ``.egg-info`` directory or file provided\n    to the constructor. It reads the metadata contained in the file itself, or\n    if the given path happens to be a directory, the metadata is read from the\n    file ``PKG-INFO`` under that directory.\"\"\"\n\n    requested = True    # as we have no way of knowing, assume it was\n    shared_locations = {}\n\n    def __init__(self, path, env=None):\n        def set_name_and_version(s, n, v):\n            s.name = n\n            s.key = n.lower()   # for case-insensitive comparisons\n            s.version = v\n\n        self.path = path\n        self.dist_path = env\n        if env and env._cache_enabled and path in env._cache_egg.path:\n            metadata = env._cache_egg.path[path].metadata\n            set_name_and_version(self, metadata.name, metadata.version)\n        else:\n            metadata = self._get_metadata(path)\n\n            # Need to be set before caching\n            set_name_and_version(self, metadata.name, metadata.version)\n\n            if env and env._cache_enabled:\n                env._cache_egg.add(self)\n        super(EggInfoDistribution, self).__init__(metadata, path, env)\n\n    def _get_metadata(self, path):\n        requires = None\n\n        def parse_requires_data(data):\n            \"\"\"Create a list of dependencies from a requires.txt file.\n\n            *data*: the contents of a setuptools-produced requires.txt file.\n            \"\"\"\n            reqs = []\n            lines = data.splitlines()\n            for line in lines:\n                line = line.strip()\n                if line.startswith('['):\n                    logger.warning('Unexpected line: quitting requirement scan: %r',\n                                   line)\n                    break\n                r = parse_requirement(line)\n                if not r:\n                    logger.warning('Not recognised as a requirement: %r', line)\n                    continue\n                if r.extras:\n                    logger.warning('extra requirements in requires.txt are '\n                                   'not supported')\n                if not r.constraints:\n                    reqs.append(r.name)\n                else:\n                    cons = ', '.join('%s%s' % c for c in r.constraints)\n                    reqs.append('%s (%s)' % (r.name, cons))\n            return reqs\n\n        def parse_requires_path(req_path):\n            \"\"\"Create a list of dependencies from a requires.txt file.\n\n            *req_path*: the path to a setuptools-produced requires.txt file.\n            \"\"\"\n\n            reqs = []\n            try:\n                with codecs.open(req_path, 'r', 'utf-8') as fp:\n                    reqs = parse_requires_data(fp.read())\n            except IOError:\n                pass\n            return reqs\n\n        tl_path = tl_data = None\n        if path.endswith('.egg'):\n            if os.path.isdir(path):\n                p = os.path.join(path, 'EGG-INFO')\n                meta_path = os.path.join(p, 'PKG-INFO')\n                metadata = Metadata(path=meta_path, scheme='legacy')\n                req_path = os.path.join(p, 'requires.txt')\n                tl_path = os.path.join(p, 'top_level.txt')\n                requires = parse_requires_path(req_path)\n            else:\n                # FIXME handle the case where zipfile is not available\n                zipf = zipimport.zipimporter(path)\n                fileobj = StringIO(\n                    zipf.get_data('EGG-INFO/PKG-INFO').decode('utf8'))\n                metadata = Metadata(fileobj=fileobj, scheme='legacy')\n                try:\n                    data = zipf.get_data('EGG-INFO/requires.txt')\n                    tl_data = zipf.get_data('EGG-INFO/top_level.txt').decode('utf-8')\n                    requires = parse_requires_data(data.decode('utf-8'))\n                except IOError:\n                    requires = None\n        elif path.endswith('.egg-info'):\n            if os.path.isdir(path):\n                req_path = os.path.join(path, 'requires.txt')\n                requires = parse_requires_path(req_path)\n                path = os.path.join(path, 'PKG-INFO')\n                tl_path = os.path.join(path, 'top_level.txt')\n            metadata = Metadata(path=path, scheme='legacy')\n        else:\n            raise DistlibException('path must end with .egg-info or .egg, '\n                                   'got %r' % path)\n\n        if requires:\n            metadata.add_requirements(requires)\n        # look for top-level modules in top_level.txt, if present\n        if tl_data is None:\n            if tl_path is not None and os.path.exists(tl_path):\n                with open(tl_path, 'rb') as f:\n                    tl_data = f.read().decode('utf-8')\n        if not tl_data:\n            tl_data = []\n        else:\n            tl_data = tl_data.splitlines()\n        self.modules = tl_data\n        return metadata\n\n    def __repr__(self):\n        return '<EggInfoDistribution %r %s at %r>' % (\n            self.name, self.version, self.path)\n\n    def __str__(self):\n        return \"%s %s\" % (self.name, self.version)\n\n    def check_installed_files(self):\n        \"\"\"\n        Checks that the hashes and sizes of the files in ``RECORD`` are\n        matched by the files themselves. Returns a (possibly empty) list of\n        mismatches. Each entry in the mismatch list will be a tuple consisting\n        of the path, 'exists', 'size' or 'hash' according to what didn't match\n        (existence is checked first, then size, then hash), the expected\n        value and the actual value.\n        \"\"\"\n        mismatches = []\n        record_path = os.path.join(self.path, 'installed-files.txt')\n        if os.path.exists(record_path):\n            for path, _, _ in self.list_installed_files():\n                if path == record_path:\n                    continue\n                if not os.path.exists(path):\n                    mismatches.append((path, 'exists', True, False))\n        return mismatches\n\n    def list_installed_files(self):\n        \"\"\"\n        Iterates over the ``installed-files.txt`` entries and returns a tuple\n        ``(path, hash, size)`` for each line.\n\n        :returns: a list of (path, hash, size)\n        \"\"\"\n\n        def _md5(path):\n            f = open(path, 'rb')\n            try:\n                content = f.read()\n            finally:\n                f.close()\n            return hashlib.md5(content).hexdigest()\n\n        def _size(path):\n            return os.stat(path).st_size\n\n        record_path = os.path.join(self.path, 'installed-files.txt')\n        result = []\n        if os.path.exists(record_path):\n            with codecs.open(record_path, 'r', encoding='utf-8') as f:\n                for line in f:\n                    line = line.strip()\n                    p = os.path.normpath(os.path.join(self.path, line))\n                    # \"./\" is present as a marker between installed files\n                    # and installation metadata files\n                    if not os.path.exists(p):\n                        logger.warning('Non-existent file: %s', p)\n                        if p.endswith(('.pyc', '.pyo')):\n                            continue\n                        #otherwise fall through and fail\n                    if not os.path.isdir(p):\n                        result.append((p, _md5(p), _size(p)))\n            result.append((record_path, None, None))\n        return result\n\n    def list_distinfo_files(self, absolute=False):\n        \"\"\"\n        Iterates over the ``installed-files.txt`` entries and returns paths for\n        each line if the path is pointing to a file located in the\n        ``.egg-info`` directory or one of its subdirectories.\n\n        :parameter absolute: If *absolute* is ``True``, each returned path is\n                          transformed into a local absolute path. Otherwise the\n                          raw value from ``installed-files.txt`` is returned.\n        :type absolute: boolean\n        :returns: iterator of paths\n        \"\"\"\n        record_path = os.path.join(self.path, 'installed-files.txt')\n        if os.path.exists(record_path):\n            skip = True\n            with codecs.open(record_path, 'r', encoding='utf-8') as f:\n                for line in f:\n                    line = line.strip()\n                    if line == './':\n                        skip = False\n                        continue\n                    if not skip:\n                        p = os.path.normpath(os.path.join(self.path, line))\n                        if p.startswith(self.path):\n                            if absolute:\n                                yield p\n                            else:\n                                yield line\n\n    def __eq__(self, other):\n        return (isinstance(other, EggInfoDistribution) and\n                self.path == other.path)\n\n    # See http://docs.python.org/reference/datamodel#object.__hash__\n    __hash__ = object.__hash__\n\nnew_dist_class = InstalledDistribution\nold_dist_class = EggInfoDistribution\n\n\nclass DependencyGraph(object):\n    \"\"\"\n    Represents a dependency graph between distributions.\n\n    The dependency relationships are stored in an ``adjacency_list`` that maps\n    distributions to a list of ``(other, label)`` tuples where  ``other``\n    is a distribution and the edge is labeled with ``label`` (i.e. the version\n    specifier, if such was provided). Also, for more efficient traversal, for\n    every distribution ``x``, a list of predecessors is kept in\n    ``reverse_list[x]``. An edge from distribution ``a`` to\n    distribution ``b`` means that ``a`` depends on ``b``. If any missing\n    dependencies are found, they are stored in ``missing``, which is a\n    dictionary that maps distributions to a list of requirements that were not\n    provided by any other distributions.\n    \"\"\"\n\n    def __init__(self):\n        self.adjacency_list = {}\n        self.reverse_list = {}\n        self.missing = {}\n\n    def add_distribution(self, distribution):\n        \"\"\"Add the *distribution* to the graph.\n\n        :type distribution: :class:`distutils2.database.InstalledDistribution`\n                            or :class:`distutils2.database.EggInfoDistribution`\n        \"\"\"\n        self.adjacency_list[distribution] = []\n        self.reverse_list[distribution] = []\n        #self.missing[distribution] = []\n\n    def add_edge(self, x, y, label=None):\n        \"\"\"Add an edge from distribution *x* to distribution *y* with the given\n        *label*.\n\n        :type x: :class:`distutils2.database.InstalledDistribution` or\n                 :class:`distutils2.database.EggInfoDistribution`\n        :type y: :class:`distutils2.database.InstalledDistribution` or\n                 :class:`distutils2.database.EggInfoDistribution`\n        :type label: ``str`` or ``None``\n        \"\"\"\n        self.adjacency_list[x].append((y, label))\n        # multiple edges are allowed, so be careful\n        if x not in self.reverse_list[y]:\n            self.reverse_list[y].append(x)\n\n    def add_missing(self, distribution, requirement):\n        \"\"\"\n        Add a missing *requirement* for the given *distribution*.\n\n        :type distribution: :class:`distutils2.database.InstalledDistribution`\n                            or :class:`distutils2.database.EggInfoDistribution`\n        :type requirement: ``str``\n        \"\"\"\n        logger.debug('%s missing %r', distribution, requirement)\n        self.missing.setdefault(distribution, []).append(requirement)\n\n    def _repr_dist(self, dist):\n        return '%s %s' % (dist.name, dist.version)\n\n    def repr_node(self, dist, level=1):\n        \"\"\"Prints only a subgraph\"\"\"\n        output = [self._repr_dist(dist)]\n        for other, label in self.adjacency_list[dist]:\n            dist = self._repr_dist(other)\n            if label is not None:\n                dist = '%s [%s]' % (dist, label)\n            output.append('    ' * level + str(dist))\n            suboutput = self.repr_node(other, level + 1)\n            subs = suboutput.split('\\n')\n            output.extend(subs[1:])\n        return '\\n'.join(output)\n\n    def to_dot(self, f, skip_disconnected=True):\n        \"\"\"Writes a DOT output for the graph to the provided file *f*.\n\n        If *skip_disconnected* is set to ``True``, then all distributions\n        that are not dependent on any other distribution are skipped.\n\n        :type f: has to support ``file``-like operations\n        :type skip_disconnected: ``bool``\n        \"\"\"\n        disconnected = []\n\n        f.write(\"digraph dependencies {\\n\")\n        for dist, adjs in self.adjacency_list.items():\n            if len(adjs) == 0 and not skip_disconnected:\n                disconnected.append(dist)\n            for other, label in adjs:\n                if not label is None:\n                    f.write('\"%s\" -> \"%s\" [label=\"%s\"]\\n' %\n                            (dist.name, other.name, label))\n                else:\n                    f.write('\"%s\" -> \"%s\"\\n' % (dist.name, other.name))\n        if not skip_disconnected and len(disconnected) > 0:\n            f.write('subgraph disconnected {\\n')\n            f.write('label = \"Disconnected\"\\n')\n            f.write('bgcolor = red\\n')\n\n            for dist in disconnected:\n                f.write('\"%s\"' % dist.name)\n                f.write('\\n')\n            f.write('}\\n')\n        f.write('}\\n')\n\n    def topological_sort(self):\n        \"\"\"\n        Perform a topological sort of the graph.\n        :return: A tuple, the first element of which is a topologically sorted\n                 list of distributions, and the second element of which is a\n                 list of distributions that cannot be sorted because they have\n                 circular dependencies and so form a cycle.\n        \"\"\"\n        result = []\n        # Make a shallow copy of the adjacency list\n        alist = {}\n        for k, v in self.adjacency_list.items():\n            alist[k] = v[:]\n        while True:\n            # See what we can remove in this run\n            to_remove = []\n            for k, v in list(alist.items())[:]:\n                if not v:\n                    to_remove.append(k)\n                    del alist[k]\n            if not to_remove:\n                # What's left in alist (if anything) is a cycle.\n                break\n            # Remove from the adjacency list of others\n            for k, v in alist.items():\n                alist[k] = [(d, r) for d, r in v if d not in to_remove]\n            logger.debug('Moving to result: %s',\n                         ['%s (%s)' % (d.name, d.version) for d in to_remove])\n            result.extend(to_remove)\n        return result, list(alist.keys())\n\n    def __repr__(self):\n        \"\"\"Representation of the graph\"\"\"\n        output = []\n        for dist, adjs in self.adjacency_list.items():\n            output.append(self.repr_node(dist))\n        return '\\n'.join(output)\n\n\ndef make_graph(dists, scheme='default'):\n    \"\"\"Makes a dependency graph from the given distributions.\n\n    :parameter dists: a list of distributions\n    :type dists: list of :class:`distutils2.database.InstalledDistribution` and\n                 :class:`distutils2.database.EggInfoDistribution` instances\n    :rtype: a :class:`DependencyGraph` instance\n    \"\"\"\n    scheme = get_scheme(scheme)\n    graph = DependencyGraph()\n    provided = {}  # maps names to lists of (version, dist) tuples\n\n    # first, build the graph and find out what's provided\n    for dist in dists:\n        graph.add_distribution(dist)\n\n        for p in dist.provides:\n            name, version = parse_name_and_version(p)\n            logger.debug('Add to provided: %s, %s, %s', name, version, dist)\n            provided.setdefault(name, []).append((version, dist))\n\n    # now make the edges\n    for dist in dists:\n        requires = (dist.run_requires | dist.meta_requires |\n                    dist.build_requires | dist.dev_requires)\n        for req in requires:\n            try:\n                matcher = scheme.matcher(req)\n            except UnsupportedVersionError:\n                # XXX compat-mode if cannot read the version\n                logger.warning('could not read version %r - using name only',\n                               req)\n                name = req.split()[0]\n                matcher = scheme.matcher(name)\n\n            name = matcher.key   # case-insensitive\n\n            matched = False\n            if name in provided:\n                for version, provider in provided[name]:\n                    try:\n                        match = matcher.match(version)\n                    except UnsupportedVersionError:\n                        match = False\n\n                    if match:\n                        graph.add_edge(dist, provider, req)\n                        matched = True\n                        break\n            if not matched:\n                graph.add_missing(dist, req)\n    return graph\n\n\ndef get_dependent_dists(dists, dist):\n    \"\"\"Recursively generate a list of distributions from *dists* that are\n    dependent on *dist*.\n\n    :param dists: a list of distributions\n    :param dist: a distribution, member of *dists* for which we are interested\n    \"\"\"\n    if dist not in dists:\n        raise DistlibException('given distribution %r is not a member '\n                               'of the list' % dist.name)\n    graph = make_graph(dists)\n\n    dep = [dist]  # dependent distributions\n    todo = graph.reverse_list[dist]  # list of nodes we should inspect\n\n    while todo:\n        d = todo.pop()\n        dep.append(d)\n        for succ in graph.reverse_list[d]:\n            if succ not in dep:\n                todo.append(succ)\n\n    dep.pop(0)  # remove dist from dep, was there to prevent infinite loops\n    return dep\n\n\ndef get_required_dists(dists, dist):\n    \"\"\"Recursively generate a list of distributions from *dists* that are\n    required by *dist*.\n\n    :param dists: a list of distributions\n    :param dist: a distribution, member of *dists* for which we are interested\n    \"\"\"\n    if dist not in dists:\n        raise DistlibException('given distribution %r is not a member '\n                               'of the list' % dist.name)\n    graph = make_graph(dists)\n\n    req = []  # required distributions\n    todo = graph.adjacency_list[dist]  # list of nodes we should inspect\n\n    while todo:\n        d = todo.pop()[0]\n        req.append(d)\n        for pred in graph.adjacency_list[d]:\n            if pred not in req:\n                todo.append(pred)\n\n    return req\n\n\ndef make_dist(name, version, **kwargs):\n    \"\"\"\n    A convenience method for making a dist given just a name and version.\n    \"\"\"\n    summary = kwargs.pop('summary', 'Placeholder for summary')\n    md = Metadata(**kwargs)\n    md.name = name\n    md.version = version\n    md.summary = summary or 'Placeholder for summary'\n    return Distribution(md)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/index.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2013 Vinay Sajip.\n# Licensed to the Python Software Foundation under a contributor agreement.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\nimport hashlib\nimport logging\nimport os\nimport shutil\nimport subprocess\nimport tempfile\ntry:\n    from threading import Thread\nexcept ImportError:\n    from dummy_threading import Thread\n\nfrom . import DistlibException\nfrom .compat import (HTTPBasicAuthHandler, Request, HTTPPasswordMgr,\n                     urlparse, build_opener, string_types)\nfrom .util import cached_property, zip_dir, ServerProxy\n\nlogger = logging.getLogger(__name__)\n\nDEFAULT_INDEX = 'https://pypi.python.org/pypi'\nDEFAULT_REALM = 'pypi'\n\nclass PackageIndex(object):\n    \"\"\"\n    This class represents a package index compatible with PyPI, the Python\n    Package Index.\n    \"\"\"\n\n    boundary = b'----------ThIs_Is_tHe_distlib_index_bouNdaRY_$'\n\n    def __init__(self, url=None):\n        \"\"\"\n        Initialise an instance.\n\n        :param url: The URL of the index. If not specified, the URL for PyPI is\n                    used.\n        \"\"\"\n        self.url = url or DEFAULT_INDEX\n        self.read_configuration()\n        scheme, netloc, path, params, query, frag = urlparse(self.url)\n        if params or query or frag or scheme not in ('http', 'https'):\n            raise DistlibException('invalid repository: %s' % self.url)\n        self.password_handler = None\n        self.ssl_verifier = None\n        self.gpg = None\n        self.gpg_home = None\n        with open(os.devnull, 'w') as sink:\n            # Use gpg by default rather than gpg2, as gpg2 insists on\n            # prompting for passwords\n            for s in ('gpg', 'gpg2'):\n                try:\n                    rc = subprocess.check_call([s, '--version'], stdout=sink,\n                                               stderr=sink)\n                    if rc == 0:\n                        self.gpg = s\n                        break\n                except OSError:\n                    pass\n\n    def _get_pypirc_command(self):\n        \"\"\"\n        Get the distutils command for interacting with PyPI configurations.\n        :return: the command.\n        \"\"\"\n        from distutils.core import Distribution\n        from distutils.config import PyPIRCCommand\n        d = Distribution()\n        return PyPIRCCommand(d)\n\n    def read_configuration(self):\n        \"\"\"\n        Read the PyPI access configuration as supported by distutils, getting\n        PyPI to do the actual work. This populates ``username``, ``password``,\n        ``realm`` and ``url`` attributes from the configuration.\n        \"\"\"\n        # get distutils to do the work\n        c = self._get_pypirc_command()\n        c.repository = self.url\n        cfg = c._read_pypirc()\n        self.username = cfg.get('username')\n        self.password = cfg.get('password')\n        self.realm = cfg.get('realm', 'pypi')\n        self.url = cfg.get('repository', self.url)\n\n    def save_configuration(self):\n        \"\"\"\n        Save the PyPI access configuration. You must have set ``username`` and\n        ``password`` attributes before calling this method.\n\n        Again, distutils is used to do the actual work.\n        \"\"\"\n        self.check_credentials()\n        # get distutils to do the work\n        c = self._get_pypirc_command()\n        c._store_pypirc(self.username, self.password)\n\n    def check_credentials(self):\n        \"\"\"\n        Check that ``username`` and ``password`` have been set, and raise an\n        exception if not.\n        \"\"\"\n        if self.username is None or self.password is None:\n            raise DistlibException('username and password must be set')\n        pm = HTTPPasswordMgr()\n        _, netloc, _, _, _, _ = urlparse(self.url)\n        pm.add_password(self.realm, netloc, self.username, self.password)\n        self.password_handler = HTTPBasicAuthHandler(pm)\n\n    def register(self, metadata):\n        \"\"\"\n        Register a distribution on PyPI, using the provided metadata.\n\n        :param metadata: A :class:`Metadata` instance defining at least a name\n                         and version number for the distribution to be\n                         registered.\n        :return: The HTTP response received from PyPI upon submission of the\n                request.\n        \"\"\"\n        self.check_credentials()\n        metadata.validate()\n        d = metadata.todict()\n        d[':action'] = 'verify'\n        request = self.encode_request(d.items(), [])\n        response = self.send_request(request)\n        d[':action'] = 'submit'\n        request = self.encode_request(d.items(), [])\n        return self.send_request(request)\n\n    def _reader(self, name, stream, outbuf):\n        \"\"\"\n        Thread runner for reading lines of from a subprocess into a buffer.\n\n        :param name: The logical name of the stream (used for logging only).\n        :param stream: The stream to read from. This will typically a pipe\n                       connected to the output stream of a subprocess.\n        :param outbuf: The list to append the read lines to.\n        \"\"\"\n        while True:\n            s = stream.readline()\n            if not s:\n                break\n            s = s.decode('utf-8').rstrip()\n            outbuf.append(s)\n            logger.debug('%s: %s' % (name, s))\n        stream.close()\n\n    def get_sign_command(self, filename, signer, sign_password,\n                         keystore=None):\n        \"\"\"\n        Return a suitable command for signing a file.\n\n        :param filename: The pathname to the file to be signed.\n        :param signer: The identifier of the signer of the file.\n        :param sign_password: The passphrase for the signer's\n                              private key used for signing.\n        :param keystore: The path to a directory which contains the keys\n                         used in verification. If not specified, the\n                         instance's ``gpg_home`` attribute is used instead.\n        :return: The signing command as a list suitable to be\n                 passed to :class:`subprocess.Popen`.\n        \"\"\"\n        cmd = [self.gpg, '--status-fd', '2', '--no-tty']\n        if keystore is None:\n            keystore = self.gpg_home\n        if keystore:\n            cmd.extend(['--homedir', keystore])\n        if sign_password is not None:\n            cmd.extend(['--batch', '--passphrase-fd', '0'])\n        td = tempfile.mkdtemp()\n        sf = os.path.join(td, os.path.basename(filename) + '.asc')\n        cmd.extend(['--detach-sign', '--armor', '--local-user',\n                    signer, '--output', sf, filename])\n        logger.debug('invoking: %s', ' '.join(cmd))\n        return cmd, sf\n\n    def run_command(self, cmd, input_data=None):\n        \"\"\"\n        Run a command in a child process , passing it any input data specified.\n\n        :param cmd: The command to run.\n        :param input_data: If specified, this must be a byte string containing\n                           data to be sent to the child process.\n        :return: A tuple consisting of the subprocess' exit code, a list of\n                 lines read from the subprocess' ``stdout``, and a list of\n                 lines read from the subprocess' ``stderr``.\n        \"\"\"\n        kwargs = {\n            'stdout': subprocess.PIPE,\n            'stderr': subprocess.PIPE,\n        }\n        if input_data is not None:\n            kwargs['stdin'] = subprocess.PIPE\n        stdout = []\n        stderr = []\n        p = subprocess.Popen(cmd, **kwargs)\n        # We don't use communicate() here because we may need to\n        # get clever with interacting with the command\n        t1 = Thread(target=self._reader, args=('stdout', p.stdout, stdout))\n        t1.start()\n        t2 = Thread(target=self._reader, args=('stderr', p.stderr, stderr))\n        t2.start()\n        if input_data is not None:\n            p.stdin.write(input_data)\n            p.stdin.close()\n\n        p.wait()\n        t1.join()\n        t2.join()\n        return p.returncode, stdout, stderr\n\n    def sign_file(self, filename, signer, sign_password, keystore=None):\n        \"\"\"\n        Sign a file.\n\n        :param filename: The pathname to the file to be signed.\n        :param signer: The identifier of the signer of the file.\n        :param sign_password: The passphrase for the signer's\n                              private key used for signing.\n        :param keystore: The path to a directory which contains the keys\n                         used in signing. If not specified, the instance's\n                         ``gpg_home`` attribute is used instead.\n        :return: The absolute pathname of the file where the signature is\n                 stored.\n        \"\"\"\n        cmd, sig_file = self.get_sign_command(filename, signer, sign_password,\n                                              keystore)\n        rc, stdout, stderr = self.run_command(cmd,\n                                              sign_password.encode('utf-8'))\n        if rc != 0:\n            raise DistlibException('sign command failed with error '\n                                   'code %s' % rc)\n        return sig_file\n\n    def upload_file(self, metadata, filename, signer=None, sign_password=None,\n                    filetype='sdist', pyversion='source', keystore=None):\n        \"\"\"\n        Upload a release file to the index.\n\n        :param metadata: A :class:`Metadata` instance defining at least a name\n                         and version number for the file to be uploaded.\n        :param filename: The pathname of the file to be uploaded.\n        :param signer: The identifier of the signer of the file.\n        :param sign_password: The passphrase for the signer's\n                              private key used for signing.\n        :param filetype: The type of the file being uploaded. This is the\n                        distutils command which produced that file, e.g.\n                        ``sdist`` or ``bdist_wheel``.\n        :param pyversion: The version of Python which the release relates\n                          to. For code compatible with any Python, this would\n                          be ``source``, otherwise it would be e.g. ``3.2``.\n        :param keystore: The path to a directory which contains the keys\n                         used in signing. If not specified, the instance's\n                         ``gpg_home`` attribute is used instead.\n        :return: The HTTP response received from PyPI upon submission of the\n                request.\n        \"\"\"\n        self.check_credentials()\n        if not os.path.exists(filename):\n            raise DistlibException('not found: %s' % filename)\n        metadata.validate()\n        d = metadata.todict()\n        sig_file = None\n        if signer:\n            if not self.gpg:\n                logger.warning('no signing program available - not signed')\n            else:\n                sig_file = self.sign_file(filename, signer, sign_password,\n                                          keystore)\n        with open(filename, 'rb') as f:\n            file_data = f.read()\n        md5_digest = hashlib.md5(file_data).hexdigest()\n        sha256_digest = hashlib.sha256(file_data).hexdigest()\n        d.update({\n            ':action': 'file_upload',\n            'protocol_version': '1',\n            'filetype': filetype,\n            'pyversion': pyversion,\n            'md5_digest': md5_digest,\n            'sha256_digest': sha256_digest,\n        })\n        files = [('content', os.path.basename(filename), file_data)]\n        if sig_file:\n            with open(sig_file, 'rb') as f:\n                sig_data = f.read()\n            files.append(('gpg_signature', os.path.basename(sig_file),\n                         sig_data))\n            shutil.rmtree(os.path.dirname(sig_file))\n        request = self.encode_request(d.items(), files)\n        return self.send_request(request)\n\n    def upload_documentation(self, metadata, doc_dir):\n        \"\"\"\n        Upload documentation to the index.\n\n        :param metadata: A :class:`Metadata` instance defining at least a name\n                         and version number for the documentation to be\n                         uploaded.\n        :param doc_dir: The pathname of the directory which contains the\n                        documentation. This should be the directory that\n                        contains the ``index.html`` for the documentation.\n        :return: The HTTP response received from PyPI upon submission of the\n                request.\n        \"\"\"\n        self.check_credentials()\n        if not os.path.isdir(doc_dir):\n            raise DistlibException('not a directory: %r' % doc_dir)\n        fn = os.path.join(doc_dir, 'index.html')\n        if not os.path.exists(fn):\n            raise DistlibException('not found: %r' % fn)\n        metadata.validate()\n        name, version = metadata.name, metadata.version\n        zip_data = zip_dir(doc_dir).getvalue()\n        fields = [(':action', 'doc_upload'),\n                  ('name', name), ('version', version)]\n        files = [('content', name, zip_data)]\n        request = self.encode_request(fields, files)\n        return self.send_request(request)\n\n    def get_verify_command(self, signature_filename, data_filename,\n                           keystore=None):\n        \"\"\"\n        Return a suitable command for verifying a file.\n\n        :param signature_filename: The pathname to the file containing the\n                                   signature.\n        :param data_filename: The pathname to the file containing the\n                              signed data.\n        :param keystore: The path to a directory which contains the keys\n                         used in verification. If not specified, the\n                         instance's ``gpg_home`` attribute is used instead.\n        :return: The verifying command as a list suitable to be\n                 passed to :class:`subprocess.Popen`.\n        \"\"\"\n        cmd = [self.gpg, '--status-fd', '2', '--no-tty']\n        if keystore is None:\n            keystore = self.gpg_home\n        if keystore:\n            cmd.extend(['--homedir', keystore])\n        cmd.extend(['--verify', signature_filename, data_filename])\n        logger.debug('invoking: %s', ' '.join(cmd))\n        return cmd\n\n    def verify_signature(self, signature_filename, data_filename,\n                         keystore=None):\n        \"\"\"\n        Verify a signature for a file.\n\n        :param signature_filename: The pathname to the file containing the\n                                   signature.\n        :param data_filename: The pathname to the file containing the\n                              signed data.\n        :param keystore: The path to a directory which contains the keys\n                         used in verification. If not specified, the\n                         instance's ``gpg_home`` attribute is used instead.\n        :return: True if the signature was verified, else False.\n        \"\"\"\n        if not self.gpg:\n            raise DistlibException('verification unavailable because gpg '\n                                   'unavailable')\n        cmd = self.get_verify_command(signature_filename, data_filename,\n                                      keystore)\n        rc, stdout, stderr = self.run_command(cmd)\n        if rc not in (0, 1):\n            raise DistlibException('verify command failed with error '\n                             'code %s' % rc)\n        return rc == 0\n\n    def download_file(self, url, destfile, digest=None, reporthook=None):\n        \"\"\"\n        This is a convenience method for downloading a file from an URL.\n        Normally, this will be a file from the index, though currently\n        no check is made for this (i.e. a file can be downloaded from\n        anywhere).\n\n        The method is just like the :func:`urlretrieve` function in the\n        standard library, except that it allows digest computation to be\n        done during download and checking that the downloaded data\n        matched any expected value.\n\n        :param url: The URL of the file to be downloaded (assumed to be\n                    available via an HTTP GET request).\n        :param destfile: The pathname where the downloaded file is to be\n                         saved.\n        :param digest: If specified, this must be a (hasher, value)\n                       tuple, where hasher is the algorithm used (e.g.\n                       ``'md5'``) and ``value`` is the expected value.\n        :param reporthook: The same as for :func:`urlretrieve` in the\n                           standard library.\n        \"\"\"\n        if digest is None:\n            digester = None\n            logger.debug('No digest specified')\n        else:\n            if isinstance(digest, (list, tuple)):\n                hasher, digest = digest\n            else:\n                hasher = 'md5'\n            digester = getattr(hashlib, hasher)()\n            logger.debug('Digest specified: %s' % digest)\n        # The following code is equivalent to urlretrieve.\n        # We need to do it this way so that we can compute the\n        # digest of the file as we go.\n        with open(destfile, 'wb') as dfp:\n            # addinfourl is not a context manager on 2.x\n            # so we have to use try/finally\n            sfp = self.send_request(Request(url))\n            try:\n                headers = sfp.info()\n                blocksize = 8192\n                size = -1\n                read = 0\n                blocknum = 0\n                if \"content-length\" in headers:\n                    size = int(headers[\"Content-Length\"])\n                if reporthook:\n                    reporthook(blocknum, blocksize, size)\n                while True:\n                    block = sfp.read(blocksize)\n                    if not block:\n                        break\n                    read += len(block)\n                    dfp.write(block)\n                    if digester:\n                        digester.update(block)\n                    blocknum += 1\n                    if reporthook:\n                        reporthook(blocknum, blocksize, size)\n            finally:\n                sfp.close()\n\n        # check that we got the whole file, if we can\n        if size >= 0 and read < size:\n            raise DistlibException(\n                'retrieval incomplete: got only %d out of %d bytes'\n                % (read, size))\n        # if we have a digest, it must match.\n        if digester:\n            actual = digester.hexdigest()\n            if digest != actual:\n                raise DistlibException('%s digest mismatch for %s: expected '\n                                       '%s, got %s' % (hasher, destfile,\n                                                       digest, actual))\n            logger.debug('Digest verified: %s', digest)\n\n    def send_request(self, req):\n        \"\"\"\n        Send a standard library :class:`Request` to PyPI and return its\n        response.\n\n        :param req: The request to send.\n        :return: The HTTP response from PyPI (a standard library HTTPResponse).\n        \"\"\"\n        handlers = []\n        if self.password_handler:\n            handlers.append(self.password_handler)\n        if self.ssl_verifier:\n            handlers.append(self.ssl_verifier)\n        opener = build_opener(*handlers)\n        return opener.open(req)\n\n    def encode_request(self, fields, files):\n        \"\"\"\n        Encode fields and files for posting to an HTTP server.\n\n        :param fields: The fields to send as a list of (fieldname, value)\n                       tuples.\n        :param files: The files to send as a list of (fieldname, filename,\n                      file_bytes) tuple.\n        \"\"\"\n        # Adapted from packaging, which in turn was adapted from\n        # http://code.activestate.com/recipes/146306\n\n        parts = []\n        boundary = self.boundary\n        for k, values in fields:\n            if not isinstance(values, (list, tuple)):\n                values = [values]\n\n            for v in values:\n                parts.extend((\n                    b'--' + boundary,\n                    ('Content-Disposition: form-data; name=\"%s\"' %\n                     k).encode('utf-8'),\n                    b'',\n                    v.encode('utf-8')))\n        for key, filename, value in files:\n            parts.extend((\n                b'--' + boundary,\n                ('Content-Disposition: form-data; name=\"%s\"; filename=\"%s\"' %\n                 (key, filename)).encode('utf-8'),\n                b'',\n                value))\n\n        parts.extend((b'--' + boundary + b'--', b''))\n\n        body = b'\\r\\n'.join(parts)\n        ct = b'multipart/form-data; boundary=' + boundary\n        headers = {\n            'Content-type': ct,\n            'Content-length': str(len(body))\n        }\n        return Request(self.url, body, headers)\n\n    def search(self, terms, operator=None):\n        if isinstance(terms, string_types):\n            terms = {'name': terms}\n        rpc_proxy = ServerProxy(self.url, timeout=3.0)\n        try:\n            return rpc_proxy.search(terms, operator or 'and')\n        finally:\n            rpc_proxy('close')()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/locators.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2012-2015 Vinay Sajip.\n# Licensed to the Python Software Foundation under a contributor agreement.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\n\nimport gzip\nfrom io import BytesIO\nimport json\nimport logging\nimport os\nimport posixpath\nimport re\ntry:\n    import threading\nexcept ImportError:  # pragma: no cover\n    import dummy_threading as threading\nimport zlib\n\nfrom . import DistlibException\nfrom .compat import (urljoin, urlparse, urlunparse, url2pathname, pathname2url,\n                     queue, quote, unescape, string_types, build_opener,\n                     HTTPRedirectHandler as BaseRedirectHandler, text_type,\n                     Request, HTTPError, URLError)\nfrom .database import Distribution, DistributionPath, make_dist\nfrom .metadata import Metadata, MetadataInvalidError\nfrom .util import (cached_property, parse_credentials, ensure_slash,\n                   split_filename, get_project_data, parse_requirement,\n                   parse_name_and_version, ServerProxy, normalize_name)\nfrom .version import get_scheme, UnsupportedVersionError\nfrom .wheel import Wheel, is_compatible\n\nlogger = logging.getLogger(__name__)\n\nHASHER_HASH = re.compile(r'^(\\w+)=([a-f0-9]+)')\nCHARSET = re.compile(r';\\s*charset\\s*=\\s*(.*)\\s*$', re.I)\nHTML_CONTENT_TYPE = re.compile('text/html|application/x(ht)?ml')\nDEFAULT_INDEX = 'https://pypi.python.org/pypi'\n\ndef get_all_distribution_names(url=None):\n    \"\"\"\n    Return all distribution names known by an index.\n    :param url: The URL of the index.\n    :return: A list of all known distribution names.\n    \"\"\"\n    if url is None:\n        url = DEFAULT_INDEX\n    client = ServerProxy(url, timeout=3.0)\n    try:\n        return client.list_packages()\n    finally:\n        client('close')()\n\nclass RedirectHandler(BaseRedirectHandler):\n    \"\"\"\n    A class to work around a bug in some Python 3.2.x releases.\n    \"\"\"\n    # There's a bug in the base version for some 3.2.x\n    # (e.g. 3.2.2 on Ubuntu Oneiric). If a Location header\n    # returns e.g. /abc, it bails because it says the scheme ''\n    # is bogus, when actually it should use the request's\n    # URL for the scheme. See Python issue #13696.\n    def http_error_302(self, req, fp, code, msg, headers):\n        # Some servers (incorrectly) return multiple Location headers\n        # (so probably same goes for URI).  Use first header.\n        newurl = None\n        for key in ('location', 'uri'):\n            if key in headers:\n                newurl = headers[key]\n                break\n        if newurl is None:  # pragma: no cover\n            return\n        urlparts = urlparse(newurl)\n        if urlparts.scheme == '':\n            newurl = urljoin(req.get_full_url(), newurl)\n            if hasattr(headers, 'replace_header'):\n                headers.replace_header(key, newurl)\n            else:\n                headers[key] = newurl\n        return BaseRedirectHandler.http_error_302(self, req, fp, code, msg,\n                                                  headers)\n\n    http_error_301 = http_error_303 = http_error_307 = http_error_302\n\nclass Locator(object):\n    \"\"\"\n    A base class for locators - things that locate distributions.\n    \"\"\"\n    source_extensions = ('.tar.gz', '.tar.bz2', '.tar', '.zip', '.tgz', '.tbz')\n    binary_extensions = ('.egg', '.exe', '.whl')\n    excluded_extensions = ('.pdf',)\n\n    # A list of tags indicating which wheels you want to match. The default\n    # value of None matches against the tags compatible with the running\n    # Python. If you want to match other values, set wheel_tags on a locator\n    # instance to a list of tuples (pyver, abi, arch) which you want to match.\n    wheel_tags = None\n\n    downloadable_extensions = source_extensions + ('.whl',)\n\n    def __init__(self, scheme='default'):\n        \"\"\"\n        Initialise an instance.\n        :param scheme: Because locators look for most recent versions, they\n                       need to know the version scheme to use. This specifies\n                       the current PEP-recommended scheme - use ``'legacy'``\n                       if you need to support existing distributions on PyPI.\n        \"\"\"\n        self._cache = {}\n        self.scheme = scheme\n        # Because of bugs in some of the handlers on some of the platforms,\n        # we use our own opener rather than just using urlopen.\n        self.opener = build_opener(RedirectHandler())\n        # If get_project() is called from locate(), the matcher instance\n        # is set from the requirement passed to locate(). See issue #18 for\n        # why this can be useful to know.\n        self.matcher = None\n        self.errors = queue.Queue()\n\n    def get_errors(self):\n        \"\"\"\n        Return any errors which have occurred.\n        \"\"\"\n        result = []\n        while not self.errors.empty():  # pragma: no cover\n            try:\n                e = self.errors.get(False)\n                result.append(e)\n            except self.errors.Empty:\n                continue\n            self.errors.task_done()\n        return result\n\n    def clear_errors(self):\n        \"\"\"\n        Clear any errors which may have been logged.\n        \"\"\"\n        # Just get the errors and throw them away\n        self.get_errors()\n\n    def clear_cache(self):\n        self._cache.clear()\n\n    def _get_scheme(self):\n        return self._scheme\n\n    def _set_scheme(self, value):\n        self._scheme = value\n\n    scheme = property(_get_scheme, _set_scheme)\n\n    def _get_project(self, name):\n        \"\"\"\n        For a given project, get a dictionary mapping available versions to Distribution\n        instances.\n\n        This should be implemented in subclasses.\n\n        If called from a locate() request, self.matcher will be set to a\n        matcher for the requirement to satisfy, otherwise it will be None.\n        \"\"\"\n        raise NotImplementedError('Please implement in the subclass')\n\n    def get_distribution_names(self):\n        \"\"\"\n        Return all the distribution names known to this locator.\n        \"\"\"\n        raise NotImplementedError('Please implement in the subclass')\n\n    def get_project(self, name):\n        \"\"\"\n        For a given project, get a dictionary mapping available versions to Distribution\n        instances.\n\n        This calls _get_project to do all the work, and just implements a caching layer on top.\n        \"\"\"\n        if self._cache is None:  # pragma: no cover\n            result = self._get_project(name)\n        elif name in self._cache:\n            result = self._cache[name]\n        else:\n            self.clear_errors()\n            result = self._get_project(name)\n            self._cache[name] = result\n        return result\n\n    def score_url(self, url):\n        \"\"\"\n        Give an url a score which can be used to choose preferred URLs\n        for a given project release.\n        \"\"\"\n        t = urlparse(url)\n        basename = posixpath.basename(t.path)\n        compatible = True\n        is_wheel = basename.endswith('.whl')\n        is_downloadable = basename.endswith(self.downloadable_extensions)\n        if is_wheel:\n            compatible = is_compatible(Wheel(basename), self.wheel_tags)\n        return (t.scheme == 'https', 'pypi.python.org' in t.netloc,\n                is_downloadable, is_wheel, compatible, basename)\n\n    def prefer_url(self, url1, url2):\n        \"\"\"\n        Choose one of two URLs where both are candidates for distribution\n        archives for the same version of a distribution (for example,\n        .tar.gz vs. zip).\n\n        The current implementation favours https:// URLs over http://, archives\n        from PyPI over those from other locations, wheel compatibility (if a\n        wheel) and then the archive name.\n        \"\"\"\n        result = url2\n        if url1:\n            s1 = self.score_url(url1)\n            s2 = self.score_url(url2)\n            if s1 > s2:\n                result = url1\n            if result != url2:\n                logger.debug('Not replacing %r with %r', url1, url2)\n            else:\n                logger.debug('Replacing %r with %r', url1, url2)\n        return result\n\n    def split_filename(self, filename, project_name):\n        \"\"\"\n        Attempt to split a filename in project name, version and Python version.\n        \"\"\"\n        return split_filename(filename, project_name)\n\n    def convert_url_to_download_info(self, url, project_name):\n        \"\"\"\n        See if a URL is a candidate for a download URL for a project (the URL\n        has typically been scraped from an HTML page).\n\n        If it is, a dictionary is returned with keys \"name\", \"version\",\n        \"filename\" and \"url\"; otherwise, None is returned.\n        \"\"\"\n        def same_project(name1, name2):\n            return normalize_name(name1) == normalize_name(name2)\n\n        result = None\n        scheme, netloc, path, params, query, frag = urlparse(url)\n        if frag.lower().startswith('egg='):  # pragma: no cover\n            logger.debug('%s: version hint in fragment: %r',\n                         project_name, frag)\n        m = HASHER_HASH.match(frag)\n        if m:\n            algo, digest = m.groups()\n        else:\n            algo, digest = None, None\n        origpath = path\n        if path and path[-1] == '/':  # pragma: no cover\n            path = path[:-1]\n        if path.endswith('.whl'):\n            try:\n                wheel = Wheel(path)\n                if not is_compatible(wheel, self.wheel_tags):\n                    logger.debug('Wheel not compatible: %s', path)\n                else:\n                    if project_name is None:\n                        include = True\n                    else:\n                        include = same_project(wheel.name, project_name)\n                    if include:\n                        result = {\n                            'name': wheel.name,\n                            'version': wheel.version,\n                            'filename': wheel.filename,\n                            'url': urlunparse((scheme, netloc, origpath,\n                                               params, query, '')),\n                            'python-version': ', '.join(\n                                ['.'.join(list(v[2:])) for v in wheel.pyver]),\n                        }\n            except Exception as e:  # pragma: no cover\n                logger.warning('invalid path for wheel: %s', path)\n        elif not path.endswith(self.downloadable_extensions):  # pragma: no cover\n            logger.debug('Not downloadable: %s', path)\n        else:  # downloadable extension\n            path = filename = posixpath.basename(path)\n            for ext in self.downloadable_extensions:\n                if path.endswith(ext):\n                    path = path[:-len(ext)]\n                    t = self.split_filename(path, project_name)\n                    if not t:  # pragma: no cover\n                        logger.debug('No match for project/version: %s', path)\n                    else:\n                        name, version, pyver = t\n                        if not project_name or same_project(project_name, name):\n                            result = {\n                                'name': name,\n                                'version': version,\n                                'filename': filename,\n                                'url': urlunparse((scheme, netloc, origpath,\n                                                   params, query, '')),\n                                #'packagetype': 'sdist',\n                            }\n                            if pyver:  # pragma: no cover\n                                result['python-version'] = pyver\n                    break\n        if result and algo:\n            result['%s_digest' % algo] = digest\n        return result\n\n    def _get_digest(self, info):\n        \"\"\"\n        Get a digest from a dictionary by looking at keys of the form\n        'algo_digest'.\n\n        Returns a 2-tuple (algo, digest) if found, else None. Currently\n        looks only for SHA256, then MD5.\n        \"\"\"\n        result = None\n        for algo in ('sha256', 'md5'):\n            key = '%s_digest' % algo\n            if key in info:\n                result = (algo, info[key])\n                break\n        return result\n\n    def _update_version_data(self, result, info):\n        \"\"\"\n        Update a result dictionary (the final result from _get_project) with a\n        dictionary for a specific version, which typically holds information\n        gleaned from a filename or URL for an archive for the distribution.\n        \"\"\"\n        name = info.pop('name')\n        version = info.pop('version')\n        if version in result:\n            dist = result[version]\n            md = dist.metadata\n        else:\n            dist = make_dist(name, version, scheme=self.scheme)\n            md = dist.metadata\n        dist.digest = digest = self._get_digest(info)\n        url = info['url']\n        result['digests'][url] = digest\n        if md.source_url != info['url']:\n            md.source_url = self.prefer_url(md.source_url, url)\n            result['urls'].setdefault(version, set()).add(url)\n        dist.locator = self\n        result[version] = dist\n\n    def locate(self, requirement, prereleases=False):\n        \"\"\"\n        Find the most recent distribution which matches the given\n        requirement.\n\n        :param requirement: A requirement of the form 'foo (1.0)' or perhaps\n                            'foo (>= 1.0, < 2.0, != 1.3)'\n        :param prereleases: If ``True``, allow pre-release versions\n                            to be located. Otherwise, pre-release versions\n                            are not returned.\n        :return: A :class:`Distribution` instance, or ``None`` if no such\n                 distribution could be located.\n        \"\"\"\n        result = None\n        r = parse_requirement(requirement)\n        if r is None:  # pragma: no cover\n            raise DistlibException('Not a valid requirement: %r' % requirement)\n        scheme = get_scheme(self.scheme)\n        self.matcher = matcher = scheme.matcher(r.requirement)\n        logger.debug('matcher: %s (%s)', matcher, type(matcher).__name__)\n        versions = self.get_project(r.name)\n        if len(versions) > 2:   # urls and digests keys are present\n            # sometimes, versions are invalid\n            slist = []\n            vcls = matcher.version_class\n            for k in versions:\n                if k in ('urls', 'digests'):\n                    continue\n                try:\n                    if not matcher.match(k):\n                        logger.debug('%s did not match %r', matcher, k)\n                    else:\n                        if prereleases or not vcls(k).is_prerelease:\n                            slist.append(k)\n                        else:\n                            logger.debug('skipping pre-release '\n                                         'version %s of %s', k, matcher.name)\n                except Exception:  # pragma: no cover\n                    logger.warning('error matching %s with %r', matcher, k)\n                    pass # slist.append(k)\n            if len(slist) > 1:\n                slist = sorted(slist, key=scheme.key)\n            if slist:\n                logger.debug('sorted list: %s', slist)\n                version = slist[-1]\n                result = versions[version]\n        if result:\n            if r.extras:\n                result.extras = r.extras\n            result.download_urls = versions.get('urls', {}).get(version, set())\n            d = {}\n            sd = versions.get('digests', {})\n            for url in result.download_urls:\n                if url in sd:  # pragma: no cover\n                    d[url] = sd[url]\n            result.digests = d\n        self.matcher = None\n        return result\n\n\nclass PyPIRPCLocator(Locator):\n    \"\"\"\n    This locator uses XML-RPC to locate distributions. It therefore\n    cannot be used with simple mirrors (that only mirror file content).\n    \"\"\"\n    def __init__(self, url, **kwargs):\n        \"\"\"\n        Initialise an instance.\n\n        :param url: The URL to use for XML-RPC.\n        :param kwargs: Passed to the superclass constructor.\n        \"\"\"\n        super(PyPIRPCLocator, self).__init__(**kwargs)\n        self.base_url = url\n        self.client = ServerProxy(url, timeout=3.0)\n\n    def get_distribution_names(self):\n        \"\"\"\n        Return all the distribution names known to this locator.\n        \"\"\"\n        return set(self.client.list_packages())\n\n    def _get_project(self, name):\n        result = {'urls': {}, 'digests': {}}\n        versions = self.client.package_releases(name, True)\n        for v in versions:\n            urls = self.client.release_urls(name, v)\n            data = self.client.release_data(name, v)\n            metadata = Metadata(scheme=self.scheme)\n            metadata.name = data['name']\n            metadata.version = data['version']\n            metadata.license = data.get('license')\n            metadata.keywords = data.get('keywords', [])\n            metadata.summary = data.get('summary')\n            dist = Distribution(metadata)\n            if urls:\n                info = urls[0]\n                metadata.source_url = info['url']\n                dist.digest = self._get_digest(info)\n                dist.locator = self\n                result[v] = dist\n                for info in urls:\n                    url = info['url']\n                    digest = self._get_digest(info)\n                    result['urls'].setdefault(v, set()).add(url)\n                    result['digests'][url] = digest\n        return result\n\nclass PyPIJSONLocator(Locator):\n    \"\"\"\n    This locator uses PyPI's JSON interface. It's very limited in functionality\n    and probably not worth using.\n    \"\"\"\n    def __init__(self, url, **kwargs):\n        super(PyPIJSONLocator, self).__init__(**kwargs)\n        self.base_url = ensure_slash(url)\n\n    def get_distribution_names(self):\n        \"\"\"\n        Return all the distribution names known to this locator.\n        \"\"\"\n        raise NotImplementedError('Not available from this locator')\n\n    def _get_project(self, name):\n        result = {'urls': {}, 'digests': {}}\n        url = urljoin(self.base_url, '%s/json' % quote(name))\n        try:\n            resp = self.opener.open(url)\n            data = resp.read().decode() # for now\n            d = json.loads(data)\n            md = Metadata(scheme=self.scheme)\n            data = d['info']\n            md.name = data['name']\n            md.version = data['version']\n            md.license = data.get('license')\n            md.keywords = data.get('keywords', [])\n            md.summary = data.get('summary')\n            dist = Distribution(md)\n            dist.locator = self\n            urls = d['urls']\n            result[md.version] = dist\n            for info in d['urls']:\n                url = info['url']\n                dist.download_urls.add(url)\n                dist.digests[url] = self._get_digest(info)\n                result['urls'].setdefault(md.version, set()).add(url)\n                result['digests'][url] = self._get_digest(info)\n            # Now get other releases\n            for version, infos in d['releases'].items():\n                if version == md.version:\n                    continue    # already done\n                omd = Metadata(scheme=self.scheme)\n                omd.name = md.name\n                omd.version = version\n                odist = Distribution(omd)\n                odist.locator = self\n                result[version] = odist\n                for info in infos:\n                    url = info['url']\n                    odist.download_urls.add(url)\n                    odist.digests[url] = self._get_digest(info)\n                    result['urls'].setdefault(version, set()).add(url)\n                    result['digests'][url] = self._get_digest(info)\n#            for info in urls:\n#                md.source_url = info['url']\n#                dist.digest = self._get_digest(info)\n#                dist.locator = self\n#                for info in urls:\n#                    url = info['url']\n#                    result['urls'].setdefault(md.version, set()).add(url)\n#                    result['digests'][url] = self._get_digest(info)\n        except Exception as e:\n            self.errors.put(text_type(e))\n            logger.exception('JSON fetch failed: %s', e)\n        return result\n\n\nclass Page(object):\n    \"\"\"\n    This class represents a scraped HTML page.\n    \"\"\"\n    # The following slightly hairy-looking regex just looks for the contents of\n    # an anchor link, which has an attribute \"href\" either immediately preceded\n    # or immediately followed by a \"rel\" attribute. The attribute values can be\n    # declared with double quotes, single quotes or no quotes - which leads to\n    # the length of the expression.\n    _href = re.compile(\"\"\"\n(rel\\\\s*=\\\\s*(?:\"(?P<rel1>[^\"]*)\"|'(?P<rel2>[^']*)'|(?P<rel3>[^>\\\\s\\n]*))\\\\s+)?\nhref\\\\s*=\\\\s*(?:\"(?P<url1>[^\"]*)\"|'(?P<url2>[^']*)'|(?P<url3>[^>\\\\s\\n]*))\n(\\\\s+rel\\\\s*=\\\\s*(?:\"(?P<rel4>[^\"]*)\"|'(?P<rel5>[^']*)'|(?P<rel6>[^>\\\\s\\n]*)))?\n\"\"\", re.I | re.S | re.X)\n    _base = re.compile(r\"\"\"<base\\s+href\\s*=\\s*['\"]?([^'\">]+)\"\"\", re.I | re.S)\n\n    def __init__(self, data, url):\n        \"\"\"\n        Initialise an instance with the Unicode page contents and the URL they\n        came from.\n        \"\"\"\n        self.data = data\n        self.base_url = self.url = url\n        m = self._base.search(self.data)\n        if m:\n            self.base_url = m.group(1)\n\n    _clean_re = re.compile(r'[^a-z0-9$&+,/:;=?@.#%_\\\\|-]', re.I)\n\n    @cached_property\n    def links(self):\n        \"\"\"\n        Return the URLs of all the links on a page together with information\n        about their \"rel\" attribute, for determining which ones to treat as\n        downloads and which ones to queue for further scraping.\n        \"\"\"\n        def clean(url):\n            \"Tidy up an URL.\"\n            scheme, netloc, path, params, query, frag = urlparse(url)\n            return urlunparse((scheme, netloc, quote(path),\n                               params, query, frag))\n\n        result = set()\n        for match in self._href.finditer(self.data):\n            d = match.groupdict('')\n            rel = (d['rel1'] or d['rel2'] or d['rel3'] or\n                   d['rel4'] or d['rel5'] or d['rel6'])\n            url = d['url1'] or d['url2'] or d['url3']\n            url = urljoin(self.base_url, url)\n            url = unescape(url)\n            url = self._clean_re.sub(lambda m: '%%%2x' % ord(m.group(0)), url)\n            result.add((url, rel))\n        # We sort the result, hoping to bring the most recent versions\n        # to the front\n        result = sorted(result, key=lambda t: t[0], reverse=True)\n        return result\n\n\nclass SimpleScrapingLocator(Locator):\n    \"\"\"\n    A locator which scrapes HTML pages to locate downloads for a distribution.\n    This runs multiple threads to do the I/O; performance is at least as good\n    as pip's PackageFinder, which works in an analogous fashion.\n    \"\"\"\n\n    # These are used to deal with various Content-Encoding schemes.\n    decoders = {\n        'deflate': zlib.decompress,\n        'gzip': lambda b: gzip.GzipFile(fileobj=BytesIO(d)).read(),\n        'none': lambda b: b,\n    }\n\n    def __init__(self, url, timeout=None, num_workers=10, **kwargs):\n        \"\"\"\n        Initialise an instance.\n        :param url: The root URL to use for scraping.\n        :param timeout: The timeout, in seconds, to be applied to requests.\n                        This defaults to ``None`` (no timeout specified).\n        :param num_workers: The number of worker threads you want to do I/O,\n                            This defaults to 10.\n        :param kwargs: Passed to the superclass.\n        \"\"\"\n        super(SimpleScrapingLocator, self).__init__(**kwargs)\n        self.base_url = ensure_slash(url)\n        self.timeout = timeout\n        self._page_cache = {}\n        self._seen = set()\n        self._to_fetch = queue.Queue()\n        self._bad_hosts = set()\n        self.skip_externals = False\n        self.num_workers = num_workers\n        self._lock = threading.RLock()\n        # See issue #45: we need to be resilient when the locator is used\n        # in a thread, e.g. with concurrent.futures. We can't use self._lock\n        # as it is for coordinating our internal threads - the ones created\n        # in _prepare_threads.\n        self._gplock = threading.RLock()\n        self.platform_check = False  # See issue #112\n\n    def _prepare_threads(self):\n        \"\"\"\n        Threads are created only when get_project is called, and terminate\n        before it returns. They are there primarily to parallelise I/O (i.e.\n        fetching web pages).\n        \"\"\"\n        self._threads = []\n        for i in range(self.num_workers):\n            t = threading.Thread(target=self._fetch)\n            t.setDaemon(True)\n            t.start()\n            self._threads.append(t)\n\n    def _wait_threads(self):\n        \"\"\"\n        Tell all the threads to terminate (by sending a sentinel value) and\n        wait for them to do so.\n        \"\"\"\n        # Note that you need two loops, since you can't say which\n        # thread will get each sentinel\n        for t in self._threads:\n            self._to_fetch.put(None)    # sentinel\n        for t in self._threads:\n            t.join()\n        self._threads = []\n\n    def _get_project(self, name):\n        result = {'urls': {}, 'digests': {}}\n        with self._gplock:\n            self.result = result\n            self.project_name = name\n            url = urljoin(self.base_url, '%s/' % quote(name))\n            self._seen.clear()\n            self._page_cache.clear()\n            self._prepare_threads()\n            try:\n                logger.debug('Queueing %s', url)\n                self._to_fetch.put(url)\n                self._to_fetch.join()\n            finally:\n                self._wait_threads()\n            del self.result\n        return result\n\n    platform_dependent = re.compile(r'\\b(linux_(i\\d86|x86_64|arm\\w+)|'\n                                    r'win(32|_amd64)|macosx_?\\d+)\\b', re.I)\n\n    def _is_platform_dependent(self, url):\n        \"\"\"\n        Does an URL refer to a platform-specific download?\n        \"\"\"\n        return self.platform_dependent.search(url)\n\n    def _process_download(self, url):\n        \"\"\"\n        See if an URL is a suitable download for a project.\n\n        If it is, register information in the result dictionary (for\n        _get_project) about the specific version it's for.\n\n        Note that the return value isn't actually used other than as a boolean\n        value.\n        \"\"\"\n        if self.platform_check and self._is_platform_dependent(url):\n            info = None\n        else:\n            info = self.convert_url_to_download_info(url, self.project_name)\n        logger.debug('process_download: %s -> %s', url, info)\n        if info:\n            with self._lock:    # needed because self.result is shared\n                self._update_version_data(self.result, info)\n        return info\n\n    def _should_queue(self, link, referrer, rel):\n        \"\"\"\n        Determine whether a link URL from a referring page and with a\n        particular \"rel\" attribute should be queued for scraping.\n        \"\"\"\n        scheme, netloc, path, _, _, _ = urlparse(link)\n        if path.endswith(self.source_extensions + self.binary_extensions +\n                         self.excluded_extensions):\n            result = False\n        elif self.skip_externals and not link.startswith(self.base_url):\n            result = False\n        elif not referrer.startswith(self.base_url):\n            result = False\n        elif rel not in ('homepage', 'download'):\n            result = False\n        elif scheme not in ('http', 'https', 'ftp'):\n            result = False\n        elif self._is_platform_dependent(link):\n            result = False\n        else:\n            host = netloc.split(':', 1)[0]\n            if host.lower() == 'localhost':\n                result = False\n            else:\n                result = True\n        logger.debug('should_queue: %s (%s) from %s -> %s', link, rel,\n                     referrer, result)\n        return result\n\n    def _fetch(self):\n        \"\"\"\n        Get a URL to fetch from the work queue, get the HTML page, examine its\n        links for download candidates and candidates for further scraping.\n\n        This is a handy method to run in a thread.\n        \"\"\"\n        while True:\n            url = self._to_fetch.get()\n            try:\n                if url:\n                    page = self.get_page(url)\n                    if page is None:    # e.g. after an error\n                        continue\n                    for link, rel in page.links:\n                        if link not in self._seen:\n                            try:\n                                self._seen.add(link)\n                                if (not self._process_download(link) and\n                                    self._should_queue(link, url, rel)):\n                                    logger.debug('Queueing %s from %s', link, url)\n                                    self._to_fetch.put(link)\n                            except MetadataInvalidError:  # e.g. invalid versions\n                                pass\n            except Exception as e:  # pragma: no cover\n                self.errors.put(text_type(e))\n            finally:\n                # always do this, to avoid hangs :-)\n                self._to_fetch.task_done()\n            if not url:\n                #logger.debug('Sentinel seen, quitting.')\n                break\n\n    def get_page(self, url):\n        \"\"\"\n        Get the HTML for an URL, possibly from an in-memory cache.\n\n        XXX TODO Note: this cache is never actually cleared. It's assumed that\n        the data won't get stale over the lifetime of a locator instance (not\n        necessarily true for the default_locator).\n        \"\"\"\n        # http://peak.telecommunity.com/DevCenter/EasyInstall#package-index-api\n        scheme, netloc, path, _, _, _ = urlparse(url)\n        if scheme == 'file' and os.path.isdir(url2pathname(path)):\n            url = urljoin(ensure_slash(url), 'index.html')\n\n        if url in self._page_cache:\n            result = self._page_cache[url]\n            logger.debug('Returning %s from cache: %s', url, result)\n        else:\n            host = netloc.split(':', 1)[0]\n            result = None\n            if host in self._bad_hosts:\n                logger.debug('Skipping %s due to bad host %s', url, host)\n            else:\n                req = Request(url, headers={'Accept-encoding': 'identity'})\n                try:\n                    logger.debug('Fetching %s', url)\n                    resp = self.opener.open(req, timeout=self.timeout)\n                    logger.debug('Fetched %s', url)\n                    headers = resp.info()\n                    content_type = headers.get('Content-Type', '')\n                    if HTML_CONTENT_TYPE.match(content_type):\n                        final_url = resp.geturl()\n                        data = resp.read()\n                        encoding = headers.get('Content-Encoding')\n                        if encoding:\n                            decoder = self.decoders[encoding]   # fail if not found\n                            data = decoder(data)\n                        encoding = 'utf-8'\n                        m = CHARSET.search(content_type)\n                        if m:\n                            encoding = m.group(1)\n                        try:\n                            data = data.decode(encoding)\n                        except UnicodeError:  # pragma: no cover\n                            data = data.decode('latin-1')    # fallback\n                        result = Page(data, final_url)\n                        self._page_cache[final_url] = result\n                except HTTPError as e:\n                    if e.code != 404:\n                        logger.exception('Fetch failed: %s: %s', url, e)\n                except URLError as e:  # pragma: no cover\n                    logger.exception('Fetch failed: %s: %s', url, e)\n                    with self._lock:\n                        self._bad_hosts.add(host)\n                except Exception as e:  # pragma: no cover\n                    logger.exception('Fetch failed: %s: %s', url, e)\n                finally:\n                    self._page_cache[url] = result   # even if None (failure)\n        return result\n\n    _distname_re = re.compile('<a href=[^>]*>([^<]+)<')\n\n    def get_distribution_names(self):\n        \"\"\"\n        Return all the distribution names known to this locator.\n        \"\"\"\n        result = set()\n        page = self.get_page(self.base_url)\n        if not page:\n            raise DistlibException('Unable to get %s' % self.base_url)\n        for match in self._distname_re.finditer(page.data):\n            result.add(match.group(1))\n        return result\n\nclass DirectoryLocator(Locator):\n    \"\"\"\n    This class locates distributions in a directory tree.\n    \"\"\"\n\n    def __init__(self, path, **kwargs):\n        \"\"\"\n        Initialise an instance.\n        :param path: The root of the directory tree to search.\n        :param kwargs: Passed to the superclass constructor,\n                       except for:\n                       * recursive - if True (the default), subdirectories are\n                         recursed into. If False, only the top-level directory\n                         is searched,\n        \"\"\"\n        self.recursive = kwargs.pop('recursive', True)\n        super(DirectoryLocator, self).__init__(**kwargs)\n        path = os.path.abspath(path)\n        if not os.path.isdir(path):  # pragma: no cover\n            raise DistlibException('Not a directory: %r' % path)\n        self.base_dir = path\n\n    def should_include(self, filename, parent):\n        \"\"\"\n        Should a filename be considered as a candidate for a distribution\n        archive? As well as the filename, the directory which contains it\n        is provided, though not used by the current implementation.\n        \"\"\"\n        return filename.endswith(self.downloadable_extensions)\n\n    def _get_project(self, name):\n        result = {'urls': {}, 'digests': {}}\n        for root, dirs, files in os.walk(self.base_dir):\n            for fn in files:\n                if self.should_include(fn, root):\n                    fn = os.path.join(root, fn)\n                    url = urlunparse(('file', '',\n                                      pathname2url(os.path.abspath(fn)),\n                                      '', '', ''))\n                    info = self.convert_url_to_download_info(url, name)\n                    if info:\n                        self._update_version_data(result, info)\n            if not self.recursive:\n                break\n        return result\n\n    def get_distribution_names(self):\n        \"\"\"\n        Return all the distribution names known to this locator.\n        \"\"\"\n        result = set()\n        for root, dirs, files in os.walk(self.base_dir):\n            for fn in files:\n                if self.should_include(fn, root):\n                    fn = os.path.join(root, fn)\n                    url = urlunparse(('file', '',\n                                      pathname2url(os.path.abspath(fn)),\n                                      '', '', ''))\n                    info = self.convert_url_to_download_info(url, None)\n                    if info:\n                        result.add(info['name'])\n            if not self.recursive:\n                break\n        return result\n\nclass JSONLocator(Locator):\n    \"\"\"\n    This locator uses special extended metadata (not available on PyPI) and is\n    the basis of performant dependency resolution in distlib. Other locators\n    require archive downloads before dependencies can be determined! As you\n    might imagine, that can be slow.\n    \"\"\"\n    def get_distribution_names(self):\n        \"\"\"\n        Return all the distribution names known to this locator.\n        \"\"\"\n        raise NotImplementedError('Not available from this locator')\n\n    def _get_project(self, name):\n        result = {'urls': {}, 'digests': {}}\n        data = get_project_data(name)\n        if data:\n            for info in data.get('files', []):\n                if info['ptype'] != 'sdist' or info['pyversion'] != 'source':\n                    continue\n                # We don't store summary in project metadata as it makes\n                # the data bigger for no benefit during dependency\n                # resolution\n                dist = make_dist(data['name'], info['version'],\n                                 summary=data.get('summary',\n                                                  'Placeholder for summary'),\n                                 scheme=self.scheme)\n                md = dist.metadata\n                md.source_url = info['url']\n                # TODO SHA256 digest\n                if 'digest' in info and info['digest']:\n                    dist.digest = ('md5', info['digest'])\n                md.dependencies = info.get('requirements', {})\n                dist.exports = info.get('exports', {})\n                result[dist.version] = dist\n                result['urls'].setdefault(dist.version, set()).add(info['url'])\n        return result\n\nclass DistPathLocator(Locator):\n    \"\"\"\n    This locator finds installed distributions in a path. It can be useful for\n    adding to an :class:`AggregatingLocator`.\n    \"\"\"\n    def __init__(self, distpath, **kwargs):\n        \"\"\"\n        Initialise an instance.\n\n        :param distpath: A :class:`DistributionPath` instance to search.\n        \"\"\"\n        super(DistPathLocator, self).__init__(**kwargs)\n        assert isinstance(distpath, DistributionPath)\n        self.distpath = distpath\n\n    def _get_project(self, name):\n        dist = self.distpath.get_distribution(name)\n        if dist is None:\n            result = {'urls': {}, 'digests': {}}\n        else:\n            result = {\n                dist.version: dist,\n                'urls': {dist.version: set([dist.source_url])},\n                'digests': {dist.version: set([None])}\n            }\n        return result\n\n\nclass AggregatingLocator(Locator):\n    \"\"\"\n    This class allows you to chain and/or merge a list of locators.\n    \"\"\"\n    def __init__(self, *locators, **kwargs):\n        \"\"\"\n        Initialise an instance.\n\n        :param locators: The list of locators to search.\n        :param kwargs: Passed to the superclass constructor,\n                       except for:\n                       * merge - if False (the default), the first successful\n                         search from any of the locators is returned. If True,\n                         the results from all locators are merged (this can be\n                         slow).\n        \"\"\"\n        self.merge = kwargs.pop('merge', False)\n        self.locators = locators\n        super(AggregatingLocator, self).__init__(**kwargs)\n\n    def clear_cache(self):\n        super(AggregatingLocator, self).clear_cache()\n        for locator in self.locators:\n            locator.clear_cache()\n\n    def _set_scheme(self, value):\n        self._scheme = value\n        for locator in self.locators:\n            locator.scheme = value\n\n    scheme = property(Locator.scheme.fget, _set_scheme)\n\n    def _get_project(self, name):\n        result = {}\n        for locator in self.locators:\n            d = locator.get_project(name)\n            if d:\n                if self.merge:\n                    files = result.get('urls', {})\n                    digests = result.get('digests', {})\n                    # next line could overwrite result['urls'], result['digests']\n                    result.update(d)\n                    df = result.get('urls')\n                    if files and df:\n                        for k, v in files.items():\n                            if k in df:\n                                df[k] |= v\n                            else:\n                                df[k] = v\n                    dd = result.get('digests')\n                    if digests and dd:\n                        dd.update(digests)\n                else:\n                    # See issue #18. If any dists are found and we're looking\n                    # for specific constraints, we only return something if\n                    # a match is found. For example, if a DirectoryLocator\n                    # returns just foo (1.0) while we're looking for\n                    # foo (>= 2.0), we'll pretend there was nothing there so\n                    # that subsequent locators can be queried. Otherwise we\n                    # would just return foo (1.0) which would then lead to a\n                    # failure to find foo (>= 2.0), because other locators\n                    # weren't searched. Note that this only matters when\n                    # merge=False.\n                    if self.matcher is None:\n                        found = True\n                    else:\n                        found = False\n                        for k in d:\n                            if self.matcher.match(k):\n                                found = True\n                                break\n                    if found:\n                        result = d\n                        break\n        return result\n\n    def get_distribution_names(self):\n        \"\"\"\n        Return all the distribution names known to this locator.\n        \"\"\"\n        result = set()\n        for locator in self.locators:\n            try:\n                result |= locator.get_distribution_names()\n            except NotImplementedError:\n                pass\n        return result\n\n\n# We use a legacy scheme simply because most of the dists on PyPI use legacy\n# versions which don't conform to PEP 426 / PEP 440.\ndefault_locator = AggregatingLocator(\n                    JSONLocator(),\n                    SimpleScrapingLocator('https://pypi.python.org/simple/',\n                                          timeout=3.0),\n                    scheme='legacy')\n\nlocate = default_locator.locate\n\nNAME_VERSION_RE = re.compile(r'(?P<name>[\\w-]+)\\s*'\n                             r'\\(\\s*(==\\s*)?(?P<ver>[^)]+)\\)$')\n\nclass DependencyFinder(object):\n    \"\"\"\n    Locate dependencies for distributions.\n    \"\"\"\n\n    def __init__(self, locator=None):\n        \"\"\"\n        Initialise an instance, using the specified locator\n        to locate distributions.\n        \"\"\"\n        self.locator = locator or default_locator\n        self.scheme = get_scheme(self.locator.scheme)\n\n    def add_distribution(self, dist):\n        \"\"\"\n        Add a distribution to the finder. This will update internal information\n        about who provides what.\n        :param dist: The distribution to add.\n        \"\"\"\n        logger.debug('adding distribution %s', dist)\n        name = dist.key\n        self.dists_by_name[name] = dist\n        self.dists[(name, dist.version)] = dist\n        for p in dist.provides:\n            name, version = parse_name_and_version(p)\n            logger.debug('Add to provided: %s, %s, %s', name, version, dist)\n            self.provided.setdefault(name, set()).add((version, dist))\n\n    def remove_distribution(self, dist):\n        \"\"\"\n        Remove a distribution from the finder. This will update internal\n        information about who provides what.\n        :param dist: The distribution to remove.\n        \"\"\"\n        logger.debug('removing distribution %s', dist)\n        name = dist.key\n        del self.dists_by_name[name]\n        del self.dists[(name, dist.version)]\n        for p in dist.provides:\n            name, version = parse_name_and_version(p)\n            logger.debug('Remove from provided: %s, %s, %s', name, version, dist)\n            s = self.provided[name]\n            s.remove((version, dist))\n            if not s:\n                del self.provided[name]\n\n    def get_matcher(self, reqt):\n        \"\"\"\n        Get a version matcher for a requirement.\n        :param reqt: The requirement\n        :type reqt: str\n        :return: A version matcher (an instance of\n                 :class:`distlib.version.Matcher`).\n        \"\"\"\n        try:\n            matcher = self.scheme.matcher(reqt)\n        except UnsupportedVersionError:  # pragma: no cover\n            # XXX compat-mode if cannot read the version\n            name = reqt.split()[0]\n            matcher = self.scheme.matcher(name)\n        return matcher\n\n    def find_providers(self, reqt):\n        \"\"\"\n        Find the distributions which can fulfill a requirement.\n\n        :param reqt: The requirement.\n         :type reqt: str\n        :return: A set of distribution which can fulfill the requirement.\n        \"\"\"\n        matcher = self.get_matcher(reqt)\n        name = matcher.key   # case-insensitive\n        result = set()\n        provided = self.provided\n        if name in provided:\n            for version, provider in provided[name]:\n                try:\n                    match = matcher.match(version)\n                except UnsupportedVersionError:\n                    match = False\n\n                if match:\n                    result.add(provider)\n                    break\n        return result\n\n    def try_to_replace(self, provider, other, problems):\n        \"\"\"\n        Attempt to replace one provider with another. This is typically used\n        when resolving dependencies from multiple sources, e.g. A requires\n        (B >= 1.0) while C requires (B >= 1.1).\n\n        For successful replacement, ``provider`` must meet all the requirements\n        which ``other`` fulfills.\n\n        :param provider: The provider we are trying to replace with.\n        :param other: The provider we're trying to replace.\n        :param problems: If False is returned, this will contain what\n                         problems prevented replacement. This is currently\n                         a tuple of the literal string 'cantreplace',\n                         ``provider``, ``other``  and the set of requirements\n                         that ``provider`` couldn't fulfill.\n        :return: True if we can replace ``other`` with ``provider``, else\n                 False.\n        \"\"\"\n        rlist = self.reqts[other]\n        unmatched = set()\n        for s in rlist:\n            matcher = self.get_matcher(s)\n            if not matcher.match(provider.version):\n                unmatched.add(s)\n        if unmatched:\n            # can't replace other with provider\n            problems.add(('cantreplace', provider, other,\n                          frozenset(unmatched)))\n            result = False\n        else:\n            # can replace other with provider\n            self.remove_distribution(other)\n            del self.reqts[other]\n            for s in rlist:\n                self.reqts.setdefault(provider, set()).add(s)\n            self.add_distribution(provider)\n            result = True\n        return result\n\n    def find(self, requirement, meta_extras=None, prereleases=False):\n        \"\"\"\n        Find a distribution and all distributions it depends on.\n\n        :param requirement: The requirement specifying the distribution to\n                            find, or a Distribution instance.\n        :param meta_extras: A list of meta extras such as :test:, :build: and\n                            so on.\n        :param prereleases: If ``True``, allow pre-release versions to be\n                            returned - otherwise, don't return prereleases\n                            unless they're all that's available.\n\n        Return a set of :class:`Distribution` instances and a set of\n        problems.\n\n        The distributions returned should be such that they have the\n        :attr:`required` attribute set to ``True`` if they were\n        from the ``requirement`` passed to ``find()``, and they have the\n        :attr:`build_time_dependency` attribute set to ``True`` unless they\n        are post-installation dependencies of the ``requirement``.\n\n        The problems should be a tuple consisting of the string\n        ``'unsatisfied'`` and the requirement which couldn't be satisfied\n        by any distribution known to the locator.\n        \"\"\"\n\n        self.provided = {}\n        self.dists = {}\n        self.dists_by_name = {}\n        self.reqts = {}\n\n        meta_extras = set(meta_extras or [])\n        if ':*:' in meta_extras:\n            meta_extras.remove(':*:')\n            # :meta: and :run: are implicitly included\n            meta_extras |= set([':test:', ':build:', ':dev:'])\n\n        if isinstance(requirement, Distribution):\n            dist = odist = requirement\n            logger.debug('passed %s as requirement', odist)\n        else:\n            dist = odist = self.locator.locate(requirement,\n                                               prereleases=prereleases)\n            if dist is None:\n                raise DistlibException('Unable to locate %r' % requirement)\n            logger.debug('located %s', odist)\n        dist.requested = True\n        problems = set()\n        todo = set([dist])\n        install_dists = set([odist])\n        while todo:\n            dist = todo.pop()\n            name = dist.key     # case-insensitive\n            if name not in self.dists_by_name:\n                self.add_distribution(dist)\n            else:\n                #import pdb; pdb.set_trace()\n                other = self.dists_by_name[name]\n                if other != dist:\n                    self.try_to_replace(dist, other, problems)\n\n            ireqts = dist.run_requires | dist.meta_requires\n            sreqts = dist.build_requires\n            ereqts = set()\n            if meta_extras and dist in install_dists:\n                for key in ('test', 'build', 'dev'):\n                    e = ':%s:' % key\n                    if e in meta_extras:\n                        ereqts |= getattr(dist, '%s_requires' % key)\n            all_reqts = ireqts | sreqts | ereqts\n            for r in all_reqts:\n                providers = self.find_providers(r)\n                if not providers:\n                    logger.debug('No providers found for %r', r)\n                    provider = self.locator.locate(r, prereleases=prereleases)\n                    # If no provider is found and we didn't consider\n                    # prereleases, consider them now.\n                    if provider is None and not prereleases:\n                        provider = self.locator.locate(r, prereleases=True)\n                    if provider is None:\n                        logger.debug('Cannot satisfy %r', r)\n                        problems.add(('unsatisfied', r))\n                    else:\n                        n, v = provider.key, provider.version\n                        if (n, v) not in self.dists:\n                            todo.add(provider)\n                        providers.add(provider)\n                        if r in ireqts and dist in install_dists:\n                            install_dists.add(provider)\n                            logger.debug('Adding %s to install_dists',\n                                         provider.name_and_version)\n                for p in providers:\n                    name = p.key\n                    if name not in self.dists_by_name:\n                        self.reqts.setdefault(p, set()).add(r)\n                    else:\n                        other = self.dists_by_name[name]\n                        if other != p:\n                            # see if other can be replaced by p\n                            self.try_to_replace(p, other, problems)\n\n        dists = set(self.dists.values())\n        for dist in dists:\n            dist.build_time_dependency = dist not in install_dists\n            if dist.build_time_dependency:\n                logger.debug('%s is a build-time dependency only.',\n                             dist.name_and_version)\n        logger.debug('find done for %s', odist)\n        return dists, problems\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/manifest.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2012-2013 Python Software Foundation.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\n\"\"\"\nClass representing the list of files in a distribution.\n\nEquivalent to distutils.filelist, but fixes some problems.\n\"\"\"\nimport fnmatch\nimport logging\nimport os\nimport re\nimport sys\n\nfrom . import DistlibException\nfrom .compat import fsdecode\nfrom .util import convert_path\n\n\n__all__ = ['Manifest']\n\nlogger = logging.getLogger(__name__)\n\n# a \\ followed by some spaces + EOL\n_COLLAPSE_PATTERN = re.compile('\\\\\\\\w*\\n', re.M)\n_COMMENTED_LINE = re.compile('#.*?(?=\\n)|\\n(?=$)', re.M | re.S)\n\n#\n# Due to the different results returned by fnmatch.translate, we need\n# to do slightly different processing for Python 2.7 and 3.2 ... this needed\n# to be brought in for Python 3.6 onwards.\n#\n_PYTHON_VERSION = sys.version_info[:2]\n\nclass Manifest(object):\n    \"\"\"A list of files built by on exploring the filesystem and filtered by\n    applying various patterns to what we find there.\n    \"\"\"\n\n    def __init__(self, base=None):\n        \"\"\"\n        Initialise an instance.\n\n        :param base: The base directory to explore under.\n        \"\"\"\n        self.base = os.path.abspath(os.path.normpath(base or os.getcwd()))\n        self.prefix = self.base + os.sep\n        self.allfiles = None\n        self.files = set()\n\n    #\n    # Public API\n    #\n\n    def findall(self):\n        \"\"\"Find all files under the base and set ``allfiles`` to the absolute\n        pathnames of files found.\n        \"\"\"\n        from stat import S_ISREG, S_ISDIR, S_ISLNK\n\n        self.allfiles = allfiles = []\n        root = self.base\n        stack = [root]\n        pop = stack.pop\n        push = stack.append\n\n        while stack:\n            root = pop()\n            names = os.listdir(root)\n\n            for name in names:\n                fullname = os.path.join(root, name)\n\n                # Avoid excess stat calls -- just one will do, thank you!\n                stat = os.stat(fullname)\n                mode = stat.st_mode\n                if S_ISREG(mode):\n                    allfiles.append(fsdecode(fullname))\n                elif S_ISDIR(mode) and not S_ISLNK(mode):\n                    push(fullname)\n\n    def add(self, item):\n        \"\"\"\n        Add a file to the manifest.\n\n        :param item: The pathname to add. This can be relative to the base.\n        \"\"\"\n        if not item.startswith(self.prefix):\n            item = os.path.join(self.base, item)\n        self.files.add(os.path.normpath(item))\n\n    def add_many(self, items):\n        \"\"\"\n        Add a list of files to the manifest.\n\n        :param items: The pathnames to add. These can be relative to the base.\n        \"\"\"\n        for item in items:\n            self.add(item)\n\n    def sorted(self, wantdirs=False):\n        \"\"\"\n        Return sorted files in directory order\n        \"\"\"\n\n        def add_dir(dirs, d):\n            dirs.add(d)\n            logger.debug('add_dir added %s', d)\n            if d != self.base:\n                parent, _ = os.path.split(d)\n                assert parent not in ('', '/')\n                add_dir(dirs, parent)\n\n        result = set(self.files)    # make a copy!\n        if wantdirs:\n            dirs = set()\n            for f in result:\n                add_dir(dirs, os.path.dirname(f))\n            result |= dirs\n        return [os.path.join(*path_tuple) for path_tuple in\n                sorted(os.path.split(path) for path in result)]\n\n    def clear(self):\n        \"\"\"Clear all collected files.\"\"\"\n        self.files = set()\n        self.allfiles = []\n\n    def process_directive(self, directive):\n        \"\"\"\n        Process a directive which either adds some files from ``allfiles`` to\n        ``files``, or removes some files from ``files``.\n\n        :param directive: The directive to process. This should be in a format\n                     compatible with distutils ``MANIFEST.in`` files:\n\n                     http://docs.python.org/distutils/sourcedist.html#commands\n        \"\"\"\n        # Parse the line: split it up, make sure the right number of words\n        # is there, and return the relevant words.  'action' is always\n        # defined: it's the first word of the line.  Which of the other\n        # three are defined depends on the action; it'll be either\n        # patterns, (dir and patterns), or (dirpattern).\n        action, patterns, thedir, dirpattern = self._parse_directive(directive)\n\n        # OK, now we know that the action is valid and we have the\n        # right number of words on the line for that action -- so we\n        # can proceed with minimal error-checking.\n        if action == 'include':\n            for pattern in patterns:\n                if not self._include_pattern(pattern, anchor=True):\n                    logger.warning('no files found matching %r', pattern)\n\n        elif action == 'exclude':\n            for pattern in patterns:\n                found = self._exclude_pattern(pattern, anchor=True)\n                #if not found:\n                #    logger.warning('no previously-included files '\n                #                   'found matching %r', pattern)\n\n        elif action == 'global-include':\n            for pattern in patterns:\n                if not self._include_pattern(pattern, anchor=False):\n                    logger.warning('no files found matching %r '\n                                   'anywhere in distribution', pattern)\n\n        elif action == 'global-exclude':\n            for pattern in patterns:\n                found = self._exclude_pattern(pattern, anchor=False)\n                #if not found:\n                #    logger.warning('no previously-included files '\n                #                   'matching %r found anywhere in '\n                #                   'distribution', pattern)\n\n        elif action == 'recursive-include':\n            for pattern in patterns:\n                if not self._include_pattern(pattern, prefix=thedir):\n                    logger.warning('no files found matching %r '\n                                   'under directory %r', pattern, thedir)\n\n        elif action == 'recursive-exclude':\n            for pattern in patterns:\n                found = self._exclude_pattern(pattern, prefix=thedir)\n                #if not found:\n                #    logger.warning('no previously-included files '\n                #                   'matching %r found under directory %r',\n                #                   pattern, thedir)\n\n        elif action == 'graft':\n            if not self._include_pattern(None, prefix=dirpattern):\n                logger.warning('no directories found matching %r',\n                               dirpattern)\n\n        elif action == 'prune':\n            if not self._exclude_pattern(None, prefix=dirpattern):\n                logger.warning('no previously-included directories found '\n                               'matching %r', dirpattern)\n        else:   # pragma: no cover\n            # This should never happen, as it should be caught in\n            # _parse_template_line\n            raise DistlibException(\n                'invalid action %r' % action)\n\n    #\n    # Private API\n    #\n\n    def _parse_directive(self, directive):\n        \"\"\"\n        Validate a directive.\n        :param directive: The directive to validate.\n        :return: A tuple of action, patterns, thedir, dir_patterns\n        \"\"\"\n        words = directive.split()\n        if len(words) == 1 and words[0] not in ('include', 'exclude',\n                                                'global-include',\n                                                'global-exclude',\n                                                'recursive-include',\n                                                'recursive-exclude',\n                                                'graft', 'prune'):\n            # no action given, let's use the default 'include'\n            words.insert(0, 'include')\n\n        action = words[0]\n        patterns = thedir = dir_pattern = None\n\n        if action in ('include', 'exclude',\n                      'global-include', 'global-exclude'):\n            if len(words) < 2:\n                raise DistlibException(\n                    '%r expects <pattern1> <pattern2> ...' % action)\n\n            patterns = [convert_path(word) for word in words[1:]]\n\n        elif action in ('recursive-include', 'recursive-exclude'):\n            if len(words) < 3:\n                raise DistlibException(\n                    '%r expects <dir> <pattern1> <pattern2> ...' % action)\n\n            thedir = convert_path(words[1])\n            patterns = [convert_path(word) for word in words[2:]]\n\n        elif action in ('graft', 'prune'):\n            if len(words) != 2:\n                raise DistlibException(\n                    '%r expects a single <dir_pattern>' % action)\n\n            dir_pattern = convert_path(words[1])\n\n        else:\n            raise DistlibException('unknown action %r' % action)\n\n        return action, patterns, thedir, dir_pattern\n\n    def _include_pattern(self, pattern, anchor=True, prefix=None,\n                         is_regex=False):\n        \"\"\"Select strings (presumably filenames) from 'self.files' that\n        match 'pattern', a Unix-style wildcard (glob) pattern.\n\n        Patterns are not quite the same as implemented by the 'fnmatch'\n        module: '*' and '?'  match non-special characters, where \"special\"\n        is platform-dependent: slash on Unix; colon, slash, and backslash on\n        DOS/Windows; and colon on Mac OS.\n\n        If 'anchor' is true (the default), then the pattern match is more\n        stringent: \"*.py\" will match \"foo.py\" but not \"foo/bar.py\".  If\n        'anchor' is false, both of these will match.\n\n        If 'prefix' is supplied, then only filenames starting with 'prefix'\n        (itself a pattern) and ending with 'pattern', with anything in between\n        them, will match.  'anchor' is ignored in this case.\n\n        If 'is_regex' is true, 'anchor' and 'prefix' are ignored, and\n        'pattern' is assumed to be either a string containing a regex or a\n        regex object -- no translation is done, the regex is just compiled\n        and used as-is.\n\n        Selected strings will be added to self.files.\n\n        Return True if files are found.\n        \"\"\"\n        # XXX docstring lying about what the special chars are?\n        found = False\n        pattern_re = self._translate_pattern(pattern, anchor, prefix, is_regex)\n\n        # delayed loading of allfiles list\n        if self.allfiles is None:\n            self.findall()\n\n        for name in self.allfiles:\n            if pattern_re.search(name):\n                self.files.add(name)\n                found = True\n        return found\n\n    def _exclude_pattern(self, pattern, anchor=True, prefix=None,\n                         is_regex=False):\n        \"\"\"Remove strings (presumably filenames) from 'files' that match\n        'pattern'.\n\n        Other parameters are the same as for 'include_pattern()', above.\n        The list 'self.files' is modified in place. Return True if files are\n        found.\n\n        This API is public to allow e.g. exclusion of SCM subdirs, e.g. when\n        packaging source distributions\n        \"\"\"\n        found = False\n        pattern_re = self._translate_pattern(pattern, anchor, prefix, is_regex)\n        for f in list(self.files):\n            if pattern_re.search(f):\n                self.files.remove(f)\n                found = True\n        return found\n\n    def _translate_pattern(self, pattern, anchor=True, prefix=None,\n                           is_regex=False):\n        \"\"\"Translate a shell-like wildcard pattern to a compiled regular\n        expression.\n\n        Return the compiled regex.  If 'is_regex' true,\n        then 'pattern' is directly compiled to a regex (if it's a string)\n        or just returned as-is (assumes it's a regex object).\n        \"\"\"\n        if is_regex:\n            if isinstance(pattern, str):\n                return re.compile(pattern)\n            else:\n                return pattern\n\n        if _PYTHON_VERSION > (3, 2):\n            # ditch start and end characters\n            start, _, end = self._glob_to_re('_').partition('_')\n\n        if pattern:\n            pattern_re = self._glob_to_re(pattern)\n            if _PYTHON_VERSION > (3, 2):\n                assert pattern_re.startswith(start) and pattern_re.endswith(end)\n        else:\n            pattern_re = ''\n\n        base = re.escape(os.path.join(self.base, ''))\n        if prefix is not None:\n            # ditch end of pattern character\n            if _PYTHON_VERSION <= (3, 2):\n                empty_pattern = self._glob_to_re('')\n                prefix_re = self._glob_to_re(prefix)[:-len(empty_pattern)]\n            else:\n                prefix_re = self._glob_to_re(prefix)\n                assert prefix_re.startswith(start) and prefix_re.endswith(end)\n                prefix_re = prefix_re[len(start): len(prefix_re) - len(end)]\n            sep = os.sep\n            if os.sep == '\\\\':\n                sep = r'\\\\'\n            if _PYTHON_VERSION <= (3, 2):\n                pattern_re = '^' + base + sep.join((prefix_re,\n                                                    '.*' + pattern_re))\n            else:\n                pattern_re = pattern_re[len(start): len(pattern_re) - len(end)]\n                pattern_re = r'%s%s%s%s.*%s%s' % (start, base, prefix_re, sep,\n                                                  pattern_re, end)\n        else:  # no prefix -- respect anchor flag\n            if anchor:\n                if _PYTHON_VERSION <= (3, 2):\n                    pattern_re = '^' + base + pattern_re\n                else:\n                    pattern_re = r'%s%s%s' % (start, base, pattern_re[len(start):])\n\n        return re.compile(pattern_re)\n\n    def _glob_to_re(self, pattern):\n        \"\"\"Translate a shell-like glob pattern to a regular expression.\n\n        Return a string containing the regex.  Differs from\n        'fnmatch.translate()' in that '*' does not match \"special characters\"\n        (which are platform-specific).\n        \"\"\"\n        pattern_re = fnmatch.translate(pattern)\n\n        # '?' and '*' in the glob pattern become '.' and '.*' in the RE, which\n        # IMHO is wrong -- '?' and '*' aren't supposed to match slash in Unix,\n        # and by extension they shouldn't match such \"special characters\" under\n        # any OS.  So change all non-escaped dots in the RE to match any\n        # character except the special characters (currently: just os.sep).\n        sep = os.sep\n        if os.sep == '\\\\':\n            # we're using a regex to manipulate a regex, so we need\n            # to escape the backslash twice\n            sep = r'\\\\\\\\'\n        escaped = r'\\1[^%s]' % sep\n        pattern_re = re.sub(r'((?<!\\\\)(\\\\\\\\)*)\\.', escaped, pattern_re)\n        return pattern_re\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/markers.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2012-2017 Vinay Sajip.\n# Licensed to the Python Software Foundation under a contributor agreement.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\n\"\"\"\nParser for the environment markers micro-language defined in PEP 508.\n\"\"\"\n\n# Note: In PEP 345, the micro-language was Python compatible, so the ast\n# module could be used to parse it. However, PEP 508 introduced operators such\n# as ~= and === which aren't in Python, necessitating a different approach.\n\nimport os\nimport sys\nimport platform\nimport re\n\nfrom .compat import python_implementation, urlparse, string_types\nfrom .util import in_venv, parse_marker\n\n__all__ = ['interpret']\n\ndef _is_literal(o):\n    if not isinstance(o, string_types) or not o:\n        return False\n    return o[0] in '\\'\"'\n\nclass Evaluator(object):\n    \"\"\"\n    This class is used to evaluate marker expessions.\n    \"\"\"\n\n    operations = {\n        '==': lambda x, y: x == y,\n        '===': lambda x, y: x == y,\n        '~=': lambda x, y: x == y or x > y,\n        '!=': lambda x, y: x != y,\n        '<':  lambda x, y: x < y,\n        '<=':  lambda x, y: x == y or x < y,\n        '>':  lambda x, y: x > y,\n        '>=':  lambda x, y: x == y or x > y,\n        'and': lambda x, y: x and y,\n        'or': lambda x, y: x or y,\n        'in': lambda x, y: x in y,\n        'not in': lambda x, y: x not in y,\n    }\n\n    def evaluate(self, expr, context):\n        \"\"\"\n        Evaluate a marker expression returned by the :func:`parse_requirement`\n        function in the specified context.\n        \"\"\"\n        if isinstance(expr, string_types):\n            if expr[0] in '\\'\"':\n                result = expr[1:-1]\n            else:\n                if expr not in context:\n                    raise SyntaxError('unknown variable: %s' % expr)\n                result = context[expr]\n        else:\n            assert isinstance(expr, dict)\n            op = expr['op']\n            if op not in self.operations:\n                raise NotImplementedError('op not implemented: %s' % op)\n            elhs = expr['lhs']\n            erhs = expr['rhs']\n            if _is_literal(expr['lhs']) and _is_literal(expr['rhs']):\n                raise SyntaxError('invalid comparison: %s %s %s' % (elhs, op, erhs))\n\n            lhs = self.evaluate(elhs, context)\n            rhs = self.evaluate(erhs, context)\n            result = self.operations[op](lhs, rhs)\n        return result\n\ndef default_context():\n    def format_full_version(info):\n        version = '%s.%s.%s' % (info.major, info.minor, info.micro)\n        kind = info.releaselevel\n        if kind != 'final':\n            version += kind[0] + str(info.serial)\n        return version\n\n    if hasattr(sys, 'implementation'):\n        implementation_version = format_full_version(sys.implementation.version)\n        implementation_name = sys.implementation.name\n    else:\n        implementation_version = '0'\n        implementation_name = ''\n\n    result = {\n        'implementation_name': implementation_name,\n        'implementation_version': implementation_version,\n        'os_name': os.name,\n        'platform_machine': platform.machine(),\n        'platform_python_implementation': platform.python_implementation(),\n        'platform_release': platform.release(),\n        'platform_system': platform.system(),\n        'platform_version': platform.version(),\n        'platform_in_venv': str(in_venv()),\n        'python_full_version': platform.python_version(),\n        'python_version': platform.python_version()[:3],\n        'sys_platform': sys.platform,\n    }\n    return result\n\nDEFAULT_CONTEXT = default_context()\ndel default_context\n\nevaluator = Evaluator()\n\ndef interpret(marker, execution_context=None):\n    \"\"\"\n    Interpret a marker and return a result depending on environment.\n\n    :param marker: The marker to interpret.\n    :type marker: str\n    :param execution_context: The context used for name lookup.\n    :type execution_context: mapping\n    \"\"\"\n    try:\n        expr, rest = parse_marker(marker)\n    except Exception as e:\n        raise SyntaxError('Unable to interpret marker syntax: %s: %s' % (marker, e))\n    if rest and rest[0] != '#':\n        raise SyntaxError('unexpected trailing data in marker: %s: %s' % (marker, rest))\n    context = dict(DEFAULT_CONTEXT)\n    if execution_context:\n        context.update(execution_context)\n    return evaluator.evaluate(expr, context)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/metadata.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2012 The Python Software Foundation.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\n\"\"\"Implementation of the Metadata for Python packages PEPs.\n\nSupports all metadata formats (1.0, 1.1, 1.2, and 2.0 experimental).\n\"\"\"\nfrom __future__ import unicode_literals\n\nimport codecs\nfrom email import message_from_file\nimport json\nimport logging\nimport re\n\n\nfrom . import DistlibException, __version__\nfrom .compat import StringIO, string_types, text_type\nfrom .markers import interpret\nfrom .util import extract_by_key, get_extras\nfrom .version import get_scheme, PEP440_VERSION_RE\n\nlogger = logging.getLogger(__name__)\n\n\nclass MetadataMissingError(DistlibException):\n    \"\"\"A required metadata is missing\"\"\"\n\n\nclass MetadataConflictError(DistlibException):\n    \"\"\"Attempt to read or write metadata fields that are conflictual.\"\"\"\n\n\nclass MetadataUnrecognizedVersionError(DistlibException):\n    \"\"\"Unknown metadata version number.\"\"\"\n\n\nclass MetadataInvalidError(DistlibException):\n    \"\"\"A metadata value is invalid\"\"\"\n\n# public API of this module\n__all__ = ['Metadata', 'PKG_INFO_ENCODING', 'PKG_INFO_PREFERRED_VERSION']\n\n# Encoding used for the PKG-INFO files\nPKG_INFO_ENCODING = 'utf-8'\n\n# preferred version. Hopefully will be changed\n# to 1.2 once PEP 345 is supported everywhere\nPKG_INFO_PREFERRED_VERSION = '1.1'\n\n_LINE_PREFIX_1_2 = re.compile('\\n       \\\\|')\n_LINE_PREFIX_PRE_1_2 = re.compile('\\n        ')\n_241_FIELDS = ('Metadata-Version', 'Name', 'Version', 'Platform',\n               'Summary', 'Description',\n               'Keywords', 'Home-page', 'Author', 'Author-email',\n               'License')\n\n_314_FIELDS = ('Metadata-Version', 'Name', 'Version', 'Platform',\n               'Supported-Platform', 'Summary', 'Description',\n               'Keywords', 'Home-page', 'Author', 'Author-email',\n               'License', 'Classifier', 'Download-URL', 'Obsoletes',\n               'Provides', 'Requires')\n\n_314_MARKERS = ('Obsoletes', 'Provides', 'Requires', 'Classifier',\n                'Download-URL')\n\n_345_FIELDS = ('Metadata-Version', 'Name', 'Version', 'Platform',\n               'Supported-Platform', 'Summary', 'Description',\n               'Keywords', 'Home-page', 'Author', 'Author-email',\n               'Maintainer', 'Maintainer-email', 'License',\n               'Classifier', 'Download-URL', 'Obsoletes-Dist',\n               'Project-URL', 'Provides-Dist', 'Requires-Dist',\n               'Requires-Python', 'Requires-External')\n\n_345_MARKERS = ('Provides-Dist', 'Requires-Dist', 'Requires-Python',\n                'Obsoletes-Dist', 'Requires-External', 'Maintainer',\n                'Maintainer-email', 'Project-URL')\n\n_426_FIELDS = ('Metadata-Version', 'Name', 'Version', 'Platform',\n               'Supported-Platform', 'Summary', 'Description',\n               'Keywords', 'Home-page', 'Author', 'Author-email',\n               'Maintainer', 'Maintainer-email', 'License',\n               'Classifier', 'Download-URL', 'Obsoletes-Dist',\n               'Project-URL', 'Provides-Dist', 'Requires-Dist',\n               'Requires-Python', 'Requires-External', 'Private-Version',\n               'Obsoleted-By', 'Setup-Requires-Dist', 'Extension',\n               'Provides-Extra')\n\n_426_MARKERS = ('Private-Version', 'Provides-Extra', 'Obsoleted-By',\n                'Setup-Requires-Dist', 'Extension')\n\n# See issue #106: Sometimes 'Requires' occurs wrongly in the metadata. Include\n# it in the tuple literal below to allow it (for now)\n_566_FIELDS = _426_FIELDS + ('Description-Content-Type', 'Requires')\n\n_566_MARKERS = ('Description-Content-Type',)\n\n_ALL_FIELDS = set()\n_ALL_FIELDS.update(_241_FIELDS)\n_ALL_FIELDS.update(_314_FIELDS)\n_ALL_FIELDS.update(_345_FIELDS)\n_ALL_FIELDS.update(_426_FIELDS)\n_ALL_FIELDS.update(_566_FIELDS)\n\nEXTRA_RE = re.compile(r'''extra\\s*==\\s*(\"([^\"]+)\"|'([^']+)')''')\n\n\ndef _version2fieldlist(version):\n    if version == '1.0':\n        return _241_FIELDS\n    elif version == '1.1':\n        return _314_FIELDS\n    elif version == '1.2':\n        return _345_FIELDS\n    elif version in ('1.3', '2.1'):\n        return _345_FIELDS + _566_FIELDS\n    elif version == '2.0':\n        return _426_FIELDS\n    raise MetadataUnrecognizedVersionError(version)\n\n\ndef _best_version(fields):\n    \"\"\"Detect the best version depending on the fields used.\"\"\"\n    def _has_marker(keys, markers):\n        for marker in markers:\n            if marker in keys:\n                return True\n        return False\n\n    keys = []\n    for key, value in fields.items():\n        if value in ([], 'UNKNOWN', None):\n            continue\n        keys.append(key)\n\n    possible_versions = ['1.0', '1.1', '1.2', '1.3', '2.0', '2.1']\n\n    # first let's try to see if a field is not part of one of the version\n    for key in keys:\n        if key not in _241_FIELDS and '1.0' in possible_versions:\n            possible_versions.remove('1.0')\n            logger.debug('Removed 1.0 due to %s', key)\n        if key not in _314_FIELDS and '1.1' in possible_versions:\n            possible_versions.remove('1.1')\n            logger.debug('Removed 1.1 due to %s', key)\n        if key not in _345_FIELDS and '1.2' in possible_versions:\n            possible_versions.remove('1.2')\n            logger.debug('Removed 1.2 due to %s', key)\n        if key not in _566_FIELDS and '1.3' in possible_versions:\n            possible_versions.remove('1.3')\n            logger.debug('Removed 1.3 due to %s', key)\n        if key not in _566_FIELDS and '2.1' in possible_versions:\n            if key != 'Description':  # In 2.1, description allowed after headers\n                possible_versions.remove('2.1')\n                logger.debug('Removed 2.1 due to %s', key)\n        if key not in _426_FIELDS and '2.0' in possible_versions:\n            possible_versions.remove('2.0')\n            logger.debug('Removed 2.0 due to %s', key)\n\n    # possible_version contains qualified versions\n    if len(possible_versions) == 1:\n        return possible_versions[0]   # found !\n    elif len(possible_versions) == 0:\n        logger.debug('Out of options - unknown metadata set: %s', fields)\n        raise MetadataConflictError('Unknown metadata set')\n\n    # let's see if one unique marker is found\n    is_1_1 = '1.1' in possible_versions and _has_marker(keys, _314_MARKERS)\n    is_1_2 = '1.2' in possible_versions and _has_marker(keys, _345_MARKERS)\n    is_2_1 = '2.1' in possible_versions and _has_marker(keys, _566_MARKERS)\n    is_2_0 = '2.0' in possible_versions and _has_marker(keys, _426_MARKERS)\n    if int(is_1_1) + int(is_1_2) + int(is_2_1) + int(is_2_0) > 1:\n        raise MetadataConflictError('You used incompatible 1.1/1.2/2.0/2.1 fields')\n\n    # we have the choice, 1.0, or 1.2, or 2.0\n    #   - 1.0 has a broken Summary field but works with all tools\n    #   - 1.1 is to avoid\n    #   - 1.2 fixes Summary but has little adoption\n    #   - 2.0 adds more features and is very new\n    if not is_1_1 and not is_1_2 and not is_2_1 and not is_2_0:\n        # we couldn't find any specific marker\n        if PKG_INFO_PREFERRED_VERSION in possible_versions:\n            return PKG_INFO_PREFERRED_VERSION\n    if is_1_1:\n        return '1.1'\n    if is_1_2:\n        return '1.2'\n    if is_2_1:\n        return '2.1'\n\n    return '2.0'\n\n_ATTR2FIELD = {\n    'metadata_version': 'Metadata-Version',\n    'name': 'Name',\n    'version': 'Version',\n    'platform': 'Platform',\n    'supported_platform': 'Supported-Platform',\n    'summary': 'Summary',\n    'description': 'Description',\n    'keywords': 'Keywords',\n    'home_page': 'Home-page',\n    'author': 'Author',\n    'author_email': 'Author-email',\n    'maintainer': 'Maintainer',\n    'maintainer_email': 'Maintainer-email',\n    'license': 'License',\n    'classifier': 'Classifier',\n    'download_url': 'Download-URL',\n    'obsoletes_dist': 'Obsoletes-Dist',\n    'provides_dist': 'Provides-Dist',\n    'requires_dist': 'Requires-Dist',\n    'setup_requires_dist': 'Setup-Requires-Dist',\n    'requires_python': 'Requires-Python',\n    'requires_external': 'Requires-External',\n    'requires': 'Requires',\n    'provides': 'Provides',\n    'obsoletes': 'Obsoletes',\n    'project_url': 'Project-URL',\n    'private_version': 'Private-Version',\n    'obsoleted_by': 'Obsoleted-By',\n    'extension': 'Extension',\n    'provides_extra': 'Provides-Extra',\n}\n\n_PREDICATE_FIELDS = ('Requires-Dist', 'Obsoletes-Dist', 'Provides-Dist')\n_VERSIONS_FIELDS = ('Requires-Python',)\n_VERSION_FIELDS = ('Version',)\n_LISTFIELDS = ('Platform', 'Classifier', 'Obsoletes',\n               'Requires', 'Provides', 'Obsoletes-Dist',\n               'Provides-Dist', 'Requires-Dist', 'Requires-External',\n               'Project-URL', 'Supported-Platform', 'Setup-Requires-Dist',\n               'Provides-Extra', 'Extension')\n_LISTTUPLEFIELDS = ('Project-URL',)\n\n_ELEMENTSFIELD = ('Keywords',)\n\n_UNICODEFIELDS = ('Author', 'Maintainer', 'Summary', 'Description')\n\n_MISSING = object()\n\n_FILESAFE = re.compile('[^A-Za-z0-9.]+')\n\n\ndef _get_name_and_version(name, version, for_filename=False):\n    \"\"\"Return the distribution name with version.\n\n    If for_filename is true, return a filename-escaped form.\"\"\"\n    if for_filename:\n        # For both name and version any runs of non-alphanumeric or '.'\n        # characters are replaced with a single '-'.  Additionally any\n        # spaces in the version string become '.'\n        name = _FILESAFE.sub('-', name)\n        version = _FILESAFE.sub('-', version.replace(' ', '.'))\n    return '%s-%s' % (name, version)\n\n\nclass LegacyMetadata(object):\n    \"\"\"The legacy metadata of a release.\n\n    Supports versions 1.0, 1.1 and 1.2 (auto-detected). You can\n    instantiate the class with one of these arguments (or none):\n    - *path*, the path to a metadata file\n    - *fileobj* give a file-like object with metadata as content\n    - *mapping* is a dict-like object\n    - *scheme* is a version scheme name\n    \"\"\"\n    # TODO document the mapping API and UNKNOWN default key\n\n    def __init__(self, path=None, fileobj=None, mapping=None,\n                 scheme='default'):\n        if [path, fileobj, mapping].count(None) < 2:\n            raise TypeError('path, fileobj and mapping are exclusive')\n        self._fields = {}\n        self.requires_files = []\n        self._dependencies = None\n        self.scheme = scheme\n        if path is not None:\n            self.read(path)\n        elif fileobj is not None:\n            self.read_file(fileobj)\n        elif mapping is not None:\n            self.update(mapping)\n            self.set_metadata_version()\n\n    def set_metadata_version(self):\n        self._fields['Metadata-Version'] = _best_version(self._fields)\n\n    def _write_field(self, fileobj, name, value):\n        fileobj.write('%s: %s\\n' % (name, value))\n\n    def __getitem__(self, name):\n        return self.get(name)\n\n    def __setitem__(self, name, value):\n        return self.set(name, value)\n\n    def __delitem__(self, name):\n        field_name = self._convert_name(name)\n        try:\n            del self._fields[field_name]\n        except KeyError:\n            raise KeyError(name)\n\n    def __contains__(self, name):\n        return (name in self._fields or\n                self._convert_name(name) in self._fields)\n\n    def _convert_name(self, name):\n        if name in _ALL_FIELDS:\n            return name\n        name = name.replace('-', '_').lower()\n        return _ATTR2FIELD.get(name, name)\n\n    def _default_value(self, name):\n        if name in _LISTFIELDS or name in _ELEMENTSFIELD:\n            return []\n        return 'UNKNOWN'\n\n    def _remove_line_prefix(self, value):\n        if self.metadata_version in ('1.0', '1.1'):\n            return _LINE_PREFIX_PRE_1_2.sub('\\n', value)\n        else:\n            return _LINE_PREFIX_1_2.sub('\\n', value)\n\n    def __getattr__(self, name):\n        if name in _ATTR2FIELD:\n            return self[name]\n        raise AttributeError(name)\n\n    #\n    # Public API\n    #\n\n#    dependencies = property(_get_dependencies, _set_dependencies)\n\n    def get_fullname(self, filesafe=False):\n        \"\"\"Return the distribution name with version.\n\n        If filesafe is true, return a filename-escaped form.\"\"\"\n        return _get_name_and_version(self['Name'], self['Version'], filesafe)\n\n    def is_field(self, name):\n        \"\"\"return True if name is a valid metadata key\"\"\"\n        name = self._convert_name(name)\n        return name in _ALL_FIELDS\n\n    def is_multi_field(self, name):\n        name = self._convert_name(name)\n        return name in _LISTFIELDS\n\n    def read(self, filepath):\n        \"\"\"Read the metadata values from a file path.\"\"\"\n        fp = codecs.open(filepath, 'r', encoding='utf-8')\n        try:\n            self.read_file(fp)\n        finally:\n            fp.close()\n\n    def read_file(self, fileob):\n        \"\"\"Read the metadata values from a file object.\"\"\"\n        msg = message_from_file(fileob)\n        self._fields['Metadata-Version'] = msg['metadata-version']\n\n        # When reading, get all the fields we can\n        for field in _ALL_FIELDS:\n            if field not in msg:\n                continue\n            if field in _LISTFIELDS:\n                # we can have multiple lines\n                values = msg.get_all(field)\n                if field in _LISTTUPLEFIELDS and values is not None:\n                    values = [tuple(value.split(',')) for value in values]\n                self.set(field, values)\n            else:\n                # single line\n                value = msg[field]\n                if value is not None and value != 'UNKNOWN':\n                    self.set(field, value)\n        # logger.debug('Attempting to set metadata for %s', self)\n        # self.set_metadata_version()\n\n    def write(self, filepath, skip_unknown=False):\n        \"\"\"Write the metadata fields to filepath.\"\"\"\n        fp = codecs.open(filepath, 'w', encoding='utf-8')\n        try:\n            self.write_file(fp, skip_unknown)\n        finally:\n            fp.close()\n\n    def write_file(self, fileobject, skip_unknown=False):\n        \"\"\"Write the PKG-INFO format data to a file object.\"\"\"\n        self.set_metadata_version()\n\n        for field in _version2fieldlist(self['Metadata-Version']):\n            values = self.get(field)\n            if skip_unknown and values in ('UNKNOWN', [], ['UNKNOWN']):\n                continue\n            if field in _ELEMENTSFIELD:\n                self._write_field(fileobject, field, ','.join(values))\n                continue\n            if field not in _LISTFIELDS:\n                if field == 'Description':\n                    if self.metadata_version in ('1.0', '1.1'):\n                        values = values.replace('\\n', '\\n        ')\n                    else:\n                        values = values.replace('\\n', '\\n       |')\n                values = [values]\n\n            if field in _LISTTUPLEFIELDS:\n                values = [','.join(value) for value in values]\n\n            for value in values:\n                self._write_field(fileobject, field, value)\n\n    def update(self, other=None, **kwargs):\n        \"\"\"Set metadata values from the given iterable `other` and kwargs.\n\n        Behavior is like `dict.update`: If `other` has a ``keys`` method,\n        they are looped over and ``self[key]`` is assigned ``other[key]``.\n        Else, ``other`` is an iterable of ``(key, value)`` iterables.\n\n        Keys that don't match a metadata field or that have an empty value are\n        dropped.\n        \"\"\"\n        def _set(key, value):\n            if key in _ATTR2FIELD and value:\n                self.set(self._convert_name(key), value)\n\n        if not other:\n            # other is None or empty container\n            pass\n        elif hasattr(other, 'keys'):\n            for k in other.keys():\n                _set(k, other[k])\n        else:\n            for k, v in other:\n                _set(k, v)\n\n        if kwargs:\n            for k, v in kwargs.items():\n                _set(k, v)\n\n    def set(self, name, value):\n        \"\"\"Control then set a metadata field.\"\"\"\n        name = self._convert_name(name)\n\n        if ((name in _ELEMENTSFIELD or name == 'Platform') and\n            not isinstance(value, (list, tuple))):\n            if isinstance(value, string_types):\n                value = [v.strip() for v in value.split(',')]\n            else:\n                value = []\n        elif (name in _LISTFIELDS and\n              not isinstance(value, (list, tuple))):\n            if isinstance(value, string_types):\n                value = [value]\n            else:\n                value = []\n\n        if logger.isEnabledFor(logging.WARNING):\n            project_name = self['Name']\n\n            scheme = get_scheme(self.scheme)\n            if name in _PREDICATE_FIELDS and value is not None:\n                for v in value:\n                    # check that the values are valid\n                    if not scheme.is_valid_matcher(v.split(';')[0]):\n                        logger.warning(\n                            \"'%s': '%s' is not valid (field '%s')\",\n                            project_name, v, name)\n            # FIXME this rejects UNKNOWN, is that right?\n            elif name in _VERSIONS_FIELDS and value is not None:\n                if not scheme.is_valid_constraint_list(value):\n                    logger.warning(\"'%s': '%s' is not a valid version (field '%s')\",\n                                   project_name, value, name)\n            elif name in _VERSION_FIELDS and value is not None:\n                if not scheme.is_valid_version(value):\n                    logger.warning(\"'%s': '%s' is not a valid version (field '%s')\",\n                                   project_name, value, name)\n\n        if name in _UNICODEFIELDS:\n            if name == 'Description':\n                value = self._remove_line_prefix(value)\n\n        self._fields[name] = value\n\n    def get(self, name, default=_MISSING):\n        \"\"\"Get a metadata field.\"\"\"\n        name = self._convert_name(name)\n        if name not in self._fields:\n            if default is _MISSING:\n                default = self._default_value(name)\n            return default\n        if name in _UNICODEFIELDS:\n            value = self._fields[name]\n            return value\n        elif name in _LISTFIELDS:\n            value = self._fields[name]\n            if value is None:\n                return []\n            res = []\n            for val in value:\n                if name not in _LISTTUPLEFIELDS:\n                    res.append(val)\n                else:\n                    # That's for Project-URL\n                    res.append((val[0], val[1]))\n            return res\n\n        elif name in _ELEMENTSFIELD:\n            value = self._fields[name]\n            if isinstance(value, string_types):\n                return value.split(',')\n        return self._fields[name]\n\n    def check(self, strict=False):\n        \"\"\"Check if the metadata is compliant. If strict is True then raise if\n        no Name or Version are provided\"\"\"\n        self.set_metadata_version()\n\n        # XXX should check the versions (if the file was loaded)\n        missing, warnings = [], []\n\n        for attr in ('Name', 'Version'):  # required by PEP 345\n            if attr not in self:\n                missing.append(attr)\n\n        if strict and missing != []:\n            msg = 'missing required metadata: %s' % ', '.join(missing)\n            raise MetadataMissingError(msg)\n\n        for attr in ('Home-page', 'Author'):\n            if attr not in self:\n                missing.append(attr)\n\n        # checking metadata 1.2 (XXX needs to check 1.1, 1.0)\n        if self['Metadata-Version'] != '1.2':\n            return missing, warnings\n\n        scheme = get_scheme(self.scheme)\n\n        def are_valid_constraints(value):\n            for v in value:\n                if not scheme.is_valid_matcher(v.split(';')[0]):\n                    return False\n            return True\n\n        for fields, controller in ((_PREDICATE_FIELDS, are_valid_constraints),\n                                   (_VERSIONS_FIELDS,\n                                    scheme.is_valid_constraint_list),\n                                   (_VERSION_FIELDS,\n                                    scheme.is_valid_version)):\n            for field in fields:\n                value = self.get(field, None)\n                if value is not None and not controller(value):\n                    warnings.append(\"Wrong value for '%s': %s\" % (field, value))\n\n        return missing, warnings\n\n    def todict(self, skip_missing=False):\n        \"\"\"Return fields as a dict.\n\n        Field names will be converted to use the underscore-lowercase style\n        instead of hyphen-mixed case (i.e. home_page instead of Home-page).\n        \"\"\"\n        self.set_metadata_version()\n\n        mapping_1_0 = (\n            ('metadata_version', 'Metadata-Version'),\n            ('name', 'Name'),\n            ('version', 'Version'),\n            ('summary', 'Summary'),\n            ('home_page', 'Home-page'),\n            ('author', 'Author'),\n            ('author_email', 'Author-email'),\n            ('license', 'License'),\n            ('description', 'Description'),\n            ('keywords', 'Keywords'),\n            ('platform', 'Platform'),\n            ('classifiers', 'Classifier'),\n            ('download_url', 'Download-URL'),\n        )\n\n        data = {}\n        for key, field_name in mapping_1_0:\n            if not skip_missing or field_name in self._fields:\n                data[key] = self[field_name]\n\n        if self['Metadata-Version'] == '1.2':\n            mapping_1_2 = (\n                ('requires_dist', 'Requires-Dist'),\n                ('requires_python', 'Requires-Python'),\n                ('requires_external', 'Requires-External'),\n                ('provides_dist', 'Provides-Dist'),\n                ('obsoletes_dist', 'Obsoletes-Dist'),\n                ('project_url', 'Project-URL'),\n                ('maintainer', 'Maintainer'),\n                ('maintainer_email', 'Maintainer-email'),\n            )\n            for key, field_name in mapping_1_2:\n                if not skip_missing or field_name in self._fields:\n                    if key != 'project_url':\n                        data[key] = self[field_name]\n                    else:\n                        data[key] = [','.join(u) for u in self[field_name]]\n\n        elif self['Metadata-Version'] == '1.1':\n            mapping_1_1 = (\n                ('provides', 'Provides'),\n                ('requires', 'Requires'),\n                ('obsoletes', 'Obsoletes'),\n            )\n            for key, field_name in mapping_1_1:\n                if not skip_missing or field_name in self._fields:\n                    data[key] = self[field_name]\n\n        return data\n\n    def add_requirements(self, requirements):\n        if self['Metadata-Version'] == '1.1':\n            # we can't have 1.1 metadata *and* Setuptools requires\n            for field in ('Obsoletes', 'Requires', 'Provides'):\n                if field in self:\n                    del self[field]\n        self['Requires-Dist'] += requirements\n\n    # Mapping API\n    # TODO could add iter* variants\n\n    def keys(self):\n        return list(_version2fieldlist(self['Metadata-Version']))\n\n    def __iter__(self):\n        for key in self.keys():\n            yield key\n\n    def values(self):\n        return [self[key] for key in self.keys()]\n\n    def items(self):\n        return [(key, self[key]) for key in self.keys()]\n\n    def __repr__(self):\n        return '<%s %s %s>' % (self.__class__.__name__, self.name,\n                               self.version)\n\n\nMETADATA_FILENAME = 'pydist.json'\nWHEEL_METADATA_FILENAME = 'metadata.json'\nLEGACY_METADATA_FILENAME = 'METADATA'\n\n\nclass Metadata(object):\n    \"\"\"\n    The metadata of a release. This implementation uses 2.0 (JSON)\n    metadata where possible. If not possible, it wraps a LegacyMetadata\n    instance which handles the key-value metadata format.\n    \"\"\"\n\n    METADATA_VERSION_MATCHER = re.compile(r'^\\d+(\\.\\d+)*$')\n\n    NAME_MATCHER = re.compile('^[0-9A-Z]([0-9A-Z_.-]*[0-9A-Z])?$', re.I)\n\n    VERSION_MATCHER = PEP440_VERSION_RE\n\n    SUMMARY_MATCHER = re.compile('.{1,2047}')\n\n    METADATA_VERSION = '2.0'\n\n    GENERATOR = 'distlib (%s)' % __version__\n\n    MANDATORY_KEYS = {\n        'name': (),\n        'version': (),\n        'summary': ('legacy',),\n    }\n\n    INDEX_KEYS = ('name version license summary description author '\n                  'author_email keywords platform home_page classifiers '\n                  'download_url')\n\n    DEPENDENCY_KEYS = ('extras run_requires test_requires build_requires '\n                       'dev_requires provides meta_requires obsoleted_by '\n                       'supports_environments')\n\n    SYNTAX_VALIDATORS = {\n        'metadata_version': (METADATA_VERSION_MATCHER, ()),\n        'name': (NAME_MATCHER, ('legacy',)),\n        'version': (VERSION_MATCHER, ('legacy',)),\n        'summary': (SUMMARY_MATCHER, ('legacy',)),\n    }\n\n    __slots__ = ('_legacy', '_data', 'scheme')\n\n    def __init__(self, path=None, fileobj=None, mapping=None,\n                 scheme='default'):\n        if [path, fileobj, mapping].count(None) < 2:\n            raise TypeError('path, fileobj and mapping are exclusive')\n        self._legacy = None\n        self._data = None\n        self.scheme = scheme\n        #import pdb; pdb.set_trace()\n        if mapping is not None:\n            try:\n                self._validate_mapping(mapping, scheme)\n                self._data = mapping\n            except MetadataUnrecognizedVersionError:\n                self._legacy = LegacyMetadata(mapping=mapping, scheme=scheme)\n                self.validate()\n        else:\n            data = None\n            if path:\n                with open(path, 'rb') as f:\n                    data = f.read()\n            elif fileobj:\n                data = fileobj.read()\n            if data is None:\n                # Initialised with no args - to be added\n                self._data = {\n                    'metadata_version': self.METADATA_VERSION,\n                    'generator': self.GENERATOR,\n                }\n            else:\n                if not isinstance(data, text_type):\n                    data = data.decode('utf-8')\n                try:\n                    self._data = json.loads(data)\n                    self._validate_mapping(self._data, scheme)\n                except ValueError:\n                    # Note: MetadataUnrecognizedVersionError does not\n                    # inherit from ValueError (it's a DistlibException,\n                    # which should not inherit from ValueError).\n                    # The ValueError comes from the json.load - if that\n                    # succeeds and we get a validation error, we want\n                    # that to propagate\n                    self._legacy = LegacyMetadata(fileobj=StringIO(data),\n                                                  scheme=scheme)\n                    self.validate()\n\n    common_keys = set(('name', 'version', 'license', 'keywords', 'summary'))\n\n    none_list = (None, list)\n    none_dict = (None, dict)\n\n    mapped_keys = {\n        'run_requires': ('Requires-Dist', list),\n        'build_requires': ('Setup-Requires-Dist', list),\n        'dev_requires': none_list,\n        'test_requires': none_list,\n        'meta_requires': none_list,\n        'extras': ('Provides-Extra', list),\n        'modules': none_list,\n        'namespaces': none_list,\n        'exports': none_dict,\n        'commands': none_dict,\n        'classifiers': ('Classifier', list),\n        'source_url': ('Download-URL', None),\n        'metadata_version': ('Metadata-Version', None),\n    }\n\n    del none_list, none_dict\n\n    def __getattribute__(self, key):\n        common = object.__getattribute__(self, 'common_keys')\n        mapped = object.__getattribute__(self, 'mapped_keys')\n        if key in mapped:\n            lk, maker = mapped[key]\n            if self._legacy:\n                if lk is None:\n                    result = None if maker is None else maker()\n                else:\n                    result = self._legacy.get(lk)\n            else:\n                value = None if maker is None else maker()\n                if key not in ('commands', 'exports', 'modules', 'namespaces',\n                               'classifiers'):\n                    result = self._data.get(key, value)\n                else:\n                    # special cases for PEP 459\n                    sentinel = object()\n                    result = sentinel\n                    d = self._data.get('extensions')\n                    if d:\n                        if key == 'commands':\n                            result = d.get('python.commands', value)\n                        elif key == 'classifiers':\n                            d = d.get('python.details')\n                            if d:\n                                result = d.get(key, value)\n                        else:\n                            d = d.get('python.exports')\n                            if not d:\n                                d = self._data.get('python.exports')\n                            if d:\n                                result = d.get(key, value)\n                    if result is sentinel:\n                        result = value\n        elif key not in common:\n            result = object.__getattribute__(self, key)\n        elif self._legacy:\n            result = self._legacy.get(key)\n        else:\n            result = self._data.get(key)\n        return result\n\n    def _validate_value(self, key, value, scheme=None):\n        if key in self.SYNTAX_VALIDATORS:\n            pattern, exclusions = self.SYNTAX_VALIDATORS[key]\n            if (scheme or self.scheme) not in exclusions:\n                m = pattern.match(value)\n                if not m:\n                    raise MetadataInvalidError(\"'%s' is an invalid value for \"\n                                               \"the '%s' property\" % (value,\n                                                                    key))\n\n    def __setattr__(self, key, value):\n        self._validate_value(key, value)\n        common = object.__getattribute__(self, 'common_keys')\n        mapped = object.__getattribute__(self, 'mapped_keys')\n        if key in mapped:\n            lk, _ = mapped[key]\n            if self._legacy:\n                if lk is None:\n                    raise NotImplementedError\n                self._legacy[lk] = value\n            elif key not in ('commands', 'exports', 'modules', 'namespaces',\n                             'classifiers'):\n                self._data[key] = value\n            else:\n                # special cases for PEP 459\n                d = self._data.setdefault('extensions', {})\n                if key == 'commands':\n                    d['python.commands'] = value\n                elif key == 'classifiers':\n                    d = d.setdefault('python.details', {})\n                    d[key] = value\n                else:\n                    d = d.setdefault('python.exports', {})\n                    d[key] = value\n        elif key not in common:\n            object.__setattr__(self, key, value)\n        else:\n            if key == 'keywords':\n                if isinstance(value, string_types):\n                    value = value.strip()\n                    if value:\n                        value = value.split()\n                    else:\n                        value = []\n            if self._legacy:\n                self._legacy[key] = value\n            else:\n                self._data[key] = value\n\n    @property\n    def name_and_version(self):\n        return _get_name_and_version(self.name, self.version, True)\n\n    @property\n    def provides(self):\n        if self._legacy:\n            result = self._legacy['Provides-Dist']\n        else:\n            result = self._data.setdefault('provides', [])\n        s = '%s (%s)' % (self.name, self.version)\n        if s not in result:\n            result.append(s)\n        return result\n\n    @provides.setter\n    def provides(self, value):\n        if self._legacy:\n            self._legacy['Provides-Dist'] = value\n        else:\n            self._data['provides'] = value\n\n    def get_requirements(self, reqts, extras=None, env=None):\n        \"\"\"\n        Base method to get dependencies, given a set of extras\n        to satisfy and an optional environment context.\n        :param reqts: A list of sometimes-wanted dependencies,\n                      perhaps dependent on extras and environment.\n        :param extras: A list of optional components being requested.\n        :param env: An optional environment for marker evaluation.\n        \"\"\"\n        if self._legacy:\n            result = reqts\n        else:\n            result = []\n            extras = get_extras(extras or [], self.extras)\n            for d in reqts:\n                if 'extra' not in d and 'environment' not in d:\n                    # unconditional\n                    include = True\n                else:\n                    if 'extra' not in d:\n                        # Not extra-dependent - only environment-dependent\n                        include = True\n                    else:\n                        include = d.get('extra') in extras\n                    if include:\n                        # Not excluded because of extras, check environment\n                        marker = d.get('environment')\n                        if marker:\n                            include = interpret(marker, env)\n                if include:\n                    result.extend(d['requires'])\n            for key in ('build', 'dev', 'test'):\n                e = ':%s:' % key\n                if e in extras:\n                    extras.remove(e)\n                    # A recursive call, but it should terminate since 'test'\n                    # has been removed from the extras\n                    reqts = self._data.get('%s_requires' % key, [])\n                    result.extend(self.get_requirements(reqts, extras=extras,\n                                                        env=env))\n        return result\n\n    @property\n    def dictionary(self):\n        if self._legacy:\n            return self._from_legacy()\n        return self._data\n\n    @property\n    def dependencies(self):\n        if self._legacy:\n            raise NotImplementedError\n        else:\n            return extract_by_key(self._data, self.DEPENDENCY_KEYS)\n\n    @dependencies.setter\n    def dependencies(self, value):\n        if self._legacy:\n            raise NotImplementedError\n        else:\n            self._data.update(value)\n\n    def _validate_mapping(self, mapping, scheme):\n        if mapping.get('metadata_version') != self.METADATA_VERSION:\n            raise MetadataUnrecognizedVersionError()\n        missing = []\n        for key, exclusions in self.MANDATORY_KEYS.items():\n            if key not in mapping:\n                if scheme not in exclusions:\n                    missing.append(key)\n        if missing:\n            msg = 'Missing metadata items: %s' % ', '.join(missing)\n            raise MetadataMissingError(msg)\n        for k, v in mapping.items():\n            self._validate_value(k, v, scheme)\n\n    def validate(self):\n        if self._legacy:\n            missing, warnings = self._legacy.check(True)\n            if missing or warnings:\n                logger.warning('Metadata: missing: %s, warnings: %s',\n                               missing, warnings)\n        else:\n            self._validate_mapping(self._data, self.scheme)\n\n    def todict(self):\n        if self._legacy:\n            return self._legacy.todict(True)\n        else:\n            result = extract_by_key(self._data, self.INDEX_KEYS)\n            return result\n\n    def _from_legacy(self):\n        assert self._legacy and not self._data\n        result = {\n            'metadata_version': self.METADATA_VERSION,\n            'generator': self.GENERATOR,\n        }\n        lmd = self._legacy.todict(True)     # skip missing ones\n        for k in ('name', 'version', 'license', 'summary', 'description',\n                  'classifier'):\n            if k in lmd:\n                if k == 'classifier':\n                    nk = 'classifiers'\n                else:\n                    nk = k\n                result[nk] = lmd[k]\n        kw = lmd.get('Keywords', [])\n        if kw == ['']:\n            kw = []\n        result['keywords'] = kw\n        keys = (('requires_dist', 'run_requires'),\n                ('setup_requires_dist', 'build_requires'))\n        for ok, nk in keys:\n            if ok in lmd and lmd[ok]:\n                result[nk] = [{'requires': lmd[ok]}]\n        result['provides'] = self.provides\n        author = {}\n        maintainer = {}\n        return result\n\n    LEGACY_MAPPING = {\n        'name': 'Name',\n        'version': 'Version',\n        'license': 'License',\n        'summary': 'Summary',\n        'description': 'Description',\n        'classifiers': 'Classifier',\n    }\n\n    def _to_legacy(self):\n        def process_entries(entries):\n            reqts = set()\n            for e in entries:\n                extra = e.get('extra')\n                env = e.get('environment')\n                rlist = e['requires']\n                for r in rlist:\n                    if not env and not extra:\n                        reqts.add(r)\n                    else:\n                        marker = ''\n                        if extra:\n                            marker = 'extra == \"%s\"' % extra\n                        if env:\n                            if marker:\n                                marker = '(%s) and %s' % (env, marker)\n                            else:\n                                marker = env\n                        reqts.add(';'.join((r, marker)))\n            return reqts\n\n        assert self._data and not self._legacy\n        result = LegacyMetadata()\n        nmd = self._data\n        for nk, ok in self.LEGACY_MAPPING.items():\n            if nk in nmd:\n                result[ok] = nmd[nk]\n        r1 = process_entries(self.run_requires + self.meta_requires)\n        r2 = process_entries(self.build_requires + self.dev_requires)\n        if self.extras:\n            result['Provides-Extra'] = sorted(self.extras)\n        result['Requires-Dist'] = sorted(r1)\n        result['Setup-Requires-Dist'] = sorted(r2)\n        # TODO: other fields such as contacts\n        return result\n\n    def write(self, path=None, fileobj=None, legacy=False, skip_unknown=True):\n        if [path, fileobj].count(None) != 1:\n            raise ValueError('Exactly one of path and fileobj is needed')\n        self.validate()\n        if legacy:\n            if self._legacy:\n                legacy_md = self._legacy\n            else:\n                legacy_md = self._to_legacy()\n            if path:\n                legacy_md.write(path, skip_unknown=skip_unknown)\n            else:\n                legacy_md.write_file(fileobj, skip_unknown=skip_unknown)\n        else:\n            if self._legacy:\n                d = self._from_legacy()\n            else:\n                d = self._data\n            if fileobj:\n                json.dump(d, fileobj, ensure_ascii=True, indent=2,\n                          sort_keys=True)\n            else:\n                with codecs.open(path, 'w', 'utf-8') as f:\n                    json.dump(d, f, ensure_ascii=True, indent=2,\n                              sort_keys=True)\n\n    def add_requirements(self, requirements):\n        if self._legacy:\n            self._legacy.add_requirements(requirements)\n        else:\n            run_requires = self._data.setdefault('run_requires', [])\n            always = None\n            for entry in run_requires:\n                if 'environment' not in entry and 'extra' not in entry:\n                    always = entry\n                    break\n            if always is None:\n                always = { 'requires': requirements }\n                run_requires.insert(0, always)\n            else:\n                rset = set(always['requires']) | set(requirements)\n                always['requires'] = sorted(rset)\n\n    def __repr__(self):\n        name = self.name or '(no name)'\n        version = self.version or 'no version'\n        return '<%s %s %s (%s)>' % (self.__class__.__name__,\n                                    self.metadata_version, name, version)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/resources.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2013-2017 Vinay Sajip.\n# Licensed to the Python Software Foundation under a contributor agreement.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\nfrom __future__ import unicode_literals\n\nimport bisect\nimport io\nimport logging\nimport os\nimport pkgutil\nimport shutil\nimport sys\nimport types\nimport zipimport\n\nfrom . import DistlibException\nfrom .util import cached_property, get_cache_base, path_to_cache_dir, Cache\n\nlogger = logging.getLogger(__name__)\n\n\ncache = None    # created when needed\n\n\nclass ResourceCache(Cache):\n    def __init__(self, base=None):\n        if base is None:\n            # Use native string to avoid issues on 2.x: see Python #20140.\n            base = os.path.join(get_cache_base(), str('resource-cache'))\n        super(ResourceCache, self).__init__(base)\n\n    def is_stale(self, resource, path):\n        \"\"\"\n        Is the cache stale for the given resource?\n\n        :param resource: The :class:`Resource` being cached.\n        :param path: The path of the resource in the cache.\n        :return: True if the cache is stale.\n        \"\"\"\n        # Cache invalidation is a hard problem :-)\n        return True\n\n    def get(self, resource):\n        \"\"\"\n        Get a resource into the cache,\n\n        :param resource: A :class:`Resource` instance.\n        :return: The pathname of the resource in the cache.\n        \"\"\"\n        prefix, path = resource.finder.get_cache_info(resource)\n        if prefix is None:\n            result = path\n        else:\n            result = os.path.join(self.base, self.prefix_to_dir(prefix), path)\n            dirname = os.path.dirname(result)\n            if not os.path.isdir(dirname):\n                os.makedirs(dirname)\n            if not os.path.exists(result):\n                stale = True\n            else:\n                stale = self.is_stale(resource, path)\n            if stale:\n                # write the bytes of the resource to the cache location\n                with open(result, 'wb') as f:\n                    f.write(resource.bytes)\n        return result\n\n\nclass ResourceBase(object):\n    def __init__(self, finder, name):\n        self.finder = finder\n        self.name = name\n\n\nclass Resource(ResourceBase):\n    \"\"\"\n    A class representing an in-package resource, such as a data file. This is\n    not normally instantiated by user code, but rather by a\n    :class:`ResourceFinder` which manages the resource.\n    \"\"\"\n    is_container = False        # Backwards compatibility\n\n    def as_stream(self):\n        \"\"\"\n        Get the resource as a stream.\n\n        This is not a property to make it obvious that it returns a new stream\n        each time.\n        \"\"\"\n        return self.finder.get_stream(self)\n\n    @cached_property\n    def file_path(self):\n        global cache\n        if cache is None:\n            cache = ResourceCache()\n        return cache.get(self)\n\n    @cached_property\n    def bytes(self):\n        return self.finder.get_bytes(self)\n\n    @cached_property\n    def size(self):\n        return self.finder.get_size(self)\n\n\nclass ResourceContainer(ResourceBase):\n    is_container = True     # Backwards compatibility\n\n    @cached_property\n    def resources(self):\n        return self.finder.get_resources(self)\n\n\nclass ResourceFinder(object):\n    \"\"\"\n    Resource finder for file system resources.\n    \"\"\"\n\n    if sys.platform.startswith('java'):\n        skipped_extensions = ('.pyc', '.pyo', '.class')\n    else:\n        skipped_extensions = ('.pyc', '.pyo')\n\n    def __init__(self, module):\n        self.module = module\n        self.loader = getattr(module, '__loader__', None)\n        self.base = os.path.dirname(getattr(module, '__file__', ''))\n\n    def _adjust_path(self, path):\n        return os.path.realpath(path)\n\n    def _make_path(self, resource_name):\n        # Issue #50: need to preserve type of path on Python 2.x\n        # like os.path._get_sep\n        if isinstance(resource_name, bytes):    # should only happen on 2.x\n            sep = b'/'\n        else:\n            sep = '/'\n        parts = resource_name.split(sep)\n        parts.insert(0, self.base)\n        result = os.path.join(*parts)\n        return self._adjust_path(result)\n\n    def _find(self, path):\n        return os.path.exists(path)\n\n    def get_cache_info(self, resource):\n        return None, resource.path\n\n    def find(self, resource_name):\n        path = self._make_path(resource_name)\n        if not self._find(path):\n            result = None\n        else:\n            if self._is_directory(path):\n                result = ResourceContainer(self, resource_name)\n            else:\n                result = Resource(self, resource_name)\n            result.path = path\n        return result\n\n    def get_stream(self, resource):\n        return open(resource.path, 'rb')\n\n    def get_bytes(self, resource):\n        with open(resource.path, 'rb') as f:\n            return f.read()\n\n    def get_size(self, resource):\n        return os.path.getsize(resource.path)\n\n    def get_resources(self, resource):\n        def allowed(f):\n            return (f != '__pycache__' and not\n                    f.endswith(self.skipped_extensions))\n        return set([f for f in os.listdir(resource.path) if allowed(f)])\n\n    def is_container(self, resource):\n        return self._is_directory(resource.path)\n\n    _is_directory = staticmethod(os.path.isdir)\n\n    def iterator(self, resource_name):\n        resource = self.find(resource_name)\n        if resource is not None:\n            todo = [resource]\n            while todo:\n                resource = todo.pop(0)\n                yield resource\n                if resource.is_container:\n                    rname = resource.name\n                    for name in resource.resources:\n                        if not rname:\n                            new_name = name\n                        else:\n                            new_name = '/'.join([rname, name])\n                        child = self.find(new_name)\n                        if child.is_container:\n                            todo.append(child)\n                        else:\n                            yield child\n\n\nclass ZipResourceFinder(ResourceFinder):\n    \"\"\"\n    Resource finder for resources in .zip files.\n    \"\"\"\n    def __init__(self, module):\n        super(ZipResourceFinder, self).__init__(module)\n        archive = self.loader.archive\n        self.prefix_len = 1 + len(archive)\n        # PyPy doesn't have a _files attr on zipimporter, and you can't set one\n        if hasattr(self.loader, '_files'):\n            self._files = self.loader._files\n        else:\n            self._files = zipimport._zip_directory_cache[archive]\n        self.index = sorted(self._files)\n\n    def _adjust_path(self, path):\n        return path\n\n    def _find(self, path):\n        path = path[self.prefix_len:]\n        if path in self._files:\n            result = True\n        else:\n            if path and path[-1] != os.sep:\n                path = path + os.sep\n            i = bisect.bisect(self.index, path)\n            try:\n                result = self.index[i].startswith(path)\n            except IndexError:\n                result = False\n        if not result:\n            logger.debug('_find failed: %r %r', path, self.loader.prefix)\n        else:\n            logger.debug('_find worked: %r %r', path, self.loader.prefix)\n        return result\n\n    def get_cache_info(self, resource):\n        prefix = self.loader.archive\n        path = resource.path[1 + len(prefix):]\n        return prefix, path\n\n    def get_bytes(self, resource):\n        return self.loader.get_data(resource.path)\n\n    def get_stream(self, resource):\n        return io.BytesIO(self.get_bytes(resource))\n\n    def get_size(self, resource):\n        path = resource.path[self.prefix_len:]\n        return self._files[path][3]\n\n    def get_resources(self, resource):\n        path = resource.path[self.prefix_len:]\n        if path and path[-1] != os.sep:\n            path += os.sep\n        plen = len(path)\n        result = set()\n        i = bisect.bisect(self.index, path)\n        while i < len(self.index):\n            if not self.index[i].startswith(path):\n                break\n            s = self.index[i][plen:]\n            result.add(s.split(os.sep, 1)[0])   # only immediate children\n            i += 1\n        return result\n\n    def _is_directory(self, path):\n        path = path[self.prefix_len:]\n        if path and path[-1] != os.sep:\n            path += os.sep\n        i = bisect.bisect(self.index, path)\n        try:\n            result = self.index[i].startswith(path)\n        except IndexError:\n            result = False\n        return result\n\n_finder_registry = {\n    type(None): ResourceFinder,\n    zipimport.zipimporter: ZipResourceFinder\n}\n\ntry:\n    # In Python 3.6, _frozen_importlib -> _frozen_importlib_external\n    try:\n        import _frozen_importlib_external as _fi\n    except ImportError:\n        import _frozen_importlib as _fi\n    _finder_registry[_fi.SourceFileLoader] = ResourceFinder\n    _finder_registry[_fi.FileFinder] = ResourceFinder\n    del _fi\nexcept (ImportError, AttributeError):\n    pass\n\n\ndef register_finder(loader, finder_maker):\n    _finder_registry[type(loader)] = finder_maker\n\n_finder_cache = {}\n\n\ndef finder(package):\n    \"\"\"\n    Return a resource finder for a package.\n    :param package: The name of the package.\n    :return: A :class:`ResourceFinder` instance for the package.\n    \"\"\"\n    if package in _finder_cache:\n        result = _finder_cache[package]\n    else:\n        if package not in sys.modules:\n            __import__(package)\n        module = sys.modules[package]\n        path = getattr(module, '__path__', None)\n        if path is None:\n            raise DistlibException('You cannot get a finder for a module, '\n                                   'only for a package')\n        loader = getattr(module, '__loader__', None)\n        finder_maker = _finder_registry.get(type(loader))\n        if finder_maker is None:\n            raise DistlibException('Unable to locate finder for %r' % package)\n        result = finder_maker(module)\n        _finder_cache[package] = result\n    return result\n\n\n_dummy_module = types.ModuleType(str('__dummy__'))\n\n\ndef finder_for_path(path):\n    \"\"\"\n    Return a resource finder for a path, which should represent a container.\n\n    :param path: The path.\n    :return: A :class:`ResourceFinder` instance for the path.\n    \"\"\"\n    result = None\n    # calls any path hooks, gets importer into cache\n    pkgutil.get_importer(path)\n    loader = sys.path_importer_cache.get(path)\n    finder = _finder_registry.get(type(loader))\n    if finder:\n        module = _dummy_module\n        module.__file__ = os.path.join(path, '')\n        module.__loader__ = loader\n        result = finder(module)\n    return result\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/scripts.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2013-2015 Vinay Sajip.\n# Licensed to the Python Software Foundation under a contributor agreement.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\nfrom io import BytesIO\nimport logging\nimport os\nimport re\nimport struct\nimport sys\n\nfrom .compat import sysconfig, detect_encoding, ZipFile\nfrom .resources import finder\nfrom .util import (FileOperator, get_export_entry, convert_path,\n                   get_executable, in_venv)\n\nlogger = logging.getLogger(__name__)\n\n_DEFAULT_MANIFEST = '''\n<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\n<assembly xmlns=\"urn:schemas-microsoft-com:asm.v1\" manifestVersion=\"1.0\">\n <assemblyIdentity version=\"1.0.0.0\"\n processorArchitecture=\"X86\"\n name=\"%s\"\n type=\"win32\"/>\n\n <!-- Identify the application security requirements. -->\n <trustInfo xmlns=\"urn:schemas-microsoft-com:asm.v3\">\n <security>\n <requestedPrivileges>\n <requestedExecutionLevel level=\"asInvoker\" uiAccess=\"false\"/>\n </requestedPrivileges>\n </security>\n </trustInfo>\n</assembly>'''.strip()\n\n# check if Python is called on the first line with this expression\nFIRST_LINE_RE = re.compile(b'^#!.*pythonw?[0-9.]*([ \\t].*)?$')\nSCRIPT_TEMPLATE = r'''# -*- coding: utf-8 -*-\nif __name__ == '__main__':\n    import sys, re\n\n    def _resolve(module, func):\n        __import__(module)\n        mod = sys.modules[module]\n        parts = func.split('.')\n        result = getattr(mod, parts.pop(0))\n        for p in parts:\n            result = getattr(result, p)\n        return result\n\n    try:\n        sys.argv[0] = re.sub(r'(-script\\.pyw?|\\.exe)?$', '', sys.argv[0])\n\n        func = _resolve('%(module)s', '%(func)s')\n        rc = func() # None interpreted as 0\n    except Exception as e:  # only supporting Python >= 2.6\n        sys.stderr.write('%%s\\n' %% e)\n        rc = 1\n    sys.exit(rc)\n'''\n\n\ndef _enquote_executable(executable):\n    if ' ' in executable:\n        # make sure we quote only the executable in case of env\n        # for example /usr/bin/env \"/dir with spaces/bin/jython\"\n        # instead of \"/usr/bin/env /dir with spaces/bin/jython\"\n        # otherwise whole\n        if executable.startswith('/usr/bin/env '):\n            env, _executable = executable.split(' ', 1)\n            if ' ' in _executable and not _executable.startswith('\"'):\n                executable = '%s \"%s\"' % (env, _executable)\n        else:\n            if not executable.startswith('\"'):\n                executable = '\"%s\"' % executable\n    return executable\n\n\nclass ScriptMaker(object):\n    \"\"\"\n    A class to copy or create scripts from source scripts or callable\n    specifications.\n    \"\"\"\n    script_template = SCRIPT_TEMPLATE\n\n    executable = None  # for shebangs\n\n    def __init__(self, source_dir, target_dir, add_launchers=True,\n                 dry_run=False, fileop=None):\n        self.source_dir = source_dir\n        self.target_dir = target_dir\n        self.add_launchers = add_launchers\n        self.force = False\n        self.clobber = False\n        # It only makes sense to set mode bits on POSIX.\n        self.set_mode = (os.name == 'posix') or (os.name == 'java' and\n                                                 os._name == 'posix')\n        self.variants = set(('', 'X.Y'))\n        self._fileop = fileop or FileOperator(dry_run)\n\n        self._is_nt = os.name == 'nt' or (\n            os.name == 'java' and os._name == 'nt')\n\n    def _get_alternate_executable(self, executable, options):\n        if options.get('gui', False) and self._is_nt:  # pragma: no cover\n            dn, fn = os.path.split(executable)\n            fn = fn.replace('python', 'pythonw')\n            executable = os.path.join(dn, fn)\n        return executable\n\n    if sys.platform.startswith('java'):  # pragma: no cover\n        def _is_shell(self, executable):\n            \"\"\"\n            Determine if the specified executable is a script\n            (contains a #! line)\n            \"\"\"\n            try:\n                with open(executable) as fp:\n                    return fp.read(2) == '#!'\n            except (OSError, IOError):\n                logger.warning('Failed to open %s', executable)\n                return False\n\n        def _fix_jython_executable(self, executable):\n            if self._is_shell(executable):\n                # Workaround for Jython is not needed on Linux systems.\n                import java\n\n                if java.lang.System.getProperty('os.name') == 'Linux':\n                    return executable\n            elif executable.lower().endswith('jython.exe'):\n                # Use wrapper exe for Jython on Windows\n                return executable\n            return '/usr/bin/env %s' % executable\n\n    def _build_shebang(self, executable, post_interp):\n        \"\"\"\n        Build a shebang line. In the simple case (on Windows, or a shebang line\n        which is not too long or contains spaces) use a simple formulation for\n        the shebang. Otherwise, use /bin/sh as the executable, with a contrived\n        shebang which allows the script to run either under Python or sh, using\n        suitable quoting. Thanks to Harald Nordgren for his input.\n\n        See also: http://www.in-ulm.de/~mascheck/various/shebang/#length\n                  https://hg.mozilla.org/mozilla-central/file/tip/mach\n        \"\"\"\n        if os.name != 'posix':\n            simple_shebang = True\n        else:\n            # Add 3 for '#!' prefix and newline suffix.\n            shebang_length = len(executable) + len(post_interp) + 3\n            if sys.platform == 'darwin':\n                max_shebang_length = 512\n            else:\n                max_shebang_length = 127\n            simple_shebang = ((b' ' not in executable) and\n                              (shebang_length <= max_shebang_length))\n\n        if simple_shebang:\n            result = b'#!' + executable + post_interp + b'\\n'\n        else:\n            result = b'#!/bin/sh\\n'\n            result += b\"'''exec' \" + executable + post_interp + b' \"$0\" \"$@\"\\n'\n            result += b\"' '''\"\n        return result\n\n    def _get_shebang(self, encoding, post_interp=b'', options=None):\n        enquote = True\n        if self.executable:\n            executable = self.executable\n            enquote = False     # assume this will be taken care of\n        elif not sysconfig.is_python_build():\n            executable = get_executable()\n        elif in_venv():  # pragma: no cover\n            executable = os.path.join(sysconfig.get_path('scripts'),\n                            'python%s' % sysconfig.get_config_var('EXE'))\n        else:  # pragma: no cover\n            executable = os.path.join(\n                sysconfig.get_config_var('BINDIR'),\n               'python%s%s' % (sysconfig.get_config_var('VERSION'),\n                               sysconfig.get_config_var('EXE')))\n        if options:\n            executable = self._get_alternate_executable(executable, options)\n\n        if sys.platform.startswith('java'):  # pragma: no cover\n            executable = self._fix_jython_executable(executable)\n        # Normalise case for Windows\n        executable = os.path.normcase(executable)\n        # If the user didn't specify an executable, it may be necessary to\n        # cater for executable paths with spaces (not uncommon on Windows)\n        if enquote:\n            executable = _enquote_executable(executable)\n        # Issue #51: don't use fsencode, since we later try to\n        # check that the shebang is decodable using utf-8.\n        executable = executable.encode('utf-8')\n        # in case of IronPython, play safe and enable frames support\n        if (sys.platform == 'cli' and '-X:Frames' not in post_interp\n            and '-X:FullFrames' not in post_interp):  # pragma: no cover\n            post_interp += b' -X:Frames'\n        shebang = self._build_shebang(executable, post_interp)\n        # Python parser starts to read a script using UTF-8 until\n        # it gets a #coding:xxx cookie. The shebang has to be the\n        # first line of a file, the #coding:xxx cookie cannot be\n        # written before. So the shebang has to be decodable from\n        # UTF-8.\n        try:\n            shebang.decode('utf-8')\n        except UnicodeDecodeError:  # pragma: no cover\n            raise ValueError(\n                'The shebang (%r) is not decodable from utf-8' % shebang)\n        # If the script is encoded to a custom encoding (use a\n        # #coding:xxx cookie), the shebang has to be decodable from\n        # the script encoding too.\n        if encoding != 'utf-8':\n            try:\n                shebang.decode(encoding)\n            except UnicodeDecodeError:  # pragma: no cover\n                raise ValueError(\n                    'The shebang (%r) is not decodable '\n                    'from the script encoding (%r)' % (shebang, encoding))\n        return shebang\n\n    def _get_script_text(self, entry):\n        return self.script_template % dict(module=entry.prefix,\n                                           func=entry.suffix)\n\n    manifest = _DEFAULT_MANIFEST\n\n    def get_manifest(self, exename):\n        base = os.path.basename(exename)\n        return self.manifest % base\n\n    def _write_script(self, names, shebang, script_bytes, filenames, ext):\n        use_launcher = self.add_launchers and self._is_nt\n        linesep = os.linesep.encode('utf-8')\n        if not shebang.endswith(linesep):\n            shebang += linesep\n        if not use_launcher:\n            script_bytes = shebang + script_bytes\n        else:  # pragma: no cover\n            if ext == 'py':\n                launcher = self._get_launcher('t')\n            else:\n                launcher = self._get_launcher('w')\n            stream = BytesIO()\n            with ZipFile(stream, 'w') as zf:\n                zf.writestr('__main__.py', script_bytes)\n            zip_data = stream.getvalue()\n            script_bytes = launcher + shebang + zip_data\n        for name in names:\n            outname = os.path.join(self.target_dir, name)\n            if use_launcher:  # pragma: no cover\n                n, e = os.path.splitext(outname)\n                if e.startswith('.py'):\n                    outname = n\n                outname = '%s.exe' % outname\n                try:\n                    self._fileop.write_binary_file(outname, script_bytes)\n                except Exception:\n                    # Failed writing an executable - it might be in use.\n                    logger.warning('Failed to write executable - trying to '\n                                   'use .deleteme logic')\n                    dfname = '%s.deleteme' % outname\n                    if os.path.exists(dfname):\n                        os.remove(dfname)       # Not allowed to fail here\n                    os.rename(outname, dfname)  # nor here\n                    self._fileop.write_binary_file(outname, script_bytes)\n                    logger.debug('Able to replace executable using '\n                                 '.deleteme logic')\n                    try:\n                        os.remove(dfname)\n                    except Exception:\n                        pass    # still in use - ignore error\n            else:\n                if self._is_nt and not outname.endswith('.' + ext):  # pragma: no cover\n                    outname = '%s.%s' % (outname, ext)\n                if os.path.exists(outname) and not self.clobber:\n                    logger.warning('Skipping existing file %s', outname)\n                    continue\n                self._fileop.write_binary_file(outname, script_bytes)\n                if self.set_mode:\n                    self._fileop.set_executable_mode([outname])\n            filenames.append(outname)\n\n    def _make_script(self, entry, filenames, options=None):\n        post_interp = b''\n        if options:\n            args = options.get('interpreter_args', [])\n            if args:\n                args = ' %s' % ' '.join(args)\n                post_interp = args.encode('utf-8')\n        shebang = self._get_shebang('utf-8', post_interp, options=options)\n        script = self._get_script_text(entry).encode('utf-8')\n        name = entry.name\n        scriptnames = set()\n        if '' in self.variants:\n            scriptnames.add(name)\n        if 'X' in self.variants:\n            scriptnames.add('%s%s' % (name, sys.version[0]))\n        if 'X.Y' in self.variants:\n            scriptnames.add('%s-%s' % (name, sys.version[:3]))\n        if options and options.get('gui', False):\n            ext = 'pyw'\n        else:\n            ext = 'py'\n        self._write_script(scriptnames, shebang, script, filenames, ext)\n\n    def _copy_script(self, script, filenames):\n        adjust = False\n        script = os.path.join(self.source_dir, convert_path(script))\n        outname = os.path.join(self.target_dir, os.path.basename(script))\n        if not self.force and not self._fileop.newer(script, outname):\n            logger.debug('not copying %s (up-to-date)', script)\n            return\n\n        # Always open the file, but ignore failures in dry-run mode --\n        # that way, we'll get accurate feedback if we can read the\n        # script.\n        try:\n            f = open(script, 'rb')\n        except IOError:  # pragma: no cover\n            if not self.dry_run:\n                raise\n            f = None\n        else:\n            first_line = f.readline()\n            if not first_line:  # pragma: no cover\n                logger.warning('%s: %s is an empty file (skipping)',\n                               self.get_command_name(),  script)\n                return\n\n            match = FIRST_LINE_RE.match(first_line.replace(b'\\r\\n', b'\\n'))\n            if match:\n                adjust = True\n                post_interp = match.group(1) or b''\n\n        if not adjust:\n            if f:\n                f.close()\n            self._fileop.copy_file(script, outname)\n            if self.set_mode:\n                self._fileop.set_executable_mode([outname])\n            filenames.append(outname)\n        else:\n            logger.info('copying and adjusting %s -> %s', script,\n                        self.target_dir)\n            if not self._fileop.dry_run:\n                encoding, lines = detect_encoding(f.readline)\n                f.seek(0)\n                shebang = self._get_shebang(encoding, post_interp)\n                if b'pythonw' in first_line:  # pragma: no cover\n                    ext = 'pyw'\n                else:\n                    ext = 'py'\n                n = os.path.basename(outname)\n                self._write_script([n], shebang, f.read(), filenames, ext)\n            if f:\n                f.close()\n\n    @property\n    def dry_run(self):\n        return self._fileop.dry_run\n\n    @dry_run.setter\n    def dry_run(self, value):\n        self._fileop.dry_run = value\n\n    if os.name == 'nt' or (os.name == 'java' and os._name == 'nt'):  # pragma: no cover\n        # Executable launcher support.\n        # Launchers are from https://bitbucket.org/vinay.sajip/simple_launcher/\n\n        def _get_launcher(self, kind):\n            if struct.calcsize('P') == 8:   # 64-bit\n                bits = '64'\n            else:\n                bits = '32'\n            name = '%s%s.exe' % (kind, bits)\n            # Issue 31: don't hardcode an absolute package name, but\n            # determine it relative to the current package\n            distlib_package = __name__.rsplit('.', 1)[0]\n            result = finder(distlib_package).find(name).bytes\n            return result\n\n    # Public API follows\n\n    def make(self, specification, options=None):\n        \"\"\"\n        Make a script.\n\n        :param specification: The specification, which is either a valid export\n                              entry specification (to make a script from a\n                              callable) or a filename (to make a script by\n                              copying from a source location).\n        :param options: A dictionary of options controlling script generation.\n        :return: A list of all absolute pathnames written to.\n        \"\"\"\n        filenames = []\n        entry = get_export_entry(specification)\n        if entry is None:\n            self._copy_script(specification, filenames)\n        else:\n            self._make_script(entry, filenames, options=options)\n        return filenames\n\n    def make_multiple(self, specifications, options=None):\n        \"\"\"\n        Take a list of specifications and make scripts from them,\n        :param specifications: A list of specifications.\n        :return: A list of all absolute pathnames written to,\n        \"\"\"\n        filenames = []\n        for specification in specifications:\n            filenames.extend(self.make(specification, options))\n        return filenames\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/util.py",
    "content": "#\n# Copyright (C) 2012-2017 The Python Software Foundation.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\nimport codecs\nfrom collections import deque\nimport contextlib\nimport csv\nfrom glob import iglob as std_iglob\nimport io\nimport json\nimport logging\nimport os\nimport py_compile\nimport re\nimport socket\ntry:\n    import ssl\nexcept ImportError:  # pragma: no cover\n    ssl = None\nimport subprocess\nimport sys\nimport tarfile\nimport tempfile\nimport textwrap\n\ntry:\n    import threading\nexcept ImportError:  # pragma: no cover\n    import dummy_threading as threading\nimport time\n\nfrom . import DistlibException\nfrom .compat import (string_types, text_type, shutil, raw_input, StringIO,\n                     cache_from_source, urlopen, urljoin, httplib, xmlrpclib,\n                     splittype, HTTPHandler, BaseConfigurator, valid_ident,\n                     Container, configparser, URLError, ZipFile, fsdecode,\n                     unquote, urlparse)\n\nlogger = logging.getLogger(__name__)\n\n#\n# Requirement parsing code as per PEP 508\n#\n\nIDENTIFIER = re.compile(r'^([\\w\\.-]+)\\s*')\nVERSION_IDENTIFIER = re.compile(r'^([\\w\\.*+-]+)\\s*')\nCOMPARE_OP = re.compile(r'^(<=?|>=?|={2,3}|[~!]=)\\s*')\nMARKER_OP = re.compile(r'^((<=?)|(>=?)|={2,3}|[~!]=|in|not\\s+in)\\s*')\nOR = re.compile(r'^or\\b\\s*')\nAND = re.compile(r'^and\\b\\s*')\nNON_SPACE = re.compile(r'(\\S+)\\s*')\nSTRING_CHUNK = re.compile(r'([\\s\\w\\.{}()*+#:;,/?!~`@$%^&=|<>\\[\\]-]+)')\n\n\ndef parse_marker(marker_string):\n    \"\"\"\n    Parse a marker string and return a dictionary containing a marker expression.\n\n    The dictionary will contain keys \"op\", \"lhs\" and \"rhs\" for non-terminals in\n    the expression grammar, or strings. A string contained in quotes is to be\n    interpreted as a literal string, and a string not contained in quotes is a\n    variable (such as os_name).\n    \"\"\"\n    def marker_var(remaining):\n        # either identifier, or literal string\n        m = IDENTIFIER.match(remaining)\n        if m:\n            result = m.groups()[0]\n            remaining = remaining[m.end():]\n        elif not remaining:\n            raise SyntaxError('unexpected end of input')\n        else:\n            q = remaining[0]\n            if q not in '\\'\"':\n                raise SyntaxError('invalid expression: %s' % remaining)\n            oq = '\\'\"'.replace(q, '')\n            remaining = remaining[1:]\n            parts = [q]\n            while remaining:\n                # either a string chunk, or oq, or q to terminate\n                if remaining[0] == q:\n                    break\n                elif remaining[0] == oq:\n                    parts.append(oq)\n                    remaining = remaining[1:]\n                else:\n                    m = STRING_CHUNK.match(remaining)\n                    if not m:\n                        raise SyntaxError('error in string literal: %s' % remaining)\n                    parts.append(m.groups()[0])\n                    remaining = remaining[m.end():]\n            else:\n                s = ''.join(parts)\n                raise SyntaxError('unterminated string: %s' % s)\n            parts.append(q)\n            result = ''.join(parts)\n            remaining = remaining[1:].lstrip() # skip past closing quote\n        return result, remaining\n\n    def marker_expr(remaining):\n        if remaining and remaining[0] == '(':\n            result, remaining = marker(remaining[1:].lstrip())\n            if remaining[0] != ')':\n                raise SyntaxError('unterminated parenthesis: %s' % remaining)\n            remaining = remaining[1:].lstrip()\n        else:\n            lhs, remaining = marker_var(remaining)\n            while remaining:\n                m = MARKER_OP.match(remaining)\n                if not m:\n                    break\n                op = m.groups()[0]\n                remaining = remaining[m.end():]\n                rhs, remaining = marker_var(remaining)\n                lhs = {'op': op, 'lhs': lhs, 'rhs': rhs}\n            result = lhs\n        return result, remaining\n\n    def marker_and(remaining):\n        lhs, remaining = marker_expr(remaining)\n        while remaining:\n            m = AND.match(remaining)\n            if not m:\n                break\n            remaining = remaining[m.end():]\n            rhs, remaining = marker_expr(remaining)\n            lhs = {'op': 'and', 'lhs': lhs, 'rhs': rhs}\n        return lhs, remaining\n\n    def marker(remaining):\n        lhs, remaining = marker_and(remaining)\n        while remaining:\n            m = OR.match(remaining)\n            if not m:\n                break\n            remaining = remaining[m.end():]\n            rhs, remaining = marker_and(remaining)\n            lhs = {'op': 'or', 'lhs': lhs, 'rhs': rhs}\n        return lhs, remaining\n\n    return marker(marker_string)\n\n\ndef parse_requirement(req):\n    \"\"\"\n    Parse a requirement passed in as a string. Return a Container\n    whose attributes contain the various parts of the requirement.\n    \"\"\"\n    remaining = req.strip()\n    if not remaining or remaining.startswith('#'):\n        return None\n    m = IDENTIFIER.match(remaining)\n    if not m:\n        raise SyntaxError('name expected: %s' % remaining)\n    distname = m.groups()[0]\n    remaining = remaining[m.end():]\n    extras = mark_expr = versions = uri = None\n    if remaining and remaining[0] == '[':\n        i = remaining.find(']', 1)\n        if i < 0:\n            raise SyntaxError('unterminated extra: %s' % remaining)\n        s = remaining[1:i]\n        remaining = remaining[i + 1:].lstrip()\n        extras = []\n        while s:\n            m = IDENTIFIER.match(s)\n            if not m:\n                raise SyntaxError('malformed extra: %s' % s)\n            extras.append(m.groups()[0])\n            s = s[m.end():]\n            if not s:\n                break\n            if s[0] != ',':\n                raise SyntaxError('comma expected in extras: %s' % s)\n            s = s[1:].lstrip()\n        if not extras:\n            extras = None\n    if remaining:\n        if remaining[0] == '@':\n            # it's a URI\n            remaining = remaining[1:].lstrip()\n            m = NON_SPACE.match(remaining)\n            if not m:\n                raise SyntaxError('invalid URI: %s' % remaining)\n            uri = m.groups()[0]\n            t = urlparse(uri)\n            # there are issues with Python and URL parsing, so this test\n            # is a bit crude. See bpo-20271, bpo-23505. Python doesn't\n            # always parse invalid URLs correctly - it should raise\n            # exceptions for malformed URLs\n            if not (t.scheme and t.netloc):\n                raise SyntaxError('Invalid URL: %s' % uri)\n            remaining = remaining[m.end():].lstrip()\n        else:\n\n            def get_versions(ver_remaining):\n                \"\"\"\n                Return a list of operator, version tuples if any are\n                specified, else None.\n                \"\"\"\n                m = COMPARE_OP.match(ver_remaining)\n                versions = None\n                if m:\n                    versions = []\n                    while True:\n                        op = m.groups()[0]\n                        ver_remaining = ver_remaining[m.end():]\n                        m = VERSION_IDENTIFIER.match(ver_remaining)\n                        if not m:\n                            raise SyntaxError('invalid version: %s' % ver_remaining)\n                        v = m.groups()[0]\n                        versions.append((op, v))\n                        ver_remaining = ver_remaining[m.end():]\n                        if not ver_remaining or ver_remaining[0] != ',':\n                            break\n                        ver_remaining = ver_remaining[1:].lstrip()\n                        m = COMPARE_OP.match(ver_remaining)\n                        if not m:\n                            raise SyntaxError('invalid constraint: %s' % ver_remaining)\n                    if not versions:\n                        versions = None\n                return versions, ver_remaining\n\n            if remaining[0] != '(':\n                versions, remaining = get_versions(remaining)\n            else:\n                i = remaining.find(')', 1)\n                if i < 0:\n                    raise SyntaxError('unterminated parenthesis: %s' % remaining)\n                s = remaining[1:i]\n                remaining = remaining[i + 1:].lstrip()\n                # As a special diversion from PEP 508, allow a version number\n                # a.b.c in parentheses as a synonym for ~= a.b.c (because this\n                # is allowed in earlier PEPs)\n                if COMPARE_OP.match(s):\n                    versions, _ = get_versions(s)\n                else:\n                    m = VERSION_IDENTIFIER.match(s)\n                    if not m:\n                        raise SyntaxError('invalid constraint: %s' % s)\n                    v = m.groups()[0]\n                    s = s[m.end():].lstrip()\n                    if s:\n                        raise SyntaxError('invalid constraint: %s' % s)\n                    versions = [('~=', v)]\n\n    if remaining:\n        if remaining[0] != ';':\n            raise SyntaxError('invalid requirement: %s' % remaining)\n        remaining = remaining[1:].lstrip()\n\n        mark_expr, remaining = parse_marker(remaining)\n\n    if remaining and remaining[0] != '#':\n        raise SyntaxError('unexpected trailing data: %s' % remaining)\n\n    if not versions:\n        rs = distname\n    else:\n        rs = '%s %s' % (distname, ', '.join(['%s %s' % con for con in versions]))\n    return Container(name=distname, extras=extras, constraints=versions,\n                     marker=mark_expr, url=uri, requirement=rs)\n\n\ndef get_resources_dests(resources_root, rules):\n    \"\"\"Find destinations for resources files\"\"\"\n\n    def get_rel_path(root, path):\n        # normalizes and returns a lstripped-/-separated path\n        root = root.replace(os.path.sep, '/')\n        path = path.replace(os.path.sep, '/')\n        assert path.startswith(root)\n        return path[len(root):].lstrip('/')\n\n    destinations = {}\n    for base, suffix, dest in rules:\n        prefix = os.path.join(resources_root, base)\n        for abs_base in iglob(prefix):\n            abs_glob = os.path.join(abs_base, suffix)\n            for abs_path in iglob(abs_glob):\n                resource_file = get_rel_path(resources_root, abs_path)\n                if dest is None:  # remove the entry if it was here\n                    destinations.pop(resource_file, None)\n                else:\n                    rel_path = get_rel_path(abs_base, abs_path)\n                    rel_dest = dest.replace(os.path.sep, '/').rstrip('/')\n                    destinations[resource_file] = rel_dest + '/' + rel_path\n    return destinations\n\n\ndef in_venv():\n    if hasattr(sys, 'real_prefix'):\n        # virtualenv venvs\n        result = True\n    else:\n        # PEP 405 venvs\n        result = sys.prefix != getattr(sys, 'base_prefix', sys.prefix)\n    return result\n\n\ndef get_executable():\n# The __PYVENV_LAUNCHER__ dance is apparently no longer needed, as\n# changes to the stub launcher mean that sys.executable always points\n# to the stub on OS X\n#    if sys.platform == 'darwin' and ('__PYVENV_LAUNCHER__'\n#                                     in os.environ):\n#        result =  os.environ['__PYVENV_LAUNCHER__']\n#    else:\n#        result = sys.executable\n#    return result\n    result = os.path.normcase(sys.executable)\n    if not isinstance(result, text_type):\n        result = fsdecode(result)\n    return result\n\n\ndef proceed(prompt, allowed_chars, error_prompt=None, default=None):\n    p = prompt\n    while True:\n        s = raw_input(p)\n        p = prompt\n        if not s and default:\n            s = default\n        if s:\n            c = s[0].lower()\n            if c in allowed_chars:\n                break\n            if error_prompt:\n                p = '%c: %s\\n%s' % (c, error_prompt, prompt)\n    return c\n\n\ndef extract_by_key(d, keys):\n    if isinstance(keys, string_types):\n        keys = keys.split()\n    result = {}\n    for key in keys:\n        if key in d:\n            result[key] = d[key]\n    return result\n\ndef read_exports(stream):\n    if sys.version_info[0] >= 3:\n        # needs to be a text stream\n        stream = codecs.getreader('utf-8')(stream)\n    # Try to load as JSON, falling back on legacy format\n    data = stream.read()\n    stream = StringIO(data)\n    try:\n        jdata = json.load(stream)\n        result = jdata['extensions']['python.exports']['exports']\n        for group, entries in result.items():\n            for k, v in entries.items():\n                s = '%s = %s' % (k, v)\n                entry = get_export_entry(s)\n                assert entry is not None\n                entries[k] = entry\n        return result\n    except Exception:\n        stream.seek(0, 0)\n\n    def read_stream(cp, stream):\n        if hasattr(cp, 'read_file'):\n            cp.read_file(stream)\n        else:\n            cp.readfp(stream)\n\n    cp = configparser.ConfigParser()\n    try:\n        read_stream(cp, stream)\n    except configparser.MissingSectionHeaderError:\n        stream.close()\n        data = textwrap.dedent(data)\n        stream = StringIO(data)\n        read_stream(cp, stream)\n\n    result = {}\n    for key in cp.sections():\n        result[key] = entries = {}\n        for name, value in cp.items(key):\n            s = '%s = %s' % (name, value)\n            entry = get_export_entry(s)\n            assert entry is not None\n            #entry.dist = self\n            entries[name] = entry\n    return result\n\n\ndef write_exports(exports, stream):\n    if sys.version_info[0] >= 3:\n        # needs to be a text stream\n        stream = codecs.getwriter('utf-8')(stream)\n    cp = configparser.ConfigParser()\n    for k, v in exports.items():\n        # TODO check k, v for valid values\n        cp.add_section(k)\n        for entry in v.values():\n            if entry.suffix is None:\n                s = entry.prefix\n            else:\n                s = '%s:%s' % (entry.prefix, entry.suffix)\n            if entry.flags:\n                s = '%s [%s]' % (s, ', '.join(entry.flags))\n            cp.set(k, entry.name, s)\n    cp.write(stream)\n\n\n@contextlib.contextmanager\ndef tempdir():\n    td = tempfile.mkdtemp()\n    try:\n        yield td\n    finally:\n        shutil.rmtree(td)\n\n@contextlib.contextmanager\ndef chdir(d):\n    cwd = os.getcwd()\n    try:\n        os.chdir(d)\n        yield\n    finally:\n        os.chdir(cwd)\n\n\n@contextlib.contextmanager\ndef socket_timeout(seconds=15):\n    cto = socket.getdefaulttimeout()\n    try:\n        socket.setdefaulttimeout(seconds)\n        yield\n    finally:\n        socket.setdefaulttimeout(cto)\n\n\nclass cached_property(object):\n    def __init__(self, func):\n        self.func = func\n        #for attr in ('__name__', '__module__', '__doc__'):\n        #    setattr(self, attr, getattr(func, attr, None))\n\n    def __get__(self, obj, cls=None):\n        if obj is None:\n            return self\n        value = self.func(obj)\n        object.__setattr__(obj, self.func.__name__, value)\n        #obj.__dict__[self.func.__name__] = value = self.func(obj)\n        return value\n\ndef convert_path(pathname):\n    \"\"\"Return 'pathname' as a name that will work on the native filesystem.\n\n    The path is split on '/' and put back together again using the current\n    directory separator.  Needed because filenames in the setup script are\n    always supplied in Unix style, and have to be converted to the local\n    convention before we can actually use them in the filesystem.  Raises\n    ValueError on non-Unix-ish systems if 'pathname' either starts or\n    ends with a slash.\n    \"\"\"\n    if os.sep == '/':\n        return pathname\n    if not pathname:\n        return pathname\n    if pathname[0] == '/':\n        raise ValueError(\"path '%s' cannot be absolute\" % pathname)\n    if pathname[-1] == '/':\n        raise ValueError(\"path '%s' cannot end with '/'\" % pathname)\n\n    paths = pathname.split('/')\n    while os.curdir in paths:\n        paths.remove(os.curdir)\n    if not paths:\n        return os.curdir\n    return os.path.join(*paths)\n\n\nclass FileOperator(object):\n    def __init__(self, dry_run=False):\n        self.dry_run = dry_run\n        self.ensured = set()\n        self._init_record()\n\n    def _init_record(self):\n        self.record = False\n        self.files_written = set()\n        self.dirs_created = set()\n\n    def record_as_written(self, path):\n        if self.record:\n            self.files_written.add(path)\n\n    def newer(self, source, target):\n        \"\"\"Tell if the target is newer than the source.\n\n        Returns true if 'source' exists and is more recently modified than\n        'target', or if 'source' exists and 'target' doesn't.\n\n        Returns false if both exist and 'target' is the same age or younger\n        than 'source'. Raise PackagingFileError if 'source' does not exist.\n\n        Note that this test is not very accurate: files created in the same\n        second will have the same \"age\".\n        \"\"\"\n        if not os.path.exists(source):\n            raise DistlibException(\"file '%r' does not exist\" %\n                                   os.path.abspath(source))\n        if not os.path.exists(target):\n            return True\n\n        return os.stat(source).st_mtime > os.stat(target).st_mtime\n\n    def copy_file(self, infile, outfile, check=True):\n        \"\"\"Copy a file respecting dry-run and force flags.\n        \"\"\"\n        self.ensure_dir(os.path.dirname(outfile))\n        logger.info('Copying %s to %s', infile, outfile)\n        if not self.dry_run:\n            msg = None\n            if check:\n                if os.path.islink(outfile):\n                    msg = '%s is a symlink' % outfile\n                elif os.path.exists(outfile) and not os.path.isfile(outfile):\n                    msg = '%s is a non-regular file' % outfile\n            if msg:\n                raise ValueError(msg + ' which would be overwritten')\n            shutil.copyfile(infile, outfile)\n        self.record_as_written(outfile)\n\n    def copy_stream(self, instream, outfile, encoding=None):\n        assert not os.path.isdir(outfile)\n        self.ensure_dir(os.path.dirname(outfile))\n        logger.info('Copying stream %s to %s', instream, outfile)\n        if not self.dry_run:\n            if encoding is None:\n                outstream = open(outfile, 'wb')\n            else:\n                outstream = codecs.open(outfile, 'w', encoding=encoding)\n            try:\n                shutil.copyfileobj(instream, outstream)\n            finally:\n                outstream.close()\n        self.record_as_written(outfile)\n\n    def write_binary_file(self, path, data):\n        self.ensure_dir(os.path.dirname(path))\n        if not self.dry_run:\n            if os.path.exists(path):\n                os.remove(path)\n            with open(path, 'wb') as f:\n                f.write(data)\n        self.record_as_written(path)\n\n    def write_text_file(self, path, data, encoding):\n        self.write_binary_file(path, data.encode(encoding))\n\n    def set_mode(self, bits, mask, files):\n        if os.name == 'posix' or (os.name == 'java' and os._name == 'posix'):\n            # Set the executable bits (owner, group, and world) on\n            # all the files specified.\n            for f in files:\n                if self.dry_run:\n                    logger.info(\"changing mode of %s\", f)\n                else:\n                    mode = (os.stat(f).st_mode | bits) & mask\n                    logger.info(\"changing mode of %s to %o\", f, mode)\n                    os.chmod(f, mode)\n\n    set_executable_mode = lambda s, f: s.set_mode(0o555, 0o7777, f)\n\n    def ensure_dir(self, path):\n        path = os.path.abspath(path)\n        if path not in self.ensured and not os.path.exists(path):\n            self.ensured.add(path)\n            d, f = os.path.split(path)\n            self.ensure_dir(d)\n            logger.info('Creating %s' % path)\n            if not self.dry_run:\n                os.mkdir(path)\n            if self.record:\n                self.dirs_created.add(path)\n\n    def byte_compile(self, path, optimize=False, force=False, prefix=None, hashed_invalidation=False):\n        dpath = cache_from_source(path, not optimize)\n        logger.info('Byte-compiling %s to %s', path, dpath)\n        if not self.dry_run:\n            if force or self.newer(path, dpath):\n                if not prefix:\n                    diagpath = None\n                else:\n                    assert path.startswith(prefix)\n                    diagpath = path[len(prefix):]\n            compile_kwargs = {}\n            if hashed_invalidation and hasattr(py_compile, 'PycInvalidationMode'):\n                compile_kwargs['invalidation_mode'] = py_compile.PycInvalidationMode.CHECKED_HASH\n            py_compile.compile(path, dpath, diagpath, True, **compile_kwargs)     # raise error\n        self.record_as_written(dpath)\n        return dpath\n\n    def ensure_removed(self, path):\n        if os.path.exists(path):\n            if os.path.isdir(path) and not os.path.islink(path):\n                logger.debug('Removing directory tree at %s', path)\n                if not self.dry_run:\n                    shutil.rmtree(path)\n                if self.record:\n                    if path in self.dirs_created:\n                        self.dirs_created.remove(path)\n            else:\n                if os.path.islink(path):\n                    s = 'link'\n                else:\n                    s = 'file'\n                logger.debug('Removing %s %s', s, path)\n                if not self.dry_run:\n                    os.remove(path)\n                if self.record:\n                    if path in self.files_written:\n                        self.files_written.remove(path)\n\n    def is_writable(self, path):\n        result = False\n        while not result:\n            if os.path.exists(path):\n                result = os.access(path, os.W_OK)\n                break\n            parent = os.path.dirname(path)\n            if parent == path:\n                break\n            path = parent\n        return result\n\n    def commit(self):\n        \"\"\"\n        Commit recorded changes, turn off recording, return\n        changes.\n        \"\"\"\n        assert self.record\n        result = self.files_written, self.dirs_created\n        self._init_record()\n        return result\n\n    def rollback(self):\n        if not self.dry_run:\n            for f in list(self.files_written):\n                if os.path.exists(f):\n                    os.remove(f)\n            # dirs should all be empty now, except perhaps for\n            # __pycache__ subdirs\n            # reverse so that subdirs appear before their parents\n            dirs = sorted(self.dirs_created, reverse=True)\n            for d in dirs:\n                flist = os.listdir(d)\n                if flist:\n                    assert flist == ['__pycache__']\n                    sd = os.path.join(d, flist[0])\n                    os.rmdir(sd)\n                os.rmdir(d)     # should fail if non-empty\n        self._init_record()\n\ndef resolve(module_name, dotted_path):\n    if module_name in sys.modules:\n        mod = sys.modules[module_name]\n    else:\n        mod = __import__(module_name)\n    if dotted_path is None:\n        result = mod\n    else:\n        parts = dotted_path.split('.')\n        result = getattr(mod, parts.pop(0))\n        for p in parts:\n            result = getattr(result, p)\n    return result\n\n\nclass ExportEntry(object):\n    def __init__(self, name, prefix, suffix, flags):\n        self.name = name\n        self.prefix = prefix\n        self.suffix = suffix\n        self.flags = flags\n\n    @cached_property\n    def value(self):\n        return resolve(self.prefix, self.suffix)\n\n    def __repr__(self):  # pragma: no cover\n        return '<ExportEntry %s = %s:%s %s>' % (self.name, self.prefix,\n                                                self.suffix, self.flags)\n\n    def __eq__(self, other):\n        if not isinstance(other, ExportEntry):\n            result = False\n        else:\n            result = (self.name == other.name and\n                      self.prefix == other.prefix and\n                      self.suffix == other.suffix and\n                      self.flags == other.flags)\n        return result\n\n    __hash__ = object.__hash__\n\n\nENTRY_RE = re.compile(r'''(?P<name>(\\w|[-.+])+)\n                      \\s*=\\s*(?P<callable>(\\w+)([:\\.]\\w+)*)\n                      \\s*(\\[\\s*(?P<flags>\\w+(=\\w+)?(,\\s*\\w+(=\\w+)?)*)\\s*\\])?\n                      ''', re.VERBOSE)\n\ndef get_export_entry(specification):\n    m = ENTRY_RE.search(specification)\n    if not m:\n        result = None\n        if '[' in specification or ']' in specification:\n            raise DistlibException(\"Invalid specification \"\n                                   \"'%s'\" % specification)\n    else:\n        d = m.groupdict()\n        name = d['name']\n        path = d['callable']\n        colons = path.count(':')\n        if colons == 0:\n            prefix, suffix = path, None\n        else:\n            if colons != 1:\n                raise DistlibException(\"Invalid specification \"\n                                       \"'%s'\" % specification)\n            prefix, suffix = path.split(':')\n        flags = d['flags']\n        if flags is None:\n            if '[' in specification or ']' in specification:\n                raise DistlibException(\"Invalid specification \"\n                                       \"'%s'\" % specification)\n            flags = []\n        else:\n            flags = [f.strip() for f in flags.split(',')]\n        result = ExportEntry(name, prefix, suffix, flags)\n    return result\n\n\ndef get_cache_base(suffix=None):\n    \"\"\"\n    Return the default base location for distlib caches. If the directory does\n    not exist, it is created. Use the suffix provided for the base directory,\n    and default to '.distlib' if it isn't provided.\n\n    On Windows, if LOCALAPPDATA is defined in the environment, then it is\n    assumed to be a directory, and will be the parent directory of the result.\n    On POSIX, and on Windows if LOCALAPPDATA is not defined, the user's home\n    directory - using os.expanduser('~') - will be the parent directory of\n    the result.\n\n    The result is just the directory '.distlib' in the parent directory as\n    determined above, or with the name specified with ``suffix``.\n    \"\"\"\n    if suffix is None:\n        suffix = '.distlib'\n    if os.name == 'nt' and 'LOCALAPPDATA' in os.environ:\n        result = os.path.expandvars('$localappdata')\n    else:\n        # Assume posix, or old Windows\n        result = os.path.expanduser('~')\n    # we use 'isdir' instead of 'exists', because we want to\n    # fail if there's a file with that name\n    if os.path.isdir(result):\n        usable = os.access(result, os.W_OK)\n        if not usable:\n            logger.warning('Directory exists but is not writable: %s', result)\n    else:\n        try:\n            os.makedirs(result)\n            usable = True\n        except OSError:\n            logger.warning('Unable to create %s', result, exc_info=True)\n            usable = False\n    if not usable:\n        result = tempfile.mkdtemp()\n        logger.warning('Default location unusable, using %s', result)\n    return os.path.join(result, suffix)\n\n\ndef path_to_cache_dir(path):\n    \"\"\"\n    Convert an absolute path to a directory name for use in a cache.\n\n    The algorithm used is:\n\n    #. On Windows, any ``':'`` in the drive is replaced with ``'---'``.\n    #. Any occurrence of ``os.sep`` is replaced with ``'--'``.\n    #. ``'.cache'`` is appended.\n    \"\"\"\n    d, p = os.path.splitdrive(os.path.abspath(path))\n    if d:\n        d = d.replace(':', '---')\n    p = p.replace(os.sep, '--')\n    return d + p + '.cache'\n\n\ndef ensure_slash(s):\n    if not s.endswith('/'):\n        return s + '/'\n    return s\n\n\ndef parse_credentials(netloc):\n    username = password = None\n    if '@' in netloc:\n        prefix, netloc = netloc.split('@', 1)\n        if ':' not in prefix:\n            username = prefix\n        else:\n            username, password = prefix.split(':', 1)\n    return username, password, netloc\n\n\ndef get_process_umask():\n    result = os.umask(0o22)\n    os.umask(result)\n    return result\n\ndef is_string_sequence(seq):\n    result = True\n    i = None\n    for i, s in enumerate(seq):\n        if not isinstance(s, string_types):\n            result = False\n            break\n    assert i is not None\n    return result\n\nPROJECT_NAME_AND_VERSION = re.compile('([a-z0-9_]+([.-][a-z_][a-z0-9_]*)*)-'\n                                      '([a-z0-9_.+-]+)', re.I)\nPYTHON_VERSION = re.compile(r'-py(\\d\\.?\\d?)')\n\n\ndef split_filename(filename, project_name=None):\n    \"\"\"\n    Extract name, version, python version from a filename (no extension)\n\n    Return name, version, pyver or None\n    \"\"\"\n    result = None\n    pyver = None\n    filename = unquote(filename).replace(' ', '-')\n    m = PYTHON_VERSION.search(filename)\n    if m:\n        pyver = m.group(1)\n        filename = filename[:m.start()]\n    if project_name and len(filename) > len(project_name) + 1:\n        m = re.match(re.escape(project_name) + r'\\b', filename)\n        if m:\n            n = m.end()\n            result = filename[:n], filename[n + 1:], pyver\n    if result is None:\n        m = PROJECT_NAME_AND_VERSION.match(filename)\n        if m:\n            result = m.group(1), m.group(3), pyver\n    return result\n\n# Allow spaces in name because of legacy dists like \"Twisted Core\"\nNAME_VERSION_RE = re.compile(r'(?P<name>[\\w .-]+)\\s*'\n                             r'\\(\\s*(?P<ver>[^\\s)]+)\\)$')\n\ndef parse_name_and_version(p):\n    \"\"\"\n    A utility method used to get name and version from a string.\n\n    From e.g. a Provides-Dist value.\n\n    :param p: A value in a form 'foo (1.0)'\n    :return: The name and version as a tuple.\n    \"\"\"\n    m = NAME_VERSION_RE.match(p)\n    if not m:\n        raise DistlibException('Ill-formed name/version string: \\'%s\\'' % p)\n    d = m.groupdict()\n    return d['name'].strip().lower(), d['ver']\n\ndef get_extras(requested, available):\n    result = set()\n    requested = set(requested or [])\n    available = set(available or [])\n    if '*' in requested:\n        requested.remove('*')\n        result |= available\n    for r in requested:\n        if r == '-':\n            result.add(r)\n        elif r.startswith('-'):\n            unwanted = r[1:]\n            if unwanted not in available:\n                logger.warning('undeclared extra: %s' % unwanted)\n            if unwanted in result:\n                result.remove(unwanted)\n        else:\n            if r not in available:\n                logger.warning('undeclared extra: %s' % r)\n            result.add(r)\n    return result\n#\n# Extended metadata functionality\n#\n\ndef _get_external_data(url):\n    result = {}\n    try:\n        # urlopen might fail if it runs into redirections,\n        # because of Python issue #13696. Fixed in locators\n        # using a custom redirect handler.\n        resp = urlopen(url)\n        headers = resp.info()\n        ct = headers.get('Content-Type')\n        if not ct.startswith('application/json'):\n            logger.debug('Unexpected response for JSON request: %s', ct)\n        else:\n            reader = codecs.getreader('utf-8')(resp)\n            #data = reader.read().decode('utf-8')\n            #result = json.loads(data)\n            result = json.load(reader)\n    except Exception as e:\n        logger.exception('Failed to get external data for %s: %s', url, e)\n    return result\n\n_external_data_base_url = 'https://www.red-dove.com/pypi/projects/'\n\ndef get_project_data(name):\n    url = '%s/%s/project.json' % (name[0].upper(), name)\n    url = urljoin(_external_data_base_url, url)\n    result = _get_external_data(url)\n    return result\n\ndef get_package_data(name, version):\n    url = '%s/%s/package-%s.json' % (name[0].upper(), name, version)\n    url = urljoin(_external_data_base_url, url)\n    return _get_external_data(url)\n\n\nclass Cache(object):\n    \"\"\"\n    A class implementing a cache for resources that need to live in the file system\n    e.g. shared libraries. This class was moved from resources to here because it\n    could be used by other modules, e.g. the wheel module.\n    \"\"\"\n\n    def __init__(self, base):\n        \"\"\"\n        Initialise an instance.\n\n        :param base: The base directory where the cache should be located.\n        \"\"\"\n        # we use 'isdir' instead of 'exists', because we want to\n        # fail if there's a file with that name\n        if not os.path.isdir(base):  # pragma: no cover\n            os.makedirs(base)\n        if (os.stat(base).st_mode & 0o77) != 0:\n            logger.warning('Directory \\'%s\\' is not private', base)\n        self.base = os.path.abspath(os.path.normpath(base))\n\n    def prefix_to_dir(self, prefix):\n        \"\"\"\n        Converts a resource prefix to a directory name in the cache.\n        \"\"\"\n        return path_to_cache_dir(prefix)\n\n    def clear(self):\n        \"\"\"\n        Clear the cache.\n        \"\"\"\n        not_removed = []\n        for fn in os.listdir(self.base):\n            fn = os.path.join(self.base, fn)\n            try:\n                if os.path.islink(fn) or os.path.isfile(fn):\n                    os.remove(fn)\n                elif os.path.isdir(fn):\n                    shutil.rmtree(fn)\n            except Exception:\n                not_removed.append(fn)\n        return not_removed\n\n\nclass EventMixin(object):\n    \"\"\"\n    A very simple publish/subscribe system.\n    \"\"\"\n    def __init__(self):\n        self._subscribers = {}\n\n    def add(self, event, subscriber, append=True):\n        \"\"\"\n        Add a subscriber for an event.\n\n        :param event: The name of an event.\n        :param subscriber: The subscriber to be added (and called when the\n                           event is published).\n        :param append: Whether to append or prepend the subscriber to an\n                       existing subscriber list for the event.\n        \"\"\"\n        subs = self._subscribers\n        if event not in subs:\n            subs[event] = deque([subscriber])\n        else:\n            sq = subs[event]\n            if append:\n                sq.append(subscriber)\n            else:\n                sq.appendleft(subscriber)\n\n    def remove(self, event, subscriber):\n        \"\"\"\n        Remove a subscriber for an event.\n\n        :param event: The name of an event.\n        :param subscriber: The subscriber to be removed.\n        \"\"\"\n        subs = self._subscribers\n        if event not in subs:\n            raise ValueError('No subscribers: %r' % event)\n        subs[event].remove(subscriber)\n\n    def get_subscribers(self, event):\n        \"\"\"\n        Return an iterator for the subscribers for an event.\n        :param event: The event to return subscribers for.\n        \"\"\"\n        return iter(self._subscribers.get(event, ()))\n\n    def publish(self, event, *args, **kwargs):\n        \"\"\"\n        Publish a event and return a list of values returned by its\n        subscribers.\n\n        :param event: The event to publish.\n        :param args: The positional arguments to pass to the event's\n                     subscribers.\n        :param kwargs: The keyword arguments to pass to the event's\n                       subscribers.\n        \"\"\"\n        result = []\n        for subscriber in self.get_subscribers(event):\n            try:\n                value = subscriber(event, *args, **kwargs)\n            except Exception:\n                logger.exception('Exception during event publication')\n                value = None\n            result.append(value)\n        logger.debug('publish %s: args = %s, kwargs = %s, result = %s',\n                     event, args, kwargs, result)\n        return result\n\n#\n# Simple sequencing\n#\nclass Sequencer(object):\n    def __init__(self):\n        self._preds = {}\n        self._succs = {}\n        self._nodes = set()     # nodes with no preds/succs\n\n    def add_node(self, node):\n        self._nodes.add(node)\n\n    def remove_node(self, node, edges=False):\n        if node in self._nodes:\n            self._nodes.remove(node)\n        if edges:\n            for p in set(self._preds.get(node, ())):\n                self.remove(p, node)\n            for s in set(self._succs.get(node, ())):\n                self.remove(node, s)\n            # Remove empties\n            for k, v in list(self._preds.items()):\n                if not v:\n                    del self._preds[k]\n            for k, v in list(self._succs.items()):\n                if not v:\n                    del self._succs[k]\n\n    def add(self, pred, succ):\n        assert pred != succ\n        self._preds.setdefault(succ, set()).add(pred)\n        self._succs.setdefault(pred, set()).add(succ)\n\n    def remove(self, pred, succ):\n        assert pred != succ\n        try:\n            preds = self._preds[succ]\n            succs = self._succs[pred]\n        except KeyError:  # pragma: no cover\n            raise ValueError('%r not a successor of anything' % succ)\n        try:\n            preds.remove(pred)\n            succs.remove(succ)\n        except KeyError:  # pragma: no cover\n            raise ValueError('%r not a successor of %r' % (succ, pred))\n\n    def is_step(self, step):\n        return (step in self._preds or step in self._succs or\n                step in self._nodes)\n\n    def get_steps(self, final):\n        if not self.is_step(final):\n            raise ValueError('Unknown: %r' % final)\n        result = []\n        todo = []\n        seen = set()\n        todo.append(final)\n        while todo:\n            step = todo.pop(0)\n            if step in seen:\n                # if a step was already seen,\n                # move it to the end (so it will appear earlier\n                # when reversed on return) ... but not for the\n                # final step, as that would be confusing for\n                # users\n                if step != final:\n                    result.remove(step)\n                    result.append(step)\n            else:\n                seen.add(step)\n                result.append(step)\n                preds = self._preds.get(step, ())\n                todo.extend(preds)\n        return reversed(result)\n\n    @property\n    def strong_connections(self):\n        #http://en.wikipedia.org/wiki/Tarjan%27s_strongly_connected_components_algorithm\n        index_counter = [0]\n        stack = []\n        lowlinks = {}\n        index = {}\n        result = []\n\n        graph = self._succs\n\n        def strongconnect(node):\n            # set the depth index for this node to the smallest unused index\n            index[node] = index_counter[0]\n            lowlinks[node] = index_counter[0]\n            index_counter[0] += 1\n            stack.append(node)\n\n            # Consider successors\n            try:\n                successors = graph[node]\n            except Exception:\n                successors = []\n            for successor in successors:\n                if successor not in lowlinks:\n                    # Successor has not yet been visited\n                    strongconnect(successor)\n                    lowlinks[node] = min(lowlinks[node],lowlinks[successor])\n                elif successor in stack:\n                    # the successor is in the stack and hence in the current\n                    # strongly connected component (SCC)\n                    lowlinks[node] = min(lowlinks[node],index[successor])\n\n            # If `node` is a root node, pop the stack and generate an SCC\n            if lowlinks[node] == index[node]:\n                connected_component = []\n\n                while True:\n                    successor = stack.pop()\n                    connected_component.append(successor)\n                    if successor == node: break\n                component = tuple(connected_component)\n                # storing the result\n                result.append(component)\n\n        for node in graph:\n            if node not in lowlinks:\n                strongconnect(node)\n\n        return result\n\n    @property\n    def dot(self):\n        result = ['digraph G {']\n        for succ in self._preds:\n            preds = self._preds[succ]\n            for pred in preds:\n                result.append('  %s -> %s;' % (pred, succ))\n        for node in self._nodes:\n            result.append('  %s;' % node)\n        result.append('}')\n        return '\\n'.join(result)\n\n#\n# Unarchiving functionality for zip, tar, tgz, tbz, whl\n#\n\nARCHIVE_EXTENSIONS = ('.tar.gz', '.tar.bz2', '.tar', '.zip',\n                      '.tgz', '.tbz', '.whl')\n\ndef unarchive(archive_filename, dest_dir, format=None, check=True):\n\n    def check_path(path):\n        if not isinstance(path, text_type):\n            path = path.decode('utf-8')\n        p = os.path.abspath(os.path.join(dest_dir, path))\n        if not p.startswith(dest_dir) or p[plen] != os.sep:\n            raise ValueError('path outside destination: %r' % p)\n\n    dest_dir = os.path.abspath(dest_dir)\n    plen = len(dest_dir)\n    archive = None\n    if format is None:\n        if archive_filename.endswith(('.zip', '.whl')):\n            format = 'zip'\n        elif archive_filename.endswith(('.tar.gz', '.tgz')):\n            format = 'tgz'\n            mode = 'r:gz'\n        elif archive_filename.endswith(('.tar.bz2', '.tbz')):\n            format = 'tbz'\n            mode = 'r:bz2'\n        elif archive_filename.endswith('.tar'):\n            format = 'tar'\n            mode = 'r'\n        else:  # pragma: no cover\n            raise ValueError('Unknown format for %r' % archive_filename)\n    try:\n        if format == 'zip':\n            archive = ZipFile(archive_filename, 'r')\n            if check:\n                names = archive.namelist()\n                for name in names:\n                    check_path(name)\n        else:\n            archive = tarfile.open(archive_filename, mode)\n            if check:\n                names = archive.getnames()\n                for name in names:\n                    check_path(name)\n        if format != 'zip' and sys.version_info[0] < 3:\n            # See Python issue 17153. If the dest path contains Unicode,\n            # tarfile extraction fails on Python 2.x if a member path name\n            # contains non-ASCII characters - it leads to an implicit\n            # bytes -> unicode conversion using ASCII to decode.\n            for tarinfo in archive.getmembers():\n                if not isinstance(tarinfo.name, text_type):\n                    tarinfo.name = tarinfo.name.decode('utf-8')\n        archive.extractall(dest_dir)\n\n    finally:\n        if archive:\n            archive.close()\n\n\ndef zip_dir(directory):\n    \"\"\"zip a directory tree into a BytesIO object\"\"\"\n    result = io.BytesIO()\n    dlen = len(directory)\n    with ZipFile(result, \"w\") as zf:\n        for root, dirs, files in os.walk(directory):\n            for name in files:\n                full = os.path.join(root, name)\n                rel = root[dlen:]\n                dest = os.path.join(rel, name)\n                zf.write(full, dest)\n    return result\n\n#\n# Simple progress bar\n#\n\nUNITS = ('', 'K', 'M', 'G','T','P')\n\n\nclass Progress(object):\n    unknown = 'UNKNOWN'\n\n    def __init__(self, minval=0, maxval=100):\n        assert maxval is None or maxval >= minval\n        self.min = self.cur = minval\n        self.max = maxval\n        self.started = None\n        self.elapsed = 0\n        self.done = False\n\n    def update(self, curval):\n        assert self.min <= curval\n        assert self.max is None or curval <= self.max\n        self.cur = curval\n        now = time.time()\n        if self.started is None:\n            self.started = now\n        else:\n            self.elapsed = now - self.started\n\n    def increment(self, incr):\n        assert incr >= 0\n        self.update(self.cur + incr)\n\n    def start(self):\n        self.update(self.min)\n        return self\n\n    def stop(self):\n        if self.max is not None:\n            self.update(self.max)\n        self.done = True\n\n    @property\n    def maximum(self):\n        return self.unknown if self.max is None else self.max\n\n    @property\n    def percentage(self):\n        if self.done:\n            result = '100 %'\n        elif self.max is None:\n            result = ' ?? %'\n        else:\n            v = 100.0 * (self.cur - self.min) / (self.max - self.min)\n            result = '%3d %%' % v\n        return result\n\n    def format_duration(self, duration):\n        if (duration <= 0) and self.max is None or self.cur == self.min:\n            result = '??:??:??'\n        #elif duration < 1:\n        #    result = '--:--:--'\n        else:\n            result = time.strftime('%H:%M:%S', time.gmtime(duration))\n        return result\n\n    @property\n    def ETA(self):\n        if self.done:\n            prefix = 'Done'\n            t = self.elapsed\n            #import pdb; pdb.set_trace()\n        else:\n            prefix = 'ETA '\n            if self.max is None:\n                t = -1\n            elif self.elapsed == 0 or (self.cur == self.min):\n                t = 0\n            else:\n                #import pdb; pdb.set_trace()\n                t = float(self.max - self.min)\n                t /= self.cur - self.min\n                t = (t - 1) * self.elapsed\n        return '%s: %s' % (prefix, self.format_duration(t))\n\n    @property\n    def speed(self):\n        if self.elapsed == 0:\n            result = 0.0\n        else:\n            result = (self.cur - self.min) / self.elapsed\n        for unit in UNITS:\n            if result < 1000:\n                break\n            result /= 1000.0\n        return '%d %sB/s' % (result, unit)\n\n#\n# Glob functionality\n#\n\nRICH_GLOB = re.compile(r'\\{([^}]*)\\}')\n_CHECK_RECURSIVE_GLOB = re.compile(r'[^/\\\\,{]\\*\\*|\\*\\*[^/\\\\,}]')\n_CHECK_MISMATCH_SET = re.compile(r'^[^{]*\\}|\\{[^}]*$')\n\n\ndef iglob(path_glob):\n    \"\"\"Extended globbing function that supports ** and {opt1,opt2,opt3}.\"\"\"\n    if _CHECK_RECURSIVE_GLOB.search(path_glob):\n        msg = \"\"\"invalid glob %r: recursive glob \"**\" must be used alone\"\"\"\n        raise ValueError(msg % path_glob)\n    if _CHECK_MISMATCH_SET.search(path_glob):\n        msg = \"\"\"invalid glob %r: mismatching set marker '{' or '}'\"\"\"\n        raise ValueError(msg % path_glob)\n    return _iglob(path_glob)\n\n\ndef _iglob(path_glob):\n    rich_path_glob = RICH_GLOB.split(path_glob, 1)\n    if len(rich_path_glob) > 1:\n        assert len(rich_path_glob) == 3, rich_path_glob\n        prefix, set, suffix = rich_path_glob\n        for item in set.split(','):\n            for path in _iglob(''.join((prefix, item, suffix))):\n                yield path\n    else:\n        if '**' not in path_glob:\n            for item in std_iglob(path_glob):\n                yield item\n        else:\n            prefix, radical = path_glob.split('**', 1)\n            if prefix == '':\n                prefix = '.'\n            if radical == '':\n                radical = '*'\n            else:\n                # we support both\n                radical = radical.lstrip('/')\n                radical = radical.lstrip('\\\\')\n            for path, dir, files in os.walk(prefix):\n                path = os.path.normpath(path)\n                for fn in _iglob(os.path.join(path, radical)):\n                    yield fn\n\nif ssl:\n    from .compat import (HTTPSHandler as BaseHTTPSHandler, match_hostname,\n                         CertificateError)\n\n\n#\n# HTTPSConnection which verifies certificates/matches domains\n#\n\n    class HTTPSConnection(httplib.HTTPSConnection):\n        ca_certs = None # set this to the path to the certs file (.pem)\n        check_domain = True # only used if ca_certs is not None\n\n        # noinspection PyPropertyAccess\n        def connect(self):\n            sock = socket.create_connection((self.host, self.port), self.timeout)\n            if getattr(self, '_tunnel_host', False):\n                self.sock = sock\n                self._tunnel()\n\n            if not hasattr(ssl, 'SSLContext'):\n                # For 2.x\n                if self.ca_certs:\n                    cert_reqs = ssl.CERT_REQUIRED\n                else:\n                    cert_reqs = ssl.CERT_NONE\n                self.sock = ssl.wrap_socket(sock, self.key_file, self.cert_file,\n                                            cert_reqs=cert_reqs,\n                                            ssl_version=ssl.PROTOCOL_SSLv23,\n                                            ca_certs=self.ca_certs)\n            else:  # pragma: no cover\n                context = ssl.SSLContext(ssl.PROTOCOL_SSLv23)\n                context.options |= ssl.OP_NO_SSLv2\n                if self.cert_file:\n                    context.load_cert_chain(self.cert_file, self.key_file)\n                kwargs = {}\n                if self.ca_certs:\n                    context.verify_mode = ssl.CERT_REQUIRED\n                    context.load_verify_locations(cafile=self.ca_certs)\n                    if getattr(ssl, 'HAS_SNI', False):\n                        kwargs['server_hostname'] = self.host\n                self.sock = context.wrap_socket(sock, **kwargs)\n            if self.ca_certs and self.check_domain:\n                try:\n                    match_hostname(self.sock.getpeercert(), self.host)\n                    logger.debug('Host verified: %s', self.host)\n                except CertificateError:  # pragma: no cover\n                    self.sock.shutdown(socket.SHUT_RDWR)\n                    self.sock.close()\n                    raise\n\n    class HTTPSHandler(BaseHTTPSHandler):\n        def __init__(self, ca_certs, check_domain=True):\n            BaseHTTPSHandler.__init__(self)\n            self.ca_certs = ca_certs\n            self.check_domain = check_domain\n\n        def _conn_maker(self, *args, **kwargs):\n            \"\"\"\n            This is called to create a connection instance. Normally you'd\n            pass a connection class to do_open, but it doesn't actually check for\n            a class, and just expects a callable. As long as we behave just as a\n            constructor would have, we should be OK. If it ever changes so that\n            we *must* pass a class, we'll create an UnsafeHTTPSConnection class\n            which just sets check_domain to False in the class definition, and\n            choose which one to pass to do_open.\n            \"\"\"\n            result = HTTPSConnection(*args, **kwargs)\n            if self.ca_certs:\n                result.ca_certs = self.ca_certs\n                result.check_domain = self.check_domain\n            return result\n\n        def https_open(self, req):\n            try:\n                return self.do_open(self._conn_maker, req)\n            except URLError as e:\n                if 'certificate verify failed' in str(e.reason):\n                    raise CertificateError('Unable to verify server certificate '\n                                           'for %s' % req.host)\n                else:\n                    raise\n\n    #\n    # To prevent against mixing HTTP traffic with HTTPS (examples: A Man-In-The-\n    # Middle proxy using HTTP listens on port 443, or an index mistakenly serves\n    # HTML containing a http://xyz link when it should be https://xyz),\n    # you can use the following handler class, which does not allow HTTP traffic.\n    #\n    # It works by inheriting from HTTPHandler - so build_opener won't add a\n    # handler for HTTP itself.\n    #\n    class HTTPSOnlyHandler(HTTPSHandler, HTTPHandler):\n        def http_open(self, req):\n            raise URLError('Unexpected HTTP request on what should be a secure '\n                           'connection: %s' % req)\n\n#\n# XML-RPC with timeouts\n#\n\n_ver_info = sys.version_info[:2]\n\nif _ver_info == (2, 6):\n    class HTTP(httplib.HTTP):\n        def __init__(self, host='', port=None, **kwargs):\n            if port == 0:   # 0 means use port 0, not the default port\n                port = None\n            self._setup(self._connection_class(host, port, **kwargs))\n\n\n    if ssl:\n        class HTTPS(httplib.HTTPS):\n            def __init__(self, host='', port=None, **kwargs):\n                if port == 0:   # 0 means use port 0, not the default port\n                    port = None\n                self._setup(self._connection_class(host, port, **kwargs))\n\n\nclass Transport(xmlrpclib.Transport):\n    def __init__(self, timeout, use_datetime=0):\n        self.timeout = timeout\n        xmlrpclib.Transport.__init__(self, use_datetime)\n\n    def make_connection(self, host):\n        h, eh, x509 = self.get_host_info(host)\n        if _ver_info == (2, 6):\n            result = HTTP(h, timeout=self.timeout)\n        else:\n            if not self._connection or host != self._connection[0]:\n                self._extra_headers = eh\n                self._connection = host, httplib.HTTPConnection(h)\n            result = self._connection[1]\n        return result\n\nif ssl:\n    class SafeTransport(xmlrpclib.SafeTransport):\n        def __init__(self, timeout, use_datetime=0):\n            self.timeout = timeout\n            xmlrpclib.SafeTransport.__init__(self, use_datetime)\n\n        def make_connection(self, host):\n            h, eh, kwargs = self.get_host_info(host)\n            if not kwargs:\n                kwargs = {}\n            kwargs['timeout'] = self.timeout\n            if _ver_info == (2, 6):\n                result = HTTPS(host, None, **kwargs)\n            else:\n                if not self._connection or host != self._connection[0]:\n                    self._extra_headers = eh\n                    self._connection = host, httplib.HTTPSConnection(h, None,\n                                                                     **kwargs)\n                result = self._connection[1]\n            return result\n\n\nclass ServerProxy(xmlrpclib.ServerProxy):\n    def __init__(self, uri, **kwargs):\n        self.timeout = timeout = kwargs.pop('timeout', None)\n        # The above classes only come into play if a timeout\n        # is specified\n        if timeout is not None:\n            scheme, _ = splittype(uri)\n            use_datetime = kwargs.get('use_datetime', 0)\n            if scheme == 'https':\n                tcls = SafeTransport\n            else:\n                tcls = Transport\n            kwargs['transport'] = t = tcls(timeout, use_datetime=use_datetime)\n            self.transport = t\n        xmlrpclib.ServerProxy.__init__(self, uri, **kwargs)\n\n#\n# CSV functionality. This is provided because on 2.x, the csv module can't\n# handle Unicode. However, we need to deal with Unicode in e.g. RECORD files.\n#\n\ndef _csv_open(fn, mode, **kwargs):\n    if sys.version_info[0] < 3:\n        mode += 'b'\n    else:\n        kwargs['newline'] = ''\n        # Python 3 determines encoding from locale. Force 'utf-8'\n        # file encoding to match other forced utf-8 encoding\n        kwargs['encoding'] = 'utf-8'\n    return open(fn, mode, **kwargs)\n\n\nclass CSVBase(object):\n    defaults = {\n        'delimiter': str(','),      # The strs are used because we need native\n        'quotechar': str('\"'),      # str in the csv API (2.x won't take\n        'lineterminator': str('\\n') # Unicode)\n    }\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, *exc_info):\n        self.stream.close()\n\n\nclass CSVReader(CSVBase):\n    def __init__(self, **kwargs):\n        if 'stream' in kwargs:\n            stream = kwargs['stream']\n            if sys.version_info[0] >= 3:\n                # needs to be a text stream\n                stream = codecs.getreader('utf-8')(stream)\n            self.stream = stream\n        else:\n            self.stream = _csv_open(kwargs['path'], 'r')\n        self.reader = csv.reader(self.stream, **self.defaults)\n\n    def __iter__(self):\n        return self\n\n    def next(self):\n        result = next(self.reader)\n        if sys.version_info[0] < 3:\n            for i, item in enumerate(result):\n                if not isinstance(item, text_type):\n                    result[i] = item.decode('utf-8')\n        return result\n\n    __next__ = next\n\nclass CSVWriter(CSVBase):\n    def __init__(self, fn, **kwargs):\n        self.stream = _csv_open(fn, 'w')\n        self.writer = csv.writer(self.stream, **self.defaults)\n\n    def writerow(self, row):\n        if sys.version_info[0] < 3:\n            r = []\n            for item in row:\n                if isinstance(item, text_type):\n                    item = item.encode('utf-8')\n                r.append(item)\n            row = r\n        self.writer.writerow(row)\n\n#\n#   Configurator functionality\n#\n\nclass Configurator(BaseConfigurator):\n\n    value_converters = dict(BaseConfigurator.value_converters)\n    value_converters['inc'] = 'inc_convert'\n\n    def __init__(self, config, base=None):\n        super(Configurator, self).__init__(config)\n        self.base = base or os.getcwd()\n\n    def configure_custom(self, config):\n        def convert(o):\n            if isinstance(o, (list, tuple)):\n                result = type(o)([convert(i) for i in o])\n            elif isinstance(o, dict):\n                if '()' in o:\n                    result = self.configure_custom(o)\n                else:\n                    result = {}\n                    for k in o:\n                        result[k] = convert(o[k])\n            else:\n                result = self.convert(o)\n            return result\n\n        c = config.pop('()')\n        if not callable(c):\n            c = self.resolve(c)\n        props = config.pop('.', None)\n        # Check for valid identifiers\n        args = config.pop('[]', ())\n        if args:\n            args = tuple([convert(o) for o in args])\n        items = [(k, convert(config[k])) for k in config if valid_ident(k)]\n        kwargs = dict(items)\n        result = c(*args, **kwargs)\n        if props:\n            for n, v in props.items():\n                setattr(result, n, convert(v))\n        return result\n\n    def __getitem__(self, key):\n        result = self.config[key]\n        if isinstance(result, dict) and '()' in result:\n            self.config[key] = result = self.configure_custom(result)\n        return result\n\n    def inc_convert(self, value):\n        \"\"\"Default converter for the inc:// protocol.\"\"\"\n        if not os.path.isabs(value):\n            value = os.path.join(self.base, value)\n        with codecs.open(value, 'r', encoding='utf-8') as f:\n            result = json.load(f)\n        return result\n\n\nclass SubprocessMixin(object):\n    \"\"\"\n    Mixin for running subprocesses and capturing their output\n    \"\"\"\n    def __init__(self, verbose=False, progress=None):\n        self.verbose = verbose\n        self.progress = progress\n\n    def reader(self, stream, context):\n        \"\"\"\n        Read lines from a subprocess' output stream and either pass to a progress\n        callable (if specified) or write progress information to sys.stderr.\n        \"\"\"\n        progress = self.progress\n        verbose = self.verbose\n        while True:\n            s = stream.readline()\n            if not s:\n                break\n            if progress is not None:\n                progress(s, context)\n            else:\n                if not verbose:\n                    sys.stderr.write('.')\n                else:\n                    sys.stderr.write(s.decode('utf-8'))\n                sys.stderr.flush()\n        stream.close()\n\n    def run_command(self, cmd, **kwargs):\n        p = subprocess.Popen(cmd, stdout=subprocess.PIPE,\n                             stderr=subprocess.PIPE, **kwargs)\n        t1 = threading.Thread(target=self.reader, args=(p.stdout, 'stdout'))\n        t1.start()\n        t2 = threading.Thread(target=self.reader, args=(p.stderr, 'stderr'))\n        t2.start()\n        p.wait()\n        t1.join()\n        t2.join()\n        if self.progress is not None:\n            self.progress('done.', 'main')\n        elif self.verbose:\n            sys.stderr.write('done.\\n')\n        return p\n\n\ndef normalize_name(name):\n    \"\"\"Normalize a python package name a la PEP 503\"\"\"\n    # https://www.python.org/dev/peps/pep-0503/#normalized-names\n    return re.sub('[-_.]+', '-', name).lower()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/version.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2012-2017 The Python Software Foundation.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\n\"\"\"\nImplementation of a flexible versioning scheme providing support for PEP-440,\nsetuptools-compatible and semantic versioning.\n\"\"\"\n\nimport logging\nimport re\n\nfrom .compat import string_types\nfrom .util import parse_requirement\n\n__all__ = ['NormalizedVersion', 'NormalizedMatcher',\n           'LegacyVersion', 'LegacyMatcher',\n           'SemanticVersion', 'SemanticMatcher',\n           'UnsupportedVersionError', 'get_scheme']\n\nlogger = logging.getLogger(__name__)\n\n\nclass UnsupportedVersionError(ValueError):\n    \"\"\"This is an unsupported version.\"\"\"\n    pass\n\n\nclass Version(object):\n    def __init__(self, s):\n        self._string = s = s.strip()\n        self._parts = parts = self.parse(s)\n        assert isinstance(parts, tuple)\n        assert len(parts) > 0\n\n    def parse(self, s):\n        raise NotImplementedError('please implement in a subclass')\n\n    def _check_compatible(self, other):\n        if type(self) != type(other):\n            raise TypeError('cannot compare %r and %r' % (self, other))\n\n    def __eq__(self, other):\n        self._check_compatible(other)\n        return self._parts == other._parts\n\n    def __ne__(self, other):\n        return not self.__eq__(other)\n\n    def __lt__(self, other):\n        self._check_compatible(other)\n        return self._parts < other._parts\n\n    def __gt__(self, other):\n        return not (self.__lt__(other) or self.__eq__(other))\n\n    def __le__(self, other):\n        return self.__lt__(other) or self.__eq__(other)\n\n    def __ge__(self, other):\n        return self.__gt__(other) or self.__eq__(other)\n\n    # See http://docs.python.org/reference/datamodel#object.__hash__\n    def __hash__(self):\n        return hash(self._parts)\n\n    def __repr__(self):\n        return \"%s('%s')\" % (self.__class__.__name__, self._string)\n\n    def __str__(self):\n        return self._string\n\n    @property\n    def is_prerelease(self):\n        raise NotImplementedError('Please implement in subclasses.')\n\n\nclass Matcher(object):\n    version_class = None\n\n    # value is either a callable or the name of a method\n    _operators = {\n        '<': lambda v, c, p: v < c,\n        '>': lambda v, c, p: v > c,\n        '<=': lambda v, c, p: v == c or v < c,\n        '>=': lambda v, c, p: v == c or v > c,\n        '==': lambda v, c, p: v == c,\n        '===': lambda v, c, p: v == c,\n        # by default, compatible => >=.\n        '~=': lambda v, c, p: v == c or v > c,\n        '!=': lambda v, c, p: v != c,\n    }\n\n    # this is a method only to support alternative implementations\n    # via overriding\n    def parse_requirement(self, s):\n        return parse_requirement(s)\n\n    def __init__(self, s):\n        if self.version_class is None:\n            raise ValueError('Please specify a version class')\n        self._string = s = s.strip()\n        r = self.parse_requirement(s)\n        if not r:\n            raise ValueError('Not valid: %r' % s)\n        self.name = r.name\n        self.key = self.name.lower()    # for case-insensitive comparisons\n        clist = []\n        if r.constraints:\n            # import pdb; pdb.set_trace()\n            for op, s in r.constraints:\n                if s.endswith('.*'):\n                    if op not in ('==', '!='):\n                        raise ValueError('\\'.*\\' not allowed for '\n                                         '%r constraints' % op)\n                    # Could be a partial version (e.g. for '2.*') which\n                    # won't parse as a version, so keep it as a string\n                    vn, prefix = s[:-2], True\n                    # Just to check that vn is a valid version\n                    self.version_class(vn)\n                else:\n                    # Should parse as a version, so we can create an\n                    # instance for the comparison\n                    vn, prefix = self.version_class(s), False\n                clist.append((op, vn, prefix))\n        self._parts = tuple(clist)\n\n    def match(self, version):\n        \"\"\"\n        Check if the provided version matches the constraints.\n\n        :param version: The version to match against this instance.\n        :type version: String or :class:`Version` instance.\n        \"\"\"\n        if isinstance(version, string_types):\n            version = self.version_class(version)\n        for operator, constraint, prefix in self._parts:\n            f = self._operators.get(operator)\n            if isinstance(f, string_types):\n                f = getattr(self, f)\n            if not f:\n                msg = ('%r not implemented '\n                       'for %s' % (operator, self.__class__.__name__))\n                raise NotImplementedError(msg)\n            if not f(version, constraint, prefix):\n                return False\n        return True\n\n    @property\n    def exact_version(self):\n        result = None\n        if len(self._parts) == 1 and self._parts[0][0] in ('==', '==='):\n            result = self._parts[0][1]\n        return result\n\n    def _check_compatible(self, other):\n        if type(self) != type(other) or self.name != other.name:\n            raise TypeError('cannot compare %s and %s' % (self, other))\n\n    def __eq__(self, other):\n        self._check_compatible(other)\n        return self.key == other.key and self._parts == other._parts\n\n    def __ne__(self, other):\n        return not self.__eq__(other)\n\n    # See http://docs.python.org/reference/datamodel#object.__hash__\n    def __hash__(self):\n        return hash(self.key) + hash(self._parts)\n\n    def __repr__(self):\n        return \"%s(%r)\" % (self.__class__.__name__, self._string)\n\n    def __str__(self):\n        return self._string\n\n\nPEP440_VERSION_RE = re.compile(r'^v?(\\d+!)?(\\d+(\\.\\d+)*)((a|b|c|rc)(\\d+))?'\n                               r'(\\.(post)(\\d+))?(\\.(dev)(\\d+))?'\n                               r'(\\+([a-zA-Z\\d]+(\\.[a-zA-Z\\d]+)?))?$')\n\n\ndef _pep_440_key(s):\n    s = s.strip()\n    m = PEP440_VERSION_RE.match(s)\n    if not m:\n        raise UnsupportedVersionError('Not a valid version: %s' % s)\n    groups = m.groups()\n    nums = tuple(int(v) for v in groups[1].split('.'))\n    while len(nums) > 1 and nums[-1] == 0:\n        nums = nums[:-1]\n\n    if not groups[0]:\n        epoch = 0\n    else:\n        epoch = int(groups[0])\n    pre = groups[4:6]\n    post = groups[7:9]\n    dev = groups[10:12]\n    local = groups[13]\n    if pre == (None, None):\n        pre = ()\n    else:\n        pre = pre[0], int(pre[1])\n    if post == (None, None):\n        post = ()\n    else:\n        post = post[0], int(post[1])\n    if dev == (None, None):\n        dev = ()\n    else:\n        dev = dev[0], int(dev[1])\n    if local is None:\n        local = ()\n    else:\n        parts = []\n        for part in local.split('.'):\n            # to ensure that numeric compares as > lexicographic, avoid\n            # comparing them directly, but encode a tuple which ensures\n            # correct sorting\n            if part.isdigit():\n                part = (1, int(part))\n            else:\n                part = (0, part)\n            parts.append(part)\n        local = tuple(parts)\n    if not pre:\n        # either before pre-release, or final release and after\n        if not post and dev:\n            # before pre-release\n            pre = ('a', -1)     # to sort before a0\n        else:\n            pre = ('z',)        # to sort after all pre-releases\n    # now look at the state of post and dev.\n    if not post:\n        post = ('_',)   # sort before 'a'\n    if not dev:\n        dev = ('final',)\n\n    #print('%s -> %s' % (s, m.groups()))\n    return epoch, nums, pre, post, dev, local\n\n\n_normalized_key = _pep_440_key\n\n\nclass NormalizedVersion(Version):\n    \"\"\"A rational version.\n\n    Good:\n        1.2         # equivalent to \"1.2.0\"\n        1.2.0\n        1.2a1\n        1.2.3a2\n        1.2.3b1\n        1.2.3c1\n        1.2.3.4\n        TODO: fill this out\n\n    Bad:\n        1           # minimum two numbers\n        1.2a        # release level must have a release serial\n        1.2.3b\n    \"\"\"\n    def parse(self, s):\n        result = _normalized_key(s)\n        # _normalized_key loses trailing zeroes in the release\n        # clause, since that's needed to ensure that X.Y == X.Y.0 == X.Y.0.0\n        # However, PEP 440 prefix matching needs it: for example,\n        # (~= 1.4.5.0) matches differently to (~= 1.4.5.0.0).\n        m = PEP440_VERSION_RE.match(s)      # must succeed\n        groups = m.groups()\n        self._release_clause = tuple(int(v) for v in groups[1].split('.'))\n        return result\n\n    PREREL_TAGS = set(['a', 'b', 'c', 'rc', 'dev'])\n\n    @property\n    def is_prerelease(self):\n        return any(t[0] in self.PREREL_TAGS for t in self._parts if t)\n\n\ndef _match_prefix(x, y):\n    x = str(x)\n    y = str(y)\n    if x == y:\n        return True\n    if not x.startswith(y):\n        return False\n    n = len(y)\n    return x[n] == '.'\n\n\nclass NormalizedMatcher(Matcher):\n    version_class = NormalizedVersion\n\n    # value is either a callable or the name of a method\n    _operators = {\n        '~=': '_match_compatible',\n        '<': '_match_lt',\n        '>': '_match_gt',\n        '<=': '_match_le',\n        '>=': '_match_ge',\n        '==': '_match_eq',\n        '===': '_match_arbitrary',\n        '!=': '_match_ne',\n    }\n\n    def _adjust_local(self, version, constraint, prefix):\n        if prefix:\n            strip_local = '+' not in constraint and version._parts[-1]\n        else:\n            # both constraint and version are\n            # NormalizedVersion instances.\n            # If constraint does not have a local component,\n            # ensure the version doesn't, either.\n            strip_local = not constraint._parts[-1] and version._parts[-1]\n        if strip_local:\n            s = version._string.split('+', 1)[0]\n            version = self.version_class(s)\n        return version, constraint\n\n    def _match_lt(self, version, constraint, prefix):\n        version, constraint = self._adjust_local(version, constraint, prefix)\n        if version >= constraint:\n            return False\n        release_clause = constraint._release_clause\n        pfx = '.'.join([str(i) for i in release_clause])\n        return not _match_prefix(version, pfx)\n\n    def _match_gt(self, version, constraint, prefix):\n        version, constraint = self._adjust_local(version, constraint, prefix)\n        if version <= constraint:\n            return False\n        release_clause = constraint._release_clause\n        pfx = '.'.join([str(i) for i in release_clause])\n        return not _match_prefix(version, pfx)\n\n    def _match_le(self, version, constraint, prefix):\n        version, constraint = self._adjust_local(version, constraint, prefix)\n        return version <= constraint\n\n    def _match_ge(self, version, constraint, prefix):\n        version, constraint = self._adjust_local(version, constraint, prefix)\n        return version >= constraint\n\n    def _match_eq(self, version, constraint, prefix):\n        version, constraint = self._adjust_local(version, constraint, prefix)\n        if not prefix:\n            result = (version == constraint)\n        else:\n            result = _match_prefix(version, constraint)\n        return result\n\n    def _match_arbitrary(self, version, constraint, prefix):\n        return str(version) == str(constraint)\n\n    def _match_ne(self, version, constraint, prefix):\n        version, constraint = self._adjust_local(version, constraint, prefix)\n        if not prefix:\n            result = (version != constraint)\n        else:\n            result = not _match_prefix(version, constraint)\n        return result\n\n    def _match_compatible(self, version, constraint, prefix):\n        version, constraint = self._adjust_local(version, constraint, prefix)\n        if version == constraint:\n            return True\n        if version < constraint:\n            return False\n#        if not prefix:\n#            return True\n        release_clause = constraint._release_clause\n        if len(release_clause) > 1:\n            release_clause = release_clause[:-1]\n        pfx = '.'.join([str(i) for i in release_clause])\n        return _match_prefix(version, pfx)\n\n_REPLACEMENTS = (\n    (re.compile('[.+-]$'), ''),                     # remove trailing puncts\n    (re.compile(r'^[.](\\d)'), r'0.\\1'),             # .N -> 0.N at start\n    (re.compile('^[.-]'), ''),                      # remove leading puncts\n    (re.compile(r'^\\((.*)\\)$'), r'\\1'),             # remove parentheses\n    (re.compile(r'^v(ersion)?\\s*(\\d+)'), r'\\2'),    # remove leading v(ersion)\n    (re.compile(r'^r(ev)?\\s*(\\d+)'), r'\\2'),        # remove leading v(ersion)\n    (re.compile('[.]{2,}'), '.'),                   # multiple runs of '.'\n    (re.compile(r'\\b(alfa|apha)\\b'), 'alpha'),      # misspelt alpha\n    (re.compile(r'\\b(pre-alpha|prealpha)\\b'),\n                'pre.alpha'),                       # standardise\n    (re.compile(r'\\(beta\\)$'), 'beta'),             # remove parentheses\n)\n\n_SUFFIX_REPLACEMENTS = (\n    (re.compile('^[:~._+-]+'), ''),                   # remove leading puncts\n    (re.compile('[,*\")([\\\\]]'), ''),                  # remove unwanted chars\n    (re.compile('[~:+_ -]'), '.'),                    # replace illegal chars\n    (re.compile('[.]{2,}'), '.'),                   # multiple runs of '.'\n    (re.compile(r'\\.$'), ''),                       # trailing '.'\n)\n\n_NUMERIC_PREFIX = re.compile(r'(\\d+(\\.\\d+)*)')\n\n\ndef _suggest_semantic_version(s):\n    \"\"\"\n    Try to suggest a semantic form for a version for which\n    _suggest_normalized_version couldn't come up with anything.\n    \"\"\"\n    result = s.strip().lower()\n    for pat, repl in _REPLACEMENTS:\n        result = pat.sub(repl, result)\n    if not result:\n        result = '0.0.0'\n\n    # Now look for numeric prefix, and separate it out from\n    # the rest.\n    #import pdb; pdb.set_trace()\n    m = _NUMERIC_PREFIX.match(result)\n    if not m:\n        prefix = '0.0.0'\n        suffix = result\n    else:\n        prefix = m.groups()[0].split('.')\n        prefix = [int(i) for i in prefix]\n        while len(prefix) < 3:\n            prefix.append(0)\n        if len(prefix) == 3:\n            suffix = result[m.end():]\n        else:\n            suffix = '.'.join([str(i) for i in prefix[3:]]) + result[m.end():]\n            prefix = prefix[:3]\n        prefix = '.'.join([str(i) for i in prefix])\n        suffix = suffix.strip()\n    if suffix:\n        #import pdb; pdb.set_trace()\n        # massage the suffix.\n        for pat, repl in _SUFFIX_REPLACEMENTS:\n            suffix = pat.sub(repl, suffix)\n\n    if not suffix:\n        result = prefix\n    else:\n        sep = '-' if 'dev' in suffix else '+'\n        result = prefix + sep + suffix\n    if not is_semver(result):\n        result = None\n    return result\n\n\ndef _suggest_normalized_version(s):\n    \"\"\"Suggest a normalized version close to the given version string.\n\n    If you have a version string that isn't rational (i.e. NormalizedVersion\n    doesn't like it) then you might be able to get an equivalent (or close)\n    rational version from this function.\n\n    This does a number of simple normalizations to the given string, based\n    on observation of versions currently in use on PyPI. Given a dump of\n    those version during PyCon 2009, 4287 of them:\n    - 2312 (53.93%) match NormalizedVersion without change\n      with the automatic suggestion\n    - 3474 (81.04%) match when using this suggestion method\n\n    @param s {str} An irrational version string.\n    @returns A rational version string, or None, if couldn't determine one.\n    \"\"\"\n    try:\n        _normalized_key(s)\n        return s   # already rational\n    except UnsupportedVersionError:\n        pass\n\n    rs = s.lower()\n\n    # part of this could use maketrans\n    for orig, repl in (('-alpha', 'a'), ('-beta', 'b'), ('alpha', 'a'),\n                       ('beta', 'b'), ('rc', 'c'), ('-final', ''),\n                       ('-pre', 'c'),\n                       ('-release', ''), ('.release', ''), ('-stable', ''),\n                       ('+', '.'), ('_', '.'), (' ', ''), ('.final', ''),\n                       ('final', '')):\n        rs = rs.replace(orig, repl)\n\n    # if something ends with dev or pre, we add a 0\n    rs = re.sub(r\"pre$\", r\"pre0\", rs)\n    rs = re.sub(r\"dev$\", r\"dev0\", rs)\n\n    # if we have something like \"b-2\" or \"a.2\" at the end of the\n    # version, that is probably beta, alpha, etc\n    # let's remove the dash or dot\n    rs = re.sub(r\"([abc]|rc)[\\-\\.](\\d+)$\", r\"\\1\\2\", rs)\n\n    # 1.0-dev-r371 -> 1.0.dev371\n    # 0.1-dev-r79 -> 0.1.dev79\n    rs = re.sub(r\"[\\-\\.](dev)[\\-\\.]?r?(\\d+)$\", r\".\\1\\2\", rs)\n\n    # Clean: 2.0.a.3, 2.0.b1, 0.9.0~c1\n    rs = re.sub(r\"[.~]?([abc])\\.?\", r\"\\1\", rs)\n\n    # Clean: v0.3, v1.0\n    if rs.startswith('v'):\n        rs = rs[1:]\n\n    # Clean leading '0's on numbers.\n    #TODO: unintended side-effect on, e.g., \"2003.05.09\"\n    # PyPI stats: 77 (~2%) better\n    rs = re.sub(r\"\\b0+(\\d+)(?!\\d)\", r\"\\1\", rs)\n\n    # Clean a/b/c with no version. E.g. \"1.0a\" -> \"1.0a0\". Setuptools infers\n    # zero.\n    # PyPI stats: 245 (7.56%) better\n    rs = re.sub(r\"(\\d+[abc])$\", r\"\\g<1>0\", rs)\n\n    # the 'dev-rNNN' tag is a dev tag\n    rs = re.sub(r\"\\.?(dev-r|dev\\.r)\\.?(\\d+)$\", r\".dev\\2\", rs)\n\n    # clean the - when used as a pre delimiter\n    rs = re.sub(r\"-(a|b|c)(\\d+)$\", r\"\\1\\2\", rs)\n\n    # a terminal \"dev\" or \"devel\" can be changed into \".dev0\"\n    rs = re.sub(r\"[\\.\\-](dev|devel)$\", r\".dev0\", rs)\n\n    # a terminal \"dev\" can be changed into \".dev0\"\n    rs = re.sub(r\"(?![\\.\\-])dev$\", r\".dev0\", rs)\n\n    # a terminal \"final\" or \"stable\" can be removed\n    rs = re.sub(r\"(final|stable)$\", \"\", rs)\n\n    # The 'r' and the '-' tags are post release tags\n    #   0.4a1.r10       ->  0.4a1.post10\n    #   0.9.33-17222    ->  0.9.33.post17222\n    #   0.9.33-r17222   ->  0.9.33.post17222\n    rs = re.sub(r\"\\.?(r|-|-r)\\.?(\\d+)$\", r\".post\\2\", rs)\n\n    # Clean 'r' instead of 'dev' usage:\n    #   0.9.33+r17222   ->  0.9.33.dev17222\n    #   1.0dev123       ->  1.0.dev123\n    #   1.0.git123      ->  1.0.dev123\n    #   1.0.bzr123      ->  1.0.dev123\n    #   0.1a0dev.123    ->  0.1a0.dev123\n    # PyPI stats:  ~150 (~4%) better\n    rs = re.sub(r\"\\.?(dev|git|bzr)\\.?(\\d+)$\", r\".dev\\2\", rs)\n\n    # Clean '.pre' (normalized from '-pre' above) instead of 'c' usage:\n    #   0.2.pre1        ->  0.2c1\n    #   0.2-c1         ->  0.2c1\n    #   1.0preview123   ->  1.0c123\n    # PyPI stats: ~21 (0.62%) better\n    rs = re.sub(r\"\\.?(pre|preview|-c)(\\d+)$\", r\"c\\g<2>\", rs)\n\n    # Tcl/Tk uses \"px\" for their post release markers\n    rs = re.sub(r\"p(\\d+)$\", r\".post\\1\", rs)\n\n    try:\n        _normalized_key(rs)\n    except UnsupportedVersionError:\n        rs = None\n    return rs\n\n#\n#   Legacy version processing (distribute-compatible)\n#\n\n_VERSION_PART = re.compile(r'([a-z]+|\\d+|[\\.-])', re.I)\n_VERSION_REPLACE = {\n    'pre': 'c',\n    'preview': 'c',\n    '-': 'final-',\n    'rc': 'c',\n    'dev': '@',\n    '': None,\n    '.': None,\n}\n\n\ndef _legacy_key(s):\n    def get_parts(s):\n        result = []\n        for p in _VERSION_PART.split(s.lower()):\n            p = _VERSION_REPLACE.get(p, p)\n            if p:\n                if '0' <= p[:1] <= '9':\n                    p = p.zfill(8)\n                else:\n                    p = '*' + p\n                result.append(p)\n        result.append('*final')\n        return result\n\n    result = []\n    for p in get_parts(s):\n        if p.startswith('*'):\n            if p < '*final':\n                while result and result[-1] == '*final-':\n                    result.pop()\n            while result and result[-1] == '00000000':\n                result.pop()\n        result.append(p)\n    return tuple(result)\n\n\nclass LegacyVersion(Version):\n    def parse(self, s):\n        return _legacy_key(s)\n\n    @property\n    def is_prerelease(self):\n        result = False\n        for x in self._parts:\n            if (isinstance(x, string_types) and x.startswith('*') and\n                x < '*final'):\n                result = True\n                break\n        return result\n\n\nclass LegacyMatcher(Matcher):\n    version_class = LegacyVersion\n\n    _operators = dict(Matcher._operators)\n    _operators['~='] = '_match_compatible'\n\n    numeric_re = re.compile(r'^(\\d+(\\.\\d+)*)')\n\n    def _match_compatible(self, version, constraint, prefix):\n        if version < constraint:\n            return False\n        m = self.numeric_re.match(str(constraint))\n        if not m:\n            logger.warning('Cannot compute compatible match for version %s '\n                           ' and constraint %s', version, constraint)\n            return True\n        s = m.groups()[0]\n        if '.' in s:\n            s = s.rsplit('.', 1)[0]\n        return _match_prefix(version, s)\n\n#\n#   Semantic versioning\n#\n\n_SEMVER_RE = re.compile(r'^(\\d+)\\.(\\d+)\\.(\\d+)'\n                        r'(-[a-z0-9]+(\\.[a-z0-9-]+)*)?'\n                        r'(\\+[a-z0-9]+(\\.[a-z0-9-]+)*)?$', re.I)\n\n\ndef is_semver(s):\n    return _SEMVER_RE.match(s)\n\n\ndef _semantic_key(s):\n    def make_tuple(s, absent):\n        if s is None:\n            result = (absent,)\n        else:\n            parts = s[1:].split('.')\n            # We can't compare ints and strings on Python 3, so fudge it\n            # by zero-filling numeric values so simulate a numeric comparison\n            result = tuple([p.zfill(8) if p.isdigit() else p for p in parts])\n        return result\n\n    m = is_semver(s)\n    if not m:\n        raise UnsupportedVersionError(s)\n    groups = m.groups()\n    major, minor, patch = [int(i) for i in groups[:3]]\n    # choose the '|' and '*' so that versions sort correctly\n    pre, build = make_tuple(groups[3], '|'), make_tuple(groups[5], '*')\n    return (major, minor, patch), pre, build\n\n\nclass SemanticVersion(Version):\n    def parse(self, s):\n        return _semantic_key(s)\n\n    @property\n    def is_prerelease(self):\n        return self._parts[1][0] != '|'\n\n\nclass SemanticMatcher(Matcher):\n    version_class = SemanticVersion\n\n\nclass VersionScheme(object):\n    def __init__(self, key, matcher, suggester=None):\n        self.key = key\n        self.matcher = matcher\n        self.suggester = suggester\n\n    def is_valid_version(self, s):\n        try:\n            self.matcher.version_class(s)\n            result = True\n        except UnsupportedVersionError:\n            result = False\n        return result\n\n    def is_valid_matcher(self, s):\n        try:\n            self.matcher(s)\n            result = True\n        except UnsupportedVersionError:\n            result = False\n        return result\n\n    def is_valid_constraint_list(self, s):\n        \"\"\"\n        Used for processing some metadata fields\n        \"\"\"\n        return self.is_valid_matcher('dummy_name (%s)' % s)\n\n    def suggest(self, s):\n        if self.suggester is None:\n            result = None\n        else:\n            result = self.suggester(s)\n        return result\n\n_SCHEMES = {\n    'normalized': VersionScheme(_normalized_key, NormalizedMatcher,\n                                _suggest_normalized_version),\n    'legacy': VersionScheme(_legacy_key, LegacyMatcher, lambda self, s: s),\n    'semantic': VersionScheme(_semantic_key, SemanticMatcher,\n                              _suggest_semantic_version),\n}\n\n_SCHEMES['default'] = _SCHEMES['normalized']\n\n\ndef get_scheme(name):\n    if name not in _SCHEMES:\n        raise ValueError('unknown scheme name: %r' % name)\n    return _SCHEMES[name]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distlib/wheel.py",
    "content": "# -*- coding: utf-8 -*-\n#\n# Copyright (C) 2013-2017 Vinay Sajip.\n# Licensed to the Python Software Foundation under a contributor agreement.\n# See LICENSE.txt and CONTRIBUTORS.txt.\n#\nfrom __future__ import unicode_literals\n\nimport base64\nimport codecs\nimport datetime\nimport distutils.util\nfrom email import message_from_file\nimport hashlib\nimport imp\nimport json\nimport logging\nimport os\nimport posixpath\nimport re\nimport shutil\nimport sys\nimport tempfile\nimport zipfile\n\nfrom . import __version__, DistlibException\nfrom .compat import sysconfig, ZipFile, fsdecode, text_type, filter\nfrom .database import InstalledDistribution\nfrom .metadata import Metadata, METADATA_FILENAME, WHEEL_METADATA_FILENAME\nfrom .util import (FileOperator, convert_path, CSVReader, CSVWriter, Cache,\n                   cached_property, get_cache_base, read_exports, tempdir)\nfrom .version import NormalizedVersion, UnsupportedVersionError\n\nlogger = logging.getLogger(__name__)\n\ncache = None    # created when needed\n\nif hasattr(sys, 'pypy_version_info'):  # pragma: no cover\n    IMP_PREFIX = 'pp'\nelif sys.platform.startswith('java'):  # pragma: no cover\n    IMP_PREFIX = 'jy'\nelif sys.platform == 'cli':  # pragma: no cover\n    IMP_PREFIX = 'ip'\nelse:\n    IMP_PREFIX = 'cp'\n\nVER_SUFFIX = sysconfig.get_config_var('py_version_nodot')\nif not VER_SUFFIX:   # pragma: no cover\n    VER_SUFFIX = '%s%s' % sys.version_info[:2]\nPYVER = 'py' + VER_SUFFIX\nIMPVER = IMP_PREFIX + VER_SUFFIX\n\nARCH = distutils.util.get_platform().replace('-', '_').replace('.', '_')\n\nABI = sysconfig.get_config_var('SOABI')\nif ABI and ABI.startswith('cpython-'):\n    ABI = ABI.replace('cpython-', 'cp')\nelse:\n    def _derive_abi():\n        parts = ['cp', VER_SUFFIX]\n        if sysconfig.get_config_var('Py_DEBUG'):\n            parts.append('d')\n        if sysconfig.get_config_var('WITH_PYMALLOC'):\n            parts.append('m')\n        if sysconfig.get_config_var('Py_UNICODE_SIZE') == 4:\n            parts.append('u')\n        return ''.join(parts)\n    ABI = _derive_abi()\n    del _derive_abi\n\nFILENAME_RE = re.compile(r'''\n(?P<nm>[^-]+)\n-(?P<vn>\\d+[^-]*)\n(-(?P<bn>\\d+[^-]*))?\n-(?P<py>\\w+\\d+(\\.\\w+\\d+)*)\n-(?P<bi>\\w+)\n-(?P<ar>\\w+(\\.\\w+)*)\n\\.whl$\n''', re.IGNORECASE | re.VERBOSE)\n\nNAME_VERSION_RE = re.compile(r'''\n(?P<nm>[^-]+)\n-(?P<vn>\\d+[^-]*)\n(-(?P<bn>\\d+[^-]*))?$\n''', re.IGNORECASE | re.VERBOSE)\n\nSHEBANG_RE = re.compile(br'\\s*#![^\\r\\n]*')\nSHEBANG_DETAIL_RE = re.compile(br'^(\\s*#!(\"[^\"]+\"|\\S+))\\s+(.*)$')\nSHEBANG_PYTHON = b'#!python'\nSHEBANG_PYTHONW = b'#!pythonw'\n\nif os.sep == '/':\n    to_posix = lambda o: o\nelse:\n    to_posix = lambda o: o.replace(os.sep, '/')\n\n\nclass Mounter(object):\n    def __init__(self):\n        self.impure_wheels = {}\n        self.libs = {}\n\n    def add(self, pathname, extensions):\n        self.impure_wheels[pathname] = extensions\n        self.libs.update(extensions)\n\n    def remove(self, pathname):\n        extensions = self.impure_wheels.pop(pathname)\n        for k, v in extensions:\n            if k in self.libs:\n                del self.libs[k]\n\n    def find_module(self, fullname, path=None):\n        if fullname in self.libs:\n            result = self\n        else:\n            result = None\n        return result\n\n    def load_module(self, fullname):\n        if fullname in sys.modules:\n            result = sys.modules[fullname]\n        else:\n            if fullname not in self.libs:\n                raise ImportError('unable to find extension for %s' % fullname)\n            result = imp.load_dynamic(fullname, self.libs[fullname])\n            result.__loader__ = self\n            parts = fullname.rsplit('.', 1)\n            if len(parts) > 1:\n                result.__package__ = parts[0]\n        return result\n\n_hook = Mounter()\n\n\nclass Wheel(object):\n    \"\"\"\n    Class to build and install from Wheel files (PEP 427).\n    \"\"\"\n\n    wheel_version = (1, 1)\n    hash_kind = 'sha256'\n\n    def __init__(self, filename=None, sign=False, verify=False):\n        \"\"\"\n        Initialise an instance using a (valid) filename.\n        \"\"\"\n        self.sign = sign\n        self.should_verify = verify\n        self.buildver = ''\n        self.pyver = [PYVER]\n        self.abi = ['none']\n        self.arch = ['any']\n        self.dirname = os.getcwd()\n        if filename is None:\n            self.name = 'dummy'\n            self.version = '0.1'\n            self._filename = self.filename\n        else:\n            m = NAME_VERSION_RE.match(filename)\n            if m:\n                info = m.groupdict('')\n                self.name = info['nm']\n                # Reinstate the local version separator\n                self.version = info['vn'].replace('_', '-')\n                self.buildver = info['bn']\n                self._filename = self.filename\n            else:\n                dirname, filename = os.path.split(filename)\n                m = FILENAME_RE.match(filename)\n                if not m:\n                    raise DistlibException('Invalid name or '\n                                           'filename: %r' % filename)\n                if dirname:\n                    self.dirname = os.path.abspath(dirname)\n                self._filename = filename\n                info = m.groupdict('')\n                self.name = info['nm']\n                self.version = info['vn']\n                self.buildver = info['bn']\n                self.pyver = info['py'].split('.')\n                self.abi = info['bi'].split('.')\n                self.arch = info['ar'].split('.')\n\n    @property\n    def filename(self):\n        \"\"\"\n        Build and return a filename from the various components.\n        \"\"\"\n        if self.buildver:\n            buildver = '-' + self.buildver\n        else:\n            buildver = ''\n        pyver = '.'.join(self.pyver)\n        abi = '.'.join(self.abi)\n        arch = '.'.join(self.arch)\n        # replace - with _ as a local version separator\n        version = self.version.replace('-', '_')\n        return '%s-%s%s-%s-%s-%s.whl' % (self.name, version, buildver,\n                                         pyver, abi, arch)\n\n    @property\n    def exists(self):\n        path = os.path.join(self.dirname, self.filename)\n        return os.path.isfile(path)\n\n    @property\n    def tags(self):\n        for pyver in self.pyver:\n            for abi in self.abi:\n                for arch in self.arch:\n                    yield pyver, abi, arch\n\n    @cached_property\n    def metadata(self):\n        pathname = os.path.join(self.dirname, self.filename)\n        name_ver = '%s-%s' % (self.name, self.version)\n        info_dir = '%s.dist-info' % name_ver\n        wrapper = codecs.getreader('utf-8')\n        with ZipFile(pathname, 'r') as zf:\n            wheel_metadata = self.get_wheel_metadata(zf)\n            wv = wheel_metadata['Wheel-Version'].split('.', 1)\n            file_version = tuple([int(i) for i in wv])\n            if file_version < (1, 1):\n                fns = [WHEEL_METADATA_FILENAME, METADATA_FILENAME, 'METADATA']\n            else:\n                fns = [WHEEL_METADATA_FILENAME, METADATA_FILENAME]\n            result = None\n            for fn in fns:\n                try:\n                    metadata_filename = posixpath.join(info_dir, fn)\n                    with zf.open(metadata_filename) as bf:\n                        wf = wrapper(bf)\n                        result = Metadata(fileobj=wf)\n                        if result:\n                            break\n                except KeyError:\n                    pass\n            if not result:\n                raise ValueError('Invalid wheel, because metadata is '\n                                 'missing: looked in %s' % ', '.join(fns))\n        return result\n\n    def get_wheel_metadata(self, zf):\n        name_ver = '%s-%s' % (self.name, self.version)\n        info_dir = '%s.dist-info' % name_ver\n        metadata_filename = posixpath.join(info_dir, 'WHEEL')\n        with zf.open(metadata_filename) as bf:\n            wf = codecs.getreader('utf-8')(bf)\n            message = message_from_file(wf)\n        return dict(message)\n\n    @cached_property\n    def info(self):\n        pathname = os.path.join(self.dirname, self.filename)\n        with ZipFile(pathname, 'r') as zf:\n            result = self.get_wheel_metadata(zf)\n        return result\n\n    def process_shebang(self, data):\n        m = SHEBANG_RE.match(data)\n        if m:\n            end = m.end()\n            shebang, data_after_shebang = data[:end], data[end:]\n            # Preserve any arguments after the interpreter\n            if b'pythonw' in shebang.lower():\n                shebang_python = SHEBANG_PYTHONW\n            else:\n                shebang_python = SHEBANG_PYTHON\n            m = SHEBANG_DETAIL_RE.match(shebang)\n            if m:\n                args = b' ' + m.groups()[-1]\n            else:\n                args = b''\n            shebang = shebang_python + args\n            data = shebang + data_after_shebang\n        else:\n            cr = data.find(b'\\r')\n            lf = data.find(b'\\n')\n            if cr < 0 or cr > lf:\n                term = b'\\n'\n            else:\n                if data[cr:cr + 2] == b'\\r\\n':\n                    term = b'\\r\\n'\n                else:\n                    term = b'\\r'\n            data = SHEBANG_PYTHON + term + data\n        return data\n\n    def get_hash(self, data, hash_kind=None):\n        if hash_kind is None:\n            hash_kind = self.hash_kind\n        try:\n            hasher = getattr(hashlib, hash_kind)\n        except AttributeError:\n            raise DistlibException('Unsupported hash algorithm: %r' % hash_kind)\n        result = hasher(data).digest()\n        result = base64.urlsafe_b64encode(result).rstrip(b'=').decode('ascii')\n        return hash_kind, result\n\n    def write_record(self, records, record_path, base):\n        records = list(records) # make a copy for sorting\n        p = to_posix(os.path.relpath(record_path, base))\n        records.append((p, '', ''))\n        records.sort()\n        with CSVWriter(record_path) as writer:\n            for row in records:\n                writer.writerow(row)\n\n    def write_records(self, info, libdir, archive_paths):\n        records = []\n        distinfo, info_dir = info\n        hasher = getattr(hashlib, self.hash_kind)\n        for ap, p in archive_paths:\n            with open(p, 'rb') as f:\n                data = f.read()\n            digest = '%s=%s' % self.get_hash(data)\n            size = os.path.getsize(p)\n            records.append((ap, digest, size))\n\n        p = os.path.join(distinfo, 'RECORD')\n        self.write_record(records, p, libdir)\n        ap = to_posix(os.path.join(info_dir, 'RECORD'))\n        archive_paths.append((ap, p))\n\n    def build_zip(self, pathname, archive_paths):\n        with ZipFile(pathname, 'w', zipfile.ZIP_DEFLATED) as zf:\n            for ap, p in archive_paths:\n                logger.debug('Wrote %s to %s in wheel', p, ap)\n                zf.write(p, ap)\n\n    def build(self, paths, tags=None, wheel_version=None):\n        \"\"\"\n        Build a wheel from files in specified paths, and use any specified tags\n        when determining the name of the wheel.\n        \"\"\"\n        if tags is None:\n            tags = {}\n\n        libkey = list(filter(lambda o: o in paths, ('purelib', 'platlib')))[0]\n        if libkey == 'platlib':\n            is_pure = 'false'\n            default_pyver = [IMPVER]\n            default_abi = [ABI]\n            default_arch = [ARCH]\n        else:\n            is_pure = 'true'\n            default_pyver = [PYVER]\n            default_abi = ['none']\n            default_arch = ['any']\n\n        self.pyver = tags.get('pyver', default_pyver)\n        self.abi = tags.get('abi', default_abi)\n        self.arch = tags.get('arch', default_arch)\n\n        libdir = paths[libkey]\n\n        name_ver = '%s-%s' % (self.name, self.version)\n        data_dir = '%s.data' % name_ver\n        info_dir = '%s.dist-info' % name_ver\n\n        archive_paths = []\n\n        # First, stuff which is not in site-packages\n        for key in ('data', 'headers', 'scripts'):\n            if key not in paths:\n                continue\n            path = paths[key]\n            if os.path.isdir(path):\n                for root, dirs, files in os.walk(path):\n                    for fn in files:\n                        p = fsdecode(os.path.join(root, fn))\n                        rp = os.path.relpath(p, path)\n                        ap = to_posix(os.path.join(data_dir, key, rp))\n                        archive_paths.append((ap, p))\n                        if key == 'scripts' and not p.endswith('.exe'):\n                            with open(p, 'rb') as f:\n                                data = f.read()\n                            data = self.process_shebang(data)\n                            with open(p, 'wb') as f:\n                                f.write(data)\n\n        # Now, stuff which is in site-packages, other than the\n        # distinfo stuff.\n        path = libdir\n        distinfo = None\n        for root, dirs, files in os.walk(path):\n            if root == path:\n                # At the top level only, save distinfo for later\n                # and skip it for now\n                for i, dn in enumerate(dirs):\n                    dn = fsdecode(dn)\n                    if dn.endswith('.dist-info'):\n                        distinfo = os.path.join(root, dn)\n                        del dirs[i]\n                        break\n                assert distinfo, '.dist-info directory expected, not found'\n\n            for fn in files:\n                # comment out next suite to leave .pyc files in\n                if fsdecode(fn).endswith(('.pyc', '.pyo')):\n                    continue\n                p = os.path.join(root, fn)\n                rp = to_posix(os.path.relpath(p, path))\n                archive_paths.append((rp, p))\n\n        # Now distinfo. Assumed to be flat, i.e. os.listdir is enough.\n        files = os.listdir(distinfo)\n        for fn in files:\n            if fn not in ('RECORD', 'INSTALLER', 'SHARED', 'WHEEL'):\n                p = fsdecode(os.path.join(distinfo, fn))\n                ap = to_posix(os.path.join(info_dir, fn))\n                archive_paths.append((ap, p))\n\n        wheel_metadata = [\n            'Wheel-Version: %d.%d' % (wheel_version or self.wheel_version),\n            'Generator: distlib %s' % __version__,\n            'Root-Is-Purelib: %s' % is_pure,\n        ]\n        for pyver, abi, arch in self.tags:\n            wheel_metadata.append('Tag: %s-%s-%s' % (pyver, abi, arch))\n        p = os.path.join(distinfo, 'WHEEL')\n        with open(p, 'w') as f:\n            f.write('\\n'.join(wheel_metadata))\n        ap = to_posix(os.path.join(info_dir, 'WHEEL'))\n        archive_paths.append((ap, p))\n\n        # Now, at last, RECORD.\n        # Paths in here are archive paths - nothing else makes sense.\n        self.write_records((distinfo, info_dir), libdir, archive_paths)\n        # Now, ready to build the zip file\n        pathname = os.path.join(self.dirname, self.filename)\n        self.build_zip(pathname, archive_paths)\n        return pathname\n\n    def install(self, paths, maker, **kwargs):\n        \"\"\"\n        Install a wheel to the specified paths. If kwarg ``warner`` is\n        specified, it should be a callable, which will be called with two\n        tuples indicating the wheel version of this software and the wheel\n        version in the file, if there is a discrepancy in the versions.\n        This can be used to issue any warnings to raise any exceptions.\n        If kwarg ``lib_only`` is True, only the purelib/platlib files are\n        installed, and the headers, scripts, data and dist-info metadata are\n        not written. If kwarg ``bytecode_hashed_invalidation`` is True, written\n        bytecode will try to use file-hash based invalidation (PEP-552) on\n        supported interpreter versions (CPython 2.7+).\n\n        The return value is a :class:`InstalledDistribution` instance unless\n        ``options.lib_only`` is True, in which case the return value is ``None``.\n        \"\"\"\n\n        dry_run = maker.dry_run\n        warner = kwargs.get('warner')\n        lib_only = kwargs.get('lib_only', False)\n        bc_hashed_invalidation = kwargs.get('bytecode_hashed_invalidation', False)\n\n        pathname = os.path.join(self.dirname, self.filename)\n        name_ver = '%s-%s' % (self.name, self.version)\n        data_dir = '%s.data' % name_ver\n        info_dir = '%s.dist-info' % name_ver\n\n        metadata_name = posixpath.join(info_dir, METADATA_FILENAME)\n        wheel_metadata_name = posixpath.join(info_dir, 'WHEEL')\n        record_name = posixpath.join(info_dir, 'RECORD')\n\n        wrapper = codecs.getreader('utf-8')\n\n        with ZipFile(pathname, 'r') as zf:\n            with zf.open(wheel_metadata_name) as bwf:\n                wf = wrapper(bwf)\n                message = message_from_file(wf)\n            wv = message['Wheel-Version'].split('.', 1)\n            file_version = tuple([int(i) for i in wv])\n            if (file_version != self.wheel_version) and warner:\n                warner(self.wheel_version, file_version)\n\n            if message['Root-Is-Purelib'] == 'true':\n                libdir = paths['purelib']\n            else:\n                libdir = paths['platlib']\n\n            records = {}\n            with zf.open(record_name) as bf:\n                with CSVReader(stream=bf) as reader:\n                    for row in reader:\n                        p = row[0]\n                        records[p] = row\n\n            data_pfx = posixpath.join(data_dir, '')\n            info_pfx = posixpath.join(info_dir, '')\n            script_pfx = posixpath.join(data_dir, 'scripts', '')\n\n            # make a new instance rather than a copy of maker's,\n            # as we mutate it\n            fileop = FileOperator(dry_run=dry_run)\n            fileop.record = True    # so we can rollback if needed\n\n            bc = not sys.dont_write_bytecode    # Double negatives. Lovely!\n\n            outfiles = []   # for RECORD writing\n\n            # for script copying/shebang processing\n            workdir = tempfile.mkdtemp()\n            # set target dir later\n            # we default add_launchers to False, as the\n            # Python Launcher should be used instead\n            maker.source_dir = workdir\n            maker.target_dir = None\n            try:\n                for zinfo in zf.infolist():\n                    arcname = zinfo.filename\n                    if isinstance(arcname, text_type):\n                        u_arcname = arcname\n                    else:\n                        u_arcname = arcname.decode('utf-8')\n                    # The signature file won't be in RECORD,\n                    # and we  don't currently don't do anything with it\n                    if u_arcname.endswith('/RECORD.jws'):\n                        continue\n                    row = records[u_arcname]\n                    if row[2] and str(zinfo.file_size) != row[2]:\n                        raise DistlibException('size mismatch for '\n                                               '%s' % u_arcname)\n                    if row[1]:\n                        kind, value = row[1].split('=', 1)\n                        with zf.open(arcname) as bf:\n                            data = bf.read()\n                        _, digest = self.get_hash(data, kind)\n                        if digest != value:\n                            raise DistlibException('digest mismatch for '\n                                                   '%s' % arcname)\n\n                    if lib_only and u_arcname.startswith((info_pfx, data_pfx)):\n                        logger.debug('lib_only: skipping %s', u_arcname)\n                        continue\n                    is_script = (u_arcname.startswith(script_pfx)\n                                 and not u_arcname.endswith('.exe'))\n\n                    if u_arcname.startswith(data_pfx):\n                        _, where, rp = u_arcname.split('/', 2)\n                        outfile = os.path.join(paths[where], convert_path(rp))\n                    else:\n                        # meant for site-packages.\n                        if u_arcname in (wheel_metadata_name, record_name):\n                            continue\n                        outfile = os.path.join(libdir, convert_path(u_arcname))\n                    if not is_script:\n                        with zf.open(arcname) as bf:\n                            fileop.copy_stream(bf, outfile)\n                        outfiles.append(outfile)\n                        # Double check the digest of the written file\n                        if not dry_run and row[1]:\n                            with open(outfile, 'rb') as bf:\n                                data = bf.read()\n                                _, newdigest = self.get_hash(data, kind)\n                                if newdigest != digest:\n                                    raise DistlibException('digest mismatch '\n                                                           'on write for '\n                                                           '%s' % outfile)\n                        if bc and outfile.endswith('.py'):\n                            try:\n                                pyc = fileop.byte_compile(outfile,\n                                                          hashed_invalidation=bc_hashed_invalidation)\n                                outfiles.append(pyc)\n                            except Exception:\n                                # Don't give up if byte-compilation fails,\n                                # but log it and perhaps warn the user\n                                logger.warning('Byte-compilation failed',\n                                               exc_info=True)\n                    else:\n                        fn = os.path.basename(convert_path(arcname))\n                        workname = os.path.join(workdir, fn)\n                        with zf.open(arcname) as bf:\n                            fileop.copy_stream(bf, workname)\n\n                        dn, fn = os.path.split(outfile)\n                        maker.target_dir = dn\n                        filenames = maker.make(fn)\n                        fileop.set_executable_mode(filenames)\n                        outfiles.extend(filenames)\n\n                if lib_only:\n                    logger.debug('lib_only: returning None')\n                    dist = None\n                else:\n                    # Generate scripts\n\n                    # Try to get pydist.json so we can see if there are\n                    # any commands to generate. If this fails (e.g. because\n                    # of a legacy wheel), log a warning but don't give up.\n                    commands = None\n                    file_version = self.info['Wheel-Version']\n                    if file_version == '1.0':\n                        # Use legacy info\n                        ep = posixpath.join(info_dir, 'entry_points.txt')\n                        try:\n                            with zf.open(ep) as bwf:\n                                epdata = read_exports(bwf)\n                            commands = {}\n                            for key in ('console', 'gui'):\n                                k = '%s_scripts' % key\n                                if k in epdata:\n                                    commands['wrap_%s' % key] = d = {}\n                                    for v in epdata[k].values():\n                                        s = '%s:%s' % (v.prefix, v.suffix)\n                                        if v.flags:\n                                            s += ' %s' % v.flags\n                                        d[v.name] = s\n                        except Exception:\n                            logger.warning('Unable to read legacy script '\n                                           'metadata, so cannot generate '\n                                           'scripts')\n                    else:\n                        try:\n                            with zf.open(metadata_name) as bwf:\n                                wf = wrapper(bwf)\n                                commands = json.load(wf).get('extensions')\n                                if commands:\n                                    commands = commands.get('python.commands')\n                        except Exception:\n                            logger.warning('Unable to read JSON metadata, so '\n                                           'cannot generate scripts')\n                    if commands:\n                        console_scripts = commands.get('wrap_console', {})\n                        gui_scripts = commands.get('wrap_gui', {})\n                        if console_scripts or gui_scripts:\n                            script_dir = paths.get('scripts', '')\n                            if not os.path.isdir(script_dir):\n                                raise ValueError('Valid script path not '\n                                                 'specified')\n                            maker.target_dir = script_dir\n                            for k, v in console_scripts.items():\n                                script = '%s = %s' % (k, v)\n                                filenames = maker.make(script)\n                                fileop.set_executable_mode(filenames)\n\n                            if gui_scripts:\n                                options = {'gui': True }\n                                for k, v in gui_scripts.items():\n                                    script = '%s = %s' % (k, v)\n                                    filenames = maker.make(script, options)\n                                    fileop.set_executable_mode(filenames)\n\n                    p = os.path.join(libdir, info_dir)\n                    dist = InstalledDistribution(p)\n\n                    # Write SHARED\n                    paths = dict(paths)     # don't change passed in dict\n                    del paths['purelib']\n                    del paths['platlib']\n                    paths['lib'] = libdir\n                    p = dist.write_shared_locations(paths, dry_run)\n                    if p:\n                        outfiles.append(p)\n\n                    # Write RECORD\n                    dist.write_installed_files(outfiles, paths['prefix'],\n                                               dry_run)\n                return dist\n            except Exception:  # pragma: no cover\n                logger.exception('installation failed.')\n                fileop.rollback()\n                raise\n            finally:\n                shutil.rmtree(workdir)\n\n    def _get_dylib_cache(self):\n        global cache\n        if cache is None:\n            # Use native string to avoid issues on 2.x: see Python #20140.\n            base = os.path.join(get_cache_base(), str('dylib-cache'),\n                                sys.version[:3])\n            cache = Cache(base)\n        return cache\n\n    def _get_extensions(self):\n        pathname = os.path.join(self.dirname, self.filename)\n        name_ver = '%s-%s' % (self.name, self.version)\n        info_dir = '%s.dist-info' % name_ver\n        arcname = posixpath.join(info_dir, 'EXTENSIONS')\n        wrapper = codecs.getreader('utf-8')\n        result = []\n        with ZipFile(pathname, 'r') as zf:\n            try:\n                with zf.open(arcname) as bf:\n                    wf = wrapper(bf)\n                    extensions = json.load(wf)\n                    cache = self._get_dylib_cache()\n                    prefix = cache.prefix_to_dir(pathname)\n                    cache_base = os.path.join(cache.base, prefix)\n                    if not os.path.isdir(cache_base):\n                        os.makedirs(cache_base)\n                    for name, relpath in extensions.items():\n                        dest = os.path.join(cache_base, convert_path(relpath))\n                        if not os.path.exists(dest):\n                            extract = True\n                        else:\n                            file_time = os.stat(dest).st_mtime\n                            file_time = datetime.datetime.fromtimestamp(file_time)\n                            info = zf.getinfo(relpath)\n                            wheel_time = datetime.datetime(*info.date_time)\n                            extract = wheel_time > file_time\n                        if extract:\n                            zf.extract(relpath, cache_base)\n                        result.append((name, dest))\n            except KeyError:\n                pass\n        return result\n\n    def is_compatible(self):\n        \"\"\"\n        Determine if a wheel is compatible with the running system.\n        \"\"\"\n        return is_compatible(self)\n\n    def is_mountable(self):\n        \"\"\"\n        Determine if a wheel is asserted as mountable by its metadata.\n        \"\"\"\n        return True # for now - metadata details TBD\n\n    def mount(self, append=False):\n        pathname = os.path.abspath(os.path.join(self.dirname, self.filename))\n        if not self.is_compatible():\n            msg = 'Wheel %s not compatible with this Python.' % pathname\n            raise DistlibException(msg)\n        if not self.is_mountable():\n            msg = 'Wheel %s is marked as not mountable.' % pathname\n            raise DistlibException(msg)\n        if pathname in sys.path:\n            logger.debug('%s already in path', pathname)\n        else:\n            if append:\n                sys.path.append(pathname)\n            else:\n                sys.path.insert(0, pathname)\n            extensions = self._get_extensions()\n            if extensions:\n                if _hook not in sys.meta_path:\n                    sys.meta_path.append(_hook)\n                _hook.add(pathname, extensions)\n\n    def unmount(self):\n        pathname = os.path.abspath(os.path.join(self.dirname, self.filename))\n        if pathname not in sys.path:\n            logger.debug('%s not in path', pathname)\n        else:\n            sys.path.remove(pathname)\n            if pathname in _hook.impure_wheels:\n                _hook.remove(pathname)\n            if not _hook.impure_wheels:\n                if _hook in sys.meta_path:\n                    sys.meta_path.remove(_hook)\n\n    def verify(self):\n        pathname = os.path.join(self.dirname, self.filename)\n        name_ver = '%s-%s' % (self.name, self.version)\n        data_dir = '%s.data' % name_ver\n        info_dir = '%s.dist-info' % name_ver\n\n        metadata_name = posixpath.join(info_dir, METADATA_FILENAME)\n        wheel_metadata_name = posixpath.join(info_dir, 'WHEEL')\n        record_name = posixpath.join(info_dir, 'RECORD')\n\n        wrapper = codecs.getreader('utf-8')\n\n        with ZipFile(pathname, 'r') as zf:\n            with zf.open(wheel_metadata_name) as bwf:\n                wf = wrapper(bwf)\n                message = message_from_file(wf)\n            wv = message['Wheel-Version'].split('.', 1)\n            file_version = tuple([int(i) for i in wv])\n            # TODO version verification\n\n            records = {}\n            with zf.open(record_name) as bf:\n                with CSVReader(stream=bf) as reader:\n                    for row in reader:\n                        p = row[0]\n                        records[p] = row\n\n            for zinfo in zf.infolist():\n                arcname = zinfo.filename\n                if isinstance(arcname, text_type):\n                    u_arcname = arcname\n                else:\n                    u_arcname = arcname.decode('utf-8')\n                if '..' in u_arcname:\n                    raise DistlibException('invalid entry in '\n                                           'wheel: %r' % u_arcname)\n\n                # The signature file won't be in RECORD,\n                # and we  don't currently don't do anything with it\n                if u_arcname.endswith('/RECORD.jws'):\n                    continue\n                row = records[u_arcname]\n                if row[2] and str(zinfo.file_size) != row[2]:\n                    raise DistlibException('size mismatch for '\n                                           '%s' % u_arcname)\n                if row[1]:\n                    kind, value = row[1].split('=', 1)\n                    with zf.open(arcname) as bf:\n                        data = bf.read()\n                    _, digest = self.get_hash(data, kind)\n                    if digest != value:\n                        raise DistlibException('digest mismatch for '\n                                               '%s' % arcname)\n\n    def update(self, modifier, dest_dir=None, **kwargs):\n        \"\"\"\n        Update the contents of a wheel in a generic way. The modifier should\n        be a callable which expects a dictionary argument: its keys are\n        archive-entry paths, and its values are absolute filesystem paths\n        where the contents the corresponding archive entries can be found. The\n        modifier is free to change the contents of the files pointed to, add\n        new entries and remove entries, before returning. This method will\n        extract the entire contents of the wheel to a temporary location, call\n        the modifier, and then use the passed (and possibly updated)\n        dictionary to write a new wheel. If ``dest_dir`` is specified, the new\n        wheel is written there -- otherwise, the original wheel is overwritten.\n\n        The modifier should return True if it updated the wheel, else False.\n        This method returns the same value the modifier returns.\n        \"\"\"\n\n        def get_version(path_map, info_dir):\n            version = path = None\n            key = '%s/%s' % (info_dir, METADATA_FILENAME)\n            if key not in path_map:\n                key = '%s/PKG-INFO' % info_dir\n            if key in path_map:\n                path = path_map[key]\n                version = Metadata(path=path).version\n            return version, path\n\n        def update_version(version, path):\n            updated = None\n            try:\n                v = NormalizedVersion(version)\n                i = version.find('-')\n                if i < 0:\n                    updated = '%s+1' % version\n                else:\n                    parts = [int(s) for s in version[i + 1:].split('.')]\n                    parts[-1] += 1\n                    updated = '%s+%s' % (version[:i],\n                                         '.'.join(str(i) for i in parts))\n            except UnsupportedVersionError:\n                logger.debug('Cannot update non-compliant (PEP-440) '\n                             'version %r', version)\n            if updated:\n                md = Metadata(path=path)\n                md.version = updated\n                legacy = not path.endswith(METADATA_FILENAME)\n                md.write(path=path, legacy=legacy)\n                logger.debug('Version updated from %r to %r', version,\n                             updated)\n\n        pathname = os.path.join(self.dirname, self.filename)\n        name_ver = '%s-%s' % (self.name, self.version)\n        info_dir = '%s.dist-info' % name_ver\n        record_name = posixpath.join(info_dir, 'RECORD')\n        with tempdir() as workdir:\n            with ZipFile(pathname, 'r') as zf:\n                path_map = {}\n                for zinfo in zf.infolist():\n                    arcname = zinfo.filename\n                    if isinstance(arcname, text_type):\n                        u_arcname = arcname\n                    else:\n                        u_arcname = arcname.decode('utf-8')\n                    if u_arcname == record_name:\n                        continue\n                    if '..' in u_arcname:\n                        raise DistlibException('invalid entry in '\n                                               'wheel: %r' % u_arcname)\n                    zf.extract(zinfo, workdir)\n                    path = os.path.join(workdir, convert_path(u_arcname))\n                    path_map[u_arcname] = path\n\n            # Remember the version.\n            original_version, _ = get_version(path_map, info_dir)\n            # Files extracted. Call the modifier.\n            modified = modifier(path_map, **kwargs)\n            if modified:\n                # Something changed - need to build a new wheel.\n                current_version, path = get_version(path_map, info_dir)\n                if current_version and (current_version == original_version):\n                    # Add or update local version to signify changes.\n                    update_version(current_version, path)\n                # Decide where the new wheel goes.\n                if dest_dir is None:\n                    fd, newpath = tempfile.mkstemp(suffix='.whl',\n                                                   prefix='wheel-update-',\n                                                   dir=workdir)\n                    os.close(fd)\n                else:\n                    if not os.path.isdir(dest_dir):\n                        raise DistlibException('Not a directory: %r' % dest_dir)\n                    newpath = os.path.join(dest_dir, self.filename)\n                archive_paths = list(path_map.items())\n                distinfo = os.path.join(workdir, info_dir)\n                info = distinfo, info_dir\n                self.write_records(info, workdir, archive_paths)\n                self.build_zip(newpath, archive_paths)\n                if dest_dir is None:\n                    shutil.copyfile(newpath, pathname)\n        return modified\n\ndef compatible_tags():\n    \"\"\"\n    Return (pyver, abi, arch) tuples compatible with this Python.\n    \"\"\"\n    versions = [VER_SUFFIX]\n    major = VER_SUFFIX[0]\n    for minor in range(sys.version_info[1] - 1, - 1, -1):\n        versions.append(''.join([major, str(minor)]))\n\n    abis = []\n    for suffix, _, _ in imp.get_suffixes():\n        if suffix.startswith('.abi'):\n            abis.append(suffix.split('.', 2)[1])\n    abis.sort()\n    if ABI != 'none':\n        abis.insert(0, ABI)\n    abis.append('none')\n    result = []\n\n    arches = [ARCH]\n    if sys.platform == 'darwin':\n        m = re.match(r'(\\w+)_(\\d+)_(\\d+)_(\\w+)$', ARCH)\n        if m:\n            name, major, minor, arch = m.groups()\n            minor = int(minor)\n            matches = [arch]\n            if arch in ('i386', 'ppc'):\n                matches.append('fat')\n            if arch in ('i386', 'ppc', 'x86_64'):\n                matches.append('fat3')\n            if arch in ('ppc64', 'x86_64'):\n                matches.append('fat64')\n            if arch in ('i386', 'x86_64'):\n                matches.append('intel')\n            if arch in ('i386', 'x86_64', 'intel', 'ppc', 'ppc64'):\n                matches.append('universal')\n            while minor >= 0:\n                for match in matches:\n                    s = '%s_%s_%s_%s' % (name, major, minor, match)\n                    if s != ARCH:   # already there\n                        arches.append(s)\n                minor -= 1\n\n    # Most specific - our Python version, ABI and arch\n    for abi in abis:\n        for arch in arches:\n            result.append((''.join((IMP_PREFIX, versions[0])), abi, arch))\n\n    # where no ABI / arch dependency, but IMP_PREFIX dependency\n    for i, version in enumerate(versions):\n        result.append((''.join((IMP_PREFIX, version)), 'none', 'any'))\n        if i == 0:\n            result.append((''.join((IMP_PREFIX, version[0])), 'none', 'any'))\n\n    # no IMP_PREFIX, ABI or arch dependency\n    for i, version in enumerate(versions):\n        result.append((''.join(('py', version)), 'none', 'any'))\n        if i == 0:\n            result.append((''.join(('py', version[0])), 'none', 'any'))\n    return set(result)\n\n\nCOMPATIBLE_TAGS = compatible_tags()\n\ndel compatible_tags\n\n\ndef is_compatible(wheel, tags=None):\n    if not isinstance(wheel, Wheel):\n        wheel = Wheel(wheel)    # assume it's a filename\n    result = False\n    if tags is None:\n        tags = COMPATIBLE_TAGS\n    for ver, abi, arch in tags:\n        if ver in wheel.pyver and abi in wheel.abi and arch in wheel.arch:\n            result = True\n            break\n    return result\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/distro.py",
    "content": "# Copyright 2015,2016,2017 Nir Cohen\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"\nThe ``distro`` package (``distro`` stands for Linux Distribution) provides\ninformation about the Linux distribution it runs on, such as a reliable\nmachine-readable distro ID, or version information.\n\nIt is a renewed alternative implementation for Python's original\n:py:func:`platform.linux_distribution` function, but it provides much more\nfunctionality. An alternative implementation became necessary because Python\n3.5 deprecated this function, and Python 3.7 is expected to remove it\naltogether. Its predecessor function :py:func:`platform.dist` was already\ndeprecated since Python 2.6 and is also expected to be removed in Python 3.7.\nStill, there are many cases in which access to OS distribution information\nis needed. See `Python issue 1322 <https://bugs.python.org/issue1322>`_ for\nmore information.\n\"\"\"\n\nimport os\nimport re\nimport sys\nimport json\nimport shlex\nimport logging\nimport argparse\nimport subprocess\n\n\n_UNIXCONFDIR = os.environ.get('UNIXCONFDIR', '/etc')\n_OS_RELEASE_BASENAME = 'os-release'\n\n#: Translation table for normalizing the \"ID\" attribute defined in os-release\n#: files, for use by the :func:`distro.id` method.\n#:\n#: * Key: Value as defined in the os-release file, translated to lower case,\n#:   with blanks translated to underscores.\n#:\n#: * Value: Normalized value.\nNORMALIZED_OS_ID = {}\n\n#: Translation table for normalizing the \"Distributor ID\" attribute returned by\n#: the lsb_release command, for use by the :func:`distro.id` method.\n#:\n#: * Key: Value as returned by the lsb_release command, translated to lower\n#:   case, with blanks translated to underscores.\n#:\n#: * Value: Normalized value.\nNORMALIZED_LSB_ID = {\n    'enterpriseenterprise': 'oracle',  # Oracle Enterprise Linux\n    'redhatenterpriseworkstation': 'rhel',  # RHEL 6, 7 Workstation\n    'redhatenterpriseserver': 'rhel',  # RHEL 6, 7 Server\n}\n\n#: Translation table for normalizing the distro ID derived from the file name\n#: of distro release files, for use by the :func:`distro.id` method.\n#:\n#: * Key: Value as derived from the file name of a distro release file,\n#:   translated to lower case, with blanks translated to underscores.\n#:\n#: * Value: Normalized value.\nNORMALIZED_DISTRO_ID = {\n    'redhat': 'rhel',  # RHEL 6.x, 7.x\n}\n\n# Pattern for content of distro release file (reversed)\n_DISTRO_RELEASE_CONTENT_REVERSED_PATTERN = re.compile(\n    r'(?:[^)]*\\)(.*)\\()? *(?:STL )?([\\d.+\\-a-z]*\\d) *(?:esaeler *)?(.+)')\n\n# Pattern for base file name of distro release file\n_DISTRO_RELEASE_BASENAME_PATTERN = re.compile(\n    r'(\\w+)[-_](release|version)$')\n\n# Base file names to be ignored when searching for distro release file\n_DISTRO_RELEASE_IGNORE_BASENAMES = (\n    'debian_version',\n    'lsb-release',\n    'oem-release',\n    _OS_RELEASE_BASENAME,\n    'system-release'\n)\n\n\ndef linux_distribution(full_distribution_name=True):\n    \"\"\"\n    Return information about the current OS distribution as a tuple\n    ``(id_name, version, codename)`` with items as follows:\n\n    * ``id_name``:  If *full_distribution_name* is false, the result of\n      :func:`distro.id`. Otherwise, the result of :func:`distro.name`.\n\n    * ``version``:  The result of :func:`distro.version`.\n\n    * ``codename``:  The result of :func:`distro.codename`.\n\n    The interface of this function is compatible with the original\n    :py:func:`platform.linux_distribution` function, supporting a subset of\n    its parameters.\n\n    The data it returns may not exactly be the same, because it uses more data\n    sources than the original function, and that may lead to different data if\n    the OS distribution is not consistent across multiple data sources it\n    provides (there are indeed such distributions ...).\n\n    Another reason for differences is the fact that the :func:`distro.id`\n    method normalizes the distro ID string to a reliable machine-readable value\n    for a number of popular OS distributions.\n    \"\"\"\n    return _distro.linux_distribution(full_distribution_name)\n\n\ndef id():\n    \"\"\"\n    Return the distro ID of the current distribution, as a\n    machine-readable string.\n\n    For a number of OS distributions, the returned distro ID value is\n    *reliable*, in the sense that it is documented and that it does not change\n    across releases of the distribution.\n\n    This package maintains the following reliable distro ID values:\n\n    ==============  =========================================\n    Distro ID       Distribution\n    ==============  =========================================\n    \"ubuntu\"        Ubuntu\n    \"debian\"        Debian\n    \"rhel\"          RedHat Enterprise Linux\n    \"centos\"        CentOS\n    \"fedora\"        Fedora\n    \"sles\"          SUSE Linux Enterprise Server\n    \"opensuse\"      openSUSE\n    \"amazon\"        Amazon Linux\n    \"arch\"          Arch Linux\n    \"cloudlinux\"    CloudLinux OS\n    \"exherbo\"       Exherbo Linux\n    \"gentoo\"        GenToo Linux\n    \"ibm_powerkvm\"  IBM PowerKVM\n    \"kvmibm\"        KVM for IBM z Systems\n    \"linuxmint\"     Linux Mint\n    \"mageia\"        Mageia\n    \"mandriva\"      Mandriva Linux\n    \"parallels\"     Parallels\n    \"pidora\"        Pidora\n    \"raspbian\"      Raspbian\n    \"oracle\"        Oracle Linux (and Oracle Enterprise Linux)\n    \"scientific\"    Scientific Linux\n    \"slackware\"     Slackware\n    \"xenserver\"     XenServer\n    \"openbsd\"       OpenBSD\n    \"netbsd\"        NetBSD\n    \"freebsd\"       FreeBSD\n    ==============  =========================================\n\n    If you have a need to get distros for reliable IDs added into this set,\n    or if you find that the :func:`distro.id` function returns a different\n    distro ID for one of the listed distros, please create an issue in the\n    `distro issue tracker`_.\n\n    **Lookup hierarchy and transformations:**\n\n    First, the ID is obtained from the following sources, in the specified\n    order. The first available and non-empty value is used:\n\n    * the value of the \"ID\" attribute of the os-release file,\n\n    * the value of the \"Distributor ID\" attribute returned by the lsb_release\n      command,\n\n    * the first part of the file name of the distro release file,\n\n    The so determined ID value then passes the following transformations,\n    before it is returned by this method:\n\n    * it is translated to lower case,\n\n    * blanks (which should not be there anyway) are translated to underscores,\n\n    * a normalization of the ID is performed, based upon\n      `normalization tables`_. The purpose of this normalization is to ensure\n      that the ID is as reliable as possible, even across incompatible changes\n      in the OS distributions. A common reason for an incompatible change is\n      the addition of an os-release file, or the addition of the lsb_release\n      command, with ID values that differ from what was previously determined\n      from the distro release file name.\n    \"\"\"\n    return _distro.id()\n\n\ndef name(pretty=False):\n    \"\"\"\n    Return the name of the current OS distribution, as a human-readable\n    string.\n\n    If *pretty* is false, the name is returned without version or codename.\n    (e.g. \"CentOS Linux\")\n\n    If *pretty* is true, the version and codename are appended.\n    (e.g. \"CentOS Linux 7.1.1503 (Core)\")\n\n    **Lookup hierarchy:**\n\n    The name is obtained from the following sources, in the specified order.\n    The first available and non-empty value is used:\n\n    * If *pretty* is false:\n\n      - the value of the \"NAME\" attribute of the os-release file,\n\n      - the value of the \"Distributor ID\" attribute returned by the lsb_release\n        command,\n\n      - the value of the \"<name>\" field of the distro release file.\n\n    * If *pretty* is true:\n\n      - the value of the \"PRETTY_NAME\" attribute of the os-release file,\n\n      - the value of the \"Description\" attribute returned by the lsb_release\n        command,\n\n      - the value of the \"<name>\" field of the distro release file, appended\n        with the value of the pretty version (\"<version_id>\" and \"<codename>\"\n        fields) of the distro release file, if available.\n    \"\"\"\n    return _distro.name(pretty)\n\n\ndef version(pretty=False, best=False):\n    \"\"\"\n    Return the version of the current OS distribution, as a human-readable\n    string.\n\n    If *pretty* is false, the version is returned without codename (e.g.\n    \"7.0\").\n\n    If *pretty* is true, the codename in parenthesis is appended, if the\n    codename is non-empty (e.g. \"7.0 (Maipo)\").\n\n    Some distributions provide version numbers with different precisions in\n    the different sources of distribution information. Examining the different\n    sources in a fixed priority order does not always yield the most precise\n    version (e.g. for Debian 8.2, or CentOS 7.1).\n\n    The *best* parameter can be used to control the approach for the returned\n    version:\n\n    If *best* is false, the first non-empty version number in priority order of\n    the examined sources is returned.\n\n    If *best* is true, the most precise version number out of all examined\n    sources is returned.\n\n    **Lookup hierarchy:**\n\n    In all cases, the version number is obtained from the following sources.\n    If *best* is false, this order represents the priority order:\n\n    * the value of the \"VERSION_ID\" attribute of the os-release file,\n    * the value of the \"Release\" attribute returned by the lsb_release\n      command,\n    * the version number parsed from the \"<version_id>\" field of the first line\n      of the distro release file,\n    * the version number parsed from the \"PRETTY_NAME\" attribute of the\n      os-release file, if it follows the format of the distro release files.\n    * the version number parsed from the \"Description\" attribute returned by\n      the lsb_release command, if it follows the format of the distro release\n      files.\n    \"\"\"\n    return _distro.version(pretty, best)\n\n\ndef version_parts(best=False):\n    \"\"\"\n    Return the version of the current OS distribution as a tuple\n    ``(major, minor, build_number)`` with items as follows:\n\n    * ``major``:  The result of :func:`distro.major_version`.\n\n    * ``minor``:  The result of :func:`distro.minor_version`.\n\n    * ``build_number``:  The result of :func:`distro.build_number`.\n\n    For a description of the *best* parameter, see the :func:`distro.version`\n    method.\n    \"\"\"\n    return _distro.version_parts(best)\n\n\ndef major_version(best=False):\n    \"\"\"\n    Return the major version of the current OS distribution, as a string,\n    if provided.\n    Otherwise, the empty string is returned. The major version is the first\n    part of the dot-separated version string.\n\n    For a description of the *best* parameter, see the :func:`distro.version`\n    method.\n    \"\"\"\n    return _distro.major_version(best)\n\n\ndef minor_version(best=False):\n    \"\"\"\n    Return the minor version of the current OS distribution, as a string,\n    if provided.\n    Otherwise, the empty string is returned. The minor version is the second\n    part of the dot-separated version string.\n\n    For a description of the *best* parameter, see the :func:`distro.version`\n    method.\n    \"\"\"\n    return _distro.minor_version(best)\n\n\ndef build_number(best=False):\n    \"\"\"\n    Return the build number of the current OS distribution, as a string,\n    if provided.\n    Otherwise, the empty string is returned. The build number is the third part\n    of the dot-separated version string.\n\n    For a description of the *best* parameter, see the :func:`distro.version`\n    method.\n    \"\"\"\n    return _distro.build_number(best)\n\n\ndef like():\n    \"\"\"\n    Return a space-separated list of distro IDs of distributions that are\n    closely related to the current OS distribution in regards to packaging\n    and programming interfaces, for example distributions the current\n    distribution is a derivative from.\n\n    **Lookup hierarchy:**\n\n    This information item is only provided by the os-release file.\n    For details, see the description of the \"ID_LIKE\" attribute in the\n    `os-release man page\n    <http://www.freedesktop.org/software/systemd/man/os-release.html>`_.\n    \"\"\"\n    return _distro.like()\n\n\ndef codename():\n    \"\"\"\n    Return the codename for the release of the current OS distribution,\n    as a string.\n\n    If the distribution does not have a codename, an empty string is returned.\n\n    Note that the returned codename is not always really a codename. For\n    example, openSUSE returns \"x86_64\". This function does not handle such\n    cases in any special way and just returns the string it finds, if any.\n\n    **Lookup hierarchy:**\n\n    * the codename within the \"VERSION\" attribute of the os-release file, if\n      provided,\n\n    * the value of the \"Codename\" attribute returned by the lsb_release\n      command,\n\n    * the value of the \"<codename>\" field of the distro release file.\n    \"\"\"\n    return _distro.codename()\n\n\ndef info(pretty=False, best=False):\n    \"\"\"\n    Return certain machine-readable information items about the current OS\n    distribution in a dictionary, as shown in the following example:\n\n    .. sourcecode:: python\n\n        {\n            'id': 'rhel',\n            'version': '7.0',\n            'version_parts': {\n                'major': '7',\n                'minor': '0',\n                'build_number': ''\n            },\n            'like': 'fedora',\n            'codename': 'Maipo'\n        }\n\n    The dictionary structure and keys are always the same, regardless of which\n    information items are available in the underlying data sources. The values\n    for the various keys are as follows:\n\n    * ``id``:  The result of :func:`distro.id`.\n\n    * ``version``:  The result of :func:`distro.version`.\n\n    * ``version_parts -> major``:  The result of :func:`distro.major_version`.\n\n    * ``version_parts -> minor``:  The result of :func:`distro.minor_version`.\n\n    * ``version_parts -> build_number``:  The result of\n      :func:`distro.build_number`.\n\n    * ``like``:  The result of :func:`distro.like`.\n\n    * ``codename``:  The result of :func:`distro.codename`.\n\n    For a description of the *pretty* and *best* parameters, see the\n    :func:`distro.version` method.\n    \"\"\"\n    return _distro.info(pretty, best)\n\n\ndef os_release_info():\n    \"\"\"\n    Return a dictionary containing key-value pairs for the information items\n    from the os-release file data source of the current OS distribution.\n\n    See `os-release file`_ for details about these information items.\n    \"\"\"\n    return _distro.os_release_info()\n\n\ndef lsb_release_info():\n    \"\"\"\n    Return a dictionary containing key-value pairs for the information items\n    from the lsb_release command data source of the current OS distribution.\n\n    See `lsb_release command output`_ for details about these information\n    items.\n    \"\"\"\n    return _distro.lsb_release_info()\n\n\ndef distro_release_info():\n    \"\"\"\n    Return a dictionary containing key-value pairs for the information items\n    from the distro release file data source of the current OS distribution.\n\n    See `distro release file`_ for details about these information items.\n    \"\"\"\n    return _distro.distro_release_info()\n\n\ndef uname_info():\n    \"\"\"\n    Return a dictionary containing key-value pairs for the information items\n    from the distro release file data source of the current OS distribution.\n    \"\"\"\n    return _distro.uname_info()\n\n\ndef os_release_attr(attribute):\n    \"\"\"\n    Return a single named information item from the os-release file data source\n    of the current OS distribution.\n\n    Parameters:\n\n    * ``attribute`` (string): Key of the information item.\n\n    Returns:\n\n    * (string): Value of the information item, if the item exists.\n      The empty string, if the item does not exist.\n\n    See `os-release file`_ for details about these information items.\n    \"\"\"\n    return _distro.os_release_attr(attribute)\n\n\ndef lsb_release_attr(attribute):\n    \"\"\"\n    Return a single named information item from the lsb_release command output\n    data source of the current OS distribution.\n\n    Parameters:\n\n    * ``attribute`` (string): Key of the information item.\n\n    Returns:\n\n    * (string): Value of the information item, if the item exists.\n      The empty string, if the item does not exist.\n\n    See `lsb_release command output`_ for details about these information\n    items.\n    \"\"\"\n    return _distro.lsb_release_attr(attribute)\n\n\ndef distro_release_attr(attribute):\n    \"\"\"\n    Return a single named information item from the distro release file\n    data source of the current OS distribution.\n\n    Parameters:\n\n    * ``attribute`` (string): Key of the information item.\n\n    Returns:\n\n    * (string): Value of the information item, if the item exists.\n      The empty string, if the item does not exist.\n\n    See `distro release file`_ for details about these information items.\n    \"\"\"\n    return _distro.distro_release_attr(attribute)\n\n\ndef uname_attr(attribute):\n    \"\"\"\n    Return a single named information item from the distro release file\n    data source of the current OS distribution.\n\n    Parameters:\n\n    * ``attribute`` (string): Key of the information item.\n\n    Returns:\n\n    * (string): Value of the information item, if the item exists.\n                The empty string, if the item does not exist.\n    \"\"\"\n    return _distro.uname_attr(attribute)\n\n\nclass cached_property(object):\n    \"\"\"A version of @property which caches the value.  On access, it calls the\n    underlying function and sets the value in `__dict__` so future accesses\n    will not re-call the property.\n    \"\"\"\n    def __init__(self, f):\n        self._fname = f.__name__\n        self._f = f\n\n    def __get__(self, obj, owner):\n        assert obj is not None, 'call {} on an instance'.format(self._fname)\n        ret = obj.__dict__[self._fname] = self._f(obj)\n        return ret\n\n\nclass LinuxDistribution(object):\n    \"\"\"\n    Provides information about a OS distribution.\n\n    This package creates a private module-global instance of this class with\n    default initialization arguments, that is used by the\n    `consolidated accessor functions`_ and `single source accessor functions`_.\n    By using default initialization arguments, that module-global instance\n    returns data about the current OS distribution (i.e. the distro this\n    package runs on).\n\n    Normally, it is not necessary to create additional instances of this class.\n    However, in situations where control is needed over the exact data sources\n    that are used, instances of this class can be created with a specific\n    distro release file, or a specific os-release file, or without invoking the\n    lsb_release command.\n    \"\"\"\n\n    def __init__(self,\n                 include_lsb=True,\n                 os_release_file='',\n                 distro_release_file='',\n                 include_uname=True):\n        \"\"\"\n        The initialization method of this class gathers information from the\n        available data sources, and stores that in private instance attributes.\n        Subsequent access to the information items uses these private instance\n        attributes, so that the data sources are read only once.\n\n        Parameters:\n\n        * ``include_lsb`` (bool): Controls whether the\n          `lsb_release command output`_ is included as a data source.\n\n          If the lsb_release command is not available in the program execution\n          path, the data source for the lsb_release command will be empty.\n\n        * ``os_release_file`` (string): The path name of the\n          `os-release file`_ that is to be used as a data source.\n\n          An empty string (the default) will cause the default path name to\n          be used (see `os-release file`_ for details).\n\n          If the specified or defaulted os-release file does not exist, the\n          data source for the os-release file will be empty.\n\n        * ``distro_release_file`` (string): The path name of the\n          `distro release file`_ that is to be used as a data source.\n\n          An empty string (the default) will cause a default search algorithm\n          to be used (see `distro release file`_ for details).\n\n          If the specified distro release file does not exist, or if no default\n          distro release file can be found, the data source for the distro\n          release file will be empty.\n\n        * ``include_name`` (bool): Controls whether uname command output is\n          included as a data source. If the uname command is not available in\n          the program execution path the data source for the uname command will\n          be empty.\n\n        Public instance attributes:\n\n        * ``os_release_file`` (string): The path name of the\n          `os-release file`_ that is actually used as a data source. The\n          empty string if no distro release file is used as a data source.\n\n        * ``distro_release_file`` (string): The path name of the\n          `distro release file`_ that is actually used as a data source. The\n          empty string if no distro release file is used as a data source.\n\n        * ``include_lsb`` (bool): The result of the ``include_lsb`` parameter.\n          This controls whether the lsb information will be loaded.\n\n        * ``include_uname`` (bool): The result of the ``include_uname``\n          parameter. This controls whether the uname information will\n          be loaded.\n\n        Raises:\n\n        * :py:exc:`IOError`: Some I/O issue with an os-release file or distro\n          release file.\n\n        * :py:exc:`subprocess.CalledProcessError`: The lsb_release command had\n          some issue (other than not being available in the program execution\n          path).\n\n        * :py:exc:`UnicodeError`: A data source has unexpected characters or\n          uses an unexpected encoding.\n        \"\"\"\n        self.os_release_file = os_release_file or \\\n            os.path.join(_UNIXCONFDIR, _OS_RELEASE_BASENAME)\n        self.distro_release_file = distro_release_file or ''  # updated later\n        self.include_lsb = include_lsb\n        self.include_uname = include_uname\n\n    def __repr__(self):\n        \"\"\"Return repr of all info\n        \"\"\"\n        return \\\n            \"LinuxDistribution(\" \\\n            \"os_release_file={self.os_release_file!r}, \" \\\n            \"distro_release_file={self.distro_release_file!r}, \" \\\n            \"include_lsb={self.include_lsb!r}, \" \\\n            \"include_uname={self.include_uname!r}, \" \\\n            \"_os_release_info={self._os_release_info!r}, \" \\\n            \"_lsb_release_info={self._lsb_release_info!r}, \" \\\n            \"_distro_release_info={self._distro_release_info!r}, \" \\\n            \"_uname_info={self._uname_info!r})\".format(\n                self=self)\n\n    def linux_distribution(self, full_distribution_name=True):\n        \"\"\"\n        Return information about the OS distribution that is compatible\n        with Python's :func:`platform.linux_distribution`, supporting a subset\n        of its parameters.\n\n        For details, see :func:`distro.linux_distribution`.\n        \"\"\"\n        return (\n            self.name() if full_distribution_name else self.id(),\n            self.version(),\n            self.codename()\n        )\n\n    def id(self):\n        \"\"\"Return the distro ID of the OS distribution, as a string.\n\n        For details, see :func:`distro.id`.\n        \"\"\"\n        def normalize(distro_id, table):\n            distro_id = distro_id.lower().replace(' ', '_')\n            return table.get(distro_id, distro_id)\n\n        distro_id = self.os_release_attr('id')\n        if distro_id:\n            return normalize(distro_id, NORMALIZED_OS_ID)\n\n        distro_id = self.lsb_release_attr('distributor_id')\n        if distro_id:\n            return normalize(distro_id, NORMALIZED_LSB_ID)\n\n        distro_id = self.distro_release_attr('id')\n        if distro_id:\n            return normalize(distro_id, NORMALIZED_DISTRO_ID)\n\n        distro_id = self.uname_attr('id')\n        if distro_id:\n            return normalize(distro_id, NORMALIZED_DISTRO_ID)\n\n        return ''\n\n    def name(self, pretty=False):\n        \"\"\"\n        Return the name of the OS distribution, as a string.\n\n        For details, see :func:`distro.name`.\n        \"\"\"\n        name = self.os_release_attr('name') \\\n            or self.lsb_release_attr('distributor_id') \\\n            or self.distro_release_attr('name') \\\n            or self.uname_attr('name')\n        if pretty:\n            name = self.os_release_attr('pretty_name') \\\n                or self.lsb_release_attr('description')\n            if not name:\n                name = self.distro_release_attr('name') \\\n                       or self.uname_attr('name')\n                version = self.version(pretty=True)\n                if version:\n                    name = name + ' ' + version\n        return name or ''\n\n    def version(self, pretty=False, best=False):\n        \"\"\"\n        Return the version of the OS distribution, as a string.\n\n        For details, see :func:`distro.version`.\n        \"\"\"\n        versions = [\n            self.os_release_attr('version_id'),\n            self.lsb_release_attr('release'),\n            self.distro_release_attr('version_id'),\n            self._parse_distro_release_content(\n                self.os_release_attr('pretty_name')).get('version_id', ''),\n            self._parse_distro_release_content(\n                self.lsb_release_attr('description')).get('version_id', ''),\n            self.uname_attr('release')\n        ]\n        version = ''\n        if best:\n            # This algorithm uses the last version in priority order that has\n            # the best precision. If the versions are not in conflict, that\n            # does not matter; otherwise, using the last one instead of the\n            # first one might be considered a surprise.\n            for v in versions:\n                if v.count(\".\") > version.count(\".\") or version == '':\n                    version = v\n        else:\n            for v in versions:\n                if v != '':\n                    version = v\n                    break\n        if pretty and version and self.codename():\n            version = u'{0} ({1})'.format(version, self.codename())\n        return version\n\n    def version_parts(self, best=False):\n        \"\"\"\n        Return the version of the OS distribution, as a tuple of version\n        numbers.\n\n        For details, see :func:`distro.version_parts`.\n        \"\"\"\n        version_str = self.version(best=best)\n        if version_str:\n            version_regex = re.compile(r'(\\d+)\\.?(\\d+)?\\.?(\\d+)?')\n            matches = version_regex.match(version_str)\n            if matches:\n                major, minor, build_number = matches.groups()\n                return major, minor or '', build_number or ''\n        return '', '', ''\n\n    def major_version(self, best=False):\n        \"\"\"\n        Return the major version number of the current distribution.\n\n        For details, see :func:`distro.major_version`.\n        \"\"\"\n        return self.version_parts(best)[0]\n\n    def minor_version(self, best=False):\n        \"\"\"\n        Return the minor version number of the current distribution.\n\n        For details, see :func:`distro.minor_version`.\n        \"\"\"\n        return self.version_parts(best)[1]\n\n    def build_number(self, best=False):\n        \"\"\"\n        Return the build number of the current distribution.\n\n        For details, see :func:`distro.build_number`.\n        \"\"\"\n        return self.version_parts(best)[2]\n\n    def like(self):\n        \"\"\"\n        Return the IDs of distributions that are like the OS distribution.\n\n        For details, see :func:`distro.like`.\n        \"\"\"\n        return self.os_release_attr('id_like') or ''\n\n    def codename(self):\n        \"\"\"\n        Return the codename of the OS distribution.\n\n        For details, see :func:`distro.codename`.\n        \"\"\"\n        return self.os_release_attr('codename') \\\n            or self.lsb_release_attr('codename') \\\n            or self.distro_release_attr('codename') \\\n            or ''\n\n    def info(self, pretty=False, best=False):\n        \"\"\"\n        Return certain machine-readable information about the OS\n        distribution.\n\n        For details, see :func:`distro.info`.\n        \"\"\"\n        return dict(\n            id=self.id(),\n            version=self.version(pretty, best),\n            version_parts=dict(\n                major=self.major_version(best),\n                minor=self.minor_version(best),\n                build_number=self.build_number(best)\n            ),\n            like=self.like(),\n            codename=self.codename(),\n        )\n\n    def os_release_info(self):\n        \"\"\"\n        Return a dictionary containing key-value pairs for the information\n        items from the os-release file data source of the OS distribution.\n\n        For details, see :func:`distro.os_release_info`.\n        \"\"\"\n        return self._os_release_info\n\n    def lsb_release_info(self):\n        \"\"\"\n        Return a dictionary containing key-value pairs for the information\n        items from the lsb_release command data source of the OS\n        distribution.\n\n        For details, see :func:`distro.lsb_release_info`.\n        \"\"\"\n        return self._lsb_release_info\n\n    def distro_release_info(self):\n        \"\"\"\n        Return a dictionary containing key-value pairs for the information\n        items from the distro release file data source of the OS\n        distribution.\n\n        For details, see :func:`distro.distro_release_info`.\n        \"\"\"\n        return self._distro_release_info\n\n    def uname_info(self):\n        \"\"\"\n        Return a dictionary containing key-value pairs for the information\n        items from the uname command data source of the OS distribution.\n\n        For details, see :func:`distro.uname_info`.\n        \"\"\"\n\n    def os_release_attr(self, attribute):\n        \"\"\"\n        Return a single named information item from the os-release file data\n        source of the OS distribution.\n\n        For details, see :func:`distro.os_release_attr`.\n        \"\"\"\n        return self._os_release_info.get(attribute, '')\n\n    def lsb_release_attr(self, attribute):\n        \"\"\"\n        Return a single named information item from the lsb_release command\n        output data source of the OS distribution.\n\n        For details, see :func:`distro.lsb_release_attr`.\n        \"\"\"\n        return self._lsb_release_info.get(attribute, '')\n\n    def distro_release_attr(self, attribute):\n        \"\"\"\n        Return a single named information item from the distro release file\n        data source of the OS distribution.\n\n        For details, see :func:`distro.distro_release_attr`.\n        \"\"\"\n        return self._distro_release_info.get(attribute, '')\n\n    def uname_attr(self, attribute):\n        \"\"\"\n        Return a single named information item from the uname command\n        output data source of the OS distribution.\n\n        For details, see :func:`distro.uname_release_attr`.\n        \"\"\"\n        return self._uname_info.get(attribute, '')\n\n    @cached_property\n    def _os_release_info(self):\n        \"\"\"\n        Get the information items from the specified os-release file.\n\n        Returns:\n            A dictionary containing all information items.\n        \"\"\"\n        if os.path.isfile(self.os_release_file):\n            with open(self.os_release_file) as release_file:\n                return self._parse_os_release_content(release_file)\n        return {}\n\n    @staticmethod\n    def _parse_os_release_content(lines):\n        \"\"\"\n        Parse the lines of an os-release file.\n\n        Parameters:\n\n        * lines: Iterable through the lines in the os-release file.\n                 Each line must be a unicode string or a UTF-8 encoded byte\n                 string.\n\n        Returns:\n            A dictionary containing all information items.\n        \"\"\"\n        props = {}\n        lexer = shlex.shlex(lines, posix=True)\n        lexer.whitespace_split = True\n\n        # The shlex module defines its `wordchars` variable using literals,\n        # making it dependent on the encoding of the Python source file.\n        # In Python 2.6 and 2.7, the shlex source file is encoded in\n        # 'iso-8859-1', and the `wordchars` variable is defined as a byte\n        # string. This causes a UnicodeDecodeError to be raised when the\n        # parsed content is a unicode object. The following fix resolves that\n        # (... but it should be fixed in shlex...):\n        if sys.version_info[0] == 2 and isinstance(lexer.wordchars, bytes):\n            lexer.wordchars = lexer.wordchars.decode('iso-8859-1')\n\n        tokens = list(lexer)\n        for token in tokens:\n            # At this point, all shell-like parsing has been done (i.e.\n            # comments processed, quotes and backslash escape sequences\n            # processed, multi-line values assembled, trailing newlines\n            # stripped, etc.), so the tokens are now either:\n            # * variable assignments: var=value\n            # * commands or their arguments (not allowed in os-release)\n            if '=' in token:\n                k, v = token.split('=', 1)\n                if isinstance(v, bytes):\n                    v = v.decode('utf-8')\n                props[k.lower()] = v\n                if k == 'VERSION':\n                    # this handles cases in which the codename is in\n                    # the `(CODENAME)` (rhel, centos, fedora) format\n                    # or in the `, CODENAME` format (Ubuntu).\n                    codename = re.search(r'(\\(\\D+\\))|,(\\s+)?\\D+', v)\n                    if codename:\n                        codename = codename.group()\n                        codename = codename.strip('()')\n                        codename = codename.strip(',')\n                        codename = codename.strip()\n                        # codename appears within paranthese.\n                        props['codename'] = codename\n                    else:\n                        props['codename'] = ''\n            else:\n                # Ignore any tokens that are not variable assignments\n                pass\n        return props\n\n    @cached_property\n    def _lsb_release_info(self):\n        \"\"\"\n        Get the information items from the lsb_release command output.\n\n        Returns:\n            A dictionary containing all information items.\n        \"\"\"\n        if not self.include_lsb:\n            return {}\n        with open(os.devnull, 'w') as devnull:\n            try:\n                cmd = ('lsb_release', '-a')\n                stdout = subprocess.check_output(cmd, stderr=devnull)\n            except OSError:  # Command not found\n                return {}\n        content = stdout.decode(sys.getfilesystemencoding()).splitlines()\n        return self._parse_lsb_release_content(content)\n\n    @staticmethod\n    def _parse_lsb_release_content(lines):\n        \"\"\"\n        Parse the output of the lsb_release command.\n\n        Parameters:\n\n        * lines: Iterable through the lines of the lsb_release output.\n                 Each line must be a unicode string or a UTF-8 encoded byte\n                 string.\n\n        Returns:\n            A dictionary containing all information items.\n        \"\"\"\n        props = {}\n        for line in lines:\n            kv = line.strip('\\n').split(':', 1)\n            if len(kv) != 2:\n                # Ignore lines without colon.\n                continue\n            k, v = kv\n            props.update({k.replace(' ', '_').lower(): v.strip()})\n        return props\n\n    @cached_property\n    def _uname_info(self):\n        with open(os.devnull, 'w') as devnull:\n            try:\n                cmd = ('uname', '-rs')\n                stdout = subprocess.check_output(cmd, stderr=devnull)\n            except OSError:\n                return {}\n        content = stdout.decode(sys.getfilesystemencoding()).splitlines()\n        return self._parse_uname_content(content)\n\n    @staticmethod\n    def _parse_uname_content(lines):\n        props = {}\n        match = re.search(r'^([^\\s]+)\\s+([\\d\\.]+)', lines[0].strip())\n        if match:\n            name, version = match.groups()\n\n            # This is to prevent the Linux kernel version from\n            # appearing as the 'best' version on otherwise\n            # identifiable distributions.\n            if name == 'Linux':\n                return {}\n            props['id'] = name.lower()\n            props['name'] = name\n            props['release'] = version\n        return props\n\n    @cached_property\n    def _distro_release_info(self):\n        \"\"\"\n        Get the information items from the specified distro release file.\n\n        Returns:\n            A dictionary containing all information items.\n        \"\"\"\n        if self.distro_release_file:\n            # If it was specified, we use it and parse what we can, even if\n            # its file name or content does not match the expected pattern.\n            distro_info = self._parse_distro_release_file(\n                self.distro_release_file)\n            basename = os.path.basename(self.distro_release_file)\n            # The file name pattern for user-specified distro release files\n            # is somewhat more tolerant (compared to when searching for the\n            # file), because we want to use what was specified as best as\n            # possible.\n            match = _DISTRO_RELEASE_BASENAME_PATTERN.match(basename)\n            if match:\n                distro_info['id'] = match.group(1)\n            return distro_info\n        else:\n            try:\n                basenames = os.listdir(_UNIXCONFDIR)\n                # We sort for repeatability in cases where there are multiple\n                # distro specific files; e.g. CentOS, Oracle, Enterprise all\n                # containing `redhat-release` on top of their own.\n                basenames.sort()\n            except OSError:\n                # This may occur when /etc is not readable but we can't be\n                # sure about the *-release files. Check common entries of\n                # /etc for information. If they turn out to not be there the\n                # error is handled in `_parse_distro_release_file()`.\n                basenames = ['SuSE-release',\n                             'arch-release',\n                             'base-release',\n                             'centos-release',\n                             'fedora-release',\n                             'gentoo-release',\n                             'mageia-release',\n                             'mandrake-release',\n                             'mandriva-release',\n                             'mandrivalinux-release',\n                             'manjaro-release',\n                             'oracle-release',\n                             'redhat-release',\n                             'sl-release',\n                             'slackware-version']\n            for basename in basenames:\n                if basename in _DISTRO_RELEASE_IGNORE_BASENAMES:\n                    continue\n                match = _DISTRO_RELEASE_BASENAME_PATTERN.match(basename)\n                if match:\n                    filepath = os.path.join(_UNIXCONFDIR, basename)\n                    distro_info = self._parse_distro_release_file(filepath)\n                    if 'name' in distro_info:\n                        # The name is always present if the pattern matches\n                        self.distro_release_file = filepath\n                        distro_info['id'] = match.group(1)\n                        return distro_info\n            return {}\n\n    def _parse_distro_release_file(self, filepath):\n        \"\"\"\n        Parse a distro release file.\n\n        Parameters:\n\n        * filepath: Path name of the distro release file.\n\n        Returns:\n            A dictionary containing all information items.\n        \"\"\"\n        try:\n            with open(filepath) as fp:\n                # Only parse the first line. For instance, on SLES there\n                # are multiple lines. We don't want them...\n                return self._parse_distro_release_content(fp.readline())\n        except (OSError, IOError):\n            # Ignore not being able to read a specific, seemingly version\n            # related file.\n            # See https://github.com/nir0s/distro/issues/162\n            return {}\n\n    @staticmethod\n    def _parse_distro_release_content(line):\n        \"\"\"\n        Parse a line from a distro release file.\n\n        Parameters:\n        * line: Line from the distro release file. Must be a unicode string\n                or a UTF-8 encoded byte string.\n\n        Returns:\n            A dictionary containing all information items.\n        \"\"\"\n        if isinstance(line, bytes):\n            line = line.decode('utf-8')\n        matches = _DISTRO_RELEASE_CONTENT_REVERSED_PATTERN.match(\n            line.strip()[::-1])\n        distro_info = {}\n        if matches:\n            # regexp ensures non-None\n            distro_info['name'] = matches.group(3)[::-1]\n            if matches.group(2):\n                distro_info['version_id'] = matches.group(2)[::-1]\n            if matches.group(1):\n                distro_info['codename'] = matches.group(1)[::-1]\n        elif line:\n            distro_info['name'] = line.strip()\n        return distro_info\n\n\n_distro = LinuxDistribution()\n\n\ndef main():\n    logger = logging.getLogger(__name__)\n    logger.setLevel(logging.DEBUG)\n    logger.addHandler(logging.StreamHandler(sys.stdout))\n\n    parser = argparse.ArgumentParser(description=\"OS distro info tool\")\n    parser.add_argument(\n        '--json',\n        '-j',\n        help=\"Output in machine readable format\",\n        action=\"store_true\")\n    args = parser.parse_args()\n\n    if args.json:\n        logger.info(json.dumps(info(), indent=4, sort_keys=True))\n    else:\n        logger.info('Name: %s', name(pretty=True))\n        distribution_version = version(pretty=True)\n        logger.info('Version: %s', distribution_version)\n        distribution_codename = codename()\n        logger.info('Codename: %s', distribution_codename)\n\n\nif __name__ == '__main__':\n    main()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/__init__.py",
    "content": "\"\"\"\nHTML parsing library based on the `WHATWG HTML specification\n<https://whatwg.org/html>`_. The parser is designed to be compatible with\nexisting HTML found in the wild and implements well-defined error recovery that\nis largely compatible with modern desktop web browsers.\n\nExample usage::\n\n    from pip._vendor import html5lib\n    with open(\"my_document.html\", \"rb\") as f:\n        tree = html5lib.parse(f)\n\nFor convenience, this module re-exports the following names:\n\n* :func:`~.html5parser.parse`\n* :func:`~.html5parser.parseFragment`\n* :class:`~.html5parser.HTMLParser`\n* :func:`~.treebuilders.getTreeBuilder`\n* :func:`~.treewalkers.getTreeWalker`\n* :func:`~.serializer.serialize`\n\"\"\"\n\nfrom __future__ import absolute_import, division, unicode_literals\n\nfrom .html5parser import HTMLParser, parse, parseFragment\nfrom .treebuilders import getTreeBuilder\nfrom .treewalkers import getTreeWalker\nfrom .serializer import serialize\n\n__all__ = [\"HTMLParser\", \"parse\", \"parseFragment\", \"getTreeBuilder\",\n           \"getTreeWalker\", \"serialize\"]\n\n# this has to be at the top level, see how setup.py parses this\n#: Distribution version number.\n__version__ = \"1.0.1\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/_ihatexml.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nimport re\nimport warnings\n\nfrom .constants import DataLossWarning\n\nbaseChar = \"\"\"\n[#x0041-#x005A] | [#x0061-#x007A] | [#x00C0-#x00D6] | [#x00D8-#x00F6] |\n[#x00F8-#x00FF] | [#x0100-#x0131] | [#x0134-#x013E] | [#x0141-#x0148] |\n[#x014A-#x017E] | [#x0180-#x01C3] | [#x01CD-#x01F0] | [#x01F4-#x01F5] |\n[#x01FA-#x0217] | [#x0250-#x02A8] | [#x02BB-#x02C1] | #x0386 |\n[#x0388-#x038A] | #x038C | [#x038E-#x03A1] | [#x03A3-#x03CE] |\n[#x03D0-#x03D6] | #x03DA | #x03DC | #x03DE | #x03E0 | [#x03E2-#x03F3] |\n[#x0401-#x040C] | [#x040E-#x044F] | [#x0451-#x045C] | [#x045E-#x0481] |\n[#x0490-#x04C4] | [#x04C7-#x04C8] | [#x04CB-#x04CC] | [#x04D0-#x04EB] |\n[#x04EE-#x04F5] | [#x04F8-#x04F9] | [#x0531-#x0556] | #x0559 |\n[#x0561-#x0586] | [#x05D0-#x05EA] | [#x05F0-#x05F2] | [#x0621-#x063A] |\n[#x0641-#x064A] | [#x0671-#x06B7] | [#x06BA-#x06BE] | [#x06C0-#x06CE] |\n[#x06D0-#x06D3] | #x06D5 | [#x06E5-#x06E6] | [#x0905-#x0939] | #x093D |\n[#x0958-#x0961] | [#x0985-#x098C] | [#x098F-#x0990] | [#x0993-#x09A8] |\n[#x09AA-#x09B0] | #x09B2 | [#x09B6-#x09B9] | [#x09DC-#x09DD] |\n[#x09DF-#x09E1] | [#x09F0-#x09F1] | [#x0A05-#x0A0A] | [#x0A0F-#x0A10] |\n[#x0A13-#x0A28] | [#x0A2A-#x0A30] | [#x0A32-#x0A33] | [#x0A35-#x0A36] |\n[#x0A38-#x0A39] | [#x0A59-#x0A5C] | #x0A5E | [#x0A72-#x0A74] |\n[#x0A85-#x0A8B] | #x0A8D | [#x0A8F-#x0A91] | [#x0A93-#x0AA8] |\n[#x0AAA-#x0AB0] | [#x0AB2-#x0AB3] | [#x0AB5-#x0AB9] | #x0ABD | #x0AE0 |\n[#x0B05-#x0B0C] | [#x0B0F-#x0B10] | [#x0B13-#x0B28] | [#x0B2A-#x0B30] |\n[#x0B32-#x0B33] | [#x0B36-#x0B39] | #x0B3D | [#x0B5C-#x0B5D] |\n[#x0B5F-#x0B61] | [#x0B85-#x0B8A] | [#x0B8E-#x0B90] | [#x0B92-#x0B95] |\n[#x0B99-#x0B9A] | #x0B9C | [#x0B9E-#x0B9F] | [#x0BA3-#x0BA4] |\n[#x0BA8-#x0BAA] | [#x0BAE-#x0BB5] | [#x0BB7-#x0BB9] | [#x0C05-#x0C0C] |\n[#x0C0E-#x0C10] | [#x0C12-#x0C28] | [#x0C2A-#x0C33] | [#x0C35-#x0C39] |\n[#x0C60-#x0C61] | [#x0C85-#x0C8C] | [#x0C8E-#x0C90] | [#x0C92-#x0CA8] |\n[#x0CAA-#x0CB3] | [#x0CB5-#x0CB9] | #x0CDE | [#x0CE0-#x0CE1] |\n[#x0D05-#x0D0C] | [#x0D0E-#x0D10] | [#x0D12-#x0D28] | [#x0D2A-#x0D39] |\n[#x0D60-#x0D61] | [#x0E01-#x0E2E] | #x0E30 | [#x0E32-#x0E33] |\n[#x0E40-#x0E45] | [#x0E81-#x0E82] | #x0E84 | [#x0E87-#x0E88] | #x0E8A |\n#x0E8D | [#x0E94-#x0E97] | [#x0E99-#x0E9F] | [#x0EA1-#x0EA3] | #x0EA5 |\n#x0EA7 | [#x0EAA-#x0EAB] | [#x0EAD-#x0EAE] | #x0EB0 | [#x0EB2-#x0EB3] |\n#x0EBD | [#x0EC0-#x0EC4] | [#x0F40-#x0F47] | [#x0F49-#x0F69] |\n[#x10A0-#x10C5] | [#x10D0-#x10F6] | #x1100 | [#x1102-#x1103] |\n[#x1105-#x1107] | #x1109 | [#x110B-#x110C] | [#x110E-#x1112] | #x113C |\n#x113E | #x1140 | #x114C | #x114E | #x1150 | [#x1154-#x1155] | #x1159 |\n[#x115F-#x1161] | #x1163 | #x1165 | #x1167 | #x1169 | [#x116D-#x116E] |\n[#x1172-#x1173] | #x1175 | #x119E | #x11A8 | #x11AB | [#x11AE-#x11AF] |\n[#x11B7-#x11B8] | #x11BA | [#x11BC-#x11C2] | #x11EB | #x11F0 | #x11F9 |\n[#x1E00-#x1E9B] | [#x1EA0-#x1EF9] | [#x1F00-#x1F15] | [#x1F18-#x1F1D] |\n[#x1F20-#x1F45] | [#x1F48-#x1F4D] | [#x1F50-#x1F57] | #x1F59 | #x1F5B |\n#x1F5D | [#x1F5F-#x1F7D] | [#x1F80-#x1FB4] | [#x1FB6-#x1FBC] | #x1FBE |\n[#x1FC2-#x1FC4] | [#x1FC6-#x1FCC] | [#x1FD0-#x1FD3] | [#x1FD6-#x1FDB] |\n[#x1FE0-#x1FEC] | [#x1FF2-#x1FF4] | [#x1FF6-#x1FFC] | #x2126 |\n[#x212A-#x212B] | #x212E | [#x2180-#x2182] | [#x3041-#x3094] |\n[#x30A1-#x30FA] | [#x3105-#x312C] | [#xAC00-#xD7A3]\"\"\"\n\nideographic = \"\"\"[#x4E00-#x9FA5] | #x3007 | [#x3021-#x3029]\"\"\"\n\ncombiningCharacter = \"\"\"\n[#x0300-#x0345] | [#x0360-#x0361] | [#x0483-#x0486] | [#x0591-#x05A1] |\n[#x05A3-#x05B9] | [#x05BB-#x05BD] | #x05BF | [#x05C1-#x05C2] | #x05C4 |\n[#x064B-#x0652] | #x0670 | [#x06D6-#x06DC] | [#x06DD-#x06DF] |\n[#x06E0-#x06E4] | [#x06E7-#x06E8] | [#x06EA-#x06ED] | [#x0901-#x0903] |\n#x093C | [#x093E-#x094C] | #x094D | [#x0951-#x0954] | [#x0962-#x0963] |\n[#x0981-#x0983] | #x09BC | #x09BE | #x09BF | [#x09C0-#x09C4] |\n[#x09C7-#x09C8] | [#x09CB-#x09CD] | #x09D7 | [#x09E2-#x09E3] | #x0A02 |\n#x0A3C | #x0A3E | #x0A3F | [#x0A40-#x0A42] | [#x0A47-#x0A48] |\n[#x0A4B-#x0A4D] | [#x0A70-#x0A71] | [#x0A81-#x0A83] | #x0ABC |\n[#x0ABE-#x0AC5] | [#x0AC7-#x0AC9] | [#x0ACB-#x0ACD] | [#x0B01-#x0B03] |\n#x0B3C | [#x0B3E-#x0B43] | [#x0B47-#x0B48] | [#x0B4B-#x0B4D] |\n[#x0B56-#x0B57] | [#x0B82-#x0B83] | [#x0BBE-#x0BC2] | [#x0BC6-#x0BC8] |\n[#x0BCA-#x0BCD] | #x0BD7 | [#x0C01-#x0C03] | [#x0C3E-#x0C44] |\n[#x0C46-#x0C48] | [#x0C4A-#x0C4D] | [#x0C55-#x0C56] | [#x0C82-#x0C83] |\n[#x0CBE-#x0CC4] | [#x0CC6-#x0CC8] | [#x0CCA-#x0CCD] | [#x0CD5-#x0CD6] |\n[#x0D02-#x0D03] | [#x0D3E-#x0D43] | [#x0D46-#x0D48] | [#x0D4A-#x0D4D] |\n#x0D57 | #x0E31 | [#x0E34-#x0E3A] | [#x0E47-#x0E4E] | #x0EB1 |\n[#x0EB4-#x0EB9] | [#x0EBB-#x0EBC] | [#x0EC8-#x0ECD] | [#x0F18-#x0F19] |\n#x0F35 | #x0F37 | #x0F39 | #x0F3E | #x0F3F | [#x0F71-#x0F84] |\n[#x0F86-#x0F8B] | [#x0F90-#x0F95] | #x0F97 | [#x0F99-#x0FAD] |\n[#x0FB1-#x0FB7] | #x0FB9 | [#x20D0-#x20DC] | #x20E1 | [#x302A-#x302F] |\n#x3099 | #x309A\"\"\"\n\ndigit = \"\"\"\n[#x0030-#x0039] | [#x0660-#x0669] | [#x06F0-#x06F9] | [#x0966-#x096F] |\n[#x09E6-#x09EF] | [#x0A66-#x0A6F] | [#x0AE6-#x0AEF] | [#x0B66-#x0B6F] |\n[#x0BE7-#x0BEF] | [#x0C66-#x0C6F] | [#x0CE6-#x0CEF] | [#x0D66-#x0D6F] |\n[#x0E50-#x0E59] | [#x0ED0-#x0ED9] | [#x0F20-#x0F29]\"\"\"\n\nextender = \"\"\"\n#x00B7 | #x02D0 | #x02D1 | #x0387 | #x0640 | #x0E46 | #x0EC6 | #x3005 |\n#[#x3031-#x3035] | [#x309D-#x309E] | [#x30FC-#x30FE]\"\"\"\n\nletter = \" | \".join([baseChar, ideographic])\n\n# Without the\nname = \" | \".join([letter, digit, \".\", \"-\", \"_\", combiningCharacter,\n                   extender])\nnameFirst = \" | \".join([letter, \"_\"])\n\nreChar = re.compile(r\"#x([\\d|A-F]{4,4})\")\nreCharRange = re.compile(r\"\\[#x([\\d|A-F]{4,4})-#x([\\d|A-F]{4,4})\\]\")\n\n\ndef charStringToList(chars):\n    charRanges = [item.strip() for item in chars.split(\" | \")]\n    rv = []\n    for item in charRanges:\n        foundMatch = False\n        for regexp in (reChar, reCharRange):\n            match = regexp.match(item)\n            if match is not None:\n                rv.append([hexToInt(item) for item in match.groups()])\n                if len(rv[-1]) == 1:\n                    rv[-1] = rv[-1] * 2\n                foundMatch = True\n                break\n        if not foundMatch:\n            assert len(item) == 1\n\n            rv.append([ord(item)] * 2)\n    rv = normaliseCharList(rv)\n    return rv\n\n\ndef normaliseCharList(charList):\n    charList = sorted(charList)\n    for item in charList:\n        assert item[1] >= item[0]\n    rv = []\n    i = 0\n    while i < len(charList):\n        j = 1\n        rv.append(charList[i])\n        while i + j < len(charList) and charList[i + j][0] <= rv[-1][1] + 1:\n            rv[-1][1] = charList[i + j][1]\n            j += 1\n        i += j\n    return rv\n\n# We don't really support characters above the BMP :(\nmax_unicode = int(\"FFFF\", 16)\n\n\ndef missingRanges(charList):\n    rv = []\n    if charList[0] != 0:\n        rv.append([0, charList[0][0] - 1])\n    for i, item in enumerate(charList[:-1]):\n        rv.append([item[1] + 1, charList[i + 1][0] - 1])\n    if charList[-1][1] != max_unicode:\n        rv.append([charList[-1][1] + 1, max_unicode])\n    return rv\n\n\ndef listToRegexpStr(charList):\n    rv = []\n    for item in charList:\n        if item[0] == item[1]:\n            rv.append(escapeRegexp(chr(item[0])))\n        else:\n            rv.append(escapeRegexp(chr(item[0])) + \"-\" +\n                      escapeRegexp(chr(item[1])))\n    return \"[%s]\" % \"\".join(rv)\n\n\ndef hexToInt(hex_str):\n    return int(hex_str, 16)\n\n\ndef escapeRegexp(string):\n    specialCharacters = (\".\", \"^\", \"$\", \"*\", \"+\", \"?\", \"{\", \"}\",\n                         \"[\", \"]\", \"|\", \"(\", \")\", \"-\")\n    for char in specialCharacters:\n        string = string.replace(char, \"\\\\\" + char)\n\n    return string\n\n# output from the above\nnonXmlNameBMPRegexp = re.compile('[\\x00-,/:-@\\\\[-\\\\^`\\\\{-\\xb6\\xb8-\\xbf\\xd7\\xf7\\u0132-\\u0133\\u013f-\\u0140\\u0149\\u017f\\u01c4-\\u01cc\\u01f1-\\u01f3\\u01f6-\\u01f9\\u0218-\\u024f\\u02a9-\\u02ba\\u02c2-\\u02cf\\u02d2-\\u02ff\\u0346-\\u035f\\u0362-\\u0385\\u038b\\u038d\\u03a2\\u03cf\\u03d7-\\u03d9\\u03db\\u03dd\\u03df\\u03e1\\u03f4-\\u0400\\u040d\\u0450\\u045d\\u0482\\u0487-\\u048f\\u04c5-\\u04c6\\u04c9-\\u04ca\\u04cd-\\u04cf\\u04ec-\\u04ed\\u04f6-\\u04f7\\u04fa-\\u0530\\u0557-\\u0558\\u055a-\\u0560\\u0587-\\u0590\\u05a2\\u05ba\\u05be\\u05c0\\u05c3\\u05c5-\\u05cf\\u05eb-\\u05ef\\u05f3-\\u0620\\u063b-\\u063f\\u0653-\\u065f\\u066a-\\u066f\\u06b8-\\u06b9\\u06bf\\u06cf\\u06d4\\u06e9\\u06ee-\\u06ef\\u06fa-\\u0900\\u0904\\u093a-\\u093b\\u094e-\\u0950\\u0955-\\u0957\\u0964-\\u0965\\u0970-\\u0980\\u0984\\u098d-\\u098e\\u0991-\\u0992\\u09a9\\u09b1\\u09b3-\\u09b5\\u09ba-\\u09bb\\u09bd\\u09c5-\\u09c6\\u09c9-\\u09ca\\u09ce-\\u09d6\\u09d8-\\u09db\\u09de\\u09e4-\\u09e5\\u09f2-\\u0a01\\u0a03-\\u0a04\\u0a0b-\\u0a0e\\u0a11-\\u0a12\\u0a29\\u0a31\\u0a34\\u0a37\\u0a3a-\\u0a3b\\u0a3d\\u0a43-\\u0a46\\u0a49-\\u0a4a\\u0a4e-\\u0a58\\u0a5d\\u0a5f-\\u0a65\\u0a75-\\u0a80\\u0a84\\u0a8c\\u0a8e\\u0a92\\u0aa9\\u0ab1\\u0ab4\\u0aba-\\u0abb\\u0ac6\\u0aca\\u0ace-\\u0adf\\u0ae1-\\u0ae5\\u0af0-\\u0b00\\u0b04\\u0b0d-\\u0b0e\\u0b11-\\u0b12\\u0b29\\u0b31\\u0b34-\\u0b35\\u0b3a-\\u0b3b\\u0b44-\\u0b46\\u0b49-\\u0b4a\\u0b4e-\\u0b55\\u0b58-\\u0b5b\\u0b5e\\u0b62-\\u0b65\\u0b70-\\u0b81\\u0b84\\u0b8b-\\u0b8d\\u0b91\\u0b96-\\u0b98\\u0b9b\\u0b9d\\u0ba0-\\u0ba2\\u0ba5-\\u0ba7\\u0bab-\\u0bad\\u0bb6\\u0bba-\\u0bbd\\u0bc3-\\u0bc5\\u0bc9\\u0bce-\\u0bd6\\u0bd8-\\u0be6\\u0bf0-\\u0c00\\u0c04\\u0c0d\\u0c11\\u0c29\\u0c34\\u0c3a-\\u0c3d\\u0c45\\u0c49\\u0c4e-\\u0c54\\u0c57-\\u0c5f\\u0c62-\\u0c65\\u0c70-\\u0c81\\u0c84\\u0c8d\\u0c91\\u0ca9\\u0cb4\\u0cba-\\u0cbd\\u0cc5\\u0cc9\\u0cce-\\u0cd4\\u0cd7-\\u0cdd\\u0cdf\\u0ce2-\\u0ce5\\u0cf0-\\u0d01\\u0d04\\u0d0d\\u0d11\\u0d29\\u0d3a-\\u0d3d\\u0d44-\\u0d45\\u0d49\\u0d4e-\\u0d56\\u0d58-\\u0d5f\\u0d62-\\u0d65\\u0d70-\\u0e00\\u0e2f\\u0e3b-\\u0e3f\\u0e4f\\u0e5a-\\u0e80\\u0e83\\u0e85-\\u0e86\\u0e89\\u0e8b-\\u0e8c\\u0e8e-\\u0e93\\u0e98\\u0ea0\\u0ea4\\u0ea6\\u0ea8-\\u0ea9\\u0eac\\u0eaf\\u0eba\\u0ebe-\\u0ebf\\u0ec5\\u0ec7\\u0ece-\\u0ecf\\u0eda-\\u0f17\\u0f1a-\\u0f1f\\u0f2a-\\u0f34\\u0f36\\u0f38\\u0f3a-\\u0f3d\\u0f48\\u0f6a-\\u0f70\\u0f85\\u0f8c-\\u0f8f\\u0f96\\u0f98\\u0fae-\\u0fb0\\u0fb8\\u0fba-\\u109f\\u10c6-\\u10cf\\u10f7-\\u10ff\\u1101\\u1104\\u1108\\u110a\\u110d\\u1113-\\u113b\\u113d\\u113f\\u1141-\\u114b\\u114d\\u114f\\u1151-\\u1153\\u1156-\\u1158\\u115a-\\u115e\\u1162\\u1164\\u1166\\u1168\\u116a-\\u116c\\u116f-\\u1171\\u1174\\u1176-\\u119d\\u119f-\\u11a7\\u11a9-\\u11aa\\u11ac-\\u11ad\\u11b0-\\u11b6\\u11b9\\u11bb\\u11c3-\\u11ea\\u11ec-\\u11ef\\u11f1-\\u11f8\\u11fa-\\u1dff\\u1e9c-\\u1e9f\\u1efa-\\u1eff\\u1f16-\\u1f17\\u1f1e-\\u1f1f\\u1f46-\\u1f47\\u1f4e-\\u1f4f\\u1f58\\u1f5a\\u1f5c\\u1f5e\\u1f7e-\\u1f7f\\u1fb5\\u1fbd\\u1fbf-\\u1fc1\\u1fc5\\u1fcd-\\u1fcf\\u1fd4-\\u1fd5\\u1fdc-\\u1fdf\\u1fed-\\u1ff1\\u1ff5\\u1ffd-\\u20cf\\u20dd-\\u20e0\\u20e2-\\u2125\\u2127-\\u2129\\u212c-\\u212d\\u212f-\\u217f\\u2183-\\u3004\\u3006\\u3008-\\u3020\\u3030\\u3036-\\u3040\\u3095-\\u3098\\u309b-\\u309c\\u309f-\\u30a0\\u30fb\\u30ff-\\u3104\\u312d-\\u4dff\\u9fa6-\\uabff\\ud7a4-\\uffff]')  # noqa\n\nnonXmlNameFirstBMPRegexp = re.compile('[\\x00-@\\\\[-\\\\^`\\\\{-\\xbf\\xd7\\xf7\\u0132-\\u0133\\u013f-\\u0140\\u0149\\u017f\\u01c4-\\u01cc\\u01f1-\\u01f3\\u01f6-\\u01f9\\u0218-\\u024f\\u02a9-\\u02ba\\u02c2-\\u0385\\u0387\\u038b\\u038d\\u03a2\\u03cf\\u03d7-\\u03d9\\u03db\\u03dd\\u03df\\u03e1\\u03f4-\\u0400\\u040d\\u0450\\u045d\\u0482-\\u048f\\u04c5-\\u04c6\\u04c9-\\u04ca\\u04cd-\\u04cf\\u04ec-\\u04ed\\u04f6-\\u04f7\\u04fa-\\u0530\\u0557-\\u0558\\u055a-\\u0560\\u0587-\\u05cf\\u05eb-\\u05ef\\u05f3-\\u0620\\u063b-\\u0640\\u064b-\\u0670\\u06b8-\\u06b9\\u06bf\\u06cf\\u06d4\\u06d6-\\u06e4\\u06e7-\\u0904\\u093a-\\u093c\\u093e-\\u0957\\u0962-\\u0984\\u098d-\\u098e\\u0991-\\u0992\\u09a9\\u09b1\\u09b3-\\u09b5\\u09ba-\\u09db\\u09de\\u09e2-\\u09ef\\u09f2-\\u0a04\\u0a0b-\\u0a0e\\u0a11-\\u0a12\\u0a29\\u0a31\\u0a34\\u0a37\\u0a3a-\\u0a58\\u0a5d\\u0a5f-\\u0a71\\u0a75-\\u0a84\\u0a8c\\u0a8e\\u0a92\\u0aa9\\u0ab1\\u0ab4\\u0aba-\\u0abc\\u0abe-\\u0adf\\u0ae1-\\u0b04\\u0b0d-\\u0b0e\\u0b11-\\u0b12\\u0b29\\u0b31\\u0b34-\\u0b35\\u0b3a-\\u0b3c\\u0b3e-\\u0b5b\\u0b5e\\u0b62-\\u0b84\\u0b8b-\\u0b8d\\u0b91\\u0b96-\\u0b98\\u0b9b\\u0b9d\\u0ba0-\\u0ba2\\u0ba5-\\u0ba7\\u0bab-\\u0bad\\u0bb6\\u0bba-\\u0c04\\u0c0d\\u0c11\\u0c29\\u0c34\\u0c3a-\\u0c5f\\u0c62-\\u0c84\\u0c8d\\u0c91\\u0ca9\\u0cb4\\u0cba-\\u0cdd\\u0cdf\\u0ce2-\\u0d04\\u0d0d\\u0d11\\u0d29\\u0d3a-\\u0d5f\\u0d62-\\u0e00\\u0e2f\\u0e31\\u0e34-\\u0e3f\\u0e46-\\u0e80\\u0e83\\u0e85-\\u0e86\\u0e89\\u0e8b-\\u0e8c\\u0e8e-\\u0e93\\u0e98\\u0ea0\\u0ea4\\u0ea6\\u0ea8-\\u0ea9\\u0eac\\u0eaf\\u0eb1\\u0eb4-\\u0ebc\\u0ebe-\\u0ebf\\u0ec5-\\u0f3f\\u0f48\\u0f6a-\\u109f\\u10c6-\\u10cf\\u10f7-\\u10ff\\u1101\\u1104\\u1108\\u110a\\u110d\\u1113-\\u113b\\u113d\\u113f\\u1141-\\u114b\\u114d\\u114f\\u1151-\\u1153\\u1156-\\u1158\\u115a-\\u115e\\u1162\\u1164\\u1166\\u1168\\u116a-\\u116c\\u116f-\\u1171\\u1174\\u1176-\\u119d\\u119f-\\u11a7\\u11a9-\\u11aa\\u11ac-\\u11ad\\u11b0-\\u11b6\\u11b9\\u11bb\\u11c3-\\u11ea\\u11ec-\\u11ef\\u11f1-\\u11f8\\u11fa-\\u1dff\\u1e9c-\\u1e9f\\u1efa-\\u1eff\\u1f16-\\u1f17\\u1f1e-\\u1f1f\\u1f46-\\u1f47\\u1f4e-\\u1f4f\\u1f58\\u1f5a\\u1f5c\\u1f5e\\u1f7e-\\u1f7f\\u1fb5\\u1fbd\\u1fbf-\\u1fc1\\u1fc5\\u1fcd-\\u1fcf\\u1fd4-\\u1fd5\\u1fdc-\\u1fdf\\u1fed-\\u1ff1\\u1ff5\\u1ffd-\\u2125\\u2127-\\u2129\\u212c-\\u212d\\u212f-\\u217f\\u2183-\\u3006\\u3008-\\u3020\\u302a-\\u3040\\u3095-\\u30a0\\u30fb-\\u3104\\u312d-\\u4dff\\u9fa6-\\uabff\\ud7a4-\\uffff]')  # noqa\n\n# Simpler things\nnonPubidCharRegexp = re.compile(\"[^\\x20\\x0D\\x0Aa-zA-Z0-9\\\\-'()+,./:=?;!*#@$_%]\")\n\n\nclass InfosetFilter(object):\n    replacementRegexp = re.compile(r\"U[\\dA-F]{5,5}\")\n\n    def __init__(self,\n                 dropXmlnsLocalName=False,\n                 dropXmlnsAttrNs=False,\n                 preventDoubleDashComments=False,\n                 preventDashAtCommentEnd=False,\n                 replaceFormFeedCharacters=True,\n                 preventSingleQuotePubid=False):\n\n        self.dropXmlnsLocalName = dropXmlnsLocalName\n        self.dropXmlnsAttrNs = dropXmlnsAttrNs\n\n        self.preventDoubleDashComments = preventDoubleDashComments\n        self.preventDashAtCommentEnd = preventDashAtCommentEnd\n\n        self.replaceFormFeedCharacters = replaceFormFeedCharacters\n\n        self.preventSingleQuotePubid = preventSingleQuotePubid\n\n        self.replaceCache = {}\n\n    def coerceAttribute(self, name, namespace=None):\n        if self.dropXmlnsLocalName and name.startswith(\"xmlns:\"):\n            warnings.warn(\"Attributes cannot begin with xmlns\", DataLossWarning)\n            return None\n        elif (self.dropXmlnsAttrNs and\n              namespace == \"http://www.w3.org/2000/xmlns/\"):\n            warnings.warn(\"Attributes cannot be in the xml namespace\", DataLossWarning)\n            return None\n        else:\n            return self.toXmlName(name)\n\n    def coerceElement(self, name):\n        return self.toXmlName(name)\n\n    def coerceComment(self, data):\n        if self.preventDoubleDashComments:\n            while \"--\" in data:\n                warnings.warn(\"Comments cannot contain adjacent dashes\", DataLossWarning)\n                data = data.replace(\"--\", \"- -\")\n            if data.endswith(\"-\"):\n                warnings.warn(\"Comments cannot end in a dash\", DataLossWarning)\n                data += \" \"\n        return data\n\n    def coerceCharacters(self, data):\n        if self.replaceFormFeedCharacters:\n            for _ in range(data.count(\"\\x0C\")):\n                warnings.warn(\"Text cannot contain U+000C\", DataLossWarning)\n            data = data.replace(\"\\x0C\", \" \")\n        # Other non-xml characters\n        return data\n\n    def coercePubid(self, data):\n        dataOutput = data\n        for char in nonPubidCharRegexp.findall(data):\n            warnings.warn(\"Coercing non-XML pubid\", DataLossWarning)\n            replacement = self.getReplacementCharacter(char)\n            dataOutput = dataOutput.replace(char, replacement)\n        if self.preventSingleQuotePubid and dataOutput.find(\"'\") >= 0:\n            warnings.warn(\"Pubid cannot contain single quote\", DataLossWarning)\n            dataOutput = dataOutput.replace(\"'\", self.getReplacementCharacter(\"'\"))\n        return dataOutput\n\n    def toXmlName(self, name):\n        nameFirst = name[0]\n        nameRest = name[1:]\n        m = nonXmlNameFirstBMPRegexp.match(nameFirst)\n        if m:\n            warnings.warn(\"Coercing non-XML name\", DataLossWarning)\n            nameFirstOutput = self.getReplacementCharacter(nameFirst)\n        else:\n            nameFirstOutput = nameFirst\n\n        nameRestOutput = nameRest\n        replaceChars = set(nonXmlNameBMPRegexp.findall(nameRest))\n        for char in replaceChars:\n            warnings.warn(\"Coercing non-XML name\", DataLossWarning)\n            replacement = self.getReplacementCharacter(char)\n            nameRestOutput = nameRestOutput.replace(char, replacement)\n        return nameFirstOutput + nameRestOutput\n\n    def getReplacementCharacter(self, char):\n        if char in self.replaceCache:\n            replacement = self.replaceCache[char]\n        else:\n            replacement = self.escapeChar(char)\n        return replacement\n\n    def fromXmlName(self, name):\n        for item in set(self.replacementRegexp.findall(name)):\n            name = name.replace(item, self.unescapeChar(item))\n        return name\n\n    def escapeChar(self, char):\n        replacement = \"U%05X\" % ord(char)\n        self.replaceCache[char] = replacement\n        return replacement\n\n    def unescapeChar(self, charcode):\n        return chr(int(charcode[1:], 16))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/_inputstream.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom pip._vendor.six import text_type, binary_type\nfrom pip._vendor.six.moves import http_client, urllib\n\nimport codecs\nimport re\n\nfrom pip._vendor import webencodings\n\nfrom .constants import EOF, spaceCharacters, asciiLetters, asciiUppercase\nfrom .constants import _ReparseException\nfrom . import _utils\n\nfrom io import StringIO\n\ntry:\n    from io import BytesIO\nexcept ImportError:\n    BytesIO = StringIO\n\n# Non-unicode versions of constants for use in the pre-parser\nspaceCharactersBytes = frozenset([item.encode(\"ascii\") for item in spaceCharacters])\nasciiLettersBytes = frozenset([item.encode(\"ascii\") for item in asciiLetters])\nasciiUppercaseBytes = frozenset([item.encode(\"ascii\") for item in asciiUppercase])\nspacesAngleBrackets = spaceCharactersBytes | frozenset([b\">\", b\"<\"])\n\n\ninvalid_unicode_no_surrogate = \"[\\u0001-\\u0008\\u000B\\u000E-\\u001F\\u007F-\\u009F\\uFDD0-\\uFDEF\\uFFFE\\uFFFF\\U0001FFFE\\U0001FFFF\\U0002FFFE\\U0002FFFF\\U0003FFFE\\U0003FFFF\\U0004FFFE\\U0004FFFF\\U0005FFFE\\U0005FFFF\\U0006FFFE\\U0006FFFF\\U0007FFFE\\U0007FFFF\\U0008FFFE\\U0008FFFF\\U0009FFFE\\U0009FFFF\\U000AFFFE\\U000AFFFF\\U000BFFFE\\U000BFFFF\\U000CFFFE\\U000CFFFF\\U000DFFFE\\U000DFFFF\\U000EFFFE\\U000EFFFF\\U000FFFFE\\U000FFFFF\\U0010FFFE\\U0010FFFF]\"  # noqa\n\nif _utils.supports_lone_surrogates:\n    # Use one extra step of indirection and create surrogates with\n    # eval. Not using this indirection would introduce an illegal\n    # unicode literal on platforms not supporting such lone\n    # surrogates.\n    assert invalid_unicode_no_surrogate[-1] == \"]\" and invalid_unicode_no_surrogate.count(\"]\") == 1\n    invalid_unicode_re = re.compile(invalid_unicode_no_surrogate[:-1] +\n                                    eval('\"\\\\uD800-\\\\uDFFF\"') +  # pylint:disable=eval-used\n                                    \"]\")\nelse:\n    invalid_unicode_re = re.compile(invalid_unicode_no_surrogate)\n\nnon_bmp_invalid_codepoints = set([0x1FFFE, 0x1FFFF, 0x2FFFE, 0x2FFFF, 0x3FFFE,\n                                  0x3FFFF, 0x4FFFE, 0x4FFFF, 0x5FFFE, 0x5FFFF,\n                                  0x6FFFE, 0x6FFFF, 0x7FFFE, 0x7FFFF, 0x8FFFE,\n                                  0x8FFFF, 0x9FFFE, 0x9FFFF, 0xAFFFE, 0xAFFFF,\n                                  0xBFFFE, 0xBFFFF, 0xCFFFE, 0xCFFFF, 0xDFFFE,\n                                  0xDFFFF, 0xEFFFE, 0xEFFFF, 0xFFFFE, 0xFFFFF,\n                                  0x10FFFE, 0x10FFFF])\n\nascii_punctuation_re = re.compile(\"[\\u0009-\\u000D\\u0020-\\u002F\\u003A-\\u0040\\u005C\\u005B-\\u0060\\u007B-\\u007E]\")\n\n# Cache for charsUntil()\ncharsUntilRegEx = {}\n\n\nclass BufferedStream(object):\n    \"\"\"Buffering for streams that do not have buffering of their own\n\n    The buffer is implemented as a list of chunks on the assumption that\n    joining many strings will be slow since it is O(n**2)\n    \"\"\"\n\n    def __init__(self, stream):\n        self.stream = stream\n        self.buffer = []\n        self.position = [-1, 0]  # chunk number, offset\n\n    def tell(self):\n        pos = 0\n        for chunk in self.buffer[:self.position[0]]:\n            pos += len(chunk)\n        pos += self.position[1]\n        return pos\n\n    def seek(self, pos):\n        assert pos <= self._bufferedBytes()\n        offset = pos\n        i = 0\n        while len(self.buffer[i]) < offset:\n            offset -= len(self.buffer[i])\n            i += 1\n        self.position = [i, offset]\n\n    def read(self, bytes):\n        if not self.buffer:\n            return self._readStream(bytes)\n        elif (self.position[0] == len(self.buffer) and\n              self.position[1] == len(self.buffer[-1])):\n            return self._readStream(bytes)\n        else:\n            return self._readFromBuffer(bytes)\n\n    def _bufferedBytes(self):\n        return sum([len(item) for item in self.buffer])\n\n    def _readStream(self, bytes):\n        data = self.stream.read(bytes)\n        self.buffer.append(data)\n        self.position[0] += 1\n        self.position[1] = len(data)\n        return data\n\n    def _readFromBuffer(self, bytes):\n        remainingBytes = bytes\n        rv = []\n        bufferIndex = self.position[0]\n        bufferOffset = self.position[1]\n        while bufferIndex < len(self.buffer) and remainingBytes != 0:\n            assert remainingBytes > 0\n            bufferedData = self.buffer[bufferIndex]\n\n            if remainingBytes <= len(bufferedData) - bufferOffset:\n                bytesToRead = remainingBytes\n                self.position = [bufferIndex, bufferOffset + bytesToRead]\n            else:\n                bytesToRead = len(bufferedData) - bufferOffset\n                self.position = [bufferIndex, len(bufferedData)]\n                bufferIndex += 1\n            rv.append(bufferedData[bufferOffset:bufferOffset + bytesToRead])\n            remainingBytes -= bytesToRead\n\n            bufferOffset = 0\n\n        if remainingBytes:\n            rv.append(self._readStream(remainingBytes))\n\n        return b\"\".join(rv)\n\n\ndef HTMLInputStream(source, **kwargs):\n    # Work around Python bug #20007: read(0) closes the connection.\n    # http://bugs.python.org/issue20007\n    if (isinstance(source, http_client.HTTPResponse) or\n        # Also check for addinfourl wrapping HTTPResponse\n        (isinstance(source, urllib.response.addbase) and\n         isinstance(source.fp, http_client.HTTPResponse))):\n        isUnicode = False\n    elif hasattr(source, \"read\"):\n        isUnicode = isinstance(source.read(0), text_type)\n    else:\n        isUnicode = isinstance(source, text_type)\n\n    if isUnicode:\n        encodings = [x for x in kwargs if x.endswith(\"_encoding\")]\n        if encodings:\n            raise TypeError(\"Cannot set an encoding with a unicode input, set %r\" % encodings)\n\n        return HTMLUnicodeInputStream(source, **kwargs)\n    else:\n        return HTMLBinaryInputStream(source, **kwargs)\n\n\nclass HTMLUnicodeInputStream(object):\n    \"\"\"Provides a unicode stream of characters to the HTMLTokenizer.\n\n    This class takes care of character encoding and removing or replacing\n    incorrect byte-sequences and also provides column and line tracking.\n\n    \"\"\"\n\n    _defaultChunkSize = 10240\n\n    def __init__(self, source):\n        \"\"\"Initialises the HTMLInputStream.\n\n        HTMLInputStream(source, [encoding]) -> Normalized stream from source\n        for use by html5lib.\n\n        source can be either a file-object, local filename or a string.\n\n        The optional encoding parameter must be a string that indicates\n        the encoding.  If specified, that encoding will be used,\n        regardless of any BOM or later declaration (such as in a meta\n        element)\n\n        \"\"\"\n\n        if not _utils.supports_lone_surrogates:\n            # Such platforms will have already checked for such\n            # surrogate errors, so no need to do this checking.\n            self.reportCharacterErrors = None\n        elif len(\"\\U0010FFFF\") == 1:\n            self.reportCharacterErrors = self.characterErrorsUCS4\n        else:\n            self.reportCharacterErrors = self.characterErrorsUCS2\n\n        # List of where new lines occur\n        self.newLines = [0]\n\n        self.charEncoding = (lookupEncoding(\"utf-8\"), \"certain\")\n        self.dataStream = self.openStream(source)\n\n        self.reset()\n\n    def reset(self):\n        self.chunk = \"\"\n        self.chunkSize = 0\n        self.chunkOffset = 0\n        self.errors = []\n\n        # number of (complete) lines in previous chunks\n        self.prevNumLines = 0\n        # number of columns in the last line of the previous chunk\n        self.prevNumCols = 0\n\n        # Deal with CR LF and surrogates split over chunk boundaries\n        self._bufferedCharacter = None\n\n    def openStream(self, source):\n        \"\"\"Produces a file object from source.\n\n        source can be either a file object, local filename or a string.\n\n        \"\"\"\n        # Already a file object\n        if hasattr(source, 'read'):\n            stream = source\n        else:\n            stream = StringIO(source)\n\n        return stream\n\n    def _position(self, offset):\n        chunk = self.chunk\n        nLines = chunk.count('\\n', 0, offset)\n        positionLine = self.prevNumLines + nLines\n        lastLinePos = chunk.rfind('\\n', 0, offset)\n        if lastLinePos == -1:\n            positionColumn = self.prevNumCols + offset\n        else:\n            positionColumn = offset - (lastLinePos + 1)\n        return (positionLine, positionColumn)\n\n    def position(self):\n        \"\"\"Returns (line, col) of the current position in the stream.\"\"\"\n        line, col = self._position(self.chunkOffset)\n        return (line + 1, col)\n\n    def char(self):\n        \"\"\" Read one character from the stream or queue if available. Return\n            EOF when EOF is reached.\n        \"\"\"\n        # Read a new chunk from the input stream if necessary\n        if self.chunkOffset >= self.chunkSize:\n            if not self.readChunk():\n                return EOF\n\n        chunkOffset = self.chunkOffset\n        char = self.chunk[chunkOffset]\n        self.chunkOffset = chunkOffset + 1\n\n        return char\n\n    def readChunk(self, chunkSize=None):\n        if chunkSize is None:\n            chunkSize = self._defaultChunkSize\n\n        self.prevNumLines, self.prevNumCols = self._position(self.chunkSize)\n\n        self.chunk = \"\"\n        self.chunkSize = 0\n        self.chunkOffset = 0\n\n        data = self.dataStream.read(chunkSize)\n\n        # Deal with CR LF and surrogates broken across chunks\n        if self._bufferedCharacter:\n            data = self._bufferedCharacter + data\n            self._bufferedCharacter = None\n        elif not data:\n            # We have no more data, bye-bye stream\n            return False\n\n        if len(data) > 1:\n            lastv = ord(data[-1])\n            if lastv == 0x0D or 0xD800 <= lastv <= 0xDBFF:\n                self._bufferedCharacter = data[-1]\n                data = data[:-1]\n\n        if self.reportCharacterErrors:\n            self.reportCharacterErrors(data)\n\n        # Replace invalid characters\n        data = data.replace(\"\\r\\n\", \"\\n\")\n        data = data.replace(\"\\r\", \"\\n\")\n\n        self.chunk = data\n        self.chunkSize = len(data)\n\n        return True\n\n    def characterErrorsUCS4(self, data):\n        for _ in range(len(invalid_unicode_re.findall(data))):\n            self.errors.append(\"invalid-codepoint\")\n\n    def characterErrorsUCS2(self, data):\n        # Someone picked the wrong compile option\n        # You lose\n        skip = False\n        for match in invalid_unicode_re.finditer(data):\n            if skip:\n                continue\n            codepoint = ord(match.group())\n            pos = match.start()\n            # Pretty sure there should be endianness issues here\n            if _utils.isSurrogatePair(data[pos:pos + 2]):\n                # We have a surrogate pair!\n                char_val = _utils.surrogatePairToCodepoint(data[pos:pos + 2])\n                if char_val in non_bmp_invalid_codepoints:\n                    self.errors.append(\"invalid-codepoint\")\n                skip = True\n            elif (codepoint >= 0xD800 and codepoint <= 0xDFFF and\n                  pos == len(data) - 1):\n                self.errors.append(\"invalid-codepoint\")\n            else:\n                skip = False\n                self.errors.append(\"invalid-codepoint\")\n\n    def charsUntil(self, characters, opposite=False):\n        \"\"\" Returns a string of characters from the stream up to but not\n        including any character in 'characters' or EOF. 'characters' must be\n        a container that supports the 'in' method and iteration over its\n        characters.\n        \"\"\"\n\n        # Use a cache of regexps to find the required characters\n        try:\n            chars = charsUntilRegEx[(characters, opposite)]\n        except KeyError:\n            if __debug__:\n                for c in characters:\n                    assert(ord(c) < 128)\n            regex = \"\".join([\"\\\\x%02x\" % ord(c) for c in characters])\n            if not opposite:\n                regex = \"^%s\" % regex\n            chars = charsUntilRegEx[(characters, opposite)] = re.compile(\"[%s]+\" % regex)\n\n        rv = []\n\n        while True:\n            # Find the longest matching prefix\n            m = chars.match(self.chunk, self.chunkOffset)\n            if m is None:\n                # If nothing matched, and it wasn't because we ran out of chunk,\n                # then stop\n                if self.chunkOffset != self.chunkSize:\n                    break\n            else:\n                end = m.end()\n                # If not the whole chunk matched, return everything\n                # up to the part that didn't match\n                if end != self.chunkSize:\n                    rv.append(self.chunk[self.chunkOffset:end])\n                    self.chunkOffset = end\n                    break\n            # If the whole remainder of the chunk matched,\n            # use it all and read the next chunk\n            rv.append(self.chunk[self.chunkOffset:])\n            if not self.readChunk():\n                # Reached EOF\n                break\n\n        r = \"\".join(rv)\n        return r\n\n    def unget(self, char):\n        # Only one character is allowed to be ungotten at once - it must\n        # be consumed again before any further call to unget\n        if char is not None:\n            if self.chunkOffset == 0:\n                # unget is called quite rarely, so it's a good idea to do\n                # more work here if it saves a bit of work in the frequently\n                # called char and charsUntil.\n                # So, just prepend the ungotten character onto the current\n                # chunk:\n                self.chunk = char + self.chunk\n                self.chunkSize += 1\n            else:\n                self.chunkOffset -= 1\n                assert self.chunk[self.chunkOffset] == char\n\n\nclass HTMLBinaryInputStream(HTMLUnicodeInputStream):\n    \"\"\"Provides a unicode stream of characters to the HTMLTokenizer.\n\n    This class takes care of character encoding and removing or replacing\n    incorrect byte-sequences and also provides column and line tracking.\n\n    \"\"\"\n\n    def __init__(self, source, override_encoding=None, transport_encoding=None,\n                 same_origin_parent_encoding=None, likely_encoding=None,\n                 default_encoding=\"windows-1252\", useChardet=True):\n        \"\"\"Initialises the HTMLInputStream.\n\n        HTMLInputStream(source, [encoding]) -> Normalized stream from source\n        for use by html5lib.\n\n        source can be either a file-object, local filename or a string.\n\n        The optional encoding parameter must be a string that indicates\n        the encoding.  If specified, that encoding will be used,\n        regardless of any BOM or later declaration (such as in a meta\n        element)\n\n        \"\"\"\n        # Raw Stream - for unicode objects this will encode to utf-8 and set\n        #              self.charEncoding as appropriate\n        self.rawStream = self.openStream(source)\n\n        HTMLUnicodeInputStream.__init__(self, self.rawStream)\n\n        # Encoding Information\n        # Number of bytes to use when looking for a meta element with\n        # encoding information\n        self.numBytesMeta = 1024\n        # Number of bytes to use when using detecting encoding using chardet\n        self.numBytesChardet = 100\n        # Things from args\n        self.override_encoding = override_encoding\n        self.transport_encoding = transport_encoding\n        self.same_origin_parent_encoding = same_origin_parent_encoding\n        self.likely_encoding = likely_encoding\n        self.default_encoding = default_encoding\n\n        # Determine encoding\n        self.charEncoding = self.determineEncoding(useChardet)\n        assert self.charEncoding[0] is not None\n\n        # Call superclass\n        self.reset()\n\n    def reset(self):\n        self.dataStream = self.charEncoding[0].codec_info.streamreader(self.rawStream, 'replace')\n        HTMLUnicodeInputStream.reset(self)\n\n    def openStream(self, source):\n        \"\"\"Produces a file object from source.\n\n        source can be either a file object, local filename or a string.\n\n        \"\"\"\n        # Already a file object\n        if hasattr(source, 'read'):\n            stream = source\n        else:\n            stream = BytesIO(source)\n\n        try:\n            stream.seek(stream.tell())\n        except:  # pylint:disable=bare-except\n            stream = BufferedStream(stream)\n\n        return stream\n\n    def determineEncoding(self, chardet=True):\n        # BOMs take precedence over everything\n        # This will also read past the BOM if present\n        charEncoding = self.detectBOM(), \"certain\"\n        if charEncoding[0] is not None:\n            return charEncoding\n\n        # If we've been overriden, we've been overriden\n        charEncoding = lookupEncoding(self.override_encoding), \"certain\"\n        if charEncoding[0] is not None:\n            return charEncoding\n\n        # Now check the transport layer\n        charEncoding = lookupEncoding(self.transport_encoding), \"certain\"\n        if charEncoding[0] is not None:\n            return charEncoding\n\n        # Look for meta elements with encoding information\n        charEncoding = self.detectEncodingMeta(), \"tentative\"\n        if charEncoding[0] is not None:\n            return charEncoding\n\n        # Parent document encoding\n        charEncoding = lookupEncoding(self.same_origin_parent_encoding), \"tentative\"\n        if charEncoding[0] is not None and not charEncoding[0].name.startswith(\"utf-16\"):\n            return charEncoding\n\n        # \"likely\" encoding\n        charEncoding = lookupEncoding(self.likely_encoding), \"tentative\"\n        if charEncoding[0] is not None:\n            return charEncoding\n\n        # Guess with chardet, if available\n        if chardet:\n            try:\n                from pip._vendor.chardet.universaldetector import UniversalDetector\n            except ImportError:\n                pass\n            else:\n                buffers = []\n                detector = UniversalDetector()\n                while not detector.done:\n                    buffer = self.rawStream.read(self.numBytesChardet)\n                    assert isinstance(buffer, bytes)\n                    if not buffer:\n                        break\n                    buffers.append(buffer)\n                    detector.feed(buffer)\n                detector.close()\n                encoding = lookupEncoding(detector.result['encoding'])\n                self.rawStream.seek(0)\n                if encoding is not None:\n                    return encoding, \"tentative\"\n\n        # Try the default encoding\n        charEncoding = lookupEncoding(self.default_encoding), \"tentative\"\n        if charEncoding[0] is not None:\n            return charEncoding\n\n        # Fallback to html5lib's default if even that hasn't worked\n        return lookupEncoding(\"windows-1252\"), \"tentative\"\n\n    def changeEncoding(self, newEncoding):\n        assert self.charEncoding[1] != \"certain\"\n        newEncoding = lookupEncoding(newEncoding)\n        if newEncoding is None:\n            return\n        if newEncoding.name in (\"utf-16be\", \"utf-16le\"):\n            newEncoding = lookupEncoding(\"utf-8\")\n            assert newEncoding is not None\n        elif newEncoding == self.charEncoding[0]:\n            self.charEncoding = (self.charEncoding[0], \"certain\")\n        else:\n            self.rawStream.seek(0)\n            self.charEncoding = (newEncoding, \"certain\")\n            self.reset()\n            raise _ReparseException(\"Encoding changed from %s to %s\" % (self.charEncoding[0], newEncoding))\n\n    def detectBOM(self):\n        \"\"\"Attempts to detect at BOM at the start of the stream. If\n        an encoding can be determined from the BOM return the name of the\n        encoding otherwise return None\"\"\"\n        bomDict = {\n            codecs.BOM_UTF8: 'utf-8',\n            codecs.BOM_UTF16_LE: 'utf-16le', codecs.BOM_UTF16_BE: 'utf-16be',\n            codecs.BOM_UTF32_LE: 'utf-32le', codecs.BOM_UTF32_BE: 'utf-32be'\n        }\n\n        # Go to beginning of file and read in 4 bytes\n        string = self.rawStream.read(4)\n        assert isinstance(string, bytes)\n\n        # Try detecting the BOM using bytes from the string\n        encoding = bomDict.get(string[:3])         # UTF-8\n        seek = 3\n        if not encoding:\n            # Need to detect UTF-32 before UTF-16\n            encoding = bomDict.get(string)         # UTF-32\n            seek = 4\n            if not encoding:\n                encoding = bomDict.get(string[:2])  # UTF-16\n                seek = 2\n\n        # Set the read position past the BOM if one was found, otherwise\n        # set it to the start of the stream\n        if encoding:\n            self.rawStream.seek(seek)\n            return lookupEncoding(encoding)\n        else:\n            self.rawStream.seek(0)\n            return None\n\n    def detectEncodingMeta(self):\n        \"\"\"Report the encoding declared by the meta element\n        \"\"\"\n        buffer = self.rawStream.read(self.numBytesMeta)\n        assert isinstance(buffer, bytes)\n        parser = EncodingParser(buffer)\n        self.rawStream.seek(0)\n        encoding = parser.getEncoding()\n\n        if encoding is not None and encoding.name in (\"utf-16be\", \"utf-16le\"):\n            encoding = lookupEncoding(\"utf-8\")\n\n        return encoding\n\n\nclass EncodingBytes(bytes):\n    \"\"\"String-like object with an associated position and various extra methods\n    If the position is ever greater than the string length then an exception is\n    raised\"\"\"\n    def __new__(self, value):\n        assert isinstance(value, bytes)\n        return bytes.__new__(self, value.lower())\n\n    def __init__(self, value):\n        # pylint:disable=unused-argument\n        self._position = -1\n\n    def __iter__(self):\n        return self\n\n    def __next__(self):\n        p = self._position = self._position + 1\n        if p >= len(self):\n            raise StopIteration\n        elif p < 0:\n            raise TypeError\n        return self[p:p + 1]\n\n    def next(self):\n        # Py2 compat\n        return self.__next__()\n\n    def previous(self):\n        p = self._position\n        if p >= len(self):\n            raise StopIteration\n        elif p < 0:\n            raise TypeError\n        self._position = p = p - 1\n        return self[p:p + 1]\n\n    def setPosition(self, position):\n        if self._position >= len(self):\n            raise StopIteration\n        self._position = position\n\n    def getPosition(self):\n        if self._position >= len(self):\n            raise StopIteration\n        if self._position >= 0:\n            return self._position\n        else:\n            return None\n\n    position = property(getPosition, setPosition)\n\n    def getCurrentByte(self):\n        return self[self.position:self.position + 1]\n\n    currentByte = property(getCurrentByte)\n\n    def skip(self, chars=spaceCharactersBytes):\n        \"\"\"Skip past a list of characters\"\"\"\n        p = self.position               # use property for the error-checking\n        while p < len(self):\n            c = self[p:p + 1]\n            if c not in chars:\n                self._position = p\n                return c\n            p += 1\n        self._position = p\n        return None\n\n    def skipUntil(self, chars):\n        p = self.position\n        while p < len(self):\n            c = self[p:p + 1]\n            if c in chars:\n                self._position = p\n                return c\n            p += 1\n        self._position = p\n        return None\n\n    def matchBytes(self, bytes):\n        \"\"\"Look for a sequence of bytes at the start of a string. If the bytes\n        are found return True and advance the position to the byte after the\n        match. Otherwise return False and leave the position alone\"\"\"\n        p = self.position\n        data = self[p:p + len(bytes)]\n        rv = data.startswith(bytes)\n        if rv:\n            self.position += len(bytes)\n        return rv\n\n    def jumpTo(self, bytes):\n        \"\"\"Look for the next sequence of bytes matching a given sequence. If\n        a match is found advance the position to the last byte of the match\"\"\"\n        newPosition = self[self.position:].find(bytes)\n        if newPosition > -1:\n            # XXX: This is ugly, but I can't see a nicer way to fix this.\n            if self._position == -1:\n                self._position = 0\n            self._position += (newPosition + len(bytes) - 1)\n            return True\n        else:\n            raise StopIteration\n\n\nclass EncodingParser(object):\n    \"\"\"Mini parser for detecting character encoding from meta elements\"\"\"\n\n    def __init__(self, data):\n        \"\"\"string - the data to work on for encoding detection\"\"\"\n        self.data = EncodingBytes(data)\n        self.encoding = None\n\n    def getEncoding(self):\n        methodDispatch = (\n            (b\"<!--\", self.handleComment),\n            (b\"<meta\", self.handleMeta),\n            (b\"</\", self.handlePossibleEndTag),\n            (b\"<!\", self.handleOther),\n            (b\"<?\", self.handleOther),\n            (b\"<\", self.handlePossibleStartTag))\n        for _ in self.data:\n            keepParsing = True\n            for key, method in methodDispatch:\n                if self.data.matchBytes(key):\n                    try:\n                        keepParsing = method()\n                        break\n                    except StopIteration:\n                        keepParsing = False\n                        break\n            if not keepParsing:\n                break\n\n        return self.encoding\n\n    def handleComment(self):\n        \"\"\"Skip over comments\"\"\"\n        return self.data.jumpTo(b\"-->\")\n\n    def handleMeta(self):\n        if self.data.currentByte not in spaceCharactersBytes:\n            # if we have <meta not followed by a space so just keep going\n            return True\n        # We have a valid meta element we want to search for attributes\n        hasPragma = False\n        pendingEncoding = None\n        while True:\n            # Try to find the next attribute after the current position\n            attr = self.getAttribute()\n            if attr is None:\n                return True\n            else:\n                if attr[0] == b\"http-equiv\":\n                    hasPragma = attr[1] == b\"content-type\"\n                    if hasPragma and pendingEncoding is not None:\n                        self.encoding = pendingEncoding\n                        return False\n                elif attr[0] == b\"charset\":\n                    tentativeEncoding = attr[1]\n                    codec = lookupEncoding(tentativeEncoding)\n                    if codec is not None:\n                        self.encoding = codec\n                        return False\n                elif attr[0] == b\"content\":\n                    contentParser = ContentAttrParser(EncodingBytes(attr[1]))\n                    tentativeEncoding = contentParser.parse()\n                    if tentativeEncoding is not None:\n                        codec = lookupEncoding(tentativeEncoding)\n                        if codec is not None:\n                            if hasPragma:\n                                self.encoding = codec\n                                return False\n                            else:\n                                pendingEncoding = codec\n\n    def handlePossibleStartTag(self):\n        return self.handlePossibleTag(False)\n\n    def handlePossibleEndTag(self):\n        next(self.data)\n        return self.handlePossibleTag(True)\n\n    def handlePossibleTag(self, endTag):\n        data = self.data\n        if data.currentByte not in asciiLettersBytes:\n            # If the next byte is not an ascii letter either ignore this\n            # fragment (possible start tag case) or treat it according to\n            # handleOther\n            if endTag:\n                data.previous()\n                self.handleOther()\n            return True\n\n        c = data.skipUntil(spacesAngleBrackets)\n        if c == b\"<\":\n            # return to the first step in the overall \"two step\" algorithm\n            # reprocessing the < byte\n            data.previous()\n        else:\n            # Read all attributes\n            attr = self.getAttribute()\n            while attr is not None:\n                attr = self.getAttribute()\n        return True\n\n    def handleOther(self):\n        return self.data.jumpTo(b\">\")\n\n    def getAttribute(self):\n        \"\"\"Return a name,value pair for the next attribute in the stream,\n        if one is found, or None\"\"\"\n        data = self.data\n        # Step 1 (skip chars)\n        c = data.skip(spaceCharactersBytes | frozenset([b\"/\"]))\n        assert c is None or len(c) == 1\n        # Step 2\n        if c in (b\">\", None):\n            return None\n        # Step 3\n        attrName = []\n        attrValue = []\n        # Step 4 attribute name\n        while True:\n            if c == b\"=\" and attrName:\n                break\n            elif c in spaceCharactersBytes:\n                # Step 6!\n                c = data.skip()\n                break\n            elif c in (b\"/\", b\">\"):\n                return b\"\".join(attrName), b\"\"\n            elif c in asciiUppercaseBytes:\n                attrName.append(c.lower())\n            elif c is None:\n                return None\n            else:\n                attrName.append(c)\n            # Step 5\n            c = next(data)\n        # Step 7\n        if c != b\"=\":\n            data.previous()\n            return b\"\".join(attrName), b\"\"\n        # Step 8\n        next(data)\n        # Step 9\n        c = data.skip()\n        # Step 10\n        if c in (b\"'\", b'\"'):\n            # 10.1\n            quoteChar = c\n            while True:\n                # 10.2\n                c = next(data)\n                # 10.3\n                if c == quoteChar:\n                    next(data)\n                    return b\"\".join(attrName), b\"\".join(attrValue)\n                # 10.4\n                elif c in asciiUppercaseBytes:\n                    attrValue.append(c.lower())\n                # 10.5\n                else:\n                    attrValue.append(c)\n        elif c == b\">\":\n            return b\"\".join(attrName), b\"\"\n        elif c in asciiUppercaseBytes:\n            attrValue.append(c.lower())\n        elif c is None:\n            return None\n        else:\n            attrValue.append(c)\n        # Step 11\n        while True:\n            c = next(data)\n            if c in spacesAngleBrackets:\n                return b\"\".join(attrName), b\"\".join(attrValue)\n            elif c in asciiUppercaseBytes:\n                attrValue.append(c.lower())\n            elif c is None:\n                return None\n            else:\n                attrValue.append(c)\n\n\nclass ContentAttrParser(object):\n    def __init__(self, data):\n        assert isinstance(data, bytes)\n        self.data = data\n\n    def parse(self):\n        try:\n            # Check if the attr name is charset\n            # otherwise return\n            self.data.jumpTo(b\"charset\")\n            self.data.position += 1\n            self.data.skip()\n            if not self.data.currentByte == b\"=\":\n                # If there is no = sign keep looking for attrs\n                return None\n            self.data.position += 1\n            self.data.skip()\n            # Look for an encoding between matching quote marks\n            if self.data.currentByte in (b'\"', b\"'\"):\n                quoteMark = self.data.currentByte\n                self.data.position += 1\n                oldPosition = self.data.position\n                if self.data.jumpTo(quoteMark):\n                    return self.data[oldPosition:self.data.position]\n                else:\n                    return None\n            else:\n                # Unquoted value\n                oldPosition = self.data.position\n                try:\n                    self.data.skipUntil(spaceCharactersBytes)\n                    return self.data[oldPosition:self.data.position]\n                except StopIteration:\n                    # Return the whole remaining value\n                    return self.data[oldPosition:]\n        except StopIteration:\n            return None\n\n\ndef lookupEncoding(encoding):\n    \"\"\"Return the python codec name corresponding to an encoding or None if the\n    string doesn't correspond to a valid encoding.\"\"\"\n    if isinstance(encoding, binary_type):\n        try:\n            encoding = encoding.decode(\"ascii\")\n        except UnicodeDecodeError:\n            return None\n\n    if encoding is not None:\n        try:\n            return webencodings.lookup(encoding)\n        except AttributeError:\n            return None\n    else:\n        return None\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/_tokenizer.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom pip._vendor.six import unichr as chr\n\nfrom collections import deque\n\nfrom .constants import spaceCharacters\nfrom .constants import entities\nfrom .constants import asciiLetters, asciiUpper2Lower\nfrom .constants import digits, hexDigits, EOF\nfrom .constants import tokenTypes, tagTokenTypes\nfrom .constants import replacementCharacters\n\nfrom ._inputstream import HTMLInputStream\n\nfrom ._trie import Trie\n\nentitiesTrie = Trie(entities)\n\n\nclass HTMLTokenizer(object):\n    \"\"\" This class takes care of tokenizing HTML.\n\n    * self.currentToken\n      Holds the token that is currently being processed.\n\n    * self.state\n      Holds a reference to the method to be invoked... XXX\n\n    * self.stream\n      Points to HTMLInputStream object.\n    \"\"\"\n\n    def __init__(self, stream, parser=None, **kwargs):\n\n        self.stream = HTMLInputStream(stream, **kwargs)\n        self.parser = parser\n\n        # Setup the initial tokenizer state\n        self.escapeFlag = False\n        self.lastFourChars = []\n        self.state = self.dataState\n        self.escape = False\n\n        # The current token being created\n        self.currentToken = None\n        super(HTMLTokenizer, self).__init__()\n\n    def __iter__(self):\n        \"\"\" This is where the magic happens.\n\n        We do our usually processing through the states and when we have a token\n        to return we yield the token which pauses processing until the next token\n        is requested.\n        \"\"\"\n        self.tokenQueue = deque([])\n        # Start processing. When EOF is reached self.state will return False\n        # instead of True and the loop will terminate.\n        while self.state():\n            while self.stream.errors:\n                yield {\"type\": tokenTypes[\"ParseError\"], \"data\": self.stream.errors.pop(0)}\n            while self.tokenQueue:\n                yield self.tokenQueue.popleft()\n\n    def consumeNumberEntity(self, isHex):\n        \"\"\"This function returns either U+FFFD or the character based on the\n        decimal or hexadecimal representation. It also discards \";\" if present.\n        If not present self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"]}) is invoked.\n        \"\"\"\n\n        allowed = digits\n        radix = 10\n        if isHex:\n            allowed = hexDigits\n            radix = 16\n\n        charStack = []\n\n        # Consume all the characters that are in range while making sure we\n        # don't hit an EOF.\n        c = self.stream.char()\n        while c in allowed and c is not EOF:\n            charStack.append(c)\n            c = self.stream.char()\n\n        # Convert the set of characters consumed to an int.\n        charAsInt = int(\"\".join(charStack), radix)\n\n        # Certain characters get replaced with others\n        if charAsInt in replacementCharacters:\n            char = replacementCharacters[charAsInt]\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"illegal-codepoint-for-numeric-entity\",\n                                    \"datavars\": {\"charAsInt\": charAsInt}})\n        elif ((0xD800 <= charAsInt <= 0xDFFF) or\n              (charAsInt > 0x10FFFF)):\n            char = \"\\uFFFD\"\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"illegal-codepoint-for-numeric-entity\",\n                                    \"datavars\": {\"charAsInt\": charAsInt}})\n        else:\n            # Should speed up this check somehow (e.g. move the set to a constant)\n            if ((0x0001 <= charAsInt <= 0x0008) or\n                (0x000E <= charAsInt <= 0x001F) or\n                (0x007F <= charAsInt <= 0x009F) or\n                (0xFDD0 <= charAsInt <= 0xFDEF) or\n                charAsInt in frozenset([0x000B, 0xFFFE, 0xFFFF, 0x1FFFE,\n                                        0x1FFFF, 0x2FFFE, 0x2FFFF, 0x3FFFE,\n                                        0x3FFFF, 0x4FFFE, 0x4FFFF, 0x5FFFE,\n                                        0x5FFFF, 0x6FFFE, 0x6FFFF, 0x7FFFE,\n                                        0x7FFFF, 0x8FFFE, 0x8FFFF, 0x9FFFE,\n                                        0x9FFFF, 0xAFFFE, 0xAFFFF, 0xBFFFE,\n                                        0xBFFFF, 0xCFFFE, 0xCFFFF, 0xDFFFE,\n                                        0xDFFFF, 0xEFFFE, 0xEFFFF, 0xFFFFE,\n                                        0xFFFFF, 0x10FFFE, 0x10FFFF])):\n                self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                        \"data\":\n                                        \"illegal-codepoint-for-numeric-entity\",\n                                        \"datavars\": {\"charAsInt\": charAsInt}})\n            try:\n                # Try/except needed as UCS-2 Python builds' unichar only works\n                # within the BMP.\n                char = chr(charAsInt)\n            except ValueError:\n                v = charAsInt - 0x10000\n                char = chr(0xD800 | (v >> 10)) + chr(0xDC00 | (v & 0x3FF))\n\n        # Discard the ; if present. Otherwise, put it back on the queue and\n        # invoke parseError on parser.\n        if c != \";\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"numeric-entity-without-semicolon\"})\n            self.stream.unget(c)\n\n        return char\n\n    def consumeEntity(self, allowedChar=None, fromAttribute=False):\n        # Initialise to the default output for when no entity is matched\n        output = \"&\"\n\n        charStack = [self.stream.char()]\n        if (charStack[0] in spaceCharacters or charStack[0] in (EOF, \"<\", \"&\") or\n                (allowedChar is not None and allowedChar == charStack[0])):\n            self.stream.unget(charStack[0])\n\n        elif charStack[0] == \"#\":\n            # Read the next character to see if it's hex or decimal\n            hex = False\n            charStack.append(self.stream.char())\n            if charStack[-1] in (\"x\", \"X\"):\n                hex = True\n                charStack.append(self.stream.char())\n\n            # charStack[-1] should be the first digit\n            if (hex and charStack[-1] in hexDigits) \\\n                    or (not hex and charStack[-1] in digits):\n                # At least one digit found, so consume the whole number\n                self.stream.unget(charStack[-1])\n                output = self.consumeNumberEntity(hex)\n            else:\n                # No digits found\n                self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                        \"data\": \"expected-numeric-entity\"})\n                self.stream.unget(charStack.pop())\n                output = \"&\" + \"\".join(charStack)\n\n        else:\n            # At this point in the process might have named entity. Entities\n            # are stored in the global variable \"entities\".\n            #\n            # Consume characters and compare to these to a substring of the\n            # entity names in the list until the substring no longer matches.\n            while (charStack[-1] is not EOF):\n                if not entitiesTrie.has_keys_with_prefix(\"\".join(charStack)):\n                    break\n                charStack.append(self.stream.char())\n\n            # At this point we have a string that starts with some characters\n            # that may match an entity\n            # Try to find the longest entity the string will match to take care\n            # of &noti for instance.\n            try:\n                entityName = entitiesTrie.longest_prefix(\"\".join(charStack[:-1]))\n                entityLength = len(entityName)\n            except KeyError:\n                entityName = None\n\n            if entityName is not None:\n                if entityName[-1] != \";\":\n                    self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                            \"named-entity-without-semicolon\"})\n                if (entityName[-1] != \";\" and fromAttribute and\n                    (charStack[entityLength] in asciiLetters or\n                     charStack[entityLength] in digits or\n                     charStack[entityLength] == \"=\")):\n                    self.stream.unget(charStack.pop())\n                    output = \"&\" + \"\".join(charStack)\n                else:\n                    output = entities[entityName]\n                    self.stream.unget(charStack.pop())\n                    output += \"\".join(charStack[entityLength:])\n            else:\n                self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                        \"expected-named-entity\"})\n                self.stream.unget(charStack.pop())\n                output = \"&\" + \"\".join(charStack)\n\n        if fromAttribute:\n            self.currentToken[\"data\"][-1][1] += output\n        else:\n            if output in spaceCharacters:\n                tokenType = \"SpaceCharacters\"\n            else:\n                tokenType = \"Characters\"\n            self.tokenQueue.append({\"type\": tokenTypes[tokenType], \"data\": output})\n\n    def processEntityInAttribute(self, allowedChar):\n        \"\"\"This method replaces the need for \"entityInAttributeValueState\".\n        \"\"\"\n        self.consumeEntity(allowedChar=allowedChar, fromAttribute=True)\n\n    def emitCurrentToken(self):\n        \"\"\"This method is a generic handler for emitting the tags. It also sets\n        the state to \"data\" because that's what's needed after a token has been\n        emitted.\n        \"\"\"\n        token = self.currentToken\n        # Add token to the queue to be yielded\n        if (token[\"type\"] in tagTokenTypes):\n            token[\"name\"] = token[\"name\"].translate(asciiUpper2Lower)\n            if token[\"type\"] == tokenTypes[\"EndTag\"]:\n                if token[\"data\"]:\n                    self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                            \"data\": \"attributes-in-end-tag\"})\n                if token[\"selfClosing\"]:\n                    self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                            \"data\": \"self-closing-flag-on-end-tag\"})\n        self.tokenQueue.append(token)\n        self.state = self.dataState\n\n    # Below are the various tokenizer states worked out.\n    def dataState(self):\n        data = self.stream.char()\n        if data == \"&\":\n            self.state = self.entityDataState\n        elif data == \"<\":\n            self.state = self.tagOpenState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"\\u0000\"})\n        elif data is EOF:\n            # Tokenization ends.\n            return False\n        elif data in spaceCharacters:\n            # Directly after emitting a token you switch back to the \"data\n            # state\". At that point spaceCharacters are important so they are\n            # emitted separately.\n            self.tokenQueue.append({\"type\": tokenTypes[\"SpaceCharacters\"], \"data\":\n                                    data + self.stream.charsUntil(spaceCharacters, True)})\n            # No need to update lastFourChars here, since the first space will\n            # have already been appended to lastFourChars and will have broken\n            # any <!-- or --> sequences\n        else:\n            chars = self.stream.charsUntil((\"&\", \"<\", \"\\u0000\"))\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\":\n                                    data + chars})\n        return True\n\n    def entityDataState(self):\n        self.consumeEntity()\n        self.state = self.dataState\n        return True\n\n    def rcdataState(self):\n        data = self.stream.char()\n        if data == \"&\":\n            self.state = self.characterReferenceInRcdata\n        elif data == \"<\":\n            self.state = self.rcdataLessThanSignState\n        elif data == EOF:\n            # Tokenization ends.\n            return False\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"\\uFFFD\"})\n        elif data in spaceCharacters:\n            # Directly after emitting a token you switch back to the \"data\n            # state\". At that point spaceCharacters are important so they are\n            # emitted separately.\n            self.tokenQueue.append({\"type\": tokenTypes[\"SpaceCharacters\"], \"data\":\n                                    data + self.stream.charsUntil(spaceCharacters, True)})\n            # No need to update lastFourChars here, since the first space will\n            # have already been appended to lastFourChars and will have broken\n            # any <!-- or --> sequences\n        else:\n            chars = self.stream.charsUntil((\"&\", \"<\", \"\\u0000\"))\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\":\n                                    data + chars})\n        return True\n\n    def characterReferenceInRcdata(self):\n        self.consumeEntity()\n        self.state = self.rcdataState\n        return True\n\n    def rawtextState(self):\n        data = self.stream.char()\n        if data == \"<\":\n            self.state = self.rawtextLessThanSignState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"\\uFFFD\"})\n        elif data == EOF:\n            # Tokenization ends.\n            return False\n        else:\n            chars = self.stream.charsUntil((\"<\", \"\\u0000\"))\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\":\n                                    data + chars})\n        return True\n\n    def scriptDataState(self):\n        data = self.stream.char()\n        if data == \"<\":\n            self.state = self.scriptDataLessThanSignState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"\\uFFFD\"})\n        elif data == EOF:\n            # Tokenization ends.\n            return False\n        else:\n            chars = self.stream.charsUntil((\"<\", \"\\u0000\"))\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\":\n                                    data + chars})\n        return True\n\n    def plaintextState(self):\n        data = self.stream.char()\n        if data == EOF:\n            # Tokenization ends.\n            return False\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"\\uFFFD\"})\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\":\n                                    data + self.stream.charsUntil(\"\\u0000\")})\n        return True\n\n    def tagOpenState(self):\n        data = self.stream.char()\n        if data == \"!\":\n            self.state = self.markupDeclarationOpenState\n        elif data == \"/\":\n            self.state = self.closeTagOpenState\n        elif data in asciiLetters:\n            self.currentToken = {\"type\": tokenTypes[\"StartTag\"],\n                                 \"name\": data, \"data\": [],\n                                 \"selfClosing\": False,\n                                 \"selfClosingAcknowledged\": False}\n            self.state = self.tagNameState\n        elif data == \">\":\n            # XXX In theory it could be something besides a tag name. But\n            # do we really care?\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-tag-name-but-got-right-bracket\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"<>\"})\n            self.state = self.dataState\n        elif data == \"?\":\n            # XXX In theory it could be something besides a tag name. But\n            # do we really care?\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-tag-name-but-got-question-mark\"})\n            self.stream.unget(data)\n            self.state = self.bogusCommentState\n        else:\n            # XXX\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-tag-name\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"<\"})\n            self.stream.unget(data)\n            self.state = self.dataState\n        return True\n\n    def closeTagOpenState(self):\n        data = self.stream.char()\n        if data in asciiLetters:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"], \"name\": data,\n                                 \"data\": [], \"selfClosing\": False}\n            self.state = self.tagNameState\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-closing-tag-but-got-right-bracket\"})\n            self.state = self.dataState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-closing-tag-but-got-eof\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"</\"})\n            self.state = self.dataState\n        else:\n            # XXX data can be _'_...\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-closing-tag-but-got-char\",\n                                    \"datavars\": {\"data\": data}})\n            self.stream.unget(data)\n            self.state = self.bogusCommentState\n        return True\n\n    def tagNameState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            self.state = self.beforeAttributeNameState\n        elif data == \">\":\n            self.emitCurrentToken()\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-tag-name\"})\n            self.state = self.dataState\n        elif data == \"/\":\n            self.state = self.selfClosingStartTagState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"name\"] += \"\\uFFFD\"\n        else:\n            self.currentToken[\"name\"] += data\n            # (Don't use charsUntil here, because tag names are\n            # very short and it's faster to not do anything fancy)\n        return True\n\n    def rcdataLessThanSignState(self):\n        data = self.stream.char()\n        if data == \"/\":\n            self.temporaryBuffer = \"\"\n            self.state = self.rcdataEndTagOpenState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"<\"})\n            self.stream.unget(data)\n            self.state = self.rcdataState\n        return True\n\n    def rcdataEndTagOpenState(self):\n        data = self.stream.char()\n        if data in asciiLetters:\n            self.temporaryBuffer += data\n            self.state = self.rcdataEndTagNameState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"</\"})\n            self.stream.unget(data)\n            self.state = self.rcdataState\n        return True\n\n    def rcdataEndTagNameState(self):\n        appropriate = self.currentToken and self.currentToken[\"name\"].lower() == self.temporaryBuffer.lower()\n        data = self.stream.char()\n        if data in spaceCharacters and appropriate:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"],\n                                 \"name\": self.temporaryBuffer,\n                                 \"data\": [], \"selfClosing\": False}\n            self.state = self.beforeAttributeNameState\n        elif data == \"/\" and appropriate:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"],\n                                 \"name\": self.temporaryBuffer,\n                                 \"data\": [], \"selfClosing\": False}\n            self.state = self.selfClosingStartTagState\n        elif data == \">\" and appropriate:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"],\n                                 \"name\": self.temporaryBuffer,\n                                 \"data\": [], \"selfClosing\": False}\n            self.emitCurrentToken()\n            self.state = self.dataState\n        elif data in asciiLetters:\n            self.temporaryBuffer += data\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"</\" + self.temporaryBuffer})\n            self.stream.unget(data)\n            self.state = self.rcdataState\n        return True\n\n    def rawtextLessThanSignState(self):\n        data = self.stream.char()\n        if data == \"/\":\n            self.temporaryBuffer = \"\"\n            self.state = self.rawtextEndTagOpenState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"<\"})\n            self.stream.unget(data)\n            self.state = self.rawtextState\n        return True\n\n    def rawtextEndTagOpenState(self):\n        data = self.stream.char()\n        if data in asciiLetters:\n            self.temporaryBuffer += data\n            self.state = self.rawtextEndTagNameState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"</\"})\n            self.stream.unget(data)\n            self.state = self.rawtextState\n        return True\n\n    def rawtextEndTagNameState(self):\n        appropriate = self.currentToken and self.currentToken[\"name\"].lower() == self.temporaryBuffer.lower()\n        data = self.stream.char()\n        if data in spaceCharacters and appropriate:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"],\n                                 \"name\": self.temporaryBuffer,\n                                 \"data\": [], \"selfClosing\": False}\n            self.state = self.beforeAttributeNameState\n        elif data == \"/\" and appropriate:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"],\n                                 \"name\": self.temporaryBuffer,\n                                 \"data\": [], \"selfClosing\": False}\n            self.state = self.selfClosingStartTagState\n        elif data == \">\" and appropriate:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"],\n                                 \"name\": self.temporaryBuffer,\n                                 \"data\": [], \"selfClosing\": False}\n            self.emitCurrentToken()\n            self.state = self.dataState\n        elif data in asciiLetters:\n            self.temporaryBuffer += data\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"</\" + self.temporaryBuffer})\n            self.stream.unget(data)\n            self.state = self.rawtextState\n        return True\n\n    def scriptDataLessThanSignState(self):\n        data = self.stream.char()\n        if data == \"/\":\n            self.temporaryBuffer = \"\"\n            self.state = self.scriptDataEndTagOpenState\n        elif data == \"!\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"<!\"})\n            self.state = self.scriptDataEscapeStartState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"<\"})\n            self.stream.unget(data)\n            self.state = self.scriptDataState\n        return True\n\n    def scriptDataEndTagOpenState(self):\n        data = self.stream.char()\n        if data in asciiLetters:\n            self.temporaryBuffer += data\n            self.state = self.scriptDataEndTagNameState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"</\"})\n            self.stream.unget(data)\n            self.state = self.scriptDataState\n        return True\n\n    def scriptDataEndTagNameState(self):\n        appropriate = self.currentToken and self.currentToken[\"name\"].lower() == self.temporaryBuffer.lower()\n        data = self.stream.char()\n        if data in spaceCharacters and appropriate:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"],\n                                 \"name\": self.temporaryBuffer,\n                                 \"data\": [], \"selfClosing\": False}\n            self.state = self.beforeAttributeNameState\n        elif data == \"/\" and appropriate:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"],\n                                 \"name\": self.temporaryBuffer,\n                                 \"data\": [], \"selfClosing\": False}\n            self.state = self.selfClosingStartTagState\n        elif data == \">\" and appropriate:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"],\n                                 \"name\": self.temporaryBuffer,\n                                 \"data\": [], \"selfClosing\": False}\n            self.emitCurrentToken()\n            self.state = self.dataState\n        elif data in asciiLetters:\n            self.temporaryBuffer += data\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"</\" + self.temporaryBuffer})\n            self.stream.unget(data)\n            self.state = self.scriptDataState\n        return True\n\n    def scriptDataEscapeStartState(self):\n        data = self.stream.char()\n        if data == \"-\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"-\"})\n            self.state = self.scriptDataEscapeStartDashState\n        else:\n            self.stream.unget(data)\n            self.state = self.scriptDataState\n        return True\n\n    def scriptDataEscapeStartDashState(self):\n        data = self.stream.char()\n        if data == \"-\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"-\"})\n            self.state = self.scriptDataEscapedDashDashState\n        else:\n            self.stream.unget(data)\n            self.state = self.scriptDataState\n        return True\n\n    def scriptDataEscapedState(self):\n        data = self.stream.char()\n        if data == \"-\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"-\"})\n            self.state = self.scriptDataEscapedDashState\n        elif data == \"<\":\n            self.state = self.scriptDataEscapedLessThanSignState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"\\uFFFD\"})\n        elif data == EOF:\n            self.state = self.dataState\n        else:\n            chars = self.stream.charsUntil((\"<\", \"-\", \"\\u0000\"))\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\":\n                                    data + chars})\n        return True\n\n    def scriptDataEscapedDashState(self):\n        data = self.stream.char()\n        if data == \"-\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"-\"})\n            self.state = self.scriptDataEscapedDashDashState\n        elif data == \"<\":\n            self.state = self.scriptDataEscapedLessThanSignState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"\\uFFFD\"})\n            self.state = self.scriptDataEscapedState\n        elif data == EOF:\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": data})\n            self.state = self.scriptDataEscapedState\n        return True\n\n    def scriptDataEscapedDashDashState(self):\n        data = self.stream.char()\n        if data == \"-\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"-\"})\n        elif data == \"<\":\n            self.state = self.scriptDataEscapedLessThanSignState\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \">\"})\n            self.state = self.scriptDataState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"\\uFFFD\"})\n            self.state = self.scriptDataEscapedState\n        elif data == EOF:\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": data})\n            self.state = self.scriptDataEscapedState\n        return True\n\n    def scriptDataEscapedLessThanSignState(self):\n        data = self.stream.char()\n        if data == \"/\":\n            self.temporaryBuffer = \"\"\n            self.state = self.scriptDataEscapedEndTagOpenState\n        elif data in asciiLetters:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"<\" + data})\n            self.temporaryBuffer = data\n            self.state = self.scriptDataDoubleEscapeStartState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"<\"})\n            self.stream.unget(data)\n            self.state = self.scriptDataEscapedState\n        return True\n\n    def scriptDataEscapedEndTagOpenState(self):\n        data = self.stream.char()\n        if data in asciiLetters:\n            self.temporaryBuffer = data\n            self.state = self.scriptDataEscapedEndTagNameState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"</\"})\n            self.stream.unget(data)\n            self.state = self.scriptDataEscapedState\n        return True\n\n    def scriptDataEscapedEndTagNameState(self):\n        appropriate = self.currentToken and self.currentToken[\"name\"].lower() == self.temporaryBuffer.lower()\n        data = self.stream.char()\n        if data in spaceCharacters and appropriate:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"],\n                                 \"name\": self.temporaryBuffer,\n                                 \"data\": [], \"selfClosing\": False}\n            self.state = self.beforeAttributeNameState\n        elif data == \"/\" and appropriate:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"],\n                                 \"name\": self.temporaryBuffer,\n                                 \"data\": [], \"selfClosing\": False}\n            self.state = self.selfClosingStartTagState\n        elif data == \">\" and appropriate:\n            self.currentToken = {\"type\": tokenTypes[\"EndTag\"],\n                                 \"name\": self.temporaryBuffer,\n                                 \"data\": [], \"selfClosing\": False}\n            self.emitCurrentToken()\n            self.state = self.dataState\n        elif data in asciiLetters:\n            self.temporaryBuffer += data\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"</\" + self.temporaryBuffer})\n            self.stream.unget(data)\n            self.state = self.scriptDataEscapedState\n        return True\n\n    def scriptDataDoubleEscapeStartState(self):\n        data = self.stream.char()\n        if data in (spaceCharacters | frozenset((\"/\", \">\"))):\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": data})\n            if self.temporaryBuffer.lower() == \"script\":\n                self.state = self.scriptDataDoubleEscapedState\n            else:\n                self.state = self.scriptDataEscapedState\n        elif data in asciiLetters:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": data})\n            self.temporaryBuffer += data\n        else:\n            self.stream.unget(data)\n            self.state = self.scriptDataEscapedState\n        return True\n\n    def scriptDataDoubleEscapedState(self):\n        data = self.stream.char()\n        if data == \"-\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"-\"})\n            self.state = self.scriptDataDoubleEscapedDashState\n        elif data == \"<\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"<\"})\n            self.state = self.scriptDataDoubleEscapedLessThanSignState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"\\uFFFD\"})\n        elif data == EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-script-in-script\"})\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": data})\n        return True\n\n    def scriptDataDoubleEscapedDashState(self):\n        data = self.stream.char()\n        if data == \"-\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"-\"})\n            self.state = self.scriptDataDoubleEscapedDashDashState\n        elif data == \"<\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"<\"})\n            self.state = self.scriptDataDoubleEscapedLessThanSignState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"\\uFFFD\"})\n            self.state = self.scriptDataDoubleEscapedState\n        elif data == EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-script-in-script\"})\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": data})\n            self.state = self.scriptDataDoubleEscapedState\n        return True\n\n    def scriptDataDoubleEscapedDashDashState(self):\n        data = self.stream.char()\n        if data == \"-\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"-\"})\n        elif data == \"<\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"<\"})\n            self.state = self.scriptDataDoubleEscapedLessThanSignState\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \">\"})\n            self.state = self.scriptDataState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": \"\\uFFFD\"})\n            self.state = self.scriptDataDoubleEscapedState\n        elif data == EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-script-in-script\"})\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": data})\n            self.state = self.scriptDataDoubleEscapedState\n        return True\n\n    def scriptDataDoubleEscapedLessThanSignState(self):\n        data = self.stream.char()\n        if data == \"/\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": \"/\"})\n            self.temporaryBuffer = \"\"\n            self.state = self.scriptDataDoubleEscapeEndState\n        else:\n            self.stream.unget(data)\n            self.state = self.scriptDataDoubleEscapedState\n        return True\n\n    def scriptDataDoubleEscapeEndState(self):\n        data = self.stream.char()\n        if data in (spaceCharacters | frozenset((\"/\", \">\"))):\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": data})\n            if self.temporaryBuffer.lower() == \"script\":\n                self.state = self.scriptDataEscapedState\n            else:\n                self.state = self.scriptDataDoubleEscapedState\n        elif data in asciiLetters:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"], \"data\": data})\n            self.temporaryBuffer += data\n        else:\n            self.stream.unget(data)\n            self.state = self.scriptDataDoubleEscapedState\n        return True\n\n    def beforeAttributeNameState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            self.stream.charsUntil(spaceCharacters, True)\n        elif data in asciiLetters:\n            self.currentToken[\"data\"].append([data, \"\"])\n            self.state = self.attributeNameState\n        elif data == \">\":\n            self.emitCurrentToken()\n        elif data == \"/\":\n            self.state = self.selfClosingStartTagState\n        elif data in (\"'\", '\"', \"=\", \"<\"):\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"invalid-character-in-attribute-name\"})\n            self.currentToken[\"data\"].append([data, \"\"])\n            self.state = self.attributeNameState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"].append([\"\\uFFFD\", \"\"])\n            self.state = self.attributeNameState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-attribute-name-but-got-eof\"})\n            self.state = self.dataState\n        else:\n            self.currentToken[\"data\"].append([data, \"\"])\n            self.state = self.attributeNameState\n        return True\n\n    def attributeNameState(self):\n        data = self.stream.char()\n        leavingThisState = True\n        emitToken = False\n        if data == \"=\":\n            self.state = self.beforeAttributeValueState\n        elif data in asciiLetters:\n            self.currentToken[\"data\"][-1][0] += data +\\\n                self.stream.charsUntil(asciiLetters, True)\n            leavingThisState = False\n        elif data == \">\":\n            # XXX If we emit here the attributes are converted to a dict\n            # without being checked and when the code below runs we error\n            # because data is a dict not a list\n            emitToken = True\n        elif data in spaceCharacters:\n            self.state = self.afterAttributeNameState\n        elif data == \"/\":\n            self.state = self.selfClosingStartTagState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"][-1][0] += \"\\uFFFD\"\n            leavingThisState = False\n        elif data in (\"'\", '\"', \"<\"):\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\":\n                                    \"invalid-character-in-attribute-name\"})\n            self.currentToken[\"data\"][-1][0] += data\n            leavingThisState = False\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"eof-in-attribute-name\"})\n            self.state = self.dataState\n        else:\n            self.currentToken[\"data\"][-1][0] += data\n            leavingThisState = False\n\n        if leavingThisState:\n            # Attributes are not dropped at this stage. That happens when the\n            # start tag token is emitted so values can still be safely appended\n            # to attributes, but we do want to report the parse error in time.\n            self.currentToken[\"data\"][-1][0] = (\n                self.currentToken[\"data\"][-1][0].translate(asciiUpper2Lower))\n            for name, _ in self.currentToken[\"data\"][:-1]:\n                if self.currentToken[\"data\"][-1][0] == name:\n                    self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                            \"duplicate-attribute\"})\n                    break\n            # XXX Fix for above XXX\n            if emitToken:\n                self.emitCurrentToken()\n        return True\n\n    def afterAttributeNameState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            self.stream.charsUntil(spaceCharacters, True)\n        elif data == \"=\":\n            self.state = self.beforeAttributeValueState\n        elif data == \">\":\n            self.emitCurrentToken()\n        elif data in asciiLetters:\n            self.currentToken[\"data\"].append([data, \"\"])\n            self.state = self.attributeNameState\n        elif data == \"/\":\n            self.state = self.selfClosingStartTagState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"].append([\"\\uFFFD\", \"\"])\n            self.state = self.attributeNameState\n        elif data in (\"'\", '\"', \"<\"):\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"invalid-character-after-attribute-name\"})\n            self.currentToken[\"data\"].append([data, \"\"])\n            self.state = self.attributeNameState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-end-of-tag-but-got-eof\"})\n            self.state = self.dataState\n        else:\n            self.currentToken[\"data\"].append([data, \"\"])\n            self.state = self.attributeNameState\n        return True\n\n    def beforeAttributeValueState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            self.stream.charsUntil(spaceCharacters, True)\n        elif data == \"\\\"\":\n            self.state = self.attributeValueDoubleQuotedState\n        elif data == \"&\":\n            self.state = self.attributeValueUnQuotedState\n            self.stream.unget(data)\n        elif data == \"'\":\n            self.state = self.attributeValueSingleQuotedState\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-attribute-value-but-got-right-bracket\"})\n            self.emitCurrentToken()\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"][-1][1] += \"\\uFFFD\"\n            self.state = self.attributeValueUnQuotedState\n        elif data in (\"=\", \"<\", \"`\"):\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"equals-in-unquoted-attribute-value\"})\n            self.currentToken[\"data\"][-1][1] += data\n            self.state = self.attributeValueUnQuotedState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-attribute-value-but-got-eof\"})\n            self.state = self.dataState\n        else:\n            self.currentToken[\"data\"][-1][1] += data\n            self.state = self.attributeValueUnQuotedState\n        return True\n\n    def attributeValueDoubleQuotedState(self):\n        data = self.stream.char()\n        if data == \"\\\"\":\n            self.state = self.afterAttributeValueState\n        elif data == \"&\":\n            self.processEntityInAttribute('\"')\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"][-1][1] += \"\\uFFFD\"\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-attribute-value-double-quote\"})\n            self.state = self.dataState\n        else:\n            self.currentToken[\"data\"][-1][1] += data +\\\n                self.stream.charsUntil((\"\\\"\", \"&\", \"\\u0000\"))\n        return True\n\n    def attributeValueSingleQuotedState(self):\n        data = self.stream.char()\n        if data == \"'\":\n            self.state = self.afterAttributeValueState\n        elif data == \"&\":\n            self.processEntityInAttribute(\"'\")\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"][-1][1] += \"\\uFFFD\"\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-attribute-value-single-quote\"})\n            self.state = self.dataState\n        else:\n            self.currentToken[\"data\"][-1][1] += data +\\\n                self.stream.charsUntil((\"'\", \"&\", \"\\u0000\"))\n        return True\n\n    def attributeValueUnQuotedState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            self.state = self.beforeAttributeNameState\n        elif data == \"&\":\n            self.processEntityInAttribute(\">\")\n        elif data == \">\":\n            self.emitCurrentToken()\n        elif data in ('\"', \"'\", \"=\", \"<\", \"`\"):\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-character-in-unquoted-attribute-value\"})\n            self.currentToken[\"data\"][-1][1] += data\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"][-1][1] += \"\\uFFFD\"\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-attribute-value-no-quotes\"})\n            self.state = self.dataState\n        else:\n            self.currentToken[\"data\"][-1][1] += data + self.stream.charsUntil(\n                frozenset((\"&\", \">\", '\"', \"'\", \"=\", \"<\", \"`\", \"\\u0000\")) | spaceCharacters)\n        return True\n\n    def afterAttributeValueState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            self.state = self.beforeAttributeNameState\n        elif data == \">\":\n            self.emitCurrentToken()\n        elif data == \"/\":\n            self.state = self.selfClosingStartTagState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-EOF-after-attribute-value\"})\n            self.stream.unget(data)\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-character-after-attribute-value\"})\n            self.stream.unget(data)\n            self.state = self.beforeAttributeNameState\n        return True\n\n    def selfClosingStartTagState(self):\n        data = self.stream.char()\n        if data == \">\":\n            self.currentToken[\"selfClosing\"] = True\n            self.emitCurrentToken()\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\":\n                                    \"unexpected-EOF-after-solidus-in-tag\"})\n            self.stream.unget(data)\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-character-after-solidus-in-tag\"})\n            self.stream.unget(data)\n            self.state = self.beforeAttributeNameState\n        return True\n\n    def bogusCommentState(self):\n        # Make a new comment token and give it as value all the characters\n        # until the first > or EOF (charsUntil checks for EOF automatically)\n        # and emit it.\n        data = self.stream.charsUntil(\">\")\n        data = data.replace(\"\\u0000\", \"\\uFFFD\")\n        self.tokenQueue.append(\n            {\"type\": tokenTypes[\"Comment\"], \"data\": data})\n\n        # Eat the character directly after the bogus comment which is either a\n        # \">\" or an EOF.\n        self.stream.char()\n        self.state = self.dataState\n        return True\n\n    def markupDeclarationOpenState(self):\n        charStack = [self.stream.char()]\n        if charStack[-1] == \"-\":\n            charStack.append(self.stream.char())\n            if charStack[-1] == \"-\":\n                self.currentToken = {\"type\": tokenTypes[\"Comment\"], \"data\": \"\"}\n                self.state = self.commentStartState\n                return True\n        elif charStack[-1] in ('d', 'D'):\n            matched = True\n            for expected in (('o', 'O'), ('c', 'C'), ('t', 'T'),\n                             ('y', 'Y'), ('p', 'P'), ('e', 'E')):\n                charStack.append(self.stream.char())\n                if charStack[-1] not in expected:\n                    matched = False\n                    break\n            if matched:\n                self.currentToken = {\"type\": tokenTypes[\"Doctype\"],\n                                     \"name\": \"\",\n                                     \"publicId\": None, \"systemId\": None,\n                                     \"correct\": True}\n                self.state = self.doctypeState\n                return True\n        elif (charStack[-1] == \"[\" and\n              self.parser is not None and\n              self.parser.tree.openElements and\n              self.parser.tree.openElements[-1].namespace != self.parser.tree.defaultNamespace):\n            matched = True\n            for expected in [\"C\", \"D\", \"A\", \"T\", \"A\", \"[\"]:\n                charStack.append(self.stream.char())\n                if charStack[-1] != expected:\n                    matched = False\n                    break\n            if matched:\n                self.state = self.cdataSectionState\n                return True\n\n        self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                \"expected-dashes-or-doctype\"})\n\n        while charStack:\n            self.stream.unget(charStack.pop())\n        self.state = self.bogusCommentState\n        return True\n\n    def commentStartState(self):\n        data = self.stream.char()\n        if data == \"-\":\n            self.state = self.commentStartDashState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"] += \"\\uFFFD\"\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"incorrect-comment\"})\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-comment\"})\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.currentToken[\"data\"] += data\n            self.state = self.commentState\n        return True\n\n    def commentStartDashState(self):\n        data = self.stream.char()\n        if data == \"-\":\n            self.state = self.commentEndState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"] += \"-\\uFFFD\"\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"incorrect-comment\"})\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-comment\"})\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.currentToken[\"data\"] += \"-\" + data\n            self.state = self.commentState\n        return True\n\n    def commentState(self):\n        data = self.stream.char()\n        if data == \"-\":\n            self.state = self.commentEndDashState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"] += \"\\uFFFD\"\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"eof-in-comment\"})\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.currentToken[\"data\"] += data + \\\n                self.stream.charsUntil((\"-\", \"\\u0000\"))\n        return True\n\n    def commentEndDashState(self):\n        data = self.stream.char()\n        if data == \"-\":\n            self.state = self.commentEndState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"] += \"-\\uFFFD\"\n            self.state = self.commentState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-comment-end-dash\"})\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.currentToken[\"data\"] += \"-\" + data\n            self.state = self.commentState\n        return True\n\n    def commentEndState(self):\n        data = self.stream.char()\n        if data == \">\":\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"] += \"--\\uFFFD\"\n            self.state = self.commentState\n        elif data == \"!\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-bang-after-double-dash-in-comment\"})\n            self.state = self.commentEndBangState\n        elif data == \"-\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-dash-after-double-dash-in-comment\"})\n            self.currentToken[\"data\"] += data\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-comment-double-dash\"})\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            # XXX\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-char-in-comment\"})\n            self.currentToken[\"data\"] += \"--\" + data\n            self.state = self.commentState\n        return True\n\n    def commentEndBangState(self):\n        data = self.stream.char()\n        if data == \">\":\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data == \"-\":\n            self.currentToken[\"data\"] += \"--!\"\n            self.state = self.commentEndDashState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"data\"] += \"--!\\uFFFD\"\n            self.state = self.commentState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-comment-end-bang-state\"})\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.currentToken[\"data\"] += \"--!\" + data\n            self.state = self.commentState\n        return True\n\n    def doctypeState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            self.state = self.beforeDoctypeNameState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-doctype-name-but-got-eof\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"need-space-after-doctype\"})\n            self.stream.unget(data)\n            self.state = self.beforeDoctypeNameState\n        return True\n\n    def beforeDoctypeNameState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            pass\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-doctype-name-but-got-right-bracket\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"name\"] = \"\\uFFFD\"\n            self.state = self.doctypeNameState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-doctype-name-but-got-eof\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.currentToken[\"name\"] = data\n            self.state = self.doctypeNameState\n        return True\n\n    def doctypeNameState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            self.currentToken[\"name\"] = self.currentToken[\"name\"].translate(asciiUpper2Lower)\n            self.state = self.afterDoctypeNameState\n        elif data == \">\":\n            self.currentToken[\"name\"] = self.currentToken[\"name\"].translate(asciiUpper2Lower)\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"name\"] += \"\\uFFFD\"\n            self.state = self.doctypeNameState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype-name\"})\n            self.currentToken[\"correct\"] = False\n            self.currentToken[\"name\"] = self.currentToken[\"name\"].translate(asciiUpper2Lower)\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.currentToken[\"name\"] += data\n        return True\n\n    def afterDoctypeNameState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            pass\n        elif data == \">\":\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data is EOF:\n            self.currentToken[\"correct\"] = False\n            self.stream.unget(data)\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype\"})\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            if data in (\"p\", \"P\"):\n                matched = True\n                for expected in ((\"u\", \"U\"), (\"b\", \"B\"), (\"l\", \"L\"),\n                                 (\"i\", \"I\"), (\"c\", \"C\")):\n                    data = self.stream.char()\n                    if data not in expected:\n                        matched = False\n                        break\n                if matched:\n                    self.state = self.afterDoctypePublicKeywordState\n                    return True\n            elif data in (\"s\", \"S\"):\n                matched = True\n                for expected in ((\"y\", \"Y\"), (\"s\", \"S\"), (\"t\", \"T\"),\n                                 (\"e\", \"E\"), (\"m\", \"M\")):\n                    data = self.stream.char()\n                    if data not in expected:\n                        matched = False\n                        break\n                if matched:\n                    self.state = self.afterDoctypeSystemKeywordState\n                    return True\n\n            # All the characters read before the current 'data' will be\n            # [a-zA-Z], so they're garbage in the bogus doctype and can be\n            # discarded; only the latest character might be '>' or EOF\n            # and needs to be ungetted\n            self.stream.unget(data)\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"expected-space-or-right-bracket-in-doctype\", \"datavars\":\n                                    {\"data\": data}})\n            self.currentToken[\"correct\"] = False\n            self.state = self.bogusDoctypeState\n\n        return True\n\n    def afterDoctypePublicKeywordState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            self.state = self.beforeDoctypePublicIdentifierState\n        elif data in (\"'\", '\"'):\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-char-in-doctype\"})\n            self.stream.unget(data)\n            self.state = self.beforeDoctypePublicIdentifierState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.stream.unget(data)\n            self.state = self.beforeDoctypePublicIdentifierState\n        return True\n\n    def beforeDoctypePublicIdentifierState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            pass\n        elif data == \"\\\"\":\n            self.currentToken[\"publicId\"] = \"\"\n            self.state = self.doctypePublicIdentifierDoubleQuotedState\n        elif data == \"'\":\n            self.currentToken[\"publicId\"] = \"\"\n            self.state = self.doctypePublicIdentifierSingleQuotedState\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-end-of-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-char-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.state = self.bogusDoctypeState\n        return True\n\n    def doctypePublicIdentifierDoubleQuotedState(self):\n        data = self.stream.char()\n        if data == \"\\\"\":\n            self.state = self.afterDoctypePublicIdentifierState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"publicId\"] += \"\\uFFFD\"\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-end-of-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.currentToken[\"publicId\"] += data\n        return True\n\n    def doctypePublicIdentifierSingleQuotedState(self):\n        data = self.stream.char()\n        if data == \"'\":\n            self.state = self.afterDoctypePublicIdentifierState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"publicId\"] += \"\\uFFFD\"\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-end-of-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.currentToken[\"publicId\"] += data\n        return True\n\n    def afterDoctypePublicIdentifierState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            self.state = self.betweenDoctypePublicAndSystemIdentifiersState\n        elif data == \">\":\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data == '\"':\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-char-in-doctype\"})\n            self.currentToken[\"systemId\"] = \"\"\n            self.state = self.doctypeSystemIdentifierDoubleQuotedState\n        elif data == \"'\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-char-in-doctype\"})\n            self.currentToken[\"systemId\"] = \"\"\n            self.state = self.doctypeSystemIdentifierSingleQuotedState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-char-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.state = self.bogusDoctypeState\n        return True\n\n    def betweenDoctypePublicAndSystemIdentifiersState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            pass\n        elif data == \">\":\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data == '\"':\n            self.currentToken[\"systemId\"] = \"\"\n            self.state = self.doctypeSystemIdentifierDoubleQuotedState\n        elif data == \"'\":\n            self.currentToken[\"systemId\"] = \"\"\n            self.state = self.doctypeSystemIdentifierSingleQuotedState\n        elif data == EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-char-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.state = self.bogusDoctypeState\n        return True\n\n    def afterDoctypeSystemKeywordState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            self.state = self.beforeDoctypeSystemIdentifierState\n        elif data in (\"'\", '\"'):\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-char-in-doctype\"})\n            self.stream.unget(data)\n            self.state = self.beforeDoctypeSystemIdentifierState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.stream.unget(data)\n            self.state = self.beforeDoctypeSystemIdentifierState\n        return True\n\n    def beforeDoctypeSystemIdentifierState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            pass\n        elif data == \"\\\"\":\n            self.currentToken[\"systemId\"] = \"\"\n            self.state = self.doctypeSystemIdentifierDoubleQuotedState\n        elif data == \"'\":\n            self.currentToken[\"systemId\"] = \"\"\n            self.state = self.doctypeSystemIdentifierSingleQuotedState\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-char-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-char-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.state = self.bogusDoctypeState\n        return True\n\n    def doctypeSystemIdentifierDoubleQuotedState(self):\n        data = self.stream.char()\n        if data == \"\\\"\":\n            self.state = self.afterDoctypeSystemIdentifierState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"systemId\"] += \"\\uFFFD\"\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-end-of-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.currentToken[\"systemId\"] += data\n        return True\n\n    def doctypeSystemIdentifierSingleQuotedState(self):\n        data = self.stream.char()\n        if data == \"'\":\n            self.state = self.afterDoctypeSystemIdentifierState\n        elif data == \"\\u0000\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                    \"data\": \"invalid-codepoint\"})\n            self.currentToken[\"systemId\"] += \"\\uFFFD\"\n        elif data == \">\":\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-end-of-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.currentToken[\"systemId\"] += data\n        return True\n\n    def afterDoctypeSystemIdentifierState(self):\n        data = self.stream.char()\n        if data in spaceCharacters:\n            pass\n        elif data == \">\":\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data is EOF:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"eof-in-doctype\"})\n            self.currentToken[\"correct\"] = False\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"], \"data\":\n                                    \"unexpected-char-in-doctype\"})\n            self.state = self.bogusDoctypeState\n        return True\n\n    def bogusDoctypeState(self):\n        data = self.stream.char()\n        if data == \">\":\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        elif data is EOF:\n            # XXX EMIT\n            self.stream.unget(data)\n            self.tokenQueue.append(self.currentToken)\n            self.state = self.dataState\n        else:\n            pass\n        return True\n\n    def cdataSectionState(self):\n        data = []\n        while True:\n            data.append(self.stream.charsUntil(\"]\"))\n            data.append(self.stream.charsUntil(\">\"))\n            char = self.stream.char()\n            if char == EOF:\n                break\n            else:\n                assert char == \">\"\n                if data[-1][-2:] == \"]]\":\n                    data[-1] = data[-1][:-2]\n                    break\n                else:\n                    data.append(char)\n\n        data = \"\".join(data)  # pylint:disable=redefined-variable-type\n        # Deal with null here rather than in the parser\n        nullCount = data.count(\"\\u0000\")\n        if nullCount > 0:\n            for _ in range(nullCount):\n                self.tokenQueue.append({\"type\": tokenTypes[\"ParseError\"],\n                                        \"data\": \"invalid-codepoint\"})\n            data = data.replace(\"\\u0000\", \"\\uFFFD\")\n        if data:\n            self.tokenQueue.append({\"type\": tokenTypes[\"Characters\"],\n                                    \"data\": data})\n        self.state = self.dataState\n        return True\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/_trie/__init__.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom .py import Trie as PyTrie\n\nTrie = PyTrie\n\n# pylint:disable=wrong-import-position\ntry:\n    from .datrie import Trie as DATrie\nexcept ImportError:\n    pass\nelse:\n    Trie = DATrie\n# pylint:enable=wrong-import-position\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/_trie/_base.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom collections import Mapping\n\n\nclass Trie(Mapping):\n    \"\"\"Abstract base class for tries\"\"\"\n\n    def keys(self, prefix=None):\n        # pylint:disable=arguments-differ\n        keys = super(Trie, self).keys()\n\n        if prefix is None:\n            return set(keys)\n\n        return {x for x in keys if x.startswith(prefix)}\n\n    def has_keys_with_prefix(self, prefix):\n        for key in self.keys():\n            if key.startswith(prefix):\n                return True\n\n        return False\n\n    def longest_prefix(self, prefix):\n        if prefix in self:\n            return prefix\n\n        for i in range(1, len(prefix) + 1):\n            if prefix[:-i] in self:\n                return prefix[:-i]\n\n        raise KeyError(prefix)\n\n    def longest_prefix_item(self, prefix):\n        lprefix = self.longest_prefix(prefix)\n        return (lprefix, self[lprefix])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/_trie/datrie.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom datrie import Trie as DATrie\nfrom pip._vendor.six import text_type\n\nfrom ._base import Trie as ABCTrie\n\n\nclass Trie(ABCTrie):\n    def __init__(self, data):\n        chars = set()\n        for key in data.keys():\n            if not isinstance(key, text_type):\n                raise TypeError(\"All keys must be strings\")\n            for char in key:\n                chars.add(char)\n\n        self._data = DATrie(\"\".join(chars))\n        for key, value in data.items():\n            self._data[key] = value\n\n    def __contains__(self, key):\n        return key in self._data\n\n    def __len__(self):\n        return len(self._data)\n\n    def __iter__(self):\n        raise NotImplementedError()\n\n    def __getitem__(self, key):\n        return self._data[key]\n\n    def keys(self, prefix=None):\n        return self._data.keys(prefix)\n\n    def has_keys_with_prefix(self, prefix):\n        return self._data.has_keys_with_prefix(prefix)\n\n    def longest_prefix(self, prefix):\n        return self._data.longest_prefix(prefix)\n\n    def longest_prefix_item(self, prefix):\n        return self._data.longest_prefix_item(prefix)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/_trie/py.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\nfrom pip._vendor.six import text_type\n\nfrom bisect import bisect_left\n\nfrom ._base import Trie as ABCTrie\n\n\nclass Trie(ABCTrie):\n    def __init__(self, data):\n        if not all(isinstance(x, text_type) for x in data.keys()):\n            raise TypeError(\"All keys must be strings\")\n\n        self._data = data\n        self._keys = sorted(data.keys())\n        self._cachestr = \"\"\n        self._cachepoints = (0, len(data))\n\n    def __contains__(self, key):\n        return key in self._data\n\n    def __len__(self):\n        return len(self._data)\n\n    def __iter__(self):\n        return iter(self._data)\n\n    def __getitem__(self, key):\n        return self._data[key]\n\n    def keys(self, prefix=None):\n        if prefix is None or prefix == \"\" or not self._keys:\n            return set(self._keys)\n\n        if prefix.startswith(self._cachestr):\n            lo, hi = self._cachepoints\n            start = i = bisect_left(self._keys, prefix, lo, hi)\n        else:\n            start = i = bisect_left(self._keys, prefix)\n\n        keys = set()\n        if start == len(self._keys):\n            return keys\n\n        while self._keys[i].startswith(prefix):\n            keys.add(self._keys[i])\n            i += 1\n\n        self._cachestr = prefix\n        self._cachepoints = (start, i)\n\n        return keys\n\n    def has_keys_with_prefix(self, prefix):\n        if prefix in self._data:\n            return True\n\n        if prefix.startswith(self._cachestr):\n            lo, hi = self._cachepoints\n            i = bisect_left(self._keys, prefix, lo, hi)\n        else:\n            i = bisect_left(self._keys, prefix)\n\n        if i == len(self._keys):\n            return False\n\n        return self._keys[i].startswith(prefix)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/_utils.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom types import ModuleType\n\nfrom pip._vendor.six import text_type\n\ntry:\n    import xml.etree.cElementTree as default_etree\nexcept ImportError:\n    import xml.etree.ElementTree as default_etree\n\n\n__all__ = [\"default_etree\", \"MethodDispatcher\", \"isSurrogatePair\",\n           \"surrogatePairToCodepoint\", \"moduleFactoryFactory\",\n           \"supports_lone_surrogates\"]\n\n\n# Platforms not supporting lone surrogates (\\uD800-\\uDFFF) should be\n# caught by the below test. In general this would be any platform\n# using UTF-16 as its encoding of unicode strings, such as\n# Jython. This is because UTF-16 itself is based on the use of such\n# surrogates, and there is no mechanism to further escape such\n# escapes.\ntry:\n    _x = eval('\"\\\\uD800\"')  # pylint:disable=eval-used\n    if not isinstance(_x, text_type):\n        # We need this with u\"\" because of http://bugs.jython.org/issue2039\n        _x = eval('u\"\\\\uD800\"')  # pylint:disable=eval-used\n        assert isinstance(_x, text_type)\nexcept:  # pylint:disable=bare-except\n    supports_lone_surrogates = False\nelse:\n    supports_lone_surrogates = True\n\n\nclass MethodDispatcher(dict):\n    \"\"\"Dict with 2 special properties:\n\n    On initiation, keys that are lists, sets or tuples are converted to\n    multiple keys so accessing any one of the items in the original\n    list-like object returns the matching value\n\n    md = MethodDispatcher({(\"foo\", \"bar\"):\"baz\"})\n    md[\"foo\"] == \"baz\"\n\n    A default value which can be set through the default attribute.\n    \"\"\"\n\n    def __init__(self, items=()):\n        # Using _dictEntries instead of directly assigning to self is about\n        # twice as fast. Please do careful performance testing before changing\n        # anything here.\n        _dictEntries = []\n        for name, value in items:\n            if isinstance(name, (list, tuple, frozenset, set)):\n                for item in name:\n                    _dictEntries.append((item, value))\n            else:\n                _dictEntries.append((name, value))\n        dict.__init__(self, _dictEntries)\n        assert len(self) == len(_dictEntries)\n        self.default = None\n\n    def __getitem__(self, key):\n        return dict.get(self, key, self.default)\n\n\n# Some utility functions to deal with weirdness around UCS2 vs UCS4\n# python builds\n\ndef isSurrogatePair(data):\n    return (len(data) == 2 and\n            ord(data[0]) >= 0xD800 and ord(data[0]) <= 0xDBFF and\n            ord(data[1]) >= 0xDC00 and ord(data[1]) <= 0xDFFF)\n\n\ndef surrogatePairToCodepoint(data):\n    char_val = (0x10000 + (ord(data[0]) - 0xD800) * 0x400 +\n                (ord(data[1]) - 0xDC00))\n    return char_val\n\n# Module Factory Factory (no, this isn't Java, I know)\n# Here to stop this being duplicated all over the place.\n\n\ndef moduleFactoryFactory(factory):\n    moduleCache = {}\n\n    def moduleFactory(baseModule, *args, **kwargs):\n        if isinstance(ModuleType.__name__, type(\"\")):\n            name = \"_%s_factory\" % baseModule.__name__\n        else:\n            name = b\"_%s_factory\" % baseModule.__name__\n\n        kwargs_tuple = tuple(kwargs.items())\n\n        try:\n            return moduleCache[name][args][kwargs_tuple]\n        except KeyError:\n            mod = ModuleType(name)\n            objs = factory(baseModule, *args, **kwargs)\n            mod.__dict__.update(objs)\n            if \"name\" not in moduleCache:\n                moduleCache[name] = {}\n            if \"args\" not in moduleCache[name]:\n                moduleCache[name][args] = {}\n            if \"kwargs\" not in moduleCache[name][args]:\n                moduleCache[name][args][kwargs_tuple] = {}\n            moduleCache[name][args][kwargs_tuple] = mod\n            return mod\n\n    return moduleFactory\n\n\ndef memoize(func):\n    cache = {}\n\n    def wrapped(*args, **kwargs):\n        key = (tuple(args), tuple(kwargs.items()))\n        if key not in cache:\n            cache[key] = func(*args, **kwargs)\n        return cache[key]\n\n    return wrapped\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/constants.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nimport string\n\nEOF = None\n\nE = {\n    \"null-character\":\n        \"Null character in input stream, replaced with U+FFFD.\",\n    \"invalid-codepoint\":\n        \"Invalid codepoint in stream.\",\n    \"incorrectly-placed-solidus\":\n        \"Solidus (/) incorrectly placed in tag.\",\n    \"incorrect-cr-newline-entity\":\n        \"Incorrect CR newline entity, replaced with LF.\",\n    \"illegal-windows-1252-entity\":\n        \"Entity used with illegal number (windows-1252 reference).\",\n    \"cant-convert-numeric-entity\":\n        \"Numeric entity couldn't be converted to character \"\n        \"(codepoint U+%(charAsInt)08x).\",\n    \"illegal-codepoint-for-numeric-entity\":\n        \"Numeric entity represents an illegal codepoint: \"\n        \"U+%(charAsInt)08x.\",\n    \"numeric-entity-without-semicolon\":\n        \"Numeric entity didn't end with ';'.\",\n    \"expected-numeric-entity-but-got-eof\":\n        \"Numeric entity expected. Got end of file instead.\",\n    \"expected-numeric-entity\":\n        \"Numeric entity expected but none found.\",\n    \"named-entity-without-semicolon\":\n        \"Named entity didn't end with ';'.\",\n    \"expected-named-entity\":\n        \"Named entity expected. Got none.\",\n    \"attributes-in-end-tag\":\n        \"End tag contains unexpected attributes.\",\n    'self-closing-flag-on-end-tag':\n        \"End tag contains unexpected self-closing flag.\",\n    \"expected-tag-name-but-got-right-bracket\":\n        \"Expected tag name. Got '>' instead.\",\n    \"expected-tag-name-but-got-question-mark\":\n        \"Expected tag name. Got '?' instead. (HTML doesn't \"\n        \"support processing instructions.)\",\n    \"expected-tag-name\":\n        \"Expected tag name. Got something else instead\",\n    \"expected-closing-tag-but-got-right-bracket\":\n        \"Expected closing tag. Got '>' instead. Ignoring '</>'.\",\n    \"expected-closing-tag-but-got-eof\":\n        \"Expected closing tag. Unexpected end of file.\",\n    \"expected-closing-tag-but-got-char\":\n        \"Expected closing tag. Unexpected character '%(data)s' found.\",\n    \"eof-in-tag-name\":\n        \"Unexpected end of file in the tag name.\",\n    \"expected-attribute-name-but-got-eof\":\n        \"Unexpected end of file. Expected attribute name instead.\",\n    \"eof-in-attribute-name\":\n        \"Unexpected end of file in attribute name.\",\n    \"invalid-character-in-attribute-name\":\n        \"Invalid character in attribute name\",\n    \"duplicate-attribute\":\n        \"Dropped duplicate attribute on tag.\",\n    \"expected-end-of-tag-name-but-got-eof\":\n        \"Unexpected end of file. Expected = or end of tag.\",\n    \"expected-attribute-value-but-got-eof\":\n        \"Unexpected end of file. Expected attribute value.\",\n    \"expected-attribute-value-but-got-right-bracket\":\n        \"Expected attribute value. Got '>' instead.\",\n    'equals-in-unquoted-attribute-value':\n        \"Unexpected = in unquoted attribute\",\n    'unexpected-character-in-unquoted-attribute-value':\n        \"Unexpected character in unquoted attribute\",\n    \"invalid-character-after-attribute-name\":\n        \"Unexpected character after attribute name.\",\n    \"unexpected-character-after-attribute-value\":\n        \"Unexpected character after attribute value.\",\n    \"eof-in-attribute-value-double-quote\":\n        \"Unexpected end of file in attribute value (\\\").\",\n    \"eof-in-attribute-value-single-quote\":\n        \"Unexpected end of file in attribute value (').\",\n    \"eof-in-attribute-value-no-quotes\":\n        \"Unexpected end of file in attribute value.\",\n    \"unexpected-EOF-after-solidus-in-tag\":\n        \"Unexpected end of file in tag. Expected >\",\n    \"unexpected-character-after-solidus-in-tag\":\n        \"Unexpected character after / in tag. Expected >\",\n    \"expected-dashes-or-doctype\":\n        \"Expected '--' or 'DOCTYPE'. Not found.\",\n    \"unexpected-bang-after-double-dash-in-comment\":\n        \"Unexpected ! after -- in comment\",\n    \"unexpected-space-after-double-dash-in-comment\":\n        \"Unexpected space after -- in comment\",\n    \"incorrect-comment\":\n        \"Incorrect comment.\",\n    \"eof-in-comment\":\n        \"Unexpected end of file in comment.\",\n    \"eof-in-comment-end-dash\":\n        \"Unexpected end of file in comment (-)\",\n    \"unexpected-dash-after-double-dash-in-comment\":\n        \"Unexpected '-' after '--' found in comment.\",\n    \"eof-in-comment-double-dash\":\n        \"Unexpected end of file in comment (--).\",\n    \"eof-in-comment-end-space-state\":\n        \"Unexpected end of file in comment.\",\n    \"eof-in-comment-end-bang-state\":\n        \"Unexpected end of file in comment.\",\n    \"unexpected-char-in-comment\":\n        \"Unexpected character in comment found.\",\n    \"need-space-after-doctype\":\n        \"No space after literal string 'DOCTYPE'.\",\n    \"expected-doctype-name-but-got-right-bracket\":\n        \"Unexpected > character. Expected DOCTYPE name.\",\n    \"expected-doctype-name-but-got-eof\":\n        \"Unexpected end of file. Expected DOCTYPE name.\",\n    \"eof-in-doctype-name\":\n        \"Unexpected end of file in DOCTYPE name.\",\n    \"eof-in-doctype\":\n        \"Unexpected end of file in DOCTYPE.\",\n    \"expected-space-or-right-bracket-in-doctype\":\n        \"Expected space or '>'. Got '%(data)s'\",\n    \"unexpected-end-of-doctype\":\n        \"Unexpected end of DOCTYPE.\",\n    \"unexpected-char-in-doctype\":\n        \"Unexpected character in DOCTYPE.\",\n    \"eof-in-innerhtml\":\n        \"XXX innerHTML EOF\",\n    \"unexpected-doctype\":\n        \"Unexpected DOCTYPE. Ignored.\",\n    \"non-html-root\":\n        \"html needs to be the first start tag.\",\n    \"expected-doctype-but-got-eof\":\n        \"Unexpected End of file. Expected DOCTYPE.\",\n    \"unknown-doctype\":\n        \"Erroneous DOCTYPE.\",\n    \"expected-doctype-but-got-chars\":\n        \"Unexpected non-space characters. Expected DOCTYPE.\",\n    \"expected-doctype-but-got-start-tag\":\n        \"Unexpected start tag (%(name)s). Expected DOCTYPE.\",\n    \"expected-doctype-but-got-end-tag\":\n        \"Unexpected end tag (%(name)s). Expected DOCTYPE.\",\n    \"end-tag-after-implied-root\":\n        \"Unexpected end tag (%(name)s) after the (implied) root element.\",\n    \"expected-named-closing-tag-but-got-eof\":\n        \"Unexpected end of file. Expected end tag (%(name)s).\",\n    \"two-heads-are-not-better-than-one\":\n        \"Unexpected start tag head in existing head. Ignored.\",\n    \"unexpected-end-tag\":\n        \"Unexpected end tag (%(name)s). Ignored.\",\n    \"unexpected-start-tag-out-of-my-head\":\n        \"Unexpected start tag (%(name)s) that can be in head. Moved.\",\n    \"unexpected-start-tag\":\n        \"Unexpected start tag (%(name)s).\",\n    \"missing-end-tag\":\n        \"Missing end tag (%(name)s).\",\n    \"missing-end-tags\":\n        \"Missing end tags (%(name)s).\",\n    \"unexpected-start-tag-implies-end-tag\":\n        \"Unexpected start tag (%(startName)s) \"\n        \"implies end tag (%(endName)s).\",\n    \"unexpected-start-tag-treated-as\":\n        \"Unexpected start tag (%(originalName)s). Treated as %(newName)s.\",\n    \"deprecated-tag\":\n        \"Unexpected start tag %(name)s. Don't use it!\",\n    \"unexpected-start-tag-ignored\":\n        \"Unexpected start tag %(name)s. Ignored.\",\n    \"expected-one-end-tag-but-got-another\":\n        \"Unexpected end tag (%(gotName)s). \"\n        \"Missing end tag (%(expectedName)s).\",\n    \"end-tag-too-early\":\n        \"End tag (%(name)s) seen too early. Expected other end tag.\",\n    \"end-tag-too-early-named\":\n        \"Unexpected end tag (%(gotName)s). Expected end tag (%(expectedName)s).\",\n    \"end-tag-too-early-ignored\":\n        \"End tag (%(name)s) seen too early. Ignored.\",\n    \"adoption-agency-1.1\":\n        \"End tag (%(name)s) violates step 1, \"\n        \"paragraph 1 of the adoption agency algorithm.\",\n    \"adoption-agency-1.2\":\n        \"End tag (%(name)s) violates step 1, \"\n        \"paragraph 2 of the adoption agency algorithm.\",\n    \"adoption-agency-1.3\":\n        \"End tag (%(name)s) violates step 1, \"\n        \"paragraph 3 of the adoption agency algorithm.\",\n    \"adoption-agency-4.4\":\n        \"End tag (%(name)s) violates step 4, \"\n        \"paragraph 4 of the adoption agency algorithm.\",\n    \"unexpected-end-tag-treated-as\":\n        \"Unexpected end tag (%(originalName)s). Treated as %(newName)s.\",\n    \"no-end-tag\":\n        \"This element (%(name)s) has no end tag.\",\n    \"unexpected-implied-end-tag-in-table\":\n        \"Unexpected implied end tag (%(name)s) in the table phase.\",\n    \"unexpected-implied-end-tag-in-table-body\":\n        \"Unexpected implied end tag (%(name)s) in the table body phase.\",\n    \"unexpected-char-implies-table-voodoo\":\n        \"Unexpected non-space characters in \"\n        \"table context caused voodoo mode.\",\n    \"unexpected-hidden-input-in-table\":\n        \"Unexpected input with type hidden in table context.\",\n    \"unexpected-form-in-table\":\n        \"Unexpected form in table context.\",\n    \"unexpected-start-tag-implies-table-voodoo\":\n        \"Unexpected start tag (%(name)s) in \"\n        \"table context caused voodoo mode.\",\n    \"unexpected-end-tag-implies-table-voodoo\":\n        \"Unexpected end tag (%(name)s) in \"\n        \"table context caused voodoo mode.\",\n    \"unexpected-cell-in-table-body\":\n        \"Unexpected table cell start tag (%(name)s) \"\n        \"in the table body phase.\",\n    \"unexpected-cell-end-tag\":\n        \"Got table cell end tag (%(name)s) \"\n        \"while required end tags are missing.\",\n    \"unexpected-end-tag-in-table-body\":\n        \"Unexpected end tag (%(name)s) in the table body phase. Ignored.\",\n    \"unexpected-implied-end-tag-in-table-row\":\n        \"Unexpected implied end tag (%(name)s) in the table row phase.\",\n    \"unexpected-end-tag-in-table-row\":\n        \"Unexpected end tag (%(name)s) in the table row phase. Ignored.\",\n    \"unexpected-select-in-select\":\n        \"Unexpected select start tag in the select phase \"\n        \"treated as select end tag.\",\n    \"unexpected-input-in-select\":\n        \"Unexpected input start tag in the select phase.\",\n    \"unexpected-start-tag-in-select\":\n        \"Unexpected start tag token (%(name)s in the select phase. \"\n        \"Ignored.\",\n    \"unexpected-end-tag-in-select\":\n        \"Unexpected end tag (%(name)s) in the select phase. Ignored.\",\n    \"unexpected-table-element-start-tag-in-select-in-table\":\n        \"Unexpected table element start tag (%(name)s) in the select in table phase.\",\n    \"unexpected-table-element-end-tag-in-select-in-table\":\n        \"Unexpected table element end tag (%(name)s) in the select in table phase.\",\n    \"unexpected-char-after-body\":\n        \"Unexpected non-space characters in the after body phase.\",\n    \"unexpected-start-tag-after-body\":\n        \"Unexpected start tag token (%(name)s)\"\n        \" in the after body phase.\",\n    \"unexpected-end-tag-after-body\":\n        \"Unexpected end tag token (%(name)s)\"\n        \" in the after body phase.\",\n    \"unexpected-char-in-frameset\":\n        \"Unexpected characters in the frameset phase. Characters ignored.\",\n    \"unexpected-start-tag-in-frameset\":\n        \"Unexpected start tag token (%(name)s)\"\n        \" in the frameset phase. Ignored.\",\n    \"unexpected-frameset-in-frameset-innerhtml\":\n        \"Unexpected end tag token (frameset) \"\n        \"in the frameset phase (innerHTML).\",\n    \"unexpected-end-tag-in-frameset\":\n        \"Unexpected end tag token (%(name)s)\"\n        \" in the frameset phase. Ignored.\",\n    \"unexpected-char-after-frameset\":\n        \"Unexpected non-space characters in the \"\n        \"after frameset phase. Ignored.\",\n    \"unexpected-start-tag-after-frameset\":\n        \"Unexpected start tag (%(name)s)\"\n        \" in the after frameset phase. Ignored.\",\n    \"unexpected-end-tag-after-frameset\":\n        \"Unexpected end tag (%(name)s)\"\n        \" in the after frameset phase. Ignored.\",\n    \"unexpected-end-tag-after-body-innerhtml\":\n        \"Unexpected end tag after body(innerHtml)\",\n    \"expected-eof-but-got-char\":\n        \"Unexpected non-space characters. Expected end of file.\",\n    \"expected-eof-but-got-start-tag\":\n        \"Unexpected start tag (%(name)s)\"\n        \". Expected end of file.\",\n    \"expected-eof-but-got-end-tag\":\n        \"Unexpected end tag (%(name)s)\"\n        \". Expected end of file.\",\n    \"eof-in-table\":\n        \"Unexpected end of file. Expected table content.\",\n    \"eof-in-select\":\n        \"Unexpected end of file. Expected select content.\",\n    \"eof-in-frameset\":\n        \"Unexpected end of file. Expected frameset content.\",\n    \"eof-in-script-in-script\":\n        \"Unexpected end of file. Expected script content.\",\n    \"eof-in-foreign-lands\":\n        \"Unexpected end of file. Expected foreign content\",\n    \"non-void-element-with-trailing-solidus\":\n        \"Trailing solidus not allowed on element %(name)s\",\n    \"unexpected-html-element-in-foreign-content\":\n        \"Element %(name)s not allowed in a non-html context\",\n    \"unexpected-end-tag-before-html\":\n        \"Unexpected end tag (%(name)s) before html.\",\n    \"unexpected-inhead-noscript-tag\":\n        \"Element %(name)s not allowed in a inhead-noscript context\",\n    \"eof-in-head-noscript\":\n        \"Unexpected end of file. Expected inhead-noscript content\",\n    \"char-in-head-noscript\":\n        \"Unexpected non-space character. Expected inhead-noscript content\",\n    \"XXX-undefined-error\":\n        \"Undefined error (this sucks and should be fixed)\",\n}\n\nnamespaces = {\n    \"html\": \"http://www.w3.org/1999/xhtml\",\n    \"mathml\": \"http://www.w3.org/1998/Math/MathML\",\n    \"svg\": \"http://www.w3.org/2000/svg\",\n    \"xlink\": \"http://www.w3.org/1999/xlink\",\n    \"xml\": \"http://www.w3.org/XML/1998/namespace\",\n    \"xmlns\": \"http://www.w3.org/2000/xmlns/\"\n}\n\nscopingElements = frozenset([\n    (namespaces[\"html\"], \"applet\"),\n    (namespaces[\"html\"], \"caption\"),\n    (namespaces[\"html\"], \"html\"),\n    (namespaces[\"html\"], \"marquee\"),\n    (namespaces[\"html\"], \"object\"),\n    (namespaces[\"html\"], \"table\"),\n    (namespaces[\"html\"], \"td\"),\n    (namespaces[\"html\"], \"th\"),\n    (namespaces[\"mathml\"], \"mi\"),\n    (namespaces[\"mathml\"], \"mo\"),\n    (namespaces[\"mathml\"], \"mn\"),\n    (namespaces[\"mathml\"], \"ms\"),\n    (namespaces[\"mathml\"], \"mtext\"),\n    (namespaces[\"mathml\"], \"annotation-xml\"),\n    (namespaces[\"svg\"], \"foreignObject\"),\n    (namespaces[\"svg\"], \"desc\"),\n    (namespaces[\"svg\"], \"title\"),\n])\n\nformattingElements = frozenset([\n    (namespaces[\"html\"], \"a\"),\n    (namespaces[\"html\"], \"b\"),\n    (namespaces[\"html\"], \"big\"),\n    (namespaces[\"html\"], \"code\"),\n    (namespaces[\"html\"], \"em\"),\n    (namespaces[\"html\"], \"font\"),\n    (namespaces[\"html\"], \"i\"),\n    (namespaces[\"html\"], \"nobr\"),\n    (namespaces[\"html\"], \"s\"),\n    (namespaces[\"html\"], \"small\"),\n    (namespaces[\"html\"], \"strike\"),\n    (namespaces[\"html\"], \"strong\"),\n    (namespaces[\"html\"], \"tt\"),\n    (namespaces[\"html\"], \"u\")\n])\n\nspecialElements = frozenset([\n    (namespaces[\"html\"], \"address\"),\n    (namespaces[\"html\"], \"applet\"),\n    (namespaces[\"html\"], \"area\"),\n    (namespaces[\"html\"], \"article\"),\n    (namespaces[\"html\"], \"aside\"),\n    (namespaces[\"html\"], \"base\"),\n    (namespaces[\"html\"], \"basefont\"),\n    (namespaces[\"html\"], \"bgsound\"),\n    (namespaces[\"html\"], \"blockquote\"),\n    (namespaces[\"html\"], \"body\"),\n    (namespaces[\"html\"], \"br\"),\n    (namespaces[\"html\"], \"button\"),\n    (namespaces[\"html\"], \"caption\"),\n    (namespaces[\"html\"], \"center\"),\n    (namespaces[\"html\"], \"col\"),\n    (namespaces[\"html\"], \"colgroup\"),\n    (namespaces[\"html\"], \"command\"),\n    (namespaces[\"html\"], \"dd\"),\n    (namespaces[\"html\"], \"details\"),\n    (namespaces[\"html\"], \"dir\"),\n    (namespaces[\"html\"], \"div\"),\n    (namespaces[\"html\"], \"dl\"),\n    (namespaces[\"html\"], \"dt\"),\n    (namespaces[\"html\"], \"embed\"),\n    (namespaces[\"html\"], \"fieldset\"),\n    (namespaces[\"html\"], \"figure\"),\n    (namespaces[\"html\"], \"footer\"),\n    (namespaces[\"html\"], \"form\"),\n    (namespaces[\"html\"], \"frame\"),\n    (namespaces[\"html\"], \"frameset\"),\n    (namespaces[\"html\"], \"h1\"),\n    (namespaces[\"html\"], \"h2\"),\n    (namespaces[\"html\"], \"h3\"),\n    (namespaces[\"html\"], \"h4\"),\n    (namespaces[\"html\"], \"h5\"),\n    (namespaces[\"html\"], \"h6\"),\n    (namespaces[\"html\"], \"head\"),\n    (namespaces[\"html\"], \"header\"),\n    (namespaces[\"html\"], \"hr\"),\n    (namespaces[\"html\"], \"html\"),\n    (namespaces[\"html\"], \"iframe\"),\n    # Note that image is commented out in the spec as \"this isn't an\n    # element that can end up on the stack, so it doesn't matter,\"\n    (namespaces[\"html\"], \"image\"),\n    (namespaces[\"html\"], \"img\"),\n    (namespaces[\"html\"], \"input\"),\n    (namespaces[\"html\"], \"isindex\"),\n    (namespaces[\"html\"], \"li\"),\n    (namespaces[\"html\"], \"link\"),\n    (namespaces[\"html\"], \"listing\"),\n    (namespaces[\"html\"], \"marquee\"),\n    (namespaces[\"html\"], \"menu\"),\n    (namespaces[\"html\"], \"meta\"),\n    (namespaces[\"html\"], \"nav\"),\n    (namespaces[\"html\"], \"noembed\"),\n    (namespaces[\"html\"], \"noframes\"),\n    (namespaces[\"html\"], \"noscript\"),\n    (namespaces[\"html\"], \"object\"),\n    (namespaces[\"html\"], \"ol\"),\n    (namespaces[\"html\"], \"p\"),\n    (namespaces[\"html\"], \"param\"),\n    (namespaces[\"html\"], \"plaintext\"),\n    (namespaces[\"html\"], \"pre\"),\n    (namespaces[\"html\"], \"script\"),\n    (namespaces[\"html\"], \"section\"),\n    (namespaces[\"html\"], \"select\"),\n    (namespaces[\"html\"], \"style\"),\n    (namespaces[\"html\"], \"table\"),\n    (namespaces[\"html\"], \"tbody\"),\n    (namespaces[\"html\"], \"td\"),\n    (namespaces[\"html\"], \"textarea\"),\n    (namespaces[\"html\"], \"tfoot\"),\n    (namespaces[\"html\"], \"th\"),\n    (namespaces[\"html\"], \"thead\"),\n    (namespaces[\"html\"], \"title\"),\n    (namespaces[\"html\"], \"tr\"),\n    (namespaces[\"html\"], \"ul\"),\n    (namespaces[\"html\"], \"wbr\"),\n    (namespaces[\"html\"], \"xmp\"),\n    (namespaces[\"svg\"], \"foreignObject\")\n])\n\nhtmlIntegrationPointElements = frozenset([\n    (namespaces[\"mathml\"], \"annotation-xml\"),\n    (namespaces[\"svg\"], \"foreignObject\"),\n    (namespaces[\"svg\"], \"desc\"),\n    (namespaces[\"svg\"], \"title\")\n])\n\nmathmlTextIntegrationPointElements = frozenset([\n    (namespaces[\"mathml\"], \"mi\"),\n    (namespaces[\"mathml\"], \"mo\"),\n    (namespaces[\"mathml\"], \"mn\"),\n    (namespaces[\"mathml\"], \"ms\"),\n    (namespaces[\"mathml\"], \"mtext\")\n])\n\nadjustSVGAttributes = {\n    \"attributename\": \"attributeName\",\n    \"attributetype\": \"attributeType\",\n    \"basefrequency\": \"baseFrequency\",\n    \"baseprofile\": \"baseProfile\",\n    \"calcmode\": \"calcMode\",\n    \"clippathunits\": \"clipPathUnits\",\n    \"contentscripttype\": \"contentScriptType\",\n    \"contentstyletype\": \"contentStyleType\",\n    \"diffuseconstant\": \"diffuseConstant\",\n    \"edgemode\": \"edgeMode\",\n    \"externalresourcesrequired\": \"externalResourcesRequired\",\n    \"filterres\": \"filterRes\",\n    \"filterunits\": \"filterUnits\",\n    \"glyphref\": \"glyphRef\",\n    \"gradienttransform\": \"gradientTransform\",\n    \"gradientunits\": \"gradientUnits\",\n    \"kernelmatrix\": \"kernelMatrix\",\n    \"kernelunitlength\": \"kernelUnitLength\",\n    \"keypoints\": \"keyPoints\",\n    \"keysplines\": \"keySplines\",\n    \"keytimes\": \"keyTimes\",\n    \"lengthadjust\": \"lengthAdjust\",\n    \"limitingconeangle\": \"limitingConeAngle\",\n    \"markerheight\": \"markerHeight\",\n    \"markerunits\": \"markerUnits\",\n    \"markerwidth\": \"markerWidth\",\n    \"maskcontentunits\": \"maskContentUnits\",\n    \"maskunits\": \"maskUnits\",\n    \"numoctaves\": \"numOctaves\",\n    \"pathlength\": \"pathLength\",\n    \"patterncontentunits\": \"patternContentUnits\",\n    \"patterntransform\": \"patternTransform\",\n    \"patternunits\": \"patternUnits\",\n    \"pointsatx\": \"pointsAtX\",\n    \"pointsaty\": \"pointsAtY\",\n    \"pointsatz\": \"pointsAtZ\",\n    \"preservealpha\": \"preserveAlpha\",\n    \"preserveaspectratio\": \"preserveAspectRatio\",\n    \"primitiveunits\": \"primitiveUnits\",\n    \"refx\": \"refX\",\n    \"refy\": \"refY\",\n    \"repeatcount\": \"repeatCount\",\n    \"repeatdur\": \"repeatDur\",\n    \"requiredextensions\": \"requiredExtensions\",\n    \"requiredfeatures\": \"requiredFeatures\",\n    \"specularconstant\": \"specularConstant\",\n    \"specularexponent\": \"specularExponent\",\n    \"spreadmethod\": \"spreadMethod\",\n    \"startoffset\": \"startOffset\",\n    \"stddeviation\": \"stdDeviation\",\n    \"stitchtiles\": \"stitchTiles\",\n    \"surfacescale\": \"surfaceScale\",\n    \"systemlanguage\": \"systemLanguage\",\n    \"tablevalues\": \"tableValues\",\n    \"targetx\": \"targetX\",\n    \"targety\": \"targetY\",\n    \"textlength\": \"textLength\",\n    \"viewbox\": \"viewBox\",\n    \"viewtarget\": \"viewTarget\",\n    \"xchannelselector\": \"xChannelSelector\",\n    \"ychannelselector\": \"yChannelSelector\",\n    \"zoomandpan\": \"zoomAndPan\"\n}\n\nadjustMathMLAttributes = {\"definitionurl\": \"definitionURL\"}\n\nadjustForeignAttributes = {\n    \"xlink:actuate\": (\"xlink\", \"actuate\", namespaces[\"xlink\"]),\n    \"xlink:arcrole\": (\"xlink\", \"arcrole\", namespaces[\"xlink\"]),\n    \"xlink:href\": (\"xlink\", \"href\", namespaces[\"xlink\"]),\n    \"xlink:role\": (\"xlink\", \"role\", namespaces[\"xlink\"]),\n    \"xlink:show\": (\"xlink\", \"show\", namespaces[\"xlink\"]),\n    \"xlink:title\": (\"xlink\", \"title\", namespaces[\"xlink\"]),\n    \"xlink:type\": (\"xlink\", \"type\", namespaces[\"xlink\"]),\n    \"xml:base\": (\"xml\", \"base\", namespaces[\"xml\"]),\n    \"xml:lang\": (\"xml\", \"lang\", namespaces[\"xml\"]),\n    \"xml:space\": (\"xml\", \"space\", namespaces[\"xml\"]),\n    \"xmlns\": (None, \"xmlns\", namespaces[\"xmlns\"]),\n    \"xmlns:xlink\": (\"xmlns\", \"xlink\", namespaces[\"xmlns\"])\n}\n\nunadjustForeignAttributes = dict([((ns, local), qname) for qname, (prefix, local, ns) in\n                                  adjustForeignAttributes.items()])\n\nspaceCharacters = frozenset([\n    \"\\t\",\n    \"\\n\",\n    \"\\u000C\",\n    \" \",\n    \"\\r\"\n])\n\ntableInsertModeElements = frozenset([\n    \"table\",\n    \"tbody\",\n    \"tfoot\",\n    \"thead\",\n    \"tr\"\n])\n\nasciiLowercase = frozenset(string.ascii_lowercase)\nasciiUppercase = frozenset(string.ascii_uppercase)\nasciiLetters = frozenset(string.ascii_letters)\ndigits = frozenset(string.digits)\nhexDigits = frozenset(string.hexdigits)\n\nasciiUpper2Lower = dict([(ord(c), ord(c.lower()))\n                         for c in string.ascii_uppercase])\n\n# Heading elements need to be ordered\nheadingElements = (\n    \"h1\",\n    \"h2\",\n    \"h3\",\n    \"h4\",\n    \"h5\",\n    \"h6\"\n)\n\nvoidElements = frozenset([\n    \"base\",\n    \"command\",\n    \"event-source\",\n    \"link\",\n    \"meta\",\n    \"hr\",\n    \"br\",\n    \"img\",\n    \"embed\",\n    \"param\",\n    \"area\",\n    \"col\",\n    \"input\",\n    \"source\",\n    \"track\"\n])\n\ncdataElements = frozenset(['title', 'textarea'])\n\nrcdataElements = frozenset([\n    'style',\n    'script',\n    'xmp',\n    'iframe',\n    'noembed',\n    'noframes',\n    'noscript'\n])\n\nbooleanAttributes = {\n    \"\": frozenset([\"irrelevant\", \"itemscope\"]),\n    \"style\": frozenset([\"scoped\"]),\n    \"img\": frozenset([\"ismap\"]),\n    \"audio\": frozenset([\"autoplay\", \"controls\"]),\n    \"video\": frozenset([\"autoplay\", \"controls\"]),\n    \"script\": frozenset([\"defer\", \"async\"]),\n    \"details\": frozenset([\"open\"]),\n    \"datagrid\": frozenset([\"multiple\", \"disabled\"]),\n    \"command\": frozenset([\"hidden\", \"disabled\", \"checked\", \"default\"]),\n    \"hr\": frozenset([\"noshade\"]),\n    \"menu\": frozenset([\"autosubmit\"]),\n    \"fieldset\": frozenset([\"disabled\", \"readonly\"]),\n    \"option\": frozenset([\"disabled\", \"readonly\", \"selected\"]),\n    \"optgroup\": frozenset([\"disabled\", \"readonly\"]),\n    \"button\": frozenset([\"disabled\", \"autofocus\"]),\n    \"input\": frozenset([\"disabled\", \"readonly\", \"required\", \"autofocus\", \"checked\", \"ismap\"]),\n    \"select\": frozenset([\"disabled\", \"readonly\", \"autofocus\", \"multiple\"]),\n    \"output\": frozenset([\"disabled\", \"readonly\"]),\n    \"iframe\": frozenset([\"seamless\"]),\n}\n\n# entitiesWindows1252 has to be _ordered_ and needs to have an index. It\n# therefore can't be a frozenset.\nentitiesWindows1252 = (\n    8364,   # 0x80  0x20AC  EURO SIGN\n    65533,  # 0x81          UNDEFINED\n    8218,   # 0x82  0x201A  SINGLE LOW-9 QUOTATION MARK\n    402,    # 0x83  0x0192  LATIN SMALL LETTER F WITH HOOK\n    8222,   # 0x84  0x201E  DOUBLE LOW-9 QUOTATION MARK\n    8230,   # 0x85  0x2026  HORIZONTAL ELLIPSIS\n    8224,   # 0x86  0x2020  DAGGER\n    8225,   # 0x87  0x2021  DOUBLE DAGGER\n    710,    # 0x88  0x02C6  MODIFIER LETTER CIRCUMFLEX ACCENT\n    8240,   # 0x89  0x2030  PER MILLE SIGN\n    352,    # 0x8A  0x0160  LATIN CAPITAL LETTER S WITH CARON\n    8249,   # 0x8B  0x2039  SINGLE LEFT-POINTING ANGLE QUOTATION MARK\n    338,    # 0x8C  0x0152  LATIN CAPITAL LIGATURE OE\n    65533,  # 0x8D          UNDEFINED\n    381,    # 0x8E  0x017D  LATIN CAPITAL LETTER Z WITH CARON\n    65533,  # 0x8F          UNDEFINED\n    65533,  # 0x90          UNDEFINED\n    8216,   # 0x91  0x2018  LEFT SINGLE QUOTATION MARK\n    8217,   # 0x92  0x2019  RIGHT SINGLE QUOTATION MARK\n    8220,   # 0x93  0x201C  LEFT DOUBLE QUOTATION MARK\n    8221,   # 0x94  0x201D  RIGHT DOUBLE QUOTATION MARK\n    8226,   # 0x95  0x2022  BULLET\n    8211,   # 0x96  0x2013  EN DASH\n    8212,   # 0x97  0x2014  EM DASH\n    732,    # 0x98  0x02DC  SMALL TILDE\n    8482,   # 0x99  0x2122  TRADE MARK SIGN\n    353,    # 0x9A  0x0161  LATIN SMALL LETTER S WITH CARON\n    8250,   # 0x9B  0x203A  SINGLE RIGHT-POINTING ANGLE QUOTATION MARK\n    339,    # 0x9C  0x0153  LATIN SMALL LIGATURE OE\n    65533,  # 0x9D          UNDEFINED\n    382,    # 0x9E  0x017E  LATIN SMALL LETTER Z WITH CARON\n    376     # 0x9F  0x0178  LATIN CAPITAL LETTER Y WITH DIAERESIS\n)\n\nxmlEntities = frozenset(['lt;', 'gt;', 'amp;', 'apos;', 'quot;'])\n\nentities = {\n    \"AElig\": \"\\xc6\",\n    \"AElig;\": \"\\xc6\",\n    \"AMP\": \"&\",\n    \"AMP;\": \"&\",\n    \"Aacute\": \"\\xc1\",\n    \"Aacute;\": \"\\xc1\",\n    \"Abreve;\": \"\\u0102\",\n    \"Acirc\": \"\\xc2\",\n    \"Acirc;\": \"\\xc2\",\n    \"Acy;\": \"\\u0410\",\n    \"Afr;\": \"\\U0001d504\",\n    \"Agrave\": \"\\xc0\",\n    \"Agrave;\": \"\\xc0\",\n    \"Alpha;\": \"\\u0391\",\n    \"Amacr;\": \"\\u0100\",\n    \"And;\": \"\\u2a53\",\n    \"Aogon;\": \"\\u0104\",\n    \"Aopf;\": \"\\U0001d538\",\n    \"ApplyFunction;\": \"\\u2061\",\n    \"Aring\": \"\\xc5\",\n    \"Aring;\": \"\\xc5\",\n    \"Ascr;\": \"\\U0001d49c\",\n    \"Assign;\": \"\\u2254\",\n    \"Atilde\": \"\\xc3\",\n    \"Atilde;\": \"\\xc3\",\n    \"Auml\": \"\\xc4\",\n    \"Auml;\": \"\\xc4\",\n    \"Backslash;\": \"\\u2216\",\n    \"Barv;\": \"\\u2ae7\",\n    \"Barwed;\": \"\\u2306\",\n    \"Bcy;\": \"\\u0411\",\n    \"Because;\": \"\\u2235\",\n    \"Bernoullis;\": \"\\u212c\",\n    \"Beta;\": \"\\u0392\",\n    \"Bfr;\": \"\\U0001d505\",\n    \"Bopf;\": \"\\U0001d539\",\n    \"Breve;\": \"\\u02d8\",\n    \"Bscr;\": \"\\u212c\",\n    \"Bumpeq;\": \"\\u224e\",\n    \"CHcy;\": \"\\u0427\",\n    \"COPY\": \"\\xa9\",\n    \"COPY;\": \"\\xa9\",\n    \"Cacute;\": \"\\u0106\",\n    \"Cap;\": \"\\u22d2\",\n    \"CapitalDifferentialD;\": \"\\u2145\",\n    \"Cayleys;\": \"\\u212d\",\n    \"Ccaron;\": \"\\u010c\",\n    \"Ccedil\": \"\\xc7\",\n    \"Ccedil;\": \"\\xc7\",\n    \"Ccirc;\": \"\\u0108\",\n    \"Cconint;\": \"\\u2230\",\n    \"Cdot;\": \"\\u010a\",\n    \"Cedilla;\": \"\\xb8\",\n    \"CenterDot;\": \"\\xb7\",\n    \"Cfr;\": \"\\u212d\",\n    \"Chi;\": \"\\u03a7\",\n    \"CircleDot;\": \"\\u2299\",\n    \"CircleMinus;\": \"\\u2296\",\n    \"CirclePlus;\": \"\\u2295\",\n    \"CircleTimes;\": \"\\u2297\",\n    \"ClockwiseContourIntegral;\": \"\\u2232\",\n    \"CloseCurlyDoubleQuote;\": \"\\u201d\",\n    \"CloseCurlyQuote;\": \"\\u2019\",\n    \"Colon;\": \"\\u2237\",\n    \"Colone;\": \"\\u2a74\",\n    \"Congruent;\": \"\\u2261\",\n    \"Conint;\": \"\\u222f\",\n    \"ContourIntegral;\": \"\\u222e\",\n    \"Copf;\": \"\\u2102\",\n    \"Coproduct;\": \"\\u2210\",\n    \"CounterClockwiseContourIntegral;\": \"\\u2233\",\n    \"Cross;\": \"\\u2a2f\",\n    \"Cscr;\": \"\\U0001d49e\",\n    \"Cup;\": \"\\u22d3\",\n    \"CupCap;\": \"\\u224d\",\n    \"DD;\": \"\\u2145\",\n    \"DDotrahd;\": \"\\u2911\",\n    \"DJcy;\": \"\\u0402\",\n    \"DScy;\": \"\\u0405\",\n    \"DZcy;\": \"\\u040f\",\n    \"Dagger;\": \"\\u2021\",\n    \"Darr;\": \"\\u21a1\",\n    \"Dashv;\": \"\\u2ae4\",\n    \"Dcaron;\": \"\\u010e\",\n    \"Dcy;\": \"\\u0414\",\n    \"Del;\": \"\\u2207\",\n    \"Delta;\": \"\\u0394\",\n    \"Dfr;\": \"\\U0001d507\",\n    \"DiacriticalAcute;\": \"\\xb4\",\n    \"DiacriticalDot;\": \"\\u02d9\",\n    \"DiacriticalDoubleAcute;\": \"\\u02dd\",\n    \"DiacriticalGrave;\": \"`\",\n    \"DiacriticalTilde;\": \"\\u02dc\",\n    \"Diamond;\": \"\\u22c4\",\n    \"DifferentialD;\": \"\\u2146\",\n    \"Dopf;\": \"\\U0001d53b\",\n    \"Dot;\": \"\\xa8\",\n    \"DotDot;\": \"\\u20dc\",\n    \"DotEqual;\": \"\\u2250\",\n    \"DoubleContourIntegral;\": \"\\u222f\",\n    \"DoubleDot;\": \"\\xa8\",\n    \"DoubleDownArrow;\": \"\\u21d3\",\n    \"DoubleLeftArrow;\": \"\\u21d0\",\n    \"DoubleLeftRightArrow;\": \"\\u21d4\",\n    \"DoubleLeftTee;\": \"\\u2ae4\",\n    \"DoubleLongLeftArrow;\": \"\\u27f8\",\n    \"DoubleLongLeftRightArrow;\": \"\\u27fa\",\n    \"DoubleLongRightArrow;\": \"\\u27f9\",\n    \"DoubleRightArrow;\": \"\\u21d2\",\n    \"DoubleRightTee;\": \"\\u22a8\",\n    \"DoubleUpArrow;\": \"\\u21d1\",\n    \"DoubleUpDownArrow;\": \"\\u21d5\",\n    \"DoubleVerticalBar;\": \"\\u2225\",\n    \"DownArrow;\": \"\\u2193\",\n    \"DownArrowBar;\": \"\\u2913\",\n    \"DownArrowUpArrow;\": \"\\u21f5\",\n    \"DownBreve;\": \"\\u0311\",\n    \"DownLeftRightVector;\": \"\\u2950\",\n    \"DownLeftTeeVector;\": \"\\u295e\",\n    \"DownLeftVector;\": \"\\u21bd\",\n    \"DownLeftVectorBar;\": \"\\u2956\",\n    \"DownRightTeeVector;\": \"\\u295f\",\n    \"DownRightVector;\": \"\\u21c1\",\n    \"DownRightVectorBar;\": \"\\u2957\",\n    \"DownTee;\": \"\\u22a4\",\n    \"DownTeeArrow;\": \"\\u21a7\",\n    \"Downarrow;\": \"\\u21d3\",\n    \"Dscr;\": \"\\U0001d49f\",\n    \"Dstrok;\": \"\\u0110\",\n    \"ENG;\": \"\\u014a\",\n    \"ETH\": \"\\xd0\",\n    \"ETH;\": \"\\xd0\",\n    \"Eacute\": \"\\xc9\",\n    \"Eacute;\": \"\\xc9\",\n    \"Ecaron;\": \"\\u011a\",\n    \"Ecirc\": \"\\xca\",\n    \"Ecirc;\": \"\\xca\",\n    \"Ecy;\": \"\\u042d\",\n    \"Edot;\": \"\\u0116\",\n    \"Efr;\": \"\\U0001d508\",\n    \"Egrave\": \"\\xc8\",\n    \"Egrave;\": \"\\xc8\",\n    \"Element;\": \"\\u2208\",\n    \"Emacr;\": \"\\u0112\",\n    \"EmptySmallSquare;\": \"\\u25fb\",\n    \"EmptyVerySmallSquare;\": \"\\u25ab\",\n    \"Eogon;\": \"\\u0118\",\n    \"Eopf;\": \"\\U0001d53c\",\n    \"Epsilon;\": \"\\u0395\",\n    \"Equal;\": \"\\u2a75\",\n    \"EqualTilde;\": \"\\u2242\",\n    \"Equilibrium;\": \"\\u21cc\",\n    \"Escr;\": \"\\u2130\",\n    \"Esim;\": \"\\u2a73\",\n    \"Eta;\": \"\\u0397\",\n    \"Euml\": \"\\xcb\",\n    \"Euml;\": \"\\xcb\",\n    \"Exists;\": \"\\u2203\",\n    \"ExponentialE;\": \"\\u2147\",\n    \"Fcy;\": \"\\u0424\",\n    \"Ffr;\": \"\\U0001d509\",\n    \"FilledSmallSquare;\": \"\\u25fc\",\n    \"FilledVerySmallSquare;\": \"\\u25aa\",\n    \"Fopf;\": \"\\U0001d53d\",\n    \"ForAll;\": \"\\u2200\",\n    \"Fouriertrf;\": \"\\u2131\",\n    \"Fscr;\": \"\\u2131\",\n    \"GJcy;\": \"\\u0403\",\n    \"GT\": \">\",\n    \"GT;\": \">\",\n    \"Gamma;\": \"\\u0393\",\n    \"Gammad;\": \"\\u03dc\",\n    \"Gbreve;\": \"\\u011e\",\n    \"Gcedil;\": \"\\u0122\",\n    \"Gcirc;\": \"\\u011c\",\n    \"Gcy;\": \"\\u0413\",\n    \"Gdot;\": \"\\u0120\",\n    \"Gfr;\": \"\\U0001d50a\",\n    \"Gg;\": \"\\u22d9\",\n    \"Gopf;\": \"\\U0001d53e\",\n    \"GreaterEqual;\": \"\\u2265\",\n    \"GreaterEqualLess;\": \"\\u22db\",\n    \"GreaterFullEqual;\": \"\\u2267\",\n    \"GreaterGreater;\": \"\\u2aa2\",\n    \"GreaterLess;\": \"\\u2277\",\n    \"GreaterSlantEqual;\": \"\\u2a7e\",\n    \"GreaterTilde;\": \"\\u2273\",\n    \"Gscr;\": \"\\U0001d4a2\",\n    \"Gt;\": \"\\u226b\",\n    \"HARDcy;\": \"\\u042a\",\n    \"Hacek;\": \"\\u02c7\",\n    \"Hat;\": \"^\",\n    \"Hcirc;\": \"\\u0124\",\n    \"Hfr;\": \"\\u210c\",\n    \"HilbertSpace;\": \"\\u210b\",\n    \"Hopf;\": \"\\u210d\",\n    \"HorizontalLine;\": \"\\u2500\",\n    \"Hscr;\": \"\\u210b\",\n    \"Hstrok;\": \"\\u0126\",\n    \"HumpDownHump;\": \"\\u224e\",\n    \"HumpEqual;\": \"\\u224f\",\n    \"IEcy;\": \"\\u0415\",\n    \"IJlig;\": \"\\u0132\",\n    \"IOcy;\": \"\\u0401\",\n    \"Iacute\": \"\\xcd\",\n    \"Iacute;\": \"\\xcd\",\n    \"Icirc\": \"\\xce\",\n    \"Icirc;\": \"\\xce\",\n    \"Icy;\": \"\\u0418\",\n    \"Idot;\": \"\\u0130\",\n    \"Ifr;\": \"\\u2111\",\n    \"Igrave\": \"\\xcc\",\n    \"Igrave;\": \"\\xcc\",\n    \"Im;\": \"\\u2111\",\n    \"Imacr;\": \"\\u012a\",\n    \"ImaginaryI;\": \"\\u2148\",\n    \"Implies;\": \"\\u21d2\",\n    \"Int;\": \"\\u222c\",\n    \"Integral;\": \"\\u222b\",\n    \"Intersection;\": \"\\u22c2\",\n    \"InvisibleComma;\": \"\\u2063\",\n    \"InvisibleTimes;\": \"\\u2062\",\n    \"Iogon;\": \"\\u012e\",\n    \"Iopf;\": \"\\U0001d540\",\n    \"Iota;\": \"\\u0399\",\n    \"Iscr;\": \"\\u2110\",\n    \"Itilde;\": \"\\u0128\",\n    \"Iukcy;\": \"\\u0406\",\n    \"Iuml\": \"\\xcf\",\n    \"Iuml;\": \"\\xcf\",\n    \"Jcirc;\": \"\\u0134\",\n    \"Jcy;\": \"\\u0419\",\n    \"Jfr;\": \"\\U0001d50d\",\n    \"Jopf;\": \"\\U0001d541\",\n    \"Jscr;\": \"\\U0001d4a5\",\n    \"Jsercy;\": \"\\u0408\",\n    \"Jukcy;\": \"\\u0404\",\n    \"KHcy;\": \"\\u0425\",\n    \"KJcy;\": \"\\u040c\",\n    \"Kappa;\": \"\\u039a\",\n    \"Kcedil;\": \"\\u0136\",\n    \"Kcy;\": \"\\u041a\",\n    \"Kfr;\": \"\\U0001d50e\",\n    \"Kopf;\": \"\\U0001d542\",\n    \"Kscr;\": \"\\U0001d4a6\",\n    \"LJcy;\": \"\\u0409\",\n    \"LT\": \"<\",\n    \"LT;\": \"<\",\n    \"Lacute;\": \"\\u0139\",\n    \"Lambda;\": \"\\u039b\",\n    \"Lang;\": \"\\u27ea\",\n    \"Laplacetrf;\": \"\\u2112\",\n    \"Larr;\": \"\\u219e\",\n    \"Lcaron;\": \"\\u013d\",\n    \"Lcedil;\": \"\\u013b\",\n    \"Lcy;\": \"\\u041b\",\n    \"LeftAngleBracket;\": \"\\u27e8\",\n    \"LeftArrow;\": \"\\u2190\",\n    \"LeftArrowBar;\": \"\\u21e4\",\n    \"LeftArrowRightArrow;\": \"\\u21c6\",\n    \"LeftCeiling;\": \"\\u2308\",\n    \"LeftDoubleBracket;\": \"\\u27e6\",\n    \"LeftDownTeeVector;\": \"\\u2961\",\n    \"LeftDownVector;\": \"\\u21c3\",\n    \"LeftDownVectorBar;\": \"\\u2959\",\n    \"LeftFloor;\": \"\\u230a\",\n    \"LeftRightArrow;\": \"\\u2194\",\n    \"LeftRightVector;\": \"\\u294e\",\n    \"LeftTee;\": \"\\u22a3\",\n    \"LeftTeeArrow;\": \"\\u21a4\",\n    \"LeftTeeVector;\": \"\\u295a\",\n    \"LeftTriangle;\": \"\\u22b2\",\n    \"LeftTriangleBar;\": \"\\u29cf\",\n    \"LeftTriangleEqual;\": \"\\u22b4\",\n    \"LeftUpDownVector;\": \"\\u2951\",\n    \"LeftUpTeeVector;\": \"\\u2960\",\n    \"LeftUpVector;\": \"\\u21bf\",\n    \"LeftUpVectorBar;\": \"\\u2958\",\n    \"LeftVector;\": \"\\u21bc\",\n    \"LeftVectorBar;\": \"\\u2952\",\n    \"Leftarrow;\": \"\\u21d0\",\n    \"Leftrightarrow;\": \"\\u21d4\",\n    \"LessEqualGreater;\": \"\\u22da\",\n    \"LessFullEqual;\": \"\\u2266\",\n    \"LessGreater;\": \"\\u2276\",\n    \"LessLess;\": \"\\u2aa1\",\n    \"LessSlantEqual;\": \"\\u2a7d\",\n    \"LessTilde;\": \"\\u2272\",\n    \"Lfr;\": \"\\U0001d50f\",\n    \"Ll;\": \"\\u22d8\",\n    \"Lleftarrow;\": \"\\u21da\",\n    \"Lmidot;\": \"\\u013f\",\n    \"LongLeftArrow;\": \"\\u27f5\",\n    \"LongLeftRightArrow;\": \"\\u27f7\",\n    \"LongRightArrow;\": \"\\u27f6\",\n    \"Longleftarrow;\": \"\\u27f8\",\n    \"Longleftrightarrow;\": \"\\u27fa\",\n    \"Longrightarrow;\": \"\\u27f9\",\n    \"Lopf;\": \"\\U0001d543\",\n    \"LowerLeftArrow;\": \"\\u2199\",\n    \"LowerRightArrow;\": \"\\u2198\",\n    \"Lscr;\": \"\\u2112\",\n    \"Lsh;\": \"\\u21b0\",\n    \"Lstrok;\": \"\\u0141\",\n    \"Lt;\": \"\\u226a\",\n    \"Map;\": \"\\u2905\",\n    \"Mcy;\": \"\\u041c\",\n    \"MediumSpace;\": \"\\u205f\",\n    \"Mellintrf;\": \"\\u2133\",\n    \"Mfr;\": \"\\U0001d510\",\n    \"MinusPlus;\": \"\\u2213\",\n    \"Mopf;\": \"\\U0001d544\",\n    \"Mscr;\": \"\\u2133\",\n    \"Mu;\": \"\\u039c\",\n    \"NJcy;\": \"\\u040a\",\n    \"Nacute;\": \"\\u0143\",\n    \"Ncaron;\": \"\\u0147\",\n    \"Ncedil;\": \"\\u0145\",\n    \"Ncy;\": \"\\u041d\",\n    \"NegativeMediumSpace;\": \"\\u200b\",\n    \"NegativeThickSpace;\": \"\\u200b\",\n    \"NegativeThinSpace;\": \"\\u200b\",\n    \"NegativeVeryThinSpace;\": \"\\u200b\",\n    \"NestedGreaterGreater;\": \"\\u226b\",\n    \"NestedLessLess;\": \"\\u226a\",\n    \"NewLine;\": \"\\n\",\n    \"Nfr;\": \"\\U0001d511\",\n    \"NoBreak;\": \"\\u2060\",\n    \"NonBreakingSpace;\": \"\\xa0\",\n    \"Nopf;\": \"\\u2115\",\n    \"Not;\": \"\\u2aec\",\n    \"NotCongruent;\": \"\\u2262\",\n    \"NotCupCap;\": \"\\u226d\",\n    \"NotDoubleVerticalBar;\": \"\\u2226\",\n    \"NotElement;\": \"\\u2209\",\n    \"NotEqual;\": \"\\u2260\",\n    \"NotEqualTilde;\": \"\\u2242\\u0338\",\n    \"NotExists;\": \"\\u2204\",\n    \"NotGreater;\": \"\\u226f\",\n    \"NotGreaterEqual;\": \"\\u2271\",\n    \"NotGreaterFullEqual;\": \"\\u2267\\u0338\",\n    \"NotGreaterGreater;\": \"\\u226b\\u0338\",\n    \"NotGreaterLess;\": \"\\u2279\",\n    \"NotGreaterSlantEqual;\": \"\\u2a7e\\u0338\",\n    \"NotGreaterTilde;\": \"\\u2275\",\n    \"NotHumpDownHump;\": \"\\u224e\\u0338\",\n    \"NotHumpEqual;\": \"\\u224f\\u0338\",\n    \"NotLeftTriangle;\": \"\\u22ea\",\n    \"NotLeftTriangleBar;\": \"\\u29cf\\u0338\",\n    \"NotLeftTriangleEqual;\": \"\\u22ec\",\n    \"NotLess;\": \"\\u226e\",\n    \"NotLessEqual;\": \"\\u2270\",\n    \"NotLessGreater;\": \"\\u2278\",\n    \"NotLessLess;\": \"\\u226a\\u0338\",\n    \"NotLessSlantEqual;\": \"\\u2a7d\\u0338\",\n    \"NotLessTilde;\": \"\\u2274\",\n    \"NotNestedGreaterGreater;\": \"\\u2aa2\\u0338\",\n    \"NotNestedLessLess;\": \"\\u2aa1\\u0338\",\n    \"NotPrecedes;\": \"\\u2280\",\n    \"NotPrecedesEqual;\": \"\\u2aaf\\u0338\",\n    \"NotPrecedesSlantEqual;\": \"\\u22e0\",\n    \"NotReverseElement;\": \"\\u220c\",\n    \"NotRightTriangle;\": \"\\u22eb\",\n    \"NotRightTriangleBar;\": \"\\u29d0\\u0338\",\n    \"NotRightTriangleEqual;\": \"\\u22ed\",\n    \"NotSquareSubset;\": \"\\u228f\\u0338\",\n    \"NotSquareSubsetEqual;\": \"\\u22e2\",\n    \"NotSquareSuperset;\": \"\\u2290\\u0338\",\n    \"NotSquareSupersetEqual;\": \"\\u22e3\",\n    \"NotSubset;\": \"\\u2282\\u20d2\",\n    \"NotSubsetEqual;\": \"\\u2288\",\n    \"NotSucceeds;\": \"\\u2281\",\n    \"NotSucceedsEqual;\": \"\\u2ab0\\u0338\",\n    \"NotSucceedsSlantEqual;\": \"\\u22e1\",\n    \"NotSucceedsTilde;\": \"\\u227f\\u0338\",\n    \"NotSuperset;\": \"\\u2283\\u20d2\",\n    \"NotSupersetEqual;\": \"\\u2289\",\n    \"NotTilde;\": \"\\u2241\",\n    \"NotTildeEqual;\": \"\\u2244\",\n    \"NotTildeFullEqual;\": \"\\u2247\",\n    \"NotTildeTilde;\": \"\\u2249\",\n    \"NotVerticalBar;\": \"\\u2224\",\n    \"Nscr;\": \"\\U0001d4a9\",\n    \"Ntilde\": \"\\xd1\",\n    \"Ntilde;\": \"\\xd1\",\n    \"Nu;\": \"\\u039d\",\n    \"OElig;\": \"\\u0152\",\n    \"Oacute\": \"\\xd3\",\n    \"Oacute;\": \"\\xd3\",\n    \"Ocirc\": \"\\xd4\",\n    \"Ocirc;\": \"\\xd4\",\n    \"Ocy;\": \"\\u041e\",\n    \"Odblac;\": \"\\u0150\",\n    \"Ofr;\": \"\\U0001d512\",\n    \"Ograve\": \"\\xd2\",\n    \"Ograve;\": \"\\xd2\",\n    \"Omacr;\": \"\\u014c\",\n    \"Omega;\": \"\\u03a9\",\n    \"Omicron;\": \"\\u039f\",\n    \"Oopf;\": \"\\U0001d546\",\n    \"OpenCurlyDoubleQuote;\": \"\\u201c\",\n    \"OpenCurlyQuote;\": \"\\u2018\",\n    \"Or;\": \"\\u2a54\",\n    \"Oscr;\": \"\\U0001d4aa\",\n    \"Oslash\": \"\\xd8\",\n    \"Oslash;\": \"\\xd8\",\n    \"Otilde\": \"\\xd5\",\n    \"Otilde;\": \"\\xd5\",\n    \"Otimes;\": \"\\u2a37\",\n    \"Ouml\": \"\\xd6\",\n    \"Ouml;\": \"\\xd6\",\n    \"OverBar;\": \"\\u203e\",\n    \"OverBrace;\": \"\\u23de\",\n    \"OverBracket;\": \"\\u23b4\",\n    \"OverParenthesis;\": \"\\u23dc\",\n    \"PartialD;\": \"\\u2202\",\n    \"Pcy;\": \"\\u041f\",\n    \"Pfr;\": \"\\U0001d513\",\n    \"Phi;\": \"\\u03a6\",\n    \"Pi;\": \"\\u03a0\",\n    \"PlusMinus;\": \"\\xb1\",\n    \"Poincareplane;\": \"\\u210c\",\n    \"Popf;\": \"\\u2119\",\n    \"Pr;\": \"\\u2abb\",\n    \"Precedes;\": \"\\u227a\",\n    \"PrecedesEqual;\": \"\\u2aaf\",\n    \"PrecedesSlantEqual;\": \"\\u227c\",\n    \"PrecedesTilde;\": \"\\u227e\",\n    \"Prime;\": \"\\u2033\",\n    \"Product;\": \"\\u220f\",\n    \"Proportion;\": \"\\u2237\",\n    \"Proportional;\": \"\\u221d\",\n    \"Pscr;\": \"\\U0001d4ab\",\n    \"Psi;\": \"\\u03a8\",\n    \"QUOT\": \"\\\"\",\n    \"QUOT;\": \"\\\"\",\n    \"Qfr;\": \"\\U0001d514\",\n    \"Qopf;\": \"\\u211a\",\n    \"Qscr;\": \"\\U0001d4ac\",\n    \"RBarr;\": \"\\u2910\",\n    \"REG\": \"\\xae\",\n    \"REG;\": \"\\xae\",\n    \"Racute;\": \"\\u0154\",\n    \"Rang;\": \"\\u27eb\",\n    \"Rarr;\": \"\\u21a0\",\n    \"Rarrtl;\": \"\\u2916\",\n    \"Rcaron;\": \"\\u0158\",\n    \"Rcedil;\": \"\\u0156\",\n    \"Rcy;\": \"\\u0420\",\n    \"Re;\": \"\\u211c\",\n    \"ReverseElement;\": \"\\u220b\",\n    \"ReverseEquilibrium;\": \"\\u21cb\",\n    \"ReverseUpEquilibrium;\": \"\\u296f\",\n    \"Rfr;\": \"\\u211c\",\n    \"Rho;\": \"\\u03a1\",\n    \"RightAngleBracket;\": \"\\u27e9\",\n    \"RightArrow;\": \"\\u2192\",\n    \"RightArrowBar;\": \"\\u21e5\",\n    \"RightArrowLeftArrow;\": \"\\u21c4\",\n    \"RightCeiling;\": \"\\u2309\",\n    \"RightDoubleBracket;\": \"\\u27e7\",\n    \"RightDownTeeVector;\": \"\\u295d\",\n    \"RightDownVector;\": \"\\u21c2\",\n    \"RightDownVectorBar;\": \"\\u2955\",\n    \"RightFloor;\": \"\\u230b\",\n    \"RightTee;\": \"\\u22a2\",\n    \"RightTeeArrow;\": \"\\u21a6\",\n    \"RightTeeVector;\": \"\\u295b\",\n    \"RightTriangle;\": \"\\u22b3\",\n    \"RightTriangleBar;\": \"\\u29d0\",\n    \"RightTriangleEqual;\": \"\\u22b5\",\n    \"RightUpDownVector;\": \"\\u294f\",\n    \"RightUpTeeVector;\": \"\\u295c\",\n    \"RightUpVector;\": \"\\u21be\",\n    \"RightUpVectorBar;\": \"\\u2954\",\n    \"RightVector;\": \"\\u21c0\",\n    \"RightVectorBar;\": \"\\u2953\",\n    \"Rightarrow;\": \"\\u21d2\",\n    \"Ropf;\": \"\\u211d\",\n    \"RoundImplies;\": \"\\u2970\",\n    \"Rrightarrow;\": \"\\u21db\",\n    \"Rscr;\": \"\\u211b\",\n    \"Rsh;\": \"\\u21b1\",\n    \"RuleDelayed;\": \"\\u29f4\",\n    \"SHCHcy;\": \"\\u0429\",\n    \"SHcy;\": \"\\u0428\",\n    \"SOFTcy;\": \"\\u042c\",\n    \"Sacute;\": \"\\u015a\",\n    \"Sc;\": \"\\u2abc\",\n    \"Scaron;\": \"\\u0160\",\n    \"Scedil;\": \"\\u015e\",\n    \"Scirc;\": \"\\u015c\",\n    \"Scy;\": \"\\u0421\",\n    \"Sfr;\": \"\\U0001d516\",\n    \"ShortDownArrow;\": \"\\u2193\",\n    \"ShortLeftArrow;\": \"\\u2190\",\n    \"ShortRightArrow;\": \"\\u2192\",\n    \"ShortUpArrow;\": \"\\u2191\",\n    \"Sigma;\": \"\\u03a3\",\n    \"SmallCircle;\": \"\\u2218\",\n    \"Sopf;\": \"\\U0001d54a\",\n    \"Sqrt;\": \"\\u221a\",\n    \"Square;\": \"\\u25a1\",\n    \"SquareIntersection;\": \"\\u2293\",\n    \"SquareSubset;\": \"\\u228f\",\n    \"SquareSubsetEqual;\": \"\\u2291\",\n    \"SquareSuperset;\": \"\\u2290\",\n    \"SquareSupersetEqual;\": \"\\u2292\",\n    \"SquareUnion;\": \"\\u2294\",\n    \"Sscr;\": \"\\U0001d4ae\",\n    \"Star;\": \"\\u22c6\",\n    \"Sub;\": \"\\u22d0\",\n    \"Subset;\": \"\\u22d0\",\n    \"SubsetEqual;\": \"\\u2286\",\n    \"Succeeds;\": \"\\u227b\",\n    \"SucceedsEqual;\": \"\\u2ab0\",\n    \"SucceedsSlantEqual;\": \"\\u227d\",\n    \"SucceedsTilde;\": \"\\u227f\",\n    \"SuchThat;\": \"\\u220b\",\n    \"Sum;\": \"\\u2211\",\n    \"Sup;\": \"\\u22d1\",\n    \"Superset;\": \"\\u2283\",\n    \"SupersetEqual;\": \"\\u2287\",\n    \"Supset;\": \"\\u22d1\",\n    \"THORN\": \"\\xde\",\n    \"THORN;\": \"\\xde\",\n    \"TRADE;\": \"\\u2122\",\n    \"TSHcy;\": \"\\u040b\",\n    \"TScy;\": \"\\u0426\",\n    \"Tab;\": \"\\t\",\n    \"Tau;\": \"\\u03a4\",\n    \"Tcaron;\": \"\\u0164\",\n    \"Tcedil;\": \"\\u0162\",\n    \"Tcy;\": \"\\u0422\",\n    \"Tfr;\": \"\\U0001d517\",\n    \"Therefore;\": \"\\u2234\",\n    \"Theta;\": \"\\u0398\",\n    \"ThickSpace;\": \"\\u205f\\u200a\",\n    \"ThinSpace;\": \"\\u2009\",\n    \"Tilde;\": \"\\u223c\",\n    \"TildeEqual;\": \"\\u2243\",\n    \"TildeFullEqual;\": \"\\u2245\",\n    \"TildeTilde;\": \"\\u2248\",\n    \"Topf;\": \"\\U0001d54b\",\n    \"TripleDot;\": \"\\u20db\",\n    \"Tscr;\": \"\\U0001d4af\",\n    \"Tstrok;\": \"\\u0166\",\n    \"Uacute\": \"\\xda\",\n    \"Uacute;\": \"\\xda\",\n    \"Uarr;\": \"\\u219f\",\n    \"Uarrocir;\": \"\\u2949\",\n    \"Ubrcy;\": \"\\u040e\",\n    \"Ubreve;\": \"\\u016c\",\n    \"Ucirc\": \"\\xdb\",\n    \"Ucirc;\": \"\\xdb\",\n    \"Ucy;\": \"\\u0423\",\n    \"Udblac;\": \"\\u0170\",\n    \"Ufr;\": \"\\U0001d518\",\n    \"Ugrave\": \"\\xd9\",\n    \"Ugrave;\": \"\\xd9\",\n    \"Umacr;\": \"\\u016a\",\n    \"UnderBar;\": \"_\",\n    \"UnderBrace;\": \"\\u23df\",\n    \"UnderBracket;\": \"\\u23b5\",\n    \"UnderParenthesis;\": \"\\u23dd\",\n    \"Union;\": \"\\u22c3\",\n    \"UnionPlus;\": \"\\u228e\",\n    \"Uogon;\": \"\\u0172\",\n    \"Uopf;\": \"\\U0001d54c\",\n    \"UpArrow;\": \"\\u2191\",\n    \"UpArrowBar;\": \"\\u2912\",\n    \"UpArrowDownArrow;\": \"\\u21c5\",\n    \"UpDownArrow;\": \"\\u2195\",\n    \"UpEquilibrium;\": \"\\u296e\",\n    \"UpTee;\": \"\\u22a5\",\n    \"UpTeeArrow;\": \"\\u21a5\",\n    \"Uparrow;\": \"\\u21d1\",\n    \"Updownarrow;\": \"\\u21d5\",\n    \"UpperLeftArrow;\": \"\\u2196\",\n    \"UpperRightArrow;\": \"\\u2197\",\n    \"Upsi;\": \"\\u03d2\",\n    \"Upsilon;\": \"\\u03a5\",\n    \"Uring;\": \"\\u016e\",\n    \"Uscr;\": \"\\U0001d4b0\",\n    \"Utilde;\": \"\\u0168\",\n    \"Uuml\": \"\\xdc\",\n    \"Uuml;\": \"\\xdc\",\n    \"VDash;\": \"\\u22ab\",\n    \"Vbar;\": \"\\u2aeb\",\n    \"Vcy;\": \"\\u0412\",\n    \"Vdash;\": \"\\u22a9\",\n    \"Vdashl;\": \"\\u2ae6\",\n    \"Vee;\": \"\\u22c1\",\n    \"Verbar;\": \"\\u2016\",\n    \"Vert;\": \"\\u2016\",\n    \"VerticalBar;\": \"\\u2223\",\n    \"VerticalLine;\": \"|\",\n    \"VerticalSeparator;\": \"\\u2758\",\n    \"VerticalTilde;\": \"\\u2240\",\n    \"VeryThinSpace;\": \"\\u200a\",\n    \"Vfr;\": \"\\U0001d519\",\n    \"Vopf;\": \"\\U0001d54d\",\n    \"Vscr;\": \"\\U0001d4b1\",\n    \"Vvdash;\": \"\\u22aa\",\n    \"Wcirc;\": \"\\u0174\",\n    \"Wedge;\": \"\\u22c0\",\n    \"Wfr;\": \"\\U0001d51a\",\n    \"Wopf;\": \"\\U0001d54e\",\n    \"Wscr;\": \"\\U0001d4b2\",\n    \"Xfr;\": \"\\U0001d51b\",\n    \"Xi;\": \"\\u039e\",\n    \"Xopf;\": \"\\U0001d54f\",\n    \"Xscr;\": \"\\U0001d4b3\",\n    \"YAcy;\": \"\\u042f\",\n    \"YIcy;\": \"\\u0407\",\n    \"YUcy;\": \"\\u042e\",\n    \"Yacute\": \"\\xdd\",\n    \"Yacute;\": \"\\xdd\",\n    \"Ycirc;\": \"\\u0176\",\n    \"Ycy;\": \"\\u042b\",\n    \"Yfr;\": \"\\U0001d51c\",\n    \"Yopf;\": \"\\U0001d550\",\n    \"Yscr;\": \"\\U0001d4b4\",\n    \"Yuml;\": \"\\u0178\",\n    \"ZHcy;\": \"\\u0416\",\n    \"Zacute;\": \"\\u0179\",\n    \"Zcaron;\": \"\\u017d\",\n    \"Zcy;\": \"\\u0417\",\n    \"Zdot;\": \"\\u017b\",\n    \"ZeroWidthSpace;\": \"\\u200b\",\n    \"Zeta;\": \"\\u0396\",\n    \"Zfr;\": \"\\u2128\",\n    \"Zopf;\": \"\\u2124\",\n    \"Zscr;\": \"\\U0001d4b5\",\n    \"aacute\": \"\\xe1\",\n    \"aacute;\": \"\\xe1\",\n    \"abreve;\": \"\\u0103\",\n    \"ac;\": \"\\u223e\",\n    \"acE;\": \"\\u223e\\u0333\",\n    \"acd;\": \"\\u223f\",\n    \"acirc\": \"\\xe2\",\n    \"acirc;\": \"\\xe2\",\n    \"acute\": \"\\xb4\",\n    \"acute;\": \"\\xb4\",\n    \"acy;\": \"\\u0430\",\n    \"aelig\": \"\\xe6\",\n    \"aelig;\": \"\\xe6\",\n    \"af;\": \"\\u2061\",\n    \"afr;\": \"\\U0001d51e\",\n    \"agrave\": \"\\xe0\",\n    \"agrave;\": \"\\xe0\",\n    \"alefsym;\": \"\\u2135\",\n    \"aleph;\": \"\\u2135\",\n    \"alpha;\": \"\\u03b1\",\n    \"amacr;\": \"\\u0101\",\n    \"amalg;\": \"\\u2a3f\",\n    \"amp\": \"&\",\n    \"amp;\": \"&\",\n    \"and;\": \"\\u2227\",\n    \"andand;\": \"\\u2a55\",\n    \"andd;\": \"\\u2a5c\",\n    \"andslope;\": \"\\u2a58\",\n    \"andv;\": \"\\u2a5a\",\n    \"ang;\": \"\\u2220\",\n    \"ange;\": \"\\u29a4\",\n    \"angle;\": \"\\u2220\",\n    \"angmsd;\": \"\\u2221\",\n    \"angmsdaa;\": \"\\u29a8\",\n    \"angmsdab;\": \"\\u29a9\",\n    \"angmsdac;\": \"\\u29aa\",\n    \"angmsdad;\": \"\\u29ab\",\n    \"angmsdae;\": \"\\u29ac\",\n    \"angmsdaf;\": \"\\u29ad\",\n    \"angmsdag;\": \"\\u29ae\",\n    \"angmsdah;\": \"\\u29af\",\n    \"angrt;\": \"\\u221f\",\n    \"angrtvb;\": \"\\u22be\",\n    \"angrtvbd;\": \"\\u299d\",\n    \"angsph;\": \"\\u2222\",\n    \"angst;\": \"\\xc5\",\n    \"angzarr;\": \"\\u237c\",\n    \"aogon;\": \"\\u0105\",\n    \"aopf;\": \"\\U0001d552\",\n    \"ap;\": \"\\u2248\",\n    \"apE;\": \"\\u2a70\",\n    \"apacir;\": \"\\u2a6f\",\n    \"ape;\": \"\\u224a\",\n    \"apid;\": \"\\u224b\",\n    \"apos;\": \"'\",\n    \"approx;\": \"\\u2248\",\n    \"approxeq;\": \"\\u224a\",\n    \"aring\": \"\\xe5\",\n    \"aring;\": \"\\xe5\",\n    \"ascr;\": \"\\U0001d4b6\",\n    \"ast;\": \"*\",\n    \"asymp;\": \"\\u2248\",\n    \"asympeq;\": \"\\u224d\",\n    \"atilde\": \"\\xe3\",\n    \"atilde;\": \"\\xe3\",\n    \"auml\": \"\\xe4\",\n    \"auml;\": \"\\xe4\",\n    \"awconint;\": \"\\u2233\",\n    \"awint;\": \"\\u2a11\",\n    \"bNot;\": \"\\u2aed\",\n    \"backcong;\": \"\\u224c\",\n    \"backepsilon;\": \"\\u03f6\",\n    \"backprime;\": \"\\u2035\",\n    \"backsim;\": \"\\u223d\",\n    \"backsimeq;\": \"\\u22cd\",\n    \"barvee;\": \"\\u22bd\",\n    \"barwed;\": \"\\u2305\",\n    \"barwedge;\": \"\\u2305\",\n    \"bbrk;\": \"\\u23b5\",\n    \"bbrktbrk;\": \"\\u23b6\",\n    \"bcong;\": \"\\u224c\",\n    \"bcy;\": \"\\u0431\",\n    \"bdquo;\": \"\\u201e\",\n    \"becaus;\": \"\\u2235\",\n    \"because;\": \"\\u2235\",\n    \"bemptyv;\": \"\\u29b0\",\n    \"bepsi;\": \"\\u03f6\",\n    \"bernou;\": \"\\u212c\",\n    \"beta;\": \"\\u03b2\",\n    \"beth;\": \"\\u2136\",\n    \"between;\": \"\\u226c\",\n    \"bfr;\": \"\\U0001d51f\",\n    \"bigcap;\": \"\\u22c2\",\n    \"bigcirc;\": \"\\u25ef\",\n    \"bigcup;\": \"\\u22c3\",\n    \"bigodot;\": \"\\u2a00\",\n    \"bigoplus;\": \"\\u2a01\",\n    \"bigotimes;\": \"\\u2a02\",\n    \"bigsqcup;\": \"\\u2a06\",\n    \"bigstar;\": \"\\u2605\",\n    \"bigtriangledown;\": \"\\u25bd\",\n    \"bigtriangleup;\": \"\\u25b3\",\n    \"biguplus;\": \"\\u2a04\",\n    \"bigvee;\": \"\\u22c1\",\n    \"bigwedge;\": \"\\u22c0\",\n    \"bkarow;\": \"\\u290d\",\n    \"blacklozenge;\": \"\\u29eb\",\n    \"blacksquare;\": \"\\u25aa\",\n    \"blacktriangle;\": \"\\u25b4\",\n    \"blacktriangledown;\": \"\\u25be\",\n    \"blacktriangleleft;\": \"\\u25c2\",\n    \"blacktriangleright;\": \"\\u25b8\",\n    \"blank;\": \"\\u2423\",\n    \"blk12;\": \"\\u2592\",\n    \"blk14;\": \"\\u2591\",\n    \"blk34;\": \"\\u2593\",\n    \"block;\": \"\\u2588\",\n    \"bne;\": \"=\\u20e5\",\n    \"bnequiv;\": \"\\u2261\\u20e5\",\n    \"bnot;\": \"\\u2310\",\n    \"bopf;\": \"\\U0001d553\",\n    \"bot;\": \"\\u22a5\",\n    \"bottom;\": \"\\u22a5\",\n    \"bowtie;\": \"\\u22c8\",\n    \"boxDL;\": \"\\u2557\",\n    \"boxDR;\": \"\\u2554\",\n    \"boxDl;\": \"\\u2556\",\n    \"boxDr;\": \"\\u2553\",\n    \"boxH;\": \"\\u2550\",\n    \"boxHD;\": \"\\u2566\",\n    \"boxHU;\": \"\\u2569\",\n    \"boxHd;\": \"\\u2564\",\n    \"boxHu;\": \"\\u2567\",\n    \"boxUL;\": \"\\u255d\",\n    \"boxUR;\": \"\\u255a\",\n    \"boxUl;\": \"\\u255c\",\n    \"boxUr;\": \"\\u2559\",\n    \"boxV;\": \"\\u2551\",\n    \"boxVH;\": \"\\u256c\",\n    \"boxVL;\": \"\\u2563\",\n    \"boxVR;\": \"\\u2560\",\n    \"boxVh;\": \"\\u256b\",\n    \"boxVl;\": \"\\u2562\",\n    \"boxVr;\": \"\\u255f\",\n    \"boxbox;\": \"\\u29c9\",\n    \"boxdL;\": \"\\u2555\",\n    \"boxdR;\": \"\\u2552\",\n    \"boxdl;\": \"\\u2510\",\n    \"boxdr;\": \"\\u250c\",\n    \"boxh;\": \"\\u2500\",\n    \"boxhD;\": \"\\u2565\",\n    \"boxhU;\": \"\\u2568\",\n    \"boxhd;\": \"\\u252c\",\n    \"boxhu;\": \"\\u2534\",\n    \"boxminus;\": \"\\u229f\",\n    \"boxplus;\": \"\\u229e\",\n    \"boxtimes;\": \"\\u22a0\",\n    \"boxuL;\": \"\\u255b\",\n    \"boxuR;\": \"\\u2558\",\n    \"boxul;\": \"\\u2518\",\n    \"boxur;\": \"\\u2514\",\n    \"boxv;\": \"\\u2502\",\n    \"boxvH;\": \"\\u256a\",\n    \"boxvL;\": \"\\u2561\",\n    \"boxvR;\": \"\\u255e\",\n    \"boxvh;\": \"\\u253c\",\n    \"boxvl;\": \"\\u2524\",\n    \"boxvr;\": \"\\u251c\",\n    \"bprime;\": \"\\u2035\",\n    \"breve;\": \"\\u02d8\",\n    \"brvbar\": \"\\xa6\",\n    \"brvbar;\": \"\\xa6\",\n    \"bscr;\": \"\\U0001d4b7\",\n    \"bsemi;\": \"\\u204f\",\n    \"bsim;\": \"\\u223d\",\n    \"bsime;\": \"\\u22cd\",\n    \"bsol;\": \"\\\\\",\n    \"bsolb;\": \"\\u29c5\",\n    \"bsolhsub;\": \"\\u27c8\",\n    \"bull;\": \"\\u2022\",\n    \"bullet;\": \"\\u2022\",\n    \"bump;\": \"\\u224e\",\n    \"bumpE;\": \"\\u2aae\",\n    \"bumpe;\": \"\\u224f\",\n    \"bumpeq;\": \"\\u224f\",\n    \"cacute;\": \"\\u0107\",\n    \"cap;\": \"\\u2229\",\n    \"capand;\": \"\\u2a44\",\n    \"capbrcup;\": \"\\u2a49\",\n    \"capcap;\": \"\\u2a4b\",\n    \"capcup;\": \"\\u2a47\",\n    \"capdot;\": \"\\u2a40\",\n    \"caps;\": \"\\u2229\\ufe00\",\n    \"caret;\": \"\\u2041\",\n    \"caron;\": \"\\u02c7\",\n    \"ccaps;\": \"\\u2a4d\",\n    \"ccaron;\": \"\\u010d\",\n    \"ccedil\": \"\\xe7\",\n    \"ccedil;\": \"\\xe7\",\n    \"ccirc;\": \"\\u0109\",\n    \"ccups;\": \"\\u2a4c\",\n    \"ccupssm;\": \"\\u2a50\",\n    \"cdot;\": \"\\u010b\",\n    \"cedil\": \"\\xb8\",\n    \"cedil;\": \"\\xb8\",\n    \"cemptyv;\": \"\\u29b2\",\n    \"cent\": \"\\xa2\",\n    \"cent;\": \"\\xa2\",\n    \"centerdot;\": \"\\xb7\",\n    \"cfr;\": \"\\U0001d520\",\n    \"chcy;\": \"\\u0447\",\n    \"check;\": \"\\u2713\",\n    \"checkmark;\": \"\\u2713\",\n    \"chi;\": \"\\u03c7\",\n    \"cir;\": \"\\u25cb\",\n    \"cirE;\": \"\\u29c3\",\n    \"circ;\": \"\\u02c6\",\n    \"circeq;\": \"\\u2257\",\n    \"circlearrowleft;\": \"\\u21ba\",\n    \"circlearrowright;\": \"\\u21bb\",\n    \"circledR;\": \"\\xae\",\n    \"circledS;\": \"\\u24c8\",\n    \"circledast;\": \"\\u229b\",\n    \"circledcirc;\": \"\\u229a\",\n    \"circleddash;\": \"\\u229d\",\n    \"cire;\": \"\\u2257\",\n    \"cirfnint;\": \"\\u2a10\",\n    \"cirmid;\": \"\\u2aef\",\n    \"cirscir;\": \"\\u29c2\",\n    \"clubs;\": \"\\u2663\",\n    \"clubsuit;\": \"\\u2663\",\n    \"colon;\": \":\",\n    \"colone;\": \"\\u2254\",\n    \"coloneq;\": \"\\u2254\",\n    \"comma;\": \",\",\n    \"commat;\": \"@\",\n    \"comp;\": \"\\u2201\",\n    \"compfn;\": \"\\u2218\",\n    \"complement;\": \"\\u2201\",\n    \"complexes;\": \"\\u2102\",\n    \"cong;\": \"\\u2245\",\n    \"congdot;\": \"\\u2a6d\",\n    \"conint;\": \"\\u222e\",\n    \"copf;\": \"\\U0001d554\",\n    \"coprod;\": \"\\u2210\",\n    \"copy\": \"\\xa9\",\n    \"copy;\": \"\\xa9\",\n    \"copysr;\": \"\\u2117\",\n    \"crarr;\": \"\\u21b5\",\n    \"cross;\": \"\\u2717\",\n    \"cscr;\": \"\\U0001d4b8\",\n    \"csub;\": \"\\u2acf\",\n    \"csube;\": \"\\u2ad1\",\n    \"csup;\": \"\\u2ad0\",\n    \"csupe;\": \"\\u2ad2\",\n    \"ctdot;\": \"\\u22ef\",\n    \"cudarrl;\": \"\\u2938\",\n    \"cudarrr;\": \"\\u2935\",\n    \"cuepr;\": \"\\u22de\",\n    \"cuesc;\": \"\\u22df\",\n    \"cularr;\": \"\\u21b6\",\n    \"cularrp;\": \"\\u293d\",\n    \"cup;\": \"\\u222a\",\n    \"cupbrcap;\": \"\\u2a48\",\n    \"cupcap;\": \"\\u2a46\",\n    \"cupcup;\": \"\\u2a4a\",\n    \"cupdot;\": \"\\u228d\",\n    \"cupor;\": \"\\u2a45\",\n    \"cups;\": \"\\u222a\\ufe00\",\n    \"curarr;\": \"\\u21b7\",\n    \"curarrm;\": \"\\u293c\",\n    \"curlyeqprec;\": \"\\u22de\",\n    \"curlyeqsucc;\": \"\\u22df\",\n    \"curlyvee;\": \"\\u22ce\",\n    \"curlywedge;\": \"\\u22cf\",\n    \"curren\": \"\\xa4\",\n    \"curren;\": \"\\xa4\",\n    \"curvearrowleft;\": \"\\u21b6\",\n    \"curvearrowright;\": \"\\u21b7\",\n    \"cuvee;\": \"\\u22ce\",\n    \"cuwed;\": \"\\u22cf\",\n    \"cwconint;\": \"\\u2232\",\n    \"cwint;\": \"\\u2231\",\n    \"cylcty;\": \"\\u232d\",\n    \"dArr;\": \"\\u21d3\",\n    \"dHar;\": \"\\u2965\",\n    \"dagger;\": \"\\u2020\",\n    \"daleth;\": \"\\u2138\",\n    \"darr;\": \"\\u2193\",\n    \"dash;\": \"\\u2010\",\n    \"dashv;\": \"\\u22a3\",\n    \"dbkarow;\": \"\\u290f\",\n    \"dblac;\": \"\\u02dd\",\n    \"dcaron;\": \"\\u010f\",\n    \"dcy;\": \"\\u0434\",\n    \"dd;\": \"\\u2146\",\n    \"ddagger;\": \"\\u2021\",\n    \"ddarr;\": \"\\u21ca\",\n    \"ddotseq;\": \"\\u2a77\",\n    \"deg\": \"\\xb0\",\n    \"deg;\": \"\\xb0\",\n    \"delta;\": \"\\u03b4\",\n    \"demptyv;\": \"\\u29b1\",\n    \"dfisht;\": \"\\u297f\",\n    \"dfr;\": \"\\U0001d521\",\n    \"dharl;\": \"\\u21c3\",\n    \"dharr;\": \"\\u21c2\",\n    \"diam;\": \"\\u22c4\",\n    \"diamond;\": \"\\u22c4\",\n    \"diamondsuit;\": \"\\u2666\",\n    \"diams;\": \"\\u2666\",\n    \"die;\": \"\\xa8\",\n    \"digamma;\": \"\\u03dd\",\n    \"disin;\": \"\\u22f2\",\n    \"div;\": \"\\xf7\",\n    \"divide\": \"\\xf7\",\n    \"divide;\": \"\\xf7\",\n    \"divideontimes;\": \"\\u22c7\",\n    \"divonx;\": \"\\u22c7\",\n    \"djcy;\": \"\\u0452\",\n    \"dlcorn;\": \"\\u231e\",\n    \"dlcrop;\": \"\\u230d\",\n    \"dollar;\": \"$\",\n    \"dopf;\": \"\\U0001d555\",\n    \"dot;\": \"\\u02d9\",\n    \"doteq;\": \"\\u2250\",\n    \"doteqdot;\": \"\\u2251\",\n    \"dotminus;\": \"\\u2238\",\n    \"dotplus;\": \"\\u2214\",\n    \"dotsquare;\": \"\\u22a1\",\n    \"doublebarwedge;\": \"\\u2306\",\n    \"downarrow;\": \"\\u2193\",\n    \"downdownarrows;\": \"\\u21ca\",\n    \"downharpoonleft;\": \"\\u21c3\",\n    \"downharpoonright;\": \"\\u21c2\",\n    \"drbkarow;\": \"\\u2910\",\n    \"drcorn;\": \"\\u231f\",\n    \"drcrop;\": \"\\u230c\",\n    \"dscr;\": \"\\U0001d4b9\",\n    \"dscy;\": \"\\u0455\",\n    \"dsol;\": \"\\u29f6\",\n    \"dstrok;\": \"\\u0111\",\n    \"dtdot;\": \"\\u22f1\",\n    \"dtri;\": \"\\u25bf\",\n    \"dtrif;\": \"\\u25be\",\n    \"duarr;\": \"\\u21f5\",\n    \"duhar;\": \"\\u296f\",\n    \"dwangle;\": \"\\u29a6\",\n    \"dzcy;\": \"\\u045f\",\n    \"dzigrarr;\": \"\\u27ff\",\n    \"eDDot;\": \"\\u2a77\",\n    \"eDot;\": \"\\u2251\",\n    \"eacute\": \"\\xe9\",\n    \"eacute;\": \"\\xe9\",\n    \"easter;\": \"\\u2a6e\",\n    \"ecaron;\": \"\\u011b\",\n    \"ecir;\": \"\\u2256\",\n    \"ecirc\": \"\\xea\",\n    \"ecirc;\": \"\\xea\",\n    \"ecolon;\": \"\\u2255\",\n    \"ecy;\": \"\\u044d\",\n    \"edot;\": \"\\u0117\",\n    \"ee;\": \"\\u2147\",\n    \"efDot;\": \"\\u2252\",\n    \"efr;\": \"\\U0001d522\",\n    \"eg;\": \"\\u2a9a\",\n    \"egrave\": \"\\xe8\",\n    \"egrave;\": \"\\xe8\",\n    \"egs;\": \"\\u2a96\",\n    \"egsdot;\": \"\\u2a98\",\n    \"el;\": \"\\u2a99\",\n    \"elinters;\": \"\\u23e7\",\n    \"ell;\": \"\\u2113\",\n    \"els;\": \"\\u2a95\",\n    \"elsdot;\": \"\\u2a97\",\n    \"emacr;\": \"\\u0113\",\n    \"empty;\": \"\\u2205\",\n    \"emptyset;\": \"\\u2205\",\n    \"emptyv;\": \"\\u2205\",\n    \"emsp13;\": \"\\u2004\",\n    \"emsp14;\": \"\\u2005\",\n    \"emsp;\": \"\\u2003\",\n    \"eng;\": \"\\u014b\",\n    \"ensp;\": \"\\u2002\",\n    \"eogon;\": \"\\u0119\",\n    \"eopf;\": \"\\U0001d556\",\n    \"epar;\": \"\\u22d5\",\n    \"eparsl;\": \"\\u29e3\",\n    \"eplus;\": \"\\u2a71\",\n    \"epsi;\": \"\\u03b5\",\n    \"epsilon;\": \"\\u03b5\",\n    \"epsiv;\": \"\\u03f5\",\n    \"eqcirc;\": \"\\u2256\",\n    \"eqcolon;\": \"\\u2255\",\n    \"eqsim;\": \"\\u2242\",\n    \"eqslantgtr;\": \"\\u2a96\",\n    \"eqslantless;\": \"\\u2a95\",\n    \"equals;\": \"=\",\n    \"equest;\": \"\\u225f\",\n    \"equiv;\": \"\\u2261\",\n    \"equivDD;\": \"\\u2a78\",\n    \"eqvparsl;\": \"\\u29e5\",\n    \"erDot;\": \"\\u2253\",\n    \"erarr;\": \"\\u2971\",\n    \"escr;\": \"\\u212f\",\n    \"esdot;\": \"\\u2250\",\n    \"esim;\": \"\\u2242\",\n    \"eta;\": \"\\u03b7\",\n    \"eth\": \"\\xf0\",\n    \"eth;\": \"\\xf0\",\n    \"euml\": \"\\xeb\",\n    \"euml;\": \"\\xeb\",\n    \"euro;\": \"\\u20ac\",\n    \"excl;\": \"!\",\n    \"exist;\": \"\\u2203\",\n    \"expectation;\": \"\\u2130\",\n    \"exponentiale;\": \"\\u2147\",\n    \"fallingdotseq;\": \"\\u2252\",\n    \"fcy;\": \"\\u0444\",\n    \"female;\": \"\\u2640\",\n    \"ffilig;\": \"\\ufb03\",\n    \"fflig;\": \"\\ufb00\",\n    \"ffllig;\": \"\\ufb04\",\n    \"ffr;\": \"\\U0001d523\",\n    \"filig;\": \"\\ufb01\",\n    \"fjlig;\": \"fj\",\n    \"flat;\": \"\\u266d\",\n    \"fllig;\": \"\\ufb02\",\n    \"fltns;\": \"\\u25b1\",\n    \"fnof;\": \"\\u0192\",\n    \"fopf;\": \"\\U0001d557\",\n    \"forall;\": \"\\u2200\",\n    \"fork;\": \"\\u22d4\",\n    \"forkv;\": \"\\u2ad9\",\n    \"fpartint;\": \"\\u2a0d\",\n    \"frac12\": \"\\xbd\",\n    \"frac12;\": \"\\xbd\",\n    \"frac13;\": \"\\u2153\",\n    \"frac14\": \"\\xbc\",\n    \"frac14;\": \"\\xbc\",\n    \"frac15;\": \"\\u2155\",\n    \"frac16;\": \"\\u2159\",\n    \"frac18;\": \"\\u215b\",\n    \"frac23;\": \"\\u2154\",\n    \"frac25;\": \"\\u2156\",\n    \"frac34\": \"\\xbe\",\n    \"frac34;\": \"\\xbe\",\n    \"frac35;\": \"\\u2157\",\n    \"frac38;\": \"\\u215c\",\n    \"frac45;\": \"\\u2158\",\n    \"frac56;\": \"\\u215a\",\n    \"frac58;\": \"\\u215d\",\n    \"frac78;\": \"\\u215e\",\n    \"frasl;\": \"\\u2044\",\n    \"frown;\": \"\\u2322\",\n    \"fscr;\": \"\\U0001d4bb\",\n    \"gE;\": \"\\u2267\",\n    \"gEl;\": \"\\u2a8c\",\n    \"gacute;\": \"\\u01f5\",\n    \"gamma;\": \"\\u03b3\",\n    \"gammad;\": \"\\u03dd\",\n    \"gap;\": \"\\u2a86\",\n    \"gbreve;\": \"\\u011f\",\n    \"gcirc;\": \"\\u011d\",\n    \"gcy;\": \"\\u0433\",\n    \"gdot;\": \"\\u0121\",\n    \"ge;\": \"\\u2265\",\n    \"gel;\": \"\\u22db\",\n    \"geq;\": \"\\u2265\",\n    \"geqq;\": \"\\u2267\",\n    \"geqslant;\": \"\\u2a7e\",\n    \"ges;\": \"\\u2a7e\",\n    \"gescc;\": \"\\u2aa9\",\n    \"gesdot;\": \"\\u2a80\",\n    \"gesdoto;\": \"\\u2a82\",\n    \"gesdotol;\": \"\\u2a84\",\n    \"gesl;\": \"\\u22db\\ufe00\",\n    \"gesles;\": \"\\u2a94\",\n    \"gfr;\": \"\\U0001d524\",\n    \"gg;\": \"\\u226b\",\n    \"ggg;\": \"\\u22d9\",\n    \"gimel;\": \"\\u2137\",\n    \"gjcy;\": \"\\u0453\",\n    \"gl;\": \"\\u2277\",\n    \"glE;\": \"\\u2a92\",\n    \"gla;\": \"\\u2aa5\",\n    \"glj;\": \"\\u2aa4\",\n    \"gnE;\": \"\\u2269\",\n    \"gnap;\": \"\\u2a8a\",\n    \"gnapprox;\": \"\\u2a8a\",\n    \"gne;\": \"\\u2a88\",\n    \"gneq;\": \"\\u2a88\",\n    \"gneqq;\": \"\\u2269\",\n    \"gnsim;\": \"\\u22e7\",\n    \"gopf;\": \"\\U0001d558\",\n    \"grave;\": \"`\",\n    \"gscr;\": \"\\u210a\",\n    \"gsim;\": \"\\u2273\",\n    \"gsime;\": \"\\u2a8e\",\n    \"gsiml;\": \"\\u2a90\",\n    \"gt\": \">\",\n    \"gt;\": \">\",\n    \"gtcc;\": \"\\u2aa7\",\n    \"gtcir;\": \"\\u2a7a\",\n    \"gtdot;\": \"\\u22d7\",\n    \"gtlPar;\": \"\\u2995\",\n    \"gtquest;\": \"\\u2a7c\",\n    \"gtrapprox;\": \"\\u2a86\",\n    \"gtrarr;\": \"\\u2978\",\n    \"gtrdot;\": \"\\u22d7\",\n    \"gtreqless;\": \"\\u22db\",\n    \"gtreqqless;\": \"\\u2a8c\",\n    \"gtrless;\": \"\\u2277\",\n    \"gtrsim;\": \"\\u2273\",\n    \"gvertneqq;\": \"\\u2269\\ufe00\",\n    \"gvnE;\": \"\\u2269\\ufe00\",\n    \"hArr;\": \"\\u21d4\",\n    \"hairsp;\": \"\\u200a\",\n    \"half;\": \"\\xbd\",\n    \"hamilt;\": \"\\u210b\",\n    \"hardcy;\": \"\\u044a\",\n    \"harr;\": \"\\u2194\",\n    \"harrcir;\": \"\\u2948\",\n    \"harrw;\": \"\\u21ad\",\n    \"hbar;\": \"\\u210f\",\n    \"hcirc;\": \"\\u0125\",\n    \"hearts;\": \"\\u2665\",\n    \"heartsuit;\": \"\\u2665\",\n    \"hellip;\": \"\\u2026\",\n    \"hercon;\": \"\\u22b9\",\n    \"hfr;\": \"\\U0001d525\",\n    \"hksearow;\": \"\\u2925\",\n    \"hkswarow;\": \"\\u2926\",\n    \"hoarr;\": \"\\u21ff\",\n    \"homtht;\": \"\\u223b\",\n    \"hookleftarrow;\": \"\\u21a9\",\n    \"hookrightarrow;\": \"\\u21aa\",\n    \"hopf;\": \"\\U0001d559\",\n    \"horbar;\": \"\\u2015\",\n    \"hscr;\": \"\\U0001d4bd\",\n    \"hslash;\": \"\\u210f\",\n    \"hstrok;\": \"\\u0127\",\n    \"hybull;\": \"\\u2043\",\n    \"hyphen;\": \"\\u2010\",\n    \"iacute\": \"\\xed\",\n    \"iacute;\": \"\\xed\",\n    \"ic;\": \"\\u2063\",\n    \"icirc\": \"\\xee\",\n    \"icirc;\": \"\\xee\",\n    \"icy;\": \"\\u0438\",\n    \"iecy;\": \"\\u0435\",\n    \"iexcl\": \"\\xa1\",\n    \"iexcl;\": \"\\xa1\",\n    \"iff;\": \"\\u21d4\",\n    \"ifr;\": \"\\U0001d526\",\n    \"igrave\": \"\\xec\",\n    \"igrave;\": \"\\xec\",\n    \"ii;\": \"\\u2148\",\n    \"iiiint;\": \"\\u2a0c\",\n    \"iiint;\": \"\\u222d\",\n    \"iinfin;\": \"\\u29dc\",\n    \"iiota;\": \"\\u2129\",\n    \"ijlig;\": \"\\u0133\",\n    \"imacr;\": \"\\u012b\",\n    \"image;\": \"\\u2111\",\n    \"imagline;\": \"\\u2110\",\n    \"imagpart;\": \"\\u2111\",\n    \"imath;\": \"\\u0131\",\n    \"imof;\": \"\\u22b7\",\n    \"imped;\": \"\\u01b5\",\n    \"in;\": \"\\u2208\",\n    \"incare;\": \"\\u2105\",\n    \"infin;\": \"\\u221e\",\n    \"infintie;\": \"\\u29dd\",\n    \"inodot;\": \"\\u0131\",\n    \"int;\": \"\\u222b\",\n    \"intcal;\": \"\\u22ba\",\n    \"integers;\": \"\\u2124\",\n    \"intercal;\": \"\\u22ba\",\n    \"intlarhk;\": \"\\u2a17\",\n    \"intprod;\": \"\\u2a3c\",\n    \"iocy;\": \"\\u0451\",\n    \"iogon;\": \"\\u012f\",\n    \"iopf;\": \"\\U0001d55a\",\n    \"iota;\": \"\\u03b9\",\n    \"iprod;\": \"\\u2a3c\",\n    \"iquest\": \"\\xbf\",\n    \"iquest;\": \"\\xbf\",\n    \"iscr;\": \"\\U0001d4be\",\n    \"isin;\": \"\\u2208\",\n    \"isinE;\": \"\\u22f9\",\n    \"isindot;\": \"\\u22f5\",\n    \"isins;\": \"\\u22f4\",\n    \"isinsv;\": \"\\u22f3\",\n    \"isinv;\": \"\\u2208\",\n    \"it;\": \"\\u2062\",\n    \"itilde;\": \"\\u0129\",\n    \"iukcy;\": \"\\u0456\",\n    \"iuml\": \"\\xef\",\n    \"iuml;\": \"\\xef\",\n    \"jcirc;\": \"\\u0135\",\n    \"jcy;\": \"\\u0439\",\n    \"jfr;\": \"\\U0001d527\",\n    \"jmath;\": \"\\u0237\",\n    \"jopf;\": \"\\U0001d55b\",\n    \"jscr;\": \"\\U0001d4bf\",\n    \"jsercy;\": \"\\u0458\",\n    \"jukcy;\": \"\\u0454\",\n    \"kappa;\": \"\\u03ba\",\n    \"kappav;\": \"\\u03f0\",\n    \"kcedil;\": \"\\u0137\",\n    \"kcy;\": \"\\u043a\",\n    \"kfr;\": \"\\U0001d528\",\n    \"kgreen;\": \"\\u0138\",\n    \"khcy;\": \"\\u0445\",\n    \"kjcy;\": \"\\u045c\",\n    \"kopf;\": \"\\U0001d55c\",\n    \"kscr;\": \"\\U0001d4c0\",\n    \"lAarr;\": \"\\u21da\",\n    \"lArr;\": \"\\u21d0\",\n    \"lAtail;\": \"\\u291b\",\n    \"lBarr;\": \"\\u290e\",\n    \"lE;\": \"\\u2266\",\n    \"lEg;\": \"\\u2a8b\",\n    \"lHar;\": \"\\u2962\",\n    \"lacute;\": \"\\u013a\",\n    \"laemptyv;\": \"\\u29b4\",\n    \"lagran;\": \"\\u2112\",\n    \"lambda;\": \"\\u03bb\",\n    \"lang;\": \"\\u27e8\",\n    \"langd;\": \"\\u2991\",\n    \"langle;\": \"\\u27e8\",\n    \"lap;\": \"\\u2a85\",\n    \"laquo\": \"\\xab\",\n    \"laquo;\": \"\\xab\",\n    \"larr;\": \"\\u2190\",\n    \"larrb;\": \"\\u21e4\",\n    \"larrbfs;\": \"\\u291f\",\n    \"larrfs;\": \"\\u291d\",\n    \"larrhk;\": \"\\u21a9\",\n    \"larrlp;\": \"\\u21ab\",\n    \"larrpl;\": \"\\u2939\",\n    \"larrsim;\": \"\\u2973\",\n    \"larrtl;\": \"\\u21a2\",\n    \"lat;\": \"\\u2aab\",\n    \"latail;\": \"\\u2919\",\n    \"late;\": \"\\u2aad\",\n    \"lates;\": \"\\u2aad\\ufe00\",\n    \"lbarr;\": \"\\u290c\",\n    \"lbbrk;\": \"\\u2772\",\n    \"lbrace;\": \"{\",\n    \"lbrack;\": \"[\",\n    \"lbrke;\": \"\\u298b\",\n    \"lbrksld;\": \"\\u298f\",\n    \"lbrkslu;\": \"\\u298d\",\n    \"lcaron;\": \"\\u013e\",\n    \"lcedil;\": \"\\u013c\",\n    \"lceil;\": \"\\u2308\",\n    \"lcub;\": \"{\",\n    \"lcy;\": \"\\u043b\",\n    \"ldca;\": \"\\u2936\",\n    \"ldquo;\": \"\\u201c\",\n    \"ldquor;\": \"\\u201e\",\n    \"ldrdhar;\": \"\\u2967\",\n    \"ldrushar;\": \"\\u294b\",\n    \"ldsh;\": \"\\u21b2\",\n    \"le;\": \"\\u2264\",\n    \"leftarrow;\": \"\\u2190\",\n    \"leftarrowtail;\": \"\\u21a2\",\n    \"leftharpoondown;\": \"\\u21bd\",\n    \"leftharpoonup;\": \"\\u21bc\",\n    \"leftleftarrows;\": \"\\u21c7\",\n    \"leftrightarrow;\": \"\\u2194\",\n    \"leftrightarrows;\": \"\\u21c6\",\n    \"leftrightharpoons;\": \"\\u21cb\",\n    \"leftrightsquigarrow;\": \"\\u21ad\",\n    \"leftthreetimes;\": \"\\u22cb\",\n    \"leg;\": \"\\u22da\",\n    \"leq;\": \"\\u2264\",\n    \"leqq;\": \"\\u2266\",\n    \"leqslant;\": \"\\u2a7d\",\n    \"les;\": \"\\u2a7d\",\n    \"lescc;\": \"\\u2aa8\",\n    \"lesdot;\": \"\\u2a7f\",\n    \"lesdoto;\": \"\\u2a81\",\n    \"lesdotor;\": \"\\u2a83\",\n    \"lesg;\": \"\\u22da\\ufe00\",\n    \"lesges;\": \"\\u2a93\",\n    \"lessapprox;\": \"\\u2a85\",\n    \"lessdot;\": \"\\u22d6\",\n    \"lesseqgtr;\": \"\\u22da\",\n    \"lesseqqgtr;\": \"\\u2a8b\",\n    \"lessgtr;\": \"\\u2276\",\n    \"lesssim;\": \"\\u2272\",\n    \"lfisht;\": \"\\u297c\",\n    \"lfloor;\": \"\\u230a\",\n    \"lfr;\": \"\\U0001d529\",\n    \"lg;\": \"\\u2276\",\n    \"lgE;\": \"\\u2a91\",\n    \"lhard;\": \"\\u21bd\",\n    \"lharu;\": \"\\u21bc\",\n    \"lharul;\": \"\\u296a\",\n    \"lhblk;\": \"\\u2584\",\n    \"ljcy;\": \"\\u0459\",\n    \"ll;\": \"\\u226a\",\n    \"llarr;\": \"\\u21c7\",\n    \"llcorner;\": \"\\u231e\",\n    \"llhard;\": \"\\u296b\",\n    \"lltri;\": \"\\u25fa\",\n    \"lmidot;\": \"\\u0140\",\n    \"lmoust;\": \"\\u23b0\",\n    \"lmoustache;\": \"\\u23b0\",\n    \"lnE;\": \"\\u2268\",\n    \"lnap;\": \"\\u2a89\",\n    \"lnapprox;\": \"\\u2a89\",\n    \"lne;\": \"\\u2a87\",\n    \"lneq;\": \"\\u2a87\",\n    \"lneqq;\": \"\\u2268\",\n    \"lnsim;\": \"\\u22e6\",\n    \"loang;\": \"\\u27ec\",\n    \"loarr;\": \"\\u21fd\",\n    \"lobrk;\": \"\\u27e6\",\n    \"longleftarrow;\": \"\\u27f5\",\n    \"longleftrightarrow;\": \"\\u27f7\",\n    \"longmapsto;\": \"\\u27fc\",\n    \"longrightarrow;\": \"\\u27f6\",\n    \"looparrowleft;\": \"\\u21ab\",\n    \"looparrowright;\": \"\\u21ac\",\n    \"lopar;\": \"\\u2985\",\n    \"lopf;\": \"\\U0001d55d\",\n    \"loplus;\": \"\\u2a2d\",\n    \"lotimes;\": \"\\u2a34\",\n    \"lowast;\": \"\\u2217\",\n    \"lowbar;\": \"_\",\n    \"loz;\": \"\\u25ca\",\n    \"lozenge;\": \"\\u25ca\",\n    \"lozf;\": \"\\u29eb\",\n    \"lpar;\": \"(\",\n    \"lparlt;\": \"\\u2993\",\n    \"lrarr;\": \"\\u21c6\",\n    \"lrcorner;\": \"\\u231f\",\n    \"lrhar;\": \"\\u21cb\",\n    \"lrhard;\": \"\\u296d\",\n    \"lrm;\": \"\\u200e\",\n    \"lrtri;\": \"\\u22bf\",\n    \"lsaquo;\": \"\\u2039\",\n    \"lscr;\": \"\\U0001d4c1\",\n    \"lsh;\": \"\\u21b0\",\n    \"lsim;\": \"\\u2272\",\n    \"lsime;\": \"\\u2a8d\",\n    \"lsimg;\": \"\\u2a8f\",\n    \"lsqb;\": \"[\",\n    \"lsquo;\": \"\\u2018\",\n    \"lsquor;\": \"\\u201a\",\n    \"lstrok;\": \"\\u0142\",\n    \"lt\": \"<\",\n    \"lt;\": \"<\",\n    \"ltcc;\": \"\\u2aa6\",\n    \"ltcir;\": \"\\u2a79\",\n    \"ltdot;\": \"\\u22d6\",\n    \"lthree;\": \"\\u22cb\",\n    \"ltimes;\": \"\\u22c9\",\n    \"ltlarr;\": \"\\u2976\",\n    \"ltquest;\": \"\\u2a7b\",\n    \"ltrPar;\": \"\\u2996\",\n    \"ltri;\": \"\\u25c3\",\n    \"ltrie;\": \"\\u22b4\",\n    \"ltrif;\": \"\\u25c2\",\n    \"lurdshar;\": \"\\u294a\",\n    \"luruhar;\": \"\\u2966\",\n    \"lvertneqq;\": \"\\u2268\\ufe00\",\n    \"lvnE;\": \"\\u2268\\ufe00\",\n    \"mDDot;\": \"\\u223a\",\n    \"macr\": \"\\xaf\",\n    \"macr;\": \"\\xaf\",\n    \"male;\": \"\\u2642\",\n    \"malt;\": \"\\u2720\",\n    \"maltese;\": \"\\u2720\",\n    \"map;\": \"\\u21a6\",\n    \"mapsto;\": \"\\u21a6\",\n    \"mapstodown;\": \"\\u21a7\",\n    \"mapstoleft;\": \"\\u21a4\",\n    \"mapstoup;\": \"\\u21a5\",\n    \"marker;\": \"\\u25ae\",\n    \"mcomma;\": \"\\u2a29\",\n    \"mcy;\": \"\\u043c\",\n    \"mdash;\": \"\\u2014\",\n    \"measuredangle;\": \"\\u2221\",\n    \"mfr;\": \"\\U0001d52a\",\n    \"mho;\": \"\\u2127\",\n    \"micro\": \"\\xb5\",\n    \"micro;\": \"\\xb5\",\n    \"mid;\": \"\\u2223\",\n    \"midast;\": \"*\",\n    \"midcir;\": \"\\u2af0\",\n    \"middot\": \"\\xb7\",\n    \"middot;\": \"\\xb7\",\n    \"minus;\": \"\\u2212\",\n    \"minusb;\": \"\\u229f\",\n    \"minusd;\": \"\\u2238\",\n    \"minusdu;\": \"\\u2a2a\",\n    \"mlcp;\": \"\\u2adb\",\n    \"mldr;\": \"\\u2026\",\n    \"mnplus;\": \"\\u2213\",\n    \"models;\": \"\\u22a7\",\n    \"mopf;\": \"\\U0001d55e\",\n    \"mp;\": \"\\u2213\",\n    \"mscr;\": \"\\U0001d4c2\",\n    \"mstpos;\": \"\\u223e\",\n    \"mu;\": \"\\u03bc\",\n    \"multimap;\": \"\\u22b8\",\n    \"mumap;\": \"\\u22b8\",\n    \"nGg;\": \"\\u22d9\\u0338\",\n    \"nGt;\": \"\\u226b\\u20d2\",\n    \"nGtv;\": \"\\u226b\\u0338\",\n    \"nLeftarrow;\": \"\\u21cd\",\n    \"nLeftrightarrow;\": \"\\u21ce\",\n    \"nLl;\": \"\\u22d8\\u0338\",\n    \"nLt;\": \"\\u226a\\u20d2\",\n    \"nLtv;\": \"\\u226a\\u0338\",\n    \"nRightarrow;\": \"\\u21cf\",\n    \"nVDash;\": \"\\u22af\",\n    \"nVdash;\": \"\\u22ae\",\n    \"nabla;\": \"\\u2207\",\n    \"nacute;\": \"\\u0144\",\n    \"nang;\": \"\\u2220\\u20d2\",\n    \"nap;\": \"\\u2249\",\n    \"napE;\": \"\\u2a70\\u0338\",\n    \"napid;\": \"\\u224b\\u0338\",\n    \"napos;\": \"\\u0149\",\n    \"napprox;\": \"\\u2249\",\n    \"natur;\": \"\\u266e\",\n    \"natural;\": \"\\u266e\",\n    \"naturals;\": \"\\u2115\",\n    \"nbsp\": \"\\xa0\",\n    \"nbsp;\": \"\\xa0\",\n    \"nbump;\": \"\\u224e\\u0338\",\n    \"nbumpe;\": \"\\u224f\\u0338\",\n    \"ncap;\": \"\\u2a43\",\n    \"ncaron;\": \"\\u0148\",\n    \"ncedil;\": \"\\u0146\",\n    \"ncong;\": \"\\u2247\",\n    \"ncongdot;\": \"\\u2a6d\\u0338\",\n    \"ncup;\": \"\\u2a42\",\n    \"ncy;\": \"\\u043d\",\n    \"ndash;\": \"\\u2013\",\n    \"ne;\": \"\\u2260\",\n    \"neArr;\": \"\\u21d7\",\n    \"nearhk;\": \"\\u2924\",\n    \"nearr;\": \"\\u2197\",\n    \"nearrow;\": \"\\u2197\",\n    \"nedot;\": \"\\u2250\\u0338\",\n    \"nequiv;\": \"\\u2262\",\n    \"nesear;\": \"\\u2928\",\n    \"nesim;\": \"\\u2242\\u0338\",\n    \"nexist;\": \"\\u2204\",\n    \"nexists;\": \"\\u2204\",\n    \"nfr;\": \"\\U0001d52b\",\n    \"ngE;\": \"\\u2267\\u0338\",\n    \"nge;\": \"\\u2271\",\n    \"ngeq;\": \"\\u2271\",\n    \"ngeqq;\": \"\\u2267\\u0338\",\n    \"ngeqslant;\": \"\\u2a7e\\u0338\",\n    \"nges;\": \"\\u2a7e\\u0338\",\n    \"ngsim;\": \"\\u2275\",\n    \"ngt;\": \"\\u226f\",\n    \"ngtr;\": \"\\u226f\",\n    \"nhArr;\": \"\\u21ce\",\n    \"nharr;\": \"\\u21ae\",\n    \"nhpar;\": \"\\u2af2\",\n    \"ni;\": \"\\u220b\",\n    \"nis;\": \"\\u22fc\",\n    \"nisd;\": \"\\u22fa\",\n    \"niv;\": \"\\u220b\",\n    \"njcy;\": \"\\u045a\",\n    \"nlArr;\": \"\\u21cd\",\n    \"nlE;\": \"\\u2266\\u0338\",\n    \"nlarr;\": \"\\u219a\",\n    \"nldr;\": \"\\u2025\",\n    \"nle;\": \"\\u2270\",\n    \"nleftarrow;\": \"\\u219a\",\n    \"nleftrightarrow;\": \"\\u21ae\",\n    \"nleq;\": \"\\u2270\",\n    \"nleqq;\": \"\\u2266\\u0338\",\n    \"nleqslant;\": \"\\u2a7d\\u0338\",\n    \"nles;\": \"\\u2a7d\\u0338\",\n    \"nless;\": \"\\u226e\",\n    \"nlsim;\": \"\\u2274\",\n    \"nlt;\": \"\\u226e\",\n    \"nltri;\": \"\\u22ea\",\n    \"nltrie;\": \"\\u22ec\",\n    \"nmid;\": \"\\u2224\",\n    \"nopf;\": \"\\U0001d55f\",\n    \"not\": \"\\xac\",\n    \"not;\": \"\\xac\",\n    \"notin;\": \"\\u2209\",\n    \"notinE;\": \"\\u22f9\\u0338\",\n    \"notindot;\": \"\\u22f5\\u0338\",\n    \"notinva;\": \"\\u2209\",\n    \"notinvb;\": \"\\u22f7\",\n    \"notinvc;\": \"\\u22f6\",\n    \"notni;\": \"\\u220c\",\n    \"notniva;\": \"\\u220c\",\n    \"notnivb;\": \"\\u22fe\",\n    \"notnivc;\": \"\\u22fd\",\n    \"npar;\": \"\\u2226\",\n    \"nparallel;\": \"\\u2226\",\n    \"nparsl;\": \"\\u2afd\\u20e5\",\n    \"npart;\": \"\\u2202\\u0338\",\n    \"npolint;\": \"\\u2a14\",\n    \"npr;\": \"\\u2280\",\n    \"nprcue;\": \"\\u22e0\",\n    \"npre;\": \"\\u2aaf\\u0338\",\n    \"nprec;\": \"\\u2280\",\n    \"npreceq;\": \"\\u2aaf\\u0338\",\n    \"nrArr;\": \"\\u21cf\",\n    \"nrarr;\": \"\\u219b\",\n    \"nrarrc;\": \"\\u2933\\u0338\",\n    \"nrarrw;\": \"\\u219d\\u0338\",\n    \"nrightarrow;\": \"\\u219b\",\n    \"nrtri;\": \"\\u22eb\",\n    \"nrtrie;\": \"\\u22ed\",\n    \"nsc;\": \"\\u2281\",\n    \"nsccue;\": \"\\u22e1\",\n    \"nsce;\": \"\\u2ab0\\u0338\",\n    \"nscr;\": \"\\U0001d4c3\",\n    \"nshortmid;\": \"\\u2224\",\n    \"nshortparallel;\": \"\\u2226\",\n    \"nsim;\": \"\\u2241\",\n    \"nsime;\": \"\\u2244\",\n    \"nsimeq;\": \"\\u2244\",\n    \"nsmid;\": \"\\u2224\",\n    \"nspar;\": \"\\u2226\",\n    \"nsqsube;\": \"\\u22e2\",\n    \"nsqsupe;\": \"\\u22e3\",\n    \"nsub;\": \"\\u2284\",\n    \"nsubE;\": \"\\u2ac5\\u0338\",\n    \"nsube;\": \"\\u2288\",\n    \"nsubset;\": \"\\u2282\\u20d2\",\n    \"nsubseteq;\": \"\\u2288\",\n    \"nsubseteqq;\": \"\\u2ac5\\u0338\",\n    \"nsucc;\": \"\\u2281\",\n    \"nsucceq;\": \"\\u2ab0\\u0338\",\n    \"nsup;\": \"\\u2285\",\n    \"nsupE;\": \"\\u2ac6\\u0338\",\n    \"nsupe;\": \"\\u2289\",\n    \"nsupset;\": \"\\u2283\\u20d2\",\n    \"nsupseteq;\": \"\\u2289\",\n    \"nsupseteqq;\": \"\\u2ac6\\u0338\",\n    \"ntgl;\": \"\\u2279\",\n    \"ntilde\": \"\\xf1\",\n    \"ntilde;\": \"\\xf1\",\n    \"ntlg;\": \"\\u2278\",\n    \"ntriangleleft;\": \"\\u22ea\",\n    \"ntrianglelefteq;\": \"\\u22ec\",\n    \"ntriangleright;\": \"\\u22eb\",\n    \"ntrianglerighteq;\": \"\\u22ed\",\n    \"nu;\": \"\\u03bd\",\n    \"num;\": \"#\",\n    \"numero;\": \"\\u2116\",\n    \"numsp;\": \"\\u2007\",\n    \"nvDash;\": \"\\u22ad\",\n    \"nvHarr;\": \"\\u2904\",\n    \"nvap;\": \"\\u224d\\u20d2\",\n    \"nvdash;\": \"\\u22ac\",\n    \"nvge;\": \"\\u2265\\u20d2\",\n    \"nvgt;\": \">\\u20d2\",\n    \"nvinfin;\": \"\\u29de\",\n    \"nvlArr;\": \"\\u2902\",\n    \"nvle;\": \"\\u2264\\u20d2\",\n    \"nvlt;\": \"<\\u20d2\",\n    \"nvltrie;\": \"\\u22b4\\u20d2\",\n    \"nvrArr;\": \"\\u2903\",\n    \"nvrtrie;\": \"\\u22b5\\u20d2\",\n    \"nvsim;\": \"\\u223c\\u20d2\",\n    \"nwArr;\": \"\\u21d6\",\n    \"nwarhk;\": \"\\u2923\",\n    \"nwarr;\": \"\\u2196\",\n    \"nwarrow;\": \"\\u2196\",\n    \"nwnear;\": \"\\u2927\",\n    \"oS;\": \"\\u24c8\",\n    \"oacute\": \"\\xf3\",\n    \"oacute;\": \"\\xf3\",\n    \"oast;\": \"\\u229b\",\n    \"ocir;\": \"\\u229a\",\n    \"ocirc\": \"\\xf4\",\n    \"ocirc;\": \"\\xf4\",\n    \"ocy;\": \"\\u043e\",\n    \"odash;\": \"\\u229d\",\n    \"odblac;\": \"\\u0151\",\n    \"odiv;\": \"\\u2a38\",\n    \"odot;\": \"\\u2299\",\n    \"odsold;\": \"\\u29bc\",\n    \"oelig;\": \"\\u0153\",\n    \"ofcir;\": \"\\u29bf\",\n    \"ofr;\": \"\\U0001d52c\",\n    \"ogon;\": \"\\u02db\",\n    \"ograve\": \"\\xf2\",\n    \"ograve;\": \"\\xf2\",\n    \"ogt;\": \"\\u29c1\",\n    \"ohbar;\": \"\\u29b5\",\n    \"ohm;\": \"\\u03a9\",\n    \"oint;\": \"\\u222e\",\n    \"olarr;\": \"\\u21ba\",\n    \"olcir;\": \"\\u29be\",\n    \"olcross;\": \"\\u29bb\",\n    \"oline;\": \"\\u203e\",\n    \"olt;\": \"\\u29c0\",\n    \"omacr;\": \"\\u014d\",\n    \"omega;\": \"\\u03c9\",\n    \"omicron;\": \"\\u03bf\",\n    \"omid;\": \"\\u29b6\",\n    \"ominus;\": \"\\u2296\",\n    \"oopf;\": \"\\U0001d560\",\n    \"opar;\": \"\\u29b7\",\n    \"operp;\": \"\\u29b9\",\n    \"oplus;\": \"\\u2295\",\n    \"or;\": \"\\u2228\",\n    \"orarr;\": \"\\u21bb\",\n    \"ord;\": \"\\u2a5d\",\n    \"order;\": \"\\u2134\",\n    \"orderof;\": \"\\u2134\",\n    \"ordf\": \"\\xaa\",\n    \"ordf;\": \"\\xaa\",\n    \"ordm\": \"\\xba\",\n    \"ordm;\": \"\\xba\",\n    \"origof;\": \"\\u22b6\",\n    \"oror;\": \"\\u2a56\",\n    \"orslope;\": \"\\u2a57\",\n    \"orv;\": \"\\u2a5b\",\n    \"oscr;\": \"\\u2134\",\n    \"oslash\": \"\\xf8\",\n    \"oslash;\": \"\\xf8\",\n    \"osol;\": \"\\u2298\",\n    \"otilde\": \"\\xf5\",\n    \"otilde;\": \"\\xf5\",\n    \"otimes;\": \"\\u2297\",\n    \"otimesas;\": \"\\u2a36\",\n    \"ouml\": \"\\xf6\",\n    \"ouml;\": \"\\xf6\",\n    \"ovbar;\": \"\\u233d\",\n    \"par;\": \"\\u2225\",\n    \"para\": \"\\xb6\",\n    \"para;\": \"\\xb6\",\n    \"parallel;\": \"\\u2225\",\n    \"parsim;\": \"\\u2af3\",\n    \"parsl;\": \"\\u2afd\",\n    \"part;\": \"\\u2202\",\n    \"pcy;\": \"\\u043f\",\n    \"percnt;\": \"%\",\n    \"period;\": \".\",\n    \"permil;\": \"\\u2030\",\n    \"perp;\": \"\\u22a5\",\n    \"pertenk;\": \"\\u2031\",\n    \"pfr;\": \"\\U0001d52d\",\n    \"phi;\": \"\\u03c6\",\n    \"phiv;\": \"\\u03d5\",\n    \"phmmat;\": \"\\u2133\",\n    \"phone;\": \"\\u260e\",\n    \"pi;\": \"\\u03c0\",\n    \"pitchfork;\": \"\\u22d4\",\n    \"piv;\": \"\\u03d6\",\n    \"planck;\": \"\\u210f\",\n    \"planckh;\": \"\\u210e\",\n    \"plankv;\": \"\\u210f\",\n    \"plus;\": \"+\",\n    \"plusacir;\": \"\\u2a23\",\n    \"plusb;\": \"\\u229e\",\n    \"pluscir;\": \"\\u2a22\",\n    \"plusdo;\": \"\\u2214\",\n    \"plusdu;\": \"\\u2a25\",\n    \"pluse;\": \"\\u2a72\",\n    \"plusmn\": \"\\xb1\",\n    \"plusmn;\": \"\\xb1\",\n    \"plussim;\": \"\\u2a26\",\n    \"plustwo;\": \"\\u2a27\",\n    \"pm;\": \"\\xb1\",\n    \"pointint;\": \"\\u2a15\",\n    \"popf;\": \"\\U0001d561\",\n    \"pound\": \"\\xa3\",\n    \"pound;\": \"\\xa3\",\n    \"pr;\": \"\\u227a\",\n    \"prE;\": \"\\u2ab3\",\n    \"prap;\": \"\\u2ab7\",\n    \"prcue;\": \"\\u227c\",\n    \"pre;\": \"\\u2aaf\",\n    \"prec;\": \"\\u227a\",\n    \"precapprox;\": \"\\u2ab7\",\n    \"preccurlyeq;\": \"\\u227c\",\n    \"preceq;\": \"\\u2aaf\",\n    \"precnapprox;\": \"\\u2ab9\",\n    \"precneqq;\": \"\\u2ab5\",\n    \"precnsim;\": \"\\u22e8\",\n    \"precsim;\": \"\\u227e\",\n    \"prime;\": \"\\u2032\",\n    \"primes;\": \"\\u2119\",\n    \"prnE;\": \"\\u2ab5\",\n    \"prnap;\": \"\\u2ab9\",\n    \"prnsim;\": \"\\u22e8\",\n    \"prod;\": \"\\u220f\",\n    \"profalar;\": \"\\u232e\",\n    \"profline;\": \"\\u2312\",\n    \"profsurf;\": \"\\u2313\",\n    \"prop;\": \"\\u221d\",\n    \"propto;\": \"\\u221d\",\n    \"prsim;\": \"\\u227e\",\n    \"prurel;\": \"\\u22b0\",\n    \"pscr;\": \"\\U0001d4c5\",\n    \"psi;\": \"\\u03c8\",\n    \"puncsp;\": \"\\u2008\",\n    \"qfr;\": \"\\U0001d52e\",\n    \"qint;\": \"\\u2a0c\",\n    \"qopf;\": \"\\U0001d562\",\n    \"qprime;\": \"\\u2057\",\n    \"qscr;\": \"\\U0001d4c6\",\n    \"quaternions;\": \"\\u210d\",\n    \"quatint;\": \"\\u2a16\",\n    \"quest;\": \"?\",\n    \"questeq;\": \"\\u225f\",\n    \"quot\": \"\\\"\",\n    \"quot;\": \"\\\"\",\n    \"rAarr;\": \"\\u21db\",\n    \"rArr;\": \"\\u21d2\",\n    \"rAtail;\": \"\\u291c\",\n    \"rBarr;\": \"\\u290f\",\n    \"rHar;\": \"\\u2964\",\n    \"race;\": \"\\u223d\\u0331\",\n    \"racute;\": \"\\u0155\",\n    \"radic;\": \"\\u221a\",\n    \"raemptyv;\": \"\\u29b3\",\n    \"rang;\": \"\\u27e9\",\n    \"rangd;\": \"\\u2992\",\n    \"range;\": \"\\u29a5\",\n    \"rangle;\": \"\\u27e9\",\n    \"raquo\": \"\\xbb\",\n    \"raquo;\": \"\\xbb\",\n    \"rarr;\": \"\\u2192\",\n    \"rarrap;\": \"\\u2975\",\n    \"rarrb;\": \"\\u21e5\",\n    \"rarrbfs;\": \"\\u2920\",\n    \"rarrc;\": \"\\u2933\",\n    \"rarrfs;\": \"\\u291e\",\n    \"rarrhk;\": \"\\u21aa\",\n    \"rarrlp;\": \"\\u21ac\",\n    \"rarrpl;\": \"\\u2945\",\n    \"rarrsim;\": \"\\u2974\",\n    \"rarrtl;\": \"\\u21a3\",\n    \"rarrw;\": \"\\u219d\",\n    \"ratail;\": \"\\u291a\",\n    \"ratio;\": \"\\u2236\",\n    \"rationals;\": \"\\u211a\",\n    \"rbarr;\": \"\\u290d\",\n    \"rbbrk;\": \"\\u2773\",\n    \"rbrace;\": \"}\",\n    \"rbrack;\": \"]\",\n    \"rbrke;\": \"\\u298c\",\n    \"rbrksld;\": \"\\u298e\",\n    \"rbrkslu;\": \"\\u2990\",\n    \"rcaron;\": \"\\u0159\",\n    \"rcedil;\": \"\\u0157\",\n    \"rceil;\": \"\\u2309\",\n    \"rcub;\": \"}\",\n    \"rcy;\": \"\\u0440\",\n    \"rdca;\": \"\\u2937\",\n    \"rdldhar;\": \"\\u2969\",\n    \"rdquo;\": \"\\u201d\",\n    \"rdquor;\": \"\\u201d\",\n    \"rdsh;\": \"\\u21b3\",\n    \"real;\": \"\\u211c\",\n    \"realine;\": \"\\u211b\",\n    \"realpart;\": \"\\u211c\",\n    \"reals;\": \"\\u211d\",\n    \"rect;\": \"\\u25ad\",\n    \"reg\": \"\\xae\",\n    \"reg;\": \"\\xae\",\n    \"rfisht;\": \"\\u297d\",\n    \"rfloor;\": \"\\u230b\",\n    \"rfr;\": \"\\U0001d52f\",\n    \"rhard;\": \"\\u21c1\",\n    \"rharu;\": \"\\u21c0\",\n    \"rharul;\": \"\\u296c\",\n    \"rho;\": \"\\u03c1\",\n    \"rhov;\": \"\\u03f1\",\n    \"rightarrow;\": \"\\u2192\",\n    \"rightarrowtail;\": \"\\u21a3\",\n    \"rightharpoondown;\": \"\\u21c1\",\n    \"rightharpoonup;\": \"\\u21c0\",\n    \"rightleftarrows;\": \"\\u21c4\",\n    \"rightleftharpoons;\": \"\\u21cc\",\n    \"rightrightarrows;\": \"\\u21c9\",\n    \"rightsquigarrow;\": \"\\u219d\",\n    \"rightthreetimes;\": \"\\u22cc\",\n    \"ring;\": \"\\u02da\",\n    \"risingdotseq;\": \"\\u2253\",\n    \"rlarr;\": \"\\u21c4\",\n    \"rlhar;\": \"\\u21cc\",\n    \"rlm;\": \"\\u200f\",\n    \"rmoust;\": \"\\u23b1\",\n    \"rmoustache;\": \"\\u23b1\",\n    \"rnmid;\": \"\\u2aee\",\n    \"roang;\": \"\\u27ed\",\n    \"roarr;\": \"\\u21fe\",\n    \"robrk;\": \"\\u27e7\",\n    \"ropar;\": \"\\u2986\",\n    \"ropf;\": \"\\U0001d563\",\n    \"roplus;\": \"\\u2a2e\",\n    \"rotimes;\": \"\\u2a35\",\n    \"rpar;\": \")\",\n    \"rpargt;\": \"\\u2994\",\n    \"rppolint;\": \"\\u2a12\",\n    \"rrarr;\": \"\\u21c9\",\n    \"rsaquo;\": \"\\u203a\",\n    \"rscr;\": \"\\U0001d4c7\",\n    \"rsh;\": \"\\u21b1\",\n    \"rsqb;\": \"]\",\n    \"rsquo;\": \"\\u2019\",\n    \"rsquor;\": \"\\u2019\",\n    \"rthree;\": \"\\u22cc\",\n    \"rtimes;\": \"\\u22ca\",\n    \"rtri;\": \"\\u25b9\",\n    \"rtrie;\": \"\\u22b5\",\n    \"rtrif;\": \"\\u25b8\",\n    \"rtriltri;\": \"\\u29ce\",\n    \"ruluhar;\": \"\\u2968\",\n    \"rx;\": \"\\u211e\",\n    \"sacute;\": \"\\u015b\",\n    \"sbquo;\": \"\\u201a\",\n    \"sc;\": \"\\u227b\",\n    \"scE;\": \"\\u2ab4\",\n    \"scap;\": \"\\u2ab8\",\n    \"scaron;\": \"\\u0161\",\n    \"sccue;\": \"\\u227d\",\n    \"sce;\": \"\\u2ab0\",\n    \"scedil;\": \"\\u015f\",\n    \"scirc;\": \"\\u015d\",\n    \"scnE;\": \"\\u2ab6\",\n    \"scnap;\": \"\\u2aba\",\n    \"scnsim;\": \"\\u22e9\",\n    \"scpolint;\": \"\\u2a13\",\n    \"scsim;\": \"\\u227f\",\n    \"scy;\": \"\\u0441\",\n    \"sdot;\": \"\\u22c5\",\n    \"sdotb;\": \"\\u22a1\",\n    \"sdote;\": \"\\u2a66\",\n    \"seArr;\": \"\\u21d8\",\n    \"searhk;\": \"\\u2925\",\n    \"searr;\": \"\\u2198\",\n    \"searrow;\": \"\\u2198\",\n    \"sect\": \"\\xa7\",\n    \"sect;\": \"\\xa7\",\n    \"semi;\": \";\",\n    \"seswar;\": \"\\u2929\",\n    \"setminus;\": \"\\u2216\",\n    \"setmn;\": \"\\u2216\",\n    \"sext;\": \"\\u2736\",\n    \"sfr;\": \"\\U0001d530\",\n    \"sfrown;\": \"\\u2322\",\n    \"sharp;\": \"\\u266f\",\n    \"shchcy;\": \"\\u0449\",\n    \"shcy;\": \"\\u0448\",\n    \"shortmid;\": \"\\u2223\",\n    \"shortparallel;\": \"\\u2225\",\n    \"shy\": \"\\xad\",\n    \"shy;\": \"\\xad\",\n    \"sigma;\": \"\\u03c3\",\n    \"sigmaf;\": \"\\u03c2\",\n    \"sigmav;\": \"\\u03c2\",\n    \"sim;\": \"\\u223c\",\n    \"simdot;\": \"\\u2a6a\",\n    \"sime;\": \"\\u2243\",\n    \"simeq;\": \"\\u2243\",\n    \"simg;\": \"\\u2a9e\",\n    \"simgE;\": \"\\u2aa0\",\n    \"siml;\": \"\\u2a9d\",\n    \"simlE;\": \"\\u2a9f\",\n    \"simne;\": \"\\u2246\",\n    \"simplus;\": \"\\u2a24\",\n    \"simrarr;\": \"\\u2972\",\n    \"slarr;\": \"\\u2190\",\n    \"smallsetminus;\": \"\\u2216\",\n    \"smashp;\": \"\\u2a33\",\n    \"smeparsl;\": \"\\u29e4\",\n    \"smid;\": \"\\u2223\",\n    \"smile;\": \"\\u2323\",\n    \"smt;\": \"\\u2aaa\",\n    \"smte;\": \"\\u2aac\",\n    \"smtes;\": \"\\u2aac\\ufe00\",\n    \"softcy;\": \"\\u044c\",\n    \"sol;\": \"/\",\n    \"solb;\": \"\\u29c4\",\n    \"solbar;\": \"\\u233f\",\n    \"sopf;\": \"\\U0001d564\",\n    \"spades;\": \"\\u2660\",\n    \"spadesuit;\": \"\\u2660\",\n    \"spar;\": \"\\u2225\",\n    \"sqcap;\": \"\\u2293\",\n    \"sqcaps;\": \"\\u2293\\ufe00\",\n    \"sqcup;\": \"\\u2294\",\n    \"sqcups;\": \"\\u2294\\ufe00\",\n    \"sqsub;\": \"\\u228f\",\n    \"sqsube;\": \"\\u2291\",\n    \"sqsubset;\": \"\\u228f\",\n    \"sqsubseteq;\": \"\\u2291\",\n    \"sqsup;\": \"\\u2290\",\n    \"sqsupe;\": \"\\u2292\",\n    \"sqsupset;\": \"\\u2290\",\n    \"sqsupseteq;\": \"\\u2292\",\n    \"squ;\": \"\\u25a1\",\n    \"square;\": \"\\u25a1\",\n    \"squarf;\": \"\\u25aa\",\n    \"squf;\": \"\\u25aa\",\n    \"srarr;\": \"\\u2192\",\n    \"sscr;\": \"\\U0001d4c8\",\n    \"ssetmn;\": \"\\u2216\",\n    \"ssmile;\": \"\\u2323\",\n    \"sstarf;\": \"\\u22c6\",\n    \"star;\": \"\\u2606\",\n    \"starf;\": \"\\u2605\",\n    \"straightepsilon;\": \"\\u03f5\",\n    \"straightphi;\": \"\\u03d5\",\n    \"strns;\": \"\\xaf\",\n    \"sub;\": \"\\u2282\",\n    \"subE;\": \"\\u2ac5\",\n    \"subdot;\": \"\\u2abd\",\n    \"sube;\": \"\\u2286\",\n    \"subedot;\": \"\\u2ac3\",\n    \"submult;\": \"\\u2ac1\",\n    \"subnE;\": \"\\u2acb\",\n    \"subne;\": \"\\u228a\",\n    \"subplus;\": \"\\u2abf\",\n    \"subrarr;\": \"\\u2979\",\n    \"subset;\": \"\\u2282\",\n    \"subseteq;\": \"\\u2286\",\n    \"subseteqq;\": \"\\u2ac5\",\n    \"subsetneq;\": \"\\u228a\",\n    \"subsetneqq;\": \"\\u2acb\",\n    \"subsim;\": \"\\u2ac7\",\n    \"subsub;\": \"\\u2ad5\",\n    \"subsup;\": \"\\u2ad3\",\n    \"succ;\": \"\\u227b\",\n    \"succapprox;\": \"\\u2ab8\",\n    \"succcurlyeq;\": \"\\u227d\",\n    \"succeq;\": \"\\u2ab0\",\n    \"succnapprox;\": \"\\u2aba\",\n    \"succneqq;\": \"\\u2ab6\",\n    \"succnsim;\": \"\\u22e9\",\n    \"succsim;\": \"\\u227f\",\n    \"sum;\": \"\\u2211\",\n    \"sung;\": \"\\u266a\",\n    \"sup1\": \"\\xb9\",\n    \"sup1;\": \"\\xb9\",\n    \"sup2\": \"\\xb2\",\n    \"sup2;\": \"\\xb2\",\n    \"sup3\": \"\\xb3\",\n    \"sup3;\": \"\\xb3\",\n    \"sup;\": \"\\u2283\",\n    \"supE;\": \"\\u2ac6\",\n    \"supdot;\": \"\\u2abe\",\n    \"supdsub;\": \"\\u2ad8\",\n    \"supe;\": \"\\u2287\",\n    \"supedot;\": \"\\u2ac4\",\n    \"suphsol;\": \"\\u27c9\",\n    \"suphsub;\": \"\\u2ad7\",\n    \"suplarr;\": \"\\u297b\",\n    \"supmult;\": \"\\u2ac2\",\n    \"supnE;\": \"\\u2acc\",\n    \"supne;\": \"\\u228b\",\n    \"supplus;\": \"\\u2ac0\",\n    \"supset;\": \"\\u2283\",\n    \"supseteq;\": \"\\u2287\",\n    \"supseteqq;\": \"\\u2ac6\",\n    \"supsetneq;\": \"\\u228b\",\n    \"supsetneqq;\": \"\\u2acc\",\n    \"supsim;\": \"\\u2ac8\",\n    \"supsub;\": \"\\u2ad4\",\n    \"supsup;\": \"\\u2ad6\",\n    \"swArr;\": \"\\u21d9\",\n    \"swarhk;\": \"\\u2926\",\n    \"swarr;\": \"\\u2199\",\n    \"swarrow;\": \"\\u2199\",\n    \"swnwar;\": \"\\u292a\",\n    \"szlig\": \"\\xdf\",\n    \"szlig;\": \"\\xdf\",\n    \"target;\": \"\\u2316\",\n    \"tau;\": \"\\u03c4\",\n    \"tbrk;\": \"\\u23b4\",\n    \"tcaron;\": \"\\u0165\",\n    \"tcedil;\": \"\\u0163\",\n    \"tcy;\": \"\\u0442\",\n    \"tdot;\": \"\\u20db\",\n    \"telrec;\": \"\\u2315\",\n    \"tfr;\": \"\\U0001d531\",\n    \"there4;\": \"\\u2234\",\n    \"therefore;\": \"\\u2234\",\n    \"theta;\": \"\\u03b8\",\n    \"thetasym;\": \"\\u03d1\",\n    \"thetav;\": \"\\u03d1\",\n    \"thickapprox;\": \"\\u2248\",\n    \"thicksim;\": \"\\u223c\",\n    \"thinsp;\": \"\\u2009\",\n    \"thkap;\": \"\\u2248\",\n    \"thksim;\": \"\\u223c\",\n    \"thorn\": \"\\xfe\",\n    \"thorn;\": \"\\xfe\",\n    \"tilde;\": \"\\u02dc\",\n    \"times\": \"\\xd7\",\n    \"times;\": \"\\xd7\",\n    \"timesb;\": \"\\u22a0\",\n    \"timesbar;\": \"\\u2a31\",\n    \"timesd;\": \"\\u2a30\",\n    \"tint;\": \"\\u222d\",\n    \"toea;\": \"\\u2928\",\n    \"top;\": \"\\u22a4\",\n    \"topbot;\": \"\\u2336\",\n    \"topcir;\": \"\\u2af1\",\n    \"topf;\": \"\\U0001d565\",\n    \"topfork;\": \"\\u2ada\",\n    \"tosa;\": \"\\u2929\",\n    \"tprime;\": \"\\u2034\",\n    \"trade;\": \"\\u2122\",\n    \"triangle;\": \"\\u25b5\",\n    \"triangledown;\": \"\\u25bf\",\n    \"triangleleft;\": \"\\u25c3\",\n    \"trianglelefteq;\": \"\\u22b4\",\n    \"triangleq;\": \"\\u225c\",\n    \"triangleright;\": \"\\u25b9\",\n    \"trianglerighteq;\": \"\\u22b5\",\n    \"tridot;\": \"\\u25ec\",\n    \"trie;\": \"\\u225c\",\n    \"triminus;\": \"\\u2a3a\",\n    \"triplus;\": \"\\u2a39\",\n    \"trisb;\": \"\\u29cd\",\n    \"tritime;\": \"\\u2a3b\",\n    \"trpezium;\": \"\\u23e2\",\n    \"tscr;\": \"\\U0001d4c9\",\n    \"tscy;\": \"\\u0446\",\n    \"tshcy;\": \"\\u045b\",\n    \"tstrok;\": \"\\u0167\",\n    \"twixt;\": \"\\u226c\",\n    \"twoheadleftarrow;\": \"\\u219e\",\n    \"twoheadrightarrow;\": \"\\u21a0\",\n    \"uArr;\": \"\\u21d1\",\n    \"uHar;\": \"\\u2963\",\n    \"uacute\": \"\\xfa\",\n    \"uacute;\": \"\\xfa\",\n    \"uarr;\": \"\\u2191\",\n    \"ubrcy;\": \"\\u045e\",\n    \"ubreve;\": \"\\u016d\",\n    \"ucirc\": \"\\xfb\",\n    \"ucirc;\": \"\\xfb\",\n    \"ucy;\": \"\\u0443\",\n    \"udarr;\": \"\\u21c5\",\n    \"udblac;\": \"\\u0171\",\n    \"udhar;\": \"\\u296e\",\n    \"ufisht;\": \"\\u297e\",\n    \"ufr;\": \"\\U0001d532\",\n    \"ugrave\": \"\\xf9\",\n    \"ugrave;\": \"\\xf9\",\n    \"uharl;\": \"\\u21bf\",\n    \"uharr;\": \"\\u21be\",\n    \"uhblk;\": \"\\u2580\",\n    \"ulcorn;\": \"\\u231c\",\n    \"ulcorner;\": \"\\u231c\",\n    \"ulcrop;\": \"\\u230f\",\n    \"ultri;\": \"\\u25f8\",\n    \"umacr;\": \"\\u016b\",\n    \"uml\": \"\\xa8\",\n    \"uml;\": \"\\xa8\",\n    \"uogon;\": \"\\u0173\",\n    \"uopf;\": \"\\U0001d566\",\n    \"uparrow;\": \"\\u2191\",\n    \"updownarrow;\": \"\\u2195\",\n    \"upharpoonleft;\": \"\\u21bf\",\n    \"upharpoonright;\": \"\\u21be\",\n    \"uplus;\": \"\\u228e\",\n    \"upsi;\": \"\\u03c5\",\n    \"upsih;\": \"\\u03d2\",\n    \"upsilon;\": \"\\u03c5\",\n    \"upuparrows;\": \"\\u21c8\",\n    \"urcorn;\": \"\\u231d\",\n    \"urcorner;\": \"\\u231d\",\n    \"urcrop;\": \"\\u230e\",\n    \"uring;\": \"\\u016f\",\n    \"urtri;\": \"\\u25f9\",\n    \"uscr;\": \"\\U0001d4ca\",\n    \"utdot;\": \"\\u22f0\",\n    \"utilde;\": \"\\u0169\",\n    \"utri;\": \"\\u25b5\",\n    \"utrif;\": \"\\u25b4\",\n    \"uuarr;\": \"\\u21c8\",\n    \"uuml\": \"\\xfc\",\n    \"uuml;\": \"\\xfc\",\n    \"uwangle;\": \"\\u29a7\",\n    \"vArr;\": \"\\u21d5\",\n    \"vBar;\": \"\\u2ae8\",\n    \"vBarv;\": \"\\u2ae9\",\n    \"vDash;\": \"\\u22a8\",\n    \"vangrt;\": \"\\u299c\",\n    \"varepsilon;\": \"\\u03f5\",\n    \"varkappa;\": \"\\u03f0\",\n    \"varnothing;\": \"\\u2205\",\n    \"varphi;\": \"\\u03d5\",\n    \"varpi;\": \"\\u03d6\",\n    \"varpropto;\": \"\\u221d\",\n    \"varr;\": \"\\u2195\",\n    \"varrho;\": \"\\u03f1\",\n    \"varsigma;\": \"\\u03c2\",\n    \"varsubsetneq;\": \"\\u228a\\ufe00\",\n    \"varsubsetneqq;\": \"\\u2acb\\ufe00\",\n    \"varsupsetneq;\": \"\\u228b\\ufe00\",\n    \"varsupsetneqq;\": \"\\u2acc\\ufe00\",\n    \"vartheta;\": \"\\u03d1\",\n    \"vartriangleleft;\": \"\\u22b2\",\n    \"vartriangleright;\": \"\\u22b3\",\n    \"vcy;\": \"\\u0432\",\n    \"vdash;\": \"\\u22a2\",\n    \"vee;\": \"\\u2228\",\n    \"veebar;\": \"\\u22bb\",\n    \"veeeq;\": \"\\u225a\",\n    \"vellip;\": \"\\u22ee\",\n    \"verbar;\": \"|\",\n    \"vert;\": \"|\",\n    \"vfr;\": \"\\U0001d533\",\n    \"vltri;\": \"\\u22b2\",\n    \"vnsub;\": \"\\u2282\\u20d2\",\n    \"vnsup;\": \"\\u2283\\u20d2\",\n    \"vopf;\": \"\\U0001d567\",\n    \"vprop;\": \"\\u221d\",\n    \"vrtri;\": \"\\u22b3\",\n    \"vscr;\": \"\\U0001d4cb\",\n    \"vsubnE;\": \"\\u2acb\\ufe00\",\n    \"vsubne;\": \"\\u228a\\ufe00\",\n    \"vsupnE;\": \"\\u2acc\\ufe00\",\n    \"vsupne;\": \"\\u228b\\ufe00\",\n    \"vzigzag;\": \"\\u299a\",\n    \"wcirc;\": \"\\u0175\",\n    \"wedbar;\": \"\\u2a5f\",\n    \"wedge;\": \"\\u2227\",\n    \"wedgeq;\": \"\\u2259\",\n    \"weierp;\": \"\\u2118\",\n    \"wfr;\": \"\\U0001d534\",\n    \"wopf;\": \"\\U0001d568\",\n    \"wp;\": \"\\u2118\",\n    \"wr;\": \"\\u2240\",\n    \"wreath;\": \"\\u2240\",\n    \"wscr;\": \"\\U0001d4cc\",\n    \"xcap;\": \"\\u22c2\",\n    \"xcirc;\": \"\\u25ef\",\n    \"xcup;\": \"\\u22c3\",\n    \"xdtri;\": \"\\u25bd\",\n    \"xfr;\": \"\\U0001d535\",\n    \"xhArr;\": \"\\u27fa\",\n    \"xharr;\": \"\\u27f7\",\n    \"xi;\": \"\\u03be\",\n    \"xlArr;\": \"\\u27f8\",\n    \"xlarr;\": \"\\u27f5\",\n    \"xmap;\": \"\\u27fc\",\n    \"xnis;\": \"\\u22fb\",\n    \"xodot;\": \"\\u2a00\",\n    \"xopf;\": \"\\U0001d569\",\n    \"xoplus;\": \"\\u2a01\",\n    \"xotime;\": \"\\u2a02\",\n    \"xrArr;\": \"\\u27f9\",\n    \"xrarr;\": \"\\u27f6\",\n    \"xscr;\": \"\\U0001d4cd\",\n    \"xsqcup;\": \"\\u2a06\",\n    \"xuplus;\": \"\\u2a04\",\n    \"xutri;\": \"\\u25b3\",\n    \"xvee;\": \"\\u22c1\",\n    \"xwedge;\": \"\\u22c0\",\n    \"yacute\": \"\\xfd\",\n    \"yacute;\": \"\\xfd\",\n    \"yacy;\": \"\\u044f\",\n    \"ycirc;\": \"\\u0177\",\n    \"ycy;\": \"\\u044b\",\n    \"yen\": \"\\xa5\",\n    \"yen;\": \"\\xa5\",\n    \"yfr;\": \"\\U0001d536\",\n    \"yicy;\": \"\\u0457\",\n    \"yopf;\": \"\\U0001d56a\",\n    \"yscr;\": \"\\U0001d4ce\",\n    \"yucy;\": \"\\u044e\",\n    \"yuml\": \"\\xff\",\n    \"yuml;\": \"\\xff\",\n    \"zacute;\": \"\\u017a\",\n    \"zcaron;\": \"\\u017e\",\n    \"zcy;\": \"\\u0437\",\n    \"zdot;\": \"\\u017c\",\n    \"zeetrf;\": \"\\u2128\",\n    \"zeta;\": \"\\u03b6\",\n    \"zfr;\": \"\\U0001d537\",\n    \"zhcy;\": \"\\u0436\",\n    \"zigrarr;\": \"\\u21dd\",\n    \"zopf;\": \"\\U0001d56b\",\n    \"zscr;\": \"\\U0001d4cf\",\n    \"zwj;\": \"\\u200d\",\n    \"zwnj;\": \"\\u200c\",\n}\n\nreplacementCharacters = {\n    0x0: \"\\uFFFD\",\n    0x0d: \"\\u000D\",\n    0x80: \"\\u20AC\",\n    0x81: \"\\u0081\",\n    0x82: \"\\u201A\",\n    0x83: \"\\u0192\",\n    0x84: \"\\u201E\",\n    0x85: \"\\u2026\",\n    0x86: \"\\u2020\",\n    0x87: \"\\u2021\",\n    0x88: \"\\u02C6\",\n    0x89: \"\\u2030\",\n    0x8A: \"\\u0160\",\n    0x8B: \"\\u2039\",\n    0x8C: \"\\u0152\",\n    0x8D: \"\\u008D\",\n    0x8E: \"\\u017D\",\n    0x8F: \"\\u008F\",\n    0x90: \"\\u0090\",\n    0x91: \"\\u2018\",\n    0x92: \"\\u2019\",\n    0x93: \"\\u201C\",\n    0x94: \"\\u201D\",\n    0x95: \"\\u2022\",\n    0x96: \"\\u2013\",\n    0x97: \"\\u2014\",\n    0x98: \"\\u02DC\",\n    0x99: \"\\u2122\",\n    0x9A: \"\\u0161\",\n    0x9B: \"\\u203A\",\n    0x9C: \"\\u0153\",\n    0x9D: \"\\u009D\",\n    0x9E: \"\\u017E\",\n    0x9F: \"\\u0178\",\n}\n\ntokenTypes = {\n    \"Doctype\": 0,\n    \"Characters\": 1,\n    \"SpaceCharacters\": 2,\n    \"StartTag\": 3,\n    \"EndTag\": 4,\n    \"EmptyTag\": 5,\n    \"Comment\": 6,\n    \"ParseError\": 7\n}\n\ntagTokenTypes = frozenset([tokenTypes[\"StartTag\"], tokenTypes[\"EndTag\"],\n                           tokenTypes[\"EmptyTag\"]])\n\n\nprefixes = dict([(v, k) for k, v in namespaces.items()])\nprefixes[\"http://www.w3.org/1998/Math/MathML\"] = \"math\"\n\n\nclass DataLossWarning(UserWarning):\n    \"\"\"Raised when the current tree is unable to represent the input data\"\"\"\n    pass\n\n\nclass _ReparseException(Exception):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/filters/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/filters/alphabeticalattributes.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom . import base\n\nfrom collections import OrderedDict\n\n\ndef _attr_key(attr):\n    \"\"\"Return an appropriate key for an attribute for sorting\n\n    Attributes have a namespace that can be either ``None`` or a string. We\n    can't compare the two because they're different types, so we convert\n    ``None`` to an empty string first.\n\n    \"\"\"\n    return (attr[0][0] or ''), attr[0][1]\n\n\nclass Filter(base.Filter):\n    \"\"\"Alphabetizes attributes for elements\"\"\"\n    def __iter__(self):\n        for token in base.Filter.__iter__(self):\n            if token[\"type\"] in (\"StartTag\", \"EmptyTag\"):\n                attrs = OrderedDict()\n                for name, value in sorted(token[\"data\"].items(),\n                                          key=_attr_key):\n                    attrs[name] = value\n                token[\"data\"] = attrs\n            yield token\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/filters/base.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\n\nclass Filter(object):\n    def __init__(self, source):\n        self.source = source\n\n    def __iter__(self):\n        return iter(self.source)\n\n    def __getattr__(self, name):\n        return getattr(self.source, name)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/filters/inject_meta_charset.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom . import base\n\n\nclass Filter(base.Filter):\n    \"\"\"Injects ``<meta charset=ENCODING>`` tag into head of document\"\"\"\n    def __init__(self, source, encoding):\n        \"\"\"Creates a Filter\n\n        :arg source: the source token stream\n\n        :arg encoding: the encoding to set\n\n        \"\"\"\n        base.Filter.__init__(self, source)\n        self.encoding = encoding\n\n    def __iter__(self):\n        state = \"pre_head\"\n        meta_found = (self.encoding is None)\n        pending = []\n\n        for token in base.Filter.__iter__(self):\n            type = token[\"type\"]\n            if type == \"StartTag\":\n                if token[\"name\"].lower() == \"head\":\n                    state = \"in_head\"\n\n            elif type == \"EmptyTag\":\n                if token[\"name\"].lower() == \"meta\":\n                    # replace charset with actual encoding\n                    has_http_equiv_content_type = False\n                    for (namespace, name), value in token[\"data\"].items():\n                        if namespace is not None:\n                            continue\n                        elif name.lower() == 'charset':\n                            token[\"data\"][(namespace, name)] = self.encoding\n                            meta_found = True\n                            break\n                        elif name == 'http-equiv' and value.lower() == 'content-type':\n                            has_http_equiv_content_type = True\n                    else:\n                        if has_http_equiv_content_type and (None, \"content\") in token[\"data\"]:\n                            token[\"data\"][(None, \"content\")] = 'text/html; charset=%s' % self.encoding\n                            meta_found = True\n\n                elif token[\"name\"].lower() == \"head\" and not meta_found:\n                    # insert meta into empty head\n                    yield {\"type\": \"StartTag\", \"name\": \"head\",\n                           \"data\": token[\"data\"]}\n                    yield {\"type\": \"EmptyTag\", \"name\": \"meta\",\n                           \"data\": {(None, \"charset\"): self.encoding}}\n                    yield {\"type\": \"EndTag\", \"name\": \"head\"}\n                    meta_found = True\n                    continue\n\n            elif type == \"EndTag\":\n                if token[\"name\"].lower() == \"head\" and pending:\n                    # insert meta into head (if necessary) and flush pending queue\n                    yield pending.pop(0)\n                    if not meta_found:\n                        yield {\"type\": \"EmptyTag\", \"name\": \"meta\",\n                               \"data\": {(None, \"charset\"): self.encoding}}\n                    while pending:\n                        yield pending.pop(0)\n                    meta_found = True\n                    state = \"post_head\"\n\n            if state == \"in_head\":\n                pending.append(token)\n            else:\n                yield token\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/filters/lint.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom pip._vendor.six import text_type\n\nfrom . import base\nfrom ..constants import namespaces, voidElements\n\nfrom ..constants import spaceCharacters\nspaceCharacters = \"\".join(spaceCharacters)\n\n\nclass Filter(base.Filter):\n    \"\"\"Lints the token stream for errors\n\n    If it finds any errors, it'll raise an ``AssertionError``.\n\n    \"\"\"\n    def __init__(self, source, require_matching_tags=True):\n        \"\"\"Creates a Filter\n\n        :arg source: the source token stream\n\n        :arg require_matching_tags: whether or not to require matching tags\n\n        \"\"\"\n        super(Filter, self).__init__(source)\n        self.require_matching_tags = require_matching_tags\n\n    def __iter__(self):\n        open_elements = []\n        for token in base.Filter.__iter__(self):\n            type = token[\"type\"]\n            if type in (\"StartTag\", \"EmptyTag\"):\n                namespace = token[\"namespace\"]\n                name = token[\"name\"]\n                assert namespace is None or isinstance(namespace, text_type)\n                assert namespace != \"\"\n                assert isinstance(name, text_type)\n                assert name != \"\"\n                assert isinstance(token[\"data\"], dict)\n                if (not namespace or namespace == namespaces[\"html\"]) and name in voidElements:\n                    assert type == \"EmptyTag\"\n                else:\n                    assert type == \"StartTag\"\n                if type == \"StartTag\" and self.require_matching_tags:\n                    open_elements.append((namespace, name))\n                for (namespace, name), value in token[\"data\"].items():\n                    assert namespace is None or isinstance(namespace, text_type)\n                    assert namespace != \"\"\n                    assert isinstance(name, text_type)\n                    assert name != \"\"\n                    assert isinstance(value, text_type)\n\n            elif type == \"EndTag\":\n                namespace = token[\"namespace\"]\n                name = token[\"name\"]\n                assert namespace is None or isinstance(namespace, text_type)\n                assert namespace != \"\"\n                assert isinstance(name, text_type)\n                assert name != \"\"\n                if (not namespace or namespace == namespaces[\"html\"]) and name in voidElements:\n                    assert False, \"Void element reported as EndTag token: %(tag)s\" % {\"tag\": name}\n                elif self.require_matching_tags:\n                    start = open_elements.pop()\n                    assert start == (namespace, name)\n\n            elif type == \"Comment\":\n                data = token[\"data\"]\n                assert isinstance(data, text_type)\n\n            elif type in (\"Characters\", \"SpaceCharacters\"):\n                data = token[\"data\"]\n                assert isinstance(data, text_type)\n                assert data != \"\"\n                if type == \"SpaceCharacters\":\n                    assert data.strip(spaceCharacters) == \"\"\n\n            elif type == \"Doctype\":\n                name = token[\"name\"]\n                assert name is None or isinstance(name, text_type)\n                assert token[\"publicId\"] is None or isinstance(name, text_type)\n                assert token[\"systemId\"] is None or isinstance(name, text_type)\n\n            elif type == \"Entity\":\n                assert isinstance(token[\"name\"], text_type)\n\n            elif type == \"SerializerError\":\n                assert isinstance(token[\"data\"], text_type)\n\n            else:\n                assert False, \"Unknown token type: %(type)s\" % {\"type\": type}\n\n            yield token\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/filters/optionaltags.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom . import base\n\n\nclass Filter(base.Filter):\n    \"\"\"Removes optional tags from the token stream\"\"\"\n    def slider(self):\n        previous1 = previous2 = None\n        for token in self.source:\n            if previous1 is not None:\n                yield previous2, previous1, token\n            previous2 = previous1\n            previous1 = token\n        if previous1 is not None:\n            yield previous2, previous1, None\n\n    def __iter__(self):\n        for previous, token, next in self.slider():\n            type = token[\"type\"]\n            if type == \"StartTag\":\n                if (token[\"data\"] or\n                        not self.is_optional_start(token[\"name\"], previous, next)):\n                    yield token\n            elif type == \"EndTag\":\n                if not self.is_optional_end(token[\"name\"], next):\n                    yield token\n            else:\n                yield token\n\n    def is_optional_start(self, tagname, previous, next):\n        type = next and next[\"type\"] or None\n        if tagname in 'html':\n            # An html element's start tag may be omitted if the first thing\n            # inside the html element is not a space character or a comment.\n            return type not in (\"Comment\", \"SpaceCharacters\")\n        elif tagname == 'head':\n            # A head element's start tag may be omitted if the first thing\n            # inside the head element is an element.\n            # XXX: we also omit the start tag if the head element is empty\n            if type in (\"StartTag\", \"EmptyTag\"):\n                return True\n            elif type == \"EndTag\":\n                return next[\"name\"] == \"head\"\n        elif tagname == 'body':\n            # A body element's start tag may be omitted if the first thing\n            # inside the body element is not a space character or a comment,\n            # except if the first thing inside the body element is a script\n            # or style element and the node immediately preceding the body\n            # element is a head element whose end tag has been omitted.\n            if type in (\"Comment\", \"SpaceCharacters\"):\n                return False\n            elif type == \"StartTag\":\n                # XXX: we do not look at the preceding event, so we never omit\n                # the body element's start tag if it's followed by a script or\n                # a style element.\n                return next[\"name\"] not in ('script', 'style')\n            else:\n                return True\n        elif tagname == 'colgroup':\n            # A colgroup element's start tag may be omitted if the first thing\n            # inside the colgroup element is a col element, and if the element\n            # is not immediately preceded by another colgroup element whose\n            # end tag has been omitted.\n            if type in (\"StartTag\", \"EmptyTag\"):\n                # XXX: we do not look at the preceding event, so instead we never\n                # omit the colgroup element's end tag when it is immediately\n                # followed by another colgroup element. See is_optional_end.\n                return next[\"name\"] == \"col\"\n            else:\n                return False\n        elif tagname == 'tbody':\n            # A tbody element's start tag may be omitted if the first thing\n            # inside the tbody element is a tr element, and if the element is\n            # not immediately preceded by a tbody, thead, or tfoot element\n            # whose end tag has been omitted.\n            if type == \"StartTag\":\n                # omit the thead and tfoot elements' end tag when they are\n                # immediately followed by a tbody element. See is_optional_end.\n                if previous and previous['type'] == 'EndTag' and \\\n                        previous['name'] in ('tbody', 'thead', 'tfoot'):\n                    return False\n                return next[\"name\"] == 'tr'\n            else:\n                return False\n        return False\n\n    def is_optional_end(self, tagname, next):\n        type = next and next[\"type\"] or None\n        if tagname in ('html', 'head', 'body'):\n            # An html element's end tag may be omitted if the html element\n            # is not immediately followed by a space character or a comment.\n            return type not in (\"Comment\", \"SpaceCharacters\")\n        elif tagname in ('li', 'optgroup', 'tr'):\n            # A li element's end tag may be omitted if the li element is\n            # immediately followed by another li element or if there is\n            # no more content in the parent element.\n            # An optgroup element's end tag may be omitted if the optgroup\n            # element is immediately followed by another optgroup element,\n            # or if there is no more content in the parent element.\n            # A tr element's end tag may be omitted if the tr element is\n            # immediately followed by another tr element, or if there is\n            # no more content in the parent element.\n            if type == \"StartTag\":\n                return next[\"name\"] == tagname\n            else:\n                return type == \"EndTag\" or type is None\n        elif tagname in ('dt', 'dd'):\n            # A dt element's end tag may be omitted if the dt element is\n            # immediately followed by another dt element or a dd element.\n            # A dd element's end tag may be omitted if the dd element is\n            # immediately followed by another dd element or a dt element,\n            # or if there is no more content in the parent element.\n            if type == \"StartTag\":\n                return next[\"name\"] in ('dt', 'dd')\n            elif tagname == 'dd':\n                return type == \"EndTag\" or type is None\n            else:\n                return False\n        elif tagname == 'p':\n            # A p element's end tag may be omitted if the p element is\n            # immediately followed by an address, article, aside,\n            # blockquote, datagrid, dialog, dir, div, dl, fieldset,\n            # footer, form, h1, h2, h3, h4, h5, h6, header, hr, menu,\n            # nav, ol, p, pre, section, table, or ul, element, or if\n            # there is no more content in the parent element.\n            if type in (\"StartTag\", \"EmptyTag\"):\n                return next[\"name\"] in ('address', 'article', 'aside',\n                                        'blockquote', 'datagrid', 'dialog',\n                                        'dir', 'div', 'dl', 'fieldset', 'footer',\n                                        'form', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6',\n                                        'header', 'hr', 'menu', 'nav', 'ol',\n                                        'p', 'pre', 'section', 'table', 'ul')\n            else:\n                return type == \"EndTag\" or type is None\n        elif tagname == 'option':\n            # An option element's end tag may be omitted if the option\n            # element is immediately followed by another option element,\n            # or if it is immediately followed by an <code>optgroup</code>\n            # element, or if there is no more content in the parent\n            # element.\n            if type == \"StartTag\":\n                return next[\"name\"] in ('option', 'optgroup')\n            else:\n                return type == \"EndTag\" or type is None\n        elif tagname in ('rt', 'rp'):\n            # An rt element's end tag may be omitted if the rt element is\n            # immediately followed by an rt or rp element, or if there is\n            # no more content in the parent element.\n            # An rp element's end tag may be omitted if the rp element is\n            # immediately followed by an rt or rp element, or if there is\n            # no more content in the parent element.\n            if type == \"StartTag\":\n                return next[\"name\"] in ('rt', 'rp')\n            else:\n                return type == \"EndTag\" or type is None\n        elif tagname == 'colgroup':\n            # A colgroup element's end tag may be omitted if the colgroup\n            # element is not immediately followed by a space character or\n            # a comment.\n            if type in (\"Comment\", \"SpaceCharacters\"):\n                return False\n            elif type == \"StartTag\":\n                # XXX: we also look for an immediately following colgroup\n                # element. See is_optional_start.\n                return next[\"name\"] != 'colgroup'\n            else:\n                return True\n        elif tagname in ('thead', 'tbody'):\n            # A thead element's end tag may be omitted if the thead element\n            # is immediately followed by a tbody or tfoot element.\n            # A tbody element's end tag may be omitted if the tbody element\n            # is immediately followed by a tbody or tfoot element, or if\n            # there is no more content in the parent element.\n            # A tfoot element's end tag may be omitted if the tfoot element\n            # is immediately followed by a tbody element, or if there is no\n            # more content in the parent element.\n            # XXX: we never omit the end tag when the following element is\n            # a tbody. See is_optional_start.\n            if type == \"StartTag\":\n                return next[\"name\"] in ['tbody', 'tfoot']\n            elif tagname == 'tbody':\n                return type == \"EndTag\" or type is None\n            else:\n                return False\n        elif tagname == 'tfoot':\n            # A tfoot element's end tag may be omitted if the tfoot element\n            # is immediately followed by a tbody element, or if there is no\n            # more content in the parent element.\n            # XXX: we never omit the end tag when the following element is\n            # a tbody. See is_optional_start.\n            if type == \"StartTag\":\n                return next[\"name\"] == 'tbody'\n            else:\n                return type == \"EndTag\" or type is None\n        elif tagname in ('td', 'th'):\n            # A td element's end tag may be omitted if the td element is\n            # immediately followed by a td or th element, or if there is\n            # no more content in the parent element.\n            # A th element's end tag may be omitted if the th element is\n            # immediately followed by a td or th element, or if there is\n            # no more content in the parent element.\n            if type == \"StartTag\":\n                return next[\"name\"] in ('td', 'th')\n            else:\n                return type == \"EndTag\" or type is None\n        return False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/filters/sanitizer.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nimport re\nfrom xml.sax.saxutils import escape, unescape\n\nfrom pip._vendor.six.moves import urllib_parse as urlparse\n\nfrom . import base\nfrom ..constants import namespaces, prefixes\n\n__all__ = [\"Filter\"]\n\n\nallowed_elements = frozenset((\n    (namespaces['html'], 'a'),\n    (namespaces['html'], 'abbr'),\n    (namespaces['html'], 'acronym'),\n    (namespaces['html'], 'address'),\n    (namespaces['html'], 'area'),\n    (namespaces['html'], 'article'),\n    (namespaces['html'], 'aside'),\n    (namespaces['html'], 'audio'),\n    (namespaces['html'], 'b'),\n    (namespaces['html'], 'big'),\n    (namespaces['html'], 'blockquote'),\n    (namespaces['html'], 'br'),\n    (namespaces['html'], 'button'),\n    (namespaces['html'], 'canvas'),\n    (namespaces['html'], 'caption'),\n    (namespaces['html'], 'center'),\n    (namespaces['html'], 'cite'),\n    (namespaces['html'], 'code'),\n    (namespaces['html'], 'col'),\n    (namespaces['html'], 'colgroup'),\n    (namespaces['html'], 'command'),\n    (namespaces['html'], 'datagrid'),\n    (namespaces['html'], 'datalist'),\n    (namespaces['html'], 'dd'),\n    (namespaces['html'], 'del'),\n    (namespaces['html'], 'details'),\n    (namespaces['html'], 'dfn'),\n    (namespaces['html'], 'dialog'),\n    (namespaces['html'], 'dir'),\n    (namespaces['html'], 'div'),\n    (namespaces['html'], 'dl'),\n    (namespaces['html'], 'dt'),\n    (namespaces['html'], 'em'),\n    (namespaces['html'], 'event-source'),\n    (namespaces['html'], 'fieldset'),\n    (namespaces['html'], 'figcaption'),\n    (namespaces['html'], 'figure'),\n    (namespaces['html'], 'footer'),\n    (namespaces['html'], 'font'),\n    (namespaces['html'], 'form'),\n    (namespaces['html'], 'header'),\n    (namespaces['html'], 'h1'),\n    (namespaces['html'], 'h2'),\n    (namespaces['html'], 'h3'),\n    (namespaces['html'], 'h4'),\n    (namespaces['html'], 'h5'),\n    (namespaces['html'], 'h6'),\n    (namespaces['html'], 'hr'),\n    (namespaces['html'], 'i'),\n    (namespaces['html'], 'img'),\n    (namespaces['html'], 'input'),\n    (namespaces['html'], 'ins'),\n    (namespaces['html'], 'keygen'),\n    (namespaces['html'], 'kbd'),\n    (namespaces['html'], 'label'),\n    (namespaces['html'], 'legend'),\n    (namespaces['html'], 'li'),\n    (namespaces['html'], 'm'),\n    (namespaces['html'], 'map'),\n    (namespaces['html'], 'menu'),\n    (namespaces['html'], 'meter'),\n    (namespaces['html'], 'multicol'),\n    (namespaces['html'], 'nav'),\n    (namespaces['html'], 'nextid'),\n    (namespaces['html'], 'ol'),\n    (namespaces['html'], 'output'),\n    (namespaces['html'], 'optgroup'),\n    (namespaces['html'], 'option'),\n    (namespaces['html'], 'p'),\n    (namespaces['html'], 'pre'),\n    (namespaces['html'], 'progress'),\n    (namespaces['html'], 'q'),\n    (namespaces['html'], 's'),\n    (namespaces['html'], 'samp'),\n    (namespaces['html'], 'section'),\n    (namespaces['html'], 'select'),\n    (namespaces['html'], 'small'),\n    (namespaces['html'], 'sound'),\n    (namespaces['html'], 'source'),\n    (namespaces['html'], 'spacer'),\n    (namespaces['html'], 'span'),\n    (namespaces['html'], 'strike'),\n    (namespaces['html'], 'strong'),\n    (namespaces['html'], 'sub'),\n    (namespaces['html'], 'sup'),\n    (namespaces['html'], 'table'),\n    (namespaces['html'], 'tbody'),\n    (namespaces['html'], 'td'),\n    (namespaces['html'], 'textarea'),\n    (namespaces['html'], 'time'),\n    (namespaces['html'], 'tfoot'),\n    (namespaces['html'], 'th'),\n    (namespaces['html'], 'thead'),\n    (namespaces['html'], 'tr'),\n    (namespaces['html'], 'tt'),\n    (namespaces['html'], 'u'),\n    (namespaces['html'], 'ul'),\n    (namespaces['html'], 'var'),\n    (namespaces['html'], 'video'),\n    (namespaces['mathml'], 'maction'),\n    (namespaces['mathml'], 'math'),\n    (namespaces['mathml'], 'merror'),\n    (namespaces['mathml'], 'mfrac'),\n    (namespaces['mathml'], 'mi'),\n    (namespaces['mathml'], 'mmultiscripts'),\n    (namespaces['mathml'], 'mn'),\n    (namespaces['mathml'], 'mo'),\n    (namespaces['mathml'], 'mover'),\n    (namespaces['mathml'], 'mpadded'),\n    (namespaces['mathml'], 'mphantom'),\n    (namespaces['mathml'], 'mprescripts'),\n    (namespaces['mathml'], 'mroot'),\n    (namespaces['mathml'], 'mrow'),\n    (namespaces['mathml'], 'mspace'),\n    (namespaces['mathml'], 'msqrt'),\n    (namespaces['mathml'], 'mstyle'),\n    (namespaces['mathml'], 'msub'),\n    (namespaces['mathml'], 'msubsup'),\n    (namespaces['mathml'], 'msup'),\n    (namespaces['mathml'], 'mtable'),\n    (namespaces['mathml'], 'mtd'),\n    (namespaces['mathml'], 'mtext'),\n    (namespaces['mathml'], 'mtr'),\n    (namespaces['mathml'], 'munder'),\n    (namespaces['mathml'], 'munderover'),\n    (namespaces['mathml'], 'none'),\n    (namespaces['svg'], 'a'),\n    (namespaces['svg'], 'animate'),\n    (namespaces['svg'], 'animateColor'),\n    (namespaces['svg'], 'animateMotion'),\n    (namespaces['svg'], 'animateTransform'),\n    (namespaces['svg'], 'clipPath'),\n    (namespaces['svg'], 'circle'),\n    (namespaces['svg'], 'defs'),\n    (namespaces['svg'], 'desc'),\n    (namespaces['svg'], 'ellipse'),\n    (namespaces['svg'], 'font-face'),\n    (namespaces['svg'], 'font-face-name'),\n    (namespaces['svg'], 'font-face-src'),\n    (namespaces['svg'], 'g'),\n    (namespaces['svg'], 'glyph'),\n    (namespaces['svg'], 'hkern'),\n    (namespaces['svg'], 'linearGradient'),\n    (namespaces['svg'], 'line'),\n    (namespaces['svg'], 'marker'),\n    (namespaces['svg'], 'metadata'),\n    (namespaces['svg'], 'missing-glyph'),\n    (namespaces['svg'], 'mpath'),\n    (namespaces['svg'], 'path'),\n    (namespaces['svg'], 'polygon'),\n    (namespaces['svg'], 'polyline'),\n    (namespaces['svg'], 'radialGradient'),\n    (namespaces['svg'], 'rect'),\n    (namespaces['svg'], 'set'),\n    (namespaces['svg'], 'stop'),\n    (namespaces['svg'], 'svg'),\n    (namespaces['svg'], 'switch'),\n    (namespaces['svg'], 'text'),\n    (namespaces['svg'], 'title'),\n    (namespaces['svg'], 'tspan'),\n    (namespaces['svg'], 'use'),\n))\n\nallowed_attributes = frozenset((\n    # HTML attributes\n    (None, 'abbr'),\n    (None, 'accept'),\n    (None, 'accept-charset'),\n    (None, 'accesskey'),\n    (None, 'action'),\n    (None, 'align'),\n    (None, 'alt'),\n    (None, 'autocomplete'),\n    (None, 'autofocus'),\n    (None, 'axis'),\n    (None, 'background'),\n    (None, 'balance'),\n    (None, 'bgcolor'),\n    (None, 'bgproperties'),\n    (None, 'border'),\n    (None, 'bordercolor'),\n    (None, 'bordercolordark'),\n    (None, 'bordercolorlight'),\n    (None, 'bottompadding'),\n    (None, 'cellpadding'),\n    (None, 'cellspacing'),\n    (None, 'ch'),\n    (None, 'challenge'),\n    (None, 'char'),\n    (None, 'charoff'),\n    (None, 'choff'),\n    (None, 'charset'),\n    (None, 'checked'),\n    (None, 'cite'),\n    (None, 'class'),\n    (None, 'clear'),\n    (None, 'color'),\n    (None, 'cols'),\n    (None, 'colspan'),\n    (None, 'compact'),\n    (None, 'contenteditable'),\n    (None, 'controls'),\n    (None, 'coords'),\n    (None, 'data'),\n    (None, 'datafld'),\n    (None, 'datapagesize'),\n    (None, 'datasrc'),\n    (None, 'datetime'),\n    (None, 'default'),\n    (None, 'delay'),\n    (None, 'dir'),\n    (None, 'disabled'),\n    (None, 'draggable'),\n    (None, 'dynsrc'),\n    (None, 'enctype'),\n    (None, 'end'),\n    (None, 'face'),\n    (None, 'for'),\n    (None, 'form'),\n    (None, 'frame'),\n    (None, 'galleryimg'),\n    (None, 'gutter'),\n    (None, 'headers'),\n    (None, 'height'),\n    (None, 'hidefocus'),\n    (None, 'hidden'),\n    (None, 'high'),\n    (None, 'href'),\n    (None, 'hreflang'),\n    (None, 'hspace'),\n    (None, 'icon'),\n    (None, 'id'),\n    (None, 'inputmode'),\n    (None, 'ismap'),\n    (None, 'keytype'),\n    (None, 'label'),\n    (None, 'leftspacing'),\n    (None, 'lang'),\n    (None, 'list'),\n    (None, 'longdesc'),\n    (None, 'loop'),\n    (None, 'loopcount'),\n    (None, 'loopend'),\n    (None, 'loopstart'),\n    (None, 'low'),\n    (None, 'lowsrc'),\n    (None, 'max'),\n    (None, 'maxlength'),\n    (None, 'media'),\n    (None, 'method'),\n    (None, 'min'),\n    (None, 'multiple'),\n    (None, 'name'),\n    (None, 'nohref'),\n    (None, 'noshade'),\n    (None, 'nowrap'),\n    (None, 'open'),\n    (None, 'optimum'),\n    (None, 'pattern'),\n    (None, 'ping'),\n    (None, 'point-size'),\n    (None, 'poster'),\n    (None, 'pqg'),\n    (None, 'preload'),\n    (None, 'prompt'),\n    (None, 'radiogroup'),\n    (None, 'readonly'),\n    (None, 'rel'),\n    (None, 'repeat-max'),\n    (None, 'repeat-min'),\n    (None, 'replace'),\n    (None, 'required'),\n    (None, 'rev'),\n    (None, 'rightspacing'),\n    (None, 'rows'),\n    (None, 'rowspan'),\n    (None, 'rules'),\n    (None, 'scope'),\n    (None, 'selected'),\n    (None, 'shape'),\n    (None, 'size'),\n    (None, 'span'),\n    (None, 'src'),\n    (None, 'start'),\n    (None, 'step'),\n    (None, 'style'),\n    (None, 'summary'),\n    (None, 'suppress'),\n    (None, 'tabindex'),\n    (None, 'target'),\n    (None, 'template'),\n    (None, 'title'),\n    (None, 'toppadding'),\n    (None, 'type'),\n    (None, 'unselectable'),\n    (None, 'usemap'),\n    (None, 'urn'),\n    (None, 'valign'),\n    (None, 'value'),\n    (None, 'variable'),\n    (None, 'volume'),\n    (None, 'vspace'),\n    (None, 'vrml'),\n    (None, 'width'),\n    (None, 'wrap'),\n    (namespaces['xml'], 'lang'),\n    # MathML attributes\n    (None, 'actiontype'),\n    (None, 'align'),\n    (None, 'columnalign'),\n    (None, 'columnalign'),\n    (None, 'columnalign'),\n    (None, 'columnlines'),\n    (None, 'columnspacing'),\n    (None, 'columnspan'),\n    (None, 'depth'),\n    (None, 'display'),\n    (None, 'displaystyle'),\n    (None, 'equalcolumns'),\n    (None, 'equalrows'),\n    (None, 'fence'),\n    (None, 'fontstyle'),\n    (None, 'fontweight'),\n    (None, 'frame'),\n    (None, 'height'),\n    (None, 'linethickness'),\n    (None, 'lspace'),\n    (None, 'mathbackground'),\n    (None, 'mathcolor'),\n    (None, 'mathvariant'),\n    (None, 'mathvariant'),\n    (None, 'maxsize'),\n    (None, 'minsize'),\n    (None, 'other'),\n    (None, 'rowalign'),\n    (None, 'rowalign'),\n    (None, 'rowalign'),\n    (None, 'rowlines'),\n    (None, 'rowspacing'),\n    (None, 'rowspan'),\n    (None, 'rspace'),\n    (None, 'scriptlevel'),\n    (None, 'selection'),\n    (None, 'separator'),\n    (None, 'stretchy'),\n    (None, 'width'),\n    (None, 'width'),\n    (namespaces['xlink'], 'href'),\n    (namespaces['xlink'], 'show'),\n    (namespaces['xlink'], 'type'),\n    # SVG attributes\n    (None, 'accent-height'),\n    (None, 'accumulate'),\n    (None, 'additive'),\n    (None, 'alphabetic'),\n    (None, 'arabic-form'),\n    (None, 'ascent'),\n    (None, 'attributeName'),\n    (None, 'attributeType'),\n    (None, 'baseProfile'),\n    (None, 'bbox'),\n    (None, 'begin'),\n    (None, 'by'),\n    (None, 'calcMode'),\n    (None, 'cap-height'),\n    (None, 'class'),\n    (None, 'clip-path'),\n    (None, 'color'),\n    (None, 'color-rendering'),\n    (None, 'content'),\n    (None, 'cx'),\n    (None, 'cy'),\n    (None, 'd'),\n    (None, 'dx'),\n    (None, 'dy'),\n    (None, 'descent'),\n    (None, 'display'),\n    (None, 'dur'),\n    (None, 'end'),\n    (None, 'fill'),\n    (None, 'fill-opacity'),\n    (None, 'fill-rule'),\n    (None, 'font-family'),\n    (None, 'font-size'),\n    (None, 'font-stretch'),\n    (None, 'font-style'),\n    (None, 'font-variant'),\n    (None, 'font-weight'),\n    (None, 'from'),\n    (None, 'fx'),\n    (None, 'fy'),\n    (None, 'g1'),\n    (None, 'g2'),\n    (None, 'glyph-name'),\n    (None, 'gradientUnits'),\n    (None, 'hanging'),\n    (None, 'height'),\n    (None, 'horiz-adv-x'),\n    (None, 'horiz-origin-x'),\n    (None, 'id'),\n    (None, 'ideographic'),\n    (None, 'k'),\n    (None, 'keyPoints'),\n    (None, 'keySplines'),\n    (None, 'keyTimes'),\n    (None, 'lang'),\n    (None, 'marker-end'),\n    (None, 'marker-mid'),\n    (None, 'marker-start'),\n    (None, 'markerHeight'),\n    (None, 'markerUnits'),\n    (None, 'markerWidth'),\n    (None, 'mathematical'),\n    (None, 'max'),\n    (None, 'min'),\n    (None, 'name'),\n    (None, 'offset'),\n    (None, 'opacity'),\n    (None, 'orient'),\n    (None, 'origin'),\n    (None, 'overline-position'),\n    (None, 'overline-thickness'),\n    (None, 'panose-1'),\n    (None, 'path'),\n    (None, 'pathLength'),\n    (None, 'points'),\n    (None, 'preserveAspectRatio'),\n    (None, 'r'),\n    (None, 'refX'),\n    (None, 'refY'),\n    (None, 'repeatCount'),\n    (None, 'repeatDur'),\n    (None, 'requiredExtensions'),\n    (None, 'requiredFeatures'),\n    (None, 'restart'),\n    (None, 'rotate'),\n    (None, 'rx'),\n    (None, 'ry'),\n    (None, 'slope'),\n    (None, 'stemh'),\n    (None, 'stemv'),\n    (None, 'stop-color'),\n    (None, 'stop-opacity'),\n    (None, 'strikethrough-position'),\n    (None, 'strikethrough-thickness'),\n    (None, 'stroke'),\n    (None, 'stroke-dasharray'),\n    (None, 'stroke-dashoffset'),\n    (None, 'stroke-linecap'),\n    (None, 'stroke-linejoin'),\n    (None, 'stroke-miterlimit'),\n    (None, 'stroke-opacity'),\n    (None, 'stroke-width'),\n    (None, 'systemLanguage'),\n    (None, 'target'),\n    (None, 'text-anchor'),\n    (None, 'to'),\n    (None, 'transform'),\n    (None, 'type'),\n    (None, 'u1'),\n    (None, 'u2'),\n    (None, 'underline-position'),\n    (None, 'underline-thickness'),\n    (None, 'unicode'),\n    (None, 'unicode-range'),\n    (None, 'units-per-em'),\n    (None, 'values'),\n    (None, 'version'),\n    (None, 'viewBox'),\n    (None, 'visibility'),\n    (None, 'width'),\n    (None, 'widths'),\n    (None, 'x'),\n    (None, 'x-height'),\n    (None, 'x1'),\n    (None, 'x2'),\n    (namespaces['xlink'], 'actuate'),\n    (namespaces['xlink'], 'arcrole'),\n    (namespaces['xlink'], 'href'),\n    (namespaces['xlink'], 'role'),\n    (namespaces['xlink'], 'show'),\n    (namespaces['xlink'], 'title'),\n    (namespaces['xlink'], 'type'),\n    (namespaces['xml'], 'base'),\n    (namespaces['xml'], 'lang'),\n    (namespaces['xml'], 'space'),\n    (None, 'y'),\n    (None, 'y1'),\n    (None, 'y2'),\n    (None, 'zoomAndPan'),\n))\n\nattr_val_is_uri = frozenset((\n    (None, 'href'),\n    (None, 'src'),\n    (None, 'cite'),\n    (None, 'action'),\n    (None, 'longdesc'),\n    (None, 'poster'),\n    (None, 'background'),\n    (None, 'datasrc'),\n    (None, 'dynsrc'),\n    (None, 'lowsrc'),\n    (None, 'ping'),\n    (namespaces['xlink'], 'href'),\n    (namespaces['xml'], 'base'),\n))\n\nsvg_attr_val_allows_ref = frozenset((\n    (None, 'clip-path'),\n    (None, 'color-profile'),\n    (None, 'cursor'),\n    (None, 'fill'),\n    (None, 'filter'),\n    (None, 'marker'),\n    (None, 'marker-start'),\n    (None, 'marker-mid'),\n    (None, 'marker-end'),\n    (None, 'mask'),\n    (None, 'stroke'),\n))\n\nsvg_allow_local_href = frozenset((\n    (None, 'altGlyph'),\n    (None, 'animate'),\n    (None, 'animateColor'),\n    (None, 'animateMotion'),\n    (None, 'animateTransform'),\n    (None, 'cursor'),\n    (None, 'feImage'),\n    (None, 'filter'),\n    (None, 'linearGradient'),\n    (None, 'pattern'),\n    (None, 'radialGradient'),\n    (None, 'textpath'),\n    (None, 'tref'),\n    (None, 'set'),\n    (None, 'use')\n))\n\nallowed_css_properties = frozenset((\n    'azimuth',\n    'background-color',\n    'border-bottom-color',\n    'border-collapse',\n    'border-color',\n    'border-left-color',\n    'border-right-color',\n    'border-top-color',\n    'clear',\n    'color',\n    'cursor',\n    'direction',\n    'display',\n    'elevation',\n    'float',\n    'font',\n    'font-family',\n    'font-size',\n    'font-style',\n    'font-variant',\n    'font-weight',\n    'height',\n    'letter-spacing',\n    'line-height',\n    'overflow',\n    'pause',\n    'pause-after',\n    'pause-before',\n    'pitch',\n    'pitch-range',\n    'richness',\n    'speak',\n    'speak-header',\n    'speak-numeral',\n    'speak-punctuation',\n    'speech-rate',\n    'stress',\n    'text-align',\n    'text-decoration',\n    'text-indent',\n    'unicode-bidi',\n    'vertical-align',\n    'voice-family',\n    'volume',\n    'white-space',\n    'width',\n))\n\nallowed_css_keywords = frozenset((\n    'auto',\n    'aqua',\n    'black',\n    'block',\n    'blue',\n    'bold',\n    'both',\n    'bottom',\n    'brown',\n    'center',\n    'collapse',\n    'dashed',\n    'dotted',\n    'fuchsia',\n    'gray',\n    'green',\n    '!important',\n    'italic',\n    'left',\n    'lime',\n    'maroon',\n    'medium',\n    'none',\n    'navy',\n    'normal',\n    'nowrap',\n    'olive',\n    'pointer',\n    'purple',\n    'red',\n    'right',\n    'solid',\n    'silver',\n    'teal',\n    'top',\n    'transparent',\n    'underline',\n    'white',\n    'yellow',\n))\n\nallowed_svg_properties = frozenset((\n    'fill',\n    'fill-opacity',\n    'fill-rule',\n    'stroke',\n    'stroke-width',\n    'stroke-linecap',\n    'stroke-linejoin',\n    'stroke-opacity',\n))\n\nallowed_protocols = frozenset((\n    'ed2k',\n    'ftp',\n    'http',\n    'https',\n    'irc',\n    'mailto',\n    'news',\n    'gopher',\n    'nntp',\n    'telnet',\n    'webcal',\n    'xmpp',\n    'callto',\n    'feed',\n    'urn',\n    'aim',\n    'rsync',\n    'tag',\n    'ssh',\n    'sftp',\n    'rtsp',\n    'afs',\n    'data',\n))\n\nallowed_content_types = frozenset((\n    'image/png',\n    'image/jpeg',\n    'image/gif',\n    'image/webp',\n    'image/bmp',\n    'text/plain',\n))\n\n\ndata_content_type = re.compile(r'''\n                                ^\n                                # Match a content type <application>/<type>\n                                (?P<content_type>[-a-zA-Z0-9.]+/[-a-zA-Z0-9.]+)\n                                # Match any character set and encoding\n                                (?:(?:;charset=(?:[-a-zA-Z0-9]+)(?:;(?:base64))?)\n                                  |(?:;(?:base64))?(?:;charset=(?:[-a-zA-Z0-9]+))?)\n                                # Assume the rest is data\n                                ,.*\n                                $\n                                ''',\n                               re.VERBOSE)\n\n\nclass Filter(base.Filter):\n    \"\"\"Sanitizes token stream of XHTML+MathML+SVG and of inline style attributes\"\"\"\n    def __init__(self,\n                 source,\n                 allowed_elements=allowed_elements,\n                 allowed_attributes=allowed_attributes,\n                 allowed_css_properties=allowed_css_properties,\n                 allowed_css_keywords=allowed_css_keywords,\n                 allowed_svg_properties=allowed_svg_properties,\n                 allowed_protocols=allowed_protocols,\n                 allowed_content_types=allowed_content_types,\n                 attr_val_is_uri=attr_val_is_uri,\n                 svg_attr_val_allows_ref=svg_attr_val_allows_ref,\n                 svg_allow_local_href=svg_allow_local_href):\n        \"\"\"Creates a Filter\n\n        :arg allowed_elements: set of elements to allow--everything else will\n            be escaped\n\n        :arg allowed_attributes: set of attributes to allow in\n            elements--everything else will be stripped\n\n        :arg allowed_css_properties: set of CSS properties to allow--everything\n            else will be stripped\n\n        :arg allowed_css_keywords: set of CSS keywords to allow--everything\n            else will be stripped\n\n        :arg allowed_svg_properties: set of SVG properties to allow--everything\n            else will be removed\n\n        :arg allowed_protocols: set of allowed protocols for URIs\n\n        :arg allowed_content_types: set of allowed content types for ``data`` URIs.\n\n        :arg attr_val_is_uri: set of attributes that have URI values--values\n            that have a scheme not listed in ``allowed_protocols`` are removed\n\n        :arg svg_attr_val_allows_ref: set of SVG attributes that can have\n            references\n\n        :arg svg_allow_local_href: set of SVG elements that can have local\n            hrefs--these are removed\n\n        \"\"\"\n        super(Filter, self).__init__(source)\n        self.allowed_elements = allowed_elements\n        self.allowed_attributes = allowed_attributes\n        self.allowed_css_properties = allowed_css_properties\n        self.allowed_css_keywords = allowed_css_keywords\n        self.allowed_svg_properties = allowed_svg_properties\n        self.allowed_protocols = allowed_protocols\n        self.allowed_content_types = allowed_content_types\n        self.attr_val_is_uri = attr_val_is_uri\n        self.svg_attr_val_allows_ref = svg_attr_val_allows_ref\n        self.svg_allow_local_href = svg_allow_local_href\n\n    def __iter__(self):\n        for token in base.Filter.__iter__(self):\n            token = self.sanitize_token(token)\n            if token:\n                yield token\n\n    # Sanitize the +html+, escaping all elements not in ALLOWED_ELEMENTS, and\n    # stripping out all attributes not in ALLOWED_ATTRIBUTES. Style attributes\n    # are parsed, and a restricted set, specified by ALLOWED_CSS_PROPERTIES and\n    # ALLOWED_CSS_KEYWORDS, are allowed through. attributes in ATTR_VAL_IS_URI\n    # are scanned, and only URI schemes specified in ALLOWED_PROTOCOLS are\n    # allowed.\n    #\n    #   sanitize_html('<script> do_nasty_stuff() </script>')\n    #    => &lt;script> do_nasty_stuff() &lt;/script>\n    #   sanitize_html('<a href=\"javascript: sucker();\">Click here for $100</a>')\n    #    => <a>Click here for $100</a>\n    def sanitize_token(self, token):\n\n        # accommodate filters which use token_type differently\n        token_type = token[\"type\"]\n        if token_type in (\"StartTag\", \"EndTag\", \"EmptyTag\"):\n            name = token[\"name\"]\n            namespace = token[\"namespace\"]\n            if ((namespace, name) in self.allowed_elements or\n                (namespace is None and\n                 (namespaces[\"html\"], name) in self.allowed_elements)):\n                return self.allowed_token(token)\n            else:\n                return self.disallowed_token(token)\n        elif token_type == \"Comment\":\n            pass\n        else:\n            return token\n\n    def allowed_token(self, token):\n        if \"data\" in token:\n            attrs = token[\"data\"]\n            attr_names = set(attrs.keys())\n\n            # Remove forbidden attributes\n            for to_remove in (attr_names - self.allowed_attributes):\n                del token[\"data\"][to_remove]\n                attr_names.remove(to_remove)\n\n            # Remove attributes with disallowed URL values\n            for attr in (attr_names & self.attr_val_is_uri):\n                assert attr in attrs\n                # I don't have a clue where this regexp comes from or why it matches those\n                # characters, nor why we call unescape. I just know it's always been here.\n                # Should you be worried by this comment in a sanitizer? Yes. On the other hand, all\n                # this will do is remove *more* than it otherwise would.\n                val_unescaped = re.sub(\"[`\\x00-\\x20\\x7f-\\xa0\\\\s]+\", '',\n                                       unescape(attrs[attr])).lower()\n                # remove replacement characters from unescaped characters\n                val_unescaped = val_unescaped.replace(\"\\ufffd\", \"\")\n                try:\n                    uri = urlparse.urlparse(val_unescaped)\n                except ValueError:\n                    uri = None\n                    del attrs[attr]\n                if uri and uri.scheme:\n                    if uri.scheme not in self.allowed_protocols:\n                        del attrs[attr]\n                    if uri.scheme == 'data':\n                        m = data_content_type.match(uri.path)\n                        if not m:\n                            del attrs[attr]\n                        elif m.group('content_type') not in self.allowed_content_types:\n                            del attrs[attr]\n\n            for attr in self.svg_attr_val_allows_ref:\n                if attr in attrs:\n                    attrs[attr] = re.sub(r'url\\s*\\(\\s*[^#\\s][^)]+?\\)',\n                                         ' ',\n                                         unescape(attrs[attr]))\n            if (token[\"name\"] in self.svg_allow_local_href and\n                (namespaces['xlink'], 'href') in attrs and re.search(r'^\\s*[^#\\s].*',\n                                                                     attrs[(namespaces['xlink'], 'href')])):\n                del attrs[(namespaces['xlink'], 'href')]\n            if (None, 'style') in attrs:\n                attrs[(None, 'style')] = self.sanitize_css(attrs[(None, 'style')])\n            token[\"data\"] = attrs\n        return token\n\n    def disallowed_token(self, token):\n        token_type = token[\"type\"]\n        if token_type == \"EndTag\":\n            token[\"data\"] = \"</%s>\" % token[\"name\"]\n        elif token[\"data\"]:\n            assert token_type in (\"StartTag\", \"EmptyTag\")\n            attrs = []\n            for (ns, name), v in token[\"data\"].items():\n                attrs.append(' %s=\"%s\"' % (name if ns is None else \"%s:%s\" % (prefixes[ns], name), escape(v)))\n            token[\"data\"] = \"<%s%s>\" % (token[\"name\"], ''.join(attrs))\n        else:\n            token[\"data\"] = \"<%s>\" % token[\"name\"]\n        if token.get(\"selfClosing\"):\n            token[\"data\"] = token[\"data\"][:-1] + \"/>\"\n\n        token[\"type\"] = \"Characters\"\n\n        del token[\"name\"]\n        return token\n\n    def sanitize_css(self, style):\n        # disallow urls\n        style = re.compile(r'url\\s*\\(\\s*[^\\s)]+?\\s*\\)\\s*').sub(' ', style)\n\n        # gauntlet\n        if not re.match(r\"\"\"^([:,;#%.\\sa-zA-Z0-9!]|\\w-\\w|'[\\s\\w]+'|\"[\\s\\w]+\"|\\([\\d,\\s]+\\))*$\"\"\", style):\n            return ''\n        if not re.match(r\"^\\s*([-\\w]+\\s*:[^:;]*(;\\s*|$))*$\", style):\n            return ''\n\n        clean = []\n        for prop, value in re.findall(r\"([-\\w]+)\\s*:\\s*([^:;]*)\", style):\n            if not value:\n                continue\n            if prop.lower() in self.allowed_css_properties:\n                clean.append(prop + ': ' + value + ';')\n            elif prop.split('-')[0].lower() in ['background', 'border', 'margin',\n                                                'padding']:\n                for keyword in value.split():\n                    if keyword not in self.allowed_css_keywords and \\\n                            not re.match(r\"^(#[0-9a-fA-F]+|rgb\\(\\d+%?,\\d*%?,?\\d*%?\\)?|\\d{0,2}\\.?\\d{0,2}(cm|em|ex|in|mm|pc|pt|px|%|,|\\))?)$\", keyword):  # noqa\n                        break\n                else:\n                    clean.append(prop + ': ' + value + ';')\n            elif prop.lower() in self.allowed_svg_properties:\n                clean.append(prop + ': ' + value + ';')\n\n        return ' '.join(clean)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/filters/whitespace.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nimport re\n\nfrom . import base\nfrom ..constants import rcdataElements, spaceCharacters\nspaceCharacters = \"\".join(spaceCharacters)\n\nSPACES_REGEX = re.compile(\"[%s]+\" % spaceCharacters)\n\n\nclass Filter(base.Filter):\n    \"\"\"Collapses whitespace except in pre, textarea, and script elements\"\"\"\n    spacePreserveElements = frozenset([\"pre\", \"textarea\"] + list(rcdataElements))\n\n    def __iter__(self):\n        preserve = 0\n        for token in base.Filter.__iter__(self):\n            type = token[\"type\"]\n            if type == \"StartTag\" \\\n                    and (preserve or token[\"name\"] in self.spacePreserveElements):\n                preserve += 1\n\n            elif type == \"EndTag\" and preserve:\n                preserve -= 1\n\n            elif not preserve and type == \"SpaceCharacters\" and token[\"data\"]:\n                # Test on token[\"data\"] above to not introduce spaces where there were not\n                token[\"data\"] = \" \"\n\n            elif not preserve and type == \"Characters\":\n                token[\"data\"] = collapse_spaces(token[\"data\"])\n\n            yield token\n\n\ndef collapse_spaces(text):\n    return SPACES_REGEX.sub(' ', text)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/html5parser.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\nfrom pip._vendor.six import with_metaclass, viewkeys\n\nimport types\nfrom collections import OrderedDict\n\nfrom . import _inputstream\nfrom . import _tokenizer\n\nfrom . import treebuilders\nfrom .treebuilders.base import Marker\n\nfrom . import _utils\nfrom .constants import (\n    spaceCharacters, asciiUpper2Lower,\n    specialElements, headingElements, cdataElements, rcdataElements,\n    tokenTypes, tagTokenTypes,\n    namespaces,\n    htmlIntegrationPointElements, mathmlTextIntegrationPointElements,\n    adjustForeignAttributes as adjustForeignAttributesMap,\n    adjustMathMLAttributes, adjustSVGAttributes,\n    E,\n    _ReparseException\n)\n\n\ndef parse(doc, treebuilder=\"etree\", namespaceHTMLElements=True, **kwargs):\n    \"\"\"Parse an HTML document as a string or file-like object into a tree\n\n    :arg doc: the document to parse as a string or file-like object\n\n    :arg treebuilder: the treebuilder to use when parsing\n\n    :arg namespaceHTMLElements: whether or not to namespace HTML elements\n\n    :returns: parsed tree\n\n    Example:\n\n    >>> from html5lib.html5parser import parse\n    >>> parse('<html><body><p>This is a doc</p></body></html>')\n    <Element u'{http://www.w3.org/1999/xhtml}html' at 0x7feac4909db0>\n\n    \"\"\"\n    tb = treebuilders.getTreeBuilder(treebuilder)\n    p = HTMLParser(tb, namespaceHTMLElements=namespaceHTMLElements)\n    return p.parse(doc, **kwargs)\n\n\ndef parseFragment(doc, container=\"div\", treebuilder=\"etree\", namespaceHTMLElements=True, **kwargs):\n    \"\"\"Parse an HTML fragment as a string or file-like object into a tree\n\n    :arg doc: the fragment to parse as a string or file-like object\n\n    :arg container: the container context to parse the fragment in\n\n    :arg treebuilder: the treebuilder to use when parsing\n\n    :arg namespaceHTMLElements: whether or not to namespace HTML elements\n\n    :returns: parsed tree\n\n    Example:\n\n    >>> from html5lib.html5libparser import parseFragment\n    >>> parseFragment('<b>this is a fragment</b>')\n    <Element u'DOCUMENT_FRAGMENT' at 0x7feac484b090>\n\n    \"\"\"\n    tb = treebuilders.getTreeBuilder(treebuilder)\n    p = HTMLParser(tb, namespaceHTMLElements=namespaceHTMLElements)\n    return p.parseFragment(doc, container=container, **kwargs)\n\n\ndef method_decorator_metaclass(function):\n    class Decorated(type):\n        def __new__(meta, classname, bases, classDict):\n            for attributeName, attribute in classDict.items():\n                if isinstance(attribute, types.FunctionType):\n                    attribute = function(attribute)\n\n                classDict[attributeName] = attribute\n            return type.__new__(meta, classname, bases, classDict)\n    return Decorated\n\n\nclass HTMLParser(object):\n    \"\"\"HTML parser\n\n    Generates a tree structure from a stream of (possibly malformed) HTML.\n\n    \"\"\"\n\n    def __init__(self, tree=None, strict=False, namespaceHTMLElements=True, debug=False):\n        \"\"\"\n        :arg tree: a treebuilder class controlling the type of tree that will be\n            returned. Built in treebuilders can be accessed through\n            html5lib.treebuilders.getTreeBuilder(treeType)\n\n        :arg strict: raise an exception when a parse error is encountered\n\n        :arg namespaceHTMLElements: whether or not to namespace HTML elements\n\n        :arg debug: whether or not to enable debug mode which logs things\n\n        Example:\n\n        >>> from html5lib.html5parser import HTMLParser\n        >>> parser = HTMLParser()                     # generates parser with etree builder\n        >>> parser = HTMLParser('lxml', strict=True)  # generates parser with lxml builder which is strict\n\n        \"\"\"\n\n        # Raise an exception on the first error encountered\n        self.strict = strict\n\n        if tree is None:\n            tree = treebuilders.getTreeBuilder(\"etree\")\n        self.tree = tree(namespaceHTMLElements)\n        self.errors = []\n\n        self.phases = dict([(name, cls(self, self.tree)) for name, cls in\n                            getPhases(debug).items()])\n\n    def _parse(self, stream, innerHTML=False, container=\"div\", scripting=False, **kwargs):\n\n        self.innerHTMLMode = innerHTML\n        self.container = container\n        self.scripting = scripting\n        self.tokenizer = _tokenizer.HTMLTokenizer(stream, parser=self, **kwargs)\n        self.reset()\n\n        try:\n            self.mainLoop()\n        except _ReparseException:\n            self.reset()\n            self.mainLoop()\n\n    def reset(self):\n        self.tree.reset()\n        self.firstStartTag = False\n        self.errors = []\n        self.log = []  # only used with debug mode\n        # \"quirks\" / \"limited quirks\" / \"no quirks\"\n        self.compatMode = \"no quirks\"\n\n        if self.innerHTMLMode:\n            self.innerHTML = self.container.lower()\n\n            if self.innerHTML in cdataElements:\n                self.tokenizer.state = self.tokenizer.rcdataState\n            elif self.innerHTML in rcdataElements:\n                self.tokenizer.state = self.tokenizer.rawtextState\n            elif self.innerHTML == 'plaintext':\n                self.tokenizer.state = self.tokenizer.plaintextState\n            else:\n                # state already is data state\n                # self.tokenizer.state = self.tokenizer.dataState\n                pass\n            self.phase = self.phases[\"beforeHtml\"]\n            self.phase.insertHtmlElement()\n            self.resetInsertionMode()\n        else:\n            self.innerHTML = False  # pylint:disable=redefined-variable-type\n            self.phase = self.phases[\"initial\"]\n\n        self.lastPhase = None\n\n        self.beforeRCDataPhase = None\n\n        self.framesetOK = True\n\n    @property\n    def documentEncoding(self):\n        \"\"\"Name of the character encoding that was used to decode the input stream, or\n        :obj:`None` if that is not determined yet\n\n        \"\"\"\n        if not hasattr(self, 'tokenizer'):\n            return None\n        return self.tokenizer.stream.charEncoding[0].name\n\n    def isHTMLIntegrationPoint(self, element):\n        if (element.name == \"annotation-xml\" and\n                element.namespace == namespaces[\"mathml\"]):\n            return (\"encoding\" in element.attributes and\n                    element.attributes[\"encoding\"].translate(\n                        asciiUpper2Lower) in\n                    (\"text/html\", \"application/xhtml+xml\"))\n        else:\n            return (element.namespace, element.name) in htmlIntegrationPointElements\n\n    def isMathMLTextIntegrationPoint(self, element):\n        return (element.namespace, element.name) in mathmlTextIntegrationPointElements\n\n    def mainLoop(self):\n        CharactersToken = tokenTypes[\"Characters\"]\n        SpaceCharactersToken = tokenTypes[\"SpaceCharacters\"]\n        StartTagToken = tokenTypes[\"StartTag\"]\n        EndTagToken = tokenTypes[\"EndTag\"]\n        CommentToken = tokenTypes[\"Comment\"]\n        DoctypeToken = tokenTypes[\"Doctype\"]\n        ParseErrorToken = tokenTypes[\"ParseError\"]\n\n        for token in self.normalizedTokens():\n            prev_token = None\n            new_token = token\n            while new_token is not None:\n                prev_token = new_token\n                currentNode = self.tree.openElements[-1] if self.tree.openElements else None\n                currentNodeNamespace = currentNode.namespace if currentNode else None\n                currentNodeName = currentNode.name if currentNode else None\n\n                type = new_token[\"type\"]\n\n                if type == ParseErrorToken:\n                    self.parseError(new_token[\"data\"], new_token.get(\"datavars\", {}))\n                    new_token = None\n                else:\n                    if (len(self.tree.openElements) == 0 or\n                        currentNodeNamespace == self.tree.defaultNamespace or\n                        (self.isMathMLTextIntegrationPoint(currentNode) and\n                         ((type == StartTagToken and\n                           token[\"name\"] not in frozenset([\"mglyph\", \"malignmark\"])) or\n                          type in (CharactersToken, SpaceCharactersToken))) or\n                        (currentNodeNamespace == namespaces[\"mathml\"] and\n                         currentNodeName == \"annotation-xml\" and\n                         type == StartTagToken and\n                         token[\"name\"] == \"svg\") or\n                        (self.isHTMLIntegrationPoint(currentNode) and\n                         type in (StartTagToken, CharactersToken, SpaceCharactersToken))):\n                        phase = self.phase\n                    else:\n                        phase = self.phases[\"inForeignContent\"]\n\n                    if type == CharactersToken:\n                        new_token = phase.processCharacters(new_token)\n                    elif type == SpaceCharactersToken:\n                        new_token = phase.processSpaceCharacters(new_token)\n                    elif type == StartTagToken:\n                        new_token = phase.processStartTag(new_token)\n                    elif type == EndTagToken:\n                        new_token = phase.processEndTag(new_token)\n                    elif type == CommentToken:\n                        new_token = phase.processComment(new_token)\n                    elif type == DoctypeToken:\n                        new_token = phase.processDoctype(new_token)\n\n            if (type == StartTagToken and prev_token[\"selfClosing\"] and\n                    not prev_token[\"selfClosingAcknowledged\"]):\n                self.parseError(\"non-void-element-with-trailing-solidus\",\n                                {\"name\": prev_token[\"name\"]})\n\n        # When the loop finishes it's EOF\n        reprocess = True\n        phases = []\n        while reprocess:\n            phases.append(self.phase)\n            reprocess = self.phase.processEOF()\n            if reprocess:\n                assert self.phase not in phases\n\n    def normalizedTokens(self):\n        for token in self.tokenizer:\n            yield self.normalizeToken(token)\n\n    def parse(self, stream, *args, **kwargs):\n        \"\"\"Parse a HTML document into a well-formed tree\n\n        :arg stream: a file-like object or string containing the HTML to be parsed\n\n            The optional encoding parameter must be a string that indicates\n            the encoding.  If specified, that encoding will be used,\n            regardless of any BOM or later declaration (such as in a meta\n            element).\n\n        :arg scripting: treat noscript elements as if JavaScript was turned on\n\n        :returns: parsed tree\n\n        Example:\n\n        >>> from html5lib.html5parser import HTMLParser\n        >>> parser = HTMLParser()\n        >>> parser.parse('<html><body><p>This is a doc</p></body></html>')\n        <Element u'{http://www.w3.org/1999/xhtml}html' at 0x7feac4909db0>\n\n        \"\"\"\n        self._parse(stream, False, None, *args, **kwargs)\n        return self.tree.getDocument()\n\n    def parseFragment(self, stream, *args, **kwargs):\n        \"\"\"Parse a HTML fragment into a well-formed tree fragment\n\n        :arg container: name of the element we're setting the innerHTML\n            property if set to None, default to 'div'\n\n        :arg stream: a file-like object or string containing the HTML to be parsed\n\n            The optional encoding parameter must be a string that indicates\n            the encoding.  If specified, that encoding will be used,\n            regardless of any BOM or later declaration (such as in a meta\n            element)\n\n        :arg scripting: treat noscript elements as if JavaScript was turned on\n\n        :returns: parsed tree\n\n        Example:\n\n        >>> from html5lib.html5libparser import HTMLParser\n        >>> parser = HTMLParser()\n        >>> parser.parseFragment('<b>this is a fragment</b>')\n        <Element u'DOCUMENT_FRAGMENT' at 0x7feac484b090>\n\n        \"\"\"\n        self._parse(stream, True, *args, **kwargs)\n        return self.tree.getFragment()\n\n    def parseError(self, errorcode=\"XXX-undefined-error\", datavars=None):\n        # XXX The idea is to make errorcode mandatory.\n        if datavars is None:\n            datavars = {}\n        self.errors.append((self.tokenizer.stream.position(), errorcode, datavars))\n        if self.strict:\n            raise ParseError(E[errorcode] % datavars)\n\n    def normalizeToken(self, token):\n        # HTML5 specific normalizations to the token stream\n        if token[\"type\"] == tokenTypes[\"StartTag\"]:\n            raw = token[\"data\"]\n            token[\"data\"] = OrderedDict(raw)\n            if len(raw) > len(token[\"data\"]):\n                # we had some duplicated attribute, fix so first wins\n                token[\"data\"].update(raw[::-1])\n\n        return token\n\n    def adjustMathMLAttributes(self, token):\n        adjust_attributes(token, adjustMathMLAttributes)\n\n    def adjustSVGAttributes(self, token):\n        adjust_attributes(token, adjustSVGAttributes)\n\n    def adjustForeignAttributes(self, token):\n        adjust_attributes(token, adjustForeignAttributesMap)\n\n    def reparseTokenNormal(self, token):\n        # pylint:disable=unused-argument\n        self.parser.phase()\n\n    def resetInsertionMode(self):\n        # The name of this method is mostly historical. (It's also used in the\n        # specification.)\n        last = False\n        newModes = {\n            \"select\": \"inSelect\",\n            \"td\": \"inCell\",\n            \"th\": \"inCell\",\n            \"tr\": \"inRow\",\n            \"tbody\": \"inTableBody\",\n            \"thead\": \"inTableBody\",\n            \"tfoot\": \"inTableBody\",\n            \"caption\": \"inCaption\",\n            \"colgroup\": \"inColumnGroup\",\n            \"table\": \"inTable\",\n            \"head\": \"inBody\",\n            \"body\": \"inBody\",\n            \"frameset\": \"inFrameset\",\n            \"html\": \"beforeHead\"\n        }\n        for node in self.tree.openElements[::-1]:\n            nodeName = node.name\n            new_phase = None\n            if node == self.tree.openElements[0]:\n                assert self.innerHTML\n                last = True\n                nodeName = self.innerHTML\n            # Check for conditions that should only happen in the innerHTML\n            # case\n            if nodeName in (\"select\", \"colgroup\", \"head\", \"html\"):\n                assert self.innerHTML\n\n            if not last and node.namespace != self.tree.defaultNamespace:\n                continue\n\n            if nodeName in newModes:\n                new_phase = self.phases[newModes[nodeName]]\n                break\n            elif last:\n                new_phase = self.phases[\"inBody\"]\n                break\n\n        self.phase = new_phase\n\n    def parseRCDataRawtext(self, token, contentType):\n        # Generic RCDATA/RAWTEXT Parsing algorithm\n        assert contentType in (\"RAWTEXT\", \"RCDATA\")\n\n        self.tree.insertElement(token)\n\n        if contentType == \"RAWTEXT\":\n            self.tokenizer.state = self.tokenizer.rawtextState\n        else:\n            self.tokenizer.state = self.tokenizer.rcdataState\n\n        self.originalPhase = self.phase\n\n        self.phase = self.phases[\"text\"]\n\n\n@_utils.memoize\ndef getPhases(debug):\n    def log(function):\n        \"\"\"Logger that records which phase processes each token\"\"\"\n        type_names = dict((value, key) for key, value in\n                          tokenTypes.items())\n\n        def wrapped(self, *args, **kwargs):\n            if function.__name__.startswith(\"process\") and len(args) > 0:\n                token = args[0]\n                try:\n                    info = {\"type\": type_names[token['type']]}\n                except:\n                    raise\n                if token['type'] in tagTokenTypes:\n                    info[\"name\"] = token['name']\n\n                self.parser.log.append((self.parser.tokenizer.state.__name__,\n                                        self.parser.phase.__class__.__name__,\n                                        self.__class__.__name__,\n                                        function.__name__,\n                                        info))\n                return function(self, *args, **kwargs)\n            else:\n                return function(self, *args, **kwargs)\n        return wrapped\n\n    def getMetaclass(use_metaclass, metaclass_func):\n        if use_metaclass:\n            return method_decorator_metaclass(metaclass_func)\n        else:\n            return type\n\n    # pylint:disable=unused-argument\n    class Phase(with_metaclass(getMetaclass(debug, log))):\n        \"\"\"Base class for helper object that implements each phase of processing\n        \"\"\"\n\n        def __init__(self, parser, tree):\n            self.parser = parser\n            self.tree = tree\n\n        def processEOF(self):\n            raise NotImplementedError\n\n        def processComment(self, token):\n            # For most phases the following is correct. Where it's not it will be\n            # overridden.\n            self.tree.insertComment(token, self.tree.openElements[-1])\n\n        def processDoctype(self, token):\n            self.parser.parseError(\"unexpected-doctype\")\n\n        def processCharacters(self, token):\n            self.tree.insertText(token[\"data\"])\n\n        def processSpaceCharacters(self, token):\n            self.tree.insertText(token[\"data\"])\n\n        def processStartTag(self, token):\n            return self.startTagHandler[token[\"name\"]](token)\n\n        def startTagHtml(self, token):\n            if not self.parser.firstStartTag and token[\"name\"] == \"html\":\n                self.parser.parseError(\"non-html-root\")\n            # XXX Need a check here to see if the first start tag token emitted is\n            # this token... If it's not, invoke self.parser.parseError().\n            for attr, value in token[\"data\"].items():\n                if attr not in self.tree.openElements[0].attributes:\n                    self.tree.openElements[0].attributes[attr] = value\n            self.parser.firstStartTag = False\n\n        def processEndTag(self, token):\n            return self.endTagHandler[token[\"name\"]](token)\n\n    class InitialPhase(Phase):\n        def processSpaceCharacters(self, token):\n            pass\n\n        def processComment(self, token):\n            self.tree.insertComment(token, self.tree.document)\n\n        def processDoctype(self, token):\n            name = token[\"name\"]\n            publicId = token[\"publicId\"]\n            systemId = token[\"systemId\"]\n            correct = token[\"correct\"]\n\n            if (name != \"html\" or publicId is not None or\n                    systemId is not None and systemId != \"about:legacy-compat\"):\n                self.parser.parseError(\"unknown-doctype\")\n\n            if publicId is None:\n                publicId = \"\"\n\n            self.tree.insertDoctype(token)\n\n            if publicId != \"\":\n                publicId = publicId.translate(asciiUpper2Lower)\n\n            if (not correct or token[\"name\"] != \"html\" or\n                    publicId.startswith(\n                        (\"+//silmaril//dtd html pro v0r11 19970101//\",\n                         \"-//advasoft ltd//dtd html 3.0 aswedit + extensions//\",\n                         \"-//as//dtd html 3.0 aswedit + extensions//\",\n                         \"-//ietf//dtd html 2.0 level 1//\",\n                         \"-//ietf//dtd html 2.0 level 2//\",\n                         \"-//ietf//dtd html 2.0 strict level 1//\",\n                         \"-//ietf//dtd html 2.0 strict level 2//\",\n                         \"-//ietf//dtd html 2.0 strict//\",\n                         \"-//ietf//dtd html 2.0//\",\n                         \"-//ietf//dtd html 2.1e//\",\n                         \"-//ietf//dtd html 3.0//\",\n                         \"-//ietf//dtd html 3.2 final//\",\n                         \"-//ietf//dtd html 3.2//\",\n                         \"-//ietf//dtd html 3//\",\n                         \"-//ietf//dtd html level 0//\",\n                         \"-//ietf//dtd html level 1//\",\n                         \"-//ietf//dtd html level 2//\",\n                         \"-//ietf//dtd html level 3//\",\n                         \"-//ietf//dtd html strict level 0//\",\n                         \"-//ietf//dtd html strict level 1//\",\n                         \"-//ietf//dtd html strict level 2//\",\n                         \"-//ietf//dtd html strict level 3//\",\n                         \"-//ietf//dtd html strict//\",\n                         \"-//ietf//dtd html//\",\n                         \"-//metrius//dtd metrius presentational//\",\n                         \"-//microsoft//dtd internet explorer 2.0 html strict//\",\n                         \"-//microsoft//dtd internet explorer 2.0 html//\",\n                         \"-//microsoft//dtd internet explorer 2.0 tables//\",\n                         \"-//microsoft//dtd internet explorer 3.0 html strict//\",\n                         \"-//microsoft//dtd internet explorer 3.0 html//\",\n                         \"-//microsoft//dtd internet explorer 3.0 tables//\",\n                         \"-//netscape comm. corp.//dtd html//\",\n                         \"-//netscape comm. corp.//dtd strict html//\",\n                         \"-//o'reilly and associates//dtd html 2.0//\",\n                         \"-//o'reilly and associates//dtd html extended 1.0//\",\n                         \"-//o'reilly and associates//dtd html extended relaxed 1.0//\",\n                         \"-//softquad software//dtd hotmetal pro 6.0::19990601::extensions to html 4.0//\",\n                         \"-//softquad//dtd hotmetal pro 4.0::19971010::extensions to html 4.0//\",\n                         \"-//spyglass//dtd html 2.0 extended//\",\n                         \"-//sq//dtd html 2.0 hotmetal + extensions//\",\n                         \"-//sun microsystems corp.//dtd hotjava html//\",\n                         \"-//sun microsystems corp.//dtd hotjava strict html//\",\n                         \"-//w3c//dtd html 3 1995-03-24//\",\n                         \"-//w3c//dtd html 3.2 draft//\",\n                         \"-//w3c//dtd html 3.2 final//\",\n                         \"-//w3c//dtd html 3.2//\",\n                         \"-//w3c//dtd html 3.2s draft//\",\n                         \"-//w3c//dtd html 4.0 frameset//\",\n                         \"-//w3c//dtd html 4.0 transitional//\",\n                         \"-//w3c//dtd html experimental 19960712//\",\n                         \"-//w3c//dtd html experimental 970421//\",\n                         \"-//w3c//dtd w3 html//\",\n                         \"-//w3o//dtd w3 html 3.0//\",\n                         \"-//webtechs//dtd mozilla html 2.0//\",\n                         \"-//webtechs//dtd mozilla html//\")) or\n                    publicId in (\"-//w3o//dtd w3 html strict 3.0//en//\",\n                                 \"-/w3c/dtd html 4.0 transitional/en\",\n                                 \"html\") or\n                    publicId.startswith(\n                        (\"-//w3c//dtd html 4.01 frameset//\",\n                         \"-//w3c//dtd html 4.01 transitional//\")) and\n                    systemId is None or\n                    systemId and systemId.lower() == \"http://www.ibm.com/data/dtd/v11/ibmxhtml1-transitional.dtd\"):\n                self.parser.compatMode = \"quirks\"\n            elif (publicId.startswith(\n                    (\"-//w3c//dtd xhtml 1.0 frameset//\",\n                     \"-//w3c//dtd xhtml 1.0 transitional//\")) or\n                  publicId.startswith(\n                      (\"-//w3c//dtd html 4.01 frameset//\",\n                       \"-//w3c//dtd html 4.01 transitional//\")) and\n                  systemId is not None):\n                self.parser.compatMode = \"limited quirks\"\n\n            self.parser.phase = self.parser.phases[\"beforeHtml\"]\n\n        def anythingElse(self):\n            self.parser.compatMode = \"quirks\"\n            self.parser.phase = self.parser.phases[\"beforeHtml\"]\n\n        def processCharacters(self, token):\n            self.parser.parseError(\"expected-doctype-but-got-chars\")\n            self.anythingElse()\n            return token\n\n        def processStartTag(self, token):\n            self.parser.parseError(\"expected-doctype-but-got-start-tag\",\n                                   {\"name\": token[\"name\"]})\n            self.anythingElse()\n            return token\n\n        def processEndTag(self, token):\n            self.parser.parseError(\"expected-doctype-but-got-end-tag\",\n                                   {\"name\": token[\"name\"]})\n            self.anythingElse()\n            return token\n\n        def processEOF(self):\n            self.parser.parseError(\"expected-doctype-but-got-eof\")\n            self.anythingElse()\n            return True\n\n    class BeforeHtmlPhase(Phase):\n        # helper methods\n        def insertHtmlElement(self):\n            self.tree.insertRoot(impliedTagToken(\"html\", \"StartTag\"))\n            self.parser.phase = self.parser.phases[\"beforeHead\"]\n\n        # other\n        def processEOF(self):\n            self.insertHtmlElement()\n            return True\n\n        def processComment(self, token):\n            self.tree.insertComment(token, self.tree.document)\n\n        def processSpaceCharacters(self, token):\n            pass\n\n        def processCharacters(self, token):\n            self.insertHtmlElement()\n            return token\n\n        def processStartTag(self, token):\n            if token[\"name\"] == \"html\":\n                self.parser.firstStartTag = True\n            self.insertHtmlElement()\n            return token\n\n        def processEndTag(self, token):\n            if token[\"name\"] not in (\"head\", \"body\", \"html\", \"br\"):\n                self.parser.parseError(\"unexpected-end-tag-before-html\",\n                                       {\"name\": token[\"name\"]})\n            else:\n                self.insertHtmlElement()\n                return token\n\n    class BeforeHeadPhase(Phase):\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                (\"head\", self.startTagHead)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                ((\"head\", \"body\", \"html\", \"br\"), self.endTagImplyHead)\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        def processEOF(self):\n            self.startTagHead(impliedTagToken(\"head\", \"StartTag\"))\n            return True\n\n        def processSpaceCharacters(self, token):\n            pass\n\n        def processCharacters(self, token):\n            self.startTagHead(impliedTagToken(\"head\", \"StartTag\"))\n            return token\n\n        def startTagHtml(self, token):\n            return self.parser.phases[\"inBody\"].processStartTag(token)\n\n        def startTagHead(self, token):\n            self.tree.insertElement(token)\n            self.tree.headPointer = self.tree.openElements[-1]\n            self.parser.phase = self.parser.phases[\"inHead\"]\n\n        def startTagOther(self, token):\n            self.startTagHead(impliedTagToken(\"head\", \"StartTag\"))\n            return token\n\n        def endTagImplyHead(self, token):\n            self.startTagHead(impliedTagToken(\"head\", \"StartTag\"))\n            return token\n\n        def endTagOther(self, token):\n            self.parser.parseError(\"end-tag-after-implied-root\",\n                                   {\"name\": token[\"name\"]})\n\n    class InHeadPhase(Phase):\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                (\"title\", self.startTagTitle),\n                ((\"noframes\", \"style\"), self.startTagNoFramesStyle),\n                (\"noscript\", self.startTagNoscript),\n                (\"script\", self.startTagScript),\n                ((\"base\", \"basefont\", \"bgsound\", \"command\", \"link\"),\n                 self.startTagBaseLinkCommand),\n                (\"meta\", self.startTagMeta),\n                (\"head\", self.startTagHead)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                (\"head\", self.endTagHead),\n                ((\"br\", \"html\", \"body\"), self.endTagHtmlBodyBr)\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        # the real thing\n        def processEOF(self):\n            self.anythingElse()\n            return True\n\n        def processCharacters(self, token):\n            self.anythingElse()\n            return token\n\n        def startTagHtml(self, token):\n            return self.parser.phases[\"inBody\"].processStartTag(token)\n\n        def startTagHead(self, token):\n            self.parser.parseError(\"two-heads-are-not-better-than-one\")\n\n        def startTagBaseLinkCommand(self, token):\n            self.tree.insertElement(token)\n            self.tree.openElements.pop()\n            token[\"selfClosingAcknowledged\"] = True\n\n        def startTagMeta(self, token):\n            self.tree.insertElement(token)\n            self.tree.openElements.pop()\n            token[\"selfClosingAcknowledged\"] = True\n\n            attributes = token[\"data\"]\n            if self.parser.tokenizer.stream.charEncoding[1] == \"tentative\":\n                if \"charset\" in attributes:\n                    self.parser.tokenizer.stream.changeEncoding(attributes[\"charset\"])\n                elif (\"content\" in attributes and\n                      \"http-equiv\" in attributes and\n                      attributes[\"http-equiv\"].lower() == \"content-type\"):\n                    # Encoding it as UTF-8 here is a hack, as really we should pass\n                    # the abstract Unicode string, and just use the\n                    # ContentAttrParser on that, but using UTF-8 allows all chars\n                    # to be encoded and as a ASCII-superset works.\n                    data = _inputstream.EncodingBytes(attributes[\"content\"].encode(\"utf-8\"))\n                    parser = _inputstream.ContentAttrParser(data)\n                    codec = parser.parse()\n                    self.parser.tokenizer.stream.changeEncoding(codec)\n\n        def startTagTitle(self, token):\n            self.parser.parseRCDataRawtext(token, \"RCDATA\")\n\n        def startTagNoFramesStyle(self, token):\n            # Need to decide whether to implement the scripting-disabled case\n            self.parser.parseRCDataRawtext(token, \"RAWTEXT\")\n\n        def startTagNoscript(self, token):\n            if self.parser.scripting:\n                self.parser.parseRCDataRawtext(token, \"RAWTEXT\")\n            else:\n                self.tree.insertElement(token)\n                self.parser.phase = self.parser.phases[\"inHeadNoscript\"]\n\n        def startTagScript(self, token):\n            self.tree.insertElement(token)\n            self.parser.tokenizer.state = self.parser.tokenizer.scriptDataState\n            self.parser.originalPhase = self.parser.phase\n            self.parser.phase = self.parser.phases[\"text\"]\n\n        def startTagOther(self, token):\n            self.anythingElse()\n            return token\n\n        def endTagHead(self, token):\n            node = self.parser.tree.openElements.pop()\n            assert node.name == \"head\", \"Expected head got %s\" % node.name\n            self.parser.phase = self.parser.phases[\"afterHead\"]\n\n        def endTagHtmlBodyBr(self, token):\n            self.anythingElse()\n            return token\n\n        def endTagOther(self, token):\n            self.parser.parseError(\"unexpected-end-tag\", {\"name\": token[\"name\"]})\n\n        def anythingElse(self):\n            self.endTagHead(impliedTagToken(\"head\"))\n\n    class InHeadNoscriptPhase(Phase):\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                ((\"basefont\", \"bgsound\", \"link\", \"meta\", \"noframes\", \"style\"), self.startTagBaseLinkCommand),\n                ((\"head\", \"noscript\"), self.startTagHeadNoscript),\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                (\"noscript\", self.endTagNoscript),\n                (\"br\", self.endTagBr),\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        def processEOF(self):\n            self.parser.parseError(\"eof-in-head-noscript\")\n            self.anythingElse()\n            return True\n\n        def processComment(self, token):\n            return self.parser.phases[\"inHead\"].processComment(token)\n\n        def processCharacters(self, token):\n            self.parser.parseError(\"char-in-head-noscript\")\n            self.anythingElse()\n            return token\n\n        def processSpaceCharacters(self, token):\n            return self.parser.phases[\"inHead\"].processSpaceCharacters(token)\n\n        def startTagHtml(self, token):\n            return self.parser.phases[\"inBody\"].processStartTag(token)\n\n        def startTagBaseLinkCommand(self, token):\n            return self.parser.phases[\"inHead\"].processStartTag(token)\n\n        def startTagHeadNoscript(self, token):\n            self.parser.parseError(\"unexpected-start-tag\", {\"name\": token[\"name\"]})\n\n        def startTagOther(self, token):\n            self.parser.parseError(\"unexpected-inhead-noscript-tag\", {\"name\": token[\"name\"]})\n            self.anythingElse()\n            return token\n\n        def endTagNoscript(self, token):\n            node = self.parser.tree.openElements.pop()\n            assert node.name == \"noscript\", \"Expected noscript got %s\" % node.name\n            self.parser.phase = self.parser.phases[\"inHead\"]\n\n        def endTagBr(self, token):\n            self.parser.parseError(\"unexpected-inhead-noscript-tag\", {\"name\": token[\"name\"]})\n            self.anythingElse()\n            return token\n\n        def endTagOther(self, token):\n            self.parser.parseError(\"unexpected-end-tag\", {\"name\": token[\"name\"]})\n\n        def anythingElse(self):\n            # Caller must raise parse error first!\n            self.endTagNoscript(impliedTagToken(\"noscript\"))\n\n    class AfterHeadPhase(Phase):\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                (\"body\", self.startTagBody),\n                (\"frameset\", self.startTagFrameset),\n                ((\"base\", \"basefont\", \"bgsound\", \"link\", \"meta\", \"noframes\", \"script\",\n                  \"style\", \"title\"),\n                 self.startTagFromHead),\n                (\"head\", self.startTagHead)\n            ])\n            self.startTagHandler.default = self.startTagOther\n            self.endTagHandler = _utils.MethodDispatcher([((\"body\", \"html\", \"br\"),\n                                                           self.endTagHtmlBodyBr)])\n            self.endTagHandler.default = self.endTagOther\n\n        def processEOF(self):\n            self.anythingElse()\n            return True\n\n        def processCharacters(self, token):\n            self.anythingElse()\n            return token\n\n        def startTagHtml(self, token):\n            return self.parser.phases[\"inBody\"].processStartTag(token)\n\n        def startTagBody(self, token):\n            self.parser.framesetOK = False\n            self.tree.insertElement(token)\n            self.parser.phase = self.parser.phases[\"inBody\"]\n\n        def startTagFrameset(self, token):\n            self.tree.insertElement(token)\n            self.parser.phase = self.parser.phases[\"inFrameset\"]\n\n        def startTagFromHead(self, token):\n            self.parser.parseError(\"unexpected-start-tag-out-of-my-head\",\n                                   {\"name\": token[\"name\"]})\n            self.tree.openElements.append(self.tree.headPointer)\n            self.parser.phases[\"inHead\"].processStartTag(token)\n            for node in self.tree.openElements[::-1]:\n                if node.name == \"head\":\n                    self.tree.openElements.remove(node)\n                    break\n\n        def startTagHead(self, token):\n            self.parser.parseError(\"unexpected-start-tag\", {\"name\": token[\"name\"]})\n\n        def startTagOther(self, token):\n            self.anythingElse()\n            return token\n\n        def endTagHtmlBodyBr(self, token):\n            self.anythingElse()\n            return token\n\n        def endTagOther(self, token):\n            self.parser.parseError(\"unexpected-end-tag\", {\"name\": token[\"name\"]})\n\n        def anythingElse(self):\n            self.tree.insertElement(impliedTagToken(\"body\", \"StartTag\"))\n            self.parser.phase = self.parser.phases[\"inBody\"]\n            self.parser.framesetOK = True\n\n    class InBodyPhase(Phase):\n        # http://www.whatwg.org/specs/web-apps/current-work/#parsing-main-inbody\n        # the really-really-really-very crazy mode\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            # Set this to the default handler\n            self.processSpaceCharacters = self.processSpaceCharactersNonPre\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                ((\"base\", \"basefont\", \"bgsound\", \"command\", \"link\", \"meta\",\n                  \"script\", \"style\", \"title\"),\n                 self.startTagProcessInHead),\n                (\"body\", self.startTagBody),\n                (\"frameset\", self.startTagFrameset),\n                ((\"address\", \"article\", \"aside\", \"blockquote\", \"center\", \"details\",\n                  \"dir\", \"div\", \"dl\", \"fieldset\", \"figcaption\", \"figure\",\n                  \"footer\", \"header\", \"hgroup\", \"main\", \"menu\", \"nav\", \"ol\", \"p\",\n                  \"section\", \"summary\", \"ul\"),\n                 self.startTagCloseP),\n                (headingElements, self.startTagHeading),\n                ((\"pre\", \"listing\"), self.startTagPreListing),\n                (\"form\", self.startTagForm),\n                ((\"li\", \"dd\", \"dt\"), self.startTagListItem),\n                (\"plaintext\", self.startTagPlaintext),\n                (\"a\", self.startTagA),\n                ((\"b\", \"big\", \"code\", \"em\", \"font\", \"i\", \"s\", \"small\", \"strike\",\n                  \"strong\", \"tt\", \"u\"), self.startTagFormatting),\n                (\"nobr\", self.startTagNobr),\n                (\"button\", self.startTagButton),\n                ((\"applet\", \"marquee\", \"object\"), self.startTagAppletMarqueeObject),\n                (\"xmp\", self.startTagXmp),\n                (\"table\", self.startTagTable),\n                ((\"area\", \"br\", \"embed\", \"img\", \"keygen\", \"wbr\"),\n                 self.startTagVoidFormatting),\n                ((\"param\", \"source\", \"track\"), self.startTagParamSource),\n                (\"input\", self.startTagInput),\n                (\"hr\", self.startTagHr),\n                (\"image\", self.startTagImage),\n                (\"isindex\", self.startTagIsIndex),\n                (\"textarea\", self.startTagTextarea),\n                (\"iframe\", self.startTagIFrame),\n                (\"noscript\", self.startTagNoscript),\n                ((\"noembed\", \"noframes\"), self.startTagRawtext),\n                (\"select\", self.startTagSelect),\n                ((\"rp\", \"rt\"), self.startTagRpRt),\n                ((\"option\", \"optgroup\"), self.startTagOpt),\n                ((\"math\"), self.startTagMath),\n                ((\"svg\"), self.startTagSvg),\n                ((\"caption\", \"col\", \"colgroup\", \"frame\", \"head\",\n                  \"tbody\", \"td\", \"tfoot\", \"th\", \"thead\",\n                  \"tr\"), self.startTagMisplaced)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                (\"body\", self.endTagBody),\n                (\"html\", self.endTagHtml),\n                ((\"address\", \"article\", \"aside\", \"blockquote\", \"button\", \"center\",\n                  \"details\", \"dialog\", \"dir\", \"div\", \"dl\", \"fieldset\", \"figcaption\", \"figure\",\n                  \"footer\", \"header\", \"hgroup\", \"listing\", \"main\", \"menu\", \"nav\", \"ol\", \"pre\",\n                  \"section\", \"summary\", \"ul\"), self.endTagBlock),\n                (\"form\", self.endTagForm),\n                (\"p\", self.endTagP),\n                ((\"dd\", \"dt\", \"li\"), self.endTagListItem),\n                (headingElements, self.endTagHeading),\n                ((\"a\", \"b\", \"big\", \"code\", \"em\", \"font\", \"i\", \"nobr\", \"s\", \"small\",\n                  \"strike\", \"strong\", \"tt\", \"u\"), self.endTagFormatting),\n                ((\"applet\", \"marquee\", \"object\"), self.endTagAppletMarqueeObject),\n                (\"br\", self.endTagBr),\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        def isMatchingFormattingElement(self, node1, node2):\n            return (node1.name == node2.name and\n                    node1.namespace == node2.namespace and\n                    node1.attributes == node2.attributes)\n\n        # helper\n        def addFormattingElement(self, token):\n            self.tree.insertElement(token)\n            element = self.tree.openElements[-1]\n\n            matchingElements = []\n            for node in self.tree.activeFormattingElements[::-1]:\n                if node is Marker:\n                    break\n                elif self.isMatchingFormattingElement(node, element):\n                    matchingElements.append(node)\n\n            assert len(matchingElements) <= 3\n            if len(matchingElements) == 3:\n                self.tree.activeFormattingElements.remove(matchingElements[-1])\n            self.tree.activeFormattingElements.append(element)\n\n        # the real deal\n        def processEOF(self):\n            allowed_elements = frozenset((\"dd\", \"dt\", \"li\", \"p\", \"tbody\", \"td\",\n                                          \"tfoot\", \"th\", \"thead\", \"tr\", \"body\",\n                                          \"html\"))\n            for node in self.tree.openElements[::-1]:\n                if node.name not in allowed_elements:\n                    self.parser.parseError(\"expected-closing-tag-but-got-eof\")\n                    break\n            # Stop parsing\n\n        def processSpaceCharactersDropNewline(self, token):\n            # Sometimes (start of <pre>, <listing>, and <textarea> blocks) we\n            # want to drop leading newlines\n            data = token[\"data\"]\n            self.processSpaceCharacters = self.processSpaceCharactersNonPre\n            if (data.startswith(\"\\n\") and\n                self.tree.openElements[-1].name in (\"pre\", \"listing\", \"textarea\") and\n                    not self.tree.openElements[-1].hasContent()):\n                data = data[1:]\n            if data:\n                self.tree.reconstructActiveFormattingElements()\n                self.tree.insertText(data)\n\n        def processCharacters(self, token):\n            if token[\"data\"] == \"\\u0000\":\n                # The tokenizer should always emit null on its own\n                return\n            self.tree.reconstructActiveFormattingElements()\n            self.tree.insertText(token[\"data\"])\n            # This must be bad for performance\n            if (self.parser.framesetOK and\n                any([char not in spaceCharacters\n                     for char in token[\"data\"]])):\n                self.parser.framesetOK = False\n\n        def processSpaceCharactersNonPre(self, token):\n            self.tree.reconstructActiveFormattingElements()\n            self.tree.insertText(token[\"data\"])\n\n        def startTagProcessInHead(self, token):\n            return self.parser.phases[\"inHead\"].processStartTag(token)\n\n        def startTagBody(self, token):\n            self.parser.parseError(\"unexpected-start-tag\", {\"name\": \"body\"})\n            if (len(self.tree.openElements) == 1 or\n                    self.tree.openElements[1].name != \"body\"):\n                assert self.parser.innerHTML\n            else:\n                self.parser.framesetOK = False\n                for attr, value in token[\"data\"].items():\n                    if attr not in self.tree.openElements[1].attributes:\n                        self.tree.openElements[1].attributes[attr] = value\n\n        def startTagFrameset(self, token):\n            self.parser.parseError(\"unexpected-start-tag\", {\"name\": \"frameset\"})\n            if (len(self.tree.openElements) == 1 or self.tree.openElements[1].name != \"body\"):\n                assert self.parser.innerHTML\n            elif not self.parser.framesetOK:\n                pass\n            else:\n                if self.tree.openElements[1].parent:\n                    self.tree.openElements[1].parent.removeChild(self.tree.openElements[1])\n                while self.tree.openElements[-1].name != \"html\":\n                    self.tree.openElements.pop()\n                self.tree.insertElement(token)\n                self.parser.phase = self.parser.phases[\"inFrameset\"]\n\n        def startTagCloseP(self, token):\n            if self.tree.elementInScope(\"p\", variant=\"button\"):\n                self.endTagP(impliedTagToken(\"p\"))\n            self.tree.insertElement(token)\n\n        def startTagPreListing(self, token):\n            if self.tree.elementInScope(\"p\", variant=\"button\"):\n                self.endTagP(impliedTagToken(\"p\"))\n            self.tree.insertElement(token)\n            self.parser.framesetOK = False\n            self.processSpaceCharacters = self.processSpaceCharactersDropNewline\n\n        def startTagForm(self, token):\n            if self.tree.formPointer:\n                self.parser.parseError(\"unexpected-start-tag\", {\"name\": \"form\"})\n            else:\n                if self.tree.elementInScope(\"p\", variant=\"button\"):\n                    self.endTagP(impliedTagToken(\"p\"))\n                self.tree.insertElement(token)\n                self.tree.formPointer = self.tree.openElements[-1]\n\n        def startTagListItem(self, token):\n            self.parser.framesetOK = False\n\n            stopNamesMap = {\"li\": [\"li\"],\n                            \"dt\": [\"dt\", \"dd\"],\n                            \"dd\": [\"dt\", \"dd\"]}\n            stopNames = stopNamesMap[token[\"name\"]]\n            for node in reversed(self.tree.openElements):\n                if node.name in stopNames:\n                    self.parser.phase.processEndTag(\n                        impliedTagToken(node.name, \"EndTag\"))\n                    break\n                if (node.nameTuple in specialElements and\n                        node.name not in (\"address\", \"div\", \"p\")):\n                    break\n\n            if self.tree.elementInScope(\"p\", variant=\"button\"):\n                self.parser.phase.processEndTag(\n                    impliedTagToken(\"p\", \"EndTag\"))\n\n            self.tree.insertElement(token)\n\n        def startTagPlaintext(self, token):\n            if self.tree.elementInScope(\"p\", variant=\"button\"):\n                self.endTagP(impliedTagToken(\"p\"))\n            self.tree.insertElement(token)\n            self.parser.tokenizer.state = self.parser.tokenizer.plaintextState\n\n        def startTagHeading(self, token):\n            if self.tree.elementInScope(\"p\", variant=\"button\"):\n                self.endTagP(impliedTagToken(\"p\"))\n            if self.tree.openElements[-1].name in headingElements:\n                self.parser.parseError(\"unexpected-start-tag\", {\"name\": token[\"name\"]})\n                self.tree.openElements.pop()\n            self.tree.insertElement(token)\n\n        def startTagA(self, token):\n            afeAElement = self.tree.elementInActiveFormattingElements(\"a\")\n            if afeAElement:\n                self.parser.parseError(\"unexpected-start-tag-implies-end-tag\",\n                                       {\"startName\": \"a\", \"endName\": \"a\"})\n                self.endTagFormatting(impliedTagToken(\"a\"))\n                if afeAElement in self.tree.openElements:\n                    self.tree.openElements.remove(afeAElement)\n                if afeAElement in self.tree.activeFormattingElements:\n                    self.tree.activeFormattingElements.remove(afeAElement)\n            self.tree.reconstructActiveFormattingElements()\n            self.addFormattingElement(token)\n\n        def startTagFormatting(self, token):\n            self.tree.reconstructActiveFormattingElements()\n            self.addFormattingElement(token)\n\n        def startTagNobr(self, token):\n            self.tree.reconstructActiveFormattingElements()\n            if self.tree.elementInScope(\"nobr\"):\n                self.parser.parseError(\"unexpected-start-tag-implies-end-tag\",\n                                       {\"startName\": \"nobr\", \"endName\": \"nobr\"})\n                self.processEndTag(impliedTagToken(\"nobr\"))\n                # XXX Need tests that trigger the following\n                self.tree.reconstructActiveFormattingElements()\n            self.addFormattingElement(token)\n\n        def startTagButton(self, token):\n            if self.tree.elementInScope(\"button\"):\n                self.parser.parseError(\"unexpected-start-tag-implies-end-tag\",\n                                       {\"startName\": \"button\", \"endName\": \"button\"})\n                self.processEndTag(impliedTagToken(\"button\"))\n                return token\n            else:\n                self.tree.reconstructActiveFormattingElements()\n                self.tree.insertElement(token)\n                self.parser.framesetOK = False\n\n        def startTagAppletMarqueeObject(self, token):\n            self.tree.reconstructActiveFormattingElements()\n            self.tree.insertElement(token)\n            self.tree.activeFormattingElements.append(Marker)\n            self.parser.framesetOK = False\n\n        def startTagXmp(self, token):\n            if self.tree.elementInScope(\"p\", variant=\"button\"):\n                self.endTagP(impliedTagToken(\"p\"))\n            self.tree.reconstructActiveFormattingElements()\n            self.parser.framesetOK = False\n            self.parser.parseRCDataRawtext(token, \"RAWTEXT\")\n\n        def startTagTable(self, token):\n            if self.parser.compatMode != \"quirks\":\n                if self.tree.elementInScope(\"p\", variant=\"button\"):\n                    self.processEndTag(impliedTagToken(\"p\"))\n            self.tree.insertElement(token)\n            self.parser.framesetOK = False\n            self.parser.phase = self.parser.phases[\"inTable\"]\n\n        def startTagVoidFormatting(self, token):\n            self.tree.reconstructActiveFormattingElements()\n            self.tree.insertElement(token)\n            self.tree.openElements.pop()\n            token[\"selfClosingAcknowledged\"] = True\n            self.parser.framesetOK = False\n\n        def startTagInput(self, token):\n            framesetOK = self.parser.framesetOK\n            self.startTagVoidFormatting(token)\n            if (\"type\" in token[\"data\"] and\n                    token[\"data\"][\"type\"].translate(asciiUpper2Lower) == \"hidden\"):\n                # input type=hidden doesn't change framesetOK\n                self.parser.framesetOK = framesetOK\n\n        def startTagParamSource(self, token):\n            self.tree.insertElement(token)\n            self.tree.openElements.pop()\n            token[\"selfClosingAcknowledged\"] = True\n\n        def startTagHr(self, token):\n            if self.tree.elementInScope(\"p\", variant=\"button\"):\n                self.endTagP(impliedTagToken(\"p\"))\n            self.tree.insertElement(token)\n            self.tree.openElements.pop()\n            token[\"selfClosingAcknowledged\"] = True\n            self.parser.framesetOK = False\n\n        def startTagImage(self, token):\n            # No really...\n            self.parser.parseError(\"unexpected-start-tag-treated-as\",\n                                   {\"originalName\": \"image\", \"newName\": \"img\"})\n            self.processStartTag(impliedTagToken(\"img\", \"StartTag\",\n                                                 attributes=token[\"data\"],\n                                                 selfClosing=token[\"selfClosing\"]))\n\n        def startTagIsIndex(self, token):\n            self.parser.parseError(\"deprecated-tag\", {\"name\": \"isindex\"})\n            if self.tree.formPointer:\n                return\n            form_attrs = {}\n            if \"action\" in token[\"data\"]:\n                form_attrs[\"action\"] = token[\"data\"][\"action\"]\n            self.processStartTag(impliedTagToken(\"form\", \"StartTag\",\n                                                 attributes=form_attrs))\n            self.processStartTag(impliedTagToken(\"hr\", \"StartTag\"))\n            self.processStartTag(impliedTagToken(\"label\", \"StartTag\"))\n            # XXX Localization ...\n            if \"prompt\" in token[\"data\"]:\n                prompt = token[\"data\"][\"prompt\"]\n            else:\n                prompt = \"This is a searchable index. Enter search keywords: \"\n            self.processCharacters(\n                {\"type\": tokenTypes[\"Characters\"], \"data\": prompt})\n            attributes = token[\"data\"].copy()\n            if \"action\" in attributes:\n                del attributes[\"action\"]\n            if \"prompt\" in attributes:\n                del attributes[\"prompt\"]\n            attributes[\"name\"] = \"isindex\"\n            self.processStartTag(impliedTagToken(\"input\", \"StartTag\",\n                                                 attributes=attributes,\n                                                 selfClosing=token[\"selfClosing\"]))\n            self.processEndTag(impliedTagToken(\"label\"))\n            self.processStartTag(impliedTagToken(\"hr\", \"StartTag\"))\n            self.processEndTag(impliedTagToken(\"form\"))\n\n        def startTagTextarea(self, token):\n            self.tree.insertElement(token)\n            self.parser.tokenizer.state = self.parser.tokenizer.rcdataState\n            self.processSpaceCharacters = self.processSpaceCharactersDropNewline\n            self.parser.framesetOK = False\n\n        def startTagIFrame(self, token):\n            self.parser.framesetOK = False\n            self.startTagRawtext(token)\n\n        def startTagNoscript(self, token):\n            if self.parser.scripting:\n                self.startTagRawtext(token)\n            else:\n                self.startTagOther(token)\n\n        def startTagRawtext(self, token):\n            \"\"\"iframe, noembed noframes, noscript(if scripting enabled)\"\"\"\n            self.parser.parseRCDataRawtext(token, \"RAWTEXT\")\n\n        def startTagOpt(self, token):\n            if self.tree.openElements[-1].name == \"option\":\n                self.parser.phase.processEndTag(impliedTagToken(\"option\"))\n            self.tree.reconstructActiveFormattingElements()\n            self.parser.tree.insertElement(token)\n\n        def startTagSelect(self, token):\n            self.tree.reconstructActiveFormattingElements()\n            self.tree.insertElement(token)\n            self.parser.framesetOK = False\n            if self.parser.phase in (self.parser.phases[\"inTable\"],\n                                     self.parser.phases[\"inCaption\"],\n                                     self.parser.phases[\"inColumnGroup\"],\n                                     self.parser.phases[\"inTableBody\"],\n                                     self.parser.phases[\"inRow\"],\n                                     self.parser.phases[\"inCell\"]):\n                self.parser.phase = self.parser.phases[\"inSelectInTable\"]\n            else:\n                self.parser.phase = self.parser.phases[\"inSelect\"]\n\n        def startTagRpRt(self, token):\n            if self.tree.elementInScope(\"ruby\"):\n                self.tree.generateImpliedEndTags()\n                if self.tree.openElements[-1].name != \"ruby\":\n                    self.parser.parseError()\n            self.tree.insertElement(token)\n\n        def startTagMath(self, token):\n            self.tree.reconstructActiveFormattingElements()\n            self.parser.adjustMathMLAttributes(token)\n            self.parser.adjustForeignAttributes(token)\n            token[\"namespace\"] = namespaces[\"mathml\"]\n            self.tree.insertElement(token)\n            # Need to get the parse error right for the case where the token\n            # has a namespace not equal to the xmlns attribute\n            if token[\"selfClosing\"]:\n                self.tree.openElements.pop()\n                token[\"selfClosingAcknowledged\"] = True\n\n        def startTagSvg(self, token):\n            self.tree.reconstructActiveFormattingElements()\n            self.parser.adjustSVGAttributes(token)\n            self.parser.adjustForeignAttributes(token)\n            token[\"namespace\"] = namespaces[\"svg\"]\n            self.tree.insertElement(token)\n            # Need to get the parse error right for the case where the token\n            # has a namespace not equal to the xmlns attribute\n            if token[\"selfClosing\"]:\n                self.tree.openElements.pop()\n                token[\"selfClosingAcknowledged\"] = True\n\n        def startTagMisplaced(self, token):\n            \"\"\" Elements that should be children of other elements that have a\n            different insertion mode; here they are ignored\n            \"caption\", \"col\", \"colgroup\", \"frame\", \"frameset\", \"head\",\n            \"option\", \"optgroup\", \"tbody\", \"td\", \"tfoot\", \"th\", \"thead\",\n            \"tr\", \"noscript\"\n            \"\"\"\n            self.parser.parseError(\"unexpected-start-tag-ignored\", {\"name\": token[\"name\"]})\n\n        def startTagOther(self, token):\n            self.tree.reconstructActiveFormattingElements()\n            self.tree.insertElement(token)\n\n        def endTagP(self, token):\n            if not self.tree.elementInScope(\"p\", variant=\"button\"):\n                self.startTagCloseP(impliedTagToken(\"p\", \"StartTag\"))\n                self.parser.parseError(\"unexpected-end-tag\", {\"name\": \"p\"})\n                self.endTagP(impliedTagToken(\"p\", \"EndTag\"))\n            else:\n                self.tree.generateImpliedEndTags(\"p\")\n                if self.tree.openElements[-1].name != \"p\":\n                    self.parser.parseError(\"unexpected-end-tag\", {\"name\": \"p\"})\n                node = self.tree.openElements.pop()\n                while node.name != \"p\":\n                    node = self.tree.openElements.pop()\n\n        def endTagBody(self, token):\n            if not self.tree.elementInScope(\"body\"):\n                self.parser.parseError()\n                return\n            elif self.tree.openElements[-1].name != \"body\":\n                for node in self.tree.openElements[2:]:\n                    if node.name not in frozenset((\"dd\", \"dt\", \"li\", \"optgroup\",\n                                                   \"option\", \"p\", \"rp\", \"rt\",\n                                                   \"tbody\", \"td\", \"tfoot\",\n                                                   \"th\", \"thead\", \"tr\", \"body\",\n                                                   \"html\")):\n                        # Not sure this is the correct name for the parse error\n                        self.parser.parseError(\n                            \"expected-one-end-tag-but-got-another\",\n                            {\"gotName\": \"body\", \"expectedName\": node.name})\n                        break\n            self.parser.phase = self.parser.phases[\"afterBody\"]\n\n        def endTagHtml(self, token):\n            # We repeat the test for the body end tag token being ignored here\n            if self.tree.elementInScope(\"body\"):\n                self.endTagBody(impliedTagToken(\"body\"))\n                return token\n\n        def endTagBlock(self, token):\n            # Put us back in the right whitespace handling mode\n            if token[\"name\"] == \"pre\":\n                self.processSpaceCharacters = self.processSpaceCharactersNonPre\n            inScope = self.tree.elementInScope(token[\"name\"])\n            if inScope:\n                self.tree.generateImpliedEndTags()\n            if self.tree.openElements[-1].name != token[\"name\"]:\n                self.parser.parseError(\"end-tag-too-early\", {\"name\": token[\"name\"]})\n            if inScope:\n                node = self.tree.openElements.pop()\n                while node.name != token[\"name\"]:\n                    node = self.tree.openElements.pop()\n\n        def endTagForm(self, token):\n            node = self.tree.formPointer\n            self.tree.formPointer = None\n            if node is None or not self.tree.elementInScope(node):\n                self.parser.parseError(\"unexpected-end-tag\",\n                                       {\"name\": \"form\"})\n            else:\n                self.tree.generateImpliedEndTags()\n                if self.tree.openElements[-1] != node:\n                    self.parser.parseError(\"end-tag-too-early-ignored\",\n                                           {\"name\": \"form\"})\n                self.tree.openElements.remove(node)\n\n        def endTagListItem(self, token):\n            if token[\"name\"] == \"li\":\n                variant = \"list\"\n            else:\n                variant = None\n            if not self.tree.elementInScope(token[\"name\"], variant=variant):\n                self.parser.parseError(\"unexpected-end-tag\", {\"name\": token[\"name\"]})\n            else:\n                self.tree.generateImpliedEndTags(exclude=token[\"name\"])\n                if self.tree.openElements[-1].name != token[\"name\"]:\n                    self.parser.parseError(\n                        \"end-tag-too-early\",\n                        {\"name\": token[\"name\"]})\n                node = self.tree.openElements.pop()\n                while node.name != token[\"name\"]:\n                    node = self.tree.openElements.pop()\n\n        def endTagHeading(self, token):\n            for item in headingElements:\n                if self.tree.elementInScope(item):\n                    self.tree.generateImpliedEndTags()\n                    break\n            if self.tree.openElements[-1].name != token[\"name\"]:\n                self.parser.parseError(\"end-tag-too-early\", {\"name\": token[\"name\"]})\n\n            for item in headingElements:\n                if self.tree.elementInScope(item):\n                    item = self.tree.openElements.pop()\n                    while item.name not in headingElements:\n                        item = self.tree.openElements.pop()\n                    break\n\n        def endTagFormatting(self, token):\n            \"\"\"The much-feared adoption agency algorithm\"\"\"\n            # http://svn.whatwg.org/webapps/complete.html#adoptionAgency revision 7867\n            # XXX Better parseError messages appreciated.\n\n            # Step 1\n            outerLoopCounter = 0\n\n            # Step 2\n            while outerLoopCounter < 8:\n\n                # Step 3\n                outerLoopCounter += 1\n\n                # Step 4:\n\n                # Let the formatting element be the last element in\n                # the list of active formatting elements that:\n                # - is between the end of the list and the last scope\n                # marker in the list, if any, or the start of the list\n                # otherwise, and\n                # - has the same tag name as the token.\n                formattingElement = self.tree.elementInActiveFormattingElements(\n                    token[\"name\"])\n                if (not formattingElement or\n                    (formattingElement in self.tree.openElements and\n                     not self.tree.elementInScope(formattingElement.name))):\n                    # If there is no such node, then abort these steps\n                    # and instead act as described in the \"any other\n                    # end tag\" entry below.\n                    self.endTagOther(token)\n                    return\n\n                # Otherwise, if there is such a node, but that node is\n                # not in the stack of open elements, then this is a\n                # parse error; remove the element from the list, and\n                # abort these steps.\n                elif formattingElement not in self.tree.openElements:\n                    self.parser.parseError(\"adoption-agency-1.2\", {\"name\": token[\"name\"]})\n                    self.tree.activeFormattingElements.remove(formattingElement)\n                    return\n\n                # Otherwise, if there is such a node, and that node is\n                # also in the stack of open elements, but the element\n                # is not in scope, then this is a parse error; ignore\n                # the token, and abort these steps.\n                elif not self.tree.elementInScope(formattingElement.name):\n                    self.parser.parseError(\"adoption-agency-4.4\", {\"name\": token[\"name\"]})\n                    return\n\n                # Otherwise, there is a formatting element and that\n                # element is in the stack and is in scope. If the\n                # element is not the current node, this is a parse\n                # error. In any case, proceed with the algorithm as\n                # written in the following steps.\n                else:\n                    if formattingElement != self.tree.openElements[-1]:\n                        self.parser.parseError(\"adoption-agency-1.3\", {\"name\": token[\"name\"]})\n\n                # Step 5:\n\n                # Let the furthest block be the topmost node in the\n                # stack of open elements that is lower in the stack\n                # than the formatting element, and is an element in\n                # the special category. There might not be one.\n                afeIndex = self.tree.openElements.index(formattingElement)\n                furthestBlock = None\n                for element in self.tree.openElements[afeIndex:]:\n                    if element.nameTuple in specialElements:\n                        furthestBlock = element\n                        break\n\n                # Step 6:\n\n                # If there is no furthest block, then the UA must\n                # first pop all the nodes from the bottom of the stack\n                # of open elements, from the current node up to and\n                # including the formatting element, then remove the\n                # formatting element from the list of active\n                # formatting elements, and finally abort these steps.\n                if furthestBlock is None:\n                    element = self.tree.openElements.pop()\n                    while element != formattingElement:\n                        element = self.tree.openElements.pop()\n                    self.tree.activeFormattingElements.remove(element)\n                    return\n\n                # Step 7\n                commonAncestor = self.tree.openElements[afeIndex - 1]\n\n                # Step 8:\n                # The bookmark is supposed to help us identify where to reinsert\n                # nodes in step 15. We have to ensure that we reinsert nodes after\n                # the node before the active formatting element. Note the bookmark\n                # can move in step 9.7\n                bookmark = self.tree.activeFormattingElements.index(formattingElement)\n\n                # Step 9\n                lastNode = node = furthestBlock\n                innerLoopCounter = 0\n\n                index = self.tree.openElements.index(node)\n                while innerLoopCounter < 3:\n                    innerLoopCounter += 1\n                    # Node is element before node in open elements\n                    index -= 1\n                    node = self.tree.openElements[index]\n                    if node not in self.tree.activeFormattingElements:\n                        self.tree.openElements.remove(node)\n                        continue\n                    # Step 9.6\n                    if node == formattingElement:\n                        break\n                    # Step 9.7\n                    if lastNode == furthestBlock:\n                        bookmark = self.tree.activeFormattingElements.index(node) + 1\n                    # Step 9.8\n                    clone = node.cloneNode()\n                    # Replace node with clone\n                    self.tree.activeFormattingElements[\n                        self.tree.activeFormattingElements.index(node)] = clone\n                    self.tree.openElements[\n                        self.tree.openElements.index(node)] = clone\n                    node = clone\n                    # Step 9.9\n                    # Remove lastNode from its parents, if any\n                    if lastNode.parent:\n                        lastNode.parent.removeChild(lastNode)\n                    node.appendChild(lastNode)\n                    # Step 9.10\n                    lastNode = node\n\n                # Step 10\n                # Foster parent lastNode if commonAncestor is a\n                # table, tbody, tfoot, thead, or tr we need to foster\n                # parent the lastNode\n                if lastNode.parent:\n                    lastNode.parent.removeChild(lastNode)\n\n                if commonAncestor.name in frozenset((\"table\", \"tbody\", \"tfoot\", \"thead\", \"tr\")):\n                    parent, insertBefore = self.tree.getTableMisnestedNodePosition()\n                    parent.insertBefore(lastNode, insertBefore)\n                else:\n                    commonAncestor.appendChild(lastNode)\n\n                # Step 11\n                clone = formattingElement.cloneNode()\n\n                # Step 12\n                furthestBlock.reparentChildren(clone)\n\n                # Step 13\n                furthestBlock.appendChild(clone)\n\n                # Step 14\n                self.tree.activeFormattingElements.remove(formattingElement)\n                self.tree.activeFormattingElements.insert(bookmark, clone)\n\n                # Step 15\n                self.tree.openElements.remove(formattingElement)\n                self.tree.openElements.insert(\n                    self.tree.openElements.index(furthestBlock) + 1, clone)\n\n        def endTagAppletMarqueeObject(self, token):\n            if self.tree.elementInScope(token[\"name\"]):\n                self.tree.generateImpliedEndTags()\n            if self.tree.openElements[-1].name != token[\"name\"]:\n                self.parser.parseError(\"end-tag-too-early\", {\"name\": token[\"name\"]})\n\n            if self.tree.elementInScope(token[\"name\"]):\n                element = self.tree.openElements.pop()\n                while element.name != token[\"name\"]:\n                    element = self.tree.openElements.pop()\n                self.tree.clearActiveFormattingElements()\n\n        def endTagBr(self, token):\n            self.parser.parseError(\"unexpected-end-tag-treated-as\",\n                                   {\"originalName\": \"br\", \"newName\": \"br element\"})\n            self.tree.reconstructActiveFormattingElements()\n            self.tree.insertElement(impliedTagToken(\"br\", \"StartTag\"))\n            self.tree.openElements.pop()\n\n        def endTagOther(self, token):\n            for node in self.tree.openElements[::-1]:\n                if node.name == token[\"name\"]:\n                    self.tree.generateImpliedEndTags(exclude=token[\"name\"])\n                    if self.tree.openElements[-1].name != token[\"name\"]:\n                        self.parser.parseError(\"unexpected-end-tag\", {\"name\": token[\"name\"]})\n                    while self.tree.openElements.pop() != node:\n                        pass\n                    break\n                else:\n                    if node.nameTuple in specialElements:\n                        self.parser.parseError(\"unexpected-end-tag\", {\"name\": token[\"name\"]})\n                        break\n\n    class TextPhase(Phase):\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n            self.startTagHandler = _utils.MethodDispatcher([])\n            self.startTagHandler.default = self.startTagOther\n            self.endTagHandler = _utils.MethodDispatcher([\n                (\"script\", self.endTagScript)])\n            self.endTagHandler.default = self.endTagOther\n\n        def processCharacters(self, token):\n            self.tree.insertText(token[\"data\"])\n\n        def processEOF(self):\n            self.parser.parseError(\"expected-named-closing-tag-but-got-eof\",\n                                   {\"name\": self.tree.openElements[-1].name})\n            self.tree.openElements.pop()\n            self.parser.phase = self.parser.originalPhase\n            return True\n\n        def startTagOther(self, token):\n            assert False, \"Tried to process start tag %s in RCDATA/RAWTEXT mode\" % token['name']\n\n        def endTagScript(self, token):\n            node = self.tree.openElements.pop()\n            assert node.name == \"script\"\n            self.parser.phase = self.parser.originalPhase\n            # The rest of this method is all stuff that only happens if\n            # document.write works\n\n        def endTagOther(self, token):\n            self.tree.openElements.pop()\n            self.parser.phase = self.parser.originalPhase\n\n    class InTablePhase(Phase):\n        # http://www.whatwg.org/specs/web-apps/current-work/#in-table\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                (\"caption\", self.startTagCaption),\n                (\"colgroup\", self.startTagColgroup),\n                (\"col\", self.startTagCol),\n                ((\"tbody\", \"tfoot\", \"thead\"), self.startTagRowGroup),\n                ((\"td\", \"th\", \"tr\"), self.startTagImplyTbody),\n                (\"table\", self.startTagTable),\n                ((\"style\", \"script\"), self.startTagStyleScript),\n                (\"input\", self.startTagInput),\n                (\"form\", self.startTagForm)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                (\"table\", self.endTagTable),\n                ((\"body\", \"caption\", \"col\", \"colgroup\", \"html\", \"tbody\", \"td\",\n                  \"tfoot\", \"th\", \"thead\", \"tr\"), self.endTagIgnore)\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        # helper methods\n        def clearStackToTableContext(self):\n            # \"clear the stack back to a table context\"\n            while self.tree.openElements[-1].name not in (\"table\", \"html\"):\n                # self.parser.parseError(\"unexpected-implied-end-tag-in-table\",\n                #  {\"name\":  self.tree.openElements[-1].name})\n                self.tree.openElements.pop()\n            # When the current node is <html> it's an innerHTML case\n\n        # processing methods\n        def processEOF(self):\n            if self.tree.openElements[-1].name != \"html\":\n                self.parser.parseError(\"eof-in-table\")\n            else:\n                assert self.parser.innerHTML\n            # Stop parsing\n\n        def processSpaceCharacters(self, token):\n            originalPhase = self.parser.phase\n            self.parser.phase = self.parser.phases[\"inTableText\"]\n            self.parser.phase.originalPhase = originalPhase\n            self.parser.phase.processSpaceCharacters(token)\n\n        def processCharacters(self, token):\n            originalPhase = self.parser.phase\n            self.parser.phase = self.parser.phases[\"inTableText\"]\n            self.parser.phase.originalPhase = originalPhase\n            self.parser.phase.processCharacters(token)\n\n        def insertText(self, token):\n            # If we get here there must be at least one non-whitespace character\n            # Do the table magic!\n            self.tree.insertFromTable = True\n            self.parser.phases[\"inBody\"].processCharacters(token)\n            self.tree.insertFromTable = False\n\n        def startTagCaption(self, token):\n            self.clearStackToTableContext()\n            self.tree.activeFormattingElements.append(Marker)\n            self.tree.insertElement(token)\n            self.parser.phase = self.parser.phases[\"inCaption\"]\n\n        def startTagColgroup(self, token):\n            self.clearStackToTableContext()\n            self.tree.insertElement(token)\n            self.parser.phase = self.parser.phases[\"inColumnGroup\"]\n\n        def startTagCol(self, token):\n            self.startTagColgroup(impliedTagToken(\"colgroup\", \"StartTag\"))\n            return token\n\n        def startTagRowGroup(self, token):\n            self.clearStackToTableContext()\n            self.tree.insertElement(token)\n            self.parser.phase = self.parser.phases[\"inTableBody\"]\n\n        def startTagImplyTbody(self, token):\n            self.startTagRowGroup(impliedTagToken(\"tbody\", \"StartTag\"))\n            return token\n\n        def startTagTable(self, token):\n            self.parser.parseError(\"unexpected-start-tag-implies-end-tag\",\n                                   {\"startName\": \"table\", \"endName\": \"table\"})\n            self.parser.phase.processEndTag(impliedTagToken(\"table\"))\n            if not self.parser.innerHTML:\n                return token\n\n        def startTagStyleScript(self, token):\n            return self.parser.phases[\"inHead\"].processStartTag(token)\n\n        def startTagInput(self, token):\n            if (\"type\" in token[\"data\"] and\n                    token[\"data\"][\"type\"].translate(asciiUpper2Lower) == \"hidden\"):\n                self.parser.parseError(\"unexpected-hidden-input-in-table\")\n                self.tree.insertElement(token)\n                # XXX associate with form\n                self.tree.openElements.pop()\n            else:\n                self.startTagOther(token)\n\n        def startTagForm(self, token):\n            self.parser.parseError(\"unexpected-form-in-table\")\n            if self.tree.formPointer is None:\n                self.tree.insertElement(token)\n                self.tree.formPointer = self.tree.openElements[-1]\n                self.tree.openElements.pop()\n\n        def startTagOther(self, token):\n            self.parser.parseError(\"unexpected-start-tag-implies-table-voodoo\", {\"name\": token[\"name\"]})\n            # Do the table magic!\n            self.tree.insertFromTable = True\n            self.parser.phases[\"inBody\"].processStartTag(token)\n            self.tree.insertFromTable = False\n\n        def endTagTable(self, token):\n            if self.tree.elementInScope(\"table\", variant=\"table\"):\n                self.tree.generateImpliedEndTags()\n                if self.tree.openElements[-1].name != \"table\":\n                    self.parser.parseError(\"end-tag-too-early-named\",\n                                           {\"gotName\": \"table\",\n                                            \"expectedName\": self.tree.openElements[-1].name})\n                while self.tree.openElements[-1].name != \"table\":\n                    self.tree.openElements.pop()\n                self.tree.openElements.pop()\n                self.parser.resetInsertionMode()\n            else:\n                # innerHTML case\n                assert self.parser.innerHTML\n                self.parser.parseError()\n\n        def endTagIgnore(self, token):\n            self.parser.parseError(\"unexpected-end-tag\", {\"name\": token[\"name\"]})\n\n        def endTagOther(self, token):\n            self.parser.parseError(\"unexpected-end-tag-implies-table-voodoo\", {\"name\": token[\"name\"]})\n            # Do the table magic!\n            self.tree.insertFromTable = True\n            self.parser.phases[\"inBody\"].processEndTag(token)\n            self.tree.insertFromTable = False\n\n    class InTableTextPhase(Phase):\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n            self.originalPhase = None\n            self.characterTokens = []\n\n        def flushCharacters(self):\n            data = \"\".join([item[\"data\"] for item in self.characterTokens])\n            if any([item not in spaceCharacters for item in data]):\n                token = {\"type\": tokenTypes[\"Characters\"], \"data\": data}\n                self.parser.phases[\"inTable\"].insertText(token)\n            elif data:\n                self.tree.insertText(data)\n            self.characterTokens = []\n\n        def processComment(self, token):\n            self.flushCharacters()\n            self.parser.phase = self.originalPhase\n            return token\n\n        def processEOF(self):\n            self.flushCharacters()\n            self.parser.phase = self.originalPhase\n            return True\n\n        def processCharacters(self, token):\n            if token[\"data\"] == \"\\u0000\":\n                return\n            self.characterTokens.append(token)\n\n        def processSpaceCharacters(self, token):\n            # pretty sure we should never reach here\n            self.characterTokens.append(token)\n    #        assert False\n\n        def processStartTag(self, token):\n            self.flushCharacters()\n            self.parser.phase = self.originalPhase\n            return token\n\n        def processEndTag(self, token):\n            self.flushCharacters()\n            self.parser.phase = self.originalPhase\n            return token\n\n    class InCaptionPhase(Phase):\n        # http://www.whatwg.org/specs/web-apps/current-work/#in-caption\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                ((\"caption\", \"col\", \"colgroup\", \"tbody\", \"td\", \"tfoot\", \"th\",\n                  \"thead\", \"tr\"), self.startTagTableElement)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                (\"caption\", self.endTagCaption),\n                (\"table\", self.endTagTable),\n                ((\"body\", \"col\", \"colgroup\", \"html\", \"tbody\", \"td\", \"tfoot\", \"th\",\n                  \"thead\", \"tr\"), self.endTagIgnore)\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        def ignoreEndTagCaption(self):\n            return not self.tree.elementInScope(\"caption\", variant=\"table\")\n\n        def processEOF(self):\n            self.parser.phases[\"inBody\"].processEOF()\n\n        def processCharacters(self, token):\n            return self.parser.phases[\"inBody\"].processCharacters(token)\n\n        def startTagTableElement(self, token):\n            self.parser.parseError()\n            # XXX Have to duplicate logic here to find out if the tag is ignored\n            ignoreEndTag = self.ignoreEndTagCaption()\n            self.parser.phase.processEndTag(impliedTagToken(\"caption\"))\n            if not ignoreEndTag:\n                return token\n\n        def startTagOther(self, token):\n            return self.parser.phases[\"inBody\"].processStartTag(token)\n\n        def endTagCaption(self, token):\n            if not self.ignoreEndTagCaption():\n                # AT this code is quite similar to endTagTable in \"InTable\"\n                self.tree.generateImpliedEndTags()\n                if self.tree.openElements[-1].name != \"caption\":\n                    self.parser.parseError(\"expected-one-end-tag-but-got-another\",\n                                           {\"gotName\": \"caption\",\n                                            \"expectedName\": self.tree.openElements[-1].name})\n                while self.tree.openElements[-1].name != \"caption\":\n                    self.tree.openElements.pop()\n                self.tree.openElements.pop()\n                self.tree.clearActiveFormattingElements()\n                self.parser.phase = self.parser.phases[\"inTable\"]\n            else:\n                # innerHTML case\n                assert self.parser.innerHTML\n                self.parser.parseError()\n\n        def endTagTable(self, token):\n            self.parser.parseError()\n            ignoreEndTag = self.ignoreEndTagCaption()\n            self.parser.phase.processEndTag(impliedTagToken(\"caption\"))\n            if not ignoreEndTag:\n                return token\n\n        def endTagIgnore(self, token):\n            self.parser.parseError(\"unexpected-end-tag\", {\"name\": token[\"name\"]})\n\n        def endTagOther(self, token):\n            return self.parser.phases[\"inBody\"].processEndTag(token)\n\n    class InColumnGroupPhase(Phase):\n        # http://www.whatwg.org/specs/web-apps/current-work/#in-column\n\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                (\"col\", self.startTagCol)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                (\"colgroup\", self.endTagColgroup),\n                (\"col\", self.endTagCol)\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        def ignoreEndTagColgroup(self):\n            return self.tree.openElements[-1].name == \"html\"\n\n        def processEOF(self):\n            if self.tree.openElements[-1].name == \"html\":\n                assert self.parser.innerHTML\n                return\n            else:\n                ignoreEndTag = self.ignoreEndTagColgroup()\n                self.endTagColgroup(impliedTagToken(\"colgroup\"))\n                if not ignoreEndTag:\n                    return True\n\n        def processCharacters(self, token):\n            ignoreEndTag = self.ignoreEndTagColgroup()\n            self.endTagColgroup(impliedTagToken(\"colgroup\"))\n            if not ignoreEndTag:\n                return token\n\n        def startTagCol(self, token):\n            self.tree.insertElement(token)\n            self.tree.openElements.pop()\n            token[\"selfClosingAcknowledged\"] = True\n\n        def startTagOther(self, token):\n            ignoreEndTag = self.ignoreEndTagColgroup()\n            self.endTagColgroup(impliedTagToken(\"colgroup\"))\n            if not ignoreEndTag:\n                return token\n\n        def endTagColgroup(self, token):\n            if self.ignoreEndTagColgroup():\n                # innerHTML case\n                assert self.parser.innerHTML\n                self.parser.parseError()\n            else:\n                self.tree.openElements.pop()\n                self.parser.phase = self.parser.phases[\"inTable\"]\n\n        def endTagCol(self, token):\n            self.parser.parseError(\"no-end-tag\", {\"name\": \"col\"})\n\n        def endTagOther(self, token):\n            ignoreEndTag = self.ignoreEndTagColgroup()\n            self.endTagColgroup(impliedTagToken(\"colgroup\"))\n            if not ignoreEndTag:\n                return token\n\n    class InTableBodyPhase(Phase):\n        # http://www.whatwg.org/specs/web-apps/current-work/#in-table0\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                (\"tr\", self.startTagTr),\n                ((\"td\", \"th\"), self.startTagTableCell),\n                ((\"caption\", \"col\", \"colgroup\", \"tbody\", \"tfoot\", \"thead\"),\n                 self.startTagTableOther)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                ((\"tbody\", \"tfoot\", \"thead\"), self.endTagTableRowGroup),\n                (\"table\", self.endTagTable),\n                ((\"body\", \"caption\", \"col\", \"colgroup\", \"html\", \"td\", \"th\",\n                  \"tr\"), self.endTagIgnore)\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        # helper methods\n        def clearStackToTableBodyContext(self):\n            while self.tree.openElements[-1].name not in (\"tbody\", \"tfoot\",\n                                                          \"thead\", \"html\"):\n                # self.parser.parseError(\"unexpected-implied-end-tag-in-table\",\n                #  {\"name\": self.tree.openElements[-1].name})\n                self.tree.openElements.pop()\n            if self.tree.openElements[-1].name == \"html\":\n                assert self.parser.innerHTML\n\n        # the rest\n        def processEOF(self):\n            self.parser.phases[\"inTable\"].processEOF()\n\n        def processSpaceCharacters(self, token):\n            return self.parser.phases[\"inTable\"].processSpaceCharacters(token)\n\n        def processCharacters(self, token):\n            return self.parser.phases[\"inTable\"].processCharacters(token)\n\n        def startTagTr(self, token):\n            self.clearStackToTableBodyContext()\n            self.tree.insertElement(token)\n            self.parser.phase = self.parser.phases[\"inRow\"]\n\n        def startTagTableCell(self, token):\n            self.parser.parseError(\"unexpected-cell-in-table-body\",\n                                   {\"name\": token[\"name\"]})\n            self.startTagTr(impliedTagToken(\"tr\", \"StartTag\"))\n            return token\n\n        def startTagTableOther(self, token):\n            # XXX AT Any ideas on how to share this with endTagTable?\n            if (self.tree.elementInScope(\"tbody\", variant=\"table\") or\n                self.tree.elementInScope(\"thead\", variant=\"table\") or\n                    self.tree.elementInScope(\"tfoot\", variant=\"table\")):\n                self.clearStackToTableBodyContext()\n                self.endTagTableRowGroup(\n                    impliedTagToken(self.tree.openElements[-1].name))\n                return token\n            else:\n                # innerHTML case\n                assert self.parser.innerHTML\n                self.parser.parseError()\n\n        def startTagOther(self, token):\n            return self.parser.phases[\"inTable\"].processStartTag(token)\n\n        def endTagTableRowGroup(self, token):\n            if self.tree.elementInScope(token[\"name\"], variant=\"table\"):\n                self.clearStackToTableBodyContext()\n                self.tree.openElements.pop()\n                self.parser.phase = self.parser.phases[\"inTable\"]\n            else:\n                self.parser.parseError(\"unexpected-end-tag-in-table-body\",\n                                       {\"name\": token[\"name\"]})\n\n        def endTagTable(self, token):\n            if (self.tree.elementInScope(\"tbody\", variant=\"table\") or\n                self.tree.elementInScope(\"thead\", variant=\"table\") or\n                    self.tree.elementInScope(\"tfoot\", variant=\"table\")):\n                self.clearStackToTableBodyContext()\n                self.endTagTableRowGroup(\n                    impliedTagToken(self.tree.openElements[-1].name))\n                return token\n            else:\n                # innerHTML case\n                assert self.parser.innerHTML\n                self.parser.parseError()\n\n        def endTagIgnore(self, token):\n            self.parser.parseError(\"unexpected-end-tag-in-table-body\",\n                                   {\"name\": token[\"name\"]})\n\n        def endTagOther(self, token):\n            return self.parser.phases[\"inTable\"].processEndTag(token)\n\n    class InRowPhase(Phase):\n        # http://www.whatwg.org/specs/web-apps/current-work/#in-row\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                ((\"td\", \"th\"), self.startTagTableCell),\n                ((\"caption\", \"col\", \"colgroup\", \"tbody\", \"tfoot\", \"thead\",\n                  \"tr\"), self.startTagTableOther)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                (\"tr\", self.endTagTr),\n                (\"table\", self.endTagTable),\n                ((\"tbody\", \"tfoot\", \"thead\"), self.endTagTableRowGroup),\n                ((\"body\", \"caption\", \"col\", \"colgroup\", \"html\", \"td\", \"th\"),\n                 self.endTagIgnore)\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        # helper methods (XXX unify this with other table helper methods)\n        def clearStackToTableRowContext(self):\n            while self.tree.openElements[-1].name not in (\"tr\", \"html\"):\n                self.parser.parseError(\"unexpected-implied-end-tag-in-table-row\",\n                                       {\"name\": self.tree.openElements[-1].name})\n                self.tree.openElements.pop()\n\n        def ignoreEndTagTr(self):\n            return not self.tree.elementInScope(\"tr\", variant=\"table\")\n\n        # the rest\n        def processEOF(self):\n            self.parser.phases[\"inTable\"].processEOF()\n\n        def processSpaceCharacters(self, token):\n            return self.parser.phases[\"inTable\"].processSpaceCharacters(token)\n\n        def processCharacters(self, token):\n            return self.parser.phases[\"inTable\"].processCharacters(token)\n\n        def startTagTableCell(self, token):\n            self.clearStackToTableRowContext()\n            self.tree.insertElement(token)\n            self.parser.phase = self.parser.phases[\"inCell\"]\n            self.tree.activeFormattingElements.append(Marker)\n\n        def startTagTableOther(self, token):\n            ignoreEndTag = self.ignoreEndTagTr()\n            self.endTagTr(impliedTagToken(\"tr\"))\n            # XXX how are we sure it's always ignored in the innerHTML case?\n            if not ignoreEndTag:\n                return token\n\n        def startTagOther(self, token):\n            return self.parser.phases[\"inTable\"].processStartTag(token)\n\n        def endTagTr(self, token):\n            if not self.ignoreEndTagTr():\n                self.clearStackToTableRowContext()\n                self.tree.openElements.pop()\n                self.parser.phase = self.parser.phases[\"inTableBody\"]\n            else:\n                # innerHTML case\n                assert self.parser.innerHTML\n                self.parser.parseError()\n\n        def endTagTable(self, token):\n            ignoreEndTag = self.ignoreEndTagTr()\n            self.endTagTr(impliedTagToken(\"tr\"))\n            # Reprocess the current tag if the tr end tag was not ignored\n            # XXX how are we sure it's always ignored in the innerHTML case?\n            if not ignoreEndTag:\n                return token\n\n        def endTagTableRowGroup(self, token):\n            if self.tree.elementInScope(token[\"name\"], variant=\"table\"):\n                self.endTagTr(impliedTagToken(\"tr\"))\n                return token\n            else:\n                self.parser.parseError()\n\n        def endTagIgnore(self, token):\n            self.parser.parseError(\"unexpected-end-tag-in-table-row\",\n                                   {\"name\": token[\"name\"]})\n\n        def endTagOther(self, token):\n            return self.parser.phases[\"inTable\"].processEndTag(token)\n\n    class InCellPhase(Phase):\n        # http://www.whatwg.org/specs/web-apps/current-work/#in-cell\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                ((\"caption\", \"col\", \"colgroup\", \"tbody\", \"td\", \"tfoot\", \"th\",\n                  \"thead\", \"tr\"), self.startTagTableOther)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                ((\"td\", \"th\"), self.endTagTableCell),\n                ((\"body\", \"caption\", \"col\", \"colgroup\", \"html\"), self.endTagIgnore),\n                ((\"table\", \"tbody\", \"tfoot\", \"thead\", \"tr\"), self.endTagImply)\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        # helper\n        def closeCell(self):\n            if self.tree.elementInScope(\"td\", variant=\"table\"):\n                self.endTagTableCell(impliedTagToken(\"td\"))\n            elif self.tree.elementInScope(\"th\", variant=\"table\"):\n                self.endTagTableCell(impliedTagToken(\"th\"))\n\n        # the rest\n        def processEOF(self):\n            self.parser.phases[\"inBody\"].processEOF()\n\n        def processCharacters(self, token):\n            return self.parser.phases[\"inBody\"].processCharacters(token)\n\n        def startTagTableOther(self, token):\n            if (self.tree.elementInScope(\"td\", variant=\"table\") or\n                    self.tree.elementInScope(\"th\", variant=\"table\")):\n                self.closeCell()\n                return token\n            else:\n                # innerHTML case\n                assert self.parser.innerHTML\n                self.parser.parseError()\n\n        def startTagOther(self, token):\n            return self.parser.phases[\"inBody\"].processStartTag(token)\n\n        def endTagTableCell(self, token):\n            if self.tree.elementInScope(token[\"name\"], variant=\"table\"):\n                self.tree.generateImpliedEndTags(token[\"name\"])\n                if self.tree.openElements[-1].name != token[\"name\"]:\n                    self.parser.parseError(\"unexpected-cell-end-tag\",\n                                           {\"name\": token[\"name\"]})\n                    while True:\n                        node = self.tree.openElements.pop()\n                        if node.name == token[\"name\"]:\n                            break\n                else:\n                    self.tree.openElements.pop()\n                self.tree.clearActiveFormattingElements()\n                self.parser.phase = self.parser.phases[\"inRow\"]\n            else:\n                self.parser.parseError(\"unexpected-end-tag\", {\"name\": token[\"name\"]})\n\n        def endTagIgnore(self, token):\n            self.parser.parseError(\"unexpected-end-tag\", {\"name\": token[\"name\"]})\n\n        def endTagImply(self, token):\n            if self.tree.elementInScope(token[\"name\"], variant=\"table\"):\n                self.closeCell()\n                return token\n            else:\n                # sometimes innerHTML case\n                self.parser.parseError()\n\n        def endTagOther(self, token):\n            return self.parser.phases[\"inBody\"].processEndTag(token)\n\n    class InSelectPhase(Phase):\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                (\"option\", self.startTagOption),\n                (\"optgroup\", self.startTagOptgroup),\n                (\"select\", self.startTagSelect),\n                ((\"input\", \"keygen\", \"textarea\"), self.startTagInput),\n                (\"script\", self.startTagScript)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                (\"option\", self.endTagOption),\n                (\"optgroup\", self.endTagOptgroup),\n                (\"select\", self.endTagSelect)\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        # http://www.whatwg.org/specs/web-apps/current-work/#in-select\n        def processEOF(self):\n            if self.tree.openElements[-1].name != \"html\":\n                self.parser.parseError(\"eof-in-select\")\n            else:\n                assert self.parser.innerHTML\n\n        def processCharacters(self, token):\n            if token[\"data\"] == \"\\u0000\":\n                return\n            self.tree.insertText(token[\"data\"])\n\n        def startTagOption(self, token):\n            # We need to imply </option> if <option> is the current node.\n            if self.tree.openElements[-1].name == \"option\":\n                self.tree.openElements.pop()\n            self.tree.insertElement(token)\n\n        def startTagOptgroup(self, token):\n            if self.tree.openElements[-1].name == \"option\":\n                self.tree.openElements.pop()\n            if self.tree.openElements[-1].name == \"optgroup\":\n                self.tree.openElements.pop()\n            self.tree.insertElement(token)\n\n        def startTagSelect(self, token):\n            self.parser.parseError(\"unexpected-select-in-select\")\n            self.endTagSelect(impliedTagToken(\"select\"))\n\n        def startTagInput(self, token):\n            self.parser.parseError(\"unexpected-input-in-select\")\n            if self.tree.elementInScope(\"select\", variant=\"select\"):\n                self.endTagSelect(impliedTagToken(\"select\"))\n                return token\n            else:\n                assert self.parser.innerHTML\n\n        def startTagScript(self, token):\n            return self.parser.phases[\"inHead\"].processStartTag(token)\n\n        def startTagOther(self, token):\n            self.parser.parseError(\"unexpected-start-tag-in-select\",\n                                   {\"name\": token[\"name\"]})\n\n        def endTagOption(self, token):\n            if self.tree.openElements[-1].name == \"option\":\n                self.tree.openElements.pop()\n            else:\n                self.parser.parseError(\"unexpected-end-tag-in-select\",\n                                       {\"name\": \"option\"})\n\n        def endTagOptgroup(self, token):\n            # </optgroup> implicitly closes <option>\n            if (self.tree.openElements[-1].name == \"option\" and\n                    self.tree.openElements[-2].name == \"optgroup\"):\n                self.tree.openElements.pop()\n            # It also closes </optgroup>\n            if self.tree.openElements[-1].name == \"optgroup\":\n                self.tree.openElements.pop()\n            # But nothing else\n            else:\n                self.parser.parseError(\"unexpected-end-tag-in-select\",\n                                       {\"name\": \"optgroup\"})\n\n        def endTagSelect(self, token):\n            if self.tree.elementInScope(\"select\", variant=\"select\"):\n                node = self.tree.openElements.pop()\n                while node.name != \"select\":\n                    node = self.tree.openElements.pop()\n                self.parser.resetInsertionMode()\n            else:\n                # innerHTML case\n                assert self.parser.innerHTML\n                self.parser.parseError()\n\n        def endTagOther(self, token):\n            self.parser.parseError(\"unexpected-end-tag-in-select\",\n                                   {\"name\": token[\"name\"]})\n\n    class InSelectInTablePhase(Phase):\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                ((\"caption\", \"table\", \"tbody\", \"tfoot\", \"thead\", \"tr\", \"td\", \"th\"),\n                 self.startTagTable)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                ((\"caption\", \"table\", \"tbody\", \"tfoot\", \"thead\", \"tr\", \"td\", \"th\"),\n                 self.endTagTable)\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        def processEOF(self):\n            self.parser.phases[\"inSelect\"].processEOF()\n\n        def processCharacters(self, token):\n            return self.parser.phases[\"inSelect\"].processCharacters(token)\n\n        def startTagTable(self, token):\n            self.parser.parseError(\"unexpected-table-element-start-tag-in-select-in-table\", {\"name\": token[\"name\"]})\n            self.endTagOther(impliedTagToken(\"select\"))\n            return token\n\n        def startTagOther(self, token):\n            return self.parser.phases[\"inSelect\"].processStartTag(token)\n\n        def endTagTable(self, token):\n            self.parser.parseError(\"unexpected-table-element-end-tag-in-select-in-table\", {\"name\": token[\"name\"]})\n            if self.tree.elementInScope(token[\"name\"], variant=\"table\"):\n                self.endTagOther(impliedTagToken(\"select\"))\n                return token\n\n        def endTagOther(self, token):\n            return self.parser.phases[\"inSelect\"].processEndTag(token)\n\n    class InForeignContentPhase(Phase):\n        breakoutElements = frozenset([\"b\", \"big\", \"blockquote\", \"body\", \"br\",\n                                      \"center\", \"code\", \"dd\", \"div\", \"dl\", \"dt\",\n                                      \"em\", \"embed\", \"h1\", \"h2\", \"h3\",\n                                      \"h4\", \"h5\", \"h6\", \"head\", \"hr\", \"i\", \"img\",\n                                      \"li\", \"listing\", \"menu\", \"meta\", \"nobr\",\n                                      \"ol\", \"p\", \"pre\", \"ruby\", \"s\", \"small\",\n                                      \"span\", \"strong\", \"strike\", \"sub\", \"sup\",\n                                      \"table\", \"tt\", \"u\", \"ul\", \"var\"])\n\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n        def adjustSVGTagNames(self, token):\n            replacements = {\"altglyph\": \"altGlyph\",\n                            \"altglyphdef\": \"altGlyphDef\",\n                            \"altglyphitem\": \"altGlyphItem\",\n                            \"animatecolor\": \"animateColor\",\n                            \"animatemotion\": \"animateMotion\",\n                            \"animatetransform\": \"animateTransform\",\n                            \"clippath\": \"clipPath\",\n                            \"feblend\": \"feBlend\",\n                            \"fecolormatrix\": \"feColorMatrix\",\n                            \"fecomponenttransfer\": \"feComponentTransfer\",\n                            \"fecomposite\": \"feComposite\",\n                            \"feconvolvematrix\": \"feConvolveMatrix\",\n                            \"fediffuselighting\": \"feDiffuseLighting\",\n                            \"fedisplacementmap\": \"feDisplacementMap\",\n                            \"fedistantlight\": \"feDistantLight\",\n                            \"feflood\": \"feFlood\",\n                            \"fefunca\": \"feFuncA\",\n                            \"fefuncb\": \"feFuncB\",\n                            \"fefuncg\": \"feFuncG\",\n                            \"fefuncr\": \"feFuncR\",\n                            \"fegaussianblur\": \"feGaussianBlur\",\n                            \"feimage\": \"feImage\",\n                            \"femerge\": \"feMerge\",\n                            \"femergenode\": \"feMergeNode\",\n                            \"femorphology\": \"feMorphology\",\n                            \"feoffset\": \"feOffset\",\n                            \"fepointlight\": \"fePointLight\",\n                            \"fespecularlighting\": \"feSpecularLighting\",\n                            \"fespotlight\": \"feSpotLight\",\n                            \"fetile\": \"feTile\",\n                            \"feturbulence\": \"feTurbulence\",\n                            \"foreignobject\": \"foreignObject\",\n                            \"glyphref\": \"glyphRef\",\n                            \"lineargradient\": \"linearGradient\",\n                            \"radialgradient\": \"radialGradient\",\n                            \"textpath\": \"textPath\"}\n\n            if token[\"name\"] in replacements:\n                token[\"name\"] = replacements[token[\"name\"]]\n\n        def processCharacters(self, token):\n            if token[\"data\"] == \"\\u0000\":\n                token[\"data\"] = \"\\uFFFD\"\n            elif (self.parser.framesetOK and\n                  any(char not in spaceCharacters for char in token[\"data\"])):\n                self.parser.framesetOK = False\n            Phase.processCharacters(self, token)\n\n        def processStartTag(self, token):\n            currentNode = self.tree.openElements[-1]\n            if (token[\"name\"] in self.breakoutElements or\n                (token[\"name\"] == \"font\" and\n                 set(token[\"data\"].keys()) & set([\"color\", \"face\", \"size\"]))):\n                self.parser.parseError(\"unexpected-html-element-in-foreign-content\",\n                                       {\"name\": token[\"name\"]})\n                while (self.tree.openElements[-1].namespace !=\n                       self.tree.defaultNamespace and\n                       not self.parser.isHTMLIntegrationPoint(self.tree.openElements[-1]) and\n                       not self.parser.isMathMLTextIntegrationPoint(self.tree.openElements[-1])):\n                    self.tree.openElements.pop()\n                return token\n\n            else:\n                if currentNode.namespace == namespaces[\"mathml\"]:\n                    self.parser.adjustMathMLAttributes(token)\n                elif currentNode.namespace == namespaces[\"svg\"]:\n                    self.adjustSVGTagNames(token)\n                    self.parser.adjustSVGAttributes(token)\n                self.parser.adjustForeignAttributes(token)\n                token[\"namespace\"] = currentNode.namespace\n                self.tree.insertElement(token)\n                if token[\"selfClosing\"]:\n                    self.tree.openElements.pop()\n                    token[\"selfClosingAcknowledged\"] = True\n\n        def processEndTag(self, token):\n            nodeIndex = len(self.tree.openElements) - 1\n            node = self.tree.openElements[-1]\n            if node.name.translate(asciiUpper2Lower) != token[\"name\"]:\n                self.parser.parseError(\"unexpected-end-tag\", {\"name\": token[\"name\"]})\n\n            while True:\n                if node.name.translate(asciiUpper2Lower) == token[\"name\"]:\n                    # XXX this isn't in the spec but it seems necessary\n                    if self.parser.phase == self.parser.phases[\"inTableText\"]:\n                        self.parser.phase.flushCharacters()\n                        self.parser.phase = self.parser.phase.originalPhase\n                    while self.tree.openElements.pop() != node:\n                        assert self.tree.openElements\n                    new_token = None\n                    break\n                nodeIndex -= 1\n\n                node = self.tree.openElements[nodeIndex]\n                if node.namespace != self.tree.defaultNamespace:\n                    continue\n                else:\n                    new_token = self.parser.phase.processEndTag(token)\n                    break\n            return new_token\n\n    class AfterBodyPhase(Phase):\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([(\"html\", self.endTagHtml)])\n            self.endTagHandler.default = self.endTagOther\n\n        def processEOF(self):\n            # Stop parsing\n            pass\n\n        def processComment(self, token):\n            # This is needed because data is to be appended to the <html> element\n            # here and not to whatever is currently open.\n            self.tree.insertComment(token, self.tree.openElements[0])\n\n        def processCharacters(self, token):\n            self.parser.parseError(\"unexpected-char-after-body\")\n            self.parser.phase = self.parser.phases[\"inBody\"]\n            return token\n\n        def startTagHtml(self, token):\n            return self.parser.phases[\"inBody\"].processStartTag(token)\n\n        def startTagOther(self, token):\n            self.parser.parseError(\"unexpected-start-tag-after-body\",\n                                   {\"name\": token[\"name\"]})\n            self.parser.phase = self.parser.phases[\"inBody\"]\n            return token\n\n        def endTagHtml(self, name):\n            if self.parser.innerHTML:\n                self.parser.parseError(\"unexpected-end-tag-after-body-innerhtml\")\n            else:\n                self.parser.phase = self.parser.phases[\"afterAfterBody\"]\n\n        def endTagOther(self, token):\n            self.parser.parseError(\"unexpected-end-tag-after-body\",\n                                   {\"name\": token[\"name\"]})\n            self.parser.phase = self.parser.phases[\"inBody\"]\n            return token\n\n    class InFramesetPhase(Phase):\n        # http://www.whatwg.org/specs/web-apps/current-work/#in-frameset\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                (\"frameset\", self.startTagFrameset),\n                (\"frame\", self.startTagFrame),\n                (\"noframes\", self.startTagNoframes)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                (\"frameset\", self.endTagFrameset)\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        def processEOF(self):\n            if self.tree.openElements[-1].name != \"html\":\n                self.parser.parseError(\"eof-in-frameset\")\n            else:\n                assert self.parser.innerHTML\n\n        def processCharacters(self, token):\n            self.parser.parseError(\"unexpected-char-in-frameset\")\n\n        def startTagFrameset(self, token):\n            self.tree.insertElement(token)\n\n        def startTagFrame(self, token):\n            self.tree.insertElement(token)\n            self.tree.openElements.pop()\n\n        def startTagNoframes(self, token):\n            return self.parser.phases[\"inBody\"].processStartTag(token)\n\n        def startTagOther(self, token):\n            self.parser.parseError(\"unexpected-start-tag-in-frameset\",\n                                   {\"name\": token[\"name\"]})\n\n        def endTagFrameset(self, token):\n            if self.tree.openElements[-1].name == \"html\":\n                # innerHTML case\n                self.parser.parseError(\"unexpected-frameset-in-frameset-innerhtml\")\n            else:\n                self.tree.openElements.pop()\n            if (not self.parser.innerHTML and\n                    self.tree.openElements[-1].name != \"frameset\"):\n                # If we're not in innerHTML mode and the current node is not a\n                # \"frameset\" element (anymore) then switch.\n                self.parser.phase = self.parser.phases[\"afterFrameset\"]\n\n        def endTagOther(self, token):\n            self.parser.parseError(\"unexpected-end-tag-in-frameset\",\n                                   {\"name\": token[\"name\"]})\n\n    class AfterFramesetPhase(Phase):\n        # http://www.whatwg.org/specs/web-apps/current-work/#after3\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                (\"noframes\", self.startTagNoframes)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n            self.endTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.endTagHtml)\n            ])\n            self.endTagHandler.default = self.endTagOther\n\n        def processEOF(self):\n            # Stop parsing\n            pass\n\n        def processCharacters(self, token):\n            self.parser.parseError(\"unexpected-char-after-frameset\")\n\n        def startTagNoframes(self, token):\n            return self.parser.phases[\"inHead\"].processStartTag(token)\n\n        def startTagOther(self, token):\n            self.parser.parseError(\"unexpected-start-tag-after-frameset\",\n                                   {\"name\": token[\"name\"]})\n\n        def endTagHtml(self, token):\n            self.parser.phase = self.parser.phases[\"afterAfterFrameset\"]\n\n        def endTagOther(self, token):\n            self.parser.parseError(\"unexpected-end-tag-after-frameset\",\n                                   {\"name\": token[\"name\"]})\n\n    class AfterAfterBodyPhase(Phase):\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n        def processEOF(self):\n            pass\n\n        def processComment(self, token):\n            self.tree.insertComment(token, self.tree.document)\n\n        def processSpaceCharacters(self, token):\n            return self.parser.phases[\"inBody\"].processSpaceCharacters(token)\n\n        def processCharacters(self, token):\n            self.parser.parseError(\"expected-eof-but-got-char\")\n            self.parser.phase = self.parser.phases[\"inBody\"]\n            return token\n\n        def startTagHtml(self, token):\n            return self.parser.phases[\"inBody\"].processStartTag(token)\n\n        def startTagOther(self, token):\n            self.parser.parseError(\"expected-eof-but-got-start-tag\",\n                                   {\"name\": token[\"name\"]})\n            self.parser.phase = self.parser.phases[\"inBody\"]\n            return token\n\n        def processEndTag(self, token):\n            self.parser.parseError(\"expected-eof-but-got-end-tag\",\n                                   {\"name\": token[\"name\"]})\n            self.parser.phase = self.parser.phases[\"inBody\"]\n            return token\n\n    class AfterAfterFramesetPhase(Phase):\n        def __init__(self, parser, tree):\n            Phase.__init__(self, parser, tree)\n\n            self.startTagHandler = _utils.MethodDispatcher([\n                (\"html\", self.startTagHtml),\n                (\"noframes\", self.startTagNoFrames)\n            ])\n            self.startTagHandler.default = self.startTagOther\n\n        def processEOF(self):\n            pass\n\n        def processComment(self, token):\n            self.tree.insertComment(token, self.tree.document)\n\n        def processSpaceCharacters(self, token):\n            return self.parser.phases[\"inBody\"].processSpaceCharacters(token)\n\n        def processCharacters(self, token):\n            self.parser.parseError(\"expected-eof-but-got-char\")\n\n        def startTagHtml(self, token):\n            return self.parser.phases[\"inBody\"].processStartTag(token)\n\n        def startTagNoFrames(self, token):\n            return self.parser.phases[\"inHead\"].processStartTag(token)\n\n        def startTagOther(self, token):\n            self.parser.parseError(\"expected-eof-but-got-start-tag\",\n                                   {\"name\": token[\"name\"]})\n\n        def processEndTag(self, token):\n            self.parser.parseError(\"expected-eof-but-got-end-tag\",\n                                   {\"name\": token[\"name\"]})\n    # pylint:enable=unused-argument\n\n    return {\n        \"initial\": InitialPhase,\n        \"beforeHtml\": BeforeHtmlPhase,\n        \"beforeHead\": BeforeHeadPhase,\n        \"inHead\": InHeadPhase,\n        \"inHeadNoscript\": InHeadNoscriptPhase,\n        \"afterHead\": AfterHeadPhase,\n        \"inBody\": InBodyPhase,\n        \"text\": TextPhase,\n        \"inTable\": InTablePhase,\n        \"inTableText\": InTableTextPhase,\n        \"inCaption\": InCaptionPhase,\n        \"inColumnGroup\": InColumnGroupPhase,\n        \"inTableBody\": InTableBodyPhase,\n        \"inRow\": InRowPhase,\n        \"inCell\": InCellPhase,\n        \"inSelect\": InSelectPhase,\n        \"inSelectInTable\": InSelectInTablePhase,\n        \"inForeignContent\": InForeignContentPhase,\n        \"afterBody\": AfterBodyPhase,\n        \"inFrameset\": InFramesetPhase,\n        \"afterFrameset\": AfterFramesetPhase,\n        \"afterAfterBody\": AfterAfterBodyPhase,\n        \"afterAfterFrameset\": AfterAfterFramesetPhase,\n        # XXX after after frameset\n    }\n\n\ndef adjust_attributes(token, replacements):\n    needs_adjustment = viewkeys(token['data']) & viewkeys(replacements)\n    if needs_adjustment:\n        token['data'] = OrderedDict((replacements.get(k, k), v)\n                                    for k, v in token['data'].items())\n\n\ndef impliedTagToken(name, type=\"EndTag\", attributes=None,\n                    selfClosing=False):\n    if attributes is None:\n        attributes = {}\n    return {\"type\": tokenTypes[type], \"name\": name, \"data\": attributes,\n            \"selfClosing\": selfClosing}\n\n\nclass ParseError(Exception):\n    \"\"\"Error in parsed document\"\"\"\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/serializer.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\nfrom pip._vendor.six import text_type\n\nimport re\n\nfrom codecs import register_error, xmlcharrefreplace_errors\n\nfrom .constants import voidElements, booleanAttributes, spaceCharacters\nfrom .constants import rcdataElements, entities, xmlEntities\nfrom . import treewalkers, _utils\nfrom xml.sax.saxutils import escape\n\n_quoteAttributeSpecChars = \"\".join(spaceCharacters) + \"\\\"'=<>`\"\n_quoteAttributeSpec = re.compile(\"[\" + _quoteAttributeSpecChars + \"]\")\n_quoteAttributeLegacy = re.compile(\"[\" + _quoteAttributeSpecChars +\n                                   \"\\x00\\x01\\x02\\x03\\x04\\x05\\x06\\x07\\x08\\t\\n\"\n                                   \"\\x0b\\x0c\\r\\x0e\\x0f\\x10\\x11\\x12\\x13\\x14\\x15\"\n                                   \"\\x16\\x17\\x18\\x19\\x1a\\x1b\\x1c\\x1d\\x1e\\x1f\"\n                                   \"\\x20\\x2f\\x60\\xa0\\u1680\\u180e\\u180f\\u2000\"\n                                   \"\\u2001\\u2002\\u2003\\u2004\\u2005\\u2006\\u2007\"\n                                   \"\\u2008\\u2009\\u200a\\u2028\\u2029\\u202f\\u205f\"\n                                   \"\\u3000]\")\n\n\n_encode_entity_map = {}\n_is_ucs4 = len(\"\\U0010FFFF\") == 1\nfor k, v in list(entities.items()):\n    # skip multi-character entities\n    if ((_is_ucs4 and len(v) > 1) or\n            (not _is_ucs4 and len(v) > 2)):\n        continue\n    if v != \"&\":\n        if len(v) == 2:\n            v = _utils.surrogatePairToCodepoint(v)\n        else:\n            v = ord(v)\n        if v not in _encode_entity_map or k.islower():\n            # prefer &lt; over &LT; and similarly for &amp;, &gt;, etc.\n            _encode_entity_map[v] = k\n\n\ndef htmlentityreplace_errors(exc):\n    if isinstance(exc, (UnicodeEncodeError, UnicodeTranslateError)):\n        res = []\n        codepoints = []\n        skip = False\n        for i, c in enumerate(exc.object[exc.start:exc.end]):\n            if skip:\n                skip = False\n                continue\n            index = i + exc.start\n            if _utils.isSurrogatePair(exc.object[index:min([exc.end, index + 2])]):\n                codepoint = _utils.surrogatePairToCodepoint(exc.object[index:index + 2])\n                skip = True\n            else:\n                codepoint = ord(c)\n            codepoints.append(codepoint)\n        for cp in codepoints:\n            e = _encode_entity_map.get(cp)\n            if e:\n                res.append(\"&\")\n                res.append(e)\n                if not e.endswith(\";\"):\n                    res.append(\";\")\n            else:\n                res.append(\"&#x%s;\" % (hex(cp)[2:]))\n        return (\"\".join(res), exc.end)\n    else:\n        return xmlcharrefreplace_errors(exc)\n\n\nregister_error(\"htmlentityreplace\", htmlentityreplace_errors)\n\n\ndef serialize(input, tree=\"etree\", encoding=None, **serializer_opts):\n    \"\"\"Serializes the input token stream using the specified treewalker\n\n    :arg input: the token stream to serialize\n\n    :arg tree: the treewalker to use\n\n    :arg encoding: the encoding to use\n\n    :arg serializer_opts: any options to pass to the\n        :py:class:`html5lib.serializer.HTMLSerializer` that gets created\n\n    :returns: the tree serialized as a string\n\n    Example:\n\n    >>> from html5lib.html5parser import parse\n    >>> from html5lib.serializer import serialize\n    >>> token_stream = parse('<html><body><p>Hi!</p></body></html>')\n    >>> serialize(token_stream, omit_optional_tags=False)\n    '<html><head></head><body><p>Hi!</p></body></html>'\n\n    \"\"\"\n    # XXX: Should we cache this?\n    walker = treewalkers.getTreeWalker(tree)\n    s = HTMLSerializer(**serializer_opts)\n    return s.render(walker(input), encoding)\n\n\nclass HTMLSerializer(object):\n\n    # attribute quoting options\n    quote_attr_values = \"legacy\"  # be secure by default\n    quote_char = '\"'\n    use_best_quote_char = True\n\n    # tag syntax options\n    omit_optional_tags = True\n    minimize_boolean_attributes = True\n    use_trailing_solidus = False\n    space_before_trailing_solidus = True\n\n    # escaping options\n    escape_lt_in_attrs = False\n    escape_rcdata = False\n    resolve_entities = True\n\n    # miscellaneous options\n    alphabetical_attributes = False\n    inject_meta_charset = True\n    strip_whitespace = False\n    sanitize = False\n\n    options = (\"quote_attr_values\", \"quote_char\", \"use_best_quote_char\",\n               \"omit_optional_tags\", \"minimize_boolean_attributes\",\n               \"use_trailing_solidus\", \"space_before_trailing_solidus\",\n               \"escape_lt_in_attrs\", \"escape_rcdata\", \"resolve_entities\",\n               \"alphabetical_attributes\", \"inject_meta_charset\",\n               \"strip_whitespace\", \"sanitize\")\n\n    def __init__(self, **kwargs):\n        \"\"\"Initialize HTMLSerializer\n\n        :arg inject_meta_charset: Whether or not to inject the meta charset.\n\n            Defaults to ``True``.\n\n        :arg quote_attr_values: Whether to quote attribute values that don't\n            require quoting per legacy browser behavior (``\"legacy\"``), when\n            required by the standard (``\"spec\"``), or always (``\"always\"``).\n\n            Defaults to ``\"legacy\"``.\n\n        :arg quote_char: Use given quote character for attribute quoting.\n\n            Defaults to ``\"`` which will use double quotes unless attribute\n            value contains a double quote, in which case single quotes are\n            used.\n\n        :arg escape_lt_in_attrs: Whether or not to escape ``<`` in attribute\n            values.\n\n            Defaults to ``False``.\n\n        :arg escape_rcdata: Whether to escape characters that need to be\n            escaped within normal elements within rcdata elements such as\n            style.\n\n            Defaults to ``False``.\n\n        :arg resolve_entities: Whether to resolve named character entities that\n            appear in the source tree. The XML predefined entities &lt; &gt;\n            &amp; &quot; &apos; are unaffected by this setting.\n\n            Defaults to ``True``.\n\n        :arg strip_whitespace: Whether to remove semantically meaningless\n            whitespace. (This compresses all whitespace to a single space\n            except within ``pre``.)\n\n            Defaults to ``False``.\n\n        :arg minimize_boolean_attributes: Shortens boolean attributes to give\n            just the attribute value, for example::\n\n              <input disabled=\"disabled\">\n\n            becomes::\n\n              <input disabled>\n\n            Defaults to ``True``.\n\n        :arg use_trailing_solidus: Includes a close-tag slash at the end of the\n            start tag of void elements (empty elements whose end tag is\n            forbidden). E.g. ``<hr/>``.\n\n            Defaults to ``False``.\n\n        :arg space_before_trailing_solidus: Places a space immediately before\n            the closing slash in a tag using a trailing solidus. E.g.\n            ``<hr />``. Requires ``use_trailing_solidus=True``.\n\n            Defaults to ``True``.\n\n        :arg sanitize: Strip all unsafe or unknown constructs from output.\n            See :py:class:`html5lib.filters.sanitizer.Filter`.\n\n            Defaults to ``False``.\n\n        :arg omit_optional_tags: Omit start/end tags that are optional.\n\n            Defaults to ``True``.\n\n        :arg alphabetical_attributes: Reorder attributes to be in alphabetical order.\n\n            Defaults to ``False``.\n\n        \"\"\"\n        unexpected_args = frozenset(kwargs) - frozenset(self.options)\n        if len(unexpected_args) > 0:\n            raise TypeError(\"__init__() got an unexpected keyword argument '%s'\" % next(iter(unexpected_args)))\n        if 'quote_char' in kwargs:\n            self.use_best_quote_char = False\n        for attr in self.options:\n            setattr(self, attr, kwargs.get(attr, getattr(self, attr)))\n        self.errors = []\n        self.strict = False\n\n    def encode(self, string):\n        assert(isinstance(string, text_type))\n        if self.encoding:\n            return string.encode(self.encoding, \"htmlentityreplace\")\n        else:\n            return string\n\n    def encodeStrict(self, string):\n        assert(isinstance(string, text_type))\n        if self.encoding:\n            return string.encode(self.encoding, \"strict\")\n        else:\n            return string\n\n    def serialize(self, treewalker, encoding=None):\n        # pylint:disable=too-many-nested-blocks\n        self.encoding = encoding\n        in_cdata = False\n        self.errors = []\n\n        if encoding and self.inject_meta_charset:\n            from .filters.inject_meta_charset import Filter\n            treewalker = Filter(treewalker, encoding)\n        # Alphabetical attributes is here under the assumption that none of\n        # the later filters add or change order of attributes; it needs to be\n        # before the sanitizer so escaped elements come out correctly\n        if self.alphabetical_attributes:\n            from .filters.alphabeticalattributes import Filter\n            treewalker = Filter(treewalker)\n        # WhitespaceFilter should be used before OptionalTagFilter\n        # for maximum efficiently of this latter filter\n        if self.strip_whitespace:\n            from .filters.whitespace import Filter\n            treewalker = Filter(treewalker)\n        if self.sanitize:\n            from .filters.sanitizer import Filter\n            treewalker = Filter(treewalker)\n        if self.omit_optional_tags:\n            from .filters.optionaltags import Filter\n            treewalker = Filter(treewalker)\n\n        for token in treewalker:\n            type = token[\"type\"]\n            if type == \"Doctype\":\n                doctype = \"<!DOCTYPE %s\" % token[\"name\"]\n\n                if token[\"publicId\"]:\n                    doctype += ' PUBLIC \"%s\"' % token[\"publicId\"]\n                elif token[\"systemId\"]:\n                    doctype += \" SYSTEM\"\n                if token[\"systemId\"]:\n                    if token[\"systemId\"].find('\"') >= 0:\n                        if token[\"systemId\"].find(\"'\") >= 0:\n                            self.serializeError(\"System identifer contains both single and double quote characters\")\n                        quote_char = \"'\"\n                    else:\n                        quote_char = '\"'\n                    doctype += \" %s%s%s\" % (quote_char, token[\"systemId\"], quote_char)\n\n                doctype += \">\"\n                yield self.encodeStrict(doctype)\n\n            elif type in (\"Characters\", \"SpaceCharacters\"):\n                if type == \"SpaceCharacters\" or in_cdata:\n                    if in_cdata and token[\"data\"].find(\"</\") >= 0:\n                        self.serializeError(\"Unexpected </ in CDATA\")\n                    yield self.encode(token[\"data\"])\n                else:\n                    yield self.encode(escape(token[\"data\"]))\n\n            elif type in (\"StartTag\", \"EmptyTag\"):\n                name = token[\"name\"]\n                yield self.encodeStrict(\"<%s\" % name)\n                if name in rcdataElements and not self.escape_rcdata:\n                    in_cdata = True\n                elif in_cdata:\n                    self.serializeError(\"Unexpected child element of a CDATA element\")\n                for (_, attr_name), attr_value in token[\"data\"].items():\n                    # TODO: Add namespace support here\n                    k = attr_name\n                    v = attr_value\n                    yield self.encodeStrict(' ')\n\n                    yield self.encodeStrict(k)\n                    if not self.minimize_boolean_attributes or \\\n                        (k not in booleanAttributes.get(name, tuple()) and\n                         k not in booleanAttributes.get(\"\", tuple())):\n                        yield self.encodeStrict(\"=\")\n                        if self.quote_attr_values == \"always\" or len(v) == 0:\n                            quote_attr = True\n                        elif self.quote_attr_values == \"spec\":\n                            quote_attr = _quoteAttributeSpec.search(v) is not None\n                        elif self.quote_attr_values == \"legacy\":\n                            quote_attr = _quoteAttributeLegacy.search(v) is not None\n                        else:\n                            raise ValueError(\"quote_attr_values must be one of: \"\n                                             \"'always', 'spec', or 'legacy'\")\n                        v = v.replace(\"&\", \"&amp;\")\n                        if self.escape_lt_in_attrs:\n                            v = v.replace(\"<\", \"&lt;\")\n                        if quote_attr:\n                            quote_char = self.quote_char\n                            if self.use_best_quote_char:\n                                if \"'\" in v and '\"' not in v:\n                                    quote_char = '\"'\n                                elif '\"' in v and \"'\" not in v:\n                                    quote_char = \"'\"\n                            if quote_char == \"'\":\n                                v = v.replace(\"'\", \"&#39;\")\n                            else:\n                                v = v.replace('\"', \"&quot;\")\n                            yield self.encodeStrict(quote_char)\n                            yield self.encode(v)\n                            yield self.encodeStrict(quote_char)\n                        else:\n                            yield self.encode(v)\n                if name in voidElements and self.use_trailing_solidus:\n                    if self.space_before_trailing_solidus:\n                        yield self.encodeStrict(\" /\")\n                    else:\n                        yield self.encodeStrict(\"/\")\n                yield self.encode(\">\")\n\n            elif type == \"EndTag\":\n                name = token[\"name\"]\n                if name in rcdataElements:\n                    in_cdata = False\n                elif in_cdata:\n                    self.serializeError(\"Unexpected child element of a CDATA element\")\n                yield self.encodeStrict(\"</%s>\" % name)\n\n            elif type == \"Comment\":\n                data = token[\"data\"]\n                if data.find(\"--\") >= 0:\n                    self.serializeError(\"Comment contains --\")\n                yield self.encodeStrict(\"<!--%s-->\" % token[\"data\"])\n\n            elif type == \"Entity\":\n                name = token[\"name\"]\n                key = name + \";\"\n                if key not in entities:\n                    self.serializeError(\"Entity %s not recognized\" % name)\n                if self.resolve_entities and key not in xmlEntities:\n                    data = entities[key]\n                else:\n                    data = \"&%s;\" % name\n                yield self.encodeStrict(data)\n\n            else:\n                self.serializeError(token[\"data\"])\n\n    def render(self, treewalker, encoding=None):\n        \"\"\"Serializes the stream from the treewalker into a string\n\n        :arg treewalker: the treewalker to serialize\n\n        :arg encoding: the string encoding to use\n\n        :returns: the serialized tree\n\n        Example:\n\n        >>> from html5lib import parse, getTreeWalker\n        >>> from html5lib.serializer import HTMLSerializer\n        >>> token_stream = parse('<html><body>Hi!</body></html>')\n        >>> walker = getTreeWalker('etree')\n        >>> serializer = HTMLSerializer(omit_optional_tags=False)\n        >>> serializer.render(walker(token_stream))\n        '<html><head></head><body>Hi!</body></html>'\n\n        \"\"\"\n        if encoding:\n            return b\"\".join(list(self.serialize(treewalker, encoding)))\n        else:\n            return \"\".join(list(self.serialize(treewalker)))\n\n    def serializeError(self, data=\"XXX ERROR MESSAGE NEEDED\"):\n        # XXX The idea is to make data mandatory.\n        self.errors.append(data)\n        if self.strict:\n            raise SerializeError\n\n\nclass SerializeError(Exception):\n    \"\"\"Error in serialized tree\"\"\"\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treeadapters/__init__.py",
    "content": "\"\"\"Tree adapters let you convert from one tree structure to another\n\nExample:\n\n.. code-block:: python\n\n   from pip._vendor import html5lib\n   from pip._vendor.html5lib.treeadapters import genshi\n\n   doc = '<html><body>Hi!</body></html>'\n   treebuilder = html5lib.getTreeBuilder('etree')\n   parser = html5lib.HTMLParser(tree=treebuilder)\n   tree = parser.parse(doc)\n   TreeWalker = html5lib.getTreeWalker('etree')\n\n   genshi_tree = genshi.to_genshi(TreeWalker(tree))\n\n\"\"\"\nfrom __future__ import absolute_import, division, unicode_literals\n\nfrom . import sax\n\n__all__ = [\"sax\"]\n\ntry:\n    from . import genshi  # noqa\nexcept ImportError:\n    pass\nelse:\n    __all__.append(\"genshi\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treeadapters/genshi.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom genshi.core import QName, Attrs\nfrom genshi.core import START, END, TEXT, COMMENT, DOCTYPE\n\n\ndef to_genshi(walker):\n    \"\"\"Convert a tree to a genshi tree\n\n    :arg walker: the treewalker to use to walk the tree to convert it\n\n    :returns: generator of genshi nodes\n\n    \"\"\"\n    text = []\n    for token in walker:\n        type = token[\"type\"]\n        if type in (\"Characters\", \"SpaceCharacters\"):\n            text.append(token[\"data\"])\n        elif text:\n            yield TEXT, \"\".join(text), (None, -1, -1)\n            text = []\n\n        if type in (\"StartTag\", \"EmptyTag\"):\n            if token[\"namespace\"]:\n                name = \"{%s}%s\" % (token[\"namespace\"], token[\"name\"])\n            else:\n                name = token[\"name\"]\n            attrs = Attrs([(QName(\"{%s}%s\" % attr if attr[0] is not None else attr[1]), value)\n                           for attr, value in token[\"data\"].items()])\n            yield (START, (QName(name), attrs), (None, -1, -1))\n            if type == \"EmptyTag\":\n                type = \"EndTag\"\n\n        if type == \"EndTag\":\n            if token[\"namespace\"]:\n                name = \"{%s}%s\" % (token[\"namespace\"], token[\"name\"])\n            else:\n                name = token[\"name\"]\n\n            yield END, QName(name), (None, -1, -1)\n\n        elif type == \"Comment\":\n            yield COMMENT, token[\"data\"], (None, -1, -1)\n\n        elif type == \"Doctype\":\n            yield DOCTYPE, (token[\"name\"], token[\"publicId\"],\n                            token[\"systemId\"]), (None, -1, -1)\n\n        else:\n            pass  # FIXME: What to do?\n\n    if text:\n        yield TEXT, \"\".join(text), (None, -1, -1)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treeadapters/sax.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom xml.sax.xmlreader import AttributesNSImpl\n\nfrom ..constants import adjustForeignAttributes, unadjustForeignAttributes\n\nprefix_mapping = {}\nfor prefix, localName, namespace in adjustForeignAttributes.values():\n    if prefix is not None:\n        prefix_mapping[prefix] = namespace\n\n\ndef to_sax(walker, handler):\n    \"\"\"Call SAX-like content handler based on treewalker walker\n\n    :arg walker: the treewalker to use to walk the tree to convert it\n\n    :arg handler: SAX handler to use\n\n    \"\"\"\n    handler.startDocument()\n    for prefix, namespace in prefix_mapping.items():\n        handler.startPrefixMapping(prefix, namespace)\n\n    for token in walker:\n        type = token[\"type\"]\n        if type == \"Doctype\":\n            continue\n        elif type in (\"StartTag\", \"EmptyTag\"):\n            attrs = AttributesNSImpl(token[\"data\"],\n                                     unadjustForeignAttributes)\n            handler.startElementNS((token[\"namespace\"], token[\"name\"]),\n                                   token[\"name\"],\n                                   attrs)\n            if type == \"EmptyTag\":\n                handler.endElementNS((token[\"namespace\"], token[\"name\"]),\n                                     token[\"name\"])\n        elif type == \"EndTag\":\n            handler.endElementNS((token[\"namespace\"], token[\"name\"]),\n                                 token[\"name\"])\n        elif type in (\"Characters\", \"SpaceCharacters\"):\n            handler.characters(token[\"data\"])\n        elif type == \"Comment\":\n            pass\n        else:\n            assert False, \"Unknown token type\"\n\n    for prefix, namespace in prefix_mapping.items():\n        handler.endPrefixMapping(prefix)\n    handler.endDocument()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treebuilders/__init__.py",
    "content": "\"\"\"A collection of modules for building different kinds of trees from HTML\ndocuments.\n\nTo create a treebuilder for a new type of tree, you need to do\nimplement several things:\n\n1. A set of classes for various types of elements: Document, Doctype, Comment,\n   Element. These must implement the interface of ``base.treebuilders.Node``\n   (although comment nodes have a different signature for their constructor,\n   see ``treebuilders.etree.Comment``) Textual content may also be implemented\n   as another node type, or not, as your tree implementation requires.\n\n2. A treebuilder object (called ``TreeBuilder`` by convention) that inherits\n   from ``treebuilders.base.TreeBuilder``. This has 4 required attributes:\n\n   * ``documentClass`` - the class to use for the bottommost node of a document\n   * ``elementClass`` - the class to use for HTML Elements\n   * ``commentClass`` - the class to use for comments\n   * ``doctypeClass`` - the class to use for doctypes\n\n   It also has one required method:\n\n   * ``getDocument`` - Returns the root node of the complete document tree\n\n3. If you wish to run the unit tests, you must also create a ``testSerializer``\n   method on your treebuilder which accepts a node and returns a string\n   containing Node and its children serialized according to the format used in\n   the unittests\n\n\"\"\"\n\nfrom __future__ import absolute_import, division, unicode_literals\n\nfrom .._utils import default_etree\n\ntreeBuilderCache = {}\n\n\ndef getTreeBuilder(treeType, implementation=None, **kwargs):\n    \"\"\"Get a TreeBuilder class for various types of trees with built-in support\n\n    :arg treeType: the name of the tree type required (case-insensitive). Supported\n        values are:\n\n        * \"dom\" - A generic builder for DOM implementations, defaulting to a\n          xml.dom.minidom based implementation.\n        * \"etree\" - A generic builder for tree implementations exposing an\n          ElementTree-like interface, defaulting to xml.etree.cElementTree if\n          available and xml.etree.ElementTree if not.\n        * \"lxml\" - A etree-based builder for lxml.etree, handling limitations\n          of lxml's implementation.\n\n    :arg implementation: (Currently applies to the \"etree\" and \"dom\" tree\n        types). A module implementing the tree type e.g. xml.etree.ElementTree\n        or xml.etree.cElementTree.\n\n    :arg kwargs: Any additional options to pass to the TreeBuilder when\n        creating it.\n\n    Example:\n\n    >>> from html5lib.treebuilders import getTreeBuilder\n    >>> builder = getTreeBuilder('etree')\n\n    \"\"\"\n\n    treeType = treeType.lower()\n    if treeType not in treeBuilderCache:\n        if treeType == \"dom\":\n            from . import dom\n            # Come up with a sane default (pref. from the stdlib)\n            if implementation is None:\n                from xml.dom import minidom\n                implementation = minidom\n            # NEVER cache here, caching is done in the dom submodule\n            return dom.getDomModule(implementation, **kwargs).TreeBuilder\n        elif treeType == \"lxml\":\n            from . import etree_lxml\n            treeBuilderCache[treeType] = etree_lxml.TreeBuilder\n        elif treeType == \"etree\":\n            from . import etree\n            if implementation is None:\n                implementation = default_etree\n            # NEVER cache here, caching is done in the etree submodule\n            return etree.getETreeModule(implementation, **kwargs).TreeBuilder\n        else:\n            raise ValueError(\"\"\"Unrecognised treebuilder \"%s\" \"\"\" % treeType)\n    return treeBuilderCache.get(treeType)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treebuilders/base.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\nfrom pip._vendor.six import text_type\n\nfrom ..constants import scopingElements, tableInsertModeElements, namespaces\n\n# The scope markers are inserted when entering object elements,\n# marquees, table cells, and table captions, and are used to prevent formatting\n# from \"leaking\" into tables, object elements, and marquees.\nMarker = None\n\nlistElementsMap = {\n    None: (frozenset(scopingElements), False),\n    \"button\": (frozenset(scopingElements | set([(namespaces[\"html\"], \"button\")])), False),\n    \"list\": (frozenset(scopingElements | set([(namespaces[\"html\"], \"ol\"),\n                                              (namespaces[\"html\"], \"ul\")])), False),\n    \"table\": (frozenset([(namespaces[\"html\"], \"html\"),\n                         (namespaces[\"html\"], \"table\")]), False),\n    \"select\": (frozenset([(namespaces[\"html\"], \"optgroup\"),\n                          (namespaces[\"html\"], \"option\")]), True)\n}\n\n\nclass Node(object):\n    \"\"\"Represents an item in the tree\"\"\"\n    def __init__(self, name):\n        \"\"\"Creates a Node\n\n        :arg name: The tag name associated with the node\n\n        \"\"\"\n        # The tag name assocaited with the node\n        self.name = name\n        # The parent of the current node (or None for the document node)\n        self.parent = None\n        # The value of the current node (applies to text nodes and comments)\n        self.value = None\n        # A dict holding name -> value pairs for attributes of the node\n        self.attributes = {}\n        # A list of child nodes of the current node. This must include all\n        # elements but not necessarily other node types.\n        self.childNodes = []\n        # A list of miscellaneous flags that can be set on the node.\n        self._flags = []\n\n    def __str__(self):\n        attributesStr = \" \".join([\"%s=\\\"%s\\\"\" % (name, value)\n                                  for name, value in\n                                  self.attributes.items()])\n        if attributesStr:\n            return \"<%s %s>\" % (self.name, attributesStr)\n        else:\n            return \"<%s>\" % (self.name)\n\n    def __repr__(self):\n        return \"<%s>\" % (self.name)\n\n    def appendChild(self, node):\n        \"\"\"Insert node as a child of the current node\n\n        :arg node: the node to insert\n\n        \"\"\"\n        raise NotImplementedError\n\n    def insertText(self, data, insertBefore=None):\n        \"\"\"Insert data as text in the current node, positioned before the\n        start of node insertBefore or to the end of the node's text.\n\n        :arg data: the data to insert\n\n        :arg insertBefore: True if you want to insert the text before the node\n            and False if you want to insert it after the node\n\n        \"\"\"\n        raise NotImplementedError\n\n    def insertBefore(self, node, refNode):\n        \"\"\"Insert node as a child of the current node, before refNode in the\n        list of child nodes. Raises ValueError if refNode is not a child of\n        the current node\n\n        :arg node: the node to insert\n\n        :arg refNode: the child node to insert the node before\n\n        \"\"\"\n        raise NotImplementedError\n\n    def removeChild(self, node):\n        \"\"\"Remove node from the children of the current node\n\n        :arg node: the child node to remove\n\n        \"\"\"\n        raise NotImplementedError\n\n    def reparentChildren(self, newParent):\n        \"\"\"Move all the children of the current node to newParent.\n        This is needed so that trees that don't store text as nodes move the\n        text in the correct way\n\n        :arg newParent: the node to move all this node's children to\n\n        \"\"\"\n        # XXX - should this method be made more general?\n        for child in self.childNodes:\n            newParent.appendChild(child)\n        self.childNodes = []\n\n    def cloneNode(self):\n        \"\"\"Return a shallow copy of the current node i.e. a node with the same\n        name and attributes but with no parent or child nodes\n        \"\"\"\n        raise NotImplementedError\n\n    def hasContent(self):\n        \"\"\"Return true if the node has children or text, false otherwise\n        \"\"\"\n        raise NotImplementedError\n\n\nclass ActiveFormattingElements(list):\n    def append(self, node):\n        equalCount = 0\n        if node != Marker:\n            for element in self[::-1]:\n                if element == Marker:\n                    break\n                if self.nodesEqual(element, node):\n                    equalCount += 1\n                if equalCount == 3:\n                    self.remove(element)\n                    break\n        list.append(self, node)\n\n    def nodesEqual(self, node1, node2):\n        if not node1.nameTuple == node2.nameTuple:\n            return False\n\n        if not node1.attributes == node2.attributes:\n            return False\n\n        return True\n\n\nclass TreeBuilder(object):\n    \"\"\"Base treebuilder implementation\n\n    * documentClass - the class to use for the bottommost node of a document\n    * elementClass - the class to use for HTML Elements\n    * commentClass - the class to use for comments\n    * doctypeClass - the class to use for doctypes\n\n    \"\"\"\n    # pylint:disable=not-callable\n\n    # Document class\n    documentClass = None\n\n    # The class to use for creating a node\n    elementClass = None\n\n    # The class to use for creating comments\n    commentClass = None\n\n    # The class to use for creating doctypes\n    doctypeClass = None\n\n    # Fragment class\n    fragmentClass = None\n\n    def __init__(self, namespaceHTMLElements):\n        \"\"\"Create a TreeBuilder\n\n        :arg namespaceHTMLElements: whether or not to namespace HTML elements\n\n        \"\"\"\n        if namespaceHTMLElements:\n            self.defaultNamespace = \"http://www.w3.org/1999/xhtml\"\n        else:\n            self.defaultNamespace = None\n        self.reset()\n\n    def reset(self):\n        self.openElements = []\n        self.activeFormattingElements = ActiveFormattingElements()\n\n        # XXX - rename these to headElement, formElement\n        self.headPointer = None\n        self.formPointer = None\n\n        self.insertFromTable = False\n\n        self.document = self.documentClass()\n\n    def elementInScope(self, target, variant=None):\n\n        # If we pass a node in we match that. if we pass a string\n        # match any node with that name\n        exactNode = hasattr(target, \"nameTuple\")\n        if not exactNode:\n            if isinstance(target, text_type):\n                target = (namespaces[\"html\"], target)\n            assert isinstance(target, tuple)\n\n        listElements, invert = listElementsMap[variant]\n\n        for node in reversed(self.openElements):\n            if exactNode and node == target:\n                return True\n            elif not exactNode and node.nameTuple == target:\n                return True\n            elif (invert ^ (node.nameTuple in listElements)):\n                return False\n\n        assert False  # We should never reach this point\n\n    def reconstructActiveFormattingElements(self):\n        # Within this algorithm the order of steps described in the\n        # specification is not quite the same as the order of steps in the\n        # code. It should still do the same though.\n\n        # Step 1: stop the algorithm when there's nothing to do.\n        if not self.activeFormattingElements:\n            return\n\n        # Step 2 and step 3: we start with the last element. So i is -1.\n        i = len(self.activeFormattingElements) - 1\n        entry = self.activeFormattingElements[i]\n        if entry == Marker or entry in self.openElements:\n            return\n\n        # Step 6\n        while entry != Marker and entry not in self.openElements:\n            if i == 0:\n                # This will be reset to 0 below\n                i = -1\n                break\n            i -= 1\n            # Step 5: let entry be one earlier in the list.\n            entry = self.activeFormattingElements[i]\n\n        while True:\n            # Step 7\n            i += 1\n\n            # Step 8\n            entry = self.activeFormattingElements[i]\n            clone = entry.cloneNode()  # Mainly to get a new copy of the attributes\n\n            # Step 9\n            element = self.insertElement({\"type\": \"StartTag\",\n                                          \"name\": clone.name,\n                                          \"namespace\": clone.namespace,\n                                          \"data\": clone.attributes})\n\n            # Step 10\n            self.activeFormattingElements[i] = element\n\n            # Step 11\n            if element == self.activeFormattingElements[-1]:\n                break\n\n    def clearActiveFormattingElements(self):\n        entry = self.activeFormattingElements.pop()\n        while self.activeFormattingElements and entry != Marker:\n            entry = self.activeFormattingElements.pop()\n\n    def elementInActiveFormattingElements(self, name):\n        \"\"\"Check if an element exists between the end of the active\n        formatting elements and the last marker. If it does, return it, else\n        return false\"\"\"\n\n        for item in self.activeFormattingElements[::-1]:\n            # Check for Marker first because if it's a Marker it doesn't have a\n            # name attribute.\n            if item == Marker:\n                break\n            elif item.name == name:\n                return item\n        return False\n\n    def insertRoot(self, token):\n        element = self.createElement(token)\n        self.openElements.append(element)\n        self.document.appendChild(element)\n\n    def insertDoctype(self, token):\n        name = token[\"name\"]\n        publicId = token[\"publicId\"]\n        systemId = token[\"systemId\"]\n\n        doctype = self.doctypeClass(name, publicId, systemId)\n        self.document.appendChild(doctype)\n\n    def insertComment(self, token, parent=None):\n        if parent is None:\n            parent = self.openElements[-1]\n        parent.appendChild(self.commentClass(token[\"data\"]))\n\n    def createElement(self, token):\n        \"\"\"Create an element but don't insert it anywhere\"\"\"\n        name = token[\"name\"]\n        namespace = token.get(\"namespace\", self.defaultNamespace)\n        element = self.elementClass(name, namespace)\n        element.attributes = token[\"data\"]\n        return element\n\n    def _getInsertFromTable(self):\n        return self._insertFromTable\n\n    def _setInsertFromTable(self, value):\n        \"\"\"Switch the function used to insert an element from the\n        normal one to the misnested table one and back again\"\"\"\n        self._insertFromTable = value\n        if value:\n            self.insertElement = self.insertElementTable\n        else:\n            self.insertElement = self.insertElementNormal\n\n    insertFromTable = property(_getInsertFromTable, _setInsertFromTable)\n\n    def insertElementNormal(self, token):\n        name = token[\"name\"]\n        assert isinstance(name, text_type), \"Element %s not unicode\" % name\n        namespace = token.get(\"namespace\", self.defaultNamespace)\n        element = self.elementClass(name, namespace)\n        element.attributes = token[\"data\"]\n        self.openElements[-1].appendChild(element)\n        self.openElements.append(element)\n        return element\n\n    def insertElementTable(self, token):\n        \"\"\"Create an element and insert it into the tree\"\"\"\n        element = self.createElement(token)\n        if self.openElements[-1].name not in tableInsertModeElements:\n            return self.insertElementNormal(token)\n        else:\n            # We should be in the InTable mode. This means we want to do\n            # special magic element rearranging\n            parent, insertBefore = self.getTableMisnestedNodePosition()\n            if insertBefore is None:\n                parent.appendChild(element)\n            else:\n                parent.insertBefore(element, insertBefore)\n            self.openElements.append(element)\n        return element\n\n    def insertText(self, data, parent=None):\n        \"\"\"Insert text data.\"\"\"\n        if parent is None:\n            parent = self.openElements[-1]\n\n        if (not self.insertFromTable or (self.insertFromTable and\n                                         self.openElements[-1].name\n                                         not in tableInsertModeElements)):\n            parent.insertText(data)\n        else:\n            # We should be in the InTable mode. This means we want to do\n            # special magic element rearranging\n            parent, insertBefore = self.getTableMisnestedNodePosition()\n            parent.insertText(data, insertBefore)\n\n    def getTableMisnestedNodePosition(self):\n        \"\"\"Get the foster parent element, and sibling to insert before\n        (or None) when inserting a misnested table node\"\"\"\n        # The foster parent element is the one which comes before the most\n        # recently opened table element\n        # XXX - this is really inelegant\n        lastTable = None\n        fosterParent = None\n        insertBefore = None\n        for elm in self.openElements[::-1]:\n            if elm.name == \"table\":\n                lastTable = elm\n                break\n        if lastTable:\n            # XXX - we should really check that this parent is actually a\n            # node here\n            if lastTable.parent:\n                fosterParent = lastTable.parent\n                insertBefore = lastTable\n            else:\n                fosterParent = self.openElements[\n                    self.openElements.index(lastTable) - 1]\n        else:\n            fosterParent = self.openElements[0]\n        return fosterParent, insertBefore\n\n    def generateImpliedEndTags(self, exclude=None):\n        name = self.openElements[-1].name\n        # XXX td, th and tr are not actually needed\n        if (name in frozenset((\"dd\", \"dt\", \"li\", \"option\", \"optgroup\", \"p\", \"rp\", \"rt\")) and\n                name != exclude):\n            self.openElements.pop()\n            # XXX This is not entirely what the specification says. We should\n            # investigate it more closely.\n            self.generateImpliedEndTags(exclude)\n\n    def getDocument(self):\n        \"\"\"Return the final tree\"\"\"\n        return self.document\n\n    def getFragment(self):\n        \"\"\"Return the final fragment\"\"\"\n        # assert self.innerHTML\n        fragment = self.fragmentClass()\n        self.openElements[0].reparentChildren(fragment)\n        return fragment\n\n    def testSerializer(self, node):\n        \"\"\"Serialize the subtree of node in the format required by unit tests\n\n        :arg node: the node from which to start serializing\n\n        \"\"\"\n        raise NotImplementedError\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treebuilders/dom.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\n\nfrom collections import MutableMapping\nfrom xml.dom import minidom, Node\nimport weakref\n\nfrom . import base\nfrom .. import constants\nfrom ..constants import namespaces\nfrom .._utils import moduleFactoryFactory\n\n\ndef getDomBuilder(DomImplementation):\n    Dom = DomImplementation\n\n    class AttrList(MutableMapping):\n        def __init__(self, element):\n            self.element = element\n\n        def __iter__(self):\n            return iter(self.element.attributes.keys())\n\n        def __setitem__(self, name, value):\n            if isinstance(name, tuple):\n                raise NotImplementedError\n            else:\n                attr = self.element.ownerDocument.createAttribute(name)\n                attr.value = value\n                self.element.attributes[name] = attr\n\n        def __len__(self):\n            return len(self.element.attributes)\n\n        def items(self):\n            return list(self.element.attributes.items())\n\n        def values(self):\n            return list(self.element.attributes.values())\n\n        def __getitem__(self, name):\n            if isinstance(name, tuple):\n                raise NotImplementedError\n            else:\n                return self.element.attributes[name].value\n\n        def __delitem__(self, name):\n            if isinstance(name, tuple):\n                raise NotImplementedError\n            else:\n                del self.element.attributes[name]\n\n    class NodeBuilder(base.Node):\n        def __init__(self, element):\n            base.Node.__init__(self, element.nodeName)\n            self.element = element\n\n        namespace = property(lambda self: hasattr(self.element, \"namespaceURI\") and\n                             self.element.namespaceURI or None)\n\n        def appendChild(self, node):\n            node.parent = self\n            self.element.appendChild(node.element)\n\n        def insertText(self, data, insertBefore=None):\n            text = self.element.ownerDocument.createTextNode(data)\n            if insertBefore:\n                self.element.insertBefore(text, insertBefore.element)\n            else:\n                self.element.appendChild(text)\n\n        def insertBefore(self, node, refNode):\n            self.element.insertBefore(node.element, refNode.element)\n            node.parent = self\n\n        def removeChild(self, node):\n            if node.element.parentNode == self.element:\n                self.element.removeChild(node.element)\n            node.parent = None\n\n        def reparentChildren(self, newParent):\n            while self.element.hasChildNodes():\n                child = self.element.firstChild\n                self.element.removeChild(child)\n                newParent.element.appendChild(child)\n            self.childNodes = []\n\n        def getAttributes(self):\n            return AttrList(self.element)\n\n        def setAttributes(self, attributes):\n            if attributes:\n                for name, value in list(attributes.items()):\n                    if isinstance(name, tuple):\n                        if name[0] is not None:\n                            qualifiedName = (name[0] + \":\" + name[1])\n                        else:\n                            qualifiedName = name[1]\n                        self.element.setAttributeNS(name[2], qualifiedName,\n                                                    value)\n                    else:\n                        self.element.setAttribute(\n                            name, value)\n        attributes = property(getAttributes, setAttributes)\n\n        def cloneNode(self):\n            return NodeBuilder(self.element.cloneNode(False))\n\n        def hasContent(self):\n            return self.element.hasChildNodes()\n\n        def getNameTuple(self):\n            if self.namespace is None:\n                return namespaces[\"html\"], self.name\n            else:\n                return self.namespace, self.name\n\n        nameTuple = property(getNameTuple)\n\n    class TreeBuilder(base.TreeBuilder):  # pylint:disable=unused-variable\n        def documentClass(self):\n            self.dom = Dom.getDOMImplementation().createDocument(None, None, None)\n            return weakref.proxy(self)\n\n        def insertDoctype(self, token):\n            name = token[\"name\"]\n            publicId = token[\"publicId\"]\n            systemId = token[\"systemId\"]\n\n            domimpl = Dom.getDOMImplementation()\n            doctype = domimpl.createDocumentType(name, publicId, systemId)\n            self.document.appendChild(NodeBuilder(doctype))\n            if Dom == minidom:\n                doctype.ownerDocument = self.dom\n\n        def elementClass(self, name, namespace=None):\n            if namespace is None and self.defaultNamespace is None:\n                node = self.dom.createElement(name)\n            else:\n                node = self.dom.createElementNS(namespace, name)\n\n            return NodeBuilder(node)\n\n        def commentClass(self, data):\n            return NodeBuilder(self.dom.createComment(data))\n\n        def fragmentClass(self):\n            return NodeBuilder(self.dom.createDocumentFragment())\n\n        def appendChild(self, node):\n            self.dom.appendChild(node.element)\n\n        def testSerializer(self, element):\n            return testSerializer(element)\n\n        def getDocument(self):\n            return self.dom\n\n        def getFragment(self):\n            return base.TreeBuilder.getFragment(self).element\n\n        def insertText(self, data, parent=None):\n            data = data\n            if parent != self:\n                base.TreeBuilder.insertText(self, data, parent)\n            else:\n                # HACK: allow text nodes as children of the document node\n                if hasattr(self.dom, '_child_node_types'):\n                    # pylint:disable=protected-access\n                    if Node.TEXT_NODE not in self.dom._child_node_types:\n                        self.dom._child_node_types = list(self.dom._child_node_types)\n                        self.dom._child_node_types.append(Node.TEXT_NODE)\n                self.dom.appendChild(self.dom.createTextNode(data))\n\n        implementation = DomImplementation\n        name = None\n\n    def testSerializer(element):\n        element.normalize()\n        rv = []\n\n        def serializeElement(element, indent=0):\n            if element.nodeType == Node.DOCUMENT_TYPE_NODE:\n                if element.name:\n                    if element.publicId or element.systemId:\n                        publicId = element.publicId or \"\"\n                        systemId = element.systemId or \"\"\n                        rv.append(\"\"\"|%s<!DOCTYPE %s \"%s\" \"%s\">\"\"\" %\n                                  (' ' * indent, element.name, publicId, systemId))\n                    else:\n                        rv.append(\"|%s<!DOCTYPE %s>\" % (' ' * indent, element.name))\n                else:\n                    rv.append(\"|%s<!DOCTYPE >\" % (' ' * indent,))\n            elif element.nodeType == Node.DOCUMENT_NODE:\n                rv.append(\"#document\")\n            elif element.nodeType == Node.DOCUMENT_FRAGMENT_NODE:\n                rv.append(\"#document-fragment\")\n            elif element.nodeType == Node.COMMENT_NODE:\n                rv.append(\"|%s<!-- %s -->\" % (' ' * indent, element.nodeValue))\n            elif element.nodeType == Node.TEXT_NODE:\n                rv.append(\"|%s\\\"%s\\\"\" % (' ' * indent, element.nodeValue))\n            else:\n                if (hasattr(element, \"namespaceURI\") and\n                        element.namespaceURI is not None):\n                    name = \"%s %s\" % (constants.prefixes[element.namespaceURI],\n                                      element.nodeName)\n                else:\n                    name = element.nodeName\n                rv.append(\"|%s<%s>\" % (' ' * indent, name))\n                if element.hasAttributes():\n                    attributes = []\n                    for i in range(len(element.attributes)):\n                        attr = element.attributes.item(i)\n                        name = attr.nodeName\n                        value = attr.value\n                        ns = attr.namespaceURI\n                        if ns:\n                            name = \"%s %s\" % (constants.prefixes[ns], attr.localName)\n                        else:\n                            name = attr.nodeName\n                        attributes.append((name, value))\n\n                    for name, value in sorted(attributes):\n                        rv.append('|%s%s=\"%s\"' % (' ' * (indent + 2), name, value))\n            indent += 2\n            for child in element.childNodes:\n                serializeElement(child, indent)\n        serializeElement(element, 0)\n\n        return \"\\n\".join(rv)\n\n    return locals()\n\n\n# The actual means to get a module!\ngetDomModule = moduleFactoryFactory(getDomBuilder)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treebuilders/etree.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n# pylint:disable=protected-access\n\nfrom pip._vendor.six import text_type\n\nimport re\n\nfrom . import base\nfrom .. import _ihatexml\nfrom .. import constants\nfrom ..constants import namespaces\nfrom .._utils import moduleFactoryFactory\n\ntag_regexp = re.compile(\"{([^}]*)}(.*)\")\n\n\ndef getETreeBuilder(ElementTreeImplementation, fullTree=False):\n    ElementTree = ElementTreeImplementation\n    ElementTreeCommentType = ElementTree.Comment(\"asd\").tag\n\n    class Element(base.Node):\n        def __init__(self, name, namespace=None):\n            self._name = name\n            self._namespace = namespace\n            self._element = ElementTree.Element(self._getETreeTag(name,\n                                                                  namespace))\n            if namespace is None:\n                self.nameTuple = namespaces[\"html\"], self._name\n            else:\n                self.nameTuple = self._namespace, self._name\n            self.parent = None\n            self._childNodes = []\n            self._flags = []\n\n        def _getETreeTag(self, name, namespace):\n            if namespace is None:\n                etree_tag = name\n            else:\n                etree_tag = \"{%s}%s\" % (namespace, name)\n            return etree_tag\n\n        def _setName(self, name):\n            self._name = name\n            self._element.tag = self._getETreeTag(self._name, self._namespace)\n\n        def _getName(self):\n            return self._name\n\n        name = property(_getName, _setName)\n\n        def _setNamespace(self, namespace):\n            self._namespace = namespace\n            self._element.tag = self._getETreeTag(self._name, self._namespace)\n\n        def _getNamespace(self):\n            return self._namespace\n\n        namespace = property(_getNamespace, _setNamespace)\n\n        def _getAttributes(self):\n            return self._element.attrib\n\n        def _setAttributes(self, attributes):\n            # Delete existing attributes first\n            # XXX - there may be a better way to do this...\n            for key in list(self._element.attrib.keys()):\n                del self._element.attrib[key]\n            for key, value in attributes.items():\n                if isinstance(key, tuple):\n                    name = \"{%s}%s\" % (key[2], key[1])\n                else:\n                    name = key\n                self._element.set(name, value)\n\n        attributes = property(_getAttributes, _setAttributes)\n\n        def _getChildNodes(self):\n            return self._childNodes\n\n        def _setChildNodes(self, value):\n            del self._element[:]\n            self._childNodes = []\n            for element in value:\n                self.insertChild(element)\n\n        childNodes = property(_getChildNodes, _setChildNodes)\n\n        def hasContent(self):\n            \"\"\"Return true if the node has children or text\"\"\"\n            return bool(self._element.text or len(self._element))\n\n        def appendChild(self, node):\n            self._childNodes.append(node)\n            self._element.append(node._element)\n            node.parent = self\n\n        def insertBefore(self, node, refNode):\n            index = list(self._element).index(refNode._element)\n            self._element.insert(index, node._element)\n            node.parent = self\n\n        def removeChild(self, node):\n            self._childNodes.remove(node)\n            self._element.remove(node._element)\n            node.parent = None\n\n        def insertText(self, data, insertBefore=None):\n            if not(len(self._element)):\n                if not self._element.text:\n                    self._element.text = \"\"\n                self._element.text += data\n            elif insertBefore is None:\n                # Insert the text as the tail of the last child element\n                if not self._element[-1].tail:\n                    self._element[-1].tail = \"\"\n                self._element[-1].tail += data\n            else:\n                # Insert the text before the specified node\n                children = list(self._element)\n                index = children.index(insertBefore._element)\n                if index > 0:\n                    if not self._element[index - 1].tail:\n                        self._element[index - 1].tail = \"\"\n                    self._element[index - 1].tail += data\n                else:\n                    if not self._element.text:\n                        self._element.text = \"\"\n                    self._element.text += data\n\n        def cloneNode(self):\n            element = type(self)(self.name, self.namespace)\n            for name, value in self.attributes.items():\n                element.attributes[name] = value\n            return element\n\n        def reparentChildren(self, newParent):\n            if newParent.childNodes:\n                newParent.childNodes[-1]._element.tail += self._element.text\n            else:\n                if not newParent._element.text:\n                    newParent._element.text = \"\"\n                if self._element.text is not None:\n                    newParent._element.text += self._element.text\n            self._element.text = \"\"\n            base.Node.reparentChildren(self, newParent)\n\n    class Comment(Element):\n        def __init__(self, data):\n            # Use the superclass constructor to set all properties on the\n            # wrapper element\n            self._element = ElementTree.Comment(data)\n            self.parent = None\n            self._childNodes = []\n            self._flags = []\n\n        def _getData(self):\n            return self._element.text\n\n        def _setData(self, value):\n            self._element.text = value\n\n        data = property(_getData, _setData)\n\n    class DocumentType(Element):\n        def __init__(self, name, publicId, systemId):\n            Element.__init__(self, \"<!DOCTYPE>\")\n            self._element.text = name\n            self.publicId = publicId\n            self.systemId = systemId\n\n        def _getPublicId(self):\n            return self._element.get(\"publicId\", \"\")\n\n        def _setPublicId(self, value):\n            if value is not None:\n                self._element.set(\"publicId\", value)\n\n        publicId = property(_getPublicId, _setPublicId)\n\n        def _getSystemId(self):\n            return self._element.get(\"systemId\", \"\")\n\n        def _setSystemId(self, value):\n            if value is not None:\n                self._element.set(\"systemId\", value)\n\n        systemId = property(_getSystemId, _setSystemId)\n\n    class Document(Element):\n        def __init__(self):\n            Element.__init__(self, \"DOCUMENT_ROOT\")\n\n    class DocumentFragment(Element):\n        def __init__(self):\n            Element.__init__(self, \"DOCUMENT_FRAGMENT\")\n\n    def testSerializer(element):\n        rv = []\n\n        def serializeElement(element, indent=0):\n            if not(hasattr(element, \"tag\")):\n                element = element.getroot()\n            if element.tag == \"<!DOCTYPE>\":\n                if element.get(\"publicId\") or element.get(\"systemId\"):\n                    publicId = element.get(\"publicId\") or \"\"\n                    systemId = element.get(\"systemId\") or \"\"\n                    rv.append(\"\"\"<!DOCTYPE %s \"%s\" \"%s\">\"\"\" %\n                              (element.text, publicId, systemId))\n                else:\n                    rv.append(\"<!DOCTYPE %s>\" % (element.text,))\n            elif element.tag == \"DOCUMENT_ROOT\":\n                rv.append(\"#document\")\n                if element.text is not None:\n                    rv.append(\"|%s\\\"%s\\\"\" % (' ' * (indent + 2), element.text))\n                if element.tail is not None:\n                    raise TypeError(\"Document node cannot have tail\")\n                if hasattr(element, \"attrib\") and len(element.attrib):\n                    raise TypeError(\"Document node cannot have attributes\")\n            elif element.tag == ElementTreeCommentType:\n                rv.append(\"|%s<!-- %s -->\" % (' ' * indent, element.text))\n            else:\n                assert isinstance(element.tag, text_type), \\\n                    \"Expected unicode, got %s, %s\" % (type(element.tag), element.tag)\n                nsmatch = tag_regexp.match(element.tag)\n\n                if nsmatch is None:\n                    name = element.tag\n                else:\n                    ns, name = nsmatch.groups()\n                    prefix = constants.prefixes[ns]\n                    name = \"%s %s\" % (prefix, name)\n                rv.append(\"|%s<%s>\" % (' ' * indent, name))\n\n                if hasattr(element, \"attrib\"):\n                    attributes = []\n                    for name, value in element.attrib.items():\n                        nsmatch = tag_regexp.match(name)\n                        if nsmatch is not None:\n                            ns, name = nsmatch.groups()\n                            prefix = constants.prefixes[ns]\n                            attr_string = \"%s %s\" % (prefix, name)\n                        else:\n                            attr_string = name\n                        attributes.append((attr_string, value))\n\n                    for name, value in sorted(attributes):\n                        rv.append('|%s%s=\"%s\"' % (' ' * (indent + 2), name, value))\n                if element.text:\n                    rv.append(\"|%s\\\"%s\\\"\" % (' ' * (indent + 2), element.text))\n            indent += 2\n            for child in element:\n                serializeElement(child, indent)\n            if element.tail:\n                rv.append(\"|%s\\\"%s\\\"\" % (' ' * (indent - 2), element.tail))\n        serializeElement(element, 0)\n\n        return \"\\n\".join(rv)\n\n    def tostring(element):  # pylint:disable=unused-variable\n        \"\"\"Serialize an element and its child nodes to a string\"\"\"\n        rv = []\n        filter = _ihatexml.InfosetFilter()\n\n        def serializeElement(element):\n            if isinstance(element, ElementTree.ElementTree):\n                element = element.getroot()\n\n            if element.tag == \"<!DOCTYPE>\":\n                if element.get(\"publicId\") or element.get(\"systemId\"):\n                    publicId = element.get(\"publicId\") or \"\"\n                    systemId = element.get(\"systemId\") or \"\"\n                    rv.append(\"\"\"<!DOCTYPE %s PUBLIC \"%s\" \"%s\">\"\"\" %\n                              (element.text, publicId, systemId))\n                else:\n                    rv.append(\"<!DOCTYPE %s>\" % (element.text,))\n            elif element.tag == \"DOCUMENT_ROOT\":\n                if element.text is not None:\n                    rv.append(element.text)\n                if element.tail is not None:\n                    raise TypeError(\"Document node cannot have tail\")\n                if hasattr(element, \"attrib\") and len(element.attrib):\n                    raise TypeError(\"Document node cannot have attributes\")\n\n                for child in element:\n                    serializeElement(child)\n\n            elif element.tag == ElementTreeCommentType:\n                rv.append(\"<!--%s-->\" % (element.text,))\n            else:\n                # This is assumed to be an ordinary element\n                if not element.attrib:\n                    rv.append(\"<%s>\" % (filter.fromXmlName(element.tag),))\n                else:\n                    attr = \" \".join([\"%s=\\\"%s\\\"\" % (\n                        filter.fromXmlName(name), value)\n                        for name, value in element.attrib.items()])\n                    rv.append(\"<%s %s>\" % (element.tag, attr))\n                if element.text:\n                    rv.append(element.text)\n\n                for child in element:\n                    serializeElement(child)\n\n                rv.append(\"</%s>\" % (element.tag,))\n\n            if element.tail:\n                rv.append(element.tail)\n\n        serializeElement(element)\n\n        return \"\".join(rv)\n\n    class TreeBuilder(base.TreeBuilder):  # pylint:disable=unused-variable\n        documentClass = Document\n        doctypeClass = DocumentType\n        elementClass = Element\n        commentClass = Comment\n        fragmentClass = DocumentFragment\n        implementation = ElementTreeImplementation\n\n        def testSerializer(self, element):\n            return testSerializer(element)\n\n        def getDocument(self):\n            if fullTree:\n                return self.document._element\n            else:\n                if self.defaultNamespace is not None:\n                    return self.document._element.find(\n                        \"{%s}html\" % self.defaultNamespace)\n                else:\n                    return self.document._element.find(\"html\")\n\n        def getFragment(self):\n            return base.TreeBuilder.getFragment(self)._element\n\n    return locals()\n\n\ngetETreeModule = moduleFactoryFactory(getETreeBuilder)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treebuilders/etree_lxml.py",
    "content": "\"\"\"Module for supporting the lxml.etree library. The idea here is to use as much\nof the native library as possible, without using fragile hacks like custom element\nnames that break between releases. The downside of this is that we cannot represent\nall possible trees; specifically the following are known to cause problems:\n\nText or comments as siblings of the root element\nDocypes with no name\n\nWhen any of these things occur, we emit a DataLossWarning\n\"\"\"\n\nfrom __future__ import absolute_import, division, unicode_literals\n# pylint:disable=protected-access\n\nimport warnings\nimport re\nimport sys\n\nfrom . import base\nfrom ..constants import DataLossWarning\nfrom .. import constants\nfrom . import etree as etree_builders\nfrom .. import _ihatexml\n\nimport lxml.etree as etree\n\n\nfullTree = True\ntag_regexp = re.compile(\"{([^}]*)}(.*)\")\n\ncomment_type = etree.Comment(\"asd\").tag\n\n\nclass DocumentType(object):\n    def __init__(self, name, publicId, systemId):\n        self.name = name\n        self.publicId = publicId\n        self.systemId = systemId\n\n\nclass Document(object):\n    def __init__(self):\n        self._elementTree = None\n        self._childNodes = []\n\n    def appendChild(self, element):\n        self._elementTree.getroot().addnext(element._element)\n\n    def _getChildNodes(self):\n        return self._childNodes\n\n    childNodes = property(_getChildNodes)\n\n\ndef testSerializer(element):\n    rv = []\n    infosetFilter = _ihatexml.InfosetFilter(preventDoubleDashComments=True)\n\n    def serializeElement(element, indent=0):\n        if not hasattr(element, \"tag\"):\n            if hasattr(element, \"getroot\"):\n                # Full tree case\n                rv.append(\"#document\")\n                if element.docinfo.internalDTD:\n                    if not (element.docinfo.public_id or\n                            element.docinfo.system_url):\n                        dtd_str = \"<!DOCTYPE %s>\" % element.docinfo.root_name\n                    else:\n                        dtd_str = \"\"\"<!DOCTYPE %s \"%s\" \"%s\">\"\"\" % (\n                            element.docinfo.root_name,\n                            element.docinfo.public_id,\n                            element.docinfo.system_url)\n                    rv.append(\"|%s%s\" % (' ' * (indent + 2), dtd_str))\n                next_element = element.getroot()\n                while next_element.getprevious() is not None:\n                    next_element = next_element.getprevious()\n                while next_element is not None:\n                    serializeElement(next_element, indent + 2)\n                    next_element = next_element.getnext()\n            elif isinstance(element, str) or isinstance(element, bytes):\n                # Text in a fragment\n                assert isinstance(element, str) or sys.version_info[0] == 2\n                rv.append(\"|%s\\\"%s\\\"\" % (' ' * indent, element))\n            else:\n                # Fragment case\n                rv.append(\"#document-fragment\")\n                for next_element in element:\n                    serializeElement(next_element, indent + 2)\n        elif element.tag == comment_type:\n            rv.append(\"|%s<!-- %s -->\" % (' ' * indent, element.text))\n            if hasattr(element, \"tail\") and element.tail:\n                rv.append(\"|%s\\\"%s\\\"\" % (' ' * indent, element.tail))\n        else:\n            assert isinstance(element, etree._Element)\n            nsmatch = etree_builders.tag_regexp.match(element.tag)\n            if nsmatch is not None:\n                ns = nsmatch.group(1)\n                tag = nsmatch.group(2)\n                prefix = constants.prefixes[ns]\n                rv.append(\"|%s<%s %s>\" % (' ' * indent, prefix,\n                                          infosetFilter.fromXmlName(tag)))\n            else:\n                rv.append(\"|%s<%s>\" % (' ' * indent,\n                                       infosetFilter.fromXmlName(element.tag)))\n\n            if hasattr(element, \"attrib\"):\n                attributes = []\n                for name, value in element.attrib.items():\n                    nsmatch = tag_regexp.match(name)\n                    if nsmatch is not None:\n                        ns, name = nsmatch.groups()\n                        name = infosetFilter.fromXmlName(name)\n                        prefix = constants.prefixes[ns]\n                        attr_string = \"%s %s\" % (prefix, name)\n                    else:\n                        attr_string = infosetFilter.fromXmlName(name)\n                    attributes.append((attr_string, value))\n\n                for name, value in sorted(attributes):\n                    rv.append('|%s%s=\"%s\"' % (' ' * (indent + 2), name, value))\n\n            if element.text:\n                rv.append(\"|%s\\\"%s\\\"\" % (' ' * (indent + 2), element.text))\n            indent += 2\n            for child in element:\n                serializeElement(child, indent)\n            if hasattr(element, \"tail\") and element.tail:\n                rv.append(\"|%s\\\"%s\\\"\" % (' ' * (indent - 2), element.tail))\n    serializeElement(element, 0)\n\n    return \"\\n\".join(rv)\n\n\ndef tostring(element):\n    \"\"\"Serialize an element and its child nodes to a string\"\"\"\n    rv = []\n\n    def serializeElement(element):\n        if not hasattr(element, \"tag\"):\n            if element.docinfo.internalDTD:\n                if element.docinfo.doctype:\n                    dtd_str = element.docinfo.doctype\n                else:\n                    dtd_str = \"<!DOCTYPE %s>\" % element.docinfo.root_name\n                rv.append(dtd_str)\n            serializeElement(element.getroot())\n\n        elif element.tag == comment_type:\n            rv.append(\"<!--%s-->\" % (element.text,))\n\n        else:\n            # This is assumed to be an ordinary element\n            if not element.attrib:\n                rv.append(\"<%s>\" % (element.tag,))\n            else:\n                attr = \" \".join([\"%s=\\\"%s\\\"\" % (name, value)\n                                 for name, value in element.attrib.items()])\n                rv.append(\"<%s %s>\" % (element.tag, attr))\n            if element.text:\n                rv.append(element.text)\n\n            for child in element:\n                serializeElement(child)\n\n            rv.append(\"</%s>\" % (element.tag,))\n\n        if hasattr(element, \"tail\") and element.tail:\n            rv.append(element.tail)\n\n    serializeElement(element)\n\n    return \"\".join(rv)\n\n\nclass TreeBuilder(base.TreeBuilder):\n    documentClass = Document\n    doctypeClass = DocumentType\n    elementClass = None\n    commentClass = None\n    fragmentClass = Document\n    implementation = etree\n\n    def __init__(self, namespaceHTMLElements, fullTree=False):\n        builder = etree_builders.getETreeModule(etree, fullTree=fullTree)\n        infosetFilter = self.infosetFilter = _ihatexml.InfosetFilter(preventDoubleDashComments=True)\n        self.namespaceHTMLElements = namespaceHTMLElements\n\n        class Attributes(dict):\n            def __init__(self, element, value=None):\n                if value is None:\n                    value = {}\n                self._element = element\n                dict.__init__(self, value)  # pylint:disable=non-parent-init-called\n                for key, value in self.items():\n                    if isinstance(key, tuple):\n                        name = \"{%s}%s\" % (key[2], infosetFilter.coerceAttribute(key[1]))\n                    else:\n                        name = infosetFilter.coerceAttribute(key)\n                    self._element._element.attrib[name] = value\n\n            def __setitem__(self, key, value):\n                dict.__setitem__(self, key, value)\n                if isinstance(key, tuple):\n                    name = \"{%s}%s\" % (key[2], infosetFilter.coerceAttribute(key[1]))\n                else:\n                    name = infosetFilter.coerceAttribute(key)\n                self._element._element.attrib[name] = value\n\n        class Element(builder.Element):\n            def __init__(self, name, namespace):\n                name = infosetFilter.coerceElement(name)\n                builder.Element.__init__(self, name, namespace=namespace)\n                self._attributes = Attributes(self)\n\n            def _setName(self, name):\n                self._name = infosetFilter.coerceElement(name)\n                self._element.tag = self._getETreeTag(\n                    self._name, self._namespace)\n\n            def _getName(self):\n                return infosetFilter.fromXmlName(self._name)\n\n            name = property(_getName, _setName)\n\n            def _getAttributes(self):\n                return self._attributes\n\n            def _setAttributes(self, attributes):\n                self._attributes = Attributes(self, attributes)\n\n            attributes = property(_getAttributes, _setAttributes)\n\n            def insertText(self, data, insertBefore=None):\n                data = infosetFilter.coerceCharacters(data)\n                builder.Element.insertText(self, data, insertBefore)\n\n            def appendChild(self, child):\n                builder.Element.appendChild(self, child)\n\n        class Comment(builder.Comment):\n            def __init__(self, data):\n                data = infosetFilter.coerceComment(data)\n                builder.Comment.__init__(self, data)\n\n            def _setData(self, data):\n                data = infosetFilter.coerceComment(data)\n                self._element.text = data\n\n            def _getData(self):\n                return self._element.text\n\n            data = property(_getData, _setData)\n\n        self.elementClass = Element\n        self.commentClass = Comment\n        # self.fragmentClass = builder.DocumentFragment\n        base.TreeBuilder.__init__(self, namespaceHTMLElements)\n\n    def reset(self):\n        base.TreeBuilder.reset(self)\n        self.insertComment = self.insertCommentInitial\n        self.initial_comments = []\n        self.doctype = None\n\n    def testSerializer(self, element):\n        return testSerializer(element)\n\n    def getDocument(self):\n        if fullTree:\n            return self.document._elementTree\n        else:\n            return self.document._elementTree.getroot()\n\n    def getFragment(self):\n        fragment = []\n        element = self.openElements[0]._element\n        if element.text:\n            fragment.append(element.text)\n        fragment.extend(list(element))\n        if element.tail:\n            fragment.append(element.tail)\n        return fragment\n\n    def insertDoctype(self, token):\n        name = token[\"name\"]\n        publicId = token[\"publicId\"]\n        systemId = token[\"systemId\"]\n\n        if not name:\n            warnings.warn(\"lxml cannot represent empty doctype\", DataLossWarning)\n            self.doctype = None\n        else:\n            coercedName = self.infosetFilter.coerceElement(name)\n            if coercedName != name:\n                warnings.warn(\"lxml cannot represent non-xml doctype\", DataLossWarning)\n\n            doctype = self.doctypeClass(coercedName, publicId, systemId)\n            self.doctype = doctype\n\n    def insertCommentInitial(self, data, parent=None):\n        assert parent is None or parent is self.document\n        assert self.document._elementTree is None\n        self.initial_comments.append(data)\n\n    def insertCommentMain(self, data, parent=None):\n        if (parent == self.document and\n                self.document._elementTree.getroot()[-1].tag == comment_type):\n            warnings.warn(\"lxml cannot represent adjacent comments beyond the root elements\", DataLossWarning)\n        super(TreeBuilder, self).insertComment(data, parent)\n\n    def insertRoot(self, token):\n        # Because of the way libxml2 works, it doesn't seem to be possible to\n        # alter information like the doctype after the tree has been parsed.\n        # Therefore we need to use the built-in parser to create our initial\n        # tree, after which we can add elements like normal\n        docStr = \"\"\n        if self.doctype:\n            assert self.doctype.name\n            docStr += \"<!DOCTYPE %s\" % self.doctype.name\n            if (self.doctype.publicId is not None or\n                    self.doctype.systemId is not None):\n                docStr += (' PUBLIC \"%s\" ' %\n                           (self.infosetFilter.coercePubid(self.doctype.publicId or \"\")))\n                if self.doctype.systemId:\n                    sysid = self.doctype.systemId\n                    if sysid.find(\"'\") >= 0 and sysid.find('\"') >= 0:\n                        warnings.warn(\"DOCTYPE system cannot contain single and double quotes\", DataLossWarning)\n                        sysid = sysid.replace(\"'\", 'U00027')\n                    if sysid.find(\"'\") >= 0:\n                        docStr += '\"%s\"' % sysid\n                    else:\n                        docStr += \"'%s'\" % sysid\n                else:\n                    docStr += \"''\"\n            docStr += \">\"\n            if self.doctype.name != token[\"name\"]:\n                warnings.warn(\"lxml cannot represent doctype with a different name to the root element\", DataLossWarning)\n        docStr += \"<THIS_SHOULD_NEVER_APPEAR_PUBLICLY/>\"\n        root = etree.fromstring(docStr)\n\n        # Append the initial comments:\n        for comment_token in self.initial_comments:\n            comment = self.commentClass(comment_token[\"data\"])\n            root.addprevious(comment._element)\n\n        # Create the root document and add the ElementTree to it\n        self.document = self.documentClass()\n        self.document._elementTree = root.getroottree()\n\n        # Give the root element the right name\n        name = token[\"name\"]\n        namespace = token.get(\"namespace\", self.defaultNamespace)\n        if namespace is None:\n            etree_tag = name\n        else:\n            etree_tag = \"{%s}%s\" % (namespace, name)\n        root.tag = etree_tag\n\n        # Add the root element to the internal child/open data structures\n        root_element = self.elementClass(name, namespace)\n        root_element._element = root\n        self.document._childNodes.append(root_element)\n        self.openElements.append(root_element)\n\n        # Reset to the default insert comment function\n        self.insertComment = self.insertCommentMain\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treewalkers/__init__.py",
    "content": "\"\"\"A collection of modules for iterating through different kinds of\ntree, generating tokens identical to those produced by the tokenizer\nmodule.\n\nTo create a tree walker for a new type of tree, you need to do\nimplement a tree walker object (called TreeWalker by convention) that\nimplements a 'serialize' method taking a tree as sole argument and\nreturning an iterator generating tokens.\n\"\"\"\n\nfrom __future__ import absolute_import, division, unicode_literals\n\nfrom .. import constants\nfrom .._utils import default_etree\n\n__all__ = [\"getTreeWalker\", \"pprint\"]\n\ntreeWalkerCache = {}\n\n\ndef getTreeWalker(treeType, implementation=None, **kwargs):\n    \"\"\"Get a TreeWalker class for various types of tree with built-in support\n\n    :arg str treeType: the name of the tree type required (case-insensitive).\n        Supported values are:\n\n        * \"dom\": The xml.dom.minidom DOM implementation\n        * \"etree\": A generic walker for tree implementations exposing an\n          elementtree-like interface (known to work with ElementTree,\n          cElementTree and lxml.etree).\n        * \"lxml\": Optimized walker for lxml.etree\n        * \"genshi\": a Genshi stream\n\n    :arg implementation: A module implementing the tree type e.g.\n        xml.etree.ElementTree or cElementTree (Currently applies to the \"etree\"\n        tree type only).\n\n    :arg kwargs: keyword arguments passed to the etree walker--for other\n        walkers, this has no effect\n\n    :returns: a TreeWalker class\n\n    \"\"\"\n\n    treeType = treeType.lower()\n    if treeType not in treeWalkerCache:\n        if treeType == \"dom\":\n            from . import dom\n            treeWalkerCache[treeType] = dom.TreeWalker\n        elif treeType == \"genshi\":\n            from . import genshi\n            treeWalkerCache[treeType] = genshi.TreeWalker\n        elif treeType == \"lxml\":\n            from . import etree_lxml\n            treeWalkerCache[treeType] = etree_lxml.TreeWalker\n        elif treeType == \"etree\":\n            from . import etree\n            if implementation is None:\n                implementation = default_etree\n            # XXX: NEVER cache here, caching is done in the etree submodule\n            return etree.getETreeModule(implementation, **kwargs).TreeWalker\n    return treeWalkerCache.get(treeType)\n\n\ndef concatenateCharacterTokens(tokens):\n    pendingCharacters = []\n    for token in tokens:\n        type = token[\"type\"]\n        if type in (\"Characters\", \"SpaceCharacters\"):\n            pendingCharacters.append(token[\"data\"])\n        else:\n            if pendingCharacters:\n                yield {\"type\": \"Characters\", \"data\": \"\".join(pendingCharacters)}\n                pendingCharacters = []\n            yield token\n    if pendingCharacters:\n        yield {\"type\": \"Characters\", \"data\": \"\".join(pendingCharacters)}\n\n\ndef pprint(walker):\n    \"\"\"Pretty printer for tree walkers\n\n    Takes a TreeWalker instance and pretty prints the output of walking the tree.\n\n    :arg walker: a TreeWalker instance\n\n    \"\"\"\n    output = []\n    indent = 0\n    for token in concatenateCharacterTokens(walker):\n        type = token[\"type\"]\n        if type in (\"StartTag\", \"EmptyTag\"):\n            # tag name\n            if token[\"namespace\"] and token[\"namespace\"] != constants.namespaces[\"html\"]:\n                if token[\"namespace\"] in constants.prefixes:\n                    ns = constants.prefixes[token[\"namespace\"]]\n                else:\n                    ns = token[\"namespace\"]\n                name = \"%s %s\" % (ns, token[\"name\"])\n            else:\n                name = token[\"name\"]\n            output.append(\"%s<%s>\" % (\" \" * indent, name))\n            indent += 2\n            # attributes (sorted for consistent ordering)\n            attrs = token[\"data\"]\n            for (namespace, localname), value in sorted(attrs.items()):\n                if namespace:\n                    if namespace in constants.prefixes:\n                        ns = constants.prefixes[namespace]\n                    else:\n                        ns = namespace\n                    name = \"%s %s\" % (ns, localname)\n                else:\n                    name = localname\n                output.append(\"%s%s=\\\"%s\\\"\" % (\" \" * indent, name, value))\n            # self-closing\n            if type == \"EmptyTag\":\n                indent -= 2\n\n        elif type == \"EndTag\":\n            indent -= 2\n\n        elif type == \"Comment\":\n            output.append(\"%s<!-- %s -->\" % (\" \" * indent, token[\"data\"]))\n\n        elif type == \"Doctype\":\n            if token[\"name\"]:\n                if token[\"publicId\"]:\n                    output.append(\"\"\"%s<!DOCTYPE %s \"%s\" \"%s\">\"\"\" %\n                                  (\" \" * indent,\n                                   token[\"name\"],\n                                   token[\"publicId\"],\n                                   token[\"systemId\"] if token[\"systemId\"] else \"\"))\n                elif token[\"systemId\"]:\n                    output.append(\"\"\"%s<!DOCTYPE %s \"\" \"%s\">\"\"\" %\n                                  (\" \" * indent,\n                                   token[\"name\"],\n                                   token[\"systemId\"]))\n                else:\n                    output.append(\"%s<!DOCTYPE %s>\" % (\" \" * indent,\n                                                       token[\"name\"]))\n            else:\n                output.append(\"%s<!DOCTYPE >\" % (\" \" * indent,))\n\n        elif type == \"Characters\":\n            output.append(\"%s\\\"%s\\\"\" % (\" \" * indent, token[\"data\"]))\n\n        elif type == \"SpaceCharacters\":\n            assert False, \"concatenateCharacterTokens should have got rid of all Space tokens\"\n\n        else:\n            raise ValueError(\"Unknown token type, %s\" % type)\n\n    return \"\\n\".join(output)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treewalkers/base.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom xml.dom import Node\nfrom ..constants import namespaces, voidElements, spaceCharacters\n\n__all__ = [\"DOCUMENT\", \"DOCTYPE\", \"TEXT\", \"ELEMENT\", \"COMMENT\", \"ENTITY\", \"UNKNOWN\",\n           \"TreeWalker\", \"NonRecursiveTreeWalker\"]\n\nDOCUMENT = Node.DOCUMENT_NODE\nDOCTYPE = Node.DOCUMENT_TYPE_NODE\nTEXT = Node.TEXT_NODE\nELEMENT = Node.ELEMENT_NODE\nCOMMENT = Node.COMMENT_NODE\nENTITY = Node.ENTITY_NODE\nUNKNOWN = \"<#UNKNOWN#>\"\n\nspaceCharacters = \"\".join(spaceCharacters)\n\n\nclass TreeWalker(object):\n    \"\"\"Walks a tree yielding tokens\n\n    Tokens are dicts that all have a ``type`` field specifying the type of the\n    token.\n\n    \"\"\"\n    def __init__(self, tree):\n        \"\"\"Creates a TreeWalker\n\n        :arg tree: the tree to walk\n\n        \"\"\"\n        self.tree = tree\n\n    def __iter__(self):\n        raise NotImplementedError\n\n    def error(self, msg):\n        \"\"\"Generates an error token with the given message\n\n        :arg msg: the error message\n\n        :returns: SerializeError token\n\n        \"\"\"\n        return {\"type\": \"SerializeError\", \"data\": msg}\n\n    def emptyTag(self, namespace, name, attrs, hasChildren=False):\n        \"\"\"Generates an EmptyTag token\n\n        :arg namespace: the namespace of the token--can be ``None``\n\n        :arg name: the name of the element\n\n        :arg attrs: the attributes of the element as a dict\n\n        :arg hasChildren: whether or not to yield a SerializationError because\n            this tag shouldn't have children\n\n        :returns: EmptyTag token\n\n        \"\"\"\n        yield {\"type\": \"EmptyTag\", \"name\": name,\n               \"namespace\": namespace,\n               \"data\": attrs}\n        if hasChildren:\n            yield self.error(\"Void element has children\")\n\n    def startTag(self, namespace, name, attrs):\n        \"\"\"Generates a StartTag token\n\n        :arg namespace: the namespace of the token--can be ``None``\n\n        :arg name: the name of the element\n\n        :arg attrs: the attributes of the element as a dict\n\n        :returns: StartTag token\n\n        \"\"\"\n        return {\"type\": \"StartTag\",\n                \"name\": name,\n                \"namespace\": namespace,\n                \"data\": attrs}\n\n    def endTag(self, namespace, name):\n        \"\"\"Generates an EndTag token\n\n        :arg namespace: the namespace of the token--can be ``None``\n\n        :arg name: the name of the element\n\n        :returns: EndTag token\n\n        \"\"\"\n        return {\"type\": \"EndTag\",\n                \"name\": name,\n                \"namespace\": namespace}\n\n    def text(self, data):\n        \"\"\"Generates SpaceCharacters and Characters tokens\n\n        Depending on what's in the data, this generates one or more\n        ``SpaceCharacters`` and ``Characters`` tokens.\n\n        For example:\n\n            >>> from html5lib.treewalkers.base import TreeWalker\n            >>> # Give it an empty tree just so it instantiates\n            >>> walker = TreeWalker([])\n            >>> list(walker.text(''))\n            []\n            >>> list(walker.text('  '))\n            [{u'data': '  ', u'type': u'SpaceCharacters'}]\n            >>> list(walker.text(' abc '))  # doctest: +NORMALIZE_WHITESPACE\n            [{u'data': ' ', u'type': u'SpaceCharacters'},\n            {u'data': u'abc', u'type': u'Characters'},\n            {u'data': u' ', u'type': u'SpaceCharacters'}]\n\n        :arg data: the text data\n\n        :returns: one or more ``SpaceCharacters`` and ``Characters`` tokens\n\n        \"\"\"\n        data = data\n        middle = data.lstrip(spaceCharacters)\n        left = data[:len(data) - len(middle)]\n        if left:\n            yield {\"type\": \"SpaceCharacters\", \"data\": left}\n        data = middle\n        middle = data.rstrip(spaceCharacters)\n        right = data[len(middle):]\n        if middle:\n            yield {\"type\": \"Characters\", \"data\": middle}\n        if right:\n            yield {\"type\": \"SpaceCharacters\", \"data\": right}\n\n    def comment(self, data):\n        \"\"\"Generates a Comment token\n\n        :arg data: the comment\n\n        :returns: Comment token\n\n        \"\"\"\n        return {\"type\": \"Comment\", \"data\": data}\n\n    def doctype(self, name, publicId=None, systemId=None):\n        \"\"\"Generates a Doctype token\n\n        :arg name:\n\n        :arg publicId:\n\n        :arg systemId:\n\n        :returns: the Doctype token\n\n        \"\"\"\n        return {\"type\": \"Doctype\",\n                \"name\": name,\n                \"publicId\": publicId,\n                \"systemId\": systemId}\n\n    def entity(self, name):\n        \"\"\"Generates an Entity token\n\n        :arg name: the entity name\n\n        :returns: an Entity token\n\n        \"\"\"\n        return {\"type\": \"Entity\", \"name\": name}\n\n    def unknown(self, nodeType):\n        \"\"\"Handles unknown node types\"\"\"\n        return self.error(\"Unknown node type: \" + nodeType)\n\n\nclass NonRecursiveTreeWalker(TreeWalker):\n    def getNodeDetails(self, node):\n        raise NotImplementedError\n\n    def getFirstChild(self, node):\n        raise NotImplementedError\n\n    def getNextSibling(self, node):\n        raise NotImplementedError\n\n    def getParentNode(self, node):\n        raise NotImplementedError\n\n    def __iter__(self):\n        currentNode = self.tree\n        while currentNode is not None:\n            details = self.getNodeDetails(currentNode)\n            type, details = details[0], details[1:]\n            hasChildren = False\n\n            if type == DOCTYPE:\n                yield self.doctype(*details)\n\n            elif type == TEXT:\n                for token in self.text(*details):\n                    yield token\n\n            elif type == ELEMENT:\n                namespace, name, attributes, hasChildren = details\n                if (not namespace or namespace == namespaces[\"html\"]) and name in voidElements:\n                    for token in self.emptyTag(namespace, name, attributes,\n                                               hasChildren):\n                        yield token\n                    hasChildren = False\n                else:\n                    yield self.startTag(namespace, name, attributes)\n\n            elif type == COMMENT:\n                yield self.comment(details[0])\n\n            elif type == ENTITY:\n                yield self.entity(details[0])\n\n            elif type == DOCUMENT:\n                hasChildren = True\n\n            else:\n                yield self.unknown(details[0])\n\n            if hasChildren:\n                firstChild = self.getFirstChild(currentNode)\n            else:\n                firstChild = None\n\n            if firstChild is not None:\n                currentNode = firstChild\n            else:\n                while currentNode is not None:\n                    details = self.getNodeDetails(currentNode)\n                    type, details = details[0], details[1:]\n                    if type == ELEMENT:\n                        namespace, name, attributes, hasChildren = details\n                        if (namespace and namespace != namespaces[\"html\"]) or name not in voidElements:\n                            yield self.endTag(namespace, name)\n                    if self.tree is currentNode:\n                        currentNode = None\n                        break\n                    nextSibling = self.getNextSibling(currentNode)\n                    if nextSibling is not None:\n                        currentNode = nextSibling\n                        break\n                    else:\n                        currentNode = self.getParentNode(currentNode)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treewalkers/dom.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom xml.dom import Node\n\nfrom . import base\n\n\nclass TreeWalker(base.NonRecursiveTreeWalker):\n    def getNodeDetails(self, node):\n        if node.nodeType == Node.DOCUMENT_TYPE_NODE:\n            return base.DOCTYPE, node.name, node.publicId, node.systemId\n\n        elif node.nodeType in (Node.TEXT_NODE, Node.CDATA_SECTION_NODE):\n            return base.TEXT, node.nodeValue\n\n        elif node.nodeType == Node.ELEMENT_NODE:\n            attrs = {}\n            for attr in list(node.attributes.keys()):\n                attr = node.getAttributeNode(attr)\n                if attr.namespaceURI:\n                    attrs[(attr.namespaceURI, attr.localName)] = attr.value\n                else:\n                    attrs[(None, attr.name)] = attr.value\n            return (base.ELEMENT, node.namespaceURI, node.nodeName,\n                    attrs, node.hasChildNodes())\n\n        elif node.nodeType == Node.COMMENT_NODE:\n            return base.COMMENT, node.nodeValue\n\n        elif node.nodeType in (Node.DOCUMENT_NODE, Node.DOCUMENT_FRAGMENT_NODE):\n            return (base.DOCUMENT,)\n\n        else:\n            return base.UNKNOWN, node.nodeType\n\n    def getFirstChild(self, node):\n        return node.firstChild\n\n    def getNextSibling(self, node):\n        return node.nextSibling\n\n    def getParentNode(self, node):\n        return node.parentNode\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treewalkers/etree.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom collections import OrderedDict\nimport re\n\nfrom pip._vendor.six import string_types\n\nfrom . import base\nfrom .._utils import moduleFactoryFactory\n\ntag_regexp = re.compile(\"{([^}]*)}(.*)\")\n\n\ndef getETreeBuilder(ElementTreeImplementation):\n    ElementTree = ElementTreeImplementation\n    ElementTreeCommentType = ElementTree.Comment(\"asd\").tag\n\n    class TreeWalker(base.NonRecursiveTreeWalker):  # pylint:disable=unused-variable\n        \"\"\"Given the particular ElementTree representation, this implementation,\n        to avoid using recursion, returns \"nodes\" as tuples with the following\n        content:\n\n        1. The current element\n\n        2. The index of the element relative to its parent\n\n        3. A stack of ancestor elements\n\n        4. A flag \"text\", \"tail\" or None to indicate if the current node is a\n           text node; either the text or tail of the current element (1)\n        \"\"\"\n        def getNodeDetails(self, node):\n            if isinstance(node, tuple):  # It might be the root Element\n                elt, _, _, flag = node\n                if flag in (\"text\", \"tail\"):\n                    return base.TEXT, getattr(elt, flag)\n                else:\n                    node = elt\n\n            if not(hasattr(node, \"tag\")):\n                node = node.getroot()\n\n            if node.tag in (\"DOCUMENT_ROOT\", \"DOCUMENT_FRAGMENT\"):\n                return (base.DOCUMENT,)\n\n            elif node.tag == \"<!DOCTYPE>\":\n                return (base.DOCTYPE, node.text,\n                        node.get(\"publicId\"), node.get(\"systemId\"))\n\n            elif node.tag == ElementTreeCommentType:\n                return base.COMMENT, node.text\n\n            else:\n                assert isinstance(node.tag, string_types), type(node.tag)\n                # This is assumed to be an ordinary element\n                match = tag_regexp.match(node.tag)\n                if match:\n                    namespace, tag = match.groups()\n                else:\n                    namespace = None\n                    tag = node.tag\n                attrs = OrderedDict()\n                for name, value in list(node.attrib.items()):\n                    match = tag_regexp.match(name)\n                    if match:\n                        attrs[(match.group(1), match.group(2))] = value\n                    else:\n                        attrs[(None, name)] = value\n                return (base.ELEMENT, namespace, tag,\n                        attrs, len(node) or node.text)\n\n        def getFirstChild(self, node):\n            if isinstance(node, tuple):\n                element, key, parents, flag = node\n            else:\n                element, key, parents, flag = node, None, [], None\n\n            if flag in (\"text\", \"tail\"):\n                return None\n            else:\n                if element.text:\n                    return element, key, parents, \"text\"\n                elif len(element):\n                    parents.append(element)\n                    return element[0], 0, parents, None\n                else:\n                    return None\n\n        def getNextSibling(self, node):\n            if isinstance(node, tuple):\n                element, key, parents, flag = node\n            else:\n                return None\n\n            if flag == \"text\":\n                if len(element):\n                    parents.append(element)\n                    return element[0], 0, parents, None\n                else:\n                    return None\n            else:\n                if element.tail and flag != \"tail\":\n                    return element, key, parents, \"tail\"\n                elif key < len(parents[-1]) - 1:\n                    return parents[-1][key + 1], key + 1, parents, None\n                else:\n                    return None\n\n        def getParentNode(self, node):\n            if isinstance(node, tuple):\n                element, key, parents, flag = node\n            else:\n                return None\n\n            if flag == \"text\":\n                if not parents:\n                    return element\n                else:\n                    return element, key, parents, None\n            else:\n                parent = parents.pop()\n                if not parents:\n                    return parent\n                else:\n                    assert list(parents[-1]).count(parent) == 1\n                    return parent, list(parents[-1]).index(parent), parents, None\n\n    return locals()\n\ngetETreeModule = moduleFactoryFactory(getETreeBuilder)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treewalkers/etree_lxml.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\nfrom pip._vendor.six import text_type\n\nfrom lxml import etree\nfrom ..treebuilders.etree import tag_regexp\n\nfrom . import base\n\nfrom .. import _ihatexml\n\n\ndef ensure_str(s):\n    if s is None:\n        return None\n    elif isinstance(s, text_type):\n        return s\n    else:\n        return s.decode(\"ascii\", \"strict\")\n\n\nclass Root(object):\n    def __init__(self, et):\n        self.elementtree = et\n        self.children = []\n\n        try:\n            if et.docinfo.internalDTD:\n                self.children.append(Doctype(self,\n                                             ensure_str(et.docinfo.root_name),\n                                             ensure_str(et.docinfo.public_id),\n                                             ensure_str(et.docinfo.system_url)))\n        except AttributeError:\n            pass\n\n        try:\n            node = et.getroot()\n        except AttributeError:\n            node = et\n\n        while node.getprevious() is not None:\n            node = node.getprevious()\n        while node is not None:\n            self.children.append(node)\n            node = node.getnext()\n\n        self.text = None\n        self.tail = None\n\n    def __getitem__(self, key):\n        return self.children[key]\n\n    def getnext(self):\n        return None\n\n    def __len__(self):\n        return 1\n\n\nclass Doctype(object):\n    def __init__(self, root_node, name, public_id, system_id):\n        self.root_node = root_node\n        self.name = name\n        self.public_id = public_id\n        self.system_id = system_id\n\n        self.text = None\n        self.tail = None\n\n    def getnext(self):\n        return self.root_node.children[1]\n\n\nclass FragmentRoot(Root):\n    def __init__(self, children):\n        self.children = [FragmentWrapper(self, child) for child in children]\n        self.text = self.tail = None\n\n    def getnext(self):\n        return None\n\n\nclass FragmentWrapper(object):\n    def __init__(self, fragment_root, obj):\n        self.root_node = fragment_root\n        self.obj = obj\n        if hasattr(self.obj, 'text'):\n            self.text = ensure_str(self.obj.text)\n        else:\n            self.text = None\n        if hasattr(self.obj, 'tail'):\n            self.tail = ensure_str(self.obj.tail)\n        else:\n            self.tail = None\n\n    def __getattr__(self, name):\n        return getattr(self.obj, name)\n\n    def getnext(self):\n        siblings = self.root_node.children\n        idx = siblings.index(self)\n        if idx < len(siblings) - 1:\n            return siblings[idx + 1]\n        else:\n            return None\n\n    def __getitem__(self, key):\n        return self.obj[key]\n\n    def __bool__(self):\n        return bool(self.obj)\n\n    def getparent(self):\n        return None\n\n    def __str__(self):\n        return str(self.obj)\n\n    def __unicode__(self):\n        return str(self.obj)\n\n    def __len__(self):\n        return len(self.obj)\n\n\nclass TreeWalker(base.NonRecursiveTreeWalker):\n    def __init__(self, tree):\n        # pylint:disable=redefined-variable-type\n        if isinstance(tree, list):\n            self.fragmentChildren = set(tree)\n            tree = FragmentRoot(tree)\n        else:\n            self.fragmentChildren = set()\n            tree = Root(tree)\n        base.NonRecursiveTreeWalker.__init__(self, tree)\n        self.filter = _ihatexml.InfosetFilter()\n\n    def getNodeDetails(self, node):\n        if isinstance(node, tuple):  # Text node\n            node, key = node\n            assert key in (\"text\", \"tail\"), \"Text nodes are text or tail, found %s\" % key\n            return base.TEXT, ensure_str(getattr(node, key))\n\n        elif isinstance(node, Root):\n            return (base.DOCUMENT,)\n\n        elif isinstance(node, Doctype):\n            return base.DOCTYPE, node.name, node.public_id, node.system_id\n\n        elif isinstance(node, FragmentWrapper) and not hasattr(node, \"tag\"):\n            return base.TEXT, ensure_str(node.obj)\n\n        elif node.tag == etree.Comment:\n            return base.COMMENT, ensure_str(node.text)\n\n        elif node.tag == etree.Entity:\n            return base.ENTITY, ensure_str(node.text)[1:-1]  # strip &;\n\n        else:\n            # This is assumed to be an ordinary element\n            match = tag_regexp.match(ensure_str(node.tag))\n            if match:\n                namespace, tag = match.groups()\n            else:\n                namespace = None\n                tag = ensure_str(node.tag)\n            attrs = {}\n            for name, value in list(node.attrib.items()):\n                name = ensure_str(name)\n                value = ensure_str(value)\n                match = tag_regexp.match(name)\n                if match:\n                    attrs[(match.group(1), match.group(2))] = value\n                else:\n                    attrs[(None, name)] = value\n            return (base.ELEMENT, namespace, self.filter.fromXmlName(tag),\n                    attrs, len(node) > 0 or node.text)\n\n    def getFirstChild(self, node):\n        assert not isinstance(node, tuple), \"Text nodes have no children\"\n\n        assert len(node) or node.text, \"Node has no children\"\n        if node.text:\n            return (node, \"text\")\n        else:\n            return node[0]\n\n    def getNextSibling(self, node):\n        if isinstance(node, tuple):  # Text node\n            node, key = node\n            assert key in (\"text\", \"tail\"), \"Text nodes are text or tail, found %s\" % key\n            if key == \"text\":\n                # XXX: we cannot use a \"bool(node) and node[0] or None\" construct here\n                # because node[0] might evaluate to False if it has no child element\n                if len(node):\n                    return node[0]\n                else:\n                    return None\n            else:  # tail\n                return node.getnext()\n\n        return (node, \"tail\") if node.tail else node.getnext()\n\n    def getParentNode(self, node):\n        if isinstance(node, tuple):  # Text node\n            node, key = node\n            assert key in (\"text\", \"tail\"), \"Text nodes are text or tail, found %s\" % key\n            if key == \"text\":\n                return node\n            # else: fallback to \"normal\" processing\n        elif node in self.fragmentChildren:\n            return None\n\n        return node.getparent()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/html5lib/treewalkers/genshi.py",
    "content": "from __future__ import absolute_import, division, unicode_literals\n\nfrom genshi.core import QName\nfrom genshi.core import START, END, XML_NAMESPACE, DOCTYPE, TEXT\nfrom genshi.core import START_NS, END_NS, START_CDATA, END_CDATA, PI, COMMENT\n\nfrom . import base\n\nfrom ..constants import voidElements, namespaces\n\n\nclass TreeWalker(base.TreeWalker):\n    def __iter__(self):\n        # Buffer the events so we can pass in the following one\n        previous = None\n        for event in self.tree:\n            if previous is not None:\n                for token in self.tokens(previous, event):\n                    yield token\n            previous = event\n\n        # Don't forget the final event!\n        if previous is not None:\n            for token in self.tokens(previous, None):\n                yield token\n\n    def tokens(self, event, next):\n        kind, data, _ = event\n        if kind == START:\n            tag, attribs = data\n            name = tag.localname\n            namespace = tag.namespace\n            converted_attribs = {}\n            for k, v in attribs:\n                if isinstance(k, QName):\n                    converted_attribs[(k.namespace, k.localname)] = v\n                else:\n                    converted_attribs[(None, k)] = v\n\n            if namespace == namespaces[\"html\"] and name in voidElements:\n                for token in self.emptyTag(namespace, name, converted_attribs,\n                                           not next or next[0] != END or\n                                           next[1] != tag):\n                    yield token\n            else:\n                yield self.startTag(namespace, name, converted_attribs)\n\n        elif kind == END:\n            name = data.localname\n            namespace = data.namespace\n            if namespace != namespaces[\"html\"] or name not in voidElements:\n                yield self.endTag(namespace, name)\n\n        elif kind == COMMENT:\n            yield self.comment(data)\n\n        elif kind == TEXT:\n            for token in self.text(data):\n                yield token\n\n        elif kind == DOCTYPE:\n            yield self.doctype(*data)\n\n        elif kind in (XML_NAMESPACE, DOCTYPE, START_NS, END_NS,\n                      START_CDATA, END_CDATA, PI):\n            pass\n\n        else:\n            yield self.unknown(kind)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/idna/__init__.py",
    "content": "from .package_data import __version__\nfrom .core import *\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/idna/codec.py",
    "content": "from .core import encode, decode, alabel, ulabel, IDNAError\nimport codecs\nimport re\n\n_unicode_dots_re = re.compile(u'[\\u002e\\u3002\\uff0e\\uff61]')\n\nclass Codec(codecs.Codec):\n\n    def encode(self, data, errors='strict'):\n\n        if errors != 'strict':\n            raise IDNAError(\"Unsupported error handling \\\"{0}\\\"\".format(errors))\n\n        if not data:\n            return \"\", 0\n\n        return encode(data), len(data)\n\n    def decode(self, data, errors='strict'):\n\n        if errors != 'strict':\n            raise IDNAError(\"Unsupported error handling \\\"{0}\\\"\".format(errors))\n\n        if not data:\n            return u\"\", 0\n\n        return decode(data), len(data)\n\nclass IncrementalEncoder(codecs.BufferedIncrementalEncoder):\n    def _buffer_encode(self, data, errors, final):\n        if errors != 'strict':\n            raise IDNAError(\"Unsupported error handling \\\"{0}\\\"\".format(errors))\n\n        if not data:\n            return (\"\", 0)\n\n        labels = _unicode_dots_re.split(data)\n        trailing_dot = u''\n        if labels:\n            if not labels[-1]:\n                trailing_dot = '.'\n                del labels[-1]\n            elif not final:\n                # Keep potentially unfinished label until the next call\n                del labels[-1]\n                if labels:\n                    trailing_dot = '.'\n\n        result = []\n        size = 0\n        for label in labels:\n            result.append(alabel(label))\n            if size:\n                size += 1\n            size += len(label)\n\n        # Join with U+002E\n        result = \".\".join(result) + trailing_dot\n        size += len(trailing_dot)\n        return (result, size)\n\nclass IncrementalDecoder(codecs.BufferedIncrementalDecoder):\n    def _buffer_decode(self, data, errors, final):\n        if errors != 'strict':\n            raise IDNAError(\"Unsupported error handling \\\"{0}\\\"\".format(errors))\n\n        if not data:\n            return (u\"\", 0)\n\n        # IDNA allows decoding to operate on Unicode strings, too.\n        if isinstance(data, unicode):\n            labels = _unicode_dots_re.split(data)\n        else:\n            # Must be ASCII string\n            data = str(data)\n            unicode(data, \"ascii\")\n            labels = data.split(\".\")\n\n        trailing_dot = u''\n        if labels:\n            if not labels[-1]:\n                trailing_dot = u'.'\n                del labels[-1]\n            elif not final:\n                # Keep potentially unfinished label until the next call\n                del labels[-1]\n                if labels:\n                    trailing_dot = u'.'\n\n        result = []\n        size = 0\n        for label in labels:\n            result.append(ulabel(label))\n            if size:\n                size += 1\n            size += len(label)\n\n        result = u\".\".join(result) + trailing_dot\n        size += len(trailing_dot)\n        return (result, size)\n\n\nclass StreamWriter(Codec, codecs.StreamWriter):\n    pass\n\nclass StreamReader(Codec, codecs.StreamReader):\n    pass\n\ndef getregentry():\n    return codecs.CodecInfo(\n        name='idna',\n        encode=Codec().encode,\n        decode=Codec().decode,\n        incrementalencoder=IncrementalEncoder,\n        incrementaldecoder=IncrementalDecoder,\n        streamwriter=StreamWriter,\n        streamreader=StreamReader,\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/idna/compat.py",
    "content": "from .core import *\nfrom .codec import *\n\ndef ToASCII(label):\n    return encode(label)\n\ndef ToUnicode(label):\n    return decode(label)\n\ndef nameprep(s):\n    raise NotImplementedError(\"IDNA 2008 does not utilise nameprep protocol\")\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/idna/core.py",
    "content": "from . import idnadata\nimport bisect\nimport unicodedata\nimport re\nimport sys\nfrom .intranges import intranges_contain\n\n_virama_combining_class = 9\n_alabel_prefix = b'xn--'\n_unicode_dots_re = re.compile(u'[\\u002e\\u3002\\uff0e\\uff61]')\n\nif sys.version_info[0] == 3:\n    unicode = str\n    unichr = chr\n\nclass IDNAError(UnicodeError):\n    \"\"\" Base exception for all IDNA-encoding related problems \"\"\"\n    pass\n\n\nclass IDNABidiError(IDNAError):\n    \"\"\" Exception when bidirectional requirements are not satisfied \"\"\"\n    pass\n\n\nclass InvalidCodepoint(IDNAError):\n    \"\"\" Exception when a disallowed or unallocated codepoint is used \"\"\"\n    pass\n\n\nclass InvalidCodepointContext(IDNAError):\n    \"\"\" Exception when the codepoint is not valid in the context it is used \"\"\"\n    pass\n\n\ndef _combining_class(cp):\n    v = unicodedata.combining(unichr(cp))\n    if v == 0:\n        if not unicodedata.name(unichr(cp)):\n            raise ValueError(\"Unknown character in unicodedata\")\n    return v\n\ndef _is_script(cp, script):\n    return intranges_contain(ord(cp), idnadata.scripts[script])\n\ndef _punycode(s):\n    return s.encode('punycode')\n\ndef _unot(s):\n    return 'U+{0:04X}'.format(s)\n\n\ndef valid_label_length(label):\n\n    if len(label) > 63:\n        return False\n    return True\n\n\ndef valid_string_length(label, trailing_dot):\n\n    if len(label) > (254 if trailing_dot else 253):\n        return False\n    return True\n\n\ndef check_bidi(label, check_ltr=False):\n\n    # Bidi rules should only be applied if string contains RTL characters\n    bidi_label = False\n    for (idx, cp) in enumerate(label, 1):\n        direction = unicodedata.bidirectional(cp)\n        if direction == '':\n            # String likely comes from a newer version of Unicode\n            raise IDNABidiError('Unknown directionality in label {0} at position {1}'.format(repr(label), idx))\n        if direction in ['R', 'AL', 'AN']:\n            bidi_label = True\n    if not bidi_label and not check_ltr:\n        return True\n\n    # Bidi rule 1\n    direction = unicodedata.bidirectional(label[0])\n    if direction in ['R', 'AL']:\n        rtl = True\n    elif direction == 'L':\n        rtl = False\n    else:\n        raise IDNABidiError('First codepoint in label {0} must be directionality L, R or AL'.format(repr(label)))\n\n    valid_ending = False\n    number_type = False\n    for (idx, cp) in enumerate(label, 1):\n        direction = unicodedata.bidirectional(cp)\n\n        if rtl:\n            # Bidi rule 2\n            if not direction in ['R', 'AL', 'AN', 'EN', 'ES', 'CS', 'ET', 'ON', 'BN', 'NSM']:\n                raise IDNABidiError('Invalid direction for codepoint at position {0} in a right-to-left label'.format(idx))\n            # Bidi rule 3\n            if direction in ['R', 'AL', 'EN', 'AN']:\n                valid_ending = True\n            elif direction != 'NSM':\n                valid_ending = False\n            # Bidi rule 4\n            if direction in ['AN', 'EN']:\n                if not number_type:\n                    number_type = direction\n                else:\n                    if number_type != direction:\n                        raise IDNABidiError('Can not mix numeral types in a right-to-left label')\n        else:\n            # Bidi rule 5\n            if not direction in ['L', 'EN', 'ES', 'CS', 'ET', 'ON', 'BN', 'NSM']:\n                raise IDNABidiError('Invalid direction for codepoint at position {0} in a left-to-right label'.format(idx))\n            # Bidi rule 6\n            if direction in ['L', 'EN']:\n                valid_ending = True\n            elif direction != 'NSM':\n                valid_ending = False\n\n    if not valid_ending:\n        raise IDNABidiError('Label ends with illegal codepoint directionality')\n\n    return True\n\n\ndef check_initial_combiner(label):\n\n    if unicodedata.category(label[0])[0] == 'M':\n        raise IDNAError('Label begins with an illegal combining character')\n    return True\n\n\ndef check_hyphen_ok(label):\n\n    if label[2:4] == '--':\n        raise IDNAError('Label has disallowed hyphens in 3rd and 4th position')\n    if label[0] == '-' or label[-1] == '-':\n        raise IDNAError('Label must not start or end with a hyphen')\n    return True\n\n\ndef check_nfc(label):\n\n    if unicodedata.normalize('NFC', label) != label:\n        raise IDNAError('Label must be in Normalization Form C')\n\n\ndef valid_contextj(label, pos):\n\n    cp_value = ord(label[pos])\n\n    if cp_value == 0x200c:\n\n        if pos > 0:\n            if _combining_class(ord(label[pos - 1])) == _virama_combining_class:\n                return True\n\n        ok = False\n        for i in range(pos-1, -1, -1):\n            joining_type = idnadata.joining_types.get(ord(label[i]))\n            if joining_type == ord('T'):\n                continue\n            if joining_type in [ord('L'), ord('D')]:\n                ok = True\n                break\n\n        if not ok:\n            return False\n\n        ok = False\n        for i in range(pos+1, len(label)):\n            joining_type = idnadata.joining_types.get(ord(label[i]))\n            if joining_type == ord('T'):\n                continue\n            if joining_type in [ord('R'), ord('D')]:\n                ok = True\n                break\n        return ok\n\n    if cp_value == 0x200d:\n\n        if pos > 0:\n            if _combining_class(ord(label[pos - 1])) == _virama_combining_class:\n                return True\n        return False\n\n    else:\n\n        return False\n\n\ndef valid_contexto(label, pos, exception=False):\n\n    cp_value = ord(label[pos])\n\n    if cp_value == 0x00b7:\n        if 0 < pos < len(label)-1:\n            if ord(label[pos - 1]) == 0x006c and ord(label[pos + 1]) == 0x006c:\n                return True\n        return False\n\n    elif cp_value == 0x0375:\n        if pos < len(label)-1 and len(label) > 1:\n            return _is_script(label[pos + 1], 'Greek')\n        return False\n\n    elif cp_value == 0x05f3 or cp_value == 0x05f4:\n        if pos > 0:\n            return _is_script(label[pos - 1], 'Hebrew')\n        return False\n\n    elif cp_value == 0x30fb:\n        for cp in label:\n            if cp == u'\\u30fb':\n                continue\n            if _is_script(cp, 'Hiragana') or _is_script(cp, 'Katakana') or _is_script(cp, 'Han'):\n                return True\n        return False\n\n    elif 0x660 <= cp_value <= 0x669:\n        for cp in label:\n            if 0x6f0 <= ord(cp) <= 0x06f9:\n                return False\n        return True\n\n    elif 0x6f0 <= cp_value <= 0x6f9:\n        for cp in label:\n            if 0x660 <= ord(cp) <= 0x0669:\n                return False\n        return True\n\n\ndef check_label(label):\n\n    if isinstance(label, (bytes, bytearray)):\n        label = label.decode('utf-8')\n    if len(label) == 0:\n        raise IDNAError('Empty Label')\n\n    check_nfc(label)\n    check_hyphen_ok(label)\n    check_initial_combiner(label)\n\n    for (pos, cp) in enumerate(label):\n        cp_value = ord(cp)\n        if intranges_contain(cp_value, idnadata.codepoint_classes['PVALID']):\n            continue\n        elif intranges_contain(cp_value, idnadata.codepoint_classes['CONTEXTJ']):\n            try:\n                if not valid_contextj(label, pos):\n                    raise InvalidCodepointContext('Joiner {0} not allowed at position {1} in {2}'.format(\n                        _unot(cp_value), pos+1, repr(label)))\n            except ValueError:\n                raise IDNAError('Unknown codepoint adjacent to joiner {0} at position {1} in {2}'.format(\n                    _unot(cp_value), pos+1, repr(label)))\n        elif intranges_contain(cp_value, idnadata.codepoint_classes['CONTEXTO']):\n            if not valid_contexto(label, pos):\n                raise InvalidCodepointContext('Codepoint {0} not allowed at position {1} in {2}'.format(_unot(cp_value), pos+1, repr(label)))\n        else:\n            raise InvalidCodepoint('Codepoint {0} at position {1} of {2} not allowed'.format(_unot(cp_value), pos+1, repr(label)))\n\n    check_bidi(label)\n\n\ndef alabel(label):\n\n    try:\n        label = label.encode('ascii')\n        ulabel(label)\n        if not valid_label_length(label):\n            raise IDNAError('Label too long')\n        return label\n    except UnicodeEncodeError:\n        pass\n\n    if not label:\n        raise IDNAError('No Input')\n\n    label = unicode(label)\n    check_label(label)\n    label = _punycode(label)\n    label = _alabel_prefix + label\n\n    if not valid_label_length(label):\n        raise IDNAError('Label too long')\n\n    return label\n\n\ndef ulabel(label):\n\n    if not isinstance(label, (bytes, bytearray)):\n        try:\n            label = label.encode('ascii')\n        except UnicodeEncodeError:\n            check_label(label)\n            return label\n\n    label = label.lower()\n    if label.startswith(_alabel_prefix):\n        label = label[len(_alabel_prefix):]\n    else:\n        check_label(label)\n        return label.decode('ascii')\n\n    label = label.decode('punycode')\n    check_label(label)\n    return label\n\n\ndef uts46_remap(domain, std3_rules=True, transitional=False):\n    \"\"\"Re-map the characters in the string according to UTS46 processing.\"\"\"\n    from .uts46data import uts46data\n    output = u\"\"\n    try:\n        for pos, char in enumerate(domain):\n            code_point = ord(char)\n            uts46row = uts46data[code_point if code_point < 256 else\n                bisect.bisect_left(uts46data, (code_point, \"Z\")) - 1]\n            status = uts46row[1]\n            replacement = uts46row[2] if len(uts46row) == 3 else None\n            if (status == \"V\" or\n                    (status == \"D\" and not transitional) or\n                    (status == \"3\" and not std3_rules and replacement is None)):\n                output += char\n            elif replacement is not None and (status == \"M\" or\n                    (status == \"3\" and not std3_rules) or\n                    (status == \"D\" and transitional)):\n                output += replacement\n            elif status != \"I\":\n                raise IndexError()\n        return unicodedata.normalize(\"NFC\", output)\n    except IndexError:\n        raise InvalidCodepoint(\n            \"Codepoint {0} not allowed at position {1} in {2}\".format(\n            _unot(code_point), pos + 1, repr(domain)))\n\n\ndef encode(s, strict=False, uts46=False, std3_rules=False, transitional=False):\n\n    if isinstance(s, (bytes, bytearray)):\n        s = s.decode(\"ascii\")\n    if uts46:\n        s = uts46_remap(s, std3_rules, transitional)\n    trailing_dot = False\n    result = []\n    if strict:\n        labels = s.split('.')\n    else:\n        labels = _unicode_dots_re.split(s)\n    if not labels or labels == ['']:\n        raise IDNAError('Empty domain')\n    if labels[-1] == '':\n        del labels[-1]\n        trailing_dot = True\n    for label in labels:\n        s = alabel(label)\n        if s:\n            result.append(s)\n        else:\n            raise IDNAError('Empty label')\n    if trailing_dot:\n        result.append(b'')\n    s = b'.'.join(result)\n    if not valid_string_length(s, trailing_dot):\n        raise IDNAError('Domain too long')\n    return s\n\n\ndef decode(s, strict=False, uts46=False, std3_rules=False):\n\n    if isinstance(s, (bytes, bytearray)):\n        s = s.decode(\"ascii\")\n    if uts46:\n        s = uts46_remap(s, std3_rules, False)\n    trailing_dot = False\n    result = []\n    if not strict:\n        labels = _unicode_dots_re.split(s)\n    else:\n        labels = s.split(u'.')\n    if not labels or labels == ['']:\n        raise IDNAError('Empty domain')\n    if not labels[-1]:\n        del labels[-1]\n        trailing_dot = True\n    for label in labels:\n        s = ulabel(label)\n        if s:\n            result.append(s)\n        else:\n            raise IDNAError('Empty label')\n    if trailing_dot:\n        result.append(u'')\n    return u'.'.join(result)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/idna/idnadata.py",
    "content": "# This file is automatically generated by tools/idna-data\n\n__version__ = \"11.0.0\"\nscripts = {\n    'Greek': (\n        0x37000000374,\n        0x37500000378,\n        0x37a0000037e,\n        0x37f00000380,\n        0x38400000385,\n        0x38600000387,\n        0x3880000038b,\n        0x38c0000038d,\n        0x38e000003a2,\n        0x3a3000003e2,\n        0x3f000000400,\n        0x1d2600001d2b,\n        0x1d5d00001d62,\n        0x1d6600001d6b,\n        0x1dbf00001dc0,\n        0x1f0000001f16,\n        0x1f1800001f1e,\n        0x1f2000001f46,\n        0x1f4800001f4e,\n        0x1f5000001f58,\n        0x1f5900001f5a,\n        0x1f5b00001f5c,\n        0x1f5d00001f5e,\n        0x1f5f00001f7e,\n        0x1f8000001fb5,\n        0x1fb600001fc5,\n        0x1fc600001fd4,\n        0x1fd600001fdc,\n        0x1fdd00001ff0,\n        0x1ff200001ff5,\n        0x1ff600001fff,\n        0x212600002127,\n        0xab650000ab66,\n        0x101400001018f,\n        0x101a0000101a1,\n        0x1d2000001d246,\n    ),\n    'Han': (\n        0x2e8000002e9a,\n        0x2e9b00002ef4,\n        0x2f0000002fd6,\n        0x300500003006,\n        0x300700003008,\n        0x30210000302a,\n        0x30380000303c,\n        0x340000004db6,\n        0x4e0000009ff0,\n        0xf9000000fa6e,\n        0xfa700000fada,\n        0x200000002a6d7,\n        0x2a7000002b735,\n        0x2b7400002b81e,\n        0x2b8200002cea2,\n        0x2ceb00002ebe1,\n        0x2f8000002fa1e,\n    ),\n    'Hebrew': (\n        0x591000005c8,\n        0x5d0000005eb,\n        0x5ef000005f5,\n        0xfb1d0000fb37,\n        0xfb380000fb3d,\n        0xfb3e0000fb3f,\n        0xfb400000fb42,\n        0xfb430000fb45,\n        0xfb460000fb50,\n    ),\n    'Hiragana': (\n        0x304100003097,\n        0x309d000030a0,\n        0x1b0010001b11f,\n        0x1f2000001f201,\n    ),\n    'Katakana': (\n        0x30a1000030fb,\n        0x30fd00003100,\n        0x31f000003200,\n        0x32d0000032ff,\n        0x330000003358,\n        0xff660000ff70,\n        0xff710000ff9e,\n        0x1b0000001b001,\n    ),\n}\njoining_types = {\n    0x600: 85,\n    0x601: 85,\n    0x602: 85,\n    0x603: 85,\n    0x604: 85,\n    0x605: 85,\n    0x608: 85,\n    0x60b: 85,\n    0x620: 68,\n    0x621: 85,\n    0x622: 82,\n    0x623: 82,\n    0x624: 82,\n    0x625: 82,\n    0x626: 68,\n    0x627: 82,\n    0x628: 68,\n    0x629: 82,\n    0x62a: 68,\n    0x62b: 68,\n    0x62c: 68,\n    0x62d: 68,\n    0x62e: 68,\n    0x62f: 82,\n    0x630: 82,\n    0x631: 82,\n    0x632: 82,\n    0x633: 68,\n    0x634: 68,\n    0x635: 68,\n    0x636: 68,\n    0x637: 68,\n    0x638: 68,\n    0x639: 68,\n    0x63a: 68,\n    0x63b: 68,\n    0x63c: 68,\n    0x63d: 68,\n    0x63e: 68,\n    0x63f: 68,\n    0x640: 67,\n    0x641: 68,\n    0x642: 68,\n    0x643: 68,\n    0x644: 68,\n    0x645: 68,\n    0x646: 68,\n    0x647: 68,\n    0x648: 82,\n    0x649: 68,\n    0x64a: 68,\n    0x66e: 68,\n    0x66f: 68,\n    0x671: 82,\n    0x672: 82,\n    0x673: 82,\n    0x674: 85,\n    0x675: 82,\n    0x676: 82,\n    0x677: 82,\n    0x678: 68,\n    0x679: 68,\n    0x67a: 68,\n    0x67b: 68,\n    0x67c: 68,\n    0x67d: 68,\n    0x67e: 68,\n    0x67f: 68,\n    0x680: 68,\n    0x681: 68,\n    0x682: 68,\n    0x683: 68,\n    0x684: 68,\n    0x685: 68,\n    0x686: 68,\n    0x687: 68,\n    0x688: 82,\n    0x689: 82,\n    0x68a: 82,\n    0x68b: 82,\n    0x68c: 82,\n    0x68d: 82,\n    0x68e: 82,\n    0x68f: 82,\n    0x690: 82,\n    0x691: 82,\n    0x692: 82,\n    0x693: 82,\n    0x694: 82,\n    0x695: 82,\n    0x696: 82,\n    0x697: 82,\n    0x698: 82,\n    0x699: 82,\n    0x69a: 68,\n    0x69b: 68,\n    0x69c: 68,\n    0x69d: 68,\n    0x69e: 68,\n    0x69f: 68,\n    0x6a0: 68,\n    0x6a1: 68,\n    0x6a2: 68,\n    0x6a3: 68,\n    0x6a4: 68,\n    0x6a5: 68,\n    0x6a6: 68,\n    0x6a7: 68,\n    0x6a8: 68,\n    0x6a9: 68,\n    0x6aa: 68,\n    0x6ab: 68,\n    0x6ac: 68,\n    0x6ad: 68,\n    0x6ae: 68,\n    0x6af: 68,\n    0x6b0: 68,\n    0x6b1: 68,\n    0x6b2: 68,\n    0x6b3: 68,\n    0x6b4: 68,\n    0x6b5: 68,\n    0x6b6: 68,\n    0x6b7: 68,\n    0x6b8: 68,\n    0x6b9: 68,\n    0x6ba: 68,\n    0x6bb: 68,\n    0x6bc: 68,\n    0x6bd: 68,\n    0x6be: 68,\n    0x6bf: 68,\n    0x6c0: 82,\n    0x6c1: 68,\n    0x6c2: 68,\n    0x6c3: 82,\n    0x6c4: 82,\n    0x6c5: 82,\n    0x6c6: 82,\n    0x6c7: 82,\n    0x6c8: 82,\n    0x6c9: 82,\n    0x6ca: 82,\n    0x6cb: 82,\n    0x6cc: 68,\n    0x6cd: 82,\n    0x6ce: 68,\n    0x6cf: 82,\n    0x6d0: 68,\n    0x6d1: 68,\n    0x6d2: 82,\n    0x6d3: 82,\n    0x6d5: 82,\n    0x6dd: 85,\n    0x6ee: 82,\n    0x6ef: 82,\n    0x6fa: 68,\n    0x6fb: 68,\n    0x6fc: 68,\n    0x6ff: 68,\n    0x70f: 84,\n    0x710: 82,\n    0x712: 68,\n    0x713: 68,\n    0x714: 68,\n    0x715: 82,\n    0x716: 82,\n    0x717: 82,\n    0x718: 82,\n    0x719: 82,\n    0x71a: 68,\n    0x71b: 68,\n    0x71c: 68,\n    0x71d: 68,\n    0x71e: 82,\n    0x71f: 68,\n    0x720: 68,\n    0x721: 68,\n    0x722: 68,\n    0x723: 68,\n    0x724: 68,\n    0x725: 68,\n    0x726: 68,\n    0x727: 68,\n    0x728: 82,\n    0x729: 68,\n    0x72a: 82,\n    0x72b: 68,\n    0x72c: 82,\n    0x72d: 68,\n    0x72e: 68,\n    0x72f: 82,\n    0x74d: 82,\n    0x74e: 68,\n    0x74f: 68,\n    0x750: 68,\n    0x751: 68,\n    0x752: 68,\n    0x753: 68,\n    0x754: 68,\n    0x755: 68,\n    0x756: 68,\n    0x757: 68,\n    0x758: 68,\n    0x759: 82,\n    0x75a: 82,\n    0x75b: 82,\n    0x75c: 68,\n    0x75d: 68,\n    0x75e: 68,\n    0x75f: 68,\n    0x760: 68,\n    0x761: 68,\n    0x762: 68,\n    0x763: 68,\n    0x764: 68,\n    0x765: 68,\n    0x766: 68,\n    0x767: 68,\n    0x768: 68,\n    0x769: 68,\n    0x76a: 68,\n    0x76b: 82,\n    0x76c: 82,\n    0x76d: 68,\n    0x76e: 68,\n    0x76f: 68,\n    0x770: 68,\n    0x771: 82,\n    0x772: 68,\n    0x773: 82,\n    0x774: 82,\n    0x775: 68,\n    0x776: 68,\n    0x777: 68,\n    0x778: 82,\n    0x779: 82,\n    0x77a: 68,\n    0x77b: 68,\n    0x77c: 68,\n    0x77d: 68,\n    0x77e: 68,\n    0x77f: 68,\n    0x7ca: 68,\n    0x7cb: 68,\n    0x7cc: 68,\n    0x7cd: 68,\n    0x7ce: 68,\n    0x7cf: 68,\n    0x7d0: 68,\n    0x7d1: 68,\n    0x7d2: 68,\n    0x7d3: 68,\n    0x7d4: 68,\n    0x7d5: 68,\n    0x7d6: 68,\n    0x7d7: 68,\n    0x7d8: 68,\n    0x7d9: 68,\n    0x7da: 68,\n    0x7db: 68,\n    0x7dc: 68,\n    0x7dd: 68,\n    0x7de: 68,\n    0x7df: 68,\n    0x7e0: 68,\n    0x7e1: 68,\n    0x7e2: 68,\n    0x7e3: 68,\n    0x7e4: 68,\n    0x7e5: 68,\n    0x7e6: 68,\n    0x7e7: 68,\n    0x7e8: 68,\n    0x7e9: 68,\n    0x7ea: 68,\n    0x7fa: 67,\n    0x840: 82,\n    0x841: 68,\n    0x842: 68,\n    0x843: 68,\n    0x844: 68,\n    0x845: 68,\n    0x846: 82,\n    0x847: 82,\n    0x848: 68,\n    0x849: 82,\n    0x84a: 68,\n    0x84b: 68,\n    0x84c: 68,\n    0x84d: 68,\n    0x84e: 68,\n    0x84f: 68,\n    0x850: 68,\n    0x851: 68,\n    0x852: 68,\n    0x853: 68,\n    0x854: 82,\n    0x855: 68,\n    0x856: 85,\n    0x857: 85,\n    0x858: 85,\n    0x860: 68,\n    0x861: 85,\n    0x862: 68,\n    0x863: 68,\n    0x864: 68,\n    0x865: 68,\n    0x866: 85,\n    0x867: 82,\n    0x868: 68,\n    0x869: 82,\n    0x86a: 82,\n    0x8a0: 68,\n    0x8a1: 68,\n    0x8a2: 68,\n    0x8a3: 68,\n    0x8a4: 68,\n    0x8a5: 68,\n    0x8a6: 68,\n    0x8a7: 68,\n    0x8a8: 68,\n    0x8a9: 68,\n    0x8aa: 82,\n    0x8ab: 82,\n    0x8ac: 82,\n    0x8ad: 85,\n    0x8ae: 82,\n    0x8af: 68,\n    0x8b0: 68,\n    0x8b1: 82,\n    0x8b2: 82,\n    0x8b3: 68,\n    0x8b4: 68,\n    0x8b6: 68,\n    0x8b7: 68,\n    0x8b8: 68,\n    0x8b9: 82,\n    0x8ba: 68,\n    0x8bb: 68,\n    0x8bc: 68,\n    0x8bd: 68,\n    0x8e2: 85,\n    0x1806: 85,\n    0x1807: 68,\n    0x180a: 67,\n    0x180e: 85,\n    0x1820: 68,\n    0x1821: 68,\n    0x1822: 68,\n    0x1823: 68,\n    0x1824: 68,\n    0x1825: 68,\n    0x1826: 68,\n    0x1827: 68,\n    0x1828: 68,\n    0x1829: 68,\n    0x182a: 68,\n    0x182b: 68,\n    0x182c: 68,\n    0x182d: 68,\n    0x182e: 68,\n    0x182f: 68,\n    0x1830: 68,\n    0x1831: 68,\n    0x1832: 68,\n    0x1833: 68,\n    0x1834: 68,\n    0x1835: 68,\n    0x1836: 68,\n    0x1837: 68,\n    0x1838: 68,\n    0x1839: 68,\n    0x183a: 68,\n    0x183b: 68,\n    0x183c: 68,\n    0x183d: 68,\n    0x183e: 68,\n    0x183f: 68,\n    0x1840: 68,\n    0x1841: 68,\n    0x1842: 68,\n    0x1843: 68,\n    0x1844: 68,\n    0x1845: 68,\n    0x1846: 68,\n    0x1847: 68,\n    0x1848: 68,\n    0x1849: 68,\n    0x184a: 68,\n    0x184b: 68,\n    0x184c: 68,\n    0x184d: 68,\n    0x184e: 68,\n    0x184f: 68,\n    0x1850: 68,\n    0x1851: 68,\n    0x1852: 68,\n    0x1853: 68,\n    0x1854: 68,\n    0x1855: 68,\n    0x1856: 68,\n    0x1857: 68,\n    0x1858: 68,\n    0x1859: 68,\n    0x185a: 68,\n    0x185b: 68,\n    0x185c: 68,\n    0x185d: 68,\n    0x185e: 68,\n    0x185f: 68,\n    0x1860: 68,\n    0x1861: 68,\n    0x1862: 68,\n    0x1863: 68,\n    0x1864: 68,\n    0x1865: 68,\n    0x1866: 68,\n    0x1867: 68,\n    0x1868: 68,\n    0x1869: 68,\n    0x186a: 68,\n    0x186b: 68,\n    0x186c: 68,\n    0x186d: 68,\n    0x186e: 68,\n    0x186f: 68,\n    0x1870: 68,\n    0x1871: 68,\n    0x1872: 68,\n    0x1873: 68,\n    0x1874: 68,\n    0x1875: 68,\n    0x1876: 68,\n    0x1877: 68,\n    0x1878: 68,\n    0x1880: 85,\n    0x1881: 85,\n    0x1882: 85,\n    0x1883: 85,\n    0x1884: 85,\n    0x1885: 84,\n    0x1886: 84,\n    0x1887: 68,\n    0x1888: 68,\n    0x1889: 68,\n    0x188a: 68,\n    0x188b: 68,\n    0x188c: 68,\n    0x188d: 68,\n    0x188e: 68,\n    0x188f: 68,\n    0x1890: 68,\n    0x1891: 68,\n    0x1892: 68,\n    0x1893: 68,\n    0x1894: 68,\n    0x1895: 68,\n    0x1896: 68,\n    0x1897: 68,\n    0x1898: 68,\n    0x1899: 68,\n    0x189a: 68,\n    0x189b: 68,\n    0x189c: 68,\n    0x189d: 68,\n    0x189e: 68,\n    0x189f: 68,\n    0x18a0: 68,\n    0x18a1: 68,\n    0x18a2: 68,\n    0x18a3: 68,\n    0x18a4: 68,\n    0x18a5: 68,\n    0x18a6: 68,\n    0x18a7: 68,\n    0x18a8: 68,\n    0x18aa: 68,\n    0x200c: 85,\n    0x200d: 67,\n    0x202f: 85,\n    0x2066: 85,\n    0x2067: 85,\n    0x2068: 85,\n    0x2069: 85,\n    0xa840: 68,\n    0xa841: 68,\n    0xa842: 68,\n    0xa843: 68,\n    0xa844: 68,\n    0xa845: 68,\n    0xa846: 68,\n    0xa847: 68,\n    0xa848: 68,\n    0xa849: 68,\n    0xa84a: 68,\n    0xa84b: 68,\n    0xa84c: 68,\n    0xa84d: 68,\n    0xa84e: 68,\n    0xa84f: 68,\n    0xa850: 68,\n    0xa851: 68,\n    0xa852: 68,\n    0xa853: 68,\n    0xa854: 68,\n    0xa855: 68,\n    0xa856: 68,\n    0xa857: 68,\n    0xa858: 68,\n    0xa859: 68,\n    0xa85a: 68,\n    0xa85b: 68,\n    0xa85c: 68,\n    0xa85d: 68,\n    0xa85e: 68,\n    0xa85f: 68,\n    0xa860: 68,\n    0xa861: 68,\n    0xa862: 68,\n    0xa863: 68,\n    0xa864: 68,\n    0xa865: 68,\n    0xa866: 68,\n    0xa867: 68,\n    0xa868: 68,\n    0xa869: 68,\n    0xa86a: 68,\n    0xa86b: 68,\n    0xa86c: 68,\n    0xa86d: 68,\n    0xa86e: 68,\n    0xa86f: 68,\n    0xa870: 68,\n    0xa871: 68,\n    0xa872: 76,\n    0xa873: 85,\n    0x10ac0: 68,\n    0x10ac1: 68,\n    0x10ac2: 68,\n    0x10ac3: 68,\n    0x10ac4: 68,\n    0x10ac5: 82,\n    0x10ac6: 85,\n    0x10ac7: 82,\n    0x10ac8: 85,\n    0x10ac9: 82,\n    0x10aca: 82,\n    0x10acb: 85,\n    0x10acc: 85,\n    0x10acd: 76,\n    0x10ace: 82,\n    0x10acf: 82,\n    0x10ad0: 82,\n    0x10ad1: 82,\n    0x10ad2: 82,\n    0x10ad3: 68,\n    0x10ad4: 68,\n    0x10ad5: 68,\n    0x10ad6: 68,\n    0x10ad7: 76,\n    0x10ad8: 68,\n    0x10ad9: 68,\n    0x10ada: 68,\n    0x10adb: 68,\n    0x10adc: 68,\n    0x10add: 82,\n    0x10ade: 68,\n    0x10adf: 68,\n    0x10ae0: 68,\n    0x10ae1: 82,\n    0x10ae2: 85,\n    0x10ae3: 85,\n    0x10ae4: 82,\n    0x10aeb: 68,\n    0x10aec: 68,\n    0x10aed: 68,\n    0x10aee: 68,\n    0x10aef: 82,\n    0x10b80: 68,\n    0x10b81: 82,\n    0x10b82: 68,\n    0x10b83: 82,\n    0x10b84: 82,\n    0x10b85: 82,\n    0x10b86: 68,\n    0x10b87: 68,\n    0x10b88: 68,\n    0x10b89: 82,\n    0x10b8a: 68,\n    0x10b8b: 68,\n    0x10b8c: 82,\n    0x10b8d: 68,\n    0x10b8e: 82,\n    0x10b8f: 82,\n    0x10b90: 68,\n    0x10b91: 82,\n    0x10ba9: 82,\n    0x10baa: 82,\n    0x10bab: 82,\n    0x10bac: 82,\n    0x10bad: 68,\n    0x10bae: 68,\n    0x10baf: 85,\n    0x10d00: 76,\n    0x10d01: 68,\n    0x10d02: 68,\n    0x10d03: 68,\n    0x10d04: 68,\n    0x10d05: 68,\n    0x10d06: 68,\n    0x10d07: 68,\n    0x10d08: 68,\n    0x10d09: 68,\n    0x10d0a: 68,\n    0x10d0b: 68,\n    0x10d0c: 68,\n    0x10d0d: 68,\n    0x10d0e: 68,\n    0x10d0f: 68,\n    0x10d10: 68,\n    0x10d11: 68,\n    0x10d12: 68,\n    0x10d13: 68,\n    0x10d14: 68,\n    0x10d15: 68,\n    0x10d16: 68,\n    0x10d17: 68,\n    0x10d18: 68,\n    0x10d19: 68,\n    0x10d1a: 68,\n    0x10d1b: 68,\n    0x10d1c: 68,\n    0x10d1d: 68,\n    0x10d1e: 68,\n    0x10d1f: 68,\n    0x10d20: 68,\n    0x10d21: 68,\n    0x10d22: 82,\n    0x10d23: 68,\n    0x10f30: 68,\n    0x10f31: 68,\n    0x10f32: 68,\n    0x10f33: 82,\n    0x10f34: 68,\n    0x10f35: 68,\n    0x10f36: 68,\n    0x10f37: 68,\n    0x10f38: 68,\n    0x10f39: 68,\n    0x10f3a: 68,\n    0x10f3b: 68,\n    0x10f3c: 68,\n    0x10f3d: 68,\n    0x10f3e: 68,\n    0x10f3f: 68,\n    0x10f40: 68,\n    0x10f41: 68,\n    0x10f42: 68,\n    0x10f43: 68,\n    0x10f44: 68,\n    0x10f45: 85,\n    0x10f51: 68,\n    0x10f52: 68,\n    0x10f53: 68,\n    0x10f54: 82,\n    0x110bd: 85,\n    0x110cd: 85,\n    0x1e900: 68,\n    0x1e901: 68,\n    0x1e902: 68,\n    0x1e903: 68,\n    0x1e904: 68,\n    0x1e905: 68,\n    0x1e906: 68,\n    0x1e907: 68,\n    0x1e908: 68,\n    0x1e909: 68,\n    0x1e90a: 68,\n    0x1e90b: 68,\n    0x1e90c: 68,\n    0x1e90d: 68,\n    0x1e90e: 68,\n    0x1e90f: 68,\n    0x1e910: 68,\n    0x1e911: 68,\n    0x1e912: 68,\n    0x1e913: 68,\n    0x1e914: 68,\n    0x1e915: 68,\n    0x1e916: 68,\n    0x1e917: 68,\n    0x1e918: 68,\n    0x1e919: 68,\n    0x1e91a: 68,\n    0x1e91b: 68,\n    0x1e91c: 68,\n    0x1e91d: 68,\n    0x1e91e: 68,\n    0x1e91f: 68,\n    0x1e920: 68,\n    0x1e921: 68,\n    0x1e922: 68,\n    0x1e923: 68,\n    0x1e924: 68,\n    0x1e925: 68,\n    0x1e926: 68,\n    0x1e927: 68,\n    0x1e928: 68,\n    0x1e929: 68,\n    0x1e92a: 68,\n    0x1e92b: 68,\n    0x1e92c: 68,\n    0x1e92d: 68,\n    0x1e92e: 68,\n    0x1e92f: 68,\n    0x1e930: 68,\n    0x1e931: 68,\n    0x1e932: 68,\n    0x1e933: 68,\n    0x1e934: 68,\n    0x1e935: 68,\n    0x1e936: 68,\n    0x1e937: 68,\n    0x1e938: 68,\n    0x1e939: 68,\n    0x1e93a: 68,\n    0x1e93b: 68,\n    0x1e93c: 68,\n    0x1e93d: 68,\n    0x1e93e: 68,\n    0x1e93f: 68,\n    0x1e940: 68,\n    0x1e941: 68,\n    0x1e942: 68,\n    0x1e943: 68,\n}\ncodepoint_classes = {\n    'PVALID': (\n        0x2d0000002e,\n        0x300000003a,\n        0x610000007b,\n        0xdf000000f7,\n        0xf800000100,\n        0x10100000102,\n        0x10300000104,\n        0x10500000106,\n        0x10700000108,\n        0x1090000010a,\n        0x10b0000010c,\n        0x10d0000010e,\n        0x10f00000110,\n        0x11100000112,\n        0x11300000114,\n        0x11500000116,\n        0x11700000118,\n        0x1190000011a,\n        0x11b0000011c,\n        0x11d0000011e,\n        0x11f00000120,\n        0x12100000122,\n        0x12300000124,\n        0x12500000126,\n        0x12700000128,\n        0x1290000012a,\n        0x12b0000012c,\n        0x12d0000012e,\n        0x12f00000130,\n        0x13100000132,\n        0x13500000136,\n        0x13700000139,\n        0x13a0000013b,\n        0x13c0000013d,\n        0x13e0000013f,\n        0x14200000143,\n        0x14400000145,\n        0x14600000147,\n        0x14800000149,\n        0x14b0000014c,\n        0x14d0000014e,\n        0x14f00000150,\n        0x15100000152,\n        0x15300000154,\n        0x15500000156,\n        0x15700000158,\n        0x1590000015a,\n        0x15b0000015c,\n        0x15d0000015e,\n        0x15f00000160,\n        0x16100000162,\n        0x16300000164,\n        0x16500000166,\n        0x16700000168,\n        0x1690000016a,\n        0x16b0000016c,\n        0x16d0000016e,\n        0x16f00000170,\n        0x17100000172,\n        0x17300000174,\n        0x17500000176,\n        0x17700000178,\n        0x17a0000017b,\n        0x17c0000017d,\n        0x17e0000017f,\n        0x18000000181,\n        0x18300000184,\n        0x18500000186,\n        0x18800000189,\n        0x18c0000018e,\n        0x19200000193,\n        0x19500000196,\n        0x1990000019c,\n        0x19e0000019f,\n        0x1a1000001a2,\n        0x1a3000001a4,\n        0x1a5000001a6,\n        0x1a8000001a9,\n        0x1aa000001ac,\n        0x1ad000001ae,\n        0x1b0000001b1,\n        0x1b4000001b5,\n        0x1b6000001b7,\n        0x1b9000001bc,\n        0x1bd000001c4,\n        0x1ce000001cf,\n        0x1d0000001d1,\n        0x1d2000001d3,\n        0x1d4000001d5,\n        0x1d6000001d7,\n        0x1d8000001d9,\n        0x1da000001db,\n        0x1dc000001de,\n        0x1df000001e0,\n        0x1e1000001e2,\n        0x1e3000001e4,\n        0x1e5000001e6,\n        0x1e7000001e8,\n        0x1e9000001ea,\n        0x1eb000001ec,\n        0x1ed000001ee,\n        0x1ef000001f1,\n        0x1f5000001f6,\n        0x1f9000001fa,\n        0x1fb000001fc,\n        0x1fd000001fe,\n        0x1ff00000200,\n        0x20100000202,\n        0x20300000204,\n        0x20500000206,\n        0x20700000208,\n        0x2090000020a,\n        0x20b0000020c,\n        0x20d0000020e,\n        0x20f00000210,\n        0x21100000212,\n        0x21300000214,\n        0x21500000216,\n        0x21700000218,\n        0x2190000021a,\n        0x21b0000021c,\n        0x21d0000021e,\n        0x21f00000220,\n        0x22100000222,\n        0x22300000224,\n        0x22500000226,\n        0x22700000228,\n        0x2290000022a,\n        0x22b0000022c,\n        0x22d0000022e,\n        0x22f00000230,\n        0x23100000232,\n        0x2330000023a,\n        0x23c0000023d,\n        0x23f00000241,\n        0x24200000243,\n        0x24700000248,\n        0x2490000024a,\n        0x24b0000024c,\n        0x24d0000024e,\n        0x24f000002b0,\n        0x2b9000002c2,\n        0x2c6000002d2,\n        0x2ec000002ed,\n        0x2ee000002ef,\n        0x30000000340,\n        0x34200000343,\n        0x3460000034f,\n        0x35000000370,\n        0x37100000372,\n        0x37300000374,\n        0x37700000378,\n        0x37b0000037e,\n        0x39000000391,\n        0x3ac000003cf,\n        0x3d7000003d8,\n        0x3d9000003da,\n        0x3db000003dc,\n        0x3dd000003de,\n        0x3df000003e0,\n        0x3e1000003e2,\n        0x3e3000003e4,\n        0x3e5000003e6,\n        0x3e7000003e8,\n        0x3e9000003ea,\n        0x3eb000003ec,\n        0x3ed000003ee,\n        0x3ef000003f0,\n        0x3f3000003f4,\n        0x3f8000003f9,\n        0x3fb000003fd,\n        0x43000000460,\n        0x46100000462,\n        0x46300000464,\n        0x46500000466,\n        0x46700000468,\n        0x4690000046a,\n        0x46b0000046c,\n        0x46d0000046e,\n        0x46f00000470,\n        0x47100000472,\n        0x47300000474,\n        0x47500000476,\n        0x47700000478,\n        0x4790000047a,\n        0x47b0000047c,\n        0x47d0000047e,\n        0x47f00000480,\n        0x48100000482,\n        0x48300000488,\n        0x48b0000048c,\n        0x48d0000048e,\n        0x48f00000490,\n        0x49100000492,\n        0x49300000494,\n        0x49500000496,\n        0x49700000498,\n        0x4990000049a,\n        0x49b0000049c,\n        0x49d0000049e,\n        0x49f000004a0,\n        0x4a1000004a2,\n        0x4a3000004a4,\n        0x4a5000004a6,\n        0x4a7000004a8,\n        0x4a9000004aa,\n        0x4ab000004ac,\n        0x4ad000004ae,\n        0x4af000004b0,\n        0x4b1000004b2,\n        0x4b3000004b4,\n        0x4b5000004b6,\n        0x4b7000004b8,\n        0x4b9000004ba,\n        0x4bb000004bc,\n        0x4bd000004be,\n        0x4bf000004c0,\n        0x4c2000004c3,\n        0x4c4000004c5,\n        0x4c6000004c7,\n        0x4c8000004c9,\n        0x4ca000004cb,\n        0x4cc000004cd,\n        0x4ce000004d0,\n        0x4d1000004d2,\n        0x4d3000004d4,\n        0x4d5000004d6,\n        0x4d7000004d8,\n        0x4d9000004da,\n        0x4db000004dc,\n        0x4dd000004de,\n        0x4df000004e0,\n        0x4e1000004e2,\n        0x4e3000004e4,\n        0x4e5000004e6,\n        0x4e7000004e8,\n        0x4e9000004ea,\n        0x4eb000004ec,\n        0x4ed000004ee,\n        0x4ef000004f0,\n        0x4f1000004f2,\n        0x4f3000004f4,\n        0x4f5000004f6,\n        0x4f7000004f8,\n        0x4f9000004fa,\n        0x4fb000004fc,\n        0x4fd000004fe,\n        0x4ff00000500,\n        0x50100000502,\n        0x50300000504,\n        0x50500000506,\n        0x50700000508,\n        0x5090000050a,\n        0x50b0000050c,\n        0x50d0000050e,\n        0x50f00000510,\n        0x51100000512,\n        0x51300000514,\n        0x51500000516,\n        0x51700000518,\n        0x5190000051a,\n        0x51b0000051c,\n        0x51d0000051e,\n        0x51f00000520,\n        0x52100000522,\n        0x52300000524,\n        0x52500000526,\n        0x52700000528,\n        0x5290000052a,\n        0x52b0000052c,\n        0x52d0000052e,\n        0x52f00000530,\n        0x5590000055a,\n        0x56000000587,\n        0x58800000589,\n        0x591000005be,\n        0x5bf000005c0,\n        0x5c1000005c3,\n        0x5c4000005c6,\n        0x5c7000005c8,\n        0x5d0000005eb,\n        0x5ef000005f3,\n        0x6100000061b,\n        0x62000000640,\n        0x64100000660,\n        0x66e00000675,\n        0x679000006d4,\n        0x6d5000006dd,\n        0x6df000006e9,\n        0x6ea000006f0,\n        0x6fa00000700,\n        0x7100000074b,\n        0x74d000007b2,\n        0x7c0000007f6,\n        0x7fd000007fe,\n        0x8000000082e,\n        0x8400000085c,\n        0x8600000086b,\n        0x8a0000008b5,\n        0x8b6000008be,\n        0x8d3000008e2,\n        0x8e300000958,\n        0x96000000964,\n        0x96600000970,\n        0x97100000984,\n        0x9850000098d,\n        0x98f00000991,\n        0x993000009a9,\n        0x9aa000009b1,\n        0x9b2000009b3,\n        0x9b6000009ba,\n        0x9bc000009c5,\n        0x9c7000009c9,\n        0x9cb000009cf,\n        0x9d7000009d8,\n        0x9e0000009e4,\n        0x9e6000009f2,\n        0x9fc000009fd,\n        0x9fe000009ff,\n        0xa0100000a04,\n        0xa0500000a0b,\n        0xa0f00000a11,\n        0xa1300000a29,\n        0xa2a00000a31,\n        0xa3200000a33,\n        0xa3500000a36,\n        0xa3800000a3a,\n        0xa3c00000a3d,\n        0xa3e00000a43,\n        0xa4700000a49,\n        0xa4b00000a4e,\n        0xa5100000a52,\n        0xa5c00000a5d,\n        0xa6600000a76,\n        0xa8100000a84,\n        0xa8500000a8e,\n        0xa8f00000a92,\n        0xa9300000aa9,\n        0xaaa00000ab1,\n        0xab200000ab4,\n        0xab500000aba,\n        0xabc00000ac6,\n        0xac700000aca,\n        0xacb00000ace,\n        0xad000000ad1,\n        0xae000000ae4,\n        0xae600000af0,\n        0xaf900000b00,\n        0xb0100000b04,\n        0xb0500000b0d,\n        0xb0f00000b11,\n        0xb1300000b29,\n        0xb2a00000b31,\n        0xb3200000b34,\n        0xb3500000b3a,\n        0xb3c00000b45,\n        0xb4700000b49,\n        0xb4b00000b4e,\n        0xb5600000b58,\n        0xb5f00000b64,\n        0xb6600000b70,\n        0xb7100000b72,\n        0xb8200000b84,\n        0xb8500000b8b,\n        0xb8e00000b91,\n        0xb9200000b96,\n        0xb9900000b9b,\n        0xb9c00000b9d,\n        0xb9e00000ba0,\n        0xba300000ba5,\n        0xba800000bab,\n        0xbae00000bba,\n        0xbbe00000bc3,\n        0xbc600000bc9,\n        0xbca00000bce,\n        0xbd000000bd1,\n        0xbd700000bd8,\n        0xbe600000bf0,\n        0xc0000000c0d,\n        0xc0e00000c11,\n        0xc1200000c29,\n        0xc2a00000c3a,\n        0xc3d00000c45,\n        0xc4600000c49,\n        0xc4a00000c4e,\n        0xc5500000c57,\n        0xc5800000c5b,\n        0xc6000000c64,\n        0xc6600000c70,\n        0xc8000000c84,\n        0xc8500000c8d,\n        0xc8e00000c91,\n        0xc9200000ca9,\n        0xcaa00000cb4,\n        0xcb500000cba,\n        0xcbc00000cc5,\n        0xcc600000cc9,\n        0xcca00000cce,\n        0xcd500000cd7,\n        0xcde00000cdf,\n        0xce000000ce4,\n        0xce600000cf0,\n        0xcf100000cf3,\n        0xd0000000d04,\n        0xd0500000d0d,\n        0xd0e00000d11,\n        0xd1200000d45,\n        0xd4600000d49,\n        0xd4a00000d4f,\n        0xd5400000d58,\n        0xd5f00000d64,\n        0xd6600000d70,\n        0xd7a00000d80,\n        0xd8200000d84,\n        0xd8500000d97,\n        0xd9a00000db2,\n        0xdb300000dbc,\n        0xdbd00000dbe,\n        0xdc000000dc7,\n        0xdca00000dcb,\n        0xdcf00000dd5,\n        0xdd600000dd7,\n        0xdd800000de0,\n        0xde600000df0,\n        0xdf200000df4,\n        0xe0100000e33,\n        0xe3400000e3b,\n        0xe4000000e4f,\n        0xe5000000e5a,\n        0xe8100000e83,\n        0xe8400000e85,\n        0xe8700000e89,\n        0xe8a00000e8b,\n        0xe8d00000e8e,\n        0xe9400000e98,\n        0xe9900000ea0,\n        0xea100000ea4,\n        0xea500000ea6,\n        0xea700000ea8,\n        0xeaa00000eac,\n        0xead00000eb3,\n        0xeb400000eba,\n        0xebb00000ebe,\n        0xec000000ec5,\n        0xec600000ec7,\n        0xec800000ece,\n        0xed000000eda,\n        0xede00000ee0,\n        0xf0000000f01,\n        0xf0b00000f0c,\n        0xf1800000f1a,\n        0xf2000000f2a,\n        0xf3500000f36,\n        0xf3700000f38,\n        0xf3900000f3a,\n        0xf3e00000f43,\n        0xf4400000f48,\n        0xf4900000f4d,\n        0xf4e00000f52,\n        0xf5300000f57,\n        0xf5800000f5c,\n        0xf5d00000f69,\n        0xf6a00000f6d,\n        0xf7100000f73,\n        0xf7400000f75,\n        0xf7a00000f81,\n        0xf8200000f85,\n        0xf8600000f93,\n        0xf9400000f98,\n        0xf9900000f9d,\n        0xf9e00000fa2,\n        0xfa300000fa7,\n        0xfa800000fac,\n        0xfad00000fb9,\n        0xfba00000fbd,\n        0xfc600000fc7,\n        0x10000000104a,\n        0x10500000109e,\n        0x10d0000010fb,\n        0x10fd00001100,\n        0x120000001249,\n        0x124a0000124e,\n        0x125000001257,\n        0x125800001259,\n        0x125a0000125e,\n        0x126000001289,\n        0x128a0000128e,\n        0x1290000012b1,\n        0x12b2000012b6,\n        0x12b8000012bf,\n        0x12c0000012c1,\n        0x12c2000012c6,\n        0x12c8000012d7,\n        0x12d800001311,\n        0x131200001316,\n        0x13180000135b,\n        0x135d00001360,\n        0x138000001390,\n        0x13a0000013f6,\n        0x14010000166d,\n        0x166f00001680,\n        0x16810000169b,\n        0x16a0000016eb,\n        0x16f1000016f9,\n        0x17000000170d,\n        0x170e00001715,\n        0x172000001735,\n        0x174000001754,\n        0x17600000176d,\n        0x176e00001771,\n        0x177200001774,\n        0x1780000017b4,\n        0x17b6000017d4,\n        0x17d7000017d8,\n        0x17dc000017de,\n        0x17e0000017ea,\n        0x18100000181a,\n        0x182000001879,\n        0x1880000018ab,\n        0x18b0000018f6,\n        0x19000000191f,\n        0x19200000192c,\n        0x19300000193c,\n        0x19460000196e,\n        0x197000001975,\n        0x1980000019ac,\n        0x19b0000019ca,\n        0x19d0000019da,\n        0x1a0000001a1c,\n        0x1a2000001a5f,\n        0x1a6000001a7d,\n        0x1a7f00001a8a,\n        0x1a9000001a9a,\n        0x1aa700001aa8,\n        0x1ab000001abe,\n        0x1b0000001b4c,\n        0x1b5000001b5a,\n        0x1b6b00001b74,\n        0x1b8000001bf4,\n        0x1c0000001c38,\n        0x1c4000001c4a,\n        0x1c4d00001c7e,\n        0x1cd000001cd3,\n        0x1cd400001cfa,\n        0x1d0000001d2c,\n        0x1d2f00001d30,\n        0x1d3b00001d3c,\n        0x1d4e00001d4f,\n        0x1d6b00001d78,\n        0x1d7900001d9b,\n        0x1dc000001dfa,\n        0x1dfb00001e00,\n        0x1e0100001e02,\n        0x1e0300001e04,\n        0x1e0500001e06,\n        0x1e0700001e08,\n        0x1e0900001e0a,\n        0x1e0b00001e0c,\n        0x1e0d00001e0e,\n        0x1e0f00001e10,\n        0x1e1100001e12,\n        0x1e1300001e14,\n        0x1e1500001e16,\n        0x1e1700001e18,\n        0x1e1900001e1a,\n        0x1e1b00001e1c,\n        0x1e1d00001e1e,\n        0x1e1f00001e20,\n        0x1e2100001e22,\n        0x1e2300001e24,\n        0x1e2500001e26,\n        0x1e2700001e28,\n        0x1e2900001e2a,\n        0x1e2b00001e2c,\n        0x1e2d00001e2e,\n        0x1e2f00001e30,\n        0x1e3100001e32,\n        0x1e3300001e34,\n        0x1e3500001e36,\n        0x1e3700001e38,\n        0x1e3900001e3a,\n        0x1e3b00001e3c,\n        0x1e3d00001e3e,\n        0x1e3f00001e40,\n        0x1e4100001e42,\n        0x1e4300001e44,\n        0x1e4500001e46,\n        0x1e4700001e48,\n        0x1e4900001e4a,\n        0x1e4b00001e4c,\n        0x1e4d00001e4e,\n        0x1e4f00001e50,\n        0x1e5100001e52,\n        0x1e5300001e54,\n        0x1e5500001e56,\n        0x1e5700001e58,\n        0x1e5900001e5a,\n        0x1e5b00001e5c,\n        0x1e5d00001e5e,\n        0x1e5f00001e60,\n        0x1e6100001e62,\n        0x1e6300001e64,\n        0x1e6500001e66,\n        0x1e6700001e68,\n        0x1e6900001e6a,\n        0x1e6b00001e6c,\n        0x1e6d00001e6e,\n        0x1e6f00001e70,\n        0x1e7100001e72,\n        0x1e7300001e74,\n        0x1e7500001e76,\n        0x1e7700001e78,\n        0x1e7900001e7a,\n        0x1e7b00001e7c,\n        0x1e7d00001e7e,\n        0x1e7f00001e80,\n        0x1e8100001e82,\n        0x1e8300001e84,\n        0x1e8500001e86,\n        0x1e8700001e88,\n        0x1e8900001e8a,\n        0x1e8b00001e8c,\n        0x1e8d00001e8e,\n        0x1e8f00001e90,\n        0x1e9100001e92,\n        0x1e9300001e94,\n        0x1e9500001e9a,\n        0x1e9c00001e9e,\n        0x1e9f00001ea0,\n        0x1ea100001ea2,\n        0x1ea300001ea4,\n        0x1ea500001ea6,\n        0x1ea700001ea8,\n        0x1ea900001eaa,\n        0x1eab00001eac,\n        0x1ead00001eae,\n        0x1eaf00001eb0,\n        0x1eb100001eb2,\n        0x1eb300001eb4,\n        0x1eb500001eb6,\n        0x1eb700001eb8,\n        0x1eb900001eba,\n        0x1ebb00001ebc,\n        0x1ebd00001ebe,\n        0x1ebf00001ec0,\n        0x1ec100001ec2,\n        0x1ec300001ec4,\n        0x1ec500001ec6,\n        0x1ec700001ec8,\n        0x1ec900001eca,\n        0x1ecb00001ecc,\n        0x1ecd00001ece,\n        0x1ecf00001ed0,\n        0x1ed100001ed2,\n        0x1ed300001ed4,\n        0x1ed500001ed6,\n        0x1ed700001ed8,\n        0x1ed900001eda,\n        0x1edb00001edc,\n        0x1edd00001ede,\n        0x1edf00001ee0,\n        0x1ee100001ee2,\n        0x1ee300001ee4,\n        0x1ee500001ee6,\n        0x1ee700001ee8,\n        0x1ee900001eea,\n        0x1eeb00001eec,\n        0x1eed00001eee,\n        0x1eef00001ef0,\n        0x1ef100001ef2,\n        0x1ef300001ef4,\n        0x1ef500001ef6,\n        0x1ef700001ef8,\n        0x1ef900001efa,\n        0x1efb00001efc,\n        0x1efd00001efe,\n        0x1eff00001f08,\n        0x1f1000001f16,\n        0x1f2000001f28,\n        0x1f3000001f38,\n        0x1f4000001f46,\n        0x1f5000001f58,\n        0x1f6000001f68,\n        0x1f7000001f71,\n        0x1f7200001f73,\n        0x1f7400001f75,\n        0x1f7600001f77,\n        0x1f7800001f79,\n        0x1f7a00001f7b,\n        0x1f7c00001f7d,\n        0x1fb000001fb2,\n        0x1fb600001fb7,\n        0x1fc600001fc7,\n        0x1fd000001fd3,\n        0x1fd600001fd8,\n        0x1fe000001fe3,\n        0x1fe400001fe8,\n        0x1ff600001ff7,\n        0x214e0000214f,\n        0x218400002185,\n        0x2c3000002c5f,\n        0x2c6100002c62,\n        0x2c6500002c67,\n        0x2c6800002c69,\n        0x2c6a00002c6b,\n        0x2c6c00002c6d,\n        0x2c7100002c72,\n        0x2c7300002c75,\n        0x2c7600002c7c,\n        0x2c8100002c82,\n        0x2c8300002c84,\n        0x2c8500002c86,\n        0x2c8700002c88,\n        0x2c8900002c8a,\n        0x2c8b00002c8c,\n        0x2c8d00002c8e,\n        0x2c8f00002c90,\n        0x2c9100002c92,\n        0x2c9300002c94,\n        0x2c9500002c96,\n        0x2c9700002c98,\n        0x2c9900002c9a,\n        0x2c9b00002c9c,\n        0x2c9d00002c9e,\n        0x2c9f00002ca0,\n        0x2ca100002ca2,\n        0x2ca300002ca4,\n        0x2ca500002ca6,\n        0x2ca700002ca8,\n        0x2ca900002caa,\n        0x2cab00002cac,\n        0x2cad00002cae,\n        0x2caf00002cb0,\n        0x2cb100002cb2,\n        0x2cb300002cb4,\n        0x2cb500002cb6,\n        0x2cb700002cb8,\n        0x2cb900002cba,\n        0x2cbb00002cbc,\n        0x2cbd00002cbe,\n        0x2cbf00002cc0,\n        0x2cc100002cc2,\n        0x2cc300002cc4,\n        0x2cc500002cc6,\n        0x2cc700002cc8,\n        0x2cc900002cca,\n        0x2ccb00002ccc,\n        0x2ccd00002cce,\n        0x2ccf00002cd0,\n        0x2cd100002cd2,\n        0x2cd300002cd4,\n        0x2cd500002cd6,\n        0x2cd700002cd8,\n        0x2cd900002cda,\n        0x2cdb00002cdc,\n        0x2cdd00002cde,\n        0x2cdf00002ce0,\n        0x2ce100002ce2,\n        0x2ce300002ce5,\n        0x2cec00002ced,\n        0x2cee00002cf2,\n        0x2cf300002cf4,\n        0x2d0000002d26,\n        0x2d2700002d28,\n        0x2d2d00002d2e,\n        0x2d3000002d68,\n        0x2d7f00002d97,\n        0x2da000002da7,\n        0x2da800002daf,\n        0x2db000002db7,\n        0x2db800002dbf,\n        0x2dc000002dc7,\n        0x2dc800002dcf,\n        0x2dd000002dd7,\n        0x2dd800002ddf,\n        0x2de000002e00,\n        0x2e2f00002e30,\n        0x300500003008,\n        0x302a0000302e,\n        0x303c0000303d,\n        0x304100003097,\n        0x30990000309b,\n        0x309d0000309f,\n        0x30a1000030fb,\n        0x30fc000030ff,\n        0x310500003130,\n        0x31a0000031bb,\n        0x31f000003200,\n        0x340000004db6,\n        0x4e0000009ff0,\n        0xa0000000a48d,\n        0xa4d00000a4fe,\n        0xa5000000a60d,\n        0xa6100000a62c,\n        0xa6410000a642,\n        0xa6430000a644,\n        0xa6450000a646,\n        0xa6470000a648,\n        0xa6490000a64a,\n        0xa64b0000a64c,\n        0xa64d0000a64e,\n        0xa64f0000a650,\n        0xa6510000a652,\n        0xa6530000a654,\n        0xa6550000a656,\n        0xa6570000a658,\n        0xa6590000a65a,\n        0xa65b0000a65c,\n        0xa65d0000a65e,\n        0xa65f0000a660,\n        0xa6610000a662,\n        0xa6630000a664,\n        0xa6650000a666,\n        0xa6670000a668,\n        0xa6690000a66a,\n        0xa66b0000a66c,\n        0xa66d0000a670,\n        0xa6740000a67e,\n        0xa67f0000a680,\n        0xa6810000a682,\n        0xa6830000a684,\n        0xa6850000a686,\n        0xa6870000a688,\n        0xa6890000a68a,\n        0xa68b0000a68c,\n        0xa68d0000a68e,\n        0xa68f0000a690,\n        0xa6910000a692,\n        0xa6930000a694,\n        0xa6950000a696,\n        0xa6970000a698,\n        0xa6990000a69a,\n        0xa69b0000a69c,\n        0xa69e0000a6e6,\n        0xa6f00000a6f2,\n        0xa7170000a720,\n        0xa7230000a724,\n        0xa7250000a726,\n        0xa7270000a728,\n        0xa7290000a72a,\n        0xa72b0000a72c,\n        0xa72d0000a72e,\n        0xa72f0000a732,\n        0xa7330000a734,\n        0xa7350000a736,\n        0xa7370000a738,\n        0xa7390000a73a,\n        0xa73b0000a73c,\n        0xa73d0000a73e,\n        0xa73f0000a740,\n        0xa7410000a742,\n        0xa7430000a744,\n        0xa7450000a746,\n        0xa7470000a748,\n        0xa7490000a74a,\n        0xa74b0000a74c,\n        0xa74d0000a74e,\n        0xa74f0000a750,\n        0xa7510000a752,\n        0xa7530000a754,\n        0xa7550000a756,\n        0xa7570000a758,\n        0xa7590000a75a,\n        0xa75b0000a75c,\n        0xa75d0000a75e,\n        0xa75f0000a760,\n        0xa7610000a762,\n        0xa7630000a764,\n        0xa7650000a766,\n        0xa7670000a768,\n        0xa7690000a76a,\n        0xa76b0000a76c,\n        0xa76d0000a76e,\n        0xa76f0000a770,\n        0xa7710000a779,\n        0xa77a0000a77b,\n        0xa77c0000a77d,\n        0xa77f0000a780,\n        0xa7810000a782,\n        0xa7830000a784,\n        0xa7850000a786,\n        0xa7870000a789,\n        0xa78c0000a78d,\n        0xa78e0000a790,\n        0xa7910000a792,\n        0xa7930000a796,\n        0xa7970000a798,\n        0xa7990000a79a,\n        0xa79b0000a79c,\n        0xa79d0000a79e,\n        0xa79f0000a7a0,\n        0xa7a10000a7a2,\n        0xa7a30000a7a4,\n        0xa7a50000a7a6,\n        0xa7a70000a7a8,\n        0xa7a90000a7aa,\n        0xa7af0000a7b0,\n        0xa7b50000a7b6,\n        0xa7b70000a7b8,\n        0xa7b90000a7ba,\n        0xa7f70000a7f8,\n        0xa7fa0000a828,\n        0xa8400000a874,\n        0xa8800000a8c6,\n        0xa8d00000a8da,\n        0xa8e00000a8f8,\n        0xa8fb0000a8fc,\n        0xa8fd0000a92e,\n        0xa9300000a954,\n        0xa9800000a9c1,\n        0xa9cf0000a9da,\n        0xa9e00000a9ff,\n        0xaa000000aa37,\n        0xaa400000aa4e,\n        0xaa500000aa5a,\n        0xaa600000aa77,\n        0xaa7a0000aac3,\n        0xaadb0000aade,\n        0xaae00000aaf0,\n        0xaaf20000aaf7,\n        0xab010000ab07,\n        0xab090000ab0f,\n        0xab110000ab17,\n        0xab200000ab27,\n        0xab280000ab2f,\n        0xab300000ab5b,\n        0xab600000ab66,\n        0xabc00000abeb,\n        0xabec0000abee,\n        0xabf00000abfa,\n        0xac000000d7a4,\n        0xfa0e0000fa10,\n        0xfa110000fa12,\n        0xfa130000fa15,\n        0xfa1f0000fa20,\n        0xfa210000fa22,\n        0xfa230000fa25,\n        0xfa270000fa2a,\n        0xfb1e0000fb1f,\n        0xfe200000fe30,\n        0xfe730000fe74,\n        0x100000001000c,\n        0x1000d00010027,\n        0x100280001003b,\n        0x1003c0001003e,\n        0x1003f0001004e,\n        0x100500001005e,\n        0x10080000100fb,\n        0x101fd000101fe,\n        0x102800001029d,\n        0x102a0000102d1,\n        0x102e0000102e1,\n        0x1030000010320,\n        0x1032d00010341,\n        0x103420001034a,\n        0x103500001037b,\n        0x103800001039e,\n        0x103a0000103c4,\n        0x103c8000103d0,\n        0x104280001049e,\n        0x104a0000104aa,\n        0x104d8000104fc,\n        0x1050000010528,\n        0x1053000010564,\n        0x1060000010737,\n        0x1074000010756,\n        0x1076000010768,\n        0x1080000010806,\n        0x1080800010809,\n        0x1080a00010836,\n        0x1083700010839,\n        0x1083c0001083d,\n        0x1083f00010856,\n        0x1086000010877,\n        0x108800001089f,\n        0x108e0000108f3,\n        0x108f4000108f6,\n        0x1090000010916,\n        0x109200001093a,\n        0x10980000109b8,\n        0x109be000109c0,\n        0x10a0000010a04,\n        0x10a0500010a07,\n        0x10a0c00010a14,\n        0x10a1500010a18,\n        0x10a1900010a36,\n        0x10a3800010a3b,\n        0x10a3f00010a40,\n        0x10a6000010a7d,\n        0x10a8000010a9d,\n        0x10ac000010ac8,\n        0x10ac900010ae7,\n        0x10b0000010b36,\n        0x10b4000010b56,\n        0x10b6000010b73,\n        0x10b8000010b92,\n        0x10c0000010c49,\n        0x10cc000010cf3,\n        0x10d0000010d28,\n        0x10d3000010d3a,\n        0x10f0000010f1d,\n        0x10f2700010f28,\n        0x10f3000010f51,\n        0x1100000011047,\n        0x1106600011070,\n        0x1107f000110bb,\n        0x110d0000110e9,\n        0x110f0000110fa,\n        0x1110000011135,\n        0x1113600011140,\n        0x1114400011147,\n        0x1115000011174,\n        0x1117600011177,\n        0x11180000111c5,\n        0x111c9000111cd,\n        0x111d0000111db,\n        0x111dc000111dd,\n        0x1120000011212,\n        0x1121300011238,\n        0x1123e0001123f,\n        0x1128000011287,\n        0x1128800011289,\n        0x1128a0001128e,\n        0x1128f0001129e,\n        0x1129f000112a9,\n        0x112b0000112eb,\n        0x112f0000112fa,\n        0x1130000011304,\n        0x113050001130d,\n        0x1130f00011311,\n        0x1131300011329,\n        0x1132a00011331,\n        0x1133200011334,\n        0x113350001133a,\n        0x1133b00011345,\n        0x1134700011349,\n        0x1134b0001134e,\n        0x1135000011351,\n        0x1135700011358,\n        0x1135d00011364,\n        0x113660001136d,\n        0x1137000011375,\n        0x114000001144b,\n        0x114500001145a,\n        0x1145e0001145f,\n        0x11480000114c6,\n        0x114c7000114c8,\n        0x114d0000114da,\n        0x11580000115b6,\n        0x115b8000115c1,\n        0x115d8000115de,\n        0x1160000011641,\n        0x1164400011645,\n        0x116500001165a,\n        0x11680000116b8,\n        0x116c0000116ca,\n        0x117000001171b,\n        0x1171d0001172c,\n        0x117300001173a,\n        0x118000001183b,\n        0x118c0000118ea,\n        0x118ff00011900,\n        0x11a0000011a3f,\n        0x11a4700011a48,\n        0x11a5000011a84,\n        0x11a8600011a9a,\n        0x11a9d00011a9e,\n        0x11ac000011af9,\n        0x11c0000011c09,\n        0x11c0a00011c37,\n        0x11c3800011c41,\n        0x11c5000011c5a,\n        0x11c7200011c90,\n        0x11c9200011ca8,\n        0x11ca900011cb7,\n        0x11d0000011d07,\n        0x11d0800011d0a,\n        0x11d0b00011d37,\n        0x11d3a00011d3b,\n        0x11d3c00011d3e,\n        0x11d3f00011d48,\n        0x11d5000011d5a,\n        0x11d6000011d66,\n        0x11d6700011d69,\n        0x11d6a00011d8f,\n        0x11d9000011d92,\n        0x11d9300011d99,\n        0x11da000011daa,\n        0x11ee000011ef7,\n        0x120000001239a,\n        0x1248000012544,\n        0x130000001342f,\n        0x1440000014647,\n        0x1680000016a39,\n        0x16a4000016a5f,\n        0x16a6000016a6a,\n        0x16ad000016aee,\n        0x16af000016af5,\n        0x16b0000016b37,\n        0x16b4000016b44,\n        0x16b5000016b5a,\n        0x16b6300016b78,\n        0x16b7d00016b90,\n        0x16e6000016e80,\n        0x16f0000016f45,\n        0x16f5000016f7f,\n        0x16f8f00016fa0,\n        0x16fe000016fe2,\n        0x17000000187f2,\n        0x1880000018af3,\n        0x1b0000001b11f,\n        0x1b1700001b2fc,\n        0x1bc000001bc6b,\n        0x1bc700001bc7d,\n        0x1bc800001bc89,\n        0x1bc900001bc9a,\n        0x1bc9d0001bc9f,\n        0x1da000001da37,\n        0x1da3b0001da6d,\n        0x1da750001da76,\n        0x1da840001da85,\n        0x1da9b0001daa0,\n        0x1daa10001dab0,\n        0x1e0000001e007,\n        0x1e0080001e019,\n        0x1e01b0001e022,\n        0x1e0230001e025,\n        0x1e0260001e02b,\n        0x1e8000001e8c5,\n        0x1e8d00001e8d7,\n        0x1e9220001e94b,\n        0x1e9500001e95a,\n        0x200000002a6d7,\n        0x2a7000002b735,\n        0x2b7400002b81e,\n        0x2b8200002cea2,\n        0x2ceb00002ebe1,\n    ),\n    'CONTEXTJ': (\n        0x200c0000200e,\n    ),\n    'CONTEXTO': (\n        0xb7000000b8,\n        0x37500000376,\n        0x5f3000005f5,\n        0x6600000066a,\n        0x6f0000006fa,\n        0x30fb000030fc,\n    ),\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/idna/intranges.py",
    "content": "\"\"\"\nGiven a list of integers, made up of (hopefully) a small number of long runs\nof consecutive integers, compute a representation of the form\n((start1, end1), (start2, end2) ...). Then answer the question \"was x present\nin the original list?\" in time O(log(# runs)).\n\"\"\"\n\nimport bisect\n\ndef intranges_from_list(list_):\n    \"\"\"Represent a list of integers as a sequence of ranges:\n    ((start_0, end_0), (start_1, end_1), ...), such that the original\n    integers are exactly those x such that start_i <= x < end_i for some i.\n\n    Ranges are encoded as single integers (start << 32 | end), not as tuples.\n    \"\"\"\n\n    sorted_list = sorted(list_)\n    ranges = []\n    last_write = -1\n    for i in range(len(sorted_list)):\n        if i+1 < len(sorted_list):\n            if sorted_list[i] == sorted_list[i+1]-1:\n                continue\n        current_range = sorted_list[last_write+1:i+1]\n        ranges.append(_encode_range(current_range[0], current_range[-1] + 1))\n        last_write = i\n\n    return tuple(ranges)\n\ndef _encode_range(start, end):\n    return (start << 32) | end\n\ndef _decode_range(r):\n    return (r >> 32), (r & ((1 << 32) - 1))\n\n\ndef intranges_contain(int_, ranges):\n    \"\"\"Determine if `int_` falls into one of the ranges in `ranges`.\"\"\"\n    tuple_ = _encode_range(int_, 0)\n    pos = bisect.bisect_left(ranges, tuple_)\n    # we could be immediately ahead of a tuple (start, end)\n    # with start < int_ <= end\n    if pos > 0:\n        left, right = _decode_range(ranges[pos-1])\n        if left <= int_ < right:\n            return True\n    # or we could be immediately behind a tuple (int_, end)\n    if pos < len(ranges):\n        left, _ = _decode_range(ranges[pos])\n        if left == int_:\n            return True\n    return False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/idna/package_data.py",
    "content": "__version__ = '2.8'\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/idna/uts46data.py",
    "content": "# This file is automatically generated by tools/idna-data\n# vim: set fileencoding=utf-8 :\n\n\"\"\"IDNA Mapping Table from UTS46.\"\"\"\n\n\n__version__ = \"11.0.0\"\ndef _seg_0():\n    return [\n    (0x0, '3'),\n    (0x1, '3'),\n    (0x2, '3'),\n    (0x3, '3'),\n    (0x4, '3'),\n    (0x5, '3'),\n    (0x6, '3'),\n    (0x7, '3'),\n    (0x8, '3'),\n    (0x9, '3'),\n    (0xA, '3'),\n    (0xB, '3'),\n    (0xC, '3'),\n    (0xD, '3'),\n    (0xE, '3'),\n    (0xF, '3'),\n    (0x10, '3'),\n    (0x11, '3'),\n    (0x12, '3'),\n    (0x13, '3'),\n    (0x14, '3'),\n    (0x15, '3'),\n    (0x16, '3'),\n    (0x17, '3'),\n    (0x18, '3'),\n    (0x19, '3'),\n    (0x1A, '3'),\n    (0x1B, '3'),\n    (0x1C, '3'),\n    (0x1D, '3'),\n    (0x1E, '3'),\n    (0x1F, '3'),\n    (0x20, '3'),\n    (0x21, '3'),\n    (0x22, '3'),\n    (0x23, '3'),\n    (0x24, '3'),\n    (0x25, '3'),\n    (0x26, '3'),\n    (0x27, '3'),\n    (0x28, '3'),\n    (0x29, '3'),\n    (0x2A, '3'),\n    (0x2B, '3'),\n    (0x2C, '3'),\n    (0x2D, 'V'),\n    (0x2E, 'V'),\n    (0x2F, '3'),\n    (0x30, 'V'),\n    (0x31, 'V'),\n    (0x32, 'V'),\n    (0x33, 'V'),\n    (0x34, 'V'),\n    (0x35, 'V'),\n    (0x36, 'V'),\n    (0x37, 'V'),\n    (0x38, 'V'),\n    (0x39, 'V'),\n    (0x3A, '3'),\n    (0x3B, '3'),\n    (0x3C, '3'),\n    (0x3D, '3'),\n    (0x3E, '3'),\n    (0x3F, '3'),\n    (0x40, '3'),\n    (0x41, 'M', u'a'),\n    (0x42, 'M', u'b'),\n    (0x43, 'M', u'c'),\n    (0x44, 'M', u'd'),\n    (0x45, 'M', u'e'),\n    (0x46, 'M', u'f'),\n    (0x47, 'M', u'g'),\n    (0x48, 'M', u'h'),\n    (0x49, 'M', u'i'),\n    (0x4A, 'M', u'j'),\n    (0x4B, 'M', u'k'),\n    (0x4C, 'M', u'l'),\n    (0x4D, 'M', u'm'),\n    (0x4E, 'M', u'n'),\n    (0x4F, 'M', u'o'),\n    (0x50, 'M', u'p'),\n    (0x51, 'M', u'q'),\n    (0x52, 'M', u'r'),\n    (0x53, 'M', u's'),\n    (0x54, 'M', u't'),\n    (0x55, 'M', u'u'),\n    (0x56, 'M', u'v'),\n    (0x57, 'M', u'w'),\n    (0x58, 'M', u'x'),\n    (0x59, 'M', u'y'),\n    (0x5A, 'M', u'z'),\n    (0x5B, '3'),\n    (0x5C, '3'),\n    (0x5D, '3'),\n    (0x5E, '3'),\n    (0x5F, '3'),\n    (0x60, '3'),\n    (0x61, 'V'),\n    (0x62, 'V'),\n    (0x63, 'V'),\n    ]\n\ndef _seg_1():\n    return [\n    (0x64, 'V'),\n    (0x65, 'V'),\n    (0x66, 'V'),\n    (0x67, 'V'),\n    (0x68, 'V'),\n    (0x69, 'V'),\n    (0x6A, 'V'),\n    (0x6B, 'V'),\n    (0x6C, 'V'),\n    (0x6D, 'V'),\n    (0x6E, 'V'),\n    (0x6F, 'V'),\n    (0x70, 'V'),\n    (0x71, 'V'),\n    (0x72, 'V'),\n    (0x73, 'V'),\n    (0x74, 'V'),\n    (0x75, 'V'),\n    (0x76, 'V'),\n    (0x77, 'V'),\n    (0x78, 'V'),\n    (0x79, 'V'),\n    (0x7A, 'V'),\n    (0x7B, '3'),\n    (0x7C, '3'),\n    (0x7D, '3'),\n    (0x7E, '3'),\n    (0x7F, '3'),\n    (0x80, 'X'),\n    (0x81, 'X'),\n    (0x82, 'X'),\n    (0x83, 'X'),\n    (0x84, 'X'),\n    (0x85, 'X'),\n    (0x86, 'X'),\n    (0x87, 'X'),\n    (0x88, 'X'),\n    (0x89, 'X'),\n    (0x8A, 'X'),\n    (0x8B, 'X'),\n    (0x8C, 'X'),\n    (0x8D, 'X'),\n    (0x8E, 'X'),\n    (0x8F, 'X'),\n    (0x90, 'X'),\n    (0x91, 'X'),\n    (0x92, 'X'),\n    (0x93, 'X'),\n    (0x94, 'X'),\n    (0x95, 'X'),\n    (0x96, 'X'),\n    (0x97, 'X'),\n    (0x98, 'X'),\n    (0x99, 'X'),\n    (0x9A, 'X'),\n    (0x9B, 'X'),\n    (0x9C, 'X'),\n    (0x9D, 'X'),\n    (0x9E, 'X'),\n    (0x9F, 'X'),\n    (0xA0, '3', u' '),\n    (0xA1, 'V'),\n    (0xA2, 'V'),\n    (0xA3, 'V'),\n    (0xA4, 'V'),\n    (0xA5, 'V'),\n    (0xA6, 'V'),\n    (0xA7, 'V'),\n    (0xA8, '3', u' ̈'),\n    (0xA9, 'V'),\n    (0xAA, 'M', u'a'),\n    (0xAB, 'V'),\n    (0xAC, 'V'),\n    (0xAD, 'I'),\n    (0xAE, 'V'),\n    (0xAF, '3', u' ̄'),\n    (0xB0, 'V'),\n    (0xB1, 'V'),\n    (0xB2, 'M', u'2'),\n    (0xB3, 'M', u'3'),\n    (0xB4, '3', u' ́'),\n    (0xB5, 'M', u'μ'),\n    (0xB6, 'V'),\n    (0xB7, 'V'),\n    (0xB8, '3', u' ̧'),\n    (0xB9, 'M', u'1'),\n    (0xBA, 'M', u'o'),\n    (0xBB, 'V'),\n    (0xBC, 'M', u'1⁄4'),\n    (0xBD, 'M', u'1⁄2'),\n    (0xBE, 'M', u'3⁄4'),\n    (0xBF, 'V'),\n    (0xC0, 'M', u'à'),\n    (0xC1, 'M', u'á'),\n    (0xC2, 'M', u'â'),\n    (0xC3, 'M', u'ã'),\n    (0xC4, 'M', u'ä'),\n    (0xC5, 'M', u'å'),\n    (0xC6, 'M', u'æ'),\n    (0xC7, 'M', u'ç'),\n    ]\n\ndef _seg_2():\n    return [\n    (0xC8, 'M', u'è'),\n    (0xC9, 'M', u'é'),\n    (0xCA, 'M', u'ê'),\n    (0xCB, 'M', u'ë'),\n    (0xCC, 'M', u'ì'),\n    (0xCD, 'M', u'í'),\n    (0xCE, 'M', u'î'),\n    (0xCF, 'M', u'ï'),\n    (0xD0, 'M', u'ð'),\n    (0xD1, 'M', u'ñ'),\n    (0xD2, 'M', u'ò'),\n    (0xD3, 'M', u'ó'),\n    (0xD4, 'M', u'ô'),\n    (0xD5, 'M', u'õ'),\n    (0xD6, 'M', u'ö'),\n    (0xD7, 'V'),\n    (0xD8, 'M', u'ø'),\n    (0xD9, 'M', u'ù'),\n    (0xDA, 'M', u'ú'),\n    (0xDB, 'M', u'û'),\n    (0xDC, 'M', u'ü'),\n    (0xDD, 'M', u'ý'),\n    (0xDE, 'M', u'þ'),\n    (0xDF, 'D', u'ss'),\n    (0xE0, 'V'),\n    (0xE1, 'V'),\n    (0xE2, 'V'),\n    (0xE3, 'V'),\n    (0xE4, 'V'),\n    (0xE5, 'V'),\n    (0xE6, 'V'),\n    (0xE7, 'V'),\n    (0xE8, 'V'),\n    (0xE9, 'V'),\n    (0xEA, 'V'),\n    (0xEB, 'V'),\n    (0xEC, 'V'),\n    (0xED, 'V'),\n    (0xEE, 'V'),\n    (0xEF, 'V'),\n    (0xF0, 'V'),\n    (0xF1, 'V'),\n    (0xF2, 'V'),\n    (0xF3, 'V'),\n    (0xF4, 'V'),\n    (0xF5, 'V'),\n    (0xF6, 'V'),\n    (0xF7, 'V'),\n    (0xF8, 'V'),\n    (0xF9, 'V'),\n    (0xFA, 'V'),\n    (0xFB, 'V'),\n    (0xFC, 'V'),\n    (0xFD, 'V'),\n    (0xFE, 'V'),\n    (0xFF, 'V'),\n    (0x100, 'M', u'ā'),\n    (0x101, 'V'),\n    (0x102, 'M', u'ă'),\n    (0x103, 'V'),\n    (0x104, 'M', u'ą'),\n    (0x105, 'V'),\n    (0x106, 'M', u'ć'),\n    (0x107, 'V'),\n    (0x108, 'M', u'ĉ'),\n    (0x109, 'V'),\n    (0x10A, 'M', u'ċ'),\n    (0x10B, 'V'),\n    (0x10C, 'M', u'č'),\n    (0x10D, 'V'),\n    (0x10E, 'M', u'ď'),\n    (0x10F, 'V'),\n    (0x110, 'M', u'đ'),\n    (0x111, 'V'),\n    (0x112, 'M', u'ē'),\n    (0x113, 'V'),\n    (0x114, 'M', u'ĕ'),\n    (0x115, 'V'),\n    (0x116, 'M', u'ė'),\n    (0x117, 'V'),\n    (0x118, 'M', u'ę'),\n    (0x119, 'V'),\n    (0x11A, 'M', u'ě'),\n    (0x11B, 'V'),\n    (0x11C, 'M', u'ĝ'),\n    (0x11D, 'V'),\n    (0x11E, 'M', u'ğ'),\n    (0x11F, 'V'),\n    (0x120, 'M', u'ġ'),\n    (0x121, 'V'),\n    (0x122, 'M', u'ģ'),\n    (0x123, 'V'),\n    (0x124, 'M', u'ĥ'),\n    (0x125, 'V'),\n    (0x126, 'M', u'ħ'),\n    (0x127, 'V'),\n    (0x128, 'M', u'ĩ'),\n    (0x129, 'V'),\n    (0x12A, 'M', u'ī'),\n    (0x12B, 'V'),\n    ]\n\ndef _seg_3():\n    return [\n    (0x12C, 'M', u'ĭ'),\n    (0x12D, 'V'),\n    (0x12E, 'M', u'į'),\n    (0x12F, 'V'),\n    (0x130, 'M', u'i̇'),\n    (0x131, 'V'),\n    (0x132, 'M', u'ij'),\n    (0x134, 'M', u'ĵ'),\n    (0x135, 'V'),\n    (0x136, 'M', u'ķ'),\n    (0x137, 'V'),\n    (0x139, 'M', u'ĺ'),\n    (0x13A, 'V'),\n    (0x13B, 'M', u'ļ'),\n    (0x13C, 'V'),\n    (0x13D, 'M', u'ľ'),\n    (0x13E, 'V'),\n    (0x13F, 'M', u'l·'),\n    (0x141, 'M', u'ł'),\n    (0x142, 'V'),\n    (0x143, 'M', u'ń'),\n    (0x144, 'V'),\n    (0x145, 'M', u'ņ'),\n    (0x146, 'V'),\n    (0x147, 'M', u'ň'),\n    (0x148, 'V'),\n    (0x149, 'M', u'ʼn'),\n    (0x14A, 'M', u'ŋ'),\n    (0x14B, 'V'),\n    (0x14C, 'M', u'ō'),\n    (0x14D, 'V'),\n    (0x14E, 'M', u'ŏ'),\n    (0x14F, 'V'),\n    (0x150, 'M', u'ő'),\n    (0x151, 'V'),\n    (0x152, 'M', u'œ'),\n    (0x153, 'V'),\n    (0x154, 'M', u'ŕ'),\n    (0x155, 'V'),\n    (0x156, 'M', u'ŗ'),\n    (0x157, 'V'),\n    (0x158, 'M', u'ř'),\n    (0x159, 'V'),\n    (0x15A, 'M', u'ś'),\n    (0x15B, 'V'),\n    (0x15C, 'M', u'ŝ'),\n    (0x15D, 'V'),\n    (0x15E, 'M', u'ş'),\n    (0x15F, 'V'),\n    (0x160, 'M', u'š'),\n    (0x161, 'V'),\n    (0x162, 'M', u'ţ'),\n    (0x163, 'V'),\n    (0x164, 'M', u'ť'),\n    (0x165, 'V'),\n    (0x166, 'M', u'ŧ'),\n    (0x167, 'V'),\n    (0x168, 'M', u'ũ'),\n    (0x169, 'V'),\n    (0x16A, 'M', u'ū'),\n    (0x16B, 'V'),\n    (0x16C, 'M', u'ŭ'),\n    (0x16D, 'V'),\n    (0x16E, 'M', u'ů'),\n    (0x16F, 'V'),\n    (0x170, 'M', u'ű'),\n    (0x171, 'V'),\n    (0x172, 'M', u'ų'),\n    (0x173, 'V'),\n    (0x174, 'M', u'ŵ'),\n    (0x175, 'V'),\n    (0x176, 'M', u'ŷ'),\n    (0x177, 'V'),\n    (0x178, 'M', u'ÿ'),\n    (0x179, 'M', u'ź'),\n    (0x17A, 'V'),\n    (0x17B, 'M', u'ż'),\n    (0x17C, 'V'),\n    (0x17D, 'M', u'ž'),\n    (0x17E, 'V'),\n    (0x17F, 'M', u's'),\n    (0x180, 'V'),\n    (0x181, 'M', u'ɓ'),\n    (0x182, 'M', u'ƃ'),\n    (0x183, 'V'),\n    (0x184, 'M', u'ƅ'),\n    (0x185, 'V'),\n    (0x186, 'M', u'ɔ'),\n    (0x187, 'M', u'ƈ'),\n    (0x188, 'V'),\n    (0x189, 'M', u'ɖ'),\n    (0x18A, 'M', u'ɗ'),\n    (0x18B, 'M', u'ƌ'),\n    (0x18C, 'V'),\n    (0x18E, 'M', u'ǝ'),\n    (0x18F, 'M', u'ə'),\n    (0x190, 'M', u'ɛ'),\n    (0x191, 'M', u'ƒ'),\n    (0x192, 'V'),\n    (0x193, 'M', u'ɠ'),\n    ]\n\ndef _seg_4():\n    return [\n    (0x194, 'M', u'ɣ'),\n    (0x195, 'V'),\n    (0x196, 'M', u'ɩ'),\n    (0x197, 'M', u'ɨ'),\n    (0x198, 'M', u'ƙ'),\n    (0x199, 'V'),\n    (0x19C, 'M', u'ɯ'),\n    (0x19D, 'M', u'ɲ'),\n    (0x19E, 'V'),\n    (0x19F, 'M', u'ɵ'),\n    (0x1A0, 'M', u'ơ'),\n    (0x1A1, 'V'),\n    (0x1A2, 'M', u'ƣ'),\n    (0x1A3, 'V'),\n    (0x1A4, 'M', u'ƥ'),\n    (0x1A5, 'V'),\n    (0x1A6, 'M', u'ʀ'),\n    (0x1A7, 'M', u'ƨ'),\n    (0x1A8, 'V'),\n    (0x1A9, 'M', u'ʃ'),\n    (0x1AA, 'V'),\n    (0x1AC, 'M', u'ƭ'),\n    (0x1AD, 'V'),\n    (0x1AE, 'M', u'ʈ'),\n    (0x1AF, 'M', u'ư'),\n    (0x1B0, 'V'),\n    (0x1B1, 'M', u'ʊ'),\n    (0x1B2, 'M', u'ʋ'),\n    (0x1B3, 'M', u'ƴ'),\n    (0x1B4, 'V'),\n    (0x1B5, 'M', u'ƶ'),\n    (0x1B6, 'V'),\n    (0x1B7, 'M', u'ʒ'),\n    (0x1B8, 'M', u'ƹ'),\n    (0x1B9, 'V'),\n    (0x1BC, 'M', u'ƽ'),\n    (0x1BD, 'V'),\n    (0x1C4, 'M', u'dž'),\n    (0x1C7, 'M', u'lj'),\n    (0x1CA, 'M', u'nj'),\n    (0x1CD, 'M', u'ǎ'),\n    (0x1CE, 'V'),\n    (0x1CF, 'M', u'ǐ'),\n    (0x1D0, 'V'),\n    (0x1D1, 'M', u'ǒ'),\n    (0x1D2, 'V'),\n    (0x1D3, 'M', u'ǔ'),\n    (0x1D4, 'V'),\n    (0x1D5, 'M', u'ǖ'),\n    (0x1D6, 'V'),\n    (0x1D7, 'M', u'ǘ'),\n    (0x1D8, 'V'),\n    (0x1D9, 'M', u'ǚ'),\n    (0x1DA, 'V'),\n    (0x1DB, 'M', u'ǜ'),\n    (0x1DC, 'V'),\n    (0x1DE, 'M', u'ǟ'),\n    (0x1DF, 'V'),\n    (0x1E0, 'M', u'ǡ'),\n    (0x1E1, 'V'),\n    (0x1E2, 'M', u'ǣ'),\n    (0x1E3, 'V'),\n    (0x1E4, 'M', u'ǥ'),\n    (0x1E5, 'V'),\n    (0x1E6, 'M', u'ǧ'),\n    (0x1E7, 'V'),\n    (0x1E8, 'M', u'ǩ'),\n    (0x1E9, 'V'),\n    (0x1EA, 'M', u'ǫ'),\n    (0x1EB, 'V'),\n    (0x1EC, 'M', u'ǭ'),\n    (0x1ED, 'V'),\n    (0x1EE, 'M', u'ǯ'),\n    (0x1EF, 'V'),\n    (0x1F1, 'M', u'dz'),\n    (0x1F4, 'M', u'ǵ'),\n    (0x1F5, 'V'),\n    (0x1F6, 'M', u'ƕ'),\n    (0x1F7, 'M', u'ƿ'),\n    (0x1F8, 'M', u'ǹ'),\n    (0x1F9, 'V'),\n    (0x1FA, 'M', u'ǻ'),\n    (0x1FB, 'V'),\n    (0x1FC, 'M', u'ǽ'),\n    (0x1FD, 'V'),\n    (0x1FE, 'M', u'ǿ'),\n    (0x1FF, 'V'),\n    (0x200, 'M', u'ȁ'),\n    (0x201, 'V'),\n    (0x202, 'M', u'ȃ'),\n    (0x203, 'V'),\n    (0x204, 'M', u'ȅ'),\n    (0x205, 'V'),\n    (0x206, 'M', u'ȇ'),\n    (0x207, 'V'),\n    (0x208, 'M', u'ȉ'),\n    (0x209, 'V'),\n    (0x20A, 'M', u'ȋ'),\n    (0x20B, 'V'),\n    (0x20C, 'M', u'ȍ'),\n    ]\n\ndef _seg_5():\n    return [\n    (0x20D, 'V'),\n    (0x20E, 'M', u'ȏ'),\n    (0x20F, 'V'),\n    (0x210, 'M', u'ȑ'),\n    (0x211, 'V'),\n    (0x212, 'M', u'ȓ'),\n    (0x213, 'V'),\n    (0x214, 'M', u'ȕ'),\n    (0x215, 'V'),\n    (0x216, 'M', u'ȗ'),\n    (0x217, 'V'),\n    (0x218, 'M', u'ș'),\n    (0x219, 'V'),\n    (0x21A, 'M', u'ț'),\n    (0x21B, 'V'),\n    (0x21C, 'M', u'ȝ'),\n    (0x21D, 'V'),\n    (0x21E, 'M', u'ȟ'),\n    (0x21F, 'V'),\n    (0x220, 'M', u'ƞ'),\n    (0x221, 'V'),\n    (0x222, 'M', u'ȣ'),\n    (0x223, 'V'),\n    (0x224, 'M', u'ȥ'),\n    (0x225, 'V'),\n    (0x226, 'M', u'ȧ'),\n    (0x227, 'V'),\n    (0x228, 'M', u'ȩ'),\n    (0x229, 'V'),\n    (0x22A, 'M', u'ȫ'),\n    (0x22B, 'V'),\n    (0x22C, 'M', u'ȭ'),\n    (0x22D, 'V'),\n    (0x22E, 'M', u'ȯ'),\n    (0x22F, 'V'),\n    (0x230, 'M', u'ȱ'),\n    (0x231, 'V'),\n    (0x232, 'M', u'ȳ'),\n    (0x233, 'V'),\n    (0x23A, 'M', u'ⱥ'),\n    (0x23B, 'M', u'ȼ'),\n    (0x23C, 'V'),\n    (0x23D, 'M', u'ƚ'),\n    (0x23E, 'M', u'ⱦ'),\n    (0x23F, 'V'),\n    (0x241, 'M', u'ɂ'),\n    (0x242, 'V'),\n    (0x243, 'M', u'ƀ'),\n    (0x244, 'M', u'ʉ'),\n    (0x245, 'M', u'ʌ'),\n    (0x246, 'M', u'ɇ'),\n    (0x247, 'V'),\n    (0x248, 'M', u'ɉ'),\n    (0x249, 'V'),\n    (0x24A, 'M', u'ɋ'),\n    (0x24B, 'V'),\n    (0x24C, 'M', u'ɍ'),\n    (0x24D, 'V'),\n    (0x24E, 'M', u'ɏ'),\n    (0x24F, 'V'),\n    (0x2B0, 'M', u'h'),\n    (0x2B1, 'M', u'ɦ'),\n    (0x2B2, 'M', u'j'),\n    (0x2B3, 'M', u'r'),\n    (0x2B4, 'M', u'ɹ'),\n    (0x2B5, 'M', u'ɻ'),\n    (0x2B6, 'M', u'ʁ'),\n    (0x2B7, 'M', u'w'),\n    (0x2B8, 'M', u'y'),\n    (0x2B9, 'V'),\n    (0x2D8, '3', u' ̆'),\n    (0x2D9, '3', u' ̇'),\n    (0x2DA, '3', u' ̊'),\n    (0x2DB, '3', u' ̨'),\n    (0x2DC, '3', u' ̃'),\n    (0x2DD, '3', u' ̋'),\n    (0x2DE, 'V'),\n    (0x2E0, 'M', u'ɣ'),\n    (0x2E1, 'M', u'l'),\n    (0x2E2, 'M', u's'),\n    (0x2E3, 'M', u'x'),\n    (0x2E4, 'M', u'ʕ'),\n    (0x2E5, 'V'),\n    (0x340, 'M', u'̀'),\n    (0x341, 'M', u'́'),\n    (0x342, 'V'),\n    (0x343, 'M', u'̓'),\n    (0x344, 'M', u'̈́'),\n    (0x345, 'M', u'ι'),\n    (0x346, 'V'),\n    (0x34F, 'I'),\n    (0x350, 'V'),\n    (0x370, 'M', u'ͱ'),\n    (0x371, 'V'),\n    (0x372, 'M', u'ͳ'),\n    (0x373, 'V'),\n    (0x374, 'M', u'ʹ'),\n    (0x375, 'V'),\n    (0x376, 'M', u'ͷ'),\n    (0x377, 'V'),\n    ]\n\ndef _seg_6():\n    return [\n    (0x378, 'X'),\n    (0x37A, '3', u' ι'),\n    (0x37B, 'V'),\n    (0x37E, '3', u';'),\n    (0x37F, 'M', u'ϳ'),\n    (0x380, 'X'),\n    (0x384, '3', u' ́'),\n    (0x385, '3', u' ̈́'),\n    (0x386, 'M', u'ά'),\n    (0x387, 'M', u'·'),\n    (0x388, 'M', u'έ'),\n    (0x389, 'M', u'ή'),\n    (0x38A, 'M', u'ί'),\n    (0x38B, 'X'),\n    (0x38C, 'M', u'ό'),\n    (0x38D, 'X'),\n    (0x38E, 'M', u'ύ'),\n    (0x38F, 'M', u'ώ'),\n    (0x390, 'V'),\n    (0x391, 'M', u'α'),\n    (0x392, 'M', u'β'),\n    (0x393, 'M', u'γ'),\n    (0x394, 'M', u'δ'),\n    (0x395, 'M', u'ε'),\n    (0x396, 'M', u'ζ'),\n    (0x397, 'M', u'η'),\n    (0x398, 'M', u'θ'),\n    (0x399, 'M', u'ι'),\n    (0x39A, 'M', u'κ'),\n    (0x39B, 'M', u'λ'),\n    (0x39C, 'M', u'μ'),\n    (0x39D, 'M', u'ν'),\n    (0x39E, 'M', u'ξ'),\n    (0x39F, 'M', u'ο'),\n    (0x3A0, 'M', u'π'),\n    (0x3A1, 'M', u'ρ'),\n    (0x3A2, 'X'),\n    (0x3A3, 'M', u'σ'),\n    (0x3A4, 'M', u'τ'),\n    (0x3A5, 'M', u'υ'),\n    (0x3A6, 'M', u'φ'),\n    (0x3A7, 'M', u'χ'),\n    (0x3A8, 'M', u'ψ'),\n    (0x3A9, 'M', u'ω'),\n    (0x3AA, 'M', u'ϊ'),\n    (0x3AB, 'M', u'ϋ'),\n    (0x3AC, 'V'),\n    (0x3C2, 'D', u'σ'),\n    (0x3C3, 'V'),\n    (0x3CF, 'M', u'ϗ'),\n    (0x3D0, 'M', u'β'),\n    (0x3D1, 'M', u'θ'),\n    (0x3D2, 'M', u'υ'),\n    (0x3D3, 'M', u'ύ'),\n    (0x3D4, 'M', u'ϋ'),\n    (0x3D5, 'M', u'φ'),\n    (0x3D6, 'M', u'π'),\n    (0x3D7, 'V'),\n    (0x3D8, 'M', u'ϙ'),\n    (0x3D9, 'V'),\n    (0x3DA, 'M', u'ϛ'),\n    (0x3DB, 'V'),\n    (0x3DC, 'M', u'ϝ'),\n    (0x3DD, 'V'),\n    (0x3DE, 'M', u'ϟ'),\n    (0x3DF, 'V'),\n    (0x3E0, 'M', u'ϡ'),\n    (0x3E1, 'V'),\n    (0x3E2, 'M', u'ϣ'),\n    (0x3E3, 'V'),\n    (0x3E4, 'M', u'ϥ'),\n    (0x3E5, 'V'),\n    (0x3E6, 'M', u'ϧ'),\n    (0x3E7, 'V'),\n    (0x3E8, 'M', u'ϩ'),\n    (0x3E9, 'V'),\n    (0x3EA, 'M', u'ϫ'),\n    (0x3EB, 'V'),\n    (0x3EC, 'M', u'ϭ'),\n    (0x3ED, 'V'),\n    (0x3EE, 'M', u'ϯ'),\n    (0x3EF, 'V'),\n    (0x3F0, 'M', u'κ'),\n    (0x3F1, 'M', u'ρ'),\n    (0x3F2, 'M', u'σ'),\n    (0x3F3, 'V'),\n    (0x3F4, 'M', u'θ'),\n    (0x3F5, 'M', u'ε'),\n    (0x3F6, 'V'),\n    (0x3F7, 'M', u'ϸ'),\n    (0x3F8, 'V'),\n    (0x3F9, 'M', u'σ'),\n    (0x3FA, 'M', u'ϻ'),\n    (0x3FB, 'V'),\n    (0x3FD, 'M', u'ͻ'),\n    (0x3FE, 'M', u'ͼ'),\n    (0x3FF, 'M', u'ͽ'),\n    (0x400, 'M', u'ѐ'),\n    (0x401, 'M', u'ё'),\n    (0x402, 'M', u'ђ'),\n    ]\n\ndef _seg_7():\n    return [\n    (0x403, 'M', u'ѓ'),\n    (0x404, 'M', u'є'),\n    (0x405, 'M', u'ѕ'),\n    (0x406, 'M', u'і'),\n    (0x407, 'M', u'ї'),\n    (0x408, 'M', u'ј'),\n    (0x409, 'M', u'љ'),\n    (0x40A, 'M', u'њ'),\n    (0x40B, 'M', u'ћ'),\n    (0x40C, 'M', u'ќ'),\n    (0x40D, 'M', u'ѝ'),\n    (0x40E, 'M', u'ў'),\n    (0x40F, 'M', u'џ'),\n    (0x410, 'M', u'а'),\n    (0x411, 'M', u'б'),\n    (0x412, 'M', u'в'),\n    (0x413, 'M', u'г'),\n    (0x414, 'M', u'д'),\n    (0x415, 'M', u'е'),\n    (0x416, 'M', u'ж'),\n    (0x417, 'M', u'з'),\n    (0x418, 'M', u'и'),\n    (0x419, 'M', u'й'),\n    (0x41A, 'M', u'к'),\n    (0x41B, 'M', u'л'),\n    (0x41C, 'M', u'м'),\n    (0x41D, 'M', u'н'),\n    (0x41E, 'M', u'о'),\n    (0x41F, 'M', u'п'),\n    (0x420, 'M', u'р'),\n    (0x421, 'M', u'с'),\n    (0x422, 'M', u'т'),\n    (0x423, 'M', u'у'),\n    (0x424, 'M', u'ф'),\n    (0x425, 'M', u'х'),\n    (0x426, 'M', u'ц'),\n    (0x427, 'M', u'ч'),\n    (0x428, 'M', u'ш'),\n    (0x429, 'M', u'щ'),\n    (0x42A, 'M', u'ъ'),\n    (0x42B, 'M', u'ы'),\n    (0x42C, 'M', u'ь'),\n    (0x42D, 'M', u'э'),\n    (0x42E, 'M', u'ю'),\n    (0x42F, 'M', u'я'),\n    (0x430, 'V'),\n    (0x460, 'M', u'ѡ'),\n    (0x461, 'V'),\n    (0x462, 'M', u'ѣ'),\n    (0x463, 'V'),\n    (0x464, 'M', u'ѥ'),\n    (0x465, 'V'),\n    (0x466, 'M', u'ѧ'),\n    (0x467, 'V'),\n    (0x468, 'M', u'ѩ'),\n    (0x469, 'V'),\n    (0x46A, 'M', u'ѫ'),\n    (0x46B, 'V'),\n    (0x46C, 'M', u'ѭ'),\n    (0x46D, 'V'),\n    (0x46E, 'M', u'ѯ'),\n    (0x46F, 'V'),\n    (0x470, 'M', u'ѱ'),\n    (0x471, 'V'),\n    (0x472, 'M', u'ѳ'),\n    (0x473, 'V'),\n    (0x474, 'M', u'ѵ'),\n    (0x475, 'V'),\n    (0x476, 'M', u'ѷ'),\n    (0x477, 'V'),\n    (0x478, 'M', u'ѹ'),\n    (0x479, 'V'),\n    (0x47A, 'M', u'ѻ'),\n    (0x47B, 'V'),\n    (0x47C, 'M', u'ѽ'),\n    (0x47D, 'V'),\n    (0x47E, 'M', u'ѿ'),\n    (0x47F, 'V'),\n    (0x480, 'M', u'ҁ'),\n    (0x481, 'V'),\n    (0x48A, 'M', u'ҋ'),\n    (0x48B, 'V'),\n    (0x48C, 'M', u'ҍ'),\n    (0x48D, 'V'),\n    (0x48E, 'M', u'ҏ'),\n    (0x48F, 'V'),\n    (0x490, 'M', u'ґ'),\n    (0x491, 'V'),\n    (0x492, 'M', u'ғ'),\n    (0x493, 'V'),\n    (0x494, 'M', u'ҕ'),\n    (0x495, 'V'),\n    (0x496, 'M', u'җ'),\n    (0x497, 'V'),\n    (0x498, 'M', u'ҙ'),\n    (0x499, 'V'),\n    (0x49A, 'M', u'қ'),\n    (0x49B, 'V'),\n    (0x49C, 'M', u'ҝ'),\n    (0x49D, 'V'),\n    ]\n\ndef _seg_8():\n    return [\n    (0x49E, 'M', u'ҟ'),\n    (0x49F, 'V'),\n    (0x4A0, 'M', u'ҡ'),\n    (0x4A1, 'V'),\n    (0x4A2, 'M', u'ң'),\n    (0x4A3, 'V'),\n    (0x4A4, 'M', u'ҥ'),\n    (0x4A5, 'V'),\n    (0x4A6, 'M', u'ҧ'),\n    (0x4A7, 'V'),\n    (0x4A8, 'M', u'ҩ'),\n    (0x4A9, 'V'),\n    (0x4AA, 'M', u'ҫ'),\n    (0x4AB, 'V'),\n    (0x4AC, 'M', u'ҭ'),\n    (0x4AD, 'V'),\n    (0x4AE, 'M', u'ү'),\n    (0x4AF, 'V'),\n    (0x4B0, 'M', u'ұ'),\n    (0x4B1, 'V'),\n    (0x4B2, 'M', u'ҳ'),\n    (0x4B3, 'V'),\n    (0x4B4, 'M', u'ҵ'),\n    (0x4B5, 'V'),\n    (0x4B6, 'M', u'ҷ'),\n    (0x4B7, 'V'),\n    (0x4B8, 'M', u'ҹ'),\n    (0x4B9, 'V'),\n    (0x4BA, 'M', u'һ'),\n    (0x4BB, 'V'),\n    (0x4BC, 'M', u'ҽ'),\n    (0x4BD, 'V'),\n    (0x4BE, 'M', u'ҿ'),\n    (0x4BF, 'V'),\n    (0x4C0, 'X'),\n    (0x4C1, 'M', u'ӂ'),\n    (0x4C2, 'V'),\n    (0x4C3, 'M', u'ӄ'),\n    (0x4C4, 'V'),\n    (0x4C5, 'M', u'ӆ'),\n    (0x4C6, 'V'),\n    (0x4C7, 'M', u'ӈ'),\n    (0x4C8, 'V'),\n    (0x4C9, 'M', u'ӊ'),\n    (0x4CA, 'V'),\n    (0x4CB, 'M', u'ӌ'),\n    (0x4CC, 'V'),\n    (0x4CD, 'M', u'ӎ'),\n    (0x4CE, 'V'),\n    (0x4D0, 'M', u'ӑ'),\n    (0x4D1, 'V'),\n    (0x4D2, 'M', u'ӓ'),\n    (0x4D3, 'V'),\n    (0x4D4, 'M', u'ӕ'),\n    (0x4D5, 'V'),\n    (0x4D6, 'M', u'ӗ'),\n    (0x4D7, 'V'),\n    (0x4D8, 'M', u'ә'),\n    (0x4D9, 'V'),\n    (0x4DA, 'M', u'ӛ'),\n    (0x4DB, 'V'),\n    (0x4DC, 'M', u'ӝ'),\n    (0x4DD, 'V'),\n    (0x4DE, 'M', u'ӟ'),\n    (0x4DF, 'V'),\n    (0x4E0, 'M', u'ӡ'),\n    (0x4E1, 'V'),\n    (0x4E2, 'M', u'ӣ'),\n    (0x4E3, 'V'),\n    (0x4E4, 'M', u'ӥ'),\n    (0x4E5, 'V'),\n    (0x4E6, 'M', u'ӧ'),\n    (0x4E7, 'V'),\n    (0x4E8, 'M', u'ө'),\n    (0x4E9, 'V'),\n    (0x4EA, 'M', u'ӫ'),\n    (0x4EB, 'V'),\n    (0x4EC, 'M', u'ӭ'),\n    (0x4ED, 'V'),\n    (0x4EE, 'M', u'ӯ'),\n    (0x4EF, 'V'),\n    (0x4F0, 'M', u'ӱ'),\n    (0x4F1, 'V'),\n    (0x4F2, 'M', u'ӳ'),\n    (0x4F3, 'V'),\n    (0x4F4, 'M', u'ӵ'),\n    (0x4F5, 'V'),\n    (0x4F6, 'M', u'ӷ'),\n    (0x4F7, 'V'),\n    (0x4F8, 'M', u'ӹ'),\n    (0x4F9, 'V'),\n    (0x4FA, 'M', u'ӻ'),\n    (0x4FB, 'V'),\n    (0x4FC, 'M', u'ӽ'),\n    (0x4FD, 'V'),\n    (0x4FE, 'M', u'ӿ'),\n    (0x4FF, 'V'),\n    (0x500, 'M', u'ԁ'),\n    (0x501, 'V'),\n    (0x502, 'M', u'ԃ'),\n    ]\n\ndef _seg_9():\n    return [\n    (0x503, 'V'),\n    (0x504, 'M', u'ԅ'),\n    (0x505, 'V'),\n    (0x506, 'M', u'ԇ'),\n    (0x507, 'V'),\n    (0x508, 'M', u'ԉ'),\n    (0x509, 'V'),\n    (0x50A, 'M', u'ԋ'),\n    (0x50B, 'V'),\n    (0x50C, 'M', u'ԍ'),\n    (0x50D, 'V'),\n    (0x50E, 'M', u'ԏ'),\n    (0x50F, 'V'),\n    (0x510, 'M', u'ԑ'),\n    (0x511, 'V'),\n    (0x512, 'M', u'ԓ'),\n    (0x513, 'V'),\n    (0x514, 'M', u'ԕ'),\n    (0x515, 'V'),\n    (0x516, 'M', u'ԗ'),\n    (0x517, 'V'),\n    (0x518, 'M', u'ԙ'),\n    (0x519, 'V'),\n    (0x51A, 'M', u'ԛ'),\n    (0x51B, 'V'),\n    (0x51C, 'M', u'ԝ'),\n    (0x51D, 'V'),\n    (0x51E, 'M', u'ԟ'),\n    (0x51F, 'V'),\n    (0x520, 'M', u'ԡ'),\n    (0x521, 'V'),\n    (0x522, 'M', u'ԣ'),\n    (0x523, 'V'),\n    (0x524, 'M', u'ԥ'),\n    (0x525, 'V'),\n    (0x526, 'M', u'ԧ'),\n    (0x527, 'V'),\n    (0x528, 'M', u'ԩ'),\n    (0x529, 'V'),\n    (0x52A, 'M', u'ԫ'),\n    (0x52B, 'V'),\n    (0x52C, 'M', u'ԭ'),\n    (0x52D, 'V'),\n    (0x52E, 'M', u'ԯ'),\n    (0x52F, 'V'),\n    (0x530, 'X'),\n    (0x531, 'M', u'ա'),\n    (0x532, 'M', u'բ'),\n    (0x533, 'M', u'գ'),\n    (0x534, 'M', u'դ'),\n    (0x535, 'M', u'ե'),\n    (0x536, 'M', u'զ'),\n    (0x537, 'M', u'է'),\n    (0x538, 'M', u'ը'),\n    (0x539, 'M', u'թ'),\n    (0x53A, 'M', u'ժ'),\n    (0x53B, 'M', u'ի'),\n    (0x53C, 'M', u'լ'),\n    (0x53D, 'M', u'խ'),\n    (0x53E, 'M', u'ծ'),\n    (0x53F, 'M', u'կ'),\n    (0x540, 'M', u'հ'),\n    (0x541, 'M', u'ձ'),\n    (0x542, 'M', u'ղ'),\n    (0x543, 'M', u'ճ'),\n    (0x544, 'M', u'մ'),\n    (0x545, 'M', u'յ'),\n    (0x546, 'M', u'ն'),\n    (0x547, 'M', u'շ'),\n    (0x548, 'M', u'ո'),\n    (0x549, 'M', u'չ'),\n    (0x54A, 'M', u'պ'),\n    (0x54B, 'M', u'ջ'),\n    (0x54C, 'M', u'ռ'),\n    (0x54D, 'M', u'ս'),\n    (0x54E, 'M', u'վ'),\n    (0x54F, 'M', u'տ'),\n    (0x550, 'M', u'ր'),\n    (0x551, 'M', u'ց'),\n    (0x552, 'M', u'ւ'),\n    (0x553, 'M', u'փ'),\n    (0x554, 'M', u'ք'),\n    (0x555, 'M', u'օ'),\n    (0x556, 'M', u'ֆ'),\n    (0x557, 'X'),\n    (0x559, 'V'),\n    (0x587, 'M', u'եւ'),\n    (0x588, 'V'),\n    (0x58B, 'X'),\n    (0x58D, 'V'),\n    (0x590, 'X'),\n    (0x591, 'V'),\n    (0x5C8, 'X'),\n    (0x5D0, 'V'),\n    (0x5EB, 'X'),\n    (0x5EF, 'V'),\n    (0x5F5, 'X'),\n    (0x606, 'V'),\n    (0x61C, 'X'),\n    (0x61E, 'V'),\n    ]\n\ndef _seg_10():\n    return [\n    (0x675, 'M', u'اٴ'),\n    (0x676, 'M', u'وٴ'),\n    (0x677, 'M', u'ۇٴ'),\n    (0x678, 'M', u'يٴ'),\n    (0x679, 'V'),\n    (0x6DD, 'X'),\n    (0x6DE, 'V'),\n    (0x70E, 'X'),\n    (0x710, 'V'),\n    (0x74B, 'X'),\n    (0x74D, 'V'),\n    (0x7B2, 'X'),\n    (0x7C0, 'V'),\n    (0x7FB, 'X'),\n    (0x7FD, 'V'),\n    (0x82E, 'X'),\n    (0x830, 'V'),\n    (0x83F, 'X'),\n    (0x840, 'V'),\n    (0x85C, 'X'),\n    (0x85E, 'V'),\n    (0x85F, 'X'),\n    (0x860, 'V'),\n    (0x86B, 'X'),\n    (0x8A0, 'V'),\n    (0x8B5, 'X'),\n    (0x8B6, 'V'),\n    (0x8BE, 'X'),\n    (0x8D3, 'V'),\n    (0x8E2, 'X'),\n    (0x8E3, 'V'),\n    (0x958, 'M', u'क़'),\n    (0x959, 'M', u'ख़'),\n    (0x95A, 'M', u'ग़'),\n    (0x95B, 'M', u'ज़'),\n    (0x95C, 'M', u'ड़'),\n    (0x95D, 'M', u'ढ़'),\n    (0x95E, 'M', u'फ़'),\n    (0x95F, 'M', u'य़'),\n    (0x960, 'V'),\n    (0x984, 'X'),\n    (0x985, 'V'),\n    (0x98D, 'X'),\n    (0x98F, 'V'),\n    (0x991, 'X'),\n    (0x993, 'V'),\n    (0x9A9, 'X'),\n    (0x9AA, 'V'),\n    (0x9B1, 'X'),\n    (0x9B2, 'V'),\n    (0x9B3, 'X'),\n    (0x9B6, 'V'),\n    (0x9BA, 'X'),\n    (0x9BC, 'V'),\n    (0x9C5, 'X'),\n    (0x9C7, 'V'),\n    (0x9C9, 'X'),\n    (0x9CB, 'V'),\n    (0x9CF, 'X'),\n    (0x9D7, 'V'),\n    (0x9D8, 'X'),\n    (0x9DC, 'M', u'ড়'),\n    (0x9DD, 'M', u'ঢ়'),\n    (0x9DE, 'X'),\n    (0x9DF, 'M', u'য়'),\n    (0x9E0, 'V'),\n    (0x9E4, 'X'),\n    (0x9E6, 'V'),\n    (0x9FF, 'X'),\n    (0xA01, 'V'),\n    (0xA04, 'X'),\n    (0xA05, 'V'),\n    (0xA0B, 'X'),\n    (0xA0F, 'V'),\n    (0xA11, 'X'),\n    (0xA13, 'V'),\n    (0xA29, 'X'),\n    (0xA2A, 'V'),\n    (0xA31, 'X'),\n    (0xA32, 'V'),\n    (0xA33, 'M', u'ਲ਼'),\n    (0xA34, 'X'),\n    (0xA35, 'V'),\n    (0xA36, 'M', u'ਸ਼'),\n    (0xA37, 'X'),\n    (0xA38, 'V'),\n    (0xA3A, 'X'),\n    (0xA3C, 'V'),\n    (0xA3D, 'X'),\n    (0xA3E, 'V'),\n    (0xA43, 'X'),\n    (0xA47, 'V'),\n    (0xA49, 'X'),\n    (0xA4B, 'V'),\n    (0xA4E, 'X'),\n    (0xA51, 'V'),\n    (0xA52, 'X'),\n    (0xA59, 'M', u'ਖ਼'),\n    (0xA5A, 'M', u'ਗ਼'),\n    (0xA5B, 'M', u'ਜ਼'),\n    ]\n\ndef _seg_11():\n    return [\n    (0xA5C, 'V'),\n    (0xA5D, 'X'),\n    (0xA5E, 'M', u'ਫ਼'),\n    (0xA5F, 'X'),\n    (0xA66, 'V'),\n    (0xA77, 'X'),\n    (0xA81, 'V'),\n    (0xA84, 'X'),\n    (0xA85, 'V'),\n    (0xA8E, 'X'),\n    (0xA8F, 'V'),\n    (0xA92, 'X'),\n    (0xA93, 'V'),\n    (0xAA9, 'X'),\n    (0xAAA, 'V'),\n    (0xAB1, 'X'),\n    (0xAB2, 'V'),\n    (0xAB4, 'X'),\n    (0xAB5, 'V'),\n    (0xABA, 'X'),\n    (0xABC, 'V'),\n    (0xAC6, 'X'),\n    (0xAC7, 'V'),\n    (0xACA, 'X'),\n    (0xACB, 'V'),\n    (0xACE, 'X'),\n    (0xAD0, 'V'),\n    (0xAD1, 'X'),\n    (0xAE0, 'V'),\n    (0xAE4, 'X'),\n    (0xAE6, 'V'),\n    (0xAF2, 'X'),\n    (0xAF9, 'V'),\n    (0xB00, 'X'),\n    (0xB01, 'V'),\n    (0xB04, 'X'),\n    (0xB05, 'V'),\n    (0xB0D, 'X'),\n    (0xB0F, 'V'),\n    (0xB11, 'X'),\n    (0xB13, 'V'),\n    (0xB29, 'X'),\n    (0xB2A, 'V'),\n    (0xB31, 'X'),\n    (0xB32, 'V'),\n    (0xB34, 'X'),\n    (0xB35, 'V'),\n    (0xB3A, 'X'),\n    (0xB3C, 'V'),\n    (0xB45, 'X'),\n    (0xB47, 'V'),\n    (0xB49, 'X'),\n    (0xB4B, 'V'),\n    (0xB4E, 'X'),\n    (0xB56, 'V'),\n    (0xB58, 'X'),\n    (0xB5C, 'M', u'ଡ଼'),\n    (0xB5D, 'M', u'ଢ଼'),\n    (0xB5E, 'X'),\n    (0xB5F, 'V'),\n    (0xB64, 'X'),\n    (0xB66, 'V'),\n    (0xB78, 'X'),\n    (0xB82, 'V'),\n    (0xB84, 'X'),\n    (0xB85, 'V'),\n    (0xB8B, 'X'),\n    (0xB8E, 'V'),\n    (0xB91, 'X'),\n    (0xB92, 'V'),\n    (0xB96, 'X'),\n    (0xB99, 'V'),\n    (0xB9B, 'X'),\n    (0xB9C, 'V'),\n    (0xB9D, 'X'),\n    (0xB9E, 'V'),\n    (0xBA0, 'X'),\n    (0xBA3, 'V'),\n    (0xBA5, 'X'),\n    (0xBA8, 'V'),\n    (0xBAB, 'X'),\n    (0xBAE, 'V'),\n    (0xBBA, 'X'),\n    (0xBBE, 'V'),\n    (0xBC3, 'X'),\n    (0xBC6, 'V'),\n    (0xBC9, 'X'),\n    (0xBCA, 'V'),\n    (0xBCE, 'X'),\n    (0xBD0, 'V'),\n    (0xBD1, 'X'),\n    (0xBD7, 'V'),\n    (0xBD8, 'X'),\n    (0xBE6, 'V'),\n    (0xBFB, 'X'),\n    (0xC00, 'V'),\n    (0xC0D, 'X'),\n    (0xC0E, 'V'),\n    (0xC11, 'X'),\n    (0xC12, 'V'),\n    ]\n\ndef _seg_12():\n    return [\n    (0xC29, 'X'),\n    (0xC2A, 'V'),\n    (0xC3A, 'X'),\n    (0xC3D, 'V'),\n    (0xC45, 'X'),\n    (0xC46, 'V'),\n    (0xC49, 'X'),\n    (0xC4A, 'V'),\n    (0xC4E, 'X'),\n    (0xC55, 'V'),\n    (0xC57, 'X'),\n    (0xC58, 'V'),\n    (0xC5B, 'X'),\n    (0xC60, 'V'),\n    (0xC64, 'X'),\n    (0xC66, 'V'),\n    (0xC70, 'X'),\n    (0xC78, 'V'),\n    (0xC8D, 'X'),\n    (0xC8E, 'V'),\n    (0xC91, 'X'),\n    (0xC92, 'V'),\n    (0xCA9, 'X'),\n    (0xCAA, 'V'),\n    (0xCB4, 'X'),\n    (0xCB5, 'V'),\n    (0xCBA, 'X'),\n    (0xCBC, 'V'),\n    (0xCC5, 'X'),\n    (0xCC6, 'V'),\n    (0xCC9, 'X'),\n    (0xCCA, 'V'),\n    (0xCCE, 'X'),\n    (0xCD5, 'V'),\n    (0xCD7, 'X'),\n    (0xCDE, 'V'),\n    (0xCDF, 'X'),\n    (0xCE0, 'V'),\n    (0xCE4, 'X'),\n    (0xCE6, 'V'),\n    (0xCF0, 'X'),\n    (0xCF1, 'V'),\n    (0xCF3, 'X'),\n    (0xD00, 'V'),\n    (0xD04, 'X'),\n    (0xD05, 'V'),\n    (0xD0D, 'X'),\n    (0xD0E, 'V'),\n    (0xD11, 'X'),\n    (0xD12, 'V'),\n    (0xD45, 'X'),\n    (0xD46, 'V'),\n    (0xD49, 'X'),\n    (0xD4A, 'V'),\n    (0xD50, 'X'),\n    (0xD54, 'V'),\n    (0xD64, 'X'),\n    (0xD66, 'V'),\n    (0xD80, 'X'),\n    (0xD82, 'V'),\n    (0xD84, 'X'),\n    (0xD85, 'V'),\n    (0xD97, 'X'),\n    (0xD9A, 'V'),\n    (0xDB2, 'X'),\n    (0xDB3, 'V'),\n    (0xDBC, 'X'),\n    (0xDBD, 'V'),\n    (0xDBE, 'X'),\n    (0xDC0, 'V'),\n    (0xDC7, 'X'),\n    (0xDCA, 'V'),\n    (0xDCB, 'X'),\n    (0xDCF, 'V'),\n    (0xDD5, 'X'),\n    (0xDD6, 'V'),\n    (0xDD7, 'X'),\n    (0xDD8, 'V'),\n    (0xDE0, 'X'),\n    (0xDE6, 'V'),\n    (0xDF0, 'X'),\n    (0xDF2, 'V'),\n    (0xDF5, 'X'),\n    (0xE01, 'V'),\n    (0xE33, 'M', u'ํา'),\n    (0xE34, 'V'),\n    (0xE3B, 'X'),\n    (0xE3F, 'V'),\n    (0xE5C, 'X'),\n    (0xE81, 'V'),\n    (0xE83, 'X'),\n    (0xE84, 'V'),\n    (0xE85, 'X'),\n    (0xE87, 'V'),\n    (0xE89, 'X'),\n    (0xE8A, 'V'),\n    (0xE8B, 'X'),\n    (0xE8D, 'V'),\n    (0xE8E, 'X'),\n    (0xE94, 'V'),\n    ]\n\ndef _seg_13():\n    return [\n    (0xE98, 'X'),\n    (0xE99, 'V'),\n    (0xEA0, 'X'),\n    (0xEA1, 'V'),\n    (0xEA4, 'X'),\n    (0xEA5, 'V'),\n    (0xEA6, 'X'),\n    (0xEA7, 'V'),\n    (0xEA8, 'X'),\n    (0xEAA, 'V'),\n    (0xEAC, 'X'),\n    (0xEAD, 'V'),\n    (0xEB3, 'M', u'ໍາ'),\n    (0xEB4, 'V'),\n    (0xEBA, 'X'),\n    (0xEBB, 'V'),\n    (0xEBE, 'X'),\n    (0xEC0, 'V'),\n    (0xEC5, 'X'),\n    (0xEC6, 'V'),\n    (0xEC7, 'X'),\n    (0xEC8, 'V'),\n    (0xECE, 'X'),\n    (0xED0, 'V'),\n    (0xEDA, 'X'),\n    (0xEDC, 'M', u'ຫນ'),\n    (0xEDD, 'M', u'ຫມ'),\n    (0xEDE, 'V'),\n    (0xEE0, 'X'),\n    (0xF00, 'V'),\n    (0xF0C, 'M', u'་'),\n    (0xF0D, 'V'),\n    (0xF43, 'M', u'གྷ'),\n    (0xF44, 'V'),\n    (0xF48, 'X'),\n    (0xF49, 'V'),\n    (0xF4D, 'M', u'ཌྷ'),\n    (0xF4E, 'V'),\n    (0xF52, 'M', u'དྷ'),\n    (0xF53, 'V'),\n    (0xF57, 'M', u'བྷ'),\n    (0xF58, 'V'),\n    (0xF5C, 'M', u'ཛྷ'),\n    (0xF5D, 'V'),\n    (0xF69, 'M', u'ཀྵ'),\n    (0xF6A, 'V'),\n    (0xF6D, 'X'),\n    (0xF71, 'V'),\n    (0xF73, 'M', u'ཱི'),\n    (0xF74, 'V'),\n    (0xF75, 'M', u'ཱུ'),\n    (0xF76, 'M', u'ྲྀ'),\n    (0xF77, 'M', u'ྲཱྀ'),\n    (0xF78, 'M', u'ླྀ'),\n    (0xF79, 'M', u'ླཱྀ'),\n    (0xF7A, 'V'),\n    (0xF81, 'M', u'ཱྀ'),\n    (0xF82, 'V'),\n    (0xF93, 'M', u'ྒྷ'),\n    (0xF94, 'V'),\n    (0xF98, 'X'),\n    (0xF99, 'V'),\n    (0xF9D, 'M', u'ྜྷ'),\n    (0xF9E, 'V'),\n    (0xFA2, 'M', u'ྡྷ'),\n    (0xFA3, 'V'),\n    (0xFA7, 'M', u'ྦྷ'),\n    (0xFA8, 'V'),\n    (0xFAC, 'M', u'ྫྷ'),\n    (0xFAD, 'V'),\n    (0xFB9, 'M', u'ྐྵ'),\n    (0xFBA, 'V'),\n    (0xFBD, 'X'),\n    (0xFBE, 'V'),\n    (0xFCD, 'X'),\n    (0xFCE, 'V'),\n    (0xFDB, 'X'),\n    (0x1000, 'V'),\n    (0x10A0, 'X'),\n    (0x10C7, 'M', u'ⴧ'),\n    (0x10C8, 'X'),\n    (0x10CD, 'M', u'ⴭ'),\n    (0x10CE, 'X'),\n    (0x10D0, 'V'),\n    (0x10FC, 'M', u'ნ'),\n    (0x10FD, 'V'),\n    (0x115F, 'X'),\n    (0x1161, 'V'),\n    (0x1249, 'X'),\n    (0x124A, 'V'),\n    (0x124E, 'X'),\n    (0x1250, 'V'),\n    (0x1257, 'X'),\n    (0x1258, 'V'),\n    (0x1259, 'X'),\n    (0x125A, 'V'),\n    (0x125E, 'X'),\n    (0x1260, 'V'),\n    (0x1289, 'X'),\n    (0x128A, 'V'),\n    ]\n\ndef _seg_14():\n    return [\n    (0x128E, 'X'),\n    (0x1290, 'V'),\n    (0x12B1, 'X'),\n    (0x12B2, 'V'),\n    (0x12B6, 'X'),\n    (0x12B8, 'V'),\n    (0x12BF, 'X'),\n    (0x12C0, 'V'),\n    (0x12C1, 'X'),\n    (0x12C2, 'V'),\n    (0x12C6, 'X'),\n    (0x12C8, 'V'),\n    (0x12D7, 'X'),\n    (0x12D8, 'V'),\n    (0x1311, 'X'),\n    (0x1312, 'V'),\n    (0x1316, 'X'),\n    (0x1318, 'V'),\n    (0x135B, 'X'),\n    (0x135D, 'V'),\n    (0x137D, 'X'),\n    (0x1380, 'V'),\n    (0x139A, 'X'),\n    (0x13A0, 'V'),\n    (0x13F6, 'X'),\n    (0x13F8, 'M', u'Ᏸ'),\n    (0x13F9, 'M', u'Ᏹ'),\n    (0x13FA, 'M', u'Ᏺ'),\n    (0x13FB, 'M', u'Ᏻ'),\n    (0x13FC, 'M', u'Ᏼ'),\n    (0x13FD, 'M', u'Ᏽ'),\n    (0x13FE, 'X'),\n    (0x1400, 'V'),\n    (0x1680, 'X'),\n    (0x1681, 'V'),\n    (0x169D, 'X'),\n    (0x16A0, 'V'),\n    (0x16F9, 'X'),\n    (0x1700, 'V'),\n    (0x170D, 'X'),\n    (0x170E, 'V'),\n    (0x1715, 'X'),\n    (0x1720, 'V'),\n    (0x1737, 'X'),\n    (0x1740, 'V'),\n    (0x1754, 'X'),\n    (0x1760, 'V'),\n    (0x176D, 'X'),\n    (0x176E, 'V'),\n    (0x1771, 'X'),\n    (0x1772, 'V'),\n    (0x1774, 'X'),\n    (0x1780, 'V'),\n    (0x17B4, 'X'),\n    (0x17B6, 'V'),\n    (0x17DE, 'X'),\n    (0x17E0, 'V'),\n    (0x17EA, 'X'),\n    (0x17F0, 'V'),\n    (0x17FA, 'X'),\n    (0x1800, 'V'),\n    (0x1806, 'X'),\n    (0x1807, 'V'),\n    (0x180B, 'I'),\n    (0x180E, 'X'),\n    (0x1810, 'V'),\n    (0x181A, 'X'),\n    (0x1820, 'V'),\n    (0x1879, 'X'),\n    (0x1880, 'V'),\n    (0x18AB, 'X'),\n    (0x18B0, 'V'),\n    (0x18F6, 'X'),\n    (0x1900, 'V'),\n    (0x191F, 'X'),\n    (0x1920, 'V'),\n    (0x192C, 'X'),\n    (0x1930, 'V'),\n    (0x193C, 'X'),\n    (0x1940, 'V'),\n    (0x1941, 'X'),\n    (0x1944, 'V'),\n    (0x196E, 'X'),\n    (0x1970, 'V'),\n    (0x1975, 'X'),\n    (0x1980, 'V'),\n    (0x19AC, 'X'),\n    (0x19B0, 'V'),\n    (0x19CA, 'X'),\n    (0x19D0, 'V'),\n    (0x19DB, 'X'),\n    (0x19DE, 'V'),\n    (0x1A1C, 'X'),\n    (0x1A1E, 'V'),\n    (0x1A5F, 'X'),\n    (0x1A60, 'V'),\n    (0x1A7D, 'X'),\n    (0x1A7F, 'V'),\n    (0x1A8A, 'X'),\n    (0x1A90, 'V'),\n    ]\n\ndef _seg_15():\n    return [\n    (0x1A9A, 'X'),\n    (0x1AA0, 'V'),\n    (0x1AAE, 'X'),\n    (0x1AB0, 'V'),\n    (0x1ABF, 'X'),\n    (0x1B00, 'V'),\n    (0x1B4C, 'X'),\n    (0x1B50, 'V'),\n    (0x1B7D, 'X'),\n    (0x1B80, 'V'),\n    (0x1BF4, 'X'),\n    (0x1BFC, 'V'),\n    (0x1C38, 'X'),\n    (0x1C3B, 'V'),\n    (0x1C4A, 'X'),\n    (0x1C4D, 'V'),\n    (0x1C80, 'M', u'в'),\n    (0x1C81, 'M', u'д'),\n    (0x1C82, 'M', u'о'),\n    (0x1C83, 'M', u'с'),\n    (0x1C84, 'M', u'т'),\n    (0x1C86, 'M', u'ъ'),\n    (0x1C87, 'M', u'ѣ'),\n    (0x1C88, 'M', u'ꙋ'),\n    (0x1C89, 'X'),\n    (0x1CC0, 'V'),\n    (0x1CC8, 'X'),\n    (0x1CD0, 'V'),\n    (0x1CFA, 'X'),\n    (0x1D00, 'V'),\n    (0x1D2C, 'M', u'a'),\n    (0x1D2D, 'M', u'æ'),\n    (0x1D2E, 'M', u'b'),\n    (0x1D2F, 'V'),\n    (0x1D30, 'M', u'd'),\n    (0x1D31, 'M', u'e'),\n    (0x1D32, 'M', u'ǝ'),\n    (0x1D33, 'M', u'g'),\n    (0x1D34, 'M', u'h'),\n    (0x1D35, 'M', u'i'),\n    (0x1D36, 'M', u'j'),\n    (0x1D37, 'M', u'k'),\n    (0x1D38, 'M', u'l'),\n    (0x1D39, 'M', u'm'),\n    (0x1D3A, 'M', u'n'),\n    (0x1D3B, 'V'),\n    (0x1D3C, 'M', u'o'),\n    (0x1D3D, 'M', u'ȣ'),\n    (0x1D3E, 'M', u'p'),\n    (0x1D3F, 'M', u'r'),\n    (0x1D40, 'M', u't'),\n    (0x1D41, 'M', u'u'),\n    (0x1D42, 'M', u'w'),\n    (0x1D43, 'M', u'a'),\n    (0x1D44, 'M', u'ɐ'),\n    (0x1D45, 'M', u'ɑ'),\n    (0x1D46, 'M', u'ᴂ'),\n    (0x1D47, 'M', u'b'),\n    (0x1D48, 'M', u'd'),\n    (0x1D49, 'M', u'e'),\n    (0x1D4A, 'M', u'ə'),\n    (0x1D4B, 'M', u'ɛ'),\n    (0x1D4C, 'M', u'ɜ'),\n    (0x1D4D, 'M', u'g'),\n    (0x1D4E, 'V'),\n    (0x1D4F, 'M', u'k'),\n    (0x1D50, 'M', u'm'),\n    (0x1D51, 'M', u'ŋ'),\n    (0x1D52, 'M', u'o'),\n    (0x1D53, 'M', u'ɔ'),\n    (0x1D54, 'M', u'ᴖ'),\n    (0x1D55, 'M', u'ᴗ'),\n    (0x1D56, 'M', u'p'),\n    (0x1D57, 'M', u't'),\n    (0x1D58, 'M', u'u'),\n    (0x1D59, 'M', u'ᴝ'),\n    (0x1D5A, 'M', u'ɯ'),\n    (0x1D5B, 'M', u'v'),\n    (0x1D5C, 'M', u'ᴥ'),\n    (0x1D5D, 'M', u'β'),\n    (0x1D5E, 'M', u'γ'),\n    (0x1D5F, 'M', u'δ'),\n    (0x1D60, 'M', u'φ'),\n    (0x1D61, 'M', u'χ'),\n    (0x1D62, 'M', u'i'),\n    (0x1D63, 'M', u'r'),\n    (0x1D64, 'M', u'u'),\n    (0x1D65, 'M', u'v'),\n    (0x1D66, 'M', u'β'),\n    (0x1D67, 'M', u'γ'),\n    (0x1D68, 'M', u'ρ'),\n    (0x1D69, 'M', u'φ'),\n    (0x1D6A, 'M', u'χ'),\n    (0x1D6B, 'V'),\n    (0x1D78, 'M', u'н'),\n    (0x1D79, 'V'),\n    (0x1D9B, 'M', u'ɒ'),\n    (0x1D9C, 'M', u'c'),\n    (0x1D9D, 'M', u'ɕ'),\n    (0x1D9E, 'M', u'ð'),\n    ]\n\ndef _seg_16():\n    return [\n    (0x1D9F, 'M', u'ɜ'),\n    (0x1DA0, 'M', u'f'),\n    (0x1DA1, 'M', u'ɟ'),\n    (0x1DA2, 'M', u'ɡ'),\n    (0x1DA3, 'M', u'ɥ'),\n    (0x1DA4, 'M', u'ɨ'),\n    (0x1DA5, 'M', u'ɩ'),\n    (0x1DA6, 'M', u'ɪ'),\n    (0x1DA7, 'M', u'ᵻ'),\n    (0x1DA8, 'M', u'ʝ'),\n    (0x1DA9, 'M', u'ɭ'),\n    (0x1DAA, 'M', u'ᶅ'),\n    (0x1DAB, 'M', u'ʟ'),\n    (0x1DAC, 'M', u'ɱ'),\n    (0x1DAD, 'M', u'ɰ'),\n    (0x1DAE, 'M', u'ɲ'),\n    (0x1DAF, 'M', u'ɳ'),\n    (0x1DB0, 'M', u'ɴ'),\n    (0x1DB1, 'M', u'ɵ'),\n    (0x1DB2, 'M', u'ɸ'),\n    (0x1DB3, 'M', u'ʂ'),\n    (0x1DB4, 'M', u'ʃ'),\n    (0x1DB5, 'M', u'ƫ'),\n    (0x1DB6, 'M', u'ʉ'),\n    (0x1DB7, 'M', u'ʊ'),\n    (0x1DB8, 'M', u'ᴜ'),\n    (0x1DB9, 'M', u'ʋ'),\n    (0x1DBA, 'M', u'ʌ'),\n    (0x1DBB, 'M', u'z'),\n    (0x1DBC, 'M', u'ʐ'),\n    (0x1DBD, 'M', u'ʑ'),\n    (0x1DBE, 'M', u'ʒ'),\n    (0x1DBF, 'M', u'θ'),\n    (0x1DC0, 'V'),\n    (0x1DFA, 'X'),\n    (0x1DFB, 'V'),\n    (0x1E00, 'M', u'ḁ'),\n    (0x1E01, 'V'),\n    (0x1E02, 'M', u'ḃ'),\n    (0x1E03, 'V'),\n    (0x1E04, 'M', u'ḅ'),\n    (0x1E05, 'V'),\n    (0x1E06, 'M', u'ḇ'),\n    (0x1E07, 'V'),\n    (0x1E08, 'M', u'ḉ'),\n    (0x1E09, 'V'),\n    (0x1E0A, 'M', u'ḋ'),\n    (0x1E0B, 'V'),\n    (0x1E0C, 'M', u'ḍ'),\n    (0x1E0D, 'V'),\n    (0x1E0E, 'M', u'ḏ'),\n    (0x1E0F, 'V'),\n    (0x1E10, 'M', u'ḑ'),\n    (0x1E11, 'V'),\n    (0x1E12, 'M', u'ḓ'),\n    (0x1E13, 'V'),\n    (0x1E14, 'M', u'ḕ'),\n    (0x1E15, 'V'),\n    (0x1E16, 'M', u'ḗ'),\n    (0x1E17, 'V'),\n    (0x1E18, 'M', u'ḙ'),\n    (0x1E19, 'V'),\n    (0x1E1A, 'M', u'ḛ'),\n    (0x1E1B, 'V'),\n    (0x1E1C, 'M', u'ḝ'),\n    (0x1E1D, 'V'),\n    (0x1E1E, 'M', u'ḟ'),\n    (0x1E1F, 'V'),\n    (0x1E20, 'M', u'ḡ'),\n    (0x1E21, 'V'),\n    (0x1E22, 'M', u'ḣ'),\n    (0x1E23, 'V'),\n    (0x1E24, 'M', u'ḥ'),\n    (0x1E25, 'V'),\n    (0x1E26, 'M', u'ḧ'),\n    (0x1E27, 'V'),\n    (0x1E28, 'M', u'ḩ'),\n    (0x1E29, 'V'),\n    (0x1E2A, 'M', u'ḫ'),\n    (0x1E2B, 'V'),\n    (0x1E2C, 'M', u'ḭ'),\n    (0x1E2D, 'V'),\n    (0x1E2E, 'M', u'ḯ'),\n    (0x1E2F, 'V'),\n    (0x1E30, 'M', u'ḱ'),\n    (0x1E31, 'V'),\n    (0x1E32, 'M', u'ḳ'),\n    (0x1E33, 'V'),\n    (0x1E34, 'M', u'ḵ'),\n    (0x1E35, 'V'),\n    (0x1E36, 'M', u'ḷ'),\n    (0x1E37, 'V'),\n    (0x1E38, 'M', u'ḹ'),\n    (0x1E39, 'V'),\n    (0x1E3A, 'M', u'ḻ'),\n    (0x1E3B, 'V'),\n    (0x1E3C, 'M', u'ḽ'),\n    (0x1E3D, 'V'),\n    (0x1E3E, 'M', u'ḿ'),\n    (0x1E3F, 'V'),\n    ]\n\ndef _seg_17():\n    return [\n    (0x1E40, 'M', u'ṁ'),\n    (0x1E41, 'V'),\n    (0x1E42, 'M', u'ṃ'),\n    (0x1E43, 'V'),\n    (0x1E44, 'M', u'ṅ'),\n    (0x1E45, 'V'),\n    (0x1E46, 'M', u'ṇ'),\n    (0x1E47, 'V'),\n    (0x1E48, 'M', u'ṉ'),\n    (0x1E49, 'V'),\n    (0x1E4A, 'M', u'ṋ'),\n    (0x1E4B, 'V'),\n    (0x1E4C, 'M', u'ṍ'),\n    (0x1E4D, 'V'),\n    (0x1E4E, 'M', u'ṏ'),\n    (0x1E4F, 'V'),\n    (0x1E50, 'M', u'ṑ'),\n    (0x1E51, 'V'),\n    (0x1E52, 'M', u'ṓ'),\n    (0x1E53, 'V'),\n    (0x1E54, 'M', u'ṕ'),\n    (0x1E55, 'V'),\n    (0x1E56, 'M', u'ṗ'),\n    (0x1E57, 'V'),\n    (0x1E58, 'M', u'ṙ'),\n    (0x1E59, 'V'),\n    (0x1E5A, 'M', u'ṛ'),\n    (0x1E5B, 'V'),\n    (0x1E5C, 'M', u'ṝ'),\n    (0x1E5D, 'V'),\n    (0x1E5E, 'M', u'ṟ'),\n    (0x1E5F, 'V'),\n    (0x1E60, 'M', u'ṡ'),\n    (0x1E61, 'V'),\n    (0x1E62, 'M', u'ṣ'),\n    (0x1E63, 'V'),\n    (0x1E64, 'M', u'ṥ'),\n    (0x1E65, 'V'),\n    (0x1E66, 'M', u'ṧ'),\n    (0x1E67, 'V'),\n    (0x1E68, 'M', u'ṩ'),\n    (0x1E69, 'V'),\n    (0x1E6A, 'M', u'ṫ'),\n    (0x1E6B, 'V'),\n    (0x1E6C, 'M', u'ṭ'),\n    (0x1E6D, 'V'),\n    (0x1E6E, 'M', u'ṯ'),\n    (0x1E6F, 'V'),\n    (0x1E70, 'M', u'ṱ'),\n    (0x1E71, 'V'),\n    (0x1E72, 'M', u'ṳ'),\n    (0x1E73, 'V'),\n    (0x1E74, 'M', u'ṵ'),\n    (0x1E75, 'V'),\n    (0x1E76, 'M', u'ṷ'),\n    (0x1E77, 'V'),\n    (0x1E78, 'M', u'ṹ'),\n    (0x1E79, 'V'),\n    (0x1E7A, 'M', u'ṻ'),\n    (0x1E7B, 'V'),\n    (0x1E7C, 'M', u'ṽ'),\n    (0x1E7D, 'V'),\n    (0x1E7E, 'M', u'ṿ'),\n    (0x1E7F, 'V'),\n    (0x1E80, 'M', u'ẁ'),\n    (0x1E81, 'V'),\n    (0x1E82, 'M', u'ẃ'),\n    (0x1E83, 'V'),\n    (0x1E84, 'M', u'ẅ'),\n    (0x1E85, 'V'),\n    (0x1E86, 'M', u'ẇ'),\n    (0x1E87, 'V'),\n    (0x1E88, 'M', u'ẉ'),\n    (0x1E89, 'V'),\n    (0x1E8A, 'M', u'ẋ'),\n    (0x1E8B, 'V'),\n    (0x1E8C, 'M', u'ẍ'),\n    (0x1E8D, 'V'),\n    (0x1E8E, 'M', u'ẏ'),\n    (0x1E8F, 'V'),\n    (0x1E90, 'M', u'ẑ'),\n    (0x1E91, 'V'),\n    (0x1E92, 'M', u'ẓ'),\n    (0x1E93, 'V'),\n    (0x1E94, 'M', u'ẕ'),\n    (0x1E95, 'V'),\n    (0x1E9A, 'M', u'aʾ'),\n    (0x1E9B, 'M', u'ṡ'),\n    (0x1E9C, 'V'),\n    (0x1E9E, 'M', u'ss'),\n    (0x1E9F, 'V'),\n    (0x1EA0, 'M', u'ạ'),\n    (0x1EA1, 'V'),\n    (0x1EA2, 'M', u'ả'),\n    (0x1EA3, 'V'),\n    (0x1EA4, 'M', u'ấ'),\n    (0x1EA5, 'V'),\n    (0x1EA6, 'M', u'ầ'),\n    (0x1EA7, 'V'),\n    (0x1EA8, 'M', u'ẩ'),\n    ]\n\ndef _seg_18():\n    return [\n    (0x1EA9, 'V'),\n    (0x1EAA, 'M', u'ẫ'),\n    (0x1EAB, 'V'),\n    (0x1EAC, 'M', u'ậ'),\n    (0x1EAD, 'V'),\n    (0x1EAE, 'M', u'ắ'),\n    (0x1EAF, 'V'),\n    (0x1EB0, 'M', u'ằ'),\n    (0x1EB1, 'V'),\n    (0x1EB2, 'M', u'ẳ'),\n    (0x1EB3, 'V'),\n    (0x1EB4, 'M', u'ẵ'),\n    (0x1EB5, 'V'),\n    (0x1EB6, 'M', u'ặ'),\n    (0x1EB7, 'V'),\n    (0x1EB8, 'M', u'ẹ'),\n    (0x1EB9, 'V'),\n    (0x1EBA, 'M', u'ẻ'),\n    (0x1EBB, 'V'),\n    (0x1EBC, 'M', u'ẽ'),\n    (0x1EBD, 'V'),\n    (0x1EBE, 'M', u'ế'),\n    (0x1EBF, 'V'),\n    (0x1EC0, 'M', u'ề'),\n    (0x1EC1, 'V'),\n    (0x1EC2, 'M', u'ể'),\n    (0x1EC3, 'V'),\n    (0x1EC4, 'M', u'ễ'),\n    (0x1EC5, 'V'),\n    (0x1EC6, 'M', u'ệ'),\n    (0x1EC7, 'V'),\n    (0x1EC8, 'M', u'ỉ'),\n    (0x1EC9, 'V'),\n    (0x1ECA, 'M', u'ị'),\n    (0x1ECB, 'V'),\n    (0x1ECC, 'M', u'ọ'),\n    (0x1ECD, 'V'),\n    (0x1ECE, 'M', u'ỏ'),\n    (0x1ECF, 'V'),\n    (0x1ED0, 'M', u'ố'),\n    (0x1ED1, 'V'),\n    (0x1ED2, 'M', u'ồ'),\n    (0x1ED3, 'V'),\n    (0x1ED4, 'M', u'ổ'),\n    (0x1ED5, 'V'),\n    (0x1ED6, 'M', u'ỗ'),\n    (0x1ED7, 'V'),\n    (0x1ED8, 'M', u'ộ'),\n    (0x1ED9, 'V'),\n    (0x1EDA, 'M', u'ớ'),\n    (0x1EDB, 'V'),\n    (0x1EDC, 'M', u'ờ'),\n    (0x1EDD, 'V'),\n    (0x1EDE, 'M', u'ở'),\n    (0x1EDF, 'V'),\n    (0x1EE0, 'M', u'ỡ'),\n    (0x1EE1, 'V'),\n    (0x1EE2, 'M', u'ợ'),\n    (0x1EE3, 'V'),\n    (0x1EE4, 'M', u'ụ'),\n    (0x1EE5, 'V'),\n    (0x1EE6, 'M', u'ủ'),\n    (0x1EE7, 'V'),\n    (0x1EE8, 'M', u'ứ'),\n    (0x1EE9, 'V'),\n    (0x1EEA, 'M', u'ừ'),\n    (0x1EEB, 'V'),\n    (0x1EEC, 'M', u'ử'),\n    (0x1EED, 'V'),\n    (0x1EEE, 'M', u'ữ'),\n    (0x1EEF, 'V'),\n    (0x1EF0, 'M', u'ự'),\n    (0x1EF1, 'V'),\n    (0x1EF2, 'M', u'ỳ'),\n    (0x1EF3, 'V'),\n    (0x1EF4, 'M', u'ỵ'),\n    (0x1EF5, 'V'),\n    (0x1EF6, 'M', u'ỷ'),\n    (0x1EF7, 'V'),\n    (0x1EF8, 'M', u'ỹ'),\n    (0x1EF9, 'V'),\n    (0x1EFA, 'M', u'ỻ'),\n    (0x1EFB, 'V'),\n    (0x1EFC, 'M', u'ỽ'),\n    (0x1EFD, 'V'),\n    (0x1EFE, 'M', u'ỿ'),\n    (0x1EFF, 'V'),\n    (0x1F08, 'M', u'ἀ'),\n    (0x1F09, 'M', u'ἁ'),\n    (0x1F0A, 'M', u'ἂ'),\n    (0x1F0B, 'M', u'ἃ'),\n    (0x1F0C, 'M', u'ἄ'),\n    (0x1F0D, 'M', u'ἅ'),\n    (0x1F0E, 'M', u'ἆ'),\n    (0x1F0F, 'M', u'ἇ'),\n    (0x1F10, 'V'),\n    (0x1F16, 'X'),\n    (0x1F18, 'M', u'ἐ'),\n    (0x1F19, 'M', u'ἑ'),\n    (0x1F1A, 'M', u'ἒ'),\n    ]\n\ndef _seg_19():\n    return [\n    (0x1F1B, 'M', u'ἓ'),\n    (0x1F1C, 'M', u'ἔ'),\n    (0x1F1D, 'M', u'ἕ'),\n    (0x1F1E, 'X'),\n    (0x1F20, 'V'),\n    (0x1F28, 'M', u'ἠ'),\n    (0x1F29, 'M', u'ἡ'),\n    (0x1F2A, 'M', u'ἢ'),\n    (0x1F2B, 'M', u'ἣ'),\n    (0x1F2C, 'M', u'ἤ'),\n    (0x1F2D, 'M', u'ἥ'),\n    (0x1F2E, 'M', u'ἦ'),\n    (0x1F2F, 'M', u'ἧ'),\n    (0x1F30, 'V'),\n    (0x1F38, 'M', u'ἰ'),\n    (0x1F39, 'M', u'ἱ'),\n    (0x1F3A, 'M', u'ἲ'),\n    (0x1F3B, 'M', u'ἳ'),\n    (0x1F3C, 'M', u'ἴ'),\n    (0x1F3D, 'M', u'ἵ'),\n    (0x1F3E, 'M', u'ἶ'),\n    (0x1F3F, 'M', u'ἷ'),\n    (0x1F40, 'V'),\n    (0x1F46, 'X'),\n    (0x1F48, 'M', u'ὀ'),\n    (0x1F49, 'M', u'ὁ'),\n    (0x1F4A, 'M', u'ὂ'),\n    (0x1F4B, 'M', u'ὃ'),\n    (0x1F4C, 'M', u'ὄ'),\n    (0x1F4D, 'M', u'ὅ'),\n    (0x1F4E, 'X'),\n    (0x1F50, 'V'),\n    (0x1F58, 'X'),\n    (0x1F59, 'M', u'ὑ'),\n    (0x1F5A, 'X'),\n    (0x1F5B, 'M', u'ὓ'),\n    (0x1F5C, 'X'),\n    (0x1F5D, 'M', u'ὕ'),\n    (0x1F5E, 'X'),\n    (0x1F5F, 'M', u'ὗ'),\n    (0x1F60, 'V'),\n    (0x1F68, 'M', u'ὠ'),\n    (0x1F69, 'M', u'ὡ'),\n    (0x1F6A, 'M', u'ὢ'),\n    (0x1F6B, 'M', u'ὣ'),\n    (0x1F6C, 'M', u'ὤ'),\n    (0x1F6D, 'M', u'ὥ'),\n    (0x1F6E, 'M', u'ὦ'),\n    (0x1F6F, 'M', u'ὧ'),\n    (0x1F70, 'V'),\n    (0x1F71, 'M', u'ά'),\n    (0x1F72, 'V'),\n    (0x1F73, 'M', u'έ'),\n    (0x1F74, 'V'),\n    (0x1F75, 'M', u'ή'),\n    (0x1F76, 'V'),\n    (0x1F77, 'M', u'ί'),\n    (0x1F78, 'V'),\n    (0x1F79, 'M', u'ό'),\n    (0x1F7A, 'V'),\n    (0x1F7B, 'M', u'ύ'),\n    (0x1F7C, 'V'),\n    (0x1F7D, 'M', u'ώ'),\n    (0x1F7E, 'X'),\n    (0x1F80, 'M', u'ἀι'),\n    (0x1F81, 'M', u'ἁι'),\n    (0x1F82, 'M', u'ἂι'),\n    (0x1F83, 'M', u'ἃι'),\n    (0x1F84, 'M', u'ἄι'),\n    (0x1F85, 'M', u'ἅι'),\n    (0x1F86, 'M', u'ἆι'),\n    (0x1F87, 'M', u'ἇι'),\n    (0x1F88, 'M', u'ἀι'),\n    (0x1F89, 'M', u'ἁι'),\n    (0x1F8A, 'M', u'ἂι'),\n    (0x1F8B, 'M', u'ἃι'),\n    (0x1F8C, 'M', u'ἄι'),\n    (0x1F8D, 'M', u'ἅι'),\n    (0x1F8E, 'M', u'ἆι'),\n    (0x1F8F, 'M', u'ἇι'),\n    (0x1F90, 'M', u'ἠι'),\n    (0x1F91, 'M', u'ἡι'),\n    (0x1F92, 'M', u'ἢι'),\n    (0x1F93, 'M', u'ἣι'),\n    (0x1F94, 'M', u'ἤι'),\n    (0x1F95, 'M', u'ἥι'),\n    (0x1F96, 'M', u'ἦι'),\n    (0x1F97, 'M', u'ἧι'),\n    (0x1F98, 'M', u'ἠι'),\n    (0x1F99, 'M', u'ἡι'),\n    (0x1F9A, 'M', u'ἢι'),\n    (0x1F9B, 'M', u'ἣι'),\n    (0x1F9C, 'M', u'ἤι'),\n    (0x1F9D, 'M', u'ἥι'),\n    (0x1F9E, 'M', u'ἦι'),\n    (0x1F9F, 'M', u'ἧι'),\n    (0x1FA0, 'M', u'ὠι'),\n    (0x1FA1, 'M', u'ὡι'),\n    (0x1FA2, 'M', u'ὢι'),\n    (0x1FA3, 'M', u'ὣι'),\n    ]\n\ndef _seg_20():\n    return [\n    (0x1FA4, 'M', u'ὤι'),\n    (0x1FA5, 'M', u'ὥι'),\n    (0x1FA6, 'M', u'ὦι'),\n    (0x1FA7, 'M', u'ὧι'),\n    (0x1FA8, 'M', u'ὠι'),\n    (0x1FA9, 'M', u'ὡι'),\n    (0x1FAA, 'M', u'ὢι'),\n    (0x1FAB, 'M', u'ὣι'),\n    (0x1FAC, 'M', u'ὤι'),\n    (0x1FAD, 'M', u'ὥι'),\n    (0x1FAE, 'M', u'ὦι'),\n    (0x1FAF, 'M', u'ὧι'),\n    (0x1FB0, 'V'),\n    (0x1FB2, 'M', u'ὰι'),\n    (0x1FB3, 'M', u'αι'),\n    (0x1FB4, 'M', u'άι'),\n    (0x1FB5, 'X'),\n    (0x1FB6, 'V'),\n    (0x1FB7, 'M', u'ᾶι'),\n    (0x1FB8, 'M', u'ᾰ'),\n    (0x1FB9, 'M', u'ᾱ'),\n    (0x1FBA, 'M', u'ὰ'),\n    (0x1FBB, 'M', u'ά'),\n    (0x1FBC, 'M', u'αι'),\n    (0x1FBD, '3', u' ̓'),\n    (0x1FBE, 'M', u'ι'),\n    (0x1FBF, '3', u' ̓'),\n    (0x1FC0, '3', u' ͂'),\n    (0x1FC1, '3', u' ̈͂'),\n    (0x1FC2, 'M', u'ὴι'),\n    (0x1FC3, 'M', u'ηι'),\n    (0x1FC4, 'M', u'ήι'),\n    (0x1FC5, 'X'),\n    (0x1FC6, 'V'),\n    (0x1FC7, 'M', u'ῆι'),\n    (0x1FC8, 'M', u'ὲ'),\n    (0x1FC9, 'M', u'έ'),\n    (0x1FCA, 'M', u'ὴ'),\n    (0x1FCB, 'M', u'ή'),\n    (0x1FCC, 'M', u'ηι'),\n    (0x1FCD, '3', u' ̓̀'),\n    (0x1FCE, '3', u' ̓́'),\n    (0x1FCF, '3', u' ̓͂'),\n    (0x1FD0, 'V'),\n    (0x1FD3, 'M', u'ΐ'),\n    (0x1FD4, 'X'),\n    (0x1FD6, 'V'),\n    (0x1FD8, 'M', u'ῐ'),\n    (0x1FD9, 'M', u'ῑ'),\n    (0x1FDA, 'M', u'ὶ'),\n    (0x1FDB, 'M', u'ί'),\n    (0x1FDC, 'X'),\n    (0x1FDD, '3', u' ̔̀'),\n    (0x1FDE, '3', u' ̔́'),\n    (0x1FDF, '3', u' ̔͂'),\n    (0x1FE0, 'V'),\n    (0x1FE3, 'M', u'ΰ'),\n    (0x1FE4, 'V'),\n    (0x1FE8, 'M', u'ῠ'),\n    (0x1FE9, 'M', u'ῡ'),\n    (0x1FEA, 'M', u'ὺ'),\n    (0x1FEB, 'M', u'ύ'),\n    (0x1FEC, 'M', u'ῥ'),\n    (0x1FED, '3', u' ̈̀'),\n    (0x1FEE, '3', u' ̈́'),\n    (0x1FEF, '3', u'`'),\n    (0x1FF0, 'X'),\n    (0x1FF2, 'M', u'ὼι'),\n    (0x1FF3, 'M', u'ωι'),\n    (0x1FF4, 'M', u'ώι'),\n    (0x1FF5, 'X'),\n    (0x1FF6, 'V'),\n    (0x1FF7, 'M', u'ῶι'),\n    (0x1FF8, 'M', u'ὸ'),\n    (0x1FF9, 'M', u'ό'),\n    (0x1FFA, 'M', u'ὼ'),\n    (0x1FFB, 'M', u'ώ'),\n    (0x1FFC, 'M', u'ωι'),\n    (0x1FFD, '3', u' ́'),\n    (0x1FFE, '3', u' ̔'),\n    (0x1FFF, 'X'),\n    (0x2000, '3', u' '),\n    (0x200B, 'I'),\n    (0x200C, 'D', u''),\n    (0x200E, 'X'),\n    (0x2010, 'V'),\n    (0x2011, 'M', u'‐'),\n    (0x2012, 'V'),\n    (0x2017, '3', u' ̳'),\n    (0x2018, 'V'),\n    (0x2024, 'X'),\n    (0x2027, 'V'),\n    (0x2028, 'X'),\n    (0x202F, '3', u' '),\n    (0x2030, 'V'),\n    (0x2033, 'M', u'′′'),\n    (0x2034, 'M', u'′′′'),\n    (0x2035, 'V'),\n    (0x2036, 'M', u'‵‵'),\n    (0x2037, 'M', u'‵‵‵'),\n    ]\n\ndef _seg_21():\n    return [\n    (0x2038, 'V'),\n    (0x203C, '3', u'!!'),\n    (0x203D, 'V'),\n    (0x203E, '3', u' ̅'),\n    (0x203F, 'V'),\n    (0x2047, '3', u'??'),\n    (0x2048, '3', u'?!'),\n    (0x2049, '3', u'!?'),\n    (0x204A, 'V'),\n    (0x2057, 'M', u'′′′′'),\n    (0x2058, 'V'),\n    (0x205F, '3', u' '),\n    (0x2060, 'I'),\n    (0x2061, 'X'),\n    (0x2064, 'I'),\n    (0x2065, 'X'),\n    (0x2070, 'M', u'0'),\n    (0x2071, 'M', u'i'),\n    (0x2072, 'X'),\n    (0x2074, 'M', u'4'),\n    (0x2075, 'M', u'5'),\n    (0x2076, 'M', u'6'),\n    (0x2077, 'M', u'7'),\n    (0x2078, 'M', u'8'),\n    (0x2079, 'M', u'9'),\n    (0x207A, '3', u'+'),\n    (0x207B, 'M', u'−'),\n    (0x207C, '3', u'='),\n    (0x207D, '3', u'('),\n    (0x207E, '3', u')'),\n    (0x207F, 'M', u'n'),\n    (0x2080, 'M', u'0'),\n    (0x2081, 'M', u'1'),\n    (0x2082, 'M', u'2'),\n    (0x2083, 'M', u'3'),\n    (0x2084, 'M', u'4'),\n    (0x2085, 'M', u'5'),\n    (0x2086, 'M', u'6'),\n    (0x2087, 'M', u'7'),\n    (0x2088, 'M', u'8'),\n    (0x2089, 'M', u'9'),\n    (0x208A, '3', u'+'),\n    (0x208B, 'M', u'−'),\n    (0x208C, '3', u'='),\n    (0x208D, '3', u'('),\n    (0x208E, '3', u')'),\n    (0x208F, 'X'),\n    (0x2090, 'M', u'a'),\n    (0x2091, 'M', u'e'),\n    (0x2092, 'M', u'o'),\n    (0x2093, 'M', u'x'),\n    (0x2094, 'M', u'ə'),\n    (0x2095, 'M', u'h'),\n    (0x2096, 'M', u'k'),\n    (0x2097, 'M', u'l'),\n    (0x2098, 'M', u'm'),\n    (0x2099, 'M', u'n'),\n    (0x209A, 'M', u'p'),\n    (0x209B, 'M', u's'),\n    (0x209C, 'M', u't'),\n    (0x209D, 'X'),\n    (0x20A0, 'V'),\n    (0x20A8, 'M', u'rs'),\n    (0x20A9, 'V'),\n    (0x20C0, 'X'),\n    (0x20D0, 'V'),\n    (0x20F1, 'X'),\n    (0x2100, '3', u'a/c'),\n    (0x2101, '3', u'a/s'),\n    (0x2102, 'M', u'c'),\n    (0x2103, 'M', u'°c'),\n    (0x2104, 'V'),\n    (0x2105, '3', u'c/o'),\n    (0x2106, '3', u'c/u'),\n    (0x2107, 'M', u'ɛ'),\n    (0x2108, 'V'),\n    (0x2109, 'M', u'°f'),\n    (0x210A, 'M', u'g'),\n    (0x210B, 'M', u'h'),\n    (0x210F, 'M', u'ħ'),\n    (0x2110, 'M', u'i'),\n    (0x2112, 'M', u'l'),\n    (0x2114, 'V'),\n    (0x2115, 'M', u'n'),\n    (0x2116, 'M', u'no'),\n    (0x2117, 'V'),\n    (0x2119, 'M', u'p'),\n    (0x211A, 'M', u'q'),\n    (0x211B, 'M', u'r'),\n    (0x211E, 'V'),\n    (0x2120, 'M', u'sm'),\n    (0x2121, 'M', u'tel'),\n    (0x2122, 'M', u'tm'),\n    (0x2123, 'V'),\n    (0x2124, 'M', u'z'),\n    (0x2125, 'V'),\n    (0x2126, 'M', u'ω'),\n    (0x2127, 'V'),\n    (0x2128, 'M', u'z'),\n    (0x2129, 'V'),\n    ]\n\ndef _seg_22():\n    return [\n    (0x212A, 'M', u'k'),\n    (0x212B, 'M', u'å'),\n    (0x212C, 'M', u'b'),\n    (0x212D, 'M', u'c'),\n    (0x212E, 'V'),\n    (0x212F, 'M', u'e'),\n    (0x2131, 'M', u'f'),\n    (0x2132, 'X'),\n    (0x2133, 'M', u'm'),\n    (0x2134, 'M', u'o'),\n    (0x2135, 'M', u'א'),\n    (0x2136, 'M', u'ב'),\n    (0x2137, 'M', u'ג'),\n    (0x2138, 'M', u'ד'),\n    (0x2139, 'M', u'i'),\n    (0x213A, 'V'),\n    (0x213B, 'M', u'fax'),\n    (0x213C, 'M', u'π'),\n    (0x213D, 'M', u'γ'),\n    (0x213F, 'M', u'π'),\n    (0x2140, 'M', u'∑'),\n    (0x2141, 'V'),\n    (0x2145, 'M', u'd'),\n    (0x2147, 'M', u'e'),\n    (0x2148, 'M', u'i'),\n    (0x2149, 'M', u'j'),\n    (0x214A, 'V'),\n    (0x2150, 'M', u'1⁄7'),\n    (0x2151, 'M', u'1⁄9'),\n    (0x2152, 'M', u'1⁄10'),\n    (0x2153, 'M', u'1⁄3'),\n    (0x2154, 'M', u'2⁄3'),\n    (0x2155, 'M', u'1⁄5'),\n    (0x2156, 'M', u'2⁄5'),\n    (0x2157, 'M', u'3⁄5'),\n    (0x2158, 'M', u'4⁄5'),\n    (0x2159, 'M', u'1⁄6'),\n    (0x215A, 'M', u'5⁄6'),\n    (0x215B, 'M', u'1⁄8'),\n    (0x215C, 'M', u'3⁄8'),\n    (0x215D, 'M', u'5⁄8'),\n    (0x215E, 'M', u'7⁄8'),\n    (0x215F, 'M', u'1⁄'),\n    (0x2160, 'M', u'i'),\n    (0x2161, 'M', u'ii'),\n    (0x2162, 'M', u'iii'),\n    (0x2163, 'M', u'iv'),\n    (0x2164, 'M', u'v'),\n    (0x2165, 'M', u'vi'),\n    (0x2166, 'M', u'vii'),\n    (0x2167, 'M', u'viii'),\n    (0x2168, 'M', u'ix'),\n    (0x2169, 'M', u'x'),\n    (0x216A, 'M', u'xi'),\n    (0x216B, 'M', u'xii'),\n    (0x216C, 'M', u'l'),\n    (0x216D, 'M', u'c'),\n    (0x216E, 'M', u'd'),\n    (0x216F, 'M', u'm'),\n    (0x2170, 'M', u'i'),\n    (0x2171, 'M', u'ii'),\n    (0x2172, 'M', u'iii'),\n    (0x2173, 'M', u'iv'),\n    (0x2174, 'M', u'v'),\n    (0x2175, 'M', u'vi'),\n    (0x2176, 'M', u'vii'),\n    (0x2177, 'M', u'viii'),\n    (0x2178, 'M', u'ix'),\n    (0x2179, 'M', u'x'),\n    (0x217A, 'M', u'xi'),\n    (0x217B, 'M', u'xii'),\n    (0x217C, 'M', u'l'),\n    (0x217D, 'M', u'c'),\n    (0x217E, 'M', u'd'),\n    (0x217F, 'M', u'm'),\n    (0x2180, 'V'),\n    (0x2183, 'X'),\n    (0x2184, 'V'),\n    (0x2189, 'M', u'0⁄3'),\n    (0x218A, 'V'),\n    (0x218C, 'X'),\n    (0x2190, 'V'),\n    (0x222C, 'M', u'∫∫'),\n    (0x222D, 'M', u'∫∫∫'),\n    (0x222E, 'V'),\n    (0x222F, 'M', u'∮∮'),\n    (0x2230, 'M', u'∮∮∮'),\n    (0x2231, 'V'),\n    (0x2260, '3'),\n    (0x2261, 'V'),\n    (0x226E, '3'),\n    (0x2270, 'V'),\n    (0x2329, 'M', u'〈'),\n    (0x232A, 'M', u'〉'),\n    (0x232B, 'V'),\n    (0x2427, 'X'),\n    (0x2440, 'V'),\n    (0x244B, 'X'),\n    (0x2460, 'M', u'1'),\n    (0x2461, 'M', u'2'),\n    ]\n\ndef _seg_23():\n    return [\n    (0x2462, 'M', u'3'),\n    (0x2463, 'M', u'4'),\n    (0x2464, 'M', u'5'),\n    (0x2465, 'M', u'6'),\n    (0x2466, 'M', u'7'),\n    (0x2467, 'M', u'8'),\n    (0x2468, 'M', u'9'),\n    (0x2469, 'M', u'10'),\n    (0x246A, 'M', u'11'),\n    (0x246B, 'M', u'12'),\n    (0x246C, 'M', u'13'),\n    (0x246D, 'M', u'14'),\n    (0x246E, 'M', u'15'),\n    (0x246F, 'M', u'16'),\n    (0x2470, 'M', u'17'),\n    (0x2471, 'M', u'18'),\n    (0x2472, 'M', u'19'),\n    (0x2473, 'M', u'20'),\n    (0x2474, '3', u'(1)'),\n    (0x2475, '3', u'(2)'),\n    (0x2476, '3', u'(3)'),\n    (0x2477, '3', u'(4)'),\n    (0x2478, '3', u'(5)'),\n    (0x2479, '3', u'(6)'),\n    (0x247A, '3', u'(7)'),\n    (0x247B, '3', u'(8)'),\n    (0x247C, '3', u'(9)'),\n    (0x247D, '3', u'(10)'),\n    (0x247E, '3', u'(11)'),\n    (0x247F, '3', u'(12)'),\n    (0x2480, '3', u'(13)'),\n    (0x2481, '3', u'(14)'),\n    (0x2482, '3', u'(15)'),\n    (0x2483, '3', u'(16)'),\n    (0x2484, '3', u'(17)'),\n    (0x2485, '3', u'(18)'),\n    (0x2486, '3', u'(19)'),\n    (0x2487, '3', u'(20)'),\n    (0x2488, 'X'),\n    (0x249C, '3', u'(a)'),\n    (0x249D, '3', u'(b)'),\n    (0x249E, '3', u'(c)'),\n    (0x249F, '3', u'(d)'),\n    (0x24A0, '3', u'(e)'),\n    (0x24A1, '3', u'(f)'),\n    (0x24A2, '3', u'(g)'),\n    (0x24A3, '3', u'(h)'),\n    (0x24A4, '3', u'(i)'),\n    (0x24A5, '3', u'(j)'),\n    (0x24A6, '3', u'(k)'),\n    (0x24A7, '3', u'(l)'),\n    (0x24A8, '3', u'(m)'),\n    (0x24A9, '3', u'(n)'),\n    (0x24AA, '3', u'(o)'),\n    (0x24AB, '3', u'(p)'),\n    (0x24AC, '3', u'(q)'),\n    (0x24AD, '3', u'(r)'),\n    (0x24AE, '3', u'(s)'),\n    (0x24AF, '3', u'(t)'),\n    (0x24B0, '3', u'(u)'),\n    (0x24B1, '3', u'(v)'),\n    (0x24B2, '3', u'(w)'),\n    (0x24B3, '3', u'(x)'),\n    (0x24B4, '3', u'(y)'),\n    (0x24B5, '3', u'(z)'),\n    (0x24B6, 'M', u'a'),\n    (0x24B7, 'M', u'b'),\n    (0x24B8, 'M', u'c'),\n    (0x24B9, 'M', u'd'),\n    (0x24BA, 'M', u'e'),\n    (0x24BB, 'M', u'f'),\n    (0x24BC, 'M', u'g'),\n    (0x24BD, 'M', u'h'),\n    (0x24BE, 'M', u'i'),\n    (0x24BF, 'M', u'j'),\n    (0x24C0, 'M', u'k'),\n    (0x24C1, 'M', u'l'),\n    (0x24C2, 'M', u'm'),\n    (0x24C3, 'M', u'n'),\n    (0x24C4, 'M', u'o'),\n    (0x24C5, 'M', u'p'),\n    (0x24C6, 'M', u'q'),\n    (0x24C7, 'M', u'r'),\n    (0x24C8, 'M', u's'),\n    (0x24C9, 'M', u't'),\n    (0x24CA, 'M', u'u'),\n    (0x24CB, 'M', u'v'),\n    (0x24CC, 'M', u'w'),\n    (0x24CD, 'M', u'x'),\n    (0x24CE, 'M', u'y'),\n    (0x24CF, 'M', u'z'),\n    (0x24D0, 'M', u'a'),\n    (0x24D1, 'M', u'b'),\n    (0x24D2, 'M', u'c'),\n    (0x24D3, 'M', u'd'),\n    (0x24D4, 'M', u'e'),\n    (0x24D5, 'M', u'f'),\n    (0x24D6, 'M', u'g'),\n    (0x24D7, 'M', u'h'),\n    (0x24D8, 'M', u'i'),\n    ]\n\ndef _seg_24():\n    return [\n    (0x24D9, 'M', u'j'),\n    (0x24DA, 'M', u'k'),\n    (0x24DB, 'M', u'l'),\n    (0x24DC, 'M', u'm'),\n    (0x24DD, 'M', u'n'),\n    (0x24DE, 'M', u'o'),\n    (0x24DF, 'M', u'p'),\n    (0x24E0, 'M', u'q'),\n    (0x24E1, 'M', u'r'),\n    (0x24E2, 'M', u's'),\n    (0x24E3, 'M', u't'),\n    (0x24E4, 'M', u'u'),\n    (0x24E5, 'M', u'v'),\n    (0x24E6, 'M', u'w'),\n    (0x24E7, 'M', u'x'),\n    (0x24E8, 'M', u'y'),\n    (0x24E9, 'M', u'z'),\n    (0x24EA, 'M', u'0'),\n    (0x24EB, 'V'),\n    (0x2A0C, 'M', u'∫∫∫∫'),\n    (0x2A0D, 'V'),\n    (0x2A74, '3', u'::='),\n    (0x2A75, '3', u'=='),\n    (0x2A76, '3', u'==='),\n    (0x2A77, 'V'),\n    (0x2ADC, 'M', u'⫝̸'),\n    (0x2ADD, 'V'),\n    (0x2B74, 'X'),\n    (0x2B76, 'V'),\n    (0x2B96, 'X'),\n    (0x2B98, 'V'),\n    (0x2BC9, 'X'),\n    (0x2BCA, 'V'),\n    (0x2BFF, 'X'),\n    (0x2C00, 'M', u'ⰰ'),\n    (0x2C01, 'M', u'ⰱ'),\n    (0x2C02, 'M', u'ⰲ'),\n    (0x2C03, 'M', u'ⰳ'),\n    (0x2C04, 'M', u'ⰴ'),\n    (0x2C05, 'M', u'ⰵ'),\n    (0x2C06, 'M', u'ⰶ'),\n    (0x2C07, 'M', u'ⰷ'),\n    (0x2C08, 'M', u'ⰸ'),\n    (0x2C09, 'M', u'ⰹ'),\n    (0x2C0A, 'M', u'ⰺ'),\n    (0x2C0B, 'M', u'ⰻ'),\n    (0x2C0C, 'M', u'ⰼ'),\n    (0x2C0D, 'M', u'ⰽ'),\n    (0x2C0E, 'M', u'ⰾ'),\n    (0x2C0F, 'M', u'ⰿ'),\n    (0x2C10, 'M', u'ⱀ'),\n    (0x2C11, 'M', u'ⱁ'),\n    (0x2C12, 'M', u'ⱂ'),\n    (0x2C13, 'M', u'ⱃ'),\n    (0x2C14, 'M', u'ⱄ'),\n    (0x2C15, 'M', u'ⱅ'),\n    (0x2C16, 'M', u'ⱆ'),\n    (0x2C17, 'M', u'ⱇ'),\n    (0x2C18, 'M', u'ⱈ'),\n    (0x2C19, 'M', u'ⱉ'),\n    (0x2C1A, 'M', u'ⱊ'),\n    (0x2C1B, 'M', u'ⱋ'),\n    (0x2C1C, 'M', u'ⱌ'),\n    (0x2C1D, 'M', u'ⱍ'),\n    (0x2C1E, 'M', u'ⱎ'),\n    (0x2C1F, 'M', u'ⱏ'),\n    (0x2C20, 'M', u'ⱐ'),\n    (0x2C21, 'M', u'ⱑ'),\n    (0x2C22, 'M', u'ⱒ'),\n    (0x2C23, 'M', u'ⱓ'),\n    (0x2C24, 'M', u'ⱔ'),\n    (0x2C25, 'M', u'ⱕ'),\n    (0x2C26, 'M', u'ⱖ'),\n    (0x2C27, 'M', u'ⱗ'),\n    (0x2C28, 'M', u'ⱘ'),\n    (0x2C29, 'M', u'ⱙ'),\n    (0x2C2A, 'M', u'ⱚ'),\n    (0x2C2B, 'M', u'ⱛ'),\n    (0x2C2C, 'M', u'ⱜ'),\n    (0x2C2D, 'M', u'ⱝ'),\n    (0x2C2E, 'M', u'ⱞ'),\n    (0x2C2F, 'X'),\n    (0x2C30, 'V'),\n    (0x2C5F, 'X'),\n    (0x2C60, 'M', u'ⱡ'),\n    (0x2C61, 'V'),\n    (0x2C62, 'M', u'ɫ'),\n    (0x2C63, 'M', u'ᵽ'),\n    (0x2C64, 'M', u'ɽ'),\n    (0x2C65, 'V'),\n    (0x2C67, 'M', u'ⱨ'),\n    (0x2C68, 'V'),\n    (0x2C69, 'M', u'ⱪ'),\n    (0x2C6A, 'V'),\n    (0x2C6B, 'M', u'ⱬ'),\n    (0x2C6C, 'V'),\n    (0x2C6D, 'M', u'ɑ'),\n    (0x2C6E, 'M', u'ɱ'),\n    (0x2C6F, 'M', u'ɐ'),\n    (0x2C70, 'M', u'ɒ'),\n    ]\n\ndef _seg_25():\n    return [\n    (0x2C71, 'V'),\n    (0x2C72, 'M', u'ⱳ'),\n    (0x2C73, 'V'),\n    (0x2C75, 'M', u'ⱶ'),\n    (0x2C76, 'V'),\n    (0x2C7C, 'M', u'j'),\n    (0x2C7D, 'M', u'v'),\n    (0x2C7E, 'M', u'ȿ'),\n    (0x2C7F, 'M', u'ɀ'),\n    (0x2C80, 'M', u'ⲁ'),\n    (0x2C81, 'V'),\n    (0x2C82, 'M', u'ⲃ'),\n    (0x2C83, 'V'),\n    (0x2C84, 'M', u'ⲅ'),\n    (0x2C85, 'V'),\n    (0x2C86, 'M', u'ⲇ'),\n    (0x2C87, 'V'),\n    (0x2C88, 'M', u'ⲉ'),\n    (0x2C89, 'V'),\n    (0x2C8A, 'M', u'ⲋ'),\n    (0x2C8B, 'V'),\n    (0x2C8C, 'M', u'ⲍ'),\n    (0x2C8D, 'V'),\n    (0x2C8E, 'M', u'ⲏ'),\n    (0x2C8F, 'V'),\n    (0x2C90, 'M', u'ⲑ'),\n    (0x2C91, 'V'),\n    (0x2C92, 'M', u'ⲓ'),\n    (0x2C93, 'V'),\n    (0x2C94, 'M', u'ⲕ'),\n    (0x2C95, 'V'),\n    (0x2C96, 'M', u'ⲗ'),\n    (0x2C97, 'V'),\n    (0x2C98, 'M', u'ⲙ'),\n    (0x2C99, 'V'),\n    (0x2C9A, 'M', u'ⲛ'),\n    (0x2C9B, 'V'),\n    (0x2C9C, 'M', u'ⲝ'),\n    (0x2C9D, 'V'),\n    (0x2C9E, 'M', u'ⲟ'),\n    (0x2C9F, 'V'),\n    (0x2CA0, 'M', u'ⲡ'),\n    (0x2CA1, 'V'),\n    (0x2CA2, 'M', u'ⲣ'),\n    (0x2CA3, 'V'),\n    (0x2CA4, 'M', u'ⲥ'),\n    (0x2CA5, 'V'),\n    (0x2CA6, 'M', u'ⲧ'),\n    (0x2CA7, 'V'),\n    (0x2CA8, 'M', u'ⲩ'),\n    (0x2CA9, 'V'),\n    (0x2CAA, 'M', u'ⲫ'),\n    (0x2CAB, 'V'),\n    (0x2CAC, 'M', u'ⲭ'),\n    (0x2CAD, 'V'),\n    (0x2CAE, 'M', u'ⲯ'),\n    (0x2CAF, 'V'),\n    (0x2CB0, 'M', u'ⲱ'),\n    (0x2CB1, 'V'),\n    (0x2CB2, 'M', u'ⲳ'),\n    (0x2CB3, 'V'),\n    (0x2CB4, 'M', u'ⲵ'),\n    (0x2CB5, 'V'),\n    (0x2CB6, 'M', u'ⲷ'),\n    (0x2CB7, 'V'),\n    (0x2CB8, 'M', u'ⲹ'),\n    (0x2CB9, 'V'),\n    (0x2CBA, 'M', u'ⲻ'),\n    (0x2CBB, 'V'),\n    (0x2CBC, 'M', u'ⲽ'),\n    (0x2CBD, 'V'),\n    (0x2CBE, 'M', u'ⲿ'),\n    (0x2CBF, 'V'),\n    (0x2CC0, 'M', u'ⳁ'),\n    (0x2CC1, 'V'),\n    (0x2CC2, 'M', u'ⳃ'),\n    (0x2CC3, 'V'),\n    (0x2CC4, 'M', u'ⳅ'),\n    (0x2CC5, 'V'),\n    (0x2CC6, 'M', u'ⳇ'),\n    (0x2CC7, 'V'),\n    (0x2CC8, 'M', u'ⳉ'),\n    (0x2CC9, 'V'),\n    (0x2CCA, 'M', u'ⳋ'),\n    (0x2CCB, 'V'),\n    (0x2CCC, 'M', u'ⳍ'),\n    (0x2CCD, 'V'),\n    (0x2CCE, 'M', u'ⳏ'),\n    (0x2CCF, 'V'),\n    (0x2CD0, 'M', u'ⳑ'),\n    (0x2CD1, 'V'),\n    (0x2CD2, 'M', u'ⳓ'),\n    (0x2CD3, 'V'),\n    (0x2CD4, 'M', u'ⳕ'),\n    (0x2CD5, 'V'),\n    (0x2CD6, 'M', u'ⳗ'),\n    (0x2CD7, 'V'),\n    (0x2CD8, 'M', u'ⳙ'),\n    (0x2CD9, 'V'),\n    (0x2CDA, 'M', u'ⳛ'),\n    ]\n\ndef _seg_26():\n    return [\n    (0x2CDB, 'V'),\n    (0x2CDC, 'M', u'ⳝ'),\n    (0x2CDD, 'V'),\n    (0x2CDE, 'M', u'ⳟ'),\n    (0x2CDF, 'V'),\n    (0x2CE0, 'M', u'ⳡ'),\n    (0x2CE1, 'V'),\n    (0x2CE2, 'M', u'ⳣ'),\n    (0x2CE3, 'V'),\n    (0x2CEB, 'M', u'ⳬ'),\n    (0x2CEC, 'V'),\n    (0x2CED, 'M', u'ⳮ'),\n    (0x2CEE, 'V'),\n    (0x2CF2, 'M', u'ⳳ'),\n    (0x2CF3, 'V'),\n    (0x2CF4, 'X'),\n    (0x2CF9, 'V'),\n    (0x2D26, 'X'),\n    (0x2D27, 'V'),\n    (0x2D28, 'X'),\n    (0x2D2D, 'V'),\n    (0x2D2E, 'X'),\n    (0x2D30, 'V'),\n    (0x2D68, 'X'),\n    (0x2D6F, 'M', u'ⵡ'),\n    (0x2D70, 'V'),\n    (0x2D71, 'X'),\n    (0x2D7F, 'V'),\n    (0x2D97, 'X'),\n    (0x2DA0, 'V'),\n    (0x2DA7, 'X'),\n    (0x2DA8, 'V'),\n    (0x2DAF, 'X'),\n    (0x2DB0, 'V'),\n    (0x2DB7, 'X'),\n    (0x2DB8, 'V'),\n    (0x2DBF, 'X'),\n    (0x2DC0, 'V'),\n    (0x2DC7, 'X'),\n    (0x2DC8, 'V'),\n    (0x2DCF, 'X'),\n    (0x2DD0, 'V'),\n    (0x2DD7, 'X'),\n    (0x2DD8, 'V'),\n    (0x2DDF, 'X'),\n    (0x2DE0, 'V'),\n    (0x2E4F, 'X'),\n    (0x2E80, 'V'),\n    (0x2E9A, 'X'),\n    (0x2E9B, 'V'),\n    (0x2E9F, 'M', u'母'),\n    (0x2EA0, 'V'),\n    (0x2EF3, 'M', u'龟'),\n    (0x2EF4, 'X'),\n    (0x2F00, 'M', u'一'),\n    (0x2F01, 'M', u'丨'),\n    (0x2F02, 'M', u'丶'),\n    (0x2F03, 'M', u'丿'),\n    (0x2F04, 'M', u'乙'),\n    (0x2F05, 'M', u'亅'),\n    (0x2F06, 'M', u'二'),\n    (0x2F07, 'M', u'亠'),\n    (0x2F08, 'M', u'人'),\n    (0x2F09, 'M', u'儿'),\n    (0x2F0A, 'M', u'入'),\n    (0x2F0B, 'M', u'八'),\n    (0x2F0C, 'M', u'冂'),\n    (0x2F0D, 'M', u'冖'),\n    (0x2F0E, 'M', u'冫'),\n    (0x2F0F, 'M', u'几'),\n    (0x2F10, 'M', u'凵'),\n    (0x2F11, 'M', u'刀'),\n    (0x2F12, 'M', u'力'),\n    (0x2F13, 'M', u'勹'),\n    (0x2F14, 'M', u'匕'),\n    (0x2F15, 'M', u'匚'),\n    (0x2F16, 'M', u'匸'),\n    (0x2F17, 'M', u'十'),\n    (0x2F18, 'M', u'卜'),\n    (0x2F19, 'M', u'卩'),\n    (0x2F1A, 'M', u'厂'),\n    (0x2F1B, 'M', u'厶'),\n    (0x2F1C, 'M', u'又'),\n    (0x2F1D, 'M', u'口'),\n    (0x2F1E, 'M', u'囗'),\n    (0x2F1F, 'M', u'土'),\n    (0x2F20, 'M', u'士'),\n    (0x2F21, 'M', u'夂'),\n    (0x2F22, 'M', u'夊'),\n    (0x2F23, 'M', u'夕'),\n    (0x2F24, 'M', u'大'),\n    (0x2F25, 'M', u'女'),\n    (0x2F26, 'M', u'子'),\n    (0x2F27, 'M', u'宀'),\n    (0x2F28, 'M', u'寸'),\n    (0x2F29, 'M', u'小'),\n    (0x2F2A, 'M', u'尢'),\n    (0x2F2B, 'M', u'尸'),\n    (0x2F2C, 'M', u'屮'),\n    (0x2F2D, 'M', u'山'),\n    ]\n\ndef _seg_27():\n    return [\n    (0x2F2E, 'M', u'巛'),\n    (0x2F2F, 'M', u'工'),\n    (0x2F30, 'M', u'己'),\n    (0x2F31, 'M', u'巾'),\n    (0x2F32, 'M', u'干'),\n    (0x2F33, 'M', u'幺'),\n    (0x2F34, 'M', u'广'),\n    (0x2F35, 'M', u'廴'),\n    (0x2F36, 'M', u'廾'),\n    (0x2F37, 'M', u'弋'),\n    (0x2F38, 'M', u'弓'),\n    (0x2F39, 'M', u'彐'),\n    (0x2F3A, 'M', u'彡'),\n    (0x2F3B, 'M', u'彳'),\n    (0x2F3C, 'M', u'心'),\n    (0x2F3D, 'M', u'戈'),\n    (0x2F3E, 'M', u'戶'),\n    (0x2F3F, 'M', u'手'),\n    (0x2F40, 'M', u'支'),\n    (0x2F41, 'M', u'攴'),\n    (0x2F42, 'M', u'文'),\n    (0x2F43, 'M', u'斗'),\n    (0x2F44, 'M', u'斤'),\n    (0x2F45, 'M', u'方'),\n    (0x2F46, 'M', u'无'),\n    (0x2F47, 'M', u'日'),\n    (0x2F48, 'M', u'曰'),\n    (0x2F49, 'M', u'月'),\n    (0x2F4A, 'M', u'木'),\n    (0x2F4B, 'M', u'欠'),\n    (0x2F4C, 'M', u'止'),\n    (0x2F4D, 'M', u'歹'),\n    (0x2F4E, 'M', u'殳'),\n    (0x2F4F, 'M', u'毋'),\n    (0x2F50, 'M', u'比'),\n    (0x2F51, 'M', u'毛'),\n    (0x2F52, 'M', u'氏'),\n    (0x2F53, 'M', u'气'),\n    (0x2F54, 'M', u'水'),\n    (0x2F55, 'M', u'火'),\n    (0x2F56, 'M', u'爪'),\n    (0x2F57, 'M', u'父'),\n    (0x2F58, 'M', u'爻'),\n    (0x2F59, 'M', u'爿'),\n    (0x2F5A, 'M', u'片'),\n    (0x2F5B, 'M', u'牙'),\n    (0x2F5C, 'M', u'牛'),\n    (0x2F5D, 'M', u'犬'),\n    (0x2F5E, 'M', u'玄'),\n    (0x2F5F, 'M', u'玉'),\n    (0x2F60, 'M', u'瓜'),\n    (0x2F61, 'M', u'瓦'),\n    (0x2F62, 'M', u'甘'),\n    (0x2F63, 'M', u'生'),\n    (0x2F64, 'M', u'用'),\n    (0x2F65, 'M', u'田'),\n    (0x2F66, 'M', u'疋'),\n    (0x2F67, 'M', u'疒'),\n    (0x2F68, 'M', u'癶'),\n    (0x2F69, 'M', u'白'),\n    (0x2F6A, 'M', u'皮'),\n    (0x2F6B, 'M', u'皿'),\n    (0x2F6C, 'M', u'目'),\n    (0x2F6D, 'M', u'矛'),\n    (0x2F6E, 'M', u'矢'),\n    (0x2F6F, 'M', u'石'),\n    (0x2F70, 'M', u'示'),\n    (0x2F71, 'M', u'禸'),\n    (0x2F72, 'M', u'禾'),\n    (0x2F73, 'M', u'穴'),\n    (0x2F74, 'M', u'立'),\n    (0x2F75, 'M', u'竹'),\n    (0x2F76, 'M', u'米'),\n    (0x2F77, 'M', u'糸'),\n    (0x2F78, 'M', u'缶'),\n    (0x2F79, 'M', u'网'),\n    (0x2F7A, 'M', u'羊'),\n    (0x2F7B, 'M', u'羽'),\n    (0x2F7C, 'M', u'老'),\n    (0x2F7D, 'M', u'而'),\n    (0x2F7E, 'M', u'耒'),\n    (0x2F7F, 'M', u'耳'),\n    (0x2F80, 'M', u'聿'),\n    (0x2F81, 'M', u'肉'),\n    (0x2F82, 'M', u'臣'),\n    (0x2F83, 'M', u'自'),\n    (0x2F84, 'M', u'至'),\n    (0x2F85, 'M', u'臼'),\n    (0x2F86, 'M', u'舌'),\n    (0x2F87, 'M', u'舛'),\n    (0x2F88, 'M', u'舟'),\n    (0x2F89, 'M', u'艮'),\n    (0x2F8A, 'M', u'色'),\n    (0x2F8B, 'M', u'艸'),\n    (0x2F8C, 'M', u'虍'),\n    (0x2F8D, 'M', u'虫'),\n    (0x2F8E, 'M', u'血'),\n    (0x2F8F, 'M', u'行'),\n    (0x2F90, 'M', u'衣'),\n    (0x2F91, 'M', u'襾'),\n    ]\n\ndef _seg_28():\n    return [\n    (0x2F92, 'M', u'見'),\n    (0x2F93, 'M', u'角'),\n    (0x2F94, 'M', u'言'),\n    (0x2F95, 'M', u'谷'),\n    (0x2F96, 'M', u'豆'),\n    (0x2F97, 'M', u'豕'),\n    (0x2F98, 'M', u'豸'),\n    (0x2F99, 'M', u'貝'),\n    (0x2F9A, 'M', u'赤'),\n    (0x2F9B, 'M', u'走'),\n    (0x2F9C, 'M', u'足'),\n    (0x2F9D, 'M', u'身'),\n    (0x2F9E, 'M', u'車'),\n    (0x2F9F, 'M', u'辛'),\n    (0x2FA0, 'M', u'辰'),\n    (0x2FA1, 'M', u'辵'),\n    (0x2FA2, 'M', u'邑'),\n    (0x2FA3, 'M', u'酉'),\n    (0x2FA4, 'M', u'釆'),\n    (0x2FA5, 'M', u'里'),\n    (0x2FA6, 'M', u'金'),\n    (0x2FA7, 'M', u'長'),\n    (0x2FA8, 'M', u'門'),\n    (0x2FA9, 'M', u'阜'),\n    (0x2FAA, 'M', u'隶'),\n    (0x2FAB, 'M', u'隹'),\n    (0x2FAC, 'M', u'雨'),\n    (0x2FAD, 'M', u'靑'),\n    (0x2FAE, 'M', u'非'),\n    (0x2FAF, 'M', u'面'),\n    (0x2FB0, 'M', u'革'),\n    (0x2FB1, 'M', u'韋'),\n    (0x2FB2, 'M', u'韭'),\n    (0x2FB3, 'M', u'音'),\n    (0x2FB4, 'M', u'頁'),\n    (0x2FB5, 'M', u'風'),\n    (0x2FB6, 'M', u'飛'),\n    (0x2FB7, 'M', u'食'),\n    (0x2FB8, 'M', u'首'),\n    (0x2FB9, 'M', u'香'),\n    (0x2FBA, 'M', u'馬'),\n    (0x2FBB, 'M', u'骨'),\n    (0x2FBC, 'M', u'高'),\n    (0x2FBD, 'M', u'髟'),\n    (0x2FBE, 'M', u'鬥'),\n    (0x2FBF, 'M', u'鬯'),\n    (0x2FC0, 'M', u'鬲'),\n    (0x2FC1, 'M', u'鬼'),\n    (0x2FC2, 'M', u'魚'),\n    (0x2FC3, 'M', u'鳥'),\n    (0x2FC4, 'M', u'鹵'),\n    (0x2FC5, 'M', u'鹿'),\n    (0x2FC6, 'M', u'麥'),\n    (0x2FC7, 'M', u'麻'),\n    (0x2FC8, 'M', u'黃'),\n    (0x2FC9, 'M', u'黍'),\n    (0x2FCA, 'M', u'黑'),\n    (0x2FCB, 'M', u'黹'),\n    (0x2FCC, 'M', u'黽'),\n    (0x2FCD, 'M', u'鼎'),\n    (0x2FCE, 'M', u'鼓'),\n    (0x2FCF, 'M', u'鼠'),\n    (0x2FD0, 'M', u'鼻'),\n    (0x2FD1, 'M', u'齊'),\n    (0x2FD2, 'M', u'齒'),\n    (0x2FD3, 'M', u'龍'),\n    (0x2FD4, 'M', u'龜'),\n    (0x2FD5, 'M', u'龠'),\n    (0x2FD6, 'X'),\n    (0x3000, '3', u' '),\n    (0x3001, 'V'),\n    (0x3002, 'M', u'.'),\n    (0x3003, 'V'),\n    (0x3036, 'M', u'〒'),\n    (0x3037, 'V'),\n    (0x3038, 'M', u'十'),\n    (0x3039, 'M', u'卄'),\n    (0x303A, 'M', u'卅'),\n    (0x303B, 'V'),\n    (0x3040, 'X'),\n    (0x3041, 'V'),\n    (0x3097, 'X'),\n    (0x3099, 'V'),\n    (0x309B, '3', u' ゙'),\n    (0x309C, '3', u' ゚'),\n    (0x309D, 'V'),\n    (0x309F, 'M', u'より'),\n    (0x30A0, 'V'),\n    (0x30FF, 'M', u'コト'),\n    (0x3100, 'X'),\n    (0x3105, 'V'),\n    (0x3130, 'X'),\n    (0x3131, 'M', u'ᄀ'),\n    (0x3132, 'M', u'ᄁ'),\n    (0x3133, 'M', u'ᆪ'),\n    (0x3134, 'M', u'ᄂ'),\n    (0x3135, 'M', u'ᆬ'),\n    (0x3136, 'M', u'ᆭ'),\n    (0x3137, 'M', u'ᄃ'),\n    (0x3138, 'M', u'ᄄ'),\n    ]\n\ndef _seg_29():\n    return [\n    (0x3139, 'M', u'ᄅ'),\n    (0x313A, 'M', u'ᆰ'),\n    (0x313B, 'M', u'ᆱ'),\n    (0x313C, 'M', u'ᆲ'),\n    (0x313D, 'M', u'ᆳ'),\n    (0x313E, 'M', u'ᆴ'),\n    (0x313F, 'M', u'ᆵ'),\n    (0x3140, 'M', u'ᄚ'),\n    (0x3141, 'M', u'ᄆ'),\n    (0x3142, 'M', u'ᄇ'),\n    (0x3143, 'M', u'ᄈ'),\n    (0x3144, 'M', u'ᄡ'),\n    (0x3145, 'M', u'ᄉ'),\n    (0x3146, 'M', u'ᄊ'),\n    (0x3147, 'M', u'ᄋ'),\n    (0x3148, 'M', u'ᄌ'),\n    (0x3149, 'M', u'ᄍ'),\n    (0x314A, 'M', u'ᄎ'),\n    (0x314B, 'M', u'ᄏ'),\n    (0x314C, 'M', u'ᄐ'),\n    (0x314D, 'M', u'ᄑ'),\n    (0x314E, 'M', u'ᄒ'),\n    (0x314F, 'M', u'ᅡ'),\n    (0x3150, 'M', u'ᅢ'),\n    (0x3151, 'M', u'ᅣ'),\n    (0x3152, 'M', u'ᅤ'),\n    (0x3153, 'M', u'ᅥ'),\n    (0x3154, 'M', u'ᅦ'),\n    (0x3155, 'M', u'ᅧ'),\n    (0x3156, 'M', u'ᅨ'),\n    (0x3157, 'M', u'ᅩ'),\n    (0x3158, 'M', u'ᅪ'),\n    (0x3159, 'M', u'ᅫ'),\n    (0x315A, 'M', u'ᅬ'),\n    (0x315B, 'M', u'ᅭ'),\n    (0x315C, 'M', u'ᅮ'),\n    (0x315D, 'M', u'ᅯ'),\n    (0x315E, 'M', u'ᅰ'),\n    (0x315F, 'M', u'ᅱ'),\n    (0x3160, 'M', u'ᅲ'),\n    (0x3161, 'M', u'ᅳ'),\n    (0x3162, 'M', u'ᅴ'),\n    (0x3163, 'M', u'ᅵ'),\n    (0x3164, 'X'),\n    (0x3165, 'M', u'ᄔ'),\n    (0x3166, 'M', u'ᄕ'),\n    (0x3167, 'M', u'ᇇ'),\n    (0x3168, 'M', u'ᇈ'),\n    (0x3169, 'M', u'ᇌ'),\n    (0x316A, 'M', u'ᇎ'),\n    (0x316B, 'M', u'ᇓ'),\n    (0x316C, 'M', u'ᇗ'),\n    (0x316D, 'M', u'ᇙ'),\n    (0x316E, 'M', u'ᄜ'),\n    (0x316F, 'M', u'ᇝ'),\n    (0x3170, 'M', u'ᇟ'),\n    (0x3171, 'M', u'ᄝ'),\n    (0x3172, 'M', u'ᄞ'),\n    (0x3173, 'M', u'ᄠ'),\n    (0x3174, 'M', u'ᄢ'),\n    (0x3175, 'M', u'ᄣ'),\n    (0x3176, 'M', u'ᄧ'),\n    (0x3177, 'M', u'ᄩ'),\n    (0x3178, 'M', u'ᄫ'),\n    (0x3179, 'M', u'ᄬ'),\n    (0x317A, 'M', u'ᄭ'),\n    (0x317B, 'M', u'ᄮ'),\n    (0x317C, 'M', u'ᄯ'),\n    (0x317D, 'M', u'ᄲ'),\n    (0x317E, 'M', u'ᄶ'),\n    (0x317F, 'M', u'ᅀ'),\n    (0x3180, 'M', u'ᅇ'),\n    (0x3181, 'M', u'ᅌ'),\n    (0x3182, 'M', u'ᇱ'),\n    (0x3183, 'M', u'ᇲ'),\n    (0x3184, 'M', u'ᅗ'),\n    (0x3185, 'M', u'ᅘ'),\n    (0x3186, 'M', u'ᅙ'),\n    (0x3187, 'M', u'ᆄ'),\n    (0x3188, 'M', u'ᆅ'),\n    (0x3189, 'M', u'ᆈ'),\n    (0x318A, 'M', u'ᆑ'),\n    (0x318B, 'M', u'ᆒ'),\n    (0x318C, 'M', u'ᆔ'),\n    (0x318D, 'M', u'ᆞ'),\n    (0x318E, 'M', u'ᆡ'),\n    (0x318F, 'X'),\n    (0x3190, 'V'),\n    (0x3192, 'M', u'一'),\n    (0x3193, 'M', u'二'),\n    (0x3194, 'M', u'三'),\n    (0x3195, 'M', u'四'),\n    (0x3196, 'M', u'上'),\n    (0x3197, 'M', u'中'),\n    (0x3198, 'M', u'下'),\n    (0x3199, 'M', u'甲'),\n    (0x319A, 'M', u'乙'),\n    (0x319B, 'M', u'丙'),\n    (0x319C, 'M', u'丁'),\n    (0x319D, 'M', u'天'),\n    ]\n\ndef _seg_30():\n    return [\n    (0x319E, 'M', u'地'),\n    (0x319F, 'M', u'人'),\n    (0x31A0, 'V'),\n    (0x31BB, 'X'),\n    (0x31C0, 'V'),\n    (0x31E4, 'X'),\n    (0x31F0, 'V'),\n    (0x3200, '3', u'(ᄀ)'),\n    (0x3201, '3', u'(ᄂ)'),\n    (0x3202, '3', u'(ᄃ)'),\n    (0x3203, '3', u'(ᄅ)'),\n    (0x3204, '3', u'(ᄆ)'),\n    (0x3205, '3', u'(ᄇ)'),\n    (0x3206, '3', u'(ᄉ)'),\n    (0x3207, '3', u'(ᄋ)'),\n    (0x3208, '3', u'(ᄌ)'),\n    (0x3209, '3', u'(ᄎ)'),\n    (0x320A, '3', u'(ᄏ)'),\n    (0x320B, '3', u'(ᄐ)'),\n    (0x320C, '3', u'(ᄑ)'),\n    (0x320D, '3', u'(ᄒ)'),\n    (0x320E, '3', u'(가)'),\n    (0x320F, '3', u'(나)'),\n    (0x3210, '3', u'(다)'),\n    (0x3211, '3', u'(라)'),\n    (0x3212, '3', u'(마)'),\n    (0x3213, '3', u'(바)'),\n    (0x3214, '3', u'(사)'),\n    (0x3215, '3', u'(아)'),\n    (0x3216, '3', u'(자)'),\n    (0x3217, '3', u'(차)'),\n    (0x3218, '3', u'(카)'),\n    (0x3219, '3', u'(타)'),\n    (0x321A, '3', u'(파)'),\n    (0x321B, '3', u'(하)'),\n    (0x321C, '3', u'(주)'),\n    (0x321D, '3', u'(오전)'),\n    (0x321E, '3', u'(오후)'),\n    (0x321F, 'X'),\n    (0x3220, '3', u'(一)'),\n    (0x3221, '3', u'(二)'),\n    (0x3222, '3', u'(三)'),\n    (0x3223, '3', u'(四)'),\n    (0x3224, '3', u'(五)'),\n    (0x3225, '3', u'(六)'),\n    (0x3226, '3', u'(七)'),\n    (0x3227, '3', u'(八)'),\n    (0x3228, '3', u'(九)'),\n    (0x3229, '3', u'(十)'),\n    (0x322A, '3', u'(月)'),\n    (0x322B, '3', u'(火)'),\n    (0x322C, '3', u'(水)'),\n    (0x322D, '3', u'(木)'),\n    (0x322E, '3', u'(金)'),\n    (0x322F, '3', u'(土)'),\n    (0x3230, '3', u'(日)'),\n    (0x3231, '3', u'(株)'),\n    (0x3232, '3', u'(有)'),\n    (0x3233, '3', u'(社)'),\n    (0x3234, '3', u'(名)'),\n    (0x3235, '3', u'(特)'),\n    (0x3236, '3', u'(財)'),\n    (0x3237, '3', u'(祝)'),\n    (0x3238, '3', u'(労)'),\n    (0x3239, '3', u'(代)'),\n    (0x323A, '3', u'(呼)'),\n    (0x323B, '3', u'(学)'),\n    (0x323C, '3', u'(監)'),\n    (0x323D, '3', u'(企)'),\n    (0x323E, '3', u'(資)'),\n    (0x323F, '3', u'(協)'),\n    (0x3240, '3', u'(祭)'),\n    (0x3241, '3', u'(休)'),\n    (0x3242, '3', u'(自)'),\n    (0x3243, '3', u'(至)'),\n    (0x3244, 'M', u'問'),\n    (0x3245, 'M', u'幼'),\n    (0x3246, 'M', u'文'),\n    (0x3247, 'M', u'箏'),\n    (0x3248, 'V'),\n    (0x3250, 'M', u'pte'),\n    (0x3251, 'M', u'21'),\n    (0x3252, 'M', u'22'),\n    (0x3253, 'M', u'23'),\n    (0x3254, 'M', u'24'),\n    (0x3255, 'M', u'25'),\n    (0x3256, 'M', u'26'),\n    (0x3257, 'M', u'27'),\n    (0x3258, 'M', u'28'),\n    (0x3259, 'M', u'29'),\n    (0x325A, 'M', u'30'),\n    (0x325B, 'M', u'31'),\n    (0x325C, 'M', u'32'),\n    (0x325D, 'M', u'33'),\n    (0x325E, 'M', u'34'),\n    (0x325F, 'M', u'35'),\n    (0x3260, 'M', u'ᄀ'),\n    (0x3261, 'M', u'ᄂ'),\n    (0x3262, 'M', u'ᄃ'),\n    (0x3263, 'M', u'ᄅ'),\n    ]\n\ndef _seg_31():\n    return [\n    (0x3264, 'M', u'ᄆ'),\n    (0x3265, 'M', u'ᄇ'),\n    (0x3266, 'M', u'ᄉ'),\n    (0x3267, 'M', u'ᄋ'),\n    (0x3268, 'M', u'ᄌ'),\n    (0x3269, 'M', u'ᄎ'),\n    (0x326A, 'M', u'ᄏ'),\n    (0x326B, 'M', u'ᄐ'),\n    (0x326C, 'M', u'ᄑ'),\n    (0x326D, 'M', u'ᄒ'),\n    (0x326E, 'M', u'가'),\n    (0x326F, 'M', u'나'),\n    (0x3270, 'M', u'다'),\n    (0x3271, 'M', u'라'),\n    (0x3272, 'M', u'마'),\n    (0x3273, 'M', u'바'),\n    (0x3274, 'M', u'사'),\n    (0x3275, 'M', u'아'),\n    (0x3276, 'M', u'자'),\n    (0x3277, 'M', u'차'),\n    (0x3278, 'M', u'카'),\n    (0x3279, 'M', u'타'),\n    (0x327A, 'M', u'파'),\n    (0x327B, 'M', u'하'),\n    (0x327C, 'M', u'참고'),\n    (0x327D, 'M', u'주의'),\n    (0x327E, 'M', u'우'),\n    (0x327F, 'V'),\n    (0x3280, 'M', u'一'),\n    (0x3281, 'M', u'二'),\n    (0x3282, 'M', u'三'),\n    (0x3283, 'M', u'四'),\n    (0x3284, 'M', u'五'),\n    (0x3285, 'M', u'六'),\n    (0x3286, 'M', u'七'),\n    (0x3287, 'M', u'八'),\n    (0x3288, 'M', u'九'),\n    (0x3289, 'M', u'十'),\n    (0x328A, 'M', u'月'),\n    (0x328B, 'M', u'火'),\n    (0x328C, 'M', u'水'),\n    (0x328D, 'M', u'木'),\n    (0x328E, 'M', u'金'),\n    (0x328F, 'M', u'土'),\n    (0x3290, 'M', u'日'),\n    (0x3291, 'M', u'株'),\n    (0x3292, 'M', u'有'),\n    (0x3293, 'M', u'社'),\n    (0x3294, 'M', u'名'),\n    (0x3295, 'M', u'特'),\n    (0x3296, 'M', u'財'),\n    (0x3297, 'M', u'祝'),\n    (0x3298, 'M', u'労'),\n    (0x3299, 'M', u'秘'),\n    (0x329A, 'M', u'男'),\n    (0x329B, 'M', u'女'),\n    (0x329C, 'M', u'適'),\n    (0x329D, 'M', u'優'),\n    (0x329E, 'M', u'印'),\n    (0x329F, 'M', u'注'),\n    (0x32A0, 'M', u'項'),\n    (0x32A1, 'M', u'休'),\n    (0x32A2, 'M', u'写'),\n    (0x32A3, 'M', u'正'),\n    (0x32A4, 'M', u'上'),\n    (0x32A5, 'M', u'中'),\n    (0x32A6, 'M', u'下'),\n    (0x32A7, 'M', u'左'),\n    (0x32A8, 'M', u'右'),\n    (0x32A9, 'M', u'医'),\n    (0x32AA, 'M', u'宗'),\n    (0x32AB, 'M', u'学'),\n    (0x32AC, 'M', u'監'),\n    (0x32AD, 'M', u'企'),\n    (0x32AE, 'M', u'資'),\n    (0x32AF, 'M', u'協'),\n    (0x32B0, 'M', u'夜'),\n    (0x32B1, 'M', u'36'),\n    (0x32B2, 'M', u'37'),\n    (0x32B3, 'M', u'38'),\n    (0x32B4, 'M', u'39'),\n    (0x32B5, 'M', u'40'),\n    (0x32B6, 'M', u'41'),\n    (0x32B7, 'M', u'42'),\n    (0x32B8, 'M', u'43'),\n    (0x32B9, 'M', u'44'),\n    (0x32BA, 'M', u'45'),\n    (0x32BB, 'M', u'46'),\n    (0x32BC, 'M', u'47'),\n    (0x32BD, 'M', u'48'),\n    (0x32BE, 'M', u'49'),\n    (0x32BF, 'M', u'50'),\n    (0x32C0, 'M', u'1月'),\n    (0x32C1, 'M', u'2月'),\n    (0x32C2, 'M', u'3月'),\n    (0x32C3, 'M', u'4月'),\n    (0x32C4, 'M', u'5月'),\n    (0x32C5, 'M', u'6月'),\n    (0x32C6, 'M', u'7月'),\n    (0x32C7, 'M', u'8月'),\n    ]\n\ndef _seg_32():\n    return [\n    (0x32C8, 'M', u'9月'),\n    (0x32C9, 'M', u'10月'),\n    (0x32CA, 'M', u'11月'),\n    (0x32CB, 'M', u'12月'),\n    (0x32CC, 'M', u'hg'),\n    (0x32CD, 'M', u'erg'),\n    (0x32CE, 'M', u'ev'),\n    (0x32CF, 'M', u'ltd'),\n    (0x32D0, 'M', u'ア'),\n    (0x32D1, 'M', u'イ'),\n    (0x32D2, 'M', u'ウ'),\n    (0x32D3, 'M', u'エ'),\n    (0x32D4, 'M', u'オ'),\n    (0x32D5, 'M', u'カ'),\n    (0x32D6, 'M', u'キ'),\n    (0x32D7, 'M', u'ク'),\n    (0x32D8, 'M', u'ケ'),\n    (0x32D9, 'M', u'コ'),\n    (0x32DA, 'M', u'サ'),\n    (0x32DB, 'M', u'シ'),\n    (0x32DC, 'M', u'ス'),\n    (0x32DD, 'M', u'セ'),\n    (0x32DE, 'M', u'ソ'),\n    (0x32DF, 'M', u'タ'),\n    (0x32E0, 'M', u'チ'),\n    (0x32E1, 'M', u'ツ'),\n    (0x32E2, 'M', u'テ'),\n    (0x32E3, 'M', u'ト'),\n    (0x32E4, 'M', u'ナ'),\n    (0x32E5, 'M', u'ニ'),\n    (0x32E6, 'M', u'ヌ'),\n    (0x32E7, 'M', u'ネ'),\n    (0x32E8, 'M', u'ノ'),\n    (0x32E9, 'M', u'ハ'),\n    (0x32EA, 'M', u'ヒ'),\n    (0x32EB, 'M', u'フ'),\n    (0x32EC, 'M', u'ヘ'),\n    (0x32ED, 'M', u'ホ'),\n    (0x32EE, 'M', u'マ'),\n    (0x32EF, 'M', u'ミ'),\n    (0x32F0, 'M', u'ム'),\n    (0x32F1, 'M', u'メ'),\n    (0x32F2, 'M', u'モ'),\n    (0x32F3, 'M', u'ヤ'),\n    (0x32F4, 'M', u'ユ'),\n    (0x32F5, 'M', u'ヨ'),\n    (0x32F6, 'M', u'ラ'),\n    (0x32F7, 'M', u'リ'),\n    (0x32F8, 'M', u'ル'),\n    (0x32F9, 'M', u'レ'),\n    (0x32FA, 'M', u'ロ'),\n    (0x32FB, 'M', u'ワ'),\n    (0x32FC, 'M', u'ヰ'),\n    (0x32FD, 'M', u'ヱ'),\n    (0x32FE, 'M', u'ヲ'),\n    (0x32FF, 'X'),\n    (0x3300, 'M', u'アパート'),\n    (0x3301, 'M', u'アルファ'),\n    (0x3302, 'M', u'アンペア'),\n    (0x3303, 'M', u'アール'),\n    (0x3304, 'M', u'イニング'),\n    (0x3305, 'M', u'インチ'),\n    (0x3306, 'M', u'ウォン'),\n    (0x3307, 'M', u'エスクード'),\n    (0x3308, 'M', u'エーカー'),\n    (0x3309, 'M', u'オンス'),\n    (0x330A, 'M', u'オーム'),\n    (0x330B, 'M', u'カイリ'),\n    (0x330C, 'M', u'カラット'),\n    (0x330D, 'M', u'カロリー'),\n    (0x330E, 'M', u'ガロン'),\n    (0x330F, 'M', u'ガンマ'),\n    (0x3310, 'M', u'ギガ'),\n    (0x3311, 'M', u'ギニー'),\n    (0x3312, 'M', u'キュリー'),\n    (0x3313, 'M', u'ギルダー'),\n    (0x3314, 'M', u'キロ'),\n    (0x3315, 'M', u'キログラム'),\n    (0x3316, 'M', u'キロメートル'),\n    (0x3317, 'M', u'キロワット'),\n    (0x3318, 'M', u'グラム'),\n    (0x3319, 'M', u'グラムトン'),\n    (0x331A, 'M', u'クルゼイロ'),\n    (0x331B, 'M', u'クローネ'),\n    (0x331C, 'M', u'ケース'),\n    (0x331D, 'M', u'コルナ'),\n    (0x331E, 'M', u'コーポ'),\n    (0x331F, 'M', u'サイクル'),\n    (0x3320, 'M', u'サンチーム'),\n    (0x3321, 'M', u'シリング'),\n    (0x3322, 'M', u'センチ'),\n    (0x3323, 'M', u'セント'),\n    (0x3324, 'M', u'ダース'),\n    (0x3325, 'M', u'デシ'),\n    (0x3326, 'M', u'ドル'),\n    (0x3327, 'M', u'トン'),\n    (0x3328, 'M', u'ナノ'),\n    (0x3329, 'M', u'ノット'),\n    (0x332A, 'M', u'ハイツ'),\n    (0x332B, 'M', u'パーセント'),\n    ]\n\ndef _seg_33():\n    return [\n    (0x332C, 'M', u'パーツ'),\n    (0x332D, 'M', u'バーレル'),\n    (0x332E, 'M', u'ピアストル'),\n    (0x332F, 'M', u'ピクル'),\n    (0x3330, 'M', u'ピコ'),\n    (0x3331, 'M', u'ビル'),\n    (0x3332, 'M', u'ファラッド'),\n    (0x3333, 'M', u'フィート'),\n    (0x3334, 'M', u'ブッシェル'),\n    (0x3335, 'M', u'フラン'),\n    (0x3336, 'M', u'ヘクタール'),\n    (0x3337, 'M', u'ペソ'),\n    (0x3338, 'M', u'ペニヒ'),\n    (0x3339, 'M', u'ヘルツ'),\n    (0x333A, 'M', u'ペンス'),\n    (0x333B, 'M', u'ページ'),\n    (0x333C, 'M', u'ベータ'),\n    (0x333D, 'M', u'ポイント'),\n    (0x333E, 'M', u'ボルト'),\n    (0x333F, 'M', u'ホン'),\n    (0x3340, 'M', u'ポンド'),\n    (0x3341, 'M', u'ホール'),\n    (0x3342, 'M', u'ホーン'),\n    (0x3343, 'M', u'マイクロ'),\n    (0x3344, 'M', u'マイル'),\n    (0x3345, 'M', u'マッハ'),\n    (0x3346, 'M', u'マルク'),\n    (0x3347, 'M', u'マンション'),\n    (0x3348, 'M', u'ミクロン'),\n    (0x3349, 'M', u'ミリ'),\n    (0x334A, 'M', u'ミリバール'),\n    (0x334B, 'M', u'メガ'),\n    (0x334C, 'M', u'メガトン'),\n    (0x334D, 'M', u'メートル'),\n    (0x334E, 'M', u'ヤード'),\n    (0x334F, 'M', u'ヤール'),\n    (0x3350, 'M', u'ユアン'),\n    (0x3351, 'M', u'リットル'),\n    (0x3352, 'M', u'リラ'),\n    (0x3353, 'M', u'ルピー'),\n    (0x3354, 'M', u'ルーブル'),\n    (0x3355, 'M', u'レム'),\n    (0x3356, 'M', u'レントゲン'),\n    (0x3357, 'M', u'ワット'),\n    (0x3358, 'M', u'0点'),\n    (0x3359, 'M', u'1点'),\n    (0x335A, 'M', u'2点'),\n    (0x335B, 'M', u'3点'),\n    (0x335C, 'M', u'4点'),\n    (0x335D, 'M', u'5点'),\n    (0x335E, 'M', u'6点'),\n    (0x335F, 'M', u'7点'),\n    (0x3360, 'M', u'8点'),\n    (0x3361, 'M', u'9点'),\n    (0x3362, 'M', u'10点'),\n    (0x3363, 'M', u'11点'),\n    (0x3364, 'M', u'12点'),\n    (0x3365, 'M', u'13点'),\n    (0x3366, 'M', u'14点'),\n    (0x3367, 'M', u'15点'),\n    (0x3368, 'M', u'16点'),\n    (0x3369, 'M', u'17点'),\n    (0x336A, 'M', u'18点'),\n    (0x336B, 'M', u'19点'),\n    (0x336C, 'M', u'20点'),\n    (0x336D, 'M', u'21点'),\n    (0x336E, 'M', u'22点'),\n    (0x336F, 'M', u'23点'),\n    (0x3370, 'M', u'24点'),\n    (0x3371, 'M', u'hpa'),\n    (0x3372, 'M', u'da'),\n    (0x3373, 'M', u'au'),\n    (0x3374, 'M', u'bar'),\n    (0x3375, 'M', u'ov'),\n    (0x3376, 'M', u'pc'),\n    (0x3377, 'M', u'dm'),\n    (0x3378, 'M', u'dm2'),\n    (0x3379, 'M', u'dm3'),\n    (0x337A, 'M', u'iu'),\n    (0x337B, 'M', u'平成'),\n    (0x337C, 'M', u'昭和'),\n    (0x337D, 'M', u'大正'),\n    (0x337E, 'M', u'明治'),\n    (0x337F, 'M', u'株式会社'),\n    (0x3380, 'M', u'pa'),\n    (0x3381, 'M', u'na'),\n    (0x3382, 'M', u'μa'),\n    (0x3383, 'M', u'ma'),\n    (0x3384, 'M', u'ka'),\n    (0x3385, 'M', u'kb'),\n    (0x3386, 'M', u'mb'),\n    (0x3387, 'M', u'gb'),\n    (0x3388, 'M', u'cal'),\n    (0x3389, 'M', u'kcal'),\n    (0x338A, 'M', u'pf'),\n    (0x338B, 'M', u'nf'),\n    (0x338C, 'M', u'μf'),\n    (0x338D, 'M', u'μg'),\n    (0x338E, 'M', u'mg'),\n    (0x338F, 'M', u'kg'),\n    ]\n\ndef _seg_34():\n    return [\n    (0x3390, 'M', u'hz'),\n    (0x3391, 'M', u'khz'),\n    (0x3392, 'M', u'mhz'),\n    (0x3393, 'M', u'ghz'),\n    (0x3394, 'M', u'thz'),\n    (0x3395, 'M', u'μl'),\n    (0x3396, 'M', u'ml'),\n    (0x3397, 'M', u'dl'),\n    (0x3398, 'M', u'kl'),\n    (0x3399, 'M', u'fm'),\n    (0x339A, 'M', u'nm'),\n    (0x339B, 'M', u'μm'),\n    (0x339C, 'M', u'mm'),\n    (0x339D, 'M', u'cm'),\n    (0x339E, 'M', u'km'),\n    (0x339F, 'M', u'mm2'),\n    (0x33A0, 'M', u'cm2'),\n    (0x33A1, 'M', u'm2'),\n    (0x33A2, 'M', u'km2'),\n    (0x33A3, 'M', u'mm3'),\n    (0x33A4, 'M', u'cm3'),\n    (0x33A5, 'M', u'm3'),\n    (0x33A6, 'M', u'km3'),\n    (0x33A7, 'M', u'm∕s'),\n    (0x33A8, 'M', u'm∕s2'),\n    (0x33A9, 'M', u'pa'),\n    (0x33AA, 'M', u'kpa'),\n    (0x33AB, 'M', u'mpa'),\n    (0x33AC, 'M', u'gpa'),\n    (0x33AD, 'M', u'rad'),\n    (0x33AE, 'M', u'rad∕s'),\n    (0x33AF, 'M', u'rad∕s2'),\n    (0x33B0, 'M', u'ps'),\n    (0x33B1, 'M', u'ns'),\n    (0x33B2, 'M', u'μs'),\n    (0x33B3, 'M', u'ms'),\n    (0x33B4, 'M', u'pv'),\n    (0x33B5, 'M', u'nv'),\n    (0x33B6, 'M', u'μv'),\n    (0x33B7, 'M', u'mv'),\n    (0x33B8, 'M', u'kv'),\n    (0x33B9, 'M', u'mv'),\n    (0x33BA, 'M', u'pw'),\n    (0x33BB, 'M', u'nw'),\n    (0x33BC, 'M', u'μw'),\n    (0x33BD, 'M', u'mw'),\n    (0x33BE, 'M', u'kw'),\n    (0x33BF, 'M', u'mw'),\n    (0x33C0, 'M', u'kω'),\n    (0x33C1, 'M', u'mω'),\n    (0x33C2, 'X'),\n    (0x33C3, 'M', u'bq'),\n    (0x33C4, 'M', u'cc'),\n    (0x33C5, 'M', u'cd'),\n    (0x33C6, 'M', u'c∕kg'),\n    (0x33C7, 'X'),\n    (0x33C8, 'M', u'db'),\n    (0x33C9, 'M', u'gy'),\n    (0x33CA, 'M', u'ha'),\n    (0x33CB, 'M', u'hp'),\n    (0x33CC, 'M', u'in'),\n    (0x33CD, 'M', u'kk'),\n    (0x33CE, 'M', u'km'),\n    (0x33CF, 'M', u'kt'),\n    (0x33D0, 'M', u'lm'),\n    (0x33D1, 'M', u'ln'),\n    (0x33D2, 'M', u'log'),\n    (0x33D3, 'M', u'lx'),\n    (0x33D4, 'M', u'mb'),\n    (0x33D5, 'M', u'mil'),\n    (0x33D6, 'M', u'mol'),\n    (0x33D7, 'M', u'ph'),\n    (0x33D8, 'X'),\n    (0x33D9, 'M', u'ppm'),\n    (0x33DA, 'M', u'pr'),\n    (0x33DB, 'M', u'sr'),\n    (0x33DC, 'M', u'sv'),\n    (0x33DD, 'M', u'wb'),\n    (0x33DE, 'M', u'v∕m'),\n    (0x33DF, 'M', u'a∕m'),\n    (0x33E0, 'M', u'1日'),\n    (0x33E1, 'M', u'2日'),\n    (0x33E2, 'M', u'3日'),\n    (0x33E3, 'M', u'4日'),\n    (0x33E4, 'M', u'5日'),\n    (0x33E5, 'M', u'6日'),\n    (0x33E6, 'M', u'7日'),\n    (0x33E7, 'M', u'8日'),\n    (0x33E8, 'M', u'9日'),\n    (0x33E9, 'M', u'10日'),\n    (0x33EA, 'M', u'11日'),\n    (0x33EB, 'M', u'12日'),\n    (0x33EC, 'M', u'13日'),\n    (0x33ED, 'M', u'14日'),\n    (0x33EE, 'M', u'15日'),\n    (0x33EF, 'M', u'16日'),\n    (0x33F0, 'M', u'17日'),\n    (0x33F1, 'M', u'18日'),\n    (0x33F2, 'M', u'19日'),\n    (0x33F3, 'M', u'20日'),\n    ]\n\ndef _seg_35():\n    return [\n    (0x33F4, 'M', u'21日'),\n    (0x33F5, 'M', u'22日'),\n    (0x33F6, 'M', u'23日'),\n    (0x33F7, 'M', u'24日'),\n    (0x33F8, 'M', u'25日'),\n    (0x33F9, 'M', u'26日'),\n    (0x33FA, 'M', u'27日'),\n    (0x33FB, 'M', u'28日'),\n    (0x33FC, 'M', u'29日'),\n    (0x33FD, 'M', u'30日'),\n    (0x33FE, 'M', u'31日'),\n    (0x33FF, 'M', u'gal'),\n    (0x3400, 'V'),\n    (0x4DB6, 'X'),\n    (0x4DC0, 'V'),\n    (0x9FF0, 'X'),\n    (0xA000, 'V'),\n    (0xA48D, 'X'),\n    (0xA490, 'V'),\n    (0xA4C7, 'X'),\n    (0xA4D0, 'V'),\n    (0xA62C, 'X'),\n    (0xA640, 'M', u'ꙁ'),\n    (0xA641, 'V'),\n    (0xA642, 'M', u'ꙃ'),\n    (0xA643, 'V'),\n    (0xA644, 'M', u'ꙅ'),\n    (0xA645, 'V'),\n    (0xA646, 'M', u'ꙇ'),\n    (0xA647, 'V'),\n    (0xA648, 'M', u'ꙉ'),\n    (0xA649, 'V'),\n    (0xA64A, 'M', u'ꙋ'),\n    (0xA64B, 'V'),\n    (0xA64C, 'M', u'ꙍ'),\n    (0xA64D, 'V'),\n    (0xA64E, 'M', u'ꙏ'),\n    (0xA64F, 'V'),\n    (0xA650, 'M', u'ꙑ'),\n    (0xA651, 'V'),\n    (0xA652, 'M', u'ꙓ'),\n    (0xA653, 'V'),\n    (0xA654, 'M', u'ꙕ'),\n    (0xA655, 'V'),\n    (0xA656, 'M', u'ꙗ'),\n    (0xA657, 'V'),\n    (0xA658, 'M', u'ꙙ'),\n    (0xA659, 'V'),\n    (0xA65A, 'M', u'ꙛ'),\n    (0xA65B, 'V'),\n    (0xA65C, 'M', u'ꙝ'),\n    (0xA65D, 'V'),\n    (0xA65E, 'M', u'ꙟ'),\n    (0xA65F, 'V'),\n    (0xA660, 'M', u'ꙡ'),\n    (0xA661, 'V'),\n    (0xA662, 'M', u'ꙣ'),\n    (0xA663, 'V'),\n    (0xA664, 'M', u'ꙥ'),\n    (0xA665, 'V'),\n    (0xA666, 'M', u'ꙧ'),\n    (0xA667, 'V'),\n    (0xA668, 'M', u'ꙩ'),\n    (0xA669, 'V'),\n    (0xA66A, 'M', u'ꙫ'),\n    (0xA66B, 'V'),\n    (0xA66C, 'M', u'ꙭ'),\n    (0xA66D, 'V'),\n    (0xA680, 'M', u'ꚁ'),\n    (0xA681, 'V'),\n    (0xA682, 'M', u'ꚃ'),\n    (0xA683, 'V'),\n    (0xA684, 'M', u'ꚅ'),\n    (0xA685, 'V'),\n    (0xA686, 'M', u'ꚇ'),\n    (0xA687, 'V'),\n    (0xA688, 'M', u'ꚉ'),\n    (0xA689, 'V'),\n    (0xA68A, 'M', u'ꚋ'),\n    (0xA68B, 'V'),\n    (0xA68C, 'M', u'ꚍ'),\n    (0xA68D, 'V'),\n    (0xA68E, 'M', u'ꚏ'),\n    (0xA68F, 'V'),\n    (0xA690, 'M', u'ꚑ'),\n    (0xA691, 'V'),\n    (0xA692, 'M', u'ꚓ'),\n    (0xA693, 'V'),\n    (0xA694, 'M', u'ꚕ'),\n    (0xA695, 'V'),\n    (0xA696, 'M', u'ꚗ'),\n    (0xA697, 'V'),\n    (0xA698, 'M', u'ꚙ'),\n    (0xA699, 'V'),\n    (0xA69A, 'M', u'ꚛ'),\n    (0xA69B, 'V'),\n    (0xA69C, 'M', u'ъ'),\n    (0xA69D, 'M', u'ь'),\n    (0xA69E, 'V'),\n    (0xA6F8, 'X'),\n    ]\n\ndef _seg_36():\n    return [\n    (0xA700, 'V'),\n    (0xA722, 'M', u'ꜣ'),\n    (0xA723, 'V'),\n    (0xA724, 'M', u'ꜥ'),\n    (0xA725, 'V'),\n    (0xA726, 'M', u'ꜧ'),\n    (0xA727, 'V'),\n    (0xA728, 'M', u'ꜩ'),\n    (0xA729, 'V'),\n    (0xA72A, 'M', u'ꜫ'),\n    (0xA72B, 'V'),\n    (0xA72C, 'M', u'ꜭ'),\n    (0xA72D, 'V'),\n    (0xA72E, 'M', u'ꜯ'),\n    (0xA72F, 'V'),\n    (0xA732, 'M', u'ꜳ'),\n    (0xA733, 'V'),\n    (0xA734, 'M', u'ꜵ'),\n    (0xA735, 'V'),\n    (0xA736, 'M', u'ꜷ'),\n    (0xA737, 'V'),\n    (0xA738, 'M', u'ꜹ'),\n    (0xA739, 'V'),\n    (0xA73A, 'M', u'ꜻ'),\n    (0xA73B, 'V'),\n    (0xA73C, 'M', u'ꜽ'),\n    (0xA73D, 'V'),\n    (0xA73E, 'M', u'ꜿ'),\n    (0xA73F, 'V'),\n    (0xA740, 'M', u'ꝁ'),\n    (0xA741, 'V'),\n    (0xA742, 'M', u'ꝃ'),\n    (0xA743, 'V'),\n    (0xA744, 'M', u'ꝅ'),\n    (0xA745, 'V'),\n    (0xA746, 'M', u'ꝇ'),\n    (0xA747, 'V'),\n    (0xA748, 'M', u'ꝉ'),\n    (0xA749, 'V'),\n    (0xA74A, 'M', u'ꝋ'),\n    (0xA74B, 'V'),\n    (0xA74C, 'M', u'ꝍ'),\n    (0xA74D, 'V'),\n    (0xA74E, 'M', u'ꝏ'),\n    (0xA74F, 'V'),\n    (0xA750, 'M', u'ꝑ'),\n    (0xA751, 'V'),\n    (0xA752, 'M', u'ꝓ'),\n    (0xA753, 'V'),\n    (0xA754, 'M', u'ꝕ'),\n    (0xA755, 'V'),\n    (0xA756, 'M', u'ꝗ'),\n    (0xA757, 'V'),\n    (0xA758, 'M', u'ꝙ'),\n    (0xA759, 'V'),\n    (0xA75A, 'M', u'ꝛ'),\n    (0xA75B, 'V'),\n    (0xA75C, 'M', u'ꝝ'),\n    (0xA75D, 'V'),\n    (0xA75E, 'M', u'ꝟ'),\n    (0xA75F, 'V'),\n    (0xA760, 'M', u'ꝡ'),\n    (0xA761, 'V'),\n    (0xA762, 'M', u'ꝣ'),\n    (0xA763, 'V'),\n    (0xA764, 'M', u'ꝥ'),\n    (0xA765, 'V'),\n    (0xA766, 'M', u'ꝧ'),\n    (0xA767, 'V'),\n    (0xA768, 'M', u'ꝩ'),\n    (0xA769, 'V'),\n    (0xA76A, 'M', u'ꝫ'),\n    (0xA76B, 'V'),\n    (0xA76C, 'M', u'ꝭ'),\n    (0xA76D, 'V'),\n    (0xA76E, 'M', u'ꝯ'),\n    (0xA76F, 'V'),\n    (0xA770, 'M', u'ꝯ'),\n    (0xA771, 'V'),\n    (0xA779, 'M', u'ꝺ'),\n    (0xA77A, 'V'),\n    (0xA77B, 'M', u'ꝼ'),\n    (0xA77C, 'V'),\n    (0xA77D, 'M', u'ᵹ'),\n    (0xA77E, 'M', u'ꝿ'),\n    (0xA77F, 'V'),\n    (0xA780, 'M', u'ꞁ'),\n    (0xA781, 'V'),\n    (0xA782, 'M', u'ꞃ'),\n    (0xA783, 'V'),\n    (0xA784, 'M', u'ꞅ'),\n    (0xA785, 'V'),\n    (0xA786, 'M', u'ꞇ'),\n    (0xA787, 'V'),\n    (0xA78B, 'M', u'ꞌ'),\n    (0xA78C, 'V'),\n    (0xA78D, 'M', u'ɥ'),\n    (0xA78E, 'V'),\n    (0xA790, 'M', u'ꞑ'),\n    (0xA791, 'V'),\n    ]\n\ndef _seg_37():\n    return [\n    (0xA792, 'M', u'ꞓ'),\n    (0xA793, 'V'),\n    (0xA796, 'M', u'ꞗ'),\n    (0xA797, 'V'),\n    (0xA798, 'M', u'ꞙ'),\n    (0xA799, 'V'),\n    (0xA79A, 'M', u'ꞛ'),\n    (0xA79B, 'V'),\n    (0xA79C, 'M', u'ꞝ'),\n    (0xA79D, 'V'),\n    (0xA79E, 'M', u'ꞟ'),\n    (0xA79F, 'V'),\n    (0xA7A0, 'M', u'ꞡ'),\n    (0xA7A1, 'V'),\n    (0xA7A2, 'M', u'ꞣ'),\n    (0xA7A3, 'V'),\n    (0xA7A4, 'M', u'ꞥ'),\n    (0xA7A5, 'V'),\n    (0xA7A6, 'M', u'ꞧ'),\n    (0xA7A7, 'V'),\n    (0xA7A8, 'M', u'ꞩ'),\n    (0xA7A9, 'V'),\n    (0xA7AA, 'M', u'ɦ'),\n    (0xA7AB, 'M', u'ɜ'),\n    (0xA7AC, 'M', u'ɡ'),\n    (0xA7AD, 'M', u'ɬ'),\n    (0xA7AE, 'M', u'ɪ'),\n    (0xA7AF, 'V'),\n    (0xA7B0, 'M', u'ʞ'),\n    (0xA7B1, 'M', u'ʇ'),\n    (0xA7B2, 'M', u'ʝ'),\n    (0xA7B3, 'M', u'ꭓ'),\n    (0xA7B4, 'M', u'ꞵ'),\n    (0xA7B5, 'V'),\n    (0xA7B6, 'M', u'ꞷ'),\n    (0xA7B7, 'V'),\n    (0xA7B8, 'X'),\n    (0xA7B9, 'V'),\n    (0xA7BA, 'X'),\n    (0xA7F7, 'V'),\n    (0xA7F8, 'M', u'ħ'),\n    (0xA7F9, 'M', u'œ'),\n    (0xA7FA, 'V'),\n    (0xA82C, 'X'),\n    (0xA830, 'V'),\n    (0xA83A, 'X'),\n    (0xA840, 'V'),\n    (0xA878, 'X'),\n    (0xA880, 'V'),\n    (0xA8C6, 'X'),\n    (0xA8CE, 'V'),\n    (0xA8DA, 'X'),\n    (0xA8E0, 'V'),\n    (0xA954, 'X'),\n    (0xA95F, 'V'),\n    (0xA97D, 'X'),\n    (0xA980, 'V'),\n    (0xA9CE, 'X'),\n    (0xA9CF, 'V'),\n    (0xA9DA, 'X'),\n    (0xA9DE, 'V'),\n    (0xA9FF, 'X'),\n    (0xAA00, 'V'),\n    (0xAA37, 'X'),\n    (0xAA40, 'V'),\n    (0xAA4E, 'X'),\n    (0xAA50, 'V'),\n    (0xAA5A, 'X'),\n    (0xAA5C, 'V'),\n    (0xAAC3, 'X'),\n    (0xAADB, 'V'),\n    (0xAAF7, 'X'),\n    (0xAB01, 'V'),\n    (0xAB07, 'X'),\n    (0xAB09, 'V'),\n    (0xAB0F, 'X'),\n    (0xAB11, 'V'),\n    (0xAB17, 'X'),\n    (0xAB20, 'V'),\n    (0xAB27, 'X'),\n    (0xAB28, 'V'),\n    (0xAB2F, 'X'),\n    (0xAB30, 'V'),\n    (0xAB5C, 'M', u'ꜧ'),\n    (0xAB5D, 'M', u'ꬷ'),\n    (0xAB5E, 'M', u'ɫ'),\n    (0xAB5F, 'M', u'ꭒ'),\n    (0xAB60, 'V'),\n    (0xAB66, 'X'),\n    (0xAB70, 'M', u'Ꭰ'),\n    (0xAB71, 'M', u'Ꭱ'),\n    (0xAB72, 'M', u'Ꭲ'),\n    (0xAB73, 'M', u'Ꭳ'),\n    (0xAB74, 'M', u'Ꭴ'),\n    (0xAB75, 'M', u'Ꭵ'),\n    (0xAB76, 'M', u'Ꭶ'),\n    (0xAB77, 'M', u'Ꭷ'),\n    (0xAB78, 'M', u'Ꭸ'),\n    (0xAB79, 'M', u'Ꭹ'),\n    (0xAB7A, 'M', u'Ꭺ'),\n    ]\n\ndef _seg_38():\n    return [\n    (0xAB7B, 'M', u'Ꭻ'),\n    (0xAB7C, 'M', u'Ꭼ'),\n    (0xAB7D, 'M', u'Ꭽ'),\n    (0xAB7E, 'M', u'Ꭾ'),\n    (0xAB7F, 'M', u'Ꭿ'),\n    (0xAB80, 'M', u'Ꮀ'),\n    (0xAB81, 'M', u'Ꮁ'),\n    (0xAB82, 'M', u'Ꮂ'),\n    (0xAB83, 'M', u'Ꮃ'),\n    (0xAB84, 'M', u'Ꮄ'),\n    (0xAB85, 'M', u'Ꮅ'),\n    (0xAB86, 'M', u'Ꮆ'),\n    (0xAB87, 'M', u'Ꮇ'),\n    (0xAB88, 'M', u'Ꮈ'),\n    (0xAB89, 'M', u'Ꮉ'),\n    (0xAB8A, 'M', u'Ꮊ'),\n    (0xAB8B, 'M', u'Ꮋ'),\n    (0xAB8C, 'M', u'Ꮌ'),\n    (0xAB8D, 'M', u'Ꮍ'),\n    (0xAB8E, 'M', u'Ꮎ'),\n    (0xAB8F, 'M', u'Ꮏ'),\n    (0xAB90, 'M', u'Ꮐ'),\n    (0xAB91, 'M', u'Ꮑ'),\n    (0xAB92, 'M', u'Ꮒ'),\n    (0xAB93, 'M', u'Ꮓ'),\n    (0xAB94, 'M', u'Ꮔ'),\n    (0xAB95, 'M', u'Ꮕ'),\n    (0xAB96, 'M', u'Ꮖ'),\n    (0xAB97, 'M', u'Ꮗ'),\n    (0xAB98, 'M', u'Ꮘ'),\n    (0xAB99, 'M', u'Ꮙ'),\n    (0xAB9A, 'M', u'Ꮚ'),\n    (0xAB9B, 'M', u'Ꮛ'),\n    (0xAB9C, 'M', u'Ꮜ'),\n    (0xAB9D, 'M', u'Ꮝ'),\n    (0xAB9E, 'M', u'Ꮞ'),\n    (0xAB9F, 'M', u'Ꮟ'),\n    (0xABA0, 'M', u'Ꮠ'),\n    (0xABA1, 'M', u'Ꮡ'),\n    (0xABA2, 'M', u'Ꮢ'),\n    (0xABA3, 'M', u'Ꮣ'),\n    (0xABA4, 'M', u'Ꮤ'),\n    (0xABA5, 'M', u'Ꮥ'),\n    (0xABA6, 'M', u'Ꮦ'),\n    (0xABA7, 'M', u'Ꮧ'),\n    (0xABA8, 'M', u'Ꮨ'),\n    (0xABA9, 'M', u'Ꮩ'),\n    (0xABAA, 'M', u'Ꮪ'),\n    (0xABAB, 'M', u'Ꮫ'),\n    (0xABAC, 'M', u'Ꮬ'),\n    (0xABAD, 'M', u'Ꮭ'),\n    (0xABAE, 'M', u'Ꮮ'),\n    (0xABAF, 'M', u'Ꮯ'),\n    (0xABB0, 'M', u'Ꮰ'),\n    (0xABB1, 'M', u'Ꮱ'),\n    (0xABB2, 'M', u'Ꮲ'),\n    (0xABB3, 'M', u'Ꮳ'),\n    (0xABB4, 'M', u'Ꮴ'),\n    (0xABB5, 'M', u'Ꮵ'),\n    (0xABB6, 'M', u'Ꮶ'),\n    (0xABB7, 'M', u'Ꮷ'),\n    (0xABB8, 'M', u'Ꮸ'),\n    (0xABB9, 'M', u'Ꮹ'),\n    (0xABBA, 'M', u'Ꮺ'),\n    (0xABBB, 'M', u'Ꮻ'),\n    (0xABBC, 'M', u'Ꮼ'),\n    (0xABBD, 'M', u'Ꮽ'),\n    (0xABBE, 'M', u'Ꮾ'),\n    (0xABBF, 'M', u'Ꮿ'),\n    (0xABC0, 'V'),\n    (0xABEE, 'X'),\n    (0xABF0, 'V'),\n    (0xABFA, 'X'),\n    (0xAC00, 'V'),\n    (0xD7A4, 'X'),\n    (0xD7B0, 'V'),\n    (0xD7C7, 'X'),\n    (0xD7CB, 'V'),\n    (0xD7FC, 'X'),\n    (0xF900, 'M', u'豈'),\n    (0xF901, 'M', u'更'),\n    (0xF902, 'M', u'車'),\n    (0xF903, 'M', u'賈'),\n    (0xF904, 'M', u'滑'),\n    (0xF905, 'M', u'串'),\n    (0xF906, 'M', u'句'),\n    (0xF907, 'M', u'龜'),\n    (0xF909, 'M', u'契'),\n    (0xF90A, 'M', u'金'),\n    (0xF90B, 'M', u'喇'),\n    (0xF90C, 'M', u'奈'),\n    (0xF90D, 'M', u'懶'),\n    (0xF90E, 'M', u'癩'),\n    (0xF90F, 'M', u'羅'),\n    (0xF910, 'M', u'蘿'),\n    (0xF911, 'M', u'螺'),\n    (0xF912, 'M', u'裸'),\n    (0xF913, 'M', u'邏'),\n    (0xF914, 'M', u'樂'),\n    (0xF915, 'M', u'洛'),\n    ]\n\ndef _seg_39():\n    return [\n    (0xF916, 'M', u'烙'),\n    (0xF917, 'M', u'珞'),\n    (0xF918, 'M', u'落'),\n    (0xF919, 'M', u'酪'),\n    (0xF91A, 'M', u'駱'),\n    (0xF91B, 'M', u'亂'),\n    (0xF91C, 'M', u'卵'),\n    (0xF91D, 'M', u'欄'),\n    (0xF91E, 'M', u'爛'),\n    (0xF91F, 'M', u'蘭'),\n    (0xF920, 'M', u'鸞'),\n    (0xF921, 'M', u'嵐'),\n    (0xF922, 'M', u'濫'),\n    (0xF923, 'M', u'藍'),\n    (0xF924, 'M', u'襤'),\n    (0xF925, 'M', u'拉'),\n    (0xF926, 'M', u'臘'),\n    (0xF927, 'M', u'蠟'),\n    (0xF928, 'M', u'廊'),\n    (0xF929, 'M', u'朗'),\n    (0xF92A, 'M', u'浪'),\n    (0xF92B, 'M', u'狼'),\n    (0xF92C, 'M', u'郎'),\n    (0xF92D, 'M', u'來'),\n    (0xF92E, 'M', u'冷'),\n    (0xF92F, 'M', u'勞'),\n    (0xF930, 'M', u'擄'),\n    (0xF931, 'M', u'櫓'),\n    (0xF932, 'M', u'爐'),\n    (0xF933, 'M', u'盧'),\n    (0xF934, 'M', u'老'),\n    (0xF935, 'M', u'蘆'),\n    (0xF936, 'M', u'虜'),\n    (0xF937, 'M', u'路'),\n    (0xF938, 'M', u'露'),\n    (0xF939, 'M', u'魯'),\n    (0xF93A, 'M', u'鷺'),\n    (0xF93B, 'M', u'碌'),\n    (0xF93C, 'M', u'祿'),\n    (0xF93D, 'M', u'綠'),\n    (0xF93E, 'M', u'菉'),\n    (0xF93F, 'M', u'錄'),\n    (0xF940, 'M', u'鹿'),\n    (0xF941, 'M', u'論'),\n    (0xF942, 'M', u'壟'),\n    (0xF943, 'M', u'弄'),\n    (0xF944, 'M', u'籠'),\n    (0xF945, 'M', u'聾'),\n    (0xF946, 'M', u'牢'),\n    (0xF947, 'M', u'磊'),\n    (0xF948, 'M', u'賂'),\n    (0xF949, 'M', u'雷'),\n    (0xF94A, 'M', u'壘'),\n    (0xF94B, 'M', u'屢'),\n    (0xF94C, 'M', u'樓'),\n    (0xF94D, 'M', u'淚'),\n    (0xF94E, 'M', u'漏'),\n    (0xF94F, 'M', u'累'),\n    (0xF950, 'M', u'縷'),\n    (0xF951, 'M', u'陋'),\n    (0xF952, 'M', u'勒'),\n    (0xF953, 'M', u'肋'),\n    (0xF954, 'M', u'凜'),\n    (0xF955, 'M', u'凌'),\n    (0xF956, 'M', u'稜'),\n    (0xF957, 'M', u'綾'),\n    (0xF958, 'M', u'菱'),\n    (0xF959, 'M', u'陵'),\n    (0xF95A, 'M', u'讀'),\n    (0xF95B, 'M', u'拏'),\n    (0xF95C, 'M', u'樂'),\n    (0xF95D, 'M', u'諾'),\n    (0xF95E, 'M', u'丹'),\n    (0xF95F, 'M', u'寧'),\n    (0xF960, 'M', u'怒'),\n    (0xF961, 'M', u'率'),\n    (0xF962, 'M', u'異'),\n    (0xF963, 'M', u'北'),\n    (0xF964, 'M', u'磻'),\n    (0xF965, 'M', u'便'),\n    (0xF966, 'M', u'復'),\n    (0xF967, 'M', u'不'),\n    (0xF968, 'M', u'泌'),\n    (0xF969, 'M', u'數'),\n    (0xF96A, 'M', u'索'),\n    (0xF96B, 'M', u'參'),\n    (0xF96C, 'M', u'塞'),\n    (0xF96D, 'M', u'省'),\n    (0xF96E, 'M', u'葉'),\n    (0xF96F, 'M', u'說'),\n    (0xF970, 'M', u'殺'),\n    (0xF971, 'M', u'辰'),\n    (0xF972, 'M', u'沈'),\n    (0xF973, 'M', u'拾'),\n    (0xF974, 'M', u'若'),\n    (0xF975, 'M', u'掠'),\n    (0xF976, 'M', u'略'),\n    (0xF977, 'M', u'亮'),\n    (0xF978, 'M', u'兩'),\n    (0xF979, 'M', u'凉'),\n    ]\n\ndef _seg_40():\n    return [\n    (0xF97A, 'M', u'梁'),\n    (0xF97B, 'M', u'糧'),\n    (0xF97C, 'M', u'良'),\n    (0xF97D, 'M', u'諒'),\n    (0xF97E, 'M', u'量'),\n    (0xF97F, 'M', u'勵'),\n    (0xF980, 'M', u'呂'),\n    (0xF981, 'M', u'女'),\n    (0xF982, 'M', u'廬'),\n    (0xF983, 'M', u'旅'),\n    (0xF984, 'M', u'濾'),\n    (0xF985, 'M', u'礪'),\n    (0xF986, 'M', u'閭'),\n    (0xF987, 'M', u'驪'),\n    (0xF988, 'M', u'麗'),\n    (0xF989, 'M', u'黎'),\n    (0xF98A, 'M', u'力'),\n    (0xF98B, 'M', u'曆'),\n    (0xF98C, 'M', u'歷'),\n    (0xF98D, 'M', u'轢'),\n    (0xF98E, 'M', u'年'),\n    (0xF98F, 'M', u'憐'),\n    (0xF990, 'M', u'戀'),\n    (0xF991, 'M', u'撚'),\n    (0xF992, 'M', u'漣'),\n    (0xF993, 'M', u'煉'),\n    (0xF994, 'M', u'璉'),\n    (0xF995, 'M', u'秊'),\n    (0xF996, 'M', u'練'),\n    (0xF997, 'M', u'聯'),\n    (0xF998, 'M', u'輦'),\n    (0xF999, 'M', u'蓮'),\n    (0xF99A, 'M', u'連'),\n    (0xF99B, 'M', u'鍊'),\n    (0xF99C, 'M', u'列'),\n    (0xF99D, 'M', u'劣'),\n    (0xF99E, 'M', u'咽'),\n    (0xF99F, 'M', u'烈'),\n    (0xF9A0, 'M', u'裂'),\n    (0xF9A1, 'M', u'說'),\n    (0xF9A2, 'M', u'廉'),\n    (0xF9A3, 'M', u'念'),\n    (0xF9A4, 'M', u'捻'),\n    (0xF9A5, 'M', u'殮'),\n    (0xF9A6, 'M', u'簾'),\n    (0xF9A7, 'M', u'獵'),\n    (0xF9A8, 'M', u'令'),\n    (0xF9A9, 'M', u'囹'),\n    (0xF9AA, 'M', u'寧'),\n    (0xF9AB, 'M', u'嶺'),\n    (0xF9AC, 'M', u'怜'),\n    (0xF9AD, 'M', u'玲'),\n    (0xF9AE, 'M', u'瑩'),\n    (0xF9AF, 'M', u'羚'),\n    (0xF9B0, 'M', u'聆'),\n    (0xF9B1, 'M', u'鈴'),\n    (0xF9B2, 'M', u'零'),\n    (0xF9B3, 'M', u'靈'),\n    (0xF9B4, 'M', u'領'),\n    (0xF9B5, 'M', u'例'),\n    (0xF9B6, 'M', u'禮'),\n    (0xF9B7, 'M', u'醴'),\n    (0xF9B8, 'M', u'隸'),\n    (0xF9B9, 'M', u'惡'),\n    (0xF9BA, 'M', u'了'),\n    (0xF9BB, 'M', u'僚'),\n    (0xF9BC, 'M', u'寮'),\n    (0xF9BD, 'M', u'尿'),\n    (0xF9BE, 'M', u'料'),\n    (0xF9BF, 'M', u'樂'),\n    (0xF9C0, 'M', u'燎'),\n    (0xF9C1, 'M', u'療'),\n    (0xF9C2, 'M', u'蓼'),\n    (0xF9C3, 'M', u'遼'),\n    (0xF9C4, 'M', u'龍'),\n    (0xF9C5, 'M', u'暈'),\n    (0xF9C6, 'M', u'阮'),\n    (0xF9C7, 'M', u'劉'),\n    (0xF9C8, 'M', u'杻'),\n    (0xF9C9, 'M', u'柳'),\n    (0xF9CA, 'M', u'流'),\n    (0xF9CB, 'M', u'溜'),\n    (0xF9CC, 'M', u'琉'),\n    (0xF9CD, 'M', u'留'),\n    (0xF9CE, 'M', u'硫'),\n    (0xF9CF, 'M', u'紐'),\n    (0xF9D0, 'M', u'類'),\n    (0xF9D1, 'M', u'六'),\n    (0xF9D2, 'M', u'戮'),\n    (0xF9D3, 'M', u'陸'),\n    (0xF9D4, 'M', u'倫'),\n    (0xF9D5, 'M', u'崙'),\n    (0xF9D6, 'M', u'淪'),\n    (0xF9D7, 'M', u'輪'),\n    (0xF9D8, 'M', u'律'),\n    (0xF9D9, 'M', u'慄'),\n    (0xF9DA, 'M', u'栗'),\n    (0xF9DB, 'M', u'率'),\n    (0xF9DC, 'M', u'隆'),\n    (0xF9DD, 'M', u'利'),\n    ]\n\ndef _seg_41():\n    return [\n    (0xF9DE, 'M', u'吏'),\n    (0xF9DF, 'M', u'履'),\n    (0xF9E0, 'M', u'易'),\n    (0xF9E1, 'M', u'李'),\n    (0xF9E2, 'M', u'梨'),\n    (0xF9E3, 'M', u'泥'),\n    (0xF9E4, 'M', u'理'),\n    (0xF9E5, 'M', u'痢'),\n    (0xF9E6, 'M', u'罹'),\n    (0xF9E7, 'M', u'裏'),\n    (0xF9E8, 'M', u'裡'),\n    (0xF9E9, 'M', u'里'),\n    (0xF9EA, 'M', u'離'),\n    (0xF9EB, 'M', u'匿'),\n    (0xF9EC, 'M', u'溺'),\n    (0xF9ED, 'M', u'吝'),\n    (0xF9EE, 'M', u'燐'),\n    (0xF9EF, 'M', u'璘'),\n    (0xF9F0, 'M', u'藺'),\n    (0xF9F1, 'M', u'隣'),\n    (0xF9F2, 'M', u'鱗'),\n    (0xF9F3, 'M', u'麟'),\n    (0xF9F4, 'M', u'林'),\n    (0xF9F5, 'M', u'淋'),\n    (0xF9F6, 'M', u'臨'),\n    (0xF9F7, 'M', u'立'),\n    (0xF9F8, 'M', u'笠'),\n    (0xF9F9, 'M', u'粒'),\n    (0xF9FA, 'M', u'狀'),\n    (0xF9FB, 'M', u'炙'),\n    (0xF9FC, 'M', u'識'),\n    (0xF9FD, 'M', u'什'),\n    (0xF9FE, 'M', u'茶'),\n    (0xF9FF, 'M', u'刺'),\n    (0xFA00, 'M', u'切'),\n    (0xFA01, 'M', u'度'),\n    (0xFA02, 'M', u'拓'),\n    (0xFA03, 'M', u'糖'),\n    (0xFA04, 'M', u'宅'),\n    (0xFA05, 'M', u'洞'),\n    (0xFA06, 'M', u'暴'),\n    (0xFA07, 'M', u'輻'),\n    (0xFA08, 'M', u'行'),\n    (0xFA09, 'M', u'降'),\n    (0xFA0A, 'M', u'見'),\n    (0xFA0B, 'M', u'廓'),\n    (0xFA0C, 'M', u'兀'),\n    (0xFA0D, 'M', u'嗀'),\n    (0xFA0E, 'V'),\n    (0xFA10, 'M', u'塚'),\n    (0xFA11, 'V'),\n    (0xFA12, 'M', u'晴'),\n    (0xFA13, 'V'),\n    (0xFA15, 'M', u'凞'),\n    (0xFA16, 'M', u'猪'),\n    (0xFA17, 'M', u'益'),\n    (0xFA18, 'M', u'礼'),\n    (0xFA19, 'M', u'神'),\n    (0xFA1A, 'M', u'祥'),\n    (0xFA1B, 'M', u'福'),\n    (0xFA1C, 'M', u'靖'),\n    (0xFA1D, 'M', u'精'),\n    (0xFA1E, 'M', u'羽'),\n    (0xFA1F, 'V'),\n    (0xFA20, 'M', u'蘒'),\n    (0xFA21, 'V'),\n    (0xFA22, 'M', u'諸'),\n    (0xFA23, 'V'),\n    (0xFA25, 'M', u'逸'),\n    (0xFA26, 'M', u'都'),\n    (0xFA27, 'V'),\n    (0xFA2A, 'M', u'飯'),\n    (0xFA2B, 'M', u'飼'),\n    (0xFA2C, 'M', u'館'),\n    (0xFA2D, 'M', u'鶴'),\n    (0xFA2E, 'M', u'郞'),\n    (0xFA2F, 'M', u'隷'),\n    (0xFA30, 'M', u'侮'),\n    (0xFA31, 'M', u'僧'),\n    (0xFA32, 'M', u'免'),\n    (0xFA33, 'M', u'勉'),\n    (0xFA34, 'M', u'勤'),\n    (0xFA35, 'M', u'卑'),\n    (0xFA36, 'M', u'喝'),\n    (0xFA37, 'M', u'嘆'),\n    (0xFA38, 'M', u'器'),\n    (0xFA39, 'M', u'塀'),\n    (0xFA3A, 'M', u'墨'),\n    (0xFA3B, 'M', u'層'),\n    (0xFA3C, 'M', u'屮'),\n    (0xFA3D, 'M', u'悔'),\n    (0xFA3E, 'M', u'慨'),\n    (0xFA3F, 'M', u'憎'),\n    (0xFA40, 'M', u'懲'),\n    (0xFA41, 'M', u'敏'),\n    (0xFA42, 'M', u'既'),\n    (0xFA43, 'M', u'暑'),\n    (0xFA44, 'M', u'梅'),\n    (0xFA45, 'M', u'海'),\n    (0xFA46, 'M', u'渚'),\n    ]\n\ndef _seg_42():\n    return [\n    (0xFA47, 'M', u'漢'),\n    (0xFA48, 'M', u'煮'),\n    (0xFA49, 'M', u'爫'),\n    (0xFA4A, 'M', u'琢'),\n    (0xFA4B, 'M', u'碑'),\n    (0xFA4C, 'M', u'社'),\n    (0xFA4D, 'M', u'祉'),\n    (0xFA4E, 'M', u'祈'),\n    (0xFA4F, 'M', u'祐'),\n    (0xFA50, 'M', u'祖'),\n    (0xFA51, 'M', u'祝'),\n    (0xFA52, 'M', u'禍'),\n    (0xFA53, 'M', u'禎'),\n    (0xFA54, 'M', u'穀'),\n    (0xFA55, 'M', u'突'),\n    (0xFA56, 'M', u'節'),\n    (0xFA57, 'M', u'練'),\n    (0xFA58, 'M', u'縉'),\n    (0xFA59, 'M', u'繁'),\n    (0xFA5A, 'M', u'署'),\n    (0xFA5B, 'M', u'者'),\n    (0xFA5C, 'M', u'臭'),\n    (0xFA5D, 'M', u'艹'),\n    (0xFA5F, 'M', u'著'),\n    (0xFA60, 'M', u'褐'),\n    (0xFA61, 'M', u'視'),\n    (0xFA62, 'M', u'謁'),\n    (0xFA63, 'M', u'謹'),\n    (0xFA64, 'M', u'賓'),\n    (0xFA65, 'M', u'贈'),\n    (0xFA66, 'M', u'辶'),\n    (0xFA67, 'M', u'逸'),\n    (0xFA68, 'M', u'難'),\n    (0xFA69, 'M', u'響'),\n    (0xFA6A, 'M', u'頻'),\n    (0xFA6B, 'M', u'恵'),\n    (0xFA6C, 'M', u'𤋮'),\n    (0xFA6D, 'M', u'舘'),\n    (0xFA6E, 'X'),\n    (0xFA70, 'M', u'並'),\n    (0xFA71, 'M', u'况'),\n    (0xFA72, 'M', u'全'),\n    (0xFA73, 'M', u'侀'),\n    (0xFA74, 'M', u'充'),\n    (0xFA75, 'M', u'冀'),\n    (0xFA76, 'M', u'勇'),\n    (0xFA77, 'M', u'勺'),\n    (0xFA78, 'M', u'喝'),\n    (0xFA79, 'M', u'啕'),\n    (0xFA7A, 'M', u'喙'),\n    (0xFA7B, 'M', u'嗢'),\n    (0xFA7C, 'M', u'塚'),\n    (0xFA7D, 'M', u'墳'),\n    (0xFA7E, 'M', u'奄'),\n    (0xFA7F, 'M', u'奔'),\n    (0xFA80, 'M', u'婢'),\n    (0xFA81, 'M', u'嬨'),\n    (0xFA82, 'M', u'廒'),\n    (0xFA83, 'M', u'廙'),\n    (0xFA84, 'M', u'彩'),\n    (0xFA85, 'M', u'徭'),\n    (0xFA86, 'M', u'惘'),\n    (0xFA87, 'M', u'慎'),\n    (0xFA88, 'M', u'愈'),\n    (0xFA89, 'M', u'憎'),\n    (0xFA8A, 'M', u'慠'),\n    (0xFA8B, 'M', u'懲'),\n    (0xFA8C, 'M', u'戴'),\n    (0xFA8D, 'M', u'揄'),\n    (0xFA8E, 'M', u'搜'),\n    (0xFA8F, 'M', u'摒'),\n    (0xFA90, 'M', u'敖'),\n    (0xFA91, 'M', u'晴'),\n    (0xFA92, 'M', u'朗'),\n    (0xFA93, 'M', u'望'),\n    (0xFA94, 'M', u'杖'),\n    (0xFA95, 'M', u'歹'),\n    (0xFA96, 'M', u'殺'),\n    (0xFA97, 'M', u'流'),\n    (0xFA98, 'M', u'滛'),\n    (0xFA99, 'M', u'滋'),\n    (0xFA9A, 'M', u'漢'),\n    (0xFA9B, 'M', u'瀞'),\n    (0xFA9C, 'M', u'煮'),\n    (0xFA9D, 'M', u'瞧'),\n    (0xFA9E, 'M', u'爵'),\n    (0xFA9F, 'M', u'犯'),\n    (0xFAA0, 'M', u'猪'),\n    (0xFAA1, 'M', u'瑱'),\n    (0xFAA2, 'M', u'甆'),\n    (0xFAA3, 'M', u'画'),\n    (0xFAA4, 'M', u'瘝'),\n    (0xFAA5, 'M', u'瘟'),\n    (0xFAA6, 'M', u'益'),\n    (0xFAA7, 'M', u'盛'),\n    (0xFAA8, 'M', u'直'),\n    (0xFAA9, 'M', u'睊'),\n    (0xFAAA, 'M', u'着'),\n    (0xFAAB, 'M', u'磌'),\n    (0xFAAC, 'M', u'窱'),\n    ]\n\ndef _seg_43():\n    return [\n    (0xFAAD, 'M', u'節'),\n    (0xFAAE, 'M', u'类'),\n    (0xFAAF, 'M', u'絛'),\n    (0xFAB0, 'M', u'練'),\n    (0xFAB1, 'M', u'缾'),\n    (0xFAB2, 'M', u'者'),\n    (0xFAB3, 'M', u'荒'),\n    (0xFAB4, 'M', u'華'),\n    (0xFAB5, 'M', u'蝹'),\n    (0xFAB6, 'M', u'襁'),\n    (0xFAB7, 'M', u'覆'),\n    (0xFAB8, 'M', u'視'),\n    (0xFAB9, 'M', u'調'),\n    (0xFABA, 'M', u'諸'),\n    (0xFABB, 'M', u'請'),\n    (0xFABC, 'M', u'謁'),\n    (0xFABD, 'M', u'諾'),\n    (0xFABE, 'M', u'諭'),\n    (0xFABF, 'M', u'謹'),\n    (0xFAC0, 'M', u'變'),\n    (0xFAC1, 'M', u'贈'),\n    (0xFAC2, 'M', u'輸'),\n    (0xFAC3, 'M', u'遲'),\n    (0xFAC4, 'M', u'醙'),\n    (0xFAC5, 'M', u'鉶'),\n    (0xFAC6, 'M', u'陼'),\n    (0xFAC7, 'M', u'難'),\n    (0xFAC8, 'M', u'靖'),\n    (0xFAC9, 'M', u'韛'),\n    (0xFACA, 'M', u'響'),\n    (0xFACB, 'M', u'頋'),\n    (0xFACC, 'M', u'頻'),\n    (0xFACD, 'M', u'鬒'),\n    (0xFACE, 'M', u'龜'),\n    (0xFACF, 'M', u'𢡊'),\n    (0xFAD0, 'M', u'𢡄'),\n    (0xFAD1, 'M', u'𣏕'),\n    (0xFAD2, 'M', u'㮝'),\n    (0xFAD3, 'M', u'䀘'),\n    (0xFAD4, 'M', u'䀹'),\n    (0xFAD5, 'M', u'𥉉'),\n    (0xFAD6, 'M', u'𥳐'),\n    (0xFAD7, 'M', u'𧻓'),\n    (0xFAD8, 'M', u'齃'),\n    (0xFAD9, 'M', u'龎'),\n    (0xFADA, 'X'),\n    (0xFB00, 'M', u'ff'),\n    (0xFB01, 'M', u'fi'),\n    (0xFB02, 'M', u'fl'),\n    (0xFB03, 'M', u'ffi'),\n    (0xFB04, 'M', u'ffl'),\n    (0xFB05, 'M', u'st'),\n    (0xFB07, 'X'),\n    (0xFB13, 'M', u'մն'),\n    (0xFB14, 'M', u'մե'),\n    (0xFB15, 'M', u'մի'),\n    (0xFB16, 'M', u'վն'),\n    (0xFB17, 'M', u'մխ'),\n    (0xFB18, 'X'),\n    (0xFB1D, 'M', u'יִ'),\n    (0xFB1E, 'V'),\n    (0xFB1F, 'M', u'ײַ'),\n    (0xFB20, 'M', u'ע'),\n    (0xFB21, 'M', u'א'),\n    (0xFB22, 'M', u'ד'),\n    (0xFB23, 'M', u'ה'),\n    (0xFB24, 'M', u'כ'),\n    (0xFB25, 'M', u'ל'),\n    (0xFB26, 'M', u'ם'),\n    (0xFB27, 'M', u'ר'),\n    (0xFB28, 'M', u'ת'),\n    (0xFB29, '3', u'+'),\n    (0xFB2A, 'M', u'שׁ'),\n    (0xFB2B, 'M', u'שׂ'),\n    (0xFB2C, 'M', u'שּׁ'),\n    (0xFB2D, 'M', u'שּׂ'),\n    (0xFB2E, 'M', u'אַ'),\n    (0xFB2F, 'M', u'אָ'),\n    (0xFB30, 'M', u'אּ'),\n    (0xFB31, 'M', u'בּ'),\n    (0xFB32, 'M', u'גּ'),\n    (0xFB33, 'M', u'דּ'),\n    (0xFB34, 'M', u'הּ'),\n    (0xFB35, 'M', u'וּ'),\n    (0xFB36, 'M', u'זּ'),\n    (0xFB37, 'X'),\n    (0xFB38, 'M', u'טּ'),\n    (0xFB39, 'M', u'יּ'),\n    (0xFB3A, 'M', u'ךּ'),\n    (0xFB3B, 'M', u'כּ'),\n    (0xFB3C, 'M', u'לּ'),\n    (0xFB3D, 'X'),\n    (0xFB3E, 'M', u'מּ'),\n    (0xFB3F, 'X'),\n    (0xFB40, 'M', u'נּ'),\n    (0xFB41, 'M', u'סּ'),\n    (0xFB42, 'X'),\n    (0xFB43, 'M', u'ףּ'),\n    (0xFB44, 'M', u'פּ'),\n    (0xFB45, 'X'),\n    ]\n\ndef _seg_44():\n    return [\n    (0xFB46, 'M', u'צּ'),\n    (0xFB47, 'M', u'קּ'),\n    (0xFB48, 'M', u'רּ'),\n    (0xFB49, 'M', u'שּ'),\n    (0xFB4A, 'M', u'תּ'),\n    (0xFB4B, 'M', u'וֹ'),\n    (0xFB4C, 'M', u'בֿ'),\n    (0xFB4D, 'M', u'כֿ'),\n    (0xFB4E, 'M', u'פֿ'),\n    (0xFB4F, 'M', u'אל'),\n    (0xFB50, 'M', u'ٱ'),\n    (0xFB52, 'M', u'ٻ'),\n    (0xFB56, 'M', u'پ'),\n    (0xFB5A, 'M', u'ڀ'),\n    (0xFB5E, 'M', u'ٺ'),\n    (0xFB62, 'M', u'ٿ'),\n    (0xFB66, 'M', u'ٹ'),\n    (0xFB6A, 'M', u'ڤ'),\n    (0xFB6E, 'M', u'ڦ'),\n    (0xFB72, 'M', u'ڄ'),\n    (0xFB76, 'M', u'ڃ'),\n    (0xFB7A, 'M', u'چ'),\n    (0xFB7E, 'M', u'ڇ'),\n    (0xFB82, 'M', u'ڍ'),\n    (0xFB84, 'M', u'ڌ'),\n    (0xFB86, 'M', u'ڎ'),\n    (0xFB88, 'M', u'ڈ'),\n    (0xFB8A, 'M', u'ژ'),\n    (0xFB8C, 'M', u'ڑ'),\n    (0xFB8E, 'M', u'ک'),\n    (0xFB92, 'M', u'گ'),\n    (0xFB96, 'M', u'ڳ'),\n    (0xFB9A, 'M', u'ڱ'),\n    (0xFB9E, 'M', u'ں'),\n    (0xFBA0, 'M', u'ڻ'),\n    (0xFBA4, 'M', u'ۀ'),\n    (0xFBA6, 'M', u'ہ'),\n    (0xFBAA, 'M', u'ھ'),\n    (0xFBAE, 'M', u'ے'),\n    (0xFBB0, 'M', u'ۓ'),\n    (0xFBB2, 'V'),\n    (0xFBC2, 'X'),\n    (0xFBD3, 'M', u'ڭ'),\n    (0xFBD7, 'M', u'ۇ'),\n    (0xFBD9, 'M', u'ۆ'),\n    (0xFBDB, 'M', u'ۈ'),\n    (0xFBDD, 'M', u'ۇٴ'),\n    (0xFBDE, 'M', u'ۋ'),\n    (0xFBE0, 'M', u'ۅ'),\n    (0xFBE2, 'M', u'ۉ'),\n    (0xFBE4, 'M', u'ې'),\n    (0xFBE8, 'M', u'ى'),\n    (0xFBEA, 'M', u'ئا'),\n    (0xFBEC, 'M', u'ئە'),\n    (0xFBEE, 'M', u'ئو'),\n    (0xFBF0, 'M', u'ئۇ'),\n    (0xFBF2, 'M', u'ئۆ'),\n    (0xFBF4, 'M', u'ئۈ'),\n    (0xFBF6, 'M', u'ئې'),\n    (0xFBF9, 'M', u'ئى'),\n    (0xFBFC, 'M', u'ی'),\n    (0xFC00, 'M', u'ئج'),\n    (0xFC01, 'M', u'ئح'),\n    (0xFC02, 'M', u'ئم'),\n    (0xFC03, 'M', u'ئى'),\n    (0xFC04, 'M', u'ئي'),\n    (0xFC05, 'M', u'بج'),\n    (0xFC06, 'M', u'بح'),\n    (0xFC07, 'M', u'بخ'),\n    (0xFC08, 'M', u'بم'),\n    (0xFC09, 'M', u'بى'),\n    (0xFC0A, 'M', u'بي'),\n    (0xFC0B, 'M', u'تج'),\n    (0xFC0C, 'M', u'تح'),\n    (0xFC0D, 'M', u'تخ'),\n    (0xFC0E, 'M', u'تم'),\n    (0xFC0F, 'M', u'تى'),\n    (0xFC10, 'M', u'تي'),\n    (0xFC11, 'M', u'ثج'),\n    (0xFC12, 'M', u'ثم'),\n    (0xFC13, 'M', u'ثى'),\n    (0xFC14, 'M', u'ثي'),\n    (0xFC15, 'M', u'جح'),\n    (0xFC16, 'M', u'جم'),\n    (0xFC17, 'M', u'حج'),\n    (0xFC18, 'M', u'حم'),\n    (0xFC19, 'M', u'خج'),\n    (0xFC1A, 'M', u'خح'),\n    (0xFC1B, 'M', u'خم'),\n    (0xFC1C, 'M', u'سج'),\n    (0xFC1D, 'M', u'سح'),\n    (0xFC1E, 'M', u'سخ'),\n    (0xFC1F, 'M', u'سم'),\n    (0xFC20, 'M', u'صح'),\n    (0xFC21, 'M', u'صم'),\n    (0xFC22, 'M', u'ضج'),\n    (0xFC23, 'M', u'ضح'),\n    (0xFC24, 'M', u'ضخ'),\n    (0xFC25, 'M', u'ضم'),\n    (0xFC26, 'M', u'طح'),\n    ]\n\ndef _seg_45():\n    return [\n    (0xFC27, 'M', u'طم'),\n    (0xFC28, 'M', u'ظم'),\n    (0xFC29, 'M', u'عج'),\n    (0xFC2A, 'M', u'عم'),\n    (0xFC2B, 'M', u'غج'),\n    (0xFC2C, 'M', u'غم'),\n    (0xFC2D, 'M', u'فج'),\n    (0xFC2E, 'M', u'فح'),\n    (0xFC2F, 'M', u'فخ'),\n    (0xFC30, 'M', u'فم'),\n    (0xFC31, 'M', u'فى'),\n    (0xFC32, 'M', u'في'),\n    (0xFC33, 'M', u'قح'),\n    (0xFC34, 'M', u'قم'),\n    (0xFC35, 'M', u'قى'),\n    (0xFC36, 'M', u'قي'),\n    (0xFC37, 'M', u'كا'),\n    (0xFC38, 'M', u'كج'),\n    (0xFC39, 'M', u'كح'),\n    (0xFC3A, 'M', u'كخ'),\n    (0xFC3B, 'M', u'كل'),\n    (0xFC3C, 'M', u'كم'),\n    (0xFC3D, 'M', u'كى'),\n    (0xFC3E, 'M', u'كي'),\n    (0xFC3F, 'M', u'لج'),\n    (0xFC40, 'M', u'لح'),\n    (0xFC41, 'M', u'لخ'),\n    (0xFC42, 'M', u'لم'),\n    (0xFC43, 'M', u'لى'),\n    (0xFC44, 'M', u'لي'),\n    (0xFC45, 'M', u'مج'),\n    (0xFC46, 'M', u'مح'),\n    (0xFC47, 'M', u'مخ'),\n    (0xFC48, 'M', u'مم'),\n    (0xFC49, 'M', u'مى'),\n    (0xFC4A, 'M', u'مي'),\n    (0xFC4B, 'M', u'نج'),\n    (0xFC4C, 'M', u'نح'),\n    (0xFC4D, 'M', u'نخ'),\n    (0xFC4E, 'M', u'نم'),\n    (0xFC4F, 'M', u'نى'),\n    (0xFC50, 'M', u'ني'),\n    (0xFC51, 'M', u'هج'),\n    (0xFC52, 'M', u'هم'),\n    (0xFC53, 'M', u'هى'),\n    (0xFC54, 'M', u'هي'),\n    (0xFC55, 'M', u'يج'),\n    (0xFC56, 'M', u'يح'),\n    (0xFC57, 'M', u'يخ'),\n    (0xFC58, 'M', u'يم'),\n    (0xFC59, 'M', u'يى'),\n    (0xFC5A, 'M', u'يي'),\n    (0xFC5B, 'M', u'ذٰ'),\n    (0xFC5C, 'M', u'رٰ'),\n    (0xFC5D, 'M', u'ىٰ'),\n    (0xFC5E, '3', u' ٌّ'),\n    (0xFC5F, '3', u' ٍّ'),\n    (0xFC60, '3', u' َّ'),\n    (0xFC61, '3', u' ُّ'),\n    (0xFC62, '3', u' ِّ'),\n    (0xFC63, '3', u' ّٰ'),\n    (0xFC64, 'M', u'ئر'),\n    (0xFC65, 'M', u'ئز'),\n    (0xFC66, 'M', u'ئم'),\n    (0xFC67, 'M', u'ئن'),\n    (0xFC68, 'M', u'ئى'),\n    (0xFC69, 'M', u'ئي'),\n    (0xFC6A, 'M', u'بر'),\n    (0xFC6B, 'M', u'بز'),\n    (0xFC6C, 'M', u'بم'),\n    (0xFC6D, 'M', u'بن'),\n    (0xFC6E, 'M', u'بى'),\n    (0xFC6F, 'M', u'بي'),\n    (0xFC70, 'M', u'تر'),\n    (0xFC71, 'M', u'تز'),\n    (0xFC72, 'M', u'تم'),\n    (0xFC73, 'M', u'تن'),\n    (0xFC74, 'M', u'تى'),\n    (0xFC75, 'M', u'تي'),\n    (0xFC76, 'M', u'ثر'),\n    (0xFC77, 'M', u'ثز'),\n    (0xFC78, 'M', u'ثم'),\n    (0xFC79, 'M', u'ثن'),\n    (0xFC7A, 'M', u'ثى'),\n    (0xFC7B, 'M', u'ثي'),\n    (0xFC7C, 'M', u'فى'),\n    (0xFC7D, 'M', u'في'),\n    (0xFC7E, 'M', u'قى'),\n    (0xFC7F, 'M', u'قي'),\n    (0xFC80, 'M', u'كا'),\n    (0xFC81, 'M', u'كل'),\n    (0xFC82, 'M', u'كم'),\n    (0xFC83, 'M', u'كى'),\n    (0xFC84, 'M', u'كي'),\n    (0xFC85, 'M', u'لم'),\n    (0xFC86, 'M', u'لى'),\n    (0xFC87, 'M', u'لي'),\n    (0xFC88, 'M', u'ما'),\n    (0xFC89, 'M', u'مم'),\n    (0xFC8A, 'M', u'نر'),\n    ]\n\ndef _seg_46():\n    return [\n    (0xFC8B, 'M', u'نز'),\n    (0xFC8C, 'M', u'نم'),\n    (0xFC8D, 'M', u'نن'),\n    (0xFC8E, 'M', u'نى'),\n    (0xFC8F, 'M', u'ني'),\n    (0xFC90, 'M', u'ىٰ'),\n    (0xFC91, 'M', u'ير'),\n    (0xFC92, 'M', u'يز'),\n    (0xFC93, 'M', u'يم'),\n    (0xFC94, 'M', u'ين'),\n    (0xFC95, 'M', u'يى'),\n    (0xFC96, 'M', u'يي'),\n    (0xFC97, 'M', u'ئج'),\n    (0xFC98, 'M', u'ئح'),\n    (0xFC99, 'M', u'ئخ'),\n    (0xFC9A, 'M', u'ئم'),\n    (0xFC9B, 'M', u'ئه'),\n    (0xFC9C, 'M', u'بج'),\n    (0xFC9D, 'M', u'بح'),\n    (0xFC9E, 'M', u'بخ'),\n    (0xFC9F, 'M', u'بم'),\n    (0xFCA0, 'M', u'به'),\n    (0xFCA1, 'M', u'تج'),\n    (0xFCA2, 'M', u'تح'),\n    (0xFCA3, 'M', u'تخ'),\n    (0xFCA4, 'M', u'تم'),\n    (0xFCA5, 'M', u'ته'),\n    (0xFCA6, 'M', u'ثم'),\n    (0xFCA7, 'M', u'جح'),\n    (0xFCA8, 'M', u'جم'),\n    (0xFCA9, 'M', u'حج'),\n    (0xFCAA, 'M', u'حم'),\n    (0xFCAB, 'M', u'خج'),\n    (0xFCAC, 'M', u'خم'),\n    (0xFCAD, 'M', u'سج'),\n    (0xFCAE, 'M', u'سح'),\n    (0xFCAF, 'M', u'سخ'),\n    (0xFCB0, 'M', u'سم'),\n    (0xFCB1, 'M', u'صح'),\n    (0xFCB2, 'M', u'صخ'),\n    (0xFCB3, 'M', u'صم'),\n    (0xFCB4, 'M', u'ضج'),\n    (0xFCB5, 'M', u'ضح'),\n    (0xFCB6, 'M', u'ضخ'),\n    (0xFCB7, 'M', u'ضم'),\n    (0xFCB8, 'M', u'طح'),\n    (0xFCB9, 'M', u'ظم'),\n    (0xFCBA, 'M', u'عج'),\n    (0xFCBB, 'M', u'عم'),\n    (0xFCBC, 'M', u'غج'),\n    (0xFCBD, 'M', u'غم'),\n    (0xFCBE, 'M', u'فج'),\n    (0xFCBF, 'M', u'فح'),\n    (0xFCC0, 'M', u'فخ'),\n    (0xFCC1, 'M', u'فم'),\n    (0xFCC2, 'M', u'قح'),\n    (0xFCC3, 'M', u'قم'),\n    (0xFCC4, 'M', u'كج'),\n    (0xFCC5, 'M', u'كح'),\n    (0xFCC6, 'M', u'كخ'),\n    (0xFCC7, 'M', u'كل'),\n    (0xFCC8, 'M', u'كم'),\n    (0xFCC9, 'M', u'لج'),\n    (0xFCCA, 'M', u'لح'),\n    (0xFCCB, 'M', u'لخ'),\n    (0xFCCC, 'M', u'لم'),\n    (0xFCCD, 'M', u'له'),\n    (0xFCCE, 'M', u'مج'),\n    (0xFCCF, 'M', u'مح'),\n    (0xFCD0, 'M', u'مخ'),\n    (0xFCD1, 'M', u'مم'),\n    (0xFCD2, 'M', u'نج'),\n    (0xFCD3, 'M', u'نح'),\n    (0xFCD4, 'M', u'نخ'),\n    (0xFCD5, 'M', u'نم'),\n    (0xFCD6, 'M', u'نه'),\n    (0xFCD7, 'M', u'هج'),\n    (0xFCD8, 'M', u'هم'),\n    (0xFCD9, 'M', u'هٰ'),\n    (0xFCDA, 'M', u'يج'),\n    (0xFCDB, 'M', u'يح'),\n    (0xFCDC, 'M', u'يخ'),\n    (0xFCDD, 'M', u'يم'),\n    (0xFCDE, 'M', u'يه'),\n    (0xFCDF, 'M', u'ئم'),\n    (0xFCE0, 'M', u'ئه'),\n    (0xFCE1, 'M', u'بم'),\n    (0xFCE2, 'M', u'به'),\n    (0xFCE3, 'M', u'تم'),\n    (0xFCE4, 'M', u'ته'),\n    (0xFCE5, 'M', u'ثم'),\n    (0xFCE6, 'M', u'ثه'),\n    (0xFCE7, 'M', u'سم'),\n    (0xFCE8, 'M', u'سه'),\n    (0xFCE9, 'M', u'شم'),\n    (0xFCEA, 'M', u'شه'),\n    (0xFCEB, 'M', u'كل'),\n    (0xFCEC, 'M', u'كم'),\n    (0xFCED, 'M', u'لم'),\n    (0xFCEE, 'M', u'نم'),\n    ]\n\ndef _seg_47():\n    return [\n    (0xFCEF, 'M', u'نه'),\n    (0xFCF0, 'M', u'يم'),\n    (0xFCF1, 'M', u'يه'),\n    (0xFCF2, 'M', u'ـَّ'),\n    (0xFCF3, 'M', u'ـُّ'),\n    (0xFCF4, 'M', u'ـِّ'),\n    (0xFCF5, 'M', u'طى'),\n    (0xFCF6, 'M', u'طي'),\n    (0xFCF7, 'M', u'عى'),\n    (0xFCF8, 'M', u'عي'),\n    (0xFCF9, 'M', u'غى'),\n    (0xFCFA, 'M', u'غي'),\n    (0xFCFB, 'M', u'سى'),\n    (0xFCFC, 'M', u'سي'),\n    (0xFCFD, 'M', u'شى'),\n    (0xFCFE, 'M', u'شي'),\n    (0xFCFF, 'M', u'حى'),\n    (0xFD00, 'M', u'حي'),\n    (0xFD01, 'M', u'جى'),\n    (0xFD02, 'M', u'جي'),\n    (0xFD03, 'M', u'خى'),\n    (0xFD04, 'M', u'خي'),\n    (0xFD05, 'M', u'صى'),\n    (0xFD06, 'M', u'صي'),\n    (0xFD07, 'M', u'ضى'),\n    (0xFD08, 'M', u'ضي'),\n    (0xFD09, 'M', u'شج'),\n    (0xFD0A, 'M', u'شح'),\n    (0xFD0B, 'M', u'شخ'),\n    (0xFD0C, 'M', u'شم'),\n    (0xFD0D, 'M', u'شر'),\n    (0xFD0E, 'M', u'سر'),\n    (0xFD0F, 'M', u'صر'),\n    (0xFD10, 'M', u'ضر'),\n    (0xFD11, 'M', u'طى'),\n    (0xFD12, 'M', u'طي'),\n    (0xFD13, 'M', u'عى'),\n    (0xFD14, 'M', u'عي'),\n    (0xFD15, 'M', u'غى'),\n    (0xFD16, 'M', u'غي'),\n    (0xFD17, 'M', u'سى'),\n    (0xFD18, 'M', u'سي'),\n    (0xFD19, 'M', u'شى'),\n    (0xFD1A, 'M', u'شي'),\n    (0xFD1B, 'M', u'حى'),\n    (0xFD1C, 'M', u'حي'),\n    (0xFD1D, 'M', u'جى'),\n    (0xFD1E, 'M', u'جي'),\n    (0xFD1F, 'M', u'خى'),\n    (0xFD20, 'M', u'خي'),\n    (0xFD21, 'M', u'صى'),\n    (0xFD22, 'M', u'صي'),\n    (0xFD23, 'M', u'ضى'),\n    (0xFD24, 'M', u'ضي'),\n    (0xFD25, 'M', u'شج'),\n    (0xFD26, 'M', u'شح'),\n    (0xFD27, 'M', u'شخ'),\n    (0xFD28, 'M', u'شم'),\n    (0xFD29, 'M', u'شر'),\n    (0xFD2A, 'M', u'سر'),\n    (0xFD2B, 'M', u'صر'),\n    (0xFD2C, 'M', u'ضر'),\n    (0xFD2D, 'M', u'شج'),\n    (0xFD2E, 'M', u'شح'),\n    (0xFD2F, 'M', u'شخ'),\n    (0xFD30, 'M', u'شم'),\n    (0xFD31, 'M', u'سه'),\n    (0xFD32, 'M', u'شه'),\n    (0xFD33, 'M', u'طم'),\n    (0xFD34, 'M', u'سج'),\n    (0xFD35, 'M', u'سح'),\n    (0xFD36, 'M', u'سخ'),\n    (0xFD37, 'M', u'شج'),\n    (0xFD38, 'M', u'شح'),\n    (0xFD39, 'M', u'شخ'),\n    (0xFD3A, 'M', u'طم'),\n    (0xFD3B, 'M', u'ظم'),\n    (0xFD3C, 'M', u'اً'),\n    (0xFD3E, 'V'),\n    (0xFD40, 'X'),\n    (0xFD50, 'M', u'تجم'),\n    (0xFD51, 'M', u'تحج'),\n    (0xFD53, 'M', u'تحم'),\n    (0xFD54, 'M', u'تخم'),\n    (0xFD55, 'M', u'تمج'),\n    (0xFD56, 'M', u'تمح'),\n    (0xFD57, 'M', u'تمخ'),\n    (0xFD58, 'M', u'جمح'),\n    (0xFD5A, 'M', u'حمي'),\n    (0xFD5B, 'M', u'حمى'),\n    (0xFD5C, 'M', u'سحج'),\n    (0xFD5D, 'M', u'سجح'),\n    (0xFD5E, 'M', u'سجى'),\n    (0xFD5F, 'M', u'سمح'),\n    (0xFD61, 'M', u'سمج'),\n    (0xFD62, 'M', u'سمم'),\n    (0xFD64, 'M', u'صحح'),\n    (0xFD66, 'M', u'صمم'),\n    (0xFD67, 'M', u'شحم'),\n    (0xFD69, 'M', u'شجي'),\n    ]\n\ndef _seg_48():\n    return [\n    (0xFD6A, 'M', u'شمخ'),\n    (0xFD6C, 'M', u'شمم'),\n    (0xFD6E, 'M', u'ضحى'),\n    (0xFD6F, 'M', u'ضخم'),\n    (0xFD71, 'M', u'طمح'),\n    (0xFD73, 'M', u'طمم'),\n    (0xFD74, 'M', u'طمي'),\n    (0xFD75, 'M', u'عجم'),\n    (0xFD76, 'M', u'عمم'),\n    (0xFD78, 'M', u'عمى'),\n    (0xFD79, 'M', u'غمم'),\n    (0xFD7A, 'M', u'غمي'),\n    (0xFD7B, 'M', u'غمى'),\n    (0xFD7C, 'M', u'فخم'),\n    (0xFD7E, 'M', u'قمح'),\n    (0xFD7F, 'M', u'قمم'),\n    (0xFD80, 'M', u'لحم'),\n    (0xFD81, 'M', u'لحي'),\n    (0xFD82, 'M', u'لحى'),\n    (0xFD83, 'M', u'لجج'),\n    (0xFD85, 'M', u'لخم'),\n    (0xFD87, 'M', u'لمح'),\n    (0xFD89, 'M', u'محج'),\n    (0xFD8A, 'M', u'محم'),\n    (0xFD8B, 'M', u'محي'),\n    (0xFD8C, 'M', u'مجح'),\n    (0xFD8D, 'M', u'مجم'),\n    (0xFD8E, 'M', u'مخج'),\n    (0xFD8F, 'M', u'مخم'),\n    (0xFD90, 'X'),\n    (0xFD92, 'M', u'مجخ'),\n    (0xFD93, 'M', u'همج'),\n    (0xFD94, 'M', u'همم'),\n    (0xFD95, 'M', u'نحم'),\n    (0xFD96, 'M', u'نحى'),\n    (0xFD97, 'M', u'نجم'),\n    (0xFD99, 'M', u'نجى'),\n    (0xFD9A, 'M', u'نمي'),\n    (0xFD9B, 'M', u'نمى'),\n    (0xFD9C, 'M', u'يمم'),\n    (0xFD9E, 'M', u'بخي'),\n    (0xFD9F, 'M', u'تجي'),\n    (0xFDA0, 'M', u'تجى'),\n    (0xFDA1, 'M', u'تخي'),\n    (0xFDA2, 'M', u'تخى'),\n    (0xFDA3, 'M', u'تمي'),\n    (0xFDA4, 'M', u'تمى'),\n    (0xFDA5, 'M', u'جمي'),\n    (0xFDA6, 'M', u'جحى'),\n    (0xFDA7, 'M', u'جمى'),\n    (0xFDA8, 'M', u'سخى'),\n    (0xFDA9, 'M', u'صحي'),\n    (0xFDAA, 'M', u'شحي'),\n    (0xFDAB, 'M', u'ضحي'),\n    (0xFDAC, 'M', u'لجي'),\n    (0xFDAD, 'M', u'لمي'),\n    (0xFDAE, 'M', u'يحي'),\n    (0xFDAF, 'M', u'يجي'),\n    (0xFDB0, 'M', u'يمي'),\n    (0xFDB1, 'M', u'ممي'),\n    (0xFDB2, 'M', u'قمي'),\n    (0xFDB3, 'M', u'نحي'),\n    (0xFDB4, 'M', u'قمح'),\n    (0xFDB5, 'M', u'لحم'),\n    (0xFDB6, 'M', u'عمي'),\n    (0xFDB7, 'M', u'كمي'),\n    (0xFDB8, 'M', u'نجح'),\n    (0xFDB9, 'M', u'مخي'),\n    (0xFDBA, 'M', u'لجم'),\n    (0xFDBB, 'M', u'كمم'),\n    (0xFDBC, 'M', u'لجم'),\n    (0xFDBD, 'M', u'نجح'),\n    (0xFDBE, 'M', u'جحي'),\n    (0xFDBF, 'M', u'حجي'),\n    (0xFDC0, 'M', u'مجي'),\n    (0xFDC1, 'M', u'فمي'),\n    (0xFDC2, 'M', u'بحي'),\n    (0xFDC3, 'M', u'كمم'),\n    (0xFDC4, 'M', u'عجم'),\n    (0xFDC5, 'M', u'صمم'),\n    (0xFDC6, 'M', u'سخي'),\n    (0xFDC7, 'M', u'نجي'),\n    (0xFDC8, 'X'),\n    (0xFDF0, 'M', u'صلے'),\n    (0xFDF1, 'M', u'قلے'),\n    (0xFDF2, 'M', u'الله'),\n    (0xFDF3, 'M', u'اكبر'),\n    (0xFDF4, 'M', u'محمد'),\n    (0xFDF5, 'M', u'صلعم'),\n    (0xFDF6, 'M', u'رسول'),\n    (0xFDF7, 'M', u'عليه'),\n    (0xFDF8, 'M', u'وسلم'),\n    (0xFDF9, 'M', u'صلى'),\n    (0xFDFA, '3', u'صلى الله عليه وسلم'),\n    (0xFDFB, '3', u'جل جلاله'),\n    (0xFDFC, 'M', u'ریال'),\n    (0xFDFD, 'V'),\n    (0xFDFE, 'X'),\n    (0xFE00, 'I'),\n    (0xFE10, '3', u','),\n    ]\n\ndef _seg_49():\n    return [\n    (0xFE11, 'M', u'、'),\n    (0xFE12, 'X'),\n    (0xFE13, '3', u':'),\n    (0xFE14, '3', u';'),\n    (0xFE15, '3', u'!'),\n    (0xFE16, '3', u'?'),\n    (0xFE17, 'M', u'〖'),\n    (0xFE18, 'M', u'〗'),\n    (0xFE19, 'X'),\n    (0xFE20, 'V'),\n    (0xFE30, 'X'),\n    (0xFE31, 'M', u'—'),\n    (0xFE32, 'M', u'–'),\n    (0xFE33, '3', u'_'),\n    (0xFE35, '3', u'('),\n    (0xFE36, '3', u')'),\n    (0xFE37, '3', u'{'),\n    (0xFE38, '3', u'}'),\n    (0xFE39, 'M', u'〔'),\n    (0xFE3A, 'M', u'〕'),\n    (0xFE3B, 'M', u'【'),\n    (0xFE3C, 'M', u'】'),\n    (0xFE3D, 'M', u'《'),\n    (0xFE3E, 'M', u'》'),\n    (0xFE3F, 'M', u'〈'),\n    (0xFE40, 'M', u'〉'),\n    (0xFE41, 'M', u'「'),\n    (0xFE42, 'M', u'」'),\n    (0xFE43, 'M', u'『'),\n    (0xFE44, 'M', u'』'),\n    (0xFE45, 'V'),\n    (0xFE47, '3', u'['),\n    (0xFE48, '3', u']'),\n    (0xFE49, '3', u' ̅'),\n    (0xFE4D, '3', u'_'),\n    (0xFE50, '3', u','),\n    (0xFE51, 'M', u'、'),\n    (0xFE52, 'X'),\n    (0xFE54, '3', u';'),\n    (0xFE55, '3', u':'),\n    (0xFE56, '3', u'?'),\n    (0xFE57, '3', u'!'),\n    (0xFE58, 'M', u'—'),\n    (0xFE59, '3', u'('),\n    (0xFE5A, '3', u')'),\n    (0xFE5B, '3', u'{'),\n    (0xFE5C, '3', u'}'),\n    (0xFE5D, 'M', u'〔'),\n    (0xFE5E, 'M', u'〕'),\n    (0xFE5F, '3', u'#'),\n    (0xFE60, '3', u'&'),\n    (0xFE61, '3', u'*'),\n    (0xFE62, '3', u'+'),\n    (0xFE63, 'M', u'-'),\n    (0xFE64, '3', u'<'),\n    (0xFE65, '3', u'>'),\n    (0xFE66, '3', u'='),\n    (0xFE67, 'X'),\n    (0xFE68, '3', u'\\\\'),\n    (0xFE69, '3', u'$'),\n    (0xFE6A, '3', u'%'),\n    (0xFE6B, '3', u'@'),\n    (0xFE6C, 'X'),\n    (0xFE70, '3', u' ً'),\n    (0xFE71, 'M', u'ـً'),\n    (0xFE72, '3', u' ٌ'),\n    (0xFE73, 'V'),\n    (0xFE74, '3', u' ٍ'),\n    (0xFE75, 'X'),\n    (0xFE76, '3', u' َ'),\n    (0xFE77, 'M', u'ـَ'),\n    (0xFE78, '3', u' ُ'),\n    (0xFE79, 'M', u'ـُ'),\n    (0xFE7A, '3', u' ِ'),\n    (0xFE7B, 'M', u'ـِ'),\n    (0xFE7C, '3', u' ّ'),\n    (0xFE7D, 'M', u'ـّ'),\n    (0xFE7E, '3', u' ْ'),\n    (0xFE7F, 'M', u'ـْ'),\n    (0xFE80, 'M', u'ء'),\n    (0xFE81, 'M', u'آ'),\n    (0xFE83, 'M', u'أ'),\n    (0xFE85, 'M', u'ؤ'),\n    (0xFE87, 'M', u'إ'),\n    (0xFE89, 'M', u'ئ'),\n    (0xFE8D, 'M', u'ا'),\n    (0xFE8F, 'M', u'ب'),\n    (0xFE93, 'M', u'ة'),\n    (0xFE95, 'M', u'ت'),\n    (0xFE99, 'M', u'ث'),\n    (0xFE9D, 'M', u'ج'),\n    (0xFEA1, 'M', u'ح'),\n    (0xFEA5, 'M', u'خ'),\n    (0xFEA9, 'M', u'د'),\n    (0xFEAB, 'M', u'ذ'),\n    (0xFEAD, 'M', u'ر'),\n    (0xFEAF, 'M', u'ز'),\n    (0xFEB1, 'M', u'س'),\n    (0xFEB5, 'M', u'ش'),\n    (0xFEB9, 'M', u'ص'),\n    ]\n\ndef _seg_50():\n    return [\n    (0xFEBD, 'M', u'ض'),\n    (0xFEC1, 'M', u'ط'),\n    (0xFEC5, 'M', u'ظ'),\n    (0xFEC9, 'M', u'ع'),\n    (0xFECD, 'M', u'غ'),\n    (0xFED1, 'M', u'ف'),\n    (0xFED5, 'M', u'ق'),\n    (0xFED9, 'M', u'ك'),\n    (0xFEDD, 'M', u'ل'),\n    (0xFEE1, 'M', u'م'),\n    (0xFEE5, 'M', u'ن'),\n    (0xFEE9, 'M', u'ه'),\n    (0xFEED, 'M', u'و'),\n    (0xFEEF, 'M', u'ى'),\n    (0xFEF1, 'M', u'ي'),\n    (0xFEF5, 'M', u'لآ'),\n    (0xFEF7, 'M', u'لأ'),\n    (0xFEF9, 'M', u'لإ'),\n    (0xFEFB, 'M', u'لا'),\n    (0xFEFD, 'X'),\n    (0xFEFF, 'I'),\n    (0xFF00, 'X'),\n    (0xFF01, '3', u'!'),\n    (0xFF02, '3', u'\"'),\n    (0xFF03, '3', u'#'),\n    (0xFF04, '3', u'$'),\n    (0xFF05, '3', u'%'),\n    (0xFF06, '3', u'&'),\n    (0xFF07, '3', u'\\''),\n    (0xFF08, '3', u'('),\n    (0xFF09, '3', u')'),\n    (0xFF0A, '3', u'*'),\n    (0xFF0B, '3', u'+'),\n    (0xFF0C, '3', u','),\n    (0xFF0D, 'M', u'-'),\n    (0xFF0E, 'M', u'.'),\n    (0xFF0F, '3', u'/'),\n    (0xFF10, 'M', u'0'),\n    (0xFF11, 'M', u'1'),\n    (0xFF12, 'M', u'2'),\n    (0xFF13, 'M', u'3'),\n    (0xFF14, 'M', u'4'),\n    (0xFF15, 'M', u'5'),\n    (0xFF16, 'M', u'6'),\n    (0xFF17, 'M', u'7'),\n    (0xFF18, 'M', u'8'),\n    (0xFF19, 'M', u'9'),\n    (0xFF1A, '3', u':'),\n    (0xFF1B, '3', u';'),\n    (0xFF1C, '3', u'<'),\n    (0xFF1D, '3', u'='),\n    (0xFF1E, '3', u'>'),\n    (0xFF1F, '3', u'?'),\n    (0xFF20, '3', u'@'),\n    (0xFF21, 'M', u'a'),\n    (0xFF22, 'M', u'b'),\n    (0xFF23, 'M', u'c'),\n    (0xFF24, 'M', u'd'),\n    (0xFF25, 'M', u'e'),\n    (0xFF26, 'M', u'f'),\n    (0xFF27, 'M', u'g'),\n    (0xFF28, 'M', u'h'),\n    (0xFF29, 'M', u'i'),\n    (0xFF2A, 'M', u'j'),\n    (0xFF2B, 'M', u'k'),\n    (0xFF2C, 'M', u'l'),\n    (0xFF2D, 'M', u'm'),\n    (0xFF2E, 'M', u'n'),\n    (0xFF2F, 'M', u'o'),\n    (0xFF30, 'M', u'p'),\n    (0xFF31, 'M', u'q'),\n    (0xFF32, 'M', u'r'),\n    (0xFF33, 'M', u's'),\n    (0xFF34, 'M', u't'),\n    (0xFF35, 'M', u'u'),\n    (0xFF36, 'M', u'v'),\n    (0xFF37, 'M', u'w'),\n    (0xFF38, 'M', u'x'),\n    (0xFF39, 'M', u'y'),\n    (0xFF3A, 'M', u'z'),\n    (0xFF3B, '3', u'['),\n    (0xFF3C, '3', u'\\\\'),\n    (0xFF3D, '3', u']'),\n    (0xFF3E, '3', u'^'),\n    (0xFF3F, '3', u'_'),\n    (0xFF40, '3', u'`'),\n    (0xFF41, 'M', u'a'),\n    (0xFF42, 'M', u'b'),\n    (0xFF43, 'M', u'c'),\n    (0xFF44, 'M', u'd'),\n    (0xFF45, 'M', u'e'),\n    (0xFF46, 'M', u'f'),\n    (0xFF47, 'M', u'g'),\n    (0xFF48, 'M', u'h'),\n    (0xFF49, 'M', u'i'),\n    (0xFF4A, 'M', u'j'),\n    (0xFF4B, 'M', u'k'),\n    (0xFF4C, 'M', u'l'),\n    (0xFF4D, 'M', u'm'),\n    (0xFF4E, 'M', u'n'),\n    ]\n\ndef _seg_51():\n    return [\n    (0xFF4F, 'M', u'o'),\n    (0xFF50, 'M', u'p'),\n    (0xFF51, 'M', u'q'),\n    (0xFF52, 'M', u'r'),\n    (0xFF53, 'M', u's'),\n    (0xFF54, 'M', u't'),\n    (0xFF55, 'M', u'u'),\n    (0xFF56, 'M', u'v'),\n    (0xFF57, 'M', u'w'),\n    (0xFF58, 'M', u'x'),\n    (0xFF59, 'M', u'y'),\n    (0xFF5A, 'M', u'z'),\n    (0xFF5B, '3', u'{'),\n    (0xFF5C, '3', u'|'),\n    (0xFF5D, '3', u'}'),\n    (0xFF5E, '3', u'~'),\n    (0xFF5F, 'M', u'⦅'),\n    (0xFF60, 'M', u'⦆'),\n    (0xFF61, 'M', u'.'),\n    (0xFF62, 'M', u'「'),\n    (0xFF63, 'M', u'」'),\n    (0xFF64, 'M', u'、'),\n    (0xFF65, 'M', u'・'),\n    (0xFF66, 'M', u'ヲ'),\n    (0xFF67, 'M', u'ァ'),\n    (0xFF68, 'M', u'ィ'),\n    (0xFF69, 'M', u'ゥ'),\n    (0xFF6A, 'M', u'ェ'),\n    (0xFF6B, 'M', u'ォ'),\n    (0xFF6C, 'M', u'ャ'),\n    (0xFF6D, 'M', u'ュ'),\n    (0xFF6E, 'M', u'ョ'),\n    (0xFF6F, 'M', u'ッ'),\n    (0xFF70, 'M', u'ー'),\n    (0xFF71, 'M', u'ア'),\n    (0xFF72, 'M', u'イ'),\n    (0xFF73, 'M', u'ウ'),\n    (0xFF74, 'M', u'エ'),\n    (0xFF75, 'M', u'オ'),\n    (0xFF76, 'M', u'カ'),\n    (0xFF77, 'M', u'キ'),\n    (0xFF78, 'M', u'ク'),\n    (0xFF79, 'M', u'ケ'),\n    (0xFF7A, 'M', u'コ'),\n    (0xFF7B, 'M', u'サ'),\n    (0xFF7C, 'M', u'シ'),\n    (0xFF7D, 'M', u'ス'),\n    (0xFF7E, 'M', u'セ'),\n    (0xFF7F, 'M', u'ソ'),\n    (0xFF80, 'M', u'タ'),\n    (0xFF81, 'M', u'チ'),\n    (0xFF82, 'M', u'ツ'),\n    (0xFF83, 'M', u'テ'),\n    (0xFF84, 'M', u'ト'),\n    (0xFF85, 'M', u'ナ'),\n    (0xFF86, 'M', u'ニ'),\n    (0xFF87, 'M', u'ヌ'),\n    (0xFF88, 'M', u'ネ'),\n    (0xFF89, 'M', u'ノ'),\n    (0xFF8A, 'M', u'ハ'),\n    (0xFF8B, 'M', u'ヒ'),\n    (0xFF8C, 'M', u'フ'),\n    (0xFF8D, 'M', u'ヘ'),\n    (0xFF8E, 'M', u'ホ'),\n    (0xFF8F, 'M', u'マ'),\n    (0xFF90, 'M', u'ミ'),\n    (0xFF91, 'M', u'ム'),\n    (0xFF92, 'M', u'メ'),\n    (0xFF93, 'M', u'モ'),\n    (0xFF94, 'M', u'ヤ'),\n    (0xFF95, 'M', u'ユ'),\n    (0xFF96, 'M', u'ヨ'),\n    (0xFF97, 'M', u'ラ'),\n    (0xFF98, 'M', u'リ'),\n    (0xFF99, 'M', u'ル'),\n    (0xFF9A, 'M', u'レ'),\n    (0xFF9B, 'M', u'ロ'),\n    (0xFF9C, 'M', u'ワ'),\n    (0xFF9D, 'M', u'ン'),\n    (0xFF9E, 'M', u'゙'),\n    (0xFF9F, 'M', u'゚'),\n    (0xFFA0, 'X'),\n    (0xFFA1, 'M', u'ᄀ'),\n    (0xFFA2, 'M', u'ᄁ'),\n    (0xFFA3, 'M', u'ᆪ'),\n    (0xFFA4, 'M', u'ᄂ'),\n    (0xFFA5, 'M', u'ᆬ'),\n    (0xFFA6, 'M', u'ᆭ'),\n    (0xFFA7, 'M', u'ᄃ'),\n    (0xFFA8, 'M', u'ᄄ'),\n    (0xFFA9, 'M', u'ᄅ'),\n    (0xFFAA, 'M', u'ᆰ'),\n    (0xFFAB, 'M', u'ᆱ'),\n    (0xFFAC, 'M', u'ᆲ'),\n    (0xFFAD, 'M', u'ᆳ'),\n    (0xFFAE, 'M', u'ᆴ'),\n    (0xFFAF, 'M', u'ᆵ'),\n    (0xFFB0, 'M', u'ᄚ'),\n    (0xFFB1, 'M', u'ᄆ'),\n    (0xFFB2, 'M', u'ᄇ'),\n    ]\n\ndef _seg_52():\n    return [\n    (0xFFB3, 'M', u'ᄈ'),\n    (0xFFB4, 'M', u'ᄡ'),\n    (0xFFB5, 'M', u'ᄉ'),\n    (0xFFB6, 'M', u'ᄊ'),\n    (0xFFB7, 'M', u'ᄋ'),\n    (0xFFB8, 'M', u'ᄌ'),\n    (0xFFB9, 'M', u'ᄍ'),\n    (0xFFBA, 'M', u'ᄎ'),\n    (0xFFBB, 'M', u'ᄏ'),\n    (0xFFBC, 'M', u'ᄐ'),\n    (0xFFBD, 'M', u'ᄑ'),\n    (0xFFBE, 'M', u'ᄒ'),\n    (0xFFBF, 'X'),\n    (0xFFC2, 'M', u'ᅡ'),\n    (0xFFC3, 'M', u'ᅢ'),\n    (0xFFC4, 'M', u'ᅣ'),\n    (0xFFC5, 'M', u'ᅤ'),\n    (0xFFC6, 'M', u'ᅥ'),\n    (0xFFC7, 'M', u'ᅦ'),\n    (0xFFC8, 'X'),\n    (0xFFCA, 'M', u'ᅧ'),\n    (0xFFCB, 'M', u'ᅨ'),\n    (0xFFCC, 'M', u'ᅩ'),\n    (0xFFCD, 'M', u'ᅪ'),\n    (0xFFCE, 'M', u'ᅫ'),\n    (0xFFCF, 'M', u'ᅬ'),\n    (0xFFD0, 'X'),\n    (0xFFD2, 'M', u'ᅭ'),\n    (0xFFD3, 'M', u'ᅮ'),\n    (0xFFD4, 'M', u'ᅯ'),\n    (0xFFD5, 'M', u'ᅰ'),\n    (0xFFD6, 'M', u'ᅱ'),\n    (0xFFD7, 'M', u'ᅲ'),\n    (0xFFD8, 'X'),\n    (0xFFDA, 'M', u'ᅳ'),\n    (0xFFDB, 'M', u'ᅴ'),\n    (0xFFDC, 'M', u'ᅵ'),\n    (0xFFDD, 'X'),\n    (0xFFE0, 'M', u'¢'),\n    (0xFFE1, 'M', u'£'),\n    (0xFFE2, 'M', u'¬'),\n    (0xFFE3, '3', u' ̄'),\n    (0xFFE4, 'M', u'¦'),\n    (0xFFE5, 'M', u'¥'),\n    (0xFFE6, 'M', u'₩'),\n    (0xFFE7, 'X'),\n    (0xFFE8, 'M', u'│'),\n    (0xFFE9, 'M', u'←'),\n    (0xFFEA, 'M', u'↑'),\n    (0xFFEB, 'M', u'→'),\n    (0xFFEC, 'M', u'↓'),\n    (0xFFED, 'M', u'■'),\n    (0xFFEE, 'M', u'○'),\n    (0xFFEF, 'X'),\n    (0x10000, 'V'),\n    (0x1000C, 'X'),\n    (0x1000D, 'V'),\n    (0x10027, 'X'),\n    (0x10028, 'V'),\n    (0x1003B, 'X'),\n    (0x1003C, 'V'),\n    (0x1003E, 'X'),\n    (0x1003F, 'V'),\n    (0x1004E, 'X'),\n    (0x10050, 'V'),\n    (0x1005E, 'X'),\n    (0x10080, 'V'),\n    (0x100FB, 'X'),\n    (0x10100, 'V'),\n    (0x10103, 'X'),\n    (0x10107, 'V'),\n    (0x10134, 'X'),\n    (0x10137, 'V'),\n    (0x1018F, 'X'),\n    (0x10190, 'V'),\n    (0x1019C, 'X'),\n    (0x101A0, 'V'),\n    (0x101A1, 'X'),\n    (0x101D0, 'V'),\n    (0x101FE, 'X'),\n    (0x10280, 'V'),\n    (0x1029D, 'X'),\n    (0x102A0, 'V'),\n    (0x102D1, 'X'),\n    (0x102E0, 'V'),\n    (0x102FC, 'X'),\n    (0x10300, 'V'),\n    (0x10324, 'X'),\n    (0x1032D, 'V'),\n    (0x1034B, 'X'),\n    (0x10350, 'V'),\n    (0x1037B, 'X'),\n    (0x10380, 'V'),\n    (0x1039E, 'X'),\n    (0x1039F, 'V'),\n    (0x103C4, 'X'),\n    (0x103C8, 'V'),\n    (0x103D6, 'X'),\n    (0x10400, 'M', u'𐐨'),\n    (0x10401, 'M', u'𐐩'),\n    ]\n\ndef _seg_53():\n    return [\n    (0x10402, 'M', u'𐐪'),\n    (0x10403, 'M', u'𐐫'),\n    (0x10404, 'M', u'𐐬'),\n    (0x10405, 'M', u'𐐭'),\n    (0x10406, 'M', u'𐐮'),\n    (0x10407, 'M', u'𐐯'),\n    (0x10408, 'M', u'𐐰'),\n    (0x10409, 'M', u'𐐱'),\n    (0x1040A, 'M', u'𐐲'),\n    (0x1040B, 'M', u'𐐳'),\n    (0x1040C, 'M', u'𐐴'),\n    (0x1040D, 'M', u'𐐵'),\n    (0x1040E, 'M', u'𐐶'),\n    (0x1040F, 'M', u'𐐷'),\n    (0x10410, 'M', u'𐐸'),\n    (0x10411, 'M', u'𐐹'),\n    (0x10412, 'M', u'𐐺'),\n    (0x10413, 'M', u'𐐻'),\n    (0x10414, 'M', u'𐐼'),\n    (0x10415, 'M', u'𐐽'),\n    (0x10416, 'M', u'𐐾'),\n    (0x10417, 'M', u'𐐿'),\n    (0x10418, 'M', u'𐑀'),\n    (0x10419, 'M', u'𐑁'),\n    (0x1041A, 'M', u'𐑂'),\n    (0x1041B, 'M', u'𐑃'),\n    (0x1041C, 'M', u'𐑄'),\n    (0x1041D, 'M', u'𐑅'),\n    (0x1041E, 'M', u'𐑆'),\n    (0x1041F, 'M', u'𐑇'),\n    (0x10420, 'M', u'𐑈'),\n    (0x10421, 'M', u'𐑉'),\n    (0x10422, 'M', u'𐑊'),\n    (0x10423, 'M', u'𐑋'),\n    (0x10424, 'M', u'𐑌'),\n    (0x10425, 'M', u'𐑍'),\n    (0x10426, 'M', u'𐑎'),\n    (0x10427, 'M', u'𐑏'),\n    (0x10428, 'V'),\n    (0x1049E, 'X'),\n    (0x104A0, 'V'),\n    (0x104AA, 'X'),\n    (0x104B0, 'M', u'𐓘'),\n    (0x104B1, 'M', u'𐓙'),\n    (0x104B2, 'M', u'𐓚'),\n    (0x104B3, 'M', u'𐓛'),\n    (0x104B4, 'M', u'𐓜'),\n    (0x104B5, 'M', u'𐓝'),\n    (0x104B6, 'M', u'𐓞'),\n    (0x104B7, 'M', u'𐓟'),\n    (0x104B8, 'M', u'𐓠'),\n    (0x104B9, 'M', u'𐓡'),\n    (0x104BA, 'M', u'𐓢'),\n    (0x104BB, 'M', u'𐓣'),\n    (0x104BC, 'M', u'𐓤'),\n    (0x104BD, 'M', u'𐓥'),\n    (0x104BE, 'M', u'𐓦'),\n    (0x104BF, 'M', u'𐓧'),\n    (0x104C0, 'M', u'𐓨'),\n    (0x104C1, 'M', u'𐓩'),\n    (0x104C2, 'M', u'𐓪'),\n    (0x104C3, 'M', u'𐓫'),\n    (0x104C4, 'M', u'𐓬'),\n    (0x104C5, 'M', u'𐓭'),\n    (0x104C6, 'M', u'𐓮'),\n    (0x104C7, 'M', u'𐓯'),\n    (0x104C8, 'M', u'𐓰'),\n    (0x104C9, 'M', u'𐓱'),\n    (0x104CA, 'M', u'𐓲'),\n    (0x104CB, 'M', u'𐓳'),\n    (0x104CC, 'M', u'𐓴'),\n    (0x104CD, 'M', u'𐓵'),\n    (0x104CE, 'M', u'𐓶'),\n    (0x104CF, 'M', u'𐓷'),\n    (0x104D0, 'M', u'𐓸'),\n    (0x104D1, 'M', u'𐓹'),\n    (0x104D2, 'M', u'𐓺'),\n    (0x104D3, 'M', u'𐓻'),\n    (0x104D4, 'X'),\n    (0x104D8, 'V'),\n    (0x104FC, 'X'),\n    (0x10500, 'V'),\n    (0x10528, 'X'),\n    (0x10530, 'V'),\n    (0x10564, 'X'),\n    (0x1056F, 'V'),\n    (0x10570, 'X'),\n    (0x10600, 'V'),\n    (0x10737, 'X'),\n    (0x10740, 'V'),\n    (0x10756, 'X'),\n    (0x10760, 'V'),\n    (0x10768, 'X'),\n    (0x10800, 'V'),\n    (0x10806, 'X'),\n    (0x10808, 'V'),\n    (0x10809, 'X'),\n    (0x1080A, 'V'),\n    (0x10836, 'X'),\n    (0x10837, 'V'),\n    ]\n\ndef _seg_54():\n    return [\n    (0x10839, 'X'),\n    (0x1083C, 'V'),\n    (0x1083D, 'X'),\n    (0x1083F, 'V'),\n    (0x10856, 'X'),\n    (0x10857, 'V'),\n    (0x1089F, 'X'),\n    (0x108A7, 'V'),\n    (0x108B0, 'X'),\n    (0x108E0, 'V'),\n    (0x108F3, 'X'),\n    (0x108F4, 'V'),\n    (0x108F6, 'X'),\n    (0x108FB, 'V'),\n    (0x1091C, 'X'),\n    (0x1091F, 'V'),\n    (0x1093A, 'X'),\n    (0x1093F, 'V'),\n    (0x10940, 'X'),\n    (0x10980, 'V'),\n    (0x109B8, 'X'),\n    (0x109BC, 'V'),\n    (0x109D0, 'X'),\n    (0x109D2, 'V'),\n    (0x10A04, 'X'),\n    (0x10A05, 'V'),\n    (0x10A07, 'X'),\n    (0x10A0C, 'V'),\n    (0x10A14, 'X'),\n    (0x10A15, 'V'),\n    (0x10A18, 'X'),\n    (0x10A19, 'V'),\n    (0x10A36, 'X'),\n    (0x10A38, 'V'),\n    (0x10A3B, 'X'),\n    (0x10A3F, 'V'),\n    (0x10A49, 'X'),\n    (0x10A50, 'V'),\n    (0x10A59, 'X'),\n    (0x10A60, 'V'),\n    (0x10AA0, 'X'),\n    (0x10AC0, 'V'),\n    (0x10AE7, 'X'),\n    (0x10AEB, 'V'),\n    (0x10AF7, 'X'),\n    (0x10B00, 'V'),\n    (0x10B36, 'X'),\n    (0x10B39, 'V'),\n    (0x10B56, 'X'),\n    (0x10B58, 'V'),\n    (0x10B73, 'X'),\n    (0x10B78, 'V'),\n    (0x10B92, 'X'),\n    (0x10B99, 'V'),\n    (0x10B9D, 'X'),\n    (0x10BA9, 'V'),\n    (0x10BB0, 'X'),\n    (0x10C00, 'V'),\n    (0x10C49, 'X'),\n    (0x10C80, 'M', u'𐳀'),\n    (0x10C81, 'M', u'𐳁'),\n    (0x10C82, 'M', u'𐳂'),\n    (0x10C83, 'M', u'𐳃'),\n    (0x10C84, 'M', u'𐳄'),\n    (0x10C85, 'M', u'𐳅'),\n    (0x10C86, 'M', u'𐳆'),\n    (0x10C87, 'M', u'𐳇'),\n    (0x10C88, 'M', u'𐳈'),\n    (0x10C89, 'M', u'𐳉'),\n    (0x10C8A, 'M', u'𐳊'),\n    (0x10C8B, 'M', u'𐳋'),\n    (0x10C8C, 'M', u'𐳌'),\n    (0x10C8D, 'M', u'𐳍'),\n    (0x10C8E, 'M', u'𐳎'),\n    (0x10C8F, 'M', u'𐳏'),\n    (0x10C90, 'M', u'𐳐'),\n    (0x10C91, 'M', u'𐳑'),\n    (0x10C92, 'M', u'𐳒'),\n    (0x10C93, 'M', u'𐳓'),\n    (0x10C94, 'M', u'𐳔'),\n    (0x10C95, 'M', u'𐳕'),\n    (0x10C96, 'M', u'𐳖'),\n    (0x10C97, 'M', u'𐳗'),\n    (0x10C98, 'M', u'𐳘'),\n    (0x10C99, 'M', u'𐳙'),\n    (0x10C9A, 'M', u'𐳚'),\n    (0x10C9B, 'M', u'𐳛'),\n    (0x10C9C, 'M', u'𐳜'),\n    (0x10C9D, 'M', u'𐳝'),\n    (0x10C9E, 'M', u'𐳞'),\n    (0x10C9F, 'M', u'𐳟'),\n    (0x10CA0, 'M', u'𐳠'),\n    (0x10CA1, 'M', u'𐳡'),\n    (0x10CA2, 'M', u'𐳢'),\n    (0x10CA3, 'M', u'𐳣'),\n    (0x10CA4, 'M', u'𐳤'),\n    (0x10CA5, 'M', u'𐳥'),\n    (0x10CA6, 'M', u'𐳦'),\n    (0x10CA7, 'M', u'𐳧'),\n    (0x10CA8, 'M', u'𐳨'),\n    ]\n\ndef _seg_55():\n    return [\n    (0x10CA9, 'M', u'𐳩'),\n    (0x10CAA, 'M', u'𐳪'),\n    (0x10CAB, 'M', u'𐳫'),\n    (0x10CAC, 'M', u'𐳬'),\n    (0x10CAD, 'M', u'𐳭'),\n    (0x10CAE, 'M', u'𐳮'),\n    (0x10CAF, 'M', u'𐳯'),\n    (0x10CB0, 'M', u'𐳰'),\n    (0x10CB1, 'M', u'𐳱'),\n    (0x10CB2, 'M', u'𐳲'),\n    (0x10CB3, 'X'),\n    (0x10CC0, 'V'),\n    (0x10CF3, 'X'),\n    (0x10CFA, 'V'),\n    (0x10D28, 'X'),\n    (0x10D30, 'V'),\n    (0x10D3A, 'X'),\n    (0x10E60, 'V'),\n    (0x10E7F, 'X'),\n    (0x10F00, 'V'),\n    (0x10F28, 'X'),\n    (0x10F30, 'V'),\n    (0x10F5A, 'X'),\n    (0x11000, 'V'),\n    (0x1104E, 'X'),\n    (0x11052, 'V'),\n    (0x11070, 'X'),\n    (0x1107F, 'V'),\n    (0x110BD, 'X'),\n    (0x110BE, 'V'),\n    (0x110C2, 'X'),\n    (0x110D0, 'V'),\n    (0x110E9, 'X'),\n    (0x110F0, 'V'),\n    (0x110FA, 'X'),\n    (0x11100, 'V'),\n    (0x11135, 'X'),\n    (0x11136, 'V'),\n    (0x11147, 'X'),\n    (0x11150, 'V'),\n    (0x11177, 'X'),\n    (0x11180, 'V'),\n    (0x111CE, 'X'),\n    (0x111D0, 'V'),\n    (0x111E0, 'X'),\n    (0x111E1, 'V'),\n    (0x111F5, 'X'),\n    (0x11200, 'V'),\n    (0x11212, 'X'),\n    (0x11213, 'V'),\n    (0x1123F, 'X'),\n    (0x11280, 'V'),\n    (0x11287, 'X'),\n    (0x11288, 'V'),\n    (0x11289, 'X'),\n    (0x1128A, 'V'),\n    (0x1128E, 'X'),\n    (0x1128F, 'V'),\n    (0x1129E, 'X'),\n    (0x1129F, 'V'),\n    (0x112AA, 'X'),\n    (0x112B0, 'V'),\n    (0x112EB, 'X'),\n    (0x112F0, 'V'),\n    (0x112FA, 'X'),\n    (0x11300, 'V'),\n    (0x11304, 'X'),\n    (0x11305, 'V'),\n    (0x1130D, 'X'),\n    (0x1130F, 'V'),\n    (0x11311, 'X'),\n    (0x11313, 'V'),\n    (0x11329, 'X'),\n    (0x1132A, 'V'),\n    (0x11331, 'X'),\n    (0x11332, 'V'),\n    (0x11334, 'X'),\n    (0x11335, 'V'),\n    (0x1133A, 'X'),\n    (0x1133B, 'V'),\n    (0x11345, 'X'),\n    (0x11347, 'V'),\n    (0x11349, 'X'),\n    (0x1134B, 'V'),\n    (0x1134E, 'X'),\n    (0x11350, 'V'),\n    (0x11351, 'X'),\n    (0x11357, 'V'),\n    (0x11358, 'X'),\n    (0x1135D, 'V'),\n    (0x11364, 'X'),\n    (0x11366, 'V'),\n    (0x1136D, 'X'),\n    (0x11370, 'V'),\n    (0x11375, 'X'),\n    (0x11400, 'V'),\n    (0x1145A, 'X'),\n    (0x1145B, 'V'),\n    (0x1145C, 'X'),\n    (0x1145D, 'V'),\n    ]\n\ndef _seg_56():\n    return [\n    (0x1145F, 'X'),\n    (0x11480, 'V'),\n    (0x114C8, 'X'),\n    (0x114D0, 'V'),\n    (0x114DA, 'X'),\n    (0x11580, 'V'),\n    (0x115B6, 'X'),\n    (0x115B8, 'V'),\n    (0x115DE, 'X'),\n    (0x11600, 'V'),\n    (0x11645, 'X'),\n    (0x11650, 'V'),\n    (0x1165A, 'X'),\n    (0x11660, 'V'),\n    (0x1166D, 'X'),\n    (0x11680, 'V'),\n    (0x116B8, 'X'),\n    (0x116C0, 'V'),\n    (0x116CA, 'X'),\n    (0x11700, 'V'),\n    (0x1171B, 'X'),\n    (0x1171D, 'V'),\n    (0x1172C, 'X'),\n    (0x11730, 'V'),\n    (0x11740, 'X'),\n    (0x11800, 'V'),\n    (0x1183C, 'X'),\n    (0x118A0, 'M', u'𑣀'),\n    (0x118A1, 'M', u'𑣁'),\n    (0x118A2, 'M', u'𑣂'),\n    (0x118A3, 'M', u'𑣃'),\n    (0x118A4, 'M', u'𑣄'),\n    (0x118A5, 'M', u'𑣅'),\n    (0x118A6, 'M', u'𑣆'),\n    (0x118A7, 'M', u'𑣇'),\n    (0x118A8, 'M', u'𑣈'),\n    (0x118A9, 'M', u'𑣉'),\n    (0x118AA, 'M', u'𑣊'),\n    (0x118AB, 'M', u'𑣋'),\n    (0x118AC, 'M', u'𑣌'),\n    (0x118AD, 'M', u'𑣍'),\n    (0x118AE, 'M', u'𑣎'),\n    (0x118AF, 'M', u'𑣏'),\n    (0x118B0, 'M', u'𑣐'),\n    (0x118B1, 'M', u'𑣑'),\n    (0x118B2, 'M', u'𑣒'),\n    (0x118B3, 'M', u'𑣓'),\n    (0x118B4, 'M', u'𑣔'),\n    (0x118B5, 'M', u'𑣕'),\n    (0x118B6, 'M', u'𑣖'),\n    (0x118B7, 'M', u'𑣗'),\n    (0x118B8, 'M', u'𑣘'),\n    (0x118B9, 'M', u'𑣙'),\n    (0x118BA, 'M', u'𑣚'),\n    (0x118BB, 'M', u'𑣛'),\n    (0x118BC, 'M', u'𑣜'),\n    (0x118BD, 'M', u'𑣝'),\n    (0x118BE, 'M', u'𑣞'),\n    (0x118BF, 'M', u'𑣟'),\n    (0x118C0, 'V'),\n    (0x118F3, 'X'),\n    (0x118FF, 'V'),\n    (0x11900, 'X'),\n    (0x11A00, 'V'),\n    (0x11A48, 'X'),\n    (0x11A50, 'V'),\n    (0x11A84, 'X'),\n    (0x11A86, 'V'),\n    (0x11AA3, 'X'),\n    (0x11AC0, 'V'),\n    (0x11AF9, 'X'),\n    (0x11C00, 'V'),\n    (0x11C09, 'X'),\n    (0x11C0A, 'V'),\n    (0x11C37, 'X'),\n    (0x11C38, 'V'),\n    (0x11C46, 'X'),\n    (0x11C50, 'V'),\n    (0x11C6D, 'X'),\n    (0x11C70, 'V'),\n    (0x11C90, 'X'),\n    (0x11C92, 'V'),\n    (0x11CA8, 'X'),\n    (0x11CA9, 'V'),\n    (0x11CB7, 'X'),\n    (0x11D00, 'V'),\n    (0x11D07, 'X'),\n    (0x11D08, 'V'),\n    (0x11D0A, 'X'),\n    (0x11D0B, 'V'),\n    (0x11D37, 'X'),\n    (0x11D3A, 'V'),\n    (0x11D3B, 'X'),\n    (0x11D3C, 'V'),\n    (0x11D3E, 'X'),\n    (0x11D3F, 'V'),\n    (0x11D48, 'X'),\n    (0x11D50, 'V'),\n    (0x11D5A, 'X'),\n    (0x11D60, 'V'),\n    ]\n\ndef _seg_57():\n    return [\n    (0x11D66, 'X'),\n    (0x11D67, 'V'),\n    (0x11D69, 'X'),\n    (0x11D6A, 'V'),\n    (0x11D8F, 'X'),\n    (0x11D90, 'V'),\n    (0x11D92, 'X'),\n    (0x11D93, 'V'),\n    (0x11D99, 'X'),\n    (0x11DA0, 'V'),\n    (0x11DAA, 'X'),\n    (0x11EE0, 'V'),\n    (0x11EF9, 'X'),\n    (0x12000, 'V'),\n    (0x1239A, 'X'),\n    (0x12400, 'V'),\n    (0x1246F, 'X'),\n    (0x12470, 'V'),\n    (0x12475, 'X'),\n    (0x12480, 'V'),\n    (0x12544, 'X'),\n    (0x13000, 'V'),\n    (0x1342F, 'X'),\n    (0x14400, 'V'),\n    (0x14647, 'X'),\n    (0x16800, 'V'),\n    (0x16A39, 'X'),\n    (0x16A40, 'V'),\n    (0x16A5F, 'X'),\n    (0x16A60, 'V'),\n    (0x16A6A, 'X'),\n    (0x16A6E, 'V'),\n    (0x16A70, 'X'),\n    (0x16AD0, 'V'),\n    (0x16AEE, 'X'),\n    (0x16AF0, 'V'),\n    (0x16AF6, 'X'),\n    (0x16B00, 'V'),\n    (0x16B46, 'X'),\n    (0x16B50, 'V'),\n    (0x16B5A, 'X'),\n    (0x16B5B, 'V'),\n    (0x16B62, 'X'),\n    (0x16B63, 'V'),\n    (0x16B78, 'X'),\n    (0x16B7D, 'V'),\n    (0x16B90, 'X'),\n    (0x16E60, 'V'),\n    (0x16E9B, 'X'),\n    (0x16F00, 'V'),\n    (0x16F45, 'X'),\n    (0x16F50, 'V'),\n    (0x16F7F, 'X'),\n    (0x16F8F, 'V'),\n    (0x16FA0, 'X'),\n    (0x16FE0, 'V'),\n    (0x16FE2, 'X'),\n    (0x17000, 'V'),\n    (0x187F2, 'X'),\n    (0x18800, 'V'),\n    (0x18AF3, 'X'),\n    (0x1B000, 'V'),\n    (0x1B11F, 'X'),\n    (0x1B170, 'V'),\n    (0x1B2FC, 'X'),\n    (0x1BC00, 'V'),\n    (0x1BC6B, 'X'),\n    (0x1BC70, 'V'),\n    (0x1BC7D, 'X'),\n    (0x1BC80, 'V'),\n    (0x1BC89, 'X'),\n    (0x1BC90, 'V'),\n    (0x1BC9A, 'X'),\n    (0x1BC9C, 'V'),\n    (0x1BCA0, 'I'),\n    (0x1BCA4, 'X'),\n    (0x1D000, 'V'),\n    (0x1D0F6, 'X'),\n    (0x1D100, 'V'),\n    (0x1D127, 'X'),\n    (0x1D129, 'V'),\n    (0x1D15E, 'M', u'𝅗𝅥'),\n    (0x1D15F, 'M', u'𝅘𝅥'),\n    (0x1D160, 'M', u'𝅘𝅥𝅮'),\n    (0x1D161, 'M', u'𝅘𝅥𝅯'),\n    (0x1D162, 'M', u'𝅘𝅥𝅰'),\n    (0x1D163, 'M', u'𝅘𝅥𝅱'),\n    (0x1D164, 'M', u'𝅘𝅥𝅲'),\n    (0x1D165, 'V'),\n    (0x1D173, 'X'),\n    (0x1D17B, 'V'),\n    (0x1D1BB, 'M', u'𝆹𝅥'),\n    (0x1D1BC, 'M', u'𝆺𝅥'),\n    (0x1D1BD, 'M', u'𝆹𝅥𝅮'),\n    (0x1D1BE, 'M', u'𝆺𝅥𝅮'),\n    (0x1D1BF, 'M', u'𝆹𝅥𝅯'),\n    (0x1D1C0, 'M', u'𝆺𝅥𝅯'),\n    (0x1D1C1, 'V'),\n    (0x1D1E9, 'X'),\n    (0x1D200, 'V'),\n    ]\n\ndef _seg_58():\n    return [\n    (0x1D246, 'X'),\n    (0x1D2E0, 'V'),\n    (0x1D2F4, 'X'),\n    (0x1D300, 'V'),\n    (0x1D357, 'X'),\n    (0x1D360, 'V'),\n    (0x1D379, 'X'),\n    (0x1D400, 'M', u'a'),\n    (0x1D401, 'M', u'b'),\n    (0x1D402, 'M', u'c'),\n    (0x1D403, 'M', u'd'),\n    (0x1D404, 'M', u'e'),\n    (0x1D405, 'M', u'f'),\n    (0x1D406, 'M', u'g'),\n    (0x1D407, 'M', u'h'),\n    (0x1D408, 'M', u'i'),\n    (0x1D409, 'M', u'j'),\n    (0x1D40A, 'M', u'k'),\n    (0x1D40B, 'M', u'l'),\n    (0x1D40C, 'M', u'm'),\n    (0x1D40D, 'M', u'n'),\n    (0x1D40E, 'M', u'o'),\n    (0x1D40F, 'M', u'p'),\n    (0x1D410, 'M', u'q'),\n    (0x1D411, 'M', u'r'),\n    (0x1D412, 'M', u's'),\n    (0x1D413, 'M', u't'),\n    (0x1D414, 'M', u'u'),\n    (0x1D415, 'M', u'v'),\n    (0x1D416, 'M', u'w'),\n    (0x1D417, 'M', u'x'),\n    (0x1D418, 'M', u'y'),\n    (0x1D419, 'M', u'z'),\n    (0x1D41A, 'M', u'a'),\n    (0x1D41B, 'M', u'b'),\n    (0x1D41C, 'M', u'c'),\n    (0x1D41D, 'M', u'd'),\n    (0x1D41E, 'M', u'e'),\n    (0x1D41F, 'M', u'f'),\n    (0x1D420, 'M', u'g'),\n    (0x1D421, 'M', u'h'),\n    (0x1D422, 'M', u'i'),\n    (0x1D423, 'M', u'j'),\n    (0x1D424, 'M', u'k'),\n    (0x1D425, 'M', u'l'),\n    (0x1D426, 'M', u'm'),\n    (0x1D427, 'M', u'n'),\n    (0x1D428, 'M', u'o'),\n    (0x1D429, 'M', u'p'),\n    (0x1D42A, 'M', u'q'),\n    (0x1D42B, 'M', u'r'),\n    (0x1D42C, 'M', u's'),\n    (0x1D42D, 'M', u't'),\n    (0x1D42E, 'M', u'u'),\n    (0x1D42F, 'M', u'v'),\n    (0x1D430, 'M', u'w'),\n    (0x1D431, 'M', u'x'),\n    (0x1D432, 'M', u'y'),\n    (0x1D433, 'M', u'z'),\n    (0x1D434, 'M', u'a'),\n    (0x1D435, 'M', u'b'),\n    (0x1D436, 'M', u'c'),\n    (0x1D437, 'M', u'd'),\n    (0x1D438, 'M', u'e'),\n    (0x1D439, 'M', u'f'),\n    (0x1D43A, 'M', u'g'),\n    (0x1D43B, 'M', u'h'),\n    (0x1D43C, 'M', u'i'),\n    (0x1D43D, 'M', u'j'),\n    (0x1D43E, 'M', u'k'),\n    (0x1D43F, 'M', u'l'),\n    (0x1D440, 'M', u'm'),\n    (0x1D441, 'M', u'n'),\n    (0x1D442, 'M', u'o'),\n    (0x1D443, 'M', u'p'),\n    (0x1D444, 'M', u'q'),\n    (0x1D445, 'M', u'r'),\n    (0x1D446, 'M', u's'),\n    (0x1D447, 'M', u't'),\n    (0x1D448, 'M', u'u'),\n    (0x1D449, 'M', u'v'),\n    (0x1D44A, 'M', u'w'),\n    (0x1D44B, 'M', u'x'),\n    (0x1D44C, 'M', u'y'),\n    (0x1D44D, 'M', u'z'),\n    (0x1D44E, 'M', u'a'),\n    (0x1D44F, 'M', u'b'),\n    (0x1D450, 'M', u'c'),\n    (0x1D451, 'M', u'd'),\n    (0x1D452, 'M', u'e'),\n    (0x1D453, 'M', u'f'),\n    (0x1D454, 'M', u'g'),\n    (0x1D455, 'X'),\n    (0x1D456, 'M', u'i'),\n    (0x1D457, 'M', u'j'),\n    (0x1D458, 'M', u'k'),\n    (0x1D459, 'M', u'l'),\n    (0x1D45A, 'M', u'm'),\n    (0x1D45B, 'M', u'n'),\n    (0x1D45C, 'M', u'o'),\n    ]\n\ndef _seg_59():\n    return [\n    (0x1D45D, 'M', u'p'),\n    (0x1D45E, 'M', u'q'),\n    (0x1D45F, 'M', u'r'),\n    (0x1D460, 'M', u's'),\n    (0x1D461, 'M', u't'),\n    (0x1D462, 'M', u'u'),\n    (0x1D463, 'M', u'v'),\n    (0x1D464, 'M', u'w'),\n    (0x1D465, 'M', u'x'),\n    (0x1D466, 'M', u'y'),\n    (0x1D467, 'M', u'z'),\n    (0x1D468, 'M', u'a'),\n    (0x1D469, 'M', u'b'),\n    (0x1D46A, 'M', u'c'),\n    (0x1D46B, 'M', u'd'),\n    (0x1D46C, 'M', u'e'),\n    (0x1D46D, 'M', u'f'),\n    (0x1D46E, 'M', u'g'),\n    (0x1D46F, 'M', u'h'),\n    (0x1D470, 'M', u'i'),\n    (0x1D471, 'M', u'j'),\n    (0x1D472, 'M', u'k'),\n    (0x1D473, 'M', u'l'),\n    (0x1D474, 'M', u'm'),\n    (0x1D475, 'M', u'n'),\n    (0x1D476, 'M', u'o'),\n    (0x1D477, 'M', u'p'),\n    (0x1D478, 'M', u'q'),\n    (0x1D479, 'M', u'r'),\n    (0x1D47A, 'M', u's'),\n    (0x1D47B, 'M', u't'),\n    (0x1D47C, 'M', u'u'),\n    (0x1D47D, 'M', u'v'),\n    (0x1D47E, 'M', u'w'),\n    (0x1D47F, 'M', u'x'),\n    (0x1D480, 'M', u'y'),\n    (0x1D481, 'M', u'z'),\n    (0x1D482, 'M', u'a'),\n    (0x1D483, 'M', u'b'),\n    (0x1D484, 'M', u'c'),\n    (0x1D485, 'M', u'd'),\n    (0x1D486, 'M', u'e'),\n    (0x1D487, 'M', u'f'),\n    (0x1D488, 'M', u'g'),\n    (0x1D489, 'M', u'h'),\n    (0x1D48A, 'M', u'i'),\n    (0x1D48B, 'M', u'j'),\n    (0x1D48C, 'M', u'k'),\n    (0x1D48D, 'M', u'l'),\n    (0x1D48E, 'M', u'm'),\n    (0x1D48F, 'M', u'n'),\n    (0x1D490, 'M', u'o'),\n    (0x1D491, 'M', u'p'),\n    (0x1D492, 'M', u'q'),\n    (0x1D493, 'M', u'r'),\n    (0x1D494, 'M', u's'),\n    (0x1D495, 'M', u't'),\n    (0x1D496, 'M', u'u'),\n    (0x1D497, 'M', u'v'),\n    (0x1D498, 'M', u'w'),\n    (0x1D499, 'M', u'x'),\n    (0x1D49A, 'M', u'y'),\n    (0x1D49B, 'M', u'z'),\n    (0x1D49C, 'M', u'a'),\n    (0x1D49D, 'X'),\n    (0x1D49E, 'M', u'c'),\n    (0x1D49F, 'M', u'd'),\n    (0x1D4A0, 'X'),\n    (0x1D4A2, 'M', u'g'),\n    (0x1D4A3, 'X'),\n    (0x1D4A5, 'M', u'j'),\n    (0x1D4A6, 'M', u'k'),\n    (0x1D4A7, 'X'),\n    (0x1D4A9, 'M', u'n'),\n    (0x1D4AA, 'M', u'o'),\n    (0x1D4AB, 'M', u'p'),\n    (0x1D4AC, 'M', u'q'),\n    (0x1D4AD, 'X'),\n    (0x1D4AE, 'M', u's'),\n    (0x1D4AF, 'M', u't'),\n    (0x1D4B0, 'M', u'u'),\n    (0x1D4B1, 'M', u'v'),\n    (0x1D4B2, 'M', u'w'),\n    (0x1D4B3, 'M', u'x'),\n    (0x1D4B4, 'M', u'y'),\n    (0x1D4B5, 'M', u'z'),\n    (0x1D4B6, 'M', u'a'),\n    (0x1D4B7, 'M', u'b'),\n    (0x1D4B8, 'M', u'c'),\n    (0x1D4B9, 'M', u'd'),\n    (0x1D4BA, 'X'),\n    (0x1D4BB, 'M', u'f'),\n    (0x1D4BC, 'X'),\n    (0x1D4BD, 'M', u'h'),\n    (0x1D4BE, 'M', u'i'),\n    (0x1D4BF, 'M', u'j'),\n    (0x1D4C0, 'M', u'k'),\n    (0x1D4C1, 'M', u'l'),\n    (0x1D4C2, 'M', u'm'),\n    (0x1D4C3, 'M', u'n'),\n    ]\n\ndef _seg_60():\n    return [\n    (0x1D4C4, 'X'),\n    (0x1D4C5, 'M', u'p'),\n    (0x1D4C6, 'M', u'q'),\n    (0x1D4C7, 'M', u'r'),\n    (0x1D4C8, 'M', u's'),\n    (0x1D4C9, 'M', u't'),\n    (0x1D4CA, 'M', u'u'),\n    (0x1D4CB, 'M', u'v'),\n    (0x1D4CC, 'M', u'w'),\n    (0x1D4CD, 'M', u'x'),\n    (0x1D4CE, 'M', u'y'),\n    (0x1D4CF, 'M', u'z'),\n    (0x1D4D0, 'M', u'a'),\n    (0x1D4D1, 'M', u'b'),\n    (0x1D4D2, 'M', u'c'),\n    (0x1D4D3, 'M', u'd'),\n    (0x1D4D4, 'M', u'e'),\n    (0x1D4D5, 'M', u'f'),\n    (0x1D4D6, 'M', u'g'),\n    (0x1D4D7, 'M', u'h'),\n    (0x1D4D8, 'M', u'i'),\n    (0x1D4D9, 'M', u'j'),\n    (0x1D4DA, 'M', u'k'),\n    (0x1D4DB, 'M', u'l'),\n    (0x1D4DC, 'M', u'm'),\n    (0x1D4DD, 'M', u'n'),\n    (0x1D4DE, 'M', u'o'),\n    (0x1D4DF, 'M', u'p'),\n    (0x1D4E0, 'M', u'q'),\n    (0x1D4E1, 'M', u'r'),\n    (0x1D4E2, 'M', u's'),\n    (0x1D4E3, 'M', u't'),\n    (0x1D4E4, 'M', u'u'),\n    (0x1D4E5, 'M', u'v'),\n    (0x1D4E6, 'M', u'w'),\n    (0x1D4E7, 'M', u'x'),\n    (0x1D4E8, 'M', u'y'),\n    (0x1D4E9, 'M', u'z'),\n    (0x1D4EA, 'M', u'a'),\n    (0x1D4EB, 'M', u'b'),\n    (0x1D4EC, 'M', u'c'),\n    (0x1D4ED, 'M', u'd'),\n    (0x1D4EE, 'M', u'e'),\n    (0x1D4EF, 'M', u'f'),\n    (0x1D4F0, 'M', u'g'),\n    (0x1D4F1, 'M', u'h'),\n    (0x1D4F2, 'M', u'i'),\n    (0x1D4F3, 'M', u'j'),\n    (0x1D4F4, 'M', u'k'),\n    (0x1D4F5, 'M', u'l'),\n    (0x1D4F6, 'M', u'm'),\n    (0x1D4F7, 'M', u'n'),\n    (0x1D4F8, 'M', u'o'),\n    (0x1D4F9, 'M', u'p'),\n    (0x1D4FA, 'M', u'q'),\n    (0x1D4FB, 'M', u'r'),\n    (0x1D4FC, 'M', u's'),\n    (0x1D4FD, 'M', u't'),\n    (0x1D4FE, 'M', u'u'),\n    (0x1D4FF, 'M', u'v'),\n    (0x1D500, 'M', u'w'),\n    (0x1D501, 'M', u'x'),\n    (0x1D502, 'M', u'y'),\n    (0x1D503, 'M', u'z'),\n    (0x1D504, 'M', u'a'),\n    (0x1D505, 'M', u'b'),\n    (0x1D506, 'X'),\n    (0x1D507, 'M', u'd'),\n    (0x1D508, 'M', u'e'),\n    (0x1D509, 'M', u'f'),\n    (0x1D50A, 'M', u'g'),\n    (0x1D50B, 'X'),\n    (0x1D50D, 'M', u'j'),\n    (0x1D50E, 'M', u'k'),\n    (0x1D50F, 'M', u'l'),\n    (0x1D510, 'M', u'm'),\n    (0x1D511, 'M', u'n'),\n    (0x1D512, 'M', u'o'),\n    (0x1D513, 'M', u'p'),\n    (0x1D514, 'M', u'q'),\n    (0x1D515, 'X'),\n    (0x1D516, 'M', u's'),\n    (0x1D517, 'M', u't'),\n    (0x1D518, 'M', u'u'),\n    (0x1D519, 'M', u'v'),\n    (0x1D51A, 'M', u'w'),\n    (0x1D51B, 'M', u'x'),\n    (0x1D51C, 'M', u'y'),\n    (0x1D51D, 'X'),\n    (0x1D51E, 'M', u'a'),\n    (0x1D51F, 'M', u'b'),\n    (0x1D520, 'M', u'c'),\n    (0x1D521, 'M', u'd'),\n    (0x1D522, 'M', u'e'),\n    (0x1D523, 'M', u'f'),\n    (0x1D524, 'M', u'g'),\n    (0x1D525, 'M', u'h'),\n    (0x1D526, 'M', u'i'),\n    (0x1D527, 'M', u'j'),\n    (0x1D528, 'M', u'k'),\n    ]\n\ndef _seg_61():\n    return [\n    (0x1D529, 'M', u'l'),\n    (0x1D52A, 'M', u'm'),\n    (0x1D52B, 'M', u'n'),\n    (0x1D52C, 'M', u'o'),\n    (0x1D52D, 'M', u'p'),\n    (0x1D52E, 'M', u'q'),\n    (0x1D52F, 'M', u'r'),\n    (0x1D530, 'M', u's'),\n    (0x1D531, 'M', u't'),\n    (0x1D532, 'M', u'u'),\n    (0x1D533, 'M', u'v'),\n    (0x1D534, 'M', u'w'),\n    (0x1D535, 'M', u'x'),\n    (0x1D536, 'M', u'y'),\n    (0x1D537, 'M', u'z'),\n    (0x1D538, 'M', u'a'),\n    (0x1D539, 'M', u'b'),\n    (0x1D53A, 'X'),\n    (0x1D53B, 'M', u'd'),\n    (0x1D53C, 'M', u'e'),\n    (0x1D53D, 'M', u'f'),\n    (0x1D53E, 'M', u'g'),\n    (0x1D53F, 'X'),\n    (0x1D540, 'M', u'i'),\n    (0x1D541, 'M', u'j'),\n    (0x1D542, 'M', u'k'),\n    (0x1D543, 'M', u'l'),\n    (0x1D544, 'M', u'm'),\n    (0x1D545, 'X'),\n    (0x1D546, 'M', u'o'),\n    (0x1D547, 'X'),\n    (0x1D54A, 'M', u's'),\n    (0x1D54B, 'M', u't'),\n    (0x1D54C, 'M', u'u'),\n    (0x1D54D, 'M', u'v'),\n    (0x1D54E, 'M', u'w'),\n    (0x1D54F, 'M', u'x'),\n    (0x1D550, 'M', u'y'),\n    (0x1D551, 'X'),\n    (0x1D552, 'M', u'a'),\n    (0x1D553, 'M', u'b'),\n    (0x1D554, 'M', u'c'),\n    (0x1D555, 'M', u'd'),\n    (0x1D556, 'M', u'e'),\n    (0x1D557, 'M', u'f'),\n    (0x1D558, 'M', u'g'),\n    (0x1D559, 'M', u'h'),\n    (0x1D55A, 'M', u'i'),\n    (0x1D55B, 'M', u'j'),\n    (0x1D55C, 'M', u'k'),\n    (0x1D55D, 'M', u'l'),\n    (0x1D55E, 'M', u'm'),\n    (0x1D55F, 'M', u'n'),\n    (0x1D560, 'M', u'o'),\n    (0x1D561, 'M', u'p'),\n    (0x1D562, 'M', u'q'),\n    (0x1D563, 'M', u'r'),\n    (0x1D564, 'M', u's'),\n    (0x1D565, 'M', u't'),\n    (0x1D566, 'M', u'u'),\n    (0x1D567, 'M', u'v'),\n    (0x1D568, 'M', u'w'),\n    (0x1D569, 'M', u'x'),\n    (0x1D56A, 'M', u'y'),\n    (0x1D56B, 'M', u'z'),\n    (0x1D56C, 'M', u'a'),\n    (0x1D56D, 'M', u'b'),\n    (0x1D56E, 'M', u'c'),\n    (0x1D56F, 'M', u'd'),\n    (0x1D570, 'M', u'e'),\n    (0x1D571, 'M', u'f'),\n    (0x1D572, 'M', u'g'),\n    (0x1D573, 'M', u'h'),\n    (0x1D574, 'M', u'i'),\n    (0x1D575, 'M', u'j'),\n    (0x1D576, 'M', u'k'),\n    (0x1D577, 'M', u'l'),\n    (0x1D578, 'M', u'm'),\n    (0x1D579, 'M', u'n'),\n    (0x1D57A, 'M', u'o'),\n    (0x1D57B, 'M', u'p'),\n    (0x1D57C, 'M', u'q'),\n    (0x1D57D, 'M', u'r'),\n    (0x1D57E, 'M', u's'),\n    (0x1D57F, 'M', u't'),\n    (0x1D580, 'M', u'u'),\n    (0x1D581, 'M', u'v'),\n    (0x1D582, 'M', u'w'),\n    (0x1D583, 'M', u'x'),\n    (0x1D584, 'M', u'y'),\n    (0x1D585, 'M', u'z'),\n    (0x1D586, 'M', u'a'),\n    (0x1D587, 'M', u'b'),\n    (0x1D588, 'M', u'c'),\n    (0x1D589, 'M', u'd'),\n    (0x1D58A, 'M', u'e'),\n    (0x1D58B, 'M', u'f'),\n    (0x1D58C, 'M', u'g'),\n    (0x1D58D, 'M', u'h'),\n    (0x1D58E, 'M', u'i'),\n    ]\n\ndef _seg_62():\n    return [\n    (0x1D58F, 'M', u'j'),\n    (0x1D590, 'M', u'k'),\n    (0x1D591, 'M', u'l'),\n    (0x1D592, 'M', u'm'),\n    (0x1D593, 'M', u'n'),\n    (0x1D594, 'M', u'o'),\n    (0x1D595, 'M', u'p'),\n    (0x1D596, 'M', u'q'),\n    (0x1D597, 'M', u'r'),\n    (0x1D598, 'M', u's'),\n    (0x1D599, 'M', u't'),\n    (0x1D59A, 'M', u'u'),\n    (0x1D59B, 'M', u'v'),\n    (0x1D59C, 'M', u'w'),\n    (0x1D59D, 'M', u'x'),\n    (0x1D59E, 'M', u'y'),\n    (0x1D59F, 'M', u'z'),\n    (0x1D5A0, 'M', u'a'),\n    (0x1D5A1, 'M', u'b'),\n    (0x1D5A2, 'M', u'c'),\n    (0x1D5A3, 'M', u'd'),\n    (0x1D5A4, 'M', u'e'),\n    (0x1D5A5, 'M', u'f'),\n    (0x1D5A6, 'M', u'g'),\n    (0x1D5A7, 'M', u'h'),\n    (0x1D5A8, 'M', u'i'),\n    (0x1D5A9, 'M', u'j'),\n    (0x1D5AA, 'M', u'k'),\n    (0x1D5AB, 'M', u'l'),\n    (0x1D5AC, 'M', u'm'),\n    (0x1D5AD, 'M', u'n'),\n    (0x1D5AE, 'M', u'o'),\n    (0x1D5AF, 'M', u'p'),\n    (0x1D5B0, 'M', u'q'),\n    (0x1D5B1, 'M', u'r'),\n    (0x1D5B2, 'M', u's'),\n    (0x1D5B3, 'M', u't'),\n    (0x1D5B4, 'M', u'u'),\n    (0x1D5B5, 'M', u'v'),\n    (0x1D5B6, 'M', u'w'),\n    (0x1D5B7, 'M', u'x'),\n    (0x1D5B8, 'M', u'y'),\n    (0x1D5B9, 'M', u'z'),\n    (0x1D5BA, 'M', u'a'),\n    (0x1D5BB, 'M', u'b'),\n    (0x1D5BC, 'M', u'c'),\n    (0x1D5BD, 'M', u'd'),\n    (0x1D5BE, 'M', u'e'),\n    (0x1D5BF, 'M', u'f'),\n    (0x1D5C0, 'M', u'g'),\n    (0x1D5C1, 'M', u'h'),\n    (0x1D5C2, 'M', u'i'),\n    (0x1D5C3, 'M', u'j'),\n    (0x1D5C4, 'M', u'k'),\n    (0x1D5C5, 'M', u'l'),\n    (0x1D5C6, 'M', u'm'),\n    (0x1D5C7, 'M', u'n'),\n    (0x1D5C8, 'M', u'o'),\n    (0x1D5C9, 'M', u'p'),\n    (0x1D5CA, 'M', u'q'),\n    (0x1D5CB, 'M', u'r'),\n    (0x1D5CC, 'M', u's'),\n    (0x1D5CD, 'M', u't'),\n    (0x1D5CE, 'M', u'u'),\n    (0x1D5CF, 'M', u'v'),\n    (0x1D5D0, 'M', u'w'),\n    (0x1D5D1, 'M', u'x'),\n    (0x1D5D2, 'M', u'y'),\n    (0x1D5D3, 'M', u'z'),\n    (0x1D5D4, 'M', u'a'),\n    (0x1D5D5, 'M', u'b'),\n    (0x1D5D6, 'M', u'c'),\n    (0x1D5D7, 'M', u'd'),\n    (0x1D5D8, 'M', u'e'),\n    (0x1D5D9, 'M', u'f'),\n    (0x1D5DA, 'M', u'g'),\n    (0x1D5DB, 'M', u'h'),\n    (0x1D5DC, 'M', u'i'),\n    (0x1D5DD, 'M', u'j'),\n    (0x1D5DE, 'M', u'k'),\n    (0x1D5DF, 'M', u'l'),\n    (0x1D5E0, 'M', u'm'),\n    (0x1D5E1, 'M', u'n'),\n    (0x1D5E2, 'M', u'o'),\n    (0x1D5E3, 'M', u'p'),\n    (0x1D5E4, 'M', u'q'),\n    (0x1D5E5, 'M', u'r'),\n    (0x1D5E6, 'M', u's'),\n    (0x1D5E7, 'M', u't'),\n    (0x1D5E8, 'M', u'u'),\n    (0x1D5E9, 'M', u'v'),\n    (0x1D5EA, 'M', u'w'),\n    (0x1D5EB, 'M', u'x'),\n    (0x1D5EC, 'M', u'y'),\n    (0x1D5ED, 'M', u'z'),\n    (0x1D5EE, 'M', u'a'),\n    (0x1D5EF, 'M', u'b'),\n    (0x1D5F0, 'M', u'c'),\n    (0x1D5F1, 'M', u'd'),\n    (0x1D5F2, 'M', u'e'),\n    ]\n\ndef _seg_63():\n    return [\n    (0x1D5F3, 'M', u'f'),\n    (0x1D5F4, 'M', u'g'),\n    (0x1D5F5, 'M', u'h'),\n    (0x1D5F6, 'M', u'i'),\n    (0x1D5F7, 'M', u'j'),\n    (0x1D5F8, 'M', u'k'),\n    (0x1D5F9, 'M', u'l'),\n    (0x1D5FA, 'M', u'm'),\n    (0x1D5FB, 'M', u'n'),\n    (0x1D5FC, 'M', u'o'),\n    (0x1D5FD, 'M', u'p'),\n    (0x1D5FE, 'M', u'q'),\n    (0x1D5FF, 'M', u'r'),\n    (0x1D600, 'M', u's'),\n    (0x1D601, 'M', u't'),\n    (0x1D602, 'M', u'u'),\n    (0x1D603, 'M', u'v'),\n    (0x1D604, 'M', u'w'),\n    (0x1D605, 'M', u'x'),\n    (0x1D606, 'M', u'y'),\n    (0x1D607, 'M', u'z'),\n    (0x1D608, 'M', u'a'),\n    (0x1D609, 'M', u'b'),\n    (0x1D60A, 'M', u'c'),\n    (0x1D60B, 'M', u'd'),\n    (0x1D60C, 'M', u'e'),\n    (0x1D60D, 'M', u'f'),\n    (0x1D60E, 'M', u'g'),\n    (0x1D60F, 'M', u'h'),\n    (0x1D610, 'M', u'i'),\n    (0x1D611, 'M', u'j'),\n    (0x1D612, 'M', u'k'),\n    (0x1D613, 'M', u'l'),\n    (0x1D614, 'M', u'm'),\n    (0x1D615, 'M', u'n'),\n    (0x1D616, 'M', u'o'),\n    (0x1D617, 'M', u'p'),\n    (0x1D618, 'M', u'q'),\n    (0x1D619, 'M', u'r'),\n    (0x1D61A, 'M', u's'),\n    (0x1D61B, 'M', u't'),\n    (0x1D61C, 'M', u'u'),\n    (0x1D61D, 'M', u'v'),\n    (0x1D61E, 'M', u'w'),\n    (0x1D61F, 'M', u'x'),\n    (0x1D620, 'M', u'y'),\n    (0x1D621, 'M', u'z'),\n    (0x1D622, 'M', u'a'),\n    (0x1D623, 'M', u'b'),\n    (0x1D624, 'M', u'c'),\n    (0x1D625, 'M', u'd'),\n    (0x1D626, 'M', u'e'),\n    (0x1D627, 'M', u'f'),\n    (0x1D628, 'M', u'g'),\n    (0x1D629, 'M', u'h'),\n    (0x1D62A, 'M', u'i'),\n    (0x1D62B, 'M', u'j'),\n    (0x1D62C, 'M', u'k'),\n    (0x1D62D, 'M', u'l'),\n    (0x1D62E, 'M', u'm'),\n    (0x1D62F, 'M', u'n'),\n    (0x1D630, 'M', u'o'),\n    (0x1D631, 'M', u'p'),\n    (0x1D632, 'M', u'q'),\n    (0x1D633, 'M', u'r'),\n    (0x1D634, 'M', u's'),\n    (0x1D635, 'M', u't'),\n    (0x1D636, 'M', u'u'),\n    (0x1D637, 'M', u'v'),\n    (0x1D638, 'M', u'w'),\n    (0x1D639, 'M', u'x'),\n    (0x1D63A, 'M', u'y'),\n    (0x1D63B, 'M', u'z'),\n    (0x1D63C, 'M', u'a'),\n    (0x1D63D, 'M', u'b'),\n    (0x1D63E, 'M', u'c'),\n    (0x1D63F, 'M', u'd'),\n    (0x1D640, 'M', u'e'),\n    (0x1D641, 'M', u'f'),\n    (0x1D642, 'M', u'g'),\n    (0x1D643, 'M', u'h'),\n    (0x1D644, 'M', u'i'),\n    (0x1D645, 'M', u'j'),\n    (0x1D646, 'M', u'k'),\n    (0x1D647, 'M', u'l'),\n    (0x1D648, 'M', u'm'),\n    (0x1D649, 'M', u'n'),\n    (0x1D64A, 'M', u'o'),\n    (0x1D64B, 'M', u'p'),\n    (0x1D64C, 'M', u'q'),\n    (0x1D64D, 'M', u'r'),\n    (0x1D64E, 'M', u's'),\n    (0x1D64F, 'M', u't'),\n    (0x1D650, 'M', u'u'),\n    (0x1D651, 'M', u'v'),\n    (0x1D652, 'M', u'w'),\n    (0x1D653, 'M', u'x'),\n    (0x1D654, 'M', u'y'),\n    (0x1D655, 'M', u'z'),\n    (0x1D656, 'M', u'a'),\n    ]\n\ndef _seg_64():\n    return [\n    (0x1D657, 'M', u'b'),\n    (0x1D658, 'M', u'c'),\n    (0x1D659, 'M', u'd'),\n    (0x1D65A, 'M', u'e'),\n    (0x1D65B, 'M', u'f'),\n    (0x1D65C, 'M', u'g'),\n    (0x1D65D, 'M', u'h'),\n    (0x1D65E, 'M', u'i'),\n    (0x1D65F, 'M', u'j'),\n    (0x1D660, 'M', u'k'),\n    (0x1D661, 'M', u'l'),\n    (0x1D662, 'M', u'm'),\n    (0x1D663, 'M', u'n'),\n    (0x1D664, 'M', u'o'),\n    (0x1D665, 'M', u'p'),\n    (0x1D666, 'M', u'q'),\n    (0x1D667, 'M', u'r'),\n    (0x1D668, 'M', u's'),\n    (0x1D669, 'M', u't'),\n    (0x1D66A, 'M', u'u'),\n    (0x1D66B, 'M', u'v'),\n    (0x1D66C, 'M', u'w'),\n    (0x1D66D, 'M', u'x'),\n    (0x1D66E, 'M', u'y'),\n    (0x1D66F, 'M', u'z'),\n    (0x1D670, 'M', u'a'),\n    (0x1D671, 'M', u'b'),\n    (0x1D672, 'M', u'c'),\n    (0x1D673, 'M', u'd'),\n    (0x1D674, 'M', u'e'),\n    (0x1D675, 'M', u'f'),\n    (0x1D676, 'M', u'g'),\n    (0x1D677, 'M', u'h'),\n    (0x1D678, 'M', u'i'),\n    (0x1D679, 'M', u'j'),\n    (0x1D67A, 'M', u'k'),\n    (0x1D67B, 'M', u'l'),\n    (0x1D67C, 'M', u'm'),\n    (0x1D67D, 'M', u'n'),\n    (0x1D67E, 'M', u'o'),\n    (0x1D67F, 'M', u'p'),\n    (0x1D680, 'M', u'q'),\n    (0x1D681, 'M', u'r'),\n    (0x1D682, 'M', u's'),\n    (0x1D683, 'M', u't'),\n    (0x1D684, 'M', u'u'),\n    (0x1D685, 'M', u'v'),\n    (0x1D686, 'M', u'w'),\n    (0x1D687, 'M', u'x'),\n    (0x1D688, 'M', u'y'),\n    (0x1D689, 'M', u'z'),\n    (0x1D68A, 'M', u'a'),\n    (0x1D68B, 'M', u'b'),\n    (0x1D68C, 'M', u'c'),\n    (0x1D68D, 'M', u'd'),\n    (0x1D68E, 'M', u'e'),\n    (0x1D68F, 'M', u'f'),\n    (0x1D690, 'M', u'g'),\n    (0x1D691, 'M', u'h'),\n    (0x1D692, 'M', u'i'),\n    (0x1D693, 'M', u'j'),\n    (0x1D694, 'M', u'k'),\n    (0x1D695, 'M', u'l'),\n    (0x1D696, 'M', u'm'),\n    (0x1D697, 'M', u'n'),\n    (0x1D698, 'M', u'o'),\n    (0x1D699, 'M', u'p'),\n    (0x1D69A, 'M', u'q'),\n    (0x1D69B, 'M', u'r'),\n    (0x1D69C, 'M', u's'),\n    (0x1D69D, 'M', u't'),\n    (0x1D69E, 'M', u'u'),\n    (0x1D69F, 'M', u'v'),\n    (0x1D6A0, 'M', u'w'),\n    (0x1D6A1, 'M', u'x'),\n    (0x1D6A2, 'M', u'y'),\n    (0x1D6A3, 'M', u'z'),\n    (0x1D6A4, 'M', u'ı'),\n    (0x1D6A5, 'M', u'ȷ'),\n    (0x1D6A6, 'X'),\n    (0x1D6A8, 'M', u'α'),\n    (0x1D6A9, 'M', u'β'),\n    (0x1D6AA, 'M', u'γ'),\n    (0x1D6AB, 'M', u'δ'),\n    (0x1D6AC, 'M', u'ε'),\n    (0x1D6AD, 'M', u'ζ'),\n    (0x1D6AE, 'M', u'η'),\n    (0x1D6AF, 'M', u'θ'),\n    (0x1D6B0, 'M', u'ι'),\n    (0x1D6B1, 'M', u'κ'),\n    (0x1D6B2, 'M', u'λ'),\n    (0x1D6B3, 'M', u'μ'),\n    (0x1D6B4, 'M', u'ν'),\n    (0x1D6B5, 'M', u'ξ'),\n    (0x1D6B6, 'M', u'ο'),\n    (0x1D6B7, 'M', u'π'),\n    (0x1D6B8, 'M', u'ρ'),\n    (0x1D6B9, 'M', u'θ'),\n    (0x1D6BA, 'M', u'σ'),\n    (0x1D6BB, 'M', u'τ'),\n    ]\n\ndef _seg_65():\n    return [\n    (0x1D6BC, 'M', u'υ'),\n    (0x1D6BD, 'M', u'φ'),\n    (0x1D6BE, 'M', u'χ'),\n    (0x1D6BF, 'M', u'ψ'),\n    (0x1D6C0, 'M', u'ω'),\n    (0x1D6C1, 'M', u'∇'),\n    (0x1D6C2, 'M', u'α'),\n    (0x1D6C3, 'M', u'β'),\n    (0x1D6C4, 'M', u'γ'),\n    (0x1D6C5, 'M', u'δ'),\n    (0x1D6C6, 'M', u'ε'),\n    (0x1D6C7, 'M', u'ζ'),\n    (0x1D6C8, 'M', u'η'),\n    (0x1D6C9, 'M', u'θ'),\n    (0x1D6CA, 'M', u'ι'),\n    (0x1D6CB, 'M', u'κ'),\n    (0x1D6CC, 'M', u'λ'),\n    (0x1D6CD, 'M', u'μ'),\n    (0x1D6CE, 'M', u'ν'),\n    (0x1D6CF, 'M', u'ξ'),\n    (0x1D6D0, 'M', u'ο'),\n    (0x1D6D1, 'M', u'π'),\n    (0x1D6D2, 'M', u'ρ'),\n    (0x1D6D3, 'M', u'σ'),\n    (0x1D6D5, 'M', u'τ'),\n    (0x1D6D6, 'M', u'υ'),\n    (0x1D6D7, 'M', u'φ'),\n    (0x1D6D8, 'M', u'χ'),\n    (0x1D6D9, 'M', u'ψ'),\n    (0x1D6DA, 'M', u'ω'),\n    (0x1D6DB, 'M', u'∂'),\n    (0x1D6DC, 'M', u'ε'),\n    (0x1D6DD, 'M', u'θ'),\n    (0x1D6DE, 'M', u'κ'),\n    (0x1D6DF, 'M', u'φ'),\n    (0x1D6E0, 'M', u'ρ'),\n    (0x1D6E1, 'M', u'π'),\n    (0x1D6E2, 'M', u'α'),\n    (0x1D6E3, 'M', u'β'),\n    (0x1D6E4, 'M', u'γ'),\n    (0x1D6E5, 'M', u'δ'),\n    (0x1D6E6, 'M', u'ε'),\n    (0x1D6E7, 'M', u'ζ'),\n    (0x1D6E8, 'M', u'η'),\n    (0x1D6E9, 'M', u'θ'),\n    (0x1D6EA, 'M', u'ι'),\n    (0x1D6EB, 'M', u'κ'),\n    (0x1D6EC, 'M', u'λ'),\n    (0x1D6ED, 'M', u'μ'),\n    (0x1D6EE, 'M', u'ν'),\n    (0x1D6EF, 'M', u'ξ'),\n    (0x1D6F0, 'M', u'ο'),\n    (0x1D6F1, 'M', u'π'),\n    (0x1D6F2, 'M', u'ρ'),\n    (0x1D6F3, 'M', u'θ'),\n    (0x1D6F4, 'M', u'σ'),\n    (0x1D6F5, 'M', u'τ'),\n    (0x1D6F6, 'M', u'υ'),\n    (0x1D6F7, 'M', u'φ'),\n    (0x1D6F8, 'M', u'χ'),\n    (0x1D6F9, 'M', u'ψ'),\n    (0x1D6FA, 'M', u'ω'),\n    (0x1D6FB, 'M', u'∇'),\n    (0x1D6FC, 'M', u'α'),\n    (0x1D6FD, 'M', u'β'),\n    (0x1D6FE, 'M', u'γ'),\n    (0x1D6FF, 'M', u'δ'),\n    (0x1D700, 'M', u'ε'),\n    (0x1D701, 'M', u'ζ'),\n    (0x1D702, 'M', u'η'),\n    (0x1D703, 'M', u'θ'),\n    (0x1D704, 'M', u'ι'),\n    (0x1D705, 'M', u'κ'),\n    (0x1D706, 'M', u'λ'),\n    (0x1D707, 'M', u'μ'),\n    (0x1D708, 'M', u'ν'),\n    (0x1D709, 'M', u'ξ'),\n    (0x1D70A, 'M', u'ο'),\n    (0x1D70B, 'M', u'π'),\n    (0x1D70C, 'M', u'ρ'),\n    (0x1D70D, 'M', u'σ'),\n    (0x1D70F, 'M', u'τ'),\n    (0x1D710, 'M', u'υ'),\n    (0x1D711, 'M', u'φ'),\n    (0x1D712, 'M', u'χ'),\n    (0x1D713, 'M', u'ψ'),\n    (0x1D714, 'M', u'ω'),\n    (0x1D715, 'M', u'∂'),\n    (0x1D716, 'M', u'ε'),\n    (0x1D717, 'M', u'θ'),\n    (0x1D718, 'M', u'κ'),\n    (0x1D719, 'M', u'φ'),\n    (0x1D71A, 'M', u'ρ'),\n    (0x1D71B, 'M', u'π'),\n    (0x1D71C, 'M', u'α'),\n    (0x1D71D, 'M', u'β'),\n    (0x1D71E, 'M', u'γ'),\n    (0x1D71F, 'M', u'δ'),\n    (0x1D720, 'M', u'ε'),\n    (0x1D721, 'M', u'ζ'),\n    ]\n\ndef _seg_66():\n    return [\n    (0x1D722, 'M', u'η'),\n    (0x1D723, 'M', u'θ'),\n    (0x1D724, 'M', u'ι'),\n    (0x1D725, 'M', u'κ'),\n    (0x1D726, 'M', u'λ'),\n    (0x1D727, 'M', u'μ'),\n    (0x1D728, 'M', u'ν'),\n    (0x1D729, 'M', u'ξ'),\n    (0x1D72A, 'M', u'ο'),\n    (0x1D72B, 'M', u'π'),\n    (0x1D72C, 'M', u'ρ'),\n    (0x1D72D, 'M', u'θ'),\n    (0x1D72E, 'M', u'σ'),\n    (0x1D72F, 'M', u'τ'),\n    (0x1D730, 'M', u'υ'),\n    (0x1D731, 'M', u'φ'),\n    (0x1D732, 'M', u'χ'),\n    (0x1D733, 'M', u'ψ'),\n    (0x1D734, 'M', u'ω'),\n    (0x1D735, 'M', u'∇'),\n    (0x1D736, 'M', u'α'),\n    (0x1D737, 'M', u'β'),\n    (0x1D738, 'M', u'γ'),\n    (0x1D739, 'M', u'δ'),\n    (0x1D73A, 'M', u'ε'),\n    (0x1D73B, 'M', u'ζ'),\n    (0x1D73C, 'M', u'η'),\n    (0x1D73D, 'M', u'θ'),\n    (0x1D73E, 'M', u'ι'),\n    (0x1D73F, 'M', u'κ'),\n    (0x1D740, 'M', u'λ'),\n    (0x1D741, 'M', u'μ'),\n    (0x1D742, 'M', u'ν'),\n    (0x1D743, 'M', u'ξ'),\n    (0x1D744, 'M', u'ο'),\n    (0x1D745, 'M', u'π'),\n    (0x1D746, 'M', u'ρ'),\n    (0x1D747, 'M', u'σ'),\n    (0x1D749, 'M', u'τ'),\n    (0x1D74A, 'M', u'υ'),\n    (0x1D74B, 'M', u'φ'),\n    (0x1D74C, 'M', u'χ'),\n    (0x1D74D, 'M', u'ψ'),\n    (0x1D74E, 'M', u'ω'),\n    (0x1D74F, 'M', u'∂'),\n    (0x1D750, 'M', u'ε'),\n    (0x1D751, 'M', u'θ'),\n    (0x1D752, 'M', u'κ'),\n    (0x1D753, 'M', u'φ'),\n    (0x1D754, 'M', u'ρ'),\n    (0x1D755, 'M', u'π'),\n    (0x1D756, 'M', u'α'),\n    (0x1D757, 'M', u'β'),\n    (0x1D758, 'M', u'γ'),\n    (0x1D759, 'M', u'δ'),\n    (0x1D75A, 'M', u'ε'),\n    (0x1D75B, 'M', u'ζ'),\n    (0x1D75C, 'M', u'η'),\n    (0x1D75D, 'M', u'θ'),\n    (0x1D75E, 'M', u'ι'),\n    (0x1D75F, 'M', u'κ'),\n    (0x1D760, 'M', u'λ'),\n    (0x1D761, 'M', u'μ'),\n    (0x1D762, 'M', u'ν'),\n    (0x1D763, 'M', u'ξ'),\n    (0x1D764, 'M', u'ο'),\n    (0x1D765, 'M', u'π'),\n    (0x1D766, 'M', u'ρ'),\n    (0x1D767, 'M', u'θ'),\n    (0x1D768, 'M', u'σ'),\n    (0x1D769, 'M', u'τ'),\n    (0x1D76A, 'M', u'υ'),\n    (0x1D76B, 'M', u'φ'),\n    (0x1D76C, 'M', u'χ'),\n    (0x1D76D, 'M', u'ψ'),\n    (0x1D76E, 'M', u'ω'),\n    (0x1D76F, 'M', u'∇'),\n    (0x1D770, 'M', u'α'),\n    (0x1D771, 'M', u'β'),\n    (0x1D772, 'M', u'γ'),\n    (0x1D773, 'M', u'δ'),\n    (0x1D774, 'M', u'ε'),\n    (0x1D775, 'M', u'ζ'),\n    (0x1D776, 'M', u'η'),\n    (0x1D777, 'M', u'θ'),\n    (0x1D778, 'M', u'ι'),\n    (0x1D779, 'M', u'κ'),\n    (0x1D77A, 'M', u'λ'),\n    (0x1D77B, 'M', u'μ'),\n    (0x1D77C, 'M', u'ν'),\n    (0x1D77D, 'M', u'ξ'),\n    (0x1D77E, 'M', u'ο'),\n    (0x1D77F, 'M', u'π'),\n    (0x1D780, 'M', u'ρ'),\n    (0x1D781, 'M', u'σ'),\n    (0x1D783, 'M', u'τ'),\n    (0x1D784, 'M', u'υ'),\n    (0x1D785, 'M', u'φ'),\n    (0x1D786, 'M', u'χ'),\n    (0x1D787, 'M', u'ψ'),\n    ]\n\ndef _seg_67():\n    return [\n    (0x1D788, 'M', u'ω'),\n    (0x1D789, 'M', u'∂'),\n    (0x1D78A, 'M', u'ε'),\n    (0x1D78B, 'M', u'θ'),\n    (0x1D78C, 'M', u'κ'),\n    (0x1D78D, 'M', u'φ'),\n    (0x1D78E, 'M', u'ρ'),\n    (0x1D78F, 'M', u'π'),\n    (0x1D790, 'M', u'α'),\n    (0x1D791, 'M', u'β'),\n    (0x1D792, 'M', u'γ'),\n    (0x1D793, 'M', u'δ'),\n    (0x1D794, 'M', u'ε'),\n    (0x1D795, 'M', u'ζ'),\n    (0x1D796, 'M', u'η'),\n    (0x1D797, 'M', u'θ'),\n    (0x1D798, 'M', u'ι'),\n    (0x1D799, 'M', u'κ'),\n    (0x1D79A, 'M', u'λ'),\n    (0x1D79B, 'M', u'μ'),\n    (0x1D79C, 'M', u'ν'),\n    (0x1D79D, 'M', u'ξ'),\n    (0x1D79E, 'M', u'ο'),\n    (0x1D79F, 'M', u'π'),\n    (0x1D7A0, 'M', u'ρ'),\n    (0x1D7A1, 'M', u'θ'),\n    (0x1D7A2, 'M', u'σ'),\n    (0x1D7A3, 'M', u'τ'),\n    (0x1D7A4, 'M', u'υ'),\n    (0x1D7A5, 'M', u'φ'),\n    (0x1D7A6, 'M', u'χ'),\n    (0x1D7A7, 'M', u'ψ'),\n    (0x1D7A8, 'M', u'ω'),\n    (0x1D7A9, 'M', u'∇'),\n    (0x1D7AA, 'M', u'α'),\n    (0x1D7AB, 'M', u'β'),\n    (0x1D7AC, 'M', u'γ'),\n    (0x1D7AD, 'M', u'δ'),\n    (0x1D7AE, 'M', u'ε'),\n    (0x1D7AF, 'M', u'ζ'),\n    (0x1D7B0, 'M', u'η'),\n    (0x1D7B1, 'M', u'θ'),\n    (0x1D7B2, 'M', u'ι'),\n    (0x1D7B3, 'M', u'κ'),\n    (0x1D7B4, 'M', u'λ'),\n    (0x1D7B5, 'M', u'μ'),\n    (0x1D7B6, 'M', u'ν'),\n    (0x1D7B7, 'M', u'ξ'),\n    (0x1D7B8, 'M', u'ο'),\n    (0x1D7B9, 'M', u'π'),\n    (0x1D7BA, 'M', u'ρ'),\n    (0x1D7BB, 'M', u'σ'),\n    (0x1D7BD, 'M', u'τ'),\n    (0x1D7BE, 'M', u'υ'),\n    (0x1D7BF, 'M', u'φ'),\n    (0x1D7C0, 'M', u'χ'),\n    (0x1D7C1, 'M', u'ψ'),\n    (0x1D7C2, 'M', u'ω'),\n    (0x1D7C3, 'M', u'∂'),\n    (0x1D7C4, 'M', u'ε'),\n    (0x1D7C5, 'M', u'θ'),\n    (0x1D7C6, 'M', u'κ'),\n    (0x1D7C7, 'M', u'φ'),\n    (0x1D7C8, 'M', u'ρ'),\n    (0x1D7C9, 'M', u'π'),\n    (0x1D7CA, 'M', u'ϝ'),\n    (0x1D7CC, 'X'),\n    (0x1D7CE, 'M', u'0'),\n    (0x1D7CF, 'M', u'1'),\n    (0x1D7D0, 'M', u'2'),\n    (0x1D7D1, 'M', u'3'),\n    (0x1D7D2, 'M', u'4'),\n    (0x1D7D3, 'M', u'5'),\n    (0x1D7D4, 'M', u'6'),\n    (0x1D7D5, 'M', u'7'),\n    (0x1D7D6, 'M', u'8'),\n    (0x1D7D7, 'M', u'9'),\n    (0x1D7D8, 'M', u'0'),\n    (0x1D7D9, 'M', u'1'),\n    (0x1D7DA, 'M', u'2'),\n    (0x1D7DB, 'M', u'3'),\n    (0x1D7DC, 'M', u'4'),\n    (0x1D7DD, 'M', u'5'),\n    (0x1D7DE, 'M', u'6'),\n    (0x1D7DF, 'M', u'7'),\n    (0x1D7E0, 'M', u'8'),\n    (0x1D7E1, 'M', u'9'),\n    (0x1D7E2, 'M', u'0'),\n    (0x1D7E3, 'M', u'1'),\n    (0x1D7E4, 'M', u'2'),\n    (0x1D7E5, 'M', u'3'),\n    (0x1D7E6, 'M', u'4'),\n    (0x1D7E7, 'M', u'5'),\n    (0x1D7E8, 'M', u'6'),\n    (0x1D7E9, 'M', u'7'),\n    (0x1D7EA, 'M', u'8'),\n    (0x1D7EB, 'M', u'9'),\n    (0x1D7EC, 'M', u'0'),\n    (0x1D7ED, 'M', u'1'),\n    (0x1D7EE, 'M', u'2'),\n    ]\n\ndef _seg_68():\n    return [\n    (0x1D7EF, 'M', u'3'),\n    (0x1D7F0, 'M', u'4'),\n    (0x1D7F1, 'M', u'5'),\n    (0x1D7F2, 'M', u'6'),\n    (0x1D7F3, 'M', u'7'),\n    (0x1D7F4, 'M', u'8'),\n    (0x1D7F5, 'M', u'9'),\n    (0x1D7F6, 'M', u'0'),\n    (0x1D7F7, 'M', u'1'),\n    (0x1D7F8, 'M', u'2'),\n    (0x1D7F9, 'M', u'3'),\n    (0x1D7FA, 'M', u'4'),\n    (0x1D7FB, 'M', u'5'),\n    (0x1D7FC, 'M', u'6'),\n    (0x1D7FD, 'M', u'7'),\n    (0x1D7FE, 'M', u'8'),\n    (0x1D7FF, 'M', u'9'),\n    (0x1D800, 'V'),\n    (0x1DA8C, 'X'),\n    (0x1DA9B, 'V'),\n    (0x1DAA0, 'X'),\n    (0x1DAA1, 'V'),\n    (0x1DAB0, 'X'),\n    (0x1E000, 'V'),\n    (0x1E007, 'X'),\n    (0x1E008, 'V'),\n    (0x1E019, 'X'),\n    (0x1E01B, 'V'),\n    (0x1E022, 'X'),\n    (0x1E023, 'V'),\n    (0x1E025, 'X'),\n    (0x1E026, 'V'),\n    (0x1E02B, 'X'),\n    (0x1E800, 'V'),\n    (0x1E8C5, 'X'),\n    (0x1E8C7, 'V'),\n    (0x1E8D7, 'X'),\n    (0x1E900, 'M', u'𞤢'),\n    (0x1E901, 'M', u'𞤣'),\n    (0x1E902, 'M', u'𞤤'),\n    (0x1E903, 'M', u'𞤥'),\n    (0x1E904, 'M', u'𞤦'),\n    (0x1E905, 'M', u'𞤧'),\n    (0x1E906, 'M', u'𞤨'),\n    (0x1E907, 'M', u'𞤩'),\n    (0x1E908, 'M', u'𞤪'),\n    (0x1E909, 'M', u'𞤫'),\n    (0x1E90A, 'M', u'𞤬'),\n    (0x1E90B, 'M', u'𞤭'),\n    (0x1E90C, 'M', u'𞤮'),\n    (0x1E90D, 'M', u'𞤯'),\n    (0x1E90E, 'M', u'𞤰'),\n    (0x1E90F, 'M', u'𞤱'),\n    (0x1E910, 'M', u'𞤲'),\n    (0x1E911, 'M', u'𞤳'),\n    (0x1E912, 'M', u'𞤴'),\n    (0x1E913, 'M', u'𞤵'),\n    (0x1E914, 'M', u'𞤶'),\n    (0x1E915, 'M', u'𞤷'),\n    (0x1E916, 'M', u'𞤸'),\n    (0x1E917, 'M', u'𞤹'),\n    (0x1E918, 'M', u'𞤺'),\n    (0x1E919, 'M', u'𞤻'),\n    (0x1E91A, 'M', u'𞤼'),\n    (0x1E91B, 'M', u'𞤽'),\n    (0x1E91C, 'M', u'𞤾'),\n    (0x1E91D, 'M', u'𞤿'),\n    (0x1E91E, 'M', u'𞥀'),\n    (0x1E91F, 'M', u'𞥁'),\n    (0x1E920, 'M', u'𞥂'),\n    (0x1E921, 'M', u'𞥃'),\n    (0x1E922, 'V'),\n    (0x1E94B, 'X'),\n    (0x1E950, 'V'),\n    (0x1E95A, 'X'),\n    (0x1E95E, 'V'),\n    (0x1E960, 'X'),\n    (0x1EC71, 'V'),\n    (0x1ECB5, 'X'),\n    (0x1EE00, 'M', u'ا'),\n    (0x1EE01, 'M', u'ب'),\n    (0x1EE02, 'M', u'ج'),\n    (0x1EE03, 'M', u'د'),\n    (0x1EE04, 'X'),\n    (0x1EE05, 'M', u'و'),\n    (0x1EE06, 'M', u'ز'),\n    (0x1EE07, 'M', u'ح'),\n    (0x1EE08, 'M', u'ط'),\n    (0x1EE09, 'M', u'ي'),\n    (0x1EE0A, 'M', u'ك'),\n    (0x1EE0B, 'M', u'ل'),\n    (0x1EE0C, 'M', u'م'),\n    (0x1EE0D, 'M', u'ن'),\n    (0x1EE0E, 'M', u'س'),\n    (0x1EE0F, 'M', u'ع'),\n    (0x1EE10, 'M', u'ف'),\n    (0x1EE11, 'M', u'ص'),\n    (0x1EE12, 'M', u'ق'),\n    (0x1EE13, 'M', u'ر'),\n    (0x1EE14, 'M', u'ش'),\n    ]\n\ndef _seg_69():\n    return [\n    (0x1EE15, 'M', u'ت'),\n    (0x1EE16, 'M', u'ث'),\n    (0x1EE17, 'M', u'خ'),\n    (0x1EE18, 'M', u'ذ'),\n    (0x1EE19, 'M', u'ض'),\n    (0x1EE1A, 'M', u'ظ'),\n    (0x1EE1B, 'M', u'غ'),\n    (0x1EE1C, 'M', u'ٮ'),\n    (0x1EE1D, 'M', u'ں'),\n    (0x1EE1E, 'M', u'ڡ'),\n    (0x1EE1F, 'M', u'ٯ'),\n    (0x1EE20, 'X'),\n    (0x1EE21, 'M', u'ب'),\n    (0x1EE22, 'M', u'ج'),\n    (0x1EE23, 'X'),\n    (0x1EE24, 'M', u'ه'),\n    (0x1EE25, 'X'),\n    (0x1EE27, 'M', u'ح'),\n    (0x1EE28, 'X'),\n    (0x1EE29, 'M', u'ي'),\n    (0x1EE2A, 'M', u'ك'),\n    (0x1EE2B, 'M', u'ل'),\n    (0x1EE2C, 'M', u'م'),\n    (0x1EE2D, 'M', u'ن'),\n    (0x1EE2E, 'M', u'س'),\n    (0x1EE2F, 'M', u'ع'),\n    (0x1EE30, 'M', u'ف'),\n    (0x1EE31, 'M', u'ص'),\n    (0x1EE32, 'M', u'ق'),\n    (0x1EE33, 'X'),\n    (0x1EE34, 'M', u'ش'),\n    (0x1EE35, 'M', u'ت'),\n    (0x1EE36, 'M', u'ث'),\n    (0x1EE37, 'M', u'خ'),\n    (0x1EE38, 'X'),\n    (0x1EE39, 'M', u'ض'),\n    (0x1EE3A, 'X'),\n    (0x1EE3B, 'M', u'غ'),\n    (0x1EE3C, 'X'),\n    (0x1EE42, 'M', u'ج'),\n    (0x1EE43, 'X'),\n    (0x1EE47, 'M', u'ح'),\n    (0x1EE48, 'X'),\n    (0x1EE49, 'M', u'ي'),\n    (0x1EE4A, 'X'),\n    (0x1EE4B, 'M', u'ل'),\n    (0x1EE4C, 'X'),\n    (0x1EE4D, 'M', u'ن'),\n    (0x1EE4E, 'M', u'س'),\n    (0x1EE4F, 'M', u'ع'),\n    (0x1EE50, 'X'),\n    (0x1EE51, 'M', u'ص'),\n    (0x1EE52, 'M', u'ق'),\n    (0x1EE53, 'X'),\n    (0x1EE54, 'M', u'ش'),\n    (0x1EE55, 'X'),\n    (0x1EE57, 'M', u'خ'),\n    (0x1EE58, 'X'),\n    (0x1EE59, 'M', u'ض'),\n    (0x1EE5A, 'X'),\n    (0x1EE5B, 'M', u'غ'),\n    (0x1EE5C, 'X'),\n    (0x1EE5D, 'M', u'ں'),\n    (0x1EE5E, 'X'),\n    (0x1EE5F, 'M', u'ٯ'),\n    (0x1EE60, 'X'),\n    (0x1EE61, 'M', u'ب'),\n    (0x1EE62, 'M', u'ج'),\n    (0x1EE63, 'X'),\n    (0x1EE64, 'M', u'ه'),\n    (0x1EE65, 'X'),\n    (0x1EE67, 'M', u'ح'),\n    (0x1EE68, 'M', u'ط'),\n    (0x1EE69, 'M', u'ي'),\n    (0x1EE6A, 'M', u'ك'),\n    (0x1EE6B, 'X'),\n    (0x1EE6C, 'M', u'م'),\n    (0x1EE6D, 'M', u'ن'),\n    (0x1EE6E, 'M', u'س'),\n    (0x1EE6F, 'M', u'ع'),\n    (0x1EE70, 'M', u'ف'),\n    (0x1EE71, 'M', u'ص'),\n    (0x1EE72, 'M', u'ق'),\n    (0x1EE73, 'X'),\n    (0x1EE74, 'M', u'ش'),\n    (0x1EE75, 'M', u'ت'),\n    (0x1EE76, 'M', u'ث'),\n    (0x1EE77, 'M', u'خ'),\n    (0x1EE78, 'X'),\n    (0x1EE79, 'M', u'ض'),\n    (0x1EE7A, 'M', u'ظ'),\n    (0x1EE7B, 'M', u'غ'),\n    (0x1EE7C, 'M', u'ٮ'),\n    (0x1EE7D, 'X'),\n    (0x1EE7E, 'M', u'ڡ'),\n    (0x1EE7F, 'X'),\n    (0x1EE80, 'M', u'ا'),\n    (0x1EE81, 'M', u'ب'),\n    (0x1EE82, 'M', u'ج'),\n    (0x1EE83, 'M', u'د'),\n    ]\n\ndef _seg_70():\n    return [\n    (0x1EE84, 'M', u'ه'),\n    (0x1EE85, 'M', u'و'),\n    (0x1EE86, 'M', u'ز'),\n    (0x1EE87, 'M', u'ح'),\n    (0x1EE88, 'M', u'ط'),\n    (0x1EE89, 'M', u'ي'),\n    (0x1EE8A, 'X'),\n    (0x1EE8B, 'M', u'ل'),\n    (0x1EE8C, 'M', u'م'),\n    (0x1EE8D, 'M', u'ن'),\n    (0x1EE8E, 'M', u'س'),\n    (0x1EE8F, 'M', u'ع'),\n    (0x1EE90, 'M', u'ف'),\n    (0x1EE91, 'M', u'ص'),\n    (0x1EE92, 'M', u'ق'),\n    (0x1EE93, 'M', u'ر'),\n    (0x1EE94, 'M', u'ش'),\n    (0x1EE95, 'M', u'ت'),\n    (0x1EE96, 'M', u'ث'),\n    (0x1EE97, 'M', u'خ'),\n    (0x1EE98, 'M', u'ذ'),\n    (0x1EE99, 'M', u'ض'),\n    (0x1EE9A, 'M', u'ظ'),\n    (0x1EE9B, 'M', u'غ'),\n    (0x1EE9C, 'X'),\n    (0x1EEA1, 'M', u'ب'),\n    (0x1EEA2, 'M', u'ج'),\n    (0x1EEA3, 'M', u'د'),\n    (0x1EEA4, 'X'),\n    (0x1EEA5, 'M', u'و'),\n    (0x1EEA6, 'M', u'ز'),\n    (0x1EEA7, 'M', u'ح'),\n    (0x1EEA8, 'M', u'ط'),\n    (0x1EEA9, 'M', u'ي'),\n    (0x1EEAA, 'X'),\n    (0x1EEAB, 'M', u'ل'),\n    (0x1EEAC, 'M', u'م'),\n    (0x1EEAD, 'M', u'ن'),\n    (0x1EEAE, 'M', u'س'),\n    (0x1EEAF, 'M', u'ع'),\n    (0x1EEB0, 'M', u'ف'),\n    (0x1EEB1, 'M', u'ص'),\n    (0x1EEB2, 'M', u'ق'),\n    (0x1EEB3, 'M', u'ر'),\n    (0x1EEB4, 'M', u'ش'),\n    (0x1EEB5, 'M', u'ت'),\n    (0x1EEB6, 'M', u'ث'),\n    (0x1EEB7, 'M', u'خ'),\n    (0x1EEB8, 'M', u'ذ'),\n    (0x1EEB9, 'M', u'ض'),\n    (0x1EEBA, 'M', u'ظ'),\n    (0x1EEBB, 'M', u'غ'),\n    (0x1EEBC, 'X'),\n    (0x1EEF0, 'V'),\n    (0x1EEF2, 'X'),\n    (0x1F000, 'V'),\n    (0x1F02C, 'X'),\n    (0x1F030, 'V'),\n    (0x1F094, 'X'),\n    (0x1F0A0, 'V'),\n    (0x1F0AF, 'X'),\n    (0x1F0B1, 'V'),\n    (0x1F0C0, 'X'),\n    (0x1F0C1, 'V'),\n    (0x1F0D0, 'X'),\n    (0x1F0D1, 'V'),\n    (0x1F0F6, 'X'),\n    (0x1F101, '3', u'0,'),\n    (0x1F102, '3', u'1,'),\n    (0x1F103, '3', u'2,'),\n    (0x1F104, '3', u'3,'),\n    (0x1F105, '3', u'4,'),\n    (0x1F106, '3', u'5,'),\n    (0x1F107, '3', u'6,'),\n    (0x1F108, '3', u'7,'),\n    (0x1F109, '3', u'8,'),\n    (0x1F10A, '3', u'9,'),\n    (0x1F10B, 'V'),\n    (0x1F10D, 'X'),\n    (0x1F110, '3', u'(a)'),\n    (0x1F111, '3', u'(b)'),\n    (0x1F112, '3', u'(c)'),\n    (0x1F113, '3', u'(d)'),\n    (0x1F114, '3', u'(e)'),\n    (0x1F115, '3', u'(f)'),\n    (0x1F116, '3', u'(g)'),\n    (0x1F117, '3', u'(h)'),\n    (0x1F118, '3', u'(i)'),\n    (0x1F119, '3', u'(j)'),\n    (0x1F11A, '3', u'(k)'),\n    (0x1F11B, '3', u'(l)'),\n    (0x1F11C, '3', u'(m)'),\n    (0x1F11D, '3', u'(n)'),\n    (0x1F11E, '3', u'(o)'),\n    (0x1F11F, '3', u'(p)'),\n    (0x1F120, '3', u'(q)'),\n    (0x1F121, '3', u'(r)'),\n    (0x1F122, '3', u'(s)'),\n    (0x1F123, '3', u'(t)'),\n    (0x1F124, '3', u'(u)'),\n    ]\n\ndef _seg_71():\n    return [\n    (0x1F125, '3', u'(v)'),\n    (0x1F126, '3', u'(w)'),\n    (0x1F127, '3', u'(x)'),\n    (0x1F128, '3', u'(y)'),\n    (0x1F129, '3', u'(z)'),\n    (0x1F12A, 'M', u'〔s〕'),\n    (0x1F12B, 'M', u'c'),\n    (0x1F12C, 'M', u'r'),\n    (0x1F12D, 'M', u'cd'),\n    (0x1F12E, 'M', u'wz'),\n    (0x1F12F, 'V'),\n    (0x1F130, 'M', u'a'),\n    (0x1F131, 'M', u'b'),\n    (0x1F132, 'M', u'c'),\n    (0x1F133, 'M', u'd'),\n    (0x1F134, 'M', u'e'),\n    (0x1F135, 'M', u'f'),\n    (0x1F136, 'M', u'g'),\n    (0x1F137, 'M', u'h'),\n    (0x1F138, 'M', u'i'),\n    (0x1F139, 'M', u'j'),\n    (0x1F13A, 'M', u'k'),\n    (0x1F13B, 'M', u'l'),\n    (0x1F13C, 'M', u'm'),\n    (0x1F13D, 'M', u'n'),\n    (0x1F13E, 'M', u'o'),\n    (0x1F13F, 'M', u'p'),\n    (0x1F140, 'M', u'q'),\n    (0x1F141, 'M', u'r'),\n    (0x1F142, 'M', u's'),\n    (0x1F143, 'M', u't'),\n    (0x1F144, 'M', u'u'),\n    (0x1F145, 'M', u'v'),\n    (0x1F146, 'M', u'w'),\n    (0x1F147, 'M', u'x'),\n    (0x1F148, 'M', u'y'),\n    (0x1F149, 'M', u'z'),\n    (0x1F14A, 'M', u'hv'),\n    (0x1F14B, 'M', u'mv'),\n    (0x1F14C, 'M', u'sd'),\n    (0x1F14D, 'M', u'ss'),\n    (0x1F14E, 'M', u'ppv'),\n    (0x1F14F, 'M', u'wc'),\n    (0x1F150, 'V'),\n    (0x1F16A, 'M', u'mc'),\n    (0x1F16B, 'M', u'md'),\n    (0x1F16C, 'X'),\n    (0x1F170, 'V'),\n    (0x1F190, 'M', u'dj'),\n    (0x1F191, 'V'),\n    (0x1F1AD, 'X'),\n    (0x1F1E6, 'V'),\n    (0x1F200, 'M', u'ほか'),\n    (0x1F201, 'M', u'ココ'),\n    (0x1F202, 'M', u'サ'),\n    (0x1F203, 'X'),\n    (0x1F210, 'M', u'手'),\n    (0x1F211, 'M', u'字'),\n    (0x1F212, 'M', u'双'),\n    (0x1F213, 'M', u'デ'),\n    (0x1F214, 'M', u'二'),\n    (0x1F215, 'M', u'多'),\n    (0x1F216, 'M', u'解'),\n    (0x1F217, 'M', u'天'),\n    (0x1F218, 'M', u'交'),\n    (0x1F219, 'M', u'映'),\n    (0x1F21A, 'M', u'無'),\n    (0x1F21B, 'M', u'料'),\n    (0x1F21C, 'M', u'前'),\n    (0x1F21D, 'M', u'後'),\n    (0x1F21E, 'M', u'再'),\n    (0x1F21F, 'M', u'新'),\n    (0x1F220, 'M', u'初'),\n    (0x1F221, 'M', u'終'),\n    (0x1F222, 'M', u'生'),\n    (0x1F223, 'M', u'販'),\n    (0x1F224, 'M', u'声'),\n    (0x1F225, 'M', u'吹'),\n    (0x1F226, 'M', u'演'),\n    (0x1F227, 'M', u'投'),\n    (0x1F228, 'M', u'捕'),\n    (0x1F229, 'M', u'一'),\n    (0x1F22A, 'M', u'三'),\n    (0x1F22B, 'M', u'遊'),\n    (0x1F22C, 'M', u'左'),\n    (0x1F22D, 'M', u'中'),\n    (0x1F22E, 'M', u'右'),\n    (0x1F22F, 'M', u'指'),\n    (0x1F230, 'M', u'走'),\n    (0x1F231, 'M', u'打'),\n    (0x1F232, 'M', u'禁'),\n    (0x1F233, 'M', u'空'),\n    (0x1F234, 'M', u'合'),\n    (0x1F235, 'M', u'満'),\n    (0x1F236, 'M', u'有'),\n    (0x1F237, 'M', u'月'),\n    (0x1F238, 'M', u'申'),\n    (0x1F239, 'M', u'割'),\n    (0x1F23A, 'M', u'営'),\n    (0x1F23B, 'M', u'配'),\n    ]\n\ndef _seg_72():\n    return [\n    (0x1F23C, 'X'),\n    (0x1F240, 'M', u'〔本〕'),\n    (0x1F241, 'M', u'〔三〕'),\n    (0x1F242, 'M', u'〔二〕'),\n    (0x1F243, 'M', u'〔安〕'),\n    (0x1F244, 'M', u'〔点〕'),\n    (0x1F245, 'M', u'〔打〕'),\n    (0x1F246, 'M', u'〔盗〕'),\n    (0x1F247, 'M', u'〔勝〕'),\n    (0x1F248, 'M', u'〔敗〕'),\n    (0x1F249, 'X'),\n    (0x1F250, 'M', u'得'),\n    (0x1F251, 'M', u'可'),\n    (0x1F252, 'X'),\n    (0x1F260, 'V'),\n    (0x1F266, 'X'),\n    (0x1F300, 'V'),\n    (0x1F6D5, 'X'),\n    (0x1F6E0, 'V'),\n    (0x1F6ED, 'X'),\n    (0x1F6F0, 'V'),\n    (0x1F6FA, 'X'),\n    (0x1F700, 'V'),\n    (0x1F774, 'X'),\n    (0x1F780, 'V'),\n    (0x1F7D9, 'X'),\n    (0x1F800, 'V'),\n    (0x1F80C, 'X'),\n    (0x1F810, 'V'),\n    (0x1F848, 'X'),\n    (0x1F850, 'V'),\n    (0x1F85A, 'X'),\n    (0x1F860, 'V'),\n    (0x1F888, 'X'),\n    (0x1F890, 'V'),\n    (0x1F8AE, 'X'),\n    (0x1F900, 'V'),\n    (0x1F90C, 'X'),\n    (0x1F910, 'V'),\n    (0x1F93F, 'X'),\n    (0x1F940, 'V'),\n    (0x1F971, 'X'),\n    (0x1F973, 'V'),\n    (0x1F977, 'X'),\n    (0x1F97A, 'V'),\n    (0x1F97B, 'X'),\n    (0x1F97C, 'V'),\n    (0x1F9A3, 'X'),\n    (0x1F9B0, 'V'),\n    (0x1F9BA, 'X'),\n    (0x1F9C0, 'V'),\n    (0x1F9C3, 'X'),\n    (0x1F9D0, 'V'),\n    (0x1FA00, 'X'),\n    (0x1FA60, 'V'),\n    (0x1FA6E, 'X'),\n    (0x20000, 'V'),\n    (0x2A6D7, 'X'),\n    (0x2A700, 'V'),\n    (0x2B735, 'X'),\n    (0x2B740, 'V'),\n    (0x2B81E, 'X'),\n    (0x2B820, 'V'),\n    (0x2CEA2, 'X'),\n    (0x2CEB0, 'V'),\n    (0x2EBE1, 'X'),\n    (0x2F800, 'M', u'丽'),\n    (0x2F801, 'M', u'丸'),\n    (0x2F802, 'M', u'乁'),\n    (0x2F803, 'M', u'𠄢'),\n    (0x2F804, 'M', u'你'),\n    (0x2F805, 'M', u'侮'),\n    (0x2F806, 'M', u'侻'),\n    (0x2F807, 'M', u'倂'),\n    (0x2F808, 'M', u'偺'),\n    (0x2F809, 'M', u'備'),\n    (0x2F80A, 'M', u'僧'),\n    (0x2F80B, 'M', u'像'),\n    (0x2F80C, 'M', u'㒞'),\n    (0x2F80D, 'M', u'𠘺'),\n    (0x2F80E, 'M', u'免'),\n    (0x2F80F, 'M', u'兔'),\n    (0x2F810, 'M', u'兤'),\n    (0x2F811, 'M', u'具'),\n    (0x2F812, 'M', u'𠔜'),\n    (0x2F813, 'M', u'㒹'),\n    (0x2F814, 'M', u'內'),\n    (0x2F815, 'M', u'再'),\n    (0x2F816, 'M', u'𠕋'),\n    (0x2F817, 'M', u'冗'),\n    (0x2F818, 'M', u'冤'),\n    (0x2F819, 'M', u'仌'),\n    (0x2F81A, 'M', u'冬'),\n    (0x2F81B, 'M', u'况'),\n    (0x2F81C, 'M', u'𩇟'),\n    (0x2F81D, 'M', u'凵'),\n    (0x2F81E, 'M', u'刃'),\n    (0x2F81F, 'M', u'㓟'),\n    (0x2F820, 'M', u'刻'),\n    (0x2F821, 'M', u'剆'),\n    ]\n\ndef _seg_73():\n    return [\n    (0x2F822, 'M', u'割'),\n    (0x2F823, 'M', u'剷'),\n    (0x2F824, 'M', u'㔕'),\n    (0x2F825, 'M', u'勇'),\n    (0x2F826, 'M', u'勉'),\n    (0x2F827, 'M', u'勤'),\n    (0x2F828, 'M', u'勺'),\n    (0x2F829, 'M', u'包'),\n    (0x2F82A, 'M', u'匆'),\n    (0x2F82B, 'M', u'北'),\n    (0x2F82C, 'M', u'卉'),\n    (0x2F82D, 'M', u'卑'),\n    (0x2F82E, 'M', u'博'),\n    (0x2F82F, 'M', u'即'),\n    (0x2F830, 'M', u'卽'),\n    (0x2F831, 'M', u'卿'),\n    (0x2F834, 'M', u'𠨬'),\n    (0x2F835, 'M', u'灰'),\n    (0x2F836, 'M', u'及'),\n    (0x2F837, 'M', u'叟'),\n    (0x2F838, 'M', u'𠭣'),\n    (0x2F839, 'M', u'叫'),\n    (0x2F83A, 'M', u'叱'),\n    (0x2F83B, 'M', u'吆'),\n    (0x2F83C, 'M', u'咞'),\n    (0x2F83D, 'M', u'吸'),\n    (0x2F83E, 'M', u'呈'),\n    (0x2F83F, 'M', u'周'),\n    (0x2F840, 'M', u'咢'),\n    (0x2F841, 'M', u'哶'),\n    (0x2F842, 'M', u'唐'),\n    (0x2F843, 'M', u'啓'),\n    (0x2F844, 'M', u'啣'),\n    (0x2F845, 'M', u'善'),\n    (0x2F847, 'M', u'喙'),\n    (0x2F848, 'M', u'喫'),\n    (0x2F849, 'M', u'喳'),\n    (0x2F84A, 'M', u'嗂'),\n    (0x2F84B, 'M', u'圖'),\n    (0x2F84C, 'M', u'嘆'),\n    (0x2F84D, 'M', u'圗'),\n    (0x2F84E, 'M', u'噑'),\n    (0x2F84F, 'M', u'噴'),\n    (0x2F850, 'M', u'切'),\n    (0x2F851, 'M', u'壮'),\n    (0x2F852, 'M', u'城'),\n    (0x2F853, 'M', u'埴'),\n    (0x2F854, 'M', u'堍'),\n    (0x2F855, 'M', u'型'),\n    (0x2F856, 'M', u'堲'),\n    (0x2F857, 'M', u'報'),\n    (0x2F858, 'M', u'墬'),\n    (0x2F859, 'M', u'𡓤'),\n    (0x2F85A, 'M', u'売'),\n    (0x2F85B, 'M', u'壷'),\n    (0x2F85C, 'M', u'夆'),\n    (0x2F85D, 'M', u'多'),\n    (0x2F85E, 'M', u'夢'),\n    (0x2F85F, 'M', u'奢'),\n    (0x2F860, 'M', u'𡚨'),\n    (0x2F861, 'M', u'𡛪'),\n    (0x2F862, 'M', u'姬'),\n    (0x2F863, 'M', u'娛'),\n    (0x2F864, 'M', u'娧'),\n    (0x2F865, 'M', u'姘'),\n    (0x2F866, 'M', u'婦'),\n    (0x2F867, 'M', u'㛮'),\n    (0x2F868, 'X'),\n    (0x2F869, 'M', u'嬈'),\n    (0x2F86A, 'M', u'嬾'),\n    (0x2F86C, 'M', u'𡧈'),\n    (0x2F86D, 'M', u'寃'),\n    (0x2F86E, 'M', u'寘'),\n    (0x2F86F, 'M', u'寧'),\n    (0x2F870, 'M', u'寳'),\n    (0x2F871, 'M', u'𡬘'),\n    (0x2F872, 'M', u'寿'),\n    (0x2F873, 'M', u'将'),\n    (0x2F874, 'X'),\n    (0x2F875, 'M', u'尢'),\n    (0x2F876, 'M', u'㞁'),\n    (0x2F877, 'M', u'屠'),\n    (0x2F878, 'M', u'屮'),\n    (0x2F879, 'M', u'峀'),\n    (0x2F87A, 'M', u'岍'),\n    (0x2F87B, 'M', u'𡷤'),\n    (0x2F87C, 'M', u'嵃'),\n    (0x2F87D, 'M', u'𡷦'),\n    (0x2F87E, 'M', u'嵮'),\n    (0x2F87F, 'M', u'嵫'),\n    (0x2F880, 'M', u'嵼'),\n    (0x2F881, 'M', u'巡'),\n    (0x2F882, 'M', u'巢'),\n    (0x2F883, 'M', u'㠯'),\n    (0x2F884, 'M', u'巽'),\n    (0x2F885, 'M', u'帨'),\n    (0x2F886, 'M', u'帽'),\n    (0x2F887, 'M', u'幩'),\n    (0x2F888, 'M', u'㡢'),\n    (0x2F889, 'M', u'𢆃'),\n    ]\n\ndef _seg_74():\n    return [\n    (0x2F88A, 'M', u'㡼'),\n    (0x2F88B, 'M', u'庰'),\n    (0x2F88C, 'M', u'庳'),\n    (0x2F88D, 'M', u'庶'),\n    (0x2F88E, 'M', u'廊'),\n    (0x2F88F, 'M', u'𪎒'),\n    (0x2F890, 'M', u'廾'),\n    (0x2F891, 'M', u'𢌱'),\n    (0x2F893, 'M', u'舁'),\n    (0x2F894, 'M', u'弢'),\n    (0x2F896, 'M', u'㣇'),\n    (0x2F897, 'M', u'𣊸'),\n    (0x2F898, 'M', u'𦇚'),\n    (0x2F899, 'M', u'形'),\n    (0x2F89A, 'M', u'彫'),\n    (0x2F89B, 'M', u'㣣'),\n    (0x2F89C, 'M', u'徚'),\n    (0x2F89D, 'M', u'忍'),\n    (0x2F89E, 'M', u'志'),\n    (0x2F89F, 'M', u'忹'),\n    (0x2F8A0, 'M', u'悁'),\n    (0x2F8A1, 'M', u'㤺'),\n    (0x2F8A2, 'M', u'㤜'),\n    (0x2F8A3, 'M', u'悔'),\n    (0x2F8A4, 'M', u'𢛔'),\n    (0x2F8A5, 'M', u'惇'),\n    (0x2F8A6, 'M', u'慈'),\n    (0x2F8A7, 'M', u'慌'),\n    (0x2F8A8, 'M', u'慎'),\n    (0x2F8A9, 'M', u'慌'),\n    (0x2F8AA, 'M', u'慺'),\n    (0x2F8AB, 'M', u'憎'),\n    (0x2F8AC, 'M', u'憲'),\n    (0x2F8AD, 'M', u'憤'),\n    (0x2F8AE, 'M', u'憯'),\n    (0x2F8AF, 'M', u'懞'),\n    (0x2F8B0, 'M', u'懲'),\n    (0x2F8B1, 'M', u'懶'),\n    (0x2F8B2, 'M', u'成'),\n    (0x2F8B3, 'M', u'戛'),\n    (0x2F8B4, 'M', u'扝'),\n    (0x2F8B5, 'M', u'抱'),\n    (0x2F8B6, 'M', u'拔'),\n    (0x2F8B7, 'M', u'捐'),\n    (0x2F8B8, 'M', u'𢬌'),\n    (0x2F8B9, 'M', u'挽'),\n    (0x2F8BA, 'M', u'拼'),\n    (0x2F8BB, 'M', u'捨'),\n    (0x2F8BC, 'M', u'掃'),\n    (0x2F8BD, 'M', u'揤'),\n    (0x2F8BE, 'M', u'𢯱'),\n    (0x2F8BF, 'M', u'搢'),\n    (0x2F8C0, 'M', u'揅'),\n    (0x2F8C1, 'M', u'掩'),\n    (0x2F8C2, 'M', u'㨮'),\n    (0x2F8C3, 'M', u'摩'),\n    (0x2F8C4, 'M', u'摾'),\n    (0x2F8C5, 'M', u'撝'),\n    (0x2F8C6, 'M', u'摷'),\n    (0x2F8C7, 'M', u'㩬'),\n    (0x2F8C8, 'M', u'敏'),\n    (0x2F8C9, 'M', u'敬'),\n    (0x2F8CA, 'M', u'𣀊'),\n    (0x2F8CB, 'M', u'旣'),\n    (0x2F8CC, 'M', u'書'),\n    (0x2F8CD, 'M', u'晉'),\n    (0x2F8CE, 'M', u'㬙'),\n    (0x2F8CF, 'M', u'暑'),\n    (0x2F8D0, 'M', u'㬈'),\n    (0x2F8D1, 'M', u'㫤'),\n    (0x2F8D2, 'M', u'冒'),\n    (0x2F8D3, 'M', u'冕'),\n    (0x2F8D4, 'M', u'最'),\n    (0x2F8D5, 'M', u'暜'),\n    (0x2F8D6, 'M', u'肭'),\n    (0x2F8D7, 'M', u'䏙'),\n    (0x2F8D8, 'M', u'朗'),\n    (0x2F8D9, 'M', u'望'),\n    (0x2F8DA, 'M', u'朡'),\n    (0x2F8DB, 'M', u'杞'),\n    (0x2F8DC, 'M', u'杓'),\n    (0x2F8DD, 'M', u'𣏃'),\n    (0x2F8DE, 'M', u'㭉'),\n    (0x2F8DF, 'M', u'柺'),\n    (0x2F8E0, 'M', u'枅'),\n    (0x2F8E1, 'M', u'桒'),\n    (0x2F8E2, 'M', u'梅'),\n    (0x2F8E3, 'M', u'𣑭'),\n    (0x2F8E4, 'M', u'梎'),\n    (0x2F8E5, 'M', u'栟'),\n    (0x2F8E6, 'M', u'椔'),\n    (0x2F8E7, 'M', u'㮝'),\n    (0x2F8E8, 'M', u'楂'),\n    (0x2F8E9, 'M', u'榣'),\n    (0x2F8EA, 'M', u'槪'),\n    (0x2F8EB, 'M', u'檨'),\n    (0x2F8EC, 'M', u'𣚣'),\n    (0x2F8ED, 'M', u'櫛'),\n    (0x2F8EE, 'M', u'㰘'),\n    (0x2F8EF, 'M', u'次'),\n    ]\n\ndef _seg_75():\n    return [\n    (0x2F8F0, 'M', u'𣢧'),\n    (0x2F8F1, 'M', u'歔'),\n    (0x2F8F2, 'M', u'㱎'),\n    (0x2F8F3, 'M', u'歲'),\n    (0x2F8F4, 'M', u'殟'),\n    (0x2F8F5, 'M', u'殺'),\n    (0x2F8F6, 'M', u'殻'),\n    (0x2F8F7, 'M', u'𣪍'),\n    (0x2F8F8, 'M', u'𡴋'),\n    (0x2F8F9, 'M', u'𣫺'),\n    (0x2F8FA, 'M', u'汎'),\n    (0x2F8FB, 'M', u'𣲼'),\n    (0x2F8FC, 'M', u'沿'),\n    (0x2F8FD, 'M', u'泍'),\n    (0x2F8FE, 'M', u'汧'),\n    (0x2F8FF, 'M', u'洖'),\n    (0x2F900, 'M', u'派'),\n    (0x2F901, 'M', u'海'),\n    (0x2F902, 'M', u'流'),\n    (0x2F903, 'M', u'浩'),\n    (0x2F904, 'M', u'浸'),\n    (0x2F905, 'M', u'涅'),\n    (0x2F906, 'M', u'𣴞'),\n    (0x2F907, 'M', u'洴'),\n    (0x2F908, 'M', u'港'),\n    (0x2F909, 'M', u'湮'),\n    (0x2F90A, 'M', u'㴳'),\n    (0x2F90B, 'M', u'滋'),\n    (0x2F90C, 'M', u'滇'),\n    (0x2F90D, 'M', u'𣻑'),\n    (0x2F90E, 'M', u'淹'),\n    (0x2F90F, 'M', u'潮'),\n    (0x2F910, 'M', u'𣽞'),\n    (0x2F911, 'M', u'𣾎'),\n    (0x2F912, 'M', u'濆'),\n    (0x2F913, 'M', u'瀹'),\n    (0x2F914, 'M', u'瀞'),\n    (0x2F915, 'M', u'瀛'),\n    (0x2F916, 'M', u'㶖'),\n    (0x2F917, 'M', u'灊'),\n    (0x2F918, 'M', u'災'),\n    (0x2F919, 'M', u'灷'),\n    (0x2F91A, 'M', u'炭'),\n    (0x2F91B, 'M', u'𠔥'),\n    (0x2F91C, 'M', u'煅'),\n    (0x2F91D, 'M', u'𤉣'),\n    (0x2F91E, 'M', u'熜'),\n    (0x2F91F, 'X'),\n    (0x2F920, 'M', u'爨'),\n    (0x2F921, 'M', u'爵'),\n    (0x2F922, 'M', u'牐'),\n    (0x2F923, 'M', u'𤘈'),\n    (0x2F924, 'M', u'犀'),\n    (0x2F925, 'M', u'犕'),\n    (0x2F926, 'M', u'𤜵'),\n    (0x2F927, 'M', u'𤠔'),\n    (0x2F928, 'M', u'獺'),\n    (0x2F929, 'M', u'王'),\n    (0x2F92A, 'M', u'㺬'),\n    (0x2F92B, 'M', u'玥'),\n    (0x2F92C, 'M', u'㺸'),\n    (0x2F92E, 'M', u'瑇'),\n    (0x2F92F, 'M', u'瑜'),\n    (0x2F930, 'M', u'瑱'),\n    (0x2F931, 'M', u'璅'),\n    (0x2F932, 'M', u'瓊'),\n    (0x2F933, 'M', u'㼛'),\n    (0x2F934, 'M', u'甤'),\n    (0x2F935, 'M', u'𤰶'),\n    (0x2F936, 'M', u'甾'),\n    (0x2F937, 'M', u'𤲒'),\n    (0x2F938, 'M', u'異'),\n    (0x2F939, 'M', u'𢆟'),\n    (0x2F93A, 'M', u'瘐'),\n    (0x2F93B, 'M', u'𤾡'),\n    (0x2F93C, 'M', u'𤾸'),\n    (0x2F93D, 'M', u'𥁄'),\n    (0x2F93E, 'M', u'㿼'),\n    (0x2F93F, 'M', u'䀈'),\n    (0x2F940, 'M', u'直'),\n    (0x2F941, 'M', u'𥃳'),\n    (0x2F942, 'M', u'𥃲'),\n    (0x2F943, 'M', u'𥄙'),\n    (0x2F944, 'M', u'𥄳'),\n    (0x2F945, 'M', u'眞'),\n    (0x2F946, 'M', u'真'),\n    (0x2F948, 'M', u'睊'),\n    (0x2F949, 'M', u'䀹'),\n    (0x2F94A, 'M', u'瞋'),\n    (0x2F94B, 'M', u'䁆'),\n    (0x2F94C, 'M', u'䂖'),\n    (0x2F94D, 'M', u'𥐝'),\n    (0x2F94E, 'M', u'硎'),\n    (0x2F94F, 'M', u'碌'),\n    (0x2F950, 'M', u'磌'),\n    (0x2F951, 'M', u'䃣'),\n    (0x2F952, 'M', u'𥘦'),\n    (0x2F953, 'M', u'祖'),\n    (0x2F954, 'M', u'𥚚'),\n    (0x2F955, 'M', u'𥛅'),\n    ]\n\ndef _seg_76():\n    return [\n    (0x2F956, 'M', u'福'),\n    (0x2F957, 'M', u'秫'),\n    (0x2F958, 'M', u'䄯'),\n    (0x2F959, 'M', u'穀'),\n    (0x2F95A, 'M', u'穊'),\n    (0x2F95B, 'M', u'穏'),\n    (0x2F95C, 'M', u'𥥼'),\n    (0x2F95D, 'M', u'𥪧'),\n    (0x2F95F, 'X'),\n    (0x2F960, 'M', u'䈂'),\n    (0x2F961, 'M', u'𥮫'),\n    (0x2F962, 'M', u'篆'),\n    (0x2F963, 'M', u'築'),\n    (0x2F964, 'M', u'䈧'),\n    (0x2F965, 'M', u'𥲀'),\n    (0x2F966, 'M', u'糒'),\n    (0x2F967, 'M', u'䊠'),\n    (0x2F968, 'M', u'糨'),\n    (0x2F969, 'M', u'糣'),\n    (0x2F96A, 'M', u'紀'),\n    (0x2F96B, 'M', u'𥾆'),\n    (0x2F96C, 'M', u'絣'),\n    (0x2F96D, 'M', u'䌁'),\n    (0x2F96E, 'M', u'緇'),\n    (0x2F96F, 'M', u'縂'),\n    (0x2F970, 'M', u'繅'),\n    (0x2F971, 'M', u'䌴'),\n    (0x2F972, 'M', u'𦈨'),\n    (0x2F973, 'M', u'𦉇'),\n    (0x2F974, 'M', u'䍙'),\n    (0x2F975, 'M', u'𦋙'),\n    (0x2F976, 'M', u'罺'),\n    (0x2F977, 'M', u'𦌾'),\n    (0x2F978, 'M', u'羕'),\n    (0x2F979, 'M', u'翺'),\n    (0x2F97A, 'M', u'者'),\n    (0x2F97B, 'M', u'𦓚'),\n    (0x2F97C, 'M', u'𦔣'),\n    (0x2F97D, 'M', u'聠'),\n    (0x2F97E, 'M', u'𦖨'),\n    (0x2F97F, 'M', u'聰'),\n    (0x2F980, 'M', u'𣍟'),\n    (0x2F981, 'M', u'䏕'),\n    (0x2F982, 'M', u'育'),\n    (0x2F983, 'M', u'脃'),\n    (0x2F984, 'M', u'䐋'),\n    (0x2F985, 'M', u'脾'),\n    (0x2F986, 'M', u'媵'),\n    (0x2F987, 'M', u'𦞧'),\n    (0x2F988, 'M', u'𦞵'),\n    (0x2F989, 'M', u'𣎓'),\n    (0x2F98A, 'M', u'𣎜'),\n    (0x2F98B, 'M', u'舁'),\n    (0x2F98C, 'M', u'舄'),\n    (0x2F98D, 'M', u'辞'),\n    (0x2F98E, 'M', u'䑫'),\n    (0x2F98F, 'M', u'芑'),\n    (0x2F990, 'M', u'芋'),\n    (0x2F991, 'M', u'芝'),\n    (0x2F992, 'M', u'劳'),\n    (0x2F993, 'M', u'花'),\n    (0x2F994, 'M', u'芳'),\n    (0x2F995, 'M', u'芽'),\n    (0x2F996, 'M', u'苦'),\n    (0x2F997, 'M', u'𦬼'),\n    (0x2F998, 'M', u'若'),\n    (0x2F999, 'M', u'茝'),\n    (0x2F99A, 'M', u'荣'),\n    (0x2F99B, 'M', u'莭'),\n    (0x2F99C, 'M', u'茣'),\n    (0x2F99D, 'M', u'莽'),\n    (0x2F99E, 'M', u'菧'),\n    (0x2F99F, 'M', u'著'),\n    (0x2F9A0, 'M', u'荓'),\n    (0x2F9A1, 'M', u'菊'),\n    (0x2F9A2, 'M', u'菌'),\n    (0x2F9A3, 'M', u'菜'),\n    (0x2F9A4, 'M', u'𦰶'),\n    (0x2F9A5, 'M', u'𦵫'),\n    (0x2F9A6, 'M', u'𦳕'),\n    (0x2F9A7, 'M', u'䔫'),\n    (0x2F9A8, 'M', u'蓱'),\n    (0x2F9A9, 'M', u'蓳'),\n    (0x2F9AA, 'M', u'蔖'),\n    (0x2F9AB, 'M', u'𧏊'),\n    (0x2F9AC, 'M', u'蕤'),\n    (0x2F9AD, 'M', u'𦼬'),\n    (0x2F9AE, 'M', u'䕝'),\n    (0x2F9AF, 'M', u'䕡'),\n    (0x2F9B0, 'M', u'𦾱'),\n    (0x2F9B1, 'M', u'𧃒'),\n    (0x2F9B2, 'M', u'䕫'),\n    (0x2F9B3, 'M', u'虐'),\n    (0x2F9B4, 'M', u'虜'),\n    (0x2F9B5, 'M', u'虧'),\n    (0x2F9B6, 'M', u'虩'),\n    (0x2F9B7, 'M', u'蚩'),\n    (0x2F9B8, 'M', u'蚈'),\n    (0x2F9B9, 'M', u'蜎'),\n    (0x2F9BA, 'M', u'蛢'),\n    ]\n\ndef _seg_77():\n    return [\n    (0x2F9BB, 'M', u'蝹'),\n    (0x2F9BC, 'M', u'蜨'),\n    (0x2F9BD, 'M', u'蝫'),\n    (0x2F9BE, 'M', u'螆'),\n    (0x2F9BF, 'X'),\n    (0x2F9C0, 'M', u'蟡'),\n    (0x2F9C1, 'M', u'蠁'),\n    (0x2F9C2, 'M', u'䗹'),\n    (0x2F9C3, 'M', u'衠'),\n    (0x2F9C4, 'M', u'衣'),\n    (0x2F9C5, 'M', u'𧙧'),\n    (0x2F9C6, 'M', u'裗'),\n    (0x2F9C7, 'M', u'裞'),\n    (0x2F9C8, 'M', u'䘵'),\n    (0x2F9C9, 'M', u'裺'),\n    (0x2F9CA, 'M', u'㒻'),\n    (0x2F9CB, 'M', u'𧢮'),\n    (0x2F9CC, 'M', u'𧥦'),\n    (0x2F9CD, 'M', u'䚾'),\n    (0x2F9CE, 'M', u'䛇'),\n    (0x2F9CF, 'M', u'誠'),\n    (0x2F9D0, 'M', u'諭'),\n    (0x2F9D1, 'M', u'變'),\n    (0x2F9D2, 'M', u'豕'),\n    (0x2F9D3, 'M', u'𧲨'),\n    (0x2F9D4, 'M', u'貫'),\n    (0x2F9D5, 'M', u'賁'),\n    (0x2F9D6, 'M', u'贛'),\n    (0x2F9D7, 'M', u'起'),\n    (0x2F9D8, 'M', u'𧼯'),\n    (0x2F9D9, 'M', u'𠠄'),\n    (0x2F9DA, 'M', u'跋'),\n    (0x2F9DB, 'M', u'趼'),\n    (0x2F9DC, 'M', u'跰'),\n    (0x2F9DD, 'M', u'𠣞'),\n    (0x2F9DE, 'M', u'軔'),\n    (0x2F9DF, 'M', u'輸'),\n    (0x2F9E0, 'M', u'𨗒'),\n    (0x2F9E1, 'M', u'𨗭'),\n    (0x2F9E2, 'M', u'邔'),\n    (0x2F9E3, 'M', u'郱'),\n    (0x2F9E4, 'M', u'鄑'),\n    (0x2F9E5, 'M', u'𨜮'),\n    (0x2F9E6, 'M', u'鄛'),\n    (0x2F9E7, 'M', u'鈸'),\n    (0x2F9E8, 'M', u'鋗'),\n    (0x2F9E9, 'M', u'鋘'),\n    (0x2F9EA, 'M', u'鉼'),\n    (0x2F9EB, 'M', u'鏹'),\n    (0x2F9EC, 'M', u'鐕'),\n    (0x2F9ED, 'M', u'𨯺'),\n    (0x2F9EE, 'M', u'開'),\n    (0x2F9EF, 'M', u'䦕'),\n    (0x2F9F0, 'M', u'閷'),\n    (0x2F9F1, 'M', u'𨵷'),\n    (0x2F9F2, 'M', u'䧦'),\n    (0x2F9F3, 'M', u'雃'),\n    (0x2F9F4, 'M', u'嶲'),\n    (0x2F9F5, 'M', u'霣'),\n    (0x2F9F6, 'M', u'𩅅'),\n    (0x2F9F7, 'M', u'𩈚'),\n    (0x2F9F8, 'M', u'䩮'),\n    (0x2F9F9, 'M', u'䩶'),\n    (0x2F9FA, 'M', u'韠'),\n    (0x2F9FB, 'M', u'𩐊'),\n    (0x2F9FC, 'M', u'䪲'),\n    (0x2F9FD, 'M', u'𩒖'),\n    (0x2F9FE, 'M', u'頋'),\n    (0x2FA00, 'M', u'頩'),\n    (0x2FA01, 'M', u'𩖶'),\n    (0x2FA02, 'M', u'飢'),\n    (0x2FA03, 'M', u'䬳'),\n    (0x2FA04, 'M', u'餩'),\n    (0x2FA05, 'M', u'馧'),\n    (0x2FA06, 'M', u'駂'),\n    (0x2FA07, 'M', u'駾'),\n    (0x2FA08, 'M', u'䯎'),\n    (0x2FA09, 'M', u'𩬰'),\n    (0x2FA0A, 'M', u'鬒'),\n    (0x2FA0B, 'M', u'鱀'),\n    (0x2FA0C, 'M', u'鳽'),\n    (0x2FA0D, 'M', u'䳎'),\n    (0x2FA0E, 'M', u'䳭'),\n    (0x2FA0F, 'M', u'鵧'),\n    (0x2FA10, 'M', u'𪃎'),\n    (0x2FA11, 'M', u'䳸'),\n    (0x2FA12, 'M', u'𪄅'),\n    (0x2FA13, 'M', u'𪈎'),\n    (0x2FA14, 'M', u'𪊑'),\n    (0x2FA15, 'M', u'麻'),\n    (0x2FA16, 'M', u'䵖'),\n    (0x2FA17, 'M', u'黹'),\n    (0x2FA18, 'M', u'黾'),\n    (0x2FA19, 'M', u'鼅'),\n    (0x2FA1A, 'M', u'鼏'),\n    (0x2FA1B, 'M', u'鼖'),\n    (0x2FA1C, 'M', u'鼻'),\n    (0x2FA1D, 'M', u'𪘀'),\n    (0x2FA1E, 'X'),\n    (0xE0100, 'I'),\n    ]\n\ndef _seg_78():\n    return [\n    (0xE01F0, 'X'),\n    ]\n\nuts46data = tuple(\n    _seg_0()\n    + _seg_1()\n    + _seg_2()\n    + _seg_3()\n    + _seg_4()\n    + _seg_5()\n    + _seg_6()\n    + _seg_7()\n    + _seg_8()\n    + _seg_9()\n    + _seg_10()\n    + _seg_11()\n    + _seg_12()\n    + _seg_13()\n    + _seg_14()\n    + _seg_15()\n    + _seg_16()\n    + _seg_17()\n    + _seg_18()\n    + _seg_19()\n    + _seg_20()\n    + _seg_21()\n    + _seg_22()\n    + _seg_23()\n    + _seg_24()\n    + _seg_25()\n    + _seg_26()\n    + _seg_27()\n    + _seg_28()\n    + _seg_29()\n    + _seg_30()\n    + _seg_31()\n    + _seg_32()\n    + _seg_33()\n    + _seg_34()\n    + _seg_35()\n    + _seg_36()\n    + _seg_37()\n    + _seg_38()\n    + _seg_39()\n    + _seg_40()\n    + _seg_41()\n    + _seg_42()\n    + _seg_43()\n    + _seg_44()\n    + _seg_45()\n    + _seg_46()\n    + _seg_47()\n    + _seg_48()\n    + _seg_49()\n    + _seg_50()\n    + _seg_51()\n    + _seg_52()\n    + _seg_53()\n    + _seg_54()\n    + _seg_55()\n    + _seg_56()\n    + _seg_57()\n    + _seg_58()\n    + _seg_59()\n    + _seg_60()\n    + _seg_61()\n    + _seg_62()\n    + _seg_63()\n    + _seg_64()\n    + _seg_65()\n    + _seg_66()\n    + _seg_67()\n    + _seg_68()\n    + _seg_69()\n    + _seg_70()\n    + _seg_71()\n    + _seg_72()\n    + _seg_73()\n    + _seg_74()\n    + _seg_75()\n    + _seg_76()\n    + _seg_77()\n    + _seg_78()\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/ipaddress.py",
    "content": "# Copyright 2007 Google Inc.\n#  Licensed to PSF under a Contributor Agreement.\n\n\"\"\"A fast, lightweight IPv4/IPv6 manipulation library in Python.\n\nThis library is used to create/poke/manipulate IPv4 and IPv6 addresses\nand networks.\n\n\"\"\"\n\nfrom __future__ import unicode_literals\n\n\nimport itertools\nimport struct\n\n__version__ = '1.0.22'\n\n# Compatibility functions\n_compat_int_types = (int,)\ntry:\n    _compat_int_types = (int, long)\nexcept NameError:\n    pass\ntry:\n    _compat_str = unicode\nexcept NameError:\n    _compat_str = str\n    assert bytes != str\nif b'\\0'[0] == 0:  # Python 3 semantics\n    def _compat_bytes_to_byte_vals(byt):\n        return byt\nelse:\n    def _compat_bytes_to_byte_vals(byt):\n        return [struct.unpack(b'!B', b)[0] for b in byt]\ntry:\n    _compat_int_from_byte_vals = int.from_bytes\nexcept AttributeError:\n    def _compat_int_from_byte_vals(bytvals, endianess):\n        assert endianess == 'big'\n        res = 0\n        for bv in bytvals:\n            assert isinstance(bv, _compat_int_types)\n            res = (res << 8) + bv\n        return res\n\n\ndef _compat_to_bytes(intval, length, endianess):\n    assert isinstance(intval, _compat_int_types)\n    assert endianess == 'big'\n    if length == 4:\n        if intval < 0 or intval >= 2 ** 32:\n            raise struct.error(\"integer out of range for 'I' format code\")\n        return struct.pack(b'!I', intval)\n    elif length == 16:\n        if intval < 0 or intval >= 2 ** 128:\n            raise struct.error(\"integer out of range for 'QQ' format code\")\n        return struct.pack(b'!QQ', intval >> 64, intval & 0xffffffffffffffff)\n    else:\n        raise NotImplementedError()\n\n\nif hasattr(int, 'bit_length'):\n    # Not int.bit_length , since that won't work in 2.7 where long exists\n    def _compat_bit_length(i):\n        return i.bit_length()\nelse:\n    def _compat_bit_length(i):\n        for res in itertools.count():\n            if i >> res == 0:\n                return res\n\n\ndef _compat_range(start, end, step=1):\n    assert step > 0\n    i = start\n    while i < end:\n        yield i\n        i += step\n\n\nclass _TotalOrderingMixin(object):\n    __slots__ = ()\n\n    # Helper that derives the other comparison operations from\n    # __lt__ and __eq__\n    # We avoid functools.total_ordering because it doesn't handle\n    # NotImplemented correctly yet (http://bugs.python.org/issue10042)\n    def __eq__(self, other):\n        raise NotImplementedError\n\n    def __ne__(self, other):\n        equal = self.__eq__(other)\n        if equal is NotImplemented:\n            return NotImplemented\n        return not equal\n\n    def __lt__(self, other):\n        raise NotImplementedError\n\n    def __le__(self, other):\n        less = self.__lt__(other)\n        if less is NotImplemented or not less:\n            return self.__eq__(other)\n        return less\n\n    def __gt__(self, other):\n        less = self.__lt__(other)\n        if less is NotImplemented:\n            return NotImplemented\n        equal = self.__eq__(other)\n        if equal is NotImplemented:\n            return NotImplemented\n        return not (less or equal)\n\n    def __ge__(self, other):\n        less = self.__lt__(other)\n        if less is NotImplemented:\n            return NotImplemented\n        return not less\n\n\nIPV4LENGTH = 32\nIPV6LENGTH = 128\n\n\nclass AddressValueError(ValueError):\n    \"\"\"A Value Error related to the address.\"\"\"\n\n\nclass NetmaskValueError(ValueError):\n    \"\"\"A Value Error related to the netmask.\"\"\"\n\n\ndef ip_address(address):\n    \"\"\"Take an IP string/int and return an object of the correct type.\n\n    Args:\n        address: A string or integer, the IP address.  Either IPv4 or\n          IPv6 addresses may be supplied; integers less than 2**32 will\n          be considered to be IPv4 by default.\n\n    Returns:\n        An IPv4Address or IPv6Address object.\n\n    Raises:\n        ValueError: if the *address* passed isn't either a v4 or a v6\n          address\n\n    \"\"\"\n    try:\n        return IPv4Address(address)\n    except (AddressValueError, NetmaskValueError):\n        pass\n\n    try:\n        return IPv6Address(address)\n    except (AddressValueError, NetmaskValueError):\n        pass\n\n    if isinstance(address, bytes):\n        raise AddressValueError(\n            '%r does not appear to be an IPv4 or IPv6 address. '\n            'Did you pass in a bytes (str in Python 2) instead of'\n            ' a unicode object?' % address)\n\n    raise ValueError('%r does not appear to be an IPv4 or IPv6 address' %\n                     address)\n\n\ndef ip_network(address, strict=True):\n    \"\"\"Take an IP string/int and return an object of the correct type.\n\n    Args:\n        address: A string or integer, the IP network.  Either IPv4 or\n          IPv6 networks may be supplied; integers less than 2**32 will\n          be considered to be IPv4 by default.\n\n    Returns:\n        An IPv4Network or IPv6Network object.\n\n    Raises:\n        ValueError: if the string passed isn't either a v4 or a v6\n          address. Or if the network has host bits set.\n\n    \"\"\"\n    try:\n        return IPv4Network(address, strict)\n    except (AddressValueError, NetmaskValueError):\n        pass\n\n    try:\n        return IPv6Network(address, strict)\n    except (AddressValueError, NetmaskValueError):\n        pass\n\n    if isinstance(address, bytes):\n        raise AddressValueError(\n            '%r does not appear to be an IPv4 or IPv6 network. '\n            'Did you pass in a bytes (str in Python 2) instead of'\n            ' a unicode object?' % address)\n\n    raise ValueError('%r does not appear to be an IPv4 or IPv6 network' %\n                     address)\n\n\ndef ip_interface(address):\n    \"\"\"Take an IP string/int and return an object of the correct type.\n\n    Args:\n        address: A string or integer, the IP address.  Either IPv4 or\n          IPv6 addresses may be supplied; integers less than 2**32 will\n          be considered to be IPv4 by default.\n\n    Returns:\n        An IPv4Interface or IPv6Interface object.\n\n    Raises:\n        ValueError: if the string passed isn't either a v4 or a v6\n          address.\n\n    Notes:\n        The IPv?Interface classes describe an Address on a particular\n        Network, so they're basically a combination of both the Address\n        and Network classes.\n\n    \"\"\"\n    try:\n        return IPv4Interface(address)\n    except (AddressValueError, NetmaskValueError):\n        pass\n\n    try:\n        return IPv6Interface(address)\n    except (AddressValueError, NetmaskValueError):\n        pass\n\n    raise ValueError('%r does not appear to be an IPv4 or IPv6 interface' %\n                     address)\n\n\ndef v4_int_to_packed(address):\n    \"\"\"Represent an address as 4 packed bytes in network (big-endian) order.\n\n    Args:\n        address: An integer representation of an IPv4 IP address.\n\n    Returns:\n        The integer address packed as 4 bytes in network (big-endian) order.\n\n    Raises:\n        ValueError: If the integer is negative or too large to be an\n          IPv4 IP address.\n\n    \"\"\"\n    try:\n        return _compat_to_bytes(address, 4, 'big')\n    except (struct.error, OverflowError):\n        raise ValueError(\"Address negative or too large for IPv4\")\n\n\ndef v6_int_to_packed(address):\n    \"\"\"Represent an address as 16 packed bytes in network (big-endian) order.\n\n    Args:\n        address: An integer representation of an IPv6 IP address.\n\n    Returns:\n        The integer address packed as 16 bytes in network (big-endian) order.\n\n    \"\"\"\n    try:\n        return _compat_to_bytes(address, 16, 'big')\n    except (struct.error, OverflowError):\n        raise ValueError(\"Address negative or too large for IPv6\")\n\n\ndef _split_optional_netmask(address):\n    \"\"\"Helper to split the netmask and raise AddressValueError if needed\"\"\"\n    addr = _compat_str(address).split('/')\n    if len(addr) > 2:\n        raise AddressValueError(\"Only one '/' permitted in %r\" % address)\n    return addr\n\n\ndef _find_address_range(addresses):\n    \"\"\"Find a sequence of sorted deduplicated IPv#Address.\n\n    Args:\n        addresses: a list of IPv#Address objects.\n\n    Yields:\n        A tuple containing the first and last IP addresses in the sequence.\n\n    \"\"\"\n    it = iter(addresses)\n    first = last = next(it)\n    for ip in it:\n        if ip._ip != last._ip + 1:\n            yield first, last\n            first = ip\n        last = ip\n    yield first, last\n\n\ndef _count_righthand_zero_bits(number, bits):\n    \"\"\"Count the number of zero bits on the right hand side.\n\n    Args:\n        number: an integer.\n        bits: maximum number of bits to count.\n\n    Returns:\n        The number of zero bits on the right hand side of the number.\n\n    \"\"\"\n    if number == 0:\n        return bits\n    return min(bits, _compat_bit_length(~number & (number - 1)))\n\n\ndef summarize_address_range(first, last):\n    \"\"\"Summarize a network range given the first and last IP addresses.\n\n    Example:\n        >>> list(summarize_address_range(IPv4Address('192.0.2.0'),\n        ...                              IPv4Address('192.0.2.130')))\n        ...                                #doctest: +NORMALIZE_WHITESPACE\n        [IPv4Network('192.0.2.0/25'), IPv4Network('192.0.2.128/31'),\n         IPv4Network('192.0.2.130/32')]\n\n    Args:\n        first: the first IPv4Address or IPv6Address in the range.\n        last: the last IPv4Address or IPv6Address in the range.\n\n    Returns:\n        An iterator of the summarized IPv(4|6) network objects.\n\n    Raise:\n        TypeError:\n            If the first and last objects are not IP addresses.\n            If the first and last objects are not the same version.\n        ValueError:\n            If the last object is not greater than the first.\n            If the version of the first address is not 4 or 6.\n\n    \"\"\"\n    if (not (isinstance(first, _BaseAddress) and\n             isinstance(last, _BaseAddress))):\n        raise TypeError('first and last must be IP addresses, not networks')\n    if first.version != last.version:\n        raise TypeError(\"%s and %s are not of the same version\" % (\n                        first, last))\n    if first > last:\n        raise ValueError('last IP address must be greater than first')\n\n    if first.version == 4:\n        ip = IPv4Network\n    elif first.version == 6:\n        ip = IPv6Network\n    else:\n        raise ValueError('unknown IP version')\n\n    ip_bits = first._max_prefixlen\n    first_int = first._ip\n    last_int = last._ip\n    while first_int <= last_int:\n        nbits = min(_count_righthand_zero_bits(first_int, ip_bits),\n                    _compat_bit_length(last_int - first_int + 1) - 1)\n        net = ip((first_int, ip_bits - nbits))\n        yield net\n        first_int += 1 << nbits\n        if first_int - 1 == ip._ALL_ONES:\n            break\n\n\ndef _collapse_addresses_internal(addresses):\n    \"\"\"Loops through the addresses, collapsing concurrent netblocks.\n\n    Example:\n\n        ip1 = IPv4Network('192.0.2.0/26')\n        ip2 = IPv4Network('192.0.2.64/26')\n        ip3 = IPv4Network('192.0.2.128/26')\n        ip4 = IPv4Network('192.0.2.192/26')\n\n        _collapse_addresses_internal([ip1, ip2, ip3, ip4]) ->\n          [IPv4Network('192.0.2.0/24')]\n\n        This shouldn't be called directly; it is called via\n          collapse_addresses([]).\n\n    Args:\n        addresses: A list of IPv4Network's or IPv6Network's\n\n    Returns:\n        A list of IPv4Network's or IPv6Network's depending on what we were\n        passed.\n\n    \"\"\"\n    # First merge\n    to_merge = list(addresses)\n    subnets = {}\n    while to_merge:\n        net = to_merge.pop()\n        supernet = net.supernet()\n        existing = subnets.get(supernet)\n        if existing is None:\n            subnets[supernet] = net\n        elif existing != net:\n            # Merge consecutive subnets\n            del subnets[supernet]\n            to_merge.append(supernet)\n    # Then iterate over resulting networks, skipping subsumed subnets\n    last = None\n    for net in sorted(subnets.values()):\n        if last is not None:\n            # Since they are sorted,\n            # last.network_address <= net.network_address is a given.\n            if last.broadcast_address >= net.broadcast_address:\n                continue\n        yield net\n        last = net\n\n\ndef collapse_addresses(addresses):\n    \"\"\"Collapse a list of IP objects.\n\n    Example:\n        collapse_addresses([IPv4Network('192.0.2.0/25'),\n                            IPv4Network('192.0.2.128/25')]) ->\n                           [IPv4Network('192.0.2.0/24')]\n\n    Args:\n        addresses: An iterator of IPv4Network or IPv6Network objects.\n\n    Returns:\n        An iterator of the collapsed IPv(4|6)Network objects.\n\n    Raises:\n        TypeError: If passed a list of mixed version objects.\n\n    \"\"\"\n    addrs = []\n    ips = []\n    nets = []\n\n    # split IP addresses and networks\n    for ip in addresses:\n        if isinstance(ip, _BaseAddress):\n            if ips and ips[-1]._version != ip._version:\n                raise TypeError(\"%s and %s are not of the same version\" % (\n                                ip, ips[-1]))\n            ips.append(ip)\n        elif ip._prefixlen == ip._max_prefixlen:\n            if ips and ips[-1]._version != ip._version:\n                raise TypeError(\"%s and %s are not of the same version\" % (\n                                ip, ips[-1]))\n            try:\n                ips.append(ip.ip)\n            except AttributeError:\n                ips.append(ip.network_address)\n        else:\n            if nets and nets[-1]._version != ip._version:\n                raise TypeError(\"%s and %s are not of the same version\" % (\n                                ip, nets[-1]))\n            nets.append(ip)\n\n    # sort and dedup\n    ips = sorted(set(ips))\n\n    # find consecutive address ranges in the sorted sequence and summarize them\n    if ips:\n        for first, last in _find_address_range(ips):\n            addrs.extend(summarize_address_range(first, last))\n\n    return _collapse_addresses_internal(addrs + nets)\n\n\ndef get_mixed_type_key(obj):\n    \"\"\"Return a key suitable for sorting between networks and addresses.\n\n    Address and Network objects are not sortable by default; they're\n    fundamentally different so the expression\n\n        IPv4Address('192.0.2.0') <= IPv4Network('192.0.2.0/24')\n\n    doesn't make any sense.  There are some times however, where you may wish\n    to have ipaddress sort these for you anyway. If you need to do this, you\n    can use this function as the key= argument to sorted().\n\n    Args:\n      obj: either a Network or Address object.\n    Returns:\n      appropriate key.\n\n    \"\"\"\n    if isinstance(obj, _BaseNetwork):\n        return obj._get_networks_key()\n    elif isinstance(obj, _BaseAddress):\n        return obj._get_address_key()\n    return NotImplemented\n\n\nclass _IPAddressBase(_TotalOrderingMixin):\n\n    \"\"\"The mother class.\"\"\"\n\n    __slots__ = ()\n\n    @property\n    def exploded(self):\n        \"\"\"Return the longhand version of the IP address as a string.\"\"\"\n        return self._explode_shorthand_ip_string()\n\n    @property\n    def compressed(self):\n        \"\"\"Return the shorthand version of the IP address as a string.\"\"\"\n        return _compat_str(self)\n\n    @property\n    def reverse_pointer(self):\n        \"\"\"The name of the reverse DNS pointer for the IP address, e.g.:\n            >>> ipaddress.ip_address(\"127.0.0.1\").reverse_pointer\n            '1.0.0.127.in-addr.arpa'\n            >>> ipaddress.ip_address(\"2001:db8::1\").reverse_pointer\n            '1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.8.b.d.0.1.0.0.2.ip6.arpa'\n\n        \"\"\"\n        return self._reverse_pointer()\n\n    @property\n    def version(self):\n        msg = '%200s has no version specified' % (type(self),)\n        raise NotImplementedError(msg)\n\n    def _check_int_address(self, address):\n        if address < 0:\n            msg = \"%d (< 0) is not permitted as an IPv%d address\"\n            raise AddressValueError(msg % (address, self._version))\n        if address > self._ALL_ONES:\n            msg = \"%d (>= 2**%d) is not permitted as an IPv%d address\"\n            raise AddressValueError(msg % (address, self._max_prefixlen,\n                                           self._version))\n\n    def _check_packed_address(self, address, expected_len):\n        address_len = len(address)\n        if address_len != expected_len:\n            msg = (\n                '%r (len %d != %d) is not permitted as an IPv%d address. '\n                'Did you pass in a bytes (str in Python 2) instead of'\n                ' a unicode object?')\n            raise AddressValueError(msg % (address, address_len,\n                                           expected_len, self._version))\n\n    @classmethod\n    def _ip_int_from_prefix(cls, prefixlen):\n        \"\"\"Turn the prefix length into a bitwise netmask\n\n        Args:\n            prefixlen: An integer, the prefix length.\n\n        Returns:\n            An integer.\n\n        \"\"\"\n        return cls._ALL_ONES ^ (cls._ALL_ONES >> prefixlen)\n\n    @classmethod\n    def _prefix_from_ip_int(cls, ip_int):\n        \"\"\"Return prefix length from the bitwise netmask.\n\n        Args:\n            ip_int: An integer, the netmask in expanded bitwise format\n\n        Returns:\n            An integer, the prefix length.\n\n        Raises:\n            ValueError: If the input intermingles zeroes & ones\n        \"\"\"\n        trailing_zeroes = _count_righthand_zero_bits(ip_int,\n                                                     cls._max_prefixlen)\n        prefixlen = cls._max_prefixlen - trailing_zeroes\n        leading_ones = ip_int >> trailing_zeroes\n        all_ones = (1 << prefixlen) - 1\n        if leading_ones != all_ones:\n            byteslen = cls._max_prefixlen // 8\n            details = _compat_to_bytes(ip_int, byteslen, 'big')\n            msg = 'Netmask pattern %r mixes zeroes & ones'\n            raise ValueError(msg % details)\n        return prefixlen\n\n    @classmethod\n    def _report_invalid_netmask(cls, netmask_str):\n        msg = '%r is not a valid netmask' % netmask_str\n        raise NetmaskValueError(msg)\n\n    @classmethod\n    def _prefix_from_prefix_string(cls, prefixlen_str):\n        \"\"\"Return prefix length from a numeric string\n\n        Args:\n            prefixlen_str: The string to be converted\n\n        Returns:\n            An integer, the prefix length.\n\n        Raises:\n            NetmaskValueError: If the input is not a valid netmask\n        \"\"\"\n        # int allows a leading +/- as well as surrounding whitespace,\n        # so we ensure that isn't the case\n        if not _BaseV4._DECIMAL_DIGITS.issuperset(prefixlen_str):\n            cls._report_invalid_netmask(prefixlen_str)\n        try:\n            prefixlen = int(prefixlen_str)\n        except ValueError:\n            cls._report_invalid_netmask(prefixlen_str)\n        if not (0 <= prefixlen <= cls._max_prefixlen):\n            cls._report_invalid_netmask(prefixlen_str)\n        return prefixlen\n\n    @classmethod\n    def _prefix_from_ip_string(cls, ip_str):\n        \"\"\"Turn a netmask/hostmask string into a prefix length\n\n        Args:\n            ip_str: The netmask/hostmask to be converted\n\n        Returns:\n            An integer, the prefix length.\n\n        Raises:\n            NetmaskValueError: If the input is not a valid netmask/hostmask\n        \"\"\"\n        # Parse the netmask/hostmask like an IP address.\n        try:\n            ip_int = cls._ip_int_from_string(ip_str)\n        except AddressValueError:\n            cls._report_invalid_netmask(ip_str)\n\n        # Try matching a netmask (this would be /1*0*/ as a bitwise regexp).\n        # Note that the two ambiguous cases (all-ones and all-zeroes) are\n        # treated as netmasks.\n        try:\n            return cls._prefix_from_ip_int(ip_int)\n        except ValueError:\n            pass\n\n        # Invert the bits, and try matching a /0+1+/ hostmask instead.\n        ip_int ^= cls._ALL_ONES\n        try:\n            return cls._prefix_from_ip_int(ip_int)\n        except ValueError:\n            cls._report_invalid_netmask(ip_str)\n\n    def __reduce__(self):\n        return self.__class__, (_compat_str(self),)\n\n\nclass _BaseAddress(_IPAddressBase):\n\n    \"\"\"A generic IP object.\n\n    This IP class contains the version independent methods which are\n    used by single IP addresses.\n    \"\"\"\n\n    __slots__ = ()\n\n    def __int__(self):\n        return self._ip\n\n    def __eq__(self, other):\n        try:\n            return (self._ip == other._ip and\n                    self._version == other._version)\n        except AttributeError:\n            return NotImplemented\n\n    def __lt__(self, other):\n        if not isinstance(other, _IPAddressBase):\n            return NotImplemented\n        if not isinstance(other, _BaseAddress):\n            raise TypeError('%s and %s are not of the same type' % (\n                self, other))\n        if self._version != other._version:\n            raise TypeError('%s and %s are not of the same version' % (\n                self, other))\n        if self._ip != other._ip:\n            return self._ip < other._ip\n        return False\n\n    # Shorthand for Integer addition and subtraction. This is not\n    # meant to ever support addition/subtraction of addresses.\n    def __add__(self, other):\n        if not isinstance(other, _compat_int_types):\n            return NotImplemented\n        return self.__class__(int(self) + other)\n\n    def __sub__(self, other):\n        if not isinstance(other, _compat_int_types):\n            return NotImplemented\n        return self.__class__(int(self) - other)\n\n    def __repr__(self):\n        return '%s(%r)' % (self.__class__.__name__, _compat_str(self))\n\n    def __str__(self):\n        return _compat_str(self._string_from_ip_int(self._ip))\n\n    def __hash__(self):\n        return hash(hex(int(self._ip)))\n\n    def _get_address_key(self):\n        return (self._version, self)\n\n    def __reduce__(self):\n        return self.__class__, (self._ip,)\n\n\nclass _BaseNetwork(_IPAddressBase):\n\n    \"\"\"A generic IP network object.\n\n    This IP class contains the version independent methods which are\n    used by networks.\n\n    \"\"\"\n    def __init__(self, address):\n        self._cache = {}\n\n    def __repr__(self):\n        return '%s(%r)' % (self.__class__.__name__, _compat_str(self))\n\n    def __str__(self):\n        return '%s/%d' % (self.network_address, self.prefixlen)\n\n    def hosts(self):\n        \"\"\"Generate Iterator over usable hosts in a network.\n\n        This is like __iter__ except it doesn't return the network\n        or broadcast addresses.\n\n        \"\"\"\n        network = int(self.network_address)\n        broadcast = int(self.broadcast_address)\n        for x in _compat_range(network + 1, broadcast):\n            yield self._address_class(x)\n\n    def __iter__(self):\n        network = int(self.network_address)\n        broadcast = int(self.broadcast_address)\n        for x in _compat_range(network, broadcast + 1):\n            yield self._address_class(x)\n\n    def __getitem__(self, n):\n        network = int(self.network_address)\n        broadcast = int(self.broadcast_address)\n        if n >= 0:\n            if network + n > broadcast:\n                raise IndexError('address out of range')\n            return self._address_class(network + n)\n        else:\n            n += 1\n            if broadcast + n < network:\n                raise IndexError('address out of range')\n            return self._address_class(broadcast + n)\n\n    def __lt__(self, other):\n        if not isinstance(other, _IPAddressBase):\n            return NotImplemented\n        if not isinstance(other, _BaseNetwork):\n            raise TypeError('%s and %s are not of the same type' % (\n                            self, other))\n        if self._version != other._version:\n            raise TypeError('%s and %s are not of the same version' % (\n                            self, other))\n        if self.network_address != other.network_address:\n            return self.network_address < other.network_address\n        if self.netmask != other.netmask:\n            return self.netmask < other.netmask\n        return False\n\n    def __eq__(self, other):\n        try:\n            return (self._version == other._version and\n                    self.network_address == other.network_address and\n                    int(self.netmask) == int(other.netmask))\n        except AttributeError:\n            return NotImplemented\n\n    def __hash__(self):\n        return hash(int(self.network_address) ^ int(self.netmask))\n\n    def __contains__(self, other):\n        # always false if one is v4 and the other is v6.\n        if self._version != other._version:\n            return False\n        # dealing with another network.\n        if isinstance(other, _BaseNetwork):\n            return False\n        # dealing with another address\n        else:\n            # address\n            return (int(self.network_address) <= int(other._ip) <=\n                    int(self.broadcast_address))\n\n    def overlaps(self, other):\n        \"\"\"Tell if self is partly contained in other.\"\"\"\n        return self.network_address in other or (\n            self.broadcast_address in other or (\n                other.network_address in self or (\n                    other.broadcast_address in self)))\n\n    @property\n    def broadcast_address(self):\n        x = self._cache.get('broadcast_address')\n        if x is None:\n            x = self._address_class(int(self.network_address) |\n                                    int(self.hostmask))\n            self._cache['broadcast_address'] = x\n        return x\n\n    @property\n    def hostmask(self):\n        x = self._cache.get('hostmask')\n        if x is None:\n            x = self._address_class(int(self.netmask) ^ self._ALL_ONES)\n            self._cache['hostmask'] = x\n        return x\n\n    @property\n    def with_prefixlen(self):\n        return '%s/%d' % (self.network_address, self._prefixlen)\n\n    @property\n    def with_netmask(self):\n        return '%s/%s' % (self.network_address, self.netmask)\n\n    @property\n    def with_hostmask(self):\n        return '%s/%s' % (self.network_address, self.hostmask)\n\n    @property\n    def num_addresses(self):\n        \"\"\"Number of hosts in the current subnet.\"\"\"\n        return int(self.broadcast_address) - int(self.network_address) + 1\n\n    @property\n    def _address_class(self):\n        # Returning bare address objects (rather than interfaces) allows for\n        # more consistent behaviour across the network address, broadcast\n        # address and individual host addresses.\n        msg = '%200s has no associated address class' % (type(self),)\n        raise NotImplementedError(msg)\n\n    @property\n    def prefixlen(self):\n        return self._prefixlen\n\n    def address_exclude(self, other):\n        \"\"\"Remove an address from a larger block.\n\n        For example:\n\n            addr1 = ip_network('192.0.2.0/28')\n            addr2 = ip_network('192.0.2.1/32')\n            list(addr1.address_exclude(addr2)) =\n                [IPv4Network('192.0.2.0/32'), IPv4Network('192.0.2.2/31'),\n                 IPv4Network('192.0.2.4/30'), IPv4Network('192.0.2.8/29')]\n\n        or IPv6:\n\n            addr1 = ip_network('2001:db8::1/32')\n            addr2 = ip_network('2001:db8::1/128')\n            list(addr1.address_exclude(addr2)) =\n                [ip_network('2001:db8::1/128'),\n                 ip_network('2001:db8::2/127'),\n                 ip_network('2001:db8::4/126'),\n                 ip_network('2001:db8::8/125'),\n                 ...\n                 ip_network('2001:db8:8000::/33')]\n\n        Args:\n            other: An IPv4Network or IPv6Network object of the same type.\n\n        Returns:\n            An iterator of the IPv(4|6)Network objects which is self\n            minus other.\n\n        Raises:\n            TypeError: If self and other are of differing address\n              versions, or if other is not a network object.\n            ValueError: If other is not completely contained by self.\n\n        \"\"\"\n        if not self._version == other._version:\n            raise TypeError(\"%s and %s are not of the same version\" % (\n                            self, other))\n\n        if not isinstance(other, _BaseNetwork):\n            raise TypeError(\"%s is not a network object\" % other)\n\n        if not other.subnet_of(self):\n            raise ValueError('%s not contained in %s' % (other, self))\n        if other == self:\n            return\n\n        # Make sure we're comparing the network of other.\n        other = other.__class__('%s/%s' % (other.network_address,\n                                           other.prefixlen))\n\n        s1, s2 = self.subnets()\n        while s1 != other and s2 != other:\n            if other.subnet_of(s1):\n                yield s2\n                s1, s2 = s1.subnets()\n            elif other.subnet_of(s2):\n                yield s1\n                s1, s2 = s2.subnets()\n            else:\n                # If we got here, there's a bug somewhere.\n                raise AssertionError('Error performing exclusion: '\n                                     's1: %s s2: %s other: %s' %\n                                     (s1, s2, other))\n        if s1 == other:\n            yield s2\n        elif s2 == other:\n            yield s1\n        else:\n            # If we got here, there's a bug somewhere.\n            raise AssertionError('Error performing exclusion: '\n                                 's1: %s s2: %s other: %s' %\n                                 (s1, s2, other))\n\n    def compare_networks(self, other):\n        \"\"\"Compare two IP objects.\n\n        This is only concerned about the comparison of the integer\n        representation of the network addresses.  This means that the\n        host bits aren't considered at all in this method.  If you want\n        to compare host bits, you can easily enough do a\n        'HostA._ip < HostB._ip'\n\n        Args:\n            other: An IP object.\n\n        Returns:\n            If the IP versions of self and other are the same, returns:\n\n            -1 if self < other:\n              eg: IPv4Network('192.0.2.0/25') < IPv4Network('192.0.2.128/25')\n              IPv6Network('2001:db8::1000/124') <\n                  IPv6Network('2001:db8::2000/124')\n            0 if self == other\n              eg: IPv4Network('192.0.2.0/24') == IPv4Network('192.0.2.0/24')\n              IPv6Network('2001:db8::1000/124') ==\n                  IPv6Network('2001:db8::1000/124')\n            1 if self > other\n              eg: IPv4Network('192.0.2.128/25') > IPv4Network('192.0.2.0/25')\n                  IPv6Network('2001:db8::2000/124') >\n                      IPv6Network('2001:db8::1000/124')\n\n          Raises:\n              TypeError if the IP versions are different.\n\n        \"\"\"\n        # does this need to raise a ValueError?\n        if self._version != other._version:\n            raise TypeError('%s and %s are not of the same type' % (\n                            self, other))\n        # self._version == other._version below here:\n        if self.network_address < other.network_address:\n            return -1\n        if self.network_address > other.network_address:\n            return 1\n        # self.network_address == other.network_address below here:\n        if self.netmask < other.netmask:\n            return -1\n        if self.netmask > other.netmask:\n            return 1\n        return 0\n\n    def _get_networks_key(self):\n        \"\"\"Network-only key function.\n\n        Returns an object that identifies this address' network and\n        netmask. This function is a suitable \"key\" argument for sorted()\n        and list.sort().\n\n        \"\"\"\n        return (self._version, self.network_address, self.netmask)\n\n    def subnets(self, prefixlen_diff=1, new_prefix=None):\n        \"\"\"The subnets which join to make the current subnet.\n\n        In the case that self contains only one IP\n        (self._prefixlen == 32 for IPv4 or self._prefixlen == 128\n        for IPv6), yield an iterator with just ourself.\n\n        Args:\n            prefixlen_diff: An integer, the amount the prefix length\n              should be increased by. This should not be set if\n              new_prefix is also set.\n            new_prefix: The desired new prefix length. This must be a\n              larger number (smaller prefix) than the existing prefix.\n              This should not be set if prefixlen_diff is also set.\n\n        Returns:\n            An iterator of IPv(4|6) objects.\n\n        Raises:\n            ValueError: The prefixlen_diff is too small or too large.\n                OR\n            prefixlen_diff and new_prefix are both set or new_prefix\n              is a smaller number than the current prefix (smaller\n              number means a larger network)\n\n        \"\"\"\n        if self._prefixlen == self._max_prefixlen:\n            yield self\n            return\n\n        if new_prefix is not None:\n            if new_prefix < self._prefixlen:\n                raise ValueError('new prefix must be longer')\n            if prefixlen_diff != 1:\n                raise ValueError('cannot set prefixlen_diff and new_prefix')\n            prefixlen_diff = new_prefix - self._prefixlen\n\n        if prefixlen_diff < 0:\n            raise ValueError('prefix length diff must be > 0')\n        new_prefixlen = self._prefixlen + prefixlen_diff\n\n        if new_prefixlen > self._max_prefixlen:\n            raise ValueError(\n                'prefix length diff %d is invalid for netblock %s' % (\n                    new_prefixlen, self))\n\n        start = int(self.network_address)\n        end = int(self.broadcast_address) + 1\n        step = (int(self.hostmask) + 1) >> prefixlen_diff\n        for new_addr in _compat_range(start, end, step):\n            current = self.__class__((new_addr, new_prefixlen))\n            yield current\n\n    def supernet(self, prefixlen_diff=1, new_prefix=None):\n        \"\"\"The supernet containing the current network.\n\n        Args:\n            prefixlen_diff: An integer, the amount the prefix length of\n              the network should be decreased by.  For example, given a\n              /24 network and a prefixlen_diff of 3, a supernet with a\n              /21 netmask is returned.\n\n        Returns:\n            An IPv4 network object.\n\n        Raises:\n            ValueError: If self.prefixlen - prefixlen_diff < 0. I.e., you have\n              a negative prefix length.\n                OR\n            If prefixlen_diff and new_prefix are both set or new_prefix is a\n              larger number than the current prefix (larger number means a\n              smaller network)\n\n        \"\"\"\n        if self._prefixlen == 0:\n            return self\n\n        if new_prefix is not None:\n            if new_prefix > self._prefixlen:\n                raise ValueError('new prefix must be shorter')\n            if prefixlen_diff != 1:\n                raise ValueError('cannot set prefixlen_diff and new_prefix')\n            prefixlen_diff = self._prefixlen - new_prefix\n\n        new_prefixlen = self.prefixlen - prefixlen_diff\n        if new_prefixlen < 0:\n            raise ValueError(\n                'current prefixlen is %d, cannot have a prefixlen_diff of %d' %\n                (self.prefixlen, prefixlen_diff))\n        return self.__class__((\n            int(self.network_address) & (int(self.netmask) << prefixlen_diff),\n            new_prefixlen))\n\n    @property\n    def is_multicast(self):\n        \"\"\"Test if the address is reserved for multicast use.\n\n        Returns:\n            A boolean, True if the address is a multicast address.\n            See RFC 2373 2.7 for details.\n\n        \"\"\"\n        return (self.network_address.is_multicast and\n                self.broadcast_address.is_multicast)\n\n    @staticmethod\n    def _is_subnet_of(a, b):\n        try:\n            # Always false if one is v4 and the other is v6.\n            if a._version != b._version:\n                raise TypeError(\"%s and %s are not of the same version\" (a, b))\n            return (b.network_address <= a.network_address and\n                    b.broadcast_address >= a.broadcast_address)\n        except AttributeError:\n            raise TypeError(\"Unable to test subnet containment \"\n                            \"between %s and %s\" % (a, b))\n\n    def subnet_of(self, other):\n        \"\"\"Return True if this network is a subnet of other.\"\"\"\n        return self._is_subnet_of(self, other)\n\n    def supernet_of(self, other):\n        \"\"\"Return True if this network is a supernet of other.\"\"\"\n        return self._is_subnet_of(other, self)\n\n    @property\n    def is_reserved(self):\n        \"\"\"Test if the address is otherwise IETF reserved.\n\n        Returns:\n            A boolean, True if the address is within one of the\n            reserved IPv6 Network ranges.\n\n        \"\"\"\n        return (self.network_address.is_reserved and\n                self.broadcast_address.is_reserved)\n\n    @property\n    def is_link_local(self):\n        \"\"\"Test if the address is reserved for link-local.\n\n        Returns:\n            A boolean, True if the address is reserved per RFC 4291.\n\n        \"\"\"\n        return (self.network_address.is_link_local and\n                self.broadcast_address.is_link_local)\n\n    @property\n    def is_private(self):\n        \"\"\"Test if this address is allocated for private networks.\n\n        Returns:\n            A boolean, True if the address is reserved per\n            iana-ipv4-special-registry or iana-ipv6-special-registry.\n\n        \"\"\"\n        return (self.network_address.is_private and\n                self.broadcast_address.is_private)\n\n    @property\n    def is_global(self):\n        \"\"\"Test if this address is allocated for public networks.\n\n        Returns:\n            A boolean, True if the address is not reserved per\n            iana-ipv4-special-registry or iana-ipv6-special-registry.\n\n        \"\"\"\n        return not self.is_private\n\n    @property\n    def is_unspecified(self):\n        \"\"\"Test if the address is unspecified.\n\n        Returns:\n            A boolean, True if this is the unspecified address as defined in\n            RFC 2373 2.5.2.\n\n        \"\"\"\n        return (self.network_address.is_unspecified and\n                self.broadcast_address.is_unspecified)\n\n    @property\n    def is_loopback(self):\n        \"\"\"Test if the address is a loopback address.\n\n        Returns:\n            A boolean, True if the address is a loopback address as defined in\n            RFC 2373 2.5.3.\n\n        \"\"\"\n        return (self.network_address.is_loopback and\n                self.broadcast_address.is_loopback)\n\n\nclass _BaseV4(object):\n\n    \"\"\"Base IPv4 object.\n\n    The following methods are used by IPv4 objects in both single IP\n    addresses and networks.\n\n    \"\"\"\n\n    __slots__ = ()\n    _version = 4\n    # Equivalent to 255.255.255.255 or 32 bits of 1's.\n    _ALL_ONES = (2 ** IPV4LENGTH) - 1\n    _DECIMAL_DIGITS = frozenset('0123456789')\n\n    # the valid octets for host and netmasks. only useful for IPv4.\n    _valid_mask_octets = frozenset([255, 254, 252, 248, 240, 224, 192, 128, 0])\n\n    _max_prefixlen = IPV4LENGTH\n    # There are only a handful of valid v4 netmasks, so we cache them all\n    # when constructed (see _make_netmask()).\n    _netmask_cache = {}\n\n    def _explode_shorthand_ip_string(self):\n        return _compat_str(self)\n\n    @classmethod\n    def _make_netmask(cls, arg):\n        \"\"\"Make a (netmask, prefix_len) tuple from the given argument.\n\n        Argument can be:\n        - an integer (the prefix length)\n        - a string representing the prefix length (e.g. \"24\")\n        - a string representing the prefix netmask (e.g. \"255.255.255.0\")\n        \"\"\"\n        if arg not in cls._netmask_cache:\n            if isinstance(arg, _compat_int_types):\n                prefixlen = arg\n            else:\n                try:\n                    # Check for a netmask in prefix length form\n                    prefixlen = cls._prefix_from_prefix_string(arg)\n                except NetmaskValueError:\n                    # Check for a netmask or hostmask in dotted-quad form.\n                    # This may raise NetmaskValueError.\n                    prefixlen = cls._prefix_from_ip_string(arg)\n            netmask = IPv4Address(cls._ip_int_from_prefix(prefixlen))\n            cls._netmask_cache[arg] = netmask, prefixlen\n        return cls._netmask_cache[arg]\n\n    @classmethod\n    def _ip_int_from_string(cls, ip_str):\n        \"\"\"Turn the given IP string into an integer for comparison.\n\n        Args:\n            ip_str: A string, the IP ip_str.\n\n        Returns:\n            The IP ip_str as an integer.\n\n        Raises:\n            AddressValueError: if ip_str isn't a valid IPv4 Address.\n\n        \"\"\"\n        if not ip_str:\n            raise AddressValueError('Address cannot be empty')\n\n        octets = ip_str.split('.')\n        if len(octets) != 4:\n            raise AddressValueError(\"Expected 4 octets in %r\" % ip_str)\n\n        try:\n            return _compat_int_from_byte_vals(\n                map(cls._parse_octet, octets), 'big')\n        except ValueError as exc:\n            raise AddressValueError(\"%s in %r\" % (exc, ip_str))\n\n    @classmethod\n    def _parse_octet(cls, octet_str):\n        \"\"\"Convert a decimal octet into an integer.\n\n        Args:\n            octet_str: A string, the number to parse.\n\n        Returns:\n            The octet as an integer.\n\n        Raises:\n            ValueError: if the octet isn't strictly a decimal from [0..255].\n\n        \"\"\"\n        if not octet_str:\n            raise ValueError(\"Empty octet not permitted\")\n        # Whitelist the characters, since int() allows a lot of bizarre stuff.\n        if not cls._DECIMAL_DIGITS.issuperset(octet_str):\n            msg = \"Only decimal digits permitted in %r\"\n            raise ValueError(msg % octet_str)\n        # We do the length check second, since the invalid character error\n        # is likely to be more informative for the user\n        if len(octet_str) > 3:\n            msg = \"At most 3 characters permitted in %r\"\n            raise ValueError(msg % octet_str)\n        # Convert to integer (we know digits are legal)\n        octet_int = int(octet_str, 10)\n        # Any octets that look like they *might* be written in octal,\n        # and which don't look exactly the same in both octal and\n        # decimal are rejected as ambiguous\n        if octet_int > 7 and octet_str[0] == '0':\n            msg = \"Ambiguous (octal/decimal) value in %r not permitted\"\n            raise ValueError(msg % octet_str)\n        if octet_int > 255:\n            raise ValueError(\"Octet %d (> 255) not permitted\" % octet_int)\n        return octet_int\n\n    @classmethod\n    def _string_from_ip_int(cls, ip_int):\n        \"\"\"Turns a 32-bit integer into dotted decimal notation.\n\n        Args:\n            ip_int: An integer, the IP address.\n\n        Returns:\n            The IP address as a string in dotted decimal notation.\n\n        \"\"\"\n        return '.'.join(_compat_str(struct.unpack(b'!B', b)[0]\n                                    if isinstance(b, bytes)\n                                    else b)\n                        for b in _compat_to_bytes(ip_int, 4, 'big'))\n\n    def _is_hostmask(self, ip_str):\n        \"\"\"Test if the IP string is a hostmask (rather than a netmask).\n\n        Args:\n            ip_str: A string, the potential hostmask.\n\n        Returns:\n            A boolean, True if the IP string is a hostmask.\n\n        \"\"\"\n        bits = ip_str.split('.')\n        try:\n            parts = [x for x in map(int, bits) if x in self._valid_mask_octets]\n        except ValueError:\n            return False\n        if len(parts) != len(bits):\n            return False\n        if parts[0] < parts[-1]:\n            return True\n        return False\n\n    def _reverse_pointer(self):\n        \"\"\"Return the reverse DNS pointer name for the IPv4 address.\n\n        This implements the method described in RFC1035 3.5.\n\n        \"\"\"\n        reverse_octets = _compat_str(self).split('.')[::-1]\n        return '.'.join(reverse_octets) + '.in-addr.arpa'\n\n    @property\n    def max_prefixlen(self):\n        return self._max_prefixlen\n\n    @property\n    def version(self):\n        return self._version\n\n\nclass IPv4Address(_BaseV4, _BaseAddress):\n\n    \"\"\"Represent and manipulate single IPv4 Addresses.\"\"\"\n\n    __slots__ = ('_ip', '__weakref__')\n\n    def __init__(self, address):\n\n        \"\"\"\n        Args:\n            address: A string or integer representing the IP\n\n              Additionally, an integer can be passed, so\n              IPv4Address('192.0.2.1') == IPv4Address(3221225985).\n              or, more generally\n              IPv4Address(int(IPv4Address('192.0.2.1'))) ==\n                IPv4Address('192.0.2.1')\n\n        Raises:\n            AddressValueError: If ipaddress isn't a valid IPv4 address.\n\n        \"\"\"\n        # Efficient constructor from integer.\n        if isinstance(address, _compat_int_types):\n            self._check_int_address(address)\n            self._ip = address\n            return\n\n        # Constructing from a packed address\n        if isinstance(address, bytes):\n            self._check_packed_address(address, 4)\n            bvs = _compat_bytes_to_byte_vals(address)\n            self._ip = _compat_int_from_byte_vals(bvs, 'big')\n            return\n\n        # Assume input argument to be string or any object representation\n        # which converts into a formatted IP string.\n        addr_str = _compat_str(address)\n        if '/' in addr_str:\n            raise AddressValueError(\"Unexpected '/' in %r\" % address)\n        self._ip = self._ip_int_from_string(addr_str)\n\n    @property\n    def packed(self):\n        \"\"\"The binary representation of this address.\"\"\"\n        return v4_int_to_packed(self._ip)\n\n    @property\n    def is_reserved(self):\n        \"\"\"Test if the address is otherwise IETF reserved.\n\n         Returns:\n             A boolean, True if the address is within the\n             reserved IPv4 Network range.\n\n        \"\"\"\n        return self in self._constants._reserved_network\n\n    @property\n    def is_private(self):\n        \"\"\"Test if this address is allocated for private networks.\n\n        Returns:\n            A boolean, True if the address is reserved per\n            iana-ipv4-special-registry.\n\n        \"\"\"\n        return any(self in net for net in self._constants._private_networks)\n\n    @property\n    def is_global(self):\n        return (\n            self not in self._constants._public_network and\n            not self.is_private)\n\n    @property\n    def is_multicast(self):\n        \"\"\"Test if the address is reserved for multicast use.\n\n        Returns:\n            A boolean, True if the address is multicast.\n            See RFC 3171 for details.\n\n        \"\"\"\n        return self in self._constants._multicast_network\n\n    @property\n    def is_unspecified(self):\n        \"\"\"Test if the address is unspecified.\n\n        Returns:\n            A boolean, True if this is the unspecified address as defined in\n            RFC 5735 3.\n\n        \"\"\"\n        return self == self._constants._unspecified_address\n\n    @property\n    def is_loopback(self):\n        \"\"\"Test if the address is a loopback address.\n\n        Returns:\n            A boolean, True if the address is a loopback per RFC 3330.\n\n        \"\"\"\n        return self in self._constants._loopback_network\n\n    @property\n    def is_link_local(self):\n        \"\"\"Test if the address is reserved for link-local.\n\n        Returns:\n            A boolean, True if the address is link-local per RFC 3927.\n\n        \"\"\"\n        return self in self._constants._linklocal_network\n\n\nclass IPv4Interface(IPv4Address):\n\n    def __init__(self, address):\n        if isinstance(address, (bytes, _compat_int_types)):\n            IPv4Address.__init__(self, address)\n            self.network = IPv4Network(self._ip)\n            self._prefixlen = self._max_prefixlen\n            return\n\n        if isinstance(address, tuple):\n            IPv4Address.__init__(self, address[0])\n            if len(address) > 1:\n                self._prefixlen = int(address[1])\n            else:\n                self._prefixlen = self._max_prefixlen\n\n            self.network = IPv4Network(address, strict=False)\n            self.netmask = self.network.netmask\n            self.hostmask = self.network.hostmask\n            return\n\n        addr = _split_optional_netmask(address)\n        IPv4Address.__init__(self, addr[0])\n\n        self.network = IPv4Network(address, strict=False)\n        self._prefixlen = self.network._prefixlen\n\n        self.netmask = self.network.netmask\n        self.hostmask = self.network.hostmask\n\n    def __str__(self):\n        return '%s/%d' % (self._string_from_ip_int(self._ip),\n                          self.network.prefixlen)\n\n    def __eq__(self, other):\n        address_equal = IPv4Address.__eq__(self, other)\n        if not address_equal or address_equal is NotImplemented:\n            return address_equal\n        try:\n            return self.network == other.network\n        except AttributeError:\n            # An interface with an associated network is NOT the\n            # same as an unassociated address. That's why the hash\n            # takes the extra info into account.\n            return False\n\n    def __lt__(self, other):\n        address_less = IPv4Address.__lt__(self, other)\n        if address_less is NotImplemented:\n            return NotImplemented\n        try:\n            return (self.network < other.network or\n                    self.network == other.network and address_less)\n        except AttributeError:\n            # We *do* allow addresses and interfaces to be sorted. The\n            # unassociated address is considered less than all interfaces.\n            return False\n\n    def __hash__(self):\n        return self._ip ^ self._prefixlen ^ int(self.network.network_address)\n\n    __reduce__ = _IPAddressBase.__reduce__\n\n    @property\n    def ip(self):\n        return IPv4Address(self._ip)\n\n    @property\n    def with_prefixlen(self):\n        return '%s/%s' % (self._string_from_ip_int(self._ip),\n                          self._prefixlen)\n\n    @property\n    def with_netmask(self):\n        return '%s/%s' % (self._string_from_ip_int(self._ip),\n                          self.netmask)\n\n    @property\n    def with_hostmask(self):\n        return '%s/%s' % (self._string_from_ip_int(self._ip),\n                          self.hostmask)\n\n\nclass IPv4Network(_BaseV4, _BaseNetwork):\n\n    \"\"\"This class represents and manipulates 32-bit IPv4 network + addresses..\n\n    Attributes: [examples for IPv4Network('192.0.2.0/27')]\n        .network_address: IPv4Address('192.0.2.0')\n        .hostmask: IPv4Address('0.0.0.31')\n        .broadcast_address: IPv4Address('192.0.2.32')\n        .netmask: IPv4Address('255.255.255.224')\n        .prefixlen: 27\n\n    \"\"\"\n    # Class to use when creating address objects\n    _address_class = IPv4Address\n\n    def __init__(self, address, strict=True):\n\n        \"\"\"Instantiate a new IPv4 network object.\n\n        Args:\n            address: A string or integer representing the IP [& network].\n              '192.0.2.0/24'\n              '192.0.2.0/255.255.255.0'\n              '192.0.0.2/0.0.0.255'\n              are all functionally the same in IPv4. Similarly,\n              '192.0.2.1'\n              '192.0.2.1/255.255.255.255'\n              '192.0.2.1/32'\n              are also functionally equivalent. That is to say, failing to\n              provide a subnetmask will create an object with a mask of /32.\n\n              If the mask (portion after the / in the argument) is given in\n              dotted quad form, it is treated as a netmask if it starts with a\n              non-zero field (e.g. /255.0.0.0 == /8) and as a hostmask if it\n              starts with a zero field (e.g. 0.255.255.255 == /8), with the\n              single exception of an all-zero mask which is treated as a\n              netmask == /0. If no mask is given, a default of /32 is used.\n\n              Additionally, an integer can be passed, so\n              IPv4Network('192.0.2.1') == IPv4Network(3221225985)\n              or, more generally\n              IPv4Interface(int(IPv4Interface('192.0.2.1'))) ==\n                IPv4Interface('192.0.2.1')\n\n        Raises:\n            AddressValueError: If ipaddress isn't a valid IPv4 address.\n            NetmaskValueError: If the netmask isn't valid for\n              an IPv4 address.\n            ValueError: If strict is True and a network address is not\n              supplied.\n\n        \"\"\"\n        _BaseNetwork.__init__(self, address)\n\n        # Constructing from a packed address or integer\n        if isinstance(address, (_compat_int_types, bytes)):\n            self.network_address = IPv4Address(address)\n            self.netmask, self._prefixlen = self._make_netmask(\n                self._max_prefixlen)\n            # fixme: address/network test here.\n            return\n\n        if isinstance(address, tuple):\n            if len(address) > 1:\n                arg = address[1]\n            else:\n                # We weren't given an address[1]\n                arg = self._max_prefixlen\n            self.network_address = IPv4Address(address[0])\n            self.netmask, self._prefixlen = self._make_netmask(arg)\n            packed = int(self.network_address)\n            if packed & int(self.netmask) != packed:\n                if strict:\n                    raise ValueError('%s has host bits set' % self)\n                else:\n                    self.network_address = IPv4Address(packed &\n                                                       int(self.netmask))\n            return\n\n        # Assume input argument to be string or any object representation\n        # which converts into a formatted IP prefix string.\n        addr = _split_optional_netmask(address)\n        self.network_address = IPv4Address(self._ip_int_from_string(addr[0]))\n\n        if len(addr) == 2:\n            arg = addr[1]\n        else:\n            arg = self._max_prefixlen\n        self.netmask, self._prefixlen = self._make_netmask(arg)\n\n        if strict:\n            if (IPv4Address(int(self.network_address) & int(self.netmask)) !=\n                    self.network_address):\n                raise ValueError('%s has host bits set' % self)\n        self.network_address = IPv4Address(int(self.network_address) &\n                                           int(self.netmask))\n\n        if self._prefixlen == (self._max_prefixlen - 1):\n            self.hosts = self.__iter__\n\n    @property\n    def is_global(self):\n        \"\"\"Test if this address is allocated for public networks.\n\n        Returns:\n            A boolean, True if the address is not reserved per\n            iana-ipv4-special-registry.\n\n        \"\"\"\n        return (not (self.network_address in IPv4Network('100.64.0.0/10') and\n                self.broadcast_address in IPv4Network('100.64.0.0/10')) and\n                not self.is_private)\n\n\nclass _IPv4Constants(object):\n\n    _linklocal_network = IPv4Network('169.254.0.0/16')\n\n    _loopback_network = IPv4Network('127.0.0.0/8')\n\n    _multicast_network = IPv4Network('224.0.0.0/4')\n\n    _public_network = IPv4Network('100.64.0.0/10')\n\n    _private_networks = [\n        IPv4Network('0.0.0.0/8'),\n        IPv4Network('10.0.0.0/8'),\n        IPv4Network('127.0.0.0/8'),\n        IPv4Network('169.254.0.0/16'),\n        IPv4Network('172.16.0.0/12'),\n        IPv4Network('192.0.0.0/29'),\n        IPv4Network('192.0.0.170/31'),\n        IPv4Network('192.0.2.0/24'),\n        IPv4Network('192.168.0.0/16'),\n        IPv4Network('198.18.0.0/15'),\n        IPv4Network('198.51.100.0/24'),\n        IPv4Network('203.0.113.0/24'),\n        IPv4Network('240.0.0.0/4'),\n        IPv4Network('255.255.255.255/32'),\n    ]\n\n    _reserved_network = IPv4Network('240.0.0.0/4')\n\n    _unspecified_address = IPv4Address('0.0.0.0')\n\n\nIPv4Address._constants = _IPv4Constants\n\n\nclass _BaseV6(object):\n\n    \"\"\"Base IPv6 object.\n\n    The following methods are used by IPv6 objects in both single IP\n    addresses and networks.\n\n    \"\"\"\n\n    __slots__ = ()\n    _version = 6\n    _ALL_ONES = (2 ** IPV6LENGTH) - 1\n    _HEXTET_COUNT = 8\n    _HEX_DIGITS = frozenset('0123456789ABCDEFabcdef')\n    _max_prefixlen = IPV6LENGTH\n\n    # There are only a bunch of valid v6 netmasks, so we cache them all\n    # when constructed (see _make_netmask()).\n    _netmask_cache = {}\n\n    @classmethod\n    def _make_netmask(cls, arg):\n        \"\"\"Make a (netmask, prefix_len) tuple from the given argument.\n\n        Argument can be:\n        - an integer (the prefix length)\n        - a string representing the prefix length (e.g. \"24\")\n        - a string representing the prefix netmask (e.g. \"255.255.255.0\")\n        \"\"\"\n        if arg not in cls._netmask_cache:\n            if isinstance(arg, _compat_int_types):\n                prefixlen = arg\n            else:\n                prefixlen = cls._prefix_from_prefix_string(arg)\n            netmask = IPv6Address(cls._ip_int_from_prefix(prefixlen))\n            cls._netmask_cache[arg] = netmask, prefixlen\n        return cls._netmask_cache[arg]\n\n    @classmethod\n    def _ip_int_from_string(cls, ip_str):\n        \"\"\"Turn an IPv6 ip_str into an integer.\n\n        Args:\n            ip_str: A string, the IPv6 ip_str.\n\n        Returns:\n            An int, the IPv6 address\n\n        Raises:\n            AddressValueError: if ip_str isn't a valid IPv6 Address.\n\n        \"\"\"\n        if not ip_str:\n            raise AddressValueError('Address cannot be empty')\n\n        parts = ip_str.split(':')\n\n        # An IPv6 address needs at least 2 colons (3 parts).\n        _min_parts = 3\n        if len(parts) < _min_parts:\n            msg = \"At least %d parts expected in %r\" % (_min_parts, ip_str)\n            raise AddressValueError(msg)\n\n        # If the address has an IPv4-style suffix, convert it to hexadecimal.\n        if '.' in parts[-1]:\n            try:\n                ipv4_int = IPv4Address(parts.pop())._ip\n            except AddressValueError as exc:\n                raise AddressValueError(\"%s in %r\" % (exc, ip_str))\n            parts.append('%x' % ((ipv4_int >> 16) & 0xFFFF))\n            parts.append('%x' % (ipv4_int & 0xFFFF))\n\n        # An IPv6 address can't have more than 8 colons (9 parts).\n        # The extra colon comes from using the \"::\" notation for a single\n        # leading or trailing zero part.\n        _max_parts = cls._HEXTET_COUNT + 1\n        if len(parts) > _max_parts:\n            msg = \"At most %d colons permitted in %r\" % (\n                _max_parts - 1, ip_str)\n            raise AddressValueError(msg)\n\n        # Disregarding the endpoints, find '::' with nothing in between.\n        # This indicates that a run of zeroes has been skipped.\n        skip_index = None\n        for i in _compat_range(1, len(parts) - 1):\n            if not parts[i]:\n                if skip_index is not None:\n                    # Can't have more than one '::'\n                    msg = \"At most one '::' permitted in %r\" % ip_str\n                    raise AddressValueError(msg)\n                skip_index = i\n\n        # parts_hi is the number of parts to copy from above/before the '::'\n        # parts_lo is the number of parts to copy from below/after the '::'\n        if skip_index is not None:\n            # If we found a '::', then check if it also covers the endpoints.\n            parts_hi = skip_index\n            parts_lo = len(parts) - skip_index - 1\n            if not parts[0]:\n                parts_hi -= 1\n                if parts_hi:\n                    msg = \"Leading ':' only permitted as part of '::' in %r\"\n                    raise AddressValueError(msg % ip_str)  # ^: requires ^::\n            if not parts[-1]:\n                parts_lo -= 1\n                if parts_lo:\n                    msg = \"Trailing ':' only permitted as part of '::' in %r\"\n                    raise AddressValueError(msg % ip_str)  # :$ requires ::$\n            parts_skipped = cls._HEXTET_COUNT - (parts_hi + parts_lo)\n            if parts_skipped < 1:\n                msg = \"Expected at most %d other parts with '::' in %r\"\n                raise AddressValueError(msg % (cls._HEXTET_COUNT - 1, ip_str))\n        else:\n            # Otherwise, allocate the entire address to parts_hi.  The\n            # endpoints could still be empty, but _parse_hextet() will check\n            # for that.\n            if len(parts) != cls._HEXTET_COUNT:\n                msg = \"Exactly %d parts expected without '::' in %r\"\n                raise AddressValueError(msg % (cls._HEXTET_COUNT, ip_str))\n            if not parts[0]:\n                msg = \"Leading ':' only permitted as part of '::' in %r\"\n                raise AddressValueError(msg % ip_str)  # ^: requires ^::\n            if not parts[-1]:\n                msg = \"Trailing ':' only permitted as part of '::' in %r\"\n                raise AddressValueError(msg % ip_str)  # :$ requires ::$\n            parts_hi = len(parts)\n            parts_lo = 0\n            parts_skipped = 0\n\n        try:\n            # Now, parse the hextets into a 128-bit integer.\n            ip_int = 0\n            for i in range(parts_hi):\n                ip_int <<= 16\n                ip_int |= cls._parse_hextet(parts[i])\n            ip_int <<= 16 * parts_skipped\n            for i in range(-parts_lo, 0):\n                ip_int <<= 16\n                ip_int |= cls._parse_hextet(parts[i])\n            return ip_int\n        except ValueError as exc:\n            raise AddressValueError(\"%s in %r\" % (exc, ip_str))\n\n    @classmethod\n    def _parse_hextet(cls, hextet_str):\n        \"\"\"Convert an IPv6 hextet string into an integer.\n\n        Args:\n            hextet_str: A string, the number to parse.\n\n        Returns:\n            The hextet as an integer.\n\n        Raises:\n            ValueError: if the input isn't strictly a hex number from\n              [0..FFFF].\n\n        \"\"\"\n        # Whitelist the characters, since int() allows a lot of bizarre stuff.\n        if not cls._HEX_DIGITS.issuperset(hextet_str):\n            raise ValueError(\"Only hex digits permitted in %r\" % hextet_str)\n        # We do the length check second, since the invalid character error\n        # is likely to be more informative for the user\n        if len(hextet_str) > 4:\n            msg = \"At most 4 characters permitted in %r\"\n            raise ValueError(msg % hextet_str)\n        # Length check means we can skip checking the integer value\n        return int(hextet_str, 16)\n\n    @classmethod\n    def _compress_hextets(cls, hextets):\n        \"\"\"Compresses a list of hextets.\n\n        Compresses a list of strings, replacing the longest continuous\n        sequence of \"0\" in the list with \"\" and adding empty strings at\n        the beginning or at the end of the string such that subsequently\n        calling \":\".join(hextets) will produce the compressed version of\n        the IPv6 address.\n\n        Args:\n            hextets: A list of strings, the hextets to compress.\n\n        Returns:\n            A list of strings.\n\n        \"\"\"\n        best_doublecolon_start = -1\n        best_doublecolon_len = 0\n        doublecolon_start = -1\n        doublecolon_len = 0\n        for index, hextet in enumerate(hextets):\n            if hextet == '0':\n                doublecolon_len += 1\n                if doublecolon_start == -1:\n                    # Start of a sequence of zeros.\n                    doublecolon_start = index\n                if doublecolon_len > best_doublecolon_len:\n                    # This is the longest sequence of zeros so far.\n                    best_doublecolon_len = doublecolon_len\n                    best_doublecolon_start = doublecolon_start\n            else:\n                doublecolon_len = 0\n                doublecolon_start = -1\n\n        if best_doublecolon_len > 1:\n            best_doublecolon_end = (best_doublecolon_start +\n                                    best_doublecolon_len)\n            # For zeros at the end of the address.\n            if best_doublecolon_end == len(hextets):\n                hextets += ['']\n            hextets[best_doublecolon_start:best_doublecolon_end] = ['']\n            # For zeros at the beginning of the address.\n            if best_doublecolon_start == 0:\n                hextets = [''] + hextets\n\n        return hextets\n\n    @classmethod\n    def _string_from_ip_int(cls, ip_int=None):\n        \"\"\"Turns a 128-bit integer into hexadecimal notation.\n\n        Args:\n            ip_int: An integer, the IP address.\n\n        Returns:\n            A string, the hexadecimal representation of the address.\n\n        Raises:\n            ValueError: The address is bigger than 128 bits of all ones.\n\n        \"\"\"\n        if ip_int is None:\n            ip_int = int(cls._ip)\n\n        if ip_int > cls._ALL_ONES:\n            raise ValueError('IPv6 address is too large')\n\n        hex_str = '%032x' % ip_int\n        hextets = ['%x' % int(hex_str[x:x + 4], 16) for x in range(0, 32, 4)]\n\n        hextets = cls._compress_hextets(hextets)\n        return ':'.join(hextets)\n\n    def _explode_shorthand_ip_string(self):\n        \"\"\"Expand a shortened IPv6 address.\n\n        Args:\n            ip_str: A string, the IPv6 address.\n\n        Returns:\n            A string, the expanded IPv6 address.\n\n        \"\"\"\n        if isinstance(self, IPv6Network):\n            ip_str = _compat_str(self.network_address)\n        elif isinstance(self, IPv6Interface):\n            ip_str = _compat_str(self.ip)\n        else:\n            ip_str = _compat_str(self)\n\n        ip_int = self._ip_int_from_string(ip_str)\n        hex_str = '%032x' % ip_int\n        parts = [hex_str[x:x + 4] for x in range(0, 32, 4)]\n        if isinstance(self, (_BaseNetwork, IPv6Interface)):\n            return '%s/%d' % (':'.join(parts), self._prefixlen)\n        return ':'.join(parts)\n\n    def _reverse_pointer(self):\n        \"\"\"Return the reverse DNS pointer name for the IPv6 address.\n\n        This implements the method described in RFC3596 2.5.\n\n        \"\"\"\n        reverse_chars = self.exploded[::-1].replace(':', '')\n        return '.'.join(reverse_chars) + '.ip6.arpa'\n\n    @property\n    def max_prefixlen(self):\n        return self._max_prefixlen\n\n    @property\n    def version(self):\n        return self._version\n\n\nclass IPv6Address(_BaseV6, _BaseAddress):\n\n    \"\"\"Represent and manipulate single IPv6 Addresses.\"\"\"\n\n    __slots__ = ('_ip', '__weakref__')\n\n    def __init__(self, address):\n        \"\"\"Instantiate a new IPv6 address object.\n\n        Args:\n            address: A string or integer representing the IP\n\n              Additionally, an integer can be passed, so\n              IPv6Address('2001:db8::') ==\n                IPv6Address(42540766411282592856903984951653826560)\n              or, more generally\n              IPv6Address(int(IPv6Address('2001:db8::'))) ==\n                IPv6Address('2001:db8::')\n\n        Raises:\n            AddressValueError: If address isn't a valid IPv6 address.\n\n        \"\"\"\n        # Efficient constructor from integer.\n        if isinstance(address, _compat_int_types):\n            self._check_int_address(address)\n            self._ip = address\n            return\n\n        # Constructing from a packed address\n        if isinstance(address, bytes):\n            self._check_packed_address(address, 16)\n            bvs = _compat_bytes_to_byte_vals(address)\n            self._ip = _compat_int_from_byte_vals(bvs, 'big')\n            return\n\n        # Assume input argument to be string or any object representation\n        # which converts into a formatted IP string.\n        addr_str = _compat_str(address)\n        if '/' in addr_str:\n            raise AddressValueError(\"Unexpected '/' in %r\" % address)\n        self._ip = self._ip_int_from_string(addr_str)\n\n    @property\n    def packed(self):\n        \"\"\"The binary representation of this address.\"\"\"\n        return v6_int_to_packed(self._ip)\n\n    @property\n    def is_multicast(self):\n        \"\"\"Test if the address is reserved for multicast use.\n\n        Returns:\n            A boolean, True if the address is a multicast address.\n            See RFC 2373 2.7 for details.\n\n        \"\"\"\n        return self in self._constants._multicast_network\n\n    @property\n    def is_reserved(self):\n        \"\"\"Test if the address is otherwise IETF reserved.\n\n        Returns:\n            A boolean, True if the address is within one of the\n            reserved IPv6 Network ranges.\n\n        \"\"\"\n        return any(self in x for x in self._constants._reserved_networks)\n\n    @property\n    def is_link_local(self):\n        \"\"\"Test if the address is reserved for link-local.\n\n        Returns:\n            A boolean, True if the address is reserved per RFC 4291.\n\n        \"\"\"\n        return self in self._constants._linklocal_network\n\n    @property\n    def is_site_local(self):\n        \"\"\"Test if the address is reserved for site-local.\n\n        Note that the site-local address space has been deprecated by RFC 3879.\n        Use is_private to test if this address is in the space of unique local\n        addresses as defined by RFC 4193.\n\n        Returns:\n            A boolean, True if the address is reserved per RFC 3513 2.5.6.\n\n        \"\"\"\n        return self in self._constants._sitelocal_network\n\n    @property\n    def is_private(self):\n        \"\"\"Test if this address is allocated for private networks.\n\n        Returns:\n            A boolean, True if the address is reserved per\n            iana-ipv6-special-registry.\n\n        \"\"\"\n        return any(self in net for net in self._constants._private_networks)\n\n    @property\n    def is_global(self):\n        \"\"\"Test if this address is allocated for public networks.\n\n        Returns:\n            A boolean, true if the address is not reserved per\n            iana-ipv6-special-registry.\n\n        \"\"\"\n        return not self.is_private\n\n    @property\n    def is_unspecified(self):\n        \"\"\"Test if the address is unspecified.\n\n        Returns:\n            A boolean, True if this is the unspecified address as defined in\n            RFC 2373 2.5.2.\n\n        \"\"\"\n        return self._ip == 0\n\n    @property\n    def is_loopback(self):\n        \"\"\"Test if the address is a loopback address.\n\n        Returns:\n            A boolean, True if the address is a loopback address as defined in\n            RFC 2373 2.5.3.\n\n        \"\"\"\n        return self._ip == 1\n\n    @property\n    def ipv4_mapped(self):\n        \"\"\"Return the IPv4 mapped address.\n\n        Returns:\n            If the IPv6 address is a v4 mapped address, return the\n            IPv4 mapped address. Return None otherwise.\n\n        \"\"\"\n        if (self._ip >> 32) != 0xFFFF:\n            return None\n        return IPv4Address(self._ip & 0xFFFFFFFF)\n\n    @property\n    def teredo(self):\n        \"\"\"Tuple of embedded teredo IPs.\n\n        Returns:\n            Tuple of the (server, client) IPs or None if the address\n            doesn't appear to be a teredo address (doesn't start with\n            2001::/32)\n\n        \"\"\"\n        if (self._ip >> 96) != 0x20010000:\n            return None\n        return (IPv4Address((self._ip >> 64) & 0xFFFFFFFF),\n                IPv4Address(~self._ip & 0xFFFFFFFF))\n\n    @property\n    def sixtofour(self):\n        \"\"\"Return the IPv4 6to4 embedded address.\n\n        Returns:\n            The IPv4 6to4-embedded address if present or None if the\n            address doesn't appear to contain a 6to4 embedded address.\n\n        \"\"\"\n        if (self._ip >> 112) != 0x2002:\n            return None\n        return IPv4Address((self._ip >> 80) & 0xFFFFFFFF)\n\n\nclass IPv6Interface(IPv6Address):\n\n    def __init__(self, address):\n        if isinstance(address, (bytes, _compat_int_types)):\n            IPv6Address.__init__(self, address)\n            self.network = IPv6Network(self._ip)\n            self._prefixlen = self._max_prefixlen\n            return\n        if isinstance(address, tuple):\n            IPv6Address.__init__(self, address[0])\n            if len(address) > 1:\n                self._prefixlen = int(address[1])\n            else:\n                self._prefixlen = self._max_prefixlen\n            self.network = IPv6Network(address, strict=False)\n            self.netmask = self.network.netmask\n            self.hostmask = self.network.hostmask\n            return\n\n        addr = _split_optional_netmask(address)\n        IPv6Address.__init__(self, addr[0])\n        self.network = IPv6Network(address, strict=False)\n        self.netmask = self.network.netmask\n        self._prefixlen = self.network._prefixlen\n        self.hostmask = self.network.hostmask\n\n    def __str__(self):\n        return '%s/%d' % (self._string_from_ip_int(self._ip),\n                          self.network.prefixlen)\n\n    def __eq__(self, other):\n        address_equal = IPv6Address.__eq__(self, other)\n        if not address_equal or address_equal is NotImplemented:\n            return address_equal\n        try:\n            return self.network == other.network\n        except AttributeError:\n            # An interface with an associated network is NOT the\n            # same as an unassociated address. That's why the hash\n            # takes the extra info into account.\n            return False\n\n    def __lt__(self, other):\n        address_less = IPv6Address.__lt__(self, other)\n        if address_less is NotImplemented:\n            return NotImplemented\n        try:\n            return (self.network < other.network or\n                    self.network == other.network and address_less)\n        except AttributeError:\n            # We *do* allow addresses and interfaces to be sorted. The\n            # unassociated address is considered less than all interfaces.\n            return False\n\n    def __hash__(self):\n        return self._ip ^ self._prefixlen ^ int(self.network.network_address)\n\n    __reduce__ = _IPAddressBase.__reduce__\n\n    @property\n    def ip(self):\n        return IPv6Address(self._ip)\n\n    @property\n    def with_prefixlen(self):\n        return '%s/%s' % (self._string_from_ip_int(self._ip),\n                          self._prefixlen)\n\n    @property\n    def with_netmask(self):\n        return '%s/%s' % (self._string_from_ip_int(self._ip),\n                          self.netmask)\n\n    @property\n    def with_hostmask(self):\n        return '%s/%s' % (self._string_from_ip_int(self._ip),\n                          self.hostmask)\n\n    @property\n    def is_unspecified(self):\n        return self._ip == 0 and self.network.is_unspecified\n\n    @property\n    def is_loopback(self):\n        return self._ip == 1 and self.network.is_loopback\n\n\nclass IPv6Network(_BaseV6, _BaseNetwork):\n\n    \"\"\"This class represents and manipulates 128-bit IPv6 networks.\n\n    Attributes: [examples for IPv6('2001:db8::1000/124')]\n        .network_address: IPv6Address('2001:db8::1000')\n        .hostmask: IPv6Address('::f')\n        .broadcast_address: IPv6Address('2001:db8::100f')\n        .netmask: IPv6Address('ffff:ffff:ffff:ffff:ffff:ffff:ffff:fff0')\n        .prefixlen: 124\n\n    \"\"\"\n\n    # Class to use when creating address objects\n    _address_class = IPv6Address\n\n    def __init__(self, address, strict=True):\n        \"\"\"Instantiate a new IPv6 Network object.\n\n        Args:\n            address: A string or integer representing the IPv6 network or the\n              IP and prefix/netmask.\n              '2001:db8::/128'\n              '2001:db8:0000:0000:0000:0000:0000:0000/128'\n              '2001:db8::'\n              are all functionally the same in IPv6.  That is to say,\n              failing to provide a subnetmask will create an object with\n              a mask of /128.\n\n              Additionally, an integer can be passed, so\n              IPv6Network('2001:db8::') ==\n                IPv6Network(42540766411282592856903984951653826560)\n              or, more generally\n              IPv6Network(int(IPv6Network('2001:db8::'))) ==\n                IPv6Network('2001:db8::')\n\n            strict: A boolean. If true, ensure that we have been passed\n              A true network address, eg, 2001:db8::1000/124 and not an\n              IP address on a network, eg, 2001:db8::1/124.\n\n        Raises:\n            AddressValueError: If address isn't a valid IPv6 address.\n            NetmaskValueError: If the netmask isn't valid for\n              an IPv6 address.\n            ValueError: If strict was True and a network address was not\n              supplied.\n\n        \"\"\"\n        _BaseNetwork.__init__(self, address)\n\n        # Efficient constructor from integer or packed address\n        if isinstance(address, (bytes, _compat_int_types)):\n            self.network_address = IPv6Address(address)\n            self.netmask, self._prefixlen = self._make_netmask(\n                self._max_prefixlen)\n            return\n\n        if isinstance(address, tuple):\n            if len(address) > 1:\n                arg = address[1]\n            else:\n                arg = self._max_prefixlen\n            self.netmask, self._prefixlen = self._make_netmask(arg)\n            self.network_address = IPv6Address(address[0])\n            packed = int(self.network_address)\n            if packed & int(self.netmask) != packed:\n                if strict:\n                    raise ValueError('%s has host bits set' % self)\n                else:\n                    self.network_address = IPv6Address(packed &\n                                                       int(self.netmask))\n            return\n\n        # Assume input argument to be string or any object representation\n        # which converts into a formatted IP prefix string.\n        addr = _split_optional_netmask(address)\n\n        self.network_address = IPv6Address(self._ip_int_from_string(addr[0]))\n\n        if len(addr) == 2:\n            arg = addr[1]\n        else:\n            arg = self._max_prefixlen\n        self.netmask, self._prefixlen = self._make_netmask(arg)\n\n        if strict:\n            if (IPv6Address(int(self.network_address) & int(self.netmask)) !=\n                    self.network_address):\n                raise ValueError('%s has host bits set' % self)\n        self.network_address = IPv6Address(int(self.network_address) &\n                                           int(self.netmask))\n\n        if self._prefixlen == (self._max_prefixlen - 1):\n            self.hosts = self.__iter__\n\n    def hosts(self):\n        \"\"\"Generate Iterator over usable hosts in a network.\n\n          This is like __iter__ except it doesn't return the\n          Subnet-Router anycast address.\n\n        \"\"\"\n        network = int(self.network_address)\n        broadcast = int(self.broadcast_address)\n        for x in _compat_range(network + 1, broadcast + 1):\n            yield self._address_class(x)\n\n    @property\n    def is_site_local(self):\n        \"\"\"Test if the address is reserved for site-local.\n\n        Note that the site-local address space has been deprecated by RFC 3879.\n        Use is_private to test if this address is in the space of unique local\n        addresses as defined by RFC 4193.\n\n        Returns:\n            A boolean, True if the address is reserved per RFC 3513 2.5.6.\n\n        \"\"\"\n        return (self.network_address.is_site_local and\n                self.broadcast_address.is_site_local)\n\n\nclass _IPv6Constants(object):\n\n    _linklocal_network = IPv6Network('fe80::/10')\n\n    _multicast_network = IPv6Network('ff00::/8')\n\n    _private_networks = [\n        IPv6Network('::1/128'),\n        IPv6Network('::/128'),\n        IPv6Network('::ffff:0:0/96'),\n        IPv6Network('100::/64'),\n        IPv6Network('2001::/23'),\n        IPv6Network('2001:2::/48'),\n        IPv6Network('2001:db8::/32'),\n        IPv6Network('2001:10::/28'),\n        IPv6Network('fc00::/7'),\n        IPv6Network('fe80::/10'),\n    ]\n\n    _reserved_networks = [\n        IPv6Network('::/8'), IPv6Network('100::/8'),\n        IPv6Network('200::/7'), IPv6Network('400::/6'),\n        IPv6Network('800::/5'), IPv6Network('1000::/4'),\n        IPv6Network('4000::/3'), IPv6Network('6000::/3'),\n        IPv6Network('8000::/3'), IPv6Network('A000::/3'),\n        IPv6Network('C000::/3'), IPv6Network('E000::/4'),\n        IPv6Network('F000::/5'), IPv6Network('F800::/6'),\n        IPv6Network('FE00::/9'),\n    ]\n\n    _sitelocal_network = IPv6Network('fec0::/10')\n\n\nIPv6Address._constants = _IPv6Constants\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/lockfile/__init__.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nlockfile.py - Platform-independent advisory file locks.\n\nRequires Python 2.5 unless you apply 2.4.diff\nLocking is done on a per-thread basis instead of a per-process basis.\n\nUsage:\n\n>>> lock = LockFile('somefile')\n>>> try:\n...     lock.acquire()\n... except AlreadyLocked:\n...     print 'somefile', 'is locked already.'\n... except LockFailed:\n...     print 'somefile', 'can\\\\'t be locked.'\n... else:\n...     print 'got lock'\ngot lock\n>>> print lock.is_locked()\nTrue\n>>> lock.release()\n\n>>> lock = LockFile('somefile')\n>>> print lock.is_locked()\nFalse\n>>> with lock:\n...    print lock.is_locked()\nTrue\n>>> print lock.is_locked()\nFalse\n\n>>> lock = LockFile('somefile')\n>>> # It is okay to lock twice from the same thread...\n>>> with lock:\n...     lock.acquire()\n...\n>>> # Though no counter is kept, so you can't unlock multiple times...\n>>> print lock.is_locked()\nFalse\n\nExceptions:\n\n    Error - base class for other exceptions\n        LockError - base class for all locking exceptions\n            AlreadyLocked - Another thread or process already holds the lock\n            LockFailed - Lock failed for some other reason\n        UnlockError - base class for all unlocking exceptions\n            AlreadyUnlocked - File was not locked.\n            NotMyLock - File was locked but not by the current thread/process\n\"\"\"\n\nfrom __future__ import absolute_import\n\nimport functools\nimport os\nimport socket\nimport threading\nimport warnings\n\n# Work with PEP8 and non-PEP8 versions of threading module.\nif not hasattr(threading, \"current_thread\"):\n    threading.current_thread = threading.currentThread\nif not hasattr(threading.Thread, \"get_name\"):\n    threading.Thread.get_name = threading.Thread.getName\n\n__all__ = ['Error', 'LockError', 'LockTimeout', 'AlreadyLocked',\n           'LockFailed', 'UnlockError', 'NotLocked', 'NotMyLock',\n           'LinkFileLock', 'MkdirFileLock', 'SQLiteFileLock',\n           'LockBase', 'locked']\n\n\nclass Error(Exception):\n    \"\"\"\n    Base class for other exceptions.\n\n    >>> try:\n    ...   raise Error\n    ... except Exception:\n    ...   pass\n    \"\"\"\n    pass\n\n\nclass LockError(Error):\n    \"\"\"\n    Base class for error arising from attempts to acquire the lock.\n\n    >>> try:\n    ...   raise LockError\n    ... except Error:\n    ...   pass\n    \"\"\"\n    pass\n\n\nclass LockTimeout(LockError):\n    \"\"\"Raised when lock creation fails within a user-defined period of time.\n\n    >>> try:\n    ...   raise LockTimeout\n    ... except LockError:\n    ...   pass\n    \"\"\"\n    pass\n\n\nclass AlreadyLocked(LockError):\n    \"\"\"Some other thread/process is locking the file.\n\n    >>> try:\n    ...   raise AlreadyLocked\n    ... except LockError:\n    ...   pass\n    \"\"\"\n    pass\n\n\nclass LockFailed(LockError):\n    \"\"\"Lock file creation failed for some other reason.\n\n    >>> try:\n    ...   raise LockFailed\n    ... except LockError:\n    ...   pass\n    \"\"\"\n    pass\n\n\nclass UnlockError(Error):\n    \"\"\"\n    Base class for errors arising from attempts to release the lock.\n\n    >>> try:\n    ...   raise UnlockError\n    ... except Error:\n    ...   pass\n    \"\"\"\n    pass\n\n\nclass NotLocked(UnlockError):\n    \"\"\"Raised when an attempt is made to unlock an unlocked file.\n\n    >>> try:\n    ...   raise NotLocked\n    ... except UnlockError:\n    ...   pass\n    \"\"\"\n    pass\n\n\nclass NotMyLock(UnlockError):\n    \"\"\"Raised when an attempt is made to unlock a file someone else locked.\n\n    >>> try:\n    ...   raise NotMyLock\n    ... except UnlockError:\n    ...   pass\n    \"\"\"\n    pass\n\n\nclass _SharedBase(object):\n    def __init__(self, path):\n        self.path = path\n\n    def acquire(self, timeout=None):\n        \"\"\"\n        Acquire the lock.\n\n        * If timeout is omitted (or None), wait forever trying to lock the\n          file.\n\n        * If timeout > 0, try to acquire the lock for that many seconds.  If\n          the lock period expires and the file is still locked, raise\n          LockTimeout.\n\n        * If timeout <= 0, raise AlreadyLocked immediately if the file is\n          already locked.\n        \"\"\"\n        raise NotImplemented(\"implement in subclass\")\n\n    def release(self):\n        \"\"\"\n        Release the lock.\n\n        If the file is not locked, raise NotLocked.\n        \"\"\"\n        raise NotImplemented(\"implement in subclass\")\n\n    def __enter__(self):\n        \"\"\"\n        Context manager support.\n        \"\"\"\n        self.acquire()\n        return self\n\n    def __exit__(self, *_exc):\n        \"\"\"\n        Context manager support.\n        \"\"\"\n        self.release()\n\n    def __repr__(self):\n        return \"<%s: %r>\" % (self.__class__.__name__, self.path)\n\n\nclass LockBase(_SharedBase):\n    \"\"\"Base class for platform-specific lock classes.\"\"\"\n    def __init__(self, path, threaded=True, timeout=None):\n        \"\"\"\n        >>> lock = LockBase('somefile')\n        >>> lock = LockBase('somefile', threaded=False)\n        \"\"\"\n        super(LockBase, self).__init__(path)\n        self.lock_file = os.path.abspath(path) + \".lock\"\n        self.hostname = socket.gethostname()\n        self.pid = os.getpid()\n        if threaded:\n            t = threading.current_thread()\n            # Thread objects in Python 2.4 and earlier do not have ident\n            # attrs.  Worm around that.\n            ident = getattr(t, \"ident\", hash(t))\n            self.tname = \"-%x\" % (ident & 0xffffffff)\n        else:\n            self.tname = \"\"\n        dirname = os.path.dirname(self.lock_file)\n\n        # unique name is mostly about the current process, but must\n        # also contain the path -- otherwise, two adjacent locked\n        # files conflict (one file gets locked, creating lock-file and\n        # unique file, the other one gets locked, creating lock-file\n        # and overwriting the already existing lock-file, then one\n        # gets unlocked, deleting both lock-file and unique file,\n        # finally the last lock errors out upon releasing.\n        self.unique_name = os.path.join(dirname,\n                                        \"%s%s.%s%s\" % (self.hostname,\n                                                       self.tname,\n                                                       self.pid,\n                                                       hash(self.path)))\n        self.timeout = timeout\n\n    def is_locked(self):\n        \"\"\"\n        Tell whether or not the file is locked.\n        \"\"\"\n        raise NotImplemented(\"implement in subclass\")\n\n    def i_am_locking(self):\n        \"\"\"\n        Return True if this object is locking the file.\n        \"\"\"\n        raise NotImplemented(\"implement in subclass\")\n\n    def break_lock(self):\n        \"\"\"\n        Remove a lock.  Useful if a locking thread failed to unlock.\n        \"\"\"\n        raise NotImplemented(\"implement in subclass\")\n\n    def __repr__(self):\n        return \"<%s: %r -- %r>\" % (self.__class__.__name__, self.unique_name,\n                                   self.path)\n\n\ndef _fl_helper(cls, mod, *args, **kwds):\n    warnings.warn(\"Import from %s module instead of lockfile package\" % mod,\n                  DeprecationWarning, stacklevel=2)\n    # This is a bit funky, but it's only for awhile.  The way the unit tests\n    # are constructed this function winds up as an unbound method, so it\n    # actually takes three args, not two.  We want to toss out self.\n    if not isinstance(args[0], str):\n        # We are testing, avoid the first arg\n        args = args[1:]\n    if len(args) == 1 and not kwds:\n        kwds[\"threaded\"] = True\n    return cls(*args, **kwds)\n\n\ndef LinkFileLock(*args, **kwds):\n    \"\"\"Factory function provided for backwards compatibility.\n\n    Do not use in new code.  Instead, import LinkLockFile from the\n    lockfile.linklockfile module.\n    \"\"\"\n    from . import linklockfile\n    return _fl_helper(linklockfile.LinkLockFile, \"lockfile.linklockfile\",\n                      *args, **kwds)\n\n\ndef MkdirFileLock(*args, **kwds):\n    \"\"\"Factory function provided for backwards compatibility.\n\n    Do not use in new code.  Instead, import MkdirLockFile from the\n    lockfile.mkdirlockfile module.\n    \"\"\"\n    from . import mkdirlockfile\n    return _fl_helper(mkdirlockfile.MkdirLockFile, \"lockfile.mkdirlockfile\",\n                      *args, **kwds)\n\n\ndef SQLiteFileLock(*args, **kwds):\n    \"\"\"Factory function provided for backwards compatibility.\n\n    Do not use in new code.  Instead, import SQLiteLockFile from the\n    lockfile.mkdirlockfile module.\n    \"\"\"\n    from . import sqlitelockfile\n    return _fl_helper(sqlitelockfile.SQLiteLockFile, \"lockfile.sqlitelockfile\",\n                      *args, **kwds)\n\n\ndef locked(path, timeout=None):\n    \"\"\"Decorator which enables locks for decorated function.\n\n    Arguments:\n     - path: path for lockfile.\n     - timeout (optional): Timeout for acquiring lock.\n\n     Usage:\n         @locked('/var/run/myname', timeout=0)\n         def myname(...):\n             ...\n    \"\"\"\n    def decor(func):\n        @functools.wraps(func)\n        def wrapper(*args, **kwargs):\n            lock = FileLock(path, timeout=timeout)\n            lock.acquire()\n            try:\n                return func(*args, **kwargs)\n            finally:\n                lock.release()\n        return wrapper\n    return decor\n\n\nif hasattr(os, \"link\"):\n    from . import linklockfile as _llf\n    LockFile = _llf.LinkLockFile\nelse:\n    from . import mkdirlockfile as _mlf\n    LockFile = _mlf.MkdirLockFile\n\nFileLock = LockFile\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/lockfile/linklockfile.py",
    "content": "from __future__ import absolute_import\n\nimport time\nimport os\n\nfrom . import (LockBase, LockFailed, NotLocked, NotMyLock, LockTimeout,\n               AlreadyLocked)\n\n\nclass LinkLockFile(LockBase):\n    \"\"\"Lock access to a file using atomic property of link(2).\n\n    >>> lock = LinkLockFile('somefile')\n    >>> lock = LinkLockFile('somefile', threaded=False)\n    \"\"\"\n\n    def acquire(self, timeout=None):\n        try:\n            open(self.unique_name, \"wb\").close()\n        except IOError:\n            raise LockFailed(\"failed to create %s\" % self.unique_name)\n\n        timeout = timeout if timeout is not None else self.timeout\n        end_time = time.time()\n        if timeout is not None and timeout > 0:\n            end_time += timeout\n\n        while True:\n            # Try and create a hard link to it.\n            try:\n                os.link(self.unique_name, self.lock_file)\n            except OSError:\n                # Link creation failed.  Maybe we've double-locked?\n                nlinks = os.stat(self.unique_name).st_nlink\n                if nlinks == 2:\n                    # The original link plus the one I created == 2.  We're\n                    # good to go.\n                    return\n                else:\n                    # Otherwise the lock creation failed.\n                    if timeout is not None and time.time() > end_time:\n                        os.unlink(self.unique_name)\n                        if timeout > 0:\n                            raise LockTimeout(\"Timeout waiting to acquire\"\n                                              \" lock for %s\" %\n                                              self.path)\n                        else:\n                            raise AlreadyLocked(\"%s is already locked\" %\n                                                self.path)\n                    time.sleep(timeout is not None and timeout / 10 or 0.1)\n            else:\n                # Link creation succeeded.  We're good to go.\n                return\n\n    def release(self):\n        if not self.is_locked():\n            raise NotLocked(\"%s is not locked\" % self.path)\n        elif not os.path.exists(self.unique_name):\n            raise NotMyLock(\"%s is locked, but not by me\" % self.path)\n        os.unlink(self.unique_name)\n        os.unlink(self.lock_file)\n\n    def is_locked(self):\n        return os.path.exists(self.lock_file)\n\n    def i_am_locking(self):\n        return (self.is_locked() and\n                os.path.exists(self.unique_name) and\n                os.stat(self.unique_name).st_nlink == 2)\n\n    def break_lock(self):\n        if os.path.exists(self.lock_file):\n            os.unlink(self.lock_file)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/lockfile/mkdirlockfile.py",
    "content": "from __future__ import absolute_import, division\n\nimport time\nimport os\nimport sys\nimport errno\n\nfrom . import (LockBase, LockFailed, NotLocked, NotMyLock, LockTimeout,\n               AlreadyLocked)\n\n\nclass MkdirLockFile(LockBase):\n    \"\"\"Lock file by creating a directory.\"\"\"\n    def __init__(self, path, threaded=True, timeout=None):\n        \"\"\"\n        >>> lock = MkdirLockFile('somefile')\n        >>> lock = MkdirLockFile('somefile', threaded=False)\n        \"\"\"\n        LockBase.__init__(self, path, threaded, timeout)\n        # Lock file itself is a directory.  Place the unique file name into\n        # it.\n        self.unique_name = os.path.join(self.lock_file,\n                                        \"%s.%s%s\" % (self.hostname,\n                                                     self.tname,\n                                                     self.pid))\n\n    def acquire(self, timeout=None):\n        timeout = timeout if timeout is not None else self.timeout\n        end_time = time.time()\n        if timeout is not None and timeout > 0:\n            end_time += timeout\n\n        if timeout is None:\n            wait = 0.1\n        else:\n            wait = max(0, timeout / 10)\n\n        while True:\n            try:\n                os.mkdir(self.lock_file)\n            except OSError:\n                err = sys.exc_info()[1]\n                if err.errno == errno.EEXIST:\n                    # Already locked.\n                    if os.path.exists(self.unique_name):\n                        # Already locked by me.\n                        return\n                    if timeout is not None and time.time() > end_time:\n                        if timeout > 0:\n                            raise LockTimeout(\"Timeout waiting to acquire\"\n                                              \" lock for %s\" %\n                                              self.path)\n                        else:\n                            # Someone else has the lock.\n                            raise AlreadyLocked(\"%s is already locked\" %\n                                                self.path)\n                    time.sleep(wait)\n                else:\n                    # Couldn't create the lock for some other reason\n                    raise LockFailed(\"failed to create %s\" % self.lock_file)\n            else:\n                open(self.unique_name, \"wb\").close()\n                return\n\n    def release(self):\n        if not self.is_locked():\n            raise NotLocked(\"%s is not locked\" % self.path)\n        elif not os.path.exists(self.unique_name):\n            raise NotMyLock(\"%s is locked, but not by me\" % self.path)\n        os.unlink(self.unique_name)\n        os.rmdir(self.lock_file)\n\n    def is_locked(self):\n        return os.path.exists(self.lock_file)\n\n    def i_am_locking(self):\n        return (self.is_locked() and\n                os.path.exists(self.unique_name))\n\n    def break_lock(self):\n        if os.path.exists(self.lock_file):\n            for name in os.listdir(self.lock_file):\n                os.unlink(os.path.join(self.lock_file, name))\n            os.rmdir(self.lock_file)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/lockfile/pidlockfile.py",
    "content": "# -*- coding: utf-8 -*-\n\n# pidlockfile.py\n#\n# Copyright © 2008–2009 Ben Finney <ben+python@benfinney.id.au>\n#\n# This is free software: you may copy, modify, and/or distribute this work\n# under the terms of the Python Software Foundation License, version 2 or\n# later as published by the Python Software Foundation.\n# No warranty expressed or implied. See the file LICENSE.PSF-2 for details.\n\n\"\"\" Lockfile behaviour implemented via Unix PID files.\n    \"\"\"\n\nfrom __future__ import absolute_import\n\nimport errno\nimport os\nimport time\n\nfrom . import (LockBase, AlreadyLocked, LockFailed, NotLocked, NotMyLock,\n               LockTimeout)\n\n\f\nclass PIDLockFile(LockBase):\n    \"\"\" Lockfile implemented as a Unix PID file.\n\n    The lock file is a normal file named by the attribute `path`.\n    A lock's PID file contains a single line of text, containing\n    the process ID (PID) of the process that acquired the lock.\n\n    >>> lock = PIDLockFile('somefile')\n    >>> lock = PIDLockFile('somefile')\n    \"\"\"\n\n    def __init__(self, path, threaded=False, timeout=None):\n        # pid lockfiles don't support threaded operation, so always force\n        # False as the threaded arg.\n        LockBase.__init__(self, path, False, timeout)\n        self.unique_name = self.path\n\n    def read_pid(self):\n        \"\"\" Get the PID from the lock file.\n            \"\"\"\n        return read_pid_from_pidfile(self.path)\n\n    def is_locked(self):\n        \"\"\" Test if the lock is currently held.\n\n            The lock is held if the PID file for this lock exists.\n\n            \"\"\"\n        return os.path.exists(self.path)\n\n    def i_am_locking(self):\n        \"\"\" Test if the lock is held by the current process.\n\n        Returns ``True`` if the current process ID matches the\n        number stored in the PID file.\n        \"\"\"\n        return self.is_locked() and os.getpid() == self.read_pid()\n\n    def acquire(self, timeout=None):\n        \"\"\" Acquire the lock.\n\n        Creates the PID file for this lock, or raises an error if\n        the lock could not be acquired.\n        \"\"\"\n\n        timeout = timeout if timeout is not None else self.timeout\n        end_time = time.time()\n        if timeout is not None and timeout > 0:\n            end_time += timeout\n\n        while True:\n            try:\n                write_pid_to_pidfile(self.path)\n            except OSError as exc:\n                if exc.errno == errno.EEXIST:\n                    # The lock creation failed.  Maybe sleep a bit.\n                    if time.time() > end_time:\n                        if timeout is not None and timeout > 0:\n                            raise LockTimeout(\"Timeout waiting to acquire\"\n                                              \" lock for %s\" %\n                                              self.path)\n                        else:\n                            raise AlreadyLocked(\"%s is already locked\" %\n                                                self.path)\n                    time.sleep(timeout is not None and timeout / 10 or 0.1)\n                else:\n                    raise LockFailed(\"failed to create %s\" % self.path)\n            else:\n                return\n\n    def release(self):\n        \"\"\" Release the lock.\n\n            Removes the PID file to release the lock, or raises an\n            error if the current process does not hold the lock.\n\n            \"\"\"\n        if not self.is_locked():\n            raise NotLocked(\"%s is not locked\" % self.path)\n        if not self.i_am_locking():\n            raise NotMyLock(\"%s is locked, but not by me\" % self.path)\n        remove_existing_pidfile(self.path)\n\n    def break_lock(self):\n        \"\"\" Break an existing lock.\n\n            Removes the PID file if it already exists, otherwise does\n            nothing.\n\n            \"\"\"\n        remove_existing_pidfile(self.path)\n\n\ndef read_pid_from_pidfile(pidfile_path):\n    \"\"\" Read the PID recorded in the named PID file.\n\n        Read and return the numeric PID recorded as text in the named\n        PID file. If the PID file cannot be read, or if the content is\n        not a valid PID, return ``None``.\n\n        \"\"\"\n    pid = None\n    try:\n        pidfile = open(pidfile_path, 'r')\n    except IOError:\n        pass\n    else:\n        # According to the FHS 2.3 section on PID files in /var/run:\n        #\n        #   The file must consist of the process identifier in\n        #   ASCII-encoded decimal, followed by a newline character.\n        #\n        #   Programs that read PID files should be somewhat flexible\n        #   in what they accept; i.e., they should ignore extra\n        #   whitespace, leading zeroes, absence of the trailing\n        #   newline, or additional lines in the PID file.\n\n        line = pidfile.readline().strip()\n        try:\n            pid = int(line)\n        except ValueError:\n            pass\n        pidfile.close()\n\n    return pid\n\n\ndef write_pid_to_pidfile(pidfile_path):\n    \"\"\" Write the PID in the named PID file.\n\n        Get the numeric process ID (“PID”) of the current process\n        and write it to the named file as a line of text.\n\n        \"\"\"\n    open_flags = (os.O_CREAT | os.O_EXCL | os.O_WRONLY)\n    open_mode = 0o644\n    pidfile_fd = os.open(pidfile_path, open_flags, open_mode)\n    pidfile = os.fdopen(pidfile_fd, 'w')\n\n    # According to the FHS 2.3 section on PID files in /var/run:\n    #\n    #   The file must consist of the process identifier in\n    #   ASCII-encoded decimal, followed by a newline character. For\n    #   example, if crond was process number 25, /var/run/crond.pid\n    #   would contain three characters: two, five, and newline.\n\n    pid = os.getpid()\n    pidfile.write(\"%s\\n\" % pid)\n    pidfile.close()\n\n\ndef remove_existing_pidfile(pidfile_path):\n    \"\"\" Remove the named PID file if it exists.\n\n        Removing a PID file that doesn't already exist puts us in the\n        desired state, so we ignore the condition if the file does not\n        exist.\n\n        \"\"\"\n    try:\n        os.remove(pidfile_path)\n    except OSError as exc:\n        if exc.errno == errno.ENOENT:\n            pass\n        else:\n            raise\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/lockfile/sqlitelockfile.py",
    "content": "from __future__ import absolute_import, division\n\nimport time\nimport os\n\ntry:\n    unicode\nexcept NameError:\n    unicode = str\n\nfrom . import LockBase, NotLocked, NotMyLock, LockTimeout, AlreadyLocked\n\n\nclass SQLiteLockFile(LockBase):\n    \"Demonstrate SQL-based locking.\"\n\n    testdb = None\n\n    def __init__(self, path, threaded=True, timeout=None):\n        \"\"\"\n        >>> lock = SQLiteLockFile('somefile')\n        >>> lock = SQLiteLockFile('somefile', threaded=False)\n        \"\"\"\n        LockBase.__init__(self, path, threaded, timeout)\n        self.lock_file = unicode(self.lock_file)\n        self.unique_name = unicode(self.unique_name)\n\n        if SQLiteLockFile.testdb is None:\n            import tempfile\n            _fd, testdb = tempfile.mkstemp()\n            os.close(_fd)\n            os.unlink(testdb)\n            del _fd, tempfile\n            SQLiteLockFile.testdb = testdb\n\n        import sqlite3\n        self.connection = sqlite3.connect(SQLiteLockFile.testdb)\n\n        c = self.connection.cursor()\n        try:\n            c.execute(\"create table locks\"\n                      \"(\"\n                      \"   lock_file varchar(32),\"\n                      \"   unique_name varchar(32)\"\n                      \")\")\n        except sqlite3.OperationalError:\n            pass\n        else:\n            self.connection.commit()\n            import atexit\n            atexit.register(os.unlink, SQLiteLockFile.testdb)\n\n    def acquire(self, timeout=None):\n        timeout = timeout if timeout is not None else self.timeout\n        end_time = time.time()\n        if timeout is not None and timeout > 0:\n            end_time += timeout\n\n        if timeout is None:\n            wait = 0.1\n        elif timeout <= 0:\n            wait = 0\n        else:\n            wait = timeout / 10\n\n        cursor = self.connection.cursor()\n\n        while True:\n            if not self.is_locked():\n                # Not locked.  Try to lock it.\n                cursor.execute(\"insert into locks\"\n                               \"  (lock_file, unique_name)\"\n                               \"  values\"\n                               \"  (?, ?)\",\n                               (self.lock_file, self.unique_name))\n                self.connection.commit()\n\n                # Check to see if we are the only lock holder.\n                cursor.execute(\"select * from locks\"\n                               \"  where unique_name = ?\",\n                               (self.unique_name,))\n                rows = cursor.fetchall()\n                if len(rows) > 1:\n                    # Nope.  Someone else got there.  Remove our lock.\n                    cursor.execute(\"delete from locks\"\n                                   \"  where unique_name = ?\",\n                                   (self.unique_name,))\n                    self.connection.commit()\n                else:\n                    # Yup.  We're done, so go home.\n                    return\n            else:\n                # Check to see if we are the only lock holder.\n                cursor.execute(\"select * from locks\"\n                               \"  where unique_name = ?\",\n                               (self.unique_name,))\n                rows = cursor.fetchall()\n                if len(rows) == 1:\n                    # We're the locker, so go home.\n                    return\n\n            # Maybe we should wait a bit longer.\n            if timeout is not None and time.time() > end_time:\n                if timeout > 0:\n                    # No more waiting.\n                    raise LockTimeout(\"Timeout waiting to acquire\"\n                                      \" lock for %s\" %\n                                      self.path)\n                else:\n                    # Someone else has the lock and we are impatient..\n                    raise AlreadyLocked(\"%s is already locked\" % self.path)\n\n            # Well, okay.  We'll give it a bit longer.\n            time.sleep(wait)\n\n    def release(self):\n        if not self.is_locked():\n            raise NotLocked(\"%s is not locked\" % self.path)\n        if not self.i_am_locking():\n            raise NotMyLock(\"%s is locked, but not by me (by %s)\" %\n                            (self.unique_name, self._who_is_locking()))\n        cursor = self.connection.cursor()\n        cursor.execute(\"delete from locks\"\n                       \"  where unique_name = ?\",\n                       (self.unique_name,))\n        self.connection.commit()\n\n    def _who_is_locking(self):\n        cursor = self.connection.cursor()\n        cursor.execute(\"select unique_name from locks\"\n                       \"  where lock_file = ?\",\n                       (self.lock_file,))\n        return cursor.fetchone()[0]\n\n    def is_locked(self):\n        cursor = self.connection.cursor()\n        cursor.execute(\"select * from locks\"\n                       \"  where lock_file = ?\",\n                       (self.lock_file,))\n        rows = cursor.fetchall()\n        return not not rows\n\n    def i_am_locking(self):\n        cursor = self.connection.cursor()\n        cursor.execute(\"select * from locks\"\n                       \"  where lock_file = ?\"\n                       \"    and unique_name = ?\",\n                       (self.lock_file, self.unique_name))\n        return not not cursor.fetchall()\n\n    def break_lock(self):\n        cursor = self.connection.cursor()\n        cursor.execute(\"delete from locks\"\n                       \"  where lock_file = ?\",\n                       (self.lock_file,))\n        self.connection.commit()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/lockfile/symlinklockfile.py",
    "content": "from __future__ import absolute_import\n\nimport os\nimport time\n\nfrom . import (LockBase, NotLocked, NotMyLock, LockTimeout,\n               AlreadyLocked)\n\n\nclass SymlinkLockFile(LockBase):\n    \"\"\"Lock access to a file using symlink(2).\"\"\"\n\n    def __init__(self, path, threaded=True, timeout=None):\n        # super(SymlinkLockFile).__init(...)\n        LockBase.__init__(self, path, threaded, timeout)\n        # split it back!\n        self.unique_name = os.path.split(self.unique_name)[1]\n\n    def acquire(self, timeout=None):\n        # Hopefully unnecessary for symlink.\n        # try:\n        #     open(self.unique_name, \"wb\").close()\n        # except IOError:\n        #     raise LockFailed(\"failed to create %s\" % self.unique_name)\n        timeout = timeout if timeout is not None else self.timeout\n        end_time = time.time()\n        if timeout is not None and timeout > 0:\n            end_time += timeout\n\n        while True:\n            # Try and create a symbolic link to it.\n            try:\n                os.symlink(self.unique_name, self.lock_file)\n            except OSError:\n                # Link creation failed.  Maybe we've double-locked?\n                if self.i_am_locking():\n                    # Linked to out unique name. Proceed.\n                    return\n                else:\n                    # Otherwise the lock creation failed.\n                    if timeout is not None and time.time() > end_time:\n                        if timeout > 0:\n                            raise LockTimeout(\"Timeout waiting to acquire\"\n                                              \" lock for %s\" %\n                                              self.path)\n                        else:\n                            raise AlreadyLocked(\"%s is already locked\" %\n                                                self.path)\n                    time.sleep(timeout / 10 if timeout is not None else 0.1)\n            else:\n                # Link creation succeeded.  We're good to go.\n                return\n\n    def release(self):\n        if not self.is_locked():\n            raise NotLocked(\"%s is not locked\" % self.path)\n        elif not self.i_am_locking():\n            raise NotMyLock(\"%s is locked, but not by me\" % self.path)\n        os.unlink(self.lock_file)\n\n    def is_locked(self):\n        return os.path.islink(self.lock_file)\n\n    def i_am_locking(self):\n        return (os.path.islink(self.lock_file)\n                and os.readlink(self.lock_file) == self.unique_name)\n\n    def break_lock(self):\n        if os.path.islink(self.lock_file):  # exists && link\n            os.unlink(self.lock_file)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/msgpack/__init__.py",
    "content": "# coding: utf-8\nfrom pip._vendor.msgpack._version import version\nfrom pip._vendor.msgpack.exceptions import *\n\nfrom collections import namedtuple\n\n\nclass ExtType(namedtuple('ExtType', 'code data')):\n    \"\"\"ExtType represents ext type in msgpack.\"\"\"\n    def __new__(cls, code, data):\n        if not isinstance(code, int):\n            raise TypeError(\"code must be int\")\n        if not isinstance(data, bytes):\n            raise TypeError(\"data must be bytes\")\n        if not 0 <= code <= 127:\n            raise ValueError(\"code must be 0~127\")\n        return super(ExtType, cls).__new__(cls, code, data)\n\n\nimport os\nif os.environ.get('MSGPACK_PUREPYTHON'):\n    from pip._vendor.msgpack.fallback import Packer, unpackb, Unpacker\nelse:\n    try:\n        from pip._vendor.msgpack._packer import Packer\n        from pip._vendor.msgpack._unpacker import unpackb, Unpacker\n    except ImportError:\n        from pip._vendor.msgpack.fallback import Packer, unpackb, Unpacker\n\n\ndef pack(o, stream, **kwargs):\n    \"\"\"\n    Pack object `o` and write it to `stream`\n\n    See :class:`Packer` for options.\n    \"\"\"\n    packer = Packer(**kwargs)\n    stream.write(packer.pack(o))\n\n\ndef packb(o, **kwargs):\n    \"\"\"\n    Pack object `o` and return packed bytes\n\n    See :class:`Packer` for options.\n    \"\"\"\n    return Packer(**kwargs).pack(o)\n\n\ndef unpack(stream, **kwargs):\n    \"\"\"\n    Unpack an object from `stream`.\n\n    Raises `ExtraData` when `stream` contains extra bytes.\n    See :class:`Unpacker` for options.\n    \"\"\"\n    data = stream.read()\n    return unpackb(data, **kwargs)\n\n\n# alias for compatibility to simplejson/marshal/pickle.\nload = unpack\nloads = unpackb\n\ndump = pack\ndumps = packb\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/msgpack/_version.py",
    "content": "version = (0, 5, 6)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/msgpack/exceptions.py",
    "content": "class UnpackException(Exception):\n    \"\"\"Deprecated.  Use Exception instead to catch all exception during unpacking.\"\"\"\n\n\nclass BufferFull(UnpackException):\n    pass\n\n\nclass OutOfData(UnpackException):\n    pass\n\n\nclass UnpackValueError(UnpackException, ValueError):\n    \"\"\"Deprecated.  Use ValueError instead.\"\"\"\n\n\nclass ExtraData(UnpackValueError):\n    def __init__(self, unpacked, extra):\n        self.unpacked = unpacked\n        self.extra = extra\n\n    def __str__(self):\n        return \"unpack(b) received extra data.\"\n\n\nclass PackException(Exception):\n    \"\"\"Deprecated.  Use Exception instead to catch all exception during packing.\"\"\"\n\n\nclass PackValueError(PackException, ValueError):\n    \"\"\"PackValueError is raised when type of input data is supported but it's value is unsupported.\n\n    Deprecated.  Use ValueError instead.\n    \"\"\"\n\n\nclass PackOverflowError(PackValueError, OverflowError):\n    \"\"\"PackOverflowError is raised when integer value is out of range of msgpack support [-2**31, 2**32).\n\n    Deprecated.  Use ValueError instead.\n    \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/msgpack/fallback.py",
    "content": "\"\"\"Fallback pure Python implementation of msgpack\"\"\"\n\nimport sys\nimport struct\nimport warnings\n\nif sys.version_info[0] == 3:\n    PY3 = True\n    int_types = int\n    Unicode = str\n    xrange = range\n    def dict_iteritems(d):\n        return d.items()\nelse:\n    PY3 = False\n    int_types = (int, long)\n    Unicode = unicode\n    def dict_iteritems(d):\n        return d.iteritems()\n\n\nif hasattr(sys, 'pypy_version_info'):\n    # cStringIO is slow on PyPy, StringIO is faster.  However: PyPy's own\n    # StringBuilder is fastest.\n    from __pypy__ import newlist_hint\n    try:\n        from __pypy__.builders import BytesBuilder as StringBuilder\n    except ImportError:\n        from __pypy__.builders import StringBuilder\n    USING_STRINGBUILDER = True\n    class StringIO(object):\n        def __init__(self, s=b''):\n            if s:\n                self.builder = StringBuilder(len(s))\n                self.builder.append(s)\n            else:\n                self.builder = StringBuilder()\n        def write(self, s):\n            if isinstance(s, memoryview):\n                s = s.tobytes()\n            elif isinstance(s, bytearray):\n                s = bytes(s)\n            self.builder.append(s)\n        def getvalue(self):\n            return self.builder.build()\nelse:\n    USING_STRINGBUILDER = False\n    from io import BytesIO as StringIO\n    newlist_hint = lambda size: []\n\n\nfrom pip._vendor.msgpack.exceptions import (\n    BufferFull,\n    OutOfData,\n    UnpackValueError,\n    PackValueError,\n    PackOverflowError,\n    ExtraData)\n\nfrom pip._vendor.msgpack import ExtType\n\n\nEX_SKIP                 = 0\nEX_CONSTRUCT            = 1\nEX_READ_ARRAY_HEADER    = 2\nEX_READ_MAP_HEADER      = 3\n\nTYPE_IMMEDIATE          = 0\nTYPE_ARRAY              = 1\nTYPE_MAP                = 2\nTYPE_RAW                = 3\nTYPE_BIN                = 4\nTYPE_EXT                = 5\n\nDEFAULT_RECURSE_LIMIT = 511\n\n\ndef _check_type_strict(obj, t, type=type, tuple=tuple):\n    if type(t) is tuple:\n        return type(obj) in t\n    else:\n        return type(obj) is t\n\n\ndef _get_data_from_buffer(obj):\n    try:\n        view = memoryview(obj)\n    except TypeError:\n        # try to use legacy buffer protocol if 2.7, otherwise re-raise\n        if not PY3:\n            view = memoryview(buffer(obj))\n            warnings.warn(\"using old buffer interface to unpack %s; \"\n                          \"this leads to unpacking errors if slicing is used and \"\n                          \"will be removed in a future version\" % type(obj),\n                          RuntimeWarning)\n        else:\n            raise\n    if view.itemsize != 1:\n        raise ValueError(\"cannot unpack from multi-byte object\")\n    return view\n\n\ndef unpack(stream, **kwargs):\n    warnings.warn(\n        \"Direct calling implementation's unpack() is deprecated, Use msgpack.unpack() or unpackb() instead.\",\n        PendingDeprecationWarning)\n    data = stream.read()\n    return unpackb(data, **kwargs)\n\n\ndef unpackb(packed, **kwargs):\n    \"\"\"\n    Unpack an object from `packed`.\n\n    Raises `ExtraData` when `packed` contains extra bytes.\n    See :class:`Unpacker` for options.\n    \"\"\"\n    unpacker = Unpacker(None, **kwargs)\n    unpacker.feed(packed)\n    try:\n        ret = unpacker._unpack()\n    except OutOfData:\n        raise UnpackValueError(\"Data is not enough.\")\n    if unpacker._got_extradata():\n        raise ExtraData(ret, unpacker._get_extradata())\n    return ret\n\n\nclass Unpacker(object):\n    \"\"\"Streaming unpacker.\n\n    arguments:\n\n    :param file_like:\n        File-like object having `.read(n)` method.\n        If specified, unpacker reads serialized data from it and :meth:`feed()` is not usable.\n\n    :param int read_size:\n        Used as `file_like.read(read_size)`. (default: `min(16*1024, max_buffer_size)`)\n\n    :param bool use_list:\n        If true, unpack msgpack array to Python list.\n        Otherwise, unpack to Python tuple. (default: True)\n\n    :param bool raw:\n        If true, unpack msgpack raw to Python bytes (default).\n        Otherwise, unpack to Python str (or unicode on Python 2) by decoding\n        with UTF-8 encoding (recommended).\n        Currently, the default is true, but it will be changed to false in\n        near future.  So you must specify it explicitly for keeping backward\n        compatibility.\n\n        *encoding* option which is deprecated overrides this option.\n\n    :param callable object_hook:\n        When specified, it should be callable.\n        Unpacker calls it with a dict argument after unpacking msgpack map.\n        (See also simplejson)\n\n    :param callable object_pairs_hook:\n        When specified, it should be callable.\n        Unpacker calls it with a list of key-value pairs after unpacking msgpack map.\n        (See also simplejson)\n\n    :param str encoding:\n        Encoding used for decoding msgpack raw.\n        If it is None (default), msgpack raw is deserialized to Python bytes.\n\n    :param str unicode_errors:\n        (deprecated) Used for decoding msgpack raw with *encoding*.\n        (default: `'strict'`)\n\n    :param int max_buffer_size:\n        Limits size of data waiting unpacked.  0 means system's INT_MAX (default).\n        Raises `BufferFull` exception when it is insufficient.\n        You should set this parameter when unpacking data from untrusted source.\n\n    :param int max_str_len:\n        Limits max length of str. (default: 2**31-1)\n\n    :param int max_bin_len:\n        Limits max length of bin. (default: 2**31-1)\n\n    :param int max_array_len:\n        Limits max length of array. (default: 2**31-1)\n\n    :param int max_map_len:\n        Limits max length of map. (default: 2**31-1)\n\n\n    example of streaming deserialize from file-like object::\n\n        unpacker = Unpacker(file_like, raw=False)\n        for o in unpacker:\n            process(o)\n\n    example of streaming deserialize from socket::\n\n        unpacker = Unpacker(raw=False)\n        while True:\n            buf = sock.recv(1024**2)\n            if not buf:\n                break\n            unpacker.feed(buf)\n            for o in unpacker:\n                process(o)\n    \"\"\"\n\n    def __init__(self, file_like=None, read_size=0, use_list=True, raw=True,\n                 object_hook=None, object_pairs_hook=None, list_hook=None,\n                 encoding=None, unicode_errors=None, max_buffer_size=0,\n                 ext_hook=ExtType,\n                 max_str_len=2147483647, # 2**32-1\n                 max_bin_len=2147483647,\n                 max_array_len=2147483647,\n                 max_map_len=2147483647,\n                 max_ext_len=2147483647):\n\n        if encoding is not None:\n            warnings.warn(\n                \"encoding is deprecated, Use raw=False instead.\",\n                PendingDeprecationWarning)\n\n        if unicode_errors is None:\n            unicode_errors = 'strict'\n\n        if file_like is None:\n            self._feeding = True\n        else:\n            if not callable(file_like.read):\n                raise TypeError(\"`file_like.read` must be callable\")\n            self.file_like = file_like\n            self._feeding = False\n\n        #: array of bytes fed.\n        self._buffer = bytearray()\n        # Some very old pythons don't support `struct.unpack_from()` with a\n        # `bytearray`. So we wrap it in a `buffer()` there.\n        if sys.version_info < (2, 7, 6):\n            self._buffer_view = buffer(self._buffer)\n        else:\n            self._buffer_view = self._buffer\n        #: Which position we currently reads\n        self._buff_i = 0\n\n        # When Unpacker is used as an iterable, between the calls to next(),\n        # the buffer is not \"consumed\" completely, for efficiency sake.\n        # Instead, it is done sloppily.  To make sure we raise BufferFull at\n        # the correct moments, we have to keep track of how sloppy we were.\n        # Furthermore, when the buffer is incomplete (that is: in the case\n        # we raise an OutOfData) we need to rollback the buffer to the correct\n        # state, which _buf_checkpoint records.\n        self._buf_checkpoint = 0\n\n        self._max_buffer_size = max_buffer_size or 2**31-1\n        if read_size > self._max_buffer_size:\n            raise ValueError(\"read_size must be smaller than max_buffer_size\")\n        self._read_size = read_size or min(self._max_buffer_size, 16*1024)\n        self._raw = bool(raw)\n        self._encoding = encoding\n        self._unicode_errors = unicode_errors\n        self._use_list = use_list\n        self._list_hook = list_hook\n        self._object_hook = object_hook\n        self._object_pairs_hook = object_pairs_hook\n        self._ext_hook = ext_hook\n        self._max_str_len = max_str_len\n        self._max_bin_len = max_bin_len\n        self._max_array_len = max_array_len\n        self._max_map_len = max_map_len\n        self._max_ext_len = max_ext_len\n        self._stream_offset = 0\n\n        if list_hook is not None and not callable(list_hook):\n            raise TypeError('`list_hook` is not callable')\n        if object_hook is not None and not callable(object_hook):\n            raise TypeError('`object_hook` is not callable')\n        if object_pairs_hook is not None and not callable(object_pairs_hook):\n            raise TypeError('`object_pairs_hook` is not callable')\n        if object_hook is not None and object_pairs_hook is not None:\n            raise TypeError(\"object_pairs_hook and object_hook are mutually \"\n                            \"exclusive\")\n        if not callable(ext_hook):\n            raise TypeError(\"`ext_hook` is not callable\")\n\n    def feed(self, next_bytes):\n        assert self._feeding\n        view = _get_data_from_buffer(next_bytes)\n        if (len(self._buffer) - self._buff_i + len(view) > self._max_buffer_size):\n            raise BufferFull\n\n        # Strip buffer before checkpoint before reading file.\n        if self._buf_checkpoint > 0:\n            del self._buffer[:self._buf_checkpoint]\n            self._buff_i -= self._buf_checkpoint\n            self._buf_checkpoint = 0\n\n        self._buffer += view\n\n    def _consume(self):\n        \"\"\" Gets rid of the used parts of the buffer. \"\"\"\n        self._stream_offset += self._buff_i - self._buf_checkpoint\n        self._buf_checkpoint = self._buff_i\n\n    def _got_extradata(self):\n        return self._buff_i < len(self._buffer)\n\n    def _get_extradata(self):\n        return self._buffer[self._buff_i:]\n\n    def read_bytes(self, n):\n        return self._read(n)\n\n    def _read(self, n):\n        # (int) -> bytearray\n        self._reserve(n)\n        i = self._buff_i\n        self._buff_i = i+n\n        return self._buffer[i:i+n]\n\n    def _reserve(self, n):\n        remain_bytes = len(self._buffer) - self._buff_i - n\n\n        # Fast path: buffer has n bytes already\n        if remain_bytes >= 0:\n            return\n\n        if self._feeding:\n            self._buff_i = self._buf_checkpoint\n            raise OutOfData\n\n        # Strip buffer before checkpoint before reading file.\n        if self._buf_checkpoint > 0:\n            del self._buffer[:self._buf_checkpoint]\n            self._buff_i -= self._buf_checkpoint\n            self._buf_checkpoint = 0\n\n        # Read from file\n        remain_bytes = -remain_bytes\n        while remain_bytes > 0:\n            to_read_bytes = max(self._read_size, remain_bytes)\n            read_data = self.file_like.read(to_read_bytes)\n            if not read_data:\n                break\n            assert isinstance(read_data, bytes)\n            self._buffer += read_data\n            remain_bytes -= len(read_data)\n\n        if len(self._buffer) < n + self._buff_i:\n            self._buff_i = 0  # rollback\n            raise OutOfData\n\n    def _read_header(self, execute=EX_CONSTRUCT):\n        typ = TYPE_IMMEDIATE\n        n = 0\n        obj = None\n        self._reserve(1)\n        b = self._buffer[self._buff_i]\n        self._buff_i += 1\n        if b & 0b10000000 == 0:\n            obj = b\n        elif b & 0b11100000 == 0b11100000:\n            obj = -1 - (b ^ 0xff)\n        elif b & 0b11100000 == 0b10100000:\n            n = b & 0b00011111\n            typ = TYPE_RAW\n            if n > self._max_str_len:\n                raise UnpackValueError(\"%s exceeds max_str_len(%s)\", n, self._max_str_len)\n            obj = self._read(n)\n        elif b & 0b11110000 == 0b10010000:\n            n = b & 0b00001111\n            typ = TYPE_ARRAY\n            if n > self._max_array_len:\n                raise UnpackValueError(\"%s exceeds max_array_len(%s)\", n, self._max_array_len)\n        elif b & 0b11110000 == 0b10000000:\n            n = b & 0b00001111\n            typ = TYPE_MAP\n            if n > self._max_map_len:\n                raise UnpackValueError(\"%s exceeds max_map_len(%s)\", n, self._max_map_len)\n        elif b == 0xc0:\n            obj = None\n        elif b == 0xc2:\n            obj = False\n        elif b == 0xc3:\n            obj = True\n        elif b == 0xc4:\n            typ = TYPE_BIN\n            self._reserve(1)\n            n = self._buffer[self._buff_i]\n            self._buff_i += 1\n            if n > self._max_bin_len:\n                raise UnpackValueError(\"%s exceeds max_bin_len(%s)\" % (n, self._max_bin_len))\n            obj = self._read(n)\n        elif b == 0xc5:\n            typ = TYPE_BIN\n            self._reserve(2)\n            n = struct.unpack_from(\">H\", self._buffer_view, self._buff_i)[0]\n            self._buff_i += 2\n            if n > self._max_bin_len:\n                raise UnpackValueError(\"%s exceeds max_bin_len(%s)\" % (n, self._max_bin_len))\n            obj = self._read(n)\n        elif b == 0xc6:\n            typ = TYPE_BIN\n            self._reserve(4)\n            n = struct.unpack_from(\">I\", self._buffer_view, self._buff_i)[0]\n            self._buff_i += 4\n            if n > self._max_bin_len:\n                raise UnpackValueError(\"%s exceeds max_bin_len(%s)\" % (n, self._max_bin_len))\n            obj = self._read(n)\n        elif b == 0xc7:  # ext 8\n            typ = TYPE_EXT\n            self._reserve(2)\n            L, n = struct.unpack_from('Bb', self._buffer_view, self._buff_i)\n            self._buff_i += 2\n            if L > self._max_ext_len:\n                raise UnpackValueError(\"%s exceeds max_ext_len(%s)\" % (L, self._max_ext_len))\n            obj = self._read(L)\n        elif b == 0xc8:  # ext 16\n            typ = TYPE_EXT\n            self._reserve(3)\n            L, n = struct.unpack_from('>Hb', self._buffer_view, self._buff_i)\n            self._buff_i += 3\n            if L > self._max_ext_len:\n                raise UnpackValueError(\"%s exceeds max_ext_len(%s)\" % (L, self._max_ext_len))\n            obj = self._read(L)\n        elif b == 0xc9:  # ext 32\n            typ = TYPE_EXT\n            self._reserve(5)\n            L, n = struct.unpack_from('>Ib', self._buffer_view, self._buff_i)\n            self._buff_i += 5\n            if L > self._max_ext_len:\n                raise UnpackValueError(\"%s exceeds max_ext_len(%s)\" % (L, self._max_ext_len))\n            obj = self._read(L)\n        elif b == 0xca:\n            self._reserve(4)\n            obj = struct.unpack_from(\">f\", self._buffer_view, self._buff_i)[0]\n            self._buff_i += 4\n        elif b == 0xcb:\n            self._reserve(8)\n            obj = struct.unpack_from(\">d\", self._buffer_view, self._buff_i)[0]\n            self._buff_i += 8\n        elif b == 0xcc:\n            self._reserve(1)\n            obj = self._buffer[self._buff_i]\n            self._buff_i += 1\n        elif b == 0xcd:\n            self._reserve(2)\n            obj = struct.unpack_from(\">H\", self._buffer_view, self._buff_i)[0]\n            self._buff_i += 2\n        elif b == 0xce:\n            self._reserve(4)\n            obj = struct.unpack_from(\">I\", self._buffer_view, self._buff_i)[0]\n            self._buff_i += 4\n        elif b == 0xcf:\n            self._reserve(8)\n            obj = struct.unpack_from(\">Q\", self._buffer_view, self._buff_i)[0]\n            self._buff_i += 8\n        elif b == 0xd0:\n            self._reserve(1)\n            obj = struct.unpack_from(\"b\", self._buffer_view, self._buff_i)[0]\n            self._buff_i += 1\n        elif b == 0xd1:\n            self._reserve(2)\n            obj = struct.unpack_from(\">h\", self._buffer_view, self._buff_i)[0]\n            self._buff_i += 2\n        elif b == 0xd2:\n            self._reserve(4)\n            obj = struct.unpack_from(\">i\", self._buffer_view, self._buff_i)[0]\n            self._buff_i += 4\n        elif b == 0xd3:\n            self._reserve(8)\n            obj = struct.unpack_from(\">q\", self._buffer_view, self._buff_i)[0]\n            self._buff_i += 8\n        elif b == 0xd4:  # fixext 1\n            typ = TYPE_EXT\n            if self._max_ext_len < 1:\n                raise UnpackValueError(\"%s exceeds max_ext_len(%s)\" % (1, self._max_ext_len))\n            self._reserve(2)\n            n, obj = struct.unpack_from(\"b1s\", self._buffer_view, self._buff_i)\n            self._buff_i += 2\n        elif b == 0xd5:  # fixext 2\n            typ = TYPE_EXT\n            if self._max_ext_len < 2:\n                raise UnpackValueError(\"%s exceeds max_ext_len(%s)\" % (2, self._max_ext_len))\n            self._reserve(3)\n            n, obj = struct.unpack_from(\"b2s\", self._buffer_view, self._buff_i)\n            self._buff_i += 3\n        elif b == 0xd6:  # fixext 4\n            typ = TYPE_EXT\n            if self._max_ext_len < 4:\n                raise UnpackValueError(\"%s exceeds max_ext_len(%s)\" % (4, self._max_ext_len))\n            self._reserve(5)\n            n, obj = struct.unpack_from(\"b4s\", self._buffer_view, self._buff_i)\n            self._buff_i += 5\n        elif b == 0xd7:  # fixext 8\n            typ = TYPE_EXT\n            if self._max_ext_len < 8:\n                raise UnpackValueError(\"%s exceeds max_ext_len(%s)\" % (8, self._max_ext_len))\n            self._reserve(9)\n            n, obj = struct.unpack_from(\"b8s\", self._buffer_view, self._buff_i)\n            self._buff_i += 9\n        elif b == 0xd8:  # fixext 16\n            typ = TYPE_EXT\n            if self._max_ext_len < 16:\n                raise UnpackValueError(\"%s exceeds max_ext_len(%s)\" % (16, self._max_ext_len))\n            self._reserve(17)\n            n, obj = struct.unpack_from(\"b16s\", self._buffer_view, self._buff_i)\n            self._buff_i += 17\n        elif b == 0xd9:\n            typ = TYPE_RAW\n            self._reserve(1)\n            n = self._buffer[self._buff_i]\n            self._buff_i += 1\n            if n > self._max_str_len:\n                raise UnpackValueError(\"%s exceeds max_str_len(%s)\", n, self._max_str_len)\n            obj = self._read(n)\n        elif b == 0xda:\n            typ = TYPE_RAW\n            self._reserve(2)\n            n, = struct.unpack_from(\">H\", self._buffer_view, self._buff_i)\n            self._buff_i += 2\n            if n > self._max_str_len:\n                raise UnpackValueError(\"%s exceeds max_str_len(%s)\", n, self._max_str_len)\n            obj = self._read(n)\n        elif b == 0xdb:\n            typ = TYPE_RAW\n            self._reserve(4)\n            n, = struct.unpack_from(\">I\", self._buffer_view, self._buff_i)\n            self._buff_i += 4\n            if n > self._max_str_len:\n                raise UnpackValueError(\"%s exceeds max_str_len(%s)\", n, self._max_str_len)\n            obj = self._read(n)\n        elif b == 0xdc:\n            typ = TYPE_ARRAY\n            self._reserve(2)\n            n, = struct.unpack_from(\">H\", self._buffer_view, self._buff_i)\n            self._buff_i += 2\n            if n > self._max_array_len:\n                raise UnpackValueError(\"%s exceeds max_array_len(%s)\", n, self._max_array_len)\n        elif b == 0xdd:\n            typ = TYPE_ARRAY\n            self._reserve(4)\n            n, = struct.unpack_from(\">I\", self._buffer_view, self._buff_i)\n            self._buff_i += 4\n            if n > self._max_array_len:\n                raise UnpackValueError(\"%s exceeds max_array_len(%s)\", n, self._max_array_len)\n        elif b == 0xde:\n            self._reserve(2)\n            n, = struct.unpack_from(\">H\", self._buffer_view, self._buff_i)\n            self._buff_i += 2\n            if n > self._max_map_len:\n                raise UnpackValueError(\"%s exceeds max_map_len(%s)\", n, self._max_map_len)\n            typ = TYPE_MAP\n        elif b == 0xdf:\n            self._reserve(4)\n            n, = struct.unpack_from(\">I\", self._buffer_view, self._buff_i)\n            self._buff_i += 4\n            if n > self._max_map_len:\n                raise UnpackValueError(\"%s exceeds max_map_len(%s)\", n, self._max_map_len)\n            typ = TYPE_MAP\n        else:\n            raise UnpackValueError(\"Unknown header: 0x%x\" % b)\n        return typ, n, obj\n\n    def _unpack(self, execute=EX_CONSTRUCT):\n        typ, n, obj = self._read_header(execute)\n\n        if execute == EX_READ_ARRAY_HEADER:\n            if typ != TYPE_ARRAY:\n                raise UnpackValueError(\"Expected array\")\n            return n\n        if execute == EX_READ_MAP_HEADER:\n            if typ != TYPE_MAP:\n                raise UnpackValueError(\"Expected map\")\n            return n\n        # TODO should we eliminate the recursion?\n        if typ == TYPE_ARRAY:\n            if execute == EX_SKIP:\n                for i in xrange(n):\n                    # TODO check whether we need to call `list_hook`\n                    self._unpack(EX_SKIP)\n                return\n            ret = newlist_hint(n)\n            for i in xrange(n):\n                ret.append(self._unpack(EX_CONSTRUCT))\n            if self._list_hook is not None:\n                ret = self._list_hook(ret)\n            # TODO is the interaction between `list_hook` and `use_list` ok?\n            return ret if self._use_list else tuple(ret)\n        if typ == TYPE_MAP:\n            if execute == EX_SKIP:\n                for i in xrange(n):\n                    # TODO check whether we need to call hooks\n                    self._unpack(EX_SKIP)\n                    self._unpack(EX_SKIP)\n                return\n            if self._object_pairs_hook is not None:\n                ret = self._object_pairs_hook(\n                    (self._unpack(EX_CONSTRUCT),\n                     self._unpack(EX_CONSTRUCT))\n                    for _ in xrange(n))\n            else:\n                ret = {}\n                for _ in xrange(n):\n                    key = self._unpack(EX_CONSTRUCT)\n                    ret[key] = self._unpack(EX_CONSTRUCT)\n                if self._object_hook is not None:\n                    ret = self._object_hook(ret)\n            return ret\n        if execute == EX_SKIP:\n            return\n        if typ == TYPE_RAW:\n            if self._encoding is not None:\n                obj = obj.decode(self._encoding, self._unicode_errors)\n            elif self._raw:\n                obj = bytes(obj)\n            else:\n                obj = obj.decode('utf_8')\n            return obj\n        if typ == TYPE_EXT:\n            return self._ext_hook(n, bytes(obj))\n        if typ == TYPE_BIN:\n            return bytes(obj)\n        assert typ == TYPE_IMMEDIATE\n        return obj\n\n    def __iter__(self):\n        return self\n\n    def __next__(self):\n        try:\n            ret = self._unpack(EX_CONSTRUCT)\n            self._consume()\n            return ret\n        except OutOfData:\n            self._consume()\n            raise StopIteration\n\n    next = __next__\n\n    def skip(self, write_bytes=None):\n        self._unpack(EX_SKIP)\n        if write_bytes is not None:\n            warnings.warn(\"`write_bytes` option is deprecated.  Use `.tell()` instead.\", DeprecationWarning)\n            write_bytes(self._buffer[self._buf_checkpoint:self._buff_i])\n        self._consume()\n\n    def unpack(self, write_bytes=None):\n        ret = self._unpack(EX_CONSTRUCT)\n        if write_bytes is not None:\n            warnings.warn(\"`write_bytes` option is deprecated.  Use `.tell()` instead.\", DeprecationWarning)\n            write_bytes(self._buffer[self._buf_checkpoint:self._buff_i])\n        self._consume()\n        return ret\n\n    def read_array_header(self, write_bytes=None):\n        ret = self._unpack(EX_READ_ARRAY_HEADER)\n        if write_bytes is not None:\n            warnings.warn(\"`write_bytes` option is deprecated.  Use `.tell()` instead.\", DeprecationWarning)\n            write_bytes(self._buffer[self._buf_checkpoint:self._buff_i])\n        self._consume()\n        return ret\n\n    def read_map_header(self, write_bytes=None):\n        ret = self._unpack(EX_READ_MAP_HEADER)\n        if write_bytes is not None:\n            warnings.warn(\"`write_bytes` option is deprecated.  Use `.tell()` instead.\", DeprecationWarning)\n            write_bytes(self._buffer[self._buf_checkpoint:self._buff_i])\n        self._consume()\n        return ret\n\n    def tell(self):\n        return self._stream_offset\n\n\nclass Packer(object):\n    \"\"\"\n    MessagePack Packer\n\n    usage:\n\n        packer = Packer()\n        astream.write(packer.pack(a))\n        astream.write(packer.pack(b))\n\n    Packer's constructor has some keyword arguments:\n\n    :param callable default:\n        Convert user type to builtin type that Packer supports.\n        See also simplejson's document.\n\n    :param bool use_single_float:\n        Use single precision float type for float. (default: False)\n\n    :param bool autoreset:\n        Reset buffer after each pack and return its content as `bytes`. (default: True).\n        If set this to false, use `bytes()` to get content and `.reset()` to clear buffer.\n\n    :param bool use_bin_type:\n        Use bin type introduced in msgpack spec 2.0 for bytes.\n        It also enables str8 type for unicode.\n\n    :param bool strict_types:\n        If set to true, types will be checked to be exact. Derived classes\n        from serializeable types will not be serialized and will be\n        treated as unsupported type and forwarded to default.\n        Additionally tuples will not be serialized as lists.\n        This is useful when trying to implement accurate serialization\n        for python types.\n\n    :param str encoding:\n        (deprecated) Convert unicode to bytes with this encoding. (default: 'utf-8')\n\n    :param str unicode_errors:\n        Error handler for encoding unicode. (default: 'strict')\n    \"\"\"\n    def __init__(self, default=None, encoding=None, unicode_errors=None,\n                 use_single_float=False, autoreset=True, use_bin_type=False,\n                 strict_types=False):\n        if encoding is None:\n            encoding = 'utf_8'\n        else:\n            warnings.warn(\n                \"encoding is deprecated, Use raw=False instead.\",\n                PendingDeprecationWarning)\n\n        if unicode_errors is None:\n            unicode_errors = 'strict'\n\n        self._strict_types = strict_types\n        self._use_float = use_single_float\n        self._autoreset = autoreset\n        self._use_bin_type = use_bin_type\n        self._encoding = encoding\n        self._unicode_errors = unicode_errors\n        self._buffer = StringIO()\n        if default is not None:\n            if not callable(default):\n                raise TypeError(\"default must be callable\")\n        self._default = default\n\n    def _pack(self, obj, nest_limit=DEFAULT_RECURSE_LIMIT,\n              check=isinstance, check_type_strict=_check_type_strict):\n        default_used = False\n        if self._strict_types:\n            check = check_type_strict\n            list_types = list\n        else:\n            list_types = (list, tuple)\n        while True:\n            if nest_limit < 0:\n                raise PackValueError(\"recursion limit exceeded\")\n            if obj is None:\n                return self._buffer.write(b\"\\xc0\")\n            if check(obj, bool):\n                if obj:\n                    return self._buffer.write(b\"\\xc3\")\n                return self._buffer.write(b\"\\xc2\")\n            if check(obj, int_types):\n                if 0 <= obj < 0x80:\n                    return self._buffer.write(struct.pack(\"B\", obj))\n                if -0x20 <= obj < 0:\n                    return self._buffer.write(struct.pack(\"b\", obj))\n                if 0x80 <= obj <= 0xff:\n                    return self._buffer.write(struct.pack(\"BB\", 0xcc, obj))\n                if -0x80 <= obj < 0:\n                    return self._buffer.write(struct.pack(\">Bb\", 0xd0, obj))\n                if 0xff < obj <= 0xffff:\n                    return self._buffer.write(struct.pack(\">BH\", 0xcd, obj))\n                if -0x8000 <= obj < -0x80:\n                    return self._buffer.write(struct.pack(\">Bh\", 0xd1, obj))\n                if 0xffff < obj <= 0xffffffff:\n                    return self._buffer.write(struct.pack(\">BI\", 0xce, obj))\n                if -0x80000000 <= obj < -0x8000:\n                    return self._buffer.write(struct.pack(\">Bi\", 0xd2, obj))\n                if 0xffffffff < obj <= 0xffffffffffffffff:\n                    return self._buffer.write(struct.pack(\">BQ\", 0xcf, obj))\n                if -0x8000000000000000 <= obj < -0x80000000:\n                    return self._buffer.write(struct.pack(\">Bq\", 0xd3, obj))\n                if not default_used and self._default is not None:\n                    obj = self._default(obj)\n                    default_used = True\n                    continue\n                raise PackOverflowError(\"Integer value out of range\")\n            if check(obj, (bytes, bytearray)):\n                n = len(obj)\n                if n >= 2**32:\n                    raise PackValueError(\"%s is too large\" % type(obj).__name__)\n                self._pack_bin_header(n)\n                return self._buffer.write(obj)\n            if check(obj, Unicode):\n                if self._encoding is None:\n                    raise TypeError(\n                        \"Can't encode unicode string: \"\n                        \"no encoding is specified\")\n                obj = obj.encode(self._encoding, self._unicode_errors)\n                n = len(obj)\n                if n >= 2**32:\n                    raise PackValueError(\"String is too large\")\n                self._pack_raw_header(n)\n                return self._buffer.write(obj)\n            if check(obj, memoryview):\n                n = len(obj) * obj.itemsize\n                if n >= 2**32:\n                    raise PackValueError(\"Memoryview is too large\")\n                self._pack_bin_header(n)\n                return self._buffer.write(obj)\n            if check(obj, float):\n                if self._use_float:\n                    return self._buffer.write(struct.pack(\">Bf\", 0xca, obj))\n                return self._buffer.write(struct.pack(\">Bd\", 0xcb, obj))\n            if check(obj, ExtType):\n                code = obj.code\n                data = obj.data\n                assert isinstance(code, int)\n                assert isinstance(data, bytes)\n                L = len(data)\n                if L == 1:\n                    self._buffer.write(b'\\xd4')\n                elif L == 2:\n                    self._buffer.write(b'\\xd5')\n                elif L == 4:\n                    self._buffer.write(b'\\xd6')\n                elif L == 8:\n                    self._buffer.write(b'\\xd7')\n                elif L == 16:\n                    self._buffer.write(b'\\xd8')\n                elif L <= 0xff:\n                    self._buffer.write(struct.pack(\">BB\", 0xc7, L))\n                elif L <= 0xffff:\n                    self._buffer.write(struct.pack(\">BH\", 0xc8, L))\n                else:\n                    self._buffer.write(struct.pack(\">BI\", 0xc9, L))\n                self._buffer.write(struct.pack(\"b\", code))\n                self._buffer.write(data)\n                return\n            if check(obj, list_types):\n                n = len(obj)\n                self._pack_array_header(n)\n                for i in xrange(n):\n                    self._pack(obj[i], nest_limit - 1)\n                return\n            if check(obj, dict):\n                return self._pack_map_pairs(len(obj), dict_iteritems(obj),\n                                               nest_limit - 1)\n            if not default_used and self._default is not None:\n                obj = self._default(obj)\n                default_used = 1\n                continue\n            raise TypeError(\"Cannot serialize %r\" % (obj, ))\n\n    def pack(self, obj):\n        try:\n            self._pack(obj)\n        except:\n            self._buffer = StringIO()  # force reset\n            raise\n        ret = self._buffer.getvalue()\n        if self._autoreset:\n            self._buffer = StringIO()\n        elif USING_STRINGBUILDER:\n            self._buffer = StringIO(ret)\n        return ret\n\n    def pack_map_pairs(self, pairs):\n        self._pack_map_pairs(len(pairs), pairs)\n        ret = self._buffer.getvalue()\n        if self._autoreset:\n            self._buffer = StringIO()\n        elif USING_STRINGBUILDER:\n            self._buffer = StringIO(ret)\n        return ret\n\n    def pack_array_header(self, n):\n        if n >= 2**32:\n            raise PackValueError\n        self._pack_array_header(n)\n        ret = self._buffer.getvalue()\n        if self._autoreset:\n            self._buffer = StringIO()\n        elif USING_STRINGBUILDER:\n            self._buffer = StringIO(ret)\n        return ret\n\n    def pack_map_header(self, n):\n        if n >= 2**32:\n            raise PackValueError\n        self._pack_map_header(n)\n        ret = self._buffer.getvalue()\n        if self._autoreset:\n            self._buffer = StringIO()\n        elif USING_STRINGBUILDER:\n            self._buffer = StringIO(ret)\n        return ret\n\n    def pack_ext_type(self, typecode, data):\n        if not isinstance(typecode, int):\n            raise TypeError(\"typecode must have int type.\")\n        if not 0 <= typecode <= 127:\n            raise ValueError(\"typecode should be 0-127\")\n        if not isinstance(data, bytes):\n            raise TypeError(\"data must have bytes type\")\n        L = len(data)\n        if L > 0xffffffff:\n            raise PackValueError(\"Too large data\")\n        if L == 1:\n            self._buffer.write(b'\\xd4')\n        elif L == 2:\n            self._buffer.write(b'\\xd5')\n        elif L == 4:\n            self._buffer.write(b'\\xd6')\n        elif L == 8:\n            self._buffer.write(b'\\xd7')\n        elif L == 16:\n            self._buffer.write(b'\\xd8')\n        elif L <= 0xff:\n            self._buffer.write(b'\\xc7' + struct.pack('B', L))\n        elif L <= 0xffff:\n            self._buffer.write(b'\\xc8' + struct.pack('>H', L))\n        else:\n            self._buffer.write(b'\\xc9' + struct.pack('>I', L))\n        self._buffer.write(struct.pack('B', typecode))\n        self._buffer.write(data)\n\n    def _pack_array_header(self, n):\n        if n <= 0x0f:\n            return self._buffer.write(struct.pack('B', 0x90 + n))\n        if n <= 0xffff:\n            return self._buffer.write(struct.pack(\">BH\", 0xdc, n))\n        if n <= 0xffffffff:\n            return self._buffer.write(struct.pack(\">BI\", 0xdd, n))\n        raise PackValueError(\"Array is too large\")\n\n    def _pack_map_header(self, n):\n        if n <= 0x0f:\n            return self._buffer.write(struct.pack('B', 0x80 + n))\n        if n <= 0xffff:\n            return self._buffer.write(struct.pack(\">BH\", 0xde, n))\n        if n <= 0xffffffff:\n            return self._buffer.write(struct.pack(\">BI\", 0xdf, n))\n        raise PackValueError(\"Dict is too large\")\n\n    def _pack_map_pairs(self, n, pairs, nest_limit=DEFAULT_RECURSE_LIMIT):\n        self._pack_map_header(n)\n        for (k, v) in pairs:\n            self._pack(k, nest_limit - 1)\n            self._pack(v, nest_limit - 1)\n\n    def _pack_raw_header(self, n):\n        if n <= 0x1f:\n            self._buffer.write(struct.pack('B', 0xa0 + n))\n        elif self._use_bin_type and n <= 0xff:\n            self._buffer.write(struct.pack('>BB', 0xd9, n))\n        elif n <= 0xffff:\n            self._buffer.write(struct.pack(\">BH\", 0xda, n))\n        elif n <= 0xffffffff:\n            self._buffer.write(struct.pack(\">BI\", 0xdb, n))\n        else:\n            raise PackValueError('Raw is too large')\n\n    def _pack_bin_header(self, n):\n        if not self._use_bin_type:\n            return self._pack_raw_header(n)\n        elif n <= 0xff:\n            return self._buffer.write(struct.pack('>BB', 0xc4, n))\n        elif n <= 0xffff:\n            return self._buffer.write(struct.pack(\">BH\", 0xc5, n))\n        elif n <= 0xffffffff:\n            return self._buffer.write(struct.pack(\">BI\", 0xc6, n))\n        else:\n            raise PackValueError('Bin is too large')\n\n    def bytes(self):\n        return self._buffer.getvalue()\n\n    def reset(self):\n        self._buffer = StringIO()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/packaging/__about__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\nfrom __future__ import absolute_import, division, print_function\n\n__all__ = [\n    \"__title__\",\n    \"__summary__\",\n    \"__uri__\",\n    \"__version__\",\n    \"__author__\",\n    \"__email__\",\n    \"__license__\",\n    \"__copyright__\",\n]\n\n__title__ = \"packaging\"\n__summary__ = \"Core utilities for Python packages\"\n__uri__ = \"https://github.com/pypa/packaging\"\n\n__version__ = \"19.0\"\n\n__author__ = \"Donald Stufft and individual contributors\"\n__email__ = \"donald@stufft.io\"\n\n__license__ = \"BSD or Apache License, Version 2.0\"\n__copyright__ = \"Copyright 2014-2019 %s\" % __author__\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/packaging/__init__.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\nfrom __future__ import absolute_import, division, print_function\n\nfrom .__about__ import (\n    __author__,\n    __copyright__,\n    __email__,\n    __license__,\n    __summary__,\n    __title__,\n    __uri__,\n    __version__,\n)\n\n__all__ = [\n    \"__title__\",\n    \"__summary__\",\n    \"__uri__\",\n    \"__version__\",\n    \"__author__\",\n    \"__email__\",\n    \"__license__\",\n    \"__copyright__\",\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/packaging/_compat.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\nfrom __future__ import absolute_import, division, print_function\n\nimport sys\n\n\nPY2 = sys.version_info[0] == 2\nPY3 = sys.version_info[0] == 3\n\n# flake8: noqa\n\nif PY3:\n    string_types = (str,)\nelse:\n    string_types = (basestring,)\n\n\ndef with_metaclass(meta, *bases):\n    \"\"\"\n    Create a base class with a metaclass.\n    \"\"\"\n    # This requires a bit of explanation: the basic idea is to make a dummy\n    # metaclass for one level of class instantiation that replaces itself with\n    # the actual metaclass.\n    class metaclass(meta):\n        def __new__(cls, name, this_bases, d):\n            return meta(name, bases, d)\n\n    return type.__new__(metaclass, \"temporary_class\", (), {})\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/packaging/_structures.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\nfrom __future__ import absolute_import, division, print_function\n\n\nclass Infinity(object):\n    def __repr__(self):\n        return \"Infinity\"\n\n    def __hash__(self):\n        return hash(repr(self))\n\n    def __lt__(self, other):\n        return False\n\n    def __le__(self, other):\n        return False\n\n    def __eq__(self, other):\n        return isinstance(other, self.__class__)\n\n    def __ne__(self, other):\n        return not isinstance(other, self.__class__)\n\n    def __gt__(self, other):\n        return True\n\n    def __ge__(self, other):\n        return True\n\n    def __neg__(self):\n        return NegativeInfinity\n\n\nInfinity = Infinity()\n\n\nclass NegativeInfinity(object):\n    def __repr__(self):\n        return \"-Infinity\"\n\n    def __hash__(self):\n        return hash(repr(self))\n\n    def __lt__(self, other):\n        return True\n\n    def __le__(self, other):\n        return True\n\n    def __eq__(self, other):\n        return isinstance(other, self.__class__)\n\n    def __ne__(self, other):\n        return not isinstance(other, self.__class__)\n\n    def __gt__(self, other):\n        return False\n\n    def __ge__(self, other):\n        return False\n\n    def __neg__(self):\n        return Infinity\n\n\nNegativeInfinity = NegativeInfinity()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/packaging/markers.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\nfrom __future__ import absolute_import, division, print_function\n\nimport operator\nimport os\nimport platform\nimport sys\n\nfrom pip._vendor.pyparsing import ParseException, ParseResults, stringStart, stringEnd\nfrom pip._vendor.pyparsing import ZeroOrMore, Group, Forward, QuotedString\nfrom pip._vendor.pyparsing import Literal as L  # noqa\n\nfrom ._compat import string_types\nfrom .specifiers import Specifier, InvalidSpecifier\n\n\n__all__ = [\n    \"InvalidMarker\",\n    \"UndefinedComparison\",\n    \"UndefinedEnvironmentName\",\n    \"Marker\",\n    \"default_environment\",\n]\n\n\nclass InvalidMarker(ValueError):\n    \"\"\"\n    An invalid marker was found, users should refer to PEP 508.\n    \"\"\"\n\n\nclass UndefinedComparison(ValueError):\n    \"\"\"\n    An invalid operation was attempted on a value that doesn't support it.\n    \"\"\"\n\n\nclass UndefinedEnvironmentName(ValueError):\n    \"\"\"\n    A name was attempted to be used that does not exist inside of the\n    environment.\n    \"\"\"\n\n\nclass Node(object):\n    def __init__(self, value):\n        self.value = value\n\n    def __str__(self):\n        return str(self.value)\n\n    def __repr__(self):\n        return \"<{0}({1!r})>\".format(self.__class__.__name__, str(self))\n\n    def serialize(self):\n        raise NotImplementedError\n\n\nclass Variable(Node):\n    def serialize(self):\n        return str(self)\n\n\nclass Value(Node):\n    def serialize(self):\n        return '\"{0}\"'.format(self)\n\n\nclass Op(Node):\n    def serialize(self):\n        return str(self)\n\n\nVARIABLE = (\n    L(\"implementation_version\")\n    | L(\"platform_python_implementation\")\n    | L(\"implementation_name\")\n    | L(\"python_full_version\")\n    | L(\"platform_release\")\n    | L(\"platform_version\")\n    | L(\"platform_machine\")\n    | L(\"platform_system\")\n    | L(\"python_version\")\n    | L(\"sys_platform\")\n    | L(\"os_name\")\n    | L(\"os.name\")\n    | L(\"sys.platform\")  # PEP-345\n    | L(\"platform.version\")  # PEP-345\n    | L(\"platform.machine\")  # PEP-345\n    | L(\"platform.python_implementation\")  # PEP-345\n    | L(\"python_implementation\")  # PEP-345\n    | L(\"extra\")  # undocumented setuptools legacy\n)\nALIASES = {\n    \"os.name\": \"os_name\",\n    \"sys.platform\": \"sys_platform\",\n    \"platform.version\": \"platform_version\",\n    \"platform.machine\": \"platform_machine\",\n    \"platform.python_implementation\": \"platform_python_implementation\",\n    \"python_implementation\": \"platform_python_implementation\",\n}\nVARIABLE.setParseAction(lambda s, l, t: Variable(ALIASES.get(t[0], t[0])))\n\nVERSION_CMP = (\n    L(\"===\") | L(\"==\") | L(\">=\") | L(\"<=\") | L(\"!=\") | L(\"~=\") | L(\">\") | L(\"<\")\n)\n\nMARKER_OP = VERSION_CMP | L(\"not in\") | L(\"in\")\nMARKER_OP.setParseAction(lambda s, l, t: Op(t[0]))\n\nMARKER_VALUE = QuotedString(\"'\") | QuotedString('\"')\nMARKER_VALUE.setParseAction(lambda s, l, t: Value(t[0]))\n\nBOOLOP = L(\"and\") | L(\"or\")\n\nMARKER_VAR = VARIABLE | MARKER_VALUE\n\nMARKER_ITEM = Group(MARKER_VAR + MARKER_OP + MARKER_VAR)\nMARKER_ITEM.setParseAction(lambda s, l, t: tuple(t[0]))\n\nLPAREN = L(\"(\").suppress()\nRPAREN = L(\")\").suppress()\n\nMARKER_EXPR = Forward()\nMARKER_ATOM = MARKER_ITEM | Group(LPAREN + MARKER_EXPR + RPAREN)\nMARKER_EXPR << MARKER_ATOM + ZeroOrMore(BOOLOP + MARKER_EXPR)\n\nMARKER = stringStart + MARKER_EXPR + stringEnd\n\n\ndef _coerce_parse_result(results):\n    if isinstance(results, ParseResults):\n        return [_coerce_parse_result(i) for i in results]\n    else:\n        return results\n\n\ndef _format_marker(marker, first=True):\n    assert isinstance(marker, (list, tuple, string_types))\n\n    # Sometimes we have a structure like [[...]] which is a single item list\n    # where the single item is itself it's own list. In that case we want skip\n    # the rest of this function so that we don't get extraneous () on the\n    # outside.\n    if (\n        isinstance(marker, list)\n        and len(marker) == 1\n        and isinstance(marker[0], (list, tuple))\n    ):\n        return _format_marker(marker[0])\n\n    if isinstance(marker, list):\n        inner = (_format_marker(m, first=False) for m in marker)\n        if first:\n            return \" \".join(inner)\n        else:\n            return \"(\" + \" \".join(inner) + \")\"\n    elif isinstance(marker, tuple):\n        return \" \".join([m.serialize() for m in marker])\n    else:\n        return marker\n\n\n_operators = {\n    \"in\": lambda lhs, rhs: lhs in rhs,\n    \"not in\": lambda lhs, rhs: lhs not in rhs,\n    \"<\": operator.lt,\n    \"<=\": operator.le,\n    \"==\": operator.eq,\n    \"!=\": operator.ne,\n    \">=\": operator.ge,\n    \">\": operator.gt,\n}\n\n\ndef _eval_op(lhs, op, rhs):\n    try:\n        spec = Specifier(\"\".join([op.serialize(), rhs]))\n    except InvalidSpecifier:\n        pass\n    else:\n        return spec.contains(lhs)\n\n    oper = _operators.get(op.serialize())\n    if oper is None:\n        raise UndefinedComparison(\n            \"Undefined {0!r} on {1!r} and {2!r}.\".format(op, lhs, rhs)\n        )\n\n    return oper(lhs, rhs)\n\n\n_undefined = object()\n\n\ndef _get_env(environment, name):\n    value = environment.get(name, _undefined)\n\n    if value is _undefined:\n        raise UndefinedEnvironmentName(\n            \"{0!r} does not exist in evaluation environment.\".format(name)\n        )\n\n    return value\n\n\ndef _evaluate_markers(markers, environment):\n    groups = [[]]\n\n    for marker in markers:\n        assert isinstance(marker, (list, tuple, string_types))\n\n        if isinstance(marker, list):\n            groups[-1].append(_evaluate_markers(marker, environment))\n        elif isinstance(marker, tuple):\n            lhs, op, rhs = marker\n\n            if isinstance(lhs, Variable):\n                lhs_value = _get_env(environment, lhs.value)\n                rhs_value = rhs.value\n            else:\n                lhs_value = lhs.value\n                rhs_value = _get_env(environment, rhs.value)\n\n            groups[-1].append(_eval_op(lhs_value, op, rhs_value))\n        else:\n            assert marker in [\"and\", \"or\"]\n            if marker == \"or\":\n                groups.append([])\n\n    return any(all(item) for item in groups)\n\n\ndef format_full_version(info):\n    version = \"{0.major}.{0.minor}.{0.micro}\".format(info)\n    kind = info.releaselevel\n    if kind != \"final\":\n        version += kind[0] + str(info.serial)\n    return version\n\n\ndef default_environment():\n    if hasattr(sys, \"implementation\"):\n        iver = format_full_version(sys.implementation.version)\n        implementation_name = sys.implementation.name\n    else:\n        iver = \"0\"\n        implementation_name = \"\"\n\n    return {\n        \"implementation_name\": implementation_name,\n        \"implementation_version\": iver,\n        \"os_name\": os.name,\n        \"platform_machine\": platform.machine(),\n        \"platform_release\": platform.release(),\n        \"platform_system\": platform.system(),\n        \"platform_version\": platform.version(),\n        \"python_full_version\": platform.python_version(),\n        \"platform_python_implementation\": platform.python_implementation(),\n        \"python_version\": platform.python_version()[:3],\n        \"sys_platform\": sys.platform,\n    }\n\n\nclass Marker(object):\n    def __init__(self, marker):\n        try:\n            self._markers = _coerce_parse_result(MARKER.parseString(marker))\n        except ParseException as e:\n            err_str = \"Invalid marker: {0!r}, parse error at {1!r}\".format(\n                marker, marker[e.loc : e.loc + 8]\n            )\n            raise InvalidMarker(err_str)\n\n    def __str__(self):\n        return _format_marker(self._markers)\n\n    def __repr__(self):\n        return \"<Marker({0!r})>\".format(str(self))\n\n    def evaluate(self, environment=None):\n        \"\"\"Evaluate a marker.\n\n        Return the boolean from evaluating the given marker against the\n        environment. environment is an optional argument to override all or\n        part of the determined environment.\n\n        The environment is determined from the current Python process.\n        \"\"\"\n        current_environment = default_environment()\n        if environment is not None:\n            current_environment.update(environment)\n\n        return _evaluate_markers(self._markers, current_environment)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/packaging/requirements.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\nfrom __future__ import absolute_import, division, print_function\n\nimport string\nimport re\n\nfrom pip._vendor.pyparsing import stringStart, stringEnd, originalTextFor, ParseException\nfrom pip._vendor.pyparsing import ZeroOrMore, Word, Optional, Regex, Combine\nfrom pip._vendor.pyparsing import Literal as L  # noqa\nfrom pip._vendor.six.moves.urllib import parse as urlparse\n\nfrom .markers import MARKER_EXPR, Marker\nfrom .specifiers import LegacySpecifier, Specifier, SpecifierSet\n\n\nclass InvalidRequirement(ValueError):\n    \"\"\"\n    An invalid requirement was found, users should refer to PEP 508.\n    \"\"\"\n\n\nALPHANUM = Word(string.ascii_letters + string.digits)\n\nLBRACKET = L(\"[\").suppress()\nRBRACKET = L(\"]\").suppress()\nLPAREN = L(\"(\").suppress()\nRPAREN = L(\")\").suppress()\nCOMMA = L(\",\").suppress()\nSEMICOLON = L(\";\").suppress()\nAT = L(\"@\").suppress()\n\nPUNCTUATION = Word(\"-_.\")\nIDENTIFIER_END = ALPHANUM | (ZeroOrMore(PUNCTUATION) + ALPHANUM)\nIDENTIFIER = Combine(ALPHANUM + ZeroOrMore(IDENTIFIER_END))\n\nNAME = IDENTIFIER(\"name\")\nEXTRA = IDENTIFIER\n\nURI = Regex(r\"[^ ]+\")(\"url\")\nURL = AT + URI\n\nEXTRAS_LIST = EXTRA + ZeroOrMore(COMMA + EXTRA)\nEXTRAS = (LBRACKET + Optional(EXTRAS_LIST) + RBRACKET)(\"extras\")\n\nVERSION_PEP440 = Regex(Specifier._regex_str, re.VERBOSE | re.IGNORECASE)\nVERSION_LEGACY = Regex(LegacySpecifier._regex_str, re.VERBOSE | re.IGNORECASE)\n\nVERSION_ONE = VERSION_PEP440 ^ VERSION_LEGACY\nVERSION_MANY = Combine(\n    VERSION_ONE + ZeroOrMore(COMMA + VERSION_ONE), joinString=\",\", adjacent=False\n)(\"_raw_spec\")\n_VERSION_SPEC = Optional(((LPAREN + VERSION_MANY + RPAREN) | VERSION_MANY))\n_VERSION_SPEC.setParseAction(lambda s, l, t: t._raw_spec or \"\")\n\nVERSION_SPEC = originalTextFor(_VERSION_SPEC)(\"specifier\")\nVERSION_SPEC.setParseAction(lambda s, l, t: t[1])\n\nMARKER_EXPR = originalTextFor(MARKER_EXPR())(\"marker\")\nMARKER_EXPR.setParseAction(\n    lambda s, l, t: Marker(s[t._original_start : t._original_end])\n)\nMARKER_SEPARATOR = SEMICOLON\nMARKER = MARKER_SEPARATOR + MARKER_EXPR\n\nVERSION_AND_MARKER = VERSION_SPEC + Optional(MARKER)\nURL_AND_MARKER = URL + Optional(MARKER)\n\nNAMED_REQUIREMENT = NAME + Optional(EXTRAS) + (URL_AND_MARKER | VERSION_AND_MARKER)\n\nREQUIREMENT = stringStart + NAMED_REQUIREMENT + stringEnd\n# pyparsing isn't thread safe during initialization, so we do it eagerly, see\n# issue #104\nREQUIREMENT.parseString(\"x[]\")\n\n\nclass Requirement(object):\n    \"\"\"Parse a requirement.\n\n    Parse a given requirement string into its parts, such as name, specifier,\n    URL, and extras. Raises InvalidRequirement on a badly-formed requirement\n    string.\n    \"\"\"\n\n    # TODO: Can we test whether something is contained within a requirement?\n    #       If so how do we do that? Do we need to test against the _name_ of\n    #       the thing as well as the version? What about the markers?\n    # TODO: Can we normalize the name and extra name?\n\n    def __init__(self, requirement_string):\n        try:\n            req = REQUIREMENT.parseString(requirement_string)\n        except ParseException as e:\n            raise InvalidRequirement(\n                'Parse error at \"{0!r}\": {1}'.format(\n                    requirement_string[e.loc : e.loc + 8], e.msg\n                )\n            )\n\n        self.name = req.name\n        if req.url:\n            parsed_url = urlparse.urlparse(req.url)\n            if parsed_url.scheme == \"file\":\n                if urlparse.urlunparse(parsed_url) != req.url:\n                    raise InvalidRequirement(\"Invalid URL given\")\n            elif not (parsed_url.scheme and parsed_url.netloc) or (\n                not parsed_url.scheme and not parsed_url.netloc\n            ):\n                raise InvalidRequirement(\"Invalid URL: {0}\".format(req.url))\n            self.url = req.url\n        else:\n            self.url = None\n        self.extras = set(req.extras.asList() if req.extras else [])\n        self.specifier = SpecifierSet(req.specifier)\n        self.marker = req.marker if req.marker else None\n\n    def __str__(self):\n        parts = [self.name]\n\n        if self.extras:\n            parts.append(\"[{0}]\".format(\",\".join(sorted(self.extras))))\n\n        if self.specifier:\n            parts.append(str(self.specifier))\n\n        if self.url:\n            parts.append(\"@ {0}\".format(self.url))\n            if self.marker:\n                parts.append(\" \")\n\n        if self.marker:\n            parts.append(\"; {0}\".format(self.marker))\n\n        return \"\".join(parts)\n\n    def __repr__(self):\n        return \"<Requirement({0!r})>\".format(str(self))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/packaging/specifiers.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\nfrom __future__ import absolute_import, division, print_function\n\nimport abc\nimport functools\nimport itertools\nimport re\n\nfrom ._compat import string_types, with_metaclass\nfrom .version import Version, LegacyVersion, parse\n\n\nclass InvalidSpecifier(ValueError):\n    \"\"\"\n    An invalid specifier was found, users should refer to PEP 440.\n    \"\"\"\n\n\nclass BaseSpecifier(with_metaclass(abc.ABCMeta, object)):\n    @abc.abstractmethod\n    def __str__(self):\n        \"\"\"\n        Returns the str representation of this Specifier like object. This\n        should be representative of the Specifier itself.\n        \"\"\"\n\n    @abc.abstractmethod\n    def __hash__(self):\n        \"\"\"\n        Returns a hash value for this Specifier like object.\n        \"\"\"\n\n    @abc.abstractmethod\n    def __eq__(self, other):\n        \"\"\"\n        Returns a boolean representing whether or not the two Specifier like\n        objects are equal.\n        \"\"\"\n\n    @abc.abstractmethod\n    def __ne__(self, other):\n        \"\"\"\n        Returns a boolean representing whether or not the two Specifier like\n        objects are not equal.\n        \"\"\"\n\n    @abc.abstractproperty\n    def prereleases(self):\n        \"\"\"\n        Returns whether or not pre-releases as a whole are allowed by this\n        specifier.\n        \"\"\"\n\n    @prereleases.setter\n    def prereleases(self, value):\n        \"\"\"\n        Sets whether or not pre-releases as a whole are allowed by this\n        specifier.\n        \"\"\"\n\n    @abc.abstractmethod\n    def contains(self, item, prereleases=None):\n        \"\"\"\n        Determines if the given item is contained within this specifier.\n        \"\"\"\n\n    @abc.abstractmethod\n    def filter(self, iterable, prereleases=None):\n        \"\"\"\n        Takes an iterable of items and filters them so that only items which\n        are contained within this specifier are allowed in it.\n        \"\"\"\n\n\nclass _IndividualSpecifier(BaseSpecifier):\n\n    _operators = {}\n\n    def __init__(self, spec=\"\", prereleases=None):\n        match = self._regex.search(spec)\n        if not match:\n            raise InvalidSpecifier(\"Invalid specifier: '{0}'\".format(spec))\n\n        self._spec = (match.group(\"operator\").strip(), match.group(\"version\").strip())\n\n        # Store whether or not this Specifier should accept prereleases\n        self._prereleases = prereleases\n\n    def __repr__(self):\n        pre = (\n            \", prereleases={0!r}\".format(self.prereleases)\n            if self._prereleases is not None\n            else \"\"\n        )\n\n        return \"<{0}({1!r}{2})>\".format(self.__class__.__name__, str(self), pre)\n\n    def __str__(self):\n        return \"{0}{1}\".format(*self._spec)\n\n    def __hash__(self):\n        return hash(self._spec)\n\n    def __eq__(self, other):\n        if isinstance(other, string_types):\n            try:\n                other = self.__class__(other)\n            except InvalidSpecifier:\n                return NotImplemented\n        elif not isinstance(other, self.__class__):\n            return NotImplemented\n\n        return self._spec == other._spec\n\n    def __ne__(self, other):\n        if isinstance(other, string_types):\n            try:\n                other = self.__class__(other)\n            except InvalidSpecifier:\n                return NotImplemented\n        elif not isinstance(other, self.__class__):\n            return NotImplemented\n\n        return self._spec != other._spec\n\n    def _get_operator(self, op):\n        return getattr(self, \"_compare_{0}\".format(self._operators[op]))\n\n    def _coerce_version(self, version):\n        if not isinstance(version, (LegacyVersion, Version)):\n            version = parse(version)\n        return version\n\n    @property\n    def operator(self):\n        return self._spec[0]\n\n    @property\n    def version(self):\n        return self._spec[1]\n\n    @property\n    def prereleases(self):\n        return self._prereleases\n\n    @prereleases.setter\n    def prereleases(self, value):\n        self._prereleases = value\n\n    def __contains__(self, item):\n        return self.contains(item)\n\n    def contains(self, item, prereleases=None):\n        # Determine if prereleases are to be allowed or not.\n        if prereleases is None:\n            prereleases = self.prereleases\n\n        # Normalize item to a Version or LegacyVersion, this allows us to have\n        # a shortcut for ``\"2.0\" in Specifier(\">=2\")\n        item = self._coerce_version(item)\n\n        # Determine if we should be supporting prereleases in this specifier\n        # or not, if we do not support prereleases than we can short circuit\n        # logic if this version is a prereleases.\n        if item.is_prerelease and not prereleases:\n            return False\n\n        # Actually do the comparison to determine if this item is contained\n        # within this Specifier or not.\n        return self._get_operator(self.operator)(item, self.version)\n\n    def filter(self, iterable, prereleases=None):\n        yielded = False\n        found_prereleases = []\n\n        kw = {\"prereleases\": prereleases if prereleases is not None else True}\n\n        # Attempt to iterate over all the values in the iterable and if any of\n        # them match, yield them.\n        for version in iterable:\n            parsed_version = self._coerce_version(version)\n\n            if self.contains(parsed_version, **kw):\n                # If our version is a prerelease, and we were not set to allow\n                # prereleases, then we'll store it for later incase nothing\n                # else matches this specifier.\n                if parsed_version.is_prerelease and not (\n                    prereleases or self.prereleases\n                ):\n                    found_prereleases.append(version)\n                # Either this is not a prerelease, or we should have been\n                # accepting prereleases from the beginning.\n                else:\n                    yielded = True\n                    yield version\n\n        # Now that we've iterated over everything, determine if we've yielded\n        # any values, and if we have not and we have any prereleases stored up\n        # then we will go ahead and yield the prereleases.\n        if not yielded and found_prereleases:\n            for version in found_prereleases:\n                yield version\n\n\nclass LegacySpecifier(_IndividualSpecifier):\n\n    _regex_str = r\"\"\"\n        (?P<operator>(==|!=|<=|>=|<|>))\n        \\s*\n        (?P<version>\n            [^,;\\s)]* # Since this is a \"legacy\" specifier, and the version\n                      # string can be just about anything, we match everything\n                      # except for whitespace, a semi-colon for marker support,\n                      # a closing paren since versions can be enclosed in\n                      # them, and a comma since it's a version separator.\n        )\n        \"\"\"\n\n    _regex = re.compile(r\"^\\s*\" + _regex_str + r\"\\s*$\", re.VERBOSE | re.IGNORECASE)\n\n    _operators = {\n        \"==\": \"equal\",\n        \"!=\": \"not_equal\",\n        \"<=\": \"less_than_equal\",\n        \">=\": \"greater_than_equal\",\n        \"<\": \"less_than\",\n        \">\": \"greater_than\",\n    }\n\n    def _coerce_version(self, version):\n        if not isinstance(version, LegacyVersion):\n            version = LegacyVersion(str(version))\n        return version\n\n    def _compare_equal(self, prospective, spec):\n        return prospective == self._coerce_version(spec)\n\n    def _compare_not_equal(self, prospective, spec):\n        return prospective != self._coerce_version(spec)\n\n    def _compare_less_than_equal(self, prospective, spec):\n        return prospective <= self._coerce_version(spec)\n\n    def _compare_greater_than_equal(self, prospective, spec):\n        return prospective >= self._coerce_version(spec)\n\n    def _compare_less_than(self, prospective, spec):\n        return prospective < self._coerce_version(spec)\n\n    def _compare_greater_than(self, prospective, spec):\n        return prospective > self._coerce_version(spec)\n\n\ndef _require_version_compare(fn):\n    @functools.wraps(fn)\n    def wrapped(self, prospective, spec):\n        if not isinstance(prospective, Version):\n            return False\n        return fn(self, prospective, spec)\n\n    return wrapped\n\n\nclass Specifier(_IndividualSpecifier):\n\n    _regex_str = r\"\"\"\n        (?P<operator>(~=|==|!=|<=|>=|<|>|===))\n        (?P<version>\n            (?:\n                # The identity operators allow for an escape hatch that will\n                # do an exact string match of the version you wish to install.\n                # This will not be parsed by PEP 440 and we cannot determine\n                # any semantic meaning from it. This operator is discouraged\n                # but included entirely as an escape hatch.\n                (?<====)  # Only match for the identity operator\n                \\s*\n                [^\\s]*    # We just match everything, except for whitespace\n                          # since we are only testing for strict identity.\n            )\n            |\n            (?:\n                # The (non)equality operators allow for wild card and local\n                # versions to be specified so we have to define these two\n                # operators separately to enable that.\n                (?<===|!=)            # Only match for equals and not equals\n\n                \\s*\n                v?\n                (?:[0-9]+!)?          # epoch\n                [0-9]+(?:\\.[0-9]+)*   # release\n                (?:                   # pre release\n                    [-_\\.]?\n                    (a|b|c|rc|alpha|beta|pre|preview)\n                    [-_\\.]?\n                    [0-9]*\n                )?\n                (?:                   # post release\n                    (?:-[0-9]+)|(?:[-_\\.]?(post|rev|r)[-_\\.]?[0-9]*)\n                )?\n\n                # You cannot use a wild card and a dev or local version\n                # together so group them with a | and make them optional.\n                (?:\n                    (?:[-_\\.]?dev[-_\\.]?[0-9]*)?         # dev release\n                    (?:\\+[a-z0-9]+(?:[-_\\.][a-z0-9]+)*)? # local\n                    |\n                    \\.\\*  # Wild card syntax of .*\n                )?\n            )\n            |\n            (?:\n                # The compatible operator requires at least two digits in the\n                # release segment.\n                (?<=~=)               # Only match for the compatible operator\n\n                \\s*\n                v?\n                (?:[0-9]+!)?          # epoch\n                [0-9]+(?:\\.[0-9]+)+   # release  (We have a + instead of a *)\n                (?:                   # pre release\n                    [-_\\.]?\n                    (a|b|c|rc|alpha|beta|pre|preview)\n                    [-_\\.]?\n                    [0-9]*\n                )?\n                (?:                                   # post release\n                    (?:-[0-9]+)|(?:[-_\\.]?(post|rev|r)[-_\\.]?[0-9]*)\n                )?\n                (?:[-_\\.]?dev[-_\\.]?[0-9]*)?          # dev release\n            )\n            |\n            (?:\n                # All other operators only allow a sub set of what the\n                # (non)equality operators do. Specifically they do not allow\n                # local versions to be specified nor do they allow the prefix\n                # matching wild cards.\n                (?<!==|!=|~=)         # We have special cases for these\n                                      # operators so we want to make sure they\n                                      # don't match here.\n\n                \\s*\n                v?\n                (?:[0-9]+!)?          # epoch\n                [0-9]+(?:\\.[0-9]+)*   # release\n                (?:                   # pre release\n                    [-_\\.]?\n                    (a|b|c|rc|alpha|beta|pre|preview)\n                    [-_\\.]?\n                    [0-9]*\n                )?\n                (?:                                   # post release\n                    (?:-[0-9]+)|(?:[-_\\.]?(post|rev|r)[-_\\.]?[0-9]*)\n                )?\n                (?:[-_\\.]?dev[-_\\.]?[0-9]*)?          # dev release\n            )\n        )\n        \"\"\"\n\n    _regex = re.compile(r\"^\\s*\" + _regex_str + r\"\\s*$\", re.VERBOSE | re.IGNORECASE)\n\n    _operators = {\n        \"~=\": \"compatible\",\n        \"==\": \"equal\",\n        \"!=\": \"not_equal\",\n        \"<=\": \"less_than_equal\",\n        \">=\": \"greater_than_equal\",\n        \"<\": \"less_than\",\n        \">\": \"greater_than\",\n        \"===\": \"arbitrary\",\n    }\n\n    @_require_version_compare\n    def _compare_compatible(self, prospective, spec):\n        # Compatible releases have an equivalent combination of >= and ==. That\n        # is that ~=2.2 is equivalent to >=2.2,==2.*. This allows us to\n        # implement this in terms of the other specifiers instead of\n        # implementing it ourselves. The only thing we need to do is construct\n        # the other specifiers.\n\n        # We want everything but the last item in the version, but we want to\n        # ignore post and dev releases and we want to treat the pre-release as\n        # it's own separate segment.\n        prefix = \".\".join(\n            list(\n                itertools.takewhile(\n                    lambda x: (not x.startswith(\"post\") and not x.startswith(\"dev\")),\n                    _version_split(spec),\n                )\n            )[:-1]\n        )\n\n        # Add the prefix notation to the end of our string\n        prefix += \".*\"\n\n        return self._get_operator(\">=\")(prospective, spec) and self._get_operator(\"==\")(\n            prospective, prefix\n        )\n\n    @_require_version_compare\n    def _compare_equal(self, prospective, spec):\n        # We need special logic to handle prefix matching\n        if spec.endswith(\".*\"):\n            # In the case of prefix matching we want to ignore local segment.\n            prospective = Version(prospective.public)\n            # Split the spec out by dots, and pretend that there is an implicit\n            # dot in between a release segment and a pre-release segment.\n            spec = _version_split(spec[:-2])  # Remove the trailing .*\n\n            # Split the prospective version out by dots, and pretend that there\n            # is an implicit dot in between a release segment and a pre-release\n            # segment.\n            prospective = _version_split(str(prospective))\n\n            # Shorten the prospective version to be the same length as the spec\n            # so that we can determine if the specifier is a prefix of the\n            # prospective version or not.\n            prospective = prospective[: len(spec)]\n\n            # Pad out our two sides with zeros so that they both equal the same\n            # length.\n            spec, prospective = _pad_version(spec, prospective)\n        else:\n            # Convert our spec string into a Version\n            spec = Version(spec)\n\n            # If the specifier does not have a local segment, then we want to\n            # act as if the prospective version also does not have a local\n            # segment.\n            if not spec.local:\n                prospective = Version(prospective.public)\n\n        return prospective == spec\n\n    @_require_version_compare\n    def _compare_not_equal(self, prospective, spec):\n        return not self._compare_equal(prospective, spec)\n\n    @_require_version_compare\n    def _compare_less_than_equal(self, prospective, spec):\n        return prospective <= Version(spec)\n\n    @_require_version_compare\n    def _compare_greater_than_equal(self, prospective, spec):\n        return prospective >= Version(spec)\n\n    @_require_version_compare\n    def _compare_less_than(self, prospective, spec):\n        # Convert our spec to a Version instance, since we'll want to work with\n        # it as a version.\n        spec = Version(spec)\n\n        # Check to see if the prospective version is less than the spec\n        # version. If it's not we can short circuit and just return False now\n        # instead of doing extra unneeded work.\n        if not prospective < spec:\n            return False\n\n        # This special case is here so that, unless the specifier itself\n        # includes is a pre-release version, that we do not accept pre-release\n        # versions for the version mentioned in the specifier (e.g. <3.1 should\n        # not match 3.1.dev0, but should match 3.0.dev0).\n        if not spec.is_prerelease and prospective.is_prerelease:\n            if Version(prospective.base_version) == Version(spec.base_version):\n                return False\n\n        # If we've gotten to here, it means that prospective version is both\n        # less than the spec version *and* it's not a pre-release of the same\n        # version in the spec.\n        return True\n\n    @_require_version_compare\n    def _compare_greater_than(self, prospective, spec):\n        # Convert our spec to a Version instance, since we'll want to work with\n        # it as a version.\n        spec = Version(spec)\n\n        # Check to see if the prospective version is greater than the spec\n        # version. If it's not we can short circuit and just return False now\n        # instead of doing extra unneeded work.\n        if not prospective > spec:\n            return False\n\n        # This special case is here so that, unless the specifier itself\n        # includes is a post-release version, that we do not accept\n        # post-release versions for the version mentioned in the specifier\n        # (e.g. >3.1 should not match 3.0.post0, but should match 3.2.post0).\n        if not spec.is_postrelease and prospective.is_postrelease:\n            if Version(prospective.base_version) == Version(spec.base_version):\n                return False\n\n        # Ensure that we do not allow a local version of the version mentioned\n        # in the specifier, which is technically greater than, to match.\n        if prospective.local is not None:\n            if Version(prospective.base_version) == Version(spec.base_version):\n                return False\n\n        # If we've gotten to here, it means that prospective version is both\n        # greater than the spec version *and* it's not a pre-release of the\n        # same version in the spec.\n        return True\n\n    def _compare_arbitrary(self, prospective, spec):\n        return str(prospective).lower() == str(spec).lower()\n\n    @property\n    def prereleases(self):\n        # If there is an explicit prereleases set for this, then we'll just\n        # blindly use that.\n        if self._prereleases is not None:\n            return self._prereleases\n\n        # Look at all of our specifiers and determine if they are inclusive\n        # operators, and if they are if they are including an explicit\n        # prerelease.\n        operator, version = self._spec\n        if operator in [\"==\", \">=\", \"<=\", \"~=\", \"===\"]:\n            # The == specifier can include a trailing .*, if it does we\n            # want to remove before parsing.\n            if operator == \"==\" and version.endswith(\".*\"):\n                version = version[:-2]\n\n            # Parse the version, and if it is a pre-release than this\n            # specifier allows pre-releases.\n            if parse(version).is_prerelease:\n                return True\n\n        return False\n\n    @prereleases.setter\n    def prereleases(self, value):\n        self._prereleases = value\n\n\n_prefix_regex = re.compile(r\"^([0-9]+)((?:a|b|c|rc)[0-9]+)$\")\n\n\ndef _version_split(version):\n    result = []\n    for item in version.split(\".\"):\n        match = _prefix_regex.search(item)\n        if match:\n            result.extend(match.groups())\n        else:\n            result.append(item)\n    return result\n\n\ndef _pad_version(left, right):\n    left_split, right_split = [], []\n\n    # Get the release segment of our versions\n    left_split.append(list(itertools.takewhile(lambda x: x.isdigit(), left)))\n    right_split.append(list(itertools.takewhile(lambda x: x.isdigit(), right)))\n\n    # Get the rest of our versions\n    left_split.append(left[len(left_split[0]) :])\n    right_split.append(right[len(right_split[0]) :])\n\n    # Insert our padding\n    left_split.insert(1, [\"0\"] * max(0, len(right_split[0]) - len(left_split[0])))\n    right_split.insert(1, [\"0\"] * max(0, len(left_split[0]) - len(right_split[0])))\n\n    return (list(itertools.chain(*left_split)), list(itertools.chain(*right_split)))\n\n\nclass SpecifierSet(BaseSpecifier):\n    def __init__(self, specifiers=\"\", prereleases=None):\n        # Split on , to break each indidivual specifier into it's own item, and\n        # strip each item to remove leading/trailing whitespace.\n        specifiers = [s.strip() for s in specifiers.split(\",\") if s.strip()]\n\n        # Parsed each individual specifier, attempting first to make it a\n        # Specifier and falling back to a LegacySpecifier.\n        parsed = set()\n        for specifier in specifiers:\n            try:\n                parsed.add(Specifier(specifier))\n            except InvalidSpecifier:\n                parsed.add(LegacySpecifier(specifier))\n\n        # Turn our parsed specifiers into a frozen set and save them for later.\n        self._specs = frozenset(parsed)\n\n        # Store our prereleases value so we can use it later to determine if\n        # we accept prereleases or not.\n        self._prereleases = prereleases\n\n    def __repr__(self):\n        pre = (\n            \", prereleases={0!r}\".format(self.prereleases)\n            if self._prereleases is not None\n            else \"\"\n        )\n\n        return \"<SpecifierSet({0!r}{1})>\".format(str(self), pre)\n\n    def __str__(self):\n        return \",\".join(sorted(str(s) for s in self._specs))\n\n    def __hash__(self):\n        return hash(self._specs)\n\n    def __and__(self, other):\n        if isinstance(other, string_types):\n            other = SpecifierSet(other)\n        elif not isinstance(other, SpecifierSet):\n            return NotImplemented\n\n        specifier = SpecifierSet()\n        specifier._specs = frozenset(self._specs | other._specs)\n\n        if self._prereleases is None and other._prereleases is not None:\n            specifier._prereleases = other._prereleases\n        elif self._prereleases is not None and other._prereleases is None:\n            specifier._prereleases = self._prereleases\n        elif self._prereleases == other._prereleases:\n            specifier._prereleases = self._prereleases\n        else:\n            raise ValueError(\n                \"Cannot combine SpecifierSets with True and False prerelease \"\n                \"overrides.\"\n            )\n\n        return specifier\n\n    def __eq__(self, other):\n        if isinstance(other, string_types):\n            other = SpecifierSet(other)\n        elif isinstance(other, _IndividualSpecifier):\n            other = SpecifierSet(str(other))\n        elif not isinstance(other, SpecifierSet):\n            return NotImplemented\n\n        return self._specs == other._specs\n\n    def __ne__(self, other):\n        if isinstance(other, string_types):\n            other = SpecifierSet(other)\n        elif isinstance(other, _IndividualSpecifier):\n            other = SpecifierSet(str(other))\n        elif not isinstance(other, SpecifierSet):\n            return NotImplemented\n\n        return self._specs != other._specs\n\n    def __len__(self):\n        return len(self._specs)\n\n    def __iter__(self):\n        return iter(self._specs)\n\n    @property\n    def prereleases(self):\n        # If we have been given an explicit prerelease modifier, then we'll\n        # pass that through here.\n        if self._prereleases is not None:\n            return self._prereleases\n\n        # If we don't have any specifiers, and we don't have a forced value,\n        # then we'll just return None since we don't know if this should have\n        # pre-releases or not.\n        if not self._specs:\n            return None\n\n        # Otherwise we'll see if any of the given specifiers accept\n        # prereleases, if any of them do we'll return True, otherwise False.\n        return any(s.prereleases for s in self._specs)\n\n    @prereleases.setter\n    def prereleases(self, value):\n        self._prereleases = value\n\n    def __contains__(self, item):\n        return self.contains(item)\n\n    def contains(self, item, prereleases=None):\n        # Ensure that our item is a Version or LegacyVersion instance.\n        if not isinstance(item, (LegacyVersion, Version)):\n            item = parse(item)\n\n        # Determine if we're forcing a prerelease or not, if we're not forcing\n        # one for this particular filter call, then we'll use whatever the\n        # SpecifierSet thinks for whether or not we should support prereleases.\n        if prereleases is None:\n            prereleases = self.prereleases\n\n        # We can determine if we're going to allow pre-releases by looking to\n        # see if any of the underlying items supports them. If none of them do\n        # and this item is a pre-release then we do not allow it and we can\n        # short circuit that here.\n        # Note: This means that 1.0.dev1 would not be contained in something\n        #       like >=1.0.devabc however it would be in >=1.0.debabc,>0.0.dev0\n        if not prereleases and item.is_prerelease:\n            return False\n\n        # We simply dispatch to the underlying specs here to make sure that the\n        # given version is contained within all of them.\n        # Note: This use of all() here means that an empty set of specifiers\n        #       will always return True, this is an explicit design decision.\n        return all(s.contains(item, prereleases=prereleases) for s in self._specs)\n\n    def filter(self, iterable, prereleases=None):\n        # Determine if we're forcing a prerelease or not, if we're not forcing\n        # one for this particular filter call, then we'll use whatever the\n        # SpecifierSet thinks for whether or not we should support prereleases.\n        if prereleases is None:\n            prereleases = self.prereleases\n\n        # If we have any specifiers, then we want to wrap our iterable in the\n        # filter method for each one, this will act as a logical AND amongst\n        # each specifier.\n        if self._specs:\n            for spec in self._specs:\n                iterable = spec.filter(iterable, prereleases=bool(prereleases))\n            return iterable\n        # If we do not have any specifiers, then we need to have a rough filter\n        # which will filter out any pre-releases, unless there are no final\n        # releases, and which will filter out LegacyVersion in general.\n        else:\n            filtered = []\n            found_prereleases = []\n\n            for item in iterable:\n                # Ensure that we some kind of Version class for this item.\n                if not isinstance(item, (LegacyVersion, Version)):\n                    parsed_version = parse(item)\n                else:\n                    parsed_version = item\n\n                # Filter out any item which is parsed as a LegacyVersion\n                if isinstance(parsed_version, LegacyVersion):\n                    continue\n\n                # Store any item which is a pre-release for later unless we've\n                # already found a final version or we are accepting prereleases\n                if parsed_version.is_prerelease and not prereleases:\n                    if not filtered:\n                        found_prereleases.append(item)\n                else:\n                    filtered.append(item)\n\n            # If we've found no items except for pre-releases, then we'll go\n            # ahead and use the pre-releases\n            if not filtered and found_prereleases and prereleases is None:\n                return found_prereleases\n\n            return filtered\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/packaging/utils.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\nfrom __future__ import absolute_import, division, print_function\n\nimport re\n\nfrom .version import InvalidVersion, Version\n\n\n_canonicalize_regex = re.compile(r\"[-_.]+\")\n\n\ndef canonicalize_name(name):\n    # This is taken from PEP 503.\n    return _canonicalize_regex.sub(\"-\", name).lower()\n\n\ndef canonicalize_version(version):\n    \"\"\"\n    This is very similar to Version.__str__, but has one subtle differences\n    with the way it handles the release segment.\n    \"\"\"\n\n    try:\n        version = Version(version)\n    except InvalidVersion:\n        # Legacy versions cannot be normalized\n        return version\n\n    parts = []\n\n    # Epoch\n    if version.epoch != 0:\n        parts.append(\"{0}!\".format(version.epoch))\n\n    # Release segment\n    # NB: This strips trailing '.0's to normalize\n    parts.append(re.sub(r\"(\\.0)+$\", \"\", \".\".join(str(x) for x in version.release)))\n\n    # Pre-release\n    if version.pre is not None:\n        parts.append(\"\".join(str(x) for x in version.pre))\n\n    # Post-release\n    if version.post is not None:\n        parts.append(\".post{0}\".format(version.post))\n\n    # Development release\n    if version.dev is not None:\n        parts.append(\".dev{0}\".format(version.dev))\n\n    # Local version segment\n    if version.local is not None:\n        parts.append(\"+{0}\".format(version.local))\n\n    return \"\".join(parts)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/packaging/version.py",
    "content": "# This file is dual licensed under the terms of the Apache License, Version\n# 2.0, and the BSD License. See the LICENSE file in the root of this repository\n# for complete details.\nfrom __future__ import absolute_import, division, print_function\n\nimport collections\nimport itertools\nimport re\n\nfrom ._structures import Infinity\n\n\n__all__ = [\"parse\", \"Version\", \"LegacyVersion\", \"InvalidVersion\", \"VERSION_PATTERN\"]\n\n\n_Version = collections.namedtuple(\n    \"_Version\", [\"epoch\", \"release\", \"dev\", \"pre\", \"post\", \"local\"]\n)\n\n\ndef parse(version):\n    \"\"\"\n    Parse the given version string and return either a :class:`Version` object\n    or a :class:`LegacyVersion` object depending on if the given version is\n    a valid PEP 440 version or a legacy version.\n    \"\"\"\n    try:\n        return Version(version)\n    except InvalidVersion:\n        return LegacyVersion(version)\n\n\nclass InvalidVersion(ValueError):\n    \"\"\"\n    An invalid version was found, users should refer to PEP 440.\n    \"\"\"\n\n\nclass _BaseVersion(object):\n    def __hash__(self):\n        return hash(self._key)\n\n    def __lt__(self, other):\n        return self._compare(other, lambda s, o: s < o)\n\n    def __le__(self, other):\n        return self._compare(other, lambda s, o: s <= o)\n\n    def __eq__(self, other):\n        return self._compare(other, lambda s, o: s == o)\n\n    def __ge__(self, other):\n        return self._compare(other, lambda s, o: s >= o)\n\n    def __gt__(self, other):\n        return self._compare(other, lambda s, o: s > o)\n\n    def __ne__(self, other):\n        return self._compare(other, lambda s, o: s != o)\n\n    def _compare(self, other, method):\n        if not isinstance(other, _BaseVersion):\n            return NotImplemented\n\n        return method(self._key, other._key)\n\n\nclass LegacyVersion(_BaseVersion):\n    def __init__(self, version):\n        self._version = str(version)\n        self._key = _legacy_cmpkey(self._version)\n\n    def __str__(self):\n        return self._version\n\n    def __repr__(self):\n        return \"<LegacyVersion({0})>\".format(repr(str(self)))\n\n    @property\n    def public(self):\n        return self._version\n\n    @property\n    def base_version(self):\n        return self._version\n\n    @property\n    def epoch(self):\n        return -1\n\n    @property\n    def release(self):\n        return None\n\n    @property\n    def pre(self):\n        return None\n\n    @property\n    def post(self):\n        return None\n\n    @property\n    def dev(self):\n        return None\n\n    @property\n    def local(self):\n        return None\n\n    @property\n    def is_prerelease(self):\n        return False\n\n    @property\n    def is_postrelease(self):\n        return False\n\n    @property\n    def is_devrelease(self):\n        return False\n\n\n_legacy_version_component_re = re.compile(r\"(\\d+ | [a-z]+ | \\.| -)\", re.VERBOSE)\n\n_legacy_version_replacement_map = {\n    \"pre\": \"c\",\n    \"preview\": \"c\",\n    \"-\": \"final-\",\n    \"rc\": \"c\",\n    \"dev\": \"@\",\n}\n\n\ndef _parse_version_parts(s):\n    for part in _legacy_version_component_re.split(s):\n        part = _legacy_version_replacement_map.get(part, part)\n\n        if not part or part == \".\":\n            continue\n\n        if part[:1] in \"0123456789\":\n            # pad for numeric comparison\n            yield part.zfill(8)\n        else:\n            yield \"*\" + part\n\n    # ensure that alpha/beta/candidate are before final\n    yield \"*final\"\n\n\ndef _legacy_cmpkey(version):\n    # We hardcode an epoch of -1 here. A PEP 440 version can only have a epoch\n    # greater than or equal to 0. This will effectively put the LegacyVersion,\n    # which uses the defacto standard originally implemented by setuptools,\n    # as before all PEP 440 versions.\n    epoch = -1\n\n    # This scheme is taken from pkg_resources.parse_version setuptools prior to\n    # it's adoption of the packaging library.\n    parts = []\n    for part in _parse_version_parts(version.lower()):\n        if part.startswith(\"*\"):\n            # remove \"-\" before a prerelease tag\n            if part < \"*final\":\n                while parts and parts[-1] == \"*final-\":\n                    parts.pop()\n\n            # remove trailing zeros from each series of numeric parts\n            while parts and parts[-1] == \"00000000\":\n                parts.pop()\n\n        parts.append(part)\n    parts = tuple(parts)\n\n    return epoch, parts\n\n\n# Deliberately not anchored to the start and end of the string, to make it\n# easier for 3rd party code to reuse\nVERSION_PATTERN = r\"\"\"\n    v?\n    (?:\n        (?:(?P<epoch>[0-9]+)!)?                           # epoch\n        (?P<release>[0-9]+(?:\\.[0-9]+)*)                  # release segment\n        (?P<pre>                                          # pre-release\n            [-_\\.]?\n            (?P<pre_l>(a|b|c|rc|alpha|beta|pre|preview))\n            [-_\\.]?\n            (?P<pre_n>[0-9]+)?\n        )?\n        (?P<post>                                         # post release\n            (?:-(?P<post_n1>[0-9]+))\n            |\n            (?:\n                [-_\\.]?\n                (?P<post_l>post|rev|r)\n                [-_\\.]?\n                (?P<post_n2>[0-9]+)?\n            )\n        )?\n        (?P<dev>                                          # dev release\n            [-_\\.]?\n            (?P<dev_l>dev)\n            [-_\\.]?\n            (?P<dev_n>[0-9]+)?\n        )?\n    )\n    (?:\\+(?P<local>[a-z0-9]+(?:[-_\\.][a-z0-9]+)*))?       # local version\n\"\"\"\n\n\nclass Version(_BaseVersion):\n\n    _regex = re.compile(r\"^\\s*\" + VERSION_PATTERN + r\"\\s*$\", re.VERBOSE | re.IGNORECASE)\n\n    def __init__(self, version):\n        # Validate the version and parse it into pieces\n        match = self._regex.search(version)\n        if not match:\n            raise InvalidVersion(\"Invalid version: '{0}'\".format(version))\n\n        # Store the parsed out pieces of the version\n        self._version = _Version(\n            epoch=int(match.group(\"epoch\")) if match.group(\"epoch\") else 0,\n            release=tuple(int(i) for i in match.group(\"release\").split(\".\")),\n            pre=_parse_letter_version(match.group(\"pre_l\"), match.group(\"pre_n\")),\n            post=_parse_letter_version(\n                match.group(\"post_l\"), match.group(\"post_n1\") or match.group(\"post_n2\")\n            ),\n            dev=_parse_letter_version(match.group(\"dev_l\"), match.group(\"dev_n\")),\n            local=_parse_local_version(match.group(\"local\")),\n        )\n\n        # Generate a key which will be used for sorting\n        self._key = _cmpkey(\n            self._version.epoch,\n            self._version.release,\n            self._version.pre,\n            self._version.post,\n            self._version.dev,\n            self._version.local,\n        )\n\n    def __repr__(self):\n        return \"<Version({0})>\".format(repr(str(self)))\n\n    def __str__(self):\n        parts = []\n\n        # Epoch\n        if self.epoch != 0:\n            parts.append(\"{0}!\".format(self.epoch))\n\n        # Release segment\n        parts.append(\".\".join(str(x) for x in self.release))\n\n        # Pre-release\n        if self.pre is not None:\n            parts.append(\"\".join(str(x) for x in self.pre))\n\n        # Post-release\n        if self.post is not None:\n            parts.append(\".post{0}\".format(self.post))\n\n        # Development release\n        if self.dev is not None:\n            parts.append(\".dev{0}\".format(self.dev))\n\n        # Local version segment\n        if self.local is not None:\n            parts.append(\"+{0}\".format(self.local))\n\n        return \"\".join(parts)\n\n    @property\n    def epoch(self):\n        return self._version.epoch\n\n    @property\n    def release(self):\n        return self._version.release\n\n    @property\n    def pre(self):\n        return self._version.pre\n\n    @property\n    def post(self):\n        return self._version.post[1] if self._version.post else None\n\n    @property\n    def dev(self):\n        return self._version.dev[1] if self._version.dev else None\n\n    @property\n    def local(self):\n        if self._version.local:\n            return \".\".join(str(x) for x in self._version.local)\n        else:\n            return None\n\n    @property\n    def public(self):\n        return str(self).split(\"+\", 1)[0]\n\n    @property\n    def base_version(self):\n        parts = []\n\n        # Epoch\n        if self.epoch != 0:\n            parts.append(\"{0}!\".format(self.epoch))\n\n        # Release segment\n        parts.append(\".\".join(str(x) for x in self.release))\n\n        return \"\".join(parts)\n\n    @property\n    def is_prerelease(self):\n        return self.dev is not None or self.pre is not None\n\n    @property\n    def is_postrelease(self):\n        return self.post is not None\n\n    @property\n    def is_devrelease(self):\n        return self.dev is not None\n\n\ndef _parse_letter_version(letter, number):\n    if letter:\n        # We consider there to be an implicit 0 in a pre-release if there is\n        # not a numeral associated with it.\n        if number is None:\n            number = 0\n\n        # We normalize any letters to their lower case form\n        letter = letter.lower()\n\n        # We consider some words to be alternate spellings of other words and\n        # in those cases we want to normalize the spellings to our preferred\n        # spelling.\n        if letter == \"alpha\":\n            letter = \"a\"\n        elif letter == \"beta\":\n            letter = \"b\"\n        elif letter in [\"c\", \"pre\", \"preview\"]:\n            letter = \"rc\"\n        elif letter in [\"rev\", \"r\"]:\n            letter = \"post\"\n\n        return letter, int(number)\n    if not letter and number:\n        # We assume if we are given a number, but we are not given a letter\n        # then this is using the implicit post release syntax (e.g. 1.0-1)\n        letter = \"post\"\n\n        return letter, int(number)\n\n\n_local_version_separators = re.compile(r\"[\\._-]\")\n\n\ndef _parse_local_version(local):\n    \"\"\"\n    Takes a string like abc.1.twelve and turns it into (\"abc\", 1, \"twelve\").\n    \"\"\"\n    if local is not None:\n        return tuple(\n            part.lower() if not part.isdigit() else int(part)\n            for part in _local_version_separators.split(local)\n        )\n\n\ndef _cmpkey(epoch, release, pre, post, dev, local):\n    # When we compare a release version, we want to compare it with all of the\n    # trailing zeros removed. So we'll use a reverse the list, drop all the now\n    # leading zeros until we come to something non zero, then take the rest\n    # re-reverse it back into the correct order and make it a tuple and use\n    # that for our sorting key.\n    release = tuple(\n        reversed(list(itertools.dropwhile(lambda x: x == 0, reversed(release))))\n    )\n\n    # We need to \"trick\" the sorting algorithm to put 1.0.dev0 before 1.0a0.\n    # We'll do this by abusing the pre segment, but we _only_ want to do this\n    # if there is not a pre or a post segment. If we have one of those then\n    # the normal sorting rules will handle this case correctly.\n    if pre is None and post is None and dev is not None:\n        pre = -Infinity\n    # Versions without a pre-release (except as noted above) should sort after\n    # those with one.\n    elif pre is None:\n        pre = Infinity\n\n    # Versions without a post segment should sort before those with one.\n    if post is None:\n        post = -Infinity\n\n    # Versions without a development segment should sort after those with one.\n    if dev is None:\n        dev = Infinity\n\n    if local is None:\n        # Versions without a local segment should sort before those with one.\n        local = -Infinity\n    else:\n        # Versions with a local segment need that segment parsed to implement\n        # the sorting rules in PEP440.\n        # - Alpha numeric segments sort before numeric segments\n        # - Alpha numeric segments sort lexicographically\n        # - Numeric segments sort numerically\n        # - Shorter versions sort before longer versions when the prefixes\n        #   match exactly\n        local = tuple((i, \"\") if isinstance(i, int) else (-Infinity, i) for i in local)\n\n    return epoch, release, pre, post, dev, local\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pep517/__init__.py",
    "content": "\"\"\"Wrappers to build Python packages using PEP 517 hooks\n\"\"\"\n\n__version__ = '0.5.0'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pep517/_in_process.py",
    "content": "\"\"\"This is invoked in a subprocess to call the build backend hooks.\n\nIt expects:\n- Command line args: hook_name, control_dir\n- Environment variable: PEP517_BUILD_BACKEND=entry.point:spec\n- control_dir/input.json:\n  - {\"kwargs\": {...}}\n\nResults:\n- control_dir/output.json\n  - {\"return_val\": ...}\n\"\"\"\nfrom glob import glob\nfrom importlib import import_module\nimport os\nfrom os.path import join as pjoin\nimport re\nimport shutil\nimport sys\n\n# This is run as a script, not a module, so it can't do a relative import\nimport compat\n\n\nclass BackendUnavailable(Exception):\n    \"\"\"Raised if we cannot import the backend\"\"\"\n\n\ndef _build_backend():\n    \"\"\"Find and load the build backend\"\"\"\n    ep = os.environ['PEP517_BUILD_BACKEND']\n    mod_path, _, obj_path = ep.partition(':')\n    try:\n        obj = import_module(mod_path)\n    except ImportError:\n        raise BackendUnavailable\n    if obj_path:\n        for path_part in obj_path.split('.'):\n            obj = getattr(obj, path_part)\n    return obj\n\n\ndef get_requires_for_build_wheel(config_settings):\n    \"\"\"Invoke the optional get_requires_for_build_wheel hook\n\n    Returns [] if the hook is not defined.\n    \"\"\"\n    backend = _build_backend()\n    try:\n        hook = backend.get_requires_for_build_wheel\n    except AttributeError:\n        return []\n    else:\n        return hook(config_settings)\n\n\ndef prepare_metadata_for_build_wheel(metadata_directory, config_settings):\n    \"\"\"Invoke optional prepare_metadata_for_build_wheel\n\n    Implements a fallback by building a wheel if the hook isn't defined.\n    \"\"\"\n    backend = _build_backend()\n    try:\n        hook = backend.prepare_metadata_for_build_wheel\n    except AttributeError:\n        return _get_wheel_metadata_from_wheel(backend, metadata_directory,\n                                              config_settings)\n    else:\n        return hook(metadata_directory, config_settings)\n\n\nWHEEL_BUILT_MARKER = 'PEP517_ALREADY_BUILT_WHEEL'\n\n\ndef _dist_info_files(whl_zip):\n    \"\"\"Identify the .dist-info folder inside a wheel ZipFile.\"\"\"\n    res = []\n    for path in whl_zip.namelist():\n        m = re.match(r'[^/\\\\]+-[^/\\\\]+\\.dist-info/', path)\n        if m:\n            res.append(path)\n    if res:\n        return res\n    raise Exception(\"No .dist-info folder found in wheel\")\n\n\ndef _get_wheel_metadata_from_wheel(\n        backend, metadata_directory, config_settings):\n    \"\"\"Build a wheel and extract the metadata from it.\n\n    Fallback for when the build backend does not\n    define the 'get_wheel_metadata' hook.\n    \"\"\"\n    from zipfile import ZipFile\n    whl_basename = backend.build_wheel(metadata_directory, config_settings)\n    with open(os.path.join(metadata_directory, WHEEL_BUILT_MARKER), 'wb'):\n        pass  # Touch marker file\n\n    whl_file = os.path.join(metadata_directory, whl_basename)\n    with ZipFile(whl_file) as zipf:\n        dist_info = _dist_info_files(zipf)\n        zipf.extractall(path=metadata_directory, members=dist_info)\n    return dist_info[0].split('/')[0]\n\n\ndef _find_already_built_wheel(metadata_directory):\n    \"\"\"Check for a wheel already built during the get_wheel_metadata hook.\n    \"\"\"\n    if not metadata_directory:\n        return None\n    metadata_parent = os.path.dirname(metadata_directory)\n    if not os.path.isfile(pjoin(metadata_parent, WHEEL_BUILT_MARKER)):\n        return None\n\n    whl_files = glob(os.path.join(metadata_parent, '*.whl'))\n    if not whl_files:\n        print('Found wheel built marker, but no .whl files')\n        return None\n    if len(whl_files) > 1:\n        print('Found multiple .whl files; unspecified behaviour. '\n              'Will call build_wheel.')\n        return None\n\n    # Exactly one .whl file\n    return whl_files[0]\n\n\ndef build_wheel(wheel_directory, config_settings, metadata_directory=None):\n    \"\"\"Invoke the mandatory build_wheel hook.\n\n    If a wheel was already built in the\n    prepare_metadata_for_build_wheel fallback, this\n    will copy it rather than rebuilding the wheel.\n    \"\"\"\n    prebuilt_whl = _find_already_built_wheel(metadata_directory)\n    if prebuilt_whl:\n        shutil.copy2(prebuilt_whl, wheel_directory)\n        return os.path.basename(prebuilt_whl)\n\n    return _build_backend().build_wheel(wheel_directory, config_settings,\n                                        metadata_directory)\n\n\ndef get_requires_for_build_sdist(config_settings):\n    \"\"\"Invoke the optional get_requires_for_build_wheel hook\n\n    Returns [] if the hook is not defined.\n    \"\"\"\n    backend = _build_backend()\n    try:\n        hook = backend.get_requires_for_build_sdist\n    except AttributeError:\n        return []\n    else:\n        return hook(config_settings)\n\n\nclass _DummyException(Exception):\n    \"\"\"Nothing should ever raise this exception\"\"\"\n\n\nclass GotUnsupportedOperation(Exception):\n    \"\"\"For internal use when backend raises UnsupportedOperation\"\"\"\n\n\ndef build_sdist(sdist_directory, config_settings):\n    \"\"\"Invoke the mandatory build_sdist hook.\"\"\"\n    backend = _build_backend()\n    try:\n        return backend.build_sdist(sdist_directory, config_settings)\n    except getattr(backend, 'UnsupportedOperation', _DummyException):\n        raise GotUnsupportedOperation\n\n\nHOOK_NAMES = {\n    'get_requires_for_build_wheel',\n    'prepare_metadata_for_build_wheel',\n    'build_wheel',\n    'get_requires_for_build_sdist',\n    'build_sdist',\n}\n\n\ndef main():\n    if len(sys.argv) < 3:\n        sys.exit(\"Needs args: hook_name, control_dir\")\n    hook_name = sys.argv[1]\n    control_dir = sys.argv[2]\n    if hook_name not in HOOK_NAMES:\n        sys.exit(\"Unknown hook: %s\" % hook_name)\n    hook = globals()[hook_name]\n\n    hook_input = compat.read_json(pjoin(control_dir, 'input.json'))\n\n    json_out = {'unsupported': False, 'return_val': None}\n    try:\n        json_out['return_val'] = hook(**hook_input['kwargs'])\n    except BackendUnavailable:\n        json_out['no_backend'] = True\n    except GotUnsupportedOperation:\n        json_out['unsupported'] = True\n\n    compat.write_json(json_out, pjoin(control_dir, 'output.json'), indent=2)\n\n\nif __name__ == '__main__':\n    main()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pep517/build.py",
    "content": "\"\"\"Build a project using PEP 517 hooks.\n\"\"\"\nimport argparse\nimport logging\nimport os\nimport contextlib\nfrom pip._vendor import pytoml\nimport shutil\nimport errno\nimport tempfile\n\nfrom .envbuild import BuildEnvironment\nfrom .wrappers import Pep517HookCaller\n\nlog = logging.getLogger(__name__)\n\n\n@contextlib.contextmanager\ndef tempdir():\n    td = tempfile.mkdtemp()\n    try:\n        yield td\n    finally:\n        shutil.rmtree(td)\n\n\ndef _do_build(hooks, env, dist, dest):\n    get_requires_name = 'get_requires_for_build_{dist}'.format(**locals())\n    get_requires = getattr(hooks, get_requires_name)\n    reqs = get_requires({})\n    log.info('Got build requires: %s', reqs)\n\n    env.pip_install(reqs)\n    log.info('Installed dynamic build dependencies')\n\n    with tempdir() as td:\n        log.info('Trying to build %s in %s', dist, td)\n        build_name = 'build_{dist}'.format(**locals())\n        build = getattr(hooks, build_name)\n        filename = build(td, {})\n        source = os.path.join(td, filename)\n        shutil.move(source, os.path.join(dest, os.path.basename(filename)))\n\n\ndef mkdir_p(*args, **kwargs):\n    \"\"\"Like `mkdir`, but does not raise an exception if the\n    directory already exists.\n    \"\"\"\n    try:\n        return os.mkdir(*args, **kwargs)\n    except OSError as exc:\n        if exc.errno != errno.EEXIST:\n            raise\n\n\ndef build(source_dir, dist, dest=None):\n    pyproject = os.path.join(source_dir, 'pyproject.toml')\n    dest = os.path.join(source_dir, dest or 'dist')\n    mkdir_p(dest)\n\n    with open(pyproject) as f:\n        pyproject_data = pytoml.load(f)\n    # Ensure the mandatory data can be loaded\n    buildsys = pyproject_data['build-system']\n    requires = buildsys['requires']\n    backend = buildsys['build-backend']\n\n    hooks = Pep517HookCaller(source_dir, backend)\n\n    with BuildEnvironment() as env:\n        env.pip_install(requires)\n        _do_build(hooks, env, dist, dest)\n\n\nparser = argparse.ArgumentParser()\nparser.add_argument(\n    'source_dir',\n    help=\"A directory containing pyproject.toml\",\n)\nparser.add_argument(\n    '--binary', '-b',\n    action='store_true',\n    default=False,\n)\nparser.add_argument(\n    '--source', '-s',\n    action='store_true',\n    default=False,\n)\nparser.add_argument(\n    '--out-dir', '-o',\n    help=\"Destination in which to save the builds relative to source dir\",\n)\n\n\ndef main(args):\n    # determine which dists to build\n    dists = list(filter(None, (\n        'sdist' if args.source or not args.binary else None,\n        'wheel' if args.binary or not args.source else None,\n    )))\n\n    for dist in dists:\n        build(args.source_dir, dist, args.out_dir)\n\n\nif __name__ == '__main__':\n    main(parser.parse_args())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pep517/check.py",
    "content": "\"\"\"Check a project and backend by attempting to build using PEP 517 hooks.\n\"\"\"\nimport argparse\nimport logging\nimport os\nfrom os.path import isfile, join as pjoin\nfrom pip._vendor.pytoml import TomlError, load as toml_load\nimport shutil\nfrom subprocess import CalledProcessError\nimport sys\nimport tarfile\nfrom tempfile import mkdtemp\nimport zipfile\n\nfrom .colorlog import enable_colourful_output\nfrom .envbuild import BuildEnvironment\nfrom .wrappers import Pep517HookCaller\n\nlog = logging.getLogger(__name__)\n\n\ndef check_build_sdist(hooks, build_sys_requires):\n    with BuildEnvironment() as env:\n        try:\n            env.pip_install(build_sys_requires)\n            log.info('Installed static build dependencies')\n        except CalledProcessError:\n            log.error('Failed to install static build dependencies')\n            return False\n\n        try:\n            reqs = hooks.get_requires_for_build_sdist({})\n            log.info('Got build requires: %s', reqs)\n        except Exception:\n            log.error('Failure in get_requires_for_build_sdist', exc_info=True)\n            return False\n\n        try:\n            env.pip_install(reqs)\n            log.info('Installed dynamic build dependencies')\n        except CalledProcessError:\n            log.error('Failed to install dynamic build dependencies')\n            return False\n\n        td = mkdtemp()\n        log.info('Trying to build sdist in %s', td)\n        try:\n            try:\n                filename = hooks.build_sdist(td, {})\n                log.info('build_sdist returned %r', filename)\n            except Exception:\n                log.info('Failure in build_sdist', exc_info=True)\n                return False\n\n            if not filename.endswith('.tar.gz'):\n                log.error(\n                    \"Filename %s doesn't have .tar.gz extension\", filename)\n                return False\n\n            path = pjoin(td, filename)\n            if isfile(path):\n                log.info(\"Output file %s exists\", path)\n            else:\n                log.error(\"Output file %s does not exist\", path)\n                return False\n\n            if tarfile.is_tarfile(path):\n                log.info(\"Output file is a tar file\")\n            else:\n                log.error(\"Output file is not a tar file\")\n                return False\n\n        finally:\n            shutil.rmtree(td)\n\n        return True\n\n\ndef check_build_wheel(hooks, build_sys_requires):\n    with BuildEnvironment() as env:\n        try:\n            env.pip_install(build_sys_requires)\n            log.info('Installed static build dependencies')\n        except CalledProcessError:\n            log.error('Failed to install static build dependencies')\n            return False\n\n        try:\n            reqs = hooks.get_requires_for_build_wheel({})\n            log.info('Got build requires: %s', reqs)\n        except Exception:\n            log.error('Failure in get_requires_for_build_sdist', exc_info=True)\n            return False\n\n        try:\n            env.pip_install(reqs)\n            log.info('Installed dynamic build dependencies')\n        except CalledProcessError:\n            log.error('Failed to install dynamic build dependencies')\n            return False\n\n        td = mkdtemp()\n        log.info('Trying to build wheel in %s', td)\n        try:\n            try:\n                filename = hooks.build_wheel(td, {})\n                log.info('build_wheel returned %r', filename)\n            except Exception:\n                log.info('Failure in build_wheel', exc_info=True)\n                return False\n\n            if not filename.endswith('.whl'):\n                log.error(\"Filename %s doesn't have .whl extension\", filename)\n                return False\n\n            path = pjoin(td, filename)\n            if isfile(path):\n                log.info(\"Output file %s exists\", path)\n            else:\n                log.error(\"Output file %s does not exist\", path)\n                return False\n\n            if zipfile.is_zipfile(path):\n                log.info(\"Output file is a zip file\")\n            else:\n                log.error(\"Output file is not a zip file\")\n                return False\n\n        finally:\n            shutil.rmtree(td)\n\n        return True\n\n\ndef check(source_dir):\n    pyproject = pjoin(source_dir, 'pyproject.toml')\n    if isfile(pyproject):\n        log.info('Found pyproject.toml')\n    else:\n        log.error('Missing pyproject.toml')\n        return False\n\n    try:\n        with open(pyproject) as f:\n            pyproject_data = toml_load(f)\n        # Ensure the mandatory data can be loaded\n        buildsys = pyproject_data['build-system']\n        requires = buildsys['requires']\n        backend = buildsys['build-backend']\n        log.info('Loaded pyproject.toml')\n    except (TomlError, KeyError):\n        log.error(\"Invalid pyproject.toml\", exc_info=True)\n        return False\n\n    hooks = Pep517HookCaller(source_dir, backend)\n\n    sdist_ok = check_build_sdist(hooks, requires)\n    wheel_ok = check_build_wheel(hooks, requires)\n\n    if not sdist_ok:\n        log.warning('Sdist checks failed; scroll up to see')\n    if not wheel_ok:\n        log.warning('Wheel checks failed')\n\n    return sdist_ok\n\n\ndef main(argv=None):\n    ap = argparse.ArgumentParser()\n    ap.add_argument(\n        'source_dir',\n        help=\"A directory containing pyproject.toml\")\n    args = ap.parse_args(argv)\n\n    enable_colourful_output()\n\n    ok = check(args.source_dir)\n\n    if ok:\n        print(ansi('Checks passed', 'green'))\n    else:\n        print(ansi('Checks failed', 'red'))\n        sys.exit(1)\n\n\nansi_codes = {\n    'reset': '\\x1b[0m',\n    'bold': '\\x1b[1m',\n    'red': '\\x1b[31m',\n    'green': '\\x1b[32m',\n}\n\n\ndef ansi(s, attr):\n    if os.name != 'nt' and sys.stdout.isatty():\n        return ansi_codes[attr] + str(s) + ansi_codes['reset']\n    else:\n        return str(s)\n\n\nif __name__ == '__main__':\n    main()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pep517/colorlog.py",
    "content": "\"\"\"Nicer log formatting with colours.\n\nCode copied from Tornado, Apache licensed.\n\"\"\"\n# Copyright 2012 Facebook\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you may\n# not use this file except in compliance with the License. You may obtain\n# a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS, WITHOUT\n# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the\n# License for the specific language governing permissions and limitations\n# under the License.\n\nimport logging\nimport sys\n\ntry:\n    import curses\nexcept ImportError:\n    curses = None\n\n\ndef _stderr_supports_color():\n    color = False\n    if curses and hasattr(sys.stderr, 'isatty') and sys.stderr.isatty():\n        try:\n            curses.setupterm()\n            if curses.tigetnum(\"colors\") > 0:\n                color = True\n        except Exception:\n            pass\n    return color\n\n\nclass LogFormatter(logging.Formatter):\n    \"\"\"Log formatter with colour support\n    \"\"\"\n    DEFAULT_COLORS = {\n        logging.INFO: 2,  # Green\n        logging.WARNING: 3,  # Yellow\n        logging.ERROR: 1,  # Red\n        logging.CRITICAL: 1,\n    }\n\n    def __init__(self, color=True, datefmt=None):\n        r\"\"\"\n        :arg bool color: Enables color support.\n        :arg string fmt: Log message format.\n        It will be applied to the attributes dict of log records. The\n        text between ``%(color)s`` and ``%(end_color)s`` will be colored\n        depending on the level if color support is on.\n        :arg dict colors: color mappings from logging level to terminal color\n        code\n        :arg string datefmt: Datetime format.\n        Used for formatting ``(asctime)`` placeholder in ``prefix_fmt``.\n        .. versionchanged:: 3.2\n        Added ``fmt`` and ``datefmt`` arguments.\n        \"\"\"\n        logging.Formatter.__init__(self, datefmt=datefmt)\n        self._colors = {}\n        if color and _stderr_supports_color():\n            # The curses module has some str/bytes confusion in\n            # python3. Until version 3.2.3, most methods return\n            # bytes, but only accept strings. In addition, we want to\n            # output these strings with the logging module, which\n            # works with unicode strings. The explicit calls to\n            # unicode() below are harmless in python2 but will do the\n            # right conversion in python 3.\n            fg_color = (curses.tigetstr(\"setaf\") or\n                        curses.tigetstr(\"setf\") or \"\")\n            if (3, 0) < sys.version_info < (3, 2, 3):\n                fg_color = str(fg_color, \"ascii\")\n\n            for levelno, code in self.DEFAULT_COLORS.items():\n                self._colors[levelno] = str(\n                    curses.tparm(fg_color, code), \"ascii\")\n            self._normal = str(curses.tigetstr(\"sgr0\"), \"ascii\")\n\n            scr = curses.initscr()\n            self.termwidth = scr.getmaxyx()[1]\n            curses.endwin()\n        else:\n            self._normal = ''\n            # Default width is usually 80, but too wide is\n            # worse than too narrow\n            self.termwidth = 70\n\n    def formatMessage(self, record):\n        mlen = len(record.message)\n        right_text = '{initial}-{name}'.format(initial=record.levelname[0],\n                                               name=record.name)\n        if mlen + len(right_text) < self.termwidth:\n            space = ' ' * (self.termwidth - (mlen + len(right_text)))\n        else:\n            space = '  '\n\n        if record.levelno in self._colors:\n            start_color = self._colors[record.levelno]\n            end_color = self._normal\n        else:\n            start_color = end_color = ''\n\n        return record.message + space + start_color + right_text + end_color\n\n\ndef enable_colourful_output(level=logging.INFO):\n    handler = logging.StreamHandler()\n    handler.setFormatter(LogFormatter())\n    logging.root.addHandler(handler)\n    logging.root.setLevel(level)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pep517/compat.py",
    "content": "\"\"\"Handle reading and writing JSON in UTF-8, on Python 3 and 2.\"\"\"\nimport json\nimport sys\n\nif sys.version_info[0] >= 3:\n    # Python 3\n    def write_json(obj, path, **kwargs):\n        with open(path, 'w', encoding='utf-8') as f:\n            json.dump(obj, f, **kwargs)\n\n    def read_json(path):\n        with open(path, 'r', encoding='utf-8') as f:\n            return json.load(f)\n\nelse:\n    # Python 2\n    def write_json(obj, path, **kwargs):\n        with open(path, 'wb') as f:\n            json.dump(obj, f, encoding='utf-8', **kwargs)\n\n    def read_json(path):\n        with open(path, 'rb') as f:\n            return json.load(f)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pep517/envbuild.py",
    "content": "\"\"\"Build wheels/sdists by installing build deps to a temporary environment.\n\"\"\"\n\nimport os\nimport logging\nfrom pip._vendor import pytoml\nimport shutil\nfrom subprocess import check_call\nimport sys\nfrom sysconfig import get_paths\nfrom tempfile import mkdtemp\n\nfrom .wrappers import Pep517HookCaller\n\nlog = logging.getLogger(__name__)\n\n\ndef _load_pyproject(source_dir):\n    with open(os.path.join(source_dir, 'pyproject.toml')) as f:\n        pyproject_data = pytoml.load(f)\n    buildsys = pyproject_data['build-system']\n    return buildsys['requires'], buildsys['build-backend']\n\n\nclass BuildEnvironment(object):\n    \"\"\"Context manager to install build deps in a simple temporary environment\n\n    Based on code I wrote for pip, which is MIT licensed.\n    \"\"\"\n    # Copyright (c) 2008-2016 The pip developers (see AUTHORS.txt file)\n    #\n    # Permission is hereby granted, free of charge, to any person obtaining\n    # a copy of this software and associated documentation files (the\n    # \"Software\"), to deal in the Software without restriction, including\n    # without limitation the rights to use, copy, modify, merge, publish,\n    # distribute, sublicense, and/or sell copies of the Software, and to\n    # permit persons to whom the Software is furnished to do so, subject to\n    # the following conditions:\n    #\n    # The above copyright notice and this permission notice shall be\n    # included in all copies or substantial portions of the Software.\n    #\n    # THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND,\n    # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\n    # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND\n    # NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE\n    # LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION\n    # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION\n    # WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n\n    path = None\n\n    def __init__(self, cleanup=True):\n        self._cleanup = cleanup\n\n    def __enter__(self):\n        self.path = mkdtemp(prefix='pep517-build-env-')\n        log.info('Temporary build environment: %s', self.path)\n\n        self.save_path = os.environ.get('PATH', None)\n        self.save_pythonpath = os.environ.get('PYTHONPATH', None)\n\n        install_scheme = 'nt' if (os.name == 'nt') else 'posix_prefix'\n        install_dirs = get_paths(install_scheme, vars={\n            'base': self.path,\n            'platbase': self.path,\n        })\n\n        scripts = install_dirs['scripts']\n        if self.save_path:\n            os.environ['PATH'] = scripts + os.pathsep + self.save_path\n        else:\n            os.environ['PATH'] = scripts + os.pathsep + os.defpath\n\n        if install_dirs['purelib'] == install_dirs['platlib']:\n            lib_dirs = install_dirs['purelib']\n        else:\n            lib_dirs = install_dirs['purelib'] + os.pathsep + \\\n                install_dirs['platlib']\n        if self.save_pythonpath:\n            os.environ['PYTHONPATH'] = lib_dirs + os.pathsep + \\\n                self.save_pythonpath\n        else:\n            os.environ['PYTHONPATH'] = lib_dirs\n\n        return self\n\n    def pip_install(self, reqs):\n        \"\"\"Install dependencies into this env by calling pip in a subprocess\"\"\"\n        if not reqs:\n            return\n        log.info('Calling pip to install %s', reqs)\n        check_call([\n            sys.executable, '-m', 'pip', 'install', '--ignore-installed',\n            '--prefix', self.path] + list(reqs))\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        needs_cleanup = (\n            self._cleanup and\n            self.path is not None and\n            os.path.isdir(self.path)\n        )\n        if needs_cleanup:\n            shutil.rmtree(self.path)\n\n        if self.save_path is None:\n            os.environ.pop('PATH', None)\n        else:\n            os.environ['PATH'] = self.save_path\n\n        if self.save_pythonpath is None:\n            os.environ.pop('PYTHONPATH', None)\n        else:\n            os.environ['PYTHONPATH'] = self.save_pythonpath\n\n\ndef build_wheel(source_dir, wheel_dir, config_settings=None):\n    \"\"\"Build a wheel from a source directory using PEP 517 hooks.\n\n    :param str source_dir: Source directory containing pyproject.toml\n    :param str wheel_dir: Target directory to create wheel in\n    :param dict config_settings: Options to pass to build backend\n\n    This is a blocking function which will run pip in a subprocess to install\n    build requirements.\n    \"\"\"\n    if config_settings is None:\n        config_settings = {}\n    requires, backend = _load_pyproject(source_dir)\n    hooks = Pep517HookCaller(source_dir, backend)\n\n    with BuildEnvironment() as env:\n        env.pip_install(requires)\n        reqs = hooks.get_requires_for_build_wheel(config_settings)\n        env.pip_install(reqs)\n        return hooks.build_wheel(wheel_dir, config_settings)\n\n\ndef build_sdist(source_dir, sdist_dir, config_settings=None):\n    \"\"\"Build an sdist from a source directory using PEP 517 hooks.\n\n    :param str source_dir: Source directory containing pyproject.toml\n    :param str sdist_dir: Target directory to place sdist in\n    :param dict config_settings: Options to pass to build backend\n\n    This is a blocking function which will run pip in a subprocess to install\n    build requirements.\n    \"\"\"\n    if config_settings is None:\n        config_settings = {}\n    requires, backend = _load_pyproject(source_dir)\n    hooks = Pep517HookCaller(source_dir, backend)\n\n    with BuildEnvironment() as env:\n        env.pip_install(requires)\n        reqs = hooks.get_requires_for_build_sdist(config_settings)\n        env.pip_install(reqs)\n        return hooks.build_sdist(sdist_dir, config_settings)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pep517/wrappers.py",
    "content": "from contextlib import contextmanager\nimport os\nfrom os.path import dirname, abspath, join as pjoin\nimport shutil\nfrom subprocess import check_call\nimport sys\nfrom tempfile import mkdtemp\n\nfrom . import compat\n\n_in_proc_script = pjoin(dirname(abspath(__file__)), '_in_process.py')\n\n\n@contextmanager\ndef tempdir():\n    td = mkdtemp()\n    try:\n        yield td\n    finally:\n        shutil.rmtree(td)\n\n\nclass BackendUnavailable(Exception):\n    \"\"\"Will be raised if the backend cannot be imported in the hook process.\"\"\"\n\n\nclass UnsupportedOperation(Exception):\n    \"\"\"May be raised by build_sdist if the backend indicates that it can't.\"\"\"\n\n\ndef default_subprocess_runner(cmd, cwd=None, extra_environ=None):\n    \"\"\"The default method of calling the wrapper subprocess.\"\"\"\n    env = os.environ.copy()\n    if extra_environ:\n        env.update(extra_environ)\n\n    check_call(cmd, cwd=cwd, env=env)\n\n\nclass Pep517HookCaller(object):\n    \"\"\"A wrapper around a source directory to be built with a PEP 517 backend.\n\n    source_dir : The path to the source directory, containing pyproject.toml.\n    backend : The build backend spec, as per PEP 517, from pyproject.toml.\n    \"\"\"\n    def __init__(self, source_dir, build_backend):\n        self.source_dir = abspath(source_dir)\n        self.build_backend = build_backend\n        self._subprocess_runner = default_subprocess_runner\n\n    # TODO: Is this over-engineered? Maybe frontends only need to\n    #       set this when creating the wrapper, not on every call.\n    @contextmanager\n    def subprocess_runner(self, runner):\n        prev = self._subprocess_runner\n        self._subprocess_runner = runner\n        yield\n        self._subprocess_runner = prev\n\n    def get_requires_for_build_wheel(self, config_settings=None):\n        \"\"\"Identify packages required for building a wheel\n\n        Returns a list of dependency specifications, e.g.:\n            [\"wheel >= 0.25\", \"setuptools\"]\n\n        This does not include requirements specified in pyproject.toml.\n        It returns the result of calling the equivalently named hook in a\n        subprocess.\n        \"\"\"\n        return self._call_hook('get_requires_for_build_wheel', {\n            'config_settings': config_settings\n        })\n\n    def prepare_metadata_for_build_wheel(\n            self, metadata_directory, config_settings=None):\n        \"\"\"Prepare a *.dist-info folder with metadata for this project.\n\n        Returns the name of the newly created folder.\n\n        If the build backend defines a hook with this name, it will be called\n        in a subprocess. If not, the backend will be asked to build a wheel,\n        and the dist-info extracted from that.\n        \"\"\"\n        return self._call_hook('prepare_metadata_for_build_wheel', {\n            'metadata_directory': abspath(metadata_directory),\n            'config_settings': config_settings,\n        })\n\n    def build_wheel(\n            self, wheel_directory, config_settings=None,\n            metadata_directory=None):\n        \"\"\"Build a wheel from this project.\n\n        Returns the name of the newly created file.\n\n        In general, this will call the 'build_wheel' hook in the backend.\n        However, if that was previously called by\n        'prepare_metadata_for_build_wheel', and the same metadata_directory is\n        used, the previously built wheel will be copied to wheel_directory.\n        \"\"\"\n        if metadata_directory is not None:\n            metadata_directory = abspath(metadata_directory)\n        return self._call_hook('build_wheel', {\n            'wheel_directory': abspath(wheel_directory),\n            'config_settings': config_settings,\n            'metadata_directory': metadata_directory,\n        })\n\n    def get_requires_for_build_sdist(self, config_settings=None):\n        \"\"\"Identify packages required for building a wheel\n\n        Returns a list of dependency specifications, e.g.:\n            [\"setuptools >= 26\"]\n\n        This does not include requirements specified in pyproject.toml.\n        It returns the result of calling the equivalently named hook in a\n        subprocess.\n        \"\"\"\n        return self._call_hook('get_requires_for_build_sdist', {\n            'config_settings': config_settings\n        })\n\n    def build_sdist(self, sdist_directory, config_settings=None):\n        \"\"\"Build an sdist from this project.\n\n        Returns the name of the newly created file.\n\n        This calls the 'build_sdist' backend hook in a subprocess.\n        \"\"\"\n        return self._call_hook('build_sdist', {\n            'sdist_directory': abspath(sdist_directory),\n            'config_settings': config_settings,\n        })\n\n    def _call_hook(self, hook_name, kwargs):\n        # On Python 2, pytoml returns Unicode values (which is correct) but the\n        # environment passed to check_call needs to contain string values. We\n        # convert here by encoding using ASCII (the backend can only contain\n        # letters, digits and _, . and : characters, and will be used as a\n        # Python identifier, so non-ASCII content is wrong on Python 2 in\n        # any case).\n        if sys.version_info[0] == 2:\n            build_backend = self.build_backend.encode('ASCII')\n        else:\n            build_backend = self.build_backend\n\n        with tempdir() as td:\n            compat.write_json({'kwargs': kwargs}, pjoin(td, 'input.json'),\n                              indent=2)\n\n            # Run the hook in a subprocess\n            self._subprocess_runner(\n                [sys.executable, _in_proc_script, hook_name, td],\n                cwd=self.source_dir,\n                extra_environ={'PEP517_BUILD_BACKEND': build_backend}\n            )\n\n            data = compat.read_json(pjoin(td, 'output.json'))\n            if data.get('unsupported'):\n                raise UnsupportedOperation\n            if data.get('no_backend'):\n                raise BackendUnavailable\n            return data['return_val']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pkg_resources/__init__.py",
    "content": "# coding: utf-8\n\"\"\"\nPackage resource API\n--------------------\n\nA resource is a logical file contained within a package, or a logical\nsubdirectory thereof.  The package resource API expects resource names\nto have their path parts separated with ``/``, *not* whatever the local\npath separator is.  Do not use os.path operations to manipulate resource\nnames being passed into the API.\n\nThe package resource API is designed to work with normal filesystem packages,\n.egg files, and unpacked .egg files.  It can also work in a limited way with\n.zip files and with custom PEP 302 loaders that support the ``get_data()``\nmethod.\n\"\"\"\n\nfrom __future__ import absolute_import\n\nimport sys\nimport os\nimport io\nimport time\nimport re\nimport types\nimport zipfile\nimport zipimport\nimport warnings\nimport stat\nimport functools\nimport pkgutil\nimport operator\nimport platform\nimport collections\nimport plistlib\nimport email.parser\nimport errno\nimport tempfile\nimport textwrap\nimport itertools\nimport inspect\nfrom pkgutil import get_importer\n\ntry:\n    import _imp\nexcept ImportError:\n    # Python 3.2 compatibility\n    import imp as _imp\n\ntry:\n    FileExistsError\nexcept NameError:\n    FileExistsError = OSError\n\nfrom pip._vendor import six\nfrom pip._vendor.six.moves import urllib, map, filter\n\n# capture these to bypass sandboxing\nfrom os import utime\ntry:\n    from os import mkdir, rename, unlink\n    WRITE_SUPPORT = True\nexcept ImportError:\n    # no write support, probably under GAE\n    WRITE_SUPPORT = False\n\nfrom os import open as os_open\nfrom os.path import isdir, split\n\ntry:\n    import importlib.machinery as importlib_machinery\n    # access attribute to force import under delayed import mechanisms.\n    importlib_machinery.__name__\nexcept ImportError:\n    importlib_machinery = None\n\nfrom . import py31compat\nfrom pip._vendor import appdirs\nfrom pip._vendor import packaging\n__import__('pip._vendor.packaging.version')\n__import__('pip._vendor.packaging.specifiers')\n__import__('pip._vendor.packaging.requirements')\n__import__('pip._vendor.packaging.markers')\n\n\n__metaclass__ = type\n\n\nif (3, 0) < sys.version_info < (3, 4):\n    raise RuntimeError(\"Python 3.4 or later is required\")\n\nif six.PY2:\n    # Those builtin exceptions are only defined in Python 3\n    PermissionError = None\n    NotADirectoryError = None\n\n# declare some globals that will be defined later to\n# satisfy the linters.\nrequire = None\nworking_set = None\nadd_activation_listener = None\nresources_stream = None\ncleanup_resources = None\nresource_dir = None\nresource_stream = None\nset_extraction_path = None\nresource_isdir = None\nresource_string = None\niter_entry_points = None\nresource_listdir = None\nresource_filename = None\nresource_exists = None\n_distribution_finders = None\n_namespace_handlers = None\n_namespace_packages = None\n\n\nclass PEP440Warning(RuntimeWarning):\n    \"\"\"\n    Used when there is an issue with a version or specifier not complying with\n    PEP 440.\n    \"\"\"\n\n\ndef parse_version(v):\n    try:\n        return packaging.version.Version(v)\n    except packaging.version.InvalidVersion:\n        return packaging.version.LegacyVersion(v)\n\n\n_state_vars = {}\n\n\ndef _declare_state(vartype, **kw):\n    globals().update(kw)\n    _state_vars.update(dict.fromkeys(kw, vartype))\n\n\ndef __getstate__():\n    state = {}\n    g = globals()\n    for k, v in _state_vars.items():\n        state[k] = g['_sget_' + v](g[k])\n    return state\n\n\ndef __setstate__(state):\n    g = globals()\n    for k, v in state.items():\n        g['_sset_' + _state_vars[k]](k, g[k], v)\n    return state\n\n\ndef _sget_dict(val):\n    return val.copy()\n\n\ndef _sset_dict(key, ob, state):\n    ob.clear()\n    ob.update(state)\n\n\ndef _sget_object(val):\n    return val.__getstate__()\n\n\ndef _sset_object(key, ob, state):\n    ob.__setstate__(state)\n\n\n_sget_none = _sset_none = lambda *args: None\n\n\ndef get_supported_platform():\n    \"\"\"Return this platform's maximum compatible version.\n\n    distutils.util.get_platform() normally reports the minimum version\n    of Mac OS X that would be required to *use* extensions produced by\n    distutils.  But what we want when checking compatibility is to know the\n    version of Mac OS X that we are *running*.  To allow usage of packages that\n    explicitly require a newer version of Mac OS X, we must also know the\n    current version of the OS.\n\n    If this condition occurs for any other platform with a version in its\n    platform strings, this function should be extended accordingly.\n    \"\"\"\n    plat = get_build_platform()\n    m = macosVersionString.match(plat)\n    if m is not None and sys.platform == \"darwin\":\n        try:\n            plat = 'macosx-%s-%s' % ('.'.join(_macosx_vers()[:2]), m.group(3))\n        except ValueError:\n            # not Mac OS X\n            pass\n    return plat\n\n\n__all__ = [\n    # Basic resource access and distribution/entry point discovery\n    'require', 'run_script', 'get_provider', 'get_distribution',\n    'load_entry_point', 'get_entry_map', 'get_entry_info',\n    'iter_entry_points',\n    'resource_string', 'resource_stream', 'resource_filename',\n    'resource_listdir', 'resource_exists', 'resource_isdir',\n\n    # Environmental control\n    'declare_namespace', 'working_set', 'add_activation_listener',\n    'find_distributions', 'set_extraction_path', 'cleanup_resources',\n    'get_default_cache',\n\n    # Primary implementation classes\n    'Environment', 'WorkingSet', 'ResourceManager',\n    'Distribution', 'Requirement', 'EntryPoint',\n\n    # Exceptions\n    'ResolutionError', 'VersionConflict', 'DistributionNotFound',\n    'UnknownExtra', 'ExtractionError',\n\n    # Warnings\n    'PEP440Warning',\n\n    # Parsing functions and string utilities\n    'parse_requirements', 'parse_version', 'safe_name', 'safe_version',\n    'get_platform', 'compatible_platforms', 'yield_lines', 'split_sections',\n    'safe_extra', 'to_filename', 'invalid_marker', 'evaluate_marker',\n\n    # filesystem utilities\n    'ensure_directory', 'normalize_path',\n\n    # Distribution \"precedence\" constants\n    'EGG_DIST', 'BINARY_DIST', 'SOURCE_DIST', 'CHECKOUT_DIST', 'DEVELOP_DIST',\n\n    # \"Provider\" interfaces, implementations, and registration/lookup APIs\n    'IMetadataProvider', 'IResourceProvider', 'FileMetadata',\n    'PathMetadata', 'EggMetadata', 'EmptyProvider', 'empty_provider',\n    'NullProvider', 'EggProvider', 'DefaultProvider', 'ZipProvider',\n    'register_finder', 'register_namespace_handler', 'register_loader_type',\n    'fixup_namespace_packages', 'get_importer',\n\n    # Warnings\n    'PkgResourcesDeprecationWarning',\n\n    # Deprecated/backward compatibility only\n    'run_main', 'AvailableDistributions',\n]\n\n\nclass ResolutionError(Exception):\n    \"\"\"Abstract base for dependency resolution errors\"\"\"\n\n    def __repr__(self):\n        return self.__class__.__name__ + repr(self.args)\n\n\nclass VersionConflict(ResolutionError):\n    \"\"\"\n    An already-installed version conflicts with the requested version.\n\n    Should be initialized with the installed Distribution and the requested\n    Requirement.\n    \"\"\"\n\n    _template = \"{self.dist} is installed but {self.req} is required\"\n\n    @property\n    def dist(self):\n        return self.args[0]\n\n    @property\n    def req(self):\n        return self.args[1]\n\n    def report(self):\n        return self._template.format(**locals())\n\n    def with_context(self, required_by):\n        \"\"\"\n        If required_by is non-empty, return a version of self that is a\n        ContextualVersionConflict.\n        \"\"\"\n        if not required_by:\n            return self\n        args = self.args + (required_by,)\n        return ContextualVersionConflict(*args)\n\n\nclass ContextualVersionConflict(VersionConflict):\n    \"\"\"\n    A VersionConflict that accepts a third parameter, the set of the\n    requirements that required the installed Distribution.\n    \"\"\"\n\n    _template = VersionConflict._template + ' by {self.required_by}'\n\n    @property\n    def required_by(self):\n        return self.args[2]\n\n\nclass DistributionNotFound(ResolutionError):\n    \"\"\"A requested distribution was not found\"\"\"\n\n    _template = (\"The '{self.req}' distribution was not found \"\n                 \"and is required by {self.requirers_str}\")\n\n    @property\n    def req(self):\n        return self.args[0]\n\n    @property\n    def requirers(self):\n        return self.args[1]\n\n    @property\n    def requirers_str(self):\n        if not self.requirers:\n            return 'the application'\n        return ', '.join(self.requirers)\n\n    def report(self):\n        return self._template.format(**locals())\n\n    def __str__(self):\n        return self.report()\n\n\nclass UnknownExtra(ResolutionError):\n    \"\"\"Distribution doesn't have an \"extra feature\" of the given name\"\"\"\n\n\n_provider_factories = {}\n\nPY_MAJOR = sys.version[:3]\nEGG_DIST = 3\nBINARY_DIST = 2\nSOURCE_DIST = 1\nCHECKOUT_DIST = 0\nDEVELOP_DIST = -1\n\n\ndef register_loader_type(loader_type, provider_factory):\n    \"\"\"Register `provider_factory` to make providers for `loader_type`\n\n    `loader_type` is the type or class of a PEP 302 ``module.__loader__``,\n    and `provider_factory` is a function that, passed a *module* object,\n    returns an ``IResourceProvider`` for that module.\n    \"\"\"\n    _provider_factories[loader_type] = provider_factory\n\n\ndef get_provider(moduleOrReq):\n    \"\"\"Return an IResourceProvider for the named module or requirement\"\"\"\n    if isinstance(moduleOrReq, Requirement):\n        return working_set.find(moduleOrReq) or require(str(moduleOrReq))[0]\n    try:\n        module = sys.modules[moduleOrReq]\n    except KeyError:\n        __import__(moduleOrReq)\n        module = sys.modules[moduleOrReq]\n    loader = getattr(module, '__loader__', None)\n    return _find_adapter(_provider_factories, loader)(module)\n\n\ndef _macosx_vers(_cache=[]):\n    if not _cache:\n        version = platform.mac_ver()[0]\n        # fallback for MacPorts\n        if version == '':\n            plist = '/System/Library/CoreServices/SystemVersion.plist'\n            if os.path.exists(plist):\n                if hasattr(plistlib, 'readPlist'):\n                    plist_content = plistlib.readPlist(plist)\n                    if 'ProductVersion' in plist_content:\n                        version = plist_content['ProductVersion']\n\n        _cache.append(version.split('.'))\n    return _cache[0]\n\n\ndef _macosx_arch(machine):\n    return {'PowerPC': 'ppc', 'Power_Macintosh': 'ppc'}.get(machine, machine)\n\n\ndef get_build_platform():\n    \"\"\"Return this platform's string for platform-specific distributions\n\n    XXX Currently this is the same as ``distutils.util.get_platform()``, but it\n    needs some hacks for Linux and Mac OS X.\n    \"\"\"\n    from sysconfig import get_platform\n\n    plat = get_platform()\n    if sys.platform == \"darwin\" and not plat.startswith('macosx-'):\n        try:\n            version = _macosx_vers()\n            machine = os.uname()[4].replace(\" \", \"_\")\n            return \"macosx-%d.%d-%s\" % (\n                int(version[0]), int(version[1]),\n                _macosx_arch(machine),\n            )\n        except ValueError:\n            # if someone is running a non-Mac darwin system, this will fall\n            # through to the default implementation\n            pass\n    return plat\n\n\nmacosVersionString = re.compile(r\"macosx-(\\d+)\\.(\\d+)-(.*)\")\ndarwinVersionString = re.compile(r\"darwin-(\\d+)\\.(\\d+)\\.(\\d+)-(.*)\")\n# XXX backward compat\nget_platform = get_build_platform\n\n\ndef compatible_platforms(provided, required):\n    \"\"\"Can code for the `provided` platform run on the `required` platform?\n\n    Returns true if either platform is ``None``, or the platforms are equal.\n\n    XXX Needs compatibility checks for Linux and other unixy OSes.\n    \"\"\"\n    if provided is None or required is None or provided == required:\n        # easy case\n        return True\n\n    # Mac OS X special cases\n    reqMac = macosVersionString.match(required)\n    if reqMac:\n        provMac = macosVersionString.match(provided)\n\n        # is this a Mac package?\n        if not provMac:\n            # this is backwards compatibility for packages built before\n            # setuptools 0.6. All packages built after this point will\n            # use the new macosx designation.\n            provDarwin = darwinVersionString.match(provided)\n            if provDarwin:\n                dversion = int(provDarwin.group(1))\n                macosversion = \"%s.%s\" % (reqMac.group(1), reqMac.group(2))\n                if dversion == 7 and macosversion >= \"10.3\" or \\\n                        dversion == 8 and macosversion >= \"10.4\":\n                    return True\n            # egg isn't macosx or legacy darwin\n            return False\n\n        # are they the same major version and machine type?\n        if provMac.group(1) != reqMac.group(1) or \\\n                provMac.group(3) != reqMac.group(3):\n            return False\n\n        # is the required OS major update >= the provided one?\n        if int(provMac.group(2)) > int(reqMac.group(2)):\n            return False\n\n        return True\n\n    # XXX Linux and other platforms' special cases should go here\n    return False\n\n\ndef run_script(dist_spec, script_name):\n    \"\"\"Locate distribution `dist_spec` and run its `script_name` script\"\"\"\n    ns = sys._getframe(1).f_globals\n    name = ns['__name__']\n    ns.clear()\n    ns['__name__'] = name\n    require(dist_spec)[0].run_script(script_name, ns)\n\n\n# backward compatibility\nrun_main = run_script\n\n\ndef get_distribution(dist):\n    \"\"\"Return a current distribution object for a Requirement or string\"\"\"\n    if isinstance(dist, six.string_types):\n        dist = Requirement.parse(dist)\n    if isinstance(dist, Requirement):\n        dist = get_provider(dist)\n    if not isinstance(dist, Distribution):\n        raise TypeError(\"Expected string, Requirement, or Distribution\", dist)\n    return dist\n\n\ndef load_entry_point(dist, group, name):\n    \"\"\"Return `name` entry point of `group` for `dist` or raise ImportError\"\"\"\n    return get_distribution(dist).load_entry_point(group, name)\n\n\ndef get_entry_map(dist, group=None):\n    \"\"\"Return the entry point map for `group`, or the full entry map\"\"\"\n    return get_distribution(dist).get_entry_map(group)\n\n\ndef get_entry_info(dist, group, name):\n    \"\"\"Return the EntryPoint object for `group`+`name`, or ``None``\"\"\"\n    return get_distribution(dist).get_entry_info(group, name)\n\n\nclass IMetadataProvider:\n    def has_metadata(name):\n        \"\"\"Does the package's distribution contain the named metadata?\"\"\"\n\n    def get_metadata(name):\n        \"\"\"The named metadata resource as a string\"\"\"\n\n    def get_metadata_lines(name):\n        \"\"\"Yield named metadata resource as list of non-blank non-comment lines\n\n       Leading and trailing whitespace is stripped from each line, and lines\n       with ``#`` as the first non-blank character are omitted.\"\"\"\n\n    def metadata_isdir(name):\n        \"\"\"Is the named metadata a directory?  (like ``os.path.isdir()``)\"\"\"\n\n    def metadata_listdir(name):\n        \"\"\"List of metadata names in the directory (like ``os.listdir()``)\"\"\"\n\n    def run_script(script_name, namespace):\n        \"\"\"Execute the named script in the supplied namespace dictionary\"\"\"\n\n\nclass IResourceProvider(IMetadataProvider):\n    \"\"\"An object that provides access to package resources\"\"\"\n\n    def get_resource_filename(manager, resource_name):\n        \"\"\"Return a true filesystem path for `resource_name`\n\n        `manager` must be an ``IResourceManager``\"\"\"\n\n    def get_resource_stream(manager, resource_name):\n        \"\"\"Return a readable file-like object for `resource_name`\n\n        `manager` must be an ``IResourceManager``\"\"\"\n\n    def get_resource_string(manager, resource_name):\n        \"\"\"Return a string containing the contents of `resource_name`\n\n        `manager` must be an ``IResourceManager``\"\"\"\n\n    def has_resource(resource_name):\n        \"\"\"Does the package contain the named resource?\"\"\"\n\n    def resource_isdir(resource_name):\n        \"\"\"Is the named resource a directory?  (like ``os.path.isdir()``)\"\"\"\n\n    def resource_listdir(resource_name):\n        \"\"\"List of resource names in the directory (like ``os.listdir()``)\"\"\"\n\n\nclass WorkingSet:\n    \"\"\"A collection of active distributions on sys.path (or a similar list)\"\"\"\n\n    def __init__(self, entries=None):\n        \"\"\"Create working set from list of path entries (default=sys.path)\"\"\"\n        self.entries = []\n        self.entry_keys = {}\n        self.by_key = {}\n        self.callbacks = []\n\n        if entries is None:\n            entries = sys.path\n\n        for entry in entries:\n            self.add_entry(entry)\n\n    @classmethod\n    def _build_master(cls):\n        \"\"\"\n        Prepare the master working set.\n        \"\"\"\n        ws = cls()\n        try:\n            from __main__ import __requires__\n        except ImportError:\n            # The main program does not list any requirements\n            return ws\n\n        # ensure the requirements are met\n        try:\n            ws.require(__requires__)\n        except VersionConflict:\n            return cls._build_from_requirements(__requires__)\n\n        return ws\n\n    @classmethod\n    def _build_from_requirements(cls, req_spec):\n        \"\"\"\n        Build a working set from a requirement spec. Rewrites sys.path.\n        \"\"\"\n        # try it without defaults already on sys.path\n        # by starting with an empty path\n        ws = cls([])\n        reqs = parse_requirements(req_spec)\n        dists = ws.resolve(reqs, Environment())\n        for dist in dists:\n            ws.add(dist)\n\n        # add any missing entries from sys.path\n        for entry in sys.path:\n            if entry not in ws.entries:\n                ws.add_entry(entry)\n\n        # then copy back to sys.path\n        sys.path[:] = ws.entries\n        return ws\n\n    def add_entry(self, entry):\n        \"\"\"Add a path item to ``.entries``, finding any distributions on it\n\n        ``find_distributions(entry, True)`` is used to find distributions\n        corresponding to the path entry, and they are added.  `entry` is\n        always appended to ``.entries``, even if it is already present.\n        (This is because ``sys.path`` can contain the same value more than\n        once, and the ``.entries`` of the ``sys.path`` WorkingSet should always\n        equal ``sys.path``.)\n        \"\"\"\n        self.entry_keys.setdefault(entry, [])\n        self.entries.append(entry)\n        for dist in find_distributions(entry, True):\n            self.add(dist, entry, False)\n\n    def __contains__(self, dist):\n        \"\"\"True if `dist` is the active distribution for its project\"\"\"\n        return self.by_key.get(dist.key) == dist\n\n    def find(self, req):\n        \"\"\"Find a distribution matching requirement `req`\n\n        If there is an active distribution for the requested project, this\n        returns it as long as it meets the version requirement specified by\n        `req`.  But, if there is an active distribution for the project and it\n        does *not* meet the `req` requirement, ``VersionConflict`` is raised.\n        If there is no active distribution for the requested project, ``None``\n        is returned.\n        \"\"\"\n        dist = self.by_key.get(req.key)\n        if dist is not None and dist not in req:\n            # XXX add more info\n            raise VersionConflict(dist, req)\n        return dist\n\n    def iter_entry_points(self, group, name=None):\n        \"\"\"Yield entry point objects from `group` matching `name`\n\n        If `name` is None, yields all entry points in `group` from all\n        distributions in the working set, otherwise only ones matching\n        both `group` and `name` are yielded (in distribution order).\n        \"\"\"\n        return (\n            entry\n            for dist in self\n            for entry in dist.get_entry_map(group).values()\n            if name is None or name == entry.name\n        )\n\n    def run_script(self, requires, script_name):\n        \"\"\"Locate distribution for `requires` and run `script_name` script\"\"\"\n        ns = sys._getframe(1).f_globals\n        name = ns['__name__']\n        ns.clear()\n        ns['__name__'] = name\n        self.require(requires)[0].run_script(script_name, ns)\n\n    def __iter__(self):\n        \"\"\"Yield distributions for non-duplicate projects in the working set\n\n        The yield order is the order in which the items' path entries were\n        added to the working set.\n        \"\"\"\n        seen = {}\n        for item in self.entries:\n            if item not in self.entry_keys:\n                # workaround a cache issue\n                continue\n\n            for key in self.entry_keys[item]:\n                if key not in seen:\n                    seen[key] = 1\n                    yield self.by_key[key]\n\n    def add(self, dist, entry=None, insert=True, replace=False):\n        \"\"\"Add `dist` to working set, associated with `entry`\n\n        If `entry` is unspecified, it defaults to the ``.location`` of `dist`.\n        On exit from this routine, `entry` is added to the end of the working\n        set's ``.entries`` (if it wasn't already present).\n\n        `dist` is only added to the working set if it's for a project that\n        doesn't already have a distribution in the set, unless `replace=True`.\n        If it's added, any callbacks registered with the ``subscribe()`` method\n        will be called.\n        \"\"\"\n        if insert:\n            dist.insert_on(self.entries, entry, replace=replace)\n\n        if entry is None:\n            entry = dist.location\n        keys = self.entry_keys.setdefault(entry, [])\n        keys2 = self.entry_keys.setdefault(dist.location, [])\n        if not replace and dist.key in self.by_key:\n            # ignore hidden distros\n            return\n\n        self.by_key[dist.key] = dist\n        if dist.key not in keys:\n            keys.append(dist.key)\n        if dist.key not in keys2:\n            keys2.append(dist.key)\n        self._added_new(dist)\n\n    def resolve(self, requirements, env=None, installer=None,\n                replace_conflicting=False, extras=None):\n        \"\"\"List all distributions needed to (recursively) meet `requirements`\n\n        `requirements` must be a sequence of ``Requirement`` objects.  `env`,\n        if supplied, should be an ``Environment`` instance.  If\n        not supplied, it defaults to all distributions available within any\n        entry or distribution in the working set.  `installer`, if supplied,\n        will be invoked with each requirement that cannot be met by an\n        already-installed distribution; it should return a ``Distribution`` or\n        ``None``.\n\n        Unless `replace_conflicting=True`, raises a VersionConflict exception\n        if\n        any requirements are found on the path that have the correct name but\n        the wrong version.  Otherwise, if an `installer` is supplied it will be\n        invoked to obtain the correct version of the requirement and activate\n        it.\n\n        `extras` is a list of the extras to be used with these requirements.\n        This is important because extra requirements may look like `my_req;\n        extra = \"my_extra\"`, which would otherwise be interpreted as a purely\n        optional requirement.  Instead, we want to be able to assert that these\n        requirements are truly required.\n        \"\"\"\n\n        # set up the stack\n        requirements = list(requirements)[::-1]\n        # set of processed requirements\n        processed = {}\n        # key -> dist\n        best = {}\n        to_activate = []\n\n        req_extras = _ReqExtras()\n\n        # Mapping of requirement to set of distributions that required it;\n        # useful for reporting info about conflicts.\n        required_by = collections.defaultdict(set)\n\n        while requirements:\n            # process dependencies breadth-first\n            req = requirements.pop(0)\n            if req in processed:\n                # Ignore cyclic or redundant dependencies\n                continue\n\n            if not req_extras.markers_pass(req, extras):\n                continue\n\n            dist = best.get(req.key)\n            if dist is None:\n                # Find the best distribution and add it to the map\n                dist = self.by_key.get(req.key)\n                if dist is None or (dist not in req and replace_conflicting):\n                    ws = self\n                    if env is None:\n                        if dist is None:\n                            env = Environment(self.entries)\n                        else:\n                            # Use an empty environment and workingset to avoid\n                            # any further conflicts with the conflicting\n                            # distribution\n                            env = Environment([])\n                            ws = WorkingSet([])\n                    dist = best[req.key] = env.best_match(\n                        req, ws, installer,\n                        replace_conflicting=replace_conflicting\n                    )\n                    if dist is None:\n                        requirers = required_by.get(req, None)\n                        raise DistributionNotFound(req, requirers)\n                to_activate.append(dist)\n            if dist not in req:\n                # Oops, the \"best\" so far conflicts with a dependency\n                dependent_req = required_by[req]\n                raise VersionConflict(dist, req).with_context(dependent_req)\n\n            # push the new requirements onto the stack\n            new_requirements = dist.requires(req.extras)[::-1]\n            requirements.extend(new_requirements)\n\n            # Register the new requirements needed by req\n            for new_requirement in new_requirements:\n                required_by[new_requirement].add(req.project_name)\n                req_extras[new_requirement] = req.extras\n\n            processed[req] = True\n\n        # return list of distros to activate\n        return to_activate\n\n    def find_plugins(\n            self, plugin_env, full_env=None, installer=None, fallback=True):\n        \"\"\"Find all activatable distributions in `plugin_env`\n\n        Example usage::\n\n            distributions, errors = working_set.find_plugins(\n                Environment(plugin_dirlist)\n            )\n            # add plugins+libs to sys.path\n            map(working_set.add, distributions)\n            # display errors\n            print('Could not load', errors)\n\n        The `plugin_env` should be an ``Environment`` instance that contains\n        only distributions that are in the project's \"plugin directory\" or\n        directories. The `full_env`, if supplied, should be an ``Environment``\n        contains all currently-available distributions.  If `full_env` is not\n        supplied, one is created automatically from the ``WorkingSet`` this\n        method is called on, which will typically mean that every directory on\n        ``sys.path`` will be scanned for distributions.\n\n        `installer` is a standard installer callback as used by the\n        ``resolve()`` method. The `fallback` flag indicates whether we should\n        attempt to resolve older versions of a plugin if the newest version\n        cannot be resolved.\n\n        This method returns a 2-tuple: (`distributions`, `error_info`), where\n        `distributions` is a list of the distributions found in `plugin_env`\n        that were loadable, along with any other distributions that are needed\n        to resolve their dependencies.  `error_info` is a dictionary mapping\n        unloadable plugin distributions to an exception instance describing the\n        error that occurred. Usually this will be a ``DistributionNotFound`` or\n        ``VersionConflict`` instance.\n        \"\"\"\n\n        plugin_projects = list(plugin_env)\n        # scan project names in alphabetic order\n        plugin_projects.sort()\n\n        error_info = {}\n        distributions = {}\n\n        if full_env is None:\n            env = Environment(self.entries)\n            env += plugin_env\n        else:\n            env = full_env + plugin_env\n\n        shadow_set = self.__class__([])\n        # put all our entries in shadow_set\n        list(map(shadow_set.add, self))\n\n        for project_name in plugin_projects:\n\n            for dist in plugin_env[project_name]:\n\n                req = [dist.as_requirement()]\n\n                try:\n                    resolvees = shadow_set.resolve(req, env, installer)\n\n                except ResolutionError as v:\n                    # save error info\n                    error_info[dist] = v\n                    if fallback:\n                        # try the next older version of project\n                        continue\n                    else:\n                        # give up on this project, keep going\n                        break\n\n                else:\n                    list(map(shadow_set.add, resolvees))\n                    distributions.update(dict.fromkeys(resolvees))\n\n                    # success, no need to try any more versions of this project\n                    break\n\n        distributions = list(distributions)\n        distributions.sort()\n\n        return distributions, error_info\n\n    def require(self, *requirements):\n        \"\"\"Ensure that distributions matching `requirements` are activated\n\n        `requirements` must be a string or a (possibly-nested) sequence\n        thereof, specifying the distributions and versions required.  The\n        return value is a sequence of the distributions that needed to be\n        activated to fulfill the requirements; all relevant distributions are\n        included, even if they were already activated in this working set.\n        \"\"\"\n        needed = self.resolve(parse_requirements(requirements))\n\n        for dist in needed:\n            self.add(dist)\n\n        return needed\n\n    def subscribe(self, callback, existing=True):\n        \"\"\"Invoke `callback` for all distributions\n\n        If `existing=True` (default),\n        call on all existing ones, as well.\n        \"\"\"\n        if callback in self.callbacks:\n            return\n        self.callbacks.append(callback)\n        if not existing:\n            return\n        for dist in self:\n            callback(dist)\n\n    def _added_new(self, dist):\n        for callback in self.callbacks:\n            callback(dist)\n\n    def __getstate__(self):\n        return (\n            self.entries[:], self.entry_keys.copy(), self.by_key.copy(),\n            self.callbacks[:]\n        )\n\n    def __setstate__(self, e_k_b_c):\n        entries, keys, by_key, callbacks = e_k_b_c\n        self.entries = entries[:]\n        self.entry_keys = keys.copy()\n        self.by_key = by_key.copy()\n        self.callbacks = callbacks[:]\n\n\nclass _ReqExtras(dict):\n    \"\"\"\n    Map each requirement to the extras that demanded it.\n    \"\"\"\n\n    def markers_pass(self, req, extras=None):\n        \"\"\"\n        Evaluate markers for req against each extra that\n        demanded it.\n\n        Return False if the req has a marker and fails\n        evaluation. Otherwise, return True.\n        \"\"\"\n        extra_evals = (\n            req.marker.evaluate({'extra': extra})\n            for extra in self.get(req, ()) + (extras or (None,))\n        )\n        return not req.marker or any(extra_evals)\n\n\nclass Environment:\n    \"\"\"Searchable snapshot of distributions on a search path\"\"\"\n\n    def __init__(\n            self, search_path=None, platform=get_supported_platform(),\n            python=PY_MAJOR):\n        \"\"\"Snapshot distributions available on a search path\n\n        Any distributions found on `search_path` are added to the environment.\n        `search_path` should be a sequence of ``sys.path`` items.  If not\n        supplied, ``sys.path`` is used.\n\n        `platform` is an optional string specifying the name of the platform\n        that platform-specific distributions must be compatible with.  If\n        unspecified, it defaults to the current platform.  `python` is an\n        optional string naming the desired version of Python (e.g. ``'3.6'``);\n        it defaults to the current version.\n\n        You may explicitly set `platform` (and/or `python`) to ``None`` if you\n        wish to map *all* distributions, not just those compatible with the\n        running platform or Python version.\n        \"\"\"\n        self._distmap = {}\n        self.platform = platform\n        self.python = python\n        self.scan(search_path)\n\n    def can_add(self, dist):\n        \"\"\"Is distribution `dist` acceptable for this environment?\n\n        The distribution must match the platform and python version\n        requirements specified when this environment was created, or False\n        is returned.\n        \"\"\"\n        py_compat = (\n            self.python is None\n            or dist.py_version is None\n            or dist.py_version == self.python\n        )\n        return py_compat and compatible_platforms(dist.platform, self.platform)\n\n    def remove(self, dist):\n        \"\"\"Remove `dist` from the environment\"\"\"\n        self._distmap[dist.key].remove(dist)\n\n    def scan(self, search_path=None):\n        \"\"\"Scan `search_path` for distributions usable in this environment\n\n        Any distributions found are added to the environment.\n        `search_path` should be a sequence of ``sys.path`` items.  If not\n        supplied, ``sys.path`` is used.  Only distributions conforming to\n        the platform/python version defined at initialization are added.\n        \"\"\"\n        if search_path is None:\n            search_path = sys.path\n\n        for item in search_path:\n            for dist in find_distributions(item):\n                self.add(dist)\n\n    def __getitem__(self, project_name):\n        \"\"\"Return a newest-to-oldest list of distributions for `project_name`\n\n        Uses case-insensitive `project_name` comparison, assuming all the\n        project's distributions use their project's name converted to all\n        lowercase as their key.\n\n        \"\"\"\n        distribution_key = project_name.lower()\n        return self._distmap.get(distribution_key, [])\n\n    def add(self, dist):\n        \"\"\"Add `dist` if we ``can_add()`` it and it has not already been added\n        \"\"\"\n        if self.can_add(dist) and dist.has_version():\n            dists = self._distmap.setdefault(dist.key, [])\n            if dist not in dists:\n                dists.append(dist)\n                dists.sort(key=operator.attrgetter('hashcmp'), reverse=True)\n\n    def best_match(\n            self, req, working_set, installer=None, replace_conflicting=False):\n        \"\"\"Find distribution best matching `req` and usable on `working_set`\n\n        This calls the ``find(req)`` method of the `working_set` to see if a\n        suitable distribution is already active.  (This may raise\n        ``VersionConflict`` if an unsuitable version of the project is already\n        active in the specified `working_set`.)  If a suitable distribution\n        isn't active, this method returns the newest distribution in the\n        environment that meets the ``Requirement`` in `req`.  If no suitable\n        distribution is found, and `installer` is supplied, then the result of\n        calling the environment's ``obtain(req, installer)`` method will be\n        returned.\n        \"\"\"\n        try:\n            dist = working_set.find(req)\n        except VersionConflict:\n            if not replace_conflicting:\n                raise\n            dist = None\n        if dist is not None:\n            return dist\n        for dist in self[req.key]:\n            if dist in req:\n                return dist\n        # try to download/install\n        return self.obtain(req, installer)\n\n    def obtain(self, requirement, installer=None):\n        \"\"\"Obtain a distribution matching `requirement` (e.g. via download)\n\n        Obtain a distro that matches requirement (e.g. via download).  In the\n        base ``Environment`` class, this routine just returns\n        ``installer(requirement)``, unless `installer` is None, in which case\n        None is returned instead.  This method is a hook that allows subclasses\n        to attempt other ways of obtaining a distribution before falling back\n        to the `installer` argument.\"\"\"\n        if installer is not None:\n            return installer(requirement)\n\n    def __iter__(self):\n        \"\"\"Yield the unique project names of the available distributions\"\"\"\n        for key in self._distmap.keys():\n            if self[key]:\n                yield key\n\n    def __iadd__(self, other):\n        \"\"\"In-place addition of a distribution or environment\"\"\"\n        if isinstance(other, Distribution):\n            self.add(other)\n        elif isinstance(other, Environment):\n            for project in other:\n                for dist in other[project]:\n                    self.add(dist)\n        else:\n            raise TypeError(\"Can't add %r to environment\" % (other,))\n        return self\n\n    def __add__(self, other):\n        \"\"\"Add an environment or distribution to an environment\"\"\"\n        new = self.__class__([], platform=None, python=None)\n        for env in self, other:\n            new += env\n        return new\n\n\n# XXX backward compatibility\nAvailableDistributions = Environment\n\n\nclass ExtractionError(RuntimeError):\n    \"\"\"An error occurred extracting a resource\n\n    The following attributes are available from instances of this exception:\n\n    manager\n        The resource manager that raised this exception\n\n    cache_path\n        The base directory for resource extraction\n\n    original_error\n        The exception instance that caused extraction to fail\n    \"\"\"\n\n\nclass ResourceManager:\n    \"\"\"Manage resource extraction and packages\"\"\"\n    extraction_path = None\n\n    def __init__(self):\n        self.cached_files = {}\n\n    def resource_exists(self, package_or_requirement, resource_name):\n        \"\"\"Does the named resource exist?\"\"\"\n        return get_provider(package_or_requirement).has_resource(resource_name)\n\n    def resource_isdir(self, package_or_requirement, resource_name):\n        \"\"\"Is the named resource an existing directory?\"\"\"\n        return get_provider(package_or_requirement).resource_isdir(\n            resource_name\n        )\n\n    def resource_filename(self, package_or_requirement, resource_name):\n        \"\"\"Return a true filesystem path for specified resource\"\"\"\n        return get_provider(package_or_requirement).get_resource_filename(\n            self, resource_name\n        )\n\n    def resource_stream(self, package_or_requirement, resource_name):\n        \"\"\"Return a readable file-like object for specified resource\"\"\"\n        return get_provider(package_or_requirement).get_resource_stream(\n            self, resource_name\n        )\n\n    def resource_string(self, package_or_requirement, resource_name):\n        \"\"\"Return specified resource as a string\"\"\"\n        return get_provider(package_or_requirement).get_resource_string(\n            self, resource_name\n        )\n\n    def resource_listdir(self, package_or_requirement, resource_name):\n        \"\"\"List the contents of the named resource directory\"\"\"\n        return get_provider(package_or_requirement).resource_listdir(\n            resource_name\n        )\n\n    def extraction_error(self):\n        \"\"\"Give an error message for problems extracting file(s)\"\"\"\n\n        old_exc = sys.exc_info()[1]\n        cache_path = self.extraction_path or get_default_cache()\n\n        tmpl = textwrap.dedent(\"\"\"\n            Can't extract file(s) to egg cache\n\n            The following error occurred while trying to extract file(s)\n            to the Python egg cache:\n\n              {old_exc}\n\n            The Python egg cache directory is currently set to:\n\n              {cache_path}\n\n            Perhaps your account does not have write access to this directory?\n            You can change the cache directory by setting the PYTHON_EGG_CACHE\n            environment variable to point to an accessible directory.\n            \"\"\").lstrip()\n        err = ExtractionError(tmpl.format(**locals()))\n        err.manager = self\n        err.cache_path = cache_path\n        err.original_error = old_exc\n        raise err\n\n    def get_cache_path(self, archive_name, names=()):\n        \"\"\"Return absolute location in cache for `archive_name` and `names`\n\n        The parent directory of the resulting path will be created if it does\n        not already exist.  `archive_name` should be the base filename of the\n        enclosing egg (which may not be the name of the enclosing zipfile!),\n        including its \".egg\" extension.  `names`, if provided, should be a\n        sequence of path name parts \"under\" the egg's extraction location.\n\n        This method should only be called by resource providers that need to\n        obtain an extraction location, and only for names they intend to\n        extract, as it tracks the generated names for possible cleanup later.\n        \"\"\"\n        extract_path = self.extraction_path or get_default_cache()\n        target_path = os.path.join(extract_path, archive_name + '-tmp', *names)\n        try:\n            _bypass_ensure_directory(target_path)\n        except Exception:\n            self.extraction_error()\n\n        self._warn_unsafe_extraction_path(extract_path)\n\n        self.cached_files[target_path] = 1\n        return target_path\n\n    @staticmethod\n    def _warn_unsafe_extraction_path(path):\n        \"\"\"\n        If the default extraction path is overridden and set to an insecure\n        location, such as /tmp, it opens up an opportunity for an attacker to\n        replace an extracted file with an unauthorized payload. Warn the user\n        if a known insecure location is used.\n\n        See Distribute #375 for more details.\n        \"\"\"\n        if os.name == 'nt' and not path.startswith(os.environ['windir']):\n            # On Windows, permissions are generally restrictive by default\n            #  and temp directories are not writable by other users, so\n            #  bypass the warning.\n            return\n        mode = os.stat(path).st_mode\n        if mode & stat.S_IWOTH or mode & stat.S_IWGRP:\n            msg = (\n                \"%s is writable by group/others and vulnerable to attack \"\n                \"when \"\n                \"used with get_resource_filename. Consider a more secure \"\n                \"location (set with .set_extraction_path or the \"\n                \"PYTHON_EGG_CACHE environment variable).\" % path\n            )\n            warnings.warn(msg, UserWarning)\n\n    def postprocess(self, tempname, filename):\n        \"\"\"Perform any platform-specific postprocessing of `tempname`\n\n        This is where Mac header rewrites should be done; other platforms don't\n        have anything special they should do.\n\n        Resource providers should call this method ONLY after successfully\n        extracting a compressed resource.  They must NOT call it on resources\n        that are already in the filesystem.\n\n        `tempname` is the current (temporary) name of the file, and `filename`\n        is the name it will be renamed to by the caller after this routine\n        returns.\n        \"\"\"\n\n        if os.name == 'posix':\n            # Make the resource executable\n            mode = ((os.stat(tempname).st_mode) | 0o555) & 0o7777\n            os.chmod(tempname, mode)\n\n    def set_extraction_path(self, path):\n        \"\"\"Set the base path where resources will be extracted to, if needed.\n\n        If you do not call this routine before any extractions take place, the\n        path defaults to the return value of ``get_default_cache()``.  (Which\n        is based on the ``PYTHON_EGG_CACHE`` environment variable, with various\n        platform-specific fallbacks.  See that routine's documentation for more\n        details.)\n\n        Resources are extracted to subdirectories of this path based upon\n        information given by the ``IResourceProvider``.  You may set this to a\n        temporary directory, but then you must call ``cleanup_resources()`` to\n        delete the extracted files when done.  There is no guarantee that\n        ``cleanup_resources()`` will be able to remove all extracted files.\n\n        (Note: you may not change the extraction path for a given resource\n        manager once resources have been extracted, unless you first call\n        ``cleanup_resources()``.)\n        \"\"\"\n        if self.cached_files:\n            raise ValueError(\n                \"Can't change extraction path, files already extracted\"\n            )\n\n        self.extraction_path = path\n\n    def cleanup_resources(self, force=False):\n        \"\"\"\n        Delete all extracted resource files and directories, returning a list\n        of the file and directory names that could not be successfully removed.\n        This function does not have any concurrency protection, so it should\n        generally only be called when the extraction path is a temporary\n        directory exclusive to a single process.  This method is not\n        automatically called; you must call it explicitly or register it as an\n        ``atexit`` function if you wish to ensure cleanup of a temporary\n        directory used for extractions.\n        \"\"\"\n        # XXX\n\n\ndef get_default_cache():\n    \"\"\"\n    Return the ``PYTHON_EGG_CACHE`` environment variable\n    or a platform-relevant user cache dir for an app\n    named \"Python-Eggs\".\n    \"\"\"\n    return (\n        os.environ.get('PYTHON_EGG_CACHE')\n        or appdirs.user_cache_dir(appname='Python-Eggs')\n    )\n\n\ndef safe_name(name):\n    \"\"\"Convert an arbitrary string to a standard distribution name\n\n    Any runs of non-alphanumeric/. characters are replaced with a single '-'.\n    \"\"\"\n    return re.sub('[^A-Za-z0-9.]+', '-', name)\n\n\ndef safe_version(version):\n    \"\"\"\n    Convert an arbitrary string to a standard version string\n    \"\"\"\n    try:\n        # normalize the version\n        return str(packaging.version.Version(version))\n    except packaging.version.InvalidVersion:\n        version = version.replace(' ', '.')\n        return re.sub('[^A-Za-z0-9.]+', '-', version)\n\n\ndef safe_extra(extra):\n    \"\"\"Convert an arbitrary string to a standard 'extra' name\n\n    Any runs of non-alphanumeric characters are replaced with a single '_',\n    and the result is always lowercased.\n    \"\"\"\n    return re.sub('[^A-Za-z0-9.-]+', '_', extra).lower()\n\n\ndef to_filename(name):\n    \"\"\"Convert a project or version name to its filename-escaped form\n\n    Any '-' characters are currently replaced with '_'.\n    \"\"\"\n    return name.replace('-', '_')\n\n\ndef invalid_marker(text):\n    \"\"\"\n    Validate text as a PEP 508 environment marker; return an exception\n    if invalid or False otherwise.\n    \"\"\"\n    try:\n        evaluate_marker(text)\n    except SyntaxError as e:\n        e.filename = None\n        e.lineno = None\n        return e\n    return False\n\n\ndef evaluate_marker(text, extra=None):\n    \"\"\"\n    Evaluate a PEP 508 environment marker.\n    Return a boolean indicating the marker result in this environment.\n    Raise SyntaxError if marker is invalid.\n\n    This implementation uses the 'pyparsing' module.\n    \"\"\"\n    try:\n        marker = packaging.markers.Marker(text)\n        return marker.evaluate()\n    except packaging.markers.InvalidMarker as e:\n        raise SyntaxError(e)\n\n\nclass NullProvider:\n    \"\"\"Try to implement resources and metadata for arbitrary PEP 302 loaders\"\"\"\n\n    egg_name = None\n    egg_info = None\n    loader = None\n\n    def __init__(self, module):\n        self.loader = getattr(module, '__loader__', None)\n        self.module_path = os.path.dirname(getattr(module, '__file__', ''))\n\n    def get_resource_filename(self, manager, resource_name):\n        return self._fn(self.module_path, resource_name)\n\n    def get_resource_stream(self, manager, resource_name):\n        return io.BytesIO(self.get_resource_string(manager, resource_name))\n\n    def get_resource_string(self, manager, resource_name):\n        return self._get(self._fn(self.module_path, resource_name))\n\n    def has_resource(self, resource_name):\n        return self._has(self._fn(self.module_path, resource_name))\n\n    def has_metadata(self, name):\n        return self.egg_info and self._has(self._fn(self.egg_info, name))\n\n    def get_metadata(self, name):\n        if not self.egg_info:\n            return \"\"\n        value = self._get(self._fn(self.egg_info, name))\n        return value.decode('utf-8') if six.PY3 else value\n\n    def get_metadata_lines(self, name):\n        return yield_lines(self.get_metadata(name))\n\n    def resource_isdir(self, resource_name):\n        return self._isdir(self._fn(self.module_path, resource_name))\n\n    def metadata_isdir(self, name):\n        return self.egg_info and self._isdir(self._fn(self.egg_info, name))\n\n    def resource_listdir(self, resource_name):\n        return self._listdir(self._fn(self.module_path, resource_name))\n\n    def metadata_listdir(self, name):\n        if self.egg_info:\n            return self._listdir(self._fn(self.egg_info, name))\n        return []\n\n    def run_script(self, script_name, namespace):\n        script = 'scripts/' + script_name\n        if not self.has_metadata(script):\n            raise ResolutionError(\n                \"Script {script!r} not found in metadata at {self.egg_info!r}\"\n                .format(**locals()),\n            )\n        script_text = self.get_metadata(script).replace('\\r\\n', '\\n')\n        script_text = script_text.replace('\\r', '\\n')\n        script_filename = self._fn(self.egg_info, script)\n        namespace['__file__'] = script_filename\n        if os.path.exists(script_filename):\n            source = open(script_filename).read()\n            code = compile(source, script_filename, 'exec')\n            exec(code, namespace, namespace)\n        else:\n            from linecache import cache\n            cache[script_filename] = (\n                len(script_text), 0, script_text.split('\\n'), script_filename\n            )\n            script_code = compile(script_text, script_filename, 'exec')\n            exec(script_code, namespace, namespace)\n\n    def _has(self, path):\n        raise NotImplementedError(\n            \"Can't perform this operation for unregistered loader type\"\n        )\n\n    def _isdir(self, path):\n        raise NotImplementedError(\n            \"Can't perform this operation for unregistered loader type\"\n        )\n\n    def _listdir(self, path):\n        raise NotImplementedError(\n            \"Can't perform this operation for unregistered loader type\"\n        )\n\n    def _fn(self, base, resource_name):\n        if resource_name:\n            return os.path.join(base, *resource_name.split('/'))\n        return base\n\n    def _get(self, path):\n        if hasattr(self.loader, 'get_data'):\n            return self.loader.get_data(path)\n        raise NotImplementedError(\n            \"Can't perform this operation for loaders without 'get_data()'\"\n        )\n\n\nregister_loader_type(object, NullProvider)\n\n\nclass EggProvider(NullProvider):\n    \"\"\"Provider based on a virtual filesystem\"\"\"\n\n    def __init__(self, module):\n        NullProvider.__init__(self, module)\n        self._setup_prefix()\n\n    def _setup_prefix(self):\n        # we assume here that our metadata may be nested inside a \"basket\"\n        # of multiple eggs; that's why we use module_path instead of .archive\n        path = self.module_path\n        old = None\n        while path != old:\n            if _is_egg_path(path):\n                self.egg_name = os.path.basename(path)\n                self.egg_info = os.path.join(path, 'EGG-INFO')\n                self.egg_root = path\n                break\n            old = path\n            path, base = os.path.split(path)\n\n\nclass DefaultProvider(EggProvider):\n    \"\"\"Provides access to package resources in the filesystem\"\"\"\n\n    def _has(self, path):\n        return os.path.exists(path)\n\n    def _isdir(self, path):\n        return os.path.isdir(path)\n\n    def _listdir(self, path):\n        return os.listdir(path)\n\n    def get_resource_stream(self, manager, resource_name):\n        return open(self._fn(self.module_path, resource_name), 'rb')\n\n    def _get(self, path):\n        with open(path, 'rb') as stream:\n            return stream.read()\n\n    @classmethod\n    def _register(cls):\n        loader_names = 'SourceFileLoader', 'SourcelessFileLoader',\n        for name in loader_names:\n            loader_cls = getattr(importlib_machinery, name, type(None))\n            register_loader_type(loader_cls, cls)\n\n\nDefaultProvider._register()\n\n\nclass EmptyProvider(NullProvider):\n    \"\"\"Provider that returns nothing for all requests\"\"\"\n\n    module_path = None\n\n    _isdir = _has = lambda self, path: False\n\n    def _get(self, path):\n        return ''\n\n    def _listdir(self, path):\n        return []\n\n    def __init__(self):\n        pass\n\n\nempty_provider = EmptyProvider()\n\n\nclass ZipManifests(dict):\n    \"\"\"\n    zip manifest builder\n    \"\"\"\n\n    @classmethod\n    def build(cls, path):\n        \"\"\"\n        Build a dictionary similar to the zipimport directory\n        caches, except instead of tuples, store ZipInfo objects.\n\n        Use a platform-specific path separator (os.sep) for the path keys\n        for compatibility with pypy on Windows.\n        \"\"\"\n        with zipfile.ZipFile(path) as zfile:\n            items = (\n                (\n                    name.replace('/', os.sep),\n                    zfile.getinfo(name),\n                )\n                for name in zfile.namelist()\n            )\n            return dict(items)\n\n    load = build\n\n\nclass MemoizedZipManifests(ZipManifests):\n    \"\"\"\n    Memoized zipfile manifests.\n    \"\"\"\n    manifest_mod = collections.namedtuple('manifest_mod', 'manifest mtime')\n\n    def load(self, path):\n        \"\"\"\n        Load a manifest at path or return a suitable manifest already loaded.\n        \"\"\"\n        path = os.path.normpath(path)\n        mtime = os.stat(path).st_mtime\n\n        if path not in self or self[path].mtime != mtime:\n            manifest = self.build(path)\n            self[path] = self.manifest_mod(manifest, mtime)\n\n        return self[path].manifest\n\n\nclass ZipProvider(EggProvider):\n    \"\"\"Resource support for zips and eggs\"\"\"\n\n    eagers = None\n    _zip_manifests = MemoizedZipManifests()\n\n    def __init__(self, module):\n        EggProvider.__init__(self, module)\n        self.zip_pre = self.loader.archive + os.sep\n\n    def _zipinfo_name(self, fspath):\n        # Convert a virtual filename (full path to file) into a zipfile subpath\n        # usable with the zipimport directory cache for our target archive\n        fspath = fspath.rstrip(os.sep)\n        if fspath == self.loader.archive:\n            return ''\n        if fspath.startswith(self.zip_pre):\n            return fspath[len(self.zip_pre):]\n        raise AssertionError(\n            \"%s is not a subpath of %s\" % (fspath, self.zip_pre)\n        )\n\n    def _parts(self, zip_path):\n        # Convert a zipfile subpath into an egg-relative path part list.\n        # pseudo-fs path\n        fspath = self.zip_pre + zip_path\n        if fspath.startswith(self.egg_root + os.sep):\n            return fspath[len(self.egg_root) + 1:].split(os.sep)\n        raise AssertionError(\n            \"%s is not a subpath of %s\" % (fspath, self.egg_root)\n        )\n\n    @property\n    def zipinfo(self):\n        return self._zip_manifests.load(self.loader.archive)\n\n    def get_resource_filename(self, manager, resource_name):\n        if not self.egg_name:\n            raise NotImplementedError(\n                \"resource_filename() only supported for .egg, not .zip\"\n            )\n        # no need to lock for extraction, since we use temp names\n        zip_path = self._resource_to_zip(resource_name)\n        eagers = self._get_eager_resources()\n        if '/'.join(self._parts(zip_path)) in eagers:\n            for name in eagers:\n                self._extract_resource(manager, self._eager_to_zip(name))\n        return self._extract_resource(manager, zip_path)\n\n    @staticmethod\n    def _get_date_and_size(zip_stat):\n        size = zip_stat.file_size\n        # ymdhms+wday, yday, dst\n        date_time = zip_stat.date_time + (0, 0, -1)\n        # 1980 offset already done\n        timestamp = time.mktime(date_time)\n        return timestamp, size\n\n    def _extract_resource(self, manager, zip_path):\n\n        if zip_path in self._index():\n            for name in self._index()[zip_path]:\n                last = self._extract_resource(\n                    manager, os.path.join(zip_path, name)\n                )\n            # return the extracted directory name\n            return os.path.dirname(last)\n\n        timestamp, size = self._get_date_and_size(self.zipinfo[zip_path])\n\n        if not WRITE_SUPPORT:\n            raise IOError('\"os.rename\" and \"os.unlink\" are not supported '\n                          'on this platform')\n        try:\n\n            real_path = manager.get_cache_path(\n                self.egg_name, self._parts(zip_path)\n            )\n\n            if self._is_current(real_path, zip_path):\n                return real_path\n\n            outf, tmpnam = _mkstemp(\n                \".$extract\",\n                dir=os.path.dirname(real_path),\n            )\n            os.write(outf, self.loader.get_data(zip_path))\n            os.close(outf)\n            utime(tmpnam, (timestamp, timestamp))\n            manager.postprocess(tmpnam, real_path)\n\n            try:\n                rename(tmpnam, real_path)\n\n            except os.error:\n                if os.path.isfile(real_path):\n                    if self._is_current(real_path, zip_path):\n                        # the file became current since it was checked above,\n                        #  so proceed.\n                        return real_path\n                    # Windows, del old file and retry\n                    elif os.name == 'nt':\n                        unlink(real_path)\n                        rename(tmpnam, real_path)\n                        return real_path\n                raise\n\n        except os.error:\n            # report a user-friendly error\n            manager.extraction_error()\n\n        return real_path\n\n    def _is_current(self, file_path, zip_path):\n        \"\"\"\n        Return True if the file_path is current for this zip_path\n        \"\"\"\n        timestamp, size = self._get_date_and_size(self.zipinfo[zip_path])\n        if not os.path.isfile(file_path):\n            return False\n        stat = os.stat(file_path)\n        if stat.st_size != size or stat.st_mtime != timestamp:\n            return False\n        # check that the contents match\n        zip_contents = self.loader.get_data(zip_path)\n        with open(file_path, 'rb') as f:\n            file_contents = f.read()\n        return zip_contents == file_contents\n\n    def _get_eager_resources(self):\n        if self.eagers is None:\n            eagers = []\n            for name in ('native_libs.txt', 'eager_resources.txt'):\n                if self.has_metadata(name):\n                    eagers.extend(self.get_metadata_lines(name))\n            self.eagers = eagers\n        return self.eagers\n\n    def _index(self):\n        try:\n            return self._dirindex\n        except AttributeError:\n            ind = {}\n            for path in self.zipinfo:\n                parts = path.split(os.sep)\n                while parts:\n                    parent = os.sep.join(parts[:-1])\n                    if parent in ind:\n                        ind[parent].append(parts[-1])\n                        break\n                    else:\n                        ind[parent] = [parts.pop()]\n            self._dirindex = ind\n            return ind\n\n    def _has(self, fspath):\n        zip_path = self._zipinfo_name(fspath)\n        return zip_path in self.zipinfo or zip_path in self._index()\n\n    def _isdir(self, fspath):\n        return self._zipinfo_name(fspath) in self._index()\n\n    def _listdir(self, fspath):\n        return list(self._index().get(self._zipinfo_name(fspath), ()))\n\n    def _eager_to_zip(self, resource_name):\n        return self._zipinfo_name(self._fn(self.egg_root, resource_name))\n\n    def _resource_to_zip(self, resource_name):\n        return self._zipinfo_name(self._fn(self.module_path, resource_name))\n\n\nregister_loader_type(zipimport.zipimporter, ZipProvider)\n\n\nclass FileMetadata(EmptyProvider):\n    \"\"\"Metadata handler for standalone PKG-INFO files\n\n    Usage::\n\n        metadata = FileMetadata(\"/path/to/PKG-INFO\")\n\n    This provider rejects all data and metadata requests except for PKG-INFO,\n    which is treated as existing, and will be the contents of the file at\n    the provided location.\n    \"\"\"\n\n    def __init__(self, path):\n        self.path = path\n\n    def has_metadata(self, name):\n        return name == 'PKG-INFO' and os.path.isfile(self.path)\n\n    def get_metadata(self, name):\n        if name != 'PKG-INFO':\n            raise KeyError(\"No metadata except PKG-INFO is available\")\n\n        with io.open(self.path, encoding='utf-8', errors=\"replace\") as f:\n            metadata = f.read()\n        self._warn_on_replacement(metadata)\n        return metadata\n\n    def _warn_on_replacement(self, metadata):\n        # Python 2.7 compat for: replacement_char = '�'\n        replacement_char = b'\\xef\\xbf\\xbd'.decode('utf-8')\n        if replacement_char in metadata:\n            tmpl = \"{self.path} could not be properly decoded in UTF-8\"\n            msg = tmpl.format(**locals())\n            warnings.warn(msg)\n\n    def get_metadata_lines(self, name):\n        return yield_lines(self.get_metadata(name))\n\n\nclass PathMetadata(DefaultProvider):\n    \"\"\"Metadata provider for egg directories\n\n    Usage::\n\n        # Development eggs:\n\n        egg_info = \"/path/to/PackageName.egg-info\"\n        base_dir = os.path.dirname(egg_info)\n        metadata = PathMetadata(base_dir, egg_info)\n        dist_name = os.path.splitext(os.path.basename(egg_info))[0]\n        dist = Distribution(basedir, project_name=dist_name, metadata=metadata)\n\n        # Unpacked egg directories:\n\n        egg_path = \"/path/to/PackageName-ver-pyver-etc.egg\"\n        metadata = PathMetadata(egg_path, os.path.join(egg_path,'EGG-INFO'))\n        dist = Distribution.from_filename(egg_path, metadata=metadata)\n    \"\"\"\n\n    def __init__(self, path, egg_info):\n        self.module_path = path\n        self.egg_info = egg_info\n\n\nclass EggMetadata(ZipProvider):\n    \"\"\"Metadata provider for .egg files\"\"\"\n\n    def __init__(self, importer):\n        \"\"\"Create a metadata provider from a zipimporter\"\"\"\n\n        self.zip_pre = importer.archive + os.sep\n        self.loader = importer\n        if importer.prefix:\n            self.module_path = os.path.join(importer.archive, importer.prefix)\n        else:\n            self.module_path = importer.archive\n        self._setup_prefix()\n\n\n_declare_state('dict', _distribution_finders={})\n\n\ndef register_finder(importer_type, distribution_finder):\n    \"\"\"Register `distribution_finder` to find distributions in sys.path items\n\n    `importer_type` is the type or class of a PEP 302 \"Importer\" (sys.path item\n    handler), and `distribution_finder` is a callable that, passed a path\n    item and the importer instance, yields ``Distribution`` instances found on\n    that path item.  See ``pkg_resources.find_on_path`` for an example.\"\"\"\n    _distribution_finders[importer_type] = distribution_finder\n\n\ndef find_distributions(path_item, only=False):\n    \"\"\"Yield distributions accessible via `path_item`\"\"\"\n    importer = get_importer(path_item)\n    finder = _find_adapter(_distribution_finders, importer)\n    return finder(importer, path_item, only)\n\n\ndef find_eggs_in_zip(importer, path_item, only=False):\n    \"\"\"\n    Find eggs in zip files; possibly multiple nested eggs.\n    \"\"\"\n    if importer.archive.endswith('.whl'):\n        # wheels are not supported with this finder\n        # they don't have PKG-INFO metadata, and won't ever contain eggs\n        return\n    metadata = EggMetadata(importer)\n    if metadata.has_metadata('PKG-INFO'):\n        yield Distribution.from_filename(path_item, metadata=metadata)\n    if only:\n        # don't yield nested distros\n        return\n    for subitem in metadata.resource_listdir('/'):\n        if _is_egg_path(subitem):\n            subpath = os.path.join(path_item, subitem)\n            dists = find_eggs_in_zip(zipimport.zipimporter(subpath), subpath)\n            for dist in dists:\n                yield dist\n        elif subitem.lower().endswith('.dist-info'):\n            subpath = os.path.join(path_item, subitem)\n            submeta = EggMetadata(zipimport.zipimporter(subpath))\n            submeta.egg_info = subpath\n            yield Distribution.from_location(path_item, subitem, submeta)\n\n\nregister_finder(zipimport.zipimporter, find_eggs_in_zip)\n\n\ndef find_nothing(importer, path_item, only=False):\n    return ()\n\n\nregister_finder(object, find_nothing)\n\n\ndef _by_version_descending(names):\n    \"\"\"\n    Given a list of filenames, return them in descending order\n    by version number.\n\n    >>> names = 'bar', 'foo', 'Python-2.7.10.egg', 'Python-2.7.2.egg'\n    >>> _by_version_descending(names)\n    ['Python-2.7.10.egg', 'Python-2.7.2.egg', 'foo', 'bar']\n    >>> names = 'Setuptools-1.2.3b1.egg', 'Setuptools-1.2.3.egg'\n    >>> _by_version_descending(names)\n    ['Setuptools-1.2.3.egg', 'Setuptools-1.2.3b1.egg']\n    >>> names = 'Setuptools-1.2.3b1.egg', 'Setuptools-1.2.3.post1.egg'\n    >>> _by_version_descending(names)\n    ['Setuptools-1.2.3.post1.egg', 'Setuptools-1.2.3b1.egg']\n    \"\"\"\n    def _by_version(name):\n        \"\"\"\n        Parse each component of the filename\n        \"\"\"\n        name, ext = os.path.splitext(name)\n        parts = itertools.chain(name.split('-'), [ext])\n        return [packaging.version.parse(part) for part in parts]\n\n    return sorted(names, key=_by_version, reverse=True)\n\n\ndef find_on_path(importer, path_item, only=False):\n    \"\"\"Yield distributions accessible on a sys.path directory\"\"\"\n    path_item = _normalize_cached(path_item)\n\n    if _is_unpacked_egg(path_item):\n        yield Distribution.from_filename(\n            path_item, metadata=PathMetadata(\n                path_item, os.path.join(path_item, 'EGG-INFO')\n            )\n        )\n        return\n\n    entries = safe_listdir(path_item)\n\n    # for performance, before sorting by version,\n    # screen entries for only those that will yield\n    # distributions\n    filtered = (\n        entry\n        for entry in entries\n        if dist_factory(path_item, entry, only)\n    )\n\n    # scan for .egg and .egg-info in directory\n    path_item_entries = _by_version_descending(filtered)\n    for entry in path_item_entries:\n        fullpath = os.path.join(path_item, entry)\n        factory = dist_factory(path_item, entry, only)\n        for dist in factory(fullpath):\n            yield dist\n\n\ndef dist_factory(path_item, entry, only):\n    \"\"\"\n    Return a dist_factory for a path_item and entry\n    \"\"\"\n    lower = entry.lower()\n    is_meta = any(map(lower.endswith, ('.egg-info', '.dist-info')))\n    return (\n        distributions_from_metadata\n        if is_meta else\n        find_distributions\n        if not only and _is_egg_path(entry) else\n        resolve_egg_link\n        if not only and lower.endswith('.egg-link') else\n        NoDists()\n    )\n\n\nclass NoDists:\n    \"\"\"\n    >>> bool(NoDists())\n    False\n\n    >>> list(NoDists()('anything'))\n    []\n    \"\"\"\n    def __bool__(self):\n        return False\n    if six.PY2:\n        __nonzero__ = __bool__\n\n    def __call__(self, fullpath):\n        return iter(())\n\n\ndef safe_listdir(path):\n    \"\"\"\n    Attempt to list contents of path, but suppress some exceptions.\n    \"\"\"\n    try:\n        return os.listdir(path)\n    except (PermissionError, NotADirectoryError):\n        pass\n    except OSError as e:\n        # Ignore the directory if does not exist, not a directory or\n        # permission denied\n        ignorable = (\n            e.errno in (errno.ENOTDIR, errno.EACCES, errno.ENOENT)\n            # Python 2 on Windows needs to be handled this way :(\n            or getattr(e, \"winerror\", None) == 267\n        )\n        if not ignorable:\n            raise\n    return ()\n\n\ndef distributions_from_metadata(path):\n    root = os.path.dirname(path)\n    if os.path.isdir(path):\n        if len(os.listdir(path)) == 0:\n            # empty metadata dir; skip\n            return\n        metadata = PathMetadata(root, path)\n    else:\n        metadata = FileMetadata(path)\n    entry = os.path.basename(path)\n    yield Distribution.from_location(\n        root, entry, metadata, precedence=DEVELOP_DIST,\n    )\n\n\ndef non_empty_lines(path):\n    \"\"\"\n    Yield non-empty lines from file at path\n    \"\"\"\n    with open(path) as f:\n        for line in f:\n            line = line.strip()\n            if line:\n                yield line\n\n\ndef resolve_egg_link(path):\n    \"\"\"\n    Given a path to an .egg-link, resolve distributions\n    present in the referenced path.\n    \"\"\"\n    referenced_paths = non_empty_lines(path)\n    resolved_paths = (\n        os.path.join(os.path.dirname(path), ref)\n        for ref in referenced_paths\n    )\n    dist_groups = map(find_distributions, resolved_paths)\n    return next(dist_groups, ())\n\n\nregister_finder(pkgutil.ImpImporter, find_on_path)\n\nif hasattr(importlib_machinery, 'FileFinder'):\n    register_finder(importlib_machinery.FileFinder, find_on_path)\n\n_declare_state('dict', _namespace_handlers={})\n_declare_state('dict', _namespace_packages={})\n\n\ndef register_namespace_handler(importer_type, namespace_handler):\n    \"\"\"Register `namespace_handler` to declare namespace packages\n\n    `importer_type` is the type or class of a PEP 302 \"Importer\" (sys.path item\n    handler), and `namespace_handler` is a callable like this::\n\n        def namespace_handler(importer, path_entry, moduleName, module):\n            # return a path_entry to use for child packages\n\n    Namespace handlers are only called if the importer object has already\n    agreed that it can handle the relevant path item, and they should only\n    return a subpath if the module __path__ does not already contain an\n    equivalent subpath.  For an example namespace handler, see\n    ``pkg_resources.file_ns_handler``.\n    \"\"\"\n    _namespace_handlers[importer_type] = namespace_handler\n\n\ndef _handle_ns(packageName, path_item):\n    \"\"\"Ensure that named package includes a subpath of path_item (if needed)\"\"\"\n\n    importer = get_importer(path_item)\n    if importer is None:\n        return None\n\n    # capture warnings due to #1111\n    with warnings.catch_warnings():\n        warnings.simplefilter(\"ignore\")\n        loader = importer.find_module(packageName)\n\n    if loader is None:\n        return None\n    module = sys.modules.get(packageName)\n    if module is None:\n        module = sys.modules[packageName] = types.ModuleType(packageName)\n        module.__path__ = []\n        _set_parent_ns(packageName)\n    elif not hasattr(module, '__path__'):\n        raise TypeError(\"Not a package:\", packageName)\n    handler = _find_adapter(_namespace_handlers, importer)\n    subpath = handler(importer, path_item, packageName, module)\n    if subpath is not None:\n        path = module.__path__\n        path.append(subpath)\n        loader.load_module(packageName)\n        _rebuild_mod_path(path, packageName, module)\n    return subpath\n\n\ndef _rebuild_mod_path(orig_path, package_name, module):\n    \"\"\"\n    Rebuild module.__path__ ensuring that all entries are ordered\n    corresponding to their sys.path order\n    \"\"\"\n    sys_path = [_normalize_cached(p) for p in sys.path]\n\n    def safe_sys_path_index(entry):\n        \"\"\"\n        Workaround for #520 and #513.\n        \"\"\"\n        try:\n            return sys_path.index(entry)\n        except ValueError:\n            return float('inf')\n\n    def position_in_sys_path(path):\n        \"\"\"\n        Return the ordinal of the path based on its position in sys.path\n        \"\"\"\n        path_parts = path.split(os.sep)\n        module_parts = package_name.count('.') + 1\n        parts = path_parts[:-module_parts]\n        return safe_sys_path_index(_normalize_cached(os.sep.join(parts)))\n\n    new_path = sorted(orig_path, key=position_in_sys_path)\n    new_path = [_normalize_cached(p) for p in new_path]\n\n    if isinstance(module.__path__, list):\n        module.__path__[:] = new_path\n    else:\n        module.__path__ = new_path\n\n\ndef declare_namespace(packageName):\n    \"\"\"Declare that package 'packageName' is a namespace package\"\"\"\n\n    _imp.acquire_lock()\n    try:\n        if packageName in _namespace_packages:\n            return\n\n        path = sys.path\n        parent, _, _ = packageName.rpartition('.')\n\n        if parent:\n            declare_namespace(parent)\n            if parent not in _namespace_packages:\n                __import__(parent)\n            try:\n                path = sys.modules[parent].__path__\n            except AttributeError:\n                raise TypeError(\"Not a package:\", parent)\n\n        # Track what packages are namespaces, so when new path items are added,\n        # they can be updated\n        _namespace_packages.setdefault(parent or None, []).append(packageName)\n        _namespace_packages.setdefault(packageName, [])\n\n        for path_item in path:\n            # Ensure all the parent's path items are reflected in the child,\n            # if they apply\n            _handle_ns(packageName, path_item)\n\n    finally:\n        _imp.release_lock()\n\n\ndef fixup_namespace_packages(path_item, parent=None):\n    \"\"\"Ensure that previously-declared namespace packages include path_item\"\"\"\n    _imp.acquire_lock()\n    try:\n        for package in _namespace_packages.get(parent, ()):\n            subpath = _handle_ns(package, path_item)\n            if subpath:\n                fixup_namespace_packages(subpath, package)\n    finally:\n        _imp.release_lock()\n\n\ndef file_ns_handler(importer, path_item, packageName, module):\n    \"\"\"Compute an ns-package subpath for a filesystem or zipfile importer\"\"\"\n\n    subpath = os.path.join(path_item, packageName.split('.')[-1])\n    normalized = _normalize_cached(subpath)\n    for item in module.__path__:\n        if _normalize_cached(item) == normalized:\n            break\n    else:\n        # Only return the path if it's not already there\n        return subpath\n\n\nregister_namespace_handler(pkgutil.ImpImporter, file_ns_handler)\nregister_namespace_handler(zipimport.zipimporter, file_ns_handler)\n\nif hasattr(importlib_machinery, 'FileFinder'):\n    register_namespace_handler(importlib_machinery.FileFinder, file_ns_handler)\n\n\ndef null_ns_handler(importer, path_item, packageName, module):\n    return None\n\n\nregister_namespace_handler(object, null_ns_handler)\n\n\ndef normalize_path(filename):\n    \"\"\"Normalize a file/dir name for comparison purposes\"\"\"\n    return os.path.normcase(os.path.realpath(os.path.normpath(_cygwin_patch(filename))))\n\n\ndef _cygwin_patch(filename):  # pragma: nocover\n    \"\"\"\n    Contrary to POSIX 2008, on Cygwin, getcwd (3) contains\n    symlink components. Using\n    os.path.abspath() works around this limitation. A fix in os.getcwd()\n    would probably better, in Cygwin even more so, except\n    that this seems to be by design...\n    \"\"\"\n    return os.path.abspath(filename) if sys.platform == 'cygwin' else filename\n\n\ndef _normalize_cached(filename, _cache={}):\n    try:\n        return _cache[filename]\n    except KeyError:\n        _cache[filename] = result = normalize_path(filename)\n        return result\n\n\ndef _is_egg_path(path):\n    \"\"\"\n    Determine if given path appears to be an egg.\n    \"\"\"\n    return path.lower().endswith('.egg')\n\n\ndef _is_unpacked_egg(path):\n    \"\"\"\n    Determine if given path appears to be an unpacked egg.\n    \"\"\"\n    return (\n        _is_egg_path(path) and\n        os.path.isfile(os.path.join(path, 'EGG-INFO', 'PKG-INFO'))\n    )\n\n\ndef _set_parent_ns(packageName):\n    parts = packageName.split('.')\n    name = parts.pop()\n    if parts:\n        parent = '.'.join(parts)\n        setattr(sys.modules[parent], name, sys.modules[packageName])\n\n\ndef yield_lines(strs):\n    \"\"\"Yield non-empty/non-comment lines of a string or sequence\"\"\"\n    if isinstance(strs, six.string_types):\n        for s in strs.splitlines():\n            s = s.strip()\n            # skip blank lines/comments\n            if s and not s.startswith('#'):\n                yield s\n    else:\n        for ss in strs:\n            for s in yield_lines(ss):\n                yield s\n\n\nMODULE = re.compile(r\"\\w+(\\.\\w+)*$\").match\nEGG_NAME = re.compile(\n    r\"\"\"\n    (?P<name>[^-]+) (\n        -(?P<ver>[^-]+) (\n            -py(?P<pyver>[^-]+) (\n                -(?P<plat>.+)\n            )?\n        )?\n    )?\n    \"\"\",\n    re.VERBOSE | re.IGNORECASE,\n).match\n\n\nclass EntryPoint:\n    \"\"\"Object representing an advertised importable object\"\"\"\n\n    def __init__(self, name, module_name, attrs=(), extras=(), dist=None):\n        if not MODULE(module_name):\n            raise ValueError(\"Invalid module name\", module_name)\n        self.name = name\n        self.module_name = module_name\n        self.attrs = tuple(attrs)\n        self.extras = tuple(extras)\n        self.dist = dist\n\n    def __str__(self):\n        s = \"%s = %s\" % (self.name, self.module_name)\n        if self.attrs:\n            s += ':' + '.'.join(self.attrs)\n        if self.extras:\n            s += ' [%s]' % ','.join(self.extras)\n        return s\n\n    def __repr__(self):\n        return \"EntryPoint.parse(%r)\" % str(self)\n\n    def load(self, require=True, *args, **kwargs):\n        \"\"\"\n        Require packages for this EntryPoint, then resolve it.\n        \"\"\"\n        if not require or args or kwargs:\n            warnings.warn(\n                \"Parameters to load are deprecated.  Call .resolve and \"\n                \".require separately.\",\n                PkgResourcesDeprecationWarning,\n                stacklevel=2,\n            )\n        if require:\n            self.require(*args, **kwargs)\n        return self.resolve()\n\n    def resolve(self):\n        \"\"\"\n        Resolve the entry point from its module and attrs.\n        \"\"\"\n        module = __import__(self.module_name, fromlist=['__name__'], level=0)\n        try:\n            return functools.reduce(getattr, self.attrs, module)\n        except AttributeError as exc:\n            raise ImportError(str(exc))\n\n    def require(self, env=None, installer=None):\n        if self.extras and not self.dist:\n            raise UnknownExtra(\"Can't require() without a distribution\", self)\n\n        # Get the requirements for this entry point with all its extras and\n        # then resolve them. We have to pass `extras` along when resolving so\n        # that the working set knows what extras we want. Otherwise, for\n        # dist-info distributions, the working set will assume that the\n        # requirements for that extra are purely optional and skip over them.\n        reqs = self.dist.requires(self.extras)\n        items = working_set.resolve(reqs, env, installer, extras=self.extras)\n        list(map(working_set.add, items))\n\n    pattern = re.compile(\n        r'\\s*'\n        r'(?P<name>.+?)\\s*'\n        r'=\\s*'\n        r'(?P<module>[\\w.]+)\\s*'\n        r'(:\\s*(?P<attr>[\\w.]+))?\\s*'\n        r'(?P<extras>\\[.*\\])?\\s*$'\n    )\n\n    @classmethod\n    def parse(cls, src, dist=None):\n        \"\"\"Parse a single entry point from string `src`\n\n        Entry point syntax follows the form::\n\n            name = some.module:some.attr [extra1, extra2]\n\n        The entry name and module name are required, but the ``:attrs`` and\n        ``[extras]`` parts are optional\n        \"\"\"\n        m = cls.pattern.match(src)\n        if not m:\n            msg = \"EntryPoint must be in 'name=module:attrs [extras]' format\"\n            raise ValueError(msg, src)\n        res = m.groupdict()\n        extras = cls._parse_extras(res['extras'])\n        attrs = res['attr'].split('.') if res['attr'] else ()\n        return cls(res['name'], res['module'], attrs, extras, dist)\n\n    @classmethod\n    def _parse_extras(cls, extras_spec):\n        if not extras_spec:\n            return ()\n        req = Requirement.parse('x' + extras_spec)\n        if req.specs:\n            raise ValueError()\n        return req.extras\n\n    @classmethod\n    def parse_group(cls, group, lines, dist=None):\n        \"\"\"Parse an entry point group\"\"\"\n        if not MODULE(group):\n            raise ValueError(\"Invalid group name\", group)\n        this = {}\n        for line in yield_lines(lines):\n            ep = cls.parse(line, dist)\n            if ep.name in this:\n                raise ValueError(\"Duplicate entry point\", group, ep.name)\n            this[ep.name] = ep\n        return this\n\n    @classmethod\n    def parse_map(cls, data, dist=None):\n        \"\"\"Parse a map of entry point groups\"\"\"\n        if isinstance(data, dict):\n            data = data.items()\n        else:\n            data = split_sections(data)\n        maps = {}\n        for group, lines in data:\n            if group is None:\n                if not lines:\n                    continue\n                raise ValueError(\"Entry points must be listed in groups\")\n            group = group.strip()\n            if group in maps:\n                raise ValueError(\"Duplicate group name\", group)\n            maps[group] = cls.parse_group(group, lines, dist)\n        return maps\n\n\ndef _remove_md5_fragment(location):\n    if not location:\n        return ''\n    parsed = urllib.parse.urlparse(location)\n    if parsed[-1].startswith('md5='):\n        return urllib.parse.urlunparse(parsed[:-1] + ('',))\n    return location\n\n\ndef _version_from_file(lines):\n    \"\"\"\n    Given an iterable of lines from a Metadata file, return\n    the value of the Version field, if present, or None otherwise.\n    \"\"\"\n    def is_version_line(line):\n        return line.lower().startswith('version:')\n    version_lines = filter(is_version_line, lines)\n    line = next(iter(version_lines), '')\n    _, _, value = line.partition(':')\n    return safe_version(value.strip()) or None\n\n\nclass Distribution:\n    \"\"\"Wrap an actual or potential sys.path entry w/metadata\"\"\"\n    PKG_INFO = 'PKG-INFO'\n\n    def __init__(\n            self, location=None, metadata=None, project_name=None,\n            version=None, py_version=PY_MAJOR, platform=None,\n            precedence=EGG_DIST):\n        self.project_name = safe_name(project_name or 'Unknown')\n        if version is not None:\n            self._version = safe_version(version)\n        self.py_version = py_version\n        self.platform = platform\n        self.location = location\n        self.precedence = precedence\n        self._provider = metadata or empty_provider\n\n    @classmethod\n    def from_location(cls, location, basename, metadata=None, **kw):\n        project_name, version, py_version, platform = [None] * 4\n        basename, ext = os.path.splitext(basename)\n        if ext.lower() in _distributionImpl:\n            cls = _distributionImpl[ext.lower()]\n\n            match = EGG_NAME(basename)\n            if match:\n                project_name, version, py_version, platform = match.group(\n                    'name', 'ver', 'pyver', 'plat'\n                )\n        return cls(\n            location, metadata, project_name=project_name, version=version,\n            py_version=py_version, platform=platform, **kw\n        )._reload_version()\n\n    def _reload_version(self):\n        return self\n\n    @property\n    def hashcmp(self):\n        return (\n            self.parsed_version,\n            self.precedence,\n            self.key,\n            _remove_md5_fragment(self.location),\n            self.py_version or '',\n            self.platform or '',\n        )\n\n    def __hash__(self):\n        return hash(self.hashcmp)\n\n    def __lt__(self, other):\n        return self.hashcmp < other.hashcmp\n\n    def __le__(self, other):\n        return self.hashcmp <= other.hashcmp\n\n    def __gt__(self, other):\n        return self.hashcmp > other.hashcmp\n\n    def __ge__(self, other):\n        return self.hashcmp >= other.hashcmp\n\n    def __eq__(self, other):\n        if not isinstance(other, self.__class__):\n            # It's not a Distribution, so they are not equal\n            return False\n        return self.hashcmp == other.hashcmp\n\n    def __ne__(self, other):\n        return not self == other\n\n    # These properties have to be lazy so that we don't have to load any\n    # metadata until/unless it's actually needed.  (i.e., some distributions\n    # may not know their name or version without loading PKG-INFO)\n\n    @property\n    def key(self):\n        try:\n            return self._key\n        except AttributeError:\n            self._key = key = self.project_name.lower()\n            return key\n\n    @property\n    def parsed_version(self):\n        if not hasattr(self, \"_parsed_version\"):\n            self._parsed_version = parse_version(self.version)\n\n        return self._parsed_version\n\n    def _warn_legacy_version(self):\n        LV = packaging.version.LegacyVersion\n        is_legacy = isinstance(self._parsed_version, LV)\n        if not is_legacy:\n            return\n\n        # While an empty version is technically a legacy version and\n        # is not a valid PEP 440 version, it's also unlikely to\n        # actually come from someone and instead it is more likely that\n        # it comes from setuptools attempting to parse a filename and\n        # including it in the list. So for that we'll gate this warning\n        # on if the version is anything at all or not.\n        if not self.version:\n            return\n\n        tmpl = textwrap.dedent(\"\"\"\n            '{project_name} ({version})' is being parsed as a legacy,\n            non PEP 440,\n            version. You may find odd behavior and sort order.\n            In particular it will be sorted as less than 0.0. It\n            is recommended to migrate to PEP 440 compatible\n            versions.\n            \"\"\").strip().replace('\\n', ' ')\n\n        warnings.warn(tmpl.format(**vars(self)), PEP440Warning)\n\n    @property\n    def version(self):\n        try:\n            return self._version\n        except AttributeError:\n            version = _version_from_file(self._get_metadata(self.PKG_INFO))\n            if version is None:\n                tmpl = \"Missing 'Version:' header and/or %s file\"\n                raise ValueError(tmpl % self.PKG_INFO, self)\n            return version\n\n    @property\n    def _dep_map(self):\n        \"\"\"\n        A map of extra to its list of (direct) requirements\n        for this distribution, including the null extra.\n        \"\"\"\n        try:\n            return self.__dep_map\n        except AttributeError:\n            self.__dep_map = self._filter_extras(self._build_dep_map())\n        return self.__dep_map\n\n    @staticmethod\n    def _filter_extras(dm):\n        \"\"\"\n        Given a mapping of extras to dependencies, strip off\n        environment markers and filter out any dependencies\n        not matching the markers.\n        \"\"\"\n        for extra in list(filter(None, dm)):\n            new_extra = extra\n            reqs = dm.pop(extra)\n            new_extra, _, marker = extra.partition(':')\n            fails_marker = marker and (\n                invalid_marker(marker)\n                or not evaluate_marker(marker)\n            )\n            if fails_marker:\n                reqs = []\n            new_extra = safe_extra(new_extra) or None\n\n            dm.setdefault(new_extra, []).extend(reqs)\n        return dm\n\n    def _build_dep_map(self):\n        dm = {}\n        for name in 'requires.txt', 'depends.txt':\n            for extra, reqs in split_sections(self._get_metadata(name)):\n                dm.setdefault(extra, []).extend(parse_requirements(reqs))\n        return dm\n\n    def requires(self, extras=()):\n        \"\"\"List of Requirements needed for this distro if `extras` are used\"\"\"\n        dm = self._dep_map\n        deps = []\n        deps.extend(dm.get(None, ()))\n        for ext in extras:\n            try:\n                deps.extend(dm[safe_extra(ext)])\n            except KeyError:\n                raise UnknownExtra(\n                    \"%s has no such extra feature %r\" % (self, ext)\n                )\n        return deps\n\n    def _get_metadata(self, name):\n        if self.has_metadata(name):\n            for line in self.get_metadata_lines(name):\n                yield line\n\n    def activate(self, path=None, replace=False):\n        \"\"\"Ensure distribution is importable on `path` (default=sys.path)\"\"\"\n        if path is None:\n            path = sys.path\n        self.insert_on(path, replace=replace)\n        if path is sys.path:\n            fixup_namespace_packages(self.location)\n            for pkg in self._get_metadata('namespace_packages.txt'):\n                if pkg in sys.modules:\n                    declare_namespace(pkg)\n\n    def egg_name(self):\n        \"\"\"Return what this distribution's standard .egg filename should be\"\"\"\n        filename = \"%s-%s-py%s\" % (\n            to_filename(self.project_name), to_filename(self.version),\n            self.py_version or PY_MAJOR\n        )\n\n        if self.platform:\n            filename += '-' + self.platform\n        return filename\n\n    def __repr__(self):\n        if self.location:\n            return \"%s (%s)\" % (self, self.location)\n        else:\n            return str(self)\n\n    def __str__(self):\n        try:\n            version = getattr(self, 'version', None)\n        except ValueError:\n            version = None\n        version = version or \"[unknown version]\"\n        return \"%s %s\" % (self.project_name, version)\n\n    def __getattr__(self, attr):\n        \"\"\"Delegate all unrecognized public attributes to .metadata provider\"\"\"\n        if attr.startswith('_'):\n            raise AttributeError(attr)\n        return getattr(self._provider, attr)\n\n    def __dir__(self):\n        return list(\n            set(super(Distribution, self).__dir__())\n            | set(\n                attr for attr in self._provider.__dir__()\n                if not attr.startswith('_')\n            )\n        )\n\n    if not hasattr(object, '__dir__'):\n        # python 2.7 not supported\n        del __dir__\n\n    @classmethod\n    def from_filename(cls, filename, metadata=None, **kw):\n        return cls.from_location(\n            _normalize_cached(filename), os.path.basename(filename), metadata,\n            **kw\n        )\n\n    def as_requirement(self):\n        \"\"\"Return a ``Requirement`` that matches this distribution exactly\"\"\"\n        if isinstance(self.parsed_version, packaging.version.Version):\n            spec = \"%s==%s\" % (self.project_name, self.parsed_version)\n        else:\n            spec = \"%s===%s\" % (self.project_name, self.parsed_version)\n\n        return Requirement.parse(spec)\n\n    def load_entry_point(self, group, name):\n        \"\"\"Return the `name` entry point of `group` or raise ImportError\"\"\"\n        ep = self.get_entry_info(group, name)\n        if ep is None:\n            raise ImportError(\"Entry point %r not found\" % ((group, name),))\n        return ep.load()\n\n    def get_entry_map(self, group=None):\n        \"\"\"Return the entry point map for `group`, or the full entry map\"\"\"\n        try:\n            ep_map = self._ep_map\n        except AttributeError:\n            ep_map = self._ep_map = EntryPoint.parse_map(\n                self._get_metadata('entry_points.txt'), self\n            )\n        if group is not None:\n            return ep_map.get(group, {})\n        return ep_map\n\n    def get_entry_info(self, group, name):\n        \"\"\"Return the EntryPoint object for `group`+`name`, or ``None``\"\"\"\n        return self.get_entry_map(group).get(name)\n\n    def insert_on(self, path, loc=None, replace=False):\n        \"\"\"Ensure self.location is on path\n\n        If replace=False (default):\n            - If location is already in path anywhere, do nothing.\n            - Else:\n              - If it's an egg and its parent directory is on path,\n                insert just ahead of the parent.\n              - Else: add to the end of path.\n        If replace=True:\n            - If location is already on path anywhere (not eggs)\n              or higher priority than its parent (eggs)\n              do nothing.\n            - Else:\n              - If it's an egg and its parent directory is on path,\n                insert just ahead of the parent,\n                removing any lower-priority entries.\n              - Else: add it to the front of path.\n        \"\"\"\n\n        loc = loc or self.location\n        if not loc:\n            return\n\n        nloc = _normalize_cached(loc)\n        bdir = os.path.dirname(nloc)\n        npath = [(p and _normalize_cached(p) or p) for p in path]\n\n        for p, item in enumerate(npath):\n            if item == nloc:\n                if replace:\n                    break\n                else:\n                    # don't modify path (even removing duplicates) if\n                    # found and not replace\n                    return\n            elif item == bdir and self.precedence == EGG_DIST:\n                # if it's an .egg, give it precedence over its directory\n                # UNLESS it's already been added to sys.path and replace=False\n                if (not replace) and nloc in npath[p:]:\n                    return\n                if path is sys.path:\n                    self.check_version_conflict()\n                path.insert(p, loc)\n                npath.insert(p, nloc)\n                break\n        else:\n            if path is sys.path:\n                self.check_version_conflict()\n            if replace:\n                path.insert(0, loc)\n            else:\n                path.append(loc)\n            return\n\n        # p is the spot where we found or inserted loc; now remove duplicates\n        while True:\n            try:\n                np = npath.index(nloc, p + 1)\n            except ValueError:\n                break\n            else:\n                del npath[np], path[np]\n                # ha!\n                p = np\n\n        return\n\n    def check_version_conflict(self):\n        if self.key == 'setuptools':\n            # ignore the inevitable setuptools self-conflicts  :(\n            return\n\n        nsp = dict.fromkeys(self._get_metadata('namespace_packages.txt'))\n        loc = normalize_path(self.location)\n        for modname in self._get_metadata('top_level.txt'):\n            if (modname not in sys.modules or modname in nsp\n                    or modname in _namespace_packages):\n                continue\n            if modname in ('pkg_resources', 'setuptools', 'site'):\n                continue\n            fn = getattr(sys.modules[modname], '__file__', None)\n            if fn and (normalize_path(fn).startswith(loc) or\n                       fn.startswith(self.location)):\n                continue\n            issue_warning(\n                \"Module %s was already imported from %s, but %s is being added\"\n                \" to sys.path\" % (modname, fn, self.location),\n            )\n\n    def has_version(self):\n        try:\n            self.version\n        except ValueError:\n            issue_warning(\"Unbuilt egg for \" + repr(self))\n            return False\n        return True\n\n    def clone(self, **kw):\n        \"\"\"Copy this distribution, substituting in any changed keyword args\"\"\"\n        names = 'project_name version py_version platform location precedence'\n        for attr in names.split():\n            kw.setdefault(attr, getattr(self, attr, None))\n        kw.setdefault('metadata', self._provider)\n        return self.__class__(**kw)\n\n    @property\n    def extras(self):\n        return [dep for dep in self._dep_map if dep]\n\n\nclass EggInfoDistribution(Distribution):\n    def _reload_version(self):\n        \"\"\"\n        Packages installed by distutils (e.g. numpy or scipy),\n        which uses an old safe_version, and so\n        their version numbers can get mangled when\n        converted to filenames (e.g., 1.11.0.dev0+2329eae to\n        1.11.0.dev0_2329eae). These distributions will not be\n        parsed properly\n        downstream by Distribution and safe_version, so\n        take an extra step and try to get the version number from\n        the metadata file itself instead of the filename.\n        \"\"\"\n        md_version = _version_from_file(self._get_metadata(self.PKG_INFO))\n        if md_version:\n            self._version = md_version\n        return self\n\n\nclass DistInfoDistribution(Distribution):\n    \"\"\"\n    Wrap an actual or potential sys.path entry\n    w/metadata, .dist-info style.\n    \"\"\"\n    PKG_INFO = 'METADATA'\n    EQEQ = re.compile(r\"([\\(,])\\s*(\\d.*?)\\s*([,\\)])\")\n\n    @property\n    def _parsed_pkg_info(self):\n        \"\"\"Parse and cache metadata\"\"\"\n        try:\n            return self._pkg_info\n        except AttributeError:\n            metadata = self.get_metadata(self.PKG_INFO)\n            self._pkg_info = email.parser.Parser().parsestr(metadata)\n            return self._pkg_info\n\n    @property\n    def _dep_map(self):\n        try:\n            return self.__dep_map\n        except AttributeError:\n            self.__dep_map = self._compute_dependencies()\n            return self.__dep_map\n\n    def _compute_dependencies(self):\n        \"\"\"Recompute this distribution's dependencies.\"\"\"\n        dm = self.__dep_map = {None: []}\n\n        reqs = []\n        # Including any condition expressions\n        for req in self._parsed_pkg_info.get_all('Requires-Dist') or []:\n            reqs.extend(parse_requirements(req))\n\n        def reqs_for_extra(extra):\n            for req in reqs:\n                if not req.marker or req.marker.evaluate({'extra': extra}):\n                    yield req\n\n        common = frozenset(reqs_for_extra(None))\n        dm[None].extend(common)\n\n        for extra in self._parsed_pkg_info.get_all('Provides-Extra') or []:\n            s_extra = safe_extra(extra.strip())\n            dm[s_extra] = list(frozenset(reqs_for_extra(extra)) - common)\n\n        return dm\n\n\n_distributionImpl = {\n    '.egg': Distribution,\n    '.egg-info': EggInfoDistribution,\n    '.dist-info': DistInfoDistribution,\n}\n\n\ndef issue_warning(*args, **kw):\n    level = 1\n    g = globals()\n    try:\n        # find the first stack frame that is *not* code in\n        # the pkg_resources module, to use for the warning\n        while sys._getframe(level).f_globals is g:\n            level += 1\n    except ValueError:\n        pass\n    warnings.warn(stacklevel=level + 1, *args, **kw)\n\n\nclass RequirementParseError(ValueError):\n    def __str__(self):\n        return ' '.join(self.args)\n\n\ndef parse_requirements(strs):\n    \"\"\"Yield ``Requirement`` objects for each specification in `strs`\n\n    `strs` must be a string, or a (possibly-nested) iterable thereof.\n    \"\"\"\n    # create a steppable iterator, so we can handle \\-continuations\n    lines = iter(yield_lines(strs))\n\n    for line in lines:\n        # Drop comments -- a hash without a space may be in a URL.\n        if ' #' in line:\n            line = line[:line.find(' #')]\n        # If there is a line continuation, drop it, and append the next line.\n        if line.endswith('\\\\'):\n            line = line[:-2].strip()\n            try:\n                line += next(lines)\n            except StopIteration:\n                return\n        yield Requirement(line)\n\n\nclass Requirement(packaging.requirements.Requirement):\n    def __init__(self, requirement_string):\n        \"\"\"DO NOT CALL THIS UNDOCUMENTED METHOD; use Requirement.parse()!\"\"\"\n        try:\n            super(Requirement, self).__init__(requirement_string)\n        except packaging.requirements.InvalidRequirement as e:\n            raise RequirementParseError(str(e))\n        self.unsafe_name = self.name\n        project_name = safe_name(self.name)\n        self.project_name, self.key = project_name, project_name.lower()\n        self.specs = [\n            (spec.operator, spec.version) for spec in self.specifier]\n        self.extras = tuple(map(safe_extra, self.extras))\n        self.hashCmp = (\n            self.key,\n            self.specifier,\n            frozenset(self.extras),\n            str(self.marker) if self.marker else None,\n        )\n        self.__hash = hash(self.hashCmp)\n\n    def __eq__(self, other):\n        return (\n            isinstance(other, Requirement) and\n            self.hashCmp == other.hashCmp\n        )\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __contains__(self, item):\n        if isinstance(item, Distribution):\n            if item.key != self.key:\n                return False\n\n            item = item.version\n\n        # Allow prereleases always in order to match the previous behavior of\n        # this method. In the future this should be smarter and follow PEP 440\n        # more accurately.\n        return self.specifier.contains(item, prereleases=True)\n\n    def __hash__(self):\n        return self.__hash\n\n    def __repr__(self):\n        return \"Requirement.parse(%r)\" % str(self)\n\n    @staticmethod\n    def parse(s):\n        req, = parse_requirements(s)\n        return req\n\n\ndef _always_object(classes):\n    \"\"\"\n    Ensure object appears in the mro even\n    for old-style classes.\n    \"\"\"\n    if object not in classes:\n        return classes + (object,)\n    return classes\n\n\ndef _find_adapter(registry, ob):\n    \"\"\"Return an adapter factory for `ob` from `registry`\"\"\"\n    types = _always_object(inspect.getmro(getattr(ob, '__class__', type(ob))))\n    for t in types:\n        if t in registry:\n            return registry[t]\n\n\ndef ensure_directory(path):\n    \"\"\"Ensure that the parent directory of `path` exists\"\"\"\n    dirname = os.path.dirname(path)\n    py31compat.makedirs(dirname, exist_ok=True)\n\n\ndef _bypass_ensure_directory(path):\n    \"\"\"Sandbox-bypassing version of ensure_directory()\"\"\"\n    if not WRITE_SUPPORT:\n        raise IOError('\"os.mkdir\" not supported on this platform.')\n    dirname, filename = split(path)\n    if dirname and filename and not isdir(dirname):\n        _bypass_ensure_directory(dirname)\n        try:\n            mkdir(dirname, 0o755)\n        except FileExistsError:\n            pass\n\n\ndef split_sections(s):\n    \"\"\"Split a string or iterable thereof into (section, content) pairs\n\n    Each ``section`` is a stripped version of the section header (\"[section]\")\n    and each ``content`` is a list of stripped lines excluding blank lines and\n    comment-only lines.  If there are any such lines before the first section\n    header, they're returned in a first ``section`` of ``None``.\n    \"\"\"\n    section = None\n    content = []\n    for line in yield_lines(s):\n        if line.startswith(\"[\"):\n            if line.endswith(\"]\"):\n                if section or content:\n                    yield section, content\n                section = line[1:-1].strip()\n                content = []\n            else:\n                raise ValueError(\"Invalid section heading\", line)\n        else:\n            content.append(line)\n\n    # wrap up last segment\n    yield section, content\n\n\ndef _mkstemp(*args, **kw):\n    old_open = os.open\n    try:\n        # temporarily bypass sandboxing\n        os.open = os_open\n        return tempfile.mkstemp(*args, **kw)\n    finally:\n        # and then put it back\n        os.open = old_open\n\n\n# Silence the PEP440Warning by default, so that end users don't get hit by it\n# randomly just because they use pkg_resources. We want to append the rule\n# because we want earlier uses of filterwarnings to take precedence over this\n# one.\nwarnings.filterwarnings(\"ignore\", category=PEP440Warning, append=True)\n\n\n# from jaraco.functools 1.3\ndef _call_aside(f, *args, **kwargs):\n    f(*args, **kwargs)\n    return f\n\n\n@_call_aside\ndef _initialize(g=globals()):\n    \"Set up global resource manager (deliberately not state-saved)\"\n    manager = ResourceManager()\n    g['_manager'] = manager\n    g.update(\n        (name, getattr(manager, name))\n        for name in dir(manager)\n        if not name.startswith('_')\n    )\n\n\n@_call_aside\ndef _initialize_master_working_set():\n    \"\"\"\n    Prepare the master working set and make the ``require()``\n    API available.\n\n    This function has explicit effects on the global state\n    of pkg_resources. It is intended to be invoked once at\n    the initialization of this module.\n\n    Invocation by other packages is unsupported and done\n    at their own risk.\n    \"\"\"\n    working_set = WorkingSet._build_master()\n    _declare_state('object', working_set=working_set)\n\n    require = working_set.require\n    iter_entry_points = working_set.iter_entry_points\n    add_activation_listener = working_set.subscribe\n    run_script = working_set.run_script\n    # backward compatibility\n    run_main = run_script\n    # Activate all distributions already on sys.path with replace=False and\n    # ensure that all distributions added to the working set in the future\n    # (e.g. by calling ``require()``) will get activated as well,\n    # with higher priority (replace=True).\n    tuple(\n        dist.activate(replace=False)\n        for dist in working_set\n    )\n    add_activation_listener(\n        lambda dist: dist.activate(replace=True),\n        existing=False,\n    )\n    working_set.entries = []\n    # match order\n    list(map(working_set.add_entry, sys.path))\n    globals().update(locals())\n\nclass PkgResourcesDeprecationWarning(Warning):\n    \"\"\"\n    Base class for warning about deprecations in ``pkg_resources``\n\n    This class is not derived from ``DeprecationWarning``, and as such is\n    visible by default.\n    \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pkg_resources/py31compat.py",
    "content": "import os\nimport errno\nimport sys\n\nfrom pip._vendor import six\n\n\ndef _makedirs_31(path, exist_ok=False):\n    try:\n        os.makedirs(path)\n    except OSError as exc:\n        if not exist_ok or exc.errno != errno.EEXIST:\n            raise\n\n\n# rely on compatibility behavior until mode considerations\n#  and exists_ok considerations are disentangled.\n# See https://github.com/pypa/setuptools/pull/1083#issuecomment-315168663\nneeds_makedirs = (\n    six.PY2 or\n    (3, 4) <= sys.version_info < (3, 4, 1)\n)\nmakedirs = _makedirs_31 if needs_makedirs else os.makedirs\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/progress/__init__.py",
    "content": "# Copyright (c) 2012 Giorgos Verigakis <verigak@gmail.com>\n#\n# Permission to use, copy, modify, and distribute this software for any\n# purpose with or without fee is hereby granted, provided that the above\n# copyright notice and this permission notice appear in all copies.\n#\n# THE SOFTWARE IS PROVIDED \"AS IS\" AND THE AUTHOR DISCLAIMS ALL WARRANTIES\n# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF\n# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR\n# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES\n# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN\n# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF\n# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.\n\nfrom __future__ import division\n\nfrom collections import deque\nfrom datetime import timedelta\nfrom math import ceil\nfrom sys import stderr\nfrom time import time\n\n\n__version__ = '1.4'\n\n\nclass Infinite(object):\n    file = stderr\n    sma_window = 10         # Simple Moving Average window\n\n    def __init__(self, *args, **kwargs):\n        self.index = 0\n        self.start_ts = time()\n        self.avg = 0\n        self._ts = self.start_ts\n        self._xput = deque(maxlen=self.sma_window)\n        for key, val in kwargs.items():\n            setattr(self, key, val)\n\n    def __getitem__(self, key):\n        if key.startswith('_'):\n            return None\n        return getattr(self, key, None)\n\n    @property\n    def elapsed(self):\n        return int(time() - self.start_ts)\n\n    @property\n    def elapsed_td(self):\n        return timedelta(seconds=self.elapsed)\n\n    def update_avg(self, n, dt):\n        if n > 0:\n            self._xput.append(dt / n)\n            self.avg = sum(self._xput) / len(self._xput)\n\n    def update(self):\n        pass\n\n    def start(self):\n        pass\n\n    def finish(self):\n        pass\n\n    def next(self, n=1):\n        now = time()\n        dt = now - self._ts\n        self.update_avg(n, dt)\n        self._ts = now\n        self.index = self.index + n\n        self.update()\n\n    def iter(self, it):\n        try:\n            for x in it:\n                yield x\n                self.next()\n        finally:\n            self.finish()\n\n\nclass Progress(Infinite):\n    def __init__(self, *args, **kwargs):\n        super(Progress, self).__init__(*args, **kwargs)\n        self.max = kwargs.get('max', 100)\n\n    @property\n    def eta(self):\n        return int(ceil(self.avg * self.remaining))\n\n    @property\n    def eta_td(self):\n        return timedelta(seconds=self.eta)\n\n    @property\n    def percent(self):\n        return self.progress * 100\n\n    @property\n    def progress(self):\n        return min(1, self.index / self.max)\n\n    @property\n    def remaining(self):\n        return max(self.max - self.index, 0)\n\n    def start(self):\n        self.update()\n\n    def goto(self, index):\n        incr = index - self.index\n        self.next(incr)\n\n    def iter(self, it):\n        try:\n            self.max = len(it)\n        except TypeError:\n            pass\n\n        try:\n            for x in it:\n                yield x\n                self.next()\n        finally:\n            self.finish()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/progress/bar.py",
    "content": "# -*- coding: utf-8 -*-\n\n# Copyright (c) 2012 Giorgos Verigakis <verigak@gmail.com>\n#\n# Permission to use, copy, modify, and distribute this software for any\n# purpose with or without fee is hereby granted, provided that the above\n# copyright notice and this permission notice appear in all copies.\n#\n# THE SOFTWARE IS PROVIDED \"AS IS\" AND THE AUTHOR DISCLAIMS ALL WARRANTIES\n# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF\n# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR\n# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES\n# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN\n# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF\n# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.\n\nfrom __future__ import unicode_literals\n\nimport sys\n\nfrom . import Progress\nfrom .helpers import WritelnMixin\n\n\nclass Bar(WritelnMixin, Progress):\n    width = 32\n    message = ''\n    suffix = '%(index)d/%(max)d'\n    bar_prefix = ' |'\n    bar_suffix = '| '\n    empty_fill = ' '\n    fill = '#'\n    hide_cursor = True\n\n    def update(self):\n        filled_length = int(self.width * self.progress)\n        empty_length = self.width - filled_length\n\n        message = self.message % self\n        bar = self.fill * filled_length\n        empty = self.empty_fill * empty_length\n        suffix = self.suffix % self\n        line = ''.join([message, self.bar_prefix, bar, empty, self.bar_suffix,\n                        suffix])\n        self.writeln(line)\n\n\nclass ChargingBar(Bar):\n    suffix = '%(percent)d%%'\n    bar_prefix = ' '\n    bar_suffix = ' '\n    empty_fill = '∙'\n    fill = '█'\n\n\nclass FillingSquaresBar(ChargingBar):\n    empty_fill = '▢'\n    fill = '▣'\n\n\nclass FillingCirclesBar(ChargingBar):\n    empty_fill = '◯'\n    fill = '◉'\n\n\nclass IncrementalBar(Bar):\n    if sys.platform.startswith('win'):\n        phases = (u' ', u'▌', u'█')\n    else:\n        phases = (' ', '▏', '▎', '▍', '▌', '▋', '▊', '▉', '█')\n\n    def update(self):\n        nphases = len(self.phases)\n        filled_len = self.width * self.progress\n        nfull = int(filled_len)                      # Number of full chars\n        phase = int((filled_len - nfull) * nphases)  # Phase of last char\n        nempty = self.width - nfull                  # Number of empty chars\n\n        message = self.message % self\n        bar = self.phases[-1] * nfull\n        current = self.phases[phase] if phase > 0 else ''\n        empty = self.empty_fill * max(0, nempty - len(current))\n        suffix = self.suffix % self\n        line = ''.join([message, self.bar_prefix, bar, current, empty,\n                        self.bar_suffix, suffix])\n        self.writeln(line)\n\n\nclass PixelBar(IncrementalBar):\n    phases = ('⡀', '⡄', '⡆', '⡇', '⣇', '⣧', '⣷', '⣿')\n\n\nclass ShadyBar(IncrementalBar):\n    phases = (' ', '░', '▒', '▓', '█')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/progress/counter.py",
    "content": "# -*- coding: utf-8 -*-\n\n# Copyright (c) 2012 Giorgos Verigakis <verigak@gmail.com>\n#\n# Permission to use, copy, modify, and distribute this software for any\n# purpose with or without fee is hereby granted, provided that the above\n# copyright notice and this permission notice appear in all copies.\n#\n# THE SOFTWARE IS PROVIDED \"AS IS\" AND THE AUTHOR DISCLAIMS ALL WARRANTIES\n# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF\n# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR\n# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES\n# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN\n# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF\n# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.\n\nfrom __future__ import unicode_literals\nfrom . import Infinite, Progress\nfrom .helpers import WriteMixin\n\n\nclass Counter(WriteMixin, Infinite):\n    message = ''\n    hide_cursor = True\n\n    def update(self):\n        self.write(str(self.index))\n\n\nclass Countdown(WriteMixin, Progress):\n    hide_cursor = True\n\n    def update(self):\n        self.write(str(self.remaining))\n\n\nclass Stack(WriteMixin, Progress):\n    phases = (' ', '▁', '▂', '▃', '▄', '▅', '▆', '▇', '█')\n    hide_cursor = True\n\n    def update(self):\n        nphases = len(self.phases)\n        i = min(nphases - 1, int(self.progress * nphases))\n        self.write(self.phases[i])\n\n\nclass Pie(Stack):\n    phases = ('○', '◔', '◑', '◕', '●')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/progress/helpers.py",
    "content": "# Copyright (c) 2012 Giorgos Verigakis <verigak@gmail.com>\n#\n# Permission to use, copy, modify, and distribute this software for any\n# purpose with or without fee is hereby granted, provided that the above\n# copyright notice and this permission notice appear in all copies.\n#\n# THE SOFTWARE IS PROVIDED \"AS IS\" AND THE AUTHOR DISCLAIMS ALL WARRANTIES\n# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF\n# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR\n# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES\n# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN\n# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF\n# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.\n\nfrom __future__ import print_function\n\n\nHIDE_CURSOR = '\\x1b[?25l'\nSHOW_CURSOR = '\\x1b[?25h'\n\n\nclass WriteMixin(object):\n    hide_cursor = False\n\n    def __init__(self, message=None, **kwargs):\n        super(WriteMixin, self).__init__(**kwargs)\n        self._width = 0\n        if message:\n            self.message = message\n\n        if self.file and self.file.isatty():\n            if self.hide_cursor:\n                print(HIDE_CURSOR, end='', file=self.file)\n            print(self.message, end='', file=self.file)\n            self.file.flush()\n\n    def write(self, s):\n        if self.file and self.file.isatty():\n            b = '\\b' * self._width\n            c = s.ljust(self._width)\n            print(b + c, end='', file=self.file)\n            self._width = max(self._width, len(s))\n            self.file.flush()\n\n    def finish(self):\n        if self.file and self.file.isatty() and self.hide_cursor:\n            print(SHOW_CURSOR, end='', file=self.file)\n\n\nclass WritelnMixin(object):\n    hide_cursor = False\n\n    def __init__(self, message=None, **kwargs):\n        super(WritelnMixin, self).__init__(**kwargs)\n        if message:\n            self.message = message\n\n        if self.file and self.file.isatty() and self.hide_cursor:\n            print(HIDE_CURSOR, end='', file=self.file)\n\n    def clearln(self):\n        if self.file and self.file.isatty():\n            print('\\r\\x1b[K', end='', file=self.file)\n\n    def writeln(self, line):\n        if self.file and self.file.isatty():\n            self.clearln()\n            print(line, end='', file=self.file)\n            self.file.flush()\n\n    def finish(self):\n        if self.file and self.file.isatty():\n            print(file=self.file)\n            if self.hide_cursor:\n                print(SHOW_CURSOR, end='', file=self.file)\n\n\nfrom signal import signal, SIGINT\nfrom sys import exit\n\n\nclass SigIntMixin(object):\n    \"\"\"Registers a signal handler that calls finish on SIGINT\"\"\"\n\n    def __init__(self, *args, **kwargs):\n        super(SigIntMixin, self).__init__(*args, **kwargs)\n        signal(SIGINT, self._sigint_handler)\n\n    def _sigint_handler(self, signum, frame):\n        self.finish()\n        exit(0)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/progress/spinner.py",
    "content": "# -*- coding: utf-8 -*-\n\n# Copyright (c) 2012 Giorgos Verigakis <verigak@gmail.com>\n#\n# Permission to use, copy, modify, and distribute this software for any\n# purpose with or without fee is hereby granted, provided that the above\n# copyright notice and this permission notice appear in all copies.\n#\n# THE SOFTWARE IS PROVIDED \"AS IS\" AND THE AUTHOR DISCLAIMS ALL WARRANTIES\n# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF\n# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR\n# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES\n# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN\n# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF\n# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.\n\nfrom __future__ import unicode_literals\nfrom . import Infinite\nfrom .helpers import WriteMixin\n\n\nclass Spinner(WriteMixin, Infinite):\n    message = ''\n    phases = ('-', '\\\\', '|', '/')\n    hide_cursor = True\n\n    def update(self):\n        i = self.index % len(self.phases)\n        self.write(self.phases[i])\n\n\nclass PieSpinner(Spinner):\n    phases = ['◷', '◶', '◵', '◴']\n\n\nclass MoonSpinner(Spinner):\n    phases = ['◑', '◒', '◐', '◓']\n\n\nclass LineSpinner(Spinner):\n    phases = ['⎺', '⎻', '⎼', '⎽', '⎼', '⎻']\n\nclass PixelSpinner(Spinner):\n    phases = ['⣾','⣷', '⣯', '⣟', '⡿', '⢿', '⣻', '⣽']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pyparsing.py",
    "content": "#-*- coding: utf-8 -*-\n# module pyparsing.py\n#\n# Copyright (c) 2003-2019  Paul T. McGuire\n#\n# Permission is hereby granted, free of charge, to any person obtaining\n# a copy of this software and associated documentation files (the\n# \"Software\"), to deal in the Software without restriction, including\n# without limitation the rights to use, copy, modify, merge, publish,\n# distribute, sublicense, and/or sell copies of the Software, and to\n# permit persons to whom the Software is furnished to do so, subject to\n# the following conditions:\n#\n# The above copyright notice and this permission notice shall be\n# included in all copies or substantial portions of the Software.\n#\n# THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND,\n# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\n# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.\n# IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY\n# CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,\n# TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE\n# SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n#\n\n__doc__ = \\\n\"\"\"\npyparsing module - Classes and methods to define and execute parsing grammars\n=============================================================================\n\nThe pyparsing module is an alternative approach to creating and\nexecuting simple grammars, vs. the traditional lex/yacc approach, or the\nuse of regular expressions.  With pyparsing, you don't need to learn\na new syntax for defining grammars or matching expressions - the parsing\nmodule provides a library of classes that you use to construct the\ngrammar directly in Python.\n\nHere is a program to parse \"Hello, World!\" (or any greeting of the form\n``\"<salutation>, <addressee>!\"``), built up using :class:`Word`,\n:class:`Literal`, and :class:`And` elements\n(the :class:`'+'<ParserElement.__add__>` operators create :class:`And` expressions,\nand the strings are auto-converted to :class:`Literal` expressions)::\n\n    from pip._vendor.pyparsing import Word, alphas\n\n    # define grammar of a greeting\n    greet = Word(alphas) + \",\" + Word(alphas) + \"!\"\n\n    hello = \"Hello, World!\"\n    print (hello, \"->\", greet.parseString(hello))\n\nThe program outputs the following::\n\n    Hello, World! -> ['Hello', ',', 'World', '!']\n\nThe Python representation of the grammar is quite readable, owing to the\nself-explanatory class names, and the use of '+', '|' and '^' operators.\n\nThe :class:`ParseResults` object returned from\n:class:`ParserElement.parseString` can be\naccessed as a nested list, a dictionary, or an object with named\nattributes.\n\nThe pyparsing module handles some of the problems that are typically\nvexing when writing text parsers:\n\n  - extra or missing whitespace (the above program will also handle\n    \"Hello,World!\", \"Hello  ,  World  !\", etc.)\n  - quoted strings\n  - embedded comments\n\n\nGetting Started -\n-----------------\nVisit the classes :class:`ParserElement` and :class:`ParseResults` to\nsee the base classes that most other pyparsing\nclasses inherit from. Use the docstrings for examples of how to:\n\n - construct literal match expressions from :class:`Literal` and\n   :class:`CaselessLiteral` classes\n - construct character word-group expressions using the :class:`Word`\n   class\n - see how to create repetitive expressions using :class:`ZeroOrMore`\n   and :class:`OneOrMore` classes\n - use :class:`'+'<And>`, :class:`'|'<MatchFirst>`, :class:`'^'<Or>`,\n   and :class:`'&'<Each>` operators to combine simple expressions into\n   more complex ones\n - associate names with your parsed results using\n   :class:`ParserElement.setResultsName`\n - find some helpful expression short-cuts like :class:`delimitedList`\n   and :class:`oneOf`\n - find more useful common expressions in the :class:`pyparsing_common`\n   namespace class\n\"\"\"\n\n__version__ = \"2.3.1\"\n__versionTime__ = \"09 Jan 2019 23:26 UTC\"\n__author__ = \"Paul McGuire <ptmcg@users.sourceforge.net>\"\n\nimport string\nfrom weakref import ref as wkref\nimport copy\nimport sys\nimport warnings\nimport re\nimport sre_constants\nimport collections\nimport pprint\nimport traceback\nimport types\nfrom datetime import datetime\n\ntry:\n    # Python 3\n    from itertools import filterfalse\nexcept ImportError:\n    from itertools import ifilterfalse as filterfalse\n\ntry:\n    from _thread import RLock\nexcept ImportError:\n    from threading import RLock\n\ntry:\n    # Python 3\n    from collections.abc import Iterable\n    from collections.abc import MutableMapping\nexcept ImportError:\n    # Python 2.7\n    from collections import Iterable\n    from collections import MutableMapping\n\ntry:\n    from collections import OrderedDict as _OrderedDict\nexcept ImportError:\n    try:\n        from ordereddict import OrderedDict as _OrderedDict\n    except ImportError:\n        _OrderedDict = None\n\ntry:\n    from types import SimpleNamespace\nexcept ImportError:\n    class SimpleNamespace: pass\n\n\n#~ sys.stderr.write( \"testing pyparsing module, version %s, %s\\n\" % (__version__,__versionTime__ ) )\n\n__all__ = [\n'And', 'CaselessKeyword', 'CaselessLiteral', 'CharsNotIn', 'Combine', 'Dict', 'Each', 'Empty',\n'FollowedBy', 'Forward', 'GoToColumn', 'Group', 'Keyword', 'LineEnd', 'LineStart', 'Literal',\n'PrecededBy', 'MatchFirst', 'NoMatch', 'NotAny', 'OneOrMore', 'OnlyOnce', 'Optional', 'Or',\n'ParseBaseException', 'ParseElementEnhance', 'ParseException', 'ParseExpression', 'ParseFatalException',\n'ParseResults', 'ParseSyntaxException', 'ParserElement', 'QuotedString', 'RecursiveGrammarException',\n'Regex', 'SkipTo', 'StringEnd', 'StringStart', 'Suppress', 'Token', 'TokenConverter',\n'White', 'Word', 'WordEnd', 'WordStart', 'ZeroOrMore', 'Char',\n'alphanums', 'alphas', 'alphas8bit', 'anyCloseTag', 'anyOpenTag', 'cStyleComment', 'col',\n'commaSeparatedList', 'commonHTMLEntity', 'countedArray', 'cppStyleComment', 'dblQuotedString',\n'dblSlashComment', 'delimitedList', 'dictOf', 'downcaseTokens', 'empty', 'hexnums',\n'htmlComment', 'javaStyleComment', 'line', 'lineEnd', 'lineStart', 'lineno',\n'makeHTMLTags', 'makeXMLTags', 'matchOnlyAtCol', 'matchPreviousExpr', 'matchPreviousLiteral',\n'nestedExpr', 'nullDebugAction', 'nums', 'oneOf', 'opAssoc', 'operatorPrecedence', 'printables',\n'punc8bit', 'pythonStyleComment', 'quotedString', 'removeQuotes', 'replaceHTMLEntity',\n'replaceWith', 'restOfLine', 'sglQuotedString', 'srange', 'stringEnd',\n'stringStart', 'traceParseAction', 'unicodeString', 'upcaseTokens', 'withAttribute',\n'indentedBlock', 'originalTextFor', 'ungroup', 'infixNotation','locatedExpr', 'withClass',\n'CloseMatch', 'tokenMap', 'pyparsing_common', 'pyparsing_unicode', 'unicode_set',\n]\n\nsystem_version = tuple(sys.version_info)[:3]\nPY_3 = system_version[0] == 3\nif PY_3:\n    _MAX_INT = sys.maxsize\n    basestring = str\n    unichr = chr\n    unicode = str\n    _ustr = str\n\n    # build list of single arg builtins, that can be used as parse actions\n    singleArgBuiltins = [sum, len, sorted, reversed, list, tuple, set, any, all, min, max]\n\nelse:\n    _MAX_INT = sys.maxint\n    range = xrange\n\n    def _ustr(obj):\n        \"\"\"Drop-in replacement for str(obj) that tries to be Unicode\n        friendly. It first tries str(obj). If that fails with\n        a UnicodeEncodeError, then it tries unicode(obj). It then\n        < returns the unicode object | encodes it with the default\n        encoding | ... >.\n        \"\"\"\n        if isinstance(obj,unicode):\n            return obj\n\n        try:\n            # If this works, then _ustr(obj) has the same behaviour as str(obj), so\n            # it won't break any existing code.\n            return str(obj)\n\n        except UnicodeEncodeError:\n            # Else encode it\n            ret = unicode(obj).encode(sys.getdefaultencoding(), 'xmlcharrefreplace')\n            xmlcharref = Regex(r'&#\\d+;')\n            xmlcharref.setParseAction(lambda t: '\\\\u' + hex(int(t[0][2:-1]))[2:])\n            return xmlcharref.transformString(ret)\n\n    # build list of single arg builtins, tolerant of Python version, that can be used as parse actions\n    singleArgBuiltins = []\n    import __builtin__\n    for fname in \"sum len sorted reversed list tuple set any all min max\".split():\n        try:\n            singleArgBuiltins.append(getattr(__builtin__,fname))\n        except AttributeError:\n            continue\n\n_generatorType = type((y for y in range(1)))\n\ndef _xml_escape(data):\n    \"\"\"Escape &, <, >, \", ', etc. in a string of data.\"\"\"\n\n    # ampersand must be replaced first\n    from_symbols = '&><\"\\''\n    to_symbols = ('&'+s+';' for s in \"amp gt lt quot apos\".split())\n    for from_,to_ in zip(from_symbols, to_symbols):\n        data = data.replace(from_, to_)\n    return data\n\nalphas     = string.ascii_uppercase + string.ascii_lowercase\nnums       = \"0123456789\"\nhexnums    = nums + \"ABCDEFabcdef\"\nalphanums  = alphas + nums\n_bslash    = chr(92)\nprintables = \"\".join(c for c in string.printable if c not in string.whitespace)\n\nclass ParseBaseException(Exception):\n    \"\"\"base exception class for all parsing runtime exceptions\"\"\"\n    # Performance tuning: we construct a *lot* of these, so keep this\n    # constructor as small and fast as possible\n    def __init__( self, pstr, loc=0, msg=None, elem=None ):\n        self.loc = loc\n        if msg is None:\n            self.msg = pstr\n            self.pstr = \"\"\n        else:\n            self.msg = msg\n            self.pstr = pstr\n        self.parserElement = elem\n        self.args = (pstr, loc, msg)\n\n    @classmethod\n    def _from_exception(cls, pe):\n        \"\"\"\n        internal factory method to simplify creating one type of ParseException\n        from another - avoids having __init__ signature conflicts among subclasses\n        \"\"\"\n        return cls(pe.pstr, pe.loc, pe.msg, pe.parserElement)\n\n    def __getattr__( self, aname ):\n        \"\"\"supported attributes by name are:\n           - lineno - returns the line number of the exception text\n           - col - returns the column number of the exception text\n           - line - returns the line containing the exception text\n        \"\"\"\n        if( aname == \"lineno\" ):\n            return lineno( self.loc, self.pstr )\n        elif( aname in (\"col\", \"column\") ):\n            return col( self.loc, self.pstr )\n        elif( aname == \"line\" ):\n            return line( self.loc, self.pstr )\n        else:\n            raise AttributeError(aname)\n\n    def __str__( self ):\n        return \"%s (at char %d), (line:%d, col:%d)\" % \\\n                ( self.msg, self.loc, self.lineno, self.column )\n    def __repr__( self ):\n        return _ustr(self)\n    def markInputline( self, markerString = \">!<\" ):\n        \"\"\"Extracts the exception line from the input string, and marks\n           the location of the exception with a special symbol.\n        \"\"\"\n        line_str = self.line\n        line_column = self.column - 1\n        if markerString:\n            line_str = \"\".join((line_str[:line_column],\n                                markerString, line_str[line_column:]))\n        return line_str.strip()\n    def __dir__(self):\n        return \"lineno col line\".split() + dir(type(self))\n\nclass ParseException(ParseBaseException):\n    \"\"\"\n    Exception thrown when parse expressions don't match class;\n    supported attributes by name are:\n    - lineno - returns the line number of the exception text\n    - col - returns the column number of the exception text\n    - line - returns the line containing the exception text\n\n    Example::\n\n        try:\n            Word(nums).setName(\"integer\").parseString(\"ABC\")\n        except ParseException as pe:\n            print(pe)\n            print(\"column: {}\".format(pe.col))\n\n    prints::\n\n       Expected integer (at char 0), (line:1, col:1)\n        column: 1\n\n    \"\"\"\n\n    @staticmethod\n    def explain(exc, depth=16):\n        \"\"\"\n        Method to take an exception and translate the Python internal traceback into a list\n        of the pyparsing expressions that caused the exception to be raised.\n\n        Parameters:\n\n         - exc - exception raised during parsing (need not be a ParseException, in support\n           of Python exceptions that might be raised in a parse action)\n         - depth (default=16) - number of levels back in the stack trace to list expression\n           and function names; if None, the full stack trace names will be listed; if 0, only\n           the failing input line, marker, and exception string will be shown\n\n        Returns a multi-line string listing the ParserElements and/or function names in the\n        exception's stack trace.\n\n        Note: the diagnostic output will include string representations of the expressions\n        that failed to parse. These representations will be more helpful if you use `setName` to\n        give identifiable names to your expressions. Otherwise they will use the default string\n        forms, which may be cryptic to read.\n\n        explain() is only supported under Python 3.\n        \"\"\"\n        import inspect\n\n        if depth is None:\n            depth = sys.getrecursionlimit()\n        ret = []\n        if isinstance(exc, ParseBaseException):\n            ret.append(exc.line)\n            ret.append(' ' * (exc.col - 1) + '^')\n        ret.append(\"{0}: {1}\".format(type(exc).__name__, exc))\n\n        if depth > 0:\n            callers = inspect.getinnerframes(exc.__traceback__, context=depth)\n            seen = set()\n            for i, ff in enumerate(callers[-depth:]):\n                frm = ff.frame\n\n                f_self = frm.f_locals.get('self', None)\n                if isinstance(f_self, ParserElement):\n                    if frm.f_code.co_name not in ('parseImpl', '_parseNoCache'):\n                        continue\n                    if f_self in seen:\n                        continue\n                    seen.add(f_self)\n\n                    self_type = type(f_self)\n                    ret.append(\"{0}.{1} - {2}\".format(self_type.__module__,\n                                                      self_type.__name__,\n                                                      f_self))\n                elif f_self is not None:\n                    self_type = type(f_self)\n                    ret.append(\"{0}.{1}\".format(self_type.__module__,\n                                                self_type.__name__))\n                else:\n                    code = frm.f_code\n                    if code.co_name in ('wrapper', '<module>'):\n                        continue\n\n                    ret.append(\"{0}\".format(code.co_name))\n\n                depth -= 1\n                if not depth:\n                    break\n\n        return '\\n'.join(ret)\n\n\nclass ParseFatalException(ParseBaseException):\n    \"\"\"user-throwable exception thrown when inconsistent parse content\n       is found; stops all parsing immediately\"\"\"\n    pass\n\nclass ParseSyntaxException(ParseFatalException):\n    \"\"\"just like :class:`ParseFatalException`, but thrown internally\n    when an :class:`ErrorStop<And._ErrorStop>` ('-' operator) indicates\n    that parsing is to stop immediately because an unbacktrackable\n    syntax error has been found.\n    \"\"\"\n    pass\n\n#~ class ReparseException(ParseBaseException):\n    #~ \"\"\"Experimental class - parse actions can raise this exception to cause\n       #~ pyparsing to reparse the input string:\n        #~ - with a modified input string, and/or\n        #~ - with a modified start location\n       #~ Set the values of the ReparseException in the constructor, and raise the\n       #~ exception in a parse action to cause pyparsing to use the new string/location.\n       #~ Setting the values as None causes no change to be made.\n       #~ \"\"\"\n    #~ def __init_( self, newstring, restartLoc ):\n        #~ self.newParseText = newstring\n        #~ self.reparseLoc = restartLoc\n\nclass RecursiveGrammarException(Exception):\n    \"\"\"exception thrown by :class:`ParserElement.validate` if the\n    grammar could be improperly recursive\n    \"\"\"\n    def __init__( self, parseElementList ):\n        self.parseElementTrace = parseElementList\n\n    def __str__( self ):\n        return \"RecursiveGrammarException: %s\" % self.parseElementTrace\n\nclass _ParseResultsWithOffset(object):\n    def __init__(self,p1,p2):\n        self.tup = (p1,p2)\n    def __getitem__(self,i):\n        return self.tup[i]\n    def __repr__(self):\n        return repr(self.tup[0])\n    def setOffset(self,i):\n        self.tup = (self.tup[0],i)\n\nclass ParseResults(object):\n    \"\"\"Structured parse results, to provide multiple means of access to\n    the parsed data:\n\n       - as a list (``len(results)``)\n       - by list index (``results[0], results[1]``, etc.)\n       - by attribute (``results.<resultsName>`` - see :class:`ParserElement.setResultsName`)\n\n    Example::\n\n        integer = Word(nums)\n        date_str = (integer.setResultsName(\"year\") + '/'\n                        + integer.setResultsName(\"month\") + '/'\n                        + integer.setResultsName(\"day\"))\n        # equivalent form:\n        # date_str = integer(\"year\") + '/' + integer(\"month\") + '/' + integer(\"day\")\n\n        # parseString returns a ParseResults object\n        result = date_str.parseString(\"1999/12/31\")\n\n        def test(s, fn=repr):\n            print(\"%s -> %s\" % (s, fn(eval(s))))\n        test(\"list(result)\")\n        test(\"result[0]\")\n        test(\"result['month']\")\n        test(\"result.day\")\n        test(\"'month' in result\")\n        test(\"'minutes' in result\")\n        test(\"result.dump()\", str)\n\n    prints::\n\n        list(result) -> ['1999', '/', '12', '/', '31']\n        result[0] -> '1999'\n        result['month'] -> '12'\n        result.day -> '31'\n        'month' in result -> True\n        'minutes' in result -> False\n        result.dump() -> ['1999', '/', '12', '/', '31']\n        - day: 31\n        - month: 12\n        - year: 1999\n    \"\"\"\n    def __new__(cls, toklist=None, name=None, asList=True, modal=True ):\n        if isinstance(toklist, cls):\n            return toklist\n        retobj = object.__new__(cls)\n        retobj.__doinit = True\n        return retobj\n\n    # Performance tuning: we construct a *lot* of these, so keep this\n    # constructor as small and fast as possible\n    def __init__( self, toklist=None, name=None, asList=True, modal=True, isinstance=isinstance ):\n        if self.__doinit:\n            self.__doinit = False\n            self.__name = None\n            self.__parent = None\n            self.__accumNames = {}\n            self.__asList = asList\n            self.__modal = modal\n            if toklist is None:\n                toklist = []\n            if isinstance(toklist, list):\n                self.__toklist = toklist[:]\n            elif isinstance(toklist, _generatorType):\n                self.__toklist = list(toklist)\n            else:\n                self.__toklist = [toklist]\n            self.__tokdict = dict()\n\n        if name is not None and name:\n            if not modal:\n                self.__accumNames[name] = 0\n            if isinstance(name,int):\n                name = _ustr(name) # will always return a str, but use _ustr for consistency\n            self.__name = name\n            if not (isinstance(toklist, (type(None), basestring, list)) and toklist in (None,'',[])):\n                if isinstance(toklist,basestring):\n                    toklist = [ toklist ]\n                if asList:\n                    if isinstance(toklist,ParseResults):\n                        self[name] = _ParseResultsWithOffset(ParseResults(toklist.__toklist), 0)\n                    else:\n                        self[name] = _ParseResultsWithOffset(ParseResults(toklist[0]),0)\n                    self[name].__name = name\n                else:\n                    try:\n                        self[name] = toklist[0]\n                    except (KeyError,TypeError,IndexError):\n                        self[name] = toklist\n\n    def __getitem__( self, i ):\n        if isinstance( i, (int,slice) ):\n            return self.__toklist[i]\n        else:\n            if i not in self.__accumNames:\n                return self.__tokdict[i][-1][0]\n            else:\n                return ParseResults([ v[0] for v in self.__tokdict[i] ])\n\n    def __setitem__( self, k, v, isinstance=isinstance ):\n        if isinstance(v,_ParseResultsWithOffset):\n            self.__tokdict[k] = self.__tokdict.get(k,list()) + [v]\n            sub = v[0]\n        elif isinstance(k,(int,slice)):\n            self.__toklist[k] = v\n            sub = v\n        else:\n            self.__tokdict[k] = self.__tokdict.get(k,list()) + [_ParseResultsWithOffset(v,0)]\n            sub = v\n        if isinstance(sub,ParseResults):\n            sub.__parent = wkref(self)\n\n    def __delitem__( self, i ):\n        if isinstance(i,(int,slice)):\n            mylen = len( self.__toklist )\n            del self.__toklist[i]\n\n            # convert int to slice\n            if isinstance(i, int):\n                if i < 0:\n                    i += mylen\n                i = slice(i, i+1)\n            # get removed indices\n            removed = list(range(*i.indices(mylen)))\n            removed.reverse()\n            # fixup indices in token dictionary\n            for name,occurrences in self.__tokdict.items():\n                for j in removed:\n                    for k, (value, position) in enumerate(occurrences):\n                        occurrences[k] = _ParseResultsWithOffset(value, position - (position > j))\n        else:\n            del self.__tokdict[i]\n\n    def __contains__( self, k ):\n        return k in self.__tokdict\n\n    def __len__( self ): return len( self.__toklist )\n    def __bool__(self): return ( not not self.__toklist )\n    __nonzero__ = __bool__\n    def __iter__( self ): return iter( self.__toklist )\n    def __reversed__( self ): return iter( self.__toklist[::-1] )\n    def _iterkeys( self ):\n        if hasattr(self.__tokdict, \"iterkeys\"):\n            return self.__tokdict.iterkeys()\n        else:\n            return iter(self.__tokdict)\n\n    def _itervalues( self ):\n        return (self[k] for k in self._iterkeys())\n\n    def _iteritems( self ):\n        return ((k, self[k]) for k in self._iterkeys())\n\n    if PY_3:\n        keys = _iterkeys\n        \"\"\"Returns an iterator of all named result keys.\"\"\"\n\n        values = _itervalues\n        \"\"\"Returns an iterator of all named result values.\"\"\"\n\n        items = _iteritems\n        \"\"\"Returns an iterator of all named result key-value tuples.\"\"\"\n\n    else:\n        iterkeys = _iterkeys\n        \"\"\"Returns an iterator of all named result keys (Python 2.x only).\"\"\"\n\n        itervalues = _itervalues\n        \"\"\"Returns an iterator of all named result values (Python 2.x only).\"\"\"\n\n        iteritems = _iteritems\n        \"\"\"Returns an iterator of all named result key-value tuples (Python 2.x only).\"\"\"\n\n        def keys( self ):\n            \"\"\"Returns all named result keys (as a list in Python 2.x, as an iterator in Python 3.x).\"\"\"\n            return list(self.iterkeys())\n\n        def values( self ):\n            \"\"\"Returns all named result values (as a list in Python 2.x, as an iterator in Python 3.x).\"\"\"\n            return list(self.itervalues())\n\n        def items( self ):\n            \"\"\"Returns all named result key-values (as a list of tuples in Python 2.x, as an iterator in Python 3.x).\"\"\"\n            return list(self.iteritems())\n\n    def haskeys( self ):\n        \"\"\"Since keys() returns an iterator, this method is helpful in bypassing\n           code that looks for the existence of any defined results names.\"\"\"\n        return bool(self.__tokdict)\n\n    def pop( self, *args, **kwargs):\n        \"\"\"\n        Removes and returns item at specified index (default= ``last``).\n        Supports both ``list`` and ``dict`` semantics for ``pop()``. If\n        passed no argument or an integer argument, it will use ``list``\n        semantics and pop tokens from the list of parsed tokens. If passed\n        a non-integer argument (most likely a string), it will use ``dict``\n        semantics and pop the corresponding value from any defined results\n        names. A second default return value argument is supported, just as in\n        ``dict.pop()``.\n\n        Example::\n\n            def remove_first(tokens):\n                tokens.pop(0)\n            print(OneOrMore(Word(nums)).parseString(\"0 123 321\")) # -> ['0', '123', '321']\n            print(OneOrMore(Word(nums)).addParseAction(remove_first).parseString(\"0 123 321\")) # -> ['123', '321']\n\n            label = Word(alphas)\n            patt = label(\"LABEL\") + OneOrMore(Word(nums))\n            print(patt.parseString(\"AAB 123 321\").dump())\n\n            # Use pop() in a parse action to remove named result (note that corresponding value is not\n            # removed from list form of results)\n            def remove_LABEL(tokens):\n                tokens.pop(\"LABEL\")\n                return tokens\n            patt.addParseAction(remove_LABEL)\n            print(patt.parseString(\"AAB 123 321\").dump())\n\n        prints::\n\n            ['AAB', '123', '321']\n            - LABEL: AAB\n\n            ['AAB', '123', '321']\n        \"\"\"\n        if not args:\n            args = [-1]\n        for k,v in kwargs.items():\n            if k == 'default':\n                args = (args[0], v)\n            else:\n                raise TypeError(\"pop() got an unexpected keyword argument '%s'\" % k)\n        if (isinstance(args[0], int) or\n                        len(args) == 1 or\n                        args[0] in self):\n            index = args[0]\n            ret = self[index]\n            del self[index]\n            return ret\n        else:\n            defaultvalue = args[1]\n            return defaultvalue\n\n    def get(self, key, defaultValue=None):\n        \"\"\"\n        Returns named result matching the given key, or if there is no\n        such name, then returns the given ``defaultValue`` or ``None`` if no\n        ``defaultValue`` is specified.\n\n        Similar to ``dict.get()``.\n\n        Example::\n\n            integer = Word(nums)\n            date_str = integer(\"year\") + '/' + integer(\"month\") + '/' + integer(\"day\")\n\n            result = date_str.parseString(\"1999/12/31\")\n            print(result.get(\"year\")) # -> '1999'\n            print(result.get(\"hour\", \"not specified\")) # -> 'not specified'\n            print(result.get(\"hour\")) # -> None\n        \"\"\"\n        if key in self:\n            return self[key]\n        else:\n            return defaultValue\n\n    def insert( self, index, insStr ):\n        \"\"\"\n        Inserts new element at location index in the list of parsed tokens.\n\n        Similar to ``list.insert()``.\n\n        Example::\n\n            print(OneOrMore(Word(nums)).parseString(\"0 123 321\")) # -> ['0', '123', '321']\n\n            # use a parse action to insert the parse location in the front of the parsed results\n            def insert_locn(locn, tokens):\n                tokens.insert(0, locn)\n            print(OneOrMore(Word(nums)).addParseAction(insert_locn).parseString(\"0 123 321\")) # -> [0, '0', '123', '321']\n        \"\"\"\n        self.__toklist.insert(index, insStr)\n        # fixup indices in token dictionary\n        for name,occurrences in self.__tokdict.items():\n            for k, (value, position) in enumerate(occurrences):\n                occurrences[k] = _ParseResultsWithOffset(value, position + (position > index))\n\n    def append( self, item ):\n        \"\"\"\n        Add single element to end of ParseResults list of elements.\n\n        Example::\n\n            print(OneOrMore(Word(nums)).parseString(\"0 123 321\")) # -> ['0', '123', '321']\n\n            # use a parse action to compute the sum of the parsed integers, and add it to the end\n            def append_sum(tokens):\n                tokens.append(sum(map(int, tokens)))\n            print(OneOrMore(Word(nums)).addParseAction(append_sum).parseString(\"0 123 321\")) # -> ['0', '123', '321', 444]\n        \"\"\"\n        self.__toklist.append(item)\n\n    def extend( self, itemseq ):\n        \"\"\"\n        Add sequence of elements to end of ParseResults list of elements.\n\n        Example::\n\n            patt = OneOrMore(Word(alphas))\n\n            # use a parse action to append the reverse of the matched strings, to make a palindrome\n            def make_palindrome(tokens):\n                tokens.extend(reversed([t[::-1] for t in tokens]))\n                return ''.join(tokens)\n            print(patt.addParseAction(make_palindrome).parseString(\"lskdj sdlkjf lksd\")) # -> 'lskdjsdlkjflksddsklfjkldsjdksl'\n        \"\"\"\n        if isinstance(itemseq, ParseResults):\n            self += itemseq\n        else:\n            self.__toklist.extend(itemseq)\n\n    def clear( self ):\n        \"\"\"\n        Clear all elements and results names.\n        \"\"\"\n        del self.__toklist[:]\n        self.__tokdict.clear()\n\n    def __getattr__( self, name ):\n        try:\n            return self[name]\n        except KeyError:\n            return \"\"\n\n        if name in self.__tokdict:\n            if name not in self.__accumNames:\n                return self.__tokdict[name][-1][0]\n            else:\n                return ParseResults([ v[0] for v in self.__tokdict[name] ])\n        else:\n            return \"\"\n\n    def __add__( self, other ):\n        ret = self.copy()\n        ret += other\n        return ret\n\n    def __iadd__( self, other ):\n        if other.__tokdict:\n            offset = len(self.__toklist)\n            addoffset = lambda a: offset if a<0 else a+offset\n            otheritems = other.__tokdict.items()\n            otherdictitems = [(k, _ParseResultsWithOffset(v[0],addoffset(v[1])) )\n                                for (k,vlist) in otheritems for v in vlist]\n            for k,v in otherdictitems:\n                self[k] = v\n                if isinstance(v[0],ParseResults):\n                    v[0].__parent = wkref(self)\n\n        self.__toklist += other.__toklist\n        self.__accumNames.update( other.__accumNames )\n        return self\n\n    def __radd__(self, other):\n        if isinstance(other,int) and other == 0:\n            # useful for merging many ParseResults using sum() builtin\n            return self.copy()\n        else:\n            # this may raise a TypeError - so be it\n            return other + self\n\n    def __repr__( self ):\n        return \"(%s, %s)\" % ( repr( self.__toklist ), repr( self.__tokdict ) )\n\n    def __str__( self ):\n        return '[' + ', '.join(_ustr(i) if isinstance(i, ParseResults) else repr(i) for i in self.__toklist) + ']'\n\n    def _asStringList( self, sep='' ):\n        out = []\n        for item in self.__toklist:\n            if out and sep:\n                out.append(sep)\n            if isinstance( item, ParseResults ):\n                out += item._asStringList()\n            else:\n                out.append( _ustr(item) )\n        return out\n\n    def asList( self ):\n        \"\"\"\n        Returns the parse results as a nested list of matching tokens, all converted to strings.\n\n        Example::\n\n            patt = OneOrMore(Word(alphas))\n            result = patt.parseString(\"sldkj lsdkj sldkj\")\n            # even though the result prints in string-like form, it is actually a pyparsing ParseResults\n            print(type(result), result) # -> <class 'pyparsing.ParseResults'> ['sldkj', 'lsdkj', 'sldkj']\n\n            # Use asList() to create an actual list\n            result_list = result.asList()\n            print(type(result_list), result_list) # -> <class 'list'> ['sldkj', 'lsdkj', 'sldkj']\n        \"\"\"\n        return [res.asList() if isinstance(res,ParseResults) else res for res in self.__toklist]\n\n    def asDict( self ):\n        \"\"\"\n        Returns the named parse results as a nested dictionary.\n\n        Example::\n\n            integer = Word(nums)\n            date_str = integer(\"year\") + '/' + integer(\"month\") + '/' + integer(\"day\")\n\n            result = date_str.parseString('12/31/1999')\n            print(type(result), repr(result)) # -> <class 'pyparsing.ParseResults'> (['12', '/', '31', '/', '1999'], {'day': [('1999', 4)], 'year': [('12', 0)], 'month': [('31', 2)]})\n\n            result_dict = result.asDict()\n            print(type(result_dict), repr(result_dict)) # -> <class 'dict'> {'day': '1999', 'year': '12', 'month': '31'}\n\n            # even though a ParseResults supports dict-like access, sometime you just need to have a dict\n            import json\n            print(json.dumps(result)) # -> Exception: TypeError: ... is not JSON serializable\n            print(json.dumps(result.asDict())) # -> {\"month\": \"31\", \"day\": \"1999\", \"year\": \"12\"}\n        \"\"\"\n        if PY_3:\n            item_fn = self.items\n        else:\n            item_fn = self.iteritems\n\n        def toItem(obj):\n            if isinstance(obj, ParseResults):\n                if obj.haskeys():\n                    return obj.asDict()\n                else:\n                    return [toItem(v) for v in obj]\n            else:\n                return obj\n\n        return dict((k,toItem(v)) for k,v in item_fn())\n\n    def copy( self ):\n        \"\"\"\n        Returns a new copy of a :class:`ParseResults` object.\n        \"\"\"\n        ret = ParseResults( self.__toklist )\n        ret.__tokdict = dict(self.__tokdict.items())\n        ret.__parent = self.__parent\n        ret.__accumNames.update( self.__accumNames )\n        ret.__name = self.__name\n        return ret\n\n    def asXML( self, doctag=None, namedItemsOnly=False, indent=\"\", formatted=True ):\n        \"\"\"\n        (Deprecated) Returns the parse results as XML. Tags are created for tokens and lists that have defined results names.\n        \"\"\"\n        nl = \"\\n\"\n        out = []\n        namedItems = dict((v[1],k) for (k,vlist) in self.__tokdict.items()\n                                                            for v in vlist)\n        nextLevelIndent = indent + \"  \"\n\n        # collapse out indents if formatting is not desired\n        if not formatted:\n            indent = \"\"\n            nextLevelIndent = \"\"\n            nl = \"\"\n\n        selfTag = None\n        if doctag is not None:\n            selfTag = doctag\n        else:\n            if self.__name:\n                selfTag = self.__name\n\n        if not selfTag:\n            if namedItemsOnly:\n                return \"\"\n            else:\n                selfTag = \"ITEM\"\n\n        out += [ nl, indent, \"<\", selfTag, \">\" ]\n\n        for i,res in enumerate(self.__toklist):\n            if isinstance(res,ParseResults):\n                if i in namedItems:\n                    out += [ res.asXML(namedItems[i],\n                                        namedItemsOnly and doctag is None,\n                                        nextLevelIndent,\n                                        formatted)]\n                else:\n                    out += [ res.asXML(None,\n                                        namedItemsOnly and doctag is None,\n                                        nextLevelIndent,\n                                        formatted)]\n            else:\n                # individual token, see if there is a name for it\n                resTag = None\n                if i in namedItems:\n                    resTag = namedItems[i]\n                if not resTag:\n                    if namedItemsOnly:\n                        continue\n                    else:\n                        resTag = \"ITEM\"\n                xmlBodyText = _xml_escape(_ustr(res))\n                out += [ nl, nextLevelIndent, \"<\", resTag, \">\",\n                                                xmlBodyText,\n                                                \"</\", resTag, \">\" ]\n\n        out += [ nl, indent, \"</\", selfTag, \">\" ]\n        return \"\".join(out)\n\n    def __lookup(self,sub):\n        for k,vlist in self.__tokdict.items():\n            for v,loc in vlist:\n                if sub is v:\n                    return k\n        return None\n\n    def getName(self):\n        r\"\"\"\n        Returns the results name for this token expression. Useful when several\n        different expressions might match at a particular location.\n\n        Example::\n\n            integer = Word(nums)\n            ssn_expr = Regex(r\"\\d\\d\\d-\\d\\d-\\d\\d\\d\\d\")\n            house_number_expr = Suppress('#') + Word(nums, alphanums)\n            user_data = (Group(house_number_expr)(\"house_number\")\n                        | Group(ssn_expr)(\"ssn\")\n                        | Group(integer)(\"age\"))\n            user_info = OneOrMore(user_data)\n\n            result = user_info.parseString(\"22 111-22-3333 #221B\")\n            for item in result:\n                print(item.getName(), ':', item[0])\n\n        prints::\n\n            age : 22\n            ssn : 111-22-3333\n            house_number : 221B\n        \"\"\"\n        if self.__name:\n            return self.__name\n        elif self.__parent:\n            par = self.__parent()\n            if par:\n                return par.__lookup(self)\n            else:\n                return None\n        elif (len(self) == 1 and\n               len(self.__tokdict) == 1 and\n               next(iter(self.__tokdict.values()))[0][1] in (0,-1)):\n            return next(iter(self.__tokdict.keys()))\n        else:\n            return None\n\n    def dump(self, indent='', depth=0, full=True):\n        \"\"\"\n        Diagnostic method for listing out the contents of\n        a :class:`ParseResults`. Accepts an optional ``indent`` argument so\n        that this string can be embedded in a nested display of other data.\n\n        Example::\n\n            integer = Word(nums)\n            date_str = integer(\"year\") + '/' + integer(\"month\") + '/' + integer(\"day\")\n\n            result = date_str.parseString('12/31/1999')\n            print(result.dump())\n\n        prints::\n\n            ['12', '/', '31', '/', '1999']\n            - day: 1999\n            - month: 31\n            - year: 12\n        \"\"\"\n        out = []\n        NL = '\\n'\n        out.append( indent+_ustr(self.asList()) )\n        if full:\n            if self.haskeys():\n                items = sorted((str(k), v) for k,v in self.items())\n                for k,v in items:\n                    if out:\n                        out.append(NL)\n                    out.append( \"%s%s- %s: \" % (indent,('  '*depth), k) )\n                    if isinstance(v,ParseResults):\n                        if v:\n                            out.append( v.dump(indent,depth+1) )\n                        else:\n                            out.append(_ustr(v))\n                    else:\n                        out.append(repr(v))\n            elif any(isinstance(vv,ParseResults) for vv in self):\n                v = self\n                for i,vv in enumerate(v):\n                    if isinstance(vv,ParseResults):\n                        out.append(\"\\n%s%s[%d]:\\n%s%s%s\" % (indent,('  '*(depth)),i,indent,('  '*(depth+1)),vv.dump(indent,depth+1) ))\n                    else:\n                        out.append(\"\\n%s%s[%d]:\\n%s%s%s\" % (indent,('  '*(depth)),i,indent,('  '*(depth+1)),_ustr(vv)))\n\n        return \"\".join(out)\n\n    def pprint(self, *args, **kwargs):\n        \"\"\"\n        Pretty-printer for parsed results as a list, using the\n        `pprint <https://docs.python.org/3/library/pprint.html>`_ module.\n        Accepts additional positional or keyword args as defined for\n        `pprint.pprint <https://docs.python.org/3/library/pprint.html#pprint.pprint>`_ .\n\n        Example::\n\n            ident = Word(alphas, alphanums)\n            num = Word(nums)\n            func = Forward()\n            term = ident | num | Group('(' + func + ')')\n            func <<= ident + Group(Optional(delimitedList(term)))\n            result = func.parseString(\"fna a,b,(fnb c,d,200),100\")\n            result.pprint(width=40)\n\n        prints::\n\n            ['fna',\n             ['a',\n              'b',\n              ['(', 'fnb', ['c', 'd', '200'], ')'],\n              '100']]\n        \"\"\"\n        pprint.pprint(self.asList(), *args, **kwargs)\n\n    # add support for pickle protocol\n    def __getstate__(self):\n        return ( self.__toklist,\n                 ( self.__tokdict.copy(),\n                   self.__parent is not None and self.__parent() or None,\n                   self.__accumNames,\n                   self.__name ) )\n\n    def __setstate__(self,state):\n        self.__toklist = state[0]\n        (self.__tokdict,\n         par,\n         inAccumNames,\n         self.__name) = state[1]\n        self.__accumNames = {}\n        self.__accumNames.update(inAccumNames)\n        if par is not None:\n            self.__parent = wkref(par)\n        else:\n            self.__parent = None\n\n    def __getnewargs__(self):\n        return self.__toklist, self.__name, self.__asList, self.__modal\n\n    def __dir__(self):\n        return (dir(type(self)) + list(self.keys()))\n\nMutableMapping.register(ParseResults)\n\ndef col (loc,strg):\n    \"\"\"Returns current column within a string, counting newlines as line separators.\n   The first column is number 1.\n\n   Note: the default parsing behavior is to expand tabs in the input string\n   before starting the parsing process.  See\n   :class:`ParserElement.parseString` for more\n   information on parsing strings containing ``<TAB>`` s, and suggested\n   methods to maintain a consistent view of the parsed string, the parse\n   location, and line and column positions within the parsed string.\n   \"\"\"\n    s = strg\n    return 1 if 0<loc<len(s) and s[loc-1] == '\\n' else loc - s.rfind(\"\\n\", 0, loc)\n\ndef lineno(loc,strg):\n    \"\"\"Returns current line number within a string, counting newlines as line separators.\n    The first line is number 1.\n\n    Note - the default parsing behavior is to expand tabs in the input string\n    before starting the parsing process.  See :class:`ParserElement.parseString`\n    for more information on parsing strings containing ``<TAB>`` s, and\n    suggested methods to maintain a consistent view of the parsed string, the\n    parse location, and line and column positions within the parsed string.\n    \"\"\"\n    return strg.count(\"\\n\",0,loc) + 1\n\ndef line( loc, strg ):\n    \"\"\"Returns the line of text containing loc within a string, counting newlines as line separators.\n       \"\"\"\n    lastCR = strg.rfind(\"\\n\", 0, loc)\n    nextCR = strg.find(\"\\n\", loc)\n    if nextCR >= 0:\n        return strg[lastCR+1:nextCR]\n    else:\n        return strg[lastCR+1:]\n\ndef _defaultStartDebugAction( instring, loc, expr ):\n    print ((\"Match \" + _ustr(expr) + \" at loc \" + _ustr(loc) + \"(%d,%d)\" % ( lineno(loc,instring), col(loc,instring) )))\n\ndef _defaultSuccessDebugAction( instring, startloc, endloc, expr, toks ):\n    print (\"Matched \" + _ustr(expr) + \" -> \" + str(toks.asList()))\n\ndef _defaultExceptionDebugAction( instring, loc, expr, exc ):\n    print (\"Exception raised:\" + _ustr(exc))\n\ndef nullDebugAction(*args):\n    \"\"\"'Do-nothing' debug action, to suppress debugging output during parsing.\"\"\"\n    pass\n\n# Only works on Python 3.x - nonlocal is toxic to Python 2 installs\n#~ 'decorator to trim function calls to match the arity of the target'\n#~ def _trim_arity(func, maxargs=3):\n    #~ if func in singleArgBuiltins:\n        #~ return lambda s,l,t: func(t)\n    #~ limit = 0\n    #~ foundArity = False\n    #~ def wrapper(*args):\n        #~ nonlocal limit,foundArity\n        #~ while 1:\n            #~ try:\n                #~ ret = func(*args[limit:])\n                #~ foundArity = True\n                #~ return ret\n            #~ except TypeError:\n                #~ if limit == maxargs or foundArity:\n                    #~ raise\n                #~ limit += 1\n                #~ continue\n    #~ return wrapper\n\n# this version is Python 2.x-3.x cross-compatible\n'decorator to trim function calls to match the arity of the target'\ndef _trim_arity(func, maxargs=2):\n    if func in singleArgBuiltins:\n        return lambda s,l,t: func(t)\n    limit = [0]\n    foundArity = [False]\n\n    # traceback return data structure changed in Py3.5 - normalize back to plain tuples\n    if system_version[:2] >= (3,5):\n        def extract_stack(limit=0):\n            # special handling for Python 3.5.0 - extra deep call stack by 1\n            offset = -3 if system_version == (3,5,0) else -2\n            frame_summary = traceback.extract_stack(limit=-offset+limit-1)[offset]\n            return [frame_summary[:2]]\n        def extract_tb(tb, limit=0):\n            frames = traceback.extract_tb(tb, limit=limit)\n            frame_summary = frames[-1]\n            return [frame_summary[:2]]\n    else:\n        extract_stack = traceback.extract_stack\n        extract_tb = traceback.extract_tb\n\n    # synthesize what would be returned by traceback.extract_stack at the call to\n    # user's parse action 'func', so that we don't incur call penalty at parse time\n\n    LINE_DIFF = 6\n    # IF ANY CODE CHANGES, EVEN JUST COMMENTS OR BLANK LINES, BETWEEN THE NEXT LINE AND\n    # THE CALL TO FUNC INSIDE WRAPPER, LINE_DIFF MUST BE MODIFIED!!!!\n    this_line = extract_stack(limit=2)[-1]\n    pa_call_line_synth = (this_line[0], this_line[1]+LINE_DIFF)\n\n    def wrapper(*args):\n        while 1:\n            try:\n                ret = func(*args[limit[0]:])\n                foundArity[0] = True\n                return ret\n            except TypeError:\n                # re-raise TypeErrors if they did not come from our arity testing\n                if foundArity[0]:\n                    raise\n                else:\n                    try:\n                        tb = sys.exc_info()[-1]\n                        if not extract_tb(tb, limit=2)[-1][:2] == pa_call_line_synth:\n                            raise\n                    finally:\n                        del tb\n\n                if limit[0] <= maxargs:\n                    limit[0] += 1\n                    continue\n                raise\n\n    # copy func name to wrapper for sensible debug output\n    func_name = \"<parse action>\"\n    try:\n        func_name = getattr(func, '__name__',\n                            getattr(func, '__class__').__name__)\n    except Exception:\n        func_name = str(func)\n    wrapper.__name__ = func_name\n\n    return wrapper\n\nclass ParserElement(object):\n    \"\"\"Abstract base level parser element class.\"\"\"\n    DEFAULT_WHITE_CHARS = \" \\n\\t\\r\"\n    verbose_stacktrace = False\n\n    @staticmethod\n    def setDefaultWhitespaceChars( chars ):\n        r\"\"\"\n        Overrides the default whitespace chars\n\n        Example::\n\n            # default whitespace chars are space, <TAB> and newline\n            OneOrMore(Word(alphas)).parseString(\"abc def\\nghi jkl\")  # -> ['abc', 'def', 'ghi', 'jkl']\n\n            # change to just treat newline as significant\n            ParserElement.setDefaultWhitespaceChars(\" \\t\")\n            OneOrMore(Word(alphas)).parseString(\"abc def\\nghi jkl\")  # -> ['abc', 'def']\n        \"\"\"\n        ParserElement.DEFAULT_WHITE_CHARS = chars\n\n    @staticmethod\n    def inlineLiteralsUsing(cls):\n        \"\"\"\n        Set class to be used for inclusion of string literals into a parser.\n\n        Example::\n\n            # default literal class used is Literal\n            integer = Word(nums)\n            date_str = integer(\"year\") + '/' + integer(\"month\") + '/' + integer(\"day\")\n\n            date_str.parseString(\"1999/12/31\")  # -> ['1999', '/', '12', '/', '31']\n\n\n            # change to Suppress\n            ParserElement.inlineLiteralsUsing(Suppress)\n            date_str = integer(\"year\") + '/' + integer(\"month\") + '/' + integer(\"day\")\n\n            date_str.parseString(\"1999/12/31\")  # -> ['1999', '12', '31']\n        \"\"\"\n        ParserElement._literalStringClass = cls\n\n    def __init__( self, savelist=False ):\n        self.parseAction = list()\n        self.failAction = None\n        #~ self.name = \"<unknown>\"  # don't define self.name, let subclasses try/except upcall\n        self.strRepr = None\n        self.resultsName = None\n        self.saveAsList = savelist\n        self.skipWhitespace = True\n        self.whiteChars = set(ParserElement.DEFAULT_WHITE_CHARS)\n        self.copyDefaultWhiteChars = True\n        self.mayReturnEmpty = False # used when checking for left-recursion\n        self.keepTabs = False\n        self.ignoreExprs = list()\n        self.debug = False\n        self.streamlined = False\n        self.mayIndexError = True # used to optimize exception handling for subclasses that don't advance parse index\n        self.errmsg = \"\"\n        self.modalResults = True # used to mark results names as modal (report only last) or cumulative (list all)\n        self.debugActions = ( None, None, None ) #custom debug actions\n        self.re = None\n        self.callPreparse = True # used to avoid redundant calls to preParse\n        self.callDuringTry = False\n\n    def copy( self ):\n        \"\"\"\n        Make a copy of this :class:`ParserElement`.  Useful for defining\n        different parse actions for the same parsing pattern, using copies of\n        the original parse element.\n\n        Example::\n\n            integer = Word(nums).setParseAction(lambda toks: int(toks[0]))\n            integerK = integer.copy().addParseAction(lambda toks: toks[0]*1024) + Suppress(\"K\")\n            integerM = integer.copy().addParseAction(lambda toks: toks[0]*1024*1024) + Suppress(\"M\")\n\n            print(OneOrMore(integerK | integerM | integer).parseString(\"5K 100 640K 256M\"))\n\n        prints::\n\n            [5120, 100, 655360, 268435456]\n\n        Equivalent form of ``expr.copy()`` is just ``expr()``::\n\n            integerM = integer().addParseAction(lambda toks: toks[0]*1024*1024) + Suppress(\"M\")\n        \"\"\"\n        cpy = copy.copy( self )\n        cpy.parseAction = self.parseAction[:]\n        cpy.ignoreExprs = self.ignoreExprs[:]\n        if self.copyDefaultWhiteChars:\n            cpy.whiteChars = ParserElement.DEFAULT_WHITE_CHARS\n        return cpy\n\n    def setName( self, name ):\n        \"\"\"\n        Define name for this expression, makes debugging and exception messages clearer.\n\n        Example::\n\n            Word(nums).parseString(\"ABC\")  # -> Exception: Expected W:(0123...) (at char 0), (line:1, col:1)\n            Word(nums).setName(\"integer\").parseString(\"ABC\")  # -> Exception: Expected integer (at char 0), (line:1, col:1)\n        \"\"\"\n        self.name = name\n        self.errmsg = \"Expected \" + self.name\n        if hasattr(self,\"exception\"):\n            self.exception.msg = self.errmsg\n        return self\n\n    def setResultsName( self, name, listAllMatches=False ):\n        \"\"\"\n        Define name for referencing matching tokens as a nested attribute\n        of the returned parse results.\n        NOTE: this returns a *copy* of the original :class:`ParserElement` object;\n        this is so that the client can define a basic element, such as an\n        integer, and reference it in multiple places with different names.\n\n        You can also set results names using the abbreviated syntax,\n        ``expr(\"name\")`` in place of ``expr.setResultsName(\"name\")``\n        - see :class:`__call__`.\n\n        Example::\n\n            date_str = (integer.setResultsName(\"year\") + '/'\n                        + integer.setResultsName(\"month\") + '/'\n                        + integer.setResultsName(\"day\"))\n\n            # equivalent form:\n            date_str = integer(\"year\") + '/' + integer(\"month\") + '/' + integer(\"day\")\n        \"\"\"\n        newself = self.copy()\n        if name.endswith(\"*\"):\n            name = name[:-1]\n            listAllMatches=True\n        newself.resultsName = name\n        newself.modalResults = not listAllMatches\n        return newself\n\n    def setBreak(self,breakFlag = True):\n        \"\"\"Method to invoke the Python pdb debugger when this element is\n           about to be parsed. Set ``breakFlag`` to True to enable, False to\n           disable.\n        \"\"\"\n        if breakFlag:\n            _parseMethod = self._parse\n            def breaker(instring, loc, doActions=True, callPreParse=True):\n                import pdb\n                pdb.set_trace()\n                return _parseMethod( instring, loc, doActions, callPreParse )\n            breaker._originalParseMethod = _parseMethod\n            self._parse = breaker\n        else:\n            if hasattr(self._parse,\"_originalParseMethod\"):\n                self._parse = self._parse._originalParseMethod\n        return self\n\n    def setParseAction( self, *fns, **kwargs ):\n        \"\"\"\n        Define one or more actions to perform when successfully matching parse element definition.\n        Parse action fn is a callable method with 0-3 arguments, called as ``fn(s,loc,toks)`` ,\n        ``fn(loc,toks)`` , ``fn(toks)`` , or just ``fn()`` , where:\n\n        - s   = the original string being parsed (see note below)\n        - loc = the location of the matching substring\n        - toks = a list of the matched tokens, packaged as a :class:`ParseResults` object\n\n        If the functions in fns modify the tokens, they can return them as the return\n        value from fn, and the modified list of tokens will replace the original.\n        Otherwise, fn does not need to return any value.\n\n        Optional keyword arguments:\n        - callDuringTry = (default= ``False`` ) indicate if parse action should be run during lookaheads and alternate testing\n\n        Note: the default parsing behavior is to expand tabs in the input string\n        before starting the parsing process.  See :class:`parseString for more\n        information on parsing strings containing ``<TAB>`` s, and suggested\n        methods to maintain a consistent view of the parsed string, the parse\n        location, and line and column positions within the parsed string.\n\n        Example::\n\n            integer = Word(nums)\n            date_str = integer + '/' + integer + '/' + integer\n\n            date_str.parseString(\"1999/12/31\")  # -> ['1999', '/', '12', '/', '31']\n\n            # use parse action to convert to ints at parse time\n            integer = Word(nums).setParseAction(lambda toks: int(toks[0]))\n            date_str = integer + '/' + integer + '/' + integer\n\n            # note that integer fields are now ints, not strings\n            date_str.parseString(\"1999/12/31\")  # -> [1999, '/', 12, '/', 31]\n        \"\"\"\n        self.parseAction = list(map(_trim_arity, list(fns)))\n        self.callDuringTry = kwargs.get(\"callDuringTry\", False)\n        return self\n\n    def addParseAction( self, *fns, **kwargs ):\n        \"\"\"\n        Add one or more parse actions to expression's list of parse actions. See :class:`setParseAction`.\n\n        See examples in :class:`copy`.\n        \"\"\"\n        self.parseAction += list(map(_trim_arity, list(fns)))\n        self.callDuringTry = self.callDuringTry or kwargs.get(\"callDuringTry\", False)\n        return self\n\n    def addCondition(self, *fns, **kwargs):\n        \"\"\"Add a boolean predicate function to expression's list of parse actions. See\n        :class:`setParseAction` for function call signatures. Unlike ``setParseAction``,\n        functions passed to ``addCondition`` need to return boolean success/fail of the condition.\n\n        Optional keyword arguments:\n        - message = define a custom message to be used in the raised exception\n        - fatal   = if True, will raise ParseFatalException to stop parsing immediately; otherwise will raise ParseException\n\n        Example::\n\n            integer = Word(nums).setParseAction(lambda toks: int(toks[0]))\n            year_int = integer.copy()\n            year_int.addCondition(lambda toks: toks[0] >= 2000, message=\"Only support years 2000 and later\")\n            date_str = year_int + '/' + integer + '/' + integer\n\n            result = date_str.parseString(\"1999/12/31\")  # -> Exception: Only support years 2000 and later (at char 0), (line:1, col:1)\n        \"\"\"\n        msg = kwargs.get(\"message\", \"failed user-defined condition\")\n        exc_type = ParseFatalException if kwargs.get(\"fatal\", False) else ParseException\n        for fn in fns:\n            fn = _trim_arity(fn)\n            def pa(s,l,t):\n                if not bool(fn(s,l,t)):\n                    raise exc_type(s,l,msg)\n            self.parseAction.append(pa)\n        self.callDuringTry = self.callDuringTry or kwargs.get(\"callDuringTry\", False)\n        return self\n\n    def setFailAction( self, fn ):\n        \"\"\"Define action to perform if parsing fails at this expression.\n           Fail acton fn is a callable function that takes the arguments\n           ``fn(s,loc,expr,err)`` where:\n           - s = string being parsed\n           - loc = location where expression match was attempted and failed\n           - expr = the parse expression that failed\n           - err = the exception thrown\n           The function returns no value.  It may throw :class:`ParseFatalException`\n           if it is desired to stop parsing immediately.\"\"\"\n        self.failAction = fn\n        return self\n\n    def _skipIgnorables( self, instring, loc ):\n        exprsFound = True\n        while exprsFound:\n            exprsFound = False\n            for e in self.ignoreExprs:\n                try:\n                    while 1:\n                        loc,dummy = e._parse( instring, loc )\n                        exprsFound = True\n                except ParseException:\n                    pass\n        return loc\n\n    def preParse( self, instring, loc ):\n        if self.ignoreExprs:\n            loc = self._skipIgnorables( instring, loc )\n\n        if self.skipWhitespace:\n            wt = self.whiteChars\n            instrlen = len(instring)\n            while loc < instrlen and instring[loc] in wt:\n                loc += 1\n\n        return loc\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        return loc, []\n\n    def postParse( self, instring, loc, tokenlist ):\n        return tokenlist\n\n    #~ @profile\n    def _parseNoCache( self, instring, loc, doActions=True, callPreParse=True ):\n        debugging = ( self.debug ) #and doActions )\n\n        if debugging or self.failAction:\n            #~ print (\"Match\",self,\"at loc\",loc,\"(%d,%d)\" % ( lineno(loc,instring), col(loc,instring) ))\n            if (self.debugActions[0] ):\n                self.debugActions[0]( instring, loc, self )\n            if callPreParse and self.callPreparse:\n                preloc = self.preParse( instring, loc )\n            else:\n                preloc = loc\n            tokensStart = preloc\n            try:\n                try:\n                    loc,tokens = self.parseImpl( instring, preloc, doActions )\n                except IndexError:\n                    raise ParseException( instring, len(instring), self.errmsg, self )\n            except ParseBaseException as err:\n                #~ print (\"Exception raised:\", err)\n                if self.debugActions[2]:\n                    self.debugActions[2]( instring, tokensStart, self, err )\n                if self.failAction:\n                    self.failAction( instring, tokensStart, self, err )\n                raise\n        else:\n            if callPreParse and self.callPreparse:\n                preloc = self.preParse( instring, loc )\n            else:\n                preloc = loc\n            tokensStart = preloc\n            if self.mayIndexError or preloc >= len(instring):\n                try:\n                    loc,tokens = self.parseImpl( instring, preloc, doActions )\n                except IndexError:\n                    raise ParseException( instring, len(instring), self.errmsg, self )\n            else:\n                loc,tokens = self.parseImpl( instring, preloc, doActions )\n\n        tokens = self.postParse( instring, loc, tokens )\n\n        retTokens = ParseResults( tokens, self.resultsName, asList=self.saveAsList, modal=self.modalResults )\n        if self.parseAction and (doActions or self.callDuringTry):\n            if debugging:\n                try:\n                    for fn in self.parseAction:\n                        try:\n                            tokens = fn( instring, tokensStart, retTokens )\n                        except IndexError as parse_action_exc:\n                            exc = ParseException(\"exception raised in parse action\")\n                            exc.__cause__ = parse_action_exc\n                            raise exc\n\n                        if tokens is not None and tokens is not retTokens:\n                            retTokens = ParseResults( tokens,\n                                                      self.resultsName,\n                                                      asList=self.saveAsList and isinstance(tokens,(ParseResults,list)),\n                                                      modal=self.modalResults )\n                except ParseBaseException as err:\n                    #~ print \"Exception raised in user parse action:\", err\n                    if (self.debugActions[2] ):\n                        self.debugActions[2]( instring, tokensStart, self, err )\n                    raise\n            else:\n                for fn in self.parseAction:\n                    try:\n                        tokens = fn( instring, tokensStart, retTokens )\n                    except IndexError as parse_action_exc:\n                        exc = ParseException(\"exception raised in parse action\")\n                        exc.__cause__ = parse_action_exc\n                        raise exc\n\n                    if tokens is not None and tokens is not retTokens:\n                        retTokens = ParseResults( tokens,\n                                                  self.resultsName,\n                                                  asList=self.saveAsList and isinstance(tokens,(ParseResults,list)),\n                                                  modal=self.modalResults )\n        if debugging:\n            #~ print (\"Matched\",self,\"->\",retTokens.asList())\n            if (self.debugActions[1] ):\n                self.debugActions[1]( instring, tokensStart, loc, self, retTokens )\n\n        return loc, retTokens\n\n    def tryParse( self, instring, loc ):\n        try:\n            return self._parse( instring, loc, doActions=False )[0]\n        except ParseFatalException:\n            raise ParseException( instring, loc, self.errmsg, self)\n\n    def canParseNext(self, instring, loc):\n        try:\n            self.tryParse(instring, loc)\n        except (ParseException, IndexError):\n            return False\n        else:\n            return True\n\n    class _UnboundedCache(object):\n        def __init__(self):\n            cache = {}\n            self.not_in_cache = not_in_cache = object()\n\n            def get(self, key):\n                return cache.get(key, not_in_cache)\n\n            def set(self, key, value):\n                cache[key] = value\n\n            def clear(self):\n                cache.clear()\n\n            def cache_len(self):\n                return len(cache)\n\n            self.get = types.MethodType(get, self)\n            self.set = types.MethodType(set, self)\n            self.clear = types.MethodType(clear, self)\n            self.__len__ = types.MethodType(cache_len, self)\n\n    if _OrderedDict is not None:\n        class _FifoCache(object):\n            def __init__(self, size):\n                self.not_in_cache = not_in_cache = object()\n\n                cache = _OrderedDict()\n\n                def get(self, key):\n                    return cache.get(key, not_in_cache)\n\n                def set(self, key, value):\n                    cache[key] = value\n                    while len(cache) > size:\n                        try:\n                            cache.popitem(False)\n                        except KeyError:\n                            pass\n\n                def clear(self):\n                    cache.clear()\n\n                def cache_len(self):\n                    return len(cache)\n\n                self.get = types.MethodType(get, self)\n                self.set = types.MethodType(set, self)\n                self.clear = types.MethodType(clear, self)\n                self.__len__ = types.MethodType(cache_len, self)\n\n    else:\n        class _FifoCache(object):\n            def __init__(self, size):\n                self.not_in_cache = not_in_cache = object()\n\n                cache = {}\n                key_fifo = collections.deque([], size)\n\n                def get(self, key):\n                    return cache.get(key, not_in_cache)\n\n                def set(self, key, value):\n                    cache[key] = value\n                    while len(key_fifo) > size:\n                        cache.pop(key_fifo.popleft(), None)\n                    key_fifo.append(key)\n\n                def clear(self):\n                    cache.clear()\n                    key_fifo.clear()\n\n                def cache_len(self):\n                    return len(cache)\n\n                self.get = types.MethodType(get, self)\n                self.set = types.MethodType(set, self)\n                self.clear = types.MethodType(clear, self)\n                self.__len__ = types.MethodType(cache_len, self)\n\n    # argument cache for optimizing repeated calls when backtracking through recursive expressions\n    packrat_cache = {} # this is set later by enabledPackrat(); this is here so that resetCache() doesn't fail\n    packrat_cache_lock = RLock()\n    packrat_cache_stats = [0, 0]\n\n    # this method gets repeatedly called during backtracking with the same arguments -\n    # we can cache these arguments and save ourselves the trouble of re-parsing the contained expression\n    def _parseCache( self, instring, loc, doActions=True, callPreParse=True ):\n        HIT, MISS = 0, 1\n        lookup = (self, instring, loc, callPreParse, doActions)\n        with ParserElement.packrat_cache_lock:\n            cache = ParserElement.packrat_cache\n            value = cache.get(lookup)\n            if value is cache.not_in_cache:\n                ParserElement.packrat_cache_stats[MISS] += 1\n                try:\n                    value = self._parseNoCache(instring, loc, doActions, callPreParse)\n                except ParseBaseException as pe:\n                    # cache a copy of the exception, without the traceback\n                    cache.set(lookup, pe.__class__(*pe.args))\n                    raise\n                else:\n                    cache.set(lookup, (value[0], value[1].copy()))\n                    return value\n            else:\n                ParserElement.packrat_cache_stats[HIT] += 1\n                if isinstance(value, Exception):\n                    raise value\n                return (value[0], value[1].copy())\n\n    _parse = _parseNoCache\n\n    @staticmethod\n    def resetCache():\n        ParserElement.packrat_cache.clear()\n        ParserElement.packrat_cache_stats[:] = [0] * len(ParserElement.packrat_cache_stats)\n\n    _packratEnabled = False\n    @staticmethod\n    def enablePackrat(cache_size_limit=128):\n        \"\"\"Enables \"packrat\" parsing, which adds memoizing to the parsing logic.\n           Repeated parse attempts at the same string location (which happens\n           often in many complex grammars) can immediately return a cached value,\n           instead of re-executing parsing/validating code.  Memoizing is done of\n           both valid results and parsing exceptions.\n\n           Parameters:\n\n           - cache_size_limit - (default= ``128``) - if an integer value is provided\n             will limit the size of the packrat cache; if None is passed, then\n             the cache size will be unbounded; if 0 is passed, the cache will\n             be effectively disabled.\n\n           This speedup may break existing programs that use parse actions that\n           have side-effects.  For this reason, packrat parsing is disabled when\n           you first import pyparsing.  To activate the packrat feature, your\n           program must call the class method :class:`ParserElement.enablePackrat`.\n           For best results, call ``enablePackrat()`` immediately after\n           importing pyparsing.\n\n           Example::\n\n               from pip._vendor import pyparsing\n               pyparsing.ParserElement.enablePackrat()\n        \"\"\"\n        if not ParserElement._packratEnabled:\n            ParserElement._packratEnabled = True\n            if cache_size_limit is None:\n                ParserElement.packrat_cache = ParserElement._UnboundedCache()\n            else:\n                ParserElement.packrat_cache = ParserElement._FifoCache(cache_size_limit)\n            ParserElement._parse = ParserElement._parseCache\n\n    def parseString( self, instring, parseAll=False ):\n        \"\"\"\n        Execute the parse expression with the given string.\n        This is the main interface to the client code, once the complete\n        expression has been built.\n\n        If you want the grammar to require that the entire input string be\n        successfully parsed, then set ``parseAll`` to True (equivalent to ending\n        the grammar with ``StringEnd()``).\n\n        Note: ``parseString`` implicitly calls ``expandtabs()`` on the input string,\n        in order to report proper column numbers in parse actions.\n        If the input string contains tabs and\n        the grammar uses parse actions that use the ``loc`` argument to index into the\n        string being parsed, you can ensure you have a consistent view of the input\n        string by:\n\n        - calling ``parseWithTabs`` on your grammar before calling ``parseString``\n          (see :class:`parseWithTabs`)\n        - define your parse action using the full ``(s,loc,toks)`` signature, and\n          reference the input string using the parse action's ``s`` argument\n        - explictly expand the tabs in your input string before calling\n          ``parseString``\n\n        Example::\n\n            Word('a').parseString('aaaaabaaa')  # -> ['aaaaa']\n            Word('a').parseString('aaaaabaaa', parseAll=True)  # -> Exception: Expected end of text\n        \"\"\"\n        ParserElement.resetCache()\n        if not self.streamlined:\n            self.streamline()\n            #~ self.saveAsList = True\n        for e in self.ignoreExprs:\n            e.streamline()\n        if not self.keepTabs:\n            instring = instring.expandtabs()\n        try:\n            loc, tokens = self._parse( instring, 0 )\n            if parseAll:\n                loc = self.preParse( instring, loc )\n                se = Empty() + StringEnd()\n                se._parse( instring, loc )\n        except ParseBaseException as exc:\n            if ParserElement.verbose_stacktrace:\n                raise\n            else:\n                # catch and re-raise exception from here, clears out pyparsing internal stack trace\n                raise exc\n        else:\n            return tokens\n\n    def scanString( self, instring, maxMatches=_MAX_INT, overlap=False ):\n        \"\"\"\n        Scan the input string for expression matches.  Each match will return the\n        matching tokens, start location, and end location.  May be called with optional\n        ``maxMatches`` argument, to clip scanning after 'n' matches are found.  If\n        ``overlap`` is specified, then overlapping matches will be reported.\n\n        Note that the start and end locations are reported relative to the string\n        being parsed.  See :class:`parseString` for more information on parsing\n        strings with embedded tabs.\n\n        Example::\n\n            source = \"sldjf123lsdjjkf345sldkjf879lkjsfd987\"\n            print(source)\n            for tokens,start,end in Word(alphas).scanString(source):\n                print(' '*start + '^'*(end-start))\n                print(' '*start + tokens[0])\n\n        prints::\n\n            sldjf123lsdjjkf345sldkjf879lkjsfd987\n            ^^^^^\n            sldjf\n                    ^^^^^^^\n                    lsdjjkf\n                              ^^^^^^\n                              sldkjf\n                                       ^^^^^^\n                                       lkjsfd\n        \"\"\"\n        if not self.streamlined:\n            self.streamline()\n        for e in self.ignoreExprs:\n            e.streamline()\n\n        if not self.keepTabs:\n            instring = _ustr(instring).expandtabs()\n        instrlen = len(instring)\n        loc = 0\n        preparseFn = self.preParse\n        parseFn = self._parse\n        ParserElement.resetCache()\n        matches = 0\n        try:\n            while loc <= instrlen and matches < maxMatches:\n                try:\n                    preloc = preparseFn( instring, loc )\n                    nextLoc,tokens = parseFn( instring, preloc, callPreParse=False )\n                except ParseException:\n                    loc = preloc+1\n                else:\n                    if nextLoc > loc:\n                        matches += 1\n                        yield tokens, preloc, nextLoc\n                        if overlap:\n                            nextloc = preparseFn( instring, loc )\n                            if nextloc > loc:\n                                loc = nextLoc\n                            else:\n                                loc += 1\n                        else:\n                            loc = nextLoc\n                    else:\n                        loc = preloc+1\n        except ParseBaseException as exc:\n            if ParserElement.verbose_stacktrace:\n                raise\n            else:\n                # catch and re-raise exception from here, clears out pyparsing internal stack trace\n                raise exc\n\n    def transformString( self, instring ):\n        \"\"\"\n        Extension to :class:`scanString`, to modify matching text with modified tokens that may\n        be returned from a parse action.  To use ``transformString``, define a grammar and\n        attach a parse action to it that modifies the returned token list.\n        Invoking ``transformString()`` on a target string will then scan for matches,\n        and replace the matched text patterns according to the logic in the parse\n        action.  ``transformString()`` returns the resulting transformed string.\n\n        Example::\n\n            wd = Word(alphas)\n            wd.setParseAction(lambda toks: toks[0].title())\n\n            print(wd.transformString(\"now is the winter of our discontent made glorious summer by this sun of york.\"))\n\n        prints::\n\n            Now Is The Winter Of Our Discontent Made Glorious Summer By This Sun Of York.\n        \"\"\"\n        out = []\n        lastE = 0\n        # force preservation of <TAB>s, to minimize unwanted transformation of string, and to\n        # keep string locs straight between transformString and scanString\n        self.keepTabs = True\n        try:\n            for t,s,e in self.scanString( instring ):\n                out.append( instring[lastE:s] )\n                if t:\n                    if isinstance(t,ParseResults):\n                        out += t.asList()\n                    elif isinstance(t,list):\n                        out += t\n                    else:\n                        out.append(t)\n                lastE = e\n            out.append(instring[lastE:])\n            out = [o for o in out if o]\n            return \"\".join(map(_ustr,_flatten(out)))\n        except ParseBaseException as exc:\n            if ParserElement.verbose_stacktrace:\n                raise\n            else:\n                # catch and re-raise exception from here, clears out pyparsing internal stack trace\n                raise exc\n\n    def searchString( self, instring, maxMatches=_MAX_INT ):\n        \"\"\"\n        Another extension to :class:`scanString`, simplifying the access to the tokens found\n        to match the given parse expression.  May be called with optional\n        ``maxMatches`` argument, to clip searching after 'n' matches are found.\n\n        Example::\n\n            # a capitalized word starts with an uppercase letter, followed by zero or more lowercase letters\n            cap_word = Word(alphas.upper(), alphas.lower())\n\n            print(cap_word.searchString(\"More than Iron, more than Lead, more than Gold I need Electricity\"))\n\n            # the sum() builtin can be used to merge results into a single ParseResults object\n            print(sum(cap_word.searchString(\"More than Iron, more than Lead, more than Gold I need Electricity\")))\n\n        prints::\n\n            [['More'], ['Iron'], ['Lead'], ['Gold'], ['I'], ['Electricity']]\n            ['More', 'Iron', 'Lead', 'Gold', 'I', 'Electricity']\n        \"\"\"\n        try:\n            return ParseResults([ t for t,s,e in self.scanString( instring, maxMatches ) ])\n        except ParseBaseException as exc:\n            if ParserElement.verbose_stacktrace:\n                raise\n            else:\n                # catch and re-raise exception from here, clears out pyparsing internal stack trace\n                raise exc\n\n    def split(self, instring, maxsplit=_MAX_INT, includeSeparators=False):\n        \"\"\"\n        Generator method to split a string using the given expression as a separator.\n        May be called with optional ``maxsplit`` argument, to limit the number of splits;\n        and the optional ``includeSeparators`` argument (default= ``False``), if the separating\n        matching text should be included in the split results.\n\n        Example::\n\n            punc = oneOf(list(\".,;:/-!?\"))\n            print(list(punc.split(\"This, this?, this sentence, is badly punctuated!\")))\n\n        prints::\n\n            ['This', ' this', '', ' this sentence', ' is badly punctuated', '']\n        \"\"\"\n        splits = 0\n        last = 0\n        for t,s,e in self.scanString(instring, maxMatches=maxsplit):\n            yield instring[last:s]\n            if includeSeparators:\n                yield t[0]\n            last = e\n        yield instring[last:]\n\n    def __add__(self, other ):\n        \"\"\"\n        Implementation of + operator - returns :class:`And`. Adding strings to a ParserElement\n        converts them to :class:`Literal`s by default.\n\n        Example::\n\n            greet = Word(alphas) + \",\" + Word(alphas) + \"!\"\n            hello = \"Hello, World!\"\n            print (hello, \"->\", greet.parseString(hello))\n\n        prints::\n\n            Hello, World! -> ['Hello', ',', 'World', '!']\n        \"\"\"\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        if not isinstance( other, ParserElement ):\n            warnings.warn(\"Cannot combine element of type %s with ParserElement\" % type(other),\n                    SyntaxWarning, stacklevel=2)\n            return None\n        return And( [ self, other ] )\n\n    def __radd__(self, other ):\n        \"\"\"\n        Implementation of + operator when left operand is not a :class:`ParserElement`\n        \"\"\"\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        if not isinstance( other, ParserElement ):\n            warnings.warn(\"Cannot combine element of type %s with ParserElement\" % type(other),\n                    SyntaxWarning, stacklevel=2)\n            return None\n        return other + self\n\n    def __sub__(self, other):\n        \"\"\"\n        Implementation of - operator, returns :class:`And` with error stop\n        \"\"\"\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        if not isinstance( other, ParserElement ):\n            warnings.warn(\"Cannot combine element of type %s with ParserElement\" % type(other),\n                    SyntaxWarning, stacklevel=2)\n            return None\n        return self + And._ErrorStop() + other\n\n    def __rsub__(self, other ):\n        \"\"\"\n        Implementation of - operator when left operand is not a :class:`ParserElement`\n        \"\"\"\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        if not isinstance( other, ParserElement ):\n            warnings.warn(\"Cannot combine element of type %s with ParserElement\" % type(other),\n                    SyntaxWarning, stacklevel=2)\n            return None\n        return other - self\n\n    def __mul__(self,other):\n        \"\"\"\n        Implementation of * operator, allows use of ``expr * 3`` in place of\n        ``expr + expr + expr``.  Expressions may also me multiplied by a 2-integer\n        tuple, similar to ``{min,max}`` multipliers in regular expressions.  Tuples\n        may also include ``None`` as in:\n         - ``expr*(n,None)`` or ``expr*(n,)`` is equivalent\n              to ``expr*n + ZeroOrMore(expr)``\n              (read as \"at least n instances of ``expr``\")\n         - ``expr*(None,n)`` is equivalent to ``expr*(0,n)``\n              (read as \"0 to n instances of ``expr``\")\n         - ``expr*(None,None)`` is equivalent to ``ZeroOrMore(expr)``\n         - ``expr*(1,None)`` is equivalent to ``OneOrMore(expr)``\n\n        Note that ``expr*(None,n)`` does not raise an exception if\n        more than n exprs exist in the input stream; that is,\n        ``expr*(None,n)`` does not enforce a maximum number of expr\n        occurrences.  If this behavior is desired, then write\n        ``expr*(None,n) + ~expr``\n        \"\"\"\n        if isinstance(other,int):\n            minElements, optElements = other,0\n        elif isinstance(other,tuple):\n            other = (other + (None, None))[:2]\n            if other[0] is None:\n                other = (0, other[1])\n            if isinstance(other[0],int) and other[1] is None:\n                if other[0] == 0:\n                    return ZeroOrMore(self)\n                if other[0] == 1:\n                    return OneOrMore(self)\n                else:\n                    return self*other[0] + ZeroOrMore(self)\n            elif isinstance(other[0],int) and isinstance(other[1],int):\n                minElements, optElements = other\n                optElements -= minElements\n            else:\n                raise TypeError(\"cannot multiply 'ParserElement' and ('%s','%s') objects\", type(other[0]),type(other[1]))\n        else:\n            raise TypeError(\"cannot multiply 'ParserElement' and '%s' objects\", type(other))\n\n        if minElements < 0:\n            raise ValueError(\"cannot multiply ParserElement by negative value\")\n        if optElements < 0:\n            raise ValueError(\"second tuple value must be greater or equal to first tuple value\")\n        if minElements == optElements == 0:\n            raise ValueError(\"cannot multiply ParserElement by 0 or (0,0)\")\n\n        if (optElements):\n            def makeOptionalList(n):\n                if n>1:\n                    return Optional(self + makeOptionalList(n-1))\n                else:\n                    return Optional(self)\n            if minElements:\n                if minElements == 1:\n                    ret = self + makeOptionalList(optElements)\n                else:\n                    ret = And([self]*minElements) + makeOptionalList(optElements)\n            else:\n                ret = makeOptionalList(optElements)\n        else:\n            if minElements == 1:\n                ret = self\n            else:\n                ret = And([self]*minElements)\n        return ret\n\n    def __rmul__(self, other):\n        return self.__mul__(other)\n\n    def __or__(self, other ):\n        \"\"\"\n        Implementation of | operator - returns :class:`MatchFirst`\n        \"\"\"\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        if not isinstance( other, ParserElement ):\n            warnings.warn(\"Cannot combine element of type %s with ParserElement\" % type(other),\n                    SyntaxWarning, stacklevel=2)\n            return None\n        return MatchFirst( [ self, other ] )\n\n    def __ror__(self, other ):\n        \"\"\"\n        Implementation of | operator when left operand is not a :class:`ParserElement`\n        \"\"\"\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        if not isinstance( other, ParserElement ):\n            warnings.warn(\"Cannot combine element of type %s with ParserElement\" % type(other),\n                    SyntaxWarning, stacklevel=2)\n            return None\n        return other | self\n\n    def __xor__(self, other ):\n        \"\"\"\n        Implementation of ^ operator - returns :class:`Or`\n        \"\"\"\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        if not isinstance( other, ParserElement ):\n            warnings.warn(\"Cannot combine element of type %s with ParserElement\" % type(other),\n                    SyntaxWarning, stacklevel=2)\n            return None\n        return Or( [ self, other ] )\n\n    def __rxor__(self, other ):\n        \"\"\"\n        Implementation of ^ operator when left operand is not a :class:`ParserElement`\n        \"\"\"\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        if not isinstance( other, ParserElement ):\n            warnings.warn(\"Cannot combine element of type %s with ParserElement\" % type(other),\n                    SyntaxWarning, stacklevel=2)\n            return None\n        return other ^ self\n\n    def __and__(self, other ):\n        \"\"\"\n        Implementation of & operator - returns :class:`Each`\n        \"\"\"\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        if not isinstance( other, ParserElement ):\n            warnings.warn(\"Cannot combine element of type %s with ParserElement\" % type(other),\n                    SyntaxWarning, stacklevel=2)\n            return None\n        return Each( [ self, other ] )\n\n    def __rand__(self, other ):\n        \"\"\"\n        Implementation of & operator when left operand is not a :class:`ParserElement`\n        \"\"\"\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        if not isinstance( other, ParserElement ):\n            warnings.warn(\"Cannot combine element of type %s with ParserElement\" % type(other),\n                    SyntaxWarning, stacklevel=2)\n            return None\n        return other & self\n\n    def __invert__( self ):\n        \"\"\"\n        Implementation of ~ operator - returns :class:`NotAny`\n        \"\"\"\n        return NotAny( self )\n\n    def __call__(self, name=None):\n        \"\"\"\n        Shortcut for :class:`setResultsName`, with ``listAllMatches=False``.\n\n        If ``name`` is given with a trailing ``'*'`` character, then ``listAllMatches`` will be\n        passed as ``True``.\n\n        If ``name` is omitted, same as calling :class:`copy`.\n\n        Example::\n\n            # these are equivalent\n            userdata = Word(alphas).setResultsName(\"name\") + Word(nums+\"-\").setResultsName(\"socsecno\")\n            userdata = Word(alphas)(\"name\") + Word(nums+\"-\")(\"socsecno\")\n        \"\"\"\n        if name is not None:\n            return self.setResultsName(name)\n        else:\n            return self.copy()\n\n    def suppress( self ):\n        \"\"\"\n        Suppresses the output of this :class:`ParserElement`; useful to keep punctuation from\n        cluttering up returned output.\n        \"\"\"\n        return Suppress( self )\n\n    def leaveWhitespace( self ):\n        \"\"\"\n        Disables the skipping of whitespace before matching the characters in the\n        :class:`ParserElement`'s defined pattern.  This is normally only used internally by\n        the pyparsing module, but may be needed in some whitespace-sensitive grammars.\n        \"\"\"\n        self.skipWhitespace = False\n        return self\n\n    def setWhitespaceChars( self, chars ):\n        \"\"\"\n        Overrides the default whitespace chars\n        \"\"\"\n        self.skipWhitespace = True\n        self.whiteChars = chars\n        self.copyDefaultWhiteChars = False\n        return self\n\n    def parseWithTabs( self ):\n        \"\"\"\n        Overrides default behavior to expand ``<TAB>``s to spaces before parsing the input string.\n        Must be called before ``parseString`` when the input grammar contains elements that\n        match ``<TAB>`` characters.\n        \"\"\"\n        self.keepTabs = True\n        return self\n\n    def ignore( self, other ):\n        \"\"\"\n        Define expression to be ignored (e.g., comments) while doing pattern\n        matching; may be called repeatedly, to define multiple comment or other\n        ignorable patterns.\n\n        Example::\n\n            patt = OneOrMore(Word(alphas))\n            patt.parseString('ablaj /* comment */ lskjd') # -> ['ablaj']\n\n            patt.ignore(cStyleComment)\n            patt.parseString('ablaj /* comment */ lskjd') # -> ['ablaj', 'lskjd']\n        \"\"\"\n        if isinstance(other, basestring):\n            other = Suppress(other)\n\n        if isinstance( other, Suppress ):\n            if other not in self.ignoreExprs:\n                self.ignoreExprs.append(other)\n        else:\n            self.ignoreExprs.append( Suppress( other.copy() ) )\n        return self\n\n    def setDebugActions( self, startAction, successAction, exceptionAction ):\n        \"\"\"\n        Enable display of debugging messages while doing pattern matching.\n        \"\"\"\n        self.debugActions = (startAction or _defaultStartDebugAction,\n                             successAction or _defaultSuccessDebugAction,\n                             exceptionAction or _defaultExceptionDebugAction)\n        self.debug = True\n        return self\n\n    def setDebug( self, flag=True ):\n        \"\"\"\n        Enable display of debugging messages while doing pattern matching.\n        Set ``flag`` to True to enable, False to disable.\n\n        Example::\n\n            wd = Word(alphas).setName(\"alphaword\")\n            integer = Word(nums).setName(\"numword\")\n            term = wd | integer\n\n            # turn on debugging for wd\n            wd.setDebug()\n\n            OneOrMore(term).parseString(\"abc 123 xyz 890\")\n\n        prints::\n\n            Match alphaword at loc 0(1,1)\n            Matched alphaword -> ['abc']\n            Match alphaword at loc 3(1,4)\n            Exception raised:Expected alphaword (at char 4), (line:1, col:5)\n            Match alphaword at loc 7(1,8)\n            Matched alphaword -> ['xyz']\n            Match alphaword at loc 11(1,12)\n            Exception raised:Expected alphaword (at char 12), (line:1, col:13)\n            Match alphaword at loc 15(1,16)\n            Exception raised:Expected alphaword (at char 15), (line:1, col:16)\n\n        The output shown is that produced by the default debug actions - custom debug actions can be\n        specified using :class:`setDebugActions`. Prior to attempting\n        to match the ``wd`` expression, the debugging message ``\"Match <exprname> at loc <n>(<line>,<col>)\"``\n        is shown. Then if the parse succeeds, a ``\"Matched\"`` message is shown, or an ``\"Exception raised\"``\n        message is shown. Also note the use of :class:`setName` to assign a human-readable name to the expression,\n        which makes debugging and exception messages easier to understand - for instance, the default\n        name created for the :class:`Word` expression without calling ``setName`` is ``\"W:(ABCD...)\"``.\n        \"\"\"\n        if flag:\n            self.setDebugActions( _defaultStartDebugAction, _defaultSuccessDebugAction, _defaultExceptionDebugAction )\n        else:\n            self.debug = False\n        return self\n\n    def __str__( self ):\n        return self.name\n\n    def __repr__( self ):\n        return _ustr(self)\n\n    def streamline( self ):\n        self.streamlined = True\n        self.strRepr = None\n        return self\n\n    def checkRecursion( self, parseElementList ):\n        pass\n\n    def validate( self, validateTrace=[] ):\n        \"\"\"\n        Check defined expressions for valid structure, check for infinite recursive definitions.\n        \"\"\"\n        self.checkRecursion( [] )\n\n    def parseFile( self, file_or_filename, parseAll=False ):\n        \"\"\"\n        Execute the parse expression on the given file or filename.\n        If a filename is specified (instead of a file object),\n        the entire file is opened, read, and closed before parsing.\n        \"\"\"\n        try:\n            file_contents = file_or_filename.read()\n        except AttributeError:\n            with open(file_or_filename, \"r\") as f:\n                file_contents = f.read()\n        try:\n            return self.parseString(file_contents, parseAll)\n        except ParseBaseException as exc:\n            if ParserElement.verbose_stacktrace:\n                raise\n            else:\n                # catch and re-raise exception from here, clears out pyparsing internal stack trace\n                raise exc\n\n    def __eq__(self,other):\n        if isinstance(other, ParserElement):\n            return self is other or vars(self) == vars(other)\n        elif isinstance(other, basestring):\n            return self.matches(other)\n        else:\n            return super(ParserElement,self)==other\n\n    def __ne__(self,other):\n        return not (self == other)\n\n    def __hash__(self):\n        return hash(id(self))\n\n    def __req__(self,other):\n        return self == other\n\n    def __rne__(self,other):\n        return not (self == other)\n\n    def matches(self, testString, parseAll=True):\n        \"\"\"\n        Method for quick testing of a parser against a test string. Good for simple\n        inline microtests of sub expressions while building up larger parser.\n\n        Parameters:\n         - testString - to test against this expression for a match\n         - parseAll - (default= ``True``) - flag to pass to :class:`parseString` when running tests\n\n        Example::\n\n            expr = Word(nums)\n            assert expr.matches(\"100\")\n        \"\"\"\n        try:\n            self.parseString(_ustr(testString), parseAll=parseAll)\n            return True\n        except ParseBaseException:\n            return False\n\n    def runTests(self, tests, parseAll=True, comment='#',\n                 fullDump=True, printResults=True, failureTests=False, postParse=None):\n        \"\"\"\n        Execute the parse expression on a series of test strings, showing each\n        test, the parsed results or where the parse failed. Quick and easy way to\n        run a parse expression against a list of sample strings.\n\n        Parameters:\n         - tests - a list of separate test strings, or a multiline string of test strings\n         - parseAll - (default= ``True``) - flag to pass to :class:`parseString` when running tests\n         - comment - (default= ``'#'``) - expression for indicating embedded comments in the test\n              string; pass None to disable comment filtering\n         - fullDump - (default= ``True``) - dump results as list followed by results names in nested outline;\n              if False, only dump nested list\n         - printResults - (default= ``True``) prints test output to stdout\n         - failureTests - (default= ``False``) indicates if these tests are expected to fail parsing\n         - postParse - (default= ``None``) optional callback for successful parse results; called as\n              `fn(test_string, parse_results)` and returns a string to be added to the test output\n\n        Returns: a (success, results) tuple, where success indicates that all tests succeeded\n        (or failed if ``failureTests`` is True), and the results contain a list of lines of each\n        test's output\n\n        Example::\n\n            number_expr = pyparsing_common.number.copy()\n\n            result = number_expr.runTests('''\n                # unsigned integer\n                100\n                # negative integer\n                -100\n                # float with scientific notation\n                6.02e23\n                # integer with scientific notation\n                1e-12\n                ''')\n            print(\"Success\" if result[0] else \"Failed!\")\n\n            result = number_expr.runTests('''\n                # stray character\n                100Z\n                # missing leading digit before '.'\n                -.100\n                # too many '.'\n                3.14.159\n                ''', failureTests=True)\n            print(\"Success\" if result[0] else \"Failed!\")\n\n        prints::\n\n            # unsigned integer\n            100\n            [100]\n\n            # negative integer\n            -100\n            [-100]\n\n            # float with scientific notation\n            6.02e23\n            [6.02e+23]\n\n            # integer with scientific notation\n            1e-12\n            [1e-12]\n\n            Success\n\n            # stray character\n            100Z\n               ^\n            FAIL: Expected end of text (at char 3), (line:1, col:4)\n\n            # missing leading digit before '.'\n            -.100\n            ^\n            FAIL: Expected {real number with scientific notation | real number | signed integer} (at char 0), (line:1, col:1)\n\n            # too many '.'\n            3.14.159\n                ^\n            FAIL: Expected end of text (at char 4), (line:1, col:5)\n\n            Success\n\n        Each test string must be on a single line. If you want to test a string that spans multiple\n        lines, create a test like this::\n\n            expr.runTest(r\"this is a test\\\\n of strings that spans \\\\n 3 lines\")\n\n        (Note that this is a raw string literal, you must include the leading 'r'.)\n        \"\"\"\n        if isinstance(tests, basestring):\n            tests = list(map(str.strip, tests.rstrip().splitlines()))\n        if isinstance(comment, basestring):\n            comment = Literal(comment)\n        allResults = []\n        comments = []\n        success = True\n        for t in tests:\n            if comment is not None and comment.matches(t, False) or comments and not t:\n                comments.append(t)\n                continue\n            if not t:\n                continue\n            out = ['\\n'.join(comments), t]\n            comments = []\n            try:\n                # convert newline marks to actual newlines, and strip leading BOM if present\n                t = t.replace(r'\\n','\\n').lstrip('\\ufeff')\n                result = self.parseString(t, parseAll=parseAll)\n                out.append(result.dump(full=fullDump))\n                success = success and not failureTests\n                if postParse is not None:\n                    try:\n                        pp_value = postParse(t, result)\n                        if pp_value is not None:\n                            out.append(str(pp_value))\n                    except Exception as e:\n                        out.append(\"{0} failed: {1}: {2}\".format(postParse.__name__, type(e).__name__, e))\n            except ParseBaseException as pe:\n                fatal = \"(FATAL)\" if isinstance(pe, ParseFatalException) else \"\"\n                if '\\n' in t:\n                    out.append(line(pe.loc, t))\n                    out.append(' '*(col(pe.loc,t)-1) + '^' + fatal)\n                else:\n                    out.append(' '*pe.loc + '^' + fatal)\n                out.append(\"FAIL: \" + str(pe))\n                success = success and failureTests\n                result = pe\n            except Exception as exc:\n                out.append(\"FAIL-EXCEPTION: \" + str(exc))\n                success = success and failureTests\n                result = exc\n\n            if printResults:\n                if fullDump:\n                    out.append('')\n                print('\\n'.join(out))\n\n            allResults.append((t, result))\n\n        return success, allResults\n\n\nclass Token(ParserElement):\n    \"\"\"Abstract :class:`ParserElement` subclass, for defining atomic\n    matching patterns.\n    \"\"\"\n    def __init__( self ):\n        super(Token,self).__init__( savelist=False )\n\n\nclass Empty(Token):\n    \"\"\"An empty token, will always match.\n    \"\"\"\n    def __init__( self ):\n        super(Empty,self).__init__()\n        self.name = \"Empty\"\n        self.mayReturnEmpty = True\n        self.mayIndexError = False\n\n\nclass NoMatch(Token):\n    \"\"\"A token that will never match.\n    \"\"\"\n    def __init__( self ):\n        super(NoMatch,self).__init__()\n        self.name = \"NoMatch\"\n        self.mayReturnEmpty = True\n        self.mayIndexError = False\n        self.errmsg = \"Unmatchable token\"\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        raise ParseException(instring, loc, self.errmsg, self)\n\n\nclass Literal(Token):\n    \"\"\"Token to exactly match a specified string.\n\n    Example::\n\n        Literal('blah').parseString('blah')  # -> ['blah']\n        Literal('blah').parseString('blahfooblah')  # -> ['blah']\n        Literal('blah').parseString('bla')  # -> Exception: Expected \"blah\"\n\n    For case-insensitive matching, use :class:`CaselessLiteral`.\n\n    For keyword matching (force word break before and after the matched string),\n    use :class:`Keyword` or :class:`CaselessKeyword`.\n    \"\"\"\n    def __init__( self, matchString ):\n        super(Literal,self).__init__()\n        self.match = matchString\n        self.matchLen = len(matchString)\n        try:\n            self.firstMatchChar = matchString[0]\n        except IndexError:\n            warnings.warn(\"null string passed to Literal; use Empty() instead\",\n                            SyntaxWarning, stacklevel=2)\n            self.__class__ = Empty\n        self.name = '\"%s\"' % _ustr(self.match)\n        self.errmsg = \"Expected \" + self.name\n        self.mayReturnEmpty = False\n        self.mayIndexError = False\n\n    # Performance tuning: this routine gets called a *lot*\n    # if this is a single character match string  and the first character matches,\n    # short-circuit as quickly as possible, and avoid calling startswith\n    #~ @profile\n    def parseImpl( self, instring, loc, doActions=True ):\n        if (instring[loc] == self.firstMatchChar and\n            (self.matchLen==1 or instring.startswith(self.match,loc)) ):\n            return loc+self.matchLen, self.match\n        raise ParseException(instring, loc, self.errmsg, self)\n_L = Literal\nParserElement._literalStringClass = Literal\n\nclass Keyword(Token):\n    \"\"\"Token to exactly match a specified string as a keyword, that is,\n    it must be immediately followed by a non-keyword character.  Compare\n    with :class:`Literal`:\n\n     - ``Literal(\"if\")`` will match the leading ``'if'`` in\n       ``'ifAndOnlyIf'``.\n     - ``Keyword(\"if\")`` will not; it will only match the leading\n       ``'if'`` in ``'if x=1'``, or ``'if(y==2)'``\n\n    Accepts two optional constructor arguments in addition to the\n    keyword string:\n\n     - ``identChars`` is a string of characters that would be valid\n       identifier characters, defaulting to all alphanumerics + \"_\" and\n       \"$\"\n     - ``caseless`` allows case-insensitive matching, default is ``False``.\n\n    Example::\n\n        Keyword(\"start\").parseString(\"start\")  # -> ['start']\n        Keyword(\"start\").parseString(\"starting\")  # -> Exception\n\n    For case-insensitive matching, use :class:`CaselessKeyword`.\n    \"\"\"\n    DEFAULT_KEYWORD_CHARS = alphanums+\"_$\"\n\n    def __init__( self, matchString, identChars=None, caseless=False ):\n        super(Keyword,self).__init__()\n        if identChars is None:\n            identChars = Keyword.DEFAULT_KEYWORD_CHARS\n        self.match = matchString\n        self.matchLen = len(matchString)\n        try:\n            self.firstMatchChar = matchString[0]\n        except IndexError:\n            warnings.warn(\"null string passed to Keyword; use Empty() instead\",\n                            SyntaxWarning, stacklevel=2)\n        self.name = '\"%s\"' % self.match\n        self.errmsg = \"Expected \" + self.name\n        self.mayReturnEmpty = False\n        self.mayIndexError = False\n        self.caseless = caseless\n        if caseless:\n            self.caselessmatch = matchString.upper()\n            identChars = identChars.upper()\n        self.identChars = set(identChars)\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        if self.caseless:\n            if ( (instring[ loc:loc+self.matchLen ].upper() == self.caselessmatch) and\n                 (loc >= len(instring)-self.matchLen or instring[loc+self.matchLen].upper() not in self.identChars) and\n                 (loc == 0 or instring[loc-1].upper() not in self.identChars) ):\n                return loc+self.matchLen, self.match\n        else:\n            if (instring[loc] == self.firstMatchChar and\n                (self.matchLen==1 or instring.startswith(self.match,loc)) and\n                (loc >= len(instring)-self.matchLen or instring[loc+self.matchLen] not in self.identChars) and\n                (loc == 0 or instring[loc-1] not in self.identChars) ):\n                return loc+self.matchLen, self.match\n        raise ParseException(instring, loc, self.errmsg, self)\n\n    def copy(self):\n        c = super(Keyword,self).copy()\n        c.identChars = Keyword.DEFAULT_KEYWORD_CHARS\n        return c\n\n    @staticmethod\n    def setDefaultKeywordChars( chars ):\n        \"\"\"Overrides the default Keyword chars\n        \"\"\"\n        Keyword.DEFAULT_KEYWORD_CHARS = chars\n\nclass CaselessLiteral(Literal):\n    \"\"\"Token to match a specified string, ignoring case of letters.\n    Note: the matched results will always be in the case of the given\n    match string, NOT the case of the input text.\n\n    Example::\n\n        OneOrMore(CaselessLiteral(\"CMD\")).parseString(\"cmd CMD Cmd10\") # -> ['CMD', 'CMD', 'CMD']\n\n    (Contrast with example for :class:`CaselessKeyword`.)\n    \"\"\"\n    def __init__( self, matchString ):\n        super(CaselessLiteral,self).__init__( matchString.upper() )\n        # Preserve the defining literal.\n        self.returnString = matchString\n        self.name = \"'%s'\" % self.returnString\n        self.errmsg = \"Expected \" + self.name\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        if instring[ loc:loc+self.matchLen ].upper() == self.match:\n            return loc+self.matchLen, self.returnString\n        raise ParseException(instring, loc, self.errmsg, self)\n\nclass CaselessKeyword(Keyword):\n    \"\"\"\n    Caseless version of :class:`Keyword`.\n\n    Example::\n\n        OneOrMore(CaselessKeyword(\"CMD\")).parseString(\"cmd CMD Cmd10\") # -> ['CMD', 'CMD']\n\n    (Contrast with example for :class:`CaselessLiteral`.)\n    \"\"\"\n    def __init__( self, matchString, identChars=None ):\n        super(CaselessKeyword,self).__init__( matchString, identChars, caseless=True )\n\nclass CloseMatch(Token):\n    \"\"\"A variation on :class:`Literal` which matches \"close\" matches,\n    that is, strings with at most 'n' mismatching characters.\n    :class:`CloseMatch` takes parameters:\n\n     - ``match_string`` - string to be matched\n     - ``maxMismatches`` - (``default=1``) maximum number of\n       mismatches allowed to count as a match\n\n    The results from a successful parse will contain the matched text\n    from the input string and the following named results:\n\n     - ``mismatches`` - a list of the positions within the\n       match_string where mismatches were found\n     - ``original`` - the original match_string used to compare\n       against the input string\n\n    If ``mismatches`` is an empty list, then the match was an exact\n    match.\n\n    Example::\n\n        patt = CloseMatch(\"ATCATCGAATGGA\")\n        patt.parseString(\"ATCATCGAAXGGA\") # -> (['ATCATCGAAXGGA'], {'mismatches': [[9]], 'original': ['ATCATCGAATGGA']})\n        patt.parseString(\"ATCAXCGAAXGGA\") # -> Exception: Expected 'ATCATCGAATGGA' (with up to 1 mismatches) (at char 0), (line:1, col:1)\n\n        # exact match\n        patt.parseString(\"ATCATCGAATGGA\") # -> (['ATCATCGAATGGA'], {'mismatches': [[]], 'original': ['ATCATCGAATGGA']})\n\n        # close match allowing up to 2 mismatches\n        patt = CloseMatch(\"ATCATCGAATGGA\", maxMismatches=2)\n        patt.parseString(\"ATCAXCGAAXGGA\") # -> (['ATCAXCGAAXGGA'], {'mismatches': [[4, 9]], 'original': ['ATCATCGAATGGA']})\n    \"\"\"\n    def __init__(self, match_string, maxMismatches=1):\n        super(CloseMatch,self).__init__()\n        self.name = match_string\n        self.match_string = match_string\n        self.maxMismatches = maxMismatches\n        self.errmsg = \"Expected %r (with up to %d mismatches)\" % (self.match_string, self.maxMismatches)\n        self.mayIndexError = False\n        self.mayReturnEmpty = False\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        start = loc\n        instrlen = len(instring)\n        maxloc = start + len(self.match_string)\n\n        if maxloc <= instrlen:\n            match_string = self.match_string\n            match_stringloc = 0\n            mismatches = []\n            maxMismatches = self.maxMismatches\n\n            for match_stringloc,s_m in enumerate(zip(instring[loc:maxloc], self.match_string)):\n                src,mat = s_m\n                if src != mat:\n                    mismatches.append(match_stringloc)\n                    if len(mismatches) > maxMismatches:\n                        break\n            else:\n                loc = match_stringloc + 1\n                results = ParseResults([instring[start:loc]])\n                results['original'] = self.match_string\n                results['mismatches'] = mismatches\n                return loc, results\n\n        raise ParseException(instring, loc, self.errmsg, self)\n\n\nclass Word(Token):\n    \"\"\"Token for matching words composed of allowed character sets.\n    Defined with string containing all allowed initial characters, an\n    optional string containing allowed body characters (if omitted,\n    defaults to the initial character set), and an optional minimum,\n    maximum, and/or exact length.  The default value for ``min`` is\n    1 (a minimum value < 1 is not valid); the default values for\n    ``max`` and ``exact`` are 0, meaning no maximum or exact\n    length restriction. An optional ``excludeChars`` parameter can\n    list characters that might be found in the input ``bodyChars``\n    string; useful to define a word of all printables except for one or\n    two characters, for instance.\n\n    :class:`srange` is useful for defining custom character set strings\n    for defining ``Word`` expressions, using range notation from\n    regular expression character sets.\n\n    A common mistake is to use :class:`Word` to match a specific literal\n    string, as in ``Word(\"Address\")``. Remember that :class:`Word`\n    uses the string argument to define *sets* of matchable characters.\n    This expression would match \"Add\", \"AAA\", \"dAred\", or any other word\n    made up of the characters 'A', 'd', 'r', 'e', and 's'. To match an\n    exact literal string, use :class:`Literal` or :class:`Keyword`.\n\n    pyparsing includes helper strings for building Words:\n\n     - :class:`alphas`\n     - :class:`nums`\n     - :class:`alphanums`\n     - :class:`hexnums`\n     - :class:`alphas8bit` (alphabetic characters in ASCII range 128-255\n       - accented, tilded, umlauted, etc.)\n     - :class:`punc8bit` (non-alphabetic characters in ASCII range\n       128-255 - currency, symbols, superscripts, diacriticals, etc.)\n     - :class:`printables` (any non-whitespace character)\n\n    Example::\n\n        # a word composed of digits\n        integer = Word(nums) # equivalent to Word(\"0123456789\") or Word(srange(\"0-9\"))\n\n        # a word with a leading capital, and zero or more lowercase\n        capital_word = Word(alphas.upper(), alphas.lower())\n\n        # hostnames are alphanumeric, with leading alpha, and '-'\n        hostname = Word(alphas, alphanums+'-')\n\n        # roman numeral (not a strict parser, accepts invalid mix of characters)\n        roman = Word(\"IVXLCDM\")\n\n        # any string of non-whitespace characters, except for ','\n        csv_value = Word(printables, excludeChars=\",\")\n    \"\"\"\n    def __init__( self, initChars, bodyChars=None, min=1, max=0, exact=0, asKeyword=False, excludeChars=None ):\n        super(Word,self).__init__()\n        if excludeChars:\n            initChars = ''.join(c for c in initChars if c not in excludeChars)\n            if bodyChars:\n                bodyChars = ''.join(c for c in bodyChars if c not in excludeChars)\n        self.initCharsOrig = initChars\n        self.initChars = set(initChars)\n        if bodyChars :\n            self.bodyCharsOrig = bodyChars\n            self.bodyChars = set(bodyChars)\n        else:\n            self.bodyCharsOrig = initChars\n            self.bodyChars = set(initChars)\n\n        self.maxSpecified = max > 0\n\n        if min < 1:\n            raise ValueError(\"cannot specify a minimum length < 1; use Optional(Word()) if zero-length word is permitted\")\n\n        self.minLen = min\n\n        if max > 0:\n            self.maxLen = max\n        else:\n            self.maxLen = _MAX_INT\n\n        if exact > 0:\n            self.maxLen = exact\n            self.minLen = exact\n\n        self.name = _ustr(self)\n        self.errmsg = \"Expected \" + self.name\n        self.mayIndexError = False\n        self.asKeyword = asKeyword\n\n        if ' ' not in self.initCharsOrig+self.bodyCharsOrig and (min==1 and max==0 and exact==0):\n            if self.bodyCharsOrig == self.initCharsOrig:\n                self.reString = \"[%s]+\" % _escapeRegexRangeChars(self.initCharsOrig)\n            elif len(self.initCharsOrig) == 1:\n                self.reString = \"%s[%s]*\" % \\\n                                      (re.escape(self.initCharsOrig),\n                                      _escapeRegexRangeChars(self.bodyCharsOrig),)\n            else:\n                self.reString = \"[%s][%s]*\" % \\\n                                      (_escapeRegexRangeChars(self.initCharsOrig),\n                                      _escapeRegexRangeChars(self.bodyCharsOrig),)\n            if self.asKeyword:\n                self.reString = r\"\\b\"+self.reString+r\"\\b\"\n            try:\n                self.re = re.compile( self.reString )\n            except Exception:\n                self.re = None\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        if self.re:\n            result = self.re.match(instring,loc)\n            if not result:\n                raise ParseException(instring, loc, self.errmsg, self)\n\n            loc = result.end()\n            return loc, result.group()\n\n        if not(instring[ loc ] in self.initChars):\n            raise ParseException(instring, loc, self.errmsg, self)\n\n        start = loc\n        loc += 1\n        instrlen = len(instring)\n        bodychars = self.bodyChars\n        maxloc = start + self.maxLen\n        maxloc = min( maxloc, instrlen )\n        while loc < maxloc and instring[loc] in bodychars:\n            loc += 1\n\n        throwException = False\n        if loc - start < self.minLen:\n            throwException = True\n        if self.maxSpecified and loc < instrlen and instring[loc] in bodychars:\n            throwException = True\n        if self.asKeyword:\n            if (start>0 and instring[start-1] in bodychars) or (loc<instrlen and instring[loc] in bodychars):\n                throwException = True\n\n        if throwException:\n            raise ParseException(instring, loc, self.errmsg, self)\n\n        return loc, instring[start:loc]\n\n    def __str__( self ):\n        try:\n            return super(Word,self).__str__()\n        except Exception:\n            pass\n\n\n        if self.strRepr is None:\n\n            def charsAsStr(s):\n                if len(s)>4:\n                    return s[:4]+\"...\"\n                else:\n                    return s\n\n            if ( self.initCharsOrig != self.bodyCharsOrig ):\n                self.strRepr = \"W:(%s,%s)\" % ( charsAsStr(self.initCharsOrig), charsAsStr(self.bodyCharsOrig) )\n            else:\n                self.strRepr = \"W:(%s)\" % charsAsStr(self.initCharsOrig)\n\n        return self.strRepr\n\n\nclass Char(Word):\n    \"\"\"A short-cut class for defining ``Word(characters, exact=1)``,\n    when defining a match of any single character in a string of\n    characters.\n    \"\"\"\n    def __init__(self, charset):\n        super(Char, self).__init__(charset, exact=1)\n        self.reString = \"[%s]\" % _escapeRegexRangeChars(self.initCharsOrig)\n        self.re = re.compile( self.reString )\n\n\nclass Regex(Token):\n    r\"\"\"Token for matching strings that match a given regular\n    expression. Defined with string specifying the regular expression in\n    a form recognized by the stdlib Python  `re module <https://docs.python.org/3/library/re.html>`_.\n    If the given regex contains named groups (defined using ``(?P<name>...)``),\n    these will be preserved as named parse results.\n\n    Example::\n\n        realnum = Regex(r\"[+-]?\\d+\\.\\d*\")\n        date = Regex(r'(?P<year>\\d{4})-(?P<month>\\d\\d?)-(?P<day>\\d\\d?)')\n        # ref: https://stackoverflow.com/questions/267399/how-do-you-match-only-valid-roman-numerals-with-a-regular-expression\n        roman = Regex(r\"M{0,4}(CM|CD|D?{0,3})(XC|XL|L?X{0,3})(IX|IV|V?I{0,3})\")\n    \"\"\"\n    compiledREtype = type(re.compile(\"[A-Z]\"))\n    def __init__( self, pattern, flags=0, asGroupList=False, asMatch=False):\n        \"\"\"The parameters ``pattern`` and ``flags`` are passed\n        to the ``re.compile()`` function as-is. See the Python\n        `re module <https://docs.python.org/3/library/re.html>`_ module for an\n        explanation of the acceptable patterns and flags.\n        \"\"\"\n        super(Regex,self).__init__()\n\n        if isinstance(pattern, basestring):\n            if not pattern:\n                warnings.warn(\"null string passed to Regex; use Empty() instead\",\n                        SyntaxWarning, stacklevel=2)\n\n            self.pattern = pattern\n            self.flags = flags\n\n            try:\n                self.re = re.compile(self.pattern, self.flags)\n                self.reString = self.pattern\n            except sre_constants.error:\n                warnings.warn(\"invalid pattern (%s) passed to Regex\" % pattern,\n                    SyntaxWarning, stacklevel=2)\n                raise\n\n        elif isinstance(pattern, Regex.compiledREtype):\n            self.re = pattern\n            self.pattern = \\\n            self.reString = str(pattern)\n            self.flags = flags\n\n        else:\n            raise ValueError(\"Regex may only be constructed with a string or a compiled RE object\")\n\n        self.name = _ustr(self)\n        self.errmsg = \"Expected \" + self.name\n        self.mayIndexError = False\n        self.mayReturnEmpty = True\n        self.asGroupList = asGroupList\n        self.asMatch = asMatch\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        result = self.re.match(instring,loc)\n        if not result:\n            raise ParseException(instring, loc, self.errmsg, self)\n\n        loc = result.end()\n        if self.asMatch:\n            ret = result\n        elif self.asGroupList:\n            ret = result.groups()\n        else:\n            ret = ParseResults(result.group())\n            d = result.groupdict()\n            if d:\n                for k, v in d.items():\n                    ret[k] = v\n        return loc,ret\n\n    def __str__( self ):\n        try:\n            return super(Regex,self).__str__()\n        except Exception:\n            pass\n\n        if self.strRepr is None:\n            self.strRepr = \"Re:(%s)\" % repr(self.pattern)\n\n        return self.strRepr\n\n    def sub(self, repl):\n        \"\"\"\n        Return Regex with an attached parse action to transform the parsed\n        result as if called using `re.sub(expr, repl, string) <https://docs.python.org/3/library/re.html#re.sub>`_.\n\n        Example::\n\n            make_html = Regex(r\"(\\w+):(.*?):\").sub(r\"<\\1>\\2</\\1>\")\n            print(make_html.transformString(\"h1:main title:\"))\n            # prints \"<h1>main title</h1>\"\n        \"\"\"\n        if self.asGroupList:\n            warnings.warn(\"cannot use sub() with Regex(asGroupList=True)\",\n                           SyntaxWarning, stacklevel=2)\n            raise SyntaxError()\n\n        if self.asMatch and callable(repl):\n            warnings.warn(\"cannot use sub() with a callable with Regex(asMatch=True)\",\n                           SyntaxWarning, stacklevel=2)\n            raise SyntaxError()\n\n        if self.asMatch:\n            def pa(tokens):\n                return tokens[0].expand(repl)\n        else:\n            def pa(tokens):\n                return self.re.sub(repl, tokens[0])\n        return self.addParseAction(pa)\n\nclass QuotedString(Token):\n    r\"\"\"\n    Token for matching strings that are delimited by quoting characters.\n\n    Defined with the following parameters:\n\n        - quoteChar - string of one or more characters defining the\n          quote delimiting string\n        - escChar - character to escape quotes, typically backslash\n          (default= ``None`` )\n        - escQuote - special quote sequence to escape an embedded quote\n          string (such as SQL's ``\"\"`` to escape an embedded ``\"``)\n          (default= ``None`` )\n        - multiline - boolean indicating whether quotes can span\n          multiple lines (default= ``False`` )\n        - unquoteResults - boolean indicating whether the matched text\n          should be unquoted (default= ``True`` )\n        - endQuoteChar - string of one or more characters defining the\n          end of the quote delimited string (default= ``None``  => same as\n          quoteChar)\n        - convertWhitespaceEscapes - convert escaped whitespace\n          (``'\\t'``, ``'\\n'``, etc.) to actual whitespace\n          (default= ``True`` )\n\n    Example::\n\n        qs = QuotedString('\"')\n        print(qs.searchString('lsjdf \"This is the quote\" sldjf'))\n        complex_qs = QuotedString('{{', endQuoteChar='}}')\n        print(complex_qs.searchString('lsjdf {{This is the \"quote\"}} sldjf'))\n        sql_qs = QuotedString('\"', escQuote='\"\"')\n        print(sql_qs.searchString('lsjdf \"This is the quote with \"\"embedded\"\" quotes\" sldjf'))\n\n    prints::\n\n        [['This is the quote']]\n        [['This is the \"quote\"']]\n        [['This is the quote with \"embedded\" quotes']]\n    \"\"\"\n    def __init__( self, quoteChar, escChar=None, escQuote=None, multiline=False, unquoteResults=True, endQuoteChar=None, convertWhitespaceEscapes=True):\n        super(QuotedString,self).__init__()\n\n        # remove white space from quote chars - wont work anyway\n        quoteChar = quoteChar.strip()\n        if not quoteChar:\n            warnings.warn(\"quoteChar cannot be the empty string\",SyntaxWarning,stacklevel=2)\n            raise SyntaxError()\n\n        if endQuoteChar is None:\n            endQuoteChar = quoteChar\n        else:\n            endQuoteChar = endQuoteChar.strip()\n            if not endQuoteChar:\n                warnings.warn(\"endQuoteChar cannot be the empty string\",SyntaxWarning,stacklevel=2)\n                raise SyntaxError()\n\n        self.quoteChar = quoteChar\n        self.quoteCharLen = len(quoteChar)\n        self.firstQuoteChar = quoteChar[0]\n        self.endQuoteChar = endQuoteChar\n        self.endQuoteCharLen = len(endQuoteChar)\n        self.escChar = escChar\n        self.escQuote = escQuote\n        self.unquoteResults = unquoteResults\n        self.convertWhitespaceEscapes = convertWhitespaceEscapes\n\n        if multiline:\n            self.flags = re.MULTILINE | re.DOTALL\n            self.pattern = r'%s(?:[^%s%s]' % \\\n                ( re.escape(self.quoteChar),\n                  _escapeRegexRangeChars(self.endQuoteChar[0]),\n                  (escChar is not None and _escapeRegexRangeChars(escChar) or '') )\n        else:\n            self.flags = 0\n            self.pattern = r'%s(?:[^%s\\n\\r%s]' % \\\n                ( re.escape(self.quoteChar),\n                  _escapeRegexRangeChars(self.endQuoteChar[0]),\n                  (escChar is not None and _escapeRegexRangeChars(escChar) or '') )\n        if len(self.endQuoteChar) > 1:\n            self.pattern += (\n                '|(?:' + ')|(?:'.join(\"%s[^%s]\" % (re.escape(self.endQuoteChar[:i]),\n                                               _escapeRegexRangeChars(self.endQuoteChar[i]))\n                                    for i in range(len(self.endQuoteChar)-1,0,-1)) + ')'\n                )\n        if escQuote:\n            self.pattern += (r'|(?:%s)' % re.escape(escQuote))\n        if escChar:\n            self.pattern += (r'|(?:%s.)' % re.escape(escChar))\n            self.escCharReplacePattern = re.escape(self.escChar)+\"(.)\"\n        self.pattern += (r')*%s' % re.escape(self.endQuoteChar))\n\n        try:\n            self.re = re.compile(self.pattern, self.flags)\n            self.reString = self.pattern\n        except sre_constants.error:\n            warnings.warn(\"invalid pattern (%s) passed to Regex\" % self.pattern,\n                SyntaxWarning, stacklevel=2)\n            raise\n\n        self.name = _ustr(self)\n        self.errmsg = \"Expected \" + self.name\n        self.mayIndexError = False\n        self.mayReturnEmpty = True\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        result = instring[loc] == self.firstQuoteChar and self.re.match(instring,loc) or None\n        if not result:\n            raise ParseException(instring, loc, self.errmsg, self)\n\n        loc = result.end()\n        ret = result.group()\n\n        if self.unquoteResults:\n\n            # strip off quotes\n            ret = ret[self.quoteCharLen:-self.endQuoteCharLen]\n\n            if isinstance(ret,basestring):\n                # replace escaped whitespace\n                if '\\\\' in ret and self.convertWhitespaceEscapes:\n                    ws_map = {\n                        r'\\t' : '\\t',\n                        r'\\n' : '\\n',\n                        r'\\f' : '\\f',\n                        r'\\r' : '\\r',\n                    }\n                    for wslit,wschar in ws_map.items():\n                        ret = ret.replace(wslit, wschar)\n\n                # replace escaped characters\n                if self.escChar:\n                    ret = re.sub(self.escCharReplacePattern, r\"\\g<1>\", ret)\n\n                # replace escaped quotes\n                if self.escQuote:\n                    ret = ret.replace(self.escQuote, self.endQuoteChar)\n\n        return loc, ret\n\n    def __str__( self ):\n        try:\n            return super(QuotedString,self).__str__()\n        except Exception:\n            pass\n\n        if self.strRepr is None:\n            self.strRepr = \"quoted string, starting with %s ending with %s\" % (self.quoteChar, self.endQuoteChar)\n\n        return self.strRepr\n\n\nclass CharsNotIn(Token):\n    \"\"\"Token for matching words composed of characters *not* in a given\n    set (will include whitespace in matched characters if not listed in\n    the provided exclusion set - see example). Defined with string\n    containing all disallowed characters, and an optional minimum,\n    maximum, and/or exact length.  The default value for ``min`` is\n    1 (a minimum value < 1 is not valid); the default values for\n    ``max`` and ``exact`` are 0, meaning no maximum or exact\n    length restriction.\n\n    Example::\n\n        # define a comma-separated-value as anything that is not a ','\n        csv_value = CharsNotIn(',')\n        print(delimitedList(csv_value).parseString(\"dkls,lsdkjf,s12 34,@!#,213\"))\n\n    prints::\n\n        ['dkls', 'lsdkjf', 's12 34', '@!#', '213']\n    \"\"\"\n    def __init__( self, notChars, min=1, max=0, exact=0 ):\n        super(CharsNotIn,self).__init__()\n        self.skipWhitespace = False\n        self.notChars = notChars\n\n        if min < 1:\n            raise ValueError(\n                \"cannot specify a minimum length < 1; use \" +\n                \"Optional(CharsNotIn()) if zero-length char group is permitted\")\n\n        self.minLen = min\n\n        if max > 0:\n            self.maxLen = max\n        else:\n            self.maxLen = _MAX_INT\n\n        if exact > 0:\n            self.maxLen = exact\n            self.minLen = exact\n\n        self.name = _ustr(self)\n        self.errmsg = \"Expected \" + self.name\n        self.mayReturnEmpty = ( self.minLen == 0 )\n        self.mayIndexError = False\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        if instring[loc] in self.notChars:\n            raise ParseException(instring, loc, self.errmsg, self)\n\n        start = loc\n        loc += 1\n        notchars = self.notChars\n        maxlen = min( start+self.maxLen, len(instring) )\n        while loc < maxlen and \\\n              (instring[loc] not in notchars):\n            loc += 1\n\n        if loc - start < self.minLen:\n            raise ParseException(instring, loc, self.errmsg, self)\n\n        return loc, instring[start:loc]\n\n    def __str__( self ):\n        try:\n            return super(CharsNotIn, self).__str__()\n        except Exception:\n            pass\n\n        if self.strRepr is None:\n            if len(self.notChars) > 4:\n                self.strRepr = \"!W:(%s...)\" % self.notChars[:4]\n            else:\n                self.strRepr = \"!W:(%s)\" % self.notChars\n\n        return self.strRepr\n\nclass White(Token):\n    \"\"\"Special matching class for matching whitespace.  Normally,\n    whitespace is ignored by pyparsing grammars.  This class is included\n    when some whitespace structures are significant.  Define with\n    a string containing the whitespace characters to be matched; default\n    is ``\" \\\\t\\\\r\\\\n\"``.  Also takes optional ``min``,\n    ``max``, and ``exact`` arguments, as defined for the\n    :class:`Word` class.\n    \"\"\"\n    whiteStrs = {\n        ' ' : '<SP>',\n        '\\t': '<TAB>',\n        '\\n': '<LF>',\n        '\\r': '<CR>',\n        '\\f': '<FF>',\n        'u\\00A0': '<NBSP>',\n        'u\\1680': '<OGHAM_SPACE_MARK>',\n        'u\\180E': '<MONGOLIAN_VOWEL_SEPARATOR>',\n        'u\\2000': '<EN_QUAD>',\n        'u\\2001': '<EM_QUAD>',\n        'u\\2002': '<EN_SPACE>',\n        'u\\2003': '<EM_SPACE>',\n        'u\\2004': '<THREE-PER-EM_SPACE>',\n        'u\\2005': '<FOUR-PER-EM_SPACE>',\n        'u\\2006': '<SIX-PER-EM_SPACE>',\n        'u\\2007': '<FIGURE_SPACE>',\n        'u\\2008': '<PUNCTUATION_SPACE>',\n        'u\\2009': '<THIN_SPACE>',\n        'u\\200A': '<HAIR_SPACE>',\n        'u\\200B': '<ZERO_WIDTH_SPACE>',\n        'u\\202F': '<NNBSP>',\n        'u\\205F': '<MMSP>',\n        'u\\3000': '<IDEOGRAPHIC_SPACE>',\n        }\n    def __init__(self, ws=\" \\t\\r\\n\", min=1, max=0, exact=0):\n        super(White,self).__init__()\n        self.matchWhite = ws\n        self.setWhitespaceChars( \"\".join(c for c in self.whiteChars if c not in self.matchWhite) )\n        #~ self.leaveWhitespace()\n        self.name = (\"\".join(White.whiteStrs[c] for c in self.matchWhite))\n        self.mayReturnEmpty = True\n        self.errmsg = \"Expected \" + self.name\n\n        self.minLen = min\n\n        if max > 0:\n            self.maxLen = max\n        else:\n            self.maxLen = _MAX_INT\n\n        if exact > 0:\n            self.maxLen = exact\n            self.minLen = exact\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        if not(instring[ loc ] in self.matchWhite):\n            raise ParseException(instring, loc, self.errmsg, self)\n        start = loc\n        loc += 1\n        maxloc = start + self.maxLen\n        maxloc = min( maxloc, len(instring) )\n        while loc < maxloc and instring[loc] in self.matchWhite:\n            loc += 1\n\n        if loc - start < self.minLen:\n            raise ParseException(instring, loc, self.errmsg, self)\n\n        return loc, instring[start:loc]\n\n\nclass _PositionToken(Token):\n    def __init__( self ):\n        super(_PositionToken,self).__init__()\n        self.name=self.__class__.__name__\n        self.mayReturnEmpty = True\n        self.mayIndexError = False\n\nclass GoToColumn(_PositionToken):\n    \"\"\"Token to advance to a specific column of input text; useful for\n    tabular report scraping.\n    \"\"\"\n    def __init__( self, colno ):\n        super(GoToColumn,self).__init__()\n        self.col = colno\n\n    def preParse( self, instring, loc ):\n        if col(loc,instring) != self.col:\n            instrlen = len(instring)\n            if self.ignoreExprs:\n                loc = self._skipIgnorables( instring, loc )\n            while loc < instrlen and instring[loc].isspace() and col( loc, instring ) != self.col :\n                loc += 1\n        return loc\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        thiscol = col( loc, instring )\n        if thiscol > self.col:\n            raise ParseException( instring, loc, \"Text not in expected column\", self )\n        newloc = loc + self.col - thiscol\n        ret = instring[ loc: newloc ]\n        return newloc, ret\n\n\nclass LineStart(_PositionToken):\n    \"\"\"Matches if current position is at the beginning of a line within\n    the parse string\n\n    Example::\n\n        test = '''\\\n        AAA this line\n        AAA and this line\n          AAA but not this one\n        B AAA and definitely not this one\n        '''\n\n        for t in (LineStart() + 'AAA' + restOfLine).searchString(test):\n            print(t)\n\n    prints::\n\n        ['AAA', ' this line']\n        ['AAA', ' and this line']\n\n    \"\"\"\n    def __init__( self ):\n        super(LineStart,self).__init__()\n        self.errmsg = \"Expected start of line\"\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        if col(loc, instring) == 1:\n            return loc, []\n        raise ParseException(instring, loc, self.errmsg, self)\n\nclass LineEnd(_PositionToken):\n    \"\"\"Matches if current position is at the end of a line within the\n    parse string\n    \"\"\"\n    def __init__( self ):\n        super(LineEnd,self).__init__()\n        self.setWhitespaceChars( ParserElement.DEFAULT_WHITE_CHARS.replace(\"\\n\",\"\") )\n        self.errmsg = \"Expected end of line\"\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        if loc<len(instring):\n            if instring[loc] == \"\\n\":\n                return loc+1, \"\\n\"\n            else:\n                raise ParseException(instring, loc, self.errmsg, self)\n        elif loc == len(instring):\n            return loc+1, []\n        else:\n            raise ParseException(instring, loc, self.errmsg, self)\n\nclass StringStart(_PositionToken):\n    \"\"\"Matches if current position is at the beginning of the parse\n    string\n    \"\"\"\n    def __init__( self ):\n        super(StringStart,self).__init__()\n        self.errmsg = \"Expected start of text\"\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        if loc != 0:\n            # see if entire string up to here is just whitespace and ignoreables\n            if loc != self.preParse( instring, 0 ):\n                raise ParseException(instring, loc, self.errmsg, self)\n        return loc, []\n\nclass StringEnd(_PositionToken):\n    \"\"\"Matches if current position is at the end of the parse string\n    \"\"\"\n    def __init__( self ):\n        super(StringEnd,self).__init__()\n        self.errmsg = \"Expected end of text\"\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        if loc < len(instring):\n            raise ParseException(instring, loc, self.errmsg, self)\n        elif loc == len(instring):\n            return loc+1, []\n        elif loc > len(instring):\n            return loc, []\n        else:\n            raise ParseException(instring, loc, self.errmsg, self)\n\nclass WordStart(_PositionToken):\n    \"\"\"Matches if the current position is at the beginning of a Word,\n    and is not preceded by any character in a given set of\n    ``wordChars`` (default= ``printables``). To emulate the\n    ``\\b`` behavior of regular expressions, use\n    ``WordStart(alphanums)``. ``WordStart`` will also match at\n    the beginning of the string being parsed, or at the beginning of\n    a line.\n    \"\"\"\n    def __init__(self, wordChars = printables):\n        super(WordStart,self).__init__()\n        self.wordChars = set(wordChars)\n        self.errmsg = \"Not at the start of a word\"\n\n    def parseImpl(self, instring, loc, doActions=True ):\n        if loc != 0:\n            if (instring[loc-1] in self.wordChars or\n                instring[loc] not in self.wordChars):\n                raise ParseException(instring, loc, self.errmsg, self)\n        return loc, []\n\nclass WordEnd(_PositionToken):\n    \"\"\"Matches if the current position is at the end of a Word, and is\n    not followed by any character in a given set of ``wordChars``\n    (default= ``printables``). To emulate the ``\\b`` behavior of\n    regular expressions, use ``WordEnd(alphanums)``. ``WordEnd``\n    will also match at the end of the string being parsed, or at the end\n    of a line.\n    \"\"\"\n    def __init__(self, wordChars = printables):\n        super(WordEnd,self).__init__()\n        self.wordChars = set(wordChars)\n        self.skipWhitespace = False\n        self.errmsg = \"Not at the end of a word\"\n\n    def parseImpl(self, instring, loc, doActions=True ):\n        instrlen = len(instring)\n        if instrlen>0 and loc<instrlen:\n            if (instring[loc] in self.wordChars or\n                instring[loc-1] not in self.wordChars):\n                raise ParseException(instring, loc, self.errmsg, self)\n        return loc, []\n\n\nclass ParseExpression(ParserElement):\n    \"\"\"Abstract subclass of ParserElement, for combining and\n    post-processing parsed tokens.\n    \"\"\"\n    def __init__( self, exprs, savelist = False ):\n        super(ParseExpression,self).__init__(savelist)\n        if isinstance( exprs, _generatorType ):\n            exprs = list(exprs)\n\n        if isinstance( exprs, basestring ):\n            self.exprs = [ ParserElement._literalStringClass( exprs ) ]\n        elif isinstance( exprs, Iterable ):\n            exprs = list(exprs)\n            # if sequence of strings provided, wrap with Literal\n            if all(isinstance(expr, basestring) for expr in exprs):\n                exprs = map(ParserElement._literalStringClass, exprs)\n            self.exprs = list(exprs)\n        else:\n            try:\n                self.exprs = list( exprs )\n            except TypeError:\n                self.exprs = [ exprs ]\n        self.callPreparse = False\n\n    def __getitem__( self, i ):\n        return self.exprs[i]\n\n    def append( self, other ):\n        self.exprs.append( other )\n        self.strRepr = None\n        return self\n\n    def leaveWhitespace( self ):\n        \"\"\"Extends ``leaveWhitespace`` defined in base class, and also invokes ``leaveWhitespace`` on\n           all contained expressions.\"\"\"\n        self.skipWhitespace = False\n        self.exprs = [ e.copy() for e in self.exprs ]\n        for e in self.exprs:\n            e.leaveWhitespace()\n        return self\n\n    def ignore( self, other ):\n        if isinstance( other, Suppress ):\n            if other not in self.ignoreExprs:\n                super( ParseExpression, self).ignore( other )\n                for e in self.exprs:\n                    e.ignore( self.ignoreExprs[-1] )\n        else:\n            super( ParseExpression, self).ignore( other )\n            for e in self.exprs:\n                e.ignore( self.ignoreExprs[-1] )\n        return self\n\n    def __str__( self ):\n        try:\n            return super(ParseExpression,self).__str__()\n        except Exception:\n            pass\n\n        if self.strRepr is None:\n            self.strRepr = \"%s:(%s)\" % ( self.__class__.__name__, _ustr(self.exprs) )\n        return self.strRepr\n\n    def streamline( self ):\n        super(ParseExpression,self).streamline()\n\n        for e in self.exprs:\n            e.streamline()\n\n        # collapse nested And's of the form And( And( And( a,b), c), d) to And( a,b,c,d )\n        # but only if there are no parse actions or resultsNames on the nested And's\n        # (likewise for Or's and MatchFirst's)\n        if ( len(self.exprs) == 2 ):\n            other = self.exprs[0]\n            if ( isinstance( other, self.__class__ ) and\n                  not(other.parseAction) and\n                  other.resultsName is None and\n                  not other.debug ):\n                self.exprs = other.exprs[:] + [ self.exprs[1] ]\n                self.strRepr = None\n                self.mayReturnEmpty |= other.mayReturnEmpty\n                self.mayIndexError  |= other.mayIndexError\n\n            other = self.exprs[-1]\n            if ( isinstance( other, self.__class__ ) and\n                  not(other.parseAction) and\n                  other.resultsName is None and\n                  not other.debug ):\n                self.exprs = self.exprs[:-1] + other.exprs[:]\n                self.strRepr = None\n                self.mayReturnEmpty |= other.mayReturnEmpty\n                self.mayIndexError  |= other.mayIndexError\n\n        self.errmsg = \"Expected \" + _ustr(self)\n\n        return self\n\n    def setResultsName( self, name, listAllMatches=False ):\n        ret = super(ParseExpression,self).setResultsName(name,listAllMatches)\n        return ret\n\n    def validate( self, validateTrace=[] ):\n        tmp = validateTrace[:]+[self]\n        for e in self.exprs:\n            e.validate(tmp)\n        self.checkRecursion( [] )\n\n    def copy(self):\n        ret = super(ParseExpression,self).copy()\n        ret.exprs = [e.copy() for e in self.exprs]\n        return ret\n\nclass And(ParseExpression):\n    \"\"\"\n    Requires all given :class:`ParseExpression` s to be found in the given order.\n    Expressions may be separated by whitespace.\n    May be constructed using the ``'+'`` operator.\n    May also be constructed using the ``'-'`` operator, which will\n    suppress backtracking.\n\n    Example::\n\n        integer = Word(nums)\n        name_expr = OneOrMore(Word(alphas))\n\n        expr = And([integer(\"id\"),name_expr(\"name\"),integer(\"age\")])\n        # more easily written as:\n        expr = integer(\"id\") + name_expr(\"name\") + integer(\"age\")\n    \"\"\"\n\n    class _ErrorStop(Empty):\n        def __init__(self, *args, **kwargs):\n            super(And._ErrorStop,self).__init__(*args, **kwargs)\n            self.name = '-'\n            self.leaveWhitespace()\n\n    def __init__( self, exprs, savelist = True ):\n        super(And,self).__init__(exprs, savelist)\n        self.mayReturnEmpty = all(e.mayReturnEmpty for e in self.exprs)\n        self.setWhitespaceChars( self.exprs[0].whiteChars )\n        self.skipWhitespace = self.exprs[0].skipWhitespace\n        self.callPreparse = True\n\n    def streamline(self):\n        super(And, self).streamline()\n        self.mayReturnEmpty = all(e.mayReturnEmpty for e in self.exprs)\n        return self\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        # pass False as last arg to _parse for first element, since we already\n        # pre-parsed the string as part of our And pre-parsing\n        loc, resultlist = self.exprs[0]._parse( instring, loc, doActions, callPreParse=False )\n        errorStop = False\n        for e in self.exprs[1:]:\n            if isinstance(e, And._ErrorStop):\n                errorStop = True\n                continue\n            if errorStop:\n                try:\n                    loc, exprtokens = e._parse( instring, loc, doActions )\n                except ParseSyntaxException:\n                    raise\n                except ParseBaseException as pe:\n                    pe.__traceback__ = None\n                    raise ParseSyntaxException._from_exception(pe)\n                except IndexError:\n                    raise ParseSyntaxException(instring, len(instring), self.errmsg, self)\n            else:\n                loc, exprtokens = e._parse( instring, loc, doActions )\n            if exprtokens or exprtokens.haskeys():\n                resultlist += exprtokens\n        return loc, resultlist\n\n    def __iadd__(self, other ):\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        return self.append( other ) #And( [ self, other ] )\n\n    def checkRecursion( self, parseElementList ):\n        subRecCheckList = parseElementList[:] + [ self ]\n        for e in self.exprs:\n            e.checkRecursion( subRecCheckList )\n            if not e.mayReturnEmpty:\n                break\n\n    def __str__( self ):\n        if hasattr(self,\"name\"):\n            return self.name\n\n        if self.strRepr is None:\n            self.strRepr = \"{\" + \" \".join(_ustr(e) for e in self.exprs) + \"}\"\n\n        return self.strRepr\n\n\nclass Or(ParseExpression):\n    \"\"\"Requires that at least one :class:`ParseExpression` is found. If\n    two expressions match, the expression that matches the longest\n    string will be used. May be constructed using the ``'^'``\n    operator.\n\n    Example::\n\n        # construct Or using '^' operator\n\n        number = Word(nums) ^ Combine(Word(nums) + '.' + Word(nums))\n        print(number.searchString(\"123 3.1416 789\"))\n\n    prints::\n\n        [['123'], ['3.1416'], ['789']]\n    \"\"\"\n    def __init__( self, exprs, savelist = False ):\n        super(Or,self).__init__(exprs, savelist)\n        if self.exprs:\n            self.mayReturnEmpty = any(e.mayReturnEmpty for e in self.exprs)\n        else:\n            self.mayReturnEmpty = True\n\n    def streamline(self):\n        super(Or, self).streamline()\n        self.saveAsList = any(e.saveAsList for e in self.exprs)\n        return self\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        maxExcLoc = -1\n        maxException = None\n        matches = []\n        for e in self.exprs:\n            try:\n                loc2 = e.tryParse( instring, loc )\n            except ParseException as err:\n                err.__traceback__ = None\n                if err.loc > maxExcLoc:\n                    maxException = err\n                    maxExcLoc = err.loc\n            except IndexError:\n                if len(instring) > maxExcLoc:\n                    maxException = ParseException(instring,len(instring),e.errmsg,self)\n                    maxExcLoc = len(instring)\n            else:\n                # save match among all matches, to retry longest to shortest\n                matches.append((loc2, e))\n\n        if matches:\n            matches.sort(key=lambda x: -x[0])\n            for _,e in matches:\n                try:\n                    return e._parse( instring, loc, doActions )\n                except ParseException as err:\n                    err.__traceback__ = None\n                    if err.loc > maxExcLoc:\n                        maxException = err\n                        maxExcLoc = err.loc\n\n        if maxException is not None:\n            maxException.msg = self.errmsg\n            raise maxException\n        else:\n            raise ParseException(instring, loc, \"no defined alternatives to match\", self)\n\n\n    def __ixor__(self, other ):\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        return self.append( other ) #Or( [ self, other ] )\n\n    def __str__( self ):\n        if hasattr(self,\"name\"):\n            return self.name\n\n        if self.strRepr is None:\n            self.strRepr = \"{\" + \" ^ \".join(_ustr(e) for e in self.exprs) + \"}\"\n\n        return self.strRepr\n\n    def checkRecursion( self, parseElementList ):\n        subRecCheckList = parseElementList[:] + [ self ]\n        for e in self.exprs:\n            e.checkRecursion( subRecCheckList )\n\n\nclass MatchFirst(ParseExpression):\n    \"\"\"Requires that at least one :class:`ParseExpression` is found. If\n    two expressions match, the first one listed is the one that will\n    match. May be constructed using the ``'|'`` operator.\n\n    Example::\n\n        # construct MatchFirst using '|' operator\n\n        # watch the order of expressions to match\n        number = Word(nums) | Combine(Word(nums) + '.' + Word(nums))\n        print(number.searchString(\"123 3.1416 789\")) #  Fail! -> [['123'], ['3'], ['1416'], ['789']]\n\n        # put more selective expression first\n        number = Combine(Word(nums) + '.' + Word(nums)) | Word(nums)\n        print(number.searchString(\"123 3.1416 789\")) #  Better -> [['123'], ['3.1416'], ['789']]\n    \"\"\"\n    def __init__( self, exprs, savelist = False ):\n        super(MatchFirst,self).__init__(exprs, savelist)\n        if self.exprs:\n            self.mayReturnEmpty = any(e.mayReturnEmpty for e in self.exprs)\n            # self.saveAsList = any(e.saveAsList for e in self.exprs)\n        else:\n            self.mayReturnEmpty = True\n\n    def streamline(self):\n        super(MatchFirst, self).streamline()\n        self.saveAsList = any(e.saveAsList for e in self.exprs)\n        return self\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        maxExcLoc = -1\n        maxException = None\n        for e in self.exprs:\n            try:\n                ret = e._parse( instring, loc, doActions )\n                return ret\n            except ParseException as err:\n                if err.loc > maxExcLoc:\n                    maxException = err\n                    maxExcLoc = err.loc\n            except IndexError:\n                if len(instring) > maxExcLoc:\n                    maxException = ParseException(instring,len(instring),e.errmsg,self)\n                    maxExcLoc = len(instring)\n\n        # only got here if no expression matched, raise exception for match that made it the furthest\n        else:\n            if maxException is not None:\n                maxException.msg = self.errmsg\n                raise maxException\n            else:\n                raise ParseException(instring, loc, \"no defined alternatives to match\", self)\n\n    def __ior__(self, other ):\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass( other )\n        return self.append( other ) #MatchFirst( [ self, other ] )\n\n    def __str__( self ):\n        if hasattr(self,\"name\"):\n            return self.name\n\n        if self.strRepr is None:\n            self.strRepr = \"{\" + \" | \".join(_ustr(e) for e in self.exprs) + \"}\"\n\n        return self.strRepr\n\n    def checkRecursion( self, parseElementList ):\n        subRecCheckList = parseElementList[:] + [ self ]\n        for e in self.exprs:\n            e.checkRecursion( subRecCheckList )\n\n\nclass Each(ParseExpression):\n    \"\"\"Requires all given :class:`ParseExpression` s to be found, but in\n    any order. Expressions may be separated by whitespace.\n\n    May be constructed using the ``'&'`` operator.\n\n    Example::\n\n        color = oneOf(\"RED ORANGE YELLOW GREEN BLUE PURPLE BLACK WHITE BROWN\")\n        shape_type = oneOf(\"SQUARE CIRCLE TRIANGLE STAR HEXAGON OCTAGON\")\n        integer = Word(nums)\n        shape_attr = \"shape:\" + shape_type(\"shape\")\n        posn_attr = \"posn:\" + Group(integer(\"x\") + ',' + integer(\"y\"))(\"posn\")\n        color_attr = \"color:\" + color(\"color\")\n        size_attr = \"size:\" + integer(\"size\")\n\n        # use Each (using operator '&') to accept attributes in any order\n        # (shape and posn are required, color and size are optional)\n        shape_spec = shape_attr & posn_attr & Optional(color_attr) & Optional(size_attr)\n\n        shape_spec.runTests('''\n            shape: SQUARE color: BLACK posn: 100, 120\n            shape: CIRCLE size: 50 color: BLUE posn: 50,80\n            color:GREEN size:20 shape:TRIANGLE posn:20,40\n            '''\n            )\n\n    prints::\n\n        shape: SQUARE color: BLACK posn: 100, 120\n        ['shape:', 'SQUARE', 'color:', 'BLACK', 'posn:', ['100', ',', '120']]\n        - color: BLACK\n        - posn: ['100', ',', '120']\n          - x: 100\n          - y: 120\n        - shape: SQUARE\n\n\n        shape: CIRCLE size: 50 color: BLUE posn: 50,80\n        ['shape:', 'CIRCLE', 'size:', '50', 'color:', 'BLUE', 'posn:', ['50', ',', '80']]\n        - color: BLUE\n        - posn: ['50', ',', '80']\n          - x: 50\n          - y: 80\n        - shape: CIRCLE\n        - size: 50\n\n\n        color: GREEN size: 20 shape: TRIANGLE posn: 20,40\n        ['color:', 'GREEN', 'size:', '20', 'shape:', 'TRIANGLE', 'posn:', ['20', ',', '40']]\n        - color: GREEN\n        - posn: ['20', ',', '40']\n          - x: 20\n          - y: 40\n        - shape: TRIANGLE\n        - size: 20\n    \"\"\"\n    def __init__( self, exprs, savelist = True ):\n        super(Each,self).__init__(exprs, savelist)\n        self.mayReturnEmpty = all(e.mayReturnEmpty for e in self.exprs)\n        self.skipWhitespace = True\n        self.initExprGroups = True\n        self.saveAsList = True\n\n    def streamline(self):\n        super(Each, self).streamline()\n        self.mayReturnEmpty = all(e.mayReturnEmpty for e in self.exprs)\n        return self\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        if self.initExprGroups:\n            self.opt1map = dict((id(e.expr),e) for e in self.exprs if isinstance(e,Optional))\n            opt1 = [ e.expr for e in self.exprs if isinstance(e,Optional) ]\n            opt2 = [ e for e in self.exprs if e.mayReturnEmpty and not isinstance(e,Optional)]\n            self.optionals = opt1 + opt2\n            self.multioptionals = [ e.expr for e in self.exprs if isinstance(e,ZeroOrMore) ]\n            self.multirequired = [ e.expr for e in self.exprs if isinstance(e,OneOrMore) ]\n            self.required = [ e for e in self.exprs if not isinstance(e,(Optional,ZeroOrMore,OneOrMore)) ]\n            self.required += self.multirequired\n            self.initExprGroups = False\n        tmpLoc = loc\n        tmpReqd = self.required[:]\n        tmpOpt  = self.optionals[:]\n        matchOrder = []\n\n        keepMatching = True\n        while keepMatching:\n            tmpExprs = tmpReqd + tmpOpt + self.multioptionals + self.multirequired\n            failed = []\n            for e in tmpExprs:\n                try:\n                    tmpLoc = e.tryParse( instring, tmpLoc )\n                except ParseException:\n                    failed.append(e)\n                else:\n                    matchOrder.append(self.opt1map.get(id(e),e))\n                    if e in tmpReqd:\n                        tmpReqd.remove(e)\n                    elif e in tmpOpt:\n                        tmpOpt.remove(e)\n            if len(failed) == len(tmpExprs):\n                keepMatching = False\n\n        if tmpReqd:\n            missing = \", \".join(_ustr(e) for e in tmpReqd)\n            raise ParseException(instring,loc,\"Missing one or more required elements (%s)\" % missing )\n\n        # add any unmatched Optionals, in case they have default values defined\n        matchOrder += [e for e in self.exprs if isinstance(e,Optional) and e.expr in tmpOpt]\n\n        resultlist = []\n        for e in matchOrder:\n            loc,results = e._parse(instring,loc,doActions)\n            resultlist.append(results)\n\n        finalResults = sum(resultlist, ParseResults([]))\n        return loc, finalResults\n\n    def __str__( self ):\n        if hasattr(self,\"name\"):\n            return self.name\n\n        if self.strRepr is None:\n            self.strRepr = \"{\" + \" & \".join(_ustr(e) for e in self.exprs) + \"}\"\n\n        return self.strRepr\n\n    def checkRecursion( self, parseElementList ):\n        subRecCheckList = parseElementList[:] + [ self ]\n        for e in self.exprs:\n            e.checkRecursion( subRecCheckList )\n\n\nclass ParseElementEnhance(ParserElement):\n    \"\"\"Abstract subclass of :class:`ParserElement`, for combining and\n    post-processing parsed tokens.\n    \"\"\"\n    def __init__( self, expr, savelist=False ):\n        super(ParseElementEnhance,self).__init__(savelist)\n        if isinstance( expr, basestring ):\n            if issubclass(ParserElement._literalStringClass, Token):\n                expr = ParserElement._literalStringClass(expr)\n            else:\n                expr = ParserElement._literalStringClass(Literal(expr))\n        self.expr = expr\n        self.strRepr = None\n        if expr is not None:\n            self.mayIndexError = expr.mayIndexError\n            self.mayReturnEmpty = expr.mayReturnEmpty\n            self.setWhitespaceChars( expr.whiteChars )\n            self.skipWhitespace = expr.skipWhitespace\n            self.saveAsList = expr.saveAsList\n            self.callPreparse = expr.callPreparse\n            self.ignoreExprs.extend(expr.ignoreExprs)\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        if self.expr is not None:\n            return self.expr._parse( instring, loc, doActions, callPreParse=False )\n        else:\n            raise ParseException(\"\",loc,self.errmsg,self)\n\n    def leaveWhitespace( self ):\n        self.skipWhitespace = False\n        self.expr = self.expr.copy()\n        if self.expr is not None:\n            self.expr.leaveWhitespace()\n        return self\n\n    def ignore( self, other ):\n        if isinstance( other, Suppress ):\n            if other not in self.ignoreExprs:\n                super( ParseElementEnhance, self).ignore( other )\n                if self.expr is not None:\n                    self.expr.ignore( self.ignoreExprs[-1] )\n        else:\n            super( ParseElementEnhance, self).ignore( other )\n            if self.expr is not None:\n                self.expr.ignore( self.ignoreExprs[-1] )\n        return self\n\n    def streamline( self ):\n        super(ParseElementEnhance,self).streamline()\n        if self.expr is not None:\n            self.expr.streamline()\n        return self\n\n    def checkRecursion( self, parseElementList ):\n        if self in parseElementList:\n            raise RecursiveGrammarException( parseElementList+[self] )\n        subRecCheckList = parseElementList[:] + [ self ]\n        if self.expr is not None:\n            self.expr.checkRecursion( subRecCheckList )\n\n    def validate( self, validateTrace=[] ):\n        tmp = validateTrace[:]+[self]\n        if self.expr is not None:\n            self.expr.validate(tmp)\n        self.checkRecursion( [] )\n\n    def __str__( self ):\n        try:\n            return super(ParseElementEnhance,self).__str__()\n        except Exception:\n            pass\n\n        if self.strRepr is None and self.expr is not None:\n            self.strRepr = \"%s:(%s)\" % ( self.__class__.__name__, _ustr(self.expr) )\n        return self.strRepr\n\n\nclass FollowedBy(ParseElementEnhance):\n    \"\"\"Lookahead matching of the given parse expression.\n    ``FollowedBy`` does *not* advance the parsing position within\n    the input string, it only verifies that the specified parse\n    expression matches at the current position.  ``FollowedBy``\n    always returns a null token list. If any results names are defined\n    in the lookahead expression, those *will* be returned for access by\n    name.\n\n    Example::\n\n        # use FollowedBy to match a label only if it is followed by a ':'\n        data_word = Word(alphas)\n        label = data_word + FollowedBy(':')\n        attr_expr = Group(label + Suppress(':') + OneOrMore(data_word, stopOn=label).setParseAction(' '.join))\n\n        OneOrMore(attr_expr).parseString(\"shape: SQUARE color: BLACK posn: upper left\").pprint()\n\n    prints::\n\n        [['shape', 'SQUARE'], ['color', 'BLACK'], ['posn', 'upper left']]\n    \"\"\"\n    def __init__( self, expr ):\n        super(FollowedBy,self).__init__(expr)\n        self.mayReturnEmpty = True\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        _, ret = self.expr._parse(instring, loc, doActions=doActions)\n        del ret[:]\n        return loc, ret\n\n\nclass PrecededBy(ParseElementEnhance):\n    \"\"\"Lookbehind matching of the given parse expression.\n    ``PrecededBy`` does not advance the parsing position within the\n    input string, it only verifies that the specified parse expression\n    matches prior to the current position.  ``PrecededBy`` always\n    returns a null token list, but if a results name is defined on the\n    given expression, it is returned.\n\n    Parameters:\n\n     - expr - expression that must match prior to the current parse\n       location\n     - retreat - (default= ``None``) - (int) maximum number of characters\n       to lookbehind prior to the current parse location\n\n    If the lookbehind expression is a string, Literal, Keyword, or\n    a Word or CharsNotIn with a specified exact or maximum length, then\n    the retreat parameter is not required. Otherwise, retreat must be\n    specified to give a maximum number of characters to look back from\n    the current parse position for a lookbehind match.\n\n    Example::\n\n        # VB-style variable names with type prefixes\n        int_var = PrecededBy(\"#\") + pyparsing_common.identifier\n        str_var = PrecededBy(\"$\") + pyparsing_common.identifier\n\n    \"\"\"\n    def __init__(self, expr, retreat=None):\n        super(PrecededBy, self).__init__(expr)\n        self.expr = self.expr().leaveWhitespace()\n        self.mayReturnEmpty = True\n        self.mayIndexError = False\n        self.exact = False\n        if isinstance(expr, str):\n            retreat = len(expr)\n            self.exact = True\n        elif isinstance(expr, (Literal, Keyword)):\n            retreat = expr.matchLen\n            self.exact = True\n        elif isinstance(expr, (Word, CharsNotIn)) and expr.maxLen != _MAX_INT:\n            retreat = expr.maxLen\n            self.exact = True\n        elif isinstance(expr, _PositionToken):\n            retreat = 0\n            self.exact = True\n        self.retreat = retreat\n        self.errmsg = \"not preceded by \" + str(expr)\n        self.skipWhitespace = False\n\n    def parseImpl(self, instring, loc=0, doActions=True):\n        if self.exact:\n            if loc < self.retreat:\n                raise ParseException(instring, loc, self.errmsg)\n            start = loc - self.retreat\n            _, ret = self.expr._parse(instring, start)\n        else:\n            # retreat specified a maximum lookbehind window, iterate\n            test_expr = self.expr + StringEnd()\n            instring_slice = instring[:loc]\n            last_expr = ParseException(instring, loc, self.errmsg)\n            for offset in range(1, min(loc, self.retreat+1)):\n                try:\n                    _, ret = test_expr._parse(instring_slice, loc-offset)\n                except ParseBaseException as pbe:\n                    last_expr = pbe\n                else:\n                    break\n            else:\n                raise last_expr\n        # return empty list of tokens, but preserve any defined results names\n        del ret[:]\n        return loc, ret\n\n\nclass NotAny(ParseElementEnhance):\n    \"\"\"Lookahead to disallow matching with the given parse expression.\n    ``NotAny`` does *not* advance the parsing position within the\n    input string, it only verifies that the specified parse expression\n    does *not* match at the current position.  Also, ``NotAny`` does\n    *not* skip over leading whitespace. ``NotAny`` always returns\n    a null token list.  May be constructed using the '~' operator.\n\n    Example::\n\n        AND, OR, NOT = map(CaselessKeyword, \"AND OR NOT\".split())\n\n        # take care not to mistake keywords for identifiers\n        ident = ~(AND | OR | NOT) + Word(alphas)\n        boolean_term = Optional(NOT) + ident\n\n        # very crude boolean expression - to support parenthesis groups and\n        # operation hierarchy, use infixNotation\n        boolean_expr = boolean_term + ZeroOrMore((AND | OR) + boolean_term)\n\n        # integers that are followed by \".\" are actually floats\n        integer = Word(nums) + ~Char(\".\")\n    \"\"\"\n    def __init__( self, expr ):\n        super(NotAny,self).__init__(expr)\n        #~ self.leaveWhitespace()\n        self.skipWhitespace = False  # do NOT use self.leaveWhitespace(), don't want to propagate to exprs\n        self.mayReturnEmpty = True\n        self.errmsg = \"Found unwanted token, \"+_ustr(self.expr)\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        if self.expr.canParseNext(instring, loc):\n            raise ParseException(instring, loc, self.errmsg, self)\n        return loc, []\n\n    def __str__( self ):\n        if hasattr(self,\"name\"):\n            return self.name\n\n        if self.strRepr is None:\n            self.strRepr = \"~{\" + _ustr(self.expr) + \"}\"\n\n        return self.strRepr\n\nclass _MultipleMatch(ParseElementEnhance):\n    def __init__( self, expr, stopOn=None):\n        super(_MultipleMatch, self).__init__(expr)\n        self.saveAsList = True\n        ender = stopOn\n        if isinstance(ender, basestring):\n            ender = ParserElement._literalStringClass(ender)\n        self.not_ender = ~ender if ender is not None else None\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        self_expr_parse = self.expr._parse\n        self_skip_ignorables = self._skipIgnorables\n        check_ender = self.not_ender is not None\n        if check_ender:\n            try_not_ender = self.not_ender.tryParse\n\n        # must be at least one (but first see if we are the stopOn sentinel;\n        # if so, fail)\n        if check_ender:\n            try_not_ender(instring, loc)\n        loc, tokens = self_expr_parse( instring, loc, doActions, callPreParse=False )\n        try:\n            hasIgnoreExprs = (not not self.ignoreExprs)\n            while 1:\n                if check_ender:\n                    try_not_ender(instring, loc)\n                if hasIgnoreExprs:\n                    preloc = self_skip_ignorables( instring, loc )\n                else:\n                    preloc = loc\n                loc, tmptokens = self_expr_parse( instring, preloc, doActions )\n                if tmptokens or tmptokens.haskeys():\n                    tokens += tmptokens\n        except (ParseException,IndexError):\n            pass\n\n        return loc, tokens\n\nclass OneOrMore(_MultipleMatch):\n    \"\"\"Repetition of one or more of the given expression.\n\n    Parameters:\n     - expr - expression that must match one or more times\n     - stopOn - (default= ``None``) - expression for a terminating sentinel\n          (only required if the sentinel would ordinarily match the repetition\n          expression)\n\n    Example::\n\n        data_word = Word(alphas)\n        label = data_word + FollowedBy(':')\n        attr_expr = Group(label + Suppress(':') + OneOrMore(data_word).setParseAction(' '.join))\n\n        text = \"shape: SQUARE posn: upper left color: BLACK\"\n        OneOrMore(attr_expr).parseString(text).pprint()  # Fail! read 'color' as data instead of next label -> [['shape', 'SQUARE color']]\n\n        # use stopOn attribute for OneOrMore to avoid reading label string as part of the data\n        attr_expr = Group(label + Suppress(':') + OneOrMore(data_word, stopOn=label).setParseAction(' '.join))\n        OneOrMore(attr_expr).parseString(text).pprint() # Better -> [['shape', 'SQUARE'], ['posn', 'upper left'], ['color', 'BLACK']]\n\n        # could also be written as\n        (attr_expr * (1,)).parseString(text).pprint()\n    \"\"\"\n\n    def __str__( self ):\n        if hasattr(self,\"name\"):\n            return self.name\n\n        if self.strRepr is None:\n            self.strRepr = \"{\" + _ustr(self.expr) + \"}...\"\n\n        return self.strRepr\n\nclass ZeroOrMore(_MultipleMatch):\n    \"\"\"Optional repetition of zero or more of the given expression.\n\n    Parameters:\n     - expr - expression that must match zero or more times\n     - stopOn - (default= ``None``) - expression for a terminating sentinel\n          (only required if the sentinel would ordinarily match the repetition\n          expression)\n\n    Example: similar to :class:`OneOrMore`\n    \"\"\"\n    def __init__( self, expr, stopOn=None):\n        super(ZeroOrMore,self).__init__(expr, stopOn=stopOn)\n        self.mayReturnEmpty = True\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        try:\n            return super(ZeroOrMore, self).parseImpl(instring, loc, doActions)\n        except (ParseException,IndexError):\n            return loc, []\n\n    def __str__( self ):\n        if hasattr(self,\"name\"):\n            return self.name\n\n        if self.strRepr is None:\n            self.strRepr = \"[\" + _ustr(self.expr) + \"]...\"\n\n        return self.strRepr\n\nclass _NullToken(object):\n    def __bool__(self):\n        return False\n    __nonzero__ = __bool__\n    def __str__(self):\n        return \"\"\n\n_optionalNotMatched = _NullToken()\nclass Optional(ParseElementEnhance):\n    \"\"\"Optional matching of the given expression.\n\n    Parameters:\n     - expr - expression that must match zero or more times\n     - default (optional) - value to be returned if the optional expression is not found.\n\n    Example::\n\n        # US postal code can be a 5-digit zip, plus optional 4-digit qualifier\n        zip = Combine(Word(nums, exact=5) + Optional('-' + Word(nums, exact=4)))\n        zip.runTests('''\n            # traditional ZIP code\n            12345\n\n            # ZIP+4 form\n            12101-0001\n\n            # invalid ZIP\n            98765-\n            ''')\n\n    prints::\n\n        # traditional ZIP code\n        12345\n        ['12345']\n\n        # ZIP+4 form\n        12101-0001\n        ['12101-0001']\n\n        # invalid ZIP\n        98765-\n             ^\n        FAIL: Expected end of text (at char 5), (line:1, col:6)\n    \"\"\"\n    def __init__( self, expr, default=_optionalNotMatched ):\n        super(Optional,self).__init__( expr, savelist=False )\n        self.saveAsList = self.expr.saveAsList\n        self.defaultValue = default\n        self.mayReturnEmpty = True\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        try:\n            loc, tokens = self.expr._parse( instring, loc, doActions, callPreParse=False )\n        except (ParseException,IndexError):\n            if self.defaultValue is not _optionalNotMatched:\n                if self.expr.resultsName:\n                    tokens = ParseResults([ self.defaultValue ])\n                    tokens[self.expr.resultsName] = self.defaultValue\n                else:\n                    tokens = [ self.defaultValue ]\n            else:\n                tokens = []\n        return loc, tokens\n\n    def __str__( self ):\n        if hasattr(self,\"name\"):\n            return self.name\n\n        if self.strRepr is None:\n            self.strRepr = \"[\" + _ustr(self.expr) + \"]\"\n\n        return self.strRepr\n\nclass SkipTo(ParseElementEnhance):\n    \"\"\"Token for skipping over all undefined text until the matched\n    expression is found.\n\n    Parameters:\n     - expr - target expression marking the end of the data to be skipped\n     - include - (default= ``False``) if True, the target expression is also parsed\n          (the skipped text and target expression are returned as a 2-element list).\n     - ignore - (default= ``None``) used to define grammars (typically quoted strings and\n          comments) that might contain false matches to the target expression\n     - failOn - (default= ``None``) define expressions that are not allowed to be\n          included in the skipped test; if found before the target expression is found,\n          the SkipTo is not a match\n\n    Example::\n\n        report = '''\n            Outstanding Issues Report - 1 Jan 2000\n\n               # | Severity | Description                               |  Days Open\n            -----+----------+-------------------------------------------+-----------\n             101 | Critical | Intermittent system crash                 |          6\n              94 | Cosmetic | Spelling error on Login ('log|n')         |         14\n              79 | Minor    | System slow when running too many reports |         47\n            '''\n        integer = Word(nums)\n        SEP = Suppress('|')\n        # use SkipTo to simply match everything up until the next SEP\n        # - ignore quoted strings, so that a '|' character inside a quoted string does not match\n        # - parse action will call token.strip() for each matched token, i.e., the description body\n        string_data = SkipTo(SEP, ignore=quotedString)\n        string_data.setParseAction(tokenMap(str.strip))\n        ticket_expr = (integer(\"issue_num\") + SEP\n                      + string_data(\"sev\") + SEP\n                      + string_data(\"desc\") + SEP\n                      + integer(\"days_open\"))\n\n        for tkt in ticket_expr.searchString(report):\n            print tkt.dump()\n\n    prints::\n\n        ['101', 'Critical', 'Intermittent system crash', '6']\n        - days_open: 6\n        - desc: Intermittent system crash\n        - issue_num: 101\n        - sev: Critical\n        ['94', 'Cosmetic', \"Spelling error on Login ('log|n')\", '14']\n        - days_open: 14\n        - desc: Spelling error on Login ('log|n')\n        - issue_num: 94\n        - sev: Cosmetic\n        ['79', 'Minor', 'System slow when running too many reports', '47']\n        - days_open: 47\n        - desc: System slow when running too many reports\n        - issue_num: 79\n        - sev: Minor\n    \"\"\"\n    def __init__( self, other, include=False, ignore=None, failOn=None ):\n        super( SkipTo, self ).__init__( other )\n        self.ignoreExpr = ignore\n        self.mayReturnEmpty = True\n        self.mayIndexError = False\n        self.includeMatch = include\n        self.saveAsList = False\n        if isinstance(failOn, basestring):\n            self.failOn = ParserElement._literalStringClass(failOn)\n        else:\n            self.failOn = failOn\n        self.errmsg = \"No match found for \"+_ustr(self.expr)\n\n    def parseImpl( self, instring, loc, doActions=True ):\n        startloc = loc\n        instrlen = len(instring)\n        expr = self.expr\n        expr_parse = self.expr._parse\n        self_failOn_canParseNext = self.failOn.canParseNext if self.failOn is not None else None\n        self_ignoreExpr_tryParse = self.ignoreExpr.tryParse if self.ignoreExpr is not None else None\n\n        tmploc = loc\n        while tmploc <= instrlen:\n            if self_failOn_canParseNext is not None:\n                # break if failOn expression matches\n                if self_failOn_canParseNext(instring, tmploc):\n                    break\n\n            if self_ignoreExpr_tryParse is not None:\n                # advance past ignore expressions\n                while 1:\n                    try:\n                        tmploc = self_ignoreExpr_tryParse(instring, tmploc)\n                    except ParseBaseException:\n                        break\n\n            try:\n                expr_parse(instring, tmploc, doActions=False, callPreParse=False)\n            except (ParseException, IndexError):\n                # no match, advance loc in string\n                tmploc += 1\n            else:\n                # matched skipto expr, done\n                break\n\n        else:\n            # ran off the end of the input string without matching skipto expr, fail\n            raise ParseException(instring, loc, self.errmsg, self)\n\n        # build up return values\n        loc = tmploc\n        skiptext = instring[startloc:loc]\n        skipresult = ParseResults(skiptext)\n\n        if self.includeMatch:\n            loc, mat = expr_parse(instring,loc,doActions,callPreParse=False)\n            skipresult += mat\n\n        return loc, skipresult\n\nclass Forward(ParseElementEnhance):\n    \"\"\"Forward declaration of an expression to be defined later -\n    used for recursive grammars, such as algebraic infix notation.\n    When the expression is known, it is assigned to the ``Forward``\n    variable using the '<<' operator.\n\n    Note: take care when assigning to ``Forward`` not to overlook\n    precedence of operators.\n\n    Specifically, '|' has a lower precedence than '<<', so that::\n\n        fwdExpr << a | b | c\n\n    will actually be evaluated as::\n\n        (fwdExpr << a) | b | c\n\n    thereby leaving b and c out as parseable alternatives.  It is recommended that you\n    explicitly group the values inserted into the ``Forward``::\n\n        fwdExpr << (a | b | c)\n\n    Converting to use the '<<=' operator instead will avoid this problem.\n\n    See :class:`ParseResults.pprint` for an example of a recursive\n    parser created using ``Forward``.\n    \"\"\"\n    def __init__( self, other=None ):\n        super(Forward,self).__init__( other, savelist=False )\n\n    def __lshift__( self, other ):\n        if isinstance( other, basestring ):\n            other = ParserElement._literalStringClass(other)\n        self.expr = other\n        self.strRepr = None\n        self.mayIndexError = self.expr.mayIndexError\n        self.mayReturnEmpty = self.expr.mayReturnEmpty\n        self.setWhitespaceChars( self.expr.whiteChars )\n        self.skipWhitespace = self.expr.skipWhitespace\n        self.saveAsList = self.expr.saveAsList\n        self.ignoreExprs.extend(self.expr.ignoreExprs)\n        return self\n\n    def __ilshift__(self, other):\n        return self << other\n\n    def leaveWhitespace( self ):\n        self.skipWhitespace = False\n        return self\n\n    def streamline( self ):\n        if not self.streamlined:\n            self.streamlined = True\n            if self.expr is not None:\n                self.expr.streamline()\n        return self\n\n    def validate( self, validateTrace=[] ):\n        if self not in validateTrace:\n            tmp = validateTrace[:]+[self]\n            if self.expr is not None:\n                self.expr.validate(tmp)\n        self.checkRecursion([])\n\n    def __str__( self ):\n        if hasattr(self,\"name\"):\n            return self.name\n        return self.__class__.__name__ + \": ...\"\n\n        # stubbed out for now - creates awful memory and perf issues\n        self._revertClass = self.__class__\n        self.__class__ = _ForwardNoRecurse\n        try:\n            if self.expr is not None:\n                retString = _ustr(self.expr)\n            else:\n                retString = \"None\"\n        finally:\n            self.__class__ = self._revertClass\n        return self.__class__.__name__ + \": \" + retString\n\n    def copy(self):\n        if self.expr is not None:\n            return super(Forward,self).copy()\n        else:\n            ret = Forward()\n            ret <<= self\n            return ret\n\nclass _ForwardNoRecurse(Forward):\n    def __str__( self ):\n        return \"...\"\n\nclass TokenConverter(ParseElementEnhance):\n    \"\"\"\n    Abstract subclass of :class:`ParseExpression`, for converting parsed results.\n    \"\"\"\n    def __init__( self, expr, savelist=False ):\n        super(TokenConverter,self).__init__( expr )#, savelist )\n        self.saveAsList = False\n\nclass Combine(TokenConverter):\n    \"\"\"Converter to concatenate all matching tokens to a single string.\n    By default, the matching patterns must also be contiguous in the\n    input string; this can be disabled by specifying\n    ``'adjacent=False'`` in the constructor.\n\n    Example::\n\n        real = Word(nums) + '.' + Word(nums)\n        print(real.parseString('3.1416')) # -> ['3', '.', '1416']\n        # will also erroneously match the following\n        print(real.parseString('3. 1416')) # -> ['3', '.', '1416']\n\n        real = Combine(Word(nums) + '.' + Word(nums))\n        print(real.parseString('3.1416')) # -> ['3.1416']\n        # no match when there are internal spaces\n        print(real.parseString('3. 1416')) # -> Exception: Expected W:(0123...)\n    \"\"\"\n    def __init__( self, expr, joinString=\"\", adjacent=True ):\n        super(Combine,self).__init__( expr )\n        # suppress whitespace-stripping in contained parse expressions, but re-enable it on the Combine itself\n        if adjacent:\n            self.leaveWhitespace()\n        self.adjacent = adjacent\n        self.skipWhitespace = True\n        self.joinString = joinString\n        self.callPreparse = True\n\n    def ignore( self, other ):\n        if self.adjacent:\n            ParserElement.ignore(self, other)\n        else:\n            super( Combine, self).ignore( other )\n        return self\n\n    def postParse( self, instring, loc, tokenlist ):\n        retToks = tokenlist.copy()\n        del retToks[:]\n        retToks += ParseResults([ \"\".join(tokenlist._asStringList(self.joinString)) ], modal=self.modalResults)\n\n        if self.resultsName and retToks.haskeys():\n            return [ retToks ]\n        else:\n            return retToks\n\nclass Group(TokenConverter):\n    \"\"\"Converter to return the matched tokens as a list - useful for\n    returning tokens of :class:`ZeroOrMore` and :class:`OneOrMore` expressions.\n\n    Example::\n\n        ident = Word(alphas)\n        num = Word(nums)\n        term = ident | num\n        func = ident + Optional(delimitedList(term))\n        print(func.parseString(\"fn a,b,100\"))  # -> ['fn', 'a', 'b', '100']\n\n        func = ident + Group(Optional(delimitedList(term)))\n        print(func.parseString(\"fn a,b,100\"))  # -> ['fn', ['a', 'b', '100']]\n    \"\"\"\n    def __init__( self, expr ):\n        super(Group,self).__init__( expr )\n        self.saveAsList = expr.saveAsList\n\n    def postParse( self, instring, loc, tokenlist ):\n        return [ tokenlist ]\n\nclass Dict(TokenConverter):\n    \"\"\"Converter to return a repetitive expression as a list, but also\n    as a dictionary. Each element can also be referenced using the first\n    token in the expression as its key. Useful for tabular report\n    scraping when the first column can be used as a item key.\n\n    Example::\n\n        data_word = Word(alphas)\n        label = data_word + FollowedBy(':')\n        attr_expr = Group(label + Suppress(':') + OneOrMore(data_word).setParseAction(' '.join))\n\n        text = \"shape: SQUARE posn: upper left color: light blue texture: burlap\"\n        attr_expr = (label + Suppress(':') + OneOrMore(data_word, stopOn=label).setParseAction(' '.join))\n\n        # print attributes as plain groups\n        print(OneOrMore(attr_expr).parseString(text).dump())\n\n        # instead of OneOrMore(expr), parse using Dict(OneOrMore(Group(expr))) - Dict will auto-assign names\n        result = Dict(OneOrMore(Group(attr_expr))).parseString(text)\n        print(result.dump())\n\n        # access named fields as dict entries, or output as dict\n        print(result['shape'])\n        print(result.asDict())\n\n    prints::\n\n        ['shape', 'SQUARE', 'posn', 'upper left', 'color', 'light blue', 'texture', 'burlap']\n        [['shape', 'SQUARE'], ['posn', 'upper left'], ['color', 'light blue'], ['texture', 'burlap']]\n        - color: light blue\n        - posn: upper left\n        - shape: SQUARE\n        - texture: burlap\n        SQUARE\n        {'color': 'light blue', 'posn': 'upper left', 'texture': 'burlap', 'shape': 'SQUARE'}\n\n    See more examples at :class:`ParseResults` of accessing fields by results name.\n    \"\"\"\n    def __init__( self, expr ):\n        super(Dict,self).__init__( expr )\n        self.saveAsList = True\n\n    def postParse( self, instring, loc, tokenlist ):\n        for i,tok in enumerate(tokenlist):\n            if len(tok) == 0:\n                continue\n            ikey = tok[0]\n            if isinstance(ikey,int):\n                ikey = _ustr(tok[0]).strip()\n            if len(tok)==1:\n                tokenlist[ikey] = _ParseResultsWithOffset(\"\",i)\n            elif len(tok)==2 and not isinstance(tok[1],ParseResults):\n                tokenlist[ikey] = _ParseResultsWithOffset(tok[1],i)\n            else:\n                dictvalue = tok.copy() #ParseResults(i)\n                del dictvalue[0]\n                if len(dictvalue)!= 1 or (isinstance(dictvalue,ParseResults) and dictvalue.haskeys()):\n                    tokenlist[ikey] = _ParseResultsWithOffset(dictvalue,i)\n                else:\n                    tokenlist[ikey] = _ParseResultsWithOffset(dictvalue[0],i)\n\n        if self.resultsName:\n            return [ tokenlist ]\n        else:\n            return tokenlist\n\n\nclass Suppress(TokenConverter):\n    \"\"\"Converter for ignoring the results of a parsed expression.\n\n    Example::\n\n        source = \"a, b, c,d\"\n        wd = Word(alphas)\n        wd_list1 = wd + ZeroOrMore(',' + wd)\n        print(wd_list1.parseString(source))\n\n        # often, delimiters that are useful during parsing are just in the\n        # way afterward - use Suppress to keep them out of the parsed output\n        wd_list2 = wd + ZeroOrMore(Suppress(',') + wd)\n        print(wd_list2.parseString(source))\n\n    prints::\n\n        ['a', ',', 'b', ',', 'c', ',', 'd']\n        ['a', 'b', 'c', 'd']\n\n    (See also :class:`delimitedList`.)\n    \"\"\"\n    def postParse( self, instring, loc, tokenlist ):\n        return []\n\n    def suppress( self ):\n        return self\n\n\nclass OnlyOnce(object):\n    \"\"\"Wrapper for parse actions, to ensure they are only called once.\n    \"\"\"\n    def __init__(self, methodCall):\n        self.callable = _trim_arity(methodCall)\n        self.called = False\n    def __call__(self,s,l,t):\n        if not self.called:\n            results = self.callable(s,l,t)\n            self.called = True\n            return results\n        raise ParseException(s,l,\"\")\n    def reset(self):\n        self.called = False\n\ndef traceParseAction(f):\n    \"\"\"Decorator for debugging parse actions.\n\n    When the parse action is called, this decorator will print\n    ``\">> entering method-name(line:<current_source_line>, <parse_location>, <matched_tokens>)\"``.\n    When the parse action completes, the decorator will print\n    ``\"<<\"`` followed by the returned value, or any exception that the parse action raised.\n\n    Example::\n\n        wd = Word(alphas)\n\n        @traceParseAction\n        def remove_duplicate_chars(tokens):\n            return ''.join(sorted(set(''.join(tokens))))\n\n        wds = OneOrMore(wd).setParseAction(remove_duplicate_chars)\n        print(wds.parseString(\"slkdjs sld sldd sdlf sdljf\"))\n\n    prints::\n\n        >>entering remove_duplicate_chars(line: 'slkdjs sld sldd sdlf sdljf', 0, (['slkdjs', 'sld', 'sldd', 'sdlf', 'sdljf'], {}))\n        <<leaving remove_duplicate_chars (ret: 'dfjkls')\n        ['dfjkls']\n    \"\"\"\n    f = _trim_arity(f)\n    def z(*paArgs):\n        thisFunc = f.__name__\n        s,l,t = paArgs[-3:]\n        if len(paArgs)>3:\n            thisFunc = paArgs[0].__class__.__name__ + '.' + thisFunc\n        sys.stderr.write( \">>entering %s(line: '%s', %d, %r)\\n\" % (thisFunc,line(l,s),l,t) )\n        try:\n            ret = f(*paArgs)\n        except Exception as exc:\n            sys.stderr.write( \"<<leaving %s (exception: %s)\\n\" % (thisFunc,exc) )\n            raise\n        sys.stderr.write( \"<<leaving %s (ret: %r)\\n\" % (thisFunc,ret) )\n        return ret\n    try:\n        z.__name__ = f.__name__\n    except AttributeError:\n        pass\n    return z\n\n#\n# global helpers\n#\ndef delimitedList( expr, delim=\",\", combine=False ):\n    \"\"\"Helper to define a delimited list of expressions - the delimiter\n    defaults to ','. By default, the list elements and delimiters can\n    have intervening whitespace, and comments, but this can be\n    overridden by passing ``combine=True`` in the constructor. If\n    ``combine`` is set to ``True``, the matching tokens are\n    returned as a single token string, with the delimiters included;\n    otherwise, the matching tokens are returned as a list of tokens,\n    with the delimiters suppressed.\n\n    Example::\n\n        delimitedList(Word(alphas)).parseString(\"aa,bb,cc\") # -> ['aa', 'bb', 'cc']\n        delimitedList(Word(hexnums), delim=':', combine=True).parseString(\"AA:BB:CC:DD:EE\") # -> ['AA:BB:CC:DD:EE']\n    \"\"\"\n    dlName = _ustr(expr)+\" [\"+_ustr(delim)+\" \"+_ustr(expr)+\"]...\"\n    if combine:\n        return Combine( expr + ZeroOrMore( delim + expr ) ).setName(dlName)\n    else:\n        return ( expr + ZeroOrMore( Suppress( delim ) + expr ) ).setName(dlName)\n\ndef countedArray( expr, intExpr=None ):\n    \"\"\"Helper to define a counted list of expressions.\n\n    This helper defines a pattern of the form::\n\n        integer expr expr expr...\n\n    where the leading integer tells how many expr expressions follow.\n    The matched tokens returns the array of expr tokens as a list - the\n    leading count token is suppressed.\n\n    If ``intExpr`` is specified, it should be a pyparsing expression\n    that produces an integer value.\n\n    Example::\n\n        countedArray(Word(alphas)).parseString('2 ab cd ef')  # -> ['ab', 'cd']\n\n        # in this parser, the leading integer value is given in binary,\n        # '10' indicating that 2 values are in the array\n        binaryConstant = Word('01').setParseAction(lambda t: int(t[0], 2))\n        countedArray(Word(alphas), intExpr=binaryConstant).parseString('10 ab cd ef')  # -> ['ab', 'cd']\n    \"\"\"\n    arrayExpr = Forward()\n    def countFieldParseAction(s,l,t):\n        n = t[0]\n        arrayExpr << (n and Group(And([expr]*n)) or Group(empty))\n        return []\n    if intExpr is None:\n        intExpr = Word(nums).setParseAction(lambda t:int(t[0]))\n    else:\n        intExpr = intExpr.copy()\n    intExpr.setName(\"arrayLen\")\n    intExpr.addParseAction(countFieldParseAction, callDuringTry=True)\n    return ( intExpr + arrayExpr ).setName('(len) ' + _ustr(expr) + '...')\n\ndef _flatten(L):\n    ret = []\n    for i in L:\n        if isinstance(i,list):\n            ret.extend(_flatten(i))\n        else:\n            ret.append(i)\n    return ret\n\ndef matchPreviousLiteral(expr):\n    \"\"\"Helper to define an expression that is indirectly defined from\n    the tokens matched in a previous expression, that is, it looks for\n    a 'repeat' of a previous expression.  For example::\n\n        first = Word(nums)\n        second = matchPreviousLiteral(first)\n        matchExpr = first + \":\" + second\n\n    will match ``\"1:1\"``, but not ``\"1:2\"``.  Because this\n    matches a previous literal, will also match the leading\n    ``\"1:1\"`` in ``\"1:10\"``. If this is not desired, use\n    :class:`matchPreviousExpr`. Do *not* use with packrat parsing\n    enabled.\n    \"\"\"\n    rep = Forward()\n    def copyTokenToRepeater(s,l,t):\n        if t:\n            if len(t) == 1:\n                rep << t[0]\n            else:\n                # flatten t tokens\n                tflat = _flatten(t.asList())\n                rep << And(Literal(tt) for tt in tflat)\n        else:\n            rep << Empty()\n    expr.addParseAction(copyTokenToRepeater, callDuringTry=True)\n    rep.setName('(prev) ' + _ustr(expr))\n    return rep\n\ndef matchPreviousExpr(expr):\n    \"\"\"Helper to define an expression that is indirectly defined from\n    the tokens matched in a previous expression, that is, it looks for\n    a 'repeat' of a previous expression.  For example::\n\n        first = Word(nums)\n        second = matchPreviousExpr(first)\n        matchExpr = first + \":\" + second\n\n    will match ``\"1:1\"``, but not ``\"1:2\"``.  Because this\n    matches by expressions, will *not* match the leading ``\"1:1\"``\n    in ``\"1:10\"``; the expressions are evaluated first, and then\n    compared, so ``\"1\"`` is compared with ``\"10\"``. Do *not* use\n    with packrat parsing enabled.\n    \"\"\"\n    rep = Forward()\n    e2 = expr.copy()\n    rep <<= e2\n    def copyTokenToRepeater(s,l,t):\n        matchTokens = _flatten(t.asList())\n        def mustMatchTheseTokens(s,l,t):\n            theseTokens = _flatten(t.asList())\n            if  theseTokens != matchTokens:\n                raise ParseException(\"\",0,\"\")\n        rep.setParseAction( mustMatchTheseTokens, callDuringTry=True )\n    expr.addParseAction(copyTokenToRepeater, callDuringTry=True)\n    rep.setName('(prev) ' + _ustr(expr))\n    return rep\n\ndef _escapeRegexRangeChars(s):\n    #~  escape these chars: ^-]\n    for c in r\"\\^-]\":\n        s = s.replace(c,_bslash+c)\n    s = s.replace(\"\\n\",r\"\\n\")\n    s = s.replace(\"\\t\",r\"\\t\")\n    return _ustr(s)\n\ndef oneOf( strs, caseless=False, useRegex=True ):\n    \"\"\"Helper to quickly define a set of alternative Literals, and makes\n    sure to do longest-first testing when there is a conflict,\n    regardless of the input order, but returns\n    a :class:`MatchFirst` for best performance.\n\n    Parameters:\n\n     - strs - a string of space-delimited literals, or a collection of\n       string literals\n     - caseless - (default= ``False``) - treat all literals as\n       caseless\n     - useRegex - (default= ``True``) - as an optimization, will\n       generate a Regex object; otherwise, will generate\n       a :class:`MatchFirst` object (if ``caseless=True``, or if\n       creating a :class:`Regex` raises an exception)\n\n    Example::\n\n        comp_oper = oneOf(\"< = > <= >= !=\")\n        var = Word(alphas)\n        number = Word(nums)\n        term = var | number\n        comparison_expr = term + comp_oper + term\n        print(comparison_expr.searchString(\"B = 12  AA=23 B<=AA AA>12\"))\n\n    prints::\n\n        [['B', '=', '12'], ['AA', '=', '23'], ['B', '<=', 'AA'], ['AA', '>', '12']]\n    \"\"\"\n    if caseless:\n        isequal = ( lambda a,b: a.upper() == b.upper() )\n        masks = ( lambda a,b: b.upper().startswith(a.upper()) )\n        parseElementClass = CaselessLiteral\n    else:\n        isequal = ( lambda a,b: a == b )\n        masks = ( lambda a,b: b.startswith(a) )\n        parseElementClass = Literal\n\n    symbols = []\n    if isinstance(strs,basestring):\n        symbols = strs.split()\n    elif isinstance(strs, Iterable):\n        symbols = list(strs)\n    else:\n        warnings.warn(\"Invalid argument to oneOf, expected string or iterable\",\n                SyntaxWarning, stacklevel=2)\n    if not symbols:\n        return NoMatch()\n\n    i = 0\n    while i < len(symbols)-1:\n        cur = symbols[i]\n        for j,other in enumerate(symbols[i+1:]):\n            if ( isequal(other, cur) ):\n                del symbols[i+j+1]\n                break\n            elif ( masks(cur, other) ):\n                del symbols[i+j+1]\n                symbols.insert(i,other)\n                cur = other\n                break\n        else:\n            i += 1\n\n    if not caseless and useRegex:\n        #~ print (strs,\"->\", \"|\".join( [ _escapeRegexChars(sym) for sym in symbols] ))\n        try:\n            if len(symbols)==len(\"\".join(symbols)):\n                return Regex( \"[%s]\" % \"\".join(_escapeRegexRangeChars(sym) for sym in symbols) ).setName(' | '.join(symbols))\n            else:\n                return Regex( \"|\".join(re.escape(sym) for sym in symbols) ).setName(' | '.join(symbols))\n        except Exception:\n            warnings.warn(\"Exception creating Regex for oneOf, building MatchFirst\",\n                    SyntaxWarning, stacklevel=2)\n\n\n    # last resort, just use MatchFirst\n    return MatchFirst(parseElementClass(sym) for sym in symbols).setName(' | '.join(symbols))\n\ndef dictOf( key, value ):\n    \"\"\"Helper to easily and clearly define a dictionary by specifying\n    the respective patterns for the key and value.  Takes care of\n    defining the :class:`Dict`, :class:`ZeroOrMore`, and\n    :class:`Group` tokens in the proper order.  The key pattern\n    can include delimiting markers or punctuation, as long as they are\n    suppressed, thereby leaving the significant key text.  The value\n    pattern can include named results, so that the :class:`Dict` results\n    can include named token fields.\n\n    Example::\n\n        text = \"shape: SQUARE posn: upper left color: light blue texture: burlap\"\n        attr_expr = (label + Suppress(':') + OneOrMore(data_word, stopOn=label).setParseAction(' '.join))\n        print(OneOrMore(attr_expr).parseString(text).dump())\n\n        attr_label = label\n        attr_value = Suppress(':') + OneOrMore(data_word, stopOn=label).setParseAction(' '.join)\n\n        # similar to Dict, but simpler call format\n        result = dictOf(attr_label, attr_value).parseString(text)\n        print(result.dump())\n        print(result['shape'])\n        print(result.shape)  # object attribute access works too\n        print(result.asDict())\n\n    prints::\n\n        [['shape', 'SQUARE'], ['posn', 'upper left'], ['color', 'light blue'], ['texture', 'burlap']]\n        - color: light blue\n        - posn: upper left\n        - shape: SQUARE\n        - texture: burlap\n        SQUARE\n        SQUARE\n        {'color': 'light blue', 'shape': 'SQUARE', 'posn': 'upper left', 'texture': 'burlap'}\n    \"\"\"\n    return Dict(OneOrMore(Group(key + value)))\n\ndef originalTextFor(expr, asString=True):\n    \"\"\"Helper to return the original, untokenized text for a given\n    expression.  Useful to restore the parsed fields of an HTML start\n    tag into the raw tag text itself, or to revert separate tokens with\n    intervening whitespace back to the original matching input text. By\n    default, returns astring containing the original parsed text.\n\n    If the optional ``asString`` argument is passed as\n    ``False``, then the return value is\n    a :class:`ParseResults` containing any results names that\n    were originally matched, and a single token containing the original\n    matched text from the input string.  So if the expression passed to\n    :class:`originalTextFor` contains expressions with defined\n    results names, you must set ``asString`` to ``False`` if you\n    want to preserve those results name values.\n\n    Example::\n\n        src = \"this is test <b> bold <i>text</i> </b> normal text \"\n        for tag in (\"b\",\"i\"):\n            opener,closer = makeHTMLTags(tag)\n            patt = originalTextFor(opener + SkipTo(closer) + closer)\n            print(patt.searchString(src)[0])\n\n    prints::\n\n        ['<b> bold <i>text</i> </b>']\n        ['<i>text</i>']\n    \"\"\"\n    locMarker = Empty().setParseAction(lambda s,loc,t: loc)\n    endlocMarker = locMarker.copy()\n    endlocMarker.callPreparse = False\n    matchExpr = locMarker(\"_original_start\") + expr + endlocMarker(\"_original_end\")\n    if asString:\n        extractText = lambda s,l,t: s[t._original_start:t._original_end]\n    else:\n        def extractText(s,l,t):\n            t[:] = [s[t.pop('_original_start'):t.pop('_original_end')]]\n    matchExpr.setParseAction(extractText)\n    matchExpr.ignoreExprs = expr.ignoreExprs\n    return matchExpr\n\ndef ungroup(expr):\n    \"\"\"Helper to undo pyparsing's default grouping of And expressions,\n    even if all but one are non-empty.\n    \"\"\"\n    return TokenConverter(expr).setParseAction(lambda t:t[0])\n\ndef locatedExpr(expr):\n    \"\"\"Helper to decorate a returned token with its starting and ending\n    locations in the input string.\n\n    This helper adds the following results names:\n\n     - locn_start = location where matched expression begins\n     - locn_end = location where matched expression ends\n     - value = the actual parsed results\n\n    Be careful if the input text contains ``<TAB>`` characters, you\n    may want to call :class:`ParserElement.parseWithTabs`\n\n    Example::\n\n        wd = Word(alphas)\n        for match in locatedExpr(wd).searchString(\"ljsdf123lksdjjf123lkkjj1222\"):\n            print(match)\n\n    prints::\n\n        [[0, 'ljsdf', 5]]\n        [[8, 'lksdjjf', 15]]\n        [[18, 'lkkjj', 23]]\n    \"\"\"\n    locator = Empty().setParseAction(lambda s,l,t: l)\n    return Group(locator(\"locn_start\") + expr(\"value\") + locator.copy().leaveWhitespace()(\"locn_end\"))\n\n\n# convenience constants for positional expressions\nempty       = Empty().setName(\"empty\")\nlineStart   = LineStart().setName(\"lineStart\")\nlineEnd     = LineEnd().setName(\"lineEnd\")\nstringStart = StringStart().setName(\"stringStart\")\nstringEnd   = StringEnd().setName(\"stringEnd\")\n\n_escapedPunc = Word( _bslash, r\"\\[]-*.$+^?()~ \", exact=2 ).setParseAction(lambda s,l,t:t[0][1])\n_escapedHexChar = Regex(r\"\\\\0?[xX][0-9a-fA-F]+\").setParseAction(lambda s,l,t:unichr(int(t[0].lstrip(r'\\0x'),16)))\n_escapedOctChar = Regex(r\"\\\\0[0-7]+\").setParseAction(lambda s,l,t:unichr(int(t[0][1:],8)))\n_singleChar = _escapedPunc | _escapedHexChar | _escapedOctChar | CharsNotIn(r'\\]', exact=1)\n_charRange = Group(_singleChar + Suppress(\"-\") + _singleChar)\n_reBracketExpr = Literal(\"[\") + Optional(\"^\").setResultsName(\"negate\") + Group( OneOrMore( _charRange | _singleChar ) ).setResultsName(\"body\") + \"]\"\n\ndef srange(s):\n    r\"\"\"Helper to easily define string ranges for use in Word\n    construction. Borrows syntax from regexp '[]' string range\n    definitions::\n\n        srange(\"[0-9]\")   -> \"0123456789\"\n        srange(\"[a-z]\")   -> \"abcdefghijklmnopqrstuvwxyz\"\n        srange(\"[a-z$_]\") -> \"abcdefghijklmnopqrstuvwxyz$_\"\n\n    The input string must be enclosed in []'s, and the returned string\n    is the expanded character set joined into a single string. The\n    values enclosed in the []'s may be:\n\n     - a single character\n     - an escaped character with a leading backslash (such as ``\\-``\n       or ``\\]``)\n     - an escaped hex character with a leading ``'\\x'``\n       (``\\x21``, which is a ``'!'`` character) (``\\0x##``\n       is also supported for backwards compatibility)\n     - an escaped octal character with a leading ``'\\0'``\n       (``\\041``, which is a ``'!'`` character)\n     - a range of any of the above, separated by a dash (``'a-z'``,\n       etc.)\n     - any combination of the above (``'aeiouy'``,\n       ``'a-zA-Z0-9_$'``, etc.)\n    \"\"\"\n    _expanded = lambda p: p if not isinstance(p,ParseResults) else ''.join(unichr(c) for c in range(ord(p[0]),ord(p[1])+1))\n    try:\n        return \"\".join(_expanded(part) for part in _reBracketExpr.parseString(s).body)\n    except Exception:\n        return \"\"\n\ndef matchOnlyAtCol(n):\n    \"\"\"Helper method for defining parse actions that require matching at\n    a specific column in the input text.\n    \"\"\"\n    def verifyCol(strg,locn,toks):\n        if col(locn,strg) != n:\n            raise ParseException(strg,locn,\"matched token not at column %d\" % n)\n    return verifyCol\n\ndef replaceWith(replStr):\n    \"\"\"Helper method for common parse actions that simply return\n    a literal value.  Especially useful when used with\n    :class:`transformString<ParserElement.transformString>` ().\n\n    Example::\n\n        num = Word(nums).setParseAction(lambda toks: int(toks[0]))\n        na = oneOf(\"N/A NA\").setParseAction(replaceWith(math.nan))\n        term = na | num\n\n        OneOrMore(term).parseString(\"324 234 N/A 234\") # -> [324, 234, nan, 234]\n    \"\"\"\n    return lambda s,l,t: [replStr]\n\ndef removeQuotes(s,l,t):\n    \"\"\"Helper parse action for removing quotation marks from parsed\n    quoted strings.\n\n    Example::\n\n        # by default, quotation marks are included in parsed results\n        quotedString.parseString(\"'Now is the Winter of our Discontent'\") # -> [\"'Now is the Winter of our Discontent'\"]\n\n        # use removeQuotes to strip quotation marks from parsed results\n        quotedString.setParseAction(removeQuotes)\n        quotedString.parseString(\"'Now is the Winter of our Discontent'\") # -> [\"Now is the Winter of our Discontent\"]\n    \"\"\"\n    return t[0][1:-1]\n\ndef tokenMap(func, *args):\n    \"\"\"Helper to define a parse action by mapping a function to all\n    elements of a ParseResults list. If any additional args are passed,\n    they are forwarded to the given function as additional arguments\n    after the token, as in\n    ``hex_integer = Word(hexnums).setParseAction(tokenMap(int, 16))``,\n    which will convert the parsed data to an integer using base 16.\n\n    Example (compare the last to example in :class:`ParserElement.transformString`::\n\n        hex_ints = OneOrMore(Word(hexnums)).setParseAction(tokenMap(int, 16))\n        hex_ints.runTests('''\n            00 11 22 aa FF 0a 0d 1a\n            ''')\n\n        upperword = Word(alphas).setParseAction(tokenMap(str.upper))\n        OneOrMore(upperword).runTests('''\n            my kingdom for a horse\n            ''')\n\n        wd = Word(alphas).setParseAction(tokenMap(str.title))\n        OneOrMore(wd).setParseAction(' '.join).runTests('''\n            now is the winter of our discontent made glorious summer by this sun of york\n            ''')\n\n    prints::\n\n        00 11 22 aa FF 0a 0d 1a\n        [0, 17, 34, 170, 255, 10, 13, 26]\n\n        my kingdom for a horse\n        ['MY', 'KINGDOM', 'FOR', 'A', 'HORSE']\n\n        now is the winter of our discontent made glorious summer by this sun of york\n        ['Now Is The Winter Of Our Discontent Made Glorious Summer By This Sun Of York']\n    \"\"\"\n    def pa(s,l,t):\n        return [func(tokn, *args) for tokn in t]\n\n    try:\n        func_name = getattr(func, '__name__',\n                            getattr(func, '__class__').__name__)\n    except Exception:\n        func_name = str(func)\n    pa.__name__ = func_name\n\n    return pa\n\nupcaseTokens = tokenMap(lambda t: _ustr(t).upper())\n\"\"\"(Deprecated) Helper parse action to convert tokens to upper case.\nDeprecated in favor of :class:`pyparsing_common.upcaseTokens`\"\"\"\n\ndowncaseTokens = tokenMap(lambda t: _ustr(t).lower())\n\"\"\"(Deprecated) Helper parse action to convert tokens to lower case.\nDeprecated in favor of :class:`pyparsing_common.downcaseTokens`\"\"\"\n\ndef _makeTags(tagStr, xml):\n    \"\"\"Internal helper to construct opening and closing tag expressions, given a tag name\"\"\"\n    if isinstance(tagStr,basestring):\n        resname = tagStr\n        tagStr = Keyword(tagStr, caseless=not xml)\n    else:\n        resname = tagStr.name\n\n    tagAttrName = Word(alphas,alphanums+\"_-:\")\n    if (xml):\n        tagAttrValue = dblQuotedString.copy().setParseAction( removeQuotes )\n        openTag = Suppress(\"<\") + tagStr(\"tag\") + \\\n                Dict(ZeroOrMore(Group( tagAttrName + Suppress(\"=\") + tagAttrValue ))) + \\\n                Optional(\"/\",default=[False]).setResultsName(\"empty\").setParseAction(lambda s,l,t:t[0]=='/') + Suppress(\">\")\n    else:\n        printablesLessRAbrack = \"\".join(c for c in printables if c not in \">\")\n        tagAttrValue = quotedString.copy().setParseAction( removeQuotes ) | Word(printablesLessRAbrack)\n        openTag = Suppress(\"<\") + tagStr(\"tag\") + \\\n                Dict(ZeroOrMore(Group( tagAttrName.setParseAction(downcaseTokens) + \\\n                Optional( Suppress(\"=\") + tagAttrValue ) ))) + \\\n                Optional(\"/\",default=[False]).setResultsName(\"empty\").setParseAction(lambda s,l,t:t[0]=='/') + Suppress(\">\")\n    closeTag = Combine(_L(\"</\") + tagStr + \">\")\n\n    openTag = openTag.setResultsName(\"start\"+\"\".join(resname.replace(\":\",\" \").title().split())).setName(\"<%s>\" % resname)\n    closeTag = closeTag.setResultsName(\"end\"+\"\".join(resname.replace(\":\",\" \").title().split())).setName(\"</%s>\" % resname)\n    openTag.tag = resname\n    closeTag.tag = resname\n    return openTag, closeTag\n\ndef makeHTMLTags(tagStr):\n    \"\"\"Helper to construct opening and closing tag expressions for HTML,\n    given a tag name. Matches tags in either upper or lower case,\n    attributes with namespaces and with quoted or unquoted values.\n\n    Example::\n\n        text = '<td>More info at the <a href=\"https://github.com/pyparsing/pyparsing/wiki\">pyparsing</a> wiki page</td>'\n        # makeHTMLTags returns pyparsing expressions for the opening and\n        # closing tags as a 2-tuple\n        a,a_end = makeHTMLTags(\"A\")\n        link_expr = a + SkipTo(a_end)(\"link_text\") + a_end\n\n        for link in link_expr.searchString(text):\n            # attributes in the <A> tag (like \"href\" shown here) are\n            # also accessible as named results\n            print(link.link_text, '->', link.href)\n\n    prints::\n\n        pyparsing -> https://github.com/pyparsing/pyparsing/wiki\n    \"\"\"\n    return _makeTags( tagStr, False )\n\ndef makeXMLTags(tagStr):\n    \"\"\"Helper to construct opening and closing tag expressions for XML,\n    given a tag name. Matches tags only in the given upper/lower case.\n\n    Example: similar to :class:`makeHTMLTags`\n    \"\"\"\n    return _makeTags( tagStr, True )\n\ndef withAttribute(*args,**attrDict):\n    \"\"\"Helper to create a validating parse action to be used with start\n    tags created with :class:`makeXMLTags` or\n    :class:`makeHTMLTags`. Use ``withAttribute`` to qualify\n    a starting tag with a required attribute value, to avoid false\n    matches on common tags such as ``<TD>`` or ``<DIV>``.\n\n    Call ``withAttribute`` with a series of attribute names and\n    values. Specify the list of filter attributes names and values as:\n\n     - keyword arguments, as in ``(align=\"right\")``, or\n     - as an explicit dict with ``**`` operator, when an attribute\n       name is also a Python reserved word, as in ``**{\"class\":\"Customer\", \"align\":\"right\"}``\n     - a list of name-value tuples, as in ``((\"ns1:class\", \"Customer\"), (\"ns2:align\",\"right\"))``\n\n    For attribute names with a namespace prefix, you must use the second\n    form.  Attribute names are matched insensitive to upper/lower case.\n\n    If just testing for ``class`` (with or without a namespace), use\n    :class:`withClass`.\n\n    To verify that the attribute exists, but without specifying a value,\n    pass ``withAttribute.ANY_VALUE`` as the value.\n\n    Example::\n\n        html = '''\n            <div>\n            Some text\n            <div type=\"grid\">1 4 0 1 0</div>\n            <div type=\"graph\">1,3 2,3 1,1</div>\n            <div>this has no type</div>\n            </div>\n\n        '''\n        div,div_end = makeHTMLTags(\"div\")\n\n        # only match div tag having a type attribute with value \"grid\"\n        div_grid = div().setParseAction(withAttribute(type=\"grid\"))\n        grid_expr = div_grid + SkipTo(div | div_end)(\"body\")\n        for grid_header in grid_expr.searchString(html):\n            print(grid_header.body)\n\n        # construct a match with any div tag having a type attribute, regardless of the value\n        div_any_type = div().setParseAction(withAttribute(type=withAttribute.ANY_VALUE))\n        div_expr = div_any_type + SkipTo(div | div_end)(\"body\")\n        for div_header in div_expr.searchString(html):\n            print(div_header.body)\n\n    prints::\n\n        1 4 0 1 0\n\n        1 4 0 1 0\n        1,3 2,3 1,1\n    \"\"\"\n    if args:\n        attrs = args[:]\n    else:\n        attrs = attrDict.items()\n    attrs = [(k,v) for k,v in attrs]\n    def pa(s,l,tokens):\n        for attrName,attrValue in attrs:\n            if attrName not in tokens:\n                raise ParseException(s,l,\"no matching attribute \" + attrName)\n            if attrValue != withAttribute.ANY_VALUE and tokens[attrName] != attrValue:\n                raise ParseException(s,l,\"attribute '%s' has value '%s', must be '%s'\" %\n                                            (attrName, tokens[attrName], attrValue))\n    return pa\nwithAttribute.ANY_VALUE = object()\n\ndef withClass(classname, namespace=''):\n    \"\"\"Simplified version of :class:`withAttribute` when\n    matching on a div class - made difficult because ``class`` is\n    a reserved word in Python.\n\n    Example::\n\n        html = '''\n            <div>\n            Some text\n            <div class=\"grid\">1 4 0 1 0</div>\n            <div class=\"graph\">1,3 2,3 1,1</div>\n            <div>this &lt;div&gt; has no class</div>\n            </div>\n\n        '''\n        div,div_end = makeHTMLTags(\"div\")\n        div_grid = div().setParseAction(withClass(\"grid\"))\n\n        grid_expr = div_grid + SkipTo(div | div_end)(\"body\")\n        for grid_header in grid_expr.searchString(html):\n            print(grid_header.body)\n\n        div_any_type = div().setParseAction(withClass(withAttribute.ANY_VALUE))\n        div_expr = div_any_type + SkipTo(div | div_end)(\"body\")\n        for div_header in div_expr.searchString(html):\n            print(div_header.body)\n\n    prints::\n\n        1 4 0 1 0\n\n        1 4 0 1 0\n        1,3 2,3 1,1\n    \"\"\"\n    classattr = \"%s:class\" % namespace if namespace else \"class\"\n    return withAttribute(**{classattr : classname})\n\nopAssoc = SimpleNamespace()\nopAssoc.LEFT = object()\nopAssoc.RIGHT = object()\n\ndef infixNotation( baseExpr, opList, lpar=Suppress('('), rpar=Suppress(')') ):\n    \"\"\"Helper method for constructing grammars of expressions made up of\n    operators working in a precedence hierarchy.  Operators may be unary\n    or binary, left- or right-associative.  Parse actions can also be\n    attached to operator expressions. The generated parser will also\n    recognize the use of parentheses to override operator precedences\n    (see example below).\n\n    Note: if you define a deep operator list, you may see performance\n    issues when using infixNotation. See\n    :class:`ParserElement.enablePackrat` for a mechanism to potentially\n    improve your parser performance.\n\n    Parameters:\n     - baseExpr - expression representing the most basic element for the\n       nested\n     - opList - list of tuples, one for each operator precedence level\n       in the expression grammar; each tuple is of the form ``(opExpr,\n       numTerms, rightLeftAssoc, parseAction)``, where:\n\n       - opExpr is the pyparsing expression for the operator; may also\n         be a string, which will be converted to a Literal; if numTerms\n         is 3, opExpr is a tuple of two expressions, for the two\n         operators separating the 3 terms\n       - numTerms is the number of terms for this operator (must be 1,\n         2, or 3)\n       - rightLeftAssoc is the indicator whether the operator is right\n         or left associative, using the pyparsing-defined constants\n         ``opAssoc.RIGHT`` and ``opAssoc.LEFT``.\n       - parseAction is the parse action to be associated with\n         expressions matching this operator expression (the parse action\n         tuple member may be omitted); if the parse action is passed\n         a tuple or list of functions, this is equivalent to calling\n         ``setParseAction(*fn)``\n         (:class:`ParserElement.setParseAction`)\n     - lpar - expression for matching left-parentheses\n       (default= ``Suppress('(')``)\n     - rpar - expression for matching right-parentheses\n       (default= ``Suppress(')')``)\n\n    Example::\n\n        # simple example of four-function arithmetic with ints and\n        # variable names\n        integer = pyparsing_common.signed_integer\n        varname = pyparsing_common.identifier\n\n        arith_expr = infixNotation(integer | varname,\n            [\n            ('-', 1, opAssoc.RIGHT),\n            (oneOf('* /'), 2, opAssoc.LEFT),\n            (oneOf('+ -'), 2, opAssoc.LEFT),\n            ])\n\n        arith_expr.runTests('''\n            5+3*6\n            (5+3)*6\n            -2--11\n            ''', fullDump=False)\n\n    prints::\n\n        5+3*6\n        [[5, '+', [3, '*', 6]]]\n\n        (5+3)*6\n        [[[5, '+', 3], '*', 6]]\n\n        -2--11\n        [[['-', 2], '-', ['-', 11]]]\n    \"\"\"\n    # captive version of FollowedBy that does not do parse actions or capture results names\n    class _FB(FollowedBy):\n        def parseImpl(self, instring, loc, doActions=True):\n            self.expr.tryParse(instring, loc)\n            return loc, []\n\n    ret = Forward()\n    lastExpr = baseExpr | ( lpar + ret + rpar )\n    for i,operDef in enumerate(opList):\n        opExpr,arity,rightLeftAssoc,pa = (operDef + (None,))[:4]\n        termName = \"%s term\" % opExpr if arity < 3 else \"%s%s term\" % opExpr\n        if arity == 3:\n            if opExpr is None or len(opExpr) != 2:\n                raise ValueError(\n                    \"if numterms=3, opExpr must be a tuple or list of two expressions\")\n            opExpr1, opExpr2 = opExpr\n        thisExpr = Forward().setName(termName)\n        if rightLeftAssoc == opAssoc.LEFT:\n            if arity == 1:\n                matchExpr = _FB(lastExpr + opExpr) + Group( lastExpr + OneOrMore( opExpr ) )\n            elif arity == 2:\n                if opExpr is not None:\n                    matchExpr = _FB(lastExpr + opExpr + lastExpr) + Group( lastExpr + OneOrMore( opExpr + lastExpr ) )\n                else:\n                    matchExpr = _FB(lastExpr+lastExpr) + Group( lastExpr + OneOrMore(lastExpr) )\n            elif arity == 3:\n                matchExpr = _FB(lastExpr + opExpr1 + lastExpr + opExpr2 + lastExpr) + \\\n                            Group( lastExpr + opExpr1 + lastExpr + opExpr2 + lastExpr )\n            else:\n                raise ValueError(\"operator must be unary (1), binary (2), or ternary (3)\")\n        elif rightLeftAssoc == opAssoc.RIGHT:\n            if arity == 1:\n                # try to avoid LR with this extra test\n                if not isinstance(opExpr, Optional):\n                    opExpr = Optional(opExpr)\n                matchExpr = _FB(opExpr.expr + thisExpr) + Group( opExpr + thisExpr )\n            elif arity == 2:\n                if opExpr is not None:\n                    matchExpr = _FB(lastExpr + opExpr + thisExpr) + Group( lastExpr + OneOrMore( opExpr + thisExpr ) )\n                else:\n                    matchExpr = _FB(lastExpr + thisExpr) + Group( lastExpr + OneOrMore( thisExpr ) )\n            elif arity == 3:\n                matchExpr = _FB(lastExpr + opExpr1 + thisExpr + opExpr2 + thisExpr) + \\\n                            Group( lastExpr + opExpr1 + thisExpr + opExpr2 + thisExpr )\n            else:\n                raise ValueError(\"operator must be unary (1), binary (2), or ternary (3)\")\n        else:\n            raise ValueError(\"operator must indicate right or left associativity\")\n        if pa:\n            if isinstance(pa, (tuple, list)):\n                matchExpr.setParseAction(*pa)\n            else:\n                matchExpr.setParseAction(pa)\n        thisExpr <<= ( matchExpr.setName(termName) | lastExpr )\n        lastExpr = thisExpr\n    ret <<= lastExpr\n    return ret\n\noperatorPrecedence = infixNotation\n\"\"\"(Deprecated) Former name of :class:`infixNotation`, will be\ndropped in a future release.\"\"\"\n\ndblQuotedString = Combine(Regex(r'\"(?:[^\"\\n\\r\\\\]|(?:\"\")|(?:\\\\(?:[^x]|x[0-9a-fA-F]+)))*')+'\"').setName(\"string enclosed in double quotes\")\nsglQuotedString = Combine(Regex(r\"'(?:[^'\\n\\r\\\\]|(?:'')|(?:\\\\(?:[^x]|x[0-9a-fA-F]+)))*\")+\"'\").setName(\"string enclosed in single quotes\")\nquotedString = Combine(Regex(r'\"(?:[^\"\\n\\r\\\\]|(?:\"\")|(?:\\\\(?:[^x]|x[0-9a-fA-F]+)))*')+'\"'|\n                       Regex(r\"'(?:[^'\\n\\r\\\\]|(?:'')|(?:\\\\(?:[^x]|x[0-9a-fA-F]+)))*\")+\"'\").setName(\"quotedString using single or double quotes\")\nunicodeString = Combine(_L('u') + quotedString.copy()).setName(\"unicode string literal\")\n\ndef nestedExpr(opener=\"(\", closer=\")\", content=None, ignoreExpr=quotedString.copy()):\n    \"\"\"Helper method for defining nested lists enclosed in opening and\n    closing delimiters (\"(\" and \")\" are the default).\n\n    Parameters:\n     - opener - opening character for a nested list\n       (default= ``\"(\"``); can also be a pyparsing expression\n     - closer - closing character for a nested list\n       (default= ``\")\"``); can also be a pyparsing expression\n     - content - expression for items within the nested lists\n       (default= ``None``)\n     - ignoreExpr - expression for ignoring opening and closing\n       delimiters (default= :class:`quotedString`)\n\n    If an expression is not provided for the content argument, the\n    nested expression will capture all whitespace-delimited content\n    between delimiters as a list of separate values.\n\n    Use the ``ignoreExpr`` argument to define expressions that may\n    contain opening or closing characters that should not be treated as\n    opening or closing characters for nesting, such as quotedString or\n    a comment expression.  Specify multiple expressions using an\n    :class:`Or` or :class:`MatchFirst`. The default is\n    :class:`quotedString`, but if no expressions are to be ignored, then\n    pass ``None`` for this argument.\n\n    Example::\n\n        data_type = oneOf(\"void int short long char float double\")\n        decl_data_type = Combine(data_type + Optional(Word('*')))\n        ident = Word(alphas+'_', alphanums+'_')\n        number = pyparsing_common.number\n        arg = Group(decl_data_type + ident)\n        LPAR,RPAR = map(Suppress, \"()\")\n\n        code_body = nestedExpr('{', '}', ignoreExpr=(quotedString | cStyleComment))\n\n        c_function = (decl_data_type(\"type\")\n                      + ident(\"name\")\n                      + LPAR + Optional(delimitedList(arg), [])(\"args\") + RPAR\n                      + code_body(\"body\"))\n        c_function.ignore(cStyleComment)\n\n        source_code = '''\n            int is_odd(int x) {\n                return (x%2);\n            }\n\n            int dec_to_hex(char hchar) {\n                if (hchar >= '0' && hchar <= '9') {\n                    return (ord(hchar)-ord('0'));\n                } else {\n                    return (10+ord(hchar)-ord('A'));\n                }\n            }\n        '''\n        for func in c_function.searchString(source_code):\n            print(\"%(name)s (%(type)s) args: %(args)s\" % func)\n\n\n    prints::\n\n        is_odd (int) args: [['int', 'x']]\n        dec_to_hex (int) args: [['char', 'hchar']]\n    \"\"\"\n    if opener == closer:\n        raise ValueError(\"opening and closing strings cannot be the same\")\n    if content is None:\n        if isinstance(opener,basestring) and isinstance(closer,basestring):\n            if len(opener) == 1 and len(closer)==1:\n                if ignoreExpr is not None:\n                    content = (Combine(OneOrMore(~ignoreExpr +\n                                    CharsNotIn(opener+closer+ParserElement.DEFAULT_WHITE_CHARS,exact=1))\n                                ).setParseAction(lambda t:t[0].strip()))\n                else:\n                    content = (empty.copy()+CharsNotIn(opener+closer+ParserElement.DEFAULT_WHITE_CHARS\n                                ).setParseAction(lambda t:t[0].strip()))\n            else:\n                if ignoreExpr is not None:\n                    content = (Combine(OneOrMore(~ignoreExpr +\n                                    ~Literal(opener) + ~Literal(closer) +\n                                    CharsNotIn(ParserElement.DEFAULT_WHITE_CHARS,exact=1))\n                                ).setParseAction(lambda t:t[0].strip()))\n                else:\n                    content = (Combine(OneOrMore(~Literal(opener) + ~Literal(closer) +\n                                    CharsNotIn(ParserElement.DEFAULT_WHITE_CHARS,exact=1))\n                                ).setParseAction(lambda t:t[0].strip()))\n        else:\n            raise ValueError(\"opening and closing arguments must be strings if no content expression is given\")\n    ret = Forward()\n    if ignoreExpr is not None:\n        ret <<= Group( Suppress(opener) + ZeroOrMore( ignoreExpr | ret | content ) + Suppress(closer) )\n    else:\n        ret <<= Group( Suppress(opener) + ZeroOrMore( ret | content )  + Suppress(closer) )\n    ret.setName('nested %s%s expression' % (opener,closer))\n    return ret\n\ndef indentedBlock(blockStatementExpr, indentStack, indent=True):\n    \"\"\"Helper method for defining space-delimited indentation blocks,\n    such as those used to define block statements in Python source code.\n\n    Parameters:\n\n     - blockStatementExpr - expression defining syntax of statement that\n       is repeated within the indented block\n     - indentStack - list created by caller to manage indentation stack\n       (multiple statementWithIndentedBlock expressions within a single\n       grammar should share a common indentStack)\n     - indent - boolean indicating whether block must be indented beyond\n       the the current level; set to False for block of left-most\n       statements (default= ``True``)\n\n    A valid block must contain at least one ``blockStatement``.\n\n    Example::\n\n        data = '''\n        def A(z):\n          A1\n          B = 100\n          G = A2\n          A2\n          A3\n        B\n        def BB(a,b,c):\n          BB1\n          def BBA():\n            bba1\n            bba2\n            bba3\n        C\n        D\n        def spam(x,y):\n             def eggs(z):\n                 pass\n        '''\n\n\n        indentStack = [1]\n        stmt = Forward()\n\n        identifier = Word(alphas, alphanums)\n        funcDecl = (\"def\" + identifier + Group( \"(\" + Optional( delimitedList(identifier) ) + \")\" ) + \":\")\n        func_body = indentedBlock(stmt, indentStack)\n        funcDef = Group( funcDecl + func_body )\n\n        rvalue = Forward()\n        funcCall = Group(identifier + \"(\" + Optional(delimitedList(rvalue)) + \")\")\n        rvalue << (funcCall | identifier | Word(nums))\n        assignment = Group(identifier + \"=\" + rvalue)\n        stmt << ( funcDef | assignment | identifier )\n\n        module_body = OneOrMore(stmt)\n\n        parseTree = module_body.parseString(data)\n        parseTree.pprint()\n\n    prints::\n\n        [['def',\n          'A',\n          ['(', 'z', ')'],\n          ':',\n          [['A1'], [['B', '=', '100']], [['G', '=', 'A2']], ['A2'], ['A3']]],\n         'B',\n         ['def',\n          'BB',\n          ['(', 'a', 'b', 'c', ')'],\n          ':',\n          [['BB1'], [['def', 'BBA', ['(', ')'], ':', [['bba1'], ['bba2'], ['bba3']]]]]],\n         'C',\n         'D',\n         ['def',\n          'spam',\n          ['(', 'x', 'y', ')'],\n          ':',\n          [[['def', 'eggs', ['(', 'z', ')'], ':', [['pass']]]]]]]\n    \"\"\"\n    def checkPeerIndent(s,l,t):\n        if l >= len(s): return\n        curCol = col(l,s)\n        if curCol != indentStack[-1]:\n            if curCol > indentStack[-1]:\n                raise ParseFatalException(s,l,\"illegal nesting\")\n            raise ParseException(s,l,\"not a peer entry\")\n\n    def checkSubIndent(s,l,t):\n        curCol = col(l,s)\n        if curCol > indentStack[-1]:\n            indentStack.append( curCol )\n        else:\n            raise ParseException(s,l,\"not a subentry\")\n\n    def checkUnindent(s,l,t):\n        if l >= len(s): return\n        curCol = col(l,s)\n        if not(indentStack and curCol < indentStack[-1] and curCol <= indentStack[-2]):\n            raise ParseException(s,l,\"not an unindent\")\n        indentStack.pop()\n\n    NL = OneOrMore(LineEnd().setWhitespaceChars(\"\\t \").suppress())\n    INDENT = (Empty() + Empty().setParseAction(checkSubIndent)).setName('INDENT')\n    PEER   = Empty().setParseAction(checkPeerIndent).setName('')\n    UNDENT = Empty().setParseAction(checkUnindent).setName('UNINDENT')\n    if indent:\n        smExpr = Group( Optional(NL) +\n            #~ FollowedBy(blockStatementExpr) +\n            INDENT + (OneOrMore( PEER + Group(blockStatementExpr) + Optional(NL) )) + UNDENT)\n    else:\n        smExpr = Group( Optional(NL) +\n            (OneOrMore( PEER + Group(blockStatementExpr) + Optional(NL) )) )\n    blockStatementExpr.ignore(_bslash + LineEnd())\n    return smExpr.setName('indented block')\n\nalphas8bit = srange(r\"[\\0xc0-\\0xd6\\0xd8-\\0xf6\\0xf8-\\0xff]\")\npunc8bit = srange(r\"[\\0xa1-\\0xbf\\0xd7\\0xf7]\")\n\nanyOpenTag,anyCloseTag = makeHTMLTags(Word(alphas,alphanums+\"_:\").setName('any tag'))\n_htmlEntityMap = dict(zip(\"gt lt amp nbsp quot apos\".split(),'><& \"\\''))\ncommonHTMLEntity = Regex('&(?P<entity>' + '|'.join(_htmlEntityMap.keys()) +\");\").setName(\"common HTML entity\")\ndef replaceHTMLEntity(t):\n    \"\"\"Helper parser action to replace common HTML entities with their special characters\"\"\"\n    return _htmlEntityMap.get(t.entity)\n\n# it's easy to get these comment structures wrong - they're very common, so may as well make them available\ncStyleComment = Combine(Regex(r\"/\\*(?:[^*]|\\*(?!/))*\") + '*/').setName(\"C style comment\")\n\"Comment of the form ``/* ... */``\"\n\nhtmlComment = Regex(r\"<!--[\\s\\S]*?-->\").setName(\"HTML comment\")\n\"Comment of the form ``<!-- ... -->``\"\n\nrestOfLine = Regex(r\".*\").leaveWhitespace().setName(\"rest of line\")\ndblSlashComment = Regex(r\"//(?:\\\\\\n|[^\\n])*\").setName(\"// comment\")\n\"Comment of the form ``// ... (to end of line)``\"\n\ncppStyleComment = Combine(Regex(r\"/\\*(?:[^*]|\\*(?!/))*\") + '*/'| dblSlashComment).setName(\"C++ style comment\")\n\"Comment of either form :class:`cStyleComment` or :class:`dblSlashComment`\"\n\njavaStyleComment = cppStyleComment\n\"Same as :class:`cppStyleComment`\"\n\npythonStyleComment = Regex(r\"#.*\").setName(\"Python style comment\")\n\"Comment of the form ``# ... (to end of line)``\"\n\n_commasepitem = Combine(OneOrMore(Word(printables, excludeChars=',') +\n                                  Optional( Word(\" \\t\") +\n                                            ~Literal(\",\") + ~LineEnd() ) ) ).streamline().setName(\"commaItem\")\ncommaSeparatedList = delimitedList( Optional( quotedString.copy() | _commasepitem, default=\"\") ).setName(\"commaSeparatedList\")\n\"\"\"(Deprecated) Predefined expression of 1 or more printable words or\nquoted strings, separated by commas.\n\nThis expression is deprecated in favor of :class:`pyparsing_common.comma_separated_list`.\n\"\"\"\n\n# some other useful expressions - using lower-case class name since we are really using this as a namespace\nclass pyparsing_common:\n    \"\"\"Here are some common low-level expressions that may be useful in\n    jump-starting parser development:\n\n     - numeric forms (:class:`integers<integer>`, :class:`reals<real>`,\n       :class:`scientific notation<sci_real>`)\n     - common :class:`programming identifiers<identifier>`\n     - network addresses (:class:`MAC<mac_address>`,\n       :class:`IPv4<ipv4_address>`, :class:`IPv6<ipv6_address>`)\n     - ISO8601 :class:`dates<iso8601_date>` and\n       :class:`datetime<iso8601_datetime>`\n     - :class:`UUID<uuid>`\n     - :class:`comma-separated list<comma_separated_list>`\n\n    Parse actions:\n\n     - :class:`convertToInteger`\n     - :class:`convertToFloat`\n     - :class:`convertToDate`\n     - :class:`convertToDatetime`\n     - :class:`stripHTMLTags`\n     - :class:`upcaseTokens`\n     - :class:`downcaseTokens`\n\n    Example::\n\n        pyparsing_common.number.runTests('''\n            # any int or real number, returned as the appropriate type\n            100\n            -100\n            +100\n            3.14159\n            6.02e23\n            1e-12\n            ''')\n\n        pyparsing_common.fnumber.runTests('''\n            # any int or real number, returned as float\n            100\n            -100\n            +100\n            3.14159\n            6.02e23\n            1e-12\n            ''')\n\n        pyparsing_common.hex_integer.runTests('''\n            # hex numbers\n            100\n            FF\n            ''')\n\n        pyparsing_common.fraction.runTests('''\n            # fractions\n            1/2\n            -3/4\n            ''')\n\n        pyparsing_common.mixed_integer.runTests('''\n            # mixed fractions\n            1\n            1/2\n            -3/4\n            1-3/4\n            ''')\n\n        import uuid\n        pyparsing_common.uuid.setParseAction(tokenMap(uuid.UUID))\n        pyparsing_common.uuid.runTests('''\n            # uuid\n            12345678-1234-5678-1234-567812345678\n            ''')\n\n    prints::\n\n        # any int or real number, returned as the appropriate type\n        100\n        [100]\n\n        -100\n        [-100]\n\n        +100\n        [100]\n\n        3.14159\n        [3.14159]\n\n        6.02e23\n        [6.02e+23]\n\n        1e-12\n        [1e-12]\n\n        # any int or real number, returned as float\n        100\n        [100.0]\n\n        -100\n        [-100.0]\n\n        +100\n        [100.0]\n\n        3.14159\n        [3.14159]\n\n        6.02e23\n        [6.02e+23]\n\n        1e-12\n        [1e-12]\n\n        # hex numbers\n        100\n        [256]\n\n        FF\n        [255]\n\n        # fractions\n        1/2\n        [0.5]\n\n        -3/4\n        [-0.75]\n\n        # mixed fractions\n        1\n        [1]\n\n        1/2\n        [0.5]\n\n        -3/4\n        [-0.75]\n\n        1-3/4\n        [1.75]\n\n        # uuid\n        12345678-1234-5678-1234-567812345678\n        [UUID('12345678-1234-5678-1234-567812345678')]\n    \"\"\"\n\n    convertToInteger = tokenMap(int)\n    \"\"\"\n    Parse action for converting parsed integers to Python int\n    \"\"\"\n\n    convertToFloat = tokenMap(float)\n    \"\"\"\n    Parse action for converting parsed numbers to Python float\n    \"\"\"\n\n    integer = Word(nums).setName(\"integer\").setParseAction(convertToInteger)\n    \"\"\"expression that parses an unsigned integer, returns an int\"\"\"\n\n    hex_integer = Word(hexnums).setName(\"hex integer\").setParseAction(tokenMap(int,16))\n    \"\"\"expression that parses a hexadecimal integer, returns an int\"\"\"\n\n    signed_integer = Regex(r'[+-]?\\d+').setName(\"signed integer\").setParseAction(convertToInteger)\n    \"\"\"expression that parses an integer with optional leading sign, returns an int\"\"\"\n\n    fraction = (signed_integer().setParseAction(convertToFloat) + '/' + signed_integer().setParseAction(convertToFloat)).setName(\"fraction\")\n    \"\"\"fractional expression of an integer divided by an integer, returns a float\"\"\"\n    fraction.addParseAction(lambda t: t[0]/t[-1])\n\n    mixed_integer = (fraction | signed_integer + Optional(Optional('-').suppress() + fraction)).setName(\"fraction or mixed integer-fraction\")\n    \"\"\"mixed integer of the form 'integer - fraction', with optional leading integer, returns float\"\"\"\n    mixed_integer.addParseAction(sum)\n\n    real = Regex(r'[+-]?\\d+\\.\\d*').setName(\"real number\").setParseAction(convertToFloat)\n    \"\"\"expression that parses a floating point number and returns a float\"\"\"\n\n    sci_real = Regex(r'[+-]?\\d+([eE][+-]?\\d+|\\.\\d*([eE][+-]?\\d+)?)').setName(\"real number with scientific notation\").setParseAction(convertToFloat)\n    \"\"\"expression that parses a floating point number with optional\n    scientific notation and returns a float\"\"\"\n\n    # streamlining this expression makes the docs nicer-looking\n    number = (sci_real | real | signed_integer).streamline()\n    \"\"\"any numeric expression, returns the corresponding Python type\"\"\"\n\n    fnumber = Regex(r'[+-]?\\d+\\.?\\d*([eE][+-]?\\d+)?').setName(\"fnumber\").setParseAction(convertToFloat)\n    \"\"\"any int or real number, returned as float\"\"\"\n\n    identifier = Word(alphas+'_', alphanums+'_').setName(\"identifier\")\n    \"\"\"typical code identifier (leading alpha or '_', followed by 0 or more alphas, nums, or '_')\"\"\"\n\n    ipv4_address = Regex(r'(25[0-5]|2[0-4][0-9]|1?[0-9]{1,2})(\\.(25[0-5]|2[0-4][0-9]|1?[0-9]{1,2})){3}').setName(\"IPv4 address\")\n    \"IPv4 address (``0.0.0.0 - 255.255.255.255``)\"\n\n    _ipv6_part = Regex(r'[0-9a-fA-F]{1,4}').setName(\"hex_integer\")\n    _full_ipv6_address = (_ipv6_part + (':' + _ipv6_part)*7).setName(\"full IPv6 address\")\n    _short_ipv6_address = (Optional(_ipv6_part + (':' + _ipv6_part)*(0,6)) + \"::\" + Optional(_ipv6_part + (':' + _ipv6_part)*(0,6))).setName(\"short IPv6 address\")\n    _short_ipv6_address.addCondition(lambda t: sum(1 for tt in t if pyparsing_common._ipv6_part.matches(tt)) < 8)\n    _mixed_ipv6_address = (\"::ffff:\" + ipv4_address).setName(\"mixed IPv6 address\")\n    ipv6_address = Combine((_full_ipv6_address | _mixed_ipv6_address | _short_ipv6_address).setName(\"IPv6 address\")).setName(\"IPv6 address\")\n    \"IPv6 address (long, short, or mixed form)\"\n\n    mac_address = Regex(r'[0-9a-fA-F]{2}([:.-])[0-9a-fA-F]{2}(?:\\1[0-9a-fA-F]{2}){4}').setName(\"MAC address\")\n    \"MAC address xx:xx:xx:xx:xx (may also have '-' or '.' delimiters)\"\n\n    @staticmethod\n    def convertToDate(fmt=\"%Y-%m-%d\"):\n        \"\"\"\n        Helper to create a parse action for converting parsed date string to Python datetime.date\n\n        Params -\n         - fmt - format to be passed to datetime.strptime (default= ``\"%Y-%m-%d\"``)\n\n        Example::\n\n            date_expr = pyparsing_common.iso8601_date.copy()\n            date_expr.setParseAction(pyparsing_common.convertToDate())\n            print(date_expr.parseString(\"1999-12-31\"))\n\n        prints::\n\n            [datetime.date(1999, 12, 31)]\n        \"\"\"\n        def cvt_fn(s,l,t):\n            try:\n                return datetime.strptime(t[0], fmt).date()\n            except ValueError as ve:\n                raise ParseException(s, l, str(ve))\n        return cvt_fn\n\n    @staticmethod\n    def convertToDatetime(fmt=\"%Y-%m-%dT%H:%M:%S.%f\"):\n        \"\"\"Helper to create a parse action for converting parsed\n        datetime string to Python datetime.datetime\n\n        Params -\n         - fmt - format to be passed to datetime.strptime (default= ``\"%Y-%m-%dT%H:%M:%S.%f\"``)\n\n        Example::\n\n            dt_expr = pyparsing_common.iso8601_datetime.copy()\n            dt_expr.setParseAction(pyparsing_common.convertToDatetime())\n            print(dt_expr.parseString(\"1999-12-31T23:59:59.999\"))\n\n        prints::\n\n            [datetime.datetime(1999, 12, 31, 23, 59, 59, 999000)]\n        \"\"\"\n        def cvt_fn(s,l,t):\n            try:\n                return datetime.strptime(t[0], fmt)\n            except ValueError as ve:\n                raise ParseException(s, l, str(ve))\n        return cvt_fn\n\n    iso8601_date = Regex(r'(?P<year>\\d{4})(?:-(?P<month>\\d\\d)(?:-(?P<day>\\d\\d))?)?').setName(\"ISO8601 date\")\n    \"ISO8601 date (``yyyy-mm-dd``)\"\n\n    iso8601_datetime = Regex(r'(?P<year>\\d{4})-(?P<month>\\d\\d)-(?P<day>\\d\\d)[T ](?P<hour>\\d\\d):(?P<minute>\\d\\d)(:(?P<second>\\d\\d(\\.\\d*)?)?)?(?P<tz>Z|[+-]\\d\\d:?\\d\\d)?').setName(\"ISO8601 datetime\")\n    \"ISO8601 datetime (``yyyy-mm-ddThh:mm:ss.s(Z|+-00:00)``) - trailing seconds, milliseconds, and timezone optional; accepts separating ``'T'`` or ``' '``\"\n\n    uuid = Regex(r'[0-9a-fA-F]{8}(-[0-9a-fA-F]{4}){3}-[0-9a-fA-F]{12}').setName(\"UUID\")\n    \"UUID (``xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx``)\"\n\n    _html_stripper = anyOpenTag.suppress() | anyCloseTag.suppress()\n    @staticmethod\n    def stripHTMLTags(s, l, tokens):\n        \"\"\"Parse action to remove HTML tags from web page HTML source\n\n        Example::\n\n            # strip HTML links from normal text\n            text = '<td>More info at the <a href=\"https://github.com/pyparsing/pyparsing/wiki\">pyparsing</a> wiki page</td>'\n            td,td_end = makeHTMLTags(\"TD\")\n            table_text = td + SkipTo(td_end).setParseAction(pyparsing_common.stripHTMLTags)(\"body\") + td_end\n            print(table_text.parseString(text).body)\n\n        Prints::\n\n            More info at the pyparsing wiki page\n        \"\"\"\n        return pyparsing_common._html_stripper.transformString(tokens[0])\n\n    _commasepitem = Combine(OneOrMore(~Literal(\",\") + ~LineEnd() + Word(printables, excludeChars=',')\n                                        + Optional( White(\" \\t\") ) ) ).streamline().setName(\"commaItem\")\n    comma_separated_list = delimitedList( Optional( quotedString.copy() | _commasepitem, default=\"\") ).setName(\"comma separated list\")\n    \"\"\"Predefined expression of 1 or more printable words or quoted strings, separated by commas.\"\"\"\n\n    upcaseTokens = staticmethod(tokenMap(lambda t: _ustr(t).upper()))\n    \"\"\"Parse action to convert tokens to upper case.\"\"\"\n\n    downcaseTokens = staticmethod(tokenMap(lambda t: _ustr(t).lower()))\n    \"\"\"Parse action to convert tokens to lower case.\"\"\"\n\n\nclass _lazyclassproperty(object):\n    def __init__(self, fn):\n        self.fn = fn\n        self.__doc__ = fn.__doc__\n        self.__name__ = fn.__name__\n\n    def __get__(self, obj, cls):\n        if cls is None:\n            cls = type(obj)\n        if not hasattr(cls, '_intern') or any(cls._intern is getattr(superclass, '_intern', []) for superclass in cls.__mro__[1:]):\n            cls._intern = {}\n        attrname = self.fn.__name__\n        if attrname not in cls._intern:\n            cls._intern[attrname] = self.fn(cls)\n        return cls._intern[attrname]\n\n\nclass unicode_set(object):\n    \"\"\"\n    A set of Unicode characters, for language-specific strings for\n    ``alphas``, ``nums``, ``alphanums``, and ``printables``.\n    A unicode_set is defined by a list of ranges in the Unicode character\n    set, in a class attribute ``_ranges``, such as::\n\n        _ranges = [(0x0020, 0x007e), (0x00a0, 0x00ff),]\n\n    A unicode set can also be defined using multiple inheritance of other unicode sets::\n\n        class CJK(Chinese, Japanese, Korean):\n            pass\n    \"\"\"\n    _ranges = []\n\n    @classmethod\n    def _get_chars_for_ranges(cls):\n        ret = []\n        for cc in cls.__mro__:\n            if cc is unicode_set:\n                break\n            for rr in cc._ranges:\n                ret.extend(range(rr[0], rr[-1]+1))\n        return [unichr(c) for c in sorted(set(ret))]\n\n    @_lazyclassproperty\n    def printables(cls):\n        \"all non-whitespace characters in this range\"\n        return u''.join(filterfalse(unicode.isspace, cls._get_chars_for_ranges()))\n\n    @_lazyclassproperty\n    def alphas(cls):\n        \"all alphabetic characters in this range\"\n        return u''.join(filter(unicode.isalpha, cls._get_chars_for_ranges()))\n\n    @_lazyclassproperty\n    def nums(cls):\n        \"all numeric digit characters in this range\"\n        return u''.join(filter(unicode.isdigit, cls._get_chars_for_ranges()))\n\n    @_lazyclassproperty\n    def alphanums(cls):\n        \"all alphanumeric characters in this range\"\n        return cls.alphas + cls.nums\n\n\nclass pyparsing_unicode(unicode_set):\n    \"\"\"\n    A namespace class for defining common language unicode_sets.\n    \"\"\"\n    _ranges = [(32, sys.maxunicode)]\n\n    class Latin1(unicode_set):\n        \"Unicode set for Latin-1 Unicode Character Range\"\n        _ranges = [(0x0020, 0x007e), (0x00a0, 0x00ff),]\n\n    class LatinA(unicode_set):\n        \"Unicode set for Latin-A Unicode Character Range\"\n        _ranges = [(0x0100, 0x017f),]\n\n    class LatinB(unicode_set):\n        \"Unicode set for Latin-B Unicode Character Range\"\n        _ranges = [(0x0180, 0x024f),]\n\n    class Greek(unicode_set):\n        \"Unicode set for Greek Unicode Character Ranges\"\n        _ranges = [\n            (0x0370, 0x03ff), (0x1f00, 0x1f15), (0x1f18, 0x1f1d), (0x1f20, 0x1f45), (0x1f48, 0x1f4d),\n            (0x1f50, 0x1f57), (0x1f59,), (0x1f5b,), (0x1f5d,), (0x1f5f, 0x1f7d), (0x1f80, 0x1fb4), (0x1fb6, 0x1fc4),\n            (0x1fc6, 0x1fd3), (0x1fd6, 0x1fdb), (0x1fdd, 0x1fef), (0x1ff2, 0x1ff4), (0x1ff6, 0x1ffe),\n        ]\n\n    class Cyrillic(unicode_set):\n        \"Unicode set for Cyrillic Unicode Character Range\"\n        _ranges = [(0x0400, 0x04ff)]\n\n    class Chinese(unicode_set):\n        \"Unicode set for Chinese Unicode Character Range\"\n        _ranges = [(0x4e00, 0x9fff), (0x3000, 0x303f), ]\n\n    class Japanese(unicode_set):\n        \"Unicode set for Japanese Unicode Character Range, combining Kanji, Hiragana, and Katakana ranges\"\n        _ranges = [ ]\n\n        class Kanji(unicode_set):\n            \"Unicode set for Kanji Unicode Character Range\"\n            _ranges = [(0x4E00, 0x9Fbf), (0x3000, 0x303f), ]\n\n        class Hiragana(unicode_set):\n            \"Unicode set for Hiragana Unicode Character Range\"\n            _ranges = [(0x3040, 0x309f), ]\n\n        class Katakana(unicode_set):\n            \"Unicode set for Katakana  Unicode Character Range\"\n            _ranges = [(0x30a0, 0x30ff), ]\n\n    class Korean(unicode_set):\n        \"Unicode set for Korean Unicode Character Range\"\n        _ranges = [(0xac00, 0xd7af), (0x1100, 0x11ff), (0x3130, 0x318f), (0xa960, 0xa97f), (0xd7b0, 0xd7ff), (0x3000, 0x303f), ]\n\n    class CJK(Chinese, Japanese, Korean):\n        \"Unicode set for combined Chinese, Japanese, and Korean (CJK) Unicode Character Range\"\n        pass\n\n    class Thai(unicode_set):\n        \"Unicode set for Thai Unicode Character Range\"\n        _ranges = [(0x0e01, 0x0e3a), (0x0e3f, 0x0e5b), ]\n\n    class Arabic(unicode_set):\n        \"Unicode set for Arabic Unicode Character Range\"\n        _ranges = [(0x0600, 0x061b), (0x061e, 0x06ff), (0x0700, 0x077f), ]\n\n    class Hebrew(unicode_set):\n        \"Unicode set for Hebrew Unicode Character Range\"\n        _ranges = [(0x0590, 0x05ff), ]\n\n    class Devanagari(unicode_set):\n        \"Unicode set for Devanagari Unicode Character Range\"\n        _ranges = [(0x0900, 0x097f), (0xa8e0, 0xa8ff)]\n\npyparsing_unicode.Japanese._ranges = (pyparsing_unicode.Japanese.Kanji._ranges\n                                      + pyparsing_unicode.Japanese.Hiragana._ranges\n                                      + pyparsing_unicode.Japanese.Katakana._ranges)\n\n# define ranges in language character sets\nif PY_3:\n    setattr(pyparsing_unicode, \"العربية\", pyparsing_unicode.Arabic)\n    setattr(pyparsing_unicode, \"中文\", pyparsing_unicode.Chinese)\n    setattr(pyparsing_unicode, \"кириллица\", pyparsing_unicode.Cyrillic)\n    setattr(pyparsing_unicode, \"Ελληνικά\", pyparsing_unicode.Greek)\n    setattr(pyparsing_unicode, \"עִברִית\", pyparsing_unicode.Hebrew)\n    setattr(pyparsing_unicode, \"日本語\", pyparsing_unicode.Japanese)\n    setattr(pyparsing_unicode.Japanese, \"漢字\", pyparsing_unicode.Japanese.Kanji)\n    setattr(pyparsing_unicode.Japanese, \"カタカナ\", pyparsing_unicode.Japanese.Katakana)\n    setattr(pyparsing_unicode.Japanese, \"ひらがな\", pyparsing_unicode.Japanese.Hiragana)\n    setattr(pyparsing_unicode, \"한국어\", pyparsing_unicode.Korean)\n    setattr(pyparsing_unicode, \"ไทย\", pyparsing_unicode.Thai)\n    setattr(pyparsing_unicode, \"देवनागरी\", pyparsing_unicode.Devanagari)\n\n\nif __name__ == \"__main__\":\n\n    selectToken    = CaselessLiteral(\"select\")\n    fromToken      = CaselessLiteral(\"from\")\n\n    ident          = Word(alphas, alphanums + \"_$\")\n\n    columnName     = delimitedList(ident, \".\", combine=True).setParseAction(upcaseTokens)\n    columnNameList = Group(delimitedList(columnName)).setName(\"columns\")\n    columnSpec     = ('*' | columnNameList)\n\n    tableName      = delimitedList(ident, \".\", combine=True).setParseAction(upcaseTokens)\n    tableNameList  = Group(delimitedList(tableName)).setName(\"tables\")\n\n    simpleSQL      = selectToken(\"command\") + columnSpec(\"columns\") + fromToken + tableNameList(\"tables\")\n\n    # demo runTests method, including embedded comments in test string\n    simpleSQL.runTests(\"\"\"\n        # '*' as column list and dotted table name\n        select * from SYS.XYZZY\n\n        # caseless match on \"SELECT\", and casts back to \"select\"\n        SELECT * from XYZZY, ABC\n\n        # list of column names, and mixed case SELECT keyword\n        Select AA,BB,CC from Sys.dual\n\n        # multiple tables\n        Select A, B, C from Sys.dual, Table2\n\n        # invalid SELECT keyword - should fail\n        Xelect A, B, C from Sys.dual\n\n        # incomplete command - should fail\n        Select\n\n        # invalid column name - should fail\n        Select ^^^ frox Sys.dual\n\n        \"\"\")\n\n    pyparsing_common.number.runTests(\"\"\"\n        100\n        -100\n        +100\n        3.14159\n        6.02e23\n        1e-12\n        \"\"\")\n\n    # any int or real number, returned as float\n    pyparsing_common.fnumber.runTests(\"\"\"\n        100\n        -100\n        +100\n        3.14159\n        6.02e23\n        1e-12\n        \"\"\")\n\n    pyparsing_common.hex_integer.runTests(\"\"\"\n        100\n        FF\n        \"\"\")\n\n    import uuid\n    pyparsing_common.uuid.setParseAction(tokenMap(uuid.UUID))\n    pyparsing_common.uuid.runTests(\"\"\"\n        12345678-1234-5678-1234-567812345678\n        \"\"\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pytoml/__init__.py",
    "content": "from .core import TomlError\nfrom .parser import load, loads\nfrom .test import translate_to_test\nfrom .writer import dump, dumps"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pytoml/core.py",
    "content": "class TomlError(RuntimeError):\n    def __init__(self, message, line, col, filename):\n        RuntimeError.__init__(self, message, line, col, filename)\n        self.message = message\n        self.line = line\n        self.col = col\n        self.filename = filename\n\n    def __str__(self):\n        return '{}({}, {}): {}'.format(self.filename, self.line, self.col, self.message)\n\n    def __repr__(self):\n        return 'TomlError({!r}, {!r}, {!r}, {!r})'.format(self.message, self.line, self.col, self.filename)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pytoml/parser.py",
    "content": "import string, re, sys, datetime\nfrom .core import TomlError\nfrom .utils import rfc3339_re, parse_rfc3339_re\n\nif sys.version_info[0] == 2:\n    _chr = unichr\nelse:\n    _chr = chr\n\ndef load(fin, translate=lambda t, x, v: v, object_pairs_hook=dict):\n    return loads(fin.read(), translate=translate, object_pairs_hook=object_pairs_hook, filename=getattr(fin, 'name', repr(fin)))\n\ndef loads(s, filename='<string>', translate=lambda t, x, v: v, object_pairs_hook=dict):\n    if isinstance(s, bytes):\n        s = s.decode('utf-8')\n\n    s = s.replace('\\r\\n', '\\n')\n\n    root = object_pairs_hook()\n    tables = object_pairs_hook()\n    scope = root\n\n    src = _Source(s, filename=filename)\n    ast = _p_toml(src, object_pairs_hook=object_pairs_hook)\n\n    def error(msg):\n        raise TomlError(msg, pos[0], pos[1], filename)\n\n    def process_value(v, object_pairs_hook):\n        kind, text, value, pos = v\n        if kind == 'str' and value.startswith('\\n'):\n            value = value[1:]\n        if kind == 'array':\n            if value and any(k != value[0][0] for k, t, v, p in value[1:]):\n                error('array-type-mismatch')\n            value = [process_value(item, object_pairs_hook=object_pairs_hook) for item in value]\n        elif kind == 'table':\n            value = object_pairs_hook([(k, process_value(value[k], object_pairs_hook=object_pairs_hook)) for k in value])\n        return translate(kind, text, value)\n\n    for kind, value, pos in ast:\n        if kind == 'kv':\n            k, v = value\n            if k in scope:\n                error('duplicate_keys. Key \"{0}\" was used more than once.'.format(k))\n            scope[k] = process_value(v, object_pairs_hook=object_pairs_hook)\n        else:\n            is_table_array = (kind == 'table_array')\n            cur = tables\n            for name in value[:-1]:\n                if isinstance(cur.get(name), list):\n                    d, cur = cur[name][-1]\n                else:\n                    d, cur = cur.setdefault(name, (None, object_pairs_hook()))\n\n            scope = object_pairs_hook()\n            name = value[-1]\n            if name not in cur:\n                if is_table_array:\n                    cur[name] = [(scope, object_pairs_hook())]\n                else:\n                    cur[name] = (scope, object_pairs_hook())\n            elif isinstance(cur[name], list):\n                if not is_table_array:\n                    error('table_type_mismatch')\n                cur[name].append((scope, object_pairs_hook()))\n            else:\n                if is_table_array:\n                    error('table_type_mismatch')\n                old_scope, next_table = cur[name]\n                if old_scope is not None:\n                    error('duplicate_tables')\n                cur[name] = (scope, next_table)\n\n    def merge_tables(scope, tables):\n        if scope is None:\n            scope = object_pairs_hook()\n        for k in tables:\n            if k in scope:\n                error('key_table_conflict')\n            v = tables[k]\n            if isinstance(v, list):\n                scope[k] = [merge_tables(sc, tbl) for sc, tbl in v]\n            else:\n                scope[k] = merge_tables(v[0], v[1])\n        return scope\n\n    return merge_tables(root, tables)\n\nclass _Source:\n    def __init__(self, s, filename=None):\n        self.s = s\n        self._pos = (1, 1)\n        self._last = None\n        self._filename = filename\n        self.backtrack_stack = []\n\n    def last(self):\n        return self._last\n\n    def pos(self):\n        return self._pos\n\n    def fail(self):\n        return self._expect(None)\n\n    def consume_dot(self):\n        if self.s:\n            self._last = self.s[0]\n            self.s = self[1:]\n            self._advance(self._last)\n            return self._last\n        return None\n\n    def expect_dot(self):\n        return self._expect(self.consume_dot())\n\n    def consume_eof(self):\n        if not self.s:\n            self._last = ''\n            return True\n        return False\n\n    def expect_eof(self):\n        return self._expect(self.consume_eof())\n\n    def consume(self, s):\n        if self.s.startswith(s):\n            self.s = self.s[len(s):]\n            self._last = s\n            self._advance(s)\n            return True\n        return False\n\n    def expect(self, s):\n        return self._expect(self.consume(s))\n\n    def consume_re(self, re):\n        m = re.match(self.s)\n        if m:\n            self.s = self.s[len(m.group(0)):]\n            self._last = m\n            self._advance(m.group(0))\n            return m\n        return None\n\n    def expect_re(self, re):\n        return self._expect(self.consume_re(re))\n\n    def __enter__(self):\n        self.backtrack_stack.append((self.s, self._pos))\n\n    def __exit__(self, type, value, traceback):\n        if type is None:\n            self.backtrack_stack.pop()\n        else:\n            self.s, self._pos = self.backtrack_stack.pop()\n        return type == TomlError\n\n    def commit(self):\n        self.backtrack_stack[-1] = (self.s, self._pos)\n\n    def _expect(self, r):\n        if not r:\n            raise TomlError('msg', self._pos[0], self._pos[1], self._filename)\n        return r\n\n    def _advance(self, s):\n        suffix_pos = s.rfind('\\n')\n        if suffix_pos == -1:\n            self._pos = (self._pos[0], self._pos[1] + len(s))\n        else:\n            self._pos = (self._pos[0] + s.count('\\n'), len(s) - suffix_pos)\n\n_ews_re = re.compile(r'(?:[ \\t]|#[^\\n]*\\n|#[^\\n]*\\Z|\\n)*')\ndef _p_ews(s):\n    s.expect_re(_ews_re)\n\n_ws_re = re.compile(r'[ \\t]*')\ndef _p_ws(s):\n    s.expect_re(_ws_re)\n\n_escapes = { 'b': '\\b', 'n': '\\n', 'r': '\\r', 't': '\\t', '\"': '\"',\n    '\\\\': '\\\\', 'f': '\\f' }\n\n_basicstr_re = re.compile(r'[^\"\\\\\\000-\\037]*')\n_short_uni_re = re.compile(r'u([0-9a-fA-F]{4})')\n_long_uni_re = re.compile(r'U([0-9a-fA-F]{8})')\n_escapes_re = re.compile(r'[btnfr\\\"\\\\]')\n_newline_esc_re = re.compile('\\n[ \\t\\n]*')\ndef _p_basicstr_content(s, content=_basicstr_re):\n    res = []\n    while True:\n        res.append(s.expect_re(content).group(0))\n        if not s.consume('\\\\'):\n            break\n        if s.consume_re(_newline_esc_re):\n            pass\n        elif s.consume_re(_short_uni_re) or s.consume_re(_long_uni_re):\n            v = int(s.last().group(1), 16)\n            if 0xd800 <= v < 0xe000:\n                s.fail()\n            res.append(_chr(v))\n        else:\n            s.expect_re(_escapes_re)\n            res.append(_escapes[s.last().group(0)])\n    return ''.join(res)\n\n_key_re = re.compile(r'[0-9a-zA-Z-_]+')\ndef _p_key(s):\n    with s:\n        s.expect('\"')\n        r = _p_basicstr_content(s, _basicstr_re)\n        s.expect('\"')\n        return r\n    if s.consume('\\''):\n        if s.consume('\\'\\''):\n            r = s.expect_re(_litstr_ml_re).group(0)\n            s.expect('\\'\\'\\'')\n        else:\n            r = s.expect_re(_litstr_re).group(0)\n            s.expect('\\'')\n        return r\n    return s.expect_re(_key_re).group(0)\n\n_float_re = re.compile(r'[+-]?(?:0|[1-9](?:_?\\d)*)(?:\\.\\d(?:_?\\d)*)?(?:[eE][+-]?(?:\\d(?:_?\\d)*))?')\n\n_basicstr_ml_re = re.compile(r'(?:\"\"?(?!\")|[^\"\\\\\\000-\\011\\013-\\037])*')\n_litstr_re = re.compile(r\"[^'\\000\\010\\012-\\037]*\")\n_litstr_ml_re = re.compile(r\"(?:(?:|'|'')(?:[^'\\000-\\010\\013-\\037]))*\")\ndef _p_value(s, object_pairs_hook):\n    pos = s.pos()\n\n    if s.consume('true'):\n        return 'bool', s.last(), True, pos\n    if s.consume('false'):\n        return 'bool', s.last(), False, pos\n\n    if s.consume('\"'):\n        if s.consume('\"\"'):\n            r = _p_basicstr_content(s, _basicstr_ml_re)\n            s.expect('\"\"\"')\n        else:\n            r = _p_basicstr_content(s, _basicstr_re)\n            s.expect('\"')\n        return 'str', r, r, pos\n\n    if s.consume('\\''):\n        if s.consume('\\'\\''):\n            r = s.expect_re(_litstr_ml_re).group(0)\n            s.expect('\\'\\'\\'')\n        else:\n            r = s.expect_re(_litstr_re).group(0)\n            s.expect('\\'')\n        return 'str', r, r, pos\n\n    if s.consume_re(rfc3339_re):\n        m = s.last()\n        return 'datetime', m.group(0), parse_rfc3339_re(m), pos\n\n    if s.consume_re(_float_re):\n        m = s.last().group(0)\n        r = m.replace('_','')\n        if '.' in m or 'e' in m or 'E' in m:\n            return 'float', m, float(r), pos\n        else:\n            return 'int', m, int(r, 10), pos\n\n    if s.consume('['):\n        items = []\n        with s:\n            while True:\n                _p_ews(s)\n                items.append(_p_value(s, object_pairs_hook=object_pairs_hook))\n                s.commit()\n                _p_ews(s)\n                s.expect(',')\n                s.commit()\n        _p_ews(s)\n        s.expect(']')\n        return 'array', None, items, pos\n\n    if s.consume('{'):\n        _p_ws(s)\n        items = object_pairs_hook()\n        if not s.consume('}'):\n            k = _p_key(s)\n            _p_ws(s)\n            s.expect('=')\n            _p_ws(s)\n            items[k] = _p_value(s, object_pairs_hook=object_pairs_hook)\n            _p_ws(s)\n            while s.consume(','):\n                _p_ws(s)\n                k = _p_key(s)\n                _p_ws(s)\n                s.expect('=')\n                _p_ws(s)\n                items[k] = _p_value(s, object_pairs_hook=object_pairs_hook)\n                _p_ws(s)\n            s.expect('}')\n        return 'table', None, items, pos\n\n    s.fail()\n\ndef _p_stmt(s, object_pairs_hook):\n    pos = s.pos()\n    if s.consume(   '['):\n        is_array = s.consume('[')\n        _p_ws(s)\n        keys = [_p_key(s)]\n        _p_ws(s)\n        while s.consume('.'):\n            _p_ws(s)\n            keys.append(_p_key(s))\n            _p_ws(s)\n        s.expect(']')\n        if is_array:\n            s.expect(']')\n        return 'table_array' if is_array else 'table', keys, pos\n\n    key = _p_key(s)\n    _p_ws(s)\n    s.expect('=')\n    _p_ws(s)\n    value = _p_value(s, object_pairs_hook=object_pairs_hook)\n    return 'kv', (key, value), pos\n\n_stmtsep_re = re.compile(r'(?:[ \\t]*(?:#[^\\n]*)?\\n)+[ \\t]*')\ndef _p_toml(s, object_pairs_hook):\n    stmts = []\n    _p_ews(s)\n    with s:\n        stmts.append(_p_stmt(s, object_pairs_hook=object_pairs_hook))\n        while True:\n            s.commit()\n            s.expect_re(_stmtsep_re)\n            stmts.append(_p_stmt(s, object_pairs_hook=object_pairs_hook))\n    _p_ews(s)\n    s.expect_eof()\n    return stmts\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pytoml/test.py",
    "content": "import datetime\nfrom .utils import format_rfc3339\n\ntry:\n    _string_types = (str, unicode)\n    _int_types = (int, long)\nexcept NameError:\n    _string_types = str\n    _int_types = int\n\ndef translate_to_test(v):\n    if isinstance(v, dict):\n        return { k: translate_to_test(v) for k, v in v.items() }\n    if isinstance(v, list):\n        a = [translate_to_test(x) for x in v]\n        if v and isinstance(v[0], dict):\n            return a\n        else:\n            return {'type': 'array', 'value': a}\n    if isinstance(v, datetime.datetime):\n        return {'type': 'datetime', 'value': format_rfc3339(v)}\n    if isinstance(v, bool):\n        return {'type': 'bool', 'value': 'true' if v else 'false'}\n    if isinstance(v, _int_types):\n        return {'type': 'integer', 'value': str(v)}\n    if isinstance(v, float):\n        return {'type': 'float', 'value': '{:.17}'.format(v)}\n    if isinstance(v, _string_types):\n        return {'type': 'string', 'value': v}\n    raise RuntimeError('unexpected value: {!r}'.format(v))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pytoml/utils.py",
    "content": "import datetime\nimport re\n\nrfc3339_re = re.compile(r'(\\d{4})-(\\d{2})-(\\d{2})T(\\d{2}):(\\d{2}):(\\d{2})(\\.\\d+)?(?:Z|([+-]\\d{2}):(\\d{2}))')\n\ndef parse_rfc3339(v):\n    m = rfc3339_re.match(v)\n    if not m or m.group(0) != v:\n        return None\n    return parse_rfc3339_re(m)\n\ndef parse_rfc3339_re(m):\n    r = map(int, m.groups()[:6])\n    if m.group(7):\n        micro = float(m.group(7))\n    else:\n        micro = 0\n\n    if m.group(8):\n        g = int(m.group(8), 10) * 60 + int(m.group(9), 10)\n        tz = _TimeZone(datetime.timedelta(0, g * 60))\n    else:\n        tz = _TimeZone(datetime.timedelta(0, 0))\n\n    y, m, d, H, M, S = r\n    return datetime.datetime(y, m, d, H, M, S, int(micro * 1000000), tz)\n\n\ndef format_rfc3339(v):\n    offs = v.utcoffset()\n    offs = int(offs.total_seconds()) // 60 if offs is not None else 0\n\n    if offs == 0:\n        suffix = 'Z'\n    else:\n        if offs > 0:\n            suffix = '+'\n        else:\n            suffix = '-'\n            offs = -offs\n        suffix = '{0}{1:02}:{2:02}'.format(suffix, offs // 60, offs % 60)\n\n    if v.microsecond:\n        return v.strftime('%Y-%m-%dT%H:%M:%S.%f') + suffix\n    else:\n        return v.strftime('%Y-%m-%dT%H:%M:%S') + suffix\n\nclass _TimeZone(datetime.tzinfo):\n    def __init__(self, offset):\n        self._offset = offset\n\n    def utcoffset(self, dt):\n        return self._offset\n\n    def dst(self, dt):\n        return None\n\n    def tzname(self, dt):\n        m = self._offset.total_seconds() // 60\n        if m < 0:\n            res = '-'\n            m = -m\n        else:\n            res = '+'\n        h = m // 60\n        m = m - h * 60\n        return '{}{:.02}{:.02}'.format(res, h, m)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/pytoml/writer.py",
    "content": "from __future__ import unicode_literals\nimport io, datetime, math, string, sys\n\nfrom .utils import format_rfc3339\n\nif sys.version_info[0] == 3:\n    long = int\n    unicode = str\n\n\ndef dumps(obj, sort_keys=False):\n    fout = io.StringIO()\n    dump(obj, fout, sort_keys=sort_keys)\n    return fout.getvalue()\n\n\n_escapes = {'\\n': 'n', '\\r': 'r', '\\\\': '\\\\', '\\t': 't', '\\b': 'b', '\\f': 'f', '\"': '\"'}\n\n\ndef _escape_string(s):\n    res = []\n    start = 0\n\n    def flush():\n        if start != i:\n            res.append(s[start:i])\n        return i + 1\n\n    i = 0\n    while i < len(s):\n        c = s[i]\n        if c in '\"\\\\\\n\\r\\t\\b\\f':\n            start = flush()\n            res.append('\\\\' + _escapes[c])\n        elif ord(c) < 0x20:\n            start = flush()\n            res.append('\\\\u%04x' % ord(c))\n        i += 1\n\n    flush()\n    return '\"' + ''.join(res) + '\"'\n\n\n_key_chars = string.digits + string.ascii_letters + '-_'\ndef _escape_id(s):\n    if any(c not in _key_chars for c in s):\n        return _escape_string(s)\n    return s\n\n\ndef _format_value(v):\n    if isinstance(v, bool):\n        return 'true' if v else 'false'\n    if isinstance(v, int) or isinstance(v, long):\n        return unicode(v)\n    if isinstance(v, float):\n        if math.isnan(v) or math.isinf(v):\n            raise ValueError(\"{0} is not a valid TOML value\".format(v))\n        else:\n            return repr(v)\n    elif isinstance(v, unicode) or isinstance(v, bytes):\n        return _escape_string(v)\n    elif isinstance(v, datetime.datetime):\n        return format_rfc3339(v)\n    elif isinstance(v, list):\n        return '[{0}]'.format(', '.join(_format_value(obj) for obj in v))\n    elif isinstance(v, dict):\n        return '{{{0}}}'.format(', '.join('{} = {}'.format(_escape_id(k), _format_value(obj)) for k, obj in v.items()))\n    else:\n        raise RuntimeError(v)\n\n\ndef dump(obj, fout, sort_keys=False):\n    tables = [((), obj, False)]\n\n    while tables:\n        name, table, is_array = tables.pop()\n        if name:\n            section_name = '.'.join(_escape_id(c) for c in name)\n            if is_array:\n                fout.write('[[{0}]]\\n'.format(section_name))\n            else:\n                fout.write('[{0}]\\n'.format(section_name))\n\n        table_keys = sorted(table.keys()) if sort_keys else table.keys()\n        new_tables = []\n        has_kv = False\n        for k in table_keys:\n            v = table[k]\n            if isinstance(v, dict):\n                new_tables.append((name + (k,), v, False))\n            elif isinstance(v, list) and v and all(isinstance(o, dict) for o in v):\n                new_tables.extend((name + (k,), d, True) for d in v)\n            elif v is None:\n                # based on mojombo's comment: https://github.com/toml-lang/toml/issues/146#issuecomment-25019344\n                fout.write(\n                    '#{} = null  # To use: uncomment and replace null with value\\n'.format(_escape_id(k)))\n                has_kv = True\n            else:\n                fout.write('{0} = {1}\\n'.format(_escape_id(k), _format_value(v)))\n                has_kv = True\n\n        tables.extend(reversed(new_tables))\n\n        if (name or has_kv) and tables:\n            fout.write('\\n')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/__init__.py",
    "content": "# -*- coding: utf-8 -*-\n\n#   __\n#  /__)  _  _     _   _ _/   _\n# / (   (- (/ (/ (- _)  /  _)\n#          /\n\n\"\"\"\nRequests HTTP Library\n~~~~~~~~~~~~~~~~~~~~~\n\nRequests is an HTTP library, written in Python, for human beings. Basic GET\nusage:\n\n   >>> import requests\n   >>> r = requests.get('https://www.python.org')\n   >>> r.status_code\n   200\n   >>> 'Python is a programming language' in r.content\n   True\n\n... or POST:\n\n   >>> payload = dict(key1='value1', key2='value2')\n   >>> r = requests.post('https://httpbin.org/post', data=payload)\n   >>> print(r.text)\n   {\n     ...\n     \"form\": {\n       \"key2\": \"value2\",\n       \"key1\": \"value1\"\n     },\n     ...\n   }\n\nThe other HTTP methods are supported - see `requests.api`. Full documentation\nis at <http://python-requests.org>.\n\n:copyright: (c) 2017 by Kenneth Reitz.\n:license: Apache 2.0, see LICENSE for more details.\n\"\"\"\n\nfrom pip._vendor import urllib3\nfrom pip._vendor import chardet\nimport warnings\nfrom .exceptions import RequestsDependencyWarning\n\n\ndef check_compatibility(urllib3_version, chardet_version):\n    urllib3_version = urllib3_version.split('.')\n    assert urllib3_version != ['dev']  # Verify urllib3 isn't installed from git.\n\n    # Sometimes, urllib3 only reports its version as 16.1.\n    if len(urllib3_version) == 2:\n        urllib3_version.append('0')\n\n    # Check urllib3 for compatibility.\n    major, minor, patch = urllib3_version  # noqa: F811\n    major, minor, patch = int(major), int(minor), int(patch)\n    # urllib3 >= 1.21.1, <= 1.24\n    assert major == 1\n    assert minor >= 21\n    assert minor <= 24\n\n    # Check chardet for compatibility.\n    major, minor, patch = chardet_version.split('.')[:3]\n    major, minor, patch = int(major), int(minor), int(patch)\n    # chardet >= 3.0.2, < 3.1.0\n    assert major == 3\n    assert minor < 1\n    assert patch >= 2\n\n\ndef _check_cryptography(cryptography_version):\n    # cryptography < 1.3.4\n    try:\n        cryptography_version = list(map(int, cryptography_version.split('.')))\n    except ValueError:\n        return\n\n    if cryptography_version < [1, 3, 4]:\n        warning = 'Old version of cryptography ({}) may cause slowdown.'.format(cryptography_version)\n        warnings.warn(warning, RequestsDependencyWarning)\n\n# Check imported dependencies for compatibility.\ntry:\n    check_compatibility(urllib3.__version__, chardet.__version__)\nexcept (AssertionError, ValueError):\n    warnings.warn(\"urllib3 ({}) or chardet ({}) doesn't match a supported \"\n                  \"version!\".format(urllib3.__version__, chardet.__version__),\n                  RequestsDependencyWarning)\n\n# Attempt to enable urllib3's SNI support, if possible\nfrom pip._internal.utils.compat import WINDOWS\nif not WINDOWS:\n    try:\n        from pip._vendor.urllib3.contrib import pyopenssl\n        pyopenssl.inject_into_urllib3()\n\n        # Check cryptography version\n        from cryptography import __version__ as cryptography_version\n        _check_cryptography(cryptography_version)\n    except ImportError:\n        pass\n\n# urllib3's DependencyWarnings should be silenced.\nfrom pip._vendor.urllib3.exceptions import DependencyWarning\nwarnings.simplefilter('ignore', DependencyWarning)\n\nfrom .__version__ import __title__, __description__, __url__, __version__\nfrom .__version__ import __build__, __author__, __author_email__, __license__\nfrom .__version__ import __copyright__, __cake__\n\nfrom . import utils\nfrom . import packages\nfrom .models import Request, Response, PreparedRequest\nfrom .api import request, get, head, post, patch, put, delete, options\nfrom .sessions import session, Session\nfrom .status_codes import codes\nfrom .exceptions import (\n    RequestException, Timeout, URLRequired,\n    TooManyRedirects, HTTPError, ConnectionError,\n    FileModeWarning, ConnectTimeout, ReadTimeout\n)\n\n# Set default logging handler to avoid \"No handler found\" warnings.\nimport logging\nfrom logging import NullHandler\n\nlogging.getLogger(__name__).addHandler(NullHandler())\n\n# FileModeWarnings go off per the default.\nwarnings.simplefilter('default', FileModeWarning, append=True)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/__version__.py",
    "content": "# .-. .-. .-. . . .-. .-. .-. .-.\n# |(  |-  |.| | | |-  `-.  |  `-.\n# ' ' `-' `-`.`-' `-' `-'  '  `-'\n\n__title__ = 'requests'\n__description__ = 'Python HTTP for Humans.'\n__url__ = 'http://python-requests.org'\n__version__ = '2.21.0'\n__build__ = 0x022100\n__author__ = 'Kenneth Reitz'\n__author_email__ = 'me@kennethreitz.org'\n__license__ = 'Apache 2.0'\n__copyright__ = 'Copyright 2018 Kenneth Reitz'\n__cake__ = u'\\u2728 \\U0001f370 \\u2728'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/_internal_utils.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests._internal_utils\n~~~~~~~~~~~~~~\n\nProvides utility functions that are consumed internally by Requests\nwhich depend on extremely few external helpers (such as compat)\n\"\"\"\n\nfrom .compat import is_py2, builtin_str, str\n\n\ndef to_native_string(string, encoding='ascii'):\n    \"\"\"Given a string object, regardless of type, returns a representation of\n    that string in the native string type, encoding and decoding where\n    necessary. This assumes ASCII unless told otherwise.\n    \"\"\"\n    if isinstance(string, builtin_str):\n        out = string\n    else:\n        if is_py2:\n            out = string.encode(encoding)\n        else:\n            out = string.decode(encoding)\n\n    return out\n\n\ndef unicode_is_ascii(u_string):\n    \"\"\"Determine if unicode string only contains ASCII characters.\n\n    :param str u_string: unicode string to check. Must be unicode\n        and not Python 2 `str`.\n    :rtype: bool\n    \"\"\"\n    assert isinstance(u_string, str)\n    try:\n        u_string.encode('ascii')\n        return True\n    except UnicodeEncodeError:\n        return False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/adapters.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests.adapters\n~~~~~~~~~~~~~~~~~\n\nThis module contains the transport adapters that Requests uses to define\nand maintain connections.\n\"\"\"\n\nimport os.path\nimport socket\n\nfrom pip._vendor.urllib3.poolmanager import PoolManager, proxy_from_url\nfrom pip._vendor.urllib3.response import HTTPResponse\nfrom pip._vendor.urllib3.util import parse_url\nfrom pip._vendor.urllib3.util import Timeout as TimeoutSauce\nfrom pip._vendor.urllib3.util.retry import Retry\nfrom pip._vendor.urllib3.exceptions import ClosedPoolError\nfrom pip._vendor.urllib3.exceptions import ConnectTimeoutError\nfrom pip._vendor.urllib3.exceptions import HTTPError as _HTTPError\nfrom pip._vendor.urllib3.exceptions import MaxRetryError\nfrom pip._vendor.urllib3.exceptions import NewConnectionError\nfrom pip._vendor.urllib3.exceptions import ProxyError as _ProxyError\nfrom pip._vendor.urllib3.exceptions import ProtocolError\nfrom pip._vendor.urllib3.exceptions import ReadTimeoutError\nfrom pip._vendor.urllib3.exceptions import SSLError as _SSLError\nfrom pip._vendor.urllib3.exceptions import ResponseError\nfrom pip._vendor.urllib3.exceptions import LocationValueError\n\nfrom .models import Response\nfrom .compat import urlparse, basestring\nfrom .utils import (DEFAULT_CA_BUNDLE_PATH, extract_zipped_paths,\n                    get_encoding_from_headers, prepend_scheme_if_needed,\n                    get_auth_from_url, urldefragauth, select_proxy)\nfrom .structures import CaseInsensitiveDict\nfrom .cookies import extract_cookies_to_jar\nfrom .exceptions import (ConnectionError, ConnectTimeout, ReadTimeout, SSLError,\n                         ProxyError, RetryError, InvalidSchema, InvalidProxyURL,\n                         InvalidURL)\nfrom .auth import _basic_auth_str\n\ntry:\n    from pip._vendor.urllib3.contrib.socks import SOCKSProxyManager\nexcept ImportError:\n    def SOCKSProxyManager(*args, **kwargs):\n        raise InvalidSchema(\"Missing dependencies for SOCKS support.\")\n\nDEFAULT_POOLBLOCK = False\nDEFAULT_POOLSIZE = 10\nDEFAULT_RETRIES = 0\nDEFAULT_POOL_TIMEOUT = None\n\n\nclass BaseAdapter(object):\n    \"\"\"The Base Transport Adapter\"\"\"\n\n    def __init__(self):\n        super(BaseAdapter, self).__init__()\n\n    def send(self, request, stream=False, timeout=None, verify=True,\n             cert=None, proxies=None):\n        \"\"\"Sends PreparedRequest object. Returns Response object.\n\n        :param request: The :class:`PreparedRequest <PreparedRequest>` being sent.\n        :param stream: (optional) Whether to stream the request content.\n        :param timeout: (optional) How long to wait for the server to send\n            data before giving up, as a float, or a :ref:`(connect timeout,\n            read timeout) <timeouts>` tuple.\n        :type timeout: float or tuple\n        :param verify: (optional) Either a boolean, in which case it controls whether we verify\n            the server's TLS certificate, or a string, in which case it must be a path\n            to a CA bundle to use\n        :param cert: (optional) Any user-provided SSL certificate to be trusted.\n        :param proxies: (optional) The proxies dictionary to apply to the request.\n        \"\"\"\n        raise NotImplementedError\n\n    def close(self):\n        \"\"\"Cleans up adapter specific items.\"\"\"\n        raise NotImplementedError\n\n\nclass HTTPAdapter(BaseAdapter):\n    \"\"\"The built-in HTTP Adapter for urllib3.\n\n    Provides a general-case interface for Requests sessions to contact HTTP and\n    HTTPS urls by implementing the Transport Adapter interface. This class will\n    usually be created by the :class:`Session <Session>` class under the\n    covers.\n\n    :param pool_connections: The number of urllib3 connection pools to cache.\n    :param pool_maxsize: The maximum number of connections to save in the pool.\n    :param max_retries: The maximum number of retries each connection\n        should attempt. Note, this applies only to failed DNS lookups, socket\n        connections and connection timeouts, never to requests where data has\n        made it to the server. By default, Requests does not retry failed\n        connections. If you need granular control over the conditions under\n        which we retry a request, import urllib3's ``Retry`` class and pass\n        that instead.\n    :param pool_block: Whether the connection pool should block for connections.\n\n    Usage::\n\n      >>> import requests\n      >>> s = requests.Session()\n      >>> a = requests.adapters.HTTPAdapter(max_retries=3)\n      >>> s.mount('http://', a)\n    \"\"\"\n    __attrs__ = ['max_retries', 'config', '_pool_connections', '_pool_maxsize',\n                 '_pool_block']\n\n    def __init__(self, pool_connections=DEFAULT_POOLSIZE,\n                 pool_maxsize=DEFAULT_POOLSIZE, max_retries=DEFAULT_RETRIES,\n                 pool_block=DEFAULT_POOLBLOCK):\n        if max_retries == DEFAULT_RETRIES:\n            self.max_retries = Retry(0, read=False)\n        else:\n            self.max_retries = Retry.from_int(max_retries)\n        self.config = {}\n        self.proxy_manager = {}\n\n        super(HTTPAdapter, self).__init__()\n\n        self._pool_connections = pool_connections\n        self._pool_maxsize = pool_maxsize\n        self._pool_block = pool_block\n\n        self.init_poolmanager(pool_connections, pool_maxsize, block=pool_block)\n\n    def __getstate__(self):\n        return {attr: getattr(self, attr, None) for attr in self.__attrs__}\n\n    def __setstate__(self, state):\n        # Can't handle by adding 'proxy_manager' to self.__attrs__ because\n        # self.poolmanager uses a lambda function, which isn't pickleable.\n        self.proxy_manager = {}\n        self.config = {}\n\n        for attr, value in state.items():\n            setattr(self, attr, value)\n\n        self.init_poolmanager(self._pool_connections, self._pool_maxsize,\n                              block=self._pool_block)\n\n    def init_poolmanager(self, connections, maxsize, block=DEFAULT_POOLBLOCK, **pool_kwargs):\n        \"\"\"Initializes a urllib3 PoolManager.\n\n        This method should not be called from user code, and is only\n        exposed for use when subclassing the\n        :class:`HTTPAdapter <requests.adapters.HTTPAdapter>`.\n\n        :param connections: The number of urllib3 connection pools to cache.\n        :param maxsize: The maximum number of connections to save in the pool.\n        :param block: Block when no free connections are available.\n        :param pool_kwargs: Extra keyword arguments used to initialize the Pool Manager.\n        \"\"\"\n        # save these values for pickling\n        self._pool_connections = connections\n        self._pool_maxsize = maxsize\n        self._pool_block = block\n\n        self.poolmanager = PoolManager(num_pools=connections, maxsize=maxsize,\n                                       block=block, strict=True, **pool_kwargs)\n\n    def proxy_manager_for(self, proxy, **proxy_kwargs):\n        \"\"\"Return urllib3 ProxyManager for the given proxy.\n\n        This method should not be called from user code, and is only\n        exposed for use when subclassing the\n        :class:`HTTPAdapter <requests.adapters.HTTPAdapter>`.\n\n        :param proxy: The proxy to return a urllib3 ProxyManager for.\n        :param proxy_kwargs: Extra keyword arguments used to configure the Proxy Manager.\n        :returns: ProxyManager\n        :rtype: urllib3.ProxyManager\n        \"\"\"\n        if proxy in self.proxy_manager:\n            manager = self.proxy_manager[proxy]\n        elif proxy.lower().startswith('socks'):\n            username, password = get_auth_from_url(proxy)\n            manager = self.proxy_manager[proxy] = SOCKSProxyManager(\n                proxy,\n                username=username,\n                password=password,\n                num_pools=self._pool_connections,\n                maxsize=self._pool_maxsize,\n                block=self._pool_block,\n                **proxy_kwargs\n            )\n        else:\n            proxy_headers = self.proxy_headers(proxy)\n            manager = self.proxy_manager[proxy] = proxy_from_url(\n                proxy,\n                proxy_headers=proxy_headers,\n                num_pools=self._pool_connections,\n                maxsize=self._pool_maxsize,\n                block=self._pool_block,\n                **proxy_kwargs)\n\n        return manager\n\n    def cert_verify(self, conn, url, verify, cert):\n        \"\"\"Verify a SSL certificate. This method should not be called from user\n        code, and is only exposed for use when subclassing the\n        :class:`HTTPAdapter <requests.adapters.HTTPAdapter>`.\n\n        :param conn: The urllib3 connection object associated with the cert.\n        :param url: The requested URL.\n        :param verify: Either a boolean, in which case it controls whether we verify\n            the server's TLS certificate, or a string, in which case it must be a path\n            to a CA bundle to use\n        :param cert: The SSL certificate to verify.\n        \"\"\"\n        if url.lower().startswith('https') and verify:\n\n            cert_loc = None\n\n            # Allow self-specified cert location.\n            if verify is not True:\n                cert_loc = verify\n\n            if not cert_loc:\n                cert_loc = extract_zipped_paths(DEFAULT_CA_BUNDLE_PATH)\n\n            if not cert_loc or not os.path.exists(cert_loc):\n                raise IOError(\"Could not find a suitable TLS CA certificate bundle, \"\n                              \"invalid path: {}\".format(cert_loc))\n\n            conn.cert_reqs = 'CERT_REQUIRED'\n\n            if not os.path.isdir(cert_loc):\n                conn.ca_certs = cert_loc\n            else:\n                conn.ca_cert_dir = cert_loc\n        else:\n            conn.cert_reqs = 'CERT_NONE'\n            conn.ca_certs = None\n            conn.ca_cert_dir = None\n\n        if cert:\n            if not isinstance(cert, basestring):\n                conn.cert_file = cert[0]\n                conn.key_file = cert[1]\n            else:\n                conn.cert_file = cert\n                conn.key_file = None\n            if conn.cert_file and not os.path.exists(conn.cert_file):\n                raise IOError(\"Could not find the TLS certificate file, \"\n                              \"invalid path: {}\".format(conn.cert_file))\n            if conn.key_file and not os.path.exists(conn.key_file):\n                raise IOError(\"Could not find the TLS key file, \"\n                              \"invalid path: {}\".format(conn.key_file))\n\n    def build_response(self, req, resp):\n        \"\"\"Builds a :class:`Response <requests.Response>` object from a urllib3\n        response. This should not be called from user code, and is only exposed\n        for use when subclassing the\n        :class:`HTTPAdapter <requests.adapters.HTTPAdapter>`\n\n        :param req: The :class:`PreparedRequest <PreparedRequest>` used to generate the response.\n        :param resp: The urllib3 response object.\n        :rtype: requests.Response\n        \"\"\"\n        response = Response()\n\n        # Fallback to None if there's no status_code, for whatever reason.\n        response.status_code = getattr(resp, 'status', None)\n\n        # Make headers case-insensitive.\n        response.headers = CaseInsensitiveDict(getattr(resp, 'headers', {}))\n\n        # Set encoding.\n        response.encoding = get_encoding_from_headers(response.headers)\n        response.raw = resp\n        response.reason = response.raw.reason\n\n        if isinstance(req.url, bytes):\n            response.url = req.url.decode('utf-8')\n        else:\n            response.url = req.url\n\n        # Add new cookies from the server.\n        extract_cookies_to_jar(response.cookies, req, resp)\n\n        # Give the Response some context.\n        response.request = req\n        response.connection = self\n\n        return response\n\n    def get_connection(self, url, proxies=None):\n        \"\"\"Returns a urllib3 connection for the given URL. This should not be\n        called from user code, and is only exposed for use when subclassing the\n        :class:`HTTPAdapter <requests.adapters.HTTPAdapter>`.\n\n        :param url: The URL to connect to.\n        :param proxies: (optional) A Requests-style dictionary of proxies used on this request.\n        :rtype: urllib3.ConnectionPool\n        \"\"\"\n        proxy = select_proxy(url, proxies)\n\n        if proxy:\n            proxy = prepend_scheme_if_needed(proxy, 'http')\n            proxy_url = parse_url(proxy)\n            if not proxy_url.host:\n                raise InvalidProxyURL(\"Please check proxy URL. It is malformed\"\n                                      \" and could be missing the host.\")\n            proxy_manager = self.proxy_manager_for(proxy)\n            conn = proxy_manager.connection_from_url(url)\n        else:\n            # Only scheme should be lower case\n            parsed = urlparse(url)\n            url = parsed.geturl()\n            conn = self.poolmanager.connection_from_url(url)\n\n        return conn\n\n    def close(self):\n        \"\"\"Disposes of any internal state.\n\n        Currently, this closes the PoolManager and any active ProxyManager,\n        which closes any pooled connections.\n        \"\"\"\n        self.poolmanager.clear()\n        for proxy in self.proxy_manager.values():\n            proxy.clear()\n\n    def request_url(self, request, proxies):\n        \"\"\"Obtain the url to use when making the final request.\n\n        If the message is being sent through a HTTP proxy, the full URL has to\n        be used. Otherwise, we should only use the path portion of the URL.\n\n        This should not be called from user code, and is only exposed for use\n        when subclassing the\n        :class:`HTTPAdapter <requests.adapters.HTTPAdapter>`.\n\n        :param request: The :class:`PreparedRequest <PreparedRequest>` being sent.\n        :param proxies: A dictionary of schemes or schemes and hosts to proxy URLs.\n        :rtype: str\n        \"\"\"\n        proxy = select_proxy(request.url, proxies)\n        scheme = urlparse(request.url).scheme\n\n        is_proxied_http_request = (proxy and scheme != 'https')\n        using_socks_proxy = False\n        if proxy:\n            proxy_scheme = urlparse(proxy).scheme.lower()\n            using_socks_proxy = proxy_scheme.startswith('socks')\n\n        url = request.path_url\n        if is_proxied_http_request and not using_socks_proxy:\n            url = urldefragauth(request.url)\n\n        return url\n\n    def add_headers(self, request, **kwargs):\n        \"\"\"Add any headers needed by the connection. As of v2.0 this does\n        nothing by default, but is left for overriding by users that subclass\n        the :class:`HTTPAdapter <requests.adapters.HTTPAdapter>`.\n\n        This should not be called from user code, and is only exposed for use\n        when subclassing the\n        :class:`HTTPAdapter <requests.adapters.HTTPAdapter>`.\n\n        :param request: The :class:`PreparedRequest <PreparedRequest>` to add headers to.\n        :param kwargs: The keyword arguments from the call to send().\n        \"\"\"\n        pass\n\n    def proxy_headers(self, proxy):\n        \"\"\"Returns a dictionary of the headers to add to any request sent\n        through a proxy. This works with urllib3 magic to ensure that they are\n        correctly sent to the proxy, rather than in a tunnelled request if\n        CONNECT is being used.\n\n        This should not be called from user code, and is only exposed for use\n        when subclassing the\n        :class:`HTTPAdapter <requests.adapters.HTTPAdapter>`.\n\n        :param proxy: The url of the proxy being used for this request.\n        :rtype: dict\n        \"\"\"\n        headers = {}\n        username, password = get_auth_from_url(proxy)\n\n        if username:\n            headers['Proxy-Authorization'] = _basic_auth_str(username,\n                                                             password)\n\n        return headers\n\n    def send(self, request, stream=False, timeout=None, verify=True, cert=None, proxies=None):\n        \"\"\"Sends PreparedRequest object. Returns Response object.\n\n        :param request: The :class:`PreparedRequest <PreparedRequest>` being sent.\n        :param stream: (optional) Whether to stream the request content.\n        :param timeout: (optional) How long to wait for the server to send\n            data before giving up, as a float, or a :ref:`(connect timeout,\n            read timeout) <timeouts>` tuple.\n        :type timeout: float or tuple or urllib3 Timeout object\n        :param verify: (optional) Either a boolean, in which case it controls whether\n            we verify the server's TLS certificate, or a string, in which case it\n            must be a path to a CA bundle to use\n        :param cert: (optional) Any user-provided SSL certificate to be trusted.\n        :param proxies: (optional) The proxies dictionary to apply to the request.\n        :rtype: requests.Response\n        \"\"\"\n\n        try:\n            conn = self.get_connection(request.url, proxies)\n        except LocationValueError as e:\n            raise InvalidURL(e, request=request)\n\n        self.cert_verify(conn, request.url, verify, cert)\n        url = self.request_url(request, proxies)\n        self.add_headers(request, stream=stream, timeout=timeout, verify=verify, cert=cert, proxies=proxies)\n\n        chunked = not (request.body is None or 'Content-Length' in request.headers)\n\n        if isinstance(timeout, tuple):\n            try:\n                connect, read = timeout\n                timeout = TimeoutSauce(connect=connect, read=read)\n            except ValueError as e:\n                # this may raise a string formatting error.\n                err = (\"Invalid timeout {}. Pass a (connect, read) \"\n                       \"timeout tuple, or a single float to set \"\n                       \"both timeouts to the same value\".format(timeout))\n                raise ValueError(err)\n        elif isinstance(timeout, TimeoutSauce):\n            pass\n        else:\n            timeout = TimeoutSauce(connect=timeout, read=timeout)\n\n        try:\n            if not chunked:\n                resp = conn.urlopen(\n                    method=request.method,\n                    url=url,\n                    body=request.body,\n                    headers=request.headers,\n                    redirect=False,\n                    assert_same_host=False,\n                    preload_content=False,\n                    decode_content=False,\n                    retries=self.max_retries,\n                    timeout=timeout\n                )\n\n            # Send the request.\n            else:\n                if hasattr(conn, 'proxy_pool'):\n                    conn = conn.proxy_pool\n\n                low_conn = conn._get_conn(timeout=DEFAULT_POOL_TIMEOUT)\n\n                try:\n                    low_conn.putrequest(request.method,\n                                        url,\n                                        skip_accept_encoding=True)\n\n                    for header, value in request.headers.items():\n                        low_conn.putheader(header, value)\n\n                    low_conn.endheaders()\n\n                    for i in request.body:\n                        low_conn.send(hex(len(i))[2:].encode('utf-8'))\n                        low_conn.send(b'\\r\\n')\n                        low_conn.send(i)\n                        low_conn.send(b'\\r\\n')\n                    low_conn.send(b'0\\r\\n\\r\\n')\n\n                    # Receive the response from the server\n                    try:\n                        # For Python 2.7, use buffering of HTTP responses\n                        r = low_conn.getresponse(buffering=True)\n                    except TypeError:\n                        # For compatibility with Python 3.3+\n                        r = low_conn.getresponse()\n\n                    resp = HTTPResponse.from_httplib(\n                        r,\n                        pool=conn,\n                        connection=low_conn,\n                        preload_content=False,\n                        decode_content=False\n                    )\n                except:\n                    # If we hit any problems here, clean up the connection.\n                    # Then, reraise so that we can handle the actual exception.\n                    low_conn.close()\n                    raise\n\n        except (ProtocolError, socket.error) as err:\n            raise ConnectionError(err, request=request)\n\n        except MaxRetryError as e:\n            if isinstance(e.reason, ConnectTimeoutError):\n                # TODO: Remove this in 3.0.0: see #2811\n                if not isinstance(e.reason, NewConnectionError):\n                    raise ConnectTimeout(e, request=request)\n\n            if isinstance(e.reason, ResponseError):\n                raise RetryError(e, request=request)\n\n            if isinstance(e.reason, _ProxyError):\n                raise ProxyError(e, request=request)\n\n            if isinstance(e.reason, _SSLError):\n                # This branch is for urllib3 v1.22 and later.\n                raise SSLError(e, request=request)\n\n            raise ConnectionError(e, request=request)\n\n        except ClosedPoolError as e:\n            raise ConnectionError(e, request=request)\n\n        except _ProxyError as e:\n            raise ProxyError(e)\n\n        except (_SSLError, _HTTPError) as e:\n            if isinstance(e, _SSLError):\n                # This branch is for urllib3 versions earlier than v1.22\n                raise SSLError(e, request=request)\n            elif isinstance(e, ReadTimeoutError):\n                raise ReadTimeout(e, request=request)\n            else:\n                raise\n\n        return self.build_response(request, resp)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/api.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests.api\n~~~~~~~~~~~~\n\nThis module implements the Requests API.\n\n:copyright: (c) 2012 by Kenneth Reitz.\n:license: Apache2, see LICENSE for more details.\n\"\"\"\n\nfrom . import sessions\n\n\ndef request(method, url, **kwargs):\n    \"\"\"Constructs and sends a :class:`Request <Request>`.\n\n    :param method: method for the new :class:`Request` object.\n    :param url: URL for the new :class:`Request` object.\n    :param params: (optional) Dictionary, list of tuples or bytes to send\n        in the body of the :class:`Request`.\n    :param data: (optional) Dictionary, list of tuples, bytes, or file-like\n        object to send in the body of the :class:`Request`.\n    :param json: (optional) A JSON serializable Python object to send in the body of the :class:`Request`.\n    :param headers: (optional) Dictionary of HTTP Headers to send with the :class:`Request`.\n    :param cookies: (optional) Dict or CookieJar object to send with the :class:`Request`.\n    :param files: (optional) Dictionary of ``'name': file-like-objects`` (or ``{'name': file-tuple}``) for multipart encoding upload.\n        ``file-tuple`` can be a 2-tuple ``('filename', fileobj)``, 3-tuple ``('filename', fileobj, 'content_type')``\n        or a 4-tuple ``('filename', fileobj, 'content_type', custom_headers)``, where ``'content-type'`` is a string\n        defining the content type of the given file and ``custom_headers`` a dict-like object containing additional headers\n        to add for the file.\n    :param auth: (optional) Auth tuple to enable Basic/Digest/Custom HTTP Auth.\n    :param timeout: (optional) How many seconds to wait for the server to send data\n        before giving up, as a float, or a :ref:`(connect timeout, read\n        timeout) <timeouts>` tuple.\n    :type timeout: float or tuple\n    :param allow_redirects: (optional) Boolean. Enable/disable GET/OPTIONS/POST/PUT/PATCH/DELETE/HEAD redirection. Defaults to ``True``.\n    :type allow_redirects: bool\n    :param proxies: (optional) Dictionary mapping protocol to the URL of the proxy.\n    :param verify: (optional) Either a boolean, in which case it controls whether we verify\n            the server's TLS certificate, or a string, in which case it must be a path\n            to a CA bundle to use. Defaults to ``True``.\n    :param stream: (optional) if ``False``, the response content will be immediately downloaded.\n    :param cert: (optional) if String, path to ssl client cert file (.pem). If Tuple, ('cert', 'key') pair.\n    :return: :class:`Response <Response>` object\n    :rtype: requests.Response\n\n    Usage::\n\n      >>> import requests\n      >>> req = requests.request('GET', 'https://httpbin.org/get')\n      <Response [200]>\n    \"\"\"\n\n    # By using the 'with' statement we are sure the session is closed, thus we\n    # avoid leaving sockets open which can trigger a ResourceWarning in some\n    # cases, and look like a memory leak in others.\n    with sessions.Session() as session:\n        return session.request(method=method, url=url, **kwargs)\n\n\ndef get(url, params=None, **kwargs):\n    r\"\"\"Sends a GET request.\n\n    :param url: URL for the new :class:`Request` object.\n    :param params: (optional) Dictionary, list of tuples or bytes to send\n        in the body of the :class:`Request`.\n    :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n    :return: :class:`Response <Response>` object\n    :rtype: requests.Response\n    \"\"\"\n\n    kwargs.setdefault('allow_redirects', True)\n    return request('get', url, params=params, **kwargs)\n\n\ndef options(url, **kwargs):\n    r\"\"\"Sends an OPTIONS request.\n\n    :param url: URL for the new :class:`Request` object.\n    :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n    :return: :class:`Response <Response>` object\n    :rtype: requests.Response\n    \"\"\"\n\n    kwargs.setdefault('allow_redirects', True)\n    return request('options', url, **kwargs)\n\n\ndef head(url, **kwargs):\n    r\"\"\"Sends a HEAD request.\n\n    :param url: URL for the new :class:`Request` object.\n    :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n    :return: :class:`Response <Response>` object\n    :rtype: requests.Response\n    \"\"\"\n\n    kwargs.setdefault('allow_redirects', False)\n    return request('head', url, **kwargs)\n\n\ndef post(url, data=None, json=None, **kwargs):\n    r\"\"\"Sends a POST request.\n\n    :param url: URL for the new :class:`Request` object.\n    :param data: (optional) Dictionary, list of tuples, bytes, or file-like\n        object to send in the body of the :class:`Request`.\n    :param json: (optional) json data to send in the body of the :class:`Request`.\n    :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n    :return: :class:`Response <Response>` object\n    :rtype: requests.Response\n    \"\"\"\n\n    return request('post', url, data=data, json=json, **kwargs)\n\n\ndef put(url, data=None, **kwargs):\n    r\"\"\"Sends a PUT request.\n\n    :param url: URL for the new :class:`Request` object.\n    :param data: (optional) Dictionary, list of tuples, bytes, or file-like\n        object to send in the body of the :class:`Request`.\n    :param json: (optional) json data to send in the body of the :class:`Request`.\n    :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n    :return: :class:`Response <Response>` object\n    :rtype: requests.Response\n    \"\"\"\n\n    return request('put', url, data=data, **kwargs)\n\n\ndef patch(url, data=None, **kwargs):\n    r\"\"\"Sends a PATCH request.\n\n    :param url: URL for the new :class:`Request` object.\n    :param data: (optional) Dictionary, list of tuples, bytes, or file-like\n        object to send in the body of the :class:`Request`.\n    :param json: (optional) json data to send in the body of the :class:`Request`.\n    :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n    :return: :class:`Response <Response>` object\n    :rtype: requests.Response\n    \"\"\"\n\n    return request('patch', url, data=data, **kwargs)\n\n\ndef delete(url, **kwargs):\n    r\"\"\"Sends a DELETE request.\n\n    :param url: URL for the new :class:`Request` object.\n    :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n    :return: :class:`Response <Response>` object\n    :rtype: requests.Response\n    \"\"\"\n\n    return request('delete', url, **kwargs)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/auth.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests.auth\n~~~~~~~~~~~~~\n\nThis module contains the authentication handlers for Requests.\n\"\"\"\n\nimport os\nimport re\nimport time\nimport hashlib\nimport threading\nimport warnings\n\nfrom base64 import b64encode\n\nfrom .compat import urlparse, str, basestring\nfrom .cookies import extract_cookies_to_jar\nfrom ._internal_utils import to_native_string\nfrom .utils import parse_dict_header\n\nCONTENT_TYPE_FORM_URLENCODED = 'application/x-www-form-urlencoded'\nCONTENT_TYPE_MULTI_PART = 'multipart/form-data'\n\n\ndef _basic_auth_str(username, password):\n    \"\"\"Returns a Basic Auth string.\"\"\"\n\n    # \"I want us to put a big-ol' comment on top of it that\n    # says that this behaviour is dumb but we need to preserve\n    # it because people are relying on it.\"\n    #    - Lukasa\n    #\n    # These are here solely to maintain backwards compatibility\n    # for things like ints. This will be removed in 3.0.0.\n    if not isinstance(username, basestring):\n        warnings.warn(\n            \"Non-string usernames will no longer be supported in Requests \"\n            \"3.0.0. Please convert the object you've passed in ({!r}) to \"\n            \"a string or bytes object in the near future to avoid \"\n            \"problems.\".format(username),\n            category=DeprecationWarning,\n        )\n        username = str(username)\n\n    if not isinstance(password, basestring):\n        warnings.warn(\n            \"Non-string passwords will no longer be supported in Requests \"\n            \"3.0.0. Please convert the object you've passed in ({!r}) to \"\n            \"a string or bytes object in the near future to avoid \"\n            \"problems.\".format(password),\n            category=DeprecationWarning,\n        )\n        password = str(password)\n    # -- End Removal --\n\n    if isinstance(username, str):\n        username = username.encode('latin1')\n\n    if isinstance(password, str):\n        password = password.encode('latin1')\n\n    authstr = 'Basic ' + to_native_string(\n        b64encode(b':'.join((username, password))).strip()\n    )\n\n    return authstr\n\n\nclass AuthBase(object):\n    \"\"\"Base class that all auth implementations derive from\"\"\"\n\n    def __call__(self, r):\n        raise NotImplementedError('Auth hooks must be callable.')\n\n\nclass HTTPBasicAuth(AuthBase):\n    \"\"\"Attaches HTTP Basic Authentication to the given Request object.\"\"\"\n\n    def __init__(self, username, password):\n        self.username = username\n        self.password = password\n\n    def __eq__(self, other):\n        return all([\n            self.username == getattr(other, 'username', None),\n            self.password == getattr(other, 'password', None)\n        ])\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __call__(self, r):\n        r.headers['Authorization'] = _basic_auth_str(self.username, self.password)\n        return r\n\n\nclass HTTPProxyAuth(HTTPBasicAuth):\n    \"\"\"Attaches HTTP Proxy Authentication to a given Request object.\"\"\"\n\n    def __call__(self, r):\n        r.headers['Proxy-Authorization'] = _basic_auth_str(self.username, self.password)\n        return r\n\n\nclass HTTPDigestAuth(AuthBase):\n    \"\"\"Attaches HTTP Digest Authentication to the given Request object.\"\"\"\n\n    def __init__(self, username, password):\n        self.username = username\n        self.password = password\n        # Keep state in per-thread local storage\n        self._thread_local = threading.local()\n\n    def init_per_thread_state(self):\n        # Ensure state is initialized just once per-thread\n        if not hasattr(self._thread_local, 'init'):\n            self._thread_local.init = True\n            self._thread_local.last_nonce = ''\n            self._thread_local.nonce_count = 0\n            self._thread_local.chal = {}\n            self._thread_local.pos = None\n            self._thread_local.num_401_calls = None\n\n    def build_digest_header(self, method, url):\n        \"\"\"\n        :rtype: str\n        \"\"\"\n\n        realm = self._thread_local.chal['realm']\n        nonce = self._thread_local.chal['nonce']\n        qop = self._thread_local.chal.get('qop')\n        algorithm = self._thread_local.chal.get('algorithm')\n        opaque = self._thread_local.chal.get('opaque')\n        hash_utf8 = None\n\n        if algorithm is None:\n            _algorithm = 'MD5'\n        else:\n            _algorithm = algorithm.upper()\n        # lambdas assume digest modules are imported at the top level\n        if _algorithm == 'MD5' or _algorithm == 'MD5-SESS':\n            def md5_utf8(x):\n                if isinstance(x, str):\n                    x = x.encode('utf-8')\n                return hashlib.md5(x).hexdigest()\n            hash_utf8 = md5_utf8\n        elif _algorithm == 'SHA':\n            def sha_utf8(x):\n                if isinstance(x, str):\n                    x = x.encode('utf-8')\n                return hashlib.sha1(x).hexdigest()\n            hash_utf8 = sha_utf8\n        elif _algorithm == 'SHA-256':\n            def sha256_utf8(x):\n                if isinstance(x, str):\n                    x = x.encode('utf-8')\n                return hashlib.sha256(x).hexdigest()\n            hash_utf8 = sha256_utf8\n        elif _algorithm == 'SHA-512':\n            def sha512_utf8(x):\n                if isinstance(x, str):\n                    x = x.encode('utf-8')\n                return hashlib.sha512(x).hexdigest()\n            hash_utf8 = sha512_utf8\n\n        KD = lambda s, d: hash_utf8(\"%s:%s\" % (s, d))\n\n        if hash_utf8 is None:\n            return None\n\n        # XXX not implemented yet\n        entdig = None\n        p_parsed = urlparse(url)\n        #: path is request-uri defined in RFC 2616 which should not be empty\n        path = p_parsed.path or \"/\"\n        if p_parsed.query:\n            path += '?' + p_parsed.query\n\n        A1 = '%s:%s:%s' % (self.username, realm, self.password)\n        A2 = '%s:%s' % (method, path)\n\n        HA1 = hash_utf8(A1)\n        HA2 = hash_utf8(A2)\n\n        if nonce == self._thread_local.last_nonce:\n            self._thread_local.nonce_count += 1\n        else:\n            self._thread_local.nonce_count = 1\n        ncvalue = '%08x' % self._thread_local.nonce_count\n        s = str(self._thread_local.nonce_count).encode('utf-8')\n        s += nonce.encode('utf-8')\n        s += time.ctime().encode('utf-8')\n        s += os.urandom(8)\n\n        cnonce = (hashlib.sha1(s).hexdigest()[:16])\n        if _algorithm == 'MD5-SESS':\n            HA1 = hash_utf8('%s:%s:%s' % (HA1, nonce, cnonce))\n\n        if not qop:\n            respdig = KD(HA1, \"%s:%s\" % (nonce, HA2))\n        elif qop == 'auth' or 'auth' in qop.split(','):\n            noncebit = \"%s:%s:%s:%s:%s\" % (\n                nonce, ncvalue, cnonce, 'auth', HA2\n            )\n            respdig = KD(HA1, noncebit)\n        else:\n            # XXX handle auth-int.\n            return None\n\n        self._thread_local.last_nonce = nonce\n\n        # XXX should the partial digests be encoded too?\n        base = 'username=\"%s\", realm=\"%s\", nonce=\"%s\", uri=\"%s\", ' \\\n               'response=\"%s\"' % (self.username, realm, nonce, path, respdig)\n        if opaque:\n            base += ', opaque=\"%s\"' % opaque\n        if algorithm:\n            base += ', algorithm=\"%s\"' % algorithm\n        if entdig:\n            base += ', digest=\"%s\"' % entdig\n        if qop:\n            base += ', qop=\"auth\", nc=%s, cnonce=\"%s\"' % (ncvalue, cnonce)\n\n        return 'Digest %s' % (base)\n\n    def handle_redirect(self, r, **kwargs):\n        \"\"\"Reset num_401_calls counter on redirects.\"\"\"\n        if r.is_redirect:\n            self._thread_local.num_401_calls = 1\n\n    def handle_401(self, r, **kwargs):\n        \"\"\"\n        Takes the given response and tries digest-auth, if needed.\n\n        :rtype: requests.Response\n        \"\"\"\n\n        # If response is not 4xx, do not auth\n        # See https://github.com/requests/requests/issues/3772\n        if not 400 <= r.status_code < 500:\n            self._thread_local.num_401_calls = 1\n            return r\n\n        if self._thread_local.pos is not None:\n            # Rewind the file position indicator of the body to where\n            # it was to resend the request.\n            r.request.body.seek(self._thread_local.pos)\n        s_auth = r.headers.get('www-authenticate', '')\n\n        if 'digest' in s_auth.lower() and self._thread_local.num_401_calls < 2:\n\n            self._thread_local.num_401_calls += 1\n            pat = re.compile(r'digest ', flags=re.IGNORECASE)\n            self._thread_local.chal = parse_dict_header(pat.sub('', s_auth, count=1))\n\n            # Consume content and release the original connection\n            # to allow our new request to reuse the same one.\n            r.content\n            r.close()\n            prep = r.request.copy()\n            extract_cookies_to_jar(prep._cookies, r.request, r.raw)\n            prep.prepare_cookies(prep._cookies)\n\n            prep.headers['Authorization'] = self.build_digest_header(\n                prep.method, prep.url)\n            _r = r.connection.send(prep, **kwargs)\n            _r.history.append(r)\n            _r.request = prep\n\n            return _r\n\n        self._thread_local.num_401_calls = 1\n        return r\n\n    def __call__(self, r):\n        # Initialize per-thread state, if needed\n        self.init_per_thread_state()\n        # If we have a saved nonce, skip the 401\n        if self._thread_local.last_nonce:\n            r.headers['Authorization'] = self.build_digest_header(r.method, r.url)\n        try:\n            self._thread_local.pos = r.body.tell()\n        except AttributeError:\n            # In the case of HTTPDigestAuth being reused and the body of\n            # the previous request was a file-like object, pos has the\n            # file position of the previous body. Ensure it's set to\n            # None.\n            self._thread_local.pos = None\n        r.register_hook('response', self.handle_401)\n        r.register_hook('response', self.handle_redirect)\n        self._thread_local.num_401_calls = 1\n\n        return r\n\n    def __eq__(self, other):\n        return all([\n            self.username == getattr(other, 'username', None),\n            self.password == getattr(other, 'password', None)\n        ])\n\n    def __ne__(self, other):\n        return not self == other\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/certs.py",
    "content": "#!/usr/bin/env python\n# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests.certs\n~~~~~~~~~~~~~~\n\nThis module returns the preferred default CA certificate bundle. There is\nonly one — the one from the certifi package.\n\nIf you are packaging Requests, e.g., for a Linux distribution or a managed\nenvironment, you can change the definition of where() to return a separately\npackaged CA bundle.\n\"\"\"\nfrom pip._vendor.certifi import where\n\nif __name__ == '__main__':\n    print(where())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/compat.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests.compat\n~~~~~~~~~~~~~~~\n\nThis module handles import compatibility issues between Python 2 and\nPython 3.\n\"\"\"\n\nfrom pip._vendor import chardet\n\nimport sys\n\n# -------\n# Pythons\n# -------\n\n# Syntax sugar.\n_ver = sys.version_info\n\n#: Python 2.x?\nis_py2 = (_ver[0] == 2)\n\n#: Python 3.x?\nis_py3 = (_ver[0] == 3)\n\n# Note: We've patched out simplejson support in pip because it prevents\n#       upgrading simplejson on Windows.\n# try:\n#     import simplejson as json\n# except (ImportError, SyntaxError):\n#     # simplejson does not support Python 3.2, it throws a SyntaxError\n#     # because of u'...' Unicode literals.\nimport json\n\n# ---------\n# Specifics\n# ---------\n\nif is_py2:\n    from urllib import (\n        quote, unquote, quote_plus, unquote_plus, urlencode, getproxies,\n        proxy_bypass, proxy_bypass_environment, getproxies_environment)\n    from urlparse import urlparse, urlunparse, urljoin, urlsplit, urldefrag\n    from urllib2 import parse_http_list\n    import cookielib\n    from Cookie import Morsel\n    from StringIO import StringIO\n    from collections import Callable, Mapping, MutableMapping, OrderedDict\n\n\n    builtin_str = str\n    bytes = str\n    str = unicode\n    basestring = basestring\n    numeric_types = (int, long, float)\n    integer_types = (int, long)\n\nelif is_py3:\n    from urllib.parse import urlparse, urlunparse, urljoin, urlsplit, urlencode, quote, unquote, quote_plus, unquote_plus, urldefrag\n    from urllib.request import parse_http_list, getproxies, proxy_bypass, proxy_bypass_environment, getproxies_environment\n    from http import cookiejar as cookielib\n    from http.cookies import Morsel\n    from io import StringIO\n    from collections import OrderedDict\n    from collections.abc import Callable, Mapping, MutableMapping\n\n    builtin_str = str\n    str = str\n    bytes = bytes\n    basestring = (str, bytes)\n    numeric_types = (int, float)\n    integer_types = (int,)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/cookies.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests.cookies\n~~~~~~~~~~~~~~~~\n\nCompatibility code to be able to use `cookielib.CookieJar` with requests.\n\nrequests.utils imports from here, so be careful with imports.\n\"\"\"\n\nimport copy\nimport time\nimport calendar\n\nfrom ._internal_utils import to_native_string\nfrom .compat import cookielib, urlparse, urlunparse, Morsel, MutableMapping\n\ntry:\n    import threading\nexcept ImportError:\n    import dummy_threading as threading\n\n\nclass MockRequest(object):\n    \"\"\"Wraps a `requests.Request` to mimic a `urllib2.Request`.\n\n    The code in `cookielib.CookieJar` expects this interface in order to correctly\n    manage cookie policies, i.e., determine whether a cookie can be set, given the\n    domains of the request and the cookie.\n\n    The original request object is read-only. The client is responsible for collecting\n    the new headers via `get_new_headers()` and interpreting them appropriately. You\n    probably want `get_cookie_header`, defined below.\n    \"\"\"\n\n    def __init__(self, request):\n        self._r = request\n        self._new_headers = {}\n        self.type = urlparse(self._r.url).scheme\n\n    def get_type(self):\n        return self.type\n\n    def get_host(self):\n        return urlparse(self._r.url).netloc\n\n    def get_origin_req_host(self):\n        return self.get_host()\n\n    def get_full_url(self):\n        # Only return the response's URL if the user hadn't set the Host\n        # header\n        if not self._r.headers.get('Host'):\n            return self._r.url\n        # If they did set it, retrieve it and reconstruct the expected domain\n        host = to_native_string(self._r.headers['Host'], encoding='utf-8')\n        parsed = urlparse(self._r.url)\n        # Reconstruct the URL as we expect it\n        return urlunparse([\n            parsed.scheme, host, parsed.path, parsed.params, parsed.query,\n            parsed.fragment\n        ])\n\n    def is_unverifiable(self):\n        return True\n\n    def has_header(self, name):\n        return name in self._r.headers or name in self._new_headers\n\n    def get_header(self, name, default=None):\n        return self._r.headers.get(name, self._new_headers.get(name, default))\n\n    def add_header(self, key, val):\n        \"\"\"cookielib has no legitimate use for this method; add it back if you find one.\"\"\"\n        raise NotImplementedError(\"Cookie headers should be added with add_unredirected_header()\")\n\n    def add_unredirected_header(self, name, value):\n        self._new_headers[name] = value\n\n    def get_new_headers(self):\n        return self._new_headers\n\n    @property\n    def unverifiable(self):\n        return self.is_unverifiable()\n\n    @property\n    def origin_req_host(self):\n        return self.get_origin_req_host()\n\n    @property\n    def host(self):\n        return self.get_host()\n\n\nclass MockResponse(object):\n    \"\"\"Wraps a `httplib.HTTPMessage` to mimic a `urllib.addinfourl`.\n\n    ...what? Basically, expose the parsed HTTP headers from the server response\n    the way `cookielib` expects to see them.\n    \"\"\"\n\n    def __init__(self, headers):\n        \"\"\"Make a MockResponse for `cookielib` to read.\n\n        :param headers: a httplib.HTTPMessage or analogous carrying the headers\n        \"\"\"\n        self._headers = headers\n\n    def info(self):\n        return self._headers\n\n    def getheaders(self, name):\n        self._headers.getheaders(name)\n\n\ndef extract_cookies_to_jar(jar, request, response):\n    \"\"\"Extract the cookies from the response into a CookieJar.\n\n    :param jar: cookielib.CookieJar (not necessarily a RequestsCookieJar)\n    :param request: our own requests.Request object\n    :param response: urllib3.HTTPResponse object\n    \"\"\"\n    if not (hasattr(response, '_original_response') and\n            response._original_response):\n        return\n    # the _original_response field is the wrapped httplib.HTTPResponse object,\n    req = MockRequest(request)\n    # pull out the HTTPMessage with the headers and put it in the mock:\n    res = MockResponse(response._original_response.msg)\n    jar.extract_cookies(res, req)\n\n\ndef get_cookie_header(jar, request):\n    \"\"\"\n    Produce an appropriate Cookie header string to be sent with `request`, or None.\n\n    :rtype: str\n    \"\"\"\n    r = MockRequest(request)\n    jar.add_cookie_header(r)\n    return r.get_new_headers().get('Cookie')\n\n\ndef remove_cookie_by_name(cookiejar, name, domain=None, path=None):\n    \"\"\"Unsets a cookie by name, by default over all domains and paths.\n\n    Wraps CookieJar.clear(), is O(n).\n    \"\"\"\n    clearables = []\n    for cookie in cookiejar:\n        if cookie.name != name:\n            continue\n        if domain is not None and domain != cookie.domain:\n            continue\n        if path is not None and path != cookie.path:\n            continue\n        clearables.append((cookie.domain, cookie.path, cookie.name))\n\n    for domain, path, name in clearables:\n        cookiejar.clear(domain, path, name)\n\n\nclass CookieConflictError(RuntimeError):\n    \"\"\"There are two cookies that meet the criteria specified in the cookie jar.\n    Use .get and .set and include domain and path args in order to be more specific.\n    \"\"\"\n\n\nclass RequestsCookieJar(cookielib.CookieJar, MutableMapping):\n    \"\"\"Compatibility class; is a cookielib.CookieJar, but exposes a dict\n    interface.\n\n    This is the CookieJar we create by default for requests and sessions that\n    don't specify one, since some clients may expect response.cookies and\n    session.cookies to support dict operations.\n\n    Requests does not use the dict interface internally; it's just for\n    compatibility with external client code. All requests code should work\n    out of the box with externally provided instances of ``CookieJar``, e.g.\n    ``LWPCookieJar`` and ``FileCookieJar``.\n\n    Unlike a regular CookieJar, this class is pickleable.\n\n    .. warning:: dictionary operations that are normally O(1) may be O(n).\n    \"\"\"\n\n    def get(self, name, default=None, domain=None, path=None):\n        \"\"\"Dict-like get() that also supports optional domain and path args in\n        order to resolve naming collisions from using one cookie jar over\n        multiple domains.\n\n        .. warning:: operation is O(n), not O(1).\n        \"\"\"\n        try:\n            return self._find_no_duplicates(name, domain, path)\n        except KeyError:\n            return default\n\n    def set(self, name, value, **kwargs):\n        \"\"\"Dict-like set() that also supports optional domain and path args in\n        order to resolve naming collisions from using one cookie jar over\n        multiple domains.\n        \"\"\"\n        # support client code that unsets cookies by assignment of a None value:\n        if value is None:\n            remove_cookie_by_name(self, name, domain=kwargs.get('domain'), path=kwargs.get('path'))\n            return\n\n        if isinstance(value, Morsel):\n            c = morsel_to_cookie(value)\n        else:\n            c = create_cookie(name, value, **kwargs)\n        self.set_cookie(c)\n        return c\n\n    def iterkeys(self):\n        \"\"\"Dict-like iterkeys() that returns an iterator of names of cookies\n        from the jar.\n\n        .. seealso:: itervalues() and iteritems().\n        \"\"\"\n        for cookie in iter(self):\n            yield cookie.name\n\n    def keys(self):\n        \"\"\"Dict-like keys() that returns a list of names of cookies from the\n        jar.\n\n        .. seealso:: values() and items().\n        \"\"\"\n        return list(self.iterkeys())\n\n    def itervalues(self):\n        \"\"\"Dict-like itervalues() that returns an iterator of values of cookies\n        from the jar.\n\n        .. seealso:: iterkeys() and iteritems().\n        \"\"\"\n        for cookie in iter(self):\n            yield cookie.value\n\n    def values(self):\n        \"\"\"Dict-like values() that returns a list of values of cookies from the\n        jar.\n\n        .. seealso:: keys() and items().\n        \"\"\"\n        return list(self.itervalues())\n\n    def iteritems(self):\n        \"\"\"Dict-like iteritems() that returns an iterator of name-value tuples\n        from the jar.\n\n        .. seealso:: iterkeys() and itervalues().\n        \"\"\"\n        for cookie in iter(self):\n            yield cookie.name, cookie.value\n\n    def items(self):\n        \"\"\"Dict-like items() that returns a list of name-value tuples from the\n        jar. Allows client-code to call ``dict(RequestsCookieJar)`` and get a\n        vanilla python dict of key value pairs.\n\n        .. seealso:: keys() and values().\n        \"\"\"\n        return list(self.iteritems())\n\n    def list_domains(self):\n        \"\"\"Utility method to list all the domains in the jar.\"\"\"\n        domains = []\n        for cookie in iter(self):\n            if cookie.domain not in domains:\n                domains.append(cookie.domain)\n        return domains\n\n    def list_paths(self):\n        \"\"\"Utility method to list all the paths in the jar.\"\"\"\n        paths = []\n        for cookie in iter(self):\n            if cookie.path not in paths:\n                paths.append(cookie.path)\n        return paths\n\n    def multiple_domains(self):\n        \"\"\"Returns True if there are multiple domains in the jar.\n        Returns False otherwise.\n\n        :rtype: bool\n        \"\"\"\n        domains = []\n        for cookie in iter(self):\n            if cookie.domain is not None and cookie.domain in domains:\n                return True\n            domains.append(cookie.domain)\n        return False  # there is only one domain in jar\n\n    def get_dict(self, domain=None, path=None):\n        \"\"\"Takes as an argument an optional domain and path and returns a plain\n        old Python dict of name-value pairs of cookies that meet the\n        requirements.\n\n        :rtype: dict\n        \"\"\"\n        dictionary = {}\n        for cookie in iter(self):\n            if (\n                (domain is None or cookie.domain == domain) and\n                (path is None or cookie.path == path)\n            ):\n                dictionary[cookie.name] = cookie.value\n        return dictionary\n\n    def __contains__(self, name):\n        try:\n            return super(RequestsCookieJar, self).__contains__(name)\n        except CookieConflictError:\n            return True\n\n    def __getitem__(self, name):\n        \"\"\"Dict-like __getitem__() for compatibility with client code. Throws\n        exception if there are more than one cookie with name. In that case,\n        use the more explicit get() method instead.\n\n        .. warning:: operation is O(n), not O(1).\n        \"\"\"\n        return self._find_no_duplicates(name)\n\n    def __setitem__(self, name, value):\n        \"\"\"Dict-like __setitem__ for compatibility with client code. Throws\n        exception if there is already a cookie of that name in the jar. In that\n        case, use the more explicit set() method instead.\n        \"\"\"\n        self.set(name, value)\n\n    def __delitem__(self, name):\n        \"\"\"Deletes a cookie given a name. Wraps ``cookielib.CookieJar``'s\n        ``remove_cookie_by_name()``.\n        \"\"\"\n        remove_cookie_by_name(self, name)\n\n    def set_cookie(self, cookie, *args, **kwargs):\n        if hasattr(cookie.value, 'startswith') and cookie.value.startswith('\"') and cookie.value.endswith('\"'):\n            cookie.value = cookie.value.replace('\\\\\"', '')\n        return super(RequestsCookieJar, self).set_cookie(cookie, *args, **kwargs)\n\n    def update(self, other):\n        \"\"\"Updates this jar with cookies from another CookieJar or dict-like\"\"\"\n        if isinstance(other, cookielib.CookieJar):\n            for cookie in other:\n                self.set_cookie(copy.copy(cookie))\n        else:\n            super(RequestsCookieJar, self).update(other)\n\n    def _find(self, name, domain=None, path=None):\n        \"\"\"Requests uses this method internally to get cookie values.\n\n        If there are conflicting cookies, _find arbitrarily chooses one.\n        See _find_no_duplicates if you want an exception thrown if there are\n        conflicting cookies.\n\n        :param name: a string containing name of cookie\n        :param domain: (optional) string containing domain of cookie\n        :param path: (optional) string containing path of cookie\n        :return: cookie.value\n        \"\"\"\n        for cookie in iter(self):\n            if cookie.name == name:\n                if domain is None or cookie.domain == domain:\n                    if path is None or cookie.path == path:\n                        return cookie.value\n\n        raise KeyError('name=%r, domain=%r, path=%r' % (name, domain, path))\n\n    def _find_no_duplicates(self, name, domain=None, path=None):\n        \"\"\"Both ``__get_item__`` and ``get`` call this function: it's never\n        used elsewhere in Requests.\n\n        :param name: a string containing name of cookie\n        :param domain: (optional) string containing domain of cookie\n        :param path: (optional) string containing path of cookie\n        :raises KeyError: if cookie is not found\n        :raises CookieConflictError: if there are multiple cookies\n            that match name and optionally domain and path\n        :return: cookie.value\n        \"\"\"\n        toReturn = None\n        for cookie in iter(self):\n            if cookie.name == name:\n                if domain is None or cookie.domain == domain:\n                    if path is None or cookie.path == path:\n                        if toReturn is not None:  # if there are multiple cookies that meet passed in criteria\n                            raise CookieConflictError('There are multiple cookies with name, %r' % (name))\n                        toReturn = cookie.value  # we will eventually return this as long as no cookie conflict\n\n        if toReturn:\n            return toReturn\n        raise KeyError('name=%r, domain=%r, path=%r' % (name, domain, path))\n\n    def __getstate__(self):\n        \"\"\"Unlike a normal CookieJar, this class is pickleable.\"\"\"\n        state = self.__dict__.copy()\n        # remove the unpickleable RLock object\n        state.pop('_cookies_lock')\n        return state\n\n    def __setstate__(self, state):\n        \"\"\"Unlike a normal CookieJar, this class is pickleable.\"\"\"\n        self.__dict__.update(state)\n        if '_cookies_lock' not in self.__dict__:\n            self._cookies_lock = threading.RLock()\n\n    def copy(self):\n        \"\"\"Return a copy of this RequestsCookieJar.\"\"\"\n        new_cj = RequestsCookieJar()\n        new_cj.set_policy(self.get_policy())\n        new_cj.update(self)\n        return new_cj\n\n    def get_policy(self):\n        \"\"\"Return the CookiePolicy instance used.\"\"\"\n        return self._policy\n\n\ndef _copy_cookie_jar(jar):\n    if jar is None:\n        return None\n\n    if hasattr(jar, 'copy'):\n        # We're dealing with an instance of RequestsCookieJar\n        return jar.copy()\n    # We're dealing with a generic CookieJar instance\n    new_jar = copy.copy(jar)\n    new_jar.clear()\n    for cookie in jar:\n        new_jar.set_cookie(copy.copy(cookie))\n    return new_jar\n\n\ndef create_cookie(name, value, **kwargs):\n    \"\"\"Make a cookie from underspecified parameters.\n\n    By default, the pair of `name` and `value` will be set for the domain ''\n    and sent on every request (this is sometimes called a \"supercookie\").\n    \"\"\"\n    result = {\n        'version': 0,\n        'name': name,\n        'value': value,\n        'port': None,\n        'domain': '',\n        'path': '/',\n        'secure': False,\n        'expires': None,\n        'discard': True,\n        'comment': None,\n        'comment_url': None,\n        'rest': {'HttpOnly': None},\n        'rfc2109': False,\n    }\n\n    badargs = set(kwargs) - set(result)\n    if badargs:\n        err = 'create_cookie() got unexpected keyword arguments: %s'\n        raise TypeError(err % list(badargs))\n\n    result.update(kwargs)\n    result['port_specified'] = bool(result['port'])\n    result['domain_specified'] = bool(result['domain'])\n    result['domain_initial_dot'] = result['domain'].startswith('.')\n    result['path_specified'] = bool(result['path'])\n\n    return cookielib.Cookie(**result)\n\n\ndef morsel_to_cookie(morsel):\n    \"\"\"Convert a Morsel object into a Cookie containing the one k/v pair.\"\"\"\n\n    expires = None\n    if morsel['max-age']:\n        try:\n            expires = int(time.time() + int(morsel['max-age']))\n        except ValueError:\n            raise TypeError('max-age: %s must be integer' % morsel['max-age'])\n    elif morsel['expires']:\n        time_template = '%a, %d-%b-%Y %H:%M:%S GMT'\n        expires = calendar.timegm(\n            time.strptime(morsel['expires'], time_template)\n        )\n    return create_cookie(\n        comment=morsel['comment'],\n        comment_url=bool(morsel['comment']),\n        discard=False,\n        domain=morsel['domain'],\n        expires=expires,\n        name=morsel.key,\n        path=morsel['path'],\n        port=None,\n        rest={'HttpOnly': morsel['httponly']},\n        rfc2109=False,\n        secure=bool(morsel['secure']),\n        value=morsel.value,\n        version=morsel['version'] or 0,\n    )\n\n\ndef cookiejar_from_dict(cookie_dict, cookiejar=None, overwrite=True):\n    \"\"\"Returns a CookieJar from a key/value dictionary.\n\n    :param cookie_dict: Dict of key/values to insert into CookieJar.\n    :param cookiejar: (optional) A cookiejar to add the cookies to.\n    :param overwrite: (optional) If False, will not replace cookies\n        already in the jar with new ones.\n    :rtype: CookieJar\n    \"\"\"\n    if cookiejar is None:\n        cookiejar = RequestsCookieJar()\n\n    if cookie_dict is not None:\n        names_from_jar = [cookie.name for cookie in cookiejar]\n        for name in cookie_dict:\n            if overwrite or (name not in names_from_jar):\n                cookiejar.set_cookie(create_cookie(name, cookie_dict[name]))\n\n    return cookiejar\n\n\ndef merge_cookies(cookiejar, cookies):\n    \"\"\"Add cookies to cookiejar and returns a merged CookieJar.\n\n    :param cookiejar: CookieJar object to add the cookies to.\n    :param cookies: Dictionary or CookieJar object to be added.\n    :rtype: CookieJar\n    \"\"\"\n    if not isinstance(cookiejar, cookielib.CookieJar):\n        raise ValueError('You can only merge into CookieJar')\n\n    if isinstance(cookies, dict):\n        cookiejar = cookiejar_from_dict(\n            cookies, cookiejar=cookiejar, overwrite=False)\n    elif isinstance(cookies, cookielib.CookieJar):\n        try:\n            cookiejar.update(cookies)\n        except AttributeError:\n            for cookie_in_jar in cookies:\n                cookiejar.set_cookie(cookie_in_jar)\n\n    return cookiejar\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/exceptions.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests.exceptions\n~~~~~~~~~~~~~~~~~~~\n\nThis module contains the set of Requests' exceptions.\n\"\"\"\nfrom pip._vendor.urllib3.exceptions import HTTPError as BaseHTTPError\n\n\nclass RequestException(IOError):\n    \"\"\"There was an ambiguous exception that occurred while handling your\n    request.\n    \"\"\"\n\n    def __init__(self, *args, **kwargs):\n        \"\"\"Initialize RequestException with `request` and `response` objects.\"\"\"\n        response = kwargs.pop('response', None)\n        self.response = response\n        self.request = kwargs.pop('request', None)\n        if (response is not None and not self.request and\n                hasattr(response, 'request')):\n            self.request = self.response.request\n        super(RequestException, self).__init__(*args, **kwargs)\n\n\nclass HTTPError(RequestException):\n    \"\"\"An HTTP error occurred.\"\"\"\n\n\nclass ConnectionError(RequestException):\n    \"\"\"A Connection error occurred.\"\"\"\n\n\nclass ProxyError(ConnectionError):\n    \"\"\"A proxy error occurred.\"\"\"\n\n\nclass SSLError(ConnectionError):\n    \"\"\"An SSL error occurred.\"\"\"\n\n\nclass Timeout(RequestException):\n    \"\"\"The request timed out.\n\n    Catching this error will catch both\n    :exc:`~requests.exceptions.ConnectTimeout` and\n    :exc:`~requests.exceptions.ReadTimeout` errors.\n    \"\"\"\n\n\nclass ConnectTimeout(ConnectionError, Timeout):\n    \"\"\"The request timed out while trying to connect to the remote server.\n\n    Requests that produced this error are safe to retry.\n    \"\"\"\n\n\nclass ReadTimeout(Timeout):\n    \"\"\"The server did not send any data in the allotted amount of time.\"\"\"\n\n\nclass URLRequired(RequestException):\n    \"\"\"A valid URL is required to make a request.\"\"\"\n\n\nclass TooManyRedirects(RequestException):\n    \"\"\"Too many redirects.\"\"\"\n\n\nclass MissingSchema(RequestException, ValueError):\n    \"\"\"The URL schema (e.g. http or https) is missing.\"\"\"\n\n\nclass InvalidSchema(RequestException, ValueError):\n    \"\"\"See defaults.py for valid schemas.\"\"\"\n\n\nclass InvalidURL(RequestException, ValueError):\n    \"\"\"The URL provided was somehow invalid.\"\"\"\n\n\nclass InvalidHeader(RequestException, ValueError):\n    \"\"\"The header value provided was somehow invalid.\"\"\"\n\n\nclass InvalidProxyURL(InvalidURL):\n    \"\"\"The proxy URL provided is invalid.\"\"\"\n\n\nclass ChunkedEncodingError(RequestException):\n    \"\"\"The server declared chunked encoding but sent an invalid chunk.\"\"\"\n\n\nclass ContentDecodingError(RequestException, BaseHTTPError):\n    \"\"\"Failed to decode response content\"\"\"\n\n\nclass StreamConsumedError(RequestException, TypeError):\n    \"\"\"The content for this response was already consumed\"\"\"\n\n\nclass RetryError(RequestException):\n    \"\"\"Custom retries logic failed\"\"\"\n\n\nclass UnrewindableBodyError(RequestException):\n    \"\"\"Requests encountered an error when trying to rewind a body\"\"\"\n\n# Warnings\n\n\nclass RequestsWarning(Warning):\n    \"\"\"Base warning for Requests.\"\"\"\n    pass\n\n\nclass FileModeWarning(RequestsWarning, DeprecationWarning):\n    \"\"\"A file was opened in text mode, but Requests determined its binary length.\"\"\"\n    pass\n\n\nclass RequestsDependencyWarning(RequestsWarning):\n    \"\"\"An imported dependency doesn't match the expected version range.\"\"\"\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/help.py",
    "content": "\"\"\"Module containing bug report helper(s).\"\"\"\nfrom __future__ import print_function\n\nimport json\nimport platform\nimport sys\nimport ssl\n\nfrom pip._vendor import idna\nfrom pip._vendor import urllib3\nfrom pip._vendor import chardet\n\nfrom . import __version__ as requests_version\n\ntry:\n    from pip._vendor.urllib3.contrib import pyopenssl\nexcept ImportError:\n    pyopenssl = None\n    OpenSSL = None\n    cryptography = None\nelse:\n    import OpenSSL\n    import cryptography\n\n\ndef _implementation():\n    \"\"\"Return a dict with the Python implementation and version.\n\n    Provide both the name and the version of the Python implementation\n    currently running. For example, on CPython 2.7.5 it will return\n    {'name': 'CPython', 'version': '2.7.5'}.\n\n    This function works best on CPython and PyPy: in particular, it probably\n    doesn't work for Jython or IronPython. Future investigation should be done\n    to work out the correct shape of the code for those platforms.\n    \"\"\"\n    implementation = platform.python_implementation()\n\n    if implementation == 'CPython':\n        implementation_version = platform.python_version()\n    elif implementation == 'PyPy':\n        implementation_version = '%s.%s.%s' % (sys.pypy_version_info.major,\n                                               sys.pypy_version_info.minor,\n                                               sys.pypy_version_info.micro)\n        if sys.pypy_version_info.releaselevel != 'final':\n            implementation_version = ''.join([\n                implementation_version, sys.pypy_version_info.releaselevel\n            ])\n    elif implementation == 'Jython':\n        implementation_version = platform.python_version()  # Complete Guess\n    elif implementation == 'IronPython':\n        implementation_version = platform.python_version()  # Complete Guess\n    else:\n        implementation_version = 'Unknown'\n\n    return {'name': implementation, 'version': implementation_version}\n\n\ndef info():\n    \"\"\"Generate information for a bug report.\"\"\"\n    try:\n        platform_info = {\n            'system': platform.system(),\n            'release': platform.release(),\n        }\n    except IOError:\n        platform_info = {\n            'system': 'Unknown',\n            'release': 'Unknown',\n        }\n\n    implementation_info = _implementation()\n    urllib3_info = {'version': urllib3.__version__}\n    chardet_info = {'version': chardet.__version__}\n\n    pyopenssl_info = {\n        'version': None,\n        'openssl_version': '',\n    }\n    if OpenSSL:\n        pyopenssl_info = {\n            'version': OpenSSL.__version__,\n            'openssl_version': '%x' % OpenSSL.SSL.OPENSSL_VERSION_NUMBER,\n        }\n    cryptography_info = {\n        'version': getattr(cryptography, '__version__', ''),\n    }\n    idna_info = {\n        'version': getattr(idna, '__version__', ''),\n    }\n\n    system_ssl = ssl.OPENSSL_VERSION_NUMBER\n    system_ssl_info = {\n        'version': '%x' % system_ssl if system_ssl is not None else ''\n    }\n\n    return {\n        'platform': platform_info,\n        'implementation': implementation_info,\n        'system_ssl': system_ssl_info,\n        'using_pyopenssl': pyopenssl is not None,\n        'pyOpenSSL': pyopenssl_info,\n        'urllib3': urllib3_info,\n        'chardet': chardet_info,\n        'cryptography': cryptography_info,\n        'idna': idna_info,\n        'requests': {\n            'version': requests_version,\n        },\n    }\n\n\ndef main():\n    \"\"\"Pretty-print the bug information as JSON.\"\"\"\n    print(json.dumps(info(), sort_keys=True, indent=2))\n\n\nif __name__ == '__main__':\n    main()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/hooks.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests.hooks\n~~~~~~~~~~~~~~\n\nThis module provides the capabilities for the Requests hooks system.\n\nAvailable hooks:\n\n``response``:\n    The response generated from a Request.\n\"\"\"\nHOOKS = ['response']\n\n\ndef default_hooks():\n    return {event: [] for event in HOOKS}\n\n# TODO: response is the only one\n\n\ndef dispatch_hook(key, hooks, hook_data, **kwargs):\n    \"\"\"Dispatches a hook dictionary on a given piece of data.\"\"\"\n    hooks = hooks or {}\n    hooks = hooks.get(key)\n    if hooks:\n        if hasattr(hooks, '__call__'):\n            hooks = [hooks]\n        for hook in hooks:\n            _hook_data = hook(hook_data, **kwargs)\n            if _hook_data is not None:\n                hook_data = _hook_data\n    return hook_data\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/models.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests.models\n~~~~~~~~~~~~~~~\n\nThis module contains the primary objects that power Requests.\n\"\"\"\n\nimport datetime\nimport sys\n\n# Import encoding now, to avoid implicit import later.\n# Implicit import within threads may cause LookupError when standard library is in a ZIP,\n# such as in Embedded Python. See https://github.com/requests/requests/issues/3578.\nimport encodings.idna\n\nfrom pip._vendor.urllib3.fields import RequestField\nfrom pip._vendor.urllib3.filepost import encode_multipart_formdata\nfrom pip._vendor.urllib3.util import parse_url\nfrom pip._vendor.urllib3.exceptions import (\n    DecodeError, ReadTimeoutError, ProtocolError, LocationParseError)\n\nfrom io import UnsupportedOperation\nfrom .hooks import default_hooks\nfrom .structures import CaseInsensitiveDict\n\nfrom .auth import HTTPBasicAuth\nfrom .cookies import cookiejar_from_dict, get_cookie_header, _copy_cookie_jar\nfrom .exceptions import (\n    HTTPError, MissingSchema, InvalidURL, ChunkedEncodingError,\n    ContentDecodingError, ConnectionError, StreamConsumedError)\nfrom ._internal_utils import to_native_string, unicode_is_ascii\nfrom .utils import (\n    guess_filename, get_auth_from_url, requote_uri,\n    stream_decode_response_unicode, to_key_val_list, parse_header_links,\n    iter_slices, guess_json_utf, super_len, check_header_validity)\nfrom .compat import (\n    Callable, Mapping,\n    cookielib, urlunparse, urlsplit, urlencode, str, bytes,\n    is_py2, chardet, builtin_str, basestring)\nfrom .compat import json as complexjson\nfrom .status_codes import codes\n\n#: The set of HTTP status codes that indicate an automatically\n#: processable redirect.\nREDIRECT_STATI = (\n    codes.moved,               # 301\n    codes.found,               # 302\n    codes.other,               # 303\n    codes.temporary_redirect,  # 307\n    codes.permanent_redirect,  # 308\n)\n\nDEFAULT_REDIRECT_LIMIT = 30\nCONTENT_CHUNK_SIZE = 10 * 1024\nITER_CHUNK_SIZE = 512\n\n\nclass RequestEncodingMixin(object):\n    @property\n    def path_url(self):\n        \"\"\"Build the path URL to use.\"\"\"\n\n        url = []\n\n        p = urlsplit(self.url)\n\n        path = p.path\n        if not path:\n            path = '/'\n\n        url.append(path)\n\n        query = p.query\n        if query:\n            url.append('?')\n            url.append(query)\n\n        return ''.join(url)\n\n    @staticmethod\n    def _encode_params(data):\n        \"\"\"Encode parameters in a piece of data.\n\n        Will successfully encode parameters when passed as a dict or a list of\n        2-tuples. Order is retained if data is a list of 2-tuples but arbitrary\n        if parameters are supplied as a dict.\n        \"\"\"\n\n        if isinstance(data, (str, bytes)):\n            return data\n        elif hasattr(data, 'read'):\n            return data\n        elif hasattr(data, '__iter__'):\n            result = []\n            for k, vs in to_key_val_list(data):\n                if isinstance(vs, basestring) or not hasattr(vs, '__iter__'):\n                    vs = [vs]\n                for v in vs:\n                    if v is not None:\n                        result.append(\n                            (k.encode('utf-8') if isinstance(k, str) else k,\n                             v.encode('utf-8') if isinstance(v, str) else v))\n            return urlencode(result, doseq=True)\n        else:\n            return data\n\n    @staticmethod\n    def _encode_files(files, data):\n        \"\"\"Build the body for a multipart/form-data request.\n\n        Will successfully encode files when passed as a dict or a list of\n        tuples. Order is retained if data is a list of tuples but arbitrary\n        if parameters are supplied as a dict.\n        The tuples may be 2-tuples (filename, fileobj), 3-tuples (filename, fileobj, contentype)\n        or 4-tuples (filename, fileobj, contentype, custom_headers).\n        \"\"\"\n        if (not files):\n            raise ValueError(\"Files must be provided.\")\n        elif isinstance(data, basestring):\n            raise ValueError(\"Data must not be a string.\")\n\n        new_fields = []\n        fields = to_key_val_list(data or {})\n        files = to_key_val_list(files or {})\n\n        for field, val in fields:\n            if isinstance(val, basestring) or not hasattr(val, '__iter__'):\n                val = [val]\n            for v in val:\n                if v is not None:\n                    # Don't call str() on bytestrings: in Py3 it all goes wrong.\n                    if not isinstance(v, bytes):\n                        v = str(v)\n\n                    new_fields.append(\n                        (field.decode('utf-8') if isinstance(field, bytes) else field,\n                         v.encode('utf-8') if isinstance(v, str) else v))\n\n        for (k, v) in files:\n            # support for explicit filename\n            ft = None\n            fh = None\n            if isinstance(v, (tuple, list)):\n                if len(v) == 2:\n                    fn, fp = v\n                elif len(v) == 3:\n                    fn, fp, ft = v\n                else:\n                    fn, fp, ft, fh = v\n            else:\n                fn = guess_filename(v) or k\n                fp = v\n\n            if isinstance(fp, (str, bytes, bytearray)):\n                fdata = fp\n            elif hasattr(fp, 'read'):\n                fdata = fp.read()\n            elif fp is None:\n                continue\n            else:\n                fdata = fp\n\n            rf = RequestField(name=k, data=fdata, filename=fn, headers=fh)\n            rf.make_multipart(content_type=ft)\n            new_fields.append(rf)\n\n        body, content_type = encode_multipart_formdata(new_fields)\n\n        return body, content_type\n\n\nclass RequestHooksMixin(object):\n    def register_hook(self, event, hook):\n        \"\"\"Properly register a hook.\"\"\"\n\n        if event not in self.hooks:\n            raise ValueError('Unsupported event specified, with event name \"%s\"' % (event))\n\n        if isinstance(hook, Callable):\n            self.hooks[event].append(hook)\n        elif hasattr(hook, '__iter__'):\n            self.hooks[event].extend(h for h in hook if isinstance(h, Callable))\n\n    def deregister_hook(self, event, hook):\n        \"\"\"Deregister a previously registered hook.\n        Returns True if the hook existed, False if not.\n        \"\"\"\n\n        try:\n            self.hooks[event].remove(hook)\n            return True\n        except ValueError:\n            return False\n\n\nclass Request(RequestHooksMixin):\n    \"\"\"A user-created :class:`Request <Request>` object.\n\n    Used to prepare a :class:`PreparedRequest <PreparedRequest>`, which is sent to the server.\n\n    :param method: HTTP method to use.\n    :param url: URL to send.\n    :param headers: dictionary of headers to send.\n    :param files: dictionary of {filename: fileobject} files to multipart upload.\n    :param data: the body to attach to the request. If a dictionary or\n        list of tuples ``[(key, value)]`` is provided, form-encoding will\n        take place.\n    :param json: json for the body to attach to the request (if files or data is not specified).\n    :param params: URL parameters to append to the URL. If a dictionary or\n        list of tuples ``[(key, value)]`` is provided, form-encoding will\n        take place.\n    :param auth: Auth handler or (user, pass) tuple.\n    :param cookies: dictionary or CookieJar of cookies to attach to this request.\n    :param hooks: dictionary of callback hooks, for internal usage.\n\n    Usage::\n\n      >>> import requests\n      >>> req = requests.Request('GET', 'https://httpbin.org/get')\n      >>> req.prepare()\n      <PreparedRequest [GET]>\n    \"\"\"\n\n    def __init__(self,\n            method=None, url=None, headers=None, files=None, data=None,\n            params=None, auth=None, cookies=None, hooks=None, json=None):\n\n        # Default empty dicts for dict params.\n        data = [] if data is None else data\n        files = [] if files is None else files\n        headers = {} if headers is None else headers\n        params = {} if params is None else params\n        hooks = {} if hooks is None else hooks\n\n        self.hooks = default_hooks()\n        for (k, v) in list(hooks.items()):\n            self.register_hook(event=k, hook=v)\n\n        self.method = method\n        self.url = url\n        self.headers = headers\n        self.files = files\n        self.data = data\n        self.json = json\n        self.params = params\n        self.auth = auth\n        self.cookies = cookies\n\n    def __repr__(self):\n        return '<Request [%s]>' % (self.method)\n\n    def prepare(self):\n        \"\"\"Constructs a :class:`PreparedRequest <PreparedRequest>` for transmission and returns it.\"\"\"\n        p = PreparedRequest()\n        p.prepare(\n            method=self.method,\n            url=self.url,\n            headers=self.headers,\n            files=self.files,\n            data=self.data,\n            json=self.json,\n            params=self.params,\n            auth=self.auth,\n            cookies=self.cookies,\n            hooks=self.hooks,\n        )\n        return p\n\n\nclass PreparedRequest(RequestEncodingMixin, RequestHooksMixin):\n    \"\"\"The fully mutable :class:`PreparedRequest <PreparedRequest>` object,\n    containing the exact bytes that will be sent to the server.\n\n    Generated from either a :class:`Request <Request>` object or manually.\n\n    Usage::\n\n      >>> import requests\n      >>> req = requests.Request('GET', 'https://httpbin.org/get')\n      >>> r = req.prepare()\n      <PreparedRequest [GET]>\n\n      >>> s = requests.Session()\n      >>> s.send(r)\n      <Response [200]>\n    \"\"\"\n\n    def __init__(self):\n        #: HTTP verb to send to the server.\n        self.method = None\n        #: HTTP URL to send the request to.\n        self.url = None\n        #: dictionary of HTTP headers.\n        self.headers = None\n        # The `CookieJar` used to create the Cookie header will be stored here\n        # after prepare_cookies is called\n        self._cookies = None\n        #: request body to send to the server.\n        self.body = None\n        #: dictionary of callback hooks, for internal usage.\n        self.hooks = default_hooks()\n        #: integer denoting starting position of a readable file-like body.\n        self._body_position = None\n\n    def prepare(self,\n            method=None, url=None, headers=None, files=None, data=None,\n            params=None, auth=None, cookies=None, hooks=None, json=None):\n        \"\"\"Prepares the entire request with the given parameters.\"\"\"\n\n        self.prepare_method(method)\n        self.prepare_url(url, params)\n        self.prepare_headers(headers)\n        self.prepare_cookies(cookies)\n        self.prepare_body(data, files, json)\n        self.prepare_auth(auth, url)\n\n        # Note that prepare_auth must be last to enable authentication schemes\n        # such as OAuth to work on a fully prepared request.\n\n        # This MUST go after prepare_auth. Authenticators could add a hook\n        self.prepare_hooks(hooks)\n\n    def __repr__(self):\n        return '<PreparedRequest [%s]>' % (self.method)\n\n    def copy(self):\n        p = PreparedRequest()\n        p.method = self.method\n        p.url = self.url\n        p.headers = self.headers.copy() if self.headers is not None else None\n        p._cookies = _copy_cookie_jar(self._cookies)\n        p.body = self.body\n        p.hooks = self.hooks\n        p._body_position = self._body_position\n        return p\n\n    def prepare_method(self, method):\n        \"\"\"Prepares the given HTTP method.\"\"\"\n        self.method = method\n        if self.method is not None:\n            self.method = to_native_string(self.method.upper())\n\n    @staticmethod\n    def _get_idna_encoded_host(host):\n        from pip._vendor import idna\n\n        try:\n            host = idna.encode(host, uts46=True).decode('utf-8')\n        except idna.IDNAError:\n            raise UnicodeError\n        return host\n\n    def prepare_url(self, url, params):\n        \"\"\"Prepares the given HTTP URL.\"\"\"\n        #: Accept objects that have string representations.\n        #: We're unable to blindly call unicode/str functions\n        #: as this will include the bytestring indicator (b'')\n        #: on python 3.x.\n        #: https://github.com/requests/requests/pull/2238\n        if isinstance(url, bytes):\n            url = url.decode('utf8')\n        else:\n            url = unicode(url) if is_py2 else str(url)\n\n        # Remove leading whitespaces from url\n        url = url.lstrip()\n\n        # Don't do any URL preparation for non-HTTP schemes like `mailto`,\n        # `data` etc to work around exceptions from `url_parse`, which\n        # handles RFC 3986 only.\n        if ':' in url and not url.lower().startswith('http'):\n            self.url = url\n            return\n\n        # Support for unicode domain names and paths.\n        try:\n            scheme, auth, host, port, path, query, fragment = parse_url(url)\n        except LocationParseError as e:\n            raise InvalidURL(*e.args)\n\n        if not scheme:\n            error = (\"Invalid URL {0!r}: No schema supplied. Perhaps you meant http://{0}?\")\n            error = error.format(to_native_string(url, 'utf8'))\n\n            raise MissingSchema(error)\n\n        if not host:\n            raise InvalidURL(\"Invalid URL %r: No host supplied\" % url)\n\n        # In general, we want to try IDNA encoding the hostname if the string contains\n        # non-ASCII characters. This allows users to automatically get the correct IDNA\n        # behaviour. For strings containing only ASCII characters, we need to also verify\n        # it doesn't start with a wildcard (*), before allowing the unencoded hostname.\n        if not unicode_is_ascii(host):\n            try:\n                host = self._get_idna_encoded_host(host)\n            except UnicodeError:\n                raise InvalidURL('URL has an invalid label.')\n        elif host.startswith(u'*'):\n            raise InvalidURL('URL has an invalid label.')\n\n        # Carefully reconstruct the network location\n        netloc = auth or ''\n        if netloc:\n            netloc += '@'\n        netloc += host\n        if port:\n            netloc += ':' + str(port)\n\n        # Bare domains aren't valid URLs.\n        if not path:\n            path = '/'\n\n        if is_py2:\n            if isinstance(scheme, str):\n                scheme = scheme.encode('utf-8')\n            if isinstance(netloc, str):\n                netloc = netloc.encode('utf-8')\n            if isinstance(path, str):\n                path = path.encode('utf-8')\n            if isinstance(query, str):\n                query = query.encode('utf-8')\n            if isinstance(fragment, str):\n                fragment = fragment.encode('utf-8')\n\n        if isinstance(params, (str, bytes)):\n            params = to_native_string(params)\n\n        enc_params = self._encode_params(params)\n        if enc_params:\n            if query:\n                query = '%s&%s' % (query, enc_params)\n            else:\n                query = enc_params\n\n        url = requote_uri(urlunparse([scheme, netloc, path, None, query, fragment]))\n        self.url = url\n\n    def prepare_headers(self, headers):\n        \"\"\"Prepares the given HTTP headers.\"\"\"\n\n        self.headers = CaseInsensitiveDict()\n        if headers:\n            for header in headers.items():\n                # Raise exception on invalid header value.\n                check_header_validity(header)\n                name, value = header\n                self.headers[to_native_string(name)] = value\n\n    def prepare_body(self, data, files, json=None):\n        \"\"\"Prepares the given HTTP body data.\"\"\"\n\n        # Check if file, fo, generator, iterator.\n        # If not, run through normal process.\n\n        # Nottin' on you.\n        body = None\n        content_type = None\n\n        if not data and json is not None:\n            # urllib3 requires a bytes-like body. Python 2's json.dumps\n            # provides this natively, but Python 3 gives a Unicode string.\n            content_type = 'application/json'\n            body = complexjson.dumps(json)\n            if not isinstance(body, bytes):\n                body = body.encode('utf-8')\n\n        is_stream = all([\n            hasattr(data, '__iter__'),\n            not isinstance(data, (basestring, list, tuple, Mapping))\n        ])\n\n        try:\n            length = super_len(data)\n        except (TypeError, AttributeError, UnsupportedOperation):\n            length = None\n\n        if is_stream:\n            body = data\n\n            if getattr(body, 'tell', None) is not None:\n                # Record the current file position before reading.\n                # This will allow us to rewind a file in the event\n                # of a redirect.\n                try:\n                    self._body_position = body.tell()\n                except (IOError, OSError):\n                    # This differentiates from None, allowing us to catch\n                    # a failed `tell()` later when trying to rewind the body\n                    self._body_position = object()\n\n            if files:\n                raise NotImplementedError('Streamed bodies and files are mutually exclusive.')\n\n            if length:\n                self.headers['Content-Length'] = builtin_str(length)\n            else:\n                self.headers['Transfer-Encoding'] = 'chunked'\n        else:\n            # Multi-part file uploads.\n            if files:\n                (body, content_type) = self._encode_files(files, data)\n            else:\n                if data:\n                    body = self._encode_params(data)\n                    if isinstance(data, basestring) or hasattr(data, 'read'):\n                        content_type = None\n                    else:\n                        content_type = 'application/x-www-form-urlencoded'\n\n            self.prepare_content_length(body)\n\n            # Add content-type if it wasn't explicitly provided.\n            if content_type and ('content-type' not in self.headers):\n                self.headers['Content-Type'] = content_type\n\n        self.body = body\n\n    def prepare_content_length(self, body):\n        \"\"\"Prepare Content-Length header based on request method and body\"\"\"\n        if body is not None:\n            length = super_len(body)\n            if length:\n                # If length exists, set it. Otherwise, we fallback\n                # to Transfer-Encoding: chunked.\n                self.headers['Content-Length'] = builtin_str(length)\n        elif self.method not in ('GET', 'HEAD') and self.headers.get('Content-Length') is None:\n            # Set Content-Length to 0 for methods that can have a body\n            # but don't provide one. (i.e. not GET or HEAD)\n            self.headers['Content-Length'] = '0'\n\n    def prepare_auth(self, auth, url=''):\n        \"\"\"Prepares the given HTTP auth data.\"\"\"\n\n        # If no Auth is explicitly provided, extract it from the URL first.\n        if auth is None:\n            url_auth = get_auth_from_url(self.url)\n            auth = url_auth if any(url_auth) else None\n\n        if auth:\n            if isinstance(auth, tuple) and len(auth) == 2:\n                # special-case basic HTTP auth\n                auth = HTTPBasicAuth(*auth)\n\n            # Allow auth to make its changes.\n            r = auth(self)\n\n            # Update self to reflect the auth changes.\n            self.__dict__.update(r.__dict__)\n\n            # Recompute Content-Length\n            self.prepare_content_length(self.body)\n\n    def prepare_cookies(self, cookies):\n        \"\"\"Prepares the given HTTP cookie data.\n\n        This function eventually generates a ``Cookie`` header from the\n        given cookies using cookielib. Due to cookielib's design, the header\n        will not be regenerated if it already exists, meaning this function\n        can only be called once for the life of the\n        :class:`PreparedRequest <PreparedRequest>` object. Any subsequent calls\n        to ``prepare_cookies`` will have no actual effect, unless the \"Cookie\"\n        header is removed beforehand.\n        \"\"\"\n        if isinstance(cookies, cookielib.CookieJar):\n            self._cookies = cookies\n        else:\n            self._cookies = cookiejar_from_dict(cookies)\n\n        cookie_header = get_cookie_header(self._cookies, self)\n        if cookie_header is not None:\n            self.headers['Cookie'] = cookie_header\n\n    def prepare_hooks(self, hooks):\n        \"\"\"Prepares the given hooks.\"\"\"\n        # hooks can be passed as None to the prepare method and to this\n        # method. To prevent iterating over None, simply use an empty list\n        # if hooks is False-y\n        hooks = hooks or []\n        for event in hooks:\n            self.register_hook(event, hooks[event])\n\n\nclass Response(object):\n    \"\"\"The :class:`Response <Response>` object, which contains a\n    server's response to an HTTP request.\n    \"\"\"\n\n    __attrs__ = [\n        '_content', 'status_code', 'headers', 'url', 'history',\n        'encoding', 'reason', 'cookies', 'elapsed', 'request'\n    ]\n\n    def __init__(self):\n        self._content = False\n        self._content_consumed = False\n        self._next = None\n\n        #: Integer Code of responded HTTP Status, e.g. 404 or 200.\n        self.status_code = None\n\n        #: Case-insensitive Dictionary of Response Headers.\n        #: For example, ``headers['content-encoding']`` will return the\n        #: value of a ``'Content-Encoding'`` response header.\n        self.headers = CaseInsensitiveDict()\n\n        #: File-like object representation of response (for advanced usage).\n        #: Use of ``raw`` requires that ``stream=True`` be set on the request.\n        # This requirement does not apply for use internally to Requests.\n        self.raw = None\n\n        #: Final URL location of Response.\n        self.url = None\n\n        #: Encoding to decode with when accessing r.text.\n        self.encoding = None\n\n        #: A list of :class:`Response <Response>` objects from\n        #: the history of the Request. Any redirect responses will end\n        #: up here. The list is sorted from the oldest to the most recent request.\n        self.history = []\n\n        #: Textual reason of responded HTTP Status, e.g. \"Not Found\" or \"OK\".\n        self.reason = None\n\n        #: A CookieJar of Cookies the server sent back.\n        self.cookies = cookiejar_from_dict({})\n\n        #: The amount of time elapsed between sending the request\n        #: and the arrival of the response (as a timedelta).\n        #: This property specifically measures the time taken between sending\n        #: the first byte of the request and finishing parsing the headers. It\n        #: is therefore unaffected by consuming the response content or the\n        #: value of the ``stream`` keyword argument.\n        self.elapsed = datetime.timedelta(0)\n\n        #: The :class:`PreparedRequest <PreparedRequest>` object to which this\n        #: is a response.\n        self.request = None\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, *args):\n        self.close()\n\n    def __getstate__(self):\n        # Consume everything; accessing the content attribute makes\n        # sure the content has been fully read.\n        if not self._content_consumed:\n            self.content\n\n        return {attr: getattr(self, attr, None) for attr in self.__attrs__}\n\n    def __setstate__(self, state):\n        for name, value in state.items():\n            setattr(self, name, value)\n\n        # pickled objects do not have .raw\n        setattr(self, '_content_consumed', True)\n        setattr(self, 'raw', None)\n\n    def __repr__(self):\n        return '<Response [%s]>' % (self.status_code)\n\n    def __bool__(self):\n        \"\"\"Returns True if :attr:`status_code` is less than 400.\n\n        This attribute checks if the status code of the response is between\n        400 and 600 to see if there was a client error or a server error. If\n        the status code, is between 200 and 400, this will return True. This\n        is **not** a check to see if the response code is ``200 OK``.\n        \"\"\"\n        return self.ok\n\n    def __nonzero__(self):\n        \"\"\"Returns True if :attr:`status_code` is less than 400.\n\n        This attribute checks if the status code of the response is between\n        400 and 600 to see if there was a client error or a server error. If\n        the status code, is between 200 and 400, this will return True. This\n        is **not** a check to see if the response code is ``200 OK``.\n        \"\"\"\n        return self.ok\n\n    def __iter__(self):\n        \"\"\"Allows you to use a response as an iterator.\"\"\"\n        return self.iter_content(128)\n\n    @property\n    def ok(self):\n        \"\"\"Returns True if :attr:`status_code` is less than 400, False if not.\n\n        This attribute checks if the status code of the response is between\n        400 and 600 to see if there was a client error or a server error. If\n        the status code is between 200 and 400, this will return True. This\n        is **not** a check to see if the response code is ``200 OK``.\n        \"\"\"\n        try:\n            self.raise_for_status()\n        except HTTPError:\n            return False\n        return True\n\n    @property\n    def is_redirect(self):\n        \"\"\"True if this Response is a well-formed HTTP redirect that could have\n        been processed automatically (by :meth:`Session.resolve_redirects`).\n        \"\"\"\n        return ('location' in self.headers and self.status_code in REDIRECT_STATI)\n\n    @property\n    def is_permanent_redirect(self):\n        \"\"\"True if this Response one of the permanent versions of redirect.\"\"\"\n        return ('location' in self.headers and self.status_code in (codes.moved_permanently, codes.permanent_redirect))\n\n    @property\n    def next(self):\n        \"\"\"Returns a PreparedRequest for the next request in a redirect chain, if there is one.\"\"\"\n        return self._next\n\n    @property\n    def apparent_encoding(self):\n        \"\"\"The apparent encoding, provided by the chardet library.\"\"\"\n        return chardet.detect(self.content)['encoding']\n\n    def iter_content(self, chunk_size=1, decode_unicode=False):\n        \"\"\"Iterates over the response data.  When stream=True is set on the\n        request, this avoids reading the content at once into memory for\n        large responses.  The chunk size is the number of bytes it should\n        read into memory.  This is not necessarily the length of each item\n        returned as decoding can take place.\n\n        chunk_size must be of type int or None. A value of None will\n        function differently depending on the value of `stream`.\n        stream=True will read data as it arrives in whatever size the\n        chunks are received. If stream=False, data is returned as\n        a single chunk.\n\n        If decode_unicode is True, content will be decoded using the best\n        available encoding based on the response.\n        \"\"\"\n\n        def generate():\n            # Special case for urllib3.\n            if hasattr(self.raw, 'stream'):\n                try:\n                    for chunk in self.raw.stream(chunk_size, decode_content=True):\n                        yield chunk\n                except ProtocolError as e:\n                    raise ChunkedEncodingError(e)\n                except DecodeError as e:\n                    raise ContentDecodingError(e)\n                except ReadTimeoutError as e:\n                    raise ConnectionError(e)\n            else:\n                # Standard file-like object.\n                while True:\n                    chunk = self.raw.read(chunk_size)\n                    if not chunk:\n                        break\n                    yield chunk\n\n            self._content_consumed = True\n\n        if self._content_consumed and isinstance(self._content, bool):\n            raise StreamConsumedError()\n        elif chunk_size is not None and not isinstance(chunk_size, int):\n            raise TypeError(\"chunk_size must be an int, it is instead a %s.\" % type(chunk_size))\n        # simulate reading small chunks of the content\n        reused_chunks = iter_slices(self._content, chunk_size)\n\n        stream_chunks = generate()\n\n        chunks = reused_chunks if self._content_consumed else stream_chunks\n\n        if decode_unicode:\n            chunks = stream_decode_response_unicode(chunks, self)\n\n        return chunks\n\n    def iter_lines(self, chunk_size=ITER_CHUNK_SIZE, decode_unicode=False, delimiter=None):\n        \"\"\"Iterates over the response data, one line at a time.  When\n        stream=True is set on the request, this avoids reading the\n        content at once into memory for large responses.\n\n        .. note:: This method is not reentrant safe.\n        \"\"\"\n\n        pending = None\n\n        for chunk in self.iter_content(chunk_size=chunk_size, decode_unicode=decode_unicode):\n\n            if pending is not None:\n                chunk = pending + chunk\n\n            if delimiter:\n                lines = chunk.split(delimiter)\n            else:\n                lines = chunk.splitlines()\n\n            if lines and lines[-1] and chunk and lines[-1][-1] == chunk[-1]:\n                pending = lines.pop()\n            else:\n                pending = None\n\n            for line in lines:\n                yield line\n\n        if pending is not None:\n            yield pending\n\n    @property\n    def content(self):\n        \"\"\"Content of the response, in bytes.\"\"\"\n\n        if self._content is False:\n            # Read the contents.\n            if self._content_consumed:\n                raise RuntimeError(\n                    'The content for this response was already consumed')\n\n            if self.status_code == 0 or self.raw is None:\n                self._content = None\n            else:\n                self._content = b''.join(self.iter_content(CONTENT_CHUNK_SIZE)) or b''\n\n        self._content_consumed = True\n        # don't need to release the connection; that's been handled by urllib3\n        # since we exhausted the data.\n        return self._content\n\n    @property\n    def text(self):\n        \"\"\"Content of the response, in unicode.\n\n        If Response.encoding is None, encoding will be guessed using\n        ``chardet``.\n\n        The encoding of the response content is determined based solely on HTTP\n        headers, following RFC 2616 to the letter. If you can take advantage of\n        non-HTTP knowledge to make a better guess at the encoding, you should\n        set ``r.encoding`` appropriately before accessing this property.\n        \"\"\"\n\n        # Try charset from content-type\n        content = None\n        encoding = self.encoding\n\n        if not self.content:\n            return str('')\n\n        # Fallback to auto-detected encoding.\n        if self.encoding is None:\n            encoding = self.apparent_encoding\n\n        # Decode unicode from given encoding.\n        try:\n            content = str(self.content, encoding, errors='replace')\n        except (LookupError, TypeError):\n            # A LookupError is raised if the encoding was not found which could\n            # indicate a misspelling or similar mistake.\n            #\n            # A TypeError can be raised if encoding is None\n            #\n            # So we try blindly encoding.\n            content = str(self.content, errors='replace')\n\n        return content\n\n    def json(self, **kwargs):\n        r\"\"\"Returns the json-encoded content of a response, if any.\n\n        :param \\*\\*kwargs: Optional arguments that ``json.loads`` takes.\n        :raises ValueError: If the response body does not contain valid json.\n        \"\"\"\n\n        if not self.encoding and self.content and len(self.content) > 3:\n            # No encoding set. JSON RFC 4627 section 3 states we should expect\n            # UTF-8, -16 or -32. Detect which one to use; If the detection or\n            # decoding fails, fall back to `self.text` (using chardet to make\n            # a best guess).\n            encoding = guess_json_utf(self.content)\n            if encoding is not None:\n                try:\n                    return complexjson.loads(\n                        self.content.decode(encoding), **kwargs\n                    )\n                except UnicodeDecodeError:\n                    # Wrong UTF codec detected; usually because it's not UTF-8\n                    # but some other 8-bit codec.  This is an RFC violation,\n                    # and the server didn't bother to tell us what codec *was*\n                    # used.\n                    pass\n        return complexjson.loads(self.text, **kwargs)\n\n    @property\n    def links(self):\n        \"\"\"Returns the parsed header links of the response, if any.\"\"\"\n\n        header = self.headers.get('link')\n\n        # l = MultiDict()\n        l = {}\n\n        if header:\n            links = parse_header_links(header)\n\n            for link in links:\n                key = link.get('rel') or link.get('url')\n                l[key] = link\n\n        return l\n\n    def raise_for_status(self):\n        \"\"\"Raises stored :class:`HTTPError`, if one occurred.\"\"\"\n\n        http_error_msg = ''\n        if isinstance(self.reason, bytes):\n            # We attempt to decode utf-8 first because some servers\n            # choose to localize their reason strings. If the string\n            # isn't utf-8, we fall back to iso-8859-1 for all other\n            # encodings. (See PR #3538)\n            try:\n                reason = self.reason.decode('utf-8')\n            except UnicodeDecodeError:\n                reason = self.reason.decode('iso-8859-1')\n        else:\n            reason = self.reason\n\n        if 400 <= self.status_code < 500:\n            http_error_msg = u'%s Client Error: %s for url: %s' % (self.status_code, reason, self.url)\n\n        elif 500 <= self.status_code < 600:\n            http_error_msg = u'%s Server Error: %s for url: %s' % (self.status_code, reason, self.url)\n\n        if http_error_msg:\n            raise HTTPError(http_error_msg, response=self)\n\n    def close(self):\n        \"\"\"Releases the connection back to the pool. Once this method has been\n        called the underlying ``raw`` object must not be accessed again.\n\n        *Note: Should not normally need to be called explicitly.*\n        \"\"\"\n        if not self._content_consumed:\n            self.raw.close()\n\n        release_conn = getattr(self.raw, 'release_conn', None)\n        if release_conn is not None:\n            release_conn()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/packages.py",
    "content": "import sys\n\n# This code exists for backwards compatibility reasons.\n# I don't like it either. Just look the other way. :)\n\nfor package in ('urllib3', 'idna', 'chardet'):\n    vendored_package = \"pip._vendor.\" + package\n    locals()[package] = __import__(vendored_package)\n    # This traversal is apparently necessary such that the identities are\n    # preserved (requests.packages.urllib3.* is urllib3.*)\n    for mod in list(sys.modules):\n        if mod == vendored_package or mod.startswith(vendored_package + '.'):\n            unprefixed_mod = mod[len(\"pip._vendor.\"):]\n            sys.modules['pip._vendor.requests.packages.' + unprefixed_mod] = sys.modules[mod]\n\n# Kinda cool, though, right?\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/sessions.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests.session\n~~~~~~~~~~~~~~~~\n\nThis module provides a Session object to manage and persist settings across\nrequests (cookies, auth, proxies).\n\"\"\"\nimport os\nimport sys\nimport time\nfrom datetime import timedelta\n\nfrom .auth import _basic_auth_str\nfrom .compat import cookielib, is_py3, OrderedDict, urljoin, urlparse, Mapping\nfrom .cookies import (\n    cookiejar_from_dict, extract_cookies_to_jar, RequestsCookieJar, merge_cookies)\nfrom .models import Request, PreparedRequest, DEFAULT_REDIRECT_LIMIT\nfrom .hooks import default_hooks, dispatch_hook\nfrom ._internal_utils import to_native_string\nfrom .utils import to_key_val_list, default_headers, DEFAULT_PORTS\nfrom .exceptions import (\n    TooManyRedirects, InvalidSchema, ChunkedEncodingError, ContentDecodingError)\n\nfrom .structures import CaseInsensitiveDict\nfrom .adapters import HTTPAdapter\n\nfrom .utils import (\n    requote_uri, get_environ_proxies, get_netrc_auth, should_bypass_proxies,\n    get_auth_from_url, rewind_body\n)\n\nfrom .status_codes import codes\n\n# formerly defined here, reexposed here for backward compatibility\nfrom .models import REDIRECT_STATI\n\n# Preferred clock, based on which one is more accurate on a given system.\nif sys.platform == 'win32':\n    try:  # Python 3.4+\n        preferred_clock = time.perf_counter\n    except AttributeError:  # Earlier than Python 3.\n        preferred_clock = time.clock\nelse:\n    preferred_clock = time.time\n\n\ndef merge_setting(request_setting, session_setting, dict_class=OrderedDict):\n    \"\"\"Determines appropriate setting for a given request, taking into account\n    the explicit setting on that request, and the setting in the session. If a\n    setting is a dictionary, they will be merged together using `dict_class`\n    \"\"\"\n\n    if session_setting is None:\n        return request_setting\n\n    if request_setting is None:\n        return session_setting\n\n    # Bypass if not a dictionary (e.g. verify)\n    if not (\n            isinstance(session_setting, Mapping) and\n            isinstance(request_setting, Mapping)\n    ):\n        return request_setting\n\n    merged_setting = dict_class(to_key_val_list(session_setting))\n    merged_setting.update(to_key_val_list(request_setting))\n\n    # Remove keys that are set to None. Extract keys first to avoid altering\n    # the dictionary during iteration.\n    none_keys = [k for (k, v) in merged_setting.items() if v is None]\n    for key in none_keys:\n        del merged_setting[key]\n\n    return merged_setting\n\n\ndef merge_hooks(request_hooks, session_hooks, dict_class=OrderedDict):\n    \"\"\"Properly merges both requests and session hooks.\n\n    This is necessary because when request_hooks == {'response': []}, the\n    merge breaks Session hooks entirely.\n    \"\"\"\n    if session_hooks is None or session_hooks.get('response') == []:\n        return request_hooks\n\n    if request_hooks is None or request_hooks.get('response') == []:\n        return session_hooks\n\n    return merge_setting(request_hooks, session_hooks, dict_class)\n\n\nclass SessionRedirectMixin(object):\n\n    def get_redirect_target(self, resp):\n        \"\"\"Receives a Response. Returns a redirect URI or ``None``\"\"\"\n        # Due to the nature of how requests processes redirects this method will\n        # be called at least once upon the original response and at least twice\n        # on each subsequent redirect response (if any).\n        # If a custom mixin is used to handle this logic, it may be advantageous\n        # to cache the redirect location onto the response object as a private\n        # attribute.\n        if resp.is_redirect:\n            location = resp.headers['location']\n            # Currently the underlying http module on py3 decode headers\n            # in latin1, but empirical evidence suggests that latin1 is very\n            # rarely used with non-ASCII characters in HTTP headers.\n            # It is more likely to get UTF8 header rather than latin1.\n            # This causes incorrect handling of UTF8 encoded location headers.\n            # To solve this, we re-encode the location in latin1.\n            if is_py3:\n                location = location.encode('latin1')\n            return to_native_string(location, 'utf8')\n        return None\n\n    def should_strip_auth(self, old_url, new_url):\n        \"\"\"Decide whether Authorization header should be removed when redirecting\"\"\"\n        old_parsed = urlparse(old_url)\n        new_parsed = urlparse(new_url)\n        if old_parsed.hostname != new_parsed.hostname:\n            return True\n        # Special case: allow http -> https redirect when using the standard\n        # ports. This isn't specified by RFC 7235, but is kept to avoid\n        # breaking backwards compatibility with older versions of requests\n        # that allowed any redirects on the same host.\n        if (old_parsed.scheme == 'http' and old_parsed.port in (80, None)\n                and new_parsed.scheme == 'https' and new_parsed.port in (443, None)):\n            return False\n\n        # Handle default port usage corresponding to scheme.\n        changed_port = old_parsed.port != new_parsed.port\n        changed_scheme = old_parsed.scheme != new_parsed.scheme\n        default_port = (DEFAULT_PORTS.get(old_parsed.scheme, None), None)\n        if (not changed_scheme and old_parsed.port in default_port\n                and new_parsed.port in default_port):\n            return False\n\n        # Standard case: root URI must match\n        return changed_port or changed_scheme\n\n    def resolve_redirects(self, resp, req, stream=False, timeout=None,\n                          verify=True, cert=None, proxies=None, yield_requests=False, **adapter_kwargs):\n        \"\"\"Receives a Response. Returns a generator of Responses or Requests.\"\"\"\n\n        hist = []  # keep track of history\n\n        url = self.get_redirect_target(resp)\n        previous_fragment = urlparse(req.url).fragment\n        while url:\n            prepared_request = req.copy()\n\n            # Update history and keep track of redirects.\n            # resp.history must ignore the original request in this loop\n            hist.append(resp)\n            resp.history = hist[1:]\n\n            try:\n                resp.content  # Consume socket so it can be released\n            except (ChunkedEncodingError, ContentDecodingError, RuntimeError):\n                resp.raw.read(decode_content=False)\n\n            if len(resp.history) >= self.max_redirects:\n                raise TooManyRedirects('Exceeded %s redirects.' % self.max_redirects, response=resp)\n\n            # Release the connection back into the pool.\n            resp.close()\n\n            # Handle redirection without scheme (see: RFC 1808 Section 4)\n            if url.startswith('//'):\n                parsed_rurl = urlparse(resp.url)\n                url = '%s:%s' % (to_native_string(parsed_rurl.scheme), url)\n\n            # Normalize url case and attach previous fragment if needed (RFC 7231 7.1.2)\n            parsed = urlparse(url)\n            if parsed.fragment == '' and previous_fragment:\n                parsed = parsed._replace(fragment=previous_fragment)\n            elif parsed.fragment:\n                previous_fragment = parsed.fragment\n            url = parsed.geturl()\n\n            # Facilitate relative 'location' headers, as allowed by RFC 7231.\n            # (e.g. '/path/to/resource' instead of 'http://domain.tld/path/to/resource')\n            # Compliant with RFC3986, we percent encode the url.\n            if not parsed.netloc:\n                url = urljoin(resp.url, requote_uri(url))\n            else:\n                url = requote_uri(url)\n\n            prepared_request.url = to_native_string(url)\n\n            self.rebuild_method(prepared_request, resp)\n\n            # https://github.com/requests/requests/issues/1084\n            if resp.status_code not in (codes.temporary_redirect, codes.permanent_redirect):\n                # https://github.com/requests/requests/issues/3490\n                purged_headers = ('Content-Length', 'Content-Type', 'Transfer-Encoding')\n                for header in purged_headers:\n                    prepared_request.headers.pop(header, None)\n                prepared_request.body = None\n\n            headers = prepared_request.headers\n            try:\n                del headers['Cookie']\n            except KeyError:\n                pass\n\n            # Extract any cookies sent on the response to the cookiejar\n            # in the new request. Because we've mutated our copied prepared\n            # request, use the old one that we haven't yet touched.\n            extract_cookies_to_jar(prepared_request._cookies, req, resp.raw)\n            merge_cookies(prepared_request._cookies, self.cookies)\n            prepared_request.prepare_cookies(prepared_request._cookies)\n\n            # Rebuild auth and proxy information.\n            proxies = self.rebuild_proxies(prepared_request, proxies)\n            self.rebuild_auth(prepared_request, resp)\n\n            # A failed tell() sets `_body_position` to `object()`. This non-None\n            # value ensures `rewindable` will be True, allowing us to raise an\n            # UnrewindableBodyError, instead of hanging the connection.\n            rewindable = (\n                prepared_request._body_position is not None and\n                ('Content-Length' in headers or 'Transfer-Encoding' in headers)\n            )\n\n            # Attempt to rewind consumed file-like object.\n            if rewindable:\n                rewind_body(prepared_request)\n\n            # Override the original request.\n            req = prepared_request\n\n            if yield_requests:\n                yield req\n            else:\n\n                resp = self.send(\n                    req,\n                    stream=stream,\n                    timeout=timeout,\n                    verify=verify,\n                    cert=cert,\n                    proxies=proxies,\n                    allow_redirects=False,\n                    **adapter_kwargs\n                )\n\n                extract_cookies_to_jar(self.cookies, prepared_request, resp.raw)\n\n                # extract redirect url, if any, for the next loop\n                url = self.get_redirect_target(resp)\n                yield resp\n\n    def rebuild_auth(self, prepared_request, response):\n        \"\"\"When being redirected we may want to strip authentication from the\n        request to avoid leaking credentials. This method intelligently removes\n        and reapplies authentication where possible to avoid credential loss.\n        \"\"\"\n        headers = prepared_request.headers\n        url = prepared_request.url\n\n        if 'Authorization' in headers and self.should_strip_auth(response.request.url, url):\n            # If we get redirected to a new host, we should strip out any\n            # authentication headers.\n            del headers['Authorization']\n\n        # .netrc might have more auth for us on our new host.\n        new_auth = get_netrc_auth(url) if self.trust_env else None\n        if new_auth is not None:\n            prepared_request.prepare_auth(new_auth)\n\n        return\n\n    def rebuild_proxies(self, prepared_request, proxies):\n        \"\"\"This method re-evaluates the proxy configuration by considering the\n        environment variables. If we are redirected to a URL covered by\n        NO_PROXY, we strip the proxy configuration. Otherwise, we set missing\n        proxy keys for this URL (in case they were stripped by a previous\n        redirect).\n\n        This method also replaces the Proxy-Authorization header where\n        necessary.\n\n        :rtype: dict\n        \"\"\"\n        proxies = proxies if proxies is not None else {}\n        headers = prepared_request.headers\n        url = prepared_request.url\n        scheme = urlparse(url).scheme\n        new_proxies = proxies.copy()\n        no_proxy = proxies.get('no_proxy')\n\n        bypass_proxy = should_bypass_proxies(url, no_proxy=no_proxy)\n        if self.trust_env and not bypass_proxy:\n            environ_proxies = get_environ_proxies(url, no_proxy=no_proxy)\n\n            proxy = environ_proxies.get(scheme, environ_proxies.get('all'))\n\n            if proxy:\n                new_proxies.setdefault(scheme, proxy)\n\n        if 'Proxy-Authorization' in headers:\n            del headers['Proxy-Authorization']\n\n        try:\n            username, password = get_auth_from_url(new_proxies[scheme])\n        except KeyError:\n            username, password = None, None\n\n        if username and password:\n            headers['Proxy-Authorization'] = _basic_auth_str(username, password)\n\n        return new_proxies\n\n    def rebuild_method(self, prepared_request, response):\n        \"\"\"When being redirected we may want to change the method of the request\n        based on certain specs or browser behavior.\n        \"\"\"\n        method = prepared_request.method\n\n        # https://tools.ietf.org/html/rfc7231#section-6.4.4\n        if response.status_code == codes.see_other and method != 'HEAD':\n            method = 'GET'\n\n        # Do what the browsers do, despite standards...\n        # First, turn 302s into GETs.\n        if response.status_code == codes.found and method != 'HEAD':\n            method = 'GET'\n\n        # Second, if a POST is responded to with a 301, turn it into a GET.\n        # This bizarre behaviour is explained in Issue 1704.\n        if response.status_code == codes.moved and method == 'POST':\n            method = 'GET'\n\n        prepared_request.method = method\n\n\nclass Session(SessionRedirectMixin):\n    \"\"\"A Requests session.\n\n    Provides cookie persistence, connection-pooling, and configuration.\n\n    Basic Usage::\n\n      >>> import requests\n      >>> s = requests.Session()\n      >>> s.get('https://httpbin.org/get')\n      <Response [200]>\n\n    Or as a context manager::\n\n      >>> with requests.Session() as s:\n      >>>     s.get('https://httpbin.org/get')\n      <Response [200]>\n    \"\"\"\n\n    __attrs__ = [\n        'headers', 'cookies', 'auth', 'proxies', 'hooks', 'params', 'verify',\n        'cert', 'prefetch', 'adapters', 'stream', 'trust_env',\n        'max_redirects',\n    ]\n\n    def __init__(self):\n\n        #: A case-insensitive dictionary of headers to be sent on each\n        #: :class:`Request <Request>` sent from this\n        #: :class:`Session <Session>`.\n        self.headers = default_headers()\n\n        #: Default Authentication tuple or object to attach to\n        #: :class:`Request <Request>`.\n        self.auth = None\n\n        #: Dictionary mapping protocol or protocol and host to the URL of the proxy\n        #: (e.g. {'http': 'foo.bar:3128', 'http://host.name': 'foo.bar:4012'}) to\n        #: be used on each :class:`Request <Request>`.\n        self.proxies = {}\n\n        #: Event-handling hooks.\n        self.hooks = default_hooks()\n\n        #: Dictionary of querystring data to attach to each\n        #: :class:`Request <Request>`. The dictionary values may be lists for\n        #: representing multivalued query parameters.\n        self.params = {}\n\n        #: Stream response content default.\n        self.stream = False\n\n        #: SSL Verification default.\n        self.verify = True\n\n        #: SSL client certificate default, if String, path to ssl client\n        #: cert file (.pem). If Tuple, ('cert', 'key') pair.\n        self.cert = None\n\n        #: Maximum number of redirects allowed. If the request exceeds this\n        #: limit, a :class:`TooManyRedirects` exception is raised.\n        #: This defaults to requests.models.DEFAULT_REDIRECT_LIMIT, which is\n        #: 30.\n        self.max_redirects = DEFAULT_REDIRECT_LIMIT\n\n        #: Trust environment settings for proxy configuration, default\n        #: authentication and similar.\n        self.trust_env = True\n\n        #: A CookieJar containing all currently outstanding cookies set on this\n        #: session. By default it is a\n        #: :class:`RequestsCookieJar <requests.cookies.RequestsCookieJar>`, but\n        #: may be any other ``cookielib.CookieJar`` compatible object.\n        self.cookies = cookiejar_from_dict({})\n\n        # Default connection adapters.\n        self.adapters = OrderedDict()\n        self.mount('https://', HTTPAdapter())\n        self.mount('http://', HTTPAdapter())\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, *args):\n        self.close()\n\n    def prepare_request(self, request):\n        \"\"\"Constructs a :class:`PreparedRequest <PreparedRequest>` for\n        transmission and returns it. The :class:`PreparedRequest` has settings\n        merged from the :class:`Request <Request>` instance and those of the\n        :class:`Session`.\n\n        :param request: :class:`Request` instance to prepare with this\n            session's settings.\n        :rtype: requests.PreparedRequest\n        \"\"\"\n        cookies = request.cookies or {}\n\n        # Bootstrap CookieJar.\n        if not isinstance(cookies, cookielib.CookieJar):\n            cookies = cookiejar_from_dict(cookies)\n\n        # Merge with session cookies\n        merged_cookies = merge_cookies(\n            merge_cookies(RequestsCookieJar(), self.cookies), cookies)\n\n        # Set environment's basic authentication if not explicitly set.\n        auth = request.auth\n        if self.trust_env and not auth and not self.auth:\n            auth = get_netrc_auth(request.url)\n\n        p = PreparedRequest()\n        p.prepare(\n            method=request.method.upper(),\n            url=request.url,\n            files=request.files,\n            data=request.data,\n            json=request.json,\n            headers=merge_setting(request.headers, self.headers, dict_class=CaseInsensitiveDict),\n            params=merge_setting(request.params, self.params),\n            auth=merge_setting(auth, self.auth),\n            cookies=merged_cookies,\n            hooks=merge_hooks(request.hooks, self.hooks),\n        )\n        return p\n\n    def request(self, method, url,\n            params=None, data=None, headers=None, cookies=None, files=None,\n            auth=None, timeout=None, allow_redirects=True, proxies=None,\n            hooks=None, stream=None, verify=None, cert=None, json=None):\n        \"\"\"Constructs a :class:`Request <Request>`, prepares it and sends it.\n        Returns :class:`Response <Response>` object.\n\n        :param method: method for the new :class:`Request` object.\n        :param url: URL for the new :class:`Request` object.\n        :param params: (optional) Dictionary or bytes to be sent in the query\n            string for the :class:`Request`.\n        :param data: (optional) Dictionary, list of tuples, bytes, or file-like\n            object to send in the body of the :class:`Request`.\n        :param json: (optional) json to send in the body of the\n            :class:`Request`.\n        :param headers: (optional) Dictionary of HTTP Headers to send with the\n            :class:`Request`.\n        :param cookies: (optional) Dict or CookieJar object to send with the\n            :class:`Request`.\n        :param files: (optional) Dictionary of ``'filename': file-like-objects``\n            for multipart encoding upload.\n        :param auth: (optional) Auth tuple or callable to enable\n            Basic/Digest/Custom HTTP Auth.\n        :param timeout: (optional) How long to wait for the server to send\n            data before giving up, as a float, or a :ref:`(connect timeout,\n            read timeout) <timeouts>` tuple.\n        :type timeout: float or tuple\n        :param allow_redirects: (optional) Set to True by default.\n        :type allow_redirects: bool\n        :param proxies: (optional) Dictionary mapping protocol or protocol and\n            hostname to the URL of the proxy.\n        :param stream: (optional) whether to immediately download the response\n            content. Defaults to ``False``.\n        :param verify: (optional) Either a boolean, in which case it controls whether we verify\n            the server's TLS certificate, or a string, in which case it must be a path\n            to a CA bundle to use. Defaults to ``True``.\n        :param cert: (optional) if String, path to ssl client cert file (.pem).\n            If Tuple, ('cert', 'key') pair.\n        :rtype: requests.Response\n        \"\"\"\n        # Create the Request.\n        req = Request(\n            method=method.upper(),\n            url=url,\n            headers=headers,\n            files=files,\n            data=data or {},\n            json=json,\n            params=params or {},\n            auth=auth,\n            cookies=cookies,\n            hooks=hooks,\n        )\n        prep = self.prepare_request(req)\n\n        proxies = proxies or {}\n\n        settings = self.merge_environment_settings(\n            prep.url, proxies, stream, verify, cert\n        )\n\n        # Send the request.\n        send_kwargs = {\n            'timeout': timeout,\n            'allow_redirects': allow_redirects,\n        }\n        send_kwargs.update(settings)\n        resp = self.send(prep, **send_kwargs)\n\n        return resp\n\n    def get(self, url, **kwargs):\n        r\"\"\"Sends a GET request. Returns :class:`Response` object.\n\n        :param url: URL for the new :class:`Request` object.\n        :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n        :rtype: requests.Response\n        \"\"\"\n\n        kwargs.setdefault('allow_redirects', True)\n        return self.request('GET', url, **kwargs)\n\n    def options(self, url, **kwargs):\n        r\"\"\"Sends a OPTIONS request. Returns :class:`Response` object.\n\n        :param url: URL for the new :class:`Request` object.\n        :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n        :rtype: requests.Response\n        \"\"\"\n\n        kwargs.setdefault('allow_redirects', True)\n        return self.request('OPTIONS', url, **kwargs)\n\n    def head(self, url, **kwargs):\n        r\"\"\"Sends a HEAD request. Returns :class:`Response` object.\n\n        :param url: URL for the new :class:`Request` object.\n        :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n        :rtype: requests.Response\n        \"\"\"\n\n        kwargs.setdefault('allow_redirects', False)\n        return self.request('HEAD', url, **kwargs)\n\n    def post(self, url, data=None, json=None, **kwargs):\n        r\"\"\"Sends a POST request. Returns :class:`Response` object.\n\n        :param url: URL for the new :class:`Request` object.\n        :param data: (optional) Dictionary, list of tuples, bytes, or file-like\n            object to send in the body of the :class:`Request`.\n        :param json: (optional) json to send in the body of the :class:`Request`.\n        :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n        :rtype: requests.Response\n        \"\"\"\n\n        return self.request('POST', url, data=data, json=json, **kwargs)\n\n    def put(self, url, data=None, **kwargs):\n        r\"\"\"Sends a PUT request. Returns :class:`Response` object.\n\n        :param url: URL for the new :class:`Request` object.\n        :param data: (optional) Dictionary, list of tuples, bytes, or file-like\n            object to send in the body of the :class:`Request`.\n        :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n        :rtype: requests.Response\n        \"\"\"\n\n        return self.request('PUT', url, data=data, **kwargs)\n\n    def patch(self, url, data=None, **kwargs):\n        r\"\"\"Sends a PATCH request. Returns :class:`Response` object.\n\n        :param url: URL for the new :class:`Request` object.\n        :param data: (optional) Dictionary, list of tuples, bytes, or file-like\n            object to send in the body of the :class:`Request`.\n        :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n        :rtype: requests.Response\n        \"\"\"\n\n        return self.request('PATCH', url, data=data, **kwargs)\n\n    def delete(self, url, **kwargs):\n        r\"\"\"Sends a DELETE request. Returns :class:`Response` object.\n\n        :param url: URL for the new :class:`Request` object.\n        :param \\*\\*kwargs: Optional arguments that ``request`` takes.\n        :rtype: requests.Response\n        \"\"\"\n\n        return self.request('DELETE', url, **kwargs)\n\n    def send(self, request, **kwargs):\n        \"\"\"Send a given PreparedRequest.\n\n        :rtype: requests.Response\n        \"\"\"\n        # Set defaults that the hooks can utilize to ensure they always have\n        # the correct parameters to reproduce the previous request.\n        kwargs.setdefault('stream', self.stream)\n        kwargs.setdefault('verify', self.verify)\n        kwargs.setdefault('cert', self.cert)\n        kwargs.setdefault('proxies', self.proxies)\n\n        # It's possible that users might accidentally send a Request object.\n        # Guard against that specific failure case.\n        if isinstance(request, Request):\n            raise ValueError('You can only send PreparedRequests.')\n\n        # Set up variables needed for resolve_redirects and dispatching of hooks\n        allow_redirects = kwargs.pop('allow_redirects', True)\n        stream = kwargs.get('stream')\n        hooks = request.hooks\n\n        # Get the appropriate adapter to use\n        adapter = self.get_adapter(url=request.url)\n\n        # Start time (approximately) of the request\n        start = preferred_clock()\n\n        # Send the request\n        r = adapter.send(request, **kwargs)\n\n        # Total elapsed time of the request (approximately)\n        elapsed = preferred_clock() - start\n        r.elapsed = timedelta(seconds=elapsed)\n\n        # Response manipulation hooks\n        r = dispatch_hook('response', hooks, r, **kwargs)\n\n        # Persist cookies\n        if r.history:\n\n            # If the hooks create history then we want those cookies too\n            for resp in r.history:\n                extract_cookies_to_jar(self.cookies, resp.request, resp.raw)\n\n        extract_cookies_to_jar(self.cookies, request, r.raw)\n\n        # Redirect resolving generator.\n        gen = self.resolve_redirects(r, request, **kwargs)\n\n        # Resolve redirects if allowed.\n        history = [resp for resp in gen] if allow_redirects else []\n\n        # Shuffle things around if there's history.\n        if history:\n            # Insert the first (original) request at the start\n            history.insert(0, r)\n            # Get the last request made\n            r = history.pop()\n            r.history = history\n\n        # If redirects aren't being followed, store the response on the Request for Response.next().\n        if not allow_redirects:\n            try:\n                r._next = next(self.resolve_redirects(r, request, yield_requests=True, **kwargs))\n            except StopIteration:\n                pass\n\n        if not stream:\n            r.content\n\n        return r\n\n    def merge_environment_settings(self, url, proxies, stream, verify, cert):\n        \"\"\"\n        Check the environment and merge it with some settings.\n\n        :rtype: dict\n        \"\"\"\n        # Gather clues from the surrounding environment.\n        if self.trust_env:\n            # Set environment's proxies.\n            no_proxy = proxies.get('no_proxy') if proxies is not None else None\n            env_proxies = get_environ_proxies(url, no_proxy=no_proxy)\n            for (k, v) in env_proxies.items():\n                proxies.setdefault(k, v)\n\n            # Look for requests environment configuration and be compatible\n            # with cURL.\n            if verify is True or verify is None:\n                verify = (os.environ.get('REQUESTS_CA_BUNDLE') or\n                          os.environ.get('CURL_CA_BUNDLE'))\n\n        # Merge all the kwargs.\n        proxies = merge_setting(proxies, self.proxies)\n        stream = merge_setting(stream, self.stream)\n        verify = merge_setting(verify, self.verify)\n        cert = merge_setting(cert, self.cert)\n\n        return {'verify': verify, 'proxies': proxies, 'stream': stream,\n                'cert': cert}\n\n    def get_adapter(self, url):\n        \"\"\"\n        Returns the appropriate connection adapter for the given URL.\n\n        :rtype: requests.adapters.BaseAdapter\n        \"\"\"\n        for (prefix, adapter) in self.adapters.items():\n\n            if url.lower().startswith(prefix.lower()):\n                return adapter\n\n        # Nothing matches :-/\n        raise InvalidSchema(\"No connection adapters were found for '%s'\" % url)\n\n    def close(self):\n        \"\"\"Closes all adapters and as such the session\"\"\"\n        for v in self.adapters.values():\n            v.close()\n\n    def mount(self, prefix, adapter):\n        \"\"\"Registers a connection adapter to a prefix.\n\n        Adapters are sorted in descending order by prefix length.\n        \"\"\"\n        self.adapters[prefix] = adapter\n        keys_to_move = [k for k in self.adapters if len(k) < len(prefix)]\n\n        for key in keys_to_move:\n            self.adapters[key] = self.adapters.pop(key)\n\n    def __getstate__(self):\n        state = {attr: getattr(self, attr, None) for attr in self.__attrs__}\n        return state\n\n    def __setstate__(self, state):\n        for attr, value in state.items():\n            setattr(self, attr, value)\n\n\ndef session():\n    \"\"\"\n    Returns a :class:`Session` for context-management.\n\n    .. deprecated:: 1.0.0\n\n        This method has been deprecated since version 1.0.0 and is only kept for\n        backwards compatibility. New code should use :class:`~requests.sessions.Session`\n        to create a session. This may be removed at a future date.\n\n    :rtype: Session\n    \"\"\"\n    return Session()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/status_codes.py",
    "content": "# -*- coding: utf-8 -*-\n\nr\"\"\"\nThe ``codes`` object defines a mapping from common names for HTTP statuses\nto their numerical codes, accessible either as attributes or as dictionary\nitems.\n\n>>> requests.codes['temporary_redirect']\n307\n>>> requests.codes.teapot\n418\n>>> requests.codes['\\o/']\n200\n\nSome codes have multiple names, and both upper- and lower-case versions of\nthe names are allowed. For example, ``codes.ok``, ``codes.OK``, and\n``codes.okay`` all correspond to the HTTP status code 200.\n\"\"\"\n\nfrom .structures import LookupDict\n\n_codes = {\n\n    # Informational.\n    100: ('continue',),\n    101: ('switching_protocols',),\n    102: ('processing',),\n    103: ('checkpoint',),\n    122: ('uri_too_long', 'request_uri_too_long'),\n    200: ('ok', 'okay', 'all_ok', 'all_okay', 'all_good', '\\\\o/', '✓'),\n    201: ('created',),\n    202: ('accepted',),\n    203: ('non_authoritative_info', 'non_authoritative_information'),\n    204: ('no_content',),\n    205: ('reset_content', 'reset'),\n    206: ('partial_content', 'partial'),\n    207: ('multi_status', 'multiple_status', 'multi_stati', 'multiple_stati'),\n    208: ('already_reported',),\n    226: ('im_used',),\n\n    # Redirection.\n    300: ('multiple_choices',),\n    301: ('moved_permanently', 'moved', '\\\\o-'),\n    302: ('found',),\n    303: ('see_other', 'other'),\n    304: ('not_modified',),\n    305: ('use_proxy',),\n    306: ('switch_proxy',),\n    307: ('temporary_redirect', 'temporary_moved', 'temporary'),\n    308: ('permanent_redirect',\n          'resume_incomplete', 'resume',),  # These 2 to be removed in 3.0\n\n    # Client Error.\n    400: ('bad_request', 'bad'),\n    401: ('unauthorized',),\n    402: ('payment_required', 'payment'),\n    403: ('forbidden',),\n    404: ('not_found', '-o-'),\n    405: ('method_not_allowed', 'not_allowed'),\n    406: ('not_acceptable',),\n    407: ('proxy_authentication_required', 'proxy_auth', 'proxy_authentication'),\n    408: ('request_timeout', 'timeout'),\n    409: ('conflict',),\n    410: ('gone',),\n    411: ('length_required',),\n    412: ('precondition_failed', 'precondition'),\n    413: ('request_entity_too_large',),\n    414: ('request_uri_too_large',),\n    415: ('unsupported_media_type', 'unsupported_media', 'media_type'),\n    416: ('requested_range_not_satisfiable', 'requested_range', 'range_not_satisfiable'),\n    417: ('expectation_failed',),\n    418: ('im_a_teapot', 'teapot', 'i_am_a_teapot'),\n    421: ('misdirected_request',),\n    422: ('unprocessable_entity', 'unprocessable'),\n    423: ('locked',),\n    424: ('failed_dependency', 'dependency'),\n    425: ('unordered_collection', 'unordered'),\n    426: ('upgrade_required', 'upgrade'),\n    428: ('precondition_required', 'precondition'),\n    429: ('too_many_requests', 'too_many'),\n    431: ('header_fields_too_large', 'fields_too_large'),\n    444: ('no_response', 'none'),\n    449: ('retry_with', 'retry'),\n    450: ('blocked_by_windows_parental_controls', 'parental_controls'),\n    451: ('unavailable_for_legal_reasons', 'legal_reasons'),\n    499: ('client_closed_request',),\n\n    # Server Error.\n    500: ('internal_server_error', 'server_error', '/o\\\\', '✗'),\n    501: ('not_implemented',),\n    502: ('bad_gateway',),\n    503: ('service_unavailable', 'unavailable'),\n    504: ('gateway_timeout',),\n    505: ('http_version_not_supported', 'http_version'),\n    506: ('variant_also_negotiates',),\n    507: ('insufficient_storage',),\n    509: ('bandwidth_limit_exceeded', 'bandwidth'),\n    510: ('not_extended',),\n    511: ('network_authentication_required', 'network_auth', 'network_authentication'),\n}\n\ncodes = LookupDict(name='status_codes')\n\ndef _init():\n    for code, titles in _codes.items():\n        for title in titles:\n            setattr(codes, title, code)\n            if not title.startswith(('\\\\', '/')):\n                setattr(codes, title.upper(), code)\n\n    def doc(code):\n        names = ', '.join('``%s``' % n for n in _codes[code])\n        return '* %d: %s' % (code, names)\n\n    global __doc__\n    __doc__ = (__doc__ + '\\n' +\n               '\\n'.join(doc(code) for code in sorted(_codes))\n               if __doc__ is not None else None)\n\n_init()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/structures.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests.structures\n~~~~~~~~~~~~~~~~~~~\n\nData structures that power Requests.\n\"\"\"\n\nfrom .compat import OrderedDict, Mapping, MutableMapping\n\n\nclass CaseInsensitiveDict(MutableMapping):\n    \"\"\"A case-insensitive ``dict``-like object.\n\n    Implements all methods and operations of\n    ``MutableMapping`` as well as dict's ``copy``. Also\n    provides ``lower_items``.\n\n    All keys are expected to be strings. The structure remembers the\n    case of the last key to be set, and ``iter(instance)``,\n    ``keys()``, ``items()``, ``iterkeys()``, and ``iteritems()``\n    will contain case-sensitive keys. However, querying and contains\n    testing is case insensitive::\n\n        cid = CaseInsensitiveDict()\n        cid['Accept'] = 'application/json'\n        cid['aCCEPT'] == 'application/json'  # True\n        list(cid) == ['Accept']  # True\n\n    For example, ``headers['content-encoding']`` will return the\n    value of a ``'Content-Encoding'`` response header, regardless\n    of how the header name was originally stored.\n\n    If the constructor, ``.update``, or equality comparison\n    operations are given keys that have equal ``.lower()``s, the\n    behavior is undefined.\n    \"\"\"\n\n    def __init__(self, data=None, **kwargs):\n        self._store = OrderedDict()\n        if data is None:\n            data = {}\n        self.update(data, **kwargs)\n\n    def __setitem__(self, key, value):\n        # Use the lowercased key for lookups, but store the actual\n        # key alongside the value.\n        self._store[key.lower()] = (key, value)\n\n    def __getitem__(self, key):\n        return self._store[key.lower()][1]\n\n    def __delitem__(self, key):\n        del self._store[key.lower()]\n\n    def __iter__(self):\n        return (casedkey for casedkey, mappedvalue in self._store.values())\n\n    def __len__(self):\n        return len(self._store)\n\n    def lower_items(self):\n        \"\"\"Like iteritems(), but with all lowercase keys.\"\"\"\n        return (\n            (lowerkey, keyval[1])\n            for (lowerkey, keyval)\n            in self._store.items()\n        )\n\n    def __eq__(self, other):\n        if isinstance(other, Mapping):\n            other = CaseInsensitiveDict(other)\n        else:\n            return NotImplemented\n        # Compare insensitively\n        return dict(self.lower_items()) == dict(other.lower_items())\n\n    # Copy is required\n    def copy(self):\n        return CaseInsensitiveDict(self._store.values())\n\n    def __repr__(self):\n        return str(dict(self.items()))\n\n\nclass LookupDict(dict):\n    \"\"\"Dictionary lookup object.\"\"\"\n\n    def __init__(self, name=None):\n        self.name = name\n        super(LookupDict, self).__init__()\n\n    def __repr__(self):\n        return '<lookup \\'%s\\'>' % (self.name)\n\n    def __getitem__(self, key):\n        # We allow fall-through here, so values default to None\n\n        return self.__dict__.get(key, None)\n\n    def get(self, key, default=None):\n        return self.__dict__.get(key, default)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/requests/utils.py",
    "content": "# -*- coding: utf-8 -*-\n\n\"\"\"\nrequests.utils\n~~~~~~~~~~~~~~\n\nThis module provides utility functions that are used within Requests\nthat are also useful for external consumption.\n\"\"\"\n\nimport codecs\nimport contextlib\nimport io\nimport os\nimport re\nimport socket\nimport struct\nimport sys\nimport tempfile\nimport warnings\nimport zipfile\n\nfrom .__version__ import __version__\nfrom . import certs\n# to_native_string is unused here, but imported here for backwards compatibility\nfrom ._internal_utils import to_native_string\nfrom .compat import parse_http_list as _parse_list_header\nfrom .compat import (\n    quote, urlparse, bytes, str, OrderedDict, unquote, getproxies,\n    proxy_bypass, urlunparse, basestring, integer_types, is_py3,\n    proxy_bypass_environment, getproxies_environment, Mapping)\nfrom .cookies import cookiejar_from_dict\nfrom .structures import CaseInsensitiveDict\nfrom .exceptions import (\n    InvalidURL, InvalidHeader, FileModeWarning, UnrewindableBodyError)\n\nNETRC_FILES = ('.netrc', '_netrc')\n\nDEFAULT_CA_BUNDLE_PATH = certs.where()\n\nDEFAULT_PORTS = {'http': 80, 'https': 443}\n\n\nif sys.platform == 'win32':\n    # provide a proxy_bypass version on Windows without DNS lookups\n\n    def proxy_bypass_registry(host):\n        try:\n            if is_py3:\n                import winreg\n            else:\n                import _winreg as winreg\n        except ImportError:\n            return False\n\n        try:\n            internetSettings = winreg.OpenKey(winreg.HKEY_CURRENT_USER,\n                r'Software\\Microsoft\\Windows\\CurrentVersion\\Internet Settings')\n            # ProxyEnable could be REG_SZ or REG_DWORD, normalizing it\n            proxyEnable = int(winreg.QueryValueEx(internetSettings,\n                                              'ProxyEnable')[0])\n            # ProxyOverride is almost always a string\n            proxyOverride = winreg.QueryValueEx(internetSettings,\n                                                'ProxyOverride')[0]\n        except OSError:\n            return False\n        if not proxyEnable or not proxyOverride:\n            return False\n\n        # make a check value list from the registry entry: replace the\n        # '<local>' string by the localhost entry and the corresponding\n        # canonical entry.\n        proxyOverride = proxyOverride.split(';')\n        # now check if we match one of the registry values.\n        for test in proxyOverride:\n            if test == '<local>':\n                if '.' not in host:\n                    return True\n            test = test.replace(\".\", r\"\\.\")     # mask dots\n            test = test.replace(\"*\", r\".*\")     # change glob sequence\n            test = test.replace(\"?\", r\".\")      # change glob char\n            if re.match(test, host, re.I):\n                return True\n        return False\n\n    def proxy_bypass(host):  # noqa\n        \"\"\"Return True, if the host should be bypassed.\n\n        Checks proxy settings gathered from the environment, if specified,\n        or the registry.\n        \"\"\"\n        if getproxies_environment():\n            return proxy_bypass_environment(host)\n        else:\n            return proxy_bypass_registry(host)\n\n\ndef dict_to_sequence(d):\n    \"\"\"Returns an internal sequence dictionary update.\"\"\"\n\n    if hasattr(d, 'items'):\n        d = d.items()\n\n    return d\n\n\ndef super_len(o):\n    total_length = None\n    current_position = 0\n\n    if hasattr(o, '__len__'):\n        total_length = len(o)\n\n    elif hasattr(o, 'len'):\n        total_length = o.len\n\n    elif hasattr(o, 'fileno'):\n        try:\n            fileno = o.fileno()\n        except io.UnsupportedOperation:\n            pass\n        else:\n            total_length = os.fstat(fileno).st_size\n\n            # Having used fstat to determine the file length, we need to\n            # confirm that this file was opened up in binary mode.\n            if 'b' not in o.mode:\n                warnings.warn((\n                    \"Requests has determined the content-length for this \"\n                    \"request using the binary size of the file: however, the \"\n                    \"file has been opened in text mode (i.e. without the 'b' \"\n                    \"flag in the mode). This may lead to an incorrect \"\n                    \"content-length. In Requests 3.0, support will be removed \"\n                    \"for files in text mode.\"),\n                    FileModeWarning\n                )\n\n    if hasattr(o, 'tell'):\n        try:\n            current_position = o.tell()\n        except (OSError, IOError):\n            # This can happen in some weird situations, such as when the file\n            # is actually a special file descriptor like stdin. In this\n            # instance, we don't know what the length is, so set it to zero and\n            # let requests chunk it instead.\n            if total_length is not None:\n                current_position = total_length\n        else:\n            if hasattr(o, 'seek') and total_length is None:\n                # StringIO and BytesIO have seek but no useable fileno\n                try:\n                    # seek to end of file\n                    o.seek(0, 2)\n                    total_length = o.tell()\n\n                    # seek back to current position to support\n                    # partially read file-like objects\n                    o.seek(current_position or 0)\n                except (OSError, IOError):\n                    total_length = 0\n\n    if total_length is None:\n        total_length = 0\n\n    return max(0, total_length - current_position)\n\n\ndef get_netrc_auth(url, raise_errors=False):\n    \"\"\"Returns the Requests tuple auth for a given url from netrc.\"\"\"\n\n    try:\n        from netrc import netrc, NetrcParseError\n\n        netrc_path = None\n\n        for f in NETRC_FILES:\n            try:\n                loc = os.path.expanduser('~/{}'.format(f))\n            except KeyError:\n                # os.path.expanduser can fail when $HOME is undefined and\n                # getpwuid fails. See https://bugs.python.org/issue20164 &\n                # https://github.com/requests/requests/issues/1846\n                return\n\n            if os.path.exists(loc):\n                netrc_path = loc\n                break\n\n        # Abort early if there isn't one.\n        if netrc_path is None:\n            return\n\n        ri = urlparse(url)\n\n        # Strip port numbers from netloc. This weird `if...encode`` dance is\n        # used for Python 3.2, which doesn't support unicode literals.\n        splitstr = b':'\n        if isinstance(url, str):\n            splitstr = splitstr.decode('ascii')\n        host = ri.netloc.split(splitstr)[0]\n\n        try:\n            _netrc = netrc(netrc_path).authenticators(host)\n            if _netrc:\n                # Return with login / password\n                login_i = (0 if _netrc[0] else 1)\n                return (_netrc[login_i], _netrc[2])\n        except (NetrcParseError, IOError):\n            # If there was a parsing error or a permissions issue reading the file,\n            # we'll just skip netrc auth unless explicitly asked to raise errors.\n            if raise_errors:\n                raise\n\n    # AppEngine hackiness.\n    except (ImportError, AttributeError):\n        pass\n\n\ndef guess_filename(obj):\n    \"\"\"Tries to guess the filename of the given object.\"\"\"\n    name = getattr(obj, 'name', None)\n    if (name and isinstance(name, basestring) and name[0] != '<' and\n            name[-1] != '>'):\n        return os.path.basename(name)\n\n\ndef extract_zipped_paths(path):\n    \"\"\"Replace nonexistent paths that look like they refer to a member of a zip\n    archive with the location of an extracted copy of the target, or else\n    just return the provided path unchanged.\n    \"\"\"\n    if os.path.exists(path):\n        # this is already a valid path, no need to do anything further\n        return path\n\n    # find the first valid part of the provided path and treat that as a zip archive\n    # assume the rest of the path is the name of a member in the archive\n    archive, member = os.path.split(path)\n    while archive and not os.path.exists(archive):\n        archive, prefix = os.path.split(archive)\n        member = '/'.join([prefix, member])\n\n    if not zipfile.is_zipfile(archive):\n        return path\n\n    zip_file = zipfile.ZipFile(archive)\n    if member not in zip_file.namelist():\n        return path\n\n    # we have a valid zip archive and a valid member of that archive\n    tmp = tempfile.gettempdir()\n    extracted_path = os.path.join(tmp, *member.split('/'))\n    if not os.path.exists(extracted_path):\n        extracted_path = zip_file.extract(member, path=tmp)\n\n    return extracted_path\n\n\ndef from_key_val_list(value):\n    \"\"\"Take an object and test to see if it can be represented as a\n    dictionary. Unless it can not be represented as such, return an\n    OrderedDict, e.g.,\n\n    ::\n\n        >>> from_key_val_list([('key', 'val')])\n        OrderedDict([('key', 'val')])\n        >>> from_key_val_list('string')\n        ValueError: cannot encode objects that are not 2-tuples\n        >>> from_key_val_list({'key': 'val'})\n        OrderedDict([('key', 'val')])\n\n    :rtype: OrderedDict\n    \"\"\"\n    if value is None:\n        return None\n\n    if isinstance(value, (str, bytes, bool, int)):\n        raise ValueError('cannot encode objects that are not 2-tuples')\n\n    return OrderedDict(value)\n\n\ndef to_key_val_list(value):\n    \"\"\"Take an object and test to see if it can be represented as a\n    dictionary. If it can be, return a list of tuples, e.g.,\n\n    ::\n\n        >>> to_key_val_list([('key', 'val')])\n        [('key', 'val')]\n        >>> to_key_val_list({'key': 'val'})\n        [('key', 'val')]\n        >>> to_key_val_list('string')\n        ValueError: cannot encode objects that are not 2-tuples.\n\n    :rtype: list\n    \"\"\"\n    if value is None:\n        return None\n\n    if isinstance(value, (str, bytes, bool, int)):\n        raise ValueError('cannot encode objects that are not 2-tuples')\n\n    if isinstance(value, Mapping):\n        value = value.items()\n\n    return list(value)\n\n\n# From mitsuhiko/werkzeug (used with permission).\ndef parse_list_header(value):\n    \"\"\"Parse lists as described by RFC 2068 Section 2.\n\n    In particular, parse comma-separated lists where the elements of\n    the list may include quoted-strings.  A quoted-string could\n    contain a comma.  A non-quoted string could have quotes in the\n    middle.  Quotes are removed automatically after parsing.\n\n    It basically works like :func:`parse_set_header` just that items\n    may appear multiple times and case sensitivity is preserved.\n\n    The return value is a standard :class:`list`:\n\n    >>> parse_list_header('token, \"quoted value\"')\n    ['token', 'quoted value']\n\n    To create a header from the :class:`list` again, use the\n    :func:`dump_header` function.\n\n    :param value: a string with a list header.\n    :return: :class:`list`\n    :rtype: list\n    \"\"\"\n    result = []\n    for item in _parse_list_header(value):\n        if item[:1] == item[-1:] == '\"':\n            item = unquote_header_value(item[1:-1])\n        result.append(item)\n    return result\n\n\n# From mitsuhiko/werkzeug (used with permission).\ndef parse_dict_header(value):\n    \"\"\"Parse lists of key, value pairs as described by RFC 2068 Section 2 and\n    convert them into a python dict:\n\n    >>> d = parse_dict_header('foo=\"is a fish\", bar=\"as well\"')\n    >>> type(d) is dict\n    True\n    >>> sorted(d.items())\n    [('bar', 'as well'), ('foo', 'is a fish')]\n\n    If there is no value for a key it will be `None`:\n\n    >>> parse_dict_header('key_without_value')\n    {'key_without_value': None}\n\n    To create a header from the :class:`dict` again, use the\n    :func:`dump_header` function.\n\n    :param value: a string with a dict header.\n    :return: :class:`dict`\n    :rtype: dict\n    \"\"\"\n    result = {}\n    for item in _parse_list_header(value):\n        if '=' not in item:\n            result[item] = None\n            continue\n        name, value = item.split('=', 1)\n        if value[:1] == value[-1:] == '\"':\n            value = unquote_header_value(value[1:-1])\n        result[name] = value\n    return result\n\n\n# From mitsuhiko/werkzeug (used with permission).\ndef unquote_header_value(value, is_filename=False):\n    r\"\"\"Unquotes a header value.  (Reversal of :func:`quote_header_value`).\n    This does not use the real unquoting but what browsers are actually\n    using for quoting.\n\n    :param value: the header value to unquote.\n    :rtype: str\n    \"\"\"\n    if value and value[0] == value[-1] == '\"':\n        # this is not the real unquoting, but fixing this so that the\n        # RFC is met will result in bugs with internet explorer and\n        # probably some other browsers as well.  IE for example is\n        # uploading files with \"C:\\foo\\bar.txt\" as filename\n        value = value[1:-1]\n\n        # if this is a filename and the starting characters look like\n        # a UNC path, then just return the value without quotes.  Using the\n        # replace sequence below on a UNC path has the effect of turning\n        # the leading double slash into a single slash and then\n        # _fix_ie_filename() doesn't work correctly.  See #458.\n        if not is_filename or value[:2] != '\\\\\\\\':\n            return value.replace('\\\\\\\\', '\\\\').replace('\\\\\"', '\"')\n    return value\n\n\ndef dict_from_cookiejar(cj):\n    \"\"\"Returns a key/value dictionary from a CookieJar.\n\n    :param cj: CookieJar object to extract cookies from.\n    :rtype: dict\n    \"\"\"\n\n    cookie_dict = {}\n\n    for cookie in cj:\n        cookie_dict[cookie.name] = cookie.value\n\n    return cookie_dict\n\n\ndef add_dict_to_cookiejar(cj, cookie_dict):\n    \"\"\"Returns a CookieJar from a key/value dictionary.\n\n    :param cj: CookieJar to insert cookies into.\n    :param cookie_dict: Dict of key/values to insert into CookieJar.\n    :rtype: CookieJar\n    \"\"\"\n\n    return cookiejar_from_dict(cookie_dict, cj)\n\n\ndef get_encodings_from_content(content):\n    \"\"\"Returns encodings from given content string.\n\n    :param content: bytestring to extract encodings from.\n    \"\"\"\n    warnings.warn((\n        'In requests 3.0, get_encodings_from_content will be removed. For '\n        'more information, please see the discussion on issue #2266. (This'\n        ' warning should only appear once.)'),\n        DeprecationWarning)\n\n    charset_re = re.compile(r'<meta.*?charset=[\"\\']*(.+?)[\"\\'>]', flags=re.I)\n    pragma_re = re.compile(r'<meta.*?content=[\"\\']*;?charset=(.+?)[\"\\'>]', flags=re.I)\n    xml_re = re.compile(r'^<\\?xml.*?encoding=[\"\\']*(.+?)[\"\\'>]')\n\n    return (charset_re.findall(content) +\n            pragma_re.findall(content) +\n            xml_re.findall(content))\n\n\ndef _parse_content_type_header(header):\n    \"\"\"Returns content type and parameters from given header\n\n    :param header: string\n    :return: tuple containing content type and dictionary of\n         parameters\n    \"\"\"\n\n    tokens = header.split(';')\n    content_type, params = tokens[0].strip(), tokens[1:]\n    params_dict = {}\n    items_to_strip = \"\\\"' \"\n\n    for param in params:\n        param = param.strip()\n        if param:\n            key, value = param, True\n            index_of_equals = param.find(\"=\")\n            if index_of_equals != -1:\n                key = param[:index_of_equals].strip(items_to_strip)\n                value = param[index_of_equals + 1:].strip(items_to_strip)\n            params_dict[key.lower()] = value\n    return content_type, params_dict\n\n\ndef get_encoding_from_headers(headers):\n    \"\"\"Returns encodings from given HTTP Header Dict.\n\n    :param headers: dictionary to extract encoding from.\n    :rtype: str\n    \"\"\"\n\n    content_type = headers.get('content-type')\n\n    if not content_type:\n        return None\n\n    content_type, params = _parse_content_type_header(content_type)\n\n    if 'charset' in params:\n        return params['charset'].strip(\"'\\\"\")\n\n    if 'text' in content_type:\n        return 'ISO-8859-1'\n\n\ndef stream_decode_response_unicode(iterator, r):\n    \"\"\"Stream decodes a iterator.\"\"\"\n\n    if r.encoding is None:\n        for item in iterator:\n            yield item\n        return\n\n    decoder = codecs.getincrementaldecoder(r.encoding)(errors='replace')\n    for chunk in iterator:\n        rv = decoder.decode(chunk)\n        if rv:\n            yield rv\n    rv = decoder.decode(b'', final=True)\n    if rv:\n        yield rv\n\n\ndef iter_slices(string, slice_length):\n    \"\"\"Iterate over slices of a string.\"\"\"\n    pos = 0\n    if slice_length is None or slice_length <= 0:\n        slice_length = len(string)\n    while pos < len(string):\n        yield string[pos:pos + slice_length]\n        pos += slice_length\n\n\ndef get_unicode_from_response(r):\n    \"\"\"Returns the requested content back in unicode.\n\n    :param r: Response object to get unicode content from.\n\n    Tried:\n\n    1. charset from content-type\n    2. fall back and replace all unicode characters\n\n    :rtype: str\n    \"\"\"\n    warnings.warn((\n        'In requests 3.0, get_unicode_from_response will be removed. For '\n        'more information, please see the discussion on issue #2266. (This'\n        ' warning should only appear once.)'),\n        DeprecationWarning)\n\n    tried_encodings = []\n\n    # Try charset from content-type\n    encoding = get_encoding_from_headers(r.headers)\n\n    if encoding:\n        try:\n            return str(r.content, encoding)\n        except UnicodeError:\n            tried_encodings.append(encoding)\n\n    # Fall back:\n    try:\n        return str(r.content, encoding, errors='replace')\n    except TypeError:\n        return r.content\n\n\n# The unreserved URI characters (RFC 3986)\nUNRESERVED_SET = frozenset(\n    \"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz\" + \"0123456789-._~\")\n\n\ndef unquote_unreserved(uri):\n    \"\"\"Un-escape any percent-escape sequences in a URI that are unreserved\n    characters. This leaves all reserved, illegal and non-ASCII bytes encoded.\n\n    :rtype: str\n    \"\"\"\n    parts = uri.split('%')\n    for i in range(1, len(parts)):\n        h = parts[i][0:2]\n        if len(h) == 2 and h.isalnum():\n            try:\n                c = chr(int(h, 16))\n            except ValueError:\n                raise InvalidURL(\"Invalid percent-escape sequence: '%s'\" % h)\n\n            if c in UNRESERVED_SET:\n                parts[i] = c + parts[i][2:]\n            else:\n                parts[i] = '%' + parts[i]\n        else:\n            parts[i] = '%' + parts[i]\n    return ''.join(parts)\n\n\ndef requote_uri(uri):\n    \"\"\"Re-quote the given URI.\n\n    This function passes the given URI through an unquote/quote cycle to\n    ensure that it is fully and consistently quoted.\n\n    :rtype: str\n    \"\"\"\n    safe_with_percent = \"!#$%&'()*+,/:;=?@[]~\"\n    safe_without_percent = \"!#$&'()*+,/:;=?@[]~\"\n    try:\n        # Unquote only the unreserved characters\n        # Then quote only illegal characters (do not quote reserved,\n        # unreserved, or '%')\n        return quote(unquote_unreserved(uri), safe=safe_with_percent)\n    except InvalidURL:\n        # We couldn't unquote the given URI, so let's try quoting it, but\n        # there may be unquoted '%'s in the URI. We need to make sure they're\n        # properly quoted so they do not cause issues elsewhere.\n        return quote(uri, safe=safe_without_percent)\n\n\ndef address_in_network(ip, net):\n    \"\"\"This function allows you to check if an IP belongs to a network subnet\n\n    Example: returns True if ip = 192.168.1.1 and net = 192.168.1.0/24\n             returns False if ip = 192.168.1.1 and net = 192.168.100.0/24\n\n    :rtype: bool\n    \"\"\"\n    ipaddr = struct.unpack('=L', socket.inet_aton(ip))[0]\n    netaddr, bits = net.split('/')\n    netmask = struct.unpack('=L', socket.inet_aton(dotted_netmask(int(bits))))[0]\n    network = struct.unpack('=L', socket.inet_aton(netaddr))[0] & netmask\n    return (ipaddr & netmask) == (network & netmask)\n\n\ndef dotted_netmask(mask):\n    \"\"\"Converts mask from /xx format to xxx.xxx.xxx.xxx\n\n    Example: if mask is 24 function returns 255.255.255.0\n\n    :rtype: str\n    \"\"\"\n    bits = 0xffffffff ^ (1 << 32 - mask) - 1\n    return socket.inet_ntoa(struct.pack('>I', bits))\n\n\ndef is_ipv4_address(string_ip):\n    \"\"\"\n    :rtype: bool\n    \"\"\"\n    try:\n        socket.inet_aton(string_ip)\n    except socket.error:\n        return False\n    return True\n\n\ndef is_valid_cidr(string_network):\n    \"\"\"\n    Very simple check of the cidr format in no_proxy variable.\n\n    :rtype: bool\n    \"\"\"\n    if string_network.count('/') == 1:\n        try:\n            mask = int(string_network.split('/')[1])\n        except ValueError:\n            return False\n\n        if mask < 1 or mask > 32:\n            return False\n\n        try:\n            socket.inet_aton(string_network.split('/')[0])\n        except socket.error:\n            return False\n    else:\n        return False\n    return True\n\n\n@contextlib.contextmanager\ndef set_environ(env_name, value):\n    \"\"\"Set the environment variable 'env_name' to 'value'\n\n    Save previous value, yield, and then restore the previous value stored in\n    the environment variable 'env_name'.\n\n    If 'value' is None, do nothing\"\"\"\n    value_changed = value is not None\n    if value_changed:\n        old_value = os.environ.get(env_name)\n        os.environ[env_name] = value\n    try:\n        yield\n    finally:\n        if value_changed:\n            if old_value is None:\n                del os.environ[env_name]\n            else:\n                os.environ[env_name] = old_value\n\n\ndef should_bypass_proxies(url, no_proxy):\n    \"\"\"\n    Returns whether we should bypass proxies or not.\n\n    :rtype: bool\n    \"\"\"\n    # Prioritize lowercase environment variables over uppercase\n    # to keep a consistent behaviour with other http projects (curl, wget).\n    get_proxy = lambda k: os.environ.get(k) or os.environ.get(k.upper())\n\n    # First check whether no_proxy is defined. If it is, check that the URL\n    # we're getting isn't in the no_proxy list.\n    no_proxy_arg = no_proxy\n    if no_proxy is None:\n        no_proxy = get_proxy('no_proxy')\n    parsed = urlparse(url)\n\n    if parsed.hostname is None:\n        # URLs don't always have hostnames, e.g. file:/// urls.\n        return True\n\n    if no_proxy:\n        # We need to check whether we match here. We need to see if we match\n        # the end of the hostname, both with and without the port.\n        no_proxy = (\n            host for host in no_proxy.replace(' ', '').split(',') if host\n        )\n\n        if is_ipv4_address(parsed.hostname):\n            for proxy_ip in no_proxy:\n                if is_valid_cidr(proxy_ip):\n                    if address_in_network(parsed.hostname, proxy_ip):\n                        return True\n                elif parsed.hostname == proxy_ip:\n                    # If no_proxy ip was defined in plain IP notation instead of cidr notation &\n                    # matches the IP of the index\n                    return True\n        else:\n            host_with_port = parsed.hostname\n            if parsed.port:\n                host_with_port += ':{}'.format(parsed.port)\n\n            for host in no_proxy:\n                if parsed.hostname.endswith(host) or host_with_port.endswith(host):\n                    # The URL does match something in no_proxy, so we don't want\n                    # to apply the proxies on this URL.\n                    return True\n\n    with set_environ('no_proxy', no_proxy_arg):\n        # parsed.hostname can be `None` in cases such as a file URI.\n        try:\n            bypass = proxy_bypass(parsed.hostname)\n        except (TypeError, socket.gaierror):\n            bypass = False\n\n    if bypass:\n        return True\n\n    return False\n\n\ndef get_environ_proxies(url, no_proxy=None):\n    \"\"\"\n    Return a dict of environment proxies.\n\n    :rtype: dict\n    \"\"\"\n    if should_bypass_proxies(url, no_proxy=no_proxy):\n        return {}\n    else:\n        return getproxies()\n\n\ndef select_proxy(url, proxies):\n    \"\"\"Select a proxy for the url, if applicable.\n\n    :param url: The url being for the request\n    :param proxies: A dictionary of schemes or schemes and hosts to proxy URLs\n    \"\"\"\n    proxies = proxies or {}\n    urlparts = urlparse(url)\n    if urlparts.hostname is None:\n        return proxies.get(urlparts.scheme, proxies.get('all'))\n\n    proxy_keys = [\n        urlparts.scheme + '://' + urlparts.hostname,\n        urlparts.scheme,\n        'all://' + urlparts.hostname,\n        'all',\n    ]\n    proxy = None\n    for proxy_key in proxy_keys:\n        if proxy_key in proxies:\n            proxy = proxies[proxy_key]\n            break\n\n    return proxy\n\n\ndef default_user_agent(name=\"python-requests\"):\n    \"\"\"\n    Return a string representing the default user agent.\n\n    :rtype: str\n    \"\"\"\n    return '%s/%s' % (name, __version__)\n\n\ndef default_headers():\n    \"\"\"\n    :rtype: requests.structures.CaseInsensitiveDict\n    \"\"\"\n    return CaseInsensitiveDict({\n        'User-Agent': default_user_agent(),\n        'Accept-Encoding': ', '.join(('gzip', 'deflate')),\n        'Accept': '*/*',\n        'Connection': 'keep-alive',\n    })\n\n\ndef parse_header_links(value):\n    \"\"\"Return a list of parsed link headers proxies.\n\n    i.e. Link: <http:/.../front.jpeg>; rel=front; type=\"image/jpeg\",<http://.../back.jpeg>; rel=back;type=\"image/jpeg\"\n\n    :rtype: list\n    \"\"\"\n\n    links = []\n\n    replace_chars = ' \\'\"'\n\n    value = value.strip(replace_chars)\n    if not value:\n        return links\n\n    for val in re.split(', *<', value):\n        try:\n            url, params = val.split(';', 1)\n        except ValueError:\n            url, params = val, ''\n\n        link = {'url': url.strip('<> \\'\"')}\n\n        for param in params.split(';'):\n            try:\n                key, value = param.split('=')\n            except ValueError:\n                break\n\n            link[key.strip(replace_chars)] = value.strip(replace_chars)\n\n        links.append(link)\n\n    return links\n\n\n# Null bytes; no need to recreate these on each call to guess_json_utf\n_null = '\\x00'.encode('ascii')  # encoding to ASCII for Python 3\n_null2 = _null * 2\n_null3 = _null * 3\n\n\ndef guess_json_utf(data):\n    \"\"\"\n    :rtype: str\n    \"\"\"\n    # JSON always starts with two ASCII characters, so detection is as\n    # easy as counting the nulls and from their location and count\n    # determine the encoding. Also detect a BOM, if present.\n    sample = data[:4]\n    if sample in (codecs.BOM_UTF32_LE, codecs.BOM_UTF32_BE):\n        return 'utf-32'     # BOM included\n    if sample[:3] == codecs.BOM_UTF8:\n        return 'utf-8-sig'  # BOM included, MS style (discouraged)\n    if sample[:2] in (codecs.BOM_UTF16_LE, codecs.BOM_UTF16_BE):\n        return 'utf-16'     # BOM included\n    nullcount = sample.count(_null)\n    if nullcount == 0:\n        return 'utf-8'\n    if nullcount == 2:\n        if sample[::2] == _null2:   # 1st and 3rd are null\n            return 'utf-16-be'\n        if sample[1::2] == _null2:  # 2nd and 4th are null\n            return 'utf-16-le'\n        # Did not detect 2 valid UTF-16 ascii-range characters\n    if nullcount == 3:\n        if sample[:3] == _null3:\n            return 'utf-32-be'\n        if sample[1:] == _null3:\n            return 'utf-32-le'\n        # Did not detect a valid UTF-32 ascii-range character\n    return None\n\n\ndef prepend_scheme_if_needed(url, new_scheme):\n    \"\"\"Given a URL that may or may not have a scheme, prepend the given scheme.\n    Does not replace a present scheme with the one provided as an argument.\n\n    :rtype: str\n    \"\"\"\n    scheme, netloc, path, params, query, fragment = urlparse(url, new_scheme)\n\n    # urlparse is a finicky beast, and sometimes decides that there isn't a\n    # netloc present. Assume that it's being over-cautious, and switch netloc\n    # and path if urlparse decided there was no netloc.\n    if not netloc:\n        netloc, path = path, netloc\n\n    return urlunparse((scheme, netloc, path, params, query, fragment))\n\n\ndef get_auth_from_url(url):\n    \"\"\"Given a url with authentication components, extract them into a tuple of\n    username,password.\n\n    :rtype: (str,str)\n    \"\"\"\n    parsed = urlparse(url)\n\n    try:\n        auth = (unquote(parsed.username), unquote(parsed.password))\n    except (AttributeError, TypeError):\n        auth = ('', '')\n\n    return auth\n\n\n# Moved outside of function to avoid recompile every call\n_CLEAN_HEADER_REGEX_BYTE = re.compile(b'^\\\\S[^\\\\r\\\\n]*$|^$')\n_CLEAN_HEADER_REGEX_STR = re.compile(r'^\\S[^\\r\\n]*$|^$')\n\n\ndef check_header_validity(header):\n    \"\"\"Verifies that header value is a string which doesn't contain\n    leading whitespace or return characters. This prevents unintended\n    header injection.\n\n    :param header: tuple, in the format (name, value).\n    \"\"\"\n    name, value = header\n\n    if isinstance(value, bytes):\n        pat = _CLEAN_HEADER_REGEX_BYTE\n    else:\n        pat = _CLEAN_HEADER_REGEX_STR\n    try:\n        if not pat.match(value):\n            raise InvalidHeader(\"Invalid return character or leading space in header: %s\" % name)\n    except TypeError:\n        raise InvalidHeader(\"Value for header {%s: %s} must be of type str or \"\n                            \"bytes, not %s\" % (name, value, type(value)))\n\n\ndef urldefragauth(url):\n    \"\"\"\n    Given a url remove the fragment and the authentication part.\n\n    :rtype: str\n    \"\"\"\n    scheme, netloc, path, params, query, fragment = urlparse(url)\n\n    # see func:`prepend_scheme_if_needed`\n    if not netloc:\n        netloc, path = path, netloc\n\n    netloc = netloc.rsplit('@', 1)[-1]\n\n    return urlunparse((scheme, netloc, path, params, query, ''))\n\n\ndef rewind_body(prepared_request):\n    \"\"\"Move file pointer back to its recorded starting position\n    so it can be read again on redirect.\n    \"\"\"\n    body_seek = getattr(prepared_request.body, 'seek', None)\n    if body_seek is not None and isinstance(prepared_request._body_position, integer_types):\n        try:\n            body_seek(prepared_request._body_position)\n        except (IOError, OSError):\n            raise UnrewindableBodyError(\"An error occurred when rewinding request \"\n                                        \"body for redirect.\")\n    else:\n        raise UnrewindableBodyError(\"Unable to rewind request body for redirect.\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/retrying.py",
    "content": "## Copyright 2013-2014 Ray Holder\n##\n## Licensed under the Apache License, Version 2.0 (the \"License\");\n## you may not use this file except in compliance with the License.\n## You may obtain a copy of the License at\n##\n## http://www.apache.org/licenses/LICENSE-2.0\n##\n## Unless required by applicable law or agreed to in writing, software\n## distributed under the License is distributed on an \"AS IS\" BASIS,\n## WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n## See the License for the specific language governing permissions and\n## limitations under the License.\n\nimport random\nfrom pip._vendor import six\nimport sys\nimport time\nimport traceback\n\n\n# sys.maxint / 2, since Python 3.2 doesn't have a sys.maxint...\nMAX_WAIT = 1073741823\n\n\ndef retry(*dargs, **dkw):\n    \"\"\"\n    Decorator function that instantiates the Retrying object\n    @param *dargs: positional arguments passed to Retrying object\n    @param **dkw: keyword arguments passed to the Retrying object\n    \"\"\"\n    # support both @retry and @retry() as valid syntax\n    if len(dargs) == 1 and callable(dargs[0]):\n        def wrap_simple(f):\n\n            @six.wraps(f)\n            def wrapped_f(*args, **kw):\n                return Retrying().call(f, *args, **kw)\n\n            return wrapped_f\n\n        return wrap_simple(dargs[0])\n\n    else:\n        def wrap(f):\n\n            @six.wraps(f)\n            def wrapped_f(*args, **kw):\n                return Retrying(*dargs, **dkw).call(f, *args, **kw)\n\n            return wrapped_f\n\n        return wrap\n\n\nclass Retrying(object):\n\n    def __init__(self,\n                 stop=None, wait=None,\n                 stop_max_attempt_number=None,\n                 stop_max_delay=None,\n                 wait_fixed=None,\n                 wait_random_min=None, wait_random_max=None,\n                 wait_incrementing_start=None, wait_incrementing_increment=None,\n                 wait_exponential_multiplier=None, wait_exponential_max=None,\n                 retry_on_exception=None,\n                 retry_on_result=None,\n                 wrap_exception=False,\n                 stop_func=None,\n                 wait_func=None,\n                 wait_jitter_max=None):\n\n        self._stop_max_attempt_number = 5 if stop_max_attempt_number is None else stop_max_attempt_number\n        self._stop_max_delay = 100 if stop_max_delay is None else stop_max_delay\n        self._wait_fixed = 1000 if wait_fixed is None else wait_fixed\n        self._wait_random_min = 0 if wait_random_min is None else wait_random_min\n        self._wait_random_max = 1000 if wait_random_max is None else wait_random_max\n        self._wait_incrementing_start = 0 if wait_incrementing_start is None else wait_incrementing_start\n        self._wait_incrementing_increment = 100 if wait_incrementing_increment is None else wait_incrementing_increment\n        self._wait_exponential_multiplier = 1 if wait_exponential_multiplier is None else wait_exponential_multiplier\n        self._wait_exponential_max = MAX_WAIT if wait_exponential_max is None else wait_exponential_max\n        self._wait_jitter_max = 0 if wait_jitter_max is None else wait_jitter_max\n\n        # TODO add chaining of stop behaviors\n        # stop behavior\n        stop_funcs = []\n        if stop_max_attempt_number is not None:\n            stop_funcs.append(self.stop_after_attempt)\n\n        if stop_max_delay is not None:\n            stop_funcs.append(self.stop_after_delay)\n\n        if stop_func is not None:\n            self.stop = stop_func\n\n        elif stop is None:\n            self.stop = lambda attempts, delay: any(f(attempts, delay) for f in stop_funcs)\n\n        else:\n            self.stop = getattr(self, stop)\n\n        # TODO add chaining of wait behaviors\n        # wait behavior\n        wait_funcs = [lambda *args, **kwargs: 0]\n        if wait_fixed is not None:\n            wait_funcs.append(self.fixed_sleep)\n\n        if wait_random_min is not None or wait_random_max is not None:\n            wait_funcs.append(self.random_sleep)\n\n        if wait_incrementing_start is not None or wait_incrementing_increment is not None:\n            wait_funcs.append(self.incrementing_sleep)\n\n        if wait_exponential_multiplier is not None or wait_exponential_max is not None:\n            wait_funcs.append(self.exponential_sleep)\n\n        if wait_func is not None:\n            self.wait = wait_func\n\n        elif wait is None:\n            self.wait = lambda attempts, delay: max(f(attempts, delay) for f in wait_funcs)\n\n        else:\n            self.wait = getattr(self, wait)\n\n        # retry on exception filter\n        if retry_on_exception is None:\n            self._retry_on_exception = self.always_reject\n        else:\n            self._retry_on_exception = retry_on_exception\n\n        # TODO simplify retrying by Exception types\n        # retry on result filter\n        if retry_on_result is None:\n            self._retry_on_result = self.never_reject\n        else:\n            self._retry_on_result = retry_on_result\n\n        self._wrap_exception = wrap_exception\n\n    def stop_after_attempt(self, previous_attempt_number, delay_since_first_attempt_ms):\n        \"\"\"Stop after the previous attempt >= stop_max_attempt_number.\"\"\"\n        return previous_attempt_number >= self._stop_max_attempt_number\n\n    def stop_after_delay(self, previous_attempt_number, delay_since_first_attempt_ms):\n        \"\"\"Stop after the time from the first attempt >= stop_max_delay.\"\"\"\n        return delay_since_first_attempt_ms >= self._stop_max_delay\n\n    def no_sleep(self, previous_attempt_number, delay_since_first_attempt_ms):\n        \"\"\"Don't sleep at all before retrying.\"\"\"\n        return 0\n\n    def fixed_sleep(self, previous_attempt_number, delay_since_first_attempt_ms):\n        \"\"\"Sleep a fixed amount of time between each retry.\"\"\"\n        return self._wait_fixed\n\n    def random_sleep(self, previous_attempt_number, delay_since_first_attempt_ms):\n        \"\"\"Sleep a random amount of time between wait_random_min and wait_random_max\"\"\"\n        return random.randint(self._wait_random_min, self._wait_random_max)\n\n    def incrementing_sleep(self, previous_attempt_number, delay_since_first_attempt_ms):\n        \"\"\"\n        Sleep an incremental amount of time after each attempt, starting at\n        wait_incrementing_start and incrementing by wait_incrementing_increment\n        \"\"\"\n        result = self._wait_incrementing_start + (self._wait_incrementing_increment * (previous_attempt_number - 1))\n        if result < 0:\n            result = 0\n        return result\n\n    def exponential_sleep(self, previous_attempt_number, delay_since_first_attempt_ms):\n        exp = 2 ** previous_attempt_number\n        result = self._wait_exponential_multiplier * exp\n        if result > self._wait_exponential_max:\n            result = self._wait_exponential_max\n        if result < 0:\n            result = 0\n        return result\n\n    def never_reject(self, result):\n        return False\n\n    def always_reject(self, result):\n        return True\n\n    def should_reject(self, attempt):\n        reject = False\n        if attempt.has_exception:\n            reject |= self._retry_on_exception(attempt.value[1])\n        else:\n            reject |= self._retry_on_result(attempt.value)\n\n        return reject\n\n    def call(self, fn, *args, **kwargs):\n        start_time = int(round(time.time() * 1000))\n        attempt_number = 1\n        while True:\n            try:\n                attempt = Attempt(fn(*args, **kwargs), attempt_number, False)\n            except:\n                tb = sys.exc_info()\n                attempt = Attempt(tb, attempt_number, True)\n\n            if not self.should_reject(attempt):\n                return attempt.get(self._wrap_exception)\n\n            delay_since_first_attempt_ms = int(round(time.time() * 1000)) - start_time\n            if self.stop(attempt_number, delay_since_first_attempt_ms):\n                if not self._wrap_exception and attempt.has_exception:\n                    # get() on an attempt with an exception should cause it to be raised, but raise just in case\n                    raise attempt.get()\n                else:\n                    raise RetryError(attempt)\n            else:\n                sleep = self.wait(attempt_number, delay_since_first_attempt_ms)\n                if self._wait_jitter_max:\n                    jitter = random.random() * self._wait_jitter_max\n                    sleep = sleep + max(0, jitter)\n                time.sleep(sleep / 1000.0)\n\n            attempt_number += 1\n\n\nclass Attempt(object):\n    \"\"\"\n    An Attempt encapsulates a call to a target function that may end as a\n    normal return value from the function or an Exception depending on what\n    occurred during the execution.\n    \"\"\"\n\n    def __init__(self, value, attempt_number, has_exception):\n        self.value = value\n        self.attempt_number = attempt_number\n        self.has_exception = has_exception\n\n    def get(self, wrap_exception=False):\n        \"\"\"\n        Return the return value of this Attempt instance or raise an Exception.\n        If wrap_exception is true, this Attempt is wrapped inside of a\n        RetryError before being raised.\n        \"\"\"\n        if self.has_exception:\n            if wrap_exception:\n                raise RetryError(self)\n            else:\n                six.reraise(self.value[0], self.value[1], self.value[2])\n        else:\n            return self.value\n\n    def __repr__(self):\n        if self.has_exception:\n            return \"Attempts: {0}, Error:\\n{1}\".format(self.attempt_number, \"\".join(traceback.format_tb(self.value[2])))\n        else:\n            return \"Attempts: {0}, Value: {1}\".format(self.attempt_number, self.value)\n\n\nclass RetryError(Exception):\n    \"\"\"\n    A RetryError encapsulates the last Attempt instance right before giving up.\n    \"\"\"\n\n    def __init__(self, last_attempt):\n        self.last_attempt = last_attempt\n\n    def __str__(self):\n        return \"RetryError[{0}]\".format(self.last_attempt)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/six.py",
    "content": "# Copyright (c) 2010-2018 Benjamin Peterson\n#\n# Permission is hereby granted, free of charge, to any person obtaining a copy\n# of this software and associated documentation files (the \"Software\"), to deal\n# in the Software without restriction, including without limitation the rights\n# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n# copies of the Software, and to permit persons to whom the Software is\n# furnished to do so, subject to the following conditions:\n#\n# The above copyright notice and this permission notice shall be included in all\n# copies or substantial portions of the Software.\n#\n# THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n# SOFTWARE.\n\n\"\"\"Utilities for writing code that runs on Python 2 and 3\"\"\"\n\nfrom __future__ import absolute_import\n\nimport functools\nimport itertools\nimport operator\nimport sys\nimport types\n\n__author__ = \"Benjamin Peterson <benjamin@python.org>\"\n__version__ = \"1.12.0\"\n\n\n# Useful for very coarse version differentiation.\nPY2 = sys.version_info[0] == 2\nPY3 = sys.version_info[0] == 3\nPY34 = sys.version_info[0:2] >= (3, 4)\n\nif PY3:\n    string_types = str,\n    integer_types = int,\n    class_types = type,\n    text_type = str\n    binary_type = bytes\n\n    MAXSIZE = sys.maxsize\nelse:\n    string_types = basestring,\n    integer_types = (int, long)\n    class_types = (type, types.ClassType)\n    text_type = unicode\n    binary_type = str\n\n    if sys.platform.startswith(\"java\"):\n        # Jython always uses 32 bits.\n        MAXSIZE = int((1 << 31) - 1)\n    else:\n        # It's possible to have sizeof(long) != sizeof(Py_ssize_t).\n        class X(object):\n\n            def __len__(self):\n                return 1 << 31\n        try:\n            len(X())\n        except OverflowError:\n            # 32-bit\n            MAXSIZE = int((1 << 31) - 1)\n        else:\n            # 64-bit\n            MAXSIZE = int((1 << 63) - 1)\n        del X\n\n\ndef _add_doc(func, doc):\n    \"\"\"Add documentation to a function.\"\"\"\n    func.__doc__ = doc\n\n\ndef _import_module(name):\n    \"\"\"Import module, returning the module after the last dot.\"\"\"\n    __import__(name)\n    return sys.modules[name]\n\n\nclass _LazyDescr(object):\n\n    def __init__(self, name):\n        self.name = name\n\n    def __get__(self, obj, tp):\n        result = self._resolve()\n        setattr(obj, self.name, result)  # Invokes __set__.\n        try:\n            # This is a bit ugly, but it avoids running this again by\n            # removing this descriptor.\n            delattr(obj.__class__, self.name)\n        except AttributeError:\n            pass\n        return result\n\n\nclass MovedModule(_LazyDescr):\n\n    def __init__(self, name, old, new=None):\n        super(MovedModule, self).__init__(name)\n        if PY3:\n            if new is None:\n                new = name\n            self.mod = new\n        else:\n            self.mod = old\n\n    def _resolve(self):\n        return _import_module(self.mod)\n\n    def __getattr__(self, attr):\n        _module = self._resolve()\n        value = getattr(_module, attr)\n        setattr(self, attr, value)\n        return value\n\n\nclass _LazyModule(types.ModuleType):\n\n    def __init__(self, name):\n        super(_LazyModule, self).__init__(name)\n        self.__doc__ = self.__class__.__doc__\n\n    def __dir__(self):\n        attrs = [\"__doc__\", \"__name__\"]\n        attrs += [attr.name for attr in self._moved_attributes]\n        return attrs\n\n    # Subclasses should override this\n    _moved_attributes = []\n\n\nclass MovedAttribute(_LazyDescr):\n\n    def __init__(self, name, old_mod, new_mod, old_attr=None, new_attr=None):\n        super(MovedAttribute, self).__init__(name)\n        if PY3:\n            if new_mod is None:\n                new_mod = name\n            self.mod = new_mod\n            if new_attr is None:\n                if old_attr is None:\n                    new_attr = name\n                else:\n                    new_attr = old_attr\n            self.attr = new_attr\n        else:\n            self.mod = old_mod\n            if old_attr is None:\n                old_attr = name\n            self.attr = old_attr\n\n    def _resolve(self):\n        module = _import_module(self.mod)\n        return getattr(module, self.attr)\n\n\nclass _SixMetaPathImporter(object):\n\n    \"\"\"\n    A meta path importer to import six.moves and its submodules.\n\n    This class implements a PEP302 finder and loader. It should be compatible\n    with Python 2.5 and all existing versions of Python3\n    \"\"\"\n\n    def __init__(self, six_module_name):\n        self.name = six_module_name\n        self.known_modules = {}\n\n    def _add_module(self, mod, *fullnames):\n        for fullname in fullnames:\n            self.known_modules[self.name + \".\" + fullname] = mod\n\n    def _get_module(self, fullname):\n        return self.known_modules[self.name + \".\" + fullname]\n\n    def find_module(self, fullname, path=None):\n        if fullname in self.known_modules:\n            return self\n        return None\n\n    def __get_module(self, fullname):\n        try:\n            return self.known_modules[fullname]\n        except KeyError:\n            raise ImportError(\"This loader does not know module \" + fullname)\n\n    def load_module(self, fullname):\n        try:\n            # in case of a reload\n            return sys.modules[fullname]\n        except KeyError:\n            pass\n        mod = self.__get_module(fullname)\n        if isinstance(mod, MovedModule):\n            mod = mod._resolve()\n        else:\n            mod.__loader__ = self\n        sys.modules[fullname] = mod\n        return mod\n\n    def is_package(self, fullname):\n        \"\"\"\n        Return true, if the named module is a package.\n\n        We need this method to get correct spec objects with\n        Python 3.4 (see PEP451)\n        \"\"\"\n        return hasattr(self.__get_module(fullname), \"__path__\")\n\n    def get_code(self, fullname):\n        \"\"\"Return None\n\n        Required, if is_package is implemented\"\"\"\n        self.__get_module(fullname)  # eventually raises ImportError\n        return None\n    get_source = get_code  # same as get_code\n\n_importer = _SixMetaPathImporter(__name__)\n\n\nclass _MovedItems(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects\"\"\"\n    __path__ = []  # mark as package\n\n\n_moved_attributes = [\n    MovedAttribute(\"cStringIO\", \"cStringIO\", \"io\", \"StringIO\"),\n    MovedAttribute(\"filter\", \"itertools\", \"builtins\", \"ifilter\", \"filter\"),\n    MovedAttribute(\"filterfalse\", \"itertools\", \"itertools\", \"ifilterfalse\", \"filterfalse\"),\n    MovedAttribute(\"input\", \"__builtin__\", \"builtins\", \"raw_input\", \"input\"),\n    MovedAttribute(\"intern\", \"__builtin__\", \"sys\"),\n    MovedAttribute(\"map\", \"itertools\", \"builtins\", \"imap\", \"map\"),\n    MovedAttribute(\"getcwd\", \"os\", \"os\", \"getcwdu\", \"getcwd\"),\n    MovedAttribute(\"getcwdb\", \"os\", \"os\", \"getcwd\", \"getcwdb\"),\n    MovedAttribute(\"getoutput\", \"commands\", \"subprocess\"),\n    MovedAttribute(\"range\", \"__builtin__\", \"builtins\", \"xrange\", \"range\"),\n    MovedAttribute(\"reload_module\", \"__builtin__\", \"importlib\" if PY34 else \"imp\", \"reload\"),\n    MovedAttribute(\"reduce\", \"__builtin__\", \"functools\"),\n    MovedAttribute(\"shlex_quote\", \"pipes\", \"shlex\", \"quote\"),\n    MovedAttribute(\"StringIO\", \"StringIO\", \"io\"),\n    MovedAttribute(\"UserDict\", \"UserDict\", \"collections\"),\n    MovedAttribute(\"UserList\", \"UserList\", \"collections\"),\n    MovedAttribute(\"UserString\", \"UserString\", \"collections\"),\n    MovedAttribute(\"xrange\", \"__builtin__\", \"builtins\", \"xrange\", \"range\"),\n    MovedAttribute(\"zip\", \"itertools\", \"builtins\", \"izip\", \"zip\"),\n    MovedAttribute(\"zip_longest\", \"itertools\", \"itertools\", \"izip_longest\", \"zip_longest\"),\n    MovedModule(\"builtins\", \"__builtin__\"),\n    MovedModule(\"configparser\", \"ConfigParser\"),\n    MovedModule(\"copyreg\", \"copy_reg\"),\n    MovedModule(\"dbm_gnu\", \"gdbm\", \"dbm.gnu\"),\n    MovedModule(\"_dummy_thread\", \"dummy_thread\", \"_dummy_thread\"),\n    MovedModule(\"http_cookiejar\", \"cookielib\", \"http.cookiejar\"),\n    MovedModule(\"http_cookies\", \"Cookie\", \"http.cookies\"),\n    MovedModule(\"html_entities\", \"htmlentitydefs\", \"html.entities\"),\n    MovedModule(\"html_parser\", \"HTMLParser\", \"html.parser\"),\n    MovedModule(\"http_client\", \"httplib\", \"http.client\"),\n    MovedModule(\"email_mime_base\", \"email.MIMEBase\", \"email.mime.base\"),\n    MovedModule(\"email_mime_image\", \"email.MIMEImage\", \"email.mime.image\"),\n    MovedModule(\"email_mime_multipart\", \"email.MIMEMultipart\", \"email.mime.multipart\"),\n    MovedModule(\"email_mime_nonmultipart\", \"email.MIMENonMultipart\", \"email.mime.nonmultipart\"),\n    MovedModule(\"email_mime_text\", \"email.MIMEText\", \"email.mime.text\"),\n    MovedModule(\"BaseHTTPServer\", \"BaseHTTPServer\", \"http.server\"),\n    MovedModule(\"CGIHTTPServer\", \"CGIHTTPServer\", \"http.server\"),\n    MovedModule(\"SimpleHTTPServer\", \"SimpleHTTPServer\", \"http.server\"),\n    MovedModule(\"cPickle\", \"cPickle\", \"pickle\"),\n    MovedModule(\"queue\", \"Queue\"),\n    MovedModule(\"reprlib\", \"repr\"),\n    MovedModule(\"socketserver\", \"SocketServer\"),\n    MovedModule(\"_thread\", \"thread\", \"_thread\"),\n    MovedModule(\"tkinter\", \"Tkinter\"),\n    MovedModule(\"tkinter_dialog\", \"Dialog\", \"tkinter.dialog\"),\n    MovedModule(\"tkinter_filedialog\", \"FileDialog\", \"tkinter.filedialog\"),\n    MovedModule(\"tkinter_scrolledtext\", \"ScrolledText\", \"tkinter.scrolledtext\"),\n    MovedModule(\"tkinter_simpledialog\", \"SimpleDialog\", \"tkinter.simpledialog\"),\n    MovedModule(\"tkinter_tix\", \"Tix\", \"tkinter.tix\"),\n    MovedModule(\"tkinter_ttk\", \"ttk\", \"tkinter.ttk\"),\n    MovedModule(\"tkinter_constants\", \"Tkconstants\", \"tkinter.constants\"),\n    MovedModule(\"tkinter_dnd\", \"Tkdnd\", \"tkinter.dnd\"),\n    MovedModule(\"tkinter_colorchooser\", \"tkColorChooser\",\n                \"tkinter.colorchooser\"),\n    MovedModule(\"tkinter_commondialog\", \"tkCommonDialog\",\n                \"tkinter.commondialog\"),\n    MovedModule(\"tkinter_tkfiledialog\", \"tkFileDialog\", \"tkinter.filedialog\"),\n    MovedModule(\"tkinter_font\", \"tkFont\", \"tkinter.font\"),\n    MovedModule(\"tkinter_messagebox\", \"tkMessageBox\", \"tkinter.messagebox\"),\n    MovedModule(\"tkinter_tksimpledialog\", \"tkSimpleDialog\",\n                \"tkinter.simpledialog\"),\n    MovedModule(\"urllib_parse\", __name__ + \".moves.urllib_parse\", \"urllib.parse\"),\n    MovedModule(\"urllib_error\", __name__ + \".moves.urllib_error\", \"urllib.error\"),\n    MovedModule(\"urllib\", __name__ + \".moves.urllib\", __name__ + \".moves.urllib\"),\n    MovedModule(\"urllib_robotparser\", \"robotparser\", \"urllib.robotparser\"),\n    MovedModule(\"xmlrpc_client\", \"xmlrpclib\", \"xmlrpc.client\"),\n    MovedModule(\"xmlrpc_server\", \"SimpleXMLRPCServer\", \"xmlrpc.server\"),\n]\n# Add windows specific modules.\nif sys.platform == \"win32\":\n    _moved_attributes += [\n        MovedModule(\"winreg\", \"_winreg\"),\n    ]\n\nfor attr in _moved_attributes:\n    setattr(_MovedItems, attr.name, attr)\n    if isinstance(attr, MovedModule):\n        _importer._add_module(attr, \"moves.\" + attr.name)\ndel attr\n\n_MovedItems._moved_attributes = _moved_attributes\n\nmoves = _MovedItems(__name__ + \".moves\")\n_importer._add_module(moves, \"moves\")\n\n\nclass Module_six_moves_urllib_parse(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_parse\"\"\"\n\n\n_urllib_parse_moved_attributes = [\n    MovedAttribute(\"ParseResult\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"SplitResult\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"parse_qs\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"parse_qsl\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urldefrag\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urljoin\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urlparse\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urlsplit\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urlunparse\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urlunsplit\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"quote\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"quote_plus\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"unquote\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"unquote_plus\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"unquote_to_bytes\", \"urllib\", \"urllib.parse\", \"unquote\", \"unquote_to_bytes\"),\n    MovedAttribute(\"urlencode\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"splitquery\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"splittag\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"splituser\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"splitvalue\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"uses_fragment\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"uses_netloc\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"uses_params\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"uses_query\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"uses_relative\", \"urlparse\", \"urllib.parse\"),\n]\nfor attr in _urllib_parse_moved_attributes:\n    setattr(Module_six_moves_urllib_parse, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_parse._moved_attributes = _urllib_parse_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_parse(__name__ + \".moves.urllib_parse\"),\n                      \"moves.urllib_parse\", \"moves.urllib.parse\")\n\n\nclass Module_six_moves_urllib_error(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_error\"\"\"\n\n\n_urllib_error_moved_attributes = [\n    MovedAttribute(\"URLError\", \"urllib2\", \"urllib.error\"),\n    MovedAttribute(\"HTTPError\", \"urllib2\", \"urllib.error\"),\n    MovedAttribute(\"ContentTooShortError\", \"urllib\", \"urllib.error\"),\n]\nfor attr in _urllib_error_moved_attributes:\n    setattr(Module_six_moves_urllib_error, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_error._moved_attributes = _urllib_error_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_error(__name__ + \".moves.urllib.error\"),\n                      \"moves.urllib_error\", \"moves.urllib.error\")\n\n\nclass Module_six_moves_urllib_request(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_request\"\"\"\n\n\n_urllib_request_moved_attributes = [\n    MovedAttribute(\"urlopen\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"install_opener\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"build_opener\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"pathname2url\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"url2pathname\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"getproxies\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"Request\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"OpenerDirector\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPDefaultErrorHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPRedirectHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPCookieProcessor\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"ProxyHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"BaseHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPPasswordMgr\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPPasswordMgrWithDefaultRealm\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"AbstractBasicAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPBasicAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"ProxyBasicAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"AbstractDigestAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPDigestAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"ProxyDigestAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPSHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"FileHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"FTPHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"CacheFTPHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"UnknownHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPErrorProcessor\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"urlretrieve\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"urlcleanup\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"URLopener\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"FancyURLopener\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"proxy_bypass\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"parse_http_list\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"parse_keqv_list\", \"urllib2\", \"urllib.request\"),\n]\nfor attr in _urllib_request_moved_attributes:\n    setattr(Module_six_moves_urllib_request, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_request._moved_attributes = _urllib_request_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_request(__name__ + \".moves.urllib.request\"),\n                      \"moves.urllib_request\", \"moves.urllib.request\")\n\n\nclass Module_six_moves_urllib_response(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_response\"\"\"\n\n\n_urllib_response_moved_attributes = [\n    MovedAttribute(\"addbase\", \"urllib\", \"urllib.response\"),\n    MovedAttribute(\"addclosehook\", \"urllib\", \"urllib.response\"),\n    MovedAttribute(\"addinfo\", \"urllib\", \"urllib.response\"),\n    MovedAttribute(\"addinfourl\", \"urllib\", \"urllib.response\"),\n]\nfor attr in _urllib_response_moved_attributes:\n    setattr(Module_six_moves_urllib_response, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_response._moved_attributes = _urllib_response_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_response(__name__ + \".moves.urllib.response\"),\n                      \"moves.urllib_response\", \"moves.urllib.response\")\n\n\nclass Module_six_moves_urllib_robotparser(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_robotparser\"\"\"\n\n\n_urllib_robotparser_moved_attributes = [\n    MovedAttribute(\"RobotFileParser\", \"robotparser\", \"urllib.robotparser\"),\n]\nfor attr in _urllib_robotparser_moved_attributes:\n    setattr(Module_six_moves_urllib_robotparser, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_robotparser._moved_attributes = _urllib_robotparser_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_robotparser(__name__ + \".moves.urllib.robotparser\"),\n                      \"moves.urllib_robotparser\", \"moves.urllib.robotparser\")\n\n\nclass Module_six_moves_urllib(types.ModuleType):\n\n    \"\"\"Create a six.moves.urllib namespace that resembles the Python 3 namespace\"\"\"\n    __path__ = []  # mark as package\n    parse = _importer._get_module(\"moves.urllib_parse\")\n    error = _importer._get_module(\"moves.urllib_error\")\n    request = _importer._get_module(\"moves.urllib_request\")\n    response = _importer._get_module(\"moves.urllib_response\")\n    robotparser = _importer._get_module(\"moves.urllib_robotparser\")\n\n    def __dir__(self):\n        return ['parse', 'error', 'request', 'response', 'robotparser']\n\n_importer._add_module(Module_six_moves_urllib(__name__ + \".moves.urllib\"),\n                      \"moves.urllib\")\n\n\ndef add_move(move):\n    \"\"\"Add an item to six.moves.\"\"\"\n    setattr(_MovedItems, move.name, move)\n\n\ndef remove_move(name):\n    \"\"\"Remove item from six.moves.\"\"\"\n    try:\n        delattr(_MovedItems, name)\n    except AttributeError:\n        try:\n            del moves.__dict__[name]\n        except KeyError:\n            raise AttributeError(\"no such move, %r\" % (name,))\n\n\nif PY3:\n    _meth_func = \"__func__\"\n    _meth_self = \"__self__\"\n\n    _func_closure = \"__closure__\"\n    _func_code = \"__code__\"\n    _func_defaults = \"__defaults__\"\n    _func_globals = \"__globals__\"\nelse:\n    _meth_func = \"im_func\"\n    _meth_self = \"im_self\"\n\n    _func_closure = \"func_closure\"\n    _func_code = \"func_code\"\n    _func_defaults = \"func_defaults\"\n    _func_globals = \"func_globals\"\n\n\ntry:\n    advance_iterator = next\nexcept NameError:\n    def advance_iterator(it):\n        return it.next()\nnext = advance_iterator\n\n\ntry:\n    callable = callable\nexcept NameError:\n    def callable(obj):\n        return any(\"__call__\" in klass.__dict__ for klass in type(obj).__mro__)\n\n\nif PY3:\n    def get_unbound_function(unbound):\n        return unbound\n\n    create_bound_method = types.MethodType\n\n    def create_unbound_method(func, cls):\n        return func\n\n    Iterator = object\nelse:\n    def get_unbound_function(unbound):\n        return unbound.im_func\n\n    def create_bound_method(func, obj):\n        return types.MethodType(func, obj, obj.__class__)\n\n    def create_unbound_method(func, cls):\n        return types.MethodType(func, None, cls)\n\n    class Iterator(object):\n\n        def next(self):\n            return type(self).__next__(self)\n\n    callable = callable\n_add_doc(get_unbound_function,\n         \"\"\"Get the function out of a possibly unbound function\"\"\")\n\n\nget_method_function = operator.attrgetter(_meth_func)\nget_method_self = operator.attrgetter(_meth_self)\nget_function_closure = operator.attrgetter(_func_closure)\nget_function_code = operator.attrgetter(_func_code)\nget_function_defaults = operator.attrgetter(_func_defaults)\nget_function_globals = operator.attrgetter(_func_globals)\n\n\nif PY3:\n    def iterkeys(d, **kw):\n        return iter(d.keys(**kw))\n\n    def itervalues(d, **kw):\n        return iter(d.values(**kw))\n\n    def iteritems(d, **kw):\n        return iter(d.items(**kw))\n\n    def iterlists(d, **kw):\n        return iter(d.lists(**kw))\n\n    viewkeys = operator.methodcaller(\"keys\")\n\n    viewvalues = operator.methodcaller(\"values\")\n\n    viewitems = operator.methodcaller(\"items\")\nelse:\n    def iterkeys(d, **kw):\n        return d.iterkeys(**kw)\n\n    def itervalues(d, **kw):\n        return d.itervalues(**kw)\n\n    def iteritems(d, **kw):\n        return d.iteritems(**kw)\n\n    def iterlists(d, **kw):\n        return d.iterlists(**kw)\n\n    viewkeys = operator.methodcaller(\"viewkeys\")\n\n    viewvalues = operator.methodcaller(\"viewvalues\")\n\n    viewitems = operator.methodcaller(\"viewitems\")\n\n_add_doc(iterkeys, \"Return an iterator over the keys of a dictionary.\")\n_add_doc(itervalues, \"Return an iterator over the values of a dictionary.\")\n_add_doc(iteritems,\n         \"Return an iterator over the (key, value) pairs of a dictionary.\")\n_add_doc(iterlists,\n         \"Return an iterator over the (key, [values]) pairs of a dictionary.\")\n\n\nif PY3:\n    def b(s):\n        return s.encode(\"latin-1\")\n\n    def u(s):\n        return s\n    unichr = chr\n    import struct\n    int2byte = struct.Struct(\">B\").pack\n    del struct\n    byte2int = operator.itemgetter(0)\n    indexbytes = operator.getitem\n    iterbytes = iter\n    import io\n    StringIO = io.StringIO\n    BytesIO = io.BytesIO\n    _assertCountEqual = \"assertCountEqual\"\n    if sys.version_info[1] <= 1:\n        _assertRaisesRegex = \"assertRaisesRegexp\"\n        _assertRegex = \"assertRegexpMatches\"\n    else:\n        _assertRaisesRegex = \"assertRaisesRegex\"\n        _assertRegex = \"assertRegex\"\nelse:\n    def b(s):\n        return s\n    # Workaround for standalone backslash\n\n    def u(s):\n        return unicode(s.replace(r'\\\\', r'\\\\\\\\'), \"unicode_escape\")\n    unichr = unichr\n    int2byte = chr\n\n    def byte2int(bs):\n        return ord(bs[0])\n\n    def indexbytes(buf, i):\n        return ord(buf[i])\n    iterbytes = functools.partial(itertools.imap, ord)\n    import StringIO\n    StringIO = BytesIO = StringIO.StringIO\n    _assertCountEqual = \"assertItemsEqual\"\n    _assertRaisesRegex = \"assertRaisesRegexp\"\n    _assertRegex = \"assertRegexpMatches\"\n_add_doc(b, \"\"\"Byte literal\"\"\")\n_add_doc(u, \"\"\"Text literal\"\"\")\n\n\ndef assertCountEqual(self, *args, **kwargs):\n    return getattr(self, _assertCountEqual)(*args, **kwargs)\n\n\ndef assertRaisesRegex(self, *args, **kwargs):\n    return getattr(self, _assertRaisesRegex)(*args, **kwargs)\n\n\ndef assertRegex(self, *args, **kwargs):\n    return getattr(self, _assertRegex)(*args, **kwargs)\n\n\nif PY3:\n    exec_ = getattr(moves.builtins, \"exec\")\n\n    def reraise(tp, value, tb=None):\n        try:\n            if value is None:\n                value = tp()\n            if value.__traceback__ is not tb:\n                raise value.with_traceback(tb)\n            raise value\n        finally:\n            value = None\n            tb = None\n\nelse:\n    def exec_(_code_, _globs_=None, _locs_=None):\n        \"\"\"Execute code in a namespace.\"\"\"\n        if _globs_ is None:\n            frame = sys._getframe(1)\n            _globs_ = frame.f_globals\n            if _locs_ is None:\n                _locs_ = frame.f_locals\n            del frame\n        elif _locs_ is None:\n            _locs_ = _globs_\n        exec(\"\"\"exec _code_ in _globs_, _locs_\"\"\")\n\n    exec_(\"\"\"def reraise(tp, value, tb=None):\n    try:\n        raise tp, value, tb\n    finally:\n        tb = None\n\"\"\")\n\n\nif sys.version_info[:2] == (3, 2):\n    exec_(\"\"\"def raise_from(value, from_value):\n    try:\n        if from_value is None:\n            raise value\n        raise value from from_value\n    finally:\n        value = None\n\"\"\")\nelif sys.version_info[:2] > (3, 2):\n    exec_(\"\"\"def raise_from(value, from_value):\n    try:\n        raise value from from_value\n    finally:\n        value = None\n\"\"\")\nelse:\n    def raise_from(value, from_value):\n        raise value\n\n\nprint_ = getattr(moves.builtins, \"print\", None)\nif print_ is None:\n    def print_(*args, **kwargs):\n        \"\"\"The new-style print function for Python 2.4 and 2.5.\"\"\"\n        fp = kwargs.pop(\"file\", sys.stdout)\n        if fp is None:\n            return\n\n        def write(data):\n            if not isinstance(data, basestring):\n                data = str(data)\n            # If the file has an encoding, encode unicode with it.\n            if (isinstance(fp, file) and\n                    isinstance(data, unicode) and\n                    fp.encoding is not None):\n                errors = getattr(fp, \"errors\", None)\n                if errors is None:\n                    errors = \"strict\"\n                data = data.encode(fp.encoding, errors)\n            fp.write(data)\n        want_unicode = False\n        sep = kwargs.pop(\"sep\", None)\n        if sep is not None:\n            if isinstance(sep, unicode):\n                want_unicode = True\n            elif not isinstance(sep, str):\n                raise TypeError(\"sep must be None or a string\")\n        end = kwargs.pop(\"end\", None)\n        if end is not None:\n            if isinstance(end, unicode):\n                want_unicode = True\n            elif not isinstance(end, str):\n                raise TypeError(\"end must be None or a string\")\n        if kwargs:\n            raise TypeError(\"invalid keyword arguments to print()\")\n        if not want_unicode:\n            for arg in args:\n                if isinstance(arg, unicode):\n                    want_unicode = True\n                    break\n        if want_unicode:\n            newline = unicode(\"\\n\")\n            space = unicode(\" \")\n        else:\n            newline = \"\\n\"\n            space = \" \"\n        if sep is None:\n            sep = space\n        if end is None:\n            end = newline\n        for i, arg in enumerate(args):\n            if i:\n                write(sep)\n            write(arg)\n        write(end)\nif sys.version_info[:2] < (3, 3):\n    _print = print_\n\n    def print_(*args, **kwargs):\n        fp = kwargs.get(\"file\", sys.stdout)\n        flush = kwargs.pop(\"flush\", False)\n        _print(*args, **kwargs)\n        if flush and fp is not None:\n            fp.flush()\n\n_add_doc(reraise, \"\"\"Reraise an exception.\"\"\")\n\nif sys.version_info[0:2] < (3, 4):\n    def wraps(wrapped, assigned=functools.WRAPPER_ASSIGNMENTS,\n              updated=functools.WRAPPER_UPDATES):\n        def wrapper(f):\n            f = functools.wraps(wrapped, assigned, updated)(f)\n            f.__wrapped__ = wrapped\n            return f\n        return wrapper\nelse:\n    wraps = functools.wraps\n\n\ndef with_metaclass(meta, *bases):\n    \"\"\"Create a base class with a metaclass.\"\"\"\n    # This requires a bit of explanation: the basic idea is to make a dummy\n    # metaclass for one level of class instantiation that replaces itself with\n    # the actual metaclass.\n    class metaclass(type):\n\n        def __new__(cls, name, this_bases, d):\n            return meta(name, bases, d)\n\n        @classmethod\n        def __prepare__(cls, name, this_bases):\n            return meta.__prepare__(name, bases)\n    return type.__new__(metaclass, 'temporary_class', (), {})\n\n\ndef add_metaclass(metaclass):\n    \"\"\"Class decorator for creating a class with a metaclass.\"\"\"\n    def wrapper(cls):\n        orig_vars = cls.__dict__.copy()\n        slots = orig_vars.get('__slots__')\n        if slots is not None:\n            if isinstance(slots, str):\n                slots = [slots]\n            for slots_var in slots:\n                orig_vars.pop(slots_var)\n        orig_vars.pop('__dict__', None)\n        orig_vars.pop('__weakref__', None)\n        if hasattr(cls, '__qualname__'):\n            orig_vars['__qualname__'] = cls.__qualname__\n        return metaclass(cls.__name__, cls.__bases__, orig_vars)\n    return wrapper\n\n\ndef ensure_binary(s, encoding='utf-8', errors='strict'):\n    \"\"\"Coerce **s** to six.binary_type.\n\n    For Python 2:\n      - `unicode` -> encoded to `str`\n      - `str` -> `str`\n\n    For Python 3:\n      - `str` -> encoded to `bytes`\n      - `bytes` -> `bytes`\n    \"\"\"\n    if isinstance(s, text_type):\n        return s.encode(encoding, errors)\n    elif isinstance(s, binary_type):\n        return s\n    else:\n        raise TypeError(\"not expecting type '%s'\" % type(s))\n\n\ndef ensure_str(s, encoding='utf-8', errors='strict'):\n    \"\"\"Coerce *s* to `str`.\n\n    For Python 2:\n      - `unicode` -> encoded to `str`\n      - `str` -> `str`\n\n    For Python 3:\n      - `str` -> `str`\n      - `bytes` -> decoded to `str`\n    \"\"\"\n    if not isinstance(s, (text_type, binary_type)):\n        raise TypeError(\"not expecting type '%s'\" % type(s))\n    if PY2 and isinstance(s, text_type):\n        s = s.encode(encoding, errors)\n    elif PY3 and isinstance(s, binary_type):\n        s = s.decode(encoding, errors)\n    return s\n\n\ndef ensure_text(s, encoding='utf-8', errors='strict'):\n    \"\"\"Coerce *s* to six.text_type.\n\n    For Python 2:\n      - `unicode` -> `unicode`\n      - `str` -> `unicode`\n\n    For Python 3:\n      - `str` -> `str`\n      - `bytes` -> decoded to `str`\n    \"\"\"\n    if isinstance(s, binary_type):\n        return s.decode(encoding, errors)\n    elif isinstance(s, text_type):\n        return s\n    else:\n        raise TypeError(\"not expecting type '%s'\" % type(s))\n\n\n\ndef python_2_unicode_compatible(klass):\n    \"\"\"\n    A decorator that defines __unicode__ and __str__ methods under Python 2.\n    Under Python 3 it does nothing.\n\n    To support Python 2 and 3 with a single code base, define a __str__ method\n    returning text and apply this decorator to the class.\n    \"\"\"\n    if PY2:\n        if '__str__' not in klass.__dict__:\n            raise ValueError(\"@python_2_unicode_compatible cannot be applied \"\n                             \"to %s because it doesn't define __str__().\" %\n                             klass.__name__)\n        klass.__unicode__ = klass.__str__\n        klass.__str__ = lambda self: self.__unicode__().encode('utf-8')\n    return klass\n\n\n# Complete the moves implementation.\n# This code is at the end of this module to speed up module loading.\n# Turn this module into a package.\n__path__ = []  # required for PEP 302 and PEP 451\n__package__ = __name__  # see PEP 366 @ReservedAssignment\nif globals().get(\"__spec__\") is not None:\n    __spec__.submodule_search_locations = []  # PEP 451 @UndefinedVariable\n# Remove other six meta path importers, since they cause problems. This can\n# happen if six is removed from sys.modules and then reloaded. (Setuptools does\n# this for some reason.)\nif sys.meta_path:\n    for i, importer in enumerate(sys.meta_path):\n        # Here's some real nastiness: Another \"instance\" of the six module might\n        # be floating around. Therefore, we can't use isinstance() to check for\n        # the six meta path importer, since the other six instance will have\n        # inserted an importer with different class.\n        if (type(importer).__name__ == \"_SixMetaPathImporter\" and\n                importer.name == __name__):\n            del sys.meta_path[i]\n            break\n    del i, importer\n# Finally, add the importer to the meta path import hook.\nsys.meta_path.append(_importer)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/__init__.py",
    "content": "\"\"\"\nurllib3 - Thread-safe connection pooling and re-using.\n\"\"\"\n\nfrom __future__ import absolute_import\nimport warnings\n\nfrom .connectionpool import (\n    HTTPConnectionPool,\n    HTTPSConnectionPool,\n    connection_from_url\n)\n\nfrom . import exceptions\nfrom .filepost import encode_multipart_formdata\nfrom .poolmanager import PoolManager, ProxyManager, proxy_from_url\nfrom .response import HTTPResponse\nfrom .util.request import make_headers\nfrom .util.url import get_host\nfrom .util.timeout import Timeout\nfrom .util.retry import Retry\n\n\n# Set default logging handler to avoid \"No handler found\" warnings.\nimport logging\nfrom logging import NullHandler\n\n__author__ = 'Andrey Petrov (andrey.petrov@shazow.net)'\n__license__ = 'MIT'\n__version__ = '1.24.1'\n\n__all__ = (\n    'HTTPConnectionPool',\n    'HTTPSConnectionPool',\n    'PoolManager',\n    'ProxyManager',\n    'HTTPResponse',\n    'Retry',\n    'Timeout',\n    'add_stderr_logger',\n    'connection_from_url',\n    'disable_warnings',\n    'encode_multipart_formdata',\n    'get_host',\n    'make_headers',\n    'proxy_from_url',\n)\n\nlogging.getLogger(__name__).addHandler(NullHandler())\n\n\ndef add_stderr_logger(level=logging.DEBUG):\n    \"\"\"\n    Helper for quickly adding a StreamHandler to the logger. Useful for\n    debugging.\n\n    Returns the handler after adding it.\n    \"\"\"\n    # This method needs to be in this __init__.py to get the __name__ correct\n    # even if urllib3 is vendored within another package.\n    logger = logging.getLogger(__name__)\n    handler = logging.StreamHandler()\n    handler.setFormatter(logging.Formatter('%(asctime)s %(levelname)s %(message)s'))\n    logger.addHandler(handler)\n    logger.setLevel(level)\n    logger.debug('Added a stderr logging handler to logger: %s', __name__)\n    return handler\n\n\n# ... Clean up.\ndel NullHandler\n\n\n# All warning filters *must* be appended unless you're really certain that they\n# shouldn't be: otherwise, it's very hard for users to use most Python\n# mechanisms to silence them.\n# SecurityWarning's always go off by default.\nwarnings.simplefilter('always', exceptions.SecurityWarning, append=True)\n# SubjectAltNameWarning's should go off once per host\nwarnings.simplefilter('default', exceptions.SubjectAltNameWarning, append=True)\n# InsecurePlatformWarning's don't vary between requests, so we keep it default.\nwarnings.simplefilter('default', exceptions.InsecurePlatformWarning,\n                      append=True)\n# SNIMissingWarnings should go off only once.\nwarnings.simplefilter('default', exceptions.SNIMissingWarning, append=True)\n\n\ndef disable_warnings(category=exceptions.HTTPWarning):\n    \"\"\"\n    Helper for quickly disabling all urllib3 warnings.\n    \"\"\"\n    warnings.simplefilter('ignore', category)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/_collections.py",
    "content": "from __future__ import absolute_import\ntry:\n    from collections.abc import Mapping, MutableMapping\nexcept ImportError:\n    from collections import Mapping, MutableMapping\ntry:\n    from threading import RLock\nexcept ImportError:  # Platform-specific: No threads available\n    class RLock:\n        def __enter__(self):\n            pass\n\n        def __exit__(self, exc_type, exc_value, traceback):\n            pass\n\n\nfrom collections import OrderedDict\nfrom .exceptions import InvalidHeader\nfrom .packages.six import iterkeys, itervalues, PY3\n\n\n__all__ = ['RecentlyUsedContainer', 'HTTPHeaderDict']\n\n\n_Null = object()\n\n\nclass RecentlyUsedContainer(MutableMapping):\n    \"\"\"\n    Provides a thread-safe dict-like container which maintains up to\n    ``maxsize`` keys while throwing away the least-recently-used keys beyond\n    ``maxsize``.\n\n    :param maxsize:\n        Maximum number of recent elements to retain.\n\n    :param dispose_func:\n        Every time an item is evicted from the container,\n        ``dispose_func(value)`` is called.  Callback which will get called\n    \"\"\"\n\n    ContainerCls = OrderedDict\n\n    def __init__(self, maxsize=10, dispose_func=None):\n        self._maxsize = maxsize\n        self.dispose_func = dispose_func\n\n        self._container = self.ContainerCls()\n        self.lock = RLock()\n\n    def __getitem__(self, key):\n        # Re-insert the item, moving it to the end of the eviction line.\n        with self.lock:\n            item = self._container.pop(key)\n            self._container[key] = item\n            return item\n\n    def __setitem__(self, key, value):\n        evicted_value = _Null\n        with self.lock:\n            # Possibly evict the existing value of 'key'\n            evicted_value = self._container.get(key, _Null)\n            self._container[key] = value\n\n            # If we didn't evict an existing value, we might have to evict the\n            # least recently used item from the beginning of the container.\n            if len(self._container) > self._maxsize:\n                _key, evicted_value = self._container.popitem(last=False)\n\n        if self.dispose_func and evicted_value is not _Null:\n            self.dispose_func(evicted_value)\n\n    def __delitem__(self, key):\n        with self.lock:\n            value = self._container.pop(key)\n\n        if self.dispose_func:\n            self.dispose_func(value)\n\n    def __len__(self):\n        with self.lock:\n            return len(self._container)\n\n    def __iter__(self):\n        raise NotImplementedError('Iteration over this class is unlikely to be threadsafe.')\n\n    def clear(self):\n        with self.lock:\n            # Copy pointers to all values, then wipe the mapping\n            values = list(itervalues(self._container))\n            self._container.clear()\n\n        if self.dispose_func:\n            for value in values:\n                self.dispose_func(value)\n\n    def keys(self):\n        with self.lock:\n            return list(iterkeys(self._container))\n\n\nclass HTTPHeaderDict(MutableMapping):\n    \"\"\"\n    :param headers:\n        An iterable of field-value pairs. Must not contain multiple field names\n        when compared case-insensitively.\n\n    :param kwargs:\n        Additional field-value pairs to pass in to ``dict.update``.\n\n    A ``dict`` like container for storing HTTP Headers.\n\n    Field names are stored and compared case-insensitively in compliance with\n    RFC 7230. Iteration provides the first case-sensitive key seen for each\n    case-insensitive pair.\n\n    Using ``__setitem__`` syntax overwrites fields that compare equal\n    case-insensitively in order to maintain ``dict``'s api. For fields that\n    compare equal, instead create a new ``HTTPHeaderDict`` and use ``.add``\n    in a loop.\n\n    If multiple fields that are equal case-insensitively are passed to the\n    constructor or ``.update``, the behavior is undefined and some will be\n    lost.\n\n    >>> headers = HTTPHeaderDict()\n    >>> headers.add('Set-Cookie', 'foo=bar')\n    >>> headers.add('set-cookie', 'baz=quxx')\n    >>> headers['content-length'] = '7'\n    >>> headers['SET-cookie']\n    'foo=bar, baz=quxx'\n    >>> headers['Content-Length']\n    '7'\n    \"\"\"\n\n    def __init__(self, headers=None, **kwargs):\n        super(HTTPHeaderDict, self).__init__()\n        self._container = OrderedDict()\n        if headers is not None:\n            if isinstance(headers, HTTPHeaderDict):\n                self._copy_from(headers)\n            else:\n                self.extend(headers)\n        if kwargs:\n            self.extend(kwargs)\n\n    def __setitem__(self, key, val):\n        self._container[key.lower()] = [key, val]\n        return self._container[key.lower()]\n\n    def __getitem__(self, key):\n        val = self._container[key.lower()]\n        return ', '.join(val[1:])\n\n    def __delitem__(self, key):\n        del self._container[key.lower()]\n\n    def __contains__(self, key):\n        return key.lower() in self._container\n\n    def __eq__(self, other):\n        if not isinstance(other, Mapping) and not hasattr(other, 'keys'):\n            return False\n        if not isinstance(other, type(self)):\n            other = type(self)(other)\n        return (dict((k.lower(), v) for k, v in self.itermerged()) ==\n                dict((k.lower(), v) for k, v in other.itermerged()))\n\n    def __ne__(self, other):\n        return not self.__eq__(other)\n\n    if not PY3:  # Python 2\n        iterkeys = MutableMapping.iterkeys\n        itervalues = MutableMapping.itervalues\n\n    __marker = object()\n\n    def __len__(self):\n        return len(self._container)\n\n    def __iter__(self):\n        # Only provide the originally cased names\n        for vals in self._container.values():\n            yield vals[0]\n\n    def pop(self, key, default=__marker):\n        '''D.pop(k[,d]) -> v, remove specified key and return the corresponding value.\n          If key is not found, d is returned if given, otherwise KeyError is raised.\n        '''\n        # Using the MutableMapping function directly fails due to the private marker.\n        # Using ordinary dict.pop would expose the internal structures.\n        # So let's reinvent the wheel.\n        try:\n            value = self[key]\n        except KeyError:\n            if default is self.__marker:\n                raise\n            return default\n        else:\n            del self[key]\n            return value\n\n    def discard(self, key):\n        try:\n            del self[key]\n        except KeyError:\n            pass\n\n    def add(self, key, val):\n        \"\"\"Adds a (name, value) pair, doesn't overwrite the value if it already\n        exists.\n\n        >>> headers = HTTPHeaderDict(foo='bar')\n        >>> headers.add('Foo', 'baz')\n        >>> headers['foo']\n        'bar, baz'\n        \"\"\"\n        key_lower = key.lower()\n        new_vals = [key, val]\n        # Keep the common case aka no item present as fast as possible\n        vals = self._container.setdefault(key_lower, new_vals)\n        if new_vals is not vals:\n            vals.append(val)\n\n    def extend(self, *args, **kwargs):\n        \"\"\"Generic import function for any type of header-like object.\n        Adapted version of MutableMapping.update in order to insert items\n        with self.add instead of self.__setitem__\n        \"\"\"\n        if len(args) > 1:\n            raise TypeError(\"extend() takes at most 1 positional \"\n                            \"arguments ({0} given)\".format(len(args)))\n        other = args[0] if len(args) >= 1 else ()\n\n        if isinstance(other, HTTPHeaderDict):\n            for key, val in other.iteritems():\n                self.add(key, val)\n        elif isinstance(other, Mapping):\n            for key in other:\n                self.add(key, other[key])\n        elif hasattr(other, \"keys\"):\n            for key in other.keys():\n                self.add(key, other[key])\n        else:\n            for key, value in other:\n                self.add(key, value)\n\n        for key, value in kwargs.items():\n            self.add(key, value)\n\n    def getlist(self, key, default=__marker):\n        \"\"\"Returns a list of all the values for the named field. Returns an\n        empty list if the key doesn't exist.\"\"\"\n        try:\n            vals = self._container[key.lower()]\n        except KeyError:\n            if default is self.__marker:\n                return []\n            return default\n        else:\n            return vals[1:]\n\n    # Backwards compatibility for httplib\n    getheaders = getlist\n    getallmatchingheaders = getlist\n    iget = getlist\n\n    # Backwards compatibility for http.cookiejar\n    get_all = getlist\n\n    def __repr__(self):\n        return \"%s(%s)\" % (type(self).__name__, dict(self.itermerged()))\n\n    def _copy_from(self, other):\n        for key in other:\n            val = other.getlist(key)\n            if isinstance(val, list):\n                # Don't need to convert tuples\n                val = list(val)\n            self._container[key.lower()] = [key] + val\n\n    def copy(self):\n        clone = type(self)()\n        clone._copy_from(self)\n        return clone\n\n    def iteritems(self):\n        \"\"\"Iterate over all header lines, including duplicate ones.\"\"\"\n        for key in self:\n            vals = self._container[key.lower()]\n            for val in vals[1:]:\n                yield vals[0], val\n\n    def itermerged(self):\n        \"\"\"Iterate over all headers, merging duplicate ones together.\"\"\"\n        for key in self:\n            val = self._container[key.lower()]\n            yield val[0], ', '.join(val[1:])\n\n    def items(self):\n        return list(self.iteritems())\n\n    @classmethod\n    def from_httplib(cls, message):  # Python 2\n        \"\"\"Read headers from a Python 2 httplib message object.\"\"\"\n        # python2.7 does not expose a proper API for exporting multiheaders\n        # efficiently. This function re-reads raw lines from the message\n        # object and extracts the multiheaders properly.\n        obs_fold_continued_leaders = (' ', '\\t')\n        headers = []\n\n        for line in message.headers:\n            if line.startswith(obs_fold_continued_leaders):\n                if not headers:\n                    # We received a header line that starts with OWS as described\n                    # in RFC-7230 S3.2.4. This indicates a multiline header, but\n                    # there exists no previous header to which we can attach it.\n                    raise InvalidHeader(\n                        'Header continuation with no previous header: %s' % line\n                    )\n                else:\n                    key, value = headers[-1]\n                    headers[-1] = (key, value + ' ' + line.strip())\n                    continue\n\n            key, value = line.split(':', 1)\n            headers.append((key, value.strip()))\n\n        return cls(headers)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/connection.py",
    "content": "from __future__ import absolute_import\nimport datetime\nimport logging\nimport os\nimport socket\nfrom socket import error as SocketError, timeout as SocketTimeout\nimport warnings\nfrom .packages import six\nfrom .packages.six.moves.http_client import HTTPConnection as _HTTPConnection\nfrom .packages.six.moves.http_client import HTTPException  # noqa: F401\n\ntry:  # Compiled with SSL?\n    import ssl\n    BaseSSLError = ssl.SSLError\nexcept (ImportError, AttributeError):  # Platform-specific: No SSL.\n    ssl = None\n\n    class BaseSSLError(BaseException):\n        pass\n\n\ntry:  # Python 3:\n    # Not a no-op, we're adding this to the namespace so it can be imported.\n    ConnectionError = ConnectionError\nexcept NameError:  # Python 2:\n    class ConnectionError(Exception):\n        pass\n\n\nfrom .exceptions import (\n    NewConnectionError,\n    ConnectTimeoutError,\n    SubjectAltNameWarning,\n    SystemTimeWarning,\n)\nfrom .packages.ssl_match_hostname import match_hostname, CertificateError\n\nfrom .util.ssl_ import (\n    resolve_cert_reqs,\n    resolve_ssl_version,\n    assert_fingerprint,\n    create_urllib3_context,\n    ssl_wrap_socket\n)\n\n\nfrom .util import connection\n\nfrom ._collections import HTTPHeaderDict\n\nlog = logging.getLogger(__name__)\n\nport_by_scheme = {\n    'http': 80,\n    'https': 443,\n}\n\n# When updating RECENT_DATE, move it to within two years of the current date,\n# and not less than 6 months ago.\n# Example: if Today is 2018-01-01, then RECENT_DATE should be any date on or\n# after 2016-01-01 (today - 2 years) AND before 2017-07-01 (today - 6 months)\nRECENT_DATE = datetime.date(2017, 6, 30)\n\n\nclass DummyConnection(object):\n    \"\"\"Used to detect a failed ConnectionCls import.\"\"\"\n    pass\n\n\nclass HTTPConnection(_HTTPConnection, object):\n    \"\"\"\n    Based on httplib.HTTPConnection but provides an extra constructor\n    backwards-compatibility layer between older and newer Pythons.\n\n    Additional keyword parameters are used to configure attributes of the connection.\n    Accepted parameters include:\n\n      - ``strict``: See the documentation on :class:`urllib3.connectionpool.HTTPConnectionPool`\n      - ``source_address``: Set the source address for the current connection.\n      - ``socket_options``: Set specific options on the underlying socket. If not specified, then\n        defaults are loaded from ``HTTPConnection.default_socket_options`` which includes disabling\n        Nagle's algorithm (sets TCP_NODELAY to 1) unless the connection is behind a proxy.\n\n        For example, if you wish to enable TCP Keep Alive in addition to the defaults,\n        you might pass::\n\n            HTTPConnection.default_socket_options + [\n                (socket.SOL_SOCKET, socket.SO_KEEPALIVE, 1),\n            ]\n\n        Or you may want to disable the defaults by passing an empty list (e.g., ``[]``).\n    \"\"\"\n\n    default_port = port_by_scheme['http']\n\n    #: Disable Nagle's algorithm by default.\n    #: ``[(socket.IPPROTO_TCP, socket.TCP_NODELAY, 1)]``\n    default_socket_options = [(socket.IPPROTO_TCP, socket.TCP_NODELAY, 1)]\n\n    #: Whether this connection verifies the host's certificate.\n    is_verified = False\n\n    def __init__(self, *args, **kw):\n        if six.PY3:  # Python 3\n            kw.pop('strict', None)\n\n        # Pre-set source_address.\n        self.source_address = kw.get('source_address')\n\n        #: The socket options provided by the user. If no options are\n        #: provided, we use the default options.\n        self.socket_options = kw.pop('socket_options', self.default_socket_options)\n\n        _HTTPConnection.__init__(self, *args, **kw)\n\n    @property\n    def host(self):\n        \"\"\"\n        Getter method to remove any trailing dots that indicate the hostname is an FQDN.\n\n        In general, SSL certificates don't include the trailing dot indicating a\n        fully-qualified domain name, and thus, they don't validate properly when\n        checked against a domain name that includes the dot. In addition, some\n        servers may not expect to receive the trailing dot when provided.\n\n        However, the hostname with trailing dot is critical to DNS resolution; doing a\n        lookup with the trailing dot will properly only resolve the appropriate FQDN,\n        whereas a lookup without a trailing dot will search the system's search domain\n        list. Thus, it's important to keep the original host around for use only in\n        those cases where it's appropriate (i.e., when doing DNS lookup to establish the\n        actual TCP connection across which we're going to send HTTP requests).\n        \"\"\"\n        return self._dns_host.rstrip('.')\n\n    @host.setter\n    def host(self, value):\n        \"\"\"\n        Setter for the `host` property.\n\n        We assume that only urllib3 uses the _dns_host attribute; httplib itself\n        only uses `host`, and it seems reasonable that other libraries follow suit.\n        \"\"\"\n        self._dns_host = value\n\n    def _new_conn(self):\n        \"\"\" Establish a socket connection and set nodelay settings on it.\n\n        :return: New socket connection.\n        \"\"\"\n        extra_kw = {}\n        if self.source_address:\n            extra_kw['source_address'] = self.source_address\n\n        if self.socket_options:\n            extra_kw['socket_options'] = self.socket_options\n\n        try:\n            conn = connection.create_connection(\n                (self._dns_host, self.port), self.timeout, **extra_kw)\n\n        except SocketTimeout as e:\n            raise ConnectTimeoutError(\n                self, \"Connection to %s timed out. (connect timeout=%s)\" %\n                (self.host, self.timeout))\n\n        except SocketError as e:\n            raise NewConnectionError(\n                self, \"Failed to establish a new connection: %s\" % e)\n\n        return conn\n\n    def _prepare_conn(self, conn):\n        self.sock = conn\n        if self._tunnel_host:\n            # TODO: Fix tunnel so it doesn't depend on self.sock state.\n            self._tunnel()\n            # Mark this connection as not reusable\n            self.auto_open = 0\n\n    def connect(self):\n        conn = self._new_conn()\n        self._prepare_conn(conn)\n\n    def request_chunked(self, method, url, body=None, headers=None):\n        \"\"\"\n        Alternative to the common request method, which sends the\n        body with chunked encoding and not as one block\n        \"\"\"\n        headers = HTTPHeaderDict(headers if headers is not None else {})\n        skip_accept_encoding = 'accept-encoding' in headers\n        skip_host = 'host' in headers\n        self.putrequest(\n            method,\n            url,\n            skip_accept_encoding=skip_accept_encoding,\n            skip_host=skip_host\n        )\n        for header, value in headers.items():\n            self.putheader(header, value)\n        if 'transfer-encoding' not in headers:\n            self.putheader('Transfer-Encoding', 'chunked')\n        self.endheaders()\n\n        if body is not None:\n            stringish_types = six.string_types + (bytes,)\n            if isinstance(body, stringish_types):\n                body = (body,)\n            for chunk in body:\n                if not chunk:\n                    continue\n                if not isinstance(chunk, bytes):\n                    chunk = chunk.encode('utf8')\n                len_str = hex(len(chunk))[2:]\n                self.send(len_str.encode('utf-8'))\n                self.send(b'\\r\\n')\n                self.send(chunk)\n                self.send(b'\\r\\n')\n\n        # After the if clause, to always have a closed body\n        self.send(b'0\\r\\n\\r\\n')\n\n\nclass HTTPSConnection(HTTPConnection):\n    default_port = port_by_scheme['https']\n\n    ssl_version = None\n\n    def __init__(self, host, port=None, key_file=None, cert_file=None,\n                 strict=None, timeout=socket._GLOBAL_DEFAULT_TIMEOUT,\n                 ssl_context=None, server_hostname=None, **kw):\n\n        HTTPConnection.__init__(self, host, port, strict=strict,\n                                timeout=timeout, **kw)\n\n        self.key_file = key_file\n        self.cert_file = cert_file\n        self.ssl_context = ssl_context\n        self.server_hostname = server_hostname\n\n        # Required property for Google AppEngine 1.9.0 which otherwise causes\n        # HTTPS requests to go out as HTTP. (See Issue #356)\n        self._protocol = 'https'\n\n    def connect(self):\n        conn = self._new_conn()\n        self._prepare_conn(conn)\n\n        if self.ssl_context is None:\n            self.ssl_context = create_urllib3_context(\n                ssl_version=resolve_ssl_version(None),\n                cert_reqs=resolve_cert_reqs(None),\n            )\n\n        self.sock = ssl_wrap_socket(\n            sock=conn,\n            keyfile=self.key_file,\n            certfile=self.cert_file,\n            ssl_context=self.ssl_context,\n            server_hostname=self.server_hostname\n        )\n\n\nclass VerifiedHTTPSConnection(HTTPSConnection):\n    \"\"\"\n    Based on httplib.HTTPSConnection but wraps the socket with\n    SSL certification.\n    \"\"\"\n    cert_reqs = None\n    ca_certs = None\n    ca_cert_dir = None\n    ssl_version = None\n    assert_fingerprint = None\n\n    def set_cert(self, key_file=None, cert_file=None,\n                 cert_reqs=None, ca_certs=None,\n                 assert_hostname=None, assert_fingerprint=None,\n                 ca_cert_dir=None):\n        \"\"\"\n        This method should only be called once, before the connection is used.\n        \"\"\"\n        # If cert_reqs is not provided, we can try to guess. If the user gave\n        # us a cert database, we assume they want to use it: otherwise, if\n        # they gave us an SSL Context object we should use whatever is set for\n        # it.\n        if cert_reqs is None:\n            if ca_certs or ca_cert_dir:\n                cert_reqs = 'CERT_REQUIRED'\n            elif self.ssl_context is not None:\n                cert_reqs = self.ssl_context.verify_mode\n\n        self.key_file = key_file\n        self.cert_file = cert_file\n        self.cert_reqs = cert_reqs\n        self.assert_hostname = assert_hostname\n        self.assert_fingerprint = assert_fingerprint\n        self.ca_certs = ca_certs and os.path.expanduser(ca_certs)\n        self.ca_cert_dir = ca_cert_dir and os.path.expanduser(ca_cert_dir)\n\n    def connect(self):\n        # Add certificate verification\n        conn = self._new_conn()\n        hostname = self.host\n\n        if self._tunnel_host:\n            self.sock = conn\n            # Calls self._set_hostport(), so self.host is\n            # self._tunnel_host below.\n            self._tunnel()\n            # Mark this connection as not reusable\n            self.auto_open = 0\n\n            # Override the host with the one we're requesting data from.\n            hostname = self._tunnel_host\n\n        server_hostname = hostname\n        if self.server_hostname is not None:\n            server_hostname = self.server_hostname\n\n        is_time_off = datetime.date.today() < RECENT_DATE\n        if is_time_off:\n            warnings.warn((\n                'System time is way off (before {0}). This will probably '\n                'lead to SSL verification errors').format(RECENT_DATE),\n                SystemTimeWarning\n            )\n\n        # Wrap socket using verification with the root certs in\n        # trusted_root_certs\n        if self.ssl_context is None:\n            self.ssl_context = create_urllib3_context(\n                ssl_version=resolve_ssl_version(self.ssl_version),\n                cert_reqs=resolve_cert_reqs(self.cert_reqs),\n            )\n\n        context = self.ssl_context\n        context.verify_mode = resolve_cert_reqs(self.cert_reqs)\n        self.sock = ssl_wrap_socket(\n            sock=conn,\n            keyfile=self.key_file,\n            certfile=self.cert_file,\n            ca_certs=self.ca_certs,\n            ca_cert_dir=self.ca_cert_dir,\n            server_hostname=server_hostname,\n            ssl_context=context)\n\n        if self.assert_fingerprint:\n            assert_fingerprint(self.sock.getpeercert(binary_form=True),\n                               self.assert_fingerprint)\n        elif context.verify_mode != ssl.CERT_NONE \\\n                and not getattr(context, 'check_hostname', False) \\\n                and self.assert_hostname is not False:\n            # While urllib3 attempts to always turn off hostname matching from\n            # the TLS library, this cannot always be done. So we check whether\n            # the TLS Library still thinks it's matching hostnames.\n            cert = self.sock.getpeercert()\n            if not cert.get('subjectAltName', ()):\n                warnings.warn((\n                    'Certificate for {0} has no `subjectAltName`, falling back to check for a '\n                    '`commonName` for now. This feature is being removed by major browsers and '\n                    'deprecated by RFC 2818. (See https://github.com/shazow/urllib3/issues/497 '\n                    'for details.)'.format(hostname)),\n                    SubjectAltNameWarning\n                )\n            _match_hostname(cert, self.assert_hostname or server_hostname)\n\n        self.is_verified = (\n            context.verify_mode == ssl.CERT_REQUIRED or\n            self.assert_fingerprint is not None\n        )\n\n\ndef _match_hostname(cert, asserted_hostname):\n    try:\n        match_hostname(cert, asserted_hostname)\n    except CertificateError as e:\n        log.error(\n            'Certificate did not match expected hostname: %s. '\n            'Certificate: %s', asserted_hostname, cert\n        )\n        # Add cert to exception and reraise so client code can inspect\n        # the cert when catching the exception, if they want to\n        e._peer_cert = cert\n        raise\n\n\nif ssl:\n    # Make a copy for testing.\n    UnverifiedHTTPSConnection = HTTPSConnection\n    HTTPSConnection = VerifiedHTTPSConnection\nelse:\n    HTTPSConnection = DummyConnection\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/connectionpool.py",
    "content": "from __future__ import absolute_import\nimport errno\nimport logging\nimport sys\nimport warnings\n\nfrom socket import error as SocketError, timeout as SocketTimeout\nimport socket\n\n\nfrom .exceptions import (\n    ClosedPoolError,\n    ProtocolError,\n    EmptyPoolError,\n    HeaderParsingError,\n    HostChangedError,\n    LocationValueError,\n    MaxRetryError,\n    ProxyError,\n    ReadTimeoutError,\n    SSLError,\n    TimeoutError,\n    InsecureRequestWarning,\n    NewConnectionError,\n)\nfrom .packages.ssl_match_hostname import CertificateError\nfrom .packages import six\nfrom .packages.six.moves import queue\nfrom .connection import (\n    port_by_scheme,\n    DummyConnection,\n    HTTPConnection, HTTPSConnection, VerifiedHTTPSConnection,\n    HTTPException, BaseSSLError,\n)\nfrom .request import RequestMethods\nfrom .response import HTTPResponse\n\nfrom .util.connection import is_connection_dropped\nfrom .util.request import set_file_position\nfrom .util.response import assert_header_parsing\nfrom .util.retry import Retry\nfrom .util.timeout import Timeout\nfrom .util.url import get_host, Url, NORMALIZABLE_SCHEMES\nfrom .util.queue import LifoQueue\n\n\nxrange = six.moves.xrange\n\nlog = logging.getLogger(__name__)\n\n_Default = object()\n\n\n# Pool objects\nclass ConnectionPool(object):\n    \"\"\"\n    Base class for all connection pools, such as\n    :class:`.HTTPConnectionPool` and :class:`.HTTPSConnectionPool`.\n    \"\"\"\n\n    scheme = None\n    QueueCls = LifoQueue\n\n    def __init__(self, host, port=None):\n        if not host:\n            raise LocationValueError(\"No host specified.\")\n\n        self.host = _ipv6_host(host, self.scheme)\n        self._proxy_host = host.lower()\n        self.port = port\n\n    def __str__(self):\n        return '%s(host=%r, port=%r)' % (type(self).__name__,\n                                         self.host, self.port)\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        self.close()\n        # Return False to re-raise any potential exceptions\n        return False\n\n    def close(self):\n        \"\"\"\n        Close all pooled connections and disable the pool.\n        \"\"\"\n        pass\n\n\n# This is taken from http://hg.python.org/cpython/file/7aaba721ebc0/Lib/socket.py#l252\n_blocking_errnos = {errno.EAGAIN, errno.EWOULDBLOCK}\n\n\nclass HTTPConnectionPool(ConnectionPool, RequestMethods):\n    \"\"\"\n    Thread-safe connection pool for one host.\n\n    :param host:\n        Host used for this HTTP Connection (e.g. \"localhost\"), passed into\n        :class:`httplib.HTTPConnection`.\n\n    :param port:\n        Port used for this HTTP Connection (None is equivalent to 80), passed\n        into :class:`httplib.HTTPConnection`.\n\n    :param strict:\n        Causes BadStatusLine to be raised if the status line can't be parsed\n        as a valid HTTP/1.0 or 1.1 status line, passed into\n        :class:`httplib.HTTPConnection`.\n\n        .. note::\n           Only works in Python 2. This parameter is ignored in Python 3.\n\n    :param timeout:\n        Socket timeout in seconds for each individual connection. This can\n        be a float or integer, which sets the timeout for the HTTP request,\n        or an instance of :class:`urllib3.util.Timeout` which gives you more\n        fine-grained control over request timeouts. After the constructor has\n        been parsed, this is always a `urllib3.util.Timeout` object.\n\n    :param maxsize:\n        Number of connections to save that can be reused. More than 1 is useful\n        in multithreaded situations. If ``block`` is set to False, more\n        connections will be created but they will not be saved once they've\n        been used.\n\n    :param block:\n        If set to True, no more than ``maxsize`` connections will be used at\n        a time. When no free connections are available, the call will block\n        until a connection has been released. This is a useful side effect for\n        particular multithreaded situations where one does not want to use more\n        than maxsize connections per host to prevent flooding.\n\n    :param headers:\n        Headers to include with all requests, unless other headers are given\n        explicitly.\n\n    :param retries:\n        Retry configuration to use by default with requests in this pool.\n\n    :param _proxy:\n        Parsed proxy URL, should not be used directly, instead, see\n        :class:`urllib3.connectionpool.ProxyManager`\"\n\n    :param _proxy_headers:\n        A dictionary with proxy headers, should not be used directly,\n        instead, see :class:`urllib3.connectionpool.ProxyManager`\"\n\n    :param \\\\**conn_kw:\n        Additional parameters are used to create fresh :class:`urllib3.connection.HTTPConnection`,\n        :class:`urllib3.connection.HTTPSConnection` instances.\n    \"\"\"\n\n    scheme = 'http'\n    ConnectionCls = HTTPConnection\n    ResponseCls = HTTPResponse\n\n    def __init__(self, host, port=None, strict=False,\n                 timeout=Timeout.DEFAULT_TIMEOUT, maxsize=1, block=False,\n                 headers=None, retries=None,\n                 _proxy=None, _proxy_headers=None,\n                 **conn_kw):\n        ConnectionPool.__init__(self, host, port)\n        RequestMethods.__init__(self, headers)\n\n        self.strict = strict\n\n        if not isinstance(timeout, Timeout):\n            timeout = Timeout.from_float(timeout)\n\n        if retries is None:\n            retries = Retry.DEFAULT\n\n        self.timeout = timeout\n        self.retries = retries\n\n        self.pool = self.QueueCls(maxsize)\n        self.block = block\n\n        self.proxy = _proxy\n        self.proxy_headers = _proxy_headers or {}\n\n        # Fill the queue up so that doing get() on it will block properly\n        for _ in xrange(maxsize):\n            self.pool.put(None)\n\n        # These are mostly for testing and debugging purposes.\n        self.num_connections = 0\n        self.num_requests = 0\n        self.conn_kw = conn_kw\n\n        if self.proxy:\n            # Enable Nagle's algorithm for proxies, to avoid packet fragmentation.\n            # We cannot know if the user has added default socket options, so we cannot replace the\n            # list.\n            self.conn_kw.setdefault('socket_options', [])\n\n    def _new_conn(self):\n        \"\"\"\n        Return a fresh :class:`HTTPConnection`.\n        \"\"\"\n        self.num_connections += 1\n        log.debug(\"Starting new HTTP connection (%d): %s:%s\",\n                  self.num_connections, self.host, self.port or \"80\")\n\n        conn = self.ConnectionCls(host=self.host, port=self.port,\n                                  timeout=self.timeout.connect_timeout,\n                                  strict=self.strict, **self.conn_kw)\n        return conn\n\n    def _get_conn(self, timeout=None):\n        \"\"\"\n        Get a connection. Will return a pooled connection if one is available.\n\n        If no connections are available and :prop:`.block` is ``False``, then a\n        fresh connection is returned.\n\n        :param timeout:\n            Seconds to wait before giving up and raising\n            :class:`urllib3.exceptions.EmptyPoolError` if the pool is empty and\n            :prop:`.block` is ``True``.\n        \"\"\"\n        conn = None\n        try:\n            conn = self.pool.get(block=self.block, timeout=timeout)\n\n        except AttributeError:  # self.pool is None\n            raise ClosedPoolError(self, \"Pool is closed.\")\n\n        except queue.Empty:\n            if self.block:\n                raise EmptyPoolError(self,\n                                     \"Pool reached maximum size and no more \"\n                                     \"connections are allowed.\")\n            pass  # Oh well, we'll create a new connection then\n\n        # If this is a persistent connection, check if it got disconnected\n        if conn and is_connection_dropped(conn):\n            log.debug(\"Resetting dropped connection: %s\", self.host)\n            conn.close()\n            if getattr(conn, 'auto_open', 1) == 0:\n                # This is a proxied connection that has been mutated by\n                # httplib._tunnel() and cannot be reused (since it would\n                # attempt to bypass the proxy)\n                conn = None\n\n        return conn or self._new_conn()\n\n    def _put_conn(self, conn):\n        \"\"\"\n        Put a connection back into the pool.\n\n        :param conn:\n            Connection object for the current host and port as returned by\n            :meth:`._new_conn` or :meth:`._get_conn`.\n\n        If the pool is already full, the connection is closed and discarded\n        because we exceeded maxsize. If connections are discarded frequently,\n        then maxsize should be increased.\n\n        If the pool is closed, then the connection will be closed and discarded.\n        \"\"\"\n        try:\n            self.pool.put(conn, block=False)\n            return  # Everything is dandy, done.\n        except AttributeError:\n            # self.pool is None.\n            pass\n        except queue.Full:\n            # This should never happen if self.block == True\n            log.warning(\n                \"Connection pool is full, discarding connection: %s\",\n                self.host)\n\n        # Connection never got put back into the pool, close it.\n        if conn:\n            conn.close()\n\n    def _validate_conn(self, conn):\n        \"\"\"\n        Called right before a request is made, after the socket is created.\n        \"\"\"\n        pass\n\n    def _prepare_proxy(self, conn):\n        # Nothing to do for HTTP connections.\n        pass\n\n    def _get_timeout(self, timeout):\n        \"\"\" Helper that always returns a :class:`urllib3.util.Timeout` \"\"\"\n        if timeout is _Default:\n            return self.timeout.clone()\n\n        if isinstance(timeout, Timeout):\n            return timeout.clone()\n        else:\n            # User passed us an int/float. This is for backwards compatibility,\n            # can be removed later\n            return Timeout.from_float(timeout)\n\n    def _raise_timeout(self, err, url, timeout_value):\n        \"\"\"Is the error actually a timeout? Will raise a ReadTimeout or pass\"\"\"\n\n        if isinstance(err, SocketTimeout):\n            raise ReadTimeoutError(self, url, \"Read timed out. (read timeout=%s)\" % timeout_value)\n\n        # See the above comment about EAGAIN in Python 3. In Python 2 we have\n        # to specifically catch it and throw the timeout error\n        if hasattr(err, 'errno') and err.errno in _blocking_errnos:\n            raise ReadTimeoutError(self, url, \"Read timed out. (read timeout=%s)\" % timeout_value)\n\n        # Catch possible read timeouts thrown as SSL errors. If not the\n        # case, rethrow the original. We need to do this because of:\n        # http://bugs.python.org/issue10272\n        if 'timed out' in str(err) or 'did not complete (read)' in str(err):  # Python < 2.7.4\n            raise ReadTimeoutError(self, url, \"Read timed out. (read timeout=%s)\" % timeout_value)\n\n    def _make_request(self, conn, method, url, timeout=_Default, chunked=False,\n                      **httplib_request_kw):\n        \"\"\"\n        Perform a request on a given urllib connection object taken from our\n        pool.\n\n        :param conn:\n            a connection from one of our connection pools\n\n        :param timeout:\n            Socket timeout in seconds for the request. This can be a\n            float or integer, which will set the same timeout value for\n            the socket connect and the socket read, or an instance of\n            :class:`urllib3.util.Timeout`, which gives you more fine-grained\n            control over your timeouts.\n        \"\"\"\n        self.num_requests += 1\n\n        timeout_obj = self._get_timeout(timeout)\n        timeout_obj.start_connect()\n        conn.timeout = timeout_obj.connect_timeout\n\n        # Trigger any extra validation we need to do.\n        try:\n            self._validate_conn(conn)\n        except (SocketTimeout, BaseSSLError) as e:\n            # Py2 raises this as a BaseSSLError, Py3 raises it as socket timeout.\n            self._raise_timeout(err=e, url=url, timeout_value=conn.timeout)\n            raise\n\n        # conn.request() calls httplib.*.request, not the method in\n        # urllib3.request. It also calls makefile (recv) on the socket.\n        if chunked:\n            conn.request_chunked(method, url, **httplib_request_kw)\n        else:\n            conn.request(method, url, **httplib_request_kw)\n\n        # Reset the timeout for the recv() on the socket\n        read_timeout = timeout_obj.read_timeout\n\n        # App Engine doesn't have a sock attr\n        if getattr(conn, 'sock', None):\n            # In Python 3 socket.py will catch EAGAIN and return None when you\n            # try and read into the file pointer created by http.client, which\n            # instead raises a BadStatusLine exception. Instead of catching\n            # the exception and assuming all BadStatusLine exceptions are read\n            # timeouts, check for a zero timeout before making the request.\n            if read_timeout == 0:\n                raise ReadTimeoutError(\n                    self, url, \"Read timed out. (read timeout=%s)\" % read_timeout)\n            if read_timeout is Timeout.DEFAULT_TIMEOUT:\n                conn.sock.settimeout(socket.getdefaulttimeout())\n            else:  # None or a value\n                conn.sock.settimeout(read_timeout)\n\n        # Receive the response from the server\n        try:\n            try:  # Python 2.7, use buffering of HTTP responses\n                httplib_response = conn.getresponse(buffering=True)\n            except TypeError:  # Python 3\n                try:\n                    httplib_response = conn.getresponse()\n                except Exception as e:\n                    # Remove the TypeError from the exception chain in Python 3;\n                    # otherwise it looks like a programming error was the cause.\n                    six.raise_from(e, None)\n        except (SocketTimeout, BaseSSLError, SocketError) as e:\n            self._raise_timeout(err=e, url=url, timeout_value=read_timeout)\n            raise\n\n        # AppEngine doesn't have a version attr.\n        http_version = getattr(conn, '_http_vsn_str', 'HTTP/?')\n        log.debug(\"%s://%s:%s \\\"%s %s %s\\\" %s %s\", self.scheme, self.host, self.port,\n                  method, url, http_version, httplib_response.status,\n                  httplib_response.length)\n\n        try:\n            assert_header_parsing(httplib_response.msg)\n        except (HeaderParsingError, TypeError) as hpe:  # Platform-specific: Python 3\n            log.warning(\n                'Failed to parse headers (url=%s): %s',\n                self._absolute_url(url), hpe, exc_info=True)\n\n        return httplib_response\n\n    def _absolute_url(self, path):\n        return Url(scheme=self.scheme, host=self.host, port=self.port, path=path).url\n\n    def close(self):\n        \"\"\"\n        Close all pooled connections and disable the pool.\n        \"\"\"\n        if self.pool is None:\n            return\n        # Disable access to the pool\n        old_pool, self.pool = self.pool, None\n\n        try:\n            while True:\n                conn = old_pool.get(block=False)\n                if conn:\n                    conn.close()\n\n        except queue.Empty:\n            pass  # Done.\n\n    def is_same_host(self, url):\n        \"\"\"\n        Check if the given ``url`` is a member of the same host as this\n        connection pool.\n        \"\"\"\n        if url.startswith('/'):\n            return True\n\n        # TODO: Add optional support for socket.gethostbyname checking.\n        scheme, host, port = get_host(url)\n\n        host = _ipv6_host(host, self.scheme)\n\n        # Use explicit default port for comparison when none is given\n        if self.port and not port:\n            port = port_by_scheme.get(scheme)\n        elif not self.port and port == port_by_scheme.get(scheme):\n            port = None\n\n        return (scheme, host, port) == (self.scheme, self.host, self.port)\n\n    def urlopen(self, method, url, body=None, headers=None, retries=None,\n                redirect=True, assert_same_host=True, timeout=_Default,\n                pool_timeout=None, release_conn=None, chunked=False,\n                body_pos=None, **response_kw):\n        \"\"\"\n        Get a connection from the pool and perform an HTTP request. This is the\n        lowest level call for making a request, so you'll need to specify all\n        the raw details.\n\n        .. note::\n\n           More commonly, it's appropriate to use a convenience method provided\n           by :class:`.RequestMethods`, such as :meth:`request`.\n\n        .. note::\n\n           `release_conn` will only behave as expected if\n           `preload_content=False` because we want to make\n           `preload_content=False` the default behaviour someday soon without\n           breaking backwards compatibility.\n\n        :param method:\n            HTTP request method (such as GET, POST, PUT, etc.)\n\n        :param body:\n            Data to send in the request body (useful for creating\n            POST requests, see HTTPConnectionPool.post_url for\n            more convenience).\n\n        :param headers:\n            Dictionary of custom headers to send, such as User-Agent,\n            If-None-Match, etc. If None, pool headers are used. If provided,\n            these headers completely replace any pool-specific headers.\n\n        :param retries:\n            Configure the number of retries to allow before raising a\n            :class:`~urllib3.exceptions.MaxRetryError` exception.\n\n            Pass ``None`` to retry until you receive a response. Pass a\n            :class:`~urllib3.util.retry.Retry` object for fine-grained control\n            over different types of retries.\n            Pass an integer number to retry connection errors that many times,\n            but no other types of errors. Pass zero to never retry.\n\n            If ``False``, then retries are disabled and any exception is raised\n            immediately. Also, instead of raising a MaxRetryError on redirects,\n            the redirect response will be returned.\n\n        :type retries: :class:`~urllib3.util.retry.Retry`, False, or an int.\n\n        :param redirect:\n            If True, automatically handle redirects (status codes 301, 302,\n            303, 307, 308). Each redirect counts as a retry. Disabling retries\n            will disable redirect, too.\n\n        :param assert_same_host:\n            If ``True``, will make sure that the host of the pool requests is\n            consistent else will raise HostChangedError. When False, you can\n            use the pool on an HTTP proxy and request foreign hosts.\n\n        :param timeout:\n            If specified, overrides the default timeout for this one\n            request. It may be a float (in seconds) or an instance of\n            :class:`urllib3.util.Timeout`.\n\n        :param pool_timeout:\n            If set and the pool is set to block=True, then this method will\n            block for ``pool_timeout`` seconds and raise EmptyPoolError if no\n            connection is available within the time period.\n\n        :param release_conn:\n            If False, then the urlopen call will not release the connection\n            back into the pool once a response is received (but will release if\n            you read the entire contents of the response such as when\n            `preload_content=True`). This is useful if you're not preloading\n            the response's content immediately. You will need to call\n            ``r.release_conn()`` on the response ``r`` to return the connection\n            back into the pool. If None, it takes the value of\n            ``response_kw.get('preload_content', True)``.\n\n        :param chunked:\n            If True, urllib3 will send the body using chunked transfer\n            encoding. Otherwise, urllib3 will send the body using the standard\n            content-length form. Defaults to False.\n\n        :param int body_pos:\n            Position to seek to in file-like body in the event of a retry or\n            redirect. Typically this won't need to be set because urllib3 will\n            auto-populate the value when needed.\n\n        :param \\\\**response_kw:\n            Additional parameters are passed to\n            :meth:`urllib3.response.HTTPResponse.from_httplib`\n        \"\"\"\n        if headers is None:\n            headers = self.headers\n\n        if not isinstance(retries, Retry):\n            retries = Retry.from_int(retries, redirect=redirect, default=self.retries)\n\n        if release_conn is None:\n            release_conn = response_kw.get('preload_content', True)\n\n        # Check host\n        if assert_same_host and not self.is_same_host(url):\n            raise HostChangedError(self, url, retries)\n\n        conn = None\n\n        # Track whether `conn` needs to be released before\n        # returning/raising/recursing. Update this variable if necessary, and\n        # leave `release_conn` constant throughout the function. That way, if\n        # the function recurses, the original value of `release_conn` will be\n        # passed down into the recursive call, and its value will be respected.\n        #\n        # See issue #651 [1] for details.\n        #\n        # [1] <https://github.com/shazow/urllib3/issues/651>\n        release_this_conn = release_conn\n\n        # Merge the proxy headers. Only do this in HTTP. We have to copy the\n        # headers dict so we can safely change it without those changes being\n        # reflected in anyone else's copy.\n        if self.scheme == 'http':\n            headers = headers.copy()\n            headers.update(self.proxy_headers)\n\n        # Must keep the exception bound to a separate variable or else Python 3\n        # complains about UnboundLocalError.\n        err = None\n\n        # Keep track of whether we cleanly exited the except block. This\n        # ensures we do proper cleanup in finally.\n        clean_exit = False\n\n        # Rewind body position, if needed. Record current position\n        # for future rewinds in the event of a redirect/retry.\n        body_pos = set_file_position(body, body_pos)\n\n        try:\n            # Request a connection from the queue.\n            timeout_obj = self._get_timeout(timeout)\n            conn = self._get_conn(timeout=pool_timeout)\n\n            conn.timeout = timeout_obj.connect_timeout\n\n            is_new_proxy_conn = self.proxy is not None and not getattr(conn, 'sock', None)\n            if is_new_proxy_conn:\n                self._prepare_proxy(conn)\n\n            # Make the request on the httplib connection object.\n            httplib_response = self._make_request(conn, method, url,\n                                                  timeout=timeout_obj,\n                                                  body=body, headers=headers,\n                                                  chunked=chunked)\n\n            # If we're going to release the connection in ``finally:``, then\n            # the response doesn't need to know about the connection. Otherwise\n            # it will also try to release it and we'll have a double-release\n            # mess.\n            response_conn = conn if not release_conn else None\n\n            # Pass method to Response for length checking\n            response_kw['request_method'] = method\n\n            # Import httplib's response into our own wrapper object\n            response = self.ResponseCls.from_httplib(httplib_response,\n                                                     pool=self,\n                                                     connection=response_conn,\n                                                     retries=retries,\n                                                     **response_kw)\n\n            # Everything went great!\n            clean_exit = True\n\n        except queue.Empty:\n            # Timed out by queue.\n            raise EmptyPoolError(self, \"No pool connections are available.\")\n\n        except (TimeoutError, HTTPException, SocketError, ProtocolError,\n                BaseSSLError, SSLError, CertificateError) as e:\n            # Discard the connection for these exceptions. It will be\n            # replaced during the next _get_conn() call.\n            clean_exit = False\n            if isinstance(e, (BaseSSLError, CertificateError)):\n                e = SSLError(e)\n            elif isinstance(e, (SocketError, NewConnectionError)) and self.proxy:\n                e = ProxyError('Cannot connect to proxy.', e)\n            elif isinstance(e, (SocketError, HTTPException)):\n                e = ProtocolError('Connection aborted.', e)\n\n            retries = retries.increment(method, url, error=e, _pool=self,\n                                        _stacktrace=sys.exc_info()[2])\n            retries.sleep()\n\n            # Keep track of the error for the retry warning.\n            err = e\n\n        finally:\n            if not clean_exit:\n                # We hit some kind of exception, handled or otherwise. We need\n                # to throw the connection away unless explicitly told not to.\n                # Close the connection, set the variable to None, and make sure\n                # we put the None back in the pool to avoid leaking it.\n                conn = conn and conn.close()\n                release_this_conn = True\n\n            if release_this_conn:\n                # Put the connection back to be reused. If the connection is\n                # expired then it will be None, which will get replaced with a\n                # fresh connection during _get_conn.\n                self._put_conn(conn)\n\n        if not conn:\n            # Try again\n            log.warning(\"Retrying (%r) after connection \"\n                        \"broken by '%r': %s\", retries, err, url)\n            return self.urlopen(method, url, body, headers, retries,\n                                redirect, assert_same_host,\n                                timeout=timeout, pool_timeout=pool_timeout,\n                                release_conn=release_conn, body_pos=body_pos,\n                                **response_kw)\n\n        def drain_and_release_conn(response):\n            try:\n                # discard any remaining response body, the connection will be\n                # released back to the pool once the entire response is read\n                response.read()\n            except (TimeoutError, HTTPException, SocketError, ProtocolError,\n                    BaseSSLError, SSLError) as e:\n                pass\n\n        # Handle redirect?\n        redirect_location = redirect and response.get_redirect_location()\n        if redirect_location:\n            if response.status == 303:\n                method = 'GET'\n\n            try:\n                retries = retries.increment(method, url, response=response, _pool=self)\n            except MaxRetryError:\n                if retries.raise_on_redirect:\n                    # Drain and release the connection for this response, since\n                    # we're not returning it to be released manually.\n                    drain_and_release_conn(response)\n                    raise\n                return response\n\n            # drain and return the connection to the pool before recursing\n            drain_and_release_conn(response)\n\n            retries.sleep_for_retry(response)\n            log.debug(\"Redirecting %s -> %s\", url, redirect_location)\n            return self.urlopen(\n                method, redirect_location, body, headers,\n                retries=retries, redirect=redirect,\n                assert_same_host=assert_same_host,\n                timeout=timeout, pool_timeout=pool_timeout,\n                release_conn=release_conn, body_pos=body_pos,\n                **response_kw)\n\n        # Check if we should retry the HTTP response.\n        has_retry_after = bool(response.getheader('Retry-After'))\n        if retries.is_retry(method, response.status, has_retry_after):\n            try:\n                retries = retries.increment(method, url, response=response, _pool=self)\n            except MaxRetryError:\n                if retries.raise_on_status:\n                    # Drain and release the connection for this response, since\n                    # we're not returning it to be released manually.\n                    drain_and_release_conn(response)\n                    raise\n                return response\n\n            # drain and return the connection to the pool before recursing\n            drain_and_release_conn(response)\n\n            retries.sleep(response)\n            log.debug(\"Retry: %s\", url)\n            return self.urlopen(\n                method, url, body, headers,\n                retries=retries, redirect=redirect,\n                assert_same_host=assert_same_host,\n                timeout=timeout, pool_timeout=pool_timeout,\n                release_conn=release_conn,\n                body_pos=body_pos, **response_kw)\n\n        return response\n\n\nclass HTTPSConnectionPool(HTTPConnectionPool):\n    \"\"\"\n    Same as :class:`.HTTPConnectionPool`, but HTTPS.\n\n    When Python is compiled with the :mod:`ssl` module, then\n    :class:`.VerifiedHTTPSConnection` is used, which *can* verify certificates,\n    instead of :class:`.HTTPSConnection`.\n\n    :class:`.VerifiedHTTPSConnection` uses one of ``assert_fingerprint``,\n    ``assert_hostname`` and ``host`` in this order to verify connections.\n    If ``assert_hostname`` is False, no verification is done.\n\n    The ``key_file``, ``cert_file``, ``cert_reqs``, ``ca_certs``,\n    ``ca_cert_dir``, and ``ssl_version`` are only used if :mod:`ssl` is\n    available and are fed into :meth:`urllib3.util.ssl_wrap_socket` to upgrade\n    the connection socket into an SSL socket.\n    \"\"\"\n\n    scheme = 'https'\n    ConnectionCls = HTTPSConnection\n\n    def __init__(self, host, port=None,\n                 strict=False, timeout=Timeout.DEFAULT_TIMEOUT, maxsize=1,\n                 block=False, headers=None, retries=None,\n                 _proxy=None, _proxy_headers=None,\n                 key_file=None, cert_file=None, cert_reqs=None,\n                 ca_certs=None, ssl_version=None,\n                 assert_hostname=None, assert_fingerprint=None,\n                 ca_cert_dir=None, **conn_kw):\n\n        HTTPConnectionPool.__init__(self, host, port, strict, timeout, maxsize,\n                                    block, headers, retries, _proxy, _proxy_headers,\n                                    **conn_kw)\n\n        if ca_certs and cert_reqs is None:\n            cert_reqs = 'CERT_REQUIRED'\n\n        self.key_file = key_file\n        self.cert_file = cert_file\n        self.cert_reqs = cert_reqs\n        self.ca_certs = ca_certs\n        self.ca_cert_dir = ca_cert_dir\n        self.ssl_version = ssl_version\n        self.assert_hostname = assert_hostname\n        self.assert_fingerprint = assert_fingerprint\n\n    def _prepare_conn(self, conn):\n        \"\"\"\n        Prepare the ``connection`` for :meth:`urllib3.util.ssl_wrap_socket`\n        and establish the tunnel if proxy is used.\n        \"\"\"\n\n        if isinstance(conn, VerifiedHTTPSConnection):\n            conn.set_cert(key_file=self.key_file,\n                          cert_file=self.cert_file,\n                          cert_reqs=self.cert_reqs,\n                          ca_certs=self.ca_certs,\n                          ca_cert_dir=self.ca_cert_dir,\n                          assert_hostname=self.assert_hostname,\n                          assert_fingerprint=self.assert_fingerprint)\n            conn.ssl_version = self.ssl_version\n        return conn\n\n    def _prepare_proxy(self, conn):\n        \"\"\"\n        Establish tunnel connection early, because otherwise httplib\n        would improperly set Host: header to proxy's IP:port.\n        \"\"\"\n        conn.set_tunnel(self._proxy_host, self.port, self.proxy_headers)\n        conn.connect()\n\n    def _new_conn(self):\n        \"\"\"\n        Return a fresh :class:`httplib.HTTPSConnection`.\n        \"\"\"\n        self.num_connections += 1\n        log.debug(\"Starting new HTTPS connection (%d): %s:%s\",\n                  self.num_connections, self.host, self.port or \"443\")\n\n        if not self.ConnectionCls or self.ConnectionCls is DummyConnection:\n            raise SSLError(\"Can't connect to HTTPS URL because the SSL \"\n                           \"module is not available.\")\n\n        actual_host = self.host\n        actual_port = self.port\n        if self.proxy is not None:\n            actual_host = self.proxy.host\n            actual_port = self.proxy.port\n\n        conn = self.ConnectionCls(host=actual_host, port=actual_port,\n                                  timeout=self.timeout.connect_timeout,\n                                  strict=self.strict, **self.conn_kw)\n\n        return self._prepare_conn(conn)\n\n    def _validate_conn(self, conn):\n        \"\"\"\n        Called right before a request is made, after the socket is created.\n        \"\"\"\n        super(HTTPSConnectionPool, self)._validate_conn(conn)\n\n        # Force connect early to allow us to validate the connection.\n        if not getattr(conn, 'sock', None):  # AppEngine might not have  `.sock`\n            conn.connect()\n\n        if not conn.is_verified:\n            warnings.warn((\n                'Unverified HTTPS request is being made. '\n                'Adding certificate verification is strongly advised. See: '\n                'https://urllib3.readthedocs.io/en/latest/advanced-usage.html'\n                '#ssl-warnings'),\n                InsecureRequestWarning)\n\n\ndef connection_from_url(url, **kw):\n    \"\"\"\n    Given a url, return an :class:`.ConnectionPool` instance of its host.\n\n    This is a shortcut for not having to parse out the scheme, host, and port\n    of the url before creating an :class:`.ConnectionPool` instance.\n\n    :param url:\n        Absolute URL string that must include the scheme. Port is optional.\n\n    :param \\\\**kw:\n        Passes additional parameters to the constructor of the appropriate\n        :class:`.ConnectionPool`. Useful for specifying things like\n        timeout, maxsize, headers, etc.\n\n    Example::\n\n        >>> conn = connection_from_url('http://google.com/')\n        >>> r = conn.request('GET', '/')\n    \"\"\"\n    scheme, host, port = get_host(url)\n    port = port or port_by_scheme.get(scheme, 80)\n    if scheme == 'https':\n        return HTTPSConnectionPool(host, port=port, **kw)\n    else:\n        return HTTPConnectionPool(host, port=port, **kw)\n\n\ndef _ipv6_host(host, scheme):\n    \"\"\"\n    Process IPv6 address literals\n    \"\"\"\n\n    # httplib doesn't like it when we include brackets in IPv6 addresses\n    # Specifically, if we include brackets but also pass the port then\n    # httplib crazily doubles up the square brackets on the Host header.\n    # Instead, we need to make sure we never pass ``None`` as the port.\n    # However, for backward compatibility reasons we can't actually\n    # *assert* that.  See http://bugs.python.org/issue28539\n    #\n    # Also if an IPv6 address literal has a zone identifier, the\n    # percent sign might be URIencoded, convert it back into ASCII\n    if host.startswith('[') and host.endswith(']'):\n        host = host.replace('%25', '%').strip('[]')\n    if scheme in NORMALIZABLE_SCHEMES:\n        host = host.lower()\n    return host\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/contrib/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/contrib/_appengine_environ.py",
    "content": "\"\"\"\nThis module provides means to detect the App Engine environment.\n\"\"\"\n\nimport os\n\n\ndef is_appengine():\n    return (is_local_appengine() or\n            is_prod_appengine() or\n            is_prod_appengine_mvms())\n\n\ndef is_appengine_sandbox():\n    return is_appengine() and not is_prod_appengine_mvms()\n\n\ndef is_local_appengine():\n    return ('APPENGINE_RUNTIME' in os.environ and\n            'Development/' in os.environ['SERVER_SOFTWARE'])\n\n\ndef is_prod_appengine():\n    return ('APPENGINE_RUNTIME' in os.environ and\n            'Google App Engine/' in os.environ['SERVER_SOFTWARE'] and\n            not is_prod_appengine_mvms())\n\n\ndef is_prod_appengine_mvms():\n    return os.environ.get('GAE_VM', False) == 'true'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/contrib/_securetransport/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/contrib/_securetransport/bindings.py",
    "content": "\"\"\"\nThis module uses ctypes to bind a whole bunch of functions and constants from\nSecureTransport. The goal here is to provide the low-level API to\nSecureTransport. These are essentially the C-level functions and constants, and\nthey're pretty gross to work with.\n\nThis code is a bastardised version of the code found in Will Bond's oscrypto\nlibrary. An enormous debt is owed to him for blazing this trail for us. For\nthat reason, this code should be considered to be covered both by urllib3's\nlicense and by oscrypto's:\n\n    Copyright (c) 2015-2016 Will Bond <will@wbond.net>\n\n    Permission is hereby granted, free of charge, to any person obtaining a\n    copy of this software and associated documentation files (the \"Software\"),\n    to deal in the Software without restriction, including without limitation\n    the rights to use, copy, modify, merge, publish, distribute, sublicense,\n    and/or sell copies of the Software, and to permit persons to whom the\n    Software is furnished to do so, subject to the following conditions:\n\n    The above copyright notice and this permission notice shall be included in\n    all copies or substantial portions of the Software.\n\n    THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n    IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n    FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n    AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n    LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING\n    FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER\n    DEALINGS IN THE SOFTWARE.\n\"\"\"\nfrom __future__ import absolute_import\n\nimport platform\nfrom ctypes.util import find_library\nfrom ctypes import (\n    c_void_p, c_int32, c_char_p, c_size_t, c_byte, c_uint32, c_ulong, c_long,\n    c_bool\n)\nfrom ctypes import CDLL, POINTER, CFUNCTYPE\n\n\nsecurity_path = find_library('Security')\nif not security_path:\n    raise ImportError('The library Security could not be found')\n\n\ncore_foundation_path = find_library('CoreFoundation')\nif not core_foundation_path:\n    raise ImportError('The library CoreFoundation could not be found')\n\n\nversion = platform.mac_ver()[0]\nversion_info = tuple(map(int, version.split('.')))\nif version_info < (10, 8):\n    raise OSError(\n        'Only OS X 10.8 and newer are supported, not %s.%s' % (\n            version_info[0], version_info[1]\n        )\n    )\n\nSecurity = CDLL(security_path, use_errno=True)\nCoreFoundation = CDLL(core_foundation_path, use_errno=True)\n\nBoolean = c_bool\nCFIndex = c_long\nCFStringEncoding = c_uint32\nCFData = c_void_p\nCFString = c_void_p\nCFArray = c_void_p\nCFMutableArray = c_void_p\nCFDictionary = c_void_p\nCFError = c_void_p\nCFType = c_void_p\nCFTypeID = c_ulong\n\nCFTypeRef = POINTER(CFType)\nCFAllocatorRef = c_void_p\n\nOSStatus = c_int32\n\nCFDataRef = POINTER(CFData)\nCFStringRef = POINTER(CFString)\nCFArrayRef = POINTER(CFArray)\nCFMutableArrayRef = POINTER(CFMutableArray)\nCFDictionaryRef = POINTER(CFDictionary)\nCFArrayCallBacks = c_void_p\nCFDictionaryKeyCallBacks = c_void_p\nCFDictionaryValueCallBacks = c_void_p\n\nSecCertificateRef = POINTER(c_void_p)\nSecExternalFormat = c_uint32\nSecExternalItemType = c_uint32\nSecIdentityRef = POINTER(c_void_p)\nSecItemImportExportFlags = c_uint32\nSecItemImportExportKeyParameters = c_void_p\nSecKeychainRef = POINTER(c_void_p)\nSSLProtocol = c_uint32\nSSLCipherSuite = c_uint32\nSSLContextRef = POINTER(c_void_p)\nSecTrustRef = POINTER(c_void_p)\nSSLConnectionRef = c_uint32\nSecTrustResultType = c_uint32\nSecTrustOptionFlags = c_uint32\nSSLProtocolSide = c_uint32\nSSLConnectionType = c_uint32\nSSLSessionOption = c_uint32\n\n\ntry:\n    Security.SecItemImport.argtypes = [\n        CFDataRef,\n        CFStringRef,\n        POINTER(SecExternalFormat),\n        POINTER(SecExternalItemType),\n        SecItemImportExportFlags,\n        POINTER(SecItemImportExportKeyParameters),\n        SecKeychainRef,\n        POINTER(CFArrayRef),\n    ]\n    Security.SecItemImport.restype = OSStatus\n\n    Security.SecCertificateGetTypeID.argtypes = []\n    Security.SecCertificateGetTypeID.restype = CFTypeID\n\n    Security.SecIdentityGetTypeID.argtypes = []\n    Security.SecIdentityGetTypeID.restype = CFTypeID\n\n    Security.SecKeyGetTypeID.argtypes = []\n    Security.SecKeyGetTypeID.restype = CFTypeID\n\n    Security.SecCertificateCreateWithData.argtypes = [\n        CFAllocatorRef,\n        CFDataRef\n    ]\n    Security.SecCertificateCreateWithData.restype = SecCertificateRef\n\n    Security.SecCertificateCopyData.argtypes = [\n        SecCertificateRef\n    ]\n    Security.SecCertificateCopyData.restype = CFDataRef\n\n    Security.SecCopyErrorMessageString.argtypes = [\n        OSStatus,\n        c_void_p\n    ]\n    Security.SecCopyErrorMessageString.restype = CFStringRef\n\n    Security.SecIdentityCreateWithCertificate.argtypes = [\n        CFTypeRef,\n        SecCertificateRef,\n        POINTER(SecIdentityRef)\n    ]\n    Security.SecIdentityCreateWithCertificate.restype = OSStatus\n\n    Security.SecKeychainCreate.argtypes = [\n        c_char_p,\n        c_uint32,\n        c_void_p,\n        Boolean,\n        c_void_p,\n        POINTER(SecKeychainRef)\n    ]\n    Security.SecKeychainCreate.restype = OSStatus\n\n    Security.SecKeychainDelete.argtypes = [\n        SecKeychainRef\n    ]\n    Security.SecKeychainDelete.restype = OSStatus\n\n    Security.SecPKCS12Import.argtypes = [\n        CFDataRef,\n        CFDictionaryRef,\n        POINTER(CFArrayRef)\n    ]\n    Security.SecPKCS12Import.restype = OSStatus\n\n    SSLReadFunc = CFUNCTYPE(OSStatus, SSLConnectionRef, c_void_p, POINTER(c_size_t))\n    SSLWriteFunc = CFUNCTYPE(OSStatus, SSLConnectionRef, POINTER(c_byte), POINTER(c_size_t))\n\n    Security.SSLSetIOFuncs.argtypes = [\n        SSLContextRef,\n        SSLReadFunc,\n        SSLWriteFunc\n    ]\n    Security.SSLSetIOFuncs.restype = OSStatus\n\n    Security.SSLSetPeerID.argtypes = [\n        SSLContextRef,\n        c_char_p,\n        c_size_t\n    ]\n    Security.SSLSetPeerID.restype = OSStatus\n\n    Security.SSLSetCertificate.argtypes = [\n        SSLContextRef,\n        CFArrayRef\n    ]\n    Security.SSLSetCertificate.restype = OSStatus\n\n    Security.SSLSetCertificateAuthorities.argtypes = [\n        SSLContextRef,\n        CFTypeRef,\n        Boolean\n    ]\n    Security.SSLSetCertificateAuthorities.restype = OSStatus\n\n    Security.SSLSetConnection.argtypes = [\n        SSLContextRef,\n        SSLConnectionRef\n    ]\n    Security.SSLSetConnection.restype = OSStatus\n\n    Security.SSLSetPeerDomainName.argtypes = [\n        SSLContextRef,\n        c_char_p,\n        c_size_t\n    ]\n    Security.SSLSetPeerDomainName.restype = OSStatus\n\n    Security.SSLHandshake.argtypes = [\n        SSLContextRef\n    ]\n    Security.SSLHandshake.restype = OSStatus\n\n    Security.SSLRead.argtypes = [\n        SSLContextRef,\n        c_char_p,\n        c_size_t,\n        POINTER(c_size_t)\n    ]\n    Security.SSLRead.restype = OSStatus\n\n    Security.SSLWrite.argtypes = [\n        SSLContextRef,\n        c_char_p,\n        c_size_t,\n        POINTER(c_size_t)\n    ]\n    Security.SSLWrite.restype = OSStatus\n\n    Security.SSLClose.argtypes = [\n        SSLContextRef\n    ]\n    Security.SSLClose.restype = OSStatus\n\n    Security.SSLGetNumberSupportedCiphers.argtypes = [\n        SSLContextRef,\n        POINTER(c_size_t)\n    ]\n    Security.SSLGetNumberSupportedCiphers.restype = OSStatus\n\n    Security.SSLGetSupportedCiphers.argtypes = [\n        SSLContextRef,\n        POINTER(SSLCipherSuite),\n        POINTER(c_size_t)\n    ]\n    Security.SSLGetSupportedCiphers.restype = OSStatus\n\n    Security.SSLSetEnabledCiphers.argtypes = [\n        SSLContextRef,\n        POINTER(SSLCipherSuite),\n        c_size_t\n    ]\n    Security.SSLSetEnabledCiphers.restype = OSStatus\n\n    Security.SSLGetNumberEnabledCiphers.argtype = [\n        SSLContextRef,\n        POINTER(c_size_t)\n    ]\n    Security.SSLGetNumberEnabledCiphers.restype = OSStatus\n\n    Security.SSLGetEnabledCiphers.argtypes = [\n        SSLContextRef,\n        POINTER(SSLCipherSuite),\n        POINTER(c_size_t)\n    ]\n    Security.SSLGetEnabledCiphers.restype = OSStatus\n\n    Security.SSLGetNegotiatedCipher.argtypes = [\n        SSLContextRef,\n        POINTER(SSLCipherSuite)\n    ]\n    Security.SSLGetNegotiatedCipher.restype = OSStatus\n\n    Security.SSLGetNegotiatedProtocolVersion.argtypes = [\n        SSLContextRef,\n        POINTER(SSLProtocol)\n    ]\n    Security.SSLGetNegotiatedProtocolVersion.restype = OSStatus\n\n    Security.SSLCopyPeerTrust.argtypes = [\n        SSLContextRef,\n        POINTER(SecTrustRef)\n    ]\n    Security.SSLCopyPeerTrust.restype = OSStatus\n\n    Security.SecTrustSetAnchorCertificates.argtypes = [\n        SecTrustRef,\n        CFArrayRef\n    ]\n    Security.SecTrustSetAnchorCertificates.restype = OSStatus\n\n    Security.SecTrustSetAnchorCertificatesOnly.argstypes = [\n        SecTrustRef,\n        Boolean\n    ]\n    Security.SecTrustSetAnchorCertificatesOnly.restype = OSStatus\n\n    Security.SecTrustEvaluate.argtypes = [\n        SecTrustRef,\n        POINTER(SecTrustResultType)\n    ]\n    Security.SecTrustEvaluate.restype = OSStatus\n\n    Security.SecTrustGetCertificateCount.argtypes = [\n        SecTrustRef\n    ]\n    Security.SecTrustGetCertificateCount.restype = CFIndex\n\n    Security.SecTrustGetCertificateAtIndex.argtypes = [\n        SecTrustRef,\n        CFIndex\n    ]\n    Security.SecTrustGetCertificateAtIndex.restype = SecCertificateRef\n\n    Security.SSLCreateContext.argtypes = [\n        CFAllocatorRef,\n        SSLProtocolSide,\n        SSLConnectionType\n    ]\n    Security.SSLCreateContext.restype = SSLContextRef\n\n    Security.SSLSetSessionOption.argtypes = [\n        SSLContextRef,\n        SSLSessionOption,\n        Boolean\n    ]\n    Security.SSLSetSessionOption.restype = OSStatus\n\n    Security.SSLSetProtocolVersionMin.argtypes = [\n        SSLContextRef,\n        SSLProtocol\n    ]\n    Security.SSLSetProtocolVersionMin.restype = OSStatus\n\n    Security.SSLSetProtocolVersionMax.argtypes = [\n        SSLContextRef,\n        SSLProtocol\n    ]\n    Security.SSLSetProtocolVersionMax.restype = OSStatus\n\n    Security.SecCopyErrorMessageString.argtypes = [\n        OSStatus,\n        c_void_p\n    ]\n    Security.SecCopyErrorMessageString.restype = CFStringRef\n\n    Security.SSLReadFunc = SSLReadFunc\n    Security.SSLWriteFunc = SSLWriteFunc\n    Security.SSLContextRef = SSLContextRef\n    Security.SSLProtocol = SSLProtocol\n    Security.SSLCipherSuite = SSLCipherSuite\n    Security.SecIdentityRef = SecIdentityRef\n    Security.SecKeychainRef = SecKeychainRef\n    Security.SecTrustRef = SecTrustRef\n    Security.SecTrustResultType = SecTrustResultType\n    Security.SecExternalFormat = SecExternalFormat\n    Security.OSStatus = OSStatus\n\n    Security.kSecImportExportPassphrase = CFStringRef.in_dll(\n        Security, 'kSecImportExportPassphrase'\n    )\n    Security.kSecImportItemIdentity = CFStringRef.in_dll(\n        Security, 'kSecImportItemIdentity'\n    )\n\n    # CoreFoundation time!\n    CoreFoundation.CFRetain.argtypes = [\n        CFTypeRef\n    ]\n    CoreFoundation.CFRetain.restype = CFTypeRef\n\n    CoreFoundation.CFRelease.argtypes = [\n        CFTypeRef\n    ]\n    CoreFoundation.CFRelease.restype = None\n\n    CoreFoundation.CFGetTypeID.argtypes = [\n        CFTypeRef\n    ]\n    CoreFoundation.CFGetTypeID.restype = CFTypeID\n\n    CoreFoundation.CFStringCreateWithCString.argtypes = [\n        CFAllocatorRef,\n        c_char_p,\n        CFStringEncoding\n    ]\n    CoreFoundation.CFStringCreateWithCString.restype = CFStringRef\n\n    CoreFoundation.CFStringGetCStringPtr.argtypes = [\n        CFStringRef,\n        CFStringEncoding\n    ]\n    CoreFoundation.CFStringGetCStringPtr.restype = c_char_p\n\n    CoreFoundation.CFStringGetCString.argtypes = [\n        CFStringRef,\n        c_char_p,\n        CFIndex,\n        CFStringEncoding\n    ]\n    CoreFoundation.CFStringGetCString.restype = c_bool\n\n    CoreFoundation.CFDataCreate.argtypes = [\n        CFAllocatorRef,\n        c_char_p,\n        CFIndex\n    ]\n    CoreFoundation.CFDataCreate.restype = CFDataRef\n\n    CoreFoundation.CFDataGetLength.argtypes = [\n        CFDataRef\n    ]\n    CoreFoundation.CFDataGetLength.restype = CFIndex\n\n    CoreFoundation.CFDataGetBytePtr.argtypes = [\n        CFDataRef\n    ]\n    CoreFoundation.CFDataGetBytePtr.restype = c_void_p\n\n    CoreFoundation.CFDictionaryCreate.argtypes = [\n        CFAllocatorRef,\n        POINTER(CFTypeRef),\n        POINTER(CFTypeRef),\n        CFIndex,\n        CFDictionaryKeyCallBacks,\n        CFDictionaryValueCallBacks\n    ]\n    CoreFoundation.CFDictionaryCreate.restype = CFDictionaryRef\n\n    CoreFoundation.CFDictionaryGetValue.argtypes = [\n        CFDictionaryRef,\n        CFTypeRef\n    ]\n    CoreFoundation.CFDictionaryGetValue.restype = CFTypeRef\n\n    CoreFoundation.CFArrayCreate.argtypes = [\n        CFAllocatorRef,\n        POINTER(CFTypeRef),\n        CFIndex,\n        CFArrayCallBacks,\n    ]\n    CoreFoundation.CFArrayCreate.restype = CFArrayRef\n\n    CoreFoundation.CFArrayCreateMutable.argtypes = [\n        CFAllocatorRef,\n        CFIndex,\n        CFArrayCallBacks\n    ]\n    CoreFoundation.CFArrayCreateMutable.restype = CFMutableArrayRef\n\n    CoreFoundation.CFArrayAppendValue.argtypes = [\n        CFMutableArrayRef,\n        c_void_p\n    ]\n    CoreFoundation.CFArrayAppendValue.restype = None\n\n    CoreFoundation.CFArrayGetCount.argtypes = [\n        CFArrayRef\n    ]\n    CoreFoundation.CFArrayGetCount.restype = CFIndex\n\n    CoreFoundation.CFArrayGetValueAtIndex.argtypes = [\n        CFArrayRef,\n        CFIndex\n    ]\n    CoreFoundation.CFArrayGetValueAtIndex.restype = c_void_p\n\n    CoreFoundation.kCFAllocatorDefault = CFAllocatorRef.in_dll(\n        CoreFoundation, 'kCFAllocatorDefault'\n    )\n    CoreFoundation.kCFTypeArrayCallBacks = c_void_p.in_dll(CoreFoundation, 'kCFTypeArrayCallBacks')\n    CoreFoundation.kCFTypeDictionaryKeyCallBacks = c_void_p.in_dll(\n        CoreFoundation, 'kCFTypeDictionaryKeyCallBacks'\n    )\n    CoreFoundation.kCFTypeDictionaryValueCallBacks = c_void_p.in_dll(\n        CoreFoundation, 'kCFTypeDictionaryValueCallBacks'\n    )\n\n    CoreFoundation.CFTypeRef = CFTypeRef\n    CoreFoundation.CFArrayRef = CFArrayRef\n    CoreFoundation.CFStringRef = CFStringRef\n    CoreFoundation.CFDictionaryRef = CFDictionaryRef\n\nexcept (AttributeError):\n    raise ImportError('Error initializing ctypes')\n\n\nclass CFConst(object):\n    \"\"\"\n    A class object that acts as essentially a namespace for CoreFoundation\n    constants.\n    \"\"\"\n    kCFStringEncodingUTF8 = CFStringEncoding(0x08000100)\n\n\nclass SecurityConst(object):\n    \"\"\"\n    A class object that acts as essentially a namespace for Security constants.\n    \"\"\"\n    kSSLSessionOptionBreakOnServerAuth = 0\n\n    kSSLProtocol2 = 1\n    kSSLProtocol3 = 2\n    kTLSProtocol1 = 4\n    kTLSProtocol11 = 7\n    kTLSProtocol12 = 8\n\n    kSSLClientSide = 1\n    kSSLStreamType = 0\n\n    kSecFormatPEMSequence = 10\n\n    kSecTrustResultInvalid = 0\n    kSecTrustResultProceed = 1\n    # This gap is present on purpose: this was kSecTrustResultConfirm, which\n    # is deprecated.\n    kSecTrustResultDeny = 3\n    kSecTrustResultUnspecified = 4\n    kSecTrustResultRecoverableTrustFailure = 5\n    kSecTrustResultFatalTrustFailure = 6\n    kSecTrustResultOtherError = 7\n\n    errSSLProtocol = -9800\n    errSSLWouldBlock = -9803\n    errSSLClosedGraceful = -9805\n    errSSLClosedNoNotify = -9816\n    errSSLClosedAbort = -9806\n\n    errSSLXCertChainInvalid = -9807\n    errSSLCrypto = -9809\n    errSSLInternal = -9810\n    errSSLCertExpired = -9814\n    errSSLCertNotYetValid = -9815\n    errSSLUnknownRootCert = -9812\n    errSSLNoRootCert = -9813\n    errSSLHostNameMismatch = -9843\n    errSSLPeerHandshakeFail = -9824\n    errSSLPeerUserCancelled = -9839\n    errSSLWeakPeerEphemeralDHKey = -9850\n    errSSLServerAuthCompleted = -9841\n    errSSLRecordOverflow = -9847\n\n    errSecVerifyFailed = -67808\n    errSecNoTrustSettings = -25263\n    errSecItemNotFound = -25300\n    errSecInvalidTrustSettings = -25262\n\n    # Cipher suites. We only pick the ones our default cipher string allows.\n    TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384 = 0xC02C\n    TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 = 0xC030\n    TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256 = 0xC02B\n    TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 = 0xC02F\n    TLS_DHE_DSS_WITH_AES_256_GCM_SHA384 = 0x00A3\n    TLS_DHE_RSA_WITH_AES_256_GCM_SHA384 = 0x009F\n    TLS_DHE_DSS_WITH_AES_128_GCM_SHA256 = 0x00A2\n    TLS_DHE_RSA_WITH_AES_128_GCM_SHA256 = 0x009E\n    TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384 = 0xC024\n    TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384 = 0xC028\n    TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA = 0xC00A\n    TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA = 0xC014\n    TLS_DHE_RSA_WITH_AES_256_CBC_SHA256 = 0x006B\n    TLS_DHE_DSS_WITH_AES_256_CBC_SHA256 = 0x006A\n    TLS_DHE_RSA_WITH_AES_256_CBC_SHA = 0x0039\n    TLS_DHE_DSS_WITH_AES_256_CBC_SHA = 0x0038\n    TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256 = 0xC023\n    TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256 = 0xC027\n    TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA = 0xC009\n    TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA = 0xC013\n    TLS_DHE_RSA_WITH_AES_128_CBC_SHA256 = 0x0067\n    TLS_DHE_DSS_WITH_AES_128_CBC_SHA256 = 0x0040\n    TLS_DHE_RSA_WITH_AES_128_CBC_SHA = 0x0033\n    TLS_DHE_DSS_WITH_AES_128_CBC_SHA = 0x0032\n    TLS_RSA_WITH_AES_256_GCM_SHA384 = 0x009D\n    TLS_RSA_WITH_AES_128_GCM_SHA256 = 0x009C\n    TLS_RSA_WITH_AES_256_CBC_SHA256 = 0x003D\n    TLS_RSA_WITH_AES_128_CBC_SHA256 = 0x003C\n    TLS_RSA_WITH_AES_256_CBC_SHA = 0x0035\n    TLS_RSA_WITH_AES_128_CBC_SHA = 0x002F\n    TLS_AES_128_GCM_SHA256 = 0x1301\n    TLS_AES_256_GCM_SHA384 = 0x1302\n    TLS_CHACHA20_POLY1305_SHA256 = 0x1303\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/contrib/_securetransport/low_level.py",
    "content": "\"\"\"\nLow-level helpers for the SecureTransport bindings.\n\nThese are Python functions that are not directly related to the high-level APIs\nbut are necessary to get them to work. They include a whole bunch of low-level\nCoreFoundation messing about and memory management. The concerns in this module\nare almost entirely about trying to avoid memory leaks and providing\nappropriate and useful assistance to the higher-level code.\n\"\"\"\nimport base64\nimport ctypes\nimport itertools\nimport re\nimport os\nimport ssl\nimport tempfile\n\nfrom .bindings import Security, CoreFoundation, CFConst\n\n\n# This regular expression is used to grab PEM data out of a PEM bundle.\n_PEM_CERTS_RE = re.compile(\n    b\"-----BEGIN CERTIFICATE-----\\n(.*?)\\n-----END CERTIFICATE-----\", re.DOTALL\n)\n\n\ndef _cf_data_from_bytes(bytestring):\n    \"\"\"\n    Given a bytestring, create a CFData object from it. This CFData object must\n    be CFReleased by the caller.\n    \"\"\"\n    return CoreFoundation.CFDataCreate(\n        CoreFoundation.kCFAllocatorDefault, bytestring, len(bytestring)\n    )\n\n\ndef _cf_dictionary_from_tuples(tuples):\n    \"\"\"\n    Given a list of Python tuples, create an associated CFDictionary.\n    \"\"\"\n    dictionary_size = len(tuples)\n\n    # We need to get the dictionary keys and values out in the same order.\n    keys = (t[0] for t in tuples)\n    values = (t[1] for t in tuples)\n    cf_keys = (CoreFoundation.CFTypeRef * dictionary_size)(*keys)\n    cf_values = (CoreFoundation.CFTypeRef * dictionary_size)(*values)\n\n    return CoreFoundation.CFDictionaryCreate(\n        CoreFoundation.kCFAllocatorDefault,\n        cf_keys,\n        cf_values,\n        dictionary_size,\n        CoreFoundation.kCFTypeDictionaryKeyCallBacks,\n        CoreFoundation.kCFTypeDictionaryValueCallBacks,\n    )\n\n\ndef _cf_string_to_unicode(value):\n    \"\"\"\n    Creates a Unicode string from a CFString object. Used entirely for error\n    reporting.\n\n    Yes, it annoys me quite a lot that this function is this complex.\n    \"\"\"\n    value_as_void_p = ctypes.cast(value, ctypes.POINTER(ctypes.c_void_p))\n\n    string = CoreFoundation.CFStringGetCStringPtr(\n        value_as_void_p,\n        CFConst.kCFStringEncodingUTF8\n    )\n    if string is None:\n        buffer = ctypes.create_string_buffer(1024)\n        result = CoreFoundation.CFStringGetCString(\n            value_as_void_p,\n            buffer,\n            1024,\n            CFConst.kCFStringEncodingUTF8\n        )\n        if not result:\n            raise OSError('Error copying C string from CFStringRef')\n        string = buffer.value\n    if string is not None:\n        string = string.decode('utf-8')\n    return string\n\n\ndef _assert_no_error(error, exception_class=None):\n    \"\"\"\n    Checks the return code and throws an exception if there is an error to\n    report\n    \"\"\"\n    if error == 0:\n        return\n\n    cf_error_string = Security.SecCopyErrorMessageString(error, None)\n    output = _cf_string_to_unicode(cf_error_string)\n    CoreFoundation.CFRelease(cf_error_string)\n\n    if output is None or output == u'':\n        output = u'OSStatus %s' % error\n\n    if exception_class is None:\n        exception_class = ssl.SSLError\n\n    raise exception_class(output)\n\n\ndef _cert_array_from_pem(pem_bundle):\n    \"\"\"\n    Given a bundle of certs in PEM format, turns them into a CFArray of certs\n    that can be used to validate a cert chain.\n    \"\"\"\n    # Normalize the PEM bundle's line endings.\n    pem_bundle = pem_bundle.replace(b\"\\r\\n\", b\"\\n\")\n\n    der_certs = [\n        base64.b64decode(match.group(1))\n        for match in _PEM_CERTS_RE.finditer(pem_bundle)\n    ]\n    if not der_certs:\n        raise ssl.SSLError(\"No root certificates specified\")\n\n    cert_array = CoreFoundation.CFArrayCreateMutable(\n        CoreFoundation.kCFAllocatorDefault,\n        0,\n        ctypes.byref(CoreFoundation.kCFTypeArrayCallBacks)\n    )\n    if not cert_array:\n        raise ssl.SSLError(\"Unable to allocate memory!\")\n\n    try:\n        for der_bytes in der_certs:\n            certdata = _cf_data_from_bytes(der_bytes)\n            if not certdata:\n                raise ssl.SSLError(\"Unable to allocate memory!\")\n            cert = Security.SecCertificateCreateWithData(\n                CoreFoundation.kCFAllocatorDefault, certdata\n            )\n            CoreFoundation.CFRelease(certdata)\n            if not cert:\n                raise ssl.SSLError(\"Unable to build cert object!\")\n\n            CoreFoundation.CFArrayAppendValue(cert_array, cert)\n            CoreFoundation.CFRelease(cert)\n    except Exception:\n        # We need to free the array before the exception bubbles further.\n        # We only want to do that if an error occurs: otherwise, the caller\n        # should free.\n        CoreFoundation.CFRelease(cert_array)\n\n    return cert_array\n\n\ndef _is_cert(item):\n    \"\"\"\n    Returns True if a given CFTypeRef is a certificate.\n    \"\"\"\n    expected = Security.SecCertificateGetTypeID()\n    return CoreFoundation.CFGetTypeID(item) == expected\n\n\ndef _is_identity(item):\n    \"\"\"\n    Returns True if a given CFTypeRef is an identity.\n    \"\"\"\n    expected = Security.SecIdentityGetTypeID()\n    return CoreFoundation.CFGetTypeID(item) == expected\n\n\ndef _temporary_keychain():\n    \"\"\"\n    This function creates a temporary Mac keychain that we can use to work with\n    credentials. This keychain uses a one-time password and a temporary file to\n    store the data. We expect to have one keychain per socket. The returned\n    SecKeychainRef must be freed by the caller, including calling\n    SecKeychainDelete.\n\n    Returns a tuple of the SecKeychainRef and the path to the temporary\n    directory that contains it.\n    \"\"\"\n    # Unfortunately, SecKeychainCreate requires a path to a keychain. This\n    # means we cannot use mkstemp to use a generic temporary file. Instead,\n    # we're going to create a temporary directory and a filename to use there.\n    # This filename will be 8 random bytes expanded into base64. We also need\n    # some random bytes to password-protect the keychain we're creating, so we\n    # ask for 40 random bytes.\n    random_bytes = os.urandom(40)\n    filename = base64.b16encode(random_bytes[:8]).decode('utf-8')\n    password = base64.b16encode(random_bytes[8:])  # Must be valid UTF-8\n    tempdirectory = tempfile.mkdtemp()\n\n    keychain_path = os.path.join(tempdirectory, filename).encode('utf-8')\n\n    # We now want to create the keychain itself.\n    keychain = Security.SecKeychainRef()\n    status = Security.SecKeychainCreate(\n        keychain_path,\n        len(password),\n        password,\n        False,\n        None,\n        ctypes.byref(keychain)\n    )\n    _assert_no_error(status)\n\n    # Having created the keychain, we want to pass it off to the caller.\n    return keychain, tempdirectory\n\n\ndef _load_items_from_file(keychain, path):\n    \"\"\"\n    Given a single file, loads all the trust objects from it into arrays and\n    the keychain.\n    Returns a tuple of lists: the first list is a list of identities, the\n    second a list of certs.\n    \"\"\"\n    certificates = []\n    identities = []\n    result_array = None\n\n    with open(path, 'rb') as f:\n        raw_filedata = f.read()\n\n    try:\n        filedata = CoreFoundation.CFDataCreate(\n            CoreFoundation.kCFAllocatorDefault,\n            raw_filedata,\n            len(raw_filedata)\n        )\n        result_array = CoreFoundation.CFArrayRef()\n        result = Security.SecItemImport(\n            filedata,  # cert data\n            None,  # Filename, leaving it out for now\n            None,  # What the type of the file is, we don't care\n            None,  # what's in the file, we don't care\n            0,  # import flags\n            None,  # key params, can include passphrase in the future\n            keychain,  # The keychain to insert into\n            ctypes.byref(result_array)  # Results\n        )\n        _assert_no_error(result)\n\n        # A CFArray is not very useful to us as an intermediary\n        # representation, so we are going to extract the objects we want\n        # and then free the array. We don't need to keep hold of keys: the\n        # keychain already has them!\n        result_count = CoreFoundation.CFArrayGetCount(result_array)\n        for index in range(result_count):\n            item = CoreFoundation.CFArrayGetValueAtIndex(\n                result_array, index\n            )\n            item = ctypes.cast(item, CoreFoundation.CFTypeRef)\n\n            if _is_cert(item):\n                CoreFoundation.CFRetain(item)\n                certificates.append(item)\n            elif _is_identity(item):\n                CoreFoundation.CFRetain(item)\n                identities.append(item)\n    finally:\n        if result_array:\n            CoreFoundation.CFRelease(result_array)\n\n        CoreFoundation.CFRelease(filedata)\n\n    return (identities, certificates)\n\n\ndef _load_client_cert_chain(keychain, *paths):\n    \"\"\"\n    Load certificates and maybe keys from a number of files. Has the end goal\n    of returning a CFArray containing one SecIdentityRef, and then zero or more\n    SecCertificateRef objects, suitable for use as a client certificate trust\n    chain.\n    \"\"\"\n    # Ok, the strategy.\n    #\n    # This relies on knowing that macOS will not give you a SecIdentityRef\n    # unless you have imported a key into a keychain. This is a somewhat\n    # artificial limitation of macOS (for example, it doesn't necessarily\n    # affect iOS), but there is nothing inside Security.framework that lets you\n    # get a SecIdentityRef without having a key in a keychain.\n    #\n    # So the policy here is we take all the files and iterate them in order.\n    # Each one will use SecItemImport to have one or more objects loaded from\n    # it. We will also point at a keychain that macOS can use to work with the\n    # private key.\n    #\n    # Once we have all the objects, we'll check what we actually have. If we\n    # already have a SecIdentityRef in hand, fab: we'll use that. Otherwise,\n    # we'll take the first certificate (which we assume to be our leaf) and\n    # ask the keychain to give us a SecIdentityRef with that cert's associated\n    # key.\n    #\n    # We'll then return a CFArray containing the trust chain: one\n    # SecIdentityRef and then zero-or-more SecCertificateRef objects. The\n    # responsibility for freeing this CFArray will be with the caller. This\n    # CFArray must remain alive for the entire connection, so in practice it\n    # will be stored with a single SSLSocket, along with the reference to the\n    # keychain.\n    certificates = []\n    identities = []\n\n    # Filter out bad paths.\n    paths = (path for path in paths if path)\n\n    try:\n        for file_path in paths:\n            new_identities, new_certs = _load_items_from_file(\n                keychain, file_path\n            )\n            identities.extend(new_identities)\n            certificates.extend(new_certs)\n\n        # Ok, we have everything. The question is: do we have an identity? If\n        # not, we want to grab one from the first cert we have.\n        if not identities:\n            new_identity = Security.SecIdentityRef()\n            status = Security.SecIdentityCreateWithCertificate(\n                keychain,\n                certificates[0],\n                ctypes.byref(new_identity)\n            )\n            _assert_no_error(status)\n            identities.append(new_identity)\n\n            # We now want to release the original certificate, as we no longer\n            # need it.\n            CoreFoundation.CFRelease(certificates.pop(0))\n\n        # We now need to build a new CFArray that holds the trust chain.\n        trust_chain = CoreFoundation.CFArrayCreateMutable(\n            CoreFoundation.kCFAllocatorDefault,\n            0,\n            ctypes.byref(CoreFoundation.kCFTypeArrayCallBacks),\n        )\n        for item in itertools.chain(identities, certificates):\n            # ArrayAppendValue does a CFRetain on the item. That's fine,\n            # because the finally block will release our other refs to them.\n            CoreFoundation.CFArrayAppendValue(trust_chain, item)\n\n        return trust_chain\n    finally:\n        for obj in itertools.chain(identities, certificates):\n            CoreFoundation.CFRelease(obj)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/contrib/appengine.py",
    "content": "\"\"\"\nThis module provides a pool manager that uses Google App Engine's\n`URLFetch Service <https://cloud.google.com/appengine/docs/python/urlfetch>`_.\n\nExample usage::\n\n    from pip._vendor.urllib3 import PoolManager\n    from pip._vendor.urllib3.contrib.appengine import AppEngineManager, is_appengine_sandbox\n\n    if is_appengine_sandbox():\n        # AppEngineManager uses AppEngine's URLFetch API behind the scenes\n        http = AppEngineManager()\n    else:\n        # PoolManager uses a socket-level API behind the scenes\n        http = PoolManager()\n\n    r = http.request('GET', 'https://google.com/')\n\nThere are `limitations <https://cloud.google.com/appengine/docs/python/\\\nurlfetch/#Python_Quotas_and_limits>`_ to the URLFetch service and it may not be\nthe best choice for your application. There are three options for using\nurllib3 on Google App Engine:\n\n1. You can use :class:`AppEngineManager` with URLFetch. URLFetch is\n   cost-effective in many circumstances as long as your usage is within the\n   limitations.\n2. You can use a normal :class:`~urllib3.PoolManager` by enabling sockets.\n   Sockets also have `limitations and restrictions\n   <https://cloud.google.com/appengine/docs/python/sockets/\\\n   #limitations-and-restrictions>`_ and have a lower free quota than URLFetch.\n   To use sockets, be sure to specify the following in your ``app.yaml``::\n\n        env_variables:\n            GAE_USE_SOCKETS_HTTPLIB : 'true'\n\n3. If you are using `App Engine Flexible\n<https://cloud.google.com/appengine/docs/flexible/>`_, you can use the standard\n:class:`PoolManager` without any configuration or special environment variables.\n\"\"\"\n\nfrom __future__ import absolute_import\nimport io\nimport logging\nimport warnings\nfrom ..packages.six.moves.urllib.parse import urljoin\n\nfrom ..exceptions import (\n    HTTPError,\n    HTTPWarning,\n    MaxRetryError,\n    ProtocolError,\n    TimeoutError,\n    SSLError\n)\n\nfrom ..request import RequestMethods\nfrom ..response import HTTPResponse\nfrom ..util.timeout import Timeout\nfrom ..util.retry import Retry\nfrom . import _appengine_environ\n\ntry:\n    from google.appengine.api import urlfetch\nexcept ImportError:\n    urlfetch = None\n\n\nlog = logging.getLogger(__name__)\n\n\nclass AppEnginePlatformWarning(HTTPWarning):\n    pass\n\n\nclass AppEnginePlatformError(HTTPError):\n    pass\n\n\nclass AppEngineManager(RequestMethods):\n    \"\"\"\n    Connection manager for Google App Engine sandbox applications.\n\n    This manager uses the URLFetch service directly instead of using the\n    emulated httplib, and is subject to URLFetch limitations as described in\n    the App Engine documentation `here\n    <https://cloud.google.com/appengine/docs/python/urlfetch>`_.\n\n    Notably it will raise an :class:`AppEnginePlatformError` if:\n        * URLFetch is not available.\n        * If you attempt to use this on App Engine Flexible, as full socket\n          support is available.\n        * If a request size is more than 10 megabytes.\n        * If a response size is more than 32 megabtyes.\n        * If you use an unsupported request method such as OPTIONS.\n\n    Beyond those cases, it will raise normal urllib3 errors.\n    \"\"\"\n\n    def __init__(self, headers=None, retries=None, validate_certificate=True,\n                 urlfetch_retries=True):\n        if not urlfetch:\n            raise AppEnginePlatformError(\n                \"URLFetch is not available in this environment.\")\n\n        if is_prod_appengine_mvms():\n            raise AppEnginePlatformError(\n                \"Use normal urllib3.PoolManager instead of AppEngineManager\"\n                \"on Managed VMs, as using URLFetch is not necessary in \"\n                \"this environment.\")\n\n        warnings.warn(\n            \"urllib3 is using URLFetch on Google App Engine sandbox instead \"\n            \"of sockets. To use sockets directly instead of URLFetch see \"\n            \"https://urllib3.readthedocs.io/en/latest/reference/urllib3.contrib.html.\",\n            AppEnginePlatformWarning)\n\n        RequestMethods.__init__(self, headers)\n        self.validate_certificate = validate_certificate\n        self.urlfetch_retries = urlfetch_retries\n\n        self.retries = retries or Retry.DEFAULT\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        # Return False to re-raise any potential exceptions\n        return False\n\n    def urlopen(self, method, url, body=None, headers=None,\n                retries=None, redirect=True, timeout=Timeout.DEFAULT_TIMEOUT,\n                **response_kw):\n\n        retries = self._get_retries(retries, redirect)\n\n        try:\n            follow_redirects = (\n                    redirect and\n                    retries.redirect != 0 and\n                    retries.total)\n            response = urlfetch.fetch(\n                url,\n                payload=body,\n                method=method,\n                headers=headers or {},\n                allow_truncated=False,\n                follow_redirects=self.urlfetch_retries and follow_redirects,\n                deadline=self._get_absolute_timeout(timeout),\n                validate_certificate=self.validate_certificate,\n            )\n        except urlfetch.DeadlineExceededError as e:\n            raise TimeoutError(self, e)\n\n        except urlfetch.InvalidURLError as e:\n            if 'too large' in str(e):\n                raise AppEnginePlatformError(\n                    \"URLFetch request too large, URLFetch only \"\n                    \"supports requests up to 10mb in size.\", e)\n            raise ProtocolError(e)\n\n        except urlfetch.DownloadError as e:\n            if 'Too many redirects' in str(e):\n                raise MaxRetryError(self, url, reason=e)\n            raise ProtocolError(e)\n\n        except urlfetch.ResponseTooLargeError as e:\n            raise AppEnginePlatformError(\n                \"URLFetch response too large, URLFetch only supports\"\n                \"responses up to 32mb in size.\", e)\n\n        except urlfetch.SSLCertificateError as e:\n            raise SSLError(e)\n\n        except urlfetch.InvalidMethodError as e:\n            raise AppEnginePlatformError(\n                \"URLFetch does not support method: %s\" % method, e)\n\n        http_response = self._urlfetch_response_to_http_response(\n            response, retries=retries, **response_kw)\n\n        # Handle redirect?\n        redirect_location = redirect and http_response.get_redirect_location()\n        if redirect_location:\n            # Check for redirect response\n            if (self.urlfetch_retries and retries.raise_on_redirect):\n                raise MaxRetryError(self, url, \"too many redirects\")\n            else:\n                if http_response.status == 303:\n                    method = 'GET'\n\n                try:\n                    retries = retries.increment(method, url, response=http_response, _pool=self)\n                except MaxRetryError:\n                    if retries.raise_on_redirect:\n                        raise MaxRetryError(self, url, \"too many redirects\")\n                    return http_response\n\n                retries.sleep_for_retry(http_response)\n                log.debug(\"Redirecting %s -> %s\", url, redirect_location)\n                redirect_url = urljoin(url, redirect_location)\n                return self.urlopen(\n                    method, redirect_url, body, headers,\n                    retries=retries, redirect=redirect,\n                    timeout=timeout, **response_kw)\n\n        # Check if we should retry the HTTP response.\n        has_retry_after = bool(http_response.getheader('Retry-After'))\n        if retries.is_retry(method, http_response.status, has_retry_after):\n            retries = retries.increment(\n                method, url, response=http_response, _pool=self)\n            log.debug(\"Retry: %s\", url)\n            retries.sleep(http_response)\n            return self.urlopen(\n                method, url,\n                body=body, headers=headers,\n                retries=retries, redirect=redirect,\n                timeout=timeout, **response_kw)\n\n        return http_response\n\n    def _urlfetch_response_to_http_response(self, urlfetch_resp, **response_kw):\n\n        if is_prod_appengine():\n            # Production GAE handles deflate encoding automatically, but does\n            # not remove the encoding header.\n            content_encoding = urlfetch_resp.headers.get('content-encoding')\n\n            if content_encoding == 'deflate':\n                del urlfetch_resp.headers['content-encoding']\n\n        transfer_encoding = urlfetch_resp.headers.get('transfer-encoding')\n        # We have a full response's content,\n        # so let's make sure we don't report ourselves as chunked data.\n        if transfer_encoding == 'chunked':\n            encodings = transfer_encoding.split(\",\")\n            encodings.remove('chunked')\n            urlfetch_resp.headers['transfer-encoding'] = ','.join(encodings)\n\n        original_response = HTTPResponse(\n            # In order for decoding to work, we must present the content as\n            # a file-like object.\n            body=io.BytesIO(urlfetch_resp.content),\n            msg=urlfetch_resp.header_msg,\n            headers=urlfetch_resp.headers,\n            status=urlfetch_resp.status_code,\n            **response_kw\n        )\n\n        return HTTPResponse(\n            body=io.BytesIO(urlfetch_resp.content),\n            headers=urlfetch_resp.headers,\n            status=urlfetch_resp.status_code,\n            original_response=original_response,\n            **response_kw\n        )\n\n    def _get_absolute_timeout(self, timeout):\n        if timeout is Timeout.DEFAULT_TIMEOUT:\n            return None  # Defer to URLFetch's default.\n        if isinstance(timeout, Timeout):\n            if timeout._read is not None or timeout._connect is not None:\n                warnings.warn(\n                    \"URLFetch does not support granular timeout settings, \"\n                    \"reverting to total or default URLFetch timeout.\",\n                    AppEnginePlatformWarning)\n            return timeout.total\n        return timeout\n\n    def _get_retries(self, retries, redirect):\n        if not isinstance(retries, Retry):\n            retries = Retry.from_int(\n                retries, redirect=redirect, default=self.retries)\n\n        if retries.connect or retries.read or retries.redirect:\n            warnings.warn(\n                \"URLFetch only supports total retries and does not \"\n                \"recognize connect, read, or redirect retry parameters.\",\n                AppEnginePlatformWarning)\n\n        return retries\n\n\n# Alias methods from _appengine_environ to maintain public API interface.\n\nis_appengine = _appengine_environ.is_appengine\nis_appengine_sandbox = _appengine_environ.is_appengine_sandbox\nis_local_appengine = _appengine_environ.is_local_appengine\nis_prod_appengine = _appengine_environ.is_prod_appengine\nis_prod_appengine_mvms = _appengine_environ.is_prod_appengine_mvms\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/contrib/ntlmpool.py",
    "content": "\"\"\"\nNTLM authenticating pool, contributed by erikcederstran\n\nIssue #10, see: http://code.google.com/p/urllib3/issues/detail?id=10\n\"\"\"\nfrom __future__ import absolute_import\n\nfrom logging import getLogger\nfrom ntlm import ntlm\n\nfrom .. import HTTPSConnectionPool\nfrom ..packages.six.moves.http_client import HTTPSConnection\n\n\nlog = getLogger(__name__)\n\n\nclass NTLMConnectionPool(HTTPSConnectionPool):\n    \"\"\"\n    Implements an NTLM authentication version of an urllib3 connection pool\n    \"\"\"\n\n    scheme = 'https'\n\n    def __init__(self, user, pw, authurl, *args, **kwargs):\n        \"\"\"\n        authurl is a random URL on the server that is protected by NTLM.\n        user is the Windows user, probably in the DOMAIN\\\\username format.\n        pw is the password for the user.\n        \"\"\"\n        super(NTLMConnectionPool, self).__init__(*args, **kwargs)\n        self.authurl = authurl\n        self.rawuser = user\n        user_parts = user.split('\\\\', 1)\n        self.domain = user_parts[0].upper()\n        self.user = user_parts[1]\n        self.pw = pw\n\n    def _new_conn(self):\n        # Performs the NTLM handshake that secures the connection. The socket\n        # must be kept open while requests are performed.\n        self.num_connections += 1\n        log.debug('Starting NTLM HTTPS connection no. %d: https://%s%s',\n                  self.num_connections, self.host, self.authurl)\n\n        headers = {'Connection': 'Keep-Alive'}\n        req_header = 'Authorization'\n        resp_header = 'www-authenticate'\n\n        conn = HTTPSConnection(host=self.host, port=self.port)\n\n        # Send negotiation message\n        headers[req_header] = (\n            'NTLM %s' % ntlm.create_NTLM_NEGOTIATE_MESSAGE(self.rawuser))\n        log.debug('Request headers: %s', headers)\n        conn.request('GET', self.authurl, None, headers)\n        res = conn.getresponse()\n        reshdr = dict(res.getheaders())\n        log.debug('Response status: %s %s', res.status, res.reason)\n        log.debug('Response headers: %s', reshdr)\n        log.debug('Response data: %s [...]', res.read(100))\n\n        # Remove the reference to the socket, so that it can not be closed by\n        # the response object (we want to keep the socket open)\n        res.fp = None\n\n        # Server should respond with a challenge message\n        auth_header_values = reshdr[resp_header].split(', ')\n        auth_header_value = None\n        for s in auth_header_values:\n            if s[:5] == 'NTLM ':\n                auth_header_value = s[5:]\n        if auth_header_value is None:\n            raise Exception('Unexpected %s response header: %s' %\n                            (resp_header, reshdr[resp_header]))\n\n        # Send authentication message\n        ServerChallenge, NegotiateFlags = \\\n            ntlm.parse_NTLM_CHALLENGE_MESSAGE(auth_header_value)\n        auth_msg = ntlm.create_NTLM_AUTHENTICATE_MESSAGE(ServerChallenge,\n                                                         self.user,\n                                                         self.domain,\n                                                         self.pw,\n                                                         NegotiateFlags)\n        headers[req_header] = 'NTLM %s' % auth_msg\n        log.debug('Request headers: %s', headers)\n        conn.request('GET', self.authurl, None, headers)\n        res = conn.getresponse()\n        log.debug('Response status: %s %s', res.status, res.reason)\n        log.debug('Response headers: %s', dict(res.getheaders()))\n        log.debug('Response data: %s [...]', res.read()[:100])\n        if res.status != 200:\n            if res.status == 401:\n                raise Exception('Server rejected request: wrong '\n                                'username or password')\n            raise Exception('Wrong server response: %s %s' %\n                            (res.status, res.reason))\n\n        res.fp = None\n        log.debug('Connection established')\n        return conn\n\n    def urlopen(self, method, url, body=None, headers=None, retries=3,\n                redirect=True, assert_same_host=True):\n        if headers is None:\n            headers = {}\n        headers['Connection'] = 'Keep-Alive'\n        return super(NTLMConnectionPool, self).urlopen(method, url, body,\n                                                       headers, retries,\n                                                       redirect,\n                                                       assert_same_host)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/contrib/pyopenssl.py",
    "content": "\"\"\"\nSSL with SNI_-support for Python 2. Follow these instructions if you would\nlike to verify SSL certificates in Python 2. Note, the default libraries do\n*not* do certificate checking; you need to do additional work to validate\ncertificates yourself.\n\nThis needs the following packages installed:\n\n* pyOpenSSL (tested with 16.0.0)\n* cryptography (minimum 1.3.4, from pyopenssl)\n* idna (minimum 2.0, from cryptography)\n\nHowever, pyopenssl depends on cryptography, which depends on idna, so while we\nuse all three directly here we end up having relatively few packages required.\n\nYou can install them with the following command:\n\n    pip install pyopenssl cryptography idna\n\nTo activate certificate checking, call\n:func:`~urllib3.contrib.pyopenssl.inject_into_urllib3` from your Python code\nbefore you begin making HTTP requests. This can be done in a ``sitecustomize``\nmodule, or at any other time before your application begins using ``urllib3``,\nlike this::\n\n    try:\n        import urllib3.contrib.pyopenssl\n        urllib3.contrib.pyopenssl.inject_into_urllib3()\n    except ImportError:\n        pass\n\nNow you can use :mod:`urllib3` as you normally would, and it will support SNI\nwhen the required modules are installed.\n\nActivating this module also has the positive side effect of disabling SSL/TLS\ncompression in Python 2 (see `CRIME attack`_).\n\nIf you want to configure the default list of supported cipher suites, you can\nset the ``urllib3.contrib.pyopenssl.DEFAULT_SSL_CIPHER_LIST`` variable.\n\n.. _sni: https://en.wikipedia.org/wiki/Server_Name_Indication\n.. _crime attack: https://en.wikipedia.org/wiki/CRIME_(security_exploit)\n\"\"\"\nfrom __future__ import absolute_import\n\nimport OpenSSL.SSL\nfrom cryptography import x509\nfrom cryptography.hazmat.backends.openssl import backend as openssl_backend\nfrom cryptography.hazmat.backends.openssl.x509 import _Certificate\ntry:\n    from cryptography.x509 import UnsupportedExtension\nexcept ImportError:\n    # UnsupportedExtension is gone in cryptography >= 2.1.0\n    class UnsupportedExtension(Exception):\n        pass\n\nfrom socket import timeout, error as SocketError\nfrom io import BytesIO\n\ntry:  # Platform-specific: Python 2\n    from socket import _fileobject\nexcept ImportError:  # Platform-specific: Python 3\n    _fileobject = None\n    from ..packages.backports.makefile import backport_makefile\n\nimport logging\nimport ssl\nfrom ..packages import six\nimport sys\n\nfrom .. import util\n\n__all__ = ['inject_into_urllib3', 'extract_from_urllib3']\n\n# SNI always works.\nHAS_SNI = True\n\n# Map from urllib3 to PyOpenSSL compatible parameter-values.\n_openssl_versions = {\n    ssl.PROTOCOL_SSLv23: OpenSSL.SSL.SSLv23_METHOD,\n    ssl.PROTOCOL_TLSv1: OpenSSL.SSL.TLSv1_METHOD,\n}\n\nif hasattr(ssl, 'PROTOCOL_TLSv1_1') and hasattr(OpenSSL.SSL, 'TLSv1_1_METHOD'):\n    _openssl_versions[ssl.PROTOCOL_TLSv1_1] = OpenSSL.SSL.TLSv1_1_METHOD\n\nif hasattr(ssl, 'PROTOCOL_TLSv1_2') and hasattr(OpenSSL.SSL, 'TLSv1_2_METHOD'):\n    _openssl_versions[ssl.PROTOCOL_TLSv1_2] = OpenSSL.SSL.TLSv1_2_METHOD\n\ntry:\n    _openssl_versions.update({ssl.PROTOCOL_SSLv3: OpenSSL.SSL.SSLv3_METHOD})\nexcept AttributeError:\n    pass\n\n_stdlib_to_openssl_verify = {\n    ssl.CERT_NONE: OpenSSL.SSL.VERIFY_NONE,\n    ssl.CERT_OPTIONAL: OpenSSL.SSL.VERIFY_PEER,\n    ssl.CERT_REQUIRED:\n        OpenSSL.SSL.VERIFY_PEER + OpenSSL.SSL.VERIFY_FAIL_IF_NO_PEER_CERT,\n}\n_openssl_to_stdlib_verify = dict(\n    (v, k) for k, v in _stdlib_to_openssl_verify.items()\n)\n\n# OpenSSL will only write 16K at a time\nSSL_WRITE_BLOCKSIZE = 16384\n\norig_util_HAS_SNI = util.HAS_SNI\norig_util_SSLContext = util.ssl_.SSLContext\n\n\nlog = logging.getLogger(__name__)\n\n\ndef inject_into_urllib3():\n    'Monkey-patch urllib3 with PyOpenSSL-backed SSL-support.'\n\n    _validate_dependencies_met()\n\n    util.ssl_.SSLContext = PyOpenSSLContext\n    util.HAS_SNI = HAS_SNI\n    util.ssl_.HAS_SNI = HAS_SNI\n    util.IS_PYOPENSSL = True\n    util.ssl_.IS_PYOPENSSL = True\n\n\ndef extract_from_urllib3():\n    'Undo monkey-patching by :func:`inject_into_urllib3`.'\n\n    util.ssl_.SSLContext = orig_util_SSLContext\n    util.HAS_SNI = orig_util_HAS_SNI\n    util.ssl_.HAS_SNI = orig_util_HAS_SNI\n    util.IS_PYOPENSSL = False\n    util.ssl_.IS_PYOPENSSL = False\n\n\ndef _validate_dependencies_met():\n    \"\"\"\n    Verifies that PyOpenSSL's package-level dependencies have been met.\n    Throws `ImportError` if they are not met.\n    \"\"\"\n    # Method added in `cryptography==1.1`; not available in older versions\n    from cryptography.x509.extensions import Extensions\n    if getattr(Extensions, \"get_extension_for_class\", None) is None:\n        raise ImportError(\"'cryptography' module missing required functionality.  \"\n                          \"Try upgrading to v1.3.4 or newer.\")\n\n    # pyOpenSSL 0.14 and above use cryptography for OpenSSL bindings. The _x509\n    # attribute is only present on those versions.\n    from OpenSSL.crypto import X509\n    x509 = X509()\n    if getattr(x509, \"_x509\", None) is None:\n        raise ImportError(\"'pyOpenSSL' module missing required functionality. \"\n                          \"Try upgrading to v0.14 or newer.\")\n\n\ndef _dnsname_to_stdlib(name):\n    \"\"\"\n    Converts a dNSName SubjectAlternativeName field to the form used by the\n    standard library on the given Python version.\n\n    Cryptography produces a dNSName as a unicode string that was idna-decoded\n    from ASCII bytes. We need to idna-encode that string to get it back, and\n    then on Python 3 we also need to convert to unicode via UTF-8 (the stdlib\n    uses PyUnicode_FromStringAndSize on it, which decodes via UTF-8).\n\n    If the name cannot be idna-encoded then we return None signalling that\n    the name given should be skipped.\n    \"\"\"\n    def idna_encode(name):\n        \"\"\"\n        Borrowed wholesale from the Python Cryptography Project. It turns out\n        that we can't just safely call `idna.encode`: it can explode for\n        wildcard names. This avoids that problem.\n        \"\"\"\n        from pip._vendor import idna\n\n        try:\n            for prefix in [u'*.', u'.']:\n                if name.startswith(prefix):\n                    name = name[len(prefix):]\n                    return prefix.encode('ascii') + idna.encode(name)\n            return idna.encode(name)\n        except idna.core.IDNAError:\n            return None\n\n    name = idna_encode(name)\n    if name is None:\n        return None\n    elif sys.version_info >= (3, 0):\n        name = name.decode('utf-8')\n    return name\n\n\ndef get_subj_alt_name(peer_cert):\n    \"\"\"\n    Given an PyOpenSSL certificate, provides all the subject alternative names.\n    \"\"\"\n    # Pass the cert to cryptography, which has much better APIs for this.\n    if hasattr(peer_cert, \"to_cryptography\"):\n        cert = peer_cert.to_cryptography()\n    else:\n        # This is technically using private APIs, but should work across all\n        # relevant versions before PyOpenSSL got a proper API for this.\n        cert = _Certificate(openssl_backend, peer_cert._x509)\n\n    # We want to find the SAN extension. Ask Cryptography to locate it (it's\n    # faster than looping in Python)\n    try:\n        ext = cert.extensions.get_extension_for_class(\n            x509.SubjectAlternativeName\n        ).value\n    except x509.ExtensionNotFound:\n        # No such extension, return the empty list.\n        return []\n    except (x509.DuplicateExtension, UnsupportedExtension,\n            x509.UnsupportedGeneralNameType, UnicodeError) as e:\n        # A problem has been found with the quality of the certificate. Assume\n        # no SAN field is present.\n        log.warning(\n            \"A problem was encountered with the certificate that prevented \"\n            \"urllib3 from finding the SubjectAlternativeName field. This can \"\n            \"affect certificate validation. The error was %s\",\n            e,\n        )\n        return []\n\n    # We want to return dNSName and iPAddress fields. We need to cast the IPs\n    # back to strings because the match_hostname function wants them as\n    # strings.\n    # Sadly the DNS names need to be idna encoded and then, on Python 3, UTF-8\n    # decoded. This is pretty frustrating, but that's what the standard library\n    # does with certificates, and so we need to attempt to do the same.\n    # We also want to skip over names which cannot be idna encoded.\n    names = [\n        ('DNS', name) for name in map(_dnsname_to_stdlib, ext.get_values_for_type(x509.DNSName))\n        if name is not None\n    ]\n    names.extend(\n        ('IP Address', str(name))\n        for name in ext.get_values_for_type(x509.IPAddress)\n    )\n\n    return names\n\n\nclass WrappedSocket(object):\n    '''API-compatibility wrapper for Python OpenSSL's Connection-class.\n\n    Note: _makefile_refs, _drop() and _reuse() are needed for the garbage\n    collector of pypy.\n    '''\n\n    def __init__(self, connection, socket, suppress_ragged_eofs=True):\n        self.connection = connection\n        self.socket = socket\n        self.suppress_ragged_eofs = suppress_ragged_eofs\n        self._makefile_refs = 0\n        self._closed = False\n\n    def fileno(self):\n        return self.socket.fileno()\n\n    # Copy-pasted from Python 3.5 source code\n    def _decref_socketios(self):\n        if self._makefile_refs > 0:\n            self._makefile_refs -= 1\n        if self._closed:\n            self.close()\n\n    def recv(self, *args, **kwargs):\n        try:\n            data = self.connection.recv(*args, **kwargs)\n        except OpenSSL.SSL.SysCallError as e:\n            if self.suppress_ragged_eofs and e.args == (-1, 'Unexpected EOF'):\n                return b''\n            else:\n                raise SocketError(str(e))\n        except OpenSSL.SSL.ZeroReturnError as e:\n            if self.connection.get_shutdown() == OpenSSL.SSL.RECEIVED_SHUTDOWN:\n                return b''\n            else:\n                raise\n        except OpenSSL.SSL.WantReadError:\n            if not util.wait_for_read(self.socket, self.socket.gettimeout()):\n                raise timeout('The read operation timed out')\n            else:\n                return self.recv(*args, **kwargs)\n        else:\n            return data\n\n    def recv_into(self, *args, **kwargs):\n        try:\n            return self.connection.recv_into(*args, **kwargs)\n        except OpenSSL.SSL.SysCallError as e:\n            if self.suppress_ragged_eofs and e.args == (-1, 'Unexpected EOF'):\n                return 0\n            else:\n                raise SocketError(str(e))\n        except OpenSSL.SSL.ZeroReturnError as e:\n            if self.connection.get_shutdown() == OpenSSL.SSL.RECEIVED_SHUTDOWN:\n                return 0\n            else:\n                raise\n        except OpenSSL.SSL.WantReadError:\n            if not util.wait_for_read(self.socket, self.socket.gettimeout()):\n                raise timeout('The read operation timed out')\n            else:\n                return self.recv_into(*args, **kwargs)\n\n    def settimeout(self, timeout):\n        return self.socket.settimeout(timeout)\n\n    def _send_until_done(self, data):\n        while True:\n            try:\n                return self.connection.send(data)\n            except OpenSSL.SSL.WantWriteError:\n                if not util.wait_for_write(self.socket, self.socket.gettimeout()):\n                    raise timeout()\n                continue\n            except OpenSSL.SSL.SysCallError as e:\n                raise SocketError(str(e))\n\n    def sendall(self, data):\n        total_sent = 0\n        while total_sent < len(data):\n            sent = self._send_until_done(data[total_sent:total_sent + SSL_WRITE_BLOCKSIZE])\n            total_sent += sent\n\n    def shutdown(self):\n        # FIXME rethrow compatible exceptions should we ever use this\n        self.connection.shutdown()\n\n    def close(self):\n        if self._makefile_refs < 1:\n            try:\n                self._closed = True\n                return self.connection.close()\n            except OpenSSL.SSL.Error:\n                return\n        else:\n            self._makefile_refs -= 1\n\n    def getpeercert(self, binary_form=False):\n        x509 = self.connection.get_peer_certificate()\n\n        if not x509:\n            return x509\n\n        if binary_form:\n            return OpenSSL.crypto.dump_certificate(\n                OpenSSL.crypto.FILETYPE_ASN1,\n                x509)\n\n        return {\n            'subject': (\n                (('commonName', x509.get_subject().CN),),\n            ),\n            'subjectAltName': get_subj_alt_name(x509)\n        }\n\n    def _reuse(self):\n        self._makefile_refs += 1\n\n    def _drop(self):\n        if self._makefile_refs < 1:\n            self.close()\n        else:\n            self._makefile_refs -= 1\n\n\nif _fileobject:  # Platform-specific: Python 2\n    def makefile(self, mode, bufsize=-1):\n        self._makefile_refs += 1\n        return _fileobject(self, mode, bufsize, close=True)\nelse:  # Platform-specific: Python 3\n    makefile = backport_makefile\n\nWrappedSocket.makefile = makefile\n\n\nclass PyOpenSSLContext(object):\n    \"\"\"\n    I am a wrapper class for the PyOpenSSL ``Context`` object. I am responsible\n    for translating the interface of the standard library ``SSLContext`` object\n    to calls into PyOpenSSL.\n    \"\"\"\n    def __init__(self, protocol):\n        self.protocol = _openssl_versions[protocol]\n        self._ctx = OpenSSL.SSL.Context(self.protocol)\n        self._options = 0\n        self.check_hostname = False\n\n    @property\n    def options(self):\n        return self._options\n\n    @options.setter\n    def options(self, value):\n        self._options = value\n        self._ctx.set_options(value)\n\n    @property\n    def verify_mode(self):\n        return _openssl_to_stdlib_verify[self._ctx.get_verify_mode()]\n\n    @verify_mode.setter\n    def verify_mode(self, value):\n        self._ctx.set_verify(\n            _stdlib_to_openssl_verify[value],\n            _verify_callback\n        )\n\n    def set_default_verify_paths(self):\n        self._ctx.set_default_verify_paths()\n\n    def set_ciphers(self, ciphers):\n        if isinstance(ciphers, six.text_type):\n            ciphers = ciphers.encode('utf-8')\n        self._ctx.set_cipher_list(ciphers)\n\n    def load_verify_locations(self, cafile=None, capath=None, cadata=None):\n        if cafile is not None:\n            cafile = cafile.encode('utf-8')\n        if capath is not None:\n            capath = capath.encode('utf-8')\n        self._ctx.load_verify_locations(cafile, capath)\n        if cadata is not None:\n            self._ctx.load_verify_locations(BytesIO(cadata))\n\n    def load_cert_chain(self, certfile, keyfile=None, password=None):\n        self._ctx.use_certificate_chain_file(certfile)\n        if password is not None:\n            self._ctx.set_passwd_cb(lambda max_length, prompt_twice, userdata: password)\n        self._ctx.use_privatekey_file(keyfile or certfile)\n\n    def wrap_socket(self, sock, server_side=False,\n                    do_handshake_on_connect=True, suppress_ragged_eofs=True,\n                    server_hostname=None):\n        cnx = OpenSSL.SSL.Connection(self._ctx, sock)\n\n        if isinstance(server_hostname, six.text_type):  # Platform-specific: Python 3\n            server_hostname = server_hostname.encode('utf-8')\n\n        if server_hostname is not None:\n            cnx.set_tlsext_host_name(server_hostname)\n\n        cnx.set_connect_state()\n\n        while True:\n            try:\n                cnx.do_handshake()\n            except OpenSSL.SSL.WantReadError:\n                if not util.wait_for_read(sock, sock.gettimeout()):\n                    raise timeout('select timed out')\n                continue\n            except OpenSSL.SSL.Error as e:\n                raise ssl.SSLError('bad handshake: %r' % e)\n            break\n\n        return WrappedSocket(cnx, sock)\n\n\ndef _verify_callback(cnx, x509, err_no, err_depth, return_code):\n    return err_no == 0\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/contrib/securetransport.py",
    "content": "\"\"\"\nSecureTranport support for urllib3 via ctypes.\n\nThis makes platform-native TLS available to urllib3 users on macOS without the\nuse of a compiler. This is an important feature because the Python Package\nIndex is moving to become a TLSv1.2-or-higher server, and the default OpenSSL\nthat ships with macOS is not capable of doing TLSv1.2. The only way to resolve\nthis is to give macOS users an alternative solution to the problem, and that\nsolution is to use SecureTransport.\n\nWe use ctypes here because this solution must not require a compiler. That's\nbecause pip is not allowed to require a compiler either.\n\nThis is not intended to be a seriously long-term solution to this problem.\nThe hope is that PEP 543 will eventually solve this issue for us, at which\npoint we can retire this contrib module. But in the short term, we need to\nsolve the impending tire fire that is Python on Mac without this kind of\ncontrib module. So...here we are.\n\nTo use this module, simply import and inject it::\n\n    import urllib3.contrib.securetransport\n    urllib3.contrib.securetransport.inject_into_urllib3()\n\nHappy TLSing!\n\"\"\"\nfrom __future__ import absolute_import\n\nimport contextlib\nimport ctypes\nimport errno\nimport os.path\nimport shutil\nimport socket\nimport ssl\nimport threading\nimport weakref\n\nfrom .. import util\nfrom ._securetransport.bindings import (\n    Security, SecurityConst, CoreFoundation\n)\nfrom ._securetransport.low_level import (\n    _assert_no_error, _cert_array_from_pem, _temporary_keychain,\n    _load_client_cert_chain\n)\n\ntry:  # Platform-specific: Python 2\n    from socket import _fileobject\nexcept ImportError:  # Platform-specific: Python 3\n    _fileobject = None\n    from ..packages.backports.makefile import backport_makefile\n\n__all__ = ['inject_into_urllib3', 'extract_from_urllib3']\n\n# SNI always works\nHAS_SNI = True\n\norig_util_HAS_SNI = util.HAS_SNI\norig_util_SSLContext = util.ssl_.SSLContext\n\n# This dictionary is used by the read callback to obtain a handle to the\n# calling wrapped socket. This is a pretty silly approach, but for now it'll\n# do. I feel like I should be able to smuggle a handle to the wrapped socket\n# directly in the SSLConnectionRef, but for now this approach will work I\n# guess.\n#\n# We need to lock around this structure for inserts, but we don't do it for\n# reads/writes in the callbacks. The reasoning here goes as follows:\n#\n#    1. It is not possible to call into the callbacks before the dictionary is\n#       populated, so once in the callback the id must be in the dictionary.\n#    2. The callbacks don't mutate the dictionary, they only read from it, and\n#       so cannot conflict with any of the insertions.\n#\n# This is good: if we had to lock in the callbacks we'd drastically slow down\n# the performance of this code.\n_connection_refs = weakref.WeakValueDictionary()\n_connection_ref_lock = threading.Lock()\n\n# Limit writes to 16kB. This is OpenSSL's limit, but we'll cargo-cult it over\n# for no better reason than we need *a* limit, and this one is right there.\nSSL_WRITE_BLOCKSIZE = 16384\n\n# This is our equivalent of util.ssl_.DEFAULT_CIPHERS, but expanded out to\n# individual cipher suites. We need to do this because this is how\n# SecureTransport wants them.\nCIPHER_SUITES = [\n    SecurityConst.TLS_AES_256_GCM_SHA384,\n    SecurityConst.TLS_CHACHA20_POLY1305_SHA256,\n    SecurityConst.TLS_AES_128_GCM_SHA256,\n    SecurityConst.TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384,\n    SecurityConst.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384,\n    SecurityConst.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,\n    SecurityConst.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256,\n    SecurityConst.TLS_DHE_DSS_WITH_AES_256_GCM_SHA384,\n    SecurityConst.TLS_DHE_RSA_WITH_AES_256_GCM_SHA384,\n    SecurityConst.TLS_DHE_DSS_WITH_AES_128_GCM_SHA256,\n    SecurityConst.TLS_DHE_RSA_WITH_AES_128_GCM_SHA256,\n    SecurityConst.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384,\n    SecurityConst.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384,\n    SecurityConst.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA,\n    SecurityConst.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA,\n    SecurityConst.TLS_DHE_RSA_WITH_AES_256_CBC_SHA256,\n    SecurityConst.TLS_DHE_DSS_WITH_AES_256_CBC_SHA256,\n    SecurityConst.TLS_DHE_RSA_WITH_AES_256_CBC_SHA,\n    SecurityConst.TLS_DHE_DSS_WITH_AES_256_CBC_SHA,\n    SecurityConst.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256,\n    SecurityConst.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256,\n    SecurityConst.TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,\n    SecurityConst.TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA,\n    SecurityConst.TLS_DHE_RSA_WITH_AES_128_CBC_SHA256,\n    SecurityConst.TLS_DHE_DSS_WITH_AES_128_CBC_SHA256,\n    SecurityConst.TLS_DHE_RSA_WITH_AES_128_CBC_SHA,\n    SecurityConst.TLS_DHE_DSS_WITH_AES_128_CBC_SHA,\n    SecurityConst.TLS_RSA_WITH_AES_256_GCM_SHA384,\n    SecurityConst.TLS_RSA_WITH_AES_128_GCM_SHA256,\n    SecurityConst.TLS_RSA_WITH_AES_256_CBC_SHA256,\n    SecurityConst.TLS_RSA_WITH_AES_128_CBC_SHA256,\n    SecurityConst.TLS_RSA_WITH_AES_256_CBC_SHA,\n    SecurityConst.TLS_RSA_WITH_AES_128_CBC_SHA,\n]\n\n# Basically this is simple: for PROTOCOL_SSLv23 we turn it into a low of\n# TLSv1 and a high of TLSv1.2. For everything else, we pin to that version.\n_protocol_to_min_max = {\n    ssl.PROTOCOL_SSLv23: (SecurityConst.kTLSProtocol1, SecurityConst.kTLSProtocol12),\n}\n\nif hasattr(ssl, \"PROTOCOL_SSLv2\"):\n    _protocol_to_min_max[ssl.PROTOCOL_SSLv2] = (\n        SecurityConst.kSSLProtocol2, SecurityConst.kSSLProtocol2\n    )\nif hasattr(ssl, \"PROTOCOL_SSLv3\"):\n    _protocol_to_min_max[ssl.PROTOCOL_SSLv3] = (\n        SecurityConst.kSSLProtocol3, SecurityConst.kSSLProtocol3\n    )\nif hasattr(ssl, \"PROTOCOL_TLSv1\"):\n    _protocol_to_min_max[ssl.PROTOCOL_TLSv1] = (\n        SecurityConst.kTLSProtocol1, SecurityConst.kTLSProtocol1\n    )\nif hasattr(ssl, \"PROTOCOL_TLSv1_1\"):\n    _protocol_to_min_max[ssl.PROTOCOL_TLSv1_1] = (\n        SecurityConst.kTLSProtocol11, SecurityConst.kTLSProtocol11\n    )\nif hasattr(ssl, \"PROTOCOL_TLSv1_2\"):\n    _protocol_to_min_max[ssl.PROTOCOL_TLSv1_2] = (\n        SecurityConst.kTLSProtocol12, SecurityConst.kTLSProtocol12\n    )\nif hasattr(ssl, \"PROTOCOL_TLS\"):\n    _protocol_to_min_max[ssl.PROTOCOL_TLS] = _protocol_to_min_max[ssl.PROTOCOL_SSLv23]\n\n\ndef inject_into_urllib3():\n    \"\"\"\n    Monkey-patch urllib3 with SecureTransport-backed SSL-support.\n    \"\"\"\n    util.ssl_.SSLContext = SecureTransportContext\n    util.HAS_SNI = HAS_SNI\n    util.ssl_.HAS_SNI = HAS_SNI\n    util.IS_SECURETRANSPORT = True\n    util.ssl_.IS_SECURETRANSPORT = True\n\n\ndef extract_from_urllib3():\n    \"\"\"\n    Undo monkey-patching by :func:`inject_into_urllib3`.\n    \"\"\"\n    util.ssl_.SSLContext = orig_util_SSLContext\n    util.HAS_SNI = orig_util_HAS_SNI\n    util.ssl_.HAS_SNI = orig_util_HAS_SNI\n    util.IS_SECURETRANSPORT = False\n    util.ssl_.IS_SECURETRANSPORT = False\n\n\ndef _read_callback(connection_id, data_buffer, data_length_pointer):\n    \"\"\"\n    SecureTransport read callback. This is called by ST to request that data\n    be returned from the socket.\n    \"\"\"\n    wrapped_socket = None\n    try:\n        wrapped_socket = _connection_refs.get(connection_id)\n        if wrapped_socket is None:\n            return SecurityConst.errSSLInternal\n        base_socket = wrapped_socket.socket\n\n        requested_length = data_length_pointer[0]\n\n        timeout = wrapped_socket.gettimeout()\n        error = None\n        read_count = 0\n\n        try:\n            while read_count < requested_length:\n                if timeout is None or timeout >= 0:\n                    if not util.wait_for_read(base_socket, timeout):\n                        raise socket.error(errno.EAGAIN, 'timed out')\n\n                remaining = requested_length - read_count\n                buffer = (ctypes.c_char * remaining).from_address(\n                    data_buffer + read_count\n                )\n                chunk_size = base_socket.recv_into(buffer, remaining)\n                read_count += chunk_size\n                if not chunk_size:\n                    if not read_count:\n                        return SecurityConst.errSSLClosedGraceful\n                    break\n        except (socket.error) as e:\n            error = e.errno\n\n            if error is not None and error != errno.EAGAIN:\n                data_length_pointer[0] = read_count\n                if error == errno.ECONNRESET or error == errno.EPIPE:\n                    return SecurityConst.errSSLClosedAbort\n                raise\n\n        data_length_pointer[0] = read_count\n\n        if read_count != requested_length:\n            return SecurityConst.errSSLWouldBlock\n\n        return 0\n    except Exception as e:\n        if wrapped_socket is not None:\n            wrapped_socket._exception = e\n        return SecurityConst.errSSLInternal\n\n\ndef _write_callback(connection_id, data_buffer, data_length_pointer):\n    \"\"\"\n    SecureTransport write callback. This is called by ST to request that data\n    actually be sent on the network.\n    \"\"\"\n    wrapped_socket = None\n    try:\n        wrapped_socket = _connection_refs.get(connection_id)\n        if wrapped_socket is None:\n            return SecurityConst.errSSLInternal\n        base_socket = wrapped_socket.socket\n\n        bytes_to_write = data_length_pointer[0]\n        data = ctypes.string_at(data_buffer, bytes_to_write)\n\n        timeout = wrapped_socket.gettimeout()\n        error = None\n        sent = 0\n\n        try:\n            while sent < bytes_to_write:\n                if timeout is None or timeout >= 0:\n                    if not util.wait_for_write(base_socket, timeout):\n                        raise socket.error(errno.EAGAIN, 'timed out')\n                chunk_sent = base_socket.send(data)\n                sent += chunk_sent\n\n                # This has some needless copying here, but I'm not sure there's\n                # much value in optimising this data path.\n                data = data[chunk_sent:]\n        except (socket.error) as e:\n            error = e.errno\n\n            if error is not None and error != errno.EAGAIN:\n                data_length_pointer[0] = sent\n                if error == errno.ECONNRESET or error == errno.EPIPE:\n                    return SecurityConst.errSSLClosedAbort\n                raise\n\n        data_length_pointer[0] = sent\n\n        if sent != bytes_to_write:\n            return SecurityConst.errSSLWouldBlock\n\n        return 0\n    except Exception as e:\n        if wrapped_socket is not None:\n            wrapped_socket._exception = e\n        return SecurityConst.errSSLInternal\n\n\n# We need to keep these two objects references alive: if they get GC'd while\n# in use then SecureTransport could attempt to call a function that is in freed\n# memory. That would be...uh...bad. Yeah, that's the word. Bad.\n_read_callback_pointer = Security.SSLReadFunc(_read_callback)\n_write_callback_pointer = Security.SSLWriteFunc(_write_callback)\n\n\nclass WrappedSocket(object):\n    \"\"\"\n    API-compatibility wrapper for Python's OpenSSL wrapped socket object.\n\n    Note: _makefile_refs, _drop(), and _reuse() are needed for the garbage\n    collector of PyPy.\n    \"\"\"\n    def __init__(self, socket):\n        self.socket = socket\n        self.context = None\n        self._makefile_refs = 0\n        self._closed = False\n        self._exception = None\n        self._keychain = None\n        self._keychain_dir = None\n        self._client_cert_chain = None\n\n        # We save off the previously-configured timeout and then set it to\n        # zero. This is done because we use select and friends to handle the\n        # timeouts, but if we leave the timeout set on the lower socket then\n        # Python will \"kindly\" call select on that socket again for us. Avoid\n        # that by forcing the timeout to zero.\n        self._timeout = self.socket.gettimeout()\n        self.socket.settimeout(0)\n\n    @contextlib.contextmanager\n    def _raise_on_error(self):\n        \"\"\"\n        A context manager that can be used to wrap calls that do I/O from\n        SecureTransport. If any of the I/O callbacks hit an exception, this\n        context manager will correctly propagate the exception after the fact.\n        This avoids silently swallowing those exceptions.\n\n        It also correctly forces the socket closed.\n        \"\"\"\n        self._exception = None\n\n        # We explicitly don't catch around this yield because in the unlikely\n        # event that an exception was hit in the block we don't want to swallow\n        # it.\n        yield\n        if self._exception is not None:\n            exception, self._exception = self._exception, None\n            self.close()\n            raise exception\n\n    def _set_ciphers(self):\n        \"\"\"\n        Sets up the allowed ciphers. By default this matches the set in\n        util.ssl_.DEFAULT_CIPHERS, at least as supported by macOS. This is done\n        custom and doesn't allow changing at this time, mostly because parsing\n        OpenSSL cipher strings is going to be a freaking nightmare.\n        \"\"\"\n        ciphers = (Security.SSLCipherSuite * len(CIPHER_SUITES))(*CIPHER_SUITES)\n        result = Security.SSLSetEnabledCiphers(\n            self.context, ciphers, len(CIPHER_SUITES)\n        )\n        _assert_no_error(result)\n\n    def _custom_validate(self, verify, trust_bundle):\n        \"\"\"\n        Called when we have set custom validation. We do this in two cases:\n        first, when cert validation is entirely disabled; and second, when\n        using a custom trust DB.\n        \"\"\"\n        # If we disabled cert validation, just say: cool.\n        if not verify:\n            return\n\n        # We want data in memory, so load it up.\n        if os.path.isfile(trust_bundle):\n            with open(trust_bundle, 'rb') as f:\n                trust_bundle = f.read()\n\n        cert_array = None\n        trust = Security.SecTrustRef()\n\n        try:\n            # Get a CFArray that contains the certs we want.\n            cert_array = _cert_array_from_pem(trust_bundle)\n\n            # Ok, now the hard part. We want to get the SecTrustRef that ST has\n            # created for this connection, shove our CAs into it, tell ST to\n            # ignore everything else it knows, and then ask if it can build a\n            # chain. This is a buuuunch of code.\n            result = Security.SSLCopyPeerTrust(\n                self.context, ctypes.byref(trust)\n            )\n            _assert_no_error(result)\n            if not trust:\n                raise ssl.SSLError(\"Failed to copy trust reference\")\n\n            result = Security.SecTrustSetAnchorCertificates(trust, cert_array)\n            _assert_no_error(result)\n\n            result = Security.SecTrustSetAnchorCertificatesOnly(trust, True)\n            _assert_no_error(result)\n\n            trust_result = Security.SecTrustResultType()\n            result = Security.SecTrustEvaluate(\n                trust, ctypes.byref(trust_result)\n            )\n            _assert_no_error(result)\n        finally:\n            if trust:\n                CoreFoundation.CFRelease(trust)\n\n            if cert_array is not None:\n                CoreFoundation.CFRelease(cert_array)\n\n        # Ok, now we can look at what the result was.\n        successes = (\n            SecurityConst.kSecTrustResultUnspecified,\n            SecurityConst.kSecTrustResultProceed\n        )\n        if trust_result.value not in successes:\n            raise ssl.SSLError(\n                \"certificate verify failed, error code: %d\" %\n                trust_result.value\n            )\n\n    def handshake(self,\n                  server_hostname,\n                  verify,\n                  trust_bundle,\n                  min_version,\n                  max_version,\n                  client_cert,\n                  client_key,\n                  client_key_passphrase):\n        \"\"\"\n        Actually performs the TLS handshake. This is run automatically by\n        wrapped socket, and shouldn't be needed in user code.\n        \"\"\"\n        # First, we do the initial bits of connection setup. We need to create\n        # a context, set its I/O funcs, and set the connection reference.\n        self.context = Security.SSLCreateContext(\n            None, SecurityConst.kSSLClientSide, SecurityConst.kSSLStreamType\n        )\n        result = Security.SSLSetIOFuncs(\n            self.context, _read_callback_pointer, _write_callback_pointer\n        )\n        _assert_no_error(result)\n\n        # Here we need to compute the handle to use. We do this by taking the\n        # id of self modulo 2**31 - 1. If this is already in the dictionary, we\n        # just keep incrementing by one until we find a free space.\n        with _connection_ref_lock:\n            handle = id(self) % 2147483647\n            while handle in _connection_refs:\n                handle = (handle + 1) % 2147483647\n            _connection_refs[handle] = self\n\n        result = Security.SSLSetConnection(self.context, handle)\n        _assert_no_error(result)\n\n        # If we have a server hostname, we should set that too.\n        if server_hostname:\n            if not isinstance(server_hostname, bytes):\n                server_hostname = server_hostname.encode('utf-8')\n\n            result = Security.SSLSetPeerDomainName(\n                self.context, server_hostname, len(server_hostname)\n            )\n            _assert_no_error(result)\n\n        # Setup the ciphers.\n        self._set_ciphers()\n\n        # Set the minimum and maximum TLS versions.\n        result = Security.SSLSetProtocolVersionMin(self.context, min_version)\n        _assert_no_error(result)\n        result = Security.SSLSetProtocolVersionMax(self.context, max_version)\n        _assert_no_error(result)\n\n        # If there's a trust DB, we need to use it. We do that by telling\n        # SecureTransport to break on server auth. We also do that if we don't\n        # want to validate the certs at all: we just won't actually do any\n        # authing in that case.\n        if not verify or trust_bundle is not None:\n            result = Security.SSLSetSessionOption(\n                self.context,\n                SecurityConst.kSSLSessionOptionBreakOnServerAuth,\n                True\n            )\n            _assert_no_error(result)\n\n        # If there's a client cert, we need to use it.\n        if client_cert:\n            self._keychain, self._keychain_dir = _temporary_keychain()\n            self._client_cert_chain = _load_client_cert_chain(\n                self._keychain, client_cert, client_key\n            )\n            result = Security.SSLSetCertificate(\n                self.context, self._client_cert_chain\n            )\n            _assert_no_error(result)\n\n        while True:\n            with self._raise_on_error():\n                result = Security.SSLHandshake(self.context)\n\n                if result == SecurityConst.errSSLWouldBlock:\n                    raise socket.timeout(\"handshake timed out\")\n                elif result == SecurityConst.errSSLServerAuthCompleted:\n                    self._custom_validate(verify, trust_bundle)\n                    continue\n                else:\n                    _assert_no_error(result)\n                    break\n\n    def fileno(self):\n        return self.socket.fileno()\n\n    # Copy-pasted from Python 3.5 source code\n    def _decref_socketios(self):\n        if self._makefile_refs > 0:\n            self._makefile_refs -= 1\n        if self._closed:\n            self.close()\n\n    def recv(self, bufsiz):\n        buffer = ctypes.create_string_buffer(bufsiz)\n        bytes_read = self.recv_into(buffer, bufsiz)\n        data = buffer[:bytes_read]\n        return data\n\n    def recv_into(self, buffer, nbytes=None):\n        # Read short on EOF.\n        if self._closed:\n            return 0\n\n        if nbytes is None:\n            nbytes = len(buffer)\n\n        buffer = (ctypes.c_char * nbytes).from_buffer(buffer)\n        processed_bytes = ctypes.c_size_t(0)\n\n        with self._raise_on_error():\n            result = Security.SSLRead(\n                self.context, buffer, nbytes, ctypes.byref(processed_bytes)\n            )\n\n        # There are some result codes that we want to treat as \"not always\n        # errors\". Specifically, those are errSSLWouldBlock,\n        # errSSLClosedGraceful, and errSSLClosedNoNotify.\n        if (result == SecurityConst.errSSLWouldBlock):\n            # If we didn't process any bytes, then this was just a time out.\n            # However, we can get errSSLWouldBlock in situations when we *did*\n            # read some data, and in those cases we should just read \"short\"\n            # and return.\n            if processed_bytes.value == 0:\n                # Timed out, no data read.\n                raise socket.timeout(\"recv timed out\")\n        elif result in (SecurityConst.errSSLClosedGraceful, SecurityConst.errSSLClosedNoNotify):\n            # The remote peer has closed this connection. We should do so as\n            # well. Note that we don't actually return here because in\n            # principle this could actually be fired along with return data.\n            # It's unlikely though.\n            self.close()\n        else:\n            _assert_no_error(result)\n\n        # Ok, we read and probably succeeded. We should return whatever data\n        # was actually read.\n        return processed_bytes.value\n\n    def settimeout(self, timeout):\n        self._timeout = timeout\n\n    def gettimeout(self):\n        return self._timeout\n\n    def send(self, data):\n        processed_bytes = ctypes.c_size_t(0)\n\n        with self._raise_on_error():\n            result = Security.SSLWrite(\n                self.context, data, len(data), ctypes.byref(processed_bytes)\n            )\n\n        if result == SecurityConst.errSSLWouldBlock and processed_bytes.value == 0:\n            # Timed out\n            raise socket.timeout(\"send timed out\")\n        else:\n            _assert_no_error(result)\n\n        # We sent, and probably succeeded. Tell them how much we sent.\n        return processed_bytes.value\n\n    def sendall(self, data):\n        total_sent = 0\n        while total_sent < len(data):\n            sent = self.send(data[total_sent:total_sent + SSL_WRITE_BLOCKSIZE])\n            total_sent += sent\n\n    def shutdown(self):\n        with self._raise_on_error():\n            Security.SSLClose(self.context)\n\n    def close(self):\n        # TODO: should I do clean shutdown here? Do I have to?\n        if self._makefile_refs < 1:\n            self._closed = True\n            if self.context:\n                CoreFoundation.CFRelease(self.context)\n                self.context = None\n            if self._client_cert_chain:\n                CoreFoundation.CFRelease(self._client_cert_chain)\n                self._client_cert_chain = None\n            if self._keychain:\n                Security.SecKeychainDelete(self._keychain)\n                CoreFoundation.CFRelease(self._keychain)\n                shutil.rmtree(self._keychain_dir)\n                self._keychain = self._keychain_dir = None\n            return self.socket.close()\n        else:\n            self._makefile_refs -= 1\n\n    def getpeercert(self, binary_form=False):\n        # Urgh, annoying.\n        #\n        # Here's how we do this:\n        #\n        # 1. Call SSLCopyPeerTrust to get hold of the trust object for this\n        #    connection.\n        # 2. Call SecTrustGetCertificateAtIndex for index 0 to get the leaf.\n        # 3. To get the CN, call SecCertificateCopyCommonName and process that\n        #    string so that it's of the appropriate type.\n        # 4. To get the SAN, we need to do something a bit more complex:\n        #    a. Call SecCertificateCopyValues to get the data, requesting\n        #       kSecOIDSubjectAltName.\n        #    b. Mess about with this dictionary to try to get the SANs out.\n        #\n        # This is gross. Really gross. It's going to be a few hundred LoC extra\n        # just to repeat something that SecureTransport can *already do*. So my\n        # operating assumption at this time is that what we want to do is\n        # instead to just flag to urllib3 that it shouldn't do its own hostname\n        # validation when using SecureTransport.\n        if not binary_form:\n            raise ValueError(\n                \"SecureTransport only supports dumping binary certs\"\n            )\n        trust = Security.SecTrustRef()\n        certdata = None\n        der_bytes = None\n\n        try:\n            # Grab the trust store.\n            result = Security.SSLCopyPeerTrust(\n                self.context, ctypes.byref(trust)\n            )\n            _assert_no_error(result)\n            if not trust:\n                # Probably we haven't done the handshake yet. No biggie.\n                return None\n\n            cert_count = Security.SecTrustGetCertificateCount(trust)\n            if not cert_count:\n                # Also a case that might happen if we haven't handshaked.\n                # Handshook? Handshaken?\n                return None\n\n            leaf = Security.SecTrustGetCertificateAtIndex(trust, 0)\n            assert leaf\n\n            # Ok, now we want the DER bytes.\n            certdata = Security.SecCertificateCopyData(leaf)\n            assert certdata\n\n            data_length = CoreFoundation.CFDataGetLength(certdata)\n            data_buffer = CoreFoundation.CFDataGetBytePtr(certdata)\n            der_bytes = ctypes.string_at(data_buffer, data_length)\n        finally:\n            if certdata:\n                CoreFoundation.CFRelease(certdata)\n            if trust:\n                CoreFoundation.CFRelease(trust)\n\n        return der_bytes\n\n    def _reuse(self):\n        self._makefile_refs += 1\n\n    def _drop(self):\n        if self._makefile_refs < 1:\n            self.close()\n        else:\n            self._makefile_refs -= 1\n\n\nif _fileobject:  # Platform-specific: Python 2\n    def makefile(self, mode, bufsize=-1):\n        self._makefile_refs += 1\n        return _fileobject(self, mode, bufsize, close=True)\nelse:  # Platform-specific: Python 3\n    def makefile(self, mode=\"r\", buffering=None, *args, **kwargs):\n        # We disable buffering with SecureTransport because it conflicts with\n        # the buffering that ST does internally (see issue #1153 for more).\n        buffering = 0\n        return backport_makefile(self, mode, buffering, *args, **kwargs)\n\nWrappedSocket.makefile = makefile\n\n\nclass SecureTransportContext(object):\n    \"\"\"\n    I am a wrapper class for the SecureTransport library, to translate the\n    interface of the standard library ``SSLContext`` object to calls into\n    SecureTransport.\n    \"\"\"\n    def __init__(self, protocol):\n        self._min_version, self._max_version = _protocol_to_min_max[protocol]\n        self._options = 0\n        self._verify = False\n        self._trust_bundle = None\n        self._client_cert = None\n        self._client_key = None\n        self._client_key_passphrase = None\n\n    @property\n    def check_hostname(self):\n        \"\"\"\n        SecureTransport cannot have its hostname checking disabled. For more,\n        see the comment on getpeercert() in this file.\n        \"\"\"\n        return True\n\n    @check_hostname.setter\n    def check_hostname(self, value):\n        \"\"\"\n        SecureTransport cannot have its hostname checking disabled. For more,\n        see the comment on getpeercert() in this file.\n        \"\"\"\n        pass\n\n    @property\n    def options(self):\n        # TODO: Well, crap.\n        #\n        # So this is the bit of the code that is the most likely to cause us\n        # trouble. Essentially we need to enumerate all of the SSL options that\n        # users might want to use and try to see if we can sensibly translate\n        # them, or whether we should just ignore them.\n        return self._options\n\n    @options.setter\n    def options(self, value):\n        # TODO: Update in line with above.\n        self._options = value\n\n    @property\n    def verify_mode(self):\n        return ssl.CERT_REQUIRED if self._verify else ssl.CERT_NONE\n\n    @verify_mode.setter\n    def verify_mode(self, value):\n        self._verify = True if value == ssl.CERT_REQUIRED else False\n\n    def set_default_verify_paths(self):\n        # So, this has to do something a bit weird. Specifically, what it does\n        # is nothing.\n        #\n        # This means that, if we had previously had load_verify_locations\n        # called, this does not undo that. We need to do that because it turns\n        # out that the rest of the urllib3 code will attempt to load the\n        # default verify paths if it hasn't been told about any paths, even if\n        # the context itself was sometime earlier. We resolve that by just\n        # ignoring it.\n        pass\n\n    def load_default_certs(self):\n        return self.set_default_verify_paths()\n\n    def set_ciphers(self, ciphers):\n        # For now, we just require the default cipher string.\n        if ciphers != util.ssl_.DEFAULT_CIPHERS:\n            raise ValueError(\n                \"SecureTransport doesn't support custom cipher strings\"\n            )\n\n    def load_verify_locations(self, cafile=None, capath=None, cadata=None):\n        # OK, we only really support cadata and cafile.\n        if capath is not None:\n            raise ValueError(\n                \"SecureTransport does not support cert directories\"\n            )\n\n        self._trust_bundle = cafile or cadata\n\n    def load_cert_chain(self, certfile, keyfile=None, password=None):\n        self._client_cert = certfile\n        self._client_key = keyfile\n        self._client_cert_passphrase = password\n\n    def wrap_socket(self, sock, server_side=False,\n                    do_handshake_on_connect=True, suppress_ragged_eofs=True,\n                    server_hostname=None):\n        # So, what do we do here? Firstly, we assert some properties. This is a\n        # stripped down shim, so there is some functionality we don't support.\n        # See PEP 543 for the real deal.\n        assert not server_side\n        assert do_handshake_on_connect\n        assert suppress_ragged_eofs\n\n        # Ok, we're good to go. Now we want to create the wrapped socket object\n        # and store it in the appropriate place.\n        wrapped_socket = WrappedSocket(sock)\n\n        # Now we can handshake\n        wrapped_socket.handshake(\n            server_hostname, self._verify, self._trust_bundle,\n            self._min_version, self._max_version, self._client_cert,\n            self._client_key, self._client_key_passphrase\n        )\n        return wrapped_socket\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/contrib/socks.py",
    "content": "# -*- coding: utf-8 -*-\n\"\"\"\nThis module contains provisional support for SOCKS proxies from within\nurllib3. This module supports SOCKS4 (specifically the SOCKS4A variant) and\nSOCKS5. To enable its functionality, either install PySocks or install this\nmodule with the ``socks`` extra.\n\nThe SOCKS implementation supports the full range of urllib3 features. It also\nsupports the following SOCKS features:\n\n- SOCKS4\n- SOCKS4a\n- SOCKS5\n- Usernames and passwords for the SOCKS proxy\n\nKnown Limitations:\n\n- Currently PySocks does not support contacting remote websites via literal\n  IPv6 addresses. Any such connection attempt will fail. You must use a domain\n  name.\n- Currently PySocks does not support IPv6 connections to the SOCKS proxy. Any\n  such connection attempt will fail.\n\"\"\"\nfrom __future__ import absolute_import\n\ntry:\n    import socks\nexcept ImportError:\n    import warnings\n    from ..exceptions import DependencyWarning\n\n    warnings.warn((\n        'SOCKS support in urllib3 requires the installation of optional '\n        'dependencies: specifically, PySocks.  For more information, see '\n        'https://urllib3.readthedocs.io/en/latest/contrib.html#socks-proxies'\n        ),\n        DependencyWarning\n    )\n    raise\n\nfrom socket import error as SocketError, timeout as SocketTimeout\n\nfrom ..connection import (\n    HTTPConnection, HTTPSConnection\n)\nfrom ..connectionpool import (\n    HTTPConnectionPool, HTTPSConnectionPool\n)\nfrom ..exceptions import ConnectTimeoutError, NewConnectionError\nfrom ..poolmanager import PoolManager\nfrom ..util.url import parse_url\n\ntry:\n    import ssl\nexcept ImportError:\n    ssl = None\n\n\nclass SOCKSConnection(HTTPConnection):\n    \"\"\"\n    A plain-text HTTP connection that connects via a SOCKS proxy.\n    \"\"\"\n    def __init__(self, *args, **kwargs):\n        self._socks_options = kwargs.pop('_socks_options')\n        super(SOCKSConnection, self).__init__(*args, **kwargs)\n\n    def _new_conn(self):\n        \"\"\"\n        Establish a new connection via the SOCKS proxy.\n        \"\"\"\n        extra_kw = {}\n        if self.source_address:\n            extra_kw['source_address'] = self.source_address\n\n        if self.socket_options:\n            extra_kw['socket_options'] = self.socket_options\n\n        try:\n            conn = socks.create_connection(\n                (self.host, self.port),\n                proxy_type=self._socks_options['socks_version'],\n                proxy_addr=self._socks_options['proxy_host'],\n                proxy_port=self._socks_options['proxy_port'],\n                proxy_username=self._socks_options['username'],\n                proxy_password=self._socks_options['password'],\n                proxy_rdns=self._socks_options['rdns'],\n                timeout=self.timeout,\n                **extra_kw\n            )\n\n        except SocketTimeout as e:\n            raise ConnectTimeoutError(\n                self, \"Connection to %s timed out. (connect timeout=%s)\" %\n                (self.host, self.timeout))\n\n        except socks.ProxyError as e:\n            # This is fragile as hell, but it seems to be the only way to raise\n            # useful errors here.\n            if e.socket_err:\n                error = e.socket_err\n                if isinstance(error, SocketTimeout):\n                    raise ConnectTimeoutError(\n                        self,\n                        \"Connection to %s timed out. (connect timeout=%s)\" %\n                        (self.host, self.timeout)\n                    )\n                else:\n                    raise NewConnectionError(\n                        self,\n                        \"Failed to establish a new connection: %s\" % error\n                    )\n            else:\n                raise NewConnectionError(\n                    self,\n                    \"Failed to establish a new connection: %s\" % e\n                )\n\n        except SocketError as e:  # Defensive: PySocks should catch all these.\n            raise NewConnectionError(\n                self, \"Failed to establish a new connection: %s\" % e)\n\n        return conn\n\n\n# We don't need to duplicate the Verified/Unverified distinction from\n# urllib3/connection.py here because the HTTPSConnection will already have been\n# correctly set to either the Verified or Unverified form by that module. This\n# means the SOCKSHTTPSConnection will automatically be the correct type.\nclass SOCKSHTTPSConnection(SOCKSConnection, HTTPSConnection):\n    pass\n\n\nclass SOCKSHTTPConnectionPool(HTTPConnectionPool):\n    ConnectionCls = SOCKSConnection\n\n\nclass SOCKSHTTPSConnectionPool(HTTPSConnectionPool):\n    ConnectionCls = SOCKSHTTPSConnection\n\n\nclass SOCKSProxyManager(PoolManager):\n    \"\"\"\n    A version of the urllib3 ProxyManager that routes connections via the\n    defined SOCKS proxy.\n    \"\"\"\n    pool_classes_by_scheme = {\n        'http': SOCKSHTTPConnectionPool,\n        'https': SOCKSHTTPSConnectionPool,\n    }\n\n    def __init__(self, proxy_url, username=None, password=None,\n                 num_pools=10, headers=None, **connection_pool_kw):\n        parsed = parse_url(proxy_url)\n\n        if username is None and password is None and parsed.auth is not None:\n            split = parsed.auth.split(':')\n            if len(split) == 2:\n                username, password = split\n        if parsed.scheme == 'socks5':\n            socks_version = socks.PROXY_TYPE_SOCKS5\n            rdns = False\n        elif parsed.scheme == 'socks5h':\n            socks_version = socks.PROXY_TYPE_SOCKS5\n            rdns = True\n        elif parsed.scheme == 'socks4':\n            socks_version = socks.PROXY_TYPE_SOCKS4\n            rdns = False\n        elif parsed.scheme == 'socks4a':\n            socks_version = socks.PROXY_TYPE_SOCKS4\n            rdns = True\n        else:\n            raise ValueError(\n                \"Unable to determine SOCKS version from %s\" % proxy_url\n            )\n\n        self.proxy_url = proxy_url\n\n        socks_options = {\n            'socks_version': socks_version,\n            'proxy_host': parsed.host,\n            'proxy_port': parsed.port,\n            'username': username,\n            'password': password,\n            'rdns': rdns\n        }\n        connection_pool_kw['_socks_options'] = socks_options\n\n        super(SOCKSProxyManager, self).__init__(\n            num_pools, headers, **connection_pool_kw\n        )\n\n        self.pool_classes_by_scheme = SOCKSProxyManager.pool_classes_by_scheme\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/exceptions.py",
    "content": "from __future__ import absolute_import\nfrom .packages.six.moves.http_client import (\n    IncompleteRead as httplib_IncompleteRead\n)\n# Base Exceptions\n\n\nclass HTTPError(Exception):\n    \"Base exception used by this module.\"\n    pass\n\n\nclass HTTPWarning(Warning):\n    \"Base warning used by this module.\"\n    pass\n\n\nclass PoolError(HTTPError):\n    \"Base exception for errors caused within a pool.\"\n    def __init__(self, pool, message):\n        self.pool = pool\n        HTTPError.__init__(self, \"%s: %s\" % (pool, message))\n\n    def __reduce__(self):\n        # For pickling purposes.\n        return self.__class__, (None, None)\n\n\nclass RequestError(PoolError):\n    \"Base exception for PoolErrors that have associated URLs.\"\n    def __init__(self, pool, url, message):\n        self.url = url\n        PoolError.__init__(self, pool, message)\n\n    def __reduce__(self):\n        # For pickling purposes.\n        return self.__class__, (None, self.url, None)\n\n\nclass SSLError(HTTPError):\n    \"Raised when SSL certificate fails in an HTTPS connection.\"\n    pass\n\n\nclass ProxyError(HTTPError):\n    \"Raised when the connection to a proxy fails.\"\n    pass\n\n\nclass DecodeError(HTTPError):\n    \"Raised when automatic decoding based on Content-Type fails.\"\n    pass\n\n\nclass ProtocolError(HTTPError):\n    \"Raised when something unexpected happens mid-request/response.\"\n    pass\n\n\n#: Renamed to ProtocolError but aliased for backwards compatibility.\nConnectionError = ProtocolError\n\n\n# Leaf Exceptions\n\nclass MaxRetryError(RequestError):\n    \"\"\"Raised when the maximum number of retries is exceeded.\n\n    :param pool: The connection pool\n    :type pool: :class:`~urllib3.connectionpool.HTTPConnectionPool`\n    :param string url: The requested Url\n    :param exceptions.Exception reason: The underlying error\n\n    \"\"\"\n\n    def __init__(self, pool, url, reason=None):\n        self.reason = reason\n\n        message = \"Max retries exceeded with url: %s (Caused by %r)\" % (\n            url, reason)\n\n        RequestError.__init__(self, pool, url, message)\n\n\nclass HostChangedError(RequestError):\n    \"Raised when an existing pool gets a request for a foreign host.\"\n\n    def __init__(self, pool, url, retries=3):\n        message = \"Tried to open a foreign host with url: %s\" % url\n        RequestError.__init__(self, pool, url, message)\n        self.retries = retries\n\n\nclass TimeoutStateError(HTTPError):\n    \"\"\" Raised when passing an invalid state to a timeout \"\"\"\n    pass\n\n\nclass TimeoutError(HTTPError):\n    \"\"\" Raised when a socket timeout error occurs.\n\n    Catching this error will catch both :exc:`ReadTimeoutErrors\n    <ReadTimeoutError>` and :exc:`ConnectTimeoutErrors <ConnectTimeoutError>`.\n    \"\"\"\n    pass\n\n\nclass ReadTimeoutError(TimeoutError, RequestError):\n    \"Raised when a socket timeout occurs while receiving data from a server\"\n    pass\n\n\n# This timeout error does not have a URL attached and needs to inherit from the\n# base HTTPError\nclass ConnectTimeoutError(TimeoutError):\n    \"Raised when a socket timeout occurs while connecting to a server\"\n    pass\n\n\nclass NewConnectionError(ConnectTimeoutError, PoolError):\n    \"Raised when we fail to establish a new connection. Usually ECONNREFUSED.\"\n    pass\n\n\nclass EmptyPoolError(PoolError):\n    \"Raised when a pool runs out of connections and no more are allowed.\"\n    pass\n\n\nclass ClosedPoolError(PoolError):\n    \"Raised when a request enters a pool after the pool has been closed.\"\n    pass\n\n\nclass LocationValueError(ValueError, HTTPError):\n    \"Raised when there is something wrong with a given URL input.\"\n    pass\n\n\nclass LocationParseError(LocationValueError):\n    \"Raised when get_host or similar fails to parse the URL input.\"\n\n    def __init__(self, location):\n        message = \"Failed to parse: %s\" % location\n        HTTPError.__init__(self, message)\n\n        self.location = location\n\n\nclass ResponseError(HTTPError):\n    \"Used as a container for an error reason supplied in a MaxRetryError.\"\n    GENERIC_ERROR = 'too many error responses'\n    SPECIFIC_ERROR = 'too many {status_code} error responses'\n\n\nclass SecurityWarning(HTTPWarning):\n    \"Warned when performing security reducing actions\"\n    pass\n\n\nclass SubjectAltNameWarning(SecurityWarning):\n    \"Warned when connecting to a host with a certificate missing a SAN.\"\n    pass\n\n\nclass InsecureRequestWarning(SecurityWarning):\n    \"Warned when making an unverified HTTPS request.\"\n    pass\n\n\nclass SystemTimeWarning(SecurityWarning):\n    \"Warned when system time is suspected to be wrong\"\n    pass\n\n\nclass InsecurePlatformWarning(SecurityWarning):\n    \"Warned when certain SSL configuration is not available on a platform.\"\n    pass\n\n\nclass SNIMissingWarning(HTTPWarning):\n    \"Warned when making a HTTPS request without SNI available.\"\n    pass\n\n\nclass DependencyWarning(HTTPWarning):\n    \"\"\"\n    Warned when an attempt is made to import a module with missing optional\n    dependencies.\n    \"\"\"\n    pass\n\n\nclass ResponseNotChunked(ProtocolError, ValueError):\n    \"Response needs to be chunked in order to read it as chunks.\"\n    pass\n\n\nclass BodyNotHttplibCompatible(HTTPError):\n    \"\"\"\n    Body should be httplib.HTTPResponse like (have an fp attribute which\n    returns raw chunks) for read_chunked().\n    \"\"\"\n    pass\n\n\nclass IncompleteRead(HTTPError, httplib_IncompleteRead):\n    \"\"\"\n    Response length doesn't match expected Content-Length\n\n    Subclass of http_client.IncompleteRead to allow int value\n    for `partial` to avoid creating large objects on streamed\n    reads.\n    \"\"\"\n    def __init__(self, partial, expected):\n        super(IncompleteRead, self).__init__(partial, expected)\n\n    def __repr__(self):\n        return ('IncompleteRead(%i bytes read, '\n                '%i more expected)' % (self.partial, self.expected))\n\n\nclass InvalidHeader(HTTPError):\n    \"The header provided was somehow invalid.\"\n    pass\n\n\nclass ProxySchemeUnknown(AssertionError, ValueError):\n    \"ProxyManager does not support the supplied scheme\"\n    # TODO(t-8ch): Stop inheriting from AssertionError in v2.0.\n\n    def __init__(self, scheme):\n        message = \"Not supported proxy scheme %s\" % scheme\n        super(ProxySchemeUnknown, self).__init__(message)\n\n\nclass HeaderParsingError(HTTPError):\n    \"Raised by assert_header_parsing, but we convert it to a log.warning statement.\"\n    def __init__(self, defects, unparsed_data):\n        message = '%s, unparsed data: %r' % (defects or 'Unknown', unparsed_data)\n        super(HeaderParsingError, self).__init__(message)\n\n\nclass UnrewindableBodyError(HTTPError):\n    \"urllib3 encountered an error when trying to rewind a body\"\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/fields.py",
    "content": "from __future__ import absolute_import\nimport email.utils\nimport mimetypes\n\nfrom .packages import six\n\n\ndef guess_content_type(filename, default='application/octet-stream'):\n    \"\"\"\n    Guess the \"Content-Type\" of a file.\n\n    :param filename:\n        The filename to guess the \"Content-Type\" of using :mod:`mimetypes`.\n    :param default:\n        If no \"Content-Type\" can be guessed, default to `default`.\n    \"\"\"\n    if filename:\n        return mimetypes.guess_type(filename)[0] or default\n    return default\n\n\ndef format_header_param(name, value):\n    \"\"\"\n    Helper function to format and quote a single header parameter.\n\n    Particularly useful for header parameters which might contain\n    non-ASCII values, like file names. This follows RFC 2231, as\n    suggested by RFC 2388 Section 4.4.\n\n    :param name:\n        The name of the parameter, a string expected to be ASCII only.\n    :param value:\n        The value of the parameter, provided as a unicode string.\n    \"\"\"\n    if not any(ch in value for ch in '\"\\\\\\r\\n'):\n        result = '%s=\"%s\"' % (name, value)\n        try:\n            result.encode('ascii')\n        except (UnicodeEncodeError, UnicodeDecodeError):\n            pass\n        else:\n            return result\n    if not six.PY3 and isinstance(value, six.text_type):  # Python 2:\n        value = value.encode('utf-8')\n    value = email.utils.encode_rfc2231(value, 'utf-8')\n    value = '%s*=%s' % (name, value)\n    return value\n\n\nclass RequestField(object):\n    \"\"\"\n    A data container for request body parameters.\n\n    :param name:\n        The name of this request field.\n    :param data:\n        The data/value body.\n    :param filename:\n        An optional filename of the request field.\n    :param headers:\n        An optional dict-like object of headers to initially use for the field.\n    \"\"\"\n    def __init__(self, name, data, filename=None, headers=None):\n        self._name = name\n        self._filename = filename\n        self.data = data\n        self.headers = {}\n        if headers:\n            self.headers = dict(headers)\n\n    @classmethod\n    def from_tuples(cls, fieldname, value):\n        \"\"\"\n        A :class:`~urllib3.fields.RequestField` factory from old-style tuple parameters.\n\n        Supports constructing :class:`~urllib3.fields.RequestField` from\n        parameter of key/value strings AND key/filetuple. A filetuple is a\n        (filename, data, MIME type) tuple where the MIME type is optional.\n        For example::\n\n            'foo': 'bar',\n            'fakefile': ('foofile.txt', 'contents of foofile'),\n            'realfile': ('barfile.txt', open('realfile').read()),\n            'typedfile': ('bazfile.bin', open('bazfile').read(), 'image/jpeg'),\n            'nonamefile': 'contents of nonamefile field',\n\n        Field names and filenames must be unicode.\n        \"\"\"\n        if isinstance(value, tuple):\n            if len(value) == 3:\n                filename, data, content_type = value\n            else:\n                filename, data = value\n                content_type = guess_content_type(filename)\n        else:\n            filename = None\n            content_type = None\n            data = value\n\n        request_param = cls(fieldname, data, filename=filename)\n        request_param.make_multipart(content_type=content_type)\n\n        return request_param\n\n    def _render_part(self, name, value):\n        \"\"\"\n        Overridable helper function to format a single header parameter.\n\n        :param name:\n            The name of the parameter, a string expected to be ASCII only.\n        :param value:\n            The value of the parameter, provided as a unicode string.\n        \"\"\"\n        return format_header_param(name, value)\n\n    def _render_parts(self, header_parts):\n        \"\"\"\n        Helper function to format and quote a single header.\n\n        Useful for single headers that are composed of multiple items. E.g.,\n        'Content-Disposition' fields.\n\n        :param header_parts:\n            A sequence of (k, v) tuples or a :class:`dict` of (k, v) to format\n            as `k1=\"v1\"; k2=\"v2\"; ...`.\n        \"\"\"\n        parts = []\n        iterable = header_parts\n        if isinstance(header_parts, dict):\n            iterable = header_parts.items()\n\n        for name, value in iterable:\n            if value is not None:\n                parts.append(self._render_part(name, value))\n\n        return '; '.join(parts)\n\n    def render_headers(self):\n        \"\"\"\n        Renders the headers for this request field.\n        \"\"\"\n        lines = []\n\n        sort_keys = ['Content-Disposition', 'Content-Type', 'Content-Location']\n        for sort_key in sort_keys:\n            if self.headers.get(sort_key, False):\n                lines.append('%s: %s' % (sort_key, self.headers[sort_key]))\n\n        for header_name, header_value in self.headers.items():\n            if header_name not in sort_keys:\n                if header_value:\n                    lines.append('%s: %s' % (header_name, header_value))\n\n        lines.append('\\r\\n')\n        return '\\r\\n'.join(lines)\n\n    def make_multipart(self, content_disposition=None, content_type=None,\n                       content_location=None):\n        \"\"\"\n        Makes this request field into a multipart request field.\n\n        This method overrides \"Content-Disposition\", \"Content-Type\" and\n        \"Content-Location\" headers to the request parameter.\n\n        :param content_type:\n            The 'Content-Type' of the request body.\n        :param content_location:\n            The 'Content-Location' of the request body.\n\n        \"\"\"\n        self.headers['Content-Disposition'] = content_disposition or 'form-data'\n        self.headers['Content-Disposition'] += '; '.join([\n            '', self._render_parts(\n                (('name', self._name), ('filename', self._filename))\n            )\n        ])\n        self.headers['Content-Type'] = content_type\n        self.headers['Content-Location'] = content_location\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/filepost.py",
    "content": "from __future__ import absolute_import\nimport binascii\nimport codecs\nimport os\n\nfrom io import BytesIO\n\nfrom .packages import six\nfrom .packages.six import b\nfrom .fields import RequestField\n\nwriter = codecs.lookup('utf-8')[3]\n\n\ndef choose_boundary():\n    \"\"\"\n    Our embarrassingly-simple replacement for mimetools.choose_boundary.\n    \"\"\"\n    boundary = binascii.hexlify(os.urandom(16))\n    if six.PY3:\n        boundary = boundary.decode('ascii')\n    return boundary\n\n\ndef iter_field_objects(fields):\n    \"\"\"\n    Iterate over fields.\n\n    Supports list of (k, v) tuples and dicts, and lists of\n    :class:`~urllib3.fields.RequestField`.\n\n    \"\"\"\n    if isinstance(fields, dict):\n        i = six.iteritems(fields)\n    else:\n        i = iter(fields)\n\n    for field in i:\n        if isinstance(field, RequestField):\n            yield field\n        else:\n            yield RequestField.from_tuples(*field)\n\n\ndef iter_fields(fields):\n    \"\"\"\n    .. deprecated:: 1.6\n\n    Iterate over fields.\n\n    The addition of :class:`~urllib3.fields.RequestField` makes this function\n    obsolete. Instead, use :func:`iter_field_objects`, which returns\n    :class:`~urllib3.fields.RequestField` objects.\n\n    Supports list of (k, v) tuples and dicts.\n    \"\"\"\n    if isinstance(fields, dict):\n        return ((k, v) for k, v in six.iteritems(fields))\n\n    return ((k, v) for k, v in fields)\n\n\ndef encode_multipart_formdata(fields, boundary=None):\n    \"\"\"\n    Encode a dictionary of ``fields`` using the multipart/form-data MIME format.\n\n    :param fields:\n        Dictionary of fields or list of (key, :class:`~urllib3.fields.RequestField`).\n\n    :param boundary:\n        If not specified, then a random boundary will be generated using\n        :func:`urllib3.filepost.choose_boundary`.\n    \"\"\"\n    body = BytesIO()\n    if boundary is None:\n        boundary = choose_boundary()\n\n    for field in iter_field_objects(fields):\n        body.write(b('--%s\\r\\n' % (boundary)))\n\n        writer(body).write(field.render_headers())\n        data = field.data\n\n        if isinstance(data, int):\n            data = str(data)  # Backwards compatibility\n\n        if isinstance(data, six.text_type):\n            writer(body).write(data)\n        else:\n            body.write(data)\n\n        body.write(b'\\r\\n')\n\n    body.write(b('--%s--\\r\\n' % (boundary)))\n\n    content_type = str('multipart/form-data; boundary=%s' % boundary)\n\n    return body.getvalue(), content_type\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/packages/__init__.py",
    "content": "from __future__ import absolute_import\n\nfrom . import ssl_match_hostname\n\n__all__ = ('ssl_match_hostname', )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/packages/backports/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/packages/backports/makefile.py",
    "content": "# -*- coding: utf-8 -*-\n\"\"\"\nbackports.makefile\n~~~~~~~~~~~~~~~~~~\n\nBackports the Python 3 ``socket.makefile`` method for use with anything that\nwants to create a \"fake\" socket object.\n\"\"\"\nimport io\n\nfrom socket import SocketIO\n\n\ndef backport_makefile(self, mode=\"r\", buffering=None, encoding=None,\n                      errors=None, newline=None):\n    \"\"\"\n    Backport of ``socket.makefile`` from Python 3.5.\n    \"\"\"\n    if not set(mode) <= {\"r\", \"w\", \"b\"}:\n        raise ValueError(\n            \"invalid mode %r (only r, w, b allowed)\" % (mode,)\n        )\n    writing = \"w\" in mode\n    reading = \"r\" in mode or not writing\n    assert reading or writing\n    binary = \"b\" in mode\n    rawmode = \"\"\n    if reading:\n        rawmode += \"r\"\n    if writing:\n        rawmode += \"w\"\n    raw = SocketIO(self, rawmode)\n    self._makefile_refs += 1\n    if buffering is None:\n        buffering = -1\n    if buffering < 0:\n        buffering = io.DEFAULT_BUFFER_SIZE\n    if buffering == 0:\n        if not binary:\n            raise ValueError(\"unbuffered streams must be binary\")\n        return raw\n    if reading and writing:\n        buffer = io.BufferedRWPair(raw, raw, buffering)\n    elif reading:\n        buffer = io.BufferedReader(raw, buffering)\n    else:\n        assert writing\n        buffer = io.BufferedWriter(raw, buffering)\n    if binary:\n        return buffer\n    text = io.TextIOWrapper(buffer, encoding, errors, newline)\n    text.mode = mode\n    return text\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/packages/six.py",
    "content": "\"\"\"Utilities for writing code that runs on Python 2 and 3\"\"\"\n\n# Copyright (c) 2010-2015 Benjamin Peterson\n#\n# Permission is hereby granted, free of charge, to any person obtaining a copy\n# of this software and associated documentation files (the \"Software\"), to deal\n# in the Software without restriction, including without limitation the rights\n# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n# copies of the Software, and to permit persons to whom the Software is\n# furnished to do so, subject to the following conditions:\n#\n# The above copyright notice and this permission notice shall be included in all\n# copies or substantial portions of the Software.\n#\n# THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n# SOFTWARE.\n\nfrom __future__ import absolute_import\n\nimport functools\nimport itertools\nimport operator\nimport sys\nimport types\n\n__author__ = \"Benjamin Peterson <benjamin@python.org>\"\n__version__ = \"1.10.0\"\n\n\n# Useful for very coarse version differentiation.\nPY2 = sys.version_info[0] == 2\nPY3 = sys.version_info[0] == 3\nPY34 = sys.version_info[0:2] >= (3, 4)\n\nif PY3:\n    string_types = str,\n    integer_types = int,\n    class_types = type,\n    text_type = str\n    binary_type = bytes\n\n    MAXSIZE = sys.maxsize\nelse:\n    string_types = basestring,\n    integer_types = (int, long)\n    class_types = (type, types.ClassType)\n    text_type = unicode\n    binary_type = str\n\n    if sys.platform.startswith(\"java\"):\n        # Jython always uses 32 bits.\n        MAXSIZE = int((1 << 31) - 1)\n    else:\n        # It's possible to have sizeof(long) != sizeof(Py_ssize_t).\n        class X(object):\n\n            def __len__(self):\n                return 1 << 31\n        try:\n            len(X())\n        except OverflowError:\n            # 32-bit\n            MAXSIZE = int((1 << 31) - 1)\n        else:\n            # 64-bit\n            MAXSIZE = int((1 << 63) - 1)\n        del X\n\n\ndef _add_doc(func, doc):\n    \"\"\"Add documentation to a function.\"\"\"\n    func.__doc__ = doc\n\n\ndef _import_module(name):\n    \"\"\"Import module, returning the module after the last dot.\"\"\"\n    __import__(name)\n    return sys.modules[name]\n\n\nclass _LazyDescr(object):\n\n    def __init__(self, name):\n        self.name = name\n\n    def __get__(self, obj, tp):\n        result = self._resolve()\n        setattr(obj, self.name, result)  # Invokes __set__.\n        try:\n            # This is a bit ugly, but it avoids running this again by\n            # removing this descriptor.\n            delattr(obj.__class__, self.name)\n        except AttributeError:\n            pass\n        return result\n\n\nclass MovedModule(_LazyDescr):\n\n    def __init__(self, name, old, new=None):\n        super(MovedModule, self).__init__(name)\n        if PY3:\n            if new is None:\n                new = name\n            self.mod = new\n        else:\n            self.mod = old\n\n    def _resolve(self):\n        return _import_module(self.mod)\n\n    def __getattr__(self, attr):\n        _module = self._resolve()\n        value = getattr(_module, attr)\n        setattr(self, attr, value)\n        return value\n\n\nclass _LazyModule(types.ModuleType):\n\n    def __init__(self, name):\n        super(_LazyModule, self).__init__(name)\n        self.__doc__ = self.__class__.__doc__\n\n    def __dir__(self):\n        attrs = [\"__doc__\", \"__name__\"]\n        attrs += [attr.name for attr in self._moved_attributes]\n        return attrs\n\n    # Subclasses should override this\n    _moved_attributes = []\n\n\nclass MovedAttribute(_LazyDescr):\n\n    def __init__(self, name, old_mod, new_mod, old_attr=None, new_attr=None):\n        super(MovedAttribute, self).__init__(name)\n        if PY3:\n            if new_mod is None:\n                new_mod = name\n            self.mod = new_mod\n            if new_attr is None:\n                if old_attr is None:\n                    new_attr = name\n                else:\n                    new_attr = old_attr\n            self.attr = new_attr\n        else:\n            self.mod = old_mod\n            if old_attr is None:\n                old_attr = name\n            self.attr = old_attr\n\n    def _resolve(self):\n        module = _import_module(self.mod)\n        return getattr(module, self.attr)\n\n\nclass _SixMetaPathImporter(object):\n\n    \"\"\"\n    A meta path importer to import six.moves and its submodules.\n\n    This class implements a PEP302 finder and loader. It should be compatible\n    with Python 2.5 and all existing versions of Python3\n    \"\"\"\n\n    def __init__(self, six_module_name):\n        self.name = six_module_name\n        self.known_modules = {}\n\n    def _add_module(self, mod, *fullnames):\n        for fullname in fullnames:\n            self.known_modules[self.name + \".\" + fullname] = mod\n\n    def _get_module(self, fullname):\n        return self.known_modules[self.name + \".\" + fullname]\n\n    def find_module(self, fullname, path=None):\n        if fullname in self.known_modules:\n            return self\n        return None\n\n    def __get_module(self, fullname):\n        try:\n            return self.known_modules[fullname]\n        except KeyError:\n            raise ImportError(\"This loader does not know module \" + fullname)\n\n    def load_module(self, fullname):\n        try:\n            # in case of a reload\n            return sys.modules[fullname]\n        except KeyError:\n            pass\n        mod = self.__get_module(fullname)\n        if isinstance(mod, MovedModule):\n            mod = mod._resolve()\n        else:\n            mod.__loader__ = self\n        sys.modules[fullname] = mod\n        return mod\n\n    def is_package(self, fullname):\n        \"\"\"\n        Return true, if the named module is a package.\n\n        We need this method to get correct spec objects with\n        Python 3.4 (see PEP451)\n        \"\"\"\n        return hasattr(self.__get_module(fullname), \"__path__\")\n\n    def get_code(self, fullname):\n        \"\"\"Return None\n\n        Required, if is_package is implemented\"\"\"\n        self.__get_module(fullname)  # eventually raises ImportError\n        return None\n    get_source = get_code  # same as get_code\n\n_importer = _SixMetaPathImporter(__name__)\n\n\nclass _MovedItems(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects\"\"\"\n    __path__ = []  # mark as package\n\n\n_moved_attributes = [\n    MovedAttribute(\"cStringIO\", \"cStringIO\", \"io\", \"StringIO\"),\n    MovedAttribute(\"filter\", \"itertools\", \"builtins\", \"ifilter\", \"filter\"),\n    MovedAttribute(\"filterfalse\", \"itertools\", \"itertools\", \"ifilterfalse\", \"filterfalse\"),\n    MovedAttribute(\"input\", \"__builtin__\", \"builtins\", \"raw_input\", \"input\"),\n    MovedAttribute(\"intern\", \"__builtin__\", \"sys\"),\n    MovedAttribute(\"map\", \"itertools\", \"builtins\", \"imap\", \"map\"),\n    MovedAttribute(\"getcwd\", \"os\", \"os\", \"getcwdu\", \"getcwd\"),\n    MovedAttribute(\"getcwdb\", \"os\", \"os\", \"getcwd\", \"getcwdb\"),\n    MovedAttribute(\"range\", \"__builtin__\", \"builtins\", \"xrange\", \"range\"),\n    MovedAttribute(\"reload_module\", \"__builtin__\", \"importlib\" if PY34 else \"imp\", \"reload\"),\n    MovedAttribute(\"reduce\", \"__builtin__\", \"functools\"),\n    MovedAttribute(\"shlex_quote\", \"pipes\", \"shlex\", \"quote\"),\n    MovedAttribute(\"StringIO\", \"StringIO\", \"io\"),\n    MovedAttribute(\"UserDict\", \"UserDict\", \"collections\"),\n    MovedAttribute(\"UserList\", \"UserList\", \"collections\"),\n    MovedAttribute(\"UserString\", \"UserString\", \"collections\"),\n    MovedAttribute(\"xrange\", \"__builtin__\", \"builtins\", \"xrange\", \"range\"),\n    MovedAttribute(\"zip\", \"itertools\", \"builtins\", \"izip\", \"zip\"),\n    MovedAttribute(\"zip_longest\", \"itertools\", \"itertools\", \"izip_longest\", \"zip_longest\"),\n    MovedModule(\"builtins\", \"__builtin__\"),\n    MovedModule(\"configparser\", \"ConfigParser\"),\n    MovedModule(\"copyreg\", \"copy_reg\"),\n    MovedModule(\"dbm_gnu\", \"gdbm\", \"dbm.gnu\"),\n    MovedModule(\"_dummy_thread\", \"dummy_thread\", \"_dummy_thread\"),\n    MovedModule(\"http_cookiejar\", \"cookielib\", \"http.cookiejar\"),\n    MovedModule(\"http_cookies\", \"Cookie\", \"http.cookies\"),\n    MovedModule(\"html_entities\", \"htmlentitydefs\", \"html.entities\"),\n    MovedModule(\"html_parser\", \"HTMLParser\", \"html.parser\"),\n    MovedModule(\"http_client\", \"httplib\", \"http.client\"),\n    MovedModule(\"email_mime_multipart\", \"email.MIMEMultipart\", \"email.mime.multipart\"),\n    MovedModule(\"email_mime_nonmultipart\", \"email.MIMENonMultipart\", \"email.mime.nonmultipart\"),\n    MovedModule(\"email_mime_text\", \"email.MIMEText\", \"email.mime.text\"),\n    MovedModule(\"email_mime_base\", \"email.MIMEBase\", \"email.mime.base\"),\n    MovedModule(\"BaseHTTPServer\", \"BaseHTTPServer\", \"http.server\"),\n    MovedModule(\"CGIHTTPServer\", \"CGIHTTPServer\", \"http.server\"),\n    MovedModule(\"SimpleHTTPServer\", \"SimpleHTTPServer\", \"http.server\"),\n    MovedModule(\"cPickle\", \"cPickle\", \"pickle\"),\n    MovedModule(\"queue\", \"Queue\"),\n    MovedModule(\"reprlib\", \"repr\"),\n    MovedModule(\"socketserver\", \"SocketServer\"),\n    MovedModule(\"_thread\", \"thread\", \"_thread\"),\n    MovedModule(\"tkinter\", \"Tkinter\"),\n    MovedModule(\"tkinter_dialog\", \"Dialog\", \"tkinter.dialog\"),\n    MovedModule(\"tkinter_filedialog\", \"FileDialog\", \"tkinter.filedialog\"),\n    MovedModule(\"tkinter_scrolledtext\", \"ScrolledText\", \"tkinter.scrolledtext\"),\n    MovedModule(\"tkinter_simpledialog\", \"SimpleDialog\", \"tkinter.simpledialog\"),\n    MovedModule(\"tkinter_tix\", \"Tix\", \"tkinter.tix\"),\n    MovedModule(\"tkinter_ttk\", \"ttk\", \"tkinter.ttk\"),\n    MovedModule(\"tkinter_constants\", \"Tkconstants\", \"tkinter.constants\"),\n    MovedModule(\"tkinter_dnd\", \"Tkdnd\", \"tkinter.dnd\"),\n    MovedModule(\"tkinter_colorchooser\", \"tkColorChooser\",\n                \"tkinter.colorchooser\"),\n    MovedModule(\"tkinter_commondialog\", \"tkCommonDialog\",\n                \"tkinter.commondialog\"),\n    MovedModule(\"tkinter_tkfiledialog\", \"tkFileDialog\", \"tkinter.filedialog\"),\n    MovedModule(\"tkinter_font\", \"tkFont\", \"tkinter.font\"),\n    MovedModule(\"tkinter_messagebox\", \"tkMessageBox\", \"tkinter.messagebox\"),\n    MovedModule(\"tkinter_tksimpledialog\", \"tkSimpleDialog\",\n                \"tkinter.simpledialog\"),\n    MovedModule(\"urllib_parse\", __name__ + \".moves.urllib_parse\", \"urllib.parse\"),\n    MovedModule(\"urllib_error\", __name__ + \".moves.urllib_error\", \"urllib.error\"),\n    MovedModule(\"urllib\", __name__ + \".moves.urllib\", __name__ + \".moves.urllib\"),\n    MovedModule(\"urllib_robotparser\", \"robotparser\", \"urllib.robotparser\"),\n    MovedModule(\"xmlrpc_client\", \"xmlrpclib\", \"xmlrpc.client\"),\n    MovedModule(\"xmlrpc_server\", \"SimpleXMLRPCServer\", \"xmlrpc.server\"),\n]\n# Add windows specific modules.\nif sys.platform == \"win32\":\n    _moved_attributes += [\n        MovedModule(\"winreg\", \"_winreg\"),\n    ]\n\nfor attr in _moved_attributes:\n    setattr(_MovedItems, attr.name, attr)\n    if isinstance(attr, MovedModule):\n        _importer._add_module(attr, \"moves.\" + attr.name)\ndel attr\n\n_MovedItems._moved_attributes = _moved_attributes\n\nmoves = _MovedItems(__name__ + \".moves\")\n_importer._add_module(moves, \"moves\")\n\n\nclass Module_six_moves_urllib_parse(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_parse\"\"\"\n\n\n_urllib_parse_moved_attributes = [\n    MovedAttribute(\"ParseResult\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"SplitResult\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"parse_qs\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"parse_qsl\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urldefrag\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urljoin\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urlparse\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urlsplit\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urlunparse\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urlunsplit\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"quote\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"quote_plus\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"unquote\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"unquote_plus\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"urlencode\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"splitquery\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"splittag\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"splituser\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"uses_fragment\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"uses_netloc\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"uses_params\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"uses_query\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"uses_relative\", \"urlparse\", \"urllib.parse\"),\n]\nfor attr in _urllib_parse_moved_attributes:\n    setattr(Module_six_moves_urllib_parse, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_parse._moved_attributes = _urllib_parse_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_parse(__name__ + \".moves.urllib_parse\"),\n                      \"moves.urllib_parse\", \"moves.urllib.parse\")\n\n\nclass Module_six_moves_urllib_error(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_error\"\"\"\n\n\n_urllib_error_moved_attributes = [\n    MovedAttribute(\"URLError\", \"urllib2\", \"urllib.error\"),\n    MovedAttribute(\"HTTPError\", \"urllib2\", \"urllib.error\"),\n    MovedAttribute(\"ContentTooShortError\", \"urllib\", \"urllib.error\"),\n]\nfor attr in _urllib_error_moved_attributes:\n    setattr(Module_six_moves_urllib_error, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_error._moved_attributes = _urllib_error_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_error(__name__ + \".moves.urllib.error\"),\n                      \"moves.urllib_error\", \"moves.urllib.error\")\n\n\nclass Module_six_moves_urllib_request(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_request\"\"\"\n\n\n_urllib_request_moved_attributes = [\n    MovedAttribute(\"urlopen\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"install_opener\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"build_opener\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"pathname2url\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"url2pathname\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"getproxies\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"Request\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"OpenerDirector\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPDefaultErrorHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPRedirectHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPCookieProcessor\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"ProxyHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"BaseHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPPasswordMgr\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPPasswordMgrWithDefaultRealm\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"AbstractBasicAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPBasicAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"ProxyBasicAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"AbstractDigestAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPDigestAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"ProxyDigestAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPSHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"FileHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"FTPHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"CacheFTPHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"UnknownHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPErrorProcessor\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"urlretrieve\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"urlcleanup\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"URLopener\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"FancyURLopener\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"proxy_bypass\", \"urllib\", \"urllib.request\"),\n]\nfor attr in _urllib_request_moved_attributes:\n    setattr(Module_six_moves_urllib_request, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_request._moved_attributes = _urllib_request_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_request(__name__ + \".moves.urllib.request\"),\n                      \"moves.urllib_request\", \"moves.urllib.request\")\n\n\nclass Module_six_moves_urllib_response(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_response\"\"\"\n\n\n_urllib_response_moved_attributes = [\n    MovedAttribute(\"addbase\", \"urllib\", \"urllib.response\"),\n    MovedAttribute(\"addclosehook\", \"urllib\", \"urllib.response\"),\n    MovedAttribute(\"addinfo\", \"urllib\", \"urllib.response\"),\n    MovedAttribute(\"addinfourl\", \"urllib\", \"urllib.response\"),\n]\nfor attr in _urllib_response_moved_attributes:\n    setattr(Module_six_moves_urllib_response, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_response._moved_attributes = _urllib_response_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_response(__name__ + \".moves.urllib.response\"),\n                      \"moves.urllib_response\", \"moves.urllib.response\")\n\n\nclass Module_six_moves_urllib_robotparser(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_robotparser\"\"\"\n\n\n_urllib_robotparser_moved_attributes = [\n    MovedAttribute(\"RobotFileParser\", \"robotparser\", \"urllib.robotparser\"),\n]\nfor attr in _urllib_robotparser_moved_attributes:\n    setattr(Module_six_moves_urllib_robotparser, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_robotparser._moved_attributes = _urllib_robotparser_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_robotparser(__name__ + \".moves.urllib.robotparser\"),\n                      \"moves.urllib_robotparser\", \"moves.urllib.robotparser\")\n\n\nclass Module_six_moves_urllib(types.ModuleType):\n\n    \"\"\"Create a six.moves.urllib namespace that resembles the Python 3 namespace\"\"\"\n    __path__ = []  # mark as package\n    parse = _importer._get_module(\"moves.urllib_parse\")\n    error = _importer._get_module(\"moves.urllib_error\")\n    request = _importer._get_module(\"moves.urllib_request\")\n    response = _importer._get_module(\"moves.urllib_response\")\n    robotparser = _importer._get_module(\"moves.urllib_robotparser\")\n\n    def __dir__(self):\n        return ['parse', 'error', 'request', 'response', 'robotparser']\n\n_importer._add_module(Module_six_moves_urllib(__name__ + \".moves.urllib\"),\n                      \"moves.urllib\")\n\n\ndef add_move(move):\n    \"\"\"Add an item to six.moves.\"\"\"\n    setattr(_MovedItems, move.name, move)\n\n\ndef remove_move(name):\n    \"\"\"Remove item from six.moves.\"\"\"\n    try:\n        delattr(_MovedItems, name)\n    except AttributeError:\n        try:\n            del moves.__dict__[name]\n        except KeyError:\n            raise AttributeError(\"no such move, %r\" % (name,))\n\n\nif PY3:\n    _meth_func = \"__func__\"\n    _meth_self = \"__self__\"\n\n    _func_closure = \"__closure__\"\n    _func_code = \"__code__\"\n    _func_defaults = \"__defaults__\"\n    _func_globals = \"__globals__\"\nelse:\n    _meth_func = \"im_func\"\n    _meth_self = \"im_self\"\n\n    _func_closure = \"func_closure\"\n    _func_code = \"func_code\"\n    _func_defaults = \"func_defaults\"\n    _func_globals = \"func_globals\"\n\n\ntry:\n    advance_iterator = next\nexcept NameError:\n    def advance_iterator(it):\n        return it.next()\nnext = advance_iterator\n\n\ntry:\n    callable = callable\nexcept NameError:\n    def callable(obj):\n        return any(\"__call__\" in klass.__dict__ for klass in type(obj).__mro__)\n\n\nif PY3:\n    def get_unbound_function(unbound):\n        return unbound\n\n    create_bound_method = types.MethodType\n\n    def create_unbound_method(func, cls):\n        return func\n\n    Iterator = object\nelse:\n    def get_unbound_function(unbound):\n        return unbound.im_func\n\n    def create_bound_method(func, obj):\n        return types.MethodType(func, obj, obj.__class__)\n\n    def create_unbound_method(func, cls):\n        return types.MethodType(func, None, cls)\n\n    class Iterator(object):\n\n        def next(self):\n            return type(self).__next__(self)\n\n    callable = callable\n_add_doc(get_unbound_function,\n         \"\"\"Get the function out of a possibly unbound function\"\"\")\n\n\nget_method_function = operator.attrgetter(_meth_func)\nget_method_self = operator.attrgetter(_meth_self)\nget_function_closure = operator.attrgetter(_func_closure)\nget_function_code = operator.attrgetter(_func_code)\nget_function_defaults = operator.attrgetter(_func_defaults)\nget_function_globals = operator.attrgetter(_func_globals)\n\n\nif PY3:\n    def iterkeys(d, **kw):\n        return iter(d.keys(**kw))\n\n    def itervalues(d, **kw):\n        return iter(d.values(**kw))\n\n    def iteritems(d, **kw):\n        return iter(d.items(**kw))\n\n    def iterlists(d, **kw):\n        return iter(d.lists(**kw))\n\n    viewkeys = operator.methodcaller(\"keys\")\n\n    viewvalues = operator.methodcaller(\"values\")\n\n    viewitems = operator.methodcaller(\"items\")\nelse:\n    def iterkeys(d, **kw):\n        return d.iterkeys(**kw)\n\n    def itervalues(d, **kw):\n        return d.itervalues(**kw)\n\n    def iteritems(d, **kw):\n        return d.iteritems(**kw)\n\n    def iterlists(d, **kw):\n        return d.iterlists(**kw)\n\n    viewkeys = operator.methodcaller(\"viewkeys\")\n\n    viewvalues = operator.methodcaller(\"viewvalues\")\n\n    viewitems = operator.methodcaller(\"viewitems\")\n\n_add_doc(iterkeys, \"Return an iterator over the keys of a dictionary.\")\n_add_doc(itervalues, \"Return an iterator over the values of a dictionary.\")\n_add_doc(iteritems,\n         \"Return an iterator over the (key, value) pairs of a dictionary.\")\n_add_doc(iterlists,\n         \"Return an iterator over the (key, [values]) pairs of a dictionary.\")\n\n\nif PY3:\n    def b(s):\n        return s.encode(\"latin-1\")\n\n    def u(s):\n        return s\n    unichr = chr\n    import struct\n    int2byte = struct.Struct(\">B\").pack\n    del struct\n    byte2int = operator.itemgetter(0)\n    indexbytes = operator.getitem\n    iterbytes = iter\n    import io\n    StringIO = io.StringIO\n    BytesIO = io.BytesIO\n    _assertCountEqual = \"assertCountEqual\"\n    if sys.version_info[1] <= 1:\n        _assertRaisesRegex = \"assertRaisesRegexp\"\n        _assertRegex = \"assertRegexpMatches\"\n    else:\n        _assertRaisesRegex = \"assertRaisesRegex\"\n        _assertRegex = \"assertRegex\"\nelse:\n    def b(s):\n        return s\n    # Workaround for standalone backslash\n\n    def u(s):\n        return unicode(s.replace(r'\\\\', r'\\\\\\\\'), \"unicode_escape\")\n    unichr = unichr\n    int2byte = chr\n\n    def byte2int(bs):\n        return ord(bs[0])\n\n    def indexbytes(buf, i):\n        return ord(buf[i])\n    iterbytes = functools.partial(itertools.imap, ord)\n    import StringIO\n    StringIO = BytesIO = StringIO.StringIO\n    _assertCountEqual = \"assertItemsEqual\"\n    _assertRaisesRegex = \"assertRaisesRegexp\"\n    _assertRegex = \"assertRegexpMatches\"\n_add_doc(b, \"\"\"Byte literal\"\"\")\n_add_doc(u, \"\"\"Text literal\"\"\")\n\n\ndef assertCountEqual(self, *args, **kwargs):\n    return getattr(self, _assertCountEqual)(*args, **kwargs)\n\n\ndef assertRaisesRegex(self, *args, **kwargs):\n    return getattr(self, _assertRaisesRegex)(*args, **kwargs)\n\n\ndef assertRegex(self, *args, **kwargs):\n    return getattr(self, _assertRegex)(*args, **kwargs)\n\n\nif PY3:\n    exec_ = getattr(moves.builtins, \"exec\")\n\n    def reraise(tp, value, tb=None):\n        if value is None:\n            value = tp()\n        if value.__traceback__ is not tb:\n            raise value.with_traceback(tb)\n        raise value\n\nelse:\n    def exec_(_code_, _globs_=None, _locs_=None):\n        \"\"\"Execute code in a namespace.\"\"\"\n        if _globs_ is None:\n            frame = sys._getframe(1)\n            _globs_ = frame.f_globals\n            if _locs_ is None:\n                _locs_ = frame.f_locals\n            del frame\n        elif _locs_ is None:\n            _locs_ = _globs_\n        exec(\"\"\"exec _code_ in _globs_, _locs_\"\"\")\n\n    exec_(\"\"\"def reraise(tp, value, tb=None):\n    raise tp, value, tb\n\"\"\")\n\n\nif sys.version_info[:2] == (3, 2):\n    exec_(\"\"\"def raise_from(value, from_value):\n    if from_value is None:\n        raise value\n    raise value from from_value\n\"\"\")\nelif sys.version_info[:2] > (3, 2):\n    exec_(\"\"\"def raise_from(value, from_value):\n    raise value from from_value\n\"\"\")\nelse:\n    def raise_from(value, from_value):\n        raise value\n\n\nprint_ = getattr(moves.builtins, \"print\", None)\nif print_ is None:\n    def print_(*args, **kwargs):\n        \"\"\"The new-style print function for Python 2.4 and 2.5.\"\"\"\n        fp = kwargs.pop(\"file\", sys.stdout)\n        if fp is None:\n            return\n\n        def write(data):\n            if not isinstance(data, basestring):\n                data = str(data)\n            # If the file has an encoding, encode unicode with it.\n            if (isinstance(fp, file) and\n                    isinstance(data, unicode) and\n                    fp.encoding is not None):\n                errors = getattr(fp, \"errors\", None)\n                if errors is None:\n                    errors = \"strict\"\n                data = data.encode(fp.encoding, errors)\n            fp.write(data)\n        want_unicode = False\n        sep = kwargs.pop(\"sep\", None)\n        if sep is not None:\n            if isinstance(sep, unicode):\n                want_unicode = True\n            elif not isinstance(sep, str):\n                raise TypeError(\"sep must be None or a string\")\n        end = kwargs.pop(\"end\", None)\n        if end is not None:\n            if isinstance(end, unicode):\n                want_unicode = True\n            elif not isinstance(end, str):\n                raise TypeError(\"end must be None or a string\")\n        if kwargs:\n            raise TypeError(\"invalid keyword arguments to print()\")\n        if not want_unicode:\n            for arg in args:\n                if isinstance(arg, unicode):\n                    want_unicode = True\n                    break\n        if want_unicode:\n            newline = unicode(\"\\n\")\n            space = unicode(\" \")\n        else:\n            newline = \"\\n\"\n            space = \" \"\n        if sep is None:\n            sep = space\n        if end is None:\n            end = newline\n        for i, arg in enumerate(args):\n            if i:\n                write(sep)\n            write(arg)\n        write(end)\nif sys.version_info[:2] < (3, 3):\n    _print = print_\n\n    def print_(*args, **kwargs):\n        fp = kwargs.get(\"file\", sys.stdout)\n        flush = kwargs.pop(\"flush\", False)\n        _print(*args, **kwargs)\n        if flush and fp is not None:\n            fp.flush()\n\n_add_doc(reraise, \"\"\"Reraise an exception.\"\"\")\n\nif sys.version_info[0:2] < (3, 4):\n    def wraps(wrapped, assigned=functools.WRAPPER_ASSIGNMENTS,\n              updated=functools.WRAPPER_UPDATES):\n        def wrapper(f):\n            f = functools.wraps(wrapped, assigned, updated)(f)\n            f.__wrapped__ = wrapped\n            return f\n        return wrapper\nelse:\n    wraps = functools.wraps\n\n\ndef with_metaclass(meta, *bases):\n    \"\"\"Create a base class with a metaclass.\"\"\"\n    # This requires a bit of explanation: the basic idea is to make a dummy\n    # metaclass for one level of class instantiation that replaces itself with\n    # the actual metaclass.\n    class metaclass(meta):\n\n        def __new__(cls, name, this_bases, d):\n            return meta(name, bases, d)\n    return type.__new__(metaclass, 'temporary_class', (), {})\n\n\ndef add_metaclass(metaclass):\n    \"\"\"Class decorator for creating a class with a metaclass.\"\"\"\n    def wrapper(cls):\n        orig_vars = cls.__dict__.copy()\n        slots = orig_vars.get('__slots__')\n        if slots is not None:\n            if isinstance(slots, str):\n                slots = [slots]\n            for slots_var in slots:\n                orig_vars.pop(slots_var)\n        orig_vars.pop('__dict__', None)\n        orig_vars.pop('__weakref__', None)\n        return metaclass(cls.__name__, cls.__bases__, orig_vars)\n    return wrapper\n\n\ndef python_2_unicode_compatible(klass):\n    \"\"\"\n    A decorator that defines __unicode__ and __str__ methods under Python 2.\n    Under Python 3 it does nothing.\n\n    To support Python 2 and 3 with a single code base, define a __str__ method\n    returning text and apply this decorator to the class.\n    \"\"\"\n    if PY2:\n        if '__str__' not in klass.__dict__:\n            raise ValueError(\"@python_2_unicode_compatible cannot be applied \"\n                             \"to %s because it doesn't define __str__().\" %\n                             klass.__name__)\n        klass.__unicode__ = klass.__str__\n        klass.__str__ = lambda self: self.__unicode__().encode('utf-8')\n    return klass\n\n\n# Complete the moves implementation.\n# This code is at the end of this module to speed up module loading.\n# Turn this module into a package.\n__path__ = []  # required for PEP 302 and PEP 451\n__package__ = __name__  # see PEP 366 @ReservedAssignment\nif globals().get(\"__spec__\") is not None:\n    __spec__.submodule_search_locations = []  # PEP 451 @UndefinedVariable\n# Remove other six meta path importers, since they cause problems. This can\n# happen if six is removed from sys.modules and then reloaded. (Setuptools does\n# this for some reason.)\nif sys.meta_path:\n    for i, importer in enumerate(sys.meta_path):\n        # Here's some real nastiness: Another \"instance\" of the six module might\n        # be floating around. Therefore, we can't use isinstance() to check for\n        # the six meta path importer, since the other six instance will have\n        # inserted an importer with different class.\n        if (type(importer).__name__ == \"_SixMetaPathImporter\" and\n                importer.name == __name__):\n            del sys.meta_path[i]\n            break\n    del i, importer\n# Finally, add the importer to the meta path import hook.\nsys.meta_path.append(_importer)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/packages/ssl_match_hostname/__init__.py",
    "content": "import sys\n\ntry:\n    # Our match_hostname function is the same as 3.5's, so we only want to\n    # import the match_hostname function if it's at least that good.\n    if sys.version_info < (3, 5):\n        raise ImportError(\"Fallback to vendored code\")\n\n    from ssl import CertificateError, match_hostname\nexcept ImportError:\n    try:\n        # Backport of the function from a pypi module\n        from backports.ssl_match_hostname import CertificateError, match_hostname\n    except ImportError:\n        # Our vendored copy\n        from ._implementation import CertificateError, match_hostname\n\n# Not needed, but documenting what we provide.\n__all__ = ('CertificateError', 'match_hostname')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/packages/ssl_match_hostname/_implementation.py",
    "content": "\"\"\"The match_hostname() function from Python 3.3.3, essential when using SSL.\"\"\"\n\n# Note: This file is under the PSF license as the code comes from the python\n# stdlib.   http://docs.python.org/3/license.html\n\nimport re\nimport sys\n\n# ipaddress has been backported to 2.6+ in pypi.  If it is installed on the\n# system, use it to handle IPAddress ServerAltnames (this was added in\n# python-3.5) otherwise only do DNS matching.  This allows\n# backports.ssl_match_hostname to continue to be used in Python 2.7.\ntry:\n    from pip._vendor import ipaddress\nexcept ImportError:\n    ipaddress = None\n\n__version__ = '3.5.0.1'\n\n\nclass CertificateError(ValueError):\n    pass\n\n\ndef _dnsname_match(dn, hostname, max_wildcards=1):\n    \"\"\"Matching according to RFC 6125, section 6.4.3\n\n    http://tools.ietf.org/html/rfc6125#section-6.4.3\n    \"\"\"\n    pats = []\n    if not dn:\n        return False\n\n    # Ported from python3-syntax:\n    # leftmost, *remainder = dn.split(r'.')\n    parts = dn.split(r'.')\n    leftmost = parts[0]\n    remainder = parts[1:]\n\n    wildcards = leftmost.count('*')\n    if wildcards > max_wildcards:\n        # Issue #17980: avoid denials of service by refusing more\n        # than one wildcard per fragment.  A survey of established\n        # policy among SSL implementations showed it to be a\n        # reasonable choice.\n        raise CertificateError(\n            \"too many wildcards in certificate DNS name: \" + repr(dn))\n\n    # speed up common case w/o wildcards\n    if not wildcards:\n        return dn.lower() == hostname.lower()\n\n    # RFC 6125, section 6.4.3, subitem 1.\n    # The client SHOULD NOT attempt to match a presented identifier in which\n    # the wildcard character comprises a label other than the left-most label.\n    if leftmost == '*':\n        # When '*' is a fragment by itself, it matches a non-empty dotless\n        # fragment.\n        pats.append('[^.]+')\n    elif leftmost.startswith('xn--') or hostname.startswith('xn--'):\n        # RFC 6125, section 6.4.3, subitem 3.\n        # The client SHOULD NOT attempt to match a presented identifier\n        # where the wildcard character is embedded within an A-label or\n        # U-label of an internationalized domain name.\n        pats.append(re.escape(leftmost))\n    else:\n        # Otherwise, '*' matches any dotless string, e.g. www*\n        pats.append(re.escape(leftmost).replace(r'\\*', '[^.]*'))\n\n    # add the remaining fragments, ignore any wildcards\n    for frag in remainder:\n        pats.append(re.escape(frag))\n\n    pat = re.compile(r'\\A' + r'\\.'.join(pats) + r'\\Z', re.IGNORECASE)\n    return pat.match(hostname)\n\n\ndef _to_unicode(obj):\n    if isinstance(obj, str) and sys.version_info < (3,):\n        obj = unicode(obj, encoding='ascii', errors='strict')\n    return obj\n\ndef _ipaddress_match(ipname, host_ip):\n    \"\"\"Exact matching of IP addresses.\n\n    RFC 6125 explicitly doesn't define an algorithm for this\n    (section 1.7.2 - \"Out of Scope\").\n    \"\"\"\n    # OpenSSL may add a trailing newline to a subjectAltName's IP address\n    # Divergence from upstream: ipaddress can't handle byte str\n    ip = ipaddress.ip_address(_to_unicode(ipname).rstrip())\n    return ip == host_ip\n\n\ndef match_hostname(cert, hostname):\n    \"\"\"Verify that *cert* (in decoded format as returned by\n    SSLSocket.getpeercert()) matches the *hostname*.  RFC 2818 and RFC 6125\n    rules are followed, but IP addresses are not accepted for *hostname*.\n\n    CertificateError is raised on failure. On success, the function\n    returns nothing.\n    \"\"\"\n    if not cert:\n        raise ValueError(\"empty or no certificate, match_hostname needs a \"\n                         \"SSL socket or SSL context with either \"\n                         \"CERT_OPTIONAL or CERT_REQUIRED\")\n    try:\n        # Divergence from upstream: ipaddress can't handle byte str\n        host_ip = ipaddress.ip_address(_to_unicode(hostname))\n    except ValueError:\n        # Not an IP address (common case)\n        host_ip = None\n    except UnicodeError:\n        # Divergence from upstream: Have to deal with ipaddress not taking\n        # byte strings.  addresses should be all ascii, so we consider it not\n        # an ipaddress in this case\n        host_ip = None\n    except AttributeError:\n        # Divergence from upstream: Make ipaddress library optional\n        if ipaddress is None:\n            host_ip = None\n        else:\n            raise\n    dnsnames = []\n    san = cert.get('subjectAltName', ())\n    for key, value in san:\n        if key == 'DNS':\n            if host_ip is None and _dnsname_match(value, hostname):\n                return\n            dnsnames.append(value)\n        elif key == 'IP Address':\n            if host_ip is not None and _ipaddress_match(value, host_ip):\n                return\n            dnsnames.append(value)\n    if not dnsnames:\n        # The subject is only checked when there is no dNSName entry\n        # in subjectAltName\n        for sub in cert.get('subject', ()):\n            for key, value in sub:\n                # XXX according to RFC 2818, the most specific Common Name\n                # must be used.\n                if key == 'commonName':\n                    if _dnsname_match(value, hostname):\n                        return\n                    dnsnames.append(value)\n    if len(dnsnames) > 1:\n        raise CertificateError(\"hostname %r \"\n            \"doesn't match either of %s\"\n            % (hostname, ', '.join(map(repr, dnsnames))))\n    elif len(dnsnames) == 1:\n        raise CertificateError(\"hostname %r \"\n            \"doesn't match %r\"\n            % (hostname, dnsnames[0]))\n    else:\n        raise CertificateError(\"no appropriate commonName or \"\n            \"subjectAltName fields were found\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/poolmanager.py",
    "content": "from __future__ import absolute_import\nimport collections\nimport functools\nimport logging\n\nfrom ._collections import RecentlyUsedContainer\nfrom .connectionpool import HTTPConnectionPool, HTTPSConnectionPool\nfrom .connectionpool import port_by_scheme\nfrom .exceptions import LocationValueError, MaxRetryError, ProxySchemeUnknown\nfrom .packages.six.moves.urllib.parse import urljoin\nfrom .request import RequestMethods\nfrom .util.url import parse_url\nfrom .util.retry import Retry\n\n\n__all__ = ['PoolManager', 'ProxyManager', 'proxy_from_url']\n\n\nlog = logging.getLogger(__name__)\n\nSSL_KEYWORDS = ('key_file', 'cert_file', 'cert_reqs', 'ca_certs',\n                'ssl_version', 'ca_cert_dir', 'ssl_context')\n\n# All known keyword arguments that could be provided to the pool manager, its\n# pools, or the underlying connections. This is used to construct a pool key.\n_key_fields = (\n    'key_scheme',  # str\n    'key_host',  # str\n    'key_port',  # int\n    'key_timeout',  # int or float or Timeout\n    'key_retries',  # int or Retry\n    'key_strict',  # bool\n    'key_block',  # bool\n    'key_source_address',  # str\n    'key_key_file',  # str\n    'key_cert_file',  # str\n    'key_cert_reqs',  # str\n    'key_ca_certs',  # str\n    'key_ssl_version',  # str\n    'key_ca_cert_dir',  # str\n    'key_ssl_context',  # instance of ssl.SSLContext or urllib3.util.ssl_.SSLContext\n    'key_maxsize',  # int\n    'key_headers',  # dict\n    'key__proxy',  # parsed proxy url\n    'key__proxy_headers',  # dict\n    'key_socket_options',  # list of (level (int), optname (int), value (int or str)) tuples\n    'key__socks_options',  # dict\n    'key_assert_hostname',  # bool or string\n    'key_assert_fingerprint',  # str\n    'key_server_hostname', #str\n)\n\n#: The namedtuple class used to construct keys for the connection pool.\n#: All custom key schemes should include the fields in this key at a minimum.\nPoolKey = collections.namedtuple('PoolKey', _key_fields)\n\n\ndef _default_key_normalizer(key_class, request_context):\n    \"\"\"\n    Create a pool key out of a request context dictionary.\n\n    According to RFC 3986, both the scheme and host are case-insensitive.\n    Therefore, this function normalizes both before constructing the pool\n    key for an HTTPS request. If you wish to change this behaviour, provide\n    alternate callables to ``key_fn_by_scheme``.\n\n    :param key_class:\n        The class to use when constructing the key. This should be a namedtuple\n        with the ``scheme`` and ``host`` keys at a minimum.\n    :type  key_class: namedtuple\n    :param request_context:\n        A dictionary-like object that contain the context for a request.\n    :type  request_context: dict\n\n    :return: A namedtuple that can be used as a connection pool key.\n    :rtype:  PoolKey\n    \"\"\"\n    # Since we mutate the dictionary, make a copy first\n    context = request_context.copy()\n    context['scheme'] = context['scheme'].lower()\n    context['host'] = context['host'].lower()\n\n    # These are both dictionaries and need to be transformed into frozensets\n    for key in ('headers', '_proxy_headers', '_socks_options'):\n        if key in context and context[key] is not None:\n            context[key] = frozenset(context[key].items())\n\n    # The socket_options key may be a list and needs to be transformed into a\n    # tuple.\n    socket_opts = context.get('socket_options')\n    if socket_opts is not None:\n        context['socket_options'] = tuple(socket_opts)\n\n    # Map the kwargs to the names in the namedtuple - this is necessary since\n    # namedtuples can't have fields starting with '_'.\n    for key in list(context.keys()):\n        context['key_' + key] = context.pop(key)\n\n    # Default to ``None`` for keys missing from the context\n    for field in key_class._fields:\n        if field not in context:\n            context[field] = None\n\n    return key_class(**context)\n\n\n#: A dictionary that maps a scheme to a callable that creates a pool key.\n#: This can be used to alter the way pool keys are constructed, if desired.\n#: Each PoolManager makes a copy of this dictionary so they can be configured\n#: globally here, or individually on the instance.\nkey_fn_by_scheme = {\n    'http': functools.partial(_default_key_normalizer, PoolKey),\n    'https': functools.partial(_default_key_normalizer, PoolKey),\n}\n\npool_classes_by_scheme = {\n    'http': HTTPConnectionPool,\n    'https': HTTPSConnectionPool,\n}\n\n\nclass PoolManager(RequestMethods):\n    \"\"\"\n    Allows for arbitrary requests while transparently keeping track of\n    necessary connection pools for you.\n\n    :param num_pools:\n        Number of connection pools to cache before discarding the least\n        recently used pool.\n\n    :param headers:\n        Headers to include with all requests, unless other headers are given\n        explicitly.\n\n    :param \\\\**connection_pool_kw:\n        Additional parameters are used to create fresh\n        :class:`urllib3.connectionpool.ConnectionPool` instances.\n\n    Example::\n\n        >>> manager = PoolManager(num_pools=2)\n        >>> r = manager.request('GET', 'http://google.com/')\n        >>> r = manager.request('GET', 'http://google.com/mail')\n        >>> r = manager.request('GET', 'http://yahoo.com/')\n        >>> len(manager.pools)\n        2\n\n    \"\"\"\n\n    proxy = None\n\n    def __init__(self, num_pools=10, headers=None, **connection_pool_kw):\n        RequestMethods.__init__(self, headers)\n        self.connection_pool_kw = connection_pool_kw\n        self.pools = RecentlyUsedContainer(num_pools,\n                                           dispose_func=lambda p: p.close())\n\n        # Locally set the pool classes and keys so other PoolManagers can\n        # override them.\n        self.pool_classes_by_scheme = pool_classes_by_scheme\n        self.key_fn_by_scheme = key_fn_by_scheme.copy()\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        self.clear()\n        # Return False to re-raise any potential exceptions\n        return False\n\n    def _new_pool(self, scheme, host, port, request_context=None):\n        \"\"\"\n        Create a new :class:`ConnectionPool` based on host, port, scheme, and\n        any additional pool keyword arguments.\n\n        If ``request_context`` is provided, it is provided as keyword arguments\n        to the pool class used. This method is used to actually create the\n        connection pools handed out by :meth:`connection_from_url` and\n        companion methods. It is intended to be overridden for customization.\n        \"\"\"\n        pool_cls = self.pool_classes_by_scheme[scheme]\n        if request_context is None:\n            request_context = self.connection_pool_kw.copy()\n\n        # Although the context has everything necessary to create the pool,\n        # this function has historically only used the scheme, host, and port\n        # in the positional args. When an API change is acceptable these can\n        # be removed.\n        for key in ('scheme', 'host', 'port'):\n            request_context.pop(key, None)\n\n        if scheme == 'http':\n            for kw in SSL_KEYWORDS:\n                request_context.pop(kw, None)\n\n        return pool_cls(host, port, **request_context)\n\n    def clear(self):\n        \"\"\"\n        Empty our store of pools and direct them all to close.\n\n        This will not affect in-flight connections, but they will not be\n        re-used after completion.\n        \"\"\"\n        self.pools.clear()\n\n    def connection_from_host(self, host, port=None, scheme='http', pool_kwargs=None):\n        \"\"\"\n        Get a :class:`ConnectionPool` based on the host, port, and scheme.\n\n        If ``port`` isn't given, it will be derived from the ``scheme`` using\n        ``urllib3.connectionpool.port_by_scheme``. If ``pool_kwargs`` is\n        provided, it is merged with the instance's ``connection_pool_kw``\n        variable and used to create the new connection pool, if one is\n        needed.\n        \"\"\"\n\n        if not host:\n            raise LocationValueError(\"No host specified.\")\n\n        request_context = self._merge_pool_kwargs(pool_kwargs)\n        request_context['scheme'] = scheme or 'http'\n        if not port:\n            port = port_by_scheme.get(request_context['scheme'].lower(), 80)\n        request_context['port'] = port\n        request_context['host'] = host\n\n        return self.connection_from_context(request_context)\n\n    def connection_from_context(self, request_context):\n        \"\"\"\n        Get a :class:`ConnectionPool` based on the request context.\n\n        ``request_context`` must at least contain the ``scheme`` key and its\n        value must be a key in ``key_fn_by_scheme`` instance variable.\n        \"\"\"\n        scheme = request_context['scheme'].lower()\n        pool_key_constructor = self.key_fn_by_scheme[scheme]\n        pool_key = pool_key_constructor(request_context)\n\n        return self.connection_from_pool_key(pool_key, request_context=request_context)\n\n    def connection_from_pool_key(self, pool_key, request_context=None):\n        \"\"\"\n        Get a :class:`ConnectionPool` based on the provided pool key.\n\n        ``pool_key`` should be a namedtuple that only contains immutable\n        objects. At a minimum it must have the ``scheme``, ``host``, and\n        ``port`` fields.\n        \"\"\"\n        with self.pools.lock:\n            # If the scheme, host, or port doesn't match existing open\n            # connections, open a new ConnectionPool.\n            pool = self.pools.get(pool_key)\n            if pool:\n                return pool\n\n            # Make a fresh ConnectionPool of the desired type\n            scheme = request_context['scheme']\n            host = request_context['host']\n            port = request_context['port']\n            pool = self._new_pool(scheme, host, port, request_context=request_context)\n            self.pools[pool_key] = pool\n\n        return pool\n\n    def connection_from_url(self, url, pool_kwargs=None):\n        \"\"\"\n        Similar to :func:`urllib3.connectionpool.connection_from_url`.\n\n        If ``pool_kwargs`` is not provided and a new pool needs to be\n        constructed, ``self.connection_pool_kw`` is used to initialize\n        the :class:`urllib3.connectionpool.ConnectionPool`. If ``pool_kwargs``\n        is provided, it is used instead. Note that if a new pool does not\n        need to be created for the request, the provided ``pool_kwargs`` are\n        not used.\n        \"\"\"\n        u = parse_url(url)\n        return self.connection_from_host(u.host, port=u.port, scheme=u.scheme,\n                                         pool_kwargs=pool_kwargs)\n\n    def _merge_pool_kwargs(self, override):\n        \"\"\"\n        Merge a dictionary of override values for self.connection_pool_kw.\n\n        This does not modify self.connection_pool_kw and returns a new dict.\n        Any keys in the override dictionary with a value of ``None`` are\n        removed from the merged dictionary.\n        \"\"\"\n        base_pool_kwargs = self.connection_pool_kw.copy()\n        if override:\n            for key, value in override.items():\n                if value is None:\n                    try:\n                        del base_pool_kwargs[key]\n                    except KeyError:\n                        pass\n                else:\n                    base_pool_kwargs[key] = value\n        return base_pool_kwargs\n\n    def urlopen(self, method, url, redirect=True, **kw):\n        \"\"\"\n        Same as :meth:`urllib3.connectionpool.HTTPConnectionPool.urlopen`\n        with custom cross-host redirect logic and only sends the request-uri\n        portion of the ``url``.\n\n        The given ``url`` parameter must be absolute, such that an appropriate\n        :class:`urllib3.connectionpool.ConnectionPool` can be chosen for it.\n        \"\"\"\n        u = parse_url(url)\n        conn = self.connection_from_host(u.host, port=u.port, scheme=u.scheme)\n\n        kw['assert_same_host'] = False\n        kw['redirect'] = False\n\n        if 'headers' not in kw:\n            kw['headers'] = self.headers.copy()\n\n        if self.proxy is not None and u.scheme == \"http\":\n            response = conn.urlopen(method, url, **kw)\n        else:\n            response = conn.urlopen(method, u.request_uri, **kw)\n\n        redirect_location = redirect and response.get_redirect_location()\n        if not redirect_location:\n            return response\n\n        # Support relative URLs for redirecting.\n        redirect_location = urljoin(url, redirect_location)\n\n        # RFC 7231, Section 6.4.4\n        if response.status == 303:\n            method = 'GET'\n\n        retries = kw.get('retries')\n        if not isinstance(retries, Retry):\n            retries = Retry.from_int(retries, redirect=redirect)\n\n        # Strip headers marked as unsafe to forward to the redirected location.\n        # Check remove_headers_on_redirect to avoid a potential network call within\n        # conn.is_same_host() which may use socket.gethostbyname() in the future.\n        if (retries.remove_headers_on_redirect\n                and not conn.is_same_host(redirect_location)):\n            for header in retries.remove_headers_on_redirect:\n                kw['headers'].pop(header, None)\n\n        try:\n            retries = retries.increment(method, url, response=response, _pool=conn)\n        except MaxRetryError:\n            if retries.raise_on_redirect:\n                raise\n            return response\n\n        kw['retries'] = retries\n        kw['redirect'] = redirect\n\n        log.info(\"Redirecting %s -> %s\", url, redirect_location)\n        return self.urlopen(method, redirect_location, **kw)\n\n\nclass ProxyManager(PoolManager):\n    \"\"\"\n    Behaves just like :class:`PoolManager`, but sends all requests through\n    the defined proxy, using the CONNECT method for HTTPS URLs.\n\n    :param proxy_url:\n        The URL of the proxy to be used.\n\n    :param proxy_headers:\n        A dictionary containing headers that will be sent to the proxy. In case\n        of HTTP they are being sent with each request, while in the\n        HTTPS/CONNECT case they are sent only once. Could be used for proxy\n        authentication.\n\n    Example:\n        >>> proxy = urllib3.ProxyManager('http://localhost:3128/')\n        >>> r1 = proxy.request('GET', 'http://google.com/')\n        >>> r2 = proxy.request('GET', 'http://httpbin.org/')\n        >>> len(proxy.pools)\n        1\n        >>> r3 = proxy.request('GET', 'https://httpbin.org/')\n        >>> r4 = proxy.request('GET', 'https://twitter.com/')\n        >>> len(proxy.pools)\n        3\n\n    \"\"\"\n\n    def __init__(self, proxy_url, num_pools=10, headers=None,\n                 proxy_headers=None, **connection_pool_kw):\n\n        if isinstance(proxy_url, HTTPConnectionPool):\n            proxy_url = '%s://%s:%i' % (proxy_url.scheme, proxy_url.host,\n                                        proxy_url.port)\n        proxy = parse_url(proxy_url)\n        if not proxy.port:\n            port = port_by_scheme.get(proxy.scheme, 80)\n            proxy = proxy._replace(port=port)\n\n        if proxy.scheme not in (\"http\", \"https\"):\n            raise ProxySchemeUnknown(proxy.scheme)\n\n        self.proxy = proxy\n        self.proxy_headers = proxy_headers or {}\n\n        connection_pool_kw['_proxy'] = self.proxy\n        connection_pool_kw['_proxy_headers'] = self.proxy_headers\n\n        super(ProxyManager, self).__init__(\n            num_pools, headers, **connection_pool_kw)\n\n    def connection_from_host(self, host, port=None, scheme='http', pool_kwargs=None):\n        if scheme == \"https\":\n            return super(ProxyManager, self).connection_from_host(\n                host, port, scheme, pool_kwargs=pool_kwargs)\n\n        return super(ProxyManager, self).connection_from_host(\n            self.proxy.host, self.proxy.port, self.proxy.scheme, pool_kwargs=pool_kwargs)\n\n    def _set_proxy_headers(self, url, headers=None):\n        \"\"\"\n        Sets headers needed by proxies: specifically, the Accept and Host\n        headers. Only sets headers not provided by the user.\n        \"\"\"\n        headers_ = {'Accept': '*/*'}\n\n        netloc = parse_url(url).netloc\n        if netloc:\n            headers_['Host'] = netloc\n\n        if headers:\n            headers_.update(headers)\n        return headers_\n\n    def urlopen(self, method, url, redirect=True, **kw):\n        \"Same as HTTP(S)ConnectionPool.urlopen, ``url`` must be absolute.\"\n        u = parse_url(url)\n\n        if u.scheme == \"http\":\n            # For proxied HTTPS requests, httplib sets the necessary headers\n            # on the CONNECT to the proxy. For HTTP, we'll definitely\n            # need to set 'Host' at the very least.\n            headers = kw.get('headers', self.headers)\n            kw['headers'] = self._set_proxy_headers(url, headers)\n\n        return super(ProxyManager, self).urlopen(method, url, redirect=redirect, **kw)\n\n\ndef proxy_from_url(url, **kw):\n    return ProxyManager(proxy_url=url, **kw)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/request.py",
    "content": "from __future__ import absolute_import\n\nfrom .filepost import encode_multipart_formdata\nfrom .packages.six.moves.urllib.parse import urlencode\n\n\n__all__ = ['RequestMethods']\n\n\nclass RequestMethods(object):\n    \"\"\"\n    Convenience mixin for classes who implement a :meth:`urlopen` method, such\n    as :class:`~urllib3.connectionpool.HTTPConnectionPool` and\n    :class:`~urllib3.poolmanager.PoolManager`.\n\n    Provides behavior for making common types of HTTP request methods and\n    decides which type of request field encoding to use.\n\n    Specifically,\n\n    :meth:`.request_encode_url` is for sending requests whose fields are\n    encoded in the URL (such as GET, HEAD, DELETE).\n\n    :meth:`.request_encode_body` is for sending requests whose fields are\n    encoded in the *body* of the request using multipart or www-form-urlencoded\n    (such as for POST, PUT, PATCH).\n\n    :meth:`.request` is for making any kind of request, it will look up the\n    appropriate encoding format and use one of the above two methods to make\n    the request.\n\n    Initializer parameters:\n\n    :param headers:\n        Headers to include with all requests, unless other headers are given\n        explicitly.\n    \"\"\"\n\n    _encode_url_methods = {'DELETE', 'GET', 'HEAD', 'OPTIONS'}\n\n    def __init__(self, headers=None):\n        self.headers = headers or {}\n\n    def urlopen(self, method, url, body=None, headers=None,\n                encode_multipart=True, multipart_boundary=None,\n                **kw):  # Abstract\n        raise NotImplementedError(\"Classes extending RequestMethods must implement \"\n                                  \"their own ``urlopen`` method.\")\n\n    def request(self, method, url, fields=None, headers=None, **urlopen_kw):\n        \"\"\"\n        Make a request using :meth:`urlopen` with the appropriate encoding of\n        ``fields`` based on the ``method`` used.\n\n        This is a convenience method that requires the least amount of manual\n        effort. It can be used in most situations, while still having the\n        option to drop down to more specific methods when necessary, such as\n        :meth:`request_encode_url`, :meth:`request_encode_body`,\n        or even the lowest level :meth:`urlopen`.\n        \"\"\"\n        method = method.upper()\n\n        urlopen_kw['request_url'] = url\n\n        if method in self._encode_url_methods:\n            return self.request_encode_url(method, url, fields=fields,\n                                           headers=headers,\n                                           **urlopen_kw)\n        else:\n            return self.request_encode_body(method, url, fields=fields,\n                                            headers=headers,\n                                            **urlopen_kw)\n\n    def request_encode_url(self, method, url, fields=None, headers=None,\n                           **urlopen_kw):\n        \"\"\"\n        Make a request using :meth:`urlopen` with the ``fields`` encoded in\n        the url. This is useful for request methods like GET, HEAD, DELETE, etc.\n        \"\"\"\n        if headers is None:\n            headers = self.headers\n\n        extra_kw = {'headers': headers}\n        extra_kw.update(urlopen_kw)\n\n        if fields:\n            url += '?' + urlencode(fields)\n\n        return self.urlopen(method, url, **extra_kw)\n\n    def request_encode_body(self, method, url, fields=None, headers=None,\n                            encode_multipart=True, multipart_boundary=None,\n                            **urlopen_kw):\n        \"\"\"\n        Make a request using :meth:`urlopen` with the ``fields`` encoded in\n        the body. This is useful for request methods like POST, PUT, PATCH, etc.\n\n        When ``encode_multipart=True`` (default), then\n        :meth:`urllib3.filepost.encode_multipart_formdata` is used to encode\n        the payload with the appropriate content type. Otherwise\n        :meth:`urllib.urlencode` is used with the\n        'application/x-www-form-urlencoded' content type.\n\n        Multipart encoding must be used when posting files, and it's reasonably\n        safe to use it in other times too. However, it may break request\n        signing, such as with OAuth.\n\n        Supports an optional ``fields`` parameter of key/value strings AND\n        key/filetuple. A filetuple is a (filename, data, MIME type) tuple where\n        the MIME type is optional. For example::\n\n            fields = {\n                'foo': 'bar',\n                'fakefile': ('foofile.txt', 'contents of foofile'),\n                'realfile': ('barfile.txt', open('realfile').read()),\n                'typedfile': ('bazfile.bin', open('bazfile').read(),\n                              'image/jpeg'),\n                'nonamefile': 'contents of nonamefile field',\n            }\n\n        When uploading a file, providing a filename (the first parameter of the\n        tuple) is optional but recommended to best mimic behavior of browsers.\n\n        Note that if ``headers`` are supplied, the 'Content-Type' header will\n        be overwritten because it depends on the dynamic random boundary string\n        which is used to compose the body of the request. The random boundary\n        string can be explicitly set with the ``multipart_boundary`` parameter.\n        \"\"\"\n        if headers is None:\n            headers = self.headers\n\n        extra_kw = {'headers': {}}\n\n        if fields:\n            if 'body' in urlopen_kw:\n                raise TypeError(\n                    \"request got values for both 'fields' and 'body', can only specify one.\")\n\n            if encode_multipart:\n                body, content_type = encode_multipart_formdata(fields, boundary=multipart_boundary)\n            else:\n                body, content_type = urlencode(fields), 'application/x-www-form-urlencoded'\n\n            extra_kw['body'] = body\n            extra_kw['headers'] = {'Content-Type': content_type}\n\n        extra_kw['headers'].update(headers)\n        extra_kw.update(urlopen_kw)\n\n        return self.urlopen(method, url, **extra_kw)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/response.py",
    "content": "from __future__ import absolute_import\nfrom contextlib import contextmanager\nimport zlib\nimport io\nimport logging\nfrom socket import timeout as SocketTimeout\nfrom socket import error as SocketError\n\nfrom ._collections import HTTPHeaderDict\nfrom .exceptions import (\n    BodyNotHttplibCompatible, ProtocolError, DecodeError, ReadTimeoutError,\n    ResponseNotChunked, IncompleteRead, InvalidHeader\n)\nfrom .packages.six import string_types as basestring, PY3\nfrom .packages.six.moves import http_client as httplib\nfrom .connection import HTTPException, BaseSSLError\nfrom .util.response import is_fp_closed, is_response_to_head\n\nlog = logging.getLogger(__name__)\n\n\nclass DeflateDecoder(object):\n\n    def __init__(self):\n        self._first_try = True\n        self._data = b''\n        self._obj = zlib.decompressobj()\n\n    def __getattr__(self, name):\n        return getattr(self._obj, name)\n\n    def decompress(self, data):\n        if not data:\n            return data\n\n        if not self._first_try:\n            return self._obj.decompress(data)\n\n        self._data += data\n        try:\n            decompressed = self._obj.decompress(data)\n            if decompressed:\n                self._first_try = False\n                self._data = None\n            return decompressed\n        except zlib.error:\n            self._first_try = False\n            self._obj = zlib.decompressobj(-zlib.MAX_WBITS)\n            try:\n                return self.decompress(self._data)\n            finally:\n                self._data = None\n\n\nclass GzipDecoderState(object):\n\n    FIRST_MEMBER = 0\n    OTHER_MEMBERS = 1\n    SWALLOW_DATA = 2\n\n\nclass GzipDecoder(object):\n\n    def __init__(self):\n        self._obj = zlib.decompressobj(16 + zlib.MAX_WBITS)\n        self._state = GzipDecoderState.FIRST_MEMBER\n\n    def __getattr__(self, name):\n        return getattr(self._obj, name)\n\n    def decompress(self, data):\n        ret = bytearray()\n        if self._state == GzipDecoderState.SWALLOW_DATA or not data:\n            return bytes(ret)\n        while True:\n            try:\n                ret += self._obj.decompress(data)\n            except zlib.error:\n                previous_state = self._state\n                # Ignore data after the first error\n                self._state = GzipDecoderState.SWALLOW_DATA\n                if previous_state == GzipDecoderState.OTHER_MEMBERS:\n                    # Allow trailing garbage acceptable in other gzip clients\n                    return bytes(ret)\n                raise\n            data = self._obj.unused_data\n            if not data:\n                return bytes(ret)\n            self._state = GzipDecoderState.OTHER_MEMBERS\n            self._obj = zlib.decompressobj(16 + zlib.MAX_WBITS)\n\n\nclass MultiDecoder(object):\n    \"\"\"\n    From RFC7231:\n        If one or more encodings have been applied to a representation, the\n        sender that applied the encodings MUST generate a Content-Encoding\n        header field that lists the content codings in the order in which\n        they were applied.\n    \"\"\"\n\n    def __init__(self, modes):\n        self._decoders = [_get_decoder(m.strip()) for m in modes.split(',')]\n\n    def flush(self):\n        return self._decoders[0].flush()\n\n    def decompress(self, data):\n        for d in reversed(self._decoders):\n            data = d.decompress(data)\n        return data\n\n\ndef _get_decoder(mode):\n    if ',' in mode:\n        return MultiDecoder(mode)\n\n    if mode == 'gzip':\n        return GzipDecoder()\n\n    return DeflateDecoder()\n\n\nclass HTTPResponse(io.IOBase):\n    \"\"\"\n    HTTP Response container.\n\n    Backwards-compatible to httplib's HTTPResponse but the response ``body`` is\n    loaded and decoded on-demand when the ``data`` property is accessed.  This\n    class is also compatible with the Python standard library's :mod:`io`\n    module, and can hence be treated as a readable object in the context of that\n    framework.\n\n    Extra parameters for behaviour not present in httplib.HTTPResponse:\n\n    :param preload_content:\n        If True, the response's body will be preloaded during construction.\n\n    :param decode_content:\n        If True, will attempt to decode the body based on the\n        'content-encoding' header.\n\n    :param original_response:\n        When this HTTPResponse wrapper is generated from an httplib.HTTPResponse\n        object, it's convenient to include the original for debug purposes. It's\n        otherwise unused.\n\n    :param retries:\n        The retries contains the last :class:`~urllib3.util.retry.Retry` that\n        was used during the request.\n\n    :param enforce_content_length:\n        Enforce content length checking. Body returned by server must match\n        value of Content-Length header, if present. Otherwise, raise error.\n    \"\"\"\n\n    CONTENT_DECODERS = ['gzip', 'deflate']\n    REDIRECT_STATUSES = [301, 302, 303, 307, 308]\n\n    def __init__(self, body='', headers=None, status=0, version=0, reason=None,\n                 strict=0, preload_content=True, decode_content=True,\n                 original_response=None, pool=None, connection=None, msg=None,\n                 retries=None, enforce_content_length=False,\n                 request_method=None, request_url=None):\n\n        if isinstance(headers, HTTPHeaderDict):\n            self.headers = headers\n        else:\n            self.headers = HTTPHeaderDict(headers)\n        self.status = status\n        self.version = version\n        self.reason = reason\n        self.strict = strict\n        self.decode_content = decode_content\n        self.retries = retries\n        self.enforce_content_length = enforce_content_length\n\n        self._decoder = None\n        self._body = None\n        self._fp = None\n        self._original_response = original_response\n        self._fp_bytes_read = 0\n        self.msg = msg\n        self._request_url = request_url\n\n        if body and isinstance(body, (basestring, bytes)):\n            self._body = body\n\n        self._pool = pool\n        self._connection = connection\n\n        if hasattr(body, 'read'):\n            self._fp = body\n\n        # Are we using the chunked-style of transfer encoding?\n        self.chunked = False\n        self.chunk_left = None\n        tr_enc = self.headers.get('transfer-encoding', '').lower()\n        # Don't incur the penalty of creating a list and then discarding it\n        encodings = (enc.strip() for enc in tr_enc.split(\",\"))\n        if \"chunked\" in encodings:\n            self.chunked = True\n\n        # Determine length of response\n        self.length_remaining = self._init_length(request_method)\n\n        # If requested, preload the body.\n        if preload_content and not self._body:\n            self._body = self.read(decode_content=decode_content)\n\n    def get_redirect_location(self):\n        \"\"\"\n        Should we redirect and where to?\n\n        :returns: Truthy redirect location string if we got a redirect status\n            code and valid location. ``None`` if redirect status and no\n            location. ``False`` if not a redirect status code.\n        \"\"\"\n        if self.status in self.REDIRECT_STATUSES:\n            return self.headers.get('location')\n\n        return False\n\n    def release_conn(self):\n        if not self._pool or not self._connection:\n            return\n\n        self._pool._put_conn(self._connection)\n        self._connection = None\n\n    @property\n    def data(self):\n        # For backwords-compat with earlier urllib3 0.4 and earlier.\n        if self._body:\n            return self._body\n\n        if self._fp:\n            return self.read(cache_content=True)\n\n    @property\n    def connection(self):\n        return self._connection\n\n    def isclosed(self):\n        return is_fp_closed(self._fp)\n\n    def tell(self):\n        \"\"\"\n        Obtain the number of bytes pulled over the wire so far. May differ from\n        the amount of content returned by :meth:``HTTPResponse.read`` if bytes\n        are encoded on the wire (e.g, compressed).\n        \"\"\"\n        return self._fp_bytes_read\n\n    def _init_length(self, request_method):\n        \"\"\"\n        Set initial length value for Response content if available.\n        \"\"\"\n        length = self.headers.get('content-length')\n\n        if length is not None:\n            if self.chunked:\n                # This Response will fail with an IncompleteRead if it can't be\n                # received as chunked. This method falls back to attempt reading\n                # the response before raising an exception.\n                log.warning(\"Received response with both Content-Length and \"\n                            \"Transfer-Encoding set. This is expressly forbidden \"\n                            \"by RFC 7230 sec 3.3.2. Ignoring Content-Length and \"\n                            \"attempting to process response as Transfer-Encoding: \"\n                            \"chunked.\")\n                return None\n\n            try:\n                # RFC 7230 section 3.3.2 specifies multiple content lengths can\n                # be sent in a single Content-Length header\n                # (e.g. Content-Length: 42, 42). This line ensures the values\n                # are all valid ints and that as long as the `set` length is 1,\n                # all values are the same. Otherwise, the header is invalid.\n                lengths = set([int(val) for val in length.split(',')])\n                if len(lengths) > 1:\n                    raise InvalidHeader(\"Content-Length contained multiple \"\n                                        \"unmatching values (%s)\" % length)\n                length = lengths.pop()\n            except ValueError:\n                length = None\n            else:\n                if length < 0:\n                    length = None\n\n        # Convert status to int for comparison\n        # In some cases, httplib returns a status of \"_UNKNOWN\"\n        try:\n            status = int(self.status)\n        except ValueError:\n            status = 0\n\n        # Check for responses that shouldn't include a body\n        if status in (204, 304) or 100 <= status < 200 or request_method == 'HEAD':\n            length = 0\n\n        return length\n\n    def _init_decoder(self):\n        \"\"\"\n        Set-up the _decoder attribute if necessary.\n        \"\"\"\n        # Note: content-encoding value should be case-insensitive, per RFC 7230\n        # Section 3.2\n        content_encoding = self.headers.get('content-encoding', '').lower()\n        if self._decoder is None:\n            if content_encoding in self.CONTENT_DECODERS:\n                self._decoder = _get_decoder(content_encoding)\n            elif ',' in content_encoding:\n                encodings = [e.strip() for e in content_encoding.split(',') if e.strip() in self.CONTENT_DECODERS]\n                if len(encodings):\n                    self._decoder = _get_decoder(content_encoding)\n\n    def _decode(self, data, decode_content, flush_decoder):\n        \"\"\"\n        Decode the data passed in and potentially flush the decoder.\n        \"\"\"\n        try:\n            if decode_content and self._decoder:\n                data = self._decoder.decompress(data)\n        except (IOError, zlib.error) as e:\n            content_encoding = self.headers.get('content-encoding', '').lower()\n            raise DecodeError(\n                \"Received response with content-encoding: %s, but \"\n                \"failed to decode it.\" % content_encoding, e)\n\n        if flush_decoder and decode_content:\n            data += self._flush_decoder()\n\n        return data\n\n    def _flush_decoder(self):\n        \"\"\"\n        Flushes the decoder. Should only be called if the decoder is actually\n        being used.\n        \"\"\"\n        if self._decoder:\n            buf = self._decoder.decompress(b'')\n            return buf + self._decoder.flush()\n\n        return b''\n\n    @contextmanager\n    def _error_catcher(self):\n        \"\"\"\n        Catch low-level python exceptions, instead re-raising urllib3\n        variants, so that low-level exceptions are not leaked in the\n        high-level api.\n\n        On exit, release the connection back to the pool.\n        \"\"\"\n        clean_exit = False\n\n        try:\n            try:\n                yield\n\n            except SocketTimeout:\n                # FIXME: Ideally we'd like to include the url in the ReadTimeoutError but\n                # there is yet no clean way to get at it from this context.\n                raise ReadTimeoutError(self._pool, None, 'Read timed out.')\n\n            except BaseSSLError as e:\n                # FIXME: Is there a better way to differentiate between SSLErrors?\n                if 'read operation timed out' not in str(e):  # Defensive:\n                    # This shouldn't happen but just in case we're missing an edge\n                    # case, let's avoid swallowing SSL errors.\n                    raise\n\n                raise ReadTimeoutError(self._pool, None, 'Read timed out.')\n\n            except (HTTPException, SocketError) as e:\n                # This includes IncompleteRead.\n                raise ProtocolError('Connection broken: %r' % e, e)\n\n            # If no exception is thrown, we should avoid cleaning up\n            # unnecessarily.\n            clean_exit = True\n        finally:\n            # If we didn't terminate cleanly, we need to throw away our\n            # connection.\n            if not clean_exit:\n                # The response may not be closed but we're not going to use it\n                # anymore so close it now to ensure that the connection is\n                # released back to the pool.\n                if self._original_response:\n                    self._original_response.close()\n\n                # Closing the response may not actually be sufficient to close\n                # everything, so if we have a hold of the connection close that\n                # too.\n                if self._connection:\n                    self._connection.close()\n\n            # If we hold the original response but it's closed now, we should\n            # return the connection back to the pool.\n            if self._original_response and self._original_response.isclosed():\n                self.release_conn()\n\n    def read(self, amt=None, decode_content=None, cache_content=False):\n        \"\"\"\n        Similar to :meth:`httplib.HTTPResponse.read`, but with two additional\n        parameters: ``decode_content`` and ``cache_content``.\n\n        :param amt:\n            How much of the content to read. If specified, caching is skipped\n            because it doesn't make sense to cache partial content as the full\n            response.\n\n        :param decode_content:\n            If True, will attempt to decode the body based on the\n            'content-encoding' header.\n\n        :param cache_content:\n            If True, will save the returned data such that the same result is\n            returned despite of the state of the underlying file object. This\n            is useful if you want the ``.data`` property to continue working\n            after having ``.read()`` the file object. (Overridden if ``amt`` is\n            set.)\n        \"\"\"\n        self._init_decoder()\n        if decode_content is None:\n            decode_content = self.decode_content\n\n        if self._fp is None:\n            return\n\n        flush_decoder = False\n        data = None\n\n        with self._error_catcher():\n            if amt is None:\n                # cStringIO doesn't like amt=None\n                data = self._fp.read()\n                flush_decoder = True\n            else:\n                cache_content = False\n                data = self._fp.read(amt)\n                if amt != 0 and not data:  # Platform-specific: Buggy versions of Python.\n                    # Close the connection when no data is returned\n                    #\n                    # This is redundant to what httplib/http.client _should_\n                    # already do.  However, versions of python released before\n                    # December 15, 2012 (http://bugs.python.org/issue16298) do\n                    # not properly close the connection in all cases. There is\n                    # no harm in redundantly calling close.\n                    self._fp.close()\n                    flush_decoder = True\n                    if self.enforce_content_length and self.length_remaining not in (0, None):\n                        # This is an edge case that httplib failed to cover due\n                        # to concerns of backward compatibility. We're\n                        # addressing it here to make sure IncompleteRead is\n                        # raised during streaming, so all calls with incorrect\n                        # Content-Length are caught.\n                        raise IncompleteRead(self._fp_bytes_read, self.length_remaining)\n\n        if data:\n            self._fp_bytes_read += len(data)\n            if self.length_remaining is not None:\n                self.length_remaining -= len(data)\n\n            data = self._decode(data, decode_content, flush_decoder)\n\n            if cache_content:\n                self._body = data\n\n        return data\n\n    def stream(self, amt=2**16, decode_content=None):\n        \"\"\"\n        A generator wrapper for the read() method. A call will block until\n        ``amt`` bytes have been read from the connection or until the\n        connection is closed.\n\n        :param amt:\n            How much of the content to read. The generator will return up to\n            much data per iteration, but may return less. This is particularly\n            likely when using compressed data. However, the empty string will\n            never be returned.\n\n        :param decode_content:\n            If True, will attempt to decode the body based on the\n            'content-encoding' header.\n        \"\"\"\n        if self.chunked and self.supports_chunked_reads():\n            for line in self.read_chunked(amt, decode_content=decode_content):\n                yield line\n        else:\n            while not is_fp_closed(self._fp):\n                data = self.read(amt=amt, decode_content=decode_content)\n\n                if data:\n                    yield data\n\n    @classmethod\n    def from_httplib(ResponseCls, r, **response_kw):\n        \"\"\"\n        Given an :class:`httplib.HTTPResponse` instance ``r``, return a\n        corresponding :class:`urllib3.response.HTTPResponse` object.\n\n        Remaining parameters are passed to the HTTPResponse constructor, along\n        with ``original_response=r``.\n        \"\"\"\n        headers = r.msg\n\n        if not isinstance(headers, HTTPHeaderDict):\n            if PY3:  # Python 3\n                headers = HTTPHeaderDict(headers.items())\n            else:  # Python 2\n                headers = HTTPHeaderDict.from_httplib(headers)\n\n        # HTTPResponse objects in Python 3 don't have a .strict attribute\n        strict = getattr(r, 'strict', 0)\n        resp = ResponseCls(body=r,\n                           headers=headers,\n                           status=r.status,\n                           version=r.version,\n                           reason=r.reason,\n                           strict=strict,\n                           original_response=r,\n                           **response_kw)\n        return resp\n\n    # Backwards-compatibility methods for httplib.HTTPResponse\n    def getheaders(self):\n        return self.headers\n\n    def getheader(self, name, default=None):\n        return self.headers.get(name, default)\n\n    # Backwards compatibility for http.cookiejar\n    def info(self):\n        return self.headers\n\n    # Overrides from io.IOBase\n    def close(self):\n        if not self.closed:\n            self._fp.close()\n\n        if self._connection:\n            self._connection.close()\n\n    @property\n    def closed(self):\n        if self._fp is None:\n            return True\n        elif hasattr(self._fp, 'isclosed'):\n            return self._fp.isclosed()\n        elif hasattr(self._fp, 'closed'):\n            return self._fp.closed\n        else:\n            return True\n\n    def fileno(self):\n        if self._fp is None:\n            raise IOError(\"HTTPResponse has no file to get a fileno from\")\n        elif hasattr(self._fp, \"fileno\"):\n            return self._fp.fileno()\n        else:\n            raise IOError(\"The file-like object this HTTPResponse is wrapped \"\n                          \"around has no file descriptor\")\n\n    def flush(self):\n        if self._fp is not None and hasattr(self._fp, 'flush'):\n            return self._fp.flush()\n\n    def readable(self):\n        # This method is required for `io` module compatibility.\n        return True\n\n    def readinto(self, b):\n        # This method is required for `io` module compatibility.\n        temp = self.read(len(b))\n        if len(temp) == 0:\n            return 0\n        else:\n            b[:len(temp)] = temp\n            return len(temp)\n\n    def supports_chunked_reads(self):\n        \"\"\"\n        Checks if the underlying file-like object looks like a\n        httplib.HTTPResponse object. We do this by testing for the fp\n        attribute. If it is present we assume it returns raw chunks as\n        processed by read_chunked().\n        \"\"\"\n        return hasattr(self._fp, 'fp')\n\n    def _update_chunk_length(self):\n        # First, we'll figure out length of a chunk and then\n        # we'll try to read it from socket.\n        if self.chunk_left is not None:\n            return\n        line = self._fp.fp.readline()\n        line = line.split(b';', 1)[0]\n        try:\n            self.chunk_left = int(line, 16)\n        except ValueError:\n            # Invalid chunked protocol response, abort.\n            self.close()\n            raise httplib.IncompleteRead(line)\n\n    def _handle_chunk(self, amt):\n        returned_chunk = None\n        if amt is None:\n            chunk = self._fp._safe_read(self.chunk_left)\n            returned_chunk = chunk\n            self._fp._safe_read(2)  # Toss the CRLF at the end of the chunk.\n            self.chunk_left = None\n        elif amt < self.chunk_left:\n            value = self._fp._safe_read(amt)\n            self.chunk_left = self.chunk_left - amt\n            returned_chunk = value\n        elif amt == self.chunk_left:\n            value = self._fp._safe_read(amt)\n            self._fp._safe_read(2)  # Toss the CRLF at the end of the chunk.\n            self.chunk_left = None\n            returned_chunk = value\n        else:  # amt > self.chunk_left\n            returned_chunk = self._fp._safe_read(self.chunk_left)\n            self._fp._safe_read(2)  # Toss the CRLF at the end of the chunk.\n            self.chunk_left = None\n        return returned_chunk\n\n    def read_chunked(self, amt=None, decode_content=None):\n        \"\"\"\n        Similar to :meth:`HTTPResponse.read`, but with an additional\n        parameter: ``decode_content``.\n\n        :param amt:\n            How much of the content to read. If specified, caching is skipped\n            because it doesn't make sense to cache partial content as the full\n            response.\n\n        :param decode_content:\n            If True, will attempt to decode the body based on the\n            'content-encoding' header.\n        \"\"\"\n        self._init_decoder()\n        # FIXME: Rewrite this method and make it a class with a better structured logic.\n        if not self.chunked:\n            raise ResponseNotChunked(\n                \"Response is not chunked. \"\n                \"Header 'transfer-encoding: chunked' is missing.\")\n        if not self.supports_chunked_reads():\n            raise BodyNotHttplibCompatible(\n                \"Body should be httplib.HTTPResponse like. \"\n                \"It should have have an fp attribute which returns raw chunks.\")\n\n        with self._error_catcher():\n            # Don't bother reading the body of a HEAD request.\n            if self._original_response and is_response_to_head(self._original_response):\n                self._original_response.close()\n                return\n\n            # If a response is already read and closed\n            # then return immediately.\n            if self._fp.fp is None:\n                return\n\n            while True:\n                self._update_chunk_length()\n                if self.chunk_left == 0:\n                    break\n                chunk = self._handle_chunk(amt)\n                decoded = self._decode(chunk, decode_content=decode_content,\n                                       flush_decoder=False)\n                if decoded:\n                    yield decoded\n\n            if decode_content:\n                # On CPython and PyPy, we should never need to flush the\n                # decoder. However, on Jython we *might* need to, so\n                # lets defensively do it anyway.\n                decoded = self._flush_decoder()\n                if decoded:  # Platform-specific: Jython.\n                    yield decoded\n\n            # Chunk content ends with \\r\\n: discard it.\n            while True:\n                line = self._fp.fp.readline()\n                if not line:\n                    # Some sites may not end with '\\r\\n'.\n                    break\n                if line == b'\\r\\n':\n                    break\n\n            # We read everything; close the \"file\".\n            if self._original_response:\n                self._original_response.close()\n\n    def geturl(self):\n        \"\"\"\n        Returns the URL that was the source of this response.\n        If the request that generated this response redirected, this method\n        will return the final redirect location.\n        \"\"\"\n        if self.retries is not None and len(self.retries.history):\n            return self.retries.history[-1].redirect_location\n        else:\n            return self._request_url\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/util/__init__.py",
    "content": "from __future__ import absolute_import\n# For backwards compatibility, provide imports that used to be here.\nfrom .connection import is_connection_dropped\nfrom .request import make_headers\nfrom .response import is_fp_closed\nfrom .ssl_ import (\n    SSLContext,\n    HAS_SNI,\n    IS_PYOPENSSL,\n    IS_SECURETRANSPORT,\n    assert_fingerprint,\n    resolve_cert_reqs,\n    resolve_ssl_version,\n    ssl_wrap_socket,\n)\nfrom .timeout import (\n    current_time,\n    Timeout,\n)\n\nfrom .retry import Retry\nfrom .url import (\n    get_host,\n    parse_url,\n    split_first,\n    Url,\n)\nfrom .wait import (\n    wait_for_read,\n    wait_for_write\n)\n\n__all__ = (\n    'HAS_SNI',\n    'IS_PYOPENSSL',\n    'IS_SECURETRANSPORT',\n    'SSLContext',\n    'Retry',\n    'Timeout',\n    'Url',\n    'assert_fingerprint',\n    'current_time',\n    'is_connection_dropped',\n    'is_fp_closed',\n    'get_host',\n    'parse_url',\n    'make_headers',\n    'resolve_cert_reqs',\n    'resolve_ssl_version',\n    'split_first',\n    'ssl_wrap_socket',\n    'wait_for_read',\n    'wait_for_write'\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/util/connection.py",
    "content": "from __future__ import absolute_import\nimport socket\nfrom .wait import NoWayToWaitForSocketError, wait_for_read\nfrom ..contrib import _appengine_environ\n\n\ndef is_connection_dropped(conn):  # Platform-specific\n    \"\"\"\n    Returns True if the connection is dropped and should be closed.\n\n    :param conn:\n        :class:`httplib.HTTPConnection` object.\n\n    Note: For platforms like AppEngine, this will always return ``False`` to\n    let the platform handle connection recycling transparently for us.\n    \"\"\"\n    sock = getattr(conn, 'sock', False)\n    if sock is False:  # Platform-specific: AppEngine\n        return False\n    if sock is None:  # Connection already closed (such as by httplib).\n        return True\n    try:\n        # Returns True if readable, which here means it's been dropped\n        return wait_for_read(sock, timeout=0.0)\n    except NoWayToWaitForSocketError:  # Platform-specific: AppEngine\n        return False\n\n\n# This function is copied from socket.py in the Python 2.7 standard\n# library test suite. Added to its signature is only `socket_options`.\n# One additional modification is that we avoid binding to IPv6 servers\n# discovered in DNS if the system doesn't have IPv6 functionality.\ndef create_connection(address, timeout=socket._GLOBAL_DEFAULT_TIMEOUT,\n                      source_address=None, socket_options=None):\n    \"\"\"Connect to *address* and return the socket object.\n\n    Convenience function.  Connect to *address* (a 2-tuple ``(host,\n    port)``) and return the socket object.  Passing the optional\n    *timeout* parameter will set the timeout on the socket instance\n    before attempting to connect.  If no *timeout* is supplied, the\n    global default timeout setting returned by :func:`getdefaulttimeout`\n    is used.  If *source_address* is set it must be a tuple of (host, port)\n    for the socket to bind as a source address before making the connection.\n    An host of '' or port 0 tells the OS to use the default.\n    \"\"\"\n\n    host, port = address\n    if host.startswith('['):\n        host = host.strip('[]')\n    err = None\n\n    # Using the value from allowed_gai_family() in the context of getaddrinfo lets\n    # us select whether to work with IPv4 DNS records, IPv6 records, or both.\n    # The original create_connection function always returns all records.\n    family = allowed_gai_family()\n\n    for res in socket.getaddrinfo(host, port, family, socket.SOCK_STREAM):\n        af, socktype, proto, canonname, sa = res\n        sock = None\n        try:\n            sock = socket.socket(af, socktype, proto)\n\n            # If provided, set socket level options before connecting.\n            _set_socket_options(sock, socket_options)\n\n            if timeout is not socket._GLOBAL_DEFAULT_TIMEOUT:\n                sock.settimeout(timeout)\n            if source_address:\n                sock.bind(source_address)\n            sock.connect(sa)\n            return sock\n\n        except socket.error as e:\n            err = e\n            if sock is not None:\n                sock.close()\n                sock = None\n\n    if err is not None:\n        raise err\n\n    raise socket.error(\"getaddrinfo returns an empty list\")\n\n\ndef _set_socket_options(sock, options):\n    if options is None:\n        return\n\n    for opt in options:\n        sock.setsockopt(*opt)\n\n\ndef allowed_gai_family():\n    \"\"\"This function is designed to work in the context of\n    getaddrinfo, where family=socket.AF_UNSPEC is the default and\n    will perform a DNS search for both IPv6 and IPv4 records.\"\"\"\n\n    family = socket.AF_INET\n    if HAS_IPV6:\n        family = socket.AF_UNSPEC\n    return family\n\n\ndef _has_ipv6(host):\n    \"\"\" Returns True if the system can bind an IPv6 address. \"\"\"\n    sock = None\n    has_ipv6 = False\n\n    # App Engine doesn't support IPV6 sockets and actually has a quota on the\n    # number of sockets that can be used, so just early out here instead of\n    # creating a socket needlessly.\n    # See https://github.com/urllib3/urllib3/issues/1446\n    if _appengine_environ.is_appengine_sandbox():\n        return False\n\n    if socket.has_ipv6:\n        # has_ipv6 returns true if cPython was compiled with IPv6 support.\n        # It does not tell us if the system has IPv6 support enabled. To\n        # determine that we must bind to an IPv6 address.\n        # https://github.com/shazow/urllib3/pull/611\n        # https://bugs.python.org/issue658327\n        try:\n            sock = socket.socket(socket.AF_INET6)\n            sock.bind((host, 0))\n            has_ipv6 = True\n        except Exception:\n            pass\n\n    if sock:\n        sock.close()\n    return has_ipv6\n\n\nHAS_IPV6 = _has_ipv6('::1')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/util/queue.py",
    "content": "import collections\nfrom ..packages import six\nfrom ..packages.six.moves import queue\n\nif six.PY2:\n    # Queue is imported for side effects on MS Windows. See issue #229.\n    import Queue as _unused_module_Queue  # noqa: F401\n\n\nclass LifoQueue(queue.Queue):\n    def _init(self, _):\n        self.queue = collections.deque()\n\n    def _qsize(self, len=len):\n        return len(self.queue)\n\n    def _put(self, item):\n        self.queue.append(item)\n\n    def _get(self):\n        return self.queue.pop()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/util/request.py",
    "content": "from __future__ import absolute_import\nfrom base64 import b64encode\n\nfrom ..packages.six import b, integer_types\nfrom ..exceptions import UnrewindableBodyError\n\nACCEPT_ENCODING = 'gzip,deflate'\n_FAILEDTELL = object()\n\n\ndef make_headers(keep_alive=None, accept_encoding=None, user_agent=None,\n                 basic_auth=None, proxy_basic_auth=None, disable_cache=None):\n    \"\"\"\n    Shortcuts for generating request headers.\n\n    :param keep_alive:\n        If ``True``, adds 'connection: keep-alive' header.\n\n    :param accept_encoding:\n        Can be a boolean, list, or string.\n        ``True`` translates to 'gzip,deflate'.\n        List will get joined by comma.\n        String will be used as provided.\n\n    :param user_agent:\n        String representing the user-agent you want, such as\n        \"python-urllib3/0.6\"\n\n    :param basic_auth:\n        Colon-separated username:password string for 'authorization: basic ...'\n        auth header.\n\n    :param proxy_basic_auth:\n        Colon-separated username:password string for 'proxy-authorization: basic ...'\n        auth header.\n\n    :param disable_cache:\n        If ``True``, adds 'cache-control: no-cache' header.\n\n    Example::\n\n        >>> make_headers(keep_alive=True, user_agent=\"Batman/1.0\")\n        {'connection': 'keep-alive', 'user-agent': 'Batman/1.0'}\n        >>> make_headers(accept_encoding=True)\n        {'accept-encoding': 'gzip,deflate'}\n    \"\"\"\n    headers = {}\n    if accept_encoding:\n        if isinstance(accept_encoding, str):\n            pass\n        elif isinstance(accept_encoding, list):\n            accept_encoding = ','.join(accept_encoding)\n        else:\n            accept_encoding = ACCEPT_ENCODING\n        headers['accept-encoding'] = accept_encoding\n\n    if user_agent:\n        headers['user-agent'] = user_agent\n\n    if keep_alive:\n        headers['connection'] = 'keep-alive'\n\n    if basic_auth:\n        headers['authorization'] = 'Basic ' + \\\n            b64encode(b(basic_auth)).decode('utf-8')\n\n    if proxy_basic_auth:\n        headers['proxy-authorization'] = 'Basic ' + \\\n            b64encode(b(proxy_basic_auth)).decode('utf-8')\n\n    if disable_cache:\n        headers['cache-control'] = 'no-cache'\n\n    return headers\n\n\ndef set_file_position(body, pos):\n    \"\"\"\n    If a position is provided, move file to that point.\n    Otherwise, we'll attempt to record a position for future use.\n    \"\"\"\n    if pos is not None:\n        rewind_body(body, pos)\n    elif getattr(body, 'tell', None) is not None:\n        try:\n            pos = body.tell()\n        except (IOError, OSError):\n            # This differentiates from None, allowing us to catch\n            # a failed `tell()` later when trying to rewind the body.\n            pos = _FAILEDTELL\n\n    return pos\n\n\ndef rewind_body(body, body_pos):\n    \"\"\"\n    Attempt to rewind body to a certain position.\n    Primarily used for request redirects and retries.\n\n    :param body:\n        File-like object that supports seek.\n\n    :param int pos:\n        Position to seek to in file.\n    \"\"\"\n    body_seek = getattr(body, 'seek', None)\n    if body_seek is not None and isinstance(body_pos, integer_types):\n        try:\n            body_seek(body_pos)\n        except (IOError, OSError):\n            raise UnrewindableBodyError(\"An error occurred when rewinding request \"\n                                        \"body for redirect/retry.\")\n    elif body_pos is _FAILEDTELL:\n        raise UnrewindableBodyError(\"Unable to record file position for rewinding \"\n                                    \"request body during a redirect/retry.\")\n    else:\n        raise ValueError(\"body_pos must be of type integer, \"\n                         \"instead it was %s.\" % type(body_pos))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/util/response.py",
    "content": "from __future__ import absolute_import\nfrom ..packages.six.moves import http_client as httplib\n\nfrom ..exceptions import HeaderParsingError\n\n\ndef is_fp_closed(obj):\n    \"\"\"\n    Checks whether a given file-like object is closed.\n\n    :param obj:\n        The file-like object to check.\n    \"\"\"\n\n    try:\n        # Check `isclosed()` first, in case Python3 doesn't set `closed`.\n        # GH Issue #928\n        return obj.isclosed()\n    except AttributeError:\n        pass\n\n    try:\n        # Check via the official file-like-object way.\n        return obj.closed\n    except AttributeError:\n        pass\n\n    try:\n        # Check if the object is a container for another file-like object that\n        # gets released on exhaustion (e.g. HTTPResponse).\n        return obj.fp is None\n    except AttributeError:\n        pass\n\n    raise ValueError(\"Unable to determine whether fp is closed.\")\n\n\ndef assert_header_parsing(headers):\n    \"\"\"\n    Asserts whether all headers have been successfully parsed.\n    Extracts encountered errors from the result of parsing headers.\n\n    Only works on Python 3.\n\n    :param headers: Headers to verify.\n    :type headers: `httplib.HTTPMessage`.\n\n    :raises urllib3.exceptions.HeaderParsingError:\n        If parsing errors are found.\n    \"\"\"\n\n    # This will fail silently if we pass in the wrong kind of parameter.\n    # To make debugging easier add an explicit check.\n    if not isinstance(headers, httplib.HTTPMessage):\n        raise TypeError('expected httplib.Message, got {0}.'.format(\n            type(headers)))\n\n    defects = getattr(headers, 'defects', None)\n    get_payload = getattr(headers, 'get_payload', None)\n\n    unparsed_data = None\n    if get_payload:\n        # get_payload is actually email.message.Message.get_payload;\n        # we're only interested in the result if it's not a multipart message\n        if not headers.is_multipart():\n            payload = get_payload()\n\n            if isinstance(payload, (bytes, str)):\n                unparsed_data = payload\n\n    if defects or unparsed_data:\n        raise HeaderParsingError(defects=defects, unparsed_data=unparsed_data)\n\n\ndef is_response_to_head(response):\n    \"\"\"\n    Checks whether the request of a response has been a HEAD-request.\n    Handles the quirks of AppEngine.\n\n    :param conn:\n    :type conn: :class:`httplib.HTTPResponse`\n    \"\"\"\n    # FIXME: Can we do this somehow without accessing private httplib _method?\n    method = response._method\n    if isinstance(method, int):  # Platform-specific: Appengine\n        return method == 3\n    return method.upper() == 'HEAD'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/util/retry.py",
    "content": "from __future__ import absolute_import\nimport time\nimport logging\nfrom collections import namedtuple\nfrom itertools import takewhile\nimport email\nimport re\n\nfrom ..exceptions import (\n    ConnectTimeoutError,\n    MaxRetryError,\n    ProtocolError,\n    ReadTimeoutError,\n    ResponseError,\n    InvalidHeader,\n)\nfrom ..packages import six\n\n\nlog = logging.getLogger(__name__)\n\n\n# Data structure for representing the metadata of requests that result in a retry.\nRequestHistory = namedtuple('RequestHistory', [\"method\", \"url\", \"error\",\n                                               \"status\", \"redirect_location\"])\n\n\nclass Retry(object):\n    \"\"\" Retry configuration.\n\n    Each retry attempt will create a new Retry object with updated values, so\n    they can be safely reused.\n\n    Retries can be defined as a default for a pool::\n\n        retries = Retry(connect=5, read=2, redirect=5)\n        http = PoolManager(retries=retries)\n        response = http.request('GET', 'http://example.com/')\n\n    Or per-request (which overrides the default for the pool)::\n\n        response = http.request('GET', 'http://example.com/', retries=Retry(10))\n\n    Retries can be disabled by passing ``False``::\n\n        response = http.request('GET', 'http://example.com/', retries=False)\n\n    Errors will be wrapped in :class:`~urllib3.exceptions.MaxRetryError` unless\n    retries are disabled, in which case the causing exception will be raised.\n\n    :param int total:\n        Total number of retries to allow. Takes precedence over other counts.\n\n        Set to ``None`` to remove this constraint and fall back on other\n        counts. It's a good idea to set this to some sensibly-high value to\n        account for unexpected edge cases and avoid infinite retry loops.\n\n        Set to ``0`` to fail on the first retry.\n\n        Set to ``False`` to disable and imply ``raise_on_redirect=False``.\n\n    :param int connect:\n        How many connection-related errors to retry on.\n\n        These are errors raised before the request is sent to the remote server,\n        which we assume has not triggered the server to process the request.\n\n        Set to ``0`` to fail on the first retry of this type.\n\n    :param int read:\n        How many times to retry on read errors.\n\n        These errors are raised after the request was sent to the server, so the\n        request may have side-effects.\n\n        Set to ``0`` to fail on the first retry of this type.\n\n    :param int redirect:\n        How many redirects to perform. Limit this to avoid infinite redirect\n        loops.\n\n        A redirect is a HTTP response with a status code 301, 302, 303, 307 or\n        308.\n\n        Set to ``0`` to fail on the first retry of this type.\n\n        Set to ``False`` to disable and imply ``raise_on_redirect=False``.\n\n    :param int status:\n        How many times to retry on bad status codes.\n\n        These are retries made on responses, where status code matches\n        ``status_forcelist``.\n\n        Set to ``0`` to fail on the first retry of this type.\n\n    :param iterable method_whitelist:\n        Set of uppercased HTTP method verbs that we should retry on.\n\n        By default, we only retry on methods which are considered to be\n        idempotent (multiple requests with the same parameters end with the\n        same state). See :attr:`Retry.DEFAULT_METHOD_WHITELIST`.\n\n        Set to a ``False`` value to retry on any verb.\n\n    :param iterable status_forcelist:\n        A set of integer HTTP status codes that we should force a retry on.\n        A retry is initiated if the request method is in ``method_whitelist``\n        and the response status code is in ``status_forcelist``.\n\n        By default, this is disabled with ``None``.\n\n    :param float backoff_factor:\n        A backoff factor to apply between attempts after the second try\n        (most errors are resolved immediately by a second try without a\n        delay). urllib3 will sleep for::\n\n            {backoff factor} * (2 ** ({number of total retries} - 1))\n\n        seconds. If the backoff_factor is 0.1, then :func:`.sleep` will sleep\n        for [0.0s, 0.2s, 0.4s, ...] between retries. It will never be longer\n        than :attr:`Retry.BACKOFF_MAX`.\n\n        By default, backoff is disabled (set to 0).\n\n    :param bool raise_on_redirect: Whether, if the number of redirects is\n        exhausted, to raise a MaxRetryError, or to return a response with a\n        response code in the 3xx range.\n\n    :param bool raise_on_status: Similar meaning to ``raise_on_redirect``:\n        whether we should raise an exception, or return a response,\n        if status falls in ``status_forcelist`` range and retries have\n        been exhausted.\n\n    :param tuple history: The history of the request encountered during\n        each call to :meth:`~Retry.increment`. The list is in the order\n        the requests occurred. Each list item is of class :class:`RequestHistory`.\n\n    :param bool respect_retry_after_header:\n        Whether to respect Retry-After header on status codes defined as\n        :attr:`Retry.RETRY_AFTER_STATUS_CODES` or not.\n\n    :param iterable remove_headers_on_redirect:\n        Sequence of headers to remove from the request when a response\n        indicating a redirect is returned before firing off the redirected\n        request.\n    \"\"\"\n\n    DEFAULT_METHOD_WHITELIST = frozenset([\n        'HEAD', 'GET', 'PUT', 'DELETE', 'OPTIONS', 'TRACE'])\n\n    RETRY_AFTER_STATUS_CODES = frozenset([413, 429, 503])\n\n    DEFAULT_REDIRECT_HEADERS_BLACKLIST = frozenset(['Authorization'])\n\n    #: Maximum backoff time.\n    BACKOFF_MAX = 120\n\n    def __init__(self, total=10, connect=None, read=None, redirect=None, status=None,\n                 method_whitelist=DEFAULT_METHOD_WHITELIST, status_forcelist=None,\n                 backoff_factor=0, raise_on_redirect=True, raise_on_status=True,\n                 history=None, respect_retry_after_header=True,\n                 remove_headers_on_redirect=DEFAULT_REDIRECT_HEADERS_BLACKLIST):\n\n        self.total = total\n        self.connect = connect\n        self.read = read\n        self.status = status\n\n        if redirect is False or total is False:\n            redirect = 0\n            raise_on_redirect = False\n\n        self.redirect = redirect\n        self.status_forcelist = status_forcelist or set()\n        self.method_whitelist = method_whitelist\n        self.backoff_factor = backoff_factor\n        self.raise_on_redirect = raise_on_redirect\n        self.raise_on_status = raise_on_status\n        self.history = history or tuple()\n        self.respect_retry_after_header = respect_retry_after_header\n        self.remove_headers_on_redirect = remove_headers_on_redirect\n\n    def new(self, **kw):\n        params = dict(\n            total=self.total,\n            connect=self.connect, read=self.read, redirect=self.redirect, status=self.status,\n            method_whitelist=self.method_whitelist,\n            status_forcelist=self.status_forcelist,\n            backoff_factor=self.backoff_factor,\n            raise_on_redirect=self.raise_on_redirect,\n            raise_on_status=self.raise_on_status,\n            history=self.history,\n            remove_headers_on_redirect=self.remove_headers_on_redirect\n        )\n        params.update(kw)\n        return type(self)(**params)\n\n    @classmethod\n    def from_int(cls, retries, redirect=True, default=None):\n        \"\"\" Backwards-compatibility for the old retries format.\"\"\"\n        if retries is None:\n            retries = default if default is not None else cls.DEFAULT\n\n        if isinstance(retries, Retry):\n            return retries\n\n        redirect = bool(redirect) and None\n        new_retries = cls(retries, redirect=redirect)\n        log.debug(\"Converted retries value: %r -> %r\", retries, new_retries)\n        return new_retries\n\n    def get_backoff_time(self):\n        \"\"\" Formula for computing the current backoff\n\n        :rtype: float\n        \"\"\"\n        # We want to consider only the last consecutive errors sequence (Ignore redirects).\n        consecutive_errors_len = len(list(takewhile(lambda x: x.redirect_location is None,\n                                                    reversed(self.history))))\n        if consecutive_errors_len <= 1:\n            return 0\n\n        backoff_value = self.backoff_factor * (2 ** (consecutive_errors_len - 1))\n        return min(self.BACKOFF_MAX, backoff_value)\n\n    def parse_retry_after(self, retry_after):\n        # Whitespace: https://tools.ietf.org/html/rfc7230#section-3.2.4\n        if re.match(r\"^\\s*[0-9]+\\s*$\", retry_after):\n            seconds = int(retry_after)\n        else:\n            retry_date_tuple = email.utils.parsedate(retry_after)\n            if retry_date_tuple is None:\n                raise InvalidHeader(\"Invalid Retry-After header: %s\" % retry_after)\n            retry_date = time.mktime(retry_date_tuple)\n            seconds = retry_date - time.time()\n\n        if seconds < 0:\n            seconds = 0\n\n        return seconds\n\n    def get_retry_after(self, response):\n        \"\"\" Get the value of Retry-After in seconds. \"\"\"\n\n        retry_after = response.getheader(\"Retry-After\")\n\n        if retry_after is None:\n            return None\n\n        return self.parse_retry_after(retry_after)\n\n    def sleep_for_retry(self, response=None):\n        retry_after = self.get_retry_after(response)\n        if retry_after:\n            time.sleep(retry_after)\n            return True\n\n        return False\n\n    def _sleep_backoff(self):\n        backoff = self.get_backoff_time()\n        if backoff <= 0:\n            return\n        time.sleep(backoff)\n\n    def sleep(self, response=None):\n        \"\"\" Sleep between retry attempts.\n\n        This method will respect a server's ``Retry-After`` response header\n        and sleep the duration of the time requested. If that is not present, it\n        will use an exponential backoff. By default, the backoff factor is 0 and\n        this method will return immediately.\n        \"\"\"\n\n        if response:\n            slept = self.sleep_for_retry(response)\n            if slept:\n                return\n\n        self._sleep_backoff()\n\n    def _is_connection_error(self, err):\n        \"\"\" Errors when we're fairly sure that the server did not receive the\n        request, so it should be safe to retry.\n        \"\"\"\n        return isinstance(err, ConnectTimeoutError)\n\n    def _is_read_error(self, err):\n        \"\"\" Errors that occur after the request has been started, so we should\n        assume that the server began processing it.\n        \"\"\"\n        return isinstance(err, (ReadTimeoutError, ProtocolError))\n\n    def _is_method_retryable(self, method):\n        \"\"\" Checks if a given HTTP method should be retried upon, depending if\n        it is included on the method whitelist.\n        \"\"\"\n        if self.method_whitelist and method.upper() not in self.method_whitelist:\n            return False\n\n        return True\n\n    def is_retry(self, method, status_code, has_retry_after=False):\n        \"\"\" Is this method/status code retryable? (Based on whitelists and control\n        variables such as the number of total retries to allow, whether to\n        respect the Retry-After header, whether this header is present, and\n        whether the returned status code is on the list of status codes to\n        be retried upon on the presence of the aforementioned header)\n        \"\"\"\n        if not self._is_method_retryable(method):\n            return False\n\n        if self.status_forcelist and status_code in self.status_forcelist:\n            return True\n\n        return (self.total and self.respect_retry_after_header and\n                has_retry_after and (status_code in self.RETRY_AFTER_STATUS_CODES))\n\n    def is_exhausted(self):\n        \"\"\" Are we out of retries? \"\"\"\n        retry_counts = (self.total, self.connect, self.read, self.redirect, self.status)\n        retry_counts = list(filter(None, retry_counts))\n        if not retry_counts:\n            return False\n\n        return min(retry_counts) < 0\n\n    def increment(self, method=None, url=None, response=None, error=None,\n                  _pool=None, _stacktrace=None):\n        \"\"\" Return a new Retry object with incremented retry counters.\n\n        :param response: A response object, or None, if the server did not\n            return a response.\n        :type response: :class:`~urllib3.response.HTTPResponse`\n        :param Exception error: An error encountered during the request, or\n            None if the response was received successfully.\n\n        :return: A new ``Retry`` object.\n        \"\"\"\n        if self.total is False and error:\n            # Disabled, indicate to re-raise the error.\n            raise six.reraise(type(error), error, _stacktrace)\n\n        total = self.total\n        if total is not None:\n            total -= 1\n\n        connect = self.connect\n        read = self.read\n        redirect = self.redirect\n        status_count = self.status\n        cause = 'unknown'\n        status = None\n        redirect_location = None\n\n        if error and self._is_connection_error(error):\n            # Connect retry?\n            if connect is False:\n                raise six.reraise(type(error), error, _stacktrace)\n            elif connect is not None:\n                connect -= 1\n\n        elif error and self._is_read_error(error):\n            # Read retry?\n            if read is False or not self._is_method_retryable(method):\n                raise six.reraise(type(error), error, _stacktrace)\n            elif read is not None:\n                read -= 1\n\n        elif response and response.get_redirect_location():\n            # Redirect retry?\n            if redirect is not None:\n                redirect -= 1\n            cause = 'too many redirects'\n            redirect_location = response.get_redirect_location()\n            status = response.status\n\n        else:\n            # Incrementing because of a server error like a 500 in\n            # status_forcelist and a the given method is in the whitelist\n            cause = ResponseError.GENERIC_ERROR\n            if response and response.status:\n                if status_count is not None:\n                    status_count -= 1\n                cause = ResponseError.SPECIFIC_ERROR.format(\n                    status_code=response.status)\n                status = response.status\n\n        history = self.history + (RequestHistory(method, url, error, status, redirect_location),)\n\n        new_retry = self.new(\n            total=total,\n            connect=connect, read=read, redirect=redirect, status=status_count,\n            history=history)\n\n        if new_retry.is_exhausted():\n            raise MaxRetryError(_pool, url, error or ResponseError(cause))\n\n        log.debug(\"Incremented Retry for (url='%s'): %r\", url, new_retry)\n\n        return new_retry\n\n    def __repr__(self):\n        return ('{cls.__name__}(total={self.total}, connect={self.connect}, '\n                'read={self.read}, redirect={self.redirect}, status={self.status})').format(\n                    cls=type(self), self=self)\n\n\n# For backwards compatibility (equivalent to pre-v1.9):\nRetry.DEFAULT = Retry(3)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/util/ssl_.py",
    "content": "from __future__ import absolute_import\nimport errno\nimport warnings\nimport hmac\nimport socket\n\nfrom binascii import hexlify, unhexlify\nfrom hashlib import md5, sha1, sha256\n\nfrom ..exceptions import SSLError, InsecurePlatformWarning, SNIMissingWarning\nfrom ..packages import six\n\n\nSSLContext = None\nHAS_SNI = False\nIS_PYOPENSSL = False\nIS_SECURETRANSPORT = False\n\n# Maps the length of a digest to a possible hash function producing this digest\nHASHFUNC_MAP = {\n    32: md5,\n    40: sha1,\n    64: sha256,\n}\n\n\ndef _const_compare_digest_backport(a, b):\n    \"\"\"\n    Compare two digests of equal length in constant time.\n\n    The digests must be of type str/bytes.\n    Returns True if the digests match, and False otherwise.\n    \"\"\"\n    result = abs(len(a) - len(b))\n    for l, r in zip(bytearray(a), bytearray(b)):\n        result |= l ^ r\n    return result == 0\n\n\n_const_compare_digest = getattr(hmac, 'compare_digest',\n                                _const_compare_digest_backport)\n\n\ntry:  # Test for SSL features\n    import ssl\n    from ssl import wrap_socket, CERT_NONE, PROTOCOL_SSLv23\n    from ssl import HAS_SNI  # Has SNI?\nexcept ImportError:\n    pass\n\n\ntry:\n    from ssl import OP_NO_SSLv2, OP_NO_SSLv3, OP_NO_COMPRESSION\nexcept ImportError:\n    OP_NO_SSLv2, OP_NO_SSLv3 = 0x1000000, 0x2000000\n    OP_NO_COMPRESSION = 0x20000\n\n\n# Python 2.7 doesn't have inet_pton on non-Linux so we fallback on inet_aton in\n# those cases. This means that we can only detect IPv4 addresses in this case.\nif hasattr(socket, 'inet_pton'):\n    inet_pton = socket.inet_pton\nelse:\n    # Maybe we can use ipaddress if the user has urllib3[secure]?\n    try:\n        from pip._vendor import ipaddress\n\n        def inet_pton(_, host):\n            if isinstance(host, bytes):\n                host = host.decode('ascii')\n            return ipaddress.ip_address(host)\n\n    except ImportError:  # Platform-specific: Non-Linux\n        def inet_pton(_, host):\n            return socket.inet_aton(host)\n\n\n# A secure default.\n# Sources for more information on TLS ciphers:\n#\n# - https://wiki.mozilla.org/Security/Server_Side_TLS\n# - https://www.ssllabs.com/projects/best-practices/index.html\n# - https://hynek.me/articles/hardening-your-web-servers-ssl-ciphers/\n#\n# The general intent is:\n# - Prefer TLS 1.3 cipher suites\n# - prefer cipher suites that offer perfect forward secrecy (DHE/ECDHE),\n# - prefer ECDHE over DHE for better performance,\n# - prefer any AES-GCM and ChaCha20 over any AES-CBC for better performance and\n#   security,\n# - prefer AES-GCM over ChaCha20 because hardware-accelerated AES is common,\n# - disable NULL authentication, MD5 MACs and DSS for security reasons.\nDEFAULT_CIPHERS = ':'.join([\n    'TLS13-AES-256-GCM-SHA384',\n    'TLS13-CHACHA20-POLY1305-SHA256',\n    'TLS13-AES-128-GCM-SHA256',\n    'ECDH+AESGCM',\n    'ECDH+CHACHA20',\n    'DH+AESGCM',\n    'DH+CHACHA20',\n    'ECDH+AES256',\n    'DH+AES256',\n    'ECDH+AES128',\n    'DH+AES',\n    'RSA+AESGCM',\n    'RSA+AES',\n    '!aNULL',\n    '!eNULL',\n    '!MD5',\n])\n\ntry:\n    from ssl import SSLContext  # Modern SSL?\nexcept ImportError:\n    import sys\n\n    class SSLContext(object):  # Platform-specific: Python 2\n        def __init__(self, protocol_version):\n            self.protocol = protocol_version\n            # Use default values from a real SSLContext\n            self.check_hostname = False\n            self.verify_mode = ssl.CERT_NONE\n            self.ca_certs = None\n            self.options = 0\n            self.certfile = None\n            self.keyfile = None\n            self.ciphers = None\n\n        def load_cert_chain(self, certfile, keyfile):\n            self.certfile = certfile\n            self.keyfile = keyfile\n\n        def load_verify_locations(self, cafile=None, capath=None):\n            self.ca_certs = cafile\n\n            if capath is not None:\n                raise SSLError(\"CA directories not supported in older Pythons\")\n\n        def set_ciphers(self, cipher_suite):\n            self.ciphers = cipher_suite\n\n        def wrap_socket(self, socket, server_hostname=None, server_side=False):\n            warnings.warn(\n                'A true SSLContext object is not available. This prevents '\n                'urllib3 from configuring SSL appropriately and may cause '\n                'certain SSL connections to fail. You can upgrade to a newer '\n                'version of Python to solve this. For more information, see '\n                'https://urllib3.readthedocs.io/en/latest/advanced-usage.html'\n                '#ssl-warnings',\n                InsecurePlatformWarning\n            )\n            kwargs = {\n                'keyfile': self.keyfile,\n                'certfile': self.certfile,\n                'ca_certs': self.ca_certs,\n                'cert_reqs': self.verify_mode,\n                'ssl_version': self.protocol,\n                'server_side': server_side,\n            }\n            return wrap_socket(socket, ciphers=self.ciphers, **kwargs)\n\n\ndef assert_fingerprint(cert, fingerprint):\n    \"\"\"\n    Checks if given fingerprint matches the supplied certificate.\n\n    :param cert:\n        Certificate as bytes object.\n    :param fingerprint:\n        Fingerprint as string of hexdigits, can be interspersed by colons.\n    \"\"\"\n\n    fingerprint = fingerprint.replace(':', '').lower()\n    digest_length = len(fingerprint)\n    hashfunc = HASHFUNC_MAP.get(digest_length)\n    if not hashfunc:\n        raise SSLError(\n            'Fingerprint of invalid length: {0}'.format(fingerprint))\n\n    # We need encode() here for py32; works on py2 and p33.\n    fingerprint_bytes = unhexlify(fingerprint.encode())\n\n    cert_digest = hashfunc(cert).digest()\n\n    if not _const_compare_digest(cert_digest, fingerprint_bytes):\n        raise SSLError('Fingerprints did not match. Expected \"{0}\", got \"{1}\".'\n                       .format(fingerprint, hexlify(cert_digest)))\n\n\ndef resolve_cert_reqs(candidate):\n    \"\"\"\n    Resolves the argument to a numeric constant, which can be passed to\n    the wrap_socket function/method from the ssl module.\n    Defaults to :data:`ssl.CERT_NONE`.\n    If given a string it is assumed to be the name of the constant in the\n    :mod:`ssl` module or its abbreviation.\n    (So you can specify `REQUIRED` instead of `CERT_REQUIRED`.\n    If it's neither `None` nor a string we assume it is already the numeric\n    constant which can directly be passed to wrap_socket.\n    \"\"\"\n    if candidate is None:\n        return CERT_NONE\n\n    if isinstance(candidate, str):\n        res = getattr(ssl, candidate, None)\n        if res is None:\n            res = getattr(ssl, 'CERT_' + candidate)\n        return res\n\n    return candidate\n\n\ndef resolve_ssl_version(candidate):\n    \"\"\"\n    like resolve_cert_reqs\n    \"\"\"\n    if candidate is None:\n        return PROTOCOL_SSLv23\n\n    if isinstance(candidate, str):\n        res = getattr(ssl, candidate, None)\n        if res is None:\n            res = getattr(ssl, 'PROTOCOL_' + candidate)\n        return res\n\n    return candidate\n\n\ndef create_urllib3_context(ssl_version=None, cert_reqs=None,\n                           options=None, ciphers=None):\n    \"\"\"All arguments have the same meaning as ``ssl_wrap_socket``.\n\n    By default, this function does a lot of the same work that\n    ``ssl.create_default_context`` does on Python 3.4+. It:\n\n    - Disables SSLv2, SSLv3, and compression\n    - Sets a restricted set of server ciphers\n\n    If you wish to enable SSLv3, you can do::\n\n        from pip._vendor.urllib3.util import ssl_\n        context = ssl_.create_urllib3_context()\n        context.options &= ~ssl_.OP_NO_SSLv3\n\n    You can do the same to enable compression (substituting ``COMPRESSION``\n    for ``SSLv3`` in the last line above).\n\n    :param ssl_version:\n        The desired protocol version to use. This will default to\n        PROTOCOL_SSLv23 which will negotiate the highest protocol that both\n        the server and your installation of OpenSSL support.\n    :param cert_reqs:\n        Whether to require the certificate verification. This defaults to\n        ``ssl.CERT_REQUIRED``.\n    :param options:\n        Specific OpenSSL options. These default to ``ssl.OP_NO_SSLv2``,\n        ``ssl.OP_NO_SSLv3``, ``ssl.OP_NO_COMPRESSION``.\n    :param ciphers:\n        Which cipher suites to allow the server to select.\n    :returns:\n        Constructed SSLContext object with specified options\n    :rtype: SSLContext\n    \"\"\"\n    context = SSLContext(ssl_version or ssl.PROTOCOL_SSLv23)\n\n    context.set_ciphers(ciphers or DEFAULT_CIPHERS)\n\n    # Setting the default here, as we may have no ssl module on import\n    cert_reqs = ssl.CERT_REQUIRED if cert_reqs is None else cert_reqs\n\n    if options is None:\n        options = 0\n        # SSLv2 is easily broken and is considered harmful and dangerous\n        options |= OP_NO_SSLv2\n        # SSLv3 has several problems and is now dangerous\n        options |= OP_NO_SSLv3\n        # Disable compression to prevent CRIME attacks for OpenSSL 1.0+\n        # (issue #309)\n        options |= OP_NO_COMPRESSION\n\n    context.options |= options\n\n    context.verify_mode = cert_reqs\n    if getattr(context, 'check_hostname', None) is not None:  # Platform-specific: Python 3.2\n        # We do our own verification, including fingerprints and alternative\n        # hostnames. So disable it here\n        context.check_hostname = False\n    return context\n\n\ndef ssl_wrap_socket(sock, keyfile=None, certfile=None, cert_reqs=None,\n                    ca_certs=None, server_hostname=None,\n                    ssl_version=None, ciphers=None, ssl_context=None,\n                    ca_cert_dir=None):\n    \"\"\"\n    All arguments except for server_hostname, ssl_context, and ca_cert_dir have\n    the same meaning as they do when using :func:`ssl.wrap_socket`.\n\n    :param server_hostname:\n        When SNI is supported, the expected hostname of the certificate\n    :param ssl_context:\n        A pre-made :class:`SSLContext` object. If none is provided, one will\n        be created using :func:`create_urllib3_context`.\n    :param ciphers:\n        A string of ciphers we wish the client to support.\n    :param ca_cert_dir:\n        A directory containing CA certificates in multiple separate files, as\n        supported by OpenSSL's -CApath flag or the capath argument to\n        SSLContext.load_verify_locations().\n    \"\"\"\n    context = ssl_context\n    if context is None:\n        # Note: This branch of code and all the variables in it are no longer\n        # used by urllib3 itself. We should consider deprecating and removing\n        # this code.\n        context = create_urllib3_context(ssl_version, cert_reqs,\n                                         ciphers=ciphers)\n\n    if ca_certs or ca_cert_dir:\n        try:\n            context.load_verify_locations(ca_certs, ca_cert_dir)\n        except IOError as e:  # Platform-specific: Python 2.7\n            raise SSLError(e)\n        # Py33 raises FileNotFoundError which subclasses OSError\n        # These are not equivalent unless we check the errno attribute\n        except OSError as e:  # Platform-specific: Python 3.3 and beyond\n            if e.errno == errno.ENOENT:\n                raise SSLError(e)\n            raise\n    elif getattr(context, 'load_default_certs', None) is not None:\n        # try to load OS default certs; works well on Windows (require Python3.4+)\n        context.load_default_certs()\n\n    if certfile:\n        context.load_cert_chain(certfile, keyfile)\n\n    # If we detect server_hostname is an IP address then the SNI\n    # extension should not be used according to RFC3546 Section 3.1\n    # We shouldn't warn the user if SNI isn't available but we would\n    # not be using SNI anyways due to IP address for server_hostname.\n    if ((server_hostname is not None and not is_ipaddress(server_hostname))\n            or IS_SECURETRANSPORT):\n        if HAS_SNI and server_hostname is not None:\n            return context.wrap_socket(sock, server_hostname=server_hostname)\n\n        warnings.warn(\n            'An HTTPS request has been made, but the SNI (Server Name '\n            'Indication) extension to TLS is not available on this platform. '\n            'This may cause the server to present an incorrect TLS '\n            'certificate, which can cause validation failures. You can upgrade to '\n            'a newer version of Python to solve this. For more information, see '\n            'https://urllib3.readthedocs.io/en/latest/advanced-usage.html'\n            '#ssl-warnings',\n            SNIMissingWarning\n        )\n\n    return context.wrap_socket(sock)\n\n\ndef is_ipaddress(hostname):\n    \"\"\"Detects whether the hostname given is an IP address.\n\n    :param str hostname: Hostname to examine.\n    :return: True if the hostname is an IP address, False otherwise.\n    \"\"\"\n    if six.PY3 and isinstance(hostname, bytes):\n        # IDN A-label bytes are ASCII compatible.\n        hostname = hostname.decode('ascii')\n\n    families = [socket.AF_INET]\n    if hasattr(socket, 'AF_INET6'):\n        families.append(socket.AF_INET6)\n\n    for af in families:\n        try:\n            inet_pton(af, hostname)\n        except (socket.error, ValueError, OSError):\n            pass\n        else:\n            return True\n    return False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/util/timeout.py",
    "content": "from __future__ import absolute_import\n# The default socket timeout, used by httplib to indicate that no timeout was\n# specified by the user\nfrom socket import _GLOBAL_DEFAULT_TIMEOUT\nimport time\n\nfrom ..exceptions import TimeoutStateError\n\n# A sentinel value to indicate that no timeout was specified by the user in\n# urllib3\n_Default = object()\n\n\n# Use time.monotonic if available.\ncurrent_time = getattr(time, \"monotonic\", time.time)\n\n\nclass Timeout(object):\n    \"\"\" Timeout configuration.\n\n    Timeouts can be defined as a default for a pool::\n\n        timeout = Timeout(connect=2.0, read=7.0)\n        http = PoolManager(timeout=timeout)\n        response = http.request('GET', 'http://example.com/')\n\n    Or per-request (which overrides the default for the pool)::\n\n        response = http.request('GET', 'http://example.com/', timeout=Timeout(10))\n\n    Timeouts can be disabled by setting all the parameters to ``None``::\n\n        no_timeout = Timeout(connect=None, read=None)\n        response = http.request('GET', 'http://example.com/, timeout=no_timeout)\n\n\n    :param total:\n        This combines the connect and read timeouts into one; the read timeout\n        will be set to the time leftover from the connect attempt. In the\n        event that both a connect timeout and a total are specified, or a read\n        timeout and a total are specified, the shorter timeout will be applied.\n\n        Defaults to None.\n\n    :type total: integer, float, or None\n\n    :param connect:\n        The maximum amount of time to wait for a connection attempt to a server\n        to succeed. Omitting the parameter will default the connect timeout to\n        the system default, probably `the global default timeout in socket.py\n        <http://hg.python.org/cpython/file/603b4d593758/Lib/socket.py#l535>`_.\n        None will set an infinite timeout for connection attempts.\n\n    :type connect: integer, float, or None\n\n    :param read:\n        The maximum amount of time to wait between consecutive\n        read operations for a response from the server. Omitting\n        the parameter will default the read timeout to the system\n        default, probably `the global default timeout in socket.py\n        <http://hg.python.org/cpython/file/603b4d593758/Lib/socket.py#l535>`_.\n        None will set an infinite timeout.\n\n    :type read: integer, float, or None\n\n    .. note::\n\n        Many factors can affect the total amount of time for urllib3 to return\n        an HTTP response.\n\n        For example, Python's DNS resolver does not obey the timeout specified\n        on the socket. Other factors that can affect total request time include\n        high CPU load, high swap, the program running at a low priority level,\n        or other behaviors.\n\n        In addition, the read and total timeouts only measure the time between\n        read operations on the socket connecting the client and the server,\n        not the total amount of time for the request to return a complete\n        response. For most requests, the timeout is raised because the server\n        has not sent the first byte in the specified time. This is not always\n        the case; if a server streams one byte every fifteen seconds, a timeout\n        of 20 seconds will not trigger, even though the request will take\n        several minutes to complete.\n\n        If your goal is to cut off any request after a set amount of wall clock\n        time, consider having a second \"watcher\" thread to cut off a slow\n        request.\n    \"\"\"\n\n    #: A sentinel object representing the default timeout value\n    DEFAULT_TIMEOUT = _GLOBAL_DEFAULT_TIMEOUT\n\n    def __init__(self, total=None, connect=_Default, read=_Default):\n        self._connect = self._validate_timeout(connect, 'connect')\n        self._read = self._validate_timeout(read, 'read')\n        self.total = self._validate_timeout(total, 'total')\n        self._start_connect = None\n\n    def __str__(self):\n        return '%s(connect=%r, read=%r, total=%r)' % (\n            type(self).__name__, self._connect, self._read, self.total)\n\n    @classmethod\n    def _validate_timeout(cls, value, name):\n        \"\"\" Check that a timeout attribute is valid.\n\n        :param value: The timeout value to validate\n        :param name: The name of the timeout attribute to validate. This is\n            used to specify in error messages.\n        :return: The validated and casted version of the given value.\n        :raises ValueError: If it is a numeric value less than or equal to\n            zero, or the type is not an integer, float, or None.\n        \"\"\"\n        if value is _Default:\n            return cls.DEFAULT_TIMEOUT\n\n        if value is None or value is cls.DEFAULT_TIMEOUT:\n            return value\n\n        if isinstance(value, bool):\n            raise ValueError(\"Timeout cannot be a boolean value. It must \"\n                             \"be an int, float or None.\")\n        try:\n            float(value)\n        except (TypeError, ValueError):\n            raise ValueError(\"Timeout value %s was %s, but it must be an \"\n                             \"int, float or None.\" % (name, value))\n\n        try:\n            if value <= 0:\n                raise ValueError(\"Attempted to set %s timeout to %s, but the \"\n                                 \"timeout cannot be set to a value less \"\n                                 \"than or equal to 0.\" % (name, value))\n        except TypeError:  # Python 3\n            raise ValueError(\"Timeout value %s was %s, but it must be an \"\n                             \"int, float or None.\" % (name, value))\n\n        return value\n\n    @classmethod\n    def from_float(cls, timeout):\n        \"\"\" Create a new Timeout from a legacy timeout value.\n\n        The timeout value used by httplib.py sets the same timeout on the\n        connect(), and recv() socket requests. This creates a :class:`Timeout`\n        object that sets the individual timeouts to the ``timeout`` value\n        passed to this function.\n\n        :param timeout: The legacy timeout value.\n        :type timeout: integer, float, sentinel default object, or None\n        :return: Timeout object\n        :rtype: :class:`Timeout`\n        \"\"\"\n        return Timeout(read=timeout, connect=timeout)\n\n    def clone(self):\n        \"\"\" Create a copy of the timeout object\n\n        Timeout properties are stored per-pool but each request needs a fresh\n        Timeout object to ensure each one has its own start/stop configured.\n\n        :return: a copy of the timeout object\n        :rtype: :class:`Timeout`\n        \"\"\"\n        # We can't use copy.deepcopy because that will also create a new object\n        # for _GLOBAL_DEFAULT_TIMEOUT, which socket.py uses as a sentinel to\n        # detect the user default.\n        return Timeout(connect=self._connect, read=self._read,\n                       total=self.total)\n\n    def start_connect(self):\n        \"\"\" Start the timeout clock, used during a connect() attempt\n\n        :raises urllib3.exceptions.TimeoutStateError: if you attempt\n            to start a timer that has been started already.\n        \"\"\"\n        if self._start_connect is not None:\n            raise TimeoutStateError(\"Timeout timer has already been started.\")\n        self._start_connect = current_time()\n        return self._start_connect\n\n    def get_connect_duration(self):\n        \"\"\" Gets the time elapsed since the call to :meth:`start_connect`.\n\n        :return: Elapsed time.\n        :rtype: float\n        :raises urllib3.exceptions.TimeoutStateError: if you attempt\n            to get duration for a timer that hasn't been started.\n        \"\"\"\n        if self._start_connect is None:\n            raise TimeoutStateError(\"Can't get connect duration for timer \"\n                                    \"that has not started.\")\n        return current_time() - self._start_connect\n\n    @property\n    def connect_timeout(self):\n        \"\"\" Get the value to use when setting a connection timeout.\n\n        This will be a positive float or integer, the value None\n        (never timeout), or the default system timeout.\n\n        :return: Connect timeout.\n        :rtype: int, float, :attr:`Timeout.DEFAULT_TIMEOUT` or None\n        \"\"\"\n        if self.total is None:\n            return self._connect\n\n        if self._connect is None or self._connect is self.DEFAULT_TIMEOUT:\n            return self.total\n\n        return min(self._connect, self.total)\n\n    @property\n    def read_timeout(self):\n        \"\"\" Get the value for the read timeout.\n\n        This assumes some time has elapsed in the connection timeout and\n        computes the read timeout appropriately.\n\n        If self.total is set, the read timeout is dependent on the amount of\n        time taken by the connect timeout. If the connection time has not been\n        established, a :exc:`~urllib3.exceptions.TimeoutStateError` will be\n        raised.\n\n        :return: Value to use for the read timeout.\n        :rtype: int, float, :attr:`Timeout.DEFAULT_TIMEOUT` or None\n        :raises urllib3.exceptions.TimeoutStateError: If :meth:`start_connect`\n            has not yet been called on this object.\n        \"\"\"\n        if (self.total is not None and\n                self.total is not self.DEFAULT_TIMEOUT and\n                self._read is not None and\n                self._read is not self.DEFAULT_TIMEOUT):\n            # In case the connect timeout has not yet been established.\n            if self._start_connect is None:\n                return self._read\n            return max(0, min(self.total - self.get_connect_duration(),\n                              self._read))\n        elif self.total is not None and self.total is not self.DEFAULT_TIMEOUT:\n            return max(0, self.total - self.get_connect_duration())\n        else:\n            return self._read\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/util/url.py",
    "content": "from __future__ import absolute_import\nfrom collections import namedtuple\n\nfrom ..exceptions import LocationParseError\n\n\nurl_attrs = ['scheme', 'auth', 'host', 'port', 'path', 'query', 'fragment']\n\n# We only want to normalize urls with an HTTP(S) scheme.\n# urllib3 infers URLs without a scheme (None) to be http.\nNORMALIZABLE_SCHEMES = ('http', 'https', None)\n\n\nclass Url(namedtuple('Url', url_attrs)):\n    \"\"\"\n    Datastructure for representing an HTTP URL. Used as a return value for\n    :func:`parse_url`. Both the scheme and host are normalized as they are\n    both case-insensitive according to RFC 3986.\n    \"\"\"\n    __slots__ = ()\n\n    def __new__(cls, scheme=None, auth=None, host=None, port=None, path=None,\n                query=None, fragment=None):\n        if path and not path.startswith('/'):\n            path = '/' + path\n        if scheme:\n            scheme = scheme.lower()\n        if host and scheme in NORMALIZABLE_SCHEMES:\n            host = host.lower()\n        return super(Url, cls).__new__(cls, scheme, auth, host, port, path,\n                                       query, fragment)\n\n    @property\n    def hostname(self):\n        \"\"\"For backwards-compatibility with urlparse. We're nice like that.\"\"\"\n        return self.host\n\n    @property\n    def request_uri(self):\n        \"\"\"Absolute path including the query string.\"\"\"\n        uri = self.path or '/'\n\n        if self.query is not None:\n            uri += '?' + self.query\n\n        return uri\n\n    @property\n    def netloc(self):\n        \"\"\"Network location including host and port\"\"\"\n        if self.port:\n            return '%s:%d' % (self.host, self.port)\n        return self.host\n\n    @property\n    def url(self):\n        \"\"\"\n        Convert self into a url\n\n        This function should more or less round-trip with :func:`.parse_url`. The\n        returned url may not be exactly the same as the url inputted to\n        :func:`.parse_url`, but it should be equivalent by the RFC (e.g., urls\n        with a blank port will have : removed).\n\n        Example: ::\n\n            >>> U = parse_url('http://google.com/mail/')\n            >>> U.url\n            'http://google.com/mail/'\n            >>> Url('http', 'username:password', 'host.com', 80,\n            ... '/path', 'query', 'fragment').url\n            'http://username:password@host.com:80/path?query#fragment'\n        \"\"\"\n        scheme, auth, host, port, path, query, fragment = self\n        url = ''\n\n        # We use \"is not None\" we want things to happen with empty strings (or 0 port)\n        if scheme is not None:\n            url += scheme + '://'\n        if auth is not None:\n            url += auth + '@'\n        if host is not None:\n            url += host\n        if port is not None:\n            url += ':' + str(port)\n        if path is not None:\n            url += path\n        if query is not None:\n            url += '?' + query\n        if fragment is not None:\n            url += '#' + fragment\n\n        return url\n\n    def __str__(self):\n        return self.url\n\n\ndef split_first(s, delims):\n    \"\"\"\n    Given a string and an iterable of delimiters, split on the first found\n    delimiter. Return two split parts and the matched delimiter.\n\n    If not found, then the first part is the full input string.\n\n    Example::\n\n        >>> split_first('foo/bar?baz', '?/=')\n        ('foo', 'bar?baz', '/')\n        >>> split_first('foo/bar?baz', '123')\n        ('foo/bar?baz', '', None)\n\n    Scales linearly with number of delims. Not ideal for large number of delims.\n    \"\"\"\n    min_idx = None\n    min_delim = None\n    for d in delims:\n        idx = s.find(d)\n        if idx < 0:\n            continue\n\n        if min_idx is None or idx < min_idx:\n            min_idx = idx\n            min_delim = d\n\n    if min_idx is None or min_idx < 0:\n        return s, '', None\n\n    return s[:min_idx], s[min_idx + 1:], min_delim\n\n\ndef parse_url(url):\n    \"\"\"\n    Given a url, return a parsed :class:`.Url` namedtuple. Best-effort is\n    performed to parse incomplete urls. Fields not provided will be None.\n\n    Partly backwards-compatible with :mod:`urlparse`.\n\n    Example::\n\n        >>> parse_url('http://google.com/mail/')\n        Url(scheme='http', host='google.com', port=None, path='/mail/', ...)\n        >>> parse_url('google.com:80')\n        Url(scheme=None, host='google.com', port=80, path=None, ...)\n        >>> parse_url('/foo?bar')\n        Url(scheme=None, host=None, port=None, path='/foo', query='bar', ...)\n    \"\"\"\n\n    # While this code has overlap with stdlib's urlparse, it is much\n    # simplified for our needs and less annoying.\n    # Additionally, this implementations does silly things to be optimal\n    # on CPython.\n\n    if not url:\n        # Empty\n        return Url()\n\n    scheme = None\n    auth = None\n    host = None\n    port = None\n    path = None\n    fragment = None\n    query = None\n\n    # Scheme\n    if '://' in url:\n        scheme, url = url.split('://', 1)\n\n    # Find the earliest Authority Terminator\n    # (http://tools.ietf.org/html/rfc3986#section-3.2)\n    url, path_, delim = split_first(url, ['/', '?', '#'])\n\n    if delim:\n        # Reassemble the path\n        path = delim + path_\n\n    # Auth\n    if '@' in url:\n        # Last '@' denotes end of auth part\n        auth, url = url.rsplit('@', 1)\n\n    # IPv6\n    if url and url[0] == '[':\n        host, url = url.split(']', 1)\n        host += ']'\n\n    # Port\n    if ':' in url:\n        _host, port = url.split(':', 1)\n\n        if not host:\n            host = _host\n\n        if port:\n            # If given, ports must be integers. No whitespace, no plus or\n            # minus prefixes, no non-integer digits such as ^2 (superscript).\n            if not port.isdigit():\n                raise LocationParseError(url)\n            try:\n                port = int(port)\n            except ValueError:\n                raise LocationParseError(url)\n        else:\n            # Blank ports are cool, too. (rfc3986#section-3.2.3)\n            port = None\n\n    elif not host and url:\n        host = url\n\n    if not path:\n        return Url(scheme, auth, host, port, path, query, fragment)\n\n    # Fragment\n    if '#' in path:\n        path, fragment = path.split('#', 1)\n\n    # Query\n    if '?' in path:\n        path, query = path.split('?', 1)\n\n    return Url(scheme, auth, host, port, path, query, fragment)\n\n\ndef get_host(url):\n    \"\"\"\n    Deprecated. Use :func:`parse_url` instead.\n    \"\"\"\n    p = parse_url(url)\n    return p.scheme or 'http', p.hostname, p.port\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/urllib3/util/wait.py",
    "content": "import errno\nfrom functools import partial\nimport select\nimport sys\ntry:\n    from time import monotonic\nexcept ImportError:\n    from time import time as monotonic\n\n__all__ = [\"NoWayToWaitForSocketError\", \"wait_for_read\", \"wait_for_write\"]\n\n\nclass NoWayToWaitForSocketError(Exception):\n    pass\n\n\n# How should we wait on sockets?\n#\n# There are two types of APIs you can use for waiting on sockets: the fancy\n# modern stateful APIs like epoll/kqueue, and the older stateless APIs like\n# select/poll. The stateful APIs are more efficient when you have a lots of\n# sockets to keep track of, because you can set them up once and then use them\n# lots of times. But we only ever want to wait on a single socket at a time\n# and don't want to keep track of state, so the stateless APIs are actually\n# more efficient. So we want to use select() or poll().\n#\n# Now, how do we choose between select() and poll()? On traditional Unixes,\n# select() has a strange calling convention that makes it slow, or fail\n# altogether, for high-numbered file descriptors. The point of poll() is to fix\n# that, so on Unixes, we prefer poll().\n#\n# On Windows, there is no poll() (or at least Python doesn't provide a wrapper\n# for it), but that's OK, because on Windows, select() doesn't have this\n# strange calling convention; plain select() works fine.\n#\n# So: on Windows we use select(), and everywhere else we use poll(). We also\n# fall back to select() in case poll() is somehow broken or missing.\n\nif sys.version_info >= (3, 5):\n    # Modern Python, that retries syscalls by default\n    def _retry_on_intr(fn, timeout):\n        return fn(timeout)\nelse:\n    # Old and broken Pythons.\n    def _retry_on_intr(fn, timeout):\n        if timeout is None:\n            deadline = float(\"inf\")\n        else:\n            deadline = monotonic() + timeout\n\n        while True:\n            try:\n                return fn(timeout)\n            # OSError for 3 <= pyver < 3.5, select.error for pyver <= 2.7\n            except (OSError, select.error) as e:\n                # 'e.args[0]' incantation works for both OSError and select.error\n                if e.args[0] != errno.EINTR:\n                    raise\n                else:\n                    timeout = deadline - monotonic()\n                    if timeout < 0:\n                        timeout = 0\n                    if timeout == float(\"inf\"):\n                        timeout = None\n                    continue\n\n\ndef select_wait_for_socket(sock, read=False, write=False, timeout=None):\n    if not read and not write:\n        raise RuntimeError(\"must specify at least one of read=True, write=True\")\n    rcheck = []\n    wcheck = []\n    if read:\n        rcheck.append(sock)\n    if write:\n        wcheck.append(sock)\n    # When doing a non-blocking connect, most systems signal success by\n    # marking the socket writable. Windows, though, signals success by marked\n    # it as \"exceptional\". We paper over the difference by checking the write\n    # sockets for both conditions. (The stdlib selectors module does the same\n    # thing.)\n    fn = partial(select.select, rcheck, wcheck, wcheck)\n    rready, wready, xready = _retry_on_intr(fn, timeout)\n    return bool(rready or wready or xready)\n\n\ndef poll_wait_for_socket(sock, read=False, write=False, timeout=None):\n    if not read and not write:\n        raise RuntimeError(\"must specify at least one of read=True, write=True\")\n    mask = 0\n    if read:\n        mask |= select.POLLIN\n    if write:\n        mask |= select.POLLOUT\n    poll_obj = select.poll()\n    poll_obj.register(sock, mask)\n\n    # For some reason, poll() takes timeout in milliseconds\n    def do_poll(t):\n        if t is not None:\n            t *= 1000\n        return poll_obj.poll(t)\n\n    return bool(_retry_on_intr(do_poll, timeout))\n\n\ndef null_wait_for_socket(*args, **kwargs):\n    raise NoWayToWaitForSocketError(\"no select-equivalent available\")\n\n\ndef _have_working_poll():\n    # Apparently some systems have a select.poll that fails as soon as you try\n    # to use it, either due to strange configuration or broken monkeypatching\n    # from libraries like eventlet/greenlet.\n    try:\n        poll_obj = select.poll()\n        _retry_on_intr(poll_obj.poll, 0)\n    except (AttributeError, OSError):\n        return False\n    else:\n        return True\n\n\ndef wait_for_socket(*args, **kwargs):\n    # We delay choosing which implementation to use until the first time we're\n    # called. We could do it at import time, but then we might make the wrong\n    # decision if someone goes wild with monkeypatching select.poll after\n    # we're imported.\n    global wait_for_socket\n    if _have_working_poll():\n        wait_for_socket = poll_wait_for_socket\n    elif hasattr(select, \"select\"):\n        wait_for_socket = select_wait_for_socket\n    else:  # Platform-specific: Appengine.\n        wait_for_socket = null_wait_for_socket\n    return wait_for_socket(*args, **kwargs)\n\n\ndef wait_for_read(sock, timeout=None):\n    \"\"\" Waits for reading to be available on a given socket.\n    Returns True if the socket is readable, or False if the timeout expired.\n    \"\"\"\n    return wait_for_socket(sock, read=True, timeout=timeout)\n\n\ndef wait_for_write(sock, timeout=None):\n    \"\"\" Waits for writing to be available on a given socket.\n    Returns True if the socket is readable, or False if the timeout expired.\n    \"\"\"\n    return wait_for_socket(sock, write=True, timeout=timeout)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/webencodings/__init__.py",
    "content": "# coding: utf-8\n\"\"\"\n\n    webencodings\n    ~~~~~~~~~~~~\n\n    This is a Python implementation of the `WHATWG Encoding standard\n    <http://encoding.spec.whatwg.org/>`. See README for details.\n\n    :copyright: Copyright 2012 by Simon Sapin\n    :license: BSD, see LICENSE for details.\n\n\"\"\"\n\nfrom __future__ import unicode_literals\n\nimport codecs\n\nfrom .labels import LABELS\n\n\nVERSION = '0.5.1'\n\n\n# Some names in Encoding are not valid Python aliases. Remap these.\nPYTHON_NAMES = {\n    'iso-8859-8-i': 'iso-8859-8',\n    'x-mac-cyrillic': 'mac-cyrillic',\n    'macintosh': 'mac-roman',\n    'windows-874': 'cp874'}\n\nCACHE = {}\n\n\ndef ascii_lower(string):\n    r\"\"\"Transform (only) ASCII letters to lower case: A-Z is mapped to a-z.\n\n    :param string: An Unicode string.\n    :returns: A new Unicode string.\n\n    This is used for `ASCII case-insensitive\n    <http://encoding.spec.whatwg.org/#ascii-case-insensitive>`_\n    matching of encoding labels.\n    The same matching is also used, among other things,\n    for `CSS keywords <http://dev.w3.org/csswg/css-values/#keywords>`_.\n\n    This is different from the :meth:`~py:str.lower` method of Unicode strings\n    which also affect non-ASCII characters,\n    sometimes mapping them into the ASCII range:\n\n        >>> keyword = u'Bac\\N{KELVIN SIGN}ground'\n        >>> assert keyword.lower() == u'background'\n        >>> assert ascii_lower(keyword) != keyword.lower()\n        >>> assert ascii_lower(keyword) == u'bac\\N{KELVIN SIGN}ground'\n\n    \"\"\"\n    # This turns out to be faster than unicode.translate()\n    return string.encode('utf8').lower().decode('utf8')\n\n\ndef lookup(label):\n    \"\"\"\n    Look for an encoding by its label.\n    This is the spec’s `get an encoding\n    <http://encoding.spec.whatwg.org/#concept-encoding-get>`_ algorithm.\n    Supported labels are listed there.\n\n    :param label: A string.\n    :returns:\n        An :class:`Encoding` object, or :obj:`None` for an unknown label.\n\n    \"\"\"\n    # Only strip ASCII whitespace: U+0009, U+000A, U+000C, U+000D, and U+0020.\n    label = ascii_lower(label.strip('\\t\\n\\f\\r '))\n    name = LABELS.get(label)\n    if name is None:\n        return None\n    encoding = CACHE.get(name)\n    if encoding is None:\n        if name == 'x-user-defined':\n            from .x_user_defined import codec_info\n        else:\n            python_name = PYTHON_NAMES.get(name, name)\n            # Any python_name value that gets to here should be valid.\n            codec_info = codecs.lookup(python_name)\n        encoding = Encoding(name, codec_info)\n        CACHE[name] = encoding\n    return encoding\n\n\ndef _get_encoding(encoding_or_label):\n    \"\"\"\n    Accept either an encoding object or label.\n\n    :param encoding: An :class:`Encoding` object or a label string.\n    :returns: An :class:`Encoding` object.\n    :raises: :exc:`~exceptions.LookupError` for an unknown label.\n\n    \"\"\"\n    if hasattr(encoding_or_label, 'codec_info'):\n        return encoding_or_label\n\n    encoding = lookup(encoding_or_label)\n    if encoding is None:\n        raise LookupError('Unknown encoding label: %r' % encoding_or_label)\n    return encoding\n\n\nclass Encoding(object):\n    \"\"\"Reresents a character encoding such as UTF-8,\n    that can be used for decoding or encoding.\n\n    .. attribute:: name\n\n        Canonical name of the encoding\n\n    .. attribute:: codec_info\n\n        The actual implementation of the encoding,\n        a stdlib :class:`~codecs.CodecInfo` object.\n        See :func:`codecs.register`.\n\n    \"\"\"\n    def __init__(self, name, codec_info):\n        self.name = name\n        self.codec_info = codec_info\n\n    def __repr__(self):\n        return '<Encoding %s>' % self.name\n\n\n#: The UTF-8 encoding. Should be used for new content and formats.\nUTF8 = lookup('utf-8')\n\n_UTF16LE = lookup('utf-16le')\n_UTF16BE = lookup('utf-16be')\n\n\ndef decode(input, fallback_encoding, errors='replace'):\n    \"\"\"\n    Decode a single string.\n\n    :param input: A byte string\n    :param fallback_encoding:\n        An :class:`Encoding` object or a label string.\n        The encoding to use if :obj:`input` does note have a BOM.\n    :param errors: Type of error handling. See :func:`codecs.register`.\n    :raises: :exc:`~exceptions.LookupError` for an unknown encoding label.\n    :return:\n        A ``(output, encoding)`` tuple of an Unicode string\n        and an :obj:`Encoding`.\n\n    \"\"\"\n    # Fail early if `encoding` is an invalid label.\n    fallback_encoding = _get_encoding(fallback_encoding)\n    bom_encoding, input = _detect_bom(input)\n    encoding = bom_encoding or fallback_encoding\n    return encoding.codec_info.decode(input, errors)[0], encoding\n\n\ndef _detect_bom(input):\n    \"\"\"Return (bom_encoding, input), with any BOM removed from the input.\"\"\"\n    if input.startswith(b'\\xFF\\xFE'):\n        return _UTF16LE, input[2:]\n    if input.startswith(b'\\xFE\\xFF'):\n        return _UTF16BE, input[2:]\n    if input.startswith(b'\\xEF\\xBB\\xBF'):\n        return UTF8, input[3:]\n    return None, input\n\n\ndef encode(input, encoding=UTF8, errors='strict'):\n    \"\"\"\n    Encode a single string.\n\n    :param input: An Unicode string.\n    :param encoding: An :class:`Encoding` object or a label string.\n    :param errors: Type of error handling. See :func:`codecs.register`.\n    :raises: :exc:`~exceptions.LookupError` for an unknown encoding label.\n    :return: A byte string.\n\n    \"\"\"\n    return _get_encoding(encoding).codec_info.encode(input, errors)[0]\n\n\ndef iter_decode(input, fallback_encoding, errors='replace'):\n    \"\"\"\n    \"Pull\"-based decoder.\n\n    :param input:\n        An iterable of byte strings.\n\n        The input is first consumed just enough to determine the encoding\n        based on the precense of a BOM,\n        then consumed on demand when the return value is.\n    :param fallback_encoding:\n        An :class:`Encoding` object or a label string.\n        The encoding to use if :obj:`input` does note have a BOM.\n    :param errors: Type of error handling. See :func:`codecs.register`.\n    :raises: :exc:`~exceptions.LookupError` for an unknown encoding label.\n    :returns:\n        An ``(output, encoding)`` tuple.\n        :obj:`output` is an iterable of Unicode strings,\n        :obj:`encoding` is the :obj:`Encoding` that is being used.\n\n    \"\"\"\n\n    decoder = IncrementalDecoder(fallback_encoding, errors)\n    generator = _iter_decode_generator(input, decoder)\n    encoding = next(generator)\n    return generator, encoding\n\n\ndef _iter_decode_generator(input, decoder):\n    \"\"\"Return a generator that first yields the :obj:`Encoding`,\n    then yields output chukns as Unicode strings.\n\n    \"\"\"\n    decode = decoder.decode\n    input = iter(input)\n    for chunck in input:\n        output = decode(chunck)\n        if output:\n            assert decoder.encoding is not None\n            yield decoder.encoding\n            yield output\n            break\n    else:\n        # Input exhausted without determining the encoding\n        output = decode(b'', final=True)\n        assert decoder.encoding is not None\n        yield decoder.encoding\n        if output:\n            yield output\n        return\n\n    for chunck in input:\n        output = decode(chunck)\n        if output:\n            yield output\n    output = decode(b'', final=True)\n    if output:\n        yield output\n\n\ndef iter_encode(input, encoding=UTF8, errors='strict'):\n    \"\"\"\n    “Pull”-based encoder.\n\n    :param input: An iterable of Unicode strings.\n    :param encoding: An :class:`Encoding` object or a label string.\n    :param errors: Type of error handling. See :func:`codecs.register`.\n    :raises: :exc:`~exceptions.LookupError` for an unknown encoding label.\n    :returns: An iterable of byte strings.\n\n    \"\"\"\n    # Fail early if `encoding` is an invalid label.\n    encode = IncrementalEncoder(encoding, errors).encode\n    return _iter_encode_generator(input, encode)\n\n\ndef _iter_encode_generator(input, encode):\n    for chunck in input:\n        output = encode(chunck)\n        if output:\n            yield output\n    output = encode('', final=True)\n    if output:\n        yield output\n\n\nclass IncrementalDecoder(object):\n    \"\"\"\n    “Push”-based decoder.\n\n    :param fallback_encoding:\n        An :class:`Encoding` object or a label string.\n        The encoding to use if :obj:`input` does note have a BOM.\n    :param errors: Type of error handling. See :func:`codecs.register`.\n    :raises: :exc:`~exceptions.LookupError` for an unknown encoding label.\n\n    \"\"\"\n    def __init__(self, fallback_encoding, errors='replace'):\n        # Fail early if `encoding` is an invalid label.\n        self._fallback_encoding = _get_encoding(fallback_encoding)\n        self._errors = errors\n        self._buffer = b''\n        self._decoder = None\n        #: The actual :class:`Encoding` that is being used,\n        #: or :obj:`None` if that is not determined yet.\n        #: (Ie. if there is not enough input yet to determine\n        #: if there is a BOM.)\n        self.encoding = None  # Not known yet.\n\n    def decode(self, input, final=False):\n        \"\"\"Decode one chunk of the input.\n\n        :param input: A byte string.\n        :param final:\n            Indicate that no more input is available.\n            Must be :obj:`True` if this is the last call.\n        :returns: An Unicode string.\n\n        \"\"\"\n        decoder = self._decoder\n        if decoder is not None:\n            return decoder(input, final)\n\n        input = self._buffer + input\n        encoding, input = _detect_bom(input)\n        if encoding is None:\n            if len(input) < 3 and not final:  # Not enough data yet.\n                self._buffer = input\n                return ''\n            else:  # No BOM\n                encoding = self._fallback_encoding\n        decoder = encoding.codec_info.incrementaldecoder(self._errors).decode\n        self._decoder = decoder\n        self.encoding = encoding\n        return decoder(input, final)\n\n\nclass IncrementalEncoder(object):\n    \"\"\"\n    “Push”-based encoder.\n\n    :param encoding: An :class:`Encoding` object or a label string.\n    :param errors: Type of error handling. See :func:`codecs.register`.\n    :raises: :exc:`~exceptions.LookupError` for an unknown encoding label.\n\n    .. method:: encode(input, final=False)\n\n        :param input: An Unicode string.\n        :param final:\n            Indicate that no more input is available.\n            Must be :obj:`True` if this is the last call.\n        :returns: A byte string.\n\n    \"\"\"\n    def __init__(self, encoding=UTF8, errors='strict'):\n        encoding = _get_encoding(encoding)\n        self.encode = encoding.codec_info.incrementalencoder(errors).encode\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/webencodings/labels.py",
    "content": "\"\"\"\n\n    webencodings.labels\n    ~~~~~~~~~~~~~~~~~~~\n\n    Map encoding labels to their name.\n\n    :copyright: Copyright 2012 by Simon Sapin\n    :license: BSD, see LICENSE for details.\n\n\"\"\"\n\n# XXX Do not edit!\n# This file is automatically generated by mklabels.py\n\nLABELS = {\n    'unicode-1-1-utf-8':   'utf-8',\n    'utf-8':               'utf-8',\n    'utf8':                'utf-8',\n    '866':                 'ibm866',\n    'cp866':               'ibm866',\n    'csibm866':            'ibm866',\n    'ibm866':              'ibm866',\n    'csisolatin2':         'iso-8859-2',\n    'iso-8859-2':          'iso-8859-2',\n    'iso-ir-101':          'iso-8859-2',\n    'iso8859-2':           'iso-8859-2',\n    'iso88592':            'iso-8859-2',\n    'iso_8859-2':          'iso-8859-2',\n    'iso_8859-2:1987':     'iso-8859-2',\n    'l2':                  'iso-8859-2',\n    'latin2':              'iso-8859-2',\n    'csisolatin3':         'iso-8859-3',\n    'iso-8859-3':          'iso-8859-3',\n    'iso-ir-109':          'iso-8859-3',\n    'iso8859-3':           'iso-8859-3',\n    'iso88593':            'iso-8859-3',\n    'iso_8859-3':          'iso-8859-3',\n    'iso_8859-3:1988':     'iso-8859-3',\n    'l3':                  'iso-8859-3',\n    'latin3':              'iso-8859-3',\n    'csisolatin4':         'iso-8859-4',\n    'iso-8859-4':          'iso-8859-4',\n    'iso-ir-110':          'iso-8859-4',\n    'iso8859-4':           'iso-8859-4',\n    'iso88594':            'iso-8859-4',\n    'iso_8859-4':          'iso-8859-4',\n    'iso_8859-4:1988':     'iso-8859-4',\n    'l4':                  'iso-8859-4',\n    'latin4':              'iso-8859-4',\n    'csisolatincyrillic':  'iso-8859-5',\n    'cyrillic':            'iso-8859-5',\n    'iso-8859-5':          'iso-8859-5',\n    'iso-ir-144':          'iso-8859-5',\n    'iso8859-5':           'iso-8859-5',\n    'iso88595':            'iso-8859-5',\n    'iso_8859-5':          'iso-8859-5',\n    'iso_8859-5:1988':     'iso-8859-5',\n    'arabic':              'iso-8859-6',\n    'asmo-708':            'iso-8859-6',\n    'csiso88596e':         'iso-8859-6',\n    'csiso88596i':         'iso-8859-6',\n    'csisolatinarabic':    'iso-8859-6',\n    'ecma-114':            'iso-8859-6',\n    'iso-8859-6':          'iso-8859-6',\n    'iso-8859-6-e':        'iso-8859-6',\n    'iso-8859-6-i':        'iso-8859-6',\n    'iso-ir-127':          'iso-8859-6',\n    'iso8859-6':           'iso-8859-6',\n    'iso88596':            'iso-8859-6',\n    'iso_8859-6':          'iso-8859-6',\n    'iso_8859-6:1987':     'iso-8859-6',\n    'csisolatingreek':     'iso-8859-7',\n    'ecma-118':            'iso-8859-7',\n    'elot_928':            'iso-8859-7',\n    'greek':               'iso-8859-7',\n    'greek8':              'iso-8859-7',\n    'iso-8859-7':          'iso-8859-7',\n    'iso-ir-126':          'iso-8859-7',\n    'iso8859-7':           'iso-8859-7',\n    'iso88597':            'iso-8859-7',\n    'iso_8859-7':          'iso-8859-7',\n    'iso_8859-7:1987':     'iso-8859-7',\n    'sun_eu_greek':        'iso-8859-7',\n    'csiso88598e':         'iso-8859-8',\n    'csisolatinhebrew':    'iso-8859-8',\n    'hebrew':              'iso-8859-8',\n    'iso-8859-8':          'iso-8859-8',\n    'iso-8859-8-e':        'iso-8859-8',\n    'iso-ir-138':          'iso-8859-8',\n    'iso8859-8':           'iso-8859-8',\n    'iso88598':            'iso-8859-8',\n    'iso_8859-8':          'iso-8859-8',\n    'iso_8859-8:1988':     'iso-8859-8',\n    'visual':              'iso-8859-8',\n    'csiso88598i':         'iso-8859-8-i',\n    'iso-8859-8-i':        'iso-8859-8-i',\n    'logical':             'iso-8859-8-i',\n    'csisolatin6':         'iso-8859-10',\n    'iso-8859-10':         'iso-8859-10',\n    'iso-ir-157':          'iso-8859-10',\n    'iso8859-10':          'iso-8859-10',\n    'iso885910':           'iso-8859-10',\n    'l6':                  'iso-8859-10',\n    'latin6':              'iso-8859-10',\n    'iso-8859-13':         'iso-8859-13',\n    'iso8859-13':          'iso-8859-13',\n    'iso885913':           'iso-8859-13',\n    'iso-8859-14':         'iso-8859-14',\n    'iso8859-14':          'iso-8859-14',\n    'iso885914':           'iso-8859-14',\n    'csisolatin9':         'iso-8859-15',\n    'iso-8859-15':         'iso-8859-15',\n    'iso8859-15':          'iso-8859-15',\n    'iso885915':           'iso-8859-15',\n    'iso_8859-15':         'iso-8859-15',\n    'l9':                  'iso-8859-15',\n    'iso-8859-16':         'iso-8859-16',\n    'cskoi8r':             'koi8-r',\n    'koi':                 'koi8-r',\n    'koi8':                'koi8-r',\n    'koi8-r':              'koi8-r',\n    'koi8_r':              'koi8-r',\n    'koi8-u':              'koi8-u',\n    'csmacintosh':         'macintosh',\n    'mac':                 'macintosh',\n    'macintosh':           'macintosh',\n    'x-mac-roman':         'macintosh',\n    'dos-874':             'windows-874',\n    'iso-8859-11':         'windows-874',\n    'iso8859-11':          'windows-874',\n    'iso885911':           'windows-874',\n    'tis-620':             'windows-874',\n    'windows-874':         'windows-874',\n    'cp1250':              'windows-1250',\n    'windows-1250':        'windows-1250',\n    'x-cp1250':            'windows-1250',\n    'cp1251':              'windows-1251',\n    'windows-1251':        'windows-1251',\n    'x-cp1251':            'windows-1251',\n    'ansi_x3.4-1968':      'windows-1252',\n    'ascii':               'windows-1252',\n    'cp1252':              'windows-1252',\n    'cp819':               'windows-1252',\n    'csisolatin1':         'windows-1252',\n    'ibm819':              'windows-1252',\n    'iso-8859-1':          'windows-1252',\n    'iso-ir-100':          'windows-1252',\n    'iso8859-1':           'windows-1252',\n    'iso88591':            'windows-1252',\n    'iso_8859-1':          'windows-1252',\n    'iso_8859-1:1987':     'windows-1252',\n    'l1':                  'windows-1252',\n    'latin1':              'windows-1252',\n    'us-ascii':            'windows-1252',\n    'windows-1252':        'windows-1252',\n    'x-cp1252':            'windows-1252',\n    'cp1253':              'windows-1253',\n    'windows-1253':        'windows-1253',\n    'x-cp1253':            'windows-1253',\n    'cp1254':              'windows-1254',\n    'csisolatin5':         'windows-1254',\n    'iso-8859-9':          'windows-1254',\n    'iso-ir-148':          'windows-1254',\n    'iso8859-9':           'windows-1254',\n    'iso88599':            'windows-1254',\n    'iso_8859-9':          'windows-1254',\n    'iso_8859-9:1989':     'windows-1254',\n    'l5':                  'windows-1254',\n    'latin5':              'windows-1254',\n    'windows-1254':        'windows-1254',\n    'x-cp1254':            'windows-1254',\n    'cp1255':              'windows-1255',\n    'windows-1255':        'windows-1255',\n    'x-cp1255':            'windows-1255',\n    'cp1256':              'windows-1256',\n    'windows-1256':        'windows-1256',\n    'x-cp1256':            'windows-1256',\n    'cp1257':              'windows-1257',\n    'windows-1257':        'windows-1257',\n    'x-cp1257':            'windows-1257',\n    'cp1258':              'windows-1258',\n    'windows-1258':        'windows-1258',\n    'x-cp1258':            'windows-1258',\n    'x-mac-cyrillic':      'x-mac-cyrillic',\n    'x-mac-ukrainian':     'x-mac-cyrillic',\n    'chinese':             'gbk',\n    'csgb2312':            'gbk',\n    'csiso58gb231280':     'gbk',\n    'gb2312':              'gbk',\n    'gb_2312':             'gbk',\n    'gb_2312-80':          'gbk',\n    'gbk':                 'gbk',\n    'iso-ir-58':           'gbk',\n    'x-gbk':               'gbk',\n    'gb18030':             'gb18030',\n    'hz-gb-2312':          'hz-gb-2312',\n    'big5':                'big5',\n    'big5-hkscs':          'big5',\n    'cn-big5':             'big5',\n    'csbig5':              'big5',\n    'x-x-big5':            'big5',\n    'cseucpkdfmtjapanese': 'euc-jp',\n    'euc-jp':              'euc-jp',\n    'x-euc-jp':            'euc-jp',\n    'csiso2022jp':         'iso-2022-jp',\n    'iso-2022-jp':         'iso-2022-jp',\n    'csshiftjis':          'shift_jis',\n    'ms_kanji':            'shift_jis',\n    'shift-jis':           'shift_jis',\n    'shift_jis':           'shift_jis',\n    'sjis':                'shift_jis',\n    'windows-31j':         'shift_jis',\n    'x-sjis':              'shift_jis',\n    'cseuckr':             'euc-kr',\n    'csksc56011987':       'euc-kr',\n    'euc-kr':              'euc-kr',\n    'iso-ir-149':          'euc-kr',\n    'korean':              'euc-kr',\n    'ks_c_5601-1987':      'euc-kr',\n    'ks_c_5601-1989':      'euc-kr',\n    'ksc5601':             'euc-kr',\n    'ksc_5601':            'euc-kr',\n    'windows-949':         'euc-kr',\n    'csiso2022kr':         'iso-2022-kr',\n    'iso-2022-kr':         'iso-2022-kr',\n    'utf-16be':            'utf-16be',\n    'utf-16':              'utf-16le',\n    'utf-16le':            'utf-16le',\n    'x-user-defined':      'x-user-defined',\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/webencodings/mklabels.py",
    "content": "\"\"\"\n\n    webencodings.mklabels\n    ~~~~~~~~~~~~~~~~~~~~~\n\n    Regenarate the webencodings.labels module.\n\n    :copyright: Copyright 2012 by Simon Sapin\n    :license: BSD, see LICENSE for details.\n\n\"\"\"\n\nimport json\ntry:\n    from urllib import urlopen\nexcept ImportError:\n    from urllib.request import urlopen\n\n\ndef assert_lower(string):\n    assert string == string.lower()\n    return string\n\n\ndef generate(url):\n    parts = ['''\\\n\"\"\"\n\n    webencodings.labels\n    ~~~~~~~~~~~~~~~~~~~\n\n    Map encoding labels to their name.\n\n    :copyright: Copyright 2012 by Simon Sapin\n    :license: BSD, see LICENSE for details.\n\n\"\"\"\n\n# XXX Do not edit!\n# This file is automatically generated by mklabels.py\n\nLABELS = {\n''']\n    labels = [\n        (repr(assert_lower(label)).lstrip('u'),\n         repr(encoding['name']).lstrip('u'))\n        for category in json.loads(urlopen(url).read().decode('ascii'))\n        for encoding in category['encodings']\n        for label in encoding['labels']]\n    max_len = max(len(label) for label, name in labels)\n    parts.extend(\n        '    %s:%s %s,\\n' % (label, ' ' * (max_len - len(label)), name)\n        for label, name in labels)\n    parts.append('}')\n    return ''.join(parts)\n\n\nif __name__ == '__main__':\n    print(generate('http://encoding.spec.whatwg.org/encodings.json'))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/webencodings/tests.py",
    "content": "# coding: utf-8\n\"\"\"\n\n    webencodings.tests\n    ~~~~~~~~~~~~~~~~~~\n\n    A basic test suite for Encoding.\n\n    :copyright: Copyright 2012 by Simon Sapin\n    :license: BSD, see LICENSE for details.\n\n\"\"\"\n\nfrom __future__ import unicode_literals\n\nfrom . import (lookup, LABELS, decode, encode, iter_decode, iter_encode,\n               IncrementalDecoder, IncrementalEncoder, UTF8)\n\n\ndef assert_raises(exception, function, *args, **kwargs):\n    try:\n        function(*args, **kwargs)\n    except exception:\n        return\n    else:  # pragma: no cover\n        raise AssertionError('Did not raise %s.' % exception)\n\n\ndef test_labels():\n    assert lookup('utf-8').name == 'utf-8'\n    assert lookup('Utf-8').name == 'utf-8'\n    assert lookup('UTF-8').name == 'utf-8'\n    assert lookup('utf8').name == 'utf-8'\n    assert lookup('utf8').name == 'utf-8'\n    assert lookup('utf8 ').name == 'utf-8'\n    assert lookup(' \\r\\nutf8\\t').name == 'utf-8'\n    assert lookup('u8') is None  # Python label.\n    assert lookup('utf-8 ') is None  # Non-ASCII white space.\n\n    assert lookup('US-ASCII').name == 'windows-1252'\n    assert lookup('iso-8859-1').name == 'windows-1252'\n    assert lookup('latin1').name == 'windows-1252'\n    assert lookup('LATIN1').name == 'windows-1252'\n    assert lookup('latin-1') is None\n    assert lookup('LATİN1') is None  # ASCII-only case insensitivity.\n\n\ndef test_all_labels():\n    for label in LABELS:\n        assert decode(b'', label) == ('', lookup(label))\n        assert encode('', label) == b''\n        for repeat in [0, 1, 12]:\n            output, _ = iter_decode([b''] * repeat, label)\n            assert list(output) == []\n            assert list(iter_encode([''] * repeat, label)) == []\n        decoder = IncrementalDecoder(label)\n        assert decoder.decode(b'') == ''\n        assert decoder.decode(b'', final=True) == ''\n        encoder = IncrementalEncoder(label)\n        assert encoder.encode('') == b''\n        assert encoder.encode('', final=True) == b''\n    # All encoding names are valid labels too:\n    for name in set(LABELS.values()):\n        assert lookup(name).name == name\n\n\ndef test_invalid_label():\n    assert_raises(LookupError, decode, b'\\xEF\\xBB\\xBF\\xc3\\xa9', 'invalid')\n    assert_raises(LookupError, encode, 'é', 'invalid')\n    assert_raises(LookupError, iter_decode, [], 'invalid')\n    assert_raises(LookupError, iter_encode, [], 'invalid')\n    assert_raises(LookupError, IncrementalDecoder, 'invalid')\n    assert_raises(LookupError, IncrementalEncoder, 'invalid')\n\n\ndef test_decode():\n    assert decode(b'\\x80', 'latin1') == ('€', lookup('latin1'))\n    assert decode(b'\\x80', lookup('latin1')) == ('€', lookup('latin1'))\n    assert decode(b'\\xc3\\xa9', 'utf8') == ('é', lookup('utf8'))\n    assert decode(b'\\xc3\\xa9', UTF8) == ('é', lookup('utf8'))\n    assert decode(b'\\xc3\\xa9', 'ascii') == ('Ã©', lookup('ascii'))\n    assert decode(b'\\xEF\\xBB\\xBF\\xc3\\xa9', 'ascii') == ('é', lookup('utf8'))  # UTF-8 with BOM\n\n    assert decode(b'\\xFE\\xFF\\x00\\xe9', 'ascii') == ('é', lookup('utf-16be'))  # UTF-16-BE with BOM\n    assert decode(b'\\xFF\\xFE\\xe9\\x00', 'ascii') == ('é', lookup('utf-16le'))  # UTF-16-LE with BOM\n    assert decode(b'\\xFE\\xFF\\xe9\\x00', 'ascii') == ('\\ue900', lookup('utf-16be'))\n    assert decode(b'\\xFF\\xFE\\x00\\xe9', 'ascii') == ('\\ue900', lookup('utf-16le'))\n\n    assert decode(b'\\x00\\xe9', 'UTF-16BE') == ('é', lookup('utf-16be'))\n    assert decode(b'\\xe9\\x00', 'UTF-16LE') == ('é', lookup('utf-16le'))\n    assert decode(b'\\xe9\\x00', 'UTF-16') == ('é', lookup('utf-16le'))\n\n    assert decode(b'\\xe9\\x00', 'UTF-16BE') == ('\\ue900', lookup('utf-16be'))\n    assert decode(b'\\x00\\xe9', 'UTF-16LE') == ('\\ue900', lookup('utf-16le'))\n    assert decode(b'\\x00\\xe9', 'UTF-16') == ('\\ue900', lookup('utf-16le'))\n\n\ndef test_encode():\n    assert encode('é', 'latin1') == b'\\xe9'\n    assert encode('é', 'utf8') == b'\\xc3\\xa9'\n    assert encode('é', 'utf8') == b'\\xc3\\xa9'\n    assert encode('é', 'utf-16') == b'\\xe9\\x00'\n    assert encode('é', 'utf-16le') == b'\\xe9\\x00'\n    assert encode('é', 'utf-16be') == b'\\x00\\xe9'\n\n\ndef test_iter_decode():\n    def iter_decode_to_string(input, fallback_encoding):\n        output, _encoding = iter_decode(input, fallback_encoding)\n        return ''.join(output)\n    assert iter_decode_to_string([], 'latin1') == ''\n    assert iter_decode_to_string([b''], 'latin1') == ''\n    assert iter_decode_to_string([b'\\xe9'], 'latin1') == 'é'\n    assert iter_decode_to_string([b'hello'], 'latin1') == 'hello'\n    assert iter_decode_to_string([b'he', b'llo'], 'latin1') == 'hello'\n    assert iter_decode_to_string([b'hell', b'o'], 'latin1') == 'hello'\n    assert iter_decode_to_string([b'\\xc3\\xa9'], 'latin1') == 'Ã©'\n    assert iter_decode_to_string([b'\\xEF\\xBB\\xBF\\xc3\\xa9'], 'latin1') == 'é'\n    assert iter_decode_to_string([\n        b'\\xEF\\xBB\\xBF', b'\\xc3', b'\\xa9'], 'latin1') == 'é'\n    assert iter_decode_to_string([\n        b'\\xEF\\xBB\\xBF', b'a', b'\\xc3'], 'latin1') == 'a\\uFFFD'\n    assert iter_decode_to_string([\n        b'', b'\\xEF', b'', b'', b'\\xBB\\xBF\\xc3', b'\\xa9'], 'latin1') == 'é'\n    assert iter_decode_to_string([b'\\xEF\\xBB\\xBF'], 'latin1') == ''\n    assert iter_decode_to_string([b'\\xEF\\xBB'], 'latin1') == 'ï»'\n    assert iter_decode_to_string([b'\\xFE\\xFF\\x00\\xe9'], 'latin1') == 'é'\n    assert iter_decode_to_string([b'\\xFF\\xFE\\xe9\\x00'], 'latin1') == 'é'\n    assert iter_decode_to_string([\n        b'', b'\\xFF', b'', b'', b'\\xFE\\xe9', b'\\x00'], 'latin1') == 'é'\n    assert iter_decode_to_string([\n        b'', b'h\\xe9', b'llo'], 'x-user-defined') == 'h\\uF7E9llo'\n\n\ndef test_iter_encode():\n    assert b''.join(iter_encode([], 'latin1')) == b''\n    assert b''.join(iter_encode([''], 'latin1')) == b''\n    assert b''.join(iter_encode(['é'], 'latin1')) == b'\\xe9'\n    assert b''.join(iter_encode(['', 'é', '', ''], 'latin1')) == b'\\xe9'\n    assert b''.join(iter_encode(['', 'é', '', ''], 'utf-16')) == b'\\xe9\\x00'\n    assert b''.join(iter_encode(['', 'é', '', ''], 'utf-16le')) == b'\\xe9\\x00'\n    assert b''.join(iter_encode(['', 'é', '', ''], 'utf-16be')) == b'\\x00\\xe9'\n    assert b''.join(iter_encode([\n        '', 'h\\uF7E9', '', 'llo'], 'x-user-defined')) == b'h\\xe9llo'\n\n\ndef test_x_user_defined():\n    encoded = b'2,\\x0c\\x0b\\x1aO\\xd9#\\xcb\\x0f\\xc9\\xbbt\\xcf\\xa8\\xca'\n    decoded = '2,\\x0c\\x0b\\x1aO\\uf7d9#\\uf7cb\\x0f\\uf7c9\\uf7bbt\\uf7cf\\uf7a8\\uf7ca'\n    encoded = b'aa'\n    decoded = 'aa'\n    assert decode(encoded, 'x-user-defined') == (decoded, lookup('x-user-defined'))\n    assert encode(decoded, 'x-user-defined') == encoded\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pip-19.0.3-py3.6.egg/pip/_vendor/webencodings/x_user_defined.py",
    "content": "# coding: utf-8\n\"\"\"\n\n    webencodings.x_user_defined\n    ~~~~~~~~~~~~~~~~~~~~~~~~~~~\n\n    An implementation of the x-user-defined encoding.\n\n    :copyright: Copyright 2012 by Simon Sapin\n    :license: BSD, see LICENSE for details.\n\n\"\"\"\n\nfrom __future__ import unicode_literals\n\nimport codecs\n\n\n### Codec APIs\n\nclass Codec(codecs.Codec):\n\n    def encode(self, input, errors='strict'):\n        return codecs.charmap_encode(input, errors, encoding_table)\n\n    def decode(self, input, errors='strict'):\n        return codecs.charmap_decode(input, errors, decoding_table)\n\n\nclass IncrementalEncoder(codecs.IncrementalEncoder):\n    def encode(self, input, final=False):\n        return codecs.charmap_encode(input, self.errors, encoding_table)[0]\n\n\nclass IncrementalDecoder(codecs.IncrementalDecoder):\n    def decode(self, input, final=False):\n        return codecs.charmap_decode(input, self.errors, decoding_table)[0]\n\n\nclass StreamWriter(Codec, codecs.StreamWriter):\n    pass\n\n\nclass StreamReader(Codec, codecs.StreamReader):\n    pass\n\n\n### encodings module API\n\ncodec_info = codecs.CodecInfo(\n    name='x-user-defined',\n    encode=Codec().encode,\n    decode=Codec().decode,\n    incrementalencoder=IncrementalEncoder,\n    incrementaldecoder=IncrementalDecoder,\n    streamreader=StreamReader,\n    streamwriter=StreamWriter,\n)\n\n\n### Decoding Table\n\n# Python 3:\n# for c in range(256): print('    %r' % chr(c if c < 128 else c + 0xF700))\ndecoding_table = (\n    '\\x00'\n    '\\x01'\n    '\\x02'\n    '\\x03'\n    '\\x04'\n    '\\x05'\n    '\\x06'\n    '\\x07'\n    '\\x08'\n    '\\t'\n    '\\n'\n    '\\x0b'\n    '\\x0c'\n    '\\r'\n    '\\x0e'\n    '\\x0f'\n    '\\x10'\n    '\\x11'\n    '\\x12'\n    '\\x13'\n    '\\x14'\n    '\\x15'\n    '\\x16'\n    '\\x17'\n    '\\x18'\n    '\\x19'\n    '\\x1a'\n    '\\x1b'\n    '\\x1c'\n    '\\x1d'\n    '\\x1e'\n    '\\x1f'\n    ' '\n    '!'\n    '\"'\n    '#'\n    '$'\n    '%'\n    '&'\n    \"'\"\n    '('\n    ')'\n    '*'\n    '+'\n    ','\n    '-'\n    '.'\n    '/'\n    '0'\n    '1'\n    '2'\n    '3'\n    '4'\n    '5'\n    '6'\n    '7'\n    '8'\n    '9'\n    ':'\n    ';'\n    '<'\n    '='\n    '>'\n    '?'\n    '@'\n    'A'\n    'B'\n    'C'\n    'D'\n    'E'\n    'F'\n    'G'\n    'H'\n    'I'\n    'J'\n    'K'\n    'L'\n    'M'\n    'N'\n    'O'\n    'P'\n    'Q'\n    'R'\n    'S'\n    'T'\n    'U'\n    'V'\n    'W'\n    'X'\n    'Y'\n    'Z'\n    '['\n    '\\\\'\n    ']'\n    '^'\n    '_'\n    '`'\n    'a'\n    'b'\n    'c'\n    'd'\n    'e'\n    'f'\n    'g'\n    'h'\n    'i'\n    'j'\n    'k'\n    'l'\n    'm'\n    'n'\n    'o'\n    'p'\n    'q'\n    'r'\n    's'\n    't'\n    'u'\n    'v'\n    'w'\n    'x'\n    'y'\n    'z'\n    '{'\n    '|'\n    '}'\n    '~'\n    '\\x7f'\n    '\\uf780'\n    '\\uf781'\n    '\\uf782'\n    '\\uf783'\n    '\\uf784'\n    '\\uf785'\n    '\\uf786'\n    '\\uf787'\n    '\\uf788'\n    '\\uf789'\n    '\\uf78a'\n    '\\uf78b'\n    '\\uf78c'\n    '\\uf78d'\n    '\\uf78e'\n    '\\uf78f'\n    '\\uf790'\n    '\\uf791'\n    '\\uf792'\n    '\\uf793'\n    '\\uf794'\n    '\\uf795'\n    '\\uf796'\n    '\\uf797'\n    '\\uf798'\n    '\\uf799'\n    '\\uf79a'\n    '\\uf79b'\n    '\\uf79c'\n    '\\uf79d'\n    '\\uf79e'\n    '\\uf79f'\n    '\\uf7a0'\n    '\\uf7a1'\n    '\\uf7a2'\n    '\\uf7a3'\n    '\\uf7a4'\n    '\\uf7a5'\n    '\\uf7a6'\n    '\\uf7a7'\n    '\\uf7a8'\n    '\\uf7a9'\n    '\\uf7aa'\n    '\\uf7ab'\n    '\\uf7ac'\n    '\\uf7ad'\n    '\\uf7ae'\n    '\\uf7af'\n    '\\uf7b0'\n    '\\uf7b1'\n    '\\uf7b2'\n    '\\uf7b3'\n    '\\uf7b4'\n    '\\uf7b5'\n    '\\uf7b6'\n    '\\uf7b7'\n    '\\uf7b8'\n    '\\uf7b9'\n    '\\uf7ba'\n    '\\uf7bb'\n    '\\uf7bc'\n    '\\uf7bd'\n    '\\uf7be'\n    '\\uf7bf'\n    '\\uf7c0'\n    '\\uf7c1'\n    '\\uf7c2'\n    '\\uf7c3'\n    '\\uf7c4'\n    '\\uf7c5'\n    '\\uf7c6'\n    '\\uf7c7'\n    '\\uf7c8'\n    '\\uf7c9'\n    '\\uf7ca'\n    '\\uf7cb'\n    '\\uf7cc'\n    '\\uf7cd'\n    '\\uf7ce'\n    '\\uf7cf'\n    '\\uf7d0'\n    '\\uf7d1'\n    '\\uf7d2'\n    '\\uf7d3'\n    '\\uf7d4'\n    '\\uf7d5'\n    '\\uf7d6'\n    '\\uf7d7'\n    '\\uf7d8'\n    '\\uf7d9'\n    '\\uf7da'\n    '\\uf7db'\n    '\\uf7dc'\n    '\\uf7dd'\n    '\\uf7de'\n    '\\uf7df'\n    '\\uf7e0'\n    '\\uf7e1'\n    '\\uf7e2'\n    '\\uf7e3'\n    '\\uf7e4'\n    '\\uf7e5'\n    '\\uf7e6'\n    '\\uf7e7'\n    '\\uf7e8'\n    '\\uf7e9'\n    '\\uf7ea'\n    '\\uf7eb'\n    '\\uf7ec'\n    '\\uf7ed'\n    '\\uf7ee'\n    '\\uf7ef'\n    '\\uf7f0'\n    '\\uf7f1'\n    '\\uf7f2'\n    '\\uf7f3'\n    '\\uf7f4'\n    '\\uf7f5'\n    '\\uf7f6'\n    '\\uf7f7'\n    '\\uf7f8'\n    '\\uf7f9'\n    '\\uf7fa'\n    '\\uf7fb'\n    '\\uf7fc'\n    '\\uf7fd'\n    '\\uf7fe'\n    '\\uf7ff'\n)\n\n### Encoding table\nencoding_table = codecs.charmap_build(decoding_table)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyOpenSSL-19.0.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyOpenSSL-19.0.0.dist-info/LICENSE",
    "content": "\n                                 Apache License\n                           Version 2.0, January 2004\n                        http://www.apache.org/licenses/\n\n   TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION\n\n   1. Definitions.\n\n      \"License\" shall mean the terms and conditions for use, reproduction,\n      and distribution as defined by Sections 1 through 9 of this document.\n\n      \"Licensor\" shall mean the copyright owner or entity authorized by\n      the copyright owner that is granting the License.\n\n      \"Legal Entity\" shall mean the union of the acting entity and all\n      other entities that control, are controlled by, or are under common\n      control with that entity. For the purposes of this definition,\n      \"control\" means (i) the power, direct or indirect, to cause the\n      direction or management of such entity, whether by contract or\n      otherwise, or (ii) ownership of fifty percent (50%) or more of the\n      outstanding shares, or (iii) beneficial ownership of such entity.\n\n      \"You\" (or \"Your\") shall mean an individual or Legal Entity\n      exercising permissions granted by this License.\n\n      \"Source\" form shall mean the preferred form for making modifications,\n      including but not limited to software source code, documentation\n      source, and configuration files.\n\n      \"Object\" form shall mean any form resulting from mechanical\n      transformation or translation of a Source form, including but\n      not limited to compiled object code, generated documentation,\n      and conversions to other media types.\n\n      \"Work\" shall mean the work of authorship, whether in Source or\n      Object form, made available under the License, as indicated by a\n      copyright notice that is included in or attached to the work\n      (an example is provided in the Appendix below).\n\n      \"Derivative Works\" shall mean any work, whether in Source or Object\n      form, that is based on (or derived from) the Work and for which the\n      editorial revisions, annotations, elaborations, or other modifications\n      represent, as a whole, an original work of authorship. For the purposes\n      of this License, Derivative Works shall not include works that remain\n      separable from, or merely link (or bind by name) to the interfaces of,\n      the Work and Derivative Works thereof.\n\n      \"Contribution\" shall mean any work of authorship, including\n      the original version of the Work and any modifications or additions\n      to that Work or Derivative Works thereof, that is intentionally\n      submitted to Licensor for inclusion in the Work by the copyright owner\n      or by an individual or Legal Entity authorized to submit on behalf of\n      the copyright owner. For the purposes of this definition, \"submitted\"\n      means any form of electronic, verbal, or written communication sent\n      to the Licensor or its representatives, including but not limited to\n      communication on electronic mailing lists, source code control systems,\n      and issue tracking systems that are managed by, or on behalf of, the\n      Licensor for the purpose of discussing and improving the Work, but\n      excluding communication that is conspicuously marked or otherwise\n      designated in writing by the copyright owner as \"Not a Contribution.\"\n\n      \"Contributor\" shall mean Licensor and any individual or Legal Entity\n      on behalf of whom a Contribution has been received by Licensor and\n      subsequently incorporated within the Work.\n\n   2. Grant of Copyright License. Subject to the terms and conditions of\n      this License, each Contributor hereby grants to You a perpetual,\n      worldwide, non-exclusive, no-charge, royalty-free, irrevocable\n      copyright license to reproduce, prepare Derivative Works of,\n      publicly display, publicly perform, sublicense, and distribute the\n      Work and such Derivative Works in Source or Object form.\n\n   3. Grant of Patent License. Subject to the terms and conditions of\n      this License, each Contributor hereby grants to You a perpetual,\n      worldwide, non-exclusive, no-charge, royalty-free, irrevocable\n      (except as stated in this section) patent license to make, have made,\n      use, offer to sell, sell, import, and otherwise transfer the Work,\n      where such license applies only to those patent claims licensable\n      by such Contributor that are necessarily infringed by their\n      Contribution(s) alone or by combination of their Contribution(s)\n      with the Work to which such Contribution(s) was submitted. If You\n      institute patent litigation against any entity (including a\n      cross-claim or counterclaim in a lawsuit) alleging that the Work\n      or a Contribution incorporated within the Work constitutes direct\n      or contributory patent infringement, then any patent licenses\n      granted to You under this License for that Work shall terminate\n      as of the date such litigation is filed.\n\n   4. Redistribution. You may reproduce and distribute copies of the\n      Work or Derivative Works thereof in any medium, with or without\n      modifications, and in Source or Object form, provided that You\n      meet the following conditions:\n\n      (a) You must give any other recipients of the Work or\n          Derivative Works a copy of this License; and\n\n      (b) You must cause any modified files to carry prominent notices\n          stating that You changed the files; and\n\n      (c) You must retain, in the Source form of any Derivative Works\n          that You distribute, all copyright, patent, trademark, and\n          attribution notices from the Source form of the Work,\n          excluding those notices that do not pertain to any part of\n          the Derivative Works; and\n\n      (d) If the Work includes a \"NOTICE\" text file as part of its\n          distribution, then any Derivative Works that You distribute must\n          include a readable copy of the attribution notices contained\n          within such NOTICE file, excluding those notices that do not\n          pertain to any part of the Derivative Works, in at least one\n          of the following places: within a NOTICE text file distributed\n          as part of the Derivative Works; within the Source form or\n          documentation, if provided along with the Derivative Works; or,\n          within a display generated by the Derivative Works, if and\n          wherever such third-party notices normally appear. The contents\n          of the NOTICE file are for informational purposes only and\n          do not modify the License. You may add Your own attribution\n          notices within Derivative Works that You distribute, alongside\n          or as an addendum to the NOTICE text from the Work, provided\n          that such additional attribution notices cannot be construed\n          as modifying the License.\n\n      You may add Your own copyright statement to Your modifications and\n      may provide additional or different license terms and conditions\n      for use, reproduction, or distribution of Your modifications, or\n      for any such Derivative Works as a whole, provided Your use,\n      reproduction, and distribution of the Work otherwise complies with\n      the conditions stated in this License.\n\n   5. Submission of Contributions. Unless You explicitly state otherwise,\n      any Contribution intentionally submitted for inclusion in the Work\n      by You to the Licensor shall be under the terms and conditions of\n      this License, without any additional terms or conditions.\n      Notwithstanding the above, nothing herein shall supersede or modify\n      the terms of any separate license agreement you may have executed\n      with Licensor regarding such Contributions.\n\n   6. Trademarks. This License does not grant permission to use the trade\n      names, trademarks, service marks, or product names of the Licensor,\n      except as required for reasonable and customary use in describing the\n      origin of the Work and reproducing the content of the NOTICE file.\n\n   7. Disclaimer of Warranty. Unless required by applicable law or\n      agreed to in writing, Licensor provides the Work (and each\n      Contributor provides its Contributions) on an \"AS IS\" BASIS,\n      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n      implied, including, without limitation, any warranties or conditions\n      of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A\n      PARTICULAR PURPOSE. You are solely responsible for determining the\n      appropriateness of using or redistributing the Work and assume any\n      risks associated with Your exercise of permissions under this License.\n\n   8. Limitation of Liability. In no event and under no legal theory,\n      whether in tort (including negligence), contract, or otherwise,\n      unless required by applicable law (such as deliberate and grossly\n      negligent acts) or agreed to in writing, shall any Contributor be\n      liable to You for damages, including any direct, indirect, special,\n      incidental, or consequential damages of any character arising as a\n      result of this License or out of the use or inability to use the\n      Work (including but not limited to damages for loss of goodwill,\n      work stoppage, computer failure or malfunction, or any and all\n      other commercial damages or losses), even if such Contributor\n      has been advised of the possibility of such damages.\n\n   9. Accepting Warranty or Additional Liability. While redistributing\n      the Work or Derivative Works thereof, You may choose to offer,\n      and charge a fee for, acceptance of support, warranty, indemnity,\n      or other liability obligations and/or rights consistent with this\n      License. However, in accepting such obligations, You may act only\n      on Your own behalf and on Your sole responsibility, not on behalf\n      of any other Contributor, and only if You agree to indemnify,\n      defend, and hold each Contributor harmless for any liability\n      incurred by, or claims asserted against, such Contributor by reason\n      of your accepting any such warranty or additional liability.\n\n   END OF TERMS AND CONDITIONS\n\n   APPENDIX: How to apply the Apache License to your work.\n\n      To apply the Apache License to your work, attach the following\n      boilerplate notice, with the fields enclosed by brackets \"[]\"\n      replaced with your own identifying information. (Don't include\n      the brackets!)  The text should be enclosed in the appropriate\n      comment syntax for the file format. We also recommend that a\n      file or class name and description of purpose be included on the\n      same \"printed page\" as the copyright notice for easier\n      identification within third-party archives.\n\n   Copyright [yyyy] [name of copyright owner]\n\n   Licensed under the Apache License, Version 2.0 (the \"License\");\n   you may not use this file except in compliance with the License.\n   You may obtain a copy of the License at\n\n       http://www.apache.org/licenses/LICENSE-2.0\n\n   Unless required by applicable law or agreed to in writing, software\n   distributed under the License is distributed on an \"AS IS\" BASIS,\n   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n   See the License for the specific language governing permissions and\n   limitations under the License.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyOpenSSL-19.0.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: pyOpenSSL\nVersion: 19.0.0\nSummary: Python wrapper module around the OpenSSL library\nHome-page: https://pyopenssl.org/\nAuthor: The pyOpenSSL developers\nAuthor-email: cryptography-dev@python.org\nMaintainer: Hynek Schlawack\nMaintainer-email: hs@ox.cx\nLicense: Apache License, Version 2.0\nPlatform: UNKNOWN\nClassifier: Development Status :: 6 - Mature\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: Apache Software License\nClassifier: Operating System :: MacOS :: MacOS X\nClassifier: Operating System :: Microsoft :: Windows\nClassifier: Operating System :: POSIX\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nClassifier: Programming Language :: Python :: Implementation :: CPython\nClassifier: Programming Language :: Python :: Implementation :: PyPy\nClassifier: Topic :: Security :: Cryptography\nClassifier: Topic :: Software Development :: Libraries :: Python Modules\nClassifier: Topic :: System :: Networking\nRequires-Dist: cryptography (>=2.3)\nRequires-Dist: six (>=1.5.2)\nProvides-Extra: docs\nRequires-Dist: sphinx ; extra == 'docs'\nRequires-Dist: sphinx-rtd-theme ; extra == 'docs'\nProvides-Extra: test\nRequires-Dist: flaky ; extra == 'test'\nRequires-Dist: pretend ; extra == 'test'\nRequires-Dist: pytest (>=3.0.1) ; extra == 'test'\n\n========================================================\npyOpenSSL -- A Python wrapper around the OpenSSL library\n========================================================\n\n.. image:: https://readthedocs.org/projects/pyopenssl/badge/?version=stable\n   :target: https://pyopenssl.org/en/stable/\n   :alt: Stable Docs\n\n.. image:: https://travis-ci.org/pyca/pyopenssl.svg?branch=master\n   :target: https://travis-ci.org/pyca/pyopenssl\n   :alt: Build status\n\n.. image:: https://codecov.io/github/pyca/pyopenssl/branch/master/graph/badge.svg\n   :target: https://codecov.io/github/pyca/pyopenssl\n   :alt: Test coverage\n\n**Note:** The Python Cryptographic Authority **strongly suggests** the use of `pyca/cryptography`_\nwhere possible. If you are using pyOpenSSL for anything other than making a TLS connection \n**you should move to cryptography and drop your pyOpenSSL dependency**.\n\nHigh-level wrapper around a subset of the OpenSSL library. Includes\n\n* ``SSL.Connection`` objects, wrapping the methods of Python's portable sockets\n* Callbacks written in Python\n* Extensive error-handling mechanism, mirroring OpenSSL's error codes\n\n... and much more.\n\nYou can find more information in the documentation_.\nDevelopment takes place on GitHub_.\n\n\nDiscussion\n==========\n\nIf you run into bugs, you can file them in our `issue tracker`_.\n\nWe maintain a cryptography-dev_ mailing list for both user and development discussions.\n\nYou can also join ``#cryptography-dev`` on Freenode to ask questions or get involved.\n\n\n.. _documentation: https://pyopenssl.org/\n.. _`issue tracker`: https://github.com/pyca/pyopenssl/issues\n.. _cryptography-dev: https://mail.python.org/mailman/listinfo/cryptography-dev\n.. _GitHub: https://github.com/pyca/pyopenssl\n.. _`pyca/cryptography`: https://github.com/pyca/cryptography\n\n\nRelease Information\n===================\n\n19.0.0 (2019-01-21)\n-------------------\n\n\nBackward-incompatible changes:\n^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n\n- ``X509Store.add_cert`` no longer raises an error if you add a duplicate cert.\n  `#787 <https://github.com/pyca/pyopenssl/pull/787>`_\n\n\nDeprecations:\n^^^^^^^^^^^^^\n\n*none*\n\n\nChanges:\n^^^^^^^^\n\n- pyOpenSSL now works with OpenSSL 1.1.1.\n  `#805 <https://github.com/pyca/pyopenssl/pull/805>`_\n- pyOpenSSL now handles NUL bytes in ``X509Name.get_components()``\n  `#804 <https://github.com/pyca/pyopenssl/pull/804>`_\n\n\n`Full changelog <https://pyopenssl.org/en/stable/changelog.html>`_.\n\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyOpenSSL-19.0.0.dist-info/RECORD",
    "content": "OpenSSL/SSL.py,sha256=4O3XFJ0B1wb6ZL4mug-u5a7rBUMmn2Ephz4--4GfbxI,88967\r\nOpenSSL/__init__.py,sha256=1R5pO1yNiTgRht2uV5rEhbsv7zTSWS7QD9jV8SmHGQg,447\r\nOpenSSL/__pycache__/SSL.cpython-36.pyc,,\r\nOpenSSL/__pycache__/__init__.cpython-36.pyc,,\r\nOpenSSL/__pycache__/_util.cpython-36.pyc,,\r\nOpenSSL/__pycache__/crypto.cpython-36.pyc,,\r\nOpenSSL/__pycache__/debug.cpython-36.pyc,,\r\nOpenSSL/__pycache__/rand.cpython-36.pyc,,\r\nOpenSSL/__pycache__/tsafe.cpython-36.pyc,,\r\nOpenSSL/__pycache__/version.cpython-36.pyc,,\r\nOpenSSL/_util.py,sha256=oGSrLJ4ff6NGc6DyVVEnQsmD2TsLz1rxqsDX2Ez3_Ok,4174\r\nOpenSSL/crypto.py,sha256=zCj7anSky05ynv9W-vjGEXvpVzwCDtJhKf0svnqdRyE,100500\r\nOpenSSL/debug.py,sha256=Zx6GGBXqk4oqt5gXrZjOXRqiCnAx7yEJMWSfDxPgMB8,1049\r\nOpenSSL/rand.py,sha256=9CGox0RJbrrdH1L7SisEQYhcOp0ygphuI801OzYwSoE,1042\r\nOpenSSL/tsafe.py,sha256=WkPK8-auBQkXmNKs8AAp6pBM6NsDuxlQ0CKVmaManII,1102\r\nOpenSSL/version.py,sha256=9A9uVqzjZMHWQoTmlwabfaEz0lj9j61nU6ALDXeeYZU,626\r\npyOpenSSL-19.0.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\npyOpenSSL-19.0.0.dist-info/LICENSE,sha256=z8d0m5b2O9McPEK1xHG_dWgUBT6EfBDz6wA0F7xSPTA,11358\r\npyOpenSSL-19.0.0.dist-info/METADATA,sha256=ZUvmhkFxLcmenp6gTCXdboaFG05bmKPkzOi4WSlbpt4,4028\r\npyOpenSSL-19.0.0.dist-info/RECORD,,\r\npyOpenSSL-19.0.0.dist-info/WHEEL,sha256=_wJFdOYk7i3xxT8ElOkUJvOdOvfNGbR9g-bf6UQT6sU,110\r\npyOpenSSL-19.0.0.dist-info/top_level.txt,sha256=NNxWqS8hKNJh2cUXa1RZOMX62VJfyd8URo1TsYnR_MU,8\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyOpenSSL-19.0.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.32.3)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyOpenSSL-19.0.0.dist-info/top_level.txt",
    "content": "OpenSSL\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/__init__.py",
    "content": "import sys\n\n# https://www.python.org/dev/peps/pep-0396/\n__version__ = '0.4.7'\n\nif sys.version_info[:2] < (2, 4):\n    raise RuntimeError('PyASN1 requires Python 2.4 or later')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/__init__.py",
    "content": "# This file is necessary to make this directory a package.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/ber/__init__.py",
    "content": "# This file is necessary to make this directory a package.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/ber/decoder.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom pyasn1 import debug\nfrom pyasn1 import error\nfrom pyasn1.codec.ber import eoo\nfrom pyasn1.compat.integer import from_bytes\nfrom pyasn1.compat.octets import oct2int, octs2ints, ints2octs, null\nfrom pyasn1.type import base\nfrom pyasn1.type import char\nfrom pyasn1.type import tag\nfrom pyasn1.type import tagmap\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\n__all__ = ['decode']\n\nLOG = debug.registerLoggee(__name__, flags=debug.DEBUG_DECODER)\n\nnoValue = base.noValue\n\n\nclass AbstractDecoder(object):\n    protoComponent = None\n\n    def valueDecoder(self, substrate, asn1Spec,\n                     tagSet=None, length=None, state=None,\n                     decodeFun=None, substrateFun=None,\n                     **options):\n        raise error.PyAsn1Error('Decoder not implemented for %s' % (tagSet,))\n\n    def indefLenValueDecoder(self, substrate, asn1Spec,\n                             tagSet=None, length=None, state=None,\n                             decodeFun=None, substrateFun=None,\n                             **options):\n        raise error.PyAsn1Error('Indefinite length mode decoder not implemented for %s' % (tagSet,))\n\n\nclass AbstractSimpleDecoder(AbstractDecoder):\n    @staticmethod\n    def substrateCollector(asn1Object, substrate, length):\n        return substrate[:length], substrate[length:]\n\n    def _createComponent(self, asn1Spec, tagSet, value, **options):\n        if options.get('native'):\n            return value\n        elif asn1Spec is None:\n            return self.protoComponent.clone(value, tagSet=tagSet)\n        elif value is noValue:\n            return asn1Spec\n        else:\n            return asn1Spec.clone(value)\n\n\nclass ExplicitTagDecoder(AbstractSimpleDecoder):\n    protoComponent = univ.Any('')\n\n    def valueDecoder(self, substrate, asn1Spec,\n                     tagSet=None, length=None, state=None,\n                     decodeFun=None, substrateFun=None,\n                     **options):\n        if substrateFun:\n            return substrateFun(\n                self._createComponent(asn1Spec, tagSet, '', **options),\n                substrate, length\n            )\n\n        head, tail = substrate[:length], substrate[length:]\n\n        value, _ = decodeFun(head, asn1Spec, tagSet, length, **options)\n\n        if LOG:\n            LOG('explicit tag container carries %d octets of trailing payload '\n                '(will be lost!): %s' % (len(_), debug.hexdump(_)))\n\n        return value, tail\n\n    def indefLenValueDecoder(self, substrate, asn1Spec,\n                             tagSet=None, length=None, state=None,\n                             decodeFun=None, substrateFun=None,\n                             **options):\n        if substrateFun:\n            return substrateFun(\n                self._createComponent(asn1Spec, tagSet, '', **options),\n                substrate, length\n            )\n\n        value, substrate = decodeFun(substrate, asn1Spec, tagSet, length, **options)\n\n        eooMarker, substrate = decodeFun(substrate, allowEoo=True, **options)\n\n        if eooMarker is eoo.endOfOctets:\n            return value, substrate\n        else:\n            raise error.PyAsn1Error('Missing end-of-octets terminator')\n\n\nexplicitTagDecoder = ExplicitTagDecoder()\n\n\nclass IntegerDecoder(AbstractSimpleDecoder):\n    protoComponent = univ.Integer(0)\n\n    def valueDecoder(self, substrate, asn1Spec,\n                     tagSet=None, length=None, state=None,\n                     decodeFun=None, substrateFun=None,\n                     **options):\n\n        if tagSet[0].tagFormat != tag.tagFormatSimple:\n            raise error.PyAsn1Error('Simple tag format expected')\n\n        head, tail = substrate[:length], substrate[length:]\n\n        if not head:\n            return self._createComponent(asn1Spec, tagSet, 0, **options), tail\n\n        value = from_bytes(head, signed=True)\n\n        return self._createComponent(asn1Spec, tagSet, value, **options), tail\n\n\nclass BooleanDecoder(IntegerDecoder):\n    protoComponent = univ.Boolean(0)\n\n    def _createComponent(self, asn1Spec, tagSet, value, **options):\n        return IntegerDecoder._createComponent(\n            self, asn1Spec, tagSet, value and 1 or 0, **options)\n\n\nclass BitStringDecoder(AbstractSimpleDecoder):\n    protoComponent = univ.BitString(())\n    supportConstructedForm = True\n\n    def valueDecoder(self, substrate, asn1Spec,\n                     tagSet=None, length=None, state=None,\n                     decodeFun=None, substrateFun=None,\n                     **options):\n        head, tail = substrate[:length], substrate[length:]\n\n        if substrateFun:\n            return substrateFun(self._createComponent(\n                asn1Spec, tagSet, noValue, **options), substrate, length)\n\n        if not head:\n            raise error.PyAsn1Error('Empty BIT STRING substrate')\n\n        if tagSet[0].tagFormat == tag.tagFormatSimple:  # XXX what tag to check?\n\n            trailingBits = oct2int(head[0])\n            if trailingBits > 7:\n                raise error.PyAsn1Error(\n                    'Trailing bits overflow %s' % trailingBits\n                )\n\n            value = self.protoComponent.fromOctetString(\n                head[1:], internalFormat=True, padding=trailingBits)\n\n            return self._createComponent(asn1Spec, tagSet, value, **options), tail\n\n        if not self.supportConstructedForm:\n            raise error.PyAsn1Error('Constructed encoding form prohibited '\n                                    'at %s' % self.__class__.__name__)\n\n        if LOG:\n            LOG('assembling constructed serialization')\n\n        # All inner fragments are of the same type, treat them as octet string\n        substrateFun = self.substrateCollector\n\n        bitString = self.protoComponent.fromOctetString(null, internalFormat=True)\n\n        while head:\n            component, head = decodeFun(head, self.protoComponent,\n                                        substrateFun=substrateFun, **options)\n\n            trailingBits = oct2int(component[0])\n            if trailingBits > 7:\n                raise error.PyAsn1Error(\n                    'Trailing bits overflow %s' % trailingBits\n                )\n\n            bitString = self.protoComponent.fromOctetString(\n                component[1:], internalFormat=True,\n                prepend=bitString, padding=trailingBits\n            )\n\n        return self._createComponent(asn1Spec, tagSet, bitString, **options), tail\n\n    def indefLenValueDecoder(self, substrate, asn1Spec,\n                             tagSet=None, length=None, state=None,\n                             decodeFun=None, substrateFun=None,\n                             **options):\n\n        if substrateFun:\n            return substrateFun(self._createComponent(asn1Spec, tagSet, noValue, **options), substrate, length)\n\n        # All inner fragments are of the same type, treat them as octet string\n        substrateFun = self.substrateCollector\n\n        bitString = self.protoComponent.fromOctetString(null, internalFormat=True)\n\n        while substrate:\n            component, substrate = decodeFun(substrate, self.protoComponent,\n                                             substrateFun=substrateFun,\n                                             allowEoo=True, **options)\n            if component is eoo.endOfOctets:\n                break\n\n            trailingBits = oct2int(component[0])\n            if trailingBits > 7:\n                raise error.PyAsn1Error(\n                    'Trailing bits overflow %s' % trailingBits\n                )\n\n            bitString = self.protoComponent.fromOctetString(\n                component[1:], internalFormat=True,\n                prepend=bitString, padding=trailingBits\n            )\n\n        else:\n            raise error.SubstrateUnderrunError('No EOO seen before substrate ends')\n\n        return self._createComponent(asn1Spec, tagSet, bitString, **options), substrate\n\n\nclass OctetStringDecoder(AbstractSimpleDecoder):\n    protoComponent = univ.OctetString('')\n    supportConstructedForm = True\n\n    def valueDecoder(self, substrate, asn1Spec,\n                     tagSet=None, length=None, state=None,\n                     decodeFun=None, substrateFun=None,\n                     **options):\n        head, tail = substrate[:length], substrate[length:]\n\n        if substrateFun:\n            return substrateFun(self._createComponent(asn1Spec, tagSet, noValue, **options),\n                                substrate, length)\n\n        if tagSet[0].tagFormat == tag.tagFormatSimple:  # XXX what tag to check?\n            return self._createComponent(asn1Spec, tagSet, head, **options), tail\n\n        if not self.supportConstructedForm:\n            raise error.PyAsn1Error('Constructed encoding form prohibited at %s' % self.__class__.__name__)\n\n        if LOG:\n            LOG('assembling constructed serialization')\n\n        # All inner fragments are of the same type, treat them as octet string\n        substrateFun = self.substrateCollector\n\n        header = null\n\n        while head:\n            component, head = decodeFun(head, self.protoComponent,\n                                        substrateFun=substrateFun,\n                                        **options)\n            header += component\n\n        return self._createComponent(asn1Spec, tagSet, header, **options), tail\n\n    def indefLenValueDecoder(self, substrate, asn1Spec,\n                             tagSet=None, length=None, state=None,\n                             decodeFun=None, substrateFun=None,\n                             **options):\n        if substrateFun and substrateFun is not self.substrateCollector:\n            asn1Object = self._createComponent(asn1Spec, tagSet, noValue, **options)\n            return substrateFun(asn1Object, substrate, length)\n\n        # All inner fragments are of the same type, treat them as octet string\n        substrateFun = self.substrateCollector\n\n        header = null\n\n        while substrate:\n            component, substrate = decodeFun(substrate,\n                                             self.protoComponent,\n                                             substrateFun=substrateFun,\n                                             allowEoo=True, **options)\n            if component is eoo.endOfOctets:\n                break\n\n            header += component\n\n        else:\n            raise error.SubstrateUnderrunError(\n                'No EOO seen before substrate ends'\n            )\n\n        return self._createComponent(asn1Spec, tagSet, header, **options), substrate\n\n\nclass NullDecoder(AbstractSimpleDecoder):\n    protoComponent = univ.Null('')\n\n    def valueDecoder(self, substrate, asn1Spec,\n                     tagSet=None, length=None, state=None,\n                     decodeFun=None, substrateFun=None,\n                     **options):\n\n        if tagSet[0].tagFormat != tag.tagFormatSimple:\n            raise error.PyAsn1Error('Simple tag format expected')\n\n        head, tail = substrate[:length], substrate[length:]\n\n        component = self._createComponent(asn1Spec, tagSet, '', **options)\n\n        if head:\n            raise error.PyAsn1Error('Unexpected %d-octet substrate for Null' % length)\n\n        return component, tail\n\n\nclass ObjectIdentifierDecoder(AbstractSimpleDecoder):\n    protoComponent = univ.ObjectIdentifier(())\n\n    def valueDecoder(self, substrate, asn1Spec,\n                     tagSet=None, length=None, state=None,\n                     decodeFun=None, substrateFun=None,\n                     **options):\n        if tagSet[0].tagFormat != tag.tagFormatSimple:\n            raise error.PyAsn1Error('Simple tag format expected')\n\n        head, tail = substrate[:length], substrate[length:]\n        if not head:\n            raise error.PyAsn1Error('Empty substrate')\n\n        head = octs2ints(head)\n\n        oid = ()\n        index = 0\n        substrateLen = len(head)\n        while index < substrateLen:\n            subId = head[index]\n            index += 1\n            if subId < 128:\n                oid += (subId,)\n            elif subId > 128:\n                # Construct subid from a number of octets\n                nextSubId = subId\n                subId = 0\n                while nextSubId >= 128:\n                    subId = (subId << 7) + (nextSubId & 0x7F)\n                    if index >= substrateLen:\n                        raise error.SubstrateUnderrunError(\n                            'Short substrate for sub-OID past %s' % (oid,)\n                        )\n                    nextSubId = head[index]\n                    index += 1\n                oid += ((subId << 7) + nextSubId,)\n            elif subId == 128:\n                # ASN.1 spec forbids leading zeros (0x80) in OID\n                # encoding, tolerating it opens a vulnerability. See\n                # https://www.esat.kuleuven.be/cosic/publications/article-1432.pdf\n                # page 7\n                raise error.PyAsn1Error('Invalid octet 0x80 in OID encoding')\n\n        # Decode two leading arcs\n        if 0 <= oid[0] <= 39:\n            oid = (0,) + oid\n        elif 40 <= oid[0] <= 79:\n            oid = (1, oid[0] - 40) + oid[1:]\n        elif oid[0] >= 80:\n            oid = (2, oid[0] - 80) + oid[1:]\n        else:\n            raise error.PyAsn1Error('Malformed first OID octet: %s' % head[0])\n\n        return self._createComponent(asn1Spec, tagSet, oid, **options), tail\n\n\nclass RealDecoder(AbstractSimpleDecoder):\n    protoComponent = univ.Real()\n\n    def valueDecoder(self, substrate, asn1Spec,\n                     tagSet=None, length=None, state=None,\n                     decodeFun=None, substrateFun=None,\n                     **options):\n        if tagSet[0].tagFormat != tag.tagFormatSimple:\n            raise error.PyAsn1Error('Simple tag format expected')\n\n        head, tail = substrate[:length], substrate[length:]\n\n        if not head:\n            return self._createComponent(asn1Spec, tagSet, 0.0, **options), tail\n\n        fo = oct2int(head[0])\n        head = head[1:]\n        if fo & 0x80:  # binary encoding\n            if not head:\n                raise error.PyAsn1Error(\"Incomplete floating-point value\")\n\n            if LOG:\n                LOG('decoding binary encoded REAL')\n\n            n = (fo & 0x03) + 1\n\n            if n == 4:\n                n = oct2int(head[0])\n                head = head[1:]\n\n            eo, head = head[:n], head[n:]\n\n            if not eo or not head:\n                raise error.PyAsn1Error('Real exponent screwed')\n\n            e = oct2int(eo[0]) & 0x80 and -1 or 0\n\n            while eo:  # exponent\n                e <<= 8\n                e |= oct2int(eo[0])\n                eo = eo[1:]\n\n            b = fo >> 4 & 0x03  # base bits\n\n            if b > 2:\n                raise error.PyAsn1Error('Illegal Real base')\n\n            if b == 1:  # encbase = 8\n                e *= 3\n\n            elif b == 2:  # encbase = 16\n                e *= 4\n            p = 0\n\n            while head:  # value\n                p <<= 8\n                p |= oct2int(head[0])\n                head = head[1:]\n\n            if fo & 0x40:  # sign bit\n                p = -p\n\n            sf = fo >> 2 & 0x03  # scale bits\n            p *= 2 ** sf\n            value = (p, 2, e)\n\n        elif fo & 0x40:  # infinite value\n            if LOG:\n                LOG('decoding infinite REAL')\n\n            value = fo & 0x01 and '-inf' or 'inf'\n\n        elif fo & 0xc0 == 0:  # character encoding\n            if not head:\n                raise error.PyAsn1Error(\"Incomplete floating-point value\")\n\n            if LOG:\n                LOG('decoding character encoded REAL')\n\n            try:\n                if fo & 0x3 == 0x1:  # NR1\n                    value = (int(head), 10, 0)\n\n                elif fo & 0x3 == 0x2:  # NR2\n                    value = float(head)\n\n                elif fo & 0x3 == 0x3:  # NR3\n                    value = float(head)\n\n                else:\n                    raise error.SubstrateUnderrunError(\n                        'Unknown NR (tag %s)' % fo\n                    )\n\n            except ValueError:\n                raise error.SubstrateUnderrunError(\n                    'Bad character Real syntax'\n                )\n\n        else:\n            raise error.SubstrateUnderrunError(\n                'Unknown encoding (tag %s)' % fo\n            )\n\n        return self._createComponent(asn1Spec, tagSet, value, **options), tail\n\n\nclass AbstractConstructedDecoder(AbstractDecoder):\n    protoComponent = None\n\n\nclass UniversalConstructedTypeDecoder(AbstractConstructedDecoder):\n    protoRecordComponent = None\n    protoSequenceComponent = None\n\n    def _getComponentTagMap(self, asn1Object, idx):\n        raise NotImplementedError()\n\n    def _getComponentPositionByType(self, asn1Object, tagSet, idx):\n        raise NotImplementedError()\n\n    def _decodeComponents(self, substrate, tagSet=None, decodeFun=None, **options):\n        components = []\n        componentTypes = set()\n\n        while substrate:\n            component, substrate = decodeFun(substrate, **options)\n            if component is eoo.endOfOctets:\n                break\n\n            components.append(component)\n            componentTypes.add(component.tagSet)\n\n        # Now we have to guess is it SEQUENCE/SET or SEQUENCE OF/SET OF\n        # The heuristics is:\n        # * 1+ components of different types -> likely SEQUENCE/SET\n        # * otherwise -> likely SEQUENCE OF/SET OF\n        if len(componentTypes) > 1:\n            protoComponent = self.protoRecordComponent\n\n        else:\n            protoComponent = self.protoSequenceComponent\n\n        asn1Object = protoComponent.clone(\n            # construct tagSet from base tag from prototype ASN.1 object\n            # and additional tags recovered from the substrate\n            tagSet=tag.TagSet(protoComponent.tagSet.baseTag, *tagSet.superTags)\n        )\n\n        if LOG:\n            LOG('guessed %r container type (pass `asn1Spec` to guide the '\n                'decoder)' % asn1Object)\n\n        for idx, component in enumerate(components):\n            asn1Object.setComponentByPosition(\n                idx, component,\n                verifyConstraints=False,\n                matchTags=False, matchConstraints=False\n            )\n\n        return asn1Object, substrate\n\n    def valueDecoder(self, substrate, asn1Spec,\n                     tagSet=None, length=None, state=None,\n                     decodeFun=None, substrateFun=None,\n                     **options):\n        if tagSet[0].tagFormat != tag.tagFormatConstructed:\n            raise error.PyAsn1Error('Constructed tag format expected')\n\n        head, tail = substrate[:length], substrate[length:]\n\n        if substrateFun is not None:\n            if asn1Spec is not None:\n                asn1Object = asn1Spec.clone()\n\n            elif self.protoComponent is not None:\n                asn1Object = self.protoComponent.clone(tagSet=tagSet)\n\n            else:\n                asn1Object = self.protoRecordComponent, self.protoSequenceComponent\n\n            return substrateFun(asn1Object, substrate, length)\n\n        if asn1Spec is None:\n            asn1Object, trailing = self._decodeComponents(\n                head, tagSet=tagSet, decodeFun=decodeFun, **options\n            )\n\n            if trailing:\n                if LOG:\n                    LOG('Unused trailing %d octets encountered: %s' % (\n                        len(trailing), debug.hexdump(trailing)))\n\n            return asn1Object, tail\n\n        asn1Object = asn1Spec.clone()\n        asn1Object.clear()\n\n        if asn1Spec.typeId in (univ.Sequence.typeId, univ.Set.typeId):\n\n            namedTypes = asn1Spec.componentType\n\n            isSetType = asn1Spec.typeId == univ.Set.typeId\n            isDeterministic = not isSetType and not namedTypes.hasOptionalOrDefault\n\n            if LOG:\n                LOG('decoding %sdeterministic %s type %r chosen by type ID' % (\n                    not isDeterministic and 'non-' or '', isSetType and 'SET' or '',\n                    asn1Spec))\n\n            seenIndices = set()\n            idx = 0\n            while head:\n                if not namedTypes:\n                    componentType = None\n\n                elif isSetType:\n                    componentType = namedTypes.tagMapUnique\n\n                else:\n                    try:\n                        if isDeterministic:\n                            componentType = namedTypes[idx].asn1Object\n\n                        elif namedTypes[idx].isOptional or namedTypes[idx].isDefaulted:\n                            componentType = namedTypes.getTagMapNearPosition(idx)\n\n                        else:\n                            componentType = namedTypes[idx].asn1Object\n\n                    except IndexError:\n                        raise error.PyAsn1Error(\n                            'Excessive components decoded at %r' % (asn1Spec,)\n                        )\n\n                component, head = decodeFun(head, componentType, **options)\n\n                if not isDeterministic and namedTypes:\n                    if isSetType:\n                        idx = namedTypes.getPositionByType(component.effectiveTagSet)\n\n                    elif namedTypes[idx].isOptional or namedTypes[idx].isDefaulted:\n                        idx = namedTypes.getPositionNearType(component.effectiveTagSet, idx)\n\n                asn1Object.setComponentByPosition(\n                    idx, component,\n                    verifyConstraints=False,\n                    matchTags=False, matchConstraints=False\n                )\n\n                seenIndices.add(idx)\n                idx += 1\n\n            if LOG:\n                LOG('seen component indices %s' % seenIndices)\n\n            if namedTypes:\n                if not namedTypes.requiredComponents.issubset(seenIndices):\n                    raise error.PyAsn1Error(\n                        'ASN.1 object %s has uninitialized '\n                        'components' % asn1Object.__class__.__name__)\n\n                if  namedTypes.hasOpenTypes:\n\n                    openTypes = options.get('openTypes', {})\n\n                    if LOG:\n                        LOG('using open types map: %r' % openTypes)\n\n                    if openTypes or options.get('decodeOpenTypes', False):\n\n                        for idx, namedType in enumerate(namedTypes.namedTypes):\n                            if not namedType.openType:\n                                continue\n\n                            if namedType.isOptional and not asn1Object.getComponentByPosition(idx).isValue:\n                                continue\n\n                            governingValue = asn1Object.getComponentByName(\n                                namedType.openType.name\n                            )\n\n                            try:\n                                openType = openTypes[governingValue]\n\n                            except KeyError:\n\n                                try:\n                                    openType = namedType.openType[governingValue]\n\n                                except KeyError:\n                                    if LOG:\n                                        LOG('failed to resolve open type by governing '\n                                            'value %r' % (governingValue,))\n                                    continue\n\n                            if LOG:\n                                LOG('resolved open type %r by governing '\n                                    'value %r' % (openType, governingValue))\n\n                            containerValue = asn1Object.getComponentByPosition(idx)\n\n                            if containerValue.typeId in (\n                                    univ.SetOf.typeId, univ.SequenceOf.typeId):\n\n                                for pos, containerElement in enumerate(\n                                        containerValue):\n\n                                    component, rest = decodeFun(\n                                        containerValue[pos].asOctets(),\n                                        asn1Spec=openType, **options\n                                    )\n\n                                    containerValue[pos] = component\n\n                            else:\n                                component, rest = decodeFun(\n                                    asn1Object.getComponentByPosition(idx).asOctets(),\n                                    asn1Spec=openType, **options\n                                )\n\n                                asn1Object.setComponentByPosition(idx, component)\n\n            else:\n                inconsistency = asn1Object.isInconsistent\n                if inconsistency:\n                    raise inconsistency\n\n        else:\n            asn1Object = asn1Spec.clone()\n            asn1Object.clear()\n\n            componentType = asn1Spec.componentType\n\n            if LOG:\n                LOG('decoding type %r chosen by given `asn1Spec`' % componentType)\n\n            idx = 0\n\n            while head:\n                component, head = decodeFun(head, componentType, **options)\n                asn1Object.setComponentByPosition(\n                    idx, component,\n                    verifyConstraints=False,\n                    matchTags=False, matchConstraints=False\n                )\n\n                idx += 1\n\n        return asn1Object, tail\n\n    def indefLenValueDecoder(self, substrate, asn1Spec,\n                             tagSet=None, length=None, state=None,\n                             decodeFun=None, substrateFun=None,\n                             **options):\n        if tagSet[0].tagFormat != tag.tagFormatConstructed:\n            raise error.PyAsn1Error('Constructed tag format expected')\n\n        if substrateFun is not None:\n            if asn1Spec is not None:\n                asn1Object = asn1Spec.clone()\n\n            elif self.protoComponent is not None:\n                asn1Object = self.protoComponent.clone(tagSet=tagSet)\n\n            else:\n                asn1Object = self.protoRecordComponent, self.protoSequenceComponent\n\n            return substrateFun(asn1Object, substrate, length)\n\n        if asn1Spec is None:\n            return self._decodeComponents(\n                substrate, tagSet=tagSet, decodeFun=decodeFun,\n                **dict(options, allowEoo=True)\n            )\n\n        asn1Object = asn1Spec.clone()\n        asn1Object.clear()\n\n        if asn1Spec.typeId in (univ.Sequence.typeId, univ.Set.typeId):\n\n            namedTypes = asn1Object.componentType\n\n            isSetType = asn1Object.typeId == univ.Set.typeId\n            isDeterministic = not isSetType and not namedTypes.hasOptionalOrDefault\n\n            if LOG:\n                LOG('decoding %sdeterministic %s type %r chosen by type ID' % (\n                    not isDeterministic and 'non-' or '', isSetType and 'SET' or '',\n                    asn1Spec))\n\n            seenIndices = set()\n            idx = 0\n            while substrate:\n                if len(namedTypes) <= idx:\n                    asn1Spec = None\n\n                elif isSetType:\n                    asn1Spec = namedTypes.tagMapUnique\n\n                else:\n                    try:\n                        if isDeterministic:\n                            asn1Spec = namedTypes[idx].asn1Object\n\n                        elif namedTypes[idx].isOptional or namedTypes[idx].isDefaulted:\n                            asn1Spec = namedTypes.getTagMapNearPosition(idx)\n\n                        else:\n                            asn1Spec = namedTypes[idx].asn1Object\n\n                    except IndexError:\n                        raise error.PyAsn1Error(\n                            'Excessive components decoded at %r' % (asn1Object,)\n                        )\n\n                component, substrate = decodeFun(substrate, asn1Spec, allowEoo=True, **options)\n                if component is eoo.endOfOctets:\n                    break\n\n                if not isDeterministic and namedTypes:\n                    if isSetType:\n                        idx = namedTypes.getPositionByType(component.effectiveTagSet)\n                    elif namedTypes[idx].isOptional or namedTypes[idx].isDefaulted:\n                        idx = namedTypes.getPositionNearType(component.effectiveTagSet, idx)\n\n                asn1Object.setComponentByPosition(\n                    idx, component,\n                    verifyConstraints=False,\n                    matchTags=False, matchConstraints=False\n                )\n\n                seenIndices.add(idx)\n                idx += 1\n\n            else:\n                raise error.SubstrateUnderrunError(\n                    'No EOO seen before substrate ends'\n                )\n\n            if LOG:\n                LOG('seen component indices %s' % seenIndices)\n\n            if namedTypes:\n                if not namedTypes.requiredComponents.issubset(seenIndices):\n                    raise error.PyAsn1Error('ASN.1 object %s has uninitialized components' % asn1Object.__class__.__name__)\n\n                if namedTypes.hasOpenTypes:\n\n                    openTypes = options.get('openTypes', {})\n\n                    if LOG:\n                        LOG('using open types map: %r' % openTypes)\n\n                    if openTypes or options.get('decodeOpenTypes', False):\n\n                        for idx, namedType in enumerate(namedTypes.namedTypes):\n                            if not namedType.openType:\n                                continue\n\n                            if namedType.isOptional and not asn1Object.getComponentByPosition(idx).isValue:\n                                continue\n\n                            governingValue = asn1Object.getComponentByName(\n                                namedType.openType.name\n                            )\n\n                            try:\n                                openType = openTypes[governingValue]\n\n                            except KeyError:\n\n                                try:\n                                    openType = namedType.openType[governingValue]\n\n                                except KeyError:\n                                    if LOG:\n                                        LOG('failed to resolve open type by governing '\n                                            'value %r' % (governingValue,))\n                                    continue\n\n                            if LOG:\n                                LOG('resolved open type %r by governing '\n                                    'value %r' % (openType, governingValue))\n\n                            containerValue = asn1Object.getComponentByPosition(idx)\n\n                            if containerValue.typeId in (\n                                    univ.SetOf.typeId, univ.SequenceOf.typeId):\n\n                                for pos, containerElement in enumerate(\n                                        containerValue):\n\n                                    component, rest = decodeFun(\n                                        containerValue[pos].asOctets(),\n                                        asn1Spec=openType, **dict(options, allowEoo=True)\n                                    )\n\n                                    containerValue[pos] = component\n\n                            else:\n                                component, rest = decodeFun(\n                                    asn1Object.getComponentByPosition(idx).asOctets(),\n                                    asn1Spec=openType, **dict(options, allowEoo=True)\n                                )\n\n                                if component is not eoo.endOfOctets:\n                                    asn1Object.setComponentByPosition(idx, component)\n\n                else:\n                    inconsistency = asn1Object.isInconsistent\n                    if inconsistency:\n                        raise inconsistency\n\n        else:\n            asn1Object = asn1Spec.clone()\n            asn1Object.clear()\n\n            componentType = asn1Spec.componentType\n\n            if LOG:\n                LOG('decoding type %r chosen by given `asn1Spec`' % componentType)\n\n            idx = 0\n\n            while substrate:\n                component, substrate = decodeFun(substrate, componentType, allowEoo=True, **options)\n\n                if component is eoo.endOfOctets:\n                    break\n\n                asn1Object.setComponentByPosition(\n                    idx, component,\n                    verifyConstraints=False,\n                    matchTags=False, matchConstraints=False\n                )\n\n                idx += 1\n\n            else:\n                raise error.SubstrateUnderrunError(\n                    'No EOO seen before substrate ends'\n                )\n\n        return asn1Object, substrate\n\n\nclass SequenceOrSequenceOfDecoder(UniversalConstructedTypeDecoder):\n    protoRecordComponent = univ.Sequence()\n    protoSequenceComponent = univ.SequenceOf()\n\n\nclass SequenceDecoder(SequenceOrSequenceOfDecoder):\n    protoComponent = univ.Sequence()\n\n\nclass SequenceOfDecoder(SequenceOrSequenceOfDecoder):\n    protoComponent = univ.SequenceOf()\n\n\nclass SetOrSetOfDecoder(UniversalConstructedTypeDecoder):\n    protoRecordComponent = univ.Set()\n    protoSequenceComponent = univ.SetOf()\n\n\nclass SetDecoder(SetOrSetOfDecoder):\n    protoComponent = univ.Set()\n\n\n\nclass SetOfDecoder(SetOrSetOfDecoder):\n    protoComponent = univ.SetOf()\n\n\nclass ChoiceDecoder(AbstractConstructedDecoder):\n    protoComponent = univ.Choice()\n\n    def valueDecoder(self, substrate, asn1Spec,\n                     tagSet=None, length=None, state=None,\n                     decodeFun=None, substrateFun=None,\n                     **options):\n        head, tail = substrate[:length], substrate[length:]\n\n        if asn1Spec is None:\n            asn1Object = self.protoComponent.clone(tagSet=tagSet)\n\n        else:\n            asn1Object = asn1Spec.clone()\n\n        if substrateFun:\n            return substrateFun(asn1Object, substrate, length)\n\n        if asn1Object.tagSet == tagSet:\n            if LOG:\n                LOG('decoding %s as explicitly tagged CHOICE' % (tagSet,))\n\n            component, head = decodeFun(\n                head, asn1Object.componentTagMap, **options\n            )\n\n        else:\n            if LOG:\n                LOG('decoding %s as untagged CHOICE' % (tagSet,))\n\n            component, head = decodeFun(\n                head, asn1Object.componentTagMap,\n                tagSet, length, state, **options\n            )\n\n        effectiveTagSet = component.effectiveTagSet\n\n        if LOG:\n            LOG('decoded component %s, effective tag set %s' % (component, effectiveTagSet))\n\n        asn1Object.setComponentByType(\n            effectiveTagSet, component,\n            verifyConstraints=False,\n            matchTags=False, matchConstraints=False,\n            innerFlag=False\n        )\n\n        return asn1Object, tail\n\n    def indefLenValueDecoder(self, substrate, asn1Spec,\n                             tagSet=None, length=None, state=None,\n                             decodeFun=None, substrateFun=None,\n                             **options):\n        if asn1Spec is None:\n            asn1Object = self.protoComponent.clone(tagSet=tagSet)\n        else:\n            asn1Object = asn1Spec.clone()\n\n        if substrateFun:\n            return substrateFun(asn1Object, substrate, length)\n\n        if asn1Object.tagSet == tagSet:\n            if LOG:\n                LOG('decoding %s as explicitly tagged CHOICE' % (tagSet,))\n\n            component, substrate = decodeFun(\n                substrate, asn1Object.componentType.tagMapUnique, **options\n            )\n\n            # eat up EOO marker\n            eooMarker, substrate = decodeFun(\n                substrate, allowEoo=True, **options\n            )\n\n            if eooMarker is not eoo.endOfOctets:\n                raise error.PyAsn1Error('No EOO seen before substrate ends')\n\n        else:\n            if LOG:\n                LOG('decoding %s as untagged CHOICE' % (tagSet,))\n\n            component, substrate = decodeFun(\n                substrate, asn1Object.componentType.tagMapUnique,\n                tagSet, length, state, **options\n            )\n\n        effectiveTagSet = component.effectiveTagSet\n\n        if LOG:\n            LOG('decoded component %s, effective tag set %s' % (component, effectiveTagSet))\n\n        asn1Object.setComponentByType(\n            effectiveTagSet, component,\n            verifyConstraints=False,\n            matchTags=False, matchConstraints=False,\n            innerFlag=False\n        )\n\n        return asn1Object, substrate\n\n\nclass AnyDecoder(AbstractSimpleDecoder):\n    protoComponent = univ.Any()\n\n    def valueDecoder(self, substrate, asn1Spec,\n                     tagSet=None, length=None, state=None,\n                     decodeFun=None, substrateFun=None,\n                     **options):\n        if asn1Spec is None:\n            isUntagged = True\n\n        elif asn1Spec.__class__ is tagmap.TagMap:\n            isUntagged = tagSet not in asn1Spec.tagMap\n\n        else:\n            isUntagged = tagSet != asn1Spec.tagSet\n\n        if isUntagged:\n            fullSubstrate = options['fullSubstrate']\n\n            # untagged Any container, recover inner header substrate\n            length += len(fullSubstrate) - len(substrate)\n            substrate = fullSubstrate\n\n            if LOG:\n                LOG('decoding as untagged ANY, substrate %s' % debug.hexdump(substrate))\n\n        if substrateFun:\n            return substrateFun(self._createComponent(asn1Spec, tagSet, noValue, **options),\n                                substrate, length)\n\n        head, tail = substrate[:length], substrate[length:]\n\n        return self._createComponent(asn1Spec, tagSet, head, **options), tail\n\n    def indefLenValueDecoder(self, substrate, asn1Spec,\n                             tagSet=None, length=None, state=None,\n                             decodeFun=None, substrateFun=None,\n                             **options):\n        if asn1Spec is None:\n            isTagged = False\n\n        elif asn1Spec.__class__ is tagmap.TagMap:\n            isTagged = tagSet in asn1Spec.tagMap\n\n        else:\n            isTagged = tagSet == asn1Spec.tagSet\n\n        if isTagged:\n            # tagged Any type -- consume header substrate\n            header = null\n\n            if LOG:\n                LOG('decoding as tagged ANY')\n\n        else:\n            fullSubstrate = options['fullSubstrate']\n\n            # untagged Any, recover header substrate\n            header = fullSubstrate[:-len(substrate)]\n\n            if LOG:\n                LOG('decoding as untagged ANY, header substrate %s' % debug.hexdump(header))\n\n        # Any components do not inherit initial tag\n        asn1Spec = self.protoComponent\n\n        if substrateFun and substrateFun is not self.substrateCollector:\n            asn1Object = self._createComponent(asn1Spec, tagSet, noValue, **options)\n            return substrateFun(asn1Object, header + substrate, length + len(header))\n\n        if LOG:\n            LOG('assembling constructed serialization')\n\n        # All inner fragments are of the same type, treat them as octet string\n        substrateFun = self.substrateCollector\n\n        while substrate:\n            component, substrate = decodeFun(substrate, asn1Spec,\n                                             substrateFun=substrateFun,\n                                             allowEoo=True, **options)\n            if component is eoo.endOfOctets:\n                break\n\n            header += component\n\n        else:\n            raise error.SubstrateUnderrunError(\n                'No EOO seen before substrate ends'\n            )\n\n        if substrateFun:\n            return header, substrate\n\n        else:\n            return self._createComponent(asn1Spec, tagSet, header, **options), substrate\n\n\n# character string types\nclass UTF8StringDecoder(OctetStringDecoder):\n    protoComponent = char.UTF8String()\n\n\nclass NumericStringDecoder(OctetStringDecoder):\n    protoComponent = char.NumericString()\n\n\nclass PrintableStringDecoder(OctetStringDecoder):\n    protoComponent = char.PrintableString()\n\n\nclass TeletexStringDecoder(OctetStringDecoder):\n    protoComponent = char.TeletexString()\n\n\nclass VideotexStringDecoder(OctetStringDecoder):\n    protoComponent = char.VideotexString()\n\n\nclass IA5StringDecoder(OctetStringDecoder):\n    protoComponent = char.IA5String()\n\n\nclass GraphicStringDecoder(OctetStringDecoder):\n    protoComponent = char.GraphicString()\n\n\nclass VisibleStringDecoder(OctetStringDecoder):\n    protoComponent = char.VisibleString()\n\n\nclass GeneralStringDecoder(OctetStringDecoder):\n    protoComponent = char.GeneralString()\n\n\nclass UniversalStringDecoder(OctetStringDecoder):\n    protoComponent = char.UniversalString()\n\n\nclass BMPStringDecoder(OctetStringDecoder):\n    protoComponent = char.BMPString()\n\n\n# \"useful\" types\nclass ObjectDescriptorDecoder(OctetStringDecoder):\n    protoComponent = useful.ObjectDescriptor()\n\n\nclass GeneralizedTimeDecoder(OctetStringDecoder):\n    protoComponent = useful.GeneralizedTime()\n\n\nclass UTCTimeDecoder(OctetStringDecoder):\n    protoComponent = useful.UTCTime()\n\n\ntagMap = {\n    univ.Integer.tagSet: IntegerDecoder(),\n    univ.Boolean.tagSet: BooleanDecoder(),\n    univ.BitString.tagSet: BitStringDecoder(),\n    univ.OctetString.tagSet: OctetStringDecoder(),\n    univ.Null.tagSet: NullDecoder(),\n    univ.ObjectIdentifier.tagSet: ObjectIdentifierDecoder(),\n    univ.Enumerated.tagSet: IntegerDecoder(),\n    univ.Real.tagSet: RealDecoder(),\n    univ.Sequence.tagSet: SequenceOrSequenceOfDecoder(),  # conflicts with SequenceOf\n    univ.Set.tagSet: SetOrSetOfDecoder(),  # conflicts with SetOf\n    univ.Choice.tagSet: ChoiceDecoder(),  # conflicts with Any\n    # character string types\n    char.UTF8String.tagSet: UTF8StringDecoder(),\n    char.NumericString.tagSet: NumericStringDecoder(),\n    char.PrintableString.tagSet: PrintableStringDecoder(),\n    char.TeletexString.tagSet: TeletexStringDecoder(),\n    char.VideotexString.tagSet: VideotexStringDecoder(),\n    char.IA5String.tagSet: IA5StringDecoder(),\n    char.GraphicString.tagSet: GraphicStringDecoder(),\n    char.VisibleString.tagSet: VisibleStringDecoder(),\n    char.GeneralString.tagSet: GeneralStringDecoder(),\n    char.UniversalString.tagSet: UniversalStringDecoder(),\n    char.BMPString.tagSet: BMPStringDecoder(),\n    # useful types\n    useful.ObjectDescriptor.tagSet: ObjectDescriptorDecoder(),\n    useful.GeneralizedTime.tagSet: GeneralizedTimeDecoder(),\n    useful.UTCTime.tagSet: UTCTimeDecoder()\n}\n\n# Type-to-codec map for ambiguous ASN.1 types\ntypeMap = {\n    univ.Set.typeId: SetDecoder(),\n    univ.SetOf.typeId: SetOfDecoder(),\n    univ.Sequence.typeId: SequenceDecoder(),\n    univ.SequenceOf.typeId: SequenceOfDecoder(),\n    univ.Choice.typeId: ChoiceDecoder(),\n    univ.Any.typeId: AnyDecoder()\n}\n\n# Put in non-ambiguous types for faster codec lookup\nfor typeDecoder in tagMap.values():\n    if typeDecoder.protoComponent is not None:\n        typeId = typeDecoder.protoComponent.__class__.typeId\n        if typeId is not None and typeId not in typeMap:\n            typeMap[typeId] = typeDecoder\n\n\n(stDecodeTag,\n stDecodeLength,\n stGetValueDecoder,\n stGetValueDecoderByAsn1Spec,\n stGetValueDecoderByTag,\n stTryAsExplicitTag,\n stDecodeValue,\n stDumpRawValue,\n stErrorCondition,\n stStop) = [x for x in range(10)]\n\n\nclass Decoder(object):\n    defaultErrorState = stErrorCondition\n    #defaultErrorState = stDumpRawValue\n    defaultRawDecoder = AnyDecoder()\n    supportIndefLength = True\n\n    # noinspection PyDefaultArgument\n    def __init__(self, tagMap, typeMap={}):\n        self.__tagMap = tagMap\n        self.__typeMap = typeMap\n        # Tag & TagSet objects caches\n        self.__tagCache = {}\n        self.__tagSetCache = {}\n        self.__eooSentinel = ints2octs((0, 0))\n\n    def __call__(self, substrate, asn1Spec=None,\n                 tagSet=None, length=None, state=stDecodeTag,\n                 decodeFun=None, substrateFun=None,\n                 **options):\n\n        if LOG:\n            LOG('decoder called at scope %s with state %d, working with up to %d octets of substrate: %s' % (debug.scope, state, len(substrate), debug.hexdump(substrate)))\n\n        allowEoo = options.pop('allowEoo', False)\n\n        # Look for end-of-octets sentinel\n        if allowEoo and self.supportIndefLength:\n            if substrate[:2] == self.__eooSentinel:\n                if LOG:\n                    LOG('end-of-octets sentinel found')\n                return eoo.endOfOctets, substrate[2:]\n\n        value = noValue\n\n        tagMap = self.__tagMap\n        typeMap = self.__typeMap\n        tagCache = self.__tagCache\n        tagSetCache = self.__tagSetCache\n\n        fullSubstrate = substrate\n\n        while state is not stStop:\n\n            if state is stDecodeTag:\n                if not substrate:\n                    raise error.SubstrateUnderrunError(\n                        'Short octet stream on tag decoding'\n                    )\n\n                # Decode tag\n                isShortTag = True\n                firstOctet = substrate[0]\n                substrate = substrate[1:]\n\n                try:\n                    lastTag = tagCache[firstOctet]\n\n                except KeyError:\n                    integerTag = oct2int(firstOctet)\n                    tagClass = integerTag & 0xC0\n                    tagFormat = integerTag & 0x20\n                    tagId = integerTag & 0x1F\n\n                    if tagId == 0x1F:\n                        isShortTag = False\n                        lengthOctetIdx = 0\n                        tagId = 0\n\n                        try:\n                            while True:\n                                integerTag = oct2int(substrate[lengthOctetIdx])\n                                lengthOctetIdx += 1\n                                tagId <<= 7\n                                tagId |= (integerTag & 0x7F)\n                                if not integerTag & 0x80:\n                                    break\n\n                            substrate = substrate[lengthOctetIdx:]\n\n                        except IndexError:\n                            raise error.SubstrateUnderrunError(\n                                'Short octet stream on long tag decoding'\n                            )\n\n                    lastTag = tag.Tag(\n                        tagClass=tagClass, tagFormat=tagFormat, tagId=tagId\n                    )\n\n                    if isShortTag:\n                        # cache short tags\n                        tagCache[firstOctet] = lastTag\n\n                if tagSet is None:\n                    if isShortTag:\n                        try:\n                            tagSet = tagSetCache[firstOctet]\n\n                        except KeyError:\n                            # base tag not recovered\n                            tagSet = tag.TagSet((), lastTag)\n                            tagSetCache[firstOctet] = tagSet\n                    else:\n                        tagSet = tag.TagSet((), lastTag)\n\n                else:\n                    tagSet = lastTag + tagSet\n\n                state = stDecodeLength\n\n                if LOG:\n                    LOG('tag decoded into %s, decoding length' % tagSet)\n\n            if state is stDecodeLength:\n                # Decode length\n                if not substrate:\n                    raise error.SubstrateUnderrunError(\n                        'Short octet stream on length decoding'\n                    )\n\n                firstOctet = oct2int(substrate[0])\n\n                if firstOctet < 128:\n                    size = 1\n                    length = firstOctet\n\n                elif firstOctet > 128:\n                    size = firstOctet & 0x7F\n                    # encoded in size bytes\n                    encodedLength = octs2ints(substrate[1:size + 1])\n                    # missing check on maximum size, which shouldn't be a\n                    # problem, we can handle more than is possible\n                    if len(encodedLength) != size:\n                        raise error.SubstrateUnderrunError(\n                            '%s<%s at %s' % (size, len(encodedLength), tagSet)\n                        )\n\n                    length = 0\n                    for lengthOctet in encodedLength:\n                        length <<= 8\n                        length |= lengthOctet\n                    size += 1\n\n                else:\n                    size = 1\n                    length = -1\n\n                substrate = substrate[size:]\n\n                if length == -1:\n                    if not self.supportIndefLength:\n                        raise error.PyAsn1Error('Indefinite length encoding not supported by this codec')\n\n                else:\n                    if len(substrate) < length:\n                        raise error.SubstrateUnderrunError('%d-octet short' % (length - len(substrate)))\n\n                state = stGetValueDecoder\n\n                if LOG:\n                    LOG('value length decoded into %d, payload substrate is: %s' % (length, debug.hexdump(length == -1 and substrate or substrate[:length])))\n\n            if state is stGetValueDecoder:\n                if asn1Spec is None:\n                    state = stGetValueDecoderByTag\n\n                else:\n                    state = stGetValueDecoderByAsn1Spec\n            #\n            # There're two ways of creating subtypes in ASN.1 what influences\n            # decoder operation. These methods are:\n            # 1) Either base types used in or no IMPLICIT tagging has been\n            #    applied on subtyping.\n            # 2) Subtype syntax drops base type information (by means of\n            #    IMPLICIT tagging.\n            # The first case allows for complete tag recovery from substrate\n            # while the second one requires original ASN.1 type spec for\n            # decoding.\n            #\n            # In either case a set of tags (tagSet) is coming from substrate\n            # in an incremental, tag-by-tag fashion (this is the case of\n            # EXPLICIT tag which is most basic). Outermost tag comes first\n            # from the wire.\n            #\n            if state is stGetValueDecoderByTag:\n                try:\n                    concreteDecoder = tagMap[tagSet]\n\n                except KeyError:\n                    concreteDecoder = None\n\n                if concreteDecoder:\n                    state = stDecodeValue\n\n                else:\n                    try:\n                        concreteDecoder = tagMap[tagSet[:1]]\n\n                    except KeyError:\n                        concreteDecoder = None\n\n                    if concreteDecoder:\n                        state = stDecodeValue\n                    else:\n                        state = stTryAsExplicitTag\n\n                if LOG:\n                    LOG('codec %s chosen by a built-in type, decoding %s' % (concreteDecoder and concreteDecoder.__class__.__name__ or \"<none>\", state is stDecodeValue and 'value' or 'as explicit tag'))\n                    debug.scope.push(concreteDecoder is None and '?' or concreteDecoder.protoComponent.__class__.__name__)\n\n            if state is stGetValueDecoderByAsn1Spec:\n\n                if asn1Spec.__class__ is tagmap.TagMap:\n                    try:\n                        chosenSpec = asn1Spec[tagSet]\n\n                    except KeyError:\n                        chosenSpec = None\n\n                    if LOG:\n                        LOG('candidate ASN.1 spec is a map of:')\n\n                        for firstOctet, v in asn1Spec.presentTypes.items():\n                            LOG('  %s -> %s' % (firstOctet, v.__class__.__name__))\n\n                        if asn1Spec.skipTypes:\n                            LOG('but neither of: ')\n                            for firstOctet, v in asn1Spec.skipTypes.items():\n                                LOG('  %s -> %s' % (firstOctet, v.__class__.__name__))\n                        LOG('new candidate ASN.1 spec is %s, chosen by %s' % (chosenSpec is None and '<none>' or chosenSpec.prettyPrintType(), tagSet))\n\n                elif tagSet == asn1Spec.tagSet or tagSet in asn1Spec.tagMap:\n                    chosenSpec = asn1Spec\n                    if LOG:\n                        LOG('candidate ASN.1 spec is %s' % asn1Spec.__class__.__name__)\n\n                else:\n                    chosenSpec = None\n\n                if chosenSpec is not None:\n                    try:\n                        # ambiguous type or just faster codec lookup\n                        concreteDecoder = typeMap[chosenSpec.typeId]\n\n                        if LOG:\n                            LOG('value decoder chosen for an ambiguous type by type ID %s' % (chosenSpec.typeId,))\n\n                    except KeyError:\n                        # use base type for codec lookup to recover untagged types\n                        baseTagSet = tag.TagSet(chosenSpec.tagSet.baseTag,  chosenSpec.tagSet.baseTag)\n                        try:\n                            # base type or tagged subtype\n                            concreteDecoder = tagMap[baseTagSet]\n\n                            if LOG:\n                                LOG('value decoder chosen by base %s' % (baseTagSet,))\n\n                        except KeyError:\n                            concreteDecoder = None\n\n                    if concreteDecoder:\n                        asn1Spec = chosenSpec\n                        state = stDecodeValue\n\n                    else:\n                        state = stTryAsExplicitTag\n\n                else:\n                    concreteDecoder = None\n                    state = stTryAsExplicitTag\n\n                if LOG:\n                    LOG('codec %s chosen by ASN.1 spec, decoding %s' % (state is stDecodeValue and concreteDecoder.__class__.__name__ or \"<none>\", state is stDecodeValue and 'value' or 'as explicit tag'))\n                    debug.scope.push(chosenSpec is None and '?' or chosenSpec.__class__.__name__)\n\n            if state is stDecodeValue:\n                if not options.get('recursiveFlag', True) and not substrateFun:  # deprecate this\n                    substrateFun = lambda a, b, c: (a, b[:c])\n\n                options.update(fullSubstrate=fullSubstrate)\n\n                if length == -1:  # indef length\n                    value, substrate = concreteDecoder.indefLenValueDecoder(\n                        substrate, asn1Spec,\n                        tagSet, length, stGetValueDecoder,\n                        self, substrateFun,\n                        **options\n                    )\n\n                else:\n                    value, substrate = concreteDecoder.valueDecoder(\n                        substrate, asn1Spec,\n                        tagSet, length, stGetValueDecoder,\n                        self, substrateFun,\n                        **options\n                    )\n\n                if LOG:\n                    LOG('codec %s yields type %s, value:\\n%s\\n...remaining substrate is: %s' % (concreteDecoder.__class__.__name__, value.__class__.__name__, isinstance(value, base.Asn1Item) and value.prettyPrint() or value, substrate and debug.hexdump(substrate) or '<none>'))\n\n                state = stStop\n                break\n\n            if state is stTryAsExplicitTag:\n                if (tagSet and\n                        tagSet[0].tagFormat == tag.tagFormatConstructed and\n                        tagSet[0].tagClass != tag.tagClassUniversal):\n                    # Assume explicit tagging\n                    concreteDecoder = explicitTagDecoder\n                    state = stDecodeValue\n\n                else:\n                    concreteDecoder = None\n                    state = self.defaultErrorState\n\n                if LOG:\n                    LOG('codec %s chosen, decoding %s' % (concreteDecoder and concreteDecoder.__class__.__name__ or \"<none>\", state is stDecodeValue and 'value' or 'as failure'))\n\n            if state is stDumpRawValue:\n                concreteDecoder = self.defaultRawDecoder\n\n                if LOG:\n                    LOG('codec %s chosen, decoding value' % concreteDecoder.__class__.__name__)\n\n                state = stDecodeValue\n\n            if state is stErrorCondition:\n                raise error.PyAsn1Error(\n                    '%s not in asn1Spec: %r' % (tagSet, asn1Spec)\n                )\n\n        if LOG:\n            debug.scope.pop()\n            LOG('decoder left scope %s, call completed' % debug.scope)\n\n        return value, substrate\n\n\n#: Turns BER octet stream into an ASN.1 object.\n#:\n#: Takes BER octet-stream and decode it into an ASN.1 object\n#: (e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative) which\n#: may be a scalar or an arbitrary nested structure.\n#:\n#: Parameters\n#: ----------\n#: substrate: :py:class:`bytes` (Python 3) or :py:class:`str` (Python 2)\n#:     BER octet-stream\n#:\n#: Keyword Args\n#: ------------\n#: asn1Spec: any pyasn1 type object e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n#:     A pyasn1 type object to act as a template guiding the decoder. Depending on the ASN.1 structure\n#:     being decoded, *asn1Spec* may or may not be required. Most common reason for\n#:     it to require is that ASN.1 structure is encoded in *IMPLICIT* tagging mode.\n#:\n#: Returns\n#: -------\n#: : :py:class:`tuple`\n#:     A tuple of pyasn1 object recovered from BER substrate (:py:class:`~pyasn1.type.base.PyAsn1Item` derivative)\n#:     and the unprocessed trailing portion of the *substrate* (may be empty)\n#:\n#: Raises\n#: ------\n#: ~pyasn1.error.PyAsn1Error, ~pyasn1.error.SubstrateUnderrunError\n#:     On decoding errors\n#:\n#: Examples\n#: --------\n#: Decode BER serialisation without ASN.1 schema\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> s, _ = decode(b'0\\t\\x02\\x01\\x01\\x02\\x01\\x02\\x02\\x01\\x03')\n#:    >>> str(s)\n#:    SequenceOf:\n#:     1 2 3\n#:\n#: Decode BER serialisation with ASN.1 schema\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> seq = SequenceOf(componentType=Integer())\n#:    >>> s, _ = decode(b'0\\t\\x02\\x01\\x01\\x02\\x01\\x02\\x02\\x01\\x03', asn1Spec=seq)\n#:    >>> str(s)\n#:    SequenceOf:\n#:     1 2 3\n#:\ndecode = Decoder(tagMap, typeMap)\n\n# XXX\n# non-recursive decoding; return position rather than substrate\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/ber/encoder.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nimport sys\n\nfrom pyasn1 import debug\nfrom pyasn1 import error\nfrom pyasn1.codec.ber import eoo\nfrom pyasn1.compat.integer import to_bytes\nfrom pyasn1.compat.octets import (int2oct, oct2int, ints2octs, null,\n                                  str2octs, isOctetsType)\nfrom pyasn1.type import char\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\n__all__ = ['encode']\n\nLOG = debug.registerLoggee(__name__, flags=debug.DEBUG_ENCODER)\n\n\nclass AbstractItemEncoder(object):\n    supportIndefLenMode = True\n\n    # An outcome of otherwise legit call `encodeFun(eoo.endOfOctets)`\n    eooIntegerSubstrate = (0, 0)\n    eooOctetsSubstrate = ints2octs(eooIntegerSubstrate)\n\n    # noinspection PyMethodMayBeStatic\n    def encodeTag(self, singleTag, isConstructed):\n        tagClass, tagFormat, tagId = singleTag\n        encodedTag = tagClass | tagFormat\n        if isConstructed:\n            encodedTag |= tag.tagFormatConstructed\n\n        if tagId < 31:\n            return encodedTag | tagId,\n\n        else:\n            substrate = tagId & 0x7f,\n\n            tagId >>= 7\n\n            while tagId:\n                substrate = (0x80 | (tagId & 0x7f),) + substrate\n                tagId >>= 7\n\n            return (encodedTag | 0x1F,) + substrate\n\n    def encodeLength(self, length, defMode):\n        if not defMode and self.supportIndefLenMode:\n            return (0x80,)\n\n        if length < 0x80:\n            return length,\n\n        else:\n            substrate = ()\n            while length:\n                substrate = (length & 0xff,) + substrate\n                length >>= 8\n\n            substrateLen = len(substrate)\n\n            if substrateLen > 126:\n                raise error.PyAsn1Error('Length octets overflow (%d)' % substrateLen)\n\n            return (0x80 | substrateLen,) + substrate\n\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        raise error.PyAsn1Error('Not implemented')\n\n    def encode(self, value, asn1Spec=None, encodeFun=None, **options):\n\n        if asn1Spec is None:\n            tagSet = value.tagSet\n        else:\n            tagSet = asn1Spec.tagSet\n\n        # untagged item?\n        if not tagSet:\n            substrate, isConstructed, isOctets = self.encodeValue(\n                value, asn1Spec, encodeFun, **options\n            )\n            return substrate\n\n        defMode = options.get('defMode', True)\n\n        substrate = null\n\n        for idx, singleTag in enumerate(tagSet.superTags):\n\n            defModeOverride = defMode\n\n            # base tag?\n            if not idx:\n                try:\n                    substrate, isConstructed, isOctets = self.encodeValue(\n                        value, asn1Spec, encodeFun, **options\n                    )\n\n                except error.PyAsn1Error:\n                    exc = sys.exc_info()\n                    raise error.PyAsn1Error(\n                        'Error encoding %r: %s' % (value, exc[1]))\n\n                if LOG:\n                    LOG('encoded %svalue %s into %s' % (\n                        isConstructed and 'constructed ' or '', value, substrate\n                    ))\n\n                if not substrate and isConstructed and options.get('ifNotEmpty', False):\n                    return substrate\n\n                if not isConstructed:\n                    defModeOverride = True\n\n                    if LOG:\n                        LOG('overridden encoding mode into definitive for primitive type')\n\n            header = self.encodeTag(singleTag, isConstructed)\n\n            if LOG:\n                LOG('encoded %stag %s into %s' % (\n                    isConstructed and 'constructed ' or '',\n                    singleTag, debug.hexdump(ints2octs(header))))\n\n            header += self.encodeLength(len(substrate), defModeOverride)\n\n            if LOG:\n                LOG('encoded %s octets (tag + payload) into %s' % (\n                    len(substrate), debug.hexdump(ints2octs(header))))\n\n            if isOctets:\n                substrate = ints2octs(header) + substrate\n\n                if not defModeOverride:\n                    substrate += self.eooOctetsSubstrate\n\n            else:\n                substrate = header + substrate\n\n                if not defModeOverride:\n                    substrate += self.eooIntegerSubstrate\n\n        if not isOctets:\n            substrate = ints2octs(substrate)\n\n        return substrate\n\n\nclass EndOfOctetsEncoder(AbstractItemEncoder):\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        return null, False, True\n\n\nclass BooleanEncoder(AbstractItemEncoder):\n    supportIndefLenMode = False\n\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        return value and (1,) or (0,), False, False\n\n\nclass IntegerEncoder(AbstractItemEncoder):\n    supportIndefLenMode = False\n    supportCompactZero = False\n\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        if value == 0:\n            if LOG:\n                LOG('encoding %spayload for zero INTEGER' % (\n                    self.supportCompactZero and 'no ' or ''\n                ))\n\n            # de-facto way to encode zero\n            if self.supportCompactZero:\n                return (), False, False\n            else:\n                return (0,), False, False\n\n        return to_bytes(int(value), signed=True), False, True\n\n\nclass BitStringEncoder(AbstractItemEncoder):\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        if asn1Spec is not None:\n            # TODO: try to avoid ASN.1 schema instantiation\n            value = asn1Spec.clone(value)\n\n        valueLength = len(value)\n        if valueLength % 8:\n            alignedValue = value << (8 - valueLength % 8)\n        else:\n            alignedValue = value\n\n        maxChunkSize = options.get('maxChunkSize', 0)\n        if not maxChunkSize or len(alignedValue) <= maxChunkSize * 8:\n            substrate = alignedValue.asOctets()\n            return int2oct(len(substrate) * 8 - valueLength) + substrate, False, True\n\n        if LOG:\n            LOG('encoding into up to %s-octet chunks' % maxChunkSize)\n\n        baseTag = value.tagSet.baseTag\n\n        # strip off explicit tags\n        if baseTag:\n            tagSet = tag.TagSet(baseTag, baseTag)\n\n        else:\n            tagSet = tag.TagSet()\n\n        alignedValue = alignedValue.clone(tagSet=tagSet)\n\n        stop = 0\n        substrate = null\n        while stop < valueLength:\n            start = stop\n            stop = min(start + maxChunkSize * 8, valueLength)\n            substrate += encodeFun(alignedValue[start:stop], asn1Spec, **options)\n\n        return substrate, True, True\n\n\nclass OctetStringEncoder(AbstractItemEncoder):\n\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n\n        if asn1Spec is None:\n            substrate = value.asOctets()\n\n        elif not isOctetsType(value):\n            substrate = asn1Spec.clone(value).asOctets()\n\n        else:\n            substrate = value\n\n        maxChunkSize = options.get('maxChunkSize', 0)\n\n        if not maxChunkSize or len(substrate) <= maxChunkSize:\n            return substrate, False, True\n\n        if LOG:\n            LOG('encoding into up to %s-octet chunks' % maxChunkSize)\n\n        # strip off explicit tags for inner chunks\n\n        if asn1Spec is None:\n            baseTag = value.tagSet.baseTag\n\n            # strip off explicit tags\n            if baseTag:\n                tagSet = tag.TagSet(baseTag, baseTag)\n\n            else:\n                tagSet = tag.TagSet()\n\n            asn1Spec = value.clone(tagSet=tagSet)\n\n        elif not isOctetsType(value):\n            baseTag = asn1Spec.tagSet.baseTag\n\n            # strip off explicit tags\n            if baseTag:\n                tagSet = tag.TagSet(baseTag, baseTag)\n\n            else:\n                tagSet = tag.TagSet()\n\n            asn1Spec = asn1Spec.clone(tagSet=tagSet)\n\n        pos = 0\n        substrate = null\n\n        while True:\n            chunk = value[pos:pos + maxChunkSize]\n            if not chunk:\n                break\n\n            substrate += encodeFun(chunk, asn1Spec, **options)\n            pos += maxChunkSize\n\n        return substrate, True, True\n\n\nclass NullEncoder(AbstractItemEncoder):\n    supportIndefLenMode = False\n\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        return null, False, True\n\n\nclass ObjectIdentifierEncoder(AbstractItemEncoder):\n    supportIndefLenMode = False\n\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        if asn1Spec is not None:\n            value = asn1Spec.clone(value)\n\n        oid = value.asTuple()\n\n        # Build the first pair\n        try:\n            first = oid[0]\n            second = oid[1]\n\n        except IndexError:\n            raise error.PyAsn1Error('Short OID %s' % (value,))\n\n        if 0 <= second <= 39:\n            if first == 1:\n                oid = (second + 40,) + oid[2:]\n            elif first == 0:\n                oid = (second,) + oid[2:]\n            elif first == 2:\n                oid = (second + 80,) + oid[2:]\n            else:\n                raise error.PyAsn1Error('Impossible first/second arcs at %s' % (value,))\n\n        elif first == 2:\n            oid = (second + 80,) + oid[2:]\n\n        else:\n            raise error.PyAsn1Error('Impossible first/second arcs at %s' % (value,))\n\n        octets = ()\n\n        # Cycle through subIds\n        for subOid in oid:\n            if 0 <= subOid <= 127:\n                # Optimize for the common case\n                octets += (subOid,)\n\n            elif subOid > 127:\n                # Pack large Sub-Object IDs\n                res = (subOid & 0x7f,)\n                subOid >>= 7\n\n                while subOid:\n                    res = (0x80 | (subOid & 0x7f),) + res\n                    subOid >>= 7\n\n                # Add packed Sub-Object ID to resulted Object ID\n                octets += res\n\n            else:\n                raise error.PyAsn1Error('Negative OID arc %s at %s' % (subOid, value))\n\n        return octets, False, False\n\n\nclass RealEncoder(AbstractItemEncoder):\n    supportIndefLenMode = 0\n    binEncBase = 2  # set to None to choose encoding base automatically\n\n    @staticmethod\n    def _dropFloatingPoint(m, encbase, e):\n        ms, es = 1, 1\n        if m < 0:\n            ms = -1  # mantissa sign\n\n        if e < 0:\n            es = -1  # exponent sign\n\n        m *= ms\n\n        if encbase == 8:\n            m *= 2 ** (abs(e) % 3 * es)\n            e = abs(e) // 3 * es\n\n        elif encbase == 16:\n            m *= 2 ** (abs(e) % 4 * es)\n            e = abs(e) // 4 * es\n\n        while True:\n            if int(m) != m:\n                m *= encbase\n                e -= 1\n                continue\n            break\n\n        return ms, int(m), encbase, e\n\n    def _chooseEncBase(self, value):\n        m, b, e = value\n        encBase = [2, 8, 16]\n        if value.binEncBase in encBase:\n            return self._dropFloatingPoint(m, value.binEncBase, e)\n\n        elif self.binEncBase in encBase:\n            return self._dropFloatingPoint(m, self.binEncBase, e)\n\n        # auto choosing base 2/8/16\n        mantissa = [m, m, m]\n        exponent = [e, e, e]\n        sign = 1\n        encbase = 2\n        e = float('inf')\n\n        for i in range(3):\n            (sign,\n             mantissa[i],\n             encBase[i],\n             exponent[i]) = self._dropFloatingPoint(mantissa[i], encBase[i], exponent[i])\n\n            if abs(exponent[i]) < abs(e) or (abs(exponent[i]) == abs(e) and mantissa[i] < m):\n                e = exponent[i]\n                m = int(mantissa[i])\n                encbase = encBase[i]\n\n        if LOG:\n            LOG('automatically chosen REAL encoding base %s, sign %s, mantissa %s, '\n                'exponent %s' % (encbase, sign, m, e))\n\n        return sign, m, encbase, e\n\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        if asn1Spec is not None:\n            value = asn1Spec.clone(value)\n\n        if value.isPlusInf:\n            return (0x40,), False, False\n\n        if value.isMinusInf:\n            return (0x41,), False, False\n\n        m, b, e = value\n\n        if not m:\n            return null, False, True\n\n        if b == 10:\n            if LOG:\n                LOG('encoding REAL into character form')\n\n            return str2octs('\\x03%dE%s%d' % (m, e == 0 and '+' or '', e)), False, True\n\n        elif b == 2:\n            fo = 0x80  # binary encoding\n            ms, m, encbase, e = self._chooseEncBase(value)\n\n            if ms < 0:  # mantissa sign\n                fo |= 0x40  # sign bit\n\n            # exponent & mantissa normalization\n            if encbase == 2:\n                while m & 0x1 == 0:\n                    m >>= 1\n                    e += 1\n\n            elif encbase == 8:\n                while m & 0x7 == 0:\n                    m >>= 3\n                    e += 1\n                fo |= 0x10\n\n            else:  # encbase = 16\n                while m & 0xf == 0:\n                    m >>= 4\n                    e += 1\n                fo |= 0x20\n\n            sf = 0  # scale factor\n\n            while m & 0x1 == 0:\n                m >>= 1\n                sf += 1\n\n            if sf > 3:\n                raise error.PyAsn1Error('Scale factor overflow')  # bug if raised\n\n            fo |= sf << 2\n            eo = null\n            if e == 0 or e == -1:\n                eo = int2oct(e & 0xff)\n\n            else:\n                while e not in (0, -1):\n                    eo = int2oct(e & 0xff) + eo\n                    e >>= 8\n\n                if e == 0 and eo and oct2int(eo[0]) & 0x80:\n                    eo = int2oct(0) + eo\n\n                if e == -1 and eo and not (oct2int(eo[0]) & 0x80):\n                    eo = int2oct(0xff) + eo\n\n            n = len(eo)\n            if n > 0xff:\n                raise error.PyAsn1Error('Real exponent overflow')\n\n            if n == 1:\n                pass\n\n            elif n == 2:\n                fo |= 1\n\n            elif n == 3:\n                fo |= 2\n\n            else:\n                fo |= 3\n                eo = int2oct(n & 0xff) + eo\n\n            po = null\n\n            while m:\n                po = int2oct(m & 0xff) + po\n                m >>= 8\n\n            substrate = int2oct(fo) + eo + po\n\n            return substrate, False, True\n\n        else:\n            raise error.PyAsn1Error('Prohibited Real base %s' % b)\n\n\nclass SequenceEncoder(AbstractItemEncoder):\n    omitEmptyOptionals = False\n\n    # TODO: handling three flavors of input is too much -- split over codecs\n\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n\n        substrate = null\n\n        omitEmptyOptionals = options.get(\n            'omitEmptyOptionals', self.omitEmptyOptionals)\n\n        if LOG:\n            LOG('%sencoding empty OPTIONAL components' % (\n                    omitEmptyOptionals and 'not ' or ''))\n\n        if asn1Spec is None:\n            # instance of ASN.1 schema\n            inconsistency = value.isInconsistent\n            if inconsistency:\n                raise inconsistency\n\n            namedTypes = value.componentType\n\n            for idx, component in enumerate(value.values()):\n                if namedTypes:\n                    namedType = namedTypes[idx]\n\n                    if namedType.isOptional and not component.isValue:\n                        if LOG:\n                            LOG('not encoding OPTIONAL component %r' % (namedType,))\n                        continue\n\n                    if namedType.isDefaulted and component == namedType.asn1Object:\n                        if LOG:\n                            LOG('not encoding DEFAULT component %r' % (namedType,))\n                        continue\n\n                    if omitEmptyOptionals:\n                        options.update(ifNotEmpty=namedType.isOptional)\n\n                # wrap open type blob if needed\n                if namedTypes and namedType.openType:\n\n                    wrapType = namedType.asn1Object\n\n                    if wrapType.typeId in (\n                            univ.SetOf.typeId, univ.SequenceOf.typeId):\n\n                        substrate += encodeFun(\n                                component, asn1Spec,\n                                **dict(options, wrapType=wrapType.componentType))\n\n                    else:\n                        chunk = encodeFun(component, asn1Spec, **options)\n\n                        if wrapType.isSameTypeWith(component):\n                            substrate += chunk\n\n                        else:\n                            substrate += encodeFun(chunk, wrapType, **options)\n\n                            if LOG:\n                                LOG('wrapped with wrap type %r' % (wrapType,))\n\n                else:\n                    substrate += encodeFun(component, asn1Spec, **options)\n\n        else:\n            # bare Python value + ASN.1 schema\n            for idx, namedType in enumerate(asn1Spec.componentType.namedTypes):\n\n                try:\n                    component = value[namedType.name]\n\n                except KeyError:\n                    raise error.PyAsn1Error('Component name \"%s\" not found in %r' % (\n                        namedType.name, value))\n\n                if namedType.isOptional and namedType.name not in value:\n                    if LOG:\n                        LOG('not encoding OPTIONAL component %r' % (namedType,))\n                    continue\n\n                if namedType.isDefaulted and component == namedType.asn1Object:\n                    if LOG:\n                        LOG('not encoding DEFAULT component %r' % (namedType,))\n                    continue\n\n                if omitEmptyOptionals:\n                    options.update(ifNotEmpty=namedType.isOptional)\n\n                componentSpec = namedType.asn1Object\n\n                # wrap open type blob if needed\n                if namedType.openType:\n\n                    if componentSpec.typeId in (\n                            univ.SetOf.typeId, univ.SequenceOf.typeId):\n\n                        substrate += encodeFun(\n                                component, componentSpec,\n                                **dict(options, wrapType=componentSpec.componentType))\n\n                    else:\n                        chunk = encodeFun(component, componentSpec, **options)\n\n                        if componentSpec.isSameTypeWith(component):\n                            substrate += chunk\n\n                        else:\n                            substrate += encodeFun(chunk, componentSpec, **options)\n\n                            if LOG:\n                                LOG('wrapped with wrap type %r' % (componentSpec,))\n\n                else:\n                    substrate += encodeFun(component, componentSpec, **options)\n\n        return substrate, True, True\n\n\nclass SequenceOfEncoder(AbstractItemEncoder):\n    def _encodeComponents(self, value, asn1Spec, encodeFun, **options):\n\n        if asn1Spec is None:\n            inconsistency = value.isInconsistent\n            if inconsistency:\n                raise inconsistency\n\n        else:\n            asn1Spec = asn1Spec.componentType\n\n        chunks = []\n\n        wrapType = options.pop('wrapType', None)\n\n        for idx, component in enumerate(value):\n            chunk = encodeFun(component, asn1Spec, **options)\n\n            if (wrapType is not None and\n                    not wrapType.isSameTypeWith(component)):\n                # wrap encoded value with wrapper container (e.g. ANY)\n                chunk = encodeFun(chunk, wrapType, **options)\n\n                if LOG:\n                    LOG('wrapped with wrap type %r' % (wrapType,))\n\n            chunks.append(chunk)\n\n        return chunks\n\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        chunks = self._encodeComponents(\n            value, asn1Spec, encodeFun, **options)\n\n        return null.join(chunks), True, True\n\n\nclass ChoiceEncoder(AbstractItemEncoder):\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        if asn1Spec is None:\n            component = value.getComponent()\n        else:\n            names = [namedType.name for namedType in asn1Spec.componentType.namedTypes\n                     if namedType.name in value]\n            if len(names) != 1:\n                raise error.PyAsn1Error('%s components for Choice at %r' % (len(names) and 'Multiple ' or 'None ', value))\n\n            name = names[0]\n\n            component = value[name]\n            asn1Spec = asn1Spec[name]\n\n        return encodeFun(component, asn1Spec, **options), True, True\n\n\nclass AnyEncoder(OctetStringEncoder):\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        if asn1Spec is None:\n            value = value.asOctets()\n        elif not isOctetsType(value):\n            value = asn1Spec.clone(value).asOctets()\n\n        return value, not options.get('defMode', True), True\n\n\ntagMap = {\n    eoo.endOfOctets.tagSet: EndOfOctetsEncoder(),\n    univ.Boolean.tagSet: BooleanEncoder(),\n    univ.Integer.tagSet: IntegerEncoder(),\n    univ.BitString.tagSet: BitStringEncoder(),\n    univ.OctetString.tagSet: OctetStringEncoder(),\n    univ.Null.tagSet: NullEncoder(),\n    univ.ObjectIdentifier.tagSet: ObjectIdentifierEncoder(),\n    univ.Enumerated.tagSet: IntegerEncoder(),\n    univ.Real.tagSet: RealEncoder(),\n    # Sequence & Set have same tags as SequenceOf & SetOf\n    univ.SequenceOf.tagSet: SequenceOfEncoder(),\n    univ.SetOf.tagSet: SequenceOfEncoder(),\n    univ.Choice.tagSet: ChoiceEncoder(),\n    # character string types\n    char.UTF8String.tagSet: OctetStringEncoder(),\n    char.NumericString.tagSet: OctetStringEncoder(),\n    char.PrintableString.tagSet: OctetStringEncoder(),\n    char.TeletexString.tagSet: OctetStringEncoder(),\n    char.VideotexString.tagSet: OctetStringEncoder(),\n    char.IA5String.tagSet: OctetStringEncoder(),\n    char.GraphicString.tagSet: OctetStringEncoder(),\n    char.VisibleString.tagSet: OctetStringEncoder(),\n    char.GeneralString.tagSet: OctetStringEncoder(),\n    char.UniversalString.tagSet: OctetStringEncoder(),\n    char.BMPString.tagSet: OctetStringEncoder(),\n    # useful types\n    useful.ObjectDescriptor.tagSet: OctetStringEncoder(),\n    useful.GeneralizedTime.tagSet: OctetStringEncoder(),\n    useful.UTCTime.tagSet: OctetStringEncoder()\n}\n\n# Put in ambiguous & non-ambiguous types for faster codec lookup\ntypeMap = {\n    univ.Boolean.typeId: BooleanEncoder(),\n    univ.Integer.typeId: IntegerEncoder(),\n    univ.BitString.typeId: BitStringEncoder(),\n    univ.OctetString.typeId: OctetStringEncoder(),\n    univ.Null.typeId: NullEncoder(),\n    univ.ObjectIdentifier.typeId: ObjectIdentifierEncoder(),\n    univ.Enumerated.typeId: IntegerEncoder(),\n    univ.Real.typeId: RealEncoder(),\n    # Sequence & Set have same tags as SequenceOf & SetOf\n    univ.Set.typeId: SequenceEncoder(),\n    univ.SetOf.typeId: SequenceOfEncoder(),\n    univ.Sequence.typeId: SequenceEncoder(),\n    univ.SequenceOf.typeId: SequenceOfEncoder(),\n    univ.Choice.typeId: ChoiceEncoder(),\n    univ.Any.typeId: AnyEncoder(),\n    # character string types\n    char.UTF8String.typeId: OctetStringEncoder(),\n    char.NumericString.typeId: OctetStringEncoder(),\n    char.PrintableString.typeId: OctetStringEncoder(),\n    char.TeletexString.typeId: OctetStringEncoder(),\n    char.VideotexString.typeId: OctetStringEncoder(),\n    char.IA5String.typeId: OctetStringEncoder(),\n    char.GraphicString.typeId: OctetStringEncoder(),\n    char.VisibleString.typeId: OctetStringEncoder(),\n    char.GeneralString.typeId: OctetStringEncoder(),\n    char.UniversalString.typeId: OctetStringEncoder(),\n    char.BMPString.typeId: OctetStringEncoder(),\n    # useful types\n    useful.ObjectDescriptor.typeId: OctetStringEncoder(),\n    useful.GeneralizedTime.typeId: OctetStringEncoder(),\n    useful.UTCTime.typeId: OctetStringEncoder()\n}\n\n\nclass Encoder(object):\n    fixedDefLengthMode = None\n    fixedChunkSize = None\n\n    # noinspection PyDefaultArgument\n    def __init__(self, tagMap, typeMap={}):\n        self.__tagMap = tagMap\n        self.__typeMap = typeMap\n\n    def __call__(self, value, asn1Spec=None, **options):\n        try:\n            if asn1Spec is None:\n                typeId = value.typeId\n            else:\n                typeId = asn1Spec.typeId\n\n        except AttributeError:\n            raise error.PyAsn1Error('Value %r is not ASN.1 type instance '\n                                    'and \"asn1Spec\" not given' % (value,))\n\n        if LOG:\n            LOG('encoder called in %sdef mode, chunk size %s for '\n                   'type %s, value:\\n%s' % (not options.get('defMode', True) and 'in' or '', options.get('maxChunkSize', 0), asn1Spec is None and value.prettyPrintType() or asn1Spec.prettyPrintType(), value))\n\n        if self.fixedDefLengthMode is not None:\n            options.update(defMode=self.fixedDefLengthMode)\n\n        if self.fixedChunkSize is not None:\n            options.update(maxChunkSize=self.fixedChunkSize)\n\n\n        try:\n            concreteEncoder = self.__typeMap[typeId]\n\n            if LOG:\n                LOG('using value codec %s chosen by type ID %s' % (concreteEncoder.__class__.__name__, typeId))\n\n        except KeyError:\n            if asn1Spec is None:\n                tagSet = value.tagSet\n            else:\n                tagSet = asn1Spec.tagSet\n\n            # use base type for codec lookup to recover untagged types\n            baseTagSet = tag.TagSet(tagSet.baseTag, tagSet.baseTag)\n\n            try:\n                concreteEncoder = self.__tagMap[baseTagSet]\n\n            except KeyError:\n                raise error.PyAsn1Error('No encoder for %r (%s)' % (value, tagSet))\n\n            if LOG:\n                LOG('using value codec %s chosen by tagSet %s' % (concreteEncoder.__class__.__name__, tagSet))\n\n        substrate = concreteEncoder.encode(value, asn1Spec, self, **options)\n\n        if LOG:\n            LOG('codec %s built %s octets of substrate: %s\\nencoder completed' % (concreteEncoder, len(substrate), debug.hexdump(substrate)))\n\n        return substrate\n\n#: Turns ASN.1 object into BER octet stream.\n#:\n#: Takes any ASN.1 object (e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative)\n#: walks all its components recursively and produces a BER octet stream.\n#:\n#: Parameters\n#: ----------\n#: value: either a Python or pyasn1 object (e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative)\n#:     A Python or pyasn1 object to encode. If Python object is given, `asnSpec`\n#:     parameter is required to guide the encoding process.\n#:\n#: Keyword Args\n#: ------------\n#: asn1Spec:\n#:     Optional ASN.1 schema or value object e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n#:\n#: defMode: :py:class:`bool`\n#:     If :obj:`False`, produces indefinite length encoding\n#:\n#: maxChunkSize: :py:class:`int`\n#:     Maximum chunk size in chunked encoding mode (0 denotes unlimited chunk size)\n#:\n#: Returns\n#: -------\n#: : :py:class:`bytes` (Python 3) or :py:class:`str` (Python 2)\n#:     Given ASN.1 object encoded into BER octetstream\n#:\n#: Raises\n#: ------\n#: ~pyasn1.error.PyAsn1Error\n#:     On encoding errors\n#:\n#: Examples\n#: --------\n#: Encode Python value into BER with ASN.1 schema\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> seq = SequenceOf(componentType=Integer())\n#:    >>> encode([1, 2, 3], asn1Spec=seq)\n#:    b'0\\t\\x02\\x01\\x01\\x02\\x01\\x02\\x02\\x01\\x03'\n#:\n#: Encode ASN.1 value object into BER\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> seq = SequenceOf(componentType=Integer())\n#:    >>> seq.extend([1, 2, 3])\n#:    >>> encode(seq)\n#:    b'0\\t\\x02\\x01\\x01\\x02\\x01\\x02\\x02\\x01\\x03'\n#:\nencode = Encoder(tagMap, typeMap)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/ber/eoo.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom pyasn1.type import base\nfrom pyasn1.type import tag\n\n__all__ = ['endOfOctets']\n\n\nclass EndOfOctets(base.SimpleAsn1Type):\n    defaultValue = 0\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 0x00)\n    )\n\n    _instance = None\n\n    def __new__(cls, *args, **kwargs):\n        if cls._instance is None:\n            cls._instance = object.__new__(cls, *args, **kwargs)\n\n        return cls._instance\n\n\nendOfOctets = EndOfOctets()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/cer/__init__.py",
    "content": "# This file is necessary to make this directory a package.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/cer/decoder.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom pyasn1 import error\nfrom pyasn1.codec.ber import decoder\nfrom pyasn1.compat.octets import oct2int\nfrom pyasn1.type import univ\n\n__all__ = ['decode']\n\n\nclass BooleanDecoder(decoder.AbstractSimpleDecoder):\n    protoComponent = univ.Boolean(0)\n\n    def valueDecoder(self, substrate, asn1Spec,\n                     tagSet=None, length=None, state=None,\n                     decodeFun=None, substrateFun=None,\n                     **options):\n        head, tail = substrate[:length], substrate[length:]\n        if not head or length != 1:\n            raise error.PyAsn1Error('Not single-octet Boolean payload')\n        byte = oct2int(head[0])\n        # CER/DER specifies encoding of TRUE as 0xFF and FALSE as 0x0, while\n        # BER allows any non-zero value as TRUE; cf. sections 8.2.2. and 11.1 \n        # in https://www.itu.int/ITU-T/studygroups/com17/languages/X.690-0207.pdf\n        if byte == 0xff:\n            value = 1\n        elif byte == 0x00:\n            value = 0\n        else:\n            raise error.PyAsn1Error('Unexpected Boolean payload: %s' % byte)\n        return self._createComponent(asn1Spec, tagSet, value, **options), tail\n\n# TODO: prohibit non-canonical encoding\nBitStringDecoder = decoder.BitStringDecoder\nOctetStringDecoder = decoder.OctetStringDecoder\nRealDecoder = decoder.RealDecoder\n\ntagMap = decoder.tagMap.copy()\ntagMap.update(\n    {univ.Boolean.tagSet: BooleanDecoder(),\n     univ.BitString.tagSet: BitStringDecoder(),\n     univ.OctetString.tagSet: OctetStringDecoder(),\n     univ.Real.tagSet: RealDecoder()}\n)\n\ntypeMap = decoder.typeMap.copy()\n\n# Put in non-ambiguous types for faster codec lookup\nfor typeDecoder in tagMap.values():\n    if typeDecoder.protoComponent is not None:\n        typeId = typeDecoder.protoComponent.__class__.typeId\n        if typeId is not None and typeId not in typeMap:\n            typeMap[typeId] = typeDecoder\n\n\nclass Decoder(decoder.Decoder):\n    pass\n\n\n#: Turns CER octet stream into an ASN.1 object.\n#:\n#: Takes CER octet-stream and decode it into an ASN.1 object\n#: (e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative) which\n#: may be a scalar or an arbitrary nested structure.\n#:\n#: Parameters\n#: ----------\n#: substrate: :py:class:`bytes` (Python 3) or :py:class:`str` (Python 2)\n#:     CER octet-stream\n#:\n#: Keyword Args\n#: ------------\n#: asn1Spec: any pyasn1 type object e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n#:     A pyasn1 type object to act as a template guiding the decoder. Depending on the ASN.1 structure\n#:     being decoded, *asn1Spec* may or may not be required. Most common reason for\n#:     it to require is that ASN.1 structure is encoded in *IMPLICIT* tagging mode.\n#:\n#: Returns\n#: -------\n#: : :py:class:`tuple`\n#:     A tuple of pyasn1 object recovered from CER substrate (:py:class:`~pyasn1.type.base.PyAsn1Item` derivative)\n#:     and the unprocessed trailing portion of the *substrate* (may be empty)\n#:\n#: Raises\n#: ------\n#: ~pyasn1.error.PyAsn1Error, ~pyasn1.error.SubstrateUnderrunError\n#:     On decoding errors\n#:\n#: Examples\n#: --------\n#: Decode CER serialisation without ASN.1 schema\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> s, _ = decode(b'0\\x80\\x02\\x01\\x01\\x02\\x01\\x02\\x02\\x01\\x03\\x00\\x00')\n#:    >>> str(s)\n#:    SequenceOf:\n#:     1 2 3\n#:\n#: Decode CER serialisation with ASN.1 schema\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> seq = SequenceOf(componentType=Integer())\n#:    >>> s, _ = decode(b'0\\x80\\x02\\x01\\x01\\x02\\x01\\x02\\x02\\x01\\x03\\x00\\x00', asn1Spec=seq)\n#:    >>> str(s)\n#:    SequenceOf:\n#:     1 2 3\n#:\ndecode = Decoder(tagMap, decoder.typeMap)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/cer/encoder.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom pyasn1 import error\nfrom pyasn1.codec.ber import encoder\nfrom pyasn1.compat.octets import str2octs, null\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\n__all__ = ['encode']\n\n\nclass BooleanEncoder(encoder.IntegerEncoder):\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        if value == 0:\n            substrate = (0,)\n        else:\n            substrate = (255,)\n        return substrate, False, False\n\n\nclass RealEncoder(encoder.RealEncoder):\n    def _chooseEncBase(self, value):\n        m, b, e = value\n        return self._dropFloatingPoint(m, b, e)\n\n\n# specialized GeneralStringEncoder here\n\nclass TimeEncoderMixIn(object):\n    Z_CHAR = ord('Z')\n    PLUS_CHAR = ord('+')\n    MINUS_CHAR = ord('-')\n    COMMA_CHAR = ord(',')\n    DOT_CHAR = ord('.')\n    ZERO_CHAR = ord('0')\n\n    MIN_LENGTH = 12\n    MAX_LENGTH = 19\n\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        # CER encoding constraints:\n        # - minutes are mandatory, seconds are optional\n        # - sub-seconds must NOT be zero / no meaningless zeros\n        # - no hanging fraction dot\n        # - time in UTC (Z)\n        # - only dot is allowed for fractions\n\n        if asn1Spec is not None:\n            value = asn1Spec.clone(value)\n\n        numbers = value.asNumbers()\n\n        if self.PLUS_CHAR in numbers or self.MINUS_CHAR in numbers:\n            raise error.PyAsn1Error('Must be UTC time: %r' % value)\n\n        if numbers[-1] != self.Z_CHAR:\n            raise error.PyAsn1Error('Missing \"Z\" time zone specifier: %r' % value)\n\n        if self.COMMA_CHAR in numbers:\n            raise error.PyAsn1Error('Comma in fractions disallowed: %r' % value)\n\n        if self.DOT_CHAR in numbers:\n\n            isModified = False\n\n            numbers = list(numbers)\n\n            searchIndex = min(numbers.index(self.DOT_CHAR) + 4, len(numbers) - 1)\n\n            while numbers[searchIndex] != self.DOT_CHAR:\n                if numbers[searchIndex] == self.ZERO_CHAR:\n                    del numbers[searchIndex]\n                    isModified = True\n\n                searchIndex -= 1\n\n            searchIndex += 1\n\n            if searchIndex < len(numbers):\n                if numbers[searchIndex] == self.Z_CHAR:\n                    # drop hanging comma\n                    del numbers[searchIndex - 1]\n                    isModified = True\n\n            if isModified:\n                value = value.clone(numbers)\n\n        if not self.MIN_LENGTH < len(numbers) < self.MAX_LENGTH:\n            raise error.PyAsn1Error('Length constraint violated: %r' % value)\n\n        options.update(maxChunkSize=1000)\n\n        return encoder.OctetStringEncoder.encodeValue(\n            self, value, asn1Spec, encodeFun, **options\n        )\n\n\nclass GeneralizedTimeEncoder(TimeEncoderMixIn, encoder.OctetStringEncoder):\n    MIN_LENGTH = 12\n    MAX_LENGTH = 20\n\n\nclass UTCTimeEncoder(TimeEncoderMixIn, encoder.OctetStringEncoder):\n    MIN_LENGTH = 10\n    MAX_LENGTH = 14\n\n\nclass SetOfEncoder(encoder.SequenceOfEncoder):\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n        chunks = self._encodeComponents(\n            value, asn1Spec, encodeFun, **options)\n\n        # sort by serialised and padded components\n        if len(chunks) > 1:\n            zero = str2octs('\\x00')\n            maxLen = max(map(len, chunks))\n            paddedChunks = [\n                (x.ljust(maxLen, zero), x) for x in chunks\n            ]\n            paddedChunks.sort(key=lambda x: x[0])\n\n            chunks = [x[1] for x in paddedChunks]\n\n        return null.join(chunks), True, True\n\n\nclass SequenceOfEncoder(encoder.SequenceOfEncoder):\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n\n        if options.get('ifNotEmpty', False) and not len(value):\n            return null, True, True\n\n        chunks = self._encodeComponents(\n            value, asn1Spec, encodeFun, **options)\n\n        return null.join(chunks), True, True\n\n\nclass SetEncoder(encoder.SequenceEncoder):\n    @staticmethod\n    def _componentSortKey(componentAndType):\n        \"\"\"Sort SET components by tag\n\n        Sort regardless of the Choice value (static sort)\n        \"\"\"\n        component, asn1Spec = componentAndType\n\n        if asn1Spec is None:\n            asn1Spec = component\n\n        if asn1Spec.typeId == univ.Choice.typeId and not asn1Spec.tagSet:\n            if asn1Spec.tagSet:\n                return asn1Spec.tagSet\n            else:\n                return asn1Spec.componentType.minTagSet\n        else:\n            return asn1Spec.tagSet\n\n    def encodeValue(self, value, asn1Spec, encodeFun, **options):\n\n        substrate = null\n\n        comps = []\n        compsMap = {}\n\n        if asn1Spec is None:\n            # instance of ASN.1 schema\n            inconsistency = value.isInconsistent\n            if inconsistency:\n                raise inconsistency\n\n            namedTypes = value.componentType\n\n            for idx, component in enumerate(value.values()):\n                if namedTypes:\n                    namedType = namedTypes[idx]\n\n                    if namedType.isOptional and not component.isValue:\n                            continue\n\n                    if namedType.isDefaulted and component == namedType.asn1Object:\n                            continue\n\n                    compsMap[id(component)] = namedType\n\n                else:\n                    compsMap[id(component)] = None\n\n                comps.append((component, asn1Spec))\n\n        else:\n            # bare Python value + ASN.1 schema\n            for idx, namedType in enumerate(asn1Spec.componentType.namedTypes):\n\n                try:\n                    component = value[namedType.name]\n\n                except KeyError:\n                    raise error.PyAsn1Error('Component name \"%s\" not found in %r' % (namedType.name, value))\n\n                if namedType.isOptional and namedType.name not in value:\n                    continue\n\n                if namedType.isDefaulted and component == namedType.asn1Object:\n                    continue\n\n                compsMap[id(component)] = namedType\n                comps.append((component, asn1Spec[idx]))\n\n        for comp, compType in sorted(comps, key=self._componentSortKey):\n            namedType = compsMap[id(comp)]\n\n            if namedType:\n                options.update(ifNotEmpty=namedType.isOptional)\n\n            chunk = encodeFun(comp, compType, **options)\n\n            # wrap open type blob if needed\n            if namedType and namedType.openType:\n                wrapType = namedType.asn1Object\n                if wrapType.tagSet and not wrapType.isSameTypeWith(comp):\n                    chunk = encodeFun(chunk, wrapType, **options)\n\n            substrate += chunk\n\n        return substrate, True, True\n\n\nclass SequenceEncoder(encoder.SequenceEncoder):\n    omitEmptyOptionals = True\n\n\ntagMap = encoder.tagMap.copy()\ntagMap.update({\n    univ.Boolean.tagSet: BooleanEncoder(),\n    univ.Real.tagSet: RealEncoder(),\n    useful.GeneralizedTime.tagSet: GeneralizedTimeEncoder(),\n    useful.UTCTime.tagSet: UTCTimeEncoder(),\n    # Sequence & Set have same tags as SequenceOf & SetOf\n    univ.SetOf.tagSet: SetOfEncoder(),\n    univ.Sequence.typeId: SequenceEncoder()\n})\n\ntypeMap = encoder.typeMap.copy()\ntypeMap.update({\n    univ.Boolean.typeId: BooleanEncoder(),\n    univ.Real.typeId: RealEncoder(),\n    useful.GeneralizedTime.typeId: GeneralizedTimeEncoder(),\n    useful.UTCTime.typeId: UTCTimeEncoder(),\n    # Sequence & Set have same tags as SequenceOf & SetOf\n    univ.Set.typeId: SetEncoder(),\n    univ.SetOf.typeId: SetOfEncoder(),\n    univ.Sequence.typeId: SequenceEncoder(),\n    univ.SequenceOf.typeId: SequenceOfEncoder()\n})\n\n\nclass Encoder(encoder.Encoder):\n    fixedDefLengthMode = False\n    fixedChunkSize = 1000\n\n#: Turns ASN.1 object into CER octet stream.\n#:\n#: Takes any ASN.1 object (e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative)\n#: walks all its components recursively and produces a CER octet stream.\n#:\n#: Parameters\n#: ----------\n#: value: either a Python or pyasn1 object (e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative)\n#:     A Python or pyasn1 object to encode. If Python object is given, `asnSpec`\n#:     parameter is required to guide the encoding process.\n#:\n#: Keyword Args\n#: ------------\n#: asn1Spec:\n#:     Optional ASN.1 schema or value object e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n#:\n#: Returns\n#: -------\n#: : :py:class:`bytes` (Python 3) or :py:class:`str` (Python 2)\n#:     Given ASN.1 object encoded into BER octet-stream\n#:\n#: Raises\n#: ------\n#: ~pyasn1.error.PyAsn1Error\n#:     On encoding errors\n#:\n#: Examples\n#: --------\n#: Encode Python value into CER with ASN.1 schema\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> seq = SequenceOf(componentType=Integer())\n#:    >>> encode([1, 2, 3], asn1Spec=seq)\n#:    b'0\\x80\\x02\\x01\\x01\\x02\\x01\\x02\\x02\\x01\\x03\\x00\\x00'\n#:\n#: Encode ASN.1 value object into CER\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> seq = SequenceOf(componentType=Integer())\n#:    >>> seq.extend([1, 2, 3])\n#:    >>> encode(seq)\n#:    b'0\\x80\\x02\\x01\\x01\\x02\\x01\\x02\\x02\\x01\\x03\\x00\\x00'\n#:\nencode = Encoder(tagMap, typeMap)\n\n# EncoderFactory queries class instance and builds a map of tags -> encoders\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/der/__init__.py",
    "content": "# This file is necessary to make this directory a package.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/der/decoder.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom pyasn1.codec.cer import decoder\nfrom pyasn1.type import univ\n\n__all__ = ['decode']\n\n\nclass BitStringDecoder(decoder.BitStringDecoder):\n    supportConstructedForm = False\n\n\nclass OctetStringDecoder(decoder.OctetStringDecoder):\n    supportConstructedForm = False\n\n# TODO: prohibit non-canonical encoding\nRealDecoder = decoder.RealDecoder\n\ntagMap = decoder.tagMap.copy()\ntagMap.update(\n    {univ.BitString.tagSet: BitStringDecoder(),\n     univ.OctetString.tagSet: OctetStringDecoder(),\n     univ.Real.tagSet: RealDecoder()}\n)\n\ntypeMap = decoder.typeMap.copy()\n\n# Put in non-ambiguous types for faster codec lookup\nfor typeDecoder in tagMap.values():\n    if typeDecoder.protoComponent is not None:\n        typeId = typeDecoder.protoComponent.__class__.typeId\n        if typeId is not None and typeId not in typeMap:\n            typeMap[typeId] = typeDecoder\n\n\nclass Decoder(decoder.Decoder):\n    supportIndefLength = False\n\n\n#: Turns DER octet stream into an ASN.1 object.\n#:\n#: Takes DER octet-stream and decode it into an ASN.1 object\n#: (e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative) which\n#: may be a scalar or an arbitrary nested structure.\n#:\n#: Parameters\n#: ----------\n#: substrate: :py:class:`bytes` (Python 3) or :py:class:`str` (Python 2)\n#:     DER octet-stream\n#:\n#: Keyword Args\n#: ------------\n#: asn1Spec: any pyasn1 type object e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n#:     A pyasn1 type object to act as a template guiding the decoder. Depending on the ASN.1 structure\n#:     being decoded, *asn1Spec* may or may not be required. Most common reason for\n#:     it to require is that ASN.1 structure is encoded in *IMPLICIT* tagging mode.\n#:\n#: Returns\n#: -------\n#: : :py:class:`tuple`\n#:     A tuple of pyasn1 object recovered from DER substrate (:py:class:`~pyasn1.type.base.PyAsn1Item` derivative)\n#:     and the unprocessed trailing portion of the *substrate* (may be empty)\n#:\n#: Raises\n#: ------\n#: ~pyasn1.error.PyAsn1Error, ~pyasn1.error.SubstrateUnderrunError\n#:     On decoding errors\n#:\n#: Examples\n#: --------\n#: Decode DER serialisation without ASN.1 schema\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> s, _ = decode(b'0\\t\\x02\\x01\\x01\\x02\\x01\\x02\\x02\\x01\\x03')\n#:    >>> str(s)\n#:    SequenceOf:\n#:     1 2 3\n#:\n#: Decode DER serialisation with ASN.1 schema\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> seq = SequenceOf(componentType=Integer())\n#:    >>> s, _ = decode(b'0\\t\\x02\\x01\\x01\\x02\\x01\\x02\\x02\\x01\\x03', asn1Spec=seq)\n#:    >>> str(s)\n#:    SequenceOf:\n#:     1 2 3\n#:\ndecode = Decoder(tagMap, typeMap)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/der/encoder.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom pyasn1 import error\nfrom pyasn1.codec.cer import encoder\nfrom pyasn1.type import univ\n\n__all__ = ['encode']\n\n\nclass SetEncoder(encoder.SetEncoder):\n    @staticmethod\n    def _componentSortKey(componentAndType):\n        \"\"\"Sort SET components by tag\n\n        Sort depending on the actual Choice value (dynamic sort)\n        \"\"\"\n        component, asn1Spec = componentAndType\n\n        if asn1Spec is None:\n            compType = component\n        else:\n            compType = asn1Spec\n\n        if compType.typeId == univ.Choice.typeId and not compType.tagSet:\n            if asn1Spec is None:\n                return component.getComponent().tagSet\n            else:\n                # TODO: move out of sorting key function\n                names = [namedType.name for namedType in asn1Spec.componentType.namedTypes\n                         if namedType.name in component]\n                if len(names) != 1:\n                    raise error.PyAsn1Error(\n                        '%s components for Choice at %r' % (len(names) and 'Multiple ' or 'None ', component))\n\n                # TODO: support nested CHOICE ordering\n                return asn1Spec[names[0]].tagSet\n\n        else:\n            return compType.tagSet\n\ntagMap = encoder.tagMap.copy()\ntagMap.update({\n    # Set & SetOf have same tags\n    univ.Set.tagSet: SetEncoder()\n})\n\ntypeMap = encoder.typeMap.copy()\ntypeMap.update({\n    # Set & SetOf have same tags\n    univ.Set.typeId: SetEncoder()\n})\n\n\nclass Encoder(encoder.Encoder):\n    fixedDefLengthMode = True\n    fixedChunkSize = 0\n\n#: Turns ASN.1 object into DER octet stream.\n#:\n#: Takes any ASN.1 object (e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative)\n#: walks all its components recursively and produces a DER octet stream.\n#:\n#: Parameters\n#: ----------\n#: value: either a Python or pyasn1 object (e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative)\n#:     A Python or pyasn1 object to encode. If Python object is given, `asnSpec`\n#:     parameter is required to guide the encoding process.\n#:\n#: Keyword Args\n#: ------------\n#: asn1Spec:\n#:     Optional ASN.1 schema or value object e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n#:\n#: Returns\n#: -------\n#: : :py:class:`bytes` (Python 3) or :py:class:`str` (Python 2)\n#:     Given ASN.1 object encoded into BER octet-stream\n#:\n#: Raises\n#: ------\n#: ~pyasn1.error.PyAsn1Error\n#:     On encoding errors\n#:\n#: Examples\n#: --------\n#: Encode Python value into DER with ASN.1 schema\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> seq = SequenceOf(componentType=Integer())\n#:    >>> encode([1, 2, 3], asn1Spec=seq)\n#:    b'0\\t\\x02\\x01\\x01\\x02\\x01\\x02\\x02\\x01\\x03'\n#:\n#: Encode ASN.1 value object into DER\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> seq = SequenceOf(componentType=Integer())\n#:    >>> seq.extend([1, 2, 3])\n#:    >>> encode(seq)\n#:    b'0\\t\\x02\\x01\\x01\\x02\\x01\\x02\\x02\\x01\\x03'\n#:\nencode = Encoder(tagMap, typeMap)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/native/__init__.py",
    "content": "# This file is necessary to make this directory a package.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/native/decoder.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom pyasn1 import debug\nfrom pyasn1 import error\nfrom pyasn1.type import base\nfrom pyasn1.type import char\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\n__all__ = ['decode']\n\nLOG = debug.registerLoggee(__name__, flags=debug.DEBUG_DECODER)\n\n\nclass AbstractScalarDecoder(object):\n    def __call__(self, pyObject, asn1Spec, decodeFun=None, **options):\n        return asn1Spec.clone(pyObject)\n\n\nclass BitStringDecoder(AbstractScalarDecoder):\n    def __call__(self, pyObject, asn1Spec, decodeFun=None, **options):\n        return asn1Spec.clone(univ.BitString.fromBinaryString(pyObject))\n\n\nclass SequenceOrSetDecoder(object):\n    def __call__(self, pyObject, asn1Spec, decodeFun=None, **options):\n        asn1Value = asn1Spec.clone()\n\n        componentsTypes = asn1Spec.componentType\n\n        for field in asn1Value:\n            if field in pyObject:\n                asn1Value[field] = decodeFun(pyObject[field], componentsTypes[field].asn1Object, **options)\n\n        return asn1Value\n\n\nclass SequenceOfOrSetOfDecoder(object):\n    def __call__(self, pyObject, asn1Spec, decodeFun=None, **options):\n        asn1Value = asn1Spec.clone()\n\n        for pyValue in pyObject:\n            asn1Value.append(decodeFun(pyValue, asn1Spec.componentType), **options)\n\n        return asn1Value\n\n\nclass ChoiceDecoder(object):\n    def __call__(self, pyObject, asn1Spec, decodeFun=None, **options):\n        asn1Value = asn1Spec.clone()\n\n        componentsTypes = asn1Spec.componentType\n\n        for field in pyObject:\n            if field in componentsTypes:\n                asn1Value[field] = decodeFun(pyObject[field], componentsTypes[field].asn1Object, **options)\n                break\n\n        return asn1Value\n\n\ntagMap = {\n    univ.Integer.tagSet: AbstractScalarDecoder(),\n    univ.Boolean.tagSet: AbstractScalarDecoder(),\n    univ.BitString.tagSet: BitStringDecoder(),\n    univ.OctetString.tagSet: AbstractScalarDecoder(),\n    univ.Null.tagSet: AbstractScalarDecoder(),\n    univ.ObjectIdentifier.tagSet: AbstractScalarDecoder(),\n    univ.Enumerated.tagSet: AbstractScalarDecoder(),\n    univ.Real.tagSet: AbstractScalarDecoder(),\n    univ.Sequence.tagSet: SequenceOrSetDecoder(),  # conflicts with SequenceOf\n    univ.Set.tagSet: SequenceOrSetDecoder(),  # conflicts with SetOf\n    univ.Choice.tagSet: ChoiceDecoder(),  # conflicts with Any\n    # character string types\n    char.UTF8String.tagSet: AbstractScalarDecoder(),\n    char.NumericString.tagSet: AbstractScalarDecoder(),\n    char.PrintableString.tagSet: AbstractScalarDecoder(),\n    char.TeletexString.tagSet: AbstractScalarDecoder(),\n    char.VideotexString.tagSet: AbstractScalarDecoder(),\n    char.IA5String.tagSet: AbstractScalarDecoder(),\n    char.GraphicString.tagSet: AbstractScalarDecoder(),\n    char.VisibleString.tagSet: AbstractScalarDecoder(),\n    char.GeneralString.tagSet: AbstractScalarDecoder(),\n    char.UniversalString.tagSet: AbstractScalarDecoder(),\n    char.BMPString.tagSet: AbstractScalarDecoder(),\n    # useful types\n    useful.ObjectDescriptor.tagSet: AbstractScalarDecoder(),\n    useful.GeneralizedTime.tagSet: AbstractScalarDecoder(),\n    useful.UTCTime.tagSet: AbstractScalarDecoder()\n}\n\n# Put in ambiguous & non-ambiguous types for faster codec lookup\ntypeMap = {\n    univ.Integer.typeId: AbstractScalarDecoder(),\n    univ.Boolean.typeId: AbstractScalarDecoder(),\n    univ.BitString.typeId: BitStringDecoder(),\n    univ.OctetString.typeId: AbstractScalarDecoder(),\n    univ.Null.typeId: AbstractScalarDecoder(),\n    univ.ObjectIdentifier.typeId: AbstractScalarDecoder(),\n    univ.Enumerated.typeId: AbstractScalarDecoder(),\n    univ.Real.typeId: AbstractScalarDecoder(),\n    # ambiguous base types\n    univ.Set.typeId: SequenceOrSetDecoder(),\n    univ.SetOf.typeId: SequenceOfOrSetOfDecoder(),\n    univ.Sequence.typeId: SequenceOrSetDecoder(),\n    univ.SequenceOf.typeId: SequenceOfOrSetOfDecoder(),\n    univ.Choice.typeId: ChoiceDecoder(),\n    univ.Any.typeId: AbstractScalarDecoder(),\n    # character string types\n    char.UTF8String.typeId: AbstractScalarDecoder(),\n    char.NumericString.typeId: AbstractScalarDecoder(),\n    char.PrintableString.typeId: AbstractScalarDecoder(),\n    char.TeletexString.typeId: AbstractScalarDecoder(),\n    char.VideotexString.typeId: AbstractScalarDecoder(),\n    char.IA5String.typeId: AbstractScalarDecoder(),\n    char.GraphicString.typeId: AbstractScalarDecoder(),\n    char.VisibleString.typeId: AbstractScalarDecoder(),\n    char.GeneralString.typeId: AbstractScalarDecoder(),\n    char.UniversalString.typeId: AbstractScalarDecoder(),\n    char.BMPString.typeId: AbstractScalarDecoder(),\n    # useful types\n    useful.ObjectDescriptor.typeId: AbstractScalarDecoder(),\n    useful.GeneralizedTime.typeId: AbstractScalarDecoder(),\n    useful.UTCTime.typeId: AbstractScalarDecoder()\n}\n\n\nclass Decoder(object):\n\n    # noinspection PyDefaultArgument\n    def __init__(self, tagMap, typeMap):\n        self.__tagMap = tagMap\n        self.__typeMap = typeMap\n\n    def __call__(self, pyObject, asn1Spec, **options):\n\n        if LOG:\n            debug.scope.push(type(pyObject).__name__)\n            LOG('decoder called at scope %s, working with type %s' % (debug.scope, type(pyObject).__name__))\n\n        if asn1Spec is None or not isinstance(asn1Spec, base.Asn1Item):\n            raise error.PyAsn1Error('asn1Spec is not valid (should be an instance of an ASN.1 Item, not %s)' % asn1Spec.__class__.__name__)\n\n        try:\n            valueDecoder = self.__typeMap[asn1Spec.typeId]\n\n        except KeyError:\n            # use base type for codec lookup to recover untagged types\n            baseTagSet = tag.TagSet(asn1Spec.tagSet.baseTag, asn1Spec.tagSet.baseTag)\n\n            try:\n                valueDecoder = self.__tagMap[baseTagSet]\n            except KeyError:\n                raise error.PyAsn1Error('Unknown ASN.1 tag %s' % asn1Spec.tagSet)\n\n        if LOG:\n            LOG('calling decoder %s on Python type %s <%s>' % (type(valueDecoder).__name__, type(pyObject).__name__, repr(pyObject)))\n\n        value = valueDecoder(pyObject, asn1Spec, self, **options)\n\n        if LOG:\n            LOG('decoder %s produced ASN.1 type %s <%s>' % (type(valueDecoder).__name__, type(value).__name__, repr(value)))\n            debug.scope.pop()\n\n        return value\n\n\n#: Turns Python objects of built-in types into ASN.1 objects.\n#:\n#: Takes Python objects of built-in types and turns them into a tree of\n#: ASN.1 objects (e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative) which\n#: may be a scalar or an arbitrary nested structure.\n#:\n#: Parameters\n#: ----------\n#: pyObject: :py:class:`object`\n#:     A scalar or nested Python objects\n#:\n#: Keyword Args\n#: ------------\n#: asn1Spec: any pyasn1 type object e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n#:     A pyasn1 type object to act as a template guiding the decoder. It is required\n#:     for successful interpretation of Python objects mapping into their ASN.1\n#:     representations.\n#:\n#: Returns\n#: -------\n#: : :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n#:     A scalar or constructed pyasn1 object\n#:\n#: Raises\n#: ------\n#: ~pyasn1.error.PyAsn1Error\n#:     On decoding errors\n#:\n#: Examples\n#: --------\n#: Decode native Python object into ASN.1 objects with ASN.1 schema\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> seq = SequenceOf(componentType=Integer())\n#:    >>> s, _ = decode([1, 2, 3], asn1Spec=seq)\n#:    >>> str(s)\n#:    SequenceOf:\n#:     1 2 3\n#:\ndecode = Decoder(tagMap, typeMap)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/codec/native/encoder.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\ntry:\n    from collections import OrderedDict\n\nexcept ImportError:\n    OrderedDict = dict\n\nfrom pyasn1 import debug\nfrom pyasn1 import error\nfrom pyasn1.type import base\nfrom pyasn1.type import char\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\n__all__ = ['encode']\n\nLOG = debug.registerLoggee(__name__, flags=debug.DEBUG_ENCODER)\n\n\nclass AbstractItemEncoder(object):\n    def encode(self, value, encodeFun, **options):\n        raise error.PyAsn1Error('Not implemented')\n\n\nclass BooleanEncoder(AbstractItemEncoder):\n    def encode(self, value, encodeFun, **options):\n        return bool(value)\n\n\nclass IntegerEncoder(AbstractItemEncoder):\n    def encode(self, value, encodeFun, **options):\n        return int(value)\n\n\nclass BitStringEncoder(AbstractItemEncoder):\n    def encode(self, value, encodeFun, **options):\n        return str(value)\n\n\nclass OctetStringEncoder(AbstractItemEncoder):\n    def encode(self, value, encodeFun, **options):\n        return value.asOctets()\n\n\nclass TextStringEncoder(AbstractItemEncoder):\n    def encode(self, value, encodeFun, **options):\n        return str(value)\n\n\nclass NullEncoder(AbstractItemEncoder):\n    def encode(self, value, encodeFun, **options):\n        return None\n\n\nclass ObjectIdentifierEncoder(AbstractItemEncoder):\n    def encode(self, value, encodeFun, **options):\n        return str(value)\n\n\nclass RealEncoder(AbstractItemEncoder):\n    def encode(self, value, encodeFun, **options):\n        return float(value)\n\n\nclass SetEncoder(AbstractItemEncoder):\n    protoDict = dict\n\n    def encode(self, value, encodeFun, **options):\n        inconsistency = value.isInconsistent\n        if inconsistency:\n            raise inconsistency\n\n        namedTypes = value.componentType\n        substrate = self.protoDict()\n\n        for idx, (key, subValue) in enumerate(value.items()):\n            if namedTypes and namedTypes[idx].isOptional and not value[idx].isValue:\n                continue\n            substrate[key] = encodeFun(subValue, **options)\n        return substrate\n\n\nclass SequenceEncoder(SetEncoder):\n    protoDict = OrderedDict\n\n\nclass SequenceOfEncoder(AbstractItemEncoder):\n    def encode(self, value, encodeFun, **options):\n        inconsistency = value.isInconsistent\n        if inconsistency:\n            raise inconsistency\n        return [encodeFun(x, **options) for x in value]\n\n\nclass ChoiceEncoder(SequenceEncoder):\n    pass\n\n\nclass AnyEncoder(AbstractItemEncoder):\n    def encode(self, value, encodeFun, **options):\n        return value.asOctets()\n\n\ntagMap = {\n    univ.Boolean.tagSet: BooleanEncoder(),\n    univ.Integer.tagSet: IntegerEncoder(),\n    univ.BitString.tagSet: BitStringEncoder(),\n    univ.OctetString.tagSet: OctetStringEncoder(),\n    univ.Null.tagSet: NullEncoder(),\n    univ.ObjectIdentifier.tagSet: ObjectIdentifierEncoder(),\n    univ.Enumerated.tagSet: IntegerEncoder(),\n    univ.Real.tagSet: RealEncoder(),\n    # Sequence & Set have same tags as SequenceOf & SetOf\n    univ.SequenceOf.tagSet: SequenceOfEncoder(),\n    univ.SetOf.tagSet: SequenceOfEncoder(),\n    univ.Choice.tagSet: ChoiceEncoder(),\n    # character string types\n    char.UTF8String.tagSet: TextStringEncoder(),\n    char.NumericString.tagSet: TextStringEncoder(),\n    char.PrintableString.tagSet: TextStringEncoder(),\n    char.TeletexString.tagSet: TextStringEncoder(),\n    char.VideotexString.tagSet: TextStringEncoder(),\n    char.IA5String.tagSet: TextStringEncoder(),\n    char.GraphicString.tagSet: TextStringEncoder(),\n    char.VisibleString.tagSet: TextStringEncoder(),\n    char.GeneralString.tagSet: TextStringEncoder(),\n    char.UniversalString.tagSet: TextStringEncoder(),\n    char.BMPString.tagSet: TextStringEncoder(),\n    # useful types\n    useful.ObjectDescriptor.tagSet: OctetStringEncoder(),\n    useful.GeneralizedTime.tagSet: OctetStringEncoder(),\n    useful.UTCTime.tagSet: OctetStringEncoder()\n}\n\n\n# Put in ambiguous & non-ambiguous types for faster codec lookup\ntypeMap = {\n    univ.Boolean.typeId: BooleanEncoder(),\n    univ.Integer.typeId: IntegerEncoder(),\n    univ.BitString.typeId: BitStringEncoder(),\n    univ.OctetString.typeId: OctetStringEncoder(),\n    univ.Null.typeId: NullEncoder(),\n    univ.ObjectIdentifier.typeId: ObjectIdentifierEncoder(),\n    univ.Enumerated.typeId: IntegerEncoder(),\n    univ.Real.typeId: RealEncoder(),\n    # Sequence & Set have same tags as SequenceOf & SetOf\n    univ.Set.typeId: SetEncoder(),\n    univ.SetOf.typeId: SequenceOfEncoder(),\n    univ.Sequence.typeId: SequenceEncoder(),\n    univ.SequenceOf.typeId: SequenceOfEncoder(),\n    univ.Choice.typeId: ChoiceEncoder(),\n    univ.Any.typeId: AnyEncoder(),\n    # character string types\n    char.UTF8String.typeId: OctetStringEncoder(),\n    char.NumericString.typeId: OctetStringEncoder(),\n    char.PrintableString.typeId: OctetStringEncoder(),\n    char.TeletexString.typeId: OctetStringEncoder(),\n    char.VideotexString.typeId: OctetStringEncoder(),\n    char.IA5String.typeId: OctetStringEncoder(),\n    char.GraphicString.typeId: OctetStringEncoder(),\n    char.VisibleString.typeId: OctetStringEncoder(),\n    char.GeneralString.typeId: OctetStringEncoder(),\n    char.UniversalString.typeId: OctetStringEncoder(),\n    char.BMPString.typeId: OctetStringEncoder(),\n    # useful types\n    useful.ObjectDescriptor.typeId: OctetStringEncoder(),\n    useful.GeneralizedTime.typeId: OctetStringEncoder(),\n    useful.UTCTime.typeId: OctetStringEncoder()\n}\n\n\nclass Encoder(object):\n\n    # noinspection PyDefaultArgument\n    def __init__(self, tagMap, typeMap={}):\n        self.__tagMap = tagMap\n        self.__typeMap = typeMap\n\n    def __call__(self, value, **options):\n        if not isinstance(value, base.Asn1Item):\n            raise error.PyAsn1Error('value is not valid (should be an instance of an ASN.1 Item)')\n\n        if LOG:\n            debug.scope.push(type(value).__name__)\n            LOG('encoder called for type %s <%s>' % (type(value).__name__, value.prettyPrint()))\n\n        tagSet = value.tagSet\n\n        try:\n            concreteEncoder = self.__typeMap[value.typeId]\n\n        except KeyError:\n            # use base type for codec lookup to recover untagged types\n            baseTagSet = tag.TagSet(value.tagSet.baseTag, value.tagSet.baseTag)\n\n            try:\n                concreteEncoder = self.__tagMap[baseTagSet]\n\n            except KeyError:\n                raise error.PyAsn1Error('No encoder for %s' % (value,))\n\n        if LOG:\n            LOG('using value codec %s chosen by %s' % (concreteEncoder.__class__.__name__, tagSet))\n\n        pyObject = concreteEncoder.encode(value, self, **options)\n\n        if LOG:\n            LOG('encoder %s produced: %s' % (type(concreteEncoder).__name__, repr(pyObject)))\n            debug.scope.pop()\n\n        return pyObject\n\n\n#: Turns ASN.1 object into a Python built-in type object(s).\n#:\n#: Takes any ASN.1 object (e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative)\n#: walks all its components recursively and produces a Python built-in type or a tree\n#: of those.\n#:\n#: One exception is that instead of :py:class:`dict`, the :py:class:`OrderedDict`\n#: can be produced (whenever available) to preserve ordering of the components\n#: in ASN.1 SEQUENCE.\n#:\n#: Parameters\n#: ----------\n#  asn1Value: any pyasn1 object (e.g. :py:class:`~pyasn1.type.base.PyAsn1Item` derivative)\n#:     pyasn1 object to encode (or a tree of them)\n#:\n#: Returns\n#: -------\n#: : :py:class:`object`\n#:     Python built-in type instance (or a tree of them)\n#:\n#: Raises\n#: ------\n#: ~pyasn1.error.PyAsn1Error\n#:     On encoding errors\n#:\n#: Examples\n#: --------\n#: Encode ASN.1 value object into native Python types\n#:\n#: .. code-block:: pycon\n#:\n#:    >>> seq = SequenceOf(componentType=Integer())\n#:    >>> seq.extend([1, 2, 3])\n#:    >>> encode(seq)\n#:    [1, 2, 3]\n#:\nencode = Encoder(tagMap, typeMap)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/compat/__init__.py",
    "content": "# This file is necessary to make this directory a package.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/compat/binary.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom sys import version_info\n\nif version_info[0:2] < (2, 6):\n    def bin(value):\n        bitstring = []\n\n        if value > 0:\n            prefix = '0b'\n        elif value < 0:\n            prefix = '-0b'\n            value = abs(value)\n        else:\n            prefix = '0b0'\n\n        while value:\n            if value & 1 == 1:\n                bitstring.append('1')\n            else:\n                bitstring.append('0')\n\n            value >>= 1\n\n        bitstring.reverse()\n\n        return prefix + ''.join(bitstring)\nelse:\n    bin = bin\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/compat/calling.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom sys import version_info\n\n__all__ = ['callable']\n\n\nif (2, 7) < version_info[:2] < (3, 2):\n    import collections\n\n    def callable(x):\n        return isinstance(x, collections.Callable)\n\nelse:\n\n    callable = callable\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/compat/dateandtime.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nimport time\nfrom datetime import datetime\nfrom sys import version_info\n\n__all__ = ['strptime']\n\n\nif version_info[:2] <= (2, 4):\n\n    def strptime(text, dateFormat):\n        return datetime(*(time.strptime(text, dateFormat)[0:6]))\n\nelse:\n\n    def strptime(text, dateFormat):\n        return datetime.strptime(text, dateFormat)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/compat/integer.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nimport sys\n\ntry:\n    import platform\n\n    implementation = platform.python_implementation()\n\nexcept (ImportError, AttributeError):\n    implementation = 'CPython'\n\nfrom pyasn1.compat.octets import oct2int, null, ensureString\n\nif sys.version_info[0:2] < (3, 2) or implementation != 'CPython':\n    from binascii import a2b_hex, b2a_hex\n\n    if sys.version_info[0] > 2:\n        long = int\n\n    def from_bytes(octets, signed=False):\n        if not octets:\n            return 0\n\n        value = long(b2a_hex(ensureString(octets)), 16)\n\n        if signed and oct2int(octets[0]) & 0x80:\n            return value - (1 << len(octets) * 8)\n\n        return value\n\n    def to_bytes(value, signed=False, length=0):\n        if value < 0:\n            if signed:\n                bits = bitLength(value)\n\n                # two's complement form\n                maxValue = 1 << bits\n                valueToEncode = (value + maxValue) % maxValue\n\n            else:\n                raise OverflowError('can\\'t convert negative int to unsigned')\n        elif value == 0 and length == 0:\n            return null\n        else:\n            bits = 0\n            valueToEncode = value\n\n        hexValue = hex(valueToEncode)[2:]\n        if hexValue.endswith('L'):\n            hexValue = hexValue[:-1]\n\n        if len(hexValue) & 1:\n            hexValue = '0' + hexValue\n\n        # padding may be needed for two's complement encoding\n        if value != valueToEncode or length:\n            hexLength = len(hexValue) * 4\n\n            padLength = max(length, bits)\n\n            if padLength > hexLength:\n                hexValue = '00' * ((padLength - hexLength - 1) // 8 + 1) + hexValue\n            elif length and hexLength - length > 7:\n                raise OverflowError('int too big to convert')\n\n        firstOctet = int(hexValue[:2], 16)\n\n        if signed:\n            if firstOctet & 0x80:\n                if value >= 0:\n                    hexValue = '00' + hexValue\n            elif value < 0:\n                hexValue = 'ff' + hexValue\n\n        octets_value = a2b_hex(hexValue)\n\n        return octets_value\n\n    def bitLength(number):\n        # bits in unsigned number\n        hexValue = hex(abs(number))\n        bits = len(hexValue) - 2\n        if hexValue.endswith('L'):\n            bits -= 1\n        if bits & 1:\n            bits += 1\n        bits *= 4\n        # TODO: strip lhs zeros\n        return bits\n\nelse:\n\n    def from_bytes(octets, signed=False):\n        return int.from_bytes(bytes(octets), 'big', signed=signed)\n\n    def to_bytes(value, signed=False, length=0):\n        length = max(value.bit_length(), length)\n\n        if signed and length % 8 == 0:\n            length += 1\n\n        return value.to_bytes(length // 8 + (length % 8 and 1 or 0), 'big', signed=signed)\n\n    def bitLength(number):\n        return int(number).bit_length()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/compat/octets.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom sys import version_info\n\nif version_info[0] <= 2:\n    int2oct = chr\n    # noinspection PyPep8\n    ints2octs = lambda s: ''.join([int2oct(x) for x in s])\n    null = ''\n    oct2int = ord\n    # TODO: refactor to return a sequence of ints\n    # noinspection PyPep8\n    octs2ints = lambda s: [oct2int(x) for x in s]\n    # noinspection PyPep8\n    str2octs = lambda x: x\n    # noinspection PyPep8\n    octs2str = lambda x: x\n    # noinspection PyPep8\n    isOctetsType = lambda s: isinstance(s, str)\n    # noinspection PyPep8\n    isStringType = lambda s: isinstance(s, (str, unicode))\n    # noinspection PyPep8\n    ensureString = str\nelse:\n    ints2octs = bytes\n    # noinspection PyPep8\n    int2oct = lambda x: ints2octs((x,))\n    null = ints2octs()\n    # noinspection PyPep8\n    oct2int = lambda x: x\n    # noinspection PyPep8\n    octs2ints = lambda x: x\n    # noinspection PyPep8\n    str2octs = lambda x: x.encode('iso-8859-1')\n    # noinspection PyPep8\n    octs2str = lambda x: x.decode('iso-8859-1')\n    # noinspection PyPep8\n    isOctetsType = lambda s: isinstance(s, bytes)\n    # noinspection PyPep8\n    isStringType = lambda s: isinstance(s, str)\n    # noinspection PyPep8\n    ensureString = bytes\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/compat/string.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom sys import version_info\n\nif version_info[:2] <= (2, 5):\n\n    def partition(string, sep):\n        try:\n            a, c = string.split(sep, 1)\n\n        except ValueError:\n            a, b, c = string, '', ''\n\n        else:\n            b = sep\n\n        return a, b, c\n\nelse:\n\n    def partition(string, sep):\n        return string.partition(sep)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/debug.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nimport logging\nimport sys\n\nfrom pyasn1 import __version__\nfrom pyasn1 import error\nfrom pyasn1.compat.octets import octs2ints\n\n__all__ = ['Debug', 'setLogger', 'hexdump']\n\nDEBUG_NONE = 0x0000\nDEBUG_ENCODER = 0x0001\nDEBUG_DECODER = 0x0002\nDEBUG_ALL = 0xffff\n\nFLAG_MAP = {\n    'none': DEBUG_NONE,\n    'encoder': DEBUG_ENCODER,\n    'decoder': DEBUG_DECODER,\n    'all': DEBUG_ALL\n}\n\nLOGGEE_MAP = {}\n\n\nclass Printer(object):\n    # noinspection PyShadowingNames\n    def __init__(self, logger=None, handler=None, formatter=None):\n        if logger is None:\n            logger = logging.getLogger('pyasn1')\n\n        logger.setLevel(logging.DEBUG)\n\n        if handler is None:\n            handler = logging.StreamHandler()\n\n        if formatter is None:\n            formatter = logging.Formatter('%(asctime)s %(name)s: %(message)s')\n\n        handler.setFormatter(formatter)\n        handler.setLevel(logging.DEBUG)\n        logger.addHandler(handler)\n\n        self.__logger = logger\n\n    def __call__(self, msg):\n        self.__logger.debug(msg)\n\n    def __str__(self):\n        return '<python logging>'\n\n\nif hasattr(logging, 'NullHandler'):\n    NullHandler = logging.NullHandler\n\nelse:\n    # Python 2.6 and older\n    class NullHandler(logging.Handler):\n        def emit(self, record):\n            pass\n\n\nclass Debug(object):\n    defaultPrinter = Printer()\n\n    def __init__(self, *flags, **options):\n        self._flags = DEBUG_NONE\n\n        if 'loggerName' in options:\n            # route our logs to parent logger\n            self._printer = Printer(\n                logger=logging.getLogger(options['loggerName']),\n                handler=NullHandler()\n            )\n\n        elif 'printer' in options:\n            self._printer = options.get('printer')\n\n        else:\n            self._printer = self.defaultPrinter\n\n        self._printer('running pyasn1 %s, debug flags %s' % (__version__, ', '.join(flags)))\n\n        for flag in flags:\n            inverse = flag and flag[0] in ('!', '~')\n            if inverse:\n                flag = flag[1:]\n            try:\n                if inverse:\n                    self._flags &= ~FLAG_MAP[flag]\n                else:\n                    self._flags |= FLAG_MAP[flag]\n            except KeyError:\n                raise error.PyAsn1Error('bad debug flag %s' % flag)\n\n            self._printer(\"debug category '%s' %s\" % (flag, inverse and 'disabled' or 'enabled'))\n\n    def __str__(self):\n        return 'logger %s, flags %x' % (self._printer, self._flags)\n\n    def __call__(self, msg):\n        self._printer(msg)\n\n    def __and__(self, flag):\n        return self._flags & flag\n\n    def __rand__(self, flag):\n        return flag & self._flags\n\n_LOG = DEBUG_NONE\n\n\ndef setLogger(userLogger):\n    global _LOG\n\n    if userLogger:\n        _LOG = userLogger\n    else:\n        _LOG = DEBUG_NONE\n\n    # Update registered logging clients\n    for module, (name, flags) in LOGGEE_MAP.items():\n        setattr(module, name, _LOG & flags and _LOG or DEBUG_NONE)\n\n\ndef registerLoggee(module, name='LOG', flags=DEBUG_NONE):\n    LOGGEE_MAP[sys.modules[module]] = name, flags\n    setLogger(_LOG)\n    return _LOG\n\n\ndef hexdump(octets):\n    return ' '.join(\n        ['%s%.2X' % (n % 16 == 0 and ('\\n%.5d: ' % n) or '', x)\n         for n, x in zip(range(len(octets)), octs2ints(octets))]\n    )\n\n\nclass Scope(object):\n    def __init__(self):\n        self._list = []\n\n    def __str__(self): return '.'.join(self._list)\n\n    def push(self, token):\n        self._list.append(token)\n\n    def pop(self):\n        return self._list.pop()\n\n\nscope = Scope()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/error.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n\n\nclass PyAsn1Error(Exception):\n    \"\"\"Base pyasn1 exception\n\n    `PyAsn1Error` is the base exception class (based on\n    :class:`Exception`) that represents all possible ASN.1 related\n    errors.\n    \"\"\"\n\n\nclass ValueConstraintError(PyAsn1Error):\n    \"\"\"ASN.1 type constraints violation exception\n\n    The `ValueConstraintError` exception indicates an ASN.1 value\n    constraint violation.\n\n    It might happen on value object instantiation (for scalar types) or on\n    serialization (for constructed types).\n    \"\"\"\n\n\nclass SubstrateUnderrunError(PyAsn1Error):\n    \"\"\"ASN.1 data structure deserialization error\n\n    The `SubstrateUnderrunError` exception indicates insufficient serialised\n    data on input of a de-serialization codec.\n    \"\"\"\n\n\nclass PyAsn1UnicodeError(PyAsn1Error, UnicodeError):\n    \"\"\"Unicode text processing error\n\n    The `PyAsn1UnicodeError` exception is a base class for errors relating to\n    unicode text de/serialization.\n\n    Apart from inheriting from :class:`PyAsn1Error`, it also inherits from\n    :class:`UnicodeError` to help the caller catching unicode-related errors.\n    \"\"\"\n    def __init__(self, message, unicode_error=None):\n        if isinstance(unicode_error, UnicodeError):\n            UnicodeError.__init__(self, *unicode_error.args)\n        PyAsn1Error.__init__(self, message)\n\n\nclass PyAsn1UnicodeDecodeError(PyAsn1UnicodeError, UnicodeDecodeError):\n    \"\"\"Unicode text decoding error\n\n    The `PyAsn1UnicodeDecodeError` exception represents a failure to\n    deserialize unicode text.\n\n    Apart from inheriting from :class:`PyAsn1UnicodeError`, it also inherits\n    from :class:`UnicodeDecodeError` to help the caller catching unicode-related\n    errors.\n    \"\"\"\n\n\nclass PyAsn1UnicodeEncodeError(PyAsn1UnicodeError, UnicodeEncodeError):\n    \"\"\"Unicode text encoding error\n\n    The `PyAsn1UnicodeEncodeError` exception represents a failure to\n    serialize unicode text.\n\n    Apart from inheriting from :class:`PyAsn1UnicodeError`, it also inherits\n    from :class:`UnicodeEncodeError` to help the caller catching\n    unicode-related errors.\n    \"\"\"\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/type/__init__.py",
    "content": "# This file is necessary to make this directory a package.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/type/base.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nimport sys\n\nfrom pyasn1 import error\nfrom pyasn1.compat import calling\nfrom pyasn1.type import constraint\nfrom pyasn1.type import tag\nfrom pyasn1.type import tagmap\n\n__all__ = ['Asn1Item', 'Asn1Type', 'SimpleAsn1Type',\n           'ConstructedAsn1Type']\n\n\nclass Asn1Item(object):\n    @classmethod\n    def getTypeId(cls, increment=1):\n        try:\n            Asn1Item._typeCounter += increment\n        except AttributeError:\n            Asn1Item._typeCounter = increment\n        return Asn1Item._typeCounter\n\n\nclass Asn1Type(Asn1Item):\n    \"\"\"Base class for all classes representing ASN.1 types.\n\n    In the user code, |ASN.1| class is normally used only for telling\n    ASN.1 objects from others.\n\n    Note\n    ----\n    For as long as ASN.1 is concerned, a way to compare ASN.1 types\n    is to use :meth:`isSameTypeWith` and :meth:`isSuperTypeOf` methods.\n    \"\"\"\n    #: Set or return a :py:class:`~pyasn1.type.tag.TagSet` object representing\n    #: ASN.1 tag(s) associated with |ASN.1| type.\n    tagSet = tag.TagSet()\n\n    #: Default :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n    #: object imposing constraints on initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection()\n\n    # Disambiguation ASN.1 types identification\n    typeId = None\n\n    def __init__(self, **kwargs):\n        readOnly = {\n            'tagSet': self.tagSet,\n            'subtypeSpec': self.subtypeSpec\n        }\n\n        readOnly.update(kwargs)\n\n        self.__dict__.update(readOnly)\n\n        self._readOnly = readOnly\n\n    def __setattr__(self, name, value):\n        if name[0] != '_' and name in self._readOnly:\n            raise error.PyAsn1Error('read-only instance attribute \"%s\"' % name)\n\n        self.__dict__[name] = value\n\n    def __str__(self):\n        return self.prettyPrint()\n\n    @property\n    def readOnly(self):\n        return self._readOnly\n\n    @property\n    def effectiveTagSet(self):\n        \"\"\"For |ASN.1| type is equivalent to *tagSet*\n        \"\"\"\n        return self.tagSet  # used by untagged types\n\n    @property\n    def tagMap(self):\n        \"\"\"Return a :class:`~pyasn1.type.tagmap.TagMap` object mapping ASN.1 tags to ASN.1 objects within callee object.\n        \"\"\"\n        return tagmap.TagMap({self.tagSet: self})\n\n    def isSameTypeWith(self, other, matchTags=True, matchConstraints=True):\n        \"\"\"Examine |ASN.1| type for equality with other ASN.1 type.\n\n        ASN.1 tags (:py:mod:`~pyasn1.type.tag`) and constraints\n        (:py:mod:`~pyasn1.type.constraint`) are examined when carrying\n        out ASN.1 types comparison.\n\n        Python class inheritance relationship is NOT considered.\n\n        Parameters\n        ----------\n        other: a pyasn1 type object\n            Class instance representing ASN.1 type.\n\n        Returns\n        -------\n        : :class:`bool`\n            :obj:`True` if *other* is |ASN.1| type,\n            :obj:`False` otherwise.\n        \"\"\"\n        return (self is other or\n                (not matchTags or self.tagSet == other.tagSet) and\n                (not matchConstraints or self.subtypeSpec == other.subtypeSpec))\n\n    def isSuperTypeOf(self, other, matchTags=True, matchConstraints=True):\n        \"\"\"Examine |ASN.1| type for subtype relationship with other ASN.1 type.\n\n        ASN.1 tags (:py:mod:`~pyasn1.type.tag`) and constraints\n        (:py:mod:`~pyasn1.type.constraint`) are examined when carrying\n        out ASN.1 types comparison.\n\n        Python class inheritance relationship is NOT considered.\n\n        Parameters\n        ----------\n            other: a pyasn1 type object\n                Class instance representing ASN.1 type.\n\n        Returns\n        -------\n            : :class:`bool`\n                :obj:`True` if *other* is a subtype of |ASN.1| type,\n                :obj:`False` otherwise.\n        \"\"\"\n        return (not matchTags or\n                (self.tagSet.isSuperTagSetOf(other.tagSet)) and\n                 (not matchConstraints or self.subtypeSpec.isSuperTypeOf(other.subtypeSpec)))\n\n    @staticmethod\n    def isNoValue(*values):\n        for value in values:\n            if value is not noValue:\n                return False\n        return True\n\n    def prettyPrint(self, scope=0):\n        raise NotImplementedError()\n\n    # backward compatibility\n\n    def getTagSet(self):\n        return self.tagSet\n\n    def getEffectiveTagSet(self):\n        return self.effectiveTagSet\n\n    def getTagMap(self):\n        return self.tagMap\n\n    def getSubtypeSpec(self):\n        return self.subtypeSpec\n\n    # backward compatibility\n    def hasValue(self):\n        return self.isValue\n\n# Backward compatibility\nAsn1ItemBase = Asn1Type\n\n\nclass NoValue(object):\n    \"\"\"Create a singleton instance of NoValue class.\n\n    The *NoValue* sentinel object represents an instance of ASN.1 schema\n    object as opposed to ASN.1 value object.\n\n    Only ASN.1 schema-related operations can be performed on ASN.1\n    schema objects.\n\n    Warning\n    -------\n    Any operation attempted on the *noValue* object will raise the\n    *PyAsn1Error* exception.\n    \"\"\"\n    skipMethods = set(\n        ('__slots__',\n         # attributes\n         '__getattribute__',\n         '__getattr__',\n         '__setattr__',\n         '__delattr__',\n         # class instance\n         '__class__',\n         '__init__',\n         '__del__',\n         '__new__',\n         '__repr__',\n         '__qualname__',\n         '__objclass__',\n         'im_class',\n         '__sizeof__',\n         # pickle protocol\n         '__reduce__',\n         '__reduce_ex__',\n         '__getnewargs__',\n         '__getinitargs__',\n         '__getstate__',\n         '__setstate__')\n    )\n\n    _instance = None\n\n    def __new__(cls):\n        if cls._instance is None:\n            def getPlug(name):\n                def plug(self, *args, **kw):\n                    raise error.PyAsn1Error('Attempted \"%s\" operation on ASN.1 schema object' % name)\n                return plug\n\n            op_names = [name\n                        for typ in (str, int, list, dict)\n                        for name in dir(typ)\n                        if (name not in cls.skipMethods and\n                            name.startswith('__') and\n                            name.endswith('__') and\n                            calling.callable(getattr(typ, name)))]\n\n            for name in set(op_names):\n                setattr(cls, name, getPlug(name))\n\n            cls._instance = object.__new__(cls)\n\n        return cls._instance\n\n    def __getattr__(self, attr):\n        if attr in self.skipMethods:\n            raise AttributeError('Attribute %s not present' % attr)\n\n        raise error.PyAsn1Error('Attempted \"%s\" operation on ASN.1 schema object' % attr)\n\n    def __repr__(self):\n        return '<%s object>' % self.__class__.__name__\n\n\nnoValue = NoValue()\n\n\nclass SimpleAsn1Type(Asn1Type):\n    \"\"\"Base class for all simple classes representing ASN.1 types.\n\n    ASN.1 distinguishes types by their ability to hold other objects.\n    Scalar types are known as *simple* in ASN.1.\n\n    In the user code, |ASN.1| class is normally used only for telling\n    ASN.1 objects from others.\n\n    Note\n    ----\n    For as long as ASN.1 is concerned, a way to compare ASN.1 types\n    is to use :meth:`isSameTypeWith` and :meth:`isSuperTypeOf` methods.\n    \"\"\"\n    #: Default payload value\n    defaultValue = noValue\n\n    def __init__(self, value=noValue, **kwargs):\n        Asn1Type.__init__(self, **kwargs)\n        if value is noValue:\n            value = self.defaultValue\n        else:\n            value = self.prettyIn(value)\n            try:\n                self.subtypeSpec(value)\n\n            except error.PyAsn1Error:\n                exType, exValue, exTb = sys.exc_info()\n                raise exType('%s at %s' % (exValue, self.__class__.__name__))\n\n        self._value = value\n\n    def __repr__(self):\n        representation = '%s %s object' % (\n            self.__class__.__name__, self.isValue and 'value' or 'schema')\n\n        for attr, value in self.readOnly.items():\n            if value:\n                representation += ', %s %s' % (attr, value)\n\n        if self.isValue:\n            value = self.prettyPrint()\n            if len(value) > 32:\n                value = value[:16] + '...' + value[-16:]\n            representation += ', payload [%s]' % value\n\n        return '<%s>' % representation\n\n    def __eq__(self, other):\n        return self is other and True or self._value == other\n\n    def __ne__(self, other):\n        return self._value != other\n\n    def __lt__(self, other):\n        return self._value < other\n\n    def __le__(self, other):\n        return self._value <= other\n\n    def __gt__(self, other):\n        return self._value > other\n\n    def __ge__(self, other):\n        return self._value >= other\n\n    if sys.version_info[0] <= 2:\n        def __nonzero__(self):\n            return self._value and True or False\n    else:\n        def __bool__(self):\n            return self._value and True or False\n\n    def __hash__(self):\n        return hash(self._value)\n\n    @property\n    def isValue(self):\n        \"\"\"Indicate that |ASN.1| object represents ASN.1 value.\n\n        If *isValue* is :obj:`False` then this object represents just\n        ASN.1 schema.\n\n        If *isValue* is :obj:`True` then, in addition to its ASN.1 schema\n        features, this object can also be used like a Python built-in object\n        (e.g. :class:`int`, :class:`str`, :class:`dict` etc.).\n\n        Returns\n        -------\n        : :class:`bool`\n            :obj:`False` if object represents just ASN.1 schema.\n            :obj:`True` if object represents ASN.1 schema and can be used as a normal value.\n\n        Note\n        ----\n        There is an important distinction between PyASN1 schema and value objects.\n        The PyASN1 schema objects can only participate in ASN.1 schema-related\n        operations (e.g. defining or testing the structure of the data). Most\n        obvious uses of ASN.1 schema is to guide serialisation codecs whilst\n        encoding/decoding serialised ASN.1 contents.\n\n        The PyASN1 value objects can **additionally** participate in many operations\n        involving regular Python objects (e.g. arithmetic, comprehension etc).\n        \"\"\"\n        return self._value is not noValue\n\n    def clone(self, value=noValue, **kwargs):\n        \"\"\"Create a modified version of |ASN.1| schema or value object.\n\n        The `clone()` method accepts the same set arguments as |ASN.1|\n        class takes on instantiation except that all arguments\n        of the `clone()` method are optional.\n\n        Whatever arguments are supplied, they are used to create a copy\n        of `self` taking precedence over the ones used to instantiate `self`.\n\n        Note\n        ----\n        Due to the immutable nature of the |ASN.1| object, if no arguments\n        are supplied, no new |ASN.1| object will be created and `self` will\n        be returned instead.\n        \"\"\"\n        if value is noValue:\n            if not kwargs:\n                return self\n\n            value = self._value\n\n        initializers = self.readOnly.copy()\n        initializers.update(kwargs)\n\n        return self.__class__(value, **initializers)\n\n    def subtype(self, value=noValue, **kwargs):\n        \"\"\"Create a specialization of |ASN.1| schema or value object.\n\n        The subtype relationship between ASN.1 types has no correlation with\n        subtype relationship between Python types. ASN.1 type is mainly identified\n        by its tag(s) (:py:class:`~pyasn1.type.tag.TagSet`) and value range\n        constraints (:py:class:`~pyasn1.type.constraint.ConstraintsIntersection`).\n        These ASN.1 type properties are implemented as |ASN.1| attributes.  \n\n        The `subtype()` method accepts the same set arguments as |ASN.1|\n        class takes on instantiation except that all parameters\n        of the `subtype()` method are optional.\n\n        With the exception of the arguments described below, the rest of\n        supplied arguments they are used to create a copy of `self` taking\n        precedence over the ones used to instantiate `self`.\n\n        The following arguments to `subtype()` create a ASN.1 subtype out of\n        |ASN.1| type:\n\n        Other Parameters\n        ----------------\n        implicitTag: :py:class:`~pyasn1.type.tag.Tag`\n            Implicitly apply given ASN.1 tag object to `self`'s\n            :py:class:`~pyasn1.type.tag.TagSet`, then use the result as\n            new object's ASN.1 tag(s).\n\n        explicitTag: :py:class:`~pyasn1.type.tag.Tag`\n            Explicitly apply given ASN.1 tag object to `self`'s\n            :py:class:`~pyasn1.type.tag.TagSet`, then use the result as\n            new object's ASN.1 tag(s).\n\n        subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n            Add ASN.1 constraints object to one of the `self`'s, then\n            use the result as new object's ASN.1 constraints.\n\n        Returns\n        -------\n        :\n            new instance of |ASN.1| schema or value object\n\n        Note\n        ----\n        Due to the immutable nature of the |ASN.1| object, if no arguments\n        are supplied, no new |ASN.1| object will be created and `self` will\n        be returned instead.\n        \"\"\"\n        if value is noValue:\n            if not kwargs:\n                return self\n\n            value = self._value\n\n        initializers = self.readOnly.copy()\n\n        implicitTag = kwargs.pop('implicitTag', None)\n        if implicitTag is not None:\n            initializers['tagSet'] = self.tagSet.tagImplicitly(implicitTag)\n\n        explicitTag = kwargs.pop('explicitTag', None)\n        if explicitTag is not None:\n            initializers['tagSet'] = self.tagSet.tagExplicitly(explicitTag)\n\n        for arg, option in kwargs.items():\n            initializers[arg] += option\n\n        return self.__class__(value, **initializers)\n\n    def prettyIn(self, value):\n        return value\n\n    def prettyOut(self, value):\n        return str(value)\n\n    def prettyPrint(self, scope=0):\n        return self.prettyOut(self._value)\n\n    def prettyPrintType(self, scope=0):\n        return '%s -> %s' % (self.tagSet, self.__class__.__name__)\n\n# Backward compatibility\nAbstractSimpleAsn1Item = SimpleAsn1Type\n\n#\n# Constructed types:\n# * There are five of them: Sequence, SequenceOf/SetOf, Set and Choice\n# * ASN1 types and values are represened by Python class instances\n# * Value initialization is made for defaulted components only\n# * Primary method of component addressing is by-position. Data model for base\n#   type is Python sequence. Additional type-specific addressing methods\n#   may be implemented for particular types.\n# * SequenceOf and SetOf types do not implement any additional methods\n# * Sequence, Set and Choice types also implement by-identifier addressing\n# * Sequence, Set and Choice types also implement by-asn1-type (tag) addressing\n# * Sequence and Set types may include optional and defaulted\n#   components\n# * Constructed types hold a reference to component types used for value\n#   verification and ordering.\n# * Component type is a scalar type for SequenceOf/SetOf types and a list\n#   of types for Sequence/Set/Choice.\n#\n\n\nclass ConstructedAsn1Type(Asn1Type):\n    \"\"\"Base class for all constructed classes representing ASN.1 types.\n\n    ASN.1 distinguishes types by their ability to hold other objects.\n    Those \"nesting\" types are known as *constructed* in ASN.1.\n\n    In the user code, |ASN.1| class is normally used only for telling\n    ASN.1 objects from others.\n\n    Note\n    ----\n    For as long as ASN.1 is concerned, a way to compare ASN.1 types\n    is to use :meth:`isSameTypeWith` and :meth:`isSuperTypeOf` methods.\n    \"\"\"\n\n    #: If :obj:`True`, requires exact component type matching,\n    #: otherwise subtype relation is only enforced\n    strictConstraints = False\n\n    componentType = None\n\n    # backward compatibility, unused\n    sizeSpec = constraint.ConstraintsIntersection()\n\n    def __init__(self, **kwargs):\n        readOnly = {\n            'componentType': self.componentType,\n            # backward compatibility, unused\n            'sizeSpec': self.sizeSpec\n        }\n\n        # backward compatibility: preserve legacy sizeSpec support\n        kwargs = self._moveSizeSpec(**kwargs)\n\n        readOnly.update(kwargs)\n\n        Asn1Type.__init__(self, **readOnly)\n\n    def _moveSizeSpec(self, **kwargs):\n        # backward compatibility, unused\n        sizeSpec = kwargs.pop('sizeSpec', self.sizeSpec)\n        if sizeSpec:\n            subtypeSpec = kwargs.pop('subtypeSpec', self.subtypeSpec)\n            if subtypeSpec:\n                subtypeSpec = sizeSpec\n\n            else:\n                subtypeSpec += sizeSpec\n\n            kwargs['subtypeSpec'] = subtypeSpec\n\n        return kwargs\n\n    def __repr__(self):\n        representation = '%s %s object' % (\n            self.__class__.__name__, self.isValue and 'value' or 'schema'\n        )\n\n        for attr, value in self.readOnly.items():\n            if value is not noValue:\n                representation += ', %s=%r' % (attr, value)\n\n        if self.isValue and self.components:\n            representation += ', payload [%s]' % ', '.join(\n                [repr(x) for x in self.components])\n\n        return '<%s>' % representation\n\n    def __eq__(self, other):\n        return self is other or self.components == other\n\n    def __ne__(self, other):\n        return self.components != other\n\n    def __lt__(self, other):\n        return self.components < other\n\n    def __le__(self, other):\n        return self.components <= other\n\n    def __gt__(self, other):\n        return self.components > other\n\n    def __ge__(self, other):\n        return self.components >= other\n\n    if sys.version_info[0] <= 2:\n        def __nonzero__(self):\n            return bool(self.components)\n    else:\n        def __bool__(self):\n            return bool(self.components)\n\n    @property\n    def components(self):\n        raise error.PyAsn1Error('Method not implemented')\n\n    def _cloneComponentValues(self, myClone, cloneValueFlag):\n        pass\n\n    def clone(self, **kwargs):\n        \"\"\"Create a modified version of |ASN.1| schema object.\n\n        The `clone()` method accepts the same set arguments as |ASN.1|\n        class takes on instantiation except that all arguments\n        of the `clone()` method are optional.\n\n        Whatever arguments are supplied, they are used to create a copy\n        of `self` taking precedence over the ones used to instantiate `self`.\n\n        Possible values of `self` are never copied over thus `clone()` can\n        only create a new schema object.\n\n        Returns\n        -------\n        :\n            new instance of |ASN.1| type/value\n\n        Note\n        ----\n        Due to the mutable nature of the |ASN.1| object, even if no arguments\n        are supplied, a new |ASN.1| object will be created and returned.\n        \"\"\"\n        cloneValueFlag = kwargs.pop('cloneValueFlag', False)\n\n        initializers = self.readOnly.copy()\n        initializers.update(kwargs)\n\n        clone = self.__class__(**initializers)\n\n        if cloneValueFlag:\n            self._cloneComponentValues(clone, cloneValueFlag)\n\n        return clone\n\n    def subtype(self, **kwargs):\n        \"\"\"Create a specialization of |ASN.1| schema object.\n\n        The `subtype()` method accepts the same set arguments as |ASN.1|\n        class takes on instantiation except that all parameters\n        of the `subtype()` method are optional.\n\n        With the exception of the arguments described below, the rest of\n        supplied arguments they are used to create a copy of `self` taking\n        precedence over the ones used to instantiate `self`.\n\n        The following arguments to `subtype()` create a ASN.1 subtype out of\n        |ASN.1| type.\n\n        Other Parameters\n        ----------------\n        implicitTag: :py:class:`~pyasn1.type.tag.Tag`\n            Implicitly apply given ASN.1 tag object to `self`'s\n            :py:class:`~pyasn1.type.tag.TagSet`, then use the result as\n            new object's ASN.1 tag(s).\n\n        explicitTag: :py:class:`~pyasn1.type.tag.Tag`\n            Explicitly apply given ASN.1 tag object to `self`'s\n            :py:class:`~pyasn1.type.tag.TagSet`, then use the result as\n            new object's ASN.1 tag(s).\n\n        subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n            Add ASN.1 constraints object to one of the `self`'s, then\n            use the result as new object's ASN.1 constraints.\n\n\n        Returns\n        -------\n        :\n            new instance of |ASN.1| type/value\n\n        Note\n        ----\n        Due to the mutable nature of the |ASN.1| object, even if no arguments\n        are supplied, a new |ASN.1| object will be created and returned.\n        \"\"\"\n\n        initializers = self.readOnly.copy()\n\n        cloneValueFlag = kwargs.pop('cloneValueFlag', False)\n\n        implicitTag = kwargs.pop('implicitTag', None)\n        if implicitTag is not None:\n            initializers['tagSet'] = self.tagSet.tagImplicitly(implicitTag)\n\n        explicitTag = kwargs.pop('explicitTag', None)\n        if explicitTag is not None:\n            initializers['tagSet'] = self.tagSet.tagExplicitly(explicitTag)\n\n        for arg, option in kwargs.items():\n            initializers[arg] += option\n\n        clone = self.__class__(**initializers)\n\n        if cloneValueFlag:\n            self._cloneComponentValues(clone, cloneValueFlag)\n\n        return clone\n\n    def getComponentByPosition(self, idx):\n        raise error.PyAsn1Error('Method not implemented')\n\n    def setComponentByPosition(self, idx, value, verifyConstraints=True):\n        raise error.PyAsn1Error('Method not implemented')\n\n    def setComponents(self, *args, **kwargs):\n        for idx, value in enumerate(args):\n            self[idx] = value\n        for k in kwargs:\n            self[k] = kwargs[k]\n        return self\n\n    # backward compatibility\n\n    def setDefaultComponents(self):\n        pass\n\n    def getComponentType(self):\n        return self.componentType\n\n    # backward compatibility, unused\n    def verifySizeSpec(self):\n        self.subtypeSpec(self)\n\n\n        # Backward compatibility\nAbstractConstructedAsn1Item = ConstructedAsn1Type\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/type/char.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nimport sys\n\nfrom pyasn1 import error\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\n__all__ = ['NumericString', 'PrintableString', 'TeletexString', 'T61String', 'VideotexString',\n           'IA5String', 'GraphicString', 'VisibleString', 'ISO646String',\n           'GeneralString', 'UniversalString', 'BMPString', 'UTF8String']\n\nNoValue = univ.NoValue\nnoValue = univ.noValue\n\n\nclass AbstractCharacterString(univ.OctetString):\n    \"\"\"Creates |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.SimpleAsn1Type`,\n    its objects are immutable and duck-type Python 2 :class:`str` or Python 3\n    :class:`bytes`. When used in octet-stream context, |ASN.1| type assumes\n    \"|encoding|\" encoding.\n\n    Keyword Args\n    ------------\n    value: :class:`unicode`, :class:`str`, :class:`bytes` or |ASN.1| object\n        :class:`unicode` object (Python 2) or :class:`str` (Python 3),\n        alternatively :class:`str` (Python 2) or :class:`bytes` (Python 3)\n        representing octet-stream of serialised unicode string\n        (note `encoding` parameter) or |ASN.1| class instance.\n        If `value` is not given, schema object will be created.\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n        Object representing non-default ASN.1 subtype constraint(s). Constraints\n        verification for |ASN.1| type occurs automatically on object\n        instantiation.\n\n    encoding: :py:class:`str`\n        Unicode codec ID to encode/decode :class:`unicode` (Python 2) or\n        :class:`str` (Python 3) the payload when |ASN.1| object is used\n        in octet-stream context.\n\n    Raises\n    ------\n    ~pyasn1.error.ValueConstraintError, ~pyasn1.error.PyAsn1Error\n        On constraint violation or bad initializer.\n    \"\"\"\n\n    if sys.version_info[0] <= 2:\n        def __str__(self):\n            try:\n                # `str` is Py2 text representation\n                return self._value.encode(self.encoding)\n\n            except UnicodeEncodeError:\n                exc = sys.exc_info()[1]\n                raise error.PyAsn1UnicodeEncodeError(\n                    \"Can't encode string '%s' with codec \"\n                    \"%s\" % (self._value, self.encoding), exc\n                )\n\n        def __unicode__(self):\n            return unicode(self._value)\n\n        def prettyIn(self, value):\n            try:\n                if isinstance(value, unicode):\n                    return value\n                elif isinstance(value, str):\n                    return value.decode(self.encoding)\n                elif isinstance(value, (tuple, list)):\n                    return self.prettyIn(''.join([chr(x) for x in value]))\n                elif isinstance(value, univ.OctetString):\n                    return value.asOctets().decode(self.encoding)\n                else:\n                    return unicode(value)\n\n            except (UnicodeDecodeError, LookupError):\n                exc = sys.exc_info()[1]\n                raise error.PyAsn1UnicodeDecodeError(\n                    \"Can't decode string '%s' with codec \"\n                    \"%s\" % (value, self.encoding), exc\n                )\n\n        def asOctets(self, padding=True):\n            return str(self)\n\n        def asNumbers(self, padding=True):\n            return tuple([ord(x) for x in str(self)])\n\n    else:\n        def __str__(self):\n            # `unicode` is Py3 text representation\n            return str(self._value)\n\n        def __bytes__(self):\n            try:\n                return self._value.encode(self.encoding)\n            except UnicodeEncodeError:\n                exc = sys.exc_info()[1]\n                raise error.PyAsn1UnicodeEncodeError(\n                    \"Can't encode string '%s' with codec \"\n                    \"%s\" % (self._value, self.encoding), exc\n                )\n\n        def prettyIn(self, value):\n            try:\n                if isinstance(value, str):\n                    return value\n                elif isinstance(value, bytes):\n                    return value.decode(self.encoding)\n                elif isinstance(value, (tuple, list)):\n                    return self.prettyIn(bytes(value))\n                elif isinstance(value, univ.OctetString):\n                    return value.asOctets().decode(self.encoding)\n                else:\n                    return str(value)\n\n            except (UnicodeDecodeError, LookupError):\n                exc = sys.exc_info()[1]\n                raise error.PyAsn1UnicodeDecodeError(\n                    \"Can't decode string '%s' with codec \"\n                    \"%s\" % (value, self.encoding), exc\n                )\n\n        def asOctets(self, padding=True):\n            return bytes(self)\n\n        def asNumbers(self, padding=True):\n            return tuple(bytes(self))\n\n    #\n    # See OctetString.prettyPrint() for the explanation\n    #\n\n    def prettyOut(self, value):\n        return value\n\n    def prettyPrint(self, scope=0):\n        # first see if subclass has its own .prettyOut()\n        value = self.prettyOut(self._value)\n\n        if value is not self._value:\n            return value\n\n        return AbstractCharacterString.__str__(self)\n\n    def __reversed__(self):\n        return reversed(self._value)\n\n\nclass NumericString(AbstractCharacterString):\n    __doc__ = AbstractCharacterString.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = AbstractCharacterString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 18)\n    )\n    encoding = 'us-ascii'\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n\n\nclass PrintableString(AbstractCharacterString):\n    __doc__ = AbstractCharacterString.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = AbstractCharacterString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 19)\n    )\n    encoding = 'us-ascii'\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n\n\nclass TeletexString(AbstractCharacterString):\n    __doc__ = AbstractCharacterString.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = AbstractCharacterString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 20)\n    )\n    encoding = 'iso-8859-1'\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n\n\nclass T61String(TeletexString):\n    __doc__ = TeletexString.__doc__\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n\n\nclass VideotexString(AbstractCharacterString):\n    __doc__ = AbstractCharacterString.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = AbstractCharacterString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 21)\n    )\n    encoding = 'iso-8859-1'\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n\n\nclass IA5String(AbstractCharacterString):\n    __doc__ = AbstractCharacterString.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = AbstractCharacterString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 22)\n    )\n    encoding = 'us-ascii'\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n\n\nclass GraphicString(AbstractCharacterString):\n    __doc__ = AbstractCharacterString.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = AbstractCharacterString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 25)\n    )\n    encoding = 'iso-8859-1'\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n\n\nclass VisibleString(AbstractCharacterString):\n    __doc__ = AbstractCharacterString.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = AbstractCharacterString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 26)\n    )\n    encoding = 'us-ascii'\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n\n\nclass ISO646String(VisibleString):\n    __doc__ = VisibleString.__doc__\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n\nclass GeneralString(AbstractCharacterString):\n    __doc__ = AbstractCharacterString.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = AbstractCharacterString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 27)\n    )\n    encoding = 'iso-8859-1'\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n\n\nclass UniversalString(AbstractCharacterString):\n    __doc__ = AbstractCharacterString.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = AbstractCharacterString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 28)\n    )\n    encoding = \"utf-32-be\"\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n\n\nclass BMPString(AbstractCharacterString):\n    __doc__ = AbstractCharacterString.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = AbstractCharacterString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 30)\n    )\n    encoding = \"utf-16-be\"\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n\n\nclass UTF8String(AbstractCharacterString):\n    __doc__ = AbstractCharacterString.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = AbstractCharacterString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 12)\n    )\n    encoding = \"utf-8\"\n\n    # Optimization for faster codec lookup\n    typeId = AbstractCharacterString.getTypeId()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/type/constraint.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Original concept and code by Mike C. Fletcher.\n#\nimport sys\n\nfrom pyasn1.type import error\n\n__all__ = ['SingleValueConstraint', 'ContainedSubtypeConstraint',\n           'ValueRangeConstraint', 'ValueSizeConstraint',\n           'PermittedAlphabetConstraint', 'InnerTypeConstraint',\n           'ConstraintsExclusion', 'ConstraintsIntersection',\n           'ConstraintsUnion']\n\n\nclass AbstractConstraint(object):\n\n    def __init__(self, *values):\n        self._valueMap = set()\n        self._setValues(values)\n        self.__hash = hash((self.__class__.__name__, self._values))\n\n    def __call__(self, value, idx=None):\n        if not self._values:\n            return\n\n        try:\n            self._testValue(value, idx)\n\n        except error.ValueConstraintError:\n            raise error.ValueConstraintError(\n                '%s failed at: %r' % (self, sys.exc_info()[1])\n            )\n\n    def __repr__(self):\n        representation = '%s object' % (self.__class__.__name__)\n\n        if self._values:\n            representation += ', consts %s' % ', '.join(\n                [repr(x) for x in self._values])\n\n        return '<%s>' % representation\n\n    def __eq__(self, other):\n        return self is other and True or self._values == other\n\n    def __ne__(self, other):\n        return self._values != other\n\n    def __lt__(self, other):\n        return self._values < other\n\n    def __le__(self, other):\n        return self._values <= other\n\n    def __gt__(self, other):\n        return self._values > other\n\n    def __ge__(self, other):\n        return self._values >= other\n\n    if sys.version_info[0] <= 2:\n        def __nonzero__(self):\n            return self._values and True or False\n    else:\n        def __bool__(self):\n            return self._values and True or False\n\n    def __hash__(self):\n        return self.__hash\n\n    def _setValues(self, values):\n        self._values = values\n\n    def _testValue(self, value, idx):\n        raise error.ValueConstraintError(value)\n\n    # Constraints derivation logic\n    def getValueMap(self):\n        return self._valueMap\n\n    def isSuperTypeOf(self, otherConstraint):\n        # TODO: fix possible comparison of set vs scalars here\n        return (otherConstraint is self or\n                not self._values or\n                otherConstraint == self or\n                self in otherConstraint.getValueMap())\n\n    def isSubTypeOf(self, otherConstraint):\n        return (otherConstraint is self or\n                not self or\n                otherConstraint == self or\n                otherConstraint in self._valueMap)\n\n\nclass SingleValueConstraint(AbstractConstraint):\n    \"\"\"Create a SingleValueConstraint object.\n\n    The SingleValueConstraint satisfies any value that\n    is present in the set of permitted values.\n\n    The SingleValueConstraint object can be applied to\n    any ASN.1 type.\n\n    Parameters\n    ----------\n    *values: :class:`int`\n        Full set of values permitted by this constraint object.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class DivisorOfSix(Integer):\n            '''\n            ASN.1 specification:\n\n            Divisor-Of-6 ::= INTEGER (1 | 2 | 3 | 6)\n            '''\n            subtypeSpec = SingleValueConstraint(1, 2, 3, 6)\n\n        # this will succeed\n        divisor_of_six = DivisorOfSix(1)\n\n        # this will raise ValueConstraintError\n        divisor_of_six = DivisorOfSix(7)\n    \"\"\"\n    def _setValues(self, values):\n        self._values = values\n        self._set = set(values)\n\n    def _testValue(self, value, idx):\n        if value not in self._set:\n            raise error.ValueConstraintError(value)\n\n\nclass ContainedSubtypeConstraint(AbstractConstraint):\n    \"\"\"Create a ContainedSubtypeConstraint object.\n\n    The ContainedSubtypeConstraint satisfies any value that\n    is present in the set of permitted values and also\n    satisfies included constraints.\n\n    The ContainedSubtypeConstraint object can be applied to\n    any ASN.1 type.\n\n    Parameters\n    ----------\n    *values:\n        Full set of values and constraint objects permitted\n        by this constraint object.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class DivisorOfEighteen(Integer):\n            '''\n            ASN.1 specification:\n\n            Divisors-of-18 ::= INTEGER (INCLUDES Divisors-of-6 | 9 | 18)\n            '''\n            subtypeSpec = ContainedSubtypeConstraint(\n                SingleValueConstraint(1, 2, 3, 6), 9, 18\n            )\n\n        # this will succeed\n        divisor_of_eighteen = DivisorOfEighteen(9)\n\n        # this will raise ValueConstraintError\n        divisor_of_eighteen = DivisorOfEighteen(10)\n    \"\"\"\n    def _testValue(self, value, idx):\n        for constraint in self._values:\n            if isinstance(constraint, AbstractConstraint):\n                constraint(value, idx)\n            elif value not in self._set:\n                raise error.ValueConstraintError(value)\n\n\nclass ValueRangeConstraint(AbstractConstraint):\n    \"\"\"Create a ValueRangeConstraint object.\n\n    The ValueRangeConstraint satisfies any value that\n    falls in the range of permitted values.\n\n    The ValueRangeConstraint object can only be applied\n    to :class:`~pyasn1.type.univ.Integer` and\n    :class:`~pyasn1.type.univ.Real` types.\n\n    Parameters\n    ----------\n    start: :class:`int`\n        Minimum permitted value in the range (inclusive)\n\n    end: :class:`int`\n        Maximum permitted value in the range (inclusive)\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class TeenAgeYears(Integer):\n            '''\n            ASN.1 specification:\n\n            TeenAgeYears ::= INTEGER (13 .. 19)\n            '''\n            subtypeSpec = ValueRangeConstraint(13, 19)\n\n        # this will succeed\n        teen_year = TeenAgeYears(18)\n\n        # this will raise ValueConstraintError\n        teen_year = TeenAgeYears(20)\n    \"\"\"\n    def _testValue(self, value, idx):\n        if value < self.start or value > self.stop:\n            raise error.ValueConstraintError(value)\n\n    def _setValues(self, values):\n        if len(values) != 2:\n            raise error.PyAsn1Error(\n                '%s: bad constraint values' % (self.__class__.__name__,)\n            )\n        self.start, self.stop = values\n        if self.start > self.stop:\n            raise error.PyAsn1Error(\n                '%s: screwed constraint values (start > stop): %s > %s' % (\n                    self.__class__.__name__,\n                    self.start, self.stop\n                )\n            )\n        AbstractConstraint._setValues(self, values)\n\n\nclass ValueSizeConstraint(ValueRangeConstraint):\n    \"\"\"Create a ValueSizeConstraint object.\n\n    The ValueSizeConstraint satisfies any value for\n    as long as its size falls within the range of\n    permitted sizes.\n\n    The ValueSizeConstraint object can be applied\n    to :class:`~pyasn1.type.univ.BitString`,\n    :class:`~pyasn1.type.univ.OctetString` (including\n    all :ref:`character ASN.1 types <type.char>`),\n    :class:`~pyasn1.type.univ.SequenceOf`\n    and :class:`~pyasn1.type.univ.SetOf` types.\n\n    Parameters\n    ----------\n    minimum: :class:`int`\n        Minimum permitted size of the value (inclusive)\n\n    maximum: :class:`int`\n        Maximum permitted size of the value (inclusive)\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class BaseballTeamRoster(SetOf):\n            '''\n            ASN.1 specification:\n\n            BaseballTeamRoster ::= SET SIZE (1..25) OF PlayerNames\n            '''\n            componentType = PlayerNames()\n            subtypeSpec = ValueSizeConstraint(1, 25)\n\n        # this will succeed\n        team = BaseballTeamRoster()\n        team.extend(['Jan', 'Matej'])\n        encode(team)\n\n        # this will raise ValueConstraintError\n        team = BaseballTeamRoster()\n        team.extend(['Jan'] * 26)\n        encode(team)\n\n    Note\n    ----\n    Whenever ValueSizeConstraint is applied to mutable types\n    (e.g. :class:`~pyasn1.type.univ.SequenceOf`,\n    :class:`~pyasn1.type.univ.SetOf`), constraint\n    validation only happens at the serialisation phase rather\n    than schema instantiation phase (as it is with immutable\n    types).\n    \"\"\"\n    def _testValue(self, value, idx):\n        valueSize = len(value)\n        if valueSize < self.start or valueSize > self.stop:\n            raise error.ValueConstraintError(value)\n\n\nclass PermittedAlphabetConstraint(SingleValueConstraint):\n    \"\"\"Create a PermittedAlphabetConstraint object.\n\n    The PermittedAlphabetConstraint satisfies any character\n    string for as long as all its characters are present in\n    the set of permitted characters.\n\n    The PermittedAlphabetConstraint object can only be applied\n    to the :ref:`character ASN.1 types <type.char>` such as\n    :class:`~pyasn1.type.char.IA5String`.\n\n    Parameters\n    ----------\n    *alphabet: :class:`str`\n        Full set of characters permitted by this constraint object.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class BooleanValue(IA5String):\n            '''\n            ASN.1 specification:\n\n            BooleanValue ::= IA5String (FROM ('T' | 'F'))\n            '''\n            subtypeSpec = PermittedAlphabetConstraint('T', 'F')\n\n        # this will succeed\n        truth = BooleanValue('T')\n        truth = BooleanValue('TF')\n\n        # this will raise ValueConstraintError\n        garbage = BooleanValue('TAF')\n    \"\"\"\n    def _setValues(self, values):\n        self._values = values\n        self._set = set(values)\n\n    def _testValue(self, value, idx):\n        if not self._set.issuperset(value):\n            raise error.ValueConstraintError(value)\n\n\nclass ComponentPresentConstraint(AbstractConstraint):\n    \"\"\"Create a ComponentPresentConstraint object.\n\n    The ComponentPresentConstraint is only satisfied when the value\n    is not `None`.\n\n    The ComponentPresentConstraint object is typically used with\n    `WithComponentsConstraint`.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        present = ComponentPresentConstraint()\n\n        # this will succeed\n        present('whatever')\n\n        # this will raise ValueConstraintError\n        present(None)\n    \"\"\"\n    def _setValues(self, values):\n        self._values = ('<must be present>',)\n\n        if values:\n            raise error.PyAsn1Error('No arguments expected')\n\n    def _testValue(self, value, idx):\n        if value is None:\n            raise error.ValueConstraintError(\n                'Component is not present:')\n\n\nclass ComponentAbsentConstraint(AbstractConstraint):\n    \"\"\"Create a ComponentAbsentConstraint object.\n\n    The ComponentAbsentConstraint is only satisfied when the value\n    is `None`.\n\n    The ComponentAbsentConstraint object is typically used with\n    `WithComponentsConstraint`.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        absent = ComponentAbsentConstraint()\n\n        # this will succeed\n        absent(None)\n\n        # this will raise ValueConstraintError\n        absent('whatever')\n    \"\"\"\n    def _setValues(self, values):\n        self._values = ('<must be absent>',)\n\n        if values:\n            raise error.PyAsn1Error('No arguments expected')\n\n    def _testValue(self, value, idx):\n        if value is not None:\n            raise error.ValueConstraintError(\n                'Component is not absent: %r' % value)\n\n\nclass WithComponentsConstraint(AbstractConstraint):\n    \"\"\"Create a WithComponentsConstraint object.\n\n    The `WithComponentsConstraint` satisfies any mapping object that has\n    constrained fields present or absent, what is indicated by\n    `ComponentPresentConstraint` and `ComponentAbsentConstraint`\n    objects respectively.\n\n    The `WithComponentsConstraint` object is typically applied\n    to  :class:`~pyasn1.type.univ.Set` or\n    :class:`~pyasn1.type.univ.Sequence` types.\n\n    Parameters\n    ----------\n    *fields: :class:`tuple`\n        Zero or more tuples of (`field`, `constraint`) indicating constrained\n        fields.\n\n    Notes\n    -----\n    On top of the primary use of `WithComponentsConstraint` (ensuring presence\n    or absence of particular components of a :class:`~pyasn1.type.univ.Set` or\n    :class:`~pyasn1.type.univ.Sequence`), it is also possible to pass any other\n    constraint objects or their combinations. In case of scalar fields, these\n    constraints will be verified in addition to the constraints belonging to\n    scalar components themselves. However, formally, these additional\n    constraints do not change the type of these ASN.1 objects.\n\n    Examples\n    --------\n\n    .. code-block:: python\n\n        class Item(Sequence):  #  Set is similar\n            '''\n            ASN.1 specification:\n\n            Item ::= SEQUENCE {\n                id    INTEGER OPTIONAL,\n                name  OCTET STRING OPTIONAL\n            } WITH COMPONENTS id PRESENT, name ABSENT | id ABSENT, name PRESENT\n            '''\n            componentType = NamedTypes(\n                OptionalNamedType('id', Integer()),\n                OptionalNamedType('name', OctetString())\n            )\n            withComponents = ConstraintsUnion(\n                WithComponentsConstraint(\n                    ('id', ComponentPresentConstraint()),\n                    ('name', ComponentAbsentConstraint())\n                ),\n                WithComponentsConstraint(\n                    ('id', ComponentAbsentConstraint()),\n                    ('name', ComponentPresentConstraint())\n                )\n            )\n\n        item = Item()\n\n        # This will succeed\n        item['id'] = 1\n\n        # This will succeed\n        item.reset()\n        item['name'] = 'John'\n\n        # This will fail (on encoding)\n        item.reset()\n        descr['id'] = 1\n        descr['name'] = 'John'\n    \"\"\"\n    def _testValue(self, value, idx):\n        for field, constraint in self._values:\n            constraint(value.get(field))\n\n    def _setValues(self, values):\n        AbstractConstraint._setValues(self, values)\n\n\n# This is a bit kludgy, meaning two op modes within a single constraint\nclass InnerTypeConstraint(AbstractConstraint):\n    \"\"\"Value must satisfy the type and presence constraints\"\"\"\n\n    def _testValue(self, value, idx):\n        if self.__singleTypeConstraint:\n            self.__singleTypeConstraint(value)\n        elif self.__multipleTypeConstraint:\n            if idx not in self.__multipleTypeConstraint:\n                raise error.ValueConstraintError(value)\n            constraint, status = self.__multipleTypeConstraint[idx]\n            if status == 'ABSENT':  # XXX presence is not checked!\n                raise error.ValueConstraintError(value)\n            constraint(value)\n\n    def _setValues(self, values):\n        self.__multipleTypeConstraint = {}\n        self.__singleTypeConstraint = None\n        for v in values:\n            if isinstance(v, tuple):\n                self.__multipleTypeConstraint[v[0]] = v[1], v[2]\n            else:\n                self.__singleTypeConstraint = v\n        AbstractConstraint._setValues(self, values)\n\n\n# Logic operations on constraints\n\nclass ConstraintsExclusion(AbstractConstraint):\n    \"\"\"Create a ConstraintsExclusion logic operator object.\n\n    The ConstraintsExclusion logic operator succeeds when the\n    value does *not* satisfy the operand constraint.\n\n    The ConstraintsExclusion object can be applied to\n    any constraint and logic operator object.\n\n    Parameters\n    ----------\n    constraint:\n        Constraint or logic operator object.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class Lipogramme(IA5STRING):\n            '''\n            ASN.1 specification:\n\n            Lipogramme ::=\n                IA5String (FROM (ALL EXCEPT (\"e\"|\"E\")))\n            '''\n            subtypeSpec = ConstraintsExclusion(\n                PermittedAlphabetConstraint('e', 'E')\n            )\n\n        # this will succeed\n        lipogramme = Lipogramme('A work of fiction?')\n\n        # this will raise ValueConstraintError\n        lipogramme = Lipogramme('Eel')\n\n    Warning\n    -------\n    The above example involving PermittedAlphabetConstraint might\n    not work due to the way how PermittedAlphabetConstraint works.\n    The other constraints might work with ConstraintsExclusion\n    though.\n    \"\"\"\n    def _testValue(self, value, idx):\n        try:\n            self._values[0](value, idx)\n        except error.ValueConstraintError:\n            return\n        else:\n            raise error.ValueConstraintError(value)\n\n    def _setValues(self, values):\n        if len(values) != 1:\n            raise error.PyAsn1Error('Single constraint expected')\n\n        AbstractConstraint._setValues(self, values)\n\n\nclass AbstractConstraintSet(AbstractConstraint):\n\n    def __getitem__(self, idx):\n        return self._values[idx]\n\n    def __iter__(self):\n        return iter(self._values)\n\n    def __add__(self, value):\n        return self.__class__(*(self._values + (value,)))\n\n    def __radd__(self, value):\n        return self.__class__(*((value,) + self._values))\n\n    def __len__(self):\n        return len(self._values)\n\n    # Constraints inclusion in sets\n\n    def _setValues(self, values):\n        self._values = values\n        for constraint in values:\n            if constraint:\n                self._valueMap.add(constraint)\n                self._valueMap.update(constraint.getValueMap())\n\n\nclass ConstraintsIntersection(AbstractConstraintSet):\n    \"\"\"Create a ConstraintsIntersection logic operator object.\n\n    The ConstraintsIntersection logic operator only succeeds\n    if *all* its operands succeed.\n\n    The ConstraintsIntersection object can be applied to\n    any constraint and logic operator objects.\n\n    The ConstraintsIntersection object duck-types the immutable\n    container object like Python :py:class:`tuple`.\n\n    Parameters\n    ----------\n    *constraints:\n        Constraint or logic operator objects.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class CapitalAndSmall(IA5String):\n            '''\n            ASN.1 specification:\n\n            CapitalAndSmall ::=\n                IA5String (FROM (\"A\"..\"Z\"|\"a\"..\"z\"))\n            '''\n            subtypeSpec = ConstraintsIntersection(\n                PermittedAlphabetConstraint('A', 'Z'),\n                PermittedAlphabetConstraint('a', 'z')\n            )\n\n        # this will succeed\n        capital_and_small = CapitalAndSmall('Hello')\n\n        # this will raise ValueConstraintError\n        capital_and_small = CapitalAndSmall('hello')\n    \"\"\"\n    def _testValue(self, value, idx):\n        for constraint in self._values:\n            constraint(value, idx)\n\n\nclass ConstraintsUnion(AbstractConstraintSet):\n    \"\"\"Create a ConstraintsUnion logic operator object.\n\n    The ConstraintsUnion logic operator succeeds if\n    *at least* a single operand succeeds.\n\n    The ConstraintsUnion object can be applied to\n    any constraint and logic operator objects.\n\n    The ConstraintsUnion object duck-types the immutable\n    container object like Python :py:class:`tuple`.\n\n    Parameters\n    ----------\n    *constraints:\n        Constraint or logic operator objects.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class CapitalOrSmall(IA5String):\n            '''\n            ASN.1 specification:\n\n            CapitalOrSmall ::=\n                IA5String (FROM (\"A\"..\"Z\") | FROM (\"a\"..\"z\"))\n            '''\n            subtypeSpec = ConstraintsUnion(\n                PermittedAlphabetConstraint('A', 'Z'),\n                PermittedAlphabetConstraint('a', 'z')\n            )\n\n        # this will succeed\n        capital_or_small = CapitalAndSmall('Hello')\n\n        # this will raise ValueConstraintError\n        capital_or_small = CapitalOrSmall('hello!')\n    \"\"\"\n    def _testValue(self, value, idx):\n        for constraint in self._values:\n            try:\n                constraint(value, idx)\n            except error.ValueConstraintError:\n                pass\n            else:\n                return\n\n        raise error.ValueConstraintError(\n            'all of %s failed for \"%s\"' % (self._values, value)\n        )\n\n# TODO:\n# refactor InnerTypeConstraint\n# add tests for type check\n# implement other constraint types\n# make constraint validation easy to skip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/type/error.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom pyasn1.error import PyAsn1Error\n\n\nclass ValueConstraintError(PyAsn1Error):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/type/namedtype.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nimport sys\n\nfrom pyasn1 import error\nfrom pyasn1.type import tag\nfrom pyasn1.type import tagmap\n\n__all__ = ['NamedType', 'OptionalNamedType', 'DefaultedNamedType',\n           'NamedTypes']\n\ntry:\n    any\n\nexcept NameError:\n    any = lambda x: bool(filter(bool, x))\n\n\nclass NamedType(object):\n    \"\"\"Create named field object for a constructed ASN.1 type.\n\n    The |NamedType| object represents a single name and ASN.1 type of a constructed ASN.1 type.\n\n    |NamedType| objects are immutable and duck-type Python :class:`tuple` objects\n    holding *name* and *asn1Object* components.\n\n    Parameters\n    ----------\n    name: :py:class:`str`\n        Field name\n\n    asn1Object:\n        ASN.1 type object\n    \"\"\"\n    isOptional = False\n    isDefaulted = False\n\n    def __init__(self, name, asn1Object, openType=None):\n        self.__name = name\n        self.__type = asn1Object\n        self.__nameAndType = name, asn1Object\n        self.__openType = openType\n\n    def __repr__(self):\n        representation = '%s=%r' % (self.name, self.asn1Object)\n\n        if self.openType:\n            representation += ', open type %r' % self.openType\n\n        return '<%s object, type %s>' % (\n            self.__class__.__name__, representation)\n\n    def __eq__(self, other):\n        return self.__nameAndType == other\n\n    def __ne__(self, other):\n        return self.__nameAndType != other\n\n    def __lt__(self, other):\n        return self.__nameAndType < other\n\n    def __le__(self, other):\n        return self.__nameAndType <= other\n\n    def __gt__(self, other):\n        return self.__nameAndType > other\n\n    def __ge__(self, other):\n        return self.__nameAndType >= other\n\n    def __hash__(self):\n        return hash(self.__nameAndType)\n\n    def __getitem__(self, idx):\n        return self.__nameAndType[idx]\n\n    def __iter__(self):\n        return iter(self.__nameAndType)\n\n    @property\n    def name(self):\n        return self.__name\n\n    @property\n    def asn1Object(self):\n        return self.__type\n\n    @property\n    def openType(self):\n        return self.__openType\n\n    # Backward compatibility\n\n    def getName(self):\n        return self.name\n\n    def getType(self):\n        return self.asn1Object\n\n\nclass OptionalNamedType(NamedType):\n    __doc__ = NamedType.__doc__\n\n    isOptional = True\n\n\nclass DefaultedNamedType(NamedType):\n    __doc__ = NamedType.__doc__\n\n    isDefaulted = True\n\n\nclass NamedTypes(object):\n    \"\"\"Create a collection of named fields for a constructed ASN.1 type.\n\n    The NamedTypes object represents a collection of named fields of a constructed ASN.1 type.\n\n    *NamedTypes* objects are immutable and duck-type Python :class:`dict` objects\n    holding *name* as keys and ASN.1 type object as values.\n\n    Parameters\n    ----------\n    *namedTypes: :class:`~pyasn1.type.namedtype.NamedType`\n\n    Examples\n    --------\n\n    .. code-block:: python\n\n        class Description(Sequence):\n            '''\n            ASN.1 specification:\n\n            Description ::= SEQUENCE {\n                surname    IA5String,\n                first-name IA5String OPTIONAL,\n                age        INTEGER DEFAULT 40\n            }\n            '''\n            componentType = NamedTypes(\n                NamedType('surname', IA5String()),\n                OptionalNamedType('first-name', IA5String()),\n                DefaultedNamedType('age', Integer(40))\n            )\n\n        descr = Description()\n        descr['surname'] = 'Smith'\n        descr['first-name'] = 'John'\n    \"\"\"\n    def __init__(self, *namedTypes, **kwargs):\n        self.__namedTypes = namedTypes\n        self.__namedTypesLen = len(self.__namedTypes)\n        self.__minTagSet = self.__computeMinTagSet()\n        self.__nameToPosMap = self.__computeNameToPosMap()\n        self.__tagToPosMap = self.__computeTagToPosMap()\n        self.__ambiguousTypes = 'terminal' not in kwargs and self.__computeAmbiguousTypes() or {}\n        self.__uniqueTagMap = self.__computeTagMaps(unique=True)\n        self.__nonUniqueTagMap = self.__computeTagMaps(unique=False)\n        self.__hasOptionalOrDefault = any([True for namedType in self.__namedTypes\n                                           if namedType.isDefaulted or namedType.isOptional])\n        self.__hasOpenTypes = any([True for namedType in self.__namedTypes\n                                   if namedType.openType])\n\n        self.__requiredComponents = frozenset(\n                [idx for idx, nt in enumerate(self.__namedTypes) if not nt.isOptional and not nt.isDefaulted]\n            )\n        self.__keys = frozenset([namedType.name for namedType in self.__namedTypes])\n        self.__values = tuple([namedType.asn1Object for namedType in self.__namedTypes])\n        self.__items = tuple([(namedType.name, namedType.asn1Object) for namedType in self.__namedTypes])\n\n    def __repr__(self):\n        representation = ', '.join(['%r' % x for x in self.__namedTypes])\n        return '<%s object, types %s>' % (\n            self.__class__.__name__, representation)\n\n    def __eq__(self, other):\n        return self.__namedTypes == other\n\n    def __ne__(self, other):\n        return self.__namedTypes != other\n\n    def __lt__(self, other):\n        return self.__namedTypes < other\n\n    def __le__(self, other):\n        return self.__namedTypes <= other\n\n    def __gt__(self, other):\n        return self.__namedTypes > other\n\n    def __ge__(self, other):\n        return self.__namedTypes >= other\n\n    def __hash__(self):\n        return hash(self.__namedTypes)\n\n    def __getitem__(self, idx):\n        try:\n            return self.__namedTypes[idx]\n\n        except TypeError:\n            return self.__namedTypes[self.__nameToPosMap[idx]]\n\n    def __contains__(self, key):\n        return key in self.__nameToPosMap\n\n    def __iter__(self):\n        return (x[0] for x in self.__namedTypes)\n\n    if sys.version_info[0] <= 2:\n        def __nonzero__(self):\n            return self.__namedTypesLen > 0\n    else:\n        def __bool__(self):\n            return self.__namedTypesLen > 0\n\n    def __len__(self):\n        return self.__namedTypesLen\n\n    # Python dict protocol\n\n    def values(self):\n        return self.__values\n\n    def keys(self):\n        return self.__keys\n\n    def items(self):\n        return self.__items\n\n    def clone(self):\n        return self.__class__(*self.__namedTypes)\n\n    class PostponedError(object):\n        def __init__(self, errorMsg):\n            self.__errorMsg = errorMsg\n\n        def __getitem__(self, item):\n            raise  error.PyAsn1Error(self.__errorMsg)\n\n    def __computeTagToPosMap(self):\n        tagToPosMap = {}\n        for idx, namedType in enumerate(self.__namedTypes):\n            tagMap = namedType.asn1Object.tagMap\n            if isinstance(tagMap, NamedTypes.PostponedError):\n                return tagMap\n            if not tagMap:\n                continue\n            for _tagSet in tagMap.presentTypes:\n                if _tagSet in tagToPosMap:\n                    return NamedTypes.PostponedError('Duplicate component tag %s at %s' % (_tagSet, namedType))\n                tagToPosMap[_tagSet] = idx\n\n        return tagToPosMap\n\n    def __computeNameToPosMap(self):\n        nameToPosMap = {}\n        for idx, namedType in enumerate(self.__namedTypes):\n            if namedType.name in nameToPosMap:\n                return NamedTypes.PostponedError('Duplicate component name %s at %s' % (namedType.name, namedType))\n            nameToPosMap[namedType.name] = idx\n\n        return nameToPosMap\n\n    def __computeAmbiguousTypes(self):\n        ambiguousTypes = {}\n        partialAmbiguousTypes = ()\n        for idx, namedType in reversed(tuple(enumerate(self.__namedTypes))):\n            if namedType.isOptional or namedType.isDefaulted:\n                partialAmbiguousTypes = (namedType,) + partialAmbiguousTypes\n            else:\n                partialAmbiguousTypes = (namedType,)\n            if len(partialAmbiguousTypes) == len(self.__namedTypes):\n                ambiguousTypes[idx] = self\n            else:\n                ambiguousTypes[idx] = NamedTypes(*partialAmbiguousTypes, **dict(terminal=True))\n        return ambiguousTypes\n\n    def getTypeByPosition(self, idx):\n        \"\"\"Return ASN.1 type object by its position in fields set.\n\n        Parameters\n        ----------\n        idx: :py:class:`int`\n            Field index\n\n        Returns\n        -------\n        :\n            ASN.1 type\n\n        Raises\n        ------\n        ~pyasn1.error.PyAsn1Error\n            If given position is out of fields range\n        \"\"\"\n        try:\n            return self.__namedTypes[idx].asn1Object\n\n        except IndexError:\n            raise error.PyAsn1Error('Type position out of range')\n\n    def getPositionByType(self, tagSet):\n        \"\"\"Return field position by its ASN.1 type.\n\n        Parameters\n        ----------\n        tagSet: :class:`~pysnmp.type.tag.TagSet`\n            ASN.1 tag set distinguishing one ASN.1 type from others.\n\n        Returns\n        -------\n        : :py:class:`int`\n            ASN.1 type position in fields set\n\n        Raises\n        ------\n        ~pyasn1.error.PyAsn1Error\n            If *tagSet* is not present or ASN.1 types are not unique within callee *NamedTypes*\n        \"\"\"\n        try:\n            return self.__tagToPosMap[tagSet]\n\n        except KeyError:\n            raise error.PyAsn1Error('Type %s not found' % (tagSet,))\n\n    def getNameByPosition(self, idx):\n        \"\"\"Return field name by its position in fields set.\n\n        Parameters\n        ----------\n        idx: :py:class:`idx`\n            Field index\n\n        Returns\n        -------\n        : :py:class:`str`\n            Field name\n\n        Raises\n        ------\n        ~pyasn1.error.PyAsn1Error\n            If given field name is not present in callee *NamedTypes*\n        \"\"\"\n        try:\n            return self.__namedTypes[idx].name\n\n        except IndexError:\n            raise error.PyAsn1Error('Type position out of range')\n\n    def getPositionByName(self, name):\n        \"\"\"Return field position by filed name.\n\n        Parameters\n        ----------\n        name: :py:class:`str`\n            Field name\n\n        Returns\n        -------\n        : :py:class:`int`\n            Field position in fields set\n\n        Raises\n        ------\n        ~pyasn1.error.PyAsn1Error\n            If *name* is not present or not unique within callee *NamedTypes*\n        \"\"\"\n        try:\n            return self.__nameToPosMap[name]\n\n        except KeyError:\n            raise error.PyAsn1Error('Name %s not found' % (name,))\n\n    def getTagMapNearPosition(self, idx):\n        \"\"\"Return ASN.1 types that are allowed at or past given field position.\n\n        Some ASN.1 serialisation allow for skipping optional and defaulted fields.\n        Some constructed ASN.1 types allow reordering of the fields. When recovering\n        such objects it may be important to know which types can possibly be\n        present at any given position in the field sets.\n\n        Parameters\n        ----------\n        idx: :py:class:`int`\n            Field index\n\n        Returns\n        -------\n        : :class:`~pyasn1.type.tagmap.TagMap`\n            Map if ASN.1 types allowed at given field position\n\n        Raises\n        ------\n        ~pyasn1.error.PyAsn1Error\n            If given position is out of fields range\n        \"\"\"\n        try:\n            return self.__ambiguousTypes[idx].tagMap\n\n        except KeyError:\n            raise error.PyAsn1Error('Type position out of range')\n\n    def getPositionNearType(self, tagSet, idx):\n        \"\"\"Return the closest field position where given ASN.1 type is allowed.\n\n        Some ASN.1 serialisation allow for skipping optional and defaulted fields.\n        Some constructed ASN.1 types allow reordering of the fields. When recovering\n        such objects it may be important to know at which field position, in field set,\n        given *tagSet* is allowed at or past *idx* position.\n\n        Parameters\n        ----------\n        tagSet: :class:`~pyasn1.type.tag.TagSet`\n           ASN.1 type which field position to look up\n\n        idx: :py:class:`int`\n            Field position at or past which to perform ASN.1 type look up\n\n        Returns\n        -------\n        : :py:class:`int`\n            Field position in fields set\n\n        Raises\n        ------\n        ~pyasn1.error.PyAsn1Error\n            If *tagSet* is not present or not unique within callee *NamedTypes*\n            or *idx* is out of fields range\n        \"\"\"\n        try:\n            return idx + self.__ambiguousTypes[idx].getPositionByType(tagSet)\n\n        except KeyError:\n            raise error.PyAsn1Error('Type position out of range')\n\n    def __computeMinTagSet(self):\n        minTagSet = None\n        for namedType in self.__namedTypes:\n            asn1Object = namedType.asn1Object\n\n            try:\n                tagSet = asn1Object.minTagSet\n\n            except AttributeError:\n                tagSet = asn1Object.tagSet\n\n            if minTagSet is None or tagSet < minTagSet:\n                minTagSet = tagSet\n\n        return minTagSet or tag.TagSet()\n\n    @property\n    def minTagSet(self):\n        \"\"\"Return the minimal TagSet among ASN.1 type in callee *NamedTypes*.\n\n        Some ASN.1 types/serialisation protocols require ASN.1 types to be\n        arranged based on their numerical tag value. The *minTagSet* property\n        returns that.\n\n        Returns\n        -------\n        : :class:`~pyasn1.type.tagset.TagSet`\n            Minimal TagSet among ASN.1 types in callee *NamedTypes*\n        \"\"\"\n        return self.__minTagSet\n\n    def __computeTagMaps(self, unique):\n        presentTypes = {}\n        skipTypes = {}\n        defaultType = None\n        for namedType in self.__namedTypes:\n            tagMap = namedType.asn1Object.tagMap\n            if isinstance(tagMap, NamedTypes.PostponedError):\n                return tagMap\n            for tagSet in tagMap:\n                if unique and tagSet in presentTypes:\n                    return NamedTypes.PostponedError('Non-unique tagSet %s of %s at %s' % (tagSet, namedType, self))\n                presentTypes[tagSet] = namedType.asn1Object\n            skipTypes.update(tagMap.skipTypes)\n\n            if defaultType is None:\n                defaultType = tagMap.defaultType\n            elif tagMap.defaultType is not None:\n                return NamedTypes.PostponedError('Duplicate default ASN.1 type at %s' % (self,))\n\n        return tagmap.TagMap(presentTypes, skipTypes, defaultType)\n\n    @property\n    def tagMap(self):\n        \"\"\"Return a *TagMap* object from tags and types recursively.\n\n        Return a :class:`~pyasn1.type.tagmap.TagMap` object by\n        combining tags from *TagMap* objects of children types and\n        associating them with their immediate child type.\n\n        Example\n        -------\n        .. code-block:: python\n\n           OuterType ::= CHOICE {\n               innerType INTEGER\n           }\n\n        Calling *.tagMap* on *OuterType* will yield a map like this:\n\n        .. code-block:: python\n\n           Integer.tagSet -> Choice\n        \"\"\"\n        return self.__nonUniqueTagMap\n\n    @property\n    def tagMapUnique(self):\n        \"\"\"Return a *TagMap* object from unique tags and types recursively.\n\n        Return a :class:`~pyasn1.type.tagmap.TagMap` object by\n        combining tags from *TagMap* objects of children types and\n        associating them with their immediate child type.\n\n        Example\n        -------\n        .. code-block:: python\n\n           OuterType ::= CHOICE {\n               innerType INTEGER\n           }\n\n        Calling *.tagMapUnique* on *OuterType* will yield a map like this:\n\n        .. code-block:: python\n\n           Integer.tagSet -> Choice\n\n        Note\n        ----\n\n        Duplicate *TagSet* objects found in the tree of children\n        types would cause error.\n        \"\"\"\n        return self.__uniqueTagMap\n\n    @property\n    def hasOptionalOrDefault(self):\n        return self.__hasOptionalOrDefault\n\n    @property\n    def hasOpenTypes(self):\n        return self.__hasOpenTypes\n\n    @property\n    def namedTypes(self):\n        return tuple(self.__namedTypes)\n\n    @property\n    def requiredComponents(self):\n        return self.__requiredComponents\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/type/namedval.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# ASN.1 named integers\n#\nfrom pyasn1 import error\n\n__all__ = ['NamedValues']\n\n\nclass NamedValues(object):\n    \"\"\"Create named values object.\n\n    The |NamedValues| object represents a collection of string names\n    associated with numeric IDs. These objects are used for giving\n    names to otherwise numerical values.\n\n    |NamedValues| objects are immutable and duck-type Python\n    :class:`dict` object mapping ID to name and vice-versa.\n\n    Parameters\n    ----------\n    *args: variable number of two-element :py:class:`tuple`\n\n        name: :py:class:`str`\n            Value label\n\n        value: :py:class:`int`\n            Numeric value\n\n    Keyword Args\n    ------------\n    name: :py:class:`str`\n        Value label\n\n    value: :py:class:`int`\n        Numeric value\n\n    Examples\n    --------\n\n    .. code-block:: pycon\n\n        >>> nv = NamedValues('a', 'b', ('c', 0), d=1)\n        >>> nv\n        >>> {'c': 0, 'd': 1, 'a': 2, 'b': 3}\n        >>> nv[0]\n        'c'\n        >>> nv['a']\n        2\n    \"\"\"\n    def __init__(self, *args, **kwargs):\n        self.__names = {}\n        self.__numbers = {}\n\n        anonymousNames = []\n\n        for namedValue in args:\n            if isinstance(namedValue, (tuple, list)):\n                try:\n                    name, number = namedValue\n\n                except ValueError:\n                    raise error.PyAsn1Error('Not a proper attribute-value pair %r' % (namedValue,))\n\n            else:\n                anonymousNames.append(namedValue)\n                continue\n\n            if name in self.__names:\n                raise error.PyAsn1Error('Duplicate name %s' % (name,))\n\n            if number in self.__numbers:\n                raise error.PyAsn1Error('Duplicate number  %s=%s' % (name, number))\n\n            self.__names[name] = number\n            self.__numbers[number] = name\n\n        for name, number in kwargs.items():\n            if name in self.__names:\n                raise error.PyAsn1Error('Duplicate name %s' % (name,))\n\n            if number in self.__numbers:\n                raise error.PyAsn1Error('Duplicate number  %s=%s' % (name, number))\n\n            self.__names[name] = number\n            self.__numbers[number] = name\n\n        if anonymousNames:\n\n            number = self.__numbers and max(self.__numbers) + 1 or 0\n\n            for name in anonymousNames:\n\n                if name in self.__names:\n                    raise error.PyAsn1Error('Duplicate name %s' % (name,))\n\n                self.__names[name] = number\n                self.__numbers[number] = name\n\n                number += 1\n\n    def __repr__(self):\n        representation = ', '.join(['%s=%d' % x for x in self.items()])\n\n        if len(representation) > 64:\n            representation = representation[:32] + '...' + representation[-32:]\n\n        return '<%s object, enums %s>' % (\n            self.__class__.__name__, representation)\n\n    def __eq__(self, other):\n        return dict(self) == other\n\n    def __ne__(self, other):\n        return dict(self) != other\n\n    def __lt__(self, other):\n        return dict(self) < other\n\n    def __le__(self, other):\n        return dict(self) <= other\n\n    def __gt__(self, other):\n        return dict(self) > other\n\n    def __ge__(self, other):\n        return dict(self) >= other\n\n    def __hash__(self):\n        return hash(self.items())\n\n    # Python dict protocol (read-only)\n\n    def __getitem__(self, key):\n        try:\n            return self.__numbers[key]\n\n        except KeyError:\n            return self.__names[key]\n\n    def __len__(self):\n        return len(self.__names)\n\n    def __contains__(self, key):\n        return key in self.__names or key in self.__numbers\n\n    def __iter__(self):\n        return iter(self.__names)\n\n    def values(self):\n        return iter(self.__numbers)\n\n    def keys(self):\n        return iter(self.__names)\n\n    def items(self):\n        for name in self.__names:\n            yield name, self.__names[name]\n\n    # support merging\n\n    def __add__(self, namedValues):\n        return self.__class__(*tuple(self.items()) + tuple(namedValues.items()))\n\n    # XXX clone/subtype?\n\n    def clone(self, *args, **kwargs):\n        new = self.__class__(*args, **kwargs)\n        return self + new\n\n    # legacy protocol\n\n    def getName(self, value):\n        if value in self.__numbers:\n            return self.__numbers[value]\n\n    def getValue(self, name):\n        if name in self.__names:\n            return self.__names[name]\n\n    def getValues(self, *names):\n        try:\n            return [self.__names[name] for name in names]\n\n        except KeyError:\n            raise error.PyAsn1Error(\n                'Unknown bit identifier(s): %s' % (set(names).difference(self.__names),)\n            )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/type/opentype.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n\n__all__ = ['OpenType']\n\n\nclass OpenType(object):\n    \"\"\"Create ASN.1 type map indexed by a value\n\n    The *OpenType* object models an untyped field of a constructed ASN.1\n    type. In ASN.1 syntax it is usually represented by the\n    `ANY DEFINED BY` for scalars or `SET OF ANY DEFINED BY`,\n    `SEQUENCE OF ANY DEFINED BY` for container types clauses. Typically\n    used together with :class:`~pyasn1.type.univ.Any` object.\n\n    OpenType objects duck-type a read-only Python :class:`dict` objects,\n    however the passed `typeMap` is not copied, but stored by reference.\n    That means the user can manipulate `typeMap` at run time having this\n    reflected on *OpenType* object behavior.\n\n    The |OpenType| class models an untyped field of a constructed ASN.1\n    type. In ASN.1 syntax it is usually represented by the\n    `ANY DEFINED BY` for scalars or `SET OF ANY DEFINED BY`,\n    `SEQUENCE OF ANY DEFINED BY` for container types clauses. Typically\n    used with :class:`~pyasn1.type.univ.Any` type.\n\n    Parameters\n    ----------\n    name: :py:class:`str`\n        Field name\n\n    typeMap: :py:class:`dict`\n        A map of value->ASN.1 type. It's stored by reference and can be\n        mutated later to register new mappings.\n\n    Examples\n    --------\n\n    For untyped scalars:\n\n    .. code-block:: python\n\n        openType = OpenType(\n            'id', {1: Integer(),\n                   2: OctetString()}\n        )\n        Sequence(\n            componentType=NamedTypes(\n                NamedType('id', Integer()),\n                NamedType('blob', Any(), openType=openType)\n            )\n        )\n\n    For untyped `SET OF` or `SEQUENCE OF` vectors:\n\n    .. code-block:: python\n\n        openType = OpenType(\n            'id', {1: Integer(),\n                   2: OctetString()}\n        )\n        Sequence(\n            componentType=NamedTypes(\n                NamedType('id', Integer()),\n                NamedType('blob', SetOf(componentType=Any()),\n                          openType=openType)\n            )\n        )\n    \"\"\"\n\n    def __init__(self, name, typeMap=None):\n        self.__name = name\n        if typeMap is None:\n            self.__typeMap = {}\n        else:\n            self.__typeMap = typeMap\n\n    @property\n    def name(self):\n        return self.__name\n\n    # Python dict protocol\n\n    def values(self):\n        return self.__typeMap.values()\n\n    def keys(self):\n        return self.__typeMap.keys()\n\n    def items(self):\n        return self.__typeMap.items()\n\n    def __contains__(self, key):\n        return key in self.__typeMap\n\n    def __getitem__(self, key):\n        return self.__typeMap[key]\n\n    def __iter__(self):\n        return iter(self.__typeMap)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/type/tag.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom pyasn1 import error\n\n__all__ = ['tagClassUniversal', 'tagClassApplication', 'tagClassContext',\n           'tagClassPrivate', 'tagFormatSimple', 'tagFormatConstructed',\n           'tagCategoryImplicit', 'tagCategoryExplicit',\n           'tagCategoryUntagged', 'Tag', 'TagSet']\n\n#: Identifier for ASN.1 class UNIVERSAL\ntagClassUniversal = 0x00\n\n#: Identifier for ASN.1 class APPLICATION\ntagClassApplication = 0x40\n\n#: Identifier for ASN.1 class context-specific\ntagClassContext = 0x80\n\n#: Identifier for ASN.1 class private\ntagClassPrivate = 0xC0\n\n#: Identifier for \"simple\" ASN.1 structure (e.g. scalar)\ntagFormatSimple = 0x00\n\n#: Identifier for \"constructed\" ASN.1 structure (e.g. may have inner components)\ntagFormatConstructed = 0x20\n\ntagCategoryImplicit = 0x01\ntagCategoryExplicit = 0x02\ntagCategoryUntagged = 0x04\n\n\nclass Tag(object):\n    \"\"\"Create ASN.1 tag\n\n    Represents ASN.1 tag that can be attached to a ASN.1 type to make\n    types distinguishable from each other.\n\n    *Tag* objects are immutable and duck-type Python :class:`tuple` objects\n    holding three integer components of a tag.\n\n    Parameters\n    ----------\n    tagClass: :py:class:`int`\n        Tag *class* value\n\n    tagFormat: :py:class:`int`\n        Tag *format* value\n\n    tagId: :py:class:`int`\n        Tag ID value\n    \"\"\"\n    def __init__(self, tagClass, tagFormat, tagId):\n        if tagId < 0:\n            raise error.PyAsn1Error('Negative tag ID (%s) not allowed' % tagId)\n        self.__tagClass = tagClass\n        self.__tagFormat = tagFormat\n        self.__tagId = tagId\n        self.__tagClassId = tagClass, tagId\n        self.__hash = hash(self.__tagClassId)\n\n    def __repr__(self):\n        representation = '[%s:%s:%s]' % (\n            self.__tagClass, self.__tagFormat, self.__tagId)\n        return '<%s object, tag %s>' % (\n            self.__class__.__name__, representation)\n\n    def __eq__(self, other):\n        return self.__tagClassId == other\n\n    def __ne__(self, other):\n        return self.__tagClassId != other\n\n    def __lt__(self, other):\n        return self.__tagClassId < other\n\n    def __le__(self, other):\n        return self.__tagClassId <= other\n\n    def __gt__(self, other):\n        return self.__tagClassId > other\n\n    def __ge__(self, other):\n        return self.__tagClassId >= other\n\n    def __hash__(self):\n        return self.__hash\n\n    def __getitem__(self, idx):\n        if idx == 0:\n            return self.__tagClass\n        elif idx == 1:\n            return self.__tagFormat\n        elif idx == 2:\n            return self.__tagId\n        else:\n            raise IndexError()\n\n    def __iter__(self):\n        yield self.__tagClass\n        yield self.__tagFormat\n        yield self.__tagId\n\n    def __and__(self, otherTag):\n        return self.__class__(self.__tagClass & otherTag.tagClass,\n                              self.__tagFormat & otherTag.tagFormat,\n                              self.__tagId & otherTag.tagId)\n\n    def __or__(self, otherTag):\n        return self.__class__(self.__tagClass | otherTag.tagClass,\n                              self.__tagFormat | otherTag.tagFormat,\n                              self.__tagId | otherTag.tagId)\n\n    @property\n    def tagClass(self):\n        \"\"\"ASN.1 tag class\n\n        Returns\n        -------\n        : :py:class:`int`\n            Tag class\n        \"\"\"\n        return self.__tagClass\n\n    @property\n    def tagFormat(self):\n        \"\"\"ASN.1 tag format\n\n        Returns\n        -------\n        : :py:class:`int`\n            Tag format\n        \"\"\"\n        return self.__tagFormat\n\n    @property\n    def tagId(self):\n        \"\"\"ASN.1 tag ID\n\n        Returns\n        -------\n        : :py:class:`int`\n            Tag ID\n        \"\"\"\n        return self.__tagId\n\n\nclass TagSet(object):\n    \"\"\"Create a collection of ASN.1 tags\n\n    Represents a combination of :class:`~pyasn1.type.tag.Tag` objects\n    that can be attached to a ASN.1 type to make types distinguishable\n    from each other.\n\n    *TagSet* objects are immutable and duck-type Python :class:`tuple` objects\n    holding arbitrary number of :class:`~pyasn1.type.tag.Tag` objects.\n\n    Parameters\n    ----------\n    baseTag: :class:`~pyasn1.type.tag.Tag`\n        Base *Tag* object. This tag survives IMPLICIT tagging.\n\n    *superTags: :class:`~pyasn1.type.tag.Tag`\n        Additional *Tag* objects taking part in subtyping.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class OrderNumber(NumericString):\n            '''\n            ASN.1 specification\n\n            Order-number ::=\n                [APPLICATION 5] IMPLICIT NumericString\n            '''\n            tagSet = NumericString.tagSet.tagImplicitly(\n                Tag(tagClassApplication, tagFormatSimple, 5)\n            )\n\n        orderNumber = OrderNumber('1234')\n    \"\"\"\n    def __init__(self, baseTag=(), *superTags):\n        self.__baseTag = baseTag\n        self.__superTags = superTags\n        self.__superTagsClassId = tuple(\n            [(superTag.tagClass, superTag.tagId) for superTag in superTags]\n        )\n        self.__lenOfSuperTags = len(superTags)\n        self.__hash = hash(self.__superTagsClassId)\n\n    def __repr__(self):\n        representation = '-'.join(['%s:%s:%s' % (x.tagClass, x.tagFormat, x.tagId)\n                                   for x in self.__superTags])\n        if representation:\n            representation = 'tags ' + representation\n        else:\n            representation = 'untagged'\n\n        return '<%s object, %s>' % (self.__class__.__name__, representation)\n\n    def __add__(self, superTag):\n        return self.__class__(self.__baseTag, *self.__superTags + (superTag,))\n\n    def __radd__(self, superTag):\n        return self.__class__(self.__baseTag, *(superTag,) + self.__superTags)\n\n    def __getitem__(self, i):\n        if i.__class__ is slice:\n            return self.__class__(self.__baseTag, *self.__superTags[i])\n        else:\n            return self.__superTags[i]\n\n    def __eq__(self, other):\n        return self.__superTagsClassId == other\n\n    def __ne__(self, other):\n        return self.__superTagsClassId != other\n\n    def __lt__(self, other):\n        return self.__superTagsClassId < other\n\n    def __le__(self, other):\n        return self.__superTagsClassId <= other\n\n    def __gt__(self, other):\n        return self.__superTagsClassId > other\n\n    def __ge__(self, other):\n        return self.__superTagsClassId >= other\n\n    def __hash__(self):\n        return self.__hash\n\n    def __len__(self):\n        return self.__lenOfSuperTags\n\n    @property\n    def baseTag(self):\n        \"\"\"Return base ASN.1 tag\n\n        Returns\n        -------\n        : :class:`~pyasn1.type.tag.Tag`\n            Base tag of this *TagSet*\n        \"\"\"\n        return self.__baseTag\n\n    @property\n    def superTags(self):\n        \"\"\"Return ASN.1 tags\n\n        Returns\n        -------\n        : :py:class:`tuple`\n            Tuple of :class:`~pyasn1.type.tag.Tag` objects that this *TagSet* contains\n        \"\"\"\n        return self.__superTags\n\n    def tagExplicitly(self, superTag):\n        \"\"\"Return explicitly tagged *TagSet*\n\n        Create a new *TagSet* representing callee *TagSet* explicitly tagged\n        with passed tag(s). With explicit tagging mode, new tags are appended\n        to existing tag(s).\n\n        Parameters\n        ----------\n        superTag: :class:`~pyasn1.type.tag.Tag`\n            *Tag* object to tag this *TagSet*\n\n        Returns\n        -------\n        : :class:`~pyasn1.type.tag.TagSet`\n            New *TagSet* object\n        \"\"\"\n        if superTag.tagClass == tagClassUniversal:\n            raise error.PyAsn1Error(\"Can't tag with UNIVERSAL class tag\")\n        if superTag.tagFormat != tagFormatConstructed:\n            superTag = Tag(superTag.tagClass, tagFormatConstructed, superTag.tagId)\n        return self + superTag\n\n    def tagImplicitly(self, superTag):\n        \"\"\"Return implicitly tagged *TagSet*\n\n        Create a new *TagSet* representing callee *TagSet* implicitly tagged\n        with passed tag(s). With implicit tagging mode, new tag(s) replace the\n        last existing tag.\n\n        Parameters\n        ----------\n        superTag: :class:`~pyasn1.type.tag.Tag`\n            *Tag* object to tag this *TagSet*\n\n        Returns\n        -------\n        : :class:`~pyasn1.type.tag.TagSet`\n            New *TagSet* object\n        \"\"\"\n        if self.__superTags:\n            superTag = Tag(superTag.tagClass, self.__superTags[-1].tagFormat, superTag.tagId)\n        return self[:-1] + superTag\n\n    def isSuperTagSetOf(self, tagSet):\n        \"\"\"Test type relationship against given *TagSet*\n\n        The callee is considered to be a supertype of given *TagSet*\n        tag-wise if all tags in *TagSet* are present in the callee and\n        they are in the same order.\n\n        Parameters\n        ----------\n        tagSet: :class:`~pyasn1.type.tag.TagSet`\n            *TagSet* object to evaluate against the callee\n\n        Returns\n        -------\n        : :py:class:`bool`\n            :obj:`True` if callee is a supertype of *tagSet*\n        \"\"\"\n        if len(tagSet) < self.__lenOfSuperTags:\n            return False\n        return self.__superTags == tagSet[:self.__lenOfSuperTags]\n\n    # Backward compatibility\n\n    def getBaseTag(self):\n        return self.__baseTag\n\ndef initTagSet(tag):\n    return TagSet(tag, tag)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/type/tagmap.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nfrom pyasn1 import error\n\n__all__ = ['TagMap']\n\n\nclass TagMap(object):\n    \"\"\"Map *TagSet* objects to ASN.1 types\n\n    Create an object mapping *TagSet* object to ASN.1 type.\n\n    *TagMap* objects are immutable and duck-type read-only Python\n    :class:`dict` objects holding *TagSet* objects as keys and ASN.1\n    type objects as values.\n\n    Parameters\n    ----------\n    presentTypes: :py:class:`dict`\n        Map of :class:`~pyasn1.type.tag.TagSet` to ASN.1 objects considered\n        as being unconditionally present in the *TagMap*.\n\n    skipTypes: :py:class:`dict`\n        A collection of :class:`~pyasn1.type.tag.TagSet` objects considered\n        as absent in the *TagMap* even when *defaultType* is present.\n\n    defaultType: ASN.1 type object\n        An ASN.1 type object callee *TagMap* returns for any *TagSet* key not present\n        in *presentTypes* (unless given key is present in *skipTypes*).\n    \"\"\"\n    def __init__(self, presentTypes=None, skipTypes=None, defaultType=None):\n        self.__presentTypes = presentTypes or {}\n        self.__skipTypes = skipTypes or {}\n        self.__defaultType = defaultType\n\n    def __contains__(self, tagSet):\n        return (tagSet in self.__presentTypes or\n                self.__defaultType is not None and tagSet not in self.__skipTypes)\n\n    def __getitem__(self, tagSet):\n        try:\n            return self.__presentTypes[tagSet]\n        except KeyError:\n            if self.__defaultType is None:\n                raise KeyError()\n            elif tagSet in self.__skipTypes:\n                raise error.PyAsn1Error('Key in negative map')\n            else:\n                return self.__defaultType\n\n    def __iter__(self):\n        return iter(self.__presentTypes)\n\n    def __repr__(self):\n        representation = '%s object' % self.__class__.__name__\n\n        if self.__presentTypes:\n            representation += ', present %s' % repr(self.__presentTypes)\n\n        if self.__skipTypes:\n            representation += ', skip %s' % repr(self.__skipTypes)\n\n        if self.__defaultType is not None:\n            representation += ', default %s' % repr(self.__defaultType)\n\n        return '<%s>' % representation\n\n    @property\n    def presentTypes(self):\n        \"\"\"Return *TagSet* to ASN.1 type map present in callee *TagMap*\"\"\"\n        return self.__presentTypes\n\n    @property\n    def skipTypes(self):\n        \"\"\"Return *TagSet* collection unconditionally absent in callee *TagMap*\"\"\"\n        return self.__skipTypes\n\n    @property\n    def defaultType(self):\n        \"\"\"Return default ASN.1 type being returned for any missing *TagSet*\"\"\"\n        return self.__defaultType\n\n    # Backward compatibility\n\n    def getPosMap(self):\n        return self.presentTypes\n\n    def getNegMap(self):\n        return self.skipTypes\n\n    def getDef(self):\n        return self.defaultType\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/type/univ.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nimport math\nimport sys\n\nfrom pyasn1 import error\nfrom pyasn1.codec.ber import eoo\nfrom pyasn1.compat import binary\nfrom pyasn1.compat import integer\nfrom pyasn1.compat import octets\nfrom pyasn1.type import base\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import tagmap\n\nNoValue = base.NoValue\nnoValue = NoValue()\n\n__all__ = ['Integer', 'Boolean', 'BitString', 'OctetString', 'Null',\n           'ObjectIdentifier', 'Real', 'Enumerated',\n           'SequenceOfAndSetOfBase', 'SequenceOf', 'SetOf',\n           'SequenceAndSetBase', 'Sequence', 'Set', 'Choice', 'Any',\n           'NoValue', 'noValue']\n\n# \"Simple\" ASN.1 types (yet incomplete)\n\n\nclass Integer(base.SimpleAsn1Type):\n    \"\"\"Create |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.SimpleAsn1Type`, its\n    objects are immutable and duck-type Python :class:`int` objects.\n\n    Keyword Args\n    ------------\n    value: :class:`int`, :class:`str` or |ASN.1| object\n        Python :class:`int` or :class:`str` literal or |ASN.1| class\n        instance. If `value` is not given, schema object will be created.\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n        Object representing non-default ASN.1 subtype constraint(s). Constraints\n        verification for |ASN.1| type occurs automatically on object\n        instantiation.\n\n    namedValues: :py:class:`~pyasn1.type.namedval.NamedValues`\n        Object representing non-default symbolic aliases for numbers\n\n    Raises\n    ------\n    ~pyasn1.error.ValueConstraintError, ~pyasn1.error.PyAsn1Error\n        On constraint violation or bad initializer.\n\n    Examples\n    --------\n\n    .. code-block:: python\n\n        class ErrorCode(Integer):\n            '''\n            ASN.1 specification:\n\n            ErrorCode ::=\n                INTEGER { disk-full(1), no-disk(-1),\n                          disk-not-formatted(2) }\n\n            error ErrorCode ::= disk-full\n            '''\n            namedValues = NamedValues(\n                ('disk-full', 1), ('no-disk', -1),\n                ('disk-not-formatted', 2)\n            )\n\n        error = ErrorCode('disk-full')\n    \"\"\"\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 0x02)\n    )\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection()\n\n    #: Default :py:class:`~pyasn1.type.namedval.NamedValues` object\n    #: representing symbolic aliases for numbers\n    namedValues = namedval.NamedValues()\n\n    # Optimization for faster codec lookup\n    typeId = base.SimpleAsn1Type.getTypeId()\n\n    def __init__(self, value=noValue, **kwargs):\n        if 'namedValues' not in kwargs:\n            kwargs['namedValues'] = self.namedValues\n\n        base.SimpleAsn1Type.__init__(self, value, **kwargs)\n\n    def __and__(self, value):\n        return self.clone(self._value & value)\n\n    def __rand__(self, value):\n        return self.clone(value & self._value)\n\n    def __or__(self, value):\n        return self.clone(self._value | value)\n\n    def __ror__(self, value):\n        return self.clone(value | self._value)\n\n    def __xor__(self, value):\n        return self.clone(self._value ^ value)\n\n    def __rxor__(self, value):\n        return self.clone(value ^ self._value)\n\n    def __lshift__(self, value):\n        return self.clone(self._value << value)\n\n    def __rshift__(self, value):\n        return self.clone(self._value >> value)\n\n    def __add__(self, value):\n        return self.clone(self._value + value)\n\n    def __radd__(self, value):\n        return self.clone(value + self._value)\n\n    def __sub__(self, value):\n        return self.clone(self._value - value)\n\n    def __rsub__(self, value):\n        return self.clone(value - self._value)\n\n    def __mul__(self, value):\n        return self.clone(self._value * value)\n\n    def __rmul__(self, value):\n        return self.clone(value * self._value)\n\n    def __mod__(self, value):\n        return self.clone(self._value % value)\n\n    def __rmod__(self, value):\n        return self.clone(value % self._value)\n\n    def __pow__(self, value, modulo=None):\n        return self.clone(pow(self._value, value, modulo))\n\n    def __rpow__(self, value):\n        return self.clone(pow(value, self._value))\n\n    def __floordiv__(self, value):\n        return self.clone(self._value // value)\n\n    def __rfloordiv__(self, value):\n        return self.clone(value // self._value)\n\n    if sys.version_info[0] <= 2:\n        def __div__(self, value):\n            if isinstance(value, float):\n                return Real(self._value / value)\n            else:\n                return self.clone(self._value / value)\n\n        def __rdiv__(self, value):\n            if isinstance(value, float):\n                return Real(value / self._value)\n            else:\n                return self.clone(value / self._value)\n    else:\n        def __truediv__(self, value):\n            return Real(self._value / value)\n\n        def __rtruediv__(self, value):\n            return Real(value / self._value)\n\n        def __divmod__(self, value):\n            return self.clone(divmod(self._value, value))\n\n        def __rdivmod__(self, value):\n            return self.clone(divmod(value, self._value))\n\n        __hash__ = base.SimpleAsn1Type.__hash__\n\n    def __int__(self):\n        return int(self._value)\n\n    if sys.version_info[0] <= 2:\n        def __long__(self):\n            return long(self._value)\n\n    def __float__(self):\n        return float(self._value)\n\n    def __abs__(self):\n        return self.clone(abs(self._value))\n\n    def __index__(self):\n        return int(self._value)\n\n    def __pos__(self):\n        return self.clone(+self._value)\n\n    def __neg__(self):\n        return self.clone(-self._value)\n\n    def __invert__(self):\n        return self.clone(~self._value)\n\n    def __round__(self, n=0):\n        r = round(self._value, n)\n        if n:\n            return self.clone(r)\n        else:\n            return r\n\n    def __floor__(self):\n        return math.floor(self._value)\n\n    def __ceil__(self):\n        return math.ceil(self._value)\n\n    if sys.version_info[0:2] > (2, 5):\n        def __trunc__(self):\n            return self.clone(math.trunc(self._value))\n\n    def __lt__(self, value):\n        return self._value < value\n\n    def __le__(self, value):\n        return self._value <= value\n\n    def __eq__(self, value):\n        return self._value == value\n\n    def __ne__(self, value):\n        return self._value != value\n\n    def __gt__(self, value):\n        return self._value > value\n\n    def __ge__(self, value):\n        return self._value >= value\n\n    def prettyIn(self, value):\n        try:\n            return int(value)\n\n        except ValueError:\n            try:\n                return self.namedValues[value]\n\n            except KeyError:\n                raise error.PyAsn1Error(\n                    'Can\\'t coerce %r into integer: %s' % (value, sys.exc_info()[1])\n                )\n\n    def prettyOut(self, value):\n        try:\n            return str(self.namedValues[value])\n\n        except KeyError:\n            return str(value)\n\n    # backward compatibility\n\n    def getNamedValues(self):\n        return self.namedValues\n\n\nclass Boolean(Integer):\n    \"\"\"Create |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.SimpleAsn1Type`, its\n    objects are immutable and duck-type Python :class:`int` objects.\n\n    Keyword Args\n    ------------\n    value: :class:`int`, :class:`str` or |ASN.1| object\n        Python :class:`int` or :class:`str` literal or |ASN.1| class\n        instance. If `value` is not given, schema object will be created.\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n        Object representing non-default ASN.1 subtype constraint(s).Constraints\n        verification for |ASN.1| type occurs automatically on object\n        instantiation.\n\n    namedValues: :py:class:`~pyasn1.type.namedval.NamedValues`\n        Object representing non-default symbolic aliases for numbers\n\n    Raises\n    ------\n    ~pyasn1.error.ValueConstraintError, ~pyasn1.error.PyAsn1Error\n        On constraint violation or bad initializer.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class RoundResult(Boolean):\n            '''\n            ASN.1 specification:\n\n            RoundResult ::= BOOLEAN\n\n            ok RoundResult ::= TRUE\n            ko RoundResult ::= FALSE\n            '''\n        ok = RoundResult(True)\n        ko = RoundResult(False)\n    \"\"\"\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 0x01),\n    )\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = Integer.subtypeSpec + constraint.SingleValueConstraint(0, 1)\n\n    #: Default :py:class:`~pyasn1.type.namedval.NamedValues` object\n    #: representing symbolic aliases for numbers\n    namedValues = namedval.NamedValues(('False', 0), ('True', 1))\n\n    # Optimization for faster codec lookup\n    typeId = Integer.getTypeId()\n\nif sys.version_info[0] < 3:\n    SizedIntegerBase = long\nelse:\n    SizedIntegerBase = int\n\n\nclass SizedInteger(SizedIntegerBase):\n    bitLength = leadingZeroBits = None\n\n    def setBitLength(self, bitLength):\n        self.bitLength = bitLength\n        self.leadingZeroBits = max(bitLength - integer.bitLength(self), 0)\n        return self\n\n    def __len__(self):\n        if self.bitLength is None:\n            self.setBitLength(integer.bitLength(self))\n\n        return self.bitLength\n\n\nclass BitString(base.SimpleAsn1Type):\n    \"\"\"Create |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.SimpleAsn1Type`, its\n    objects are immutable and duck-type both Python :class:`tuple` (as a tuple\n    of bits) and :class:`int` objects.\n\n    Keyword Args\n    ------------\n    value: :class:`int`, :class:`str` or |ASN.1| object\n        Python :class:`int` or :class:`str` literal representing binary\n        or hexadecimal number or sequence of integer bits or |ASN.1| object.\n        If `value` is not given, schema object will be created.\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n        Object representing non-default ASN.1 subtype constraint(s). Constraints\n        verification for |ASN.1| type occurs automatically on object\n        instantiation.\n\n    namedValues: :py:class:`~pyasn1.type.namedval.NamedValues`\n        Object representing non-default symbolic aliases for numbers\n\n    binValue: :py:class:`str`\n        Binary string initializer to use instead of the *value*.\n        Example: '10110011'.\n\n    hexValue: :py:class:`str`\n        Hexadecimal string initializer to use instead of the *value*.\n        Example: 'DEADBEEF'.\n\n    Raises\n    ------\n    ~pyasn1.error.ValueConstraintError, ~pyasn1.error.PyAsn1Error\n        On constraint violation or bad initializer.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class Rights(BitString):\n            '''\n            ASN.1 specification:\n\n            Rights ::= BIT STRING { user-read(0), user-write(1),\n                                    group-read(2), group-write(3),\n                                    other-read(4), other-write(5) }\n\n            group1 Rights ::= { group-read, group-write }\n            group2 Rights ::= '0011'B\n            group3 Rights ::= '3'H\n            '''\n            namedValues = NamedValues(\n                ('user-read', 0), ('user-write', 1),\n                ('group-read', 2), ('group-write', 3),\n                ('other-read', 4), ('other-write', 5)\n            )\n\n        group1 = Rights(('group-read', 'group-write'))\n        group2 = Rights('0011')\n        group3 = Rights(0x3)\n    \"\"\"\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 0x03)\n    )\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection()\n\n    #: Default :py:class:`~pyasn1.type.namedval.NamedValues` object\n    #: representing symbolic aliases for numbers\n    namedValues = namedval.NamedValues()\n\n    # Optimization for faster codec lookup\n    typeId = base.SimpleAsn1Type.getTypeId()\n\n    defaultBinValue = defaultHexValue = noValue\n\n    def __init__(self, value=noValue, **kwargs):\n        if value is noValue:\n            if kwargs:\n                try:\n                    value = self.fromBinaryString(kwargs.pop('binValue'), internalFormat=True)\n\n                except KeyError:\n                    pass\n\n                try:\n                    value = self.fromHexString(kwargs.pop('hexValue'), internalFormat=True)\n\n                except KeyError:\n                    pass\n\n        if value is noValue:\n            if self.defaultBinValue is not noValue:\n                value = self.fromBinaryString(self.defaultBinValue, internalFormat=True)\n\n            elif self.defaultHexValue is not noValue:\n                value = self.fromHexString(self.defaultHexValue, internalFormat=True)\n\n        if 'namedValues' not in kwargs:\n            kwargs['namedValues'] = self.namedValues\n\n        base.SimpleAsn1Type.__init__(self, value, **kwargs)\n\n    def __str__(self):\n        return self.asBinary()\n\n    def __eq__(self, other):\n        other = self.prettyIn(other)\n        return self is other or self._value == other and len(self._value) == len(other)\n\n    def __ne__(self, other):\n        other = self.prettyIn(other)\n        return self._value != other or len(self._value) != len(other)\n\n    def __lt__(self, other):\n        other = self.prettyIn(other)\n        return len(self._value) < len(other) or len(self._value) == len(other) and self._value < other\n\n    def __le__(self, other):\n        other = self.prettyIn(other)\n        return len(self._value) <= len(other) or len(self._value) == len(other) and self._value <= other\n\n    def __gt__(self, other):\n        other = self.prettyIn(other)\n        return len(self._value) > len(other) or len(self._value) == len(other) and self._value > other\n\n    def __ge__(self, other):\n        other = self.prettyIn(other)\n        return len(self._value) >= len(other) or len(self._value) == len(other) and self._value >= other\n\n    # Immutable sequence object protocol\n\n    def __len__(self):\n        return len(self._value)\n\n    def __getitem__(self, i):\n        if i.__class__ is slice:\n            return self.clone([self[x] for x in range(*i.indices(len(self)))])\n        else:\n            length = len(self._value) - 1\n            if i > length or i < 0:\n                raise IndexError('bit index out of range')\n            return (self._value >> (length - i)) & 1\n\n    def __iter__(self):\n        length = len(self._value)\n        while length:\n            length -= 1\n            yield (self._value >> length) & 1\n\n    def __reversed__(self):\n        return reversed(tuple(self))\n\n    # arithmetic operators\n\n    def __add__(self, value):\n        value = self.prettyIn(value)\n        return self.clone(SizedInteger(self._value << len(value) | value).setBitLength(len(self._value) + len(value)))\n\n    def __radd__(self, value):\n        value = self.prettyIn(value)\n        return self.clone(SizedInteger(value << len(self._value) | self._value).setBitLength(len(self._value) + len(value)))\n\n    def __mul__(self, value):\n        bitString = self._value\n        while value > 1:\n            bitString <<= len(self._value)\n            bitString |= self._value\n            value -= 1\n        return self.clone(bitString)\n\n    def __rmul__(self, value):\n        return self * value\n\n    def __lshift__(self, count):\n        return self.clone(SizedInteger(self._value << count).setBitLength(len(self._value) + count))\n\n    def __rshift__(self, count):\n        return self.clone(SizedInteger(self._value >> count).setBitLength(max(0, len(self._value) - count)))\n\n    def __int__(self):\n        return self._value\n\n    def __float__(self):\n        return float(self._value)\n\n    if sys.version_info[0] < 3:\n        def __long__(self):\n            return self._value\n\n    def asNumbers(self):\n        \"\"\"Get |ASN.1| value as a sequence of 8-bit integers.\n\n        If |ASN.1| object length is not a multiple of 8, result\n        will be left-padded with zeros.\n        \"\"\"\n        return tuple(octets.octs2ints(self.asOctets()))\n\n    def asOctets(self):\n        \"\"\"Get |ASN.1| value as a sequence of octets.\n\n        If |ASN.1| object length is not a multiple of 8, result\n        will be left-padded with zeros.\n        \"\"\"\n        return integer.to_bytes(self._value, length=len(self))\n\n    def asInteger(self):\n        \"\"\"Get |ASN.1| value as a single integer value.\n        \"\"\"\n        return self._value\n\n    def asBinary(self):\n        \"\"\"Get |ASN.1| value as a text string of bits.\n        \"\"\"\n        binString = binary.bin(self._value)[2:]\n        return '0' * (len(self._value) - len(binString)) + binString\n\n    @classmethod\n    def fromHexString(cls, value, internalFormat=False, prepend=None):\n        \"\"\"Create a |ASN.1| object initialized from the hex string.\n\n        Parameters\n        ----------\n        value: :class:`str`\n            Text string like 'DEADBEEF'\n        \"\"\"\n        try:\n            value = SizedInteger(value, 16).setBitLength(len(value) * 4)\n\n        except ValueError:\n            raise error.PyAsn1Error('%s.fromHexString() error: %s' % (cls.__name__, sys.exc_info()[1]))\n\n        if prepend is not None:\n            value = SizedInteger(\n                (SizedInteger(prepend) << len(value)) | value\n            ).setBitLength(len(prepend) + len(value))\n\n        if not internalFormat:\n            value = cls(value)\n\n        return value\n\n    @classmethod\n    def fromBinaryString(cls, value, internalFormat=False, prepend=None):\n        \"\"\"Create a |ASN.1| object initialized from a string of '0' and '1'.\n\n        Parameters\n        ----------\n        value: :class:`str`\n            Text string like '1010111'\n        \"\"\"\n        try:\n            value = SizedInteger(value or '0', 2).setBitLength(len(value))\n\n        except ValueError:\n            raise error.PyAsn1Error('%s.fromBinaryString() error: %s' % (cls.__name__, sys.exc_info()[1]))\n\n        if prepend is not None:\n            value = SizedInteger(\n                (SizedInteger(prepend) << len(value)) | value\n            ).setBitLength(len(prepend) + len(value))\n\n        if not internalFormat:\n            value = cls(value)\n\n        return value\n\n    @classmethod\n    def fromOctetString(cls, value, internalFormat=False, prepend=None, padding=0):\n        \"\"\"Create a |ASN.1| object initialized from a string.\n\n        Parameters\n        ----------\n        value: :class:`str` (Py2) or :class:`bytes` (Py3)\n            Text string like '\\\\\\\\x01\\\\\\\\xff' (Py2) or b'\\\\\\\\x01\\\\\\\\xff' (Py3)\n        \"\"\"\n        value = SizedInteger(integer.from_bytes(value) >> padding).setBitLength(len(value) * 8 - padding)\n\n        if prepend is not None:\n            value = SizedInteger(\n                (SizedInteger(prepend) << len(value)) | value\n            ).setBitLength(len(prepend) + len(value))\n\n        if not internalFormat:\n            value = cls(value)\n\n        return value\n\n    def prettyIn(self, value):\n        if isinstance(value, SizedInteger):\n            return value\n        elif octets.isStringType(value):\n            if not value:\n                return SizedInteger(0).setBitLength(0)\n\n            elif value[0] == '\\'':  # \"'1011'B\" -- ASN.1 schema representation (deprecated)\n                if value[-2:] == '\\'B':\n                    return self.fromBinaryString(value[1:-2], internalFormat=True)\n                elif value[-2:] == '\\'H':\n                    return self.fromHexString(value[1:-2], internalFormat=True)\n                else:\n                    raise error.PyAsn1Error(\n                        'Bad BIT STRING value notation %s' % (value,)\n                    )\n\n            elif self.namedValues and not value.isdigit():  # named bits like 'Urgent, Active'\n                names = [x.strip() for x in value.split(',')]\n\n                try:\n\n                    bitPositions = [self.namedValues[name] for name in names]\n\n                except KeyError:\n                    raise error.PyAsn1Error('unknown bit name(s) in %r' % (names,))\n\n                rightmostPosition = max(bitPositions)\n\n                number = 0\n                for bitPosition in bitPositions:\n                    number |= 1 << (rightmostPosition - bitPosition)\n\n                return SizedInteger(number).setBitLength(rightmostPosition + 1)\n\n            elif value.startswith('0x'):\n                return self.fromHexString(value[2:], internalFormat=True)\n\n            elif value.startswith('0b'):\n                return self.fromBinaryString(value[2:], internalFormat=True)\n\n            else:  # assume plain binary string like '1011'\n                return self.fromBinaryString(value, internalFormat=True)\n\n        elif isinstance(value, (tuple, list)):\n            return self.fromBinaryString(''.join([b and '1' or '0' for b in value]), internalFormat=True)\n\n        elif isinstance(value, BitString):\n            return SizedInteger(value).setBitLength(len(value))\n\n        elif isinstance(value, intTypes):\n            return SizedInteger(value)\n\n        else:\n            raise error.PyAsn1Error(\n                'Bad BitString initializer type \\'%s\\'' % (value,)\n            )\n\n\ntry:\n    # noinspection PyStatementEffect\n    all\n\nexcept NameError:  # Python 2.4\n    # noinspection PyShadowingBuiltins\n    def all(iterable):\n        for element in iterable:\n            if not element:\n                return False\n        return True\n\n\nclass OctetString(base.SimpleAsn1Type):\n    \"\"\"Create |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.SimpleAsn1Type`, its\n    objects are immutable and duck-type Python 2 :class:`str` or\n    Python 3 :class:`bytes`. When used in Unicode context, |ASN.1| type\n    assumes \"|encoding|\" serialisation.\n\n    Keyword Args\n    ------------\n    value: :class:`unicode`, :class:`str`, :class:`bytes` or |ASN.1| object\n        class:`str` (Python 2) or :class:`bytes` (Python 3), alternatively\n        class:`unicode` object (Python 2) or :class:`str` (Python 3)\n        representing character string to be serialised into octets\n        (note `encoding` parameter) or |ASN.1| object.\n        If `value` is not given, schema object will be created.\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n        Object representing non-default ASN.1 subtype constraint(s). Constraints\n        verification for |ASN.1| type occurs automatically on object\n        instantiation.\n\n    encoding: :py:class:`str`\n        Unicode codec ID to encode/decode :class:`unicode` (Python 2) or\n        :class:`str` (Python 3) the payload when |ASN.1| object is used\n        in text string context.\n\n    binValue: :py:class:`str`\n        Binary string initializer to use instead of the *value*.\n        Example: '10110011'.\n\n    hexValue: :py:class:`str`\n        Hexadecimal string initializer to use instead of the *value*.\n        Example: 'DEADBEEF'.\n\n    Raises\n    ------\n    ~pyasn1.error.ValueConstraintError, ~pyasn1.error.PyAsn1Error\n        On constraint violation or bad initializer.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class Icon(OctetString):\n            '''\n            ASN.1 specification:\n\n            Icon ::= OCTET STRING\n\n            icon1 Icon ::= '001100010011001000110011'B\n            icon2 Icon ::= '313233'H\n            '''\n        icon1 = Icon.fromBinaryString('001100010011001000110011')\n        icon2 = Icon.fromHexString('313233')\n    \"\"\"\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 0x04)\n    )\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection()\n\n    # Optimization for faster codec lookup\n    typeId = base.SimpleAsn1Type.getTypeId()\n\n    defaultBinValue = defaultHexValue = noValue\n    encoding = 'iso-8859-1'\n\n    def __init__(self, value=noValue, **kwargs):\n        if kwargs:\n            if value is noValue:\n                try:\n                    value = self.fromBinaryString(kwargs.pop('binValue'))\n\n                except KeyError:\n                    pass\n\n                try:\n                    value = self.fromHexString(kwargs.pop('hexValue'))\n\n                except KeyError:\n                    pass\n\n        if value is noValue:\n            if self.defaultBinValue is not noValue:\n                value = self.fromBinaryString(self.defaultBinValue)\n\n            elif self.defaultHexValue is not noValue:\n                value = self.fromHexString(self.defaultHexValue)\n\n        if 'encoding' not in kwargs:\n            kwargs['encoding'] = self.encoding\n\n        base.SimpleAsn1Type.__init__(self, value, **kwargs)\n\n    if sys.version_info[0] <= 2:\n        def prettyIn(self, value):\n            if isinstance(value, str):\n                return value\n\n            elif isinstance(value, unicode):\n                try:\n                    return value.encode(self.encoding)\n\n                except (LookupError, UnicodeEncodeError):\n                    exc = sys.exc_info()[1]\n                    raise error.PyAsn1UnicodeEncodeError(\n                        \"Can't encode string '%s' with codec \"\n                        \"%s\" % (value, self.encoding), exc\n                    )\n\n            elif isinstance(value, (tuple, list)):\n                try:\n                    return ''.join([chr(x) for x in value])\n\n                except ValueError:\n                    raise error.PyAsn1Error(\n                        \"Bad %s initializer '%s'\" % (self.__class__.__name__, value)\n                    )\n\n            else:\n                return str(value)\n\n        def __str__(self):\n            return str(self._value)\n\n        def __unicode__(self):\n            try:\n                return self._value.decode(self.encoding)\n\n            except UnicodeDecodeError:\n                exc = sys.exc_info()[1]\n                raise error.PyAsn1UnicodeDecodeError(\n                    \"Can't decode string '%s' with codec \"\n                    \"%s\" % (self._value, self.encoding), exc\n                )\n\n        def asOctets(self):\n            return str(self._value)\n\n        def asNumbers(self):\n            return tuple([ord(x) for x in self._value])\n\n    else:\n        def prettyIn(self, value):\n            if isinstance(value, bytes):\n                return value\n\n            elif isinstance(value, str):\n                try:\n                    return value.encode(self.encoding)\n\n                except UnicodeEncodeError:\n                    exc = sys.exc_info()[1]\n                    raise error.PyAsn1UnicodeEncodeError(\n                        \"Can't encode string '%s' with '%s' \"\n                        \"codec\" % (value, self.encoding), exc\n                    )\n            elif isinstance(value, OctetString):  # a shortcut, bytes() would work the same way\n                return value.asOctets()\n\n            elif isinstance(value, base.SimpleAsn1Type):  # this mostly targets Integer objects\n                return self.prettyIn(str(value))\n\n            elif isinstance(value, (tuple, list)):\n                return self.prettyIn(bytes(value))\n\n            else:\n                return bytes(value)\n\n        def __str__(self):\n            try:\n                return self._value.decode(self.encoding)\n\n            except UnicodeDecodeError:\n                exc = sys.exc_info()[1]\n                raise error.PyAsn1UnicodeDecodeError(\n                    \"Can't decode string '%s' with '%s' codec at \"\n                    \"'%s'\" % (self._value, self.encoding,\n                              self.__class__.__name__), exc\n                )\n\n        def __bytes__(self):\n            return bytes(self._value)\n\n        def asOctets(self):\n            return bytes(self._value)\n\n        def asNumbers(self):\n            return tuple(self._value)\n\n    #\n    # Normally, `.prettyPrint()` is called from `__str__()`. Historically,\n    # OctetString.prettyPrint() used to return hexified payload\n    # representation in cases when non-printable content is present. At the\n    # same time `str()` used to produce either octet-stream (Py2) or\n    # text (Py3) representations.\n    #\n    # Therefore `OctetString.__str__()` -> `.prettyPrint()` call chain is\n    # reversed to preserve the original behaviour.\n    #\n    # Eventually we should deprecate `.prettyPrint()` / `.prettyOut()` harness\n    # and end up with just `__str__()` producing hexified representation while\n    # both text and octet-stream representation should only be requested via\n    # the `.asOctets()` method.\n    #\n    # Note: ASN.1 OCTET STRING is never mean to contain text!\n    #\n\n    def prettyOut(self, value):\n        return value\n\n    def prettyPrint(self, scope=0):\n        # first see if subclass has its own .prettyOut()\n        value = self.prettyOut(self._value)\n\n        if value is not self._value:\n            return value\n\n        numbers = self.asNumbers()\n\n        for x in numbers:\n            # hexify if needed\n            if x < 32 or x > 126:\n                return '0x' + ''.join(('%.2x' % x for x in numbers))\n        else:\n            # this prevents infinite recursion\n            return OctetString.__str__(self)\n\n    @staticmethod\n    def fromBinaryString(value):\n        \"\"\"Create a |ASN.1| object initialized from a string of '0' and '1'.\n\n        Parameters\n        ----------\n        value: :class:`str`\n            Text string like '1010111'\n        \"\"\"\n        bitNo = 8\n        byte = 0\n        r = []\n        for v in value:\n            if bitNo:\n                bitNo -= 1\n            else:\n                bitNo = 7\n                r.append(byte)\n                byte = 0\n            if v in ('0', '1'):\n                v = int(v)\n            else:\n                raise error.PyAsn1Error(\n                    'Non-binary OCTET STRING initializer %s' % (v,)\n                )\n            byte |= v << bitNo\n\n        r.append(byte)\n\n        return octets.ints2octs(r)\n\n    @staticmethod\n    def fromHexString(value):\n        \"\"\"Create a |ASN.1| object initialized from the hex string.\n\n        Parameters\n        ----------\n        value: :class:`str`\n            Text string like 'DEADBEEF'\n        \"\"\"\n        r = []\n        p = []\n        for v in value:\n            if p:\n                r.append(int(p + v, 16))\n                p = None\n            else:\n                p = v\n        if p:\n            r.append(int(p + '0', 16))\n\n        return octets.ints2octs(r)\n\n    # Immutable sequence object protocol\n\n    def __len__(self):\n        return len(self._value)\n\n    def __getitem__(self, i):\n        if i.__class__ is slice:\n            return self.clone(self._value[i])\n        else:\n            return self._value[i]\n\n    def __iter__(self):\n        return iter(self._value)\n\n    def __contains__(self, value):\n        return value in self._value\n\n    def __add__(self, value):\n        return self.clone(self._value + self.prettyIn(value))\n\n    def __radd__(self, value):\n        return self.clone(self.prettyIn(value) + self._value)\n\n    def __mul__(self, value):\n        return self.clone(self._value * value)\n\n    def __rmul__(self, value):\n        return self * value\n\n    def __int__(self):\n        return int(self._value)\n\n    def __float__(self):\n        return float(self._value)\n\n    def __reversed__(self):\n        return reversed(self._value)\n\n\nclass Null(OctetString):\n    \"\"\"Create |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.SimpleAsn1Type`, its\n    objects are immutable and duck-type Python :class:`str` objects\n    (always empty).\n\n    Keyword Args\n    ------------\n    value: :class:`str` or |ASN.1| object\n        Python empty :class:`str` literal or any object that evaluates to :obj:`False`\n        If `value` is not given, schema object will be created.\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    Raises\n    ------\n    ~pyasn1.error.ValueConstraintError, ~pyasn1.error.PyAsn1Error\n        On constraint violation or bad initializer.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class Ack(Null):\n            '''\n            ASN.1 specification:\n\n            Ack ::= NULL\n            '''\n        ack = Ack('')\n    \"\"\"\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 0x05)\n    )\n    subtypeSpec = OctetString.subtypeSpec + constraint.SingleValueConstraint(octets.str2octs(''))\n\n    # Optimization for faster codec lookup\n    typeId = OctetString.getTypeId()\n\n    def prettyIn(self, value):\n        if value:\n            return value\n\n        return octets.str2octs('')\n\nif sys.version_info[0] <= 2:\n    intTypes = (int, long)\nelse:\n    intTypes = (int,)\n\nnumericTypes = intTypes + (float,)\n\n\nclass ObjectIdentifier(base.SimpleAsn1Type):\n    \"\"\"Create |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.SimpleAsn1Type`, its\n    objects are immutable and duck-type Python :class:`tuple` objects\n    (tuple of non-negative integers).\n\n    Keyword Args\n    ------------\n    value: :class:`tuple`, :class:`str` or |ASN.1| object\n        Python sequence of :class:`int` or :class:`str` literal or |ASN.1| object.\n        If `value` is not given, schema object will be created.\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n        Object representing non-default ASN.1 subtype constraint(s). Constraints\n        verification for |ASN.1| type occurs automatically on object\n        instantiation.\n\n    Raises\n    ------\n    ~pyasn1.error.ValueConstraintError, ~pyasn1.error.PyAsn1Error\n        On constraint violation or bad initializer.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class ID(ObjectIdentifier):\n            '''\n            ASN.1 specification:\n\n            ID ::= OBJECT IDENTIFIER\n\n            id-edims ID ::= { joint-iso-itu-t mhs-motif(6) edims(7) }\n            id-bp ID ::= { id-edims 11 }\n            '''\n        id_edims = ID('2.6.7')\n        id_bp = id_edims + (11,)\n    \"\"\"\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 0x06)\n    )\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection()\n\n    # Optimization for faster codec lookup\n    typeId = base.SimpleAsn1Type.getTypeId()\n\n    def __add__(self, other):\n        return self.clone(self._value + other)\n\n    def __radd__(self, other):\n        return self.clone(other + self._value)\n\n    def asTuple(self):\n        return self._value\n\n    # Sequence object protocol\n\n    def __len__(self):\n        return len(self._value)\n\n    def __getitem__(self, i):\n        if i.__class__ is slice:\n            return self.clone(self._value[i])\n        else:\n            return self._value[i]\n\n    def __iter__(self):\n        return iter(self._value)\n\n    def __contains__(self, value):\n        return value in self._value\n\n    def index(self, suboid):\n        return self._value.index(suboid)\n\n    def isPrefixOf(self, other):\n        \"\"\"Indicate if this |ASN.1| object is a prefix of other |ASN.1| object.\n\n        Parameters\n        ----------\n        other: |ASN.1| object\n            |ASN.1| object\n\n        Returns\n        -------\n        : :class:`bool`\n            :obj:`True` if this |ASN.1| object is a parent (e.g. prefix) of the other |ASN.1| object\n            or :obj:`False` otherwise.\n        \"\"\"\n        l = len(self)\n        if l <= len(other):\n            if self._value[:l] == other[:l]:\n                return True\n        return False\n\n    def prettyIn(self, value):\n        if isinstance(value, ObjectIdentifier):\n            return tuple(value)\n        elif octets.isStringType(value):\n            if '-' in value:\n                raise error.PyAsn1Error(\n                    'Malformed Object ID %s at %s: %s' % (value, self.__class__.__name__, sys.exc_info()[1])\n                )\n            try:\n                return tuple([int(subOid) for subOid in value.split('.') if subOid])\n            except ValueError:\n                raise error.PyAsn1Error(\n                    'Malformed Object ID %s at %s: %s' % (value, self.__class__.__name__, sys.exc_info()[1])\n                )\n\n        try:\n            tupleOfInts = tuple([int(subOid) for subOid in value if subOid >= 0])\n\n        except (ValueError, TypeError):\n            raise error.PyAsn1Error(\n                'Malformed Object ID %s at %s: %s' % (value, self.__class__.__name__, sys.exc_info()[1])\n            )\n\n        if len(tupleOfInts) == len(value):\n            return tupleOfInts\n\n        raise error.PyAsn1Error('Malformed Object ID %s at %s' % (value, self.__class__.__name__))\n\n    def prettyOut(self, value):\n        return '.'.join([str(x) for x in value])\n\n\nclass Real(base.SimpleAsn1Type):\n    \"\"\"Create |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.SimpleAsn1Type`, its\n    objects are immutable and duck-type Python :class:`float` objects.\n    Additionally, |ASN.1| objects behave like a :class:`tuple` in which case its\n    elements are mantissa, base and exponent.\n\n    Keyword Args\n    ------------\n    value: :class:`tuple`, :class:`float` or |ASN.1| object\n        Python sequence of :class:`int` (representing mantissa, base and\n        exponent) or :class:`float` instance or |ASN.1| object.\n        If `value` is not given, schema object will be created.\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n        Object representing non-default ASN.1 subtype constraint(s). Constraints\n        verification for |ASN.1| type occurs automatically on object\n        instantiation.\n\n    Raises\n    ------\n    ~pyasn1.error.ValueConstraintError, ~pyasn1.error.PyAsn1Error\n        On constraint violation or bad initializer.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class Pi(Real):\n            '''\n            ASN.1 specification:\n\n            Pi ::= REAL\n\n            pi Pi ::= { mantissa 314159, base 10, exponent -5 }\n\n            '''\n        pi = Pi((314159, 10, -5))\n    \"\"\"\n    binEncBase = None  # binEncBase = 16 is recommended for large numbers\n\n    try:\n        _plusInf = float('inf')\n        _minusInf = float('-inf')\n        _inf = _plusInf, _minusInf\n\n    except ValueError:\n        # Infinity support is platform and Python dependent\n        _plusInf = _minusInf = None\n        _inf = ()\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 0x09)\n    )\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection()\n\n    # Optimization for faster codec lookup\n    typeId = base.SimpleAsn1Type.getTypeId()\n\n    @staticmethod\n    def __normalizeBase10(value):\n        m, b, e = value\n        while m and m % 10 == 0:\n            m /= 10\n            e += 1\n        return m, b, e\n\n    def prettyIn(self, value):\n        if isinstance(value, tuple) and len(value) == 3:\n            if (not isinstance(value[0], numericTypes) or\n                    not isinstance(value[1], intTypes) or\n                    not isinstance(value[2], intTypes)):\n                raise error.PyAsn1Error('Lame Real value syntax: %s' % (value,))\n            if (isinstance(value[0], float) and\n                    self._inf and value[0] in self._inf):\n                return value[0]\n            if value[1] not in (2, 10):\n                raise error.PyAsn1Error(\n                    'Prohibited base for Real value: %s' % (value[1],)\n                )\n            if value[1] == 10:\n                value = self.__normalizeBase10(value)\n            return value\n        elif isinstance(value, intTypes):\n            return self.__normalizeBase10((value, 10, 0))\n        elif isinstance(value, float) or octets.isStringType(value):\n            if octets.isStringType(value):\n                try:\n                    value = float(value)\n                except ValueError:\n                    raise error.PyAsn1Error(\n                        'Bad real value syntax: %s' % (value,)\n                    )\n            if self._inf and value in self._inf:\n                return value\n            else:\n                e = 0\n                while int(value) != value:\n                    value *= 10\n                    e -= 1\n                return self.__normalizeBase10((int(value), 10, e))\n        elif isinstance(value, Real):\n            return tuple(value)\n        raise error.PyAsn1Error(\n            'Bad real value syntax: %s' % (value,)\n        )\n\n    def prettyPrint(self, scope=0):\n        try:\n            return self.prettyOut(float(self))\n\n        except OverflowError:\n            return '<overflow>'\n\n    @property\n    def isPlusInf(self):\n        \"\"\"Indicate PLUS-INFINITY object value\n\n        Returns\n        -------\n        : :class:`bool`\n            :obj:`True` if calling object represents plus infinity\n            or :obj:`False` otherwise.\n\n        \"\"\"\n        return self._value == self._plusInf\n\n    @property\n    def isMinusInf(self):\n        \"\"\"Indicate MINUS-INFINITY object value\n\n        Returns\n        -------\n        : :class:`bool`\n            :obj:`True` if calling object represents minus infinity\n            or :obj:`False` otherwise.\n        \"\"\"\n        return self._value == self._minusInf\n\n    @property\n    def isInf(self):\n        return self._value in self._inf\n\n    def __add__(self, value):\n        return self.clone(float(self) + value)\n\n    def __radd__(self, value):\n        return self + value\n\n    def __mul__(self, value):\n        return self.clone(float(self) * value)\n\n    def __rmul__(self, value):\n        return self * value\n\n    def __sub__(self, value):\n        return self.clone(float(self) - value)\n\n    def __rsub__(self, value):\n        return self.clone(value - float(self))\n\n    def __mod__(self, value):\n        return self.clone(float(self) % value)\n\n    def __rmod__(self, value):\n        return self.clone(value % float(self))\n\n    def __pow__(self, value, modulo=None):\n        return self.clone(pow(float(self), value, modulo))\n\n    def __rpow__(self, value):\n        return self.clone(pow(value, float(self)))\n\n    if sys.version_info[0] <= 2:\n        def __div__(self, value):\n            return self.clone(float(self) / value)\n\n        def __rdiv__(self, value):\n            return self.clone(value / float(self))\n    else:\n        def __truediv__(self, value):\n            return self.clone(float(self) / value)\n\n        def __rtruediv__(self, value):\n            return self.clone(value / float(self))\n\n        def __divmod__(self, value):\n            return self.clone(float(self) // value)\n\n        def __rdivmod__(self, value):\n            return self.clone(value // float(self))\n\n    def __int__(self):\n        return int(float(self))\n\n    if sys.version_info[0] <= 2:\n        def __long__(self):\n            return long(float(self))\n\n    def __float__(self):\n        if self._value in self._inf:\n            return self._value\n        else:\n            return float(\n                self._value[0] * pow(self._value[1], self._value[2])\n            )\n\n    def __abs__(self):\n        return self.clone(abs(float(self)))\n\n    def __pos__(self):\n        return self.clone(+float(self))\n\n    def __neg__(self):\n        return self.clone(-float(self))\n\n    def __round__(self, n=0):\n        r = round(float(self), n)\n        if n:\n            return self.clone(r)\n        else:\n            return r\n\n    def __floor__(self):\n        return self.clone(math.floor(float(self)))\n\n    def __ceil__(self):\n        return self.clone(math.ceil(float(self)))\n\n    if sys.version_info[0:2] > (2, 5):\n        def __trunc__(self):\n            return self.clone(math.trunc(float(self)))\n\n    def __lt__(self, value):\n        return float(self) < value\n\n    def __le__(self, value):\n        return float(self) <= value\n\n    def __eq__(self, value):\n        return float(self) == value\n\n    def __ne__(self, value):\n        return float(self) != value\n\n    def __gt__(self, value):\n        return float(self) > value\n\n    def __ge__(self, value):\n        return float(self) >= value\n\n    if sys.version_info[0] <= 2:\n        def __nonzero__(self):\n            return bool(float(self))\n    else:\n        def __bool__(self):\n            return bool(float(self))\n\n        __hash__ = base.SimpleAsn1Type.__hash__\n\n    def __getitem__(self, idx):\n        if self._value in self._inf:\n            raise error.PyAsn1Error('Invalid infinite value operation')\n        else:\n            return self._value[idx]\n\n    # compatibility stubs\n\n    def isPlusInfinity(self):\n        return self.isPlusInf\n\n    def isMinusInfinity(self):\n        return self.isMinusInf\n\n    def isInfinity(self):\n        return self.isInf\n\n\nclass Enumerated(Integer):\n    \"\"\"Create |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.SimpleAsn1Type`, its\n    objects are immutable and duck-type Python :class:`int` objects.\n\n    Keyword Args\n    ------------\n    value: :class:`int`, :class:`str` or |ASN.1| object\n        Python :class:`int` or :class:`str` literal or |ASN.1| object.\n        If `value` is not given, schema object will be created.\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n        Object representing non-default ASN.1 subtype constraint(s). Constraints\n        verification for |ASN.1| type occurs automatically on object\n        instantiation.\n\n    namedValues: :py:class:`~pyasn1.type.namedval.NamedValues`\n        Object representing non-default symbolic aliases for numbers\n\n    Raises\n    ------\n    ~pyasn1.error.ValueConstraintError, ~pyasn1.error.PyAsn1Error\n        On constraint violation or bad initializer.\n\n    Examples\n    --------\n\n    .. code-block:: python\n\n        class RadioButton(Enumerated):\n            '''\n            ASN.1 specification:\n\n            RadioButton ::= ENUMERATED { button1(0), button2(1),\n                                         button3(2) }\n\n            selected-by-default RadioButton ::= button1\n            '''\n            namedValues = NamedValues(\n                ('button1', 0), ('button2', 1),\n                ('button3', 2)\n            )\n\n        selected_by_default = RadioButton('button1')\n    \"\"\"\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 0x0A)\n    )\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection()\n\n    # Optimization for faster codec lookup\n    typeId = Integer.getTypeId()\n\n    #: Default :py:class:`~pyasn1.type.namedval.NamedValues` object\n    #: representing symbolic aliases for numbers\n    namedValues = namedval.NamedValues()\n\n\n# \"Structured\" ASN.1 types\n\nclass SequenceOfAndSetOfBase(base.ConstructedAsn1Type):\n    \"\"\"Create |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.ConstructedAsn1Type`,\n    its objects are mutable and duck-type Python :class:`list` objects.\n\n    Keyword Args\n    ------------\n    componentType : :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n        A pyasn1 object representing ASN.1 type allowed within |ASN.1| type\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n        Object representing non-default ASN.1 subtype constraint(s). Constraints\n        verification for |ASN.1| type can only occur on explicit\n        `.isInconsistent` call.\n\n    Examples\n    --------\n\n    .. code-block:: python\n\n        class LotteryDraw(SequenceOf):  #  SetOf is similar\n            '''\n            ASN.1 specification:\n\n            LotteryDraw ::= SEQUENCE OF INTEGER\n            '''\n            componentType = Integer()\n\n        lotteryDraw = LotteryDraw()\n        lotteryDraw.extend([123, 456, 789])\n    \"\"\"\n    def __init__(self, *args, **kwargs):\n        # support positional params for backward compatibility\n        if args:\n            for key, value in zip(('componentType', 'tagSet',\n                                   'subtypeSpec'), args):\n                if key in kwargs:\n                    raise error.PyAsn1Error('Conflicting positional and keyword params!')\n                kwargs['componentType'] = value\n\n        self._componentValues = noValue\n\n        base.ConstructedAsn1Type.__init__(self, **kwargs)\n\n    # Python list protocol\n\n    def __getitem__(self, idx):\n        try:\n            return self.getComponentByPosition(idx)\n\n        except error.PyAsn1Error:\n            raise IndexError(sys.exc_info()[1])\n\n    def __setitem__(self, idx, value):\n        try:\n            self.setComponentByPosition(idx, value)\n\n        except error.PyAsn1Error:\n            raise IndexError(sys.exc_info()[1])\n\n    def append(self, value):\n        if self._componentValues is noValue:\n            pos = 0\n\n        else:\n            pos = len(self._componentValues)\n\n        self[pos] = value\n\n    def count(self, value):\n        return list(self._componentValues.values()).count(value)\n\n    def extend(self, values):\n        for value in values:\n            self.append(value)\n\n        if self._componentValues is noValue:\n            self._componentValues = {}\n\n    def index(self, value, start=0, stop=None):\n        if stop is None:\n            stop = len(self)\n\n        indices, values = zip(*self._componentValues.items())\n\n        # TODO: remove when Py2.5 support is gone\n        values = list(values)\n\n        try:\n            return indices[values.index(value, start, stop)]\n\n        except error.PyAsn1Error:\n            raise ValueError(sys.exc_info()[1])\n\n    def reverse(self):\n        self._componentValues.reverse()\n\n    def sort(self, key=None, reverse=False):\n        self._componentValues = dict(\n            enumerate(sorted(self._componentValues.values(),\n                             key=key, reverse=reverse)))\n\n    def __len__(self):\n        if self._componentValues is noValue or not self._componentValues:\n            return 0\n\n        return max(self._componentValues) + 1\n\n    def __iter__(self):\n        for idx in range(0, len(self)):\n            yield self.getComponentByPosition(idx)\n\n    def _cloneComponentValues(self, myClone, cloneValueFlag):\n        for idx, componentValue in self._componentValues.items():\n            if componentValue is not noValue:\n                if isinstance(componentValue, base.ConstructedAsn1Type):\n                    myClone.setComponentByPosition(\n                        idx, componentValue.clone(cloneValueFlag=cloneValueFlag)\n                    )\n                else:\n                    myClone.setComponentByPosition(idx, componentValue.clone())\n\n    def getComponentByPosition(self, idx, default=noValue, instantiate=True):\n        \"\"\"Return |ASN.1| type component value by position.\n\n        Equivalent to Python sequence subscription operation (e.g. `[]`).\n\n        Parameters\n        ----------\n        idx : :class:`int`\n            Component index (zero-based). Must either refer to an existing\n            component or to N+1 component (if *componentType* is set). In the latter\n            case a new component type gets instantiated and appended to the |ASN.1|\n            sequence.\n\n        Keyword Args\n        ------------\n        default: :class:`object`\n            If set and requested component is a schema object, return the `default`\n            object instead of the requested component.\n\n        instantiate: :class:`bool`\n            If :obj:`True` (default), inner component will be automatically instantiated.\n            If :obj:`False` either existing component or the :class:`NoValue` object will be\n            returned.\n\n        Returns\n        -------\n        : :py:class:`~pyasn1.type.base.PyAsn1Item`\n            Instantiate |ASN.1| component type or return existing component value\n\n        Examples\n        --------\n\n        .. code-block:: python\n\n            # can also be SetOf\n            class MySequenceOf(SequenceOf):\n                componentType = OctetString()\n\n            s = MySequenceOf()\n\n            # returns component #0 with `.isValue` property False\n            s.getComponentByPosition(0)\n\n            # returns None\n            s.getComponentByPosition(0, default=None)\n\n            s.clear()\n\n            # returns noValue\n            s.getComponentByPosition(0, instantiate=False)\n\n            # sets component #0 to OctetString() ASN.1 schema\n            # object and returns it\n            s.getComponentByPosition(0, instantiate=True)\n\n            # sets component #0 to ASN.1 value object\n            s.setComponentByPosition(0, 'ABCD')\n\n            # returns OctetString('ABCD') value object\n            s.getComponentByPosition(0, instantiate=False)\n\n            s.clear()\n\n            # returns noValue\n            s.getComponentByPosition(0, instantiate=False)\n        \"\"\"\n        if isinstance(idx, slice):\n            indices = tuple(range(len(self)))\n            return [self.getComponentByPosition(subidx, default, instantiate)\n                    for subidx in indices[idx]]\n\n        if idx < 0:\n            idx = len(self) + idx\n            if idx < 0:\n                raise error.PyAsn1Error(\n                    'SequenceOf/SetOf index is out of range')\n\n        try:\n            componentValue = self._componentValues[idx]\n\n        except (KeyError, error.PyAsn1Error):\n            if not instantiate:\n                return default\n\n            self.setComponentByPosition(idx)\n\n            componentValue = self._componentValues[idx]\n\n        if default is noValue or componentValue.isValue:\n            return componentValue\n        else:\n            return default\n\n    def setComponentByPosition(self, idx, value=noValue,\n                               verifyConstraints=True,\n                               matchTags=True,\n                               matchConstraints=True):\n        \"\"\"Assign |ASN.1| type component by position.\n\n        Equivalent to Python sequence item assignment operation (e.g. `[]`)\n        or list.append() (when idx == len(self)).\n\n        Parameters\n        ----------\n        idx: :class:`int`\n            Component index (zero-based). Must either refer to existing\n            component or to N+1 component. In the latter case a new component\n            type gets instantiated (if *componentType* is set, or given ASN.1\n            object is taken otherwise) and appended to the |ASN.1| sequence.\n\n        Keyword Args\n        ------------\n        value: :class:`object` or :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n            A Python value to initialize |ASN.1| component with (if *componentType* is set)\n            or ASN.1 value object to assign to |ASN.1| component.\n            If `value` is not given, schema object will be set as a component.\n\n        verifyConstraints: :class:`bool`\n             If :obj:`False`, skip constraints validation\n\n        matchTags: :class:`bool`\n             If :obj:`False`, skip component tags matching\n\n        matchConstraints: :class:`bool`\n             If :obj:`False`, skip component constraints matching\n\n        Returns\n        -------\n        self\n\n        Raises\n        ------\n        ~pyasn1.error.ValueConstraintError, ~pyasn1.error.PyAsn1Error\n            On constraint violation or bad initializer\n        IndexError\n            When idx > len(self)\n        \"\"\"\n        if isinstance(idx, slice):\n            indices = tuple(range(len(self)))\n            startIdx = indices and indices[idx][0] or 0\n            for subIdx, subValue in enumerate(value):\n                self.setComponentByPosition(\n                    startIdx + subIdx, subValue, verifyConstraints,\n                    matchTags, matchConstraints)\n            return self\n\n        if idx < 0:\n            idx = len(self) + idx\n            if idx < 0:\n                raise error.PyAsn1Error(\n                    'SequenceOf/SetOf index is out of range')\n\n        componentType = self.componentType\n\n        if self._componentValues is noValue:\n            componentValues = {}\n\n        else:\n            componentValues = self._componentValues\n\n        currentValue = componentValues.get(idx, noValue)\n\n        if value is noValue:\n            if componentType is not None:\n                value = componentType.clone()\n\n            elif currentValue is noValue:\n                raise error.PyAsn1Error('Component type not defined')\n\n        elif not isinstance(value, base.Asn1Item):\n            if (componentType is not None and\n                    isinstance(componentType, base.SimpleAsn1Type)):\n                value = componentType.clone(value=value)\n\n            elif (currentValue is not noValue and\n                    isinstance(currentValue, base.SimpleAsn1Type)):\n                value = currentValue.clone(value=value)\n\n            else:\n                raise error.PyAsn1Error(\n                    'Non-ASN.1 value %r and undefined component'\n                    ' type at %r' % (value, self))\n\n        elif componentType is not None and (matchTags or matchConstraints):\n            subtypeChecker = (\n                    self.strictConstraints and\n                    componentType.isSameTypeWith or\n                    componentType.isSuperTypeOf)\n\n            if not subtypeChecker(value, verifyConstraints and matchTags,\n                                  verifyConstraints and matchConstraints):\n                # TODO: we should wrap componentType with UnnamedType to carry\n                # additional properties associated with componentType\n                if componentType.typeId != Any.typeId:\n                    raise error.PyAsn1Error(\n                        'Component value is tag-incompatible: %r vs '\n                        '%r' % (value, componentType))\n\n        componentValues[idx] = value\n\n        self._componentValues = componentValues\n\n        return self\n\n    @property\n    def componentTagMap(self):\n        if self.componentType is not None:\n            return self.componentType.tagMap\n\n    @property\n    def components(self):\n        return [self._componentValues[idx]\n                for idx in sorted(self._componentValues)]\n\n    def clear(self):\n        \"\"\"Remove all components and become an empty |ASN.1| value object.\n\n        Has the same effect on |ASN.1| object as it does on :class:`list`\n        built-in.\n        \"\"\"\n        self._componentValues = {}\n        return self\n\n    def reset(self):\n        \"\"\"Remove all components and become a |ASN.1| schema object.\n\n        See :meth:`isValue` property for more information on the\n        distinction between value and schema objects.\n        \"\"\"\n        self._componentValues = noValue\n        return self\n\n    def prettyPrint(self, scope=0):\n        scope += 1\n        representation = self.__class__.__name__ + ':\\n'\n\n        if not self.isValue:\n            return representation\n\n        for idx, componentValue in enumerate(self):\n            representation += ' ' * scope\n            if (componentValue is noValue and\n                    self.componentType is not None):\n                representation += '<empty>'\n            else:\n                representation += componentValue.prettyPrint(scope)\n\n        return representation\n\n    def prettyPrintType(self, scope=0):\n        scope += 1\n        representation = '%s -> %s {\\n' % (self.tagSet, self.__class__.__name__)\n        if self.componentType is not None:\n            representation += ' ' * scope\n            representation += self.componentType.prettyPrintType(scope)\n        return representation + '\\n' + ' ' * (scope - 1) + '}'\n\n\n    @property\n    def isValue(self):\n        \"\"\"Indicate that |ASN.1| object represents ASN.1 value.\n\n        If *isValue* is :obj:`False` then this object represents just ASN.1 schema.\n\n        If *isValue* is :obj:`True` then, in addition to its ASN.1 schema features,\n        this object can also be used like a Python built-in object\n        (e.g. :class:`int`, :class:`str`, :class:`dict` etc.).\n\n        Returns\n        -------\n        : :class:`bool`\n            :obj:`False` if object represents just ASN.1 schema.\n            :obj:`True` if object represents ASN.1 schema and can be used as a normal value.\n\n        Note\n        ----\n        There is an important distinction between PyASN1 schema and value objects.\n        The PyASN1 schema objects can only participate in ASN.1 schema-related\n        operations (e.g. defining or testing the structure of the data). Most\n        obvious uses of ASN.1 schema is to guide serialisation codecs whilst\n        encoding/decoding serialised ASN.1 contents.\n\n        The PyASN1 value objects can **additionally** participate in many operations\n        involving regular Python objects (e.g. arithmetic, comprehension etc).\n        \"\"\"\n        if self._componentValues is noValue:\n            return False\n\n        if len(self._componentValues) != len(self):\n            return False\n\n        for componentValue in self._componentValues.values():\n            if componentValue is noValue or not componentValue.isValue:\n                return False\n\n        return True\n\n    @property\n    def isInconsistent(self):\n        \"\"\"Run necessary checks to ensure |ASN.1| object consistency.\n\n        Default action is to verify |ASN.1| object against constraints imposed\n        by `subtypeSpec`.\n\n        Raises\n        ------\n        :py:class:`~pyasn1.error.PyAsn1tError` on any inconsistencies found\n        \"\"\"\n        if self.componentType is noValue or not self.subtypeSpec:\n            return False\n\n        if self._componentValues is noValue:\n            return True\n\n        mapping = {}\n\n        for idx, value in self._componentValues.items():\n            # Absent fields are not in the mapping\n            if value is noValue:\n                continue\n\n            mapping[idx] = value\n\n        try:\n            # Represent SequenceOf/SetOf as a bare dict to constraints chain\n            self.subtypeSpec(mapping)\n\n        except error.PyAsn1Error:\n            exc = sys.exc_info()[1]\n            return exc\n\n        return False\n\nclass SequenceOf(SequenceOfAndSetOfBase):\n    __doc__ = SequenceOfAndSetOfBase.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatConstructed, 0x10)\n    )\n\n    #: Default :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n    #: object representing ASN.1 type allowed within |ASN.1| type\n    componentType = None\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection()\n\n    # Disambiguation ASN.1 types identification\n    typeId = SequenceOfAndSetOfBase.getTypeId()\n\n\nclass SetOf(SequenceOfAndSetOfBase):\n    __doc__ = SequenceOfAndSetOfBase.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatConstructed, 0x11)\n    )\n\n    #: Default :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n    #: object representing ASN.1 type allowed within |ASN.1| type\n    componentType = None\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection()\n\n    # Disambiguation ASN.1 types identification\n    typeId = SequenceOfAndSetOfBase.getTypeId()\n\n\nclass SequenceAndSetBase(base.ConstructedAsn1Type):\n    \"\"\"Create |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.ConstructedAsn1Type`,\n    its objects are mutable and duck-type Python :class:`dict` objects.\n\n    Keyword Args\n    ------------\n    componentType: :py:class:`~pyasn1.type.namedtype.NamedType`\n        Object holding named ASN.1 types allowed within this collection\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n        Object representing non-default ASN.1 subtype constraint(s).  Constraints\n        verification for |ASN.1| type can only occur on explicit\n        `.isInconsistent` call.\n\n    Examples\n    --------\n\n    .. code-block:: python\n\n        class Description(Sequence):  #  Set is similar\n            '''\n            ASN.1 specification:\n\n            Description ::= SEQUENCE {\n                surname    IA5String,\n                first-name IA5String OPTIONAL,\n                age        INTEGER DEFAULT 40\n            }\n            '''\n            componentType = NamedTypes(\n                NamedType('surname', IA5String()),\n                OptionalNamedType('first-name', IA5String()),\n                DefaultedNamedType('age', Integer(40))\n            )\n\n        descr = Description()\n        descr['surname'] = 'Smith'\n        descr['first-name'] = 'John'\n    \"\"\"\n    #: Default :py:class:`~pyasn1.type.namedtype.NamedTypes`\n    #: object representing named ASN.1 types allowed within |ASN.1| type\n    componentType = namedtype.NamedTypes()\n\n\n    class DynamicNames(object):\n        \"\"\"Fields names/positions mapping for component-less objects\"\"\"\n        def __init__(self):\n            self._keyToIdxMap = {}\n            self._idxToKeyMap = {}\n\n        def __len__(self):\n            return len(self._keyToIdxMap)\n\n        def __contains__(self, item):\n            return item in self._keyToIdxMap or item in self._idxToKeyMap\n\n        def __iter__(self):\n            return (self._idxToKeyMap[idx] for idx in range(len(self._idxToKeyMap)))\n\n        def __getitem__(self, item):\n            try:\n                return self._keyToIdxMap[item]\n\n            except KeyError:\n                return self._idxToKeyMap[item]\n\n        def getNameByPosition(self, idx):\n            try:\n                return self._idxToKeyMap[idx]\n\n            except KeyError:\n                raise error.PyAsn1Error('Type position out of range')\n\n        def getPositionByName(self, name):\n            try:\n                return self._keyToIdxMap[name]\n\n            except KeyError:\n                raise error.PyAsn1Error('Name %s not found' % (name,))\n\n        def addField(self, idx):\n            self._keyToIdxMap['field-%d' % idx] = idx\n            self._idxToKeyMap[idx] = 'field-%d' % idx\n\n\n    def __init__(self, **kwargs):\n        base.ConstructedAsn1Type.__init__(self, **kwargs)\n        self._componentTypeLen = len(self.componentType)\n        if self._componentTypeLen:\n            self._componentValues = []\n        else:\n            self._componentValues = noValue\n        self._dynamicNames = self._componentTypeLen or self.DynamicNames()\n\n    def __getitem__(self, idx):\n        if octets.isStringType(idx):\n            try:\n                return self.getComponentByName(idx)\n\n            except error.PyAsn1Error:\n                # duck-typing dict\n                raise KeyError(sys.exc_info()[1])\n\n        else:\n            try:\n                return self.getComponentByPosition(idx)\n\n            except error.PyAsn1Error:\n                # duck-typing list\n                raise IndexError(sys.exc_info()[1])\n\n    def __setitem__(self, idx, value):\n        if octets.isStringType(idx):\n            try:\n                self.setComponentByName(idx, value)\n\n            except error.PyAsn1Error:\n                # duck-typing dict\n                raise KeyError(sys.exc_info()[1])\n\n        else:\n            try:\n                self.setComponentByPosition(idx, value)\n\n            except error.PyAsn1Error:\n                # duck-typing list\n                raise IndexError(sys.exc_info()[1])\n\n    def __contains__(self, key):\n        if self._componentTypeLen:\n            return key in self.componentType\n        else:\n            return key in self._dynamicNames\n\n    def __len__(self):\n        return len(self._componentValues)\n\n    def __iter__(self):\n        return iter(self.componentType or self._dynamicNames)\n\n    # Python dict protocol\n\n    def values(self):\n        for idx in range(self._componentTypeLen or len(self._dynamicNames)):\n            yield self[idx]\n\n    def keys(self):\n        return iter(self)\n\n    def items(self):\n        for idx in range(self._componentTypeLen or len(self._dynamicNames)):\n            if self._componentTypeLen:\n                yield self.componentType[idx].name, self[idx]\n            else:\n                yield self._dynamicNames[idx], self[idx]\n\n    def update(self, *iterValue, **mappingValue):\n        for k, v in iterValue:\n            self[k] = v\n        for k in mappingValue:\n            self[k] = mappingValue[k]\n\n    def clear(self):\n        \"\"\"Remove all components and become an empty |ASN.1| value object.\n\n        Has the same effect on |ASN.1| object as it does on :class:`dict`\n        built-in.\n        \"\"\"\n        self._componentValues = []\n        self._dynamicNames = self.DynamicNames()\n        return self\n\n    def reset(self):\n        \"\"\"Remove all components and become a |ASN.1| schema object.\n\n        See :meth:`isValue` property for more information on the\n        distinction between value and schema objects.\n        \"\"\"\n        self._componentValues = noValue\n        self._dynamicNames = self.DynamicNames()\n        return self\n\n    @property\n    def components(self):\n        return self._componentValues\n\n    def _cloneComponentValues(self, myClone, cloneValueFlag):\n        if self._componentValues is noValue:\n            return\n\n        for idx, componentValue in enumerate(self._componentValues):\n            if componentValue is not noValue:\n                if isinstance(componentValue, base.ConstructedAsn1Type):\n                    myClone.setComponentByPosition(\n                        idx, componentValue.clone(cloneValueFlag=cloneValueFlag)\n                    )\n                else:\n                    myClone.setComponentByPosition(idx, componentValue.clone())\n\n    def getComponentByName(self, name, default=noValue, instantiate=True):\n        \"\"\"Returns |ASN.1| type component by name.\n\n        Equivalent to Python :class:`dict` subscription operation (e.g. `[]`).\n\n        Parameters\n        ----------\n        name: :class:`str`\n            |ASN.1| type component name\n\n        Keyword Args\n        ------------\n        default: :class:`object`\n            If set and requested component is a schema object, return the `default`\n            object instead of the requested component.\n\n        instantiate: :class:`bool`\n            If :obj:`True` (default), inner component will be automatically\n            instantiated.\n            If :obj:`False` either existing component or the :class:`NoValue`\n            object will be returned.\n\n        Returns\n        -------\n        : :py:class:`~pyasn1.type.base.PyAsn1Item`\n            Instantiate |ASN.1| component type or return existing\n            component value\n        \"\"\"\n        if self._componentTypeLen:\n            idx = self.componentType.getPositionByName(name)\n        else:\n            try:\n                idx = self._dynamicNames.getPositionByName(name)\n\n            except KeyError:\n                raise error.PyAsn1Error('Name %s not found' % (name,))\n\n        return self.getComponentByPosition(idx, default=default, instantiate=instantiate)\n\n    def setComponentByName(self, name, value=noValue,\n                           verifyConstraints=True,\n                           matchTags=True,\n                           matchConstraints=True):\n        \"\"\"Assign |ASN.1| type component by name.\n\n        Equivalent to Python :class:`dict` item assignment operation (e.g. `[]`).\n\n        Parameters\n        ----------\n        name: :class:`str`\n            |ASN.1| type component name\n\n        Keyword Args\n        ------------\n        value: :class:`object` or :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n            A Python value to initialize |ASN.1| component with (if *componentType* is set)\n            or ASN.1 value object to assign to |ASN.1| component.\n            If `value` is not given, schema object will be set as a component.\n\n        verifyConstraints: :class:`bool`\n             If :obj:`False`, skip constraints validation\n\n        matchTags: :class:`bool`\n             If :obj:`False`, skip component tags matching\n\n        matchConstraints: :class:`bool`\n             If :obj:`False`, skip component constraints matching\n\n        Returns\n        -------\n        self\n        \"\"\"\n        if self._componentTypeLen:\n            idx = self.componentType.getPositionByName(name)\n        else:\n            try:\n                idx = self._dynamicNames.getPositionByName(name)\n\n            except KeyError:\n                raise error.PyAsn1Error('Name %s not found' % (name,))\n\n        return self.setComponentByPosition(\n            idx, value, verifyConstraints, matchTags, matchConstraints\n        )\n\n    def getComponentByPosition(self, idx, default=noValue, instantiate=True):\n        \"\"\"Returns |ASN.1| type component by index.\n\n        Equivalent to Python sequence subscription operation (e.g. `[]`).\n\n        Parameters\n        ----------\n        idx: :class:`int`\n            Component index (zero-based). Must either refer to an existing\n            component or (if *componentType* is set) new ASN.1 schema object gets\n            instantiated.\n\n        Keyword Args\n        ------------\n        default: :class:`object`\n            If set and requested component is a schema object, return the `default`\n            object instead of the requested component.\n\n        instantiate: :class:`bool`\n            If :obj:`True` (default), inner component will be automatically\n            instantiated.\n            If :obj:`False` either existing component or the :class:`NoValue`\n            object will be returned.\n\n        Returns\n        -------\n        : :py:class:`~pyasn1.type.base.PyAsn1Item`\n            a PyASN1 object\n\n        Examples\n        --------\n\n        .. code-block:: python\n\n            # can also be Set\n            class MySequence(Sequence):\n                componentType = NamedTypes(\n                    NamedType('id', OctetString())\n                )\n\n            s = MySequence()\n\n            # returns component #0 with `.isValue` property False\n            s.getComponentByPosition(0)\n\n            # returns None\n            s.getComponentByPosition(0, default=None)\n\n            s.clear()\n\n            # returns noValue\n            s.getComponentByPosition(0, instantiate=False)\n\n            # sets component #0 to OctetString() ASN.1 schema\n            # object and returns it\n            s.getComponentByPosition(0, instantiate=True)\n\n            # sets component #0 to ASN.1 value object\n            s.setComponentByPosition(0, 'ABCD')\n\n            # returns OctetString('ABCD') value object\n            s.getComponentByPosition(0, instantiate=False)\n\n            s.clear()\n\n            # returns noValue\n            s.getComponentByPosition(0, instantiate=False)\n        \"\"\"\n        try:\n            if self._componentValues is noValue:\n                componentValue = noValue\n\n            else:\n                componentValue = self._componentValues[idx]\n\n        except IndexError:\n            componentValue = noValue\n\n        if not instantiate:\n            if componentValue is noValue or not componentValue.isValue:\n                return default\n            else:\n                return componentValue\n\n        if componentValue is noValue:\n            self.setComponentByPosition(idx)\n\n        componentValue = self._componentValues[idx]\n\n        if default is noValue or componentValue.isValue:\n            return componentValue\n        else:\n            return default\n\n    def setComponentByPosition(self, idx, value=noValue,\n                               verifyConstraints=True,\n                               matchTags=True,\n                               matchConstraints=True):\n        \"\"\"Assign |ASN.1| type component by position.\n\n        Equivalent to Python sequence item assignment operation (e.g. `[]`).\n\n        Parameters\n        ----------\n        idx : :class:`int`\n            Component index (zero-based). Must either refer to existing\n            component (if *componentType* is set) or to N+1 component\n            otherwise. In the latter case a new component of given ASN.1\n            type gets instantiated and appended to |ASN.1| sequence.\n\n        Keyword Args\n        ------------\n        value: :class:`object` or :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n            A Python value to initialize |ASN.1| component with (if *componentType* is set)\n            or ASN.1 value object to assign to |ASN.1| component.\n            If `value` is not given, schema object will be set as a component.\n\n        verifyConstraints : :class:`bool`\n             If :obj:`False`, skip constraints validation\n\n        matchTags: :class:`bool`\n             If :obj:`False`, skip component tags matching\n\n        matchConstraints: :class:`bool`\n             If :obj:`False`, skip component constraints matching\n\n        Returns\n        -------\n        self\n        \"\"\"\n        componentType = self.componentType\n        componentTypeLen = self._componentTypeLen\n\n        if self._componentValues is noValue:\n            componentValues = []\n\n        else:\n            componentValues = self._componentValues\n\n        try:\n            currentValue = componentValues[idx]\n\n        except IndexError:\n            currentValue = noValue\n            if componentTypeLen:\n                if componentTypeLen < idx:\n                    raise error.PyAsn1Error('component index out of range')\n\n                componentValues = [noValue] * componentTypeLen\n\n        if value is noValue:\n            if componentTypeLen:\n                value = componentType.getTypeByPosition(idx)\n                if isinstance(value, base.ConstructedAsn1Type):\n                    value = value.clone(cloneValueFlag=componentType[idx].isDefaulted)\n\n            elif currentValue is noValue:\n                raise error.PyAsn1Error('Component type not defined')\n\n        elif not isinstance(value, base.Asn1Item):\n            if componentTypeLen:\n                subComponentType = componentType.getTypeByPosition(idx)\n                if isinstance(subComponentType, base.SimpleAsn1Type):\n                    value = subComponentType.clone(value=value)\n\n                else:\n                    raise error.PyAsn1Error('%s can cast only scalar values' % componentType.__class__.__name__)\n\n            elif currentValue is not noValue and isinstance(currentValue, base.SimpleAsn1Type):\n                value = currentValue.clone(value=value)\n\n            else:\n                raise error.PyAsn1Error('%s undefined component type' % componentType.__class__.__name__)\n\n        elif ((verifyConstraints or matchTags or matchConstraints) and\n              componentTypeLen):\n            subComponentType = componentType.getTypeByPosition(idx)\n            if subComponentType is not noValue:\n                subtypeChecker = (self.strictConstraints and\n                                  subComponentType.isSameTypeWith or\n                                  subComponentType.isSuperTypeOf)\n\n                if not subtypeChecker(value, verifyConstraints and matchTags,\n                                      verifyConstraints and matchConstraints):\n                    if not componentType[idx].openType:\n                        raise error.PyAsn1Error('Component value is tag-incompatible: %r vs %r' % (value, componentType))\n\n        if componentTypeLen or idx in self._dynamicNames:\n            componentValues[idx] = value\n\n        elif len(componentValues) == idx:\n            componentValues.append(value)\n            self._dynamicNames.addField(idx)\n\n        else:\n            raise error.PyAsn1Error('Component index out of range')\n\n        self._componentValues = componentValues\n\n        return self\n\n    @property\n    def isValue(self):\n        \"\"\"Indicate that |ASN.1| object represents ASN.1 value.\n\n        If *isValue* is :obj:`False` then this object represents just ASN.1 schema.\n\n        If *isValue* is :obj:`True` then, in addition to its ASN.1 schema features,\n        this object can also be used like a Python built-in object (e.g.\n        :class:`int`, :class:`str`, :class:`dict` etc.).\n\n        Returns\n        -------\n        : :class:`bool`\n            :obj:`False` if object represents just ASN.1 schema.\n            :obj:`True` if object represents ASN.1 schema and can be used as a\n            normal value.\n\n        Note\n        ----\n        There is an important distinction between PyASN1 schema and value objects.\n        The PyASN1 schema objects can only participate in ASN.1 schema-related\n        operations (e.g. defining or testing the structure of the data). Most\n        obvious uses of ASN.1 schema is to guide serialisation codecs whilst\n        encoding/decoding serialised ASN.1 contents.\n\n        The PyASN1 value objects can **additionally** participate in many operations\n        involving regular Python objects (e.g. arithmetic, comprehension etc).\n\n        It is sufficient for |ASN.1| objects to have all non-optional and non-defaulted\n        components being value objects to be considered as a value objects as a whole.\n        In other words, even having one or more optional components not turned into\n        value objects, |ASN.1| object is still considered as a value object. Defaulted\n        components are normally value objects by default.\n        \"\"\"\n        if self._componentValues is noValue:\n            return False\n\n        componentType = self.componentType\n\n        if componentType:\n            for idx, subComponentType in enumerate(componentType.namedTypes):\n                if subComponentType.isDefaulted or subComponentType.isOptional:\n                    continue\n\n                if not self._componentValues:\n                    return False\n\n                componentValue = self._componentValues[idx]\n                if componentValue is noValue or not componentValue.isValue:\n                    return False\n\n        else:\n            for componentValue in self._componentValues:\n                if componentValue is noValue or not componentValue.isValue:\n                    return False\n\n        return True\n\n    @property\n    def isInconsistent(self):\n        \"\"\"Run necessary checks to ensure |ASN.1| object consistency.\n\n        Default action is to verify |ASN.1| object against constraints imposed\n        by `subtypeSpec`.\n\n        Raises\n        ------\n        :py:class:`~pyasn1.error.PyAsn1tError` on any inconsistencies found\n        \"\"\"\n        if self.componentType is noValue or not self.subtypeSpec:\n            return False\n\n        if self._componentValues is noValue:\n            return True\n\n        mapping = {}\n\n        for idx, value in enumerate(self._componentValues):\n            # Absent fields are not in the mapping\n            if value is noValue:\n                continue\n\n            name = self.componentType.getNameByPosition(idx)\n\n            mapping[name] = value\n\n        try:\n            # Represent Sequence/Set as a bare dict to constraints chain\n            self.subtypeSpec(mapping)\n\n        except error.PyAsn1Error:\n            exc = sys.exc_info()[1]\n            return exc\n\n        return False\n\n    def prettyPrint(self, scope=0):\n        \"\"\"Return an object representation string.\n\n        Returns\n        -------\n        : :class:`str`\n            Human-friendly object representation.\n        \"\"\"\n        scope += 1\n        representation = self.__class__.__name__ + ':\\n'\n        for idx, componentValue in enumerate(self._componentValues):\n            if componentValue is not noValue and componentValue.isValue:\n                representation += ' ' * scope\n                if self.componentType:\n                    representation += self.componentType.getNameByPosition(idx)\n                else:\n                    representation += self._dynamicNames.getNameByPosition(idx)\n                representation = '%s=%s\\n' % (\n                    representation, componentValue.prettyPrint(scope)\n                )\n        return representation\n\n    def prettyPrintType(self, scope=0):\n        scope += 1\n        representation = '%s -> %s {\\n' % (self.tagSet, self.__class__.__name__)\n        for idx, componentType in enumerate(self.componentType.values() or self._componentValues):\n            representation += ' ' * scope\n            if self.componentType:\n                representation += '\"%s\"' % self.componentType.getNameByPosition(idx)\n            else:\n                representation += '\"%s\"' % self._dynamicNames.getNameByPosition(idx)\n            representation = '%s = %s\\n' % (\n                representation, componentType.prettyPrintType(scope)\n            )\n        return representation + '\\n' + ' ' * (scope - 1) + '}'\n\n    # backward compatibility\n\n    def setDefaultComponents(self):\n        return self\n\n    def getComponentType(self):\n        if self._componentTypeLen:\n            return self.componentType\n\n    def getNameByPosition(self, idx):\n        if self._componentTypeLen:\n            return self.componentType[idx].name\n\nclass Sequence(SequenceAndSetBase):\n    __doc__ = SequenceAndSetBase.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatConstructed, 0x10)\n    )\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection()\n\n    #: Default collection of ASN.1 types of component (e.g. :py:class:`~pyasn1.type.namedtype.NamedType`)\n    #: object imposing size constraint on |ASN.1| objects\n    componentType = namedtype.NamedTypes()\n\n    # Disambiguation ASN.1 types identification\n    typeId = SequenceAndSetBase.getTypeId()\n\n    # backward compatibility\n\n    def getComponentTagMapNearPosition(self, idx):\n        if self.componentType:\n            return self.componentType.getTagMapNearPosition(idx)\n\n    def getComponentPositionNearType(self, tagSet, idx):\n        if self.componentType:\n            return self.componentType.getPositionNearType(tagSet, idx)\n        else:\n            return idx\n\n\nclass Set(SequenceAndSetBase):\n    __doc__ = SequenceAndSetBase.__doc__\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.initTagSet(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatConstructed, 0x11)\n    )\n\n    #: Default collection of ASN.1 types of component (e.g. :py:class:`~pyasn1.type.namedtype.NamedType`)\n    #: object representing ASN.1 type allowed within |ASN.1| type\n    componentType = namedtype.NamedTypes()\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection()\n\n    # Disambiguation ASN.1 types identification\n    typeId = SequenceAndSetBase.getTypeId()\n\n    def getComponent(self, innerFlag=False):\n        return self\n\n    def getComponentByType(self, tagSet, default=noValue,\n                           instantiate=True, innerFlag=False):\n        \"\"\"Returns |ASN.1| type component by ASN.1 tag.\n\n        Parameters\n        ----------\n        tagSet : :py:class:`~pyasn1.type.tag.TagSet`\n            Object representing ASN.1 tags to identify one of\n            |ASN.1| object component\n\n        Keyword Args\n        ------------\n        default: :class:`object`\n            If set and requested component is a schema object, return the `default`\n            object instead of the requested component.\n\n        instantiate: :class:`bool`\n            If :obj:`True` (default), inner component will be automatically\n            instantiated.\n            If :obj:`False` either existing component or the :class:`noValue`\n            object will be returned.\n\n        Returns\n        -------\n        : :py:class:`~pyasn1.type.base.PyAsn1Item`\n            a pyasn1 object\n        \"\"\"\n        componentValue = self.getComponentByPosition(\n            self.componentType.getPositionByType(tagSet),\n            default=default, instantiate=instantiate\n        )\n        if innerFlag and isinstance(componentValue, Set):\n            # get inner component by inner tagSet\n            return componentValue.getComponent(innerFlag=True)\n        else:\n            # get outer component by inner tagSet\n            return componentValue\n\n    def setComponentByType(self, tagSet, value=noValue,\n                           verifyConstraints=True,\n                           matchTags=True,\n                           matchConstraints=True,\n                           innerFlag=False):\n        \"\"\"Assign |ASN.1| type component by ASN.1 tag.\n\n        Parameters\n        ----------\n        tagSet : :py:class:`~pyasn1.type.tag.TagSet`\n            Object representing ASN.1 tags to identify one of\n            |ASN.1| object component\n\n        Keyword Args\n        ------------\n        value: :class:`object` or :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n            A Python value to initialize |ASN.1| component with (if *componentType* is set)\n            or ASN.1 value object to assign to |ASN.1| component.\n            If `value` is not given, schema object will be set as a component.\n\n        verifyConstraints : :class:`bool`\n            If :obj:`False`, skip constraints validation\n\n        matchTags: :class:`bool`\n            If :obj:`False`, skip component tags matching\n\n        matchConstraints: :class:`bool`\n            If :obj:`False`, skip component constraints matching\n\n        innerFlag: :class:`bool`\n            If :obj:`True`, search for matching *tagSet* recursively.\n\n        Returns\n        -------\n        self\n        \"\"\"\n        idx = self.componentType.getPositionByType(tagSet)\n\n        if innerFlag:  # set inner component by inner tagSet\n            componentType = self.componentType.getTypeByPosition(idx)\n\n            if componentType.tagSet:\n                return self.setComponentByPosition(\n                    idx, value, verifyConstraints, matchTags, matchConstraints\n                )\n            else:\n                componentType = self.getComponentByPosition(idx)\n                return componentType.setComponentByType(\n                    tagSet, value, verifyConstraints, matchTags, matchConstraints, innerFlag=innerFlag\n                )\n        else:  # set outer component by inner tagSet\n            return self.setComponentByPosition(\n                idx, value, verifyConstraints, matchTags, matchConstraints\n            )\n\n    @property\n    def componentTagMap(self):\n        if self.componentType:\n            return self.componentType.tagMapUnique\n\n\nclass Choice(Set):\n    \"\"\"Create |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.ConstructedAsn1Type`,\n    its objects are mutable and duck-type Python :class:`list` objects.\n\n    Keyword Args\n    ------------\n    componentType: :py:class:`~pyasn1.type.namedtype.NamedType`\n        Object holding named ASN.1 types allowed within this collection\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n        Object representing non-default ASN.1 subtype constraint(s).  Constraints\n        verification for |ASN.1| type can only occur on explicit\n        `.isInconsistent` call.\n\n    Examples\n    --------\n\n    .. code-block:: python\n\n        class Afters(Choice):\n            '''\n            ASN.1 specification:\n\n            Afters ::= CHOICE {\n                cheese  [0] IA5String,\n                dessert [1] IA5String\n            }\n            '''\n            componentType = NamedTypes(\n                NamedType('cheese', IA5String().subtype(\n                    implicitTag=Tag(tagClassContext, tagFormatSimple, 0)\n                ),\n                NamedType('dessert', IA5String().subtype(\n                    implicitTag=Tag(tagClassContext, tagFormatSimple, 1)\n                )\n            )\n\n        afters = Afters()\n        afters['cheese'] = 'Mascarpone'\n    \"\"\"\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.TagSet()  # untagged\n\n    #: Default collection of ASN.1 types of component (e.g. :py:class:`~pyasn1.type.namedtype.NamedType`)\n    #: object representing ASN.1 type allowed within |ASN.1| type\n    componentType = namedtype.NamedTypes()\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection(\n        constraint.ValueSizeConstraint(1, 1)\n    )\n\n    # Disambiguation ASN.1 types identification\n    typeId = Set.getTypeId()\n\n    _currentIdx = None\n\n    def __eq__(self, other):\n        if self._componentValues:\n            return self._componentValues[self._currentIdx] == other\n        return NotImplemented\n\n    def __ne__(self, other):\n        if self._componentValues:\n            return self._componentValues[self._currentIdx] != other\n        return NotImplemented\n\n    def __lt__(self, other):\n        if self._componentValues:\n            return self._componentValues[self._currentIdx] < other\n        return NotImplemented\n\n    def __le__(self, other):\n        if self._componentValues:\n            return self._componentValues[self._currentIdx] <= other\n        return NotImplemented\n\n    def __gt__(self, other):\n        if self._componentValues:\n            return self._componentValues[self._currentIdx] > other\n        return NotImplemented\n\n    def __ge__(self, other):\n        if self._componentValues:\n            return self._componentValues[self._currentIdx] >= other\n        return NotImplemented\n\n    if sys.version_info[0] <= 2:\n        def __nonzero__(self):\n            return self._componentValues and True or False\n    else:\n        def __bool__(self):\n            return self._componentValues and True or False\n\n    def __len__(self):\n        return self._currentIdx is not None and 1 or 0\n\n    def __contains__(self, key):\n        if self._currentIdx is None:\n            return False\n        return key == self.componentType[self._currentIdx].getName()\n\n    def __iter__(self):\n        if self._currentIdx is None:\n            raise StopIteration\n        yield self.componentType[self._currentIdx].getName()\n\n    # Python dict protocol\n\n    def values(self):\n        if self._currentIdx is not None:\n            yield self._componentValues[self._currentIdx]\n\n    def keys(self):\n        if self._currentIdx is not None:\n            yield self.componentType[self._currentIdx].getName()\n\n    def items(self):\n        if self._currentIdx is not None:\n            yield self.componentType[self._currentIdx].getName(), self[self._currentIdx]\n\n    def checkConsistency(self):\n        if self._currentIdx is None:\n            raise error.PyAsn1Error('Component not chosen')\n\n    def _cloneComponentValues(self, myClone, cloneValueFlag):\n        try:\n            component = self.getComponent()\n        except error.PyAsn1Error:\n            pass\n        else:\n            if isinstance(component, Choice):\n                tagSet = component.effectiveTagSet\n            else:\n                tagSet = component.tagSet\n            if isinstance(component, base.ConstructedAsn1Type):\n                myClone.setComponentByType(\n                    tagSet, component.clone(cloneValueFlag=cloneValueFlag)\n                )\n            else:\n                myClone.setComponentByType(tagSet, component.clone())\n\n    def getComponentByPosition(self, idx, default=noValue, instantiate=True):\n        __doc__ = Set.__doc__\n\n        if self._currentIdx is None or self._currentIdx != idx:\n            return Set.getComponentByPosition(self, idx, default=default,\n                                              instantiate=instantiate)\n\n        return self._componentValues[idx]\n\n    def setComponentByPosition(self, idx, value=noValue,\n                               verifyConstraints=True,\n                               matchTags=True,\n                               matchConstraints=True):\n        \"\"\"Assign |ASN.1| type component by position.\n\n        Equivalent to Python sequence item assignment operation (e.g. `[]`).\n\n        Parameters\n        ----------\n        idx: :class:`int`\n            Component index (zero-based). Must either refer to existing\n            component or to N+1 component. In the latter case a new component\n            type gets instantiated (if *componentType* is set, or given ASN.1\n            object is taken otherwise) and appended to the |ASN.1| sequence.\n\n        Keyword Args\n        ------------\n        value: :class:`object` or :py:class:`~pyasn1.type.base.PyAsn1Item` derivative\n            A Python value to initialize |ASN.1| component with (if *componentType* is set)\n            or ASN.1 value object to assign to |ASN.1| component. Once a new value is\n            set to *idx* component, previous value is dropped.\n            If `value` is not given, schema object will be set as a component.\n\n        verifyConstraints : :class:`bool`\n            If :obj:`False`, skip constraints validation\n\n        matchTags: :class:`bool`\n            If :obj:`False`, skip component tags matching\n\n        matchConstraints: :class:`bool`\n            If :obj:`False`, skip component constraints matching\n\n        Returns\n        -------\n        self\n        \"\"\"\n        oldIdx = self._currentIdx\n        Set.setComponentByPosition(self, idx, value, verifyConstraints, matchTags, matchConstraints)\n        self._currentIdx = idx\n        if oldIdx is not None and oldIdx != idx:\n            self._componentValues[oldIdx] = noValue\n        return self\n\n    @property\n    def effectiveTagSet(self):\n        \"\"\"Return a :class:`~pyasn1.type.tag.TagSet` object of the currently initialized component or self (if |ASN.1| is tagged).\"\"\"\n        if self.tagSet:\n            return self.tagSet\n        else:\n            component = self.getComponent()\n            return component.effectiveTagSet\n\n    @property\n    def tagMap(self):\n        \"\"\"\"Return a :class:`~pyasn1.type.tagmap.TagMap` object mapping\n            ASN.1 tags to ASN.1 objects contained within callee.\n        \"\"\"\n        if self.tagSet:\n            return Set.tagMap.fget(self)\n        else:\n            return self.componentType.tagMapUnique\n\n    def getComponent(self, innerFlag=False):\n        \"\"\"Return currently assigned component of the |ASN.1| object.\n\n        Returns\n        -------\n        : :py:class:`~pyasn1.type.base.PyAsn1Item`\n            a PyASN1 object\n        \"\"\"\n        if self._currentIdx is None:\n            raise error.PyAsn1Error('Component not chosen')\n        else:\n            c = self._componentValues[self._currentIdx]\n            if innerFlag and isinstance(c, Choice):\n                return c.getComponent(innerFlag)\n            else:\n                return c\n\n    def getName(self, innerFlag=False):\n        \"\"\"Return the name of currently assigned component of the |ASN.1| object.\n\n        Returns\n        -------\n        : :py:class:`str`\n            |ASN.1| component name\n        \"\"\"\n        if self._currentIdx is None:\n            raise error.PyAsn1Error('Component not chosen')\n        else:\n            if innerFlag:\n                c = self._componentValues[self._currentIdx]\n                if isinstance(c, Choice):\n                    return c.getName(innerFlag)\n            return self.componentType.getNameByPosition(self._currentIdx)\n\n    @property\n    def isValue(self):\n        \"\"\"Indicate that |ASN.1| object represents ASN.1 value.\n\n        If *isValue* is :obj:`False` then this object represents just ASN.1 schema.\n\n        If *isValue* is :obj:`True` then, in addition to its ASN.1 schema features,\n        this object can also be used like a Python built-in object (e.g.\n        :class:`int`, :class:`str`, :class:`dict` etc.).\n\n        Returns\n        -------\n        : :class:`bool`\n            :obj:`False` if object represents just ASN.1 schema.\n            :obj:`True` if object represents ASN.1 schema and can be used as a normal\n            value.\n\n        Note\n        ----\n        There is an important distinction between PyASN1 schema and value objects.\n        The PyASN1 schema objects can only participate in ASN.1 schema-related\n        operations (e.g. defining or testing the structure of the data). Most\n        obvious uses of ASN.1 schema is to guide serialisation codecs whilst\n        encoding/decoding serialised ASN.1 contents.\n\n        The PyASN1 value objects can **additionally** participate in many operations\n        involving regular Python objects (e.g. arithmetic, comprehension etc).\n        \"\"\"\n        if self._currentIdx is None:\n            return False\n\n        componentValue = self._componentValues[self._currentIdx]\n\n        return componentValue is not noValue and componentValue.isValue\n\n    def clear(self):\n        self._currentIdx = None\n        return Set.clear(self)\n\n    # compatibility stubs\n\n    def getMinTagSet(self):\n        return self.minTagSet\n\n\nclass Any(OctetString):\n    \"\"\"Create |ASN.1| schema or value object.\n\n    |ASN.1| class is based on :class:`~pyasn1.type.base.SimpleAsn1Type`,\n    its objects are immutable and duck-type Python 2 :class:`str` or Python 3\n    :class:`bytes`. When used in Unicode context, |ASN.1| type assumes\n    \"|encoding|\" serialisation.\n\n    Keyword Args\n    ------------\n    value: :class:`unicode`, :class:`str`, :class:`bytes` or |ASN.1| object\n        :class:`str` (Python 2) or :class:`bytes` (Python 3), alternatively\n        :class:`unicode` object (Python 2) or :class:`str` (Python 3)\n        representing character string to be serialised into octets (note\n        `encoding` parameter) or |ASN.1| object.\n        If `value` is not given, schema object will be created.\n\n    tagSet: :py:class:`~pyasn1.type.tag.TagSet`\n        Object representing non-default ASN.1 tag(s)\n\n    subtypeSpec: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection`\n        Object representing non-default ASN.1 subtype constraint(s). Constraints\n        verification for |ASN.1| type occurs automatically on object\n        instantiation.\n\n    encoding: :py:class:`str`\n        Unicode codec ID to encode/decode :class:`unicode` (Python 2) or\n        :class:`str` (Python 3) the payload when |ASN.1| object is used\n        in text string context.\n\n    binValue: :py:class:`str`\n        Binary string initializer to use instead of the *value*.\n        Example: '10110011'.\n\n    hexValue: :py:class:`str`\n        Hexadecimal string initializer to use instead of the *value*.\n        Example: 'DEADBEEF'.\n\n    Raises\n    ------\n    ~pyasn1.error.ValueConstraintError, ~pyasn1.error.PyAsn1Error\n        On constraint violation or bad initializer.\n\n    Examples\n    --------\n    .. code-block:: python\n\n        class Error(Sequence):\n            '''\n            ASN.1 specification:\n\n            Error ::= SEQUENCE {\n                code      INTEGER,\n                parameter ANY DEFINED BY code  -- Either INTEGER or REAL\n            }\n            '''\n            componentType=NamedTypes(\n                NamedType('code', Integer()),\n                NamedType('parameter', Any(),\n                          openType=OpenType('code', {1: Integer(),\n                                                     2: Real()}))\n            )\n\n        error = Error()\n        error['code'] = 1\n        error['parameter'] = Integer(1234)\n    \"\"\"\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.tag.TagSet` object representing ASN.1 tag(s)\n    #: associated with |ASN.1| type.\n    tagSet = tag.TagSet()  # untagged\n\n    #: Set (on class, not on instance) or return a\n    #: :py:class:`~pyasn1.type.constraint.ConstraintsIntersection` object\n    #: imposing constraints on |ASN.1| type initialization values.\n    subtypeSpec = constraint.ConstraintsIntersection()\n\n    # Disambiguation ASN.1 types identification\n    typeId = OctetString.getTypeId()\n\n    @property\n    def tagMap(self):\n        \"\"\"\"Return a :class:`~pyasn1.type.tagmap.TagMap` object mapping\n            ASN.1 tags to ASN.1 objects contained within callee.\n        \"\"\"\n        try:\n            return self._tagMap\n\n        except AttributeError:\n            self._tagMap = tagmap.TagMap(\n                {self.tagSet: self},\n                {eoo.endOfOctets.tagSet: eoo.endOfOctets},\n                self\n            )\n\n            return self._tagMap\n\n# XXX\n# coercion rules?\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1/type/useful.py",
    "content": "#\n# This file is part of pyasn1 software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nimport datetime\n\nfrom pyasn1 import error\nfrom pyasn1.compat import dateandtime\nfrom pyasn1.compat import string\nfrom pyasn1.type import char\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\n__all__ = ['ObjectDescriptor', 'GeneralizedTime', 'UTCTime']\n\nNoValue = univ.NoValue\nnoValue = univ.noValue\n\n\nclass ObjectDescriptor(char.GraphicString):\n    __doc__ = char.GraphicString.__doc__\n\n    #: Default :py:class:`~pyasn1.type.tag.TagSet` object for |ASN.1| objects\n    tagSet = char.GraphicString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 7)\n    )\n\n    # Optimization for faster codec lookup\n    typeId = char.GraphicString.getTypeId()\n\n\nclass TimeMixIn(object):\n\n    _yearsDigits = 4\n    _hasSubsecond = False\n    _optionalMinutes = False\n    _shortTZ = False\n\n    class FixedOffset(datetime.tzinfo):\n        \"\"\"Fixed offset in minutes east from UTC.\"\"\"\n\n        # defaulted arguments required\n        # https: // docs.python.org / 2.3 / lib / datetime - tzinfo.html\n        def __init__(self, offset=0, name='UTC'):\n            self.__offset = datetime.timedelta(minutes=offset)\n            self.__name = name\n\n        def utcoffset(self, dt):\n            return self.__offset\n\n        def tzname(self, dt):\n            return self.__name\n\n        def dst(self, dt):\n            return datetime.timedelta(0)\n\n    UTC = FixedOffset()\n\n    @property\n    def asDateTime(self):\n        \"\"\"Create :py:class:`datetime.datetime` object from a |ASN.1| object.\n\n        Returns\n        -------\n        :\n            new instance of :py:class:`datetime.datetime` object\n        \"\"\"\n        text = str(self)\n        if text.endswith('Z'):\n            tzinfo = TimeMixIn.UTC\n            text = text[:-1]\n\n        elif '-' in text or '+' in text:\n            if '+' in text:\n                text, plusminus, tz = string.partition(text, '+')\n            else:\n                text, plusminus, tz = string.partition(text, '-')\n\n            if self._shortTZ and len(tz) == 2:\n                tz += '00'\n\n            if len(tz) != 4:\n                raise error.PyAsn1Error('malformed time zone offset %s' % tz)\n\n            try:\n                minutes = int(tz[:2]) * 60 + int(tz[2:])\n                if plusminus == '-':\n                    minutes *= -1\n\n            except ValueError:\n                raise error.PyAsn1Error('unknown time specification %s' % self)\n\n            tzinfo = TimeMixIn.FixedOffset(minutes, '?')\n\n        else:\n            tzinfo = None\n\n        if '.' in text or ',' in text:\n            if '.' in text:\n                text, _, ms = string.partition(text, '.')\n            else:\n                text, _, ms = string.partition(text, ',')\n\n            try:\n                ms = int(ms) * 1000\n\n            except ValueError:\n                raise error.PyAsn1Error('bad sub-second time specification %s' % self)\n\n        else:\n            ms = 0\n\n        if self._optionalMinutes and len(text) - self._yearsDigits == 6:\n            text += '0000'\n        elif len(text) - self._yearsDigits == 8:\n            text += '00'\n\n        try:\n            dt = dateandtime.strptime(text, self._yearsDigits == 4 and '%Y%m%d%H%M%S' or '%y%m%d%H%M%S')\n\n        except ValueError:\n            raise error.PyAsn1Error('malformed datetime format %s' % self)\n\n        return dt.replace(microsecond=ms, tzinfo=tzinfo)\n\n    @classmethod\n    def fromDateTime(cls, dt):\n        \"\"\"Create |ASN.1| object from a :py:class:`datetime.datetime` object.\n\n        Parameters\n        ----------\n        dt: :py:class:`datetime.datetime` object\n            The `datetime.datetime` object to initialize the |ASN.1| object\n            from\n\n        Returns\n        -------\n        :\n            new instance of |ASN.1| value\n        \"\"\"\n        text = dt.strftime(cls._yearsDigits == 4 and '%Y%m%d%H%M%S' or '%y%m%d%H%M%S')\n        if cls._hasSubsecond:\n            text += '.%d' % (dt.microsecond // 1000)\n\n        if dt.utcoffset():\n            seconds = dt.utcoffset().seconds\n            if seconds < 0:\n                text += '-'\n            else:\n                text += '+'\n            text += '%.2d%.2d' % (seconds // 3600, seconds % 3600)\n        else:\n            text += 'Z'\n\n        return cls(text)\n\n\nclass GeneralizedTime(char.VisibleString, TimeMixIn):\n    __doc__ = char.VisibleString.__doc__\n\n    #: Default :py:class:`~pyasn1.type.tag.TagSet` object for |ASN.1| objects\n    tagSet = char.VisibleString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 24)\n    )\n\n    # Optimization for faster codec lookup\n    typeId = char.VideotexString.getTypeId()\n\n    _yearsDigits = 4\n    _hasSubsecond = True\n    _optionalMinutes = True\n    _shortTZ = True\n\n\nclass UTCTime(char.VisibleString, TimeMixIn):\n    __doc__ = char.VisibleString.__doc__\n\n    #: Default :py:class:`~pyasn1.type.tag.TagSet` object for |ASN.1| objects\n    tagSet = char.VisibleString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassUniversal, tag.tagFormatSimple, 23)\n    )\n\n    # Optimization for faster codec lookup\n    typeId = char.VideotexString.getTypeId()\n\n    _yearsDigits = 2\n    _hasSubsecond = False\n    _optionalMinutes = False\n    _shortTZ = False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1-0.4.7.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1-0.4.7.dist-info/LICENSE.rst",
    "content": "Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\nAll rights reserved.\n\nRedistribution and use in source and binary forms, with or without\nmodification, are permitted provided that the following conditions are met:\n\n  * Redistributions of source code must retain the above copyright notice, \n    this list of conditions and the following disclaimer.\n\n  * Redistributions in binary form must reproduce the above copyright notice,\n    this list of conditions and the following disclaimer in the documentation\n    and/or other materials provided with the distribution.\n\nTHIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\"\nAND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE \nIMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE \nARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE\nLIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR\nCONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF\nSUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS\nINTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN\nCONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)\nARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\nPOSSIBILITY OF SUCH DAMAGE. \n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1-0.4.7.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: pyasn1\nVersion: 0.4.7\nSummary: ASN.1 types and codecs\nHome-page: https://github.com/etingof/pyasn1\nAuthor: Ilya Etingof\nAuthor-email: etingof@gmail.com\nMaintainer: Ilya Etingof <etingof@gmail.com>\nLicense: BSD\nPlatform: any\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Environment :: Console\nClassifier: Intended Audience :: Developers\nClassifier: Intended Audience :: Education\nClassifier: Intended Audience :: Information Technology\nClassifier: Intended Audience :: System Administrators\nClassifier: Intended Audience :: Telecommunications Industry\nClassifier: License :: OSI Approved :: BSD License\nClassifier: Natural Language :: English\nClassifier: Operating System :: OS Independent\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.4\nClassifier: Programming Language :: Python :: 2.5\nClassifier: Programming Language :: Python :: 2.6\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.2\nClassifier: Programming Language :: Python :: 3.3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nClassifier: Topic :: Communications\nClassifier: Topic :: Software Development :: Libraries :: Python Modules\n\nPure-Python implementation of ASN.1 types and DER/BER/CER codecs (X.208)\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1-0.4.7.dist-info/RECORD",
    "content": "pyasn1-0.4.7.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\npyasn1-0.4.7.dist-info/LICENSE.rst,sha256=IsXMaSKrXWn7oy2MXuTN0UmBUIy1OvwOvYVZOEf9laU,1334\r\npyasn1-0.4.7.dist-info/METADATA,sha256=Qn9Feg1hgw8UV4mXmHZOOdHGdZL0-XmPMOzDcvEN_Js,1521\r\npyasn1-0.4.7.dist-info/RECORD,,\r\npyasn1-0.4.7.dist-info/WHEEL,sha256=h_aVn5OB2IERUjMbi2pucmR_zzWJtk303YXvhh60NJ8,110\r\npyasn1-0.4.7.dist-info/top_level.txt,sha256=dnNEQt3nIDIO5mSCCOB5obQHrjDOUsRycdBujc2vrWE,7\r\npyasn1-0.4.7.dist-info/zip-safe,sha256=AbpHGcgLb-kRsJGnwFEktk7uzpZOCcBY74-YBdrKVGs,1\r\npyasn1/__init__.py,sha256=XYfXE9uSoZjOeFLX8M4qe79YnSKWK-MJyZTcPgGbx50,175\r\npyasn1/__pycache__/__init__.cpython-36.pyc,,\r\npyasn1/__pycache__/debug.cpython-36.pyc,,\r\npyasn1/__pycache__/error.cpython-36.pyc,,\r\npyasn1/codec/__init__.py,sha256=EEDlJYS172EH39GUidN_8FbkNcWY9OVV8e30AV58pn0,59\r\npyasn1/codec/__pycache__/__init__.cpython-36.pyc,,\r\npyasn1/codec/ber/__init__.py,sha256=EEDlJYS172EH39GUidN_8FbkNcWY9OVV8e30AV58pn0,59\r\npyasn1/codec/ber/__pycache__/__init__.cpython-36.pyc,,\r\npyasn1/codec/ber/__pycache__/decoder.cpython-36.pyc,,\r\npyasn1/codec/ber/__pycache__/encoder.cpython-36.pyc,,\r\npyasn1/codec/ber/__pycache__/eoo.cpython-36.pyc,,\r\npyasn1/codec/ber/decoder.py,sha256=oNKgtMafEOX0C-EvmCclThMO5mmdoRtFL1JkUYd4zN0,58234\r\npyasn1/codec/ber/encoder.py,sha256=xHl01PCIAiHZXev4x01sjbCgAUKcsTT6SzaLI3nt-9E,27741\r\npyasn1/codec/ber/eoo.py,sha256=eZ6lEyHdayMcMmNqtceDIyzf7u5lOeZoRK-WEUxVThI,626\r\npyasn1/codec/cer/__init__.py,sha256=EEDlJYS172EH39GUidN_8FbkNcWY9OVV8e30AV58pn0,59\r\npyasn1/codec/cer/__pycache__/__init__.cpython-36.pyc,,\r\npyasn1/codec/cer/__pycache__/decoder.cpython-36.pyc,,\r\npyasn1/codec/cer/__pycache__/encoder.cpython-36.pyc,,\r\npyasn1/codec/cer/decoder.py,sha256=ZYBqtDGNiYmKDpKDvioMDf-TYVWoJeZY3I8TEAKuk5s,3745\r\npyasn1/codec/cer/encoder.py,sha256=PGtzcIelIHj5d5Yqc5FATMEIWCJybQYFlCaK1gy-NIA,9409\r\npyasn1/codec/der/__init__.py,sha256=EEDlJYS172EH39GUidN_8FbkNcWY9OVV8e30AV58pn0,59\r\npyasn1/codec/der/__pycache__/__init__.cpython-36.pyc,,\r\npyasn1/codec/der/__pycache__/decoder.cpython-36.pyc,,\r\npyasn1/codec/der/__pycache__/encoder.cpython-36.pyc,,\r\npyasn1/codec/der/decoder.py,sha256=kinXcogMDPGlR3f7hmAxRv2YbQyeP-UhuKM0r8gkbeA,2722\r\npyasn1/codec/der/encoder.py,sha256=ZfRRxSCefQyLg0DLNb4zllaYf5_AWGIv3SPzB83Ln2I,3073\r\npyasn1/codec/native/__init__.py,sha256=EEDlJYS172EH39GUidN_8FbkNcWY9OVV8e30AV58pn0,59\r\npyasn1/codec/native/__pycache__/__init__.cpython-36.pyc,,\r\npyasn1/codec/native/__pycache__/decoder.cpython-36.pyc,,\r\npyasn1/codec/native/__pycache__/encoder.cpython-36.pyc,,\r\npyasn1/codec/native/decoder.py,sha256=4Q29tdKyytK3Oz-m94MSWxxPi_GhcBKvUfvPNKQcL0Y,7671\r\npyasn1/codec/native/encoder.py,sha256=0eMLWR49dwMA1X4si0XswR1kX1aDAWyCeUNTpEbChag,8002\r\npyasn1/compat/__init__.py,sha256=EEDlJYS172EH39GUidN_8FbkNcWY9OVV8e30AV58pn0,59\r\npyasn1/compat/__pycache__/__init__.cpython-36.pyc,,\r\npyasn1/compat/__pycache__/binary.cpython-36.pyc,,\r\npyasn1/compat/__pycache__/calling.cpython-36.pyc,,\r\npyasn1/compat/__pycache__/dateandtime.cpython-36.pyc,,\r\npyasn1/compat/__pycache__/integer.cpython-36.pyc,,\r\npyasn1/compat/__pycache__/octets.cpython-36.pyc,,\r\npyasn1/compat/__pycache__/string.cpython-36.pyc,,\r\npyasn1/compat/binary.py,sha256=mgWqHmr_SMEdB2WVVr6jyYMnodSbPP6IByE5qKccWLM,698\r\npyasn1/compat/calling.py,sha256=uTk3nJtGrElqJi8t34SoO8-eWFBG0gwNhXrlo1YmFEE,379\r\npyasn1/compat/dateandtime.py,sha256=zHvXXBp4t3XJ6teg_tz6qgNDevzd93qnrLoEbNxZQ_E,482\r\npyasn1/compat/integer.py,sha256=k6tqyxXMC0zJoU-Rz4oUPPoUpTmWXE6Prnzu0tkmmks,2988\r\npyasn1/compat/octets.py,sha256=ICe-DVLBIOHmNSz-sp3ioMh--smodJ4VW3Ju0ogJMWA,1359\r\npyasn1/compat/string.py,sha256=exqXJmPM6vYj4MjzsjciQdpUcJprRdgrLma8I4UcYHA,505\r\npyasn1/debug.py,sha256=HWGbLlEPLoCNyHqBd1Vd_KK91TppEn3CA4YgUxktT2k,3726\r\npyasn1/error.py,sha256=DIn2FWY3ACYNbk_42b3ny2bevkehpK2lOqfAsfdkvBE,2257\r\npyasn1/type/__init__.py,sha256=EEDlJYS172EH39GUidN_8FbkNcWY9OVV8e30AV58pn0,59\r\npyasn1/type/__pycache__/__init__.cpython-36.pyc,,\r\npyasn1/type/__pycache__/base.cpython-36.pyc,,\r\npyasn1/type/__pycache__/char.cpython-36.pyc,,\r\npyasn1/type/__pycache__/constraint.cpython-36.pyc,,\r\npyasn1/type/__pycache__/error.cpython-36.pyc,,\r\npyasn1/type/__pycache__/namedtype.cpython-36.pyc,,\r\npyasn1/type/__pycache__/namedval.cpython-36.pyc,,\r\npyasn1/type/__pycache__/opentype.cpython-36.pyc,,\r\npyasn1/type/__pycache__/tag.cpython-36.pyc,,\r\npyasn1/type/__pycache__/tagmap.cpython-36.pyc,,\r\npyasn1/type/__pycache__/univ.cpython-36.pyc,,\r\npyasn1/type/__pycache__/useful.cpython-36.pyc,,\r\npyasn1/type/base.py,sha256=TX7qdOX3EPiY7-11MY4fwK2Hy6nQsrdQ_M41aUcApno,22386\r\npyasn1/type/char.py,sha256=5HH8r1IqZMDCsfDlQHVCRphLlFuZ93bE2NW78CgeUTI,11397\r\npyasn1/type/constraint.py,sha256=4DqdqrwhE8tafg2QRLh0UpHYBay_F2-WcX_ClaxfNSg,20348\r\npyasn1/type/error.py,sha256=4_BHdjX-AL5WMTpU-tX1Nfo_P88c2z1sDvqPU-S9Bns,246\r\npyasn1/type/namedtype.py,sha256=VIL3H3oPgA0zNrDSeAhKmi4CZGTb69uDBVNJzzRk3wM,16368\r\npyasn1/type/namedval.py,sha256=dXYWiVTihvBy4RiebGY3AlIXsJvW78mJ1L7JSw-H7Qw,4886\r\npyasn1/type/opentype.py,sha256=pUpnPqv8o4AFeIsmGHDTFfuxXAq7FvG3hrTEnoAgBO8,2848\r\npyasn1/type/tag.py,sha256=nAK54C0_F_DL4_IaWRthIfIYBOTuXZoVVcbcbqgZiVA,9486\r\npyasn1/type/tagmap.py,sha256=2bwm0hqxG2gvXYheOI_iasfl2Z_B93qU7y39EHteUvs,2998\r\npyasn1/type/univ.py,sha256=FXc_VOStZfC-xIVTznpFO0qTq1aO4XyJFU0ayQWgPMY,108921\r\npyasn1/type/useful.py,sha256=r_K6UhgcrJ0ej658X-s9522I9T7oYVdmEKcbXTkZMds,5368\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1-0.4.7.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.33.4)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1-0.4.7.dist-info/top_level.txt",
    "content": "pyasn1\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1-0.4.7.dist-info/zip-safe",
    "content": "\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/__init__.py",
    "content": "# http://www.python.org/dev/peps/pep-0396/\n__version__ = '0.2.7'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/pem.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\nimport base64\nimport sys\n\nstSpam, stHam, stDump = 0, 1, 2\n\n\n# The markers parameters is in form ('start1', 'stop1'), ('start2', 'stop2')...\n# Return is (marker-index, substrate)\ndef readPemBlocksFromFile(fileObj, *markers):\n    startMarkers = dict(map(lambda x: (x[1], x[0]),\n                            enumerate(map(lambda y: y[0], markers))))\n    stopMarkers = dict(map(lambda x: (x[1], x[0]),\n                           enumerate(map(lambda y: y[1], markers))))\n    idx = -1\n    substrate = ''\n    certLines = []\n    state = stSpam\n    while True:\n        certLine = fileObj.readline()\n        if not certLine:\n            break\n        certLine = certLine.strip()\n        if state == stSpam:\n            if certLine in startMarkers:\n                certLines = []\n                idx = startMarkers[certLine]\n                state = stHam\n                continue\n        if state == stHam:\n            if certLine in stopMarkers and stopMarkers[certLine] == idx:\n                state = stDump\n            else:\n                certLines.append(certLine)\n        if state == stDump:\n            if sys.version_info[0] <= 2:\n                substrate = ''.join([base64.b64decode(x) for x in certLines])\n            else:\n                substrate = ''.encode().join([base64.b64decode(x.encode()) for x in certLines])\n            break\n    return idx, substrate\n\n\n# Backward compatibility routine\ndef readPemFromFile(fileObj,\n                    startMarker='-----BEGIN CERTIFICATE-----',\n                    endMarker='-----END CERTIFICATE-----'):\n    idx, substrate = readPemBlocksFromFile(fileObj, (startMarker, endMarker))\n    return substrate\n\n\ndef readBase64fromText(text):\n    if sys.version_info[0] <= 2:\n        return base64.b64decode(text)\n    else:\n        return base64.b64decode(text.encode())\n\n\ndef readBase64FromFile(fileObj):\n    return readBase64fromText(fileObj.read())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc1155.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# SNMPv1 message syntax\n#\n# ASN.1 source from:\n# http://www.ietf.org/rfc/rfc1155.txt\n#\n# Sample captures from:\n# http://wiki.wireshark.org/SampleCaptures/\n#\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\n\nclass ObjectName(univ.ObjectIdentifier):\n    pass\n\n\nclass SimpleSyntax(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('number', univ.Integer()),\n        namedtype.NamedType('string', univ.OctetString()),\n        namedtype.NamedType('object', univ.ObjectIdentifier()),\n        namedtype.NamedType('empty', univ.Null())\n    )\n\n\nclass IpAddress(univ.OctetString):\n    tagSet = univ.OctetString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 0)\n    )\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueSizeConstraint(\n        4, 4\n    )\n\n\nclass NetworkAddress(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('internet', IpAddress())\n    )\n\n\nclass Counter(univ.Integer):\n    tagSet = univ.Integer.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 1)\n    )\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueRangeConstraint(\n        0, 4294967295\n    )\n\n\nclass Gauge(univ.Integer):\n    tagSet = univ.Integer.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 2)\n    )\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueRangeConstraint(\n        0, 4294967295\n    )\n\n\nclass TimeTicks(univ.Integer):\n    tagSet = univ.Integer.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 3)\n    )\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueRangeConstraint(\n        0, 4294967295\n    )\n\n\nclass Opaque(univ.OctetString):\n    tagSet = univ.OctetString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 4)\n    )\n\n\nclass ApplicationSyntax(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('address', NetworkAddress()),\n        namedtype.NamedType('counter', Counter()),\n        namedtype.NamedType('gauge', Gauge()),\n        namedtype.NamedType('ticks', TimeTicks()),\n        namedtype.NamedType('arbitrary', Opaque())\n    )\n\n\nclass ObjectSyntax(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('simple', SimpleSyntax()),\n        namedtype.NamedType('application-wide', ApplicationSyntax())\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc1157.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# SNMPv1 message syntax\n#\n# ASN.1 source from:\n# http://www.ietf.org/rfc/rfc1157.txt\n#\n# Sample captures from:\n# http://wiki.wireshark.org/SampleCaptures/\n#\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc1155\n\n\nclass Version(univ.Integer):\n    namedValues = namedval.NamedValues(\n        ('version-1', 0)\n    )\n    defaultValue = 0\n\n\nclass Community(univ.OctetString):\n    pass\n\n\nclass RequestID(univ.Integer):\n    pass\n\n\nclass ErrorStatus(univ.Integer):\n    namedValues = namedval.NamedValues(\n        ('noError', 0),\n        ('tooBig', 1),\n        ('noSuchName', 2),\n        ('badValue', 3),\n        ('readOnly', 4),\n        ('genErr', 5)\n    )\n\n\nclass ErrorIndex(univ.Integer):\n    pass\n\n\nclass VarBind(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('name', rfc1155.ObjectName()),\n        namedtype.NamedType('value', rfc1155.ObjectSyntax())\n    )\n\n\nclass VarBindList(univ.SequenceOf):\n    componentType = VarBind()\n\n\nclass _RequestBase(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('request-id', RequestID()),\n        namedtype.NamedType('error-status', ErrorStatus()),\n        namedtype.NamedType('error-index', ErrorIndex()),\n        namedtype.NamedType('variable-bindings', VarBindList())\n    )\n\n\nclass GetRequestPDU(_RequestBase):\n    tagSet = _RequestBase.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)\n    )\n\n\nclass GetNextRequestPDU(_RequestBase):\n    tagSet = _RequestBase.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)\n    )\n\n\nclass GetResponsePDU(_RequestBase):\n    tagSet = _RequestBase.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2)\n    )\n\n\nclass SetRequestPDU(_RequestBase):\n    tagSet = _RequestBase.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3)\n    )\n\n\nclass TrapPDU(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('enterprise', univ.ObjectIdentifier()),\n        namedtype.NamedType('agent-addr', rfc1155.NetworkAddress()),\n        namedtype.NamedType('generic-trap', univ.Integer().clone(\n            namedValues=namedval.NamedValues(('coldStart', 0), ('warmStart', 1), ('linkDown', 2), ('linkUp', 3),\n                                             ('authenticationFailure', 4), ('egpNeighborLoss', 5),\n                                             ('enterpriseSpecific', 6)))),\n        namedtype.NamedType('specific-trap', univ.Integer()),\n        namedtype.NamedType('time-stamp', rfc1155.TimeTicks()),\n        namedtype.NamedType('variable-bindings', VarBindList())\n    )\n\n\nclass Pdus(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('get-request', GetRequestPDU()),\n        namedtype.NamedType('get-next-request', GetNextRequestPDU()),\n        namedtype.NamedType('get-response', GetResponsePDU()),\n        namedtype.NamedType('set-request', SetRequestPDU()),\n        namedtype.NamedType('trap', TrapPDU())\n    )\n\n\nclass Message(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.NamedType('community', Community()),\n        namedtype.NamedType('data', Pdus())\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc1901.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# SNMPv2c message syntax\n#\n# ASN.1 source from:\n# http://www.ietf.org/rfc/rfc1901.txt\n#\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import univ\n\n\nclass Message(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', univ.Integer(namedValues=namedval.NamedValues(('version-2c', 1)))),\n        namedtype.NamedType('community', univ.OctetString()),\n        namedtype.NamedType('data', univ.Any())\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc1902.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# SNMPv2c message syntax\n#\n# ASN.1 source from:\n# http://www.ietf.org/rfc/rfc1902.txt\n#\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\n\nclass Integer(univ.Integer):\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueRangeConstraint(\n        -2147483648, 2147483647\n    )\n\n\nclass Integer32(univ.Integer):\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueRangeConstraint(\n        -2147483648, 2147483647\n    )\n\n\nclass OctetString(univ.OctetString):\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueSizeConstraint(\n        0, 65535\n    )\n\n\nclass IpAddress(univ.OctetString):\n    tagSet = univ.OctetString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 0x00)\n    )\n    subtypeSpec = univ.OctetString.subtypeSpec + constraint.ValueSizeConstraint(\n        4, 4\n    )\n\n\nclass Counter32(univ.Integer):\n    tagSet = univ.Integer.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 0x01)\n    )\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueRangeConstraint(\n        0, 4294967295\n    )\n\n\nclass Gauge32(univ.Integer):\n    tagSet = univ.Integer.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 0x02)\n    )\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueRangeConstraint(\n        0, 4294967295\n    )\n\n\nclass Unsigned32(univ.Integer):\n    tagSet = univ.Integer.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 0x02)\n    )\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueRangeConstraint(\n        0, 4294967295\n    )\n\n\nclass TimeTicks(univ.Integer):\n    tagSet = univ.Integer.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 0x03)\n    )\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueRangeConstraint(\n        0, 4294967295\n    )\n\n\nclass Opaque(univ.OctetString):\n    tagSet = univ.OctetString.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 0x04)\n    )\n\n\nclass Counter64(univ.Integer):\n    tagSet = univ.Integer.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 0x06)\n    )\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueRangeConstraint(\n        0, 18446744073709551615\n    )\n\n\nclass Bits(univ.OctetString):\n    pass\n\n\nclass ObjectName(univ.ObjectIdentifier):\n    pass\n\n\nclass SimpleSyntax(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('integer-value', Integer()),\n        namedtype.NamedType('string-value', OctetString()),\n        namedtype.NamedType('objectID-value', univ.ObjectIdentifier())\n    )\n\n\nclass ApplicationSyntax(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('ipAddress-value', IpAddress()),\n        namedtype.NamedType('counter-value', Counter32()),\n        namedtype.NamedType('timeticks-value', TimeTicks()),\n        namedtype.NamedType('arbitrary-value', Opaque()),\n        namedtype.NamedType('big-counter-value', Counter64()),\n        # This conflicts with Counter32\n        #        namedtype.NamedType('unsigned-integer-value', Unsigned32()),\n        namedtype.NamedType('gauge32-value', Gauge32())\n    )  # BITS misplaced?\n\n\nclass ObjectSyntax(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('simple', SimpleSyntax()),\n        namedtype.NamedType('application-wide', ApplicationSyntax())\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc1905.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# SNMPv2c PDU syntax\n#\n# ASN.1 source from:\n# http://www.ietf.org/rfc/rfc1905.txt\n#\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc1902\n\nmax_bindings = rfc1902.Integer(2147483647)\n\n\nclass _BindValue(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('value', rfc1902.ObjectSyntax()),\n        namedtype.NamedType('unSpecified', univ.Null()),\n        namedtype.NamedType('noSuchObject',\n                            univ.Null().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.NamedType('noSuchInstance',\n                            univ.Null().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.NamedType('endOfMibView',\n                            univ.Null().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n    )\n\n\nclass VarBind(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('name', rfc1902.ObjectName()),\n        namedtype.NamedType('', _BindValue())\n    )\n\n\nclass VarBindList(univ.SequenceOf):\n    componentType = VarBind()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(\n        0, max_bindings\n    )\n\n\nclass PDU(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('request-id', rfc1902.Integer32()),\n        namedtype.NamedType('error-status', univ.Integer(\n            namedValues=namedval.NamedValues(('noError', 0), ('tooBig', 1), ('noSuchName', 2), ('badValue', 3),\n                                             ('readOnly', 4), ('genErr', 5), ('noAccess', 6), ('wrongType', 7),\n                                             ('wrongLength', 8), ('wrongEncoding', 9), ('wrongValue', 10),\n                                             ('noCreation', 11), ('inconsistentValue', 12), ('resourceUnavailable', 13),\n                                             ('commitFailed', 14), ('undoFailed', 15), ('authorizationError', 16),\n                                             ('notWritable', 17), ('inconsistentName', 18)))),\n        namedtype.NamedType('error-index',\n                            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, max_bindings))),\n        namedtype.NamedType('variable-bindings', VarBindList())\n    )\n\n\nclass BulkPDU(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('request-id', rfc1902.Integer32()),\n        namedtype.NamedType('non-repeaters',\n                            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, max_bindings))),\n        namedtype.NamedType('max-repetitions',\n                            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, max_bindings))),\n        namedtype.NamedType('variable-bindings', VarBindList())\n    )\n\n\nclass GetRequestPDU(PDU):\n    tagSet = PDU.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)\n    )\n\n\nclass GetNextRequestPDU(PDU):\n    tagSet = PDU.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)\n    )\n\n\nclass ResponsePDU(PDU):\n    tagSet = PDU.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2)\n    )\n\n\nclass SetRequestPDU(PDU):\n    tagSet = PDU.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3)\n    )\n\n\nclass GetBulkRequestPDU(BulkPDU):\n    tagSet = PDU.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 5)\n    )\n\n\nclass InformRequestPDU(PDU):\n    tagSet = PDU.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 6)\n    )\n\n\nclass SNMPv2TrapPDU(PDU):\n    tagSet = PDU.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 7)\n    )\n\n\nclass ReportPDU(PDU):\n    tagSet = PDU.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 8)\n    )\n\n\nclass PDUs(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('get-request', GetRequestPDU()),\n        namedtype.NamedType('get-next-request', GetNextRequestPDU()),\n        namedtype.NamedType('get-bulk-request', GetBulkRequestPDU()),\n        namedtype.NamedType('response', ResponsePDU()),\n        namedtype.NamedType('set-request', SetRequestPDU()),\n        namedtype.NamedType('inform-request', InformRequestPDU()),\n        namedtype.NamedType('snmpV2-trap', SNMPv2TrapPDU()),\n        namedtype.NamedType('report', ReportPDU())\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc2251.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# LDAP message syntax\n#\n# ASN.1 source from:\n# http://www.trl.ibm.com/projects/xml/xss4j/data/asn1/grammars/ldap.asn\n#\n# Sample captures from:\n# http://wiki.wireshark.org/SampleCaptures/\n#\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nmaxInt = univ.Integer(2147483647)\n\n\nclass LDAPString(univ.OctetString):\n    pass\n\n\nclass LDAPOID(univ.OctetString):\n    pass\n\n\nclass LDAPDN(LDAPString):\n    pass\n\n\nclass RelativeLDAPDN(LDAPString):\n    pass\n\n\nclass AttributeType(LDAPString):\n    pass\n\n\nclass AttributeDescription(LDAPString):\n    pass\n\n\nclass AttributeDescriptionList(univ.SequenceOf):\n    componentType = AttributeDescription()\n\n\nclass AttributeValue(univ.OctetString):\n    pass\n\n\nclass AssertionValue(univ.OctetString):\n    pass\n\n\nclass AttributeValueAssertion(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('attributeDesc', AttributeDescription()),\n        namedtype.NamedType('assertionValue', AssertionValue())\n    )\n\n\nclass Attribute(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('type', AttributeDescription()),\n        namedtype.NamedType('vals', univ.SetOf(componentType=AttributeValue()))\n    )\n\n\nclass MatchingRuleId(LDAPString):\n    pass\n\n\nclass Control(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('controlType', LDAPOID()),\n        namedtype.DefaultedNamedType('criticality', univ.Boolean('False')),\n        namedtype.OptionalNamedType('controlValue', univ.OctetString())\n    )\n\n\nclass Controls(univ.SequenceOf):\n    componentType = Control()\n\n\nclass LDAPURL(LDAPString):\n    pass\n\n\nclass Referral(univ.SequenceOf):\n    componentType = LDAPURL()\n\n\nclass SaslCredentials(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('mechanism', LDAPString()),\n        namedtype.OptionalNamedType('credentials', univ.OctetString())\n    )\n\n\nclass AuthenticationChoice(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('simple', univ.OctetString().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.NamedType('reserved-1', univ.OctetString().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.NamedType('reserved-2', univ.OctetString().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n        namedtype.NamedType('sasl',\n                            SaslCredentials().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n    )\n\n\nclass BindRequest(univ.Sequence):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 0)\n    )\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(1, 127))),\n        namedtype.NamedType('name', LDAPDN()),\n        namedtype.NamedType('authentication', AuthenticationChoice())\n    )\n\n\nclass PartialAttributeList(univ.SequenceOf):\n    componentType = univ.Sequence(\n        componentType=namedtype.NamedTypes(\n            namedtype.NamedType('type', AttributeDescription()),\n            namedtype.NamedType('vals', univ.SetOf(componentType=AttributeValue()))\n        )\n    )\n\n\nclass SearchResultEntry(univ.Sequence):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 4)\n    )\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('objectName', LDAPDN()),\n        namedtype.NamedType('attributes', PartialAttributeList())\n    )\n\n\nclass MatchingRuleAssertion(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('matchingRule', MatchingRuleId().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.OptionalNamedType('type', AttributeDescription().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n        namedtype.NamedType('matchValue',\n                            AssertionValue().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n        namedtype.DefaultedNamedType('dnAttributes', univ.Boolean('False').subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4)))\n    )\n\n\nclass SubstringFilter(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('type', AttributeDescription()),\n        namedtype.NamedType('substrings',\n            univ.SequenceOf(\n                componentType=univ.Choice(\n                    componentType=namedtype.NamedTypes(\n                        namedtype.NamedType(\n                            'initial', LDAPString().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))\n                        ),\n                        namedtype.NamedType(\n                            'any', LDAPString().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))\n                        ),\n                        namedtype.NamedType(\n                            'final', LDAPString().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))\n                        )\n                    )\n                )\n            )\n        )\n    )\n\n\n# Ugly hack to handle recursive Filter reference (up to 3-levels deep).\n\nclass Filter3(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('equalityMatch', AttributeValueAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3))),\n        namedtype.NamedType('substrings', SubstringFilter().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 4))),\n        namedtype.NamedType('greaterOrEqual', AttributeValueAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 5))),\n        namedtype.NamedType('lessOrEqual', AttributeValueAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 6))),\n        namedtype.NamedType('present', AttributeDescription().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 7))),\n        namedtype.NamedType('approxMatch', AttributeValueAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 8))),\n        namedtype.NamedType('extensibleMatch', MatchingRuleAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 9)))\n    )\n\n\nclass Filter2(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('and', univ.SetOf(componentType=Filter3()).subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.NamedType('or', univ.SetOf(componentType=Filter3()).subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n        namedtype.NamedType('not',\n                            Filter3().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2))),\n        namedtype.NamedType('equalityMatch', AttributeValueAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3))),\n        namedtype.NamedType('substrings', SubstringFilter().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 4))),\n        namedtype.NamedType('greaterOrEqual', AttributeValueAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 5))),\n        namedtype.NamedType('lessOrEqual', AttributeValueAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 6))),\n        namedtype.NamedType('present', AttributeDescription().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 7))),\n        namedtype.NamedType('approxMatch', AttributeValueAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 8))),\n        namedtype.NamedType('extensibleMatch', MatchingRuleAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 9)))\n    )\n\n\nclass Filter(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('and', univ.SetOf(componentType=Filter2()).subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.NamedType('or', univ.SetOf(componentType=Filter2()).subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n        namedtype.NamedType('not',\n                            Filter2().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2))),\n        namedtype.NamedType('equalityMatch', AttributeValueAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3))),\n        namedtype.NamedType('substrings', SubstringFilter().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 4))),\n        namedtype.NamedType('greaterOrEqual', AttributeValueAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 5))),\n        namedtype.NamedType('lessOrEqual', AttributeValueAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 6))),\n        namedtype.NamedType('present', AttributeDescription().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 7))),\n        namedtype.NamedType('approxMatch', AttributeValueAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 8))),\n        namedtype.NamedType('extensibleMatch', MatchingRuleAssertion().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 9)))\n    )\n\n\n# End of Filter hack\n\nclass SearchRequest(univ.Sequence):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 3)\n    )\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('baseObject', LDAPDN()),\n        namedtype.NamedType('scope', univ.Enumerated(\n            namedValues=namedval.NamedValues(('baseObject', 0), ('singleLevel', 1), ('wholeSubtree', 2)))),\n        namedtype.NamedType('derefAliases', univ.Enumerated(\n            namedValues=namedval.NamedValues(('neverDerefAliases', 0), ('derefInSearching', 1),\n                                             ('derefFindingBaseObj', 2), ('derefAlways', 3)))),\n        namedtype.NamedType('sizeLimit',\n                            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, maxInt))),\n        namedtype.NamedType('timeLimit',\n                            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, maxInt))),\n        namedtype.NamedType('typesOnly', univ.Boolean()),\n        namedtype.NamedType('filter', Filter()),\n        namedtype.NamedType('attributes', AttributeDescriptionList())\n    )\n\n\nclass UnbindRequest(univ.Null):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatSimple, 2)\n    )\n\n\nclass BindResponse(univ.Sequence):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 1)\n    )\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('resultCode', univ.Enumerated(\n            namedValues=namedval.NamedValues(('success', 0), ('operationsError', 1), ('protocolError', 2),\n                                             ('timeLimitExceeded', 3), ('sizeLimitExceeded', 4), ('compareFalse', 5),\n                                             ('compareTrue', 6), ('authMethodNotSupported', 7),\n                                             ('strongAuthRequired', 8), ('reserved-9', 9), ('referral', 10),\n                                             ('adminLimitExceeded', 11), ('unavailableCriticalExtension', 12),\n                                             ('confidentialityRequired', 13), ('saslBindInProgress', 14),\n                                             ('noSuchAttribute', 16), ('undefinedAttributeType', 17),\n                                             ('inappropriateMatching', 18), ('constraintViolation', 19),\n                                             ('attributeOrValueExists', 20), ('invalidAttributeSyntax', 21),\n                                             ('noSuchObject', 32), ('aliasProblem', 33), ('invalidDNSyntax', 34),\n                                             ('reserved-35', 35), ('aliasDereferencingProblem', 36),\n                                             ('inappropriateAuthentication', 48), ('invalidCredentials', 49),\n                                             ('insufficientAccessRights', 50), ('busy', 51), ('unavailable', 52),\n                                             ('unwillingToPerform', 53), ('loopDetect', 54), ('namingViolation', 64),\n                                             ('objectClassViolation', 65), ('notAllowedOnNonLeaf', 66),\n                                             ('notAllowedOnRDN', 67), ('entryAlreadyExists', 68),\n                                             ('objectClassModsProhibited', 69), ('reserved-70', 70),\n                                             ('affectsMultipleDSAs', 71), ('other', 80), ('reserved-81', 81),\n                                             ('reserved-82', 82), ('reserved-83', 83), ('reserved-84', 84),\n                                             ('reserved-85', 85), ('reserved-86', 86), ('reserved-87', 87),\n                                             ('reserved-88', 88), ('reserved-89', 89), ('reserved-90', 90)))),\n        namedtype.NamedType('matchedDN', LDAPDN()),\n        namedtype.NamedType('errorMessage', LDAPString()),\n        namedtype.OptionalNamedType('referral', Referral().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3))),\n        namedtype.OptionalNamedType('serverSaslCreds', univ.OctetString().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 7)))\n    )\n\n\nclass LDAPResult(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('resultCode', univ.Enumerated(\n            namedValues=namedval.NamedValues(('success', 0), ('operationsError', 1), ('protocolError', 2),\n                                             ('timeLimitExceeded', 3), ('sizeLimitExceeded', 4), ('compareFalse', 5),\n                                             ('compareTrue', 6), ('authMethodNotSupported', 7),\n                                             ('strongAuthRequired', 8), ('reserved-9', 9), ('referral', 10),\n                                             ('adminLimitExceeded', 11), ('unavailableCriticalExtension', 12),\n                                             ('confidentialityRequired', 13), ('saslBindInProgress', 14),\n                                             ('noSuchAttribute', 16), ('undefinedAttributeType', 17),\n                                             ('inappropriateMatching', 18), ('constraintViolation', 19),\n                                             ('attributeOrValueExists', 20), ('invalidAttributeSyntax', 21),\n                                             ('noSuchObject', 32), ('aliasProblem', 33), ('invalidDNSyntax', 34),\n                                             ('reserved-35', 35), ('aliasDereferencingProblem', 36),\n                                             ('inappropriateAuthentication', 48), ('invalidCredentials', 49),\n                                             ('insufficientAccessRights', 50), ('busy', 51), ('unavailable', 52),\n                                             ('unwillingToPerform', 53), ('loopDetect', 54), ('namingViolation', 64),\n                                             ('objectClassViolation', 65), ('notAllowedOnNonLeaf', 66),\n                                             ('notAllowedOnRDN', 67), ('entryAlreadyExists', 68),\n                                             ('objectClassModsProhibited', 69), ('reserved-70', 70),\n                                             ('affectsMultipleDSAs', 71), ('other', 80), ('reserved-81', 81),\n                                             ('reserved-82', 82), ('reserved-83', 83), ('reserved-84', 84),\n                                             ('reserved-85', 85), ('reserved-86', 86), ('reserved-87', 87),\n                                             ('reserved-88', 88), ('reserved-89', 89), ('reserved-90', 90)))),\n        namedtype.NamedType('matchedDN', LDAPDN()),\n        namedtype.NamedType('errorMessage', LDAPString()),\n        namedtype.OptionalNamedType('referral', Referral().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3)))\n    )\n\n\nclass SearchResultReference(univ.SequenceOf):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 19)\n    )\n    componentType = LDAPURL()\n\n\nclass SearchResultDone(LDAPResult):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 5)\n    )\n\n\nclass AttributeTypeAndValues(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('type', AttributeDescription()),\n        namedtype.NamedType('vals', univ.SetOf(componentType=AttributeValue()))\n    )\n\n\nclass ModifyRequest(univ.Sequence):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 6)\n    )\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('object', LDAPDN()),\n        namedtype.NamedType('modification',\n            univ.SequenceOf(\n                componentType=univ.Sequence(\n                    componentType=namedtype.NamedTypes(\n                        namedtype.NamedType(\n                            'operation', univ.Enumerated(namedValues=namedval.NamedValues(('add', 0), ('delete', 1), ('replace', 2)))\n                        ),\n                        namedtype.NamedType('modification', AttributeTypeAndValues())))\n            )\n        )\n    )\n\n\nclass ModifyResponse(LDAPResult):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 7)\n    )\n\n\nclass AttributeList(univ.SequenceOf):\n    componentType = univ.Sequence(\n        componentType=namedtype.NamedTypes(\n           namedtype.NamedType('type', AttributeDescription()),\n           namedtype.NamedType('vals', univ.SetOf(componentType=AttributeValue()))\n        )\n    )\n\n\nclass AddRequest(univ.Sequence):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 8)\n    )\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('entry', LDAPDN()),\n        namedtype.NamedType('attributes', AttributeList())\n    )\n\n\nclass AddResponse(LDAPResult):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 9)\n    )\n\n\nclass DelRequest(LDAPResult):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 10)\n    )\n\n\nclass DelResponse(LDAPResult):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 11)\n    )\n\n\nclass ModifyDNRequest(univ.Sequence):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 12)\n    )\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('entry', LDAPDN()),\n        namedtype.NamedType('newrdn', RelativeLDAPDN()),\n        namedtype.NamedType('deleteoldrdn', univ.Boolean()),\n        namedtype.OptionalNamedType('newSuperior',\n                                    LDAPDN().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n\n    )\n\n\nclass ModifyDNResponse(LDAPResult):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 13)\n    )\n\n\nclass CompareRequest(univ.Sequence):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 14)\n    )\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('entry', LDAPDN()),\n        namedtype.NamedType('ava', AttributeValueAssertion())\n    )\n\n\nclass CompareResponse(LDAPResult):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 15)\n    )\n\n\nclass AbandonRequest(LDAPResult):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 16)\n    )\n\n\nclass ExtendedRequest(univ.Sequence):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 23)\n    )\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('requestName',\n                            LDAPOID().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('requestValue', univ.OctetString().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n    )\n\n\nclass ExtendedResponse(univ.Sequence):\n    tagSet = univ.Sequence.tagSet.tagImplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 24)\n    )\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('resultCode', univ.Enumerated(\n            namedValues=namedval.NamedValues(('success', 0), ('operationsError', 1), ('protocolError', 2),\n                                             ('timeLimitExceeded', 3), ('sizeLimitExceeded', 4), ('compareFalse', 5),\n                                             ('compareTrue', 6), ('authMethodNotSupported', 7),\n                                             ('strongAuthRequired', 8), ('reserved-9', 9), ('referral', 10),\n                                             ('adminLimitExceeded', 11), ('unavailableCriticalExtension', 12),\n                                             ('confidentialityRequired', 13), ('saslBindInProgress', 14),\n                                             ('noSuchAttribute', 16), ('undefinedAttributeType', 17),\n                                             ('inappropriateMatching', 18), ('constraintViolation', 19),\n                                             ('attributeOrValueExists', 20), ('invalidAttributeSyntax', 21),\n                                             ('noSuchObject', 32), ('aliasProblem', 33), ('invalidDNSyntax', 34),\n                                             ('reserved-35', 35), ('aliasDereferencingProblem', 36),\n                                             ('inappropriateAuthentication', 48), ('invalidCredentials', 49),\n                                             ('insufficientAccessRights', 50), ('busy', 51), ('unavailable', 52),\n                                             ('unwillingToPerform', 53), ('loopDetect', 54), ('namingViolation', 64),\n                                             ('objectClassViolation', 65), ('notAllowedOnNonLeaf', 66),\n                                             ('notAllowedOnRDN', 67), ('entryAlreadyExists', 68),\n                                             ('objectClassModsProhibited', 69), ('reserved-70', 70),\n                                             ('affectsMultipleDSAs', 71), ('other', 80), ('reserved-81', 81),\n                                             ('reserved-82', 82), ('reserved-83', 83), ('reserved-84', 84),\n                                             ('reserved-85', 85), ('reserved-86', 86), ('reserved-87', 87),\n                                             ('reserved-88', 88), ('reserved-89', 89), ('reserved-90', 90)))),\n        namedtype.NamedType('matchedDN', LDAPDN()),\n        namedtype.NamedType('errorMessage', LDAPString()),\n        namedtype.OptionalNamedType('referral', Referral().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3))),\n\n        namedtype.OptionalNamedType('responseName', LDAPOID().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 10))),\n        namedtype.OptionalNamedType('response', univ.OctetString().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 11)))\n    )\n\n\nclass MessageID(univ.Integer):\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueRangeConstraint(\n        0, maxInt\n    )\n\n\nclass LDAPMessage(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('messageID', MessageID()),\n        namedtype.NamedType(\n            'protocolOp', univ.Choice(\n                componentType=namedtype.NamedTypes(\n                    namedtype.NamedType('bindRequest', BindRequest()),\n                    namedtype.NamedType('bindResponse', BindResponse()),\n                    namedtype.NamedType('unbindRequest', UnbindRequest()),\n                    namedtype.NamedType('searchRequest', SearchRequest()),\n                    namedtype.NamedType('searchResEntry', SearchResultEntry()),\n                    namedtype.NamedType('searchResDone', SearchResultDone()),\n                    namedtype.NamedType('searchResRef', SearchResultReference()),\n                    namedtype.NamedType('modifyRequest', ModifyRequest()),\n                    namedtype.NamedType('modifyResponse', ModifyResponse()),\n                    namedtype.NamedType('addRequest', AddRequest()),\n                    namedtype.NamedType('addResponse', AddResponse()),\n                    namedtype.NamedType('delRequest', DelRequest()),\n                    namedtype.NamedType('delResponse', DelResponse()),\n                    namedtype.NamedType('modDNRequest', ModifyDNRequest()),\n                    namedtype.NamedType('modDNResponse', ModifyDNResponse()),\n                    namedtype.NamedType('compareRequest', CompareRequest()),\n                    namedtype.NamedType('compareResponse', CompareResponse()),\n                    namedtype.NamedType('abandonRequest', AbandonRequest()),\n                    namedtype.NamedType('extendedReq', ExtendedRequest()),\n                    namedtype.NamedType('extendedResp', ExtendedResponse())\n                )\n            )\n        ),\n        namedtype.OptionalNamedType('controls', Controls().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc2314.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# PKCS#10 syntax\n#\n# ASN.1 source from:\n# http://tools.ietf.org/html/rfc2314\n#\n# Sample captures could be obtained with \"openssl req\" command\n#\nfrom pyasn1_modules.rfc2459 import *\n\n\nclass Attributes(univ.SetOf):\n    componentType = Attribute()\n\n\nclass Version(univ.Integer):\n    pass\n\n\nclass CertificationRequestInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.NamedType('subject', Name()),\n        namedtype.NamedType('subjectPublicKeyInfo', SubjectPublicKeyInfo()),\n        namedtype.NamedType('attributes',\n                            Attributes().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n    )\n\n\nclass Signature(univ.BitString):\n    pass\n\n\nclass SignatureAlgorithmIdentifier(AlgorithmIdentifier):\n    pass\n\n\nclass CertificationRequest(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('certificationRequestInfo', CertificationRequestInfo()),\n        namedtype.NamedType('signatureAlgorithm', SignatureAlgorithmIdentifier()),\n        namedtype.NamedType('signature', Signature())\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc2315.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# PKCS#7 message syntax\n#\n# ASN.1 source from:\n# https://opensource.apple.com/source/Security/Security-55179.1/libsecurity_asn1/asn1/pkcs7.asn.auto.html\n#\n# Sample captures from:\n# openssl crl2pkcs7 -nocrl -certfile cert1.cer -out outfile.p7b\n#\nfrom pyasn1_modules.rfc2459 import *\n\n\nclass Attribute(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('type', AttributeType()),\n        namedtype.NamedType('values', univ.SetOf(componentType=AttributeValue()))\n    )\n\n\nclass AttributeValueAssertion(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('attributeType', AttributeType()),\n        namedtype.NamedType('attributeValue', AttributeValue(),\n                            openType=opentype.OpenType('type', certificateAttributesMap))\n    )\n\n\npkcs_7 = univ.ObjectIdentifier('1.2.840.113549.1.7')\ndata = univ.ObjectIdentifier('1.2.840.113549.1.7.1')\nsignedData = univ.ObjectIdentifier('1.2.840.113549.1.7.2')\nenvelopedData = univ.ObjectIdentifier('1.2.840.113549.1.7.3')\nsignedAndEnvelopedData = univ.ObjectIdentifier('1.2.840.113549.1.7.4')\ndigestedData = univ.ObjectIdentifier('1.2.840.113549.1.7.5')\nencryptedData = univ.ObjectIdentifier('1.2.840.113549.1.7.6')\n\n\nclass ContentType(univ.ObjectIdentifier):\n    pass\n\n\nclass ContentEncryptionAlgorithmIdentifier(AlgorithmIdentifier):\n    pass\n\n\nclass EncryptedContent(univ.OctetString):\n    pass\n\n\ncontentTypeMap = {}\n\n\nclass EncryptedContentInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('contentType', ContentType()),\n        namedtype.NamedType('contentEncryptionAlgorithm', ContentEncryptionAlgorithmIdentifier()),\n        namedtype.OptionalNamedType(\n            'encryptedContent', EncryptedContent().subtype(\n                implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)\n            ),\n            openType=opentype.OpenType('contentType', contentTypeMap)\n        )\n    )\n\n\nclass Version(univ.Integer):  # overrides x509.Version\n    pass\n\n\nclass EncryptedData(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.NamedType('encryptedContentInfo', EncryptedContentInfo())\n    )\n\n\nclass DigestAlgorithmIdentifier(AlgorithmIdentifier):\n    pass\n\n\nclass DigestAlgorithmIdentifiers(univ.SetOf):\n    componentType = DigestAlgorithmIdentifier()\n\n\nclass Digest(univ.OctetString):\n    pass\n\n\nclass ContentInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('contentType', ContentType()),\n        namedtype.OptionalNamedType(\n            'content',\n            univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)),\n            openType=opentype.OpenType('contentType', contentTypeMap)\n        )\n    )\n\n\nclass DigestedData(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.NamedType('digestAlgorithm', DigestAlgorithmIdentifier()),\n        namedtype.NamedType('contentInfo', ContentInfo()),\n        namedtype.NamedType('digest', Digest())\n    )\n\n\nclass IssuerAndSerialNumber(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('issuer', Name()),\n        namedtype.NamedType('serialNumber', CertificateSerialNumber())\n    )\n\n\nclass KeyEncryptionAlgorithmIdentifier(AlgorithmIdentifier):\n    pass\n\n\nclass EncryptedKey(univ.OctetString):\n    pass\n\n\nclass RecipientInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.NamedType('issuerAndSerialNumber', IssuerAndSerialNumber()),\n        namedtype.NamedType('keyEncryptionAlgorithm', KeyEncryptionAlgorithmIdentifier()),\n        namedtype.NamedType('encryptedKey', EncryptedKey())\n    )\n\n\nclass RecipientInfos(univ.SetOf):\n    componentType = RecipientInfo()\n\n\nclass Attributes(univ.SetOf):\n    componentType = Attribute()\n\n\nclass ExtendedCertificateInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.NamedType('certificate', Certificate()),\n        namedtype.NamedType('attributes', Attributes())\n    )\n\n\nclass SignatureAlgorithmIdentifier(AlgorithmIdentifier):\n    pass\n\n\nclass Signature(univ.BitString):\n    pass\n\n\nclass ExtendedCertificate(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('extendedCertificateInfo', ExtendedCertificateInfo()),\n        namedtype.NamedType('signatureAlgorithm', SignatureAlgorithmIdentifier()),\n        namedtype.NamedType('signature', Signature())\n    )\n\n\nclass ExtendedCertificateOrCertificate(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('certificate', Certificate()),\n        namedtype.NamedType('extendedCertificate', ExtendedCertificate().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n    )\n\n\nclass ExtendedCertificatesAndCertificates(univ.SetOf):\n    componentType = ExtendedCertificateOrCertificate()\n\n\nclass SerialNumber(univ.Integer):\n    pass\n\n\nclass CRLEntry(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('userCertificate', SerialNumber()),\n        namedtype.NamedType('revocationDate', useful.UTCTime())\n    )\n\n\nclass TBSCertificateRevocationList(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('signature', AlgorithmIdentifier()),\n        namedtype.NamedType('issuer', Name()),\n        namedtype.NamedType('lastUpdate', useful.UTCTime()),\n        namedtype.NamedType('nextUpdate', useful.UTCTime()),\n        namedtype.OptionalNamedType('revokedCertificates', univ.SequenceOf(componentType=CRLEntry()))\n    )\n\n\nclass CertificateRevocationList(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('tbsCertificateRevocationList', TBSCertificateRevocationList()),\n        namedtype.NamedType('signatureAlgorithm', AlgorithmIdentifier()),\n        namedtype.NamedType('signature', univ.BitString())\n    )\n\n\nclass CertificateRevocationLists(univ.SetOf):\n    componentType = CertificateRevocationList()\n\n\nclass DigestEncryptionAlgorithmIdentifier(AlgorithmIdentifier):\n    pass\n\n\nclass EncryptedDigest(univ.OctetString):\n    pass\n\n\nclass SignerInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.NamedType('issuerAndSerialNumber', IssuerAndSerialNumber()),\n        namedtype.NamedType('digestAlgorithm', DigestAlgorithmIdentifier()),\n        namedtype.OptionalNamedType('authenticatedAttributes', Attributes().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.NamedType('digestEncryptionAlgorithm', DigestEncryptionAlgorithmIdentifier()),\n        namedtype.NamedType('encryptedDigest', EncryptedDigest()),\n        namedtype.OptionalNamedType('unauthenticatedAttributes', Attributes().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n    )\n\n\nclass SignerInfos(univ.SetOf):\n    componentType = SignerInfo()\n\n\nclass SignedAndEnvelopedData(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.NamedType('recipientInfos', RecipientInfos()),\n        namedtype.NamedType('digestAlgorithms', DigestAlgorithmIdentifiers()),\n        namedtype.NamedType('encryptedContentInfo', EncryptedContentInfo()),\n        namedtype.OptionalNamedType('certificates', ExtendedCertificatesAndCertificates().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.OptionalNamedType('crls', CertificateRevocationLists().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n        namedtype.NamedType('signerInfos', SignerInfos())\n    )\n\n\nclass EnvelopedData(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.NamedType('recipientInfos', RecipientInfos()),\n        namedtype.NamedType('encryptedContentInfo', EncryptedContentInfo())\n    )\n\n\nclass DigestInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('digestAlgorithm', DigestAlgorithmIdentifier()),\n        namedtype.NamedType('digest', Digest())\n    )\n\n\nclass SignedData(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.OptionalNamedType('digestAlgorithms', DigestAlgorithmIdentifiers()),\n        namedtype.NamedType('contentInfo', ContentInfo()),\n        namedtype.OptionalNamedType('certificates', ExtendedCertificatesAndCertificates().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.OptionalNamedType('crls', CertificateRevocationLists().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n        namedtype.OptionalNamedType('signerInfos', SignerInfos())\n    )\n\n\nclass Data(univ.OctetString):\n    pass\n\n_contentTypeMapUpdate = {\n    data: Data(),\n    signedData: SignedData(),\n    envelopedData: EnvelopedData(),\n    signedAndEnvelopedData: SignedAndEnvelopedData(),\n    digestedData: DigestedData(),\n    encryptedData: EncryptedData()\n}\n\ncontentTypeMap.update(_contentTypeMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc2437.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# PKCS#1 syntax\n#\n# ASN.1 source from:\n# ftp://ftp.rsasecurity.com/pub/pkcs/pkcs-1/pkcs-1v2.asn\n#\n# Sample captures could be obtained with \"openssl genrsa\" command\n#\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules.rfc2459 import AlgorithmIdentifier\n\npkcs_1 = univ.ObjectIdentifier('1.2.840.113549.1.1')\nrsaEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.1')\nmd2WithRSAEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.2')\nmd4WithRSAEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.3')\nmd5WithRSAEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.4')\nsha1WithRSAEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.5')\nrsaOAEPEncryptionSET = univ.ObjectIdentifier('1.2.840.113549.1.1.6')\nid_RSAES_OAEP = univ.ObjectIdentifier('1.2.840.113549.1.1.7')\nid_mgf1 = univ.ObjectIdentifier('1.2.840.113549.1.1.8')\nid_pSpecified = univ.ObjectIdentifier('1.2.840.113549.1.1.9')\nid_sha1 = univ.ObjectIdentifier('1.3.14.3.2.26')\n\nMAX = float('inf')\n\n\nclass Version(univ.Integer):\n    pass\n\n\nclass RSAPrivateKey(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.NamedType('modulus', univ.Integer()),\n        namedtype.NamedType('publicExponent', univ.Integer()),\n        namedtype.NamedType('privateExponent', univ.Integer()),\n        namedtype.NamedType('prime1', univ.Integer()),\n        namedtype.NamedType('prime2', univ.Integer()),\n        namedtype.NamedType('exponent1', univ.Integer()),\n        namedtype.NamedType('exponent2', univ.Integer()),\n        namedtype.NamedType('coefficient', univ.Integer())\n    )\n\n\nclass RSAPublicKey(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('modulus', univ.Integer()),\n        namedtype.NamedType('publicExponent', univ.Integer())\n    )\n\n\n# XXX defaults not set\nclass RSAES_OAEP_params(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('hashFunc', AlgorithmIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.NamedType('maskGenFunc', AlgorithmIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n        namedtype.NamedType('pSourceFunc', AlgorithmIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2)))\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc2459.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Updated by Russ Housley to resolve the TODO regarding the Certificate\n#   Policies Certificate Extension.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# X.509 message syntax\n#\n# ASN.1 source from:\n# http://www.trl.ibm.com/projects/xml/xss4j/data/asn1/grammars/x509.asn\n# http://www.ietf.org/rfc/rfc2459.txt\n#\n# Sample captures from:\n# http://wiki.wireshark.org/SampleCaptures/\n#\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import opentype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nMAX = float('inf')\n\n#\n# PKIX1Explicit88\n#\n\n# Upper Bounds\nub_name = univ.Integer(32768)\nub_common_name = univ.Integer(64)\nub_locality_name = univ.Integer(128)\nub_state_name = univ.Integer(128)\nub_organization_name = univ.Integer(64)\nub_organizational_unit_name = univ.Integer(64)\nub_title = univ.Integer(64)\nub_match = univ.Integer(128)\nub_emailaddress_length = univ.Integer(128)\nub_common_name_length = univ.Integer(64)\nub_country_name_alpha_length = univ.Integer(2)\nub_country_name_numeric_length = univ.Integer(3)\nub_domain_defined_attributes = univ.Integer(4)\nub_domain_defined_attribute_type_length = univ.Integer(8)\nub_domain_defined_attribute_value_length = univ.Integer(128)\nub_domain_name_length = univ.Integer(16)\nub_extension_attributes = univ.Integer(256)\nub_e163_4_number_length = univ.Integer(15)\nub_e163_4_sub_address_length = univ.Integer(40)\nub_generation_qualifier_length = univ.Integer(3)\nub_given_name_length = univ.Integer(16)\nub_initials_length = univ.Integer(5)\nub_integer_options = univ.Integer(256)\nub_numeric_user_id_length = univ.Integer(32)\nub_organization_name_length = univ.Integer(64)\nub_organizational_unit_name_length = univ.Integer(32)\nub_organizational_units = univ.Integer(4)\nub_pds_name_length = univ.Integer(16)\nub_pds_parameter_length = univ.Integer(30)\nub_pds_physical_address_lines = univ.Integer(6)\nub_postal_code_length = univ.Integer(16)\nub_surname_length = univ.Integer(40)\nub_terminal_id_length = univ.Integer(24)\nub_unformatted_address_length = univ.Integer(180)\nub_x121_address_length = univ.Integer(16)\n\n\nclass UniversalString(char.UniversalString):\n    pass\n\n\nclass BMPString(char.BMPString):\n    pass\n\n\nclass UTF8String(char.UTF8String):\n    pass\n\n\nid_pkix = univ.ObjectIdentifier('1.3.6.1.5.5.7')\nid_pe = univ.ObjectIdentifier('1.3.6.1.5.5.7.1')\nid_qt = univ.ObjectIdentifier('1.3.6.1.5.5.7.2')\nid_kp = univ.ObjectIdentifier('1.3.6.1.5.5.7.3')\nid_ad = univ.ObjectIdentifier('1.3.6.1.5.5.7.48')\n\nid_qt_cps = univ.ObjectIdentifier('1.3.6.1.5.5.7.2.1')\nid_qt_unotice = univ.ObjectIdentifier('1.3.6.1.5.5.7.2.2')\n\nid_ad_ocsp = univ.ObjectIdentifier('1.3.6.1.5.5.7.48.1')\nid_ad_caIssuers = univ.ObjectIdentifier('1.3.6.1.5.5.7.48.2')\n\n\n\n\nid_at = univ.ObjectIdentifier('2.5.4')\nid_at_name = univ.ObjectIdentifier('2.5.4.41')\n# preserve misspelled variable for compatibility\nid_at_sutname = id_at_surname = univ.ObjectIdentifier('2.5.4.4')\nid_at_givenName = univ.ObjectIdentifier('2.5.4.42')\nid_at_initials = univ.ObjectIdentifier('2.5.4.43')\nid_at_generationQualifier = univ.ObjectIdentifier('2.5.4.44')\n\n\nclass X520name(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('teletexString',\n                            char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name))),\n        namedtype.NamedType('printableString',\n                            char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name))),\n        namedtype.NamedType('universalString',\n                            char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name))),\n        namedtype.NamedType('utf8String',\n                            char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name))),\n        namedtype.NamedType('bmpString',\n                            char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name)))\n    )\n\n\nid_at_commonName = univ.ObjectIdentifier('2.5.4.3')\n\n\nclass X520CommonName(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('teletexString', char.TeletexString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name))),\n        namedtype.NamedType('printableString', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name))),\n        namedtype.NamedType('universalString', char.UniversalString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name))),\n        namedtype.NamedType('utf8String',\n                            char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name))),\n        namedtype.NamedType('bmpString',\n                            char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name)))\n    )\n\n\nid_at_localityName = univ.ObjectIdentifier('2.5.4.7')\n\n\nclass X520LocalityName(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('teletexString', char.TeletexString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name))),\n        namedtype.NamedType('printableString', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name))),\n        namedtype.NamedType('universalString', char.UniversalString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name))),\n        namedtype.NamedType('utf8String',\n                            char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name))),\n        namedtype.NamedType('bmpString',\n                            char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name)))\n    )\n\n\nid_at_stateOrProvinceName = univ.ObjectIdentifier('2.5.4.8')\n\n\nclass X520StateOrProvinceName(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('teletexString',\n                            char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name))),\n        namedtype.NamedType('printableString', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name))),\n        namedtype.NamedType('universalString', char.UniversalString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name))),\n        namedtype.NamedType('utf8String',\n                            char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name))),\n        namedtype.NamedType('bmpString',\n                            char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name)))\n    )\n\n\nid_at_organizationName = univ.ObjectIdentifier('2.5.4.10')\n\n\nclass X520OrganizationName(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('teletexString', char.TeletexString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name))),\n        namedtype.NamedType('printableString', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name))),\n        namedtype.NamedType('universalString', char.UniversalString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name))),\n        namedtype.NamedType('utf8String', char.UTF8String().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name))),\n        namedtype.NamedType('bmpString', char.BMPString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name)))\n    )\n\n\nid_at_organizationalUnitName = univ.ObjectIdentifier('2.5.4.11')\n\n\nclass X520OrganizationalUnitName(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('teletexString', char.TeletexString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name))),\n        namedtype.NamedType('printableString', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name))),\n        namedtype.NamedType('universalString', char.UniversalString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name))),\n        namedtype.NamedType('utf8String', char.UTF8String().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name))),\n        namedtype.NamedType('bmpString', char.BMPString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name)))\n    )\n\n\nid_at_title = univ.ObjectIdentifier('2.5.4.12')\n\n\nclass X520Title(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('teletexString',\n                            char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title))),\n        namedtype.NamedType('printableString',\n                            char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title))),\n        namedtype.NamedType('universalString',\n                            char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title))),\n        namedtype.NamedType('utf8String',\n                            char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title))),\n        namedtype.NamedType('bmpString',\n                            char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title)))\n    )\n\n\nid_at_dnQualifier = univ.ObjectIdentifier('2.5.4.46')\n\n\nclass X520dnQualifier(char.PrintableString):\n    pass\n\n\nid_at_countryName = univ.ObjectIdentifier('2.5.4.6')\n\n\nclass X520countryName(char.PrintableString):\n    subtypeSpec = char.PrintableString.subtypeSpec + constraint.ValueSizeConstraint(2, 2)\n\n\npkcs_9 = univ.ObjectIdentifier('1.2.840.113549.1.9')\n\nemailAddress = univ.ObjectIdentifier('1.2.840.113549.1.9.1')\n\n\nclass Pkcs9email(char.IA5String):\n    subtypeSpec = char.IA5String.subtypeSpec + constraint.ValueSizeConstraint(1, ub_emailaddress_length)\n\n\n# ----\n\nclass DSAPrivateKey(univ.Sequence):\n    \"\"\"PKIX compliant DSA private key structure\"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', univ.Integer(namedValues=namedval.NamedValues(('v1', 0)))),\n        namedtype.NamedType('p', univ.Integer()),\n        namedtype.NamedType('q', univ.Integer()),\n        namedtype.NamedType('g', univ.Integer()),\n        namedtype.NamedType('public', univ.Integer()),\n        namedtype.NamedType('private', univ.Integer())\n    )\n\n\n# ----\n\n\nclass DirectoryString(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('teletexString',\n                            char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n        namedtype.NamedType('printableString',\n                            char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n        namedtype.NamedType('universalString',\n                            char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n        namedtype.NamedType('utf8String',\n                            char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n        namedtype.NamedType('bmpString', char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n        namedtype.NamedType('ia5String', char.IA5String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX)))\n        # hm, this should not be here!? XXX\n    )\n\n\n# certificate and CRL specific structures begin here\n\nclass AlgorithmIdentifier(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('algorithm', univ.ObjectIdentifier()),\n        namedtype.OptionalNamedType('parameters', univ.Any())\n    )\n\n\n\n# Algorithm OIDs and parameter structures\n\npkcs_1 = univ.ObjectIdentifier('1.2.840.113549.1.1')\nrsaEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.1')\nmd2WithRSAEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.2')\nmd5WithRSAEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.4')\nsha1WithRSAEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.5')\nid_dsa_with_sha1 = univ.ObjectIdentifier('1.2.840.10040.4.3')\n\n\nclass Dss_Sig_Value(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('r', univ.Integer()),\n        namedtype.NamedType('s', univ.Integer())\n    )\n\n\ndhpublicnumber = univ.ObjectIdentifier('1.2.840.10046.2.1')\n\n\nclass ValidationParms(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('seed', univ.BitString()),\n        namedtype.NamedType('pgenCounter', univ.Integer())\n    )\n\n\nclass DomainParameters(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('p', univ.Integer()),\n        namedtype.NamedType('g', univ.Integer()),\n        namedtype.NamedType('q', univ.Integer()),\n        namedtype.NamedType('j', univ.Integer()),\n        namedtype.OptionalNamedType('validationParms', ValidationParms())\n    )\n\n\nid_dsa = univ.ObjectIdentifier('1.2.840.10040.4.1')\n\n\nclass Dss_Parms(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('p', univ.Integer()),\n        namedtype.NamedType('q', univ.Integer()),\n        namedtype.NamedType('g', univ.Integer())\n    )\n\n\n# x400 address syntax starts here\n\nteletex_domain_defined_attributes = univ.Integer(6)\n\n\nclass TeletexDomainDefinedAttribute(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('type', char.TeletexString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_defined_attribute_type_length))),\n        namedtype.NamedType('value', char.TeletexString())\n    )\n\n\nclass TeletexDomainDefinedAttributes(univ.SequenceOf):\n    componentType = TeletexDomainDefinedAttribute()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, ub_domain_defined_attributes)\n\n\nterminal_type = univ.Integer(23)\n\n\nclass TerminalType(univ.Integer):\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueSizeConstraint(0, ub_integer_options)\n    namedValues = namedval.NamedValues(\n        ('telex', 3),\n        ('teletelex', 4),\n        ('g3-facsimile', 5),\n        ('g4-facsimile', 6),\n        ('ia5-terminal', 7),\n        ('videotex', 8)\n    )\n\n\nclass PresentationAddress(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('pSelector', univ.OctetString().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('sSelector', univ.OctetString().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.OptionalNamedType('tSelector', univ.OctetString().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n        namedtype.OptionalNamedType('nAddresses', univ.SetOf(componentType=univ.OctetString()).subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3),\n            subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    )\n\n\nextended_network_address = univ.Integer(22)\n\n\nclass E163_4_address(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('number', char.NumericString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_e163_4_number_length),\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('sub-address', char.NumericString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_e163_4_sub_address_length),\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n    )\n\n\nclass ExtendedNetworkAddress(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('e163-4-address', E163_4_address()),\n        namedtype.NamedType('psap-address', PresentationAddress().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n    )\n\n\nclass PDSParameter(univ.Set):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('printable-string', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_pds_parameter_length))),\n        namedtype.OptionalNamedType('teletex-string', char.TeletexString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_pds_parameter_length)))\n    )\n\n\nlocal_postal_attributes = univ.Integer(21)\n\n\nclass LocalPostalAttributes(PDSParameter):\n    pass\n\n\nclass UniquePostalName(PDSParameter):\n    pass\n\n\nunique_postal_name = univ.Integer(20)\n\nposte_restante_address = univ.Integer(19)\n\n\nclass PosteRestanteAddress(PDSParameter):\n    pass\n\n\npost_office_box_address = univ.Integer(18)\n\n\nclass PostOfficeBoxAddress(PDSParameter):\n    pass\n\n\nstreet_address = univ.Integer(17)\n\n\nclass StreetAddress(PDSParameter):\n    pass\n\n\nclass UnformattedPostalAddress(univ.Set):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('printable-address', univ.SequenceOf(componentType=char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_pds_parameter_length)).subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_pds_physical_address_lines)))),\n        namedtype.OptionalNamedType('teletex-string', char.TeletexString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_unformatted_address_length)))\n    )\n\n\nphysical_delivery_office_name = univ.Integer(10)\n\n\nclass PhysicalDeliveryOfficeName(PDSParameter):\n    pass\n\n\nphysical_delivery_office_number = univ.Integer(11)\n\n\nclass PhysicalDeliveryOfficeNumber(PDSParameter):\n    pass\n\n\nextension_OR_address_components = univ.Integer(12)\n\n\nclass ExtensionORAddressComponents(PDSParameter):\n    pass\n\n\nphysical_delivery_personal_name = univ.Integer(13)\n\n\nclass PhysicalDeliveryPersonalName(PDSParameter):\n    pass\n\n\nphysical_delivery_organization_name = univ.Integer(14)\n\n\nclass PhysicalDeliveryOrganizationName(PDSParameter):\n    pass\n\n\nextension_physical_delivery_address_components = univ.Integer(15)\n\n\nclass ExtensionPhysicalDeliveryAddressComponents(PDSParameter):\n    pass\n\n\nunformatted_postal_address = univ.Integer(16)\n\npostal_code = univ.Integer(9)\n\n\nclass PostalCode(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('numeric-code', char.NumericString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_postal_code_length))),\n        namedtype.NamedType('printable-code', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_postal_code_length)))\n    )\n\n\nclass PhysicalDeliveryCountryName(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('x121-dcc-code', char.NumericString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(ub_country_name_numeric_length,\n                                                       ub_country_name_numeric_length))),\n        namedtype.NamedType('iso-3166-alpha2-code', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(ub_country_name_alpha_length, ub_country_name_alpha_length)))\n    )\n\n\nclass PDSName(char.PrintableString):\n    subtypeSpec = char.PrintableString.subtypeSpec + constraint.ValueSizeConstraint(1, ub_pds_name_length)\n\n\nphysical_delivery_country_name = univ.Integer(8)\n\n\nclass TeletexOrganizationalUnitName(char.TeletexString):\n    subtypeSpec = char.TeletexString.subtypeSpec + constraint.ValueSizeConstraint(1, ub_organizational_unit_name_length)\n\n\npds_name = univ.Integer(7)\n\nteletex_organizational_unit_names = univ.Integer(5)\n\n\nclass TeletexOrganizationalUnitNames(univ.SequenceOf):\n    componentType = TeletexOrganizationalUnitName()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, ub_organizational_units)\n\n\nteletex_personal_name = univ.Integer(4)\n\n\nclass TeletexPersonalName(univ.Set):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('surname', char.TeletexString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_surname_length),\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('given-name', char.TeletexString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_given_name_length),\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.OptionalNamedType('initials', char.TeletexString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_initials_length),\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n        namedtype.OptionalNamedType('generation-qualifier', char.TeletexString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_generation_qualifier_length),\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n    )\n\n\nteletex_organization_name = univ.Integer(3)\n\n\nclass TeletexOrganizationName(char.TeletexString):\n    subtypeSpec = char.TeletexString.subtypeSpec + constraint.ValueSizeConstraint(1, ub_organization_name_length)\n\n\nteletex_common_name = univ.Integer(2)\n\n\nclass TeletexCommonName(char.TeletexString):\n    subtypeSpec = char.TeletexString.subtypeSpec + constraint.ValueSizeConstraint(1, ub_common_name_length)\n\n\nclass CommonName(char.PrintableString):\n    subtypeSpec = char.PrintableString.subtypeSpec + constraint.ValueSizeConstraint(1, ub_common_name_length)\n\n\ncommon_name = univ.Integer(1)\n\n\nclass ExtensionAttribute(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('extension-attribute-type', univ.Integer().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(0, ub_extension_attributes),\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.NamedType('extension-attribute-value',\n                            univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n    )\n\n\nclass ExtensionAttributes(univ.SetOf):\n    componentType = ExtensionAttribute()\n    sizeSpec = univ.SetOf.sizeSpec + constraint.ValueSizeConstraint(1, ub_extension_attributes)\n\n\nclass BuiltInDomainDefinedAttribute(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('type', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_defined_attribute_type_length))),\n        namedtype.NamedType('value', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_defined_attribute_value_length)))\n    )\n\n\nclass BuiltInDomainDefinedAttributes(univ.SequenceOf):\n    componentType = BuiltInDomainDefinedAttribute()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, ub_domain_defined_attributes)\n\n\nclass OrganizationalUnitName(char.PrintableString):\n    subtypeSpec = char.PrintableString.subtypeSpec + constraint.ValueSizeConstraint(1, ub_organizational_unit_name_length)\n\n\nclass OrganizationalUnitNames(univ.SequenceOf):\n    componentType = OrganizationalUnitName()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, ub_organizational_units)\n\n\nclass PersonalName(univ.Set):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('surname', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_surname_length),\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('given-name', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_given_name_length),\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.OptionalNamedType('initials', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_initials_length),\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n        namedtype.OptionalNamedType('generation-qualifier', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_generation_qualifier_length),\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n    )\n\n\nclass NumericUserIdentifier(char.NumericString):\n    subtypeSpec = char.NumericString.subtypeSpec + constraint.ValueSizeConstraint(1, ub_numeric_user_id_length)\n\n\nclass OrganizationName(char.PrintableString):\n    subtypeSpec = char.PrintableString.subtypeSpec + constraint.ValueSizeConstraint(1, ub_organization_name_length)\n\n\nclass PrivateDomainName(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('numeric', char.NumericString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_name_length))),\n        namedtype.NamedType('printable', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_name_length)))\n    )\n\n\nclass TerminalIdentifier(char.PrintableString):\n    subtypeSpec = char.PrintableString.subtypeSpec + constraint.ValueSizeConstraint(1, ub_terminal_id_length)\n\n\nclass X121Address(char.NumericString):\n    subtypeSpec = char.NumericString.subtypeSpec + constraint.ValueSizeConstraint(1, ub_x121_address_length)\n\n\nclass NetworkAddress(X121Address):\n    pass\n\n\nclass AdministrationDomainName(univ.Choice):\n    tagSet = univ.Choice.tagSet.tagExplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 2)\n    )\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('numeric', char.NumericString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(0, ub_domain_name_length))),\n        namedtype.NamedType('printable', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(0, ub_domain_name_length)))\n    )\n\n\nclass CountryName(univ.Choice):\n    tagSet = univ.Choice.tagSet.tagExplicitly(\n        tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 1)\n    )\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('x121-dcc-code', char.NumericString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(ub_country_name_numeric_length,\n                                                       ub_country_name_numeric_length))),\n        namedtype.NamedType('iso-3166-alpha2-code', char.PrintableString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(ub_country_name_alpha_length, ub_country_name_alpha_length)))\n    )\n\n\nclass BuiltInStandardAttributes(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('country-name', CountryName()),\n        namedtype.OptionalNamedType('administration-domain-name', AdministrationDomainName()),\n        namedtype.OptionalNamedType('network-address', NetworkAddress().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('terminal-identifier', TerminalIdentifier().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.OptionalNamedType('private-domain-name', PrivateDomainName().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n        namedtype.OptionalNamedType('organization-name', OrganizationName().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n        namedtype.OptionalNamedType('numeric-user-identifier', NumericUserIdentifier().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4))),\n        namedtype.OptionalNamedType('personal-name', PersonalName().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 5))),\n        namedtype.OptionalNamedType('organizational-unit-names', OrganizationalUnitNames().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 6)))\n    )\n\n\nclass ORAddress(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('built-in-standard-attributes', BuiltInStandardAttributes()),\n        namedtype.OptionalNamedType('built-in-domain-defined-attributes', BuiltInDomainDefinedAttributes()),\n        namedtype.OptionalNamedType('extension-attributes', ExtensionAttributes())\n    )\n\n\n#\n# PKIX1Implicit88\n#\n\nid_ce_invalidityDate = univ.ObjectIdentifier('2.5.29.24')\n\n\nclass InvalidityDate(useful.GeneralizedTime):\n    pass\n\n\nid_holdinstruction_none = univ.ObjectIdentifier('2.2.840.10040.2.1')\nid_holdinstruction_callissuer = univ.ObjectIdentifier('2.2.840.10040.2.2')\nid_holdinstruction_reject = univ.ObjectIdentifier('2.2.840.10040.2.3')\n\nholdInstruction = univ.ObjectIdentifier('2.2.840.10040.2')\n\nid_ce_holdInstructionCode = univ.ObjectIdentifier('2.5.29.23')\n\n\nclass HoldInstructionCode(univ.ObjectIdentifier):\n    pass\n\n\nid_ce_cRLReasons = univ.ObjectIdentifier('2.5.29.21')\n\n\nclass CRLReason(univ.Enumerated):\n    namedValues = namedval.NamedValues(\n        ('unspecified', 0),\n        ('keyCompromise', 1),\n        ('cACompromise', 2),\n        ('affiliationChanged', 3),\n        ('superseded', 4),\n        ('cessationOfOperation', 5),\n        ('certificateHold', 6),\n        ('removeFromCRL', 8)\n    )\n\n\nid_ce_cRLNumber = univ.ObjectIdentifier('2.5.29.20')\n\n\nclass CRLNumber(univ.Integer):\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueSizeConstraint(0, MAX)\n\n\nclass BaseCRLNumber(CRLNumber):\n    pass\n\n\nid_kp_serverAuth = univ.ObjectIdentifier('1.3.6.1.5.5.7.3.1')\nid_kp_clientAuth = univ.ObjectIdentifier('1.3.6.1.5.5.7.3.2')\nid_kp_codeSigning = univ.ObjectIdentifier('1.3.6.1.5.5.7.3.3')\nid_kp_emailProtection = univ.ObjectIdentifier('1.3.6.1.5.5.7.3.4')\nid_kp_ipsecEndSystem = univ.ObjectIdentifier('1.3.6.1.5.5.7.3.5')\nid_kp_ipsecTunnel = univ.ObjectIdentifier('1.3.6.1.5.5.7.3.6')\nid_kp_ipsecUser = univ.ObjectIdentifier('1.3.6.1.5.5.7.3.7')\nid_kp_timeStamping = univ.ObjectIdentifier('1.3.6.1.5.5.7.3.8')\nid_pe_authorityInfoAccess = univ.ObjectIdentifier('1.3.6.1.5.5.7.1.1')\nid_ce_extKeyUsage = univ.ObjectIdentifier('2.5.29.37')\n\n\nclass KeyPurposeId(univ.ObjectIdentifier):\n    pass\n\n\nclass ExtKeyUsageSyntax(univ.SequenceOf):\n    componentType = KeyPurposeId()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\nclass ReasonFlags(univ.BitString):\n    namedValues = namedval.NamedValues(\n        ('unused', 0),\n        ('keyCompromise', 1),\n        ('cACompromise', 2),\n        ('affiliationChanged', 3),\n        ('superseded', 4),\n        ('cessationOfOperation', 5),\n        ('certificateHold', 6)\n    )\n\n\nclass SkipCerts(univ.Integer):\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueSizeConstraint(0, MAX)\n\n\nid_ce_policyConstraints = univ.ObjectIdentifier('2.5.29.36')\n\n\nclass PolicyConstraints(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('requireExplicitPolicy', SkipCerts().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.OptionalNamedType('inhibitPolicyMapping', SkipCerts().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n    )\n\n\nid_ce_basicConstraints = univ.ObjectIdentifier('2.5.29.19')\n\n\nclass BasicConstraints(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.DefaultedNamedType('cA', univ.Boolean(False)),\n        namedtype.OptionalNamedType('pathLenConstraint',\n                                    univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, MAX)))\n    )\n\n\nid_ce_subjectDirectoryAttributes = univ.ObjectIdentifier('2.5.29.9')\n\n\nclass EDIPartyName(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('nameAssigner', DirectoryString().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.NamedType('partyName',\n                            DirectoryString().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n    )\n\n\n\nid_ce_deltaCRLIndicator = univ.ObjectIdentifier('2.5.29.27')\n\n\n\nclass BaseDistance(univ.Integer):\n    subtypeSpec = univ.Integer.subtypeSpec + constraint.ValueRangeConstraint(0, MAX)\n\n\nid_ce_cRLDistributionPoints = univ.ObjectIdentifier('2.5.29.31')\n\n\nid_ce_issuingDistributionPoint = univ.ObjectIdentifier('2.5.29.28')\n\n\n\n\nid_ce_nameConstraints = univ.ObjectIdentifier('2.5.29.30')\n\n\nclass DisplayText(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('visibleString',\n                            char.VisibleString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, 200))),\n        namedtype.NamedType('bmpString', char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, 200))),\n        namedtype.NamedType('utf8String', char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, 200)))\n    )\n\n\nclass NoticeReference(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('organization', DisplayText()),\n        namedtype.NamedType('noticeNumbers', univ.SequenceOf(componentType=univ.Integer()))\n    )\n\n\nclass UserNotice(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('noticeRef', NoticeReference()),\n        namedtype.OptionalNamedType('explicitText', DisplayText())\n    )\n\n\nclass CPSuri(char.IA5String):\n    pass\n\n\nclass PolicyQualifierId(univ.ObjectIdentifier):\n    subtypeSpec = univ.ObjectIdentifier.subtypeSpec + constraint.SingleValueConstraint(id_qt_cps, id_qt_unotice)\n\n\nclass CertPolicyId(univ.ObjectIdentifier):\n    pass\n\n\nclass PolicyQualifierInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('policyQualifierId', PolicyQualifierId()),\n        namedtype.NamedType('qualifier', univ.Any())\n    )\n\n\nid_ce_certificatePolicies = univ.ObjectIdentifier('2.5.29.32')\n\n\nclass PolicyInformation(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('policyIdentifier', CertPolicyId()),\n        namedtype.OptionalNamedType('policyQualifiers', univ.SequenceOf(componentType=PolicyQualifierInfo()).subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, MAX)))\n    )\n\n\nclass CertificatePolicies(univ.SequenceOf):\n    componentType = PolicyInformation()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\nid_ce_policyMappings = univ.ObjectIdentifier('2.5.29.33')\n\n\nclass PolicyMapping(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('issuerDomainPolicy', CertPolicyId()),\n        namedtype.NamedType('subjectDomainPolicy', CertPolicyId())\n    )\n\n\nclass PolicyMappings(univ.SequenceOf):\n    componentType = PolicyMapping()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\nid_ce_privateKeyUsagePeriod = univ.ObjectIdentifier('2.5.29.16')\n\n\nclass PrivateKeyUsagePeriod(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('notBefore', useful.GeneralizedTime().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('notAfter', useful.GeneralizedTime().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n    )\n\n\nid_ce_keyUsage = univ.ObjectIdentifier('2.5.29.15')\n\n\nclass KeyUsage(univ.BitString):\n    namedValues = namedval.NamedValues(\n        ('digitalSignature', 0),\n        ('nonRepudiation', 1),\n        ('keyEncipherment', 2),\n        ('dataEncipherment', 3),\n        ('keyAgreement', 4),\n        ('keyCertSign', 5),\n        ('cRLSign', 6),\n        ('encipherOnly', 7),\n        ('decipherOnly', 8)\n    )\n\n\nid_ce = univ.ObjectIdentifier('2.5.29')\n\nid_ce_authorityKeyIdentifier = univ.ObjectIdentifier('2.5.29.35')\n\n\nclass KeyIdentifier(univ.OctetString):\n    pass\n\n\nid_ce_subjectKeyIdentifier = univ.ObjectIdentifier('2.5.29.14')\n\n\nclass SubjectKeyIdentifier(KeyIdentifier):\n    pass\n\n\nid_ce_certificateIssuer = univ.ObjectIdentifier('2.5.29.29')\n\n\nid_ce_subjectAltName = univ.ObjectIdentifier('2.5.29.17')\n\n\nid_ce_issuerAltName = univ.ObjectIdentifier('2.5.29.18')\n\n\nclass AttributeValue(univ.Any):\n    pass\n\n\nclass AttributeType(univ.ObjectIdentifier):\n    pass\n\ncertificateAttributesMap = {}\n\n\nclass AttributeTypeAndValue(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('type', AttributeType()),\n        namedtype.NamedType('value', AttributeValue(),\n                            openType=opentype.OpenType('type', certificateAttributesMap))\n    )\n\n\nclass Attribute(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('type', AttributeType()),\n        namedtype.NamedType('vals', univ.SetOf(componentType=AttributeValue()))\n    )\n\n\nclass SubjectDirectoryAttributes(univ.SequenceOf):\n    componentType = Attribute()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\nclass RelativeDistinguishedName(univ.SetOf):\n    componentType = AttributeTypeAndValue()\n\n\nclass RDNSequence(univ.SequenceOf):\n    componentType = RelativeDistinguishedName()\n\n\nclass Name(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('', RDNSequence())\n    )\n\nclass CertificateSerialNumber(univ.Integer):\n    pass\n\n\nclass AnotherName(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('type-id', univ.ObjectIdentifier()),\n        namedtype.NamedType('value',\n                            univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n    )\n\n\nclass GeneralName(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('otherName',\n                            AnotherName().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.NamedType('rfc822Name',\n                            char.IA5String().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.NamedType('dNSName',\n                            char.IA5String().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n        namedtype.NamedType('x400Address',\n                            ORAddress().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n        namedtype.NamedType('directoryName',\n                            Name().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4))),\n        namedtype.NamedType('ediPartyName',\n                            EDIPartyName().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 5))),\n        namedtype.NamedType('uniformResourceIdentifier',\n                            char.IA5String().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 6))),\n        namedtype.NamedType('iPAddress', univ.OctetString().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 7))),\n        namedtype.NamedType('registeredID', univ.ObjectIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 8)))\n    )\n\n\nclass GeneralNames(univ.SequenceOf):\n    componentType = GeneralName()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\nclass AccessDescription(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('accessMethod', univ.ObjectIdentifier()),\n        namedtype.NamedType('accessLocation', GeneralName())\n    )\n\n\nclass AuthorityInfoAccessSyntax(univ.SequenceOf):\n    componentType = AccessDescription()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\nclass AuthorityKeyIdentifier(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('keyIdentifier', KeyIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('authorityCertIssuer', GeneralNames().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.OptionalNamedType('authorityCertSerialNumber', CertificateSerialNumber().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n    )\n\n\nclass DistributionPointName(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('fullName', GeneralNames().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.NamedType('nameRelativeToCRLIssuer', RelativeDistinguishedName().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n    )\n\n\nclass DistributionPoint(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('distributionPoint', DistributionPointName().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.OptionalNamedType('reasons', ReasonFlags().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.OptionalNamedType('cRLIssuer', GeneralNames().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2)))\n    )\n\n\nclass CRLDistPointsSyntax(univ.SequenceOf):\n    componentType = DistributionPoint()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\nclass IssuingDistributionPoint(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('distributionPoint', DistributionPointName().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.NamedType('onlyContainsUserCerts', univ.Boolean(False).subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.NamedType('onlyContainsCACerts', univ.Boolean(False).subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n        namedtype.OptionalNamedType('onlySomeReasons', ReasonFlags().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n        namedtype.NamedType('indirectCRL', univ.Boolean(False).subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4)))\n    )\n\n\nclass GeneralSubtree(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('base', GeneralName()),\n        namedtype.DefaultedNamedType('minimum', BaseDistance(0).subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.OptionalNamedType('maximum', BaseDistance().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n    )\n\n\nclass GeneralSubtrees(univ.SequenceOf):\n    componentType = GeneralSubtree()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\nclass NameConstraints(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('permittedSubtrees', GeneralSubtrees().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.OptionalNamedType('excludedSubtrees', GeneralSubtrees().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n    )\n\n\nclass CertificateIssuer(GeneralNames):\n    pass\n\n\nclass SubjectAltName(GeneralNames):\n    pass\n\n\nclass IssuerAltName(GeneralNames):\n    pass\n\n\ncertificateExtensionsMap = {}\n\n\nclass Extension(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('extnID', univ.ObjectIdentifier()),\n        namedtype.DefaultedNamedType('critical', univ.Boolean('False')),\n        namedtype.NamedType('extnValue', univ.OctetString(),\n                            openType=opentype.OpenType('extnID', certificateExtensionsMap))\n    )\n\n\nclass Extensions(univ.SequenceOf):\n    componentType = Extension()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\nclass SubjectPublicKeyInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('algorithm', AlgorithmIdentifier()),\n        namedtype.NamedType('subjectPublicKey', univ.BitString())\n    )\n\n\nclass UniqueIdentifier(univ.BitString):\n    pass\n\n\nclass Time(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('utcTime', useful.UTCTime()),\n        namedtype.NamedType('generalTime', useful.GeneralizedTime())\n    )\n\n\nclass Validity(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('notBefore', Time()),\n        namedtype.NamedType('notAfter', Time())\n    )\n\n\nclass Version(univ.Integer):\n    namedValues = namedval.NamedValues(\n        ('v1', 0), ('v2', 1), ('v3', 2)\n    )\n\n\nclass TBSCertificate(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.DefaultedNamedType('version', Version('v1').subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.NamedType('serialNumber', CertificateSerialNumber()),\n        namedtype.NamedType('signature', AlgorithmIdentifier()),\n        namedtype.NamedType('issuer', Name()),\n        namedtype.NamedType('validity', Validity()),\n        namedtype.NamedType('subject', Name()),\n        namedtype.NamedType('subjectPublicKeyInfo', SubjectPublicKeyInfo()),\n        namedtype.OptionalNamedType('issuerUniqueID', UniqueIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.OptionalNamedType('subjectUniqueID', UniqueIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n        namedtype.OptionalNamedType('extensions', Extensions().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n    )\n\n\nclass Certificate(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('tbsCertificate', TBSCertificate()),\n        namedtype.NamedType('signatureAlgorithm', AlgorithmIdentifier()),\n        namedtype.NamedType('signatureValue', univ.BitString())\n    )\n\n# CRL structures\n\nclass RevokedCertificate(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('userCertificate', CertificateSerialNumber()),\n        namedtype.NamedType('revocationDate', Time()),\n        namedtype.OptionalNamedType('crlEntryExtensions', Extensions())\n    )\n\n\nclass TBSCertList(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('version', Version()),\n        namedtype.NamedType('signature', AlgorithmIdentifier()),\n        namedtype.NamedType('issuer', Name()),\n        namedtype.NamedType('thisUpdate', Time()),\n        namedtype.OptionalNamedType('nextUpdate', Time()),\n        namedtype.OptionalNamedType('revokedCertificates', univ.SequenceOf(componentType=RevokedCertificate())),\n        namedtype.OptionalNamedType('crlExtensions', Extensions().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n    )\n\n\nclass CertificateList(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('tbsCertList', TBSCertList()),\n        namedtype.NamedType('signatureAlgorithm', AlgorithmIdentifier()),\n        namedtype.NamedType('signature', univ.BitString())\n    )\n\n# map of AttributeType -> AttributeValue\n\n_certificateAttributesMapUpdate = {\n    id_at_name: X520name(),\n    id_at_surname: X520name(),\n    id_at_givenName: X520name(),\n    id_at_initials: X520name(),\n    id_at_generationQualifier: X520name(),\n    id_at_commonName: X520CommonName(),\n    id_at_localityName: X520LocalityName(),\n    id_at_stateOrProvinceName: X520StateOrProvinceName(),\n    id_at_organizationName: X520OrganizationName(),\n    id_at_organizationalUnitName: X520OrganizationalUnitName(),\n    id_at_title: X520Title(),\n    id_at_dnQualifier: X520dnQualifier(),\n    id_at_countryName: X520countryName(),\n    emailAddress: Pkcs9email(),\n}\n\ncertificateAttributesMap.update(_certificateAttributesMapUpdate)\n\n\n# map of Certificate Extension OIDs to Extensions\n\n_certificateExtensionsMapUpdate = {\n    id_ce_authorityKeyIdentifier: AuthorityKeyIdentifier(),\n    id_ce_subjectKeyIdentifier: SubjectKeyIdentifier(),\n    id_ce_keyUsage: KeyUsage(),\n    id_ce_privateKeyUsagePeriod: PrivateKeyUsagePeriod(),\n    id_ce_certificatePolicies: CertificatePolicies(),\n    id_ce_policyMappings: PolicyMappings(),\n    id_ce_subjectAltName: SubjectAltName(),\n    id_ce_issuerAltName: IssuerAltName(),\n    id_ce_subjectDirectoryAttributes: SubjectDirectoryAttributes(),\n    id_ce_basicConstraints: BasicConstraints(),\n    id_ce_nameConstraints: NameConstraints(),\n    id_ce_policyConstraints: PolicyConstraints(),\n    id_ce_extKeyUsage: ExtKeyUsageSyntax(),\n    id_ce_cRLDistributionPoints: CRLDistPointsSyntax(),\n    id_pe_authorityInfoAccess: AuthorityInfoAccessSyntax(),\n    id_ce_cRLNumber: univ.Integer(),\n    id_ce_deltaCRLIndicator: BaseCRLNumber(),\n    id_ce_issuingDistributionPoint: IssuingDistributionPoint(),\n    id_ce_cRLReasons: CRLReason(),\n    id_ce_holdInstructionCode: univ.ObjectIdentifier(),\n    id_ce_invalidityDate: useful.GeneralizedTime(),\n    id_ce_certificateIssuer: GeneralNames(),\n}\n\ncertificateExtensionsMap.update(_certificateExtensionsMapUpdate)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc2511.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# X.509 certificate Request Message Format (CRMF) syntax\n#\n# ASN.1 source from:\n# http://tools.ietf.org/html/rfc2511\n#\n# Sample captures could be obtained with OpenSSL\n#\nfrom pyasn1_modules import rfc2315\nfrom pyasn1_modules.rfc2459 import *\n\nMAX = float('inf')\n\nid_pkix = univ.ObjectIdentifier('1.3.6.1.5.5.7')\nid_pkip = univ.ObjectIdentifier('1.3.6.1.5.5.7.5')\nid_regCtrl = univ.ObjectIdentifier('1.3.6.1.5.5.7.5.1')\nid_regCtrl_regToken = univ.ObjectIdentifier('1.3.6.1.5.5.7.5.1.1')\nid_regCtrl_authenticator = univ.ObjectIdentifier('1.3.6.1.5.5.7.5.1.2')\nid_regCtrl_pkiPublicationInfo = univ.ObjectIdentifier('1.3.6.1.5.5.7.5.1.3')\nid_regCtrl_pkiArchiveOptions = univ.ObjectIdentifier('1.3.6.1.5.5.7.5.1.4')\nid_regCtrl_oldCertID = univ.ObjectIdentifier('1.3.6.1.5.5.7.5.1.5')\nid_regCtrl_protocolEncrKey = univ.ObjectIdentifier('1.3.6.1.5.5.7.5.1.6')\nid_regInfo = univ.ObjectIdentifier('1.3.6.1.5.5.7.5.2')\nid_regInfo_utf8Pairs = univ.ObjectIdentifier('1.3.6.1.5.5.7.5.2.1')\nid_regInfo_certReq = univ.ObjectIdentifier('1.3.6.1.5.5.7.5.2.2')\n\n\n# This should be in PKIX Certificate Extensions module\n\nclass GeneralName(univ.OctetString):\n    pass\n\n\n# end of PKIX Certificate Extensions module\n\nclass UTF8Pairs(char.UTF8String):\n    pass\n\n\nclass ProtocolEncrKey(SubjectPublicKeyInfo):\n    pass\n\n\nclass CertId(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('issuer', GeneralName()),\n        namedtype.NamedType('serialNumber', univ.Integer())\n    )\n\n\nclass OldCertId(CertId):\n    pass\n\n\nclass KeyGenParameters(univ.OctetString):\n    pass\n\n\nclass EncryptedValue(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('intendedAlg', AlgorithmIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.OptionalNamedType('symmAlg', AlgorithmIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n        namedtype.OptionalNamedType('encSymmKey', univ.BitString().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2))),\n        namedtype.OptionalNamedType('keyAlg', AlgorithmIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3))),\n        namedtype.OptionalNamedType('valueHint', univ.OctetString().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 4))),\n        namedtype.NamedType('encValue', univ.BitString())\n    )\n\n\nclass EncryptedKey(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('encryptedValue', EncryptedValue()),\n        namedtype.NamedType('envelopedData', rfc2315.EnvelopedData().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n    )\n\n\nclass PKIArchiveOptions(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('encryptedPrivKey', EncryptedKey().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.NamedType('keyGenParameters', KeyGenParameters().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.NamedType('archiveRemGenPrivKey',\n                            univ.Boolean().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n    )\n\n\nclass SinglePubInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('pubMethod', univ.Integer(\n            namedValues=namedval.NamedValues(('dontCare', 0), ('x500', 1), ('web', 2), ('ldap', 3)))),\n        namedtype.OptionalNamedType('pubLocation', GeneralName())\n    )\n\n\nclass PKIPublicationInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('action',\n                            univ.Integer(namedValues=namedval.NamedValues(('dontPublish', 0), ('pleasePublish', 1)))),\n        namedtype.OptionalNamedType('pubInfos', univ.SequenceOf(componentType=SinglePubInfo()).subtype(\n            sizeSpec=constraint.ValueSizeConstraint(1, MAX)))\n    )\n\n\nclass Authenticator(char.UTF8String):\n    pass\n\n\nclass RegToken(char.UTF8String):\n    pass\n\n\nclass SubsequentMessage(univ.Integer):\n    namedValues = namedval.NamedValues(\n        ('encrCert', 0),\n        ('challengeResp', 1)\n    )\n\n\nclass POPOPrivKey(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('thisMessage',\n                            univ.BitString().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.NamedType('subsequentMessage', SubsequentMessage().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.NamedType('dhMAC',\n                            univ.BitString().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n    )\n\n\nclass PBMParameter(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('salt', univ.OctetString()),\n        namedtype.NamedType('owf', AlgorithmIdentifier()),\n        namedtype.NamedType('iterationCount', univ.Integer()),\n        namedtype.NamedType('mac', AlgorithmIdentifier())\n    )\n\n\nclass PKMACValue(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('algId', AlgorithmIdentifier()),\n        namedtype.NamedType('value', univ.BitString())\n    )\n\n\nclass POPOSigningKeyInput(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType(\n            'authInfo', univ.Choice(\n                componentType=namedtype.NamedTypes(\n                    namedtype.NamedType(\n                        'sender', GeneralName().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))\n                    ),\n                    namedtype.NamedType('publicKeyMAC', PKMACValue())\n                )\n            )\n        ),\n        namedtype.NamedType('publicKey', SubjectPublicKeyInfo())\n    )\n\n\nclass POPOSigningKey(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('poposkInput', POPOSigningKeyInput().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.NamedType('algorithmIdentifier', AlgorithmIdentifier()),\n        namedtype.NamedType('signature', univ.BitString())\n    )\n\n\nclass ProofOfPossession(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('raVerified',\n                            univ.Null().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.NamedType('signature', POPOSigningKey().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n        namedtype.NamedType('keyEncipherment', POPOPrivKey().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2))),\n        namedtype.NamedType('keyAgreement', POPOPrivKey().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3)))\n    )\n\n\nclass Controls(univ.SequenceOf):\n    componentType = AttributeTypeAndValue()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\nclass OptionalValidity(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('notBefore',\n                                    Time().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('notAfter',\n                                    Time().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n    )\n\n\nclass CertTemplate(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('version', Version().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('serialNumber', univ.Integer().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.OptionalNamedType('signingAlg', AlgorithmIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2))),\n        namedtype.OptionalNamedType('issuer', Name().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3))),\n        namedtype.OptionalNamedType('validity', OptionalValidity().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 4))),\n        namedtype.OptionalNamedType('subject', Name().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 5))),\n        namedtype.OptionalNamedType('publicKey', SubjectPublicKeyInfo().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 6))),\n        namedtype.OptionalNamedType('issuerUID', UniqueIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 7))),\n        namedtype.OptionalNamedType('subjectUID', UniqueIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 8))),\n        namedtype.OptionalNamedType('extensions', Extensions().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 9)))\n    )\n\n\nclass CertRequest(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('certReqId', univ.Integer()),\n        namedtype.NamedType('certTemplate', CertTemplate()),\n        namedtype.OptionalNamedType('controls', Controls())\n    )\n\n\nclass CertReq(CertRequest):\n    pass\n\n\nclass CertReqMsg(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('certReq', CertRequest()),\n        namedtype.OptionalNamedType('pop', ProofOfPossession()),\n        namedtype.OptionalNamedType('regInfo', univ.SequenceOf(componentType=AttributeTypeAndValue()).subtype(\n            sizeSpec=constraint.ValueSizeConstraint(1, MAX)))\n    )\n\n\nclass CertReqMessages(univ.SequenceOf):\n    componentType = CertReqMsg()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc2560.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# OCSP request/response syntax\n#\n# Derived from a minimal OCSP library (RFC2560) code written by\n# Bud P. Bruegger <bud@ancitel.it>\n# Copyright: Ancitel, S.p.a,  Rome, Italy\n# License: BSD\n#\n\n#\n# current limitations:\n# * request and response works only for a single certificate\n# * only some values are parsed out of the response\n# * the request does't set a nonce nor signature\n# * there is no signature validation of the response\n# * dates are left as strings in GeneralizedTime format -- datetime.datetime\n# would be nicer\n#\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nfrom pyasn1_modules import rfc2459\n\n\n# Start of OCSP module definitions\n\n# This should be in directory Authentication Framework (X.509) module\n\nclass CRLReason(univ.Enumerated):\n    namedValues = namedval.NamedValues(\n        ('unspecified', 0),\n        ('keyCompromise', 1),\n        ('cACompromise', 2),\n        ('affiliationChanged', 3),\n        ('superseded', 4),\n        ('cessationOfOperation', 5),\n        ('certificateHold', 6),\n        ('removeFromCRL', 8),\n        ('privilegeWithdrawn', 9),\n        ('aACompromise', 10)\n    )\n\n\n# end of directory Authentication Framework (X.509) module\n\n# This should be in PKIX Certificate Extensions module\n\nclass GeneralName(univ.OctetString):\n    pass\n\n\n# end of PKIX Certificate Extensions module\n\nid_kp_OCSPSigning = univ.ObjectIdentifier((1, 3, 6, 1, 5, 5, 7, 3, 9))\nid_pkix_ocsp = univ.ObjectIdentifier((1, 3, 6, 1, 5, 5, 7, 48, 1))\nid_pkix_ocsp_basic = univ.ObjectIdentifier((1, 3, 6, 1, 5, 5, 7, 48, 1, 1))\nid_pkix_ocsp_nonce = univ.ObjectIdentifier((1, 3, 6, 1, 5, 5, 7, 48, 1, 2))\nid_pkix_ocsp_crl = univ.ObjectIdentifier((1, 3, 6, 1, 5, 5, 7, 48, 1, 3))\nid_pkix_ocsp_response = univ.ObjectIdentifier((1, 3, 6, 1, 5, 5, 7, 48, 1, 4))\nid_pkix_ocsp_nocheck = univ.ObjectIdentifier((1, 3, 6, 1, 5, 5, 7, 48, 1, 5))\nid_pkix_ocsp_archive_cutoff = univ.ObjectIdentifier((1, 3, 6, 1, 5, 5, 7, 48, 1, 6))\nid_pkix_ocsp_service_locator = univ.ObjectIdentifier((1, 3, 6, 1, 5, 5, 7, 48, 1, 7))\n\n\nclass AcceptableResponses(univ.SequenceOf):\n    componentType = univ.ObjectIdentifier()\n\n\nclass ArchiveCutoff(useful.GeneralizedTime):\n    pass\n\n\nclass UnknownInfo(univ.Null):\n    pass\n\n\nclass RevokedInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('revocationTime', useful.GeneralizedTime()),\n        namedtype.OptionalNamedType('revocationReason', CRLReason().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n    )\n\n\nclass CertID(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('hashAlgorithm', rfc2459.AlgorithmIdentifier()),\n        namedtype.NamedType('issuerNameHash', univ.OctetString()),\n        namedtype.NamedType('issuerKeyHash', univ.OctetString()),\n        namedtype.NamedType('serialNumber', rfc2459.CertificateSerialNumber())\n    )\n\n\nclass CertStatus(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('good',\n                            univ.Null().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.NamedType('revoked',\n                            RevokedInfo().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.NamedType('unknown',\n                            UnknownInfo().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n    )\n\n\nclass SingleResponse(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('certID', CertID()),\n        namedtype.NamedType('certStatus', CertStatus()),\n        namedtype.NamedType('thisUpdate', useful.GeneralizedTime()),\n        namedtype.OptionalNamedType('nextUpdate', useful.GeneralizedTime().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('singleExtensions', rfc2459.Extensions().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n    )\n\n\nclass KeyHash(univ.OctetString):\n    pass\n\n\nclass ResponderID(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('byName',\n                            rfc2459.Name().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.NamedType('byKey',\n                            KeyHash().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n    )\n\n\nclass Version(univ.Integer):\n    namedValues = namedval.NamedValues(('v1', 0))\n\n\nclass ResponseData(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.DefaultedNamedType('version', Version('v1').subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.NamedType('responderID', ResponderID()),\n        namedtype.NamedType('producedAt', useful.GeneralizedTime()),\n        namedtype.NamedType('responses', univ.SequenceOf(componentType=SingleResponse())),\n        namedtype.OptionalNamedType('responseExtensions', rfc2459.Extensions().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n    )\n\n\nclass BasicOCSPResponse(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('tbsResponseData', ResponseData()),\n        namedtype.NamedType('signatureAlgorithm', rfc2459.AlgorithmIdentifier()),\n        namedtype.NamedType('signature', univ.BitString()),\n        namedtype.OptionalNamedType('certs', univ.SequenceOf(componentType=rfc2459.Certificate()).subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n    )\n\n\nclass ResponseBytes(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('responseType', univ.ObjectIdentifier()),\n        namedtype.NamedType('response', univ.OctetString())\n    )\n\n\nclass OCSPResponseStatus(univ.Enumerated):\n    namedValues = namedval.NamedValues(\n        ('successful', 0),\n        ('malformedRequest', 1),\n        ('internalError', 2),\n        ('tryLater', 3),\n        ('undefinedStatus', 4),  # should never occur\n        ('sigRequired', 5),\n        ('unauthorized', 6)\n    )\n\n\nclass OCSPResponse(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('responseStatus', OCSPResponseStatus()),\n        namedtype.OptionalNamedType('responseBytes', ResponseBytes().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n    )\n\n\nclass Request(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('reqCert', CertID()),\n        namedtype.OptionalNamedType('singleRequestExtensions', rfc2459.Extensions().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n    )\n\n\nclass Signature(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('signatureAlgorithm', rfc2459.AlgorithmIdentifier()),\n        namedtype.NamedType('signature', univ.BitString()),\n        namedtype.OptionalNamedType('certs', univ.SequenceOf(componentType=rfc2459.Certificate()).subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n    )\n\n\nclass TBSRequest(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.DefaultedNamedType('version', Version('v1').subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('requestorName', GeneralName().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.NamedType('requestList', univ.SequenceOf(componentType=Request())),\n        namedtype.OptionalNamedType('requestExtensions', rfc2459.Extensions().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n    )\n\n\nclass OCSPRequest(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('tbsRequest', TBSRequest()),\n        namedtype.OptionalNamedType('optionalSignature', Signature().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc2634.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n# Modified by Russ Housley to add a map for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Enhanced Security Services for S/MIME\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc2634.txt\n#\n\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedval\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nfrom pyasn1_modules import rfc5652\nfrom pyasn1_modules import rfc5280\n\nMAX = float('inf')\n\nContentType = rfc5652.ContentType\n\nIssuerAndSerialNumber = rfc5652.IssuerAndSerialNumber\n\nSubjectKeyIdentifier = rfc5652.SubjectKeyIdentifier\n\nPolicyInformation = rfc5280.PolicyInformation\n\nGeneralNames = rfc5280.GeneralNames\n\nCertificateSerialNumber = rfc5280.CertificateSerialNumber\n\n\n# Signing Certificate Attribute\n# Warning: It is better to use SigningCertificateV2 from RFC 5035\n\nid_aa_signingCertificate = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.12')\n\nclass Hash(univ.OctetString):\n    pass  # SHA-1 hash of entire certificate; RFC 5035 supports other hash algorithms\n\n\nclass IssuerSerial(univ.Sequence):\n    pass\n\nIssuerSerial.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuer', GeneralNames()),\n    namedtype.NamedType('serialNumber', CertificateSerialNumber())\n)\n\n\nclass ESSCertID(univ.Sequence):\n    pass\n\nESSCertID.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('certHash', Hash()),\n    namedtype.OptionalNamedType('issuerSerial', IssuerSerial())\n)\n\n\nclass SigningCertificate(univ.Sequence):\n    pass\n\nSigningCertificate.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('certs', univ.SequenceOf(\n        componentType=ESSCertID())),\n    namedtype.OptionalNamedType('policies', univ.SequenceOf(\n        componentType=PolicyInformation()))\n)\n\n\n# Mail List Expansion History Attribute\n\nid_aa_mlExpandHistory = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.3')\n\nub_ml_expansion_history = univ.Integer(64)\n\n\nclass EntityIdentifier(univ.Choice):\n    pass\n\nEntityIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerAndSerialNumber', IssuerAndSerialNumber()),\n    namedtype.NamedType('subjectKeyIdentifier', SubjectKeyIdentifier())\n)\n\n\nclass MLReceiptPolicy(univ.Choice):\n    pass\n\nMLReceiptPolicy.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('none', univ.Null().subtype(implicitTag=tag.Tag(\n        tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('insteadOf', univ.SequenceOf(\n        componentType=GeneralNames()).subtype(\n        sizeSpec=constraint.ValueSizeConstraint(1, MAX)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('inAdditionTo', univ.SequenceOf(\n        componentType=GeneralNames()).subtype(\n        sizeSpec=constraint.ValueSizeConstraint(1, MAX)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\n\nclass MLData(univ.Sequence):\n    pass\n\nMLData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('mailListIdentifier', EntityIdentifier()),\n    namedtype.NamedType('expansionTime', useful.GeneralizedTime()),\n    namedtype.OptionalNamedType('mlReceiptPolicy', MLReceiptPolicy())\n)\n\nclass MLExpansionHistory(univ.SequenceOf):\n    pass\n\nMLExpansionHistory.componentType = MLData()\nMLExpansionHistory.sizeSpec = constraint.ValueSizeConstraint(1, ub_ml_expansion_history)\n\n\n# ESS Security Label Attribute\n\nid_aa_securityLabel = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.2')\n\nub_privacy_mark_length = univ.Integer(128)\n\nub_security_categories = univ.Integer(64)\n\nub_integer_options = univ.Integer(256)\n\n\nclass ESSPrivacyMark(univ.Choice):\n    pass\n\nESSPrivacyMark.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('pString', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_privacy_mark_length))),\n    namedtype.NamedType('utf8String', char.UTF8String().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, MAX)))\n)\n\n\nclass SecurityClassification(univ.Integer):\n    pass\n\nSecurityClassification.subtypeSpec=constraint.ValueRangeConstraint(0, ub_integer_options)\n\nSecurityClassification.namedValues = namedval.NamedValues(\n    ('unmarked', 0),\n    ('unclassified', 1),\n    ('restricted', 2),\n    ('confidential', 3),\n    ('secret', 4),\n    ('top-secret', 5)\n)\n\n\nclass SecurityPolicyIdentifier(univ.ObjectIdentifier):\n    pass\n\n\nclass SecurityCategory(univ.Sequence):\n    pass\n\nSecurityCategory.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('type', univ.ObjectIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('value', univ.Any().subtype(implicitTag=tag.Tag(\n        tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass SecurityCategories(univ.SetOf):\n    pass\n\nSecurityCategories.componentType = SecurityCategory()\nSecurityCategories.sizeSpec = constraint.ValueSizeConstraint(1, ub_security_categories)\n\n\nclass ESSSecurityLabel(univ.Set):\n    pass\n\nESSSecurityLabel.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('security-policy-identifier', SecurityPolicyIdentifier()),\n    namedtype.OptionalNamedType('security-classification', SecurityClassification()),\n    namedtype.OptionalNamedType('privacy-mark', ESSPrivacyMark()),\n    namedtype.OptionalNamedType('security-categories', SecurityCategories())\n)\n\n\n# Equivalent Labels Attribute\n\nid_aa_equivalentLabels = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.9')\n\nclass EquivalentLabels(univ.SequenceOf):\n    pass\n\nEquivalentLabels.componentType = ESSSecurityLabel()\n\n\n# Content Identifier Attribute\n\nid_aa_contentIdentifier = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.7')\n\nclass ContentIdentifier(univ.OctetString):\n    pass\n\n\n# Content Reference Attribute\n\nid_aa_contentReference = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.10')\n\nclass ContentReference(univ.Sequence):\n    pass\n\nContentReference.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('contentType', ContentType()),\n    namedtype.NamedType('signedContentIdentifier', ContentIdentifier()),\n    namedtype.NamedType('originatorSignatureValue', univ.OctetString())\n)\n\n\n# Message Signature Digest Attribute\n\nid_aa_msgSigDigest = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.5')\n\nclass MsgSigDigest(univ.OctetString):\n    pass\n\n\n# Content Hints Attribute\n\nid_aa_contentHint = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.4')\n\nclass ContentHints(univ.Sequence):\n    pass\n\nContentHints.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('contentDescription', char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.NamedType('contentType', ContentType())\n)\n\n\n# Receipt Request Attribute\n\nclass AllOrFirstTier(univ.Integer):\n    pass\n\nAllOrFirstTier.namedValues = namedval.NamedValues(\n    ('allReceipts', 0),\n    ('firstTierRecipients', 1)\n)\n\n\nclass ReceiptsFrom(univ.Choice):\n    pass\n\nReceiptsFrom.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('allOrFirstTier', AllOrFirstTier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('receiptList', univ.SequenceOf(\n        componentType=GeneralNames()).subtype(implicitTag=tag.Tag(\n        tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nid_aa_receiptRequest = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.1')\n\nub_receiptsTo = univ.Integer(16)\n\nclass ReceiptRequest(univ.Sequence):\n    pass\n\nReceiptRequest.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('signedContentIdentifier', ContentIdentifier()),\n    namedtype.NamedType('receiptsFrom', ReceiptsFrom()),\n    namedtype.NamedType('receiptsTo', univ.SequenceOf(componentType=GeneralNames()).subtype(sizeSpec=constraint.ValueSizeConstraint(1, ub_receiptsTo)))\n)\n\n# Receipt Content Type\n\nclass ESSVersion(univ.Integer):\n    pass\n\nESSVersion.namedValues = namedval.NamedValues(\n    ('v1', 1)\n)\n\n\nid_ct_receipt = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.1')\n\nclass Receipt(univ.Sequence):\n    pass\n\nReceipt.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', ESSVersion()),\n    namedtype.NamedType('contentType', ContentType()),\n    namedtype.NamedType('signedContentIdentifier', ContentIdentifier()),\n    namedtype.NamedType('originatorSignatureValue', univ.OctetString())\n)\n\n\n# Map of Attribute Type to the Attribute structure is added to the\n# ones that are in rfc5652.py\n\n_cmsAttributesMapUpdate = {\n    id_aa_signingCertificate: SigningCertificate(),\n    id_aa_mlExpandHistory: MLExpansionHistory(),\n    id_aa_securityLabel: ESSSecurityLabel(),\n    id_aa_equivalentLabels: EquivalentLabels(),\n    id_aa_contentIdentifier: ContentIdentifier(),\n    id_aa_contentReference: ContentReference(),\n    id_aa_msgSigDigest: MsgSigDigest(),\n    id_aa_contentHint: ContentHints(),\n    id_aa_receiptRequest: ReceiptRequest(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n\n\n# Map of Content Type OIDs to Content Types is added to the\n# ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_receipt: Receipt(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc2985.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# PKCS#9: Selected Attribute Types (Version 2.0)\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc2985.txt\n#\n\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import opentype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nfrom pyasn1_modules import rfc7292\nfrom pyasn1_modules import rfc5958\nfrom pyasn1_modules import rfc5652\nfrom pyasn1_modules import rfc5280\n\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\nMAX = float('inf')\n\n\n# Imports from RFC 5280\n\nAlgorithmIdentifier = rfc5280.AlgorithmIdentifier\n\nAttribute = rfc5280.Attribute\n\nEmailAddress = rfc5280.EmailAddress\n\nExtensions = rfc5280.Extensions\n\nTime = rfc5280.Time\n\nX520countryName = rfc5280.X520countryName\n\nX520SerialNumber = rfc5280.X520SerialNumber\n\n\n# Imports from RFC 5652\n\nContentInfo = rfc5652.ContentInfo\n\nContentType = rfc5652.ContentType\n\nCountersignature = rfc5652.Countersignature\n\nMessageDigest = rfc5652.MessageDigest\n\nSignerInfo = rfc5652.SignerInfo\n\nSigningTime = rfc5652.SigningTime\n\n\n# Imports from RFC 5958\n\nEncryptedPrivateKeyInfo = rfc5958.EncryptedPrivateKeyInfo\n\n\n# Imports from RFC 7292\n\nPFX = rfc7292.PFX\n\n\n# TODO:\n# Need a place to import PKCS15Token; it does not yet appear in an RFC\n\n\n# SingleAttribute is the same as Attribute in RFC 5280, except that the\n# attrValues SET must have one and only one member\n\nclass AttributeType(univ.ObjectIdentifier):\n    pass\n\n\nclass AttributeValue(univ.Any):\n    pass\n\n\nclass AttributeValues(univ.SetOf):\n    pass\n\nAttributeValues.componentType = AttributeValue()\n\n\nclass SingleAttributeValues(univ.SetOf):\n    pass\n\nSingleAttributeValues.componentType = AttributeValue()\n\n\nclass SingleAttribute(univ.Sequence):\n    pass\n\nSingleAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('type', AttributeType()),\n    namedtype.NamedType('values',\n        AttributeValues().subtype(sizeSpec=constraint.ValueSizeConstraint(1, 1)),\n        openType=opentype.OpenType('type', rfc5280.certificateAttributesMap)\n    )\n)\n\n\n# CMSAttribute is the same as Attribute in RFC 5652, and CMSSingleAttribute\n# is the companion where the attrValues SET must have one and only one member\n\nCMSAttribute = rfc5652.Attribute\n\n\nclass CMSSingleAttribute(univ.Sequence):\n    pass\n\nCMSSingleAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('attrType', AttributeType()),\n    namedtype.NamedType('attrValues',\n        AttributeValues().subtype(sizeSpec=constraint.ValueSizeConstraint(1, 1)),\n        openType=opentype.OpenType('attrType', rfc5652.cmsAttributesMap)\n    )\n)\n\n\n# DirectoryString is the same as RFC 5280, except the length is limited to 255\n\nclass DirectoryString(univ.Choice):\n    pass\n\nDirectoryString.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, 255))),\n    namedtype.NamedType('printableString', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, 255))),\n    namedtype.NamedType('universalString', char.UniversalString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, 255))),\n    namedtype.NamedType('utf8String', char.UTF8String().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, 255))),\n    namedtype.NamedType('bmpString', char.BMPString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, 255)))\n)\n\n\n# PKCS9String is DirectoryString with an additional choice of IA5String,\n# and the SIZE is limited to 255\n\nclass PKCS9String(univ.Choice):\n    pass\n\nPKCS9String.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('ia5String', char.IA5String().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, 255))),\n    namedtype.NamedType('directoryString', DirectoryString())\n)\n\n\n# Upper Bounds\n\npkcs_9_ub_pkcs9String = univ.Integer(255)\n\npkcs_9_ub_challengePassword = univ.Integer(pkcs_9_ub_pkcs9String)\n\npkcs_9_ub_emailAddress = univ.Integer(pkcs_9_ub_pkcs9String)\n\npkcs_9_ub_friendlyName = univ.Integer(pkcs_9_ub_pkcs9String)\n\npkcs_9_ub_match = univ.Integer(pkcs_9_ub_pkcs9String)\n\npkcs_9_ub_signingDescription = univ.Integer(pkcs_9_ub_pkcs9String)\n\npkcs_9_ub_unstructuredAddress = univ.Integer(pkcs_9_ub_pkcs9String)\n\npkcs_9_ub_unstructuredName = univ.Integer(pkcs_9_ub_pkcs9String)\n\n\nub_name = univ.Integer(32768)\n\npkcs_9_ub_placeOfBirth = univ.Integer(ub_name)\n\npkcs_9_ub_pseudonym = univ.Integer(ub_name)\n\n\n# Object Identifier Arcs\n\nietf_at = _OID(1, 3, 6, 1, 5, 5, 7, 9)\n\nid_at = _OID(2, 5, 4)\n\npkcs_9 = _OID(1, 2, 840, 113549, 1, 9)\n\npkcs_9_mo = _OID(pkcs_9, 0)\n\nsmime = _OID(pkcs_9, 16)\n\ncertTypes = _OID(pkcs_9, 22)\n\ncrlTypes = _OID(pkcs_9, 23)\n\npkcs_9_oc = _OID(pkcs_9, 24)\n\npkcs_9_at = _OID(pkcs_9, 25)\n\npkcs_9_sx = _OID(pkcs_9, 26)\n\npkcs_9_mr = _OID(pkcs_9, 27)\n\n\n# Object Identifiers for Syntaxes for use with LDAP-accessible directories\n\npkcs_9_sx_pkcs9String = _OID(pkcs_9_sx, 1)\n\npkcs_9_sx_signingTime = _OID(pkcs_9_sx, 2)\n\n\n# Object Identifiers for object classes\n\npkcs_9_oc_pkcsEntity = _OID(pkcs_9_oc, 1)\n\npkcs_9_oc_naturalPerson = _OID(pkcs_9_oc, 2)\n\n\n# Object Identifiers for matching rules\n\npkcs_9_mr_caseIgnoreMatch = _OID(pkcs_9_mr, 1)\n\npkcs_9_mr_signingTimeMatch = _OID(pkcs_9_mr, 2)\n\n\n# PKCS #7 PDU\n\npkcs_9_at_pkcs7PDU = _OID(pkcs_9_at, 5)\n\npKCS7PDU = Attribute()\npKCS7PDU['type'] = pkcs_9_at_pkcs7PDU\npKCS7PDU['values'][0] = ContentInfo()\n\n\n# PKCS #12 token\n\npkcs_9_at_userPKCS12 = _OID(2, 16, 840, 1, 113730, 3, 1, 216)\n\nuserPKCS12 = Attribute()\nuserPKCS12['type'] = pkcs_9_at_userPKCS12\nuserPKCS12['values'][0] = PFX()\n\n\n# PKCS #15 token\n\npkcs_9_at_pkcs15Token = _OID(pkcs_9_at, 1)\n\n# TODO: Once PKCS15Token can be imported, this can be included\n# \n# pKCS15Token = Attribute()\n# userPKCS12['type'] = pkcs_9_at_pkcs15Token\n# userPKCS12['values'][0] = PKCS15Token()\n\n\n# PKCS #8 encrypted private key information\n\npkcs_9_at_encryptedPrivateKeyInfo = _OID(pkcs_9_at, 2)\n\nencryptedPrivateKeyInfo = Attribute()\nencryptedPrivateKeyInfo['type'] = pkcs_9_at_encryptedPrivateKeyInfo\nencryptedPrivateKeyInfo['values'][0] = EncryptedPrivateKeyInfo()\n\n\n# Electronic-mail address\n\npkcs_9_at_emailAddress = rfc5280.id_emailAddress\n\nemailAddress = Attribute()\nemailAddress['type'] = pkcs_9_at_emailAddress\nemailAddress['values'][0] = EmailAddress()\n\n\n# Unstructured name\n\npkcs_9_at_unstructuredName = _OID(pkcs_9, 2)\n\nunstructuredName = Attribute()\nunstructuredName['type'] = pkcs_9_at_unstructuredName\nunstructuredName['values'][0] = PKCS9String()\n\n\n# Unstructured address\n\npkcs_9_at_unstructuredAddress = _OID(pkcs_9, 8)\n\nunstructuredAddress = Attribute()\nunstructuredAddress['type'] = pkcs_9_at_unstructuredAddress\nunstructuredAddress['values'][0] = DirectoryString()\n\n\n# Date of birth\n\npkcs_9_at_dateOfBirth = _OID(ietf_at, 1)\n\ndateOfBirth = SingleAttribute()\ndateOfBirth['type'] = pkcs_9_at_dateOfBirth\ndateOfBirth['values'][0] = useful.GeneralizedTime()\n\n\n# Place of birth\n\npkcs_9_at_placeOfBirth = _OID(ietf_at, 2)\n\nplaceOfBirth = SingleAttribute()\nplaceOfBirth['type'] = pkcs_9_at_placeOfBirth\nplaceOfBirth['values'][0] = DirectoryString()\n\n\n# Gender\n\nclass GenderString(char.PrintableString):\n    pass\n\nGenderString.subtypeSpec = constraint.ValueSizeConstraint(1, 1)\nGenderString.subtypeSpec = constraint.SingleValueConstraint(\"M\", \"F\", \"m\", \"f\")\n\n\npkcs_9_at_gender = _OID(ietf_at, 3)\n\ngender = SingleAttribute()\ngender['type'] = pkcs_9_at_gender\ngender['values'][0] = GenderString()\n\n\n# Country of citizenship\n\npkcs_9_at_countryOfCitizenship = _OID(ietf_at, 4)\n\ncountryOfCitizenship = Attribute()\ncountryOfCitizenship['type'] = pkcs_9_at_countryOfCitizenship\ncountryOfCitizenship['values'][0] = X520countryName()\n\n\n#  Country of residence\n\npkcs_9_at_countryOfResidence = _OID(ietf_at, 5)\n\ncountryOfResidence = Attribute()\ncountryOfResidence['type'] = pkcs_9_at_countryOfResidence\ncountryOfResidence['values'][0] = X520countryName()\n\n\n# Pseudonym\n\nid_at_pseudonym = _OID(2, 5, 4, 65)\n\npseudonym = Attribute()\npseudonym['type'] = id_at_pseudonym\npseudonym['values'][0] = DirectoryString()\n\n\n# Serial number\n\nid_at_serialNumber = rfc5280.id_at_serialNumber\n\nserialNumber = Attribute()\nserialNumber['type'] = id_at_serialNumber\nserialNumber['values'][0] = X520SerialNumber()\n\n\n# Content type\n\npkcs_9_at_contentType = rfc5652.id_contentType\n\ncontentType = CMSSingleAttribute()\ncontentType['attrType'] = pkcs_9_at_contentType\ncontentType['attrValues'][0] = ContentType()\n\n\n# Message digest\n\npkcs_9_at_messageDigest = rfc5652.id_messageDigest\n\nmessageDigest = CMSSingleAttribute()\nmessageDigest['attrType'] = pkcs_9_at_messageDigest\nmessageDigest['attrValues'][0] = MessageDigest()\n\n\n# Signing time\n\npkcs_9_at_signingTime = rfc5652.id_signingTime\n\nsigningTime = CMSSingleAttribute()\nsigningTime['attrType'] = pkcs_9_at_signingTime\nsigningTime['attrValues'][0] = SigningTime()\n\n\n# Random nonce\n\nclass RandomNonce(univ.OctetString):\n    pass\n\nRandomNonce.subtypeSpec = constraint.ValueSizeConstraint(4, MAX)\n\n\npkcs_9_at_randomNonce = _OID(pkcs_9_at, 3)\n\nrandomNonce = CMSSingleAttribute()\nrandomNonce['attrType'] = pkcs_9_at_randomNonce\nrandomNonce['attrValues'][0] = RandomNonce()\n\n\n# Sequence number\n\nclass SequenceNumber(univ.Integer):\n    pass\n\nSequenceNumber.subtypeSpec = constraint.ValueRangeConstraint(1, MAX)\n\n\npkcs_9_at_sequenceNumber = _OID(pkcs_9_at, 4)\n\nsequenceNumber = CMSSingleAttribute()\nsequenceNumber['attrType'] = pkcs_9_at_sequenceNumber\nsequenceNumber['attrValues'][0] = SequenceNumber()\n\n\n# Countersignature\n\npkcs_9_at_counterSignature = rfc5652.id_countersignature\n\ncounterSignature = CMSAttribute()\ncounterSignature['attrType'] = pkcs_9_at_counterSignature\ncounterSignature['attrValues'][0] = Countersignature()\n\n\n# Challenge password\n\npkcs_9_at_challengePassword = _OID(pkcs_9, 7)\n\nchallengePassword = SingleAttribute()\nchallengePassword['type'] = pkcs_9_at_challengePassword\nchallengePassword['values'][0] = DirectoryString()\n\n\n# Extension request\n\nclass ExtensionRequest(Extensions):\n    pass\n\n\npkcs_9_at_extensionRequest = _OID(pkcs_9, 14)\n\nextensionRequest = SingleAttribute()\nextensionRequest['type'] = pkcs_9_at_extensionRequest\nextensionRequest['values'][0] = ExtensionRequest()\n\n\n# Extended-certificate attributes (deprecated)\n\nclass AttributeSet(univ.SetOf):\n    pass\n\nAttributeSet.componentType = Attribute()\n\n\npkcs_9_at_extendedCertificateAttributes = _OID(pkcs_9, 9)\n\nextendedCertificateAttributes = SingleAttribute()\nextendedCertificateAttributes['type'] = pkcs_9_at_extendedCertificateAttributes\nextendedCertificateAttributes['values'][0] = AttributeSet()\n\n\n# Friendly name\n\nclass FriendlyName(char.BMPString):\n    pass\n\nFriendlyName.subtypeSpec = constraint.ValueSizeConstraint(1, pkcs_9_ub_friendlyName)\n\n\npkcs_9_at_friendlyName = _OID(pkcs_9, 20)\n\nfriendlyName = SingleAttribute()\nfriendlyName['type'] = pkcs_9_at_friendlyName\nfriendlyName['values'][0] = FriendlyName()\n\n\n# Local key identifier\n\npkcs_9_at_localKeyId = _OID(pkcs_9, 21)\n\nlocalKeyId = SingleAttribute()\nlocalKeyId['type'] = pkcs_9_at_localKeyId\nlocalKeyId['values'][0] = univ.OctetString()\n\n\n# Signing description\n\npkcs_9_at_signingDescription = _OID(pkcs_9, 13)\n\nsigningDescription = CMSSingleAttribute()\nsigningDescription['attrType'] = pkcs_9_at_signingDescription\nsigningDescription['attrValues'][0] = DirectoryString()\n\n\n# S/MIME capabilities\n\nclass SMIMECapability(AlgorithmIdentifier):\n    pass\n\n\nclass SMIMECapabilities(univ.SequenceOf):\n    pass\n\nSMIMECapabilities.componentType = SMIMECapability()\n\n\npkcs_9_at_smimeCapabilities = _OID(pkcs_9, 15)\n\nsmimeCapabilities = CMSSingleAttribute()\nsmimeCapabilities['attrType'] = pkcs_9_at_smimeCapabilities\nsmimeCapabilities['attrValues'][0] = SMIMECapabilities()\n\n\n# Certificate Attribute Map\n\n_certificateAttributesMapUpdate = {\n    # Attribute types for use with the \"pkcsEntity\" object class\n    pkcs_9_at_pkcs7PDU: ContentInfo(),\n    pkcs_9_at_userPKCS12: PFX(),\n    # TODO: Once PKCS15Token can be imported, this can be included\n    # pkcs_9_at_pkcs15Token: PKCS15Token(),\n    pkcs_9_at_encryptedPrivateKeyInfo: EncryptedPrivateKeyInfo(),\n    # Attribute types for use with the \"naturalPerson\" object class\n    pkcs_9_at_emailAddress: EmailAddress(),\n    pkcs_9_at_unstructuredName: PKCS9String(),\n    pkcs_9_at_unstructuredAddress: DirectoryString(),\n    pkcs_9_at_dateOfBirth: useful.GeneralizedTime(),\n    pkcs_9_at_placeOfBirth: DirectoryString(),\n    pkcs_9_at_gender: GenderString(),\n    pkcs_9_at_countryOfCitizenship: X520countryName(),\n    pkcs_9_at_countryOfResidence: X520countryName(),\n    id_at_pseudonym: DirectoryString(),\n    id_at_serialNumber: X520SerialNumber(),\n    # Attribute types for use with PKCS #10 certificate requests\n    pkcs_9_at_challengePassword: DirectoryString(),\n    pkcs_9_at_extensionRequest: ExtensionRequest(),\n    pkcs_9_at_extendedCertificateAttributes: AttributeSet(),\n}\n\nrfc5280.certificateAttributesMap.update(_certificateAttributesMapUpdate)\n\n\n# CMS Attribute Map\n\n# Note: pkcs_9_at_smimeCapabilities is not included in the map because\n#       the definition in RFC 5751 is preferred, which produces the same\n#       encoding, but it allows different parameters for SMIMECapability\n#       and AlgorithmIdentifier.\n\n_cmsAttributesMapUpdate = {\n    # Attribute types for use in PKCS #7 data (a.k.a. CMS)\n    pkcs_9_at_contentType: ContentType(),\n    pkcs_9_at_messageDigest: MessageDigest(),\n    pkcs_9_at_signingTime: SigningTime(),\n    pkcs_9_at_randomNonce: RandomNonce(),\n    pkcs_9_at_sequenceNumber: SequenceNumber(),\n    pkcs_9_at_counterSignature: Countersignature(),\n    # Attributes for use in PKCS #12 \"PFX\" PDUs or PKCS #15 tokens\n    pkcs_9_at_friendlyName: FriendlyName(),\n    pkcs_9_at_localKeyId: univ.OctetString(),\n    pkcs_9_at_signingDescription: DirectoryString(),\n    # pkcs_9_at_smimeCapabilities: SMIMECapabilities(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc2986.py",
    "content": "# coding: utf-8\n#\n# This file is part of pyasn1-modules software.\n#\n# Created by Joel Johnson with asn1ate tool.\n# Modified by Russ Housley to add support for opentypes by importing\n#   definitions from rfc5280 so that the same maps are used.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# PKCS #10: Certification Request Syntax Specification\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc2986.txt\n#\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\nMAX = float('inf')\n\n\nAttributeType = rfc5280.AttributeType\n\nAttributeValue = rfc5280.AttributeValue\n\nAttributeTypeAndValue = rfc5280.AttributeTypeAndValue\n\nAttribute = rfc5280.Attribute\n\nRelativeDistinguishedName = rfc5280.RelativeDistinguishedName\n\nRDNSequence = rfc5280.RDNSequence\n\nName = rfc5280.Name\n\nAlgorithmIdentifier = rfc5280.AlgorithmIdentifier\n\nSubjectPublicKeyInfo = rfc5280.SubjectPublicKeyInfo\n\n\nclass Attributes(univ.SetOf):\n    pass\n\n\nAttributes.componentType = Attribute()\n\n\nclass CertificationRequestInfo(univ.Sequence):\n    pass\n\n\nCertificationRequestInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', univ.Integer()),\n    namedtype.NamedType('subject', Name()),\n    namedtype.NamedType('subjectPKInfo', SubjectPublicKeyInfo()),\n    namedtype.NamedType('attributes',\n                        Attributes().subtype(implicitTag=tag.Tag(\n                            tag.tagClassContext, tag.tagFormatSimple, 0))\n    )\n)\n\n\nclass CertificationRequest(univ.Sequence):\n    pass\n\n\nCertificationRequest.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('certificationRequestInfo', CertificationRequestInfo()),\n    namedtype.NamedType('signatureAlgorithm', AlgorithmIdentifier()),\n    namedtype.NamedType('signature', univ.BitString())\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3161.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Time-Stamp Protocol (TSP)\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc3161.txt\n#\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nfrom pyasn1_modules import rfc4210\nfrom pyasn1_modules import rfc5280\nfrom pyasn1_modules import rfc5652\n\n\nExtensions = rfc5280.Extensions\n\nAlgorithmIdentifier = rfc5280.AlgorithmIdentifier\n\nGeneralName = rfc5280.GeneralName\n\nContentInfo = rfc5652.ContentInfo\n\nPKIFreeText = rfc4210.PKIFreeText\n\n\nid_ct_TSTInfo = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.4')\n\n\nclass Accuracy(univ.Sequence):\n    pass\n\nAccuracy.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('seconds', univ.Integer()),\n    namedtype.OptionalNamedType('millis', univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(1, 999)).subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('micros', univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(1, 999)).subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass MessageImprint(univ.Sequence):\n    pass\n\nMessageImprint.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('hashAlgorithm', AlgorithmIdentifier()),\n    namedtype.NamedType('hashedMessage', univ.OctetString())\n)\n\n\nclass PKIFailureInfo(univ.BitString):\n    pass\n\nPKIFailureInfo.namedValues = namedval.NamedValues(\n    ('badAlg', 0),\n    ('badRequest', 2),\n    ('badDataFormat', 5),\n    ('timeNotAvailable', 14),\n    ('unacceptedPolicy', 15),\n    ('unacceptedExtension', 16),\n    ('addInfoNotAvailable', 17),\n    ('systemFailure', 25)\n)\n\n\nclass PKIStatus(univ.Integer):\n    pass\n\nPKIStatus.namedValues = namedval.NamedValues(\n    ('granted', 0),\n    ('grantedWithMods', 1),\n    ('rejection', 2),\n    ('waiting', 3),\n    ('revocationWarning', 4),\n    ('revocationNotification', 5)\n)\n\n\nclass PKIStatusInfo(univ.Sequence):\n    pass\n\nPKIStatusInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('status', PKIStatus()),\n    namedtype.OptionalNamedType('statusString', PKIFreeText()),\n    namedtype.OptionalNamedType('failInfo', PKIFailureInfo())\n)\n\n\nclass TSAPolicyId(univ.ObjectIdentifier):\n    pass\n\n\nclass TSTInfo(univ.Sequence):\n    pass\n\nTSTInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', univ.Integer(namedValues=namedval.NamedValues(('v1', 1)))),\n    namedtype.NamedType('policy', TSAPolicyId()),\n    namedtype.NamedType('messageImprint', MessageImprint()),\n    namedtype.NamedType('serialNumber', univ.Integer()),\n    namedtype.NamedType('genTime', useful.GeneralizedTime()),\n    namedtype.OptionalNamedType('accuracy', Accuracy()),\n    namedtype.DefaultedNamedType('ordering', univ.Boolean().subtype(value=0)),\n    namedtype.OptionalNamedType('nonce', univ.Integer()),\n    namedtype.OptionalNamedType('tsa', GeneralName().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('extensions', Extensions().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass TimeStampReq(univ.Sequence):\n    pass\n\nTimeStampReq.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', univ.Integer(namedValues=namedval.NamedValues(('v1', 1)))),\n    namedtype.NamedType('messageImprint', MessageImprint()),\n    namedtype.OptionalNamedType('reqPolicy', TSAPolicyId()),\n    namedtype.OptionalNamedType('nonce', univ.Integer()),\n    namedtype.DefaultedNamedType('certReq', univ.Boolean().subtype(value=0)),\n    namedtype.OptionalNamedType('extensions', Extensions().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass TimeStampToken(ContentInfo):\n    pass\n\n\nclass TimeStampResp(univ.Sequence):\n    pass\n\nTimeStampResp.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('status', PKIStatusInfo()),\n    namedtype.OptionalNamedType('timeStampToken', TimeStampToken())\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3274.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n# Modified by Russ Housley to add a map for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# CMS Compressed Data Content Type\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc3274.txt\n#\n\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\nfrom pyasn1_modules import rfc5652\n\n\nclass CompressionAlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\n# The CMS Compressed Data Content Type\n\nid_ct_compressedData = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.9')\n\nclass CompressedData(univ.Sequence):\n    pass\n\nCompressedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', rfc5652.CMSVersion()), # Always set to 0\n    namedtype.NamedType('compressionAlgorithm', CompressionAlgorithmIdentifier()),\n    namedtype.NamedType('encapContentInfo', rfc5652.EncapsulatedContentInfo())\n)\n\n\n# Algorithm identifier for the zLib Compression Algorithm\n# This includes cpa_zlibCompress as defined in RFC 6268,\n# from https://www.rfc-editor.org/rfc/rfc6268.txt\n\nid_alg_zlibCompress = univ.ObjectIdentifier('1.2.840.113549.1.9.16.3.8')\n\ncpa_zlibCompress = rfc5280.AlgorithmIdentifier()\ncpa_zlibCompress['algorithm'] = id_alg_zlibCompress\n# cpa_zlibCompress['parameters'] are absent\n\n\n# Map of Content Type OIDs to Content Types is added to thr\n# ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_compressedData: CompressedData(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3279.py",
    "content": "#\n# This file is part of pyasn1-modules.\n#\n# Copyright (c) 2017, Danielle Madeley <danielle@madeley.id.au>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Derived from RFC 3279\n#\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import univ\n\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\nmd2 = _OID(1, 2, 840, 113549, 2, 2)\nmd5 = _OID(1, 2, 840, 113549, 2, 5)\nid_sha1 = _OID(1, 3, 14, 3, 2, 26)\nid_dsa = _OID(1, 2, 840, 10040, 4, 1)\n\n\nclass DSAPublicKey(univ.Integer):\n    pass\n\n\nclass Dss_Parms(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('p', univ.Integer()),\n        namedtype.NamedType('q', univ.Integer()),\n        namedtype.NamedType('g', univ.Integer())\n    )\n\n\nid_dsa_with_sha1 = _OID(1, 2, 840, 10040, 4, 3)\n\n\nclass Dss_Sig_Value(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('r', univ.Integer()),\n        namedtype.NamedType('s', univ.Integer())\n    )\n\n\npkcs_1 = _OID(1, 2, 840, 113549, 1, 1)\nrsaEncryption = _OID(pkcs_1, 1)\nmd2WithRSAEncryption = _OID(pkcs_1, 2)\nmd5WithRSAEncryption = _OID(pkcs_1, 4)\nsha1WithRSAEncryption = _OID(pkcs_1, 5)\n\n\nclass RSAPublicKey(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('modulus', univ.Integer()),\n        namedtype.NamedType('publicExponent', univ.Integer())\n    )\n\n\ndhpublicnumber = _OID(1, 2, 840, 10046, 2, 1)\n\n\nclass DHPublicKey(univ.Integer):\n    pass\n\n\nclass ValidationParms(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('seed', univ.BitString()),\n        namedtype.NamedType('pgenCounter', univ.Integer())\n    )\n\n\nclass DomainParameters(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('p', univ.Integer()),\n        namedtype.NamedType('g', univ.Integer()),\n        namedtype.NamedType('q', univ.Integer()),\n        namedtype.OptionalNamedType('j', univ.Integer()),\n        namedtype.OptionalNamedType('validationParms', ValidationParms())\n    )\n\n\nid_keyExchangeAlgorithm = _OID(2, 16, 840, 1, 101, 2, 1, 1, 22)\n\n\nclass KEA_Parms_Id(univ.OctetString):\n    pass\n\n\nansi_X9_62 = _OID(1, 2, 840, 10045)\n\n\nclass FieldID(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('fieldType', univ.ObjectIdentifier()),\n        namedtype.NamedType('parameters', univ.Any())\n    )\n\n\nid_ecSigType = _OID(ansi_X9_62, 4)\necdsa_with_SHA1 = _OID(id_ecSigType, 1)\n\n\nclass ECDSA_Sig_Value(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('r', univ.Integer()),\n        namedtype.NamedType('s', univ.Integer())\n    )\n\n\nid_fieldType = _OID(ansi_X9_62, 1)\nprime_field = _OID(id_fieldType, 1)\n\n\nclass Prime_p(univ.Integer):\n    pass\n\n\ncharacteristic_two_field = _OID(id_fieldType, 2)\n\n\nclass Characteristic_two(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('m', univ.Integer()),\n        namedtype.NamedType('basis', univ.ObjectIdentifier()),\n        namedtype.NamedType('parameters', univ.Any())\n    )\n\n\nid_characteristic_two_basis = _OID(characteristic_two_field, 3)\ngnBasis = _OID(id_characteristic_two_basis, 1)\ntpBasis = _OID(id_characteristic_two_basis, 2)\n\n\nclass Trinomial(univ.Integer):\n    pass\n\n\nppBasis = _OID(id_characteristic_two_basis, 3)\n\n\nclass Pentanomial(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('k1', univ.Integer()),\n        namedtype.NamedType('k2', univ.Integer()),\n        namedtype.NamedType('k3', univ.Integer())\n    )\n\n\nclass FieldElement(univ.OctetString):\n    pass\n\n\nclass ECPoint(univ.OctetString):\n    pass\n\n\nclass Curve(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('a', FieldElement()),\n        namedtype.NamedType('b', FieldElement()),\n        namedtype.OptionalNamedType('seed', univ.BitString())\n    )\n\n\nclass ECPVer(univ.Integer):\n    namedValues = namedval.NamedValues(\n        ('ecpVer1', 1)\n    )\n\n\nclass ECParameters(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', ECPVer()),\n        namedtype.NamedType('fieldID', FieldID()),\n        namedtype.NamedType('curve', Curve()),\n        namedtype.NamedType('base', ECPoint()),\n        namedtype.NamedType('order', univ.Integer()),\n        namedtype.OptionalNamedType('cofactor', univ.Integer())\n    )\n\n\nclass EcpkParameters(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('ecParameters', ECParameters()),\n        namedtype.NamedType('namedCurve', univ.ObjectIdentifier()),\n        namedtype.NamedType('implicitlyCA', univ.Null())\n    )\n\n\nid_publicKeyType = _OID(ansi_X9_62, 2)\nid_ecPublicKey = _OID(id_publicKeyType, 1)\n\nellipticCurve = _OID(ansi_X9_62, 3)\n\nc_TwoCurve = _OID(ellipticCurve, 0)\nc2pnb163v1 = _OID(c_TwoCurve, 1)\nc2pnb163v2 = _OID(c_TwoCurve, 2)\nc2pnb163v3 = _OID(c_TwoCurve, 3)\nc2pnb176w1 = _OID(c_TwoCurve, 4)\nc2tnb191v1 = _OID(c_TwoCurve, 5)\nc2tnb191v2 = _OID(c_TwoCurve, 6)\nc2tnb191v3 = _OID(c_TwoCurve, 7)\nc2onb191v4 = _OID(c_TwoCurve, 8)\nc2onb191v5 = _OID(c_TwoCurve, 9)\nc2pnb208w1 = _OID(c_TwoCurve, 10)\nc2tnb239v1 = _OID(c_TwoCurve, 11)\nc2tnb239v2 = _OID(c_TwoCurve, 12)\nc2tnb239v3 = _OID(c_TwoCurve, 13)\nc2onb239v4 = _OID(c_TwoCurve, 14)\nc2onb239v5 = _OID(c_TwoCurve, 15)\nc2pnb272w1 = _OID(c_TwoCurve, 16)\nc2pnb304w1 = _OID(c_TwoCurve, 17)\nc2tnb359v1 = _OID(c_TwoCurve, 18)\nc2pnb368w1 = _OID(c_TwoCurve, 19)\nc2tnb431r1 = _OID(c_TwoCurve, 20)\n\nprimeCurve = _OID(ellipticCurve, 1)\nprime192v1 = _OID(primeCurve, 1)\nprime192v2 = _OID(primeCurve, 2)\nprime192v3 = _OID(primeCurve, 3)\nprime239v1 = _OID(primeCurve, 4)\nprime239v2 = _OID(primeCurve, 5)\nprime239v3 = _OID(primeCurve, 6)\nprime256v1 = _OID(primeCurve, 7)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3280.py",
    "content": "# coding: utf-8\n#\n# This file is part of pyasn1-modules software.\n#\n# Created by Stanisław Pitucha with asn1ate tool.\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Internet X.509 Public Key Infrastructure Certificate and Certificate\n# Revocation List (CRL) Profile\n#\n# ASN.1 source from:\n# http://www.ietf.org/rfc/rfc3280.txt\n#\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nMAX = float('inf')\n\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\nunformatted_postal_address = univ.Integer(16)\n\nub_organizational_units = univ.Integer(4)\n\nub_organizational_unit_name_length = univ.Integer(32)\n\n\nclass OrganizationalUnitName(char.PrintableString):\n    pass\n\n\nOrganizationalUnitName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_organizational_unit_name_length)\n\n\nclass OrganizationalUnitNames(univ.SequenceOf):\n    pass\n\n\nOrganizationalUnitNames.componentType = OrganizationalUnitName()\nOrganizationalUnitNames.sizeSpec = constraint.ValueSizeConstraint(1, ub_organizational_units)\n\n\nclass AttributeType(univ.ObjectIdentifier):\n    pass\n\n\nid_at = _OID(2, 5, 4)\n\nid_at_name = _OID(id_at, 41)\n\nub_pds_parameter_length = univ.Integer(30)\n\n\nclass PDSParameter(univ.Set):\n    pass\n\n\nPDSParameter.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('printable-string', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_pds_parameter_length))),\n    namedtype.OptionalNamedType('teletex-string', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_pds_parameter_length)))\n)\n\n\nclass PhysicalDeliveryOrganizationName(PDSParameter):\n    pass\n\n\nub_organization_name_length = univ.Integer(64)\n\nub_domain_defined_attribute_type_length = univ.Integer(8)\n\nub_domain_defined_attribute_value_length = univ.Integer(128)\n\n\nclass TeletexDomainDefinedAttribute(univ.Sequence):\n    pass\n\n\nTeletexDomainDefinedAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('type', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_defined_attribute_type_length))),\n    namedtype.NamedType('value', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_defined_attribute_value_length)))\n)\n\nid_pkix = _OID(1, 3, 6, 1, 5, 5, 7)\n\nid_qt = _OID(id_pkix, 2)\n\n\nclass PresentationAddress(univ.Sequence):\n    pass\n\n\nPresentationAddress.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('pSelector', univ.OctetString().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('sSelector', univ.OctetString().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('tSelector', univ.OctetString().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.NamedType('nAddresses', univ.SetOf(componentType=univ.OctetString()).subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\n\nclass AlgorithmIdentifier(univ.Sequence):\n    pass\n\n\nAlgorithmIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('algorithm', univ.ObjectIdentifier()),\n    namedtype.OptionalNamedType('parameters', univ.Any())\n)\n\n\nclass UniqueIdentifier(univ.BitString):\n    pass\n\n\nclass Extension(univ.Sequence):\n    pass\n\n\nExtension.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('extnID', univ.ObjectIdentifier()),\n    namedtype.DefaultedNamedType('critical', univ.Boolean().subtype(value=0)),\n    namedtype.NamedType('extnValue', univ.OctetString())\n)\n\n\nclass Extensions(univ.SequenceOf):\n    pass\n\n\nExtensions.componentType = Extension()\nExtensions.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass CertificateSerialNumber(univ.Integer):\n    pass\n\n\nclass SubjectPublicKeyInfo(univ.Sequence):\n    pass\n\n\nSubjectPublicKeyInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('algorithm', AlgorithmIdentifier()),\n    namedtype.NamedType('subjectPublicKey', univ.BitString())\n)\n\n\nclass Time(univ.Choice):\n    pass\n\n\nTime.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('utcTime', useful.UTCTime()),\n    namedtype.NamedType('generalTime', useful.GeneralizedTime())\n)\n\n\nclass Validity(univ.Sequence):\n    pass\n\n\nValidity.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('notBefore', Time()),\n    namedtype.NamedType('notAfter', Time())\n)\n\n\nclass Version(univ.Integer):\n    pass\n\n\nVersion.namedValues = namedval.NamedValues(\n    ('v1', 0),\n    ('v2', 1),\n    ('v3', 2)\n)\n\n\nclass AttributeValue(univ.Any):\n    pass\n\n\nclass AttributeTypeAndValue(univ.Sequence):\n    pass\n\n\nAttributeTypeAndValue.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('type', AttributeType()),\n    namedtype.NamedType('value', AttributeValue())\n)\n\n\nclass RelativeDistinguishedName(univ.SetOf):\n    pass\n\n\nRelativeDistinguishedName.componentType = AttributeTypeAndValue()\nRelativeDistinguishedName.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass RDNSequence(univ.SequenceOf):\n    pass\n\n\nRDNSequence.componentType = RelativeDistinguishedName()\n\n\nclass Name(univ.Choice):\n    pass\n\n\nName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('rdnSequence', RDNSequence())\n)\n\n\nclass TBSCertificate(univ.Sequence):\n    pass\n\n\nTBSCertificate.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version',\n                                 Version().subtype(explicitTag=tag.Tag(tag.tagClassContext,\n                                                                       tag.tagFormatSimple, 0)).subtype(value=\"v1\")),\n    namedtype.NamedType('serialNumber', CertificateSerialNumber()),\n    namedtype.NamedType('signature', AlgorithmIdentifier()),\n    namedtype.NamedType('issuer', Name()),\n    namedtype.NamedType('validity', Validity()),\n    namedtype.NamedType('subject', Name()),\n    namedtype.NamedType('subjectPublicKeyInfo', SubjectPublicKeyInfo()),\n    namedtype.OptionalNamedType('issuerUniqueID', UniqueIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('subjectUniqueID', UniqueIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.OptionalNamedType('extensions',\n                                Extensions().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\n\nclass Certificate(univ.Sequence):\n    pass\n\n\nCertificate.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('tbsCertificate', TBSCertificate()),\n    namedtype.NamedType('signatureAlgorithm', AlgorithmIdentifier()),\n    namedtype.NamedType('signature', univ.BitString())\n)\n\nub_surname_length = univ.Integer(40)\n\n\nclass TeletexOrganizationName(char.TeletexString):\n    pass\n\n\nTeletexOrganizationName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_organization_name_length)\n\nub_e163_4_sub_address_length = univ.Integer(40)\n\nteletex_common_name = univ.Integer(2)\n\nub_country_name_alpha_length = univ.Integer(2)\n\nub_country_name_numeric_length = univ.Integer(3)\n\n\nclass CountryName(univ.Choice):\n    pass\n\n\nCountryName.tagSet = univ.Choice.tagSet.tagExplicitly(tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 1))\nCountryName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('x121-dcc-code', char.NumericString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(ub_country_name_numeric_length, ub_country_name_numeric_length))),\n    namedtype.NamedType('iso-3166-alpha2-code', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(ub_country_name_alpha_length, ub_country_name_alpha_length)))\n)\n\nextension_OR_address_components = univ.Integer(12)\n\nid_at_dnQualifier = _OID(id_at, 46)\n\nub_e163_4_number_length = univ.Integer(15)\n\n\nclass ExtendedNetworkAddress(univ.Choice):\n    pass\n\n\nExtendedNetworkAddress.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('e163-4-address', univ.Sequence(componentType=namedtype.NamedTypes(\n        namedtype.NamedType('number', char.NumericString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_e163_4_number_length)).subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('sub-address', char.NumericString().subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, ub_e163_4_sub_address_length)).subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n    ))\n                        ),\n    namedtype.NamedType('psap-address', PresentationAddress().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n)\n\nterminal_type = univ.Integer(23)\n\nid_domainComponent = _OID(0, 9, 2342, 19200300, 100, 1, 25)\n\nub_state_name = univ.Integer(128)\n\n\nclass X520StateOrProvinceName(univ.Choice):\n    pass\n\n\nX520StateOrProvinceName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name))),\n    namedtype.NamedType('printableString',\n                        char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name))),\n    namedtype.NamedType('universalString',\n                        char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name))),\n    namedtype.NamedType('bmpString',\n                        char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name)))\n)\n\nub_organization_name = univ.Integer(64)\n\n\nclass X520OrganizationName(univ.Choice):\n    pass\n\n\nX520OrganizationName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name))),\n    namedtype.NamedType('printableString', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name))),\n    namedtype.NamedType('universalString', char.UniversalString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name))),\n    namedtype.NamedType('bmpString',\n                        char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name)))\n)\n\nub_emailaddress_length = univ.Integer(128)\n\n\nclass ExtensionPhysicalDeliveryAddressComponents(PDSParameter):\n    pass\n\n\nid_at_surname = _OID(id_at, 4)\n\nub_common_name_length = univ.Integer(64)\n\nid_ad = _OID(id_pkix, 48)\n\nub_numeric_user_id_length = univ.Integer(32)\n\n\nclass NumericUserIdentifier(char.NumericString):\n    pass\n\n\nNumericUserIdentifier.subtypeSpec = constraint.ValueSizeConstraint(1, ub_numeric_user_id_length)\n\n\nclass OrganizationName(char.PrintableString):\n    pass\n\n\nOrganizationName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_organization_name_length)\n\nub_domain_name_length = univ.Integer(16)\n\n\nclass AdministrationDomainName(univ.Choice):\n    pass\n\n\nAdministrationDomainName.tagSet = univ.Choice.tagSet.tagExplicitly(\n    tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 2))\nAdministrationDomainName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('numeric', char.NumericString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(0, ub_domain_name_length))),\n    namedtype.NamedType('printable', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(0, ub_domain_name_length)))\n)\n\n\nclass PrivateDomainName(univ.Choice):\n    pass\n\n\nPrivateDomainName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('numeric', char.NumericString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_name_length))),\n    namedtype.NamedType('printable', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_name_length)))\n)\n\nub_generation_qualifier_length = univ.Integer(3)\n\nub_given_name_length = univ.Integer(16)\n\nub_initials_length = univ.Integer(5)\n\n\nclass PersonalName(univ.Set):\n    pass\n\n\nPersonalName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('surname', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_surname_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('given-name', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_given_name_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('initials', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_initials_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.OptionalNamedType('generation-qualifier', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_generation_qualifier_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\nub_terminal_id_length = univ.Integer(24)\n\n\nclass TerminalIdentifier(char.PrintableString):\n    pass\n\n\nTerminalIdentifier.subtypeSpec = constraint.ValueSizeConstraint(1, ub_terminal_id_length)\n\nub_x121_address_length = univ.Integer(16)\n\n\nclass X121Address(char.NumericString):\n    pass\n\n\nX121Address.subtypeSpec = constraint.ValueSizeConstraint(1, ub_x121_address_length)\n\n\nclass NetworkAddress(X121Address):\n    pass\n\n\nclass BuiltInStandardAttributes(univ.Sequence):\n    pass\n\n\nBuiltInStandardAttributes.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('country-name', CountryName()),\n    namedtype.OptionalNamedType('administration-domain-name', AdministrationDomainName()),\n    namedtype.OptionalNamedType('network-address', NetworkAddress().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('terminal-identifier', TerminalIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('private-domain-name', PrivateDomainName().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2))),\n    namedtype.OptionalNamedType('organization-name', OrganizationName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n    namedtype.OptionalNamedType('numeric-user-identifier', NumericUserIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4))),\n    namedtype.OptionalNamedType('personal-name', PersonalName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 5))),\n    namedtype.OptionalNamedType('organizational-unit-names', OrganizationalUnitNames().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 6)))\n)\n\nub_domain_defined_attributes = univ.Integer(4)\n\n\nclass BuiltInDomainDefinedAttribute(univ.Sequence):\n    pass\n\n\nBuiltInDomainDefinedAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('type', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_defined_attribute_type_length))),\n    namedtype.NamedType('value', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_defined_attribute_value_length)))\n)\n\n\nclass BuiltInDomainDefinedAttributes(univ.SequenceOf):\n    pass\n\n\nBuiltInDomainDefinedAttributes.componentType = BuiltInDomainDefinedAttribute()\nBuiltInDomainDefinedAttributes.sizeSpec = constraint.ValueSizeConstraint(1, ub_domain_defined_attributes)\n\nub_extension_attributes = univ.Integer(256)\n\n\nclass ExtensionAttribute(univ.Sequence):\n    pass\n\n\nExtensionAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('extension-attribute-type', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(0, ub_extension_attributes)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('extension-attribute-value',\n                        univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass ExtensionAttributes(univ.SetOf):\n    pass\n\n\nExtensionAttributes.componentType = ExtensionAttribute()\nExtensionAttributes.sizeSpec = constraint.ValueSizeConstraint(1, ub_extension_attributes)\n\n\nclass ORAddress(univ.Sequence):\n    pass\n\n\nORAddress.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('built-in-standard-attributes', BuiltInStandardAttributes()),\n    namedtype.OptionalNamedType('built-in-domain-defined-attributes', BuiltInDomainDefinedAttributes()),\n    namedtype.OptionalNamedType('extension-attributes', ExtensionAttributes())\n)\n\nid_pe = _OID(id_pkix, 1)\n\nub_title = univ.Integer(64)\n\n\nclass X520Title(univ.Choice):\n    pass\n\n\nX520Title.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title))),\n    namedtype.NamedType('printableString',\n                        char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title))),\n    namedtype.NamedType('universalString',\n                        char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title))),\n    namedtype.NamedType('bmpString', char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title)))\n)\n\nid_at_organizationalUnitName = _OID(id_at, 11)\n\n\nclass EmailAddress(char.IA5String):\n    pass\n\n\nEmailAddress.subtypeSpec = constraint.ValueSizeConstraint(1, ub_emailaddress_length)\n\nphysical_delivery_country_name = univ.Integer(8)\n\nid_at_givenName = _OID(id_at, 42)\n\n\nclass TeletexCommonName(char.TeletexString):\n    pass\n\n\nTeletexCommonName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_common_name_length)\n\nid_qt_cps = _OID(id_qt, 1)\n\n\nclass LocalPostalAttributes(PDSParameter):\n    pass\n\n\nclass StreetAddress(PDSParameter):\n    pass\n\n\nid_kp = _OID(id_pkix, 3)\n\n\nclass DirectoryString(univ.Choice):\n    pass\n\n\nDirectoryString.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.NamedType('printableString',\n                        char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.NamedType('universalString',\n                        char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.NamedType('utf8String', char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.NamedType('bmpString', char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX)))\n)\n\n\nclass DomainComponent(char.IA5String):\n    pass\n\n\nid_at_initials = _OID(id_at, 43)\n\nid_qt_unotice = _OID(id_qt, 2)\n\nub_pds_name_length = univ.Integer(16)\n\n\nclass PDSName(char.PrintableString):\n    pass\n\n\nPDSName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_pds_name_length)\n\n\nclass PosteRestanteAddress(PDSParameter):\n    pass\n\n\nclass DistinguishedName(RDNSequence):\n    pass\n\n\nclass CommonName(char.PrintableString):\n    pass\n\n\nCommonName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_common_name_length)\n\nub_serial_number = univ.Integer(64)\n\n\nclass X520SerialNumber(char.PrintableString):\n    pass\n\n\nX520SerialNumber.subtypeSpec = constraint.ValueSizeConstraint(1, ub_serial_number)\n\nid_at_generationQualifier = _OID(id_at, 44)\n\nub_organizational_unit_name = univ.Integer(64)\n\nid_ad_ocsp = _OID(id_ad, 1)\n\n\nclass TeletexOrganizationalUnitName(char.TeletexString):\n    pass\n\n\nTeletexOrganizationalUnitName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_organizational_unit_name_length)\n\n\nclass TeletexPersonalName(univ.Set):\n    pass\n\n\nTeletexPersonalName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('surname', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_surname_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('given-name', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_given_name_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('initials', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_initials_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.OptionalNamedType('generation-qualifier', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_generation_qualifier_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\n\nclass TeletexDomainDefinedAttributes(univ.SequenceOf):\n    pass\n\n\nTeletexDomainDefinedAttributes.componentType = TeletexDomainDefinedAttribute()\nTeletexDomainDefinedAttributes.sizeSpec = constraint.ValueSizeConstraint(1, ub_domain_defined_attributes)\n\n\nclass TBSCertList(univ.Sequence):\n    pass\n\n\nTBSCertList.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('version', Version()),\n    namedtype.NamedType('signature', AlgorithmIdentifier()),\n    namedtype.NamedType('issuer', Name()),\n    namedtype.NamedType('thisUpdate', Time()),\n    namedtype.OptionalNamedType('nextUpdate', Time()),\n    namedtype.OptionalNamedType('revokedCertificates',\n                                univ.SequenceOf(componentType=univ.Sequence(componentType=namedtype.NamedTypes(\n                                    namedtype.NamedType('userCertificate', CertificateSerialNumber()),\n                                    namedtype.NamedType('revocationDate', Time()),\n                                    namedtype.OptionalNamedType('crlEntryExtensions', Extensions())\n                                ))\n                                )),\n    namedtype.OptionalNamedType('crlExtensions',\n                                Extensions().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\nlocal_postal_attributes = univ.Integer(21)\n\npkcs_9 = _OID(1, 2, 840, 113549, 1, 9)\n\n\nclass PhysicalDeliveryCountryName(univ.Choice):\n    pass\n\n\nPhysicalDeliveryCountryName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('x121-dcc-code', char.NumericString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(ub_country_name_numeric_length, ub_country_name_numeric_length))),\n    namedtype.NamedType('iso-3166-alpha2-code', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(ub_country_name_alpha_length, ub_country_name_alpha_length)))\n)\n\nub_name = univ.Integer(32768)\n\n\nclass X520name(univ.Choice):\n    pass\n\n\nX520name.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name))),\n    namedtype.NamedType('printableString',\n                        char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name))),\n    namedtype.NamedType('universalString',\n                        char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name))),\n    namedtype.NamedType('bmpString', char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name)))\n)\n\nid_emailAddress = _OID(pkcs_9, 1)\n\n\nclass TerminalType(univ.Integer):\n    pass\n\n\nTerminalType.namedValues = namedval.NamedValues(\n    ('telex', 3),\n    ('teletex', 4),\n    ('g3-facsimile', 5),\n    ('g4-facsimile', 6),\n    ('ia5-terminal', 7),\n    ('videotex', 8)\n)\n\n\nclass X520OrganizationalUnitName(univ.Choice):\n    pass\n\n\nX520OrganizationalUnitName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name))),\n    namedtype.NamedType('printableString', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name))),\n    namedtype.NamedType('universalString', char.UniversalString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name))),\n    namedtype.NamedType('utf8String', char.UTF8String().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name))),\n    namedtype.NamedType('bmpString', char.BMPString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name)))\n)\n\nid_at_commonName = _OID(id_at, 3)\n\npds_name = univ.Integer(7)\n\npost_office_box_address = univ.Integer(18)\n\nub_locality_name = univ.Integer(128)\n\n\nclass X520LocalityName(univ.Choice):\n    pass\n\n\nX520LocalityName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name))),\n    namedtype.NamedType('printableString', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name))),\n    namedtype.NamedType('universalString', char.UniversalString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name))),\n    namedtype.NamedType('bmpString',\n                        char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name)))\n)\n\nid_ad_timeStamping = _OID(id_ad, 3)\n\nid_at_countryName = _OID(id_at, 6)\n\nphysical_delivery_personal_name = univ.Integer(13)\n\nteletex_personal_name = univ.Integer(4)\n\nteletex_organizational_unit_names = univ.Integer(5)\n\n\nclass PhysicalDeliveryPersonalName(PDSParameter):\n    pass\n\n\nub_postal_code_length = univ.Integer(16)\n\n\nclass PostalCode(univ.Choice):\n    pass\n\n\nPostalCode.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('numeric-code', char.NumericString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_postal_code_length))),\n    namedtype.NamedType('printable-code', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_postal_code_length)))\n)\n\n\nclass X520countryName(char.PrintableString):\n    pass\n\n\nX520countryName.subtypeSpec = constraint.ValueSizeConstraint(2, 2)\n\npostal_code = univ.Integer(9)\n\nid_ad_caRepository = _OID(id_ad, 5)\n\nextension_physical_delivery_address_components = univ.Integer(15)\n\n\nclass PostOfficeBoxAddress(PDSParameter):\n    pass\n\n\nclass PhysicalDeliveryOfficeName(PDSParameter):\n    pass\n\n\nid_at_title = _OID(id_at, 12)\n\nid_at_serialNumber = _OID(id_at, 5)\n\nid_ad_caIssuers = _OID(id_ad, 2)\n\nub_integer_options = univ.Integer(256)\n\n\nclass CertificateList(univ.Sequence):\n    pass\n\n\nCertificateList.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('tbsCertList', TBSCertList()),\n    namedtype.NamedType('signatureAlgorithm', AlgorithmIdentifier()),\n    namedtype.NamedType('signature', univ.BitString())\n)\n\n\nclass PhysicalDeliveryOfficeNumber(PDSParameter):\n    pass\n\n\nclass TeletexOrganizationalUnitNames(univ.SequenceOf):\n    pass\n\n\nTeletexOrganizationalUnitNames.componentType = TeletexOrganizationalUnitName()\nTeletexOrganizationalUnitNames.sizeSpec = constraint.ValueSizeConstraint(1, ub_organizational_units)\n\nphysical_delivery_office_name = univ.Integer(10)\n\nub_common_name = univ.Integer(64)\n\n\nclass ExtensionORAddressComponents(PDSParameter):\n    pass\n\n\nub_pseudonym = univ.Integer(128)\n\nposte_restante_address = univ.Integer(19)\n\nid_at_organizationName = _OID(id_at, 10)\n\nphysical_delivery_office_number = univ.Integer(11)\n\nid_at_pseudonym = _OID(id_at, 65)\n\n\nclass X520CommonName(univ.Choice):\n    pass\n\n\nX520CommonName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name))),\n    namedtype.NamedType('printableString',\n                        char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name))),\n    namedtype.NamedType('universalString',\n                        char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name))),\n    namedtype.NamedType('bmpString',\n                        char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name)))\n)\n\nphysical_delivery_organization_name = univ.Integer(14)\n\n\nclass X520dnQualifier(char.PrintableString):\n    pass\n\n\nid_at_stateOrProvinceName = _OID(id_at, 8)\n\ncommon_name = univ.Integer(1)\n\nid_at_localityName = _OID(id_at, 7)\n\nub_match = univ.Integer(128)\n\nub_unformatted_address_length = univ.Integer(180)\n\n\nclass Attribute(univ.Sequence):\n    pass\n\n\nAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('type', AttributeType()),\n    namedtype.NamedType('values', univ.SetOf(componentType=AttributeValue()))\n)\n\nextended_network_address = univ.Integer(22)\n\nunique_postal_name = univ.Integer(20)\n\nub_pds_physical_address_lines = univ.Integer(6)\n\n\nclass UnformattedPostalAddress(univ.Set):\n    pass\n\n\nUnformattedPostalAddress.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('printable-address', univ.SequenceOf(componentType=char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_pds_parameter_length)))),\n    namedtype.OptionalNamedType('teletex-string', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_unformatted_address_length)))\n)\n\n\nclass UniquePostalName(PDSParameter):\n    pass\n\n\nclass X520Pseudonym(univ.Choice):\n    pass\n\n\nX520Pseudonym.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_pseudonym))),\n    namedtype.NamedType('printableString',\n                        char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_pseudonym))),\n    namedtype.NamedType('universalString',\n                        char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_pseudonym))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_pseudonym))),\n    namedtype.NamedType('bmpString',\n                        char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_pseudonym)))\n)\n\nteletex_organization_name = univ.Integer(3)\n\nteletex_domain_defined_attributes = univ.Integer(6)\n\nstreet_address = univ.Integer(17)\n\nid_kp_OCSPSigning = _OID(id_kp, 9)\n\nid_ce = _OID(2, 5, 29)\n\nid_ce_certificatePolicies = _OID(id_ce, 32)\n\n\nclass EDIPartyName(univ.Sequence):\n    pass\n\n\nEDIPartyName.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('nameAssigner', DirectoryString().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('partyName',\n                        DirectoryString().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass AnotherName(univ.Sequence):\n    pass\n\n\nAnotherName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('type-id', univ.ObjectIdentifier()),\n    namedtype.NamedType('value', univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass GeneralName(univ.Choice):\n    pass\n\n\nGeneralName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('otherName',\n                        AnotherName().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('rfc822Name',\n                        char.IA5String().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('dNSName',\n                        char.IA5String().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.NamedType('x400Address',\n                        ORAddress().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n    namedtype.NamedType('directoryName',\n                        Name().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 4))),\n    namedtype.NamedType('ediPartyName',\n                        EDIPartyName().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 5))),\n    namedtype.NamedType('uniformResourceIdentifier',\n                        char.IA5String().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 6))),\n    namedtype.NamedType('iPAddress',\n                        univ.OctetString().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 7))),\n    namedtype.NamedType('registeredID', univ.ObjectIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 8)))\n)\n\n\nclass GeneralNames(univ.SequenceOf):\n    pass\n\n\nGeneralNames.componentType = GeneralName()\nGeneralNames.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass IssuerAltName(GeneralNames):\n    pass\n\n\nid_ce_cRLDistributionPoints = _OID(id_ce, 31)\n\n\nclass CertPolicyId(univ.ObjectIdentifier):\n    pass\n\n\nclass PolicyMappings(univ.SequenceOf):\n    pass\n\n\nPolicyMappings.componentType = univ.Sequence(componentType=namedtype.NamedTypes(\n    namedtype.NamedType('issuerDomainPolicy', CertPolicyId()),\n    namedtype.NamedType('subjectDomainPolicy', CertPolicyId())\n))\n\nPolicyMappings.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass PolicyQualifierId(univ.ObjectIdentifier):\n    pass\n\n\nholdInstruction = _OID(2, 2, 840, 10040, 2)\n\nid_ce_subjectDirectoryAttributes = _OID(id_ce, 9)\n\nid_holdinstruction_callissuer = _OID(holdInstruction, 2)\n\n\nclass SubjectDirectoryAttributes(univ.SequenceOf):\n    pass\n\n\nSubjectDirectoryAttributes.componentType = Attribute()\nSubjectDirectoryAttributes.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\nanyPolicy = _OID(id_ce_certificatePolicies, 0)\n\nid_ce_subjectAltName = _OID(id_ce, 17)\n\nid_kp_emailProtection = _OID(id_kp, 4)\n\n\nclass ReasonFlags(univ.BitString):\n    pass\n\n\nReasonFlags.namedValues = namedval.NamedValues(\n    ('unused', 0),\n    ('keyCompromise', 1),\n    ('cACompromise', 2),\n    ('affiliationChanged', 3),\n    ('superseded', 4),\n    ('cessationOfOperation', 5),\n    ('certificateHold', 6),\n    ('privilegeWithdrawn', 7),\n    ('aACompromise', 8)\n)\n\n\nclass DistributionPointName(univ.Choice):\n    pass\n\n\nDistributionPointName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('fullName',\n                        GeneralNames().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('nameRelativeToCRLIssuer', RelativeDistinguishedName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass DistributionPoint(univ.Sequence):\n    pass\n\n\nDistributionPoint.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('distributionPoint', DistributionPointName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.OptionalNamedType('reasons', ReasonFlags().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('cRLIssuer', GeneralNames().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\nid_ce_keyUsage = _OID(id_ce, 15)\n\n\nclass PolicyQualifierInfo(univ.Sequence):\n    pass\n\n\nPolicyQualifierInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('policyQualifierId', PolicyQualifierId()),\n    namedtype.NamedType('qualifier', univ.Any())\n)\n\n\nclass PolicyInformation(univ.Sequence):\n    pass\n\n\nPolicyInformation.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('policyIdentifier', CertPolicyId()),\n    namedtype.OptionalNamedType('policyQualifiers', univ.SequenceOf(componentType=PolicyQualifierInfo()))\n)\n\n\nclass CertificatePolicies(univ.SequenceOf):\n    pass\n\n\nCertificatePolicies.componentType = PolicyInformation()\nCertificatePolicies.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\nid_ce_basicConstraints = _OID(id_ce, 19)\n\n\nclass HoldInstructionCode(univ.ObjectIdentifier):\n    pass\n\n\nclass KeyPurposeId(univ.ObjectIdentifier):\n    pass\n\n\nclass ExtKeyUsageSyntax(univ.SequenceOf):\n    pass\n\n\nExtKeyUsageSyntax.componentType = KeyPurposeId()\nExtKeyUsageSyntax.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass SubjectAltName(GeneralNames):\n    pass\n\n\nclass BasicConstraints(univ.Sequence):\n    pass\n\n\nBasicConstraints.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('cA', univ.Boolean().subtype(value=0)),\n    namedtype.OptionalNamedType('pathLenConstraint',\n                                univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, MAX)))\n)\n\n\nclass SkipCerts(univ.Integer):\n    pass\n\n\nSkipCerts.subtypeSpec = constraint.ValueRangeConstraint(0, MAX)\n\n\nclass InhibitAnyPolicy(SkipCerts):\n    pass\n\n\nclass CRLNumber(univ.Integer):\n    pass\n\n\nCRLNumber.subtypeSpec = constraint.ValueRangeConstraint(0, MAX)\n\n\nclass BaseCRLNumber(CRLNumber):\n    pass\n\n\nclass KeyIdentifier(univ.OctetString):\n    pass\n\n\nclass AuthorityKeyIdentifier(univ.Sequence):\n    pass\n\n\nAuthorityKeyIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('keyIdentifier', KeyIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('authorityCertIssuer', GeneralNames().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('authorityCertSerialNumber', CertificateSerialNumber().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\nid_ce_nameConstraints = _OID(id_ce, 30)\n\nid_kp_serverAuth = _OID(id_kp, 1)\n\nid_ce_freshestCRL = _OID(id_ce, 46)\n\nid_ce_cRLReasons = _OID(id_ce, 21)\n\n\nclass CRLDistributionPoints(univ.SequenceOf):\n    pass\n\n\nCRLDistributionPoints.componentType = DistributionPoint()\nCRLDistributionPoints.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass FreshestCRL(CRLDistributionPoints):\n    pass\n\n\nid_ce_inhibitAnyPolicy = _OID(id_ce, 54)\n\n\nclass CRLReason(univ.Enumerated):\n    pass\n\n\nCRLReason.namedValues = namedval.NamedValues(\n    ('unspecified', 0),\n    ('keyCompromise', 1),\n    ('cACompromise', 2),\n    ('affiliationChanged', 3),\n    ('superseded', 4),\n    ('cessationOfOperation', 5),\n    ('certificateHold', 6),\n    ('removeFromCRL', 8),\n    ('privilegeWithdrawn', 9),\n    ('aACompromise', 10)\n)\n\n\nclass BaseDistance(univ.Integer):\n    pass\n\n\nBaseDistance.subtypeSpec = constraint.ValueRangeConstraint(0, MAX)\n\n\nclass GeneralSubtree(univ.Sequence):\n    pass\n\n\nGeneralSubtree.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('base', GeneralName()),\n    namedtype.DefaultedNamedType('minimum', BaseDistance().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)).subtype(value=0)),\n    namedtype.OptionalNamedType('maximum', BaseDistance().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass GeneralSubtrees(univ.SequenceOf):\n    pass\n\n\nGeneralSubtrees.componentType = GeneralSubtree()\nGeneralSubtrees.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass NameConstraints(univ.Sequence):\n    pass\n\n\nNameConstraints.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('permittedSubtrees', GeneralSubtrees().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('excludedSubtrees', GeneralSubtrees().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\nid_pe_authorityInfoAccess = _OID(id_pe, 1)\n\nid_pe_subjectInfoAccess = _OID(id_pe, 11)\n\nid_ce_certificateIssuer = _OID(id_ce, 29)\n\nid_ce_invalidityDate = _OID(id_ce, 24)\n\n\nclass DirectoryString(univ.Choice):\n    pass\n\n\nDirectoryString.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('any', univ.Any())\n)\n\nid_ce_authorityKeyIdentifier = _OID(id_ce, 35)\n\n\nclass AccessDescription(univ.Sequence):\n    pass\n\n\nAccessDescription.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('accessMethod', univ.ObjectIdentifier()),\n    namedtype.NamedType('accessLocation', GeneralName())\n)\n\n\nclass AuthorityInfoAccessSyntax(univ.SequenceOf):\n    pass\n\n\nAuthorityInfoAccessSyntax.componentType = AccessDescription()\nAuthorityInfoAccessSyntax.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\nid_ce_issuingDistributionPoint = _OID(id_ce, 28)\n\n\nclass CPSuri(char.IA5String):\n    pass\n\n\nclass DisplayText(univ.Choice):\n    pass\n\n\nDisplayText.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('ia5String', char.IA5String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, 200))),\n    namedtype.NamedType('visibleString',\n                        char.VisibleString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, 200))),\n    namedtype.NamedType('bmpString', char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, 200))),\n    namedtype.NamedType('utf8String', char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, 200)))\n)\n\n\nclass NoticeReference(univ.Sequence):\n    pass\n\n\nNoticeReference.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('organization', DisplayText()),\n    namedtype.NamedType('noticeNumbers', univ.SequenceOf(componentType=univ.Integer()))\n)\n\n\nclass UserNotice(univ.Sequence):\n    pass\n\n\nUserNotice.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('noticeRef', NoticeReference()),\n    namedtype.OptionalNamedType('explicitText', DisplayText())\n)\n\n\nclass PrivateKeyUsagePeriod(univ.Sequence):\n    pass\n\n\nPrivateKeyUsagePeriod.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('notBefore', useful.GeneralizedTime().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('notAfter', useful.GeneralizedTime().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\nid_ce_subjectKeyIdentifier = _OID(id_ce, 14)\n\n\nclass CertificateIssuer(GeneralNames):\n    pass\n\n\nclass InvalidityDate(useful.GeneralizedTime):\n    pass\n\n\nclass SubjectInfoAccessSyntax(univ.SequenceOf):\n    pass\n\n\nSubjectInfoAccessSyntax.componentType = AccessDescription()\nSubjectInfoAccessSyntax.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass KeyUsage(univ.BitString):\n    pass\n\n\nKeyUsage.namedValues = namedval.NamedValues(\n    ('digitalSignature', 0),\n    ('nonRepudiation', 1),\n    ('keyEncipherment', 2),\n    ('dataEncipherment', 3),\n    ('keyAgreement', 4),\n    ('keyCertSign', 5),\n    ('cRLSign', 6),\n    ('encipherOnly', 7),\n    ('decipherOnly', 8)\n)\n\nid_ce_extKeyUsage = _OID(id_ce, 37)\n\nanyExtendedKeyUsage = _OID(id_ce_extKeyUsage, 0)\n\nid_ce_privateKeyUsagePeriod = _OID(id_ce, 16)\n\nid_ce_policyMappings = _OID(id_ce, 33)\n\nid_ce_cRLNumber = _OID(id_ce, 20)\n\nid_ce_policyConstraints = _OID(id_ce, 36)\n\nid_holdinstruction_none = _OID(holdInstruction, 1)\n\nid_holdinstruction_reject = _OID(holdInstruction, 3)\n\nid_kp_timeStamping = _OID(id_kp, 8)\n\n\nclass PolicyConstraints(univ.Sequence):\n    pass\n\n\nPolicyConstraints.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('requireExplicitPolicy',\n                                SkipCerts().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('inhibitPolicyMapping',\n                                SkipCerts().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass SubjectKeyIdentifier(KeyIdentifier):\n    pass\n\n\nid_kp_clientAuth = _OID(id_kp, 2)\n\nid_ce_deltaCRLIndicator = _OID(id_ce, 27)\n\nid_ce_issuerAltName = _OID(id_ce, 18)\n\nid_kp_codeSigning = _OID(id_kp, 3)\n\nid_ce_holdInstructionCode = _OID(id_ce, 23)\n\n\nclass IssuingDistributionPoint(univ.Sequence):\n    pass\n\n\nIssuingDistributionPoint.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('distributionPoint', DistributionPointName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.DefaultedNamedType('onlyContainsUserCerts', univ.Boolean().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)).subtype(value=0)),\n    namedtype.DefaultedNamedType('onlyContainsCACerts', univ.Boolean().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)).subtype(value=0)),\n    namedtype.OptionalNamedType('onlySomeReasons', ReasonFlags().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n    namedtype.DefaultedNamedType('indirectCRL', univ.Boolean().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4)).subtype(value=0)),\n    namedtype.DefaultedNamedType('onlyContainsAttributeCerts', univ.Boolean().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 5)).subtype(value=0))\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3281.py",
    "content": "# coding: utf-8\n#\n# This file is part of pyasn1-modules software.\n#\n# Created by Stanisław Pitucha with asn1ate tool.\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# An Internet Attribute Certificate Profile for Authorization\n#\n# ASN.1 source from:\n# http://www.ietf.org/rfc/rfc3281.txt\n#\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nfrom pyasn1_modules import rfc3280\n\nMAX = float('inf')\n\n\ndef _buildOid(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\nclass ObjectDigestInfo(univ.Sequence):\n    pass\n\n\nObjectDigestInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('digestedObjectType', univ.Enumerated(\n        namedValues=namedval.NamedValues(('publicKey', 0), ('publicKeyCert', 1), ('otherObjectTypes', 2)))),\n    namedtype.OptionalNamedType('otherObjectTypeID', univ.ObjectIdentifier()),\n    namedtype.NamedType('digestAlgorithm', rfc3280.AlgorithmIdentifier()),\n    namedtype.NamedType('objectDigest', univ.BitString())\n)\n\n\nclass IssuerSerial(univ.Sequence):\n    pass\n\n\nIssuerSerial.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuer', rfc3280.GeneralNames()),\n    namedtype.NamedType('serial', rfc3280.CertificateSerialNumber()),\n    namedtype.OptionalNamedType('issuerUID', rfc3280.UniqueIdentifier())\n)\n\n\nclass TargetCert(univ.Sequence):\n    pass\n\n\nTargetCert.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('targetCertificate', IssuerSerial()),\n    namedtype.OptionalNamedType('targetName', rfc3280.GeneralName()),\n    namedtype.OptionalNamedType('certDigestInfo', ObjectDigestInfo())\n)\n\n\nclass Target(univ.Choice):\n    pass\n\n\nTarget.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('targetName', rfc3280.GeneralName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('targetGroup', rfc3280.GeneralName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('targetCert',\n                        TargetCert().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2)))\n)\n\n\nclass Targets(univ.SequenceOf):\n    pass\n\n\nTargets.componentType = Target()\n\n\nclass ProxyInfo(univ.SequenceOf):\n    pass\n\n\nProxyInfo.componentType = Targets()\n\nid_at_role = _buildOid(rfc3280.id_at, 72)\n\nid_pe_aaControls = _buildOid(rfc3280.id_pe, 6)\n\nid_ce_targetInformation = _buildOid(rfc3280.id_ce, 55)\n\nid_pe_ac_auditIdentity = _buildOid(rfc3280.id_pe, 4)\n\n\nclass ClassList(univ.BitString):\n    pass\n\n\nClassList.namedValues = namedval.NamedValues(\n    ('unmarked', 0),\n    ('unclassified', 1),\n    ('restricted', 2),\n    ('confidential', 3),\n    ('secret', 4),\n    ('topSecret', 5)\n)\n\n\nclass SecurityCategory(univ.Sequence):\n    pass\n\n\nSecurityCategory.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('type', univ.ObjectIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('value', univ.Any().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass Clearance(univ.Sequence):\n    pass\n\n\nClearance.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('policyId', univ.ObjectIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.DefaultedNamedType('classList',\n                                 ClassList().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n                                                                         tag.tagFormatSimple, 1)).subtype(\n                                     value=\"unclassified\")),\n    namedtype.OptionalNamedType('securityCategories', univ.SetOf(componentType=SecurityCategory()).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\n\nclass AttCertVersion(univ.Integer):\n    pass\n\n\nAttCertVersion.namedValues = namedval.NamedValues(\n    ('v2', 1)\n)\n\nid_aca = _buildOid(rfc3280.id_pkix, 10)\n\nid_at_clearance = _buildOid(2, 5, 1, 5, 55)\n\n\nclass AttrSpec(univ.SequenceOf):\n    pass\n\n\nAttrSpec.componentType = univ.ObjectIdentifier()\n\n\nclass AAControls(univ.Sequence):\n    pass\n\n\nAAControls.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('pathLenConstraint',\n                                univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, MAX))),\n    namedtype.OptionalNamedType('permittedAttrs',\n                                AttrSpec().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('excludedAttrs',\n                                AttrSpec().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.DefaultedNamedType('permitUnSpecified', univ.Boolean().subtype(value=1))\n)\n\n\nclass AttCertValidityPeriod(univ.Sequence):\n    pass\n\n\nAttCertValidityPeriod.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('notBeforeTime', useful.GeneralizedTime()),\n    namedtype.NamedType('notAfterTime', useful.GeneralizedTime())\n)\n\n\nid_aca_authenticationInfo = _buildOid(id_aca, 1)\n\n\nclass V2Form(univ.Sequence):\n    pass\n\n\nV2Form.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('issuerName', rfc3280.GeneralNames()),\n    namedtype.OptionalNamedType('baseCertificateID', IssuerSerial().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.OptionalNamedType('objectDigestInfo', ObjectDigestInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n)\n\n\nclass AttCertIssuer(univ.Choice):\n    pass\n\n\nAttCertIssuer.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('v1Form', rfc3280.GeneralNames()),\n    namedtype.NamedType('v2Form',\n                        V2Form().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n)\n\n\nclass Holder(univ.Sequence):\n    pass\n\n\nHolder.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('baseCertificateID', IssuerSerial().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.OptionalNamedType('entityName', rfc3280.GeneralNames().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('objectDigestInfo', ObjectDigestInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2)))\n)\n\n\nclass AttributeCertificateInfo(univ.Sequence):\n    pass\n\n\nAttributeCertificateInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', AttCertVersion()),\n    namedtype.NamedType('holder', Holder()),\n    namedtype.NamedType('issuer', AttCertIssuer()),\n    namedtype.NamedType('signature', rfc3280.AlgorithmIdentifier()),\n    namedtype.NamedType('serialNumber', rfc3280.CertificateSerialNumber()),\n    namedtype.NamedType('attrCertValidityPeriod', AttCertValidityPeriod()),\n    namedtype.NamedType('attributes', univ.SequenceOf(componentType=rfc3280.Attribute())),\n    namedtype.OptionalNamedType('issuerUniqueID', rfc3280.UniqueIdentifier()),\n    namedtype.OptionalNamedType('extensions', rfc3280.Extensions())\n)\n\n\nclass AttributeCertificate(univ.Sequence):\n    pass\n\n\nAttributeCertificate.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('acinfo', AttributeCertificateInfo()),\n    namedtype.NamedType('signatureAlgorithm', rfc3280.AlgorithmIdentifier()),\n    namedtype.NamedType('signatureValue', univ.BitString())\n)\n\nid_mod = _buildOid(rfc3280.id_pkix, 0)\n\nid_mod_attribute_cert = _buildOid(id_mod, 12)\n\nid_aca_accessIdentity = _buildOid(id_aca, 2)\n\n\nclass RoleSyntax(univ.Sequence):\n    pass\n\n\nRoleSyntax.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('roleAuthority', rfc3280.GeneralNames().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('roleName',\n                        rfc3280.GeneralName().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\nid_aca_chargingIdentity = _buildOid(id_aca, 3)\n\n\nclass ACClearAttrs(univ.Sequence):\n    pass\n\n\nACClearAttrs.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('acIssuer', rfc3280.GeneralName()),\n    namedtype.NamedType('acSerial', univ.Integer()),\n    namedtype.NamedType('attrs', univ.SequenceOf(componentType=rfc3280.Attribute()))\n)\n\nid_aca_group = _buildOid(id_aca, 4)\n\nid_pe_ac_proxying = _buildOid(rfc3280.id_pe, 10)\n\n\nclass SvceAuthInfo(univ.Sequence):\n    pass\n\n\nSvceAuthInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('service', rfc3280.GeneralName()),\n    namedtype.NamedType('ident', rfc3280.GeneralName()),\n    namedtype.OptionalNamedType('authInfo', univ.OctetString())\n)\n\n\nclass IetfAttrSyntax(univ.Sequence):\n    pass\n\n\nIetfAttrSyntax.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType(\n        'policyAuthority', rfc3280.GeneralNames().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))\n    ),\n    namedtype.NamedType(\n        'values', univ.SequenceOf(\n            componentType=univ.Choice(\n                componentType=namedtype.NamedTypes(\n                    namedtype.NamedType('octets', univ.OctetString()),\n                    namedtype.NamedType('oid', univ.ObjectIdentifier()),\n                    namedtype.NamedType('string', char.UTF8String())\n                )\n            )\n        )\n    )\n)\n\nid_aca_encAttrs = _buildOid(id_aca, 6)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3412.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# SNMPv3 message syntax\n#\n# ASN.1 source from:\n# http://www.ietf.org/rfc/rfc3412.txt\n#\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc1905\n\n\nclass ScopedPDU(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('contextEngineId', univ.OctetString()),\n        namedtype.NamedType('contextName', univ.OctetString()),\n        namedtype.NamedType('data', rfc1905.PDUs())\n    )\n\n\nclass ScopedPduData(univ.Choice):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('plaintext', ScopedPDU()),\n        namedtype.NamedType('encryptedPDU', univ.OctetString()),\n    )\n\n\nclass HeaderData(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('msgID',\n                            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, 2147483647))),\n        namedtype.NamedType('msgMaxSize',\n                            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(484, 2147483647))),\n        namedtype.NamedType('msgFlags', univ.OctetString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, 1))),\n        namedtype.NamedType('msgSecurityModel',\n                            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(1, 2147483647)))\n    )\n\n\nclass SNMPv3Message(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('msgVersion',\n                            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, 2147483647))),\n        namedtype.NamedType('msgGlobalData', HeaderData()),\n        namedtype.NamedType('msgSecurityParameters', univ.OctetString()),\n        namedtype.NamedType('msgData', ScopedPduData())\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3414.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# SNMPv3 message syntax\n#\n# ASN.1 source from:\n# http://www.ietf.org/rfc/rfc3414.txt\n#\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\n\nclass UsmSecurityParameters(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('msgAuthoritativeEngineID', univ.OctetString()),\n        namedtype.NamedType('msgAuthoritativeEngineBoots',\n                            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, 2147483647))),\n        namedtype.NamedType('msgAuthoritativeEngineTime',\n                            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, 2147483647))),\n        namedtype.NamedType('msgUserName',\n                            univ.OctetString().subtype(subtypeSpec=constraint.ValueSizeConstraint(0, 32))),\n        namedtype.NamedType('msgAuthenticationParameters', univ.OctetString()),\n        namedtype.NamedType('msgPrivacyParameters', univ.OctetString())\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3447.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# PKCS#1 syntax\n#\n# ASN.1 source from:\n# ftp://ftp.rsasecurity.com/pub/pkcs/pkcs-1/pkcs-1v2-1.asn\n#\n# Sample captures could be obtained with \"openssl genrsa\" command\n#\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedval\n\nfrom pyasn1_modules.rfc2437 import *\n\n\nclass OtherPrimeInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('prime', univ.Integer()),\n        namedtype.NamedType('exponent', univ.Integer()),\n        namedtype.NamedType('coefficient', univ.Integer())\n    )\n\n\nclass OtherPrimeInfos(univ.SequenceOf):\n    componentType = OtherPrimeInfo()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\nclass RSAPrivateKey(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', univ.Integer(namedValues=namedval.NamedValues(('two-prime', 0), ('multi', 1)))),\n        namedtype.NamedType('modulus', univ.Integer()),\n        namedtype.NamedType('publicExponent', univ.Integer()),\n        namedtype.NamedType('privateExponent', univ.Integer()),\n        namedtype.NamedType('prime1', univ.Integer()),\n        namedtype.NamedType('prime2', univ.Integer()),\n        namedtype.NamedType('exponent1', univ.Integer()),\n        namedtype.NamedType('exponent2', univ.Integer()),\n        namedtype.NamedType('coefficient', univ.Integer()),\n        namedtype.OptionalNamedType('otherPrimeInfos', OtherPrimeInfos())\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3560.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# RSAES-OAEP Key Transport Algorithm in CMS\n#\n# Notice that all of the things needed in RFC 3560 are also defined\n# in RFC 4055.  So, they are all pulled from the RFC 4055 module into\n# this one so that people looking a RFC 3560 can easily find them.\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc3560.txt\n#\n\nfrom pyasn1_modules import rfc4055\n\nid_sha1 = rfc4055.id_sha1\n\nid_sha256 = rfc4055.id_sha256\n\nid_sha384 = rfc4055.id_sha384\n\nid_sha512 = rfc4055.id_sha512\n\nid_mgf1 = rfc4055.id_mgf1\n\nrsaEncryption = rfc4055.rsaEncryption\n\nid_RSAES_OAEP = rfc4055.id_RSAES_OAEP\n\nid_pSpecified = rfc4055.id_pSpecified\n\nsha1Identifier = rfc4055.sha1Identifier\n\nsha256Identifier = rfc4055.sha256Identifier\n\nsha384Identifier = rfc4055.sha384Identifier\n\nsha512Identifier = rfc4055.sha512Identifier\n\nmgf1SHA1Identifier = rfc4055.mgf1SHA1Identifier\n\nmgf1SHA256Identifier = rfc4055.mgf1SHA256Identifier\n\nmgf1SHA384Identifier = rfc4055.mgf1SHA384Identifier\n\nmgf1SHA512Identifier = rfc4055.mgf1SHA512Identifier\n\npSpecifiedEmptyIdentifier = rfc4055.pSpecifiedEmptyIdentifier\n\n\nclass RSAES_OAEP_params(rfc4055.RSAES_OAEP_params):\n    pass\n\n\nrSAES_OAEP_Default_Params = RSAES_OAEP_params()\n\nrSAES_OAEP_Default_Identifier = rfc4055.rSAES_OAEP_Default_Identifier\n\nrSAES_OAEP_SHA256_Params = rfc4055.rSAES_OAEP_SHA256_Params\n\nrSAES_OAEP_SHA256_Identifier = rfc4055.rSAES_OAEP_SHA256_Identifier\n\nrSAES_OAEP_SHA384_Params = rfc4055.rSAES_OAEP_SHA384_Params\n\nrSAES_OAEP_SHA384_Identifier = rfc4055.rSAES_OAEP_SHA384_Identifier\n\nrSAES_OAEP_SHA512_Params = rfc4055.rSAES_OAEP_SHA512_Params\n\nrSAES_OAEP_SHA512_Identifier = rfc4055.rSAES_OAEP_SHA512_Identifier\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3565.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley.\n# Modified by Russ Housley to add maps for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Use of the Advanced Encryption Standard (AES) Encryption\n#   Algorithm in the Cryptographic Message Syntax (CMS)\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc3565.txt\n\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\n\nclass AlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass AES_IV(univ.OctetString):\n    pass\n\nAES_IV.subtypeSpec = constraint.ValueSizeConstraint(16, 16)\n\n\nid_aes128_CBC = univ.ObjectIdentifier('2.16.840.1.101.3.4.1.2')\n\nid_aes192_CBC = univ.ObjectIdentifier('2.16.840.1.101.3.4.1.22')\n\nid_aes256_CBC = univ.ObjectIdentifier('2.16.840.1.101.3.4.1.42')\n\n\nid_aes128_wrap = univ.ObjectIdentifier('2.16.840.1.101.3.4.1.5')\n\nid_aes192_wrap = univ.ObjectIdentifier('2.16.840.1.101.3.4.1.25')\n\nid_aes256_wrap = univ.ObjectIdentifier('2.16.840.1.101.3.4.1.45')\n\n\n# Update the Algorithm Identifier map\n\n_algorithmIdentifierMapUpdate = {\n    id_aes128_CBC: AES_IV(),\n    id_aes192_CBC: AES_IV(),\n    id_aes256_CBC: AES_IV(),\n    id_aes128_wrap: univ.Null(),\n    id_aes192_wrap: univ.Null(),\n    id_aes256_wrap: univ.Null(),\n}\n\nrfc5280.algorithmIdentifierMap.update(_algorithmIdentifierMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3709.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n# Modified by Russ Housley to add maps for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Logotypes in X.509 Certificates\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc3709.txt\n#\n\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\nMAX = float('inf')\n\n\nclass HashAlgAndValue(univ.Sequence):\n    pass\n\nHashAlgAndValue.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('hashAlg', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('hashValue', univ.OctetString())\n)\n\n\nclass LogotypeDetails(univ.Sequence):\n    pass\n\nLogotypeDetails.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('mediaType', char.IA5String()),\n    namedtype.NamedType('logotypeHash', univ.SequenceOf(\n        componentType=HashAlgAndValue()).subtype(\n            sizeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.NamedType('logotypeURI', univ.SequenceOf(\n        componentType=char.IA5String()).subtype(\n            sizeSpec=constraint.ValueSizeConstraint(1, MAX)))\n)\n\n\nclass LogotypeAudioInfo(univ.Sequence):\n    pass\n\nLogotypeAudioInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('fileSize', univ.Integer()),\n    namedtype.NamedType('playTime', univ.Integer()),\n    namedtype.NamedType('channels', univ.Integer()),\n    namedtype.OptionalNamedType('sampleRate', univ.Integer().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n    namedtype.OptionalNamedType('language', char.IA5String().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4)))\n)\n\n\nclass LogotypeAudio(univ.Sequence):\n    pass\n\nLogotypeAudio.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('audioDetails', LogotypeDetails()),\n    namedtype.OptionalNamedType('audioInfo', LogotypeAudioInfo())\n)\n\n\nclass LogotypeImageType(univ.Integer):\n    pass\n\nLogotypeImageType.namedValues = namedval.NamedValues(\n    ('grayScale', 0),\n    ('color', 1)\n)\n\n\nclass LogotypeImageResolution(univ.Choice):\n    pass\n\nLogotypeImageResolution.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('numBits',\n        univ.Integer().subtype(implicitTag=tag.Tag(\n            tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('tableSize',\n        univ.Integer().subtype(implicitTag=tag.Tag(\n            tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\n\nclass LogotypeImageInfo(univ.Sequence):\n    pass\n\nLogotypeImageInfo.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('type', LogotypeImageType().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext,\n            tag.tagFormatSimple, 0)).subtype(value='color')),\n    namedtype.NamedType('fileSize', univ.Integer()),\n    namedtype.NamedType('xSize', univ.Integer()),\n    namedtype.NamedType('ySize', univ.Integer()),\n    namedtype.OptionalNamedType('resolution', LogotypeImageResolution()),\n    namedtype.OptionalNamedType('language', char.IA5String().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4)))\n)\n\n\nclass LogotypeImage(univ.Sequence):\n    pass\n\nLogotypeImage.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('imageDetails', LogotypeDetails()),\n    namedtype.OptionalNamedType('imageInfo', LogotypeImageInfo())\n)\n\n\nclass LogotypeData(univ.Sequence):\n    pass\n\nLogotypeData.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('image', univ.SequenceOf(\n        componentType=LogotypeImage())),\n    namedtype.OptionalNamedType('audio', univ.SequenceOf(\n        componentType=LogotypeAudio()).subtype(\n            implicitTag=tag.Tag(tag.tagClassContext,\n            tag.tagFormatSimple, 1)))\n)\n\n\nclass LogotypeReference(univ.Sequence):\n    pass\n\nLogotypeReference.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('refStructHash', univ.SequenceOf(\n        componentType=HashAlgAndValue()).subtype(\n            sizeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.NamedType('refStructURI', univ.SequenceOf(\n        componentType=char.IA5String()).subtype(\n            sizeSpec=constraint.ValueSizeConstraint(1, MAX)))\n)\n\n\nclass LogotypeInfo(univ.Choice):\n    pass\n\nLogotypeInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('direct',\n        LogotypeData().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n            tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('indirect', LogotypeReference().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext,\n             tag.tagFormatConstructed, 1)))\n)\n\n# Other logotype type and associated object identifiers\n\nid_logo_background = univ.ObjectIdentifier('1.3.6.1.5.5.7.20.2')\n\nid_logo_loyalty = univ.ObjectIdentifier('1.3.6.1.5.5.7.20.1')\n\n\nclass OtherLogotypeInfo(univ.Sequence):\n    pass\n\nOtherLogotypeInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('logotypeType', univ.ObjectIdentifier()),\n    namedtype.NamedType('info', LogotypeInfo())\n)\n\n\n# Logotype Certificate Extension\n\nid_pe_logotype = univ.ObjectIdentifier('1.3.6.1.5.5.7.1.12')\n\n\nclass LogotypeExtn(univ.Sequence):\n    pass\n\nLogotypeExtn.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('communityLogos', univ.SequenceOf(\n        componentType=LogotypeInfo()).subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('issuerLogo', LogotypeInfo().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n    namedtype.OptionalNamedType('subjectLogo', LogotypeInfo().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2))),\n    namedtype.OptionalNamedType('otherLogos', univ.SequenceOf(\n        componentType=OtherLogotypeInfo()).subtype(explicitTag=tag.Tag(\n            tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\n\n# Map of Certificate Extension OIDs to Extensions added to the\n# ones that are in rfc5280.py\n\n_certificateExtensionsMapUpdate = {\n    id_pe_logotype: LogotypeExtn(),\n}\n\nrfc5280.certificateExtensionsMap.update(_certificateExtensionsMapUpdate)"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3770.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Certificate Extensions and Attributes Supporting Authentication\n#   in PPP and Wireless LAN Networks\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc3770.txt\n#\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\n\nMAX = float('inf')\n\n\n# Extended Key Usage Values\n\nid_kp_eapOverLAN = univ.ObjectIdentifier('1.3.6.1.5.5.7.3.14')\n\nid_kp_eapOverPPP = univ.ObjectIdentifier('1.3.6.1.5.5.7.3.13')\n\n\n# Wireless LAN SSID Extension\n\nid_pe_wlanSSID = univ.ObjectIdentifier('1.3.6.1.5.5.7.1.13')\n\n\nclass SSID(univ.OctetString):\n    pass\n\nSSID.subtypeSpec = constraint.ValueSizeConstraint(1, 32)\n\n\nclass SSIDList(univ.SequenceOf):\n    pass\n\nSSIDList.componentType = SSID()\nSSIDList.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\n# Wireless LAN SSID Attribute Certificate Attribute\n# Uses same syntax as the certificate extension: SSIDList\n\nid_aca_wlanSSID = univ.ObjectIdentifier('1.3.6.1.5.5.7.10.6')\n\n\n# Map of Certificate Extension OIDs to Extensions\n# To be added to the ones that are in rfc5280.py\n\n_certificateExtensionsMap = {\n    id_pe_wlanSSID: SSIDList(),\n}\n\nrfc5280.certificateExtensionsMap.update(_certificateExtensionsMap)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3779.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n# Modified by Russ Housley to add maps for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# X.509 Extensions for IP Addresses and AS Identifiers\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc3779.txt\n#\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\n\n# IP Address Delegation Extension\n\nid_pe_ipAddrBlocks = univ.ObjectIdentifier('1.3.6.1.5.5.7.1.7')\n\n\nclass IPAddress(univ.BitString):\n    pass\n\n\nclass IPAddressRange(univ.Sequence):\n    pass\n\nIPAddressRange.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('min', IPAddress()),\n    namedtype.NamedType('max', IPAddress())\n)\n\n\nclass IPAddressOrRange(univ.Choice):\n    pass\n\nIPAddressOrRange.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('addressPrefix', IPAddress()),\n    namedtype.NamedType('addressRange', IPAddressRange())\n)\n\n\nclass IPAddressChoice(univ.Choice):\n    pass\n\nIPAddressChoice.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('inherit', univ.Null()),\n    namedtype.NamedType('addressesOrRanges', univ.SequenceOf(\n        componentType=IPAddressOrRange())\n    )\n)\n\n\nclass IPAddressFamily(univ.Sequence):\n    pass\n\nIPAddressFamily.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('addressFamily', univ.OctetString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(2, 3))),\n    namedtype.NamedType('ipAddressChoice', IPAddressChoice())\n)\n\n\nclass IPAddrBlocks(univ.SequenceOf):\n    pass\n\nIPAddrBlocks.componentType = IPAddressFamily()\n\n\n# Autonomous System Identifier Delegation Extension\n\nid_pe_autonomousSysIds = univ.ObjectIdentifier('1.3.6.1.5.5.7.1.8')\n\n\nclass ASId(univ.Integer):\n    pass\n\n\nclass ASRange(univ.Sequence):\n    pass\n\nASRange.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('min', ASId()),\n    namedtype.NamedType('max', ASId())\n)\n\n\nclass ASIdOrRange(univ.Choice):\n    pass\n\nASIdOrRange.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('id', ASId()),\n    namedtype.NamedType('range', ASRange())\n)\n\n\nclass ASIdentifierChoice(univ.Choice):\n    pass\n\nASIdentifierChoice.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('inherit', univ.Null()),\n    namedtype.NamedType('asIdsOrRanges', univ.SequenceOf(\n        componentType=ASIdOrRange())\n    )\n)\n\n\nclass ASIdentifiers(univ.Sequence):\n    pass\n\nASIdentifiers.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('asnum', ASIdentifierChoice().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatConstructed, 0))),\n    namedtype.OptionalNamedType('rdi', ASIdentifierChoice().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatConstructed, 1)))\n)\n\n\n# Map of Certificate Extension OIDs to Extensions is added to the\n# ones that are in rfc5280.py\n\n_certificateExtensionsMapUpdate = {\n    id_pe_ipAddrBlocks: IPAddrBlocks(),\n    id_pe_autonomousSysIds: ASIdentifiers(),\n}\n\nrfc5280.certificateExtensionsMap.update(_certificateExtensionsMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc3852.py",
    "content": "# coding: utf-8\n#\n# This file is part of pyasn1-modules software.\n#\n# Created by Stanisław Pitucha with asn1ate tool.\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Cryptographic Message Syntax (CMS)\n#\n# ASN.1 source from:\n# http://www.ietf.org/rfc/rfc3852.txt\n#\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nfrom pyasn1_modules import rfc3280\nfrom pyasn1_modules import rfc3281\n\nMAX = float('inf')\n\n\ndef _buildOid(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\nclass AttributeValue(univ.Any):\n    pass\n\n\nclass Attribute(univ.Sequence):\n    pass\n\n\nAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('attrType', univ.ObjectIdentifier()),\n    namedtype.NamedType('attrValues', univ.SetOf(componentType=AttributeValue()))\n)\n\n\nclass SignedAttributes(univ.SetOf):\n    pass\n\n\nSignedAttributes.componentType = Attribute()\nSignedAttributes.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass OtherRevocationInfoFormat(univ.Sequence):\n    pass\n\n\nOtherRevocationInfoFormat.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('otherRevInfoFormat', univ.ObjectIdentifier()),\n    namedtype.NamedType('otherRevInfo', univ.Any())\n)\n\n\nclass RevocationInfoChoice(univ.Choice):\n    pass\n\n\nRevocationInfoChoice.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('crl', rfc3280.CertificateList()),\n    namedtype.NamedType('other', OtherRevocationInfoFormat().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n)\n\n\nclass RevocationInfoChoices(univ.SetOf):\n    pass\n\n\nRevocationInfoChoices.componentType = RevocationInfoChoice()\n\n\nclass OtherKeyAttribute(univ.Sequence):\n    pass\n\n\nOtherKeyAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('keyAttrId', univ.ObjectIdentifier()),\n    namedtype.OptionalNamedType('keyAttr', univ.Any())\n)\n\nid_signedData = _buildOid(1, 2, 840, 113549, 1, 7, 2)\n\n\nclass KeyEncryptionAlgorithmIdentifier(rfc3280.AlgorithmIdentifier):\n    pass\n\n\nclass EncryptedKey(univ.OctetString):\n    pass\n\n\nclass CMSVersion(univ.Integer):\n    pass\n\n\nCMSVersion.namedValues = namedval.NamedValues(\n    ('v0', 0),\n    ('v1', 1),\n    ('v2', 2),\n    ('v3', 3),\n    ('v4', 4),\n    ('v5', 5)\n)\n\n\nclass KEKIdentifier(univ.Sequence):\n    pass\n\n\nKEKIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('keyIdentifier', univ.OctetString()),\n    namedtype.OptionalNamedType('date', useful.GeneralizedTime()),\n    namedtype.OptionalNamedType('other', OtherKeyAttribute())\n)\n\n\nclass KEKRecipientInfo(univ.Sequence):\n    pass\n\n\nKEKRecipientInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('kekid', KEKIdentifier()),\n    namedtype.NamedType('keyEncryptionAlgorithm', KeyEncryptionAlgorithmIdentifier()),\n    namedtype.NamedType('encryptedKey', EncryptedKey())\n)\n\n\nclass KeyDerivationAlgorithmIdentifier(rfc3280.AlgorithmIdentifier):\n    pass\n\n\nclass PasswordRecipientInfo(univ.Sequence):\n    pass\n\n\nPasswordRecipientInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.OptionalNamedType('keyDerivationAlgorithm', KeyDerivationAlgorithmIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('keyEncryptionAlgorithm', KeyEncryptionAlgorithmIdentifier()),\n    namedtype.NamedType('encryptedKey', EncryptedKey())\n)\n\n\nclass OtherRecipientInfo(univ.Sequence):\n    pass\n\n\nOtherRecipientInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('oriType', univ.ObjectIdentifier()),\n    namedtype.NamedType('oriValue', univ.Any())\n)\n\n\nclass IssuerAndSerialNumber(univ.Sequence):\n    pass\n\n\nIssuerAndSerialNumber.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuer', rfc3280.Name()),\n    namedtype.NamedType('serialNumber', rfc3280.CertificateSerialNumber())\n)\n\n\nclass SubjectKeyIdentifier(univ.OctetString):\n    pass\n\n\nclass RecipientKeyIdentifier(univ.Sequence):\n    pass\n\n\nRecipientKeyIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('subjectKeyIdentifier', SubjectKeyIdentifier()),\n    namedtype.OptionalNamedType('date', useful.GeneralizedTime()),\n    namedtype.OptionalNamedType('other', OtherKeyAttribute())\n)\n\n\nclass KeyAgreeRecipientIdentifier(univ.Choice):\n    pass\n\n\nKeyAgreeRecipientIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerAndSerialNumber', IssuerAndSerialNumber()),\n    namedtype.NamedType('rKeyId', RecipientKeyIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n)\n\n\nclass RecipientEncryptedKey(univ.Sequence):\n    pass\n\n\nRecipientEncryptedKey.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('rid', KeyAgreeRecipientIdentifier()),\n    namedtype.NamedType('encryptedKey', EncryptedKey())\n)\n\n\nclass RecipientEncryptedKeys(univ.SequenceOf):\n    pass\n\n\nRecipientEncryptedKeys.componentType = RecipientEncryptedKey()\n\n\nclass UserKeyingMaterial(univ.OctetString):\n    pass\n\n\nclass OriginatorPublicKey(univ.Sequence):\n    pass\n\n\nOriginatorPublicKey.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('algorithm', rfc3280.AlgorithmIdentifier()),\n    namedtype.NamedType('publicKey', univ.BitString())\n)\n\n\nclass OriginatorIdentifierOrKey(univ.Choice):\n    pass\n\n\nOriginatorIdentifierOrKey.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerAndSerialNumber', IssuerAndSerialNumber()),\n    namedtype.NamedType('subjectKeyIdentifier', SubjectKeyIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('originatorKey', OriginatorPublicKey().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n)\n\n\nclass KeyAgreeRecipientInfo(univ.Sequence):\n    pass\n\n\nKeyAgreeRecipientInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('originator', OriginatorIdentifierOrKey().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.OptionalNamedType('ukm', UserKeyingMaterial().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('keyEncryptionAlgorithm', KeyEncryptionAlgorithmIdentifier()),\n    namedtype.NamedType('recipientEncryptedKeys', RecipientEncryptedKeys())\n)\n\n\nclass RecipientIdentifier(univ.Choice):\n    pass\n\n\nRecipientIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerAndSerialNumber', IssuerAndSerialNumber()),\n    namedtype.NamedType('subjectKeyIdentifier', SubjectKeyIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass KeyTransRecipientInfo(univ.Sequence):\n    pass\n\n\nKeyTransRecipientInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('rid', RecipientIdentifier()),\n    namedtype.NamedType('keyEncryptionAlgorithm', KeyEncryptionAlgorithmIdentifier()),\n    namedtype.NamedType('encryptedKey', EncryptedKey())\n)\n\n\nclass RecipientInfo(univ.Choice):\n    pass\n\n\nRecipientInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('ktri', KeyTransRecipientInfo()),\n    namedtype.NamedType('kari', KeyAgreeRecipientInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n    namedtype.NamedType('kekri', KEKRecipientInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2))),\n    namedtype.NamedType('pwri', PasswordRecipientInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3))),\n    namedtype.NamedType('ori', OtherRecipientInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 4)))\n)\n\n\nclass RecipientInfos(univ.SetOf):\n    pass\n\n\nRecipientInfos.componentType = RecipientInfo()\nRecipientInfos.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass DigestAlgorithmIdentifier(rfc3280.AlgorithmIdentifier):\n    pass\n\n\nclass Signature(univ.BitString):\n    pass\n\n\nclass SignerIdentifier(univ.Choice):\n    pass\n\n\nSignerIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerAndSerialNumber', IssuerAndSerialNumber()),\n    namedtype.NamedType('subjectKeyIdentifier', SubjectKeyIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass UnprotectedAttributes(univ.SetOf):\n    pass\n\n\nUnprotectedAttributes.componentType = Attribute()\nUnprotectedAttributes.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass ContentType(univ.ObjectIdentifier):\n    pass\n\n\nclass EncryptedContent(univ.OctetString):\n    pass\n\n\nclass ContentEncryptionAlgorithmIdentifier(rfc3280.AlgorithmIdentifier):\n    pass\n\n\nclass EncryptedContentInfo(univ.Sequence):\n    pass\n\n\nEncryptedContentInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('contentType', ContentType()),\n    namedtype.NamedType('contentEncryptionAlgorithm', ContentEncryptionAlgorithmIdentifier()),\n    namedtype.OptionalNamedType('encryptedContent', EncryptedContent().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass EncryptedData(univ.Sequence):\n    pass\n\n\nEncryptedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('encryptedContentInfo', EncryptedContentInfo()),\n    namedtype.OptionalNamedType('unprotectedAttrs', UnprotectedAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\nid_contentType = _buildOid(1, 2, 840, 113549, 1, 9, 3)\n\nid_data = _buildOid(1, 2, 840, 113549, 1, 7, 1)\n\nid_messageDigest = _buildOid(1, 2, 840, 113549, 1, 9, 4)\n\n\nclass DigestAlgorithmIdentifiers(univ.SetOf):\n    pass\n\n\nDigestAlgorithmIdentifiers.componentType = DigestAlgorithmIdentifier()\n\n\nclass EncapsulatedContentInfo(univ.Sequence):\n    pass\n\n\nEncapsulatedContentInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('eContentType', ContentType()),\n    namedtype.OptionalNamedType('eContent', univ.OctetString().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass Digest(univ.OctetString):\n    pass\n\n\nclass DigestedData(univ.Sequence):\n    pass\n\n\nDigestedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('digestAlgorithm', DigestAlgorithmIdentifier()),\n    namedtype.NamedType('encapContentInfo', EncapsulatedContentInfo()),\n    namedtype.NamedType('digest', Digest())\n)\n\n\nclass ContentInfo(univ.Sequence):\n    pass\n\n\nContentInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('contentType', ContentType()),\n    namedtype.NamedType('content', univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass UnauthAttributes(univ.SetOf):\n    pass\n\n\nUnauthAttributes.componentType = Attribute()\nUnauthAttributes.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass ExtendedCertificateInfo(univ.Sequence):\n    pass\n\n\nExtendedCertificateInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('certificate', rfc3280.Certificate()),\n    namedtype.NamedType('attributes', UnauthAttributes())\n)\n\n\nclass SignatureAlgorithmIdentifier(rfc3280.AlgorithmIdentifier):\n    pass\n\n\nclass ExtendedCertificate(univ.Sequence):\n    pass\n\n\nExtendedCertificate.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('extendedCertificateInfo', ExtendedCertificateInfo()),\n    namedtype.NamedType('signatureAlgorithm', SignatureAlgorithmIdentifier()),\n    namedtype.NamedType('signature', Signature())\n)\n\n\nclass OtherCertificateFormat(univ.Sequence):\n    pass\n\n\nOtherCertificateFormat.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('otherCertFormat', univ.ObjectIdentifier()),\n    namedtype.NamedType('otherCert', univ.Any())\n)\n\n\nclass AttributeCertificateV2(rfc3281.AttributeCertificate):\n    pass\n\n\nclass AttCertVersionV1(univ.Integer):\n    pass\n\n\nAttCertVersionV1.namedValues = namedval.NamedValues(\n    ('v1', 0)\n)\n\n\nclass AttributeCertificateInfoV1(univ.Sequence):\n    pass\n\n\nAttributeCertificateInfoV1.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version', AttCertVersionV1().subtype(value=\"v1\")),\n    namedtype.NamedType(\n        'subject', univ.Choice(\n            componentType=namedtype.NamedTypes(\n                namedtype.NamedType('baseCertificateID', rfc3281.IssuerSerial().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n                namedtype.NamedType('subjectName', rfc3280.GeneralNames().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n            )\n        )\n    ),\n    namedtype.NamedType('issuer', rfc3280.GeneralNames()),\n    namedtype.NamedType('signature', rfc3280.AlgorithmIdentifier()),\n    namedtype.NamedType('serialNumber', rfc3280.CertificateSerialNumber()),\n    namedtype.NamedType('attCertValidityPeriod', rfc3281.AttCertValidityPeriod()),\n    namedtype.NamedType('attributes', univ.SequenceOf(componentType=rfc3280.Attribute())),\n    namedtype.OptionalNamedType('issuerUniqueID', rfc3280.UniqueIdentifier()),\n    namedtype.OptionalNamedType('extensions', rfc3280.Extensions())\n)\n\n\nclass AttributeCertificateV1(univ.Sequence):\n    pass\n\n\nAttributeCertificateV1.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('acInfo', AttributeCertificateInfoV1()),\n    namedtype.NamedType('signatureAlgorithm', rfc3280.AlgorithmIdentifier()),\n    namedtype.NamedType('signature', univ.BitString())\n)\n\n\nclass CertificateChoices(univ.Choice):\n    pass\n\n\nCertificateChoices.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('certificate', rfc3280.Certificate()),\n    namedtype.NamedType('extendedCertificate', ExtendedCertificate().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('v1AttrCert', AttributeCertificateV1().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('v2AttrCert', AttributeCertificateV2().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.NamedType('other', OtherCertificateFormat().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3)))\n)\n\n\nclass CertificateSet(univ.SetOf):\n    pass\n\n\nCertificateSet.componentType = CertificateChoices()\n\n\nclass MessageAuthenticationCode(univ.OctetString):\n    pass\n\n\nclass UnsignedAttributes(univ.SetOf):\n    pass\n\n\nUnsignedAttributes.componentType = Attribute()\nUnsignedAttributes.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass SignatureValue(univ.OctetString):\n    pass\n\n\nclass SignerInfo(univ.Sequence):\n    pass\n\n\nSignerInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('sid', SignerIdentifier()),\n    namedtype.NamedType('digestAlgorithm', DigestAlgorithmIdentifier()),\n    namedtype.OptionalNamedType('signedAttrs', SignedAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('signatureAlgorithm', SignatureAlgorithmIdentifier()),\n    namedtype.NamedType('signature', SignatureValue()),\n    namedtype.OptionalNamedType('unsignedAttrs', UnsignedAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass SignerInfos(univ.SetOf):\n    pass\n\n\nSignerInfos.componentType = SignerInfo()\n\n\nclass SignedData(univ.Sequence):\n    pass\n\n\nSignedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('digestAlgorithms', DigestAlgorithmIdentifiers()),\n    namedtype.NamedType('encapContentInfo', EncapsulatedContentInfo()),\n    namedtype.OptionalNamedType('certificates', CertificateSet().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('crls', RevocationInfoChoices().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('signerInfos', SignerInfos())\n)\n\n\nclass MessageAuthenticationCodeAlgorithm(rfc3280.AlgorithmIdentifier):\n    pass\n\n\nclass MessageDigest(univ.OctetString):\n    pass\n\n\nclass Time(univ.Choice):\n    pass\n\n\nTime.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('utcTime', useful.UTCTime()),\n    namedtype.NamedType('generalTime', useful.GeneralizedTime())\n)\n\n\nclass OriginatorInfo(univ.Sequence):\n    pass\n\n\nOriginatorInfo.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('certs', CertificateSet().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('crls', RevocationInfoChoices().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass AuthAttributes(univ.SetOf):\n    pass\n\n\nAuthAttributes.componentType = Attribute()\nAuthAttributes.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass AuthenticatedData(univ.Sequence):\n    pass\n\n\nAuthenticatedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.OptionalNamedType('originatorInfo', OriginatorInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('recipientInfos', RecipientInfos()),\n    namedtype.NamedType('macAlgorithm', MessageAuthenticationCodeAlgorithm()),\n    namedtype.OptionalNamedType('digestAlgorithm', DigestAlgorithmIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('encapContentInfo', EncapsulatedContentInfo()),\n    namedtype.OptionalNamedType('authAttrs', AuthAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.NamedType('mac', MessageAuthenticationCode()),\n    namedtype.OptionalNamedType('unauthAttrs', UnauthAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\nid_ct_contentInfo = _buildOid(1, 2, 840, 113549, 1, 9, 16, 1, 6)\n\nid_envelopedData = _buildOid(1, 2, 840, 113549, 1, 7, 3)\n\n\nclass EnvelopedData(univ.Sequence):\n    pass\n\n\nEnvelopedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.OptionalNamedType('originatorInfo', OriginatorInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('recipientInfos', RecipientInfos()),\n    namedtype.NamedType('encryptedContentInfo', EncryptedContentInfo()),\n    namedtype.OptionalNamedType('unprotectedAttrs', UnprotectedAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass Countersignature(SignerInfo):\n    pass\n\n\nid_digestedData = _buildOid(1, 2, 840, 113549, 1, 7, 5)\n\nid_signingTime = _buildOid(1, 2, 840, 113549, 1, 9, 5)\n\n\nclass ExtendedCertificateOrCertificate(univ.Choice):\n    pass\n\n\nExtendedCertificateOrCertificate.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('certificate', rfc3280.Certificate()),\n    namedtype.NamedType('extendedCertificate', ExtendedCertificate().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n)\n\nid_encryptedData = _buildOid(1, 2, 840, 113549, 1, 7, 6)\n\nid_ct_authData = _buildOid(1, 2, 840, 113549, 1, 9, 16, 1, 2)\n\n\nclass SigningTime(Time):\n    pass\n\n\nid_countersignature = _buildOid(1, 2, 840, 113549, 1, 9, 6)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc4055.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with a very small amount of assistance from\n# asn1ate v.0.6.0.\n# Modified by Russ Housley to add maps for opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Additional Algorithms and Identifiers for RSA Cryptography\n# for use in Certificates and CRLs\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc4055.txt\n#\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n    return univ.ObjectIdentifier(output)\n\n\nid_sha1 = _OID(1, 3, 14, 3, 2, 26)\n\nid_sha256 = _OID(2, 16, 840, 1, 101, 3, 4, 2, 1)\n\nid_sha384 = _OID(2, 16, 840, 1, 101, 3, 4, 2, 2)\n\nid_sha512 = _OID(2, 16, 840, 1, 101, 3, 4, 2, 3)\n\nid_sha224 = _OID(2, 16, 840, 1, 101, 3, 4, 2, 4)\n\nrsaEncryption = _OID(1, 2, 840, 113549, 1, 1, 1)\n\nid_mgf1 = _OID(1, 2, 840, 113549, 1, 1, 8)\n\nid_RSAES_OAEP = _OID(1, 2, 840, 113549, 1, 1, 7)\n\nid_pSpecified = _OID(1, 2, 840, 113549, 1, 1, 9)\n\nid_RSASSA_PSS = _OID(1, 2, 840, 113549, 1, 1, 10)\n\nsha256WithRSAEncryption = _OID(1, 2, 840, 113549, 1, 1, 11)\n\nsha384WithRSAEncryption = _OID(1, 2, 840, 113549, 1, 1, 12)\n\nsha512WithRSAEncryption = _OID(1, 2, 840, 113549, 1, 1, 13)\n\nsha224WithRSAEncryption = _OID(1, 2, 840, 113549, 1, 1, 14)\n\nsha1Identifier = rfc5280.AlgorithmIdentifier()\nsha1Identifier['algorithm'] = id_sha1\nsha1Identifier['parameters'] = univ.Null(\"\")\n\nsha224Identifier = rfc5280.AlgorithmIdentifier()\nsha224Identifier['algorithm'] = id_sha224\nsha224Identifier['parameters'] = univ.Null(\"\")\n\nsha256Identifier = rfc5280.AlgorithmIdentifier()\nsha256Identifier['algorithm'] = id_sha256\nsha256Identifier['parameters'] = univ.Null(\"\")\n\nsha384Identifier = rfc5280.AlgorithmIdentifier()\nsha384Identifier['algorithm'] = id_sha384\nsha384Identifier['parameters'] = univ.Null(\"\")\n\nsha512Identifier = rfc5280.AlgorithmIdentifier()\nsha512Identifier['algorithm'] = id_sha512\nsha512Identifier['parameters'] = univ.Null(\"\")\n\nmgf1SHA1Identifier = rfc5280.AlgorithmIdentifier()\nmgf1SHA1Identifier['algorithm'] = id_mgf1\nmgf1SHA1Identifier['parameters'] = sha1Identifier\n\nmgf1SHA224Identifier = rfc5280.AlgorithmIdentifier()\nmgf1SHA224Identifier['algorithm'] = id_mgf1\nmgf1SHA224Identifier['parameters'] = sha224Identifier\n\nmgf1SHA256Identifier = rfc5280.AlgorithmIdentifier()\nmgf1SHA256Identifier['algorithm'] = id_mgf1\nmgf1SHA256Identifier['parameters'] = sha256Identifier\n\nmgf1SHA384Identifier = rfc5280.AlgorithmIdentifier()\nmgf1SHA384Identifier['algorithm'] = id_mgf1\nmgf1SHA384Identifier['parameters'] = sha384Identifier\n\nmgf1SHA512Identifier = rfc5280.AlgorithmIdentifier()\nmgf1SHA512Identifier['algorithm'] = id_mgf1\nmgf1SHA512Identifier['parameters'] = sha512Identifier\n\npSpecifiedEmptyIdentifier = rfc5280.AlgorithmIdentifier()\npSpecifiedEmptyIdentifier['algorithm'] = id_pSpecified\npSpecifiedEmptyIdentifier['parameters'] = univ.OctetString(value='')\n\n\nclass RSAPublicKey(univ.Sequence):\n    pass\n\nRSAPublicKey.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('modulus', univ.Integer()),\n    namedtype.NamedType('publicExponent', univ.Integer())\n)\n\n\nclass HashAlgorithm(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass MaskGenAlgorithm(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass RSAES_OAEP_params(univ.Sequence):\n    pass\n\nRSAES_OAEP_params.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('hashFunc', rfc5280.AlgorithmIdentifier().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.OptionalNamedType('maskGenFunc', rfc5280.AlgorithmIdentifier().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n    namedtype.OptionalNamedType('pSourceFunc', rfc5280.AlgorithmIdentifier().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2)))\n)\n\nrSAES_OAEP_Default_Params = RSAES_OAEP_params()\n\nrSAES_OAEP_Default_Identifier = rfc5280.AlgorithmIdentifier()\nrSAES_OAEP_Default_Identifier['algorithm'] = id_RSAES_OAEP\nrSAES_OAEP_Default_Identifier['parameters'] = rSAES_OAEP_Default_Params\n\nrSAES_OAEP_SHA224_Params = RSAES_OAEP_params()\nrSAES_OAEP_SHA224_Params['hashFunc'] = sha224Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0), cloneValueFlag=True)\nrSAES_OAEP_SHA224_Params['maskGenFunc'] = mgf1SHA224Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1), cloneValueFlag=True)\n\nrSAES_OAEP_SHA224_Identifier = rfc5280.AlgorithmIdentifier()\nrSAES_OAEP_SHA224_Identifier['algorithm'] = id_RSAES_OAEP\nrSAES_OAEP_SHA224_Identifier['parameters'] = rSAES_OAEP_SHA224_Params\n\nrSAES_OAEP_SHA256_Params = RSAES_OAEP_params()\nrSAES_OAEP_SHA256_Params['hashFunc'] = sha256Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0), cloneValueFlag=True)\nrSAES_OAEP_SHA256_Params['maskGenFunc'] = mgf1SHA256Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1), cloneValueFlag=True)\n\nrSAES_OAEP_SHA256_Identifier = rfc5280.AlgorithmIdentifier()\nrSAES_OAEP_SHA256_Identifier['algorithm'] = id_RSAES_OAEP\nrSAES_OAEP_SHA256_Identifier['parameters'] = rSAES_OAEP_SHA256_Params\n\nrSAES_OAEP_SHA384_Params = RSAES_OAEP_params()\nrSAES_OAEP_SHA384_Params['hashFunc'] = sha384Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0), cloneValueFlag=True)\nrSAES_OAEP_SHA384_Params['maskGenFunc'] = mgf1SHA384Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1), cloneValueFlag=True)\n\nrSAES_OAEP_SHA384_Identifier = rfc5280.AlgorithmIdentifier()\nrSAES_OAEP_SHA384_Identifier['algorithm'] = id_RSAES_OAEP\nrSAES_OAEP_SHA384_Identifier['parameters'] = rSAES_OAEP_SHA384_Params\n\nrSAES_OAEP_SHA512_Params = RSAES_OAEP_params()\nrSAES_OAEP_SHA512_Params['hashFunc'] = sha512Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0), cloneValueFlag=True)\nrSAES_OAEP_SHA512_Params['maskGenFunc'] = mgf1SHA512Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1), cloneValueFlag=True)\n\nrSAES_OAEP_SHA512_Identifier = rfc5280.AlgorithmIdentifier()\nrSAES_OAEP_SHA512_Identifier['algorithm'] = id_RSAES_OAEP\nrSAES_OAEP_SHA512_Identifier['parameters'] = rSAES_OAEP_SHA512_Params\n\n\nclass RSASSA_PSS_params(univ.Sequence):\n    pass\n\nRSASSA_PSS_params.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('hashAlgorithm', rfc5280.AlgorithmIdentifier().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.OptionalNamedType('maskGenAlgorithm', rfc5280.AlgorithmIdentifier().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n    namedtype.DefaultedNamedType('saltLength', univ.Integer(value=20).subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.DefaultedNamedType('trailerField', univ.Integer(value=1).subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\nrSASSA_PSS_Default_Params = RSASSA_PSS_params()\n\nrSASSA_PSS_Default_Identifier = rfc5280.AlgorithmIdentifier()\nrSASSA_PSS_Default_Identifier['algorithm'] = id_RSASSA_PSS\nrSASSA_PSS_Default_Identifier['parameters'] = rSASSA_PSS_Default_Params\n\nrSASSA_PSS_SHA224_Params = RSASSA_PSS_params()\nrSASSA_PSS_SHA224_Params['hashAlgorithm'] = sha224Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0), cloneValueFlag=True)\nrSASSA_PSS_SHA224_Params['maskGenAlgorithm'] = mgf1SHA224Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1), cloneValueFlag=True)\n\nrSASSA_PSS_SHA224_Identifier = rfc5280.AlgorithmIdentifier()\nrSASSA_PSS_SHA224_Identifier['algorithm'] = id_RSASSA_PSS\nrSASSA_PSS_SHA224_Identifier['parameters'] = rSASSA_PSS_SHA224_Params\n\nrSASSA_PSS_SHA256_Params = RSASSA_PSS_params()\nrSASSA_PSS_SHA256_Params['hashAlgorithm'] = sha256Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0), cloneValueFlag=True)\nrSASSA_PSS_SHA256_Params['maskGenAlgorithm'] = mgf1SHA256Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1), cloneValueFlag=True)\n\nrSASSA_PSS_SHA256_Identifier = rfc5280.AlgorithmIdentifier()\nrSASSA_PSS_SHA256_Identifier['algorithm'] = id_RSASSA_PSS\nrSASSA_PSS_SHA256_Identifier['parameters'] = rSASSA_PSS_SHA256_Params\n\nrSASSA_PSS_SHA384_Params = RSASSA_PSS_params()\nrSASSA_PSS_SHA384_Params['hashAlgorithm'] = sha384Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0), cloneValueFlag=True)\nrSASSA_PSS_SHA384_Params['maskGenAlgorithm'] = mgf1SHA384Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1), cloneValueFlag=True)\n\nrSASSA_PSS_SHA384_Identifier = rfc5280.AlgorithmIdentifier()\nrSASSA_PSS_SHA384_Identifier['algorithm'] = id_RSASSA_PSS\nrSASSA_PSS_SHA384_Identifier['parameters'] = rSASSA_PSS_SHA384_Params\n\nrSASSA_PSS_SHA512_Params = RSASSA_PSS_params()\nrSASSA_PSS_SHA512_Params['hashAlgorithm'] = sha512Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0), cloneValueFlag=True)\nrSASSA_PSS_SHA512_Params['maskGenAlgorithm'] = mgf1SHA512Identifier.subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1), cloneValueFlag=True)\n\nrSASSA_PSS_SHA512_Identifier = rfc5280.AlgorithmIdentifier()\nrSASSA_PSS_SHA512_Identifier['algorithm'] = id_RSASSA_PSS\nrSASSA_PSS_SHA512_Identifier['parameters'] = rSASSA_PSS_SHA512_Params\n\n\n# Update the Algorithm Identifier map\n\n_algorithmIdentifierMapUpdate = {\n    id_sha1: univ.Null(),\n    id_sha224: univ.Null(),\n    id_sha256: univ.Null(),\n    id_sha384: univ.Null(),\n    id_sha512: univ.Null(),\n    id_mgf1: rfc5280.AlgorithmIdentifier(),\n    id_pSpecified: univ.OctetString(),\n    id_RSAES_OAEP: RSAES_OAEP_params(),\n    id_RSASSA_PSS: RSASSA_PSS_params(),\n}\n\nrfc5280.algorithmIdentifierMap.update(_algorithmIdentifierMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc4073.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with some assistance from asn1ate v.0.6.0.\n# Modified by Russ Housley to add a map for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Protecting Multiple Contents with the CMS\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc4073.txt\n#\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5652\n\nMAX = float('inf')\n\n\n# Content Collection Content Type and Object Identifier\n\nid_ct_contentCollection = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.19')\n\nclass ContentCollection(univ.SequenceOf):\n    pass\n\nContentCollection.componentType = rfc5652.ContentInfo()\nContentCollection.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\n# Content With Attributes Content Type and Object Identifier\n\nid_ct_contentWithAttrs = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.20')\n\nclass ContentWithAttributes(univ.Sequence):\n    pass\n\nContentWithAttributes.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('content', rfc5652.ContentInfo()),\n    namedtype.NamedType('attrs', univ.SequenceOf(\n        componentType=rfc5652.Attribute()).subtype(\n            sizeSpec=constraint.ValueSizeConstraint(1, MAX)))\n)\n\n\n# Map of Content Type OIDs to Content Types is added to the\n# ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_contentCollection: ContentCollection(),\n    id_ct_contentWithAttrs: ContentWithAttributes(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc4108.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n# Modified by Russ Housley to add items from the verified errata.\n# Modified by Russ Housley to add maps for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# CMS Firmware Wrapper\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc4108.txt\n# https://www.rfc-editor.org/errata_search.php?rfc=4108\n#\n\n\nfrom pyasn1.type import univ, char, namedtype, namedval, tag, constraint, useful\n\nfrom pyasn1_modules import rfc5280\nfrom pyasn1_modules import rfc5652\n\nMAX = float('inf')\n\n\nclass HardwareSerialEntry(univ.Choice):\n    pass\n\nHardwareSerialEntry.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('all', univ.Null()),\n    namedtype.NamedType('single', univ.OctetString()),\n    namedtype.NamedType('block', univ.Sequence(componentType=namedtype.NamedTypes(\n        namedtype.NamedType('low', univ.OctetString()),\n        namedtype.NamedType('high', univ.OctetString())\n    ))\n    )\n)\n\n\nclass HardwareModules(univ.Sequence):\n    pass\n\nHardwareModules.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('hwType', univ.ObjectIdentifier()),\n    namedtype.NamedType('hwSerialEntries', univ.SequenceOf(componentType=HardwareSerialEntry()))\n)\n\n\nclass CommunityIdentifier(univ.Choice):\n    pass\n\nCommunityIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('communityOID', univ.ObjectIdentifier()),\n    namedtype.NamedType('hwModuleList', HardwareModules())\n)\n\n\n\nclass PreferredPackageIdentifier(univ.Sequence):\n    pass\n\nPreferredPackageIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('fwPkgID', univ.ObjectIdentifier()),\n    namedtype.NamedType('verNum', univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, MAX)))\n)\n\n\nclass PreferredOrLegacyPackageIdentifier(univ.Choice):\n    pass\n\nPreferredOrLegacyPackageIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('preferred', PreferredPackageIdentifier()),\n    namedtype.NamedType('legacy', univ.OctetString())\n)\n\n\nclass CurrentFWConfig(univ.Sequence):\n    pass\n\nCurrentFWConfig.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('fwPkgType', univ.Integer()),\n    namedtype.NamedType('fwPkgName', PreferredOrLegacyPackageIdentifier())\n)\n\n\nclass PreferredOrLegacyStalePackageIdentifier(univ.Choice):\n    pass\n\nPreferredOrLegacyStalePackageIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('preferredStaleVerNum', univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, MAX))),\n    namedtype.NamedType('legacyStaleVersion', univ.OctetString())\n)\n\n\nclass FirmwarePackageLoadErrorCode(univ.Enumerated):\n    pass\n\nFirmwarePackageLoadErrorCode.namedValues = namedval.NamedValues(\n    ('decodeFailure', 1),\n    ('badContentInfo', 2),\n    ('badSignedData', 3),\n    ('badEncapContent', 4),\n    ('badCertificate', 5),\n    ('badSignerInfo', 6),\n    ('badSignedAttrs', 7),\n    ('badUnsignedAttrs', 8),\n    ('missingContent', 9),\n    ('noTrustAnchor', 10),\n    ('notAuthorized', 11),\n    ('badDigestAlgorithm', 12),\n    ('badSignatureAlgorithm', 13),\n    ('unsupportedKeySize', 14),\n    ('signatureFailure', 15),\n    ('contentTypeMismatch', 16),\n    ('badEncryptedData', 17),\n    ('unprotectedAttrsPresent', 18),\n    ('badEncryptContent', 19),\n    ('badEncryptAlgorithm', 20),\n    ('missingCiphertext', 21),\n    ('noDecryptKey', 22),\n    ('decryptFailure', 23),\n    ('badCompressAlgorithm', 24),\n    ('missingCompressedContent', 25),\n    ('decompressFailure', 26),\n    ('wrongHardware', 27),\n    ('stalePackage', 28),\n    ('notInCommunity', 29),\n    ('unsupportedPackageType', 30),\n    ('missingDependency', 31),\n    ('wrongDependencyVersion', 32),\n    ('insufficientMemory', 33),\n    ('badFirmware', 34),\n    ('unsupportedParameters', 35),\n    ('breaksDependency', 36),\n    ('otherError', 99)\n)\n\n\nclass VendorLoadErrorCode(univ.Integer):\n    pass\n\n\n# Wrapped Firmware Key Unsigned Attribute and Object Identifier\n\nid_aa_wrappedFirmwareKey = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.39')\n\nclass WrappedFirmwareKey(rfc5652.EnvelopedData):\n    pass\n\n\n# Firmware Package Information Signed Attribute and Object Identifier\n\nid_aa_firmwarePackageInfo = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.42')\n\nclass FirmwarePackageInfo(univ.Sequence):\n    pass\n\nFirmwarePackageInfo.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('fwPkgType', univ.Integer()),\n    namedtype.OptionalNamedType('dependencies', univ.SequenceOf(componentType=PreferredOrLegacyPackageIdentifier()))\n)\n\nFirmwarePackageInfo.sizeSpec = univ.Sequence.sizeSpec + constraint.ValueSizeConstraint(1, 2)\n\n\n# Community Identifiers Signed Attribute and Object Identifier\n\nid_aa_communityIdentifiers = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.40')\n\nclass CommunityIdentifiers(univ.SequenceOf):\n    pass\n\nCommunityIdentifiers.componentType = CommunityIdentifier()\n\n\n# Implemented Compression Algorithms Signed Attribute and Object Identifier\n\nid_aa_implCompressAlgs = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.43')\n\nclass ImplementedCompressAlgorithms(univ.SequenceOf):\n    pass\n\nImplementedCompressAlgorithms.componentType = univ.ObjectIdentifier()\n\n\n# Implemented Cryptographic Algorithms Signed Attribute and Object Identifier\n\nid_aa_implCryptoAlgs = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.38')\n\nclass ImplementedCryptoAlgorithms(univ.SequenceOf):\n    pass\n\nImplementedCryptoAlgorithms.componentType = univ.ObjectIdentifier()\n\n\n# Decrypt Key Identifier Signed Attribute and Object Identifier\n\nid_aa_decryptKeyID = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.37')\n\nclass DecryptKeyIdentifier(univ.OctetString):\n    pass\n\n\n# Target Hardware Identifier Signed Attribute and Object Identifier\n\nid_aa_targetHardwareIDs = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.36')\n\nclass TargetHardwareIdentifiers(univ.SequenceOf):\n    pass\n\nTargetHardwareIdentifiers.componentType = univ.ObjectIdentifier()\n\n\n# Firmware Package Identifier Signed Attribute and Object Identifier\n\nid_aa_firmwarePackageID = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.35')\n\nclass FirmwarePackageIdentifier(univ.Sequence):\n    pass\n\nFirmwarePackageIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('name', PreferredOrLegacyPackageIdentifier()),\n    namedtype.OptionalNamedType('stale', PreferredOrLegacyStalePackageIdentifier())\n)\n\n\n# Firmware Package Message Digest Signed Attribute and Object Identifier\n\nid_aa_fwPkgMessageDigest = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.41')\n\nclass FirmwarePackageMessageDigest(univ.Sequence):\n    pass\n\nFirmwarePackageMessageDigest.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('algorithm', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('msgDigest', univ.OctetString())\n)\n\n\n# Firmware Package Load Error Report Content Type and Object Identifier\n\nclass FWErrorVersion(univ.Integer):\n    pass\n\nFWErrorVersion.namedValues = namedval.NamedValues(\n    ('v1', 1)\n)\n\n\nid_ct_firmwareLoadError = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.18')\n\nclass FirmwarePackageLoadError(univ.Sequence):\n    pass\n\nFirmwarePackageLoadError.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version', FWErrorVersion().subtype(value='v1')),\n    namedtype.NamedType('hwType', univ.ObjectIdentifier()),\n    namedtype.NamedType('hwSerialNum', univ.OctetString()),\n    namedtype.NamedType('errorCode', FirmwarePackageLoadErrorCode()),\n    namedtype.OptionalNamedType('vendorErrorCode', VendorLoadErrorCode()),\n    namedtype.OptionalNamedType('fwPkgName', PreferredOrLegacyPackageIdentifier()),\n    namedtype.OptionalNamedType('config', univ.SequenceOf(componentType=CurrentFWConfig()).subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\n# Firmware Package Load Receipt Content Type and Object Identifier\n\nclass FWReceiptVersion(univ.Integer):\n    pass\n\nFWReceiptVersion.namedValues = namedval.NamedValues(\n    ('v1', 1)\n)\n\n\nid_ct_firmwareLoadReceipt = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.17')\n\nclass FirmwarePackageLoadReceipt(univ.Sequence):\n    pass\n\nFirmwarePackageLoadReceipt.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version', FWReceiptVersion().subtype(value='v1')),\n    namedtype.NamedType('hwType', univ.ObjectIdentifier()),\n    namedtype.NamedType('hwSerialNum', univ.OctetString()),\n    namedtype.NamedType('fwPkgName', PreferredOrLegacyPackageIdentifier()),\n    namedtype.OptionalNamedType('trustAnchorKeyID', univ.OctetString()),\n    namedtype.OptionalNamedType('decryptKeyID', univ.OctetString().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\n# Firmware Package Content Type and Object Identifier\n\nid_ct_firmwarePackage = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.16')\n\nclass FirmwarePkgData(univ.OctetString):\n    pass\n\n\n# Other Name syntax for Hardware Module Name\n\nid_on_hardwareModuleName = univ.ObjectIdentifier('1.3.6.1.5.5.7.8.4')\n\nclass HardwareModuleName(univ.Sequence):\n    pass\n\nHardwareModuleName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('hwType', univ.ObjectIdentifier()),\n    namedtype.NamedType('hwSerialNum', univ.OctetString())\n)\n\n\n# Map of Attribute Type OIDs to Attributes is added to the\n# ones that are in rfc5652.py\n\n_cmsAttributesMapUpdate = {\n    id_aa_wrappedFirmwareKey: WrappedFirmwareKey(),\n    id_aa_firmwarePackageInfo: FirmwarePackageInfo(),\n    id_aa_communityIdentifiers: CommunityIdentifiers(),\n    id_aa_implCompressAlgs: ImplementedCompressAlgorithms(),\n    id_aa_implCryptoAlgs: ImplementedCryptoAlgorithms(),\n    id_aa_decryptKeyID: DecryptKeyIdentifier(),\n    id_aa_targetHardwareIDs: TargetHardwareIdentifiers(),\n    id_aa_firmwarePackageID: FirmwarePackageIdentifier(),\n    id_aa_fwPkgMessageDigest: FirmwarePackageMessageDigest(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n\n\n# Map of Content Type OIDs to Content Types is added to the\n# ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_firmwareLoadError: FirmwarePackageLoadError(),\n    id_ct_firmwareLoadReceipt: FirmwarePackageLoadReceipt(),\n    id_ct_firmwarePackage: FirmwarePkgData(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n\n\n# Map of Other Name OIDs to Other Name is added to the\n# ones that are in rfc5280.py\n\n_anotherNameMapUpdate = {\n    id_on_hardwareModuleName: HardwareModuleName(),\n}\n\nrfc5280.anotherNameMap.update(_anotherNameMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc4210.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Certificate Management Protocol structures as per RFC4210\n#\n# Based on Alex Railean's work\n#\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nfrom pyasn1_modules import rfc2314\nfrom pyasn1_modules import rfc2459\nfrom pyasn1_modules import rfc2511\n\nMAX = float('inf')\n\n\nclass KeyIdentifier(univ.OctetString):\n    pass\n\n\nclass CMPCertificate(rfc2459.Certificate):\n    pass\n\n\nclass OOBCert(CMPCertificate):\n    pass\n\n\nclass CertAnnContent(CMPCertificate):\n    pass\n\n\nclass PKIFreeText(univ.SequenceOf):\n    \"\"\"\n    PKIFreeText ::= SEQUENCE SIZE (1..MAX) OF UTF8String\n    \"\"\"\n    componentType = char.UTF8String()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\nclass PollRepContent(univ.SequenceOf):\n    \"\"\"\n         PollRepContent ::= SEQUENCE OF SEQUENCE {\n         certReqId              INTEGER,\n         checkAfter             INTEGER,  -- time in seconds\n         reason                 PKIFreeText OPTIONAL\n     }\n    \"\"\"\n\n    class CertReq(univ.Sequence):\n        componentType = namedtype.NamedTypes(\n            namedtype.NamedType('certReqId', univ.Integer()),\n            namedtype.NamedType('checkAfter', univ.Integer()),\n            namedtype.OptionalNamedType('reason', PKIFreeText())\n        )\n\n    componentType = CertReq()\n\n\nclass PollReqContent(univ.SequenceOf):\n    \"\"\"\n         PollReqContent ::= SEQUENCE OF SEQUENCE {\n         certReqId              INTEGER\n     }\n\n    \"\"\"\n\n    class CertReq(univ.Sequence):\n        componentType = namedtype.NamedTypes(\n            namedtype.NamedType('certReqId', univ.Integer())\n        )\n\n    componentType = CertReq()\n\n\nclass InfoTypeAndValue(univ.Sequence):\n    \"\"\"\n    InfoTypeAndValue ::= SEQUENCE {\n     infoType               OBJECT IDENTIFIER,\n     infoValue              ANY DEFINED BY infoType  OPTIONAL\n    }\"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('infoType', univ.ObjectIdentifier()),\n        namedtype.OptionalNamedType('infoValue', univ.Any())\n    )\n\n\nclass GenRepContent(univ.SequenceOf):\n    componentType = InfoTypeAndValue()\n\n\nclass GenMsgContent(univ.SequenceOf):\n    componentType = InfoTypeAndValue()\n\n\nclass PKIConfirmContent(univ.Null):\n    pass\n\n\nclass CRLAnnContent(univ.SequenceOf):\n    componentType = rfc2459.CertificateList()\n\n\nclass CAKeyUpdAnnContent(univ.Sequence):\n    \"\"\"\n    CAKeyUpdAnnContent ::= SEQUENCE {\n         oldWithNew   CMPCertificate,\n         newWithOld   CMPCertificate,\n         newWithNew   CMPCertificate\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('oldWithNew', CMPCertificate()),\n        namedtype.NamedType('newWithOld', CMPCertificate()),\n        namedtype.NamedType('newWithNew', CMPCertificate())\n    )\n\n\nclass RevDetails(univ.Sequence):\n    \"\"\"\n    RevDetails ::= SEQUENCE {\n         certDetails         CertTemplate,\n         crlEntryDetails     Extensions       OPTIONAL\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('certDetails', rfc2511.CertTemplate()),\n        namedtype.OptionalNamedType('crlEntryDetails', rfc2459.Extensions())\n    )\n\n\nclass RevReqContent(univ.SequenceOf):\n    componentType = RevDetails()\n\n\nclass CertOrEncCert(univ.Choice):\n    \"\"\"\n     CertOrEncCert ::= CHOICE {\n         certificate     [0] CMPCertificate,\n         encryptedCert   [1] EncryptedValue\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('certificate', CMPCertificate().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.NamedType('encryptedCert', rfc2511.EncryptedValue().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n    )\n\n\nclass CertifiedKeyPair(univ.Sequence):\n    \"\"\"\n    CertifiedKeyPair ::= SEQUENCE {\n         certOrEncCert       CertOrEncCert,\n         privateKey      [0] EncryptedValue      OPTIONAL,\n         publicationInfo [1] PKIPublicationInfo  OPTIONAL\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('certOrEncCert', CertOrEncCert()),\n        namedtype.OptionalNamedType('privateKey', rfc2511.EncryptedValue().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.OptionalNamedType('publicationInfo', rfc2511.PKIPublicationInfo().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n    )\n\n\nclass POPODecKeyRespContent(univ.SequenceOf):\n    componentType = univ.Integer()\n\n\nclass Challenge(univ.Sequence):\n    \"\"\"\n    Challenge ::= SEQUENCE {\n         owf                 AlgorithmIdentifier  OPTIONAL,\n         witness             OCTET STRING,\n         challenge           OCTET STRING\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType('owf', rfc2459.AlgorithmIdentifier()),\n        namedtype.NamedType('witness', univ.OctetString()),\n        namedtype.NamedType('challenge', univ.OctetString())\n    )\n\n\nclass PKIStatus(univ.Integer):\n    \"\"\"\n    PKIStatus ::= INTEGER {\n         accepted                (0),\n         grantedWithMods        (1),\n         rejection              (2),\n         waiting                (3),\n         revocationWarning      (4),\n         revocationNotification (5),\n         keyUpdateWarning       (6)\n     }\n    \"\"\"\n    namedValues = namedval.NamedValues(\n        ('accepted', 0),\n        ('grantedWithMods', 1),\n        ('rejection', 2),\n        ('waiting', 3),\n        ('revocationWarning', 4),\n        ('revocationNotification', 5),\n        ('keyUpdateWarning', 6)\n    )\n\n\nclass PKIFailureInfo(univ.BitString):\n    \"\"\"\n    PKIFailureInfo ::= BIT STRING {\n         badAlg              (0),\n         badMessageCheck     (1),\n         badRequest          (2),\n         badTime             (3),\n         badCertId           (4),\n         badDataFormat       (5),\n         wrongAuthority      (6),\n         incorrectData       (7),\n         missingTimeStamp    (8),\n         badPOP              (9),\n         certRevoked         (10),\n         certConfirmed       (11),\n         wrongIntegrity      (12),\n         badRecipientNonce   (13),\n         timeNotAvailable    (14),\n         unacceptedPolicy    (15),\n         unacceptedExtension (16),\n         addInfoNotAvailable (17),\n         badSenderNonce      (18),\n         badCertTemplate     (19),\n         signerNotTrusted    (20),\n         transactionIdInUse  (21),\n         unsupportedVersion  (22),\n         notAuthorized       (23),\n         systemUnavail       (24),\n         systemFailure       (25),\n         duplicateCertReq    (26)\n    \"\"\"\n    namedValues = namedval.NamedValues(\n        ('badAlg', 0),\n        ('badMessageCheck', 1),\n        ('badRequest', 2),\n        ('badTime', 3),\n        ('badCertId', 4),\n        ('badDataFormat', 5),\n        ('wrongAuthority', 6),\n        ('incorrectData', 7),\n        ('missingTimeStamp', 8),\n        ('badPOP', 9),\n        ('certRevoked', 10),\n        ('certConfirmed', 11),\n        ('wrongIntegrity', 12),\n        ('badRecipientNonce', 13),\n        ('timeNotAvailable', 14),\n        ('unacceptedPolicy', 15),\n        ('unacceptedExtension', 16),\n        ('addInfoNotAvailable', 17),\n        ('badSenderNonce', 18),\n        ('badCertTemplate', 19),\n        ('signerNotTrusted', 20),\n        ('transactionIdInUse', 21),\n        ('unsupportedVersion', 22),\n        ('notAuthorized', 23),\n        ('systemUnavail', 24),\n        ('systemFailure', 25),\n        ('duplicateCertReq', 26)\n    )\n\n\nclass PKIStatusInfo(univ.Sequence):\n    \"\"\"\n    PKIStatusInfo ::= SEQUENCE {\n         status        PKIStatus,\n         statusString  PKIFreeText     OPTIONAL,\n         failInfo      PKIFailureInfo  OPTIONAL\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('status', PKIStatus()),\n        namedtype.OptionalNamedType('statusString', PKIFreeText()),\n        namedtype.OptionalNamedType('failInfo', PKIFailureInfo())\n    )\n\n\nclass ErrorMsgContent(univ.Sequence):\n    \"\"\"\n    ErrorMsgContent ::= SEQUENCE {\n         pKIStatusInfo          PKIStatusInfo,\n         errorCode              INTEGER           OPTIONAL,\n         -- implementation-specific error codes\n         errorDetails           PKIFreeText       OPTIONAL\n         -- implementation-specific error details\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('pKIStatusInfo', PKIStatusInfo()),\n        namedtype.OptionalNamedType('errorCode', univ.Integer()),\n        namedtype.OptionalNamedType('errorDetails', PKIFreeText())\n    )\n\n\nclass CertStatus(univ.Sequence):\n    \"\"\"\n    CertStatus ::= SEQUENCE {\n        certHash    OCTET STRING,\n        certReqId   INTEGER,\n        statusInfo  PKIStatusInfo OPTIONAL\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('certHash', univ.OctetString()),\n        namedtype.NamedType('certReqId', univ.Integer()),\n        namedtype.OptionalNamedType('statusInfo', PKIStatusInfo())\n    )\n\n\nclass CertConfirmContent(univ.SequenceOf):\n    componentType = CertStatus()\n\n\nclass RevAnnContent(univ.Sequence):\n    \"\"\"\n    RevAnnContent ::= SEQUENCE {\n         status              PKIStatus,\n         certId              CertId,\n         willBeRevokedAt     GeneralizedTime,\n         badSinceDate        GeneralizedTime,\n         crlDetails          Extensions  OPTIONAL\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('status', PKIStatus()),\n        namedtype.NamedType('certId', rfc2511.CertId()),\n        namedtype.NamedType('willBeRevokedAt', useful.GeneralizedTime()),\n        namedtype.NamedType('badSinceDate', useful.GeneralizedTime()),\n        namedtype.OptionalNamedType('crlDetails', rfc2459.Extensions())\n    )\n\n\nclass RevRepContent(univ.Sequence):\n    \"\"\"\n    RevRepContent ::= SEQUENCE {\n         status       SEQUENCE SIZE (1..MAX) OF PKIStatusInfo,\n         revCerts [0] SEQUENCE SIZE (1..MAX) OF CertId\n                                             OPTIONAL,\n         crls     [1] SEQUENCE SIZE (1..MAX) OF CertificateList\n                                             OPTIONAL\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType(\n            'status', univ.SequenceOf(\n                componentType=PKIStatusInfo(),\n                sizeSpec=constraint.ValueSizeConstraint(1, MAX)\n            )\n        ),\n        namedtype.OptionalNamedType(\n            'revCerts', univ.SequenceOf(componentType=rfc2511.CertId()).subtype(\n                sizeSpec=constraint.ValueSizeConstraint(1, MAX),\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)\n            )\n        ),\n        namedtype.OptionalNamedType(\n            'crls', univ.SequenceOf(componentType=rfc2459.CertificateList()).subtype(\n                sizeSpec=constraint.ValueSizeConstraint(1, MAX),\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)\n            )\n        )\n    )\n\n\nclass KeyRecRepContent(univ.Sequence):\n    \"\"\"\n    KeyRecRepContent ::= SEQUENCE {\n         status                  PKIStatusInfo,\n         newSigCert          [0] CMPCertificate OPTIONAL,\n         caCerts             [1] SEQUENCE SIZE (1..MAX) OF\n                                             CMPCertificate OPTIONAL,\n         keyPairHist         [2] SEQUENCE SIZE (1..MAX) OF\n                                             CertifiedKeyPair OPTIONAL\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('status', PKIStatusInfo()),\n        namedtype.OptionalNamedType(\n            'newSigCert', CMPCertificate().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)\n            )\n        ),\n        namedtype.OptionalNamedType(\n            'caCerts', univ.SequenceOf(componentType=CMPCertificate()).subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1),\n                sizeSpec=constraint.ValueSizeConstraint(1, MAX)\n            )\n        ),\n        namedtype.OptionalNamedType('keyPairHist', univ.SequenceOf(componentType=CertifiedKeyPair()).subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2),\n            sizeSpec=constraint.ValueSizeConstraint(1, MAX))\n        )\n    )\n\n\nclass CertResponse(univ.Sequence):\n    \"\"\"\n    CertResponse ::= SEQUENCE {\n         certReqId           INTEGER,\n         status              PKIStatusInfo,\n         certifiedKeyPair    CertifiedKeyPair    OPTIONAL,\n         rspInfo             OCTET STRING        OPTIONAL\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('certReqId', univ.Integer()),\n        namedtype.NamedType('status', PKIStatusInfo()),\n        namedtype.OptionalNamedType('certifiedKeyPair', CertifiedKeyPair()),\n        namedtype.OptionalNamedType('rspInfo', univ.OctetString())\n    )\n\n\nclass CertRepMessage(univ.Sequence):\n    \"\"\"\n    CertRepMessage ::= SEQUENCE {\n         caPubs       [1] SEQUENCE SIZE (1..MAX) OF CMPCertificate\n                          OPTIONAL,\n         response         SEQUENCE OF CertResponse\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType(\n            'caPubs', univ.SequenceOf(\n                componentType=CMPCertificate()\n            ).subtype(sizeSpec=constraint.ValueSizeConstraint(1, MAX),\n                      explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))\n        ),\n        namedtype.NamedType('response', univ.SequenceOf(componentType=CertResponse()))\n    )\n\n\nclass POPODecKeyChallContent(univ.SequenceOf):\n    componentType = Challenge()\n\n\nclass OOBCertHash(univ.Sequence):\n    \"\"\"\n    OOBCertHash ::= SEQUENCE {\n         hashAlg     [0] AlgorithmIdentifier     OPTIONAL,\n         certId      [1] CertId                  OPTIONAL,\n         hashVal         BIT STRING\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.OptionalNamedType(\n            'hashAlg', rfc2459.AlgorithmIdentifier().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))\n        ),\n        namedtype.OptionalNamedType(\n            'certId', rfc2511.CertId().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))\n        ),\n        namedtype.NamedType('hashVal', univ.BitString())\n    )\n\n\n# pyasn1 does not naturally handle recursive definitions, thus this hack:\n# NestedMessageContent ::= PKIMessages\nclass NestedMessageContent(univ.SequenceOf):\n    \"\"\"\n    NestedMessageContent ::= PKIMessages\n    \"\"\"\n    componentType = univ.Any()\n\n\nclass DHBMParameter(univ.Sequence):\n    \"\"\"\n    DHBMParameter ::= SEQUENCE {\n         owf                 AlgorithmIdentifier,\n         -- AlgId for a One-Way Function (SHA-1 recommended)\n         mac                 AlgorithmIdentifier\n         -- the MAC AlgId (e.g., DES-MAC, Triple-DES-MAC [PKCS11],\n     }   -- or HMAC [RFC2104, RFC2202])\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('owf', rfc2459.AlgorithmIdentifier()),\n        namedtype.NamedType('mac', rfc2459.AlgorithmIdentifier())\n    )\n\n\nid_DHBasedMac = univ.ObjectIdentifier('1.2.840.113533.7.66.30')\n\n\nclass PBMParameter(univ.Sequence):\n    \"\"\"\n    PBMParameter ::= SEQUENCE {\n         salt                OCTET STRING,\n         owf                 AlgorithmIdentifier,\n         iterationCount      INTEGER,\n         mac                 AlgorithmIdentifier\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType(\n            'salt', univ.OctetString().subtype(subtypeSpec=constraint.ValueSizeConstraint(0, 128))\n        ),\n        namedtype.NamedType('owf', rfc2459.AlgorithmIdentifier()),\n        namedtype.NamedType('iterationCount', univ.Integer()),\n        namedtype.NamedType('mac', rfc2459.AlgorithmIdentifier())\n    )\n\n\nid_PasswordBasedMac = univ.ObjectIdentifier('1.2.840.113533.7.66.13')\n\n\nclass PKIProtection(univ.BitString):\n    pass\n\n\n# pyasn1 does not naturally handle recursive definitions, thus this hack:\n# NestedMessageContent ::= PKIMessages\nnestedMessageContent = NestedMessageContent().subtype(\n    explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 20))\n\n\nclass PKIBody(univ.Choice):\n    \"\"\"\n    PKIBody ::= CHOICE {       -- message-specific body elements\n         ir       [0]  CertReqMessages,        --Initialization Request\n         ip       [1]  CertRepMessage,         --Initialization Response\n         cr       [2]  CertReqMessages,        --Certification Request\n         cp       [3]  CertRepMessage,         --Certification Response\n         p10cr    [4]  CertificationRequest,   --imported from [PKCS10]\n         popdecc  [5]  POPODecKeyChallContent, --pop Challenge\n         popdecr  [6]  POPODecKeyRespContent,  --pop Response\n         kur      [7]  CertReqMessages,        --Key Update Request\n         kup      [8]  CertRepMessage,         --Key Update Response\n         krr      [9]  CertReqMessages,        --Key Recovery Request\n         krp      [10] KeyRecRepContent,       --Key Recovery Response\n         rr       [11] RevReqContent,          --Revocation Request\n         rp       [12] RevRepContent,          --Revocation Response\n         ccr      [13] CertReqMessages,        --Cross-Cert. Request\n         ccp      [14] CertRepMessage,         --Cross-Cert. Response\n         ckuann   [15] CAKeyUpdAnnContent,     --CA Key Update Ann.\n         cann     [16] CertAnnContent,         --Certificate Ann.\n         rann     [17] RevAnnContent,          --Revocation Ann.\n         crlann   [18] CRLAnnContent,          --CRL Announcement\n         pkiconf  [19] PKIConfirmContent,      --Confirmation\n         nested   [20] NestedMessageContent,   --Nested Message\n         genm     [21] GenMsgContent,          --General Message\n         genp     [22] GenRepContent,          --General Response\n         error    [23] ErrorMsgContent,        --Error Message\n         certConf [24] CertConfirmContent,     --Certificate confirm\n         pollReq  [25] PollReqContent,         --Polling request\n         pollRep  [26] PollRepContent          --Polling response\n\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType(\n            'ir', rfc2511.CertReqMessages().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)\n            )\n        ),\n        namedtype.NamedType(\n            'ip', CertRepMessage().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)\n            )\n        ),\n        namedtype.NamedType(\n            'cr', rfc2511.CertReqMessages().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2)\n            )\n        ),\n        namedtype.NamedType(\n            'cp', CertRepMessage().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3)\n            )\n        ),\n        namedtype.NamedType(\n            'p10cr', rfc2314.CertificationRequest().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 4)\n            )\n        ),\n        namedtype.NamedType(\n            'popdecc', POPODecKeyChallContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 5)\n            )\n        ),\n        namedtype.NamedType(\n            'popdecr', POPODecKeyRespContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 6)\n            )\n        ),\n        namedtype.NamedType(\n            'kur', rfc2511.CertReqMessages().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 7)\n            )\n        ),\n        namedtype.NamedType(\n            'kup', CertRepMessage().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 8)\n            )\n        ),\n        namedtype.NamedType(\n            'krr', rfc2511.CertReqMessages().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 9)\n            )\n        ),\n        namedtype.NamedType(\n            'krp', KeyRecRepContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 10)\n            )\n        ),\n        namedtype.NamedType(\n            'rr', RevReqContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 11)\n            )\n        ),\n        namedtype.NamedType(\n            'rp', RevRepContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 12)\n            )\n        ),\n        namedtype.NamedType(\n            'ccr', rfc2511.CertReqMessages().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 13)\n            )\n        ),\n        namedtype.NamedType(\n            'ccp', CertRepMessage().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 14)\n            )\n        ),\n        namedtype.NamedType(\n            'ckuann', CAKeyUpdAnnContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 15)\n            )\n        ),\n        namedtype.NamedType(\n            'cann', CertAnnContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 16)\n            )\n        ),\n        namedtype.NamedType(\n            'rann', RevAnnContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 17)\n            )\n        ),\n        namedtype.NamedType(\n            'crlann', CRLAnnContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 18)\n            )\n        ),\n        namedtype.NamedType(\n            'pkiconf', PKIConfirmContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 19)\n            )\n        ),\n        namedtype.NamedType(\n            'nested', nestedMessageContent\n        ),\n        #        namedtype.NamedType('nested', NestedMessageContent().subtype(\n        #            explicitTag=tag.Tag(tag.tagClassContext,tag.tagFormatConstructed,20)\n        #            )\n        #        ),\n        namedtype.NamedType(\n            'genm', GenMsgContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 21)\n            )\n        ),\n        namedtype.NamedType(\n            'gen', GenRepContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 22)\n            )\n        ),\n        namedtype.NamedType(\n            'error', ErrorMsgContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 23)\n            )\n        ),\n        namedtype.NamedType(\n            'certConf', CertConfirmContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 24)\n            )\n        ),\n        namedtype.NamedType(\n            'pollReq', PollReqContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 25)\n            )\n        ),\n        namedtype.NamedType(\n            'pollRep', PollRepContent().subtype(\n                explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 26)\n            )\n        )\n    )\n\n\nclass PKIHeader(univ.Sequence):\n    \"\"\"\n    PKIHeader ::= SEQUENCE {\n    pvno                INTEGER     { cmp1999(1), cmp2000(2) },\n    sender              GeneralName,\n    recipient           GeneralName,\n    messageTime     [0] GeneralizedTime         OPTIONAL,\n    protectionAlg   [1] AlgorithmIdentifier     OPTIONAL,\n    senderKID       [2] KeyIdentifier           OPTIONAL,\n    recipKID        [3] KeyIdentifier           OPTIONAL,\n    transactionID   [4] OCTET STRING            OPTIONAL,\n    senderNonce     [5] OCTET STRING            OPTIONAL,\n    recipNonce      [6] OCTET STRING            OPTIONAL,\n    freeText        [7] PKIFreeText             OPTIONAL,\n    generalInfo     [8] SEQUENCE SIZE (1..MAX) OF\n                     InfoTypeAndValue     OPTIONAL\n    }\n\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType(\n            'pvno', univ.Integer(\n                namedValues=namedval.NamedValues(('cmp1999', 1), ('cmp2000', 2))\n            )\n        ),\n        namedtype.NamedType('sender', rfc2459.GeneralName()),\n        namedtype.NamedType('recipient', rfc2459.GeneralName()),\n        namedtype.OptionalNamedType('messageTime', useful.GeneralizedTime().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('protectionAlg', rfc2459.AlgorithmIdentifier().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n        namedtype.OptionalNamedType('senderKID', rfc2459.KeyIdentifier().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n        namedtype.OptionalNamedType('recipKID', rfc2459.KeyIdentifier().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n        namedtype.OptionalNamedType('transactionID', univ.OctetString().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4))),\n        namedtype.OptionalNamedType('senderNonce', univ.OctetString().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 5))),\n        namedtype.OptionalNamedType('recipNonce', univ.OctetString().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 6))),\n        namedtype.OptionalNamedType('freeText', PKIFreeText().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 7))),\n        namedtype.OptionalNamedType('generalInfo',\n                                    univ.SequenceOf(\n                                        componentType=InfoTypeAndValue().subtype(\n                                            sizeSpec=constraint.ValueSizeConstraint(1, MAX),\n                                            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 8)\n                                        )\n                                    )\n                                    )\n    )\n\n\nclass ProtectedPart(univ.Sequence):\n    \"\"\"\n     ProtectedPart ::= SEQUENCE {\n         header    PKIHeader,\n         body      PKIBody\n     }\n    \"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('header', PKIHeader()),\n        namedtype.NamedType('infoValue', PKIBody())\n    )\n\n\nclass PKIMessage(univ.Sequence):\n    \"\"\"\n    PKIMessage ::= SEQUENCE {\n    header           PKIHeader,\n    body             PKIBody,\n    protection   [0] PKIProtection OPTIONAL,\n    extraCerts   [1] SEQUENCE SIZE (1..MAX) OF CMPCertificate\n                  OPTIONAL\n     }\"\"\"\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('header', PKIHeader()),\n        namedtype.NamedType('body', PKIBody()),\n        namedtype.OptionalNamedType('protection', PKIProtection().subtype(\n            explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.OptionalNamedType('extraCerts',\n                                    univ.SequenceOf(\n                                        componentType=CMPCertificate()\n                                    ).subtype(\n                                        sizeSpec=constraint.ValueSizeConstraint(1, MAX),\n                                        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)\n                                    )\n                                    )\n    )\n\n\nclass PKIMessages(univ.SequenceOf):\n    \"\"\"\n    PKIMessages ::= SEQUENCE SIZE (1..MAX) OF PKIMessage\n    \"\"\"\n    componentType = PKIMessage()\n    sizeSpec = univ.SequenceOf.sizeSpec + constraint.ValueSizeConstraint(1, MAX)\n\n\n# pyasn1 does not naturally handle recursive definitions, thus this hack:\n# NestedMessageContent ::= PKIMessages\nNestedMessageContent._componentType = PKIMessages()\nnestedMessageContent._componentType = PKIMessages()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc4211.py",
    "content": "# coding: utf-8\n#\n# This file is part of pyasn1-modules software.\n#\n# Created by Stanisław Pitucha with asn1ate tool.\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Internet X.509 Public Key Infrastructure Certificate Request\n# Message Format (CRMF)\n#\n# ASN.1 source from:\n# http://www.ietf.org/rfc/rfc4211.txt\n#\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc3280\nfrom pyasn1_modules import rfc3852\n\nMAX = float('inf')\n\n\ndef _buildOid(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\nid_pkix = _buildOid(1, 3, 6, 1, 5, 5, 7)\n\nid_pkip = _buildOid(id_pkix, 5)\n\nid_regCtrl = _buildOid(id_pkip, 1)\n\n\nclass SinglePubInfo(univ.Sequence):\n    pass\n\n\nSinglePubInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('pubMethod', univ.Integer(\n        namedValues=namedval.NamedValues(('dontCare', 0), ('x500', 1), ('web', 2), ('ldap', 3)))),\n    namedtype.OptionalNamedType('pubLocation', rfc3280.GeneralName())\n)\n\n\nclass UTF8Pairs(char.UTF8String):\n    pass\n\n\nclass PKMACValue(univ.Sequence):\n    pass\n\n\nPKMACValue.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('algId', rfc3280.AlgorithmIdentifier()),\n    namedtype.NamedType('value', univ.BitString())\n)\n\n\nclass POPOSigningKeyInput(univ.Sequence):\n    pass\n\n\nPOPOSigningKeyInput.componentType = namedtype.NamedTypes(\n    namedtype.NamedType(\n        'authInfo', univ.Choice(\n            componentType=namedtype.NamedTypes(\n                namedtype.NamedType(\n                    'sender', rfc3280.GeneralName().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))\n                ),\n                namedtype.NamedType(\n                    'publicKeyMAC', PKMACValue()\n                )\n            )\n        )\n    ),\n    namedtype.NamedType('publicKey', rfc3280.SubjectPublicKeyInfo())\n)\n\n\nclass POPOSigningKey(univ.Sequence):\n    pass\n\n\nPOPOSigningKey.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('poposkInput', POPOSigningKeyInput().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('algorithmIdentifier', rfc3280.AlgorithmIdentifier()),\n    namedtype.NamedType('signature', univ.BitString())\n)\n\n\nclass Attributes(univ.SetOf):\n    pass\n\n\nAttributes.componentType = rfc3280.Attribute()\n\n\nclass PrivateKeyInfo(univ.Sequence):\n    pass\n\n\nPrivateKeyInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', univ.Integer()),\n    namedtype.NamedType('privateKeyAlgorithm', rfc3280.AlgorithmIdentifier()),\n    namedtype.NamedType('privateKey', univ.OctetString()),\n    namedtype.OptionalNamedType('attributes',\n                                Attributes().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass EncryptedValue(univ.Sequence):\n    pass\n\n\nEncryptedValue.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('intendedAlg', rfc3280.AlgorithmIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('symmAlg', rfc3280.AlgorithmIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('encSymmKey', univ.BitString().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.OptionalNamedType('keyAlg', rfc3280.AlgorithmIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n    namedtype.OptionalNamedType('valueHint', univ.OctetString().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4))),\n    namedtype.NamedType('encValue', univ.BitString())\n)\n\n\nclass EncryptedKey(univ.Choice):\n    pass\n\n\nEncryptedKey.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('encryptedValue', EncryptedValue()),\n    namedtype.NamedType('envelopedData', rfc3852.EnvelopedData().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass KeyGenParameters(univ.OctetString):\n    pass\n\n\nclass PKIArchiveOptions(univ.Choice):\n    pass\n\n\nPKIArchiveOptions.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('encryptedPrivKey',\n                        EncryptedKey().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('keyGenParameters',\n                        KeyGenParameters().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('archiveRemGenPrivKey',\n                        univ.Boolean().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\nid_regCtrl_authenticator = _buildOid(id_regCtrl, 2)\n\nid_regInfo = _buildOid(id_pkip, 2)\n\nid_regInfo_certReq = _buildOid(id_regInfo, 2)\n\n\nclass ProtocolEncrKey(rfc3280.SubjectPublicKeyInfo):\n    pass\n\n\nclass Authenticator(char.UTF8String):\n    pass\n\n\nclass SubsequentMessage(univ.Integer):\n    pass\n\n\nSubsequentMessage.namedValues = namedval.NamedValues(\n    ('encrCert', 0),\n    ('challengeResp', 1)\n)\n\n\nclass AttributeTypeAndValue(univ.Sequence):\n    pass\n\n\nAttributeTypeAndValue.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('type', univ.ObjectIdentifier()),\n    namedtype.NamedType('value', univ.Any())\n)\n\n\nclass POPOPrivKey(univ.Choice):\n    pass\n\n\nPOPOPrivKey.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('thisMessage',\n                        univ.BitString().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('subsequentMessage',\n                        SubsequentMessage().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('dhMAC',\n                        univ.BitString().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.NamedType('agreeMAC',\n                        PKMACValue().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3))),\n    namedtype.NamedType('encryptedKey', rfc3852.EnvelopedData().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4)))\n)\n\n\nclass ProofOfPossession(univ.Choice):\n    pass\n\n\nProofOfPossession.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('raVerified',\n                        univ.Null().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('signature', POPOSigningKey().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n    namedtype.NamedType('keyEncipherment',\n                        POPOPrivKey().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2))),\n    namedtype.NamedType('keyAgreement',\n                        POPOPrivKey().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3)))\n)\n\n\nclass OptionalValidity(univ.Sequence):\n    pass\n\n\nOptionalValidity.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('notBefore', rfc3280.Time().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.OptionalNamedType('notAfter', rfc3280.Time().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n)\n\n\nclass CertTemplate(univ.Sequence):\n    pass\n\n\nCertTemplate.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('version', rfc3280.Version().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('serialNumber', univ.Integer().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('signingAlg', rfc3280.AlgorithmIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.OptionalNamedType('issuer', rfc3280.Name().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3))),\n    namedtype.OptionalNamedType('validity', OptionalValidity().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 4))),\n    namedtype.OptionalNamedType('subject', rfc3280.Name().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 5))),\n    namedtype.OptionalNamedType('publicKey', rfc3280.SubjectPublicKeyInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 6))),\n    namedtype.OptionalNamedType('issuerUID', rfc3280.UniqueIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 7))),\n    namedtype.OptionalNamedType('subjectUID', rfc3280.UniqueIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 8))),\n    namedtype.OptionalNamedType('extensions', rfc3280.Extensions().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 9)))\n)\n\n\nclass Controls(univ.SequenceOf):\n    pass\n\n\nControls.componentType = AttributeTypeAndValue()\nControls.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass CertRequest(univ.Sequence):\n    pass\n\n\nCertRequest.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('certReqId', univ.Integer()),\n    namedtype.NamedType('certTemplate', CertTemplate()),\n    namedtype.OptionalNamedType('controls', Controls())\n)\n\n\nclass CertReqMsg(univ.Sequence):\n    pass\n\n\nCertReqMsg.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('certReq', CertRequest()),\n    namedtype.OptionalNamedType('popo', ProofOfPossession()),\n    namedtype.OptionalNamedType('regInfo', univ.SequenceOf(componentType=AttributeTypeAndValue()))\n)\n\n\nclass CertReqMessages(univ.SequenceOf):\n    pass\n\n\nCertReqMessages.componentType = CertReqMsg()\nCertReqMessages.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass CertReq(CertRequest):\n    pass\n\n\nid_regCtrl_pkiPublicationInfo = _buildOid(id_regCtrl, 3)\n\n\nclass CertId(univ.Sequence):\n    pass\n\n\nCertId.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuer', rfc3280.GeneralName()),\n    namedtype.NamedType('serialNumber', univ.Integer())\n)\n\n\nclass OldCertId(CertId):\n    pass\n\n\nclass PKIPublicationInfo(univ.Sequence):\n    pass\n\n\nPKIPublicationInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('action',\n                        univ.Integer(namedValues=namedval.NamedValues(('dontPublish', 0), ('pleasePublish', 1)))),\n    namedtype.OptionalNamedType('pubInfos', univ.SequenceOf(componentType=SinglePubInfo()))\n)\n\n\nclass EncKeyWithID(univ.Sequence):\n    pass\n\n\nEncKeyWithID.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('privateKey', PrivateKeyInfo()),\n    namedtype.OptionalNamedType(\n        'identifier', univ.Choice(\n            componentType=namedtype.NamedTypes(\n                namedtype.NamedType('string', char.UTF8String()),\n                namedtype.NamedType('generalName', rfc3280.GeneralName())\n            )\n        )\n    )\n)\n\nid_regCtrl_protocolEncrKey = _buildOid(id_regCtrl, 6)\n\nid_regCtrl_oldCertID = _buildOid(id_regCtrl, 5)\n\nid_smime = _buildOid(1, 2, 840, 113549, 1, 9, 16)\n\n\nclass PBMParameter(univ.Sequence):\n    pass\n\n\nPBMParameter.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('salt', univ.OctetString()),\n    namedtype.NamedType('owf', rfc3280.AlgorithmIdentifier()),\n    namedtype.NamedType('iterationCount', univ.Integer()),\n    namedtype.NamedType('mac', rfc3280.AlgorithmIdentifier())\n)\n\nid_regCtrl_regToken = _buildOid(id_regCtrl, 1)\n\nid_regCtrl_pkiArchiveOptions = _buildOid(id_regCtrl, 4)\n\nid_regInfo_utf8Pairs = _buildOid(id_regInfo, 1)\n\nid_ct = _buildOid(id_smime, 1)\n\nid_ct_encKeyWithID = _buildOid(id_ct, 21)\n\n\nclass RegToken(char.UTF8String):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5035.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n# Modified by Russ Housley to add a map for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Update to Enhanced Security Services for S/MIME\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5035.txt\n#\n\nfrom pyasn1.codec.der.encoder import encode as der_encode\n\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc2634\nfrom pyasn1_modules import rfc4055\nfrom pyasn1_modules import rfc5652\nfrom pyasn1_modules import rfc5280\n\nContentType = rfc5652.ContentType\n\nIssuerAndSerialNumber = rfc5652.IssuerAndSerialNumber\n\nSubjectKeyIdentifier = rfc5652.SubjectKeyIdentifier\n\nAlgorithmIdentifier = rfc5280.AlgorithmIdentifier\n\nPolicyInformation = rfc5280.PolicyInformation\n\nGeneralNames = rfc5280.GeneralNames\n\nCertificateSerialNumber = rfc5280.CertificateSerialNumber\n\n\n# Signing Certificate Attribute V1 and V2\n\nid_aa_signingCertificate = rfc2634.id_aa_signingCertificate\n\nid_aa_signingCertificateV2 = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.47')\n\nHash = rfc2634.Hash\n\nIssuerSerial = rfc2634.IssuerSerial\n\nESSCertID = rfc2634.ESSCertID\n\nSigningCertificate = rfc2634.SigningCertificate\n\n\nsha256AlgId = AlgorithmIdentifier()\nsha256AlgId['algorithm'] = rfc4055.id_sha256\n# A non-schema object for sha256AlgId['parameters'] as absent\nsha256AlgId['parameters'] = der_encode(univ.OctetString(''))\n\n\nclass ESSCertIDv2(univ.Sequence):\n    pass\n\nESSCertIDv2.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('hashAlgorithm', sha256AlgId),\n    namedtype.NamedType('certHash', Hash()),\n    namedtype.OptionalNamedType('issuerSerial', IssuerSerial())\n)\n\n\nclass SigningCertificateV2(univ.Sequence):\n    pass\n\nSigningCertificateV2.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('certs', univ.SequenceOf(\n        componentType=ESSCertIDv2())),\n    namedtype.OptionalNamedType('policies', univ.SequenceOf(\n        componentType=PolicyInformation()))\n)\n\n\n# Mail List Expansion History Attribute\n\nid_aa_mlExpandHistory = rfc2634.id_aa_mlExpandHistory\n\nub_ml_expansion_history = rfc2634.ub_ml_expansion_history\n\nEntityIdentifier = rfc2634.EntityIdentifier\n\nMLReceiptPolicy = rfc2634.MLReceiptPolicy\n\nMLData = rfc2634.MLData\n\nMLExpansionHistory = rfc2634.MLExpansionHistory\n\n\n# ESS Security Label Attribute\n\nid_aa_securityLabel = rfc2634.id_aa_securityLabel\n\nub_privacy_mark_length = rfc2634.ub_privacy_mark_length\n\nub_security_categories = rfc2634.ub_security_categories\n\nub_integer_options = rfc2634.ub_integer_options\n\nESSPrivacyMark = rfc2634.ESSPrivacyMark\n\nSecurityClassification = rfc2634.SecurityClassification\n\nSecurityPolicyIdentifier = rfc2634.SecurityPolicyIdentifier\n\nSecurityCategory = rfc2634.SecurityCategory\n\nSecurityCategories = rfc2634.SecurityCategories\n\nESSSecurityLabel = rfc2634.ESSSecurityLabel\n\n\n# Equivalent Labels Attribute\n\nid_aa_equivalentLabels = rfc2634.id_aa_equivalentLabels\n\nEquivalentLabels = rfc2634.EquivalentLabels\n\n\n# Content Identifier Attribute\n\nid_aa_contentIdentifier = rfc2634.id_aa_contentIdentifier\n\nContentIdentifier = rfc2634.ContentIdentifier\n\n\n# Content Reference Attribute\n\nid_aa_contentReference = rfc2634.id_aa_contentReference\n\nContentReference = rfc2634.ContentReference\n\n\n# Message Signature Digest Attribute\n\nid_aa_msgSigDigest = rfc2634.id_aa_msgSigDigest\n\nMsgSigDigest = rfc2634.MsgSigDigest\n\n\n# Content Hints Attribute\n\nid_aa_contentHint = rfc2634.id_aa_contentHint\n\nContentHints = rfc2634.ContentHints\n\n\n# Receipt Request Attribute\n\nAllOrFirstTier = rfc2634.AllOrFirstTier\n\nReceiptsFrom = rfc2634.ReceiptsFrom\n\nid_aa_receiptRequest = rfc2634.id_aa_receiptRequest\n\nub_receiptsTo = rfc2634.ub_receiptsTo\n\nReceiptRequest = rfc2634.ReceiptRequest\n\n\n# Receipt Content Type\n\nESSVersion = rfc2634.ESSVersion\n\nid_ct_receipt = rfc2634.id_ct_receipt\n\nReceipt = rfc2634.Receipt\n\nub_receiptsTo = rfc2634.ub_receiptsTo\n\nReceiptRequest = rfc2634.ReceiptRequest\n\n\n# Map of Attribute Type to the Attribute structure is added to the\n# ones that are in rfc5652.py\n\n_cmsAttributesMapUpdate = {\n    id_aa_signingCertificateV2: SigningCertificateV2(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n\n\n# Map of Content Type OIDs to Content Types is added to the\n# ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_receipt: Receipt(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5083.py",
    "content": "# This file is being contributed to of pyasn1-modules software.\n#\n# Created by Russ Housley without assistance from the asn1ate tool.\n# Modified by Russ Housley to add a map for use with opentypes and\n#   simplify the code for the object identifier assignment.\n#\n# Copyright (c) 2018, 2019 Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n#  Authenticated-Enveloped-Data for the Cryptographic Message Syntax (CMS)\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5083.txt\n\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5652\n\nMAX = float('inf')\n\n\n# CMS Authenticated-Enveloped-Data Content Type\n\nid_ct_authEnvelopedData = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.23')\n\nclass AuthEnvelopedData(univ.Sequence):\n    pass\n\nAuthEnvelopedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', rfc5652.CMSVersion()),\n    namedtype.OptionalNamedType('originatorInfo', rfc5652.OriginatorInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('recipientInfos', rfc5652.RecipientInfos()),\n    namedtype.NamedType('authEncryptedContentInfo', rfc5652.EncryptedContentInfo()),\n    namedtype.OptionalNamedType('authAttrs', rfc5652.AuthAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('mac', rfc5652.MessageAuthenticationCode()),\n    namedtype.OptionalNamedType('unauthAttrs', rfc5652.UnauthAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\n\n# Map of Content Type OIDs to Content Types is added to the\n# ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_authEnvelopedData: AuthEnvelopedData(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5084.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from the asn1ate tool, with manual\n#   changes to AES_CCM_ICVlen.subtypeSpec and added comments\n#\n# Copyright (c) 2018-2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n#  AES-CCM and AES-GCM Algorithms fo use with the Authenticated-Enveloped-Data\n#  protecting content type for the Cryptographic Message Syntax (CMS)\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5084.txt\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\nclass AES_CCM_ICVlen(univ.Integer):\n    pass\n\n\nclass AES_GCM_ICVlen(univ.Integer):\n    pass\n\n\nAES_CCM_ICVlen.subtypeSpec = constraint.SingleValueConstraint(4, 6, 8, 10, 12, 14, 16)\n\nAES_GCM_ICVlen.subtypeSpec = constraint.ValueRangeConstraint(12, 16)\n\n\nclass CCMParameters(univ.Sequence):\n    pass\n\n\nCCMParameters.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('aes-nonce', univ.OctetString().subtype(subtypeSpec=constraint.ValueSizeConstraint(7, 13))),\n    # The aes-nonce parameter contains 15-L octets, where L is the size of the length field. L=8 is RECOMMENDED.\n    # Within the scope of any content-authenticated-encryption key, the nonce value MUST be unique.\n    namedtype.DefaultedNamedType('aes-ICVlen', AES_CCM_ICVlen().subtype(value=12))\n)\n\n\nclass GCMParameters(univ.Sequence):\n    pass\n\n\nGCMParameters.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('aes-nonce', univ.OctetString()),\n    # The aes-nonce may have any number of bits between 8 and 2^64, but it MUST be a multiple of 8 bits.\n    # Within the scope of any content-authenticated-encryption key, the nonce value MUST be unique.\n    # A nonce value of 12 octets can be processed more efficiently, so that length is RECOMMENDED.\n    namedtype.DefaultedNamedType('aes-ICVlen', AES_GCM_ICVlen().subtype(value=12))\n)\n\naes = _OID(2, 16, 840, 1, 101, 3, 4, 1)\n\nid_aes128_CCM = _OID(aes, 7)\n\nid_aes128_GCM = _OID(aes, 6)\n\nid_aes192_CCM = _OID(aes, 27)\n\nid_aes192_GCM = _OID(aes, 26)\n\nid_aes256_CCM = _OID(aes, 47)\n\nid_aes256_GCM = _OID(aes, 46)\n\n\n# Map of Algorithm Identifier OIDs to Parameters is added to the\n# ones in rfc5280.py\n\n_algorithmIdentifierMapUpdate = {\n    id_aes128_CCM: CCMParameters(),\n    id_aes128_GCM: GCMParameters(),\n    id_aes192_CCM: CCMParameters(),\n    id_aes192_GCM: GCMParameters(),\n    id_aes256_CCM: CCMParameters(),\n    id_aes256_GCM: GCMParameters(),\n}\n\nrfc5280.algorithmIdentifierMap.update(_algorithmIdentifierMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5208.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# PKCS#8 syntax\n#\n# ASN.1 source from:\n# http://tools.ietf.org/html/rfc5208\n#\n# Sample captures could be obtained with \"openssl pkcs8 -topk8\" command\n#\nfrom pyasn1_modules import rfc2251\nfrom pyasn1_modules.rfc2459 import *\n\n\nclass KeyEncryptionAlgorithms(AlgorithmIdentifier):\n    pass\n\n\nclass PrivateKeyAlgorithms(AlgorithmIdentifier):\n    pass\n\n\nclass EncryptedData(univ.OctetString):\n    pass\n\n\nclass EncryptedPrivateKeyInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('encryptionAlgorithm', AlgorithmIdentifier()),\n        namedtype.NamedType('encryptedData', EncryptedData())\n    )\n\n\nclass PrivateKey(univ.OctetString):\n    pass\n\n\nclass Attributes(univ.SetOf):\n    componentType = rfc2251.Attribute()\n\n\nclass Version(univ.Integer):\n    namedValues = namedval.NamedValues(('v1', 0), ('v2', 1))\n\n\nclass PrivateKeyInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.NamedType('privateKeyAlgorithm', AlgorithmIdentifier()),\n        namedtype.NamedType('privateKey', PrivateKey()),\n        namedtype.OptionalNamedType('attributes', Attributes().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5280.py",
    "content": "# coding: utf-8\n#\n# This file is part of pyasn1-modules software.\n#\n# Created by Stanisław Pitucha with asn1ate tool.\n# Updated by Russ Housley for ORAddress Extension Attribute opentype support.\n# Updated by Russ Housley for AlgorithmIdentifier opentype support.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Internet X.509 Public Key Infrastructure Certificate and Certificate\n# Revocation List (CRL) Profile\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5280.txt\n#\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import opentype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nMAX = float('inf')\n\n\ndef _buildOid(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\nub_e163_4_sub_address_length = univ.Integer(40)\n\nub_e163_4_number_length = univ.Integer(15)\n\nunformatted_postal_address = univ.Integer(16)\n\n\nclass TerminalType(univ.Integer):\n    pass\n\n\nTerminalType.namedValues = namedval.NamedValues(\n    ('telex', 3),\n    ('teletex', 4),\n    ('g3-facsimile', 5),\n    ('g4-facsimile', 6),\n    ('ia5-terminal', 7),\n    ('videotex', 8)\n)\n\n\nclass Extension(univ.Sequence):\n    pass\n\n\nExtension.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('extnID', univ.ObjectIdentifier()),\n    namedtype.DefaultedNamedType('critical', univ.Boolean().subtype(value=0)),\n    namedtype.NamedType('extnValue', univ.OctetString())\n)\n\n\nclass Extensions(univ.SequenceOf):\n    pass\n\n\nExtensions.componentType = Extension()\nExtensions.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\nphysical_delivery_personal_name = univ.Integer(13)\n\nub_unformatted_address_length = univ.Integer(180)\n\nub_pds_parameter_length = univ.Integer(30)\n\nub_pds_physical_address_lines = univ.Integer(6)\n\n\nclass UnformattedPostalAddress(univ.Set):\n    pass\n\n\nUnformattedPostalAddress.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('printable-address', univ.SequenceOf(componentType=char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_pds_parameter_length)))),\n    namedtype.OptionalNamedType('teletex-string', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_unformatted_address_length)))\n)\n\nub_organization_name = univ.Integer(64)\n\n\nclass X520OrganizationName(univ.Choice):\n    pass\n\n\nX520OrganizationName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name))),\n    namedtype.NamedType('printableString', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name))),\n    namedtype.NamedType('universalString', char.UniversalString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name))),\n    namedtype.NamedType('bmpString',\n                        char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_organization_name)))\n)\n\nub_x121_address_length = univ.Integer(16)\n\npds_name = univ.Integer(7)\n\nid_pkix = _buildOid(1, 3, 6, 1, 5, 5, 7)\n\nid_kp = _buildOid(id_pkix, 3)\n\nub_postal_code_length = univ.Integer(16)\n\n\nclass PostalCode(univ.Choice):\n    pass\n\n\nPostalCode.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('numeric-code', char.NumericString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_postal_code_length))),\n    namedtype.NamedType('printable-code', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_postal_code_length)))\n)\n\nub_generation_qualifier_length = univ.Integer(3)\n\nunique_postal_name = univ.Integer(20)\n\n\nclass DomainComponent(char.IA5String):\n    pass\n\n\nub_domain_defined_attribute_value_length = univ.Integer(128)\n\nub_match = univ.Integer(128)\n\nid_at = _buildOid(2, 5, 4)\n\n\nclass AttributeType(univ.ObjectIdentifier):\n    pass\n\n\nid_at_organizationalUnitName = _buildOid(id_at, 11)\n\nterminal_type = univ.Integer(23)\n\n\nclass PDSParameter(univ.Set):\n    pass\n\n\nPDSParameter.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('printable-string', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_pds_parameter_length))),\n    namedtype.OptionalNamedType('teletex-string', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_pds_parameter_length)))\n)\n\n\nclass PhysicalDeliveryPersonalName(PDSParameter):\n    pass\n\n\nub_surname_length = univ.Integer(40)\n\nid_ad = _buildOid(id_pkix, 48)\n\nub_domain_defined_attribute_type_length = univ.Integer(8)\n\n\nclass TeletexDomainDefinedAttribute(univ.Sequence):\n    pass\n\n\nTeletexDomainDefinedAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('type', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_defined_attribute_type_length))),\n    namedtype.NamedType('value', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_defined_attribute_value_length)))\n)\n\nub_domain_defined_attributes = univ.Integer(4)\n\n\nclass TeletexDomainDefinedAttributes(univ.SequenceOf):\n    pass\n\n\nTeletexDomainDefinedAttributes.componentType = TeletexDomainDefinedAttribute()\nTeletexDomainDefinedAttributes.sizeSpec = constraint.ValueSizeConstraint(1, ub_domain_defined_attributes)\n\nextended_network_address = univ.Integer(22)\n\nub_locality_name = univ.Integer(128)\n\n\nclass X520LocalityName(univ.Choice):\n    pass\n\n\nX520LocalityName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name))),\n    namedtype.NamedType('printableString', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name))),\n    namedtype.NamedType('universalString', char.UniversalString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name))),\n    namedtype.NamedType('bmpString',\n                        char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_locality_name)))\n)\n\nteletex_organization_name = univ.Integer(3)\n\nub_given_name_length = univ.Integer(16)\n\nub_initials_length = univ.Integer(5)\n\n\nclass PersonalName(univ.Set):\n    pass\n\n\nPersonalName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('surname', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_surname_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('given-name', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_given_name_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('initials', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_initials_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.OptionalNamedType('generation-qualifier', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_generation_qualifier_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\nub_organizational_unit_name_length = univ.Integer(32)\n\n\nclass OrganizationalUnitName(char.PrintableString):\n    pass\n\n\nOrganizationalUnitName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_organizational_unit_name_length)\n\nid_at_generationQualifier = _buildOid(id_at, 44)\n\n\nclass Version(univ.Integer):\n    pass\n\n\nVersion.namedValues = namedval.NamedValues(\n    ('v1', 0),\n    ('v2', 1),\n    ('v3', 2)\n)\n\n\nclass CertificateSerialNumber(univ.Integer):\n    pass\n\n\nalgorithmIdentifierMap = {}\n\n\nclass AlgorithmIdentifier(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('algorithm', univ.ObjectIdentifier()),\n        namedtype.OptionalNamedType('parameters', univ.Any(),\n            openType=opentype.OpenType('algorithm', algorithmIdentifierMap)\n        )\n    )\n\n\nclass Time(univ.Choice):\n    pass\n\n\nTime.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('utcTime', useful.UTCTime()),\n    namedtype.NamedType('generalTime', useful.GeneralizedTime())\n)\n\n\nclass AttributeValue(univ.Any):\n    pass\n\n\ncertificateAttributesMap = {}\n\n\nclass AttributeTypeAndValue(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('type', AttributeType()),\n        namedtype.NamedType(\n            'value', AttributeValue(),\n            openType=opentype.OpenType('type', certificateAttributesMap)\n        )\n    )\n\n\nclass RelativeDistinguishedName(univ.SetOf):\n    pass\n\n\nRelativeDistinguishedName.componentType = AttributeTypeAndValue()\nRelativeDistinguishedName.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass RDNSequence(univ.SequenceOf):\n    pass\n\n\nRDNSequence.componentType = RelativeDistinguishedName()\n\n\nclass Name(univ.Choice):\n    pass\n\n\nName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('rdnSequence', RDNSequence())\n)\n\n\nclass TBSCertList(univ.Sequence):\n    pass\n\n\nTBSCertList.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('version', Version()),\n    namedtype.NamedType('signature', AlgorithmIdentifier()),\n    namedtype.NamedType('issuer', Name()),\n    namedtype.NamedType('thisUpdate', Time()),\n    namedtype.OptionalNamedType('nextUpdate', Time()),\n    namedtype.OptionalNamedType(\n        'revokedCertificates', univ.SequenceOf(\n            componentType=univ.Sequence(\n                componentType=namedtype.NamedTypes(\n                    namedtype.NamedType('userCertificate', CertificateSerialNumber()),\n                    namedtype.NamedType('revocationDate', Time()),\n                    namedtype.OptionalNamedType('crlEntryExtensions', Extensions())\n                )\n            )\n        )\n    ),\n    namedtype.OptionalNamedType(\n        'crlExtensions', Extensions().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass CertificateList(univ.Sequence):\n    pass\n\n\nCertificateList.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('tbsCertList', TBSCertList()),\n    namedtype.NamedType('signatureAlgorithm', AlgorithmIdentifier()),\n    namedtype.NamedType('signature', univ.BitString())\n)\n\n\nclass PhysicalDeliveryOfficeName(PDSParameter):\n    pass\n\n\nub_extension_attributes = univ.Integer(256)\n\ncertificateExtensionsMap = {\n}\n\noraddressExtensionAttributeMap = {\n}\n\n\nclass ExtensionAttribute(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType(\n            'extension-attribute-type',\n            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, ub_extension_attributes)).subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.NamedType(\n            'extension-attribute-value',\n            univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)),\n            openType=opentype.OpenType('extension-attribute-type', oraddressExtensionAttributeMap))\n    )\n\nid_qt = _buildOid(id_pkix, 2)\n\nid_qt_cps = _buildOid(id_qt, 1)\n\nid_at_stateOrProvinceName = _buildOid(id_at, 8)\n\nid_at_title = _buildOid(id_at, 12)\n\nid_at_serialNumber = _buildOid(id_at, 5)\n\n\nclass X520dnQualifier(char.PrintableString):\n    pass\n\n\nclass PosteRestanteAddress(PDSParameter):\n    pass\n\n\nposte_restante_address = univ.Integer(19)\n\n\nclass UniqueIdentifier(univ.BitString):\n    pass\n\n\nclass Validity(univ.Sequence):\n    pass\n\n\nValidity.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('notBefore', Time()),\n    namedtype.NamedType('notAfter', Time())\n)\n\n\nclass SubjectPublicKeyInfo(univ.Sequence):\n    pass\n\n\nSubjectPublicKeyInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('algorithm', AlgorithmIdentifier()),\n    namedtype.NamedType('subjectPublicKey', univ.BitString())\n)\n\n\nclass TBSCertificate(univ.Sequence):\n    pass\n\n\nTBSCertificate.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version',\n                                 Version().subtype(explicitTag=tag.Tag(tag.tagClassContext,\n                                                                       tag.tagFormatSimple, 0)).subtype(value=\"v1\")),\n    namedtype.NamedType('serialNumber', CertificateSerialNumber()),\n    namedtype.NamedType('signature', AlgorithmIdentifier()),\n    namedtype.NamedType('issuer', Name()),\n    namedtype.NamedType('validity', Validity()),\n    namedtype.NamedType('subject', Name()),\n    namedtype.NamedType('subjectPublicKeyInfo', SubjectPublicKeyInfo()),\n    namedtype.OptionalNamedType('issuerUniqueID', UniqueIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('subjectUniqueID', UniqueIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.OptionalNamedType('extensions',\n                                Extensions().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\nphysical_delivery_office_name = univ.Integer(10)\n\nub_name = univ.Integer(32768)\n\n\nclass X520name(univ.Choice):\n    pass\n\n\nX520name.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name))),\n    namedtype.NamedType('printableString',\n                        char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name))),\n    namedtype.NamedType('universalString',\n                        char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name))),\n    namedtype.NamedType('bmpString', char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_name)))\n)\n\nid_at_dnQualifier = _buildOid(id_at, 46)\n\nub_serial_number = univ.Integer(64)\n\nub_pseudonym = univ.Integer(128)\n\npkcs_9 = _buildOid(1, 2, 840, 113549, 1, 9)\n\n\nclass X121Address(char.NumericString):\n    pass\n\n\nX121Address.subtypeSpec = constraint.ValueSizeConstraint(1, ub_x121_address_length)\n\n\nclass NetworkAddress(X121Address):\n    pass\n\n\nub_integer_options = univ.Integer(256)\n\nid_at_commonName = _buildOid(id_at, 3)\n\nub_organization_name_length = univ.Integer(64)\n\nid_ad_ocsp = _buildOid(id_ad, 1)\n\nub_country_name_numeric_length = univ.Integer(3)\n\nub_country_name_alpha_length = univ.Integer(2)\n\n\nclass PhysicalDeliveryCountryName(univ.Choice):\n    pass\n\n\nPhysicalDeliveryCountryName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('x121-dcc-code', char.NumericString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(ub_country_name_numeric_length, ub_country_name_numeric_length))),\n    namedtype.NamedType('iso-3166-alpha2-code', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(ub_country_name_alpha_length, ub_country_name_alpha_length)))\n)\n\nid_emailAddress = _buildOid(pkcs_9, 1)\n\ncommon_name = univ.Integer(1)\n\n\nclass X520Pseudonym(univ.Choice):\n    pass\n\n\nX520Pseudonym.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_pseudonym))),\n    namedtype.NamedType('printableString',\n                        char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_pseudonym))),\n    namedtype.NamedType('universalString',\n                        char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_pseudonym))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_pseudonym))),\n    namedtype.NamedType('bmpString',\n                        char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_pseudonym)))\n)\n\nub_domain_name_length = univ.Integer(16)\n\n\nclass AdministrationDomainName(univ.Choice):\n    pass\n\n\nAdministrationDomainName.tagSet = univ.Choice.tagSet.tagExplicitly(\n    tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 2))\nAdministrationDomainName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('numeric', char.NumericString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(0, ub_domain_name_length))),\n    namedtype.NamedType('printable', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(0, ub_domain_name_length)))\n)\n\n\nclass PresentationAddress(univ.Sequence):\n    pass\n\n\nPresentationAddress.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('pSelector', univ.OctetString().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('sSelector', univ.OctetString().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('tSelector', univ.OctetString().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.NamedType('nAddresses', univ.SetOf(componentType=univ.OctetString()).subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\n\nclass ExtendedNetworkAddress(univ.Choice):\n    pass\n\n\nExtendedNetworkAddress.componentType = namedtype.NamedTypes(\n    namedtype.NamedType(\n        'e163-4-address', univ.Sequence(\n            componentType=namedtype.NamedTypes(\n                namedtype.NamedType('number', char.NumericString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_e163_4_number_length)).subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n                namedtype.OptionalNamedType('sub-address', char.NumericString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_e163_4_sub_address_length)).subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n            )\n        )\n    ),\n    namedtype.NamedType('psap-address', PresentationAddress().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n)\n\n\nclass TeletexOrganizationName(char.TeletexString):\n    pass\n\n\nTeletexOrganizationName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_organization_name_length)\n\nub_terminal_id_length = univ.Integer(24)\n\n\nclass TerminalIdentifier(char.PrintableString):\n    pass\n\n\nTerminalIdentifier.subtypeSpec = constraint.ValueSizeConstraint(1, ub_terminal_id_length)\n\nid_ad_caIssuers = _buildOid(id_ad, 2)\n\nid_at_countryName = _buildOid(id_at, 6)\n\n\nclass StreetAddress(PDSParameter):\n    pass\n\n\npostal_code = univ.Integer(9)\n\nid_at_givenName = _buildOid(id_at, 42)\n\nub_title = univ.Integer(64)\n\n\nclass ExtensionAttributes(univ.SetOf):\n    pass\n\n\nExtensionAttributes.componentType = ExtensionAttribute()\nExtensionAttributes.sizeSpec = constraint.ValueSizeConstraint(1, ub_extension_attributes)\n\nub_emailaddress_length = univ.Integer(255)\n\nid_ad_caRepository = _buildOid(id_ad, 5)\n\n\nclass ExtensionORAddressComponents(PDSParameter):\n    pass\n\n\nub_organizational_unit_name = univ.Integer(64)\n\n\nclass X520OrganizationalUnitName(univ.Choice):\n    pass\n\n\nX520OrganizationalUnitName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name))),\n    namedtype.NamedType('printableString', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name))),\n    namedtype.NamedType('universalString', char.UniversalString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name))),\n    namedtype.NamedType('utf8String', char.UTF8String().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name))),\n    namedtype.NamedType('bmpString', char.BMPString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_organizational_unit_name)))\n)\n\n\nclass LocalPostalAttributes(PDSParameter):\n    pass\n\n\nteletex_organizational_unit_names = univ.Integer(5)\n\n\nclass X520Title(univ.Choice):\n    pass\n\n\nX520Title.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title))),\n    namedtype.NamedType('printableString',\n                        char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title))),\n    namedtype.NamedType('universalString',\n                        char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title))),\n    namedtype.NamedType('bmpString', char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_title)))\n)\n\nid_at_localityName = _buildOid(id_at, 7)\n\nid_at_initials = _buildOid(id_at, 43)\n\nub_state_name = univ.Integer(128)\n\n\nclass X520StateOrProvinceName(univ.Choice):\n    pass\n\n\nX520StateOrProvinceName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name))),\n    namedtype.NamedType('printableString',\n                        char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name))),\n    namedtype.NamedType('universalString',\n                        char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name))),\n    namedtype.NamedType('bmpString',\n                        char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_state_name)))\n)\n\nphysical_delivery_organization_name = univ.Integer(14)\n\nid_at_surname = _buildOid(id_at, 4)\n\n\nclass X520countryName(char.PrintableString):\n    pass\n\n\nX520countryName.subtypeSpec = constraint.ValueSizeConstraint(2, 2)\n\nphysical_delivery_office_number = univ.Integer(11)\n\nid_qt_unotice = _buildOid(id_qt, 2)\n\n\nclass X520SerialNumber(char.PrintableString):\n    pass\n\n\nX520SerialNumber.subtypeSpec = constraint.ValueSizeConstraint(1, ub_serial_number)\n\n\nclass Attribute(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('type', AttributeType()),\n        namedtype.NamedType('values',\n                            univ.SetOf(componentType=AttributeValue()),\n                            openType=opentype.OpenType('type', certificateAttributesMap))\n    )\n\nub_common_name = univ.Integer(64)\n\nid_pe = _buildOid(id_pkix, 1)\n\n\nclass ExtensionPhysicalDeliveryAddressComponents(PDSParameter):\n    pass\n\n\nclass EmailAddress(char.IA5String):\n    pass\n\n\nEmailAddress.subtypeSpec = constraint.ValueSizeConstraint(1, ub_emailaddress_length)\n\nid_at_organizationName = _buildOid(id_at, 10)\n\npost_office_box_address = univ.Integer(18)\n\n\nclass BuiltInDomainDefinedAttribute(univ.Sequence):\n    pass\n\n\nBuiltInDomainDefinedAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('type', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_defined_attribute_type_length))),\n    namedtype.NamedType('value', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_defined_attribute_value_length)))\n)\n\n\nclass BuiltInDomainDefinedAttributes(univ.SequenceOf):\n    pass\n\n\nBuiltInDomainDefinedAttributes.componentType = BuiltInDomainDefinedAttribute()\nBuiltInDomainDefinedAttributes.sizeSpec = constraint.ValueSizeConstraint(1, ub_domain_defined_attributes)\n\nid_at_pseudonym = _buildOid(id_at, 65)\n\nid_domainComponent = _buildOid(0, 9, 2342, 19200300, 100, 1, 25)\n\n\nclass X520CommonName(univ.Choice):\n    pass\n\n\nX520CommonName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name))),\n    namedtype.NamedType('printableString',\n                        char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name))),\n    namedtype.NamedType('universalString',\n                        char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name))),\n    namedtype.NamedType('utf8String',\n                        char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name))),\n    namedtype.NamedType('bmpString',\n                        char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, ub_common_name)))\n)\n\nextension_OR_address_components = univ.Integer(12)\n\nub_organizational_units = univ.Integer(4)\n\nteletex_personal_name = univ.Integer(4)\n\nub_numeric_user_id_length = univ.Integer(32)\n\nub_common_name_length = univ.Integer(64)\n\n\nclass TeletexCommonName(char.TeletexString):\n    pass\n\n\nTeletexCommonName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_common_name_length)\n\n\nclass PhysicalDeliveryOrganizationName(PDSParameter):\n    pass\n\n\nextension_physical_delivery_address_components = univ.Integer(15)\n\n\nclass NumericUserIdentifier(char.NumericString):\n    pass\n\n\nNumericUserIdentifier.subtypeSpec = constraint.ValueSizeConstraint(1, ub_numeric_user_id_length)\n\n\nclass CountryName(univ.Choice):\n    pass\n\n\nCountryName.tagSet = univ.Choice.tagSet.tagExplicitly(tag.Tag(tag.tagClassApplication, tag.tagFormatConstructed, 1))\nCountryName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('x121-dcc-code', char.NumericString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(ub_country_name_numeric_length, ub_country_name_numeric_length))),\n    namedtype.NamedType('iso-3166-alpha2-code', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(ub_country_name_alpha_length, ub_country_name_alpha_length)))\n)\n\n\nclass OrganizationName(char.PrintableString):\n    pass\n\n\nOrganizationName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_organization_name_length)\n\n\nclass OrganizationalUnitNames(univ.SequenceOf):\n    pass\n\n\nOrganizationalUnitNames.componentType = OrganizationalUnitName()\nOrganizationalUnitNames.sizeSpec = constraint.ValueSizeConstraint(1, ub_organizational_units)\n\n\nclass PrivateDomainName(univ.Choice):\n    pass\n\n\nPrivateDomainName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('numeric', char.NumericString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_name_length))),\n    namedtype.NamedType('printable', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_domain_name_length)))\n)\n\n\nclass BuiltInStandardAttributes(univ.Sequence):\n    pass\n\n\nBuiltInStandardAttributes.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('country-name', CountryName()),\n    namedtype.OptionalNamedType('administration-domain-name', AdministrationDomainName()),\n    namedtype.OptionalNamedType('network-address', NetworkAddress().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('terminal-identifier', TerminalIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('private-domain-name', PrivateDomainName().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2))),\n    namedtype.OptionalNamedType('organization-name', OrganizationName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n    namedtype.OptionalNamedType('numeric-user-identifier', NumericUserIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4))),\n    namedtype.OptionalNamedType('personal-name', PersonalName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 5))),\n    namedtype.OptionalNamedType('organizational-unit-names', OrganizationalUnitNames().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 6)))\n)\n\n\nclass ORAddress(univ.Sequence):\n    pass\n\n\nORAddress.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('built-in-standard-attributes', BuiltInStandardAttributes()),\n    namedtype.OptionalNamedType('built-in-domain-defined-attributes', BuiltInDomainDefinedAttributes()),\n    namedtype.OptionalNamedType('extension-attributes', ExtensionAttributes())\n)\n\n\nclass DistinguishedName(RDNSequence):\n    pass\n\n\nid_ad_timeStamping = _buildOid(id_ad, 3)\n\n\nclass PhysicalDeliveryOfficeNumber(PDSParameter):\n    pass\n\n\nteletex_domain_defined_attributes = univ.Integer(6)\n\n\nclass UniquePostalName(PDSParameter):\n    pass\n\n\nphysical_delivery_country_name = univ.Integer(8)\n\nub_pds_name_length = univ.Integer(16)\n\n\nclass PDSName(char.PrintableString):\n    pass\n\n\nPDSName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_pds_name_length)\n\n\nclass TeletexPersonalName(univ.Set):\n    pass\n\n\nTeletexPersonalName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('surname', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_surname_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('given-name', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_given_name_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('initials', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_initials_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.OptionalNamedType('generation-qualifier', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, ub_generation_qualifier_length)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\nstreet_address = univ.Integer(17)\n\n\nclass PostOfficeBoxAddress(PDSParameter):\n    pass\n\n\nlocal_postal_attributes = univ.Integer(21)\n\n\nclass DirectoryString(univ.Choice):\n    pass\n\n\nDirectoryString.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString',\n                        char.TeletexString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.NamedType('printableString',\n                        char.PrintableString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.NamedType('universalString',\n                        char.UniversalString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.NamedType('utf8String', char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.NamedType('bmpString', char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX)))\n)\n\nteletex_common_name = univ.Integer(2)\n\n\nclass CommonName(char.PrintableString):\n    pass\n\n\nCommonName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_common_name_length)\n\n\nclass Certificate(univ.Sequence):\n    pass\n\n\nCertificate.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('tbsCertificate', TBSCertificate()),\n    namedtype.NamedType('signatureAlgorithm', AlgorithmIdentifier()),\n    namedtype.NamedType('signature', univ.BitString())\n)\n\n\nclass TeletexOrganizationalUnitName(char.TeletexString):\n    pass\n\n\nTeletexOrganizationalUnitName.subtypeSpec = constraint.ValueSizeConstraint(1, ub_organizational_unit_name_length)\n\nid_at_name = _buildOid(id_at, 41)\n\n\nclass TeletexOrganizationalUnitNames(univ.SequenceOf):\n    pass\n\n\nTeletexOrganizationalUnitNames.componentType = TeletexOrganizationalUnitName()\nTeletexOrganizationalUnitNames.sizeSpec = constraint.ValueSizeConstraint(1, ub_organizational_units)\n\nid_ce = _buildOid(2, 5, 29)\n\nid_ce_issuerAltName = _buildOid(id_ce, 18)\n\n\nclass SkipCerts(univ.Integer):\n    pass\n\n\nSkipCerts.subtypeSpec = constraint.ValueRangeConstraint(0, MAX)\n\n\nclass CRLReason(univ.Enumerated):\n    pass\n\n\nCRLReason.namedValues = namedval.NamedValues(\n    ('unspecified', 0),\n    ('keyCompromise', 1),\n    ('cACompromise', 2),\n    ('affiliationChanged', 3),\n    ('superseded', 4),\n    ('cessationOfOperation', 5),\n    ('certificateHold', 6),\n    ('removeFromCRL', 8),\n    ('privilegeWithdrawn', 9),\n    ('aACompromise', 10)\n)\n\n\nclass PrivateKeyUsagePeriod(univ.Sequence):\n    pass\n\n\nPrivateKeyUsagePeriod.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('notBefore', useful.GeneralizedTime().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('notAfter', useful.GeneralizedTime().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nanotherNameMap = {\n\n}\n\n\nclass AnotherName(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('type-id', univ.ObjectIdentifier()),\n        namedtype.NamedType(\n            'value',\n            univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)),\n            openType=opentype.OpenType('type-id', anotherNameMap)\n        )\n    )\n\n\nclass EDIPartyName(univ.Sequence):\n    pass\n\n\nEDIPartyName.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('nameAssigner', DirectoryString().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('partyName', DirectoryString().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n)\n\n\nclass GeneralName(univ.Choice):\n    pass\n\n\nGeneralName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('otherName',\n                        AnotherName().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('rfc822Name',\n                        char.IA5String().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('dNSName',\n                        char.IA5String().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.NamedType('x400Address',\n                        ORAddress().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n    namedtype.NamedType('directoryName',\n                        Name().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 4))),\n    namedtype.NamedType('ediPartyName',\n                        EDIPartyName().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 5))),\n    namedtype.NamedType('uniformResourceIdentifier',\n                        char.IA5String().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 6))),\n    namedtype.NamedType('iPAddress',\n                        univ.OctetString().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 7))),\n    namedtype.NamedType('registeredID', univ.ObjectIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 8)))\n)\n\n\nclass BaseDistance(univ.Integer):\n    pass\n\n\nBaseDistance.subtypeSpec = constraint.ValueRangeConstraint(0, MAX)\n\n\nclass GeneralSubtree(univ.Sequence):\n    pass\n\n\nGeneralSubtree.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('base', GeneralName()),\n    namedtype.DefaultedNamedType('minimum', BaseDistance().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)).subtype(value=0)),\n    namedtype.OptionalNamedType('maximum', BaseDistance().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass GeneralNames(univ.SequenceOf):\n    pass\n\n\nGeneralNames.componentType = GeneralName()\nGeneralNames.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass DistributionPointName(univ.Choice):\n    pass\n\n\nDistributionPointName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('fullName',\n                        GeneralNames().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('nameRelativeToCRLIssuer', RelativeDistinguishedName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass ReasonFlags(univ.BitString):\n    pass\n\n\nReasonFlags.namedValues = namedval.NamedValues(\n    ('unused', 0),\n    ('keyCompromise', 1),\n    ('cACompromise', 2),\n    ('affiliationChanged', 3),\n    ('superseded', 4),\n    ('cessationOfOperation', 5),\n    ('certificateHold', 6),\n    ('privilegeWithdrawn', 7),\n    ('aACompromise', 8)\n)\n\n\nclass IssuingDistributionPoint(univ.Sequence):\n    pass\n\n\nIssuingDistributionPoint.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('distributionPoint', DistributionPointName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.DefaultedNamedType('onlyContainsUserCerts', univ.Boolean().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)).subtype(value=0)),\n    namedtype.DefaultedNamedType('onlyContainsCACerts', univ.Boolean().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)).subtype(value=0)),\n    namedtype.OptionalNamedType('onlySomeReasons', ReasonFlags().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n    namedtype.DefaultedNamedType('indirectCRL', univ.Boolean().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4)).subtype(value=0)),\n    namedtype.DefaultedNamedType('onlyContainsAttributeCerts', univ.Boolean().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 5)).subtype(value=0))\n)\n\nid_ce_certificatePolicies = _buildOid(id_ce, 32)\n\nid_kp_emailProtection = _buildOid(id_kp, 4)\n\n\nclass AccessDescription(univ.Sequence):\n    pass\n\n\nAccessDescription.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('accessMethod', univ.ObjectIdentifier()),\n    namedtype.NamedType('accessLocation', GeneralName())\n)\n\n\nclass IssuerAltName(GeneralNames):\n    pass\n\n\nid_ce_cRLDistributionPoints = _buildOid(id_ce, 31)\n\nholdInstruction = _buildOid(2, 2, 840, 10040, 2)\n\nid_holdinstruction_callissuer = _buildOid(holdInstruction, 2)\n\nid_ce_subjectDirectoryAttributes = _buildOid(id_ce, 9)\n\nid_ce_issuingDistributionPoint = _buildOid(id_ce, 28)\n\n\nclass DistributionPoint(univ.Sequence):\n    pass\n\n\nDistributionPoint.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('distributionPoint', DistributionPointName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.OptionalNamedType('reasons', ReasonFlags().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('cRLIssuer', GeneralNames().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\n\nclass CRLDistributionPoints(univ.SequenceOf):\n    pass\n\n\nCRLDistributionPoints.componentType = DistributionPoint()\nCRLDistributionPoints.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass GeneralSubtrees(univ.SequenceOf):\n    pass\n\n\nGeneralSubtrees.componentType = GeneralSubtree()\nGeneralSubtrees.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass NameConstraints(univ.Sequence):\n    pass\n\n\nNameConstraints.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('permittedSubtrees', GeneralSubtrees().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('excludedSubtrees', GeneralSubtrees().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass SubjectDirectoryAttributes(univ.SequenceOf):\n    pass\n\n\nSubjectDirectoryAttributes.componentType = Attribute()\nSubjectDirectoryAttributes.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\nid_kp_OCSPSigning = _buildOid(id_kp, 9)\n\nid_kp_timeStamping = _buildOid(id_kp, 8)\n\n\nclass DisplayText(univ.Choice):\n    pass\n\n\nDisplayText.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('ia5String', char.IA5String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, 200))),\n    namedtype.NamedType('visibleString',\n                        char.VisibleString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, 200))),\n    namedtype.NamedType('bmpString', char.BMPString().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, 200))),\n    namedtype.NamedType('utf8String', char.UTF8String().subtype(subtypeSpec=constraint.ValueSizeConstraint(1, 200)))\n)\n\n\nclass NoticeReference(univ.Sequence):\n    pass\n\n\nNoticeReference.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('organization', DisplayText()),\n    namedtype.NamedType('noticeNumbers', univ.SequenceOf(componentType=univ.Integer()))\n)\n\n\nclass UserNotice(univ.Sequence):\n    pass\n\n\nUserNotice.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('noticeRef', NoticeReference()),\n    namedtype.OptionalNamedType('explicitText', DisplayText())\n)\n\n\nclass PolicyQualifierId(univ.ObjectIdentifier):\n    pass\n\n\npolicyQualifierInfoMap = {\n\n}\n\n\nclass PolicyQualifierInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('policyQualifierId', PolicyQualifierId()),\n        namedtype.NamedType(\n            'qualifier', univ.Any(),\n            openType=opentype.OpenType('policyQualifierId', policyQualifierInfoMap)\n        )\n    )\n\n\nclass CertPolicyId(univ.ObjectIdentifier):\n    pass\n\n\nclass PolicyInformation(univ.Sequence):\n    pass\n\n\nPolicyInformation.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('policyIdentifier', CertPolicyId()),\n    namedtype.OptionalNamedType('policyQualifiers', univ.SequenceOf(componentType=PolicyQualifierInfo()))\n)\n\n\nclass CertificatePolicies(univ.SequenceOf):\n    pass\n\n\nCertificatePolicies.componentType = PolicyInformation()\nCertificatePolicies.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass SubjectAltName(GeneralNames):\n    pass\n\n\nid_ce_basicConstraints = _buildOid(id_ce, 19)\n\nid_ce_authorityKeyIdentifier = _buildOid(id_ce, 35)\n\nid_kp_codeSigning = _buildOid(id_kp, 3)\n\n\nclass BasicConstraints(univ.Sequence):\n    pass\n\n\nBasicConstraints.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('cA', univ.Boolean().subtype(value=0)),\n    namedtype.OptionalNamedType('pathLenConstraint',\n                                univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(0, MAX)))\n)\n\nid_ce_certificateIssuer = _buildOid(id_ce, 29)\n\n\nclass PolicyMappings(univ.SequenceOf):\n    pass\n\n\nPolicyMappings.componentType = univ.Sequence(\n    componentType=namedtype.NamedTypes(\n        namedtype.NamedType('issuerDomainPolicy', CertPolicyId()),\n        namedtype.NamedType('subjectDomainPolicy', CertPolicyId())\n    )\n)\n\nPolicyMappings.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass InhibitAnyPolicy(SkipCerts):\n    pass\n\n\nanyPolicy = _buildOid(id_ce_certificatePolicies, 0)\n\n\nclass CRLNumber(univ.Integer):\n    pass\n\n\nCRLNumber.subtypeSpec = constraint.ValueRangeConstraint(0, MAX)\n\n\nclass BaseCRLNumber(CRLNumber):\n    pass\n\n\nid_ce_nameConstraints = _buildOid(id_ce, 30)\n\nid_kp_serverAuth = _buildOid(id_kp, 1)\n\nid_ce_freshestCRL = _buildOid(id_ce, 46)\n\nid_ce_cRLReasons = _buildOid(id_ce, 21)\n\nid_ce_extKeyUsage = _buildOid(id_ce, 37)\n\n\nclass KeyIdentifier(univ.OctetString):\n    pass\n\n\nclass AuthorityKeyIdentifier(univ.Sequence):\n    pass\n\n\nAuthorityKeyIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('keyIdentifier', KeyIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('authorityCertIssuer', GeneralNames().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('authorityCertSerialNumber', CertificateSerialNumber().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\n\nclass FreshestCRL(CRLDistributionPoints):\n    pass\n\n\nid_ce_policyConstraints = _buildOid(id_ce, 36)\n\nid_pe_authorityInfoAccess = _buildOid(id_pe, 1)\n\n\nclass AuthorityInfoAccessSyntax(univ.SequenceOf):\n    pass\n\n\nAuthorityInfoAccessSyntax.componentType = AccessDescription()\nAuthorityInfoAccessSyntax.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\nid_holdinstruction_none = _buildOid(holdInstruction, 1)\n\n\nclass CPSuri(char.IA5String):\n    pass\n\n\nid_pe_subjectInfoAccess = _buildOid(id_pe, 11)\n\n\nclass SubjectKeyIdentifier(KeyIdentifier):\n    pass\n\n\nid_ce_subjectAltName = _buildOid(id_ce, 17)\n\n\nclass KeyPurposeId(univ.ObjectIdentifier):\n    pass\n\n\nclass ExtKeyUsageSyntax(univ.SequenceOf):\n    pass\n\n\nExtKeyUsageSyntax.componentType = KeyPurposeId()\nExtKeyUsageSyntax.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass HoldInstructionCode(univ.ObjectIdentifier):\n    pass\n\n\nid_ce_deltaCRLIndicator = _buildOid(id_ce, 27)\n\nid_ce_keyUsage = _buildOid(id_ce, 15)\n\nid_ce_holdInstructionCode = _buildOid(id_ce, 23)\n\n\nclass SubjectInfoAccessSyntax(univ.SequenceOf):\n    pass\n\n\nSubjectInfoAccessSyntax.componentType = AccessDescription()\nSubjectInfoAccessSyntax.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass InvalidityDate(useful.GeneralizedTime):\n    pass\n\n\nclass KeyUsage(univ.BitString):\n    pass\n\n\nKeyUsage.namedValues = namedval.NamedValues(\n    ('digitalSignature', 0),\n    ('nonRepudiation', 1),\n    ('keyEncipherment', 2),\n    ('dataEncipherment', 3),\n    ('keyAgreement', 4),\n    ('keyCertSign', 5),\n    ('cRLSign', 6),\n    ('encipherOnly', 7),\n    ('decipherOnly', 8)\n)\n\nid_ce_invalidityDate = _buildOid(id_ce, 24)\n\nid_ce_policyMappings = _buildOid(id_ce, 33)\n\nanyExtendedKeyUsage = _buildOid(id_ce_extKeyUsage, 0)\n\nid_ce_privateKeyUsagePeriod = _buildOid(id_ce, 16)\n\nid_ce_cRLNumber = _buildOid(id_ce, 20)\n\n\nclass CertificateIssuer(GeneralNames):\n    pass\n\n\nid_holdinstruction_reject = _buildOid(holdInstruction, 3)\n\n\nclass PolicyConstraints(univ.Sequence):\n    pass\n\n\nPolicyConstraints.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('requireExplicitPolicy',\n                                SkipCerts().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('inhibitPolicyMapping',\n                                SkipCerts().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\nid_kp_clientAuth = _buildOid(id_kp, 2)\n\nid_ce_subjectKeyIdentifier = _buildOid(id_ce, 14)\n\nid_ce_inhibitAnyPolicy = _buildOid(id_ce, 54)\n\n# map of ORAddress ExtensionAttribute type to ExtensionAttribute value\n\n_oraddressExtensionAttributeMapUpdate = {\n    common_name: CommonName(),\n    teletex_common_name: TeletexCommonName(),\n    teletex_organization_name: TeletexOrganizationName(),\n    teletex_personal_name: TeletexPersonalName(),\n    teletex_organizational_unit_names: TeletexOrganizationalUnitNames(),\n    pds_name: PDSName(),\n    physical_delivery_country_name: PhysicalDeliveryCountryName(),\n    postal_code: PostalCode(),\n    physical_delivery_office_name: PhysicalDeliveryOfficeName(),\n    physical_delivery_office_number: PhysicalDeliveryOfficeNumber(),\n    extension_OR_address_components: ExtensionORAddressComponents(),\n    physical_delivery_personal_name: PhysicalDeliveryPersonalName(),\n    physical_delivery_organization_name: PhysicalDeliveryOrganizationName(),\n    extension_physical_delivery_address_components: ExtensionPhysicalDeliveryAddressComponents(),\n    unformatted_postal_address: UnformattedPostalAddress(),\n    street_address: StreetAddress(),\n    post_office_box_address: PostOfficeBoxAddress(),\n    poste_restante_address: PosteRestanteAddress(),\n    unique_postal_name: UniquePostalName(),\n    local_postal_attributes: LocalPostalAttributes(),\n    extended_network_address: ExtendedNetworkAddress(),\n    terminal_type: TerminalType(),\n    teletex_domain_defined_attributes: TeletexDomainDefinedAttributes(),\n}\n\noraddressExtensionAttributeMap.update(_oraddressExtensionAttributeMapUpdate)\n\n\n# map of AttributeType -> AttributeValue\n\n_certificateAttributesMapUpdate = {\n    id_at_name: X520name(),\n    id_at_surname: X520name(),\n    id_at_givenName: X520name(),\n    id_at_initials: X520name(),\n    id_at_generationQualifier: X520name(),\n    id_at_commonName: X520CommonName(),\n    id_at_localityName: X520LocalityName(),\n    id_at_stateOrProvinceName: X520StateOrProvinceName(),\n    id_at_organizationName: X520OrganizationName(),\n    id_at_organizationalUnitName: X520OrganizationalUnitName(),\n    id_at_title: X520Title(),\n    id_at_dnQualifier: X520dnQualifier(),\n    id_at_countryName: X520countryName(),\n    id_at_serialNumber: X520SerialNumber(),\n    id_at_pseudonym: X520Pseudonym(),\n    id_domainComponent: DomainComponent(),\n    id_emailAddress: EmailAddress(),\n}\n\ncertificateAttributesMap.update(_certificateAttributesMapUpdate)\n\n\n# map of Certificate Extension OIDs to Extensions\n\n_certificateExtensionsMap = {\n    id_ce_authorityKeyIdentifier: AuthorityKeyIdentifier(),\n    id_ce_subjectKeyIdentifier: SubjectKeyIdentifier(),\n    id_ce_keyUsage: KeyUsage(),\n    id_ce_privateKeyUsagePeriod: PrivateKeyUsagePeriod(),\n    id_ce_certificatePolicies: CertificatePolicies(),\n    id_ce_policyMappings: PolicyMappings(),\n    id_ce_subjectAltName: SubjectAltName(),\n    id_ce_issuerAltName: IssuerAltName(),\n    id_ce_subjectDirectoryAttributes: SubjectDirectoryAttributes(),\n    id_ce_basicConstraints: BasicConstraints(),\n    id_ce_nameConstraints: NameConstraints(),\n    id_ce_policyConstraints: PolicyConstraints(),\n    id_ce_extKeyUsage: ExtKeyUsageSyntax(),\n    id_ce_cRLDistributionPoints: CRLDistributionPoints(),\n    id_pe_authorityInfoAccess: AuthorityInfoAccessSyntax(),\n    id_ce_cRLNumber: univ.Integer(),\n    id_ce_deltaCRLIndicator: BaseCRLNumber(),\n    id_ce_issuingDistributionPoint: IssuingDistributionPoint(),\n    id_ce_cRLReasons: CRLReason(),\n    id_ce_holdInstructionCode: univ.ObjectIdentifier(),\n    id_ce_invalidityDate: useful.GeneralizedTime(),\n    id_ce_certificateIssuer: GeneralNames(),\n}\n\ncertificateExtensionsMap.update(_certificateExtensionsMap)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5480.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n# Modified by Russ Housley to add maps for opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Elliptic Curve Cryptography Subject Public Key Information\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5480.txt\n\n\n# What can be imported from rfc4055.py ?\n\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc3279\nfrom pyasn1_modules import rfc5280\n\n\n# These structures are the same as RFC 3279.\n\nDHPublicKey = rfc3279.DHPublicKey\n\nDSAPublicKey = rfc3279.DSAPublicKey\n\nValidationParms = rfc3279.ValidationParms\n\nDomainParameters = rfc3279.DomainParameters\n\nECDSA_Sig_Value = rfc3279.ECDSA_Sig_Value\n\nECPoint = rfc3279.ECPoint\n\nKEA_Parms_Id = rfc3279.KEA_Parms_Id\n\nRSAPublicKey = rfc3279.RSAPublicKey\n\n\n# RFC 5480 changed the names of these structures from RFC 3279.\n\nDSS_Parms = rfc3279.Dss_Parms\n\nDSA_Sig_Value = rfc3279.Dss_Sig_Value\n\n\n# RFC 3279 defines a more complex alternative for ECParameters.\n# RFC 5480 narrows the definition to a single CHOICE: namedCurve.\n\nclass ECParameters(univ.Choice):\n    pass\n\nECParameters.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('namedCurve', univ.ObjectIdentifier())\n)\n\n\n# OIDs for Message Digest Algorithms\n\nid_md2 = univ.ObjectIdentifier('1.2.840.113549.2.2')\n\nid_md5 = univ.ObjectIdentifier('1.2.840.113549.2.5')\n\nid_sha1 = univ.ObjectIdentifier('1.3.14.3.2.26')\n\nid_sha224 = univ.ObjectIdentifier('2.16.840.1.101.3.4.2.4')\n\nid_sha256 = univ.ObjectIdentifier('2.16.840.1.101.3.4.2.1')\n\nid_sha384 = univ.ObjectIdentifier('2.16.840.1.101.3.4.2.2')\n\nid_sha512 = univ.ObjectIdentifier('2.16.840.1.101.3.4.2.3')\n\n\n# OID for RSA PK Algorithm and Key\n\nrsaEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.1')\n\n\n# OID for DSA PK Algorithm, Key, and Parameters\n\nid_dsa = univ.ObjectIdentifier('1.2.840.10040.4.1')\n\n\n# OID for Diffie-Hellman PK Algorithm, Key, and Parameters\n\ndhpublicnumber = univ.ObjectIdentifier('1.2.840.10046.2.1')\n\n# OID for KEA PK Algorithm and Parameters\n\nid_keyExchangeAlgorithm = univ.ObjectIdentifier('2.16.840.1.101.2.1.1.22')\n\n\n# OIDs for Elliptic Curve Algorithm ID, Key, and Parameters\n# Note that ECDSA keys always use this OID\n\nid_ecPublicKey = univ.ObjectIdentifier('1.2.840.10045.2.1')\n\nid_ecDH = univ.ObjectIdentifier('1.3.132.1.12')\n\nid_ecMQV = univ.ObjectIdentifier('1.3.132.1.13')\n\n\n# OIDs for RSA Signature Algorithms\n\nmd2WithRSAEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.2')\n\nmd5WithRSAEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.4')\n\nsha1WithRSAEncryption = univ.ObjectIdentifier('1.2.840.113549.1.1.5')\n\n\n# OIDs for DSA Signature Algorithms\n\nid_dsa_with_sha1 = univ.ObjectIdentifier('1.2.840.10040.4.3')\n\nid_dsa_with_sha224 = univ.ObjectIdentifier('2.16.840.1.101.3.4.3.1')\n\nid_dsa_with_sha256 = univ.ObjectIdentifier('2.16.840.1.101.3.4.3.2')\n\n\n# OIDs for ECDSA Signature Algorithms\n\necdsa_with_SHA1 = univ.ObjectIdentifier('1.2.840.10045.4.1')\n\necdsa_with_SHA224 = univ.ObjectIdentifier('1.2.840.10045.4.3.1')\n\necdsa_with_SHA256 = univ.ObjectIdentifier('1.2.840.10045.4.3.2')\n\necdsa_with_SHA384 = univ.ObjectIdentifier('1.2.840.10045.4.3.3')\n\necdsa_with_SHA512 = univ.ObjectIdentifier('1.2.840.10045.4.3.4')\n\n\n# OIDs for Named Elliptic Curves\n\nsecp192r1 = univ.ObjectIdentifier('1.2.840.10045.3.1.1')\n\nsect163k1 = univ.ObjectIdentifier('1.3.132.0.1')\n\nsect163r2 = univ.ObjectIdentifier('1.3.132.0.15')\n\nsecp224r1 = univ.ObjectIdentifier('1.3.132.0.33')\n\nsect233k1 = univ.ObjectIdentifier('1.3.132.0.26')\n\nsect233r1 = univ.ObjectIdentifier('1.3.132.0.27')\n\nsecp256r1 = univ.ObjectIdentifier('1.2.840.10045.3.1.7')\n\nsect283k1 = univ.ObjectIdentifier('1.3.132.0.16')\n\nsect283r1 = univ.ObjectIdentifier('1.3.132.0.17')\n\nsecp384r1 = univ.ObjectIdentifier('1.3.132.0.34')\n\nsect409k1 = univ.ObjectIdentifier('1.3.132.0.36')\n\nsect409r1 = univ.ObjectIdentifier('1.3.132.0.37')\n\nsecp521r1 = univ.ObjectIdentifier('1.3.132.0.35')\n\nsect571k1 = univ.ObjectIdentifier('1.3.132.0.38')\n\nsect571r1 = univ.ObjectIdentifier('1.3.132.0.39')\n\n\n# Map of Algorithm Identifier OIDs to Parameters\n# The algorithm is not included if the parameters MUST be absent\n\n_algorithmIdentifierMapUpdate = {\n    rsaEncryption: univ.Null(),\n    md2WithRSAEncryption: univ.Null(),\n    md5WithRSAEncryption: univ.Null(),\n    sha1WithRSAEncryption: univ.Null(),\n    id_dsa: DSS_Parms(),\n    dhpublicnumber: DomainParameters(),\n    id_keyExchangeAlgorithm: KEA_Parms_Id(),\n    id_ecPublicKey: ECParameters(),\n    id_ecDH: ECParameters(),\n    id_ecMQV: ECParameters(),\n}\n\n\n# Add these Algorithm Identifier map entries to the ones in rfc5280.py\n\nrfc5280.algorithmIdentifierMap.update(_algorithmIdentifierMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5649.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# AES Key Wrap with Padding\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5649.txt\n\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\n\nclass AlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nid_aes128_wrap = univ.ObjectIdentifier('2.16.840.1.101.3.4.1.5')\n\nid_aes192_wrap = univ.ObjectIdentifier('2.16.840.1.101.3.4.1.25')\n\nid_aes256_wrap = univ.ObjectIdentifier('2.16.840.1.101.3.4.1.45')\n\n\nid_aes128_wrap_pad = univ.ObjectIdentifier('2.16.840.1.101.3.4.1.8')\n\nid_aes192_wrap_pad = univ.ObjectIdentifier('2.16.840.1.101.3.4.1.28')\n\nid_aes256_wrap_pad = univ.ObjectIdentifier('2.16.840.1.101.3.4.1.48')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5652.py",
    "content": "# coding: utf-8\n#\n# This file is part of pyasn1-modules software.\n#\n# Created by Stanisław Pitucha with asn1ate tool.\n# Modified by Russ Housley to add support for opentypes.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Cryptographic Message Syntax (CMS)\n#\n# ASN.1 source from:\n# http://www.ietf.org/rfc/rfc5652.txt\n#\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import opentype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nfrom pyasn1_modules import rfc3281\nfrom pyasn1_modules import rfc5280\n\nMAX = float('inf')\n\n\ndef _buildOid(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\ncmsContentTypesMap = { }\n\ncmsAttributesMap = { }\n\notherKeyAttributesMap = { }\n\notherCertFormatMap = { }\n\notherRevInfoFormatMap = { }\n\notherRecipientInfoMap = { }\n\n\nclass AttCertVersionV1(univ.Integer):\n    pass\n\n\nAttCertVersionV1.namedValues = namedval.NamedValues(\n    ('v1', 0)\n)\n\n\nclass AttributeCertificateInfoV1(univ.Sequence):\n    pass\n\n\nAttributeCertificateInfoV1.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version', AttCertVersionV1().subtype(value=\"v1\")),\n    namedtype.NamedType(\n        'subject', univ.Choice(\n            componentType=namedtype.NamedTypes(\n                namedtype.NamedType('baseCertificateID', rfc3281.IssuerSerial().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n                namedtype.NamedType('subjectName', rfc5280.GeneralNames().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n            )\n        )\n    ),\n    namedtype.NamedType('issuer', rfc5280.GeneralNames()),\n    namedtype.NamedType('signature', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('serialNumber', rfc5280.CertificateSerialNumber()),\n    namedtype.NamedType('attCertValidityPeriod', rfc3281.AttCertValidityPeriod()),\n    namedtype.NamedType('attributes', univ.SequenceOf(componentType=rfc5280.Attribute())),\n    namedtype.OptionalNamedType('issuerUniqueID', rfc5280.UniqueIdentifier()),\n    namedtype.OptionalNamedType('extensions', rfc5280.Extensions())\n)\n\n\nclass AttributeCertificateV1(univ.Sequence):\n    pass\n\n\nAttributeCertificateV1.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('acInfo', AttributeCertificateInfoV1()),\n    namedtype.NamedType('signatureAlgorithm', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('signature', univ.BitString())\n)\n\n\nclass AttributeValue(univ.Any):\n    pass\n\n\nclass Attribute(univ.Sequence):\n    pass\n\n\nAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('attrType', univ.ObjectIdentifier()),\n    namedtype.NamedType('attrValues', univ.SetOf(componentType=AttributeValue()),\n        openType=opentype.OpenType('attrType', cmsAttributesMap)\n    )\n)\n\n\nclass SignedAttributes(univ.SetOf):\n    pass\n\n\nSignedAttributes.componentType = Attribute()\nSignedAttributes.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass AttributeCertificateV2(rfc3281.AttributeCertificate):\n    pass\n\n\nclass OtherKeyAttribute(univ.Sequence):\n    pass\n\n\nOtherKeyAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('keyAttrId', univ.ObjectIdentifier()),\n    namedtype.OptionalNamedType('keyAttr', univ.Any(),\n        openType=opentype.OpenType('keyAttrId', otherKeyAttributesMap)\n    )\n)\n\n\nclass UnauthAttributes(univ.SetOf):\n    pass\n\n\nUnauthAttributes.componentType = Attribute()\nUnauthAttributes.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\nid_encryptedData = _buildOid(1, 2, 840, 113549, 1, 7, 6)\n\n\nclass SignatureValue(univ.OctetString):\n    pass\n\n\nclass IssuerAndSerialNumber(univ.Sequence):\n    pass\n\n\nIssuerAndSerialNumber.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuer', rfc5280.Name()),\n    namedtype.NamedType('serialNumber', rfc5280.CertificateSerialNumber())\n)\n\n\nclass SubjectKeyIdentifier(univ.OctetString):\n    pass\n\n\nclass RecipientKeyIdentifier(univ.Sequence):\n    pass\n\n\nRecipientKeyIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('subjectKeyIdentifier', SubjectKeyIdentifier()),\n    namedtype.OptionalNamedType('date', useful.GeneralizedTime()),\n    namedtype.OptionalNamedType('other', OtherKeyAttribute())\n)\n\n\nclass KeyAgreeRecipientIdentifier(univ.Choice):\n    pass\n\n\nKeyAgreeRecipientIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerAndSerialNumber', IssuerAndSerialNumber()),\n    namedtype.NamedType('rKeyId', RecipientKeyIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n)\n\n\nclass EncryptedKey(univ.OctetString):\n    pass\n\n\nclass RecipientEncryptedKey(univ.Sequence):\n    pass\n\n\nRecipientEncryptedKey.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('rid', KeyAgreeRecipientIdentifier()),\n    namedtype.NamedType('encryptedKey', EncryptedKey())\n)\n\n\nclass RecipientEncryptedKeys(univ.SequenceOf):\n    pass\n\n\nRecipientEncryptedKeys.componentType = RecipientEncryptedKey()\n\n\nclass MessageAuthenticationCode(univ.OctetString):\n    pass\n\n\nclass CMSVersion(univ.Integer):\n    pass\n\n\nCMSVersion.namedValues = namedval.NamedValues(\n    ('v0', 0),\n    ('v1', 1),\n    ('v2', 2),\n    ('v3', 3),\n    ('v4', 4),\n    ('v5', 5)\n)\n\n\nclass OtherCertificateFormat(univ.Sequence):\n    pass\n\n\nOtherCertificateFormat.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('otherCertFormat', univ.ObjectIdentifier()),\n    namedtype.NamedType('otherCert', univ.Any(),\n        openType=opentype.OpenType('otherCertFormat', otherCertFormatMap)\n    )\n)\n\n\nclass ExtendedCertificateInfo(univ.Sequence):\n    pass\n\n\nExtendedCertificateInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('certificate', rfc5280.Certificate()),\n    namedtype.NamedType('attributes', UnauthAttributes())\n)\n\n\nclass Signature(univ.BitString):\n    pass\n\n\nclass SignatureAlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass ExtendedCertificate(univ.Sequence):\n    pass\n\n\nExtendedCertificate.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('extendedCertificateInfo', ExtendedCertificateInfo()),\n    namedtype.NamedType('signatureAlgorithm', SignatureAlgorithmIdentifier()),\n    namedtype.NamedType('signature', Signature())\n)\n\n\nclass CertificateChoices(univ.Choice):\n    pass\n\n\nCertificateChoices.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('certificate', rfc5280.Certificate()),\n    namedtype.NamedType('extendedCertificate', ExtendedCertificate().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('v1AttrCert', AttributeCertificateV1().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('v2AttrCert', AttributeCertificateV2().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.NamedType('other', OtherCertificateFormat().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3)))\n)\n\n\nclass CertificateSet(univ.SetOf):\n    pass\n\n\nCertificateSet.componentType = CertificateChoices()\n\n\nclass OtherRevocationInfoFormat(univ.Sequence):\n    pass\n\n\nOtherRevocationInfoFormat.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('otherRevInfoFormat', univ.ObjectIdentifier()),\n    namedtype.NamedType('otherRevInfo', univ.Any(),\n        openType=opentype.OpenType('otherRevInfoFormat', otherRevInfoFormatMap)\n    )\n)\n\n\nclass RevocationInfoChoice(univ.Choice):\n    pass\n\n\nRevocationInfoChoice.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('crl', rfc5280.CertificateList()),\n    namedtype.NamedType('other', OtherRevocationInfoFormat().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n)\n\n\nclass RevocationInfoChoices(univ.SetOf):\n    pass\n\n\nRevocationInfoChoices.componentType = RevocationInfoChoice()\n\n\nclass OriginatorInfo(univ.Sequence):\n    pass\n\n\nOriginatorInfo.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('certs', CertificateSet().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('crls', RevocationInfoChoices().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass ContentType(univ.ObjectIdentifier):\n    pass\n\n\nclass EncryptedContent(univ.OctetString):\n    pass\n\n\nclass ContentEncryptionAlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass EncryptedContentInfo(univ.Sequence):\n    pass\n\n\nEncryptedContentInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('contentType', ContentType()),\n    namedtype.NamedType('contentEncryptionAlgorithm', ContentEncryptionAlgorithmIdentifier()),\n    namedtype.OptionalNamedType('encryptedContent', EncryptedContent().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass UnprotectedAttributes(univ.SetOf):\n    pass\n\n\nUnprotectedAttributes.componentType = Attribute()\nUnprotectedAttributes.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass KeyEncryptionAlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass KEKIdentifier(univ.Sequence):\n    pass\n\n\nKEKIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('keyIdentifier', univ.OctetString()),\n    namedtype.OptionalNamedType('date', useful.GeneralizedTime()),\n    namedtype.OptionalNamedType('other', OtherKeyAttribute())\n)\n\n\nclass KEKRecipientInfo(univ.Sequence):\n    pass\n\n\nKEKRecipientInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('kekid', KEKIdentifier()),\n    namedtype.NamedType('keyEncryptionAlgorithm', KeyEncryptionAlgorithmIdentifier()),\n    namedtype.NamedType('encryptedKey', EncryptedKey())\n)\n\n\nclass KeyDerivationAlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass PasswordRecipientInfo(univ.Sequence):\n    pass\n\n\nPasswordRecipientInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.OptionalNamedType('keyDerivationAlgorithm', KeyDerivationAlgorithmIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('keyEncryptionAlgorithm', KeyEncryptionAlgorithmIdentifier()),\n    namedtype.NamedType('encryptedKey', EncryptedKey())\n)\n\n\nclass RecipientIdentifier(univ.Choice):\n    pass\n\n\nRecipientIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerAndSerialNumber', IssuerAndSerialNumber()),\n    namedtype.NamedType('subjectKeyIdentifier', SubjectKeyIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass KeyTransRecipientInfo(univ.Sequence):\n    pass\n\n\nKeyTransRecipientInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('rid', RecipientIdentifier()),\n    namedtype.NamedType('keyEncryptionAlgorithm', KeyEncryptionAlgorithmIdentifier()),\n    namedtype.NamedType('encryptedKey', EncryptedKey())\n)\n\n\nclass UserKeyingMaterial(univ.OctetString):\n    pass\n\n\nclass OriginatorPublicKey(univ.Sequence):\n    pass\n\n\nOriginatorPublicKey.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('algorithm', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('publicKey', univ.BitString())\n)\n\n\nclass OriginatorIdentifierOrKey(univ.Choice):\n    pass\n\n\nOriginatorIdentifierOrKey.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerAndSerialNumber', IssuerAndSerialNumber()),\n    namedtype.NamedType('subjectKeyIdentifier', SubjectKeyIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('originatorKey', OriginatorPublicKey().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n)\n\n\nclass KeyAgreeRecipientInfo(univ.Sequence):\n    pass\n\n\nKeyAgreeRecipientInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('originator', OriginatorIdentifierOrKey().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.OptionalNamedType('ukm', UserKeyingMaterial().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('keyEncryptionAlgorithm', KeyEncryptionAlgorithmIdentifier()),\n    namedtype.NamedType('recipientEncryptedKeys', RecipientEncryptedKeys())\n)\n\n\nclass OtherRecipientInfo(univ.Sequence):\n    pass\n\n\nOtherRecipientInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('oriType', univ.ObjectIdentifier()),\n    namedtype.NamedType('oriValue', univ.Any(),\n        openType=opentype.OpenType('oriType', otherRecipientInfoMap)\n    )\n)\n\n\nclass RecipientInfo(univ.Choice):\n    pass\n\n\nRecipientInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('ktri', KeyTransRecipientInfo()),\n    namedtype.NamedType('kari', KeyAgreeRecipientInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1))),\n    namedtype.NamedType('kekri', KEKRecipientInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2))),\n    namedtype.NamedType('pwri', PasswordRecipientInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3))),\n    namedtype.NamedType('ori', OtherRecipientInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 4)))\n)\n\n\nclass RecipientInfos(univ.SetOf):\n    pass\n\n\nRecipientInfos.componentType = RecipientInfo()\nRecipientInfos.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass EnvelopedData(univ.Sequence):\n    pass\n\n\nEnvelopedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.OptionalNamedType('originatorInfo', OriginatorInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('recipientInfos', RecipientInfos()),\n    namedtype.NamedType('encryptedContentInfo', EncryptedContentInfo()),\n    namedtype.OptionalNamedType('unprotectedAttrs', UnprotectedAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass DigestAlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nid_ct_contentInfo = _buildOid(1, 2, 840, 113549, 1, 9, 16, 1, 6)\n\nid_digestedData = _buildOid(1, 2, 840, 113549, 1, 7, 5)\n\n\nclass EncryptedData(univ.Sequence):\n    pass\n\n\nEncryptedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('encryptedContentInfo', EncryptedContentInfo()),\n    namedtype.OptionalNamedType('unprotectedAttrs', UnprotectedAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\nid_messageDigest = _buildOid(1, 2, 840, 113549, 1, 9, 4)\n\nid_signedData = _buildOid(1, 2, 840, 113549, 1, 7, 2)\n\n\nclass MessageAuthenticationCodeAlgorithm(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass UnsignedAttributes(univ.SetOf):\n    pass\n\n\nUnsignedAttributes.componentType = Attribute()\nUnsignedAttributes.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass SignerIdentifier(univ.Choice):\n    pass\n\n\nSignerIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerAndSerialNumber', IssuerAndSerialNumber()),\n    namedtype.NamedType('subjectKeyIdentifier', SubjectKeyIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass SignerInfo(univ.Sequence):\n    pass\n\n\nSignerInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('sid', SignerIdentifier()),\n    namedtype.NamedType('digestAlgorithm', DigestAlgorithmIdentifier()),\n    namedtype.OptionalNamedType('signedAttrs', SignedAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('signatureAlgorithm', SignatureAlgorithmIdentifier()),\n    namedtype.NamedType('signature', SignatureValue()),\n    namedtype.OptionalNamedType('unsignedAttrs', UnsignedAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass SignerInfos(univ.SetOf):\n    pass\n\n\nSignerInfos.componentType = SignerInfo()\n\n\nclass Countersignature(SignerInfo):\n    pass\n\n\nclass ContentInfo(univ.Sequence):\n    pass\n\n\nContentInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('contentType', ContentType()),\n    namedtype.NamedType('content', univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)),\n        openType=opentype.OpenType('contentType', cmsContentTypesMap)\n    )\n)\n\n\nclass EncapsulatedContentInfo(univ.Sequence):\n    pass\n\n\nEncapsulatedContentInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('eContentType', ContentType()),\n    namedtype.OptionalNamedType('eContent', univ.OctetString().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\nid_countersignature = _buildOid(1, 2, 840, 113549, 1, 9, 6)\n\nid_data = _buildOid(1, 2, 840, 113549, 1, 7, 1)\n\n\nclass MessageDigest(univ.OctetString):\n    pass\n\n\nclass AuthAttributes(univ.SetOf):\n    pass\n\n\nAuthAttributes.componentType = Attribute()\nAuthAttributes.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass Time(univ.Choice):\n    pass\n\n\nTime.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('utcTime', useful.UTCTime()),\n    namedtype.NamedType('generalTime', useful.GeneralizedTime())\n)\n\n\nclass AuthenticatedData(univ.Sequence):\n    pass\n\n\nAuthenticatedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.OptionalNamedType('originatorInfo', OriginatorInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('recipientInfos', RecipientInfos()),\n    namedtype.NamedType('macAlgorithm', MessageAuthenticationCodeAlgorithm()),\n    namedtype.OptionalNamedType('digestAlgorithm', DigestAlgorithmIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('encapContentInfo', EncapsulatedContentInfo()),\n    namedtype.OptionalNamedType('authAttrs', AuthAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.NamedType('mac', MessageAuthenticationCode()),\n    namedtype.OptionalNamedType('unauthAttrs', UnauthAttributes().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\nid_contentType = _buildOid(1, 2, 840, 113549, 1, 9, 3)\n\n\nclass ExtendedCertificateOrCertificate(univ.Choice):\n    pass\n\n\nExtendedCertificateOrCertificate.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('certificate', rfc5280.Certificate()),\n    namedtype.NamedType('extendedCertificate', ExtendedCertificate().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0)))\n)\n\n\nclass Digest(univ.OctetString):\n    pass\n\n\nclass DigestedData(univ.Sequence):\n    pass\n\n\nDigestedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('digestAlgorithm', DigestAlgorithmIdentifier()),\n    namedtype.NamedType('encapContentInfo', EncapsulatedContentInfo()),\n    namedtype.NamedType('digest', Digest())\n)\n\nid_envelopedData = _buildOid(1, 2, 840, 113549, 1, 7, 3)\n\n\nclass DigestAlgorithmIdentifiers(univ.SetOf):\n    pass\n\n\nDigestAlgorithmIdentifiers.componentType = DigestAlgorithmIdentifier()\n\n\nclass SignedData(univ.Sequence):\n    pass\n\n\nSignedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', CMSVersion()),\n    namedtype.NamedType('digestAlgorithms', DigestAlgorithmIdentifiers()),\n    namedtype.NamedType('encapContentInfo', EncapsulatedContentInfo()),\n    namedtype.OptionalNamedType('certificates', CertificateSet().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('crls', RevocationInfoChoices().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('signerInfos', SignerInfos())\n)\n\nid_signingTime = _buildOid(1, 2, 840, 113549, 1, 9, 5)\n\n\nclass SigningTime(Time):\n    pass\n\n\nid_ct_authData = _buildOid(1, 2, 840, 113549, 1, 9, 16, 1, 2)\n\n\n# CMS Content Type Map\n\n_cmsContentTypesMapUpdate = {\n    id_ct_contentInfo: ContentInfo(),\n    id_data: univ.OctetString(),\n    id_signedData: SignedData(),\n    id_envelopedData: EnvelopedData(),\n    id_digestedData: DigestedData(),\n    id_encryptedData: EncryptedData(),\n    id_ct_authData: AuthenticatedData(),\n}\n\ncmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n\n\n# CMS Attribute Map\n\n_cmsAttributesMapUpdate = {\n    id_contentType: ContentType(),\n    id_messageDigest: MessageDigest(),\n    id_signingTime: SigningTime(),\n    id_countersignature: Countersignature(),\n}\n\ncmsAttributesMap.update(_cmsAttributesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5751.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# S/MIME Version 3.2 Message Specification\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5751.txt\n\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import opentype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5652\nfrom pyasn1_modules import rfc8018\n\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n    return univ.ObjectIdentifier(output)\n\n\n# Imports from RFC 5652 and RFC 8018\n\nIssuerAndSerialNumber = rfc5652.IssuerAndSerialNumber\n\nRecipientKeyIdentifier = rfc5652.RecipientKeyIdentifier\n\nSubjectKeyIdentifier = rfc5652.SubjectKeyIdentifier\n\nrc2CBC = rfc8018.rc2CBC\n\n\n# S/MIME Capabilities Attribute\n\nsmimeCapabilities = univ.ObjectIdentifier('1.2.840.113549.1.9.15')\n\n\nsmimeCapabilityMap = { }\n\n\nclass SMIMECapability(univ.Sequence):\n    pass\n\nSMIMECapability.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('capabilityID', univ.ObjectIdentifier()),\n    namedtype.OptionalNamedType('parameters', univ.Any(),\n        openType=opentype.OpenType('capabilityID', smimeCapabilityMap))\n)\n\n\nclass SMIMECapabilities(univ.SequenceOf):\n    pass\n\nSMIMECapabilities.componentType = SMIMECapability()\n\n\nclass SMIMECapabilitiesParametersForRC2CBC(univ.Integer):\n    # which carries the RC2 Key Length (number of bits)\n    pass\n\n\n# S/MIME Encryption Key Preference Attribute\n\nid_smime = univ.ObjectIdentifier('1.2.840.113549.1.9.16')\n\nid_aa = _OID(id_smime, 2)\n\nid_aa_encrypKeyPref = _OID(id_aa, 11)\n\n\nclass SMIMEEncryptionKeyPreference(univ.Choice):\n    pass\n\nSMIMEEncryptionKeyPreference.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerAndSerialNumber',\n        IssuerAndSerialNumber().subtype(implicitTag=tag.Tag(\n            tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('receipentKeyId',\n        # Yes, 'receipentKeyId' is spelled incorrectly, but kept\n        # this way for alignment with the ASN.1 module in the RFC.\n        RecipientKeyIdentifier().subtype(implicitTag=tag.Tag(\n            tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('subjectAltKeyIdentifier',\n        SubjectKeyIdentifier().subtype(implicitTag=tag.Tag(\n            tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\n\n# The Prefer Binary Inside SMIMECapabilities attribute\n\nid_cap = _OID(id_smime, 11)\n\nid_cap_preferBinaryInside = _OID(id_cap, 1)\n\n\n# CMS Attribute Map\n\n_cmsAttributesMapUpdate = {\n    smimeCapabilities: SMIMECapabilities(),\n    id_aa_encrypKeyPref: SMIMEEncryptionKeyPreference(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n\n\n# SMIMECapabilities Attribute Map\n#\n# Do not include OIDs in the dictionary when the parameters are absent.\n\n_smimeCapabilityMapUpdate = {\n    rc2CBC: SMIMECapabilitiesParametersForRC2CBC(),\n}\n\nsmimeCapabilityMap.update(_smimeCapabilityMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5914.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Trust Anchor Format\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5914.txt\n\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\n\nMAX = float('inf')\n\nCertificate = rfc5280.Certificate\n\nName = rfc5280.Name\n\nExtensions = rfc5280.Extensions\n\nSubjectPublicKeyInfo = rfc5280.SubjectPublicKeyInfo\n\nTBSCertificate = rfc5280.TBSCertificate\n\nCertificatePolicies = rfc5280.CertificatePolicies\n\nKeyIdentifier = rfc5280.KeyIdentifier\n\nNameConstraints = rfc5280.NameConstraints\n\n\nclass CertPolicyFlags(univ.BitString):\n    pass\n\nCertPolicyFlags.namedValues = namedval.NamedValues(\n    ('inhibitPolicyMapping', 0),\n    ('requireExplicitPolicy', 1),\n    ('inhibitAnyPolicy', 2)\n)\n\n\nclass CertPathControls(univ.Sequence):\n    pass\n\nCertPathControls.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('taName', Name()),\n    namedtype.OptionalNamedType('certificate', Certificate().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('policySet', CertificatePolicies().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('policyFlags', CertPolicyFlags().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.OptionalNamedType('nameConstr', NameConstraints().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n    namedtype.OptionalNamedType('pathLenConstraint', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(0, MAX)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4)))\n)\n\n\nclass TrustAnchorTitle(char.UTF8String):\n    pass\n\nTrustAnchorTitle.subtypeSpec = constraint.ValueSizeConstraint(1, 64)\n\n\nclass TrustAnchorInfoVersion(univ.Integer):\n    pass\n\nTrustAnchorInfoVersion.namedValues = namedval.NamedValues(\n    ('v1', 1)\n)\n\n\nclass TrustAnchorInfo(univ.Sequence):\n    pass\n\nTrustAnchorInfo.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version', TrustAnchorInfoVersion().subtype(value='v1')),\n    namedtype.NamedType('pubKey', SubjectPublicKeyInfo()),\n    namedtype.NamedType('keyId', KeyIdentifier()),\n    namedtype.OptionalNamedType('taTitle', TrustAnchorTitle()),\n    namedtype.OptionalNamedType('certPath', CertPathControls()),\n    namedtype.OptionalNamedType('exts', Extensions().subtype(explicitTag=tag.Tag(\n        tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('taTitleLangTag', char.UTF8String().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\n\nclass TrustAnchorChoice(univ.Choice):\n    pass\n\nTrustAnchorChoice.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('certificate', Certificate()),\n    namedtype.NamedType('tbsCert', TBSCertificate().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('taInfo', TrustAnchorInfo().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2)))\n)\n\n\nid_ct_trustAnchorList = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.34')\n\nclass TrustAnchorList(univ.SequenceOf):\n    pass\n\nTrustAnchorList.componentType = TrustAnchorChoice()\nTrustAnchorList.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5915.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Elliptic Curve Private Key\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5915.txt\n\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5480\n\n\nclass ECPrivateKey(univ.Sequence):\n    pass\n\nECPrivateKey.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version', univ.Integer(\n        namedValues=namedval.NamedValues(('ecPrivkeyVer1', 1)))),\n    namedtype.NamedType('privateKey', univ.OctetString()),\n    namedtype.OptionalNamedType('parameters', rfc5480.ECParameters().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('publicKey', univ.BitString().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5934.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Trust Anchor Format\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5934.txt\n\nfrom pyasn1.type import univ, char, namedtype, namedval, tag, constraint, useful\n\nfrom pyasn1_modules import rfc2985\nfrom pyasn1_modules import rfc5280\nfrom pyasn1_modules import rfc5652\nfrom pyasn1_modules import rfc5914\n\nMAX = float('inf')\n\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n    return univ.ObjectIdentifier(output)\n\n\n# Imports from RFC 2985\n\nSingleAttribute = rfc2985.SingleAttribute\n\n\n# Imports from RFC5914\n\nCertPathControls = rfc5914.CertPathControls\n\nTrustAnchorChoice = rfc5914.TrustAnchorChoice\n\nTrustAnchorTitle = rfc5914.TrustAnchorTitle\n\n\n# Imports from RFC 5280\n\nAlgorithmIdentifier = rfc5280.AlgorithmIdentifier\n\nAnotherName = rfc5280.AnotherName\n\nAttribute = rfc5280.Attribute\n\nCertificate = rfc5280.Certificate\n\nCertificateSerialNumber = rfc5280.CertificateSerialNumber\n\nExtension = rfc5280.Extension\n\nExtensions = rfc5280.Extensions\n\nKeyIdentifier = rfc5280.KeyIdentifier\n\nName = rfc5280.Name\n\nSubjectPublicKeyInfo = rfc5280.SubjectPublicKeyInfo\n\nTBSCertificate = rfc5280.TBSCertificate\n\nValidity = rfc5280.Validity\n\n\n# Object Identifier Arc for TAMP Message Content Types\n\nid_tamp = univ.ObjectIdentifier('2.16.840.1.101.2.1.2.77')\n\n\n# TAMP Status Query Message\n\nid_ct_TAMP_statusQuery = _OID(id_tamp, 1)\n\n\nclass TAMPVersion(univ.Integer):\n    pass\n\nTAMPVersion.namedValues = namedval.NamedValues(\n    ('v1', 1),\n    ('v2', 2)\n)\n\n\nclass TerseOrVerbose(univ.Enumerated):\n    pass\n\nTerseOrVerbose.namedValues = namedval.NamedValues(\n    ('terse', 1),\n    ('verbose', 2)\n)\n\n\nclass HardwareSerialEntry(univ.Choice):\n    pass\n\nHardwareSerialEntry.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('all', univ.Null()),\n    namedtype.NamedType('single', univ.OctetString()),\n    namedtype.NamedType('block', univ.Sequence(componentType=namedtype.NamedTypes(\n        namedtype.NamedType('low', univ.OctetString()),\n        namedtype.NamedType('high', univ.OctetString())\n    ))\n    )\n)\n\n\nclass HardwareModules(univ.Sequence):\n    pass\n\nHardwareModules.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('hwType', univ.ObjectIdentifier()),\n    namedtype.NamedType('hwSerialEntries', univ.SequenceOf(\n        componentType=HardwareSerialEntry()).subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, MAX)))\n)\n\n\nclass HardwareModuleIdentifierList(univ.SequenceOf):\n    pass\n\nHardwareModuleIdentifierList.componentType = HardwareModules()\nHardwareModuleIdentifierList.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\nclass Community(univ.ObjectIdentifier):\n    pass\n\n\nclass CommunityIdentifierList(univ.SequenceOf):\n    pass\n\nCommunityIdentifierList.componentType = Community()\nCommunityIdentifierList.subtypeSpec=constraint.ValueSizeConstraint(0, MAX)\n\n\nclass TargetIdentifier(univ.Choice):\n    pass\n\nTargetIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('hwModules', HardwareModuleIdentifierList().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('communities', CommunityIdentifierList().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.NamedType('allModules', univ.Null().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n    namedtype.NamedType('uri', char.IA5String().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4))),\n    namedtype.NamedType('otherName', AnotherName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 5)))\n)\n\n\nclass SeqNumber(univ.Integer):\n    pass\n\nSeqNumber.subtypeSpec = constraint.ValueRangeConstraint(0, 9223372036854775807)\n\n\nclass TAMPMsgRef(univ.Sequence):\n    pass\n\nTAMPMsgRef.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('target', TargetIdentifier()),\n    namedtype.NamedType('seqNum', SeqNumber())\n)\n\n\nclass TAMPStatusQuery(univ.Sequence):\n    pass\n\nTAMPStatusQuery.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version', TAMPVersion().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0)).subtype(value='v2')),\n    namedtype.DefaultedNamedType('terse', TerseOrVerbose().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 1)).subtype(value='verbose')),\n    namedtype.NamedType('query', TAMPMsgRef())\n)\n\n\ntamp_status_query = rfc5652.ContentInfo()\ntamp_status_query['contentType'] = id_ct_TAMP_statusQuery\ntamp_status_query['content'] = TAMPStatusQuery()\n\n\n# TAMP Status Response Message\n\nid_ct_TAMP_statusResponse = _OID(id_tamp, 2)\n\n\nclass KeyIdentifiers(univ.SequenceOf):\n    pass\n\nKeyIdentifiers.componentType = KeyIdentifier()\nKeyIdentifiers.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\nclass TrustAnchorChoiceList(univ.SequenceOf):\n    pass\n\nTrustAnchorChoiceList.componentType = TrustAnchorChoice()\nTrustAnchorChoiceList.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\nclass TAMPSequenceNumber(univ.Sequence):\n    pass\n\nTAMPSequenceNumber.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('keyId', KeyIdentifier()),\n    namedtype.NamedType('seqNumber', SeqNumber())\n)\n\n\nclass TAMPSequenceNumbers(univ.SequenceOf):\n    pass\n\nTAMPSequenceNumbers.componentType = TAMPSequenceNumber()\nTAMPSequenceNumbers.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\nclass TerseStatusResponse(univ.Sequence):\n    pass\n\nTerseStatusResponse.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('taKeyIds', KeyIdentifiers()),\n    namedtype.OptionalNamedType('communities', CommunityIdentifierList())\n)\n\n\nclass VerboseStatusResponse(univ.Sequence):\n    pass\n\nVerboseStatusResponse.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('taInfo', TrustAnchorChoiceList()),\n    namedtype.OptionalNamedType('continPubKeyDecryptAlg',\n        AlgorithmIdentifier().subtype(implicitTag=tag.Tag(\n        tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('communities',\n        CommunityIdentifierList().subtype(implicitTag=tag.Tag(\n        tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('tampSeqNumbers',\n        TAMPSequenceNumbers().subtype(implicitTag=tag.Tag(\n        tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\n\nclass StatusResponse(univ.Choice):\n    pass\n\nStatusResponse.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('terseResponse', TerseStatusResponse().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('verboseResponse', VerboseStatusResponse().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n)\n\n\nclass TAMPStatusResponse(univ.Sequence):\n    pass\n\nTAMPStatusResponse.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version', TAMPVersion().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0)).subtype(value='v2')),\n    namedtype.NamedType('query', TAMPMsgRef()),\n    namedtype.NamedType('response', StatusResponse()),\n    namedtype.DefaultedNamedType('usesApex', univ.Boolean().subtype(value=1))\n)\n\n\ntamp_status_response = rfc5652.ContentInfo()\ntamp_status_response['contentType'] = id_ct_TAMP_statusResponse\ntamp_status_response['content'] = TAMPStatusResponse()\n\n\n# Trust Anchor Update Message\n\nid_ct_TAMP_update = _OID(id_tamp, 3)\n\n\nclass TBSCertificateChangeInfo(univ.Sequence):\n    pass\n\nTBSCertificateChangeInfo.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('serialNumber', CertificateSerialNumber()),\n    namedtype.OptionalNamedType('signature', AlgorithmIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('issuer', Name().subtype(implicitTag=tag.Tag(\n        tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('validity', Validity().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.OptionalNamedType('subject', Name().subtype(implicitTag=tag.Tag(\n        tag.tagClassContext, tag.tagFormatSimple, 3))),\n    namedtype.NamedType('subjectPublicKeyInfo', SubjectPublicKeyInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4))),\n    namedtype.OptionalNamedType('exts', Extensions().subtype(explicitTag=tag.Tag(\n        tag.tagClassContext, tag.tagFormatSimple, 5)))\n)\n\n\nclass TrustAnchorChangeInfo(univ.Sequence):\n    pass\n\nTrustAnchorChangeInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('pubKey', SubjectPublicKeyInfo()),\n    namedtype.OptionalNamedType('keyId', KeyIdentifier()),\n    namedtype.OptionalNamedType('taTitle', TrustAnchorTitle()),\n    namedtype.OptionalNamedType('certPath', CertPathControls()),\n    namedtype.OptionalNamedType('exts', Extensions().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass TrustAnchorChangeInfoChoice(univ.Choice):\n    pass\n\nTrustAnchorChangeInfoChoice.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('tbsCertChange', TBSCertificateChangeInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('taChange', TrustAnchorChangeInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n)\n\n\nclass TrustAnchorUpdate(univ.Choice):\n    pass\n\nTrustAnchorUpdate.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('add', TrustAnchorChoice().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('remove', SubjectPublicKeyInfo().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.NamedType('change', TrustAnchorChangeInfoChoice().subtype(\n        explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 3)))\n)\n\n\nclass TAMPUpdate(univ.Sequence):\n    pass\n\nTAMPUpdate.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version',\n        TAMPVersion().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0)).subtype(value='v2')),\n    namedtype.DefaultedNamedType('terse',\n        TerseOrVerbose().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 1)).subtype(value='verbose')),\n    namedtype.NamedType('msgRef', TAMPMsgRef()),\n    namedtype.NamedType('updates',\n        univ.SequenceOf(componentType=TrustAnchorUpdate()).subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.OptionalNamedType('tampSeqNumbers',\n        TAMPSequenceNumbers().subtype(implicitTag=tag.Tag(\n        tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\n\ntamp_update = rfc5652.ContentInfo()\ntamp_update['contentType'] = id_ct_TAMP_update\ntamp_update['content'] = TAMPUpdate()\n\n\n# Trust Anchor Update Confirm Message\n\nid_ct_TAMP_updateConfirm = _OID(id_tamp, 4)\n\n\nclass StatusCode(univ.Enumerated):\n    pass\n\nStatusCode.namedValues = namedval.NamedValues(\n    ('success', 0),\n    ('decodeFailure', 1),\n    ('badContentInfo', 2),\n    ('badSignedData', 3),\n    ('badEncapContent', 4),\n    ('badCertificate', 5),\n    ('badSignerInfo', 6),\n    ('badSignedAttrs', 7),\n    ('badUnsignedAttrs', 8),\n    ('missingContent', 9),\n    ('noTrustAnchor', 10),\n    ('notAuthorized', 11),\n    ('badDigestAlgorithm', 12),\n    ('badSignatureAlgorithm', 13),\n    ('unsupportedKeySize', 14),\n    ('unsupportedParameters', 15),\n    ('signatureFailure', 16),\n    ('insufficientMemory', 17),\n    ('unsupportedTAMPMsgType', 18),\n    ('apexTAMPAnchor', 19),\n    ('improperTAAddition', 20),\n    ('seqNumFailure', 21),\n    ('contingencyPublicKeyDecrypt', 22),\n    ('incorrectTarget', 23),\n    ('communityUpdateFailed', 24),\n    ('trustAnchorNotFound', 25),\n    ('unsupportedTAAlgorithm', 26),\n    ('unsupportedTAKeySize', 27),\n    ('unsupportedContinPubKeyDecryptAlg', 28),\n    ('missingSignature', 29),\n    ('resourcesBusy', 30),\n    ('versionNumberMismatch', 31),\n    ('missingPolicySet', 32),\n    ('revokedCertificate', 33),\n    ('unsupportedTrustAnchorFormat', 34),\n    ('improperTAChange', 35),\n    ('malformed', 36),\n    ('cmsError', 37),\n    ('unsupportedTargetIdentifier', 38),\n    ('other', 127)\n)\n\n\nclass StatusCodeList(univ.SequenceOf):\n    pass\n\nStatusCodeList.componentType = StatusCode()\nStatusCodeList.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\nclass TerseUpdateConfirm(StatusCodeList):\n    pass\n\n\nclass VerboseUpdateConfirm(univ.Sequence):\n    pass\n\nVerboseUpdateConfirm.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('status', StatusCodeList()),\n    namedtype.NamedType('taInfo', TrustAnchorChoiceList()),\n    namedtype.OptionalNamedType('tampSeqNumbers', TAMPSequenceNumbers()),\n    namedtype.DefaultedNamedType('usesApex', univ.Boolean().subtype(value=1))\n)\n\n\nclass UpdateConfirm(univ.Choice):\n    pass\n\nUpdateConfirm.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('terseConfirm', TerseUpdateConfirm().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('verboseConfirm', VerboseUpdateConfirm().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n)\n\n\nclass TAMPUpdateConfirm(univ.Sequence):\n    pass\n\nTAMPUpdateConfirm.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version', TAMPVersion().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0)).subtype(value='v2')),\n    namedtype.NamedType('update', TAMPMsgRef()),\n    namedtype.NamedType('confirm', UpdateConfirm())\n)\n\n\ntamp_update_confirm = rfc5652.ContentInfo()\ntamp_update_confirm['contentType'] = id_ct_TAMP_updateConfirm\ntamp_update_confirm['content'] = TAMPUpdateConfirm()\n\n\n# Apex Trust Anchor Update Message\n\nid_ct_TAMP_apexUpdate = _OID(id_tamp, 5)\n\n\nclass TAMPApexUpdate(univ.Sequence):\n    pass\n\nTAMPApexUpdate.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version',\n        TAMPVersion().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0)).subtype(value='v2')),\n    namedtype.DefaultedNamedType('terse',\n        TerseOrVerbose().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 1)).subtype(value='verbose')),\n    namedtype.NamedType('msgRef', TAMPMsgRef()),\n    namedtype.NamedType('clearTrustAnchors', univ.Boolean()),\n    namedtype.NamedType('clearCommunities', univ.Boolean()),\n    namedtype.OptionalNamedType('seqNumber', SeqNumber()),\n    namedtype.NamedType('apexTA', TrustAnchorChoice())\n)\n\n\ntamp_apex_update = rfc5652.ContentInfo()\ntamp_apex_update['contentType'] = id_ct_TAMP_apexUpdate\ntamp_apex_update['content'] = TAMPApexUpdate()\n\n\n# Apex Trust Anchor Update Confirm Message\n\nid_ct_TAMP_apexUpdateConfirm = _OID(id_tamp, 6)\n\n\nclass TerseApexUpdateConfirm(StatusCode):\n    pass\n\n\nclass VerboseApexUpdateConfirm(univ.Sequence):\n    pass\n\nVerboseApexUpdateConfirm.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('status', StatusCode()),\n    namedtype.NamedType('taInfo', TrustAnchorChoiceList()),\n    namedtype.OptionalNamedType('communities',\n        CommunityIdentifierList().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('tampSeqNumbers',\n        TAMPSequenceNumbers().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 1)))\n)\n\n\nclass ApexUpdateConfirm(univ.Choice):\n    pass\n\nApexUpdateConfirm.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('terseApexConfirm',\n        TerseApexUpdateConfirm().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0))),\n    namedtype.NamedType('verboseApexConfirm',\n        VerboseApexUpdateConfirm().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatConstructed, 1)))\n)\n\n\nclass TAMPApexUpdateConfirm(univ.Sequence):\n    pass\n\nTAMPApexUpdateConfirm.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version',\n        TAMPVersion().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0)).subtype(value='v2')),\n    namedtype.NamedType('apexReplace', TAMPMsgRef()),\n    namedtype.NamedType('apexConfirm', ApexUpdateConfirm())\n)\n\n\ntamp_apex_update_confirm = rfc5652.ContentInfo()\ntamp_apex_update_confirm['contentType'] = id_ct_TAMP_apexUpdateConfirm\ntamp_apex_update_confirm['content'] = TAMPApexUpdateConfirm()\n\n\n# Community Update Message\n\nid_ct_TAMP_communityUpdate = _OID(id_tamp, 7)\n\n\nclass CommunityUpdates(univ.Sequence):\n    pass\n\nCommunityUpdates.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('remove',\n        CommunityIdentifierList().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('add',\n        CommunityIdentifierList().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 2)))\n)\n\n\nclass TAMPCommunityUpdate(univ.Sequence):\n    pass\n\nTAMPCommunityUpdate.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version',\n        TAMPVersion().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0)).subtype(value='v2')),\n    namedtype.DefaultedNamedType('terse',\n        TerseOrVerbose().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 1)).subtype(value='verbose')),\n    namedtype.NamedType('msgRef', TAMPMsgRef()),\n    namedtype.NamedType('updates', CommunityUpdates())\n)\n\n\ntamp_community_update = rfc5652.ContentInfo()\ntamp_community_update['contentType'] = id_ct_TAMP_communityUpdate\ntamp_community_update['content'] = TAMPCommunityUpdate()\n\n\n# Community Update Confirm Message\n\nid_ct_TAMP_communityUpdateConfirm = _OID(id_tamp, 8)\n\n\nclass TerseCommunityConfirm(StatusCode):\n    pass\n\n\nclass VerboseCommunityConfirm(univ.Sequence):\n    pass\n\nVerboseCommunityConfirm.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('status', StatusCode()),\n    namedtype.OptionalNamedType('communities', CommunityIdentifierList())\n)\n\n\nclass CommunityConfirm(univ.Choice):\n    pass\n\nCommunityConfirm.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('terseCommConfirm',\n        TerseCommunityConfirm().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0))),\n    namedtype.NamedType('verboseCommConfirm',\n        VerboseCommunityConfirm().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatConstructed, 1)))\n)\n\n\nclass TAMPCommunityUpdateConfirm(univ.Sequence):\n    pass\n\nTAMPCommunityUpdateConfirm.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version',\n        TAMPVersion().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0)).subtype(value='v2')),\n    namedtype.NamedType('update', TAMPMsgRef()),\n    namedtype.NamedType('commConfirm', CommunityConfirm())\n)\n\n\ntamp_community_update_confirm = rfc5652.ContentInfo()\ntamp_community_update_confirm['contentType'] = id_ct_TAMP_communityUpdateConfirm\ntamp_community_update_confirm['content'] = TAMPCommunityUpdateConfirm()\n\n\n# Sequence Number Adjust Message\n\nid_ct_TAMP_seqNumAdjust = _OID(id_tamp, 10)\n\n\n\nclass SequenceNumberAdjust(univ.Sequence):\n    pass\n\nSequenceNumberAdjust.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version',\n        TAMPVersion().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0)).subtype(value='v2')),\n    namedtype.NamedType('msgRef', TAMPMsgRef())\n)\n\n\ntamp_sequence_number_adjust = rfc5652.ContentInfo()\ntamp_sequence_number_adjust['contentType'] = id_ct_TAMP_seqNumAdjust\ntamp_sequence_number_adjust['content'] = SequenceNumberAdjust()\n\n\n# Sequence Number Adjust Confirm Message\n\nid_ct_TAMP_seqNumAdjustConfirm = _OID(id_tamp, 11)\n\n\nclass SequenceNumberAdjustConfirm(univ.Sequence):\n    pass\n\nSequenceNumberAdjustConfirm.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version',\n        TAMPVersion().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0)).subtype(value='v2')),\n    namedtype.NamedType('adjust', TAMPMsgRef()),\n    namedtype.NamedType('status', StatusCode())\n)\n\n\ntamp_sequence_number_adjust_confirm = rfc5652.ContentInfo()\ntamp_sequence_number_adjust_confirm['contentType'] = id_ct_TAMP_seqNumAdjustConfirm\ntamp_sequence_number_adjust_confirm['content'] = SequenceNumberAdjustConfirm()\n\n\n# TAMP Error Message\n\nid_ct_TAMP_error = _OID(id_tamp, 9)\n\n\nclass TAMPError(univ.Sequence):\n    pass\n\nTAMPError.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version',\n        TAMPVersion().subtype(implicitTag=tag.Tag(tag.tagClassContext,\n        tag.tagFormatSimple, 0)).subtype(value='v2')),\n    namedtype.NamedType('msgType', univ.ObjectIdentifier()),\n    namedtype.NamedType('status', StatusCode()),\n    namedtype.OptionalNamedType('msgRef', TAMPMsgRef())\n)\n\n\ntamp_error = rfc5652.ContentInfo()\ntamp_error['contentType'] = id_ct_TAMP_error\ntamp_error['content'] = TAMPError()\n\n\n# Object Identifier Arc for Attributes\n\nid_attributes = univ.ObjectIdentifier('2.16.840.1.101.2.1.5')\n\n\n# contingency-public-key-decrypt-key unsigned attribute\n\nid_aa_TAMP_contingencyPublicKeyDecryptKey = _OID(id_attributes, 63)\n\n\nclass PlaintextSymmetricKey(univ.OctetString):\n    pass\n\n\ncontingency_public_key_decrypt_key = Attribute()\ncontingency_public_key_decrypt_key['type'] = id_aa_TAMP_contingencyPublicKeyDecryptKey\ncontingency_public_key_decrypt_key['values'][0] = PlaintextSymmetricKey()\n\n\n# id-pe-wrappedApexContinKey extension\n\nid_pe_wrappedApexContinKey =univ.ObjectIdentifier('1.3.6.1.5.5.7.1.20')\n\n\nclass ApexContingencyKey(univ.Sequence):\n    pass\n\nApexContingencyKey.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('wrapAlgorithm', AlgorithmIdentifier()),\n    namedtype.NamedType('wrappedContinPubKey', univ.OctetString())\n)\n\n\nwrappedApexContinKey = Extension()\nwrappedApexContinKey['extnID'] = id_pe_wrappedApexContinKey\nwrappedApexContinKey['critical'] = 0\nwrappedApexContinKey['extnValue'] = univ.OctetString()\n\n\n# Add to the map of CMS Content Type OIDs to Content Types in\n# rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_TAMP_statusQuery: TAMPStatusQuery(),\n    id_ct_TAMP_statusResponse: TAMPStatusResponse(),\n    id_ct_TAMP_update: TAMPUpdate(),\n    id_ct_TAMP_updateConfirm: TAMPUpdateConfirm(),\n    id_ct_TAMP_apexUpdate: TAMPApexUpdate(),\n    id_ct_TAMP_apexUpdateConfirm: TAMPApexUpdateConfirm(),\n    id_ct_TAMP_communityUpdate: TAMPCommunityUpdate(),\n    id_ct_TAMP_communityUpdateConfirm: TAMPCommunityUpdateConfirm(),\n    id_ct_TAMP_seqNumAdjust: SequenceNumberAdjust(),\n    id_ct_TAMP_seqNumAdjustConfirm: SequenceNumberAdjustConfirm(),\n    id_ct_TAMP_error: TAMPError(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n\n\n# Add to the map of CMS Attribute OIDs to Attribute Values in\n# rfc5652.py\n\n_cmsAttributesMapUpdate = {\n    id_aa_TAMP_contingencyPublicKeyDecryptKey: PlaintextSymmetricKey(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n\n\n# Add to the map of Certificate Extension OIDs to Extensions in\n# rfc5280.py\n\n_certificateExtensionsMap = {\n    id_pe_wrappedApexContinKey: ApexContingencyKey(),\n}\n\nrfc5280.certificateExtensionsMap.update(_certificateExtensionsMap)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5940.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n# Modified by Russ Housley to add map for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Additional CMS Revocation Information Choices\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5940.txt\n#\n\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc2560\nfrom pyasn1_modules import rfc5652\n\n\n# RevocationInfoChoice for OCSP response:\n# The OID is included in otherRevInfoFormat, and\n# signed OCSPResponse is included in otherRevInfo\n\nid_ri_ocsp_response = univ.ObjectIdentifier('1.3.6.1.5.5.7.16.2')\n\nOCSPResponse = rfc2560.OCSPResponse\n\n\n# RevocationInfoChoice for SCVP request/response:\n# The OID is included in otherRevInfoFormat, and\n# SCVPReqRes is included in otherRevInfo\n\nid_ri_scvp = univ.ObjectIdentifier('1.3.6.1.5.5.7.16.4')\n\nContentInfo = rfc5652.ContentInfo\n\nclass SCVPReqRes(univ.Sequence):\n    pass\n\nSCVPReqRes.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('request',\n        ContentInfo().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('response', ContentInfo())\n)\n\n\n# Map of Revocation Info Format OIDs to Revocation Info Format\n# is added to the ones that are in rfc5652.py\n\n_otherRevInfoFormatMapUpdate = {\n     id_ri_ocsp_response: OCSPResponse(),\n     id_ri_scvp: SCVPReqRes(),\n}\n\nrfc5652.otherRevInfoFormatMap.update(_otherRevInfoFormatMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5958.py",
    "content": "#\n# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley.\n# Modified by Russ Housley to add a map for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Asymmetric Key Packages, which is essentially version 2 of\n#   the PrivateKeyInfo structure in PKCS#8 in RFC 5208\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5958.txt\n\nfrom pyasn1.type import univ, constraint, namedtype, namedval, tag\n\nfrom pyasn1_modules import rfc5280\nfrom pyasn1_modules import rfc5652\n\n\nMAX = float('inf')\n\n\nclass KeyEncryptionAlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass PrivateKeyAlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass EncryptedData(univ.OctetString):\n    pass\n\n\nclass EncryptedPrivateKeyInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('encryptionAlgorithm', KeyEncryptionAlgorithmIdentifier()),\n        namedtype.NamedType('encryptedData', EncryptedData())\n    )\n\n\nclass Version(univ.Integer):\n    namedValues = namedval.NamedValues(('v1', 0), ('v2', 1))\n\n\nclass PrivateKey(univ.OctetString):\n    pass\n\n\nclass Attributes(univ.SetOf):\n    componentType = rfc5652.Attribute()\n\n\nclass PublicKey(univ.BitString):\n   pass\n\n\n# OneAsymmetricKey is essentially version 2 of PrivateKeyInfo.\n# If publicKey is present, then the version must be v2;\n# otherwise, the version should be v1.\n\nclass OneAsymmetricKey(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('version', Version()),\n        namedtype.NamedType('privateKeyAlgorithm', PrivateKeyAlgorithmIdentifier()),\n        namedtype.NamedType('privateKey', PrivateKey()),\n        namedtype.OptionalNamedType('attributes', Attributes().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n        namedtype.OptionalNamedType('publicKey', PublicKey().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n    )\n\n\nclass PrivateKeyInfo(OneAsymmetricKey):\n    pass\n\n\n# The CMS AsymmetricKeyPackage Content Type\n\nid_ct_KP_aKeyPackage = univ.ObjectIdentifier('2.16.840.1.101.2.1.2.78.5')\n\nclass AsymmetricKeyPackage(univ.SequenceOf):\n    pass\n\nAsymmetricKeyPackage.componentType = OneAsymmetricKey()\nAsymmetricKeyPackage.sizeSpec=constraint.ValueSizeConstraint(1, MAX)\n    \n\n# Map of Content Type OIDs to Content Types is added to the\n# ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_KP_aKeyPackage: AsymmetricKeyPackage(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc5990.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Use of the RSA-KEM Key Transport Algorithm in the CMS\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc5990.txt\n#\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\nMAX = float('inf')\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n    return univ.ObjectIdentifier(output)\n\n\n# Imports from RFC 5280\n\nAlgorithmIdentifier = rfc5280.AlgorithmIdentifier\n\n\n# Useful types and definitions\n\nclass NullParms(univ.Null):\n    pass\n\n\n# Object identifier arcs\n\nis18033_2 = _OID(1, 0, 18033, 2)\n\nnistAlgorithm = _OID(2, 16, 840, 1, 101, 3, 4)\n\npkcs_1 = _OID(1, 2, 840, 113549, 1, 1)\n\nx9_44 = _OID(1, 3, 133, 16, 840, 9, 44)\n\nx9_44_components = _OID(x9_44, 1)\n\n\n# Types for algorithm identifiers\n\nclass Camellia_KeyWrappingScheme(AlgorithmIdentifier):\n    pass\n\nclass DataEncapsulationMechanism(AlgorithmIdentifier):\n    pass\n\nclass KDF2_HashFunction(AlgorithmIdentifier):\n    pass\n\nclass KDF3_HashFunction(AlgorithmIdentifier):\n    pass\n\nclass KeyDerivationFunction(AlgorithmIdentifier):\n    pass\n\nclass KeyEncapsulationMechanism(AlgorithmIdentifier):\n    pass\n\nclass X9_SymmetricKeyWrappingScheme(AlgorithmIdentifier):\n    pass\n\n\n# RSA-KEM Key Transport Algorithm\n\nid_rsa_kem = _OID(1, 2, 840, 113549, 1, 9, 16, 3, 14)\n\n\nclass GenericHybridParameters(univ.Sequence):\n    pass\n\nGenericHybridParameters.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('kem', KeyEncapsulationMechanism()),\n    namedtype.NamedType('dem', DataEncapsulationMechanism())\n)\n\n\nrsa_kem = AlgorithmIdentifier()\nrsa_kem['algorithm'] = id_rsa_kem\nrsa_kem['parameters'] = GenericHybridParameters()\n\n\n# KEM-RSA Key Encapsulation Mechanism\n\nid_kem_rsa = _OID(is18033_2, 2, 4)\n\n\nclass KeyLength(univ.Integer):\n    pass\n\nKeyLength.subtypeSpec = constraint.ValueRangeConstraint(1, MAX)\n\n\nclass RsaKemParameters(univ.Sequence):\n    pass\n\nRsaKemParameters.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('keyDerivationFunction', KeyDerivationFunction()),\n    namedtype.NamedType('keyLength', KeyLength())\n)\n\n\nkem_rsa = AlgorithmIdentifier()\nkem_rsa['algorithm'] = id_kem_rsa\nkem_rsa['parameters'] = RsaKemParameters()\n\n\n# Key Derivation Functions\n\nid_kdf_kdf2 = _OID(x9_44_components, 1)\n\nid_kdf_kdf3 = _OID(x9_44_components, 2)\n\n\nkdf2 = AlgorithmIdentifier()\nkdf2['algorithm'] = id_kdf_kdf2\nkdf2['parameters'] = KDF2_HashFunction()\n\nkdf3 = AlgorithmIdentifier()\nkdf3['algorithm'] = id_kdf_kdf3\nkdf3['parameters'] = KDF3_HashFunction()\n\n\n# Hash Functions\n\nid_sha1 = _OID(1, 3, 14, 3, 2, 26)\n\nid_sha224 = _OID(2, 16, 840, 1, 101, 3, 4, 2, 4)\n\nid_sha256 = _OID(2, 16, 840, 1, 101, 3, 4, 2, 1)\n\nid_sha384 = _OID(2, 16, 840, 1, 101, 3, 4, 2, 2)\n\nid_sha512 = _OID(2, 16, 840, 1, 101, 3, 4, 2, 3)\n\n\nsha1 = AlgorithmIdentifier()\nsha1['algorithm'] = id_sha1\nsha1['parameters'] = univ.Null(\"\")\n\nsha224 = AlgorithmIdentifier()\nsha224['algorithm'] = id_sha224\nsha224['parameters'] = univ.Null(\"\")\n\nsha256 = AlgorithmIdentifier()\nsha256['algorithm'] = id_sha256\nsha256['parameters'] = univ.Null(\"\")\n\nsha384 = AlgorithmIdentifier()\nsha384['algorithm'] = id_sha384\nsha384['parameters'] = univ.Null(\"\")\n\nsha512 = AlgorithmIdentifier()\nsha512['algorithm'] = id_sha512\nsha512['parameters'] = univ.Null(\"\")\n\n\n# Symmetric Key-Wrapping Schemes\n\nid_aes128_Wrap = _OID(nistAlgorithm, 1, 5)\n\nid_aes192_Wrap = _OID(nistAlgorithm, 1, 25)\n\nid_aes256_Wrap = _OID(nistAlgorithm, 1, 45)\n\nid_alg_CMS3DESwrap = _OID(1, 2, 840, 113549, 1, 9, 16, 3, 6)\n\nid_camellia128_Wrap = _OID(1, 2, 392, 200011, 61, 1, 1, 3, 2)\n\nid_camellia192_Wrap = _OID(1, 2, 392, 200011, 61, 1, 1, 3, 3)\n\nid_camellia256_Wrap = _OID(1, 2, 392, 200011, 61, 1, 1, 3, 4)\n\n\naes128_Wrap = AlgorithmIdentifier()\naes128_Wrap['algorithm'] = id_aes128_Wrap\n# aes128_Wrap['parameters'] are absent\n\naes192_Wrap = AlgorithmIdentifier()\naes192_Wrap['algorithm'] = id_aes128_Wrap\n# aes192_Wrap['parameters'] are absent\n\naes256_Wrap = AlgorithmIdentifier()\naes256_Wrap['algorithm'] = id_sha256\n# aes256_Wrap['parameters'] are absent\n\ntdes_Wrap = AlgorithmIdentifier()\ntdes_Wrap['algorithm'] = id_alg_CMS3DESwrap\ntdes_Wrap['parameters'] = univ.Null(\"\")\n\ncamellia128_Wrap = AlgorithmIdentifier()\ncamellia128_Wrap['algorithm'] = id_camellia128_Wrap\n# camellia128_Wrap['parameters'] are absent\n\ncamellia192_Wrap = AlgorithmIdentifier()\ncamellia192_Wrap['algorithm'] = id_camellia192_Wrap\n# camellia192_Wrap['parameters'] are absent\n\ncamellia256_Wrap = AlgorithmIdentifier()\ncamellia256_Wrap['algorithm'] = id_camellia256_Wrap\n# camellia256_Wrap['parameters'] are absent\n\n\n# Update the Algorithm Identifier map in rfc5280.py.\n# Note that the ones that must not have parameters are not added to the map.\n\n_algorithmIdentifierMapUpdate = {\n    id_rsa_kem: GenericHybridParameters(),\n    id_kem_rsa: RsaKemParameters(),\n    id_kdf_kdf2: KDF2_HashFunction(),\n    id_kdf_kdf3: KDF3_HashFunction(),\n    id_sha1: univ.Null(),\n    id_sha224: univ.Null(),\n    id_sha256: univ.Null(),\n    id_sha384: univ.Null(),\n    id_sha512: univ.Null(),\n    id_alg_CMS3DESwrap: univ.Null(),\n}\n\nrfc5280.algorithmIdentifierMap.update(_algorithmIdentifierMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc6010.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n# Modified by Russ Housley to add maps for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Certificate Extension for CMS Content Constraints (CCC)\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc6010.txt\n#\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\nMAX = float('inf')\n\n\nAttributeType = rfc5280.AttributeType\n\nAttributeValue = rfc5280.AttributeValue\n\n\nid_ct_anyContentType = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.0')\n\n\nclass AttrConstraint(univ.Sequence):\n    pass\n\nAttrConstraint.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('attrType', AttributeType()),\n    namedtype.NamedType('attrValues', univ.SetOf(\n        componentType=AttributeValue()).subtype(subtypeSpec=constraint.ValueSizeConstraint(1, MAX)))\n)\n\n\nclass AttrConstraintList(univ.SequenceOf):\n    pass\n\nAttrConstraintList.componentType = AttrConstraint()\nAttrConstraintList.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\nclass ContentTypeGeneration(univ.Enumerated):\n    pass\n\nContentTypeGeneration.namedValues = namedval.NamedValues(\n    ('canSource', 0),\n    ('cannotSource', 1)\n)\n\n\nclass ContentTypeConstraint(univ.Sequence):\n    pass\n\nContentTypeConstraint.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('contentType', univ.ObjectIdentifier()),\n    namedtype.DefaultedNamedType('canSource', ContentTypeGeneration().subtype(value='canSource')),\n    namedtype.OptionalNamedType('attrConstraints', AttrConstraintList())\n)\n\n\n# CMS Content Constraints (CCC) Extension and Object Identifier\n\nid_pe_cmsContentConstraints = univ.ObjectIdentifier('1.3.6.1.5.5.7.1.18')\n\nclass CMSContentConstraints(univ.SequenceOf):\n    pass\n\nCMSContentConstraints.componentType = ContentTypeConstraint()\nCMSContentConstraints.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\n# Map of Certificate Extension OIDs to Extensions\n# To be added to the ones that are in rfc5280.py\n\n_certificateExtensionsMap = {\n    id_pe_cmsContentConstraints: CMSContentConstraints(),\n}\n\nrfc5280.certificateExtensionsMap.update(_certificateExtensionsMap)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc6019.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley.\n# Modified by Russ Housley to add a map for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# BinaryTime: An Alternate Format for Representing Date and Time\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc6019.txt\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5652\n\nMAX = float('inf')\n\n\n# BinaryTime: Represent date and time as an integer \n\nclass BinaryTime(univ.Integer):\n    pass\n\nBinaryTime.subtypeSpec = constraint.ValueRangeConstraint(0, MAX)\n\n\n# CMS Attribute for representing signing time in BinaryTime\n\nid_aa_binarySigningTime = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.46')\n\nclass BinarySigningTime(BinaryTime):\n    pass\n\n\n# Map of Attribute Type OIDs to Attributes ia added to the\n# ones that are in rfc5652.py\n\n_cmsAttributesMapUpdate = {\n    id_aa_binarySigningTime: BinarySigningTime(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc6031.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# CMS Symmetric Key Package Content Type\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc6031.txt\n#\n\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import opentype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nfrom pyasn1_modules import rfc5652\nfrom pyasn1_modules import rfc6019\n\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n    return univ.ObjectIdentifier(output)\n\n\nMAX = float('inf')\n\nid_pskc = univ.ObjectIdentifier('1.2.840.113549.1.9.16.12')\n\n\n# Symmetric Key Package Attributes\n\nid_pskc_manufacturer = _OID(id_pskc, 1)\n\nclass at_pskc_manufacturer(char.UTF8String):\n    pass\n\n\nid_pskc_serialNo = _OID(id_pskc, 2)\n\nclass at_pskc_serialNo(char.UTF8String):\n    pass\n\n\nid_pskc_model = _OID(id_pskc, 3)\n\nclass at_pskc_model(char.UTF8String):\n    pass\n\n\nid_pskc_issueNo = _OID(id_pskc, 4)\n\nclass at_pskc_issueNo(char.UTF8String):\n    pass\n\n\nid_pskc_deviceBinding = _OID(id_pskc, 5)\n\nclass at_pskc_deviceBinding(char.UTF8String):\n    pass\n\n\nid_pskc_deviceStartDate = _OID(id_pskc, 6)\n\nclass at_pskc_deviceStartDate(useful.GeneralizedTime):\n    pass\n\n\nid_pskc_deviceExpiryDate = _OID(id_pskc, 7)\n\nclass at_pskc_deviceExpiryDate(useful.GeneralizedTime):\n    pass\n\n\nid_pskc_moduleId = _OID(id_pskc, 8)\n\nclass at_pskc_moduleId(char.UTF8String):\n    pass\n\n\nid_pskc_deviceUserId = _OID(id_pskc, 26)\n\nclass at_pskc_deviceUserId(char.UTF8String):\n    pass\n\n\n# Symmetric Key Attributes\n\nid_pskc_keyId = _OID(id_pskc, 9)\n\nclass at_pskc_keyUserId(char.UTF8String):\n    pass\n\n\nid_pskc_algorithm = _OID(id_pskc, 10)\n\nclass at_pskc_algorithm(char.UTF8String):\n    pass\n\n\nid_pskc_issuer = _OID(id_pskc, 11)\n\nclass at_pskc_issuer(char.UTF8String):\n    pass\n\n\nid_pskc_keyProfileId = _OID(id_pskc, 12)\n\nclass at_pskc_keyProfileId(char.UTF8String):\n    pass\n\n\nid_pskc_keyReference = _OID(id_pskc, 13)\n\nclass at_pskc_keyReference(char.UTF8String):\n    pass\n\n\nid_pskc_friendlyName = _OID(id_pskc, 14)\n\nclass FriendlyName(univ.Sequence):\n    pass\n\nFriendlyName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('friendlyName', char.UTF8String()),\n    namedtype.OptionalNamedType('friendlyNameLangTag', char.UTF8String())\n)\n\nclass at_pskc_friendlyName(FriendlyName):\n    pass\n\n\nid_pskc_algorithmParameters = _OID(id_pskc, 15)\n\nclass Encoding(char.UTF8String):\n    pass\n\nEncoding.namedValues = namedval.NamedValues(\n    ('dec',   \"DECIMAL\"),\n    ('hex',   \"HEXADECIMAL\"),\n    ('alpha', \"ALPHANUMERIC\"),\n    ('b64',   \"BASE64\"),\n    ('bin',   \"BINARY\")\n)\n\nEncoding.subtypeSpec = constraint.SingleValueConstraint(\n    \"DECIMAL\", \"HEXADECIMAL\", \"ALPHANUMERIC\", \"BASE64\", \"BINARY\" )\n\nclass ChallengeFormat(univ.Sequence):\n    pass\n\nChallengeFormat.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('encoding', Encoding()),\n    namedtype.DefaultedNamedType('checkDigit',\n        univ.Boolean().subtype(value=0)),\n    namedtype.NamedType('min', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(0, MAX))),\n    namedtype.NamedType('max', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(0, MAX)))\n)\n\nclass ResponseFormat(univ.Sequence):\n    pass\n\nResponseFormat.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('encoding', Encoding()),\n    namedtype.NamedType('length', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(0, MAX))),\n    namedtype.DefaultedNamedType('checkDigit',\n        univ.Boolean().subtype(value=0))\n)\n\nclass PSKCAlgorithmParameters(univ.Choice):\n    pass\n\nPSKCAlgorithmParameters.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('suite', char.UTF8String()),\n    namedtype.NamedType('challengeFormat', ChallengeFormat().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('responseFormat', ResponseFormat().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 1)))\n)\n\nclass at_pskc_algorithmParameters(PSKCAlgorithmParameters):\n    pass\n\n\nid_pskc_counter = _OID(id_pskc, 16)\n\nclass at_pskc_counter(univ.Integer):\n    pass\n\nat_pskc_counter.subtypeSpec = constraint.ValueRangeConstraint(0, MAX)\n\n\nid_pskc_time = _OID(id_pskc, 17)\n\nclass at_pskc_time(rfc6019.BinaryTime):\n    pass\n\n\nid_pskc_timeInterval = _OID(id_pskc, 18)\n\nclass at_pskc_timeInterval(univ.Integer):\n    pass\n\nat_pskc_timeInterval.subtypeSpec = constraint.ValueRangeConstraint(0, MAX)\n\n\nid_pskc_timeDrift = _OID(id_pskc, 19)\n\nclass at_pskc_timeDrift(univ.Integer):\n    pass\n\nat_pskc_timeDrift.subtypeSpec = constraint.ValueRangeConstraint(0, MAX)\n\n\nid_pskc_valueMAC = _OID(id_pskc, 20)\n\nclass ValueMac(univ.Sequence):\n    pass\n\nValueMac.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('macAlgorithm', char.UTF8String()),\n    namedtype.NamedType('mac', char.UTF8String())\n)\n\nclass at_pskc_valueMAC(ValueMac):\n    pass\n\n\nid_pskc_keyUserId = _OID(id_pskc, 27)\n\nclass at_pskc_keyId(char.UTF8String):\n    pass\n\n\nid_pskc_keyStartDate = _OID(id_pskc, 21)\n\nclass at_pskc_keyStartDate(useful.GeneralizedTime):\n    pass\n\n\nid_pskc_keyExpiryDate = _OID(id_pskc, 22)\n\nclass at_pskc_keyExpiryDate(useful.GeneralizedTime):\n    pass\n\n\nid_pskc_numberOfTransactions = _OID(id_pskc, 23)\n\nclass at_pskc_numberOfTransactions(univ.Integer):\n    pass\n    \nat_pskc_numberOfTransactions.subtypeSpec = constraint.ValueRangeConstraint(0, MAX)\n\n\nid_pskc_keyUsages = _OID(id_pskc, 24)\n\nclass PSKCKeyUsage(char.UTF8String):\n    pass\n\nPSKCKeyUsage.namedValues = namedval.NamedValues(\n    ('otp',       \"OTP\"),\n    ('cr',        \"CR\"),\n    ('encrypt',   \"Encrypt\"),\n    ('integrity', \"Integrity\"),\n    ('verify',    \"Verify\"),\n    ('unlock',    \"Unlock\"),\n    ('decrypt',   \"Decrypt\"),\n    ('keywrap',   \"KeyWrap\"),\n    ('unwrap',    \"Unwrap\"),\n    ('derive',    \"Derive\"),\n    ('generate',  \"Generate\")\n)\n\nPSKCKeyUsage.subtypeSpec = constraint.SingleValueConstraint(\n    \"OTP\", \"CR\", \"Encrypt\", \"Integrity\", \"Verify\", \"Unlock\",\n    \"Decrypt\", \"KeyWrap\", \"Unwrap\", \"Derive\", \"Generate\" )\n\nclass PSKCKeyUsages(univ.SequenceOf):\n    pass\n\nPSKCKeyUsages.componentType = PSKCKeyUsage()\n\nclass at_pskc_keyUsage(PSKCKeyUsages):\n    pass\n\n\nid_pskc_pinPolicy = _OID(id_pskc, 25)\n\nclass PINUsageMode(char.UTF8String):\n    pass\n\nPINUsageMode.namedValues = namedval.NamedValues(\n    (\"local\",       \"Local\"),\n    (\"prepend\",     \"Prepend\"),\n    (\"append\",      \"Append\"),\n    (\"algorithmic\", \"Algorithmic\")\n)\n\nPINUsageMode.subtypeSpec = constraint.SingleValueConstraint(\n    \"Local\", \"Prepend\", \"Append\", \"Algorithmic\" )\n\nclass PINPolicy(univ.Sequence):\n    pass\n\nPINPolicy.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('pinKeyId', char.UTF8String().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('pinUsageMode', PINUsageMode().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('maxFailedAttempts', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(0, MAX)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.OptionalNamedType('minLength', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(0, MAX)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n    namedtype.OptionalNamedType('maxLength', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(0, MAX)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 4))),\n    namedtype.OptionalNamedType('pinEncoding', Encoding().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 5)))\n)\n\nclass at_pskc_pinPolicy(PINPolicy):\n    pass\n\n\n# Map of Symmetric Key Package Attribute OIDs to Attributes\n\nsKeyPkgAttributesMap = {\n     id_pskc_manufacturer: at_pskc_manufacturer(),\n     id_pskc_serialNo: at_pskc_serialNo(),\n     id_pskc_model: at_pskc_model(),\n     id_pskc_issueNo: at_pskc_issueNo(),\n     id_pskc_deviceBinding: at_pskc_deviceBinding(),\n     id_pskc_deviceStartDate: at_pskc_deviceStartDate(),\n     id_pskc_deviceExpiryDate: at_pskc_deviceExpiryDate(),\n     id_pskc_moduleId: at_pskc_moduleId(),\n     id_pskc_deviceUserId: at_pskc_deviceUserId(),\n}\n\n\n# Map of Symmetric Key Attribute OIDs to Attributes\n\nsKeyAttributesMap = {\n     id_pskc_keyId: at_pskc_keyId(),\n     id_pskc_algorithm: at_pskc_algorithm(),\n     id_pskc_issuer: at_pskc_issuer(),\n     id_pskc_keyProfileId: at_pskc_keyProfileId(),\n     id_pskc_keyReference: at_pskc_keyReference(),\n     id_pskc_friendlyName: at_pskc_friendlyName(),\n     id_pskc_algorithmParameters: at_pskc_algorithmParameters(),\n     id_pskc_counter: at_pskc_counter(),\n     id_pskc_time: at_pskc_time(),\n     id_pskc_timeInterval: at_pskc_timeInterval(),\n     id_pskc_timeDrift: at_pskc_timeDrift(),\n     id_pskc_valueMAC: at_pskc_valueMAC(),\n     id_pskc_keyUserId: at_pskc_keyUserId(),\n     id_pskc_keyStartDate: at_pskc_keyStartDate(),\n     id_pskc_keyExpiryDate: at_pskc_keyExpiryDate(),\n     id_pskc_numberOfTransactions: at_pskc_numberOfTransactions(),\n     id_pskc_keyUsages: at_pskc_keyUsage(),\n     id_pskc_pinPolicy: at_pskc_pinPolicy(),\n}\n\n\n# This definition replaces Attribute() from rfc5652.py; it is the same except\n# that opentype is added with sKeyPkgAttributesMap and sKeyAttributesMap\n\nclass AttributeType(univ.ObjectIdentifier):\n    pass\n\n\nclass AttributeValue(univ.Any):\n    pass\n\n\nclass SKeyAttribute(univ.Sequence):\n    pass\n\nSKeyAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('attrType', AttributeType()),\n    namedtype.NamedType('attrValues',\n        univ.SetOf(componentType=AttributeValue()),\n        openType=opentype.OpenType('attrType', sKeyAttributesMap)\n    )\n)\n\n\nclass SKeyPkgAttribute(univ.Sequence):\n    pass\n\nSKeyPkgAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('attrType', AttributeType()),\n    namedtype.NamedType('attrValues',\n        univ.SetOf(componentType=AttributeValue()),\n        openType=opentype.OpenType('attrType', sKeyPkgAttributesMap)\n    )\n)\n\n\n# Symmetric Key Package Content Type\n\nid_ct_KP_sKeyPackage = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.25')\n\n\nclass KeyPkgVersion(univ.Integer):\n    pass\n\nKeyPkgVersion.namedValues = namedval.NamedValues(\n    ('v1', 1)\n)\n\n\nclass OneSymmetricKey(univ.Sequence):\n    pass\n\nOneSymmetricKey.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('sKeyAttrs',\n        univ.SequenceOf(componentType=SKeyAttribute()).subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, MAX))),\n    namedtype.OptionalNamedType('sKey', univ.OctetString())\n)\n\nOneSymmetricKey.sizeSpec = univ.Sequence.sizeSpec + constraint.ValueSizeConstraint(1, 2)\n\n\nclass SymmetricKeys(univ.SequenceOf):\n    pass\n\nSymmetricKeys.componentType = OneSymmetricKey()\nSymmetricKeys.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\nclass SymmetricKeyPackage(univ.Sequence):\n    pass\n\nSymmetricKeyPackage.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version', KeyPkgVersion().subtype(value='v1')),\n    namedtype.OptionalNamedType('sKeyPkgAttrs',\n        univ.SequenceOf(componentType=SKeyPkgAttribute()).subtype(\n            subtypeSpec=constraint.ValueSizeConstraint(1, MAX),\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('sKeys', SymmetricKeys())\n)\n\n\n# Map of Content Type OIDs to Content Types are\n# added to the ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_KP_sKeyPackage: SymmetricKeyPackage(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc6032.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# CMS Encrypted Key Package Content Type\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc6032.txt\n#\n\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5652\nfrom pyasn1_modules import rfc5083\n\n\n# Content Decryption Key Identifier attribute\n\nid_aa_KP_contentDecryptKeyID = univ.ObjectIdentifier('2.16.840.1.101.2.1.5.66')\n\nclass ContentDecryptKeyID(univ.OctetString):\n    pass\n\naa_content_decrypt_key_identifier = rfc5652.Attribute()\naa_content_decrypt_key_identifier['attrType'] = id_aa_KP_contentDecryptKeyID\naa_content_decrypt_key_identifier['attrValues'][0] = ContentDecryptKeyID()\n\n\n# Encrypted Key Package Content Type\n\nid_ct_KP_encryptedKeyPkg = univ.ObjectIdentifier('2.16.840.1.101.2.1.2.78.2')\n\nclass EncryptedKeyPackage(univ.Choice):\n    pass\n\nEncryptedKeyPackage.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('encrypted', rfc5652.EncryptedData()),\n    namedtype.NamedType('enveloped', rfc5652.EnvelopedData().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('authEnveloped', rfc5083.AuthEnvelopedData().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\n# Map of Attribute Type OIDs to Attributes are\n# added to the ones that are in rfc5652.py\n\n_cmsAttributesMapUpdate = {\n    id_aa_KP_contentDecryptKeyID: ContentDecryptKeyID(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n\n\n# Map of Content Type OIDs to Content Types are\n# added to the ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_KP_encryptedKeyPkg: EncryptedKeyPackage(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc6210.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Experiment for Hash Functions with Parameters in the CMS\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc6210.txt\n#\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\n\nid_alg_MD5_XOR_EXPERIMENT = univ.ObjectIdentifier('1.2.840.113549.1.9.16.3.13')\n\n\nclass MD5_XOR_EXPERIMENT(univ.OctetString):\n    pass\n\nMD5_XOR_EXPERIMENT.subtypeSpec = constraint.ValueSizeConstraint(64, 64)\n\n\nmda_xor_md5_EXPERIMENT = rfc5280.AlgorithmIdentifier()\nmda_xor_md5_EXPERIMENT['algorithm'] = id_alg_MD5_XOR_EXPERIMENT\nmda_xor_md5_EXPERIMENT['parameters'] = MD5_XOR_EXPERIMENT()\n\n\n# Map of Algorithm Identifier OIDs to Parameters added to the\n# ones that are in rfc5280.py.\n\n_algorithmIdentifierMapUpdate = {\n    id_alg_MD5_XOR_EXPERIMENT: MD5_XOR_EXPERIMENT(),\n}\n\nrfc5280.algorithmIdentifierMap.update(_algorithmIdentifierMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc6211.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# CMS Algorithm Identifier Protection Attribute\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc6211.txt\n#\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5652\n\n\n# Imports from RFC 5652\n\nDigestAlgorithmIdentifier = rfc5652.DigestAlgorithmIdentifier\n\nMessageAuthenticationCodeAlgorithm = rfc5652.MessageAuthenticationCodeAlgorithm\n\nSignatureAlgorithmIdentifier = rfc5652.SignatureAlgorithmIdentifier\n\n\n# CMS Algorithm Protection attribute\n\nid_aa_cmsAlgorithmProtect = univ.ObjectIdentifier('1.2.840.113549.1.9.52')\n\n\nclass CMSAlgorithmProtection(univ.Sequence):\n    pass\n\nCMSAlgorithmProtection.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('digestAlgorithm', DigestAlgorithmIdentifier()),\n    namedtype.OptionalNamedType('signatureAlgorithm',\n        SignatureAlgorithmIdentifier().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('macAlgorithm',\n        MessageAuthenticationCodeAlgorithm().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\nCMSAlgorithmProtection.subtypeSpec = constraint.ConstraintsUnion(\n    constraint.WithComponentsConstraint(\n        ('signatureAlgorithm', constraint.ComponentPresentConstraint()),\n        ('macAlgorithm', constraint.ComponentAbsentConstraint())),\n    constraint.WithComponentsConstraint(\n        ('signatureAlgorithm', constraint.ComponentAbsentConstraint()),\n        ('macAlgorithm', constraint.ComponentPresentConstraint()))\n)\n\n\naa_cmsAlgorithmProtection = rfc5652.Attribute()\naa_cmsAlgorithmProtection['attrType'] = id_aa_cmsAlgorithmProtect\naa_cmsAlgorithmProtection['attrValues'][0] = CMSAlgorithmProtection()\n\n\n# Map of Attribute Type OIDs to Attributes are\n# added to the ones that are in rfc5652.py\n\n_cmsAttributesMapUpdate = {\n    id_aa_cmsAlgorithmProtect: CMSAlgorithmProtection(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc6402.py",
    "content": "# coding: utf-8\n#\n# This file is part of pyasn1-modules software.\n#\n# Created by Stanisław Pitucha with asn1ate tool.\n# Modified by Russ Housley to add a maps for CMC Control Attributes\n#   and CMC Content Types for use with opentypes.\n#\n# Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Certificate Management over CMS (CMC) Updates\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc6402.txt\n#\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import opentype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\nfrom pyasn1.type import useful\n\nfrom pyasn1_modules import rfc4211\nfrom pyasn1_modules import rfc5280\nfrom pyasn1_modules import rfc5652\n\nMAX = float('inf')\n\n\ndef _buildOid(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\n# Since CMS Attributes and CMC Controls both use 'attrType', one map is used \ncmcControlAttributesMap = rfc5652.cmsAttributesMap\n\n\nclass ChangeSubjectName(univ.Sequence):\n    pass\n\n\nChangeSubjectName.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('subject', rfc5280.Name()),\n    namedtype.OptionalNamedType('subjectAlt', rfc5280.GeneralNames())\n)\n\n\nclass AttributeValue(univ.Any):\n    pass\n\n\nclass CMCStatus(univ.Integer):\n    pass\n\n\nCMCStatus.namedValues = namedval.NamedValues(\n    ('success', 0),\n    ('failed', 2),\n    ('pending', 3),\n    ('noSupport', 4),\n    ('confirmRequired', 5),\n    ('popRequired', 6),\n    ('partial', 7)\n)\n\n\nclass PendInfo(univ.Sequence):\n    pass\n\n\nPendInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('pendToken', univ.OctetString()),\n    namedtype.NamedType('pendTime', useful.GeneralizedTime())\n)\n\nbodyIdMax = univ.Integer(4294967295)\n\n\nclass BodyPartID(univ.Integer):\n    pass\n\n\nBodyPartID.subtypeSpec = constraint.ValueRangeConstraint(0, bodyIdMax)\n\n\nclass BodyPartPath(univ.SequenceOf):\n    pass\n\n\nBodyPartPath.componentType = BodyPartID()\nBodyPartPath.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass BodyPartReference(univ.Choice):\n    pass\n\n\nBodyPartReference.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('bodyPartID', BodyPartID()),\n    namedtype.NamedType('bodyPartPath', BodyPartPath())\n)\n\n\nclass CMCFailInfo(univ.Integer):\n    pass\n\n\nCMCFailInfo.namedValues = namedval.NamedValues(\n    ('badAlg', 0),\n    ('badMessageCheck', 1),\n    ('badRequest', 2),\n    ('badTime', 3),\n    ('badCertId', 4),\n    ('unsupportedExt', 5),\n    ('mustArchiveKeys', 6),\n    ('badIdentity', 7),\n    ('popRequired', 8),\n    ('popFailed', 9),\n    ('noKeyReuse', 10),\n    ('internalCAError', 11),\n    ('tryLater', 12),\n    ('authDataFail', 13)\n)\n\n\nclass CMCStatusInfoV2(univ.Sequence):\n    pass\n\n\nCMCStatusInfoV2.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('cMCStatus', CMCStatus()),\n    namedtype.NamedType('bodyList', univ.SequenceOf(componentType=BodyPartReference())),\n    namedtype.OptionalNamedType('statusString', char.UTF8String()),\n    namedtype.OptionalNamedType(\n        'otherInfo', univ.Choice(\n            componentType=namedtype.NamedTypes(\n                namedtype.NamedType('failInfo', CMCFailInfo()),\n                namedtype.NamedType('pendInfo', PendInfo()),\n                namedtype.NamedType(\n                    'extendedFailInfo', univ.Sequence(\n                    componentType=namedtype.NamedTypes(\n                        namedtype.NamedType('failInfoOID', univ.ObjectIdentifier()),\n                        namedtype.NamedType('failInfoValue', AttributeValue()))\n                    )\n                )\n            )\n        )\n    )\n)\n\n\nclass GetCRL(univ.Sequence):\n    pass\n\n\nGetCRL.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerName', rfc5280.Name()),\n    namedtype.OptionalNamedType('cRLName', rfc5280.GeneralName()),\n    namedtype.OptionalNamedType('time', useful.GeneralizedTime()),\n    namedtype.OptionalNamedType('reasons', rfc5280.ReasonFlags())\n)\n\nid_pkix = _buildOid(1, 3, 6, 1, 5, 5, 7)\n\nid_cmc = _buildOid(id_pkix, 7)\n\nid_cmc_batchResponses = _buildOid(id_cmc, 29)\n\nid_cmc_popLinkWitness = _buildOid(id_cmc, 23)\n\n\nclass PopLinkWitnessV2(univ.Sequence):\n    pass\n\n\nPopLinkWitnessV2.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('keyGenAlgorithm', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('macAlgorithm', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('witness', univ.OctetString())\n)\n\nid_cmc_popLinkWitnessV2 = _buildOid(id_cmc, 33)\n\nid_cmc_identityProofV2 = _buildOid(id_cmc, 34)\n\nid_cmc_revokeRequest = _buildOid(id_cmc, 17)\n\nid_cmc_recipientNonce = _buildOid(id_cmc, 7)\n\n\nclass ControlsProcessed(univ.Sequence):\n    pass\n\n\nControlsProcessed.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('bodyList', univ.SequenceOf(componentType=BodyPartReference()))\n)\n\n\nclass CertificationRequest(univ.Sequence):\n    pass\n\n\nCertificationRequest.componentType = namedtype.NamedTypes(\n    namedtype.NamedType(\n        'certificationRequestInfo', univ.Sequence(\n            componentType=namedtype.NamedTypes(\n                namedtype.NamedType('version', univ.Integer()),\n                namedtype.NamedType('subject', rfc5280.Name()),\n                namedtype.NamedType(\n                    'subjectPublicKeyInfo', univ.Sequence(\n                        componentType=namedtype.NamedTypes(\n                            namedtype.NamedType('algorithm', rfc5280.AlgorithmIdentifier()),\n                            namedtype.NamedType('subjectPublicKey', univ.BitString())\n                        )\n                    )\n                ),\n                namedtype.NamedType(\n                    'attributes', univ.SetOf(\n                        componentType=rfc5652.Attribute()).subtype(\n                        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))\n                )\n            )\n        )\n    ),\n    namedtype.NamedType('signatureAlgorithm', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('signature', univ.BitString())\n)\n\n\nclass TaggedCertificationRequest(univ.Sequence):\n    pass\n\n\nTaggedCertificationRequest.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('bodyPartID', BodyPartID()),\n    namedtype.NamedType('certificationRequest', CertificationRequest())\n)\n\n\nclass TaggedRequest(univ.Choice):\n    pass\n\n\nTaggedRequest.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('tcr', TaggedCertificationRequest().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('crm',\n                        rfc4211.CertReqMsg().subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('orm', univ.Sequence(componentType=namedtype.NamedTypes(\n        namedtype.NamedType('bodyPartID', BodyPartID()),\n        namedtype.NamedType('requestMessageType', univ.ObjectIdentifier()),\n        namedtype.NamedType('requestMessageValue', univ.Any())\n    ))\n                        .subtype(implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2)))\n)\n\nid_cmc_popLinkRandom = _buildOid(id_cmc, 22)\n\nid_cmc_statusInfo = _buildOid(id_cmc, 1)\n\nid_cmc_trustedAnchors = _buildOid(id_cmc, 26)\n\nid_cmc_transactionId = _buildOid(id_cmc, 5)\n\nid_cmc_encryptedPOP = _buildOid(id_cmc, 9)\n\n\nclass PublishTrustAnchors(univ.Sequence):\n    pass\n\n\nPublishTrustAnchors.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('seqNumber', univ.Integer()),\n    namedtype.NamedType('hashAlgorithm', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('anchorHashes', univ.SequenceOf(componentType=univ.OctetString()))\n)\n\n\nclass RevokeRequest(univ.Sequence):\n    pass\n\n\nRevokeRequest.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerName', rfc5280.Name()),\n    namedtype.NamedType('serialNumber', univ.Integer()),\n    namedtype.NamedType('reason', rfc5280.CRLReason()),\n    namedtype.OptionalNamedType('invalidityDate', useful.GeneralizedTime()),\n    namedtype.OptionalNamedType('passphrase', univ.OctetString()),\n    namedtype.OptionalNamedType('comment', char.UTF8String())\n)\n\nid_cmc_senderNonce = _buildOid(id_cmc, 6)\n\nid_cmc_authData = _buildOid(id_cmc, 27)\n\n\nclass TaggedContentInfo(univ.Sequence):\n    pass\n\n\nTaggedContentInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('bodyPartID', BodyPartID()),\n    namedtype.NamedType('contentInfo', rfc5652.ContentInfo())\n)\n\n\nclass IdentifyProofV2(univ.Sequence):\n    pass\n\n\nIdentifyProofV2.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('proofAlgID', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('macAlgId', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('witness', univ.OctetString())\n)\n\n\nclass CMCPublicationInfo(univ.Sequence):\n    pass\n\n\nCMCPublicationInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('hashAlg', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('certHashes', univ.SequenceOf(componentType=univ.OctetString())),\n    namedtype.NamedType('pubInfo', rfc4211.PKIPublicationInfo())\n)\n\nid_kp_cmcCA = _buildOid(rfc5280.id_kp, 27)\n\nid_cmc_confirmCertAcceptance = _buildOid(id_cmc, 24)\n\nid_cmc_raIdentityWitness = _buildOid(id_cmc, 35)\n\nid_ExtensionReq = _buildOid(1, 2, 840, 113549, 1, 9, 14)\n\nid_cct = _buildOid(id_pkix, 12)\n\nid_cct_PKIData = _buildOid(id_cct, 2)\n\nid_kp_cmcRA = _buildOid(rfc5280.id_kp, 28)\n\n\nclass CMCStatusInfo(univ.Sequence):\n    pass\n\n\nCMCStatusInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('cMCStatus', CMCStatus()),\n    namedtype.NamedType('bodyList', univ.SequenceOf(componentType=BodyPartID())),\n    namedtype.OptionalNamedType('statusString', char.UTF8String()),\n    namedtype.OptionalNamedType(\n        'otherInfo', univ.Choice(\n            componentType=namedtype.NamedTypes(\n                namedtype.NamedType('failInfo', CMCFailInfo()),\n                namedtype.NamedType('pendInfo', PendInfo())\n            )\n        )\n    )\n)\n\n\nclass DecryptedPOP(univ.Sequence):\n    pass\n\n\nDecryptedPOP.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('bodyPartID', BodyPartID()),\n    namedtype.NamedType('thePOPAlgID', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('thePOP', univ.OctetString())\n)\n\nid_cmc_addExtensions = _buildOid(id_cmc, 8)\n\nid_cmc_modCertTemplate = _buildOid(id_cmc, 31)\n\n\nclass TaggedAttribute(univ.Sequence):\n    pass\n\n\nTaggedAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('bodyPartID', BodyPartID()),\n    namedtype.NamedType('attrType', univ.ObjectIdentifier()),\n    namedtype.NamedType('attrValues', univ.SetOf(componentType=AttributeValue()),\n        openType=opentype.OpenType('attrType', cmcControlAttributesMap)\n    )\n)\n\n\nclass OtherMsg(univ.Sequence):\n    pass\n\n\nOtherMsg.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('bodyPartID', BodyPartID()),\n    namedtype.NamedType('otherMsgType', univ.ObjectIdentifier()),\n    namedtype.NamedType('otherMsgValue', univ.Any())\n)\n\n\nclass PKIData(univ.Sequence):\n    pass\n\n\nPKIData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('controlSequence', univ.SequenceOf(componentType=TaggedAttribute())),\n    namedtype.NamedType('reqSequence', univ.SequenceOf(componentType=TaggedRequest())),\n    namedtype.NamedType('cmsSequence', univ.SequenceOf(componentType=TaggedContentInfo())),\n    namedtype.NamedType('otherMsgSequence', univ.SequenceOf(componentType=OtherMsg()))\n)\n\n\nclass BodyPartList(univ.SequenceOf):\n    pass\n\n\nBodyPartList.componentType = BodyPartID()\nBodyPartList.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\nid_cmc_responseBody = _buildOid(id_cmc, 37)\n\n\nclass AuthPublish(BodyPartID):\n    pass\n\n\nclass CMCUnsignedData(univ.Sequence):\n    pass\n\n\nCMCUnsignedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('bodyPartPath', BodyPartPath()),\n    namedtype.NamedType('identifier', univ.ObjectIdentifier()),\n    namedtype.NamedType('content', univ.Any())\n)\n\n\nclass CMCCertId(rfc5652.IssuerAndSerialNumber):\n    pass\n\n\nclass PKIResponse(univ.Sequence):\n    pass\n\n\nPKIResponse.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('controlSequence', univ.SequenceOf(componentType=TaggedAttribute())),\n    namedtype.NamedType('cmsSequence', univ.SequenceOf(componentType=TaggedContentInfo())),\n    namedtype.NamedType('otherMsgSequence', univ.SequenceOf(componentType=OtherMsg()))\n)\n\n\nclass ResponseBody(PKIResponse):\n    pass\n\n\nid_cmc_statusInfoV2 = _buildOid(id_cmc, 25)\n\nid_cmc_lraPOPWitness = _buildOid(id_cmc, 11)\n\n\nclass ModCertTemplate(univ.Sequence):\n    pass\n\n\nModCertTemplate.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('pkiDataReference', BodyPartPath()),\n    namedtype.NamedType('certReferences', BodyPartList()),\n    namedtype.DefaultedNamedType('replace', univ.Boolean().subtype(value=1)),\n    namedtype.NamedType('certTemplate', rfc4211.CertTemplate())\n)\n\nid_cmc_regInfo = _buildOid(id_cmc, 18)\n\nid_cmc_identityProof = _buildOid(id_cmc, 3)\n\n\nclass ExtensionReq(univ.SequenceOf):\n    pass\n\n\nExtensionReq.componentType = rfc5280.Extension()\nExtensionReq.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\nid_kp_cmcArchive = _buildOid(rfc5280.id_kp, 28)\n\nid_cmc_publishCert = _buildOid(id_cmc, 30)\n\nid_cmc_dataReturn = _buildOid(id_cmc, 4)\n\n\nclass LraPopWitness(univ.Sequence):\n    pass\n\n\nLraPopWitness.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('pkiDataBodyid', BodyPartID()),\n    namedtype.NamedType('bodyIds', univ.SequenceOf(componentType=BodyPartID()))\n)\n\nid_aa = _buildOid(1, 2, 840, 113549, 1, 9, 16, 2)\n\nid_aa_cmc_unsignedData = _buildOid(id_aa, 34)\n\nid_cmc_getCert = _buildOid(id_cmc, 15)\n\nid_cmc_batchRequests = _buildOid(id_cmc, 28)\n\nid_cmc_decryptedPOP = _buildOid(id_cmc, 10)\n\nid_cmc_responseInfo = _buildOid(id_cmc, 19)\n\nid_cmc_changeSubjectName = _buildOid(id_cmc, 36)\n\n\nclass GetCert(univ.Sequence):\n    pass\n\n\nGetCert.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('issuerName', rfc5280.GeneralName()),\n    namedtype.NamedType('serialNumber', univ.Integer())\n)\n\nid_cmc_identification = _buildOid(id_cmc, 2)\n\nid_cmc_queryPending = _buildOid(id_cmc, 21)\n\n\nclass AddExtensions(univ.Sequence):\n    pass\n\n\nAddExtensions.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('pkiDataReference', BodyPartID()),\n    namedtype.NamedType('certReferences', univ.SequenceOf(componentType=BodyPartID())),\n    namedtype.NamedType('extensions', univ.SequenceOf(componentType=rfc5280.Extension()))\n)\n\n\nclass EncryptedPOP(univ.Sequence):\n    pass\n\n\nEncryptedPOP.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('request', TaggedRequest()),\n    namedtype.NamedType('cms', rfc5652.ContentInfo()),\n    namedtype.NamedType('thePOPAlgID', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('witnessAlgID', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('witness', univ.OctetString())\n)\n\nid_cmc_getCRL = _buildOid(id_cmc, 16)\n\nid_cct_PKIResponse = _buildOid(id_cct, 3)\n\nid_cmc_controlProcessed = _buildOid(id_cmc, 32)\n\n\nclass NoSignatureValue(univ.OctetString):\n    pass\n\n\nid_ad_cmc = _buildOid(rfc5280.id_ad, 12)\n\nid_alg_noSignature = _buildOid(id_pkix, 6, 2)\n\n\n# Map of CMC Control OIDs to CMC Control Attributes\n\n_cmcControlAttributesMapUpdate = {\n    id_cmc_statusInfo: CMCStatusInfo(),\n    id_cmc_statusInfoV2: CMCStatusInfoV2(),\n    id_cmc_identification: char.UTF8String(),\n    id_cmc_identityProof: univ.OctetString(),\n    id_cmc_identityProofV2: IdentifyProofV2(),\n    id_cmc_dataReturn: univ.OctetString(),\n    id_cmc_transactionId: univ.Integer(),\n    id_cmc_senderNonce: univ.OctetString(),\n    id_cmc_recipientNonce: univ.OctetString(),\n    id_cmc_addExtensions: AddExtensions(),\n    id_cmc_encryptedPOP: EncryptedPOP(),\n    id_cmc_decryptedPOP: DecryptedPOP(),\n    id_cmc_lraPOPWitness: LraPopWitness(),\n    id_cmc_getCert: GetCert(),\n    id_cmc_getCRL: GetCRL(),\n    id_cmc_revokeRequest: RevokeRequest(),\n    id_cmc_regInfo: univ.OctetString(),\n    id_cmc_responseInfo: univ.OctetString(),\n    id_cmc_queryPending: univ.OctetString(),\n    id_cmc_popLinkRandom: univ.OctetString(),\n    id_cmc_popLinkWitness: univ.OctetString(),\n    id_cmc_popLinkWitnessV2: PopLinkWitnessV2(),\n    id_cmc_confirmCertAcceptance: CMCCertId(),\n    id_cmc_trustedAnchors: PublishTrustAnchors(),\n    id_cmc_authData: AuthPublish(),\n    id_cmc_batchRequests: BodyPartList(),\n    id_cmc_batchResponses: BodyPartList(),\n    id_cmc_publishCert: CMCPublicationInfo(),\n    id_cmc_modCertTemplate: ModCertTemplate(),\n    id_cmc_controlProcessed: ControlsProcessed(),\n    id_ExtensionReq: ExtensionReq(),\n}\n\ncmcControlAttributesMap.update(_cmcControlAttributesMapUpdate)\n\n\n# Map of CMC Content Type OIDs to CMC Content Types are added to\n# the ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_cct_PKIData: PKIData(),\n    id_cct_PKIResponse: PKIResponse(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc7030.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Enrollment over Secure Transport (EST)\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc7030.txt\n#\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5652\n\nMAX = float('inf')\n\n\n# Imports from RFC 5652\n\nAttribute = rfc5652.Attribute\n\n\n# Asymmetric Decrypt Key Identifier Attribute\n\nid_aa_asymmDecryptKeyID = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.54')\n\nclass AsymmetricDecryptKeyIdentifier(univ.OctetString):\n    pass\n\n\naa_asymmDecryptKeyID = Attribute()\naa_asymmDecryptKeyID['attrType'] = id_aa_asymmDecryptKeyID\naa_asymmDecryptKeyID['attrValues'][0] = AsymmetricDecryptKeyIdentifier()\n\n\n# CSR Attributes\n\nclass AttrOrOID(univ.Choice):\n    pass\n\nAttrOrOID.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('oid', univ.ObjectIdentifier()),\n    namedtype.NamedType('attribute', Attribute())\n)\n\n\nclass CsrAttrs(univ.SequenceOf):\n    pass\n\nCsrAttrs.componentType = AttrOrOID()\nCsrAttrs.subtypeSpec=constraint.ValueSizeConstraint(0, MAX)\n\n   \n# Update CMS Attribute Map\n\n_cmsAttributesMapUpdate = {\n    id_aa_asymmDecryptKeyID: AsymmetricDecryptKeyIdentifier(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc7191.py",
    "content": "# This file is being contributed to of pyasn1-modules software.\n#\n# Created by Russ Housley without assistance from the asn1ate tool.\n# Modified by Russ Housley to add support for opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# CMS Key Package Receipt and Error Content Types\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc7191.txt\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import opentype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\nfrom pyasn1_modules import rfc5652\n\nMAX = float('inf')\n\nDistinguishedName = rfc5280.DistinguishedName\n\n\n# SingleAttribute is the same as Attribute in RFC 5652, except that the\n# attrValues SET must have one and only one member\n\nclass AttributeValue(univ.Any):\n    pass\n\n\nclass AttributeValues(univ.SetOf):\n    pass\n\nAttributeValues.componentType = AttributeValue()\nAttributeValues.sizeSpec = univ.Set.sizeSpec + constraint.ValueSizeConstraint(1, 1)\n\n\nclass SingleAttribute(univ.Sequence):\n    pass\n\nSingleAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('attrType', univ.ObjectIdentifier()),\n    namedtype.NamedType('attrValues', AttributeValues(),\n        openType=opentype.OpenType('attrType', rfc5652.cmsAttributesMap)\n    )\n)\n\n\n# SIR Entity Name\n\nclass SIREntityNameType(univ.ObjectIdentifier):\n    pass\n\n\nclass SIREntityNameValue(univ.Any):\n    pass\n\n\nclass SIREntityName(univ.Sequence):\n    pass\n\nSIREntityName.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('sirenType', SIREntityNameType()),\n    namedtype.NamedType('sirenValue', univ.OctetString())\n    # CONTAINING the DER-encoded SIREntityNameValue\n)\n\n\nclass SIREntityNames(univ.SequenceOf):\n    pass\n\nSIREntityNames.componentType = SIREntityName()\nSIREntityNames.sizeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\nid_dn = univ.ObjectIdentifier('2.16.840.1.101.2.1.16.0')\n\n\nclass siren_dn(SIREntityName):\n    def __init__(self):\n        SIREntityName.__init__(self)\n        self['sirenType'] = id_dn\n\n\n# Key Package Error CMS Content Type\n\nclass EnumeratedErrorCode(univ.Enumerated):\n    pass\n\n# Error codes with values <= 33 are aligned with RFC 5934\nEnumeratedErrorCode.namedValues = namedval.NamedValues(\n    ('decodeFailure', 1),\n    ('badContentInfo', 2),\n    ('badSignedData', 3),\n    ('badEncapContent', 4),\n    ('badCertificate', 5),\n    ('badSignerInfo', 6),\n    ('badSignedAttrs', 7),\n    ('badUnsignedAttrs', 8),\n    ('missingContent', 9),\n    ('noTrustAnchor', 10),\n    ('notAuthorized', 11),\n    ('badDigestAlgorithm', 12),\n    ('badSignatureAlgorithm', 13),\n    ('unsupportedKeySize', 14),\n    ('unsupportedParameters', 15),\n    ('signatureFailure', 16),\n    ('insufficientMemory', 17),\n    ('incorrectTarget', 23),\n    ('missingSignature', 29),\n    ('resourcesBusy', 30),\n    ('versionNumberMismatch', 31),\n    ('revokedCertificate', 33),\n    ('ambiguousDecrypt', 60),\n    ('noDecryptKey', 61),\n    ('badEncryptedData', 62),\n    ('badEnvelopedData', 63),\n    ('badAuthenticatedData', 64),\n    ('badAuthEnvelopedData', 65),\n    ('badKeyAgreeRecipientInfo', 66),\n    ('badKEKRecipientInfo', 67),\n    ('badEncryptContent', 68),\n    ('badEncryptAlgorithm', 69),\n    ('missingCiphertext', 70),\n    ('decryptFailure', 71),\n    ('badMACAlgorithm', 72),\n    ('badAuthAttrs', 73),\n    ('badUnauthAttrs', 74),\n    ('invalidMAC', 75),\n    ('mismatchedDigestAlg', 76),\n    ('missingCertificate', 77),\n    ('tooManySigners', 78),\n    ('missingSignedAttributes', 79),\n    ('derEncodingNotUsed', 80),\n    ('missingContentHints', 81),\n    ('invalidAttributeLocation', 82),\n    ('badMessageDigest', 83),\n    ('badKeyPackage', 84),\n    ('badAttributes', 85),\n    ('attributeComparisonFailure', 86),\n    ('unsupportedSymmetricKeyPackage', 87),\n    ('unsupportedAsymmetricKeyPackage', 88),\n    ('constraintViolation', 89),\n    ('ambiguousDefaultValue', 90),\n    ('noMatchingRecipientInfo', 91),\n    ('unsupportedKeyWrapAlgorithm', 92),\n    ('badKeyTransRecipientInfo', 93),\n    ('other', 127)\n)\n\n\nclass ErrorCodeChoice(univ.Choice):\n    pass\n\nErrorCodeChoice.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('enum', EnumeratedErrorCode()),\n    namedtype.NamedType('oid', univ.ObjectIdentifier())\n)\n\n\nclass KeyPkgID(univ.OctetString):\n    pass\n\n\nclass KeyPkgIdentifier(univ.Choice):\n    pass\n\nKeyPkgIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('pkgID', KeyPkgID()),\n    namedtype.NamedType('attribute', SingleAttribute())\n)\n\n\nclass KeyPkgVersion(univ.Integer):\n    pass\n\n\nKeyPkgVersion.namedValues = namedval.NamedValues(\n    ('v1', 1),\n    ('v2', 2)\n)\n\nKeyPkgVersion.subtypeSpec = constraint.ValueRangeConstraint(1, 65535)\n\n\nid_ct_KP_keyPackageError = univ.ObjectIdentifier('2.16.840.1.101.2.1.2.78.6')\n\nclass KeyPackageError(univ.Sequence):\n    pass\n\nKeyPackageError.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version', KeyPkgVersion().subtype(value='v2')),\n    namedtype.OptionalNamedType('errorOf', KeyPkgIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 0))),\n    namedtype.NamedType('errorBy', SIREntityName()),\n    namedtype.NamedType('errorCode', ErrorCodeChoice())\n)\n\n\n# Key Package Receipt CMS Content Type\n\nid_ct_KP_keyPackageReceipt = univ.ObjectIdentifier('2.16.840.1.101.2.1.2.78.3')\n\nclass KeyPackageReceipt(univ.Sequence):\n    pass\n\nKeyPackageReceipt.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('version', KeyPkgVersion().subtype(value='v2')),\n    namedtype.NamedType('receiptOf', KeyPkgIdentifier()),\n    namedtype.NamedType('receivedBy', SIREntityName())\n)\n\n\n# Key Package Receipt Request Attribute\n\nclass KeyPkgReceiptReq(univ.Sequence):\n    pass\n\nKeyPkgReceiptReq.componentType = namedtype.NamedTypes(\n    namedtype.DefaultedNamedType('encryptReceipt', univ.Boolean().subtype(value=0)),\n    namedtype.OptionalNamedType('receiptsFrom', SIREntityNames().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('receiptsTo', SIREntityNames())\n)\n\n\nid_aa_KP_keyPkgIdAndReceiptReq = univ.ObjectIdentifier('2.16.840.1.101.2.1.5.65')\n\nclass KeyPkgIdentifierAndReceiptReq(univ.Sequence):\n    pass\n\nKeyPkgIdentifierAndReceiptReq.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('pkgID', KeyPkgID()),\n    namedtype.OptionalNamedType('receiptReq', KeyPkgReceiptReq())\n)\n\n\n# Map of Attribute Type OIDs to Attributes are added to\n# the ones that are in rfc5652.py\n\n_cmsAttributesMapUpdate = {\n    id_aa_KP_keyPkgIdAndReceiptReq: KeyPkgIdentifierAndReceiptReq(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n\n\n# Map of CMC Content Type OIDs to CMC Content Types are added to\n# the ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_KP_keyPackageError: KeyPackageError(),\n    id_ct_KP_keyPackageReceipt: KeyPackageReceipt(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc7292.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from the asn1ate tool.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# PKCS #12: Personal Information Exchange Syntax v1.1\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc7292.txt\n# https://www.rfc-editor.org/errata_search.php?rfc=7292\n\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import opentype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc2315\nfrom pyasn1_modules import rfc5652\nfrom pyasn1_modules import rfc5280\nfrom pyasn1_modules import rfc5958\n\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\n# Initialize the maps used in PKCS#12\n\npkcs12BagTypeMap = { }\n\npkcs12CertBagMap = { }\n\npkcs12CRLBagMap = { }\n\npkcs12SecretBagMap = { }\n\n\n# Imports from RFC 2315, RFC 5652, and RFC 5958\n\nDigestInfo = rfc2315.DigestInfo\n\n\nContentInfo = rfc5652.ContentInfo\n\nPKCS12Attribute = rfc5652.Attribute\n\n\nEncryptedPrivateKeyInfo = rfc5958.EncryptedPrivateKeyInfo\n\nPrivateKeyInfo = rfc5958.PrivateKeyInfo\n\n\n# CMSSingleAttribute is the same as Attribute in RFC 5652 except the attrValues\n# SET must have one and only one member\n\nclass AttributeType(univ.ObjectIdentifier):\n    pass\n\n\nclass AttributeValue(univ.Any):\n    pass\n\n\nclass AttributeValues(univ.SetOf):\n    pass\n\nAttributeValues.componentType = AttributeValue()\n\n\nclass CMSSingleAttribute(univ.Sequence):\n    pass\n\nCMSSingleAttribute.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('attrType', AttributeType()),\n    namedtype.NamedType('attrValues',\n        AttributeValues().subtype(sizeSpec=constraint.ValueSizeConstraint(1, 1)),\n        openType=opentype.OpenType('attrType', rfc5652.cmsAttributesMap)\n    )\n)\n\n\n# Object identifier arcs\n\nrsadsi = _OID(1, 2, 840, 113549)\n\npkcs = _OID(rsadsi, 1)\n\npkcs_9 = _OID(pkcs, 9)\n\ncertTypes = _OID(pkcs_9, 22)\n\ncrlTypes = _OID(pkcs_9, 23)\n\npkcs_12 = _OID(pkcs, 12)\n\n\n# PBE Algorithm Identifiers and Parameters Structure\n\npkcs_12PbeIds = _OID(pkcs_12, 1)\n\npbeWithSHAAnd128BitRC4 = _OID(pkcs_12PbeIds, 1)\n\npbeWithSHAAnd40BitRC4 = _OID(pkcs_12PbeIds, 2)\n\npbeWithSHAAnd3_KeyTripleDES_CBC = _OID(pkcs_12PbeIds, 3)\n\npbeWithSHAAnd2_KeyTripleDES_CBC = _OID(pkcs_12PbeIds, 4)\n\npbeWithSHAAnd128BitRC2_CBC = _OID(pkcs_12PbeIds, 5)\n\npbeWithSHAAnd40BitRC2_CBC = _OID(pkcs_12PbeIds, 6)\n\n\nclass Pkcs_12PbeParams(univ.Sequence):\n    pass\n\nPkcs_12PbeParams.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('salt', univ.OctetString()),\n    namedtype.NamedType('iterations', univ.Integer())\n)\n\n\n# Bag types\n\nbagtypes = _OID(pkcs_12, 10, 1)\n\nclass BAG_TYPE(univ.Sequence):\n    pass\n\nBAG_TYPE.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('id', univ.ObjectIdentifier()),\n    namedtype.NamedType('unnamed1', univ.Any(),\n        openType=opentype.OpenType('attrType', pkcs12BagTypeMap)\n    )\n)\n\n\nid_keyBag = _OID(bagtypes, 1)\n\nclass KeyBag(PrivateKeyInfo):\n    pass\n\n\nid_pkcs8ShroudedKeyBag = _OID(bagtypes, 2)\n\nclass PKCS8ShroudedKeyBag(EncryptedPrivateKeyInfo):\n    pass\n\n\nid_certBag = _OID(bagtypes, 3)\n\nclass CertBag(univ.Sequence):\n    pass\n\nCertBag.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('certId', univ.ObjectIdentifier()),\n    namedtype.NamedType('certValue',\n        univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)),\n        openType=opentype.OpenType('certId', pkcs12CertBagMap)\n    )\n)\n\n\nx509Certificate = CertBag()\nx509Certificate['certId'] = _OID(certTypes, 1)\nx509Certificate['certValue'] = univ.OctetString()\n# DER-encoded X.509 certificate stored in OCTET STRING\n\n\nsdsiCertificate = CertBag()\nsdsiCertificate['certId'] = _OID(certTypes, 2)\nsdsiCertificate['certValue'] = char.IA5String()\n# Base64-encoded SDSI certificate stored in IA5String\n\n\nid_CRLBag = _OID(bagtypes, 4)\n\nclass CRLBag(univ.Sequence):\n    pass\n\nCRLBag.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('crlId', univ.ObjectIdentifier()),\n    namedtype.NamedType('crlValue',\n        univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)),\n                openType=opentype.OpenType('crlId', pkcs12CRLBagMap)\n    )\n)\n\n\nx509CRL = CRLBag()\nx509CRL['crlId'] = _OID(crlTypes, 1)\nx509CRL['crlValue'] = univ.OctetString()\n# DER-encoded X.509 CRL stored in OCTET STRING\n\n\nid_secretBag = _OID(bagtypes, 5)\n\nclass SecretBag(univ.Sequence):\n    pass\n\nSecretBag.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('secretTypeId', univ.ObjectIdentifier()),\n    namedtype.NamedType('secretValue',\n        univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)),\n        openType=opentype.OpenType('secretTypeId', pkcs12SecretBagMap)\n    )\n)\n\n\nid_safeContentsBag = _OID(bagtypes, 6)\n\nclass SafeBag(univ.Sequence):\n    pass\n\nSafeBag.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('bagId', univ.ObjectIdentifier()),\n    namedtype.NamedType('bagValue',\n        univ.Any().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0)),\n        openType=opentype.OpenType('bagId', pkcs12BagTypeMap)\n    ),\n    namedtype.OptionalNamedType('bagAttributes',\n        univ.SetOf(componentType=PKCS12Attribute())\n    )\n)\n\n\nclass SafeContents(univ.SequenceOf):\n    pass\n\nSafeContents.componentType = SafeBag()\n\n\n# The PFX PDU\n\nclass AuthenticatedSafe(univ.SequenceOf):\n    pass\n\nAuthenticatedSafe.componentType = ContentInfo()\n# Data if unencrypted\n# EncryptedData if password-encrypted\n# EnvelopedData if public key-encrypted\n\n\nclass MacData(univ.Sequence):\n    pass\n\nMacData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('mac', DigestInfo()),\n    namedtype.NamedType('macSalt', univ.OctetString()),\n    namedtype.DefaultedNamedType('iterations', univ.Integer().subtype(value=1))\n    # Note: The default is for historical reasons and its use is deprecated\n)\n\n\nclass PFX(univ.Sequence):\n    pass\n\nPFX.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version',\n        univ.Integer(namedValues=namedval.NamedValues(('v3', 3)))\n    ),\n    namedtype.NamedType('authSafe', ContentInfo()),\n    namedtype.OptionalNamedType('macData', MacData())\n)\n\n\n# Local key identifier (also defined as certificateAttribute in rfc2985.py)\n\npkcs_9_at_localKeyId = _OID(pkcs_9, 21)\n\nlocalKeyId = CMSSingleAttribute()\nlocalKeyId['attrType'] = pkcs_9_at_localKeyId\nlocalKeyId['attrValues'][0] = univ.OctetString()\n\n\n# Friendly name (also defined as certificateAttribute in rfc2985.py)\n\npkcs_9_ub_pkcs9String = univ.Integer(255)\n\npkcs_9_ub_friendlyName = univ.Integer(pkcs_9_ub_pkcs9String)\n\npkcs_9_at_friendlyName = _OID(pkcs_9, 20)\n\nclass FriendlyName(char.BMPString):\n    pass\n\nFriendlyName.subtypeSpec = constraint.ValueSizeConstraint(1, pkcs_9_ub_friendlyName)\n\n\nfriendlyName = CMSSingleAttribute()\nfriendlyName['attrType'] = pkcs_9_at_friendlyName\nfriendlyName['attrValues'][0] = FriendlyName()\n\n\n# Update the PKCS#12 maps\n\n_pkcs12BagTypeMap = {\n    id_keyBag: KeyBag(),\n    id_pkcs8ShroudedKeyBag: PKCS8ShroudedKeyBag(),\n    id_certBag: CertBag(),\n    id_CRLBag: CRLBag(),\n    id_secretBag: SecretBag(),\n    id_safeContentsBag: SafeBag(),\n}\n\npkcs12BagTypeMap.update(_pkcs12BagTypeMap)\n\n\n_pkcs12CertBagMap = {\n    _OID(certTypes, 1): univ.OctetString(),\n    _OID(certTypes, 2): char.IA5String(),\n}\n\npkcs12CertBagMap.update(_pkcs12CertBagMap)\n\n\n_pkcs12CRLBagMap = {\n    _OID(crlTypes, 1): univ.OctetString(),\n}\n\npkcs12CRLBagMap.update(_pkcs12CRLBagMap)\n\n\n# Update the Algorithm Identifier map\n\n_algorithmIdentifierMapUpdate = {\n    pbeWithSHAAnd128BitRC4: Pkcs_12PbeParams(),\n    pbeWithSHAAnd40BitRC4: Pkcs_12PbeParams(),\n    pbeWithSHAAnd3_KeyTripleDES_CBC: Pkcs_12PbeParams(),\n    pbeWithSHAAnd2_KeyTripleDES_CBC: Pkcs_12PbeParams(),\n    pbeWithSHAAnd128BitRC2_CBC: Pkcs_12PbeParams(),\n    pbeWithSHAAnd40BitRC2_CBC: Pkcs_12PbeParams(),\n}\n\nrfc5280.algorithmIdentifierMap.update(_algorithmIdentifierMapUpdate)\n\n\n# Update the CMS Attribute map\n\n_cmsAttributesMapUpdate = {\n    pkcs_9_at_friendlyName: FriendlyName(),\n    pkcs_9_at_localKeyId: univ.OctetString(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc7296.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# IKEv2 Certificate Bundle\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc7296.txt\n\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\n\nclass CertificateOrCRL(univ.Choice):\n    pass\n\nCertificateOrCRL.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('cert', rfc5280.Certificate().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('crl', rfc5280.CertificateList().subtype(explicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass CertificateBundle(univ.SequenceOf):\n    pass\n\nCertificateBundle.componentType = CertificateOrCRL()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc7773.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with some assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Authentication Context Certificate Extension\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc7773.txt\n#\n\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\nMAX = float('inf')\n\n\n# Authentication Context Extension\n\ne_legnamnden = univ.ObjectIdentifier('1.2.752.201')\n\nid_eleg_ce = e_legnamnden + (5, )\n\nid_ce_authContext = id_eleg_ce + (1, )\n\n\nclass AuthenticationContext(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('contextType', char.UTF8String()),\n        namedtype.OptionalNamedType('contextInfo', char.UTF8String())\n    )\n\nclass AuthenticationContexts(univ.SequenceOf):\n    componentType = AuthenticationContext()\n    subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\n# Map of Certificate Extension OIDs to Extensions added to the\n# ones that are in rfc5280.py\n\n_certificateExtensionsMapUpdate = {\n    id_ce_authContext: AuthenticationContexts(),\n}\n\nrfc5280.certificateExtensionsMap.update(_certificateExtensionsMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc7894.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Alternative Challenge Password Attributes for EST\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc7894.txt\n#\n\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5652\nfrom pyasn1_modules import rfc6402\nfrom pyasn1_modules import rfc7191\n\n\n# SingleAttribute is the same as Attribute in RFC 5652, except that the\n# attrValues SET must have one and only one member\n\nAttribute = rfc7191.SingleAttribute\n\n\n# DirectoryString is the same as RFC 5280, except the length is limited to 255\n\nclass DirectoryString(univ.Choice):\n    pass\n\nDirectoryString.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('teletexString', char.TeletexString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, 255))),\n    namedtype.NamedType('printableString', char.PrintableString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, 255))),\n    namedtype.NamedType('universalString', char.UniversalString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, 255))),\n    namedtype.NamedType('utf8String', char.UTF8String().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, 255))),\n    namedtype.NamedType('bmpString', char.BMPString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(1, 255)))\n)\n\n\n# OTP Challenge Attribute\n\nid_aa_otpChallenge = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.56')\n\nub_aa_otpChallenge = univ.Integer(255)\n\notpChallenge = Attribute()\notpChallenge['attrType'] = id_aa_otpChallenge\notpChallenge['attrValues'][0] = DirectoryString()\n\n\n# Revocation Challenge Attribute\n\nid_aa_revocationChallenge = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.57')\n\nub_aa_revocationChallenge = univ.Integer(255)\n\nrevocationChallenge = Attribute()\nrevocationChallenge['attrType'] = id_aa_revocationChallenge\nrevocationChallenge['attrValues'][0] = DirectoryString()\n\n\n#  EST Identity Linking Attribute\n\nid_aa_estIdentityLinking = univ.ObjectIdentifier('1.2.840.113549.1.9.16.2.58')\n\nub_aa_est_identity_linking = univ.Integer(255)\n\nestIdentityLinking = Attribute()\nestIdentityLinking['attrType'] = id_aa_estIdentityLinking\nestIdentityLinking['attrValues'][0] = DirectoryString()\n\n\n# Map of Attribute Type OIDs to Attributes added to the\n# ones that are in rfc6402.py\n\n_cmcControlAttributesMapUpdate = {\n    id_aa_otpChallenge: DirectoryString(),\n    id_aa_revocationChallenge: DirectoryString(),\n    id_aa_estIdentityLinking: DirectoryString(),\n}\n\nrfc6402.cmcControlAttributesMap.update(_cmcControlAttributesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc7906.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# NSA's CMS Key Management Attributes\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc7906.txt\n# https://www.rfc-editor.org/errata/eid5850\n#\n\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc2634\nfrom pyasn1_modules import rfc4108\nfrom pyasn1_modules import rfc5280\nfrom pyasn1_modules import rfc5652\nfrom pyasn1_modules import rfc6010\nfrom pyasn1_modules import rfc6019\nfrom pyasn1_modules import rfc7191\n\nMAX = float('inf')\n\n\n# Imports From RFC 2634\n\nid_aa_contentHint = rfc2634.id_aa_contentHint\n\nContentHints = rfc2634.ContentHints\n\nid_aa_securityLabel = rfc2634.id_aa_securityLabel\n\nSecurityPolicyIdentifier = rfc2634.SecurityPolicyIdentifier\n\nSecurityClassification = rfc2634.SecurityClassification\n\nESSPrivacyMark = rfc2634.ESSPrivacyMark\n\nSecurityCategories= rfc2634.SecurityCategories\n\nESSSecurityLabel = rfc2634.ESSSecurityLabel\n\n\n# Imports From RFC 4108\n\nid_aa_communityIdentifiers = rfc4108.id_aa_communityIdentifiers\n\nCommunityIdentifier = rfc4108.CommunityIdentifier\n\nCommunityIdentifiers = rfc4108.CommunityIdentifiers\n\n\n# Imports From RFC 5280\n\nAlgorithmIdentifier = rfc5280.AlgorithmIdentifier\n\nName = rfc5280.Name\n\nCertificate = rfc5280.Certificate\n\nGeneralNames = rfc5280.GeneralNames\n\nGeneralName = rfc5280.GeneralName\n\n\nSubjectInfoAccessSyntax = rfc5280.SubjectInfoAccessSyntax\n\nid_pkix = rfc5280.id_pkix\n\nid_pe = rfc5280.id_pe\n\nid_pe_subjectInfoAccess = rfc5280.id_pe_subjectInfoAccess\n\n\n# Imports From RFC 6010\n\nCMSContentConstraints = rfc6010.CMSContentConstraints\n\n\n# Imports From RFC 6019\n\nBinaryTime = rfc6019.BinaryTime\n\nid_aa_binarySigningTime = rfc6019.id_aa_binarySigningTime\n\nBinarySigningTime = rfc6019.BinarySigningTime\n\n\n# Imports From RFC 5652\n\nAttribute = rfc5652.Attribute\n\nCertificateSet = rfc5652.CertificateSet\n\nCertificateChoices = rfc5652.CertificateChoices\n\nid_contentType = rfc5652.id_contentType\n\nContentType = rfc5652.ContentType\n\nid_messageDigest = rfc5652.id_messageDigest\n\nMessageDigest = rfc5652.MessageDigest\n\n\n# Imports From RFC 7191\n\nSIREntityName = rfc7191.SIREntityName\n\nid_aa_KP_keyPkgIdAndReceiptReq = rfc7191.id_aa_KP_keyPkgIdAndReceiptReq\n\nKeyPkgIdentifierAndReceiptReq = rfc7191.KeyPkgIdentifierAndReceiptReq\n\n\n# Key Province Attribute\n\nid_aa_KP_keyProvinceV2 = univ.ObjectIdentifier('2.16.840.1.101.2.1.5.71')\n\n\nclass KeyProvinceV2(univ.ObjectIdentifier):\n    pass\n\n\naa_keyProvince_v2 = Attribute()\naa_keyProvince_v2['attrType'] = id_aa_KP_keyProvinceV2\naa_keyProvince_v2['attrValues'][0] = KeyProvinceV2()\n \n\n# Manifest Attribute\n\nid_aa_KP_manifest = univ.ObjectIdentifier('2.16.840.1.101.2.1.5.72')\n\n\nclass ShortTitle(char.PrintableString):\n    pass\n\n\nclass Manifest(univ.SequenceOf):\n    pass\n\nManifest.componentType = ShortTitle()\nManifest.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\naa_manifest = Attribute()\naa_manifest['attrType'] = id_aa_KP_manifest\naa_manifest['attrValues'][0] = Manifest()\n\n\n# Key Algorithm Attribute\n\nid_kma_keyAlgorithm = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.1')\n\n\nclass KeyAlgorithm(univ.Sequence):\n    pass\n\nKeyAlgorithm.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('keyAlg', univ.ObjectIdentifier()),\n    namedtype.OptionalNamedType('checkWordAlg', univ.ObjectIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.OptionalNamedType('crcAlg', univ.ObjectIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2)))\n)\n\n\naa_keyAlgorithm = Attribute()\naa_keyAlgorithm['attrType'] = id_kma_keyAlgorithm\naa_keyAlgorithm['attrValues'][0] = KeyAlgorithm()\n\n\n# User Certificate Attribute\n\nid_at_userCertificate = univ.ObjectIdentifier('2.5.4.36')\n\n\naa_userCertificate = Attribute()\naa_userCertificate['attrType'] = id_at_userCertificate\naa_userCertificate['attrValues'][0] =  Certificate()\n\n\n# Key Package Receivers Attribute\n\nid_kma_keyPkgReceiversV2 = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.16')\n\n\nclass KeyPkgReceiver(univ.Choice):\n    pass\n\nKeyPkgReceiver.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('sirEntity', SIREntityName().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('community', CommunityIdentifier().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass KeyPkgReceiversV2(univ.SequenceOf):\n    pass\n\nKeyPkgReceiversV2.componentType = KeyPkgReceiver()\nKeyPkgReceiversV2.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\naa_keyPackageReceivers_v2 = Attribute()\naa_keyPackageReceivers_v2['attrType'] = id_kma_keyPkgReceiversV2\naa_keyPackageReceivers_v2['attrValues'][0] = KeyPkgReceiversV2()\n\n\n# TSEC Nomenclature Attribute\n\nid_kma_TSECNomenclature = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.3')\n\n\nclass CharEdition(char.PrintableString):\n    pass\n\n\nclass CharEditionRange(univ.Sequence):\n    pass\n\nCharEditionRange.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('firstCharEdition', CharEdition()),\n    namedtype.NamedType('lastCharEdition', CharEdition())\n)\n\n\nclass NumEdition(univ.Integer):\n    pass\n\nNumEdition.subtypeSpec = constraint.ValueRangeConstraint(0, 308915776)\n\n\nclass NumEditionRange(univ.Sequence):\n    pass\n\nNumEditionRange.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('firstNumEdition', NumEdition()),\n    namedtype.NamedType('lastNumEdition', NumEdition())\n)\n\n\nclass EditionID(univ.Choice):\n    pass\n\nEditionID.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('char', univ.Choice(componentType=namedtype.NamedTypes(\n        namedtype.NamedType('charEdition', CharEdition().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n        namedtype.NamedType('charEditionRange', CharEditionRange().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 2)))\n    ))\n    ),\n    namedtype.NamedType('num', univ.Choice(componentType=namedtype.NamedTypes(\n        namedtype.NamedType('numEdition', NumEdition().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3))),\n        namedtype.NamedType('numEditionRange', NumEditionRange().subtype(\n            implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 4)))\n    ))\n    )\n)\n\n\nclass Register(univ.Integer):\n    pass\n\nRegister.subtypeSpec = constraint.ValueRangeConstraint(0, 2147483647)\n\n\nclass RegisterRange(univ.Sequence):\n    pass\n\nRegisterRange.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('firstRegister', Register()),\n    namedtype.NamedType('lastRegister', Register())\n)\n\n\nclass RegisterID(univ.Choice):\n    pass\n\nRegisterID.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('register', Register().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 5))),\n    namedtype.NamedType('registerRange', RegisterRange().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 6)))\n)\n\n\nclass SegmentNumber(univ.Integer):\n    pass\n\nSegmentNumber.subtypeSpec = constraint.ValueRangeConstraint(1, 127)\n\n\nclass SegmentRange(univ.Sequence):\n    pass\n\nSegmentRange.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('firstSegment', SegmentNumber()),\n    namedtype.NamedType('lastSegment', SegmentNumber())\n)\n\n\nclass SegmentID(univ.Choice):\n    pass\n\nSegmentID.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('segmentNumber', SegmentNumber().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 7))),\n    namedtype.NamedType('segmentRange', SegmentRange().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatConstructed, 8)))\n)\n\n\nclass TSECNomenclature(univ.Sequence):\n    pass\n\nTSECNomenclature.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('shortTitle', ShortTitle()),\n    namedtype.OptionalNamedType('editionID', EditionID()),\n    namedtype.OptionalNamedType('registerID', RegisterID()),\n    namedtype.OptionalNamedType('segmentID', SegmentID())\n)\n\n\naa_tsecNomenclature = Attribute()\naa_tsecNomenclature['attrType'] = id_kma_TSECNomenclature\naa_tsecNomenclature['attrValues'][0] = TSECNomenclature()\n\n\n# Key Purpose Attribute\n\nid_kma_keyPurpose = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.13')\n\n\nclass KeyPurpose(univ.Enumerated):\n    pass\n\nKeyPurpose.namedValues = namedval.NamedValues(\n    ('n-a', 0),\n    ('a', 65),\n    ('b', 66),\n    ('l', 76),\n    ('m', 77),\n    ('r', 82),\n    ('s', 83),\n    ('t', 84),\n    ('v', 86),\n    ('x', 88),\n    ('z', 90)\n)\n\n\naa_keyPurpose = Attribute()\naa_keyPurpose['attrType'] = id_kma_keyPurpose\naa_keyPurpose['attrValues'][0] = KeyPurpose()\n\n\n# Key Use Attribute\n\nid_kma_keyUse = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.14')\n\n\nclass KeyUse(univ.Enumerated):\n    pass\n\nKeyUse.namedValues = namedval.NamedValues(\n    ('n-a', 0),\n    ('ffk', 1),\n    ('kek', 2),\n    ('kpk', 3),\n    ('msk', 4),\n    ('qkek', 5),\n    ('tek', 6),\n    ('tsk', 7),\n    ('trkek', 8),\n    ('nfk', 9),\n    ('effk', 10),\n    ('ebfk', 11),\n    ('aek', 12),\n    ('wod', 13),\n    ('kesk', 246),\n    ('eik', 247),\n    ('ask', 248),\n    ('kmk', 249),\n    ('rsk', 250),\n    ('csk', 251),\n    ('sak', 252),\n    ('rgk', 253),\n    ('cek', 254),\n    ('exk', 255)\n)\n\n\naa_keyUse = Attribute()\naa_keyPurpose['attrType'] = id_kma_keyUse\naa_keyPurpose['attrValues'][0] = KeyUse()\n\n\n# Transport Key Attribute\n\nid_kma_transportKey = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.15')\n\n\nclass TransOp(univ.Enumerated):\n    pass\n\nTransOp.namedValues = namedval.NamedValues(\n    ('transport', 1),\n    ('operational', 2)\n)\n\n\naa_transportKey = Attribute()\naa_transportKey['attrType'] = id_kma_transportKey\naa_transportKey['attrValues'][0] = TransOp()\n\n\n# Key Distribution Period Attribute\n\nid_kma_keyDistPeriod = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.5')\n\n\nclass KeyDistPeriod(univ.Sequence):\n    pass\n\nKeyDistPeriod.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('doNotDistBefore', BinaryTime().subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('doNotDistAfter', BinaryTime())\n)\n\n\naa_keyDistributionPeriod = Attribute()\naa_keyDistributionPeriod['attrType'] = id_kma_keyDistPeriod\naa_keyDistributionPeriod['attrValues'][0] = KeyDistPeriod()\n\n\n# Key Validity Period Attribute\n\nid_kma_keyValidityPeriod = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.6')\n\n\nclass KeyValidityPeriod(univ.Sequence):\n    pass\n\nKeyValidityPeriod.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('doNotUseBefore', BinaryTime()),\n    namedtype.OptionalNamedType('doNotUseAfter', BinaryTime())\n)\n\n\naa_keyValidityPeriod = Attribute()\naa_keyValidityPeriod['attrType'] = id_kma_keyValidityPeriod\naa_keyValidityPeriod['attrValues'][0] = KeyValidityPeriod()\n\n\n# Key Duration Attribute\n\nid_kma_keyDuration = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.7')\n\n\nub_KeyDuration_months = univ.Integer(72)\n\nub_KeyDuration_hours = univ.Integer(96)\n\nub_KeyDuration_days = univ.Integer(732)\n\nub_KeyDuration_weeks = univ.Integer(104)\n\nub_KeyDuration_years = univ.Integer(100)\n\n\nclass KeyDuration(univ.Choice):\n    pass\n\nKeyDuration.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('hours', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(1, ub_KeyDuration_hours)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('days', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(1, ub_KeyDuration_days))),\n    namedtype.NamedType('weeks', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(1, ub_KeyDuration_weeks)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 1))),\n    namedtype.NamedType('months', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(1, ub_KeyDuration_months)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 2))),\n    namedtype.NamedType('years', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(1, ub_KeyDuration_years)).subtype(\n        implicitTag=tag.Tag(tag.tagClassContext, tag.tagFormatSimple, 3)))\n)\n\n\naa_keyDurationPeriod = Attribute()\naa_keyDurationPeriod['attrType'] = id_kma_keyDuration\naa_keyDurationPeriod['attrValues'][0] = KeyDuration()\n\n\n# Classification Attribute\n\nid_aa_KP_classification = univ.ObjectIdentifier(id_aa_securityLabel)\n\n\nid_enumeratedPermissiveAttributes = univ.ObjectIdentifier('2.16.840.1.101.2.1.8.3.1')\n\nid_enumeratedRestrictiveAttributes = univ.ObjectIdentifier('2.16.840.1.101.2.1.8.3.4')\n\nid_informativeAttributes = univ.ObjectIdentifier('2.16.840.1.101.2.1.8.3.3')\n\n\nclass SecurityAttribute(univ.Integer):\n    pass\n\nSecurityAttribute.subtypeSpec = constraint.ValueRangeConstraint(0, MAX)\n\n\nclass EnumeratedTag(univ.Sequence):\n    pass\n\nEnumeratedTag.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('tagName', univ.ObjectIdentifier()),\n    namedtype.NamedType('attributeList', univ.SetOf(componentType=SecurityAttribute()))\n)\n\n\nclass FreeFormField(univ.Choice):\n    pass\n\nFreeFormField.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('bitSetAttributes', univ.BitString()), # Not permitted in RFC 7906\n    namedtype.NamedType('securityAttributes', univ.SetOf(componentType=SecurityAttribute()))\n)\n\n\nclass InformativeTag(univ.Sequence):\n    pass\n\nInformativeTag.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('tagName', univ.ObjectIdentifier()),\n    namedtype.NamedType('attributes', FreeFormField())\n)\n\n\nclass Classification(ESSSecurityLabel):\n    pass\n\n\naa_classification = Attribute()\naa_classification['attrType'] = id_aa_KP_classification\naa_classification['attrValues'][0] = Classification()\n\n\n# Split Identifier Attribute\n\nid_kma_splitID = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.11')\n\n\nclass SplitID(univ.Sequence):\n    pass\n\nSplitID.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('half', univ.Enumerated(\n        namedValues=namedval.NamedValues(('a', 0), ('b', 1)))),\n    namedtype.OptionalNamedType('combineAlg', AlgorithmIdentifier())\n)\n\n\naa_splitIdentifier = Attribute()\naa_splitIdentifier['attrType'] = id_kma_splitID\naa_splitIdentifier['attrValues'][0] = SplitID()\n\n\n# Key Package Type Attribute\n\nid_kma_keyPkgType = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.12')\n\n\nclass KeyPkgType(univ.ObjectIdentifier):\n    pass\n\n\naa_keyPackageType = Attribute()\naa_keyPackageType['attrType'] = id_kma_keyPkgType\naa_keyPackageType['attrValues'][0] = KeyPkgType()\n\n\n# Signature Usage Attribute\n\nid_kma_sigUsageV3 = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.22')\n\n\nclass SignatureUsage(CMSContentConstraints):\n    pass\n\n\naa_signatureUsage_v3 = Attribute()\naa_signatureUsage_v3['attrType'] = id_kma_sigUsageV3\naa_signatureUsage_v3['attrValues'][0] = SignatureUsage()\n\n\n# Other Certificate Format Attribute\n\nid_kma_otherCertFormats = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.19')\n\n\naa_otherCertificateFormats = Attribute()\naa_signatureUsage_v3['attrType'] = id_kma_otherCertFormats\naa_signatureUsage_v3['attrValues'][0] = CertificateChoices()\n\n\n# PKI Path Attribute\n\nid_at_pkiPath = univ.ObjectIdentifier('2.5.4.70')\n\n\nclass PkiPath(univ.SequenceOf):\n    pass\n\nPkiPath.componentType = Certificate()\nPkiPath.subtypeSpec=constraint.ValueSizeConstraint(1, MAX)\n\n\naa_pkiPath = Attribute()\naa_pkiPath['attrType'] = id_at_pkiPath\naa_pkiPath['attrValues'][0] = PkiPath()\n\n\n# Useful Certificates Attribute\n\nid_kma_usefulCerts = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.20')\n\n\naa_usefulCertificates = Attribute()\naa_usefulCertificates['attrType'] = id_kma_usefulCerts\naa_usefulCertificates['attrValues'][0] = CertificateSet()\n\n\n# Key Wrap Attribute\n\nid_kma_keyWrapAlgorithm = univ.ObjectIdentifier('2.16.840.1.101.2.1.13.21')\n\n\naa_keyWrapAlgorithm  = Attribute()\naa_keyWrapAlgorithm['attrType'] = id_kma_keyWrapAlgorithm\naa_keyWrapAlgorithm['attrValues'][0] = AlgorithmIdentifier()\n\n\n# Content Decryption Key Identifier Attribute\n\nid_aa_KP_contentDecryptKeyID = univ.ObjectIdentifier('2.16.840.1.101.2.1.5.66')\n\n\nclass ContentDecryptKeyID(univ.OctetString):\n    pass\n\n\naa_contentDecryptKeyIdentifier = Attribute()\naa_contentDecryptKeyIdentifier['attrType'] = id_aa_KP_contentDecryptKeyID\naa_contentDecryptKeyIdentifier['attrValues'][0] = ContentDecryptKeyID()\n\n\n# Certificate Pointers Attribute\n\naa_certificatePointers = Attribute()\naa_certificatePointers['attrType'] = id_pe_subjectInfoAccess\naa_certificatePointers['attrValues'][0] = SubjectInfoAccessSyntax()\n\n\n# CRL Pointers Attribute\n\nid_aa_KP_crlPointers = univ.ObjectIdentifier('2.16.840.1.101.2.1.5.70')\n\n\naa_cRLDistributionPoints = Attribute()\naa_cRLDistributionPoints['attrType'] = id_aa_KP_crlPointers\naa_cRLDistributionPoints['attrValues'][0] = GeneralNames()\n\n\n# Extended Error Codes\n\nid_errorCodes = univ.ObjectIdentifier('2.16.840.1.101.2.1.22')\n\nid_missingKeyType = univ.ObjectIdentifier('2.16.840.1.101.2.1.22.1')\n\nid_privacyMarkTooLong = univ.ObjectIdentifier('2.16.840.1.101.2.1.22.2')\n\nid_unrecognizedSecurityPolicy = univ.ObjectIdentifier('2.16.840.1.101.2.1.22.3')\n\n\n# Map of Attribute Type OIDs to Attributes added to the\n# ones that are in rfc5652.py\n\n_cmsAttributesMapUpdate = {\n    id_aa_contentHint: ContentHints(),\n    id_aa_communityIdentifiers: CommunityIdentifiers(),\n    id_aa_binarySigningTime: BinarySigningTime(),\n    id_contentType: ContentType(),\n    id_messageDigest: MessageDigest(),\n    id_aa_KP_keyPkgIdAndReceiptReq: KeyPkgIdentifierAndReceiptReq(),\n    id_aa_KP_keyProvinceV2: KeyProvinceV2(),\n    id_aa_KP_manifest: Manifest(),\n    id_kma_keyAlgorithm: KeyAlgorithm(),\n    id_at_userCertificate: Certificate(),\n    id_kma_keyPkgReceiversV2: KeyPkgReceiversV2(),\n    id_kma_TSECNomenclature: TSECNomenclature(),\n    id_kma_keyPurpose: KeyPurpose(),\n    id_kma_keyUse: KeyUse(),\n    id_kma_transportKey: TransOp(),\n    id_kma_keyDistPeriod: KeyDistPeriod(),\n    id_kma_keyValidityPeriod: KeyValidityPeriod(),\n    id_kma_keyDuration: KeyDuration(),\n    id_aa_KP_classification: Classification(),\n    id_kma_splitID: SplitID(),\n    id_kma_keyPkgType: KeyPkgType(),\n    id_kma_sigUsageV3: SignatureUsage(),\n    id_kma_otherCertFormats: CertificateChoices(),\n    id_at_pkiPath: PkiPath(),\n    id_kma_usefulCerts: CertificateSet(),\n    id_kma_keyWrapAlgorithm: AlgorithmIdentifier(),\n    id_aa_KP_contentDecryptKeyID: ContentDecryptKeyID(),\n    id_pe_subjectInfoAccess: SubjectInfoAccessSyntax(),\n    id_aa_KP_crlPointers: GeneralNames(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc7914.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n#The scrypt Password-Based Key Derivation Function\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8520.txt\n# https://www.rfc-editor.org/errata/eid5871\n#\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\nMAX = float('inf')\n\n\nid_scrypt = univ.ObjectIdentifier('1.3.6.1.4.1.11591.4.11')\n\n\nclass Scrypt_params(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('salt',\n            univ.OctetString()),\n        namedtype.NamedType('costParameter',\n            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(1, MAX))),\n        namedtype.NamedType('blockSize',\n            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(1, MAX))),\n        namedtype.NamedType('parallelizationParameter',\n            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(1, MAX))),\n        namedtype.OptionalNamedType('keyLength',\n            univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(1, MAX)))\n    )\n\n\n# Update the Algorithm Identifier map in rfc5280.py\n\n_algorithmIdentifierMapUpdate = {\n    id_scrypt: Scrypt_params(),\n}\n\nrfc5280.algorithmIdentifierMap.update(_algorithmIdentifierMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8017.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# PKCS #1: RSA Cryptography Specifications Version 2.2\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8017.txt\n#\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc2437\nfrom pyasn1_modules import rfc3447\nfrom pyasn1_modules import rfc4055\nfrom pyasn1_modules import rfc5280\n\nMAX = float('inf')\n\n\n# Import Algorithm Identifier from RFC 5280\n\nAlgorithmIdentifier = rfc5280.AlgorithmIdentifier\n\nclass DigestAlgorithm(AlgorithmIdentifier):\n    pass\n\nclass HashAlgorithm(AlgorithmIdentifier):\n    pass\n\nclass MaskGenAlgorithm(AlgorithmIdentifier):\n    pass\n\nclass PSourceAlgorithm(AlgorithmIdentifier):\n    pass\n\n\n# Object identifiers from NIST SHA2\n\nhashAlgs = univ.ObjectIdentifier('2.16.840.1.101.3.4.2')\nid_sha256 = rfc4055.id_sha256\nid_sha384 = rfc4055.id_sha384\nid_sha512 = rfc4055.id_sha512\nid_sha224 = rfc4055.id_sha224\nid_sha512_224 = hashAlgs + (5, )\nid_sha512_256 = hashAlgs + (6, )\n\n\n# Basic object identifiers\n\npkcs_1 = univ.ObjectIdentifier('1.2.840.113549.1.1')\nrsaEncryption = rfc2437.rsaEncryption\nid_RSAES_OAEP = rfc2437.id_RSAES_OAEP\nid_pSpecified = rfc2437.id_pSpecified\nid_RSASSA_PSS = rfc4055.id_RSASSA_PSS\nmd2WithRSAEncryption = rfc2437.md2WithRSAEncryption\nmd5WithRSAEncryption = rfc2437.md5WithRSAEncryption\nsha1WithRSAEncryption = rfc2437.sha1WithRSAEncryption\nsha224WithRSAEncryption = rfc4055.sha224WithRSAEncryption\nsha256WithRSAEncryption = rfc4055.sha256WithRSAEncryption\nsha384WithRSAEncryption = rfc4055.sha384WithRSAEncryption\nsha512WithRSAEncryption = rfc4055.sha512WithRSAEncryption\nsha512_224WithRSAEncryption = pkcs_1 + (15, )\nsha512_256WithRSAEncryption = pkcs_1 + (16, )\nid_sha1 = rfc2437.id_sha1\nid_md2 = univ.ObjectIdentifier('1.2.840.113549.2.2')\nid_md5 = univ.ObjectIdentifier('1.2.840.113549.2.5')\nid_mgf1 = rfc2437.id_mgf1\n\n\n# Default parameter values\n\nsha1 = rfc4055.sha1Identifier\nSHA1Parameters = univ.Null(\"\")\n\nmgf1SHA1 = rfc4055.mgf1SHA1Identifier\n\nclass EncodingParameters(univ.OctetString):\n    subtypeSpec = constraint.ValueSizeConstraint(0, MAX)\n\npSpecifiedEmpty = rfc4055.pSpecifiedEmptyIdentifier\n\nemptyString = EncodingParameters(value='')\n\n\n# Main structures\n\nclass Version(univ.Integer):\n    namedValues = namedval.NamedValues(\n        ('two-prime', 0),\n        ('multi', 1)\n    )\n\nclass TrailerField(univ.Integer):\n    namedValues = namedval.NamedValues(\n       ('trailerFieldBC', 1)\n    )\n\nRSAPublicKey = rfc2437.RSAPublicKey\n\nOtherPrimeInfo = rfc3447.OtherPrimeInfo\nOtherPrimeInfos = rfc3447.OtherPrimeInfos\nRSAPrivateKey = rfc3447.RSAPrivateKey\n\nRSAES_OAEP_params = rfc4055.RSAES_OAEP_params\nrSAES_OAEP_Default_Identifier = rfc4055.rSAES_OAEP_Default_Identifier\n\nRSASSA_PSS_params = rfc4055.RSASSA_PSS_params\nrSASSA_PSS_Default_Identifier = rfc4055.rSASSA_PSS_Default_Identifier\n\n\n# Syntax for the EMSA-PKCS1-v1_5 hash identifier\n\nclass DigestInfo(univ.Sequence):\n    componentType = namedtype.NamedTypes(\n        namedtype.NamedType('digestAlgorithm', DigestAlgorithm()),\n        namedtype.NamedType('digest', univ.OctetString())\n    )\n\n\n# Update the Algorithm Identifier map\n\n_algorithmIdentifierMapUpdate = {\n    id_sha1: univ.Null(),\n    id_sha224: univ.Null(),\n    id_sha256: univ.Null(),\n    id_sha384: univ.Null(),\n    id_sha512: univ.Null(),\n    id_sha512_224: univ.Null(),\n    id_sha512_256: univ.Null(),\n    id_mgf1: AlgorithmIdentifier(),\n    id_pSpecified: univ.OctetString(),\n    id_RSAES_OAEP: RSAES_OAEP_params(),\n    id_RSASSA_PSS: RSASSA_PSS_params(),\n    md2WithRSAEncryption: univ.Null(),\n    md5WithRSAEncryption: univ.Null(),\n    sha1WithRSAEncryption: univ.Null(),\n    sha224WithRSAEncryption: univ.Null(),\n    sha256WithRSAEncryption: univ.Null(),\n    sha384WithRSAEncryption: univ.Null(),\n    sha512WithRSAEncryption: univ.Null(),\n    sha512_224WithRSAEncryption: univ.Null(),\n    sha512_256WithRSAEncryption: univ.Null(),\n}\n\nrfc5280.algorithmIdentifierMap.update(_algorithmIdentifierMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8018.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# PKCS #5: Password-Based Cryptography Specification, Version 2.1\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8018.txt\n#\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc3565\nfrom pyasn1_modules import rfc5280\n\nMAX = float('inf')\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\n# Import from RFC 3565\n\nAES_IV = rfc3565.AES_IV\n\n\n# Import from RFC 5280\n\nAlgorithmIdentifier = rfc5280.AlgorithmIdentifier\n\n\n# Basic object identifiers\n\nnistAlgorithms = _OID(2, 16, 840, 1, 101, 3, 4)\n\naes = _OID(nistAlgorithms, 1)\n\noiw = _OID(1, 3, 14)\n\nrsadsi = _OID(1, 2, 840, 113549)\n\npkcs = _OID(rsadsi, 1)\n\ndigestAlgorithm = _OID(rsadsi, 2)\n\nencryptionAlgorithm = _OID(rsadsi, 3)\n\npkcs_5 = _OID(pkcs, 5)\n\n\n\n# HMAC object identifiers\n\nid_hmacWithSHA1 = _OID(digestAlgorithm, 7)\n\nid_hmacWithSHA224 = _OID(digestAlgorithm, 8)\n\nid_hmacWithSHA256 = _OID(digestAlgorithm, 9)\n\nid_hmacWithSHA384 = _OID(digestAlgorithm, 10)\n\nid_hmacWithSHA512 = _OID(digestAlgorithm, 11)\n\nid_hmacWithSHA512_224 = _OID(digestAlgorithm, 12)\n\nid_hmacWithSHA512_256 = _OID(digestAlgorithm, 13)\n\n\n# PBES1 object identifiers\n\npbeWithMD2AndDES_CBC = _OID(pkcs_5, 1)\n\npbeWithMD2AndRC2_CBC = _OID(pkcs_5, 4)\n\npbeWithMD5AndDES_CBC = _OID(pkcs_5, 3)\n\npbeWithMD5AndRC2_CBC = _OID(pkcs_5, 6)\n\npbeWithSHA1AndDES_CBC = _OID(pkcs_5, 10)\n\npbeWithSHA1AndRC2_CBC = _OID(pkcs_5, 11)\n\n\n# Supporting techniques object identifiers\n\ndesCBC = _OID(oiw, 3, 2, 7)\n\ndes_EDE3_CBC = _OID(encryptionAlgorithm, 7)\n\nrc2CBC = _OID(encryptionAlgorithm, 2)\n\nrc5_CBC_PAD = _OID(encryptionAlgorithm, 9)\n\naes128_CBC_PAD = _OID(aes, 2)\n\naes192_CBC_PAD = _OID(aes, 22)\n\naes256_CBC_PAD = _OID(aes, 42)\n\n\n# PBES1\n\nclass PBEParameter(univ.Sequence):\n    pass\n\nPBEParameter.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('salt', univ.OctetString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(8, 8))),\n    namedtype.NamedType('iterationCount', univ.Integer())\n)\n\n\n# PBES2\n\nid_PBES2 = _OID(pkcs_5, 13)\n\n\nclass PBES2_params(univ.Sequence):\n    pass\n\nPBES2_params.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('keyDerivationFunc', AlgorithmIdentifier()),\n    namedtype.NamedType('encryptionScheme', AlgorithmIdentifier())\n)\n\n\n# PBMAC1\n\nid_PBMAC1 = _OID(pkcs_5, 14)\n\n\nclass PBMAC1_params(univ.Sequence):\n    pass\n\nPBMAC1_params.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('keyDerivationFunc', AlgorithmIdentifier()),\n    namedtype.NamedType('messageAuthScheme', AlgorithmIdentifier())\n)\n\n\n# PBKDF2\n\nid_PBKDF2 = _OID(pkcs_5, 12)\n\n\nalgid_hmacWithSHA1 = AlgorithmIdentifier()\nalgid_hmacWithSHA1['algorithm'] = id_hmacWithSHA1\nalgid_hmacWithSHA1['parameters'] = univ.Null(\"\")\n\n\nclass PBKDF2_params(univ.Sequence):\n    pass\n\nPBKDF2_params.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('salt', univ.Choice(componentType=namedtype.NamedTypes(\n        namedtype.NamedType('specified', univ.OctetString()),\n        namedtype.NamedType('otherSource', AlgorithmIdentifier())\n    ))),\n    namedtype.NamedType('iterationCount', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(1, MAX))),\n    namedtype.OptionalNamedType('keyLength', univ.Integer().subtype(\n        subtypeSpec=constraint.ValueRangeConstraint(1, MAX))),\n    namedtype.DefaultedNamedType('prf', algid_hmacWithSHA1)\n)\n\n\n# RC2 CBC algorithm parameter\n\nclass RC2_CBC_Parameter(univ.Sequence):\n    pass\n\nRC2_CBC_Parameter.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('rc2ParameterVersion', univ.Integer()),\n    namedtype.NamedType('iv', univ.OctetString().subtype(\n        subtypeSpec=constraint.ValueSizeConstraint(8, 8)))\n)\n\n\n# RC5 CBC algorithm parameter\n\nclass RC5_CBC_Parameters(univ.Sequence):\n    pass\n\nRC5_CBC_Parameters.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('version',\n        univ.Integer(namedValues=namedval.NamedValues(('v1_0', 16))).subtype(\n            subtypeSpec=constraint.SingleValueConstraint(16))),\n    namedtype.NamedType('rounds',\n        univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(8, 127))),\n    namedtype.NamedType('blockSizeInBits',\n        univ.Integer().subtype(subtypeSpec=constraint.SingleValueConstraint(64, 128))),\n    namedtype.OptionalNamedType('iv', univ.OctetString())\n)\n\n\n# Initialization Vector for AES: OCTET STRING (SIZE(16))\n\nclass AES_IV(univ.OctetString):\n    pass\n\nAES_IV.subtypeSpec = constraint.ValueSizeConstraint(16, 16)\n\n\n# Initialization Vector for DES: OCTET STRING (SIZE(8))\n\nclass DES_IV(univ.OctetString):\n    pass\n\nDES_IV.subtypeSpec = constraint.ValueSizeConstraint(8, 8)\n\n\n# Update the Algorithm Identifier map\n\n_algorithmIdentifierMapUpdate = {\n    # PBKDF2-PRFs\n    id_hmacWithSHA1: univ.Null(),\n    id_hmacWithSHA224: univ.Null(),\n    id_hmacWithSHA256: univ.Null(),\n    id_hmacWithSHA384: univ.Null(),\n    id_hmacWithSHA512: univ.Null(),\n    id_hmacWithSHA512_224: univ.Null(),\n    id_hmacWithSHA512_256: univ.Null(),\n    # PBES1Algorithms\n    pbeWithMD2AndDES_CBC: PBEParameter(),\n    pbeWithMD2AndRC2_CBC: PBEParameter(),\n    pbeWithMD5AndDES_CBC: PBEParameter(),\n    pbeWithMD5AndRC2_CBC: PBEParameter(),\n    pbeWithSHA1AndDES_CBC: PBEParameter(),\n    pbeWithSHA1AndRC2_CBC: PBEParameter(),\n    # PBES2Algorithms\n    id_PBES2: PBES2_params(),\n    # PBES2-KDFs\n    id_PBKDF2: PBKDF2_params(),\n    # PBMAC1Algorithms\n    id_PBMAC1: PBMAC1_params(),\n    # SupportingAlgorithms\n    desCBC: DES_IV(),\n    des_EDE3_CBC: DES_IV(),\n    rc2CBC: RC2_CBC_Parameter(),\n    rc5_CBC_PAD: RC5_CBC_Parameters(),\n    aes128_CBC_PAD: AES_IV(),\n    aes192_CBC_PAD: AES_IV(),\n    aes256_CBC_PAD: AES_IV(),\n}\n\nrfc5280.algorithmIdentifierMap.update(_algorithmIdentifierMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8103.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from the asn1ate tool.\n# Auto-generated by asn1ate v.0.6.0 from rfc8103.asn.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# ChaCha20Poly1305 algorithm fo use with the Authenticated-Enveloped-Data\n# protecting content type for the Cryptographic Message Syntax (CMS)\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8103.txt\n\nfrom pyasn1.type import constraint\nfrom pyasn1.type import univ\n\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\nclass AEADChaCha20Poly1305Nonce(univ.OctetString):\n    pass\n\n\nAEADChaCha20Poly1305Nonce.subtypeSpec = constraint.ValueSizeConstraint(12, 12)\n\nid_alg_AEADChaCha20Poly1305 = _OID(1, 2, 840, 113549, 1, 9, 16, 3, 18)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8209.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# BGPsec Router PKI Profile\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8209.txt\n#\n\nfrom pyasn1.type import univ\n\n\nid_kp = univ.ObjectIdentifier('1.3.6.1.5.5.7.3')\n\nid_kp_bgpsec_router = id_kp + (30, )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8226.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from the asn1ate tool, with manual\n#   changes to implement appropriate constraints and added comments.\n# Modified by Russ Housley to add maps for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# JWT Claim Constraints and TN Authorization List for certificate extensions.\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8226.txt (with errata corrected)\n\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\nMAX = float('inf')\n\n\ndef _OID(*components):\n    output = []\n    for x in tuple(components):\n        if isinstance(x, univ.ObjectIdentifier):\n            output.extend(list(x))\n        else:\n            output.append(int(x))\n\n    return univ.ObjectIdentifier(output)\n\n\nclass JWTClaimName(char.IA5String):\n    pass\n\n\nclass JWTClaimNames(univ.SequenceOf):\n    pass\n\nJWTClaimNames.componentType = JWTClaimName()\nJWTClaimNames.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass JWTClaimPermittedValues(univ.Sequence):\n    pass\n\nJWTClaimPermittedValues.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('claim', JWTClaimName()),\n    namedtype.NamedType('permitted', univ.SequenceOf(\n        componentType=char.UTF8String()).subtype(\n            sizeSpec=constraint.ValueSizeConstraint(1, MAX)))\n)\n\n\nclass JWTClaimPermittedValuesList(univ.SequenceOf):\n    pass\n\nJWTClaimPermittedValuesList.componentType = JWTClaimPermittedValues()\nJWTClaimPermittedValuesList.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\nclass JWTClaimConstraints(univ.Sequence):\n    pass\n\nJWTClaimConstraints.componentType = namedtype.NamedTypes(\n    namedtype.OptionalNamedType('mustInclude',\n        JWTClaimNames().subtype(explicitTag=tag.Tag(tag.tagClassContext,\n            tag.tagFormatSimple, 0))),\n    namedtype.OptionalNamedType('permittedValues',\n        JWTClaimPermittedValuesList().subtype(explicitTag=tag.Tag(tag.tagClassContext,\n            tag.tagFormatSimple, 1)))\n)\n\n\nJWTClaimConstraints.sizeSpec = univ.Sequence.sizeSpec + constraint.ValueSizeConstraint(1, 2)\n\n\nid_pe_JWTClaimConstraints = _OID(1, 3, 6, 1, 5, 5, 7, 1, 27)\n\n\nclass ServiceProviderCode(char.IA5String):\n    pass\n\n\nclass TelephoneNumber(char.IA5String):\n    pass\n\nTelephoneNumber.subtypeSpec = constraint.ConstraintsIntersection(\n    constraint.ValueSizeConstraint(1, 15),\n    constraint.PermittedAlphabetConstraint(\n        '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '#', '*')\n)\n\n\nclass TelephoneNumberRange(univ.Sequence):\n    pass\n\nTelephoneNumberRange.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('start', TelephoneNumber()),\n    namedtype.NamedType('count',\n        univ.Integer().subtype(subtypeSpec=constraint.ValueRangeConstraint(2, MAX)))\n)\n\n\nclass TNEntry(univ.Choice):\n    pass\n\nTNEntry.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('spc',\n        ServiceProviderCode().subtype(explicitTag=tag.Tag(tag.tagClassContext,\n            tag.tagFormatSimple, 0))),\n    namedtype.NamedType('range',\n        TelephoneNumberRange().subtype(explicitTag=tag.Tag(tag.tagClassContext,\n            tag.tagFormatConstructed, 1))),\n    namedtype.NamedType('one',\n        TelephoneNumber().subtype(explicitTag=tag.Tag(tag.tagClassContext,\n            tag.tagFormatSimple, 2)))\n)\n\n\nclass TNAuthorizationList(univ.SequenceOf):\n    pass\n\nTNAuthorizationList.componentType = TNEntry()\nTNAuthorizationList.sizeSpec = constraint.ValueSizeConstraint(1, MAX)\n\nid_pe_TNAuthList = _OID(1, 3, 6, 1, 5, 5, 7, 1, 26)\n\n\nid_ad_stirTNList = _OID(1, 3, 6, 1, 5, 5, 7, 48, 14)\n\n\n# Map of Certificate Extension OIDs to Extensions added to the\n# ones that are in rfc5280.py\n\n_certificateExtensionsMapUpdate = {\n    id_pe_TNAuthList: TNAuthorizationList(),\n    id_pe_JWTClaimConstraints: JWTClaimConstraints(),\n}\n\nrfc5280.certificateExtensionsMap.update(_certificateExtensionsMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8358.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Digital Signatures on Internet-Draft Documents\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8358.txt\n#\n\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5652\n\n\nid_ct = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1')\n\nid_ct_asciiTextWithCRLF = id_ct + (27, )\n\nid_ct_epub = id_ct + (39, )\n\nid_ct_htmlWithCRLF = id_ct + (38, )\n\nid_ct_pdf = id_ct + (29, )\n\nid_ct_postscript = id_ct + (30, )\n\nid_ct_utf8TextWithCRLF = id_ct + (37, )\n\nid_ct_xml = id_ct + (28, )\n\n\n# Map of Content Type OIDs to Content Types is added to the\n# ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_asciiTextWithCRLF: univ.OctetString(),\n    id_ct_epub: univ.OctetString(),\n    id_ct_htmlWithCRLF: univ.OctetString(),\n    id_ct_pdf: univ.OctetString(),\n    id_ct_postscript: univ.OctetString(),\n    id_ct_utf8TextWithCRLF: univ.OctetString(),\n    id_ct_xml: univ.OctetString(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8360.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Resource Public Key Infrastructure (RPKI) Validation Reconsidered\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8360.txt\n# https://www.rfc-editor.org/errata/eid5870\n#\n\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc3779\nfrom pyasn1_modules import rfc5280\n\n\n# IP Address Delegation Extension V2\n\nid_pe_ipAddrBlocks_v2 = univ.ObjectIdentifier('1.3.6.1.5.5.7.1.28')\n\nIPAddrBlocks = rfc3779.IPAddrBlocks\n\n\n# Autonomous System Identifier Delegation Extension V2\n\nid_pe_autonomousSysIds_v2 = univ.ObjectIdentifier('1.3.6.1.5.5.7.1.29')\n\nASIdentifiers = rfc3779.ASIdentifiers\n\n\n# Map of Certificate Extension OIDs to Extensions is added to the\n# ones that are in rfc5280.py\n\n_certificateExtensionsMapUpdate = {\n    id_pe_ipAddrBlocks_v2: IPAddrBlocks(),\n    id_pe_autonomousSysIds_v2: ASIdentifiers(),\n}\n\nrfc5280.certificateExtensionsMap.update(_certificateExtensionsMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8398.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with some assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Internationalized Email Addresses in X.509 Certificates\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8398.txt\n# https://www.rfc-editor.org/errata/eid5418\n#\n\nfrom pyasn1.type import char\nfrom pyasn1.type import constraint\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\nMAX = float('inf')\n\n\n# SmtpUTF8Mailbox contains Mailbox as specified in Section 3.3 of RFC 6531\n\nid_pkix = rfc5280.id_pkix\n\nid_on = id_pkix + (8, )\n\nid_on_SmtpUTF8Mailbox = id_on + (9, )\n\n\nclass SmtpUTF8Mailbox(char.UTF8String):\n    pass\n\nSmtpUTF8Mailbox.subtypeSpec = constraint.ValueSizeConstraint(1, MAX)\n\n\non_SmtpUTF8Mailbox = rfc5280.AnotherName()\non_SmtpUTF8Mailbox['type-id'] = id_on_SmtpUTF8Mailbox\non_SmtpUTF8Mailbox['value'] = SmtpUTF8Mailbox()\n\n\n# Map of Other Name OIDs to Other Name is added to the\n# ones that are in rfc5280.py\n\n_anotherNameMapUpdate = {\n    id_on_SmtpUTF8Mailbox: SmtpUTF8Mailbox(),\n}\n\nrfc5280.anotherNameMap.update(_anotherNameMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8410.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Algorithm Identifiers for Ed25519, Ed448, X25519, and X448\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8410.txt\n\nfrom pyasn1.type import univ\nfrom pyasn1_modules import rfc3565\nfrom pyasn1_modules import rfc4055\nfrom pyasn1_modules import rfc5280\n\n\nclass SignatureAlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass KeyEncryptionAlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass CurvePrivateKey(univ.OctetString):\n    pass\n\n\nid_X25519 = univ.ObjectIdentifier('1.3.101.110')\n\nid_X448 = univ.ObjectIdentifier('1.3.101.111')\n\nid_Ed25519 = univ.ObjectIdentifier('1.3.101.112')\n\nid_Ed448 = univ.ObjectIdentifier('1.3.101.113')\n\nid_sha512 = rfc4055.id_sha512\n\nid_aes128_wrap = rfc3565.id_aes128_wrap\n\nid_aes256_wrap = rfc3565.id_aes256_wrap\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8418.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Elliptic Curve Diffie-Hellman (ECDH) Key Agreement Algorithm\n#   with X25519 and X448\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8418.txt\n\nfrom pyasn1.type import univ\nfrom pyasn1_modules import rfc5280\n\n\nclass KeyEncryptionAlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\nclass KeyWrapAlgorithmIdentifier(rfc5280.AlgorithmIdentifier):\n    pass\n\n\ndhSinglePass_stdDH_sha256kdf_scheme = univ.ObjectIdentifier('1.3.133.16.840.63.0.11.1')\n\ndhSinglePass_stdDH_sha384kdf_scheme = univ.ObjectIdentifier('1.3.133.16.840.63.0.11.2')\n\ndhSinglePass_stdDH_sha512kdf_scheme = univ.ObjectIdentifier('1.3.133.16.840.63.0.11.3')\n\ndhSinglePass_stdDH_hkdf_sha256_scheme = univ.ObjectIdentifier('1.2.840.113549.1.9.16.3.19')\n\ndhSinglePass_stdDH_hkdf_sha384_scheme = univ.ObjectIdentifier('1.2.840.113549.1.9.16.3.20')\n\ndhSinglePass_stdDH_hkdf_sha512_scheme = univ.ObjectIdentifier('1.2.840.113549.1.9.16.3.21')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8419.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Edwards-Curve Digital Signature Algorithm (EdDSA) Signatures in the CMS\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8419.txt\n# https://www.rfc-editor.org/errata/eid5869\n\n\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\n\nclass ShakeOutputLen(univ.Integer):\n    pass\n\n\nid_Ed25519 = univ.ObjectIdentifier('1.3.101.112')\n\nsigAlg_Ed25519 = rfc5280.AlgorithmIdentifier()\nsigAlg_Ed25519['algorithm'] = id_Ed25519\n# sigAlg_Ed25519['parameters'] is absent\n\n\nid_Ed448 = univ.ObjectIdentifier('1.3.101.113')\n\nsigAlg_Ed448 = rfc5280.AlgorithmIdentifier()\nsigAlg_Ed448['algorithm'] = id_Ed448\n# sigAlg_Ed448['parameters'] is absent\n\n\nhashAlgs = univ.ObjectIdentifier('2.16.840.1.101.3.4.2')\n\nid_sha512 = hashAlgs + (3, )\n\nhashAlg_SHA_512 = rfc5280.AlgorithmIdentifier()\nhashAlg_SHA_512['algorithm'] = id_sha512\n# hashAlg_SHA_512['parameters'] is absent\n\n\nid_shake256 = hashAlgs + (12, )\n\nhashAlg_SHAKE256 = rfc5280.AlgorithmIdentifier()\nhashAlg_SHAKE256['algorithm'] = id_shake256\n# hashAlg_SHAKE256['parameters']is absent\n\n\nid_shake256_len = hashAlgs + (18, )\n\nhashAlg_SHAKE256_LEN  = rfc5280.AlgorithmIdentifier()\nhashAlg_SHAKE256_LEN['algorithm'] = id_shake256_len\nhashAlg_SHAKE256_LEN['parameters'] = ShakeOutputLen()\n\n\n# Map of Algorithm Identifier OIDs to Parameters added to the\n# ones in rfc5280.py.  Do not add OIDs with absent paramaters.\n\n_algorithmIdentifierMapUpdate = {\n    id_shake256_len: ShakeOutputLen(),\n}\n\nrfc5280.algorithmIdentifierMap.update(_algorithmIdentifierMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8479.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Storing Validation Parameters in PKCS#8\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8479.txt\n#\n\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5652\n\n\nid_attr_validation_parameters = univ.ObjectIdentifier('1.3.6.1.4.1.2312.18.8.1')\n\n\nclass ValidationParams(univ.Sequence):\n    pass\n\nValidationParams.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('hashAlg', univ.ObjectIdentifier()),\n    namedtype.NamedType('seed', univ.OctetString())\n)\n\n\nat_validation_parameters = rfc5652.Attribute()\nat_validation_parameters['attrType'] = id_attr_validation_parameters\nat_validation_parameters['attrValues'][0] = ValidationParams()\n\n\n# Map of Attribute Type OIDs to Attributes added to the\n# ones that are in rfc5652.py\n\n_cmsAttributesMapUpdate = {\n    id_attr_validation_parameters: ValidationParams(),\n}\n\nrfc5652.cmsAttributesMap.update(_cmsAttributesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8494.py",
    "content": "# This file is being contributed to pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Multicast Email (MULE) over Allied Communications Publication 142\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8494.txt\n\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import namedval\nfrom pyasn1.type import tag\nfrom pyasn1.type import univ\n\n\nid_mmhs_CDT = univ.ObjectIdentifier('1.3.26.0.4406.0.4.2')\n\n\nclass AlgorithmID_ShortForm(univ.Integer):\n    pass\n\nAlgorithmID_ShortForm.namedValues = namedval.NamedValues(\n    ('zlibCompress', 0)\n)\n\n\nclass ContentType_ShortForm(univ.Integer):\n    pass\n\nContentType_ShortForm.namedValues = namedval.NamedValues(\n    ('unidentified', 0),\n    ('external', 1),\n    ('p1', 2),\n    ('p3', 3),\n    ('p7', 4),\n    ('mule', 25)\n)\n\n\nclass CompressedContentInfo(univ.Sequence):\n    pass\n\nCompressedContentInfo.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('unnamed', univ.Choice(componentType=namedtype.NamedTypes(\n        namedtype.NamedType('contentType-ShortForm',\n            ContentType_ShortForm().subtype(explicitTag=tag.Tag(\n                tag.tagClassContext, tag.tagFormatSimple, 0))),\n        namedtype.NamedType('contentType-OID',\n            univ.ObjectIdentifier().subtype(explicitTag=tag.Tag(\n                tag.tagClassContext, tag.tagFormatSimple, 1)))\n    ))),\n    namedtype.NamedType('compressedContent',\n        univ.OctetString().subtype(explicitTag=tag.Tag(\n            tag.tagClassContext, tag.tagFormatSimple, 0)))\n)\n\n\nclass CompressionAlgorithmIdentifier(univ.Choice):\n    pass\n\nCompressionAlgorithmIdentifier.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('algorithmID-ShortForm',\n        AlgorithmID_ShortForm().subtype(explicitTag=tag.Tag(\n            tag.tagClassContext, tag.tagFormatSimple, 0))),\n    namedtype.NamedType('algorithmID-OID',\n        univ.ObjectIdentifier().subtype(explicitTag=tag.Tag(\n            tag.tagClassContext, tag.tagFormatSimple, 1)))\n)\n\n\nclass CompressedData(univ.Sequence):\n    pass\n\nCompressedData.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('compressionAlgorithm', CompressionAlgorithmIdentifier()),\n    namedtype.NamedType('compressedContentInfo', CompressedContentInfo())\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8520.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n# Modified by Russ Housley to add maps for use with opentypes.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# X.509 Extensions for MUD URL and MUD Signer;\n# Object Identifier for CMS Content Type for a MUD file\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8520.txt\n#\n\nfrom pyasn1.type import char\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\nfrom pyasn1_modules import rfc5652\n\n\n# X.509 Extension for MUD URL\n\nid_pe_mud_url = univ.ObjectIdentifier('1.3.6.1.5.5.7.1.25')\n\nclass MUDURLSyntax(char.IA5String):\n    pass\n\n\n# X.509 Extension for MUD Signer\n\nid_pe_mudsigner = univ.ObjectIdentifier('1.3.6.1.5.5.7.1.30')\n\nclass MUDsignerSyntax(rfc5280.Name):\n    pass\n\n\n# Object Identifier for CMS Content Type for a MUD file\n\nid_ct_mudtype = univ.ObjectIdentifier('1.2.840.113549.1.9.16.1.41')\n\n\n# Map of Certificate Extension OIDs to Extensions added to the\n# ones that are in rfc5280.py\n\n_certificateExtensionsMapUpdate = {\n    id_pe_mud_url: MUDURLSyntax(),\n    id_pe_mudsigner: MUDsignerSyntax(),\n}\n\nrfc5280.certificateExtensionsMap.update(_certificateExtensionsMapUpdate)\n\n\n# Map of Content Type OIDs to Content Types added to the\n# ones that are in rfc5652.py\n\n_cmsContentTypesMapUpdate = {\n    id_ct_mudtype: univ.OctetString(),\n}\n\nrfc5652.cmsContentTypesMap.update(_cmsContentTypesMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8619.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# Algorithm Identifiers for HKDF\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8619.txt\n#\n\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\n\n# Object Identifiers\n\nid_alg_hkdf_with_sha256 = univ.ObjectIdentifier('1.2.840.113549.1.9.16.3.28')\n\n\nid_alg_hkdf_with_sha384 = univ.ObjectIdentifier('1.2.840.113549.1.9.16.3.29')\n\n\nid_alg_hkdf_with_sha512 = univ.ObjectIdentifier('1.2.840.113549.1.9.16.3.30')\n\n\n# Key Derivation Algorithm Identifiers\n\nkda_hkdf_with_sha256 = rfc5280.AlgorithmIdentifier()\nkda_hkdf_with_sha256['algorithm'] = id_alg_hkdf_with_sha256\n# kda_hkdf_with_sha256['parameters'] are absent\n\n\nkda_hkdf_with_sha384 = rfc5280.AlgorithmIdentifier()\nkda_hkdf_with_sha384['algorithm'] = id_alg_hkdf_with_sha384\n# kda_hkdf_with_sha384['parameters'] are absent\n\n\nkda_hkdf_with_sha512 = rfc5280.AlgorithmIdentifier()\nkda_hkdf_with_sha512['algorithm'] = id_alg_hkdf_with_sha512\n# kda_hkdf_with_sha512['parameters'] are absent\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules/rfc8649.py",
    "content": "#\n# This file is part of pyasn1-modules software.\n#\n# Created by Russ Housley with assistance from asn1ate v.0.6.0.\n#\n# Copyright (c) 2019, Vigil Security, LLC\n# License: http://snmplabs.com/pyasn1/license.html\n#\n# X.509 Certificate Extension for Hash Of Root Key\n#\n# ASN.1 source from:\n# https://www.rfc-editor.org/rfc/rfc8649.txt\n#\n\nfrom pyasn1.type import namedtype\nfrom pyasn1.type import univ\n\nfrom pyasn1_modules import rfc5280\n\n\nid_ce_hashOfRootKey = univ.ObjectIdentifier('1.3.6.1.4.1.51483.2.1')\n\n\nclass HashedRootKey(univ.Sequence):\n    pass\n\nHashedRootKey.componentType = namedtype.NamedTypes(\n    namedtype.NamedType('hashAlg', rfc5280.AlgorithmIdentifier()),\n    namedtype.NamedType('hashValue', univ.OctetString())\n)\n\n\n# Map of Certificate Extension OIDs to Extensions added to the\n# ones that are in rfc5280.py\n\n_certificateExtensionsMapUpdate = {\n    id_ce_hashOfRootKey: HashedRootKey(),\t\n}\n\nrfc5280.certificateExtensionsMap.update(_certificateExtensionsMapUpdate)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules-0.2.7.dist-info/DESCRIPTION.rst",
    "content": "A collection of ASN.1 modules expressed in form of pyasn1 classes. Includes protocols PDUs definition (SNMP, LDAP etc.) and various data structures (X.509, PKCS etc.).\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules-0.2.7.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules-0.2.7.dist-info/LICENSE.txt",
    "content": "Copyright (c) 2005-2019, Ilya Etingof <etingof@gmail.com>\nAll rights reserved.\n\nRedistribution and use in source and binary forms, with or without\nmodification, are permitted provided that the following conditions are met:\n\n  * Redistributions of source code must retain the above copyright notice, \n    this list of conditions and the following disclaimer.\n\n  * Redistributions in binary form must reproduce the above copyright notice,\n    this list of conditions and the following disclaimer in the documentation\n    and/or other materials provided with the distribution.\n\nTHIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \"AS IS\"\nAND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE \nIMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE \nARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE\nLIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR\nCONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF\nSUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS\nINTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN\nCONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)\nARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\nPOSSIBILITY OF SUCH DAMAGE. \n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules-0.2.7.dist-info/METADATA",
    "content": "Metadata-Version: 2.0\nName: pyasn1-modules\nVersion: 0.2.7\nSummary: A collection of ASN.1-based protocols modules.\nHome-page: https://github.com/etingof/pyasn1-modules\nAuthor: Ilya Etingof <etingof@gmail.com>\nAuthor-email: etingof@gmail.com\nLicense: BSD-2-Clause\nPlatform: any\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Environment :: Console\nClassifier: Intended Audience :: Developers\nClassifier: Intended Audience :: Education\nClassifier: Intended Audience :: Information Technology\nClassifier: Intended Audience :: System Administrators\nClassifier: Intended Audience :: Telecommunications Industry\nClassifier: License :: OSI Approved :: BSD License\nClassifier: Natural Language :: English\nClassifier: Operating System :: OS Independent\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.4\nClassifier: Programming Language :: Python :: 2.5\nClassifier: Programming Language :: Python :: 2.6\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.2\nClassifier: Programming Language :: Python :: 3.3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nClassifier: Topic :: Communications\nClassifier: Topic :: System :: Monitoring\nClassifier: Topic :: System :: Networking :: Monitoring\nClassifier: Topic :: Software Development :: Libraries :: Python Modules\nRequires-Dist: pyasn1 (>=0.4.6,<0.5.0)\n\nA collection of ASN.1 modules expressed in form of pyasn1 classes. Includes protocols PDUs definition (SNMP, LDAP etc.) and various data structures (X.509, PKCS etc.).\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules-0.2.7.dist-info/RECORD",
    "content": "pyasn1_modules-0.2.7.dist-info/DESCRIPTION.rst,sha256=Z8HrCNCVUAFBjxwa6YsEPUgeMMXd44PbFObjn5h1cdA,170\r\npyasn1_modules-0.2.7.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\npyasn1_modules-0.2.7.dist-info/LICENSE.txt,sha256=IsXMaSKrXWn7oy2MXuTN0UmBUIy1OvwOvYVZOEf9laU,1334\r\npyasn1_modules-0.2.7.dist-info/METADATA,sha256=wDV_TnJWzvbNKF6mV9tnMJFq05wjrJxAgD7dlQvEmxg,1777\r\npyasn1_modules-0.2.7.dist-info/RECORD,,\r\npyasn1_modules-0.2.7.dist-info/WHEEL,sha256=o2k-Qa-RMNIJmUdIc7KU6VWR_ErNRbWNlxDIpl7lm34,110\r\npyasn1_modules-0.2.7.dist-info/metadata.json,sha256=CGnAZuGdv9Oghr7pzRK_sZ125zrXzu2Ud_wMlbO6NEM,1661\r\npyasn1_modules-0.2.7.dist-info/top_level.txt,sha256=e_AojfE1DNY4M8P9LAS7qh8Fx3eOmovobqkr7NEjlg4,15\r\npyasn1_modules-0.2.7.dist-info/zip-safe,sha256=AbpHGcgLb-kRsJGnwFEktk7uzpZOCcBY74-YBdrKVGs,1\r\npyasn1_modules/__init__.py,sha256=54eX4ZQ0gHViKgYb3Jh8gyQ0jHGsp6NSN7JX4E4e5b4,65\r\npyasn1_modules/__pycache__/__init__.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/pem.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc1155.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc1157.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc1901.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc1902.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc1905.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc2251.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc2314.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc2315.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc2437.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc2459.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc2511.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc2560.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc2634.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc2985.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc2986.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3161.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3274.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3279.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3280.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3281.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3412.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3414.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3447.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3560.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3565.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3709.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3770.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3779.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc3852.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc4055.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc4073.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc4108.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc4210.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc4211.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5035.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5083.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5084.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5208.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5280.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5480.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5649.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5652.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5751.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5914.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5915.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5934.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5940.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5958.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc5990.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc6010.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc6019.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc6031.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc6032.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc6210.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc6211.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc6402.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc7030.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc7191.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc7292.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc7296.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc7773.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc7894.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc7906.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc7914.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8017.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8018.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8103.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8209.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8226.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8358.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8360.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8398.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8410.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8418.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8419.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8479.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8494.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8520.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8619.cpython-36.pyc,,\r\npyasn1_modules/__pycache__/rfc8649.cpython-36.pyc,,\r\npyasn1_modules/pem.py,sha256=j3qNWa4Bbgq6NKs343cUGYrhyUzHUDAU-hC23aeCIog,2058\r\npyasn1_modules/rfc1155.py,sha256=9xUfGI35hFQ3OF4UxGd3V_B0DMflGfnLqjjmlEngDqs,2683\r\npyasn1_modules/rfc1157.py,sha256=GnLq_jcPLdUHREomh7HmsT9ZyNnPDw4NLEEFwppCyJQ,3554\r\npyasn1_modules/rfc1901.py,sha256=Uq8zJ4HdCClnV0du14_hF3ggNdHAM-heaxuz23cwoOQ,646\r\npyasn1_modules/rfc1902.py,sha256=JUYq7hBfik2w-_Ju17hpe_j00QKAZEguwe20BK8fC9I,3705\r\npyasn1_modules/rfc1905.py,sha256=qTqjTF4L4Wz4svQADIjliqyqPs0mnD8GDqhgngJWdN0,4831\r\npyasn1_modules/rfc2251.py,sha256=hBEhoVDvkNxSQY6zeX6WxpKL1i2vqrIPZ5Jmvl5KC7M,26931\r\npyasn1_modules/rfc2314.py,sha256=r9tTFaflcmVtQVTDoDo_-OYk5W98gD4NglZX78j3a6M,1313\r\npyasn1_modules/rfc2315.py,sha256=ZfyNEbwHz-q0y3twhBZlogIeWNrP_lcBUAzIfcXYGUo,9666\r\npyasn1_modules/rfc2437.py,sha256=9l6YNwD0BUrdhmg5NAs_K3PqrwfJVDR-5N9_EjeRRk4,2623\r\npyasn1_modules/rfc2459.py,sha256=TYZuSTbv868F5dXKi83H-ShqCwy7SQIyUAMBWVDgc2Q,50002\r\npyasn1_modules/rfc2511.py,sha256=S6Bggb2UR45IRdSNVdWFVfedsa1Om2VoZILlY-oL6QU,10350\r\npyasn1_modules/rfc2560.py,sha256=QfVWkw4GJXKVsjDUPh9ORF2kpi5XQTLlZdIB677qvv8,8406\r\npyasn1_modules/rfc2634.py,sha256=7sTu3YysbHImknLk7CbdQIjJjt6cC849-XqkuEDgFPk,9425\r\npyasn1_modules/rfc2985.py,sha256=8GL8jkWGpN1t7sVaEtyhVgfCM80XhlYOUEi9jhcAX0E,14359\r\npyasn1_modules/rfc2986.py,sha256=sjlXnV2fnyaYqZjgepsneTqXiwk2N0mrdExEuEHp92I,1896\r\npyasn1_modules/rfc3161.py,sha256=9kz_TvQ5_OpBPuHQDAh2WyqKeOThgxPq8E5iBB-sNp8,4260\r\npyasn1_modules/rfc3274.py,sha256=ZULbMN3wksvv_fWvT_C1vskxuh_IzRCAD9QD1hdk-lo,1670\r\npyasn1_modules/rfc3279.py,sha256=RBgSR_yoFxyHx3hhqSGPp0aek7iPDQFDEYfdTIshLlY,5972\r\npyasn1_modules/rfc3280.py,sha256=nra0JN8HEPg3XorP-ry8H1Wb7xiG81VBGSFmKFCEldU,46620\r\npyasn1_modules/rfc3281.py,sha256=s0MV7DaVXhap8bIeKqCbjmrwrMytxBTFPFl2TD21g6Y,9866\r\npyasn1_modules/rfc3412.py,sha256=_PQEwCmLcxlNlflAv-xQbfwTr_Fks7FvmBfCGQIF3ME,1956\r\npyasn1_modules/rfc3414.py,sha256=lbn5t4ycmhbg6smNvpZwcX3L1VaU0ns3VYplyHCyVc0,1167\r\npyasn1_modules/rfc3447.py,sha256=c5KidhoTIibl1nvqvEIbBSBFmbQcAns75GDpFwMHUhM,1605\r\npyasn1_modules/rfc3560.py,sha256=3Ud7sY7OAV_4KGNn_hg5xZblEkxE_ILH1kP2TI-KbZw,1818\r\npyasn1_modules/rfc3565.py,sha256=nRephcXY7ioG5I4iaT6mSQYGwaouRQXoMnp2kFQQOE0,1438\r\npyasn1_modules/rfc3709.py,sha256=9G4nLJMxpUAsZKZ6MXs70sUIY1tFjTT4C2j9mCykDQY,6386\r\npyasn1_modules/rfc3770.py,sha256=5oHvmhD1E8ef-mdqvNo-_TggqepP78jOPOnAbLoNEWQ,1405\r\npyasn1_modules/rfc3779.py,sha256=x8HYKGCaGO3BohCREHQUEa1oYGArWIC2J0PftxiPrjI,3260\r\npyasn1_modules/rfc3852.py,sha256=Ekx1BOSu7Bsg1IFO96uDZ4iGCGzu-r5n0KPwvxT18BY,20101\r\npyasn1_modules/rfc4055.py,sha256=f2rlyaBeNhl287b_qLLsNpjgwxYRVzBgbOH28UnJZwQ,10392\r\npyasn1_modules/rfc4073.py,sha256=bHVssQE3yXwetes1TPWAT30UhOEinHj8vEBaYjWC24g,1636\r\npyasn1_modules/rfc4108.py,sha256=-I63Z0crn_Elvr85nSa9BqAlRx7cIJfEb9ItPDkq8JY,10598\r\npyasn1_modules/rfc4210.py,sha256=2e53NGVNOxJqIoLTlA8w7KWp_HmcRg5F3x2T6D9hYdA,28520\r\npyasn1_modules/rfc4211.py,sha256=W2YVMJWUEsRNGvdEmf4Ktoav5mwHfDhJyaPsCso9hFA,12110\r\npyasn1_modules/rfc5035.py,sha256=xgw9ztAM_bJKlIUCzni2zcE_z3ErEuXpWRPJpXI1KEw,4523\r\npyasn1_modules/rfc5083.py,sha256=ENXIEL0CYrTqvf_iwpvAkBBJpi2pOFNBDFEYc37yqF8,1888\r\npyasn1_modules/rfc5084.py,sha256=i9sFdUklbdTQodTya4BNFnpeFxGIB2uS1aNkfFdZpu4,2855\r\npyasn1_modules/rfc5208.py,sha256=O2ZDYy-lqXeQcK_9gryuvm71TUnzIF7yL8j_LrIBEQc,1432\r\npyasn1_modules/rfc5280.py,sha256=GweilWgd70v1Z0YovOSU3Bnu7vvu4rMscgE6WhksBkg,51236\r\npyasn1_modules/rfc5480.py,sha256=GzBTgKQ68V-L-Qy0SBrCQMgqR5mGF7U73uXlBzfV2Jk,4834\r\npyasn1_modules/rfc5649.py,sha256=3A--LQL7iw8DGXSDyiSUeh6wwFPKQQGyVY94mNzY0Ek,830\r\npyasn1_modules/rfc5652.py,sha256=jmL6fOHqTAQvceW9mtkAZpOaxkemRjWDrdpL4pglQkk,21451\r\npyasn1_modules/rfc5751.py,sha256=M8kTLARhdqh3UqmlZv_FWJfuJb-ph7P6MVGxSP7Q4wQ,3198\r\npyasn1_modules/rfc5914.py,sha256=nXOb4SvESbEFYI8h0nEYkRArNZ9w5Zqxva_4uAdMXNY,3714\r\npyasn1_modules/rfc5915.py,sha256=VqMRd_Ksm0LFvE5XX4_MO6BdFG7Ch7NdQcwT_DMWAK4,1056\r\npyasn1_modules/rfc5934.py,sha256=77z96SeP4iM2R6Rl5-Vx7OaENA8ZQvzrfhDVZRy9lqk,23798\r\npyasn1_modules/rfc5940.py,sha256=66rMmgyKBhay-RZsWaKz7PUGwp0bqEAVULPb4Edk1vk,1613\r\npyasn1_modules/rfc5958.py,sha256=NZPx-7FvjzgErz2lTURiRq8m3XCZ7D9QbGDhtIF-zCE,2650\r\npyasn1_modules/rfc5990.py,sha256=-b0St64ba3LVRGSeNmbGoMIbkU8c8FDpo4zFWF0PCFM,5505\r\npyasn1_modules/rfc6010.py,sha256=F43AYVFUwu-2_xjJE2Wmw1Wdt0K7l3vg0_fCa_QHqBU,2347\r\npyasn1_modules/rfc6019.py,sha256=vzj5tfG4694-ucpErpAtE1DVOE4-v0dkN894Zr9xm4o,1086\r\npyasn1_modules/rfc6031.py,sha256=X2cjNyVnrX3G2zG7kD4Rq__kF6-ftmmnqHlCQJDCuMU,12137\r\npyasn1_modules/rfc6032.py,sha256=uNAu5zLHg0b583xxzFNUZxCnJaCzMw1iobzREuejMoM,1950\r\npyasn1_modules/rfc6210.py,sha256=wLifK_EShv1a4TOhGJ-k9zA1kVVYVDNjS-Rh0ohmCh0,1052\r\npyasn1_modules/rfc6211.py,sha256=XotTBQVseK7y0nJB4Fx-npdhRHeH53IM84kGupWIprk,2257\r\npyasn1_modules/rfc6402.py,sha256=0ciItKf7voeSCTZl1kKYd6gyQ68IZzwMe1-fj16etKs,17148\r\npyasn1_modules/rfc7030.py,sha256=t-s2BDyX3Zk2sy_jMQl-P2I2NXFOn7huu0wFcM-2sqs,1441\r\npyasn1_modules/rfc7191.py,sha256=uMsBzJ9167wxsiPYDQUnZQFVFNfgUxnCwRNeKnXxNGM,7062\r\npyasn1_modules/rfc7292.py,sha256=wORjDGD_aqHoujB2wu6nNrEjYTw3VO_xDp-Qx0VWLbc,8478\r\npyasn1_modules/rfc7296.py,sha256=eAZpZ2dgUhxbJrLLGtDff4UspauG7Tr5dj8WELYHnUM,885\r\npyasn1_modules/rfc7773.py,sha256=6UGPWyVYuicKe6snZCnD1wuAu1MOVgzPoSALL2uvTrI,1315\r\npyasn1_modules/rfc7894.py,sha256=HLaSBoOUB-_cSE5935TXAnuFBVpZBv6jBnLOPp_-LNk,2769\r\npyasn1_modules/rfc7906.py,sha256=mDf1pWwVNlCcEQfswUhtQDStAnwS-5xbZtjMlfnWLdI,18921\r\npyasn1_modules/rfc7914.py,sha256=JxWGnXV-V13xzOn7c7-_3vxDNpkPtdZIYU4KF2kFXR4,1493\r\npyasn1_modules/rfc8017.py,sha256=pwPRSchvMtXuatcCLULHuvSL8kAPEqkC4aIJjd5vEAo,4178\r\npyasn1_modules/rfc8018.py,sha256=8_49xA3vEOdlGUhasw2xTUv4TpHBvjRuoonMT_k1TTk,6166\r\npyasn1_modules/rfc8103.py,sha256=pNYAFfKCNrg9ZmRKsNNwr2ooptEABF3gMaPbqCroRnQ,1017\r\npyasn1_modules/rfc8209.py,sha256=9EQ077rjD9uoTZWIOGmeOaHLDDq0IRXh3Rt0eYB-Ysc,393\r\npyasn1_modules/rfc8226.py,sha256=nkSqgdiXlH_gcZpXJb9VNJ_44yTEYJ77GmWb9Sg0ZKU,4101\r\npyasn1_modules/rfc8358.py,sha256=aiHaXQAaaP-q5c90x_uZHSpQRTB-yekwhe6V9-EtrFg,1136\r\npyasn1_modules/rfc8360.py,sha256=T4sY6o2VLVPnZ9s4yJ8PzfVA8Y60ne-1KcVNtw5yt-s,1075\r\npyasn1_modules/rfc8398.py,sha256=i3lwgf__9oJzOaaHJKWmDAx3d_deKNCCuvIDWqQWiJ4,1192\r\npyasn1_modules/rfc8410.py,sha256=nteKyTKcIwVlgh1qUl-8kE63kKG-KgWtLrfF92TWyyQ,971\r\npyasn1_modules/rfc8418.py,sha256=eTCPTOm6t-RyHd6PlowLogDzUO72lRddESYLiSiOpC0,1109\r\npyasn1_modules/rfc8419.py,sha256=qcvBlXxqvsCvG_F6AKKjqBderqbWwBy8zjZOjAPdYU4,1704\r\npyasn1_modules/rfc8479.py,sha256=rDKzrp-MmEF0t3E7lqKXhgwcggvx8NoWVbtJHGLxDYM,1142\r\npyasn1_modules/rfc8494.py,sha256=GMht1RdAbjHLtSqHdJ2cLO8HXRz6SLIPE254T4oy0S4,2363\r\npyasn1_modules/rfc8520.py,sha256=_o00lv2MYciOqo0UKjlZBQNY_MzzgQt1SV9VXCI0T9A,1496\r\npyasn1_modules/rfc8619.py,sha256=qSYiBefLSFukLg6VIgR6dnhX-uBwJMItxqHjNXnBgM0,1136\r\npyasn1_modules/rfc8649.py,sha256=oHCQK7g4vKs1B0IO9GgiidTyPOk4pz5bYkXSRmBOAHo,982\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules-0.2.7.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.29.0)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules-0.2.7.dist-info/metadata.json",
    "content": "{\"classifiers\": [\"Development Status :: 5 - Production/Stable\", \"Environment :: Console\", \"Intended Audience :: Developers\", \"Intended Audience :: Education\", \"Intended Audience :: Information Technology\", \"Intended Audience :: System Administrators\", \"Intended Audience :: Telecommunications Industry\", \"License :: OSI Approved :: BSD License\", \"Natural Language :: English\", \"Operating System :: OS Independent\", \"Programming Language :: Python :: 2\", \"Programming Language :: Python :: 2.4\", \"Programming Language :: Python :: 2.5\", \"Programming Language :: Python :: 2.6\", \"Programming Language :: Python :: 2.7\", \"Programming Language :: Python :: 3\", \"Programming Language :: Python :: 3.2\", \"Programming Language :: Python :: 3.3\", \"Programming Language :: Python :: 3.4\", \"Programming Language :: Python :: 3.5\", \"Programming Language :: Python :: 3.6\", \"Programming Language :: Python :: 3.7\", \"Topic :: Communications\", \"Topic :: System :: Monitoring\", \"Topic :: System :: Networking :: Monitoring\", \"Topic :: Software Development :: Libraries :: Python Modules\"], \"extensions\": {\"python.details\": {\"contacts\": [{\"email\": \"etingof@gmail.com\", \"name\": \"Ilya Etingof <etingof@gmail.com>\", \"role\": \"author\"}], \"document_names\": {\"description\": \"DESCRIPTION.rst\", \"license\": \"LICENSE.txt\"}, \"project_urls\": {\"Home\": \"https://github.com/etingof/pyasn1-modules\"}}}, \"extras\": [], \"generator\": \"bdist_wheel (0.29.0)\", \"license\": \"BSD-2-Clause\", \"metadata_version\": \"2.0\", \"name\": \"pyasn1-modules\", \"platform\": \"any\", \"run_requires\": [{\"requires\": [\"pyasn1 (>=0.4.6,<0.5.0)\"]}], \"summary\": \"A collection of ASN.1-based protocols modules.\", \"version\": \"0.2.7\"}"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules-0.2.7.dist-info/top_level.txt",
    "content": "pyasn1_modules\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pyasn1_modules-0.2.7.dist-info/zip-safe",
    "content": "\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/__init__.py",
    "content": "#-----------------------------------------------------------------\n# pycparser: __init__.py\n#\n# This package file exports some convenience functions for\n# interacting with pycparser\n#\n# Eli Bendersky [https://eli.thegreenplace.net/]\n# License: BSD\n#-----------------------------------------------------------------\n__all__ = ['c_lexer', 'c_parser', 'c_ast']\n__version__ = '2.19'\n\nimport io\nfrom subprocess import check_output\nfrom .c_parser import CParser\n\n\ndef preprocess_file(filename, cpp_path='cpp', cpp_args=''):\n    \"\"\" Preprocess a file using cpp.\n\n        filename:\n            Name of the file you want to preprocess.\n\n        cpp_path:\n        cpp_args:\n            Refer to the documentation of parse_file for the meaning of these\n            arguments.\n\n        When successful, returns the preprocessed file's contents.\n        Errors from cpp will be printed out.\n    \"\"\"\n    path_list = [cpp_path]\n    if isinstance(cpp_args, list):\n        path_list += cpp_args\n    elif cpp_args != '':\n        path_list += [cpp_args]\n    path_list += [filename]\n\n    try:\n        # Note the use of universal_newlines to treat all newlines\n        # as \\n for Python's purpose\n        text = check_output(path_list, universal_newlines=True)\n    except OSError as e:\n        raise RuntimeError(\"Unable to invoke 'cpp'.  \" +\n            'Make sure its path was passed correctly\\n' +\n            ('Original error: %s' % e))\n\n    return text\n\n\ndef parse_file(filename, use_cpp=False, cpp_path='cpp', cpp_args='',\n               parser=None):\n    \"\"\" Parse a C file using pycparser.\n\n        filename:\n            Name of the file you want to parse.\n\n        use_cpp:\n            Set to True if you want to execute the C pre-processor\n            on the file prior to parsing it.\n\n        cpp_path:\n            If use_cpp is True, this is the path to 'cpp' on your\n            system. If no path is provided, it attempts to just\n            execute 'cpp', so it must be in your PATH.\n\n        cpp_args:\n            If use_cpp is True, set this to the command line arguments strings\n            to cpp. Be careful with quotes - it's best to pass a raw string\n            (r'') here. For example:\n            r'-I../utils/fake_libc_include'\n            If several arguments are required, pass a list of strings.\n\n        parser:\n            Optional parser object to be used instead of the default CParser\n\n        When successful, an AST is returned. ParseError can be\n        thrown if the file doesn't parse successfully.\n\n        Errors from cpp will be printed out.\n    \"\"\"\n    if use_cpp:\n        text = preprocess_file(filename, cpp_path, cpp_args)\n    else:\n        with io.open(filename) as f:\n            text = f.read()\n\n    if parser is None:\n        parser = CParser()\n    return parser.parse(text, filename)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/_ast_gen.py",
    "content": "#-----------------------------------------------------------------\n# _ast_gen.py\n#\n# Generates the AST Node classes from a specification given in\n# a configuration file\n#\n# The design of this module was inspired by astgen.py from the\n# Python 2.5 code-base.\n#\n# Eli Bendersky [https://eli.thegreenplace.net/]\n# License: BSD\n#-----------------------------------------------------------------\nimport pprint\nfrom string import Template\n\n\nclass ASTCodeGenerator(object):\n    def __init__(self, cfg_filename='_c_ast.cfg'):\n        \"\"\" Initialize the code generator from a configuration\n            file.\n        \"\"\"\n        self.cfg_filename = cfg_filename\n        self.node_cfg = [NodeCfg(name, contents)\n            for (name, contents) in self.parse_cfgfile(cfg_filename)]\n\n    def generate(self, file=None):\n        \"\"\" Generates the code into file, an open file buffer.\n        \"\"\"\n        src = Template(_PROLOGUE_COMMENT).substitute(\n            cfg_filename=self.cfg_filename)\n\n        src += _PROLOGUE_CODE\n        for node_cfg in self.node_cfg:\n            src += node_cfg.generate_source() + '\\n\\n'\n\n        file.write(src)\n\n    def parse_cfgfile(self, filename):\n        \"\"\" Parse the configuration file and yield pairs of\n            (name, contents) for each node.\n        \"\"\"\n        with open(filename, \"r\") as f:\n            for line in f:\n                line = line.strip()\n                if not line or line.startswith('#'):\n                    continue\n                colon_i = line.find(':')\n                lbracket_i = line.find('[')\n                rbracket_i = line.find(']')\n                if colon_i < 1 or lbracket_i <= colon_i or rbracket_i <= lbracket_i:\n                    raise RuntimeError(\"Invalid line in %s:\\n%s\\n\" % (filename, line))\n\n                name = line[:colon_i]\n                val = line[lbracket_i + 1:rbracket_i]\n                vallist = [v.strip() for v in val.split(',')] if val else []\n                yield name, vallist\n\n\nclass NodeCfg(object):\n    \"\"\" Node configuration.\n\n        name: node name\n        contents: a list of contents - attributes and child nodes\n        See comment at the top of the configuration file for details.\n    \"\"\"\n\n    def __init__(self, name, contents):\n        self.name = name\n        self.all_entries = []\n        self.attr = []\n        self.child = []\n        self.seq_child = []\n\n        for entry in contents:\n            clean_entry = entry.rstrip('*')\n            self.all_entries.append(clean_entry)\n\n            if entry.endswith('**'):\n                self.seq_child.append(clean_entry)\n            elif entry.endswith('*'):\n                self.child.append(clean_entry)\n            else:\n                self.attr.append(entry)\n\n    def generate_source(self):\n        src = self._gen_init()\n        src += '\\n' + self._gen_children()\n        src += '\\n' + self._gen_iter()\n\n        src += '\\n' + self._gen_attr_names()\n        return src\n\n    def _gen_init(self):\n        src = \"class %s(Node):\\n\" % self.name\n\n        if self.all_entries:\n            args = ', '.join(self.all_entries)\n            slots = ', '.join(\"'{0}'\".format(e) for e in self.all_entries)\n            slots += \", 'coord', '__weakref__'\"\n            arglist = '(self, %s, coord=None)' % args\n        else:\n            slots = \"'coord', '__weakref__'\"\n            arglist = '(self, coord=None)'\n\n        src += \"    __slots__ = (%s)\\n\" % slots\n        src += \"    def __init__%s:\\n\" % arglist\n\n        for name in self.all_entries + ['coord']:\n            src += \"        self.%s = %s\\n\" % (name, name)\n\n        return src\n\n    def _gen_children(self):\n        src = '    def children(self):\\n'\n\n        if self.all_entries:\n            src += '        nodelist = []\\n'\n\n            for child in self.child:\n                src += (\n                    '        if self.%(child)s is not None:' +\n                    ' nodelist.append((\"%(child)s\", self.%(child)s))\\n') % (\n                        dict(child=child))\n\n            for seq_child in self.seq_child:\n                src += (\n                    '        for i, child in enumerate(self.%(child)s or []):\\n'\n                    '            nodelist.append((\"%(child)s[%%d]\" %% i, child))\\n') % (\n                        dict(child=seq_child))\n\n            src += '        return tuple(nodelist)\\n'\n        else:\n            src += '        return ()\\n'\n\n        return src\n\n    def _gen_iter(self):\n        src = '    def __iter__(self):\\n'\n\n        if self.all_entries:\n            for child in self.child:\n                src += (\n                    '        if self.%(child)s is not None:\\n' +\n                    '            yield self.%(child)s\\n') % (dict(child=child))\n\n            for seq_child in self.seq_child:\n                src += (\n                    '        for child in (self.%(child)s or []):\\n'\n                    '            yield child\\n') % (dict(child=seq_child))\n\n            if not (self.child or self.seq_child):\n                # Empty generator\n                src += (\n                    '        return\\n' +\n                    '        yield\\n')\n        else:\n            # Empty generator\n            src += (\n                '        return\\n' +\n                '        yield\\n')\n\n        return src\n\n    def _gen_attr_names(self):\n        src = \"    attr_names = (\" + ''.join(\"%r, \" % nm for nm in self.attr) + ')'\n        return src\n\n\n_PROLOGUE_COMMENT = \\\nr'''#-----------------------------------------------------------------\n# ** ATTENTION **\n# This code was automatically generated from the file:\n# $cfg_filename\n#\n# Do not modify it directly. Modify the configuration file and\n# run the generator again.\n# ** ** *** ** **\n#\n# pycparser: c_ast.py\n#\n# AST Node classes.\n#\n# Eli Bendersky [https://eli.thegreenplace.net/]\n# License: BSD\n#-----------------------------------------------------------------\n\n'''\n\n_PROLOGUE_CODE = r'''\nimport sys\n\ndef _repr(obj):\n    \"\"\"\n    Get the representation of an object, with dedicated pprint-like format for lists.\n    \"\"\"\n    if isinstance(obj, list):\n        return '[' + (',\\n '.join((_repr(e).replace('\\n', '\\n ') for e in obj))) + '\\n]'\n    else:\n        return repr(obj) \n\nclass Node(object):\n    __slots__ = ()\n    \"\"\" Abstract base class for AST nodes.\n    \"\"\"\n    def __repr__(self):\n        \"\"\" Generates a python representation of the current node\n        \"\"\"\n        result = self.__class__.__name__ + '('\n        \n        indent = ''\n        separator = ''\n        for name in self.__slots__[:-2]:\n            result += separator\n            result += indent\n            result += name + '=' + (_repr(getattr(self, name)).replace('\\n', '\\n  ' + (' ' * (len(name) + len(self.__class__.__name__)))))\n            \n            separator = ','\n            indent = '\\n ' + (' ' * len(self.__class__.__name__))\n        \n        result += indent + ')'\n        \n        return result\n\n    def children(self):\n        \"\"\" A sequence of all children that are Nodes\n        \"\"\"\n        pass\n\n    def show(self, buf=sys.stdout, offset=0, attrnames=False, nodenames=False, showcoord=False, _my_node_name=None):\n        \"\"\" Pretty print the Node and all its attributes and\n            children (recursively) to a buffer.\n\n            buf:\n                Open IO buffer into which the Node is printed.\n\n            offset:\n                Initial offset (amount of leading spaces)\n\n            attrnames:\n                True if you want to see the attribute names in\n                name=value pairs. False to only see the values.\n\n            nodenames:\n                True if you want to see the actual node names\n                within their parents.\n\n            showcoord:\n                Do you want the coordinates of each Node to be\n                displayed.\n        \"\"\"\n        lead = ' ' * offset\n        if nodenames and _my_node_name is not None:\n            buf.write(lead + self.__class__.__name__+ ' <' + _my_node_name + '>: ')\n        else:\n            buf.write(lead + self.__class__.__name__+ ': ')\n\n        if self.attr_names:\n            if attrnames:\n                nvlist = [(n, getattr(self,n)) for n in self.attr_names]\n                attrstr = ', '.join('%s=%s' % nv for nv in nvlist)\n            else:\n                vlist = [getattr(self, n) for n in self.attr_names]\n                attrstr = ', '.join('%s' % v for v in vlist)\n            buf.write(attrstr)\n\n        if showcoord:\n            buf.write(' (at %s)' % self.coord)\n        buf.write('\\n')\n\n        for (child_name, child) in self.children():\n            child.show(\n                buf,\n                offset=offset + 2,\n                attrnames=attrnames,\n                nodenames=nodenames,\n                showcoord=showcoord,\n                _my_node_name=child_name)\n\n\nclass NodeVisitor(object):\n    \"\"\" A base NodeVisitor class for visiting c_ast nodes.\n        Subclass it and define your own visit_XXX methods, where\n        XXX is the class name you want to visit with these\n        methods.\n\n        For example:\n\n        class ConstantVisitor(NodeVisitor):\n            def __init__(self):\n                self.values = []\n\n            def visit_Constant(self, node):\n                self.values.append(node.value)\n\n        Creates a list of values of all the constant nodes\n        encountered below the given node. To use it:\n\n        cv = ConstantVisitor()\n        cv.visit(node)\n\n        Notes:\n\n        *   generic_visit() will be called for AST nodes for which\n            no visit_XXX method was defined.\n        *   The children of nodes for which a visit_XXX was\n            defined will not be visited - if you need this, call\n            generic_visit() on the node.\n            You can use:\n                NodeVisitor.generic_visit(self, node)\n        *   Modeled after Python's own AST visiting facilities\n            (the ast module of Python 3.0)\n    \"\"\"\n\n    _method_cache = None\n\n    def visit(self, node):\n        \"\"\" Visit a node.\n        \"\"\"\n\n        if self._method_cache is None:\n            self._method_cache = {}\n\n        visitor = self._method_cache.get(node.__class__.__name__, None)\n        if visitor is None:\n            method = 'visit_' + node.__class__.__name__\n            visitor = getattr(self, method, self.generic_visit)\n            self._method_cache[node.__class__.__name__] = visitor\n\n        return visitor(node)\n\n    def generic_visit(self, node):\n        \"\"\" Called if no explicit visitor function exists for a\n            node. Implements preorder visiting of the node.\n        \"\"\"\n        for c in node:\n            self.visit(c)\n\n'''\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/_build_tables.py",
    "content": "#-----------------------------------------------------------------\n# pycparser: _build_tables.py\n#\n# A dummy for generating the lexing/parsing tables and and\n# compiling them into .pyc for faster execution in optimized mode.\n# Also generates AST code from the configuration file.\n# Should be called from the pycparser directory.\n#\n# Eli Bendersky [https://eli.thegreenplace.net/]\n# License: BSD\n#-----------------------------------------------------------------\n\n# Generate c_ast.py\nfrom _ast_gen import ASTCodeGenerator\nast_gen = ASTCodeGenerator('_c_ast.cfg')\nast_gen.generate(open('c_ast.py', 'w'))\n\nimport sys\nsys.path[0:0] = ['.', '..']\nfrom pycparser import c_parser\n\n# Generates the tables\n#\nc_parser.CParser(\n    lex_optimize=True,\n    yacc_debug=False,\n    yacc_optimize=True)\n\n# Load to compile into .pyc\n#\nimport lextab\nimport yacctab\nimport c_ast\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/_c_ast.cfg",
    "content": "#-----------------------------------------------------------------\n# pycparser: _c_ast.cfg\n#\n# Defines the AST Node classes used in pycparser.\n#\n# Each entry is a Node sub-class name, listing the attributes\n# and child nodes of the class:\n#   <name>*     - a child node\n#   <name>**    - a sequence of child nodes\n#   <name>      - an attribute\n#\n# Eli Bendersky [https://eli.thegreenplace.net/]\n# License: BSD\n#-----------------------------------------------------------------\n\n# ArrayDecl is a nested declaration of an array with the given type.\n# dim: the dimension (for example, constant 42)\n# dim_quals: list of dimension qualifiers, to support C99's allowing 'const'\n#            and 'static' within the array dimension in function declarations.\nArrayDecl: [type*, dim*, dim_quals]\n\nArrayRef: [name*, subscript*]\n\n# op: =, +=, /= etc.\n#\nAssignment: [op, lvalue*, rvalue*]\n\nBinaryOp: [op, left*, right*]\n\nBreak: []\n\nCase: [expr*, stmts**]\n\nCast: [to_type*, expr*]\n\n# Compound statement in C99 is a list of block items (declarations or\n# statements).\n#\nCompound: [block_items**]\n\n# Compound literal (anonymous aggregate) for C99.\n# (type-name) {initializer_list}\n# type: the typename\n# init: InitList for the initializer list\n#\nCompoundLiteral: [type*, init*]\n\n# type: int, char, float, etc. see CLexer for constant token types\n#\nConstant: [type, value]\n\nContinue: []\n\n# name: the variable being declared\n# quals: list of qualifiers (const, volatile)\n# funcspec: list function specifiers (i.e. inline in C99)\n# storage: list of storage specifiers (extern, register, etc.)\n# type: declaration type (probably nested with all the modifiers)\n# init: initialization value, or None\n# bitsize: bit field size, or None\n#\nDecl: [name, quals, storage, funcspec, type*, init*, bitsize*]\n\nDeclList: [decls**]\n\nDefault: [stmts**]\n\nDoWhile: [cond*, stmt*]\n\n# Represents the ellipsis (...) parameter in a function\n# declaration\n#\nEllipsisParam: []\n\n# An empty statement (a semicolon ';' on its own)\n#\nEmptyStatement: []\n\n# Enumeration type specifier\n# name: an optional ID\n# values: an EnumeratorList\n#\nEnum: [name, values*]\n\n# A name/value pair for enumeration values\n#\nEnumerator: [name, value*]\n\n# A list of enumerators\n#\nEnumeratorList: [enumerators**]\n\n# A list of expressions separated by the comma operator.\n#\nExprList: [exprs**]\n\n# This is the top of the AST, representing a single C file (a\n# translation unit in K&R jargon). It contains a list of\n# \"external-declaration\"s, which is either declarations (Decl),\n# Typedef or function definitions (FuncDef).\n#\nFileAST: [ext**]\n\n# for (init; cond; next) stmt\n#\nFor: [init*, cond*, next*, stmt*]\n\n# name: Id\n# args: ExprList\n#\nFuncCall: [name*, args*]\n\n# type <decl>(args)\n#\nFuncDecl: [args*, type*]\n\n# Function definition: a declarator for the function name and\n# a body, which is a compound statement.\n# There's an optional list of parameter declarations for old\n# K&R-style definitions\n#\nFuncDef: [decl*, param_decls**, body*]\n\nGoto: [name]\n\nID: [name]\n\n# Holder for types that are a simple identifier (e.g. the built\n# ins void, char etc. and typedef-defined types)\n#\nIdentifierType: [names]\n\nIf: [cond*, iftrue*, iffalse*]\n\n# An initialization list used for compound literals.\n#\nInitList: [exprs**]\n\nLabel: [name, stmt*]\n\n# A named initializer for C99.\n# The name of a NamedInitializer is a sequence of Nodes, because\n# names can be hierarchical and contain constant expressions.\n#\nNamedInitializer: [name**, expr*]\n\n# a list of comma separated function parameter declarations\n#\nParamList: [params**]\n\nPtrDecl: [quals, type*]\n\nReturn: [expr*]\n\n# name: struct tag name\n# decls: declaration of members\n#\nStruct: [name, decls**]\n\n# type: . or ->\n# name.field or name->field\n#\nStructRef: [name*, type, field*]\n\nSwitch: [cond*, stmt*]\n\n# cond ? iftrue : iffalse\n#\nTernaryOp: [cond*, iftrue*, iffalse*]\n\n# A base type declaration\n#\nTypeDecl: [declname, quals, type*]\n\n# A typedef declaration.\n# Very similar to Decl, but without some attributes\n#\nTypedef: [name, quals, storage, type*]\n\nTypename: [name, quals, type*]\n\nUnaryOp: [op, expr*]\n\n# name: union tag name\n# decls: declaration of members\n#\nUnion: [name, decls**]\n\nWhile: [cond*, stmt*]\n\nPragma: [string]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/ast_transforms.py",
    "content": "#------------------------------------------------------------------------------\n# pycparser: ast_transforms.py\n#\n# Some utilities used by the parser to create a friendlier AST.\n#\n# Eli Bendersky [https://eli.thegreenplace.net/]\n# License: BSD\n#------------------------------------------------------------------------------\n\nfrom . import c_ast\n\n\ndef fix_switch_cases(switch_node):\n    \"\"\" The 'case' statements in a 'switch' come out of parsing with one\n        child node, so subsequent statements are just tucked to the parent\n        Compound. Additionally, consecutive (fall-through) case statements\n        come out messy. This is a peculiarity of the C grammar. The following:\n\n            switch (myvar) {\n                case 10:\n                    k = 10;\n                    p = k + 1;\n                    return 10;\n                case 20:\n                case 30:\n                    return 20;\n                default:\n                    break;\n            }\n\n        Creates this tree (pseudo-dump):\n\n            Switch\n                ID: myvar\n                Compound:\n                    Case 10:\n                        k = 10\n                    p = k + 1\n                    return 10\n                    Case 20:\n                        Case 30:\n                            return 20\n                    Default:\n                        break\n\n        The goal of this transform is to fix this mess, turning it into the\n        following:\n\n            Switch\n                ID: myvar\n                Compound:\n                    Case 10:\n                        k = 10\n                        p = k + 1\n                        return 10\n                    Case 20:\n                    Case 30:\n                        return 20\n                    Default:\n                        break\n\n        A fixed AST node is returned. The argument may be modified.\n    \"\"\"\n    assert isinstance(switch_node, c_ast.Switch)\n    if not isinstance(switch_node.stmt, c_ast.Compound):\n        return switch_node\n\n    # The new Compound child for the Switch, which will collect children in the\n    # correct order\n    new_compound = c_ast.Compound([], switch_node.stmt.coord)\n\n    # The last Case/Default node\n    last_case = None\n\n    # Goes over the children of the Compound below the Switch, adding them\n    # either directly below new_compound or below the last Case as appropriate\n    for child in switch_node.stmt.block_items:\n        if isinstance(child, (c_ast.Case, c_ast.Default)):\n            # If it's a Case/Default:\n            # 1. Add it to the Compound and mark as \"last case\"\n            # 2. If its immediate child is also a Case or Default, promote it\n            #    to a sibling.\n            new_compound.block_items.append(child)\n            _extract_nested_case(child, new_compound.block_items)\n            last_case = new_compound.block_items[-1]\n        else:\n            # Other statements are added as children to the last case, if it\n            # exists.\n            if last_case is None:\n                new_compound.block_items.append(child)\n            else:\n                last_case.stmts.append(child)\n\n    switch_node.stmt = new_compound\n    return switch_node\n\n\ndef _extract_nested_case(case_node, stmts_list):\n    \"\"\" Recursively extract consecutive Case statements that are made nested\n        by the parser and add them to the stmts_list.\n    \"\"\"\n    if isinstance(case_node.stmts[0], (c_ast.Case, c_ast.Default)):\n        stmts_list.append(case_node.stmts.pop())\n        _extract_nested_case(stmts_list[-1], stmts_list)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/c_ast.py",
    "content": "#-----------------------------------------------------------------\n# ** ATTENTION **\n# This code was automatically generated from the file:\n# _c_ast.cfg\n#\n# Do not modify it directly. Modify the configuration file and\n# run the generator again.\n# ** ** *** ** **\n#\n# pycparser: c_ast.py\n#\n# AST Node classes.\n#\n# Eli Bendersky [https://eli.thegreenplace.net/]\n# License: BSD\n#-----------------------------------------------------------------\n\n\nimport sys\n\ndef _repr(obj):\n    \"\"\"\n    Get the representation of an object, with dedicated pprint-like format for lists.\n    \"\"\"\n    if isinstance(obj, list):\n        return '[' + (',\\n '.join((_repr(e).replace('\\n', '\\n ') for e in obj))) + '\\n]'\n    else:\n        return repr(obj) \n\nclass Node(object):\n    __slots__ = ()\n    \"\"\" Abstract base class for AST nodes.\n    \"\"\"\n    def __repr__(self):\n        \"\"\" Generates a python representation of the current node\n        \"\"\"\n        result = self.__class__.__name__ + '('\n        \n        indent = ''\n        separator = ''\n        for name in self.__slots__[:-2]:\n            result += separator\n            result += indent\n            result += name + '=' + (_repr(getattr(self, name)).replace('\\n', '\\n  ' + (' ' * (len(name) + len(self.__class__.__name__)))))\n            \n            separator = ','\n            indent = '\\n ' + (' ' * len(self.__class__.__name__))\n        \n        result += indent + ')'\n        \n        return result\n\n    def children(self):\n        \"\"\" A sequence of all children that are Nodes\n        \"\"\"\n        pass\n\n    def show(self, buf=sys.stdout, offset=0, attrnames=False, nodenames=False, showcoord=False, _my_node_name=None):\n        \"\"\" Pretty print the Node and all its attributes and\n            children (recursively) to a buffer.\n\n            buf:\n                Open IO buffer into which the Node is printed.\n\n            offset:\n                Initial offset (amount of leading spaces)\n\n            attrnames:\n                True if you want to see the attribute names in\n                name=value pairs. False to only see the values.\n\n            nodenames:\n                True if you want to see the actual node names\n                within their parents.\n\n            showcoord:\n                Do you want the coordinates of each Node to be\n                displayed.\n        \"\"\"\n        lead = ' ' * offset\n        if nodenames and _my_node_name is not None:\n            buf.write(lead + self.__class__.__name__+ ' <' + _my_node_name + '>: ')\n        else:\n            buf.write(lead + self.__class__.__name__+ ': ')\n\n        if self.attr_names:\n            if attrnames:\n                nvlist = [(n, getattr(self,n)) for n in self.attr_names]\n                attrstr = ', '.join('%s=%s' % nv for nv in nvlist)\n            else:\n                vlist = [getattr(self, n) for n in self.attr_names]\n                attrstr = ', '.join('%s' % v for v in vlist)\n            buf.write(attrstr)\n\n        if showcoord:\n            buf.write(' (at %s)' % self.coord)\n        buf.write('\\n')\n\n        for (child_name, child) in self.children():\n            child.show(\n                buf,\n                offset=offset + 2,\n                attrnames=attrnames,\n                nodenames=nodenames,\n                showcoord=showcoord,\n                _my_node_name=child_name)\n\n\nclass NodeVisitor(object):\n    \"\"\" A base NodeVisitor class for visiting c_ast nodes.\n        Subclass it and define your own visit_XXX methods, where\n        XXX is the class name you want to visit with these\n        methods.\n\n        For example:\n\n        class ConstantVisitor(NodeVisitor):\n            def __init__(self):\n                self.values = []\n\n            def visit_Constant(self, node):\n                self.values.append(node.value)\n\n        Creates a list of values of all the constant nodes\n        encountered below the given node. To use it:\n\n        cv = ConstantVisitor()\n        cv.visit(node)\n\n        Notes:\n\n        *   generic_visit() will be called for AST nodes for which\n            no visit_XXX method was defined.\n        *   The children of nodes for which a visit_XXX was\n            defined will not be visited - if you need this, call\n            generic_visit() on the node.\n            You can use:\n                NodeVisitor.generic_visit(self, node)\n        *   Modeled after Python's own AST visiting facilities\n            (the ast module of Python 3.0)\n    \"\"\"\n\n    _method_cache = None\n\n    def visit(self, node):\n        \"\"\" Visit a node.\n        \"\"\"\n\n        if self._method_cache is None:\n            self._method_cache = {}\n\n        visitor = self._method_cache.get(node.__class__.__name__, None)\n        if visitor is None:\n            method = 'visit_' + node.__class__.__name__\n            visitor = getattr(self, method, self.generic_visit)\n            self._method_cache[node.__class__.__name__] = visitor\n\n        return visitor(node)\n\n    def generic_visit(self, node):\n        \"\"\" Called if no explicit visitor function exists for a\n            node. Implements preorder visiting of the node.\n        \"\"\"\n        for c in node:\n            self.visit(c)\n\nclass ArrayDecl(Node):\n    __slots__ = ('type', 'dim', 'dim_quals', 'coord', '__weakref__')\n    def __init__(self, type, dim, dim_quals, coord=None):\n        self.type = type\n        self.dim = dim\n        self.dim_quals = dim_quals\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.type is not None: nodelist.append((\"type\", self.type))\n        if self.dim is not None: nodelist.append((\"dim\", self.dim))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.type is not None:\n            yield self.type\n        if self.dim is not None:\n            yield self.dim\n\n    attr_names = ('dim_quals', )\n\nclass ArrayRef(Node):\n    __slots__ = ('name', 'subscript', 'coord', '__weakref__')\n    def __init__(self, name, subscript, coord=None):\n        self.name = name\n        self.subscript = subscript\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.name is not None: nodelist.append((\"name\", self.name))\n        if self.subscript is not None: nodelist.append((\"subscript\", self.subscript))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.name is not None:\n            yield self.name\n        if self.subscript is not None:\n            yield self.subscript\n\n    attr_names = ()\n\nclass Assignment(Node):\n    __slots__ = ('op', 'lvalue', 'rvalue', 'coord', '__weakref__')\n    def __init__(self, op, lvalue, rvalue, coord=None):\n        self.op = op\n        self.lvalue = lvalue\n        self.rvalue = rvalue\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.lvalue is not None: nodelist.append((\"lvalue\", self.lvalue))\n        if self.rvalue is not None: nodelist.append((\"rvalue\", self.rvalue))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.lvalue is not None:\n            yield self.lvalue\n        if self.rvalue is not None:\n            yield self.rvalue\n\n    attr_names = ('op', )\n\nclass BinaryOp(Node):\n    __slots__ = ('op', 'left', 'right', 'coord', '__weakref__')\n    def __init__(self, op, left, right, coord=None):\n        self.op = op\n        self.left = left\n        self.right = right\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.left is not None: nodelist.append((\"left\", self.left))\n        if self.right is not None: nodelist.append((\"right\", self.right))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.left is not None:\n            yield self.left\n        if self.right is not None:\n            yield self.right\n\n    attr_names = ('op', )\n\nclass Break(Node):\n    __slots__ = ('coord', '__weakref__')\n    def __init__(self, coord=None):\n        self.coord = coord\n\n    def children(self):\n        return ()\n\n    def __iter__(self):\n        return\n        yield\n\n    attr_names = ()\n\nclass Case(Node):\n    __slots__ = ('expr', 'stmts', 'coord', '__weakref__')\n    def __init__(self, expr, stmts, coord=None):\n        self.expr = expr\n        self.stmts = stmts\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.expr is not None: nodelist.append((\"expr\", self.expr))\n        for i, child in enumerate(self.stmts or []):\n            nodelist.append((\"stmts[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.expr is not None:\n            yield self.expr\n        for child in (self.stmts or []):\n            yield child\n\n    attr_names = ()\n\nclass Cast(Node):\n    __slots__ = ('to_type', 'expr', 'coord', '__weakref__')\n    def __init__(self, to_type, expr, coord=None):\n        self.to_type = to_type\n        self.expr = expr\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.to_type is not None: nodelist.append((\"to_type\", self.to_type))\n        if self.expr is not None: nodelist.append((\"expr\", self.expr))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.to_type is not None:\n            yield self.to_type\n        if self.expr is not None:\n            yield self.expr\n\n    attr_names = ()\n\nclass Compound(Node):\n    __slots__ = ('block_items', 'coord', '__weakref__')\n    def __init__(self, block_items, coord=None):\n        self.block_items = block_items\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        for i, child in enumerate(self.block_items or []):\n            nodelist.append((\"block_items[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        for child in (self.block_items or []):\n            yield child\n\n    attr_names = ()\n\nclass CompoundLiteral(Node):\n    __slots__ = ('type', 'init', 'coord', '__weakref__')\n    def __init__(self, type, init, coord=None):\n        self.type = type\n        self.init = init\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.type is not None: nodelist.append((\"type\", self.type))\n        if self.init is not None: nodelist.append((\"init\", self.init))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.type is not None:\n            yield self.type\n        if self.init is not None:\n            yield self.init\n\n    attr_names = ()\n\nclass Constant(Node):\n    __slots__ = ('type', 'value', 'coord', '__weakref__')\n    def __init__(self, type, value, coord=None):\n        self.type = type\n        self.value = value\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        return tuple(nodelist)\n\n    def __iter__(self):\n        return\n        yield\n\n    attr_names = ('type', 'value', )\n\nclass Continue(Node):\n    __slots__ = ('coord', '__weakref__')\n    def __init__(self, coord=None):\n        self.coord = coord\n\n    def children(self):\n        return ()\n\n    def __iter__(self):\n        return\n        yield\n\n    attr_names = ()\n\nclass Decl(Node):\n    __slots__ = ('name', 'quals', 'storage', 'funcspec', 'type', 'init', 'bitsize', 'coord', '__weakref__')\n    def __init__(self, name, quals, storage, funcspec, type, init, bitsize, coord=None):\n        self.name = name\n        self.quals = quals\n        self.storage = storage\n        self.funcspec = funcspec\n        self.type = type\n        self.init = init\n        self.bitsize = bitsize\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.type is not None: nodelist.append((\"type\", self.type))\n        if self.init is not None: nodelist.append((\"init\", self.init))\n        if self.bitsize is not None: nodelist.append((\"bitsize\", self.bitsize))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.type is not None:\n            yield self.type\n        if self.init is not None:\n            yield self.init\n        if self.bitsize is not None:\n            yield self.bitsize\n\n    attr_names = ('name', 'quals', 'storage', 'funcspec', )\n\nclass DeclList(Node):\n    __slots__ = ('decls', 'coord', '__weakref__')\n    def __init__(self, decls, coord=None):\n        self.decls = decls\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        for i, child in enumerate(self.decls or []):\n            nodelist.append((\"decls[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        for child in (self.decls or []):\n            yield child\n\n    attr_names = ()\n\nclass Default(Node):\n    __slots__ = ('stmts', 'coord', '__weakref__')\n    def __init__(self, stmts, coord=None):\n        self.stmts = stmts\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        for i, child in enumerate(self.stmts or []):\n            nodelist.append((\"stmts[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        for child in (self.stmts or []):\n            yield child\n\n    attr_names = ()\n\nclass DoWhile(Node):\n    __slots__ = ('cond', 'stmt', 'coord', '__weakref__')\n    def __init__(self, cond, stmt, coord=None):\n        self.cond = cond\n        self.stmt = stmt\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.cond is not None: nodelist.append((\"cond\", self.cond))\n        if self.stmt is not None: nodelist.append((\"stmt\", self.stmt))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.cond is not None:\n            yield self.cond\n        if self.stmt is not None:\n            yield self.stmt\n\n    attr_names = ()\n\nclass EllipsisParam(Node):\n    __slots__ = ('coord', '__weakref__')\n    def __init__(self, coord=None):\n        self.coord = coord\n\n    def children(self):\n        return ()\n\n    def __iter__(self):\n        return\n        yield\n\n    attr_names = ()\n\nclass EmptyStatement(Node):\n    __slots__ = ('coord', '__weakref__')\n    def __init__(self, coord=None):\n        self.coord = coord\n\n    def children(self):\n        return ()\n\n    def __iter__(self):\n        return\n        yield\n\n    attr_names = ()\n\nclass Enum(Node):\n    __slots__ = ('name', 'values', 'coord', '__weakref__')\n    def __init__(self, name, values, coord=None):\n        self.name = name\n        self.values = values\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.values is not None: nodelist.append((\"values\", self.values))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.values is not None:\n            yield self.values\n\n    attr_names = ('name', )\n\nclass Enumerator(Node):\n    __slots__ = ('name', 'value', 'coord', '__weakref__')\n    def __init__(self, name, value, coord=None):\n        self.name = name\n        self.value = value\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.value is not None: nodelist.append((\"value\", self.value))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.value is not None:\n            yield self.value\n\n    attr_names = ('name', )\n\nclass EnumeratorList(Node):\n    __slots__ = ('enumerators', 'coord', '__weakref__')\n    def __init__(self, enumerators, coord=None):\n        self.enumerators = enumerators\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        for i, child in enumerate(self.enumerators or []):\n            nodelist.append((\"enumerators[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        for child in (self.enumerators or []):\n            yield child\n\n    attr_names = ()\n\nclass ExprList(Node):\n    __slots__ = ('exprs', 'coord', '__weakref__')\n    def __init__(self, exprs, coord=None):\n        self.exprs = exprs\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        for i, child in enumerate(self.exprs or []):\n            nodelist.append((\"exprs[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        for child in (self.exprs or []):\n            yield child\n\n    attr_names = ()\n\nclass FileAST(Node):\n    __slots__ = ('ext', 'coord', '__weakref__')\n    def __init__(self, ext, coord=None):\n        self.ext = ext\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        for i, child in enumerate(self.ext or []):\n            nodelist.append((\"ext[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        for child in (self.ext or []):\n            yield child\n\n    attr_names = ()\n\nclass For(Node):\n    __slots__ = ('init', 'cond', 'next', 'stmt', 'coord', '__weakref__')\n    def __init__(self, init, cond, next, stmt, coord=None):\n        self.init = init\n        self.cond = cond\n        self.next = next\n        self.stmt = stmt\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.init is not None: nodelist.append((\"init\", self.init))\n        if self.cond is not None: nodelist.append((\"cond\", self.cond))\n        if self.next is not None: nodelist.append((\"next\", self.next))\n        if self.stmt is not None: nodelist.append((\"stmt\", self.stmt))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.init is not None:\n            yield self.init\n        if self.cond is not None:\n            yield self.cond\n        if self.next is not None:\n            yield self.next\n        if self.stmt is not None:\n            yield self.stmt\n\n    attr_names = ()\n\nclass FuncCall(Node):\n    __slots__ = ('name', 'args', 'coord', '__weakref__')\n    def __init__(self, name, args, coord=None):\n        self.name = name\n        self.args = args\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.name is not None: nodelist.append((\"name\", self.name))\n        if self.args is not None: nodelist.append((\"args\", self.args))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.name is not None:\n            yield self.name\n        if self.args is not None:\n            yield self.args\n\n    attr_names = ()\n\nclass FuncDecl(Node):\n    __slots__ = ('args', 'type', 'coord', '__weakref__')\n    def __init__(self, args, type, coord=None):\n        self.args = args\n        self.type = type\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.args is not None: nodelist.append((\"args\", self.args))\n        if self.type is not None: nodelist.append((\"type\", self.type))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.args is not None:\n            yield self.args\n        if self.type is not None:\n            yield self.type\n\n    attr_names = ()\n\nclass FuncDef(Node):\n    __slots__ = ('decl', 'param_decls', 'body', 'coord', '__weakref__')\n    def __init__(self, decl, param_decls, body, coord=None):\n        self.decl = decl\n        self.param_decls = param_decls\n        self.body = body\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.decl is not None: nodelist.append((\"decl\", self.decl))\n        if self.body is not None: nodelist.append((\"body\", self.body))\n        for i, child in enumerate(self.param_decls or []):\n            nodelist.append((\"param_decls[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.decl is not None:\n            yield self.decl\n        if self.body is not None:\n            yield self.body\n        for child in (self.param_decls or []):\n            yield child\n\n    attr_names = ()\n\nclass Goto(Node):\n    __slots__ = ('name', 'coord', '__weakref__')\n    def __init__(self, name, coord=None):\n        self.name = name\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        return tuple(nodelist)\n\n    def __iter__(self):\n        return\n        yield\n\n    attr_names = ('name', )\n\nclass ID(Node):\n    __slots__ = ('name', 'coord', '__weakref__')\n    def __init__(self, name, coord=None):\n        self.name = name\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        return tuple(nodelist)\n\n    def __iter__(self):\n        return\n        yield\n\n    attr_names = ('name', )\n\nclass IdentifierType(Node):\n    __slots__ = ('names', 'coord', '__weakref__')\n    def __init__(self, names, coord=None):\n        self.names = names\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        return tuple(nodelist)\n\n    def __iter__(self):\n        return\n        yield\n\n    attr_names = ('names', )\n\nclass If(Node):\n    __slots__ = ('cond', 'iftrue', 'iffalse', 'coord', '__weakref__')\n    def __init__(self, cond, iftrue, iffalse, coord=None):\n        self.cond = cond\n        self.iftrue = iftrue\n        self.iffalse = iffalse\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.cond is not None: nodelist.append((\"cond\", self.cond))\n        if self.iftrue is not None: nodelist.append((\"iftrue\", self.iftrue))\n        if self.iffalse is not None: nodelist.append((\"iffalse\", self.iffalse))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.cond is not None:\n            yield self.cond\n        if self.iftrue is not None:\n            yield self.iftrue\n        if self.iffalse is not None:\n            yield self.iffalse\n\n    attr_names = ()\n\nclass InitList(Node):\n    __slots__ = ('exprs', 'coord', '__weakref__')\n    def __init__(self, exprs, coord=None):\n        self.exprs = exprs\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        for i, child in enumerate(self.exprs or []):\n            nodelist.append((\"exprs[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        for child in (self.exprs or []):\n            yield child\n\n    attr_names = ()\n\nclass Label(Node):\n    __slots__ = ('name', 'stmt', 'coord', '__weakref__')\n    def __init__(self, name, stmt, coord=None):\n        self.name = name\n        self.stmt = stmt\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.stmt is not None: nodelist.append((\"stmt\", self.stmt))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.stmt is not None:\n            yield self.stmt\n\n    attr_names = ('name', )\n\nclass NamedInitializer(Node):\n    __slots__ = ('name', 'expr', 'coord', '__weakref__')\n    def __init__(self, name, expr, coord=None):\n        self.name = name\n        self.expr = expr\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.expr is not None: nodelist.append((\"expr\", self.expr))\n        for i, child in enumerate(self.name or []):\n            nodelist.append((\"name[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.expr is not None:\n            yield self.expr\n        for child in (self.name or []):\n            yield child\n\n    attr_names = ()\n\nclass ParamList(Node):\n    __slots__ = ('params', 'coord', '__weakref__')\n    def __init__(self, params, coord=None):\n        self.params = params\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        for i, child in enumerate(self.params or []):\n            nodelist.append((\"params[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        for child in (self.params or []):\n            yield child\n\n    attr_names = ()\n\nclass PtrDecl(Node):\n    __slots__ = ('quals', 'type', 'coord', '__weakref__')\n    def __init__(self, quals, type, coord=None):\n        self.quals = quals\n        self.type = type\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.type is not None: nodelist.append((\"type\", self.type))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.type is not None:\n            yield self.type\n\n    attr_names = ('quals', )\n\nclass Return(Node):\n    __slots__ = ('expr', 'coord', '__weakref__')\n    def __init__(self, expr, coord=None):\n        self.expr = expr\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.expr is not None: nodelist.append((\"expr\", self.expr))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.expr is not None:\n            yield self.expr\n\n    attr_names = ()\n\nclass Struct(Node):\n    __slots__ = ('name', 'decls', 'coord', '__weakref__')\n    def __init__(self, name, decls, coord=None):\n        self.name = name\n        self.decls = decls\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        for i, child in enumerate(self.decls or []):\n            nodelist.append((\"decls[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        for child in (self.decls or []):\n            yield child\n\n    attr_names = ('name', )\n\nclass StructRef(Node):\n    __slots__ = ('name', 'type', 'field', 'coord', '__weakref__')\n    def __init__(self, name, type, field, coord=None):\n        self.name = name\n        self.type = type\n        self.field = field\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.name is not None: nodelist.append((\"name\", self.name))\n        if self.field is not None: nodelist.append((\"field\", self.field))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.name is not None:\n            yield self.name\n        if self.field is not None:\n            yield self.field\n\n    attr_names = ('type', )\n\nclass Switch(Node):\n    __slots__ = ('cond', 'stmt', 'coord', '__weakref__')\n    def __init__(self, cond, stmt, coord=None):\n        self.cond = cond\n        self.stmt = stmt\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.cond is not None: nodelist.append((\"cond\", self.cond))\n        if self.stmt is not None: nodelist.append((\"stmt\", self.stmt))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.cond is not None:\n            yield self.cond\n        if self.stmt is not None:\n            yield self.stmt\n\n    attr_names = ()\n\nclass TernaryOp(Node):\n    __slots__ = ('cond', 'iftrue', 'iffalse', 'coord', '__weakref__')\n    def __init__(self, cond, iftrue, iffalse, coord=None):\n        self.cond = cond\n        self.iftrue = iftrue\n        self.iffalse = iffalse\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.cond is not None: nodelist.append((\"cond\", self.cond))\n        if self.iftrue is not None: nodelist.append((\"iftrue\", self.iftrue))\n        if self.iffalse is not None: nodelist.append((\"iffalse\", self.iffalse))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.cond is not None:\n            yield self.cond\n        if self.iftrue is not None:\n            yield self.iftrue\n        if self.iffalse is not None:\n            yield self.iffalse\n\n    attr_names = ()\n\nclass TypeDecl(Node):\n    __slots__ = ('declname', 'quals', 'type', 'coord', '__weakref__')\n    def __init__(self, declname, quals, type, coord=None):\n        self.declname = declname\n        self.quals = quals\n        self.type = type\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.type is not None: nodelist.append((\"type\", self.type))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.type is not None:\n            yield self.type\n\n    attr_names = ('declname', 'quals', )\n\nclass Typedef(Node):\n    __slots__ = ('name', 'quals', 'storage', 'type', 'coord', '__weakref__')\n    def __init__(self, name, quals, storage, type, coord=None):\n        self.name = name\n        self.quals = quals\n        self.storage = storage\n        self.type = type\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.type is not None: nodelist.append((\"type\", self.type))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.type is not None:\n            yield self.type\n\n    attr_names = ('name', 'quals', 'storage', )\n\nclass Typename(Node):\n    __slots__ = ('name', 'quals', 'type', 'coord', '__weakref__')\n    def __init__(self, name, quals, type, coord=None):\n        self.name = name\n        self.quals = quals\n        self.type = type\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.type is not None: nodelist.append((\"type\", self.type))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.type is not None:\n            yield self.type\n\n    attr_names = ('name', 'quals', )\n\nclass UnaryOp(Node):\n    __slots__ = ('op', 'expr', 'coord', '__weakref__')\n    def __init__(self, op, expr, coord=None):\n        self.op = op\n        self.expr = expr\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.expr is not None: nodelist.append((\"expr\", self.expr))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.expr is not None:\n            yield self.expr\n\n    attr_names = ('op', )\n\nclass Union(Node):\n    __slots__ = ('name', 'decls', 'coord', '__weakref__')\n    def __init__(self, name, decls, coord=None):\n        self.name = name\n        self.decls = decls\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        for i, child in enumerate(self.decls or []):\n            nodelist.append((\"decls[%d]\" % i, child))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        for child in (self.decls or []):\n            yield child\n\n    attr_names = ('name', )\n\nclass While(Node):\n    __slots__ = ('cond', 'stmt', 'coord', '__weakref__')\n    def __init__(self, cond, stmt, coord=None):\n        self.cond = cond\n        self.stmt = stmt\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        if self.cond is not None: nodelist.append((\"cond\", self.cond))\n        if self.stmt is not None: nodelist.append((\"stmt\", self.stmt))\n        return tuple(nodelist)\n\n    def __iter__(self):\n        if self.cond is not None:\n            yield self.cond\n        if self.stmt is not None:\n            yield self.stmt\n\n    attr_names = ()\n\nclass Pragma(Node):\n    __slots__ = ('string', 'coord', '__weakref__')\n    def __init__(self, string, coord=None):\n        self.string = string\n        self.coord = coord\n\n    def children(self):\n        nodelist = []\n        return tuple(nodelist)\n\n    def __iter__(self):\n        return\n        yield\n\n    attr_names = ('string', )\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/c_generator.py",
    "content": "#------------------------------------------------------------------------------\n# pycparser: c_generator.py\n#\n# C code generator from pycparser AST nodes.\n#\n# Eli Bendersky [https://eli.thegreenplace.net/]\n# License: BSD\n#------------------------------------------------------------------------------\nfrom . import c_ast\n\n\nclass CGenerator(object):\n    \"\"\" Uses the same visitor pattern as c_ast.NodeVisitor, but modified to\n        return a value from each visit method, using string accumulation in\n        generic_visit.\n    \"\"\"\n    def __init__(self):\n        # Statements start with indentation of self.indent_level spaces, using\n        # the _make_indent method\n        #\n        self.indent_level = 0\n\n    def _make_indent(self):\n        return ' ' * self.indent_level\n\n    def visit(self, node):\n        method = 'visit_' + node.__class__.__name__\n        return getattr(self, method, self.generic_visit)(node)\n\n    def generic_visit(self, node):\n        #~ print('generic:', type(node))\n        if node is None:\n            return ''\n        else:\n            return ''.join(self.visit(c) for c_name, c in node.children())\n\n    def visit_Constant(self, n):\n        return n.value\n\n    def visit_ID(self, n):\n        return n.name\n\n    def visit_Pragma(self, n):\n        ret = '#pragma'\n        if n.string:\n            ret += ' ' + n.string\n        return ret\n\n    def visit_ArrayRef(self, n):\n        arrref = self._parenthesize_unless_simple(n.name)\n        return arrref + '[' + self.visit(n.subscript) + ']'\n\n    def visit_StructRef(self, n):\n        sref = self._parenthesize_unless_simple(n.name)\n        return sref + n.type + self.visit(n.field)\n\n    def visit_FuncCall(self, n):\n        fref = self._parenthesize_unless_simple(n.name)\n        return fref + '(' + self.visit(n.args) + ')'\n\n    def visit_UnaryOp(self, n):\n        operand = self._parenthesize_unless_simple(n.expr)\n        if n.op == 'p++':\n            return '%s++' % operand\n        elif n.op == 'p--':\n            return '%s--' % operand\n        elif n.op == 'sizeof':\n            # Always parenthesize the argument of sizeof since it can be\n            # a name.\n            return 'sizeof(%s)' % self.visit(n.expr)\n        else:\n            return '%s%s' % (n.op, operand)\n\n    def visit_BinaryOp(self, n):\n        lval_str = self._parenthesize_if(n.left,\n                            lambda d: not self._is_simple_node(d))\n        rval_str = self._parenthesize_if(n.right,\n                            lambda d: not self._is_simple_node(d))\n        return '%s %s %s' % (lval_str, n.op, rval_str)\n\n    def visit_Assignment(self, n):\n        rval_str = self._parenthesize_if(\n                            n.rvalue,\n                            lambda n: isinstance(n, c_ast.Assignment))\n        return '%s %s %s' % (self.visit(n.lvalue), n.op, rval_str)\n\n    def visit_IdentifierType(self, n):\n        return ' '.join(n.names)\n\n    def _visit_expr(self, n):\n        if isinstance(n, c_ast.InitList):\n            return '{' + self.visit(n) + '}'\n        elif isinstance(n, c_ast.ExprList):\n            return '(' + self.visit(n) + ')'\n        else:\n            return self.visit(n)\n\n    def visit_Decl(self, n, no_type=False):\n        # no_type is used when a Decl is part of a DeclList, where the type is\n        # explicitly only for the first declaration in a list.\n        #\n        s = n.name if no_type else self._generate_decl(n)\n        if n.bitsize: s += ' : ' + self.visit(n.bitsize)\n        if n.init:\n            s += ' = ' + self._visit_expr(n.init)\n        return s\n\n    def visit_DeclList(self, n):\n        s = self.visit(n.decls[0])\n        if len(n.decls) > 1:\n            s += ', ' + ', '.join(self.visit_Decl(decl, no_type=True)\n                                    for decl in n.decls[1:])\n        return s\n\n    def visit_Typedef(self, n):\n        s = ''\n        if n.storage: s += ' '.join(n.storage) + ' '\n        s += self._generate_type(n.type)\n        return s\n\n    def visit_Cast(self, n):\n        s = '(' + self._generate_type(n.to_type) + ')'\n        return s + ' ' + self._parenthesize_unless_simple(n.expr)\n\n    def visit_ExprList(self, n):\n        visited_subexprs = []\n        for expr in n.exprs:\n            visited_subexprs.append(self._visit_expr(expr))\n        return ', '.join(visited_subexprs)\n\n    def visit_InitList(self, n):\n        visited_subexprs = []\n        for expr in n.exprs:\n            visited_subexprs.append(self._visit_expr(expr))\n        return ', '.join(visited_subexprs)\n\n    def visit_Enum(self, n):\n        return self._generate_struct_union_enum(n, name='enum')\n\n    def visit_Enumerator(self, n):\n        if not n.value:\n            return '{indent}{name},\\n'.format(\n                indent=self._make_indent(),\n                name=n.name,\n            )\n        else:\n            return '{indent}{name} = {value},\\n'.format(\n                indent=self._make_indent(),\n                name=n.name,\n                value=self.visit(n.value),\n            )\n\n    def visit_FuncDef(self, n):\n        decl = self.visit(n.decl)\n        self.indent_level = 0\n        body = self.visit(n.body)\n        if n.param_decls:\n            knrdecls = ';\\n'.join(self.visit(p) for p in n.param_decls)\n            return decl + '\\n' + knrdecls + ';\\n' + body + '\\n'\n        else:\n            return decl + '\\n' + body + '\\n'\n\n    def visit_FileAST(self, n):\n        s = ''\n        for ext in n.ext:\n            if isinstance(ext, c_ast.FuncDef):\n                s += self.visit(ext)\n            elif isinstance(ext, c_ast.Pragma):\n                s += self.visit(ext) + '\\n'\n            else:\n                s += self.visit(ext) + ';\\n'\n        return s\n\n    def visit_Compound(self, n):\n        s = self._make_indent() + '{\\n'\n        self.indent_level += 2\n        if n.block_items:\n            s += ''.join(self._generate_stmt(stmt) for stmt in n.block_items)\n        self.indent_level -= 2\n        s += self._make_indent() + '}\\n'\n        return s\n\n    def visit_CompoundLiteral(self, n):\n        return '(' + self.visit(n.type) + '){' + self.visit(n.init) + '}'\n\n\n    def visit_EmptyStatement(self, n):\n        return ';'\n\n    def visit_ParamList(self, n):\n        return ', '.join(self.visit(param) for param in n.params)\n\n    def visit_Return(self, n):\n        s = 'return'\n        if n.expr: s += ' ' + self.visit(n.expr)\n        return s + ';'\n\n    def visit_Break(self, n):\n        return 'break;'\n\n    def visit_Continue(self, n):\n        return 'continue;'\n\n    def visit_TernaryOp(self, n):\n        s  = '(' + self._visit_expr(n.cond) + ') ? '\n        s += '(' + self._visit_expr(n.iftrue) + ') : '\n        s += '(' + self._visit_expr(n.iffalse) + ')'\n        return s\n\n    def visit_If(self, n):\n        s = 'if ('\n        if n.cond: s += self.visit(n.cond)\n        s += ')\\n'\n        s += self._generate_stmt(n.iftrue, add_indent=True)\n        if n.iffalse:\n            s += self._make_indent() + 'else\\n'\n            s += self._generate_stmt(n.iffalse, add_indent=True)\n        return s\n\n    def visit_For(self, n):\n        s = 'for ('\n        if n.init: s += self.visit(n.init)\n        s += ';'\n        if n.cond: s += ' ' + self.visit(n.cond)\n        s += ';'\n        if n.next: s += ' ' + self.visit(n.next)\n        s += ')\\n'\n        s += self._generate_stmt(n.stmt, add_indent=True)\n        return s\n\n    def visit_While(self, n):\n        s = 'while ('\n        if n.cond: s += self.visit(n.cond)\n        s += ')\\n'\n        s += self._generate_stmt(n.stmt, add_indent=True)\n        return s\n\n    def visit_DoWhile(self, n):\n        s = 'do\\n'\n        s += self._generate_stmt(n.stmt, add_indent=True)\n        s += self._make_indent() + 'while ('\n        if n.cond: s += self.visit(n.cond)\n        s += ');'\n        return s\n\n    def visit_Switch(self, n):\n        s = 'switch (' + self.visit(n.cond) + ')\\n'\n        s += self._generate_stmt(n.stmt, add_indent=True)\n        return s\n\n    def visit_Case(self, n):\n        s = 'case ' + self.visit(n.expr) + ':\\n'\n        for stmt in n.stmts:\n            s += self._generate_stmt(stmt, add_indent=True)\n        return s\n\n    def visit_Default(self, n):\n        s = 'default:\\n'\n        for stmt in n.stmts:\n            s += self._generate_stmt(stmt, add_indent=True)\n        return s\n\n    def visit_Label(self, n):\n        return n.name + ':\\n' + self._generate_stmt(n.stmt)\n\n    def visit_Goto(self, n):\n        return 'goto ' + n.name + ';'\n\n    def visit_EllipsisParam(self, n):\n        return '...'\n\n    def visit_Struct(self, n):\n        return self._generate_struct_union_enum(n, 'struct')\n\n    def visit_Typename(self, n):\n        return self._generate_type(n.type)\n\n    def visit_Union(self, n):\n        return self._generate_struct_union_enum(n, 'union')\n\n    def visit_NamedInitializer(self, n):\n        s = ''\n        for name in n.name:\n            if isinstance(name, c_ast.ID):\n                s += '.' + name.name\n            else:\n                s += '[' + self.visit(name) + ']'\n        s += ' = ' + self._visit_expr(n.expr)\n        return s\n\n    def visit_FuncDecl(self, n):\n        return self._generate_type(n)\n\n    def _generate_struct_union_enum(self, n, name):\n        \"\"\" Generates code for structs, unions, and enums. name should be\n            'struct', 'union', or 'enum'.\n        \"\"\"\n        if name in ('struct', 'union'):\n            members = n.decls\n            body_function = self._generate_struct_union_body\n        else:\n            assert name == 'enum'\n            members = None if n.values is None else n.values.enumerators\n            body_function = self._generate_enum_body\n        s = name + ' ' + (n.name or '')\n        if members is not None:\n            # None means no members\n            # Empty sequence means an empty list of members\n            s += '\\n'\n            s += self._make_indent()\n            self.indent_level += 2\n            s += '{\\n'\n            s += body_function(members)\n            self.indent_level -= 2\n            s += self._make_indent() + '}'\n        return s\n\n    def _generate_struct_union_body(self, members):\n        return ''.join(self._generate_stmt(decl) for decl in members)\n\n    def _generate_enum_body(self, members):\n        # `[:-2] + '\\n'` removes the final `,` from the enumerator list\n        return ''.join(self.visit(value) for value in members)[:-2] + '\\n'\n\n    def _generate_stmt(self, n, add_indent=False):\n        \"\"\" Generation from a statement node. This method exists as a wrapper\n            for individual visit_* methods to handle different treatment of\n            some statements in this context.\n        \"\"\"\n        typ = type(n)\n        if add_indent: self.indent_level += 2\n        indent = self._make_indent()\n        if add_indent: self.indent_level -= 2\n\n        if typ in (\n                c_ast.Decl, c_ast.Assignment, c_ast.Cast, c_ast.UnaryOp,\n                c_ast.BinaryOp, c_ast.TernaryOp, c_ast.FuncCall, c_ast.ArrayRef,\n                c_ast.StructRef, c_ast.Constant, c_ast.ID, c_ast.Typedef,\n                c_ast.ExprList):\n            # These can also appear in an expression context so no semicolon\n            # is added to them automatically\n            #\n            return indent + self.visit(n) + ';\\n'\n        elif typ in (c_ast.Compound,):\n            # No extra indentation required before the opening brace of a\n            # compound - because it consists of multiple lines it has to\n            # compute its own indentation.\n            #\n            return self.visit(n)\n        else:\n            return indent + self.visit(n) + '\\n'\n\n    def _generate_decl(self, n):\n        \"\"\" Generation from a Decl node.\n        \"\"\"\n        s = ''\n        if n.funcspec: s = ' '.join(n.funcspec) + ' '\n        if n.storage: s += ' '.join(n.storage) + ' '\n        s += self._generate_type(n.type)\n        return s\n\n    def _generate_type(self, n, modifiers=[]):\n        \"\"\" Recursive generation from a type node. n is the type node.\n            modifiers collects the PtrDecl, ArrayDecl and FuncDecl modifiers\n            encountered on the way down to a TypeDecl, to allow proper\n            generation from it.\n        \"\"\"\n        typ = type(n)\n        #~ print(n, modifiers)\n\n        if typ == c_ast.TypeDecl:\n            s = ''\n            if n.quals: s += ' '.join(n.quals) + ' '\n            s += self.visit(n.type)\n\n            nstr = n.declname if n.declname else ''\n            # Resolve modifiers.\n            # Wrap in parens to distinguish pointer to array and pointer to\n            # function syntax.\n            #\n            for i, modifier in enumerate(modifiers):\n                if isinstance(modifier, c_ast.ArrayDecl):\n                    if (i != 0 and isinstance(modifiers[i - 1], c_ast.PtrDecl)):\n                        nstr = '(' + nstr + ')'\n                    nstr += '[' + self.visit(modifier.dim) + ']'\n                elif isinstance(modifier, c_ast.FuncDecl):\n                    if (i != 0 and isinstance(modifiers[i - 1], c_ast.PtrDecl)):\n                        nstr = '(' + nstr + ')'\n                    nstr += '(' + self.visit(modifier.args) + ')'\n                elif isinstance(modifier, c_ast.PtrDecl):\n                    if modifier.quals:\n                        nstr = '* %s %s' % (' '.join(modifier.quals), nstr)\n                    else:\n                        nstr = '*' + nstr\n            if nstr: s += ' ' + nstr\n            return s\n        elif typ == c_ast.Decl:\n            return self._generate_decl(n.type)\n        elif typ == c_ast.Typename:\n            return self._generate_type(n.type)\n        elif typ == c_ast.IdentifierType:\n            return ' '.join(n.names) + ' '\n        elif typ in (c_ast.ArrayDecl, c_ast.PtrDecl, c_ast.FuncDecl):\n            return self._generate_type(n.type, modifiers + [n])\n        else:\n            return self.visit(n)\n\n    def _parenthesize_if(self, n, condition):\n        \"\"\" Visits 'n' and returns its string representation, parenthesized\n            if the condition function applied to the node returns True.\n        \"\"\"\n        s = self._visit_expr(n)\n        if condition(n):\n            return '(' + s + ')'\n        else:\n            return s\n\n    def _parenthesize_unless_simple(self, n):\n        \"\"\" Common use case for _parenthesize_if\n        \"\"\"\n        return self._parenthesize_if(n, lambda d: not self._is_simple_node(d))\n\n    def _is_simple_node(self, n):\n        \"\"\" Returns True for nodes that are \"simple\" - i.e. nodes that always\n            have higher precedence than operators.\n        \"\"\"\n        return isinstance(n, (c_ast.Constant, c_ast.ID, c_ast.ArrayRef,\n                              c_ast.StructRef, c_ast.FuncCall))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/c_lexer.py",
    "content": "#------------------------------------------------------------------------------\n# pycparser: c_lexer.py\n#\n# CLexer class: lexer for the C language\n#\n# Eli Bendersky [https://eli.thegreenplace.net/]\n# License: BSD\n#------------------------------------------------------------------------------\nimport re\nimport sys\n\nfrom .ply import lex\nfrom .ply.lex import TOKEN\n\n\nclass CLexer(object):\n    \"\"\" A lexer for the C language. After building it, set the\n        input text with input(), and call token() to get new\n        tokens.\n\n        The public attribute filename can be set to an initial\n        filaneme, but the lexer will update it upon #line\n        directives.\n    \"\"\"\n    def __init__(self, error_func, on_lbrace_func, on_rbrace_func,\n                 type_lookup_func):\n        \"\"\" Create a new Lexer.\n\n            error_func:\n                An error function. Will be called with an error\n                message, line and column as arguments, in case of\n                an error during lexing.\n\n            on_lbrace_func, on_rbrace_func:\n                Called when an LBRACE or RBRACE is encountered\n                (likely to push/pop type_lookup_func's scope)\n\n            type_lookup_func:\n                A type lookup function. Given a string, it must\n                return True IFF this string is a name of a type\n                that was defined with a typedef earlier.\n        \"\"\"\n        self.error_func = error_func\n        self.on_lbrace_func = on_lbrace_func\n        self.on_rbrace_func = on_rbrace_func\n        self.type_lookup_func = type_lookup_func\n        self.filename = ''\n\n        # Keeps track of the last token returned from self.token()\n        self.last_token = None\n\n        # Allow either \"# line\" or \"# <num>\" to support GCC's\n        # cpp output\n        #\n        self.line_pattern = re.compile(r'([ \\t]*line\\W)|([ \\t]*\\d+)')\n        self.pragma_pattern = re.compile(r'[ \\t]*pragma\\W')\n\n    def build(self, **kwargs):\n        \"\"\" Builds the lexer from the specification. Must be\n            called after the lexer object is created.\n\n            This method exists separately, because the PLY\n            manual warns against calling lex.lex inside\n            __init__\n        \"\"\"\n        self.lexer = lex.lex(object=self, **kwargs)\n\n    def reset_lineno(self):\n        \"\"\" Resets the internal line number counter of the lexer.\n        \"\"\"\n        self.lexer.lineno = 1\n\n    def input(self, text):\n        self.lexer.input(text)\n\n    def token(self):\n        self.last_token = self.lexer.token()\n        return self.last_token\n\n    def find_tok_column(self, token):\n        \"\"\" Find the column of the token in its line.\n        \"\"\"\n        last_cr = self.lexer.lexdata.rfind('\\n', 0, token.lexpos)\n        return token.lexpos - last_cr\n\n    ######################--   PRIVATE   --######################\n\n    ##\n    ## Internal auxiliary methods\n    ##\n    def _error(self, msg, token):\n        location = self._make_tok_location(token)\n        self.error_func(msg, location[0], location[1])\n        self.lexer.skip(1)\n\n    def _make_tok_location(self, token):\n        return (token.lineno, self.find_tok_column(token))\n\n    ##\n    ## Reserved keywords\n    ##\n    keywords = (\n        '_BOOL', '_COMPLEX', 'AUTO', 'BREAK', 'CASE', 'CHAR', 'CONST',\n        'CONTINUE', 'DEFAULT', 'DO', 'DOUBLE', 'ELSE', 'ENUM', 'EXTERN',\n        'FLOAT', 'FOR', 'GOTO', 'IF', 'INLINE', 'INT', 'LONG',\n        'REGISTER', 'OFFSETOF',\n        'RESTRICT', 'RETURN', 'SHORT', 'SIGNED', 'SIZEOF', 'STATIC', 'STRUCT',\n        'SWITCH', 'TYPEDEF', 'UNION', 'UNSIGNED', 'VOID',\n        'VOLATILE', 'WHILE', '__INT128',\n    )\n\n    keyword_map = {}\n    for keyword in keywords:\n        if keyword == '_BOOL':\n            keyword_map['_Bool'] = keyword\n        elif keyword == '_COMPLEX':\n            keyword_map['_Complex'] = keyword\n        else:\n            keyword_map[keyword.lower()] = keyword\n\n    ##\n    ## All the tokens recognized by the lexer\n    ##\n    tokens = keywords + (\n        # Identifiers\n        'ID',\n\n        # Type identifiers (identifiers previously defined as\n        # types with typedef)\n        'TYPEID',\n\n        # constants\n        'INT_CONST_DEC', 'INT_CONST_OCT', 'INT_CONST_HEX', 'INT_CONST_BIN',\n        'FLOAT_CONST', 'HEX_FLOAT_CONST',\n        'CHAR_CONST',\n        'WCHAR_CONST',\n\n        # String literals\n        'STRING_LITERAL',\n        'WSTRING_LITERAL',\n\n        # Operators\n        'PLUS', 'MINUS', 'TIMES', 'DIVIDE', 'MOD',\n        'OR', 'AND', 'NOT', 'XOR', 'LSHIFT', 'RSHIFT',\n        'LOR', 'LAND', 'LNOT',\n        'LT', 'LE', 'GT', 'GE', 'EQ', 'NE',\n\n        # Assignment\n        'EQUALS', 'TIMESEQUAL', 'DIVEQUAL', 'MODEQUAL',\n        'PLUSEQUAL', 'MINUSEQUAL',\n        'LSHIFTEQUAL','RSHIFTEQUAL', 'ANDEQUAL', 'XOREQUAL',\n        'OREQUAL',\n\n        # Increment/decrement\n        'PLUSPLUS', 'MINUSMINUS',\n\n        # Structure dereference (->)\n        'ARROW',\n\n        # Conditional operator (?)\n        'CONDOP',\n\n        # Delimeters\n        'LPAREN', 'RPAREN',         # ( )\n        'LBRACKET', 'RBRACKET',     # [ ]\n        'LBRACE', 'RBRACE',         # { }\n        'COMMA', 'PERIOD',          # . ,\n        'SEMI', 'COLON',            # ; :\n\n        # Ellipsis (...)\n        'ELLIPSIS',\n\n        # pre-processor\n        'PPHASH',       # '#'\n        'PPPRAGMA',     # 'pragma'\n        'PPPRAGMASTR',\n    )\n\n    ##\n    ## Regexes for use in tokens\n    ##\n    ##\n\n    # valid C identifiers (K&R2: A.2.3), plus '$' (supported by some compilers)\n    identifier = r'[a-zA-Z_$][0-9a-zA-Z_$]*'\n\n    hex_prefix = '0[xX]'\n    hex_digits = '[0-9a-fA-F]+'\n    bin_prefix = '0[bB]'\n    bin_digits = '[01]+'\n\n    # integer constants (K&R2: A.2.5.1)\n    integer_suffix_opt = r'(([uU]ll)|([uU]LL)|(ll[uU]?)|(LL[uU]?)|([uU][lL])|([lL][uU]?)|[uU])?'\n    decimal_constant = '(0'+integer_suffix_opt+')|([1-9][0-9]*'+integer_suffix_opt+')'\n    octal_constant = '0[0-7]*'+integer_suffix_opt\n    hex_constant = hex_prefix+hex_digits+integer_suffix_opt\n    bin_constant = bin_prefix+bin_digits+integer_suffix_opt\n\n    bad_octal_constant = '0[0-7]*[89]'\n\n    # character constants (K&R2: A.2.5.2)\n    # Note: a-zA-Z and '.-~^_!=&;,' are allowed as escape chars to support #line\n    # directives with Windows paths as filenames (..\\..\\dir\\file)\n    # For the same reason, decimal_escape allows all digit sequences. We want to\n    # parse all correct code, even if it means to sometimes parse incorrect\n    # code.\n    #\n    simple_escape = r\"\"\"([a-zA-Z._~!=&\\^\\-\\\\?'\"])\"\"\"\n    decimal_escape = r\"\"\"(\\d+)\"\"\"\n    hex_escape = r\"\"\"(x[0-9a-fA-F]+)\"\"\"\n    bad_escape = r\"\"\"([\\\\][^a-zA-Z._~^!=&\\^\\-\\\\?'\"x0-7])\"\"\"\n\n    escape_sequence = r\"\"\"(\\\\(\"\"\"+simple_escape+'|'+decimal_escape+'|'+hex_escape+'))'\n    cconst_char = r\"\"\"([^'\\\\\\n]|\"\"\"+escape_sequence+')'\n    char_const = \"'\"+cconst_char+\"'\"\n    wchar_const = 'L'+char_const\n    unmatched_quote = \"('\"+cconst_char+\"*\\\\n)|('\"+cconst_char+\"*$)\"\n    bad_char_const = r\"\"\"('\"\"\"+cconst_char+\"\"\"[^'\\n]+')|('')|('\"\"\"+bad_escape+r\"\"\"[^'\\n]*')\"\"\"\n\n    # string literals (K&R2: A.2.6)\n    string_char = r\"\"\"([^\"\\\\\\n]|\"\"\"+escape_sequence+')'\n    string_literal = '\"'+string_char+'*\"'\n    wstring_literal = 'L'+string_literal\n    bad_string_literal = '\"'+string_char+'*?'+bad_escape+string_char+'*\"'\n\n    # floating constants (K&R2: A.2.5.3)\n    exponent_part = r\"\"\"([eE][-+]?[0-9]+)\"\"\"\n    fractional_constant = r\"\"\"([0-9]*\\.[0-9]+)|([0-9]+\\.)\"\"\"\n    floating_constant = '(((('+fractional_constant+')'+exponent_part+'?)|([0-9]+'+exponent_part+'))[FfLl]?)'\n    binary_exponent_part = r'''([pP][+-]?[0-9]+)'''\n    hex_fractional_constant = '((('+hex_digits+r\"\"\")?\\.\"\"\"+hex_digits+')|('+hex_digits+r\"\"\"\\.))\"\"\"\n    hex_floating_constant = '('+hex_prefix+'('+hex_digits+'|'+hex_fractional_constant+')'+binary_exponent_part+'[FfLl]?)'\n\n    ##\n    ## Lexer states: used for preprocessor \\n-terminated directives\n    ##\n    states = (\n        # ppline: preprocessor line directives\n        #\n        ('ppline', 'exclusive'),\n\n        # pppragma: pragma\n        #\n        ('pppragma', 'exclusive'),\n    )\n\n    def t_PPHASH(self, t):\n        r'[ \\t]*\\#'\n        if self.line_pattern.match(t.lexer.lexdata, pos=t.lexer.lexpos):\n            t.lexer.begin('ppline')\n            self.pp_line = self.pp_filename = None\n        elif self.pragma_pattern.match(t.lexer.lexdata, pos=t.lexer.lexpos):\n            t.lexer.begin('pppragma')\n        else:\n            t.type = 'PPHASH'\n            return t\n\n    ##\n    ## Rules for the ppline state\n    ##\n    @TOKEN(string_literal)\n    def t_ppline_FILENAME(self, t):\n        if self.pp_line is None:\n            self._error('filename before line number in #line', t)\n        else:\n            self.pp_filename = t.value.lstrip('\"').rstrip('\"')\n\n    @TOKEN(decimal_constant)\n    def t_ppline_LINE_NUMBER(self, t):\n        if self.pp_line is None:\n            self.pp_line = t.value\n        else:\n            # Ignore: GCC's cpp sometimes inserts a numeric flag\n            # after the file name\n            pass\n\n    def t_ppline_NEWLINE(self, t):\n        r'\\n'\n        if self.pp_line is None:\n            self._error('line number missing in #line', t)\n        else:\n            self.lexer.lineno = int(self.pp_line)\n\n            if self.pp_filename is not None:\n                self.filename = self.pp_filename\n\n        t.lexer.begin('INITIAL')\n\n    def t_ppline_PPLINE(self, t):\n        r'line'\n        pass\n\n    t_ppline_ignore = ' \\t'\n\n    def t_ppline_error(self, t):\n        self._error('invalid #line directive', t)\n\n    ##\n    ## Rules for the pppragma state\n    ##\n    def t_pppragma_NEWLINE(self, t):\n        r'\\n'\n        t.lexer.lineno += 1\n        t.lexer.begin('INITIAL')\n\n    def t_pppragma_PPPRAGMA(self, t):\n        r'pragma'\n        return t\n\n    t_pppragma_ignore = ' \\t'\n\n    def t_pppragma_STR(self, t):\n        '.+'\n        t.type = 'PPPRAGMASTR'\n        return t\n\n    def t_pppragma_error(self, t):\n        self._error('invalid #pragma directive', t)\n\n    ##\n    ## Rules for the normal state\n    ##\n    t_ignore = ' \\t'\n\n    # Newlines\n    def t_NEWLINE(self, t):\n        r'\\n+'\n        t.lexer.lineno += t.value.count(\"\\n\")\n\n    # Operators\n    t_PLUS              = r'\\+'\n    t_MINUS             = r'-'\n    t_TIMES             = r'\\*'\n    t_DIVIDE            = r'/'\n    t_MOD               = r'%'\n    t_OR                = r'\\|'\n    t_AND               = r'&'\n    t_NOT               = r'~'\n    t_XOR               = r'\\^'\n    t_LSHIFT            = r'<<'\n    t_RSHIFT            = r'>>'\n    t_LOR               = r'\\|\\|'\n    t_LAND              = r'&&'\n    t_LNOT              = r'!'\n    t_LT                = r'<'\n    t_GT                = r'>'\n    t_LE                = r'<='\n    t_GE                = r'>='\n    t_EQ                = r'=='\n    t_NE                = r'!='\n\n    # Assignment operators\n    t_EQUALS            = r'='\n    t_TIMESEQUAL        = r'\\*='\n    t_DIVEQUAL          = r'/='\n    t_MODEQUAL          = r'%='\n    t_PLUSEQUAL         = r'\\+='\n    t_MINUSEQUAL        = r'-='\n    t_LSHIFTEQUAL       = r'<<='\n    t_RSHIFTEQUAL       = r'>>='\n    t_ANDEQUAL          = r'&='\n    t_OREQUAL           = r'\\|='\n    t_XOREQUAL          = r'\\^='\n\n    # Increment/decrement\n    t_PLUSPLUS          = r'\\+\\+'\n    t_MINUSMINUS        = r'--'\n\n    # ->\n    t_ARROW             = r'->'\n\n    # ?\n    t_CONDOP            = r'\\?'\n\n    # Delimeters\n    t_LPAREN            = r'\\('\n    t_RPAREN            = r'\\)'\n    t_LBRACKET          = r'\\['\n    t_RBRACKET          = r'\\]'\n    t_COMMA             = r','\n    t_PERIOD            = r'\\.'\n    t_SEMI              = r';'\n    t_COLON             = r':'\n    t_ELLIPSIS          = r'\\.\\.\\.'\n\n    # Scope delimiters\n    # To see why on_lbrace_func is needed, consider:\n    #   typedef char TT;\n    #   void foo(int TT) { TT = 10; }\n    #   TT x = 5;\n    # Outside the function, TT is a typedef, but inside (starting and ending\n    # with the braces) it's a parameter.  The trouble begins with yacc's\n    # lookahead token.  If we open a new scope in brace_open, then TT has\n    # already been read and incorrectly interpreted as TYPEID.  So, we need\n    # to open and close scopes from within the lexer.\n    # Similar for the TT immediately outside the end of the function.\n    #\n    @TOKEN(r'\\{')\n    def t_LBRACE(self, t):\n        self.on_lbrace_func()\n        return t\n    @TOKEN(r'\\}')\n    def t_RBRACE(self, t):\n        self.on_rbrace_func()\n        return t\n\n    t_STRING_LITERAL = string_literal\n\n    # The following floating and integer constants are defined as\n    # functions to impose a strict order (otherwise, decimal\n    # is placed before the others because its regex is longer,\n    # and this is bad)\n    #\n    @TOKEN(floating_constant)\n    def t_FLOAT_CONST(self, t):\n        return t\n\n    @TOKEN(hex_floating_constant)\n    def t_HEX_FLOAT_CONST(self, t):\n        return t\n\n    @TOKEN(hex_constant)\n    def t_INT_CONST_HEX(self, t):\n        return t\n\n    @TOKEN(bin_constant)\n    def t_INT_CONST_BIN(self, t):\n        return t\n\n    @TOKEN(bad_octal_constant)\n    def t_BAD_CONST_OCT(self, t):\n        msg = \"Invalid octal constant\"\n        self._error(msg, t)\n\n    @TOKEN(octal_constant)\n    def t_INT_CONST_OCT(self, t):\n        return t\n\n    @TOKEN(decimal_constant)\n    def t_INT_CONST_DEC(self, t):\n        return t\n\n    # Must come before bad_char_const, to prevent it from\n    # catching valid char constants as invalid\n    #\n    @TOKEN(char_const)\n    def t_CHAR_CONST(self, t):\n        return t\n\n    @TOKEN(wchar_const)\n    def t_WCHAR_CONST(self, t):\n        return t\n\n    @TOKEN(unmatched_quote)\n    def t_UNMATCHED_QUOTE(self, t):\n        msg = \"Unmatched '\"\n        self._error(msg, t)\n\n    @TOKEN(bad_char_const)\n    def t_BAD_CHAR_CONST(self, t):\n        msg = \"Invalid char constant %s\" % t.value\n        self._error(msg, t)\n\n    @TOKEN(wstring_literal)\n    def t_WSTRING_LITERAL(self, t):\n        return t\n\n    # unmatched string literals are caught by the preprocessor\n\n    @TOKEN(bad_string_literal)\n    def t_BAD_STRING_LITERAL(self, t):\n        msg = \"String contains invalid escape code\"\n        self._error(msg, t)\n\n    @TOKEN(identifier)\n    def t_ID(self, t):\n        t.type = self.keyword_map.get(t.value, \"ID\")\n        if t.type == 'ID' and self.type_lookup_func(t.value):\n            t.type = \"TYPEID\"\n        return t\n\n    def t_error(self, t):\n        msg = 'Illegal character %s' % repr(t.value[0])\n        self._error(msg, t)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/c_parser.py",
    "content": "#------------------------------------------------------------------------------\n# pycparser: c_parser.py\n#\n# CParser class: Parser and AST builder for the C language\n#\n# Eli Bendersky [https://eli.thegreenplace.net/]\n# License: BSD\n#------------------------------------------------------------------------------\nimport re\n\nfrom .ply import yacc\n\nfrom . import c_ast\nfrom .c_lexer import CLexer\nfrom .plyparser import PLYParser, Coord, ParseError, parameterized, template\nfrom .ast_transforms import fix_switch_cases\n\n\n@template\nclass CParser(PLYParser):\n    def __init__(\n            self,\n            lex_optimize=True,\n            lexer=CLexer,\n            lextab='pycparser.lextab',\n            yacc_optimize=True,\n            yacctab='pycparser.yacctab',\n            yacc_debug=False,\n            taboutputdir=''):\n        \"\"\" Create a new CParser.\n\n            Some arguments for controlling the debug/optimization\n            level of the parser are provided. The defaults are\n            tuned for release/performance mode.\n            The simple rules for using them are:\n            *) When tweaking CParser/CLexer, set these to False\n            *) When releasing a stable parser, set to True\n\n            lex_optimize:\n                Set to False when you're modifying the lexer.\n                Otherwise, changes in the lexer won't be used, if\n                some lextab.py file exists.\n                When releasing with a stable lexer, set to True\n                to save the re-generation of the lexer table on\n                each run.\n\n            lexer:\n                Set this parameter to define the lexer to use if\n                you're not using the default CLexer.\n\n            lextab:\n                Points to the lex table that's used for optimized\n                mode. Only if you're modifying the lexer and want\n                some tests to avoid re-generating the table, make\n                this point to a local lex table file (that's been\n                earlier generated with lex_optimize=True)\n\n            yacc_optimize:\n                Set to False when you're modifying the parser.\n                Otherwise, changes in the parser won't be used, if\n                some parsetab.py file exists.\n                When releasing with a stable parser, set to True\n                to save the re-generation of the parser table on\n                each run.\n\n            yacctab:\n                Points to the yacc table that's used for optimized\n                mode. Only if you're modifying the parser, make\n                this point to a local yacc table file\n\n            yacc_debug:\n                Generate a parser.out file that explains how yacc\n                built the parsing table from the grammar.\n\n            taboutputdir:\n                Set this parameter to control the location of generated\n                lextab and yacctab files.\n        \"\"\"\n        self.clex = lexer(\n            error_func=self._lex_error_func,\n            on_lbrace_func=self._lex_on_lbrace_func,\n            on_rbrace_func=self._lex_on_rbrace_func,\n            type_lookup_func=self._lex_type_lookup_func)\n\n        self.clex.build(\n            optimize=lex_optimize,\n            lextab=lextab,\n            outputdir=taboutputdir)\n        self.tokens = self.clex.tokens\n\n        rules_with_opt = [\n            'abstract_declarator',\n            'assignment_expression',\n            'declaration_list',\n            'declaration_specifiers_no_type',\n            'designation',\n            'expression',\n            'identifier_list',\n            'init_declarator_list',\n            'id_init_declarator_list',\n            'initializer_list',\n            'parameter_type_list',\n            'block_item_list',\n            'type_qualifier_list',\n            'struct_declarator_list'\n        ]\n\n        for rule in rules_with_opt:\n            self._create_opt_rule(rule)\n\n        self.cparser = yacc.yacc(\n            module=self,\n            start='translation_unit_or_empty',\n            debug=yacc_debug,\n            optimize=yacc_optimize,\n            tabmodule=yacctab,\n            outputdir=taboutputdir)\n\n        # Stack of scopes for keeping track of symbols. _scope_stack[-1] is\n        # the current (topmost) scope. Each scope is a dictionary that\n        # specifies whether a name is a type. If _scope_stack[n][name] is\n        # True, 'name' is currently a type in the scope. If it's False,\n        # 'name' is used in the scope but not as a type (for instance, if we\n        # saw: int name;\n        # If 'name' is not a key in _scope_stack[n] then 'name' was not defined\n        # in this scope at all.\n        self._scope_stack = [dict()]\n\n        # Keeps track of the last token given to yacc (the lookahead token)\n        self._last_yielded_token = None\n\n    def parse(self, text, filename='', debuglevel=0):\n        \"\"\" Parses C code and returns an AST.\n\n            text:\n                A string containing the C source code\n\n            filename:\n                Name of the file being parsed (for meaningful\n                error messages)\n\n            debuglevel:\n                Debug level to yacc\n        \"\"\"\n        self.clex.filename = filename\n        self.clex.reset_lineno()\n        self._scope_stack = [dict()]\n        self._last_yielded_token = None\n        return self.cparser.parse(\n                input=text,\n                lexer=self.clex,\n                debug=debuglevel)\n\n    ######################--   PRIVATE   --######################\n\n    def _push_scope(self):\n        self._scope_stack.append(dict())\n\n    def _pop_scope(self):\n        assert len(self._scope_stack) > 1\n        self._scope_stack.pop()\n\n    def _add_typedef_name(self, name, coord):\n        \"\"\" Add a new typedef name (ie a TYPEID) to the current scope\n        \"\"\"\n        if not self._scope_stack[-1].get(name, True):\n            self._parse_error(\n                \"Typedef %r previously declared as non-typedef \"\n                \"in this scope\" % name, coord)\n        self._scope_stack[-1][name] = True\n\n    def _add_identifier(self, name, coord):\n        \"\"\" Add a new object, function, or enum member name (ie an ID) to the\n            current scope\n        \"\"\"\n        if self._scope_stack[-1].get(name, False):\n            self._parse_error(\n                \"Non-typedef %r previously declared as typedef \"\n                \"in this scope\" % name, coord)\n        self._scope_stack[-1][name] = False\n\n    def _is_type_in_scope(self, name):\n        \"\"\" Is *name* a typedef-name in the current scope?\n        \"\"\"\n        for scope in reversed(self._scope_stack):\n            # If name is an identifier in this scope it shadows typedefs in\n            # higher scopes.\n            in_scope = scope.get(name)\n            if in_scope is not None: return in_scope\n        return False\n\n    def _lex_error_func(self, msg, line, column):\n        self._parse_error(msg, self._coord(line, column))\n\n    def _lex_on_lbrace_func(self):\n        self._push_scope()\n\n    def _lex_on_rbrace_func(self):\n        self._pop_scope()\n\n    def _lex_type_lookup_func(self, name):\n        \"\"\" Looks up types that were previously defined with\n            typedef.\n            Passed to the lexer for recognizing identifiers that\n            are types.\n        \"\"\"\n        is_type = self._is_type_in_scope(name)\n        return is_type\n\n    def _get_yacc_lookahead_token(self):\n        \"\"\" We need access to yacc's lookahead token in certain cases.\n            This is the last token yacc requested from the lexer, so we\n            ask the lexer.\n        \"\"\"\n        return self.clex.last_token\n\n    # To understand what's going on here, read sections A.8.5 and\n    # A.8.6 of K&R2 very carefully.\n    #\n    # A C type consists of a basic type declaration, with a list\n    # of modifiers. For example:\n    #\n    # int *c[5];\n    #\n    # The basic declaration here is 'int c', and the pointer and\n    # the array are the modifiers.\n    #\n    # Basic declarations are represented by TypeDecl (from module c_ast) and the\n    # modifiers are FuncDecl, PtrDecl and ArrayDecl.\n    #\n    # The standard states that whenever a new modifier is parsed, it should be\n    # added to the end of the list of modifiers. For example:\n    #\n    # K&R2 A.8.6.2: Array Declarators\n    #\n    # In a declaration T D where D has the form\n    #   D1 [constant-expression-opt]\n    # and the type of the identifier in the declaration T D1 is\n    # \"type-modifier T\", the type of the\n    # identifier of D is \"type-modifier array of T\"\n    #\n    # This is what this method does. The declarator it receives\n    # can be a list of declarators ending with TypeDecl. It\n    # tacks the modifier to the end of this list, just before\n    # the TypeDecl.\n    #\n    # Additionally, the modifier may be a list itself. This is\n    # useful for pointers, that can come as a chain from the rule\n    # p_pointer. In this case, the whole modifier list is spliced\n    # into the new location.\n    def _type_modify_decl(self, decl, modifier):\n        \"\"\" Tacks a type modifier on a declarator, and returns\n            the modified declarator.\n\n            Note: the declarator and modifier may be modified\n        \"\"\"\n        #~ print '****'\n        #~ decl.show(offset=3)\n        #~ modifier.show(offset=3)\n        #~ print '****'\n\n        modifier_head = modifier\n        modifier_tail = modifier\n\n        # The modifier may be a nested list. Reach its tail.\n        #\n        while modifier_tail.type:\n            modifier_tail = modifier_tail.type\n\n        # If the decl is a basic type, just tack the modifier onto\n        # it\n        #\n        if isinstance(decl, c_ast.TypeDecl):\n            modifier_tail.type = decl\n            return modifier\n        else:\n            # Otherwise, the decl is a list of modifiers. Reach\n            # its tail and splice the modifier onto the tail,\n            # pointing to the underlying basic type.\n            #\n            decl_tail = decl\n\n            while not isinstance(decl_tail.type, c_ast.TypeDecl):\n                decl_tail = decl_tail.type\n\n            modifier_tail.type = decl_tail.type\n            decl_tail.type = modifier_head\n            return decl\n\n    # Due to the order in which declarators are constructed,\n    # they have to be fixed in order to look like a normal AST.\n    #\n    # When a declaration arrives from syntax construction, it has\n    # these problems:\n    # * The innermost TypeDecl has no type (because the basic\n    #   type is only known at the uppermost declaration level)\n    # * The declaration has no variable name, since that is saved\n    #   in the innermost TypeDecl\n    # * The typename of the declaration is a list of type\n    #   specifiers, and not a node. Here, basic identifier types\n    #   should be separated from more complex types like enums\n    #   and structs.\n    #\n    # This method fixes these problems.\n    #\n    def _fix_decl_name_type(self, decl, typename):\n        \"\"\" Fixes a declaration. Modifies decl.\n        \"\"\"\n        # Reach the underlying basic type\n        #\n        type = decl\n        while not isinstance(type, c_ast.TypeDecl):\n            type = type.type\n\n        decl.name = type.declname\n        type.quals = decl.quals\n\n        # The typename is a list of types. If any type in this\n        # list isn't an IdentifierType, it must be the only\n        # type in the list (it's illegal to declare \"int enum ..\")\n        # If all the types are basic, they're collected in the\n        # IdentifierType holder.\n        #\n        for tn in typename:\n            if not isinstance(tn, c_ast.IdentifierType):\n                if len(typename) > 1:\n                    self._parse_error(\n                        \"Invalid multiple types specified\", tn.coord)\n                else:\n                    type.type = tn\n                    return decl\n\n        if not typename:\n            # Functions default to returning int\n            #\n            if not isinstance(decl.type, c_ast.FuncDecl):\n                self._parse_error(\n                        \"Missing type in declaration\", decl.coord)\n            type.type = c_ast.IdentifierType(\n                    ['int'],\n                    coord=decl.coord)\n        else:\n            # At this point, we know that typename is a list of IdentifierType\n            # nodes. Concatenate all the names into a single list.\n            #\n            type.type = c_ast.IdentifierType(\n                [name for id in typename for name in id.names],\n                coord=typename[0].coord)\n        return decl\n\n    def _add_declaration_specifier(self, declspec, newspec, kind, append=False):\n        \"\"\" Declaration specifiers are represented by a dictionary\n            with the entries:\n            * qual: a list of type qualifiers\n            * storage: a list of storage type qualifiers\n            * type: a list of type specifiers\n            * function: a list of function specifiers\n\n            This method is given a declaration specifier, and a\n            new specifier of a given kind.\n            If `append` is True, the new specifier is added to the end of\n            the specifiers list, otherwise it's added at the beginning.\n            Returns the declaration specifier, with the new\n            specifier incorporated.\n        \"\"\"\n        spec = declspec or dict(qual=[], storage=[], type=[], function=[])\n\n        if append:\n            spec[kind].append(newspec)\n        else:\n            spec[kind].insert(0, newspec)\n\n        return spec\n\n    def _build_declarations(self, spec, decls, typedef_namespace=False):\n        \"\"\" Builds a list of declarations all sharing the given specifiers.\n            If typedef_namespace is true, each declared name is added\n            to the \"typedef namespace\", which also includes objects,\n            functions, and enum constants.\n        \"\"\"\n        is_typedef = 'typedef' in spec['storage']\n        declarations = []\n\n        # Bit-fields are allowed to be unnamed.\n        #\n        if decls[0].get('bitsize') is not None:\n            pass\n\n        # When redeclaring typedef names as identifiers in inner scopes, a\n        # problem can occur where the identifier gets grouped into\n        # spec['type'], leaving decl as None.  This can only occur for the\n        # first declarator.\n        #\n        elif decls[0]['decl'] is None:\n            if len(spec['type']) < 2 or len(spec['type'][-1].names) != 1 or \\\n                    not self._is_type_in_scope(spec['type'][-1].names[0]):\n                coord = '?'\n                for t in spec['type']:\n                    if hasattr(t, 'coord'):\n                        coord = t.coord\n                        break\n                self._parse_error('Invalid declaration', coord)\n\n            # Make this look as if it came from \"direct_declarator:ID\"\n            decls[0]['decl'] = c_ast.TypeDecl(\n                declname=spec['type'][-1].names[0],\n                type=None,\n                quals=None,\n                coord=spec['type'][-1].coord)\n            # Remove the \"new\" type's name from the end of spec['type']\n            del spec['type'][-1]\n\n        # A similar problem can occur where the declaration ends up looking\n        # like an abstract declarator.  Give it a name if this is the case.\n        #\n        elif not isinstance(decls[0]['decl'],\n                (c_ast.Struct, c_ast.Union, c_ast.IdentifierType)):\n            decls_0_tail = decls[0]['decl']\n            while not isinstance(decls_0_tail, c_ast.TypeDecl):\n                decls_0_tail = decls_0_tail.type\n            if decls_0_tail.declname is None:\n                decls_0_tail.declname = spec['type'][-1].names[0]\n                del spec['type'][-1]\n\n        for decl in decls:\n            assert decl['decl'] is not None\n            if is_typedef:\n                declaration = c_ast.Typedef(\n                    name=None,\n                    quals=spec['qual'],\n                    storage=spec['storage'],\n                    type=decl['decl'],\n                    coord=decl['decl'].coord)\n            else:\n                declaration = c_ast.Decl(\n                    name=None,\n                    quals=spec['qual'],\n                    storage=spec['storage'],\n                    funcspec=spec['function'],\n                    type=decl['decl'],\n                    init=decl.get('init'),\n                    bitsize=decl.get('bitsize'),\n                    coord=decl['decl'].coord)\n\n            if isinstance(declaration.type,\n                    (c_ast.Struct, c_ast.Union, c_ast.IdentifierType)):\n                fixed_decl = declaration\n            else:\n                fixed_decl = self._fix_decl_name_type(declaration, spec['type'])\n\n            # Add the type name defined by typedef to a\n            # symbol table (for usage in the lexer)\n            #\n            if typedef_namespace:\n                if is_typedef:\n                    self._add_typedef_name(fixed_decl.name, fixed_decl.coord)\n                else:\n                    self._add_identifier(fixed_decl.name, fixed_decl.coord)\n\n            declarations.append(fixed_decl)\n\n        return declarations\n\n    def _build_function_definition(self, spec, decl, param_decls, body):\n        \"\"\" Builds a function definition.\n        \"\"\"\n        assert 'typedef' not in spec['storage']\n\n        declaration = self._build_declarations(\n            spec=spec,\n            decls=[dict(decl=decl, init=None)],\n            typedef_namespace=True)[0]\n\n        return c_ast.FuncDef(\n            decl=declaration,\n            param_decls=param_decls,\n            body=body,\n            coord=decl.coord)\n\n    def _select_struct_union_class(self, token):\n        \"\"\" Given a token (either STRUCT or UNION), selects the\n            appropriate AST class.\n        \"\"\"\n        if token == 'struct':\n            return c_ast.Struct\n        else:\n            return c_ast.Union\n\n    ##\n    ## Precedence and associativity of operators\n    ##\n    precedence = (\n        ('left', 'LOR'),\n        ('left', 'LAND'),\n        ('left', 'OR'),\n        ('left', 'XOR'),\n        ('left', 'AND'),\n        ('left', 'EQ', 'NE'),\n        ('left', 'GT', 'GE', 'LT', 'LE'),\n        ('left', 'RSHIFT', 'LSHIFT'),\n        ('left', 'PLUS', 'MINUS'),\n        ('left', 'TIMES', 'DIVIDE', 'MOD')\n    )\n\n    ##\n    ## Grammar productions\n    ## Implementation of the BNF defined in K&R2 A.13\n    ##\n\n    # Wrapper around a translation unit, to allow for empty input.\n    # Not strictly part of the C99 Grammar, but useful in practice.\n    #\n    def p_translation_unit_or_empty(self, p):\n        \"\"\" translation_unit_or_empty   : translation_unit\n                                        | empty\n        \"\"\"\n        if p[1] is None:\n            p[0] = c_ast.FileAST([])\n        else:\n            p[0] = c_ast.FileAST(p[1])\n\n    def p_translation_unit_1(self, p):\n        \"\"\" translation_unit    : external_declaration\n        \"\"\"\n        # Note: external_declaration is already a list\n        #\n        p[0] = p[1]\n\n    def p_translation_unit_2(self, p):\n        \"\"\" translation_unit    : translation_unit external_declaration\n        \"\"\"\n        if p[2] is not None:\n            p[1].extend(p[2])\n        p[0] = p[1]\n\n    # Declarations always come as lists (because they can be\n    # several in one line), so we wrap the function definition\n    # into a list as well, to make the return value of\n    # external_declaration homogenous.\n    #\n    def p_external_declaration_1(self, p):\n        \"\"\" external_declaration    : function_definition\n        \"\"\"\n        p[0] = [p[1]]\n\n    def p_external_declaration_2(self, p):\n        \"\"\" external_declaration    : declaration\n        \"\"\"\n        p[0] = p[1]\n\n    def p_external_declaration_3(self, p):\n        \"\"\" external_declaration    : pp_directive\n                                    | pppragma_directive\n        \"\"\"\n        p[0] = [p[1]]\n\n    def p_external_declaration_4(self, p):\n        \"\"\" external_declaration    : SEMI\n        \"\"\"\n        p[0] = None\n\n    def p_pp_directive(self, p):\n        \"\"\" pp_directive  : PPHASH\n        \"\"\"\n        self._parse_error('Directives not supported yet',\n                          self._token_coord(p, 1))\n\n    def p_pppragma_directive(self, p):\n        \"\"\" pppragma_directive      : PPPRAGMA\n                                    | PPPRAGMA PPPRAGMASTR\n        \"\"\"\n        if len(p) == 3:\n            p[0] = c_ast.Pragma(p[2], self._token_coord(p, 2))\n        else:\n            p[0] = c_ast.Pragma(\"\", self._token_coord(p, 1))\n\n    # In function definitions, the declarator can be followed by\n    # a declaration list, for old \"K&R style\" function definitios.\n    #\n    def p_function_definition_1(self, p):\n        \"\"\" function_definition : id_declarator declaration_list_opt compound_statement\n        \"\"\"\n        # no declaration specifiers - 'int' becomes the default type\n        spec = dict(\n            qual=[],\n            storage=[],\n            type=[c_ast.IdentifierType(['int'],\n                                       coord=self._token_coord(p, 1))],\n            function=[])\n\n        p[0] = self._build_function_definition(\n            spec=spec,\n            decl=p[1],\n            param_decls=p[2],\n            body=p[3])\n\n    def p_function_definition_2(self, p):\n        \"\"\" function_definition : declaration_specifiers id_declarator declaration_list_opt compound_statement\n        \"\"\"\n        spec = p[1]\n\n        p[0] = self._build_function_definition(\n            spec=spec,\n            decl=p[2],\n            param_decls=p[3],\n            body=p[4])\n\n    def p_statement(self, p):\n        \"\"\" statement   : labeled_statement\n                        | expression_statement\n                        | compound_statement\n                        | selection_statement\n                        | iteration_statement\n                        | jump_statement\n                        | pppragma_directive\n        \"\"\"\n        p[0] = p[1]\n\n    # A pragma is generally considered a decorator rather than an actual statement.\n    # Still, for the purposes of analyzing an abstract syntax tree of C code,\n    # pragma's should not be ignored and were previously treated as a statement.\n    # This presents a problem for constructs that take a statement such as labeled_statements,\n    # selection_statements, and iteration_statements, causing a misleading structure\n    # in the AST. For example, consider the following C code.\n    #\n    #   for (int i = 0; i < 3; i++)\n    #       #pragma omp critical\n    #       sum += 1;\n    #\n    # This code will compile and execute \"sum += 1;\" as the body of the for loop.\n    # Previous implementations of PyCParser would render the AST for this\n    # block of code as follows:\n    #\n    #   For:\n    #     DeclList:\n    #       Decl: i, [], [], []\n    #         TypeDecl: i, []\n    #           IdentifierType: ['int']\n    #         Constant: int, 0\n    #     BinaryOp: <\n    #       ID: i\n    #       Constant: int, 3\n    #     UnaryOp: p++\n    #       ID: i\n    #     Pragma: omp critical\n    #   Assignment: +=\n    #     ID: sum\n    #     Constant: int, 1\n    #\n    # This AST misleadingly takes the Pragma as the body of the loop and the\n    # assignment then becomes a sibling of the loop.\n    #\n    # To solve edge cases like these, the pragmacomp_or_statement rule groups\n    # a pragma and its following statement (which would otherwise be orphaned)\n    # using a compound block, effectively turning the above code into:\n    #\n    #   for (int i = 0; i < 3; i++) {\n    #       #pragma omp critical\n    #       sum += 1;\n    #   }\n    def p_pragmacomp_or_statement(self, p):\n        \"\"\" pragmacomp_or_statement     : pppragma_directive statement\n                                        | statement\n        \"\"\"\n        if isinstance(p[1], c_ast.Pragma) and len(p) == 3:\n            p[0] = c_ast.Compound(\n                block_items=[p[1], p[2]],\n                coord=self._token_coord(p, 1))\n        else:\n            p[0] = p[1]\n\n    # In C, declarations can come several in a line:\n    #   int x, *px, romulo = 5;\n    #\n    # However, for the AST, we will split them to separate Decl\n    # nodes.\n    #\n    # This rule splits its declarations and always returns a list\n    # of Decl nodes, even if it's one element long.\n    #\n    def p_decl_body(self, p):\n        \"\"\" decl_body : declaration_specifiers init_declarator_list_opt\n                      | declaration_specifiers_no_type id_init_declarator_list_opt\n        \"\"\"\n        spec = p[1]\n\n        # p[2] (init_declarator_list_opt) is either a list or None\n        #\n        if p[2] is None:\n            # By the standard, you must have at least one declarator unless\n            # declaring a structure tag, a union tag, or the members of an\n            # enumeration.\n            #\n            ty = spec['type']\n            s_u_or_e = (c_ast.Struct, c_ast.Union, c_ast.Enum)\n            if len(ty) == 1 and isinstance(ty[0], s_u_or_e):\n                decls = [c_ast.Decl(\n                    name=None,\n                    quals=spec['qual'],\n                    storage=spec['storage'],\n                    funcspec=spec['function'],\n                    type=ty[0],\n                    init=None,\n                    bitsize=None,\n                    coord=ty[0].coord)]\n\n            # However, this case can also occur on redeclared identifiers in\n            # an inner scope.  The trouble is that the redeclared type's name\n            # gets grouped into declaration_specifiers; _build_declarations\n            # compensates for this.\n            #\n            else:\n                decls = self._build_declarations(\n                    spec=spec,\n                    decls=[dict(decl=None, init=None)],\n                    typedef_namespace=True)\n\n        else:\n            decls = self._build_declarations(\n                spec=spec,\n                decls=p[2],\n                typedef_namespace=True)\n\n        p[0] = decls\n\n    # The declaration has been split to a decl_body sub-rule and\n    # SEMI, because having them in a single rule created a problem\n    # for defining typedefs.\n    #\n    # If a typedef line was directly followed by a line using the\n    # type defined with the typedef, the type would not be\n    # recognized. This is because to reduce the declaration rule,\n    # the parser's lookahead asked for the token after SEMI, which\n    # was the type from the next line, and the lexer had no chance\n    # to see the updated type symbol table.\n    #\n    # Splitting solves this problem, because after seeing SEMI,\n    # the parser reduces decl_body, which actually adds the new\n    # type into the table to be seen by the lexer before the next\n    # line is reached.\n    def p_declaration(self, p):\n        \"\"\" declaration : decl_body SEMI\n        \"\"\"\n        p[0] = p[1]\n\n    # Since each declaration is a list of declarations, this\n    # rule will combine all the declarations and return a single\n    # list\n    #\n    def p_declaration_list(self, p):\n        \"\"\" declaration_list    : declaration\n                                | declaration_list declaration\n        \"\"\"\n        p[0] = p[1] if len(p) == 2 else p[1] + p[2]\n\n    # To know when declaration-specifiers end and declarators begin,\n    # we require declaration-specifiers to have at least one\n    # type-specifier, and disallow typedef-names after we've seen any\n    # type-specifier. These are both required by the spec.\n    #\n    def p_declaration_specifiers_no_type_1(self, p):\n        \"\"\" declaration_specifiers_no_type  : type_qualifier declaration_specifiers_no_type_opt\n        \"\"\"\n        p[0] = self._add_declaration_specifier(p[2], p[1], 'qual')\n\n    def p_declaration_specifiers_no_type_2(self, p):\n        \"\"\" declaration_specifiers_no_type  : storage_class_specifier declaration_specifiers_no_type_opt\n        \"\"\"\n        p[0] = self._add_declaration_specifier(p[2], p[1], 'storage')\n\n    def p_declaration_specifiers_no_type_3(self, p):\n        \"\"\" declaration_specifiers_no_type  : function_specifier declaration_specifiers_no_type_opt\n        \"\"\"\n        p[0] = self._add_declaration_specifier(p[2], p[1], 'function')\n\n\n    def p_declaration_specifiers_1(self, p):\n        \"\"\" declaration_specifiers  : declaration_specifiers type_qualifier\n        \"\"\"\n        p[0] = self._add_declaration_specifier(p[1], p[2], 'qual', append=True)\n\n    def p_declaration_specifiers_2(self, p):\n        \"\"\" declaration_specifiers  : declaration_specifiers storage_class_specifier\n        \"\"\"\n        p[0] = self._add_declaration_specifier(p[1], p[2], 'storage', append=True)\n\n    def p_declaration_specifiers_3(self, p):\n        \"\"\" declaration_specifiers  : declaration_specifiers function_specifier\n        \"\"\"\n        p[0] = self._add_declaration_specifier(p[1], p[2], 'function', append=True)\n\n    def p_declaration_specifiers_4(self, p):\n        \"\"\" declaration_specifiers  : declaration_specifiers type_specifier_no_typeid\n        \"\"\"\n        p[0] = self._add_declaration_specifier(p[1], p[2], 'type', append=True)\n\n    def p_declaration_specifiers_5(self, p):\n        \"\"\" declaration_specifiers  : type_specifier\n        \"\"\"\n        p[0] = self._add_declaration_specifier(None, p[1], 'type')\n\n    def p_declaration_specifiers_6(self, p):\n        \"\"\" declaration_specifiers  : declaration_specifiers_no_type type_specifier\n        \"\"\"\n        p[0] = self._add_declaration_specifier(p[1], p[2], 'type', append=True)\n\n\n    def p_storage_class_specifier(self, p):\n        \"\"\" storage_class_specifier : AUTO\n                                    | REGISTER\n                                    | STATIC\n                                    | EXTERN\n                                    | TYPEDEF\n        \"\"\"\n        p[0] = p[1]\n\n    def p_function_specifier(self, p):\n        \"\"\" function_specifier  : INLINE\n        \"\"\"\n        p[0] = p[1]\n\n    def p_type_specifier_no_typeid(self, p):\n        \"\"\" type_specifier_no_typeid  : VOID\n                                      | _BOOL\n                                      | CHAR\n                                      | SHORT\n                                      | INT\n                                      | LONG\n                                      | FLOAT\n                                      | DOUBLE\n                                      | _COMPLEX\n                                      | SIGNED\n                                      | UNSIGNED\n                                      | __INT128\n        \"\"\"\n        p[0] = c_ast.IdentifierType([p[1]], coord=self._token_coord(p, 1))\n\n    def p_type_specifier(self, p):\n        \"\"\" type_specifier  : typedef_name\n                            | enum_specifier\n                            | struct_or_union_specifier\n                            | type_specifier_no_typeid\n        \"\"\"\n        p[0] = p[1]\n\n    def p_type_qualifier(self, p):\n        \"\"\" type_qualifier  : CONST\n                            | RESTRICT\n                            | VOLATILE\n        \"\"\"\n        p[0] = p[1]\n\n    def p_init_declarator_list(self, p):\n        \"\"\" init_declarator_list    : init_declarator\n                                    | init_declarator_list COMMA init_declarator\n        \"\"\"\n        p[0] = p[1] + [p[3]] if len(p) == 4 else [p[1]]\n\n    # Returns a {decl=<declarator> : init=<initializer>} dictionary\n    # If there's no initializer, uses None\n    #\n    def p_init_declarator(self, p):\n        \"\"\" init_declarator : declarator\n                            | declarator EQUALS initializer\n        \"\"\"\n        p[0] = dict(decl=p[1], init=(p[3] if len(p) > 2 else None))\n\n    def p_id_init_declarator_list(self, p):\n        \"\"\" id_init_declarator_list    : id_init_declarator\n                                       | id_init_declarator_list COMMA init_declarator\n        \"\"\"\n        p[0] = p[1] + [p[3]] if len(p) == 4 else [p[1]]\n\n    def p_id_init_declarator(self, p):\n        \"\"\" id_init_declarator : id_declarator\n                               | id_declarator EQUALS initializer\n        \"\"\"\n        p[0] = dict(decl=p[1], init=(p[3] if len(p) > 2 else None))\n\n    # Require at least one type specifier in a specifier-qualifier-list\n    #\n    def p_specifier_qualifier_list_1(self, p):\n        \"\"\" specifier_qualifier_list    : specifier_qualifier_list type_specifier_no_typeid\n        \"\"\"\n        p[0] = self._add_declaration_specifier(p[1], p[2], 'type', append=True)\n\n    def p_specifier_qualifier_list_2(self, p):\n        \"\"\" specifier_qualifier_list    : specifier_qualifier_list type_qualifier\n        \"\"\"\n        p[0] = self._add_declaration_specifier(p[1], p[2], 'qual', append=True)\n\n    def p_specifier_qualifier_list_3(self, p):\n        \"\"\" specifier_qualifier_list  : type_specifier\n        \"\"\"\n        p[0] = self._add_declaration_specifier(None, p[1], 'type')\n\n    def p_specifier_qualifier_list_4(self, p):\n        \"\"\" specifier_qualifier_list  : type_qualifier_list type_specifier\n        \"\"\"\n        spec = dict(qual=p[1], storage=[], type=[], function=[])\n        p[0] = self._add_declaration_specifier(spec, p[2], 'type', append=True)\n\n    # TYPEID is allowed here (and in other struct/enum related tag names), because\n    # struct/enum tags reside in their own namespace and can be named the same as types\n    #\n    def p_struct_or_union_specifier_1(self, p):\n        \"\"\" struct_or_union_specifier   : struct_or_union ID\n                                        | struct_or_union TYPEID\n        \"\"\"\n        klass = self._select_struct_union_class(p[1])\n        # None means no list of members\n        p[0] = klass(\n            name=p[2],\n            decls=None,\n            coord=self._token_coord(p, 2))\n\n    def p_struct_or_union_specifier_2(self, p):\n        \"\"\" struct_or_union_specifier : struct_or_union brace_open struct_declaration_list brace_close\n                                      | struct_or_union brace_open brace_close\n        \"\"\"\n        klass = self._select_struct_union_class(p[1])\n        if len(p) == 4:\n            # Empty sequence means an empty list of members\n            p[0] = klass(\n                name=None,\n                decls=[],\n                coord=self._token_coord(p, 2))\n        else:\n            p[0] = klass(\n                name=None,\n                decls=p[3],\n                coord=self._token_coord(p, 2))\n\n\n    def p_struct_or_union_specifier_3(self, p):\n        \"\"\" struct_or_union_specifier   : struct_or_union ID brace_open struct_declaration_list brace_close\n                                        | struct_or_union ID brace_open brace_close\n                                        | struct_or_union TYPEID brace_open struct_declaration_list brace_close\n                                        | struct_or_union TYPEID brace_open brace_close\n        \"\"\"\n        klass = self._select_struct_union_class(p[1])\n        if len(p) == 5:\n            # Empty sequence means an empty list of members\n            p[0] = klass(\n                name=p[2],\n                decls=[],\n                coord=self._token_coord(p, 2))\n        else:\n            p[0] = klass(\n                name=p[2],\n                decls=p[4],\n                coord=self._token_coord(p, 2))\n\n    def p_struct_or_union(self, p):\n        \"\"\" struct_or_union : STRUCT\n                            | UNION\n        \"\"\"\n        p[0] = p[1]\n\n    # Combine all declarations into a single list\n    #\n    def p_struct_declaration_list(self, p):\n        \"\"\" struct_declaration_list     : struct_declaration\n                                        | struct_declaration_list struct_declaration\n        \"\"\"\n        if len(p) == 2:\n            p[0] = p[1] or []\n        else:\n            p[0] = p[1] + (p[2] or [])\n\n    def p_struct_declaration_1(self, p):\n        \"\"\" struct_declaration : specifier_qualifier_list struct_declarator_list_opt SEMI\n        \"\"\"\n        spec = p[1]\n        assert 'typedef' not in spec['storage']\n\n        if p[2] is not None:\n            decls = self._build_declarations(\n                spec=spec,\n                decls=p[2])\n\n        elif len(spec['type']) == 1:\n            # Anonymous struct/union, gcc extension, C1x feature.\n            # Although the standard only allows structs/unions here, I see no\n            # reason to disallow other types since some compilers have typedefs\n            # here, and pycparser isn't about rejecting all invalid code.\n            #\n            node = spec['type'][0]\n            if isinstance(node, c_ast.Node):\n                decl_type = node\n            else:\n                decl_type = c_ast.IdentifierType(node)\n\n            decls = self._build_declarations(\n                spec=spec,\n                decls=[dict(decl=decl_type)])\n\n        else:\n            # Structure/union members can have the same names as typedefs.\n            # The trouble is that the member's name gets grouped into\n            # specifier_qualifier_list; _build_declarations compensates.\n            #\n            decls = self._build_declarations(\n                spec=spec,\n                decls=[dict(decl=None, init=None)])\n\n        p[0] = decls\n\n    def p_struct_declaration_2(self, p):\n        \"\"\" struct_declaration : SEMI\n        \"\"\"\n        p[0] = None\n\n    def p_struct_declaration_3(self, p):\n        \"\"\" struct_declaration : pppragma_directive\n        \"\"\"\n        p[0] = [p[1]]\n\n    def p_struct_declarator_list(self, p):\n        \"\"\" struct_declarator_list  : struct_declarator\n                                    | struct_declarator_list COMMA struct_declarator\n        \"\"\"\n        p[0] = p[1] + [p[3]] if len(p) == 4 else [p[1]]\n\n    # struct_declarator passes up a dict with the keys: decl (for\n    # the underlying declarator) and bitsize (for the bitsize)\n    #\n    def p_struct_declarator_1(self, p):\n        \"\"\" struct_declarator : declarator\n        \"\"\"\n        p[0] = {'decl': p[1], 'bitsize': None}\n\n    def p_struct_declarator_2(self, p):\n        \"\"\" struct_declarator   : declarator COLON constant_expression\n                                | COLON constant_expression\n        \"\"\"\n        if len(p) > 3:\n            p[0] = {'decl': p[1], 'bitsize': p[3]}\n        else:\n            p[0] = {'decl': c_ast.TypeDecl(None, None, None), 'bitsize': p[2]}\n\n    def p_enum_specifier_1(self, p):\n        \"\"\" enum_specifier  : ENUM ID\n                            | ENUM TYPEID\n        \"\"\"\n        p[0] = c_ast.Enum(p[2], None, self._token_coord(p, 1))\n\n    def p_enum_specifier_2(self, p):\n        \"\"\" enum_specifier  : ENUM brace_open enumerator_list brace_close\n        \"\"\"\n        p[0] = c_ast.Enum(None, p[3], self._token_coord(p, 1))\n\n    def p_enum_specifier_3(self, p):\n        \"\"\" enum_specifier  : ENUM ID brace_open enumerator_list brace_close\n                            | ENUM TYPEID brace_open enumerator_list brace_close\n        \"\"\"\n        p[0] = c_ast.Enum(p[2], p[4], self._token_coord(p, 1))\n\n    def p_enumerator_list(self, p):\n        \"\"\" enumerator_list : enumerator\n                            | enumerator_list COMMA\n                            | enumerator_list COMMA enumerator\n        \"\"\"\n        if len(p) == 2:\n            p[0] = c_ast.EnumeratorList([p[1]], p[1].coord)\n        elif len(p) == 3:\n            p[0] = p[1]\n        else:\n            p[1].enumerators.append(p[3])\n            p[0] = p[1]\n\n    def p_enumerator(self, p):\n        \"\"\" enumerator  : ID\n                        | ID EQUALS constant_expression\n        \"\"\"\n        if len(p) == 2:\n            enumerator = c_ast.Enumerator(\n                        p[1], None,\n                        self._token_coord(p, 1))\n        else:\n            enumerator = c_ast.Enumerator(\n                        p[1], p[3],\n                        self._token_coord(p, 1))\n        self._add_identifier(enumerator.name, enumerator.coord)\n\n        p[0] = enumerator\n\n    def p_declarator(self, p):\n        \"\"\" declarator  : id_declarator\n                        | typeid_declarator\n        \"\"\"\n        p[0] = p[1]\n\n    @parameterized(('id', 'ID'), ('typeid', 'TYPEID'), ('typeid_noparen', 'TYPEID'))\n    def p_xxx_declarator_1(self, p):\n        \"\"\" xxx_declarator  : direct_xxx_declarator\n        \"\"\"\n        p[0] = p[1]\n\n    @parameterized(('id', 'ID'), ('typeid', 'TYPEID'), ('typeid_noparen', 'TYPEID'))\n    def p_xxx_declarator_2(self, p):\n        \"\"\" xxx_declarator  : pointer direct_xxx_declarator\n        \"\"\"\n        p[0] = self._type_modify_decl(p[2], p[1])\n\n    @parameterized(('id', 'ID'), ('typeid', 'TYPEID'), ('typeid_noparen', 'TYPEID'))\n    def p_direct_xxx_declarator_1(self, p):\n        \"\"\" direct_xxx_declarator   : yyy\n        \"\"\"\n        p[0] = c_ast.TypeDecl(\n            declname=p[1],\n            type=None,\n            quals=None,\n            coord=self._token_coord(p, 1))\n\n    @parameterized(('id', 'ID'), ('typeid', 'TYPEID'))\n    def p_direct_xxx_declarator_2(self, p):\n        \"\"\" direct_xxx_declarator   : LPAREN xxx_declarator RPAREN\n        \"\"\"\n        p[0] = p[2]\n\n    @parameterized(('id', 'ID'), ('typeid', 'TYPEID'), ('typeid_noparen', 'TYPEID'))\n    def p_direct_xxx_declarator_3(self, p):\n        \"\"\" direct_xxx_declarator   : direct_xxx_declarator LBRACKET type_qualifier_list_opt assignment_expression_opt RBRACKET\n        \"\"\"\n        quals = (p[3] if len(p) > 5 else []) or []\n        # Accept dimension qualifiers\n        # Per C99 6.7.5.3 p7\n        arr = c_ast.ArrayDecl(\n            type=None,\n            dim=p[4] if len(p) > 5 else p[3],\n            dim_quals=quals,\n            coord=p[1].coord)\n\n        p[0] = self._type_modify_decl(decl=p[1], modifier=arr)\n\n    @parameterized(('id', 'ID'), ('typeid', 'TYPEID'), ('typeid_noparen', 'TYPEID'))\n    def p_direct_xxx_declarator_4(self, p):\n        \"\"\" direct_xxx_declarator   : direct_xxx_declarator LBRACKET STATIC type_qualifier_list_opt assignment_expression RBRACKET\n                                    | direct_xxx_declarator LBRACKET type_qualifier_list STATIC assignment_expression RBRACKET\n        \"\"\"\n        # Using slice notation for PLY objects doesn't work in Python 3 for the\n        # version of PLY embedded with pycparser; see PLY Google Code issue 30.\n        # Work around that here by listing the two elements separately.\n        listed_quals = [item if isinstance(item, list) else [item]\n            for item in [p[3],p[4]]]\n        dim_quals = [qual for sublist in listed_quals for qual in sublist\n            if qual is not None]\n        arr = c_ast.ArrayDecl(\n            type=None,\n            dim=p[5],\n            dim_quals=dim_quals,\n            coord=p[1].coord)\n\n        p[0] = self._type_modify_decl(decl=p[1], modifier=arr)\n\n    # Special for VLAs\n    #\n    @parameterized(('id', 'ID'), ('typeid', 'TYPEID'), ('typeid_noparen', 'TYPEID'))\n    def p_direct_xxx_declarator_5(self, p):\n        \"\"\" direct_xxx_declarator   : direct_xxx_declarator LBRACKET type_qualifier_list_opt TIMES RBRACKET\n        \"\"\"\n        arr = c_ast.ArrayDecl(\n            type=None,\n            dim=c_ast.ID(p[4], self._token_coord(p, 4)),\n            dim_quals=p[3] if p[3] != None else [],\n            coord=p[1].coord)\n\n        p[0] = self._type_modify_decl(decl=p[1], modifier=arr)\n\n    @parameterized(('id', 'ID'), ('typeid', 'TYPEID'), ('typeid_noparen', 'TYPEID'))\n    def p_direct_xxx_declarator_6(self, p):\n        \"\"\" direct_xxx_declarator   : direct_xxx_declarator LPAREN parameter_type_list RPAREN\n                                    | direct_xxx_declarator LPAREN identifier_list_opt RPAREN\n        \"\"\"\n        func = c_ast.FuncDecl(\n            args=p[3],\n            type=None,\n            coord=p[1].coord)\n\n        # To see why _get_yacc_lookahead_token is needed, consider:\n        #   typedef char TT;\n        #   void foo(int TT) { TT = 10; }\n        # Outside the function, TT is a typedef, but inside (starting and\n        # ending with the braces) it's a parameter.  The trouble begins with\n        # yacc's lookahead token.  We don't know if we're declaring or\n        # defining a function until we see LBRACE, but if we wait for yacc to\n        # trigger a rule on that token, then TT will have already been read\n        # and incorrectly interpreted as TYPEID.  We need to add the\n        # parameters to the scope the moment the lexer sees LBRACE.\n        #\n        if self._get_yacc_lookahead_token().type == \"LBRACE\":\n            if func.args is not None:\n                for param in func.args.params:\n                    if isinstance(param, c_ast.EllipsisParam): break\n                    self._add_identifier(param.name, param.coord)\n\n        p[0] = self._type_modify_decl(decl=p[1], modifier=func)\n\n    def p_pointer(self, p):\n        \"\"\" pointer : TIMES type_qualifier_list_opt\n                    | TIMES type_qualifier_list_opt pointer\n        \"\"\"\n        coord = self._token_coord(p, 1)\n        # Pointer decls nest from inside out. This is important when different\n        # levels have different qualifiers. For example:\n        #\n        #  char * const * p;\n        #\n        # Means \"pointer to const pointer to char\"\n        #\n        # While:\n        #\n        #  char ** const p;\n        #\n        # Means \"const pointer to pointer to char\"\n        #\n        # So when we construct PtrDecl nestings, the leftmost pointer goes in\n        # as the most nested type.\n        nested_type = c_ast.PtrDecl(quals=p[2] or [], type=None, coord=coord)\n        if len(p) > 3:\n            tail_type = p[3]\n            while tail_type.type is not None:\n                tail_type = tail_type.type\n            tail_type.type = nested_type\n            p[0] = p[3]\n        else:\n            p[0] = nested_type\n\n    def p_type_qualifier_list(self, p):\n        \"\"\" type_qualifier_list : type_qualifier\n                                | type_qualifier_list type_qualifier\n        \"\"\"\n        p[0] = [p[1]] if len(p) == 2 else p[1] + [p[2]]\n\n    def p_parameter_type_list(self, p):\n        \"\"\" parameter_type_list : parameter_list\n                                | parameter_list COMMA ELLIPSIS\n        \"\"\"\n        if len(p) > 2:\n            p[1].params.append(c_ast.EllipsisParam(self._token_coord(p, 3)))\n\n        p[0] = p[1]\n\n    def p_parameter_list(self, p):\n        \"\"\" parameter_list  : parameter_declaration\n                            | parameter_list COMMA parameter_declaration\n        \"\"\"\n        if len(p) == 2: # single parameter\n            p[0] = c_ast.ParamList([p[1]], p[1].coord)\n        else:\n            p[1].params.append(p[3])\n            p[0] = p[1]\n\n    # From ISO/IEC 9899:TC2, 6.7.5.3.11:\n    # \"If, in a parameter declaration, an identifier can be treated either\n    #  as a typedef name or as a parameter name, it shall be taken as a\n    #  typedef name.\"\n    #\n    # Inside a parameter declaration, once we've reduced declaration specifiers,\n    # if we shift in an LPAREN and see a TYPEID, it could be either an abstract\n    # declarator or a declarator nested inside parens. This rule tells us to\n    # always treat it as an abstract declarator. Therefore, we only accept\n    # `id_declarator`s and `typeid_noparen_declarator`s.\n    def p_parameter_declaration_1(self, p):\n        \"\"\" parameter_declaration   : declaration_specifiers id_declarator\n                                    | declaration_specifiers typeid_noparen_declarator\n        \"\"\"\n        spec = p[1]\n        if not spec['type']:\n            spec['type'] = [c_ast.IdentifierType(['int'],\n                coord=self._token_coord(p, 1))]\n        p[0] = self._build_declarations(\n            spec=spec,\n            decls=[dict(decl=p[2])])[0]\n\n    def p_parameter_declaration_2(self, p):\n        \"\"\" parameter_declaration   : declaration_specifiers abstract_declarator_opt\n        \"\"\"\n        spec = p[1]\n        if not spec['type']:\n            spec['type'] = [c_ast.IdentifierType(['int'],\n                coord=self._token_coord(p, 1))]\n\n        # Parameters can have the same names as typedefs.  The trouble is that\n        # the parameter's name gets grouped into declaration_specifiers, making\n        # it look like an old-style declaration; compensate.\n        #\n        if len(spec['type']) > 1 and len(spec['type'][-1].names) == 1 and \\\n                self._is_type_in_scope(spec['type'][-1].names[0]):\n            decl = self._build_declarations(\n                    spec=spec,\n                    decls=[dict(decl=p[2], init=None)])[0]\n\n        # This truly is an old-style parameter declaration\n        #\n        else:\n            decl = c_ast.Typename(\n                name='',\n                quals=spec['qual'],\n                type=p[2] or c_ast.TypeDecl(None, None, None),\n                coord=self._token_coord(p, 2))\n            typename = spec['type']\n            decl = self._fix_decl_name_type(decl, typename)\n\n        p[0] = decl\n\n    def p_identifier_list(self, p):\n        \"\"\" identifier_list : identifier\n                            | identifier_list COMMA identifier\n        \"\"\"\n        if len(p) == 2: # single parameter\n            p[0] = c_ast.ParamList([p[1]], p[1].coord)\n        else:\n            p[1].params.append(p[3])\n            p[0] = p[1]\n\n    def p_initializer_1(self, p):\n        \"\"\" initializer : assignment_expression\n        \"\"\"\n        p[0] = p[1]\n\n    def p_initializer_2(self, p):\n        \"\"\" initializer : brace_open initializer_list_opt brace_close\n                        | brace_open initializer_list COMMA brace_close\n        \"\"\"\n        if p[2] is None:\n            p[0] = c_ast.InitList([], self._token_coord(p, 1))\n        else:\n            p[0] = p[2]\n\n    def p_initializer_list(self, p):\n        \"\"\" initializer_list    : designation_opt initializer\n                                | initializer_list COMMA designation_opt initializer\n        \"\"\"\n        if len(p) == 3: # single initializer\n            init = p[2] if p[1] is None else c_ast.NamedInitializer(p[1], p[2])\n            p[0] = c_ast.InitList([init], p[2].coord)\n        else:\n            init = p[4] if p[3] is None else c_ast.NamedInitializer(p[3], p[4])\n            p[1].exprs.append(init)\n            p[0] = p[1]\n\n    def p_designation(self, p):\n        \"\"\" designation : designator_list EQUALS\n        \"\"\"\n        p[0] = p[1]\n\n    # Designators are represented as a list of nodes, in the order in which\n    # they're written in the code.\n    #\n    def p_designator_list(self, p):\n        \"\"\" designator_list : designator\n                            | designator_list designator\n        \"\"\"\n        p[0] = [p[1]] if len(p) == 2 else p[1] + [p[2]]\n\n    def p_designator(self, p):\n        \"\"\" designator  : LBRACKET constant_expression RBRACKET\n                        | PERIOD identifier\n        \"\"\"\n        p[0] = p[2]\n\n    def p_type_name(self, p):\n        \"\"\" type_name   : specifier_qualifier_list abstract_declarator_opt\n        \"\"\"\n        typename = c_ast.Typename(\n            name='',\n            quals=p[1]['qual'],\n            type=p[2] or c_ast.TypeDecl(None, None, None),\n            coord=self._token_coord(p, 2))\n\n        p[0] = self._fix_decl_name_type(typename, p[1]['type'])\n\n    def p_abstract_declarator_1(self, p):\n        \"\"\" abstract_declarator     : pointer\n        \"\"\"\n        dummytype = c_ast.TypeDecl(None, None, None)\n        p[0] = self._type_modify_decl(\n            decl=dummytype,\n            modifier=p[1])\n\n    def p_abstract_declarator_2(self, p):\n        \"\"\" abstract_declarator     : pointer direct_abstract_declarator\n        \"\"\"\n        p[0] = self._type_modify_decl(p[2], p[1])\n\n    def p_abstract_declarator_3(self, p):\n        \"\"\" abstract_declarator     : direct_abstract_declarator\n        \"\"\"\n        p[0] = p[1]\n\n    # Creating and using direct_abstract_declarator_opt here\n    # instead of listing both direct_abstract_declarator and the\n    # lack of it in the beginning of _1 and _2 caused two\n    # shift/reduce errors.\n    #\n    def p_direct_abstract_declarator_1(self, p):\n        \"\"\" direct_abstract_declarator  : LPAREN abstract_declarator RPAREN \"\"\"\n        p[0] = p[2]\n\n    def p_direct_abstract_declarator_2(self, p):\n        \"\"\" direct_abstract_declarator  : direct_abstract_declarator LBRACKET assignment_expression_opt RBRACKET\n        \"\"\"\n        arr = c_ast.ArrayDecl(\n            type=None,\n            dim=p[3],\n            dim_quals=[],\n            coord=p[1].coord)\n\n        p[0] = self._type_modify_decl(decl=p[1], modifier=arr)\n\n    def p_direct_abstract_declarator_3(self, p):\n        \"\"\" direct_abstract_declarator  : LBRACKET assignment_expression_opt RBRACKET\n        \"\"\"\n        p[0] = c_ast.ArrayDecl(\n            type=c_ast.TypeDecl(None, None, None),\n            dim=p[2],\n            dim_quals=[],\n            coord=self._token_coord(p, 1))\n\n    def p_direct_abstract_declarator_4(self, p):\n        \"\"\" direct_abstract_declarator  : direct_abstract_declarator LBRACKET TIMES RBRACKET\n        \"\"\"\n        arr = c_ast.ArrayDecl(\n            type=None,\n            dim=c_ast.ID(p[3], self._token_coord(p, 3)),\n            dim_quals=[],\n            coord=p[1].coord)\n\n        p[0] = self._type_modify_decl(decl=p[1], modifier=arr)\n\n    def p_direct_abstract_declarator_5(self, p):\n        \"\"\" direct_abstract_declarator  : LBRACKET TIMES RBRACKET\n        \"\"\"\n        p[0] = c_ast.ArrayDecl(\n            type=c_ast.TypeDecl(None, None, None),\n            dim=c_ast.ID(p[3], self._token_coord(p, 3)),\n            dim_quals=[],\n            coord=self._token_coord(p, 1))\n\n    def p_direct_abstract_declarator_6(self, p):\n        \"\"\" direct_abstract_declarator  : direct_abstract_declarator LPAREN parameter_type_list_opt RPAREN\n        \"\"\"\n        func = c_ast.FuncDecl(\n            args=p[3],\n            type=None,\n            coord=p[1].coord)\n\n        p[0] = self._type_modify_decl(decl=p[1], modifier=func)\n\n    def p_direct_abstract_declarator_7(self, p):\n        \"\"\" direct_abstract_declarator  : LPAREN parameter_type_list_opt RPAREN\n        \"\"\"\n        p[0] = c_ast.FuncDecl(\n            args=p[2],\n            type=c_ast.TypeDecl(None, None, None),\n            coord=self._token_coord(p, 1))\n\n    # declaration is a list, statement isn't. To make it consistent, block_item\n    # will always be a list\n    #\n    def p_block_item(self, p):\n        \"\"\" block_item  : declaration\n                        | statement\n        \"\"\"\n        p[0] = p[1] if isinstance(p[1], list) else [p[1]]\n\n    # Since we made block_item a list, this just combines lists\n    #\n    def p_block_item_list(self, p):\n        \"\"\" block_item_list : block_item\n                            | block_item_list block_item\n        \"\"\"\n        # Empty block items (plain ';') produce [None], so ignore them\n        p[0] = p[1] if (len(p) == 2 or p[2] == [None]) else p[1] + p[2]\n\n    def p_compound_statement_1(self, p):\n        \"\"\" compound_statement : brace_open block_item_list_opt brace_close \"\"\"\n        p[0] = c_ast.Compound(\n            block_items=p[2],\n            coord=self._token_coord(p, 1))\n\n    def p_labeled_statement_1(self, p):\n        \"\"\" labeled_statement : ID COLON pragmacomp_or_statement \"\"\"\n        p[0] = c_ast.Label(p[1], p[3], self._token_coord(p, 1))\n\n    def p_labeled_statement_2(self, p):\n        \"\"\" labeled_statement : CASE constant_expression COLON pragmacomp_or_statement \"\"\"\n        p[0] = c_ast.Case(p[2], [p[4]], self._token_coord(p, 1))\n\n    def p_labeled_statement_3(self, p):\n        \"\"\" labeled_statement : DEFAULT COLON pragmacomp_or_statement \"\"\"\n        p[0] = c_ast.Default([p[3]], self._token_coord(p, 1))\n\n    def p_selection_statement_1(self, p):\n        \"\"\" selection_statement : IF LPAREN expression RPAREN pragmacomp_or_statement \"\"\"\n        p[0] = c_ast.If(p[3], p[5], None, self._token_coord(p, 1))\n\n    def p_selection_statement_2(self, p):\n        \"\"\" selection_statement : IF LPAREN expression RPAREN statement ELSE pragmacomp_or_statement \"\"\"\n        p[0] = c_ast.If(p[3], p[5], p[7], self._token_coord(p, 1))\n\n    def p_selection_statement_3(self, p):\n        \"\"\" selection_statement : SWITCH LPAREN expression RPAREN pragmacomp_or_statement \"\"\"\n        p[0] = fix_switch_cases(\n                c_ast.Switch(p[3], p[5], self._token_coord(p, 1)))\n\n    def p_iteration_statement_1(self, p):\n        \"\"\" iteration_statement : WHILE LPAREN expression RPAREN pragmacomp_or_statement \"\"\"\n        p[0] = c_ast.While(p[3], p[5], self._token_coord(p, 1))\n\n    def p_iteration_statement_2(self, p):\n        \"\"\" iteration_statement : DO pragmacomp_or_statement WHILE LPAREN expression RPAREN SEMI \"\"\"\n        p[0] = c_ast.DoWhile(p[5], p[2], self._token_coord(p, 1))\n\n    def p_iteration_statement_3(self, p):\n        \"\"\" iteration_statement : FOR LPAREN expression_opt SEMI expression_opt SEMI expression_opt RPAREN pragmacomp_or_statement \"\"\"\n        p[0] = c_ast.For(p[3], p[5], p[7], p[9], self._token_coord(p, 1))\n\n    def p_iteration_statement_4(self, p):\n        \"\"\" iteration_statement : FOR LPAREN declaration expression_opt SEMI expression_opt RPAREN pragmacomp_or_statement \"\"\"\n        p[0] = c_ast.For(c_ast.DeclList(p[3], self._token_coord(p, 1)),\n                         p[4], p[6], p[8], self._token_coord(p, 1))\n\n    def p_jump_statement_1(self, p):\n        \"\"\" jump_statement  : GOTO ID SEMI \"\"\"\n        p[0] = c_ast.Goto(p[2], self._token_coord(p, 1))\n\n    def p_jump_statement_2(self, p):\n        \"\"\" jump_statement  : BREAK SEMI \"\"\"\n        p[0] = c_ast.Break(self._token_coord(p, 1))\n\n    def p_jump_statement_3(self, p):\n        \"\"\" jump_statement  : CONTINUE SEMI \"\"\"\n        p[0] = c_ast.Continue(self._token_coord(p, 1))\n\n    def p_jump_statement_4(self, p):\n        \"\"\" jump_statement  : RETURN expression SEMI\n                            | RETURN SEMI\n        \"\"\"\n        p[0] = c_ast.Return(p[2] if len(p) == 4 else None, self._token_coord(p, 1))\n\n    def p_expression_statement(self, p):\n        \"\"\" expression_statement : expression_opt SEMI \"\"\"\n        if p[1] is None:\n            p[0] = c_ast.EmptyStatement(self._token_coord(p, 2))\n        else:\n            p[0] = p[1]\n\n    def p_expression(self, p):\n        \"\"\" expression  : assignment_expression\n                        | expression COMMA assignment_expression\n        \"\"\"\n        if len(p) == 2:\n            p[0] = p[1]\n        else:\n            if not isinstance(p[1], c_ast.ExprList):\n                p[1] = c_ast.ExprList([p[1]], p[1].coord)\n\n            p[1].exprs.append(p[3])\n            p[0] = p[1]\n\n    def p_typedef_name(self, p):\n        \"\"\" typedef_name : TYPEID \"\"\"\n        p[0] = c_ast.IdentifierType([p[1]], coord=self._token_coord(p, 1))\n\n    def p_assignment_expression(self, p):\n        \"\"\" assignment_expression   : conditional_expression\n                                    | unary_expression assignment_operator assignment_expression\n        \"\"\"\n        if len(p) == 2:\n            p[0] = p[1]\n        else:\n            p[0] = c_ast.Assignment(p[2], p[1], p[3], p[1].coord)\n\n    # K&R2 defines these as many separate rules, to encode\n    # precedence and associativity. Why work hard ? I'll just use\n    # the built in precedence/associativity specification feature\n    # of PLY. (see precedence declaration above)\n    #\n    def p_assignment_operator(self, p):\n        \"\"\" assignment_operator : EQUALS\n                                | XOREQUAL\n                                | TIMESEQUAL\n                                | DIVEQUAL\n                                | MODEQUAL\n                                | PLUSEQUAL\n                                | MINUSEQUAL\n                                | LSHIFTEQUAL\n                                | RSHIFTEQUAL\n                                | ANDEQUAL\n                                | OREQUAL\n        \"\"\"\n        p[0] = p[1]\n\n    def p_constant_expression(self, p):\n        \"\"\" constant_expression : conditional_expression \"\"\"\n        p[0] = p[1]\n\n    def p_conditional_expression(self, p):\n        \"\"\" conditional_expression  : binary_expression\n                                    | binary_expression CONDOP expression COLON conditional_expression\n        \"\"\"\n        if len(p) == 2:\n            p[0] = p[1]\n        else:\n            p[0] = c_ast.TernaryOp(p[1], p[3], p[5], p[1].coord)\n\n    def p_binary_expression(self, p):\n        \"\"\" binary_expression   : cast_expression\n                                | binary_expression TIMES binary_expression\n                                | binary_expression DIVIDE binary_expression\n                                | binary_expression MOD binary_expression\n                                | binary_expression PLUS binary_expression\n                                | binary_expression MINUS binary_expression\n                                | binary_expression RSHIFT binary_expression\n                                | binary_expression LSHIFT binary_expression\n                                | binary_expression LT binary_expression\n                                | binary_expression LE binary_expression\n                                | binary_expression GE binary_expression\n                                | binary_expression GT binary_expression\n                                | binary_expression EQ binary_expression\n                                | binary_expression NE binary_expression\n                                | binary_expression AND binary_expression\n                                | binary_expression OR binary_expression\n                                | binary_expression XOR binary_expression\n                                | binary_expression LAND binary_expression\n                                | binary_expression LOR binary_expression\n        \"\"\"\n        if len(p) == 2:\n            p[0] = p[1]\n        else:\n            p[0] = c_ast.BinaryOp(p[2], p[1], p[3], p[1].coord)\n\n    def p_cast_expression_1(self, p):\n        \"\"\" cast_expression : unary_expression \"\"\"\n        p[0] = p[1]\n\n    def p_cast_expression_2(self, p):\n        \"\"\" cast_expression : LPAREN type_name RPAREN cast_expression \"\"\"\n        p[0] = c_ast.Cast(p[2], p[4], self._token_coord(p, 1))\n\n    def p_unary_expression_1(self, p):\n        \"\"\" unary_expression    : postfix_expression \"\"\"\n        p[0] = p[1]\n\n    def p_unary_expression_2(self, p):\n        \"\"\" unary_expression    : PLUSPLUS unary_expression\n                                | MINUSMINUS unary_expression\n                                | unary_operator cast_expression\n        \"\"\"\n        p[0] = c_ast.UnaryOp(p[1], p[2], p[2].coord)\n\n    def p_unary_expression_3(self, p):\n        \"\"\" unary_expression    : SIZEOF unary_expression\n                                | SIZEOF LPAREN type_name RPAREN\n        \"\"\"\n        p[0] = c_ast.UnaryOp(\n            p[1],\n            p[2] if len(p) == 3 else p[3],\n            self._token_coord(p, 1))\n\n    def p_unary_operator(self, p):\n        \"\"\" unary_operator  : AND\n                            | TIMES\n                            | PLUS\n                            | MINUS\n                            | NOT\n                            | LNOT\n        \"\"\"\n        p[0] = p[1]\n\n    def p_postfix_expression_1(self, p):\n        \"\"\" postfix_expression  : primary_expression \"\"\"\n        p[0] = p[1]\n\n    def p_postfix_expression_2(self, p):\n        \"\"\" postfix_expression  : postfix_expression LBRACKET expression RBRACKET \"\"\"\n        p[0] = c_ast.ArrayRef(p[1], p[3], p[1].coord)\n\n    def p_postfix_expression_3(self, p):\n        \"\"\" postfix_expression  : postfix_expression LPAREN argument_expression_list RPAREN\n                                | postfix_expression LPAREN RPAREN\n        \"\"\"\n        p[0] = c_ast.FuncCall(p[1], p[3] if len(p) == 5 else None, p[1].coord)\n\n    def p_postfix_expression_4(self, p):\n        \"\"\" postfix_expression  : postfix_expression PERIOD ID\n                                | postfix_expression PERIOD TYPEID\n                                | postfix_expression ARROW ID\n                                | postfix_expression ARROW TYPEID\n        \"\"\"\n        field = c_ast.ID(p[3], self._token_coord(p, 3))\n        p[0] = c_ast.StructRef(p[1], p[2], field, p[1].coord)\n\n    def p_postfix_expression_5(self, p):\n        \"\"\" postfix_expression  : postfix_expression PLUSPLUS\n                                | postfix_expression MINUSMINUS\n        \"\"\"\n        p[0] = c_ast.UnaryOp('p' + p[2], p[1], p[1].coord)\n\n    def p_postfix_expression_6(self, p):\n        \"\"\" postfix_expression  : LPAREN type_name RPAREN brace_open initializer_list brace_close\n                                | LPAREN type_name RPAREN brace_open initializer_list COMMA brace_close\n        \"\"\"\n        p[0] = c_ast.CompoundLiteral(p[2], p[5])\n\n    def p_primary_expression_1(self, p):\n        \"\"\" primary_expression  : identifier \"\"\"\n        p[0] = p[1]\n\n    def p_primary_expression_2(self, p):\n        \"\"\" primary_expression  : constant \"\"\"\n        p[0] = p[1]\n\n    def p_primary_expression_3(self, p):\n        \"\"\" primary_expression  : unified_string_literal\n                                | unified_wstring_literal\n        \"\"\"\n        p[0] = p[1]\n\n    def p_primary_expression_4(self, p):\n        \"\"\" primary_expression  : LPAREN expression RPAREN \"\"\"\n        p[0] = p[2]\n\n    def p_primary_expression_5(self, p):\n        \"\"\" primary_expression  : OFFSETOF LPAREN type_name COMMA offsetof_member_designator RPAREN\n        \"\"\"\n        coord = self._token_coord(p, 1)\n        p[0] = c_ast.FuncCall(c_ast.ID(p[1], coord),\n                              c_ast.ExprList([p[3], p[5]], coord),\n                              coord)\n\n    def p_offsetof_member_designator(self, p):\n        \"\"\" offsetof_member_designator : identifier\n                                         | offsetof_member_designator PERIOD identifier\n                                         | offsetof_member_designator LBRACKET expression RBRACKET\n        \"\"\"\n        if len(p) == 2:\n            p[0] = p[1]\n        elif len(p) == 4:\n            field = c_ast.ID(p[3], self._token_coord(p, 3))\n            p[0] = c_ast.StructRef(p[1], p[2], field, p[1].coord)\n        elif len(p) == 5:\n            p[0] = c_ast.ArrayRef(p[1], p[3], p[1].coord)\n        else:\n            raise NotImplementedError(\"Unexpected parsing state. len(p): %u\" % len(p))\n\n    def p_argument_expression_list(self, p):\n        \"\"\" argument_expression_list    : assignment_expression\n                                        | argument_expression_list COMMA assignment_expression\n        \"\"\"\n        if len(p) == 2: # single expr\n            p[0] = c_ast.ExprList([p[1]], p[1].coord)\n        else:\n            p[1].exprs.append(p[3])\n            p[0] = p[1]\n\n    def p_identifier(self, p):\n        \"\"\" identifier  : ID \"\"\"\n        p[0] = c_ast.ID(p[1], self._token_coord(p, 1))\n\n    def p_constant_1(self, p):\n        \"\"\" constant    : INT_CONST_DEC\n                        | INT_CONST_OCT\n                        | INT_CONST_HEX\n                        | INT_CONST_BIN\n        \"\"\"\n        p[0] = c_ast.Constant(\n            'int', p[1], self._token_coord(p, 1))\n\n    def p_constant_2(self, p):\n        \"\"\" constant    : FLOAT_CONST\n                        | HEX_FLOAT_CONST\n        \"\"\"\n        if 'x' in p[1].lower():\n            t = 'float'\n        else:\n            if p[1][-1] in ('f', 'F'):\n                t = 'float'\n            elif p[1][-1] in ('l', 'L'):\n                t = 'long double'\n            else:\n                t = 'double'\n\n        p[0] = c_ast.Constant(\n            t, p[1], self._token_coord(p, 1))\n\n    def p_constant_3(self, p):\n        \"\"\" constant    : CHAR_CONST\n                        | WCHAR_CONST\n        \"\"\"\n        p[0] = c_ast.Constant(\n            'char', p[1], self._token_coord(p, 1))\n\n    # The \"unified\" string and wstring literal rules are for supporting\n    # concatenation of adjacent string literals.\n    # I.e. \"hello \" \"world\" is seen by the C compiler as a single string literal\n    # with the value \"hello world\"\n    #\n    def p_unified_string_literal(self, p):\n        \"\"\" unified_string_literal  : STRING_LITERAL\n                                    | unified_string_literal STRING_LITERAL\n        \"\"\"\n        if len(p) == 2: # single literal\n            p[0] = c_ast.Constant(\n                'string', p[1], self._token_coord(p, 1))\n        else:\n            p[1].value = p[1].value[:-1] + p[2][1:]\n            p[0] = p[1]\n\n    def p_unified_wstring_literal(self, p):\n        \"\"\" unified_wstring_literal : WSTRING_LITERAL\n                                    | unified_wstring_literal WSTRING_LITERAL\n        \"\"\"\n        if len(p) == 2: # single literal\n            p[0] = c_ast.Constant(\n                'string', p[1], self._token_coord(p, 1))\n        else:\n            p[1].value = p[1].value.rstrip()[:-1] + p[2][2:]\n            p[0] = p[1]\n\n    def p_brace_open(self, p):\n        \"\"\" brace_open  :   LBRACE\n        \"\"\"\n        p[0] = p[1]\n        p.set_lineno(0, p.lineno(1))\n\n    def p_brace_close(self, p):\n        \"\"\" brace_close :   RBRACE\n        \"\"\"\n        p[0] = p[1]\n        p.set_lineno(0, p.lineno(1))\n\n    def p_empty(self, p):\n        'empty : '\n        p[0] = None\n\n    def p_error(self, p):\n        # If error recovery is added here in the future, make sure\n        # _get_yacc_lookahead_token still works!\n        #\n        if p:\n            self._parse_error(\n                'before: %s' % p.value,\n                self._coord(lineno=p.lineno,\n                            column=self.clex.find_tok_column(p)))\n        else:\n            self._parse_error('At end of input', self.clex.filename)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/lextab.py",
    "content": "# lextab.py. This file automatically created by PLY (version 3.10). Don't edit!\n_tabversion   = '3.10'\n_lextokens    = set(('VOID', 'LBRACKET', 'WCHAR_CONST', 'FLOAT_CONST', 'MINUS', 'RPAREN', 'LONG', 'PLUS', 'ELLIPSIS', 'GT', 'GOTO', 'ENUM', 'PERIOD', 'GE', 'INT_CONST_DEC', 'ARROW', '__INT128', 'HEX_FLOAT_CONST', 'DOUBLE', 'MINUSEQUAL', 'INT_CONST_OCT', 'TIMESEQUAL', 'OR', 'SHORT', 'RETURN', 'RSHIFTEQUAL', 'RESTRICT', 'STATIC', 'SIZEOF', 'UNSIGNED', 'UNION', 'COLON', 'WSTRING_LITERAL', 'DIVIDE', 'FOR', 'PLUSPLUS', 'EQUALS', 'ELSE', 'INLINE', 'EQ', 'AND', 'TYPEID', 'LBRACE', 'PPHASH', 'INT', 'SIGNED', 'CONTINUE', 'NOT', 'OREQUAL', 'MOD', 'RSHIFT', 'DEFAULT', 'CHAR', 'WHILE', 'DIVEQUAL', 'EXTERN', 'CASE', 'LAND', 'REGISTER', 'MODEQUAL', 'NE', 'SWITCH', 'INT_CONST_HEX', '_COMPLEX', 'PPPRAGMASTR', 'PLUSEQUAL', 'STRUCT', 'CONDOP', 'BREAK', 'VOLATILE', 'PPPRAGMA', 'ANDEQUAL', 'INT_CONST_BIN', 'DO', 'LNOT', 'CONST', 'LOR', 'CHAR_CONST', 'LSHIFT', 'RBRACE', '_BOOL', 'LE', 'SEMI', 'LT', 'COMMA', 'OFFSETOF', 'TYPEDEF', 'XOR', 'AUTO', 'TIMES', 'LPAREN', 'MINUSMINUS', 'ID', 'IF', 'STRING_LITERAL', 'FLOAT', 'XOREQUAL', 'LSHIFTEQUAL', 'RBRACKET'))\n_lexreflags   = 64\n_lexliterals  = ''\n_lexstateinfo = {'ppline': 'exclusive', 'pppragma': 'exclusive', 'INITIAL': 'inclusive'}\n_lexstatere   = {'ppline': [('(?P<t_ppline_FILENAME>\"([^\"\\\\\\\\\\\\n]|(\\\\\\\\(([a-zA-Z._~!=&\\\\^\\\\-\\\\\\\\?\\'\"])|(\\\\d+)|(x[0-9a-fA-F]+))))*\")|(?P<t_ppline_LINE_NUMBER>(0(([uU]ll)|([uU]LL)|(ll[uU]?)|(LL[uU]?)|([uU][lL])|([lL][uU]?)|[uU])?)|([1-9][0-9]*(([uU]ll)|([uU]LL)|(ll[uU]?)|(LL[uU]?)|([uU][lL])|([lL][uU]?)|[uU])?))|(?P<t_ppline_NEWLINE>\\\\n)|(?P<t_ppline_PPLINE>line)', [None, ('t_ppline_FILENAME', 'FILENAME'), None, None, None, None, None, None, ('t_ppline_LINE_NUMBER', 'LINE_NUMBER'), None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, ('t_ppline_NEWLINE', 'NEWLINE'), ('t_ppline_PPLINE', 'PPLINE')])], 'pppragma': [('(?P<t_pppragma_NEWLINE>\\\\n)|(?P<t_pppragma_PPPRAGMA>pragma)|(?P<t_pppragma_STR>.+)', [None, ('t_pppragma_NEWLINE', 'NEWLINE'), ('t_pppragma_PPPRAGMA', 'PPPRAGMA'), ('t_pppragma_STR', 'STR')])], 'INITIAL': [('(?P<t_PPHASH>[ \\\\t]*\\\\#)|(?P<t_NEWLINE>\\\\n+)|(?P<t_LBRACE>\\\\{)|(?P<t_RBRACE>\\\\})|(?P<t_FLOAT_CONST>((((([0-9]*\\\\.[0-9]+)|([0-9]+\\\\.))([eE][-+]?[0-9]+)?)|([0-9]+([eE][-+]?[0-9]+)))[FfLl]?))|(?P<t_HEX_FLOAT_CONST>(0[xX]([0-9a-fA-F]+|((([0-9a-fA-F]+)?\\\\.[0-9a-fA-F]+)|([0-9a-fA-F]+\\\\.)))([pP][+-]?[0-9]+)[FfLl]?))|(?P<t_INT_CONST_HEX>0[xX][0-9a-fA-F]+(([uU]ll)|([uU]LL)|(ll[uU]?)|(LL[uU]?)|([uU][lL])|([lL][uU]?)|[uU])?)', [None, ('t_PPHASH', 'PPHASH'), ('t_NEWLINE', 'NEWLINE'), ('t_LBRACE', 'LBRACE'), ('t_RBRACE', 'RBRACE'), ('t_FLOAT_CONST', 'FLOAT_CONST'), None, None, None, None, None, None, None, None, None, ('t_HEX_FLOAT_CONST', 'HEX_FLOAT_CONST'), None, None, None, None, None, None, None, ('t_INT_CONST_HEX', 'INT_CONST_HEX')]), ('(?P<t_INT_CONST_BIN>0[bB][01]+(([uU]ll)|([uU]LL)|(ll[uU]?)|(LL[uU]?)|([uU][lL])|([lL][uU]?)|[uU])?)|(?P<t_BAD_CONST_OCT>0[0-7]*[89])|(?P<t_INT_CONST_OCT>0[0-7]*(([uU]ll)|([uU]LL)|(ll[uU]?)|(LL[uU]?)|([uU][lL])|([lL][uU]?)|[uU])?)|(?P<t_INT_CONST_DEC>(0(([uU]ll)|([uU]LL)|(ll[uU]?)|(LL[uU]?)|([uU][lL])|([lL][uU]?)|[uU])?)|([1-9][0-9]*(([uU]ll)|([uU]LL)|(ll[uU]?)|(LL[uU]?)|([uU][lL])|([lL][uU]?)|[uU])?))|(?P<t_CHAR_CONST>\\'([^\\'\\\\\\\\\\\\n]|(\\\\\\\\(([a-zA-Z._~!=&\\\\^\\\\-\\\\\\\\?\\'\"])|(\\\\d+)|(x[0-9a-fA-F]+))))\\')|(?P<t_WCHAR_CONST>L\\'([^\\'\\\\\\\\\\\\n]|(\\\\\\\\(([a-zA-Z._~!=&\\\\^\\\\-\\\\\\\\?\\'\"])|(\\\\d+)|(x[0-9a-fA-F]+))))\\')|(?P<t_UNMATCHED_QUOTE>(\\'([^\\'\\\\\\\\\\\\n]|(\\\\\\\\(([a-zA-Z._~!=&\\\\^\\\\-\\\\\\\\?\\'\"])|(\\\\d+)|(x[0-9a-fA-F]+))))*\\\\n)|(\\'([^\\'\\\\\\\\\\\\n]|(\\\\\\\\(([a-zA-Z._~!=&\\\\^\\\\-\\\\\\\\?\\'\"])|(\\\\d+)|(x[0-9a-fA-F]+))))*$))|(?P<t_BAD_CHAR_CONST>(\\'([^\\'\\\\\\\\\\\\n]|(\\\\\\\\(([a-zA-Z._~!=&\\\\^\\\\-\\\\\\\\?\\'\"])|(\\\\d+)|(x[0-9a-fA-F]+))))[^\\'\\n]+\\')|(\\'\\')|(\\'([\\\\\\\\][^a-zA-Z._~^!=&\\\\^\\\\-\\\\\\\\?\\'\"x0-7])[^\\'\\\\n]*\\'))', [None, ('t_INT_CONST_BIN', 'INT_CONST_BIN'), None, None, None, None, None, None, None, ('t_BAD_CONST_OCT', 'BAD_CONST_OCT'), ('t_INT_CONST_OCT', 'INT_CONST_OCT'), None, None, None, None, None, None, None, ('t_INT_CONST_DEC', 'INT_CONST_DEC'), None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, ('t_CHAR_CONST', 'CHAR_CONST'), None, None, None, None, None, None, ('t_WCHAR_CONST', 'WCHAR_CONST'), None, None, None, None, None, None, ('t_UNMATCHED_QUOTE', 'UNMATCHED_QUOTE'), None, None, None, None, None, None, None, None, None, None, None, None, None, None, ('t_BAD_CHAR_CONST', 'BAD_CHAR_CONST')]), ('(?P<t_WSTRING_LITERAL>L\"([^\"\\\\\\\\\\\\n]|(\\\\\\\\(([a-zA-Z._~!=&\\\\^\\\\-\\\\\\\\?\\'\"])|(\\\\d+)|(x[0-9a-fA-F]+))))*\")|(?P<t_BAD_STRING_LITERAL>\"([^\"\\\\\\\\\\\\n]|(\\\\\\\\(([a-zA-Z._~!=&\\\\^\\\\-\\\\\\\\?\\'\"])|(\\\\d+)|(x[0-9a-fA-F]+))))*?([\\\\\\\\][^a-zA-Z._~^!=&\\\\^\\\\-\\\\\\\\?\\'\"x0-7])([^\"\\\\\\\\\\\\n]|(\\\\\\\\(([a-zA-Z._~!=&\\\\^\\\\-\\\\\\\\?\\'\"])|(\\\\d+)|(x[0-9a-fA-F]+))))*\")|(?P<t_ID>[a-zA-Z_$][0-9a-zA-Z_$]*)|(?P<t_STRING_LITERAL>\"([^\"\\\\\\\\\\\\n]|(\\\\\\\\(([a-zA-Z._~!=&\\\\^\\\\-\\\\\\\\?\\'\"])|(\\\\d+)|(x[0-9a-fA-F]+))))*\")|(?P<t_ELLIPSIS>\\\\.\\\\.\\\\.)|(?P<t_PLUSPLUS>\\\\+\\\\+)|(?P<t_LOR>\\\\|\\\\|)|(?P<t_XOREQUAL>\\\\^=)|(?P<t_OREQUAL>\\\\|=)|(?P<t_LSHIFTEQUAL><<=)|(?P<t_RSHIFTEQUAL>>>=)|(?P<t_PLUSEQUAL>\\\\+=)|(?P<t_TIMESEQUAL>\\\\*=)|(?P<t_PLUS>\\\\+)|(?P<t_MODEQUAL>%=)|(?P<t_DIVEQUAL>/=)', [None, ('t_WSTRING_LITERAL', 'WSTRING_LITERAL'), None, None, None, None, None, None, ('t_BAD_STRING_LITERAL', 'BAD_STRING_LITERAL'), None, None, None, None, None, None, None, None, None, None, None, None, None, ('t_ID', 'ID'), (None, 'STRING_LITERAL'), None, None, None, None, None, None, (None, 'ELLIPSIS'), (None, 'PLUSPLUS'), (None, 'LOR'), (None, 'XOREQUAL'), (None, 'OREQUAL'), (None, 'LSHIFTEQUAL'), (None, 'RSHIFTEQUAL'), (None, 'PLUSEQUAL'), (None, 'TIMESEQUAL'), (None, 'PLUS'), (None, 'MODEQUAL'), (None, 'DIVEQUAL')]), ('(?P<t_RBRACKET>\\\\])|(?P<t_CONDOP>\\\\?)|(?P<t_XOR>\\\\^)|(?P<t_LSHIFT><<)|(?P<t_LE><=)|(?P<t_LPAREN>\\\\()|(?P<t_ARROW>->)|(?P<t_EQ>==)|(?P<t_NE>!=)|(?P<t_MINUSMINUS>--)|(?P<t_OR>\\\\|)|(?P<t_TIMES>\\\\*)|(?P<t_LBRACKET>\\\\[)|(?P<t_GE>>=)|(?P<t_RPAREN>\\\\))|(?P<t_LAND>&&)|(?P<t_RSHIFT>>>)|(?P<t_MINUSEQUAL>-=)|(?P<t_PERIOD>\\\\.)|(?P<t_ANDEQUAL>&=)|(?P<t_EQUALS>=)|(?P<t_LT><)|(?P<t_COMMA>,)|(?P<t_DIVIDE>/)|(?P<t_AND>&)|(?P<t_MOD>%)|(?P<t_SEMI>;)|(?P<t_MINUS>-)|(?P<t_GT>>)|(?P<t_COLON>:)|(?P<t_NOT>~)|(?P<t_LNOT>!)', [None, (None, 'RBRACKET'), (None, 'CONDOP'), (None, 'XOR'), (None, 'LSHIFT'), (None, 'LE'), (None, 'LPAREN'), (None, 'ARROW'), (None, 'EQ'), (None, 'NE'), (None, 'MINUSMINUS'), (None, 'OR'), (None, 'TIMES'), (None, 'LBRACKET'), (None, 'GE'), (None, 'RPAREN'), (None, 'LAND'), (None, 'RSHIFT'), (None, 'MINUSEQUAL'), (None, 'PERIOD'), (None, 'ANDEQUAL'), (None, 'EQUALS'), (None, 'LT'), (None, 'COMMA'), (None, 'DIVIDE'), (None, 'AND'), (None, 'MOD'), (None, 'SEMI'), (None, 'MINUS'), (None, 'GT'), (None, 'COLON'), (None, 'NOT'), (None, 'LNOT')])]}\n_lexstateignore = {'ppline': ' \\t', 'pppragma': ' \\t', 'INITIAL': ' \\t'}\n_lexstateerrorf = {'ppline': 't_ppline_error', 'pppragma': 't_pppragma_error', 'INITIAL': 't_error'}\n_lexstateeoff = {}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/ply/__init__.py",
    "content": "# PLY package\n# Author: David Beazley (dave@dabeaz.com)\n\n__version__ = '3.9'\n__all__ = ['lex','yacc']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/ply/cpp.py",
    "content": "# -----------------------------------------------------------------------------\n# cpp.py\n#\n# Author:  David Beazley (http://www.dabeaz.com)\n# Copyright (C) 2017\n# All rights reserved\n#\n# This module implements an ANSI-C style lexical preprocessor for PLY.\n# -----------------------------------------------------------------------------\nimport sys\n\n# Some Python 3 compatibility shims\nif sys.version_info.major < 3:\n    STRING_TYPES = (str, unicode)\nelse:\n    STRING_TYPES = str\n    xrange = range\n\n# -----------------------------------------------------------------------------\n# Default preprocessor lexer definitions.   These tokens are enough to get\n# a basic preprocessor working.   Other modules may import these if they want\n# -----------------------------------------------------------------------------\n\ntokens = (\n   'CPP_ID','CPP_INTEGER', 'CPP_FLOAT', 'CPP_STRING', 'CPP_CHAR', 'CPP_WS', 'CPP_COMMENT1', 'CPP_COMMENT2', 'CPP_POUND','CPP_DPOUND'\n)\n\nliterals = \"+-*/%|&~^<>=!?()[]{}.,;:\\\\\\'\\\"\"\n\n# Whitespace\ndef t_CPP_WS(t):\n    r'\\s+'\n    t.lexer.lineno += t.value.count(\"\\n\")\n    return t\n\nt_CPP_POUND = r'\\#'\nt_CPP_DPOUND = r'\\#\\#'\n\n# Identifier\nt_CPP_ID = r'[A-Za-z_][\\w_]*'\n\n# Integer literal\ndef CPP_INTEGER(t):\n    r'(((((0x)|(0X))[0-9a-fA-F]+)|(\\d+))([uU][lL]|[lL][uU]|[uU]|[lL])?)'\n    return t\n\nt_CPP_INTEGER = CPP_INTEGER\n\n# Floating literal\nt_CPP_FLOAT = r'((\\d+)(\\.\\d+)(e(\\+|-)?(\\d+))? | (\\d+)e(\\+|-)?(\\d+))([lL]|[fF])?'\n\n# String literal\ndef t_CPP_STRING(t):\n    r'\\\"([^\\\\\\n]|(\\\\(.|\\n)))*?\\\"'\n    t.lexer.lineno += t.value.count(\"\\n\")\n    return t\n\n# Character constant 'c' or L'c'\ndef t_CPP_CHAR(t):\n    r'(L)?\\'([^\\\\\\n]|(\\\\(.|\\n)))*?\\''\n    t.lexer.lineno += t.value.count(\"\\n\")\n    return t\n\n# Comment\ndef t_CPP_COMMENT1(t):\n    r'(/\\*(.|\\n)*?\\*/)'\n    ncr = t.value.count(\"\\n\")\n    t.lexer.lineno += ncr\n    # replace with one space or a number of '\\n'\n    t.type = 'CPP_WS'; t.value = '\\n' * ncr if ncr else ' '\n    return t\n\n# Line comment\ndef t_CPP_COMMENT2(t):\n    r'(//.*?(\\n|$))'\n    # replace with '/n'\n    t.type = 'CPP_WS'; t.value = '\\n'\n    return t\n\ndef t_error(t):\n    t.type = t.value[0]\n    t.value = t.value[0]\n    t.lexer.skip(1)\n    return t\n\nimport re\nimport copy\nimport time\nimport os.path\n\n# -----------------------------------------------------------------------------\n# trigraph()\n#\n# Given an input string, this function replaces all trigraph sequences.\n# The following mapping is used:\n#\n#     ??=    #\n#     ??/    \\\n#     ??'    ^\n#     ??(    [\n#     ??)    ]\n#     ??!    |\n#     ??<    {\n#     ??>    }\n#     ??-    ~\n# -----------------------------------------------------------------------------\n\n_trigraph_pat = re.compile(r'''\\?\\?[=/\\'\\(\\)\\!<>\\-]''')\n_trigraph_rep = {\n    '=':'#',\n    '/':'\\\\',\n    \"'\":'^',\n    '(':'[',\n    ')':']',\n    '!':'|',\n    '<':'{',\n    '>':'}',\n    '-':'~'\n}\n\ndef trigraph(input):\n    return _trigraph_pat.sub(lambda g: _trigraph_rep[g.group()[-1]],input)\n\n# ------------------------------------------------------------------\n# Macro object\n#\n# This object holds information about preprocessor macros\n#\n#    .name      - Macro name (string)\n#    .value     - Macro value (a list of tokens)\n#    .arglist   - List of argument names\n#    .variadic  - Boolean indicating whether or not variadic macro\n#    .vararg    - Name of the variadic parameter\n#\n# When a macro is created, the macro replacement token sequence is\n# pre-scanned and used to create patch lists that are later used\n# during macro expansion\n# ------------------------------------------------------------------\n\nclass Macro(object):\n    def __init__(self,name,value,arglist=None,variadic=False):\n        self.name = name\n        self.value = value\n        self.arglist = arglist\n        self.variadic = variadic\n        if variadic:\n            self.vararg = arglist[-1]\n        self.source = None\n\n# ------------------------------------------------------------------\n# Preprocessor object\n#\n# Object representing a preprocessor.  Contains macro definitions,\n# include directories, and other information\n# ------------------------------------------------------------------\n\nclass Preprocessor(object):\n    def __init__(self,lexer=None):\n        if lexer is None:\n            lexer = lex.lexer\n        self.lexer = lexer\n        self.macros = { }\n        self.path = []\n        self.temp_path = []\n\n        # Probe the lexer for selected tokens\n        self.lexprobe()\n\n        tm = time.localtime()\n        self.define(\"__DATE__ \\\"%s\\\"\" % time.strftime(\"%b %d %Y\",tm))\n        self.define(\"__TIME__ \\\"%s\\\"\" % time.strftime(\"%H:%M:%S\",tm))\n        self.parser = None\n\n    # -----------------------------------------------------------------------------\n    # tokenize()\n    #\n    # Utility function. Given a string of text, tokenize into a list of tokens\n    # -----------------------------------------------------------------------------\n\n    def tokenize(self,text):\n        tokens = []\n        self.lexer.input(text)\n        while True:\n            tok = self.lexer.token()\n            if not tok: break\n            tokens.append(tok)\n        return tokens\n\n    # ---------------------------------------------------------------------\n    # error()\n    #\n    # Report a preprocessor error/warning of some kind\n    # ----------------------------------------------------------------------\n\n    def error(self,file,line,msg):\n        print(\"%s:%d %s\" % (file,line,msg))\n\n    # ----------------------------------------------------------------------\n    # lexprobe()\n    #\n    # This method probes the preprocessor lexer object to discover\n    # the token types of symbols that are important to the preprocessor.\n    # If this works right, the preprocessor will simply \"work\"\n    # with any suitable lexer regardless of how tokens have been named.\n    # ----------------------------------------------------------------------\n\n    def lexprobe(self):\n\n        # Determine the token type for identifiers\n        self.lexer.input(\"identifier\")\n        tok = self.lexer.token()\n        if not tok or tok.value != \"identifier\":\n            print(\"Couldn't determine identifier type\")\n        else:\n            self.t_ID = tok.type\n\n        # Determine the token type for integers\n        self.lexer.input(\"12345\")\n        tok = self.lexer.token()\n        if not tok or int(tok.value) != 12345:\n            print(\"Couldn't determine integer type\")\n        else:\n            self.t_INTEGER = tok.type\n            self.t_INTEGER_TYPE = type(tok.value)\n\n        # Determine the token type for strings enclosed in double quotes\n        self.lexer.input(\"\\\"filename\\\"\")\n        tok = self.lexer.token()\n        if not tok or tok.value != \"\\\"filename\\\"\":\n            print(\"Couldn't determine string type\")\n        else:\n            self.t_STRING = tok.type\n\n        # Determine the token type for whitespace--if any\n        self.lexer.input(\"  \")\n        tok = self.lexer.token()\n        if not tok or tok.value != \"  \":\n            self.t_SPACE = None\n        else:\n            self.t_SPACE = tok.type\n\n        # Determine the token type for newlines\n        self.lexer.input(\"\\n\")\n        tok = self.lexer.token()\n        if not tok or tok.value != \"\\n\":\n            self.t_NEWLINE = None\n            print(\"Couldn't determine token for newlines\")\n        else:\n            self.t_NEWLINE = tok.type\n\n        self.t_WS = (self.t_SPACE, self.t_NEWLINE)\n\n        # Check for other characters used by the preprocessor\n        chars = [ '<','>','#','##','\\\\','(',')',',','.']\n        for c in chars:\n            self.lexer.input(c)\n            tok = self.lexer.token()\n            if not tok or tok.value != c:\n                print(\"Unable to lex '%s' required for preprocessor\" % c)\n\n    # ----------------------------------------------------------------------\n    # add_path()\n    #\n    # Adds a search path to the preprocessor.\n    # ----------------------------------------------------------------------\n\n    def add_path(self,path):\n        self.path.append(path)\n\n    # ----------------------------------------------------------------------\n    # group_lines()\n    #\n    # Given an input string, this function splits it into lines.  Trailing whitespace\n    # is removed.   Any line ending with \\ is grouped with the next line.  This\n    # function forms the lowest level of the preprocessor---grouping into text into\n    # a line-by-line format.\n    # ----------------------------------------------------------------------\n\n    def group_lines(self,input):\n        lex = self.lexer.clone()\n        lines = [x.rstrip() for x in input.splitlines()]\n        for i in xrange(len(lines)):\n            j = i+1\n            while lines[i].endswith('\\\\') and (j < len(lines)):\n                lines[i] = lines[i][:-1]+lines[j]\n                lines[j] = \"\"\n                j += 1\n\n        input = \"\\n\".join(lines)\n        lex.input(input)\n        lex.lineno = 1\n\n        current_line = []\n        while True:\n            tok = lex.token()\n            if not tok:\n                break\n            current_line.append(tok)\n            if tok.type in self.t_WS and '\\n' in tok.value:\n                yield current_line\n                current_line = []\n\n        if current_line:\n            yield current_line\n\n    # ----------------------------------------------------------------------\n    # tokenstrip()\n    #\n    # Remove leading/trailing whitespace tokens from a token list\n    # ----------------------------------------------------------------------\n\n    def tokenstrip(self,tokens):\n        i = 0\n        while i < len(tokens) and tokens[i].type in self.t_WS:\n            i += 1\n        del tokens[:i]\n        i = len(tokens)-1\n        while i >= 0 and tokens[i].type in self.t_WS:\n            i -= 1\n        del tokens[i+1:]\n        return tokens\n\n\n    # ----------------------------------------------------------------------\n    # collect_args()\n    #\n    # Collects comma separated arguments from a list of tokens.   The arguments\n    # must be enclosed in parenthesis.  Returns a tuple (tokencount,args,positions)\n    # where tokencount is the number of tokens consumed, args is a list of arguments,\n    # and positions is a list of integers containing the starting index of each\n    # argument.  Each argument is represented by a list of tokens.\n    #\n    # When collecting arguments, leading and trailing whitespace is removed\n    # from each argument.\n    #\n    # This function properly handles nested parenthesis and commas---these do not\n    # define new arguments.\n    # ----------------------------------------------------------------------\n\n    def collect_args(self,tokenlist):\n        args = []\n        positions = []\n        current_arg = []\n        nesting = 1\n        tokenlen = len(tokenlist)\n\n        # Search for the opening '('.\n        i = 0\n        while (i < tokenlen) and (tokenlist[i].type in self.t_WS):\n            i += 1\n\n        if (i < tokenlen) and (tokenlist[i].value == '('):\n            positions.append(i+1)\n        else:\n            self.error(self.source,tokenlist[0].lineno,\"Missing '(' in macro arguments\")\n            return 0, [], []\n\n        i += 1\n\n        while i < tokenlen:\n            t = tokenlist[i]\n            if t.value == '(':\n                current_arg.append(t)\n                nesting += 1\n            elif t.value == ')':\n                nesting -= 1\n                if nesting == 0:\n                    if current_arg:\n                        args.append(self.tokenstrip(current_arg))\n                        positions.append(i)\n                    return i+1,args,positions\n                current_arg.append(t)\n            elif t.value == ',' and nesting == 1:\n                args.append(self.tokenstrip(current_arg))\n                positions.append(i+1)\n                current_arg = []\n            else:\n                current_arg.append(t)\n            i += 1\n\n        # Missing end argument\n        self.error(self.source,tokenlist[-1].lineno,\"Missing ')' in macro arguments\")\n        return 0, [],[]\n\n    # ----------------------------------------------------------------------\n    # macro_prescan()\n    #\n    # Examine the macro value (token sequence) and identify patch points\n    # This is used to speed up macro expansion later on---we'll know\n    # right away where to apply patches to the value to form the expansion\n    # ----------------------------------------------------------------------\n\n    def macro_prescan(self,macro):\n        macro.patch     = []             # Standard macro arguments\n        macro.str_patch = []             # String conversion expansion\n        macro.var_comma_patch = []       # Variadic macro comma patch\n        i = 0\n        while i < len(macro.value):\n            if macro.value[i].type == self.t_ID and macro.value[i].value in macro.arglist:\n                argnum = macro.arglist.index(macro.value[i].value)\n                # Conversion of argument to a string\n                if i > 0 and macro.value[i-1].value == '#':\n                    macro.value[i] = copy.copy(macro.value[i])\n                    macro.value[i].type = self.t_STRING\n                    del macro.value[i-1]\n                    macro.str_patch.append((argnum,i-1))\n                    continue\n                # Concatenation\n                elif (i > 0 and macro.value[i-1].value == '##'):\n                    macro.patch.append(('c',argnum,i-1))\n                    del macro.value[i-1]\n                    continue\n                elif ((i+1) < len(macro.value) and macro.value[i+1].value == '##'):\n                    macro.patch.append(('c',argnum,i))\n                    i += 1\n                    continue\n                # Standard expansion\n                else:\n                    macro.patch.append(('e',argnum,i))\n            elif macro.value[i].value == '##':\n                if macro.variadic and (i > 0) and (macro.value[i-1].value == ',') and \\\n                        ((i+1) < len(macro.value)) and (macro.value[i+1].type == self.t_ID) and \\\n                        (macro.value[i+1].value == macro.vararg):\n                    macro.var_comma_patch.append(i-1)\n            i += 1\n        macro.patch.sort(key=lambda x: x[2],reverse=True)\n\n    # ----------------------------------------------------------------------\n    # macro_expand_args()\n    #\n    # Given a Macro and list of arguments (each a token list), this method\n    # returns an expanded version of a macro.  The return value is a token sequence\n    # representing the replacement macro tokens\n    # ----------------------------------------------------------------------\n\n    def macro_expand_args(self,macro,args):\n        # Make a copy of the macro token sequence\n        rep = [copy.copy(_x) for _x in macro.value]\n\n        # Make string expansion patches.  These do not alter the length of the replacement sequence\n\n        str_expansion = {}\n        for argnum, i in macro.str_patch:\n            if argnum not in str_expansion:\n                str_expansion[argnum] = ('\"%s\"' % \"\".join([x.value for x in args[argnum]])).replace(\"\\\\\",\"\\\\\\\\\")\n            rep[i] = copy.copy(rep[i])\n            rep[i].value = str_expansion[argnum]\n\n        # Make the variadic macro comma patch.  If the variadic macro argument is empty, we get rid\n        comma_patch = False\n        if macro.variadic and not args[-1]:\n            for i in macro.var_comma_patch:\n                rep[i] = None\n                comma_patch = True\n\n        # Make all other patches.   The order of these matters.  It is assumed that the patch list\n        # has been sorted in reverse order of patch location since replacements will cause the\n        # size of the replacement sequence to expand from the patch point.\n\n        expanded = { }\n        for ptype, argnum, i in macro.patch:\n            # Concatenation.   Argument is left unexpanded\n            if ptype == 'c':\n                rep[i:i+1] = args[argnum]\n            # Normal expansion.  Argument is macro expanded first\n            elif ptype == 'e':\n                if argnum not in expanded:\n                    expanded[argnum] = self.expand_macros(args[argnum])\n                rep[i:i+1] = expanded[argnum]\n\n        # Get rid of removed comma if necessary\n        if comma_patch:\n            rep = [_i for _i in rep if _i]\n\n        return rep\n\n\n    # ----------------------------------------------------------------------\n    # expand_macros()\n    #\n    # Given a list of tokens, this function performs macro expansion.\n    # The expanded argument is a dictionary that contains macros already\n    # expanded.  This is used to prevent infinite recursion.\n    # ----------------------------------------------------------------------\n\n    def expand_macros(self,tokens,expanded=None):\n        if expanded is None:\n            expanded = {}\n        i = 0\n        while i < len(tokens):\n            t = tokens[i]\n            if t.type == self.t_ID:\n                if t.value in self.macros and t.value not in expanded:\n                    # Yes, we found a macro match\n                    expanded[t.value] = True\n\n                    m = self.macros[t.value]\n                    if not m.arglist:\n                        # A simple macro\n                        ex = self.expand_macros([copy.copy(_x) for _x in m.value],expanded)\n                        for e in ex:\n                            e.lineno = t.lineno\n                        tokens[i:i+1] = ex\n                        i += len(ex)\n                    else:\n                        # A macro with arguments\n                        j = i + 1\n                        while j < len(tokens) and tokens[j].type in self.t_WS:\n                            j += 1\n                        if tokens[j].value == '(':\n                            tokcount,args,positions = self.collect_args(tokens[j:])\n                            if not m.variadic and len(args) !=  len(m.arglist):\n                                self.error(self.source,t.lineno,\"Macro %s requires %d arguments\" % (t.value,len(m.arglist)))\n                                i = j + tokcount\n                            elif m.variadic and len(args) < len(m.arglist)-1:\n                                if len(m.arglist) > 2:\n                                    self.error(self.source,t.lineno,\"Macro %s must have at least %d arguments\" % (t.value, len(m.arglist)-1))\n                                else:\n                                    self.error(self.source,t.lineno,\"Macro %s must have at least %d argument\" % (t.value, len(m.arglist)-1))\n                                i = j + tokcount\n                            else:\n                                if m.variadic:\n                                    if len(args) == len(m.arglist)-1:\n                                        args.append([])\n                                    else:\n                                        args[len(m.arglist)-1] = tokens[j+positions[len(m.arglist)-1]:j+tokcount-1]\n                                        del args[len(m.arglist):]\n\n                                # Get macro replacement text\n                                rep = self.macro_expand_args(m,args)\n                                rep = self.expand_macros(rep,expanded)\n                                for r in rep:\n                                    r.lineno = t.lineno\n                                tokens[i:j+tokcount] = rep\n                                i += len(rep)\n                    del expanded[t.value]\n                    continue\n                elif t.value == '__LINE__':\n                    t.type = self.t_INTEGER\n                    t.value = self.t_INTEGER_TYPE(t.lineno)\n\n            i += 1\n        return tokens\n\n    # ----------------------------------------------------------------------\n    # evalexpr()\n    #\n    # Evaluate an expression token sequence for the purposes of evaluating\n    # integral expressions.\n    # ----------------------------------------------------------------------\n\n    def evalexpr(self,tokens):\n        # tokens = tokenize(line)\n        # Search for defined macros\n        i = 0\n        while i < len(tokens):\n            if tokens[i].type == self.t_ID and tokens[i].value == 'defined':\n                j = i + 1\n                needparen = False\n                result = \"0L\"\n                while j < len(tokens):\n                    if tokens[j].type in self.t_WS:\n                        j += 1\n                        continue\n                    elif tokens[j].type == self.t_ID:\n                        if tokens[j].value in self.macros:\n                            result = \"1L\"\n                        else:\n                            result = \"0L\"\n                        if not needparen: break\n                    elif tokens[j].value == '(':\n                        needparen = True\n                    elif tokens[j].value == ')':\n                        break\n                    else:\n                        self.error(self.source,tokens[i].lineno,\"Malformed defined()\")\n                    j += 1\n                tokens[i].type = self.t_INTEGER\n                tokens[i].value = self.t_INTEGER_TYPE(result)\n                del tokens[i+1:j+1]\n            i += 1\n        tokens = self.expand_macros(tokens)\n        for i,t in enumerate(tokens):\n            if t.type == self.t_ID:\n                tokens[i] = copy.copy(t)\n                tokens[i].type = self.t_INTEGER\n                tokens[i].value = self.t_INTEGER_TYPE(\"0L\")\n            elif t.type == self.t_INTEGER:\n                tokens[i] = copy.copy(t)\n                # Strip off any trailing suffixes\n                tokens[i].value = str(tokens[i].value)\n                while tokens[i].value[-1] not in \"0123456789abcdefABCDEF\":\n                    tokens[i].value = tokens[i].value[:-1]\n\n        expr = \"\".join([str(x.value) for x in tokens])\n        expr = expr.replace(\"&&\",\" and \")\n        expr = expr.replace(\"||\",\" or \")\n        expr = expr.replace(\"!\",\" not \")\n        try:\n            result = eval(expr)\n        except Exception:\n            self.error(self.source,tokens[0].lineno,\"Couldn't evaluate expression\")\n            result = 0\n        return result\n\n    # ----------------------------------------------------------------------\n    # parsegen()\n    #\n    # Parse an input string/\n    # ----------------------------------------------------------------------\n    def parsegen(self,input,source=None):\n\n        # Replace trigraph sequences\n        t = trigraph(input)\n        lines = self.group_lines(t)\n\n        if not source:\n            source = \"\"\n\n        self.define(\"__FILE__ \\\"%s\\\"\" % source)\n\n        self.source = source\n        chunk = []\n        enable = True\n        iftrigger = False\n        ifstack = []\n\n        for x in lines:\n            for i,tok in enumerate(x):\n                if tok.type not in self.t_WS: break\n            if tok.value == '#':\n                # Preprocessor directive\n\n                # insert necessary whitespace instead of eaten tokens\n                for tok in x:\n                    if tok.type in self.t_WS and '\\n' in tok.value:\n                        chunk.append(tok)\n\n                dirtokens = self.tokenstrip(x[i+1:])\n                if dirtokens:\n                    name = dirtokens[0].value\n                    args = self.tokenstrip(dirtokens[1:])\n                else:\n                    name = \"\"\n                    args = []\n\n                if name == 'define':\n                    if enable:\n                        for tok in self.expand_macros(chunk):\n                            yield tok\n                        chunk = []\n                        self.define(args)\n                elif name == 'include':\n                    if enable:\n                        for tok in self.expand_macros(chunk):\n                            yield tok\n                        chunk = []\n                        oldfile = self.macros['__FILE__']\n                        for tok in self.include(args):\n                            yield tok\n                        self.macros['__FILE__'] = oldfile\n                        self.source = source\n                elif name == 'undef':\n                    if enable:\n                        for tok in self.expand_macros(chunk):\n                            yield tok\n                        chunk = []\n                        self.undef(args)\n                elif name == 'ifdef':\n                    ifstack.append((enable,iftrigger))\n                    if enable:\n                        if not args[0].value in self.macros:\n                            enable = False\n                            iftrigger = False\n                        else:\n                            iftrigger = True\n                elif name == 'ifndef':\n                    ifstack.append((enable,iftrigger))\n                    if enable:\n                        if args[0].value in self.macros:\n                            enable = False\n                            iftrigger = False\n                        else:\n                            iftrigger = True\n                elif name == 'if':\n                    ifstack.append((enable,iftrigger))\n                    if enable:\n                        result = self.evalexpr(args)\n                        if not result:\n                            enable = False\n                            iftrigger = False\n                        else:\n                            iftrigger = True\n                elif name == 'elif':\n                    if ifstack:\n                        if ifstack[-1][0]:     # We only pay attention if outer \"if\" allows this\n                            if enable:         # If already true, we flip enable False\n                                enable = False\n                            elif not iftrigger:   # If False, but not triggered yet, we'll check expression\n                                result = self.evalexpr(args)\n                                if result:\n                                    enable  = True\n                                    iftrigger = True\n                    else:\n                        self.error(self.source,dirtokens[0].lineno,\"Misplaced #elif\")\n\n                elif name == 'else':\n                    if ifstack:\n                        if ifstack[-1][0]:\n                            if enable:\n                                enable = False\n                            elif not iftrigger:\n                                enable = True\n                                iftrigger = True\n                    else:\n                        self.error(self.source,dirtokens[0].lineno,\"Misplaced #else\")\n\n                elif name == 'endif':\n                    if ifstack:\n                        enable,iftrigger = ifstack.pop()\n                    else:\n                        self.error(self.source,dirtokens[0].lineno,\"Misplaced #endif\")\n                else:\n                    # Unknown preprocessor directive\n                    pass\n\n            else:\n                # Normal text\n                if enable:\n                    chunk.extend(x)\n\n        for tok in self.expand_macros(chunk):\n            yield tok\n        chunk = []\n\n    # ----------------------------------------------------------------------\n    # include()\n    #\n    # Implementation of file-inclusion\n    # ----------------------------------------------------------------------\n\n    def include(self,tokens):\n        # Try to extract the filename and then process an include file\n        if not tokens:\n            return\n        if tokens:\n            if tokens[0].value != '<' and tokens[0].type != self.t_STRING:\n                tokens = self.expand_macros(tokens)\n\n            if tokens[0].value == '<':\n                # Include <...>\n                i = 1\n                while i < len(tokens):\n                    if tokens[i].value == '>':\n                        break\n                    i += 1\n                else:\n                    print(\"Malformed #include <...>\")\n                    return\n                filename = \"\".join([x.value for x in tokens[1:i]])\n                path = self.path + [\"\"] + self.temp_path\n            elif tokens[0].type == self.t_STRING:\n                filename = tokens[0].value[1:-1]\n                path = self.temp_path + [\"\"] + self.path\n            else:\n                print(\"Malformed #include statement\")\n                return\n        for p in path:\n            iname = os.path.join(p,filename)\n            try:\n                data = open(iname,\"r\").read()\n                dname = os.path.dirname(iname)\n                if dname:\n                    self.temp_path.insert(0,dname)\n                for tok in self.parsegen(data,filename):\n                    yield tok\n                if dname:\n                    del self.temp_path[0]\n                break\n            except IOError:\n                pass\n        else:\n            print(\"Couldn't find '%s'\" % filename)\n\n    # ----------------------------------------------------------------------\n    # define()\n    #\n    # Define a new macro\n    # ----------------------------------------------------------------------\n\n    def define(self,tokens):\n        if isinstance(tokens,STRING_TYPES):\n            tokens = self.tokenize(tokens)\n\n        linetok = tokens\n        try:\n            name = linetok[0]\n            if len(linetok) > 1:\n                mtype = linetok[1]\n            else:\n                mtype = None\n            if not mtype:\n                m = Macro(name.value,[])\n                self.macros[name.value] = m\n            elif mtype.type in self.t_WS:\n                # A normal macro\n                m = Macro(name.value,self.tokenstrip(linetok[2:]))\n                self.macros[name.value] = m\n            elif mtype.value == '(':\n                # A macro with arguments\n                tokcount, args, positions = self.collect_args(linetok[1:])\n                variadic = False\n                for a in args:\n                    if variadic:\n                        print(\"No more arguments may follow a variadic argument\")\n                        break\n                    astr = \"\".join([str(_i.value) for _i in a])\n                    if astr == \"...\":\n                        variadic = True\n                        a[0].type = self.t_ID\n                        a[0].value = '__VA_ARGS__'\n                        variadic = True\n                        del a[1:]\n                        continue\n                    elif astr[-3:] == \"...\" and a[0].type == self.t_ID:\n                        variadic = True\n                        del a[1:]\n                        # If, for some reason, \".\" is part of the identifier, strip off the name for the purposes\n                        # of macro expansion\n                        if a[0].value[-3:] == '...':\n                            a[0].value = a[0].value[:-3]\n                        continue\n                    if len(a) > 1 or a[0].type != self.t_ID:\n                        print(\"Invalid macro argument\")\n                        break\n                else:\n                    mvalue = self.tokenstrip(linetok[1+tokcount:])\n                    i = 0\n                    while i < len(mvalue):\n                        if i+1 < len(mvalue):\n                            if mvalue[i].type in self.t_WS and mvalue[i+1].value == '##':\n                                del mvalue[i]\n                                continue\n                            elif mvalue[i].value == '##' and mvalue[i+1].type in self.t_WS:\n                                del mvalue[i+1]\n                        i += 1\n                    m = Macro(name.value,mvalue,[x[0].value for x in args],variadic)\n                    self.macro_prescan(m)\n                    self.macros[name.value] = m\n            else:\n                print(\"Bad macro definition\")\n        except LookupError:\n            print(\"Bad macro definition\")\n\n    # ----------------------------------------------------------------------\n    # undef()\n    #\n    # Undefine a macro\n    # ----------------------------------------------------------------------\n\n    def undef(self,tokens):\n        id = tokens[0].value\n        try:\n            del self.macros[id]\n        except LookupError:\n            pass\n\n    # ----------------------------------------------------------------------\n    # parse()\n    #\n    # Parse input text.\n    # ----------------------------------------------------------------------\n    def parse(self,input,source=None,ignore={}):\n        self.ignore = ignore\n        self.parser = self.parsegen(input,source)\n\n    # ----------------------------------------------------------------------\n    # token()\n    #\n    # Method to return individual tokens\n    # ----------------------------------------------------------------------\n    def token(self):\n        try:\n            while True:\n                tok = next(self.parser)\n                if tok.type not in self.ignore: return tok\n        except StopIteration:\n            self.parser = None\n            return None\n\nif __name__ == '__main__':\n    import ply.lex as lex\n    lexer = lex.lex()\n\n    # Run a preprocessor\n    import sys\n    f = open(sys.argv[1])\n    input = f.read()\n\n    p = Preprocessor(lexer)\n    p.parse(input,sys.argv[1])\n    while True:\n        tok = p.token()\n        if not tok: break\n        print(p.source, tok)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/ply/ctokens.py",
    "content": "# ----------------------------------------------------------------------\n# ctokens.py\n#\n# Token specifications for symbols in ANSI C and C++.  This file is\n# meant to be used as a library in other tokenizers.\n# ----------------------------------------------------------------------\n\n# Reserved words\n\ntokens = [\n    # Literals (identifier, integer constant, float constant, string constant, char const)\n    'ID', 'TYPEID', 'INTEGER', 'FLOAT', 'STRING', 'CHARACTER',\n\n    # Operators (+,-,*,/,%,|,&,~,^,<<,>>, ||, &&, !, <, <=, >, >=, ==, !=)\n    'PLUS', 'MINUS', 'TIMES', 'DIVIDE', 'MODULO',\n    'OR', 'AND', 'NOT', 'XOR', 'LSHIFT', 'RSHIFT',\n    'LOR', 'LAND', 'LNOT',\n    'LT', 'LE', 'GT', 'GE', 'EQ', 'NE',\n    \n    # Assignment (=, *=, /=, %=, +=, -=, <<=, >>=, &=, ^=, |=)\n    'EQUALS', 'TIMESEQUAL', 'DIVEQUAL', 'MODEQUAL', 'PLUSEQUAL', 'MINUSEQUAL',\n    'LSHIFTEQUAL','RSHIFTEQUAL', 'ANDEQUAL', 'XOREQUAL', 'OREQUAL',\n\n    # Increment/decrement (++,--)\n    'INCREMENT', 'DECREMENT',\n\n    # Structure dereference (->)\n    'ARROW',\n\n    # Ternary operator (?)\n    'TERNARY',\n    \n    # Delimeters ( ) [ ] { } , . ; :\n    'LPAREN', 'RPAREN',\n    'LBRACKET', 'RBRACKET',\n    'LBRACE', 'RBRACE',\n    'COMMA', 'PERIOD', 'SEMI', 'COLON',\n\n    # Ellipsis (...)\n    'ELLIPSIS',\n]\n    \n# Operators\nt_PLUS             = r'\\+'\nt_MINUS            = r'-'\nt_TIMES            = r'\\*'\nt_DIVIDE           = r'/'\nt_MODULO           = r'%'\nt_OR               = r'\\|'\nt_AND              = r'&'\nt_NOT              = r'~'\nt_XOR              = r'\\^'\nt_LSHIFT           = r'<<'\nt_RSHIFT           = r'>>'\nt_LOR              = r'\\|\\|'\nt_LAND             = r'&&'\nt_LNOT             = r'!'\nt_LT               = r'<'\nt_GT               = r'>'\nt_LE               = r'<='\nt_GE               = r'>='\nt_EQ               = r'=='\nt_NE               = r'!='\n\n# Assignment operators\n\nt_EQUALS           = r'='\nt_TIMESEQUAL       = r'\\*='\nt_DIVEQUAL         = r'/='\nt_MODEQUAL         = r'%='\nt_PLUSEQUAL        = r'\\+='\nt_MINUSEQUAL       = r'-='\nt_LSHIFTEQUAL      = r'<<='\nt_RSHIFTEQUAL      = r'>>='\nt_ANDEQUAL         = r'&='\nt_OREQUAL          = r'\\|='\nt_XOREQUAL         = r'\\^='\n\n# Increment/decrement\nt_INCREMENT        = r'\\+\\+'\nt_DECREMENT        = r'--'\n\n# ->\nt_ARROW            = r'->'\n\n# ?\nt_TERNARY          = r'\\?'\n\n# Delimeters\nt_LPAREN           = r'\\('\nt_RPAREN           = r'\\)'\nt_LBRACKET         = r'\\['\nt_RBRACKET         = r'\\]'\nt_LBRACE           = r'\\{'\nt_RBRACE           = r'\\}'\nt_COMMA            = r','\nt_PERIOD           = r'\\.'\nt_SEMI             = r';'\nt_COLON            = r':'\nt_ELLIPSIS         = r'\\.\\.\\.'\n\n# Identifiers\nt_ID = r'[A-Za-z_][A-Za-z0-9_]*'\n\n# Integer literal\nt_INTEGER = r'\\d+([uU]|[lL]|[uU][lL]|[lL][uU])?'\n\n# Floating literal\nt_FLOAT = r'((\\d+)(\\.\\d+)(e(\\+|-)?(\\d+))? | (\\d+)e(\\+|-)?(\\d+))([lL]|[fF])?'\n\n# String literal\nt_STRING = r'\\\"([^\\\\\\n]|(\\\\.))*?\\\"'\n\n# Character constant 'c' or L'c'\nt_CHARACTER = r'(L)?\\'([^\\\\\\n]|(\\\\.))*?\\''\n\n# Comment (C-Style)\ndef t_COMMENT(t):\n    r'/\\*(.|\\n)*?\\*/'\n    t.lexer.lineno += t.value.count('\\n')\n    return t\n\n# Comment (C++-Style)\ndef t_CPPCOMMENT(t):\n    r'//.*\\n'\n    t.lexer.lineno += 1\n    return t\n\n\n    \n\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/ply/lex.py",
    "content": "# -----------------------------------------------------------------------------\n# ply: lex.py\n#\n# Copyright (C) 2001-2017\n# David M. Beazley (Dabeaz LLC)\n# All rights reserved.\n#\n# Redistribution and use in source and binary forms, with or without\n# modification, are permitted provided that the following conditions are\n# met:\n#\n# * Redistributions of source code must retain the above copyright notice,\n#   this list of conditions and the following disclaimer.\n# * Redistributions in binary form must reproduce the above copyright notice,\n#   this list of conditions and the following disclaimer in the documentation\n#   and/or other materials provided with the distribution.\n# * Neither the name of the David Beazley or Dabeaz LLC may be used to\n#   endorse or promote products derived from this software without\n#  specific prior written permission.\n#\n# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n# \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR\n# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT\n# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,\n# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT\n# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,\n# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY\n# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE\n# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n# -----------------------------------------------------------------------------\n\n__version__    = '3.10'\n__tabversion__ = '3.10'\n\nimport re\nimport sys\nimport types\nimport copy\nimport os\nimport inspect\n\n# This tuple contains known string types\ntry:\n    # Python 2.6\n    StringTypes = (types.StringType, types.UnicodeType)\nexcept AttributeError:\n    # Python 3.0\n    StringTypes = (str, bytes)\n\n# This regular expression is used to match valid token names\n_is_identifier = re.compile(r'^[a-zA-Z0-9_]+$')\n\n# Exception thrown when invalid token encountered and no default error\n# handler is defined.\nclass LexError(Exception):\n    def __init__(self, message, s):\n        self.args = (message,)\n        self.text = s\n\n\n# Token class.  This class is used to represent the tokens produced.\nclass LexToken(object):\n    def __str__(self):\n        return 'LexToken(%s,%r,%d,%d)' % (self.type, self.value, self.lineno, self.lexpos)\n\n    def __repr__(self):\n        return str(self)\n\n\n# This object is a stand-in for a logging object created by the\n# logging module.\n\nclass PlyLogger(object):\n    def __init__(self, f):\n        self.f = f\n\n    def critical(self, msg, *args, **kwargs):\n        self.f.write((msg % args) + '\\n')\n\n    def warning(self, msg, *args, **kwargs):\n        self.f.write('WARNING: ' + (msg % args) + '\\n')\n\n    def error(self, msg, *args, **kwargs):\n        self.f.write('ERROR: ' + (msg % args) + '\\n')\n\n    info = critical\n    debug = critical\n\n\n# Null logger is used when no output is generated. Does nothing.\nclass NullLogger(object):\n    def __getattribute__(self, name):\n        return self\n\n    def __call__(self, *args, **kwargs):\n        return self\n\n\n# -----------------------------------------------------------------------------\n#                        === Lexing Engine ===\n#\n# The following Lexer class implements the lexer runtime.   There are only\n# a few public methods and attributes:\n#\n#    input()          -  Store a new string in the lexer\n#    token()          -  Get the next token\n#    clone()          -  Clone the lexer\n#\n#    lineno           -  Current line number\n#    lexpos           -  Current position in the input string\n# -----------------------------------------------------------------------------\n\nclass Lexer:\n    def __init__(self):\n        self.lexre = None             # Master regular expression. This is a list of\n                                      # tuples (re, findex) where re is a compiled\n                                      # regular expression and findex is a list\n                                      # mapping regex group numbers to rules\n        self.lexretext = None         # Current regular expression strings\n        self.lexstatere = {}          # Dictionary mapping lexer states to master regexs\n        self.lexstateretext = {}      # Dictionary mapping lexer states to regex strings\n        self.lexstaterenames = {}     # Dictionary mapping lexer states to symbol names\n        self.lexstate = 'INITIAL'     # Current lexer state\n        self.lexstatestack = []       # Stack of lexer states\n        self.lexstateinfo = None      # State information\n        self.lexstateignore = {}      # Dictionary of ignored characters for each state\n        self.lexstateerrorf = {}      # Dictionary of error functions for each state\n        self.lexstateeoff = {}        # Dictionary of eof functions for each state\n        self.lexreflags = 0           # Optional re compile flags\n        self.lexdata = None           # Actual input data (as a string)\n        self.lexpos = 0               # Current position in input text\n        self.lexlen = 0               # Length of the input text\n        self.lexerrorf = None         # Error rule (if any)\n        self.lexeoff = None           # EOF rule (if any)\n        self.lextokens = None         # List of valid tokens\n        self.lexignore = ''           # Ignored characters\n        self.lexliterals = ''         # Literal characters that can be passed through\n        self.lexmodule = None         # Module\n        self.lineno = 1               # Current line number\n        self.lexoptimize = False      # Optimized mode\n\n    def clone(self, object=None):\n        c = copy.copy(self)\n\n        # If the object parameter has been supplied, it means we are attaching the\n        # lexer to a new object.  In this case, we have to rebind all methods in\n        # the lexstatere and lexstateerrorf tables.\n\n        if object:\n            newtab = {}\n            for key, ritem in self.lexstatere.items():\n                newre = []\n                for cre, findex in ritem:\n                    newfindex = []\n                    for f in findex:\n                        if not f or not f[0]:\n                            newfindex.append(f)\n                            continue\n                        newfindex.append((getattr(object, f[0].__name__), f[1]))\n                newre.append((cre, newfindex))\n                newtab[key] = newre\n            c.lexstatere = newtab\n            c.lexstateerrorf = {}\n            for key, ef in self.lexstateerrorf.items():\n                c.lexstateerrorf[key] = getattr(object, ef.__name__)\n            c.lexmodule = object\n        return c\n\n    # ------------------------------------------------------------\n    # writetab() - Write lexer information to a table file\n    # ------------------------------------------------------------\n    def writetab(self, lextab, outputdir=''):\n        if isinstance(lextab, types.ModuleType):\n            raise IOError(\"Won't overwrite existing lextab module\")\n        basetabmodule = lextab.split('.')[-1]\n        filename = os.path.join(outputdir, basetabmodule) + '.py'\n        with open(filename, 'w') as tf:\n            tf.write('# %s.py. This file automatically created by PLY (version %s). Don\\'t edit!\\n' % (basetabmodule, __version__))\n            tf.write('_tabversion   = %s\\n' % repr(__tabversion__))\n            tf.write('_lextokens    = set(%s)\\n' % repr(tuple(self.lextokens)))\n            tf.write('_lexreflags   = %s\\n' % repr(self.lexreflags))\n            tf.write('_lexliterals  = %s\\n' % repr(self.lexliterals))\n            tf.write('_lexstateinfo = %s\\n' % repr(self.lexstateinfo))\n\n            # Rewrite the lexstatere table, replacing function objects with function names\n            tabre = {}\n            for statename, lre in self.lexstatere.items():\n                titem = []\n                for (pat, func), retext, renames in zip(lre, self.lexstateretext[statename], self.lexstaterenames[statename]):\n                    titem.append((retext, _funcs_to_names(func, renames)))\n                tabre[statename] = titem\n\n            tf.write('_lexstatere   = %s\\n' % repr(tabre))\n            tf.write('_lexstateignore = %s\\n' % repr(self.lexstateignore))\n\n            taberr = {}\n            for statename, ef in self.lexstateerrorf.items():\n                taberr[statename] = ef.__name__ if ef else None\n            tf.write('_lexstateerrorf = %s\\n' % repr(taberr))\n\n            tabeof = {}\n            for statename, ef in self.lexstateeoff.items():\n                tabeof[statename] = ef.__name__ if ef else None\n            tf.write('_lexstateeoff = %s\\n' % repr(tabeof))\n\n    # ------------------------------------------------------------\n    # readtab() - Read lexer information from a tab file\n    # ------------------------------------------------------------\n    def readtab(self, tabfile, fdict):\n        if isinstance(tabfile, types.ModuleType):\n            lextab = tabfile\n        else:\n            exec('import %s' % tabfile)\n            lextab = sys.modules[tabfile]\n\n        if getattr(lextab, '_tabversion', '0.0') != __tabversion__:\n            raise ImportError('Inconsistent PLY version')\n\n        self.lextokens      = lextab._lextokens\n        self.lexreflags     = lextab._lexreflags\n        self.lexliterals    = lextab._lexliterals\n        self.lextokens_all  = self.lextokens | set(self.lexliterals)\n        self.lexstateinfo   = lextab._lexstateinfo\n        self.lexstateignore = lextab._lexstateignore\n        self.lexstatere     = {}\n        self.lexstateretext = {}\n        for statename, lre in lextab._lexstatere.items():\n            titem = []\n            txtitem = []\n            for pat, func_name in lre:\n                titem.append((re.compile(pat, lextab._lexreflags), _names_to_funcs(func_name, fdict)))\n\n            self.lexstatere[statename] = titem\n            self.lexstateretext[statename] = txtitem\n\n        self.lexstateerrorf = {}\n        for statename, ef in lextab._lexstateerrorf.items():\n            self.lexstateerrorf[statename] = fdict[ef]\n\n        self.lexstateeoff = {}\n        for statename, ef in lextab._lexstateeoff.items():\n            self.lexstateeoff[statename] = fdict[ef]\n\n        self.begin('INITIAL')\n\n    # ------------------------------------------------------------\n    # input() - Push a new string into the lexer\n    # ------------------------------------------------------------\n    def input(self, s):\n        # Pull off the first character to see if s looks like a string\n        c = s[:1]\n        if not isinstance(c, StringTypes):\n            raise ValueError('Expected a string')\n        self.lexdata = s\n        self.lexpos = 0\n        self.lexlen = len(s)\n\n    # ------------------------------------------------------------\n    # begin() - Changes the lexing state\n    # ------------------------------------------------------------\n    def begin(self, state):\n        if state not in self.lexstatere:\n            raise ValueError('Undefined state')\n        self.lexre = self.lexstatere[state]\n        self.lexretext = self.lexstateretext[state]\n        self.lexignore = self.lexstateignore.get(state, '')\n        self.lexerrorf = self.lexstateerrorf.get(state, None)\n        self.lexeoff = self.lexstateeoff.get(state, None)\n        self.lexstate = state\n\n    # ------------------------------------------------------------\n    # push_state() - Changes the lexing state and saves old on stack\n    # ------------------------------------------------------------\n    def push_state(self, state):\n        self.lexstatestack.append(self.lexstate)\n        self.begin(state)\n\n    # ------------------------------------------------------------\n    # pop_state() - Restores the previous state\n    # ------------------------------------------------------------\n    def pop_state(self):\n        self.begin(self.lexstatestack.pop())\n\n    # ------------------------------------------------------------\n    # current_state() - Returns the current lexing state\n    # ------------------------------------------------------------\n    def current_state(self):\n        return self.lexstate\n\n    # ------------------------------------------------------------\n    # skip() - Skip ahead n characters\n    # ------------------------------------------------------------\n    def skip(self, n):\n        self.lexpos += n\n\n    # ------------------------------------------------------------\n    # opttoken() - Return the next token from the Lexer\n    #\n    # Note: This function has been carefully implemented to be as fast\n    # as possible.  Don't make changes unless you really know what\n    # you are doing\n    # ------------------------------------------------------------\n    def token(self):\n        # Make local copies of frequently referenced attributes\n        lexpos    = self.lexpos\n        lexlen    = self.lexlen\n        lexignore = self.lexignore\n        lexdata   = self.lexdata\n\n        while lexpos < lexlen:\n            # This code provides some short-circuit code for whitespace, tabs, and other ignored characters\n            if lexdata[lexpos] in lexignore:\n                lexpos += 1\n                continue\n\n            # Look for a regular expression match\n            for lexre, lexindexfunc in self.lexre:\n                m = lexre.match(lexdata, lexpos)\n                if not m:\n                    continue\n\n                # Create a token for return\n                tok = LexToken()\n                tok.value = m.group()\n                tok.lineno = self.lineno\n                tok.lexpos = lexpos\n\n                i = m.lastindex\n                func, tok.type = lexindexfunc[i]\n\n                if not func:\n                    # If no token type was set, it's an ignored token\n                    if tok.type:\n                        self.lexpos = m.end()\n                        return tok\n                    else:\n                        lexpos = m.end()\n                        break\n\n                lexpos = m.end()\n\n                # If token is processed by a function, call it\n\n                tok.lexer = self      # Set additional attributes useful in token rules\n                self.lexmatch = m\n                self.lexpos = lexpos\n\n                newtok = func(tok)\n\n                # Every function must return a token, if nothing, we just move to next token\n                if not newtok:\n                    lexpos    = self.lexpos         # This is here in case user has updated lexpos.\n                    lexignore = self.lexignore      # This is here in case there was a state change\n                    break\n\n                # Verify type of the token.  If not in the token map, raise an error\n                if not self.lexoptimize:\n                    if newtok.type not in self.lextokens_all:\n                        raise LexError(\"%s:%d: Rule '%s' returned an unknown token type '%s'\" % (\n                            func.__code__.co_filename, func.__code__.co_firstlineno,\n                            func.__name__, newtok.type), lexdata[lexpos:])\n\n                return newtok\n            else:\n                # No match, see if in literals\n                if lexdata[lexpos] in self.lexliterals:\n                    tok = LexToken()\n                    tok.value = lexdata[lexpos]\n                    tok.lineno = self.lineno\n                    tok.type = tok.value\n                    tok.lexpos = lexpos\n                    self.lexpos = lexpos + 1\n                    return tok\n\n                # No match. Call t_error() if defined.\n                if self.lexerrorf:\n                    tok = LexToken()\n                    tok.value = self.lexdata[lexpos:]\n                    tok.lineno = self.lineno\n                    tok.type = 'error'\n                    tok.lexer = self\n                    tok.lexpos = lexpos\n                    self.lexpos = lexpos\n                    newtok = self.lexerrorf(tok)\n                    if lexpos == self.lexpos:\n                        # Error method didn't change text position at all. This is an error.\n                        raise LexError(\"Scanning error. Illegal character '%s'\" % (lexdata[lexpos]), lexdata[lexpos:])\n                    lexpos = self.lexpos\n                    if not newtok:\n                        continue\n                    return newtok\n\n                self.lexpos = lexpos\n                raise LexError(\"Illegal character '%s' at index %d\" % (lexdata[lexpos], lexpos), lexdata[lexpos:])\n\n        if self.lexeoff:\n            tok = LexToken()\n            tok.type = 'eof'\n            tok.value = ''\n            tok.lineno = self.lineno\n            tok.lexpos = lexpos\n            tok.lexer = self\n            self.lexpos = lexpos\n            newtok = self.lexeoff(tok)\n            return newtok\n\n        self.lexpos = lexpos + 1\n        if self.lexdata is None:\n            raise RuntimeError('No input string given with input()')\n        return None\n\n    # Iterator interface\n    def __iter__(self):\n        return self\n\n    def next(self):\n        t = self.token()\n        if t is None:\n            raise StopIteration\n        return t\n\n    __next__ = next\n\n# -----------------------------------------------------------------------------\n#                           ==== Lex Builder ===\n#\n# The functions and classes below are used to collect lexing information\n# and build a Lexer object from it.\n# -----------------------------------------------------------------------------\n\n# -----------------------------------------------------------------------------\n# _get_regex(func)\n#\n# Returns the regular expression assigned to a function either as a doc string\n# or as a .regex attribute attached by the @TOKEN decorator.\n# -----------------------------------------------------------------------------\ndef _get_regex(func):\n    return getattr(func, 'regex', func.__doc__)\n\n# -----------------------------------------------------------------------------\n# get_caller_module_dict()\n#\n# This function returns a dictionary containing all of the symbols defined within\n# a caller further down the call stack.  This is used to get the environment\n# associated with the yacc() call if none was provided.\n# -----------------------------------------------------------------------------\ndef get_caller_module_dict(levels):\n    f = sys._getframe(levels)\n    ldict = f.f_globals.copy()\n    if f.f_globals != f.f_locals:\n        ldict.update(f.f_locals)\n    return ldict\n\n# -----------------------------------------------------------------------------\n# _funcs_to_names()\n#\n# Given a list of regular expression functions, this converts it to a list\n# suitable for output to a table file\n# -----------------------------------------------------------------------------\ndef _funcs_to_names(funclist, namelist):\n    result = []\n    for f, name in zip(funclist, namelist):\n        if f and f[0]:\n            result.append((name, f[1]))\n        else:\n            result.append(f)\n    return result\n\n# -----------------------------------------------------------------------------\n# _names_to_funcs()\n#\n# Given a list of regular expression function names, this converts it back to\n# functions.\n# -----------------------------------------------------------------------------\ndef _names_to_funcs(namelist, fdict):\n    result = []\n    for n in namelist:\n        if n and n[0]:\n            result.append((fdict[n[0]], n[1]))\n        else:\n            result.append(n)\n    return result\n\n# -----------------------------------------------------------------------------\n# _form_master_re()\n#\n# This function takes a list of all of the regex components and attempts to\n# form the master regular expression.  Given limitations in the Python re\n# module, it may be necessary to break the master regex into separate expressions.\n# -----------------------------------------------------------------------------\ndef _form_master_re(relist, reflags, ldict, toknames):\n    if not relist:\n        return []\n    regex = '|'.join(relist)\n    try:\n        lexre = re.compile(regex, reflags)\n\n        # Build the index to function map for the matching engine\n        lexindexfunc = [None] * (max(lexre.groupindex.values()) + 1)\n        lexindexnames = lexindexfunc[:]\n\n        for f, i in lexre.groupindex.items():\n            handle = ldict.get(f, None)\n            if type(handle) in (types.FunctionType, types.MethodType):\n                lexindexfunc[i] = (handle, toknames[f])\n                lexindexnames[i] = f\n            elif handle is not None:\n                lexindexnames[i] = f\n                if f.find('ignore_') > 0:\n                    lexindexfunc[i] = (None, None)\n                else:\n                    lexindexfunc[i] = (None, toknames[f])\n\n        return [(lexre, lexindexfunc)], [regex], [lexindexnames]\n    except Exception:\n        m = int(len(relist)/2)\n        if m == 0:\n            m = 1\n        llist, lre, lnames = _form_master_re(relist[:m], reflags, ldict, toknames)\n        rlist, rre, rnames = _form_master_re(relist[m:], reflags, ldict, toknames)\n        return (llist+rlist), (lre+rre), (lnames+rnames)\n\n# -----------------------------------------------------------------------------\n# def _statetoken(s,names)\n#\n# Given a declaration name s of the form \"t_\" and a dictionary whose keys are\n# state names, this function returns a tuple (states,tokenname) where states\n# is a tuple of state names and tokenname is the name of the token.  For example,\n# calling this with s = \"t_foo_bar_SPAM\" might return (('foo','bar'),'SPAM')\n# -----------------------------------------------------------------------------\ndef _statetoken(s, names):\n    nonstate = 1\n    parts = s.split('_')\n    for i, part in enumerate(parts[1:], 1):\n        if part not in names and part != 'ANY':\n            break\n\n    if i > 1:\n        states = tuple(parts[1:i])\n    else:\n        states = ('INITIAL',)\n\n    if 'ANY' in states:\n        states = tuple(names)\n\n    tokenname = '_'.join(parts[i:])\n    return (states, tokenname)\n\n\n# -----------------------------------------------------------------------------\n# LexerReflect()\n#\n# This class represents information needed to build a lexer as extracted from a\n# user's input file.\n# -----------------------------------------------------------------------------\nclass LexerReflect(object):\n    def __init__(self, ldict, log=None, reflags=0):\n        self.ldict      = ldict\n        self.error_func = None\n        self.tokens     = []\n        self.reflags    = reflags\n        self.stateinfo  = {'INITIAL': 'inclusive'}\n        self.modules    = set()\n        self.error      = False\n        self.log        = PlyLogger(sys.stderr) if log is None else log\n\n    # Get all of the basic information\n    def get_all(self):\n        self.get_tokens()\n        self.get_literals()\n        self.get_states()\n        self.get_rules()\n\n    # Validate all of the information\n    def validate_all(self):\n        self.validate_tokens()\n        self.validate_literals()\n        self.validate_rules()\n        return self.error\n\n    # Get the tokens map\n    def get_tokens(self):\n        tokens = self.ldict.get('tokens', None)\n        if not tokens:\n            self.log.error('No token list is defined')\n            self.error = True\n            return\n\n        if not isinstance(tokens, (list, tuple)):\n            self.log.error('tokens must be a list or tuple')\n            self.error = True\n            return\n\n        if not tokens:\n            self.log.error('tokens is empty')\n            self.error = True\n            return\n\n        self.tokens = tokens\n\n    # Validate the tokens\n    def validate_tokens(self):\n        terminals = {}\n        for n in self.tokens:\n            if not _is_identifier.match(n):\n                self.log.error(\"Bad token name '%s'\", n)\n                self.error = True\n            if n in terminals:\n                self.log.warning(\"Token '%s' multiply defined\", n)\n            terminals[n] = 1\n\n    # Get the literals specifier\n    def get_literals(self):\n        self.literals = self.ldict.get('literals', '')\n        if not self.literals:\n            self.literals = ''\n\n    # Validate literals\n    def validate_literals(self):\n        try:\n            for c in self.literals:\n                if not isinstance(c, StringTypes) or len(c) > 1:\n                    self.log.error('Invalid literal %s. Must be a single character', repr(c))\n                    self.error = True\n\n        except TypeError:\n            self.log.error('Invalid literals specification. literals must be a sequence of characters')\n            self.error = True\n\n    def get_states(self):\n        self.states = self.ldict.get('states', None)\n        # Build statemap\n        if self.states:\n            if not isinstance(self.states, (tuple, list)):\n                self.log.error('states must be defined as a tuple or list')\n                self.error = True\n            else:\n                for s in self.states:\n                    if not isinstance(s, tuple) or len(s) != 2:\n                        self.log.error(\"Invalid state specifier %s. Must be a tuple (statename,'exclusive|inclusive')\", repr(s))\n                        self.error = True\n                        continue\n                    name, statetype = s\n                    if not isinstance(name, StringTypes):\n                        self.log.error('State name %s must be a string', repr(name))\n                        self.error = True\n                        continue\n                    if not (statetype == 'inclusive' or statetype == 'exclusive'):\n                        self.log.error(\"State type for state %s must be 'inclusive' or 'exclusive'\", name)\n                        self.error = True\n                        continue\n                    if name in self.stateinfo:\n                        self.log.error(\"State '%s' already defined\", name)\n                        self.error = True\n                        continue\n                    self.stateinfo[name] = statetype\n\n    # Get all of the symbols with a t_ prefix and sort them into various\n    # categories (functions, strings, error functions, and ignore characters)\n\n    def get_rules(self):\n        tsymbols = [f for f in self.ldict if f[:2] == 't_']\n\n        # Now build up a list of functions and a list of strings\n        self.toknames = {}        # Mapping of symbols to token names\n        self.funcsym  = {}        # Symbols defined as functions\n        self.strsym   = {}        # Symbols defined as strings\n        self.ignore   = {}        # Ignore strings by state\n        self.errorf   = {}        # Error functions by state\n        self.eoff     = {}        # EOF functions by state\n\n        for s in self.stateinfo:\n            self.funcsym[s] = []\n            self.strsym[s] = []\n\n        if len(tsymbols) == 0:\n            self.log.error('No rules of the form t_rulename are defined')\n            self.error = True\n            return\n\n        for f in tsymbols:\n            t = self.ldict[f]\n            states, tokname = _statetoken(f, self.stateinfo)\n            self.toknames[f] = tokname\n\n            if hasattr(t, '__call__'):\n                if tokname == 'error':\n                    for s in states:\n                        self.errorf[s] = t\n                elif tokname == 'eof':\n                    for s in states:\n                        self.eoff[s] = t\n                elif tokname == 'ignore':\n                    line = t.__code__.co_firstlineno\n                    file = t.__code__.co_filename\n                    self.log.error(\"%s:%d: Rule '%s' must be defined as a string\", file, line, t.__name__)\n                    self.error = True\n                else:\n                    for s in states:\n                        self.funcsym[s].append((f, t))\n            elif isinstance(t, StringTypes):\n                if tokname == 'ignore':\n                    for s in states:\n                        self.ignore[s] = t\n                    if '\\\\' in t:\n                        self.log.warning(\"%s contains a literal backslash '\\\\'\", f)\n\n                elif tokname == 'error':\n                    self.log.error(\"Rule '%s' must be defined as a function\", f)\n                    self.error = True\n                else:\n                    for s in states:\n                        self.strsym[s].append((f, t))\n            else:\n                self.log.error('%s not defined as a function or string', f)\n                self.error = True\n\n        # Sort the functions by line number\n        for f in self.funcsym.values():\n            f.sort(key=lambda x: x[1].__code__.co_firstlineno)\n\n        # Sort the strings by regular expression length\n        for s in self.strsym.values():\n            s.sort(key=lambda x: len(x[1]), reverse=True)\n\n    # Validate all of the t_rules collected\n    def validate_rules(self):\n        for state in self.stateinfo:\n            # Validate all rules defined by functions\n\n            for fname, f in self.funcsym[state]:\n                line = f.__code__.co_firstlineno\n                file = f.__code__.co_filename\n                module = inspect.getmodule(f)\n                self.modules.add(module)\n\n                tokname = self.toknames[fname]\n                if isinstance(f, types.MethodType):\n                    reqargs = 2\n                else:\n                    reqargs = 1\n                nargs = f.__code__.co_argcount\n                if nargs > reqargs:\n                    self.log.error(\"%s:%d: Rule '%s' has too many arguments\", file, line, f.__name__)\n                    self.error = True\n                    continue\n\n                if nargs < reqargs:\n                    self.log.error(\"%s:%d: Rule '%s' requires an argument\", file, line, f.__name__)\n                    self.error = True\n                    continue\n\n                if not _get_regex(f):\n                    self.log.error(\"%s:%d: No regular expression defined for rule '%s'\", file, line, f.__name__)\n                    self.error = True\n                    continue\n\n                try:\n                    c = re.compile('(?P<%s>%s)' % (fname, _get_regex(f)), self.reflags)\n                    if c.match(''):\n                        self.log.error(\"%s:%d: Regular expression for rule '%s' matches empty string\", file, line, f.__name__)\n                        self.error = True\n                except re.error as e:\n                    self.log.error(\"%s:%d: Invalid regular expression for rule '%s'. %s\", file, line, f.__name__, e)\n                    if '#' in _get_regex(f):\n                        self.log.error(\"%s:%d. Make sure '#' in rule '%s' is escaped with '\\\\#'\", file, line, f.__name__)\n                    self.error = True\n\n            # Validate all rules defined by strings\n            for name, r in self.strsym[state]:\n                tokname = self.toknames[name]\n                if tokname == 'error':\n                    self.log.error(\"Rule '%s' must be defined as a function\", name)\n                    self.error = True\n                    continue\n\n                if tokname not in self.tokens and tokname.find('ignore_') < 0:\n                    self.log.error(\"Rule '%s' defined for an unspecified token %s\", name, tokname)\n                    self.error = True\n                    continue\n\n                try:\n                    c = re.compile('(?P<%s>%s)' % (name, r), self.reflags)\n                    if (c.match('')):\n                        self.log.error(\"Regular expression for rule '%s' matches empty string\", name)\n                        self.error = True\n                except re.error as e:\n                    self.log.error(\"Invalid regular expression for rule '%s'. %s\", name, e)\n                    if '#' in r:\n                        self.log.error(\"Make sure '#' in rule '%s' is escaped with '\\\\#'\", name)\n                    self.error = True\n\n            if not self.funcsym[state] and not self.strsym[state]:\n                self.log.error(\"No rules defined for state '%s'\", state)\n                self.error = True\n\n            # Validate the error function\n            efunc = self.errorf.get(state, None)\n            if efunc:\n                f = efunc\n                line = f.__code__.co_firstlineno\n                file = f.__code__.co_filename\n                module = inspect.getmodule(f)\n                self.modules.add(module)\n\n                if isinstance(f, types.MethodType):\n                    reqargs = 2\n                else:\n                    reqargs = 1\n                nargs = f.__code__.co_argcount\n                if nargs > reqargs:\n                    self.log.error(\"%s:%d: Rule '%s' has too many arguments\", file, line, f.__name__)\n                    self.error = True\n\n                if nargs < reqargs:\n                    self.log.error(\"%s:%d: Rule '%s' requires an argument\", file, line, f.__name__)\n                    self.error = True\n\n        for module in self.modules:\n            self.validate_module(module)\n\n    # -----------------------------------------------------------------------------\n    # validate_module()\n    #\n    # This checks to see if there are duplicated t_rulename() functions or strings\n    # in the parser input file.  This is done using a simple regular expression\n    # match on each line in the source code of the given module.\n    # -----------------------------------------------------------------------------\n\n    def validate_module(self, module):\n        try:\n            lines, linen = inspect.getsourcelines(module)\n        except IOError:\n            return\n\n        fre = re.compile(r'\\s*def\\s+(t_[a-zA-Z_0-9]*)\\(')\n        sre = re.compile(r'\\s*(t_[a-zA-Z_0-9]*)\\s*=')\n\n        counthash = {}\n        linen += 1\n        for line in lines:\n            m = fre.match(line)\n            if not m:\n                m = sre.match(line)\n            if m:\n                name = m.group(1)\n                prev = counthash.get(name)\n                if not prev:\n                    counthash[name] = linen\n                else:\n                    filename = inspect.getsourcefile(module)\n                    self.log.error('%s:%d: Rule %s redefined. Previously defined on line %d', filename, linen, name, prev)\n                    self.error = True\n            linen += 1\n\n# -----------------------------------------------------------------------------\n# lex(module)\n#\n# Build all of the regular expression rules from definitions in the supplied module\n# -----------------------------------------------------------------------------\ndef lex(module=None, object=None, debug=False, optimize=False, lextab='lextab',\n        reflags=int(re.VERBOSE), nowarn=False, outputdir=None, debuglog=None, errorlog=None):\n\n    if lextab is None:\n        lextab = 'lextab'\n\n    global lexer\n\n    ldict = None\n    stateinfo  = {'INITIAL': 'inclusive'}\n    lexobj = Lexer()\n    lexobj.lexoptimize = optimize\n    global token, input\n\n    if errorlog is None:\n        errorlog = PlyLogger(sys.stderr)\n\n    if debug:\n        if debuglog is None:\n            debuglog = PlyLogger(sys.stderr)\n\n    # Get the module dictionary used for the lexer\n    if object:\n        module = object\n\n    # Get the module dictionary used for the parser\n    if module:\n        _items = [(k, getattr(module, k)) for k in dir(module)]\n        ldict = dict(_items)\n        # If no __file__ attribute is available, try to obtain it from the __module__ instead\n        if '__file__' not in ldict:\n            ldict['__file__'] = sys.modules[ldict['__module__']].__file__\n    else:\n        ldict = get_caller_module_dict(2)\n\n    # Determine if the module is package of a package or not.\n    # If so, fix the tabmodule setting so that tables load correctly\n    pkg = ldict.get('__package__')\n    if pkg and isinstance(lextab, str):\n        if '.' not in lextab:\n            lextab = pkg + '.' + lextab\n\n    # Collect parser information from the dictionary\n    linfo = LexerReflect(ldict, log=errorlog, reflags=reflags)\n    linfo.get_all()\n    if not optimize:\n        if linfo.validate_all():\n            raise SyntaxError(\"Can't build lexer\")\n\n    if optimize and lextab:\n        try:\n            lexobj.readtab(lextab, ldict)\n            token = lexobj.token\n            input = lexobj.input\n            lexer = lexobj\n            return lexobj\n\n        except ImportError:\n            pass\n\n    # Dump some basic debugging information\n    if debug:\n        debuglog.info('lex: tokens   = %r', linfo.tokens)\n        debuglog.info('lex: literals = %r', linfo.literals)\n        debuglog.info('lex: states   = %r', linfo.stateinfo)\n\n    # Build a dictionary of valid token names\n    lexobj.lextokens = set()\n    for n in linfo.tokens:\n        lexobj.lextokens.add(n)\n\n    # Get literals specification\n    if isinstance(linfo.literals, (list, tuple)):\n        lexobj.lexliterals = type(linfo.literals[0])().join(linfo.literals)\n    else:\n        lexobj.lexliterals = linfo.literals\n\n    lexobj.lextokens_all = lexobj.lextokens | set(lexobj.lexliterals)\n\n    # Get the stateinfo dictionary\n    stateinfo = linfo.stateinfo\n\n    regexs = {}\n    # Build the master regular expressions\n    for state in stateinfo:\n        regex_list = []\n\n        # Add rules defined by functions first\n        for fname, f in linfo.funcsym[state]:\n            line = f.__code__.co_firstlineno\n            file = f.__code__.co_filename\n            regex_list.append('(?P<%s>%s)' % (fname, _get_regex(f)))\n            if debug:\n                debuglog.info(\"lex: Adding rule %s -> '%s' (state '%s')\", fname, _get_regex(f), state)\n\n        # Now add all of the simple rules\n        for name, r in linfo.strsym[state]:\n            regex_list.append('(?P<%s>%s)' % (name, r))\n            if debug:\n                debuglog.info(\"lex: Adding rule %s -> '%s' (state '%s')\", name, r, state)\n\n        regexs[state] = regex_list\n\n    # Build the master regular expressions\n\n    if debug:\n        debuglog.info('lex: ==== MASTER REGEXS FOLLOW ====')\n\n    for state in regexs:\n        lexre, re_text, re_names = _form_master_re(regexs[state], reflags, ldict, linfo.toknames)\n        lexobj.lexstatere[state] = lexre\n        lexobj.lexstateretext[state] = re_text\n        lexobj.lexstaterenames[state] = re_names\n        if debug:\n            for i, text in enumerate(re_text):\n                debuglog.info(\"lex: state '%s' : regex[%d] = '%s'\", state, i, text)\n\n    # For inclusive states, we need to add the regular expressions from the INITIAL state\n    for state, stype in stateinfo.items():\n        if state != 'INITIAL' and stype == 'inclusive':\n            lexobj.lexstatere[state].extend(lexobj.lexstatere['INITIAL'])\n            lexobj.lexstateretext[state].extend(lexobj.lexstateretext['INITIAL'])\n            lexobj.lexstaterenames[state].extend(lexobj.lexstaterenames['INITIAL'])\n\n    lexobj.lexstateinfo = stateinfo\n    lexobj.lexre = lexobj.lexstatere['INITIAL']\n    lexobj.lexretext = lexobj.lexstateretext['INITIAL']\n    lexobj.lexreflags = reflags\n\n    # Set up ignore variables\n    lexobj.lexstateignore = linfo.ignore\n    lexobj.lexignore = lexobj.lexstateignore.get('INITIAL', '')\n\n    # Set up error functions\n    lexobj.lexstateerrorf = linfo.errorf\n    lexobj.lexerrorf = linfo.errorf.get('INITIAL', None)\n    if not lexobj.lexerrorf:\n        errorlog.warning('No t_error rule is defined')\n\n    # Set up eof functions\n    lexobj.lexstateeoff = linfo.eoff\n    lexobj.lexeoff = linfo.eoff.get('INITIAL', None)\n\n    # Check state information for ignore and error rules\n    for s, stype in stateinfo.items():\n        if stype == 'exclusive':\n            if s not in linfo.errorf:\n                errorlog.warning(\"No error rule is defined for exclusive state '%s'\", s)\n            if s not in linfo.ignore and lexobj.lexignore:\n                errorlog.warning(\"No ignore rule is defined for exclusive state '%s'\", s)\n        elif stype == 'inclusive':\n            if s not in linfo.errorf:\n                linfo.errorf[s] = linfo.errorf.get('INITIAL', None)\n            if s not in linfo.ignore:\n                linfo.ignore[s] = linfo.ignore.get('INITIAL', '')\n\n    # Create global versions of the token() and input() functions\n    token = lexobj.token\n    input = lexobj.input\n    lexer = lexobj\n\n    # If in optimize mode, we write the lextab\n    if lextab and optimize:\n        if outputdir is None:\n            # If no output directory is set, the location of the output files\n            # is determined according to the following rules:\n            #     - If lextab specifies a package, files go into that package directory\n            #     - Otherwise, files go in the same directory as the specifying module\n            if isinstance(lextab, types.ModuleType):\n                srcfile = lextab.__file__\n            else:\n                if '.' not in lextab:\n                    srcfile = ldict['__file__']\n                else:\n                    parts = lextab.split('.')\n                    pkgname = '.'.join(parts[:-1])\n                    exec('import %s' % pkgname)\n                    srcfile = getattr(sys.modules[pkgname], '__file__', '')\n            outputdir = os.path.dirname(srcfile)\n        try:\n            lexobj.writetab(lextab, outputdir)\n        except IOError as e:\n            errorlog.warning(\"Couldn't write lextab module %r. %s\" % (lextab, e))\n\n    return lexobj\n\n# -----------------------------------------------------------------------------\n# runmain()\n#\n# This runs the lexer as a main program\n# -----------------------------------------------------------------------------\n\ndef runmain(lexer=None, data=None):\n    if not data:\n        try:\n            filename = sys.argv[1]\n            f = open(filename)\n            data = f.read()\n            f.close()\n        except IndexError:\n            sys.stdout.write('Reading from standard input (type EOF to end):\\n')\n            data = sys.stdin.read()\n\n    if lexer:\n        _input = lexer.input\n    else:\n        _input = input\n    _input(data)\n    if lexer:\n        _token = lexer.token\n    else:\n        _token = token\n\n    while True:\n        tok = _token()\n        if not tok:\n            break\n        sys.stdout.write('(%s,%r,%d,%d)\\n' % (tok.type, tok.value, tok.lineno, tok.lexpos))\n\n# -----------------------------------------------------------------------------\n# @TOKEN(regex)\n#\n# This decorator function can be used to set the regex expression on a function\n# when its docstring might need to be set in an alternative way\n# -----------------------------------------------------------------------------\n\ndef TOKEN(r):\n    def set_regex(f):\n        if hasattr(r, '__call__'):\n            f.regex = _get_regex(r)\n        else:\n            f.regex = r\n        return f\n    return set_regex\n\n# Alternative spelling of the TOKEN decorator\nToken = TOKEN\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/ply/yacc.py",
    "content": "# -----------------------------------------------------------------------------\n# ply: yacc.py\n#\n# Copyright (C) 2001-2017\n# David M. Beazley (Dabeaz LLC)\n# All rights reserved.\n#\n# Redistribution and use in source and binary forms, with or without\n# modification, are permitted provided that the following conditions are\n# met:\n#\n# * Redistributions of source code must retain the above copyright notice,\n#   this list of conditions and the following disclaimer.\n# * Redistributions in binary form must reproduce the above copyright notice,\n#   this list of conditions and the following disclaimer in the documentation\n#   and/or other materials provided with the distribution.\n# * Neither the name of the David Beazley or Dabeaz LLC may be used to\n#   endorse or promote products derived from this software without\n#  specific prior written permission.\n#\n# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n# \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR\n# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT\n# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,\n# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT\n# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,\n# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY\n# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE\n# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n# -----------------------------------------------------------------------------\n#\n# This implements an LR parser that is constructed from grammar rules defined\n# as Python functions. The grammer is specified by supplying the BNF inside\n# Python documentation strings.  The inspiration for this technique was borrowed\n# from John Aycock's Spark parsing system.  PLY might be viewed as cross between\n# Spark and the GNU bison utility.\n#\n# The current implementation is only somewhat object-oriented. The\n# LR parser itself is defined in terms of an object (which allows multiple\n# parsers to co-exist).  However, most of the variables used during table\n# construction are defined in terms of global variables.  Users shouldn't\n# notice unless they are trying to define multiple parsers at the same\n# time using threads (in which case they should have their head examined).\n#\n# This implementation supports both SLR and LALR(1) parsing.  LALR(1)\n# support was originally implemented by Elias Ioup (ezioup@alumni.uchicago.edu),\n# using the algorithm found in Aho, Sethi, and Ullman \"Compilers: Principles,\n# Techniques, and Tools\" (The Dragon Book).  LALR(1) has since been replaced\n# by the more efficient DeRemer and Pennello algorithm.\n#\n# :::::::: WARNING :::::::\n#\n# Construction of LR parsing tables is fairly complicated and expensive.\n# To make this module run fast, a *LOT* of work has been put into\n# optimization---often at the expensive of readability and what might\n# consider to be good Python \"coding style.\"   Modify the code at your\n# own risk!\n# ----------------------------------------------------------------------------\n\nimport re\nimport types\nimport sys\nimport os.path\nimport inspect\nimport base64\nimport warnings\n\n__version__    = '3.10'\n__tabversion__ = '3.10'\n\n#-----------------------------------------------------------------------------\n#                     === User configurable parameters ===\n#\n# Change these to modify the default behavior of yacc (if you wish)\n#-----------------------------------------------------------------------------\n\nyaccdebug   = True             # Debugging mode.  If set, yacc generates a\n                               # a 'parser.out' file in the current directory\n\ndebug_file  = 'parser.out'     # Default name of the debugging file\ntab_module  = 'parsetab'       # Default name of the table module\ndefault_lr  = 'LALR'           # Default LR table generation method\n\nerror_count = 3                # Number of symbols that must be shifted to leave recovery mode\n\nyaccdevel   = False            # Set to True if developing yacc.  This turns off optimized\n                               # implementations of certain functions.\n\nresultlimit = 40               # Size limit of results when running in debug mode.\n\npickle_protocol = 0            # Protocol to use when writing pickle files\n\n# String type-checking compatibility\nif sys.version_info[0] < 3:\n    string_types = basestring\nelse:\n    string_types = str\n\nMAXINT = sys.maxsize\n\n# This object is a stand-in for a logging object created by the\n# logging module.   PLY will use this by default to create things\n# such as the parser.out file.  If a user wants more detailed\n# information, they can create their own logging object and pass\n# it into PLY.\n\nclass PlyLogger(object):\n    def __init__(self, f):\n        self.f = f\n\n    def debug(self, msg, *args, **kwargs):\n        self.f.write((msg % args) + '\\n')\n\n    info = debug\n\n    def warning(self, msg, *args, **kwargs):\n        self.f.write('WARNING: ' + (msg % args) + '\\n')\n\n    def error(self, msg, *args, **kwargs):\n        self.f.write('ERROR: ' + (msg % args) + '\\n')\n\n    critical = debug\n\n# Null logger is used when no output is generated. Does nothing.\nclass NullLogger(object):\n    def __getattribute__(self, name):\n        return self\n\n    def __call__(self, *args, **kwargs):\n        return self\n\n# Exception raised for yacc-related errors\nclass YaccError(Exception):\n    pass\n\n# Format the result message that the parser produces when running in debug mode.\ndef format_result(r):\n    repr_str = repr(r)\n    if '\\n' in repr_str:\n        repr_str = repr(repr_str)\n    if len(repr_str) > resultlimit:\n        repr_str = repr_str[:resultlimit] + ' ...'\n    result = '<%s @ 0x%x> (%s)' % (type(r).__name__, id(r), repr_str)\n    return result\n\n# Format stack entries when the parser is running in debug mode\ndef format_stack_entry(r):\n    repr_str = repr(r)\n    if '\\n' in repr_str:\n        repr_str = repr(repr_str)\n    if len(repr_str) < 16:\n        return repr_str\n    else:\n        return '<%s @ 0x%x>' % (type(r).__name__, id(r))\n\n# Panic mode error recovery support.   This feature is being reworked--much of the\n# code here is to offer a deprecation/backwards compatible transition\n\n_errok = None\n_token = None\n_restart = None\n_warnmsg = '''PLY: Don't use global functions errok(), token(), and restart() in p_error().\nInstead, invoke the methods on the associated parser instance:\n\n    def p_error(p):\n        ...\n        # Use parser.errok(), parser.token(), parser.restart()\n        ...\n\n    parser = yacc.yacc()\n'''\n\ndef errok():\n    warnings.warn(_warnmsg)\n    return _errok()\n\ndef restart():\n    warnings.warn(_warnmsg)\n    return _restart()\n\ndef token():\n    warnings.warn(_warnmsg)\n    return _token()\n\n# Utility function to call the p_error() function with some deprecation hacks\ndef call_errorfunc(errorfunc, token, parser):\n    global _errok, _token, _restart\n    _errok = parser.errok\n    _token = parser.token\n    _restart = parser.restart\n    r = errorfunc(token)\n    try:\n        del _errok, _token, _restart\n    except NameError:\n        pass\n    return r\n\n#-----------------------------------------------------------------------------\n#                        ===  LR Parsing Engine ===\n#\n# The following classes are used for the LR parser itself.  These are not\n# used during table construction and are independent of the actual LR\n# table generation algorithm\n#-----------------------------------------------------------------------------\n\n# This class is used to hold non-terminal grammar symbols during parsing.\n# It normally has the following attributes set:\n#        .type       = Grammar symbol type\n#        .value      = Symbol value\n#        .lineno     = Starting line number\n#        .endlineno  = Ending line number (optional, set automatically)\n#        .lexpos     = Starting lex position\n#        .endlexpos  = Ending lex position (optional, set automatically)\n\nclass YaccSymbol:\n    def __str__(self):\n        return self.type\n\n    def __repr__(self):\n        return str(self)\n\n# This class is a wrapper around the objects actually passed to each\n# grammar rule.   Index lookup and assignment actually assign the\n# .value attribute of the underlying YaccSymbol object.\n# The lineno() method returns the line number of a given\n# item (or 0 if not defined).   The linespan() method returns\n# a tuple of (startline,endline) representing the range of lines\n# for a symbol.  The lexspan() method returns a tuple (lexpos,endlexpos)\n# representing the range of positional information for a symbol.\n\nclass YaccProduction:\n    def __init__(self, s, stack=None):\n        self.slice = s\n        self.stack = stack\n        self.lexer = None\n        self.parser = None\n\n    def __getitem__(self, n):\n        if isinstance(n, slice):\n            return [s.value for s in self.slice[n]]\n        elif n >= 0:\n            return self.slice[n].value\n        else:\n            return self.stack[n].value\n\n    def __setitem__(self, n, v):\n        self.slice[n].value = v\n\n    def __getslice__(self, i, j):\n        return [s.value for s in self.slice[i:j]]\n\n    def __len__(self):\n        return len(self.slice)\n\n    def lineno(self, n):\n        return getattr(self.slice[n], 'lineno', 0)\n\n    def set_lineno(self, n, lineno):\n        self.slice[n].lineno = lineno\n\n    def linespan(self, n):\n        startline = getattr(self.slice[n], 'lineno', 0)\n        endline = getattr(self.slice[n], 'endlineno', startline)\n        return startline, endline\n\n    def lexpos(self, n):\n        return getattr(self.slice[n], 'lexpos', 0)\n\n    def lexspan(self, n):\n        startpos = getattr(self.slice[n], 'lexpos', 0)\n        endpos = getattr(self.slice[n], 'endlexpos', startpos)\n        return startpos, endpos\n\n    def error(self):\n        raise SyntaxError\n\n# -----------------------------------------------------------------------------\n#                               == LRParser ==\n#\n# The LR Parsing engine.\n# -----------------------------------------------------------------------------\n\nclass LRParser:\n    def __init__(self, lrtab, errorf):\n        self.productions = lrtab.lr_productions\n        self.action = lrtab.lr_action\n        self.goto = lrtab.lr_goto\n        self.errorfunc = errorf\n        self.set_defaulted_states()\n        self.errorok = True\n\n    def errok(self):\n        self.errorok = True\n\n    def restart(self):\n        del self.statestack[:]\n        del self.symstack[:]\n        sym = YaccSymbol()\n        sym.type = '$end'\n        self.symstack.append(sym)\n        self.statestack.append(0)\n\n    # Defaulted state support.\n    # This method identifies parser states where there is only one possible reduction action.\n    # For such states, the parser can make a choose to make a rule reduction without consuming\n    # the next look-ahead token.  This delayed invocation of the tokenizer can be useful in\n    # certain kinds of advanced parsing situations where the lexer and parser interact with\n    # each other or change states (i.e., manipulation of scope, lexer states, etc.).\n    #\n    # See:  https://www.gnu.org/software/bison/manual/html_node/Default-Reductions.html#Default-Reductions\n    def set_defaulted_states(self):\n        self.defaulted_states = {}\n        for state, actions in self.action.items():\n            rules = list(actions.values())\n            if len(rules) == 1 and rules[0] < 0:\n                self.defaulted_states[state] = rules[0]\n\n    def disable_defaulted_states(self):\n        self.defaulted_states = {}\n\n    def parse(self, input=None, lexer=None, debug=False, tracking=False, tokenfunc=None):\n        if debug or yaccdevel:\n            if isinstance(debug, int):\n                debug = PlyLogger(sys.stderr)\n            return self.parsedebug(input, lexer, debug, tracking, tokenfunc)\n        elif tracking:\n            return self.parseopt(input, lexer, debug, tracking, tokenfunc)\n        else:\n            return self.parseopt_notrack(input, lexer, debug, tracking, tokenfunc)\n\n\n    # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n    # parsedebug().\n    #\n    # This is the debugging enabled version of parse().  All changes made to the\n    # parsing engine should be made here.   Optimized versions of this function\n    # are automatically created by the ply/ygen.py script.  This script cuts out\n    # sections enclosed in markers such as this:\n    #\n    #      #--! DEBUG\n    #      statements\n    #      #--! DEBUG\n    #\n    # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n\n    def parsedebug(self, input=None, lexer=None, debug=False, tracking=False, tokenfunc=None):\n        #--! parsedebug-start\n        lookahead = None                         # Current lookahead symbol\n        lookaheadstack = []                      # Stack of lookahead symbols\n        actions = self.action                    # Local reference to action table (to avoid lookup on self.)\n        goto    = self.goto                      # Local reference to goto table (to avoid lookup on self.)\n        prod    = self.productions               # Local reference to production list (to avoid lookup on self.)\n        defaulted_states = self.defaulted_states # Local reference to defaulted states\n        pslice  = YaccProduction(None)           # Production object passed to grammar rules\n        errorcount = 0                           # Used during error recovery\n\n        #--! DEBUG\n        debug.info('PLY: PARSE DEBUG START')\n        #--! DEBUG\n\n        # If no lexer was given, we will try to use the lex module\n        if not lexer:\n            from . import lex\n            lexer = lex.lexer\n\n        # Set up the lexer and parser objects on pslice\n        pslice.lexer = lexer\n        pslice.parser = self\n\n        # If input was supplied, pass to lexer\n        if input is not None:\n            lexer.input(input)\n\n        if tokenfunc is None:\n            # Tokenize function\n            get_token = lexer.token\n        else:\n            get_token = tokenfunc\n\n        # Set the parser() token method (sometimes used in error recovery)\n        self.token = get_token\n\n        # Set up the state and symbol stacks\n\n        statestack = []                # Stack of parsing states\n        self.statestack = statestack\n        symstack   = []                # Stack of grammar symbols\n        self.symstack = symstack\n\n        pslice.stack = symstack         # Put in the production\n        errtoken   = None               # Err token\n\n        # The start state is assumed to be (0,$end)\n\n        statestack.append(0)\n        sym = YaccSymbol()\n        sym.type = '$end'\n        symstack.append(sym)\n        state = 0\n        while True:\n            # Get the next symbol on the input.  If a lookahead symbol\n            # is already set, we just use that. Otherwise, we'll pull\n            # the next token off of the lookaheadstack or from the lexer\n\n            #--! DEBUG\n            debug.debug('')\n            debug.debug('State  : %s', state)\n            #--! DEBUG\n\n            if state not in defaulted_states:\n                if not lookahead:\n                    if not lookaheadstack:\n                        lookahead = get_token()     # Get the next token\n                    else:\n                        lookahead = lookaheadstack.pop()\n                    if not lookahead:\n                        lookahead = YaccSymbol()\n                        lookahead.type = '$end'\n\n                # Check the action table\n                ltype = lookahead.type\n                t = actions[state].get(ltype)\n            else:\n                t = defaulted_states[state]\n                #--! DEBUG\n                debug.debug('Defaulted state %s: Reduce using %d', state, -t)\n                #--! DEBUG\n\n            #--! DEBUG\n            debug.debug('Stack  : %s',\n                        ('%s . %s' % (' '.join([xx.type for xx in symstack][1:]), str(lookahead))).lstrip())\n            #--! DEBUG\n\n            if t is not None:\n                if t > 0:\n                    # shift a symbol on the stack\n                    statestack.append(t)\n                    state = t\n\n                    #--! DEBUG\n                    debug.debug('Action : Shift and goto state %s', t)\n                    #--! DEBUG\n\n                    symstack.append(lookahead)\n                    lookahead = None\n\n                    # Decrease error count on successful shift\n                    if errorcount:\n                        errorcount -= 1\n                    continue\n\n                if t < 0:\n                    # reduce a symbol on the stack, emit a production\n                    p = prod[-t]\n                    pname = p.name\n                    plen  = p.len\n\n                    # Get production function\n                    sym = YaccSymbol()\n                    sym.type = pname       # Production name\n                    sym.value = None\n\n                    #--! DEBUG\n                    if plen:\n                        debug.info('Action : Reduce rule [%s] with %s and goto state %d', p.str,\n                                   '['+','.join([format_stack_entry(_v.value) for _v in symstack[-plen:]])+']',\n                                   goto[statestack[-1-plen]][pname])\n                    else:\n                        debug.info('Action : Reduce rule [%s] with %s and goto state %d', p.str, [],\n                                   goto[statestack[-1]][pname])\n\n                    #--! DEBUG\n\n                    if plen:\n                        targ = symstack[-plen-1:]\n                        targ[0] = sym\n\n                        #--! TRACKING\n                        if tracking:\n                            t1 = targ[1]\n                            sym.lineno = t1.lineno\n                            sym.lexpos = t1.lexpos\n                            t1 = targ[-1]\n                            sym.endlineno = getattr(t1, 'endlineno', t1.lineno)\n                            sym.endlexpos = getattr(t1, 'endlexpos', t1.lexpos)\n                        #--! TRACKING\n\n                        # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n                        # The code enclosed in this section is duplicated\n                        # below as a performance optimization.  Make sure\n                        # changes get made in both locations.\n\n                        pslice.slice = targ\n\n                        try:\n                            # Call the grammar rule with our special slice object\n                            del symstack[-plen:]\n                            self.state = state\n                            p.callable(pslice)\n                            del statestack[-plen:]\n                            #--! DEBUG\n                            debug.info('Result : %s', format_result(pslice[0]))\n                            #--! DEBUG\n                            symstack.append(sym)\n                            state = goto[statestack[-1]][pname]\n                            statestack.append(state)\n                        except SyntaxError:\n                            # If an error was set. Enter error recovery state\n                            lookaheadstack.append(lookahead)    # Save the current lookahead token\n                            symstack.extend(targ[1:-1])         # Put the production slice back on the stack\n                            statestack.pop()                    # Pop back one state (before the reduce)\n                            state = statestack[-1]\n                            sym.type = 'error'\n                            sym.value = 'error'\n                            lookahead = sym\n                            errorcount = error_count\n                            self.errorok = False\n\n                        continue\n                        # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n\n                    else:\n\n                        #--! TRACKING\n                        if tracking:\n                            sym.lineno = lexer.lineno\n                            sym.lexpos = lexer.lexpos\n                        #--! TRACKING\n\n                        targ = [sym]\n\n                        # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n                        # The code enclosed in this section is duplicated\n                        # above as a performance optimization.  Make sure\n                        # changes get made in both locations.\n\n                        pslice.slice = targ\n\n                        try:\n                            # Call the grammar rule with our special slice object\n                            self.state = state\n                            p.callable(pslice)\n                            #--! DEBUG\n                            debug.info('Result : %s', format_result(pslice[0]))\n                            #--! DEBUG\n                            symstack.append(sym)\n                            state = goto[statestack[-1]][pname]\n                            statestack.append(state)\n                        except SyntaxError:\n                            # If an error was set. Enter error recovery state\n                            lookaheadstack.append(lookahead)    # Save the current lookahead token\n                            statestack.pop()                    # Pop back one state (before the reduce)\n                            state = statestack[-1]\n                            sym.type = 'error'\n                            sym.value = 'error'\n                            lookahead = sym\n                            errorcount = error_count\n                            self.errorok = False\n\n                        continue\n                        # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n\n                if t == 0:\n                    n = symstack[-1]\n                    result = getattr(n, 'value', None)\n                    #--! DEBUG\n                    debug.info('Done   : Returning %s', format_result(result))\n                    debug.info('PLY: PARSE DEBUG END')\n                    #--! DEBUG\n                    return result\n\n            if t is None:\n\n                #--! DEBUG\n                debug.error('Error  : %s',\n                            ('%s . %s' % (' '.join([xx.type for xx in symstack][1:]), str(lookahead))).lstrip())\n                #--! DEBUG\n\n                # We have some kind of parsing error here.  To handle\n                # this, we are going to push the current token onto\n                # the tokenstack and replace it with an 'error' token.\n                # If there are any synchronization rules, they may\n                # catch it.\n                #\n                # In addition to pushing the error token, we call call\n                # the user defined p_error() function if this is the\n                # first syntax error.  This function is only called if\n                # errorcount == 0.\n                if errorcount == 0 or self.errorok:\n                    errorcount = error_count\n                    self.errorok = False\n                    errtoken = lookahead\n                    if errtoken.type == '$end':\n                        errtoken = None               # End of file!\n                    if self.errorfunc:\n                        if errtoken and not hasattr(errtoken, 'lexer'):\n                            errtoken.lexer = lexer\n                        self.state = state\n                        tok = call_errorfunc(self.errorfunc, errtoken, self)\n                        if self.errorok:\n                            # User must have done some kind of panic\n                            # mode recovery on their own.  The\n                            # returned token is the next lookahead\n                            lookahead = tok\n                            errtoken = None\n                            continue\n                    else:\n                        if errtoken:\n                            if hasattr(errtoken, 'lineno'):\n                                lineno = lookahead.lineno\n                            else:\n                                lineno = 0\n                            if lineno:\n                                sys.stderr.write('yacc: Syntax error at line %d, token=%s\\n' % (lineno, errtoken.type))\n                            else:\n                                sys.stderr.write('yacc: Syntax error, token=%s' % errtoken.type)\n                        else:\n                            sys.stderr.write('yacc: Parse error in input. EOF\\n')\n                            return\n\n                else:\n                    errorcount = error_count\n\n                # case 1:  the statestack only has 1 entry on it.  If we're in this state, the\n                # entire parse has been rolled back and we're completely hosed.   The token is\n                # discarded and we just keep going.\n\n                if len(statestack) <= 1 and lookahead.type != '$end':\n                    lookahead = None\n                    errtoken = None\n                    state = 0\n                    # Nuke the pushback stack\n                    del lookaheadstack[:]\n                    continue\n\n                # case 2: the statestack has a couple of entries on it, but we're\n                # at the end of the file. nuke the top entry and generate an error token\n\n                # Start nuking entries on the stack\n                if lookahead.type == '$end':\n                    # Whoa. We're really hosed here. Bail out\n                    return\n\n                if lookahead.type != 'error':\n                    sym = symstack[-1]\n                    if sym.type == 'error':\n                        # Hmmm. Error is on top of stack, we'll just nuke input\n                        # symbol and continue\n                        #--! TRACKING\n                        if tracking:\n                            sym.endlineno = getattr(lookahead, 'lineno', sym.lineno)\n                            sym.endlexpos = getattr(lookahead, 'lexpos', sym.lexpos)\n                        #--! TRACKING\n                        lookahead = None\n                        continue\n\n                    # Create the error symbol for the first time and make it the new lookahead symbol\n                    t = YaccSymbol()\n                    t.type = 'error'\n\n                    if hasattr(lookahead, 'lineno'):\n                        t.lineno = t.endlineno = lookahead.lineno\n                    if hasattr(lookahead, 'lexpos'):\n                        t.lexpos = t.endlexpos = lookahead.lexpos\n                    t.value = lookahead\n                    lookaheadstack.append(lookahead)\n                    lookahead = t\n                else:\n                    sym = symstack.pop()\n                    #--! TRACKING\n                    if tracking:\n                        lookahead.lineno = sym.lineno\n                        lookahead.lexpos = sym.lexpos\n                    #--! TRACKING\n                    statestack.pop()\n                    state = statestack[-1]\n\n                continue\n\n            # Call an error function here\n            raise RuntimeError('yacc: internal parser error!!!\\n')\n\n        #--! parsedebug-end\n\n    # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n    # parseopt().\n    #\n    # Optimized version of parse() method.  DO NOT EDIT THIS CODE DIRECTLY!\n    # This code is automatically generated by the ply/ygen.py script. Make\n    # changes to the parsedebug() method instead.\n    # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n\n    def parseopt(self, input=None, lexer=None, debug=False, tracking=False, tokenfunc=None):\n        #--! parseopt-start\n        lookahead = None                         # Current lookahead symbol\n        lookaheadstack = []                      # Stack of lookahead symbols\n        actions = self.action                    # Local reference to action table (to avoid lookup on self.)\n        goto    = self.goto                      # Local reference to goto table (to avoid lookup on self.)\n        prod    = self.productions               # Local reference to production list (to avoid lookup on self.)\n        defaulted_states = self.defaulted_states # Local reference to defaulted states\n        pslice  = YaccProduction(None)           # Production object passed to grammar rules\n        errorcount = 0                           # Used during error recovery\n\n\n        # If no lexer was given, we will try to use the lex module\n        if not lexer:\n            from . import lex\n            lexer = lex.lexer\n\n        # Set up the lexer and parser objects on pslice\n        pslice.lexer = lexer\n        pslice.parser = self\n\n        # If input was supplied, pass to lexer\n        if input is not None:\n            lexer.input(input)\n\n        if tokenfunc is None:\n            # Tokenize function\n            get_token = lexer.token\n        else:\n            get_token = tokenfunc\n\n        # Set the parser() token method (sometimes used in error recovery)\n        self.token = get_token\n\n        # Set up the state and symbol stacks\n\n        statestack = []                # Stack of parsing states\n        self.statestack = statestack\n        symstack   = []                # Stack of grammar symbols\n        self.symstack = symstack\n\n        pslice.stack = symstack         # Put in the production\n        errtoken   = None               # Err token\n\n        # The start state is assumed to be (0,$end)\n\n        statestack.append(0)\n        sym = YaccSymbol()\n        sym.type = '$end'\n        symstack.append(sym)\n        state = 0\n        while True:\n            # Get the next symbol on the input.  If a lookahead symbol\n            # is already set, we just use that. Otherwise, we'll pull\n            # the next token off of the lookaheadstack or from the lexer\n\n\n            if state not in defaulted_states:\n                if not lookahead:\n                    if not lookaheadstack:\n                        lookahead = get_token()     # Get the next token\n                    else:\n                        lookahead = lookaheadstack.pop()\n                    if not lookahead:\n                        lookahead = YaccSymbol()\n                        lookahead.type = '$end'\n\n                # Check the action table\n                ltype = lookahead.type\n                t = actions[state].get(ltype)\n            else:\n                t = defaulted_states[state]\n\n\n            if t is not None:\n                if t > 0:\n                    # shift a symbol on the stack\n                    statestack.append(t)\n                    state = t\n\n\n                    symstack.append(lookahead)\n                    lookahead = None\n\n                    # Decrease error count on successful shift\n                    if errorcount:\n                        errorcount -= 1\n                    continue\n\n                if t < 0:\n                    # reduce a symbol on the stack, emit a production\n                    p = prod[-t]\n                    pname = p.name\n                    plen  = p.len\n\n                    # Get production function\n                    sym = YaccSymbol()\n                    sym.type = pname       # Production name\n                    sym.value = None\n\n\n                    if plen:\n                        targ = symstack[-plen-1:]\n                        targ[0] = sym\n\n                        #--! TRACKING\n                        if tracking:\n                            t1 = targ[1]\n                            sym.lineno = t1.lineno\n                            sym.lexpos = t1.lexpos\n                            t1 = targ[-1]\n                            sym.endlineno = getattr(t1, 'endlineno', t1.lineno)\n                            sym.endlexpos = getattr(t1, 'endlexpos', t1.lexpos)\n                        #--! TRACKING\n\n                        # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n                        # The code enclosed in this section is duplicated\n                        # below as a performance optimization.  Make sure\n                        # changes get made in both locations.\n\n                        pslice.slice = targ\n\n                        try:\n                            # Call the grammar rule with our special slice object\n                            del symstack[-plen:]\n                            self.state = state\n                            p.callable(pslice)\n                            del statestack[-plen:]\n                            symstack.append(sym)\n                            state = goto[statestack[-1]][pname]\n                            statestack.append(state)\n                        except SyntaxError:\n                            # If an error was set. Enter error recovery state\n                            lookaheadstack.append(lookahead)    # Save the current lookahead token\n                            symstack.extend(targ[1:-1])         # Put the production slice back on the stack\n                            statestack.pop()                    # Pop back one state (before the reduce)\n                            state = statestack[-1]\n                            sym.type = 'error'\n                            sym.value = 'error'\n                            lookahead = sym\n                            errorcount = error_count\n                            self.errorok = False\n\n                        continue\n                        # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n\n                    else:\n\n                        #--! TRACKING\n                        if tracking:\n                            sym.lineno = lexer.lineno\n                            sym.lexpos = lexer.lexpos\n                        #--! TRACKING\n\n                        targ = [sym]\n\n                        # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n                        # The code enclosed in this section is duplicated\n                        # above as a performance optimization.  Make sure\n                        # changes get made in both locations.\n\n                        pslice.slice = targ\n\n                        try:\n                            # Call the grammar rule with our special slice object\n                            self.state = state\n                            p.callable(pslice)\n                            symstack.append(sym)\n                            state = goto[statestack[-1]][pname]\n                            statestack.append(state)\n                        except SyntaxError:\n                            # If an error was set. Enter error recovery state\n                            lookaheadstack.append(lookahead)    # Save the current lookahead token\n                            statestack.pop()                    # Pop back one state (before the reduce)\n                            state = statestack[-1]\n                            sym.type = 'error'\n                            sym.value = 'error'\n                            lookahead = sym\n                            errorcount = error_count\n                            self.errorok = False\n\n                        continue\n                        # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n\n                if t == 0:\n                    n = symstack[-1]\n                    result = getattr(n, 'value', None)\n                    return result\n\n            if t is None:\n\n\n                # We have some kind of parsing error here.  To handle\n                # this, we are going to push the current token onto\n                # the tokenstack and replace it with an 'error' token.\n                # If there are any synchronization rules, they may\n                # catch it.\n                #\n                # In addition to pushing the error token, we call call\n                # the user defined p_error() function if this is the\n                # first syntax error.  This function is only called if\n                # errorcount == 0.\n                if errorcount == 0 or self.errorok:\n                    errorcount = error_count\n                    self.errorok = False\n                    errtoken = lookahead\n                    if errtoken.type == '$end':\n                        errtoken = None               # End of file!\n                    if self.errorfunc:\n                        if errtoken and not hasattr(errtoken, 'lexer'):\n                            errtoken.lexer = lexer\n                        self.state = state\n                        tok = call_errorfunc(self.errorfunc, errtoken, self)\n                        if self.errorok:\n                            # User must have done some kind of panic\n                            # mode recovery on their own.  The\n                            # returned token is the next lookahead\n                            lookahead = tok\n                            errtoken = None\n                            continue\n                    else:\n                        if errtoken:\n                            if hasattr(errtoken, 'lineno'):\n                                lineno = lookahead.lineno\n                            else:\n                                lineno = 0\n                            if lineno:\n                                sys.stderr.write('yacc: Syntax error at line %d, token=%s\\n' % (lineno, errtoken.type))\n                            else:\n                                sys.stderr.write('yacc: Syntax error, token=%s' % errtoken.type)\n                        else:\n                            sys.stderr.write('yacc: Parse error in input. EOF\\n')\n                            return\n\n                else:\n                    errorcount = error_count\n\n                # case 1:  the statestack only has 1 entry on it.  If we're in this state, the\n                # entire parse has been rolled back and we're completely hosed.   The token is\n                # discarded and we just keep going.\n\n                if len(statestack) <= 1 and lookahead.type != '$end':\n                    lookahead = None\n                    errtoken = None\n                    state = 0\n                    # Nuke the pushback stack\n                    del lookaheadstack[:]\n                    continue\n\n                # case 2: the statestack has a couple of entries on it, but we're\n                # at the end of the file. nuke the top entry and generate an error token\n\n                # Start nuking entries on the stack\n                if lookahead.type == '$end':\n                    # Whoa. We're really hosed here. Bail out\n                    return\n\n                if lookahead.type != 'error':\n                    sym = symstack[-1]\n                    if sym.type == 'error':\n                        # Hmmm. Error is on top of stack, we'll just nuke input\n                        # symbol and continue\n                        #--! TRACKING\n                        if tracking:\n                            sym.endlineno = getattr(lookahead, 'lineno', sym.lineno)\n                            sym.endlexpos = getattr(lookahead, 'lexpos', sym.lexpos)\n                        #--! TRACKING\n                        lookahead = None\n                        continue\n\n                    # Create the error symbol for the first time and make it the new lookahead symbol\n                    t = YaccSymbol()\n                    t.type = 'error'\n\n                    if hasattr(lookahead, 'lineno'):\n                        t.lineno = t.endlineno = lookahead.lineno\n                    if hasattr(lookahead, 'lexpos'):\n                        t.lexpos = t.endlexpos = lookahead.lexpos\n                    t.value = lookahead\n                    lookaheadstack.append(lookahead)\n                    lookahead = t\n                else:\n                    sym = symstack.pop()\n                    #--! TRACKING\n                    if tracking:\n                        lookahead.lineno = sym.lineno\n                        lookahead.lexpos = sym.lexpos\n                    #--! TRACKING\n                    statestack.pop()\n                    state = statestack[-1]\n\n                continue\n\n            # Call an error function here\n            raise RuntimeError('yacc: internal parser error!!!\\n')\n\n        #--! parseopt-end\n\n    # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n    # parseopt_notrack().\n    #\n    # Optimized version of parseopt() with line number tracking removed.\n    # DO NOT EDIT THIS CODE DIRECTLY. This code is automatically generated\n    # by the ply/ygen.py script. Make changes to the parsedebug() method instead.\n    # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n\n    def parseopt_notrack(self, input=None, lexer=None, debug=False, tracking=False, tokenfunc=None):\n        #--! parseopt-notrack-start\n        lookahead = None                         # Current lookahead symbol\n        lookaheadstack = []                      # Stack of lookahead symbols\n        actions = self.action                    # Local reference to action table (to avoid lookup on self.)\n        goto    = self.goto                      # Local reference to goto table (to avoid lookup on self.)\n        prod    = self.productions               # Local reference to production list (to avoid lookup on self.)\n        defaulted_states = self.defaulted_states # Local reference to defaulted states\n        pslice  = YaccProduction(None)           # Production object passed to grammar rules\n        errorcount = 0                           # Used during error recovery\n\n\n        # If no lexer was given, we will try to use the lex module\n        if not lexer:\n            from . import lex\n            lexer = lex.lexer\n\n        # Set up the lexer and parser objects on pslice\n        pslice.lexer = lexer\n        pslice.parser = self\n\n        # If input was supplied, pass to lexer\n        if input is not None:\n            lexer.input(input)\n\n        if tokenfunc is None:\n            # Tokenize function\n            get_token = lexer.token\n        else:\n            get_token = tokenfunc\n\n        # Set the parser() token method (sometimes used in error recovery)\n        self.token = get_token\n\n        # Set up the state and symbol stacks\n\n        statestack = []                # Stack of parsing states\n        self.statestack = statestack\n        symstack   = []                # Stack of grammar symbols\n        self.symstack = symstack\n\n        pslice.stack = symstack         # Put in the production\n        errtoken   = None               # Err token\n\n        # The start state is assumed to be (0,$end)\n\n        statestack.append(0)\n        sym = YaccSymbol()\n        sym.type = '$end'\n        symstack.append(sym)\n        state = 0\n        while True:\n            # Get the next symbol on the input.  If a lookahead symbol\n            # is already set, we just use that. Otherwise, we'll pull\n            # the next token off of the lookaheadstack or from the lexer\n\n\n            if state not in defaulted_states:\n                if not lookahead:\n                    if not lookaheadstack:\n                        lookahead = get_token()     # Get the next token\n                    else:\n                        lookahead = lookaheadstack.pop()\n                    if not lookahead:\n                        lookahead = YaccSymbol()\n                        lookahead.type = '$end'\n\n                # Check the action table\n                ltype = lookahead.type\n                t = actions[state].get(ltype)\n            else:\n                t = defaulted_states[state]\n\n\n            if t is not None:\n                if t > 0:\n                    # shift a symbol on the stack\n                    statestack.append(t)\n                    state = t\n\n\n                    symstack.append(lookahead)\n                    lookahead = None\n\n                    # Decrease error count on successful shift\n                    if errorcount:\n                        errorcount -= 1\n                    continue\n\n                if t < 0:\n                    # reduce a symbol on the stack, emit a production\n                    p = prod[-t]\n                    pname = p.name\n                    plen  = p.len\n\n                    # Get production function\n                    sym = YaccSymbol()\n                    sym.type = pname       # Production name\n                    sym.value = None\n\n\n                    if plen:\n                        targ = symstack[-plen-1:]\n                        targ[0] = sym\n\n\n                        # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n                        # The code enclosed in this section is duplicated\n                        # below as a performance optimization.  Make sure\n                        # changes get made in both locations.\n\n                        pslice.slice = targ\n\n                        try:\n                            # Call the grammar rule with our special slice object\n                            del symstack[-plen:]\n                            self.state = state\n                            p.callable(pslice)\n                            del statestack[-plen:]\n                            symstack.append(sym)\n                            state = goto[statestack[-1]][pname]\n                            statestack.append(state)\n                        except SyntaxError:\n                            # If an error was set. Enter error recovery state\n                            lookaheadstack.append(lookahead)    # Save the current lookahead token\n                            symstack.extend(targ[1:-1])         # Put the production slice back on the stack\n                            statestack.pop()                    # Pop back one state (before the reduce)\n                            state = statestack[-1]\n                            sym.type = 'error'\n                            sym.value = 'error'\n                            lookahead = sym\n                            errorcount = error_count\n                            self.errorok = False\n\n                        continue\n                        # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n\n                    else:\n\n\n                        targ = [sym]\n\n                        # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n                        # The code enclosed in this section is duplicated\n                        # above as a performance optimization.  Make sure\n                        # changes get made in both locations.\n\n                        pslice.slice = targ\n\n                        try:\n                            # Call the grammar rule with our special slice object\n                            self.state = state\n                            p.callable(pslice)\n                            symstack.append(sym)\n                            state = goto[statestack[-1]][pname]\n                            statestack.append(state)\n                        except SyntaxError:\n                            # If an error was set. Enter error recovery state\n                            lookaheadstack.append(lookahead)    # Save the current lookahead token\n                            statestack.pop()                    # Pop back one state (before the reduce)\n                            state = statestack[-1]\n                            sym.type = 'error'\n                            sym.value = 'error'\n                            lookahead = sym\n                            errorcount = error_count\n                            self.errorok = False\n\n                        continue\n                        # !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n\n                if t == 0:\n                    n = symstack[-1]\n                    result = getattr(n, 'value', None)\n                    return result\n\n            if t is None:\n\n\n                # We have some kind of parsing error here.  To handle\n                # this, we are going to push the current token onto\n                # the tokenstack and replace it with an 'error' token.\n                # If there are any synchronization rules, they may\n                # catch it.\n                #\n                # In addition to pushing the error token, we call call\n                # the user defined p_error() function if this is the\n                # first syntax error.  This function is only called if\n                # errorcount == 0.\n                if errorcount == 0 or self.errorok:\n                    errorcount = error_count\n                    self.errorok = False\n                    errtoken = lookahead\n                    if errtoken.type == '$end':\n                        errtoken = None               # End of file!\n                    if self.errorfunc:\n                        if errtoken and not hasattr(errtoken, 'lexer'):\n                            errtoken.lexer = lexer\n                        self.state = state\n                        tok = call_errorfunc(self.errorfunc, errtoken, self)\n                        if self.errorok:\n                            # User must have done some kind of panic\n                            # mode recovery on their own.  The\n                            # returned token is the next lookahead\n                            lookahead = tok\n                            errtoken = None\n                            continue\n                    else:\n                        if errtoken:\n                            if hasattr(errtoken, 'lineno'):\n                                lineno = lookahead.lineno\n                            else:\n                                lineno = 0\n                            if lineno:\n                                sys.stderr.write('yacc: Syntax error at line %d, token=%s\\n' % (lineno, errtoken.type))\n                            else:\n                                sys.stderr.write('yacc: Syntax error, token=%s' % errtoken.type)\n                        else:\n                            sys.stderr.write('yacc: Parse error in input. EOF\\n')\n                            return\n\n                else:\n                    errorcount = error_count\n\n                # case 1:  the statestack only has 1 entry on it.  If we're in this state, the\n                # entire parse has been rolled back and we're completely hosed.   The token is\n                # discarded and we just keep going.\n\n                if len(statestack) <= 1 and lookahead.type != '$end':\n                    lookahead = None\n                    errtoken = None\n                    state = 0\n                    # Nuke the pushback stack\n                    del lookaheadstack[:]\n                    continue\n\n                # case 2: the statestack has a couple of entries on it, but we're\n                # at the end of the file. nuke the top entry and generate an error token\n\n                # Start nuking entries on the stack\n                if lookahead.type == '$end':\n                    # Whoa. We're really hosed here. Bail out\n                    return\n\n                if lookahead.type != 'error':\n                    sym = symstack[-1]\n                    if sym.type == 'error':\n                        # Hmmm. Error is on top of stack, we'll just nuke input\n                        # symbol and continue\n                        lookahead = None\n                        continue\n\n                    # Create the error symbol for the first time and make it the new lookahead symbol\n                    t = YaccSymbol()\n                    t.type = 'error'\n\n                    if hasattr(lookahead, 'lineno'):\n                        t.lineno = t.endlineno = lookahead.lineno\n                    if hasattr(lookahead, 'lexpos'):\n                        t.lexpos = t.endlexpos = lookahead.lexpos\n                    t.value = lookahead\n                    lookaheadstack.append(lookahead)\n                    lookahead = t\n                else:\n                    sym = symstack.pop()\n                    statestack.pop()\n                    state = statestack[-1]\n\n                continue\n\n            # Call an error function here\n            raise RuntimeError('yacc: internal parser error!!!\\n')\n\n        #--! parseopt-notrack-end\n\n# -----------------------------------------------------------------------------\n#                          === Grammar Representation ===\n#\n# The following functions, classes, and variables are used to represent and\n# manipulate the rules that make up a grammar.\n# -----------------------------------------------------------------------------\n\n# regex matching identifiers\n_is_identifier = re.compile(r'^[a-zA-Z0-9_-]+$')\n\n# -----------------------------------------------------------------------------\n# class Production:\n#\n# This class stores the raw information about a single production or grammar rule.\n# A grammar rule refers to a specification such as this:\n#\n#       expr : expr PLUS term\n#\n# Here are the basic attributes defined on all productions\n#\n#       name     - Name of the production.  For example 'expr'\n#       prod     - A list of symbols on the right side ['expr','PLUS','term']\n#       prec     - Production precedence level\n#       number   - Production number.\n#       func     - Function that executes on reduce\n#       file     - File where production function is defined\n#       lineno   - Line number where production function is defined\n#\n# The following attributes are defined or optional.\n#\n#       len       - Length of the production (number of symbols on right hand side)\n#       usyms     - Set of unique symbols found in the production\n# -----------------------------------------------------------------------------\n\nclass Production(object):\n    reduced = 0\n    def __init__(self, number, name, prod, precedence=('right', 0), func=None, file='', line=0):\n        self.name     = name\n        self.prod     = tuple(prod)\n        self.number   = number\n        self.func     = func\n        self.callable = None\n        self.file     = file\n        self.line     = line\n        self.prec     = precedence\n\n        # Internal settings used during table construction\n\n        self.len  = len(self.prod)   # Length of the production\n\n        # Create a list of unique production symbols used in the production\n        self.usyms = []\n        for s in self.prod:\n            if s not in self.usyms:\n                self.usyms.append(s)\n\n        # List of all LR items for the production\n        self.lr_items = []\n        self.lr_next = None\n\n        # Create a string representation\n        if self.prod:\n            self.str = '%s -> %s' % (self.name, ' '.join(self.prod))\n        else:\n            self.str = '%s -> <empty>' % self.name\n\n    def __str__(self):\n        return self.str\n\n    def __repr__(self):\n        return 'Production(' + str(self) + ')'\n\n    def __len__(self):\n        return len(self.prod)\n\n    def __nonzero__(self):\n        return 1\n\n    def __getitem__(self, index):\n        return self.prod[index]\n\n    # Return the nth lr_item from the production (or None if at the end)\n    def lr_item(self, n):\n        if n > len(self.prod):\n            return None\n        p = LRItem(self, n)\n        # Precompute the list of productions immediately following.\n        try:\n            p.lr_after = Prodnames[p.prod[n+1]]\n        except (IndexError, KeyError):\n            p.lr_after = []\n        try:\n            p.lr_before = p.prod[n-1]\n        except IndexError:\n            p.lr_before = None\n        return p\n\n    # Bind the production function name to a callable\n    def bind(self, pdict):\n        if self.func:\n            self.callable = pdict[self.func]\n\n# This class serves as a minimal standin for Production objects when\n# reading table data from files.   It only contains information\n# actually used by the LR parsing engine, plus some additional\n# debugging information.\nclass MiniProduction(object):\n    def __init__(self, str, name, len, func, file, line):\n        self.name     = name\n        self.len      = len\n        self.func     = func\n        self.callable = None\n        self.file     = file\n        self.line     = line\n        self.str      = str\n\n    def __str__(self):\n        return self.str\n\n    def __repr__(self):\n        return 'MiniProduction(%s)' % self.str\n\n    # Bind the production function name to a callable\n    def bind(self, pdict):\n        if self.func:\n            self.callable = pdict[self.func]\n\n\n# -----------------------------------------------------------------------------\n# class LRItem\n#\n# This class represents a specific stage of parsing a production rule.  For\n# example:\n#\n#       expr : expr . PLUS term\n#\n# In the above, the \".\" represents the current location of the parse.  Here\n# basic attributes:\n#\n#       name       - Name of the production.  For example 'expr'\n#       prod       - A list of symbols on the right side ['expr','.', 'PLUS','term']\n#       number     - Production number.\n#\n#       lr_next      Next LR item. Example, if we are ' expr -> expr . PLUS term'\n#                    then lr_next refers to 'expr -> expr PLUS . term'\n#       lr_index   - LR item index (location of the \".\") in the prod list.\n#       lookaheads - LALR lookahead symbols for this item\n#       len        - Length of the production (number of symbols on right hand side)\n#       lr_after    - List of all productions that immediately follow\n#       lr_before   - Grammar symbol immediately before\n# -----------------------------------------------------------------------------\n\nclass LRItem(object):\n    def __init__(self, p, n):\n        self.name       = p.name\n        self.prod       = list(p.prod)\n        self.number     = p.number\n        self.lr_index   = n\n        self.lookaheads = {}\n        self.prod.insert(n, '.')\n        self.prod       = tuple(self.prod)\n        self.len        = len(self.prod)\n        self.usyms      = p.usyms\n\n    def __str__(self):\n        if self.prod:\n            s = '%s -> %s' % (self.name, ' '.join(self.prod))\n        else:\n            s = '%s -> <empty>' % self.name\n        return s\n\n    def __repr__(self):\n        return 'LRItem(' + str(self) + ')'\n\n# -----------------------------------------------------------------------------\n# rightmost_terminal()\n#\n# Return the rightmost terminal from a list of symbols.  Used in add_production()\n# -----------------------------------------------------------------------------\ndef rightmost_terminal(symbols, terminals):\n    i = len(symbols) - 1\n    while i >= 0:\n        if symbols[i] in terminals:\n            return symbols[i]\n        i -= 1\n    return None\n\n# -----------------------------------------------------------------------------\n#                           === GRAMMAR CLASS ===\n#\n# The following class represents the contents of the specified grammar along\n# with various computed properties such as first sets, follow sets, LR items, etc.\n# This data is used for critical parts of the table generation process later.\n# -----------------------------------------------------------------------------\n\nclass GrammarError(YaccError):\n    pass\n\nclass Grammar(object):\n    def __init__(self, terminals):\n        self.Productions  = [None]  # A list of all of the productions.  The first\n                                    # entry is always reserved for the purpose of\n                                    # building an augmented grammar\n\n        self.Prodnames    = {}      # A dictionary mapping the names of nonterminals to a list of all\n                                    # productions of that nonterminal.\n\n        self.Prodmap      = {}      # A dictionary that is only used to detect duplicate\n                                    # productions.\n\n        self.Terminals    = {}      # A dictionary mapping the names of terminal symbols to a\n                                    # list of the rules where they are used.\n\n        for term in terminals:\n            self.Terminals[term] = []\n\n        self.Terminals['error'] = []\n\n        self.Nonterminals = {}      # A dictionary mapping names of nonterminals to a list\n                                    # of rule numbers where they are used.\n\n        self.First        = {}      # A dictionary of precomputed FIRST(x) symbols\n\n        self.Follow       = {}      # A dictionary of precomputed FOLLOW(x) symbols\n\n        self.Precedence   = {}      # Precedence rules for each terminal. Contains tuples of the\n                                    # form ('right',level) or ('nonassoc', level) or ('left',level)\n\n        self.UsedPrecedence = set() # Precedence rules that were actually used by the grammer.\n                                    # This is only used to provide error checking and to generate\n                                    # a warning about unused precedence rules.\n\n        self.Start = None           # Starting symbol for the grammar\n\n\n    def __len__(self):\n        return len(self.Productions)\n\n    def __getitem__(self, index):\n        return self.Productions[index]\n\n    # -----------------------------------------------------------------------------\n    # set_precedence()\n    #\n    # Sets the precedence for a given terminal. assoc is the associativity such as\n    # 'left','right', or 'nonassoc'.  level is a numeric level.\n    #\n    # -----------------------------------------------------------------------------\n\n    def set_precedence(self, term, assoc, level):\n        assert self.Productions == [None], 'Must call set_precedence() before add_production()'\n        if term in self.Precedence:\n            raise GrammarError('Precedence already specified for terminal %r' % term)\n        if assoc not in ['left', 'right', 'nonassoc']:\n            raise GrammarError(\"Associativity must be one of 'left','right', or 'nonassoc'\")\n        self.Precedence[term] = (assoc, level)\n\n    # -----------------------------------------------------------------------------\n    # add_production()\n    #\n    # Given an action function, this function assembles a production rule and\n    # computes its precedence level.\n    #\n    # The production rule is supplied as a list of symbols.   For example,\n    # a rule such as 'expr : expr PLUS term' has a production name of 'expr' and\n    # symbols ['expr','PLUS','term'].\n    #\n    # Precedence is determined by the precedence of the right-most non-terminal\n    # or the precedence of a terminal specified by %prec.\n    #\n    # A variety of error checks are performed to make sure production symbols\n    # are valid and that %prec is used correctly.\n    # -----------------------------------------------------------------------------\n\n    def add_production(self, prodname, syms, func=None, file='', line=0):\n\n        if prodname in self.Terminals:\n            raise GrammarError('%s:%d: Illegal rule name %r. Already defined as a token' % (file, line, prodname))\n        if prodname == 'error':\n            raise GrammarError('%s:%d: Illegal rule name %r. error is a reserved word' % (file, line, prodname))\n        if not _is_identifier.match(prodname):\n            raise GrammarError('%s:%d: Illegal rule name %r' % (file, line, prodname))\n\n        # Look for literal tokens\n        for n, s in enumerate(syms):\n            if s[0] in \"'\\\"\":\n                try:\n                    c = eval(s)\n                    if (len(c) > 1):\n                        raise GrammarError('%s:%d: Literal token %s in rule %r may only be a single character' %\n                                           (file, line, s, prodname))\n                    if c not in self.Terminals:\n                        self.Terminals[c] = []\n                    syms[n] = c\n                    continue\n                except SyntaxError:\n                    pass\n            if not _is_identifier.match(s) and s != '%prec':\n                raise GrammarError('%s:%d: Illegal name %r in rule %r' % (file, line, s, prodname))\n\n        # Determine the precedence level\n        if '%prec' in syms:\n            if syms[-1] == '%prec':\n                raise GrammarError('%s:%d: Syntax error. Nothing follows %%prec' % (file, line))\n            if syms[-2] != '%prec':\n                raise GrammarError('%s:%d: Syntax error. %%prec can only appear at the end of a grammar rule' %\n                                   (file, line))\n            precname = syms[-1]\n            prodprec = self.Precedence.get(precname)\n            if not prodprec:\n                raise GrammarError('%s:%d: Nothing known about the precedence of %r' % (file, line, precname))\n            else:\n                self.UsedPrecedence.add(precname)\n            del syms[-2:]     # Drop %prec from the rule\n        else:\n            # If no %prec, precedence is determined by the rightmost terminal symbol\n            precname = rightmost_terminal(syms, self.Terminals)\n            prodprec = self.Precedence.get(precname, ('right', 0))\n\n        # See if the rule is already in the rulemap\n        map = '%s -> %s' % (prodname, syms)\n        if map in self.Prodmap:\n            m = self.Prodmap[map]\n            raise GrammarError('%s:%d: Duplicate rule %s. ' % (file, line, m) +\n                               'Previous definition at %s:%d' % (m.file, m.line))\n\n        # From this point on, everything is valid.  Create a new Production instance\n        pnumber  = len(self.Productions)\n        if prodname not in self.Nonterminals:\n            self.Nonterminals[prodname] = []\n\n        # Add the production number to Terminals and Nonterminals\n        for t in syms:\n            if t in self.Terminals:\n                self.Terminals[t].append(pnumber)\n            else:\n                if t not in self.Nonterminals:\n                    self.Nonterminals[t] = []\n                self.Nonterminals[t].append(pnumber)\n\n        # Create a production and add it to the list of productions\n        p = Production(pnumber, prodname, syms, prodprec, func, file, line)\n        self.Productions.append(p)\n        self.Prodmap[map] = p\n\n        # Add to the global productions list\n        try:\n            self.Prodnames[prodname].append(p)\n        except KeyError:\n            self.Prodnames[prodname] = [p]\n\n    # -----------------------------------------------------------------------------\n    # set_start()\n    #\n    # Sets the starting symbol and creates the augmented grammar.  Production\n    # rule 0 is S' -> start where start is the start symbol.\n    # -----------------------------------------------------------------------------\n\n    def set_start(self, start=None):\n        if not start:\n            start = self.Productions[1].name\n        if start not in self.Nonterminals:\n            raise GrammarError('start symbol %s undefined' % start)\n        self.Productions[0] = Production(0, \"S'\", [start])\n        self.Nonterminals[start].append(0)\n        self.Start = start\n\n    # -----------------------------------------------------------------------------\n    # find_unreachable()\n    #\n    # Find all of the nonterminal symbols that can't be reached from the starting\n    # symbol.  Returns a list of nonterminals that can't be reached.\n    # -----------------------------------------------------------------------------\n\n    def find_unreachable(self):\n\n        # Mark all symbols that are reachable from a symbol s\n        def mark_reachable_from(s):\n            if s in reachable:\n                return\n            reachable.add(s)\n            for p in self.Prodnames.get(s, []):\n                for r in p.prod:\n                    mark_reachable_from(r)\n\n        reachable = set()\n        mark_reachable_from(self.Productions[0].prod[0])\n        return [s for s in self.Nonterminals if s not in reachable]\n\n    # -----------------------------------------------------------------------------\n    # infinite_cycles()\n    #\n    # This function looks at the various parsing rules and tries to detect\n    # infinite recursion cycles (grammar rules where there is no possible way\n    # to derive a string of only terminals).\n    # -----------------------------------------------------------------------------\n\n    def infinite_cycles(self):\n        terminates = {}\n\n        # Terminals:\n        for t in self.Terminals:\n            terminates[t] = True\n\n        terminates['$end'] = True\n\n        # Nonterminals:\n\n        # Initialize to false:\n        for n in self.Nonterminals:\n            terminates[n] = False\n\n        # Then propagate termination until no change:\n        while True:\n            some_change = False\n            for (n, pl) in self.Prodnames.items():\n                # Nonterminal n terminates iff any of its productions terminates.\n                for p in pl:\n                    # Production p terminates iff all of its rhs symbols terminate.\n                    for s in p.prod:\n                        if not terminates[s]:\n                            # The symbol s does not terminate,\n                            # so production p does not terminate.\n                            p_terminates = False\n                            break\n                    else:\n                        # didn't break from the loop,\n                        # so every symbol s terminates\n                        # so production p terminates.\n                        p_terminates = True\n\n                    if p_terminates:\n                        # symbol n terminates!\n                        if not terminates[n]:\n                            terminates[n] = True\n                            some_change = True\n                        # Don't need to consider any more productions for this n.\n                        break\n\n            if not some_change:\n                break\n\n        infinite = []\n        for (s, term) in terminates.items():\n            if not term:\n                if s not in self.Prodnames and s not in self.Terminals and s != 'error':\n                    # s is used-but-not-defined, and we've already warned of that,\n                    # so it would be overkill to say that it's also non-terminating.\n                    pass\n                else:\n                    infinite.append(s)\n\n        return infinite\n\n    # -----------------------------------------------------------------------------\n    # undefined_symbols()\n    #\n    # Find all symbols that were used the grammar, but not defined as tokens or\n    # grammar rules.  Returns a list of tuples (sym, prod) where sym in the symbol\n    # and prod is the production where the symbol was used.\n    # -----------------------------------------------------------------------------\n    def undefined_symbols(self):\n        result = []\n        for p in self.Productions:\n            if not p:\n                continue\n\n            for s in p.prod:\n                if s not in self.Prodnames and s not in self.Terminals and s != 'error':\n                    result.append((s, p))\n        return result\n\n    # -----------------------------------------------------------------------------\n    # unused_terminals()\n    #\n    # Find all terminals that were defined, but not used by the grammar.  Returns\n    # a list of all symbols.\n    # -----------------------------------------------------------------------------\n    def unused_terminals(self):\n        unused_tok = []\n        for s, v in self.Terminals.items():\n            if s != 'error' and not v:\n                unused_tok.append(s)\n\n        return unused_tok\n\n    # ------------------------------------------------------------------------------\n    # unused_rules()\n    #\n    # Find all grammar rules that were defined,  but not used (maybe not reachable)\n    # Returns a list of productions.\n    # ------------------------------------------------------------------------------\n\n    def unused_rules(self):\n        unused_prod = []\n        for s, v in self.Nonterminals.items():\n            if not v:\n                p = self.Prodnames[s][0]\n                unused_prod.append(p)\n        return unused_prod\n\n    # -----------------------------------------------------------------------------\n    # unused_precedence()\n    #\n    # Returns a list of tuples (term,precedence) corresponding to precedence\n    # rules that were never used by the grammar.  term is the name of the terminal\n    # on which precedence was applied and precedence is a string such as 'left' or\n    # 'right' corresponding to the type of precedence.\n    # -----------------------------------------------------------------------------\n\n    def unused_precedence(self):\n        unused = []\n        for termname in self.Precedence:\n            if not (termname in self.Terminals or termname in self.UsedPrecedence):\n                unused.append((termname, self.Precedence[termname][0]))\n\n        return unused\n\n    # -------------------------------------------------------------------------\n    # _first()\n    #\n    # Compute the value of FIRST1(beta) where beta is a tuple of symbols.\n    #\n    # During execution of compute_first1, the result may be incomplete.\n    # Afterward (e.g., when called from compute_follow()), it will be complete.\n    # -------------------------------------------------------------------------\n    def _first(self, beta):\n\n        # We are computing First(x1,x2,x3,...,xn)\n        result = []\n        for x in beta:\n            x_produces_empty = False\n\n            # Add all the non-<empty> symbols of First[x] to the result.\n            for f in self.First[x]:\n                if f == '<empty>':\n                    x_produces_empty = True\n                else:\n                    if f not in result:\n                        result.append(f)\n\n            if x_produces_empty:\n                # We have to consider the next x in beta,\n                # i.e. stay in the loop.\n                pass\n            else:\n                # We don't have to consider any further symbols in beta.\n                break\n        else:\n            # There was no 'break' from the loop,\n            # so x_produces_empty was true for all x in beta,\n            # so beta produces empty as well.\n            result.append('<empty>')\n\n        return result\n\n    # -------------------------------------------------------------------------\n    # compute_first()\n    #\n    # Compute the value of FIRST1(X) for all symbols\n    # -------------------------------------------------------------------------\n    def compute_first(self):\n        if self.First:\n            return self.First\n\n        # Terminals:\n        for t in self.Terminals:\n            self.First[t] = [t]\n\n        self.First['$end'] = ['$end']\n\n        # Nonterminals:\n\n        # Initialize to the empty set:\n        for n in self.Nonterminals:\n            self.First[n] = []\n\n        # Then propagate symbols until no change:\n        while True:\n            some_change = False\n            for n in self.Nonterminals:\n                for p in self.Prodnames[n]:\n                    for f in self._first(p.prod):\n                        if f not in self.First[n]:\n                            self.First[n].append(f)\n                            some_change = True\n            if not some_change:\n                break\n\n        return self.First\n\n    # ---------------------------------------------------------------------\n    # compute_follow()\n    #\n    # Computes all of the follow sets for every non-terminal symbol.  The\n    # follow set is the set of all symbols that might follow a given\n    # non-terminal.  See the Dragon book, 2nd Ed. p. 189.\n    # ---------------------------------------------------------------------\n    def compute_follow(self, start=None):\n        # If already computed, return the result\n        if self.Follow:\n            return self.Follow\n\n        # If first sets not computed yet, do that first.\n        if not self.First:\n            self.compute_first()\n\n        # Add '$end' to the follow list of the start symbol\n        for k in self.Nonterminals:\n            self.Follow[k] = []\n\n        if not start:\n            start = self.Productions[1].name\n\n        self.Follow[start] = ['$end']\n\n        while True:\n            didadd = False\n            for p in self.Productions[1:]:\n                # Here is the production set\n                for i, B in enumerate(p.prod):\n                    if B in self.Nonterminals:\n                        # Okay. We got a non-terminal in a production\n                        fst = self._first(p.prod[i+1:])\n                        hasempty = False\n                        for f in fst:\n                            if f != '<empty>' and f not in self.Follow[B]:\n                                self.Follow[B].append(f)\n                                didadd = True\n                            if f == '<empty>':\n                                hasempty = True\n                        if hasempty or i == (len(p.prod)-1):\n                            # Add elements of follow(a) to follow(b)\n                            for f in self.Follow[p.name]:\n                                if f not in self.Follow[B]:\n                                    self.Follow[B].append(f)\n                                    didadd = True\n            if not didadd:\n                break\n        return self.Follow\n\n\n    # -----------------------------------------------------------------------------\n    # build_lritems()\n    #\n    # This function walks the list of productions and builds a complete set of the\n    # LR items.  The LR items are stored in two ways:  First, they are uniquely\n    # numbered and placed in the list _lritems.  Second, a linked list of LR items\n    # is built for each production.  For example:\n    #\n    #   E -> E PLUS E\n    #\n    # Creates the list\n    #\n    #  [E -> . E PLUS E, E -> E . PLUS E, E -> E PLUS . E, E -> E PLUS E . ]\n    # -----------------------------------------------------------------------------\n\n    def build_lritems(self):\n        for p in self.Productions:\n            lastlri = p\n            i = 0\n            lr_items = []\n            while True:\n                if i > len(p):\n                    lri = None\n                else:\n                    lri = LRItem(p, i)\n                    # Precompute the list of productions immediately following\n                    try:\n                        lri.lr_after = self.Prodnames[lri.prod[i+1]]\n                    except (IndexError, KeyError):\n                        lri.lr_after = []\n                    try:\n                        lri.lr_before = lri.prod[i-1]\n                    except IndexError:\n                        lri.lr_before = None\n\n                lastlri.lr_next = lri\n                if not lri:\n                    break\n                lr_items.append(lri)\n                lastlri = lri\n                i += 1\n            p.lr_items = lr_items\n\n# -----------------------------------------------------------------------------\n#                            == Class LRTable ==\n#\n# This basic class represents a basic table of LR parsing information.\n# Methods for generating the tables are not defined here.  They are defined\n# in the derived class LRGeneratedTable.\n# -----------------------------------------------------------------------------\n\nclass VersionError(YaccError):\n    pass\n\nclass LRTable(object):\n    def __init__(self):\n        self.lr_action = None\n        self.lr_goto = None\n        self.lr_productions = None\n        self.lr_method = None\n\n    def read_table(self, module):\n        if isinstance(module, types.ModuleType):\n            parsetab = module\n        else:\n            exec('import %s' % module)\n            parsetab = sys.modules[module]\n\n        if parsetab._tabversion != __tabversion__:\n            raise VersionError('yacc table file version is out of date')\n\n        self.lr_action = parsetab._lr_action\n        self.lr_goto = parsetab._lr_goto\n\n        self.lr_productions = []\n        for p in parsetab._lr_productions:\n            self.lr_productions.append(MiniProduction(*p))\n\n        self.lr_method = parsetab._lr_method\n        return parsetab._lr_signature\n\n    def read_pickle(self, filename):\n        try:\n            import cPickle as pickle\n        except ImportError:\n            import pickle\n\n        if not os.path.exists(filename):\n          raise ImportError\n\n        in_f = open(filename, 'rb')\n\n        tabversion = pickle.load(in_f)\n        if tabversion != __tabversion__:\n            raise VersionError('yacc table file version is out of date')\n        self.lr_method = pickle.load(in_f)\n        signature      = pickle.load(in_f)\n        self.lr_action = pickle.load(in_f)\n        self.lr_goto   = pickle.load(in_f)\n        productions    = pickle.load(in_f)\n\n        self.lr_productions = []\n        for p in productions:\n            self.lr_productions.append(MiniProduction(*p))\n\n        in_f.close()\n        return signature\n\n    # Bind all production function names to callable objects in pdict\n    def bind_callables(self, pdict):\n        for p in self.lr_productions:\n            p.bind(pdict)\n\n\n# -----------------------------------------------------------------------------\n#                           === LR Generator ===\n#\n# The following classes and functions are used to generate LR parsing tables on\n# a grammar.\n# -----------------------------------------------------------------------------\n\n# -----------------------------------------------------------------------------\n# digraph()\n# traverse()\n#\n# The following two functions are used to compute set valued functions\n# of the form:\n#\n#     F(x) = F'(x) U U{F(y) | x R y}\n#\n# This is used to compute the values of Read() sets as well as FOLLOW sets\n# in LALR(1) generation.\n#\n# Inputs:  X    - An input set\n#          R    - A relation\n#          FP   - Set-valued function\n# ------------------------------------------------------------------------------\n\ndef digraph(X, R, FP):\n    N = {}\n    for x in X:\n        N[x] = 0\n    stack = []\n    F = {}\n    for x in X:\n        if N[x] == 0:\n            traverse(x, N, stack, F, X, R, FP)\n    return F\n\ndef traverse(x, N, stack, F, X, R, FP):\n    stack.append(x)\n    d = len(stack)\n    N[x] = d\n    F[x] = FP(x)             # F(X) <- F'(x)\n\n    rel = R(x)               # Get y's related to x\n    for y in rel:\n        if N[y] == 0:\n            traverse(y, N, stack, F, X, R, FP)\n        N[x] = min(N[x], N[y])\n        for a in F.get(y, []):\n            if a not in F[x]:\n                F[x].append(a)\n    if N[x] == d:\n        N[stack[-1]] = MAXINT\n        F[stack[-1]] = F[x]\n        element = stack.pop()\n        while element != x:\n            N[stack[-1]] = MAXINT\n            F[stack[-1]] = F[x]\n            element = stack.pop()\n\nclass LALRError(YaccError):\n    pass\n\n# -----------------------------------------------------------------------------\n#                             == LRGeneratedTable ==\n#\n# This class implements the LR table generation algorithm.  There are no\n# public methods except for write()\n# -----------------------------------------------------------------------------\n\nclass LRGeneratedTable(LRTable):\n    def __init__(self, grammar, method='LALR', log=None):\n        if method not in ['SLR', 'LALR']:\n            raise LALRError('Unsupported method %s' % method)\n\n        self.grammar = grammar\n        self.lr_method = method\n\n        # Set up the logger\n        if not log:\n            log = NullLogger()\n        self.log = log\n\n        # Internal attributes\n        self.lr_action     = {}        # Action table\n        self.lr_goto       = {}        # Goto table\n        self.lr_productions  = grammar.Productions    # Copy of grammar Production array\n        self.lr_goto_cache = {}        # Cache of computed gotos\n        self.lr0_cidhash   = {}        # Cache of closures\n\n        self._add_count    = 0         # Internal counter used to detect cycles\n\n        # Diagonistic information filled in by the table generator\n        self.sr_conflict   = 0\n        self.rr_conflict   = 0\n        self.conflicts     = []        # List of conflicts\n\n        self.sr_conflicts  = []\n        self.rr_conflicts  = []\n\n        # Build the tables\n        self.grammar.build_lritems()\n        self.grammar.compute_first()\n        self.grammar.compute_follow()\n        self.lr_parse_table()\n\n    # Compute the LR(0) closure operation on I, where I is a set of LR(0) items.\n\n    def lr0_closure(self, I):\n        self._add_count += 1\n\n        # Add everything in I to J\n        J = I[:]\n        didadd = True\n        while didadd:\n            didadd = False\n            for j in J:\n                for x in j.lr_after:\n                    if getattr(x, 'lr0_added', 0) == self._add_count:\n                        continue\n                    # Add B --> .G to J\n                    J.append(x.lr_next)\n                    x.lr0_added = self._add_count\n                    didadd = True\n\n        return J\n\n    # Compute the LR(0) goto function goto(I,X) where I is a set\n    # of LR(0) items and X is a grammar symbol.   This function is written\n    # in a way that guarantees uniqueness of the generated goto sets\n    # (i.e. the same goto set will never be returned as two different Python\n    # objects).  With uniqueness, we can later do fast set comparisons using\n    # id(obj) instead of element-wise comparison.\n\n    def lr0_goto(self, I, x):\n        # First we look for a previously cached entry\n        g = self.lr_goto_cache.get((id(I), x))\n        if g:\n            return g\n\n        # Now we generate the goto set in a way that guarantees uniqueness\n        # of the result\n\n        s = self.lr_goto_cache.get(x)\n        if not s:\n            s = {}\n            self.lr_goto_cache[x] = s\n\n        gs = []\n        for p in I:\n            n = p.lr_next\n            if n and n.lr_before == x:\n                s1 = s.get(id(n))\n                if not s1:\n                    s1 = {}\n                    s[id(n)] = s1\n                gs.append(n)\n                s = s1\n        g = s.get('$end')\n        if not g:\n            if gs:\n                g = self.lr0_closure(gs)\n                s['$end'] = g\n            else:\n                s['$end'] = gs\n        self.lr_goto_cache[(id(I), x)] = g\n        return g\n\n    # Compute the LR(0) sets of item function\n    def lr0_items(self):\n        C = [self.lr0_closure([self.grammar.Productions[0].lr_next])]\n        i = 0\n        for I in C:\n            self.lr0_cidhash[id(I)] = i\n            i += 1\n\n        # Loop over the items in C and each grammar symbols\n        i = 0\n        while i < len(C):\n            I = C[i]\n            i += 1\n\n            # Collect all of the symbols that could possibly be in the goto(I,X) sets\n            asyms = {}\n            for ii in I:\n                for s in ii.usyms:\n                    asyms[s] = None\n\n            for x in asyms:\n                g = self.lr0_goto(I, x)\n                if not g or id(g) in self.lr0_cidhash:\n                    continue\n                self.lr0_cidhash[id(g)] = len(C)\n                C.append(g)\n\n        return C\n\n    # -----------------------------------------------------------------------------\n    #                       ==== LALR(1) Parsing ====\n    #\n    # LALR(1) parsing is almost exactly the same as SLR except that instead of\n    # relying upon Follow() sets when performing reductions, a more selective\n    # lookahead set that incorporates the state of the LR(0) machine is utilized.\n    # Thus, we mainly just have to focus on calculating the lookahead sets.\n    #\n    # The method used here is due to DeRemer and Pennelo (1982).\n    #\n    # DeRemer, F. L., and T. J. Pennelo: \"Efficient Computation of LALR(1)\n    #     Lookahead Sets\", ACM Transactions on Programming Languages and Systems,\n    #     Vol. 4, No. 4, Oct. 1982, pp. 615-649\n    #\n    # Further details can also be found in:\n    #\n    #  J. Tremblay and P. Sorenson, \"The Theory and Practice of Compiler Writing\",\n    #      McGraw-Hill Book Company, (1985).\n    #\n    # -----------------------------------------------------------------------------\n\n    # -----------------------------------------------------------------------------\n    # compute_nullable_nonterminals()\n    #\n    # Creates a dictionary containing all of the non-terminals that might produce\n    # an empty production.\n    # -----------------------------------------------------------------------------\n\n    def compute_nullable_nonterminals(self):\n        nullable = set()\n        num_nullable = 0\n        while True:\n            for p in self.grammar.Productions[1:]:\n                if p.len == 0:\n                    nullable.add(p.name)\n                    continue\n                for t in p.prod:\n                    if t not in nullable:\n                        break\n                else:\n                    nullable.add(p.name)\n            if len(nullable) == num_nullable:\n                break\n            num_nullable = len(nullable)\n        return nullable\n\n    # -----------------------------------------------------------------------------\n    # find_nonterminal_trans(C)\n    #\n    # Given a set of LR(0) items, this functions finds all of the non-terminal\n    # transitions.    These are transitions in which a dot appears immediately before\n    # a non-terminal.   Returns a list of tuples of the form (state,N) where state\n    # is the state number and N is the nonterminal symbol.\n    #\n    # The input C is the set of LR(0) items.\n    # -----------------------------------------------------------------------------\n\n    def find_nonterminal_transitions(self, C):\n        trans = []\n        for stateno, state in enumerate(C):\n            for p in state:\n                if p.lr_index < p.len - 1:\n                    t = (stateno, p.prod[p.lr_index+1])\n                    if t[1] in self.grammar.Nonterminals:\n                        if t not in trans:\n                            trans.append(t)\n        return trans\n\n    # -----------------------------------------------------------------------------\n    # dr_relation()\n    #\n    # Computes the DR(p,A) relationships for non-terminal transitions.  The input\n    # is a tuple (state,N) where state is a number and N is a nonterminal symbol.\n    #\n    # Returns a list of terminals.\n    # -----------------------------------------------------------------------------\n\n    def dr_relation(self, C, trans, nullable):\n        dr_set = {}\n        state, N = trans\n        terms = []\n\n        g = self.lr0_goto(C[state], N)\n        for p in g:\n            if p.lr_index < p.len - 1:\n                a = p.prod[p.lr_index+1]\n                if a in self.grammar.Terminals:\n                    if a not in terms:\n                        terms.append(a)\n\n        # This extra bit is to handle the start state\n        if state == 0 and N == self.grammar.Productions[0].prod[0]:\n            terms.append('$end')\n\n        return terms\n\n    # -----------------------------------------------------------------------------\n    # reads_relation()\n    #\n    # Computes the READS() relation (p,A) READS (t,C).\n    # -----------------------------------------------------------------------------\n\n    def reads_relation(self, C, trans, empty):\n        # Look for empty transitions\n        rel = []\n        state, N = trans\n\n        g = self.lr0_goto(C[state], N)\n        j = self.lr0_cidhash.get(id(g), -1)\n        for p in g:\n            if p.lr_index < p.len - 1:\n                a = p.prod[p.lr_index + 1]\n                if a in empty:\n                    rel.append((j, a))\n\n        return rel\n\n    # -----------------------------------------------------------------------------\n    # compute_lookback_includes()\n    #\n    # Determines the lookback and includes relations\n    #\n    # LOOKBACK:\n    #\n    # This relation is determined by running the LR(0) state machine forward.\n    # For example, starting with a production \"N : . A B C\", we run it forward\n    # to obtain \"N : A B C .\"   We then build a relationship between this final\n    # state and the starting state.   These relationships are stored in a dictionary\n    # lookdict.\n    #\n    # INCLUDES:\n    #\n    # Computes the INCLUDE() relation (p,A) INCLUDES (p',B).\n    #\n    # This relation is used to determine non-terminal transitions that occur\n    # inside of other non-terminal transition states.   (p,A) INCLUDES (p', B)\n    # if the following holds:\n    #\n    #       B -> LAT, where T -> epsilon and p' -L-> p\n    #\n    # L is essentially a prefix (which may be empty), T is a suffix that must be\n    # able to derive an empty string.  State p' must lead to state p with the string L.\n    #\n    # -----------------------------------------------------------------------------\n\n    def compute_lookback_includes(self, C, trans, nullable):\n        lookdict = {}          # Dictionary of lookback relations\n        includedict = {}       # Dictionary of include relations\n\n        # Make a dictionary of non-terminal transitions\n        dtrans = {}\n        for t in trans:\n            dtrans[t] = 1\n\n        # Loop over all transitions and compute lookbacks and includes\n        for state, N in trans:\n            lookb = []\n            includes = []\n            for p in C[state]:\n                if p.name != N:\n                    continue\n\n                # Okay, we have a name match.  We now follow the production all the way\n                # through the state machine until we get the . on the right hand side\n\n                lr_index = p.lr_index\n                j = state\n                while lr_index < p.len - 1:\n                    lr_index = lr_index + 1\n                    t = p.prod[lr_index]\n\n                    # Check to see if this symbol and state are a non-terminal transition\n                    if (j, t) in dtrans:\n                        # Yes.  Okay, there is some chance that this is an includes relation\n                        # the only way to know for certain is whether the rest of the\n                        # production derives empty\n\n                        li = lr_index + 1\n                        while li < p.len:\n                            if p.prod[li] in self.grammar.Terminals:\n                                break      # No forget it\n                            if p.prod[li] not in nullable:\n                                break\n                            li = li + 1\n                        else:\n                            # Appears to be a relation between (j,t) and (state,N)\n                            includes.append((j, t))\n\n                    g = self.lr0_goto(C[j], t)               # Go to next set\n                    j = self.lr0_cidhash.get(id(g), -1)      # Go to next state\n\n                # When we get here, j is the final state, now we have to locate the production\n                for r in C[j]:\n                    if r.name != p.name:\n                        continue\n                    if r.len != p.len:\n                        continue\n                    i = 0\n                    # This look is comparing a production \". A B C\" with \"A B C .\"\n                    while i < r.lr_index:\n                        if r.prod[i] != p.prod[i+1]:\n                            break\n                        i = i + 1\n                    else:\n                        lookb.append((j, r))\n            for i in includes:\n                if i not in includedict:\n                    includedict[i] = []\n                includedict[i].append((state, N))\n            lookdict[(state, N)] = lookb\n\n        return lookdict, includedict\n\n    # -----------------------------------------------------------------------------\n    # compute_read_sets()\n    #\n    # Given a set of LR(0) items, this function computes the read sets.\n    #\n    # Inputs:  C        =  Set of LR(0) items\n    #          ntrans   = Set of nonterminal transitions\n    #          nullable = Set of empty transitions\n    #\n    # Returns a set containing the read sets\n    # -----------------------------------------------------------------------------\n\n    def compute_read_sets(self, C, ntrans, nullable):\n        FP = lambda x: self.dr_relation(C, x, nullable)\n        R =  lambda x: self.reads_relation(C, x, nullable)\n        F = digraph(ntrans, R, FP)\n        return F\n\n    # -----------------------------------------------------------------------------\n    # compute_follow_sets()\n    #\n    # Given a set of LR(0) items, a set of non-terminal transitions, a readset,\n    # and an include set, this function computes the follow sets\n    #\n    # Follow(p,A) = Read(p,A) U U {Follow(p',B) | (p,A) INCLUDES (p',B)}\n    #\n    # Inputs:\n    #            ntrans     = Set of nonterminal transitions\n    #            readsets   = Readset (previously computed)\n    #            inclsets   = Include sets (previously computed)\n    #\n    # Returns a set containing the follow sets\n    # -----------------------------------------------------------------------------\n\n    def compute_follow_sets(self, ntrans, readsets, inclsets):\n        FP = lambda x: readsets[x]\n        R  = lambda x: inclsets.get(x, [])\n        F = digraph(ntrans, R, FP)\n        return F\n\n    # -----------------------------------------------------------------------------\n    # add_lookaheads()\n    #\n    # Attaches the lookahead symbols to grammar rules.\n    #\n    # Inputs:    lookbacks         -  Set of lookback relations\n    #            followset         -  Computed follow set\n    #\n    # This function directly attaches the lookaheads to productions contained\n    # in the lookbacks set\n    # -----------------------------------------------------------------------------\n\n    def add_lookaheads(self, lookbacks, followset):\n        for trans, lb in lookbacks.items():\n            # Loop over productions in lookback\n            for state, p in lb:\n                if state not in p.lookaheads:\n                    p.lookaheads[state] = []\n                f = followset.get(trans, [])\n                for a in f:\n                    if a not in p.lookaheads[state]:\n                        p.lookaheads[state].append(a)\n\n    # -----------------------------------------------------------------------------\n    # add_lalr_lookaheads()\n    #\n    # This function does all of the work of adding lookahead information for use\n    # with LALR parsing\n    # -----------------------------------------------------------------------------\n\n    def add_lalr_lookaheads(self, C):\n        # Determine all of the nullable nonterminals\n        nullable = self.compute_nullable_nonterminals()\n\n        # Find all non-terminal transitions\n        trans = self.find_nonterminal_transitions(C)\n\n        # Compute read sets\n        readsets = self.compute_read_sets(C, trans, nullable)\n\n        # Compute lookback/includes relations\n        lookd, included = self.compute_lookback_includes(C, trans, nullable)\n\n        # Compute LALR FOLLOW sets\n        followsets = self.compute_follow_sets(trans, readsets, included)\n\n        # Add all of the lookaheads\n        self.add_lookaheads(lookd, followsets)\n\n    # -----------------------------------------------------------------------------\n    # lr_parse_table()\n    #\n    # This function constructs the parse tables for SLR or LALR\n    # -----------------------------------------------------------------------------\n    def lr_parse_table(self):\n        Productions = self.grammar.Productions\n        Precedence  = self.grammar.Precedence\n        goto   = self.lr_goto         # Goto array\n        action = self.lr_action       # Action array\n        log    = self.log             # Logger for output\n\n        actionp = {}                  # Action production array (temporary)\n\n        log.info('Parsing method: %s', self.lr_method)\n\n        # Step 1: Construct C = { I0, I1, ... IN}, collection of LR(0) items\n        # This determines the number of states\n\n        C = self.lr0_items()\n\n        if self.lr_method == 'LALR':\n            self.add_lalr_lookaheads(C)\n\n        # Build the parser table, state by state\n        st = 0\n        for I in C:\n            # Loop over each production in I\n            actlist = []              # List of actions\n            st_action  = {}\n            st_actionp = {}\n            st_goto    = {}\n            log.info('')\n            log.info('state %d', st)\n            log.info('')\n            for p in I:\n                log.info('    (%d) %s', p.number, p)\n            log.info('')\n\n            for p in I:\n                    if p.len == p.lr_index + 1:\n                        if p.name == \"S'\":\n                            # Start symbol. Accept!\n                            st_action['$end'] = 0\n                            st_actionp['$end'] = p\n                        else:\n                            # We are at the end of a production.  Reduce!\n                            if self.lr_method == 'LALR':\n                                laheads = p.lookaheads[st]\n                            else:\n                                laheads = self.grammar.Follow[p.name]\n                            for a in laheads:\n                                actlist.append((a, p, 'reduce using rule %d (%s)' % (p.number, p)))\n                                r = st_action.get(a)\n                                if r is not None:\n                                    # Whoa. Have a shift/reduce or reduce/reduce conflict\n                                    if r > 0:\n                                        # Need to decide on shift or reduce here\n                                        # By default we favor shifting. Need to add\n                                        # some precedence rules here.\n\n                                        # Shift precedence comes from the token\n                                        sprec, slevel = Precedence.get(a, ('right', 0))\n\n                                        # Reduce precedence comes from rule being reduced (p)\n                                        rprec, rlevel = Productions[p.number].prec\n\n                                        if (slevel < rlevel) or ((slevel == rlevel) and (rprec == 'left')):\n                                            # We really need to reduce here.\n                                            st_action[a] = -p.number\n                                            st_actionp[a] = p\n                                            if not slevel and not rlevel:\n                                                log.info('  ! shift/reduce conflict for %s resolved as reduce', a)\n                                                self.sr_conflicts.append((st, a, 'reduce'))\n                                            Productions[p.number].reduced += 1\n                                        elif (slevel == rlevel) and (rprec == 'nonassoc'):\n                                            st_action[a] = None\n                                        else:\n                                            # Hmmm. Guess we'll keep the shift\n                                            if not rlevel:\n                                                log.info('  ! shift/reduce conflict for %s resolved as shift', a)\n                                                self.sr_conflicts.append((st, a, 'shift'))\n                                    elif r < 0:\n                                        # Reduce/reduce conflict.   In this case, we favor the rule\n                                        # that was defined first in the grammar file\n                                        oldp = Productions[-r]\n                                        pp = Productions[p.number]\n                                        if oldp.line > pp.line:\n                                            st_action[a] = -p.number\n                                            st_actionp[a] = p\n                                            chosenp, rejectp = pp, oldp\n                                            Productions[p.number].reduced += 1\n                                            Productions[oldp.number].reduced -= 1\n                                        else:\n                                            chosenp, rejectp = oldp, pp\n                                        self.rr_conflicts.append((st, chosenp, rejectp))\n                                        log.info('  ! reduce/reduce conflict for %s resolved using rule %d (%s)',\n                                                 a, st_actionp[a].number, st_actionp[a])\n                                    else:\n                                        raise LALRError('Unknown conflict in state %d' % st)\n                                else:\n                                    st_action[a] = -p.number\n                                    st_actionp[a] = p\n                                    Productions[p.number].reduced += 1\n                    else:\n                        i = p.lr_index\n                        a = p.prod[i+1]       # Get symbol right after the \".\"\n                        if a in self.grammar.Terminals:\n                            g = self.lr0_goto(I, a)\n                            j = self.lr0_cidhash.get(id(g), -1)\n                            if j >= 0:\n                                # We are in a shift state\n                                actlist.append((a, p, 'shift and go to state %d' % j))\n                                r = st_action.get(a)\n                                if r is not None:\n                                    # Whoa have a shift/reduce or shift/shift conflict\n                                    if r > 0:\n                                        if r != j:\n                                            raise LALRError('Shift/shift conflict in state %d' % st)\n                                    elif r < 0:\n                                        # Do a precedence check.\n                                        #   -  if precedence of reduce rule is higher, we reduce.\n                                        #   -  if precedence of reduce is same and left assoc, we reduce.\n                                        #   -  otherwise we shift\n\n                                        # Shift precedence comes from the token\n                                        sprec, slevel = Precedence.get(a, ('right', 0))\n\n                                        # Reduce precedence comes from the rule that could have been reduced\n                                        rprec, rlevel = Productions[st_actionp[a].number].prec\n\n                                        if (slevel > rlevel) or ((slevel == rlevel) and (rprec == 'right')):\n                                            # We decide to shift here... highest precedence to shift\n                                            Productions[st_actionp[a].number].reduced -= 1\n                                            st_action[a] = j\n                                            st_actionp[a] = p\n                                            if not rlevel:\n                                                log.info('  ! shift/reduce conflict for %s resolved as shift', a)\n                                                self.sr_conflicts.append((st, a, 'shift'))\n                                        elif (slevel == rlevel) and (rprec == 'nonassoc'):\n                                            st_action[a] = None\n                                        else:\n                                            # Hmmm. Guess we'll keep the reduce\n                                            if not slevel and not rlevel:\n                                                log.info('  ! shift/reduce conflict for %s resolved as reduce', a)\n                                                self.sr_conflicts.append((st, a, 'reduce'))\n\n                                    else:\n                                        raise LALRError('Unknown conflict in state %d' % st)\n                                else:\n                                    st_action[a] = j\n                                    st_actionp[a] = p\n\n            # Print the actions associated with each terminal\n            _actprint = {}\n            for a, p, m in actlist:\n                if a in st_action:\n                    if p is st_actionp[a]:\n                        log.info('    %-15s %s', a, m)\n                        _actprint[(a, m)] = 1\n            log.info('')\n            # Print the actions that were not used. (debugging)\n            not_used = 0\n            for a, p, m in actlist:\n                if a in st_action:\n                    if p is not st_actionp[a]:\n                        if not (a, m) in _actprint:\n                            log.debug('  ! %-15s [ %s ]', a, m)\n                            not_used = 1\n                            _actprint[(a, m)] = 1\n            if not_used:\n                log.debug('')\n\n            # Construct the goto table for this state\n\n            nkeys = {}\n            for ii in I:\n                for s in ii.usyms:\n                    if s in self.grammar.Nonterminals:\n                        nkeys[s] = None\n            for n in nkeys:\n                g = self.lr0_goto(I, n)\n                j = self.lr0_cidhash.get(id(g), -1)\n                if j >= 0:\n                    st_goto[n] = j\n                    log.info('    %-30s shift and go to state %d', n, j)\n\n            action[st] = st_action\n            actionp[st] = st_actionp\n            goto[st] = st_goto\n            st += 1\n\n    # -----------------------------------------------------------------------------\n    # write()\n    #\n    # This function writes the LR parsing tables to a file\n    # -----------------------------------------------------------------------------\n\n    def write_table(self, tabmodule, outputdir='', signature=''):\n        if isinstance(tabmodule, types.ModuleType):\n            raise IOError(\"Won't overwrite existing tabmodule\")\n\n        basemodulename = tabmodule.split('.')[-1]\n        filename = os.path.join(outputdir, basemodulename) + '.py'\n        try:\n            f = open(filename, 'w')\n\n            f.write('''\n# %s\n# This file is automatically generated. Do not edit.\n_tabversion = %r\n\n_lr_method = %r\n\n_lr_signature = %r\n    ''' % (os.path.basename(filename), __tabversion__, self.lr_method, signature))\n\n            # Change smaller to 0 to go back to original tables\n            smaller = 1\n\n            # Factor out names to try and make smaller\n            if smaller:\n                items = {}\n\n                for s, nd in self.lr_action.items():\n                    for name, v in nd.items():\n                        i = items.get(name)\n                        if not i:\n                            i = ([], [])\n                            items[name] = i\n                        i[0].append(s)\n                        i[1].append(v)\n\n                f.write('\\n_lr_action_items = {')\n                for k, v in items.items():\n                    f.write('%r:([' % k)\n                    for i in v[0]:\n                        f.write('%r,' % i)\n                    f.write('],[')\n                    for i in v[1]:\n                        f.write('%r,' % i)\n\n                    f.write(']),')\n                f.write('}\\n')\n\n                f.write('''\n_lr_action = {}\nfor _k, _v in _lr_action_items.items():\n   for _x,_y in zip(_v[0],_v[1]):\n      if not _x in _lr_action:  _lr_action[_x] = {}\n      _lr_action[_x][_k] = _y\ndel _lr_action_items\n''')\n\n            else:\n                f.write('\\n_lr_action = { ')\n                for k, v in self.lr_action.items():\n                    f.write('(%r,%r):%r,' % (k[0], k[1], v))\n                f.write('}\\n')\n\n            if smaller:\n                # Factor out names to try and make smaller\n                items = {}\n\n                for s, nd in self.lr_goto.items():\n                    for name, v in nd.items():\n                        i = items.get(name)\n                        if not i:\n                            i = ([], [])\n                            items[name] = i\n                        i[0].append(s)\n                        i[1].append(v)\n\n                f.write('\\n_lr_goto_items = {')\n                for k, v in items.items():\n                    f.write('%r:([' % k)\n                    for i in v[0]:\n                        f.write('%r,' % i)\n                    f.write('],[')\n                    for i in v[1]:\n                        f.write('%r,' % i)\n\n                    f.write(']),')\n                f.write('}\\n')\n\n                f.write('''\n_lr_goto = {}\nfor _k, _v in _lr_goto_items.items():\n   for _x, _y in zip(_v[0], _v[1]):\n       if not _x in _lr_goto: _lr_goto[_x] = {}\n       _lr_goto[_x][_k] = _y\ndel _lr_goto_items\n''')\n            else:\n                f.write('\\n_lr_goto = { ')\n                for k, v in self.lr_goto.items():\n                    f.write('(%r,%r):%r,' % (k[0], k[1], v))\n                f.write('}\\n')\n\n            # Write production table\n            f.write('_lr_productions = [\\n')\n            for p in self.lr_productions:\n                if p.func:\n                    f.write('  (%r,%r,%d,%r,%r,%d),\\n' % (p.str, p.name, p.len,\n                                                          p.func, os.path.basename(p.file), p.line))\n                else:\n                    f.write('  (%r,%r,%d,None,None,None),\\n' % (str(p), p.name, p.len))\n            f.write(']\\n')\n            f.close()\n\n        except IOError as e:\n            raise\n\n\n    # -----------------------------------------------------------------------------\n    # pickle_table()\n    #\n    # This function pickles the LR parsing tables to a supplied file object\n    # -----------------------------------------------------------------------------\n\n    def pickle_table(self, filename, signature=''):\n        try:\n            import cPickle as pickle\n        except ImportError:\n            import pickle\n        with open(filename, 'wb') as outf:\n            pickle.dump(__tabversion__, outf, pickle_protocol)\n            pickle.dump(self.lr_method, outf, pickle_protocol)\n            pickle.dump(signature, outf, pickle_protocol)\n            pickle.dump(self.lr_action, outf, pickle_protocol)\n            pickle.dump(self.lr_goto, outf, pickle_protocol)\n\n            outp = []\n            for p in self.lr_productions:\n                if p.func:\n                    outp.append((p.str, p.name, p.len, p.func, os.path.basename(p.file), p.line))\n                else:\n                    outp.append((str(p), p.name, p.len, None, None, None))\n            pickle.dump(outp, outf, pickle_protocol)\n\n# -----------------------------------------------------------------------------\n#                            === INTROSPECTION ===\n#\n# The following functions and classes are used to implement the PLY\n# introspection features followed by the yacc() function itself.\n# -----------------------------------------------------------------------------\n\n# -----------------------------------------------------------------------------\n# get_caller_module_dict()\n#\n# This function returns a dictionary containing all of the symbols defined within\n# a caller further down the call stack.  This is used to get the environment\n# associated with the yacc() call if none was provided.\n# -----------------------------------------------------------------------------\n\ndef get_caller_module_dict(levels):\n    f = sys._getframe(levels)\n    ldict = f.f_globals.copy()\n    if f.f_globals != f.f_locals:\n        ldict.update(f.f_locals)\n    return ldict\n\n# -----------------------------------------------------------------------------\n# parse_grammar()\n#\n# This takes a raw grammar rule string and parses it into production data\n# -----------------------------------------------------------------------------\ndef parse_grammar(doc, file, line):\n    grammar = []\n    # Split the doc string into lines\n    pstrings = doc.splitlines()\n    lastp = None\n    dline = line\n    for ps in pstrings:\n        dline += 1\n        p = ps.split()\n        if not p:\n            continue\n        try:\n            if p[0] == '|':\n                # This is a continuation of a previous rule\n                if not lastp:\n                    raise SyntaxError(\"%s:%d: Misplaced '|'\" % (file, dline))\n                prodname = lastp\n                syms = p[1:]\n            else:\n                prodname = p[0]\n                lastp = prodname\n                syms   = p[2:]\n                assign = p[1]\n                if assign != ':' and assign != '::=':\n                    raise SyntaxError(\"%s:%d: Syntax error. Expected ':'\" % (file, dline))\n\n            grammar.append((file, dline, prodname, syms))\n        except SyntaxError:\n            raise\n        except Exception:\n            raise SyntaxError('%s:%d: Syntax error in rule %r' % (file, dline, ps.strip()))\n\n    return grammar\n\n# -----------------------------------------------------------------------------\n# ParserReflect()\n#\n# This class represents information extracted for building a parser including\n# start symbol, error function, tokens, precedence list, action functions,\n# etc.\n# -----------------------------------------------------------------------------\nclass ParserReflect(object):\n    def __init__(self, pdict, log=None):\n        self.pdict      = pdict\n        self.start      = None\n        self.error_func = None\n        self.tokens     = None\n        self.modules    = set()\n        self.grammar    = []\n        self.error      = False\n\n        if log is None:\n            self.log = PlyLogger(sys.stderr)\n        else:\n            self.log = log\n\n    # Get all of the basic information\n    def get_all(self):\n        self.get_start()\n        self.get_error_func()\n        self.get_tokens()\n        self.get_precedence()\n        self.get_pfunctions()\n\n    # Validate all of the information\n    def validate_all(self):\n        self.validate_start()\n        self.validate_error_func()\n        self.validate_tokens()\n        self.validate_precedence()\n        self.validate_pfunctions()\n        self.validate_modules()\n        return self.error\n\n    # Compute a signature over the grammar\n    def signature(self):\n        parts = []\n        try:\n            if self.start:\n                parts.append(self.start)\n            if self.prec:\n                parts.append(''.join([''.join(p) for p in self.prec]))\n            if self.tokens:\n                parts.append(' '.join(self.tokens))\n            for f in self.pfuncs:\n                if f[3]:\n                    parts.append(f[3])\n        except (TypeError, ValueError):\n            pass\n        return ''.join(parts)\n\n    # -----------------------------------------------------------------------------\n    # validate_modules()\n    #\n    # This method checks to see if there are duplicated p_rulename() functions\n    # in the parser module file.  Without this function, it is really easy for\n    # users to make mistakes by cutting and pasting code fragments (and it's a real\n    # bugger to try and figure out why the resulting parser doesn't work).  Therefore,\n    # we just do a little regular expression pattern matching of def statements\n    # to try and detect duplicates.\n    # -----------------------------------------------------------------------------\n\n    def validate_modules(self):\n        # Match def p_funcname(\n        fre = re.compile(r'\\s*def\\s+(p_[a-zA-Z_0-9]*)\\(')\n\n        for module in self.modules:\n            try:\n                lines, linen = inspect.getsourcelines(module)\n            except IOError:\n                continue\n\n            counthash = {}\n            for linen, line in enumerate(lines):\n                linen += 1\n                m = fre.match(line)\n                if m:\n                    name = m.group(1)\n                    prev = counthash.get(name)\n                    if not prev:\n                        counthash[name] = linen\n                    else:\n                        filename = inspect.getsourcefile(module)\n                        self.log.warning('%s:%d: Function %s redefined. Previously defined on line %d',\n                                         filename, linen, name, prev)\n\n    # Get the start symbol\n    def get_start(self):\n        self.start = self.pdict.get('start')\n\n    # Validate the start symbol\n    def validate_start(self):\n        if self.start is not None:\n            if not isinstance(self.start, string_types):\n                self.log.error(\"'start' must be a string\")\n\n    # Look for error handler\n    def get_error_func(self):\n        self.error_func = self.pdict.get('p_error')\n\n    # Validate the error function\n    def validate_error_func(self):\n        if self.error_func:\n            if isinstance(self.error_func, types.FunctionType):\n                ismethod = 0\n            elif isinstance(self.error_func, types.MethodType):\n                ismethod = 1\n            else:\n                self.log.error(\"'p_error' defined, but is not a function or method\")\n                self.error = True\n                return\n\n            eline = self.error_func.__code__.co_firstlineno\n            efile = self.error_func.__code__.co_filename\n            module = inspect.getmodule(self.error_func)\n            self.modules.add(module)\n\n            argcount = self.error_func.__code__.co_argcount - ismethod\n            if argcount != 1:\n                self.log.error('%s:%d: p_error() requires 1 argument', efile, eline)\n                self.error = True\n\n    # Get the tokens map\n    def get_tokens(self):\n        tokens = self.pdict.get('tokens')\n        if not tokens:\n            self.log.error('No token list is defined')\n            self.error = True\n            return\n\n        if not isinstance(tokens, (list, tuple)):\n            self.log.error('tokens must be a list or tuple')\n            self.error = True\n            return\n\n        if not tokens:\n            self.log.error('tokens is empty')\n            self.error = True\n            return\n\n        self.tokens = tokens\n\n    # Validate the tokens\n    def validate_tokens(self):\n        # Validate the tokens.\n        if 'error' in self.tokens:\n            self.log.error(\"Illegal token name 'error'. Is a reserved word\")\n            self.error = True\n            return\n\n        terminals = set()\n        for n in self.tokens:\n            if n in terminals:\n                self.log.warning('Token %r multiply defined', n)\n            terminals.add(n)\n\n    # Get the precedence map (if any)\n    def get_precedence(self):\n        self.prec = self.pdict.get('precedence')\n\n    # Validate and parse the precedence map\n    def validate_precedence(self):\n        preclist = []\n        if self.prec:\n            if not isinstance(self.prec, (list, tuple)):\n                self.log.error('precedence must be a list or tuple')\n                self.error = True\n                return\n            for level, p in enumerate(self.prec):\n                if not isinstance(p, (list, tuple)):\n                    self.log.error('Bad precedence table')\n                    self.error = True\n                    return\n\n                if len(p) < 2:\n                    self.log.error('Malformed precedence entry %s. Must be (assoc, term, ..., term)', p)\n                    self.error = True\n                    return\n                assoc = p[0]\n                if not isinstance(assoc, string_types):\n                    self.log.error('precedence associativity must be a string')\n                    self.error = True\n                    return\n                for term in p[1:]:\n                    if not isinstance(term, string_types):\n                        self.log.error('precedence items must be strings')\n                        self.error = True\n                        return\n                    preclist.append((term, assoc, level+1))\n        self.preclist = preclist\n\n    # Get all p_functions from the grammar\n    def get_pfunctions(self):\n        p_functions = []\n        for name, item in self.pdict.items():\n            if not name.startswith('p_') or name == 'p_error':\n                continue\n            if isinstance(item, (types.FunctionType, types.MethodType)):\n                line = getattr(item, 'co_firstlineno', item.__code__.co_firstlineno)\n                module = inspect.getmodule(item)\n                p_functions.append((line, module, name, item.__doc__))\n\n        # Sort all of the actions by line number; make sure to stringify\n        # modules to make them sortable, since `line` may not uniquely sort all\n        # p functions\n        p_functions.sort(key=lambda p_function: (\n            p_function[0],\n            str(p_function[1]),\n            p_function[2],\n            p_function[3]))\n        self.pfuncs = p_functions\n\n    # Validate all of the p_functions\n    def validate_pfunctions(self):\n        grammar = []\n        # Check for non-empty symbols\n        if len(self.pfuncs) == 0:\n            self.log.error('no rules of the form p_rulename are defined')\n            self.error = True\n            return\n\n        for line, module, name, doc in self.pfuncs:\n            file = inspect.getsourcefile(module)\n            func = self.pdict[name]\n            if isinstance(func, types.MethodType):\n                reqargs = 2\n            else:\n                reqargs = 1\n            if func.__code__.co_argcount > reqargs:\n                self.log.error('%s:%d: Rule %r has too many arguments', file, line, func.__name__)\n                self.error = True\n            elif func.__code__.co_argcount < reqargs:\n                self.log.error('%s:%d: Rule %r requires an argument', file, line, func.__name__)\n                self.error = True\n            elif not func.__doc__:\n                self.log.warning('%s:%d: No documentation string specified in function %r (ignored)',\n                                 file, line, func.__name__)\n            else:\n                try:\n                    parsed_g = parse_grammar(doc, file, line)\n                    for g in parsed_g:\n                        grammar.append((name, g))\n                except SyntaxError as e:\n                    self.log.error(str(e))\n                    self.error = True\n\n                # Looks like a valid grammar rule\n                # Mark the file in which defined.\n                self.modules.add(module)\n\n        # Secondary validation step that looks for p_ definitions that are not functions\n        # or functions that look like they might be grammar rules.\n\n        for n, v in self.pdict.items():\n            if n.startswith('p_') and isinstance(v, (types.FunctionType, types.MethodType)):\n                continue\n            if n.startswith('t_'):\n                continue\n            if n.startswith('p_') and n != 'p_error':\n                self.log.warning('%r not defined as a function', n)\n            if ((isinstance(v, types.FunctionType) and v.__code__.co_argcount == 1) or\n                   (isinstance(v, types.MethodType) and v.__func__.__code__.co_argcount == 2)):\n                if v.__doc__:\n                    try:\n                        doc = v.__doc__.split(' ')\n                        if doc[1] == ':':\n                            self.log.warning('%s:%d: Possible grammar rule %r defined without p_ prefix',\n                                             v.__code__.co_filename, v.__code__.co_firstlineno, n)\n                    except IndexError:\n                        pass\n\n        self.grammar = grammar\n\n# -----------------------------------------------------------------------------\n# yacc(module)\n#\n# Build a parser\n# -----------------------------------------------------------------------------\n\ndef yacc(method='LALR', debug=yaccdebug, module=None, tabmodule=tab_module, start=None,\n         check_recursion=True, optimize=False, write_tables=True, debugfile=debug_file,\n         outputdir=None, debuglog=None, errorlog=None, picklefile=None):\n\n    if tabmodule is None:\n        tabmodule = tab_module\n\n    # Reference to the parsing method of the last built parser\n    global parse\n\n    # If pickling is enabled, table files are not created\n    if picklefile:\n        write_tables = 0\n\n    if errorlog is None:\n        errorlog = PlyLogger(sys.stderr)\n\n    # Get the module dictionary used for the parser\n    if module:\n        _items = [(k, getattr(module, k)) for k in dir(module)]\n        pdict = dict(_items)\n        # If no __file__ attribute is available, try to obtain it from the __module__ instead\n        if '__file__' not in pdict:\n            pdict['__file__'] = sys.modules[pdict['__module__']].__file__\n    else:\n        pdict = get_caller_module_dict(2)\n\n    if outputdir is None:\n        # If no output directory is set, the location of the output files\n        # is determined according to the following rules:\n        #     - If tabmodule specifies a package, files go into that package directory\n        #     - Otherwise, files go in the same directory as the specifying module\n        if isinstance(tabmodule, types.ModuleType):\n            srcfile = tabmodule.__file__\n        else:\n            if '.' not in tabmodule:\n                srcfile = pdict['__file__']\n            else:\n                parts = tabmodule.split('.')\n                pkgname = '.'.join(parts[:-1])\n                exec('import %s' % pkgname)\n                srcfile = getattr(sys.modules[pkgname], '__file__', '')\n        outputdir = os.path.dirname(srcfile)\n\n    # Determine if the module is package of a package or not.\n    # If so, fix the tabmodule setting so that tables load correctly\n    pkg = pdict.get('__package__')\n    if pkg and isinstance(tabmodule, str):\n        if '.' not in tabmodule:\n            tabmodule = pkg + '.' + tabmodule\n\n\n\n    # Set start symbol if it's specified directly using an argument\n    if start is not None:\n        pdict['start'] = start\n\n    # Collect parser information from the dictionary\n    pinfo = ParserReflect(pdict, log=errorlog)\n    pinfo.get_all()\n\n    if pinfo.error:\n        raise YaccError('Unable to build parser')\n\n    # Check signature against table files (if any)\n    signature = pinfo.signature()\n\n    # Read the tables\n    try:\n        lr = LRTable()\n        if picklefile:\n            read_signature = lr.read_pickle(picklefile)\n        else:\n            read_signature = lr.read_table(tabmodule)\n        if optimize or (read_signature == signature):\n            try:\n                lr.bind_callables(pinfo.pdict)\n                parser = LRParser(lr, pinfo.error_func)\n                parse = parser.parse\n                return parser\n            except Exception as e:\n                errorlog.warning('There was a problem loading the table file: %r', e)\n    except VersionError as e:\n        errorlog.warning(str(e))\n    except ImportError:\n        pass\n\n    if debuglog is None:\n        if debug:\n            try:\n                debuglog = PlyLogger(open(os.path.join(outputdir, debugfile), 'w'))\n            except IOError as e:\n                errorlog.warning(\"Couldn't open %r. %s\" % (debugfile, e))\n                debuglog = NullLogger()\n        else:\n            debuglog = NullLogger()\n\n    debuglog.info('Created by PLY version %s (http://www.dabeaz.com/ply)', __version__)\n\n    errors = False\n\n    # Validate the parser information\n    if pinfo.validate_all():\n        raise YaccError('Unable to build parser')\n\n    if not pinfo.error_func:\n        errorlog.warning('no p_error() function is defined')\n\n    # Create a grammar object\n    grammar = Grammar(pinfo.tokens)\n\n    # Set precedence level for terminals\n    for term, assoc, level in pinfo.preclist:\n        try:\n            grammar.set_precedence(term, assoc, level)\n        except GrammarError as e:\n            errorlog.warning('%s', e)\n\n    # Add productions to the grammar\n    for funcname, gram in pinfo.grammar:\n        file, line, prodname, syms = gram\n        try:\n            grammar.add_production(prodname, syms, funcname, file, line)\n        except GrammarError as e:\n            errorlog.error('%s', e)\n            errors = True\n\n    # Set the grammar start symbols\n    try:\n        if start is None:\n            grammar.set_start(pinfo.start)\n        else:\n            grammar.set_start(start)\n    except GrammarError as e:\n        errorlog.error(str(e))\n        errors = True\n\n    if errors:\n        raise YaccError('Unable to build parser')\n\n    # Verify the grammar structure\n    undefined_symbols = grammar.undefined_symbols()\n    for sym, prod in undefined_symbols:\n        errorlog.error('%s:%d: Symbol %r used, but not defined as a token or a rule', prod.file, prod.line, sym)\n        errors = True\n\n    unused_terminals = grammar.unused_terminals()\n    if unused_terminals:\n        debuglog.info('')\n        debuglog.info('Unused terminals:')\n        debuglog.info('')\n        for term in unused_terminals:\n            errorlog.warning('Token %r defined, but not used', term)\n            debuglog.info('    %s', term)\n\n    # Print out all productions to the debug log\n    if debug:\n        debuglog.info('')\n        debuglog.info('Grammar')\n        debuglog.info('')\n        for n, p in enumerate(grammar.Productions):\n            debuglog.info('Rule %-5d %s', n, p)\n\n    # Find unused non-terminals\n    unused_rules = grammar.unused_rules()\n    for prod in unused_rules:\n        errorlog.warning('%s:%d: Rule %r defined, but not used', prod.file, prod.line, prod.name)\n\n    if len(unused_terminals) == 1:\n        errorlog.warning('There is 1 unused token')\n    if len(unused_terminals) > 1:\n        errorlog.warning('There are %d unused tokens', len(unused_terminals))\n\n    if len(unused_rules) == 1:\n        errorlog.warning('There is 1 unused rule')\n    if len(unused_rules) > 1:\n        errorlog.warning('There are %d unused rules', len(unused_rules))\n\n    if debug:\n        debuglog.info('')\n        debuglog.info('Terminals, with rules where they appear')\n        debuglog.info('')\n        terms = list(grammar.Terminals)\n        terms.sort()\n        for term in terms:\n            debuglog.info('%-20s : %s', term, ' '.join([str(s) for s in grammar.Terminals[term]]))\n\n        debuglog.info('')\n        debuglog.info('Nonterminals, with rules where they appear')\n        debuglog.info('')\n        nonterms = list(grammar.Nonterminals)\n        nonterms.sort()\n        for nonterm in nonterms:\n            debuglog.info('%-20s : %s', nonterm, ' '.join([str(s) for s in grammar.Nonterminals[nonterm]]))\n        debuglog.info('')\n\n    if check_recursion:\n        unreachable = grammar.find_unreachable()\n        for u in unreachable:\n            errorlog.warning('Symbol %r is unreachable', u)\n\n        infinite = grammar.infinite_cycles()\n        for inf in infinite:\n            errorlog.error('Infinite recursion detected for symbol %r', inf)\n            errors = True\n\n    unused_prec = grammar.unused_precedence()\n    for term, assoc in unused_prec:\n        errorlog.error('Precedence rule %r defined for unknown symbol %r', assoc, term)\n        errors = True\n\n    if errors:\n        raise YaccError('Unable to build parser')\n\n    # Run the LRGeneratedTable on the grammar\n    if debug:\n        errorlog.debug('Generating %s tables', method)\n\n    lr = LRGeneratedTable(grammar, method, debuglog)\n\n    if debug:\n        num_sr = len(lr.sr_conflicts)\n\n        # Report shift/reduce and reduce/reduce conflicts\n        if num_sr == 1:\n            errorlog.warning('1 shift/reduce conflict')\n        elif num_sr > 1:\n            errorlog.warning('%d shift/reduce conflicts', num_sr)\n\n        num_rr = len(lr.rr_conflicts)\n        if num_rr == 1:\n            errorlog.warning('1 reduce/reduce conflict')\n        elif num_rr > 1:\n            errorlog.warning('%d reduce/reduce conflicts', num_rr)\n\n    # Write out conflicts to the output file\n    if debug and (lr.sr_conflicts or lr.rr_conflicts):\n        debuglog.warning('')\n        debuglog.warning('Conflicts:')\n        debuglog.warning('')\n\n        for state, tok, resolution in lr.sr_conflicts:\n            debuglog.warning('shift/reduce conflict for %s in state %d resolved as %s',  tok, state, resolution)\n\n        already_reported = set()\n        for state, rule, rejected in lr.rr_conflicts:\n            if (state, id(rule), id(rejected)) in already_reported:\n                continue\n            debuglog.warning('reduce/reduce conflict in state %d resolved using rule (%s)', state, rule)\n            debuglog.warning('rejected rule (%s) in state %d', rejected, state)\n            errorlog.warning('reduce/reduce conflict in state %d resolved using rule (%s)', state, rule)\n            errorlog.warning('rejected rule (%s) in state %d', rejected, state)\n            already_reported.add((state, id(rule), id(rejected)))\n\n        warned_never = []\n        for state, rule, rejected in lr.rr_conflicts:\n            if not rejected.reduced and (rejected not in warned_never):\n                debuglog.warning('Rule (%s) is never reduced', rejected)\n                errorlog.warning('Rule (%s) is never reduced', rejected)\n                warned_never.append(rejected)\n\n    # Write the table file if requested\n    if write_tables:\n        try:\n            lr.write_table(tabmodule, outputdir, signature)\n        except IOError as e:\n            errorlog.warning(\"Couldn't create %r. %s\" % (tabmodule, e))\n\n    # Write a pickled version of the tables\n    if picklefile:\n        try:\n            lr.pickle_table(picklefile, signature)\n        except IOError as e:\n            errorlog.warning(\"Couldn't create %r. %s\" % (picklefile, e))\n\n    # Build the parser\n    lr.bind_callables(pinfo.pdict)\n    parser = LRParser(lr, pinfo.error_func)\n\n    parse = parser.parse\n    return parser\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/ply/ygen.py",
    "content": "# ply: ygen.py\n#\n# This is a support program that auto-generates different versions of the YACC parsing\n# function with different features removed for the purposes of performance.\n#\n# Users should edit the method LParser.parsedebug() in yacc.py.   The source code \n# for that method is then used to create the other methods.   See the comments in\n# yacc.py for further details.\n\nimport os.path\nimport shutil\n\ndef get_source_range(lines, tag):\n    srclines = enumerate(lines)\n    start_tag = '#--! %s-start' % tag\n    end_tag = '#--! %s-end' % tag\n\n    for start_index, line in srclines:\n        if line.strip().startswith(start_tag):\n            break\n\n    for end_index, line in srclines:\n        if line.strip().endswith(end_tag):\n            break\n\n    return (start_index + 1, end_index)\n\ndef filter_section(lines, tag):\n    filtered_lines = []\n    include = True\n    tag_text = '#--! %s' % tag\n    for line in lines:\n        if line.strip().startswith(tag_text):\n            include = not include\n        elif include:\n            filtered_lines.append(line)\n    return filtered_lines\n\ndef main():\n    dirname = os.path.dirname(__file__)\n    shutil.copy2(os.path.join(dirname, 'yacc.py'), os.path.join(dirname, 'yacc.py.bak'))\n    with open(os.path.join(dirname, 'yacc.py'), 'r') as f:\n        lines = f.readlines()\n\n    parse_start, parse_end = get_source_range(lines, 'parsedebug')\n    parseopt_start, parseopt_end = get_source_range(lines, 'parseopt')\n    parseopt_notrack_start, parseopt_notrack_end = get_source_range(lines, 'parseopt-notrack')\n\n    # Get the original source\n    orig_lines = lines[parse_start:parse_end]\n\n    # Filter the DEBUG sections out\n    parseopt_lines = filter_section(orig_lines, 'DEBUG')\n\n    # Filter the TRACKING sections out\n    parseopt_notrack_lines = filter_section(parseopt_lines, 'TRACKING')\n\n    # Replace the parser source sections with updated versions\n    lines[parseopt_notrack_start:parseopt_notrack_end] = parseopt_notrack_lines\n    lines[parseopt_start:parseopt_end] = parseopt_lines\n\n    lines = [line.rstrip()+'\\n' for line in lines]\n    with open(os.path.join(dirname, 'yacc.py'), 'w') as f:\n        f.writelines(lines)\n\n    print('Updated yacc.py')\n\nif __name__ == '__main__':\n    main()\n\n\n\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/plyparser.py",
    "content": "#-----------------------------------------------------------------\n# plyparser.py\n#\n# PLYParser class and other utilites for simplifying programming\n# parsers with PLY\n#\n# Eli Bendersky [https://eli.thegreenplace.net/]\n# License: BSD\n#-----------------------------------------------------------------\n\nimport warnings\n\nclass Coord(object):\n    \"\"\" Coordinates of a syntactic element. Consists of:\n            - File name\n            - Line number\n            - (optional) column number, for the Lexer\n    \"\"\"\n    __slots__ = ('file', 'line', 'column', '__weakref__')\n    def __init__(self, file, line, column=None):\n        self.file = file\n        self.line = line\n        self.column = column\n\n    def __str__(self):\n        str = \"%s:%s\" % (self.file, self.line)\n        if self.column: str += \":%s\" % self.column\n        return str\n\n\nclass ParseError(Exception): pass\n\n\nclass PLYParser(object):\n    def _create_opt_rule(self, rulename):\n        \"\"\" Given a rule name, creates an optional ply.yacc rule\n            for it. The name of the optional rule is\n            <rulename>_opt\n        \"\"\"\n        optname = rulename + '_opt'\n\n        def optrule(self, p):\n            p[0] = p[1]\n\n        optrule.__doc__ = '%s : empty\\n| %s' % (optname, rulename)\n        optrule.__name__ = 'p_%s' % optname\n        setattr(self.__class__, optrule.__name__, optrule)\n\n    def _coord(self, lineno, column=None):\n        return Coord(\n                file=self.clex.filename,\n                line=lineno,\n                column=column)\n\n    def _token_coord(self, p, token_idx):\n        \"\"\" Returns the coordinates for the YaccProduction objet 'p' indexed\n            with 'token_idx'. The coordinate includes the 'lineno' and\n            'column'. Both follow the lex semantic, starting from 1.\n        \"\"\"\n        last_cr = p.lexer.lexer.lexdata.rfind('\\n', 0, p.lexpos(token_idx))\n        if last_cr < 0:\n            last_cr = -1\n        column = (p.lexpos(token_idx) - (last_cr))\n        return self._coord(p.lineno(token_idx), column)\n\n    def _parse_error(self, msg, coord):\n        raise ParseError(\"%s: %s\" % (coord, msg))\n\n\ndef parameterized(*params):\n    \"\"\" Decorator to create parameterized rules.\n\n    Parameterized rule methods must be named starting with 'p_' and contain\n    'xxx', and their docstrings may contain 'xxx' and 'yyy'. These will be\n    replaced by the given parameter tuples. For example, ``p_xxx_rule()`` with\n    docstring 'xxx_rule  : yyy' when decorated with\n    ``@parameterized(('id', 'ID'))`` produces ``p_id_rule()`` with the docstring\n    'id_rule  : ID'. Using multiple tuples produces multiple rules.\n    \"\"\"\n    def decorate(rule_func):\n        rule_func._params = params\n        return rule_func\n    return decorate\n\n\ndef template(cls):\n    \"\"\" Class decorator to generate rules from parameterized rule templates.\n\n    See `parameterized` for more information on parameterized rules.\n    \"\"\"\n    issued_nodoc_warning = False\n    for attr_name in dir(cls):\n        if attr_name.startswith('p_'):\n            method = getattr(cls, attr_name)\n            if hasattr(method, '_params'):\n                # Remove the template method\n                delattr(cls, attr_name)\n                # Create parameterized rules from this method; only run this if\n                # the method has a docstring. This is to address an issue when\n                # pycparser's users are installed in -OO mode which strips\n                # docstrings away.\n                # See: https://github.com/eliben/pycparser/pull/198/ and\n                #      https://github.com/eliben/pycparser/issues/197\n                # for discussion.\n                if method.__doc__ is not None:\n                    _create_param_rules(cls, method)\n                elif not issued_nodoc_warning:\n                    warnings.warn(\n                        'parsing methods must have __doc__ for pycparser to work properly',\n                        RuntimeWarning,\n                        stacklevel=2)\n                    issued_nodoc_warning = True\n    return cls\n\n\ndef _create_param_rules(cls, func):\n    \"\"\" Create ply.yacc rules based on a parameterized rule function\n\n    Generates new methods (one per each pair of parameters) based on the\n    template rule function `func`, and attaches them to `cls`. The rule\n    function's parameters must be accessible via its `_params` attribute.\n    \"\"\"\n    for xxx, yyy in func._params:\n        # Use the template method's body for each new method\n        def param_rule(self, p):\n            func(self, p)\n\n        # Substitute in the params for the grammar rule and function name\n        param_rule.__doc__ = func.__doc__.replace('xxx', xxx).replace('yyy', yyy)\n        param_rule.__name__ = func.__name__.replace('xxx', xxx)\n\n        # Attach the new method to the class\n        setattr(cls, param_rule.__name__, param_rule)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser/yacctab.py",
    "content": "\n# yacctab.py\n# This file is automatically generated. Do not edit.\n_tabversion = '3.10'\n\n_lr_method = 'LALR'\n\n_lr_signature = 'translation_unit_or_emptyleftLORleftLANDleftORleftXORleftANDleftEQNEleftGTGELTLEleftRSHIFTLSHIFTleftPLUSMINUSleftTIMESDIVIDEMOD_BOOL _COMPLEX AUTO BREAK CASE CHAR CONST CONTINUE DEFAULT DO DOUBLE ELSE ENUM EXTERN FLOAT FOR GOTO IF INLINE INT LONG REGISTER OFFSETOF RESTRICT RETURN SHORT SIGNED SIZEOF STATIC STRUCT SWITCH TYPEDEF UNION UNSIGNED VOID VOLATILE WHILE __INT128 ID TYPEID INT_CONST_DEC INT_CONST_OCT INT_CONST_HEX INT_CONST_BIN FLOAT_CONST HEX_FLOAT_CONST CHAR_CONST WCHAR_CONST STRING_LITERAL WSTRING_LITERAL PLUS MINUS TIMES DIVIDE MOD OR AND NOT XOR LSHIFT RSHIFT LOR LAND LNOT LT LE GT GE EQ NE EQUALS TIMESEQUAL DIVEQUAL MODEQUAL PLUSEQUAL MINUSEQUAL LSHIFTEQUAL RSHIFTEQUAL ANDEQUAL XOREQUAL OREQUAL PLUSPLUS MINUSMINUS ARROW CONDOP LPAREN RPAREN LBRACKET RBRACKET LBRACE RBRACE COMMA PERIOD SEMI COLON ELLIPSIS PPHASH PPPRAGMA PPPRAGMASTRabstract_declarator_opt : empty\\n| abstract_declaratorassignment_expression_opt : empty\\n| assignment_expressionblock_item_list_opt : empty\\n| block_item_listdeclaration_list_opt : empty\\n| declaration_listdeclaration_specifiers_no_type_opt : empty\\n| declaration_specifiers_no_typedesignation_opt : empty\\n| designationexpression_opt : empty\\n| expressionid_init_declarator_list_opt : empty\\n| id_init_declarator_listidentifier_list_opt : empty\\n| identifier_listinit_declarator_list_opt : empty\\n| init_declarator_listinitializer_list_opt : empty\\n| initializer_listparameter_type_list_opt : empty\\n| parameter_type_liststruct_declarator_list_opt : empty\\n| struct_declarator_listtype_qualifier_list_opt : empty\\n| type_qualifier_list direct_id_declarator   : ID\\n         direct_id_declarator   : LPAREN id_declarator RPAREN\\n         direct_id_declarator   : direct_id_declarator LBRACKET type_qualifier_list_opt assignment_expression_opt RBRACKET\\n         direct_id_declarator   : direct_id_declarator LBRACKET STATIC type_qualifier_list_opt assignment_expression RBRACKET\\n                                    | direct_id_declarator LBRACKET type_qualifier_list STATIC assignment_expression RBRACKET\\n         direct_id_declarator   : direct_id_declarator LBRACKET type_qualifier_list_opt TIMES RBRACKET\\n         direct_id_declarator   : direct_id_declarator LPAREN parameter_type_list RPAREN\\n                                    | direct_id_declarator LPAREN identifier_list_opt RPAREN\\n         direct_typeid_declarator   : TYPEID\\n         direct_typeid_declarator   : LPAREN typeid_declarator RPAREN\\n         direct_typeid_declarator   : direct_typeid_declarator LBRACKET type_qualifier_list_opt assignment_expression_opt RBRACKET\\n         direct_typeid_declarator   : direct_typeid_declarator LBRACKET STATIC type_qualifier_list_opt assignment_expression RBRACKET\\n                                    | direct_typeid_declarator LBRACKET type_qualifier_list STATIC assignment_expression RBRACKET\\n         direct_typeid_declarator   : direct_typeid_declarator LBRACKET type_qualifier_list_opt TIMES RBRACKET\\n         direct_typeid_declarator   : direct_typeid_declarator LPAREN parameter_type_list RPAREN\\n                                    | direct_typeid_declarator LPAREN identifier_list_opt RPAREN\\n         direct_typeid_noparen_declarator   : TYPEID\\n         direct_typeid_noparen_declarator   : direct_typeid_noparen_declarator LBRACKET type_qualifier_list_opt assignment_expression_opt RBRACKET\\n         direct_typeid_noparen_declarator   : direct_typeid_noparen_declarator LBRACKET STATIC type_qualifier_list_opt assignment_expression RBRACKET\\n                                    | direct_typeid_noparen_declarator LBRACKET type_qualifier_list STATIC assignment_expression RBRACKET\\n         direct_typeid_noparen_declarator   : direct_typeid_noparen_declarator LBRACKET type_qualifier_list_opt TIMES RBRACKET\\n         direct_typeid_noparen_declarator   : direct_typeid_noparen_declarator LPAREN parameter_type_list RPAREN\\n                                    | direct_typeid_noparen_declarator LPAREN identifier_list_opt RPAREN\\n         id_declarator  : direct_id_declarator\\n         id_declarator  : pointer direct_id_declarator\\n         typeid_declarator  : direct_typeid_declarator\\n         typeid_declarator  : pointer direct_typeid_declarator\\n         typeid_noparen_declarator  : direct_typeid_noparen_declarator\\n         typeid_noparen_declarator  : pointer direct_typeid_noparen_declarator\\n         translation_unit_or_empty   : translation_unit\\n                                        | empty\\n         translation_unit    : external_declaration\\n         translation_unit    : translation_unit external_declaration\\n         external_declaration    : function_definition\\n         external_declaration    : declaration\\n         external_declaration    : pp_directive\\n                                    | pppragma_directive\\n         external_declaration    : SEMI\\n         pp_directive  : PPHASH\\n         pppragma_directive      : PPPRAGMA\\n                                    | PPPRAGMA PPPRAGMASTR\\n         function_definition : id_declarator declaration_list_opt compound_statement\\n         function_definition : declaration_specifiers id_declarator declaration_list_opt compound_statement\\n         statement   : labeled_statement\\n                        | expression_statement\\n                        | compound_statement\\n                        | selection_statement\\n                        | iteration_statement\\n                        | jump_statement\\n                        | pppragma_directive\\n         pragmacomp_or_statement     : pppragma_directive statement\\n                                        | statement\\n         decl_body : declaration_specifiers init_declarator_list_opt\\n                      | declaration_specifiers_no_type id_init_declarator_list_opt\\n         declaration : decl_body SEMI\\n         declaration_list    : declaration\\n                                | declaration_list declaration\\n         declaration_specifiers_no_type  : type_qualifier declaration_specifiers_no_type_opt\\n         declaration_specifiers_no_type  : storage_class_specifier declaration_specifiers_no_type_opt\\n         declaration_specifiers_no_type  : function_specifier declaration_specifiers_no_type_opt\\n         declaration_specifiers  : declaration_specifiers type_qualifier\\n         declaration_specifiers  : declaration_specifiers storage_class_specifier\\n         declaration_specifiers  : declaration_specifiers function_specifier\\n         declaration_specifiers  : declaration_specifiers type_specifier_no_typeid\\n         declaration_specifiers  : type_specifier\\n         declaration_specifiers  : declaration_specifiers_no_type type_specifier\\n         storage_class_specifier : AUTO\\n                                    | REGISTER\\n                                    | STATIC\\n                                    | EXTERN\\n                                    | TYPEDEF\\n         function_specifier  : INLINE\\n         type_specifier_no_typeid  : VOID\\n                                      | _BOOL\\n                                      | CHAR\\n                                      | SHORT\\n                                      | INT\\n                                      | LONG\\n                                      | FLOAT\\n                                      | DOUBLE\\n                                      | _COMPLEX\\n                                      | SIGNED\\n                                      | UNSIGNED\\n                                      | __INT128\\n         type_specifier  : typedef_name\\n                            | enum_specifier\\n                            | struct_or_union_specifier\\n                            | type_specifier_no_typeid\\n         type_qualifier  : CONST\\n                            | RESTRICT\\n                            | VOLATILE\\n         init_declarator_list    : init_declarator\\n                                    | init_declarator_list COMMA init_declarator\\n         init_declarator : declarator\\n                            | declarator EQUALS initializer\\n         id_init_declarator_list    : id_init_declarator\\n                                       | id_init_declarator_list COMMA init_declarator\\n         id_init_declarator : id_declarator\\n                               | id_declarator EQUALS initializer\\n         specifier_qualifier_list    : specifier_qualifier_list type_specifier_no_typeid\\n         specifier_qualifier_list    : specifier_qualifier_list type_qualifier\\n         specifier_qualifier_list  : type_specifier\\n         specifier_qualifier_list  : type_qualifier_list type_specifier\\n         struct_or_union_specifier   : struct_or_union ID\\n                                        | struct_or_union TYPEID\\n         struct_or_union_specifier : struct_or_union brace_open struct_declaration_list brace_close\\n                                      | struct_or_union brace_open brace_close\\n         struct_or_union_specifier   : struct_or_union ID brace_open struct_declaration_list brace_close\\n                                        | struct_or_union ID brace_open brace_close\\n                                        | struct_or_union TYPEID brace_open struct_declaration_list brace_close\\n                                        | struct_or_union TYPEID brace_open brace_close\\n         struct_or_union : STRUCT\\n                            | UNION\\n         struct_declaration_list     : struct_declaration\\n                                        | struct_declaration_list struct_declaration\\n         struct_declaration : specifier_qualifier_list struct_declarator_list_opt SEMI\\n         struct_declaration : SEMI\\n         struct_declaration : pppragma_directive\\n         struct_declarator_list  : struct_declarator\\n                                    | struct_declarator_list COMMA struct_declarator\\n         struct_declarator : declarator\\n         struct_declarator   : declarator COLON constant_expression\\n                                | COLON constant_expression\\n         enum_specifier  : ENUM ID\\n                            | ENUM TYPEID\\n         enum_specifier  : ENUM brace_open enumerator_list brace_close\\n         enum_specifier  : ENUM ID brace_open enumerator_list brace_close\\n                            | ENUM TYPEID brace_open enumerator_list brace_close\\n         enumerator_list : enumerator\\n                            | enumerator_list COMMA\\n                            | enumerator_list COMMA enumerator\\n         enumerator  : ID\\n                        | ID EQUALS constant_expression\\n         declarator  : id_declarator\\n                        | typeid_declarator\\n         pointer : TIMES type_qualifier_list_opt\\n                    | TIMES type_qualifier_list_opt pointer\\n         type_qualifier_list : type_qualifier\\n                                | type_qualifier_list type_qualifier\\n         parameter_type_list : parameter_list\\n                                | parameter_list COMMA ELLIPSIS\\n         parameter_list  : parameter_declaration\\n                            | parameter_list COMMA parameter_declaration\\n         parameter_declaration   : declaration_specifiers id_declarator\\n                                    | declaration_specifiers typeid_noparen_declarator\\n         parameter_declaration   : declaration_specifiers abstract_declarator_opt\\n         identifier_list : identifier\\n                            | identifier_list COMMA identifier\\n         initializer : assignment_expression\\n         initializer : brace_open initializer_list_opt brace_close\\n                        | brace_open initializer_list COMMA brace_close\\n         initializer_list    : designation_opt initializer\\n                                | initializer_list COMMA designation_opt initializer\\n         designation : designator_list EQUALS\\n         designator_list : designator\\n                            | designator_list designator\\n         designator  : LBRACKET constant_expression RBRACKET\\n                        | PERIOD identifier\\n         type_name   : specifier_qualifier_list abstract_declarator_opt\\n         abstract_declarator     : pointer\\n         abstract_declarator     : pointer direct_abstract_declarator\\n         abstract_declarator     : direct_abstract_declarator\\n         direct_abstract_declarator  : LPAREN abstract_declarator RPAREN  direct_abstract_declarator  : direct_abstract_declarator LBRACKET assignment_expression_opt RBRACKET\\n         direct_abstract_declarator  : LBRACKET assignment_expression_opt RBRACKET\\n         direct_abstract_declarator  : direct_abstract_declarator LBRACKET TIMES RBRACKET\\n         direct_abstract_declarator  : LBRACKET TIMES RBRACKET\\n         direct_abstract_declarator  : direct_abstract_declarator LPAREN parameter_type_list_opt RPAREN\\n         direct_abstract_declarator  : LPAREN parameter_type_list_opt RPAREN\\n         block_item  : declaration\\n                        | statement\\n         block_item_list : block_item\\n                            | block_item_list block_item\\n         compound_statement : brace_open block_item_list_opt brace_close  labeled_statement : ID COLON pragmacomp_or_statement  labeled_statement : CASE constant_expression COLON pragmacomp_or_statement  labeled_statement : DEFAULT COLON pragmacomp_or_statement  selection_statement : IF LPAREN expression RPAREN pragmacomp_or_statement  selection_statement : IF LPAREN expression RPAREN statement ELSE pragmacomp_or_statement  selection_statement : SWITCH LPAREN expression RPAREN pragmacomp_or_statement  iteration_statement : WHILE LPAREN expression RPAREN pragmacomp_or_statement  iteration_statement : DO pragmacomp_or_statement WHILE LPAREN expression RPAREN SEMI  iteration_statement : FOR LPAREN expression_opt SEMI expression_opt SEMI expression_opt RPAREN pragmacomp_or_statement  iteration_statement : FOR LPAREN declaration expression_opt SEMI expression_opt RPAREN pragmacomp_or_statement  jump_statement  : GOTO ID SEMI  jump_statement  : BREAK SEMI  jump_statement  : CONTINUE SEMI  jump_statement  : RETURN expression SEMI\\n                            | RETURN SEMI\\n         expression_statement : expression_opt SEMI  expression  : assignment_expression\\n                        | expression COMMA assignment_expression\\n         typedef_name : TYPEID  assignment_expression   : conditional_expression\\n                                    | unary_expression assignment_operator assignment_expression\\n         assignment_operator : EQUALS\\n                                | XOREQUAL\\n                                | TIMESEQUAL\\n                                | DIVEQUAL\\n                                | MODEQUAL\\n                                | PLUSEQUAL\\n                                | MINUSEQUAL\\n                                | LSHIFTEQUAL\\n                                | RSHIFTEQUAL\\n                                | ANDEQUAL\\n                                | OREQUAL\\n         constant_expression : conditional_expression  conditional_expression  : binary_expression\\n                                    | binary_expression CONDOP expression COLON conditional_expression\\n         binary_expression   : cast_expression\\n                                | binary_expression TIMES binary_expression\\n                                | binary_expression DIVIDE binary_expression\\n                                | binary_expression MOD binary_expression\\n                                | binary_expression PLUS binary_expression\\n                                | binary_expression MINUS binary_expression\\n                                | binary_expression RSHIFT binary_expression\\n                                | binary_expression LSHIFT binary_expression\\n                                | binary_expression LT binary_expression\\n                                | binary_expression LE binary_expression\\n                                | binary_expression GE binary_expression\\n                                | binary_expression GT binary_expression\\n                                | binary_expression EQ binary_expression\\n                                | binary_expression NE binary_expression\\n                                | binary_expression AND binary_expression\\n                                | binary_expression OR binary_expression\\n                                | binary_expression XOR binary_expression\\n                                | binary_expression LAND binary_expression\\n                                | binary_expression LOR binary_expression\\n         cast_expression : unary_expression  cast_expression : LPAREN type_name RPAREN cast_expression  unary_expression    : postfix_expression  unary_expression    : PLUSPLUS unary_expression\\n                                | MINUSMINUS unary_expression\\n                                | unary_operator cast_expression\\n         unary_expression    : SIZEOF unary_expression\\n                                | SIZEOF LPAREN type_name RPAREN\\n         unary_operator  : AND\\n                            | TIMES\\n                            | PLUS\\n                            | MINUS\\n                            | NOT\\n                            | LNOT\\n         postfix_expression  : primary_expression  postfix_expression  : postfix_expression LBRACKET expression RBRACKET  postfix_expression  : postfix_expression LPAREN argument_expression_list RPAREN\\n                                | postfix_expression LPAREN RPAREN\\n         postfix_expression  : postfix_expression PERIOD ID\\n                                | postfix_expression PERIOD TYPEID\\n                                | postfix_expression ARROW ID\\n                                | postfix_expression ARROW TYPEID\\n         postfix_expression  : postfix_expression PLUSPLUS\\n                                | postfix_expression MINUSMINUS\\n         postfix_expression  : LPAREN type_name RPAREN brace_open initializer_list brace_close\\n                                | LPAREN type_name RPAREN brace_open initializer_list COMMA brace_close\\n         primary_expression  : identifier  primary_expression  : constant  primary_expression  : unified_string_literal\\n                                | unified_wstring_literal\\n         primary_expression  : LPAREN expression RPAREN  primary_expression  : OFFSETOF LPAREN type_name COMMA offsetof_member_designator RPAREN\\n         offsetof_member_designator : identifier\\n                                         | offsetof_member_designator PERIOD identifier\\n                                         | offsetof_member_designator LBRACKET expression RBRACKET\\n         argument_expression_list    : assignment_expression\\n                                        | argument_expression_list COMMA assignment_expression\\n         identifier  : ID  constant    : INT_CONST_DEC\\n                        | INT_CONST_OCT\\n                        | INT_CONST_HEX\\n                        | INT_CONST_BIN\\n         constant    : FLOAT_CONST\\n                        | HEX_FLOAT_CONST\\n         constant    : CHAR_CONST\\n                        | WCHAR_CONST\\n         unified_string_literal  : STRING_LITERAL\\n                                    | unified_string_literal STRING_LITERAL\\n         unified_wstring_literal : WSTRING_LITERAL\\n                                    | unified_wstring_literal WSTRING_LITERAL\\n         brace_open  :   LBRACE\\n         brace_close :   RBRACE\\n        empty : '\n    \n_lr_action_items = {'VOID':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,78,80,83,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,286,287,288,291,293,296,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[6,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,6,-96,-111,-106,-65,-95,-112,6,-221,-109,-113,6,-63,-118,6,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,6,-53,6,-84,6,6,-61,-133,-307,-132,6,-153,-152,-166,-90,-92,6,-89,-91,-94,-83,-86,-88,-69,-30,6,6,-70,6,-85,6,6,6,-135,-130,-145,-146,-142,-308,6,6,-167,6,6,-36,-35,6,6,-73,-76,-72,-74,6,-78,-199,-198,-77,-200,-75,6,-139,6,-137,-134,-143,-131,-128,-129,-154,-71,6,-31,6,6,6,-34,6,6,6,-218,-217,6,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,6,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'LBRACKET':([2,3,5,6,7,8,9,10,11,15,16,19,20,21,24,25,29,30,31,32,35,37,39,41,44,45,48,50,51,54,61,69,70,71,73,74,76,77,78,79,80,83,85,88,91,92,96,105,113,115,126,127,131,139,140,143,150,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,187,188,189,192,193,196,199,229,232,234,235,237,238,244,249,251,260,276,279,280,282,286,293,296,319,324,325,356,357,362,363,370,371,374,379,383,384,385,386,389,394,397,398,418,419,420,421,427,428,447,448,452,454,456,459,460,466,472,473,474,475,476,484,485,486,491,492,495,496,507,510,511,512,513,518,520,525,],[-104,-117,-115,-101,-99,59,-97,-116,-98,-102,-93,-96,-111,-106,-95,-112,-221,-109,-309,-113,-118,-29,-107,-103,-114,-108,-110,-105,-119,-100,59,-133,-307,-132,-153,-152,-28,-164,-166,-27,-90,-92,144,-37,-89,-91,-94,-30,198,-294,-135,-130,-308,-167,-165,144,-298,-286,-301,-305,-302,-299,-284,-285,284,-297,-271,-303,-295,-283,-300,-296,-36,-35,198,198,326,-45,330,-294,-139,-137,-134,-131,-128,-129,-154,-38,376,-306,-304,-280,-279,-31,-34,198,198,326,330,-138,-136,-156,-155,-44,-43,-183,376,-278,-277,-276,-275,-274,-287,198,198,-33,-32,-197,-191,-193,-195,-39,-42,-186,376,-184,-272,-273,376,-51,-50,-192,-194,-196,-41,-40,-185,509,-289,-46,-49,-288,376,-281,-48,-47,-290,-282,-291,]),'WCHAR_CONST':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,156,-28,-309,156,-308,-167,-309,156,156,-270,156,-268,156,-267,156,-266,156,156,-265,-269,156,156,156,-73,-76,-72,156,-74,156,156,-78,-199,-198,-77,-200,156,-75,-266,156,156,156,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,156,-233,-234,-226,-232,156,156,156,156,156,156,156,156,156,156,156,156,156,156,156,156,156,156,156,156,156,156,156,156,-309,-266,156,-218,-217,156,-215,156,156,156,-201,156,-214,156,-80,-202,156,156,156,-266,156,156,-12,156,156,-11,156,156,-28,-309,-266,-213,-216,156,-205,156,-79,-203,-309,-182,156,156,-309,156,-266,156,156,156,156,-204,156,156,156,156,-11,156,-209,-208,-206,-80,156,-309,156,156,156,-210,-207,156,-212,-211,]),'FLOAT_CONST':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,157,-28,-309,157,-308,-167,-309,157,157,-270,157,-268,157,-267,157,-266,157,157,-265,-269,157,157,157,-73,-76,-72,157,-74,157,157,-78,-199,-198,-77,-200,157,-75,-266,157,157,157,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,157,-233,-234,-226,-232,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,157,-309,-266,157,-218,-217,157,-215,157,157,157,-201,157,-214,157,-80,-202,157,157,157,-266,157,157,-12,157,157,-11,157,157,-28,-309,-266,-213,-216,157,-205,157,-79,-203,-309,-182,157,157,-309,157,-266,157,157,157,157,-204,157,157,157,157,-11,157,-209,-208,-206,-80,157,-309,157,157,157,-210,-207,157,-212,-211,]),'MINUS':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,115,121,131,139,144,147,148,150,151,152,153,154,155,156,157,158,159,160,161,162,164,166,167,169,170,171,172,173,174,175,176,177,178,179,180,181,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,229,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,276,277,278,279,280,282,284,285,288,289,290,291,292,297,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,383,384,385,386,389,394,395,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,422,423,424,430,432,433,435,437,439,442,443,454,457,458,459,460,461,463,465,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,507,509,510,511,514,517,520,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,160,-28,-309,-294,160,-308,-167,-309,160,160,-298,-270,-257,-286,-301,-305,-302,-299,-284,160,-268,-285,-259,-238,160,-267,160,-297,-266,-271,160,160,-303,-265,-295,-283,301,-300,-296,-269,160,160,160,-73,-76,-72,160,-74,160,160,-78,-199,-198,-77,-200,160,-75,-266,-294,160,160,160,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,160,-233,-234,-226,-232,-306,160,-263,-304,-280,-279,160,160,160,-257,-262,160,-260,-261,160,160,160,160,160,160,160,160,160,160,160,160,160,160,160,160,160,160,160,-309,-266,160,-218,-217,160,-215,160,160,160,-201,160,-214,160,-80,-202,160,160,160,-266,160,160,-12,160,160,-11,-278,-277,-276,-275,-274,-287,160,301,301,301,-243,301,301,301,-242,301,301,-240,-239,301,301,301,301,301,-241,160,-28,-309,-266,-213,-216,160,-205,160,-79,-203,-309,-182,-264,-272,-273,160,160,-258,-309,160,-266,160,160,160,160,-204,160,160,160,160,-11,160,-209,-208,-206,-80,-288,160,-309,-281,160,160,-282,160,-210,-207,160,-212,-211,]),'RPAREN':([2,3,5,6,7,8,9,10,11,15,16,19,20,21,24,25,29,30,31,32,35,37,39,41,44,45,48,50,51,54,58,60,61,69,71,73,74,76,77,78,79,80,83,85,88,91,92,96,105,109,110,111,112,113,114,115,116,118,126,127,131,139,140,141,143,145,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,183,187,188,189,190,191,192,193,194,195,196,197,199,211,227,232,234,235,237,238,244,249,251,256,257,276,278,279,280,282,285,286,289,290,292,293,294,295,296,297,319,320,321,322,323,324,325,327,331,332,333,334,347,356,357,362,363,370,371,381,382,383,384,385,386,388,389,390,392,393,394,396,397,398,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,418,419,420,421,425,426,427,428,431,436,438,440,444,447,448,458,459,460,465,472,473,474,475,476,484,485,490,491,492,494,495,496,500,503,507,511,512,513,514,515,518,520,521,525,],[-104,-117,-115,-101,-99,-52,-97,-116,-98,-102,-93,-96,-111,-106,-95,-112,-221,-109,-309,-113,-118,-29,-107,-103,-114,-108,-110,-105,-119,-100,105,-309,-53,-133,-132,-153,-152,-28,-164,-166,-27,-90,-92,-54,-37,-89,-91,-94,-30,187,-17,188,-170,-309,-18,-294,-168,-175,-135,-130,-308,-167,-165,251,-55,-309,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,-236,-300,-296,-222,-36,-35,-309,-174,-2,-188,-56,-172,-1,-45,-173,-190,-14,-219,-139,-137,-134,-131,-128,-129,-154,-38,370,371,-306,-263,-304,-280,-279,389,-31,-257,-262,-260,-34,394,395,-309,-261,-188,-23,-24,420,421,-57,-189,-309,-309,-176,-169,-171,-13,-138,-136,-156,-155,-44,-43,-223,458,-278,-277,-276,-275,-292,-274,460,463,464,-287,-187,-188,-309,-244,-256,-245,-243,-247,-251,-246,-242,-249,-254,-240,-239,-248,-255,-250,-252,-253,-241,-33,-32,-197,-191,472,473,-193,-195,476,-220,479,481,483,-39,-42,-264,-272,-273,-258,-51,-50,-192,-194,-196,-41,-40,-293,507,-289,-237,-46,-49,-309,516,-288,-281,-48,-47,-309,522,-290,-282,526,-291,]),'LONG':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,78,80,83,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,286,287,288,291,293,296,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[21,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,21,-96,-111,-106,-65,-95,-112,21,-221,-109,-113,21,-63,-118,21,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,21,-53,21,-84,21,21,-61,-133,-307,-132,21,-153,-152,-166,-90,-92,21,-89,-91,-94,-83,-86,-88,-69,-30,21,21,-70,21,-85,21,21,21,-135,-130,-145,-146,-142,-308,21,21,-167,21,21,-36,-35,21,21,-73,-76,-72,-74,21,-78,-199,-198,-77,-200,-75,21,-139,21,-137,-134,-143,-131,-128,-129,-154,-71,21,-31,21,21,21,-34,21,21,21,-218,-217,21,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,21,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'PLUS':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,115,121,131,139,144,147,148,150,151,152,153,154,155,156,157,158,159,160,161,162,164,166,167,169,170,171,172,173,174,175,176,177,178,179,180,181,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,229,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,276,277,278,279,280,282,284,285,288,289,290,291,292,297,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,383,384,385,386,389,394,395,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,422,423,424,430,432,433,435,437,439,442,443,454,457,458,459,460,461,463,465,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,507,509,510,511,514,517,520,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,167,-28,-309,-294,167,-308,-167,-309,167,167,-298,-270,-257,-286,-301,-305,-302,-299,-284,167,-268,-285,-259,-238,167,-267,167,-297,-266,-271,167,167,-303,-265,-295,-283,305,-300,-296,-269,167,167,167,-73,-76,-72,167,-74,167,167,-78,-199,-198,-77,-200,167,-75,-266,-294,167,167,167,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,167,-233,-234,-226,-232,-306,167,-263,-304,-280,-279,167,167,167,-257,-262,167,-260,-261,167,167,167,167,167,167,167,167,167,167,167,167,167,167,167,167,167,167,167,-309,-266,167,-218,-217,167,-215,167,167,167,-201,167,-214,167,-80,-202,167,167,167,-266,167,167,-12,167,167,-11,-278,-277,-276,-275,-274,-287,167,305,305,305,-243,305,305,305,-242,305,305,-240,-239,305,305,305,305,305,-241,167,-28,-309,-266,-213,-216,167,-205,167,-79,-203,-309,-182,-264,-272,-273,167,167,-258,-309,167,-266,167,167,167,167,-204,167,167,167,167,-11,167,-209,-208,-206,-80,-288,167,-309,-281,167,167,-282,167,-210,-207,167,-212,-211,]),'ELLIPSIS':([201,],[333,]),'GT':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,306,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,306,-245,-243,-247,306,-246,-242,-249,306,-240,-239,-248,306,306,306,306,-241,-264,-272,-273,-258,-288,-281,-282,]),'GOTO':([53,70,101,104,121,131,202,203,206,208,215,217,218,219,220,222,224,225,336,337,340,342,346,349,351,352,353,354,432,433,437,439,442,443,479,480,481,483,501,502,504,505,517,522,523,524,526,527,528,],[-68,-307,-83,-69,204,-308,-73,-76,-72,-74,204,-78,-199,-198,-77,-200,204,-75,-218,-217,-215,204,-201,-214,204,-80,-202,204,-213,-216,-205,204,-79,-203,204,-204,204,204,-209,-208,-206,-80,204,204,-210,-207,204,-212,-211,]),'ENUM':([0,1,3,7,8,9,11,12,14,17,18,19,23,24,26,34,35,36,37,40,42,47,49,51,53,54,55,56,57,60,61,64,65,67,68,70,72,78,87,101,102,103,104,105,117,120,121,122,123,124,125,128,129,130,131,132,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,233,236,258,277,286,287,288,291,293,327,331,336,337,339,340,346,349,351,352,353,360,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[28,-309,-117,-99,-52,-97,-98,-64,-60,-66,28,-96,-65,-95,28,-63,-118,28,-29,-62,-67,-309,-309,-119,-68,-100,-87,-10,-9,28,-53,-84,28,28,-61,-307,28,-166,28,-83,-86,-88,-69,-30,28,-70,28,-85,28,28,28,-145,-146,-142,-308,28,-167,28,28,-36,-35,28,28,-73,-76,-72,-74,28,-78,-199,-198,-77,-200,-75,28,28,-143,-71,28,-31,28,28,28,-34,28,28,-218,-217,28,-215,-201,-214,-78,-80,-202,-144,28,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'PERIOD':([70,115,131,150,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,229,260,276,279,280,282,374,379,383,384,385,386,389,394,452,454,456,459,460,466,486,491,492,507,510,511,518,520,525,],[-307,-294,-308,-298,-286,-301,-305,-302,-299,-284,-285,283,-297,-271,-303,-295,-283,-300,-296,-294,375,-306,-304,-280,-279,-183,375,-278,-277,-276,-275,-274,-287,-186,375,-184,-272,-273,375,-185,508,-289,-288,375,-281,-290,-282,-291,]),'GE':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,310,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,310,-245,-243,-247,310,-246,-242,-249,310,-240,-239,-248,310,310,310,310,-241,-264,-272,-273,-258,-288,-281,-282,]),'INT_CONST_DEC':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,177,-28,-309,177,-308,-167,-309,177,177,-270,177,-268,177,-267,177,-266,177,177,-265,-269,177,177,177,-73,-76,-72,177,-74,177,177,-78,-199,-198,-77,-200,177,-75,-266,177,177,177,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,177,-233,-234,-226,-232,177,177,177,177,177,177,177,177,177,177,177,177,177,177,177,177,177,177,177,177,177,177,177,177,-309,-266,177,-218,-217,177,-215,177,177,177,-201,177,-214,177,-80,-202,177,177,177,-266,177,177,-12,177,177,-11,177,177,-28,-309,-266,-213,-216,177,-205,177,-79,-203,-309,-182,177,177,-309,177,-266,177,177,177,177,-204,177,177,177,177,-11,177,-209,-208,-206,-80,177,-309,177,177,177,-210,-207,177,-212,-211,]),'ARROW':([115,131,150,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,229,276,279,280,282,383,384,385,386,389,394,459,460,507,511,520,],[-294,-308,-298,-286,-301,-305,-302,-299,-284,-285,281,-297,-271,-303,-295,-283,-300,-296,-294,-306,-304,-280,-279,-278,-277,-276,-275,-274,-287,-272,-273,-288,-281,-282,]),'CHAR':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,78,80,83,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,286,287,288,291,293,296,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[41,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,41,-96,-111,-106,-65,-95,-112,41,-221,-109,-113,41,-63,-118,41,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,41,-53,41,-84,41,41,-61,-133,-307,-132,41,-153,-152,-166,-90,-92,41,-89,-91,-94,-83,-86,-88,-69,-30,41,41,-70,41,-85,41,41,41,-135,-130,-145,-146,-142,-308,41,41,-167,41,41,-36,-35,41,41,-73,-76,-72,-74,41,-78,-199,-198,-77,-200,-75,41,-139,41,-137,-134,-143,-131,-128,-129,-154,-71,41,-31,41,41,41,-34,41,41,41,-218,-217,41,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,41,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'HEX_FLOAT_CONST':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,180,-28,-309,180,-308,-167,-309,180,180,-270,180,-268,180,-267,180,-266,180,180,-265,-269,180,180,180,-73,-76,-72,180,-74,180,180,-78,-199,-198,-77,-200,180,-75,-266,180,180,180,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,180,-233,-234,-226,-232,180,180,180,180,180,180,180,180,180,180,180,180,180,180,180,180,180,180,180,180,180,180,180,180,-309,-266,180,-218,-217,180,-215,180,180,180,-201,180,-214,180,-80,-202,180,180,180,-266,180,180,-12,180,180,-11,180,180,-28,-309,-266,-213,-216,180,-205,180,-79,-203,-309,-182,180,180,-309,180,-266,180,180,180,180,-204,180,180,180,180,-11,180,-209,-208,-206,-80,180,-309,180,180,180,-210,-207,180,-212,-211,]),'DOUBLE':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,78,80,83,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,286,287,288,291,293,296,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[45,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,45,-96,-111,-106,-65,-95,-112,45,-221,-109,-113,45,-63,-118,45,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,45,-53,45,-84,45,45,-61,-133,-307,-132,45,-153,-152,-166,-90,-92,45,-89,-91,-94,-83,-86,-88,-69,-30,45,45,-70,45,-85,45,45,45,-135,-130,-145,-146,-142,-308,45,45,-167,45,45,-36,-35,45,45,-73,-76,-72,-74,45,-78,-199,-198,-77,-200,-75,45,-139,45,-137,-134,-143,-131,-128,-129,-154,-71,45,-31,45,45,45,-34,45,45,45,-218,-217,45,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,45,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'MINUSEQUAL':([115,131,150,152,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,458,459,460,465,507,511,520,],[-294,-308,-298,265,-286,-301,-305,-302,-299,-284,-285,-259,-297,-271,-303,-295,-283,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-264,-272,-273,-258,-288,-281,-282,]),'INT_CONST_OCT':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,181,-28,-309,181,-308,-167,-309,181,181,-270,181,-268,181,-267,181,-266,181,181,-265,-269,181,181,181,-73,-76,-72,181,-74,181,181,-78,-199,-198,-77,-200,181,-75,-266,181,181,181,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,181,-233,-234,-226,-232,181,181,181,181,181,181,181,181,181,181,181,181,181,181,181,181,181,181,181,181,181,181,181,181,-309,-266,181,-218,-217,181,-215,181,181,181,-201,181,-214,181,-80,-202,181,181,181,-266,181,181,-12,181,181,-11,181,181,-28,-309,-266,-213,-216,181,-205,181,-79,-203,-309,-182,181,181,-309,181,-266,181,181,181,181,-204,181,181,181,181,-11,181,-209,-208,-206,-80,181,-309,181,181,181,-210,-207,181,-212,-211,]),'TIMESEQUAL':([115,131,150,152,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,458,459,460,465,507,511,520,],[-294,-308,-298,274,-286,-301,-305,-302,-299,-284,-285,-259,-297,-271,-303,-295,-283,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-264,-272,-273,-258,-288,-281,-282,]),'OR':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,315,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,315,-245,-243,-247,-251,-246,-242,-249,-254,-240,-239,-248,315,-250,-252,-253,-241,-264,-272,-273,-258,-288,-281,-282,]),'SHORT':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,78,80,83,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,286,287,288,291,293,296,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[2,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,2,-96,-111,-106,-65,-95,-112,2,-221,-109,-113,2,-63,-118,2,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,2,-53,2,-84,2,2,-61,-133,-307,-132,2,-153,-152,-166,-90,-92,2,-89,-91,-94,-83,-86,-88,-69,-30,2,2,-70,2,-85,2,2,2,-135,-130,-145,-146,-142,-308,2,2,-167,2,2,-36,-35,2,2,-73,-76,-72,-74,2,-78,-199,-198,-77,-200,-75,2,-139,2,-137,-134,-143,-131,-128,-129,-154,-71,2,-31,2,2,2,-34,2,2,2,-218,-217,2,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,2,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'RETURN':([53,70,101,104,121,131,202,203,206,208,215,217,218,219,220,222,224,225,336,337,340,342,346,349,351,352,353,354,432,433,437,439,442,443,479,480,481,483,501,502,504,505,517,522,523,524,526,527,528,],[-68,-307,-83,-69,207,-308,-73,-76,-72,-74,207,-78,-199,-198,-77,-200,207,-75,-218,-217,-215,207,-201,-214,207,-80,-202,207,-213,-216,-205,207,-79,-203,207,-204,207,207,-209,-208,-206,-80,207,207,-210,-207,207,-212,-211,]),'RSHIFTEQUAL':([115,131,150,152,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,458,459,460,465,507,511,520,],[-294,-308,-298,275,-286,-301,-305,-302,-299,-284,-285,-259,-297,-271,-303,-295,-283,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-264,-272,-273,-258,-288,-281,-282,]),'RESTRICT':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,31,32,33,34,35,37,39,40,41,42,44,45,47,48,49,50,51,53,54,59,60,61,63,64,67,68,69,70,71,72,73,74,76,78,80,83,87,91,92,96,101,104,105,107,108,113,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,144,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,254,255,258,277,286,287,288,291,293,296,326,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,423,424,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[35,35,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,35,-96,-111,-106,-65,-95,-112,35,-221,-109,35,-113,35,-63,-118,-29,-107,-62,-103,-67,-114,-108,35,-110,35,-105,-119,-68,-100,35,35,-53,35,-84,35,-61,-133,-307,-132,35,-153,-152,35,-166,-90,-92,35,-89,-91,-94,-83,-69,-30,35,35,35,-70,35,-85,35,35,35,-135,-130,-145,-146,-142,-308,35,35,-167,35,35,35,-36,-35,35,35,-73,-76,-72,-74,35,-78,-199,-198,-77,-200,-75,35,-139,35,-137,-134,-143,-131,-128,-129,-154,35,35,-71,35,-31,35,35,35,-34,35,35,35,35,-218,-217,35,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,35,-33,-32,35,35,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'STATIC':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,37,39,40,41,42,44,45,47,48,49,50,51,53,54,59,60,61,63,64,67,68,69,70,71,73,74,78,80,83,87,91,92,96,101,104,105,107,113,120,121,122,126,131,139,144,145,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,232,234,235,249,254,258,286,293,326,327,331,336,337,339,340,346,349,351,352,353,356,357,362,363,398,418,419,423,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[9,9,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,9,-96,-111,-106,-65,-95,-112,9,-221,-109,-113,9,-63,-118,-29,-107,-62,-103,-67,-114,-108,9,-110,9,-105,-119,-68,-100,108,9,-53,9,-84,9,-61,-133,-307,-132,-153,-152,-166,-90,-92,9,-89,-91,-94,-83,-69,-30,185,9,-70,9,-85,-135,-308,-167,255,9,-36,-35,9,9,-73,-76,-72,-74,9,-78,-199,-198,-77,-200,-75,-139,-137,-134,-154,368,-71,-31,-34,424,9,9,-218,-217,9,-215,-201,-214,-78,-80,-202,-138,-136,-156,-155,9,-33,-32,470,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'SIZEOF':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,159,-28,-309,159,-308,-167,-309,159,159,-270,159,-268,159,-267,159,-266,159,159,-265,-269,159,159,159,-73,-76,-72,159,-74,159,159,-78,-199,-198,-77,-200,159,-75,-266,159,159,159,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,159,-233,-234,-226,-232,159,159,159,159,159,159,159,159,159,159,159,159,159,159,159,159,159,159,159,159,159,159,159,159,-309,-266,159,-218,-217,159,-215,159,159,159,-201,159,-214,159,-80,-202,159,159,159,-266,159,159,-12,159,159,-11,159,159,-28,-309,-266,-213,-216,159,-205,159,-79,-203,-309,-182,159,159,-309,159,-266,159,159,159,159,-204,159,159,159,159,-11,159,-209,-208,-206,-80,159,-309,159,159,159,-210,-207,159,-212,-211,]),'UNSIGNED':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,78,80,83,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,286,287,288,291,293,296,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[20,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,20,-96,-111,-106,-65,-95,-112,20,-221,-109,-113,20,-63,-118,20,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,20,-53,20,-84,20,20,-61,-133,-307,-132,20,-153,-152,-166,-90,-92,20,-89,-91,-94,-83,-86,-88,-69,-30,20,20,-70,20,-85,20,20,20,-135,-130,-145,-146,-142,-308,20,20,-167,20,20,-36,-35,20,20,-73,-76,-72,-74,20,-78,-199,-198,-77,-200,-75,20,-139,20,-137,-134,-143,-131,-128,-129,-154,-71,20,-31,20,20,20,-34,20,20,20,-218,-217,20,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,20,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'UNION':([0,1,3,7,8,9,11,12,14,17,18,19,23,24,26,34,35,36,37,40,42,47,49,51,53,54,55,56,57,60,61,64,65,67,68,70,72,78,87,101,102,103,104,105,117,120,121,122,123,124,125,128,129,130,131,132,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,233,236,258,277,286,287,288,291,293,327,331,336,337,339,340,346,349,351,352,353,360,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[22,-309,-117,-99,-52,-97,-98,-64,-60,-66,22,-96,-65,-95,22,-63,-118,22,-29,-62,-67,-309,-309,-119,-68,-100,-87,-10,-9,22,-53,-84,22,22,-61,-307,22,-166,22,-83,-86,-88,-69,-30,22,-70,22,-85,22,22,22,-145,-146,-142,-308,22,-167,22,22,-36,-35,22,22,-73,-76,-72,-74,22,-78,-199,-198,-77,-200,-75,22,22,-143,-71,22,-31,22,22,22,-34,22,22,-218,-217,22,-215,-201,-214,-78,-80,-202,-144,22,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'COLON':([2,3,5,6,8,10,15,20,21,25,29,30,32,35,37,39,41,44,45,48,50,51,61,69,71,73,74,85,86,88,105,115,119,126,127,131,133,143,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,183,187,188,212,227,229,232,234,235,237,238,244,245,249,251,276,278,279,280,282,286,289,290,292,293,297,344,345,356,357,359,362,363,370,371,381,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,415,416,417,418,419,436,447,448,458,459,460,465,484,485,494,507,511,520,],[-104,-117,-115,-101,-52,-116,-102,-111,-106,-112,-221,-109,-113,-118,-29,-107,-103,-114,-108,-110,-105,-119,-53,-133,-132,-153,-152,-54,-163,-37,-30,-294,-162,-135,-130,-308,239,-55,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,-236,-300,-296,-222,-36,-35,342,-219,354,-139,-137,-134,-131,-128,-129,361,-154,-38,-306,-263,-304,-280,-279,-31,-257,-262,-260,-34,-261,439,-235,-138,-136,239,-156,-155,-44,-43,-223,-278,-277,-276,-275,-274,-287,-244,-256,-245,-243,-247,-251,-246,-242,-249,-254,-240,-239,-248,-255,-250,-252,467,-253,-241,-33,-32,-220,-39,-42,-264,-272,-273,-258,-41,-40,-237,-288,-281,-282,]),'$end':([0,12,14,17,23,26,34,40,42,43,52,53,68,101,104,120,131,258,353,],[-309,-64,-60,-66,-65,-58,-63,-62,-67,0,-59,-68,-61,-83,-69,-70,-308,-71,-202,]),'WSTRING_LITERAL':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,153,155,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,276,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,155,-28,-309,155,-308,-167,-309,155,155,-270,276,-305,155,-268,155,-267,155,-266,155,155,-265,-269,155,155,155,-73,-76,-72,155,-74,155,155,-78,-199,-198,-77,-200,155,-75,-266,155,155,155,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,155,-233,-234,-226,-232,-306,155,155,155,155,155,155,155,155,155,155,155,155,155,155,155,155,155,155,155,155,155,155,155,155,-309,-266,155,-218,-217,155,-215,155,155,155,-201,155,-214,155,-80,-202,155,155,155,-266,155,155,-12,155,155,-11,155,155,-28,-309,-266,-213,-216,155,-205,155,-79,-203,-309,-182,155,155,-309,155,-266,155,155,155,155,-204,155,155,155,155,-11,155,-209,-208,-206,-80,155,-309,155,155,155,-210,-207,155,-212,-211,]),'DIVIDE':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,308,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,308,308,308,308,308,308,308,308,308,308,-240,-239,308,308,308,308,308,-241,-264,-272,-273,-258,-288,-281,-282,]),'FOR':([53,70,101,104,121,131,202,203,206,208,215,217,218,219,220,222,224,225,336,337,340,342,346,349,351,352,353,354,432,433,437,439,442,443,479,480,481,483,501,502,504,505,517,522,523,524,526,527,528,],[-68,-307,-83,-69,209,-308,-73,-76,-72,-74,209,-78,-199,-198,-77,-200,209,-75,-218,-217,-215,209,-201,-214,209,-80,-202,209,-213,-216,-205,209,-79,-203,209,-204,209,209,-209,-208,-206,-80,209,209,-210,-207,209,-212,-211,]),'PLUSPLUS':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,115,121,131,139,144,147,148,150,151,153,154,155,156,157,158,159,160,161,162,166,167,169,170,171,172,173,174,175,176,177,178,180,181,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,229,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,276,277,279,280,282,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,383,384,385,386,389,394,395,422,423,424,430,432,433,435,437,439,442,443,454,457,459,460,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,507,509,510,511,514,517,520,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,169,-28,-309,-294,169,-308,-167,-309,169,169,-298,-270,-286,-301,-305,-302,-299,-284,169,-268,-285,282,169,-267,169,-297,-266,-271,169,169,-303,-265,-295,-283,-300,-296,-269,169,169,169,-73,-76,-72,169,-74,169,169,-78,-199,-198,-77,-200,169,-75,-266,-294,169,169,169,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,169,-233,-234,-226,-232,-306,169,-304,-280,-279,169,169,169,169,169,169,169,169,169,169,169,169,169,169,169,169,169,169,169,169,169,169,169,-309,-266,169,-218,-217,169,-215,169,169,169,-201,169,-214,169,-80,-202,169,169,169,-266,169,169,-12,169,169,-11,-278,-277,-276,-275,-274,-287,169,169,-28,-309,-266,-213,-216,169,-205,169,-79,-203,-309,-182,-272,-273,169,169,-309,169,-266,169,169,169,169,-204,169,169,169,169,-11,169,-209,-208,-206,-80,-288,169,-309,-281,169,169,-282,169,-210,-207,169,-212,-211,]),'EQUALS':([8,37,61,85,86,87,88,89,97,105,115,119,131,138,143,150,152,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,187,188,229,251,276,278,279,280,282,286,289,290,292,293,297,370,371,374,379,383,384,385,386,389,394,418,419,447,448,452,456,458,459,460,465,484,485,486,507,511,520,],[-52,-29,-53,-54,-163,-162,-37,147,148,-30,-294,-162,-308,250,-55,-298,267,-286,-301,-305,-302,-299,-284,-285,-259,-297,-271,-303,-295,-283,-300,-296,-36,-35,-294,-38,-306,-263,-304,-280,-279,-31,-257,-262,-260,-34,-261,-44,-43,-183,457,-278,-277,-276,-275,-274,-287,-33,-32,-39,-42,-186,-184,-264,-272,-273,-258,-41,-40,-185,-288,-281,-282,]),'ELSE':([53,104,131,202,203,206,208,217,220,225,336,337,340,349,351,352,353,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[-68,-69,-308,-73,-76,-72,-74,-78,-77,-75,-218,-217,-215,-214,-78,-80,-202,-213,-216,-205,-79,-203,-204,-209,-208,-206,517,-210,-207,-212,-211,]),'ANDEQUAL':([115,131,150,152,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,458,459,460,465,507,511,520,],[-294,-308,-298,272,-286,-301,-305,-302,-299,-284,-285,-259,-297,-271,-303,-295,-283,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-264,-272,-273,-258,-288,-281,-282,]),'EQ':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,312,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,312,-245,-243,-247,-251,-246,-242,-249,312,-240,-239,-248,312,-250,312,312,-241,-264,-272,-273,-258,-288,-281,-282,]),'AND':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,115,121,131,139,144,147,148,150,151,152,153,154,155,156,157,158,159,160,161,162,164,166,167,169,170,171,172,173,174,175,176,177,178,179,180,181,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,229,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,276,277,278,279,280,282,284,285,288,289,290,291,292,297,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,383,384,385,386,389,394,395,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,422,423,424,430,432,433,435,437,439,442,443,454,457,458,459,460,461,463,465,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,507,509,510,511,514,517,520,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,176,-28,-309,-294,176,-308,-167,-309,176,176,-298,-270,-257,-286,-301,-305,-302,-299,-284,176,-268,-285,-259,-238,176,-267,176,-297,-266,-271,176,176,-303,-265,-295,-283,313,-300,-296,-269,176,176,176,-73,-76,-72,176,-74,176,176,-78,-199,-198,-77,-200,176,-75,-266,-294,176,176,176,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,176,-233,-234,-226,-232,-306,176,-263,-304,-280,-279,176,176,176,-257,-262,176,-260,-261,176,176,176,176,176,176,176,176,176,176,176,176,176,176,176,176,176,176,176,-309,-266,176,-218,-217,176,-215,176,176,176,-201,176,-214,176,-80,-202,176,176,176,-266,176,176,-12,176,176,-11,-278,-277,-276,-275,-274,-287,176,-244,313,-245,-243,-247,-251,-246,-242,-249,313,-240,-239,-248,313,-250,-252,313,-241,176,-28,-309,-266,-213,-216,176,-205,176,-79,-203,-309,-182,-264,-272,-273,176,176,-258,-309,176,-266,176,176,176,176,-204,176,176,176,176,-11,176,-209,-208,-206,-80,-288,176,-309,-281,176,176,-282,176,-210,-207,176,-212,-211,]),'TYPEID':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,76,77,78,79,80,81,83,84,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,140,142,145,149,173,187,188,189,192,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,281,283,286,287,288,291,293,327,331,336,337,339,340,346,349,351,352,353,356,357,359,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[29,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,29,-96,-111,-106,-141,-65,-95,-112,29,69,73,-221,-109,-309,-113,88,-63,-118,29,-29,-140,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,29,-53,88,-84,29,29,-61,-133,-307,-132,29,-153,-152,-28,-164,-166,-27,-90,88,-92,88,29,-89,-91,-94,-83,-86,-88,-69,-30,196,29,-70,29,-85,29,29,29,-135,-130,-145,-146,-142,-308,29,88,-167,-165,88,29,88,29,-36,-35,29,196,29,-73,-76,-72,-74,29,-78,-199,-198,-77,-200,-75,29,-139,29,-137,-134,-143,-131,-128,-129,-154,-71,29,383,385,-31,29,29,29,-34,29,29,-218,-217,29,-215,-201,-214,-78,-80,-202,-138,-136,88,-144,-156,-155,29,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'LBRACE':([8,18,22,27,28,37,38,53,61,62,64,66,67,69,70,71,73,74,87,101,104,105,121,122,131,146,147,148,187,188,202,203,206,208,215,217,218,219,220,222,224,225,260,286,293,336,337,340,342,346,349,351,352,353,354,372,378,380,395,418,419,432,433,437,439,442,443,454,457,458,463,464,466,479,480,481,483,487,488,501,502,504,505,510,517,522,523,524,526,527,528,],[-52,-309,-141,70,70,-29,-140,-68,-53,-7,-84,70,-8,70,-307,70,70,70,-309,-83,-69,-30,70,-85,-308,70,70,70,-36,-35,-73,-76,-72,-74,70,-78,-199,-198,-77,-200,70,-75,-309,-31,-34,-218,-217,-215,70,-201,-214,70,-80,-202,70,-12,70,-11,70,-33,-32,-213,-216,-205,70,-79,-203,-309,-182,70,70,70,-309,70,-204,70,70,70,-11,-209,-208,-206,-80,-309,70,70,-210,-207,70,-212,-211,]),'PPHASH':([0,12,14,17,23,26,34,40,42,53,68,101,104,120,131,258,353,],[42,-64,-60,-66,-65,42,-63,-62,-67,-68,-61,-83,-69,-70,-308,-71,-202,]),'INT':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,78,80,83,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,286,287,288,291,293,296,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[50,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,50,-96,-111,-106,-65,-95,-112,50,-221,-109,-113,50,-63,-118,50,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,50,-53,50,-84,50,50,-61,-133,-307,-132,50,-153,-152,-166,-90,-92,50,-89,-91,-94,-83,-86,-88,-69,-30,50,50,-70,50,-85,50,50,50,-135,-130,-145,-146,-142,-308,50,50,-167,50,50,-36,-35,50,50,-73,-76,-72,-74,50,-78,-199,-198,-77,-200,-75,50,-139,50,-137,-134,-143,-131,-128,-129,-154,-71,50,-31,50,50,50,-34,50,50,50,-218,-217,50,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,50,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'SIGNED':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,78,80,83,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,286,287,288,291,293,296,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[48,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,48,-96,-111,-106,-65,-95,-112,48,-221,-109,-113,48,-63,-118,48,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,48,-53,48,-84,48,48,-61,-133,-307,-132,48,-153,-152,-166,-90,-92,48,-89,-91,-94,-83,-86,-88,-69,-30,48,48,-70,48,-85,48,48,48,-135,-130,-145,-146,-142,-308,48,48,-167,48,48,-36,-35,48,48,-73,-76,-72,-74,48,-78,-199,-198,-77,-200,-75,48,-139,48,-137,-134,-143,-131,-128,-129,-154,-71,48,-31,48,48,48,-34,48,48,48,-218,-217,48,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,48,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'CONTINUE':([53,70,101,104,121,131,202,203,206,208,215,217,218,219,220,222,224,225,336,337,340,342,346,349,351,352,353,354,432,433,437,439,442,443,479,480,481,483,501,502,504,505,517,522,523,524,526,527,528,],[-68,-307,-83,-69,210,-308,-73,-76,-72,-74,210,-78,-199,-198,-77,-200,210,-75,-218,-217,-215,210,-201,-214,210,-80,-202,210,-213,-216,-205,210,-79,-203,210,-204,210,210,-209,-208,-206,-80,210,210,-210,-207,210,-212,-211,]),'NOT':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,184,-28,-309,184,-308,-167,-309,184,184,-270,184,-268,184,-267,184,-266,184,184,-265,-269,184,184,184,-73,-76,-72,184,-74,184,184,-78,-199,-198,-77,-200,184,-75,-266,184,184,184,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,184,-233,-234,-226,-232,184,184,184,184,184,184,184,184,184,184,184,184,184,184,184,184,184,184,184,184,184,184,184,184,-309,-266,184,-218,-217,184,-215,184,184,184,-201,184,-214,184,-80,-202,184,184,184,-266,184,184,-12,184,184,-11,184,184,-28,-309,-266,-213,-216,184,-205,184,-79,-203,-309,-182,184,184,-309,184,-266,184,184,184,184,-204,184,184,184,184,-11,184,-209,-208,-206,-80,184,-309,184,184,184,-210,-207,184,-212,-211,]),'OREQUAL':([115,131,150,152,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,458,459,460,465,507,511,520,],[-294,-308,-298,273,-286,-301,-305,-302,-299,-284,-285,-259,-297,-271,-303,-295,-283,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-264,-272,-273,-258,-288,-281,-282,]),'MOD':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,316,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,316,316,316,316,316,316,316,316,316,316,-240,-239,316,316,316,316,316,-241,-264,-272,-273,-258,-288,-281,-282,]),'RSHIFT':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,298,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,298,-245,-243,298,298,298,-242,298,298,-240,-239,298,298,298,298,298,-241,-264,-272,-273,-258,-288,-281,-282,]),'DEFAULT':([53,70,101,104,121,131,202,203,206,208,215,217,218,219,220,222,224,225,336,337,340,342,346,349,351,352,353,354,432,433,437,439,442,443,479,480,481,483,501,502,504,505,517,522,523,524,526,527,528,],[-68,-307,-83,-69,212,-308,-73,-76,-72,-74,212,-78,-199,-198,-77,-200,212,-75,-218,-217,-215,212,-201,-214,212,-80,-202,212,-213,-216,-205,212,-79,-203,212,-204,212,212,-209,-208,-206,-80,212,212,-210,-207,212,-212,-211,]),'__INT128':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,78,80,83,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,286,287,288,291,293,296,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[25,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,25,-96,-111,-106,-65,-95,-112,25,-221,-109,-113,25,-63,-118,25,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,25,-53,25,-84,25,25,-61,-133,-307,-132,25,-153,-152,-166,-90,-92,25,-89,-91,-94,-83,-86,-88,-69,-30,25,25,-70,25,-85,25,25,25,-135,-130,-145,-146,-142,-308,25,25,-167,25,25,-36,-35,25,25,-73,-76,-72,-74,25,-78,-199,-198,-77,-200,-75,25,-139,25,-137,-134,-143,-131,-128,-129,-154,-71,25,-31,25,25,25,-34,25,25,25,-218,-217,25,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,25,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'WHILE':([53,70,101,104,121,131,202,203,206,208,215,217,218,219,220,222,224,225,336,337,340,342,346,349,350,351,352,353,354,432,433,437,439,442,443,479,480,481,483,501,502,504,505,517,522,523,524,526,527,528,],[-68,-307,-83,-69,213,-308,-73,-76,-72,-74,213,-78,-199,-198,-77,-200,213,-75,-218,-217,-215,213,-201,-214,441,213,-80,-202,213,-213,-216,-205,213,-79,-203,213,-204,213,213,-209,-208,-206,-80,213,213,-210,-207,213,-212,-211,]),'DIVEQUAL':([115,131,150,152,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,458,459,460,465,507,511,520,],[-294,-308,-298,264,-286,-301,-305,-302,-299,-284,-285,-259,-297,-271,-303,-295,-283,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-264,-272,-273,-258,-288,-281,-282,]),'EXTERN':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,37,39,40,41,42,44,45,47,48,49,50,51,53,54,60,61,63,64,67,68,69,70,71,73,74,80,83,87,91,92,96,101,104,105,113,120,121,122,126,131,145,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,232,234,235,249,258,286,293,327,331,336,337,339,340,346,349,351,352,353,356,357,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[11,11,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,11,-96,-111,-106,-65,-95,-112,11,-221,-109,-113,11,-63,-118,-29,-107,-62,-103,-67,-114,-108,11,-110,11,-105,-119,-68,-100,11,-53,11,-84,11,-61,-133,-307,-132,-153,-152,-90,-92,11,-89,-91,-94,-83,-69,-30,11,-70,11,-85,-135,-308,11,-36,-35,11,11,-73,-76,-72,-74,11,-78,-199,-198,-77,-200,-75,-139,-137,-134,-154,-71,-31,-34,11,11,-218,-217,11,-215,-201,-214,-78,-80,-202,-138,-136,-156,-155,11,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'CASE':([53,70,101,104,121,131,202,203,206,208,215,217,218,219,220,222,224,225,336,337,340,342,346,349,351,352,353,354,432,433,437,439,442,443,479,480,481,483,501,502,504,505,517,522,523,524,526,527,528,],[-68,-307,-83,-69,214,-308,-73,-76,-72,-74,214,-78,-199,-198,-77,-200,214,-75,-218,-217,-215,214,-201,-214,214,-80,-202,214,-213,-216,-205,214,-79,-203,214,-204,214,214,-209,-208,-206,-80,214,214,-210,-207,214,-212,-211,]),'LAND':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,311,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,311,-245,-243,-247,-251,-246,-242,-249,-254,-240,-239,-248,-255,-250,-252,-253,-241,-264,-272,-273,-258,-288,-281,-282,]),'REGISTER':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,37,39,40,41,42,44,45,47,48,49,50,51,53,54,60,61,63,64,67,68,69,70,71,73,74,80,83,87,91,92,96,101,104,105,113,120,121,122,126,131,145,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,232,234,235,249,258,286,293,327,331,336,337,339,340,346,349,351,352,353,356,357,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[19,19,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,19,-96,-111,-106,-65,-95,-112,19,-221,-109,-113,19,-63,-118,-29,-107,-62,-103,-67,-114,-108,19,-110,19,-105,-119,-68,-100,19,-53,19,-84,19,-61,-133,-307,-132,-153,-152,-90,-92,19,-89,-91,-94,-83,-69,-30,19,-70,19,-85,-135,-308,19,-36,-35,19,19,-73,-76,-72,-74,19,-78,-199,-198,-77,-200,-75,-139,-137,-134,-154,-71,-31,-34,19,19,-218,-217,19,-215,-201,-214,-78,-80,-202,-138,-136,-156,-155,19,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'MODEQUAL':([115,131,150,152,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,458,459,460,465,507,511,520,],[-294,-308,-298,266,-286,-301,-305,-302,-299,-284,-285,-259,-297,-271,-303,-295,-283,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-264,-272,-273,-258,-288,-281,-282,]),'NE':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,303,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,303,-245,-243,-247,-251,-246,-242,-249,303,-240,-239,-248,303,-250,303,303,-241,-264,-272,-273,-258,-288,-281,-282,]),'SWITCH':([53,70,101,104,121,131,202,203,206,208,215,217,218,219,220,222,224,225,336,337,340,342,346,349,351,352,353,354,432,433,437,439,442,443,479,480,481,483,501,502,504,505,517,522,523,524,526,527,528,],[-68,-307,-83,-69,216,-308,-73,-76,-72,-74,216,-78,-199,-198,-77,-200,216,-75,-218,-217,-215,216,-201,-214,216,-80,-202,216,-213,-216,-205,216,-79,-203,216,-204,216,216,-209,-208,-206,-80,216,216,-210,-207,216,-212,-211,]),'INT_CONST_HEX':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,170,-28,-309,170,-308,-167,-309,170,170,-270,170,-268,170,-267,170,-266,170,170,-265,-269,170,170,170,-73,-76,-72,170,-74,170,170,-78,-199,-198,-77,-200,170,-75,-266,170,170,170,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,170,-233,-234,-226,-232,170,170,170,170,170,170,170,170,170,170,170,170,170,170,170,170,170,170,170,170,170,170,170,170,-309,-266,170,-218,-217,170,-215,170,170,170,-201,170,-214,170,-80,-202,170,170,170,-266,170,170,-12,170,170,-11,170,170,-28,-309,-266,-213,-216,170,-205,170,-79,-203,-309,-182,170,170,-309,170,-266,170,170,170,170,-204,170,170,170,170,-11,170,-209,-208,-206,-80,170,-309,170,170,170,-210,-207,170,-212,-211,]),'_COMPLEX':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,78,80,83,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,286,287,288,291,293,296,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[30,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,30,-96,-111,-106,-65,-95,-112,30,-221,-109,-113,30,-63,-118,30,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,30,-53,30,-84,30,30,-61,-133,-307,-132,30,-153,-152,-166,-90,-92,30,-89,-91,-94,-83,-86,-88,-69,-30,30,30,-70,30,-85,30,30,30,-135,-130,-145,-146,-142,-308,30,30,-167,30,30,-36,-35,30,30,-73,-76,-72,-74,30,-78,-199,-198,-77,-200,-75,30,-139,30,-137,-134,-143,-131,-128,-129,-154,-71,30,-31,30,30,30,-34,30,30,30,-218,-217,30,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,30,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'PPPRAGMASTR':([53,],[104,]),'PLUSEQUAL':([115,131,150,152,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,458,459,460,465,507,511,520,],[-294,-308,-298,269,-286,-301,-305,-302,-299,-284,-285,-259,-297,-271,-303,-295,-283,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-264,-272,-273,-258,-288,-281,-282,]),'STRUCT':([0,1,3,7,8,9,11,12,14,17,18,19,23,24,26,34,35,36,37,40,42,47,49,51,53,54,55,56,57,60,61,64,65,67,68,70,72,78,87,101,102,103,104,105,117,120,121,122,123,124,125,128,129,130,131,132,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,233,236,258,277,286,287,288,291,293,327,331,336,337,339,340,346,349,351,352,353,360,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[38,-309,-117,-99,-52,-97,-98,-64,-60,-66,38,-96,-65,-95,38,-63,-118,38,-29,-62,-67,-309,-309,-119,-68,-100,-87,-10,-9,38,-53,-84,38,38,-61,-307,38,-166,38,-83,-86,-88,-69,-30,38,-70,38,-85,38,38,38,-145,-146,-142,-308,38,-167,38,38,-36,-35,38,38,-73,-76,-72,-74,38,-78,-199,-198,-77,-200,-75,38,38,-143,-71,38,-31,38,38,38,-34,38,38,-218,-217,38,-215,-201,-214,-78,-80,-202,-144,38,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'CONDOP':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,314,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,-256,-245,-243,-247,-251,-246,-242,-249,-254,-240,-239,-248,-255,-250,-252,-253,-241,-264,-272,-273,-258,-288,-281,-282,]),'BREAK':([53,70,101,104,121,131,202,203,206,208,215,217,218,219,220,222,224,225,336,337,340,342,346,349,351,352,353,354,432,433,437,439,442,443,479,480,481,483,501,502,504,505,517,522,523,524,526,527,528,],[-68,-307,-83,-69,221,-308,-73,-76,-72,-74,221,-78,-199,-198,-77,-200,221,-75,-218,-217,-215,221,-201,-214,221,-80,-202,221,-213,-216,-205,221,-79,-203,221,-204,221,221,-209,-208,-206,-80,221,221,-210,-207,221,-212,-211,]),'VOLATILE':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,31,32,33,34,35,37,39,40,41,42,44,45,47,48,49,50,51,53,54,59,60,61,63,64,67,68,69,70,71,72,73,74,76,78,80,83,87,91,92,96,101,104,105,107,108,113,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,144,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,254,255,258,277,286,287,288,291,293,296,326,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,423,424,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[51,51,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,51,-96,-111,-106,-65,-95,-112,51,-221,-109,51,-113,51,-63,-118,-29,-107,-62,-103,-67,-114,-108,51,-110,51,-105,-119,-68,-100,51,51,-53,51,-84,51,-61,-133,-307,-132,51,-153,-152,51,-166,-90,-92,51,-89,-91,-94,-83,-69,-30,51,51,51,-70,51,-85,51,51,51,-135,-130,-145,-146,-142,-308,51,51,-167,51,51,51,-36,-35,51,51,-73,-76,-72,-74,51,-78,-199,-198,-77,-200,-75,51,-139,51,-137,-134,-143,-131,-128,-129,-154,51,51,-71,51,-31,51,51,51,-34,51,51,51,51,-218,-217,51,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,51,-33,-32,51,51,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'PPPRAGMA':([0,12,14,17,23,26,34,40,42,53,68,70,72,101,104,120,121,123,124,125,128,129,130,131,202,203,206,208,215,217,218,219,220,222,224,225,231,233,236,258,336,337,340,342,346,349,351,352,353,354,360,432,433,437,439,442,443,479,480,481,483,501,502,504,505,517,522,523,524,526,527,528,],[53,-64,-60,-66,-65,53,-63,-62,-67,-68,-61,-307,53,-83,-69,-70,53,53,53,53,-145,-146,-142,-308,-73,-76,-72,-74,53,-78,-199,-198,-77,-200,53,-75,53,53,-143,-71,-218,-217,-215,53,-201,-214,53,-80,-202,53,-144,-213,-216,-205,53,-79,-203,53,-204,53,53,-209,-208,-206,-80,53,53,-210,-207,53,-212,-211,]),'INLINE':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,37,39,40,41,42,44,45,47,48,49,50,51,53,54,60,61,63,64,67,68,69,70,71,73,74,80,83,87,91,92,96,101,104,105,113,120,121,122,126,131,145,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,232,234,235,249,258,286,293,327,331,336,337,339,340,346,349,351,352,353,356,357,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[54,54,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,54,-96,-111,-106,-65,-95,-112,54,-221,-109,-113,54,-63,-118,-29,-107,-62,-103,-67,-114,-108,54,-110,54,-105,-119,-68,-100,54,-53,54,-84,54,-61,-133,-307,-132,-153,-152,-90,-92,54,-89,-91,-94,-83,-69,-30,54,-70,54,-85,-135,-308,54,-36,-35,54,54,-73,-76,-72,-74,54,-78,-199,-198,-77,-200,-75,-139,-137,-134,-154,-71,-31,-34,54,54,-218,-217,54,-215,-201,-214,-78,-80,-202,-138,-136,-156,-155,54,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'INT_CONST_BIN':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,150,-28,-309,150,-308,-167,-309,150,150,-270,150,-268,150,-267,150,-266,150,150,-265,-269,150,150,150,-73,-76,-72,150,-74,150,150,-78,-199,-198,-77,-200,150,-75,-266,150,150,150,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,150,-233,-234,-226,-232,150,150,150,150,150,150,150,150,150,150,150,150,150,150,150,150,150,150,150,150,150,150,150,150,-309,-266,150,-218,-217,150,-215,150,150,150,-201,150,-214,150,-80,-202,150,150,150,-266,150,150,-12,150,150,-11,150,150,-28,-309,-266,-213,-216,150,-205,150,-79,-203,-309,-182,150,150,-309,150,-266,150,150,150,150,-204,150,150,150,150,-11,150,-209,-208,-206,-80,150,-309,150,150,150,-210,-207,150,-212,-211,]),'DO':([53,70,101,104,121,131,202,203,206,208,215,217,218,219,220,222,224,225,336,337,340,342,346,349,351,352,353,354,432,433,437,439,442,443,479,480,481,483,501,502,504,505,517,522,523,524,526,527,528,],[-68,-307,-83,-69,224,-308,-73,-76,-72,-74,224,-78,-199,-198,-77,-200,224,-75,-218,-217,-215,224,-201,-214,224,-80,-202,224,-213,-216,-205,224,-79,-203,224,-204,224,224,-209,-208,-206,-80,224,224,-210,-207,224,-212,-211,]),'LNOT':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,151,-28,-309,151,-308,-167,-309,151,151,-270,151,-268,151,-267,151,-266,151,151,-265,-269,151,151,151,-73,-76,-72,151,-74,151,151,-78,-199,-198,-77,-200,151,-75,-266,151,151,151,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,151,-233,-234,-226,-232,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,151,-309,-266,151,-218,-217,151,-215,151,151,151,-201,151,-214,151,-80,-202,151,151,151,-266,151,151,-12,151,151,-11,151,151,-28,-309,-266,-213,-216,151,-205,151,-79,-203,-309,-182,151,151,-309,151,-266,151,151,151,151,-204,151,151,151,151,-11,151,-209,-208,-206,-80,151,-309,151,151,151,-210,-207,151,-212,-211,]),'CONST':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,31,32,33,34,35,37,39,40,41,42,44,45,47,48,49,50,51,53,54,59,60,61,63,64,67,68,69,70,71,72,73,74,76,78,80,83,87,91,92,96,101,104,105,107,108,113,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,144,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,254,255,258,277,286,287,288,291,293,296,326,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,423,424,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[3,3,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,3,-96,-111,-106,-65,-95,-112,3,-221,-109,3,-113,3,-63,-118,-29,-107,-62,-103,-67,-114,-108,3,-110,3,-105,-119,-68,-100,3,3,-53,3,-84,3,-61,-133,-307,-132,3,-153,-152,3,-166,-90,-92,3,-89,-91,-94,-83,-69,-30,3,3,3,-70,3,-85,3,3,3,-135,-130,-145,-146,-142,-308,3,3,-167,3,3,3,-36,-35,3,3,-73,-76,-72,-74,3,-78,-199,-198,-77,-200,-75,3,-139,3,-137,-134,-143,-131,-128,-129,-154,3,3,-71,3,-31,3,3,3,-34,3,3,3,3,-218,-217,3,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,3,-33,-32,3,3,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'LOR':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,299,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,-256,-245,-243,-247,-251,-246,-242,-249,-254,-240,-239,-248,-255,-250,-252,-253,-241,-264,-272,-273,-258,-288,-281,-282,]),'CHAR_CONST':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,154,-28,-309,154,-308,-167,-309,154,154,-270,154,-268,154,-267,154,-266,154,154,-265,-269,154,154,154,-73,-76,-72,154,-74,154,154,-78,-199,-198,-77,-200,154,-75,-266,154,154,154,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,154,-233,-234,-226,-232,154,154,154,154,154,154,154,154,154,154,154,154,154,154,154,154,154,154,154,154,154,154,154,154,-309,-266,154,-218,-217,154,-215,154,154,154,-201,154,-214,154,-80,-202,154,154,154,-266,154,154,-12,154,154,-11,154,154,-28,-309,-266,-213,-216,154,-205,154,-79,-203,-309,-182,154,154,-309,154,-266,154,154,154,154,-204,154,154,154,154,-11,154,-209,-208,-206,-80,154,-309,154,154,154,-210,-207,154,-212,-211,]),'LSHIFT':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,300,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,300,-245,-243,300,300,300,-242,300,300,-240,-239,300,300,300,300,300,-241,-264,-272,-273,-258,-288,-281,-282,]),'RBRACE':([53,70,72,101,104,115,121,123,124,125,128,129,130,131,136,137,138,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,183,202,203,206,208,215,217,218,219,220,222,223,225,226,231,233,236,246,247,248,260,261,276,278,279,280,282,289,290,292,297,336,337,340,345,346,349,351,352,353,360,364,365,373,377,380,381,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,432,433,437,442,443,451,454,455,458,459,460,465,480,489,493,494,501,502,504,505,506,507,510,511,520,523,524,527,528,],[-68,-307,131,-83,-69,-294,-309,131,131,131,-145,-146,-142,-308,-157,131,-160,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,-236,-300,-296,-222,-73,-76,-72,-74,-6,-78,-199,-198,-77,-200,-5,-75,131,131,131,-143,131,131,-158,-309,-177,-306,-263,-304,-280,-279,-257,-262,-260,-261,-218,-217,-215,-235,-201,-214,-78,-80,-202,-144,-159,-161,131,-22,-21,-223,-278,-277,-276,-275,-274,-287,-244,-256,-245,-243,-247,-251,-246,-242,-249,-254,-240,-239,-248,-255,-250,-252,-253,-241,-213,-216,-205,-79,-203,-178,131,-180,-264,-272,-273,-258,-204,-179,131,-237,-209,-208,-206,-80,-181,-288,131,-281,-282,-210,-207,-212,-211,]),'_BOOL':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,78,80,83,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,286,287,288,291,293,296,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[15,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,15,-96,-111,-106,-65,-95,-112,15,-221,-109,-113,15,-63,-118,15,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,15,-53,15,-84,15,15,-61,-133,-307,-132,15,-153,-152,-166,-90,-92,15,-89,-91,-94,-83,-86,-88,-69,-30,15,15,-70,15,-85,15,15,15,-135,-130,-145,-146,-142,-308,15,15,-167,15,15,-36,-35,15,15,-73,-76,-72,-74,15,-78,-199,-198,-77,-200,-75,15,-139,15,-137,-134,-143,-131,-128,-129,-154,-71,15,-31,15,15,15,-34,15,15,15,-218,-217,15,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,15,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'LE':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,302,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,302,-245,-243,-247,302,-246,-242,-249,302,-240,-239,-248,302,302,302,302,-241,-264,-272,-273,-258,-288,-281,-282,]),'SEMI':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,46,47,48,49,50,51,53,54,55,56,57,61,63,65,68,69,70,71,72,73,74,80,82,83,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,115,119,120,121,123,124,125,126,127,128,129,130,131,133,143,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,183,187,188,202,203,205,206,207,208,210,211,215,217,218,219,220,221,222,223,224,225,227,229,231,232,233,234,235,236,237,238,240,241,242,243,244,245,249,251,252,258,259,261,262,263,276,278,279,280,282,286,289,290,292,293,297,335,336,337,338,339,340,342,345,346,347,349,351,352,353,354,356,357,358,360,362,363,370,371,381,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,418,419,432,433,434,435,436,437,439,442,443,445,446,447,448,451,458,459,460,465,477,478,479,480,481,483,484,485,489,494,499,501,502,504,505,507,511,516,517,520,522,523,524,526,527,528,],[17,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,-96,-111,-106,-65,-95,-112,17,-221,-109,-113,-309,-63,-118,-309,-29,-107,-62,-103,-67,-114,-108,101,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,-53,-309,-309,-61,-133,-307,-132,128,-153,-152,-90,-20,-92,-54,-163,-162,-37,-122,-81,-89,-91,-19,-120,-124,-94,-126,-16,-82,-15,-83,-86,-88,-69,-30,-294,-162,-70,-309,128,128,128,-135,-130,-145,-146,-142,-308,-309,-55,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,-236,-300,-296,-222,-36,-35,-73,-76,336,-72,337,-74,340,-14,-309,-78,-199,-198,-77,349,-200,-13,-309,-75,-219,-294,128,-139,128,-137,-134,-143,-131,-128,-26,-25,360,-147,-129,-149,-154,-38,-121,-71,-123,-177,-127,-125,-306,-263,-304,-280,-279,-31,-257,-262,-260,-34,-261,432,-218,-217,433,-309,-215,-309,-235,-201,-13,-214,-78,-80,-202,-309,-138,-136,-151,-144,-156,-155,-44,-43,-223,-278,-277,-276,-275,-274,-287,-244,-256,-245,-243,-247,-251,-246,-242,-249,-254,-240,-239,-248,-255,-250,-252,-253,-241,-33,-32,-213,-216,477,-309,-220,-205,-309,-79,-203,-148,-150,-39,-42,-178,-264,-272,-273,-258,-309,500,-309,-204,-309,-309,-41,-40,-179,-237,514,-209,-208,-206,-80,-288,-281,523,-309,-282,-309,-210,-207,-309,-212,-211,]),'LT':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,304,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,304,-245,-243,-247,304,-246,-242,-249,304,-240,-239,-248,304,304,304,304,-241,-264,-272,-273,-258,-288,-281,-282,]),'COMMA':([2,3,5,6,7,8,9,10,11,15,16,19,20,21,24,25,29,30,31,32,35,37,39,41,44,45,48,50,51,54,61,69,71,73,74,76,77,78,79,80,82,83,85,86,87,88,89,91,92,94,95,96,97,98,105,112,113,114,115,116,118,119,126,127,131,136,137,138,139,140,143,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,183,187,188,190,191,192,193,194,195,196,197,199,211,227,229,232,234,235,237,238,240,243,244,245,246,247,248,249,251,252,259,261,262,263,276,278,279,280,282,286,289,290,292,293,294,296,297,324,325,332,334,338,345,356,357,358,362,363,364,365,370,371,377,381,383,384,385,386,387,388,389,390,391,394,396,397,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,415,416,417,418,419,420,421,427,428,436,438,440,444,445,446,447,448,451,455,458,459,460,465,472,473,474,475,476,484,485,489,490,493,494,495,496,503,506,507,511,512,513,519,520,],[-104,-117,-115,-101,-99,-52,-97,-116,-98,-102,-93,-96,-111,-106,-95,-112,-221,-109,-309,-113,-118,-29,-107,-103,-114,-108,-110,-105,-119,-100,-53,-133,-132,-153,-152,-28,-164,-166,-27,-90,142,-92,-54,-163,-162,-37,-122,-89,-91,-120,-124,-94,-126,149,-30,-170,-309,200,-294,201,-175,-162,-135,-130,-308,-157,248,-160,-167,-165,-55,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,-236,-300,-296,-222,-36,-35,-174,-2,-188,-56,-172,-1,-45,-173,-190,341,-219,-294,-139,-137,-134,-131,-128,359,-147,-129,-149,248,248,-158,-154,-38,-121,-123,-177,-127,-125,-306,-263,-304,-280,-279,-31,-257,-262,-260,-34,341,-309,-261,-57,-189,-176,-171,341,-235,-138,-136,-151,-156,-155,-159,-161,-44,-43,454,-223,-278,-277,-276,-275,341,-292,-274,461,462,-287,-187,-188,-244,-256,-245,-243,-247,-251,-246,-242,-249,-254,-240,-239,-248,-255,-250,-252,341,-253,-241,-33,-32,-197,-191,-193,-195,-220,341,341,341,-148,-150,-39,-42,-178,-180,-264,-272,-273,-258,-51,-50,-192,-194,-196,-41,-40,-179,-293,510,-237,-46,-49,341,-181,-288,-281,-48,-47,341,-282,]),'OFFSETOF':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,166,167,169,171,173,174,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,165,-28,-309,165,-308,-167,-309,165,165,-270,165,-268,165,-267,165,-266,165,165,-265,-269,165,165,165,-73,-76,-72,165,-74,165,165,-78,-199,-198,-77,-200,165,-75,-266,165,165,165,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,165,-233,-234,-226,-232,165,165,165,165,165,165,165,165,165,165,165,165,165,165,165,165,165,165,165,165,165,165,165,165,-309,-266,165,-218,-217,165,-215,165,165,165,-201,165,-214,165,-80,-202,165,165,165,-266,165,165,-12,165,165,-11,165,165,-28,-309,-266,-213,-216,165,-205,165,-79,-203,-309,-182,165,165,-309,165,-266,165,165,165,165,-204,165,165,165,165,-11,165,-209,-208,-206,-80,165,-309,165,165,165,-210,-207,165,-212,-211,]),'TYPEDEF':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,37,39,40,41,42,44,45,47,48,49,50,51,53,54,60,61,63,64,67,68,69,70,71,73,74,80,83,87,91,92,96,101,104,105,113,120,121,122,126,131,145,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,232,234,235,249,258,286,293,327,331,336,337,339,340,346,349,351,352,353,356,357,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[7,7,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,7,-96,-111,-106,-65,-95,-112,7,-221,-109,-113,7,-63,-118,-29,-107,-62,-103,-67,-114,-108,7,-110,7,-105,-119,-68,-100,7,-53,7,-84,7,-61,-133,-307,-132,-153,-152,-90,-92,7,-89,-91,-94,-83,-69,-30,7,-70,7,-85,-135,-308,7,-36,-35,7,7,-73,-76,-72,-74,7,-78,-199,-198,-77,-200,-75,-139,-137,-134,-154,-71,-31,-34,7,7,-218,-217,7,-215,-201,-214,-78,-80,-202,-138,-136,-156,-155,7,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'XOR':([115,131,150,152,153,154,155,156,157,158,161,162,164,170,172,175,177,178,179,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,458,459,460,465,507,511,520,],[-294,-308,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,-238,-297,-271,-303,-295,-283,307,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-244,307,-245,-243,-247,-251,-246,-242,-249,-254,-240,-239,-248,307,-250,-252,307,-241,-264,-272,-273,-258,-288,-281,-282,]),'AUTO':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,37,39,40,41,42,44,45,47,48,49,50,51,53,54,60,61,63,64,67,68,69,70,71,73,74,80,83,87,91,92,96,101,104,105,113,120,121,122,126,131,145,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,232,234,235,249,258,286,293,327,331,336,337,339,340,346,349,351,352,353,356,357,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[24,24,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,24,-96,-111,-106,-65,-95,-112,24,-221,-109,-113,24,-63,-118,-29,-107,-62,-103,-67,-114,-108,24,-110,24,-105,-119,-68,-100,24,-53,24,-84,24,-61,-133,-307,-132,-153,-152,-90,-92,24,-89,-91,-94,-83,-69,-30,24,-70,24,-85,-135,-308,24,-36,-35,24,24,-73,-76,-72,-74,24,-78,-199,-198,-77,-200,-75,-139,-137,-134,-154,-71,-31,-34,24,24,-218,-217,24,-215,-201,-214,-78,-80,-202,-138,-136,-156,-155,24,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'TIMES':([0,1,2,3,4,5,6,7,9,10,11,12,14,15,16,17,19,20,21,23,24,25,26,29,30,31,32,33,34,35,36,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,59,63,65,68,69,70,71,73,74,76,77,78,79,80,81,83,91,92,96,101,102,103,104,106,107,108,113,115,120,121,126,127,131,133,139,142,144,147,148,149,150,151,152,153,154,155,156,157,158,159,160,161,162,164,166,167,169,170,171,172,173,174,175,176,177,178,179,180,181,184,185,186,189,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,229,232,234,235,237,238,239,244,249,250,253,254,255,258,260,264,265,266,267,268,269,270,271,272,273,274,275,276,277,278,279,280,282,284,285,288,289,290,291,292,296,297,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,356,357,359,361,362,363,367,368,369,372,376,378,380,383,384,385,386,389,394,395,398,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,422,423,424,430,432,433,435,437,439,442,443,454,457,458,459,460,461,463,465,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,507,509,510,511,514,517,520,522,523,524,526,527,528,],[31,-309,-104,-117,31,-115,-101,-99,-97,-116,-98,-64,-60,-102,-93,-66,-96,-111,-106,-65,-95,-112,31,-221,-109,-309,-113,31,-63,-118,31,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,-309,31,31,-61,-133,-307,-132,-153,-152,-28,31,-166,-27,-90,31,-92,-89,-91,-94,-83,-86,-88,-69,171,-28,-309,31,-294,-70,228,-135,-130,-308,31,-167,31,-309,228,228,31,-298,-270,-257,-286,-301,-305,-302,-299,-284,228,-268,-285,-259,-238,228,-267,228,-297,-266,-271,228,228,-303,-265,-295,-283,309,-300,-296,-269,228,228,31,329,-73,-76,-72,228,-74,228,228,-78,-199,-198,-77,-200,228,-75,-266,-294,-139,-137,-134,-131,-128,228,-129,-154,228,367,-28,-309,-71,-309,-227,-230,-228,-224,-225,-229,-231,228,-233,-234,-226,-232,-306,228,-263,-304,-280,-279,228,228,228,-257,-262,228,-260,31,-261,228,228,228,228,228,228,228,228,228,228,228,228,228,228,228,228,228,228,228,-309,-266,430,-218,-217,228,-215,228,228,228,-201,228,-214,228,-80,-202,228,228,-138,-136,31,228,-156,-155,-266,228,228,-12,228,228,-11,-278,-277,-276,-275,-274,-287,228,31,309,309,309,309,309,309,309,309,309,309,-240,-239,309,309,309,309,309,-241,469,-28,-309,-266,-213,-216,228,-205,228,-79,-203,-309,-182,-264,-272,-273,228,228,-258,-309,228,-266,228,228,228,228,-204,228,228,228,228,-11,228,-209,-208,-206,-80,-288,228,-309,-281,228,228,-282,228,-210,-207,228,-212,-211,]),'LPAREN':([0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,19,20,21,23,24,25,26,29,30,31,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,59,61,63,65,68,69,70,71,73,74,76,77,78,79,80,81,83,84,85,88,91,92,96,101,102,103,104,105,106,107,108,113,115,120,121,126,127,131,133,139,140,142,143,144,147,148,149,150,151,153,154,155,156,157,158,159,160,161,162,165,166,167,169,170,171,172,173,174,175,176,177,178,180,181,184,185,186,187,188,189,192,193,196,198,199,202,203,206,207,208,209,213,214,215,216,217,218,219,220,222,224,225,228,229,230,232,234,235,237,238,239,244,249,250,251,253,254,255,258,260,264,265,266,267,268,269,270,271,272,273,274,275,276,277,279,280,282,284,285,286,288,291,293,296,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,319,324,325,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,356,357,359,361,362,363,367,368,369,370,371,372,376,378,380,383,384,385,386,389,394,395,397,398,418,419,420,421,422,423,424,427,428,430,432,433,435,437,439,441,442,443,447,448,454,457,459,460,461,463,466,467,469,470,471,472,473,474,475,476,477,479,480,481,482,483,484,485,487,488,495,496,500,501,502,504,505,507,509,510,511,512,513,514,517,520,522,523,524,526,527,528,],[4,-309,-104,-117,4,-115,-101,-99,60,-97,-116,-98,-64,4,-60,-102,-93,-66,-96,-111,-106,-65,-95,-112,4,-221,-109,-309,-113,81,-63,-118,4,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,-309,60,81,4,-61,-133,-307,-132,-153,-152,-28,-164,-166,-27,-90,81,-92,81,145,-37,-89,-91,-94,-83,-86,-88,-69,-30,173,-28,-309,189,-294,-70,173,-135,-130,-308,81,-167,-165,81,145,-309,173,173,81,-298,-270,-286,-301,-305,-302,-299,-284,277,-268,-285,285,287,288,-267,291,-297,-266,-271,173,291,-303,-265,-295,-283,-300,-296,-269,173,173,-36,-35,189,189,327,-45,173,331,-73,-76,-72,173,-74,339,343,288,173,348,-78,-199,-198,-77,-200,173,-75,-266,-294,355,-139,-137,-134,-131,-128,288,-129,-154,288,-38,173,-28,-309,-71,-309,-227,-230,-228,-224,-225,-229,-231,173,-233,-234,-226,-232,-306,173,-304,-280,-279,173,173,-31,173,173,-34,398,288,288,288,288,288,288,288,288,288,288,288,288,288,288,288,288,173,288,288,189,327,331,-309,-266,173,-218,-217,173,-215,173,173,173,-201,173,-214,173,-80,-202,173,173,-138,-136,81,288,-156,-155,-266,173,173,-44,-43,-12,288,173,-11,-278,-277,-276,-275,-274,-287,288,398,398,-33,-32,-197,-191,173,-28,-309,-193,-195,-266,-213,-216,173,-205,173,482,-79,-203,-39,-42,-309,-182,-272,-273,173,288,-309,288,-266,173,173,-51,-50,-192,-194,-196,173,173,-204,173,173,173,-41,-40,173,-11,-46,-49,173,-209,-208,-206,-80,-288,173,-309,-281,-48,-47,173,173,-282,173,-210,-207,173,-212,-211,]),'MINUSMINUS':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,115,121,131,139,144,147,148,150,151,153,154,155,156,157,158,159,160,161,162,166,167,169,170,171,172,173,174,175,176,177,178,180,181,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,229,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,276,277,279,280,282,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,383,384,385,386,389,394,395,422,423,424,430,432,433,435,437,439,442,443,454,457,459,460,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,507,509,510,511,514,517,520,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,174,-28,-309,-294,174,-308,-167,-309,174,174,-298,-270,-286,-301,-305,-302,-299,-284,174,-268,-285,280,174,-267,174,-297,-266,-271,174,174,-303,-265,-295,-283,-300,-296,-269,174,174,174,-73,-76,-72,174,-74,174,174,-78,-199,-198,-77,-200,174,-75,-266,-294,174,174,174,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,174,-233,-234,-226,-232,-306,174,-304,-280,-279,174,174,174,174,174,174,174,174,174,174,174,174,174,174,174,174,174,174,174,174,174,174,174,-309,-266,174,-218,-217,174,-215,174,174,174,-201,174,-214,174,-80,-202,174,174,174,-266,174,174,-12,174,174,-11,-278,-277,-276,-275,-274,-287,174,174,-28,-309,-266,-213,-216,174,-205,174,-79,-203,-309,-182,-272,-273,174,174,-309,174,-266,174,174,174,174,-204,174,174,174,174,-11,174,-209,-208,-206,-80,-288,174,-309,-281,174,174,-282,174,-210,-207,174,-212,-211,]),'ID':([0,1,2,3,4,5,6,7,9,10,11,12,13,14,15,16,17,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,38,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,59,60,63,65,68,69,70,71,73,74,75,76,77,78,79,80,81,83,84,91,92,96,101,102,103,104,106,107,108,113,120,121,126,127,131,133,134,135,139,140,142,144,145,147,148,149,151,159,160,166,167,169,171,173,174,176,184,185,186,189,192,198,200,202,203,204,206,207,208,214,215,217,218,219,220,222,224,225,228,232,234,235,237,238,239,244,248,249,250,253,254,255,258,260,264,265,266,267,268,269,270,271,272,273,274,275,277,281,283,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,319,326,327,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,356,357,359,361,362,363,367,368,369,372,375,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,462,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,508,509,510,514,517,522,523,524,526,527,528,],[37,-309,-104,-117,37,-115,-101,-99,-97,-116,-98,-64,37,-60,-102,-93,-66,-96,-111,-106,-141,-65,-95,-112,37,71,74,-221,-109,-309,-113,37,-63,-118,37,-140,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,-309,115,37,37,-61,-133,-307,-132,-153,-152,138,-28,-164,-166,-27,-90,37,-92,37,-89,-91,-94,-83,-86,-88,-69,115,-28,-309,37,-70,229,-135,-130,-308,37,138,138,-167,-165,37,-309,115,115,115,37,-270,115,-268,115,-267,115,-266,115,115,-265,-269,115,115,37,37,115,115,-73,-76,335,-72,115,-74,115,229,-78,-199,-198,-77,-200,229,-75,-266,-139,-137,-134,-131,-128,115,-129,138,-154,115,115,-28,-309,-71,-309,-227,-230,-228,-224,-225,-229,-231,115,-233,-234,-226,-232,115,384,386,115,115,115,115,115,115,115,115,115,115,115,115,115,115,115,115,115,115,115,115,115,115,115,37,-309,115,-266,115,-218,-217,115,-215,115,229,115,-201,115,-214,229,-80,-202,229,115,-138,-136,37,115,-156,-155,-266,115,115,-12,115,115,115,-11,115,115,-28,-309,-266,-213,-216,115,-205,229,-79,-203,-309,-182,115,115,115,-309,115,-266,115,115,115,229,-204,229,115,229,115,-11,115,-209,-208,-206,-80,115,115,-309,115,229,229,-210,-207,229,-212,-211,]),'IF':([53,70,101,104,121,131,202,203,206,208,215,217,218,219,220,222,224,225,336,337,340,342,346,349,351,352,353,354,432,433,437,439,442,443,479,480,481,483,501,502,504,505,517,522,523,524,526,527,528,],[-68,-307,-83,-69,230,-308,-73,-76,-72,-74,230,-78,-199,-198,-77,-200,230,-75,-218,-217,-215,230,-201,-214,230,-80,-202,230,-213,-216,-205,230,-79,-203,230,-204,230,230,-209,-208,-206,-80,230,230,-210,-207,230,-212,-211,]),'STRING_LITERAL':([3,35,51,53,59,70,76,78,79,101,104,106,107,108,121,131,139,144,147,148,151,159,160,161,166,167,169,171,173,174,175,176,184,185,186,198,202,203,206,207,208,214,215,217,218,219,220,222,224,225,228,239,250,253,254,255,260,264,265,266,267,268,269,270,271,272,273,274,275,277,279,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,326,329,330,336,337,339,340,341,342,343,346,348,349,351,352,353,354,355,361,367,368,369,372,376,378,380,395,422,423,424,430,432,433,435,437,439,442,443,454,457,461,463,466,467,469,470,471,477,479,480,481,482,483,487,488,500,501,502,504,505,509,510,514,517,522,523,524,526,527,528,],[-117,-118,-119,-68,-309,-307,-28,-166,-27,-83,-69,175,-28,-309,175,-308,-167,-309,175,175,-270,175,-268,279,175,-267,175,-266,175,175,-303,-265,-269,175,175,175,-73,-76,-72,175,-74,175,175,-78,-199,-198,-77,-200,175,-75,-266,175,175,175,-28,-309,-309,-227,-230,-228,-224,-225,-229,-231,175,-233,-234,-226,-232,175,-304,175,175,175,175,175,175,175,175,175,175,175,175,175,175,175,175,175,175,175,175,175,175,175,-309,-266,175,-218,-217,175,-215,175,175,175,-201,175,-214,175,-80,-202,175,175,175,-266,175,175,-12,175,175,-11,175,175,-28,-309,-266,-213,-216,175,-205,175,-79,-203,-309,-182,175,175,-309,175,-266,175,175,175,175,-204,175,175,175,175,-11,175,-209,-208,-206,-80,175,-309,175,175,175,-210,-207,175,-212,-211,]),'FLOAT':([0,1,2,3,5,6,7,8,9,10,11,12,14,15,16,17,18,19,20,21,23,24,25,26,29,30,32,33,34,35,36,37,39,40,41,42,44,45,47,48,49,50,51,53,54,55,56,57,60,61,63,64,65,67,68,69,70,71,72,73,74,78,80,83,87,91,92,96,101,102,103,104,105,113,117,120,121,122,123,124,125,126,127,128,129,130,131,132,133,139,145,173,187,188,189,201,202,203,206,208,215,217,218,219,220,222,225,231,232,233,234,235,236,237,238,244,249,258,277,286,287,288,291,293,296,327,331,336,337,339,340,346,349,351,352,353,356,357,360,362,363,398,418,419,432,433,437,442,443,480,501,502,504,505,523,524,527,528,],[39,-309,-104,-117,-115,-101,-99,-52,-97,-116,-98,-64,-60,-102,-93,-66,39,-96,-111,-106,-65,-95,-112,39,-221,-109,-113,39,-63,-118,39,-29,-107,-62,-103,-67,-114,-108,-309,-110,-309,-105,-119,-68,-100,-87,-10,-9,39,-53,39,-84,39,39,-61,-133,-307,-132,39,-153,-152,-166,-90,-92,39,-89,-91,-94,-83,-86,-88,-69,-30,39,39,-70,39,-85,39,39,39,-135,-130,-145,-146,-142,-308,39,39,-167,39,39,-36,-35,39,39,-73,-76,-72,-74,39,-78,-199,-198,-77,-200,-75,39,-139,39,-137,-134,-143,-131,-128,-129,-154,-71,39,-31,39,39,39,-34,39,39,39,-218,-217,39,-215,-201,-214,-78,-80,-202,-138,-136,-144,-156,-155,39,-33,-32,-213,-216,-205,-79,-203,-204,-209,-208,-206,-80,-210,-207,-212,-211,]),'XOREQUAL':([115,131,150,152,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,458,459,460,465,507,511,520,],[-294,-308,-298,268,-286,-301,-305,-302,-299,-284,-285,-259,-297,-271,-303,-295,-283,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-264,-272,-273,-258,-288,-281,-282,]),'LSHIFTEQUAL':([115,131,150,152,153,154,155,156,157,158,161,162,170,172,175,177,178,180,181,229,276,278,279,280,282,289,290,292,297,383,384,385,386,389,394,458,459,460,465,507,511,520,],[-294,-308,-298,270,-286,-301,-305,-302,-299,-284,-285,-259,-297,-271,-303,-295,-283,-300,-296,-294,-306,-263,-304,-280,-279,-257,-262,-260,-261,-278,-277,-276,-275,-274,-287,-264,-272,-273,-258,-288,-281,-282,]),'RBRACKET':([3,35,51,59,78,79,106,107,115,131,139,144,150,152,153,154,155,156,157,158,161,162,163,164,168,170,171,172,175,177,178,179,180,181,182,183,198,227,253,254,276,278,279,280,282,289,290,292,297,317,318,326,328,329,330,345,366,367,381,383,384,385,386,387,389,394,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,416,417,422,423,429,430,436,449,450,453,458,459,460,465,468,469,494,497,498,507,511,519,520,],[-117,-118,-119,-309,-166,-27,-309,-28,-294,-308,-167,-309,-298,-257,-286,-301,-305,-302,-299,-284,-285,-259,286,-238,-4,-297,293,-271,-303,-295,-283,-236,-300,-296,-3,-222,-309,-219,-309,-28,-306,-263,-304,-280,-279,-257,-262,-260,-261,418,419,-309,427,428,-309,-235,447,448,-223,-278,-277,-276,-275,459,-274,-287,-244,-256,-245,-243,-247,-251,-246,-242,-249,-254,-240,-239,-248,-255,-250,-252,-253,-241,-309,-28,474,475,-220,484,485,486,-264,-272,-273,-258,495,496,-237,512,513,-288,-281,525,-282,]),}\n\n_lr_action = {}\nfor _k, _v in _lr_action_items.items():\n   for _x,_y in zip(_v[0],_v[1]):\n      if not _x in _lr_action:  _lr_action[_x] = {}\n      _lr_action[_x][_k] = _y\ndel _lr_action_items\n\n_lr_goto_items = {'expression_statement':([121,215,224,342,351,354,439,479,481,483,517,522,526,],[202,202,202,202,202,202,202,202,202,202,202,202,202,]),'struct_or_union_specifier':([0,18,26,36,60,65,67,72,87,117,121,123,124,125,132,145,173,189,201,215,231,233,277,287,288,291,327,331,339,398,],[5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,5,]),'init_declarator_list':([33,63,],[82,82,]),'init_declarator_list_opt':([33,63,],[90,90,]),'iteration_statement':([121,215,224,342,351,354,439,479,481,483,517,522,526,],[203,203,203,203,203,203,203,203,203,203,203,203,203,]),'unified_string_literal':([106,121,147,148,159,166,169,173,174,185,186,198,207,214,215,224,239,250,253,271,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,330,339,341,342,343,348,351,354,355,361,368,369,376,378,395,422,435,439,461,463,467,470,471,477,479,481,482,483,487,500,509,514,517,522,526,],[161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,161,]),'assignment_expression_opt':([106,198,253,330,422,],[163,328,366,429,468,]),'brace_open':([27,28,66,69,71,73,74,121,146,147,148,215,224,342,351,354,378,395,439,458,463,464,479,481,483,487,517,522,526,],[72,75,121,123,124,134,135,121,121,260,260,121,121,121,121,121,260,466,121,466,466,466,121,121,121,260,121,121,121,]),'enumerator':([75,134,135,248,],[136,136,136,364,]),'typeid_noparen_declarator':([113,],[197,]),'type_qualifier_list_opt':([31,59,108,144,255,326,424,],[77,106,186,253,369,422,471,]),'declaration_specifiers_no_type_opt':([1,47,49,],[55,102,103,]),'expression_opt':([121,215,224,339,342,351,354,435,439,477,479,481,483,500,514,517,522,526,],[205,205,205,434,205,205,205,478,205,499,205,205,205,515,521,205,205,205,]),'designation':([260,454,466,510,],[372,372,372,372,]),'parameter_list':([60,145,189,327,331,398,],[116,116,116,116,116,116,]),'labeled_statement':([121,215,224,342,351,354,439,479,481,483,517,522,526,],[206,206,206,206,206,206,206,206,206,206,206,206,206,]),'abstract_declarator':([113,189,296,398,],[191,323,191,323,]),'translation_unit':([0,],[26,]),'init_declarator':([33,63,142,149,],[94,94,252,263,]),'direct_abstract_declarator':([113,189,192,296,319,397,398,],[199,199,325,199,325,325,199,]),'designator_list':([260,454,466,510,],[379,379,379,379,]),'identifier':([60,106,121,145,147,148,159,166,169,173,174,185,186,198,200,207,214,215,224,239,250,253,271,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,327,330,339,341,342,343,348,351,354,355,361,368,369,375,376,378,395,422,435,439,461,462,463,467,470,471,477,479,481,482,483,487,500,508,509,514,517,522,526,],[118,178,178,118,178,178,178,178,178,178,178,178,178,178,332,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,178,118,178,178,178,178,178,178,178,178,178,178,178,178,452,178,178,178,178,178,178,178,492,178,178,178,178,178,178,178,178,178,178,178,518,178,178,178,178,178,]),'offsetof_member_designator':([462,],[491,]),'unary_expression':([106,121,147,148,159,166,169,173,174,185,186,198,207,214,215,224,239,250,253,271,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,330,339,341,342,343,348,351,354,355,361,368,369,376,378,395,422,435,439,461,463,467,470,471,477,479,481,482,483,487,500,509,514,517,522,526,],[152,152,152,152,278,289,292,152,297,152,152,152,152,289,152,152,289,289,152,152,152,152,152,152,152,289,289,289,289,289,289,289,289,289,289,289,289,289,289,289,289,152,289,289,152,152,152,152,152,152,152,152,152,289,152,152,289,152,289,152,152,152,152,289,289,152,152,152,152,152,152,152,152,152,152,152,152,152,152,]),'abstract_declarator_opt':([113,296,],[190,396,]),'initializer':([147,148,378,487,],[259,262,455,506,]),'direct_id_declarator':([0,4,13,26,33,36,63,65,81,84,113,133,142,149,189,192,319,359,],[8,8,61,8,8,8,8,8,8,61,8,8,8,8,8,61,61,8,]),'struct_declaration_list':([72,123,124,],[125,231,233,]),'pp_directive':([0,26,],[12,12,]),'declaration_list':([18,87,],[67,67,]),'id_init_declarator':([36,65,],[95,95,]),'type_specifier':([0,18,26,36,60,65,67,72,87,117,121,123,124,125,132,145,173,189,201,215,231,233,277,287,288,291,327,331,339,398,],[16,16,16,96,16,96,16,127,16,96,16,127,127,127,237,16,127,16,16,16,127,127,127,127,127,127,16,16,16,16,]),'compound_statement':([66,121,146,215,224,342,351,354,439,479,481,483,517,522,526,],[120,208,258,208,208,208,208,208,208,208,208,208,208,208,208,]),'pointer':([0,4,26,33,36,63,65,77,81,113,133,142,149,189,296,359,398,],[13,13,13,84,13,84,13,140,84,192,84,84,84,319,397,84,397,]),'typeid_declarator':([33,63,81,133,142,149,359,],[86,86,141,86,86,86,86,]),'id_init_declarator_list':([36,65,],[98,98,]),'declarator':([33,63,133,142,149,359,],[89,89,245,89,89,245,]),'argument_expression_list':([285,],[390,]),'struct_declarator_list_opt':([133,],[242,]),'typedef_name':([0,18,26,36,60,65,67,72,87,117,121,123,124,125,132,145,173,189,201,215,231,233,277,287,288,291,327,331,339,398,],[32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,32,]),'parameter_type_list_opt':([189,331,398,],[322,431,322,]),'struct_declarator':([133,359,],[243,445,]),'type_qualifier':([0,1,18,26,31,33,47,49,59,60,63,67,72,76,87,107,108,113,121,123,124,125,132,133,144,145,173,189,201,215,231,233,254,255,277,287,288,291,296,326,327,331,339,398,423,424,],[47,47,47,47,78,91,47,47,78,47,91,47,78,139,47,139,78,91,47,78,78,78,139,244,78,47,78,47,47,47,78,78,139,78,78,78,78,78,244,78,47,47,47,47,139,78,]),'assignment_operator':([152,],[271,]),'expression':([121,173,207,215,224,277,284,288,291,314,339,342,343,348,351,354,355,435,439,477,479,481,482,483,500,509,514,517,522,526,],[211,294,338,211,211,294,387,294,294,415,211,211,438,440,211,211,444,211,211,211,211,211,503,211,211,519,211,211,211,211,]),'storage_class_specifier':([0,1,18,26,33,47,49,60,63,67,87,113,121,145,189,201,215,327,331,339,398,],[1,1,1,1,80,1,1,1,80,1,1,80,1,1,1,1,1,1,1,1,1,]),'unified_wstring_literal':([106,121,147,148,159,166,169,173,174,185,186,198,207,214,215,224,239,250,253,271,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,330,339,341,342,343,348,351,354,355,361,368,369,376,378,395,422,435,439,461,463,467,470,471,477,479,481,482,483,487,500,509,514,517,522,526,],[153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,153,]),'translation_unit_or_empty':([0,],[43,]),'initializer_list_opt':([260,],[373,]),'brace_close':([72,123,124,125,137,226,231,233,246,247,373,454,493,510,],[126,232,234,235,249,353,356,357,362,363,451,489,511,520,]),'direct_typeid_declarator':([33,63,81,84,133,142,149,359,],[85,85,85,143,85,85,85,85,]),'external_declaration':([0,26,],[14,68,]),'pragmacomp_or_statement':([224,342,354,439,479,481,483,517,522,526,],[350,437,443,480,501,502,504,524,527,528,]),'type_name':([173,277,287,288,291,],[295,382,391,392,393,]),'block_item_list':([121,],[215,]),'pppragma_directive':([0,26,72,121,123,124,125,215,224,231,233,342,351,354,439,479,481,483,517,522,526,],[23,23,129,217,129,129,129,217,351,129,129,351,217,351,351,351,351,351,351,351,351,]),'statement':([121,215,224,342,351,354,439,479,481,483,517,522,526,],[218,218,352,352,442,352,352,352,352,505,352,352,352,]),'cast_expression':([106,121,147,148,166,173,185,186,198,207,214,215,224,239,250,253,271,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,330,339,341,342,343,348,351,354,355,361,368,369,376,378,395,422,435,439,461,463,467,470,471,477,479,481,482,483,487,500,509,514,517,522,526,],[164,164,164,164,290,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,465,164,164,164,164,465,164,164,164,164,164,164,164,164,164,164,164,164,164,164,164,]),'struct_declarator_list':([133,],[240,]),'empty':([0,1,18,31,33,36,47,49,59,60,63,65,87,106,108,113,121,133,144,145,189,198,215,224,253,255,260,296,326,327,330,331,339,342,351,354,398,422,424,435,439,454,466,477,479,481,483,500,510,514,517,522,526,],[52,57,62,79,93,100,57,57,79,110,93,100,62,182,79,195,223,241,79,110,320,182,347,347,182,79,380,195,79,110,182,320,347,347,347,347,320,182,79,347,347,488,488,347,347,347,347,347,488,347,347,347,347,]),'parameter_declaration':([60,145,189,201,327,331,398,],[112,112,112,334,112,112,112,]),'primary_expression':([106,121,147,148,159,166,169,173,174,185,186,198,207,214,215,224,239,250,253,271,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,330,339,341,342,343,348,351,354,355,361,368,369,376,378,395,422,435,439,461,463,467,470,471,477,479,481,482,483,487,500,509,514,517,522,526,],[172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,172,]),'declaration':([0,18,26,67,87,121,215,339,],[34,64,34,122,64,219,219,435,]),'declaration_specifiers_no_type':([0,1,18,26,47,49,60,67,87,121,145,189,201,215,327,331,339,398,],[36,56,65,36,56,56,117,65,65,65,117,117,117,65,117,117,65,117,]),'jump_statement':([121,215,224,342,351,354,439,479,481,483,517,522,526,],[220,220,220,220,220,220,220,220,220,220,220,220,220,]),'enumerator_list':([75,134,135,],[137,246,247,]),'block_item':([121,215,],[222,346,]),'constant_expression':([214,239,250,361,376,],[344,358,365,446,453,]),'identifier_list_opt':([60,145,327,],[109,256,425,]),'constant':([106,121,147,148,159,166,169,173,174,185,186,198,207,214,215,224,239,250,253,271,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,330,339,341,342,343,348,351,354,355,361,368,369,376,378,395,422,435,439,461,463,467,470,471,477,479,481,482,483,487,500,509,514,517,522,526,],[158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,158,]),'type_specifier_no_typeid':([0,18,26,33,36,60,63,65,67,72,87,113,117,121,123,124,125,132,133,145,173,189,201,215,231,233,277,287,288,291,296,327,331,339,398,],[10,10,10,83,10,10,83,10,10,10,10,83,10,10,10,10,10,10,238,10,10,10,10,10,10,10,10,10,10,10,238,10,10,10,10,]),'struct_declaration':([72,123,124,125,231,233,],[130,130,130,236,236,236,]),'direct_typeid_noparen_declarator':([113,192,],[193,324,]),'id_declarator':([0,4,26,33,36,63,65,81,113,133,142,149,189,359,],[18,58,18,87,97,119,97,58,194,119,119,119,58,119,]),'selection_statement':([121,215,224,342,351,354,439,479,481,483,517,522,526,],[225,225,225,225,225,225,225,225,225,225,225,225,225,]),'postfix_expression':([106,121,147,148,159,166,169,173,174,185,186,198,207,214,215,224,239,250,253,271,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,330,339,341,342,343,348,351,354,355,361,368,369,376,378,395,422,435,439,461,463,467,470,471,477,479,481,482,483,487,500,509,514,517,522,526,],[162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,162,]),'initializer_list':([260,466,],[377,493,]),'unary_operator':([106,121,147,148,159,166,169,173,174,185,186,198,207,214,215,224,239,250,253,271,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,330,339,341,342,343,348,351,354,355,361,368,369,376,378,395,422,435,439,461,463,467,470,471,477,479,481,482,483,487,500,509,514,517,522,526,],[166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,166,]),'struct_or_union':([0,18,26,36,60,65,67,72,87,117,121,123,124,125,132,145,173,189,201,215,231,233,277,287,288,291,327,331,339,398,],[27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,27,]),'block_item_list_opt':([121,],[226,]),'assignment_expression':([106,121,147,148,173,185,186,198,207,215,224,253,271,277,284,285,288,291,314,330,339,341,342,343,348,351,354,355,368,369,378,422,435,439,461,470,471,477,479,481,482,483,487,500,509,514,517,522,526,],[168,227,261,261,227,317,318,168,227,227,227,168,381,227,227,388,227,227,227,168,227,436,227,227,227,227,227,227,449,450,261,168,227,227,490,497,498,227,227,227,227,227,261,227,227,227,227,227,227,]),'designation_opt':([260,454,466,510,],[378,487,378,487,]),'parameter_type_list':([60,145,189,327,331,398,],[111,257,321,426,321,321,]),'type_qualifier_list':([31,59,72,108,123,124,125,144,173,231,233,255,277,287,288,291,326,424,],[76,107,132,76,132,132,132,254,132,132,132,76,132,132,132,132,423,76,]),'designator':([260,379,454,466,510,],[374,456,374,374,374,]),'id_init_declarator_list_opt':([36,65,],[99,99,]),'declaration_specifiers':([0,18,26,60,67,87,121,145,189,201,215,327,331,339,398,],[33,63,33,113,63,63,63,113,113,113,63,113,113,63,113,]),'identifier_list':([60,145,327,],[114,114,114,]),'declaration_list_opt':([18,87,],[66,146,]),'function_definition':([0,26,],[40,40,]),'binary_expression':([106,121,147,148,173,185,186,198,207,214,215,224,239,250,253,271,277,284,285,288,291,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,330,339,341,342,343,348,351,354,355,361,368,369,376,378,422,435,439,461,467,470,471,477,479,481,482,483,487,500,509,514,517,522,526,],[179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,179,416,417,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,179,]),'enum_specifier':([0,18,26,36,60,65,67,72,87,117,121,123,124,125,132,145,173,189,201,215,231,233,277,287,288,291,327,331,339,398,],[44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,44,]),'decl_body':([0,18,26,67,87,121,215,339,],[46,46,46,46,46,46,46,46,]),'function_specifier':([0,1,18,26,33,47,49,60,63,67,87,113,121,145,189,201,215,327,331,339,398,],[49,49,49,49,92,49,49,49,92,49,49,92,49,49,49,49,49,49,49,49,49,]),'specifier_qualifier_list':([72,123,124,125,173,231,233,277,287,288,291,],[133,133,133,133,296,133,133,296,296,296,296,]),'conditional_expression':([106,121,147,148,173,185,186,198,207,214,215,224,239,250,253,271,277,284,285,288,291,314,330,339,341,342,343,348,351,354,355,361,368,369,376,378,422,435,439,461,467,470,471,477,479,481,482,483,487,500,509,514,517,522,526,],[183,183,183,183,183,183,183,183,183,345,183,183,345,345,183,183,183,183,183,183,183,183,183,183,183,183,183,183,183,183,183,345,183,183,345,183,183,183,183,183,494,183,183,183,183,183,183,183,183,183,183,183,183,183,183,]),}\n\n_lr_goto = {}\nfor _k, _v in _lr_goto_items.items():\n   for _x, _y in zip(_v[0], _v[1]):\n       if not _x in _lr_goto: _lr_goto[_x] = {}\n       _lr_goto[_x][_k] = _y\ndel _lr_goto_items\n_lr_productions = [\n  (\"S' -> translation_unit_or_empty\",\"S'\",1,None,None,None),\n  ('abstract_declarator_opt -> empty','abstract_declarator_opt',1,'p_abstract_declarator_opt','plyparser.py',43),\n  ('abstract_declarator_opt -> abstract_declarator','abstract_declarator_opt',1,'p_abstract_declarator_opt','plyparser.py',44),\n  ('assignment_expression_opt -> empty','assignment_expression_opt',1,'p_assignment_expression_opt','plyparser.py',43),\n  ('assignment_expression_opt -> assignment_expression','assignment_expression_opt',1,'p_assignment_expression_opt','plyparser.py',44),\n  ('block_item_list_opt -> empty','block_item_list_opt',1,'p_block_item_list_opt','plyparser.py',43),\n  ('block_item_list_opt -> block_item_list','block_item_list_opt',1,'p_block_item_list_opt','plyparser.py',44),\n  ('declaration_list_opt -> empty','declaration_list_opt',1,'p_declaration_list_opt','plyparser.py',43),\n  ('declaration_list_opt -> declaration_list','declaration_list_opt',1,'p_declaration_list_opt','plyparser.py',44),\n  ('declaration_specifiers_no_type_opt -> empty','declaration_specifiers_no_type_opt',1,'p_declaration_specifiers_no_type_opt','plyparser.py',43),\n  ('declaration_specifiers_no_type_opt -> declaration_specifiers_no_type','declaration_specifiers_no_type_opt',1,'p_declaration_specifiers_no_type_opt','plyparser.py',44),\n  ('designation_opt -> empty','designation_opt',1,'p_designation_opt','plyparser.py',43),\n  ('designation_opt -> designation','designation_opt',1,'p_designation_opt','plyparser.py',44),\n  ('expression_opt -> empty','expression_opt',1,'p_expression_opt','plyparser.py',43),\n  ('expression_opt -> expression','expression_opt',1,'p_expression_opt','plyparser.py',44),\n  ('id_init_declarator_list_opt -> empty','id_init_declarator_list_opt',1,'p_id_init_declarator_list_opt','plyparser.py',43),\n  ('id_init_declarator_list_opt -> id_init_declarator_list','id_init_declarator_list_opt',1,'p_id_init_declarator_list_opt','plyparser.py',44),\n  ('identifier_list_opt -> empty','identifier_list_opt',1,'p_identifier_list_opt','plyparser.py',43),\n  ('identifier_list_opt -> identifier_list','identifier_list_opt',1,'p_identifier_list_opt','plyparser.py',44),\n  ('init_declarator_list_opt -> empty','init_declarator_list_opt',1,'p_init_declarator_list_opt','plyparser.py',43),\n  ('init_declarator_list_opt -> init_declarator_list','init_declarator_list_opt',1,'p_init_declarator_list_opt','plyparser.py',44),\n  ('initializer_list_opt -> empty','initializer_list_opt',1,'p_initializer_list_opt','plyparser.py',43),\n  ('initializer_list_opt -> initializer_list','initializer_list_opt',1,'p_initializer_list_opt','plyparser.py',44),\n  ('parameter_type_list_opt -> empty','parameter_type_list_opt',1,'p_parameter_type_list_opt','plyparser.py',43),\n  ('parameter_type_list_opt -> parameter_type_list','parameter_type_list_opt',1,'p_parameter_type_list_opt','plyparser.py',44),\n  ('struct_declarator_list_opt -> empty','struct_declarator_list_opt',1,'p_struct_declarator_list_opt','plyparser.py',43),\n  ('struct_declarator_list_opt -> struct_declarator_list','struct_declarator_list_opt',1,'p_struct_declarator_list_opt','plyparser.py',44),\n  ('type_qualifier_list_opt -> empty','type_qualifier_list_opt',1,'p_type_qualifier_list_opt','plyparser.py',43),\n  ('type_qualifier_list_opt -> type_qualifier_list','type_qualifier_list_opt',1,'p_type_qualifier_list_opt','plyparser.py',44),\n  ('direct_id_declarator -> ID','direct_id_declarator',1,'p_direct_id_declarator_1','plyparser.py',126),\n  ('direct_id_declarator -> LPAREN id_declarator RPAREN','direct_id_declarator',3,'p_direct_id_declarator_2','plyparser.py',126),\n  ('direct_id_declarator -> direct_id_declarator LBRACKET type_qualifier_list_opt assignment_expression_opt RBRACKET','direct_id_declarator',5,'p_direct_id_declarator_3','plyparser.py',126),\n  ('direct_id_declarator -> direct_id_declarator LBRACKET STATIC type_qualifier_list_opt assignment_expression RBRACKET','direct_id_declarator',6,'p_direct_id_declarator_4','plyparser.py',126),\n  ('direct_id_declarator -> direct_id_declarator LBRACKET type_qualifier_list STATIC assignment_expression RBRACKET','direct_id_declarator',6,'p_direct_id_declarator_4','plyparser.py',127),\n  ('direct_id_declarator -> direct_id_declarator LBRACKET type_qualifier_list_opt TIMES RBRACKET','direct_id_declarator',5,'p_direct_id_declarator_5','plyparser.py',126),\n  ('direct_id_declarator -> direct_id_declarator LPAREN parameter_type_list RPAREN','direct_id_declarator',4,'p_direct_id_declarator_6','plyparser.py',126),\n  ('direct_id_declarator -> direct_id_declarator LPAREN identifier_list_opt RPAREN','direct_id_declarator',4,'p_direct_id_declarator_6','plyparser.py',127),\n  ('direct_typeid_declarator -> TYPEID','direct_typeid_declarator',1,'p_direct_typeid_declarator_1','plyparser.py',126),\n  ('direct_typeid_declarator -> LPAREN typeid_declarator RPAREN','direct_typeid_declarator',3,'p_direct_typeid_declarator_2','plyparser.py',126),\n  ('direct_typeid_declarator -> direct_typeid_declarator LBRACKET type_qualifier_list_opt assignment_expression_opt RBRACKET','direct_typeid_declarator',5,'p_direct_typeid_declarator_3','plyparser.py',126),\n  ('direct_typeid_declarator -> direct_typeid_declarator LBRACKET STATIC type_qualifier_list_opt assignment_expression RBRACKET','direct_typeid_declarator',6,'p_direct_typeid_declarator_4','plyparser.py',126),\n  ('direct_typeid_declarator -> direct_typeid_declarator LBRACKET type_qualifier_list STATIC assignment_expression RBRACKET','direct_typeid_declarator',6,'p_direct_typeid_declarator_4','plyparser.py',127),\n  ('direct_typeid_declarator -> direct_typeid_declarator LBRACKET type_qualifier_list_opt TIMES RBRACKET','direct_typeid_declarator',5,'p_direct_typeid_declarator_5','plyparser.py',126),\n  ('direct_typeid_declarator -> direct_typeid_declarator LPAREN parameter_type_list RPAREN','direct_typeid_declarator',4,'p_direct_typeid_declarator_6','plyparser.py',126),\n  ('direct_typeid_declarator -> direct_typeid_declarator LPAREN identifier_list_opt RPAREN','direct_typeid_declarator',4,'p_direct_typeid_declarator_6','plyparser.py',127),\n  ('direct_typeid_noparen_declarator -> TYPEID','direct_typeid_noparen_declarator',1,'p_direct_typeid_noparen_declarator_1','plyparser.py',126),\n  ('direct_typeid_noparen_declarator -> direct_typeid_noparen_declarator LBRACKET type_qualifier_list_opt assignment_expression_opt RBRACKET','direct_typeid_noparen_declarator',5,'p_direct_typeid_noparen_declarator_3','plyparser.py',126),\n  ('direct_typeid_noparen_declarator -> direct_typeid_noparen_declarator LBRACKET STATIC type_qualifier_list_opt assignment_expression RBRACKET','direct_typeid_noparen_declarator',6,'p_direct_typeid_noparen_declarator_4','plyparser.py',126),\n  ('direct_typeid_noparen_declarator -> direct_typeid_noparen_declarator LBRACKET type_qualifier_list STATIC assignment_expression RBRACKET','direct_typeid_noparen_declarator',6,'p_direct_typeid_noparen_declarator_4','plyparser.py',127),\n  ('direct_typeid_noparen_declarator -> direct_typeid_noparen_declarator LBRACKET type_qualifier_list_opt TIMES RBRACKET','direct_typeid_noparen_declarator',5,'p_direct_typeid_noparen_declarator_5','plyparser.py',126),\n  ('direct_typeid_noparen_declarator -> direct_typeid_noparen_declarator LPAREN parameter_type_list RPAREN','direct_typeid_noparen_declarator',4,'p_direct_typeid_noparen_declarator_6','plyparser.py',126),\n  ('direct_typeid_noparen_declarator -> direct_typeid_noparen_declarator LPAREN identifier_list_opt RPAREN','direct_typeid_noparen_declarator',4,'p_direct_typeid_noparen_declarator_6','plyparser.py',127),\n  ('id_declarator -> direct_id_declarator','id_declarator',1,'p_id_declarator_1','plyparser.py',126),\n  ('id_declarator -> pointer direct_id_declarator','id_declarator',2,'p_id_declarator_2','plyparser.py',126),\n  ('typeid_declarator -> direct_typeid_declarator','typeid_declarator',1,'p_typeid_declarator_1','plyparser.py',126),\n  ('typeid_declarator -> pointer direct_typeid_declarator','typeid_declarator',2,'p_typeid_declarator_2','plyparser.py',126),\n  ('typeid_noparen_declarator -> direct_typeid_noparen_declarator','typeid_noparen_declarator',1,'p_typeid_noparen_declarator_1','plyparser.py',126),\n  ('typeid_noparen_declarator -> pointer direct_typeid_noparen_declarator','typeid_noparen_declarator',2,'p_typeid_noparen_declarator_2','plyparser.py',126),\n  ('translation_unit_or_empty -> translation_unit','translation_unit_or_empty',1,'p_translation_unit_or_empty','c_parser.py',514),\n  ('translation_unit_or_empty -> empty','translation_unit_or_empty',1,'p_translation_unit_or_empty','c_parser.py',515),\n  ('translation_unit -> external_declaration','translation_unit',1,'p_translation_unit_1','c_parser.py',523),\n  ('translation_unit -> translation_unit external_declaration','translation_unit',2,'p_translation_unit_2','c_parser.py',530),\n  ('external_declaration -> function_definition','external_declaration',1,'p_external_declaration_1','c_parser.py',542),\n  ('external_declaration -> declaration','external_declaration',1,'p_external_declaration_2','c_parser.py',547),\n  ('external_declaration -> pp_directive','external_declaration',1,'p_external_declaration_3','c_parser.py',552),\n  ('external_declaration -> pppragma_directive','external_declaration',1,'p_external_declaration_3','c_parser.py',553),\n  ('external_declaration -> SEMI','external_declaration',1,'p_external_declaration_4','c_parser.py',558),\n  ('pp_directive -> PPHASH','pp_directive',1,'p_pp_directive','c_parser.py',563),\n  ('pppragma_directive -> PPPRAGMA','pppragma_directive',1,'p_pppragma_directive','c_parser.py',569),\n  ('pppragma_directive -> PPPRAGMA PPPRAGMASTR','pppragma_directive',2,'p_pppragma_directive','c_parser.py',570),\n  ('function_definition -> id_declarator declaration_list_opt compound_statement','function_definition',3,'p_function_definition_1','c_parser.py',581),\n  ('function_definition -> declaration_specifiers id_declarator declaration_list_opt compound_statement','function_definition',4,'p_function_definition_2','c_parser.py',598),\n  ('statement -> labeled_statement','statement',1,'p_statement','c_parser.py',609),\n  ('statement -> expression_statement','statement',1,'p_statement','c_parser.py',610),\n  ('statement -> compound_statement','statement',1,'p_statement','c_parser.py',611),\n  ('statement -> selection_statement','statement',1,'p_statement','c_parser.py',612),\n  ('statement -> iteration_statement','statement',1,'p_statement','c_parser.py',613),\n  ('statement -> jump_statement','statement',1,'p_statement','c_parser.py',614),\n  ('statement -> pppragma_directive','statement',1,'p_statement','c_parser.py',615),\n  ('pragmacomp_or_statement -> pppragma_directive statement','pragmacomp_or_statement',2,'p_pragmacomp_or_statement','c_parser.py',662),\n  ('pragmacomp_or_statement -> statement','pragmacomp_or_statement',1,'p_pragmacomp_or_statement','c_parser.py',663),\n  ('decl_body -> declaration_specifiers init_declarator_list_opt','decl_body',2,'p_decl_body','c_parser.py',682),\n  ('decl_body -> declaration_specifiers_no_type id_init_declarator_list_opt','decl_body',2,'p_decl_body','c_parser.py',683),\n  ('declaration -> decl_body SEMI','declaration',2,'p_declaration','c_parser.py',742),\n  ('declaration_list -> declaration','declaration_list',1,'p_declaration_list','c_parser.py',751),\n  ('declaration_list -> declaration_list declaration','declaration_list',2,'p_declaration_list','c_parser.py',752),\n  ('declaration_specifiers_no_type -> type_qualifier declaration_specifiers_no_type_opt','declaration_specifiers_no_type',2,'p_declaration_specifiers_no_type_1','c_parser.py',762),\n  ('declaration_specifiers_no_type -> storage_class_specifier declaration_specifiers_no_type_opt','declaration_specifiers_no_type',2,'p_declaration_specifiers_no_type_2','c_parser.py',767),\n  ('declaration_specifiers_no_type -> function_specifier declaration_specifiers_no_type_opt','declaration_specifiers_no_type',2,'p_declaration_specifiers_no_type_3','c_parser.py',772),\n  ('declaration_specifiers -> declaration_specifiers type_qualifier','declaration_specifiers',2,'p_declaration_specifiers_1','c_parser.py',778),\n  ('declaration_specifiers -> declaration_specifiers storage_class_specifier','declaration_specifiers',2,'p_declaration_specifiers_2','c_parser.py',783),\n  ('declaration_specifiers -> declaration_specifiers function_specifier','declaration_specifiers',2,'p_declaration_specifiers_3','c_parser.py',788),\n  ('declaration_specifiers -> declaration_specifiers type_specifier_no_typeid','declaration_specifiers',2,'p_declaration_specifiers_4','c_parser.py',793),\n  ('declaration_specifiers -> type_specifier','declaration_specifiers',1,'p_declaration_specifiers_5','c_parser.py',798),\n  ('declaration_specifiers -> declaration_specifiers_no_type type_specifier','declaration_specifiers',2,'p_declaration_specifiers_6','c_parser.py',803),\n  ('storage_class_specifier -> AUTO','storage_class_specifier',1,'p_storage_class_specifier','c_parser.py',809),\n  ('storage_class_specifier -> REGISTER','storage_class_specifier',1,'p_storage_class_specifier','c_parser.py',810),\n  ('storage_class_specifier -> STATIC','storage_class_specifier',1,'p_storage_class_specifier','c_parser.py',811),\n  ('storage_class_specifier -> EXTERN','storage_class_specifier',1,'p_storage_class_specifier','c_parser.py',812),\n  ('storage_class_specifier -> TYPEDEF','storage_class_specifier',1,'p_storage_class_specifier','c_parser.py',813),\n  ('function_specifier -> INLINE','function_specifier',1,'p_function_specifier','c_parser.py',818),\n  ('type_specifier_no_typeid -> VOID','type_specifier_no_typeid',1,'p_type_specifier_no_typeid','c_parser.py',823),\n  ('type_specifier_no_typeid -> _BOOL','type_specifier_no_typeid',1,'p_type_specifier_no_typeid','c_parser.py',824),\n  ('type_specifier_no_typeid -> CHAR','type_specifier_no_typeid',1,'p_type_specifier_no_typeid','c_parser.py',825),\n  ('type_specifier_no_typeid -> SHORT','type_specifier_no_typeid',1,'p_type_specifier_no_typeid','c_parser.py',826),\n  ('type_specifier_no_typeid -> INT','type_specifier_no_typeid',1,'p_type_specifier_no_typeid','c_parser.py',827),\n  ('type_specifier_no_typeid -> LONG','type_specifier_no_typeid',1,'p_type_specifier_no_typeid','c_parser.py',828),\n  ('type_specifier_no_typeid -> FLOAT','type_specifier_no_typeid',1,'p_type_specifier_no_typeid','c_parser.py',829),\n  ('type_specifier_no_typeid -> DOUBLE','type_specifier_no_typeid',1,'p_type_specifier_no_typeid','c_parser.py',830),\n  ('type_specifier_no_typeid -> _COMPLEX','type_specifier_no_typeid',1,'p_type_specifier_no_typeid','c_parser.py',831),\n  ('type_specifier_no_typeid -> SIGNED','type_specifier_no_typeid',1,'p_type_specifier_no_typeid','c_parser.py',832),\n  ('type_specifier_no_typeid -> UNSIGNED','type_specifier_no_typeid',1,'p_type_specifier_no_typeid','c_parser.py',833),\n  ('type_specifier_no_typeid -> __INT128','type_specifier_no_typeid',1,'p_type_specifier_no_typeid','c_parser.py',834),\n  ('type_specifier -> typedef_name','type_specifier',1,'p_type_specifier','c_parser.py',839),\n  ('type_specifier -> enum_specifier','type_specifier',1,'p_type_specifier','c_parser.py',840),\n  ('type_specifier -> struct_or_union_specifier','type_specifier',1,'p_type_specifier','c_parser.py',841),\n  ('type_specifier -> type_specifier_no_typeid','type_specifier',1,'p_type_specifier','c_parser.py',842),\n  ('type_qualifier -> CONST','type_qualifier',1,'p_type_qualifier','c_parser.py',847),\n  ('type_qualifier -> RESTRICT','type_qualifier',1,'p_type_qualifier','c_parser.py',848),\n  ('type_qualifier -> VOLATILE','type_qualifier',1,'p_type_qualifier','c_parser.py',849),\n  ('init_declarator_list -> init_declarator','init_declarator_list',1,'p_init_declarator_list','c_parser.py',854),\n  ('init_declarator_list -> init_declarator_list COMMA init_declarator','init_declarator_list',3,'p_init_declarator_list','c_parser.py',855),\n  ('init_declarator -> declarator','init_declarator',1,'p_init_declarator','c_parser.py',863),\n  ('init_declarator -> declarator EQUALS initializer','init_declarator',3,'p_init_declarator','c_parser.py',864),\n  ('id_init_declarator_list -> id_init_declarator','id_init_declarator_list',1,'p_id_init_declarator_list','c_parser.py',869),\n  ('id_init_declarator_list -> id_init_declarator_list COMMA init_declarator','id_init_declarator_list',3,'p_id_init_declarator_list','c_parser.py',870),\n  ('id_init_declarator -> id_declarator','id_init_declarator',1,'p_id_init_declarator','c_parser.py',875),\n  ('id_init_declarator -> id_declarator EQUALS initializer','id_init_declarator',3,'p_id_init_declarator','c_parser.py',876),\n  ('specifier_qualifier_list -> specifier_qualifier_list type_specifier_no_typeid','specifier_qualifier_list',2,'p_specifier_qualifier_list_1','c_parser.py',883),\n  ('specifier_qualifier_list -> specifier_qualifier_list type_qualifier','specifier_qualifier_list',2,'p_specifier_qualifier_list_2','c_parser.py',888),\n  ('specifier_qualifier_list -> type_specifier','specifier_qualifier_list',1,'p_specifier_qualifier_list_3','c_parser.py',893),\n  ('specifier_qualifier_list -> type_qualifier_list type_specifier','specifier_qualifier_list',2,'p_specifier_qualifier_list_4','c_parser.py',898),\n  ('struct_or_union_specifier -> struct_or_union ID','struct_or_union_specifier',2,'p_struct_or_union_specifier_1','c_parser.py',907),\n  ('struct_or_union_specifier -> struct_or_union TYPEID','struct_or_union_specifier',2,'p_struct_or_union_specifier_1','c_parser.py',908),\n  ('struct_or_union_specifier -> struct_or_union brace_open struct_declaration_list brace_close','struct_or_union_specifier',4,'p_struct_or_union_specifier_2','c_parser.py',918),\n  ('struct_or_union_specifier -> struct_or_union brace_open brace_close','struct_or_union_specifier',3,'p_struct_or_union_specifier_2','c_parser.py',919),\n  ('struct_or_union_specifier -> struct_or_union ID brace_open struct_declaration_list brace_close','struct_or_union_specifier',5,'p_struct_or_union_specifier_3','c_parser.py',936),\n  ('struct_or_union_specifier -> struct_or_union ID brace_open brace_close','struct_or_union_specifier',4,'p_struct_or_union_specifier_3','c_parser.py',937),\n  ('struct_or_union_specifier -> struct_or_union TYPEID brace_open struct_declaration_list brace_close','struct_or_union_specifier',5,'p_struct_or_union_specifier_3','c_parser.py',938),\n  ('struct_or_union_specifier -> struct_or_union TYPEID brace_open brace_close','struct_or_union_specifier',4,'p_struct_or_union_specifier_3','c_parser.py',939),\n  ('struct_or_union -> STRUCT','struct_or_union',1,'p_struct_or_union','c_parser.py',955),\n  ('struct_or_union -> UNION','struct_or_union',1,'p_struct_or_union','c_parser.py',956),\n  ('struct_declaration_list -> struct_declaration','struct_declaration_list',1,'p_struct_declaration_list','c_parser.py',963),\n  ('struct_declaration_list -> struct_declaration_list struct_declaration','struct_declaration_list',2,'p_struct_declaration_list','c_parser.py',964),\n  ('struct_declaration -> specifier_qualifier_list struct_declarator_list_opt SEMI','struct_declaration',3,'p_struct_declaration_1','c_parser.py',972),\n  ('struct_declaration -> SEMI','struct_declaration',1,'p_struct_declaration_2','c_parser.py',1010),\n  ('struct_declaration -> pppragma_directive','struct_declaration',1,'p_struct_declaration_3','c_parser.py',1015),\n  ('struct_declarator_list -> struct_declarator','struct_declarator_list',1,'p_struct_declarator_list','c_parser.py',1020),\n  ('struct_declarator_list -> struct_declarator_list COMMA struct_declarator','struct_declarator_list',3,'p_struct_declarator_list','c_parser.py',1021),\n  ('struct_declarator -> declarator','struct_declarator',1,'p_struct_declarator_1','c_parser.py',1029),\n  ('struct_declarator -> declarator COLON constant_expression','struct_declarator',3,'p_struct_declarator_2','c_parser.py',1034),\n  ('struct_declarator -> COLON constant_expression','struct_declarator',2,'p_struct_declarator_2','c_parser.py',1035),\n  ('enum_specifier -> ENUM ID','enum_specifier',2,'p_enum_specifier_1','c_parser.py',1043),\n  ('enum_specifier -> ENUM TYPEID','enum_specifier',2,'p_enum_specifier_1','c_parser.py',1044),\n  ('enum_specifier -> ENUM brace_open enumerator_list brace_close','enum_specifier',4,'p_enum_specifier_2','c_parser.py',1049),\n  ('enum_specifier -> ENUM ID brace_open enumerator_list brace_close','enum_specifier',5,'p_enum_specifier_3','c_parser.py',1054),\n  ('enum_specifier -> ENUM TYPEID brace_open enumerator_list brace_close','enum_specifier',5,'p_enum_specifier_3','c_parser.py',1055),\n  ('enumerator_list -> enumerator','enumerator_list',1,'p_enumerator_list','c_parser.py',1060),\n  ('enumerator_list -> enumerator_list COMMA','enumerator_list',2,'p_enumerator_list','c_parser.py',1061),\n  ('enumerator_list -> enumerator_list COMMA enumerator','enumerator_list',3,'p_enumerator_list','c_parser.py',1062),\n  ('enumerator -> ID','enumerator',1,'p_enumerator','c_parser.py',1073),\n  ('enumerator -> ID EQUALS constant_expression','enumerator',3,'p_enumerator','c_parser.py',1074),\n  ('declarator -> id_declarator','declarator',1,'p_declarator','c_parser.py',1089),\n  ('declarator -> typeid_declarator','declarator',1,'p_declarator','c_parser.py',1090),\n  ('pointer -> TIMES type_qualifier_list_opt','pointer',2,'p_pointer','c_parser.py',1201),\n  ('pointer -> TIMES type_qualifier_list_opt pointer','pointer',3,'p_pointer','c_parser.py',1202),\n  ('type_qualifier_list -> type_qualifier','type_qualifier_list',1,'p_type_qualifier_list','c_parser.py',1231),\n  ('type_qualifier_list -> type_qualifier_list type_qualifier','type_qualifier_list',2,'p_type_qualifier_list','c_parser.py',1232),\n  ('parameter_type_list -> parameter_list','parameter_type_list',1,'p_parameter_type_list','c_parser.py',1237),\n  ('parameter_type_list -> parameter_list COMMA ELLIPSIS','parameter_type_list',3,'p_parameter_type_list','c_parser.py',1238),\n  ('parameter_list -> parameter_declaration','parameter_list',1,'p_parameter_list','c_parser.py',1246),\n  ('parameter_list -> parameter_list COMMA parameter_declaration','parameter_list',3,'p_parameter_list','c_parser.py',1247),\n  ('parameter_declaration -> declaration_specifiers id_declarator','parameter_declaration',2,'p_parameter_declaration_1','c_parser.py',1266),\n  ('parameter_declaration -> declaration_specifiers typeid_noparen_declarator','parameter_declaration',2,'p_parameter_declaration_1','c_parser.py',1267),\n  ('parameter_declaration -> declaration_specifiers abstract_declarator_opt','parameter_declaration',2,'p_parameter_declaration_2','c_parser.py',1278),\n  ('identifier_list -> identifier','identifier_list',1,'p_identifier_list','c_parser.py',1309),\n  ('identifier_list -> identifier_list COMMA identifier','identifier_list',3,'p_identifier_list','c_parser.py',1310),\n  ('initializer -> assignment_expression','initializer',1,'p_initializer_1','c_parser.py',1319),\n  ('initializer -> brace_open initializer_list_opt brace_close','initializer',3,'p_initializer_2','c_parser.py',1324),\n  ('initializer -> brace_open initializer_list COMMA brace_close','initializer',4,'p_initializer_2','c_parser.py',1325),\n  ('initializer_list -> designation_opt initializer','initializer_list',2,'p_initializer_list','c_parser.py',1333),\n  ('initializer_list -> initializer_list COMMA designation_opt initializer','initializer_list',4,'p_initializer_list','c_parser.py',1334),\n  ('designation -> designator_list EQUALS','designation',2,'p_designation','c_parser.py',1345),\n  ('designator_list -> designator','designator_list',1,'p_designator_list','c_parser.py',1353),\n  ('designator_list -> designator_list designator','designator_list',2,'p_designator_list','c_parser.py',1354),\n  ('designator -> LBRACKET constant_expression RBRACKET','designator',3,'p_designator','c_parser.py',1359),\n  ('designator -> PERIOD identifier','designator',2,'p_designator','c_parser.py',1360),\n  ('type_name -> specifier_qualifier_list abstract_declarator_opt','type_name',2,'p_type_name','c_parser.py',1365),\n  ('abstract_declarator -> pointer','abstract_declarator',1,'p_abstract_declarator_1','c_parser.py',1376),\n  ('abstract_declarator -> pointer direct_abstract_declarator','abstract_declarator',2,'p_abstract_declarator_2','c_parser.py',1384),\n  ('abstract_declarator -> direct_abstract_declarator','abstract_declarator',1,'p_abstract_declarator_3','c_parser.py',1389),\n  ('direct_abstract_declarator -> LPAREN abstract_declarator RPAREN','direct_abstract_declarator',3,'p_direct_abstract_declarator_1','c_parser.py',1399),\n  ('direct_abstract_declarator -> direct_abstract_declarator LBRACKET assignment_expression_opt RBRACKET','direct_abstract_declarator',4,'p_direct_abstract_declarator_2','c_parser.py',1403),\n  ('direct_abstract_declarator -> LBRACKET assignment_expression_opt RBRACKET','direct_abstract_declarator',3,'p_direct_abstract_declarator_3','c_parser.py',1414),\n  ('direct_abstract_declarator -> direct_abstract_declarator LBRACKET TIMES RBRACKET','direct_abstract_declarator',4,'p_direct_abstract_declarator_4','c_parser.py',1423),\n  ('direct_abstract_declarator -> LBRACKET TIMES RBRACKET','direct_abstract_declarator',3,'p_direct_abstract_declarator_5','c_parser.py',1434),\n  ('direct_abstract_declarator -> direct_abstract_declarator LPAREN parameter_type_list_opt RPAREN','direct_abstract_declarator',4,'p_direct_abstract_declarator_6','c_parser.py',1443),\n  ('direct_abstract_declarator -> LPAREN parameter_type_list_opt RPAREN','direct_abstract_declarator',3,'p_direct_abstract_declarator_7','c_parser.py',1453),\n  ('block_item -> declaration','block_item',1,'p_block_item','c_parser.py',1464),\n  ('block_item -> statement','block_item',1,'p_block_item','c_parser.py',1465),\n  ('block_item_list -> block_item','block_item_list',1,'p_block_item_list','c_parser.py',1472),\n  ('block_item_list -> block_item_list block_item','block_item_list',2,'p_block_item_list','c_parser.py',1473),\n  ('compound_statement -> brace_open block_item_list_opt brace_close','compound_statement',3,'p_compound_statement_1','c_parser.py',1479),\n  ('labeled_statement -> ID COLON pragmacomp_or_statement','labeled_statement',3,'p_labeled_statement_1','c_parser.py',1485),\n  ('labeled_statement -> CASE constant_expression COLON pragmacomp_or_statement','labeled_statement',4,'p_labeled_statement_2','c_parser.py',1489),\n  ('labeled_statement -> DEFAULT COLON pragmacomp_or_statement','labeled_statement',3,'p_labeled_statement_3','c_parser.py',1493),\n  ('selection_statement -> IF LPAREN expression RPAREN pragmacomp_or_statement','selection_statement',5,'p_selection_statement_1','c_parser.py',1497),\n  ('selection_statement -> IF LPAREN expression RPAREN statement ELSE pragmacomp_or_statement','selection_statement',7,'p_selection_statement_2','c_parser.py',1501),\n  ('selection_statement -> SWITCH LPAREN expression RPAREN pragmacomp_or_statement','selection_statement',5,'p_selection_statement_3','c_parser.py',1505),\n  ('iteration_statement -> WHILE LPAREN expression RPAREN pragmacomp_or_statement','iteration_statement',5,'p_iteration_statement_1','c_parser.py',1510),\n  ('iteration_statement -> DO pragmacomp_or_statement WHILE LPAREN expression RPAREN SEMI','iteration_statement',7,'p_iteration_statement_2','c_parser.py',1514),\n  ('iteration_statement -> FOR LPAREN expression_opt SEMI expression_opt SEMI expression_opt RPAREN pragmacomp_or_statement','iteration_statement',9,'p_iteration_statement_3','c_parser.py',1518),\n  ('iteration_statement -> FOR LPAREN declaration expression_opt SEMI expression_opt RPAREN pragmacomp_or_statement','iteration_statement',8,'p_iteration_statement_4','c_parser.py',1522),\n  ('jump_statement -> GOTO ID SEMI','jump_statement',3,'p_jump_statement_1','c_parser.py',1527),\n  ('jump_statement -> BREAK SEMI','jump_statement',2,'p_jump_statement_2','c_parser.py',1531),\n  ('jump_statement -> CONTINUE SEMI','jump_statement',2,'p_jump_statement_3','c_parser.py',1535),\n  ('jump_statement -> RETURN expression SEMI','jump_statement',3,'p_jump_statement_4','c_parser.py',1539),\n  ('jump_statement -> RETURN SEMI','jump_statement',2,'p_jump_statement_4','c_parser.py',1540),\n  ('expression_statement -> expression_opt SEMI','expression_statement',2,'p_expression_statement','c_parser.py',1545),\n  ('expression -> assignment_expression','expression',1,'p_expression','c_parser.py',1552),\n  ('expression -> expression COMMA assignment_expression','expression',3,'p_expression','c_parser.py',1553),\n  ('typedef_name -> TYPEID','typedef_name',1,'p_typedef_name','c_parser.py',1565),\n  ('assignment_expression -> conditional_expression','assignment_expression',1,'p_assignment_expression','c_parser.py',1569),\n  ('assignment_expression -> unary_expression assignment_operator assignment_expression','assignment_expression',3,'p_assignment_expression','c_parser.py',1570),\n  ('assignment_operator -> EQUALS','assignment_operator',1,'p_assignment_operator','c_parser.py',1583),\n  ('assignment_operator -> XOREQUAL','assignment_operator',1,'p_assignment_operator','c_parser.py',1584),\n  ('assignment_operator -> TIMESEQUAL','assignment_operator',1,'p_assignment_operator','c_parser.py',1585),\n  ('assignment_operator -> DIVEQUAL','assignment_operator',1,'p_assignment_operator','c_parser.py',1586),\n  ('assignment_operator -> MODEQUAL','assignment_operator',1,'p_assignment_operator','c_parser.py',1587),\n  ('assignment_operator -> PLUSEQUAL','assignment_operator',1,'p_assignment_operator','c_parser.py',1588),\n  ('assignment_operator -> MINUSEQUAL','assignment_operator',1,'p_assignment_operator','c_parser.py',1589),\n  ('assignment_operator -> LSHIFTEQUAL','assignment_operator',1,'p_assignment_operator','c_parser.py',1590),\n  ('assignment_operator -> RSHIFTEQUAL','assignment_operator',1,'p_assignment_operator','c_parser.py',1591),\n  ('assignment_operator -> ANDEQUAL','assignment_operator',1,'p_assignment_operator','c_parser.py',1592),\n  ('assignment_operator -> OREQUAL','assignment_operator',1,'p_assignment_operator','c_parser.py',1593),\n  ('constant_expression -> conditional_expression','constant_expression',1,'p_constant_expression','c_parser.py',1598),\n  ('conditional_expression -> binary_expression','conditional_expression',1,'p_conditional_expression','c_parser.py',1602),\n  ('conditional_expression -> binary_expression CONDOP expression COLON conditional_expression','conditional_expression',5,'p_conditional_expression','c_parser.py',1603),\n  ('binary_expression -> cast_expression','binary_expression',1,'p_binary_expression','c_parser.py',1611),\n  ('binary_expression -> binary_expression TIMES binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1612),\n  ('binary_expression -> binary_expression DIVIDE binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1613),\n  ('binary_expression -> binary_expression MOD binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1614),\n  ('binary_expression -> binary_expression PLUS binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1615),\n  ('binary_expression -> binary_expression MINUS binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1616),\n  ('binary_expression -> binary_expression RSHIFT binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1617),\n  ('binary_expression -> binary_expression LSHIFT binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1618),\n  ('binary_expression -> binary_expression LT binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1619),\n  ('binary_expression -> binary_expression LE binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1620),\n  ('binary_expression -> binary_expression GE binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1621),\n  ('binary_expression -> binary_expression GT binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1622),\n  ('binary_expression -> binary_expression EQ binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1623),\n  ('binary_expression -> binary_expression NE binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1624),\n  ('binary_expression -> binary_expression AND binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1625),\n  ('binary_expression -> binary_expression OR binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1626),\n  ('binary_expression -> binary_expression XOR binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1627),\n  ('binary_expression -> binary_expression LAND binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1628),\n  ('binary_expression -> binary_expression LOR binary_expression','binary_expression',3,'p_binary_expression','c_parser.py',1629),\n  ('cast_expression -> unary_expression','cast_expression',1,'p_cast_expression_1','c_parser.py',1637),\n  ('cast_expression -> LPAREN type_name RPAREN cast_expression','cast_expression',4,'p_cast_expression_2','c_parser.py',1641),\n  ('unary_expression -> postfix_expression','unary_expression',1,'p_unary_expression_1','c_parser.py',1645),\n  ('unary_expression -> PLUSPLUS unary_expression','unary_expression',2,'p_unary_expression_2','c_parser.py',1649),\n  ('unary_expression -> MINUSMINUS unary_expression','unary_expression',2,'p_unary_expression_2','c_parser.py',1650),\n  ('unary_expression -> unary_operator cast_expression','unary_expression',2,'p_unary_expression_2','c_parser.py',1651),\n  ('unary_expression -> SIZEOF unary_expression','unary_expression',2,'p_unary_expression_3','c_parser.py',1656),\n  ('unary_expression -> SIZEOF LPAREN type_name RPAREN','unary_expression',4,'p_unary_expression_3','c_parser.py',1657),\n  ('unary_operator -> AND','unary_operator',1,'p_unary_operator','c_parser.py',1665),\n  ('unary_operator -> TIMES','unary_operator',1,'p_unary_operator','c_parser.py',1666),\n  ('unary_operator -> PLUS','unary_operator',1,'p_unary_operator','c_parser.py',1667),\n  ('unary_operator -> MINUS','unary_operator',1,'p_unary_operator','c_parser.py',1668),\n  ('unary_operator -> NOT','unary_operator',1,'p_unary_operator','c_parser.py',1669),\n  ('unary_operator -> LNOT','unary_operator',1,'p_unary_operator','c_parser.py',1670),\n  ('postfix_expression -> primary_expression','postfix_expression',1,'p_postfix_expression_1','c_parser.py',1675),\n  ('postfix_expression -> postfix_expression LBRACKET expression RBRACKET','postfix_expression',4,'p_postfix_expression_2','c_parser.py',1679),\n  ('postfix_expression -> postfix_expression LPAREN argument_expression_list RPAREN','postfix_expression',4,'p_postfix_expression_3','c_parser.py',1683),\n  ('postfix_expression -> postfix_expression LPAREN RPAREN','postfix_expression',3,'p_postfix_expression_3','c_parser.py',1684),\n  ('postfix_expression -> postfix_expression PERIOD ID','postfix_expression',3,'p_postfix_expression_4','c_parser.py',1689),\n  ('postfix_expression -> postfix_expression PERIOD TYPEID','postfix_expression',3,'p_postfix_expression_4','c_parser.py',1690),\n  ('postfix_expression -> postfix_expression ARROW ID','postfix_expression',3,'p_postfix_expression_4','c_parser.py',1691),\n  ('postfix_expression -> postfix_expression ARROW TYPEID','postfix_expression',3,'p_postfix_expression_4','c_parser.py',1692),\n  ('postfix_expression -> postfix_expression PLUSPLUS','postfix_expression',2,'p_postfix_expression_5','c_parser.py',1698),\n  ('postfix_expression -> postfix_expression MINUSMINUS','postfix_expression',2,'p_postfix_expression_5','c_parser.py',1699),\n  ('postfix_expression -> LPAREN type_name RPAREN brace_open initializer_list brace_close','postfix_expression',6,'p_postfix_expression_6','c_parser.py',1704),\n  ('postfix_expression -> LPAREN type_name RPAREN brace_open initializer_list COMMA brace_close','postfix_expression',7,'p_postfix_expression_6','c_parser.py',1705),\n  ('primary_expression -> identifier','primary_expression',1,'p_primary_expression_1','c_parser.py',1710),\n  ('primary_expression -> constant','primary_expression',1,'p_primary_expression_2','c_parser.py',1714),\n  ('primary_expression -> unified_string_literal','primary_expression',1,'p_primary_expression_3','c_parser.py',1718),\n  ('primary_expression -> unified_wstring_literal','primary_expression',1,'p_primary_expression_3','c_parser.py',1719),\n  ('primary_expression -> LPAREN expression RPAREN','primary_expression',3,'p_primary_expression_4','c_parser.py',1724),\n  ('primary_expression -> OFFSETOF LPAREN type_name COMMA offsetof_member_designator RPAREN','primary_expression',6,'p_primary_expression_5','c_parser.py',1728),\n  ('offsetof_member_designator -> identifier','offsetof_member_designator',1,'p_offsetof_member_designator','c_parser.py',1736),\n  ('offsetof_member_designator -> offsetof_member_designator PERIOD identifier','offsetof_member_designator',3,'p_offsetof_member_designator','c_parser.py',1737),\n  ('offsetof_member_designator -> offsetof_member_designator LBRACKET expression RBRACKET','offsetof_member_designator',4,'p_offsetof_member_designator','c_parser.py',1738),\n  ('argument_expression_list -> assignment_expression','argument_expression_list',1,'p_argument_expression_list','c_parser.py',1751),\n  ('argument_expression_list -> argument_expression_list COMMA assignment_expression','argument_expression_list',3,'p_argument_expression_list','c_parser.py',1752),\n  ('identifier -> ID','identifier',1,'p_identifier','c_parser.py',1761),\n  ('constant -> INT_CONST_DEC','constant',1,'p_constant_1','c_parser.py',1765),\n  ('constant -> INT_CONST_OCT','constant',1,'p_constant_1','c_parser.py',1766),\n  ('constant -> INT_CONST_HEX','constant',1,'p_constant_1','c_parser.py',1767),\n  ('constant -> INT_CONST_BIN','constant',1,'p_constant_1','c_parser.py',1768),\n  ('constant -> FLOAT_CONST','constant',1,'p_constant_2','c_parser.py',1774),\n  ('constant -> HEX_FLOAT_CONST','constant',1,'p_constant_2','c_parser.py',1775),\n  ('constant -> CHAR_CONST','constant',1,'p_constant_3','c_parser.py',1791),\n  ('constant -> WCHAR_CONST','constant',1,'p_constant_3','c_parser.py',1792),\n  ('unified_string_literal -> STRING_LITERAL','unified_string_literal',1,'p_unified_string_literal','c_parser.py',1803),\n  ('unified_string_literal -> unified_string_literal STRING_LITERAL','unified_string_literal',2,'p_unified_string_literal','c_parser.py',1804),\n  ('unified_wstring_literal -> WSTRING_LITERAL','unified_wstring_literal',1,'p_unified_wstring_literal','c_parser.py',1814),\n  ('unified_wstring_literal -> unified_wstring_literal WSTRING_LITERAL','unified_wstring_literal',2,'p_unified_wstring_literal','c_parser.py',1815),\n  ('brace_open -> LBRACE','brace_open',1,'p_brace_open','c_parser.py',1825),\n  ('brace_close -> RBRACE','brace_close',1,'p_brace_close','c_parser.py',1831),\n  ('empty -> <empty>','empty',0,'p_empty','c_parser.py',1837),\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser-2.19-py3.6.egg-info/PKG-INFO",
    "content": "Metadata-Version: 1.2\nName: pycparser\nVersion: 2.19\nSummary: C parser in Python\nHome-page: https://github.com/eliben/pycparser\nAuthor: Eli Bendersky\nAuthor-email: eliben@gmail.com\nMaintainer: Eli Bendersky\nLicense: BSD\nDescription: \n                pycparser is a complete parser of the C language, written in\n                pure Python using the PLY parsing library.\n                It parses C code into an AST and can serve as a front-end for\n                C compilers or analysis tools.\n            \nPlatform: Cross Platform\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: License :: OSI Approved :: BSD License\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nRequires-Python: >=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser-2.19-py3.6.egg-info/SOURCES.txt",
    "content": "CHANGES\nLICENSE\nMANIFEST.in\nREADME.rst\nsetup.cfg\nsetup.py\nexamples/c-to-c.py\nexamples/c_json.py\nexamples/cdecl.py\nexamples/dump_ast.py\nexamples/explore_ast.py\nexamples/func_calls.py\nexamples/func_defs.py\nexamples/rewrite_ast.py\nexamples/serialize_ast.py\nexamples/using_cpp_libc.py\nexamples/using_gcc_E_libc.py\nexamples/c_files/funky.c\nexamples/c_files/hash.c\nexamples/c_files/memmgr.c\nexamples/c_files/memmgr.h\nexamples/c_files/year.c\npycparser/__init__.py\npycparser/_ast_gen.py\npycparser/_build_tables.py\npycparser/_c_ast.cfg\npycparser/ast_transforms.py\npycparser/c_ast.py\npycparser/c_generator.py\npycparser/c_lexer.py\npycparser/c_parser.py\npycparser/lextab.py\npycparser/plyparser.py\npycparser/yacctab.py\npycparser.egg-info/PKG-INFO\npycparser.egg-info/SOURCES.txt\npycparser.egg-info/dependency_links.txt\npycparser.egg-info/top_level.txt\npycparser/ply/__init__.py\npycparser/ply/cpp.py\npycparser/ply/ctokens.py\npycparser/ply/lex.py\npycparser/ply/yacc.py\npycparser/ply/ygen.py\ntests/all_tests.py\ntests/test_c_ast.py\ntests/test_c_generator.py\ntests/test_c_lexer.py\ntests/test_c_parser.py\ntests/test_general.py\ntests/c_files/cppd_with_stdio_h.c\ntests/c_files/empty.h\ntests/c_files/example_c_file.c\ntests/c_files/memmgr.c\ntests/c_files/memmgr.h\ntests/c_files/memmgr_with_h.c\ntests/c_files/simplemain.c\ntests/c_files/year.c\ntests/c_files/hdir/9/inc.h\nutils/fake_libc_include/_ansi.h\nutils/fake_libc_include/_fake_defines.h\nutils/fake_libc_include/_fake_typedefs.h\nutils/fake_libc_include/_syslist.h\nutils/fake_libc_include/aio.h\nutils/fake_libc_include/alloca.h\nutils/fake_libc_include/ar.h\nutils/fake_libc_include/argz.h\nutils/fake_libc_include/assert.h\nutils/fake_libc_include/complex.h\nutils/fake_libc_include/cpio.h\nutils/fake_libc_include/ctype.h\nutils/fake_libc_include/dirent.h\nutils/fake_libc_include/dlfcn.h\nutils/fake_libc_include/endian.h\nutils/fake_libc_include/envz.h\nutils/fake_libc_include/errno.h\nutils/fake_libc_include/fastmath.h\nutils/fake_libc_include/fcntl.h\nutils/fake_libc_include/features.h\nutils/fake_libc_include/fenv.h\nutils/fake_libc_include/float.h\nutils/fake_libc_include/fmtmsg.h\nutils/fake_libc_include/fnmatch.h\nutils/fake_libc_include/ftw.h\nutils/fake_libc_include/getopt.h\nutils/fake_libc_include/glob.h\nutils/fake_libc_include/grp.h\nutils/fake_libc_include/iconv.h\nutils/fake_libc_include/ieeefp.h\nutils/fake_libc_include/inttypes.h\nutils/fake_libc_include/iso646.h\nutils/fake_libc_include/langinfo.h\nutils/fake_libc_include/libgen.h\nutils/fake_libc_include/libintl.h\nutils/fake_libc_include/limits.h\nutils/fake_libc_include/locale.h\nutils/fake_libc_include/malloc.h\nutils/fake_libc_include/math.h\nutils/fake_libc_include/monetary.h\nutils/fake_libc_include/mqueue.h\nutils/fake_libc_include/ndbm.h\nutils/fake_libc_include/netdb.h\nutils/fake_libc_include/newlib.h\nutils/fake_libc_include/nl_types.h\nutils/fake_libc_include/paths.h\nutils/fake_libc_include/poll.h\nutils/fake_libc_include/process.h\nutils/fake_libc_include/pthread.h\nutils/fake_libc_include/pwd.h\nutils/fake_libc_include/reent.h\nutils/fake_libc_include/regdef.h\nutils/fake_libc_include/regex.h\nutils/fake_libc_include/sched.h\nutils/fake_libc_include/search.h\nutils/fake_libc_include/semaphore.h\nutils/fake_libc_include/setjmp.h\nutils/fake_libc_include/signal.h\nutils/fake_libc_include/spawn.h\nutils/fake_libc_include/stdarg.h\nutils/fake_libc_include/stdbool.h\nutils/fake_libc_include/stddef.h\nutils/fake_libc_include/stdint.h\nutils/fake_libc_include/stdio.h\nutils/fake_libc_include/stdlib.h\nutils/fake_libc_include/string.h\nutils/fake_libc_include/strings.h\nutils/fake_libc_include/stropts.h\nutils/fake_libc_include/syslog.h\nutils/fake_libc_include/tar.h\nutils/fake_libc_include/termios.h\nutils/fake_libc_include/tgmath.h\nutils/fake_libc_include/time.h\nutils/fake_libc_include/trace.h\nutils/fake_libc_include/ulimit.h\nutils/fake_libc_include/unctrl.h\nutils/fake_libc_include/unistd.h\nutils/fake_libc_include/utime.h\nutils/fake_libc_include/utmp.h\nutils/fake_libc_include/utmpx.h\nutils/fake_libc_include/wchar.h\nutils/fake_libc_include/wctype.h\nutils/fake_libc_include/wordexp.h\nutils/fake_libc_include/zlib.h\nutils/fake_libc_include/X11/Intrinsic.h\nutils/fake_libc_include/X11/Xlib.h\nutils/fake_libc_include/X11/_X11_fake_defines.h\nutils/fake_libc_include/X11/_X11_fake_typedefs.h\nutils/fake_libc_include/arpa/inet.h\nutils/fake_libc_include/asm-generic/int-ll64.h\nutils/fake_libc_include/linux/socket.h\nutils/fake_libc_include/linux/version.h\nutils/fake_libc_include/mir_toolkit/client_types.h\nutils/fake_libc_include/net/if.h\nutils/fake_libc_include/netinet/in.h\nutils/fake_libc_include/netinet/tcp.h\nutils/fake_libc_include/openssl/err.h\nutils/fake_libc_include/openssl/evp.h\nutils/fake_libc_include/openssl/hmac.h\nutils/fake_libc_include/openssl/ssl.h\nutils/fake_libc_include/openssl/x509v3.h\nutils/fake_libc_include/sys/ioctl.h\nutils/fake_libc_include/sys/ipc.h\nutils/fake_libc_include/sys/mman.h\nutils/fake_libc_include/sys/msg.h\nutils/fake_libc_include/sys/poll.h\nutils/fake_libc_include/sys/resource.h\nutils/fake_libc_include/sys/select.h\nutils/fake_libc_include/sys/sem.h\nutils/fake_libc_include/sys/shm.h\nutils/fake_libc_include/sys/socket.h\nutils/fake_libc_include/sys/stat.h\nutils/fake_libc_include/sys/statvfs.h\nutils/fake_libc_include/sys/sysctl.h\nutils/fake_libc_include/sys/time.h\nutils/fake_libc_include/sys/times.h\nutils/fake_libc_include/sys/types.h\nutils/fake_libc_include/sys/uio.h\nutils/fake_libc_include/sys/un.h\nutils/fake_libc_include/sys/utsname.h\nutils/fake_libc_include/sys/wait.h\nutils/fake_libc_include/xcb/xcb.h"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser-2.19-py3.6.egg-info/dependency_links.txt",
    "content": "\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser-2.19-py3.6.egg-info/installed-files.txt",
    "content": "../pycparser/__init__.py\n../pycparser/__pycache__/__init__.cpython-36.pyc\n../pycparser/__pycache__/_ast_gen.cpython-36.pyc\n../pycparser/__pycache__/_build_tables.cpython-36.pyc\n../pycparser/__pycache__/ast_transforms.cpython-36.pyc\n../pycparser/__pycache__/c_ast.cpython-36.pyc\n../pycparser/__pycache__/c_generator.cpython-36.pyc\n../pycparser/__pycache__/c_lexer.cpython-36.pyc\n../pycparser/__pycache__/c_parser.cpython-36.pyc\n../pycparser/__pycache__/lextab.cpython-36.pyc\n../pycparser/__pycache__/plyparser.cpython-36.pyc\n../pycparser/__pycache__/yacctab.cpython-36.pyc\n../pycparser/_ast_gen.py\n../pycparser/_build_tables.py\n../pycparser/_c_ast.cfg\n../pycparser/ast_transforms.py\n../pycparser/c_ast.py\n../pycparser/c_generator.py\n../pycparser/c_lexer.py\n../pycparser/c_parser.py\n../pycparser/lextab.py\n../pycparser/ply/__init__.py\n../pycparser/ply/__pycache__/__init__.cpython-36.pyc\n../pycparser/ply/__pycache__/cpp.cpython-36.pyc\n../pycparser/ply/__pycache__/ctokens.cpython-36.pyc\n../pycparser/ply/__pycache__/lex.cpython-36.pyc\n../pycparser/ply/__pycache__/yacc.cpython-36.pyc\n../pycparser/ply/__pycache__/ygen.cpython-36.pyc\n../pycparser/ply/cpp.py\n../pycparser/ply/ctokens.py\n../pycparser/ply/lex.py\n../pycparser/ply/yacc.py\n../pycparser/ply/ygen.py\n../pycparser/plyparser.py\n../pycparser/yacctab.py\nPKG-INFO\nSOURCES.txt\ndependency_links.txt\ntop_level.txt\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pycparser-2.19-py3.6.egg-info/top_level.txt",
    "content": "pycparser\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pydispatch/__init__.py",
    "content": "\"\"\"Multi-consumer multi-producer dispatching mechanism\n\"\"\"\n__version__ = \"2.0.5\"\n__author__ = \"Patrick K. O'Brien\"\n__license__ = \"BSD-style, see license.txt for details\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pydispatch/dispatcher.py",
    "content": "\"\"\"Multiple-producer-multiple-consumer signal-dispatching\n\ndispatcher is the core of the PyDispatcher system,\nproviding the primary API and the core logic for the\nsystem.\n\nModule attributes of note:\n\n    Any -- Singleton used to signal either \"Any Sender\" or\n        \"Any Signal\".  See documentation of the _Any class.\n    Anonymous -- Singleton used to signal \"Anonymous Sender\"\n        See documentation of the _Anonymous class.\n\nInternal attributes:\n    WEAKREF_TYPES -- tuple of types/classes which represent\n        weak references to receivers, and thus must be de-\n        referenced on retrieval to retrieve the callable\n        object\n    connections -- { senderkey (id) : { signal : [receivers...]}}\n    senders -- { senderkey (id) : weakref(sender) }\n        used for cleaning up sender references on sender\n        deletion\n    sendersBack -- { receiverkey (id) : [senderkey (id)...] }\n        used for cleaning up receiver references on receiver\n        deletion, (considerably speeds up the cleanup process\n        vs. the original code.)\n\"\"\"\nimport weakref\nfrom pydispatch import saferef, robustapply, errors\n\nclass _Parameter:\n    \"\"\"Used to represent default parameter values.\"\"\"\n    def __repr__(self):\n        return self.__class__.__name__\n\nclass _Any(_Parameter):\n    \"\"\"Singleton used to signal either \"Any Sender\" or \"Any Signal\"\n\n    The Any object can be used with connect, disconnect,\n    send, or sendExact to signal that the parameter given\n    Any should react to all senders/signals, not just\n    a particular sender/signal.\n    \"\"\"\nAny = _Any()\n\nclass _Anonymous(_Parameter):\n    \"\"\"Singleton used to signal \"Anonymous Sender\"\n\n    The Anonymous object is used to signal that the sender\n    of a message is not specified (as distinct from being\n    \"any sender\").  Registering callbacks for Anonymous\n    will only receive messages sent without senders.  Sending\n    with anonymous will only send messages to those receivers\n    registered for Any or Anonymous.\n\n    Note:\n        The default sender for connect is Any, while the\n        default sender for send is Anonymous.  This has\n        the effect that if you do not specify any senders\n        in either function then all messages are routed\n        as though there was a single sender (Anonymous)\n        being used everywhere.\n    \"\"\"\nAnonymous = _Anonymous()\n\nWEAKREF_TYPES = (weakref.ReferenceType, saferef.BoundMethodWeakref)\n\nconnections = {}\nsenders = {}\nsendersBack = {}\n\n\ndef connect(receiver, signal=Any, sender=Any, weak=True):\n    \"\"\"Connect receiver to sender for signal\n\n    receiver -- a callable Python object which is to receive\n        messages/signals/events.  Receivers must be hashable\n        objects.\n\n        if weak is True, then receiver must be weak-referencable\n        (more precisely saferef.safeRef() must be able to create\n        a reference to the receiver).\n    \n        Receivers are fairly flexible in their specification,\n        as the machinery in the robustApply module takes care\n        of most of the details regarding figuring out appropriate\n        subsets of the sent arguments to apply to a given\n        receiver.\n\n        Note:\n            if receiver is itself a weak reference (a callable),\n            it will be de-referenced by the system's machinery,\n            so *generally* weak references are not suitable as\n            receivers, though some use might be found for the\n            facility whereby a higher-level library passes in\n            pre-weakrefed receiver references.\n\n    signal -- the signal to which the receiver should respond\n    \n        if Any, receiver will receive any signal from the\n        indicated sender (which might also be Any, but is not\n        necessarily Any).\n        \n        Otherwise must be a hashable Python object other than\n        None (DispatcherError raised on None).\n        \n    sender -- the sender to which the receiver should respond\n    \n        if Any, receiver will receive the indicated signals\n        from any sender.\n        \n        if Anonymous, receiver will only receive indicated\n        signals from send/sendExact which do not specify a\n        sender, or specify Anonymous explicitly as the sender.\n\n        Otherwise can be any python object.\n        \n    weak -- whether to use weak references to the receiver\n        By default, the module will attempt to use weak\n        references to the receiver objects.  If this parameter\n        is false, then strong references will be used.\n\n    returns None, may raise DispatcherTypeError\n    \"\"\"\n    if signal is None:\n        raise errors.DispatcherTypeError(\n            'Signal cannot be None (receiver=%r sender=%r)'%( receiver,sender)\n        )\n    if weak:\n        receiver = saferef.safeRef(receiver, onDelete=_removeReceiver)\n    senderkey = id(sender)\n    if senderkey in connections:\n        signals = connections[senderkey]\n    else:\n        connections[senderkey] = signals = {}\n    # Keep track of senders for cleanup.\n    # Is Anonymous something we want to clean up?\n    if sender not in (None, Anonymous, Any):\n        def remove(object, senderkey=senderkey):\n            _removeSender(senderkey=senderkey)\n        # Skip objects that can not be weakly referenced, which means\n        # they won't be automatically cleaned up, but that's too bad.\n        try:\n            weakSender = weakref.ref(sender, remove)\n            senders[senderkey] = weakSender\n        except:\n            pass\n        \n    receiverID = id(receiver)\n    # get current set, remove any current references to\n    # this receiver in the set, including back-references\n    if signal in signals:\n        receivers = signals[signal]\n        _removeOldBackRefs(senderkey, signal, receiver, receivers)\n    else:\n        receivers = signals[signal] = []\n    try:\n        current = sendersBack.get( receiverID )\n        if current is None:\n            sendersBack[ receiverID ] = current = []\n        if senderkey not in current:\n            current.append(senderkey)\n    except:\n        pass\n\n    receivers.append(receiver)\n\n\n\ndef disconnect(receiver, signal=Any, sender=Any, weak=True):\n    \"\"\"Disconnect receiver from sender for signal\n\n    receiver -- the registered receiver to disconnect\n    signal -- the registered signal to disconnect\n    sender -- the registered sender to disconnect\n    weak -- the weakref state to disconnect\n\n    disconnect reverses the process of connect,\n    the semantics for the individual elements are\n    logically equivalent to a tuple of\n    (receiver, signal, sender, weak) used as a key\n    to be deleted from the internal routing tables.\n    (The actual process is slightly more complex\n    but the semantics are basically the same).\n\n    Note:\n        Using disconnect is not required to cleanup\n        routing when an object is deleted, the framework\n        will remove routes for deleted objects\n        automatically.  It's only necessary to disconnect\n        if you want to stop routing to a live object.\n        \n    returns None, may raise DispatcherTypeError or\n        DispatcherKeyError\n    \"\"\"\n    if signal is None:\n        raise errors.DispatcherTypeError(\n            'Signal cannot be None (receiver=%r sender=%r)'%( receiver,sender)\n        )\n    if weak: receiver = saferef.safeRef(receiver)\n    senderkey = id(sender)\n    try:\n        signals = connections[senderkey]\n        receivers = signals[signal]\n    except KeyError:\n        raise errors.DispatcherKeyError(\n            \"\"\"No receivers found for signal %r from sender %r\"\"\" %(\n                signal,\n                sender\n            )\n        )\n    try:\n        # also removes from receivers\n        _removeOldBackRefs(senderkey, signal, receiver, receivers)\n    except ValueError:\n        raise errors.DispatcherKeyError(\n            \"\"\"No connection to receiver %s for signal %s from sender %s\"\"\" %(\n                receiver,\n                signal,\n                sender\n            )\n        )\n    _cleanupConnections(senderkey, signal)\n\ndef getReceivers( sender = Any, signal = Any ):\n    \"\"\"Get list of receivers from global tables\n\n    This utility function allows you to retrieve the\n    raw list of receivers from the connections table\n    for the given sender and signal pair.\n\n    Note:\n        there is no guarantee that this is the actual list\n        stored in the connections table, so the value\n        should be treated as a simple iterable/truth value\n        rather than, for instance a list to which you\n        might append new records.\n\n    Normally you would use liveReceivers( getReceivers( ...))\n    to retrieve the actual receiver objects as an iterable\n    object.\n    \"\"\"\n    try:\n        return connections[id(sender)][signal]\n    except KeyError:\n        return []\n\ndef liveReceivers(receivers):\n    \"\"\"Filter sequence of receivers to get resolved, live receivers\n\n    This is a generator which will iterate over\n    the passed sequence, checking for weak references\n    and resolving them, then returning all live\n    receivers.\n    \"\"\"\n    for receiver in receivers:\n        if isinstance( receiver, WEAKREF_TYPES):\n            # Dereference the weak reference.\n            receiver = receiver()\n            if receiver is not None:\n                yield receiver\n        else:\n            yield receiver\n\n\n\ndef getAllReceivers( sender = Any, signal = Any ):\n    \"\"\"Get list of all receivers from global tables\n\n    This gets all receivers which should receive\n    the given signal from sender, each receiver should\n    be produced only once by the resulting generator\n    \"\"\"\n    receivers = {}\n    for set in (\n        # Get receivers that receive *this* signal from *this* sender.\n        getReceivers( sender, signal ),\n        # Add receivers that receive *any* signal from *this* sender.\n        getReceivers( sender, Any ),\n        # Add receivers that receive *this* signal from *any* sender.\n        getReceivers( Any, signal ),\n        # Add receivers that receive *any* signal from *any* sender.\n        getReceivers( Any, Any ),\n    ):\n        for receiver in set:\n            if receiver: # filter out dead instance-method weakrefs\n                try:\n                    if receiver not in receivers:\n                        receivers[receiver] = 1\n                        yield receiver\n                except TypeError:\n                    # dead weakrefs raise TypeError on hash...\n                    pass\n\ndef send(signal=Any, sender=Anonymous, *arguments, **named):\n    \"\"\"Send signal from sender to all connected receivers.\n    \n    signal -- (hashable) signal value, see connect for details\n\n    sender -- the sender of the signal\n    \n        if Any, only receivers registered for Any will receive\n        the message.\n\n        if Anonymous, only receivers registered to receive\n        messages from Anonymous or Any will receive the message\n\n        Otherwise can be any python object (normally one\n        registered with a connect if you actually want\n        something to occur).\n\n    arguments -- positional arguments which will be passed to\n        *all* receivers. Note that this may raise TypeErrors\n        if the receivers do not allow the particular arguments.\n        Note also that arguments are applied before named\n        arguments, so they should be used with care.\n\n    named -- named arguments which will be filtered according\n        to the parameters of the receivers to only provide those\n        acceptable to the receiver.\n\n    Return a list of tuple pairs [(receiver, response), ... ]\n\n    if any receiver raises an error, the error propagates back\n    through send, terminating the dispatch loop, so it is quite\n    possible to not have all receivers called if a raises an\n    error.\n    \"\"\"\n    # Call each receiver with whatever arguments it can accept.\n    # Return a list of tuple pairs [(receiver, response), ... ].\n    responses = []\n    for receiver in liveReceivers(getAllReceivers(sender, signal)):\n        response = robustapply.robustApply(\n            receiver,\n            signal=signal,\n            sender=sender,\n            *arguments,\n            **named\n        )\n        responses.append((receiver, response))\n    return responses\ndef sendExact( signal=Any, sender=Anonymous, *arguments, **named ):\n    \"\"\"Send signal only to those receivers registered for exact message\n\n    sendExact allows for avoiding Any/Anonymous registered\n    handlers, sending only to those receivers explicitly\n    registered for a particular signal on a particular\n    sender.\n    \"\"\"\n    responses = []\n    for receiver in liveReceivers(getReceivers(sender, signal)):\n        response = robustapply.robustApply(\n            receiver,\n            signal=signal,\n            sender=sender,\n            *arguments,\n            **named\n        )\n        responses.append((receiver, response))\n    return responses\n    \n\ndef _removeReceiver(receiver):\n    \"\"\"Remove receiver from connections.\"\"\"\n    if not sendersBack:\n        # During module cleanup the mapping will be replaced with None\n        return False\n    backKey = id(receiver)\n    try:\n        backSet = sendersBack.pop(backKey)\n    except KeyError:\n        return False \n    else:\n        for senderkey in backSet:\n            try:\n                signals = list(connections[senderkey].keys())\n            except KeyError:\n                pass\n            else:\n                for signal in signals:\n                    try:\n                        receivers = connections[senderkey][signal]\n                    except KeyError:\n                        pass\n                    else:\n                        try:\n                            receivers.remove( receiver )\n                        except Exception:\n                            pass\n                    _cleanupConnections(senderkey, signal)\n\ndef _cleanupConnections(senderkey, signal):\n    \"\"\"Delete any empty signals for senderkey. Delete senderkey if empty.\"\"\"\n    try:\n        receivers = connections[senderkey][signal]\n    except:\n        pass\n    else:\n        if not receivers:\n            # No more connected receivers. Therefore, remove the signal.\n            try:\n                signals = connections[senderkey]\n            except KeyError:\n                pass\n            else:\n                del signals[signal]\n                if not signals:\n                    # No more signal connections. Therefore, remove the sender.\n                    _removeSender(senderkey)\n\ndef _removeSender(senderkey):\n    \"\"\"Remove senderkey from connections.\"\"\"\n    _removeBackrefs(senderkey)\n    try:\n        del connections[senderkey]\n    except KeyError:\n        pass\n    # Senderkey will only be in senders dictionary if sender \n    # could be weakly referenced.\n    try: \n        del senders[senderkey]\n    except: \n        pass\n\n\ndef _removeBackrefs( senderkey):\n    \"\"\"Remove all back-references to this senderkey\"\"\"\n    try:\n        signals = connections[senderkey]\n    except KeyError:\n        signals = None\n    else:\n        items = signals.items()\n        def allReceivers( ):\n            for signal,set in items:\n                for item in set:\n                    yield item\n        for receiver in allReceivers():\n            _killBackref( receiver, senderkey )\n\ndef _removeOldBackRefs(senderkey, signal, receiver, receivers):\n    \"\"\"Kill old sendersBack references from receiver\n\n    This guards against multiple registration of the same\n    receiver for a given signal and sender leaking memory\n    as old back reference records build up.\n\n    Also removes old receiver instance from receivers\n    \"\"\"\n    try:\n        index = receivers.index(receiver)\n        # need to scan back references here and remove senderkey\n    except ValueError:\n        return False\n    else:\n        oldReceiver = receivers[index]\n        del receivers[index]\n        found = 0\n        signals = connections.get(signal)\n        if signals is not None:\n            for sig,recs in connections.get(signal,{}).items():\n                if sig != signal:\n                    for rec in recs:\n                        if rec is oldReceiver:\n                            found = 1\n                            break\n        if not found:\n            _killBackref( oldReceiver, senderkey )\n            return True\n        return False\n        \n        \ndef _killBackref( receiver, senderkey ):\n    \"\"\"Do the actual removal of back reference from receiver to senderkey\"\"\"\n    receiverkey = id(receiver)\n    set = sendersBack.get( receiverkey, () )\n    while senderkey in set:\n        try:\n            set.remove( senderkey )\n        except:\n            break\n    if not set:\n        try:\n            del sendersBack[ receiverkey ]\n        except KeyError:\n            pass\n    return True\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pydispatch/errors.py",
    "content": "\"\"\"Error types for dispatcher mechanism\n\"\"\"\n\nclass DispatcherError(Exception):\n    \"\"\"Base class for all Dispatcher errors\"\"\"\nclass DispatcherKeyError(KeyError, DispatcherError):\n    \"\"\"Error raised when unknown (sender,signal) set specified\"\"\"\nclass DispatcherTypeError(TypeError, DispatcherError):\n    \"\"\"Error raised when inappropriate signal-type specified (None)\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pydispatch/robust.py",
    "content": "\"\"\"Module implementing error-catching version of send (sendRobust)\"\"\"\nfrom pydispatch.dispatcher import Any, Anonymous, liveReceivers, getAllReceivers\nfrom pydispatch.robustapply import robustApply\n\ndef sendRobust(\n    signal=Any, \n    sender=Anonymous, \n    *arguments, **named\n):\n    \"\"\"Send signal from sender to all connected receivers catching errors\n    \n    signal -- (hashable) signal value, see connect for details\n\n    sender -- the sender of the signal\n    \n        if Any, only receivers registered for Any will receive\n        the message.\n\n        if Anonymous, only receivers registered to receive\n        messages from Anonymous or Any will receive the message\n\n        Otherwise can be any python object (normally one\n        registered with a connect if you actually want\n        something to occur).\n\n    arguments -- positional arguments which will be passed to\n        *all* receivers. Note that this may raise TypeErrors\n        if the receivers do not allow the particular arguments.\n        Note also that arguments are applied before named\n        arguments, so they should be used with care.\n\n    named -- named arguments which will be filtered according\n        to the parameters of the receivers to only provide those\n        acceptable to the receiver.\n\n    Return a list of tuple pairs [(receiver, response), ... ]\n\n    if any receiver raises an error (specifically any subclass of Exception),\n    the error instance is returned as the result for that receiver.\n    \"\"\"\n    # Call each receiver with whatever arguments it can accept.\n    # Return a list of tuple pairs [(receiver, response), ... ].\n    responses = []\n    for receiver in liveReceivers(getAllReceivers(sender, signal)):\n        try:\n            response = robustApply(\n                receiver,\n                signal=signal,\n                sender=sender,\n                *arguments,\n                **named\n            )\n        except Exception as err:\n            responses.append((receiver, err))\n        else:\n            responses.append((receiver, response))\n    return responses"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pydispatch/robustapply.py",
    "content": "\"\"\"Robust apply mechanism\n\nProvides a function \"call\", which can sort out\nwhat arguments a given callable object can take,\nand subset the given arguments to match only\nthose which are acceptable.\n\"\"\"\nimport sys\nif sys.hexversion >= 0x3000000:\n    im_func = '__func__'\n    im_self = '__self__'\n    im_code = '__code__'\n    func_code = '__code__'\nelse:\n    im_func = 'im_func'\n    im_self = 'im_self'\n    im_code = 'im_code'\n    func_code = 'func_code'\n\ndef function( receiver ):\n    \"\"\"Get function-like callable object for given receiver\n\n    returns (function_or_method, codeObject, fromMethod)\n\n    If fromMethod is true, then the callable already\n    has its first argument bound\n    \"\"\"\n    if hasattr(receiver, '__call__'):\n        # Reassign receiver to the actual method that will be called.\n        if hasattr( receiver.__call__, im_func) or hasattr( receiver.__call__, im_code):\n            receiver = receiver.__call__\n    if hasattr( receiver, im_func ):\n        # an instance-method...\n        return receiver, getattr(getattr(receiver, im_func), func_code), 1\n    elif not hasattr( receiver, func_code):\n        raise ValueError('unknown reciever type %s %s'%(receiver, type(receiver)))\n    return receiver, getattr(receiver,func_code), 0\n\ndef robustApply(receiver, *arguments, **named):\n    \"\"\"Call receiver with arguments and an appropriate subset of named\n    \"\"\"\n    receiver, codeObject, startIndex = function( receiver )\n    acceptable = codeObject.co_varnames[startIndex+len(arguments):codeObject.co_argcount]\n    for name in codeObject.co_varnames[startIndex:startIndex+len(arguments)]:\n        if name in named:\n            raise TypeError(\n                \"\"\"Argument %r specified both positionally and as a keyword for calling %r\"\"\"% (\n                    name, receiver,\n                )\n            )\n    if not (codeObject.co_flags & 8):\n        # fc does not have a **kwds type parameter, therefore \n        # remove unacceptable arguments.\n        named = dict([(k,v) for k,v in named.items() if k in acceptable])\n    return receiver(*arguments, **named)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pydispatch/saferef.py",
    "content": "\"\"\"Refactored \"safe reference\" from dispatcher.py\"\"\"\nimport weakref, traceback, sys\n\nif sys.hexversion >= 0x3000000:\n    im_func = '__func__'\n    im_self = '__self__'\nelse:\n    im_func = 'im_func'\n    im_self = 'im_self'\ndef safeRef(target, onDelete = None):\n    \"\"\"Return a *safe* weak reference to a callable target\n\n    target -- the object to be weakly referenced, if it's a\n        bound method reference, will create a BoundMethodWeakref,\n        otherwise creates a simple weakref.\n    onDelete -- if provided, will have a hard reference stored\n        to the callable to be called after the safe reference\n        goes out of scope with the reference object, (either a\n        weakref or a BoundMethodWeakref) as argument.\n    \"\"\"\n    if hasattr(target, im_self):\n        if getattr(target, im_self) is not None:\n            # Turn a bound method into a BoundMethodWeakref instance.\n            # Keep track of these instances for lookup by disconnect().\n            assert hasattr(target, im_func), \"\"\"safeRef target %r has %s, but no %s, don't know how to create reference\"\"\"%( target,im_self,im_func)\n            reference = BoundMethodWeakref(\n                target=target,\n                onDelete=onDelete\n            )\n            return reference\n    if onDelete is not None:\n        return weakref.ref(target, onDelete)\n    else:\n        return weakref.ref( target )\n\nclass BoundMethodWeakref(object):\n    \"\"\"'Safe' and reusable weak references to instance methods\n\n    BoundMethodWeakref objects provide a mechanism for\n    referencing a bound method without requiring that the\n    method object itself (which is normally a transient\n    object) is kept alive.  Instead, the BoundMethodWeakref\n    object keeps weak references to both the object and the\n    function which together define the instance method.\n\n    Attributes:\n        key -- the identity key for the reference, calculated\n            by the class's calculateKey method applied to the\n            target instance method\n        deletionMethods -- sequence of callable objects taking\n            single argument, a reference to this object which\n            will be called when *either* the target object or\n            target function is garbage collected (i.e. when\n            this object becomes invalid).  These are specified\n            as the onDelete parameters of safeRef calls.\n        weakSelf -- weak reference to the target object\n        weakFunc -- weak reference to the target function\n\n    Class Attributes:\n        _allInstances -- class attribute pointing to all live\n            BoundMethodWeakref objects indexed by the class's\n            calculateKey(target) method applied to the target\n            objects.  This weak value dictionary is used to\n            short-circuit creation so that multiple references\n            to the same (object, function) pair produce the\n            same BoundMethodWeakref instance.\n\n    \"\"\"\n    _allInstances = weakref.WeakValueDictionary()\n    def __new__( cls, target, onDelete=None, *arguments,**named ):\n        \"\"\"Create new instance or return current instance\n\n        Basically this method of construction allows us to\n        short-circuit creation of references to already-\n        referenced instance methods.  The key corresponding\n        to the target is calculated, and if there is already\n        an existing reference, that is returned, with its\n        deletionMethods attribute updated.  Otherwise the\n        new instance is created and registered in the table\n        of already-referenced methods.\n        \"\"\"\n        key = cls.calculateKey(target)\n        current =cls._allInstances.get(key)\n        if current is not None:\n            current.deletionMethods.append( onDelete)\n            return current\n        else:\n            base = super( BoundMethodWeakref, cls).__new__( cls )\n            cls._allInstances[key] = base\n            base.__init__( target, onDelete, *arguments,**named)\n            return base\n    def __init__(self, target, onDelete=None):\n        \"\"\"Return a weak-reference-like instance for a bound method\n\n        target -- the instance-method target for the weak\n            reference, must have <im_self> and <im_func> attributes\n            and be reconstructable via:\n                target.<im_func>.__get__( target.<im_self> )\n            which is true of built-in instance methods.\n        onDelete -- optional callback which will be called\n            when this weak reference ceases to be valid\n            (i.e. either the object or the function is garbage\n            collected).  Should take a single argument,\n            which will be passed a pointer to this object.\n        \"\"\"\n        def remove(weak, self=self):\n            \"\"\"Set self.isDead to true when method or instance is destroyed\"\"\"\n            methods = self.deletionMethods[:]\n            del self.deletionMethods[:]\n            try:\n                del self.__class__._allInstances[ self.key ]\n            except KeyError:\n                pass\n            for function in methods:\n                try:\n                    if hasattr(function, '__call__' ):\n                        function( self )\n                except Exception as e:\n                    try:\n                        traceback.print_exc()\n                    except AttributeError:\n                        print('''Exception during saferef %s cleanup function %s: %s'''%(\n                            self, function, e\n                        ))\n        self.deletionMethods = [onDelete]\n        self.key = self.calculateKey( target )\n        self.weakSelf = weakref.ref(getattr(target,im_self), remove)\n        self.weakFunc = weakref.ref(getattr(target,im_func), remove)\n        self.selfName = getattr(target,im_self).__class__.__name__\n        self.funcName = str(getattr(target,im_func).__name__)\n    def calculateKey( cls, target ):\n        \"\"\"Calculate the reference key for this reference\n\n        Currently this is a two-tuple of the id()'s of the\n        target object and the target function respectively.\n        \"\"\"\n        return (id(getattr(target,im_self)),id(getattr(target,im_func)))\n    calculateKey = classmethod( calculateKey )\n    def __str__(self):\n        \"\"\"Give a friendly representation of the object\"\"\"\n        return \"\"\"%s( %s.%s )\"\"\"%(\n            self.__class__.__name__,\n            self.selfName,\n            self.funcName,\n        )\n    __repr__ = __str__\n    def __nonzero__( self ):\n        \"\"\"Whether we are still a valid reference\"\"\"\n        return self() is not None\n    __bool__ = __nonzero__\n    def __cmp__( self, other ):\n        \"\"\"Compare with another reference\"\"\"\n        if not isinstance (other,self.__class__):\n            return cmp( self.__class__, type(other) )\n        return cmp( self.key, other.key)\n    def __call__(self):\n        \"\"\"Return a strong reference to the bound method\n\n        If the target cannot be retrieved, then will\n        return None, otherwise returns a bound instance\n        method for our object and function.\n\n        Note:\n            You may call this method any number of times,\n            as it does not invalidate the reference.\n        \"\"\"\n        target = self.weakSelf()\n        if target is not None:\n            function = self.weakFunc()\n            if function is not None:\n                return function.__get__(target)\n        return None\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/__init__.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Python driver for MongoDB.\"\"\"\n\nASCENDING = 1\n\"\"\"Ascending sort order.\"\"\"\nDESCENDING = -1\n\"\"\"Descending sort order.\"\"\"\n\nGEO2D = \"2d\"\n\"\"\"Index specifier for a 2-dimensional `geospatial index`_.\n\n.. _geospatial index: http://docs.mongodb.org/manual/core/2d/\n\"\"\"\n\nGEOHAYSTACK = \"geoHaystack\"\n\"\"\"Index specifier for a 2-dimensional `haystack index`_.\n\n.. versionadded:: 2.1\n\n.. _haystack index: http://docs.mongodb.org/manual/core/geohaystack/\n\"\"\"\n\nGEOSPHERE = \"2dsphere\"\n\"\"\"Index specifier for a `spherical geospatial index`_.\n\n.. versionadded:: 2.5\n\n.. _spherical geospatial index: http://docs.mongodb.org/manual/core/2dsphere/\n\"\"\"\n\nHASHED = \"hashed\"\n\"\"\"Index specifier for a `hashed index`_.\n\n.. versionadded:: 2.5\n\n.. _hashed index: http://docs.mongodb.org/manual/core/index-hashed/\n\"\"\"\n\nTEXT = \"text\"\n\"\"\"Index specifier for a `text index`_.\n\n.. versionadded:: 2.7.1\n\n.. _text index: http://docs.mongodb.org/manual/core/index-text/\n\"\"\"\n\nOFF = 0\n\"\"\"No database profiling.\"\"\"\nSLOW_ONLY = 1\n\"\"\"Only profile slow operations.\"\"\"\nALL = 2\n\"\"\"Profile all operations.\"\"\"\n\nversion_tuple = (3, 9, 0)\n\ndef get_version_string():\n    if isinstance(version_tuple[-1], str):\n        return '.'.join(map(str, version_tuple[:-1])) + version_tuple[-1]\n    return '.'.join(map(str, version_tuple))\n\n__version__ = version = get_version_string()\n\"\"\"Current version of PyMongo.\"\"\"\n\nfrom pymongo.collection import ReturnDocument\nfrom pymongo.common import (MIN_SUPPORTED_WIRE_VERSION,\n                            MAX_SUPPORTED_WIRE_VERSION)\nfrom pymongo.cursor import CursorType\nfrom pymongo.mongo_client import MongoClient\nfrom pymongo.mongo_replica_set_client import MongoReplicaSetClient\nfrom pymongo.operations import (IndexModel,\n                                InsertOne,\n                                DeleteOne,\n                                DeleteMany,\n                                UpdateOne,\n                                UpdateMany,\n                                ReplaceOne)\nfrom pymongo.read_preferences import ReadPreference\nfrom pymongo.write_concern import WriteConcern\n\ndef has_c():\n    \"\"\"Is the C extension installed?\"\"\"\n    try:\n        from pymongo import _cmessage\n        return True\n    except ImportError:\n        return False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/aggregation.py",
    "content": "# Copyright 2019-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Perform aggregation operations on a collection or database.\"\"\"\n\nfrom bson.son import SON\n\nfrom pymongo import common\nfrom pymongo.collation import validate_collation_or_none\nfrom pymongo.errors import ConfigurationError\nfrom pymongo.read_preferences import ReadPreference\n\n\nclass _AggregationCommand(object):\n    \"\"\"The internal abstract base class for aggregation cursors.\n\n    Should not be called directly by application developers. Use\n    :meth:`pymongo.collection.Collection.aggregate`, or\n    :meth:`pymongo.database.Database.aggregate` instead.\n    \"\"\"\n    def __init__(self, target, cursor_class, pipeline, options,\n                 explicit_session, user_fields=None, result_processor=None):\n        if \"explain\" in options:\n            raise ConfigurationError(\"The explain option is not supported. \"\n                                     \"Use Database.command instead.\")\n\n        self._target = target\n\n        common.validate_list('pipeline', pipeline)\n        self._pipeline = pipeline\n        self._performs_write = False\n        if pipeline and (\"$out\" in pipeline[-1] or \"$merge\" in pipeline[-1]):\n            self._performs_write = True\n\n        common.validate_is_mapping('options', options)\n        self._options = options\n\n        # This is the batchSize that will be used for setting the initial\n        # batchSize for the cursor, as well as the subsequent getMores.\n        self._batch_size = common.validate_non_negative_integer_or_none(\n            \"batchSize\", self._options.pop(\"batchSize\", None))\n\n        # If the cursor option is already specified, avoid overriding it.\n        self._options.setdefault(\"cursor\", {})\n        # If the pipeline performs a write, we ignore the initial batchSize\n        # since the server doesn't return results in this case.\n        if self._batch_size is not None and not self._performs_write:\n            self._options[\"cursor\"][\"batchSize\"] = self._batch_size\n\n        self._cursor_class = cursor_class\n        self._explicit_session = explicit_session\n        self._user_fields = user_fields\n        self._result_processor = result_processor\n\n        self._collation = validate_collation_or_none(\n            options.pop('collation', None))\n\n        self._max_await_time_ms = options.pop('maxAwaitTimeMS', None)\n\n    @property\n    def _aggregation_target(self):\n        \"\"\"The argument to pass to the aggregate command.\"\"\"\n        raise NotImplementedError\n\n    @property\n    def _cursor_namespace(self):\n        \"\"\"The namespace in which the aggregate command is run.\"\"\"\n        raise NotImplementedError\n\n    @property\n    def _cursor_collection(self, cursor_doc):\n        \"\"\"The Collection used for the aggregate command cursor.\"\"\"\n        raise NotImplementedError\n\n    @property\n    def _database(self):\n        \"\"\"The database against which the aggregation command is run.\"\"\"\n        raise NotImplementedError\n\n    @staticmethod\n    def _check_compat(sock_info):\n        \"\"\"Check whether the server version in-use supports aggregation.\"\"\"\n        pass\n\n    def _process_result(self, result, session, server, sock_info, slave_ok):\n        if self._result_processor:\n            self._result_processor(\n                result, session, server, sock_info, slave_ok)\n\n    def get_read_preference(self, session):\n        if self._performs_write:\n            return ReadPreference.PRIMARY\n        return self._target._read_preference_for(session)\n\n    def get_cursor(self, session, server, sock_info, slave_ok):\n        # Ensure command compatibility.\n        self._check_compat(sock_info)\n\n        # Serialize command.\n        cmd = SON([(\"aggregate\", self._aggregation_target),\n                   (\"pipeline\", self._pipeline)])\n        cmd.update(self._options)\n\n        # Apply this target's read concern if:\n        # readConcern has not been specified as a kwarg and either\n        # - server version is >= 4.2 or\n        # - server version is >= 3.2 and pipeline doesn't use $out\n        if (('readConcern' not in cmd) and\n                ((sock_info.max_wire_version >= 4 and\n                  not self._performs_write) or\n                 (sock_info.max_wire_version >= 8))):\n            read_concern = self._target.read_concern\n        else:\n            read_concern = None\n\n        # Apply this target's write concern if:\n        # writeConcern has not been specified as a kwarg and pipeline doesn't\n        # perform a write operation\n        if 'writeConcern' not in cmd and self._performs_write:\n            write_concern = self._target._write_concern_for(session)\n        else:\n            write_concern = None\n\n        # Run command.\n        result = sock_info.command(\n            self._database.name,\n            cmd,\n            slave_ok,\n            self.get_read_preference(session),\n            self._target.codec_options,\n            parse_write_concern_error=True,\n            read_concern=read_concern,\n            write_concern=write_concern,\n            collation=self._collation,\n            session=session,\n            client=self._database.client,\n            user_fields=self._user_fields)\n\n        self._process_result(result, session, server, sock_info, slave_ok)\n\n        # Extract cursor from result or mock/fake one if necessary.\n        if 'cursor' in result:\n            cursor = result['cursor']\n        else:\n            # Pre-MongoDB 2.6 or unacknowledged write. Fake a cursor.\n            cursor = {\n                \"id\": 0,\n                \"firstBatch\": result.get(\"result\", []),\n                \"ns\": self._cursor_namespace,\n            }\n\n        # Create and return cursor instance.\n        return self._cursor_class(\n            self._cursor_collection(cursor), cursor, sock_info.address,\n            batch_size=self._batch_size or 0,\n            max_await_time_ms=self._max_await_time_ms,\n            session=session, explicit_session=self._explicit_session)\n\n\nclass _CollectionAggregationCommand(_AggregationCommand):\n    def __init__(self, *args, **kwargs):\n        # Pop additional option and initialize parent class.\n        use_cursor = kwargs.pop(\"use_cursor\", True)\n        super(_CollectionAggregationCommand, self).__init__(*args, **kwargs)\n\n        # Remove the cursor document if the user has set use_cursor to False.\n        self._use_cursor = use_cursor\n        if not self._use_cursor:\n            self._options.pop(\"cursor\", None)\n\n    @property\n    def _aggregation_target(self):\n        return self._target.name\n\n    @property\n    def _cursor_namespace(self):\n        return self._target.full_name\n\n    def _cursor_collection(self, cursor):\n        \"\"\"The Collection used for the aggregate command cursor.\"\"\"\n        return self._target\n\n    @property\n    def _database(self):\n        return self._target.database\n\n\nclass _CollectionRawAggregationCommand(_CollectionAggregationCommand):\n    def __init__(self, *args, **kwargs):\n        super(_CollectionRawAggregationCommand, self).__init__(*args, **kwargs)\n\n        # For raw-batches, we set the initial batchSize for the cursor to 0.\n        if self._use_cursor and not self._performs_write:\n            self._options[\"cursor\"][\"batchSize\"] = 0\n\n\nclass _DatabaseAggregationCommand(_AggregationCommand):\n    @property\n    def _aggregation_target(self):\n        return 1\n\n    @property\n    def _cursor_namespace(self):\n        return \"%s.$cmd.aggregate\" % (self._target.name,)\n\n    @property\n    def _database(self):\n        return self._target\n\n    def _cursor_collection(self, cursor):\n        \"\"\"The Collection used for the aggregate command cursor.\"\"\"\n        # Collection level aggregate may not always return the \"ns\" field\n        # according to our MockupDB tests. Let's handle that case for db level\n        # aggregate too by defaulting to the <db>.$cmd.aggregate namespace.\n        _, collname = cursor.get(\"ns\", self._cursor_namespace).split(\".\", 1)\n        return self._database[collname]\n\n    @staticmethod\n    def _check_compat(sock_info):\n        # Older server version don't raise a descriptive error, so we raise\n        # one instead.\n        if not sock_info.max_wire_version >= 6:\n            err_msg = \"Database.aggregate() is only supported on MongoDB 3.6+.\"\n            raise ConfigurationError(err_msg)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/auth.py",
    "content": "# Copyright 2013-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Authentication helpers.\"\"\"\n\nimport functools\nimport hashlib\nimport hmac\nimport os\nimport socket\n\ntry:\n    from urllib import quote\nexcept ImportError:\n    from urllib.parse import quote\n\nHAVE_KERBEROS = True\n_USE_PRINCIPAL = False\ntry:\n    import winkerberos as kerberos\n    if tuple(map(int, kerberos.__version__.split('.')[:2])) >= (0, 5):\n        _USE_PRINCIPAL = True\nexcept ImportError:\n    try:\n        import kerberos\n    except ImportError:\n        HAVE_KERBEROS = False\n\nfrom base64 import standard_b64decode, standard_b64encode\nfrom collections import namedtuple\n\nfrom bson.binary import Binary\nfrom bson.py3compat import string_type, _unicode, PY3\nfrom bson.son import SON\nfrom pymongo.errors import ConfigurationError, OperationFailure\nfrom pymongo.saslprep import saslprep\n\n\nMECHANISMS = frozenset(\n    ['GSSAPI',\n     'MONGODB-CR',\n     'MONGODB-X509',\n     'PLAIN',\n     'SCRAM-SHA-1',\n     'SCRAM-SHA-256',\n     'DEFAULT'])\n\"\"\"The authentication mechanisms supported by PyMongo.\"\"\"\n\n\nclass _Cache(object):\n    __slots__ = (\"data\",)\n\n    _hash_val = hash('_Cache')\n\n    def __init__(self):\n        self.data = None\n\n    def __eq__(self, other):\n        # Two instances must always compare equal.\n        if isinstance(other, _Cache):\n            return True\n        return NotImplemented\n\n    def __ne__(self, other):\n        if isinstance(other, _Cache):\n            return False\n        return NotImplemented\n\n    def __hash__(self):\n        return self._hash_val\n\n\n\nMongoCredential = namedtuple(\n    'MongoCredential',\n    ['mechanism',\n     'source',\n     'username',\n     'password',\n     'mechanism_properties',\n     'cache'])\n\"\"\"A hashable namedtuple of values used for authentication.\"\"\"\n\n\nGSSAPIProperties = namedtuple('GSSAPIProperties',\n                              ['service_name',\n                               'canonicalize_host_name',\n                               'service_realm'])\n\"\"\"Mechanism properties for GSSAPI authentication.\"\"\"\n\n\ndef _build_credentials_tuple(mech, source, user, passwd, extra, database):\n    \"\"\"Build and return a mechanism specific credentials tuple.\n    \"\"\"\n    if mech != 'MONGODB-X509' and user is None:\n        raise ConfigurationError(\"%s requires a username.\" % (mech,))\n    if mech == 'GSSAPI':\n        if source is not None and source != '$external':\n            raise ValueError(\n                \"authentication source must be $external or None for GSSAPI\")\n        properties = extra.get('authmechanismproperties', {})\n        service_name = properties.get('SERVICE_NAME', 'mongodb')\n        canonicalize = properties.get('CANONICALIZE_HOST_NAME', False)\n        service_realm = properties.get('SERVICE_REALM')\n        props = GSSAPIProperties(service_name=service_name,\n                                 canonicalize_host_name=canonicalize,\n                                 service_realm=service_realm)\n        # Source is always $external.\n        return MongoCredential(mech, '$external', user, passwd, props, None)\n    elif mech == 'MONGODB-X509':\n        if passwd is not None:\n            raise ConfigurationError(\n                \"Passwords are not supported by MONGODB-X509\")\n        if source is not None and source != '$external':\n            raise ValueError(\n                \"authentication source must be \"\n                \"$external or None for MONGODB-X509\")\n        # user can be None.\n        return MongoCredential(mech, '$external', user, None, None, None)\n    elif mech == 'PLAIN':\n        source_database = source or database or '$external'\n        return MongoCredential(mech, source_database, user, passwd, None, None)\n    else:\n        source_database = source or database or 'admin'\n        if passwd is None:\n            raise ConfigurationError(\"A password is required.\")\n        return MongoCredential(\n            mech, source_database, user, passwd, None, _Cache())\n\n\nif PY3:\n    def _xor(fir, sec):\n        \"\"\"XOR two byte strings together (python 3.x).\"\"\"\n        return b\"\".join([bytes([x ^ y]) for x, y in zip(fir, sec)])\n\n\n    _from_bytes = int.from_bytes\n    _to_bytes = int.to_bytes\nelse:\n    from binascii import (hexlify as _hexlify,\n                          unhexlify as _unhexlify)\n\n\n    def _xor(fir, sec):\n        \"\"\"XOR two byte strings together (python 2.x).\"\"\"\n        return b\"\".join([chr(ord(x) ^ ord(y)) for x, y in zip(fir, sec)])\n\n\n    def _from_bytes(value, dummy, _int=int, _hexlify=_hexlify):\n        \"\"\"An implementation of int.from_bytes for python 2.x.\"\"\"\n        return _int(_hexlify(value), 16)\n\n\n    def _to_bytes(value, length, dummy, _unhexlify=_unhexlify):\n        \"\"\"An implementation of int.to_bytes for python 2.x.\"\"\"\n        fmt = '%%0%dx' % (2 * length,)\n        return _unhexlify(fmt % value)\n\n\ntry:\n    # The fastest option, if it's been compiled to use OpenSSL's HMAC.\n    from backports.pbkdf2 import pbkdf2_hmac as _hi\nexcept ImportError:\n    try:\n        # Python 2.7.8+, or Python 3.4+.\n        from hashlib import pbkdf2_hmac as _hi\n    except ImportError:\n\n        def _hi(hash_name, data, salt, iterations):\n            \"\"\"A simple implementation of PBKDF2-HMAC.\"\"\"\n            mac = hmac.HMAC(data, None, getattr(hashlib, hash_name))\n\n            def _digest(msg, mac=mac):\n                \"\"\"Get a digest for msg.\"\"\"\n                _mac = mac.copy()\n                _mac.update(msg)\n                return _mac.digest()\n\n            from_bytes = _from_bytes\n            to_bytes = _to_bytes\n\n            _u1 = _digest(salt + b'\\x00\\x00\\x00\\x01')\n            _ui = from_bytes(_u1, 'big')\n            for _ in range(iterations - 1):\n                _u1 = _digest(_u1)\n                _ui ^= from_bytes(_u1, 'big')\n            return to_bytes(_ui, mac.digest_size, 'big')\n\ntry:\n    from hmac import compare_digest\nexcept ImportError:\n    if PY3:\n        def _xor_bytes(a, b):\n            return a ^ b\n    else:\n        def _xor_bytes(a, b, _ord=ord):\n            return _ord(a) ^ _ord(b)\n\n    # Python 2.x < 2.7.7\n    # Note: This method is intentionally obtuse to prevent timing attacks. Do\n    # not refactor it!\n    # References:\n    #  - http://bugs.python.org/issue14532\n    #  - http://bugs.python.org/issue14955\n    #  - http://bugs.python.org/issue15061\n    def compare_digest(a, b, _xor_bytes=_xor_bytes):\n        left = None\n        right = b\n        if len(a) == len(b):\n            left = a\n            result = 0\n        if len(a) != len(b):\n            left = b\n            result = 1\n\n        for x, y in zip(left, right):\n            result |= _xor_bytes(x, y)\n        return result == 0\n\n\ndef _parse_scram_response(response):\n    \"\"\"Split a scram response into key, value pairs.\"\"\"\n    return dict(item.split(b\"=\", 1) for item in response.split(b\",\"))\n\n\ndef _authenticate_scram(credentials, sock_info, mechanism):\n    \"\"\"Authenticate using SCRAM.\"\"\"\n\n    username = credentials.username\n    if mechanism == 'SCRAM-SHA-256':\n        digest = \"sha256\"\n        digestmod = hashlib.sha256\n        data = saslprep(credentials.password).encode(\"utf-8\")\n    else:\n        digest = \"sha1\"\n        digestmod = hashlib.sha1\n        data = _password_digest(username, credentials.password).encode(\"utf-8\")\n    source = credentials.source\n    cache = credentials.cache\n\n    # Make local\n    _hmac = hmac.HMAC\n\n    user = username.encode(\"utf-8\").replace(b\"=\", b\"=3D\").replace(b\",\", b\"=2C\")\n    nonce = standard_b64encode(os.urandom(32))\n    first_bare = b\"n=\" + user + b\",r=\" + nonce\n\n    cmd = SON([('saslStart', 1),\n               ('mechanism', mechanism),\n               ('payload', Binary(b\"n,,\" + first_bare)),\n               ('autoAuthorize', 1)])\n    res = sock_info.command(source, cmd)\n\n    server_first = res['payload']\n    parsed = _parse_scram_response(server_first)\n    iterations = int(parsed[b'i'])\n    if iterations < 4096:\n        raise OperationFailure(\"Server returned an invalid iteration count.\")\n    salt = parsed[b's']\n    rnonce = parsed[b'r']\n    if not rnonce.startswith(nonce):\n        raise OperationFailure(\"Server returned an invalid nonce.\")\n\n    without_proof = b\"c=biws,r=\" + rnonce\n    if cache.data:\n        client_key, server_key, csalt, citerations = cache.data\n    else:\n        client_key, server_key, csalt, citerations = None, None, None, None\n\n    # Salt and / or iterations could change for a number of different\n    # reasons. Either changing invalidates the cache.\n    if not client_key or salt != csalt or iterations != citerations:\n        salted_pass = _hi(\n            digest, data, standard_b64decode(salt), iterations)\n        client_key = _hmac(salted_pass, b\"Client Key\", digestmod).digest()\n        server_key = _hmac(salted_pass, b\"Server Key\", digestmod).digest()\n        cache.data = (client_key, server_key, salt, iterations)\n    stored_key = digestmod(client_key).digest()\n    auth_msg = b\",\".join((first_bare, server_first, without_proof))\n    client_sig = _hmac(stored_key, auth_msg, digestmod).digest()\n    client_proof = b\"p=\" + standard_b64encode(_xor(client_key, client_sig))\n    client_final = b\",\".join((without_proof, client_proof))\n\n    server_sig = standard_b64encode(\n        _hmac(server_key, auth_msg, digestmod).digest())\n\n    cmd = SON([('saslContinue', 1),\n               ('conversationId', res['conversationId']),\n               ('payload', Binary(client_final))])\n    res = sock_info.command(source, cmd)\n\n    parsed = _parse_scram_response(res['payload'])\n    if not compare_digest(parsed[b'v'], server_sig):\n        raise OperationFailure(\"Server returned an invalid signature.\")\n\n    # Depending on how it's configured, Cyrus SASL (which the server uses)\n    # requires a third empty challenge.\n    if not res['done']:\n        cmd = SON([('saslContinue', 1),\n                   ('conversationId', res['conversationId']),\n                   ('payload', Binary(b''))])\n        res = sock_info.command(source, cmd)\n        if not res['done']:\n            raise OperationFailure('SASL conversation failed to complete.')\n\n\ndef _password_digest(username, password):\n    \"\"\"Get a password digest to use for authentication.\n    \"\"\"\n    if not isinstance(password, string_type):\n        raise TypeError(\"password must be an \"\n                        \"instance of %s\" % (string_type.__name__,))\n    if len(password) == 0:\n        raise ValueError(\"password can't be empty\")\n    if not isinstance(username, string_type):\n        raise TypeError(\"password must be an \"\n                        \"instance of  %s\" % (string_type.__name__,))\n\n    md5hash = hashlib.md5()\n    data = \"%s:mongo:%s\" % (username, password)\n    md5hash.update(data.encode('utf-8'))\n    return _unicode(md5hash.hexdigest())\n\n\ndef _auth_key(nonce, username, password):\n    \"\"\"Get an auth key to use for authentication.\n    \"\"\"\n    digest = _password_digest(username, password)\n    md5hash = hashlib.md5()\n    data = \"%s%s%s\" % (nonce, username, digest)\n    md5hash.update(data.encode('utf-8'))\n    return _unicode(md5hash.hexdigest())\n\n\ndef _authenticate_gssapi(credentials, sock_info):\n    \"\"\"Authenticate using GSSAPI.\n    \"\"\"\n    if not HAVE_KERBEROS:\n        raise ConfigurationError('The \"kerberos\" module must be '\n                                 'installed to use GSSAPI authentication.')\n\n    try:\n        username = credentials.username\n        password = credentials.password\n        props = credentials.mechanism_properties\n        # Starting here and continuing through the while loop below - establish\n        # the security context. See RFC 4752, Section 3.1, first paragraph.\n        host = sock_info.address[0]\n        if props.canonicalize_host_name:\n            host = socket.getfqdn(host)\n        service = props.service_name + '@' + host\n        if props.service_realm is not None:\n            service = service + '@' + props.service_realm\n\n        if password is not None:\n            if _USE_PRINCIPAL:\n                # Note that, though we use unquote_plus for unquoting URI\n                # options, we use quote here. Microsoft's UrlUnescape (used\n                # by WinKerberos) doesn't support +.\n                principal = \":\".join((quote(username), quote(password)))\n                result, ctx = kerberos.authGSSClientInit(\n                    service, principal, gssflags=kerberos.GSS_C_MUTUAL_FLAG)\n            else:\n                if '@' in username:\n                    user, domain = username.split('@', 1)\n                else:\n                    user, domain = username, None\n                result, ctx = kerberos.authGSSClientInit(\n                    service, gssflags=kerberos.GSS_C_MUTUAL_FLAG,\n                    user=user, domain=domain, password=password)\n        else:\n            result, ctx = kerberos.authGSSClientInit(\n                service, gssflags=kerberos.GSS_C_MUTUAL_FLAG)\n\n        if result != kerberos.AUTH_GSS_COMPLETE:\n            raise OperationFailure('Kerberos context failed to initialize.')\n\n        try:\n            # pykerberos uses a weird mix of exceptions and return values\n            # to indicate errors.\n            # 0 == continue, 1 == complete, -1 == error\n            # Only authGSSClientStep can return 0.\n            if kerberos.authGSSClientStep(ctx, '') != 0:\n                raise OperationFailure('Unknown kerberos '\n                                       'failure in step function.')\n\n            # Start a SASL conversation with mongod/s\n            # Note: pykerberos deals with base64 encoded byte strings.\n            # Since mongo accepts base64 strings as the payload we don't\n            # have to use bson.binary.Binary.\n            payload = kerberos.authGSSClientResponse(ctx)\n            cmd = SON([('saslStart', 1),\n                       ('mechanism', 'GSSAPI'),\n                       ('payload', payload),\n                       ('autoAuthorize', 1)])\n            response = sock_info.command('$external', cmd)\n\n            # Limit how many times we loop to catch protocol / library issues\n            for _ in range(10):\n                result = kerberos.authGSSClientStep(ctx,\n                                                    str(response['payload']))\n                if result == -1:\n                    raise OperationFailure('Unknown kerberos '\n                                           'failure in step function.')\n\n                payload = kerberos.authGSSClientResponse(ctx) or ''\n\n                cmd = SON([('saslContinue', 1),\n                           ('conversationId', response['conversationId']),\n                           ('payload', payload)])\n                response = sock_info.command('$external', cmd)\n\n                if result == kerberos.AUTH_GSS_COMPLETE:\n                    break\n            else:\n                raise OperationFailure('Kerberos '\n                                       'authentication failed to complete.')\n\n            # Once the security context is established actually authenticate.\n            # See RFC 4752, Section 3.1, last two paragraphs.\n            if kerberos.authGSSClientUnwrap(ctx,\n                                            str(response['payload'])) != 1:\n                raise OperationFailure('Unknown kerberos '\n                                       'failure during GSS_Unwrap step.')\n\n            if kerberos.authGSSClientWrap(ctx,\n                                          kerberos.authGSSClientResponse(ctx),\n                                          username) != 1:\n                raise OperationFailure('Unknown kerberos '\n                                       'failure during GSS_Wrap step.')\n\n            payload = kerberos.authGSSClientResponse(ctx)\n            cmd = SON([('saslContinue', 1),\n                       ('conversationId', response['conversationId']),\n                       ('payload', payload)])\n            sock_info.command('$external', cmd)\n\n        finally:\n            kerberos.authGSSClientClean(ctx)\n\n    except kerberos.KrbError as exc:\n        raise OperationFailure(str(exc))\n\n\ndef _authenticate_plain(credentials, sock_info):\n    \"\"\"Authenticate using SASL PLAIN (RFC 4616)\n    \"\"\"\n    source = credentials.source\n    username = credentials.username\n    password = credentials.password\n    payload = ('\\x00%s\\x00%s' % (username, password)).encode('utf-8')\n    cmd = SON([('saslStart', 1),\n               ('mechanism', 'PLAIN'),\n               ('payload', Binary(payload)),\n               ('autoAuthorize', 1)])\n    sock_info.command(source, cmd)\n\n\ndef _authenticate_cram_md5(credentials, sock_info):\n    \"\"\"Authenticate using CRAM-MD5 (RFC 2195)\n    \"\"\"\n    source = credentials.source\n    username = credentials.username\n    password = credentials.password\n    # The password used as the mac key is the\n    # same as what we use for MONGODB-CR\n    passwd = _password_digest(username, password)\n    cmd = SON([('saslStart', 1),\n               ('mechanism', 'CRAM-MD5'),\n               ('payload', Binary(b'')),\n               ('autoAuthorize', 1)])\n    response = sock_info.command(source, cmd)\n    # MD5 as implicit default digest for digestmod is deprecated\n    # in python 3.4\n    mac = hmac.HMAC(key=passwd.encode('utf-8'), digestmod=hashlib.md5)\n    mac.update(response['payload'])\n    challenge = username.encode('utf-8') + b' ' + mac.hexdigest().encode('utf-8')\n    cmd = SON([('saslContinue', 1),\n               ('conversationId', response['conversationId']),\n               ('payload', Binary(challenge))])\n    sock_info.command(source, cmd)\n\n\ndef _authenticate_x509(credentials, sock_info):\n    \"\"\"Authenticate using MONGODB-X509.\n    \"\"\"\n    query = SON([('authenticate', 1),\n                 ('mechanism', 'MONGODB-X509')])\n    if credentials.username is not None:\n        query['user'] = credentials.username\n    elif sock_info.max_wire_version < 5:\n        raise ConfigurationError(\n            \"A username is required for MONGODB-X509 authentication \"\n            \"when connected to MongoDB versions older than 3.4.\")\n    sock_info.command('$external', query)\n\n\ndef _authenticate_mongo_cr(credentials, sock_info):\n    \"\"\"Authenticate using MONGODB-CR.\n    \"\"\"\n    source = credentials.source\n    username = credentials.username\n    password = credentials.password\n    # Get a nonce\n    response = sock_info.command(source, {'getnonce': 1})\n    nonce = response['nonce']\n    key = _auth_key(nonce, username, password)\n\n    # Actually authenticate\n    query = SON([('authenticate', 1),\n                 ('user', username),\n                 ('nonce', nonce),\n                 ('key', key)])\n    sock_info.command(source, query)\n\n\ndef _authenticate_default(credentials, sock_info):\n    if sock_info.max_wire_version >= 7:\n        source = credentials.source\n        cmd = SON([\n            ('ismaster', 1),\n            ('saslSupportedMechs', source + '.' + credentials.username)])\n        mechs = sock_info.command(\n            source, cmd, publish_events=False).get('saslSupportedMechs', [])\n        if 'SCRAM-SHA-256' in mechs:\n            return _authenticate_scram(credentials, sock_info, 'SCRAM-SHA-256')\n        else:\n            return _authenticate_scram(credentials, sock_info, 'SCRAM-SHA-1')\n    elif sock_info.max_wire_version >= 3:\n        return _authenticate_scram(credentials, sock_info, 'SCRAM-SHA-1')\n    else:\n        return _authenticate_mongo_cr(credentials, sock_info)\n\n\n_AUTH_MAP = {\n    'CRAM-MD5': _authenticate_cram_md5,\n    'GSSAPI': _authenticate_gssapi,\n    'MONGODB-CR': _authenticate_mongo_cr,\n    'MONGODB-X509': _authenticate_x509,\n    'PLAIN': _authenticate_plain,\n    'SCRAM-SHA-1': functools.partial(\n        _authenticate_scram, mechanism='SCRAM-SHA-1'),\n    'SCRAM-SHA-256': functools.partial(\n        _authenticate_scram, mechanism='SCRAM-SHA-256'),\n    'DEFAULT': _authenticate_default,\n}\n\n\ndef authenticate(credentials, sock_info):\n    \"\"\"Authenticate sock_info.\"\"\"\n    mechanism = credentials.mechanism\n    auth_func = _AUTH_MAP.get(mechanism)\n    auth_func(credentials, sock_info)\n\n\ndef logout(source, sock_info):\n    \"\"\"Log out from a database.\"\"\"\n    sock_info.command(source, {'logout': 1})\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/bulk.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"The bulk write operations interface.\n\n.. versionadded:: 2.7\n\"\"\"\nimport copy\n\nfrom itertools import islice\n\nfrom bson.objectid import ObjectId\nfrom bson.raw_bson import RawBSONDocument\nfrom bson.son import SON\nfrom pymongo.client_session import _validate_session_write_concern\nfrom pymongo.common import (validate_is_mapping,\n                            validate_is_document_type,\n                            validate_ok_for_replace,\n                            validate_ok_for_update)\nfrom pymongo.helpers import _RETRYABLE_ERROR_CODES\nfrom pymongo.collation import validate_collation_or_none\nfrom pymongo.errors import (BulkWriteError,\n                            ConfigurationError,\n                            InvalidOperation,\n                            OperationFailure)\nfrom pymongo.message import (_INSERT, _UPDATE, _DELETE,\n                             _do_batched_insert,\n                             _randint,\n                             _BulkWriteContext,\n                             _EncryptedBulkWriteContext)\nfrom pymongo.read_preferences import ReadPreference\nfrom pymongo.write_concern import WriteConcern\n\n\n_DELETE_ALL = 0\n_DELETE_ONE = 1\n\n# For backwards compatibility. See MongoDB src/mongo/base/error_codes.err\n_BAD_VALUE = 2\n_UNKNOWN_ERROR = 8\n_WRITE_CONCERN_ERROR = 64\n\n_COMMANDS = ('insert', 'update', 'delete')\n\n\n# These string literals are used when we create fake server return\n# documents client side. We use unicode literals in python 2.x to\n# match the actual return values from the server.\n_UOP = u\"op\"\n\n\nclass _Run(object):\n    \"\"\"Represents a batch of write operations.\n    \"\"\"\n    def __init__(self, op_type):\n        \"\"\"Initialize a new Run object.\n        \"\"\"\n        self.op_type = op_type\n        self.index_map = []\n        self.ops = []\n        self.idx_offset = 0\n\n    def index(self, idx):\n        \"\"\"Get the original index of an operation in this run.\n\n        :Parameters:\n          - `idx`: The Run index that maps to the original index.\n        \"\"\"\n        return self.index_map[idx]\n\n    def add(self, original_index, operation):\n        \"\"\"Add an operation to this Run instance.\n\n        :Parameters:\n          - `original_index`: The original index of this operation\n            within a larger bulk operation.\n          - `operation`: The operation document.\n        \"\"\"\n        self.index_map.append(original_index)\n        self.ops.append(operation)\n\n\ndef _merge_command(run, full_result, offset, result):\n    \"\"\"Merge a write command result into the full bulk result.\n    \"\"\"\n    affected = result.get(\"n\", 0)\n\n    if run.op_type == _INSERT:\n        full_result[\"nInserted\"] += affected\n\n    elif run.op_type == _DELETE:\n        full_result[\"nRemoved\"] += affected\n\n    elif run.op_type == _UPDATE:\n        upserted = result.get(\"upserted\")\n        if upserted:\n            n_upserted = len(upserted)\n            for doc in upserted:\n                doc[\"index\"] = run.index(doc[\"index\"] + offset)\n            full_result[\"upserted\"].extend(upserted)\n            full_result[\"nUpserted\"] += n_upserted\n            full_result[\"nMatched\"] += (affected - n_upserted)\n        else:\n            full_result[\"nMatched\"] += affected\n        full_result[\"nModified\"] += result[\"nModified\"]\n\n    write_errors = result.get(\"writeErrors\")\n    if write_errors:\n        for doc in write_errors:\n            # Leave the server response intact for APM.\n            replacement = doc.copy()\n            idx = doc[\"index\"] + offset\n            replacement[\"index\"] = run.index(idx)\n            # Add the failed operation to the error document.\n            replacement[_UOP] = run.ops[idx]\n            full_result[\"writeErrors\"].append(replacement)\n\n    wc_error = result.get(\"writeConcernError\")\n    if wc_error:\n        full_result[\"writeConcernErrors\"].append(wc_error)\n\n\ndef _raise_bulk_write_error(full_result):\n    \"\"\"Raise a BulkWriteError from the full bulk api result.\n    \"\"\"\n    if full_result[\"writeErrors\"]:\n        full_result[\"writeErrors\"].sort(\n            key=lambda error: error[\"index\"])\n    raise BulkWriteError(full_result)\n\n\nclass _Bulk(object):\n    \"\"\"The private guts of the bulk write API.\n    \"\"\"\n    def __init__(self, collection, ordered, bypass_document_validation):\n        \"\"\"Initialize a _Bulk instance.\n        \"\"\"\n        self.collection = collection.with_options(\n            codec_options=collection.codec_options._replace(\n                unicode_decode_error_handler='replace',\n                document_class=dict))\n        self.ordered = ordered\n        self.ops = []\n        self.executed = False\n        self.bypass_doc_val = bypass_document_validation\n        self.uses_collation = False\n        self.uses_array_filters = False\n        self.is_retryable = True\n        self.retrying = False\n        self.started_retryable_write = False\n        # Extra state so that we know where to pick up on a retry attempt.\n        self.current_run = None\n\n    @property\n    def bulk_ctx_class(self):\n        encrypter = self.collection.database.client._encrypter\n        if encrypter and not encrypter._bypass_auto_encryption:\n            return _EncryptedBulkWriteContext\n        else:\n            return _BulkWriteContext\n\n    def add_insert(self, document):\n        \"\"\"Add an insert document to the list of ops.\n        \"\"\"\n        validate_is_document_type(\"document\", document)\n        # Generate ObjectId client side.\n        if not (isinstance(document, RawBSONDocument) or '_id' in document):\n            document['_id'] = ObjectId()\n        self.ops.append((_INSERT, document))\n\n    def add_update(self, selector, update, multi=False, upsert=False,\n                   collation=None, array_filters=None):\n        \"\"\"Create an update document and add it to the list of ops.\n        \"\"\"\n        validate_ok_for_update(update)\n        cmd = SON([('q', selector), ('u', update),\n                   ('multi', multi), ('upsert', upsert)])\n        collation = validate_collation_or_none(collation)\n        if collation is not None:\n            self.uses_collation = True\n            cmd['collation'] = collation\n        if array_filters is not None:\n            self.uses_array_filters = True\n            cmd['arrayFilters'] = array_filters\n        if multi:\n            # A bulk_write containing an update_many is not retryable.\n            self.is_retryable = False\n        self.ops.append((_UPDATE, cmd))\n\n    def add_replace(self, selector, replacement, upsert=False,\n                    collation=None):\n        \"\"\"Create a replace document and add it to the list of ops.\n        \"\"\"\n        validate_ok_for_replace(replacement)\n        cmd = SON([('q', selector), ('u', replacement),\n                   ('multi', False), ('upsert', upsert)])\n        collation = validate_collation_or_none(collation)\n        if collation is not None:\n            self.uses_collation = True\n            cmd['collation'] = collation\n        self.ops.append((_UPDATE, cmd))\n\n    def add_delete(self, selector, limit, collation=None):\n        \"\"\"Create a delete document and add it to the list of ops.\n        \"\"\"\n        cmd = SON([('q', selector), ('limit', limit)])\n        collation = validate_collation_or_none(collation)\n        if collation is not None:\n            self.uses_collation = True\n            cmd['collation'] = collation\n        if limit == _DELETE_ALL:\n            # A bulk_write containing a delete_many is not retryable.\n            self.is_retryable = False\n        self.ops.append((_DELETE, cmd))\n\n    def gen_ordered(self):\n        \"\"\"Generate batches of operations, batched by type of\n        operation, in the order **provided**.\n        \"\"\"\n        run = None\n        for idx, (op_type, operation) in enumerate(self.ops):\n            if run is None:\n                run = _Run(op_type)\n            elif run.op_type != op_type:\n                yield run\n                run = _Run(op_type)\n            run.add(idx, operation)\n        yield run\n\n    def gen_unordered(self):\n        \"\"\"Generate batches of operations, batched by type of\n        operation, in arbitrary order.\n        \"\"\"\n        operations = [_Run(_INSERT), _Run(_UPDATE), _Run(_DELETE)]\n        for idx, (op_type, operation) in enumerate(self.ops):\n            operations[op_type].add(idx, operation)\n\n        for run in operations:\n            if run.ops:\n                yield run\n\n    def _execute_command(self, generator, write_concern, session,\n                         sock_info, op_id, retryable, full_result):\n        if sock_info.max_wire_version < 5 and self.uses_collation:\n            raise ConfigurationError(\n                'Must be connected to MongoDB 3.4+ to use a collation.')\n        if sock_info.max_wire_version < 6 and self.uses_array_filters:\n            raise ConfigurationError(\n                'Must be connected to MongoDB 3.6+ to use arrayFilters.')\n\n        db_name = self.collection.database.name\n        client = self.collection.database.client\n        listeners = client._event_listeners\n\n        if not self.current_run:\n            self.current_run = next(generator)\n        run = self.current_run\n\n        # sock_info.command validates the session, but we use\n        # sock_info.write_command.\n        sock_info.validate_session(client, session)\n        while run:\n            cmd = SON([(_COMMANDS[run.op_type], self.collection.name),\n                       ('ordered', self.ordered)])\n            if not write_concern.is_server_default:\n                cmd['writeConcern'] = write_concern.document\n            if self.bypass_doc_val and sock_info.max_wire_version >= 4:\n                cmd['bypassDocumentValidation'] = True\n            bwc = self.bulk_ctx_class(\n                db_name, cmd, sock_info, op_id, listeners, session,\n                run.op_type, self.collection.codec_options)\n\n            while run.idx_offset < len(run.ops):\n                if session:\n                    # Start a new retryable write unless one was already\n                    # started for this command.\n                    if retryable and not self.started_retryable_write:\n                        session._start_retryable_write()\n                        self.started_retryable_write = True\n                    session._apply_to(cmd, retryable, ReadPreference.PRIMARY)\n                sock_info.send_cluster_time(cmd, session, client)\n                ops = islice(run.ops, run.idx_offset, None)\n                # Run as many ops as possible in one command.\n                result, to_send = bwc.execute(ops, client)\n\n                # Retryable writeConcernErrors halt the execution of this run.\n                wce = result.get('writeConcernError', {})\n                if wce.get('code', 0) in _RETRYABLE_ERROR_CODES:\n                    # Synthesize the full bulk result without modifying the\n                    # current one because this write operation may be retried.\n                    full = copy.deepcopy(full_result)\n                    _merge_command(run, full, run.idx_offset, result)\n                    _raise_bulk_write_error(full)\n\n                _merge_command(run, full_result, run.idx_offset, result)\n                # We're no longer in a retry once a command succeeds.\n                self.retrying = False\n                self.started_retryable_write = False\n\n                if self.ordered and \"writeErrors\" in result:\n                    break\n                run.idx_offset += len(to_send)\n\n            # We're supposed to continue if errors are\n            # at the write concern level (e.g. wtimeout)\n            if self.ordered and full_result['writeErrors']:\n                break\n            # Reset our state\n            self.current_run = run = next(generator, None)\n\n    def execute_command(self, generator, write_concern, session):\n        \"\"\"Execute using write commands.\n        \"\"\"\n        # nModified is only reported for write commands, not legacy ops.\n        full_result = {\n            \"writeErrors\": [],\n            \"writeConcernErrors\": [],\n            \"nInserted\": 0,\n            \"nUpserted\": 0,\n            \"nMatched\": 0,\n            \"nModified\": 0,\n            \"nRemoved\": 0,\n            \"upserted\": [],\n        }\n        op_id = _randint()\n\n        def retryable_bulk(session, sock_info, retryable):\n            self._execute_command(\n                generator, write_concern, session, sock_info, op_id,\n                retryable, full_result)\n\n        client = self.collection.database.client\n        with client._tmp_session(session) as s:\n            client._retry_with_session(\n                self.is_retryable, retryable_bulk, s, self)\n\n        if full_result[\"writeErrors\"] or full_result[\"writeConcernErrors\"]:\n            _raise_bulk_write_error(full_result)\n        return full_result\n\n    def execute_insert_no_results(self, sock_info, run, op_id, acknowledged):\n        \"\"\"Execute insert, returning no results.\n        \"\"\"\n        command = SON([('insert', self.collection.name),\n                       ('ordered', self.ordered)])\n        concern = {'w': int(self.ordered)}\n        command['writeConcern'] = concern\n        if self.bypass_doc_val and sock_info.max_wire_version >= 4:\n            command['bypassDocumentValidation'] = True\n        db = self.collection.database\n        bwc = _BulkWriteContext(\n            db.name, command, sock_info, op_id, db.client._event_listeners,\n            None, _INSERT, self.collection.codec_options)\n        # Legacy batched OP_INSERT.\n        _do_batched_insert(\n            self.collection.full_name, run.ops, True, acknowledged, concern,\n            not self.ordered, self.collection.codec_options, bwc)\n\n    def execute_op_msg_no_results(self, sock_info, generator):\n        \"\"\"Execute write commands with OP_MSG and w=0 writeConcern, unordered.\n        \"\"\"\n        db_name = self.collection.database.name\n        client = self.collection.database.client\n        listeners = client._event_listeners\n        op_id = _randint()\n\n        if not self.current_run:\n            self.current_run = next(generator)\n        run = self.current_run\n\n        while run:\n            cmd = SON([(_COMMANDS[run.op_type], self.collection.name),\n                       ('ordered', False),\n                       ('writeConcern', {'w': 0})])\n            bwc = self.bulk_ctx_class(\n                db_name, cmd, sock_info, op_id, listeners, None,\n                run.op_type, self.collection.codec_options)\n\n            while run.idx_offset < len(run.ops):\n                ops = islice(run.ops, run.idx_offset, None)\n                # Run as many ops as possible.\n                to_send = bwc.execute_unack(ops, client)\n                run.idx_offset += len(to_send)\n            self.current_run = run = next(generator, None)\n\n    def execute_command_no_results(self, sock_info, generator):\n        \"\"\"Execute write commands with OP_MSG and w=0 WriteConcern, ordered.\n        \"\"\"\n        full_result = {\n            \"writeErrors\": [],\n            \"writeConcernErrors\": [],\n            \"nInserted\": 0,\n            \"nUpserted\": 0,\n            \"nMatched\": 0,\n            \"nModified\": 0,\n            \"nRemoved\": 0,\n            \"upserted\": [],\n        }\n        # Ordered bulk writes have to be acknowledged so that we stop\n        # processing at the first error, even when the application\n        # specified unacknowledged writeConcern.\n        write_concern = WriteConcern()\n        op_id = _randint()\n        try:\n            self._execute_command(\n                generator, write_concern, None,\n                sock_info, op_id, False, full_result)\n        except OperationFailure:\n            pass\n\n    def execute_no_results(self, sock_info, generator):\n        \"\"\"Execute all operations, returning no results (w=0).\n        \"\"\"\n        if self.uses_collation:\n            raise ConfigurationError(\n                'Collation is unsupported for unacknowledged writes.')\n        if self.uses_array_filters:\n            raise ConfigurationError(\n                'arrayFilters is unsupported for unacknowledged writes.')\n        # Cannot have both unacknowledged writes and bypass document validation.\n        if self.bypass_doc_val and sock_info.max_wire_version >= 4:\n            raise OperationFailure(\"Cannot set bypass_document_validation with\"\n                                   \" unacknowledged write concern\")\n\n        # OP_MSG\n        if sock_info.max_wire_version > 5:\n            if self.ordered:\n                return self.execute_command_no_results(sock_info, generator)\n            return self.execute_op_msg_no_results(sock_info, generator)\n\n        coll = self.collection\n        # If ordered is True we have to send GLE or use write\n        # commands so we can abort on the first error.\n        write_concern = WriteConcern(w=int(self.ordered))\n        op_id = _randint()\n\n        next_run = next(generator)\n        while next_run:\n            # An ordered bulk write needs to send acknowledged writes to short\n            # circuit the next run. However, the final message on the final\n            # run can be unacknowledged.\n            run = next_run\n            next_run = next(generator, None)\n            needs_ack = self.ordered and next_run is not None\n            try:\n                if run.op_type == _INSERT:\n                    self.execute_insert_no_results(\n                        sock_info, run, op_id, needs_ack)\n                elif run.op_type == _UPDATE:\n                    for operation in run.ops:\n                        doc = operation['u']\n                        check_keys = True\n                        if doc and next(iter(doc)).startswith('$'):\n                            check_keys = False\n                        coll._update(\n                            sock_info,\n                            operation['q'],\n                            doc,\n                            operation['upsert'],\n                            check_keys,\n                            operation['multi'],\n                            write_concern=write_concern,\n                            op_id=op_id,\n                            ordered=self.ordered,\n                            bypass_doc_val=self.bypass_doc_val)\n                else:\n                    for operation in run.ops:\n                        coll._delete(sock_info,\n                                     operation['q'],\n                                     not operation['limit'],\n                                     write_concern,\n                                     op_id,\n                                     self.ordered)\n            except OperationFailure:\n                if self.ordered:\n                    break\n\n    def execute(self, write_concern, session):\n        \"\"\"Execute operations.\n        \"\"\"\n        if not self.ops:\n            raise InvalidOperation('No operations to execute')\n        if self.executed:\n            raise InvalidOperation('Bulk operations can '\n                                   'only be executed once.')\n        self.executed = True\n        write_concern = write_concern or self.collection.write_concern\n        session = _validate_session_write_concern(session, write_concern)\n\n        if self.ordered:\n            generator = self.gen_ordered()\n        else:\n            generator = self.gen_unordered()\n\n        client = self.collection.database.client\n        if not write_concern.acknowledged:\n            with client._socket_for_writes(session) as sock_info:\n                self.execute_no_results(sock_info, generator)\n        else:\n            return self.execute_command(generator, write_concern, session)\n\n\nclass BulkUpsertOperation(object):\n    \"\"\"An interface for adding upsert operations.\n    \"\"\"\n\n    __slots__ = ('__selector', '__bulk', '__collation')\n\n    def __init__(self, selector, bulk, collation):\n        self.__selector = selector\n        self.__bulk = bulk\n        self.__collation = collation\n\n    def update_one(self, update):\n        \"\"\"Update one document matching the selector.\n\n        :Parameters:\n          - `update` (dict): the update operations to apply\n        \"\"\"\n        self.__bulk.add_update(self.__selector,\n                               update, multi=False, upsert=True,\n                               collation=self.__collation)\n\n    def update(self, update):\n        \"\"\"Update all documents matching the selector.\n\n        :Parameters:\n          - `update` (dict): the update operations to apply\n        \"\"\"\n        self.__bulk.add_update(self.__selector,\n                               update, multi=True, upsert=True,\n                               collation=self.__collation)\n\n    def replace_one(self, replacement):\n        \"\"\"Replace one entire document matching the selector criteria.\n\n        :Parameters:\n          - `replacement` (dict): the replacement document\n        \"\"\"\n        self.__bulk.add_replace(self.__selector, replacement, upsert=True,\n                                collation=self.__collation)\n\n\nclass BulkWriteOperation(object):\n    \"\"\"An interface for adding update or remove operations.\n    \"\"\"\n\n    __slots__ = ('__selector', '__bulk', '__collation')\n\n    def __init__(self, selector, bulk, collation):\n        self.__selector = selector\n        self.__bulk = bulk\n        self.__collation = collation\n\n    def update_one(self, update):\n        \"\"\"Update one document matching the selector criteria.\n\n        :Parameters:\n          - `update` (dict): the update operations to apply\n        \"\"\"\n        self.__bulk.add_update(self.__selector, update, multi=False,\n                               collation=self.__collation)\n\n    def update(self, update):\n        \"\"\"Update all documents matching the selector criteria.\n\n        :Parameters:\n          - `update` (dict): the update operations to apply\n        \"\"\"\n        self.__bulk.add_update(self.__selector, update, multi=True,\n                               collation=self.__collation)\n\n    def replace_one(self, replacement):\n        \"\"\"Replace one entire document matching the selector criteria.\n\n        :Parameters:\n          - `replacement` (dict): the replacement document\n        \"\"\"\n        self.__bulk.add_replace(self.__selector, replacement,\n                                collation=self.__collation)\n\n    def remove_one(self):\n        \"\"\"Remove a single document matching the selector criteria.\n        \"\"\"\n        self.__bulk.add_delete(self.__selector, _DELETE_ONE,\n                               collation=self.__collation)\n\n    def remove(self):\n        \"\"\"Remove all documents matching the selector criteria.\n        \"\"\"\n        self.__bulk.add_delete(self.__selector, _DELETE_ALL,\n                               collation=self.__collation)\n\n    def upsert(self):\n        \"\"\"Specify that all chained update operations should be\n        upserts.\n\n        :Returns:\n          - A :class:`BulkUpsertOperation` instance, used to add\n            update operations to this bulk operation.\n        \"\"\"\n        return BulkUpsertOperation(self.__selector, self.__bulk,\n                                   self.__collation)\n\n\nclass BulkOperationBuilder(object):\n    \"\"\"**DEPRECATED**: An interface for executing a batch of write operations.\n    \"\"\"\n\n    __slots__ = '__bulk'\n\n    def __init__(self, collection, ordered=True,\n                 bypass_document_validation=False):\n        \"\"\"**DEPRECATED**: Initialize a new BulkOperationBuilder instance.\n\n        :Parameters:\n          - `collection`: A :class:`~pymongo.collection.Collection` instance.\n          - `ordered` (optional): If ``True`` all operations will be executed\n            serially, in the order provided, and the entire execution will\n            abort on the first error. If ``False`` operations will be executed\n            in arbitrary order (possibly in parallel on the server), reporting\n            any errors that occurred after attempting all operations. Defaults\n            to ``True``.\n          - `bypass_document_validation`: (optional) If ``True``, allows the\n            write to opt-out of document level validation. Default is\n            ``False``.\n\n        .. note:: `bypass_document_validation` requires server version\n          **>= 3.2**\n\n        .. versionchanged:: 3.5\n           Deprecated. Use :meth:`~pymongo.collection.Collection.bulk_write`\n           instead.\n\n        .. versionchanged:: 3.2\n          Added bypass_document_validation support\n        \"\"\"\n        self.__bulk = _Bulk(collection, ordered, bypass_document_validation)\n\n    def find(self, selector, collation=None):\n        \"\"\"Specify selection criteria for bulk operations.\n\n        :Parameters:\n          - `selector` (dict): the selection criteria for update\n            and remove operations.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only\n            supported on MongoDB 3.4 and above.\n\n        :Returns:\n          - A :class:`BulkWriteOperation` instance, used to add\n            update and remove operations to this bulk operation.\n\n        .. versionchanged:: 3.4\n           Added the `collation` option.\n\n        \"\"\"\n        validate_is_mapping(\"selector\", selector)\n        return BulkWriteOperation(selector, self.__bulk, collation)\n\n    def insert(self, document):\n        \"\"\"Insert a single document.\n\n        :Parameters:\n          - `document` (dict): the document to insert\n\n        .. seealso:: :ref:`writes-and-ids`\n        \"\"\"\n        self.__bulk.add_insert(document)\n\n    def execute(self, write_concern=None):\n        \"\"\"Execute all provided operations.\n\n        :Parameters:\n          - write_concern (optional): the write concern for this bulk\n            execution.\n        \"\"\"\n        if write_concern is not None:\n            write_concern = WriteConcern(**write_concern)\n        return self.__bulk.execute(write_concern, session=None)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/change_stream.py",
    "content": "# Copyright 2017 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Watch changes on a collection, a database, or the entire cluster.\"\"\"\n\nimport copy\n\nfrom bson import _bson_to_dict\nfrom bson.raw_bson import RawBSONDocument\n\nfrom pymongo import common\nfrom pymongo.aggregation import (_CollectionAggregationCommand,\n                                 _DatabaseAggregationCommand)\nfrom pymongo.collation import validate_collation_or_none\nfrom pymongo.command_cursor import CommandCursor\nfrom pymongo.errors import (ConnectionFailure,\n                            InvalidOperation,\n                            OperationFailure,\n                            PyMongoError)\n\n\n# The change streams spec considers the following server errors from the\n# getMore command non-resumable. All other getMore errors are resumable.\n_NON_RESUMABLE_GETMORE_ERRORS = frozenset([\n    11601,  # Interrupted\n    136,    # CappedPositionLost\n    237,    # CursorKilled\n    None,   # No error code was returned.\n])\n\n\nclass ChangeStream(object):\n    \"\"\"The internal abstract base class for change stream cursors.\n\n    Should not be called directly by application developers. Use \n    :meth:`pymongo.collection.Collection.watch`,\n    :meth:`pymongo.database.Database.watch`, or\n    :meth:`pymongo.mongo_client.MongoClient.watch` instead.\n\n    .. versionadded:: 3.6\n    .. mongodoc:: changeStreams\n    \"\"\"\n    def __init__(self, target, pipeline, full_document, resume_after,\n                 max_await_time_ms, batch_size, collation,\n                 start_at_operation_time, session, start_after):\n        if pipeline is None:\n            pipeline = []\n        elif not isinstance(pipeline, list):\n            raise TypeError(\"pipeline must be a list\")\n\n        common.validate_string_or_none('full_document', full_document)\n        validate_collation_or_none(collation)\n        common.validate_non_negative_integer_or_none(\"batchSize\", batch_size)\n\n        self._decode_custom = False\n        self._orig_codec_options = target.codec_options\n        if target.codec_options.type_registry._decoder_map:\n            self._decode_custom = True\n            # Keep the type registry so that we support encoding custom types\n            # in the pipeline.\n            self._target = target.with_options(\n                codec_options=target.codec_options.with_options(\n                    document_class=RawBSONDocument))\n        else:\n            self._target = target\n\n        self._pipeline = copy.deepcopy(pipeline)\n        self._full_document = full_document\n        self._uses_start_after = start_after is not None\n        self._uses_resume_after = resume_after is not None\n        self._resume_token = copy.deepcopy(start_after or resume_after)\n        self._max_await_time_ms = max_await_time_ms\n        self._batch_size = batch_size\n        self._collation = collation\n        self._start_at_operation_time = start_at_operation_time\n        self._session = session\n\n        # Initialize cursor.\n        self._cursor = self._create_cursor()\n\n    @property\n    def _aggregation_command_class(self):\n        \"\"\"The aggregation command class to be used.\"\"\"\n        raise NotImplementedError\n\n    @property\n    def _client(self):\n        \"\"\"The client against which the aggregation commands for\n        this ChangeStream will be run. \"\"\"\n        raise NotImplementedError\n\n    def _change_stream_options(self):\n        \"\"\"Return the options dict for the $changeStream pipeline stage.\"\"\"\n        options = {}\n        if self._full_document is not None:\n            options['fullDocument'] = self._full_document\n\n        resume_token = self.resume_token\n        if resume_token is not None:\n            if self._uses_start_after:\n                options['startAfter'] = resume_token\n            if self._uses_resume_after:\n                options['resumeAfter'] = resume_token\n\n        if self._start_at_operation_time is not None:\n            options['startAtOperationTime'] = self._start_at_operation_time\n        return options\n\n    def _command_options(self):\n        \"\"\"Return the options dict for the aggregation command.\"\"\"\n        options = {}\n        if self._max_await_time_ms is not None:\n            options[\"maxAwaitTimeMS\"] = self._max_await_time_ms\n        if self._batch_size is not None:\n            options[\"batchSize\"] = self._batch_size\n        return options\n\n    def _aggregation_pipeline(self):\n        \"\"\"Return the full aggregation pipeline for this ChangeStream.\"\"\"\n        options = self._change_stream_options()\n        full_pipeline = [{'$changeStream': options}]\n        full_pipeline.extend(self._pipeline)\n        return full_pipeline\n\n    def _process_result(self, result, session, server, sock_info, slave_ok):\n        \"\"\"Callback that caches the startAtOperationTime from a changeStream\n        aggregate command response containing an empty batch of change\n        documents.\n\n        This is implemented as a callback because we need access to the wire\n        version in order to determine whether to cache this value.\n        \"\"\"\n        if not result['cursor']['firstBatch']:\n            if (self._start_at_operation_time is None and\n                    self.resume_token is None and\n                    sock_info.max_wire_version >= 7):\n                self._start_at_operation_time = result[\"operationTime\"]\n\n    def _run_aggregation_cmd(self, session, explicit_session):\n        \"\"\"Run the full aggregation pipeline for this ChangeStream and return\n        the corresponding CommandCursor.\n        \"\"\"\n        cmd = self._aggregation_command_class(\n            self._target, CommandCursor, self._aggregation_pipeline(),\n            self._command_options(), explicit_session,\n            result_processor=self._process_result)\n\n        return self._client._retryable_read(\n            cmd.get_cursor, self._target._read_preference_for(session),\n            session)\n\n    def _create_cursor(self):\n        with self._client._tmp_session(self._session, close=False) as s:\n            return self._run_aggregation_cmd(\n                session=s,\n                explicit_session=self._session is not None)\n\n    def _resume(self):\n        \"\"\"Reestablish this change stream after a resumable error.\"\"\"\n        try:\n            self._cursor.close()\n        except PyMongoError:\n            pass\n        self._cursor = self._create_cursor()\n\n    def close(self):\n        \"\"\"Close this ChangeStream.\"\"\"\n        self._cursor.close()\n\n    def __iter__(self):\n        return self\n\n    @property\n    def resume_token(self):\n        \"\"\"The cached resume token that will be used to resume after the most\n        recently returned change.\n\n        .. versionadded:: 3.9\n        \"\"\"\n        return copy.deepcopy(self._resume_token)\n\n    def next(self):\n        \"\"\"Advance the cursor.\n\n        This method blocks until the next change document is returned or an\n        unrecoverable error is raised. This method is used when iterating over\n        all changes in the cursor. For example::\n\n            try:\n                resume_token = None\n                pipeline = [{'$match': {'operationType': 'insert'}}]\n                with db.collection.watch(pipeline) as stream:\n                    for insert_change in stream:\n                        print(insert_change)\n                        resume_token = stream.resume_token\n            except pymongo.errors.PyMongoError:\n                # The ChangeStream encountered an unrecoverable error or the\n                # resume attempt failed to recreate the cursor.\n                if resume_token is None:\n                    # There is no usable resume token because there was a\n                    # failure during ChangeStream initialization.\n                    logging.error('...')\n                else:\n                    # Use the interrupted ChangeStream's resume token to create\n                    # a new ChangeStream. The new stream will continue from the\n                    # last seen insert change without missing any events.\n                    with db.collection.watch(\n                            pipeline, resume_after=resume_token) as stream:\n                        for insert_change in stream:\n                            print(insert_change)\n\n        Raises :exc:`StopIteration` if this ChangeStream is closed.\n        \"\"\"\n        while self.alive:\n            doc = self.try_next()\n            if doc is not None:\n                return doc\n\n        raise StopIteration\n\n    __next__ = next\n\n    @property\n    def alive(self):\n        \"\"\"Does this cursor have the potential to return more data?\n\n        .. note:: Even if :attr:`alive` is ``True``, :meth:`next` can raise\n            :exc:`StopIteration` and :meth:`try_next` can return ``None``.\n\n        .. versionadded:: 3.8\n        \"\"\"\n        return self._cursor.alive\n\n    def try_next(self):\n        \"\"\"Advance the cursor without blocking indefinitely.\n\n        This method returns the next change document without waiting\n        indefinitely for the next change. For example::\n\n            with db.collection.watch() as stream:\n                while stream.alive:\n                    change = stream.try_next()\n                    # Note that the ChangeStream's resume token may be updated\n                    # even when no changes are returned.\n                    print(\"Current resume token: %r\" % (stream.resume_token,))\n                    if change is not None:\n                        print(\"Change document: %r\" % (change,))\n                        continue\n                    # We end up here when there are no recent changes.\n                    # Sleep for a while before trying again to avoid flooding\n                    # the server with getMore requests when no changes are\n                    # available.\n                    time.sleep(10)\n\n        If no change document is cached locally then this method runs a single\n        getMore command. If the getMore yields any documents, the next\n        document is returned, otherwise, if the getMore returns no documents\n        (because there have been no changes) then ``None`` is returned.\n\n        :Returns:\n          The next change document or ``None`` when no document is available\n          after running a single getMore or when the cursor is closed.\n\n        .. versionadded:: 3.8\n        \"\"\"\n        # Attempt to get the next change with at most one getMore and at most\n        # one resume attempt.\n        try:\n            change = self._cursor._try_next(True)\n        except ConnectionFailure:\n            self._resume()\n            change = self._cursor._try_next(False)\n        except OperationFailure as exc:\n            if (exc.code in _NON_RESUMABLE_GETMORE_ERRORS or\n                    exc.has_error_label(\"NonResumableChangeStreamError\")):\n                raise\n            self._resume()\n            change = self._cursor._try_next(False)\n\n        # If no changes are available.\n        if change is None:\n            # We have either iterated over all documents in the cursor,\n            # OR the most-recently returned batch is empty. In either case,\n            # update the cached resume token with the postBatchResumeToken if\n            # one was returned. We also clear the startAtOperationTime.\n            if self._cursor._post_batch_resume_token is not None:\n                self._resume_token = self._cursor._post_batch_resume_token\n                self._start_at_operation_time = None\n            return change\n\n        # Else, changes are available.\n        try:\n            resume_token = change['_id']\n        except KeyError:\n            self.close()\n            raise InvalidOperation(\n                \"Cannot provide resume functionality when the resume \"\n                \"token is missing.\")\n\n        # If this is the last change document from the current batch, cache the\n        # postBatchResumeToken.\n        if (not self._cursor._has_next() and\n                self._cursor._post_batch_resume_token):\n            resume_token = self._cursor._post_batch_resume_token\n\n        # Hereafter, don't use startAfter; instead use resumeAfter.\n        self._uses_start_after = False\n        self._uses_resume_after = True\n\n        # Cache the resume token and clear startAtOperationTime.\n        self._resume_token = resume_token\n        self._start_at_operation_time = None\n\n        if self._decode_custom:\n            return _bson_to_dict(change.raw, self._orig_codec_options)\n        return change\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        self.close()\n\n\nclass CollectionChangeStream(ChangeStream):\n    \"\"\"A change stream that watches changes on a single collection.\n\n    Should not be called directly by application developers. Use\n    helper method :meth:`pymongo.collection.Collection.watch` instead.\n\n    .. versionadded:: 3.7\n    \"\"\"\n    @property\n    def _aggregation_command_class(self):\n        return _CollectionAggregationCommand\n\n    @property\n    def _client(self):\n        return self._target.database.client\n\n\nclass DatabaseChangeStream(ChangeStream):\n    \"\"\"A change stream that watches changes on all collections in a database.\n\n    Should not be called directly by application developers. Use\n    helper method :meth:`pymongo.database.Database.watch` instead.\n\n    .. versionadded:: 3.7\n    \"\"\"\n    @property\n    def _aggregation_command_class(self):\n        return _DatabaseAggregationCommand\n\n    @property\n    def _client(self):\n        return self._target.client\n\n\nclass ClusterChangeStream(DatabaseChangeStream):\n    \"\"\"A change stream that watches changes on all collections in the cluster.\n\n    Should not be called directly by application developers. Use\n    helper method :meth:`pymongo.mongo_client.MongoClient.watch` instead.\n\n    .. versionadded:: 3.7\n    \"\"\"\n    def _change_stream_options(self):\n        options = super(ClusterChangeStream, self)._change_stream_options()\n        options[\"allChangesForCluster\"] = True\n        return options\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/client_options.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Tools to parse mongo client options.\"\"\"\n\nfrom bson.codec_options import _parse_codec_options\nfrom pymongo.auth import _build_credentials_tuple\nfrom pymongo.common import validate_boolean\nfrom pymongo import common\nfrom pymongo.compression_support import CompressionSettings\nfrom pymongo.errors import ConfigurationError\nfrom pymongo.monitoring import _EventListeners\nfrom pymongo.pool import PoolOptions\nfrom pymongo.read_concern import ReadConcern\nfrom pymongo.read_preferences import (make_read_preference,\n                                      read_pref_mode_from_name)\nfrom pymongo.server_selectors import any_server_selector\nfrom pymongo.ssl_support import get_ssl_context\nfrom pymongo.write_concern import WriteConcern\n\n\ndef _parse_credentials(username, password, database, options):\n    \"\"\"Parse authentication credentials.\"\"\"\n    mechanism = options.get('authmechanism', 'DEFAULT' if username else None)\n    source = options.get('authsource')\n    if username or mechanism:\n        return _build_credentials_tuple(\n            mechanism, source, username, password, options, database)\n    return None\n\n\ndef _parse_read_preference(options):\n    \"\"\"Parse read preference options.\"\"\"\n    if 'read_preference' in options:\n        return options['read_preference']\n\n    name = options.get('readpreference', 'primary')\n    mode = read_pref_mode_from_name(name)\n    tags = options.get('readpreferencetags')\n    max_staleness = options.get('maxstalenessseconds', -1)\n    return make_read_preference(mode, tags, max_staleness)\n\n\ndef _parse_write_concern(options):\n    \"\"\"Parse write concern options.\"\"\"\n    concern = options.get('w')\n    wtimeout = options.get('wtimeoutms')\n    j = options.get('journal')\n    fsync = options.get('fsync')\n    return WriteConcern(concern, wtimeout, j, fsync)\n\n\ndef _parse_read_concern(options):\n    \"\"\"Parse read concern options.\"\"\"\n    concern = options.get('readconcernlevel')\n    return ReadConcern(concern)\n\n\ndef _parse_ssl_options(options):\n    \"\"\"Parse ssl options.\"\"\"\n    use_ssl = options.get('ssl')\n    if use_ssl is not None:\n        validate_boolean('ssl', use_ssl)\n\n    certfile = options.get('ssl_certfile')\n    keyfile = options.get('ssl_keyfile')\n    passphrase = options.get('ssl_pem_passphrase')\n    ca_certs = options.get('ssl_ca_certs')\n    cert_reqs = options.get('ssl_cert_reqs')\n    match_hostname = options.get('ssl_match_hostname', True)\n    crlfile = options.get('ssl_crlfile')\n\n    ssl_kwarg_keys = [k for k in options\n                      if k.startswith('ssl_') and options[k]]\n    if use_ssl == False and ssl_kwarg_keys:\n        raise ConfigurationError(\"ssl has not been enabled but the \"\n                                 \"following ssl parameters have been set: \"\n                                 \"%s. Please set `ssl=True` or remove.\"\n                                 % ', '.join(ssl_kwarg_keys))\n\n    if ssl_kwarg_keys and use_ssl is None:\n        # ssl options imply ssl = True\n        use_ssl = True\n\n    if use_ssl is True:\n        ctx = get_ssl_context(\n            certfile,\n            keyfile,\n            passphrase,\n            ca_certs,\n            cert_reqs,\n            crlfile,\n            match_hostname)\n        return ctx, match_hostname\n    return None, match_hostname\n\n\ndef _parse_pool_options(options):\n    \"\"\"Parse connection pool options.\"\"\"\n    max_pool_size = options.get('maxpoolsize', common.MAX_POOL_SIZE)\n    min_pool_size = options.get('minpoolsize', common.MIN_POOL_SIZE)\n    max_idle_time_seconds = options.get(\n        'maxidletimems', common.MAX_IDLE_TIME_SEC)\n    if max_pool_size is not None and min_pool_size > max_pool_size:\n        raise ValueError(\"minPoolSize must be smaller or equal to maxPoolSize\")\n    connect_timeout = options.get('connecttimeoutms', common.CONNECT_TIMEOUT)\n    socket_keepalive = options.get('socketkeepalive', True)\n    socket_timeout = options.get('sockettimeoutms')\n    wait_queue_timeout = options.get(\n        'waitqueuetimeoutms', common.WAIT_QUEUE_TIMEOUT)\n    wait_queue_multiple = options.get('waitqueuemultiple')\n    event_listeners = options.get('event_listeners')\n    appname = options.get('appname')\n    driver = options.get('driver')\n    compression_settings = CompressionSettings(\n        options.get('compressors', []),\n        options.get('zlibcompressionlevel', -1))\n    ssl_context, ssl_match_hostname = _parse_ssl_options(options)\n    return PoolOptions(max_pool_size,\n                       min_pool_size,\n                       max_idle_time_seconds,\n                       connect_timeout, socket_timeout,\n                       wait_queue_timeout, wait_queue_multiple,\n                       ssl_context, ssl_match_hostname, socket_keepalive,\n                       _EventListeners(event_listeners),\n                       appname,\n                       driver,\n                       compression_settings)\n\n\nclass ClientOptions(object):\n\n    \"\"\"ClientOptions\"\"\"\n\n    def __init__(self, username, password, database, options):\n        self.__options = options\n\n        self.__codec_options = _parse_codec_options(options)\n        self.__credentials = _parse_credentials(\n            username, password, database, options)\n        self.__local_threshold_ms = options.get(\n            'localthresholdms', common.LOCAL_THRESHOLD_MS)\n        # self.__server_selection_timeout is in seconds. Must use full name for\n        # common.SERVER_SELECTION_TIMEOUT because it is set directly by tests.\n        self.__server_selection_timeout = options.get(\n            'serverselectiontimeoutms', common.SERVER_SELECTION_TIMEOUT)\n        self.__pool_options = _parse_pool_options(options)\n        self.__read_preference = _parse_read_preference(options)\n        self.__replica_set_name = options.get('replicaset')\n        self.__write_concern = _parse_write_concern(options)\n        self.__read_concern = _parse_read_concern(options)\n        self.__connect = options.get('connect')\n        self.__heartbeat_frequency = options.get(\n            'heartbeatfrequencyms', common.HEARTBEAT_FREQUENCY)\n        self.__retry_writes = options.get('retrywrites', common.RETRY_WRITES)\n        self.__retry_reads = options.get('retryreads', common.RETRY_READS)\n        self.__server_selector = options.get(\n            'server_selector', any_server_selector)\n        self.__auto_encryption_opts = options.get('auto_encryption_opts')\n\n    @property\n    def _options(self):\n        \"\"\"The original options used to create this ClientOptions.\"\"\"\n        return self.__options\n\n    @property\n    def connect(self):\n        \"\"\"Whether to begin discovering a MongoDB topology automatically.\"\"\"\n        return self.__connect\n\n    @property\n    def codec_options(self):\n        \"\"\"A :class:`~bson.codec_options.CodecOptions` instance.\"\"\"\n        return self.__codec_options\n\n    @property\n    def credentials(self):\n        \"\"\"A :class:`~pymongo.auth.MongoCredentials` instance or None.\"\"\"\n        return self.__credentials\n\n    @property\n    def local_threshold_ms(self):\n        \"\"\"The local threshold for this instance.\"\"\"\n        return self.__local_threshold_ms\n\n    @property\n    def server_selection_timeout(self):\n        \"\"\"The server selection timeout for this instance in seconds.\"\"\"\n        return self.__server_selection_timeout\n\n    @property\n    def server_selector(self):\n        return self.__server_selector\n\n    @property\n    def heartbeat_frequency(self):\n        \"\"\"The monitoring frequency in seconds.\"\"\"\n        return self.__heartbeat_frequency\n\n    @property\n    def pool_options(self):\n        \"\"\"A :class:`~pymongo.pool.PoolOptions` instance.\"\"\"\n        return self.__pool_options\n\n    @property\n    def read_preference(self):\n        \"\"\"A read preference instance.\"\"\"\n        return self.__read_preference\n\n    @property\n    def replica_set_name(self):\n        \"\"\"Replica set name or None.\"\"\"\n        return self.__replica_set_name\n\n    @property\n    def write_concern(self):\n        \"\"\"A :class:`~pymongo.write_concern.WriteConcern` instance.\"\"\"\n        return self.__write_concern\n\n    @property\n    def read_concern(self):\n        \"\"\"A :class:`~pymongo.read_concern.ReadConcern` instance.\"\"\"\n        return self.__read_concern\n\n    @property\n    def retry_writes(self):\n        \"\"\"If this instance should retry supported write operations.\"\"\"\n        return self.__retry_writes\n\n    @property\n    def retry_reads(self):\n        \"\"\"If this instance should retry supported read operations.\"\"\"\n        return self.__retry_reads\n\n    @property\n    def auto_encryption_opts(self):\n        \"\"\"A :class:`~pymongo.encryption.AutoEncryptionOpts` or None.\"\"\"\n        return self.__auto_encryption_opts\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/client_session.py",
    "content": "# Copyright 2017 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Logical sessions for ordering sequential operations.\n\nRequires MongoDB 3.6.\n\n.. versionadded:: 3.6\n\nCausally Consistent Reads\n=========================\n\n.. code-block:: python\n\n  with client.start_session(causal_consistency=True) as session:\n      collection = client.db.collection\n      collection.update_one({'_id': 1}, {'$set': {'x': 10}}, session=session)\n      secondary_c = collection.with_options(\n          read_preference=ReadPreference.SECONDARY)\n\n      # A secondary read waits for replication of the write.\n      secondary_c.find_one({'_id': 1}, session=session)\n\nIf `causal_consistency` is True (the default), read operations that use\nthe session are causally after previous read and write operations. Using a\ncausally consistent session, an application can read its own writes and is\nguaranteed monotonic reads, even when reading from replica set secondaries.\n\n.. mongodoc:: causal-consistency\n\n.. _transactions-ref:\n\nTransactions\n============\n\nMongoDB 4.0 adds support for transactions on replica set primaries. A\ntransaction is associated with a :class:`ClientSession`. To start a transaction\non a session, use :meth:`ClientSession.start_transaction` in a with-statement.\nThen, execute an operation within the transaction by passing the session to the\noperation:\n\n.. code-block:: python\n\n  orders = client.db.orders\n  inventory = client.db.inventory\n  with client.start_session() as session:\n      with session.start_transaction():\n          orders.insert_one({\"sku\": \"abc123\", \"qty\": 100}, session=session)\n          inventory.update_one({\"sku\": \"abc123\", \"qty\": {\"$gte\": 100}},\n                               {\"$inc\": {\"qty\": -100}}, session=session)\n\nUpon normal completion of ``with session.start_transaction()`` block, the\ntransaction automatically calls :meth:`ClientSession.commit_transaction`.\nIf the block exits with an exception, the transaction automatically calls\n:meth:`ClientSession.abort_transaction`.\n\nFor multi-document transactions, you can only specify read/write (CRUD)\noperations on existing collections. For example, a multi-document transaction\ncannot include a create or drop collection/index operations, including an\ninsert operation that would result in the creation of a new collection.\n\nA session may only have a single active transaction at a time, multiple\ntransactions on the same session can be executed in sequence.\n\n.. versionadded:: 3.7\n\nSharded Transactions\n^^^^^^^^^^^^^^^^^^^^\n\nPyMongo 3.9 adds support for transactions on sharded clusters running MongoDB\n4.2. Sharded transactions have the same API as replica set transactions.\nWhen running a transaction against a sharded cluster, the session is\npinned to the mongos server selected for the first operation in the\ntransaction. All subsequent operations that are part of the same transaction\nare routed to the same mongos server. When the transaction is completed, by\nrunning either commitTransaction or abortTransaction, the session is unpinned.\n\n.. versionadded:: 3.9\n\n.. mongodoc:: transactions\n\nClasses\n=======\n\"\"\"\n\nimport collections\nimport sys\nimport uuid\n\nfrom bson.binary import Binary\nfrom bson.int64 import Int64\nfrom bson.py3compat import abc, integer_types, reraise_instance\nfrom bson.son import SON\nfrom bson.timestamp import Timestamp\n\nfrom pymongo import monotonic\nfrom pymongo.errors import (ConfigurationError,\n                            ConnectionFailure,\n                            InvalidOperation,\n                            OperationFailure,\n                            PyMongoError,\n                            ServerSelectionTimeoutError,\n                            WTimeoutError)\nfrom pymongo.helpers import _RETRYABLE_ERROR_CODES\nfrom pymongo.read_concern import ReadConcern\nfrom pymongo.read_preferences import ReadPreference, _ServerMode\nfrom pymongo.write_concern import WriteConcern\n\n\nclass SessionOptions(object):\n    \"\"\"Options for a new :class:`ClientSession`.\n\n    :Parameters:\n      - `causal_consistency` (optional): If True (the default), read\n        operations are causally ordered within the session.\n      - `default_transaction_options` (optional): The default\n        TransactionOptions to use for transactions started on this session.\n    \"\"\"\n    def __init__(self,\n                 causal_consistency=True,\n                 default_transaction_options=None):\n        self._causal_consistency = causal_consistency\n        if default_transaction_options is not None:\n            if not isinstance(default_transaction_options, TransactionOptions):\n                raise TypeError(\n                    \"default_transaction_options must be an instance of \"\n                    \"pymongo.client_session.TransactionOptions, not: %r\" %\n                    (default_transaction_options,))\n        self._default_transaction_options = default_transaction_options\n\n    @property\n    def causal_consistency(self):\n        \"\"\"Whether causal consistency is configured.\"\"\"\n        return self._causal_consistency\n\n    @property\n    def default_transaction_options(self):\n        \"\"\"The default TransactionOptions to use for transactions started on\n        this session.\n\n        .. versionadded:: 3.7\n        \"\"\"\n        return self._default_transaction_options\n\n\nclass TransactionOptions(object):\n    \"\"\"Options for :meth:`ClientSession.start_transaction`.\n    \n    :Parameters:\n      - `read_concern` (optional): The\n        :class:`~pymongo.read_concern.ReadConcern` to use for this transaction.\n        If ``None`` (the default) the :attr:`read_preference` of\n        the :class:`MongoClient` is used.\n      - `write_concern` (optional): The\n        :class:`~pymongo.write_concern.WriteConcern` to use for this\n        transaction. If ``None`` (the default) the :attr:`read_preference` of\n        the :class:`MongoClient` is used.\n      - `read_preference` (optional): The read preference to use. If\n        ``None`` (the default) the :attr:`read_preference` of this\n        :class:`MongoClient` is used. See :mod:`~pymongo.read_preferences`\n        for options. Transactions which read must use\n        :attr:`~pymongo.read_preferences.ReadPreference.PRIMARY`.\n      - `max_commit_time_ms` (optional): The maximum amount of time to allow a\n        single commitTransaction command to run. This option is an alias for\n        maxTimeMS option on the commitTransaction command. If ``None`` (the\n        default) maxTimeMS is not used.\n\n    .. versionchanged:: 3.9\n       Added the ``max_commit_time_ms`` option.\n\n    .. versionadded:: 3.7\n    \"\"\"\n    def __init__(self, read_concern=None, write_concern=None,\n                 read_preference=None, max_commit_time_ms=None):\n        self._read_concern = read_concern\n        self._write_concern = write_concern\n        self._read_preference = read_preference\n        self._max_commit_time_ms = max_commit_time_ms\n        if read_concern is not None:\n            if not isinstance(read_concern, ReadConcern):\n                raise TypeError(\"read_concern must be an instance of \"\n                                \"pymongo.read_concern.ReadConcern, not: %r\" %\n                                (read_concern,))\n        if write_concern is not None:\n            if not isinstance(write_concern, WriteConcern):\n                raise TypeError(\"write_concern must be an instance of \"\n                                \"pymongo.write_concern.WriteConcern, not: %r\" %\n                                (write_concern,))\n            if not write_concern.acknowledged:\n                raise ConfigurationError(\n                    \"transactions do not support unacknowledged write concern\"\n                    \": %r\" % (write_concern,))\n        if read_preference is not None:\n            if not isinstance(read_preference, _ServerMode):\n                raise TypeError(\"%r is not valid for read_preference. See \"\n                                \"pymongo.read_preferences for valid \"\n                                \"options.\" % (read_preference,))\n        if max_commit_time_ms is not None:\n            if not isinstance(max_commit_time_ms, integer_types):\n                raise TypeError(\n                    \"max_commit_time_ms must be an integer or None\")\n\n    @property\n    def read_concern(self):\n        \"\"\"This transaction's :class:`~pymongo.read_concern.ReadConcern`.\"\"\"\n        return self._read_concern\n\n    @property\n    def write_concern(self):\n        \"\"\"This transaction's :class:`~pymongo.write_concern.WriteConcern`.\"\"\"\n        return self._write_concern\n\n    @property\n    def read_preference(self):\n        \"\"\"This transaction's :class:`~pymongo.read_preferences.ReadPreference`.\n        \"\"\"\n        return self._read_preference\n\n    @property\n    def max_commit_time_ms(self):\n        \"\"\"The maxTimeMS to use when running a commitTransaction command.\n\n        .. versionadded:: 3.9\n        \"\"\"\n        return self._max_commit_time_ms\n\n\ndef _validate_session_write_concern(session, write_concern):\n    \"\"\"Validate that an explicit session is not used with an unack'ed write.\n\n    Returns the session to use for the next operation.\n    \"\"\"\n    if session:\n        if write_concern is not None and not write_concern.acknowledged:\n            # For unacknowledged writes without an explicit session,\n            # drivers SHOULD NOT use an implicit session. If a driver\n            # creates an implicit session for unacknowledged writes\n            # without an explicit session, the driver MUST NOT send the\n            # session ID.\n            if session._implicit:\n                return None\n            else:\n                raise ConfigurationError(\n                    'Explicit sessions are incompatible with '\n                    'unacknowledged write concern: %r' % (\n                        write_concern,))\n    return session\n\n\nclass _TransactionContext(object):\n    \"\"\"Internal transaction context manager for start_transaction.\"\"\"\n    def __init__(self, session):\n        self.__session = session\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        if self.__session._in_transaction:\n            if exc_val is None:\n                self.__session.commit_transaction()\n            else:\n                self.__session.abort_transaction()\n\n\nclass _TxnState(object):\n    NONE = 1\n    STARTING = 2\n    IN_PROGRESS = 3\n    COMMITTED = 4\n    COMMITTED_EMPTY = 5\n    ABORTED = 6\n\n\nclass _Transaction(object):\n    \"\"\"Internal class to hold transaction information in a ClientSession.\"\"\"\n    def __init__(self, opts):\n        self.opts = opts\n        self.state = _TxnState.NONE\n        self.sharded = False\n        self.pinned_address = None\n        self.recovery_token = None\n\n    def active(self):\n        return self.state in (_TxnState.STARTING, _TxnState.IN_PROGRESS)\n\n    def reset(self):\n        self.state = _TxnState.NONE\n        self.sharded = False\n        self.pinned_address = None\n        self.recovery_token = None\n\n\ndef _reraise_with_unknown_commit(exc):\n    \"\"\"Re-raise an exception with the UnknownTransactionCommitResult label.\"\"\"\n    exc._add_error_label(\"UnknownTransactionCommitResult\")\n    reraise_instance(exc, trace=sys.exc_info()[2])\n\n\ndef _max_time_expired_error(exc):\n    \"\"\"Return true if exc is a MaxTimeMSExpired error.\"\"\"\n    return isinstance(exc, OperationFailure) and exc.code == 50\n\n\n# From the transactions spec, all the retryable writes errors plus\n# WriteConcernFailed.\n_UNKNOWN_COMMIT_ERROR_CODES = _RETRYABLE_ERROR_CODES | frozenset([\n    64,    # WriteConcernFailed\n    50,    # MaxTimeMSExpired\n])\n\n# From the Convenient API for Transactions spec, with_transaction must\n# halt retries after 120 seconds.\n# This limit is non-configurable and was chosen to be twice the 60 second\n# default value of MongoDB's `transactionLifetimeLimitSeconds` parameter.\n_WITH_TRANSACTION_RETRY_TIME_LIMIT = 120\n\n\ndef _within_time_limit(start_time):\n    \"\"\"Are we within the with_transaction retry limit?\"\"\"\n    return monotonic.time() - start_time < _WITH_TRANSACTION_RETRY_TIME_LIMIT\n\n\nclass ClientSession(object):\n    \"\"\"A session for ordering sequential operations.\"\"\"\n    def __init__(self, client, server_session, options, authset, implicit):\n        # A MongoClient, a _ServerSession, a SessionOptions, and a set.\n        self._client = client\n        self._server_session = server_session\n        self._options = options\n        self._authset = authset\n        self._cluster_time = None\n        self._operation_time = None\n        # Is this an implicitly created session?\n        self._implicit = implicit\n        self._transaction = _Transaction(None)\n\n    def end_session(self):\n        \"\"\"Finish this session. If a transaction has started, abort it.\n\n        It is an error to use the session after the session has ended.\n        \"\"\"\n        self._end_session(lock=True)\n\n    def _end_session(self, lock):\n        if self._server_session is not None:\n            try:\n                if self._in_transaction:\n                    self.abort_transaction()\n            finally:\n                self._client._return_server_session(self._server_session, lock)\n                self._server_session = None\n\n    def _check_ended(self):\n        if self._server_session is None:\n            raise InvalidOperation(\"Cannot use ended session\")\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        self._end_session(lock=True)\n\n    @property\n    def client(self):\n        \"\"\"The :class:`~pymongo.mongo_client.MongoClient` this session was\n        created from.\n        \"\"\"\n        return self._client\n\n    @property\n    def options(self):\n        \"\"\"The :class:`SessionOptions` this session was created with.\"\"\"\n        return self._options\n\n    @property\n    def session_id(self):\n        \"\"\"A BSON document, the opaque server session identifier.\"\"\"\n        self._check_ended()\n        return self._server_session.session_id\n\n    @property\n    def cluster_time(self):\n        \"\"\"The cluster time returned by the last operation executed\n        in this session.\n        \"\"\"\n        return self._cluster_time\n\n    @property\n    def operation_time(self):\n        \"\"\"The operation time returned by the last operation executed\n        in this session.\n        \"\"\"\n        return self._operation_time\n\n    def _inherit_option(self, name, val):\n        \"\"\"Return the inherited TransactionOption value.\"\"\"\n        if val:\n            return val\n        txn_opts = self.options.default_transaction_options\n        val = txn_opts and getattr(txn_opts, name)\n        if val:\n            return val\n        return getattr(self.client, name)\n\n    def with_transaction(self, callback, read_concern=None, write_concern=None,\n                         read_preference=None, max_commit_time_ms=None):\n        \"\"\"Execute a callback in a transaction.\n\n        This method starts a transaction on this session, executes ``callback``\n        once, and then commits the transaction. For example::\n\n          def callback(session):\n              orders = session.client.db.orders\n              inventory = session.client.db.inventory\n              orders.insert_one({\"sku\": \"abc123\", \"qty\": 100}, session=session)\n              inventory.update_one({\"sku\": \"abc123\", \"qty\": {\"$gte\": 100}},\n                                   {\"$inc\": {\"qty\": -100}}, session=session)\n\n          with client.start_session() as session:\n              session.with_transaction(callback)\n\n        To pass arbitrary arguments to the ``callback``, wrap your callable\n        with a ``lambda`` like this::\n\n          def callback(session, custom_arg, custom_kwarg=None):\n              # Transaction operations...\n\n          with client.start_session() as session:\n              session.with_transaction(\n                  lambda s: callback(s, \"custom_arg\", custom_kwarg=1))\n\n        In the event of an exception, ``with_transaction`` may retry the commit\n        or the entire transaction, therefore ``callback`` may be invoked\n        multiple times by a single call to ``with_transaction``. Developers\n        should be mindful of this possiblity when writing a ``callback`` that\n        modifies application state or has any other side-effects.\n        Note that even when the ``callback`` is invoked multiple times,\n        ``with_transaction`` ensures that the transaction will be committed\n        at-most-once on the server.\n\n        The ``callback`` should not attempt to start new transactions, but\n        should simply run operations meant to be contained within a\n        transaction. The ``callback`` should also not commit the transaction;\n        this is handled automatically by ``with_transaction``. If the\n        ``callback`` does commit or abort the transaction without error,\n        however, ``with_transaction`` will return without taking further\n        action.\n\n        When ``callback`` raises an exception, ``with_transaction``\n        automatically aborts the current transaction. When ``callback`` or\n        :meth:`~ClientSession.commit_transaction` raises an exception that\n        includes the ``\"TransientTransactionError\"`` error label,\n        ``with_transaction`` starts a new transaction and re-executes\n        the ``callback``.\n\n        When :meth:`~ClientSession.commit_transaction` raises an exception with\n        the ``\"UnknownTransactionCommitResult\"`` error label,\n        ``with_transaction`` retries the commit until the result of the\n        transaction is known.\n\n        This method will cease retrying after 120 seconds has elapsed. This\n        timeout is not configurable and any exception raised by the\n        ``callback`` or by :meth:`ClientSession.commit_transaction` after the\n        timeout is reached will be re-raised. Applications that desire a\n        different timeout duration should not use this method.\n\n        :Parameters:\n          - `callback`: The callable ``callback`` to run inside a transaction.\n            The callable must accept a single argument, this session. Note,\n            under certain error conditions the callback may be run multiple\n            times.\n          - `read_concern` (optional): The\n            :class:`~pymongo.read_concern.ReadConcern` to use for this\n            transaction.\n          - `write_concern` (optional): The\n            :class:`~pymongo.write_concern.WriteConcern` to use for this\n            transaction.\n          - `read_preference` (optional): The read preference to use for this\n            transaction. If ``None`` (the default) the :attr:`read_preference`\n            of this :class:`Database` is used. See\n            :mod:`~pymongo.read_preferences` for options.\n\n        :Returns:\n          The return value of the ``callback``.\n\n        .. versionadded:: 3.9\n        \"\"\"\n        start_time = monotonic.time()\n        while True:\n            self.start_transaction(\n                read_concern, write_concern, read_preference,\n                max_commit_time_ms)\n            try:\n                ret = callback(self)\n            except Exception as exc:\n                if self._in_transaction:\n                    self.abort_transaction()\n                if (isinstance(exc, PyMongoError) and\n                        exc.has_error_label(\"TransientTransactionError\") and\n                        _within_time_limit(start_time)):\n                    # Retry the entire transaction.\n                    continue\n                raise\n\n            if self._transaction.state in (\n                    _TxnState.NONE, _TxnState.COMMITTED, _TxnState.ABORTED):\n                # Assume callback intentionally ended the transaction.\n                return ret\n\n            while True:\n                try:\n                    self.commit_transaction()\n                except PyMongoError as exc:\n                    if (exc.has_error_label(\"UnknownTransactionCommitResult\")\n                            and _within_time_limit(start_time)\n                            and not _max_time_expired_error(exc)):\n                        # Retry the commit.\n                        continue\n\n                    if (exc.has_error_label(\"TransientTransactionError\") and\n                            _within_time_limit(start_time)):\n                        # Retry the entire transaction.\n                        break\n                    raise\n\n                # Commit succeeded.\n                return ret\n\n    def start_transaction(self, read_concern=None, write_concern=None,\n                          read_preference=None, max_commit_time_ms=None):\n        \"\"\"Start a multi-statement transaction.\n\n        Takes the same arguments as :class:`TransactionOptions`.\n\n        .. versionchanged:: 3.9\n           Added the ``max_commit_time_ms`` option.\n\n        .. versionadded:: 3.7\n        \"\"\"\n        self._check_ended()\n\n        if self._in_transaction:\n            raise InvalidOperation(\"Transaction already in progress\")\n\n        read_concern = self._inherit_option(\"read_concern\", read_concern)\n        write_concern = self._inherit_option(\"write_concern\", write_concern)\n        read_preference = self._inherit_option(\n            \"read_preference\", read_preference)\n        if max_commit_time_ms is None:\n            opts = self.options.default_transaction_options\n            if opts:\n                max_commit_time_ms = opts.max_commit_time_ms\n\n        self._transaction.opts = TransactionOptions(\n            read_concern, write_concern, read_preference, max_commit_time_ms)\n        self._transaction.reset()\n        self._transaction.state = _TxnState.STARTING\n        self._start_retryable_write()\n        return _TransactionContext(self)\n\n    def commit_transaction(self):\n        \"\"\"Commit a multi-statement transaction.\n\n        .. versionadded:: 3.7\n        \"\"\"\n        self._check_ended()\n        retry = False\n        state = self._transaction.state\n        if state is _TxnState.NONE:\n            raise InvalidOperation(\"No transaction started\")\n        elif state in (_TxnState.STARTING, _TxnState.COMMITTED_EMPTY):\n            # Server transaction was never started, no need to send a command.\n            self._transaction.state = _TxnState.COMMITTED_EMPTY\n            return\n        elif state is _TxnState.ABORTED:\n            raise InvalidOperation(\n                \"Cannot call commitTransaction after calling abortTransaction\")\n        elif state is _TxnState.COMMITTED:\n            # We're explicitly retrying the commit, move the state back to\n            # \"in progress\" so that _in_transaction returns true.\n            self._transaction.state = _TxnState.IN_PROGRESS\n            retry = True\n\n        try:\n            self._finish_transaction_with_retry(\"commitTransaction\", retry)\n        except ConnectionFailure as exc:\n            # We do not know if the commit was successfully applied on the\n            # server or if it satisfied the provided write concern, set the\n            # unknown commit error label.\n            exc._remove_error_label(\"TransientTransactionError\")\n            _reraise_with_unknown_commit(exc)\n        except WTimeoutError as exc:\n            # We do not know if the commit has satisfied the provided write\n            # concern, add the unknown commit error label.\n            _reraise_with_unknown_commit(exc)\n        except OperationFailure as exc:\n            if exc.code not in _UNKNOWN_COMMIT_ERROR_CODES:\n                # The server reports errorLabels in the case.\n                raise\n            # We do not know if the commit was successfully applied on the\n            # server or if it satisfied the provided write concern, set the\n            # unknown commit error label.\n            _reraise_with_unknown_commit(exc)\n        finally:\n            self._transaction.state = _TxnState.COMMITTED\n\n    def abort_transaction(self):\n        \"\"\"Abort a multi-statement transaction.\n\n        .. versionadded:: 3.7\n        \"\"\"\n        self._check_ended()\n\n        state = self._transaction.state\n        if state is _TxnState.NONE:\n            raise InvalidOperation(\"No transaction started\")\n        elif state is _TxnState.STARTING:\n            # Server transaction was never started, no need to send a command.\n            self._transaction.state = _TxnState.ABORTED\n            return\n        elif state is _TxnState.ABORTED:\n            raise InvalidOperation(\"Cannot call abortTransaction twice\")\n        elif state in (_TxnState.COMMITTED, _TxnState.COMMITTED_EMPTY):\n            raise InvalidOperation(\n                \"Cannot call abortTransaction after calling commitTransaction\")\n\n        try:\n            self._finish_transaction_with_retry(\"abortTransaction\", False)\n        except (OperationFailure, ConnectionFailure):\n            # The transactions spec says to ignore abortTransaction errors.\n            pass\n        finally:\n            self._transaction.state = _TxnState.ABORTED\n\n    def _finish_transaction_with_retry(self, command_name, explict_retry):\n        \"\"\"Run commit or abort with one retry after any retryable error.\n\n        :Parameters:\n          - `command_name`: Either \"commitTransaction\" or \"abortTransaction\".\n          - `explict_retry`: True when this is an explict commit retry attempt,\n            ie the application called session.commit_transaction() twice.\n        \"\"\"\n        # This can be refactored with MongoClient._retry_with_session.\n        try:\n            return self._finish_transaction(command_name, explict_retry)\n        except ServerSelectionTimeoutError:\n            raise\n        except ConnectionFailure as exc:\n            try:\n                return self._finish_transaction(command_name, True)\n            except ServerSelectionTimeoutError:\n                # Raise the original error so the application can infer that\n                # an attempt was made.\n                raise exc\n        except OperationFailure as exc:\n            if exc.code not in _RETRYABLE_ERROR_CODES:\n                raise\n            try:\n                return self._finish_transaction(command_name, True)\n            except ServerSelectionTimeoutError:\n                # Raise the original error so the application can infer that\n                # an attempt was made.\n                raise exc\n\n    def _finish_transaction(self, command_name, retrying):\n        opts = self._transaction.opts\n        wc = opts.write_concern\n        cmd = SON([(command_name, 1)])\n        if command_name == \"commitTransaction\":\n            if opts.max_commit_time_ms:\n                cmd['maxTimeMS'] = opts.max_commit_time_ms\n\n            # Transaction spec says that after the initial commit attempt,\n            # subsequent commitTransaction commands should be upgraded to use\n            # w:\"majority\" and set a default value of 10 seconds for wtimeout.\n            if retrying:\n                wc_doc = wc.document\n                wc_doc[\"w\"] = \"majority\"\n                wc_doc.setdefault(\"wtimeout\", 10000)\n                wc = WriteConcern(**wc_doc)\n\n        if self._transaction.recovery_token:\n            cmd['recoveryToken'] = self._transaction.recovery_token\n\n        with self._client._socket_for_writes(self) as sock_info:\n            return self._client.admin._command(\n                sock_info,\n                cmd,\n                session=self,\n                write_concern=wc,\n                parse_write_concern_error=True)\n\n    def _advance_cluster_time(self, cluster_time):\n        \"\"\"Internal cluster time helper.\"\"\"\n        if self._cluster_time is None:\n            self._cluster_time = cluster_time\n        elif cluster_time is not None:\n            if cluster_time[\"clusterTime\"] > self._cluster_time[\"clusterTime\"]:\n                self._cluster_time = cluster_time\n\n    def advance_cluster_time(self, cluster_time):\n        \"\"\"Update the cluster time for this session.\n\n        :Parameters:\n          - `cluster_time`: The\n            :data:`~pymongo.client_session.ClientSession.cluster_time` from\n            another `ClientSession` instance.\n        \"\"\"\n        if not isinstance(cluster_time, abc.Mapping):\n            raise TypeError(\n                \"cluster_time must be a subclass of collections.Mapping\")\n        if not isinstance(cluster_time.get(\"clusterTime\"), Timestamp):\n            raise ValueError(\"Invalid cluster_time\")\n        self._advance_cluster_time(cluster_time)\n\n    def _advance_operation_time(self, operation_time):\n        \"\"\"Internal operation time helper.\"\"\"\n        if self._operation_time is None:\n            self._operation_time = operation_time\n        elif operation_time is not None:\n            if operation_time > self._operation_time:\n                self._operation_time = operation_time\n\n    def advance_operation_time(self, operation_time):\n        \"\"\"Update the operation time for this session.\n\n        :Parameters:\n          - `operation_time`: The\n            :data:`~pymongo.client_session.ClientSession.operation_time` from\n            another `ClientSession` instance.\n        \"\"\"\n        if not isinstance(operation_time, Timestamp):\n            raise TypeError(\"operation_time must be an instance \"\n                            \"of bson.timestamp.Timestamp\")\n        self._advance_operation_time(operation_time)\n\n    def _process_response(self, reply):\n        \"\"\"Process a response to a command that was run with this session.\"\"\"\n        self._advance_cluster_time(reply.get('$clusterTime'))\n        self._advance_operation_time(reply.get('operationTime'))\n        if self._in_transaction and self._transaction.sharded:\n            recovery_token = reply.get('recoveryToken')\n            if recovery_token:\n                self._transaction.recovery_token = recovery_token\n\n    @property\n    def has_ended(self):\n        \"\"\"True if this session is finished.\"\"\"\n        return self._server_session is None\n\n    @property\n    def _in_transaction(self):\n        \"\"\"True if this session has an active multi-statement transaction.\"\"\"\n        return self._transaction.active()\n\n    @property\n    def _pinned_address(self):\n        \"\"\"The mongos address this transaction was created on.\"\"\"\n        if self._transaction.active():\n            return self._transaction.pinned_address\n        return None\n\n    def _pin_mongos(self, server):\n        \"\"\"Pin this session to the given mongos Server.\"\"\"\n        self._transaction.sharded = True\n        self._transaction.pinned_address = server.description.address\n\n    def _unpin_mongos(self):\n        \"\"\"Unpin this session from any pinned mongos address.\"\"\"\n        self._transaction.pinned_address = None\n\n    def _txn_read_preference(self):\n        \"\"\"Return read preference of this transaction or None.\"\"\"\n        if self._in_transaction:\n            return self._transaction.opts.read_preference\n        return None\n\n    def _apply_to(self, command, is_retryable, read_preference):\n        self._check_ended()\n\n        self._server_session.last_use = monotonic.time()\n        command['lsid'] = self._server_session.session_id\n\n        if not self._in_transaction:\n            self._transaction.reset()\n\n        if is_retryable:\n            command['txnNumber'] = self._server_session.transaction_id\n            return\n\n        if self._in_transaction:\n            if read_preference != ReadPreference.PRIMARY:\n                raise InvalidOperation(\n                    'read preference in a transaction must be primary, not: '\n                    '%r' % (read_preference,))\n\n            if self._transaction.state == _TxnState.STARTING:\n                # First command begins a new transaction.\n                self._transaction.state = _TxnState.IN_PROGRESS\n                command['startTransaction'] = True\n\n                if self._transaction.opts.read_concern:\n                    rc = self._transaction.opts.read_concern.document\n                else:\n                    rc = {}\n\n                if (self.options.causal_consistency\n                        and self.operation_time is not None):\n                    rc['afterClusterTime'] = self.operation_time\n\n                if rc:\n                    command['readConcern'] = rc\n\n            command['txnNumber'] = self._server_session.transaction_id\n            command['autocommit'] = False\n\n    def _start_retryable_write(self):\n        self._check_ended()\n        self._server_session.inc_transaction_id()\n\n\nclass _ServerSession(object):\n    def __init__(self):\n        # Ensure id is type 4, regardless of CodecOptions.uuid_representation.\n        self.session_id = {'id': Binary(uuid.uuid4().bytes, 4)}\n        self.last_use = monotonic.time()\n        self._transaction_id = 0\n        self.dirty = False\n\n    def mark_dirty(self):\n        \"\"\"Mark this session as dirty.\n\n        A server session is marked dirty when a command fails with a network\n        error. Dirty sessions are later discarded from the server session pool.\n        \"\"\"\n        self.dirty = True\n\n    def timed_out(self, session_timeout_minutes):\n        idle_seconds = monotonic.time() - self.last_use\n\n        # Timed out if we have less than a minute to live.\n        return idle_seconds > (session_timeout_minutes - 1) * 60\n\n    @property\n    def transaction_id(self):\n        \"\"\"Positive 64-bit integer.\"\"\"\n        return Int64(self._transaction_id)\n\n    def inc_transaction_id(self):\n        self._transaction_id += 1\n\n\nclass _ServerSessionPool(collections.deque):\n    \"\"\"Pool of _ServerSession objects.\n\n    This class is not thread-safe, access it while holding the Topology lock.\n    \"\"\"\n    def pop_all(self):\n        ids = []\n        while self:\n            ids.append(self.pop().session_id)\n        return ids\n\n    def get_server_session(self, session_timeout_minutes):\n        # Although the Driver Sessions Spec says we only clear stale sessions\n        # in return_server_session, PyMongo can't take a lock when returning\n        # sessions from a __del__ method (like in Cursor.__die), so it can't\n        # clear stale sessions there. In case many sessions were returned via\n        # __del__, check for stale sessions here too.\n        self._clear_stale(session_timeout_minutes)\n\n        # The most recently used sessions are on the left.\n        while self:\n            s = self.popleft()\n            if not s.timed_out(session_timeout_minutes):\n                return s\n\n        return _ServerSession()\n\n    def return_server_session(self, server_session, session_timeout_minutes):\n        self._clear_stale(session_timeout_minutes)\n        if not server_session.timed_out(session_timeout_minutes):\n            self.return_server_session_no_lock(server_session)\n\n    def return_server_session_no_lock(self, server_session):\n        if not server_session.dirty:\n            self.appendleft(server_session)\n\n    def _clear_stale(self, session_timeout_minutes):\n        # Clear stale sessions. The least recently used are on the right.\n        while self:\n            if self[-1].timed_out(session_timeout_minutes):\n                self.pop()\n            else:\n                # The remaining sessions also haven't timed out.\n                break\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/collation.py",
    "content": "# Copyright 2016 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for working with `collations`_.\n\n.. _collations: http://userguide.icu-project.org/collation/concepts\n\"\"\"\n\nfrom pymongo import common\n\n\nclass CollationStrength(object):\n    \"\"\"\n    An enum that defines values for `strength` on a\n    :class:`~pymongo.collation.Collation`.\n    \"\"\"\n\n    PRIMARY = 1\n    \"\"\"Differentiate base (unadorned) characters.\"\"\"\n\n    SECONDARY = 2\n    \"\"\"Differentiate character accents.\"\"\"\n\n    TERTIARY = 3\n    \"\"\"Differentiate character case.\"\"\"\n\n    QUATERNARY = 4\n    \"\"\"Differentiate words with and without punctuation.\"\"\"\n\n    IDENTICAL = 5\n    \"\"\"Differentiate unicode code point (characters are exactly identical).\"\"\"\n\n\nclass CollationAlternate(object):\n    \"\"\"\n    An enum that defines values for `alternate` on a\n    :class:`~pymongo.collation.Collation`.\n    \"\"\"\n\n    NON_IGNORABLE = 'non-ignorable'\n    \"\"\"Spaces and punctuation are treated as base characters.\"\"\"\n\n    SHIFTED = 'shifted'\n    \"\"\"Spaces and punctuation are *not* considered base characters.\n\n    Spaces and punctuation are distinguished regardless when the\n    :class:`~pymongo.collation.Collation` strength is at least\n    :data:`~pymongo.collation.CollationStrength.QUATERNARY`.\n\n    \"\"\"\n\n\nclass CollationMaxVariable(object):\n    \"\"\"\n    An enum that defines values for `max_variable` on a\n    :class:`~pymongo.collation.Collation`.\n    \"\"\"\n\n    PUNCT = 'punct'\n    \"\"\"Both punctuation and spaces are ignored.\"\"\"\n\n    SPACE = 'space'\n    \"\"\"Spaces alone are ignored.\"\"\"\n\n\nclass CollationCaseFirst(object):\n    \"\"\"\n    An enum that defines values for `case_first` on a\n    :class:`~pymongo.collation.Collation`.\n    \"\"\"\n\n    UPPER = 'upper'\n    \"\"\"Sort uppercase characters first.\"\"\"\n\n    LOWER = 'lower'\n    \"\"\"Sort lowercase characters first.\"\"\"\n\n    OFF = 'off'\n    \"\"\"Default for locale or collation strength.\"\"\"\n\n\nclass Collation(object):\n    \"\"\"Collation\n\n    :Parameters:\n      - `locale`: (string) The locale of the collation. This should be a string\n        that identifies an `ICU locale ID` exactly. For example, ``en_US`` is\n        valid, but ``en_us`` and ``en-US`` are not. Consult the MongoDB\n        documentation for a list of supported locales.\n      - `caseLevel`: (optional) If ``True``, turn on case sensitivity if\n        `strength` is 1 or 2 (case sensitivity is implied if `strength` is\n        greater than 2). Defaults to ``False``.\n      - `caseFirst`: (optional) Specify that either uppercase or lowercase\n        characters take precedence. Must be one of the following values:\n\n          * :data:`~CollationCaseFirst.UPPER`\n          * :data:`~CollationCaseFirst.LOWER`\n          * :data:`~CollationCaseFirst.OFF` (the default)\n\n      - `strength`: (optional) Specify the comparison strength. This is also\n        known as the ICU comparison level. This must be one of the following\n        values:\n\n          * :data:`~CollationStrength.PRIMARY`\n          * :data:`~CollationStrength.SECONDARY`\n          * :data:`~CollationStrength.TERTIARY` (the default)\n          * :data:`~CollationStrength.QUATERNARY`\n          * :data:`~CollationStrength.IDENTICAL`\n\n        Each successive level builds upon the previous. For example, a\n        `strength` of :data:`~CollationStrength.SECONDARY` differentiates\n        characters based both on the unadorned base character and its accents.\n\n      - `numericOrdering`: (optional) If ``True``, order numbers numerically\n        instead of in collation order (defaults to ``False``).\n      - `alternate`: (optional) Specify whether spaces and punctuation are\n        considered base characters. This must be one of the following values:\n\n          * :data:`~CollationAlternate.NON_IGNORABLE` (the default)\n          * :data:`~CollationAlternate.SHIFTED`\n\n      - `maxVariable`: (optional) When `alternate` is\n        :data:`~CollationAlternate.SHIFTED`, this option specifies what\n        characters may be ignored. This must be one of the following values:\n\n          * :data:`~CollationMaxVariable.PUNCT` (the default)\n          * :data:`~CollationMaxVariable.SPACE`\n\n      - `normalization`: (optional) If ``True``, normalizes text into Unicode\n        NFD. Defaults to ``False``.\n      - `backwards`: (optional) If ``True``, accents on characters are\n        considered from the back of the word to the front, as it is done in some\n        French dictionary ordering traditions. Defaults to ``False``.\n      - `kwargs`: (optional) Keyword arguments supplying any additional options\n        to be sent with this Collation object.\n\n    .. versionadded: 3.4\n\n    \"\"\"\n\n    __slots__ = (\"__document\",)\n\n    def __init__(self, locale,\n                 caseLevel=None,\n                 caseFirst=None,\n                 strength=None,\n                 numericOrdering=None,\n                 alternate=None,\n                 maxVariable=None,\n                 normalization=None,\n                 backwards=None,\n                 **kwargs):\n        locale = common.validate_string('locale', locale)\n        self.__document = {'locale': locale}\n        if caseLevel is not None:\n            self.__document['caseLevel'] = common.validate_boolean(\n                'caseLevel', caseLevel)\n        if caseFirst is not None:\n            self.__document['caseFirst'] = common.validate_string(\n                'caseFirst', caseFirst)\n        if strength is not None:\n            self.__document['strength'] = common.validate_integer(\n                'strength', strength)\n        if numericOrdering is not None:\n            self.__document['numericOrdering'] = common.validate_boolean(\n                'numericOrdering', numericOrdering)\n        if alternate is not None:\n            self.__document['alternate'] = common.validate_string(\n                'alternate', alternate)\n        if maxVariable is not None:\n            self.__document['maxVariable'] = common.validate_string(\n                'maxVariable', maxVariable)\n        if normalization is not None:\n            self.__document['normalization'] = common.validate_boolean(\n                'normalization', normalization)\n        if backwards is not None:\n            self.__document['backwards'] = common.validate_boolean(\n                'backwards', backwards)\n        self.__document.update(kwargs)\n\n    @property\n    def document(self):\n        \"\"\"The document representation of this collation.\n\n        .. note::\n          :class:`Collation` is immutable. Mutating the value of\n          :attr:`document` does not mutate this :class:`Collation`.\n        \"\"\"\n        return self.__document.copy()\n\n    def __repr__(self):\n        document = self.document\n        return 'Collation(%s)' % (\n            ', '.join('%s=%r' % (key, document[key]) for key in document),)\n\n    def __eq__(self, other):\n        if isinstance(other, Collation):\n            return self.document == other.document\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n\n\ndef validate_collation_or_none(value):\n    if value is None:\n        return None\n    if isinstance(value, Collation):\n        return value.document\n    if isinstance(value, dict):\n        return value\n    raise TypeError(\n        'collation must be a dict, an instance of collation.Collation, '\n        'or None.')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/collection.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Collection level utilities for Mongo.\"\"\"\n\nimport datetime\nimport warnings\n\nfrom bson.code import Code\nfrom bson.objectid import ObjectId\nfrom bson.py3compat import (_unicode,\n                            abc,\n                            integer_types,\n                            string_type)\nfrom bson.raw_bson import RawBSONDocument\nfrom bson.codec_options import CodecOptions\nfrom bson.son import SON\nfrom pymongo import (common,\n                     helpers,\n                     message)\nfrom pymongo.aggregation import (_CollectionAggregationCommand,\n                                 _CollectionRawAggregationCommand)\nfrom pymongo.bulk import BulkOperationBuilder, _Bulk\nfrom pymongo.command_cursor import CommandCursor, RawBatchCommandCursor\nfrom pymongo.common import ORDERED_TYPES\nfrom pymongo.collation import validate_collation_or_none\nfrom pymongo.change_stream import CollectionChangeStream\nfrom pymongo.cursor import Cursor, RawBatchCursor\nfrom pymongo.errors import (BulkWriteError,\n                            ConfigurationError,\n                            InvalidName,\n                            InvalidOperation,\n                            OperationFailure)\nfrom pymongo.helpers import (_check_write_command_response,\n                             _raise_last_error)\nfrom pymongo.message import _UNICODE_REPLACE_CODEC_OPTIONS\nfrom pymongo.operations import IndexModel\nfrom pymongo.read_preferences import ReadPreference\nfrom pymongo.results import (BulkWriteResult,\n                             DeleteResult,\n                             InsertOneResult,\n                             InsertManyResult,\n                             UpdateResult)\nfrom pymongo.write_concern import WriteConcern\n\n_NO_OBJ_ERROR = \"No matching object found\"\n_UJOIN = u\"%s.%s\"\n_FIND_AND_MODIFY_DOC_FIELDS = {'value': 1}\n\n\nclass ReturnDocument(object):\n    \"\"\"An enum used with\n    :meth:`~pymongo.collection.Collection.find_one_and_replace` and\n    :meth:`~pymongo.collection.Collection.find_one_and_update`.\n    \"\"\"\n    BEFORE = False\n    \"\"\"Return the original document before it was updated/replaced, or\n    ``None`` if no document matches the query.\n    \"\"\"\n    AFTER = True\n    \"\"\"Return the updated/replaced or inserted document.\"\"\"\n\n\nclass Collection(common.BaseObject):\n    \"\"\"A Mongo collection.\n    \"\"\"\n\n    def __init__(self, database, name, create=False, codec_options=None,\n                 read_preference=None, write_concern=None, read_concern=None,\n                 session=None, **kwargs):\n        \"\"\"Get / create a Mongo collection.\n\n        Raises :class:`TypeError` if `name` is not an instance of\n        :class:`basestring` (:class:`str` in python 3). Raises\n        :class:`~pymongo.errors.InvalidName` if `name` is not a valid\n        collection name. Any additional keyword arguments will be used\n        as options passed to the create command. See\n        :meth:`~pymongo.database.Database.create_collection` for valid\n        options.\n\n        If `create` is ``True``, `collation` is specified, or any additional\n        keyword arguments are present, a ``create`` command will be\n        sent, using ``session`` if specified. Otherwise, a ``create`` command\n        will not be sent and the collection will be created implicitly on first\n        use. The optional ``session`` argument is *only* used for the ``create``\n        command, it is not associated with the collection afterward.\n\n        :Parameters:\n          - `database`: the database to get a collection from\n          - `name`: the name of the collection to get\n          - `create` (optional): if ``True``, force collection\n            creation even without options being set\n          - `codec_options` (optional): An instance of\n            :class:`~bson.codec_options.CodecOptions`. If ``None`` (the\n            default) database.codec_options is used.\n          - `read_preference` (optional): The read preference to use. If\n            ``None`` (the default) database.read_preference is used.\n          - `write_concern` (optional): An instance of\n            :class:`~pymongo.write_concern.WriteConcern`. If ``None`` (the\n            default) database.write_concern is used.\n          - `read_concern` (optional): An instance of\n            :class:`~pymongo.read_concern.ReadConcern`. If ``None`` (the\n            default) database.read_concern is used.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. If a collation is provided,\n            it will be passed to the create collection command. This option is\n            only supported on MongoDB 3.4 and above.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession` that is used with\n            the create collection command\n          - `**kwargs` (optional): additional keyword arguments will\n            be passed as options for the create collection command\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.4\n           Support the `collation` option.\n\n        .. versionchanged:: 3.2\n           Added the read_concern option.\n\n        .. versionchanged:: 3.0\n           Added the codec_options, read_preference, and write_concern options.\n           Removed the uuid_subtype attribute.\n           :class:`~pymongo.collection.Collection` no longer returns an\n           instance of :class:`~pymongo.collection.Collection` for attribute\n           names with leading underscores. You must use dict-style lookups\n           instead::\n\n               collection['__my_collection__']\n\n           Not:\n\n               collection.__my_collection__\n\n        .. versionchanged:: 2.2\n           Removed deprecated argument: options\n\n        .. versionadded:: 2.1\n           uuid_subtype attribute\n\n        .. mongodoc:: collections\n        \"\"\"\n        super(Collection, self).__init__(\n            codec_options or database.codec_options,\n            read_preference or database.read_preference,\n            write_concern or database.write_concern,\n            read_concern or database.read_concern)\n\n        if not isinstance(name, string_type):\n            raise TypeError(\"name must be an instance \"\n                            \"of %s\" % (string_type.__name__,))\n\n        if not name or \"..\" in name:\n            raise InvalidName(\"collection names cannot be empty\")\n        if \"$\" in name and not (name.startswith(\"oplog.$main\") or\n                                name.startswith(\"$cmd\")):\n            raise InvalidName(\"collection names must not \"\n                              \"contain '$': %r\" % name)\n        if name[0] == \".\" or name[-1] == \".\":\n            raise InvalidName(\"collection names must not start \"\n                              \"or end with '.': %r\" % name)\n        if \"\\x00\" in name:\n            raise InvalidName(\"collection names must not contain the \"\n                              \"null character\")\n        collation = validate_collation_or_none(kwargs.pop('collation', None))\n\n        self.__database = database\n        self.__name = _unicode(name)\n        self.__full_name = _UJOIN % (self.__database.name, self.__name)\n        if create or kwargs or collation:\n            self.__create(kwargs, collation, session)\n\n        self.__write_response_codec_options = self.codec_options._replace(\n            unicode_decode_error_handler='replace',\n            document_class=dict)\n\n    def _socket_for_reads(self, session):\n        return self.__database.client._socket_for_reads(\n            self._read_preference_for(session), session)\n\n    def _socket_for_writes(self, session):\n        return self.__database.client._socket_for_writes(session)\n\n    def _command(self, sock_info, command, slave_ok=False,\n                 read_preference=None,\n                 codec_options=None, check=True, allowable_errors=None,\n                 read_concern=None,\n                 write_concern=None,\n                 collation=None,\n                 session=None,\n                 retryable_write=False,\n                 user_fields=None):\n        \"\"\"Internal command helper.\n\n        :Parameters:\n          - `sock_info` - A SocketInfo instance.\n          - `command` - The command itself, as a SON instance.\n          - `slave_ok`: whether to set the SlaveOkay wire protocol bit.\n          - `codec_options` (optional) - An instance of\n            :class:`~bson.codec_options.CodecOptions`.\n          - `check`: raise OperationFailure if there are errors\n          - `allowable_errors`: errors to ignore if `check` is True\n          - `read_concern` (optional) - An instance of\n            :class:`~pymongo.read_concern.ReadConcern`.\n          - `write_concern`: An instance of\n            :class:`~pymongo.write_concern.WriteConcern`. This option is only\n            valid for MongoDB 3.4 and above.\n          - `collation` (optional) - An instance of\n            :class:`~pymongo.collation.Collation`.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `retryable_write` (optional): True if this command is a retryable\n            write.\n          - `user_fields` (optional): Response fields that should be decoded\n            using the TypeDecoders from codec_options, passed to\n            bson._decode_all_selective.\n\n        :Returns:\n          The result document.\n        \"\"\"\n        with self.__database.client._tmp_session(session) as s:\n            return sock_info.command(\n                self.__database.name,\n                command,\n                slave_ok,\n                read_preference or self._read_preference_for(session),\n                codec_options or self.codec_options,\n                check,\n                allowable_errors,\n                read_concern=read_concern,\n                write_concern=write_concern,\n                parse_write_concern_error=True,\n                collation=collation,\n                session=s,\n                client=self.__database.client,\n                retryable_write=retryable_write,\n                user_fields=user_fields)\n\n    def __create(self, options, collation, session):\n        \"\"\"Sends a create command with the given options.\n        \"\"\"\n        cmd = SON([(\"create\", self.__name)])\n        if options:\n            if \"size\" in options:\n                options[\"size\"] = float(options[\"size\"])\n            cmd.update(options)\n        with self._socket_for_writes(session) as sock_info:\n            self._command(\n                sock_info, cmd, read_preference=ReadPreference.PRIMARY,\n                write_concern=self._write_concern_for(session),\n                collation=collation, session=session)\n\n    def __getattr__(self, name):\n        \"\"\"Get a sub-collection of this collection by name.\n\n        Raises InvalidName if an invalid collection name is used.\n\n        :Parameters:\n          - `name`: the name of the collection to get\n        \"\"\"\n        if name.startswith('_'):\n            full_name = _UJOIN % (self.__name, name)\n            raise AttributeError(\n                \"Collection has no attribute %r. To access the %s\"\n                \" collection, use database['%s'].\" % (\n                    name, full_name, full_name))\n        return self.__getitem__(name)\n\n    def __getitem__(self, name):\n        return Collection(self.__database,\n                          _UJOIN % (self.__name, name),\n                          False,\n                          self.codec_options,\n                          self.read_preference,\n                          self.write_concern,\n                          self.read_concern)\n\n    def __repr__(self):\n        return \"Collection(%r, %r)\" % (self.__database, self.__name)\n\n    def __eq__(self, other):\n        if isinstance(other, Collection):\n            return (self.__database == other.database and\n                    self.__name == other.name)\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n\n    @property\n    def full_name(self):\n        \"\"\"The full name of this :class:`Collection`.\n\n        The full name is of the form `database_name.collection_name`.\n        \"\"\"\n        return self.__full_name\n\n    @property\n    def name(self):\n        \"\"\"The name of this :class:`Collection`.\"\"\"\n        return self.__name\n\n    @property\n    def database(self):\n        \"\"\"The :class:`~pymongo.database.Database` that this\n        :class:`Collection` is a part of.\n        \"\"\"\n        return self.__database\n\n    def with_options(self, codec_options=None, read_preference=None,\n                     write_concern=None, read_concern=None):\n        \"\"\"Get a clone of this collection changing the specified settings.\n\n          >>> coll1.read_preference\n          Primary()\n          >>> from pymongo import ReadPreference\n          >>> coll2 = coll1.with_options(read_preference=ReadPreference.SECONDARY)\n          >>> coll1.read_preference\n          Primary()\n          >>> coll2.read_preference\n          Secondary(tag_sets=None)\n\n        :Parameters:\n          - `codec_options` (optional): An instance of\n            :class:`~bson.codec_options.CodecOptions`. If ``None`` (the\n            default) the :attr:`codec_options` of this :class:`Collection`\n            is used.\n          - `read_preference` (optional): The read preference to use. If\n            ``None`` (the default) the :attr:`read_preference` of this\n            :class:`Collection` is used. See :mod:`~pymongo.read_preferences`\n            for options.\n          - `write_concern` (optional): An instance of\n            :class:`~pymongo.write_concern.WriteConcern`. If ``None`` (the\n            default) the :attr:`write_concern` of this :class:`Collection`\n            is used.\n          - `read_concern` (optional): An instance of\n            :class:`~pymongo.read_concern.ReadConcern`. If ``None`` (the\n            default) the :attr:`read_concern` of this :class:`Collection`\n            is used.\n        \"\"\"\n        return Collection(self.__database,\n                          self.__name,\n                          False,\n                          codec_options or self.codec_options,\n                          read_preference or self.read_preference,\n                          write_concern or self.write_concern,\n                          read_concern or self.read_concern)\n\n    def initialize_unordered_bulk_op(self, bypass_document_validation=False):\n        \"\"\"**DEPRECATED** - Initialize an unordered batch of write operations.\n\n        Operations will be performed on the server in arbitrary order,\n        possibly in parallel. All operations will be attempted.\n\n        :Parameters:\n          - `bypass_document_validation`: (optional) If ``True``, allows the\n            write to opt-out of document level validation. Default is\n            ``False``.\n\n        Returns a :class:`~pymongo.bulk.BulkOperationBuilder` instance.\n\n        See :ref:`unordered_bulk` for examples.\n\n        .. note:: `bypass_document_validation` requires server version\n          **>= 3.2**\n\n        .. versionchanged:: 3.5\n           Deprecated. Use :meth:`~pymongo.collection.Collection.bulk_write`\n           instead.\n\n        .. versionchanged:: 3.2\n           Added bypass_document_validation support\n\n        .. versionadded:: 2.7\n        \"\"\"\n        warnings.warn(\"initialize_unordered_bulk_op is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n        return BulkOperationBuilder(self, False, bypass_document_validation)\n\n    def initialize_ordered_bulk_op(self, bypass_document_validation=False):\n        \"\"\"**DEPRECATED** - Initialize an ordered batch of write operations.\n\n        Operations will be performed on the server serially, in the\n        order provided. If an error occurs all remaining operations\n        are aborted.\n\n        :Parameters:\n          - `bypass_document_validation`: (optional) If ``True``, allows the\n            write to opt-out of document level validation. Default is\n            ``False``.\n\n        Returns a :class:`~pymongo.bulk.BulkOperationBuilder` instance.\n\n        See :ref:`ordered_bulk` for examples.\n\n        .. note:: `bypass_document_validation` requires server version\n          **>= 3.2**\n\n        .. versionchanged:: 3.5\n           Deprecated. Use :meth:`~pymongo.collection.Collection.bulk_write`\n           instead.\n\n        .. versionchanged:: 3.2\n           Added bypass_document_validation support\n\n        .. versionadded:: 2.7\n        \"\"\"\n        warnings.warn(\"initialize_ordered_bulk_op is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n        return BulkOperationBuilder(self, True, bypass_document_validation)\n\n    def bulk_write(self, requests, ordered=True,\n                   bypass_document_validation=False, session=None):\n        \"\"\"Send a batch of write operations to the server.\n\n        Requests are passed as a list of write operation instances (\n        :class:`~pymongo.operations.InsertOne`,\n        :class:`~pymongo.operations.UpdateOne`,\n        :class:`~pymongo.operations.UpdateMany`,\n        :class:`~pymongo.operations.ReplaceOne`,\n        :class:`~pymongo.operations.DeleteOne`, or\n        :class:`~pymongo.operations.DeleteMany`).\n\n          >>> for doc in db.test.find({}):\n          ...     print(doc)\n          ...\n          {u'x': 1, u'_id': ObjectId('54f62e60fba5226811f634ef')}\n          {u'x': 1, u'_id': ObjectId('54f62e60fba5226811f634f0')}\n          >>> # DeleteMany, UpdateOne, and UpdateMany are also available.\n          ...\n          >>> from pymongo import InsertOne, DeleteOne, ReplaceOne\n          >>> requests = [InsertOne({'y': 1}), DeleteOne({'x': 1}),\n          ...             ReplaceOne({'w': 1}, {'z': 1}, upsert=True)]\n          >>> result = db.test.bulk_write(requests)\n          >>> result.inserted_count\n          1\n          >>> result.deleted_count\n          1\n          >>> result.modified_count\n          0\n          >>> result.upserted_ids\n          {2: ObjectId('54f62ee28891e756a6e1abd5')}\n          >>> for doc in db.test.find({}):\n          ...     print(doc)\n          ...\n          {u'x': 1, u'_id': ObjectId('54f62e60fba5226811f634f0')}\n          {u'y': 1, u'_id': ObjectId('54f62ee2fba5226811f634f1')}\n          {u'z': 1, u'_id': ObjectId('54f62ee28891e756a6e1abd5')}\n\n        :Parameters:\n          - `requests`: A list of write operations (see examples above).\n          - `ordered` (optional): If ``True`` (the default) requests will be\n            performed on the server serially, in the order provided. If an error\n            occurs all remaining operations are aborted. If ``False`` requests\n            will be performed on the server in arbitrary order, possibly in\n            parallel, and all operations will be attempted.\n          - `bypass_document_validation`: (optional) If ``True``, allows the\n            write to opt-out of document level validation. Default is\n            ``False``.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        :Returns:\n          An instance of :class:`~pymongo.results.BulkWriteResult`.\n\n        .. seealso:: :ref:`writes-and-ids`\n\n        .. note:: `bypass_document_validation` requires server version\n          **>= 3.2**\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.2\n          Added bypass_document_validation support\n\n        .. versionadded:: 3.0\n        \"\"\"\n        common.validate_list(\"requests\", requests)\n\n        blk = _Bulk(self, ordered, bypass_document_validation)\n        for request in requests:\n            try:\n                request._add_to_bulk(blk)\n            except AttributeError:\n                raise TypeError(\"%r is not a valid request\" % (request,))\n\n        write_concern = self._write_concern_for(session)\n        bulk_api_result = blk.execute(write_concern, session)\n        if bulk_api_result is not None:\n            return BulkWriteResult(bulk_api_result, True)\n        return BulkWriteResult({}, False)\n\n    def _legacy_write(self, sock_info, name, cmd, op_id,\n                      bypass_doc_val, func, *args):\n        \"\"\"Internal legacy unacknowledged write helper.\"\"\"\n        # Cannot have both unacknowledged write and bypass document validation.\n        if bypass_doc_val and sock_info.max_wire_version >= 4:\n            raise OperationFailure(\"Cannot set bypass_document_validation with\"\n                                   \" unacknowledged write concern\")\n        listeners = self.database.client._event_listeners\n        publish = listeners.enabled_for_commands\n\n        if publish:\n            start = datetime.datetime.now()\n        args = args + (sock_info.compression_context,)\n        rqst_id, msg, max_size = func(*args)\n        if publish:\n            duration = datetime.datetime.now() - start\n            listeners.publish_command_start(\n                cmd, self.__database.name, rqst_id, sock_info.address, op_id)\n            start = datetime.datetime.now()\n        try:\n            result = sock_info.legacy_write(rqst_id, msg, max_size, False)\n        except Exception as exc:\n            if publish:\n                dur = (datetime.datetime.now() - start) + duration\n                if isinstance(exc, OperationFailure):\n                    details = exc.details\n                    # Succeed if GLE was successful and this is a write error.\n                    if details.get(\"ok\") and \"n\" in details:\n                        reply = message._convert_write_result(\n                            name, cmd, details)\n                        listeners.publish_command_success(\n                            dur, reply, name, rqst_id, sock_info.address, op_id)\n                        raise\n                else:\n                    details = message._convert_exception(exc)\n                listeners.publish_command_failure(\n                    dur, details, name, rqst_id, sock_info.address, op_id)\n            raise\n        if publish:\n            if result is not None:\n                reply = message._convert_write_result(name, cmd, result)\n            else:\n                # Comply with APM spec.\n                reply = {'ok': 1}\n            duration = (datetime.datetime.now() - start) + duration\n            listeners.publish_command_success(\n                duration, reply, name, rqst_id, sock_info.address, op_id)\n        return result\n\n    def _insert_one(\n            self, doc, ordered,\n            check_keys, manipulate, write_concern, op_id, bypass_doc_val,\n            session):\n        \"\"\"Internal helper for inserting a single document.\"\"\"\n        if manipulate:\n            doc = self.__database._apply_incoming_manipulators(doc, self)\n            if not isinstance(doc, RawBSONDocument) and '_id' not in doc:\n                doc['_id'] = ObjectId()\n            doc = self.__database._apply_incoming_copying_manipulators(doc,\n                                                                       self)\n        write_concern = write_concern or self.write_concern\n        acknowledged = write_concern.acknowledged\n        command = SON([('insert', self.name),\n                       ('ordered', ordered),\n                       ('documents', [doc])])\n        if not write_concern.is_server_default:\n            command['writeConcern'] = write_concern.document\n\n        def _insert_command(session, sock_info, retryable_write):\n            if not sock_info.op_msg_enabled and not acknowledged:\n                # Legacy OP_INSERT.\n                return self._legacy_write(\n                    sock_info, 'insert', command, op_id,\n                    bypass_doc_val, message.insert, self.__full_name,\n                    [doc], check_keys, False, write_concern.document, False,\n                    self.__write_response_codec_options)\n\n            if bypass_doc_val and sock_info.max_wire_version >= 4:\n                command['bypassDocumentValidation'] = True\n\n            result = sock_info.command(\n                self.__database.name,\n                command,\n                write_concern=write_concern,\n                codec_options=self.__write_response_codec_options,\n                check_keys=check_keys,\n                session=session,\n                client=self.__database.client,\n                retryable_write=retryable_write)\n\n            _check_write_command_response(result)\n\n        self.__database.client._retryable_write(\n            acknowledged, _insert_command, session)\n\n        if not isinstance(doc, RawBSONDocument):\n            return doc.get('_id')\n\n    def _insert(self, docs, ordered=True, check_keys=True,\n                manipulate=False, write_concern=None, op_id=None,\n                bypass_doc_val=False, session=None):\n        \"\"\"Internal insert helper.\"\"\"\n        if isinstance(docs, abc.Mapping):\n            return self._insert_one(\n                docs, ordered, check_keys, manipulate, write_concern, op_id,\n                bypass_doc_val, session)\n\n        ids = []\n\n        if manipulate:\n            def gen():\n                \"\"\"Generator that applies SON manipulators to each document\n                and adds _id if necessary.\n                \"\"\"\n                _db = self.__database\n                for doc in docs:\n                    # Apply user-configured SON manipulators. This order of\n                    # operations is required for backwards compatibility,\n                    # see PYTHON-709.\n                    doc = _db._apply_incoming_manipulators(doc, self)\n                    if not (isinstance(doc, RawBSONDocument) or '_id' in doc):\n                        doc['_id'] = ObjectId()\n\n                    doc = _db._apply_incoming_copying_manipulators(doc, self)\n                    ids.append(doc['_id'])\n                    yield doc\n        else:\n            def gen():\n                \"\"\"Generator that only tracks existing _ids.\"\"\"\n                for doc in docs:\n                    # Don't inflate RawBSONDocument by touching fields.\n                    if not isinstance(doc, RawBSONDocument):\n                        ids.append(doc.get('_id'))\n                    yield doc\n\n        write_concern = write_concern or self._write_concern_for(session)\n        blk = _Bulk(self, ordered, bypass_doc_val)\n        blk.ops = [(message._INSERT, doc) for doc in gen()]\n        try:\n            blk.execute(write_concern, session=session)\n        except BulkWriteError as bwe:\n            _raise_last_error(bwe.details)\n        return ids\n\n    def insert_one(self, document, bypass_document_validation=False,\n                   session=None):\n        \"\"\"Insert a single document.\n\n          >>> db.test.count_documents({'x': 1})\n          0\n          >>> result = db.test.insert_one({'x': 1})\n          >>> result.inserted_id\n          ObjectId('54f112defba522406c9cc208')\n          >>> db.test.find_one({'x': 1})\n          {u'x': 1, u'_id': ObjectId('54f112defba522406c9cc208')}\n\n        :Parameters:\n          - `document`: The document to insert. Must be a mutable mapping\n            type. If the document does not have an _id field one will be\n            added automatically.\n          - `bypass_document_validation`: (optional) If ``True``, allows the\n            write to opt-out of document level validation. Default is\n            ``False``.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        :Returns:\n          - An instance of :class:`~pymongo.results.InsertOneResult`.\n\n        .. seealso:: :ref:`writes-and-ids`\n\n        .. note:: `bypass_document_validation` requires server version\n          **>= 3.2**\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.2\n          Added bypass_document_validation support\n\n        .. versionadded:: 3.0\n        \"\"\"\n        common.validate_is_document_type(\"document\", document)\n        if not (isinstance(document, RawBSONDocument) or \"_id\" in document):\n            document[\"_id\"] = ObjectId()\n\n        write_concern = self._write_concern_for(session)\n        return InsertOneResult(\n            self._insert(document,\n                         write_concern=write_concern,\n                         bypass_doc_val=bypass_document_validation,\n                         session=session),\n            write_concern.acknowledged)\n\n    def insert_many(self, documents, ordered=True,\n                    bypass_document_validation=False, session=None):\n        \"\"\"Insert an iterable of documents.\n\n          >>> db.test.count_documents({})\n          0\n          >>> result = db.test.insert_many([{'x': i} for i in range(2)])\n          >>> result.inserted_ids\n          [ObjectId('54f113fffba522406c9cc20e'), ObjectId('54f113fffba522406c9cc20f')]\n          >>> db.test.count_documents({})\n          2\n\n        :Parameters:\n          - `documents`: A iterable of documents to insert.\n          - `ordered` (optional): If ``True`` (the default) documents will be\n            inserted on the server serially, in the order provided. If an error\n            occurs all remaining inserts are aborted. If ``False``, documents\n            will be inserted on the server in arbitrary order, possibly in\n            parallel, and all document inserts will be attempted.\n          - `bypass_document_validation`: (optional) If ``True``, allows the\n            write to opt-out of document level validation. Default is\n            ``False``.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        :Returns:\n          An instance of :class:`~pymongo.results.InsertManyResult`.\n\n        .. seealso:: :ref:`writes-and-ids`\n\n        .. note:: `bypass_document_validation` requires server version\n          **>= 3.2**\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.2\n          Added bypass_document_validation support\n\n        .. versionadded:: 3.0\n        \"\"\"\n        if not isinstance(documents, abc.Iterable) or not documents:\n            raise TypeError(\"documents must be a non-empty list\")\n        inserted_ids = []\n        def gen():\n            \"\"\"A generator that validates documents and handles _ids.\"\"\"\n            for document in documents:\n                common.validate_is_document_type(\"document\", document)\n                if not isinstance(document, RawBSONDocument):\n                    if \"_id\" not in document:\n                        document[\"_id\"] = ObjectId()\n                    inserted_ids.append(document[\"_id\"])\n                yield (message._INSERT, document)\n\n        write_concern = self._write_concern_for(session)\n        blk = _Bulk(self, ordered, bypass_document_validation)\n        blk.ops = [doc for doc in gen()]\n        blk.execute(write_concern, session=session)\n        return InsertManyResult(inserted_ids, write_concern.acknowledged)\n\n    def _update(self, sock_info, criteria, document, upsert=False,\n                check_keys=True, multi=False, manipulate=False,\n                write_concern=None, op_id=None, ordered=True,\n                bypass_doc_val=False, collation=None, array_filters=None,\n                session=None, retryable_write=False):\n        \"\"\"Internal update / replace helper.\"\"\"\n        common.validate_boolean(\"upsert\", upsert)\n        if manipulate:\n            document = self.__database._fix_incoming(document, self)\n        collation = validate_collation_or_none(collation)\n        write_concern = write_concern or self.write_concern\n        acknowledged = write_concern.acknowledged\n        update_doc = SON([('q', criteria),\n                          ('u', document),\n                          ('multi', multi),\n                          ('upsert', upsert)])\n        if collation is not None:\n            if sock_info.max_wire_version < 5:\n                raise ConfigurationError(\n                    'Must be connected to MongoDB 3.4+ to use collations.')\n            elif not acknowledged:\n                raise ConfigurationError(\n                    'Collation is unsupported for unacknowledged writes.')\n            else:\n                update_doc['collation'] = collation\n        if array_filters is not None:\n            if sock_info.max_wire_version < 6:\n                raise ConfigurationError(\n                    'Must be connected to MongoDB 3.6+ to use array_filters.')\n            elif not acknowledged:\n                raise ConfigurationError(\n                    'arrayFilters is unsupported for unacknowledged writes.')\n            else:\n                update_doc['arrayFilters'] = array_filters\n        command = SON([('update', self.name),\n                       ('ordered', ordered),\n                       ('updates', [update_doc])])\n        if not write_concern.is_server_default:\n            command['writeConcern'] = write_concern.document\n\n        if not sock_info.op_msg_enabled and not acknowledged:\n            # Legacy OP_UPDATE.\n            return self._legacy_write(\n                sock_info, 'update', command, op_id,\n                bypass_doc_val, message.update, self.__full_name, upsert,\n                multi, criteria, document, False, write_concern.document,\n                check_keys, self.__write_response_codec_options)\n\n        # Update command.\n        if bypass_doc_val and sock_info.max_wire_version >= 4:\n            command['bypassDocumentValidation'] = True\n\n        # The command result has to be published for APM unmodified\n        # so we make a shallow copy here before adding updatedExisting.\n        result = sock_info.command(\n            self.__database.name,\n            command,\n            write_concern=write_concern,\n            codec_options=self.__write_response_codec_options,\n            session=session,\n            client=self.__database.client,\n            retryable_write=retryable_write).copy()\n        _check_write_command_response(result)\n        # Add the updatedExisting field for compatibility.\n        if result.get('n') and 'upserted' not in result:\n            result['updatedExisting'] = True\n        else:\n            result['updatedExisting'] = False\n            # MongoDB >= 2.6.0 returns the upsert _id in an array\n            # element. Break it out for backward compatibility.\n            if 'upserted' in result:\n                result['upserted'] = result['upserted'][0]['_id']\n\n        if not acknowledged:\n            return None\n        return result\n\n    def _update_retryable(\n            self, criteria, document, upsert=False,\n            check_keys=True, multi=False, manipulate=False,\n            write_concern=None, op_id=None, ordered=True,\n            bypass_doc_val=False, collation=None, array_filters=None,\n            session=None):\n        \"\"\"Internal update / replace helper.\"\"\"\n        def _update(session, sock_info, retryable_write):\n            return self._update(\n                sock_info, criteria, document, upsert=upsert,\n                check_keys=check_keys, multi=multi, manipulate=manipulate,\n                write_concern=write_concern, op_id=op_id, ordered=ordered,\n                bypass_doc_val=bypass_doc_val, collation=collation,\n                array_filters=array_filters, session=session,\n                retryable_write=retryable_write)\n\n        return self.__database.client._retryable_write(\n            (write_concern or self.write_concern).acknowledged and not multi,\n            _update, session)\n\n    def replace_one(self, filter, replacement, upsert=False,\n                    bypass_document_validation=False, collation=None,\n                    session=None):\n        \"\"\"Replace a single document matching the filter.\n\n          >>> for doc in db.test.find({}):\n          ...     print(doc)\n          ...\n          {u'x': 1, u'_id': ObjectId('54f4c5befba5220aa4d6dee7')}\n          >>> result = db.test.replace_one({'x': 1}, {'y': 1})\n          >>> result.matched_count\n          1\n          >>> result.modified_count\n          1\n          >>> for doc in db.test.find({}):\n          ...     print(doc)\n          ...\n          {u'y': 1, u'_id': ObjectId('54f4c5befba5220aa4d6dee7')}\n\n        The *upsert* option can be used to insert a new document if a matching\n        document does not exist.\n\n          >>> result = db.test.replace_one({'x': 1}, {'x': 1}, True)\n          >>> result.matched_count\n          0\n          >>> result.modified_count\n          0\n          >>> result.upserted_id\n          ObjectId('54f11e5c8891e756a6e1abd4')\n          >>> db.test.find_one({'x': 1})\n          {u'x': 1, u'_id': ObjectId('54f11e5c8891e756a6e1abd4')}\n\n        :Parameters:\n          - `filter`: A query that matches the document to replace.\n          - `replacement`: The new document.\n          - `upsert` (optional): If ``True``, perform an insert if no documents\n            match the filter.\n          - `bypass_document_validation`: (optional) If ``True``, allows the\n            write to opt-out of document level validation. Default is\n            ``False``.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only supported\n            on MongoDB 3.4 and above.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        :Returns:\n          - An instance of :class:`~pymongo.results.UpdateResult`.\n\n        .. note:: `bypass_document_validation` requires server version\n          **>= 3.2**\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.4\n          Added the `collation` option.\n\n        .. versionchanged:: 3.2\n          Added bypass_document_validation support\n\n        .. versionadded:: 3.0\n        \"\"\"\n        common.validate_is_mapping(\"filter\", filter)\n        common.validate_ok_for_replace(replacement)\n\n        write_concern = self._write_concern_for(session)\n        return UpdateResult(\n            self._update_retryable(\n                filter, replacement, upsert,\n                write_concern=write_concern,\n                bypass_doc_val=bypass_document_validation,\n                collation=collation, session=session),\n            write_concern.acknowledged)\n\n    def update_one(self, filter, update, upsert=False,\n                   bypass_document_validation=False,\n                   collation=None, array_filters=None, session=None):\n        \"\"\"Update a single document matching the filter.\n\n          >>> for doc in db.test.find():\n          ...     print(doc)\n          ...\n          {u'x': 1, u'_id': 0}\n          {u'x': 1, u'_id': 1}\n          {u'x': 1, u'_id': 2}\n          >>> result = db.test.update_one({'x': 1}, {'$inc': {'x': 3}})\n          >>> result.matched_count\n          1\n          >>> result.modified_count\n          1\n          >>> for doc in db.test.find():\n          ...     print(doc)\n          ...\n          {u'x': 4, u'_id': 0}\n          {u'x': 1, u'_id': 1}\n          {u'x': 1, u'_id': 2}\n\n        :Parameters:\n          - `filter`: A query that matches the document to update.\n          - `update`: The modifications to apply.\n          - `upsert` (optional): If ``True``, perform an insert if no documents\n            match the filter.\n          - `bypass_document_validation`: (optional) If ``True``, allows the\n            write to opt-out of document level validation. Default is\n            ``False``.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only supported\n            on MongoDB 3.4 and above.\n          - `array_filters` (optional): A list of filters specifying which\n            array elements an update should apply. Requires MongoDB 3.6+.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        :Returns:\n          - An instance of :class:`~pymongo.results.UpdateResult`.\n\n        .. note:: `bypass_document_validation` requires server version\n          **>= 3.2**\n\n        .. versionchanged:: 3.9\n           Added the ability to accept a pipeline as the `update`.\n\n        .. versionchanged:: 3.6\n           Added the `array_filters` and ``session`` parameters.\n\n        .. versionchanged:: 3.4\n          Added the `collation` option.\n\n        .. versionchanged:: 3.2\n          Added bypass_document_validation support\n\n        .. versionadded:: 3.0\n        \"\"\"\n        common.validate_is_mapping(\"filter\", filter)\n        common.validate_ok_for_update(update)\n        common.validate_list_or_none('array_filters', array_filters)\n\n        write_concern = self._write_concern_for(session)\n        return UpdateResult(\n            self._update_retryable(\n                filter, update, upsert, check_keys=False,\n                write_concern=write_concern,\n                bypass_doc_val=bypass_document_validation,\n                collation=collation, array_filters=array_filters,\n                session=session),\n            write_concern.acknowledged)\n\n    def update_many(self, filter, update, upsert=False, array_filters=None,\n                    bypass_document_validation=False, collation=None,\n                    session=None):\n        \"\"\"Update one or more documents that match the filter.\n\n          >>> for doc in db.test.find():\n          ...     print(doc)\n          ...\n          {u'x': 1, u'_id': 0}\n          {u'x': 1, u'_id': 1}\n          {u'x': 1, u'_id': 2}\n          >>> result = db.test.update_many({'x': 1}, {'$inc': {'x': 3}})\n          >>> result.matched_count\n          3\n          >>> result.modified_count\n          3\n          >>> for doc in db.test.find():\n          ...     print(doc)\n          ...\n          {u'x': 4, u'_id': 0}\n          {u'x': 4, u'_id': 1}\n          {u'x': 4, u'_id': 2}\n\n        :Parameters:\n          - `filter`: A query that matches the documents to update.\n          - `update`: The modifications to apply.\n          - `upsert` (optional): If ``True``, perform an insert if no documents\n            match the filter.\n          - `bypass_document_validation` (optional): If ``True``, allows the\n            write to opt-out of document level validation. Default is\n            ``False``.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only supported\n            on MongoDB 3.4 and above.\n          - `array_filters` (optional): A list of filters specifying which\n            array elements an update should apply. Requires MongoDB 3.6+.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        :Returns:\n          - An instance of :class:`~pymongo.results.UpdateResult`.\n\n        .. note:: `bypass_document_validation` requires server version\n          **>= 3.2**\n\n        .. versionchanged:: 3.9\n           Added the ability to accept a pipeline as the `update`.\n\n        .. versionchanged:: 3.6\n           Added ``array_filters`` and ``session`` parameters.\n\n        .. versionchanged:: 3.4\n          Added the `collation` option.\n\n        .. versionchanged:: 3.2\n          Added bypass_document_validation support\n\n        .. versionadded:: 3.0\n        \"\"\"\n        common.validate_is_mapping(\"filter\", filter)\n        common.validate_ok_for_update(update)\n        common.validate_list_or_none('array_filters', array_filters)\n\n        write_concern = self._write_concern_for(session)\n        return UpdateResult(\n            self._update_retryable(\n                filter, update, upsert, check_keys=False, multi=True,\n                write_concern=write_concern,\n                bypass_doc_val=bypass_document_validation,\n                collation=collation, array_filters=array_filters,\n                session=session),\n            write_concern.acknowledged)\n\n    def drop(self, session=None):\n        \"\"\"Alias for :meth:`~pymongo.database.Database.drop_collection`.\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        The following two calls are equivalent:\n\n          >>> db.foo.drop()\n          >>> db.drop_collection(\"foo\")\n\n        .. versionchanged:: 3.7\n           :meth:`drop` now respects this :class:`Collection`'s :attr:`write_concern`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        dbo = self.__database.client.get_database(\n            self.__database.name,\n            self.codec_options,\n            self.read_preference,\n            self.write_concern,\n            self.read_concern)\n        dbo.drop_collection(self.__name, session=session)\n\n    def _delete(\n            self, sock_info, criteria, multi,\n            write_concern=None, op_id=None, ordered=True,\n            collation=None, session=None, retryable_write=False):\n        \"\"\"Internal delete helper.\"\"\"\n        common.validate_is_mapping(\"filter\", criteria)\n        write_concern = write_concern or self.write_concern\n        acknowledged = write_concern.acknowledged\n        delete_doc = SON([('q', criteria),\n                          ('limit', int(not multi))])\n        collation = validate_collation_or_none(collation)\n        if collation is not None:\n            if sock_info.max_wire_version < 5:\n                raise ConfigurationError(\n                    'Must be connected to MongoDB 3.4+ to use collations.')\n            elif not acknowledged:\n                raise ConfigurationError(\n                    'Collation is unsupported for unacknowledged writes.')\n            else:\n                delete_doc['collation'] = collation\n        command = SON([('delete', self.name),\n                       ('ordered', ordered),\n                       ('deletes', [delete_doc])])\n        if not write_concern.is_server_default:\n            command['writeConcern'] = write_concern.document\n\n        if not sock_info.op_msg_enabled and not acknowledged:\n            # Legacy OP_DELETE.\n            return self._legacy_write(\n                sock_info, 'delete', command, op_id,\n                False, message.delete, self.__full_name, criteria,\n                False, write_concern.document,\n                self.__write_response_codec_options,\n                int(not multi))\n        # Delete command.\n        result = sock_info.command(\n            self.__database.name,\n            command,\n            write_concern=write_concern,\n            codec_options=self.__write_response_codec_options,\n            session=session,\n            client=self.__database.client,\n            retryable_write=retryable_write)\n        _check_write_command_response(result)\n        return result\n\n    def _delete_retryable(\n            self, criteria, multi,\n            write_concern=None, op_id=None, ordered=True,\n            collation=None, session=None):\n        \"\"\"Internal delete helper.\"\"\"\n        def _delete(session, sock_info, retryable_write):\n            return self._delete(\n                sock_info, criteria, multi,\n                write_concern=write_concern, op_id=op_id, ordered=ordered,\n                collation=collation, session=session,\n                retryable_write=retryable_write)\n\n        return self.__database.client._retryable_write(\n            (write_concern or self.write_concern).acknowledged and not multi,\n            _delete, session)\n\n    def delete_one(self, filter, collation=None, session=None):\n        \"\"\"Delete a single document matching the filter.\n\n          >>> db.test.count_documents({'x': 1})\n          3\n          >>> result = db.test.delete_one({'x': 1})\n          >>> result.deleted_count\n          1\n          >>> db.test.count_documents({'x': 1})\n          2\n\n        :Parameters:\n          - `filter`: A query that matches the document to delete.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only supported\n            on MongoDB 3.4 and above.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        :Returns:\n          - An instance of :class:`~pymongo.results.DeleteResult`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.4\n          Added the `collation` option.\n\n        .. versionadded:: 3.0\n        \"\"\"\n        write_concern = self._write_concern_for(session)\n        return DeleteResult(\n            self._delete_retryable(\n                filter, False,\n                write_concern=write_concern,\n                collation=collation, session=session),\n            write_concern.acknowledged)\n\n    def delete_many(self, filter, collation=None, session=None):\n        \"\"\"Delete one or more documents matching the filter.\n\n          >>> db.test.count_documents({'x': 1})\n          3\n          >>> result = db.test.delete_many({'x': 1})\n          >>> result.deleted_count\n          3\n          >>> db.test.count_documents({'x': 1})\n          0\n\n        :Parameters:\n          - `filter`: A query that matches the documents to delete.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only supported\n            on MongoDB 3.4 and above.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        :Returns:\n          - An instance of :class:`~pymongo.results.DeleteResult`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.4\n          Added the `collation` option.\n\n        .. versionadded:: 3.0\n        \"\"\"\n        write_concern = self._write_concern_for(session)\n        return DeleteResult(\n            self._delete_retryable(\n                filter, True,\n                write_concern=write_concern,\n                collation=collation, session=session),\n            write_concern.acknowledged)\n\n    def find_one(self, filter=None, *args, **kwargs):\n        \"\"\"Get a single document from the database.\n\n        All arguments to :meth:`find` are also valid arguments for\n        :meth:`find_one`, although any `limit` argument will be\n        ignored. Returns a single document, or ``None`` if no matching\n        document is found.\n\n        The :meth:`find_one` method obeys the :attr:`read_preference` of\n        this :class:`Collection`.\n\n        :Parameters:\n\n          - `filter` (optional): a dictionary specifying\n            the query to be performed OR any other type to be used as\n            the value for a query for ``\"_id\"``.\n\n          - `*args` (optional): any additional positional arguments\n            are the same as the arguments to :meth:`find`.\n\n          - `**kwargs` (optional): any additional keyword arguments\n            are the same as the arguments to :meth:`find`.\n\n              >>> collection.find_one(max_time_ms=100)\n        \"\"\"\n        if (filter is not None and not\n                isinstance(filter, abc.Mapping)):\n            filter = {\"_id\": filter}\n\n        cursor = self.find(filter, *args, **kwargs)\n        for result in cursor.limit(-1):\n            return result\n        return None\n\n    def find(self, *args, **kwargs):\n        \"\"\"Query the database.\n\n        The `filter` argument is a prototype document that all results\n        must match. For example:\n\n        >>> db.test.find({\"hello\": \"world\"})\n\n        only matches documents that have a key \"hello\" with value\n        \"world\".  Matches can have other keys *in addition* to\n        \"hello\". The `projection` argument is used to specify a subset\n        of fields that should be included in the result documents. By\n        limiting results to a certain subset of fields you can cut\n        down on network traffic and decoding time.\n\n        Raises :class:`TypeError` if any of the arguments are of\n        improper type. Returns an instance of\n        :class:`~pymongo.cursor.Cursor` corresponding to this query.\n\n        The :meth:`find` method obeys the :attr:`read_preference` of\n        this :class:`Collection`.\n\n        :Parameters:\n          - `filter` (optional): a SON object specifying elements which\n            must be present for a document to be included in the\n            result set\n          - `projection` (optional): a list of field names that should be\n            returned in the result set or a dict specifying the fields\n            to include or exclude. If `projection` is a list \"_id\" will\n            always be returned. Use a dict to exclude fields from\n            the result (e.g. projection={'_id': False}).\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `skip` (optional): the number of documents to omit (from\n            the start of the result set) when returning the results\n          - `limit` (optional): the maximum number of results to\n            return. A limit of 0 (the default) is equivalent to setting no\n            limit.\n          - `no_cursor_timeout` (optional): if False (the default), any\n            returned cursor is closed by the server after 10 minutes of\n            inactivity. If set to True, the returned cursor will never\n            time out on the server. Care should be taken to ensure that\n            cursors with no_cursor_timeout turned on are properly closed.\n          - `cursor_type` (optional): the type of cursor to return. The valid\n            options are defined by :class:`~pymongo.cursor.CursorType`:\n\n            - :attr:`~pymongo.cursor.CursorType.NON_TAILABLE` - the result of\n              this find call will return a standard cursor over the result set.\n            - :attr:`~pymongo.cursor.CursorType.TAILABLE` - the result of this\n              find call will be a tailable cursor - tailable cursors are only\n              for use with capped collections. They are not closed when the\n              last data is retrieved but are kept open and the cursor location\n              marks the final document position. If more data is received\n              iteration of the cursor will continue from the last document\n              received. For details, see the `tailable cursor documentation\n              <http://www.mongodb.org/display/DOCS/Tailable+Cursors>`_.\n            - :attr:`~pymongo.cursor.CursorType.TAILABLE_AWAIT` - the result\n              of this find call will be a tailable cursor with the await flag\n              set. The server will wait for a few seconds after returning the\n              full result set so that it can capture and return additional data\n              added during the query.\n            - :attr:`~pymongo.cursor.CursorType.EXHAUST` - the result of this\n              find call will be an exhaust cursor. MongoDB will stream batched\n              results to the client without waiting for the client to request\n              each batch, reducing latency. See notes on compatibility below.\n\n          - `sort` (optional): a list of (key, direction) pairs\n            specifying the sort order for this query. See\n            :meth:`~pymongo.cursor.Cursor.sort` for details.\n          - `allow_partial_results` (optional): if True, mongos will return\n            partial results if some shards are down instead of returning an\n            error.\n          - `oplog_replay` (optional): If True, set the oplogReplay query\n            flag.\n          - `batch_size` (optional): Limits the number of documents returned in\n            a single batch.\n          - `manipulate` (optional): **DEPRECATED** - If True (the default),\n            apply any outgoing SON manipulators before returning.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only supported\n            on MongoDB 3.4 and above.\n          - `return_key` (optional): If True, return only the index keys in\n            each document.\n          - `show_record_id` (optional): If True, adds a field ``$recordId`` in\n            each document with the storage engine's internal record identifier.\n          - `snapshot` (optional): **DEPRECATED** - If True, prevents the\n            cursor from returning a document more than once because of an\n            intervening write operation.\n          - `hint` (optional): An index, in the same format as passed to\n            :meth:`~pymongo.collection.Collection.create_index` (e.g.\n            ``[('field', ASCENDING)]``). Pass this as an alternative to calling\n            :meth:`~pymongo.cursor.Cursor.hint` on the cursor to tell Mongo the\n            proper index to use for the query.\n          - `max_time_ms` (optional): Specifies a time limit for a query\n            operation. If the specified time is exceeded, the operation will be\n            aborted and :exc:`~pymongo.errors.ExecutionTimeout` is raised. Pass\n            this as an alternative to calling\n            :meth:`~pymongo.cursor.Cursor.max_time_ms` on the cursor.\n          - `max_scan` (optional): **DEPRECATED** - The maximum number of\n            documents to scan. Pass this as an alternative to calling\n            :meth:`~pymongo.cursor.Cursor.max_scan` on the cursor.\n          - `min` (optional): A list of field, limit pairs specifying the\n            inclusive lower bound for all keys of a specific index in order.\n            Pass this as an alternative to calling\n            :meth:`~pymongo.cursor.Cursor.min` on the cursor. ``hint`` must\n            also be passed to ensure the query utilizes the correct index.\n          - `max` (optional): A list of field, limit pairs specifying the\n            exclusive upper bound for all keys of a specific index in order.\n            Pass this as an alternative to calling\n            :meth:`~pymongo.cursor.Cursor.max` on the cursor. ``hint`` must\n            also be passed to ensure the query utilizes the correct index.\n          - `comment` (optional): A string to attach to the query to help\n            interpret and trace the operation in the server logs and in profile\n            data. Pass this as an alternative to calling\n            :meth:`~pymongo.cursor.Cursor.comment` on the cursor.\n          - `modifiers` (optional): **DEPRECATED** - A dict specifying\n            additional MongoDB query modifiers. Use the keyword arguments listed\n            above instead.\n\n        .. note:: There are a number of caveats to using\n          :attr:`~pymongo.cursor.CursorType.EXHAUST` as cursor_type:\n\n          - The `limit` option can not be used with an exhaust cursor.\n\n          - Exhaust cursors are not supported by mongos and can not be\n            used with a sharded cluster.\n\n          - A :class:`~pymongo.cursor.Cursor` instance created with the\n            :attr:`~pymongo.cursor.CursorType.EXHAUST` cursor_type requires an\n            exclusive :class:`~socket.socket` connection to MongoDB. If the\n            :class:`~pymongo.cursor.Cursor` is discarded without being\n            completely iterated the underlying :class:`~socket.socket`\n            connection will be closed and discarded without being returned to\n            the connection pool.\n\n        .. versionchanged:: 3.7\n           Deprecated the `snapshot` option, which is deprecated in MongoDB\n           3.6 and removed in MongoDB 4.0.\n           Deprecated the `max_scan` option. Support for this option is\n           deprecated in MongoDB 4.0. Use `max_time_ms` instead to limit server\n           side execution time.\n\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.5\n           Added the options `return_key`, `show_record_id`, `snapshot`,\n           `hint`, `max_time_ms`, `max_scan`, `min`, `max`, and `comment`.\n           Deprecated the option `modifiers`.\n\n        .. versionchanged:: 3.4\n           Support the `collation` option.\n\n        .. versionchanged:: 3.0\n           Changed the parameter names `spec`, `fields`, `timeout`, and\n           `partial` to `filter`, `projection`, `no_cursor_timeout`, and\n           `allow_partial_results` respectively.\n           Added the `cursor_type`, `oplog_replay`, and `modifiers` options.\n           Removed the `network_timeout`, `read_preference`, `tag_sets`,\n           `secondary_acceptable_latency_ms`, `max_scan`, `snapshot`,\n           `tailable`, `await_data`, `exhaust`, `as_class`, and slave_okay\n           parameters. Removed `compile_re` option: PyMongo now always\n           represents BSON regular expressions as :class:`~bson.regex.Regex`\n           objects. Use :meth:`~bson.regex.Regex.try_compile` to attempt to\n           convert from a BSON regular expression to a Python regular\n           expression object. Soft deprecated the `manipulate` option.\n\n        .. versionchanged:: 2.7\n           Added `compile_re` option. If set to False, PyMongo represented BSON\n           regular expressions as :class:`~bson.regex.Regex` objects instead of\n           attempting to compile BSON regular expressions as Python native\n           regular expressions, thus preventing errors for some incompatible\n           patterns, see `PYTHON-500`_.\n\n        .. versionadded:: 2.3\n           The `tag_sets` and `secondary_acceptable_latency_ms` parameters.\n\n        .. _PYTHON-500: https://jira.mongodb.org/browse/PYTHON-500\n\n        .. mongodoc:: find\n\n        \"\"\"\n        return Cursor(self, *args, **kwargs)\n\n    def find_raw_batches(self, *args, **kwargs):\n        \"\"\"Query the database and retrieve batches of raw BSON.\n\n        Similar to the :meth:`find` method but returns a\n        :class:`~pymongo.cursor.RawBatchCursor`.\n\n        This example demonstrates how to work with raw batches, but in practice\n        raw batches should be passed to an external library that can decode\n        BSON into another data type, rather than used with PyMongo's\n        :mod:`bson` module.\n\n          >>> import bson\n          >>> cursor = db.test.find_raw_batches()\n          >>> for batch in cursor:\n          ...     print(bson.decode_all(batch))\n\n        .. note:: find_raw_batches does not support sessions or auto\n           encryption.\n\n        .. versionadded:: 3.6\n        \"\"\"\n        # OP_MSG with document stream returns is required to support\n        # sessions.\n        if \"session\" in kwargs:\n            raise ConfigurationError(\n                \"find_raw_batches does not support sessions\")\n\n        # OP_MSG is required to support encryption.\n        if self.__database.client._encrypter:\n            raise InvalidOperation(\n                \"find_raw_batches does not support auto encryption\")\n\n        return RawBatchCursor(self, *args, **kwargs)\n\n    def parallel_scan(self, num_cursors, session=None, **kwargs):\n        \"\"\"**DEPRECATED**: Scan this entire collection in parallel.\n\n        Returns a list of up to ``num_cursors`` cursors that can be iterated\n        concurrently. As long as the collection is not modified during\n        scanning, each document appears once in one of the cursors result\n        sets.\n\n        For example, to process each document in a collection using some\n        thread-safe ``process_document()`` function:\n\n          >>> def process_cursor(cursor):\n          ...     for document in cursor:\n          ...     # Some thread-safe processing function:\n          ...     process_document(document)\n          >>>\n          >>> # Get up to 4 cursors.\n          ...\n          >>> cursors = collection.parallel_scan(4)\n          >>> threads = [\n          ...     threading.Thread(target=process_cursor, args=(cursor,))\n          ...     for cursor in cursors]\n          >>>\n          >>> for thread in threads:\n          ...     thread.start()\n          >>>\n          >>> for thread in threads:\n          ...     thread.join()\n          >>>\n          >>> # All documents have now been processed.\n\n        The :meth:`parallel_scan` method obeys the :attr:`read_preference` of\n        this :class:`Collection`.\n\n        :Parameters:\n          - `num_cursors`: the number of cursors to return\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs`: additional options for the parallelCollectionScan\n            command can be passed as keyword arguments.\n\n        .. note:: Requires server version **>= 2.5.5**.\n\n        .. versionchanged:: 3.7\n           Deprecated.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.4\n           Added back support for arbitrary keyword arguments. MongoDB 3.4\n           adds support for maxTimeMS as an option to the\n           parallelCollectionScan command.\n\n        .. versionchanged:: 3.0\n           Removed support for arbitrary keyword arguments, since\n           the parallelCollectionScan command has no optional arguments.\n        \"\"\"\n        warnings.warn(\"parallel_scan is deprecated. MongoDB 4.2 will remove \"\n                      \"the parallelCollectionScan command.\",\n                      DeprecationWarning, stacklevel=2)\n        cmd = SON([('parallelCollectionScan', self.__name),\n                   ('numCursors', num_cursors)])\n        cmd.update(kwargs)\n\n        with self._socket_for_reads(session) as (sock_info, slave_ok):\n            # We call sock_info.command here directly, instead of\n            # calling self._command to avoid using an implicit session.\n            result = sock_info.command(\n                self.__database.name,\n                cmd,\n                slave_ok,\n                self._read_preference_for(session),\n                self.codec_options,\n                read_concern=self.read_concern,\n                parse_write_concern_error=True,\n                session=session,\n                client=self.__database.client)\n\n        cursors = []\n        for cursor in result['cursors']:\n            cursors.append(CommandCursor(\n                self, cursor['cursor'], sock_info.address,\n                session=session, explicit_session=session is not None))\n\n        return cursors\n\n    def _count(self, cmd, collation=None, session=None):\n        \"\"\"Internal count helper.\"\"\"\n        def _cmd(session, server, sock_info, slave_ok):\n            res = self._command(\n                sock_info,\n                cmd,\n                slave_ok,\n                allowable_errors=[\"ns missing\"],\n                codec_options=self.__write_response_codec_options,\n                read_concern=self.read_concern,\n                collation=collation,\n                session=session)\n            if res.get(\"errmsg\", \"\") == \"ns missing\":\n                return 0\n            return int(res[\"n\"])\n\n        return self.__database.client._retryable_read(\n            _cmd, self._read_preference_for(session), session)\n\n    def _aggregate_one_result(\n            self, sock_info, slave_ok, cmd, collation=None, session=None):\n        \"\"\"Internal helper to run an aggregate that returns a single result.\"\"\"\n        result = self._command(\n            sock_info,\n            cmd,\n            slave_ok,\n            codec_options=self.__write_response_codec_options,\n            read_concern=self.read_concern,\n            collation=collation,\n            session=session)\n        batch = result['cursor']['firstBatch']\n        return batch[0] if batch else None\n\n    def estimated_document_count(self, **kwargs):\n        \"\"\"Get an estimate of the number of documents in this collection using\n        collection metadata.\n\n        The :meth:`estimated_document_count` method is **not** supported in a\n        transaction.\n\n        All optional parameters should be passed as keyword arguments\n        to this method. Valid options include:\n\n          - `maxTimeMS` (int): The maximum amount of time to allow this\n            operation to run, in milliseconds.\n\n        :Parameters:\n          - `**kwargs` (optional): See list of options above.\n\n        .. versionadded:: 3.7\n        \"\"\"\n        if 'session' in kwargs:\n            raise ConfigurationError(\n                'estimated_document_count does not support sessions')\n        cmd = SON([('count', self.__name)])\n        cmd.update(kwargs)\n        return self._count(cmd)\n\n    def count_documents(self, filter, session=None, **kwargs):\n        \"\"\"Count the number of documents in this collection.\n\n        .. note:: For a fast count of the total documents in a collection see\n           :meth:`estimated_document_count`.\n\n        The :meth:`count_documents` method is supported in a transaction.\n\n        All optional parameters should be passed as keyword arguments\n        to this method. Valid options include:\n\n          - `skip` (int): The number of matching documents to skip before\n            returning results.\n          - `limit` (int): The maximum number of documents to count. Must be\n            a positive integer. If not provided, no limit is imposed.\n          - `maxTimeMS` (int): The maximum amount of time to allow this\n            operation to run, in milliseconds.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only supported\n            on MongoDB 3.4 and above.\n          - `hint` (string or list of tuples): The index to use. Specify either\n            the index name as a string or the index specification as a list of\n            tuples (e.g. [('a', pymongo.ASCENDING), ('b', pymongo.ASCENDING)]).\n            This option is only supported on MongoDB 3.6 and above.\n\n        The :meth:`count_documents` method obeys the :attr:`read_preference` of\n        this :class:`Collection`.\n\n        .. note:: When migrating from :meth:`count` to :meth:`count_documents`\n           the following query operators must be replaced:\n\n           +-------------+-------------------------------------+\n           | Operator    | Replacement                         |\n           +=============+=====================================+\n           | $where      | `$expr`_                            |\n           +-------------+-------------------------------------+\n           | $near       | `$geoWithin`_ with `$center`_       |\n           +-------------+-------------------------------------+\n           | $nearSphere | `$geoWithin`_ with `$centerSphere`_ |\n           +-------------+-------------------------------------+\n\n           $expr requires MongoDB 3.6+\n\n        :Parameters:\n          - `filter` (required): A query document that selects which documents\n            to count in the collection. Can be an empty document to count all\n            documents.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): See list of options above.\n\n        .. versionadded:: 3.7\n\n        .. _$expr: https://docs.mongodb.com/manual/reference/operator/query/expr/\n        .. _$geoWithin: https://docs.mongodb.com/manual/reference/operator/query/geoWithin/\n        .. _$center: https://docs.mongodb.com/manual/reference/operator/query/center/#op._S_center\n        .. _$centerSphere: https://docs.mongodb.com/manual/reference/operator/query/centerSphere/#op._S_centerSphere\n        \"\"\"\n        pipeline = [{'$match': filter}]\n        if 'skip' in kwargs:\n            pipeline.append({'$skip': kwargs.pop('skip')})\n        if 'limit' in kwargs:\n            pipeline.append({'$limit': kwargs.pop('limit')})\n        pipeline.append({'$group': {'_id': 1, 'n': {'$sum': 1}}})\n        cmd = SON([('aggregate', self.__name),\n                   ('pipeline', pipeline),\n                   ('cursor', {})])\n        if \"hint\" in kwargs and not isinstance(kwargs[\"hint\"], string_type):\n            kwargs[\"hint\"] = helpers._index_document(kwargs[\"hint\"])\n        collation = validate_collation_or_none(kwargs.pop('collation', None))\n        cmd.update(kwargs)\n\n        def _cmd(session, server, sock_info, slave_ok):\n            result = self._aggregate_one_result(\n                sock_info, slave_ok, cmd, collation, session)\n            if not result:\n                return 0\n            return result['n']\n\n        return self.__database.client._retryable_read(\n            _cmd, self._read_preference_for(session), session)\n\n    def count(self, filter=None, session=None, **kwargs):\n        \"\"\"**DEPRECATED** - Get the number of documents in this collection.\n\n        The :meth:`count` method is deprecated and **not** supported in a\n        transaction. Please use :meth:`count_documents` or\n        :meth:`estimated_document_count` instead.\n\n        All optional count parameters should be passed as keyword arguments\n        to this method. Valid options include:\n\n          - `skip` (int): The number of matching documents to skip before\n            returning results.\n          - `limit` (int): The maximum number of documents to count. A limit\n            of 0 (the default) is equivalent to setting no limit.\n          - `maxTimeMS` (int): The maximum amount of time to allow the count\n            command to run, in milliseconds.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only supported\n            on MongoDB 3.4 and above.\n          - `hint` (string or list of tuples): The index to use. Specify either\n            the index name as a string or the index specification as a list of\n            tuples (e.g. [('a', pymongo.ASCENDING), ('b', pymongo.ASCENDING)]).\n\n        The :meth:`count` method obeys the :attr:`read_preference` of\n        this :class:`Collection`.\n\n        .. note:: When migrating from :meth:`count` to :meth:`count_documents`\n           the following query operators must be replaced:\n\n           +-------------+-------------------------------------+\n           | Operator    | Replacement                         |\n           +=============+=====================================+\n           | $where      | `$expr`_                            |\n           +-------------+-------------------------------------+\n           | $near       | `$geoWithin`_ with `$center`_       |\n           +-------------+-------------------------------------+\n           | $nearSphere | `$geoWithin`_ with `$centerSphere`_ |\n           +-------------+-------------------------------------+\n\n           $expr requires MongoDB 3.6+\n\n        :Parameters:\n          - `filter` (optional): A query document that selects which documents\n            to count in the collection.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): See list of options above.\n\n        .. versionchanged:: 3.7\n           Deprecated.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.4\n           Support the `collation` option.\n\n        .. _$expr: https://docs.mongodb.com/manual/reference/operator/query/expr/\n        .. _$geoWithin: https://docs.mongodb.com/manual/reference/operator/query/geoWithin/\n        .. _$center: https://docs.mongodb.com/manual/reference/operator/query/center/#op._S_center\n        .. _$centerSphere: https://docs.mongodb.com/manual/reference/operator/query/centerSphere/#op._S_centerSphere\n        \"\"\"\n        warnings.warn(\"count is deprecated. Use estimated_document_count or \"\n                      \"count_documents instead. Please note that $where must \"\n                      \"be replaced by $expr, $near must be replaced by \"\n                      \"$geoWithin with $center, and $nearSphere must be \"\n                      \"replaced by $geoWithin with $centerSphere\",\n                      DeprecationWarning, stacklevel=2)\n        cmd = SON([(\"count\", self.__name)])\n        if filter is not None:\n            if \"query\" in kwargs:\n                raise ConfigurationError(\"can't pass both filter and query\")\n            kwargs[\"query\"] = filter\n        if \"hint\" in kwargs and not isinstance(kwargs[\"hint\"], string_type):\n            kwargs[\"hint\"] = helpers._index_document(kwargs[\"hint\"])\n        collation = validate_collation_or_none(kwargs.pop('collation', None))\n        cmd.update(kwargs)\n        return self._count(cmd, collation, session)\n\n    def create_indexes(self, indexes, session=None, **kwargs):\n        \"\"\"Create one or more indexes on this collection.\n\n          >>> from pymongo import IndexModel, ASCENDING, DESCENDING\n          >>> index1 = IndexModel([(\"hello\", DESCENDING),\n          ...                      (\"world\", ASCENDING)], name=\"hello_world\")\n          >>> index2 = IndexModel([(\"goodbye\", DESCENDING)])\n          >>> db.test.create_indexes([index1, index2])\n          [\"hello_world\", \"goodbye_-1\"]\n\n        :Parameters:\n          - `indexes`: A list of :class:`~pymongo.operations.IndexModel`\n            instances.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): optional arguments to the createIndexes\n            command (like maxTimeMS) can be passed as keyword arguments.\n\n        .. note:: `create_indexes` uses the `createIndexes`_ command\n           introduced in MongoDB **2.6** and cannot be used with earlier\n           versions.\n\n        .. note:: The :attr:`~pymongo.collection.Collection.write_concern` of\n           this collection is automatically applied to this operation when using\n           MongoDB >= 3.4.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter. Added support for arbitrary keyword\n           arguments.\n\n        .. versionchanged:: 3.4\n           Apply this collection's write concern automatically to this operation\n           when connected to MongoDB >= 3.4.\n        .. versionadded:: 3.0\n\n        .. _createIndexes: https://docs.mongodb.com/manual/reference/command/createIndexes/\n        \"\"\"\n        common.validate_list('indexes', indexes)\n        names = []\n        with self._socket_for_writes(session) as sock_info:\n            supports_collations = sock_info.max_wire_version >= 5\n            def gen_indexes():\n                for index in indexes:\n                    if not isinstance(index, IndexModel):\n                        raise TypeError(\n                            \"%r is not an instance of \"\n                            \"pymongo.operations.IndexModel\" % (index,))\n                    document = index.document\n                    if \"collation\" in document and not supports_collations:\n                        raise ConfigurationError(\n                            \"Must be connected to MongoDB \"\n                            \"3.4+ to use collations.\")\n                    names.append(document[\"name\"])\n                    yield document\n            cmd = SON([('createIndexes', self.name),\n                       ('indexes', list(gen_indexes()))])\n            cmd.update(kwargs)\n            self._command(\n                sock_info, cmd, read_preference=ReadPreference.PRIMARY,\n                codec_options=_UNICODE_REPLACE_CODEC_OPTIONS,\n                write_concern=self._write_concern_for(session),\n                session=session)\n        return names\n\n    def __create_index(self, keys, index_options, session, **kwargs):\n        \"\"\"Internal create index helper.\n\n        :Parameters:\n          - `keys`: a list of tuples [(key, type), (key, type), ...]\n          - `index_options`: a dict of index options.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n        \"\"\"\n        index_doc = helpers._index_document(keys)\n        index = {\"key\": index_doc}\n        collation = validate_collation_or_none(\n            index_options.pop('collation', None))\n        index.update(index_options)\n\n        with self._socket_for_writes(session) as sock_info:\n            if collation is not None:\n                if sock_info.max_wire_version < 5:\n                    raise ConfigurationError(\n                        'Must be connected to MongoDB 3.4+ to use collations.')\n                else:\n                    index['collation'] = collation\n            cmd = SON([('createIndexes', self.name), ('indexes', [index])])\n            cmd.update(kwargs)\n            self._command(\n                sock_info, cmd, read_preference=ReadPreference.PRIMARY,\n                codec_options=_UNICODE_REPLACE_CODEC_OPTIONS,\n                write_concern=self._write_concern_for(session),\n                session=session)\n\n    def create_index(self, keys, session=None, **kwargs):\n        \"\"\"Creates an index on this collection.\n\n        Takes either a single key or a list of (key, direction) pairs.\n        The key(s) must be an instance of :class:`basestring`\n        (:class:`str` in python 3), and the direction(s) must be one of\n        (:data:`~pymongo.ASCENDING`, :data:`~pymongo.DESCENDING`,\n        :data:`~pymongo.GEO2D`, :data:`~pymongo.GEOHAYSTACK`,\n        :data:`~pymongo.GEOSPHERE`, :data:`~pymongo.HASHED`,\n        :data:`~pymongo.TEXT`).\n\n        To create a single key ascending index on the key ``'mike'`` we just\n        use a string argument::\n\n          >>> my_collection.create_index(\"mike\")\n\n        For a compound index on ``'mike'`` descending and ``'eliot'``\n        ascending we need to use a list of tuples::\n\n          >>> my_collection.create_index([(\"mike\", pymongo.DESCENDING),\n          ...                             (\"eliot\", pymongo.ASCENDING)])\n\n        All optional index creation parameters should be passed as\n        keyword arguments to this method. For example::\n\n          >>> my_collection.create_index([(\"mike\", pymongo.DESCENDING)],\n          ...                            background=True)\n\n        Valid options include, but are not limited to:\n\n          - `name`: custom name to use for this index - if none is\n            given, a name will be generated.\n          - `unique`: if ``True`` creates a uniqueness constraint on the index.\n          - `background`: if ``True`` this index should be created in the\n            background.\n          - `sparse`: if ``True``, omit from the index any documents that lack\n            the indexed field.\n          - `bucketSize`: for use with geoHaystack indexes.\n            Number of documents to group together within a certain proximity\n            to a given longitude and latitude.\n          - `min`: minimum value for keys in a :data:`~pymongo.GEO2D`\n            index.\n          - `max`: maximum value for keys in a :data:`~pymongo.GEO2D`\n            index.\n          - `expireAfterSeconds`: <int> Used to create an expiring (TTL)\n            collection. MongoDB will automatically delete documents from\n            this collection after <int> seconds. The indexed field must\n            be a UTC datetime or the data will not expire.\n          - `partialFilterExpression`: A document that specifies a filter for\n            a partial index. Requires server version >=3.2.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only supported\n            on MongoDB 3.4 and above.\n          - `wildcardProjection`: Allows users to include or exclude specific\n            field paths from a `wildcard index`_ using the { \"$**\" : 1} key\n            pattern. Requires server version >= 4.2.\n\n        See the MongoDB documentation for a full list of supported options by\n        server version.\n\n        .. warning:: `dropDups` is not supported by MongoDB 3.0 or newer. The\n          option is silently ignored by the server and unique index builds\n          using the option will fail if a duplicate value is detected.\n\n        .. note:: The :attr:`~pymongo.collection.Collection.write_concern` of\n           this collection is automatically applied to this operation when using\n           MongoDB >= 3.4.\n\n        :Parameters:\n          - `keys`: a single key or a list of (key, direction)\n            pairs specifying the index to create\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): any additional index creation\n            options (see the above list) should be passed as keyword\n            arguments\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter. Added support for passing maxTimeMS\n           in kwargs.\n        .. versionchanged:: 3.4\n           Apply this collection's write concern automatically to this operation\n           when connected to MongoDB >= 3.4. Support the `collation` option.\n        .. versionchanged:: 3.2\n            Added partialFilterExpression to support partial indexes.\n        .. versionchanged:: 3.0\n            Renamed `key_or_list` to `keys`. Removed the `cache_for` option.\n            :meth:`create_index` no longer caches index names. Removed support\n            for the drop_dups and bucket_size aliases.\n\n        .. mongodoc:: indexes\n\n        .. _wildcard index: https://docs.mongodb.com/master/core/index-wildcard/#wildcard-index-core\n        \"\"\"\n        keys = helpers._index_list(keys)\n        name = kwargs.setdefault(\"name\", helpers._gen_index_name(keys))\n        cmd_options = {}\n        if \"maxTimeMS\" in kwargs:\n            cmd_options[\"maxTimeMS\"] = kwargs.pop(\"maxTimeMS\")\n        self.__create_index(keys, kwargs, session, **cmd_options)\n        return name\n\n    def ensure_index(self, key_or_list, cache_for=300, **kwargs):\n        \"\"\"**DEPRECATED** - Ensures that an index exists on this collection.\n\n        .. versionchanged:: 3.0\n            **DEPRECATED**\n        \"\"\"\n        warnings.warn(\"ensure_index is deprecated. Use create_index instead.\",\n                      DeprecationWarning, stacklevel=2)\n        # The types supported by datetime.timedelta.\n        if not (isinstance(cache_for, integer_types) or\n                isinstance(cache_for, float)):\n            raise TypeError(\"cache_for must be an integer or float.\")\n\n        if \"drop_dups\" in kwargs:\n            kwargs[\"dropDups\"] = kwargs.pop(\"drop_dups\")\n\n        if \"bucket_size\" in kwargs:\n            kwargs[\"bucketSize\"] = kwargs.pop(\"bucket_size\")\n\n        keys = helpers._index_list(key_or_list)\n        name = kwargs.setdefault(\"name\", helpers._gen_index_name(keys))\n\n        # Note that there is a race condition here. One thread could\n        # check if the index is cached and be preempted before creating\n        # and caching the index. This means multiple threads attempting\n        # to create the same index concurrently could send the index\n        # to the server two or more times. This has no practical impact\n        # other than wasted round trips.\n        if not self.__database.client._cached(self.__database.name,\n                                              self.__name, name):\n            self.__create_index(keys, kwargs, session=None)\n            self.__database.client._cache_index(self.__database.name,\n                                                self.__name, name, cache_for)\n            return name\n        return None\n\n    def drop_indexes(self, session=None, **kwargs):\n        \"\"\"Drops all indexes on this collection.\n\n        Can be used on non-existant collections or collections with no indexes.\n        Raises OperationFailure on an error.\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): optional arguments to the createIndexes\n            command (like maxTimeMS) can be passed as keyword arguments.\n\n        .. note:: The :attr:`~pymongo.collection.Collection.write_concern` of\n           this collection is automatically applied to this operation when using\n           MongoDB >= 3.4.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter. Added support for arbitrary keyword\n           arguments.\n\n        .. versionchanged:: 3.4\n           Apply this collection's write concern automatically to this operation\n           when connected to MongoDB >= 3.4.\n\n        \"\"\"\n        self.__database.client._purge_index(self.__database.name, self.__name)\n        self.drop_index(\"*\", session=session, **kwargs)\n\n    def drop_index(self, index_or_name, session=None, **kwargs):\n        \"\"\"Drops the specified index on this collection.\n\n        Can be used on non-existant collections or collections with no\n        indexes.  Raises OperationFailure on an error (e.g. trying to\n        drop an index that does not exist). `index_or_name`\n        can be either an index name (as returned by `create_index`),\n        or an index specifier (as passed to `create_index`). An index\n        specifier should be a list of (key, direction) pairs. Raises\n        TypeError if index is not an instance of (str, unicode, list).\n\n        .. warning::\n\n          if a custom name was used on index creation (by\n          passing the `name` parameter to :meth:`create_index` or\n          :meth:`ensure_index`) the index **must** be dropped by name.\n\n        :Parameters:\n          - `index_or_name`: index (or name of index) to drop\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): optional arguments to the createIndexes\n            command (like maxTimeMS) can be passed as keyword arguments.\n\n        .. note:: The :attr:`~pymongo.collection.Collection.write_concern` of\n           this collection is automatically applied to this operation when using\n           MongoDB >= 3.4.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter. Added support for arbitrary keyword\n           arguments.\n\n        .. versionchanged:: 3.4\n           Apply this collection's write concern automatically to this operation\n           when connected to MongoDB >= 3.4.\n\n        \"\"\"\n        name = index_or_name\n        if isinstance(index_or_name, list):\n            name = helpers._gen_index_name(index_or_name)\n\n        if not isinstance(name, string_type):\n            raise TypeError(\"index_or_name must be an index name or list\")\n\n        self.__database.client._purge_index(\n            self.__database.name, self.__name, name)\n        cmd = SON([(\"dropIndexes\", self.__name), (\"index\", name)])\n        cmd.update(kwargs)\n        with self._socket_for_writes(session) as sock_info:\n            self._command(sock_info,\n                          cmd,\n                          read_preference=ReadPreference.PRIMARY,\n                          allowable_errors=[\"ns not found\"],\n                          write_concern=self._write_concern_for(session),\n                          session=session)\n\n    def reindex(self, session=None, **kwargs):\n        \"\"\"Rebuilds all indexes on this collection.\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): optional arguments to the reIndex\n            command (like maxTimeMS) can be passed as keyword arguments.\n\n        .. warning:: reindex blocks all other operations (indexes\n           are built in the foreground) and will be slow for large\n           collections.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter. Added support for arbitrary keyword\n           arguments.\n\n        .. versionchanged:: 3.4\n           Apply this collection's write concern automatically to this operation\n           when connected to MongoDB >= 3.4.\n\n        .. versionchanged:: 3.5\n           We no longer apply this collection's write concern to this operation.\n           MongoDB 3.4 silently ignored the write concern. MongoDB 3.6+ returns\n           an error if we include the write concern.\n        \"\"\"\n        cmd = SON([(\"reIndex\", self.__name)])\n        cmd.update(kwargs)\n        with self._socket_for_writes(session) as sock_info:\n            return self._command(\n                sock_info, cmd, read_preference=ReadPreference.PRIMARY,\n                session=session)\n\n    def list_indexes(self, session=None):\n        \"\"\"Get a cursor over the index documents for this collection.\n\n          >>> for index in db.test.list_indexes():\n          ...     print(index)\n          ...\n          SON([(u'v', 1), (u'key', SON([(u'_id', 1)])),\n               (u'name', u'_id_'), (u'ns', u'test.test')])\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        :Returns:\n          An instance of :class:`~pymongo.command_cursor.CommandCursor`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionadded:: 3.0\n        \"\"\"\n        codec_options = CodecOptions(SON)\n        coll = self.with_options(codec_options=codec_options,\n                                 read_preference=ReadPreference.PRIMARY)\n        read_pref = ((session and session._txn_read_preference())\n                     or ReadPreference.PRIMARY)\n\n        def _cmd(session, server, sock_info, slave_ok):\n            cmd = SON([(\"listIndexes\", self.__name), (\"cursor\", {})])\n            if sock_info.max_wire_version > 2:\n                with self.__database.client._tmp_session(session, False) as s:\n                    try:\n                        cursor = self._command(sock_info, cmd, slave_ok,\n                                               read_pref,\n                                               codec_options,\n                                               session=s)[\"cursor\"]\n                    except OperationFailure as exc:\n                        # Ignore NamespaceNotFound errors to match the behavior\n                        # of reading from *.system.indexes.\n                        if exc.code != 26:\n                            raise\n                        cursor = {'id': 0, 'firstBatch': []}\n                return CommandCursor(coll, cursor, sock_info.address,\n                                     session=s,\n                                     explicit_session=session is not None)\n            else:\n                res = message._first_batch(\n                    sock_info, self.__database.name, \"system.indexes\",\n                    {\"ns\": self.__full_name}, 0, slave_ok, codec_options,\n                    read_pref, cmd,\n                    self.database.client._event_listeners)\n                cursor = res[\"cursor\"]\n                # Note that a collection can only have 64 indexes, so there\n                # will never be a getMore call.\n                return CommandCursor(coll, cursor, sock_info.address)\n\n        return self.__database.client._retryable_read(\n            _cmd, read_pref, session)\n\n    def index_information(self, session=None):\n        \"\"\"Get information on this collection's indexes.\n\n        Returns a dictionary where the keys are index names (as\n        returned by create_index()) and the values are dictionaries\n        containing information about each index. The dictionary is\n        guaranteed to contain at least a single key, ``\"key\"`` which\n        is a list of (key, direction) pairs specifying the index (as\n        passed to create_index()). It will also contain any other\n        metadata about the indexes, except for the ``\"ns\"`` and\n        ``\"name\"`` keys, which are cleaned. Example output might look\n        like this:\n\n        >>> db.test.create_index(\"x\", unique=True)\n        u'x_1'\n        >>> db.test.index_information()\n        {u'_id_': {u'key': [(u'_id', 1)]},\n         u'x_1': {u'unique': True, u'key': [(u'x', 1)]}}\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        cursor = self.list_indexes(session=session)\n        info = {}\n        for index in cursor:\n            index[\"key\"] = index[\"key\"].items()\n            index = dict(index)\n            info[index.pop(\"name\")] = index\n        return info\n\n    def options(self, session=None):\n        \"\"\"Get the options set on this collection.\n\n        Returns a dictionary of options and their values - see\n        :meth:`~pymongo.database.Database.create_collection` for more\n        information on the possible options. Returns an empty\n        dictionary if the collection has not been created yet.\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        dbo = self.__database.client.get_database(\n            self.__database.name,\n            self.codec_options,\n            self.read_preference,\n            self.write_concern,\n            self.read_concern)\n        cursor = dbo.list_collections(\n            session=session, filter={\"name\": self.__name})\n\n        result = None\n        for doc in cursor:\n            result = doc\n            break\n\n        if not result:\n            return {}\n\n        options = result.get(\"options\", {})\n        if \"create\" in options:\n            del options[\"create\"]\n\n        return options\n\n    def _aggregate(self, aggregation_command, pipeline, cursor_class, session,\n                   explicit_session, **kwargs):\n        # Remove things that are not command options.\n        use_cursor = True\n        if \"useCursor\" in kwargs:\n            warnings.warn(\n                \"The useCursor option is deprecated \"\n                \"and will be removed in PyMongo 4.0\",\n                DeprecationWarning, stacklevel=2)\n            use_cursor = common.validate_boolean(\n                \"useCursor\", kwargs.pop(\"useCursor\", True))\n\n        cmd = aggregation_command(\n            self, cursor_class, pipeline, kwargs, explicit_session,\n            user_fields={'cursor': {'firstBatch': 1}}, use_cursor=use_cursor)\n        return self.__database.client._retryable_read(\n            cmd.get_cursor, cmd.get_read_preference(session), session,\n            retryable=not cmd._performs_write)\n\n    def aggregate(self, pipeline, session=None, **kwargs):\n        \"\"\"Perform an aggregation using the aggregation framework on this\n        collection.\n\n        All optional `aggregate command`_ parameters should be passed as\n        keyword arguments to this method. Valid options include, but are not\n        limited to:\n\n          - `allowDiskUse` (bool): Enables writing to temporary files. When set\n            to True, aggregation stages can write data to the _tmp subdirectory\n            of the --dbpath directory. The default is False.\n          - `maxTimeMS` (int): The maximum amount of time to allow the operation\n            to run in milliseconds.\n          - `batchSize` (int): The maximum number of documents to return per\n            batch. Ignored if the connected mongod or mongos does not support\n            returning aggregate results using a cursor, or `useCursor` is\n            ``False``.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only supported\n            on MongoDB 3.4 and above.\n          - `useCursor` (bool): Deprecated. Will be removed in PyMongo 4.0.\n\n        The :meth:`aggregate` method obeys the :attr:`read_preference` of this\n        :class:`Collection`, except when ``$out`` or ``$merge`` are used, in\n        which case  :attr:`~pymongo.read_preferences.ReadPreference.PRIMARY`\n        is used.\n\n        .. note:: This method does not support the 'explain' option. Please\n           use :meth:`~pymongo.database.Database.command` instead. An\n           example is included in the :ref:`aggregate-examples` documentation.\n\n        .. note:: The :attr:`~pymongo.collection.Collection.write_concern` of\n           this collection is automatically applied to this operation when using\n           MongoDB >= 3.4.\n\n        :Parameters:\n          - `pipeline`: a list of aggregation pipeline stages\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): See list of options above.\n\n        :Returns:\n          A :class:`~pymongo.command_cursor.CommandCursor` over the result\n          set.\n\n        .. versionchanged:: 3.9\n           Apply this collection's read concern to pipelines containing the\n           `$out` stage when connected to MongoDB >= 4.2.\n           Added support for the ``$merge`` pipeline stage.\n           Aggregations that write always use read preference\n           :attr:`~pymongo.read_preferences.ReadPreference.PRIMARY`.\n        .. versionchanged:: 3.6\n           Added the `session` parameter. Added the `maxAwaitTimeMS` option.\n           Deprecated the `useCursor` option.\n        .. versionchanged:: 3.4\n           Apply this collection's write concern automatically to this operation\n           when connected to MongoDB >= 3.4. Support the `collation` option.\n        .. versionchanged:: 3.0\n           The :meth:`aggregate` method always returns a CommandCursor. The\n           pipeline argument must be a list.\n        .. versionchanged:: 2.7\n           When the cursor option is used, return\n           :class:`~pymongo.command_cursor.CommandCursor` instead of\n           :class:`~pymongo.cursor.Cursor`.\n        .. versionchanged:: 2.6\n           Added cursor support.\n        .. versionadded:: 2.3\n\n        .. seealso:: :doc:`/examples/aggregation`\n\n        .. _aggregate command:\n            https://docs.mongodb.com/manual/reference/command/aggregate\n        \"\"\"\n        with self.__database.client._tmp_session(session, close=False) as s:\n            return self._aggregate(_CollectionAggregationCommand,\n                                   pipeline,\n                                   CommandCursor,\n                                   session=s,\n                                   explicit_session=session is not None,\n                                   **kwargs)\n\n    def aggregate_raw_batches(self, pipeline, **kwargs):\n        \"\"\"Perform an aggregation and retrieve batches of raw BSON.\n\n        Similar to the :meth:`aggregate` method but returns a\n        :class:`~pymongo.cursor.RawBatchCursor`.\n\n        This example demonstrates how to work with raw batches, but in practice\n        raw batches should be passed to an external library that can decode\n        BSON into another data type, rather than used with PyMongo's\n        :mod:`bson` module.\n\n          >>> import bson\n          >>> cursor = db.test.aggregate_raw_batches([\n          ...     {'$project': {'x': {'$multiply': [2, '$x']}}}])\n          >>> for batch in cursor:\n          ...     print(bson.decode_all(batch))\n\n        .. note:: aggregate_raw_batches does not support sessions or auto\n           encryption.\n\n        .. versionadded:: 3.6\n        \"\"\"\n        # OP_MSG with document stream returns is required to support\n        # sessions.\n        if \"session\" in kwargs:\n            raise ConfigurationError(\n                \"aggregate_raw_batches does not support sessions\")\n\n        # OP_MSG is required to support encryption.\n        if self.__database.client._encrypter:\n            raise InvalidOperation(\n                \"aggregate_raw_batches does not support auto encryption\")\n\n        return self._aggregate(_CollectionRawAggregationCommand,\n                               pipeline,\n                               RawBatchCommandCursor,\n                               session=None,\n                               explicit_session=False,\n                               **kwargs)\n\n    def watch(self, pipeline=None, full_document=None, resume_after=None,\n              max_await_time_ms=None, batch_size=None, collation=None,\n              start_at_operation_time=None, session=None, start_after=None):\n        \"\"\"Watch changes on this collection.\n\n        Performs an aggregation with an implicit initial ``$changeStream``\n        stage and returns a\n        :class:`~pymongo.change_stream.CollectionChangeStream` cursor which\n        iterates over changes on this collection.\n\n        Introduced in MongoDB 3.6.\n\n        .. code-block:: python\n\n           with db.collection.watch() as stream:\n               for change in stream:\n                   print(change)\n\n        The :class:`~pymongo.change_stream.CollectionChangeStream` iterable\n        blocks until the next change document is returned or an error is\n        raised. If the\n        :meth:`~pymongo.change_stream.CollectionChangeStream.next` method\n        encounters a network error when retrieving a batch from the server,\n        it will automatically attempt to recreate the cursor such that no\n        change events are missed. Any error encountered during the resume\n        attempt indicates there may be an outage and will be raised.\n\n        .. code-block:: python\n\n            try:\n                with db.collection.watch(\n                        [{'$match': {'operationType': 'insert'}}]) as stream:\n                    for insert_change in stream:\n                        print(insert_change)\n            except pymongo.errors.PyMongoError:\n                # The ChangeStream encountered an unrecoverable error or the\n                # resume attempt failed to recreate the cursor.\n                logging.error('...')\n\n        For a precise description of the resume process see the\n        `change streams specification`_.\n\n        .. note:: Using this helper method is preferred to directly calling\n            :meth:`~pymongo.collection.Collection.aggregate` with a\n            ``$changeStream`` stage, for the purpose of supporting\n            resumability.\n\n        .. warning:: This Collection's :attr:`read_concern` must be\n            ``ReadConcern(\"majority\")`` in order to use the ``$changeStream``\n            stage.\n\n        :Parameters:\n          - `pipeline` (optional): A list of aggregation pipeline stages to\n            append to an initial ``$changeStream`` stage. Not all\n            pipeline stages are valid after a ``$changeStream`` stage, see the\n            MongoDB documentation on change streams for the supported stages.\n          - `full_document` (optional): The fullDocument to pass as an option\n            to the ``$changeStream`` stage. Allowed values: 'updateLookup'.\n            When set to 'updateLookup', the change notification for partial\n            updates will include both a delta describing the changes to the\n            document, as well as a copy of the entire document that was\n            changed from some time after the change occurred.\n          - `resume_after` (optional): A resume token. If provided, the\n            change stream will start returning changes that occur directly\n            after the operation specified in the resume token. A resume token\n            is the _id value of a change document.\n          - `max_await_time_ms` (optional): The maximum time in milliseconds\n            for the server to wait for changes before responding to a getMore\n            operation.\n          - `batch_size` (optional): The maximum number of documents to return\n            per batch.\n          - `collation` (optional): The :class:`~pymongo.collation.Collation`\n            to use for the aggregation.\n          - `start_at_operation_time` (optional): If provided, the resulting\n            change stream will only return changes that occurred at or after\n            the specified :class:`~bson.timestamp.Timestamp`. Requires\n            MongoDB >= 4.0.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `start_after` (optional): The same as `resume_after` except that\n            `start_after` can resume notifications after an invalidate event.\n            This option and `resume_after` are mutually exclusive.\n\n        :Returns:\n          A :class:`~pymongo.change_stream.CollectionChangeStream` cursor.\n\n        .. versionchanged:: 3.9\n           Added the ``start_after`` parameter.\n\n        .. versionchanged:: 3.7\n           Added the ``start_at_operation_time`` parameter.\n\n        .. versionadded:: 3.6\n\n        .. mongodoc:: changeStreams\n\n        .. _change streams specification:\n            https://github.com/mongodb/specifications/blob/master/source/change-streams/change-streams.rst\n        \"\"\"\n        return CollectionChangeStream(\n            self, pipeline, full_document, resume_after, max_await_time_ms,\n            batch_size, collation, start_at_operation_time, session,\n            start_after)\n\n    def group(self, key, condition, initial, reduce, finalize=None, **kwargs):\n        \"\"\"Perform a query similar to an SQL *group by* operation.\n\n        **DEPRECATED** - The group command was deprecated in MongoDB 3.4. The\n        :meth:`~group` method is deprecated and will be removed in PyMongo 4.0.\n        Use :meth:`~aggregate` with the `$group` stage or :meth:`~map_reduce`\n        instead.\n\n        .. versionchanged:: 3.5\n           Deprecated the group method.\n        .. versionchanged:: 3.4\n           Added the `collation` option.\n        .. versionchanged:: 2.2\n           Removed deprecated argument: command\n        \"\"\"\n        warnings.warn(\"The group method is deprecated and will be removed in \"\n                      \"PyMongo 4.0. Use the aggregate method with the $group \"\n                      \"stage or the map_reduce method instead.\",\n                      DeprecationWarning, stacklevel=2)\n        group = {}\n        if isinstance(key, string_type):\n            group[\"$keyf\"] = Code(key)\n        elif key is not None:\n            group = {\"key\": helpers._fields_list_to_dict(key, \"key\")}\n        group[\"ns\"] = self.__name\n        group[\"$reduce\"] = Code(reduce)\n        group[\"cond\"] = condition\n        group[\"initial\"] = initial\n        if finalize is not None:\n            group[\"finalize\"] = Code(finalize)\n\n        cmd = SON([(\"group\", group)])\n        collation = validate_collation_or_none(kwargs.pop('collation', None))\n        cmd.update(kwargs)\n\n        with self._socket_for_reads(session=None) as (sock_info, slave_ok):\n            return self._command(sock_info, cmd, slave_ok,\n                                 collation=collation,\n                                 user_fields={'retval': 1})[\"retval\"]\n\n    def rename(self, new_name, session=None, **kwargs):\n        \"\"\"Rename this collection.\n\n        If operating in auth mode, client must be authorized as an\n        admin to perform this operation. Raises :class:`TypeError` if\n        `new_name` is not an instance of :class:`basestring`\n        (:class:`str` in python 3). Raises :class:`~pymongo.errors.InvalidName`\n        if `new_name` is not a valid collection name.\n\n        :Parameters:\n          - `new_name`: new name for this collection\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): additional arguments to the rename command\n            may be passed as keyword arguments to this helper method\n            (i.e. ``dropTarget=True``)\n\n        .. note:: The :attr:`~pymongo.collection.Collection.write_concern` of\n           this collection is automatically applied to this operation when using\n           MongoDB >= 3.4.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.4\n           Apply this collection's write concern automatically to this operation\n           when connected to MongoDB >= 3.4.\n\n        \"\"\"\n        if not isinstance(new_name, string_type):\n            raise TypeError(\"new_name must be an \"\n                            \"instance of %s\" % (string_type.__name__,))\n\n        if not new_name or \"..\" in new_name:\n            raise InvalidName(\"collection names cannot be empty\")\n        if new_name[0] == \".\" or new_name[-1] == \".\":\n            raise InvalidName(\"collecion names must not start or end with '.'\")\n        if \"$\" in new_name and not new_name.startswith(\"oplog.$main\"):\n            raise InvalidName(\"collection names must not contain '$'\")\n\n        new_name = \"%s.%s\" % (self.__database.name, new_name)\n        cmd = SON([(\"renameCollection\", self.__full_name), (\"to\", new_name)])\n        cmd.update(kwargs)\n        write_concern = self._write_concern_for_cmd(cmd, session)\n\n        with self._socket_for_writes(session) as sock_info:\n            with self.__database.client._tmp_session(session) as s:\n                return sock_info.command(\n                    'admin', cmd,\n                    write_concern=write_concern,\n                    parse_write_concern_error=True,\n                    session=s, client=self.__database.client)\n\n    def distinct(self, key, filter=None, session=None, **kwargs):\n        \"\"\"Get a list of distinct values for `key` among all documents\n        in this collection.\n\n        Raises :class:`TypeError` if `key` is not an instance of\n        :class:`basestring` (:class:`str` in python 3).\n\n        All optional distinct parameters should be passed as keyword arguments\n        to this method. Valid options include:\n\n          - `maxTimeMS` (int): The maximum amount of time to allow the count\n            command to run, in milliseconds.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only supported\n            on MongoDB 3.4 and above.\n\n        The :meth:`distinct` method obeys the :attr:`read_preference` of\n        this :class:`Collection`.\n\n        :Parameters:\n          - `key`: name of the field for which we want to get the distinct\n            values\n          - `filter` (optional): A query document that specifies the documents\n            from which to retrieve the distinct values.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): See list of options above.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.4\n           Support the `collation` option.\n\n        \"\"\"\n        if not isinstance(key, string_type):\n            raise TypeError(\"key must be an \"\n                            \"instance of %s\" % (string_type.__name__,))\n        cmd = SON([(\"distinct\", self.__name),\n                   (\"key\", key)])\n        if filter is not None:\n            if \"query\" in kwargs:\n                raise ConfigurationError(\"can't pass both filter and query\")\n            kwargs[\"query\"] = filter\n        collation = validate_collation_or_none(kwargs.pop('collation', None))\n        cmd.update(kwargs)\n        def _cmd(session, server, sock_info, slave_ok):\n            return self._command(\n                sock_info, cmd, slave_ok, read_concern=self.read_concern,\n                collation=collation, session=session,\n                user_fields={\"values\": 1})[\"values\"]\n\n        return self.__database.client._retryable_read(\n            _cmd, self._read_preference_for(session), session)\n\n    def _map_reduce(self, map, reduce, out, session, read_pref, **kwargs):\n        \"\"\"Internal mapReduce helper.\"\"\"\n        cmd = SON([(\"mapReduce\", self.__name),\n                   (\"map\", map),\n                   (\"reduce\", reduce),\n                   (\"out\", out)])\n        collation = validate_collation_or_none(kwargs.pop('collation', None))\n        cmd.update(kwargs)\n\n        inline = 'inline' in out\n\n        if inline:\n            user_fields = {'results': 1}\n        else:\n            user_fields = None\n\n        read_pref = ((session and session._txn_read_preference())\n                     or read_pref)\n\n        with self.__database.client._socket_for_reads(read_pref, session) as (\n                sock_info, slave_ok):\n            if (sock_info.max_wire_version >= 4 and\n                    ('readConcern' not in cmd) and\n                    inline):\n                read_concern = self.read_concern\n            else:\n                read_concern = None\n            if 'writeConcern' not in cmd and not inline:\n                write_concern = self._write_concern_for(session)\n            else:\n                write_concern = None\n\n            return self._command(\n                sock_info, cmd, slave_ok, read_pref,\n                read_concern=read_concern,\n                write_concern=write_concern,\n                collation=collation, session=session,\n                user_fields=user_fields)\n\n    def map_reduce(self, map, reduce, out, full_response=False, session=None,\n                   **kwargs):\n        \"\"\"Perform a map/reduce operation on this collection.\n\n        If `full_response` is ``False`` (default) returns a\n        :class:`~pymongo.collection.Collection` instance containing\n        the results of the operation. Otherwise, returns the full\n        response from the server to the `map reduce command`_.\n\n        :Parameters:\n          - `map`: map function (as a JavaScript string)\n          - `reduce`: reduce function (as a JavaScript string)\n          - `out`: output collection name or `out object` (dict). See\n            the `map reduce command`_ documentation for available options.\n            Note: `out` options are order sensitive. :class:`~bson.son.SON`\n            can be used to specify multiple options.\n            e.g. SON([('replace', <collection name>), ('db', <database name>)])\n          - `full_response` (optional): if ``True``, return full response to\n            this command - otherwise just return the result collection\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): additional arguments to the\n            `map reduce command`_ may be passed as keyword arguments to this\n            helper method, e.g.::\n\n            >>> db.test.map_reduce(map, reduce, \"myresults\", limit=2)\n\n        .. note:: The :meth:`map_reduce` method does **not** obey the\n           :attr:`read_preference` of this :class:`Collection`. To run\n           mapReduce on a secondary use the :meth:`inline_map_reduce` method\n           instead.\n\n        .. note:: The :attr:`~pymongo.collection.Collection.write_concern` of\n           this collection is automatically applied to this operation (if the\n           output is not inline) when using MongoDB >= 3.4.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.4\n           Apply this collection's write concern automatically to this operation\n           when connected to MongoDB >= 3.4.\n\n        .. seealso:: :doc:`/examples/aggregation`\n\n        .. versionchanged:: 3.4\n           Added the `collation` option.\n        .. versionchanged:: 2.2\n           Removed deprecated arguments: merge_output and reduce_output\n\n        .. _map reduce command: http://docs.mongodb.org/manual/reference/command/mapReduce/\n\n        .. mongodoc:: mapreduce\n\n        \"\"\"\n        if not isinstance(out, (string_type, abc.Mapping)):\n            raise TypeError(\"'out' must be an instance of \"\n                            \"%s or a mapping\" % (string_type.__name__,))\n\n        response = self._map_reduce(map, reduce, out, session,\n                                    ReadPreference.PRIMARY, **kwargs)\n\n        if full_response or not response.get('result'):\n            return response\n        elif isinstance(response['result'], dict):\n            dbase = response['result']['db']\n            coll = response['result']['collection']\n            return self.__database.client[dbase][coll]\n        else:\n            return self.__database[response[\"result\"]]\n\n    def inline_map_reduce(self, map, reduce, full_response=False, session=None,\n                          **kwargs):\n        \"\"\"Perform an inline map/reduce operation on this collection.\n\n        Perform the map/reduce operation on the server in RAM. A result\n        collection is not created. The result set is returned as a list\n        of documents.\n\n        If `full_response` is ``False`` (default) returns the\n        result documents in a list. Otherwise, returns the full\n        response from the server to the `map reduce command`_.\n\n        The :meth:`inline_map_reduce` method obeys the :attr:`read_preference`\n        of this :class:`Collection`.\n\n        :Parameters:\n          - `map`: map function (as a JavaScript string)\n          - `reduce`: reduce function (as a JavaScript string)\n          - `full_response` (optional): if ``True``, return full response to\n            this command - otherwise just return the result collection\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): additional arguments to the\n            `map reduce command`_ may be passed as keyword arguments to this\n            helper method, e.g.::\n\n            >>> db.test.inline_map_reduce(map, reduce, limit=2)\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.4\n           Added the `collation` option.\n\n        \"\"\"\n        res = self._map_reduce(map, reduce, {\"inline\": 1}, session,\n                               self.read_preference, **kwargs)\n\n        if full_response:\n            return res\n        else:\n            return res.get(\"results\")\n\n    def _write_concern_for_cmd(self, cmd, session):\n        raw_wc = cmd.get('writeConcern')\n        if raw_wc is not None:\n            return WriteConcern(**raw_wc)\n        else:\n            return self._write_concern_for(session)\n\n    def __find_and_modify(self, filter, projection, sort, upsert=None,\n                          return_document=ReturnDocument.BEFORE,\n                          array_filters=None, session=None, **kwargs):\n        \"\"\"Internal findAndModify helper.\"\"\"\n\n        common.validate_is_mapping(\"filter\", filter)\n        if not isinstance(return_document, bool):\n            raise ValueError(\"return_document must be \"\n                             \"ReturnDocument.BEFORE or ReturnDocument.AFTER\")\n        collation = validate_collation_or_none(kwargs.pop('collation', None))\n        cmd = SON([(\"findAndModify\", self.__name),\n                   (\"query\", filter),\n                   (\"new\", return_document)])\n        cmd.update(kwargs)\n        if projection is not None:\n            cmd[\"fields\"] = helpers._fields_list_to_dict(projection,\n                                                         \"projection\")\n        if sort is not None:\n            cmd[\"sort\"] = helpers._index_document(sort)\n        if upsert is not None:\n            common.validate_boolean(\"upsert\", upsert)\n            cmd[\"upsert\"] = upsert\n\n        write_concern = self._write_concern_for_cmd(cmd, session)\n\n        def _find_and_modify(session, sock_info, retryable_write):\n            if array_filters is not None:\n                if sock_info.max_wire_version < 6:\n                    raise ConfigurationError(\n                        'Must be connected to MongoDB 3.6+ to use '\n                        'arrayFilters.')\n                if not write_concern.acknowledged:\n                    raise ConfigurationError(\n                        'arrayFilters is unsupported for unacknowledged '\n                        'writes.')\n                cmd[\"arrayFilters\"] = array_filters\n            if (sock_info.max_wire_version >= 4 and\n                    not write_concern.is_server_default):\n                cmd['writeConcern'] = write_concern.document\n            out = self._command(sock_info, cmd,\n                                read_preference=ReadPreference.PRIMARY,\n                                write_concern=write_concern,\n                                allowable_errors=[_NO_OBJ_ERROR],\n                                collation=collation, session=session,\n                                retryable_write=retryable_write,\n                                user_fields=_FIND_AND_MODIFY_DOC_FIELDS)\n            _check_write_command_response(out)\n\n            return out.get(\"value\")\n\n        return self.__database.client._retryable_write(\n            write_concern.acknowledged, _find_and_modify, session)\n\n    def find_one_and_delete(self, filter,\n                            projection=None, sort=None, session=None, **kwargs):\n        \"\"\"Finds a single document and deletes it, returning the document.\n\n          >>> db.test.count_documents({'x': 1})\n          2\n          >>> db.test.find_one_and_delete({'x': 1})\n          {u'x': 1, u'_id': ObjectId('54f4e12bfba5220aa4d6dee8')}\n          >>> db.test.count_documents({'x': 1})\n          1\n\n        If multiple documents match *filter*, a *sort* can be applied.\n\n          >>> for doc in db.test.find({'x': 1}):\n          ...     print(doc)\n          ...\n          {u'x': 1, u'_id': 0}\n          {u'x': 1, u'_id': 1}\n          {u'x': 1, u'_id': 2}\n          >>> db.test.find_one_and_delete(\n          ...     {'x': 1}, sort=[('_id', pymongo.DESCENDING)])\n          {u'x': 1, u'_id': 2}\n\n        The *projection* option can be used to limit the fields returned.\n\n          >>> db.test.find_one_and_delete({'x': 1}, projection={'_id': False})\n          {u'x': 1}\n\n        :Parameters:\n          - `filter`: A query that matches the document to delete.\n          - `projection` (optional): a list of field names that should be\n            returned in the result document or a mapping specifying the fields\n            to include or exclude. If `projection` is a list \"_id\" will\n            always be returned. Use a mapping to exclude fields from\n            the result (e.g. projection={'_id': False}).\n          - `sort` (optional): a list of (key, direction) pairs\n            specifying the sort order for the query. If multiple documents\n            match the query, they are sorted and the first is deleted.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): additional command arguments can be passed\n            as keyword arguments (for example maxTimeMS can be used with\n            recent server versions).\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.2\n           Respects write concern.\n\n        .. warning:: Starting in PyMongo 3.2, this command uses the\n           :class:`~pymongo.write_concern.WriteConcern` of this\n           :class:`~pymongo.collection.Collection` when connected to MongoDB >=\n           3.2. Note that using an elevated write concern with this command may\n           be slower compared to using the default write concern.\n\n        .. versionchanged:: 3.4\n           Added the `collation` option.\n        .. versionadded:: 3.0\n\n        \"\"\"\n        kwargs['remove'] = True\n        return self.__find_and_modify(filter, projection, sort,\n                                      session=session, **kwargs)\n\n    def find_one_and_replace(self, filter, replacement,\n                             projection=None, sort=None, upsert=False,\n                             return_document=ReturnDocument.BEFORE,\n                             session=None, **kwargs):\n        \"\"\"Finds a single document and replaces it, returning either the\n        original or the replaced document.\n\n        The :meth:`find_one_and_replace` method differs from\n        :meth:`find_one_and_update` by replacing the document matched by\n        *filter*, rather than modifying the existing document.\n\n          >>> for doc in db.test.find({}):\n          ...     print(doc)\n          ...\n          {u'x': 1, u'_id': 0}\n          {u'x': 1, u'_id': 1}\n          {u'x': 1, u'_id': 2}\n          >>> db.test.find_one_and_replace({'x': 1}, {'y': 1})\n          {u'x': 1, u'_id': 0}\n          >>> for doc in db.test.find({}):\n          ...     print(doc)\n          ...\n          {u'y': 1, u'_id': 0}\n          {u'x': 1, u'_id': 1}\n          {u'x': 1, u'_id': 2}\n\n        :Parameters:\n          - `filter`: A query that matches the document to replace.\n          - `replacement`: The replacement document.\n          - `projection` (optional): A list of field names that should be\n            returned in the result document or a mapping specifying the fields\n            to include or exclude. If `projection` is a list \"_id\" will\n            always be returned. Use a mapping to exclude fields from\n            the result (e.g. projection={'_id': False}).\n          - `sort` (optional): a list of (key, direction) pairs\n            specifying the sort order for the query. If multiple documents\n            match the query, they are sorted and the first is replaced.\n          - `upsert` (optional): When ``True``, inserts a new document if no\n            document matches the query. Defaults to ``False``.\n          - `return_document`: If\n            :attr:`ReturnDocument.BEFORE` (the default),\n            returns the original document before it was replaced, or ``None``\n            if no document matches. If\n            :attr:`ReturnDocument.AFTER`, returns the replaced\n            or inserted document.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): additional command arguments can be passed\n            as keyword arguments (for example maxTimeMS can be used with\n            recent server versions).\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        .. versionchanged:: 3.4\n           Added the `collation` option.\n        .. versionchanged:: 3.2\n           Respects write concern.\n\n        .. warning:: Starting in PyMongo 3.2, this command uses the\n           :class:`~pymongo.write_concern.WriteConcern` of this\n           :class:`~pymongo.collection.Collection` when connected to MongoDB >=\n           3.2. Note that using an elevated write concern with this command may\n           be slower compared to using the default write concern.\n\n        .. versionadded:: 3.0\n        \"\"\"\n        common.validate_ok_for_replace(replacement)\n        kwargs['update'] = replacement\n        return self.__find_and_modify(filter, projection,\n                                      sort, upsert, return_document,\n                                      session=session, **kwargs)\n\n    def find_one_and_update(self, filter, update,\n                            projection=None, sort=None, upsert=False,\n                            return_document=ReturnDocument.BEFORE,\n                            array_filters=None, session=None, **kwargs):\n        \"\"\"Finds a single document and updates it, returning either the\n        original or the updated document.\n\n          >>> db.test.find_one_and_update(\n          ...    {'_id': 665}, {'$inc': {'count': 1}, '$set': {'done': True}})\n          {u'_id': 665, u'done': False, u'count': 25}}\n\n        Returns ``None`` if no document matches the filter.\n\n          >>> db.test.find_one_and_update(\n          ...    {'_exists': False}, {'$inc': {'count': 1}})\n\n        When the filter matches, by default :meth:`find_one_and_update`\n        returns the original version of the document before the update was\n        applied. To return the updated (or inserted in the case of\n        *upsert*) version of the document instead, use the *return_document*\n        option.\n\n          >>> from pymongo import ReturnDocument\n          >>> db.example.find_one_and_update(\n          ...     {'_id': 'userid'},\n          ...     {'$inc': {'seq': 1}},\n          ...     return_document=ReturnDocument.AFTER)\n          {u'_id': u'userid', u'seq': 1}\n\n        You can limit the fields returned with the *projection* option.\n\n          >>> db.example.find_one_and_update(\n          ...     {'_id': 'userid'},\n          ...     {'$inc': {'seq': 1}},\n          ...     projection={'seq': True, '_id': False},\n          ...     return_document=ReturnDocument.AFTER)\n          {u'seq': 2}\n\n        The *upsert* option can be used to create the document if it doesn't\n        already exist.\n\n          >>> db.example.delete_many({}).deleted_count\n          1\n          >>> db.example.find_one_and_update(\n          ...     {'_id': 'userid'},\n          ...     {'$inc': {'seq': 1}},\n          ...     projection={'seq': True, '_id': False},\n          ...     upsert=True,\n          ...     return_document=ReturnDocument.AFTER)\n          {u'seq': 1}\n\n        If multiple documents match *filter*, a *sort* can be applied.\n\n          >>> for doc in db.test.find({'done': True}):\n          ...     print(doc)\n          ...\n          {u'_id': 665, u'done': True, u'result': {u'count': 26}}\n          {u'_id': 701, u'done': True, u'result': {u'count': 17}}\n          >>> db.test.find_one_and_update(\n          ...     {'done': True},\n          ...     {'$set': {'final': True}},\n          ...     sort=[('_id', pymongo.DESCENDING)])\n          {u'_id': 701, u'done': True, u'result': {u'count': 17}}\n\n        :Parameters:\n          - `filter`: A query that matches the document to update.\n          - `update`: The update operations to apply.\n          - `projection` (optional): A list of field names that should be\n            returned in the result document or a mapping specifying the fields\n            to include or exclude. If `projection` is a list \"_id\" will\n            always be returned. Use a dict to exclude fields from\n            the result (e.g. projection={'_id': False}).\n          - `sort` (optional): a list of (key, direction) pairs\n            specifying the sort order for the query. If multiple documents\n            match the query, they are sorted and the first is updated.\n          - `upsert` (optional): When ``True``, inserts a new document if no\n            document matches the query. Defaults to ``False``.\n          - `return_document`: If\n            :attr:`ReturnDocument.BEFORE` (the default),\n            returns the original document before it was updated. If\n            :attr:`ReturnDocument.AFTER`, returns the updated\n            or inserted document.\n          - `array_filters` (optional): A list of filters specifying which\n            array elements an update should apply. Requires MongoDB 3.6+.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): additional command arguments can be passed\n            as keyword arguments (for example maxTimeMS can be used with\n            recent server versions).\n\n        .. versionchanged:: 3.9\n           Added the ability to accept a pipeline as the `update`.\n        .. versionchanged:: 3.6\n           Added the `array_filters` and `session` options.\n        .. versionchanged:: 3.4\n           Added the `collation` option.\n        .. versionchanged:: 3.2\n           Respects write concern.\n\n        .. warning:: Starting in PyMongo 3.2, this command uses the\n           :class:`~pymongo.write_concern.WriteConcern` of this\n           :class:`~pymongo.collection.Collection` when connected to MongoDB >=\n           3.2. Note that using an elevated write concern with this command may\n           be slower compared to using the default write concern.\n\n        .. versionadded:: 3.0\n        \"\"\"\n        common.validate_ok_for_update(update)\n        common.validate_list_or_none('array_filters', array_filters)\n        kwargs['update'] = update\n        return self.__find_and_modify(filter, projection,\n                                      sort, upsert, return_document,\n                                      array_filters, session=session, **kwargs)\n\n    def save(self, to_save, manipulate=True, check_keys=True, **kwargs):\n        \"\"\"Save a document in this collection.\n\n        **DEPRECATED** - Use :meth:`insert_one` or :meth:`replace_one` instead.\n\n        .. versionchanged:: 3.0\n           Removed the `safe` parameter. Pass ``w=0`` for unacknowledged write\n           operations.\n        \"\"\"\n        warnings.warn(\"save is deprecated. Use insert_one or replace_one \"\n                      \"instead\", DeprecationWarning, stacklevel=2)\n        common.validate_is_document_type(\"to_save\", to_save)\n\n        write_concern = None\n        collation = validate_collation_or_none(kwargs.pop('collation', None))\n        if kwargs:\n            write_concern = WriteConcern(**kwargs)\n\n        if not (isinstance(to_save, RawBSONDocument) or \"_id\" in to_save):\n            return self._insert(\n                to_save, True, check_keys, manipulate, write_concern)\n        else:\n            self._update_retryable(\n                {\"_id\": to_save[\"_id\"]}, to_save, True,\n                check_keys, False, manipulate, write_concern,\n                collation=collation)\n            return to_save.get(\"_id\")\n\n    def insert(self, doc_or_docs, manipulate=True,\n               check_keys=True, continue_on_error=False, **kwargs):\n        \"\"\"Insert a document(s) into this collection.\n\n        **DEPRECATED** - Use :meth:`insert_one` or :meth:`insert_many` instead.\n\n        .. versionchanged:: 3.0\n           Removed the `safe` parameter. Pass ``w=0`` for unacknowledged write\n           operations.\n        \"\"\"\n        warnings.warn(\"insert is deprecated. Use insert_one or insert_many \"\n                      \"instead.\", DeprecationWarning, stacklevel=2)\n        write_concern = None\n        if kwargs:\n            write_concern = WriteConcern(**kwargs)\n        return self._insert(doc_or_docs, not continue_on_error,\n                            check_keys, manipulate, write_concern)\n\n    def update(self, spec, document, upsert=False, manipulate=False,\n               multi=False, check_keys=True, **kwargs):\n        \"\"\"Update a document(s) in this collection.\n\n        **DEPRECATED** - Use :meth:`replace_one`, :meth:`update_one`, or\n        :meth:`update_many` instead.\n\n        .. versionchanged:: 3.0\n           Removed the `safe` parameter. Pass ``w=0`` for unacknowledged write\n           operations.\n        \"\"\"\n        warnings.warn(\"update is deprecated. Use replace_one, update_one or \"\n                      \"update_many instead.\", DeprecationWarning, stacklevel=2)\n        common.validate_is_mapping(\"spec\", spec)\n        common.validate_is_mapping(\"document\", document)\n        if document:\n            # If a top level key begins with '$' this is a modify operation\n            # and we should skip key validation. It doesn't matter which key\n            # we check here. Passing a document with a mix of top level keys\n            # starting with and without a '$' is invalid and the server will\n            # raise an appropriate exception.\n            first = next(iter(document))\n            if first.startswith('$'):\n                check_keys = False\n\n        write_concern = None\n        collation = validate_collation_or_none(kwargs.pop('collation', None))\n        if kwargs:\n            write_concern = WriteConcern(**kwargs)\n        return self._update_retryable(\n            spec, document, upsert, check_keys, multi, manipulate,\n            write_concern, collation=collation)\n\n    def remove(self, spec_or_id=None, multi=True, **kwargs):\n        \"\"\"Remove a document(s) from this collection.\n\n        **DEPRECATED** - Use :meth:`delete_one` or :meth:`delete_many` instead.\n\n        .. versionchanged:: 3.0\n           Removed the `safe` parameter. Pass ``w=0`` for unacknowledged write\n           operations.\n        \"\"\"\n        warnings.warn(\"remove is deprecated. Use delete_one or delete_many \"\n                      \"instead.\", DeprecationWarning, stacklevel=2)\n        if spec_or_id is None:\n            spec_or_id = {}\n        if not isinstance(spec_or_id, abc.Mapping):\n            spec_or_id = {\"_id\": spec_or_id}\n        write_concern = None\n        collation = validate_collation_or_none(kwargs.pop('collation', None))\n        if kwargs:\n            write_concern = WriteConcern(**kwargs)\n        return self._delete_retryable(\n            spec_or_id, multi, write_concern, collation=collation)\n\n    def find_and_modify(self, query={}, update=None,\n                        upsert=False, sort=None, full_response=False,\n                        manipulate=False, **kwargs):\n        \"\"\"Update and return an object.\n\n        **DEPRECATED** - Use :meth:`find_one_and_delete`,\n        :meth:`find_one_and_replace`, or :meth:`find_one_and_update` instead.\n        \"\"\"\n        warnings.warn(\"find_and_modify is deprecated, use find_one_and_delete\"\n                      \", find_one_and_replace, or find_one_and_update instead\",\n                      DeprecationWarning, stacklevel=2)\n\n        if not update and not kwargs.get('remove', None):\n            raise ValueError(\"Must either update or remove\")\n\n        if update and kwargs.get('remove', None):\n            raise ValueError(\"Can't do both update and remove\")\n\n        # No need to include empty args\n        if query:\n            kwargs['query'] = query\n        if update:\n            kwargs['update'] = update\n        if upsert:\n            kwargs['upsert'] = upsert\n        if sort:\n            # Accept a list of tuples to match Cursor's sort parameter.\n            if isinstance(sort, list):\n                kwargs['sort'] = helpers._index_document(sort)\n            # Accept OrderedDict, SON, and dict with len == 1 so we\n            # don't break existing code already using find_and_modify.\n            elif (isinstance(sort, ORDERED_TYPES) or\n                  isinstance(sort, dict) and len(sort) == 1):\n                warnings.warn(\"Passing mapping types for `sort` is deprecated,\"\n                              \" use a list of (key, direction) pairs instead\",\n                              DeprecationWarning, stacklevel=2)\n                kwargs['sort'] = sort\n            else:\n                raise TypeError(\"sort must be a list of (key, direction) \"\n                                \"pairs, a dict of len 1, or an instance of \"\n                                \"SON or OrderedDict\")\n\n        fields = kwargs.pop(\"fields\", None)\n        if fields is not None:\n            kwargs[\"fields\"] = helpers._fields_list_to_dict(fields, \"fields\")\n\n        collation = validate_collation_or_none(kwargs.pop('collation', None))\n\n        cmd = SON([(\"findAndModify\", self.__name)])\n        cmd.update(kwargs)\n\n        write_concern = self._write_concern_for_cmd(cmd, None)\n\n        def _find_and_modify(session, sock_info, retryable_write):\n            if (sock_info.max_wire_version >= 4 and\n                    not write_concern.is_server_default):\n                cmd['writeConcern'] = write_concern.document\n            result = self._command(\n                sock_info, cmd, read_preference=ReadPreference.PRIMARY,\n                allowable_errors=[_NO_OBJ_ERROR], collation=collation,\n                session=session, retryable_write=retryable_write,\n                user_fields=_FIND_AND_MODIFY_DOC_FIELDS)\n\n            _check_write_command_response(result)\n            return result\n\n        out = self.__database.client._retryable_write(\n            write_concern.acknowledged, _find_and_modify, None)\n\n        if not out['ok']:\n            if out[\"errmsg\"] == _NO_OBJ_ERROR:\n                return None\n            else:\n                # Should never get here b/c of allowable_errors\n                raise ValueError(\"Unexpected Error: %s\" % (out,))\n\n        if full_response:\n            return out\n        else:\n            document = out.get('value')\n            if manipulate:\n                document = self.__database._fix_outgoing(document, self)\n            return document\n\n    def __iter__(self):\n        return self\n\n    def __next__(self):\n        raise TypeError(\"'Collection' object is not iterable\")\n\n    next = __next__\n\n    def __call__(self, *args, **kwargs):\n        \"\"\"This is only here so that some API misusages are easier to debug.\n        \"\"\"\n        if \".\" not in self.__name:\n            raise TypeError(\"'Collection' object is not callable. If you \"\n                            \"meant to call the '%s' method on a 'Database' \"\n                            \"object it is failing because no such method \"\n                            \"exists.\" %\n                            self.__name)\n        raise TypeError(\"'Collection' object is not callable. If you meant to \"\n                        \"call the '%s' method on a 'Collection' object it is \"\n                        \"failing because no such method exists.\" %\n                        self.__name.split(\".\")[-1])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/command_cursor.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"CommandCursor class to iterate over command results.\"\"\"\n\nfrom collections import deque\n\nfrom bson.py3compat import integer_types\nfrom pymongo.errors import (ConnectionFailure,\n                            InvalidOperation,\n                            NotMasterError,\n                            OperationFailure)\nfrom pymongo.message import (_CursorAddress,\n                             _GetMore,\n                             _RawBatchGetMore)\n\n\nclass CommandCursor(object):\n    \"\"\"A cursor / iterator over command cursors.\"\"\"\n    _getmore_class = _GetMore\n\n    def __init__(self, collection, cursor_info, address, retrieved=0,\n                 batch_size=0, max_await_time_ms=None, session=None,\n                 explicit_session=False):\n        \"\"\"Create a new command cursor.\n\n        The parameter 'retrieved' is unused.\n        \"\"\"\n        self.__collection = collection\n        self.__id = cursor_info['id']\n        self.__data = deque(cursor_info['firstBatch'])\n        self.__postbatchresumetoken = cursor_info.get('postBatchResumeToken')\n        self.__address = address\n        self.__batch_size = batch_size\n        self.__max_await_time_ms = max_await_time_ms\n        self.__session = session\n        self.__explicit_session = explicit_session\n        self.__killed = (self.__id == 0)\n        if self.__killed:\n            self.__end_session(True)\n\n        if \"ns\" in cursor_info:\n            self.__ns = cursor_info[\"ns\"]\n        else:\n            self.__ns = collection.full_name\n\n        self.batch_size(batch_size)\n\n        if (not isinstance(max_await_time_ms, integer_types)\n                and max_await_time_ms is not None):\n            raise TypeError(\"max_await_time_ms must be an integer or None\")\n\n    def __del__(self):\n        if self.__id and not self.__killed:\n            self.__die()\n\n    def __die(self, synchronous=False):\n        \"\"\"Closes this cursor.\n        \"\"\"\n        already_killed = self.__killed\n        self.__killed = True\n        if self.__id and not already_killed:\n            address = _CursorAddress(\n                self.__address, self.__collection.full_name)\n            if synchronous:\n                self.__collection.database.client._close_cursor_now(\n                    self.__id, address, session=self.__session)\n            else:\n                # The cursor will be closed later in a different session.\n                self.__collection.database.client._close_cursor(\n                    self.__id, address)\n        self.__end_session(synchronous)\n\n    def __end_session(self, synchronous):\n        if self.__session and not self.__explicit_session:\n            self.__session._end_session(lock=synchronous)\n            self.__session = None\n\n    def close(self):\n        \"\"\"Explicitly close / kill this cursor.\n        \"\"\"\n        self.__die(True)\n\n    def batch_size(self, batch_size):\n        \"\"\"Limits the number of documents returned in one batch. Each batch\n        requires a round trip to the server. It can be adjusted to optimize\n        performance and limit data transfer.\n\n        .. note:: batch_size can not override MongoDB's internal limits on the\n           amount of data it will return to the client in a single batch (i.e\n           if you set batch size to 1,000,000,000, MongoDB will currently only\n           return 4-16MB of results per batch).\n\n        Raises :exc:`TypeError` if `batch_size` is not an integer.\n        Raises :exc:`ValueError` if `batch_size` is less than ``0``.\n\n        :Parameters:\n          - `batch_size`: The size of each batch of results requested.\n        \"\"\"\n        if not isinstance(batch_size, integer_types):\n            raise TypeError(\"batch_size must be an integer\")\n        if batch_size < 0:\n            raise ValueError(\"batch_size must be >= 0\")\n\n        self.__batch_size = batch_size == 1 and 2 or batch_size\n        return self\n\n    def _has_next(self):\n        \"\"\"Returns `True` if the cursor has documents remaining from the\n        previous batch.\"\"\"\n        return len(self.__data) > 0\n\n    @property\n    def _post_batch_resume_token(self):\n        \"\"\"Retrieve the postBatchResumeToken from the response to a\n        changeStream aggregate or getMore.\"\"\"\n        return self.__postbatchresumetoken\n\n    def __send_message(self, operation):\n        \"\"\"Send a getmore message and handle the response.\n        \"\"\"\n        def kill():\n            self.__killed = True\n            self.__end_session(True)\n\n        client = self.__collection.database.client\n        try:\n            response = client._run_operation_with_response(\n                operation, self._unpack_response, address=self.__address)\n        except OperationFailure:\n            kill()\n            raise\n        except NotMasterError:\n            # Don't send kill cursors to another server after a \"not master\"\n            # error. It's completely pointless.\n            kill()\n            raise\n        except ConnectionFailure:\n            # Don't try to send kill cursors on another socket\n            # or to another server. It can cause a _pinValue\n            # assertion on some server releases if we get here\n            # due to a socket timeout.\n            kill()\n            raise\n        except Exception:\n            # Close the cursor\n            self.__die()\n            raise\n\n        from_command = response.from_command\n        reply = response.data\n        docs = response.docs\n\n        if from_command:\n            cursor = docs[0]['cursor']\n            documents = cursor['nextBatch']\n            self.__postbatchresumetoken = cursor.get('postBatchResumeToken')\n            self.__id = cursor['id']\n        else:\n            documents = docs\n            self.__id = reply.cursor_id\n\n        if self.__id == 0:\n            kill()\n        self.__data = deque(documents)\n\n    def _unpack_response(self, response, cursor_id, codec_options,\n                         user_fields=None, legacy_response=False):\n        return response.unpack_response(cursor_id, codec_options, user_fields,\n                                        legacy_response)\n\n    def _refresh(self):\n        \"\"\"Refreshes the cursor with more data from the server.\n\n        Returns the length of self.__data after refresh. Will exit early if\n        self.__data is already non-empty. Raises OperationFailure when the\n        cursor cannot be refreshed due to an error on the query.\n        \"\"\"\n        if len(self.__data) or self.__killed:\n            return len(self.__data)\n\n        if self.__id:  # Get More\n            dbname, collname = self.__ns.split('.', 1)\n            read_pref = self.__collection._read_preference_for(self.session)\n            self.__send_message(\n                self._getmore_class(dbname,\n                                    collname,\n                                    self.__batch_size,\n                                    self.__id,\n                                    self.__collection.codec_options,\n                                    read_pref,\n                                    self.__session,\n                                    self.__collection.database.client,\n                                    self.__max_await_time_ms,\n                                    False))\n        else:  # Cursor id is zero nothing else to return\n            self.__killed = True\n            self.__end_session(True)\n\n        return len(self.__data)\n\n    @property\n    def alive(self):\n        \"\"\"Does this cursor have the potential to return more data?\n\n        Even if :attr:`alive` is ``True``, :meth:`next` can raise\n        :exc:`StopIteration`. Best to use a for loop::\n\n            for doc in collection.aggregate(pipeline):\n                print(doc)\n\n        .. note:: :attr:`alive` can be True while iterating a cursor from\n          a failed server. In this case :attr:`alive` will return False after\n          :meth:`next` fails to retrieve the next batch of results from the\n          server.\n        \"\"\"\n        return bool(len(self.__data) or (not self.__killed))\n\n    @property\n    def cursor_id(self):\n        \"\"\"Returns the id of the cursor.\"\"\"\n        return self.__id\n\n    @property\n    def address(self):\n        \"\"\"The (host, port) of the server used, or None.\n\n        .. versionadded:: 3.0\n        \"\"\"\n        return self.__address\n\n    @property\n    def session(self):\n        \"\"\"The cursor's :class:`~pymongo.client_session.ClientSession`, or None.\n\n        .. versionadded:: 3.6\n        \"\"\"\n        if self.__explicit_session:\n            return self.__session\n\n    def __iter__(self):\n        return self\n\n    def next(self):\n        \"\"\"Advance the cursor.\"\"\"\n        # Block until a document is returnable.\n        while self.alive:\n            doc = self._try_next(True)\n            if doc is not None:\n                return doc\n\n        raise StopIteration\n\n    __next__ = next\n\n    def _try_next(self, get_more_allowed):\n        \"\"\"Advance the cursor blocking for at most one getMore command.\"\"\"\n        if not len(self.__data) and not self.__killed and get_more_allowed:\n            self._refresh()\n        if len(self.__data):\n            coll = self.__collection\n            return coll.database._fix_outgoing(self.__data.popleft(), coll)\n        else:\n            return None\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        self.close()\n\n\nclass RawBatchCommandCursor(CommandCursor):\n    _getmore_class = _RawBatchGetMore\n\n    def __init__(self, collection, cursor_info, address, retrieved=0,\n                 batch_size=0, max_await_time_ms=None, session=None,\n                 explicit_session=False):\n        \"\"\"Create a new cursor / iterator over raw batches of BSON data.\n\n        Should not be called directly by application developers -\n        see :meth:`~pymongo.collection.Collection.aggregate_raw_batches`\n        instead.\n\n        .. mongodoc:: cursors\n        \"\"\"\n        assert not cursor_info.get('firstBatch')\n        super(RawBatchCommandCursor, self).__init__(\n            collection, cursor_info, address, retrieved, batch_size,\n            max_await_time_ms, session, explicit_session)\n\n    def _unpack_response(self, response, cursor_id, codec_options,\n                         user_fields=None, legacy_response=False):\n        return response.raw_response(cursor_id)\n\n    def __getitem__(self, index):\n        raise InvalidOperation(\"Cannot call __getitem__ on RawBatchCursor\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/common.py",
    "content": "# Copyright 2011-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\n\"\"\"Functions and classes common to multiple pymongo modules.\"\"\"\n\nimport datetime\nimport warnings\n\nfrom bson import SON\nfrom bson.binary import (STANDARD, PYTHON_LEGACY,\n                         JAVA_LEGACY, CSHARP_LEGACY)\nfrom bson.codec_options import CodecOptions, TypeRegistry\nfrom bson.py3compat import abc, integer_types, iteritems, string_type\nfrom bson.raw_bson import RawBSONDocument\nfrom pymongo.auth import MECHANISMS\nfrom pymongo.compression_support import (validate_compressors,\n                                         validate_zlib_compression_level)\nfrom pymongo.driver_info import DriverInfo\nfrom pymongo.encryption_options import validate_auto_encryption_opts_or_none\nfrom pymongo.errors import ConfigurationError\nfrom pymongo.monitoring import _validate_event_listeners\nfrom pymongo.read_concern import ReadConcern\nfrom pymongo.read_preferences import _MONGOS_MODES, _ServerMode\nfrom pymongo.ssl_support import (validate_cert_reqs,\n                                 validate_allow_invalid_certs)\nfrom pymongo.write_concern import DEFAULT_WRITE_CONCERN, WriteConcern\n\ntry:\n    from collections import OrderedDict\n    ORDERED_TYPES = (SON, OrderedDict)\nexcept ImportError:\n    ORDERED_TYPES = (SON,)\n\n\n# Defaults until we connect to a server and get updated limits.\nMAX_BSON_SIZE = 16 * (1024 ** 2)\nMAX_MESSAGE_SIZE = 2 * MAX_BSON_SIZE\nMIN_WIRE_VERSION = 0\nMAX_WIRE_VERSION = 0\nMAX_WRITE_BATCH_SIZE = 1000\n\n# What this version of PyMongo supports.\nMIN_SUPPORTED_SERVER_VERSION = \"2.6\"\nMIN_SUPPORTED_WIRE_VERSION = 2\nMAX_SUPPORTED_WIRE_VERSION = 8\n\n# Frequency to call ismaster on servers, in seconds.\nHEARTBEAT_FREQUENCY = 10\n\n# Frequency to process kill-cursors, in seconds. See MongoClient.close_cursor.\nKILL_CURSOR_FREQUENCY = 1\n\n# Frequency to process events queue, in seconds.\nEVENTS_QUEUE_FREQUENCY = 1\n\n# How long to wait, in seconds, for a suitable server to be found before\n# aborting an operation. For example, if the client attempts an insert\n# during a replica set election, SERVER_SELECTION_TIMEOUT governs the\n# longest it is willing to wait for a new primary to be found.\nSERVER_SELECTION_TIMEOUT = 30\n\n# Spec requires at least 500ms between ismaster calls.\nMIN_HEARTBEAT_INTERVAL = 0.5\n\n# Spec requires at least 60s between SRV rescans.\nMIN_SRV_RESCAN_INTERVAL = 60\n\n# Default connectTimeout in seconds.\nCONNECT_TIMEOUT = 20.0\n\n# Default value for maxPoolSize.\nMAX_POOL_SIZE = 100\n\n# Default value for minPoolSize.\nMIN_POOL_SIZE = 0\n\n# Default value for maxIdleTimeMS.\nMAX_IDLE_TIME_MS = None\n\n# Default value for maxIdleTimeMS in seconds.\nMAX_IDLE_TIME_SEC = None\n\n# Default value for waitQueueTimeoutMS in seconds.\nWAIT_QUEUE_TIMEOUT = None\n\n# Default value for localThresholdMS.\nLOCAL_THRESHOLD_MS = 15\n\n# Default value for retryWrites.\nRETRY_WRITES = True\n\n# Default value for retryReads.\nRETRY_READS = True\n\n# mongod/s 2.6 and above return code 59 when a command doesn't exist.\nCOMMAND_NOT_FOUND_CODES = (59,)\n\n# Error codes to ignore if GridFS calls createIndex on a secondary\nUNAUTHORIZED_CODES = (13, 16547, 16548)\n\n# Maximum number of sessions to send in a single endSessions command.\n# From the driver sessions spec.\n_MAX_END_SESSIONS = 10000\n\n\ndef partition_node(node):\n    \"\"\"Split a host:port string into (host, int(port)) pair.\"\"\"\n    host = node\n    port = 27017\n    idx = node.rfind(':')\n    if idx != -1:\n        host, port = node[:idx], int(node[idx + 1:])\n    if host.startswith('['):\n        host = host[1:-1]\n    return host, port\n\n\ndef clean_node(node):\n    \"\"\"Split and normalize a node name from an ismaster response.\"\"\"\n    host, port = partition_node(node)\n\n    # Normalize hostname to lowercase, since DNS is case-insensitive:\n    # http://tools.ietf.org/html/rfc4343\n    # This prevents useless rediscovery if \"foo.com\" is in the seed list but\n    # \"FOO.com\" is in the ismaster response.\n    return host.lower(), port\n\n\ndef raise_config_error(key, dummy):\n    \"\"\"Raise ConfigurationError with the given key name.\"\"\"\n    raise ConfigurationError(\"Unknown option %s\" % (key,))\n\n\n# Mapping of URI uuid representation options to valid subtypes.\n_UUID_REPRESENTATIONS = {\n    'standard': STANDARD,\n    'pythonLegacy': PYTHON_LEGACY,\n    'javaLegacy': JAVA_LEGACY,\n    'csharpLegacy': CSHARP_LEGACY\n}\n\n\ndef validate_boolean(option, value):\n    \"\"\"Validates that 'value' is True or False.\"\"\"\n    if isinstance(value, bool):\n        return value\n    raise TypeError(\"%s must be True or False\" % (option,))\n\n\ndef validate_boolean_or_string(option, value):\n    \"\"\"Validates that value is True, False, 'true', or 'false'.\"\"\"\n    if isinstance(value, string_type):\n        if value not in ('true', 'false'):\n            raise ValueError(\"The value of %s must be \"\n                             \"'true' or 'false'\" % (option,))\n        return value == 'true'\n    return validate_boolean(option, value)\n\n\ndef validate_integer(option, value):\n    \"\"\"Validates that 'value' is an integer (or basestring representation).\n    \"\"\"\n    if isinstance(value, integer_types):\n        return value\n    elif isinstance(value, string_type):\n        try:\n            return int(value)\n        except ValueError:\n            raise ValueError(\"The value of %s must be \"\n                             \"an integer\" % (option,))\n    raise TypeError(\"Wrong type for %s, value must be an integer\" % (option,))\n\n\ndef validate_positive_integer(option, value):\n    \"\"\"Validate that 'value' is a positive integer, which does not include 0.\n    \"\"\"\n    val = validate_integer(option, value)\n    if val <= 0:\n        raise ValueError(\"The value of %s must be \"\n                         \"a positive integer\" % (option,))\n    return val\n\n\ndef validate_non_negative_integer(option, value):\n    \"\"\"Validate that 'value' is a positive integer or 0.\n    \"\"\"\n    val = validate_integer(option, value)\n    if val < 0:\n        raise ValueError(\"The value of %s must be \"\n                         \"a non negative integer\" % (option,))\n    return val\n\n\ndef validate_readable(option, value):\n    \"\"\"Validates that 'value' is file-like and readable.\n    \"\"\"\n    if value is None:\n        return value\n    # First make sure its a string py3.3 open(True, 'r') succeeds\n    # Used in ssl cert checking due to poor ssl module error reporting\n    value = validate_string(option, value)\n    open(value, 'r').close()\n    return value\n\n\ndef validate_positive_integer_or_none(option, value):\n    \"\"\"Validate that 'value' is a positive integer or None.\n    \"\"\"\n    if value is None:\n        return value\n    return validate_positive_integer(option, value)\n\n\ndef validate_non_negative_integer_or_none(option, value):\n    \"\"\"Validate that 'value' is a positive integer or 0 or None.\n    \"\"\"\n    if value is None:\n        return value\n    return validate_non_negative_integer(option, value)\n\n\ndef validate_string(option, value):\n    \"\"\"Validates that 'value' is an instance of `basestring` for Python 2\n    or `str` for Python 3.\n    \"\"\"\n    if isinstance(value, string_type):\n        return value\n    raise TypeError(\"Wrong type for %s, value must be \"\n                    \"an instance of %s\" % (option, string_type.__name__))\n\n\ndef validate_string_or_none(option, value):\n    \"\"\"Validates that 'value' is an instance of `basestring` or `None`.\n    \"\"\"\n    if value is None:\n        return value\n    return validate_string(option, value)\n\n\ndef validate_int_or_basestring(option, value):\n    \"\"\"Validates that 'value' is an integer or string.\n    \"\"\"\n    if isinstance(value, integer_types):\n        return value\n    elif isinstance(value, string_type):\n        try:\n            return int(value)\n        except ValueError:\n            return value\n    raise TypeError(\"Wrong type for %s, value must be an \"\n                    \"integer or a string\" % (option,))\n\n\ndef validate_non_negative_int_or_basestring(option, value):\n    \"\"\"Validates that 'value' is an integer or string.\n    \"\"\"\n    if isinstance(value, integer_types):\n        return value\n    elif isinstance(value, string_type):\n        try:\n            val = int(value)\n        except ValueError:\n            return value\n        return validate_non_negative_integer(option, val)\n    raise TypeError(\"Wrong type for %s, value must be an \"\n                    \"non negative integer or a string\" % (option,))\n\n\ndef validate_positive_float(option, value):\n    \"\"\"Validates that 'value' is a float, or can be converted to one, and is\n       positive.\n    \"\"\"\n    errmsg = \"%s must be an integer or float\" % (option,)\n    try:\n        value = float(value)\n    except ValueError:\n        raise ValueError(errmsg)\n    except TypeError:\n        raise TypeError(errmsg)\n\n    # float('inf') doesn't work in 2.4 or 2.5 on Windows, so just cap floats at\n    # one billion - this is a reasonable approximation for infinity\n    if not 0 < value < 1e9:\n        raise ValueError(\"%s must be greater than 0 and \"\n                         \"less than one billion\" % (option,))\n    return value\n\n\ndef validate_positive_float_or_zero(option, value):\n    \"\"\"Validates that 'value' is 0 or a positive float, or can be converted to\n    0 or a positive float.\n    \"\"\"\n    if value == 0 or value == \"0\":\n        return 0\n    return validate_positive_float(option, value)\n\n\ndef validate_timeout_or_none(option, value):\n    \"\"\"Validates a timeout specified in milliseconds returning\n    a value in floating point seconds.\n    \"\"\"\n    if value is None:\n        return value\n    return validate_positive_float(option, value) / 1000.0\n\n\ndef validate_timeout_or_zero(option, value):\n    \"\"\"Validates a timeout specified in milliseconds returning\n    a value in floating point seconds for the case where None is an error\n    and 0 is valid. Setting the timeout to nothing in the URI string is a\n    config error.\n    \"\"\"\n    if value is None:\n        raise ConfigurationError(\"%s cannot be None\" % (option, ))\n    if value == 0 or value == \"0\":\n        return 0\n    return validate_positive_float(option, value) / 1000.0\n\n\ndef validate_max_staleness(option, value):\n    \"\"\"Validates maxStalenessSeconds according to the Max Staleness Spec.\"\"\"\n    if value == -1 or value == \"-1\":\n        # Default: No maximum staleness.\n        return -1\n    return validate_positive_integer(option, value)\n\n\ndef validate_read_preference(dummy, value):\n    \"\"\"Validate a read preference.\n    \"\"\"\n    if not isinstance(value, _ServerMode):\n        raise TypeError(\"%r is not a read preference.\" % (value,))\n    return value\n\n\ndef validate_read_preference_mode(dummy, value):\n    \"\"\"Validate read preference mode for a MongoReplicaSetClient.\n\n    .. versionchanged:: 3.5\n       Returns the original ``value`` instead of the validated read preference\n       mode.\n    \"\"\"\n    if value not in _MONGOS_MODES:\n        raise ValueError(\"%s is not a valid read preference\" % (value,))\n    return value\n\n\ndef validate_auth_mechanism(option, value):\n    \"\"\"Validate the authMechanism URI option.\n    \"\"\"\n    # CRAM-MD5 is for server testing only. Undocumented,\n    # unsupported, may be removed at any time. You have\n    # been warned.\n    if value not in MECHANISMS and value != 'CRAM-MD5':\n        raise ValueError(\"%s must be in %s\" % (option, tuple(MECHANISMS)))\n    return value\n\n\ndef validate_uuid_representation(dummy, value):\n    \"\"\"Validate the uuid representation option selected in the URI.\n    \"\"\"\n    try:\n        return _UUID_REPRESENTATIONS[value]\n    except KeyError:\n        raise ValueError(\"%s is an invalid UUID representation. \"\n                         \"Must be one of \"\n                         \"%s\" % (value, tuple(_UUID_REPRESENTATIONS)))\n\n\ndef validate_read_preference_tags(name, value):\n    \"\"\"Parse readPreferenceTags if passed as a client kwarg.\n    \"\"\"\n    if not isinstance(value, list):\n        value = [value]\n\n    tag_sets = []\n    for tag_set in value:\n        if tag_set == '':\n            tag_sets.append({})\n            continue\n        try:\n            tag_sets.append(dict([tag.split(\":\")\n                                  for tag in tag_set.split(\",\")]))\n        except Exception:\n            raise ValueError(\"%r not a valid \"\n                             \"value for %s\" % (tag_set, name))\n    return tag_sets\n\n\n_MECHANISM_PROPS = frozenset(['SERVICE_NAME',\n                              'CANONICALIZE_HOST_NAME',\n                              'SERVICE_REALM'])\n\n\ndef validate_auth_mechanism_properties(option, value):\n    \"\"\"Validate authMechanismProperties.\"\"\"\n    value = validate_string(option, value)\n    props = {}\n    for opt in value.split(','):\n        try:\n            key, val = opt.split(':')\n        except ValueError:\n            raise ValueError(\"auth mechanism properties must be \"\n                             \"key:value pairs like SERVICE_NAME:\"\n                             \"mongodb, not %s.\" % (opt,))\n        if key not in _MECHANISM_PROPS:\n            raise ValueError(\"%s is not a supported auth \"\n                             \"mechanism property. Must be one of \"\n                             \"%s.\" % (key, tuple(_MECHANISM_PROPS)))\n        if key == 'CANONICALIZE_HOST_NAME':\n            props[key] = validate_boolean_or_string(key, val)\n        else:\n            props[key] = val\n\n    return props\n\n\ndef validate_document_class(option, value):\n    \"\"\"Validate the document_class option.\"\"\"\n    if not issubclass(value, (abc.MutableMapping, RawBSONDocument)):\n        raise TypeError(\"%s must be dict, bson.son.SON, \"\n                        \"bson.raw_bson.RawBSONDocument, or a \"\n                        \"sublass of collections.MutableMapping\" % (option,))\n    return value\n\n\ndef validate_type_registry(option, value):\n    \"\"\"Validate the type_registry option.\"\"\"\n    if value is not None and not isinstance(value, TypeRegistry):\n        raise TypeError(\"%s must be an instance of %s\" % (\n            option, TypeRegistry))\n    return value\n\n\ndef validate_list(option, value):\n    \"\"\"Validates that 'value' is a list.\"\"\"\n    if not isinstance(value, list):\n        raise TypeError(\"%s must be a list\" % (option,))\n    return value\n\n\ndef validate_list_or_none(option, value):\n    \"\"\"Validates that 'value' is a list or None.\"\"\"\n    if value is None:\n        return value\n    return validate_list(option, value)\n\n\ndef validate_list_or_mapping(option, value):\n    \"\"\"Validates that 'value' is a list or a document.\"\"\"\n    if not isinstance(value, (abc.Mapping, list)):\n        raise TypeError(\"%s must either be a list or an instance of dict, \"\n                        \"bson.son.SON, or any other type that inherits from \"\n                        \"collections.Mapping\" % (option,))\n\n\ndef validate_is_mapping(option, value):\n    \"\"\"Validate the type of method arguments that expect a document.\"\"\"\n    if not isinstance(value, abc.Mapping):\n        raise TypeError(\"%s must be an instance of dict, bson.son.SON, or \"\n                        \"any other type that inherits from \"\n                        \"collections.Mapping\" % (option,))\n\n\ndef validate_is_document_type(option, value):\n    \"\"\"Validate the type of method arguments that expect a MongoDB document.\"\"\"\n    if not isinstance(value, (abc.MutableMapping, RawBSONDocument)):\n        raise TypeError(\"%s must be an instance of dict, bson.son.SON, \"\n                        \"bson.raw_bson.RawBSONDocument, or \"\n                        \"a type that inherits from \"\n                        \"collections.MutableMapping\" % (option,))\n\n\ndef validate_appname_or_none(option, value):\n    \"\"\"Validate the appname option.\"\"\"\n    if value is None:\n        return value\n    validate_string(option, value)\n    # We need length in bytes, so encode utf8 first.\n    if len(value.encode('utf-8')) > 128:\n        raise ValueError(\"%s must be <= 128 bytes\" % (option,))\n    return value\n\n\ndef validate_driver_or_none(option, value):\n    \"\"\"Validate the driver keyword arg.\"\"\"\n    if value is None:\n        return value\n    if not isinstance(value, DriverInfo):\n        raise TypeError(\"%s must be an instance of DriverInfo\" % (option,))\n    return value\n\n\ndef validate_is_callable_or_none(option, value):\n    \"\"\"Validates that 'value' is a callable.\"\"\"\n    if value is None:\n        return value\n    if not callable(value):\n        raise ValueError(\"%s must be a callable\" % (option,))\n    return value\n\n\ndef validate_ok_for_replace(replacement):\n    \"\"\"Validate a replacement document.\"\"\"\n    validate_is_mapping(\"replacement\", replacement)\n    # Replacement can be {}\n    if replacement and not isinstance(replacement, RawBSONDocument):\n        first = next(iter(replacement))\n        if first.startswith('$'):\n            raise ValueError('replacement can not include $ operators')\n\n\ndef validate_ok_for_update(update):\n    \"\"\"Validate an update document.\"\"\"\n    validate_list_or_mapping(\"update\", update)\n    # Update cannot be {}.\n    if not update:\n        raise ValueError('update cannot be empty')\n\n    is_document = not isinstance(update, list)\n    first = next(iter(update))\n    if is_document and not first.startswith('$'):\n        raise ValueError('update only works with $ operators')\n\n\n_UNICODE_DECODE_ERROR_HANDLERS = frozenset(['strict', 'replace', 'ignore'])\n\n\ndef validate_unicode_decode_error_handler(dummy, value):\n    \"\"\"Validate the Unicode decode error handler option of CodecOptions.\n    \"\"\"\n    if value not in _UNICODE_DECODE_ERROR_HANDLERS:\n        raise ValueError(\"%s is an invalid Unicode decode error handler. \"\n                         \"Must be one of \"\n                         \"%s\" % (value, tuple(_UNICODE_DECODE_ERROR_HANDLERS)))\n    return value\n\n\ndef validate_tzinfo(dummy, value):\n    \"\"\"Validate the tzinfo option\n    \"\"\"\n    if value is not None and not isinstance(value, datetime.tzinfo):\n        raise TypeError(\"%s must be an instance of datetime.tzinfo\" % value)\n    return value\n\n\n# Dictionary where keys are the names of public URI options, and values\n# are lists of aliases for that option. Aliases of option names are assumed\n# to have been deprecated.\nURI_OPTIONS_ALIAS_MAP = {\n    'journal': ['j'],\n    'wtimeoutms': ['wtimeout'],\n    'tls': ['ssl'],\n    'tlsallowinvalidcertificates': ['ssl_cert_reqs'],\n    'tlsallowinvalidhostnames': ['ssl_match_hostname'],\n    'tlscrlfile': ['ssl_crlfile'],\n    'tlscafile': ['ssl_ca_certs'],\n    'tlscertificatekeyfile': ['ssl_certfile'],\n    'tlscertificatekeyfilepassword': ['ssl_pem_passphrase'],\n}\n\n# Dictionary where keys are the names of URI options, and values\n# are functions that validate user-input values for that option. If an option\n# alias uses a different validator than its public counterpart, it should be\n# included here as a key, value pair.\nURI_OPTIONS_VALIDATOR_MAP = {\n    'appname': validate_appname_or_none,\n    'authmechanism': validate_auth_mechanism,\n    'authmechanismproperties': validate_auth_mechanism_properties,\n    'authsource': validate_string,\n    'compressors': validate_compressors,\n    'connecttimeoutms': validate_timeout_or_none,\n    'heartbeatfrequencyms': validate_timeout_or_none,\n    'journal': validate_boolean_or_string,\n    'localthresholdms': validate_positive_float_or_zero,\n    'maxidletimems': validate_timeout_or_none,\n    'maxpoolsize': validate_positive_integer_or_none,\n    'maxstalenessseconds': validate_max_staleness,\n    'readconcernlevel': validate_string_or_none,\n    'readpreference': validate_read_preference_mode,\n    'readpreferencetags': validate_read_preference_tags,\n    'replicaset': validate_string_or_none,\n    'retryreads': validate_boolean_or_string,\n    'retrywrites': validate_boolean_or_string,\n    'serverselectiontimeoutms': validate_timeout_or_zero,\n    'sockettimeoutms': validate_timeout_or_none,\n    'ssl_keyfile': validate_readable,\n    'tls': validate_boolean_or_string,\n    'tlsallowinvalidcertificates': validate_allow_invalid_certs,\n    'ssl_cert_reqs': validate_cert_reqs,\n    'tlsallowinvalidhostnames': lambda *x: not validate_boolean_or_string(*x),\n    'ssl_match_hostname': validate_boolean_or_string,\n    'tlscafile': validate_readable,\n    'tlscertificatekeyfile': validate_readable,\n    'tlscertificatekeyfilepassword': validate_string_or_none,\n    'tlsinsecure': validate_boolean_or_string,\n    'w': validate_non_negative_int_or_basestring,\n    'wtimeoutms': validate_non_negative_integer,\n    'zlibcompressionlevel': validate_zlib_compression_level,\n}\n\n# Dictionary where keys are the names of URI options specific to pymongo,\n# and values are functions that validate user-input values for those options.\nNONSPEC_OPTIONS_VALIDATOR_MAP = {\n    'connect': validate_boolean_or_string,\n    'driver': validate_driver_or_none,\n    'fsync': validate_boolean_or_string,\n    'minpoolsize': validate_non_negative_integer,\n    'socketkeepalive': validate_boolean_or_string,\n    'tlscrlfile': validate_readable,\n    'tz_aware': validate_boolean_or_string,\n    'unicode_decode_error_handler': validate_unicode_decode_error_handler,\n    'uuidrepresentation': validate_uuid_representation,\n    'waitqueuemultiple': validate_non_negative_integer_or_none,\n    'waitqueuetimeoutms': validate_timeout_or_none,\n}\n\n# Dictionary where keys are the names of keyword-only options for the\n# MongoClient constructor, and values are functions that validate user-input\n# values for those options.\nKW_VALIDATORS = {\n    'document_class': validate_document_class,\n    'type_registry': validate_type_registry,\n    'read_preference': validate_read_preference,\n    'event_listeners': _validate_event_listeners,\n    'tzinfo': validate_tzinfo,\n    'username': validate_string_or_none,\n    'password': validate_string_or_none,\n    'server_selector': validate_is_callable_or_none,\n    'auto_encryption_opts': validate_auto_encryption_opts_or_none,\n}\n\n# Dictionary where keys are any URI option name, and values are the\n# internally-used names of that URI option. Options with only one name\n# variant need not be included here. Options whose public and internal\n# names are the same need not be included here.\nINTERNAL_URI_OPTION_NAME_MAP = {\n    'j': 'journal',\n    'wtimeout': 'wtimeoutms',\n    'tls': 'ssl',\n    'tlsallowinvalidcertificates': 'ssl_cert_reqs',\n    'tlsallowinvalidhostnames': 'ssl_match_hostname',\n    'tlscrlfile': 'ssl_crlfile',\n    'tlscafile': 'ssl_ca_certs',\n    'tlscertificatekeyfile': 'ssl_certfile',\n    'tlscertificatekeyfilepassword': 'ssl_pem_passphrase',\n}\n\n# Map from deprecated URI option names to a tuple indicating the method of\n# their deprecation and any additional information that may be needed to\n# construct the warning message.\nURI_OPTIONS_DEPRECATION_MAP = {\n    # format: <deprecated option name>: (<mode>, <message>),\n    # Supported <mode> values:\n    # - 'renamed': <message> should be the new option name. Note that case is\n    #   preserved for renamed options as they are part of user warnings.\n    # - 'removed': <message> may suggest the rationale for deprecating the\n    #   option and/or recommend remedial action.\n    'j': ('renamed', 'journal'),\n    'wtimeout': ('renamed', 'wTimeoutMS'),\n    'ssl_cert_reqs': ('renamed', 'tlsAllowInvalidCertificates'),\n    'ssl_match_hostname': ('renamed', 'tlsAllowInvalidHostnames'),\n    'ssl_crlfile': ('renamed', 'tlsCRLFile'),\n    'ssl_ca_certs': ('renamed', 'tlsCAFile'),\n    'ssl_pem_passphrase': ('renamed', 'tlsCertificateKeyFilePassword'),\n    'waitqueuemultiple': ('removed', (\n        'Instead of using waitQueueMultiple to bound queuing, limit the size '\n        'of the thread pool in your application server'))\n}\n\n# Augment the option validator map with pymongo-specific option information.\nURI_OPTIONS_VALIDATOR_MAP.update(NONSPEC_OPTIONS_VALIDATOR_MAP)\nfor optname, aliases in iteritems(URI_OPTIONS_ALIAS_MAP):\n    for alias in aliases:\n        if alias not in URI_OPTIONS_VALIDATOR_MAP:\n            URI_OPTIONS_VALIDATOR_MAP[alias] = (\n                URI_OPTIONS_VALIDATOR_MAP[optname])\n\n# Map containing all URI option and keyword argument validators.\nVALIDATORS = URI_OPTIONS_VALIDATOR_MAP.copy()\nVALIDATORS.update(KW_VALIDATORS)\n\n# List of timeout-related options.\nTIMEOUT_OPTIONS = [\n    'connecttimeoutms',\n    'heartbeatfrequencyms',\n    'maxidletimems',\n    'maxstalenessseconds',\n    'serverselectiontimeoutms',\n    'sockettimeoutms',\n    'waitqueuetimeoutms',\n]\n\n\n_AUTH_OPTIONS = frozenset(['authmechanismproperties'])\n\n\ndef validate_auth_option(option, value):\n    \"\"\"Validate optional authentication parameters.\n    \"\"\"\n    lower, value = validate(option, value)\n    if lower not in _AUTH_OPTIONS:\n        raise ConfigurationError('Unknown '\n                                 'authentication option: %s' % (option,))\n    return lower, value\n\n\ndef validate(option, value):\n    \"\"\"Generic validation function.\n    \"\"\"\n    lower = option.lower()\n    validator = VALIDATORS.get(lower, raise_config_error)\n    value = validator(option, value)\n    return lower, value\n\n\ndef get_validated_options(options, warn=True):\n    \"\"\"Validate each entry in options and raise a warning if it is not valid.\n    Returns a copy of options with invalid entries removed.\n\n    :Parameters:\n        - `opts`: A dict containing MongoDB URI options.\n        - `warn` (optional): If ``True`` then warnings will be logged and\n          invalid options will be ignored. Otherwise, invalid options will\n          cause errors.\n    \"\"\"\n    if isinstance(options, _CaseInsensitiveDictionary):\n        validated_options = _CaseInsensitiveDictionary()\n        get_normed_key = lambda x: x\n        get_setter_key = lambda x: options.cased_key(x)\n    else:\n        validated_options = {}\n        get_normed_key = lambda x: x.lower()\n        get_setter_key = lambda x: x\n\n    for opt, value in iteritems(options):\n        normed_key = get_normed_key(opt)\n        try:\n            validator = URI_OPTIONS_VALIDATOR_MAP.get(\n                normed_key, raise_config_error)\n            value = validator(opt, value)\n        except (ValueError, TypeError, ConfigurationError) as exc:\n            if warn:\n                warnings.warn(str(exc))\n            else:\n                raise\n        else:\n            validated_options[get_setter_key(normed_key)] = value\n    return validated_options\n\n\n# List of write-concern-related options.\nWRITE_CONCERN_OPTIONS = frozenset([\n    'w',\n    'wtimeout',\n    'wtimeoutms',\n    'fsync',\n    'j',\n    'journal'\n])\n\n\nclass BaseObject(object):\n    \"\"\"A base class that provides attributes and methods common\n    to multiple pymongo classes.\n\n    SHOULD NOT BE USED BY DEVELOPERS EXTERNAL TO MONGODB.\n    \"\"\"\n\n    def __init__(self, codec_options, read_preference, write_concern,\n                 read_concern):\n\n        if not isinstance(codec_options, CodecOptions):\n            raise TypeError(\"codec_options must be an instance of \"\n                            \"bson.codec_options.CodecOptions\")\n        self.__codec_options = codec_options\n\n        if not isinstance(read_preference, _ServerMode):\n            raise TypeError(\"%r is not valid for read_preference. See \"\n                            \"pymongo.read_preferences for valid \"\n                            \"options.\" % (read_preference,))\n        self.__read_preference = read_preference\n\n        if not isinstance(write_concern, WriteConcern):\n            raise TypeError(\"write_concern must be an instance of \"\n                            \"pymongo.write_concern.WriteConcern\")\n        self.__write_concern = write_concern\n\n        if not isinstance(read_concern, ReadConcern):\n            raise TypeError(\"read_concern must be an instance of \"\n                            \"pymongo.read_concern.ReadConcern\")\n        self.__read_concern = read_concern\n\n    @property\n    def codec_options(self):\n        \"\"\"Read only access to the :class:`~bson.codec_options.CodecOptions`\n        of this instance.\n        \"\"\"\n        return self.__codec_options\n\n    @property\n    def write_concern(self):\n        \"\"\"Read only access to the :class:`~pymongo.write_concern.WriteConcern`\n        of this instance.\n\n        .. versionchanged:: 3.0\n          The :attr:`write_concern` attribute is now read only.\n        \"\"\"\n        return self.__write_concern\n\n    def _write_concern_for(self, session):\n        \"\"\"Read only access to the write concern of this instance or session.\n        \"\"\"\n        # Override this operation's write concern with the transaction's.\n        if session and session._in_transaction:\n            return DEFAULT_WRITE_CONCERN\n        return self.write_concern\n\n    @property\n    def read_preference(self):\n        \"\"\"Read only access to the read preference of this instance.\n\n        .. versionchanged:: 3.0\n          The :attr:`read_preference` attribute is now read only.\n        \"\"\"\n        return self.__read_preference\n\n    def _read_preference_for(self, session):\n        \"\"\"Read only access to the read preference of this instance or session.\n        \"\"\"\n        # Override this operation's read preference with the transaction's.\n        if session:\n            return session._txn_read_preference() or self.__read_preference\n        return self.__read_preference\n\n    @property\n    def read_concern(self):\n        \"\"\"Read only access to the :class:`~pymongo.read_concern.ReadConcern`\n        of this instance.\n\n        .. versionadded:: 3.2\n        \"\"\"\n        return self.__read_concern\n\n\nclass _CaseInsensitiveDictionary(abc.MutableMapping):\n    def __init__(self, *args, **kwargs):\n        self.__casedkeys = {}\n        self.__data = {}\n        self.update(dict(*args, **kwargs))\n\n    def __contains__(self, key):\n        return key.lower() in self.__data\n\n    def __len__(self):\n        return len(self.__data)\n\n    def __iter__(self):\n        return (key for key in self.__casedkeys)\n\n    def __repr__(self):\n        return str({self.__casedkeys[k]: self.__data[k] for k in self})\n\n    def __setitem__(self, key, value):\n        lc_key = key.lower()\n        self.__casedkeys[lc_key] = key\n        self.__data[lc_key] = value\n\n    def __getitem__(self, key):\n        return self.__data[key.lower()]\n\n    def __delitem__(self, key):\n        lc_key = key.lower()\n        del self.__casedkeys[lc_key]\n        del self.__data[lc_key]\n\n    def __eq__(self, other):\n        if not isinstance(other, abc.Mapping):\n            return NotImplemented\n        if len(self) != len(other):\n            return False\n        for key in other:\n            if self[key] != other[key]:\n                return False\n\n        return True\n\n    def get(self, key, default=None):\n        return self.__data.get(key.lower(), default)\n\n    def pop(self, key, *args, **kwargs):\n        lc_key = key.lower()\n        self.__casedkeys.pop(lc_key, None)\n        return self.__data.pop(lc_key, *args, **kwargs)\n\n    def popitem(self):\n        lc_key, cased_key = self.__casedkeys.popitem()\n        value = self.__data.pop(lc_key)\n        return cased_key, value\n\n    def clear(self):\n        self.__casedkeys.clear()\n        self.__data.clear()\n\n    def setdefault(self, key, default=None):\n        lc_key = key.lower()\n        if key in self:\n            return self.__data[lc_key]\n        else:\n            self.__casedkeys[lc_key] = key\n            self.__data[lc_key] = default\n            return default\n\n    def update(self, other):\n        if isinstance(other, _CaseInsensitiveDictionary):\n            for key in other:\n                self[other.cased_key(key)] = other[key]\n        else:\n            for key in other:\n                self[key] = other[key]\n\n    def cased_key(self, key):\n        return self.__casedkeys[key.lower()]"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/compression_support.py",
    "content": "# Copyright 2018 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\nimport warnings\n\ntry:\n    import snappy\n    _HAVE_SNAPPY = True\nexcept ImportError:\n    # python-snappy isn't available.\n    _HAVE_SNAPPY = False\n\ntry:\n    import zlib\n    _HAVE_ZLIB = True\nexcept ImportError:\n    # Python built without zlib support.\n    _HAVE_ZLIB = False\n\ntry:\n    from zstandard import ZstdCompressor, ZstdDecompressor\n    _HAVE_ZSTD = True\nexcept ImportError:\n    _HAVE_ZSTD = False\n\nfrom pymongo.monitoring import _SENSITIVE_COMMANDS\n\n_SUPPORTED_COMPRESSORS = set([\"snappy\", \"zlib\", \"zstd\"])\n_NO_COMPRESSION = set(['ismaster'])\n_NO_COMPRESSION.update(_SENSITIVE_COMMANDS)\n\n\ndef validate_compressors(dummy, value):\n    try:\n        # `value` is string.\n        compressors = value.split(\",\")\n    except AttributeError:\n        # `value` is an iterable.\n        compressors = list(value)\n\n    for compressor in compressors[:]:\n        if compressor not in _SUPPORTED_COMPRESSORS:\n            compressors.remove(compressor)\n            warnings.warn(\"Unsupported compressor: %s\" % (compressor,))\n        elif compressor == \"snappy\" and not _HAVE_SNAPPY:\n            compressors.remove(compressor)\n            warnings.warn(\n                \"Wire protocol compression with snappy is not available. \"\n                \"You must install the python-snappy module for snappy support.\")\n        elif compressor == \"zlib\" and not _HAVE_ZLIB:\n            compressors.remove(compressor)\n            warnings.warn(\n                \"Wire protocol compression with zlib is not available. \"\n                \"The zlib module is not available.\")\n        elif compressor == \"zstd\" and not _HAVE_ZSTD:\n            compressors.remove(compressor)\n            warnings.warn(\n                \"Wire protocol compression with zstandard is not available. \"\n                \"You must install the zstandard module for zstandard support.\")\n    return compressors\n\n\ndef validate_zlib_compression_level(option, value):\n    try:\n        level = int(value)\n    except:\n        raise TypeError(\"%s must be an integer, not %r.\" % (option, value))\n    if level < -1 or level > 9:\n        raise ValueError(\n            \"%s must be between -1 and 9, not %d.\" % (option, level))\n    return level\n\n\nclass CompressionSettings(object):\n    def __init__(self, compressors, zlib_compression_level):\n        self.compressors = compressors\n        self.zlib_compression_level = zlib_compression_level\n\n    def get_compression_context(self, compressors):\n        if compressors:\n            chosen = compressors[0]\n            if chosen == \"snappy\":\n                return SnappyContext()\n            elif chosen == \"zlib\":\n                return ZlibContext(self.zlib_compression_level)\n            elif chosen == \"zstd\":\n                return ZstdContext()\n\n\ndef _zlib_no_compress(data):\n    \"\"\"Compress data with zlib level 0.\"\"\"\n    cobj = zlib.compressobj(0)\n    return b\"\".join([cobj.compress(data), cobj.flush()])\n\n\nclass SnappyContext(object):\n    compressor_id = 1\n\n    @staticmethod\n    def compress(data):\n        return snappy.compress(data)\n\n\nclass ZlibContext(object):\n    compressor_id = 2\n\n    def __init__(self, level):\n        # Jython zlib.compress doesn't support -1\n        if level == -1:\n            self.compress = zlib.compress\n        # Jython zlib.compress also doesn't support 0\n        elif level == 0:\n            self.compress = _zlib_no_compress\n        else:\n            self.compress = lambda data: zlib.compress(data, level)\n\n\nclass ZstdContext(object):\n    compressor_id = 3\n\n    @staticmethod\n    def compress(data):\n        # ZstdCompressor is not thread safe.\n        # TODO: Use a pool?\n        return ZstdCompressor().compress(data)\n\n\ndef decompress(data, compressor_id):\n    if compressor_id == SnappyContext.compressor_id:\n        # python-snappy doesn't support the buffer interface.\n        # https://github.com/andrix/python-snappy/issues/65\n        # This only matters when data is a memoryview since\n        # id(bytes(data)) == id(data) when data is a bytes.\n        # NOTE: bytes(memoryview) returns the memoryview repr\n        # in Python 2.7. The right thing to do in 2.7 is call\n        # memoryview.tobytes(), but we currently only use\n        # memoryview in Python 3.x.\n        return snappy.uncompress(bytes(data))\n    elif compressor_id == ZlibContext.compressor_id:\n        return zlib.decompress(data)\n    elif compressor_id == ZstdContext.compressor_id:\n        # ZstdDecompressor is not thread safe.\n        # TODO: Use a pool?\n        return ZstdDecompressor().decompress(data)\n    else:\n        raise ValueError(\"Unknown compressorId %d\" % (compressor_id,))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/cursor.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Cursor class to iterate over Mongo query results.\"\"\"\n\nimport copy\nimport warnings\n\nfrom collections import deque\n\nfrom bson import RE_TYPE\nfrom bson.code import Code\nfrom bson.py3compat import (iteritems,\n                            integer_types,\n                            string_type)\nfrom bson.son import SON\nfrom pymongo import helpers\nfrom pymongo.common import validate_boolean, validate_is_mapping\nfrom pymongo.collation import validate_collation_or_none\nfrom pymongo.errors import (ConnectionFailure,\n                            InvalidOperation,\n                            NotMasterError,\n                            OperationFailure)\nfrom pymongo.message import (_CursorAddress,\n                             _GetMore,\n                             _RawBatchGetMore,\n                             _Query,\n                             _RawBatchQuery)\nfrom pymongo.monitoring import ConnectionClosedReason\n\n\n_QUERY_OPTIONS = {\n    \"tailable_cursor\": 2,\n    \"slave_okay\": 4,\n    \"oplog_replay\": 8,\n    \"no_timeout\": 16,\n    \"await_data\": 32,\n    \"exhaust\": 64,\n    \"partial\": 128}\n\n\nclass CursorType(object):\n    NON_TAILABLE = 0\n    \"\"\"The standard cursor type.\"\"\"\n\n    TAILABLE = _QUERY_OPTIONS[\"tailable_cursor\"]\n    \"\"\"The tailable cursor type.\n\n    Tailable cursors are only for use with capped collections. They are not\n    closed when the last data is retrieved but are kept open and the cursor\n    location marks the final document position. If more data is received\n    iteration of the cursor will continue from the last document received.\n    \"\"\"\n\n    TAILABLE_AWAIT = TAILABLE | _QUERY_OPTIONS[\"await_data\"]\n    \"\"\"A tailable cursor with the await option set.\n\n    Creates a tailable cursor that will wait for a few seconds after returning\n    the full result set so that it can capture and return additional data added\n    during the query.\n    \"\"\"\n\n    EXHAUST = _QUERY_OPTIONS[\"exhaust\"]\n    \"\"\"An exhaust cursor.\n\n    MongoDB will stream batched results to the client without waiting for the\n    client to request each batch, reducing latency.\n    \"\"\"\n\n\n# This has to be an old style class due to\n# http://bugs.jython.org/issue1057\nclass _SocketManager:\n    \"\"\"Used with exhaust cursors to ensure the socket is returned.\n    \"\"\"\n    def __init__(self, sock, pool):\n        self.sock = sock\n        self.pool = pool\n        self.__closed = False\n\n    def __del__(self):\n        self.close()\n\n    def close(self):\n        \"\"\"Return this instance's socket to the connection pool.\n        \"\"\"\n        if not self.__closed:\n            self.__closed = True\n            self.pool.return_socket(self.sock)\n            self.sock, self.pool = None, None\n\n\nclass Cursor(object):\n    \"\"\"A cursor / iterator over Mongo query results.\n    \"\"\"\n    _query_class = _Query\n    _getmore_class = _GetMore\n\n    def __init__(self, collection, filter=None, projection=None, skip=0,\n                 limit=0, no_cursor_timeout=False,\n                 cursor_type=CursorType.NON_TAILABLE,\n                 sort=None, allow_partial_results=False, oplog_replay=False,\n                 modifiers=None, batch_size=0, manipulate=True,\n                 collation=None, hint=None, max_scan=None, max_time_ms=None,\n                 max=None, min=None, return_key=False, show_record_id=False,\n                 snapshot=False, comment=None, session=None):\n        \"\"\"Create a new cursor.\n\n        Should not be called directly by application developers - see\n        :meth:`~pymongo.collection.Collection.find` instead.\n\n        .. mongodoc:: cursors\n        \"\"\"\n        # Initialize all attributes used in __del__ before possibly raising\n        # an error to avoid attribute errors during garbage collection.\n        self.__id = None\n        self.__exhaust = False\n        self.__exhaust_mgr = None\n        self.__killed = False\n\n        if session:\n            self.__session = session\n            self.__explicit_session = True\n        else:\n            self.__session = None\n            self.__explicit_session = False\n\n        spec = filter\n        if spec is None:\n            spec = {}\n\n        validate_is_mapping(\"filter\", spec)\n        if not isinstance(skip, int):\n            raise TypeError(\"skip must be an instance of int\")\n        if not isinstance(limit, int):\n            raise TypeError(\"limit must be an instance of int\")\n        validate_boolean(\"no_cursor_timeout\", no_cursor_timeout)\n        if cursor_type not in (CursorType.NON_TAILABLE, CursorType.TAILABLE,\n                               CursorType.TAILABLE_AWAIT, CursorType.EXHAUST):\n            raise ValueError(\"not a valid value for cursor_type\")\n        validate_boolean(\"allow_partial_results\", allow_partial_results)\n        validate_boolean(\"oplog_replay\", oplog_replay)\n        if modifiers is not None:\n            warnings.warn(\"the 'modifiers' parameter is deprecated\",\n                          DeprecationWarning, stacklevel=2)\n            validate_is_mapping(\"modifiers\", modifiers)\n        if not isinstance(batch_size, integer_types):\n            raise TypeError(\"batch_size must be an integer\")\n        if batch_size < 0:\n            raise ValueError(\"batch_size must be >= 0\")\n\n        if projection is not None:\n            if not projection:\n                projection = {\"_id\": 1}\n            projection = helpers._fields_list_to_dict(projection, \"projection\")\n\n        self.__collection = collection\n        self.__spec = spec\n        self.__projection = projection\n        self.__skip = skip\n        self.__limit = limit\n        self.__batch_size = batch_size\n        self.__modifiers = modifiers and modifiers.copy() or {}\n        self.__ordering = sort and helpers._index_document(sort) or None\n        self.__max_scan = max_scan\n        self.__explain = False\n        self.__comment = comment\n        self.__max_time_ms = max_time_ms\n        self.__max_await_time_ms = None\n        self.__max = max\n        self.__min = min\n        self.__manipulate = manipulate\n        self.__collation = validate_collation_or_none(collation)\n        self.__return_key = return_key\n        self.__show_record_id = show_record_id\n        self.__snapshot = snapshot\n        self.__set_hint(hint)\n\n        # Exhaust cursor support\n        if cursor_type == CursorType.EXHAUST:\n            if self.__collection.database.client.is_mongos:\n                raise InvalidOperation('Exhaust cursors are '\n                                       'not supported by mongos')\n            if limit:\n                raise InvalidOperation(\"Can't use limit and exhaust together.\")\n            self.__exhaust = True\n\n        # This is ugly. People want to be able to do cursor[5:5] and\n        # get an empty result set (old behavior was an\n        # exception). It's hard to do that right, though, because the\n        # server uses limit(0) to mean 'no limit'. So we set __empty\n        # in that case and check for it when iterating. We also unset\n        # it anytime we change __limit.\n        self.__empty = False\n\n        self.__data = deque()\n        self.__address = None\n        self.__retrieved = 0\n\n        self.__codec_options = collection.codec_options\n        # Read preference is set when the initial find is sent.\n        self.__read_preference = None\n        self.__read_concern = collection.read_concern\n\n        self.__query_flags = cursor_type\n        if no_cursor_timeout:\n            self.__query_flags |= _QUERY_OPTIONS[\"no_timeout\"]\n        if allow_partial_results:\n            self.__query_flags |= _QUERY_OPTIONS[\"partial\"]\n        if oplog_replay:\n            self.__query_flags |= _QUERY_OPTIONS[\"oplog_replay\"]\n\n    @property\n    def collection(self):\n        \"\"\"The :class:`~pymongo.collection.Collection` that this\n        :class:`Cursor` is iterating.\n        \"\"\"\n        return self.__collection\n\n    @property\n    def retrieved(self):\n        \"\"\"The number of documents retrieved so far.\n        \"\"\"\n        return self.__retrieved\n\n    def __del__(self):\n        self.__die()\n\n    def rewind(self):\n        \"\"\"Rewind this cursor to its unevaluated state.\n\n        Reset this cursor if it has been partially or completely evaluated.\n        Any options that are present on the cursor will remain in effect.\n        Future iterating performed on this cursor will cause new queries to\n        be sent to the server, even if the resultant data has already been\n        retrieved by this cursor.\n        \"\"\"\n        self.__data = deque()\n        self.__id = None\n        self.__address = None\n        self.__retrieved = 0\n        self.__killed = False\n\n        return self\n\n    def clone(self):\n        \"\"\"Get a clone of this cursor.\n\n        Returns a new Cursor instance with options matching those that have\n        been set on the current instance. The clone will be completely\n        unevaluated, even if the current instance has been partially or\n        completely evaluated.\n        \"\"\"\n        return self._clone(True)\n\n    def _clone(self, deepcopy=True, base=None):\n        \"\"\"Internal clone helper.\"\"\"\n        if not base:\n            if self.__explicit_session:\n                base = self._clone_base(self.__session)\n            else:\n                base = self._clone_base(None)\n\n        values_to_clone = (\"spec\", \"projection\", \"skip\", \"limit\",\n                           \"max_time_ms\", \"max_await_time_ms\", \"comment\",\n                           \"max\", \"min\", \"ordering\", \"explain\", \"hint\",\n                           \"batch_size\", \"max_scan\", \"manipulate\",\n                           \"query_flags\", \"modifiers\", \"collation\")\n        data = dict((k, v) for k, v in iteritems(self.__dict__)\n                    if k.startswith('_Cursor__') and k[9:] in values_to_clone)\n        if deepcopy:\n            data = self._deepcopy(data)\n        base.__dict__.update(data)\n        return base\n\n    def _clone_base(self, session):\n        \"\"\"Creates an empty Cursor object for information to be copied into.\n        \"\"\"\n        return self.__class__(self.__collection, session=session)\n\n    def __die(self, synchronous=False):\n        \"\"\"Closes this cursor.\n        \"\"\"\n        try:\n            already_killed = self.__killed\n        except AttributeError:\n            # __init__ did not run to completion (or at all).\n            return\n\n        self.__killed = True\n        if self.__id and not already_killed:\n            if self.__exhaust and self.__exhaust_mgr:\n                # If this is an exhaust cursor and we haven't completely\n                # exhausted the result set we *must* close the socket\n                # to stop the server from sending more data.\n                self.__exhaust_mgr.sock.close_socket(\n                    ConnectionClosedReason.ERROR)\n            else:\n                address = _CursorAddress(\n                    self.__address, self.__collection.full_name)\n                if synchronous:\n                    self.__collection.database.client._close_cursor_now(\n                        self.__id, address, session=self.__session)\n                else:\n                    # The cursor will be closed later in a different session.\n                    self.__collection.database.client._close_cursor(\n                        self.__id, address)\n        if self.__exhaust and self.__exhaust_mgr:\n            self.__exhaust_mgr.close()\n        if self.__session and not self.__explicit_session:\n            self.__session._end_session(lock=synchronous)\n            self.__session = None\n\n    def close(self):\n        \"\"\"Explicitly close / kill this cursor.\n        \"\"\"\n        self.__die(True)\n\n    def __query_spec(self):\n        \"\"\"Get the spec to use for a query.\n        \"\"\"\n        operators = self.__modifiers.copy()\n        if self.__ordering:\n            operators[\"$orderby\"] = self.__ordering\n        if self.__explain:\n            operators[\"$explain\"] = True\n        if self.__hint:\n            operators[\"$hint\"] = self.__hint\n        if self.__comment:\n            operators[\"$comment\"] = self.__comment\n        if self.__max_scan:\n            operators[\"$maxScan\"] = self.__max_scan\n        if self.__max_time_ms is not None:\n            operators[\"$maxTimeMS\"] = self.__max_time_ms\n        if self.__max:\n            operators[\"$max\"] = self.__max\n        if self.__min:\n            operators[\"$min\"] = self.__min\n        if self.__return_key:\n            operators[\"$returnKey\"] = self.__return_key\n        if self.__show_record_id:\n            # This is upgraded to showRecordId for MongoDB 3.2+ \"find\" command.\n            operators[\"$showDiskLoc\"] = self.__show_record_id\n        if self.__snapshot:\n            operators[\"$snapshot\"] = self.__snapshot\n\n        if operators:\n            # Make a shallow copy so we can cleanly rewind or clone.\n            spec = self.__spec.copy()\n\n            # White-listed commands must be wrapped in $query.\n            if \"$query\" not in spec:\n                # $query has to come first\n                spec = SON([(\"$query\", spec)])\n\n            if not isinstance(spec, SON):\n                # Ensure the spec is SON. As order is important this will\n                # ensure its set before merging in any extra operators.\n                spec = SON(spec)\n\n            spec.update(operators)\n            return spec\n        # Have to wrap with $query if \"query\" is the first key.\n        # We can't just use $query anytime \"query\" is a key as\n        # that breaks commands like count and find_and_modify.\n        # Checking spec.keys()[0] covers the case that the spec\n        # was passed as an instance of SON or OrderedDict.\n        elif (\"query\" in self.__spec and\n              (len(self.__spec) == 1 or\n               next(iter(self.__spec)) == \"query\")):\n            return SON({\"$query\": self.__spec})\n\n        return self.__spec\n\n    def __check_okay_to_chain(self):\n        \"\"\"Check if it is okay to chain more options onto this cursor.\n        \"\"\"\n        if self.__retrieved or self.__id is not None:\n            raise InvalidOperation(\"cannot set options after executing query\")\n\n    def add_option(self, mask):\n        \"\"\"Set arbitrary query flags using a bitmask.\n\n        To set the tailable flag:\n        cursor.add_option(2)\n        \"\"\"\n        if not isinstance(mask, int):\n            raise TypeError(\"mask must be an int\")\n        self.__check_okay_to_chain()\n\n        if mask & _QUERY_OPTIONS[\"exhaust\"]:\n            if self.__limit:\n                raise InvalidOperation(\"Can't use limit and exhaust together.\")\n            if self.__collection.database.client.is_mongos:\n                raise InvalidOperation('Exhaust cursors are '\n                                       'not supported by mongos')\n            self.__exhaust = True\n\n        self.__query_flags |= mask\n        return self\n\n    def remove_option(self, mask):\n        \"\"\"Unset arbitrary query flags using a bitmask.\n\n        To unset the tailable flag:\n        cursor.remove_option(2)\n        \"\"\"\n        if not isinstance(mask, int):\n            raise TypeError(\"mask must be an int\")\n        self.__check_okay_to_chain()\n\n        if mask & _QUERY_OPTIONS[\"exhaust\"]:\n            self.__exhaust = False\n\n        self.__query_flags &= ~mask\n        return self\n\n    def limit(self, limit):\n        \"\"\"Limits the number of results to be returned by this cursor.\n\n        Raises :exc:`TypeError` if `limit` is not an integer. Raises\n        :exc:`~pymongo.errors.InvalidOperation` if this :class:`Cursor`\n        has already been used. The last `limit` applied to this cursor\n        takes precedence. A limit of ``0`` is equivalent to no limit.\n\n        :Parameters:\n          - `limit`: the number of results to return\n\n        .. mongodoc:: limit\n        \"\"\"\n        if not isinstance(limit, integer_types):\n            raise TypeError(\"limit must be an integer\")\n        if self.__exhaust:\n            raise InvalidOperation(\"Can't use limit and exhaust together.\")\n        self.__check_okay_to_chain()\n\n        self.__empty = False\n        self.__limit = limit\n        return self\n\n    def batch_size(self, batch_size):\n        \"\"\"Limits the number of documents returned in one batch. Each batch\n        requires a round trip to the server. It can be adjusted to optimize\n        performance and limit data transfer.\n\n        .. note:: batch_size can not override MongoDB's internal limits on the\n           amount of data it will return to the client in a single batch (i.e\n           if you set batch size to 1,000,000,000, MongoDB will currently only\n           return 4-16MB of results per batch).\n\n        Raises :exc:`TypeError` if `batch_size` is not an integer.\n        Raises :exc:`ValueError` if `batch_size` is less than ``0``.\n        Raises :exc:`~pymongo.errors.InvalidOperation` if this\n        :class:`Cursor` has already been used. The last `batch_size`\n        applied to this cursor takes precedence.\n\n        :Parameters:\n          - `batch_size`: The size of each batch of results requested.\n        \"\"\"\n        if not isinstance(batch_size, integer_types):\n            raise TypeError(\"batch_size must be an integer\")\n        if batch_size < 0:\n            raise ValueError(\"batch_size must be >= 0\")\n        self.__check_okay_to_chain()\n\n        self.__batch_size = batch_size\n        return self\n\n    def skip(self, skip):\n        \"\"\"Skips the first `skip` results of this cursor.\n\n        Raises :exc:`TypeError` if `skip` is not an integer. Raises\n        :exc:`ValueError` if `skip` is less than ``0``. Raises\n        :exc:`~pymongo.errors.InvalidOperation` if this :class:`Cursor` has\n        already been used. The last `skip` applied to this cursor takes\n        precedence.\n\n        :Parameters:\n          - `skip`: the number of results to skip\n        \"\"\"\n        if not isinstance(skip, integer_types):\n            raise TypeError(\"skip must be an integer\")\n        if skip < 0:\n            raise ValueError(\"skip must be >= 0\")\n        self.__check_okay_to_chain()\n\n        self.__skip = skip\n        return self\n\n    def max_time_ms(self, max_time_ms):\n        \"\"\"Specifies a time limit for a query operation. If the specified\n        time is exceeded, the operation will be aborted and\n        :exc:`~pymongo.errors.ExecutionTimeout` is raised. If `max_time_ms`\n        is ``None`` no limit is applied.\n\n        Raises :exc:`TypeError` if `max_time_ms` is not an integer or ``None``.\n        Raises :exc:`~pymongo.errors.InvalidOperation` if this :class:`Cursor`\n        has already been used.\n\n        :Parameters:\n          - `max_time_ms`: the time limit after which the operation is aborted\n        \"\"\"\n        if (not isinstance(max_time_ms, integer_types)\n                and max_time_ms is not None):\n            raise TypeError(\"max_time_ms must be an integer or None\")\n        self.__check_okay_to_chain()\n\n        self.__max_time_ms = max_time_ms\n        return self\n\n    def max_await_time_ms(self, max_await_time_ms):\n        \"\"\"Specifies a time limit for a getMore operation on a\n        :attr:`~pymongo.cursor.CursorType.TAILABLE_AWAIT` cursor. For all other\n        types of cursor max_await_time_ms is ignored.\n\n        Raises :exc:`TypeError` if `max_await_time_ms` is not an integer or\n        ``None``. Raises :exc:`~pymongo.errors.InvalidOperation` if this\n        :class:`Cursor` has already been used.\n\n        .. note:: `max_await_time_ms` requires server version **>= 3.2**\n\n        :Parameters:\n          - `max_await_time_ms`: the time limit after which the operation is\n            aborted\n\n        .. versionadded:: 3.2\n        \"\"\"\n        if (not isinstance(max_await_time_ms, integer_types)\n                and max_await_time_ms is not None):\n            raise TypeError(\"max_await_time_ms must be an integer or None\")\n        self.__check_okay_to_chain()\n\n        # Ignore max_await_time_ms if not tailable or await_data is False.\n        if self.__query_flags & CursorType.TAILABLE_AWAIT:\n            self.__max_await_time_ms = max_await_time_ms\n\n        return self\n\n    def __getitem__(self, index):\n        \"\"\"Get a single document or a slice of documents from this cursor.\n\n        Raises :class:`~pymongo.errors.InvalidOperation` if this\n        cursor has already been used.\n\n        To get a single document use an integral index, e.g.::\n\n          >>> db.test.find()[50]\n\n        An :class:`IndexError` will be raised if the index is negative\n        or greater than the amount of documents in this cursor. Any\n        limit previously applied to this cursor will be ignored.\n\n        To get a slice of documents use a slice index, e.g.::\n\n          >>> db.test.find()[20:25]\n\n        This will return this cursor with a limit of ``5`` and skip of\n        ``20`` applied.  Using a slice index will override any prior\n        limits or skips applied to this cursor (including those\n        applied through previous calls to this method). Raises\n        :class:`IndexError` when the slice has a step, a negative\n        start value, or a stop value less than or equal to the start\n        value.\n\n        :Parameters:\n          - `index`: An integer or slice index to be applied to this cursor\n        \"\"\"\n        self.__check_okay_to_chain()\n        self.__empty = False\n        if isinstance(index, slice):\n            if index.step is not None:\n                raise IndexError(\"Cursor instances do not support slice steps\")\n\n            skip = 0\n            if index.start is not None:\n                if index.start < 0:\n                    raise IndexError(\"Cursor instances do not support \"\n                                     \"negative indices\")\n                skip = index.start\n\n            if index.stop is not None:\n                limit = index.stop - skip\n                if limit < 0:\n                    raise IndexError(\"stop index must be greater than start \"\n                                     \"index for slice %r\" % index)\n                if limit == 0:\n                    self.__empty = True\n            else:\n                limit = 0\n\n            self.__skip = skip\n            self.__limit = limit\n            return self\n\n        if isinstance(index, integer_types):\n            if index < 0:\n                raise IndexError(\"Cursor instances do not support negative \"\n                                 \"indices\")\n            clone = self.clone()\n            clone.skip(index + self.__skip)\n            clone.limit(-1)  # use a hard limit\n            clone.__query_flags &= ~CursorType.TAILABLE_AWAIT  # PYTHON-1371\n            for doc in clone:\n                return doc\n            raise IndexError(\"no such item for Cursor instance\")\n        raise TypeError(\"index %r cannot be applied to Cursor \"\n                        \"instances\" % index)\n\n    def max_scan(self, max_scan):\n        \"\"\"**DEPRECATED** - Limit the number of documents to scan when\n        performing the query.\n\n        Raises :class:`~pymongo.errors.InvalidOperation` if this\n        cursor has already been used. Only the last :meth:`max_scan`\n        applied to this cursor has any effect.\n\n        :Parameters:\n          - `max_scan`: the maximum number of documents to scan\n\n        .. versionchanged:: 3.7\n          Deprecated :meth:`max_scan`. Support for this option is deprecated in\n          MongoDB 4.0. Use :meth:`max_time_ms` instead to limit server side\n          execution time.\n        \"\"\"\n        self.__check_okay_to_chain()\n        self.__max_scan = max_scan\n        return self\n\n    def max(self, spec):\n        \"\"\"Adds ``max`` operator that specifies upper bound for specific index.\n\n        When using ``max``, :meth:`~hint` should also be configured to ensure\n        the query uses the expected index and starting in MongoDB 4.2\n        :meth:`~hint` will be required.\n\n        :Parameters:\n          - `spec`: a list of field, limit pairs specifying the exclusive\n            upper bound for all keys of a specific index in order.\n\n        .. versionchanged:: 3.8\n           Deprecated cursors that use ``max`` without a :meth:`~hint`.\n\n        .. versionadded:: 2.7\n        \"\"\"\n        if not isinstance(spec, (list, tuple)):\n            raise TypeError(\"spec must be an instance of list or tuple\")\n\n        self.__check_okay_to_chain()\n        self.__max = SON(spec)\n        return self\n\n    def min(self, spec):\n        \"\"\"Adds ``min`` operator that specifies lower bound for specific index.\n\n        When using ``min``, :meth:`~hint` should also be configured to ensure\n        the query uses the expected index and starting in MongoDB 4.2\n        :meth:`~hint` will be required.\n\n        :Parameters:\n          - `spec`: a list of field, limit pairs specifying the inclusive\n            lower bound for all keys of a specific index in order.\n\n        .. versionchanged:: 3.8\n           Deprecated cursors that use ``min`` without a :meth:`~hint`.\n\n        .. versionadded:: 2.7\n        \"\"\"\n        if not isinstance(spec, (list, tuple)):\n            raise TypeError(\"spec must be an instance of list or tuple\")\n\n        self.__check_okay_to_chain()\n        self.__min = SON(spec)\n        return self\n\n    def sort(self, key_or_list, direction=None):\n        \"\"\"Sorts this cursor's results.\n\n        Pass a field name and a direction, either\n        :data:`~pymongo.ASCENDING` or :data:`~pymongo.DESCENDING`::\n\n            for doc in collection.find().sort('field', pymongo.ASCENDING):\n                print(doc)\n\n        To sort by multiple fields, pass a list of (key, direction) pairs::\n\n            for doc in collection.find().sort([\n                    ('field1', pymongo.ASCENDING),\n                    ('field2', pymongo.DESCENDING)]):\n                print(doc)\n\n        Beginning with MongoDB version 2.6, text search results can be\n        sorted by relevance::\n\n            cursor = db.test.find(\n                {'$text': {'$search': 'some words'}},\n                {'score': {'$meta': 'textScore'}})\n\n            # Sort by 'score' field.\n            cursor.sort([('score', {'$meta': 'textScore'})])\n\n            for doc in cursor:\n                print(doc)\n\n        Raises :class:`~pymongo.errors.InvalidOperation` if this cursor has\n        already been used. Only the last :meth:`sort` applied to this\n        cursor has any effect.\n\n        :Parameters:\n          - `key_or_list`: a single key or a list of (key, direction)\n            pairs specifying the keys to sort on\n          - `direction` (optional): only used if `key_or_list` is a single\n            key, if not given :data:`~pymongo.ASCENDING` is assumed\n        \"\"\"\n        self.__check_okay_to_chain()\n        keys = helpers._index_list(key_or_list, direction)\n        self.__ordering = helpers._index_document(keys)\n        return self\n\n    def count(self, with_limit_and_skip=False):\n        \"\"\"**DEPRECATED** - Get the size of the results set for this query.\n\n        The :meth:`count` method is deprecated and **not** supported in a\n        transaction. Please use\n        :meth:`~pymongo.collection.Collection.count_documents` instead.\n\n        Returns the number of documents in the results set for this query. Does\n        not take :meth:`limit` and :meth:`skip` into account by default - set\n        `with_limit_and_skip` to ``True`` if that is the desired behavior.\n        Raises :class:`~pymongo.errors.OperationFailure` on a database error.\n\n        When used with MongoDB >= 2.6, :meth:`~count` uses any :meth:`~hint`\n        applied to the query. In the following example the hint is passed to\n        the count command:\n\n          collection.find({'field': 'value'}).hint('field_1').count()\n\n        The :meth:`count` method obeys the\n        :attr:`~pymongo.collection.Collection.read_preference` of the\n        :class:`~pymongo.collection.Collection` instance on which\n        :meth:`~pymongo.collection.Collection.find` was called.\n\n        :Parameters:\n          - `with_limit_and_skip` (optional): take any :meth:`limit` or\n            :meth:`skip` that has been applied to this cursor into account when\n            getting the count\n\n        .. note:: The `with_limit_and_skip` parameter requires server\n           version **>= 1.1.4-**\n\n        .. versionchanged:: 3.7\n           Deprecated.\n\n        .. versionchanged:: 2.8\n           The :meth:`~count` method now supports :meth:`~hint`.\n        \"\"\"\n        warnings.warn(\"count is deprecated. Use Collection.count_documents \"\n                      \"instead.\", DeprecationWarning, stacklevel=2)\n        validate_boolean(\"with_limit_and_skip\", with_limit_and_skip)\n        cmd = SON([(\"count\", self.__collection.name),\n                   (\"query\", self.__spec)])\n        if self.__max_time_ms is not None:\n            cmd[\"maxTimeMS\"] = self.__max_time_ms\n        if self.__comment:\n            cmd[\"comment\"] = self.__comment\n\n        if self.__hint is not None:\n            cmd[\"hint\"] = self.__hint\n\n        if with_limit_and_skip:\n            if self.__limit:\n                cmd[\"limit\"] = self.__limit\n            if self.__skip:\n                cmd[\"skip\"] = self.__skip\n\n        return self.__collection._count(\n            cmd, self.__collation, session=self.__session)\n\n    def distinct(self, key):\n        \"\"\"Get a list of distinct values for `key` among all documents\n        in the result set of this query.\n\n        Raises :class:`TypeError` if `key` is not an instance of\n        :class:`basestring` (:class:`str` in python 3).\n\n        The :meth:`distinct` method obeys the\n        :attr:`~pymongo.collection.Collection.read_preference` of the\n        :class:`~pymongo.collection.Collection` instance on which\n        :meth:`~pymongo.collection.Collection.find` was called.\n\n        :Parameters:\n          - `key`: name of key for which we want to get the distinct values\n\n        .. seealso:: :meth:`pymongo.collection.Collection.distinct`\n        \"\"\"\n        options = {}\n        if self.__spec:\n            options[\"query\"] = self.__spec\n        if self.__max_time_ms is not None:\n            options['maxTimeMS'] = self.__max_time_ms\n        if self.__comment:\n            options['comment'] = self.__comment\n        if self.__collation is not None:\n            options['collation'] = self.__collation\n\n        return self.__collection.distinct(\n            key, session=self.__session, **options)\n\n    def explain(self):\n        \"\"\"Returns an explain plan record for this cursor.\n\n        .. note:: Starting with MongoDB 3.2 :meth:`explain` uses\n          the default verbosity mode of the `explain command\n          <https://docs.mongodb.com/manual/reference/command/explain/>`_,\n          ``allPlansExecution``. To use a different verbosity use\n          :meth:`~pymongo.database.Database.command` to run the explain\n          command directly.\n\n        .. mongodoc:: explain\n        \"\"\"\n        c = self.clone()\n        c.__explain = True\n\n        # always use a hard limit for explains\n        if c.__limit:\n            c.__limit = -abs(c.__limit)\n        return next(c)\n\n    def __set_hint(self, index):\n        if index is None:\n            self.__hint = None\n            return\n\n        if isinstance(index, string_type):\n            self.__hint = index\n        else:\n            self.__hint = helpers._index_document(index)\n\n    def hint(self, index):\n        \"\"\"Adds a 'hint', telling Mongo the proper index to use for the query.\n\n        Judicious use of hints can greatly improve query\n        performance. When doing a query on multiple fields (at least\n        one of which is indexed) pass the indexed field as a hint to\n        the query. Raises :class:`~pymongo.errors.OperationFailure` if the\n        provided hint requires an index that does not exist on this collection,\n        and raises :class:`~pymongo.errors.InvalidOperation` if this cursor has\n        already been used.\n\n        `index` should be an index as passed to\n        :meth:`~pymongo.collection.Collection.create_index`\n        (e.g. ``[('field', ASCENDING)]``) or the name of the index.\n        If `index` is ``None`` any existing hint for this query is\n        cleared. The last hint applied to this cursor takes precedence\n        over all others.\n\n        :Parameters:\n          - `index`: index to hint on (as an index specifier)\n\n        .. versionchanged:: 2.8\n           The :meth:`~hint` method accepts the name of the index.\n        \"\"\"\n        self.__check_okay_to_chain()\n        self.__set_hint(index)\n        return self\n\n    def comment(self, comment):\n        \"\"\"Adds a 'comment' to the cursor.\n\n        http://docs.mongodb.org/manual/reference/operator/comment/\n\n        :Parameters:\n          - `comment`: A string to attach to the query to help interpret and\n            trace the operation in the server logs and in profile data.\n\n        .. versionadded:: 2.7\n        \"\"\"\n        self.__check_okay_to_chain()\n        self.__comment = comment\n        return self\n\n    def where(self, code):\n        \"\"\"Adds a $where clause to this query.\n\n        The `code` argument must be an instance of :class:`basestring`\n        (:class:`str` in python 3) or :class:`~bson.code.Code`\n        containing a JavaScript expression. This expression will be\n        evaluated for each document scanned. Only those documents\n        for which the expression evaluates to *true* will be returned\n        as results. The keyword *this* refers to the object currently\n        being scanned.\n\n        Raises :class:`TypeError` if `code` is not an instance of\n        :class:`basestring` (:class:`str` in python 3). Raises\n        :class:`~pymongo.errors.InvalidOperation` if this\n        :class:`Cursor` has already been used. Only the last call to\n        :meth:`where` applied to a :class:`Cursor` has any effect.\n\n        :Parameters:\n          - `code`: JavaScript expression to use as a filter\n        \"\"\"\n        self.__check_okay_to_chain()\n        if not isinstance(code, Code):\n            code = Code(code)\n\n        self.__spec[\"$where\"] = code\n        return self\n\n    def collation(self, collation):\n        \"\"\"Adds a :class:`~pymongo.collation.Collation` to this query.\n\n        This option is only supported on MongoDB 3.4 and above.\n\n        Raises :exc:`TypeError` if `collation` is not an instance of\n        :class:`~pymongo.collation.Collation` or a ``dict``. Raises\n        :exc:`~pymongo.errors.InvalidOperation` if this :class:`Cursor` has\n        already been used. Only the last collation applied to this cursor has\n        any effect.\n\n        :Parameters:\n          - `collation`: An instance of :class:`~pymongo.collation.Collation`.\n        \"\"\"\n        self.__check_okay_to_chain()\n        self.__collation = validate_collation_or_none(collation)\n        return self\n\n    def __send_message(self, operation):\n        \"\"\"Send a query or getmore operation and handles the response.\n\n        If operation is ``None`` this is an exhaust cursor, which reads\n        the next result batch off the exhaust socket instead of\n        sending getMore messages to the server.\n\n        Can raise ConnectionFailure.\n        \"\"\"\n        client = self.__collection.database.client\n        # OP_MSG is required to support exhaust cursors with encryption.\n        if client._encrypter and self.__exhaust:\n            raise InvalidOperation(\n                \"exhaust cursors do not support auto encryption\")\n\n        try:\n            response = client._run_operation_with_response(\n                operation, self._unpack_response, exhaust=self.__exhaust,\n                address=self.__address)\n        except OperationFailure:\n            self.__killed = True\n\n            # Make sure exhaust socket is returned immediately, if necessary.\n            self.__die()\n\n            # If this is a tailable cursor the error is likely\n            # due to capped collection roll over. Setting\n            # self.__killed to True ensures Cursor.alive will be\n            # False. No need to re-raise.\n            if self.__query_flags & _QUERY_OPTIONS[\"tailable_cursor\"]:\n                return\n            raise\n        except NotMasterError:\n            # Don't send kill cursors to another server after a \"not master\"\n            # error. It's completely pointless.\n            self.__killed = True\n\n            # Make sure exhaust socket is returned immediately, if necessary.\n            self.__die()\n\n            raise\n        except ConnectionFailure:\n            # Don't try to send kill cursors on another socket\n            # or to another server. It can cause a _pinValue\n            # assertion on some server releases if we get here\n            # due to a socket timeout.\n            self.__killed = True\n            self.__die()\n            raise\n        except Exception:\n            # Close the cursor\n            self.__die()\n            raise\n\n        self.__address = response.address\n        if self.__exhaust and not self.__exhaust_mgr:\n            # 'response' is an ExhaustResponse.\n            self.__exhaust_mgr = _SocketManager(response.socket_info,\n                                                response.pool)\n\n        cmd_name = operation.name\n        docs = response.docs\n        if response.from_command:\n            if cmd_name != \"explain\":\n                cursor = docs[0]['cursor']\n                self.__id = cursor['id']\n                if cmd_name == 'find':\n                    documents = cursor['firstBatch']\n                else:\n                    documents = cursor['nextBatch']\n                self.__data = deque(documents)\n                self.__retrieved += len(documents)\n            else:\n                self.__id = 0\n                self.__data = deque(docs)\n                self.__retrieved += len(docs)\n        else:\n            self.__id = response.data.cursor_id\n            self.__data = deque(docs)\n            self.__retrieved += response.data.number_returned\n\n        if self.__id == 0:\n            self.__killed = True\n            # Don't wait for garbage collection to call __del__, return the\n            # socket and the session to the pool now.\n            self.__die()\n\n        if self.__limit and self.__id and self.__limit <= self.__retrieved:\n            self.__die()\n\n    def _unpack_response(self, response, cursor_id, codec_options,\n                         user_fields=None, legacy_response=False):\n        return response.unpack_response(cursor_id, codec_options, user_fields,\n                                        legacy_response)\n\n    def _read_preference(self):\n        if self.__read_preference is None:\n            # Save the read preference for getMore commands.\n            self.__read_preference = self.__collection._read_preference_for(\n                self.session)\n        return self.__read_preference\n\n    def _refresh(self):\n        \"\"\"Refreshes the cursor with more data from Mongo.\n\n        Returns the length of self.__data after refresh. Will exit early if\n        self.__data is already non-empty. Raises OperationFailure when the\n        cursor cannot be refreshed due to an error on the query.\n        \"\"\"\n        if len(self.__data) or self.__killed:\n            return len(self.__data)\n\n        if not self.__session:\n            self.__session = self.__collection.database.client._ensure_session()\n\n        if self.__id is None:  # Query\n            if (self.__min or self.__max) and not self.__hint:\n                warnings.warn(\"using a min/max query operator without \"\n                              \"specifying a Cursor.hint is deprecated. A \"\n                              \"hint will be required when using min/max in \"\n                              \"PyMongo 4.0\",\n                              DeprecationWarning, stacklevel=3)\n            q = self._query_class(self.__query_flags,\n                                  self.__collection.database.name,\n                                  self.__collection.name,\n                                  self.__skip,\n                                  self.__query_spec(),\n                                  self.__projection,\n                                  self.__codec_options,\n                                  self._read_preference(),\n                                  self.__limit,\n                                  self.__batch_size,\n                                  self.__read_concern,\n                                  self.__collation,\n                                  self.__session,\n                                  self.__collection.database.client)\n            self.__send_message(q)\n        elif self.__id:  # Get More\n            if self.__limit:\n                limit = self.__limit - self.__retrieved\n                if self.__batch_size:\n                    limit = min(limit, self.__batch_size)\n            else:\n                limit = self.__batch_size\n\n            # Exhaust cursors don't send getMore messages.\n            g = self._getmore_class(self.__collection.database.name,\n                                    self.__collection.name,\n                                    limit,\n                                    self.__id,\n                                    self.__codec_options,\n                                    self._read_preference(),\n                                    self.__session,\n                                    self.__collection.database.client,\n                                    self.__max_await_time_ms,\n                                    self.__exhaust_mgr)\n            self.__send_message(g)\n\n        return len(self.__data)\n\n    @property\n    def alive(self):\n        \"\"\"Does this cursor have the potential to return more data?\n\n        This is mostly useful with `tailable cursors\n        <http://www.mongodb.org/display/DOCS/Tailable+Cursors>`_\n        since they will stop iterating even though they *may* return more\n        results in the future.\n\n        With regular cursors, simply use a for loop instead of :attr:`alive`::\n\n            for doc in collection.find():\n                print(doc)\n\n        .. note:: Even if :attr:`alive` is True, :meth:`next` can raise\n          :exc:`StopIteration`. :attr:`alive` can also be True while iterating\n          a cursor from a failed server. In this case :attr:`alive` will\n          return False after :meth:`next` fails to retrieve the next batch\n          of results from the server.\n        \"\"\"\n        return bool(len(self.__data) or (not self.__killed))\n\n    @property\n    def cursor_id(self):\n        \"\"\"Returns the id of the cursor\n\n        Useful if you need to manage cursor ids and want to handle killing\n        cursors manually using\n        :meth:`~pymongo.mongo_client.MongoClient.kill_cursors`\n\n        .. versionadded:: 2.2\n        \"\"\"\n        return self.__id\n\n    @property\n    def address(self):\n        \"\"\"The (host, port) of the server used, or None.\n\n        .. versionchanged:: 3.0\n           Renamed from \"conn_id\".\n        \"\"\"\n        return self.__address\n\n    @property\n    def session(self):\n        \"\"\"The cursor's :class:`~pymongo.client_session.ClientSession`, or None.\n\n        .. versionadded:: 3.6\n        \"\"\"\n        if self.__explicit_session:\n            return self.__session\n\n    def __iter__(self):\n        return self\n\n    def next(self):\n        \"\"\"Advance the cursor.\"\"\"\n        if self.__empty:\n            raise StopIteration\n        if len(self.__data) or self._refresh():\n            if self.__manipulate:\n                _db = self.__collection.database\n                return _db._fix_outgoing(self.__data.popleft(),\n                                         self.__collection)\n            else:\n                return self.__data.popleft()\n        else:\n            raise StopIteration\n\n    __next__ = next\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        self.close()\n\n    def __copy__(self):\n        \"\"\"Support function for `copy.copy()`.\n\n        .. versionadded:: 2.4\n        \"\"\"\n        return self._clone(deepcopy=False)\n\n    def __deepcopy__(self, memo):\n        \"\"\"Support function for `copy.deepcopy()`.\n\n        .. versionadded:: 2.4\n        \"\"\"\n        return self._clone(deepcopy=True)\n\n    def _deepcopy(self, x, memo=None):\n        \"\"\"Deepcopy helper for the data dictionary or list.\n\n        Regular expressions cannot be deep copied but as they are immutable we\n        don't have to copy them when cloning.\n        \"\"\"\n        if not hasattr(x, 'items'):\n            y, is_list, iterator = [], True, enumerate(x)\n        else:\n            y, is_list, iterator = {}, False, iteritems(x)\n\n        if memo is None:\n            memo = {}\n        val_id = id(x)\n        if val_id in memo:\n            return memo.get(val_id)\n        memo[val_id] = y\n\n        for key, value in iterator:\n            if isinstance(value, (dict, list)) and not isinstance(value, SON):\n                value = self._deepcopy(value, memo)\n            elif not isinstance(value, RE_TYPE):\n                value = copy.deepcopy(value, memo)\n\n            if is_list:\n                y.append(value)\n            else:\n                if not isinstance(key, RE_TYPE):\n                    key = copy.deepcopy(key, memo)\n                y[key] = value\n        return y\n\n\nclass RawBatchCursor(Cursor):\n    \"\"\"A cursor / iterator over raw batches of BSON data from a query result.\"\"\"\n\n    _query_class = _RawBatchQuery\n    _getmore_class = _RawBatchGetMore\n\n    def __init__(self, *args, **kwargs):\n        \"\"\"Create a new cursor / iterator over raw batches of BSON data.\n\n        Should not be called directly by application developers -\n        see :meth:`~pymongo.collection.Collection.find_raw_batches`\n        instead.\n\n        .. mongodoc:: cursors\n        \"\"\"\n        manipulate = kwargs.get('manipulate')\n        kwargs['manipulate'] = False\n        super(RawBatchCursor, self).__init__(*args, **kwargs)\n\n        # Throw only after cursor's initialized, to prevent errors in __del__.\n        if manipulate:\n            raise InvalidOperation(\n                \"Cannot use RawBatchCursor with manipulate=True\")\n\n    def _unpack_response(self, response, cursor_id, codec_options,\n                         user_fields=None, legacy_response=False):\n        return response.raw_response(cursor_id)\n\n    def explain(self):\n        \"\"\"Returns an explain plan record for this cursor.\n\n        .. mongodoc:: explain\n        \"\"\"\n        clone = self._clone(deepcopy=True, base=Cursor(self.collection))\n        return clone.explain()\n\n    def __getitem__(self, index):\n        raise InvalidOperation(\"Cannot call __getitem__ on RawBatchCursor\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/cursor_manager.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"DEPRECATED - A manager to handle when cursors are killed after they are\nclosed.\n\nNew cursor managers should be defined as subclasses of CursorManager and can be\ninstalled on a client by calling\n:meth:`~pymongo.mongo_client.MongoClient.set_cursor_manager`.\n\n.. versionchanged:: 3.3\n   Deprecated, for real this time.\n\n.. versionchanged:: 3.0\n   Undeprecated. :meth:`~pymongo.cursor_manager.CursorManager.close` now\n   requires an `address` argument. The ``BatchCursorManager`` class is removed.\n\"\"\"\n\nimport warnings\nimport weakref\nfrom bson.py3compat import integer_types\n\n\nclass CursorManager(object):\n    \"\"\"DEPRECATED - The cursor manager base class.\"\"\"\n\n    def __init__(self, client):\n        \"\"\"Instantiate the manager.\n\n        :Parameters:\n          - `client`: a MongoClient\n        \"\"\"\n        warnings.warn(\n            \"Cursor managers are deprecated.\",\n            DeprecationWarning,\n            stacklevel=2)\n        self.__client = weakref.ref(client)\n\n    def close(self, cursor_id, address):\n        \"\"\"Kill a cursor.\n\n        Raises TypeError if cursor_id is not an instance of (int, long).\n\n        :Parameters:\n          - `cursor_id`: cursor id to close\n          - `address`: the cursor's server's (host, port) pair\n\n        .. versionchanged:: 3.0\n           Now requires an `address` argument.\n        \"\"\"\n        if not isinstance(cursor_id, integer_types):\n            raise TypeError(\"cursor_id must be an integer\")\n\n        self.__client().kill_cursors([cursor_id], address)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/database.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Database level operations.\"\"\"\n\nimport warnings\n\nfrom bson.code import Code\nfrom bson.codec_options import DEFAULT_CODEC_OPTIONS\nfrom bson.dbref import DBRef\nfrom bson.py3compat import iteritems, string_type, _unicode\nfrom bson.son import SON\nfrom pymongo import auth, common\nfrom pymongo.aggregation import _DatabaseAggregationCommand\nfrom pymongo.change_stream import DatabaseChangeStream\nfrom pymongo.collection import Collection\nfrom pymongo.command_cursor import CommandCursor\nfrom pymongo.errors import (CollectionInvalid,\n                            ConfigurationError,\n                            InvalidName,\n                            OperationFailure)\nfrom pymongo.message import _first_batch\nfrom pymongo.read_preferences import ReadPreference\nfrom pymongo.son_manipulator import SONManipulator\nfrom pymongo.write_concern import DEFAULT_WRITE_CONCERN\n\n\n_INDEX_REGEX = {\"name\": {\"$regex\": r\"^(?!.*\\$)\"}}\n_SYSTEM_FILTER = {\"filter\": {\"name\": {\"$regex\": r\"^(?!system\\.)\"}}}\n\n\ndef _check_name(name):\n    \"\"\"Check if a database name is valid.\n    \"\"\"\n    if not name:\n        raise InvalidName(\"database name cannot be the empty string\")\n\n    for invalid_char in [' ', '.', '$', '/', '\\\\', '\\x00', '\"']:\n        if invalid_char in name:\n            raise InvalidName(\"database names cannot contain the \"\n                              \"character %r\" % invalid_char)\n\n\nclass Database(common.BaseObject):\n    \"\"\"A Mongo database.\n    \"\"\"\n\n    def __init__(self, client, name, codec_options=None, read_preference=None,\n                 write_concern=None, read_concern=None):\n        \"\"\"Get a database by client and name.\n\n        Raises :class:`TypeError` if `name` is not an instance of\n        :class:`basestring` (:class:`str` in python 3). Raises\n        :class:`~pymongo.errors.InvalidName` if `name` is not a valid\n        database name.\n\n        :Parameters:\n          - `client`: A :class:`~pymongo.mongo_client.MongoClient` instance.\n          - `name`: The database name.\n          - `codec_options` (optional): An instance of\n            :class:`~bson.codec_options.CodecOptions`. If ``None`` (the\n            default) client.codec_options is used.\n          - `read_preference` (optional): The read preference to use. If\n            ``None`` (the default) client.read_preference is used.\n          - `write_concern` (optional): An instance of\n            :class:`~pymongo.write_concern.WriteConcern`. If ``None`` (the\n            default) client.write_concern is used.\n          - `read_concern` (optional): An instance of\n            :class:`~pymongo.read_concern.ReadConcern`. If ``None`` (the\n            default) client.read_concern is used.\n\n        .. mongodoc:: databases\n\n        .. versionchanged:: 3.2\n           Added the read_concern option.\n\n        .. versionchanged:: 3.0\n           Added the codec_options, read_preference, and write_concern options.\n           :class:`~pymongo.database.Database` no longer returns an instance\n           of :class:`~pymongo.collection.Collection` for attribute names\n           with leading underscores. You must use dict-style lookups instead::\n\n               db['__my_collection__']\n\n           Not:\n\n               db.__my_collection__\n        \"\"\"\n        super(Database, self).__init__(\n            codec_options or client.codec_options,\n            read_preference or client.read_preference,\n            write_concern or client.write_concern,\n            read_concern or client.read_concern)\n\n        if not isinstance(name, string_type):\n            raise TypeError(\"name must be an instance \"\n                            \"of %s\" % (string_type.__name__,))\n\n        if name != '$external':\n            _check_name(name)\n\n        self.__name = _unicode(name)\n        self.__client = client\n\n        self.__incoming_manipulators = []\n        self.__incoming_copying_manipulators = []\n        self.__outgoing_manipulators = []\n        self.__outgoing_copying_manipulators = []\n\n    def add_son_manipulator(self, manipulator):\n        \"\"\"Add a new son manipulator to this database.\n\n        **DEPRECATED** - `add_son_manipulator` is deprecated.\n\n        .. versionchanged:: 3.0\n          Deprecated add_son_manipulator.\n        \"\"\"\n        warnings.warn(\"add_son_manipulator is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n        base = SONManipulator()\n        def method_overwritten(instance, method):\n            \"\"\"Test if this method has been overridden.\"\"\"\n            return (getattr(\n                instance, method).__func__ != getattr(base, method).__func__)\n\n        if manipulator.will_copy():\n            if method_overwritten(manipulator, \"transform_incoming\"):\n                self.__incoming_copying_manipulators.insert(0, manipulator)\n            if method_overwritten(manipulator, \"transform_outgoing\"):\n                self.__outgoing_copying_manipulators.insert(0, manipulator)\n        else:\n            if method_overwritten(manipulator, \"transform_incoming\"):\n                self.__incoming_manipulators.insert(0, manipulator)\n            if method_overwritten(manipulator, \"transform_outgoing\"):\n                self.__outgoing_manipulators.insert(0, manipulator)\n\n    @property\n    def system_js(self):\n        \"\"\"**DEPRECATED**: :class:`SystemJS` helper for this :class:`Database`.\n\n        See the documentation for :class:`SystemJS` for more details.\n        \"\"\"\n        return SystemJS(self)\n\n    @property\n    def client(self):\n        \"\"\"The client instance for this :class:`Database`.\"\"\"\n        return self.__client\n\n    @property\n    def name(self):\n        \"\"\"The name of this :class:`Database`.\"\"\"\n        return self.__name\n\n    @property\n    def incoming_manipulators(self):\n        \"\"\"**DEPRECATED**: All incoming SON manipulators.\n\n        .. versionchanged:: 3.5\n          Deprecated.\n\n        .. versionadded:: 2.0\n        \"\"\"\n        warnings.warn(\"Database.incoming_manipulators() is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n\n        return [manipulator.__class__.__name__\n                for manipulator in self.__incoming_manipulators]\n\n    @property\n    def incoming_copying_manipulators(self):\n        \"\"\"**DEPRECATED**: All incoming SON copying manipulators.\n\n        .. versionchanged:: 3.5\n          Deprecated.\n\n        .. versionadded:: 2.0\n        \"\"\"\n        warnings.warn(\"Database.incoming_copying_manipulators() is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n\n        return [manipulator.__class__.__name__\n                for manipulator in self.__incoming_copying_manipulators]\n\n    @property\n    def outgoing_manipulators(self):\n        \"\"\"**DEPRECATED**: All outgoing SON manipulators.\n\n        .. versionchanged:: 3.5\n          Deprecated.\n\n        .. versionadded:: 2.0\n        \"\"\"\n        warnings.warn(\"Database.outgoing_manipulators() is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n\n        return [manipulator.__class__.__name__\n                for manipulator in self.__outgoing_manipulators]\n\n    @property\n    def outgoing_copying_manipulators(self):\n        \"\"\"**DEPRECATED**: All outgoing SON copying manipulators.\n\n        .. versionchanged:: 3.5\n          Deprecated.\n\n        .. versionadded:: 2.0\n        \"\"\"\n        warnings.warn(\"Database.outgoing_copying_manipulators() is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n\n        return [manipulator.__class__.__name__\n                for manipulator in self.__outgoing_copying_manipulators]\n\n    def with_options(self, codec_options=None, read_preference=None,\n                     write_concern=None, read_concern=None):\n        \"\"\"Get a clone of this database changing the specified settings.\n\n          >>> db1.read_preference\n          Primary()\n          >>> from pymongo import ReadPreference\n          >>> db2 = db1.with_options(read_preference=ReadPreference.SECONDARY)\n          >>> db1.read_preference\n          Primary()\n          >>> db2.read_preference\n          Secondary(tag_sets=None)\n\n        :Parameters:\n          - `codec_options` (optional): An instance of\n            :class:`~bson.codec_options.CodecOptions`. If ``None`` (the\n            default) the :attr:`codec_options` of this :class:`Collection`\n            is used.\n          - `read_preference` (optional): The read preference to use. If\n            ``None`` (the default) the :attr:`read_preference` of this\n            :class:`Collection` is used. See :mod:`~pymongo.read_preferences`\n            for options.\n          - `write_concern` (optional): An instance of\n            :class:`~pymongo.write_concern.WriteConcern`. If ``None`` (the\n            default) the :attr:`write_concern` of this :class:`Collection`\n            is used.\n          - `read_concern` (optional): An instance of\n            :class:`~pymongo.read_concern.ReadConcern`. If ``None`` (the\n            default) the :attr:`read_concern` of this :class:`Collection`\n            is used.\n\n        .. versionadded:: 3.8\n        \"\"\"\n        return Database(self.client,\n                        self.__name,\n                        codec_options or self.codec_options,\n                        read_preference or self.read_preference,\n                        write_concern or self.write_concern,\n                        read_concern or self.read_concern)\n\n    def __eq__(self, other):\n        if isinstance(other, Database):\n            return (self.__client == other.client and\n                    self.__name == other.name)\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __repr__(self):\n        return \"Database(%r, %r)\" % (self.__client, self.__name)\n\n    def __getattr__(self, name):\n        \"\"\"Get a collection of this database by name.\n\n        Raises InvalidName if an invalid collection name is used.\n\n        :Parameters:\n          - `name`: the name of the collection to get\n        \"\"\"\n        if name.startswith('_'):\n            raise AttributeError(\n                \"Database has no attribute %r. To access the %s\"\n                \" collection, use database[%r].\" % (name, name, name))\n        return self.__getitem__(name)\n\n    def __getitem__(self, name):\n        \"\"\"Get a collection of this database by name.\n\n        Raises InvalidName if an invalid collection name is used.\n\n        :Parameters:\n          - `name`: the name of the collection to get\n        \"\"\"\n        return Collection(self, name)\n\n    def get_collection(self, name, codec_options=None, read_preference=None,\n                       write_concern=None, read_concern=None):\n        \"\"\"Get a :class:`~pymongo.collection.Collection` with the given name\n        and options.\n\n        Useful for creating a :class:`~pymongo.collection.Collection` with\n        different codec options, read preference, and/or write concern from\n        this :class:`Database`.\n\n          >>> db.read_preference\n          Primary()\n          >>> coll1 = db.test\n          >>> coll1.read_preference\n          Primary()\n          >>> from pymongo import ReadPreference\n          >>> coll2 = db.get_collection(\n          ...     'test', read_preference=ReadPreference.SECONDARY)\n          >>> coll2.read_preference\n          Secondary(tag_sets=None)\n\n        :Parameters:\n          - `name`: The name of the collection - a string.\n          - `codec_options` (optional): An instance of\n            :class:`~bson.codec_options.CodecOptions`. If ``None`` (the\n            default) the :attr:`codec_options` of this :class:`Database` is\n            used.\n          - `read_preference` (optional): The read preference to use. If\n            ``None`` (the default) the :attr:`read_preference` of this\n            :class:`Database` is used. See :mod:`~pymongo.read_preferences`\n            for options.\n          - `write_concern` (optional): An instance of\n            :class:`~pymongo.write_concern.WriteConcern`. If ``None`` (the\n            default) the :attr:`write_concern` of this :class:`Database` is\n            used.\n          - `read_concern` (optional): An instance of\n            :class:`~pymongo.read_concern.ReadConcern`. If ``None`` (the\n            default) the :attr:`read_concern` of this :class:`Database` is\n            used.\n        \"\"\"\n        return Collection(\n            self, name, False, codec_options, read_preference,\n            write_concern, read_concern)\n\n    def create_collection(self, name, codec_options=None,\n                          read_preference=None, write_concern=None,\n                          read_concern=None, session=None, **kwargs):\n        \"\"\"Create a new :class:`~pymongo.collection.Collection` in this\n        database.\n\n        Normally collection creation is automatic. This method should\n        only be used to specify options on\n        creation. :class:`~pymongo.errors.CollectionInvalid` will be\n        raised if the collection already exists.\n\n        Options should be passed as keyword arguments to this method. Supported\n        options vary with MongoDB release. Some examples include:\n\n          - \"size\": desired initial size for the collection (in\n            bytes). For capped collections this size is the max\n            size of the collection.\n          - \"capped\": if True, this is a capped collection\n          - \"max\": maximum number of objects if capped (optional)\n\n        See the MongoDB documentation for a full list of supported options by\n        server version.\n\n        :Parameters:\n          - `name`: the name of the collection to create\n          - `codec_options` (optional): An instance of\n            :class:`~bson.codec_options.CodecOptions`. If ``None`` (the\n            default) the :attr:`codec_options` of this :class:`Database` is\n            used.\n          - `read_preference` (optional): The read preference to use. If\n            ``None`` (the default) the :attr:`read_preference` of this\n            :class:`Database` is used.\n          - `write_concern` (optional): An instance of\n            :class:`~pymongo.write_concern.WriteConcern`. If ``None`` (the\n            default) the :attr:`write_concern` of this :class:`Database` is\n            used.\n          - `read_concern` (optional): An instance of\n            :class:`~pymongo.read_concern.ReadConcern`. If ``None`` (the\n            default) the :attr:`read_concern` of this :class:`Database` is\n            used.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): additional keyword arguments will\n            be passed as options for the create collection command\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.4\n           Added the collation option.\n\n        .. versionchanged:: 3.0\n           Added the codec_options, read_preference, and write_concern options.\n\n        .. versionchanged:: 2.2\n           Removed deprecated argument: options\n        \"\"\"\n        with self.__client._tmp_session(session) as s:\n            if name in self.list_collection_names(\n                    filter={\"name\": name}, session=s):\n                raise CollectionInvalid(\"collection %s already exists\" % name)\n\n            return Collection(self, name, True, codec_options,\n                              read_preference, write_concern,\n                              read_concern, session=s, **kwargs)\n\n    def _apply_incoming_manipulators(self, son, collection):\n        \"\"\"Apply incoming manipulators to `son`.\"\"\"\n        for manipulator in self.__incoming_manipulators:\n            son = manipulator.transform_incoming(son, collection)\n        return son\n\n    def _apply_incoming_copying_manipulators(self, son, collection):\n        \"\"\"Apply incoming copying manipulators to `son`.\"\"\"\n        for manipulator in self.__incoming_copying_manipulators:\n            son = manipulator.transform_incoming(son, collection)\n        return son\n\n    def _fix_incoming(self, son, collection):\n        \"\"\"Apply manipulators to an incoming SON object before it gets stored.\n\n        :Parameters:\n          - `son`: the son object going into the database\n          - `collection`: the collection the son object is being saved in\n        \"\"\"\n        son = self._apply_incoming_manipulators(son, collection)\n        son = self._apply_incoming_copying_manipulators(son, collection)\n        return son\n\n    def _fix_outgoing(self, son, collection):\n        \"\"\"Apply manipulators to a SON object as it comes out of the database.\n\n        :Parameters:\n          - `son`: the son object coming out of the database\n          - `collection`: the collection the son object was saved in\n        \"\"\"\n        for manipulator in reversed(self.__outgoing_manipulators):\n            son = manipulator.transform_outgoing(son, collection)\n        for manipulator in reversed(self.__outgoing_copying_manipulators):\n            son = manipulator.transform_outgoing(son, collection)\n        return son\n\n    def aggregate(self, pipeline, session=None, **kwargs):\n        \"\"\"Perform a database-level aggregation.\n\n        See the `aggregation pipeline`_ documentation for a list of stages\n        that are supported.\n\n        Introduced in MongoDB 3.6.\n\n        .. code-block:: python\n\n           # Lists all operations currently running on the server.\n           with client.admin.aggregate([{\"$currentOp\": {}}]) as cursor:\n               for operation in cursor:\n                   print(operation)\n\n        All optional `aggregate command`_ parameters should be passed as\n        keyword arguments to this method. Valid options include, but are not\n        limited to:\n\n          - `allowDiskUse` (bool): Enables writing to temporary files. When set\n            to True, aggregation stages can write data to the _tmp subdirectory\n            of the --dbpath directory. The default is False.\n          - `maxTimeMS` (int): The maximum amount of time to allow the operation\n            to run in milliseconds.\n          - `batchSize` (int): The maximum number of documents to return per\n            batch. Ignored if the connected mongod or mongos does not support\n            returning aggregate results using a cursor.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`.\n\n        The :meth:`aggregate` method obeys the :attr:`read_preference` of this\n        :class:`Database`, except when ``$out`` or ``$merge`` are used, in\n        which case  :attr:`~pymongo.read_preferences.ReadPreference.PRIMARY`\n        is used.\n\n        .. note:: This method does not support the 'explain' option. Please\n           use :meth:`~pymongo.database.Database.command` instead.\n\n        .. note:: The :attr:`~pymongo.database.Database.write_concern` of\n           this collection is automatically applied to this operation.\n\n        :Parameters:\n          - `pipeline`: a list of aggregation pipeline stages\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): See list of options above.\n\n        :Returns:\n          A :class:`~pymongo.command_cursor.CommandCursor` over the result\n          set.\n\n        .. versionadded:: 3.9\n\n        .. _aggregation pipeline:\n            https://docs.mongodb.com/manual/reference/operator/aggregation-pipeline\n\n        .. _aggregate command:\n            https://docs.mongodb.com/manual/reference/command/aggregate\n        \"\"\"\n        with self.client._tmp_session(session, close=False) as s:\n            cmd = _DatabaseAggregationCommand(\n                self, CommandCursor, pipeline, kwargs, session is not None,\n                user_fields={'cursor': {'firstBatch': 1}})\n            return self.client._retryable_read(\n                cmd.get_cursor, cmd.get_read_preference(s), s,\n                retryable=not cmd._performs_write)\n\n    def watch(self, pipeline=None, full_document=None, resume_after=None,\n              max_await_time_ms=None, batch_size=None, collation=None,\n              start_at_operation_time=None, session=None, start_after=None):\n        \"\"\"Watch changes on this database.\n\n        Performs an aggregation with an implicit initial ``$changeStream``\n        stage and returns a\n        :class:`~pymongo.change_stream.DatabaseChangeStream` cursor which\n        iterates over changes on all collections in this database.\n\n        Introduced in MongoDB 4.0.\n\n        .. code-block:: python\n\n           with db.watch() as stream:\n               for change in stream:\n                   print(change)\n\n        The :class:`~pymongo.change_stream.DatabaseChangeStream` iterable\n        blocks until the next change document is returned or an error is\n        raised. If the\n        :meth:`~pymongo.change_stream.DatabaseChangeStream.next` method\n        encounters a network error when retrieving a batch from the server,\n        it will automatically attempt to recreate the cursor such that no\n        change events are missed. Any error encountered during the resume\n        attempt indicates there may be an outage and will be raised.\n\n        .. code-block:: python\n\n            try:\n                with db.watch(\n                        [{'$match': {'operationType': 'insert'}}]) as stream:\n                    for insert_change in stream:\n                        print(insert_change)\n            except pymongo.errors.PyMongoError:\n                # The ChangeStream encountered an unrecoverable error or the\n                # resume attempt failed to recreate the cursor.\n                logging.error('...')\n\n        For a precise description of the resume process see the\n        `change streams specification`_.\n\n        :Parameters:\n          - `pipeline` (optional): A list of aggregation pipeline stages to\n            append to an initial ``$changeStream`` stage. Not all\n            pipeline stages are valid after a ``$changeStream`` stage, see the\n            MongoDB documentation on change streams for the supported stages.\n          - `full_document` (optional): The fullDocument to pass as an option\n            to the ``$changeStream`` stage. Allowed values: 'updateLookup'.\n            When set to 'updateLookup', the change notification for partial\n            updates will include both a delta describing the changes to the\n            document, as well as a copy of the entire document that was\n            changed from some time after the change occurred.\n          - `resume_after` (optional): A resume token. If provided, the\n            change stream will start returning changes that occur directly\n            after the operation specified in the resume token. A resume token\n            is the _id value of a change document.\n          - `max_await_time_ms` (optional): The maximum time in milliseconds\n            for the server to wait for changes before responding to a getMore\n            operation.\n          - `batch_size` (optional): The maximum number of documents to return\n            per batch.\n          - `collation` (optional): The :class:`~pymongo.collation.Collation`\n            to use for the aggregation.\n          - `start_at_operation_time` (optional): If provided, the resulting\n            change stream will only return changes that occurred at or after\n            the specified :class:`~bson.timestamp.Timestamp`. Requires\n            MongoDB >= 4.0.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `start_after` (optional): The same as `resume_after` except that\n            `start_after` can resume notifications after an invalidate event.\n            This option and `resume_after` are mutually exclusive.\n\n        :Returns:\n          A :class:`~pymongo.change_stream.DatabaseChangeStream` cursor.\n\n        .. versionchanged:: 3.9\n           Added the ``start_after`` parameter.\n\n        .. versionadded:: 3.7\n\n        .. mongodoc:: changeStreams\n\n        .. _change streams specification:\n            https://github.com/mongodb/specifications/blob/master/source/change-streams/change-streams.rst\n        \"\"\"\n        return DatabaseChangeStream(\n            self, pipeline, full_document, resume_after, max_await_time_ms,\n            batch_size, collation, start_at_operation_time, session,\n            start_after)\n\n    def _command(self, sock_info, command, slave_ok=False, value=1, check=True,\n                 allowable_errors=None, read_preference=ReadPreference.PRIMARY,\n                 codec_options=DEFAULT_CODEC_OPTIONS,\n                 write_concern=None,\n                 parse_write_concern_error=False, session=None, **kwargs):\n        \"\"\"Internal command helper.\"\"\"\n        if isinstance(command, string_type):\n            command = SON([(command, value)])\n\n        command.update(kwargs)\n        with self.__client._tmp_session(session) as s:\n            return sock_info.command(\n                self.__name,\n                command,\n                slave_ok,\n                read_preference,\n                codec_options,\n                check,\n                allowable_errors,\n                write_concern=write_concern,\n                parse_write_concern_error=parse_write_concern_error,\n                session=s,\n                client=self.__client)\n\n    def command(self, command, value=1, check=True,\n                allowable_errors=None, read_preference=None,\n                codec_options=DEFAULT_CODEC_OPTIONS, session=None, **kwargs):\n        \"\"\"Issue a MongoDB command.\n\n        Send command `command` to the database and return the\n        response. If `command` is an instance of :class:`basestring`\n        (:class:`str` in python 3) then the command {`command`: `value`}\n        will be sent. Otherwise, `command` must be an instance of\n        :class:`dict` and will be sent as is.\n\n        Any additional keyword arguments will be added to the final\n        command document before it is sent.\n\n        For example, a command like ``{buildinfo: 1}`` can be sent\n        using:\n\n        >>> db.command(\"buildinfo\")\n\n        For a command where the value matters, like ``{collstats:\n        collection_name}`` we can do:\n\n        >>> db.command(\"collstats\", collection_name)\n\n        For commands that take additional arguments we can use\n        kwargs. So ``{filemd5: object_id, root: file_root}`` becomes:\n\n        >>> db.command(\"filemd5\", object_id, root=file_root)\n\n        :Parameters:\n          - `command`: document representing the command to be issued,\n            or the name of the command (for simple commands only).\n\n            .. note:: the order of keys in the `command` document is\n               significant (the \"verb\" must come first), so commands\n               which require multiple keys (e.g. `findandmodify`)\n               should use an instance of :class:`~bson.son.SON` or\n               a string and kwargs instead of a Python `dict`.\n\n          - `value` (optional): value to use for the command verb when\n            `command` is passed as a string\n          - `check` (optional): check the response for errors, raising\n            :class:`~pymongo.errors.OperationFailure` if there are any\n          - `allowable_errors`: if `check` is ``True``, error messages\n            in this list will be ignored by error-checking\n          - `read_preference` (optional): The read preference for this\n            operation. See :mod:`~pymongo.read_preferences` for options.\n            If the provided `session` is in a transaction, defaults to the\n            read preference configured for the transaction.\n            Otherwise, defaults to\n            :attr:`~pymongo.read_preferences.ReadPreference.PRIMARY`.\n          - `codec_options`: A :class:`~bson.codec_options.CodecOptions`\n            instance.\n          - `session` (optional): A\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): additional keyword arguments will\n            be added to the command document before it is sent\n\n        .. note:: :meth:`command` does **not** obey this Database's\n           :attr:`read_preference` or :attr:`codec_options`. You must use the\n           `read_preference` and `codec_options` parameters instead.\n\n        .. note:: :meth:`command` does **not** apply any custom TypeDecoders\n           when decoding the command response.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.0\n           Removed the `as_class`, `fields`, `uuid_subtype`, `tag_sets`,\n           and `secondary_acceptable_latency_ms` option.\n           Removed `compile_re` option: PyMongo now always represents BSON\n           regular expressions as :class:`~bson.regex.Regex` objects. Use\n           :meth:`~bson.regex.Regex.try_compile` to attempt to convert from a\n           BSON regular expression to a Python regular expression object.\n           Added the `codec_options` parameter.\n\n        .. versionchanged:: 2.7\n           Added `compile_re` option. If set to False, PyMongo represented BSON\n           regular expressions as :class:`~bson.regex.Regex` objects instead of\n           attempting to compile BSON regular expressions as Python native\n           regular expressions, thus preventing errors for some incompatible\n           patterns, see `PYTHON-500`_.\n\n        .. versionchanged:: 2.3\n           Added `tag_sets` and `secondary_acceptable_latency_ms` options.\n        .. versionchanged:: 2.2\n           Added support for `as_class` - the class you want to use for\n           the resulting documents\n\n        .. _PYTHON-500: https://jira.mongodb.org/browse/PYTHON-500\n\n        .. mongodoc:: commands\n        \"\"\"\n        if read_preference is None:\n            read_preference = ((session and session._txn_read_preference())\n                               or ReadPreference.PRIMARY)\n        with self.__client._socket_for_reads(\n                read_preference, session) as (sock_info, slave_ok):\n            return self._command(sock_info, command, slave_ok, value,\n                                 check, allowable_errors, read_preference,\n                                 codec_options, session=session, **kwargs)\n\n    def _retryable_read_command(self, command, value=1, check=True,\n                allowable_errors=None, read_preference=None,\n                codec_options=DEFAULT_CODEC_OPTIONS, session=None, **kwargs):\n        \"\"\"Same as command but used for retryable read commands.\"\"\"\n        if read_preference is None:\n            read_preference = ((session and session._txn_read_preference())\n                               or ReadPreference.PRIMARY)\n\n        def _cmd(session, server, sock_info, slave_ok):\n            return self._command(sock_info, command, slave_ok, value,\n                                 check, allowable_errors, read_preference,\n                                 codec_options, session=session, **kwargs)\n\n        return self.__client._retryable_read(\n            _cmd, read_preference, session)\n\n    def _list_collections(self, sock_info, slave_okay, session,\n                          read_preference, **kwargs):\n        \"\"\"Internal listCollections helper.\"\"\"\n\n        coll = self.get_collection(\n            \"$cmd\", read_preference=read_preference)\n        if sock_info.max_wire_version > 2:\n            cmd = SON([(\"listCollections\", 1),\n                       (\"cursor\", {})])\n            cmd.update(kwargs)\n            with self.__client._tmp_session(\n                    session, close=False) as tmp_session:\n                cursor = self._command(\n                    sock_info, cmd, slave_okay,\n                    read_preference=read_preference,\n                    session=tmp_session)[\"cursor\"]\n                return CommandCursor(\n                    coll,\n                    cursor,\n                    sock_info.address,\n                    session=tmp_session,\n                    explicit_session=session is not None)\n        else:\n            match = _INDEX_REGEX\n            if \"filter\" in kwargs:\n                match = {\"$and\": [_INDEX_REGEX, kwargs[\"filter\"]]}\n            dblen = len(self.name.encode(\"utf8\") + b\".\")\n            pipeline = [\n                {\"$project\": {\"name\": {\"$substr\": [\"$name\", dblen, -1]},\n                              \"options\": 1}},\n                {\"$match\": match}\n            ]\n            cmd = SON([(\"aggregate\", \"system.namespaces\"),\n                       (\"pipeline\", pipeline),\n                       (\"cursor\", kwargs.get(\"cursor\", {}))])\n            cursor = self._command(sock_info, cmd, slave_okay)[\"cursor\"]\n            return CommandCursor(coll, cursor, sock_info.address)\n\n    def list_collections(self, session=None, filter=None, **kwargs):\n        \"\"\"Get a cursor over the collectons of this database.\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `filter` (optional):  A query document to filter the list of\n            collections returned from the listCollections command.\n          - `**kwargs` (optional): Optional parameters of the\n            `listCollections command\n            <https://docs.mongodb.com/manual/reference/command/listCollections/>`_\n            can be passed as keyword arguments to this method. The supported\n            options differ by server version.\n\n        :Returns:\n          An instance of :class:`~pymongo.command_cursor.CommandCursor`.\n\n        .. versionadded:: 3.6\n        \"\"\"\n        if filter is not None:\n            kwargs['filter'] = filter\n        read_pref = ((session and session._txn_read_preference())\n                     or ReadPreference.PRIMARY)\n\n        def _cmd(session, server, sock_info, slave_okay):\n            return self._list_collections(\n                sock_info, slave_okay, session, read_preference=read_pref,\n                **kwargs)\n\n        return self.__client._retryable_read(\n            _cmd, read_pref, session)\n\n    def list_collection_names(self, session=None, filter=None, **kwargs):\n        \"\"\"Get a list of all the collection names in this database.\n\n        For example, to list all non-system collections::\n\n            filter = {\"name\": {\"$regex\": r\"^(?!system\\.)\"}}\n            db.list_collection_names(filter=filter)\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `filter` (optional):  A query document to filter the list of\n            collections returned from the listCollections command.\n          - `**kwargs` (optional): Optional parameters of the\n            `listCollections command\n            <https://docs.mongodb.com/manual/reference/command/listCollections/>`_\n            can be passed as keyword arguments to this method. The supported\n            options differ by server version.\n\n        .. versionchanged:: 3.8\n           Added the ``filter`` and ``**kwargs`` parameters.\n\n        .. versionadded:: 3.6\n        \"\"\"\n        if filter is None:\n            kwargs[\"nameOnly\"] = True\n        else:\n            # The enumerate collections spec states that \"drivers MUST NOT set\n            # nameOnly if a filter specifies any keys other than name.\"\n            common.validate_is_mapping(\"filter\", filter)\n            kwargs[\"filter\"] = filter\n            if not filter or (len(filter) == 1 and \"name\" in filter):\n                kwargs[\"nameOnly\"] = True\n\n        return [result[\"name\"]\n                for result in self.list_collections(session=session, **kwargs)]\n\n    def collection_names(self, include_system_collections=True,\n                         session=None):\n        \"\"\"**DEPRECATED**: Get a list of all the collection names in this\n        database.\n\n        :Parameters:\n          - `include_system_collections` (optional): if ``False`` list\n            will not include system collections (e.g ``system.indexes``)\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.7\n           Deprecated. Use :meth:`list_collection_names` instead.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        warnings.warn(\"collection_names is deprecated. Use \"\n                      \"list_collection_names instead.\",\n                      DeprecationWarning, stacklevel=2)\n        kws = {} if include_system_collections else _SYSTEM_FILTER\n        return [result[\"name\"]\n                for result in self.list_collections(session=session,\n                                                    nameOnly=True, **kws)]\n\n    def drop_collection(self, name_or_collection, session=None):\n        \"\"\"Drop a collection.\n\n        :Parameters:\n          - `name_or_collection`: the name of a collection to drop or the\n            collection object itself\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. note:: The :attr:`~pymongo.database.Database.write_concern` of\n           this database is automatically applied to this operation when using\n           MongoDB >= 3.4.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. versionchanged:: 3.4\n           Apply this database's write concern automatically to this operation\n           when connected to MongoDB >= 3.4.\n\n        \"\"\"\n        name = name_or_collection\n        if isinstance(name, Collection):\n            name = name.name\n\n        if not isinstance(name, string_type):\n            raise TypeError(\"name_or_collection must be an \"\n                            \"instance of %s\" % (string_type.__name__,))\n\n        self.__client._purge_index(self.__name, name)\n\n        with self.__client._socket_for_writes(session) as sock_info:\n            return self._command(\n                sock_info, 'drop', value=_unicode(name),\n                allowable_errors=['ns not found'],\n                write_concern=self._write_concern_for(session),\n                parse_write_concern_error=True,\n                session=session)\n\n    def validate_collection(self, name_or_collection,\n                            scandata=False, full=False, session=None):\n        \"\"\"Validate a collection.\n\n        Returns a dict of validation info. Raises CollectionInvalid if\n        validation fails.\n\n        :Parameters:\n          - `name_or_collection`: A Collection object or the name of a\n            collection to validate.\n          - `scandata`: Do extra checks beyond checking the overall\n            structure of the collection.\n          - `full`: Have the server do a more thorough scan of the\n            collection. Use with `scandata` for a thorough scan\n            of the structure of the collection and the individual\n            documents.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        name = name_or_collection\n        if isinstance(name, Collection):\n            name = name.name\n\n        if not isinstance(name, string_type):\n            raise TypeError(\"name_or_collection must be an instance of \"\n                            \"%s or Collection\" % (string_type.__name__,))\n\n        result = self.command(\"validate\", _unicode(name),\n                              scandata=scandata, full=full, session=session)\n\n        valid = True\n        # Pre 1.9 results\n        if \"result\" in result:\n            info = result[\"result\"]\n            if info.find(\"exception\") != -1 or info.find(\"corrupt\") != -1:\n                raise CollectionInvalid(\"%s invalid: %s\" % (name, info))\n        # Sharded results\n        elif \"raw\" in result:\n            for _, res in iteritems(result[\"raw\"]):\n                if \"result\" in res:\n                    info = res[\"result\"]\n                    if (info.find(\"exception\") != -1 or\n                            info.find(\"corrupt\") != -1):\n                        raise CollectionInvalid(\"%s invalid: \"\n                                                \"%s\" % (name, info))\n                elif not res.get(\"valid\", False):\n                    valid = False\n                    break\n        # Post 1.9 non-sharded results.\n        elif not result.get(\"valid\", False):\n            valid = False\n\n        if not valid:\n            raise CollectionInvalid(\"%s invalid: %r\" % (name, result))\n\n        return result\n\n    def _current_op(self, include_all=False, session=None):\n        \"\"\"Helper for running $currentOp.\"\"\"\n        cmd = SON([(\"currentOp\", 1), (\"$all\", include_all)])\n        with self.__client._socket_for_writes(session) as sock_info:\n            if sock_info.max_wire_version >= 4:\n                return self.__client.admin._command(\n                    sock_info, cmd, codec_options=self.codec_options,\n                    session=session)\n            else:\n                spec = {\"$all\": True} if include_all else {}\n                return _first_batch(sock_info, \"admin\", \"$cmd.sys.inprog\",\n                                    spec, -1, True, self.codec_options,\n                                    ReadPreference.PRIMARY, cmd,\n                                    self.client._event_listeners)\n\n    def current_op(self, include_all=False, session=None):\n        \"\"\"**DEPRECATED**: Get information on operations currently running.\n\n        Starting with MongoDB 3.6 this helper is obsolete. The functionality\n        provided by this helper is available in MongoDB 3.6+ using the\n        `$currentOp aggregation pipeline stage`_, which can be used with\n        :meth:`aggregate`. Note that, while this helper can only return\n        a single document limited to a 16MB result, :meth:`aggregate`\n        returns a cursor avoiding that limitation.\n\n        Users of MongoDB versions older than 3.6 can use the `currentOp command`_\n        directly::\n\n          # MongoDB 3.2 and 3.4\n          client.admin.command(\"currentOp\")\n\n        Or query the \"inprog\" virtual collection::\n\n          # MongoDB 2.6 and 3.0\n          client.admin[\"$cmd.sys.inprog\"].find_one()\n\n        :Parameters:\n          - `include_all` (optional): if ``True`` also list currently\n            idle operations in the result\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.9\n           Deprecated.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. _$currentOp aggregation pipeline stage: https://docs.mongodb.com/manual/reference/operator/aggregation/currentOp/\n        .. _currentOp command: https://docs.mongodb.com/manual/reference/command/currentOp/\n        \"\"\"\n        warnings.warn(\"current_op() is deprecated. See the documentation for \"\n                      \"more information\",\n                      DeprecationWarning, stacklevel=2)\n        return self._current_op(include_all, session)\n\n    def profiling_level(self, session=None):\n        \"\"\"Get the database's current profiling level.\n\n        Returns one of (:data:`~pymongo.OFF`,\n        :data:`~pymongo.SLOW_ONLY`, :data:`~pymongo.ALL`).\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. mongodoc:: profiling\n        \"\"\"\n        result = self.command(\"profile\", -1, session=session)\n\n        assert result[\"was\"] >= 0 and result[\"was\"] <= 2\n        return result[\"was\"]\n\n    def set_profiling_level(self, level, slow_ms=None, session=None):\n        \"\"\"Set the database's profiling level.\n\n        :Parameters:\n          - `level`: Specifies a profiling level, see list of possible values\n            below.\n          - `slow_ms`: Optionally modify the threshold for the profile to\n            consider a query or operation.  Even if the profiler is off queries\n            slower than the `slow_ms` level will get written to the logs.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        Possible `level` values:\n\n        +----------------------------+------------------------------------+\n        | Level                      | Setting                            |\n        +============================+====================================+\n        | :data:`~pymongo.OFF`       | Off. No profiling.                 |\n        +----------------------------+------------------------------------+\n        | :data:`~pymongo.SLOW_ONLY` | On. Only includes slow operations. |\n        +----------------------------+------------------------------------+\n        | :data:`~pymongo.ALL`       | On. Includes all operations.       |\n        +----------------------------+------------------------------------+\n\n        Raises :class:`ValueError` if level is not one of\n        (:data:`~pymongo.OFF`, :data:`~pymongo.SLOW_ONLY`,\n        :data:`~pymongo.ALL`).\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. mongodoc:: profiling\n        \"\"\"\n        if not isinstance(level, int) or level < 0 or level > 2:\n            raise ValueError(\"level must be one of (OFF, SLOW_ONLY, ALL)\")\n\n        if slow_ms is not None and not isinstance(slow_ms, int):\n            raise TypeError(\"slow_ms must be an integer\")\n\n        if slow_ms is not None:\n            self.command(\"profile\", level, slowms=slow_ms, session=session)\n        else:\n            self.command(\"profile\", level, session=session)\n\n    def profiling_info(self, session=None):\n        \"\"\"Returns a list containing current profiling information.\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. mongodoc:: profiling\n        \"\"\"\n        return list(self[\"system.profile\"].find(session=session))\n\n    def error(self):\n        \"\"\"**DEPRECATED**: Get the error if one occurred on the last operation.\n\n        This method is obsolete: all MongoDB write operations (insert, update,\n        remove, and so on) use the write concern ``w=1`` and report their\n        errors by default.\n\n        .. versionchanged:: 2.8\n           Deprecated.\n        \"\"\"\n        warnings.warn(\"Database.error() is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n\n        error = self.command(\"getlasterror\")\n        error_msg = error.get(\"err\", \"\")\n        if error_msg is None:\n            return None\n        if error_msg.startswith(\"not master\"):\n            # Reset primary server and request check, if another thread isn't\n            # doing so already.\n            primary = self.__client.primary\n            if primary:\n                self.__client._reset_server_and_request_check(primary)\n        return error\n\n    def last_status(self):\n        \"\"\"**DEPRECATED**: Get status information from the last operation.\n\n        This method is obsolete: all MongoDB write operations (insert, update,\n        remove, and so on) use the write concern ``w=1`` and report their\n        errors by default.\n\n        Returns a SON object with status information.\n\n        .. versionchanged:: 2.8\n           Deprecated.\n        \"\"\"\n        warnings.warn(\"last_status() is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n\n        return self.command(\"getlasterror\")\n\n    def previous_error(self):\n        \"\"\"**DEPRECATED**: Get the most recent error on this database.\n\n        This method is obsolete: all MongoDB write operations (insert, update,\n        remove, and so on) use the write concern ``w=1`` and report their\n        errors by default.\n\n        Only returns errors that have occurred since the last call to\n        :meth:`reset_error_history`. Returns None if no such errors have\n        occurred.\n\n        .. versionchanged:: 2.8\n           Deprecated.\n        \"\"\"\n        warnings.warn(\"previous_error() is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n\n        error = self.command(\"getpreverror\")\n        if error.get(\"err\", 0) is None:\n            return None\n        return error\n\n    def reset_error_history(self):\n        \"\"\"**DEPRECATED**: Reset the error history of this database.\n\n        This method is obsolete: all MongoDB write operations (insert, update,\n        remove, and so on) use the write concern ``w=1`` and report their\n        errors by default.\n\n        Calls to :meth:`previous_error` will only return errors that have\n        occurred since the most recent call to this method.\n\n        .. versionchanged:: 2.8\n           Deprecated.\n        \"\"\"\n        warnings.warn(\"reset_error_history() is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n\n        self.command(\"reseterror\")\n\n    def __iter__(self):\n        return self\n\n    def __next__(self):\n        raise TypeError(\"'Database' object is not iterable\")\n\n    next = __next__\n\n    def _default_role(self, read_only):\n        \"\"\"Return the default user role for this database.\"\"\"\n        if self.name == \"admin\":\n            if read_only:\n                return \"readAnyDatabase\"\n            else:\n                return \"root\"\n        else:\n            if read_only:\n                return \"read\"\n            else:\n                return \"dbOwner\"\n\n    def _create_or_update_user(\n            self, create, name, password, read_only, session=None, **kwargs):\n        \"\"\"Use a command to create (if create=True) or modify a user.\n        \"\"\"\n        opts = {}\n        if read_only or (create and \"roles\" not in kwargs):\n            warnings.warn(\"Creating a user with the read_only option \"\n                          \"or without roles is deprecated in MongoDB \"\n                          \">= 2.6\", DeprecationWarning)\n\n            opts[\"roles\"] = [self._default_role(read_only)]\n\n        if read_only:\n            warnings.warn(\"The read_only option is deprecated in MongoDB \"\n                          \">= 2.6, use 'roles' instead\", DeprecationWarning)\n\n        if password is not None:\n            if \"digestPassword\" in kwargs:\n                raise ConfigurationError(\"The digestPassword option is not \"\n                                         \"supported via add_user. Please use \"\n                                         \"db.command('createUser', ...) \"\n                                         \"instead for this option.\")\n            opts[\"pwd\"] = password\n\n        # Don't send {} as writeConcern.\n        if self.write_concern.acknowledged and self.write_concern.document:\n            opts[\"writeConcern\"] = self.write_concern.document\n        opts.update(kwargs)\n\n        if create:\n            command_name = \"createUser\"\n        else:\n            command_name = \"updateUser\"\n\n        self.command(command_name, name, session=session, **opts)\n\n    def add_user(self, name, password=None, read_only=None, session=None,\n                 **kwargs):\n        \"\"\"**DEPRECATED**: Create user `name` with password `password`.\n\n        Add a new user with permissions for this :class:`Database`.\n\n        .. note:: Will change the password if user `name` already exists.\n\n        .. note:: add_user is deprecated and will be removed in PyMongo\n          4.0. Starting with MongoDB 2.6 user management is handled with four\n          database commands, createUser_, usersInfo_, updateUser_, and\n          dropUser_.\n\n          To create a user::\n\n            db.command(\"createUser\", \"admin\", pwd=\"password\", roles=[\"root\"])\n\n          To create a read-only user::\n\n            db.command(\"createUser\", \"user\", pwd=\"password\", roles=[\"read\"])\n\n          To change a password::\n\n            db.command(\"updateUser\", \"user\", pwd=\"newpassword\")\n\n          Or change roles::\n\n            db.command(\"updateUser\", \"user\", roles=[\"readWrite\"])\n\n        .. _createUser: https://docs.mongodb.com/manual/reference/command/createUser/\n        .. _usersInfo: https://docs.mongodb.com/manual/reference/command/usersInfo/\n        .. _updateUser: https://docs.mongodb.com/manual/reference/command/updateUser/\n        .. _dropUser: https://docs.mongodb.com/manual/reference/command/createUser/\n\n        .. warning:: Never create or modify users over an insecure network without\n          the use of TLS. See :doc:`/examples/tls` for more information.\n\n        :Parameters:\n          - `name`: the name of the user to create\n          - `password` (optional): the password of the user to create. Can not\n            be used with the ``userSource`` argument.\n          - `read_only` (optional): if ``True`` the user will be read only\n          - `**kwargs` (optional): optional fields for the user document\n            (e.g. ``userSource``, ``otherDBRoles``, or ``roles``). See\n            `<http://docs.mongodb.org/manual/reference/privilege-documents>`_\n            for more information.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.7\n           Added support for SCRAM-SHA-256 users with MongoDB 4.0 and later.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter. Deprecated add_user.\n\n        .. versionchanged:: 2.5\n           Added kwargs support for optional fields introduced in MongoDB 2.4\n\n        .. versionchanged:: 2.2\n           Added support for read only users\n        \"\"\"\n        warnings.warn(\"add_user is deprecated and will be removed in PyMongo \"\n                      \"4.0. Use db.command with createUser or updateUser \"\n                      \"instead\", DeprecationWarning, stacklevel=2)\n        if not isinstance(name, string_type):\n            raise TypeError(\"name must be an \"\n                            \"instance of %s\" % (string_type.__name__,))\n        if password is not None:\n            if not isinstance(password, string_type):\n                raise TypeError(\"password must be an \"\n                                \"instance of %s\" % (string_type.__name__,))\n            if len(password) == 0:\n                raise ValueError(\"password can't be empty\")\n        if read_only is not None:\n            read_only = common.validate_boolean('read_only', read_only)\n            if 'roles' in kwargs:\n                raise ConfigurationError(\"Can not use \"\n                                         \"read_only and roles together\")\n\n        try:\n            uinfo = self.command(\"usersInfo\", name, session=session)\n            # Create the user if not found in uinfo, otherwise update one.\n            self._create_or_update_user(\n                (not uinfo[\"users\"]), name, password, read_only,\n                session=session, **kwargs)\n        except OperationFailure as exc:\n            # Unauthorized. Attempt to create the user in case of\n            # localhost exception.\n            if exc.code == 13:\n                self._create_or_update_user(\n                    True, name, password, read_only, session=session, **kwargs)\n            else:\n                raise\n\n    def remove_user(self, name, session=None):\n        \"\"\"**DEPRECATED**: Remove user `name` from this :class:`Database`.\n\n        User `name` will no longer have permissions to access this\n        :class:`Database`.\n\n        .. note:: remove_user is deprecated and will be removed in PyMongo\n          4.0. Use the dropUser command instead::\n\n            db.command(\"dropUser\", \"user\")\n\n        :Parameters:\n          - `name`: the name of the user to remove\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter. Deprecated remove_user.\n        \"\"\"\n        warnings.warn(\"remove_user is deprecated and will be removed in \"\n                      \"PyMongo 4.0. Use db.command with dropUser \"\n                      \"instead\", DeprecationWarning, stacklevel=2)\n        cmd = SON([(\"dropUser\", name)])\n        # Don't send {} as writeConcern.\n        if self.write_concern.acknowledged and self.write_concern.document:\n            cmd[\"writeConcern\"] = self.write_concern.document\n        self.command(cmd, session=session)\n\n    def authenticate(self, name=None, password=None,\n                     source=None, mechanism='DEFAULT', **kwargs):\n        \"\"\"**DEPRECATED**: Authenticate to use this database.\n\n        .. warning:: Starting in MongoDB 3.6, calling :meth:`authenticate`\n          invalidates all existing cursors. It may also leave logical sessions\n          open on the server for up to 30 minutes until they time out.\n\n        Authentication lasts for the life of the underlying client\n        instance, or until :meth:`logout` is called.\n\n        Raises :class:`TypeError` if (required) `name`, (optional) `password`,\n        or (optional) `source` is not an instance of :class:`basestring`\n        (:class:`str` in python 3).\n\n        .. note::\n          - This method authenticates the current connection, and\n            will also cause all new :class:`~socket.socket` connections\n            in the underlying client instance to be authenticated automatically.\n\n          - Authenticating more than once on the same database with different\n            credentials is not supported. You must call :meth:`logout` before\n            authenticating with new credentials.\n\n          - When sharing a client instance between multiple threads, all\n            threads will share the authentication. If you need different\n            authentication profiles for different purposes you must use\n            distinct client instances.\n\n        :Parameters:\n          - `name`: the name of the user to authenticate. Optional when\n            `mechanism` is MONGODB-X509 and the MongoDB server version is\n            >= 3.4.\n          - `password` (optional): the password of the user to authenticate.\n            Not used with GSSAPI or MONGODB-X509 authentication.\n          - `source` (optional): the database to authenticate on. If not\n            specified the current database is used.\n          - `mechanism` (optional): See :data:`~pymongo.auth.MECHANISMS` for\n            options. If no mechanism is specified, PyMongo automatically uses\n            MONGODB-CR when connected to a pre-3.0 version of MongoDB,\n            SCRAM-SHA-1 when connected to MongoDB 3.0 through 3.6, and\n            negotiates the mechanism to use (SCRAM-SHA-1 or SCRAM-SHA-256) when\n            connected to MongoDB 4.0+.\n          - `authMechanismProperties` (optional): Used to specify\n            authentication mechanism specific options. To specify the service\n            name for GSSAPI authentication pass\n            authMechanismProperties='SERVICE_NAME:<service name>'\n\n        .. versionchanged:: 3.7\n           Added support for SCRAM-SHA-256 with MongoDB 4.0 and later.\n\n        .. versionchanged:: 3.5\n           Deprecated. Authenticating multiple users conflicts with support for\n           logical sessions in MongoDB 3.6. To authenticate as multiple users,\n           create multiple instances of MongoClient.\n\n        .. versionadded:: 2.8\n           Use SCRAM-SHA-1 with MongoDB 3.0 and later.\n\n        .. versionchanged:: 2.5\n           Added the `source` and `mechanism` parameters. :meth:`authenticate`\n           now raises a subclass of :class:`~pymongo.errors.PyMongoError` if\n           authentication fails due to invalid credentials or configuration\n           issues.\n\n        .. mongodoc:: authenticate\n        \"\"\"\n        if name is not None and not isinstance(name, string_type):\n            raise TypeError(\"name must be an \"\n                            \"instance of %s\" % (string_type.__name__,))\n        if password is not None and not isinstance(password, string_type):\n            raise TypeError(\"password must be an \"\n                            \"instance of %s\" % (string_type.__name__,))\n        if source is not None and not isinstance(source, string_type):\n            raise TypeError(\"source must be an \"\n                            \"instance of %s\" % (string_type.__name__,))\n        common.validate_auth_mechanism('mechanism', mechanism)\n\n        validated_options = {}\n        for option, value in iteritems(kwargs):\n            normalized, val = common.validate_auth_option(option, value)\n            validated_options[normalized] = val\n\n        credentials = auth._build_credentials_tuple(\n            mechanism,\n            source,\n            name,\n            password,\n            validated_options,\n            self.name)\n\n        self.client._cache_credentials(\n            self.name,\n            credentials,\n            connect=True)\n\n        return True\n\n    def logout(self):\n        \"\"\"**DEPRECATED**: Deauthorize use of this database.\n\n        .. warning:: Starting in MongoDB 3.6, calling :meth:`logout`\n          invalidates all existing cursors. It may also leave logical sessions\n          open on the server for up to 30 minutes until they time out.\n        \"\"\"\n        warnings.warn(\"Database.logout() is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n\n        # Sockets will be deauthenticated as they are used.\n        self.client._purge_credentials(self.name)\n\n    def dereference(self, dbref, session=None, **kwargs):\n        \"\"\"Dereference a :class:`~bson.dbref.DBRef`, getting the\n        document it points to.\n\n        Raises :class:`TypeError` if `dbref` is not an instance of\n        :class:`~bson.dbref.DBRef`. Returns a document, or ``None`` if\n        the reference does not point to a valid document.  Raises\n        :class:`ValueError` if `dbref` has a database specified that\n        is different from the current database.\n\n        :Parameters:\n          - `dbref`: the reference\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): any additional keyword arguments\n            are the same as the arguments to\n            :meth:`~pymongo.collection.Collection.find`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        if not isinstance(dbref, DBRef):\n            raise TypeError(\"cannot dereference a %s\" % type(dbref))\n        if dbref.database is not None and dbref.database != self.__name:\n            raise ValueError(\"trying to dereference a DBRef that points to \"\n                             \"another database (%r not %r)\" % (dbref.database,\n                                                               self.__name))\n        return self[dbref.collection].find_one(\n            {\"_id\": dbref.id}, session=session, **kwargs)\n\n    def eval(self, code, *args):\n        \"\"\"**DEPRECATED**: Evaluate a JavaScript expression in MongoDB.\n\n        :Parameters:\n          - `code`: string representation of JavaScript code to be\n            evaluated\n          - `args` (optional): additional positional arguments are\n            passed to the `code` being evaluated\n\n        .. warning:: the eval command is deprecated in MongoDB 3.0 and\n          will be removed in a future server version.\n        \"\"\"\n        warnings.warn(\"Database.eval() is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n\n        if not isinstance(code, Code):\n            code = Code(code)\n\n        result = self.command(\"$eval\", code, args=args)\n        return result.get(\"retval\", None)\n\n    def __call__(self, *args, **kwargs):\n        \"\"\"This is only here so that some API misusages are easier to debug.\n        \"\"\"\n        raise TypeError(\"'Database' object is not callable. If you meant to \"\n                        \"call the '%s' method on a '%s' object it is \"\n                        \"failing because no such method exists.\" % (\n                            self.__name, self.__client.__class__.__name__))\n\n\nclass SystemJS(object):\n    \"\"\"**DEPRECATED**: Helper class for dealing with stored JavaScript.\n    \"\"\"\n\n    def __init__(self, database):\n        \"\"\"**DEPRECATED**: Get a system js helper for the database `database`.\n\n        SystemJS will be removed in PyMongo 4.0.\n        \"\"\"\n        warnings.warn(\"SystemJS is deprecated\",\n                      DeprecationWarning, stacklevel=2)\n\n        if not database.write_concern.acknowledged:\n            database = database.client.get_database(\n                database.name, write_concern=DEFAULT_WRITE_CONCERN)\n        # can't just assign it since we've overridden __setattr__\n        object.__setattr__(self, \"_db\", database)\n\n    def __setattr__(self, name, code):\n        self._db.system.js.replace_one(\n            {\"_id\": name}, {\"_id\": name, \"value\": Code(code)}, True)\n\n    def __setitem__(self, name, code):\n        self.__setattr__(name, code)\n\n    def __delattr__(self, name):\n        self._db.system.js.delete_one({\"_id\": name})\n\n    def __delitem__(self, name):\n        self.__delattr__(name)\n\n    def __getattr__(self, name):\n        return lambda *args: self._db.eval(Code(\"function() { \"\n                                                \"return this[name].apply(\"\n                                                \"this, arguments); }\",\n                                                scope={'name': name}), *args)\n\n    def __getitem__(self, name):\n        return self.__getattr__(name)\n\n    def list(self):\n        \"\"\"Get a list of the names of the functions stored in this database.\"\"\"\n        return [x[\"_id\"] for x in self._db.system.js.find(projection=[\"_id\"])]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/driver_info.py",
    "content": "# Copyright 2018-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Advanced options for MongoDB drivers implemented on top of PyMongo.\"\"\"\n\nfrom collections import namedtuple\n\nfrom bson.py3compat import string_type\n\n\nclass DriverInfo(namedtuple('DriverInfo', ['name', 'version', 'platform'])):\n    \"\"\"Info about a driver wrapping PyMongo.\n\n    The MongoDB server logs PyMongo's name, version, and platform whenever\n    PyMongo establishes a connection. A driver implemented on top of PyMongo\n    can add its own info to this log message. Initialize with three strings\n    like 'MyDriver', '1.2.3', 'some platform info'. Any of these strings may be\n    None to accept PyMongo's default.\n    \"\"\"\n    def __new__(cls, name=None, version=None, platform=None):\n        self = super(DriverInfo, cls).__new__(cls, name, version, platform)\n        for name, value in self._asdict().items():\n            if value is not None and not isinstance(value, string_type):\n                raise TypeError(\"Wrong type for DriverInfo %s option, value \"\n                                \"must be an instance of %s\" % (\n                                    name, string_type.__name__))\n\n        return self\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/encryption.py",
    "content": "# Copyright 2019-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Support for explicit client side encryption.\n\n**Support for client side encryption is in beta. Backwards-breaking changes\nmay be made before the final release.**\n\"\"\"\n\nimport contextlib\nimport subprocess\nimport uuid\nimport weakref\n\ntry:\n    from pymongocrypt.auto_encrypter import AutoEncrypter\n    from pymongocrypt.errors import MongoCryptError\n    from pymongocrypt.explicit_encrypter import ExplicitEncrypter\n    from pymongocrypt.mongocrypt import MongoCryptOptions\n    from pymongocrypt.state_machine import MongoCryptCallback\n    _HAVE_PYMONGOCRYPT = True\nexcept ImportError:\n    _HAVE_PYMONGOCRYPT = False\n    MongoCryptCallback = object\n\nfrom bson import _bson_to_dict, _dict_to_bson, decode, encode\nfrom bson.codec_options import CodecOptions\nfrom bson.binary import (Binary,\n                         STANDARD,\n                         UUID_SUBTYPE)\nfrom bson.errors import BSONError\nfrom bson.raw_bson import (DEFAULT_RAW_BSON_OPTIONS,\n                           RawBSONDocument,\n                           _inflate_bson)\nfrom bson.son import SON\n\nfrom pymongo.errors import (ConfigurationError,\n                            EncryptionError,\n                            InvalidOperation,\n                            ServerSelectionTimeoutError)\nfrom pymongo.message import (_COMMAND_OVERHEAD,\n                             _MAX_ENC_BSON_SIZE,\n                             _raise_document_too_large)\nfrom pymongo.mongo_client import MongoClient\nfrom pymongo.pool import _configured_socket, PoolOptions\nfrom pymongo.read_concern import ReadConcern\nfrom pymongo.ssl_support import get_ssl_context\nfrom pymongo.write_concern import WriteConcern\n\n\n_HTTPS_PORT = 443\n_KMS_CONNECT_TIMEOUT = 10  # TODO: CDRIVER-3262 will define this value.\n_MONGOCRYPTD_TIMEOUT_MS = 1000\n\n_DATA_KEY_OPTS = CodecOptions(document_class=SON, uuid_representation=STANDARD)\n# Use RawBSONDocument codec options to avoid needlessly decoding\n# documents from the key vault.\n_KEY_VAULT_OPTS = CodecOptions(document_class=RawBSONDocument,\n                               uuid_representation=STANDARD)\n\n\n@contextlib.contextmanager\ndef _wrap_encryption_errors():\n    \"\"\"Context manager to wrap encryption related errors.\"\"\"\n    try:\n        yield\n    except BSONError:\n        # BSON encoding/decoding errors are unrelated to encryption so\n        # we should propagate them unchanged.\n        raise\n    except Exception as exc:\n        raise EncryptionError(exc)\n\n\nclass _EncryptionIO(MongoCryptCallback):\n    def __init__(self, client, key_vault_coll, mongocryptd_client, opts):\n        \"\"\"Internal class to perform I/O on behalf of pymongocrypt.\"\"\"\n        # Use a weak ref to break reference cycle.\n        if client is not None:\n            self.client_ref = weakref.ref(client)\n        else:\n            self.client_ref = None\n        self.key_vault_coll = key_vault_coll.with_options(\n            codec_options=_KEY_VAULT_OPTS,\n            read_concern=ReadConcern(level='majority'),\n            write_concern=WriteConcern(w='majority'))\n        self.mongocryptd_client = mongocryptd_client\n        self.opts = opts\n        self._spawned = False\n\n    def kms_request(self, kms_context):\n        \"\"\"Complete a KMS request.\n\n        :Parameters:\n          - `kms_context`: A :class:`MongoCryptKmsContext`.\n\n        :Returns:\n          None\n        \"\"\"\n        endpoint = kms_context.endpoint\n        message = kms_context.message\n        ctx = get_ssl_context(None, None, None, None, None, None, True)\n        opts = PoolOptions(connect_timeout=_KMS_CONNECT_TIMEOUT,\n                           socket_timeout=_KMS_CONNECT_TIMEOUT,\n                           ssl_context=ctx)\n        conn = _configured_socket((endpoint, _HTTPS_PORT), opts)\n        try:\n            conn.sendall(message)\n            while kms_context.bytes_needed > 0:\n                data = conn.recv(kms_context.bytes_needed)\n                kms_context.feed(data)\n        finally:\n            conn.close()\n\n    def collection_info(self, database, filter):\n        \"\"\"Get the collection info for a namespace.\n\n        The returned collection info is passed to libmongocrypt which reads\n        the JSON schema.\n\n        :Parameters:\n          - `database`: The database on which to run listCollections.\n          - `filter`: The filter to pass to listCollections.\n\n        :Returns:\n          The first document from the listCollections command response as BSON.\n        \"\"\"\n        with self.client_ref()[database].list_collections(\n                filter=RawBSONDocument(filter)) as cursor:\n            for doc in cursor:\n                return _dict_to_bson(doc, False, _DATA_KEY_OPTS)\n\n    def spawn(self):\n        \"\"\"Spawn mongocryptd.\n\n        Note this method is thread safe; at most one mongocryptd will start\n        successfully.\n        \"\"\"\n        self._spawned = True\n        args = [self.opts._mongocryptd_spawn_path or 'mongocryptd']\n        args.extend(self.opts._mongocryptd_spawn_args)\n        subprocess.Popen(args)\n\n    def mark_command(self, database, cmd):\n        \"\"\"Mark a command for encryption.\n\n        :Parameters:\n          - `database`: The database on which to run this command.\n          - `cmd`: The BSON command to run.\n\n        :Returns:\n          The marked command response from mongocryptd.\n        \"\"\"\n        if not self._spawned and not self.opts._mongocryptd_bypass_spawn:\n            self.spawn()\n        # Database.command only supports mutable mappings so we need to decode\n        # the raw BSON command first.\n        inflated_cmd = _inflate_bson(cmd, DEFAULT_RAW_BSON_OPTIONS)\n        try:\n            res = self.mongocryptd_client[database].command(\n                inflated_cmd,\n                codec_options=DEFAULT_RAW_BSON_OPTIONS)\n        except ServerSelectionTimeoutError:\n            if self.opts._mongocryptd_bypass_spawn:\n                raise\n            self.spawn()\n            res = self.mongocryptd_client[database].command(\n                inflated_cmd,\n                codec_options=DEFAULT_RAW_BSON_OPTIONS)\n        return res.raw\n\n    def fetch_keys(self, filter):\n        \"\"\"Yields one or more keys from the key vault.\n\n        :Parameters:\n          - `filter`: The filter to pass to find.\n\n        :Returns:\n          A generator which yields the requested keys from the key vault.\n        \"\"\"\n        with self.key_vault_coll.find(RawBSONDocument(filter)) as cursor:\n            for key in cursor:\n                yield key.raw\n\n    def insert_data_key(self, data_key):\n        \"\"\"Insert a data key into the key vault.\n\n        :Parameters:\n          - `data_key`: The data key document to insert.\n\n        :Returns:\n          The _id of the inserted data key document.\n        \"\"\"\n        # insert does not return the inserted _id when given a RawBSONDocument.\n        doc = _bson_to_dict(data_key, _DATA_KEY_OPTS)\n        if not isinstance(doc.get('_id'), uuid.UUID):\n            raise TypeError(\n                'data_key _id must be a bson.binary.Binary with subtype 4')\n        res = self.key_vault_coll.insert_one(doc)\n        return Binary(res.inserted_id.bytes, subtype=UUID_SUBTYPE)\n\n    def bson_encode(self, doc):\n        \"\"\"Encode a document to BSON.\n\n        A document can be any mapping type (like :class:`dict`).\n\n        :Parameters:\n          - `doc`: mapping type representing a document\n\n        :Returns:\n          The encoded BSON bytes.\n        \"\"\"\n        return encode(doc)\n\n    def close(self):\n        \"\"\"Release resources.\n\n        Note it is not safe to call this method from __del__ or any GC hooks.\n        \"\"\"\n        self.client_ref = None\n        self.key_vault_coll = None\n        if self.mongocryptd_client:\n            self.mongocryptd_client.close()\n            self.mongocryptd_client = None\n\n\nclass _Encrypter(object):\n    def __init__(self, io_callbacks, opts):\n        \"\"\"Encrypts and decrypts MongoDB commands.\n\n        This class is used to support automatic encryption and decryption of\n        MongoDB commands.\n\n        :Parameters:\n          - `io_callbacks`: A :class:`MongoCryptCallback`.\n          - `opts`: The encrypted client's :class:`AutoEncryptionOpts`.\n        \"\"\"\n        if opts._schema_map is None:\n            schema_map = None\n        else:\n            schema_map = _dict_to_bson(opts._schema_map, False, _DATA_KEY_OPTS)\n        self._auto_encrypter = AutoEncrypter(io_callbacks, MongoCryptOptions(\n            opts._kms_providers, schema_map))\n        self._bypass_auto_encryption = opts._bypass_auto_encryption\n        self._closed = False\n\n    def encrypt(self, database, cmd, check_keys, codec_options):\n        \"\"\"Encrypt a MongoDB command.\n\n        :Parameters:\n          - `database`: The database for this command.\n          - `cmd`: A command document.\n          - `check_keys`: If True, check `cmd` for invalid keys.\n          - `codec_options`: The CodecOptions to use while encoding `cmd`.\n\n        :Returns:\n          The encrypted command to execute.\n        \"\"\"\n        self._check_closed()\n        # Workaround for $clusterTime which is incompatible with\n        # check_keys.\n        cluster_time = check_keys and cmd.pop('$clusterTime', None)\n        encoded_cmd = _dict_to_bson(cmd, check_keys, codec_options)\n        max_cmd_size = _MAX_ENC_BSON_SIZE + _COMMAND_OVERHEAD\n        if len(encoded_cmd) > max_cmd_size:\n            raise _raise_document_too_large(\n                next(iter(cmd)), len(encoded_cmd), max_cmd_size)\n        with _wrap_encryption_errors():\n            encrypted_cmd = self._auto_encrypter.encrypt(database, encoded_cmd)\n            # TODO: PYTHON-1922 avoid decoding the encrypted_cmd.\n            encrypt_cmd = _inflate_bson(\n                encrypted_cmd, DEFAULT_RAW_BSON_OPTIONS)\n            if cluster_time:\n                encrypt_cmd['$clusterTime'] = cluster_time\n            return encrypt_cmd\n\n    def decrypt(self, response):\n        \"\"\"Decrypt a MongoDB command response.\n\n        :Parameters:\n          - `response`: A MongoDB command response as BSON.\n\n        :Returns:\n          The decrypted command response.\n        \"\"\"\n        self._check_closed()\n        with _wrap_encryption_errors():\n            return self._auto_encrypter.decrypt(response)\n\n    def _check_closed(self):\n        if self._closed:\n            raise InvalidOperation(\"Cannot use MongoClient after close\")\n\n    def close(self):\n        \"\"\"Cleanup resources.\"\"\"\n        self._closed = True\n        self._auto_encrypter.close()\n\n    @staticmethod\n    def create(client, opts):\n        \"\"\"Create a _CommandEncyptor for a client.\n\n        :Parameters:\n          - `client`: The encrypted MongoClient.\n          - `opts`: The encrypted client's :class:`AutoEncryptionOpts`.\n\n        :Returns:\n          A :class:`_CommandEncrypter` for this client.\n        \"\"\"\n        key_vault_client = opts._key_vault_client or client\n        db, coll = opts._key_vault_namespace.split('.', 1)\n        key_vault_coll = key_vault_client[db][coll]\n\n        mongocryptd_client = MongoClient(\n            opts._mongocryptd_uri, connect=False,\n            serverSelectionTimeoutMS=_MONGOCRYPTD_TIMEOUT_MS)\n\n        io_callbacks = _EncryptionIO(\n            client, key_vault_coll, mongocryptd_client, opts)\n        return _Encrypter(io_callbacks, opts)\n\n\nclass Algorithm(object):\n    \"\"\"An enum that defines the supported encryption algorithms.\"\"\"\n    AEAD_AES_256_CBC_HMAC_SHA_512_Deterministic = (\n        \"AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic\")\n    AEAD_AES_256_CBC_HMAC_SHA_512_Random = (\n        \"AEAD_AES_256_CBC_HMAC_SHA_512-Random\")\n\n\nclass ClientEncryption(object):\n    \"\"\"Explicit client side encryption.\"\"\"\n\n    def __init__(self, kms_providers, key_vault_namespace, key_vault_client,\n                 codec_options):\n        \"\"\"Explicit client side encryption.\n\n        The ClientEncryption class encapsulates explicit operations on a key\n        vault collection that cannot be done directly on a MongoClient. Similar\n        to configuring auto encryption on a MongoClient, it is constructed with\n        a MongoClient (to a MongoDB cluster containing the key vault\n        collection), KMS provider configuration, and keyVaultNamespace. It\n        provides an API for explicitly encrypting and decrypting values, and\n        creating data keys. It does not provide an API to query keys from the\n        key vault collection, as this can be done directly on the MongoClient.\n\n        .. note:: Support for client side encryption is in beta.\n           Backwards-breaking changes may be made before the final release.\n\n        :Parameters:\n          - `kms_providers`: Map of KMS provider options. Two KMS providers\n            are supported: \"aws\" and \"local\". The kmsProviders map values\n            differ by provider:\n\n              - `aws`: Map with \"accessKeyId\" and \"secretAccessKey\" as strings.\n                These are the AWS access key ID and AWS secret access key used\n                to generate KMS messages.\n              - `local`: Map with \"key\" as a 96-byte array or string. \"key\"\n                is the master key used to encrypt/decrypt data keys. This key\n                should be generated and stored as securely as possible.\n\n          - `key_vault_namespace`: The namespace for the key vault collection.\n            The key vault collection contains all data keys used for encryption\n            and decryption. Data keys are stored as documents in this MongoDB\n            collection. Data keys are protected with encryption by a KMS\n            provider.\n          - `key_vault_client`: A MongoClient connected to a MongoDB cluster\n            containing the `key_vault_namespace` collection.\n          - `codec_options`: An instance of\n            :class:`~bson.codec_options.CodecOptions` to use when encoding a\n            value for encryption and decoding the decrypted BSON value.\n\n        .. versionadded:: 3.9\n        \"\"\"\n        if not _HAVE_PYMONGOCRYPT:\n            raise ConfigurationError(\n                \"client side encryption requires the pymongocrypt library: \"\n                \"install a compatible version with: \"\n                \"python -m pip install pymongo['encryption']\")\n\n        if not isinstance(codec_options, CodecOptions):\n            raise TypeError(\"codec_options must be an instance of \"\n                            \"bson.codec_options.CodecOptions\")\n\n        self._kms_providers = kms_providers\n        self._key_vault_namespace = key_vault_namespace\n        self._key_vault_client = key_vault_client\n        self._codec_options = codec_options\n\n        db, coll = key_vault_namespace.split('.', 1)\n        key_vault_coll = key_vault_client[db][coll]\n\n        self._io_callbacks = _EncryptionIO(None, key_vault_coll, None, None)\n        self._encryption = ExplicitEncrypter(\n            self._io_callbacks, MongoCryptOptions(kms_providers, None))\n\n    def create_data_key(self, kms_provider, master_key=None,\n                        key_alt_names=None):\n        \"\"\"Create and insert a new data key into the key vault collection.\n\n        :Parameters:\n          - `kms_provider`: The KMS provider to use. Supported values are\n            \"aws\" and \"local\".\n          - `master_key`: The `master_key` identifies a KMS-specific key used\n            to encrypt the new data key. If the kmsProvider is \"local\" the\n            `master_key` is not applicable and may be omitted.\n            If the `kms_provider` is \"aws\", `master_key` is required and must\n            have the following fields:\n\n              - `region` (string): The AWS region as a string.\n              - `key` (string): The Amazon Resource Name (ARN) to the AWS\n                customer master key (CMK).\n\n          - `key_alt_names` (optional): An optional list of string alternate\n            names used to reference a key. If a key is created with alternate\n            names, then encryption may refer to the key by the unique alternate\n            name instead of by ``key_id``. The following example shows creating\n            and referring to a data key by alternate name::\n\n              client_encryption.create_data_key(\"local\", keyAltNames=[\"name1\"])\n              # reference the key with the alternate name\n              client_encryption.encrypt(\"457-55-5462\", keyAltName=\"name1\",\n                                        algorithm=Algorithm.Random)\n\n        :Returns:\n          The ``_id`` of the created data key document.\n        \"\"\"\n        self._check_closed()\n        with _wrap_encryption_errors():\n            return self._encryption.create_data_key(\n                kms_provider, master_key=master_key,\n                key_alt_names=key_alt_names)\n\n    def encrypt(self, value, algorithm, key_id=None, key_alt_name=None):\n        \"\"\"Encrypt a BSON value with a given key and algorithm.\n\n        Note that exactly one of ``key_id`` or  ``key_alt_name`` must be\n        provided.\n\n        :Parameters:\n          - `value`: The BSON value to encrypt.\n          - `algorithm` (string): The encryption algorithm to use. See\n            :class:`Algorithm` for some valid options.\n          - `key_id`: Identifies a data key by ``_id`` which must be a\n            :class:`~bson.binary.Binary` with subtype 4 (\n            :attr:`~bson.binary.UUID_SUBTYPE`).\n          - `key_alt_name`: Identifies a key vault document by 'keyAltName'.\n\n        :Returns:\n          The encrypted value, a :class:`~bson.binary.Binary` with subtype 6.\n        \"\"\"\n        self._check_closed()\n        if (key_id is not None and not (\n                isinstance(key_id, Binary) and\n                key_id.subtype == UUID_SUBTYPE)):\n            raise TypeError(\n                'key_id must be a bson.binary.Binary with subtype 4')\n\n        doc = encode({'v': value}, codec_options=self._codec_options)\n        with _wrap_encryption_errors():\n            encrypted_doc = self._encryption.encrypt(\n                doc, algorithm, key_id=key_id, key_alt_name=key_alt_name)\n            return decode(encrypted_doc)['v']\n\n    def decrypt(self, value):\n        \"\"\"Decrypt an encrypted value.\n\n        :Parameters:\n          - `value` (Binary): The encrypted value, a\n            :class:`~bson.binary.Binary` with subtype 6.\n\n        :Returns:\n          The decrypted BSON value.\n        \"\"\"\n        self._check_closed()\n        if not (isinstance(value, Binary) and value.subtype == 6):\n            raise TypeError(\n                'value to decrypt must be a bson.binary.Binary with subtype 6')\n\n        with _wrap_encryption_errors():\n            doc = encode({'v': value})\n            decrypted_doc = self._encryption.decrypt(doc)\n            return decode(decrypted_doc,\n                          codec_options=self._codec_options)['v']\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        self.close()\n\n    def _check_closed(self):\n        if self._encryption is None:\n            raise InvalidOperation(\"Cannot use closed ClientEncryption\")\n\n    def close(self):\n        \"\"\"Release resources.\n\n        Note that using this class in a with-statement will automatically call\n        :meth:`close`::\n\n            with ClientEncryption(...) as client_encryption:\n                encrypted = client_encryption.encrypt(value, ...)\n                decrypted = client_encryption.decrypt(encrypted)\n\n        \"\"\"\n        if self._io_callbacks:\n            self._io_callbacks.close()\n            self._encryption.close()\n            self._io_callbacks = None\n            self._encryption = None\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/encryption_options.py",
    "content": "# Copyright 2019-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Support for automatic client side encryption.\n\n**Support for client side encryption is in beta. Backwards-breaking changes\nmay be made before the final release.**\n\"\"\"\n\nimport copy\n\ntry:\n    import pymongocrypt\n    _HAVE_PYMONGOCRYPT = True\nexcept ImportError:\n    _HAVE_PYMONGOCRYPT = False\n\nfrom pymongo.errors import ConfigurationError\n\n\nclass AutoEncryptionOpts(object):\n    \"\"\"Options to configure automatic encryption.\"\"\"\n\n    def __init__(self, kms_providers, key_vault_namespace,\n                 key_vault_client=None, schema_map=None,\n                 bypass_auto_encryption=False,\n                 mongocryptd_uri='mongodb://localhost:27020',\n                 mongocryptd_bypass_spawn=False,\n                 mongocryptd_spawn_path='mongocryptd',\n                 mongocryptd_spawn_args=None):\n        \"\"\"Options to configure automatic encryption.\n\n        Automatic encryption is an enterprise only feature that only\n        applies to operations on a collection. Automatic encryption is not\n        supported for operations on a database or view and will result in\n        error. To bypass automatic encryption (but enable automatic\n        decryption), set ``bypass_auto_encryption=True`` in\n        AutoEncryptionOpts.\n\n        Explicit encryption/decryption and automatic decryption is a\n        community feature. A MongoClient configured with\n        bypassAutoEncryption=true will still automatically decrypt.\n\n        .. note:: Support for client side encryption is in beta.\n           Backwards-breaking changes may be made before the final release.\n\n        :Parameters:\n          - `kms_providers`: Map of KMS provider options. Two KMS providers\n            are supported: \"aws\" and \"local\". The kmsProviders map values\n            differ by provider:\n\n              - `aws`: Map with \"accessKeyId\" and \"secretAccessKey\" as strings.\n                These are the AWS access key ID and AWS secret access key used\n                to generate KMS messages.\n              - `local`: Map with \"key\" as a 96-byte array or string. \"key\"\n                is the master key used to encrypt/decrypt data keys. This key\n                should be generated and stored as securely as possible.\n\n          - `key_vault_namespace`: The namespace for the key vault collection.\n            The key vault collection contains all data keys used for encryption\n            and decryption. Data keys are stored as documents in this MongoDB\n            collection. Data keys are protected with encryption by a KMS\n            provider.\n          - `key_vault_client` (optional): By default the key vault collection\n            is assumed to reside in the same MongoDB cluster as the encrypted\n            MongoClient. Use this option to route data key queries to a\n            separate MongoDB cluster.\n          - `schema_map` (optional): Map of collection namespace (\"db.coll\") to\n            JSON Schema.  By default, a collection's JSONSchema is periodically\n            polled with the listCollections command. But a JSONSchema may be\n            specified locally with the schemaMap option.\n\n            **Supplying a `schema_map` provides more security than relying on\n            JSON Schemas obtained from the server. It protects against a\n            malicious server advertising a false JSON Schema, which could trick\n            the client into sending unencrypted data that should be\n            encrypted.**\n\n            Schemas supplied in the schemaMap only apply to configuring\n            automatic encryption for client side encryption. Other validation\n            rules in the JSON schema will not be enforced by the driver and\n            will result in an error.\n          - `bypass_auto_encryption` (optional): If ``True``, automatic\n            encryption will be disabled but automatic decryption will still be\n            enabled. Defaults to ``False``.\n          - `mongocryptd_uri` (optional): The MongoDB URI used to connect\n            to the *local* mongocryptd process. Defaults to\n            ``'mongodb://localhost:27020'``.\n          - `mongocryptd_bypass_spawn` (optional): If ``True``, the encrypted\n            MongoClient will not attempt to spawn the mongocryptd process.\n            Defaults to ``False``.\n          - `mongocryptd_spawn_path` (optional): Used for spawning the\n            mongocryptd process. Defaults to ``'mongocryptd'`` and spawns\n            mongocryptd from the system path.\n          - `mongocryptd_spawn_args` (optional): A list of string arguments to\n            use when spawning the mongocryptd process. Defaults to\n            ``['--idleShutdownTimeoutSecs=60']``. If the list does not include\n            the ``idleShutdownTimeoutSecs`` option then\n            ``'--idleShutdownTimeoutSecs=60'`` will be added.\n\n        .. versionadded:: 3.9\n        \"\"\"\n        if not _HAVE_PYMONGOCRYPT:\n            raise ConfigurationError(\n                \"client side encryption requires the pymongocrypt library: \"\n                \"install a compatible version with: \"\n                \"python -m pip install pymongo['encryption']\")\n\n        self._kms_providers = kms_providers\n        self._key_vault_namespace = key_vault_namespace\n        self._key_vault_client = key_vault_client\n        self._schema_map = schema_map\n        self._bypass_auto_encryption = bypass_auto_encryption\n        self._mongocryptd_uri = mongocryptd_uri\n        self._mongocryptd_bypass_spawn = mongocryptd_bypass_spawn\n        self._mongocryptd_spawn_path = mongocryptd_spawn_path\n        self._mongocryptd_spawn_args = (copy.copy(mongocryptd_spawn_args) or\n                                        ['--idleShutdownTimeoutSecs=60'])\n        if not isinstance(self._mongocryptd_spawn_args, list):\n            raise TypeError('mongocryptd_spawn_args must be a list')\n        if not any('idleShutdownTimeoutSecs' in s\n                   for s in self._mongocryptd_spawn_args):\n            self._mongocryptd_spawn_args.append('--idleShutdownTimeoutSecs=60')\n\n\ndef validate_auto_encryption_opts_or_none(option, value):\n    \"\"\"Validate the driver keyword arg.\"\"\"\n    if value is None:\n        return value\n    if not isinstance(value, AutoEncryptionOpts):\n        raise TypeError(\"%s must be an instance of AutoEncryptionOpts\" % (\n            option,))\n\n    return value\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/errors.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Exceptions raised by PyMongo.\"\"\"\n\nimport sys\n\nfrom bson.errors import *\n\ntry:\n    from ssl import CertificateError\nexcept ImportError:\n    from pymongo.ssl_match_hostname import CertificateError\n\n\nclass PyMongoError(Exception):\n    \"\"\"Base class for all PyMongo exceptions.\"\"\"\n    def __init__(self, message='', error_labels=None):\n        super(PyMongoError, self).__init__(message)\n        self._message = message\n        self._error_labels = set(error_labels or [])\n\n    def has_error_label(self, label):\n        \"\"\"Return True if this error contains the given label.\n\n        .. versionadded:: 3.7\n        \"\"\"\n        return label in self._error_labels\n\n    def _add_error_label(self, label):\n        \"\"\"Add the given label to this error.\"\"\"\n        self._error_labels.add(label)\n\n    def _remove_error_label(self, label):\n        \"\"\"Remove the given label from this error.\"\"\"\n        self._error_labels.remove(label)\n\n    def __str__(self):\n        if sys.version_info[0] == 2 and isinstance(self._message, unicode):\n            return self._message.encode('utf-8', errors='replace')\n        return str(self._message)\n\n\nclass ProtocolError(PyMongoError):\n    \"\"\"Raised for failures related to the wire protocol.\"\"\"\n\n\nclass ConnectionFailure(PyMongoError):\n    \"\"\"Raised when a connection to the database cannot be made or is lost.\"\"\"\n    def __init__(self, message='', error_labels=None):\n        if error_labels is None:\n            # Connection errors are transient errors by default.\n            error_labels = (\"TransientTransactionError\",)\n        super(ConnectionFailure, self).__init__(\n            message, error_labels=error_labels)\n\n\nclass AutoReconnect(ConnectionFailure):\n    \"\"\"Raised when a connection to the database is lost and an attempt to\n    auto-reconnect will be made.\n\n    In order to auto-reconnect you must handle this exception, recognizing that\n    the operation which caused it has not necessarily succeeded. Future\n    operations will attempt to open a new connection to the database (and\n    will continue to raise this exception until the first successful\n    connection is made).\n\n    Subclass of :exc:`~pymongo.errors.ConnectionFailure`.\n    \"\"\"\n    def __init__(self, message='', errors=None):\n        super(AutoReconnect, self).__init__(message)\n        self.errors = self.details = errors or []\n\n\nclass NetworkTimeout(AutoReconnect):\n    \"\"\"An operation on an open connection exceeded socketTimeoutMS.\n\n    The remaining connections in the pool stay open. In the case of a write\n    operation, you cannot know whether it succeeded or failed.\n\n    Subclass of :exc:`~pymongo.errors.AutoReconnect`.\n    \"\"\"\n\n\nclass NotMasterError(AutoReconnect):\n    \"\"\"The server responded \"not master\" or \"node is recovering\".\n\n    These errors result from a query, write, or command. The operation failed\n    because the client thought it was using the primary but the primary has\n    stepped down, or the client thought it was using a healthy secondary but\n    the secondary is stale and trying to recover.\n\n    The client launches a refresh operation on a background thread, to update\n    its view of the server as soon as possible after throwing this exception.\n\n    Subclass of :exc:`~pymongo.errors.AutoReconnect`.\n    \"\"\"\n\n\nclass ServerSelectionTimeoutError(AutoReconnect):\n    \"\"\"Thrown when no MongoDB server is available for an operation\n\n    If there is no suitable server for an operation PyMongo tries for\n    ``serverSelectionTimeoutMS`` (default 30 seconds) to find one, then\n    throws this exception. For example, it is thrown after attempting an\n    operation when PyMongo cannot connect to any server, or if you attempt\n    an insert into a replica set that has no primary and does not elect one\n    within the timeout window, or if you attempt to query with a Read\n    Preference that the replica set cannot satisfy.\n    \"\"\"\n\n\nclass ConfigurationError(PyMongoError):\n    \"\"\"Raised when something is incorrectly configured.\n    \"\"\"\n\n\nclass OperationFailure(PyMongoError):\n    \"\"\"Raised when a database operation fails.\n\n    .. versionadded:: 2.7\n       The :attr:`details` attribute.\n    \"\"\"\n\n    def __init__(self, error, code=None, details=None):\n        error_labels = None\n        if details is not None:\n            error_labels = details.get('errorLabels')\n        super(OperationFailure, self).__init__(\n            error, error_labels=error_labels)\n        self.__code = code\n        self.__details = details\n\n    @property\n    def code(self):\n        \"\"\"The error code returned by the server, if any.\n        \"\"\"\n        return self.__code\n\n    @property\n    def details(self):\n        \"\"\"The complete error document returned by the server.\n\n        Depending on the error that occurred, the error document\n        may include useful information beyond just the error\n        message. When connected to a mongos the error document\n        may contain one or more subdocuments if errors occurred\n        on multiple shards.\n        \"\"\"\n        return self.__details\n\n\nclass CursorNotFound(OperationFailure):\n    \"\"\"Raised while iterating query results if the cursor is\n    invalidated on the server.\n\n    .. versionadded:: 2.7\n    \"\"\"\n\n\nclass ExecutionTimeout(OperationFailure):\n    \"\"\"Raised when a database operation times out, exceeding the $maxTimeMS\n    set in the query or command option.\n\n    .. note:: Requires server version **>= 2.6.0**\n\n    .. versionadded:: 2.7\n    \"\"\"\n\n\nclass WriteConcernError(OperationFailure):\n    \"\"\"Base exception type for errors raised due to write concern.\n\n    .. versionadded:: 3.0\n    \"\"\"\n\n\nclass WriteError(OperationFailure):\n    \"\"\"Base exception type for errors raised during write operations.\n\n    .. versionadded:: 3.0\n    \"\"\"\n\n\nclass WTimeoutError(WriteConcernError):\n    \"\"\"Raised when a database operation times out (i.e. wtimeout expires)\n    before replication completes.\n\n    With newer versions of MongoDB the `details` attribute may include\n    write concern fields like 'n', 'updatedExisting', or 'writtenTo'.\n\n    .. versionadded:: 2.7\n    \"\"\"\n\n\nclass DuplicateKeyError(WriteError):\n    \"\"\"Raised when an insert or update fails due to a duplicate key error.\"\"\"\n\n\nclass BulkWriteError(OperationFailure):\n    \"\"\"Exception class for bulk write errors.\n\n    .. versionadded:: 2.7\n    \"\"\"\n    def __init__(self, results):\n        super(BulkWriteError, self).__init__(\n            \"batch op errors occurred\", 65, results)\n\n\nclass InvalidOperation(PyMongoError):\n    \"\"\"Raised when a client attempts to perform an invalid operation.\"\"\"\n\n\nclass InvalidName(PyMongoError):\n    \"\"\"Raised when an invalid name is used.\"\"\"\n\n\nclass CollectionInvalid(PyMongoError):\n    \"\"\"Raised when collection validation fails.\"\"\"\n\n\nclass InvalidURI(ConfigurationError):\n    \"\"\"Raised when trying to parse an invalid mongodb URI.\"\"\"\n\n\nclass ExceededMaxWaiters(PyMongoError):\n    \"\"\"Raised when a thread tries to get a connection from a pool and\n    ``maxPoolSize * waitQueueMultiple`` threads are already waiting.\n\n    .. versionadded:: 2.6\n    \"\"\"\n    pass\n\n\nclass DocumentTooLarge(InvalidDocument):\n    \"\"\"Raised when an encoded document is too large for the connected server.\n    \"\"\"\n    pass\n\n\nclass EncryptionError(PyMongoError):\n    \"\"\"Raised when encryption or decryption fails.\n\n    This error always wraps another exception which can be retrieved via the\n    :attr:`cause` property.\n\n    .. versionadded:: 3.9\n    \"\"\"\n\n    def __init__(self, cause):\n        super(EncryptionError, self).__init__(str(cause))\n        self.__cause = cause\n\n    @property\n    def cause(self):\n        \"\"\"The exception that caused this encryption or decryption error.\"\"\"\n        return self.__cause\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/helpers.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Bits and pieces used by the driver that don't really fit elsewhere.\"\"\"\n\nimport sys\nimport traceback\n\nfrom bson.py3compat import abc, iteritems, itervalues, string_type\nfrom bson.son import SON\nfrom pymongo import ASCENDING\nfrom pymongo.errors import (CursorNotFound,\n                            DuplicateKeyError,\n                            ExecutionTimeout,\n                            NotMasterError,\n                            OperationFailure,\n                            WriteError,\n                            WriteConcernError,\n                            WTimeoutError)\n\n# From the SDAM spec, the \"node is shutting down\" codes.\n_SHUTDOWN_CODES = frozenset([\n    11600,  # InterruptedAtShutdown\n    91,     # ShutdownInProgress\n])\n# From the SDAM spec, the \"not master\" error codes are combined with the\n# \"node is recovering\" error codes (of which the \"node is shutting down\"\n# errors are a subset).\n_NOT_MASTER_CODES = frozenset([\n    10107,  # NotMaster\n    13435,  # NotMasterNoSlaveOk\n    11602,  # InterruptedDueToReplStateChange\n    13436,  # NotMasterOrSecondary\n    189,    # PrimarySteppedDown\n]) | _SHUTDOWN_CODES\n# From the retryable writes spec.\n_RETRYABLE_ERROR_CODES = _NOT_MASTER_CODES | frozenset([\n    7,     # HostNotFound\n    6,     # HostUnreachable\n    89,    # NetworkTimeout\n    9001,  # SocketException\n])\n_UUNDER = u\"_\"\n\n\ndef _gen_index_name(keys):\n    \"\"\"Generate an index name from the set of fields it is over.\"\"\"\n    return _UUNDER.join([\"%s_%s\" % item for item in keys])\n\n\ndef _index_list(key_or_list, direction=None):\n    \"\"\"Helper to generate a list of (key, direction) pairs.\n\n    Takes such a list, or a single key, or a single key and direction.\n    \"\"\"\n    if direction is not None:\n        return [(key_or_list, direction)]\n    else:\n        if isinstance(key_or_list, string_type):\n            return [(key_or_list, ASCENDING)]\n        elif not isinstance(key_or_list, (list, tuple)):\n            raise TypeError(\"if no direction is specified, \"\n                            \"key_or_list must be an instance of list\")\n        return key_or_list\n\n\ndef _index_document(index_list):\n    \"\"\"Helper to generate an index specifying document.\n\n    Takes a list of (key, direction) pairs.\n    \"\"\"\n    if isinstance(index_list, abc.Mapping):\n        raise TypeError(\"passing a dict to sort/create_index/hint is not \"\n                        \"allowed - use a list of tuples instead. did you \"\n                        \"mean %r?\" % list(iteritems(index_list)))\n    elif not isinstance(index_list, (list, tuple)):\n        raise TypeError(\"must use a list of (key, direction) pairs, \"\n                        \"not: \" + repr(index_list))\n    if not len(index_list):\n        raise ValueError(\"key_or_list must not be the empty list\")\n\n    index = SON()\n    for (key, value) in index_list:\n        if not isinstance(key, string_type):\n            raise TypeError(\"first item in each key pair must be a string\")\n        if not isinstance(value, (string_type, int, abc.Mapping)):\n            raise TypeError(\"second item in each key pair must be 1, -1, \"\n                            \"'2d', 'geoHaystack', or another valid MongoDB \"\n                            \"index specifier.\")\n        index[key] = value\n    return index\n\n\ndef _check_command_response(response, msg=None, allowable_errors=None,\n                            parse_write_concern_error=False):\n    \"\"\"Check the response to a command for errors.\n    \"\"\"\n    if \"ok\" not in response:\n        # Server didn't recognize our message as a command.\n        raise OperationFailure(response.get(\"$err\"),\n                               response.get(\"code\"),\n                               response)\n\n    if parse_write_concern_error and 'writeConcernError' in response:\n        _raise_write_concern_error(response['writeConcernError'])\n\n    if not response[\"ok\"]:\n\n        details = response\n        # Mongos returns the error details in a 'raw' object\n        # for some errors.\n        if \"raw\" in response:\n            for shard in itervalues(response[\"raw\"]):\n                # Grab the first non-empty raw error from a shard.\n                if shard.get(\"errmsg\") and not shard.get(\"ok\"):\n                    details = shard\n                    break\n\n        errmsg = details[\"errmsg\"]\n        if allowable_errors is None or errmsg not in allowable_errors:\n\n            code = details.get(\"code\")\n            # Server is \"not master\" or \"recovering\"\n            if code in _NOT_MASTER_CODES:\n                raise NotMasterError(errmsg, response)\n            elif (\"not master\" in errmsg\n                  or \"node is recovering\" in errmsg):\n                raise NotMasterError(errmsg, response)\n\n            # Server assertion failures\n            if errmsg == \"db assertion failure\":\n                errmsg = (\"db assertion failure, assertion: '%s'\" %\n                          details.get(\"assertion\", \"\"))\n                raise OperationFailure(errmsg,\n                                       details.get(\"assertionCode\"),\n                                       response)\n\n            # Other errors\n            # findAndModify with upsert can raise duplicate key error\n            if code in (11000, 11001, 12582):\n                raise DuplicateKeyError(errmsg, code, response)\n            elif code == 50:\n                raise ExecutionTimeout(errmsg, code, response)\n            elif code == 43:\n                raise CursorNotFound(errmsg, code, response)\n\n            msg = msg or \"%s\"\n            raise OperationFailure(msg % errmsg, code, response)\n\n\ndef _check_gle_response(result):\n    \"\"\"Return getlasterror response as a dict, or raise OperationFailure.\"\"\"\n    # Did getlasterror itself fail?\n    _check_command_response(result)\n\n    if result.get(\"wtimeout\", False):\n        # MongoDB versions before 1.8.0 return the error message in an \"errmsg\"\n        # field. If \"errmsg\" exists \"err\" will also exist set to None, so we\n        # have to check for \"errmsg\" first.\n        raise WTimeoutError(result.get(\"errmsg\", result.get(\"err\")),\n                            result.get(\"code\"),\n                            result)\n\n    error_msg = result.get(\"err\", \"\")\n    if error_msg is None:\n        return result\n\n    if error_msg.startswith(\"not master\"):\n        raise NotMasterError(error_msg, result)\n\n    details = result\n\n    # mongos returns the error code in an error object for some errors.\n    if \"errObjects\" in result:\n        for errobj in result[\"errObjects\"]:\n            if errobj.get(\"err\") == error_msg:\n                details = errobj\n                break\n\n    code = details.get(\"code\")\n    if code in (11000, 11001, 12582):\n        raise DuplicateKeyError(details[\"err\"], code, result)\n    raise OperationFailure(details[\"err\"], code, result)\n\n\ndef _raise_last_write_error(write_errors):\n    # If the last batch had multiple errors only report\n    # the last error to emulate continue_on_error.\n    error = write_errors[-1]\n    if error.get(\"code\") == 11000:\n        raise DuplicateKeyError(error.get(\"errmsg\"), 11000, error)\n    raise WriteError(error.get(\"errmsg\"), error.get(\"code\"), error)\n\n\ndef _raise_write_concern_error(error):\n    if \"errInfo\" in error and error[\"errInfo\"].get('wtimeout'):\n        # Make sure we raise WTimeoutError\n        raise WTimeoutError(\n            error.get(\"errmsg\"), error.get(\"code\"), error)\n    raise WriteConcernError(\n        error.get(\"errmsg\"), error.get(\"code\"), error)\n\n\ndef _check_write_command_response(result):\n    \"\"\"Backward compatibility helper for write command error handling.\n    \"\"\"\n    # Prefer write errors over write concern errors\n    write_errors = result.get(\"writeErrors\")\n    if write_errors:\n        _raise_last_write_error(write_errors)\n\n    error = result.get(\"writeConcernError\")\n    if error:\n        _raise_write_concern_error(error)\n\n\ndef _raise_last_error(bulk_write_result):\n    \"\"\"Backward compatibility helper for insert error handling.\n    \"\"\"\n    # Prefer write errors over write concern errors\n    write_errors = bulk_write_result.get(\"writeErrors\")\n    if write_errors:\n        _raise_last_write_error(write_errors)\n\n    _raise_write_concern_error(bulk_write_result[\"writeConcernErrors\"][-1])\n\n\ndef _fields_list_to_dict(fields, option_name):\n    \"\"\"Takes a sequence of field names and returns a matching dictionary.\n\n    [\"a\", \"b\"] becomes {\"a\": 1, \"b\": 1}\n\n    and\n\n    [\"a.b.c\", \"d\", \"a.c\"] becomes {\"a.b.c\": 1, \"d\": 1, \"a.c\": 1}\n    \"\"\"\n    if isinstance(fields, abc.Mapping):\n        return fields\n\n    if isinstance(fields, (abc.Sequence, abc.Set)):\n        if not all(isinstance(field, string_type) for field in fields):\n            raise TypeError(\"%s must be a list of key names, each an \"\n                            \"instance of %s\" % (option_name,\n                                                string_type.__name__))\n        return dict.fromkeys(fields, 1)\n\n    raise TypeError(\"%s must be a mapping or \"\n                    \"list of key names\" % (option_name,))\n\n\ndef _handle_exception():\n    \"\"\"Print exceptions raised by subscribers to stderr.\"\"\"\n    # Heavily influenced by logging.Handler.handleError.\n\n    # See note here:\n    # https://docs.python.org/3.4/library/sys.html#sys.__stderr__\n    if sys.stderr:\n        einfo = sys.exc_info()\n        try:\n            traceback.print_exception(einfo[0], einfo[1], einfo[2],\n                                      None, sys.stderr)\n        except IOError:\n            pass\n        finally:\n            del einfo\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/ismaster.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Parse a response to the 'ismaster' command.\"\"\"\n\nimport itertools\n\nfrom bson.py3compat import imap\nfrom pymongo import common\nfrom pymongo.server_type import SERVER_TYPE\n\n\ndef _get_server_type(doc):\n    \"\"\"Determine the server type from an ismaster response.\"\"\"\n    if not doc.get('ok'):\n        return SERVER_TYPE.Unknown\n\n    if doc.get('isreplicaset'):\n        return SERVER_TYPE.RSGhost\n    elif doc.get('setName'):\n        if doc.get('hidden'):\n            return SERVER_TYPE.RSOther\n        elif doc.get('ismaster'):\n            return SERVER_TYPE.RSPrimary\n        elif doc.get('secondary'):\n            return SERVER_TYPE.RSSecondary\n        elif doc.get('arbiterOnly'):\n            return SERVER_TYPE.RSArbiter\n        else:\n            return SERVER_TYPE.RSOther\n    elif doc.get('msg') == 'isdbgrid':\n        return SERVER_TYPE.Mongos\n    else:\n        return SERVER_TYPE.Standalone\n\n\nclass IsMaster(object):\n    __slots__ = ('_doc', '_server_type', '_is_writable', '_is_readable')\n\n    def __init__(self, doc):\n        \"\"\"Parse an ismaster response from the server.\"\"\"\n        self._server_type = _get_server_type(doc)\n        self._doc = doc\n        self._is_writable = self._server_type in (\n            SERVER_TYPE.RSPrimary,\n            SERVER_TYPE.Standalone,\n            SERVER_TYPE.Mongos)\n\n        self._is_readable = (\n            self.server_type == SERVER_TYPE.RSSecondary\n            or self._is_writable)\n\n    @property\n    def document(self):\n        \"\"\"The complete ismaster command response document.\n\n        .. versionadded:: 3.4\n        \"\"\"\n        return self._doc.copy()\n\n    @property\n    def server_type(self):\n        return self._server_type\n\n    @property\n    def all_hosts(self):\n        \"\"\"List of hosts, passives, and arbiters known to this server.\"\"\"\n        return set(imap(common.clean_node, itertools.chain(\n            self._doc.get('hosts', []),\n            self._doc.get('passives', []),\n            self._doc.get('arbiters', []))))\n\n    @property\n    def tags(self):\n        \"\"\"Replica set member tags or empty dict.\"\"\"\n        return self._doc.get('tags', {})\n\n    @property\n    def primary(self):\n        \"\"\"This server's opinion about who the primary is, or None.\"\"\"\n        if self._doc.get('primary'):\n            return common.partition_node(self._doc['primary'])\n        else:\n            return None\n\n    @property\n    def replica_set_name(self):\n        \"\"\"Replica set name or None.\"\"\"\n        return self._doc.get('setName')\n\n    @property\n    def max_bson_size(self):\n        return self._doc.get('maxBsonObjectSize', common.MAX_BSON_SIZE)\n\n    @property\n    def max_message_size(self):\n        return self._doc.get('maxMessageSizeBytes', 2 * self.max_bson_size)\n\n    @property\n    def max_write_batch_size(self):\n        return self._doc.get('maxWriteBatchSize', common.MAX_WRITE_BATCH_SIZE)\n\n    @property\n    def min_wire_version(self):\n        return self._doc.get('minWireVersion', common.MIN_WIRE_VERSION)\n\n    @property\n    def max_wire_version(self):\n        return self._doc.get('maxWireVersion', common.MAX_WIRE_VERSION)\n\n    @property\n    def set_version(self):\n        return self._doc.get('setVersion')\n\n    @property\n    def election_id(self):\n        return self._doc.get('electionId')\n\n    @property\n    def cluster_time(self):\n        return self._doc.get('$clusterTime')\n\n    @property\n    def logical_session_timeout_minutes(self):\n        return self._doc.get('logicalSessionTimeoutMinutes')\n\n    @property\n    def is_writable(self):\n        return self._is_writable\n\n    @property\n    def is_readable(self):\n        return self._is_readable\n\n    @property\n    def me(self):\n        me = self._doc.get('me')\n        if me:\n            return common.clean_node(me)\n\n    @property\n    def last_write_date(self):\n        return self._doc.get('lastWrite', {}).get('lastWriteDate')\n\n    @property\n    def compressors(self):\n        return self._doc.get('compression')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/max_staleness_selectors.py",
    "content": "# Copyright 2016 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Criteria to select ServerDescriptions based on maxStalenessSeconds.\n\nThe Max Staleness Spec says: When there is a known primary P,\na secondary S's staleness is estimated with this formula:\n\n  (S.lastUpdateTime - S.lastWriteDate) - (P.lastUpdateTime - P.lastWriteDate)\n  + heartbeatFrequencyMS\n\nWhen there is no known primary, a secondary S's staleness is estimated with:\n\n  SMax.lastWriteDate - S.lastWriteDate + heartbeatFrequencyMS\n\nwhere \"SMax\" is the secondary with the greatest lastWriteDate.\n\"\"\"\n\nfrom pymongo.errors import ConfigurationError\nfrom pymongo.server_type import SERVER_TYPE\n\n\n# Constant defined in Max Staleness Spec: An idle primary writes a no-op every\n# 10 seconds to refresh secondaries' lastWriteDate values.\nIDLE_WRITE_PERIOD = 10\nSMALLEST_MAX_STALENESS = 90\n\n\ndef _validate_max_staleness(max_staleness,\n                            heartbeat_frequency):\n    # We checked for max staleness -1 before this, it must be positive here.\n    if max_staleness < heartbeat_frequency + IDLE_WRITE_PERIOD:\n        raise ConfigurationError(\n            \"maxStalenessSeconds must be at least heartbeatFrequencyMS +\"\n            \" %d seconds. maxStalenessSeconds is set to %d,\"\n            \" heartbeatFrequencyMS is set to %d.\" % (\n                IDLE_WRITE_PERIOD, max_staleness, heartbeat_frequency * 1000))\n\n    if max_staleness < SMALLEST_MAX_STALENESS:\n        raise ConfigurationError(\n            \"maxStalenessSeconds must be at least %d. \"\n            \"maxStalenessSeconds is set to %d.\" % (\n                SMALLEST_MAX_STALENESS, max_staleness))\n\n\ndef _with_primary(max_staleness, selection):\n    \"\"\"Apply max_staleness, in seconds, to a Selection with a known primary.\"\"\"\n    primary = selection.primary\n    sds = []\n\n    for s in selection.server_descriptions:\n        if s.server_type == SERVER_TYPE.RSSecondary:\n            # See max-staleness.rst for explanation of this formula.\n            staleness = (\n                (s.last_update_time - s.last_write_date) -\n                (primary.last_update_time - primary.last_write_date) +\n                selection.heartbeat_frequency)\n\n            if staleness <= max_staleness:\n                sds.append(s)\n        else:\n            sds.append(s)\n\n    return selection.with_server_descriptions(sds)\n\n\ndef _no_primary(max_staleness, selection):\n    \"\"\"Apply max_staleness, in seconds, to a Selection with no known primary.\"\"\"\n    # Secondary that's replicated the most recent writes.\n    smax = selection.secondary_with_max_last_write_date()\n    if not smax:\n        # No secondaries and no primary, short-circuit out of here.\n        return selection.with_server_descriptions([])\n\n    sds = []\n\n    for s in selection.server_descriptions:\n        if s.server_type == SERVER_TYPE.RSSecondary:\n            # See max-staleness.rst for explanation of this formula.\n            staleness = (smax.last_write_date -\n                         s.last_write_date +\n                         selection.heartbeat_frequency)\n\n            if staleness <= max_staleness:\n                sds.append(s)\n        else:\n            sds.append(s)\n\n    return selection.with_server_descriptions(sds)\n\n\ndef select(max_staleness, selection):\n    \"\"\"Apply max_staleness, in seconds, to a Selection.\"\"\"\n    if max_staleness == -1:\n        return selection\n\n    # Server Selection Spec: If the TopologyType is ReplicaSetWithPrimary or\n    # ReplicaSetNoPrimary, a client MUST raise an error if maxStaleness <\n    # heartbeatFrequency + IDLE_WRITE_PERIOD, or if maxStaleness < 90.\n    _validate_max_staleness(max_staleness, selection.heartbeat_frequency)\n\n    if selection.primary:\n        return _with_primary(max_staleness, selection)\n    else:\n        return _no_primary(max_staleness, selection)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/message.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for creating `messages\n<http://www.mongodb.org/display/DOCS/Mongo+Wire+Protocol>`_ to be sent to\nMongoDB.\n\n.. note:: This module is for internal use and is generally not needed by\n   application developers.\n\"\"\"\n\nimport datetime\nimport random\nimport struct\n\nimport bson\nfrom bson import (CodecOptions,\n                  _dict_to_bson,\n                  _make_c_string)\nfrom bson.codec_options import DEFAULT_CODEC_OPTIONS\nfrom bson.raw_bson import _inflate_bson, DEFAULT_RAW_BSON_OPTIONS\nfrom bson.py3compat import b, StringIO\nfrom bson.son import SON\n\ntry:\n    from pymongo import _cmessage\n    _use_c = True\nexcept ImportError:\n    _use_c = False\nfrom pymongo.errors import (ConfigurationError,\n                            CursorNotFound,\n                            DocumentTooLarge,\n                            ExecutionTimeout,\n                            InvalidOperation,\n                            NotMasterError,\n                            OperationFailure,\n                            ProtocolError)\nfrom pymongo.read_concern import DEFAULT_READ_CONCERN\nfrom pymongo.read_preferences import ReadPreference\nfrom pymongo.write_concern import WriteConcern\n\n\nMAX_INT32 = 2147483647\nMIN_INT32 = -2147483648\n\n# Overhead allowed for encoded command documents.\n_COMMAND_OVERHEAD = 16382\n\n_INSERT = 0\n_UPDATE = 1\n_DELETE = 2\n\n_EMPTY   = b''\n_BSONOBJ = b'\\x03'\n_ZERO_8  = b'\\x00'\n_ZERO_16 = b'\\x00\\x00'\n_ZERO_32 = b'\\x00\\x00\\x00\\x00'\n_ZERO_64 = b'\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00'\n_SKIPLIM = b'\\x00\\x00\\x00\\x00\\xff\\xff\\xff\\xff'\n_OP_MAP = {\n    _INSERT: b'\\x04documents\\x00\\x00\\x00\\x00\\x00',\n    _UPDATE: b'\\x04updates\\x00\\x00\\x00\\x00\\x00',\n    _DELETE: b'\\x04deletes\\x00\\x00\\x00\\x00\\x00',\n}\n_FIELD_MAP = {\n    'insert': 'documents',\n    'update': 'updates',\n    'delete': 'deletes'\n}\n\n_UJOIN = u\"%s.%s\"\n\n_UNICODE_REPLACE_CODEC_OPTIONS = CodecOptions(\n    unicode_decode_error_handler='replace')\n\n\ndef _randint():\n    \"\"\"Generate a pseudo random 32 bit integer.\"\"\"\n    return random.randint(MIN_INT32, MAX_INT32)\n\n\ndef _maybe_add_read_preference(spec, read_preference):\n    \"\"\"Add $readPreference to spec when appropriate.\"\"\"\n    mode = read_preference.mode\n    tag_sets = read_preference.tag_sets\n    max_staleness = read_preference.max_staleness\n    # Only add $readPreference if it's something other than primary to avoid\n    # problems with mongos versions that don't support read preferences. Also,\n    # for maximum backwards compatibility, don't add $readPreference for\n    # secondaryPreferred unless tags or maxStalenessSeconds are in use (setting\n    # the slaveOkay bit has the same effect).\n    if mode and (\n        mode != ReadPreference.SECONDARY_PREFERRED.mode\n        or tag_sets != [{}]\n        or max_staleness != -1):\n\n        if \"$query\" not in spec:\n            spec = SON([(\"$query\", spec)])\n        spec[\"$readPreference\"] = read_preference.document\n    return spec\n\n\ndef _convert_exception(exception):\n    \"\"\"Convert an Exception into a failure document for publishing.\"\"\"\n    return {'errmsg': str(exception),\n            'errtype': exception.__class__.__name__}\n\n\ndef _convert_write_result(operation, command, result):\n    \"\"\"Convert a legacy write result to write commmand format.\"\"\"\n\n    # Based on _merge_legacy from bulk.py\n    affected = result.get(\"n\", 0)\n    res = {\"ok\": 1, \"n\": affected}\n    errmsg = result.get(\"errmsg\", result.get(\"err\", \"\"))\n    if errmsg:\n        # The write was successful on at least the primary so don't return.\n        if result.get(\"wtimeout\"):\n            res[\"writeConcernError\"] = {\"errmsg\": errmsg,\n                                        \"code\": 64,\n                                        \"errInfo\": {\"wtimeout\": True}}\n        else:\n            # The write failed.\n            error = {\"index\": 0,\n                     \"code\": result.get(\"code\", 8),\n                     \"errmsg\": errmsg}\n            if \"errInfo\" in result:\n                error[\"errInfo\"] = result[\"errInfo\"]\n            res[\"writeErrors\"] = [error]\n            return res\n    if operation == \"insert\":\n        # GLE result for insert is always 0 in most MongoDB versions.\n        res[\"n\"] = len(command['documents'])\n    elif operation == \"update\":\n        if \"upserted\" in result:\n            res[\"upserted\"] = [{\"index\": 0, \"_id\": result[\"upserted\"]}]\n        # Versions of MongoDB before 2.6 don't return the _id for an\n        # upsert if _id is not an ObjectId.\n        elif result.get(\"updatedExisting\") is False and affected == 1:\n            # If _id is in both the update document *and* the query spec\n            # the update document _id takes precedence.\n            update = command['updates'][0]\n            _id = update[\"u\"].get(\"_id\", update[\"q\"].get(\"_id\"))\n            res[\"upserted\"] = [{\"index\": 0, \"_id\": _id}]\n    return res\n\n\n_OPTIONS = SON([\n    ('tailable', 2),\n    ('oplogReplay', 8),\n    ('noCursorTimeout', 16),\n    ('awaitData', 32),\n    ('allowPartialResults', 128)])\n\n\n_MODIFIERS = SON([\n    ('$query', 'filter'),\n    ('$orderby', 'sort'),\n    ('$hint', 'hint'),\n    ('$comment', 'comment'),\n    ('$maxScan', 'maxScan'),\n    ('$maxTimeMS', 'maxTimeMS'),\n    ('$max', 'max'),\n    ('$min', 'min'),\n    ('$returnKey', 'returnKey'),\n    ('$showRecordId', 'showRecordId'),\n    ('$showDiskLoc', 'showRecordId'),  # <= MongoDb 3.0\n    ('$snapshot', 'snapshot')])\n\n\ndef _gen_find_command(coll, spec, projection, skip, limit, batch_size, options,\n                      read_concern, collation=None, session=None):\n    \"\"\"Generate a find command document.\"\"\"\n    cmd = SON([('find', coll)])\n    if '$query' in spec:\n        cmd.update([(_MODIFIERS[key], val) if key in _MODIFIERS else (key, val)\n                    for key, val in spec.items()])\n        if '$explain' in cmd:\n            cmd.pop('$explain')\n        if '$readPreference' in cmd:\n            cmd.pop('$readPreference')\n    else:\n        cmd['filter'] = spec\n\n    if projection:\n        cmd['projection'] = projection\n    if skip:\n        cmd['skip'] = skip\n    if limit:\n        cmd['limit'] = abs(limit)\n        if limit < 0:\n            cmd['singleBatch'] = True\n    if batch_size:\n        cmd['batchSize'] = batch_size\n    if read_concern.level and not (session and session._in_transaction):\n        cmd['readConcern'] = read_concern.document\n    if collation:\n        cmd['collation'] = collation\n    if options:\n        cmd.update([(opt, True)\n                    for opt, val in _OPTIONS.items()\n                    if options & val])\n    return cmd\n\n\ndef _gen_get_more_command(cursor_id, coll, batch_size, max_await_time_ms):\n    \"\"\"Generate a getMore command document.\"\"\"\n    cmd = SON([('getMore', cursor_id),\n               ('collection', coll)])\n    if batch_size:\n        cmd['batchSize'] = batch_size\n    if max_await_time_ms is not None:\n        cmd['maxTimeMS'] = max_await_time_ms\n    return cmd\n\n\nclass _Query(object):\n    \"\"\"A query operation.\"\"\"\n\n    __slots__ = ('flags', 'db', 'coll', 'ntoskip', 'spec',\n                 'fields', 'codec_options', 'read_preference', 'limit',\n                 'batch_size', 'name', 'read_concern', 'collation',\n                 'session', 'client', '_as_command')\n\n    # For compatibility with the _GetMore class.\n    exhaust_mgr = None\n    cursor_id = None\n\n    def __init__(self, flags, db, coll, ntoskip, spec, fields,\n                 codec_options, read_preference, limit,\n                 batch_size, read_concern, collation, session, client):\n        self.flags = flags\n        self.db = db\n        self.coll = coll\n        self.ntoskip = ntoskip\n        self.spec = spec\n        self.fields = fields\n        self.codec_options = codec_options\n        self.read_preference = read_preference\n        self.read_concern = read_concern\n        self.limit = limit\n        self.batch_size = batch_size\n        self.collation = collation\n        self.session = session\n        self.client = client\n        self.name = 'find'\n        self._as_command = None\n\n    def namespace(self):\n        return _UJOIN % (self.db, self.coll)\n\n    def use_command(self, sock_info, exhaust):\n        use_find_cmd = False\n        if sock_info.max_wire_version >= 4:\n            if not exhaust:\n                use_find_cmd = True\n        elif not self.read_concern.ok_for_legacy:\n            raise ConfigurationError(\n                'read concern level of %s is not valid '\n                'with a max wire version of %d.'\n                % (self.read_concern.level,\n                   sock_info.max_wire_version))\n\n        if sock_info.max_wire_version < 5 and self.collation is not None:\n            raise ConfigurationError(\n                'Specifying a collation is unsupported with a max wire '\n                'version of %d.' % (sock_info.max_wire_version,))\n\n        sock_info.validate_session(self.client, self.session)\n\n        return use_find_cmd\n\n    def as_command(self, sock_info):\n        \"\"\"Return a find command document for this query.\"\"\"\n        # We use the command twice: on the wire and for command monitoring.\n        # Generate it once, for speed and to avoid repeating side-effects.\n        if self._as_command is not None:\n            return self._as_command\n\n        explain = '$explain' in self.spec\n        cmd = _gen_find_command(\n            self.coll, self.spec, self.fields, self.ntoskip,\n            self.limit, self.batch_size, self.flags, self.read_concern,\n            self.collation, self.session)\n        if explain:\n            self.name = 'explain'\n            cmd = SON([('explain', cmd)])\n        session = self.session\n        if session:\n            session._apply_to(cmd, False, self.read_preference)\n            # Explain does not support readConcern.\n            if (not explain and session.options.causal_consistency\n                    and session.operation_time is not None\n                    and not session._in_transaction):\n                cmd.setdefault(\n                    'readConcern', {})[\n                    'afterClusterTime'] = session.operation_time\n        sock_info.send_cluster_time(cmd, session, self.client)\n        # Support auto encryption\n        client = self.client\n        if (client._encrypter and\n                not client._encrypter._bypass_auto_encryption):\n            cmd = client._encrypter.encrypt(\n                self.db, cmd, False, self.codec_options)\n        self._as_command = cmd, self.db\n        return self._as_command\n\n    def get_message(self, set_slave_ok, sock_info, use_cmd=False):\n        \"\"\"Get a query message, possibly setting the slaveOk bit.\"\"\"\n        if set_slave_ok:\n            # Set the slaveOk bit.\n            flags = self.flags | 4\n        else:\n            flags = self.flags\n\n        ns = self.namespace()\n        spec = self.spec\n\n        if use_cmd:\n            spec = self.as_command(sock_info)[0]\n            if sock_info.op_msg_enabled:\n                request_id, msg, size, _ = _op_msg(\n                    0, spec, self.db, self.read_preference,\n                    set_slave_ok, False, self.codec_options,\n                    ctx=sock_info.compression_context)\n                return request_id, msg, size\n            ns = _UJOIN % (self.db, \"$cmd\")\n            ntoreturn = -1  # All DB commands return 1 document\n        else:\n            # OP_QUERY treats ntoreturn of -1 and 1 the same, return\n            # one document and close the cursor. We have to use 2 for\n            # batch size if 1 is specified.\n            ntoreturn = self.batch_size == 1 and 2 or self.batch_size\n            if self.limit:\n                if ntoreturn:\n                    ntoreturn = min(self.limit, ntoreturn)\n                else:\n                    ntoreturn = self.limit\n\n        if sock_info.is_mongos:\n            spec = _maybe_add_read_preference(spec,\n                                              self.read_preference)\n\n        return query(flags, ns, self.ntoskip, ntoreturn,\n                     spec, None if use_cmd else self.fields,\n                     self.codec_options, ctx=sock_info.compression_context)\n\n\nclass _GetMore(object):\n    \"\"\"A getmore operation.\"\"\"\n\n    __slots__ = ('db', 'coll', 'ntoreturn', 'cursor_id', 'max_await_time_ms',\n                 'codec_options', 'read_preference', 'session', 'client',\n                 'exhaust_mgr', '_as_command')\n\n    name = 'getMore'\n\n    def __init__(self, db, coll, ntoreturn, cursor_id, codec_options,\n                 read_preference, session, client, max_await_time_ms,\n                 exhaust_mgr):\n        self.db = db\n        self.coll = coll\n        self.ntoreturn = ntoreturn\n        self.cursor_id = cursor_id\n        self.codec_options = codec_options\n        self.read_preference = read_preference\n        self.session = session\n        self.client = client\n        self.max_await_time_ms = max_await_time_ms\n        self.exhaust_mgr = exhaust_mgr\n        self._as_command = None\n\n    def namespace(self):\n        return _UJOIN % (self.db, self.coll)\n\n    def use_command(self, sock_info, exhaust):\n        sock_info.validate_session(self.client, self.session)\n        return sock_info.max_wire_version >= 4 and not exhaust\n\n    def as_command(self, sock_info):\n        \"\"\"Return a getMore command document for this query.\"\"\"\n        # See _Query.as_command for an explanation of this caching.\n        if self._as_command is not None:\n            return self._as_command\n\n        cmd = _gen_get_more_command(self.cursor_id, self.coll,\n                                    self.ntoreturn,\n                                    self.max_await_time_ms)\n\n        if self.session:\n            self.session._apply_to(cmd, False, self.read_preference)\n        sock_info.send_cluster_time(cmd, self.session, self.client)\n        # Support auto encryption\n        client = self.client\n        if (client._encrypter and\n                not client._encrypter._bypass_auto_encryption):\n            cmd = client._encrypter.encrypt(\n                self.db, cmd, False, self.codec_options)\n        self._as_command = cmd, self.db\n        return self._as_command\n\n    def get_message(self, dummy0, sock_info, use_cmd=False):\n        \"\"\"Get a getmore message.\"\"\"\n\n        ns = self.namespace()\n        ctx = sock_info.compression_context\n\n        if use_cmd:\n            spec = self.as_command(sock_info)[0]\n            if sock_info.op_msg_enabled:\n                request_id, msg, size, _ = _op_msg(\n                    0, spec, self.db, ReadPreference.PRIMARY,\n                    False, False, self.codec_options,\n                    ctx=sock_info.compression_context)\n                return request_id, msg, size\n            ns = _UJOIN % (self.db, \"$cmd\")\n            return query(0, ns, 0, -1, spec, None, self.codec_options, ctx=ctx)\n\n        return get_more(ns, self.ntoreturn, self.cursor_id, ctx)\n\n\n# TODO: Use OP_MSG once the server is able to respond with document streams.\nclass _RawBatchQuery(_Query):\n    def use_command(self, socket_info, exhaust):\n        # Compatibility checks.\n        super(_RawBatchQuery, self).use_command(socket_info, exhaust)\n\n        return False\n\n    def get_message(self, set_slave_ok, sock_info, use_cmd=False):\n        # Always pass False for use_cmd.\n        return super(_RawBatchQuery, self).get_message(\n            set_slave_ok, sock_info, False)\n\n\nclass _RawBatchGetMore(_GetMore):\n    def use_command(self, socket_info, exhaust):\n        return False\n\n    def get_message(self, set_slave_ok, sock_info, use_cmd=False):\n        # Always pass False for use_cmd.\n        return super(_RawBatchGetMore, self).get_message(\n            set_slave_ok, sock_info, False)\n\n\nclass _CursorAddress(tuple):\n    \"\"\"The server address (host, port) of a cursor, with namespace property.\"\"\"\n\n    def __new__(cls, address, namespace):\n        self = tuple.__new__(cls, address)\n        self.__namespace = namespace\n        return self\n\n    @property\n    def namespace(self):\n        \"\"\"The namespace this cursor.\"\"\"\n        return self.__namespace\n\n    def __hash__(self):\n        # Two _CursorAddress instances with different namespaces\n        # must not hash the same.\n        return (self + (self.__namespace,)).__hash__()\n\n    def __eq__(self, other):\n        if isinstance(other, _CursorAddress):\n            return (tuple(self) == tuple(other)\n                    and self.namespace == other.namespace)\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n\n\n_pack_compression_header = struct.Struct(\"<iiiiiiB\").pack\n_COMPRESSION_HEADER_SIZE = 25\n\ndef _compress(operation, data, ctx):\n    \"\"\"Takes message data, compresses it, and adds an OP_COMPRESSED header.\"\"\"\n    compressed = ctx.compress(data)\n    request_id = _randint()\n\n    header = _pack_compression_header(\n        _COMPRESSION_HEADER_SIZE + len(compressed), # Total message length\n        request_id, # Request id\n        0, # responseTo\n        2012, # operation id\n        operation, # original operation id\n        len(data), # uncompressed message length\n        ctx.compressor_id) # compressor id\n    return request_id, header + compressed\n\n\ndef __last_error(namespace, args):\n    \"\"\"Data to send to do a lastError.\n    \"\"\"\n    cmd = SON([(\"getlasterror\", 1)])\n    cmd.update(args)\n    splitns = namespace.split('.', 1)\n    return query(0, splitns[0] + '.$cmd', 0, -1, cmd,\n                 None, DEFAULT_CODEC_OPTIONS)\n\n\n_pack_header = struct.Struct(\"<iiii\").pack\n\n\ndef __pack_message(operation, data):\n    \"\"\"Takes message data and adds a message header based on the operation.\n\n    Returns the resultant message string.\n    \"\"\"\n    rid = _randint()\n    message = _pack_header(16 + len(data), rid, 0, operation)\n    return rid, message + data\n\n\n_pack_int = struct.Struct(\"<i\").pack\n\n\ndef _insert(collection_name, docs, check_keys, flags, opts):\n    \"\"\"Get an OP_INSERT message\"\"\"\n    encode = _dict_to_bson  # Make local. Uses extensions.\n    if len(docs) == 1:\n        encoded = encode(docs[0], check_keys, opts)\n        return b\"\".join([\n            b\"\\x00\\x00\\x00\\x00\",  # Flags don't matter for one doc.\n            _make_c_string(collection_name),\n            encoded]), len(encoded)\n\n    encoded = [encode(doc, check_keys, opts) for doc in docs]\n    if not encoded:\n        raise InvalidOperation(\"cannot do an empty bulk insert\")\n    return b\"\".join([\n        _pack_int(flags),\n        _make_c_string(collection_name),\n        b\"\".join(encoded)]), max(map(len, encoded))\n\n\ndef _insert_compressed(\n        collection_name, docs, check_keys, continue_on_error, opts, ctx):\n    \"\"\"Internal compressed unacknowledged insert message helper.\"\"\"\n    op_insert, max_bson_size = _insert(\n        collection_name, docs, check_keys, continue_on_error, opts)\n    rid, msg = _compress(2002, op_insert, ctx)\n    return rid, msg, max_bson_size\n\n\ndef _insert_uncompressed(collection_name, docs, check_keys,\n            safe, last_error_args, continue_on_error, opts):\n    \"\"\"Internal insert message helper.\"\"\"\n    op_insert, max_bson_size = _insert(\n        collection_name, docs, check_keys, continue_on_error, opts)\n    rid, msg = __pack_message(2002, op_insert)\n    if safe:\n        rid, gle, _ = __last_error(collection_name, last_error_args)\n        return rid, msg + gle, max_bson_size\n    return rid, msg, max_bson_size\nif _use_c:\n    _insert_uncompressed = _cmessage._insert_message\n\n\ndef insert(collection_name, docs, check_keys,\n           safe, last_error_args, continue_on_error, opts, ctx=None):\n    \"\"\"Get an **insert** message.\"\"\"\n    if ctx:\n        return _insert_compressed(\n            collection_name, docs, check_keys, continue_on_error, opts, ctx)\n    return _insert_uncompressed(collection_name, docs, check_keys, safe,\n                                last_error_args, continue_on_error, opts)\n\n\ndef _update(collection_name, upsert, multi, spec, doc, check_keys, opts):\n    \"\"\"Get an OP_UPDATE message.\"\"\"\n    flags = 0\n    if upsert:\n        flags += 1\n    if multi:\n        flags += 2\n    encode = _dict_to_bson  # Make local. Uses extensions.\n    encoded_update = encode(doc, check_keys, opts)\n    return b\"\".join([\n        _ZERO_32,\n        _make_c_string(collection_name),\n        _pack_int(flags),\n        encode(spec, False, opts),\n        encoded_update]), len(encoded_update)\n\n\ndef _update_compressed(\n        collection_name, upsert, multi, spec, doc, check_keys, opts, ctx):\n    \"\"\"Internal compressed unacknowledged update message helper.\"\"\"\n    op_update, max_bson_size = _update(\n        collection_name, upsert, multi, spec, doc, check_keys, opts)\n    rid, msg = _compress(2001, op_update, ctx)\n    return rid, msg, max_bson_size\n\n\ndef _update_uncompressed(collection_name, upsert, multi, spec,\n                         doc, safe, last_error_args, check_keys, opts):\n    \"\"\"Internal update message helper.\"\"\"\n    op_update, max_bson_size = _update(\n        collection_name, upsert, multi, spec, doc, check_keys, opts)\n    rid, msg = __pack_message(2001, op_update)\n    if safe:\n        rid, gle, _ = __last_error(collection_name, last_error_args)\n        return rid, msg + gle, max_bson_size\n    return rid, msg, max_bson_size\nif _use_c:\n    _update_uncompressed = _cmessage._update_message\n\n\ndef update(collection_name, upsert, multi, spec,\n           doc, safe, last_error_args, check_keys, opts, ctx=None):\n    \"\"\"Get an **update** message.\"\"\"\n    if ctx:\n        return _update_compressed(\n            collection_name, upsert, multi, spec, doc, check_keys, opts, ctx)\n    return _update_uncompressed(collection_name, upsert, multi, spec,\n                                doc, safe, last_error_args, check_keys, opts)\n\n\n_pack_op_msg_flags_type = struct.Struct(\"<IB\").pack\n_pack_byte = struct.Struct(\"<B\").pack\n\n\ndef _op_msg_no_header(flags, command, identifier, docs, check_keys, opts):\n    \"\"\"Get a OP_MSG message.\n\n    Note: this method handles multiple documents in a type one payload but\n    it does not perform batch splitting and the total message size is\n    only checked *after* generating the entire message.\n    \"\"\"\n    # Encode the command document in payload 0 without checking keys.\n    encoded = _dict_to_bson(command, False, opts)\n    flags_type = _pack_op_msg_flags_type(flags, 0)\n    total_size = len(encoded)\n    max_doc_size = 0\n    if identifier:\n        type_one = _pack_byte(1)\n        cstring = _make_c_string(identifier)\n        encoded_docs = [_dict_to_bson(doc, check_keys, opts) for doc in docs]\n        size = len(cstring) + sum(len(doc) for doc in encoded_docs) + 4\n        encoded_size = _pack_int(size)\n        total_size += size\n        max_doc_size = max(len(doc) for doc in encoded_docs)\n        data = ([flags_type, encoded, type_one, encoded_size, cstring] +\n                encoded_docs)\n    else:\n        data = [flags_type, encoded]\n    return b''.join(data), total_size, max_doc_size\n\n\ndef _op_msg_compressed(flags, command, identifier, docs, check_keys, opts,\n                       ctx):\n    \"\"\"Internal OP_MSG message helper.\"\"\"\n    msg, total_size, max_bson_size = _op_msg_no_header(\n        flags, command, identifier, docs, check_keys, opts)\n    rid, msg = _compress(2013, msg, ctx)\n    return rid, msg, total_size, max_bson_size\n\n\ndef _op_msg_uncompressed(flags, command, identifier, docs, check_keys, opts):\n    \"\"\"Internal compressed OP_MSG message helper.\"\"\"\n    data, total_size, max_bson_size = _op_msg_no_header(\n        flags, command, identifier, docs, check_keys, opts)\n    request_id, op_message = __pack_message(2013, data)\n    return request_id, op_message, total_size, max_bson_size\nif _use_c:\n    _op_msg_uncompressed = _cmessage._op_msg\n\n\ndef _op_msg(flags, command, dbname, read_preference, slave_ok, check_keys,\n            opts, ctx=None):\n    \"\"\"Get a OP_MSG message.\"\"\"\n    command['$db'] = dbname\n    if \"$readPreference\" not in command:\n        if slave_ok and not read_preference.mode:\n            command[\"$readPreference\"] = (\n                ReadPreference.PRIMARY_PREFERRED.document)\n        else:\n            command[\"$readPreference\"] = read_preference.document\n    name = next(iter(command))\n    try:\n        identifier = _FIELD_MAP.get(name)\n        docs = command.pop(identifier)\n    except KeyError:\n        identifier = \"\"\n        docs = None\n    try:\n        if ctx:\n            return _op_msg_compressed(\n                flags, command, identifier, docs, check_keys, opts, ctx)\n        return _op_msg_uncompressed(\n            flags, command, identifier, docs, check_keys, opts)\n    finally:\n        # Add the field back to the command.\n        if identifier:\n            command[identifier] = docs\n\n\ndef _query(options, collection_name, num_to_skip,\n           num_to_return, query, field_selector, opts, check_keys):\n    \"\"\"Get an OP_QUERY message.\"\"\"\n    encoded = _dict_to_bson(query, check_keys, opts)\n    if field_selector:\n        efs = _dict_to_bson(field_selector, False, opts)\n    else:\n        efs = b\"\"\n    max_bson_size = max(len(encoded), len(efs))\n    return b\"\".join([\n        _pack_int(options),\n        _make_c_string(collection_name),\n        _pack_int(num_to_skip),\n        _pack_int(num_to_return),\n        encoded,\n        efs]), max_bson_size\n\n\ndef _query_compressed(options, collection_name, num_to_skip,\n                      num_to_return, query, field_selector,\n                      opts, check_keys=False, ctx=None):\n    \"\"\"Internal compressed query message helper.\"\"\"\n    op_query, max_bson_size = _query(\n        options,\n        collection_name,\n        num_to_skip,\n        num_to_return,\n        query,\n        field_selector,\n        opts,\n        check_keys)\n    rid, msg = _compress(2004, op_query, ctx)\n    return rid, msg, max_bson_size\n\n\ndef _query_uncompressed(options, collection_name, num_to_skip,\n          num_to_return, query, field_selector, opts, check_keys=False):\n    \"\"\"Internal query message helper.\"\"\"\n    op_query, max_bson_size = _query(\n        options,\n        collection_name,\n        num_to_skip,\n        num_to_return,\n        query,\n        field_selector,\n        opts,\n        check_keys)\n    rid, msg = __pack_message(2004, op_query)\n    return rid, msg, max_bson_size\nif _use_c:\n    _query_uncompressed = _cmessage._query_message\n\n\ndef query(options, collection_name, num_to_skip, num_to_return,\n          query, field_selector, opts, check_keys=False, ctx=None):\n    \"\"\"Get a **query** message.\"\"\"\n    if ctx:\n        return _query_compressed(options, collection_name, num_to_skip,\n                                 num_to_return, query, field_selector,\n                                 opts, check_keys, ctx)\n    return _query_uncompressed(options, collection_name, num_to_skip,\n                               num_to_return, query, field_selector, opts,\n                               check_keys)\n\n\n_pack_long_long = struct.Struct(\"<q\").pack\n\n\ndef _get_more(collection_name, num_to_return, cursor_id):\n    \"\"\"Get an OP_GET_MORE message.\"\"\"\n    return b\"\".join([\n        _ZERO_32,\n        _make_c_string(collection_name),\n        _pack_int(num_to_return),\n        _pack_long_long(cursor_id)])\n\n\ndef _get_more_compressed(collection_name, num_to_return, cursor_id, ctx):\n    \"\"\"Internal compressed getMore message helper.\"\"\"\n    return _compress(\n        2005, _get_more(collection_name, num_to_return, cursor_id), ctx)\n\n\ndef _get_more_uncompressed(collection_name, num_to_return, cursor_id):\n    \"\"\"Internal getMore message helper.\"\"\"\n    return __pack_message(\n        2005, _get_more(collection_name, num_to_return, cursor_id))\nif _use_c:\n    _get_more_uncompressed = _cmessage._get_more_message\n\n\ndef get_more(collection_name, num_to_return, cursor_id, ctx=None):\n    \"\"\"Get a **getMore** message.\"\"\"\n    if ctx:\n        return _get_more_compressed(\n            collection_name, num_to_return, cursor_id, ctx)\n    return _get_more_uncompressed(collection_name, num_to_return, cursor_id)\n\n\ndef _delete(collection_name, spec, opts, flags):\n    \"\"\"Get an OP_DELETE message.\"\"\"\n    encoded = _dict_to_bson(spec, False, opts)  # Uses extensions.\n    return b\"\".join([\n        _ZERO_32,\n        _make_c_string(collection_name),\n        _pack_int(flags),\n        encoded]), len(encoded)\n\n\ndef _delete_compressed(collection_name, spec, opts, flags, ctx):\n    \"\"\"Internal compressed unacknowledged delete message helper.\"\"\"\n    op_delete, max_bson_size = _delete(collection_name, spec, opts, flags)\n    rid, msg = _compress(2006, op_delete, ctx)\n    return rid, msg, max_bson_size\n\n\ndef _delete_uncompressed(\n        collection_name, spec, safe, last_error_args, opts, flags=0):\n    \"\"\"Internal delete message helper.\"\"\"\n    op_delete, max_bson_size = _delete(collection_name, spec, opts, flags)\n    rid, msg = __pack_message(2006, op_delete)\n    if safe:\n        rid, gle, _ = __last_error(collection_name, last_error_args)\n        return rid, msg + gle, max_bson_size\n    return rid, msg, max_bson_size\n\n\ndef delete(\n        collection_name, spec, safe, last_error_args, opts, flags=0, ctx=None):\n    \"\"\"Get a **delete** message.\n\n    `opts` is a CodecOptions. `flags` is a bit vector that may contain\n    the SingleRemove flag or not:\n\n    http://docs.mongodb.org/meta-driver/latest/legacy/mongodb-wire-protocol/#op-delete\n    \"\"\"\n    if ctx:\n        return _delete_compressed(collection_name, spec, opts, flags, ctx)\n    return _delete_uncompressed(\n        collection_name, spec, safe, last_error_args, opts, flags)\n\n\ndef kill_cursors(cursor_ids):\n    \"\"\"Get a **killCursors** message.\n    \"\"\"\n    num_cursors = len(cursor_ids)\n    pack = struct.Struct(\"<ii\" + (\"q\" * num_cursors)).pack\n    op_kill_cursors = pack(0, num_cursors, *cursor_ids)\n    return __pack_message(2007, op_kill_cursors)\n\n\nclass _BulkWriteContext(object):\n    \"\"\"A wrapper around SocketInfo for use with write splitting functions.\"\"\"\n\n    __slots__ = ('db_name', 'command', 'sock_info', 'op_id',\n                 'name', 'field', 'publish', 'start_time', 'listeners',\n                 'session', 'compress', 'op_type', 'codec')\n\n    def __init__(self, database_name, command, sock_info, operation_id,\n                 listeners, session, op_type, codec):\n        self.db_name = database_name\n        self.command = command\n        self.sock_info = sock_info\n        self.op_id = operation_id\n        self.listeners = listeners\n        self.publish = listeners.enabled_for_commands\n        self.name = next(iter(command))\n        self.field = _FIELD_MAP[self.name]\n        self.start_time = datetime.datetime.now() if self.publish else None\n        self.session = session\n        self.compress = True if sock_info.compression_context else False\n        self.op_type = op_type\n        self.codec = codec\n\n    def _batch_command(self, docs):\n        namespace = self.db_name + '.$cmd'\n        request_id, msg, to_send = _do_bulk_write_command(\n            namespace, self.op_type, self.command, docs, self.check_keys,\n            self.codec, self)\n        if not to_send:\n            raise InvalidOperation(\"cannot do an empty bulk write\")\n        return request_id, msg, to_send\n\n    def execute(self, docs, client):\n        request_id, msg, to_send = self._batch_command(docs)\n        result = self.write_command(request_id, msg, to_send)\n        client._process_response(result, self.session)\n        return result, to_send\n\n    def execute_unack(self, docs, client):\n        request_id, msg, to_send = self._batch_command(docs)\n        # Though this isn't strictly a \"legacy\" write, the helper\n        # handles publishing commands and sending our message\n        # without receiving a result. Send 0 for max_doc_size\n        # to disable size checking. Size checking is handled while\n        # the documents are encoded to BSON.\n        self.legacy_write(request_id, msg, 0, False, to_send)\n        return to_send\n\n    @property\n    def check_keys(self):\n        \"\"\"Should we check keys for this operation type?\"\"\"\n        return self.op_type == _INSERT\n\n    @property\n    def max_bson_size(self):\n        \"\"\"A proxy for SockInfo.max_bson_size.\"\"\"\n        return self.sock_info.max_bson_size\n\n    @property\n    def max_message_size(self):\n        \"\"\"A proxy for SockInfo.max_message_size.\"\"\"\n        return self.sock_info.max_message_size\n\n    @property\n    def max_write_batch_size(self):\n        \"\"\"A proxy for SockInfo.max_write_batch_size.\"\"\"\n        return self.sock_info.max_write_batch_size\n\n    def legacy_bulk_insert(\n            self, request_id, msg, max_doc_size, acknowledged, docs, compress):\n        if compress:\n            request_id, msg = _compress(\n                2002, msg, self.sock_info.compression_context)\n        return self.legacy_write(\n            request_id, msg, max_doc_size, acknowledged, docs)\n\n    def legacy_write(self, request_id, msg, max_doc_size, acknowledged, docs):\n        \"\"\"A proxy for SocketInfo.legacy_write that handles event publishing.\n        \"\"\"\n        if self.publish:\n            duration = datetime.datetime.now() - self.start_time\n            cmd = self._start(request_id, docs)\n            start = datetime.datetime.now()\n        try:\n            result = self.sock_info.legacy_write(\n                request_id, msg, max_doc_size, acknowledged)\n            if self.publish:\n                duration = (datetime.datetime.now() - start) + duration\n                if result is not None:\n                    reply = _convert_write_result(self.name, cmd, result)\n                else:\n                    # Comply with APM spec.\n                    reply = {'ok': 1}\n                self._succeed(request_id, reply, duration)\n        except OperationFailure as exc:\n            if self.publish:\n                duration = (datetime.datetime.now() - start) + duration\n                self._fail(\n                    request_id,\n                    _convert_write_result(\n                        self.name, cmd, exc.details),\n                    duration)\n            raise\n        finally:\n            self.start_time = datetime.datetime.now()\n        return result\n\n    def write_command(self, request_id, msg, docs):\n        \"\"\"A proxy for SocketInfo.write_command that handles event publishing.\n        \"\"\"\n        if self.publish:\n            duration = datetime.datetime.now() - self.start_time\n            self._start(request_id, docs)\n            start = datetime.datetime.now()\n        try:\n            reply = self.sock_info.write_command(request_id, msg)\n            if self.publish:\n                duration = (datetime.datetime.now() - start) + duration\n                self._succeed(request_id, reply, duration)\n        except OperationFailure as exc:\n            if self.publish:\n                duration = (datetime.datetime.now() - start) + duration\n                self._fail(request_id, exc.details, duration)\n            raise\n        finally:\n            self.start_time = datetime.datetime.now()\n        return reply\n\n    def _start(self, request_id, docs):\n        \"\"\"Publish a CommandStartedEvent.\"\"\"\n        cmd = self.command.copy()\n        cmd[self.field] = docs\n        self.listeners.publish_command_start(\n            cmd, self.db_name,\n            request_id, self.sock_info.address, self.op_id)\n        return cmd\n\n    def _succeed(self, request_id, reply, duration):\n        \"\"\"Publish a CommandSucceededEvent.\"\"\"\n        self.listeners.publish_command_success(\n            duration, reply, self.name,\n            request_id, self.sock_info.address, self.op_id)\n\n    def _fail(self, request_id, failure, duration):\n        \"\"\"Publish a CommandFailedEvent.\"\"\"\n        self.listeners.publish_command_failure(\n            duration, failure, self.name,\n            request_id, self.sock_info.address, self.op_id)\n\n\n# 2MiB\n_MAX_ENC_BSON_SIZE = 2 * (1024 * 1024)\n# 6MB\n_MAX_ENC_MESSAGE_SIZE = 6 * (1000 * 1000)\n\n\nclass _EncryptedBulkWriteContext(_BulkWriteContext):\n    __slots__ = ()\n\n    def _batch_command(self, docs):\n        namespace = self.db_name + '.$cmd'\n        msg, to_send = _encode_batched_write_command(\n            namespace, self.op_type, self.command, docs, self.check_keys,\n            self.codec, self)\n        if not to_send:\n            raise InvalidOperation(\"cannot do an empty bulk write\")\n\n        # Chop off the OP_QUERY header to get a properly batched write command.\n        cmd_start = msg.index(b\"\\x00\", 4) + 9\n        cmd = _inflate_bson(memoryview(msg)[cmd_start:],\n                            DEFAULT_RAW_BSON_OPTIONS)\n        return cmd, to_send\n\n    def execute(self, docs, client):\n        cmd, to_send = self._batch_command(docs)\n        result = self.sock_info.command(\n            self.db_name, cmd, codec_options=_UNICODE_REPLACE_CODEC_OPTIONS,\n            session=self.session, client=client)\n        return result, to_send\n\n    def execute_unack(self, docs, client):\n        cmd, to_send = self._batch_command(docs)\n        self.sock_info.command(\n            self.db_name, cmd, write_concern=WriteConcern(w=0),\n            session=self.session, client=client)\n        return to_send\n\n    @property\n    def max_bson_size(self):\n        \"\"\"A proxy for SockInfo.max_bson_size.\"\"\"\n        return min(self.sock_info.max_bson_size, _MAX_ENC_BSON_SIZE)\n\n    @property\n    def max_message_size(self):\n        \"\"\"A proxy for SockInfo.max_message_size.\"\"\"\n        return min(self.sock_info.max_message_size, _MAX_ENC_MESSAGE_SIZE)\n\n\ndef _raise_document_too_large(operation, doc_size, max_size):\n    \"\"\"Internal helper for raising DocumentTooLarge.\"\"\"\n    if operation == \"insert\":\n        raise DocumentTooLarge(\"BSON document too large (%d bytes)\"\n                               \" - the connected server supports\"\n                               \" BSON document sizes up to %d\"\n                               \" bytes.\" % (doc_size, max_size))\n    else:\n        # There's nothing intelligent we can say\n        # about size for update and delete\n        raise DocumentTooLarge(\"%r command document too large\" % (operation,))\n\n\ndef _do_batched_insert(collection_name, docs, check_keys,\n                       safe, last_error_args, continue_on_error, opts,\n                       ctx):\n    \"\"\"Insert `docs` using multiple batches.\n    \"\"\"\n    def _insert_message(insert_message, send_safe):\n        \"\"\"Build the insert message with header and GLE.\n        \"\"\"\n        request_id, final_message = __pack_message(2002, insert_message)\n        if send_safe:\n            request_id, error_message, _ = __last_error(collection_name,\n                                                        last_error_args)\n            final_message += error_message\n        return request_id, final_message\n\n    send_safe = safe or not continue_on_error\n    last_error = None\n    data = StringIO()\n    data.write(struct.pack(\"<i\", int(continue_on_error)))\n    data.write(_make_c_string(collection_name))\n    message_length = begin_loc = data.tell()\n    has_docs = False\n    to_send = []\n    encode = _dict_to_bson  # Make local\n    compress = ctx.compress and not (safe or send_safe)\n    for doc in docs:\n        encoded = encode(doc, check_keys, opts)\n        encoded_length = len(encoded)\n        too_large = (encoded_length > ctx.max_bson_size)\n\n        message_length += encoded_length\n        if message_length < ctx.max_message_size and not too_large:\n            data.write(encoded)\n            to_send.append(doc)\n            has_docs = True\n            continue\n\n        if has_docs:\n            # We have enough data, send this message.\n            try:\n                if compress:\n                    rid, msg = None, data.getvalue()\n                else:\n                    rid, msg = _insert_message(data.getvalue(), send_safe)\n                ctx.legacy_bulk_insert(\n                    rid, msg, 0, send_safe, to_send, compress)\n            # Exception type could be OperationFailure or a subtype\n            # (e.g. DuplicateKeyError)\n            except OperationFailure as exc:\n                # Like it says, continue on error...\n                if continue_on_error:\n                    # Store exception details to re-raise after the final batch.\n                    last_error = exc\n                # With unacknowledged writes just return at the first error.\n                elif not safe:\n                    return\n                # With acknowledged writes raise immediately.\n                else:\n                    raise\n\n        if too_large:\n            _raise_document_too_large(\n                \"insert\", encoded_length, ctx.max_bson_size)\n\n        message_length = begin_loc + encoded_length\n        data.seek(begin_loc)\n        data.truncate()\n        data.write(encoded)\n        to_send = [doc]\n\n    if not has_docs:\n        raise InvalidOperation(\"cannot do an empty bulk insert\")\n\n    if compress:\n        request_id, msg = None, data.getvalue()\n    else:\n        request_id, msg = _insert_message(data.getvalue(), safe)\n    ctx.legacy_bulk_insert(request_id, msg, 0, safe, to_send, compress)\n\n    # Re-raise any exception stored due to continue_on_error\n    if last_error is not None:\n        raise last_error\nif _use_c:\n    _do_batched_insert = _cmessage._do_batched_insert\n\n# OP_MSG -------------------------------------------------------------\n\n\n_OP_MSG_MAP = {\n    _INSERT: b'documents\\x00',\n    _UPDATE: b'updates\\x00',\n    _DELETE: b'deletes\\x00',\n}\n\n\ndef _batched_op_msg_impl(\n        operation, command, docs, check_keys, ack, opts, ctx, buf):\n    \"\"\"Create a batched OP_MSG write.\"\"\"\n    max_bson_size = ctx.max_bson_size\n    max_write_batch_size = ctx.max_write_batch_size\n    max_message_size = ctx.max_message_size\n\n    flags = b\"\\x00\\x00\\x00\\x00\" if ack else b\"\\x02\\x00\\x00\\x00\"\n    # Flags\n    buf.write(flags)\n\n    # Type 0 Section\n    buf.write(b\"\\x00\")\n    buf.write(_dict_to_bson(command, False, opts))\n\n    # Type 1 Section\n    buf.write(b\"\\x01\")\n    size_location = buf.tell()\n    # Save space for size\n    buf.write(b\"\\x00\\x00\\x00\\x00\")\n    try:\n        buf.write(_OP_MSG_MAP[operation])\n    except KeyError:\n        raise InvalidOperation('Unknown command')\n\n    if operation in (_UPDATE, _DELETE):\n        check_keys = False\n\n    to_send = []\n    idx = 0\n    for doc in docs:\n        # Encode the current operation\n        value = _dict_to_bson(doc, check_keys, opts)\n        doc_length = len(value)\n        new_message_size = buf.tell() + doc_length\n        # Does first document exceed max_message_size?\n        doc_too_large = (idx == 0 and (new_message_size > max_message_size))\n        # When OP_MSG is used unacknowleged we have to check\n        # document size client side or applications won't be notified.\n        # Otherwise we let the server deal with documents that are too large\n        # since ordered=False causes those documents to be skipped instead of\n        # halting the bulk write operation.\n        unacked_doc_too_large = (not ack and (doc_length > max_bson_size))\n        if doc_too_large or unacked_doc_too_large:\n            write_op = list(_FIELD_MAP.keys())[operation]\n            _raise_document_too_large(\n                write_op, len(value), max_bson_size)\n        # We have enough data, return this batch.\n        if new_message_size > max_message_size:\n            break\n        buf.write(value)\n        to_send.append(doc)\n        idx += 1\n        # We have enough documents, return this batch.\n        if idx == max_write_batch_size:\n            break\n\n    # Write type 1 section size\n    length = buf.tell()\n    buf.seek(size_location)\n    buf.write(_pack_int(length - size_location))\n\n    return to_send, length\n\n\ndef _encode_batched_op_msg(\n        operation, command, docs, check_keys, ack, opts, ctx):\n    \"\"\"Encode the next batched insert, update, or delete operation\n    as OP_MSG.\n    \"\"\"\n    buf = StringIO()\n\n    to_send, _ = _batched_op_msg_impl(\n        operation, command, docs, check_keys, ack, opts, ctx, buf)\n    return buf.getvalue(), to_send\nif _use_c:\n    _encode_batched_op_msg = _cmessage._encode_batched_op_msg\n\n\ndef _batched_op_msg_compressed(\n        operation, command, docs, check_keys, ack, opts, ctx):\n    \"\"\"Create the next batched insert, update, or delete operation\n    with OP_MSG, compressed.\n    \"\"\"\n    data, to_send = _encode_batched_op_msg(\n        operation, command, docs, check_keys, ack, opts, ctx)\n\n    request_id, msg = _compress(\n        2013,\n        data,\n        ctx.sock_info.compression_context)\n    return request_id, msg, to_send\n\n\ndef _batched_op_msg(\n        operation, command, docs, check_keys, ack, opts, ctx):\n    \"\"\"OP_MSG implementation entry point.\"\"\"\n    buf = StringIO()\n\n    # Save space for message length and request id\n    buf.write(_ZERO_64)\n    # responseTo, opCode\n    buf.write(b\"\\x00\\x00\\x00\\x00\\xdd\\x07\\x00\\x00\")\n\n    to_send, length = _batched_op_msg_impl(\n        operation, command, docs, check_keys, ack, opts, ctx, buf)\n\n    # Header - request id and message length\n    buf.seek(4)\n    request_id = _randint()\n    buf.write(_pack_int(request_id))\n    buf.seek(0)\n    buf.write(_pack_int(length))\n\n    return request_id, buf.getvalue(), to_send\nif _use_c:\n    _batched_op_msg = _cmessage._batched_op_msg\n\n\ndef _do_batched_op_msg(\n        namespace, operation, command, docs, check_keys, opts, ctx):\n    \"\"\"Create the next batched insert, update, or delete operation\n    using OP_MSG.\n    \"\"\"\n    command['$db'] = namespace.split('.', 1)[0]\n    if 'writeConcern' in command:\n        ack = bool(command['writeConcern'].get('w', 1))\n    else:\n        ack = True\n    if ctx.sock_info.compression_context:\n        return _batched_op_msg_compressed(\n            operation, command, docs, check_keys, ack, opts, ctx)\n    return _batched_op_msg(\n        operation, command, docs, check_keys, ack, opts, ctx)\n\n\n# End OP_MSG -----------------------------------------------------\n\n\ndef _batched_write_command_compressed(\n        namespace, operation, command, docs, check_keys, opts, ctx):\n    \"\"\"Create the next batched insert, update, or delete command, compressed.\n    \"\"\"\n    data, to_send = _encode_batched_write_command(\n        namespace, operation, command, docs, check_keys, opts, ctx)\n\n    request_id, msg = _compress(\n        2004,\n        data,\n        ctx.sock_info.compression_context)\n    return request_id, msg, to_send\n\n\ndef _encode_batched_write_command(\n        namespace, operation, command, docs, check_keys, opts, ctx):\n    \"\"\"Encode the next batched insert, update, or delete command.\n    \"\"\"\n    buf = StringIO()\n\n    to_send, _ = _batched_write_command_impl(\n        namespace, operation, command, docs, check_keys, opts, ctx, buf)\n    return buf.getvalue(), to_send\nif _use_c:\n    _encode_batched_write_command = _cmessage._encode_batched_write_command\n\n\ndef _batched_write_command(\n        namespace, operation, command, docs, check_keys, opts, ctx):\n    \"\"\"Create the next batched insert, update, or delete command.\n    \"\"\"\n    buf = StringIO()\n\n    # Save space for message length and request id\n    buf.write(_ZERO_64)\n    # responseTo, opCode\n    buf.write(b\"\\x00\\x00\\x00\\x00\\xd4\\x07\\x00\\x00\")\n\n    # Write OP_QUERY write command\n    to_send, length = _batched_write_command_impl(\n        namespace, operation, command, docs, check_keys, opts, ctx, buf)\n\n    # Header - request id and message length\n    buf.seek(4)\n    request_id = _randint()\n    buf.write(_pack_int(request_id))\n    buf.seek(0)\n    buf.write(_pack_int(length))\n\n    return request_id, buf.getvalue(), to_send\nif _use_c:\n    _batched_write_command = _cmessage._batched_write_command\n\n\ndef _do_batched_write_command(\n        namespace, operation, command, docs, check_keys, opts, ctx):\n    \"\"\"Batched write commands entry point.\"\"\"\n    if ctx.sock_info.compression_context:\n        return _batched_write_command_compressed(\n            namespace, operation, command, docs, check_keys, opts, ctx)\n    return _batched_write_command(\n        namespace, operation, command, docs, check_keys, opts, ctx)\n\n\ndef _do_bulk_write_command(\n        namespace, operation, command, docs, check_keys, opts, ctx):\n    \"\"\"Bulk write commands entry point.\"\"\"\n    if ctx.sock_info.max_wire_version > 5:\n        return _do_batched_op_msg(\n            namespace, operation, command, docs, check_keys, opts, ctx)\n    return _do_batched_write_command(\n        namespace, operation, command, docs, check_keys, opts, ctx)\n\n\ndef _batched_write_command_impl(\n        namespace, operation, command, docs, check_keys, opts, ctx, buf):\n    \"\"\"Create a batched OP_QUERY write command.\"\"\"\n    max_bson_size = ctx.max_bson_size\n    max_write_batch_size = ctx.max_write_batch_size\n    # Max BSON object size + 16k - 2 bytes for ending NUL bytes.\n    # Server guarantees there is enough room: SERVER-10643.\n    max_cmd_size = max_bson_size + _COMMAND_OVERHEAD\n\n    # No options\n    buf.write(_ZERO_32)\n    # Namespace as C string\n    buf.write(b(namespace))\n    buf.write(_ZERO_8)\n    # Skip: 0, Limit: -1\n    buf.write(_SKIPLIM)\n\n    # Where to write command document length\n    command_start = buf.tell()\n    buf.write(bson.BSON.encode(command))\n\n    # Start of payload\n    buf.seek(-1, 2)\n    # Work around some Jython weirdness.\n    buf.truncate()\n    try:\n        buf.write(_OP_MAP[operation])\n    except KeyError:\n        raise InvalidOperation('Unknown command')\n\n    if operation in (_UPDATE, _DELETE):\n        check_keys = False\n\n    # Where to write list document length\n    list_start = buf.tell() - 4\n    to_send = []\n    idx = 0\n    for doc in docs:\n        # Encode the current operation\n        key = b(str(idx))\n        value = bson.BSON.encode(doc, check_keys, opts)\n        # Is there enough room to add this document? max_cmd_size accounts for\n        # the two trailing null bytes.\n        doc_too_large = len(value) > max_cmd_size\n        enough_data = (buf.tell() + len(key) + len(value)) >= max_cmd_size\n        enough_documents = (idx >= max_write_batch_size)\n        if doc_too_large:\n            write_op = list(_FIELD_MAP.keys())[operation]\n            _raise_document_too_large(\n                write_op, len(value), max_bson_size)\n        if enough_data or enough_documents:\n            break\n        buf.write(_BSONOBJ)\n        buf.write(key)\n        buf.write(_ZERO_8)\n        buf.write(value)\n        to_send.append(doc)\n        idx += 1\n\n    # Finalize the current OP_QUERY message.\n    # Close list and command documents\n    buf.write(_ZERO_16)\n\n    # Write document lengths and request id\n    length = buf.tell()\n    buf.seek(list_start)\n    buf.write(_pack_int(length - list_start - 1))\n    buf.seek(command_start)\n    buf.write(_pack_int(length - command_start))\n\n    return to_send, length\n\n\nclass _OpReply(object):\n    \"\"\"A MongoDB OP_REPLY response message.\"\"\"\n\n    __slots__ = (\"flags\", \"cursor_id\", \"number_returned\", \"documents\")\n\n    UNPACK_FROM = struct.Struct(\"<iqii\").unpack_from\n    OP_CODE = 1\n\n    def __init__(self, flags, cursor_id, number_returned, documents):\n        self.flags = flags\n        self.cursor_id = cursor_id\n        self.number_returned = number_returned\n        self.documents = documents\n\n    def raw_response(self, cursor_id=None):\n        \"\"\"Check the response header from the database, without decoding BSON.\n\n        Check the response for errors and unpack.\n\n        Can raise CursorNotFound, NotMasterError, ExecutionTimeout, or\n        OperationFailure.\n\n        :Parameters:\n          - `cursor_id` (optional): cursor_id we sent to get this response -\n            used for raising an informative exception when we get cursor id not\n            valid at server response.\n        \"\"\"\n        if self.flags & 1:\n            # Shouldn't get this response if we aren't doing a getMore\n            if cursor_id is None:\n                raise ProtocolError(\"No cursor id for getMore operation\")\n\n            # Fake a getMore command response. OP_GET_MORE provides no\n            # document.\n            msg = \"Cursor not found, cursor id: %d\" % (cursor_id,)\n            errobj = {\"ok\": 0, \"errmsg\": msg, \"code\": 43}\n            raise CursorNotFound(msg, 43, errobj)\n        elif self.flags & 2:\n            error_object = bson.BSON(self.documents).decode()\n            # Fake the ok field if it doesn't exist.\n            error_object.setdefault(\"ok\", 0)\n            if error_object[\"$err\"].startswith(\"not master\"):\n                raise NotMasterError(error_object[\"$err\"], error_object)\n            elif error_object.get(\"code\") == 50:\n                raise ExecutionTimeout(error_object.get(\"$err\"),\n                                       error_object.get(\"code\"),\n                                       error_object)\n            raise OperationFailure(\"database error: %s\" %\n                                   error_object.get(\"$err\"),\n                                   error_object.get(\"code\"),\n                                   error_object)\n        return [self.documents]\n\n    def unpack_response(self, cursor_id=None,\n                        codec_options=_UNICODE_REPLACE_CODEC_OPTIONS,\n                        user_fields=None, legacy_response=False):\n        \"\"\"Unpack a response from the database and decode the BSON document(s).\n\n        Check the response for errors and unpack, returning a dictionary\n        containing the response data.\n\n        Can raise CursorNotFound, NotMasterError, ExecutionTimeout, or\n        OperationFailure.\n\n        :Parameters:\n          - `cursor_id` (optional): cursor_id we sent to get this response -\n            used for raising an informative exception when we get cursor id not\n            valid at server response\n          - `codec_options` (optional): an instance of\n            :class:`~bson.codec_options.CodecOptions`\n        \"\"\"\n        self.raw_response(cursor_id)\n        if legacy_response:\n            return bson.decode_all(self.documents, codec_options)\n        return bson._decode_all_selective(\n            self.documents, codec_options, user_fields)\n\n    def command_response(self):\n        \"\"\"Unpack a command response.\"\"\"\n        docs = self.unpack_response()\n        assert self.number_returned == 1\n        return docs[0]\n\n    def raw_command_response(self):\n        \"\"\"Return the bytes of the command response.\"\"\"\n        # This should never be called on _OpReply.\n        raise NotImplementedError\n\n    @classmethod\n    def unpack(cls, msg):\n        \"\"\"Construct an _OpReply from raw bytes.\"\"\"\n        # PYTHON-945: ignore starting_from field.\n        flags, cursor_id, _, number_returned = cls.UNPACK_FROM(msg)\n\n        # Convert Python 3 memoryview to bytes. Note we should call\n        # memoryview.tobytes() if we start using memoryview in Python 2.7.\n        documents = bytes(msg[20:])\n        return cls(flags, cursor_id, number_returned, documents)\n\n\nclass _OpMsg(object):\n    \"\"\"A MongoDB OP_MSG response message.\"\"\"\n\n    __slots__ = (\"flags\", \"cursor_id\", \"number_returned\", \"payload_document\")\n\n    UNPACK_FROM = struct.Struct(\"<IBi\").unpack_from\n    OP_CODE = 2013\n\n    def __init__(self, flags, payload_document):\n        self.flags = flags\n        self.payload_document = payload_document\n\n    def raw_response(self, cursor_id=None):\n        raise NotImplementedError\n\n    def unpack_response(self, cursor_id=None,\n                        codec_options=_UNICODE_REPLACE_CODEC_OPTIONS,\n                        user_fields=None, legacy_response=False):\n        \"\"\"Unpack a OP_MSG command response.\n\n        :Parameters:\n          - `cursor_id` (optional): Ignored, for compatibility with _OpReply.\n          - `codec_options` (optional): an instance of\n            :class:`~bson.codec_options.CodecOptions`\n        \"\"\"\n        # If _OpMsg is in-use, this cannot be a legacy response.\n        assert not legacy_response\n        return bson._decode_all_selective(\n            self.payload_document, codec_options, user_fields)\n\n    def command_response(self):\n        \"\"\"Unpack a command response.\"\"\"\n        return self.unpack_response()[0]\n\n    def raw_command_response(self):\n        \"\"\"Return the bytes of the command response.\"\"\"\n        return self.payload_document\n\n    @classmethod\n    def unpack(cls, msg):\n        \"\"\"Construct an _OpMsg from raw bytes.\"\"\"\n        flags, first_payload_type, first_payload_size = cls.UNPACK_FROM(msg)\n        if flags != 0:\n            raise ProtocolError(\"Unsupported OP_MSG flags (%r)\" % (flags,))\n        if first_payload_type != 0:\n            raise ProtocolError(\n                \"Unsupported OP_MSG payload type (%r)\" % (first_payload_type,))\n\n        if len(msg) != first_payload_size + 5:\n            raise ProtocolError(\"Unsupported OP_MSG reply: >1 section\")\n\n        # Convert Python 3 memoryview to bytes. Note we should call\n        # memoryview.tobytes() if we start using memoryview in Python 2.7.\n        payload_document = bytes(msg[5:])\n        return cls(flags, payload_document)\n\n\n_UNPACK_REPLY = {\n    _OpReply.OP_CODE: _OpReply.unpack,\n    _OpMsg.OP_CODE: _OpMsg.unpack,\n}\n\n\ndef _first_batch(sock_info, db, coll, query, ntoreturn,\n                 slave_ok, codec_options, read_preference, cmd, listeners):\n    \"\"\"Simple query helper for retrieving a first (and possibly only) batch.\"\"\"\n    query = _Query(\n        0, db, coll, 0, query, None, codec_options,\n        read_preference, ntoreturn, 0, DEFAULT_READ_CONCERN, None, None,\n        None)\n\n    name = next(iter(cmd))\n    publish = listeners.enabled_for_commands\n    if publish:\n        start = datetime.datetime.now()\n\n    request_id, msg, max_doc_size = query.get_message(slave_ok, sock_info)\n\n    if publish:\n        encoding_duration = datetime.datetime.now() - start\n        listeners.publish_command_start(\n            cmd, db, request_id, sock_info.address)\n        start = datetime.datetime.now()\n\n    sock_info.send_message(msg, max_doc_size)\n    reply = sock_info.receive_message(request_id)\n    try:\n        docs = reply.unpack_response(None, codec_options)\n    except Exception as exc:\n        if publish:\n            duration = (datetime.datetime.now() - start) + encoding_duration\n            if isinstance(exc, (NotMasterError, OperationFailure)):\n                failure = exc.details\n            else:\n                failure = _convert_exception(exc)\n            listeners.publish_command_failure(\n                duration, failure, name, request_id, sock_info.address)\n        raise\n    # listIndexes\n    if 'cursor' in cmd:\n        result = {\n            u'cursor': {\n                u'firstBatch': docs,\n                u'id': reply.cursor_id,\n                u'ns': u'%s.%s' % (db, coll)\n            },\n            u'ok': 1.0\n        }\n    # fsyncUnlock, currentOp\n    else:\n        result = docs[0] if docs else {}\n        result[u'ok'] = 1.0\n    if publish:\n        duration = (datetime.datetime.now() - start) + encoding_duration\n        listeners.publish_command_success(\n            duration, result, name, request_id, sock_info.address)\n\n    return result\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/mongo_client.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Tools for connecting to MongoDB.\n\n.. seealso:: :doc:`/examples/high_availability` for examples of connecting\n   to replica sets or sets of mongos servers.\n\nTo get a :class:`~pymongo.database.Database` instance from a\n:class:`MongoClient` use either dictionary-style or attribute-style\naccess:\n\n.. doctest::\n\n  >>> from pymongo import MongoClient\n  >>> c = MongoClient()\n  >>> c.test_database\n  Database(MongoClient(host=['localhost:27017'], document_class=dict, tz_aware=False, connect=True), u'test_database')\n  >>> c['test-database']\n  Database(MongoClient(host=['localhost:27017'], document_class=dict, tz_aware=False, connect=True), u'test-database')\n\"\"\"\n\nimport contextlib\nimport datetime\nimport threading\nimport warnings\nimport weakref\n\nfrom collections import defaultdict\n\nfrom bson.codec_options import DEFAULT_CODEC_OPTIONS\nfrom bson.py3compat import (integer_types,\n                            string_type)\nfrom bson.son import SON\nfrom pymongo import (common,\n                     database,\n                     helpers,\n                     message,\n                     periodic_executor,\n                     uri_parser,\n                     client_session)\nfrom pymongo.change_stream import ClusterChangeStream\nfrom pymongo.client_options import ClientOptions\nfrom pymongo.command_cursor import CommandCursor\nfrom pymongo.cursor_manager import CursorManager\nfrom pymongo.errors import (AutoReconnect,\n                            BulkWriteError,\n                            ConfigurationError,\n                            ConnectionFailure,\n                            InvalidOperation,\n                            NetworkTimeout,\n                            NotMasterError,\n                            OperationFailure,\n                            PyMongoError,\n                            ServerSelectionTimeoutError)\nfrom pymongo.read_preferences import ReadPreference\nfrom pymongo.server_selectors import (writable_preferred_server_selector,\n                                      writable_server_selector)\nfrom pymongo.server_type import SERVER_TYPE\nfrom pymongo.topology import Topology\nfrom pymongo.topology_description import TOPOLOGY_TYPE\nfrom pymongo.settings import TopologySettings\nfrom pymongo.uri_parser import (_handle_option_deprecations,\n                                _handle_security_options,\n                                _normalize_options)\nfrom pymongo.write_concern import DEFAULT_WRITE_CONCERN\n\n\nclass MongoClient(common.BaseObject):\n    \"\"\"\n    A client-side representation of a MongoDB cluster.\n\n    Instances can represent either a standalone MongoDB server, a replica\n    set, or a sharded cluster. Instances of this class are responsible for\n    maintaining up-to-date state of the cluster, and possibly cache\n    resources related to this, including background threads for monitoring,\n    and connection pools.\n    \"\"\"\n    HOST = \"localhost\"\n    PORT = 27017\n    # Define order to retrieve options from ClientOptions for __repr__.\n    # No host/port; these are retrieved from TopologySettings.\n    _constructor_args = ('document_class', 'tz_aware', 'connect')\n\n    def __init__(\n            self,\n            host=None,\n            port=None,\n            document_class=dict,\n            tz_aware=None,\n            connect=None,\n            type_registry=None,\n            **kwargs):\n        \"\"\"Client for a MongoDB instance, a replica set, or a set of mongoses.\n\n        The client object is thread-safe and has connection-pooling built in.\n        If an operation fails because of a network error,\n        :class:`~pymongo.errors.ConnectionFailure` is raised and the client\n        reconnects in the background. Application code should handle this\n        exception (recognizing that the operation failed) and then continue to\n        execute.\n\n        The `host` parameter can be a full `mongodb URI\n        <http://dochub.mongodb.org/core/connections>`_, in addition to\n        a simple hostname. It can also be a list of hostnames or\n        URIs. Any port specified in the host string(s) will override\n        the `port` parameter. If multiple mongodb URIs containing\n        database or auth information are passed, the last database,\n        username, and password present will be used.  For username and\n        passwords reserved characters like ':', '/', '+' and '@' must be\n        percent encoded following RFC 2396::\n\n            try:\n                # Python 3.x\n                from urllib.parse import quote_plus\n            except ImportError:\n                # Python 2.x\n                from urllib import quote_plus\n\n            uri = \"mongodb://%s:%s@%s\" % (\n                quote_plus(user), quote_plus(password), host)\n            client = MongoClient(uri)\n\n        Unix domain sockets are also supported. The socket path must be percent\n        encoded in the URI::\n\n            uri = \"mongodb://%s:%s@%s\" % (\n                quote_plus(user), quote_plus(password), quote_plus(socket_path))\n            client = MongoClient(uri)\n\n        But not when passed as a simple hostname::\n\n            client = MongoClient('/tmp/mongodb-27017.sock')\n\n        Starting with version 3.6, PyMongo supports mongodb+srv:// URIs. The\n        URI must include one, and only one, hostname. The hostname will be\n        resolved to one or more DNS `SRV records\n        <https://en.wikipedia.org/wiki/SRV_record>`_ which will be used\n        as the seed list for connecting to the MongoDB deployment. When using\n        SRV URIs, the `authSource` and `replicaSet` configuration options can\n        be specified using `TXT records\n        <https://en.wikipedia.org/wiki/TXT_record>`_. See the\n        `Initial DNS Seedlist Discovery spec\n        <https://github.com/mongodb/specifications/blob/master/source/\n        initial-dns-seedlist-discovery/initial-dns-seedlist-discovery.rst>`_\n        for more details. Note that the use of SRV URIs implicitly enables\n        TLS support. Pass tls=false in the URI to override.\n\n        .. note:: MongoClient creation will block waiting for answers from\n          DNS when mongodb+srv:// URIs are used.\n\n        .. note:: Starting with version 3.0 the :class:`MongoClient`\n          constructor no longer blocks while connecting to the server or\n          servers, and it no longer raises\n          :class:`~pymongo.errors.ConnectionFailure` if they are\n          unavailable, nor :class:`~pymongo.errors.ConfigurationError`\n          if the user's credentials are wrong. Instead, the constructor\n          returns immediately and launches the connection process on\n          background threads. You can check if the server is available\n          like this::\n\n            from pymongo.errors import ConnectionFailure\n            client = MongoClient()\n            try:\n                # The ismaster command is cheap and does not require auth.\n                client.admin.command('ismaster')\n            except ConnectionFailure:\n                print(\"Server not available\")\n\n        .. warning:: When using PyMongo in a multiprocessing context, please\n          read :ref:`multiprocessing` first.\n\n        .. note:: Many of the following options can be passed using a MongoDB\n          URI or keyword parameters. If the same option is passed in a URI and\n          as a keyword parameter the keyword parameter takes precedence.\n\n        :Parameters:\n          - `host` (optional): hostname or IP address or Unix domain socket\n            path of a single mongod or mongos instance to connect to, or a\n            mongodb URI, or a list of hostnames / mongodb URIs. If `host` is\n            an IPv6 literal it must be enclosed in '[' and ']' characters\n            following the RFC2732 URL syntax (e.g. '[::1]' for localhost).\n            Multihomed and round robin DNS addresses are **not** supported.\n          - `port` (optional): port number on which to connect\n          - `document_class` (optional): default class to use for\n            documents returned from queries on this client\n          - `type_registry` (optional): instance of\n            :class:`~bson.codec_options.TypeRegistry` to enable encoding\n            and decoding of custom types.\n          - `tz_aware` (optional): if ``True``,\n            :class:`~datetime.datetime` instances returned as values\n            in a document by this :class:`MongoClient` will be timezone\n            aware (otherwise they will be naive)\n          - `connect` (optional): if ``True`` (the default), immediately\n            begin connecting to MongoDB in the background. Otherwise connect\n            on the first operation.\n\n          | **Other optional parameters can be passed as keyword arguments:**\n\n          - `maxPoolSize` (optional): The maximum allowable number of\n            concurrent connections to each connected server. Requests to a\n            server will block if there are `maxPoolSize` outstanding\n            connections to the requested server. Defaults to 100. Cannot be 0.\n          - `minPoolSize` (optional): The minimum required number of concurrent\n            connections that the pool will maintain to each connected server.\n            Default is 0.\n          - `maxIdleTimeMS` (optional): The maximum number of milliseconds that\n            a connection can remain idle in the pool before being removed and\n            replaced. Defaults to `None` (no limit).\n          - `socketTimeoutMS`: (integer or None) Controls how long (in\n            milliseconds) the driver will wait for a response after sending an\n            ordinary (non-monitoring) database operation before concluding that\n            a network error has occurred. Defaults to ``None`` (no timeout).\n          - `connectTimeoutMS`: (integer or None) Controls how long (in\n            milliseconds) the driver will wait during server monitoring when\n            connecting a new socket to a server before concluding the server\n            is unavailable. Defaults to ``20000`` (20 seconds).\n          - `server_selector`: (callable or None) Optional, user-provided\n            function that augments server selection rules. The function should\n            accept as an argument a list of\n            :class:`~pymongo.server_description.ServerDescription` objects and\n            return a list of server descriptions that should be considered\n            suitable for the desired operation.\n          - `serverSelectionTimeoutMS`: (integer) Controls how long (in\n            milliseconds) the driver will wait to find an available,\n            appropriate server to carry out a database operation; while it is\n            waiting, multiple server monitoring operations may be carried out,\n            each controlled by `connectTimeoutMS`. Defaults to ``30000`` (30\n            seconds).\n          - `waitQueueTimeoutMS`: (integer or None) How long (in milliseconds)\n            a thread will wait for a socket from the pool if the pool has no\n            free sockets. Defaults to ``None`` (no timeout).\n          - `waitQueueMultiple`: (integer or None) Multiplied by maxPoolSize\n            to give the number of threads allowed to wait for a socket at one\n            time. Defaults to ``None`` (no limit).\n          - `heartbeatFrequencyMS`: (optional) The number of milliseconds\n            between periodic server checks, or None to accept the default\n            frequency of 10 seconds.\n          - `appname`: (string or None) The name of the application that\n            created this MongoClient instance. MongoDB 3.4 and newer will\n            print this value in the server log upon establishing each\n            connection. It is also recorded in the slow query log and\n            profile collections.\n          - `driver`: (pair or None) A driver implemented on top of PyMongo can\n            pass a :class:`~pymongo.driver_info.DriverInfo` to add its name,\n            version, and platform to the message printed in the server log when\n            establishing a connection.\n          - `event_listeners`: a list or tuple of event listeners. See\n            :mod:`~pymongo.monitoring` for details.\n          - `retryWrites`: (boolean) Whether supported write operations\n            executed within this MongoClient will be retried once after a\n            network error on MongoDB 3.6+. Defaults to ``True``.\n            The supported write operations are:\n\n              - :meth:`~pymongo.collection.Collection.bulk_write`, as long as\n                :class:`~pymongo.operations.UpdateMany` or\n                :class:`~pymongo.operations.DeleteMany` are not included.\n              - :meth:`~pymongo.collection.Collection.delete_one`\n              - :meth:`~pymongo.collection.Collection.insert_one`\n              - :meth:`~pymongo.collection.Collection.insert_many`\n              - :meth:`~pymongo.collection.Collection.replace_one`\n              - :meth:`~pymongo.collection.Collection.update_one`\n              - :meth:`~pymongo.collection.Collection.find_one_and_delete`\n              - :meth:`~pymongo.collection.Collection.find_one_and_replace`\n              - :meth:`~pymongo.collection.Collection.find_one_and_update`\n\n            Unsupported write operations include, but are not limited to,\n            :meth:`~pymongo.collection.Collection.aggregate` using the ``$out``\n            pipeline operator and any operation with an unacknowledged write\n            concern (e.g. {w: 0})). See\n            https://github.com/mongodb/specifications/blob/master/source/retryable-writes/retryable-writes.rst\n          - `retryReads`: (boolean) Whether supported read operations\n            executed within this MongoClient will be retried once after a\n            network error on MongoDB 3.6+. Defaults to ``True``.\n            The supported read operations are:\n            :meth:`~pymongo.collection.Collection.find`,\n            :meth:`~pymongo.collection.Collection.find_one`,\n            :meth:`~pymongo.collection.Collection.aggregate` without ``$out``,\n            :meth:`~pymongo.collection.Collection.distinct`,\n            :meth:`~pymongo.collection.Collection.count`,\n            :meth:`~pymongo.collection.Collection.estimated_document_count`,\n            :meth:`~pymongo.collection.Collection.count_documents`,\n            :meth:`pymongo.collection.Collection.watch`,\n            :meth:`~pymongo.collection.Collection.list_indexes`,\n            :meth:`pymongo.database.Database.watch`,\n            :meth:`~pymongo.database.Database.list_collections`,\n            :meth:`pymongo.mongo_client.MongoClient.watch`,\n            and :meth:`~pymongo.mongo_client.MongoClient.list_databases`.\n\n            Unsupported read operations include, but are not limited to:\n            :meth:`~pymongo.collection.Collection.map_reduce`,\n            :meth:`~pymongo.collection.Collection.inline_map_reduce`,\n            :meth:`~pymongo.database.Database.command`,\n            and any getMore operation on a cursor.\n\n            Enabling retryable reads makes applications more resilient to\n            transient errors such as network failures, database upgrades, and\n            replica set failovers. For an exact definition of which errors\n            trigger a retry, see the `retryable reads specification\n            <https://github.com/mongodb/specifications/blob/master/source/retryable-reads/retryable-reads.rst>`_.\n\n          - `socketKeepAlive`: (boolean) **DEPRECATED** Whether to send\n            periodic keep-alive packets on connected sockets. Defaults to\n            ``True``. Disabling it is not recommended, see\n            https://docs.mongodb.com/manual/faq/diagnostics/#does-tcp-keepalive-time-affect-mongodb-deployments\",\n          - `compressors`: Comma separated list of compressors for wire\n            protocol compression. The list is used to negotiate a compressor\n            with the server. Currently supported options are \"snappy\", \"zlib\"\n            and \"zstd\". Support for snappy requires the\n            `python-snappy <https://pypi.org/project/python-snappy/>`_ package.\n            zlib support requires the Python standard library zlib module. zstd\n            requires the `zstandard <https://pypi.org/project/zstandard/>`_\n            package. By default no compression is used. Compression support\n            must also be enabled on the server. MongoDB 3.4+ supports snappy\n            compression. MongoDB 3.6 adds support for zlib. MongoDB 4.2 adds\n            support for zstd.\n          - `zlibCompressionLevel`: (int) The zlib compression level to use\n            when zlib is used as the wire protocol compressor. Supported values\n            are -1 through 9. -1 tells the zlib library to use its default\n            compression level (usually 6). 0 means no compression. 1 is best\n            speed. 9 is best compression. Defaults to -1.\n          - `uuidRepresentation`: The BSON representation to use when encoding\n            from and decoding to instances of :class:`~uuid.UUID`. Valid\n            values are `pythonLegacy` (the default), `javaLegacy`,\n            `csharpLegacy` and `standard`. New applications should consider\n            setting this to `standard` for cross language compatibility.\n\n          | **Write Concern options:**\n          | (Only set if passed. No default values.)\n\n          - `w`: (integer or string) If this is a replica set, write operations\n            will block until they have been replicated to the specified number\n            or tagged set of servers. `w=<int>` always includes the replica set\n            primary (e.g. w=3 means write to the primary and wait until\n            replicated to **two** secondaries). Passing w=0 **disables write\n            acknowledgement** and all other write concern options.\n          - `wTimeoutMS`: (integer) Used in conjunction with `w`. Specify a value\n            in milliseconds to control how long to wait for write propagation\n            to complete. If replication does not complete in the given\n            timeframe, a timeout exception is raised. Passing wTimeoutMS=0\n            will cause **write operations to wait indefinitely**.\n          - `journal`: If ``True`` block until write operations have been\n            committed to the journal. Cannot be used in combination with\n            `fsync`. Prior to MongoDB 2.6 this option was ignored if the server\n            was running without journaling. Starting with MongoDB 2.6 write\n            operations will fail with an exception if this option is used when\n            the server is running without journaling.\n          - `fsync`: If ``True`` and the server is running without journaling,\n            blocks until the server has synced all data files to disk. If the\n            server is running with journaling, this acts the same as the `j`\n            option, blocking until write operations have been committed to the\n            journal. Cannot be used in combination with `j`.\n\n          | **Replica set keyword arguments for connecting with a replica set\n            - either directly or via a mongos:**\n\n          - `replicaSet`: (string or None) The name of the replica set to\n            connect to. The driver will verify that all servers it connects to\n            match this name. Implies that the hosts specified are a seed list\n            and the driver should attempt to find all members of the set.\n            Defaults to ``None``.\n\n          | **Read Preference:**\n\n          - `readPreference`: The replica set read preference for this client.\n            One of ``primary``, ``primaryPreferred``, ``secondary``,\n            ``secondaryPreferred``, or ``nearest``. Defaults to ``primary``.\n          - `readPreferenceTags`: Specifies a tag set as a comma-separated list\n            of colon-separated key-value pairs. For example ``dc:ny,rack:1``.\n            Defaults to ``None``.\n          - `maxStalenessSeconds`: (integer) The maximum estimated\n            length of time a replica set secondary can fall behind the primary\n            in replication before it will no longer be selected for operations.\n            Defaults to ``-1``, meaning no maximum. If maxStalenessSeconds\n            is set, it must be a positive integer greater than or equal to\n            90 seconds.\n\n          .. seealso:: :doc:`/examples/server_selection`\n\n          | **Authentication:**\n\n          - `username`: A string.\n          - `password`: A string.\n\n            Although username and password must be percent-escaped in a MongoDB\n            URI, they must not be percent-escaped when passed as parameters. In\n            this example, both the space and slash special characters are passed\n            as-is::\n\n              MongoClient(username=\"user name\", password=\"pass/word\")\n\n          - `authSource`: The database to authenticate on. Defaults to the\n            database specified in the URI, if provided, or to \"admin\".\n          - `authMechanism`: See :data:`~pymongo.auth.MECHANISMS` for options.\n            If no mechanism is specified, PyMongo automatically uses MONGODB-CR\n            when connected to a pre-3.0 version of MongoDB, SCRAM-SHA-1 when\n            connected to MongoDB 3.0 through 3.6, and negotiates the mechanism\n            to use (SCRAM-SHA-1 or SCRAM-SHA-256) when connected to MongoDB\n            4.0+.\n          - `authMechanismProperties`: Used to specify authentication mechanism\n            specific options. To specify the service name for GSSAPI\n            authentication pass authMechanismProperties='SERVICE_NAME:<service\n            name>'\n\n          .. seealso:: :doc:`/examples/authentication`\n\n          | **TLS/SSL configuration:**\n\n          - `tls`: (boolean) If ``True``, create the connection to the server\n            using transport layer security. Defaults to ``False``.\n          - `tlsInsecure`: (boolean) Specify whether TLS constraints should be\n            relaxed as much as possible. Setting ``tlsInsecure=True`` implies\n            ``tlsAllowInvalidCertificates=True`` and\n            ``tlsAllowInvalidHostnames=True``. Defaults to ``False``. Think\n            very carefully before setting this to ``True`` as it dramatically\n            reduces the security of TLS.\n          - `tlsAllowInvalidCertificates`: (boolean) If ``True``, continues\n            the TLS handshake regardless of the outcome of the certificate\n            verification process. If this is ``False``, and a value is not\n            provided for ``tlsCAFile``, PyMongo will attempt to load system\n            provided CA certificates. If the python version in use does not\n            support loading system CA certificates then the ``tlsCAFile``\n            parameter must point to a file of CA certificates.\n            ``tlsAllowInvalidCertificates=False`` implies ``tls=True``.\n            Defaults to ``False``. Think very carefully before setting this\n            to ``True`` as that could make your application vulnerable to\n            man-in-the-middle attacks.\n          - `tlsAllowInvalidHostnames`: (boolean) If ``True``, disables TLS\n            hostname verification. ``tlsAllowInvalidHostnames=False`` implies\n            ``tls=True``. Defaults to ``False``. Think very carefully before\n            setting this to ``True`` as that could make your application\n            vulnerable to man-in-the-middle attacks.\n          - `tlsCAFile`: A file containing a single or a bundle of\n            \"certification authority\" certificates, which are used to validate\n            certificates passed from the other end of the connection.\n            Implies ``tls=True``. Defaults to ``None``.\n          - `tlsCertificateKeyFile`: A file containing the client certificate\n            and private key. If you want to pass the certificate and private\n            key as separate files, use the ``ssl_certfile`` and ``ssl_keyfile``\n            options instead. Implies ``tls=True``. Defaults to ``None``.\n          - `tlsCRLFile`: A file containing a PEM or DER formatted\n            certificate revocation list. Only supported by python 2.7.9+\n            (pypy 2.5.1+). Implies ``tls=True``. Defaults to ``None``.\n          - `tlsCertificateKeyFilePassword`: The password or passphrase for\n            decrypting the private key in ``tlsCertificateKeyFile`` or\n            ``ssl_keyfile``. Only necessary if the private key is encrypted.\n            Only supported by python 2.7.9+ (pypy 2.5.1+) and 3.3+. Defaults\n            to ``None``.\n          - `ssl`: (boolean) Alias for ``tls``.\n          - `ssl_certfile`: The certificate file used to identify the local\n            connection against mongod. Implies ``tls=True``. Defaults to\n            ``None``.\n          - `ssl_keyfile`: The private keyfile used to identify the local\n            connection against mongod. Can be omitted if the keyfile is\n            included with the ``tlsCertificateKeyFile``. Implies ``tls=True``.\n            Defaults to ``None``.\n\n          | **Read Concern options:**\n          | (If not set explicitly, this will use the server default)\n\n          - `readConcernLevel`: (string) The read concern level specifies the\n            level of isolation for read operations.  For example, a read\n            operation using a read concern level of ``majority`` will only\n            return data that has been written to a majority of nodes. If the\n            level is left unspecified, the server default will be used.\n\n          | **Client side encryption options:**\n          | (If not set explicitly, client side encryption will not be enabled.)\n\n          - `auto_encryption_opts`: A\n            :class:`~pymongo.encryption_options.AutoEncryptionOpts` which\n            configures this client to automatically encrypt collection commands\n            and automatically decrypt results. **Support for client side\n            encryption is in beta. Backwards-breaking changes may be made\n            before the final release.**\n\n        .. mongodoc:: connections\n\n        .. versionchanged:: 3.9\n           Added the ``retryReads`` keyword argument and URI option.\n           Added the ``tlsInsecure`` keyword argument and URI option.\n           The following keyword arguments and URI options were deprecated:\n\n             - ``wTimeout`` was deprecated in favor of ``wTimeoutMS``.\n             - ``j`` was deprecated in favor of ``journal``.\n             - ``ssl_cert_reqs`` was deprecated in favor of\n               ``tlsAllowInvalidCertificates``.\n             - ``ssl_match_hostname`` was deprecated in favor of\n               ``tlsAllowInvalidHostnames``.\n             - ``ssl_ca_certs`` was deprecated in favor of ``tlsCAFile``.\n             - ``ssl_certfile`` was deprecated in favor of\n               ``tlsCertificateKeyFile``.\n             - ``ssl_crlfile`` was deprecated in favor of ``tlsCRLFile``.\n             - ``ssl_pem_passphrase`` was deprecated in favor of\n               ``tlsCertificateKeyFilePassword``.\n\n        .. versionchanged:: 3.9\n           ``retryWrites`` now defaults to ``True``.\n\n        .. versionchanged:: 3.8\n           Added the ``server_selector`` keyword argument.\n           Added the ``type_registry`` keyword argument.\n\n        .. versionchanged:: 3.7\n           Added the ``driver`` keyword argument.\n\n        .. versionchanged:: 3.6\n           Added support for mongodb+srv:// URIs.\n           Added the ``retryWrites`` keyword argument and URI option.\n\n        .. versionchanged:: 3.5\n           Add ``username`` and ``password`` options. Document the\n           ``authSource``, ``authMechanism``, and ``authMechanismProperties ``\n           options.\n           Deprecated the ``socketKeepAlive`` keyword argument and URI option.\n           ``socketKeepAlive`` now defaults to ``True``.\n\n        .. versionchanged:: 3.0\n           :class:`~pymongo.mongo_client.MongoClient` is now the one and only\n           client class for a standalone server, mongos, or replica set.\n           It includes the functionality that had been split into\n           :class:`~pymongo.mongo_client.MongoReplicaSetClient`: it can connect\n           to a replica set, discover all its members, and monitor the set for\n           stepdowns, elections, and reconfigs.\n\n           The :class:`~pymongo.mongo_client.MongoClient` constructor no\n           longer blocks while connecting to the server or servers, and it no\n           longer raises :class:`~pymongo.errors.ConnectionFailure` if they\n           are unavailable, nor :class:`~pymongo.errors.ConfigurationError`\n           if the user's credentials are wrong. Instead, the constructor\n           returns immediately and launches the connection process on\n           background threads.\n\n           Therefore the ``alive`` method is removed since it no longer\n           provides meaningful information; even if the client is disconnected,\n           it may discover a server in time to fulfill the next operation.\n\n           In PyMongo 2.x, :class:`~pymongo.MongoClient` accepted a list of\n           standalone MongoDB servers and used the first it could connect to::\n\n               MongoClient(['host1.com:27017', 'host2.com:27017'])\n\n           A list of multiple standalones is no longer supported; if multiple\n           servers are listed they must be members of the same replica set, or\n           mongoses in the same sharded cluster.\n\n           The behavior for a list of mongoses is changed from \"high\n           availability\" to \"load balancing\". Before, the client connected to\n           the lowest-latency mongos in the list, and used it until a network\n           error prompted it to re-evaluate all mongoses' latencies and\n           reconnect to one of them. In PyMongo 3, the client monitors its\n           network latency to all the mongoses continuously, and distributes\n           operations evenly among those with the lowest latency. See\n           :ref:`mongos-load-balancing` for more information.\n\n           The ``connect`` option is added.\n\n           The ``start_request``, ``in_request``, and ``end_request`` methods\n           are removed, as well as the ``auto_start_request`` option.\n\n           The ``copy_database`` method is removed, see the\n           :doc:`copy_database examples </examples/copydb>` for alternatives.\n\n           The :meth:`MongoClient.disconnect` method is removed; it was a\n           synonym for :meth:`~pymongo.MongoClient.close`.\n\n           :class:`~pymongo.mongo_client.MongoClient` no longer returns an\n           instance of :class:`~pymongo.database.Database` for attribute names\n           with leading underscores. You must use dict-style lookups instead::\n\n               client['__my_database__']\n\n           Not::\n\n               client.__my_database__\n        \"\"\"\n        if host is None:\n            host = self.HOST\n        if isinstance(host, string_type):\n            host = [host]\n        if port is None:\n            port = self.PORT\n        if not isinstance(port, int):\n            raise TypeError(\"port must be an instance of int\")\n\n        # _pool_class, _monitor_class, and _condition_class are for deep\n        # customization of PyMongo, e.g. Motor.\n        pool_class = kwargs.pop('_pool_class', None)\n        monitor_class = kwargs.pop('_monitor_class', None)\n        condition_class = kwargs.pop('_condition_class', None)\n\n        # Parse options passed as kwargs.\n        keyword_opts = common._CaseInsensitiveDictionary(kwargs)\n        keyword_opts['document_class'] = document_class\n\n        seeds = set()\n        username = None\n        password = None\n        dbase = None\n        opts = {}\n        fqdn = None\n        for entity in host:\n            if \"://\" in entity:\n                # Determine connection timeout from kwargs.\n                timeout = keyword_opts.get(\"connecttimeoutms\")\n                if timeout is not None:\n                    timeout = common.validate_timeout_or_none(\n                        keyword_opts.cased_key(\"connecttimeoutms\"), timeout)\n                res = uri_parser.parse_uri(\n                    entity, port, validate=True, warn=True, normalize=False,\n                    connect_timeout=timeout)\n                seeds.update(res[\"nodelist\"])\n                username = res[\"username\"] or username\n                password = res[\"password\"] or password\n                dbase = res[\"database\"] or dbase\n                opts = res[\"options\"]\n                fqdn = res[\"fqdn\"]\n            else:\n                seeds.update(uri_parser.split_hosts(entity, port))\n        if not seeds:\n            raise ConfigurationError(\"need to specify at least one host\")\n\n        # Add options with named keyword arguments to the parsed kwarg options.\n        if type_registry is not None:\n            keyword_opts['type_registry'] = type_registry\n        if tz_aware is None:\n            tz_aware = opts.get('tz_aware', False)\n        if connect is None:\n            connect = opts.get('connect', True)\n        keyword_opts['tz_aware'] = tz_aware\n        keyword_opts['connect'] = connect\n\n        # Handle deprecated options in kwarg options.\n        keyword_opts = _handle_option_deprecations(keyword_opts)\n        # Validate kwarg options.\n        keyword_opts = common._CaseInsensitiveDictionary(\n            dict(common.validate(k, v) for k, v in keyword_opts.items()))\n\n        # Override connection string options with kwarg options.\n        opts.update(keyword_opts)\n        # Handle security-option conflicts in combined options.\n        opts = _handle_security_options(opts)\n        # Normalize combined options.\n        opts = _normalize_options(opts)\n\n        # Username and password passed as kwargs override user info in URI.\n        username = opts.get(\"username\", username)\n        password = opts.get(\"password\", password)\n        if 'socketkeepalive' in opts:\n            warnings.warn(\n                \"The socketKeepAlive option is deprecated. It now\"\n                \"defaults to true and disabling it is not recommended, see \"\n                \"https://docs.mongodb.com/manual/faq/diagnostics/\"\n                \"#does-tcp-keepalive-time-affect-mongodb-deployments\",\n                DeprecationWarning, stacklevel=2)\n        self.__options = options = ClientOptions(\n            username, password, dbase, opts)\n\n        self.__default_database_name = dbase\n        self.__lock = threading.Lock()\n        self.__cursor_manager = None\n        self.__kill_cursors_queue = []\n\n        self._event_listeners = options.pool_options.event_listeners\n\n        # Cache of existing indexes used by ensure_index ops.\n        self.__index_cache = {}\n        self.__index_cache_lock = threading.Lock()\n\n        super(MongoClient, self).__init__(options.codec_options,\n                                          options.read_preference,\n                                          options.write_concern,\n                                          options.read_concern)\n\n        self.__all_credentials = {}\n        creds = options.credentials\n        if creds:\n            self._cache_credentials(creds.source, creds)\n\n        self._topology_settings = TopologySettings(\n            seeds=seeds,\n            replica_set_name=options.replica_set_name,\n            pool_class=pool_class,\n            pool_options=options.pool_options,\n            monitor_class=monitor_class,\n            condition_class=condition_class,\n            local_threshold_ms=options.local_threshold_ms,\n            server_selection_timeout=options.server_selection_timeout,\n            server_selector=options.server_selector,\n            heartbeat_frequency=options.heartbeat_frequency,\n            fqdn=fqdn)\n\n        self._topology = Topology(self._topology_settings)\n        if connect:\n            self._topology.open()\n\n        def target():\n            client = self_ref()\n            if client is None:\n                return False  # Stop the executor.\n            MongoClient._process_periodic_tasks(client)\n            return True\n\n        executor = periodic_executor.PeriodicExecutor(\n            interval=common.KILL_CURSOR_FREQUENCY,\n            min_interval=0.5,\n            target=target,\n            name=\"pymongo_kill_cursors_thread\")\n\n        # We strongly reference the executor and it weakly references us via\n        # this closure. When the client is freed, stop the executor soon.\n        self_ref = weakref.ref(self, executor.close)\n        self._kill_cursors_executor = executor\n        executor.open()\n\n        self._encrypter = None\n        if self.__options.auto_encryption_opts:\n            from pymongo.encryption import _Encrypter\n            self._encrypter = _Encrypter.create(\n                self, self.__options.auto_encryption_opts)\n\n    def _cache_credentials(self, source, credentials, connect=False):\n        \"\"\"Save a set of authentication credentials.\n\n        The credentials are used to login a socket whenever one is created.\n        If `connect` is True, verify the credentials on the server first.\n        \"\"\"\n        # Don't let other threads affect this call's data.\n        all_credentials = self.__all_credentials.copy()\n\n        if source in all_credentials:\n            # Nothing to do if we already have these credentials.\n            if credentials == all_credentials[source]:\n                return\n            raise OperationFailure('Another user is already authenticated '\n                                   'to this database. You must logout first.')\n\n        if connect:\n            server = self._get_topology().select_server(\n                writable_preferred_server_selector)\n\n            # get_socket() logs out of the database if logged in with old\n            # credentials, and logs in with new ones.\n            with server.get_socket(all_credentials) as sock_info:\n                sock_info.authenticate(credentials)\n\n        # If several threads run _cache_credentials at once, last one wins.\n        self.__all_credentials[source] = credentials\n\n    def _purge_credentials(self, source):\n        \"\"\"Purge credentials from the authentication cache.\"\"\"\n        self.__all_credentials.pop(source, None)\n\n    def _cached(self, dbname, coll, index):\n        \"\"\"Test if `index` is cached.\"\"\"\n        cache = self.__index_cache\n        now = datetime.datetime.utcnow()\n        with self.__index_cache_lock:\n            return (dbname in cache and\n                    coll in cache[dbname] and\n                    index in cache[dbname][coll] and\n                    now < cache[dbname][coll][index])\n\n    def _cache_index(self, dbname, collection, index, cache_for):\n        \"\"\"Add an index to the index cache for ensure_index operations.\"\"\"\n        now = datetime.datetime.utcnow()\n        expire = datetime.timedelta(seconds=cache_for) + now\n\n        with self.__index_cache_lock:\n            if dbname not in self.__index_cache:\n                self.__index_cache[dbname] = {}\n                self.__index_cache[dbname][collection] = {}\n                self.__index_cache[dbname][collection][index] = expire\n\n            elif collection not in self.__index_cache[dbname]:\n                self.__index_cache[dbname][collection] = {}\n                self.__index_cache[dbname][collection][index] = expire\n\n            else:\n                self.__index_cache[dbname][collection][index] = expire\n\n    def _purge_index(self, database_name,\n                     collection_name=None, index_name=None):\n        \"\"\"Purge an index from the index cache.\n\n        If `index_name` is None purge an entire collection.\n\n        If `collection_name` is None purge an entire database.\n        \"\"\"\n        with self.__index_cache_lock:\n            if not database_name in self.__index_cache:\n                return\n\n            if collection_name is None:\n                del self.__index_cache[database_name]\n                return\n\n            if not collection_name in self.__index_cache[database_name]:\n                return\n\n            if index_name is None:\n                del self.__index_cache[database_name][collection_name]\n                return\n\n            if index_name in self.__index_cache[database_name][collection_name]:\n                del self.__index_cache[database_name][collection_name][index_name]\n\n    def _server_property(self, attr_name):\n        \"\"\"An attribute of the current server's description.\n\n        If the client is not connected, this will block until a connection is\n        established or raise ServerSelectionTimeoutError if no server is\n        available.\n\n        Not threadsafe if used multiple times in a single method, since\n        the server may change. In such cases, store a local reference to a\n        ServerDescription first, then use its properties.\n        \"\"\"\n        server = self._topology.select_server(\n            writable_server_selector)\n\n        return getattr(server.description, attr_name)\n\n    def watch(self, pipeline=None, full_document=None, resume_after=None,\n              max_await_time_ms=None, batch_size=None, collation=None,\n              start_at_operation_time=None, session=None, start_after=None):\n        \"\"\"Watch changes on this cluster.\n\n        Performs an aggregation with an implicit initial ``$changeStream``\n        stage and returns a\n        :class:`~pymongo.change_stream.ClusterChangeStream` cursor which\n        iterates over changes on all databases on this cluster.\n\n        Introduced in MongoDB 4.0.\n\n        .. code-block:: python\n\n           with client.watch() as stream:\n               for change in stream:\n                   print(change)\n\n        The :class:`~pymongo.change_stream.ClusterChangeStream` iterable\n        blocks until the next change document is returned or an error is\n        raised. If the\n        :meth:`~pymongo.change_stream.ClusterChangeStream.next` method\n        encounters a network error when retrieving a batch from the server,\n        it will automatically attempt to recreate the cursor such that no\n        change events are missed. Any error encountered during the resume\n        attempt indicates there may be an outage and will be raised.\n\n        .. code-block:: python\n\n            try:\n                with client.watch(\n                        [{'$match': {'operationType': 'insert'}}]) as stream:\n                    for insert_change in stream:\n                        print(insert_change)\n            except pymongo.errors.PyMongoError:\n                # The ChangeStream encountered an unrecoverable error or the\n                # resume attempt failed to recreate the cursor.\n                logging.error('...')\n\n        For a precise description of the resume process see the\n        `change streams specification`_.\n\n        :Parameters:\n          - `pipeline` (optional): A list of aggregation pipeline stages to\n            append to an initial ``$changeStream`` stage. Not all\n            pipeline stages are valid after a ``$changeStream`` stage, see the\n            MongoDB documentation on change streams for the supported stages.\n          - `full_document` (optional): The fullDocument to pass as an option\n            to the ``$changeStream`` stage. Allowed values: 'updateLookup'.\n            When set to 'updateLookup', the change notification for partial\n            updates will include both a delta describing the changes to the\n            document, as well as a copy of the entire document that was\n            changed from some time after the change occurred.\n          - `resume_after` (optional): A resume token. If provided, the\n            change stream will start returning changes that occur directly\n            after the operation specified in the resume token. A resume token\n            is the _id value of a change document.\n          - `max_await_time_ms` (optional): The maximum time in milliseconds\n            for the server to wait for changes before responding to a getMore\n            operation.\n          - `batch_size` (optional): The maximum number of documents to return\n            per batch.\n          - `collation` (optional): The :class:`~pymongo.collation.Collation`\n            to use for the aggregation.\n          - `start_at_operation_time` (optional): If provided, the resulting\n            change stream will only return changes that occurred at or after\n            the specified :class:`~bson.timestamp.Timestamp`. Requires\n            MongoDB >= 4.0.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `start_after` (optional): The same as `resume_after` except that\n            `start_after` can resume notifications after an invalidate event.\n            This option and `resume_after` are mutually exclusive.\n\n        :Returns:\n          A :class:`~pymongo.change_stream.ClusterChangeStream` cursor.\n\n        .. versionchanged:: 3.9\n           Added the ``start_after`` parameter.\n\n        .. versionadded:: 3.7\n\n        .. mongodoc:: changeStreams\n\n        .. _change streams specification:\n            https://github.com/mongodb/specifications/blob/master/source/change-streams/change-streams.rst\n        \"\"\"\n        return ClusterChangeStream(\n            self.admin, pipeline, full_document, resume_after, max_await_time_ms,\n            batch_size, collation, start_at_operation_time, session,\n            start_after)\n\n    @property\n    def event_listeners(self):\n        \"\"\"The event listeners registered for this client.\n\n        See :mod:`~pymongo.monitoring` for details.\n        \"\"\"\n        return self._event_listeners.event_listeners\n\n    @property\n    def address(self):\n        \"\"\"(host, port) of the current standalone, primary, or mongos, or None.\n\n        Accessing :attr:`address` raises :exc:`~.errors.InvalidOperation` if\n        the client is load-balancing among mongoses, since there is no single\n        address. Use :attr:`nodes` instead.\n\n        If the client is not connected, this will block until a connection is\n        established or raise ServerSelectionTimeoutError if no server is\n        available.\n\n        .. versionadded:: 3.0\n        \"\"\"\n        topology_type = self._topology._description.topology_type\n        if topology_type == TOPOLOGY_TYPE.Sharded:\n            raise InvalidOperation(\n                'Cannot use \"address\" property when load balancing among'\n                ' mongoses, use \"nodes\" instead.')\n        if topology_type not in (TOPOLOGY_TYPE.ReplicaSetWithPrimary,\n                                 TOPOLOGY_TYPE.Single):\n            return None\n        return self._server_property('address')\n\n    @property\n    def primary(self):\n        \"\"\"The (host, port) of the current primary of the replica set.\n\n        Returns ``None`` if this client is not connected to a replica set,\n        there is no primary, or this client was created without the\n        `replicaSet` option.\n\n        .. versionadded:: 3.0\n           MongoClient gained this property in version 3.0 when\n           MongoReplicaSetClient's functionality was merged in.\n        \"\"\"\n        return self._topology.get_primary()\n\n    @property\n    def secondaries(self):\n        \"\"\"The secondary members known to this client.\n\n        A sequence of (host, port) pairs. Empty if this client is not\n        connected to a replica set, there are no visible secondaries, or this\n        client was created without the `replicaSet` option.\n\n        .. versionadded:: 3.0\n           MongoClient gained this property in version 3.0 when\n           MongoReplicaSetClient's functionality was merged in.\n        \"\"\"\n        return self._topology.get_secondaries()\n\n    @property\n    def arbiters(self):\n        \"\"\"Arbiters in the replica set.\n\n        A sequence of (host, port) pairs. Empty if this client is not\n        connected to a replica set, there are no arbiters, or this client was\n        created without the `replicaSet` option.\n        \"\"\"\n        return self._topology.get_arbiters()\n\n    @property\n    def is_primary(self):\n        \"\"\"If this client is connected to a server that can accept writes.\n\n        True if the current server is a standalone, mongos, or the primary of\n        a replica set. If the client is not connected, this will block until a\n        connection is established or raise ServerSelectionTimeoutError if no\n        server is available.\n        \"\"\"\n        return self._server_property('is_writable')\n\n    @property\n    def is_mongos(self):\n        \"\"\"If this client is connected to mongos. If the client is not\n        connected, this will block until a connection is established or raise\n        ServerSelectionTimeoutError if no server is available..\n        \"\"\"\n        return self._server_property('server_type') == SERVER_TYPE.Mongos\n\n    @property\n    def max_pool_size(self):\n        \"\"\"The maximum allowable number of concurrent connections to each\n        connected server. Requests to a server will block if there are\n        `maxPoolSize` outstanding connections to the requested server.\n        Defaults to 100. Cannot be 0.\n\n        When a server's pool has reached `max_pool_size`, operations for that\n        server block waiting for a socket to be returned to the pool. If\n        ``waitQueueTimeoutMS`` is set, a blocked operation will raise\n        :exc:`~pymongo.errors.ConnectionFailure` after a timeout.\n        By default ``waitQueueTimeoutMS`` is not set.\n        \"\"\"\n        return self.__options.pool_options.max_pool_size\n\n    @property\n    def min_pool_size(self):\n        \"\"\"The minimum required number of concurrent connections that the pool\n        will maintain to each connected server. Default is 0.\n        \"\"\"\n        return self.__options.pool_options.min_pool_size\n\n    @property\n    def max_idle_time_ms(self):\n        \"\"\"The maximum number of milliseconds that a connection can remain\n        idle in the pool before being removed and replaced. Defaults to\n        `None` (no limit).\n        \"\"\"\n        seconds = self.__options.pool_options.max_idle_time_seconds\n        if seconds is None:\n            return None\n        return 1000 * seconds\n\n    @property\n    def nodes(self):\n        \"\"\"Set of all currently connected servers.\n\n        .. warning:: When connected to a replica set the value of :attr:`nodes`\n          can change over time as :class:`MongoClient`'s view of the replica\n          set changes. :attr:`nodes` can also be an empty set when\n          :class:`MongoClient` is first instantiated and hasn't yet connected\n          to any servers, or a network partition causes it to lose connection\n          to all servers.\n        \"\"\"\n        description = self._topology.description\n        return frozenset(s.address for s in description.known_servers)\n\n    @property\n    def max_bson_size(self):\n        \"\"\"The largest BSON object the connected server accepts in bytes.\n\n        If the client is not connected, this will block until a connection is\n        established or raise ServerSelectionTimeoutError if no server is\n        available.\n        \"\"\"\n        return self._server_property('max_bson_size')\n\n    @property\n    def max_message_size(self):\n        \"\"\"The largest message the connected server accepts in bytes.\n\n        If the client is not connected, this will block until a connection is\n        established or raise ServerSelectionTimeoutError if no server is\n        available.\n        \"\"\"\n        return self._server_property('max_message_size')\n\n    @property\n    def max_write_batch_size(self):\n        \"\"\"The maxWriteBatchSize reported by the server.\n\n        If the client is not connected, this will block until a connection is\n        established or raise ServerSelectionTimeoutError if no server is\n        available.\n\n        Returns a default value when connected to server versions prior to\n        MongoDB 2.6.\n        \"\"\"\n        return self._server_property('max_write_batch_size')\n\n    @property\n    def local_threshold_ms(self):\n        \"\"\"The local threshold for this instance.\"\"\"\n        return self.__options.local_threshold_ms\n\n    @property\n    def server_selection_timeout(self):\n        \"\"\"The server selection timeout for this instance in seconds.\"\"\"\n        return self.__options.server_selection_timeout\n\n    @property\n    def retry_writes(self):\n        \"\"\"If this instance should retry supported write operations.\"\"\"\n        return self.__options.retry_writes\n\n    @property\n    def retry_reads(self):\n        \"\"\"If this instance should retry supported write operations.\"\"\"\n        return self.__options.retry_reads\n\n    def _is_writable(self):\n        \"\"\"Attempt to connect to a writable server, or return False.\n        \"\"\"\n        topology = self._get_topology()  # Starts monitors if necessary.\n        try:\n            svr = topology.select_server(writable_server_selector)\n\n            # When directly connected to a secondary, arbiter, etc.,\n            # select_server returns it, whatever the selector. Check\n            # again if the server is writable.\n            return svr.description.is_writable\n        except ConnectionFailure:\n            return False\n\n    def _end_sessions(self, session_ids):\n        \"\"\"Send endSessions command(s) with the given session ids.\"\"\"\n        try:\n            # Use SocketInfo.command directly to avoid implicitly creating\n            # another session.\n            with self._socket_for_reads(\n                    ReadPreference.PRIMARY_PREFERRED,\n                    None) as (sock_info, slave_ok):\n                if not sock_info.supports_sessions:\n                    return\n\n                for i in range(0, len(session_ids), common._MAX_END_SESSIONS):\n                    spec = SON([('endSessions',\n                                 session_ids[i:i + common._MAX_END_SESSIONS])])\n                    sock_info.command(\n                        'admin', spec, slave_ok=slave_ok, client=self)\n        except PyMongoError:\n            # Drivers MUST ignore any errors returned by the endSessions\n            # command.\n            pass\n\n    def close(self):\n        \"\"\"Cleanup client resources and disconnect from MongoDB.\n\n        On MongoDB >= 3.6, end all server sessions created by this client by\n        sending one or more endSessions commands.\n\n        Close all sockets in the connection pools and stop the monitor threads.\n        If this instance is used again it will be automatically re-opened and\n        the threads restarted unless auto encryption is enabled. A client\n        enabled with auto encryption cannot be used again after being closed;\n        any attempt will raise :exc:`~.errors.InvalidOperation`.\n\n        .. versionchanged:: 3.6\n           End all server sessions created by this client.\n        \"\"\"\n        session_ids = self._topology.pop_all_sessions()\n        if session_ids:\n            self._end_sessions(session_ids)\n        # Stop the periodic task thread and then run _process_periodic_tasks\n        # to send pending killCursor requests before closing the topology.\n        self._kill_cursors_executor.close()\n        self._process_periodic_tasks()\n        self._topology.close()\n        if self._encrypter:\n            # TODO: PYTHON-1921 Encrypted MongoClients cannot be re-opened.\n            self._encrypter.close()\n\n    def set_cursor_manager(self, manager_class):\n        \"\"\"DEPRECATED - Set this client's cursor manager.\n\n        Raises :class:`TypeError` if `manager_class` is not a subclass of\n        :class:`~pymongo.cursor_manager.CursorManager`. A cursor manager\n        handles closing cursors. Different managers can implement different\n        policies in terms of when to actually kill a cursor that has\n        been closed.\n\n        :Parameters:\n          - `manager_class`: cursor manager to use\n\n        .. versionchanged:: 3.3\n           Deprecated, for real this time.\n\n        .. versionchanged:: 3.0\n           Undeprecated.\n        \"\"\"\n        warnings.warn(\n            \"set_cursor_manager is Deprecated\",\n            DeprecationWarning,\n            stacklevel=2)\n        manager = manager_class(self)\n        if not isinstance(manager, CursorManager):\n            raise TypeError(\"manager_class must be a subclass of \"\n                            \"CursorManager\")\n\n        self.__cursor_manager = manager\n\n    def _get_topology(self):\n        \"\"\"Get the internal :class:`~pymongo.topology.Topology` object.\n\n        If this client was created with \"connect=False\", calling _get_topology\n        launches the connection process in the background.\n        \"\"\"\n        self._topology.open()\n        with self.__lock:\n            self._kill_cursors_executor.open()\n        return self._topology\n\n    @contextlib.contextmanager\n    def _get_socket(self, server, session, exhaust=False):\n        with _MongoClientErrorHandler(\n                self, server.description.address, session) as err_handler:\n            with server.get_socket(\n                    self.__all_credentials, checkout=exhaust) as sock_info:\n                err_handler.contribute_socket(sock_info)\n                if (self._encrypter and\n                        not self._encrypter._bypass_auto_encryption and\n                        sock_info.max_wire_version < 8):\n                    raise ConfigurationError(\n                        'Auto-encryption requires a minimum MongoDB version '\n                        'of 4.2')\n                yield sock_info\n\n    def _select_server(self, server_selector, session, address=None):\n        \"\"\"Select a server to run an operation on this client.\n\n        :Parameters:\n          - `server_selector`: The server selector to use if the session is\n            not pinned and no address is given.\n          - `session`: The ClientSession for the next operation, or None. May\n            be pinned to a mongos server address.\n          - `address` (optional): Address when sending a message\n            to a specific server, used for getMore.\n        \"\"\"\n        try:\n            topology = self._get_topology()\n            address = address or (session and session._pinned_address)\n            if address:\n                # We're running a getMore or this session is pinned to a mongos.\n                server = topology.select_server_by_address(address)\n                if not server:\n                    raise AutoReconnect('server %s:%d no longer available'\n                                        % address)\n            else:\n                server = topology.select_server(server_selector)\n                # Pin this session to the selected server if it's performing a\n                # sharded transaction.\n                if server.description.mongos and (session and\n                                                  session._in_transaction):\n                    session._pin_mongos(server)\n            return server\n        except PyMongoError as exc:\n            if session and exc.has_error_label(\"TransientTransactionError\"):\n                session._unpin_mongos()\n            raise\n\n    def _socket_for_writes(self, session):\n        server = self._select_server(writable_server_selector, session)\n        return self._get_socket(server, session)\n\n    @contextlib.contextmanager\n    def _slaveok_for_server(self, read_preference, server, session,\n                            exhaust=False):\n        assert read_preference is not None, \"read_preference must not be None\"\n        # Get a socket for a server matching the read preference, and yield\n        # sock_info, slave_ok. Server Selection Spec: \"slaveOK must be sent to\n        # mongods with topology type Single. If the server type is Mongos,\n        # follow the rules for passing read preference to mongos, even for\n        # topology type Single.\"\n        # Thread safe: if the type is single it cannot change.\n        topology = self._get_topology()\n        single = topology.description.topology_type == TOPOLOGY_TYPE.Single\n\n        with self._get_socket(server, session, exhaust=exhaust) as sock_info:\n            slave_ok = (single and not sock_info.is_mongos) or (\n                read_preference != ReadPreference.PRIMARY)\n            yield sock_info, slave_ok\n\n    @contextlib.contextmanager\n    def _socket_for_reads(self, read_preference, session):\n        assert read_preference is not None, \"read_preference must not be None\"\n        # Get a socket for a server matching the read preference, and yield\n        # sock_info, slave_ok. Server Selection Spec: \"slaveOK must be sent to\n        # mongods with topology type Single. If the server type is Mongos,\n        # follow the rules for passing read preference to mongos, even for\n        # topology type Single.\"\n        # Thread safe: if the type is single it cannot change.\n        topology = self._get_topology()\n        single = topology.description.topology_type == TOPOLOGY_TYPE.Single\n        server = self._select_server(read_preference, session)\n\n        with self._get_socket(server, session) as sock_info:\n            slave_ok = (single and not sock_info.is_mongos) or (\n                read_preference != ReadPreference.PRIMARY)\n            yield sock_info, slave_ok\n\n    def _run_operation_with_response(self, operation, unpack_res,\n                                     exhaust=False, address=None):\n        \"\"\"Run a _Query/_GetMore operation and return a Response.\n\n        :Parameters:\n          - `operation`: a _Query or _GetMore object.\n          - `unpack_res`: A callable that decodes the wire protocol response.\n          - `exhaust` (optional): If True, the socket used stays checked out.\n            It is returned along with its Pool in the Response.\n          - `address` (optional): Optional address when sending a message\n            to a specific server, used for getMore.\n        \"\"\"\n        if operation.exhaust_mgr:\n            server = self._select_server(\n                operation.read_preference, operation.session, address=address)\n\n            with _MongoClientErrorHandler(\n                    self, server.description.address,\n                    operation.session) as err_handler:\n                err_handler.contribute_socket(operation.exhaust_mgr.sock)\n                return server.run_operation_with_response(\n                    operation.exhaust_mgr.sock,\n                    operation,\n                    True,\n                    self._event_listeners,\n                    exhaust,\n                    unpack_res)\n\n        def _cmd(session, server, sock_info, slave_ok):\n            return server.run_operation_with_response(\n                sock_info,\n                operation,\n                slave_ok,\n                self._event_listeners,\n                exhaust,\n                unpack_res)\n\n        return self._retryable_read(\n            _cmd, operation.read_preference, operation.session,\n            address=address,\n            retryable=isinstance(operation, message._Query),\n            exhaust=exhaust)\n\n    def _retry_with_session(self, retryable, func, session, bulk):\n        \"\"\"Execute an operation with at most one consecutive retries\n\n        Returns func()'s return value on success. On error retries the same\n        command once.\n\n        Re-raises any exception thrown by func().\n        \"\"\"\n        retryable = (retryable and self.retry_writes\n                     and session and not session._in_transaction)\n        last_error = None\n        retrying = False\n\n        def is_retrying():\n            return bulk.retrying if bulk else retrying\n        # Increment the transaction id up front to ensure any retry attempt\n        # will use the proper txnNumber, even if server or socket selection\n        # fails before the command can be sent.\n        if retryable:\n            session._start_retryable_write()\n            if bulk:\n                bulk.started_retryable_write = True\n\n        while True:\n            try:\n                server = self._select_server(writable_server_selector, session)\n                supports_session = (\n                    session is not None and\n                    server.description.retryable_writes_supported)\n                with self._get_socket(server, session) as sock_info:\n                    if retryable and not supports_session:\n                        if is_retrying():\n                            # A retry is not possible because this server does\n                            # not support sessions raise the last error.\n                            raise last_error\n                        retryable = False\n                    return func(session, sock_info, retryable)\n            except ServerSelectionTimeoutError:\n                if is_retrying():\n                    # The application may think the write was never attempted\n                    # if we raise ServerSelectionTimeoutError on the retry\n                    # attempt. Raise the original exception instead.\n                    raise last_error\n                # A ServerSelectionTimeoutError error indicates that there may\n                # be a persistent outage. Attempting to retry in this case will\n                # most likely be a waste of time.\n                raise\n            except ConnectionFailure as exc:\n                if not retryable or is_retrying():\n                    raise\n                if bulk:\n                    bulk.retrying = True\n                else:\n                    retrying = True\n                last_error = exc\n            except BulkWriteError as exc:\n                if not retryable or is_retrying():\n                    raise\n                # Check the last writeConcernError to determine if this\n                # BulkWriteError is retryable.\n                wces = exc.details['writeConcernErrors']\n                wce = wces[-1] if wces else {}\n                if wce.get('code', 0) not in helpers._RETRYABLE_ERROR_CODES:\n                    raise\n                if bulk:\n                    bulk.retrying = True\n                else:\n                    retrying = True\n                last_error = exc\n            except OperationFailure as exc:\n                # retryWrites on MMAPv1 should raise an actionable error.\n                if (exc.code == 20 and\n                        str(exc).startswith(\"Transaction numbers\")):\n                    errmsg = (\n                        \"This MongoDB deployment does not support \"\n                        \"retryable writes. Please add retryWrites=false \"\n                        \"to your connection string.\")\n                    raise OperationFailure(errmsg, exc.code, exc.details)\n                if not retryable or is_retrying():\n                    raise\n                if exc.code not in helpers._RETRYABLE_ERROR_CODES:\n                    raise\n                if bulk:\n                    bulk.retrying = True\n                else:\n                    retrying = True\n                last_error = exc\n\n    def _retryable_read(self, func, read_pref, session, address=None,\n                        retryable=True, exhaust=False):\n        \"\"\"Execute an operation with at most one consecutive retries\n\n        Returns func()'s return value on success. On error retries the same\n        command once.\n\n        Re-raises any exception thrown by func().\n        \"\"\"\n        retryable = (retryable and\n                     self.retry_reads\n                     and not (session and session._in_transaction))\n        last_error = None\n        retrying = False\n\n        while True:\n            try:\n                server = self._select_server(\n                    read_pref, session, address=address)\n                if not server.description.retryable_reads_supported:\n                    retryable = False\n                with self._slaveok_for_server(read_pref, server, session,\n                                              exhaust=exhaust) as (sock_info,\n                                                                   slave_ok):\n                    if retrying and not retryable:\n                        # A retry is not possible because this server does\n                        # not support retryable reads, raise the last error.\n                        raise last_error\n                    return func(session, server, sock_info, slave_ok)\n            except ServerSelectionTimeoutError:\n                if retrying:\n                    # The application may think the write was never attempted\n                    # if we raise ServerSelectionTimeoutError on the retry\n                    # attempt. Raise the original exception instead.\n                    raise last_error\n                # A ServerSelectionTimeoutError error indicates that there may\n                # be a persistent outage. Attempting to retry in this case will\n                # most likely be a waste of time.\n                raise\n            except ConnectionFailure as exc:\n                if not retryable or retrying:\n                    raise\n                retrying = True\n                last_error = exc\n            except OperationFailure as exc:\n                if not retryable or retrying:\n                    raise\n                if exc.code not in helpers._RETRYABLE_ERROR_CODES:\n                    raise\n                retrying = True\n                last_error = exc\n\n    def _retryable_write(self, retryable, func, session):\n        \"\"\"Internal retryable write helper.\"\"\"\n        with self._tmp_session(session) as s:\n            return self._retry_with_session(retryable, func, s, None)\n\n    def _reset_server(self, address):\n        \"\"\"Clear our connection pool for a server and mark it Unknown.\"\"\"\n        self._topology.reset_server(address)\n\n    def _reset_server_and_request_check(self, address):\n        \"\"\"Clear our pool for a server, mark it Unknown, and check it soon.\"\"\"\n        self._topology.reset_server_and_request_check(address)\n\n    def __eq__(self, other):\n        if isinstance(other, self.__class__):\n            return self.address == other.address\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n\n    def _repr_helper(self):\n        def option_repr(option, value):\n            \"\"\"Fix options whose __repr__ isn't usable in a constructor.\"\"\"\n            if option == 'document_class':\n                if value is dict:\n                    return 'document_class=dict'\n                else:\n                    return 'document_class=%s.%s' % (value.__module__,\n                                                     value.__name__)\n            if option in common.TIMEOUT_OPTIONS and value is not None:\n                return \"%s=%s\" % (option, int(value * 1000))\n\n            return '%s=%r' % (option, value)\n\n        # Host first...\n        options = ['host=%r' % [\n            '%s:%d' % (host, port) if port is not None else host\n            for host, port in self._topology_settings.seeds]]\n        # ... then everything in self._constructor_args...\n        options.extend(\n            option_repr(key, self.__options._options[key])\n            for key in self._constructor_args)\n        # ... then everything else.\n        options.extend(\n            option_repr(key, self.__options._options[key])\n            for key in self.__options._options\n            if key not in set(self._constructor_args)\n            and key != 'username' and key != 'password')\n        return ', '.join(options)\n\n    def __repr__(self):\n        return (\"MongoClient(%s)\" % (self._repr_helper(),))\n\n    def __getattr__(self, name):\n        \"\"\"Get a database by name.\n\n        Raises :class:`~pymongo.errors.InvalidName` if an invalid\n        database name is used.\n\n        :Parameters:\n          - `name`: the name of the database to get\n        \"\"\"\n        if name.startswith('_'):\n            raise AttributeError(\n                \"MongoClient has no attribute %r. To access the %s\"\n                \" database, use client[%r].\" % (name, name, name))\n        return self.__getitem__(name)\n\n    def __getitem__(self, name):\n        \"\"\"Get a database by name.\n\n        Raises :class:`~pymongo.errors.InvalidName` if an invalid\n        database name is used.\n\n        :Parameters:\n          - `name`: the name of the database to get\n        \"\"\"\n        return database.Database(self, name)\n\n    def close_cursor(self, cursor_id, address=None):\n        \"\"\"DEPRECATED - Send a kill cursors message soon with the given id.\n\n        Raises :class:`TypeError` if `cursor_id` is not an instance of\n        ``(int, long)``. What closing the cursor actually means\n        depends on this client's cursor manager.\n\n        This method may be called from a :class:`~pymongo.cursor.Cursor`\n        destructor during garbage collection, so it isn't safe to take a\n        lock or do network I/O. Instead, we schedule the cursor to be closed\n        soon on a background thread.\n\n        :Parameters:\n          - `cursor_id`: id of cursor to close\n          - `address` (optional): (host, port) pair of the cursor's server.\n            If it is not provided, the client attempts to close the cursor on\n            the primary or standalone, or a mongos server.\n\n        .. versionchanged:: 3.7\n           Deprecated.\n\n        .. versionchanged:: 3.0\n           Added ``address`` parameter.\n        \"\"\"\n        warnings.warn(\n            \"close_cursor is deprecated.\",\n            DeprecationWarning,\n            stacklevel=2)\n        if not isinstance(cursor_id, integer_types):\n            raise TypeError(\"cursor_id must be an instance of (int, long)\")\n\n        self._close_cursor(cursor_id, address)\n\n    def _close_cursor(self, cursor_id, address):\n        \"\"\"Send a kill cursors message with the given id.\n\n        What closing the cursor actually means depends on this client's\n        cursor manager. If there is none, the cursor is closed asynchronously\n        on a background thread.\n        \"\"\"\n        if self.__cursor_manager is not None:\n            self.__cursor_manager.close(cursor_id, address)\n        else:\n            self.__kill_cursors_queue.append((address, [cursor_id]))\n\n    def _close_cursor_now(self, cursor_id, address=None, session=None):\n        \"\"\"Send a kill cursors message with the given id.\n\n        What closing the cursor actually means depends on this client's\n        cursor manager. If there is none, the cursor is closed synchronously\n        on the current thread.\n        \"\"\"\n        if not isinstance(cursor_id, integer_types):\n            raise TypeError(\"cursor_id must be an instance of (int, long)\")\n\n        if self.__cursor_manager is not None:\n            self.__cursor_manager.close(cursor_id, address)\n        else:\n            try:\n                self._kill_cursors(\n                    [cursor_id], address, self._get_topology(), session)\n            except PyMongoError:\n                # Make another attempt to kill the cursor later.\n                self.__kill_cursors_queue.append((address, [cursor_id]))\n\n    def kill_cursors(self, cursor_ids, address=None):\n        \"\"\"DEPRECATED - Send a kill cursors message soon with the given ids.\n\n        Raises :class:`TypeError` if `cursor_ids` is not an instance of\n        ``list``.\n\n        :Parameters:\n          - `cursor_ids`: list of cursor ids to kill\n          - `address` (optional): (host, port) pair of the cursor's server.\n            If it is not provided, the client attempts to close the cursor on\n            the primary or standalone, or a mongos server.\n\n        .. versionchanged:: 3.3\n           Deprecated.\n\n        .. versionchanged:: 3.0\n           Now accepts an `address` argument. Schedules the cursors to be\n           closed on a background thread instead of sending the message\n           immediately.\n        \"\"\"\n        warnings.warn(\n            \"kill_cursors is deprecated.\",\n            DeprecationWarning,\n            stacklevel=2)\n\n        if not isinstance(cursor_ids, list):\n            raise TypeError(\"cursor_ids must be a list\")\n\n        # \"Atomic\", needs no lock.\n        self.__kill_cursors_queue.append((address, cursor_ids))\n\n    def _kill_cursors(self, cursor_ids, address, topology, session):\n        \"\"\"Send a kill cursors message with the given ids.\"\"\"\n        listeners = self._event_listeners\n        publish = listeners.enabled_for_commands\n        if address:\n            # address could be a tuple or _CursorAddress, but\n            # select_server_by_address needs (host, port).\n            server = topology.select_server_by_address(tuple(address))\n        else:\n            # Application called close_cursor() with no address.\n            server = topology.select_server(writable_server_selector)\n\n        try:\n            namespace = address.namespace\n            db, coll = namespace.split('.', 1)\n        except AttributeError:\n            namespace = None\n            db = coll = \"OP_KILL_CURSORS\"\n\n        spec = SON([('killCursors', coll), ('cursors', cursor_ids)])\n        with server.get_socket(self.__all_credentials) as sock_info:\n            if sock_info.max_wire_version >= 4 and namespace is not None:\n                sock_info.command(db, spec, session=session, client=self)\n            else:\n                if publish:\n                    start = datetime.datetime.now()\n                request_id, msg = message.kill_cursors(cursor_ids)\n                if publish:\n                    duration = datetime.datetime.now() - start\n                    # Here and below, address could be a tuple or\n                    # _CursorAddress. We always want to publish a\n                    # tuple to match the rest of the monitoring\n                    # API.\n                    listeners.publish_command_start(\n                        spec, db, request_id, tuple(address))\n                    start = datetime.datetime.now()\n\n                try:\n                    sock_info.send_message(msg, 0)\n                except Exception as exc:\n                    if publish:\n                        dur = ((datetime.datetime.now() - start) + duration)\n                        listeners.publish_command_failure(\n                            dur, message._convert_exception(exc),\n                            'killCursors', request_id,\n                            tuple(address))\n                    raise\n\n                if publish:\n                    duration = ((datetime.datetime.now() - start) + duration)\n                    # OP_KILL_CURSORS returns no reply, fake one.\n                    reply = {'cursorsUnknown': cursor_ids, 'ok': 1}\n                    listeners.publish_command_success(\n                        duration, reply, 'killCursors', request_id,\n                        tuple(address))\n\n    # This method is run periodically by a background thread.\n    def _process_periodic_tasks(self):\n        \"\"\"Process any pending kill cursors requests and\n        maintain connection pool parameters.\"\"\"\n        address_to_cursor_ids = defaultdict(list)\n\n        # Other threads or the GC may append to the queue concurrently.\n        while True:\n            try:\n                address, cursor_ids = self.__kill_cursors_queue.pop()\n            except IndexError:\n                break\n\n            address_to_cursor_ids[address].extend(cursor_ids)\n\n        # Don't re-open topology if it's closed and there's no pending cursors.\n        if address_to_cursor_ids:\n            topology = self._get_topology()\n            for address, cursor_ids in address_to_cursor_ids.items():\n                try:\n                    self._kill_cursors(\n                        cursor_ids, address, topology, session=None)\n                except Exception:\n                    helpers._handle_exception()\n        try:\n            self._topology.update_pool()\n        except Exception:\n            helpers._handle_exception()\n\n    def __start_session(self, implicit, **kwargs):\n        # Driver Sessions Spec: \"If startSession is called when multiple users\n        # are authenticated drivers MUST raise an error with the error message\n        # 'Cannot call startSession when multiple users are authenticated.'\"\n        authset = set(self.__all_credentials.values())\n        if len(authset) > 1:\n            raise InvalidOperation(\"Cannot call start_session when\"\n                                   \" multiple users are authenticated\")\n\n        # Raises ConfigurationError if sessions are not supported.\n        server_session = self._get_server_session()\n        opts = client_session.SessionOptions(**kwargs)\n        return client_session.ClientSession(\n            self, server_session, opts, authset, implicit)\n\n    def start_session(self,\n                      causal_consistency=True,\n                      default_transaction_options=None):\n        \"\"\"Start a logical session.\n\n        This method takes the same parameters as\n        :class:`~pymongo.client_session.SessionOptions`. See the\n        :mod:`~pymongo.client_session` module for details and examples.\n\n        Requires MongoDB 3.6. It is an error to call :meth:`start_session`\n        if this client has been authenticated to multiple databases using the\n        deprecated method :meth:`~pymongo.database.Database.authenticate`.\n\n        A :class:`~pymongo.client_session.ClientSession` may only be used with\n        the MongoClient that started it.\n\n        :Returns:\n          An instance of :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionadded:: 3.6\n        \"\"\"\n        return self.__start_session(\n            False,\n            causal_consistency=causal_consistency,\n            default_transaction_options=default_transaction_options)\n\n    def _get_server_session(self):\n        \"\"\"Internal: start or resume a _ServerSession.\"\"\"\n        return self._topology.get_server_session()\n\n    def _return_server_session(self, server_session, lock):\n        \"\"\"Internal: return a _ServerSession to the pool.\"\"\"\n        return self._topology.return_server_session(server_session, lock)\n\n    def _ensure_session(self, session=None):\n        \"\"\"If provided session is None, lend a temporary session.\"\"\"\n        if session:\n            return session\n\n        try:\n            # Don't make implicit sessions causally consistent. Applications\n            # should always opt-in.\n            return self.__start_session(True, causal_consistency=False)\n        except (ConfigurationError, InvalidOperation):\n            # Sessions not supported, or multiple users authenticated.\n            return None\n\n    @contextlib.contextmanager\n    def _tmp_session(self, session, close=True):\n        \"\"\"If provided session is None, lend a temporary session.\"\"\"\n        if session:\n            # Don't call end_session.\n            yield session\n            return\n\n        s = self._ensure_session(session)\n        if s and close:\n            with s:\n                # Call end_session when we exit this scope.\n                yield s\n        elif s:\n            try:\n                # Only call end_session on error.\n                yield s\n            except Exception:\n                s.end_session()\n                raise\n        else:\n            yield None\n\n    def _send_cluster_time(self, command, session):\n        topology_time = self._topology.max_cluster_time()\n        session_time = session.cluster_time if session else None\n        if topology_time and session_time:\n            if topology_time['clusterTime'] > session_time['clusterTime']:\n                cluster_time = topology_time\n            else:\n                cluster_time = session_time\n        else:\n            cluster_time = topology_time or session_time\n        if cluster_time:\n            command['$clusterTime'] = cluster_time\n\n    def _process_response(self, reply, session):\n        self._topology.receive_cluster_time(reply.get('$clusterTime'))\n        if session is not None:\n            session._process_response(reply)\n\n    def server_info(self, session=None):\n        \"\"\"Get information about the MongoDB server we're connected to.\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        return self.admin.command(\"buildinfo\",\n                                  read_preference=ReadPreference.PRIMARY,\n                                  session=session)\n\n    def list_databases(self, session=None, **kwargs):\n        \"\"\"Get a cursor over the databases of the connected server.\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n          - `**kwargs` (optional): Optional parameters of the\n            `listDatabases command\n            <https://docs.mongodb.com/manual/reference/command/listDatabases/>`_\n            can be passed as keyword arguments to this method. The supported\n            options differ by server version.\n\n        :Returns:\n          An instance of :class:`~pymongo.command_cursor.CommandCursor`.\n\n        .. versionadded:: 3.6\n        \"\"\"\n        cmd = SON([(\"listDatabases\", 1)])\n        cmd.update(kwargs)\n        admin = self._database_default_options(\"admin\")\n        res = admin._retryable_read_command(cmd, session=session)\n        # listDatabases doesn't return a cursor (yet). Fake one.\n        cursor = {\n            \"id\": 0,\n            \"firstBatch\": res[\"databases\"],\n            \"ns\": \"admin.$cmd\",\n        }\n        return CommandCursor(admin[\"$cmd\"], cursor, None)\n\n    def list_database_names(self, session=None):\n        \"\"\"Get a list of the names of all databases on the connected server.\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionadded:: 3.6\n        \"\"\"\n        return [doc[\"name\"]\n                for doc in self.list_databases(session, nameOnly=True)]\n\n    def database_names(self, session=None):\n        \"\"\"**DEPRECATED**: Get a list of the names of all databases on the\n        connected server.\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.7\n           Deprecated. Use :meth:`list_database_names` instead.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        warnings.warn(\"database_names is deprecated. Use list_database_names \"\n                      \"instead.\", DeprecationWarning, stacklevel=2)\n        return self.list_database_names(session)\n\n    def drop_database(self, name_or_database, session=None):\n        \"\"\"Drop a database.\n\n        Raises :class:`TypeError` if `name_or_database` is not an instance of\n        :class:`basestring` (:class:`str` in python 3) or\n        :class:`~pymongo.database.Database`.\n\n        :Parameters:\n          - `name_or_database`: the name of a database to drop, or a\n            :class:`~pymongo.database.Database` instance representing the\n            database to drop\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. note:: The :attr:`~pymongo.mongo_client.MongoClient.write_concern` of\n           this client is automatically applied to this operation when using\n           MongoDB >= 3.4.\n\n        .. versionchanged:: 3.4\n           Apply this client's write concern automatically to this operation\n           when connected to MongoDB >= 3.4.\n\n        \"\"\"\n        name = name_or_database\n        if isinstance(name, database.Database):\n            name = name.name\n\n        if not isinstance(name, string_type):\n            raise TypeError(\"name_or_database must be an instance \"\n                            \"of %s or a Database\" % (string_type.__name__,))\n\n        self._purge_index(name)\n        with self._socket_for_writes(session) as sock_info:\n            self[name]._command(\n                sock_info,\n                \"dropDatabase\",\n                read_preference=ReadPreference.PRIMARY,\n                write_concern=self._write_concern_for(session),\n                parse_write_concern_error=True,\n                session=session)\n\n    def get_default_database(self, default=None, codec_options=None,\n            read_preference=None, write_concern=None, read_concern=None):\n        \"\"\"Get the database named in the MongoDB connection URI.\n\n        >>> uri = 'mongodb://host/my_database'\n        >>> client = MongoClient(uri)\n        >>> db = client.get_default_database()\n        >>> assert db.name == 'my_database'\n        >>> db = client.get_database()\n        >>> assert db.name == 'my_database'\n\n        Useful in scripts where you want to choose which database to use\n        based only on the URI in a configuration file.\n\n        :Parameters:\n          - `default` (optional): the database name to use if no database name\n            was provided in the URI.\n          - `codec_options` (optional): An instance of\n            :class:`~bson.codec_options.CodecOptions`. If ``None`` (the\n            default) the :attr:`codec_options` of this :class:`MongoClient` is\n            used.\n          - `read_preference` (optional): The read preference to use. If\n            ``None`` (the default) the :attr:`read_preference` of this\n            :class:`MongoClient` is used. See :mod:`~pymongo.read_preferences`\n            for options.\n          - `write_concern` (optional): An instance of\n            :class:`~pymongo.write_concern.WriteConcern`. If ``None`` (the\n            default) the :attr:`write_concern` of this :class:`MongoClient` is\n            used.\n          - `read_concern` (optional): An instance of\n            :class:`~pymongo.read_concern.ReadConcern`. If ``None`` (the\n            default) the :attr:`read_concern` of this :class:`MongoClient` is\n            used.\n\n        .. versionchanged:: 3.8\n           Undeprecated. Added the ``default``, ``codec_options``,\n           ``read_preference``, ``write_concern`` and ``read_concern``\n           parameters.\n\n        .. versionchanged:: 3.5\n           Deprecated, use :meth:`get_database` instead.\n        \"\"\"\n        if self.__default_database_name is None and default is None:\n            raise ConfigurationError(\n                'No default database name defined or provided.')\n\n        return database.Database(\n            self, self.__default_database_name or default, codec_options,\n            read_preference, write_concern, read_concern)\n\n    def get_database(self, name=None, codec_options=None, read_preference=None,\n                     write_concern=None, read_concern=None):\n        \"\"\"Get a :class:`~pymongo.database.Database` with the given name and\n        options.\n\n        Useful for creating a :class:`~pymongo.database.Database` with\n        different codec options, read preference, and/or write concern from\n        this :class:`MongoClient`.\n\n          >>> client.read_preference\n          Primary()\n          >>> db1 = client.test\n          >>> db1.read_preference\n          Primary()\n          >>> from pymongo import ReadPreference\n          >>> db2 = client.get_database(\n          ...     'test', read_preference=ReadPreference.SECONDARY)\n          >>> db2.read_preference\n          Secondary(tag_sets=None)\n\n        :Parameters:\n          - `name` (optional): The name of the database - a string. If ``None``\n            (the default) the database named in the MongoDB connection URI is\n            returned.\n          - `codec_options` (optional): An instance of\n            :class:`~bson.codec_options.CodecOptions`. If ``None`` (the\n            default) the :attr:`codec_options` of this :class:`MongoClient` is\n            used.\n          - `read_preference` (optional): The read preference to use. If\n            ``None`` (the default) the :attr:`read_preference` of this\n            :class:`MongoClient` is used. See :mod:`~pymongo.read_preferences`\n            for options.\n          - `write_concern` (optional): An instance of\n            :class:`~pymongo.write_concern.WriteConcern`. If ``None`` (the\n            default) the :attr:`write_concern` of this :class:`MongoClient` is\n            used.\n          - `read_concern` (optional): An instance of\n            :class:`~pymongo.read_concern.ReadConcern`. If ``None`` (the\n            default) the :attr:`read_concern` of this :class:`MongoClient` is\n            used.\n\n        .. versionchanged:: 3.5\n           The `name` parameter is now optional, defaulting to the database\n           named in the MongoDB connection URI.\n        \"\"\"\n        if name is None:\n            if self.__default_database_name is None:\n                raise ConfigurationError('No default database defined')\n            name = self.__default_database_name\n\n        return database.Database(\n            self, name, codec_options, read_preference,\n            write_concern, read_concern)\n\n    def _database_default_options(self, name):\n        \"\"\"Get a Database instance with the default settings.\"\"\"\n        return self.get_database(\n            name, codec_options=DEFAULT_CODEC_OPTIONS,\n            read_preference=ReadPreference.PRIMARY,\n            write_concern=DEFAULT_WRITE_CONCERN)\n\n    @property\n    def is_locked(self):\n        \"\"\"Is this server locked? While locked, all write operations\n        are blocked, although read operations may still be allowed.\n        Use :meth:`unlock` to unlock.\n        \"\"\"\n        ops = self._database_default_options('admin')._current_op()\n        return bool(ops.get('fsyncLock', 0))\n\n    def fsync(self, **kwargs):\n        \"\"\"Flush all pending writes to datafiles.\n\n        Optional parameters can be passed as keyword arguments:\n          - `lock`: If True lock the server to disallow writes.\n          - `async`: If True don't block while synchronizing.\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. note:: Starting with Python 3.7 `async` is a reserved keyword.\n          The async option to the fsync command can be passed using a\n          dictionary instead::\n\n            options = {'async': True}\n            client.fsync(**options)\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n\n        .. warning:: `async` and `lock` can not be used together.\n\n        .. warning:: MongoDB does not support the `async` option\n                     on Windows and will raise an exception on that\n                     platform.\n        \"\"\"\n        self.admin.command(\"fsync\",\n                           read_preference=ReadPreference.PRIMARY, **kwargs)\n\n    def unlock(self, session=None):\n        \"\"\"Unlock a previously locked server.\n\n        :Parameters:\n          - `session` (optional): a\n            :class:`~pymongo.client_session.ClientSession`.\n\n        .. versionchanged:: 3.6\n           Added ``session`` parameter.\n        \"\"\"\n        cmd = SON([(\"fsyncUnlock\", 1)])\n        with self._socket_for_writes(session) as sock_info:\n            if sock_info.max_wire_version >= 4:\n                try:\n                    with self._tmp_session(session) as s:\n                        sock_info.command(\n                            \"admin\", cmd, session=s, client=self)\n                except OperationFailure as exc:\n                    # Ignore \"DB not locked\" to replicate old behavior\n                    if exc.code != 125:\n                        raise\n            else:\n                message._first_batch(sock_info, \"admin\", \"$cmd.sys.unlock\",\n                                     {}, -1, True, self.codec_options,\n                                     ReadPreference.PRIMARY, cmd,\n                                     self._event_listeners)\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        self.close()\n\n    def __iter__(self):\n        return self\n\n    def __next__(self):\n        raise TypeError(\"'MongoClient' object is not iterable\")\n\n    next = __next__\n\n\nclass _MongoClientErrorHandler(object):\n    \"\"\"Error handler for MongoClient.\"\"\"\n    __slots__ = ('_client', '_server_address', '_session', '_max_wire_version')\n\n    def __init__(self, client, server_address, session):\n        self._client = client\n        self._server_address = server_address\n        self._session = session\n        self._max_wire_version = None\n\n    def contribute_socket(self, sock_info):\n        \"\"\"Provide socket information to the error handler.\"\"\"\n        # Currently, we only extract the max_wire_version information.\n        self._max_wire_version = sock_info.max_wire_version\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_val, exc_tb):\n        if exc_type is None:\n            return\n\n        if issubclass(exc_type, PyMongoError):\n            if self._session and exc_val.has_error_label(\n                    \"TransientTransactionError\"):\n                self._session._unpin_mongos()\n\n        if issubclass(exc_type, NetworkTimeout):\n            # The socket has been closed. Don't reset the server.\n            # Server Discovery And Monitoring Spec: \"When an application\n            # operation fails because of any network error besides a socket\n            # timeout....\"\n            if self._session:\n                self._session._server_session.mark_dirty()\n        elif issubclass(exc_type, NotMasterError):\n            # As per the SDAM spec if:\n            #   - the server sees a \"not master\" error, and\n            #   - the server is not shutting down, and\n            #   - the server version is >= 4.2, then\n            # we keep the existing connection pool, but mark the server type\n            # as Unknown and request an immediate check of the server.\n            # Otherwise, we clear the connection pool, mark the server as\n            # Unknown and request an immediate check of the server.\n            err_code = exc_val.details.get('code', -1)\n            is_shutting_down = err_code in helpers._SHUTDOWN_CODES\n            if (is_shutting_down or (self._max_wire_version is None) or\n                    (self._max_wire_version <= 7)):\n                # Clear the pool, mark server Unknown and request check.\n                self._client._reset_server_and_request_check(\n                    self._server_address)\n            else:\n                self._client._topology.mark_server_unknown_and_request_check(\n                    self._server_address)\n        elif issubclass(exc_type, ConnectionFailure):\n            # \"Client MUST replace the server's description with type Unknown\n            # ... MUST NOT request an immediate check of the server.\"\n            self._client._reset_server(self._server_address)\n            if self._session:\n                self._session._server_session.mark_dirty()\n        elif issubclass(exc_type, OperationFailure):\n            # Do not request an immediate check since the server is likely\n            # shutting down.\n            if exc_val.code in helpers._RETRYABLE_ERROR_CODES:\n                self._client._reset_server(self._server_address)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/mongo_replica_set_client.py",
    "content": "# Copyright 2011-2015 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Deprecated. See :doc:`/examples/high_availability`.\"\"\"\n\nimport warnings\n\nfrom pymongo import mongo_client\n\n\nclass MongoReplicaSetClient(mongo_client.MongoClient):\n    \"\"\"Deprecated alias for :class:`~pymongo.mongo_client.MongoClient`.\n\n    :class:`~pymongo.mongo_replica_set_client.MongoReplicaSetClient`\n    will be removed in a future version of PyMongo.\n\n    .. versionchanged:: 3.0\n       :class:`~pymongo.mongo_client.MongoClient` is now the one and only\n       client class for a standalone server, mongos, or replica set.\n       It includes the functionality that had been split into\n       :class:`~pymongo.mongo_replica_set_client.MongoReplicaSetClient`: it\n       can connect to a replica set, discover all its members, and monitor\n       the set for stepdowns, elections, and reconfigs.\n\n       The ``refresh`` method is removed from\n       :class:`~pymongo.mongo_replica_set_client.MongoReplicaSetClient`,\n       as are the ``seeds`` and ``hosts`` properties.\n    \"\"\"\n    def __init__(self, *args, **kwargs):\n        warnings.warn('MongoReplicaSetClient is deprecated, use MongoClient'\n                      ' to connect to a replica set',\n                      DeprecationWarning, stacklevel=2)\n\n        super(MongoReplicaSetClient, self).__init__(*args, **kwargs)\n\n    def __repr__(self):\n        return \"MongoReplicaSetClient(%s)\" % (self._repr_helper(),)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/monitor.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Class to monitor a MongoDB server on a background thread.\"\"\"\n\nimport weakref\n\nfrom pymongo import common, periodic_executor\nfrom pymongo.errors import OperationFailure\nfrom pymongo.monotonic import time as _time\nfrom pymongo.read_preferences import MovingAverage\nfrom pymongo.server_description import ServerDescription\nfrom pymongo.server_type import SERVER_TYPE\nfrom pymongo.srv_resolver import _SrvResolver\n\n\nclass MonitorBase(object):\n    def __init__(self, *args, **kwargs):\n        \"\"\"Override this method to create an executor.\"\"\"\n        raise NotImplementedError\n\n    def open(self):\n        \"\"\"Start monitoring, or restart after a fork.\n\n        Multiple calls have no effect.\n        \"\"\"\n        self._executor.open()\n\n    def close(self):\n        \"\"\"Close and stop monitoring.\n\n        open() restarts the monitor after closing.\n        \"\"\"\n        self._executor.close()\n\n    def join(self, timeout=None):\n        \"\"\"Wait for the monitor to stop.\"\"\"\n        self._executor.join(timeout)\n\n    def request_check(self):\n        \"\"\"If the monitor is sleeping, wake it soon.\"\"\"\n        self._executor.wake()\n\n\nclass Monitor(MonitorBase):\n    def __init__(\n            self,\n            server_description,\n            topology,\n            pool,\n            topology_settings):\n        \"\"\"Class to monitor a MongoDB server on a background thread.\n\n        Pass an initial ServerDescription, a Topology, a Pool, and\n        TopologySettings.\n\n        The Topology is weakly referenced. The Pool must be exclusive to this\n        Monitor.\n        \"\"\"\n        self._server_description = server_description\n        self._pool = pool\n        self._settings = topology_settings\n        self._avg_round_trip_time = MovingAverage()\n        self._listeners = self._settings._pool_options.event_listeners\n        pub = self._listeners is not None\n        self._publish = pub and self._listeners.enabled_for_server_heartbeat\n\n        # We strongly reference the executor and it weakly references us via\n        # this closure. When the monitor is freed, stop the executor soon.\n        def target():\n            monitor = self_ref()\n            if monitor is None:\n                return False  # Stop the executor.\n            Monitor._run(monitor)\n            return True\n\n        executor = periodic_executor.PeriodicExecutor(\n            interval=self._settings.heartbeat_frequency,\n            min_interval=common.MIN_HEARTBEAT_INTERVAL,\n            target=target,\n            name=\"pymongo_server_monitor_thread\")\n\n        self._executor = executor\n\n        # Avoid cycles. When self or topology is freed, stop executor soon.\n        self_ref = weakref.ref(self, executor.close)\n        self._topology = weakref.proxy(topology, executor.close)\n\n    def close(self):\n        super(Monitor, self).close()\n\n        # Increment the pool_id and maybe close the socket. If the executor\n        # thread has the socket checked out, it will be closed when checked in.\n        self._pool.reset()\n\n    def _run(self):\n        try:\n            self._server_description = self._check_with_retry()\n            self._topology.on_change(self._server_description)\n        except ReferenceError:\n            # Topology was garbage-collected.\n            self.close()\n\n    def _check_with_retry(self):\n        \"\"\"Call ismaster once or twice. Reset server's pool on error.\n\n        Returns a ServerDescription.\n        \"\"\"\n        # According to the spec, if an ismaster call fails we reset the\n        # server's pool. If a server was once connected, change its type\n        # to Unknown only after retrying once.\n        address = self._server_description.address\n        retry = True\n        if self._server_description.server_type == SERVER_TYPE.Unknown:\n            retry = False\n\n        start = _time()\n        try:\n            return self._check_once()\n        except ReferenceError:\n            raise\n        except Exception as error:\n            error_time = _time() - start\n            if self._publish:\n                self._listeners.publish_server_heartbeat_failed(\n                    address, error_time, error)\n            self._topology.reset_pool(address)\n            default = ServerDescription(address, error=error)\n            if not retry:\n                self._avg_round_trip_time.reset()\n                # Server type defaults to Unknown.\n                return default\n\n            # Try a second and final time. If it fails return original error.\n            # Always send metadata: this is a new connection.\n            start = _time()\n            try:\n                return self._check_once()\n            except ReferenceError:\n                raise\n            except Exception as error:\n                error_time = _time() - start\n                if self._publish:\n                    self._listeners.publish_server_heartbeat_failed(\n                        address, error_time, error)\n                self._avg_round_trip_time.reset()\n                return default\n\n    def _check_once(self):\n        \"\"\"A single attempt to call ismaster.\n\n        Returns a ServerDescription, or raises an exception.\n        \"\"\"\n        address = self._server_description.address\n        if self._publish:\n            self._listeners.publish_server_heartbeat_started(address)\n        with self._pool.get_socket({}) as sock_info:\n            response, round_trip_time = self._check_with_socket(sock_info)\n            self._avg_round_trip_time.add_sample(round_trip_time)\n            sd = ServerDescription(\n                address=address,\n                ismaster=response,\n                round_trip_time=self._avg_round_trip_time.get())\n            if self._publish:\n                self._listeners.publish_server_heartbeat_succeeded(\n                    address, round_trip_time, response)\n\n            return sd\n\n    def _check_with_socket(self, sock_info):\n        \"\"\"Return (IsMaster, round_trip_time).\n\n        Can raise ConnectionFailure or OperationFailure.\n        \"\"\"\n        start = _time()\n        try:\n            return (sock_info.ismaster(self._pool.opts.metadata,\n                                       self._topology.max_cluster_time()),\n                    _time() - start)\n        except OperationFailure as exc:\n            # Update max cluster time even when isMaster fails.\n            self._topology.receive_cluster_time(\n                exc.details.get('$clusterTime'))\n            raise\n\n\nclass SrvMonitor(MonitorBase):\n    def __init__(self, topology, topology_settings):\n        \"\"\"Class to poll SRV records on a background thread.\n\n        Pass a Topology and a TopologySettings.\n\n        The Topology is weakly referenced.\n        \"\"\"\n        self._settings = topology_settings\n        self._seedlist = self._settings._seeds\n        self._fqdn = self._settings.fqdn\n\n        # We strongly reference the executor and it weakly references us via\n        # this closure. When the monitor is freed, stop the executor soon.\n        def target():\n            monitor = self_ref()\n            if monitor is None:\n                return False  # Stop the executor.\n            SrvMonitor._run(monitor)\n            return True\n\n        executor = periodic_executor.PeriodicExecutor(\n            interval=common.MIN_SRV_RESCAN_INTERVAL,\n            min_interval=self._settings.heartbeat_frequency,\n            target=target,\n            name=\"pymongo_srv_polling_thread\")\n\n        self._executor = executor\n\n        # Avoid cycles. When self or topology is freed, stop executor soon.\n        self_ref = weakref.ref(self, executor.close)\n        self._topology = weakref.proxy(topology, executor.close)\n\n    def _run(self):\n        seedlist = self._get_seedlist()\n        if seedlist:\n            self._seedlist = seedlist\n            try:\n                self._topology.on_srv_update(self._seedlist)\n            except ReferenceError:\n                # Topology was garbage-collected.\n                self.close()\n\n    def _get_seedlist(self):\n        \"\"\"Poll SRV records for a seedlist.\n\n        Returns a list of ServerDescriptions.\n        \"\"\"\n        try:\n            seedlist, ttl = _SrvResolver(self._fqdn).get_hosts_and_min_ttl()\n            if len(seedlist) == 0:\n                # As per the spec: this should be treated as a failure.\n                raise Exception\n        except Exception:\n            # As per the spec, upon encountering an error:\n            # - An error must not be raised\n            # - SRV records must be rescanned every heartbeatFrequencyMS\n            # - Topology must be left unchanged\n            self.request_check()\n            return None\n        else:\n            self._executor.update_interval(\n                max(ttl, common.MIN_SRV_RESCAN_INTERVAL))\n            return seedlist\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/monitoring.py",
    "content": "# Copyright 2015-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Tools to monitor driver events.\n\n.. versionadded:: 3.1\n\nUse :func:`register` to register global listeners for specific events.\nListeners must inherit from one of the abstract classes below and implement\nthe correct functions for that class.\n\nFor example, a simple command logger might be implemented like this::\n\n    import logging\n\n    from pymongo import monitoring\n\n    class CommandLogger(monitoring.CommandListener):\n\n        def started(self, event):\n            logging.info(\"Command {0.command_name} with request id \"\n                         \"{0.request_id} started on server \"\n                         \"{0.connection_id}\".format(event))\n\n        def succeeded(self, event):\n            logging.info(\"Command {0.command_name} with request id \"\n                         \"{0.request_id} on server {0.connection_id} \"\n                         \"succeeded in {0.duration_micros} \"\n                         \"microseconds\".format(event))\n\n        def failed(self, event):\n            logging.info(\"Command {0.command_name} with request id \"\n                         \"{0.request_id} on server {0.connection_id} \"\n                         \"failed in {0.duration_micros} \"\n                         \"microseconds\".format(event))\n\n    monitoring.register(CommandLogger())\n\nServer discovery and monitoring events are also available. For example::\n\n    class ServerLogger(monitoring.ServerListener):\n\n        def opened(self, event):\n            logging.info(\"Server {0.server_address} added to topology \"\n                         \"{0.topology_id}\".format(event))\n\n        def description_changed(self, event):\n            previous_server_type = event.previous_description.server_type\n            new_server_type = event.new_description.server_type\n            if new_server_type != previous_server_type:\n                # server_type_name was added in PyMongo 3.4\n                logging.info(\n                    \"Server {0.server_address} changed type from \"\n                    \"{0.previous_description.server_type_name} to \"\n                    \"{0.new_description.server_type_name}\".format(event))\n\n        def closed(self, event):\n            logging.warning(\"Server {0.server_address} removed from topology \"\n                            \"{0.topology_id}\".format(event))\n\n\n    class HeartbeatLogger(monitoring.ServerHeartbeatListener):\n\n        def started(self, event):\n            logging.info(\"Heartbeat sent to server \"\n                         \"{0.connection_id}\".format(event))\n\n        def succeeded(self, event):\n            # The reply.document attribute was added in PyMongo 3.4.\n            logging.info(\"Heartbeat to server {0.connection_id} \"\n                         \"succeeded with reply \"\n                         \"{0.reply.document}\".format(event))\n\n        def failed(self, event):\n            logging.warning(\"Heartbeat to server {0.connection_id} \"\n                            \"failed with error {0.reply}\".format(event))\n\n    class TopologyLogger(monitoring.TopologyListener):\n\n        def opened(self, event):\n            logging.info(\"Topology with id {0.topology_id} \"\n                         \"opened\".format(event))\n\n        def description_changed(self, event):\n            logging.info(\"Topology description updated for \"\n                         \"topology id {0.topology_id}\".format(event))\n            previous_topology_type = event.previous_description.topology_type\n            new_topology_type = event.new_description.topology_type\n            if new_topology_type != previous_topology_type:\n                # topology_type_name was added in PyMongo 3.4\n                logging.info(\n                    \"Topology {0.topology_id} changed type from \"\n                    \"{0.previous_description.topology_type_name} to \"\n                    \"{0.new_description.topology_type_name}\".format(event))\n            # The has_writable_server and has_readable_server methods\n            # were added in PyMongo 3.4.\n            if not event.new_description.has_writable_server():\n                logging.warning(\"No writable servers available.\")\n            if not event.new_description.has_readable_server():\n                logging.warning(\"No readable servers available.\")\n\n        def closed(self, event):\n            logging.info(\"Topology with id {0.topology_id} \"\n                         \"closed\".format(event))\n\nConnection monitoring and pooling events are also available. For example::\n\n    class ConnectionPoolLogger(ConnectionPoolListener):\n\n        def pool_created(self, event):\n            logging.info(\"[pool {0.address}] pool created\".format(event))\n\n        def pool_cleared(self, event):\n            logging.info(\"[pool {0.address}] pool cleared\".format(event))\n\n        def pool_closed(self, event):\n            logging.info(\"[pool {0.address}] pool closed\".format(event))\n\n        def connection_created(self, event):\n            logging.info(\"[pool {0.address}][conn #{0.connection_id}] \"\n                         \"connection created\".format(event))\n\n        def connection_ready(self, event):\n            logging.info(\"[pool {0.address}][conn #{0.connection_id}] \"\n                         \"connection setup succeeded\".format(event))\n\n        def connection_closed(self, event):\n            logging.info(\"[pool {0.address}][conn #{0.connection_id}] \"\n                         \"connection closed, reason: \"\n                         \"{0.reason}\".format(event))\n\n        def connection_check_out_started(self, event):\n            logging.info(\"[pool {0.address}] connection check out \"\n                         \"started\".format(event))\n\n        def connection_check_out_failed(self, event):\n            logging.info(\"[pool {0.address}] connection check out \"\n                         \"failed, reason: {0.reason}\".format(event))\n\n        def connection_checked_out(self, event):\n            logging.info(\"[pool {0.address}][conn #{0.connection_id}] \"\n                         \"connection checked out of pool\".format(event))\n\n        def connection_checked_in(self, event):\n            logging.info(\"[pool {0.address}][conn #{0.connection_id}] \"\n                         \"connection checked into pool\".format(event))\n\n\nEvent listeners can also be registered per instance of\n:class:`~pymongo.mongo_client.MongoClient`::\n\n    client = MongoClient(event_listeners=[CommandLogger()])\n\nNote that previously registered global listeners are automatically included\nwhen configuring per client event listeners. Registering a new global listener\nwill not add that listener to existing client instances.\n\n.. note:: Events are delivered **synchronously**. Application threads block\n  waiting for event handlers (e.g. :meth:`~CommandListener.started`) to\n  return. Care must be taken to ensure that your event handlers are efficient\n  enough to not adversely affect overall application performance.\n\n.. warning:: The command documents published through this API are *not* copies.\n  If you intend to modify them in any way you must copy them in your event\n  handler first.\n\"\"\"\n\nfrom collections import namedtuple\n\nfrom bson.py3compat import abc\nfrom pymongo.helpers import _handle_exception\n\n_Listeners = namedtuple('Listeners',\n                        ('command_listeners', 'server_listeners',\n                         'server_heartbeat_listeners', 'topology_listeners',\n                         'cmap_listeners'))\n\n_LISTENERS = _Listeners([], [], [], [], [])\n\n\nclass _EventListener(object):\n    \"\"\"Abstract base class for all event listeners.\"\"\"\n\n\nclass CommandListener(_EventListener):\n    \"\"\"Abstract base class for command listeners.\n\n    Handles `CommandStartedEvent`, `CommandSucceededEvent`,\n    and `CommandFailedEvent`.\n    \"\"\"\n\n    def started(self, event):\n        \"\"\"Abstract method to handle a `CommandStartedEvent`.\n\n        :Parameters:\n          - `event`: An instance of :class:`CommandStartedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def succeeded(self, event):\n        \"\"\"Abstract method to handle a `CommandSucceededEvent`.\n\n        :Parameters:\n          - `event`: An instance of :class:`CommandSucceededEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def failed(self, event):\n        \"\"\"Abstract method to handle a `CommandFailedEvent`.\n\n        :Parameters:\n          - `event`: An instance of :class:`CommandFailedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n\nclass ConnectionPoolListener(_EventListener):\n    \"\"\"Abstract base class for connection pool listeners.\n\n    Handles all of the connection pool events defined in the Connection\n    Monitoring and Pooling Specification:\n    :class:`PoolCreatedEvent`, :class:`PoolClearedEvent`,\n    :class:`PoolClosedEvent`, :class:`ConnectionCreatedEvent`,\n    :class:`ConnectionReadyEvent`, :class:`ConnectionClosedEvent`,\n    :class:`ConnectionCheckOutStartedEvent`,\n    :class:`ConnectionCheckOutFailedEvent`,\n    :class:`ConnectionCheckedOutEvent`,\n    and :class:`ConnectionCheckedInEvent`.\n\n    .. versionadded:: 3.9\n    \"\"\"\n\n    def pool_created(self, event):\n        \"\"\"Abstract method to handle a :class:`PoolCreatedEvent`.\n\n        Emitted when a Connection Pool is created.\n\n        :Parameters:\n          - `event`: An instance of :class:`PoolCreatedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def pool_cleared(self, event):\n        \"\"\"Abstract method to handle a `PoolClearedEvent`.\n\n        Emitted when a Connection Pool is cleared.\n\n        :Parameters:\n          - `event`: An instance of :class:`PoolClearedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def pool_closed(self, event):\n        \"\"\"Abstract method to handle a `PoolClosedEvent`.\n\n        Emitted when a Connection Pool is closed.\n\n        :Parameters:\n          - `event`: An instance of :class:`PoolClosedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def connection_created(self, event):\n        \"\"\"Abstract method to handle a :class:`ConnectionCreatedEvent`.\n\n        Emitted when a Connection Pool creates a Connection object.\n\n        :Parameters:\n          - `event`: An instance of :class:`ConnectionCreatedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def connection_ready(self, event):\n        \"\"\"Abstract method to handle a :class:`ConnectionReadyEvent`.\n\n        Emitted when a Connection has finished its setup, and is now ready to\n        use.\n\n        :Parameters:\n          - `event`: An instance of :class:`ConnectionReadyEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def connection_closed(self, event):\n        \"\"\"Abstract method to handle a :class:`ConnectionClosedEvent`.\n\n        Emitted when a Connection Pool closes a Connection.\n\n        :Parameters:\n          - `event`: An instance of :class:`ConnectionClosedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def connection_check_out_started(self, event):\n        \"\"\"Abstract method to handle a :class:`ConnectionCheckOutStartedEvent`.\n\n        Emitted when the driver starts attempting to check out a connection.\n\n        :Parameters:\n          - `event`: An instance of :class:`ConnectionCheckOutStartedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def connection_check_out_failed(self, event):\n        \"\"\"Abstract method to handle a :class:`ConnectionCheckOutFailedEvent`.\n\n        Emitted when the driver's attempt to check out a connection fails.\n\n        :Parameters:\n          - `event`: An instance of :class:`ConnectionCheckOutFailedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def connection_checked_out(self, event):\n        \"\"\"Abstract method to handle a :class:`ConnectionCheckedOutEvent`.\n\n        Emitted when the driver successfully checks out a Connection.\n\n        :Parameters:\n          - `event`: An instance of :class:`ConnectionCheckedOutEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def connection_checked_in(self, event):\n        \"\"\"Abstract method to handle a :class:`ConnectionCheckedInEvent`.\n\n        Emitted when the driver checks in a Connection back to the Connection\n        Pool.\n\n        :Parameters:\n          - `event`: An instance of :class:`ConnectionCheckedInEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n\nclass ServerHeartbeatListener(_EventListener):\n    \"\"\"Abstract base class for server heartbeat listeners.\n\n    Handles `ServerHeartbeatStartedEvent`, `ServerHeartbeatSucceededEvent`,\n    and `ServerHeartbeatFailedEvent`.\n\n    .. versionadded:: 3.3\n    \"\"\"\n\n    def started(self, event):\n        \"\"\"Abstract method to handle a `ServerHeartbeatStartedEvent`.\n\n        :Parameters:\n          - `event`: An instance of :class:`ServerHeartbeatStartedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def succeeded(self, event):\n        \"\"\"Abstract method to handle a `ServerHeartbeatSucceededEvent`.\n\n        :Parameters:\n          - `event`: An instance of :class:`ServerHeartbeatSucceededEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def failed(self, event):\n        \"\"\"Abstract method to handle a `ServerHeartbeatFailedEvent`.\n\n        :Parameters:\n          - `event`: An instance of :class:`ServerHeartbeatFailedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n\nclass TopologyListener(_EventListener):\n    \"\"\"Abstract base class for topology monitoring listeners.\n    Handles `TopologyOpenedEvent`, `TopologyDescriptionChangedEvent`, and\n    `TopologyClosedEvent`.\n\n    .. versionadded:: 3.3\n    \"\"\"\n\n    def opened(self, event):\n        \"\"\"Abstract method to handle a `TopologyOpenedEvent`.\n\n        :Parameters:\n          - `event`: An instance of :class:`TopologyOpenedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def description_changed(self, event):\n        \"\"\"Abstract method to handle a `TopologyDescriptionChangedEvent`.\n\n        :Parameters:\n          - `event`: An instance of :class:`TopologyDescriptionChangedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def closed(self, event):\n        \"\"\"Abstract method to handle a `TopologyClosedEvent`.\n\n        :Parameters:\n          - `event`: An instance of :class:`TopologyClosedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n\nclass ServerListener(_EventListener):\n    \"\"\"Abstract base class for server listeners.\n    Handles `ServerOpeningEvent`, `ServerDescriptionChangedEvent`, and\n    `ServerClosedEvent`.\n\n    .. versionadded:: 3.3\n    \"\"\"\n\n    def opened(self, event):\n        \"\"\"Abstract method to handle a `ServerOpeningEvent`.\n\n        :Parameters:\n          - `event`: An instance of :class:`ServerOpeningEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def description_changed(self, event):\n        \"\"\"Abstract method to handle a `ServerDescriptionChangedEvent`.\n\n        :Parameters:\n          - `event`: An instance of :class:`ServerDescriptionChangedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n    def closed(self, event):\n        \"\"\"Abstract method to handle a `ServerClosedEvent`.\n\n        :Parameters:\n          - `event`: An instance of :class:`ServerClosedEvent`.\n        \"\"\"\n        raise NotImplementedError\n\n\ndef _to_micros(dur):\n    \"\"\"Convert duration 'dur' to microseconds.\"\"\"\n    return int(dur.total_seconds() * 10e5)\n\n\ndef _validate_event_listeners(option, listeners):\n    \"\"\"Validate event listeners\"\"\"\n    if not isinstance(listeners, abc.Sequence):\n        raise TypeError(\"%s must be a list or tuple\" % (option,))\n    for listener in listeners:\n        if not isinstance(listener, _EventListener):\n            raise TypeError(\"Listeners for %s must be either a \"\n                            \"CommandListener, ServerHeartbeatListener, \"\n                            \"ServerListener, TopologyListener, or \"\n                            \"ConnectionPoolListener.\" % (option,))\n    return listeners\n\n\ndef register(listener):\n    \"\"\"Register a global event listener.\n\n    :Parameters:\n      - `listener`: A subclasses of :class:`CommandListener`,\n        :class:`ServerHeartbeatListener`, :class:`ServerListener`,\n        :class:`TopologyListener`, or :class:`ConnectionPoolListener`.\n    \"\"\"\n    if not isinstance(listener, _EventListener):\n        raise TypeError(\"Listeners for %s must be either a \"\n                        \"CommandListener, ServerHeartbeatListener, \"\n                        \"ServerListener, TopologyListener, or \"\n                        \"ConnectionPoolListener.\" % (listener,))\n    if isinstance(listener, CommandListener):\n        _LISTENERS.command_listeners.append(listener)\n    if isinstance(listener, ServerHeartbeatListener):\n        _LISTENERS.server_heartbeat_listeners.append(listener)\n    if isinstance(listener, ServerListener):\n        _LISTENERS.server_listeners.append(listener)\n    if isinstance(listener, TopologyListener):\n        _LISTENERS.topology_listeners.append(listener)\n    if isinstance(listener, ConnectionPoolListener):\n        _LISTENERS.cmap_listeners.append(listener)\n\n# Note - to avoid bugs from forgetting which if these is all lowercase and\n# which are camelCase, and at the same time avoid having to add a test for\n# every command, use all lowercase here and test against command_name.lower().\n_SENSITIVE_COMMANDS = set(\n    [\"authenticate\", \"saslstart\", \"saslcontinue\", \"getnonce\", \"createuser\",\n     \"updateuser\", \"copydbgetnonce\", \"copydbsaslstart\", \"copydb\"])\n\n\nclass _CommandEvent(object):\n    \"\"\"Base class for command events.\"\"\"\n\n    __slots__ = (\"__cmd_name\", \"__rqst_id\", \"__conn_id\", \"__op_id\")\n\n    def __init__(self, command_name, request_id, connection_id, operation_id):\n        self.__cmd_name = command_name\n        self.__rqst_id = request_id\n        self.__conn_id = connection_id\n        self.__op_id = operation_id\n\n    @property\n    def command_name(self):\n        \"\"\"The command name.\"\"\"\n        return self.__cmd_name\n\n    @property\n    def request_id(self):\n        \"\"\"The request id for this operation.\"\"\"\n        return self.__rqst_id\n\n    @property\n    def connection_id(self):\n        \"\"\"The address (host, port) of the server this command was sent to.\"\"\"\n        return self.__conn_id\n\n    @property\n    def operation_id(self):\n        \"\"\"An id for this series of events or None.\"\"\"\n        return self.__op_id\n\n\nclass CommandStartedEvent(_CommandEvent):\n    \"\"\"Event published when a command starts.\n\n    :Parameters:\n      - `command`: The command document.\n      - `database_name`: The name of the database this command was run against.\n      - `request_id`: The request id for this operation.\n      - `connection_id`: The address (host, port) of the server this command\n        was sent to.\n      - `operation_id`: An optional identifier for a series of related events.\n    \"\"\"\n    __slots__ = (\"__cmd\", \"__db\")\n\n    def __init__(self, command, database_name, *args):\n        if not command:\n            raise ValueError(\"%r is not a valid command\" % (command,))\n        # Command name must be first key.\n        command_name = next(iter(command))\n        super(CommandStartedEvent, self).__init__(command_name, *args)\n        if command_name.lower() in _SENSITIVE_COMMANDS:\n            self.__cmd = {}\n        else:\n            self.__cmd = command\n        self.__db = database_name\n\n    @property\n    def command(self):\n        \"\"\"The command document.\"\"\"\n        return self.__cmd\n\n    @property\n    def database_name(self):\n        \"\"\"The name of the database this command was run against.\"\"\"\n        return self.__db\n\n\nclass CommandSucceededEvent(_CommandEvent):\n    \"\"\"Event published when a command succeeds.\n\n    :Parameters:\n      - `duration`: The command duration as a datetime.timedelta.\n      - `reply`: The server reply document.\n      - `command_name`: The command name.\n      - `request_id`: The request id for this operation.\n      - `connection_id`: The address (host, port) of the server this command\n        was sent to.\n      - `operation_id`: An optional identifier for a series of related events.\n    \"\"\"\n    __slots__ = (\"__duration_micros\", \"__reply\")\n\n    def __init__(self, duration, reply, command_name,\n                 request_id, connection_id, operation_id):\n        super(CommandSucceededEvent, self).__init__(\n            command_name, request_id, connection_id, operation_id)\n        self.__duration_micros = _to_micros(duration)\n        if command_name.lower() in _SENSITIVE_COMMANDS:\n            self.__reply = {}\n        else:\n            self.__reply = reply\n\n    @property\n    def duration_micros(self):\n        \"\"\"The duration of this operation in microseconds.\"\"\"\n        return self.__duration_micros\n\n    @property\n    def reply(self):\n        \"\"\"The server failure document for this operation.\"\"\"\n        return self.__reply\n\n\nclass CommandFailedEvent(_CommandEvent):\n    \"\"\"Event published when a command fails.\n\n    :Parameters:\n      - `duration`: The command duration as a datetime.timedelta.\n      - `failure`: The server reply document.\n      - `command_name`: The command name.\n      - `request_id`: The request id for this operation.\n      - `connection_id`: The address (host, port) of the server this command\n        was sent to.\n      - `operation_id`: An optional identifier for a series of related events.\n    \"\"\"\n    __slots__ = (\"__duration_micros\", \"__failure\")\n\n    def __init__(self, duration, failure, *args):\n        super(CommandFailedEvent, self).__init__(*args)\n        self.__duration_micros = _to_micros(duration)\n        self.__failure = failure\n\n    @property\n    def duration_micros(self):\n        \"\"\"The duration of this operation in microseconds.\"\"\"\n        return self.__duration_micros\n\n    @property\n    def failure(self):\n        \"\"\"The server failure document for this operation.\"\"\"\n        return self.__failure\n\n\nclass _PoolEvent(object):\n    \"\"\"Base class for pool events.\"\"\"\n    __slots__ = (\"__address\",)\n\n    def __init__(self, address):\n        self.__address = address\n\n    @property\n    def address(self):\n        \"\"\"The address (host, port) pair of the server the pool is attempting\n        to connect to.\n        \"\"\"\n        return self.__address\n\n    def __repr__(self):\n        return '%s(%r)' % (self.__class__.__name__, self.__address)\n\n\nclass PoolCreatedEvent(_PoolEvent):\n    \"\"\"Published when a Connection Pool is created.\n\n    :Parameters:\n     - `address`: The address (host, port) pair of the server this Pool is\n       attempting to connect to.\n\n    .. versionadded:: 3.9\n    \"\"\"\n    __slots__ = (\"__options\",)\n\n    def __init__(self, address, options):\n        super(PoolCreatedEvent, self).__init__(address)\n        self.__options = options\n\n    @property\n    def options(self):\n        \"\"\"Any non-default pool options that were set on this Connection Pool.\n        \"\"\"\n        return self.__options\n\n    def __repr__(self):\n        return '%s(%r, %r)' % (\n            self.__class__.__name__, self.address, self.__options)\n\n\nclass PoolClearedEvent(_PoolEvent):\n    \"\"\"Published when a Connection Pool is cleared.\n\n    :Parameters:\n     - `address`: The address (host, port) pair of the server this Pool is\n       attempting to connect to.\n\n    .. versionadded:: 3.9\n    \"\"\"\n    __slots__ = ()\n\n\nclass PoolClosedEvent(_PoolEvent):\n    \"\"\"Published when a Connection Pool is closed.\n\n    :Parameters:\n     - `address`: The address (host, port) pair of the server this Pool is\n       attempting to connect to.\n\n    .. versionadded:: 3.9\n    \"\"\"\n    __slots__ = ()\n\n\nclass ConnectionClosedReason(object):\n    \"\"\"An enum that defines values for `reason` on a\n    :class:`ConnectionClosedEvent`.\n\n    .. versionadded:: 3.9\n    \"\"\"\n\n    STALE = 'stale'\n    \"\"\"The pool was cleared, making the connection no longer valid.\"\"\"\n\n    IDLE = 'idle'\n    \"\"\"The connection became stale by being idle for too long (maxIdleTimeMS).\n    \"\"\"\n\n    ERROR = 'error'\n    \"\"\"The connection experienced an error, making it no longer valid.\"\"\"\n\n    POOL_CLOSED = 'poolClosed'\n    \"\"\"The pool was closed, making the connection no longer valid.\"\"\"\n\n\nclass ConnectionCheckOutFailedReason(object):\n    \"\"\"An enum that defines values for `reason` on a\n    :class:`ConnectionCheckOutFailedEvent`.\n\n    .. versionadded:: 3.9\n    \"\"\"\n\n    TIMEOUT = 'timeout'\n    \"\"\"The connection check out attempt exceeded the specified timeout.\"\"\"\n\n    POOL_CLOSED = 'poolClosed'\n    \"\"\"The pool was previously closed, and cannot provide new connections.\"\"\"\n\n    CONN_ERROR = 'connectionError'\n    \"\"\"The connection check out attempt experienced an error while setting up\n    a new connection.\n    \"\"\"\n\n\nclass _ConnectionEvent(object):\n    \"\"\"Private base class for some connection events.\"\"\"\n    __slots__ = (\"__address\", \"__connection_id\")\n\n    def __init__(self, address, connection_id):\n        self.__address = address\n        self.__connection_id = connection_id\n\n    @property\n    def address(self):\n        \"\"\"The address (host, port) pair of the server this connection is\n        attempting to connect to.\n        \"\"\"\n        return self.__address\n\n    @property\n    def connection_id(self):\n        \"\"\"The ID of the Connection.\"\"\"\n        return self.__connection_id\n\n    def __repr__(self):\n        return '%s(%r, %r)' % (\n            self.__class__.__name__, self.__address, self.__connection_id)\n\n\nclass ConnectionCreatedEvent(_ConnectionEvent):\n    \"\"\"Published when a Connection Pool creates a Connection object.\n\n    NOTE: This connection is not ready for use until the\n    :class:`ConnectionReadyEvent` is published.\n\n    :Parameters:\n     - `address`: The address (host, port) pair of the server this\n       Connection is attempting to connect to.\n     - `connection_id`: The integer ID of the Connection in this Pool.\n\n    .. versionadded:: 3.9\n    \"\"\"\n    __slots__ = ()\n\n\nclass ConnectionReadyEvent(_ConnectionEvent):\n    \"\"\"Published when a Connection has finished its setup, and is ready to use.\n\n    :Parameters:\n     - `address`: The address (host, port) pair of the server this\n       Connection is attempting to connect to.\n     - `connection_id`: The integer ID of the Connection in this Pool.\n\n    .. versionadded:: 3.9\n    \"\"\"\n    __slots__ = ()\n\n\nclass ConnectionClosedEvent(_ConnectionEvent):\n    \"\"\"Published when a Connection is closed.\n\n    :Parameters:\n     - `address`: The address (host, port) pair of the server this\n       Connection is attempting to connect to.\n     - `connection_id`: The integer ID of the Connection in this Pool.\n     - `reason`: A reason explaining why this connection was closed.\n\n    .. versionadded:: 3.9\n    \"\"\"\n    __slots__ = (\"__reason\",)\n\n    def __init__(self, address, connection_id, reason):\n        super(ConnectionClosedEvent, self).__init__(address, connection_id)\n        self.__reason = reason\n\n    @property\n    def reason(self):\n        \"\"\"A reason explaining why this connection was closed.\n\n        The reason must be one of the strings from the\n        :class:`ConnectionClosedReason` enum.\n        \"\"\"\n        return self.__reason\n\n    def __repr__(self):\n        return '%s(%r, %r, %r)' % (\n            self.__class__.__name__, self.address, self.connection_id,\n            self.__reason)\n\n\nclass ConnectionCheckOutStartedEvent(object):\n    \"\"\"Published when the driver starts attempting to check out a connection.\n\n    :Parameters:\n     - `address`: The address (host, port) pair of the server this\n       Connection is attempting to connect to.\n\n    .. versionadded:: 3.9\n    \"\"\"\n    __slots__ = (\"__address\",)\n\n    def __init__(self, address):\n        self.__address = address\n\n    @property\n    def address(self):\n        \"\"\"The address (host, port) pair of the server this connection is\n        attempting to connect to.\n        \"\"\"\n        return self.__address\n\n    def __repr__(self):\n        return '%s(%r)' % (self.__class__.__name__, self.__address)\n\n\nclass ConnectionCheckOutFailedEvent(object):\n    \"\"\"Published when the driver's attempt to check out a connection fails.\n\n    :Parameters:\n     - `address`: The address (host, port) pair of the server this\n       Connection is attempting to connect to.\n     - `reason`: A reason explaining why connection check out failed.\n\n    .. versionadded:: 3.9\n    \"\"\"\n    __slots__ = (\"__address\", \"__reason\")\n\n    def __init__(self, address, reason):\n        self.__address = address\n        self.__reason = reason\n\n    @property\n    def address(self):\n        \"\"\"The address (host, port) pair of the server this connection is\n        attempting to connect to.\n        \"\"\"\n        return self.__address\n\n    @property\n    def reason(self):\n        \"\"\"A reason explaining why connection check out failed.\n\n        The reason must be one of the strings from the\n        :class:`ConnectionCheckOutFailedReason` enum.\n        \"\"\"\n        return self.__reason\n\n    def __repr__(self):\n        return '%s(%r, %r)' % (\n            self.__class__.__name__, self.__address, self.__reason)\n\n\nclass ConnectionCheckedOutEvent(_ConnectionEvent):\n    \"\"\"Published when the driver successfully checks out a Connection.\n\n    :Parameters:\n     - `address`: The address (host, port) pair of the server this\n       Connection is attempting to connect to.\n     - `connection_id`: The integer ID of the Connection in this Pool.\n\n    .. versionadded:: 3.9\n    \"\"\"\n    __slots__ = ()\n\n\nclass ConnectionCheckedInEvent(_ConnectionEvent):\n    \"\"\"Published when the driver checks in a Connection into the Pool.\n\n    :Parameters:\n     - `address`: The address (host, port) pair of the server this\n       Connection is attempting to connect to.\n     - `connection_id`: The integer ID of the Connection in this Pool.\n\n    .. versionadded:: 3.9\n    \"\"\"\n    __slots__ = ()\n\n\nclass _ServerEvent(object):\n    \"\"\"Base class for server events.\"\"\"\n\n    __slots__ = (\"__server_address\", \"__topology_id\")\n\n    def __init__(self, server_address, topology_id):\n        self.__server_address = server_address\n        self.__topology_id = topology_id\n\n    @property\n    def server_address(self):\n        \"\"\"The address (host, port) pair of the server\"\"\"\n        return self.__server_address\n\n    @property\n    def topology_id(self):\n        \"\"\"A unique identifier for the topology this server is a part of.\"\"\"\n        return self.__topology_id\n\n\nclass ServerDescriptionChangedEvent(_ServerEvent):\n    \"\"\"Published when server description changes.\n\n    .. versionadded:: 3.3\n    \"\"\"\n\n    __slots__ = ('__previous_description', '__new_description')\n\n    def __init__(self, previous_description, new_description, *args):\n        super(ServerDescriptionChangedEvent, self).__init__(*args)\n        self.__previous_description = previous_description\n        self.__new_description = new_description\n\n    @property\n    def previous_description(self):\n        \"\"\"The previous\n        :class:`~pymongo.server_description.ServerDescription`.\"\"\"\n        return self.__previous_description\n\n    @property\n    def new_description(self):\n        \"\"\"The new\n        :class:`~pymongo.server_description.ServerDescription`.\"\"\"\n        return self.__new_description\n\n\nclass ServerOpeningEvent(_ServerEvent):\n    \"\"\"Published when server is initialized.\n\n    .. versionadded:: 3.3\n    \"\"\"\n\n    __slots__ = ()\n\n\nclass ServerClosedEvent(_ServerEvent):\n    \"\"\"Published when server is closed.\n\n    .. versionadded:: 3.3\n    \"\"\"\n\n    __slots__ = ()\n\n\nclass TopologyEvent(object):\n    \"\"\"Base class for topology description events.\"\"\"\n\n    __slots__ = ('__topology_id')\n\n    def __init__(self, topology_id):\n        self.__topology_id = topology_id\n\n    @property\n    def topology_id(self):\n        \"\"\"A unique identifier for the topology this server is a part of.\"\"\"\n        return self.__topology_id\n\n\nclass TopologyDescriptionChangedEvent(TopologyEvent):\n    \"\"\"Published when the topology description changes.\n\n    .. versionadded:: 3.3\n    \"\"\"\n\n    __slots__ = ('__previous_description', '__new_description')\n\n    def __init__(self, previous_description,  new_description, *args):\n        super(TopologyDescriptionChangedEvent, self).__init__(*args)\n        self.__previous_description = previous_description\n        self.__new_description = new_description\n\n    @property\n    def previous_description(self):\n        \"\"\"The previous\n        :class:`~pymongo.topology_description.TopologyDescription`.\"\"\"\n        return self.__previous_description\n\n    @property\n    def new_description(self):\n        \"\"\"The new\n        :class:`~pymongo.topology_description.TopologyDescription`.\"\"\"\n        return self.__new_description\n\n\nclass TopologyOpenedEvent(TopologyEvent):\n    \"\"\"Published when the topology is initialized.\n\n    .. versionadded:: 3.3\n    \"\"\"\n\n    __slots__ = ()\n\n\nclass TopologyClosedEvent(TopologyEvent):\n    \"\"\"Published when the topology is closed.\n\n    .. versionadded:: 3.3\n    \"\"\"\n\n    __slots__ = ()\n\n\nclass _ServerHeartbeatEvent(object):\n    \"\"\"Base class for server heartbeat events.\"\"\"\n\n    __slots__ = ('__connection_id')\n\n    def __init__(self, connection_id):\n        self.__connection_id = connection_id\n\n    @property\n    def connection_id(self):\n        \"\"\"The address (host, port) of the server this heartbeat was sent\n        to.\"\"\"\n        return self.__connection_id\n\n\nclass ServerHeartbeatStartedEvent(_ServerHeartbeatEvent):\n    \"\"\"Published when a heartbeat is started.\n\n    .. versionadded:: 3.3\n    \"\"\"\n\n    __slots__ = ()\n\n\nclass ServerHeartbeatSucceededEvent(_ServerHeartbeatEvent):\n    \"\"\"Fired when the server heartbeat succeeds.\n\n    .. versionadded:: 3.3\n    \"\"\"\n\n    __slots__ = ('__duration', '__reply')\n\n    def __init__(self, duration, reply, *args):\n        super(ServerHeartbeatSucceededEvent, self).__init__(*args)\n        self.__duration = duration\n        self.__reply = reply\n\n    @property\n    def duration(self):\n        \"\"\"The duration of this heartbeat in microseconds.\"\"\"\n        return self.__duration\n\n    @property\n    def reply(self):\n        \"\"\"An instance of :class:`~pymongo.ismaster.IsMaster`.\"\"\"\n        return self.__reply\n\n\nclass ServerHeartbeatFailedEvent(_ServerHeartbeatEvent):\n    \"\"\"Fired when the server heartbeat fails, either with an \"ok: 0\"\n    or a socket exception.\n\n    .. versionadded:: 3.3\n    \"\"\"\n\n    __slots__ = ('__duration', '__reply')\n\n    def __init__(self, duration, reply, *args):\n        super(ServerHeartbeatFailedEvent, self).__init__(*args)\n        self.__duration = duration\n        self.__reply = reply\n\n    @property\n    def duration(self):\n        \"\"\"The duration of this heartbeat in microseconds.\"\"\"\n        return self.__duration\n\n    @property\n    def reply(self):\n        \"\"\"A subclass of :exc:`Exception`.\"\"\"\n        return self.__reply\n\n\nclass _EventListeners(object):\n    \"\"\"Configure event listeners for a client instance.\n\n    Any event listeners registered globally are included by default.\n\n    :Parameters:\n      - `listeners`: A list of event listeners.\n    \"\"\"\n    def __init__(self, listeners):\n        self.__command_listeners = _LISTENERS.command_listeners[:]\n        self.__server_listeners = _LISTENERS.server_listeners[:]\n        lst = _LISTENERS.server_heartbeat_listeners\n        self.__server_heartbeat_listeners = lst[:]\n        self.__topology_listeners = _LISTENERS.topology_listeners[:]\n        self.__cmap_listeners = _LISTENERS.cmap_listeners[:]\n        if listeners is not None:\n            for lst in listeners:\n                if isinstance(lst, CommandListener):\n                    self.__command_listeners.append(lst)\n                if isinstance(lst, ServerListener):\n                    self.__server_listeners.append(lst)\n                if isinstance(lst, ServerHeartbeatListener):\n                    self.__server_heartbeat_listeners.append(lst)\n                if isinstance(lst, TopologyListener):\n                    self.__topology_listeners.append(lst)\n                if isinstance(lst, ConnectionPoolListener):\n                    self.__cmap_listeners.append(lst)\n        self.__enabled_for_commands = bool(self.__command_listeners)\n        self.__enabled_for_server = bool(self.__server_listeners)\n        self.__enabled_for_server_heartbeat = bool(\n            self.__server_heartbeat_listeners)\n        self.__enabled_for_topology = bool(self.__topology_listeners)\n        self.__enabled_for_cmap = bool(self.__cmap_listeners)\n\n    @property\n    def enabled_for_commands(self):\n        \"\"\"Are any CommandListener instances registered?\"\"\"\n        return self.__enabled_for_commands\n\n    @property\n    def enabled_for_server(self):\n        \"\"\"Are any ServerListener instances registered?\"\"\"\n        return self.__enabled_for_server\n\n    @property\n    def enabled_for_server_heartbeat(self):\n        \"\"\"Are any ServerHeartbeatListener instances registered?\"\"\"\n        return self.__enabled_for_server_heartbeat\n\n    @property\n    def enabled_for_topology(self):\n        \"\"\"Are any TopologyListener instances registered?\"\"\"\n        return self.__enabled_for_topology\n\n    @property\n    def enabled_for_cmap(self):\n        \"\"\"Are any ConnectionPoolListener instances registered?\"\"\"\n        return self.__enabled_for_cmap\n\n    def event_listeners(self):\n        \"\"\"List of registered event listeners.\"\"\"\n        return (self.__command_listeners[:],\n                self.__server_heartbeat_listeners[:],\n                self.__server_listeners[:],\n                self.__topology_listeners[:])\n\n    def publish_command_start(self, command, database_name,\n                              request_id, connection_id, op_id=None):\n        \"\"\"Publish a CommandStartedEvent to all command listeners.\n\n        :Parameters:\n          - `command`: The command document.\n          - `database_name`: The name of the database this command was run\n            against.\n          - `request_id`: The request id for this operation.\n          - `connection_id`: The address (host, port) of the server this\n            command was sent to.\n          - `op_id`: The (optional) operation id for this operation.\n        \"\"\"\n        if op_id is None:\n            op_id = request_id\n        event = CommandStartedEvent(\n            command, database_name, request_id, connection_id, op_id)\n        for subscriber in self.__command_listeners:\n            try:\n                subscriber.started(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_command_success(self, duration, reply, command_name,\n                                request_id, connection_id, op_id=None):\n        \"\"\"Publish a CommandSucceededEvent to all command listeners.\n\n        :Parameters:\n          - `duration`: The command duration as a datetime.timedelta.\n          - `reply`: The server reply document.\n          - `command_name`: The command name.\n          - `request_id`: The request id for this operation.\n          - `connection_id`: The address (host, port) of the server this\n            command was sent to.\n          - `op_id`: The (optional) operation id for this operation.\n        \"\"\"\n        if op_id is None:\n            op_id = request_id\n        event = CommandSucceededEvent(\n            duration, reply, command_name, request_id, connection_id, op_id)\n        for subscriber in self.__command_listeners:\n            try:\n                subscriber.succeeded(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_command_failure(self, duration, failure, command_name,\n                                request_id, connection_id, op_id=None):\n        \"\"\"Publish a CommandFailedEvent to all command listeners.\n\n        :Parameters:\n          - `duration`: The command duration as a datetime.timedelta.\n          - `failure`: The server reply document or failure description\n            document.\n          - `command_name`: The command name.\n          - `request_id`: The request id for this operation.\n          - `connection_id`: The address (host, port) of the server this\n            command was sent to.\n          - `op_id`: The (optional) operation id for this operation.\n        \"\"\"\n        if op_id is None:\n            op_id = request_id\n        event = CommandFailedEvent(\n            duration, failure, command_name, request_id, connection_id, op_id)\n        for subscriber in self.__command_listeners:\n            try:\n                subscriber.failed(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_server_heartbeat_started(self, connection_id):\n        \"\"\"Publish a ServerHeartbeatStartedEvent to all server heartbeat\n        listeners.\n\n        :Parameters:\n         - `connection_id`: The address (host, port) pair of the connection.\n        \"\"\"\n        event = ServerHeartbeatStartedEvent(connection_id)\n        for subscriber in self.__server_heartbeat_listeners:\n            try:\n                subscriber.started(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_server_heartbeat_succeeded(self, connection_id, duration,\n                                           reply):\n        \"\"\"Publish a ServerHeartbeatSucceededEvent to all server heartbeat\n        listeners.\n\n        :Parameters:\n         - `connection_id`: The address (host, port) pair of the connection.\n         - `duration`: The execution time of the event in the highest possible\n            resolution for the platform.\n         - `reply`: The command reply.\n         \"\"\"\n        event = ServerHeartbeatSucceededEvent(duration, reply, connection_id)\n        for subscriber in self.__server_heartbeat_listeners:\n            try:\n                subscriber.succeeded(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_server_heartbeat_failed(self, connection_id, duration, reply):\n        \"\"\"Publish a ServerHeartbeatFailedEvent to all server heartbeat\n        listeners.\n\n        :Parameters:\n         - `connection_id`: The address (host, port) pair of the connection.\n         - `duration`: The execution time of the event in the highest possible\n            resolution for the platform.\n         - `reply`: The command reply.\n         \"\"\"\n        event = ServerHeartbeatFailedEvent(duration, reply, connection_id)\n        for subscriber in self.__server_heartbeat_listeners:\n            try:\n                subscriber.failed(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_server_opened(self, server_address, topology_id):\n        \"\"\"Publish a ServerOpeningEvent to all server listeners.\n\n        :Parameters:\n         - `server_address`: The address (host, port) pair of the server.\n         - `topology_id`: A unique identifier for the topology this server\n           is a part of.\n        \"\"\"\n        event = ServerOpeningEvent(server_address, topology_id)\n        for subscriber in self.__server_listeners:\n            try:\n                subscriber.opened(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_server_closed(self, server_address, topology_id):\n        \"\"\"Publish a ServerClosedEvent to all server listeners.\n\n        :Parameters:\n         - `server_address`: The address (host, port) pair of the server.\n         - `topology_id`: A unique identifier for the topology this server\n           is a part of.\n        \"\"\"\n        event = ServerClosedEvent(server_address, topology_id)\n        for subscriber in self.__server_listeners:\n            try:\n                subscriber.closed(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_server_description_changed(self, previous_description,\n                                           new_description, server_address,\n                                           topology_id):\n        \"\"\"Publish a ServerDescriptionChangedEvent to all server listeners.\n\n        :Parameters:\n         - `previous_description`: The previous server description.\n         - `server_address`: The address (host, port) pair of the server.\n         - `new_description`: The new server description.\n         - `topology_id`: A unique identifier for the topology this server\n           is a part of.\n        \"\"\"\n        event = ServerDescriptionChangedEvent(previous_description,\n                                              new_description, server_address,\n                                              topology_id)\n        for subscriber in self.__server_listeners:\n            try:\n                subscriber.description_changed(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_topology_opened(self, topology_id):\n        \"\"\"Publish a TopologyOpenedEvent to all topology listeners.\n\n        :Parameters:\n         - `topology_id`: A unique identifier for the topology this server\n           is a part of.\n        \"\"\"\n        event = TopologyOpenedEvent(topology_id)\n        for subscriber in self.__topology_listeners:\n            try:\n                subscriber.opened(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_topology_closed(self, topology_id):\n        \"\"\"Publish a TopologyClosedEvent to all topology listeners.\n\n        :Parameters:\n         - `topology_id`: A unique identifier for the topology this server\n           is a part of.\n        \"\"\"\n        event = TopologyClosedEvent(topology_id)\n        for subscriber in self.__topology_listeners:\n            try:\n                subscriber.closed(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_topology_description_changed(self, previous_description,\n                                             new_description, topology_id):\n        \"\"\"Publish a TopologyDescriptionChangedEvent to all topology listeners.\n\n        :Parameters:\n         - `previous_description`: The previous topology description.\n         - `new_description`: The new topology description.\n         - `topology_id`: A unique identifier for the topology this server\n           is a part of.\n        \"\"\"\n        event = TopologyDescriptionChangedEvent(previous_description,\n                                                new_description, topology_id)\n        for subscriber in self.__topology_listeners:\n            try:\n                subscriber.description_changed(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_pool_created(self, address, options):\n        \"\"\"Publish a :class:`PoolCreatedEvent` to all pool listeners.\n        \"\"\"\n        event = PoolCreatedEvent(address, options)\n        for subscriber in self.__cmap_listeners:\n            try:\n                subscriber.pool_created(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_pool_cleared(self, address):\n        \"\"\"Publish a :class:`PoolClearedEvent` to all pool listeners.\n        \"\"\"\n        event = PoolClearedEvent(address)\n        for subscriber in self.__cmap_listeners:\n            try:\n                subscriber.pool_cleared(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_pool_closed(self, address):\n        \"\"\"Publish a :class:`PoolClosedEvent` to all pool listeners.\n        \"\"\"\n        event = PoolClosedEvent(address)\n        for subscriber in self.__cmap_listeners:\n            try:\n                subscriber.pool_closed(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_connection_created(self, address, connection_id):\n        \"\"\"Publish a :class:`ConnectionCreatedEvent` to all connection\n        listeners.\n        \"\"\"\n        event = ConnectionCreatedEvent(address, connection_id)\n        for subscriber in self.__cmap_listeners:\n            try:\n                subscriber.connection_created(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_connection_ready(self, address, connection_id):\n        \"\"\"Publish a :class:`ConnectionReadyEvent` to all connection listeners.\n        \"\"\"\n        event = ConnectionReadyEvent(address, connection_id)\n        for subscriber in self.__cmap_listeners:\n            try:\n                subscriber.connection_ready(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_connection_closed(self, address, connection_id, reason):\n        \"\"\"Publish a :class:`ConnectionClosedEvent` to all connection\n        listeners.\n        \"\"\"\n        event = ConnectionClosedEvent(address, connection_id, reason)\n        for subscriber in self.__cmap_listeners:\n            try:\n                subscriber.connection_closed(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_connection_check_out_started(self, address):\n        \"\"\"Publish a :class:`ConnectionCheckOutStartedEvent` to all connection\n        listeners.\n        \"\"\"\n        event = ConnectionCheckOutStartedEvent(address)\n        for subscriber in self.__cmap_listeners:\n            try:\n                subscriber.connection_check_out_started(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_connection_check_out_failed(self, address, reason):\n        \"\"\"Publish a :class:`ConnectionCheckOutFailedEvent` to all connection\n        listeners.\n        \"\"\"\n        event = ConnectionCheckOutFailedEvent(address, reason)\n        for subscriber in self.__cmap_listeners:\n            try:\n                subscriber.connection_check_out_started(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_connection_checked_out(self, address, connection_id):\n        \"\"\"Publish a :class:`ConnectionCheckedOutEvent` to all connection\n        listeners.\n        \"\"\"\n        event = ConnectionCheckedOutEvent(address, connection_id)\n        for subscriber in self.__cmap_listeners:\n            try:\n                subscriber.connection_checked_out(event)\n            except Exception:\n                _handle_exception()\n\n    def publish_connection_checked_in(self, address, connection_id):\n        \"\"\"Publish a :class:`ConnectionCheckedInEvent` to all connection\n        listeners.\n        \"\"\"\n        event = ConnectionCheckedInEvent(address, connection_id)\n        for subscriber in self.__cmap_listeners:\n            try:\n                subscriber.connection_checked_in(event)\n            except Exception:\n                _handle_exception()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/monotonic.py",
    "content": "# Copyright 2014-2015 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Time. Monotonic if possible.\n\"\"\"\n\nfrom __future__ import absolute_import\n\n__all__ = ['time']\n\ntry:\n    # Patches standard time module.\n    # From https://pypi.python.org/pypi/Monotime.\n    import monotime\nexcept ImportError:\n    pass\n\ntry:\n    # From https://pypi.python.org/pypi/monotonic.\n    from monotonic import monotonic as time\nexcept ImportError:\n    try:\n        # Monotime or Python 3.\n        from time import monotonic as time\n    except ImportError:\n        # Not monotonic.\n        from time import time\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/network.py",
    "content": "# Copyright 2015-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Internal network layer helper methods.\"\"\"\n\nimport datetime\nimport errno\nimport select\nimport struct\nimport threading\n\n_HAS_POLL = True\n_EVENT_MASK = 0\ntry:\n    from select import poll\n    _EVENT_MASK = (\n        select.POLLIN | select.POLLPRI | select.POLLERR | select.POLLHUP)\nexcept ImportError:\n    _HAS_POLL = False\n\ntry:\n    from select import error as _SELECT_ERROR\nexcept ImportError:\n    _SELECT_ERROR = OSError\n\nfrom bson import _decode_all_selective\nfrom bson.py3compat import PY3\n\nfrom pymongo import helpers, message\nfrom pymongo.common import MAX_MESSAGE_SIZE\nfrom pymongo.compression_support import decompress, _NO_COMPRESSION\nfrom pymongo.errors import (AutoReconnect,\n                            NotMasterError,\n                            OperationFailure,\n                            ProtocolError)\nfrom pymongo.message import _UNPACK_REPLY\n\n\n_UNPACK_HEADER = struct.Struct(\"<iiii\").unpack\n\n\ndef command(sock, dbname, spec, slave_ok, is_mongos,\n            read_preference, codec_options, session, client, check=True,\n            allowable_errors=None, address=None,\n            check_keys=False, listeners=None, max_bson_size=None,\n            read_concern=None,\n            parse_write_concern_error=False,\n            collation=None,\n            compression_ctx=None,\n            use_op_msg=False,\n            unacknowledged=False,\n            user_fields=None):\n    \"\"\"Execute a command over the socket, or raise socket.error.\n\n    :Parameters:\n      - `sock`: a raw socket instance\n      - `dbname`: name of the database on which to run the command\n      - `spec`: a command document as an ordered dict type, eg SON.\n      - `slave_ok`: whether to set the SlaveOkay wire protocol bit\n      - `is_mongos`: are we connected to a mongos?\n      - `read_preference`: a read preference\n      - `codec_options`: a CodecOptions instance\n      - `session`: optional ClientSession instance.\n      - `client`: optional MongoClient instance for updating $clusterTime.\n      - `check`: raise OperationFailure if there are errors\n      - `allowable_errors`: errors to ignore if `check` is True\n      - `address`: the (host, port) of `sock`\n      - `check_keys`: if True, check `spec` for invalid keys\n      - `listeners`: An instance of :class:`~pymongo.monitoring.EventListeners`\n      - `max_bson_size`: The maximum encoded bson size for this server\n      - `read_concern`: The read concern for this command.\n      - `parse_write_concern_error`: Whether to parse the ``writeConcernError``\n        field in the command response.\n      - `collation`: The collation for this command.\n      - `compression_ctx`: optional compression Context.\n      - `use_op_msg`: True if we should use OP_MSG.\n      - `unacknowledged`: True if this is an unacknowledged command.\n      - `user_fields` (optional): Response fields that should be decoded\n        using the TypeDecoders from codec_options, passed to\n        bson._decode_all_selective.\n    \"\"\"\n    name = next(iter(spec))\n    ns = dbname + '.$cmd'\n    flags = 4 if slave_ok else 0\n\n    # Publish the original command document, perhaps with lsid and $clusterTime.\n    orig = spec\n    if is_mongos and not use_op_msg:\n        spec = message._maybe_add_read_preference(spec, read_preference)\n    if read_concern and not (session and session._in_transaction):\n        if read_concern.level:\n            spec['readConcern'] = read_concern.document\n        if (session and session.options.causal_consistency\n                and session.operation_time is not None):\n            spec.setdefault(\n                'readConcern', {})['afterClusterTime'] = session.operation_time\n    if collation is not None:\n        spec['collation'] = collation\n\n    publish = listeners is not None and listeners.enabled_for_commands\n    if publish:\n        start = datetime.datetime.now()\n\n    if compression_ctx and name.lower() in _NO_COMPRESSION:\n        compression_ctx = None\n\n    if (client and client._encrypter and\n            not client._encrypter._bypass_auto_encryption):\n        spec = orig = client._encrypter.encrypt(\n            dbname, spec, check_keys, codec_options)\n        # We already checked the keys, no need to do it again.\n        check_keys = False\n\n    if use_op_msg:\n        flags = 2 if unacknowledged else 0\n        request_id, msg, size, max_doc_size = message._op_msg(\n            flags, spec, dbname, read_preference, slave_ok, check_keys,\n            codec_options, ctx=compression_ctx)\n        # If this is an unacknowledged write then make sure the encoded doc(s)\n        # are small enough, otherwise rely on the server to return an error.\n        if (unacknowledged and max_bson_size is not None and\n                max_doc_size > max_bson_size):\n            message._raise_document_too_large(name, size, max_bson_size)\n    else:\n        request_id, msg, size = message.query(\n            flags, ns, 0, -1, spec, None, codec_options, check_keys,\n            compression_ctx)\n\n    if (max_bson_size is not None\n            and size > max_bson_size + message._COMMAND_OVERHEAD):\n        message._raise_document_too_large(\n            name, size, max_bson_size + message._COMMAND_OVERHEAD)\n\n    if publish:\n        encoding_duration = datetime.datetime.now() - start\n        listeners.publish_command_start(orig, dbname, request_id, address)\n        start = datetime.datetime.now()\n\n    try:\n        sock.sendall(msg)\n        if use_op_msg and unacknowledged:\n            # Unacknowledged, fake a successful command response.\n            reply = None\n            response_doc = {\"ok\": 1}\n        else:\n            reply = receive_message(sock, request_id)\n            unpacked_docs = reply.unpack_response(\n                codec_options=codec_options, user_fields=user_fields)\n\n            response_doc = unpacked_docs[0]\n            if client:\n                client._process_response(response_doc, session)\n            if check:\n                helpers._check_command_response(\n                    response_doc, None, allowable_errors,\n                    parse_write_concern_error=parse_write_concern_error)\n    except Exception as exc:\n        if publish:\n            duration = (datetime.datetime.now() - start) + encoding_duration\n            if isinstance(exc, (NotMasterError, OperationFailure)):\n                failure = exc.details\n            else:\n                failure = message._convert_exception(exc)\n            listeners.publish_command_failure(\n                duration, failure, name, request_id, address)\n        raise\n    if publish:\n        duration = (datetime.datetime.now() - start) + encoding_duration\n        listeners.publish_command_success(\n            duration, response_doc, name, request_id, address)\n\n    if client and client._encrypter and reply:\n        decrypted = client._encrypter.decrypt(reply.raw_command_response())\n        response_doc = _decode_all_selective(decrypted, codec_options,\n                                             user_fields)[0]\n\n    return response_doc\n\n_UNPACK_COMPRESSION_HEADER = struct.Struct(\"<iiB\").unpack\n\ndef receive_message(sock, request_id, max_message_size=MAX_MESSAGE_SIZE):\n    \"\"\"Receive a raw BSON message or raise socket.error.\"\"\"\n    # Ignore the response's request id.\n    length, _, response_to, op_code = _UNPACK_HEADER(\n        _receive_data_on_socket(sock, 16))\n    # No request_id for exhaust cursor \"getMore\".\n    if request_id is not None:\n        if request_id != response_to:\n            raise ProtocolError(\"Got response id %r but expected \"\n                                \"%r\" % (response_to, request_id))\n    if length <= 16:\n        raise ProtocolError(\"Message length (%r) not longer than standard \"\n                            \"message header size (16)\" % (length,))\n    if length > max_message_size:\n        raise ProtocolError(\"Message length (%r) is larger than server max \"\n                            \"message size (%r)\" % (length, max_message_size))\n    if op_code == 2012:\n        op_code, _, compressor_id = _UNPACK_COMPRESSION_HEADER(\n            _receive_data_on_socket(sock, 9))\n        data = decompress(\n            _receive_data_on_socket(sock, length - 25), compressor_id)\n    else:\n        data = _receive_data_on_socket(sock, length - 16)\n\n    try:\n        unpack_reply = _UNPACK_REPLY[op_code]\n    except KeyError:\n        raise ProtocolError(\"Got opcode %r but expected \"\n                            \"%r\" % (op_code, _UNPACK_REPLY.keys()))\n    return unpack_reply(data)\n\n\n# memoryview was introduced in Python 2.7 but we only use it on Python 3\n# because before 2.7.4 the struct module did not support memoryview:\n# https://bugs.python.org/issue10212.\n# In Jython, using slice assignment on a memoryview results in a\n# NullPointerException.\nif not PY3:\n    def _receive_data_on_socket(sock, length):\n        buf = bytearray(length)\n        i = 0\n        while length:\n            try:\n                chunk = sock.recv(length)\n            except (IOError, OSError) as exc:\n                if _errno_from_exception(exc) == errno.EINTR:\n                    continue\n                raise\n            if chunk == b\"\":\n                raise AutoReconnect(\"connection closed\")\n\n            buf[i:i + len(chunk)] = chunk\n            i += len(chunk)\n            length -= len(chunk)\n\n        return bytes(buf)\nelse:\n    def _receive_data_on_socket(sock, length):\n        buf = bytearray(length)\n        mv = memoryview(buf)\n        bytes_read = 0\n        while bytes_read < length:\n            try:\n                chunk_length = sock.recv_into(mv[bytes_read:])\n            except (IOError, OSError) as exc:\n                if _errno_from_exception(exc) == errno.EINTR:\n                    continue\n                raise\n            if chunk_length == 0:\n                raise AutoReconnect(\"connection closed\")\n\n            bytes_read += chunk_length\n\n        return mv\n\n\ndef _errno_from_exception(exc):\n    if hasattr(exc, 'errno'):\n        return exc.errno\n    elif exc.args:\n        return exc.args[0]\n    else:\n        return None\n\n\nclass SocketChecker(object):\n\n    def __init__(self):\n        if _HAS_POLL:\n            self._lock = threading.Lock()\n            self._poller = poll()\n        else:\n            self._lock = None\n            self._poller = None\n\n    def socket_closed(self, sock):\n        \"\"\"Return True if we know socket has been closed, False otherwise.\n        \"\"\"\n        while True:\n            try:\n                if self._poller:\n                    with self._lock:\n                        self._poller.register(sock, _EVENT_MASK)\n                        try:\n                            rd = self._poller.poll(0)\n                        finally:\n                            self._poller.unregister(sock)\n                else:\n                    rd, _, _ = select.select([sock], [], [], 0)\n            except (RuntimeError, KeyError):\n                # RuntimeError is raised during a concurrent poll. KeyError\n                # is raised by unregister if the socket is not in the poller.\n                # These errors should not be possible since we protect the\n                # poller with a mutex.\n                raise\n            except ValueError:\n                # ValueError is raised by register/unregister/select if the\n                # socket file descriptor is negative or outside the range for\n                # select (> 1023).\n                return True\n            except (_SELECT_ERROR, IOError) as exc:\n                if _errno_from_exception(exc) in (errno.EINTR, errno.EAGAIN):\n                    continue\n                return True\n            except Exception:\n                # Any other exceptions should be attributed to a closed\n                # or invalid socket.\n                return True\n            return len(rd) > 0\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/operations.py",
    "content": "# Copyright 2015-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Operation class definitions.\"\"\"\n\nfrom pymongo.common import validate_boolean, validate_is_mapping, validate_list\nfrom pymongo.collation import validate_collation_or_none\nfrom pymongo.helpers import _gen_index_name, _index_document, _index_list\n\n\nclass InsertOne(object):\n    \"\"\"Represents an insert_one operation.\"\"\"\n\n    __slots__ = (\"_doc\",)\n\n    def __init__(self, document):\n        \"\"\"Create an InsertOne instance.\n\n        For use with :meth:`~pymongo.collection.Collection.bulk_write`.\n\n        :Parameters:\n          - `document`: The document to insert. If the document is missing an\n            _id field one will be added.\n        \"\"\"\n        self._doc = document\n\n    def _add_to_bulk(self, bulkobj):\n        \"\"\"Add this operation to the _Bulk instance `bulkobj`.\"\"\"\n        bulkobj.add_insert(self._doc)\n\n    def __repr__(self):\n        return \"InsertOne(%r)\" % (self._doc,)\n\n    def __eq__(self, other):\n        if type(other) == type(self):\n            return other._doc == self._doc\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n\n\nclass DeleteOne(object):\n    \"\"\"Represents a delete_one operation.\"\"\"\n\n    __slots__ = (\"_filter\", \"_collation\")\n\n    def __init__(self, filter, collation=None):\n        \"\"\"Create a DeleteOne instance.\n\n        For use with :meth:`~pymongo.collection.Collection.bulk_write`.\n\n        :Parameters:\n          - `filter`: A query that matches the document to delete.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only\n            supported on MongoDB 3.4 and above.\n\n        .. versionchanged:: 3.5\n           Added the `collation` option.\n        \"\"\"\n        if filter is not None:\n            validate_is_mapping(\"filter\", filter)\n        self._filter = filter\n        self._collation = collation\n\n    def _add_to_bulk(self, bulkobj):\n        \"\"\"Add this operation to the _Bulk instance `bulkobj`.\"\"\"\n        bulkobj.add_delete(self._filter, 1, collation=self._collation)\n\n    def __repr__(self):\n        return \"DeleteOne(%r, %r)\" % (self._filter, self._collation)\n\n    def __eq__(self, other):\n        if type(other) == type(self):\n            return ((other._filter, other._collation) ==\n                    (self._filter, self._collation))\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n\n\nclass DeleteMany(object):\n    \"\"\"Represents a delete_many operation.\"\"\"\n\n    __slots__ = (\"_filter\", \"_collation\")\n\n    def __init__(self, filter, collation=None):\n        \"\"\"Create a DeleteMany instance.\n\n        For use with :meth:`~pymongo.collection.Collection.bulk_write`.\n\n        :Parameters:\n          - `filter`: A query that matches the documents to delete.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only\n            supported on MongoDB 3.4 and above.\n\n        .. versionchanged:: 3.5\n           Added the `collation` option.\n        \"\"\"\n        if filter is not None:\n            validate_is_mapping(\"filter\", filter)\n        self._filter = filter\n        self._collation = collation\n\n    def _add_to_bulk(self, bulkobj):\n        \"\"\"Add this operation to the _Bulk instance `bulkobj`.\"\"\"\n        bulkobj.add_delete(self._filter, 0, collation=self._collation)\n\n    def __repr__(self):\n        return \"DeleteMany(%r, %r)\" % (self._filter, self._collation)\n\n    def __eq__(self, other):\n        if type(other) == type(self):\n            return ((other._filter, other._collation) ==\n                    (self._filter, self._collation))\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n\n\nclass ReplaceOne(object):\n    \"\"\"Represents a replace_one operation.\"\"\"\n\n    __slots__ = (\"_filter\", \"_doc\", \"_upsert\", \"_collation\")\n\n    def __init__(self, filter, replacement, upsert=False, collation=None):\n        \"\"\"Create a ReplaceOne instance.\n\n        For use with :meth:`~pymongo.collection.Collection.bulk_write`.\n\n        :Parameters:\n          - `filter`: A query that matches the document to replace.\n          - `replacement`: The new document.\n          - `upsert` (optional): If ``True``, perform an insert if no documents\n            match the filter.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only\n            supported on MongoDB 3.4 and above.\n\n        .. versionchanged:: 3.5\n           Added the `collation` option.\n        \"\"\"\n        if filter is not None:\n            validate_is_mapping(\"filter\", filter)\n        if upsert is not None:\n            validate_boolean(\"upsert\", upsert)\n        self._filter = filter\n        self._doc = replacement\n        self._upsert = upsert\n        self._collation = collation\n\n    def _add_to_bulk(self, bulkobj):\n        \"\"\"Add this operation to the _Bulk instance `bulkobj`.\"\"\"\n        bulkobj.add_replace(self._filter, self._doc, self._upsert,\n                            collation=self._collation)\n\n    def __eq__(self, other):\n        if type(other) == type(self):\n            return (\n                (other._filter, other._doc, other._upsert, other._collation) ==\n                (self._filter, self._doc, self._upsert, self._collation))\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __repr__(self):\n        return \"%s(%r, %r, %r, %r)\" % (\n            self.__class__.__name__, self._filter, self._doc, self._upsert,\n            self._collation)\n\n\nclass _UpdateOp(object):\n    \"\"\"Private base class for update operations.\"\"\"\n\n    __slots__ = (\"_filter\", \"_doc\", \"_upsert\", \"_collation\", \"_array_filters\")\n\n    def __init__(self, filter, doc, upsert, collation, array_filters):\n        if filter is not None:\n            validate_is_mapping(\"filter\", filter)\n        if upsert is not None:\n            validate_boolean(\"upsert\", upsert)\n        if array_filters is not None:\n            validate_list(\"array_filters\", array_filters)\n        self._filter = filter\n        self._doc = doc\n        self._upsert = upsert\n        self._collation = collation\n        self._array_filters = array_filters\n\n    def __eq__(self, other):\n        if type(other) == type(self):\n            return (\n                (other._filter, other._doc, other._upsert, other._collation,\n                 other._array_filters) ==\n                (self._filter, self._doc, self._upsert, self._collation,\n                 self._array_filters))\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __repr__(self):\n        return \"%s(%r, %r, %r, %r, %r)\" % (\n            self.__class__.__name__, self._filter, self._doc, self._upsert,\n            self._collation, self._array_filters)\n\n\nclass UpdateOne(_UpdateOp):\n    \"\"\"Represents an update_one operation.\"\"\"\n\n    __slots__ = ()\n\n    def __init__(self, filter, update, upsert=False, collation=None,\n                 array_filters=None):\n        \"\"\"Represents an update_one operation.\n\n        For use with :meth:`~pymongo.collection.Collection.bulk_write`.\n\n        :Parameters:\n          - `filter`: A query that matches the document to update.\n          - `update`: The modifications to apply.\n          - `upsert` (optional): If ``True``, perform an insert if no documents\n            match the filter.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only\n            supported on MongoDB 3.4 and above.\n          - `array_filters` (optional): A list of filters specifying which\n            array elements an update should apply. Requires MongoDB 3.6+.\n\n        .. versionchanged:: 3.9\n           Added the ability to accept a pipeline as the `update`.\n        .. versionchanged:: 3.6\n           Added the `array_filters` option.\n        .. versionchanged:: 3.5\n           Added the `collation` option.\n        \"\"\"\n        super(UpdateOne, self).__init__(filter, update, upsert, collation,\n                                        array_filters)\n\n    def _add_to_bulk(self, bulkobj):\n        \"\"\"Add this operation to the _Bulk instance `bulkobj`.\"\"\"\n        bulkobj.add_update(self._filter, self._doc, False, self._upsert,\n                           collation=self._collation,\n                           array_filters=self._array_filters)\n\n\nclass UpdateMany(_UpdateOp):\n    \"\"\"Represents an update_many operation.\"\"\"\n\n    __slots__ = ()\n\n    def __init__(self, filter, update, upsert=False, collation=None,\n                 array_filters=None):\n        \"\"\"Create an UpdateMany instance.\n\n        For use with :meth:`~pymongo.collection.Collection.bulk_write`.\n\n        :Parameters:\n          - `filter`: A query that matches the documents to update.\n          - `update`: The modifications to apply.\n          - `upsert` (optional): If ``True``, perform an insert if no documents\n            match the filter.\n          - `collation` (optional): An instance of\n            :class:`~pymongo.collation.Collation`. This option is only\n            supported on MongoDB 3.4 and above.\n          - `array_filters` (optional): A list of filters specifying which\n            array elements an update should apply. Requires MongoDB 3.6+.\n\n        .. versionchanged:: 3.9\n           Added the ability to accept a pipeline as the `update`.\n        .. versionchanged:: 3.6\n           Added the `array_filters` option.\n        .. versionchanged:: 3.5\n           Added the `collation` option.\n        \"\"\"\n        super(UpdateMany, self).__init__(filter, update, upsert, collation,\n                                         array_filters)\n\n    def _add_to_bulk(self, bulkobj):\n        \"\"\"Add this operation to the _Bulk instance `bulkobj`.\"\"\"\n        bulkobj.add_update(self._filter, self._doc, True, self._upsert,\n                           collation=self._collation,\n                           array_filters=self._array_filters)\n\n\nclass IndexModel(object):\n    \"\"\"Represents an index to create.\"\"\"\n\n    __slots__ = (\"__document\",)\n\n    def __init__(self, keys, **kwargs):\n        \"\"\"Create an Index instance.\n\n        For use with :meth:`~pymongo.collection.Collection.create_indexes`.\n\n        Takes either a single key or a list of (key, direction) pairs.\n        The key(s) must be an instance of :class:`basestring`\n        (:class:`str` in python 3), and the direction(s) must be one of\n        (:data:`~pymongo.ASCENDING`, :data:`~pymongo.DESCENDING`,\n        :data:`~pymongo.GEO2D`, :data:`~pymongo.GEOHAYSTACK`,\n        :data:`~pymongo.GEOSPHERE`, :data:`~pymongo.HASHED`,\n        :data:`~pymongo.TEXT`).\n\n        Valid options include, but are not limited to:\n\n          - `name`: custom name to use for this index - if none is\n            given, a name will be generated.\n          - `unique`: if ``True`` creates a uniqueness constraint on the index.\n          - `background`: if ``True`` this index should be created in the\n            background.\n          - `sparse`: if ``True``, omit from the index any documents that lack\n            the indexed field.\n          - `bucketSize`: for use with geoHaystack indexes.\n            Number of documents to group together within a certain proximity\n            to a given longitude and latitude.\n          - `min`: minimum value for keys in a :data:`~pymongo.GEO2D`\n            index.\n          - `max`: maximum value for keys in a :data:`~pymongo.GEO2D`\n            index.\n          - `expireAfterSeconds`: <int> Used to create an expiring (TTL)\n            collection. MongoDB will automatically delete documents from\n            this collection after <int> seconds. The indexed field must\n            be a UTC datetime or the data will not expire.\n          - `partialFilterExpression`: A document that specifies a filter for\n            a partial index. Requires server version >= 3.2.\n          - `collation`: An instance of :class:`~pymongo.collation.Collation`\n            that specifies the collation to use in MongoDB >= 3.4.\n          - `wildcardProjection`: Allows users to include or exclude specific\n            field paths from a `wildcard index`_ using the { \"$**\" : 1} key\n            pattern. Requires server version >= 4.2.\n\n        See the MongoDB documentation for a full list of supported options by\n        server version.\n\n        :Parameters:\n          - `keys`: a single key or a list of (key, direction)\n            pairs specifying the index to create\n          - `**kwargs` (optional): any additional index creation\n            options (see the above list) should be passed as keyword\n            arguments\n\n        .. versionchanged:: 3.2\n            Added partialFilterExpression to support partial indexes.\n\n        .. _wildcard index: https://docs.mongodb.com/master/core/index-wildcard/#wildcard-index-core\n        \"\"\"\n        keys = _index_list(keys)\n        if \"name\" not in kwargs:\n            kwargs[\"name\"] = _gen_index_name(keys)\n        kwargs[\"key\"] = _index_document(keys)\n        collation = validate_collation_or_none(kwargs.pop('collation', None))\n        self.__document = kwargs\n        if collation is not None:\n            self.__document['collation'] = collation\n\n    @property\n    def document(self):\n        \"\"\"An index document suitable for passing to the createIndexes\n        command.\n        \"\"\"\n        return self.__document\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/periodic_executor.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Run a target function on a background thread.\"\"\"\n\nimport atexit\nimport threading\nimport time\nimport weakref\n\nfrom pymongo.monotonic import time as _time\n\n\nclass PeriodicExecutor(object):\n    def __init__(self, interval, min_interval, target, name=None):\n        \"\"\"\"Run a target function periodically on a background thread.\n\n        If the target's return value is false, the executor stops.\n\n        :Parameters:\n          - `interval`: Seconds between calls to `target`.\n          - `min_interval`: Minimum seconds between calls if `wake` is\n            called very often.\n          - `target`: A function.\n          - `name`: A name to give the underlying thread.\n        \"\"\"\n        # threading.Event and its internal condition variable are expensive\n        # in Python 2, see PYTHON-983. Use a boolean to know when to wake.\n        # The executor's design is constrained by several Python issues, see\n        # \"periodic_executor.rst\" in this repository.\n        self._event = False\n        self._interval = interval\n        self._min_interval = min_interval\n        self._target = target\n        self._stopped = False\n        self._thread = None\n        self._name = name\n\n        self._thread_will_exit = False\n        self._lock = threading.Lock()\n\n    def open(self):\n        \"\"\"Start. Multiple calls have no effect.\n\n        Not safe to call from multiple threads at once.\n        \"\"\"\n        with self._lock:\n            if self._thread_will_exit:\n                # If the background thread has read self._stopped as True\n                # there is a chance that it has not yet exited. The call to\n                # join should not block indefinitely because there is no\n                # other work done outside the while loop in self._run.\n                try:\n                    self._thread.join()\n                except ReferenceError:\n                    # Thread terminated.\n                    pass\n            self._thread_will_exit = False\n            self._stopped = False\n        started = False\n        try:\n            started = self._thread and self._thread.is_alive()\n        except ReferenceError:\n            # Thread terminated.\n            pass\n\n        if not started:\n            thread = threading.Thread(target=self._run, name=self._name)\n            thread.daemon = True\n            self._thread = weakref.proxy(thread)\n            _register_executor(self)\n            thread.start()\n\n    def close(self, dummy=None):\n        \"\"\"Stop. To restart, call open().\n\n        The dummy parameter allows an executor's close method to be a weakref\n        callback; see monitor.py.\n        \"\"\"\n        self._stopped = True\n\n    def join(self, timeout=None):\n        if self._thread is not None:\n            try:\n                self._thread.join(timeout)\n            except (ReferenceError, RuntimeError):\n                # Thread already terminated, or not yet started.\n                pass\n\n    def wake(self):\n        \"\"\"Execute the target function soon.\"\"\"\n        self._event = True\n\n    def update_interval(self, new_interval):\n        self._interval = new_interval\n\n    def __should_stop(self):\n        with self._lock:\n            if self._stopped:\n                self._thread_will_exit = True\n                return True\n            return False\n\n    def _run(self):\n        while not self.__should_stop():\n            try:\n                if not self._target():\n                    self._stopped = True\n                    break\n            except:\n                with self._lock:\n                    self._stopped = True\n                    self._thread_will_exit = True\n\n                raise\n\n            deadline = _time() + self._interval\n\n            while not self._stopped and _time() < deadline:\n                time.sleep(self._min_interval)\n                if self._event:\n                    break  # Early wake.\n\n            self._event = False\n\n\n# _EXECUTORS has a weakref to each running PeriodicExecutor. Once started,\n# an executor is kept alive by a strong reference from its thread and perhaps\n# from other objects. When the thread dies and all other referrers are freed,\n# the executor is freed and removed from _EXECUTORS. If any threads are\n# running when the interpreter begins to shut down, we try to halt and join\n# them to avoid spurious errors.\n_EXECUTORS = set()\n\n\ndef _register_executor(executor):\n    ref = weakref.ref(executor, _on_executor_deleted)\n    _EXECUTORS.add(ref)\n\n\ndef _on_executor_deleted(ref):\n    _EXECUTORS.remove(ref)\n\n\ndef _shutdown_executors():\n    if _EXECUTORS is None:\n        return\n\n    # Copy the set. Stopping threads has the side effect of removing executors.\n    executors = list(_EXECUTORS)\n\n    # First signal all executors to close...\n    for ref in executors:\n        executor = ref()\n        if executor:\n            executor.close()\n\n    # ...then try to join them.\n    for ref in executors:\n        executor = ref()\n        if executor:\n            executor.join(1)\n\n    executor = None\n\natexit.register(_shutdown_executors)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/pool.py",
    "content": "# Copyright 2011-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\nimport contextlib\nimport copy\nimport os\nimport platform\nimport socket\nimport sys\nimport threading\nimport collections\n\ntry:\n    import ssl\n    from ssl import SSLError\n    _HAVE_SNI = getattr(ssl, 'HAS_SNI', False)\nexcept ImportError:\n    _HAVE_SNI = False\n    class SSLError(socket.error):\n        pass\n\ntry:\n    from ssl import CertificateError as _SSLCertificateError\nexcept ImportError:\n    class _SSLCertificateError(ValueError):\n        pass\n\n\nfrom bson import DEFAULT_CODEC_OPTIONS\nfrom bson.py3compat import imap, itervalues, _unicode, integer_types\nfrom bson.son import SON\nfrom pymongo import auth, helpers, thread_util, __version__\nfrom pymongo.client_session import _validate_session_write_concern\nfrom pymongo.common import (MAX_BSON_SIZE,\n                            MAX_IDLE_TIME_SEC,\n                            MAX_MESSAGE_SIZE,\n                            MAX_POOL_SIZE,\n                            MAX_WIRE_VERSION,\n                            MAX_WRITE_BATCH_SIZE,\n                            MIN_POOL_SIZE,\n                            ORDERED_TYPES,\n                            WAIT_QUEUE_TIMEOUT)\nfrom pymongo.errors import (AutoReconnect,\n                            ConnectionFailure,\n                            ConfigurationError,\n                            InvalidOperation,\n                            DocumentTooLarge,\n                            NetworkTimeout,\n                            NotMasterError,\n                            OperationFailure,\n                            PyMongoError)\nfrom pymongo.ismaster import IsMaster\nfrom pymongo.monotonic import time as _time\nfrom pymongo.monitoring import (ConnectionCheckOutFailedReason,\n                                ConnectionClosedReason)\nfrom pymongo.network import (command,\n                             receive_message,\n                             SocketChecker)\nfrom pymongo.read_preferences import ReadPreference\nfrom pymongo.server_type import SERVER_TYPE\n# Always use our backport so we always have support for IP address matching\nfrom pymongo.ssl_match_hostname import match_hostname, CertificateError\n\n# For SNI support. According to RFC6066, section 3, IPv4 and IPv6 literals are\n# not permitted for SNI hostname.\ntry:\n    from ipaddress import ip_address\n    def is_ip_address(address):\n        try:\n            ip_address(_unicode(address))\n            return True\n        except (ValueError, UnicodeError):\n            return False\nexcept ImportError:\n    if hasattr(socket, 'inet_pton') and socket.has_ipv6:\n        # Most *nix, recent Windows\n        def is_ip_address(address):\n            try:\n                # inet_pton rejects IPv4 literals with leading zeros\n                # (e.g. 192.168.0.01), inet_aton does not, and we\n                # can connect to them without issue. Use inet_aton.\n                socket.inet_aton(address)\n                return True\n            except socket.error:\n                try:\n                    socket.inet_pton(socket.AF_INET6, address)\n                    return True\n                except socket.error:\n                    return False\n    else:\n        # No inet_pton\n        def is_ip_address(address):\n            try:\n                socket.inet_aton(address)\n                return True\n            except socket.error:\n                if ':' in address:\n                    # ':' is not a valid character for a hostname. If we get\n                    # here a few things have to be true:\n                    #   - We're on a recent version of python 2.7 (2.7.9+).\n                    #     Older 2.7 versions don't support SNI.\n                    #   - We're on Windows XP or some unusual Unix that doesn't\n                    #     have inet_pton.\n                    #   - The application is using IPv6 literals with TLS, which\n                    #     is pretty unusual.\n                    return True\n                return False\n\ntry:\n    from fcntl import fcntl, F_GETFD, F_SETFD, FD_CLOEXEC\n    def _set_non_inheritable_non_atomic(fd):\n        \"\"\"Set the close-on-exec flag on the given file descriptor.\"\"\"\n        flags = fcntl(fd, F_GETFD)\n        fcntl(fd, F_SETFD, flags | FD_CLOEXEC)\nexcept ImportError:\n    # Windows, various platforms we don't claim to support\n    # (Jython, IronPython, ...), systems that don't provide\n    # everything we need from fcntl, etc.\n    def _set_non_inheritable_non_atomic(dummy):\n        \"\"\"Dummy function for platforms that don't provide fcntl.\"\"\"\n        pass\n\n_MAX_TCP_KEEPIDLE = 300\n_MAX_TCP_KEEPINTVL = 10\n_MAX_TCP_KEEPCNT = 9\n\nif sys.platform == 'win32':\n    try:\n        import _winreg as winreg\n    except ImportError:\n        import winreg\n\n    try:\n        with winreg.OpenKey(\n                winreg.HKEY_LOCAL_MACHINE,\n                r\"SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters\") as key:\n            _DEFAULT_TCP_IDLE_MS, _ = winreg.QueryValueEx(key, \"KeepAliveTime\")\n            _DEFAULT_TCP_INTERVAL_MS, _ = winreg.QueryValueEx(\n                key, \"KeepAliveInterval\")\n            # Make sure these are integers.\n            if not isinstance(_DEFAULT_TCP_IDLE_MS, integer_types):\n                raise ValueError\n            if not isinstance(_DEFAULT_TCP_INTERVAL_MS, integer_types):\n                raise ValueError\n    except (OSError, ValueError):\n        # We could not check the default values so do not attempt to override.\n        def _set_keepalive_times(dummy):\n            pass\n    else:\n        def _set_keepalive_times(sock):\n            idle_ms = min(_DEFAULT_TCP_IDLE_MS, _MAX_TCP_KEEPIDLE * 1000)\n            interval_ms = min(_DEFAULT_TCP_INTERVAL_MS,\n                              _MAX_TCP_KEEPINTVL * 1000)\n            if (idle_ms < _DEFAULT_TCP_IDLE_MS or\n                    interval_ms < _DEFAULT_TCP_INTERVAL_MS):\n                sock.ioctl(socket.SIO_KEEPALIVE_VALS,\n                           (1, idle_ms, interval_ms))\nelse:\n    def _set_tcp_option(sock, tcp_option, max_value):\n        if hasattr(socket, tcp_option):\n            sockopt = getattr(socket, tcp_option)\n            try:\n                # PYTHON-1350 - NetBSD doesn't implement getsockopt for\n                # TCP_KEEPIDLE and friends. Don't attempt to set the\n                # values there.\n                default = sock.getsockopt(socket.IPPROTO_TCP, sockopt)\n                if default > max_value:\n                    sock.setsockopt(socket.IPPROTO_TCP, sockopt, max_value)\n            except socket.error:\n                pass\n\n    def _set_keepalive_times(sock):\n        _set_tcp_option(sock, 'TCP_KEEPIDLE', _MAX_TCP_KEEPIDLE)\n        _set_tcp_option(sock, 'TCP_KEEPINTVL', _MAX_TCP_KEEPINTVL)\n        _set_tcp_option(sock, 'TCP_KEEPCNT', _MAX_TCP_KEEPCNT)\n\n_METADATA = SON([\n    ('driver', SON([('name', 'PyMongo'), ('version', __version__)])),\n])\n\nif sys.platform.startswith('linux'):\n    # platform.linux_distribution was deprecated in Python 3.5.\n    if sys.version_info[:2] < (3, 5):\n        # Distro name and version (e.g. Ubuntu 16.04 xenial)\n        _name = ' '.join([part for part in\n                          platform.linux_distribution() if part])\n    else:\n        _name = platform.system()\n    _METADATA['os'] = SON([\n        ('type', platform.system()),\n        ('name', _name),\n        ('architecture', platform.machine()),\n        # Kernel version (e.g. 4.4.0-17-generic).\n        ('version', platform.release())\n    ])\nelif sys.platform == 'darwin':\n    _METADATA['os'] = SON([\n        ('type', platform.system()),\n        ('name', platform.system()),\n        ('architecture', platform.machine()),\n        # (mac|i|tv)OS(X) version (e.g. 10.11.6) instead of darwin\n        # kernel version.\n        ('version', platform.mac_ver()[0])\n    ])\nelif sys.platform == 'win32':\n    _METADATA['os'] = SON([\n        ('type', platform.system()),\n        # \"Windows XP\", \"Windows 7\", \"Windows 10\", etc.\n        ('name', ' '.join((platform.system(), platform.release()))),\n        ('architecture', platform.machine()),\n        # Windows patch level (e.g. 5.1.2600-SP3)\n        ('version', '-'.join(platform.win32_ver()[1:3]))\n    ])\nelif sys.platform.startswith('java'):\n    _name, _ver, _arch = platform.java_ver()[-1]\n    _METADATA['os'] = SON([\n        # Linux, Windows 7, Mac OS X, etc.\n        ('type', _name),\n        ('name', _name),\n        # x86, x86_64, AMD64, etc.\n        ('architecture', _arch),\n        # Linux kernel version, OSX version, etc.\n        ('version', _ver)\n    ])\nelse:\n    # Get potential alias (e.g. SunOS 5.11 becomes Solaris 2.11)\n    _aliased = platform.system_alias(\n        platform.system(), platform.release(), platform.version())\n    _METADATA['os'] = SON([\n        ('type', platform.system()),\n        ('name', ' '.join([part for part in _aliased[:2] if part])),\n        ('architecture', platform.machine()),\n        ('version', _aliased[2])\n    ])\n\nif platform.python_implementation().startswith('PyPy'):\n    _METADATA['platform'] = ' '.join(\n        (platform.python_implementation(),\n         '.'.join(imap(str, sys.pypy_version_info)),\n         '(Python %s)' % '.'.join(imap(str, sys.version_info))))\nelif sys.platform.startswith('java'):\n    _METADATA['platform'] = ' '.join(\n        (platform.python_implementation(),\n         '.'.join(imap(str, sys.version_info)),\n         '(%s)' % ' '.join((platform.system(), platform.release()))))\nelse:\n    _METADATA['platform'] = ' '.join(\n        (platform.python_implementation(),\n         '.'.join(imap(str, sys.version_info))))\n\n\n# If the first getaddrinfo call of this interpreter's life is on a thread,\n# while the main thread holds the import lock, getaddrinfo deadlocks trying\n# to import the IDNA codec. Import it here, where presumably we're on the\n# main thread, to avoid the deadlock. See PYTHON-607.\nu'foo'.encode('idna')\n\n\ndef _raise_connection_failure(address, error, msg_prefix=None):\n    \"\"\"Convert a socket.error to ConnectionFailure and raise it.\"\"\"\n    host, port = address\n    # If connecting to a Unix socket, port will be None.\n    if port is not None:\n        msg = '%s:%d: %s' % (host, port, error)\n    else:\n        msg = '%s: %s' % (host, error)\n    if msg_prefix:\n        msg = msg_prefix + msg\n    if isinstance(error, socket.timeout):\n        raise NetworkTimeout(msg)\n    elif isinstance(error, SSLError) and 'timed out' in str(error):\n        # CPython 2.7 and PyPy 2.x do not distinguish network\n        # timeouts from other SSLErrors (https://bugs.python.org/issue10272).\n        # Luckily, we can work around this limitation because the phrase\n        # 'timed out' appears in all the timeout related SSLErrors raised\n        # on the above platforms.\n        raise NetworkTimeout(msg)\n    else:\n        raise AutoReconnect(msg)\n\n\nclass PoolOptions(object):\n\n    __slots__ = ('__max_pool_size', '__min_pool_size',\n                 '__max_idle_time_seconds',\n                 '__connect_timeout', '__socket_timeout',\n                 '__wait_queue_timeout', '__wait_queue_multiple',\n                 '__ssl_context', '__ssl_match_hostname', '__socket_keepalive',\n                 '__event_listeners', '__appname', '__driver', '__metadata',\n                 '__compression_settings')\n\n    def __init__(self, max_pool_size=MAX_POOL_SIZE,\n                 min_pool_size=MIN_POOL_SIZE,\n                 max_idle_time_seconds=MAX_IDLE_TIME_SEC, connect_timeout=None,\n                 socket_timeout=None, wait_queue_timeout=WAIT_QUEUE_TIMEOUT,\n                 wait_queue_multiple=None, ssl_context=None,\n                 ssl_match_hostname=True, socket_keepalive=True,\n                 event_listeners=None, appname=None, driver=None,\n                 compression_settings=None):\n\n        self.__max_pool_size = max_pool_size\n        self.__min_pool_size = min_pool_size\n        self.__max_idle_time_seconds = max_idle_time_seconds\n        self.__connect_timeout = connect_timeout\n        self.__socket_timeout = socket_timeout\n        self.__wait_queue_timeout = wait_queue_timeout\n        self.__wait_queue_multiple = wait_queue_multiple\n        self.__ssl_context = ssl_context\n        self.__ssl_match_hostname = ssl_match_hostname\n        self.__socket_keepalive = socket_keepalive\n        self.__event_listeners = event_listeners\n        self.__appname = appname\n        self.__driver = driver\n        self.__compression_settings = compression_settings\n        self.__metadata = copy.deepcopy(_METADATA)\n        if appname:\n            self.__metadata['application'] = {'name': appname}\n\n        # Combine the \"driver\" MongoClient option with PyMongo's info, like:\n        # {\n        #    'driver': {\n        #        'name': 'PyMongo|MyDriver',\n        #        'version': '3.7.0|1.2.3',\n        #    },\n        #    'platform': 'CPython 3.6.0|MyPlatform'\n        # }\n        if driver:\n            if driver.name:\n                self.__metadata['driver']['name'] = \"%s|%s\" % (\n                    _METADATA['driver']['name'], driver.name)\n            if driver.version:\n                self.__metadata['driver']['version'] = \"%s|%s\" % (\n                    _METADATA['driver']['version'], driver.version)\n            if driver.platform:\n                self.__metadata['platform'] = \"%s|%s\" % (\n                    _METADATA['platform'], driver.platform)\n\n    @property\n    def non_default_options(self):\n        \"\"\"The non-default options this pool was created with.\n\n        Added for CMAP's :class:`PoolCreatedEvent`.\n        \"\"\"\n        opts = {}\n        if self.__max_pool_size != MAX_POOL_SIZE:\n            opts['maxPoolSize'] = self.__max_pool_size\n        if self.__min_pool_size != MIN_POOL_SIZE:\n            opts['minPoolSize'] = self.__min_pool_size\n        if self.__max_idle_time_seconds != MAX_IDLE_TIME_SEC:\n            opts['maxIdleTimeMS'] = self.__max_idle_time_seconds * 1000\n        if self.__wait_queue_timeout != WAIT_QUEUE_TIMEOUT:\n            opts['waitQueueTimeoutMS'] = self.__wait_queue_timeout * 1000\n        return opts\n\n    @property\n    def max_pool_size(self):\n        \"\"\"The maximum allowable number of concurrent connections to each\n        connected server. Requests to a server will block if there are\n        `maxPoolSize` outstanding connections to the requested server.\n        Defaults to 100. Cannot be 0.\n\n        When a server's pool has reached `max_pool_size`, operations for that\n        server block waiting for a socket to be returned to the pool. If\n        ``waitQueueTimeoutMS`` is set, a blocked operation will raise\n        :exc:`~pymongo.errors.ConnectionFailure` after a timeout.\n        By default ``waitQueueTimeoutMS`` is not set.\n        \"\"\"\n        return self.__max_pool_size\n\n    @property\n    def min_pool_size(self):\n        \"\"\"The minimum required number of concurrent connections that the pool\n        will maintain to each connected server. Default is 0.\n        \"\"\"\n        return self.__min_pool_size\n\n    @property\n    def max_idle_time_seconds(self):\n        \"\"\"The maximum number of seconds that a connection can remain\n        idle in the pool before being removed and replaced. Defaults to\n        `None` (no limit).\n        \"\"\"\n        return self.__max_idle_time_seconds\n\n    @property\n    def connect_timeout(self):\n        \"\"\"How long a connection can take to be opened before timing out.\n        \"\"\"\n        return self.__connect_timeout\n\n    @property\n    def socket_timeout(self):\n        \"\"\"How long a send or receive on a socket can take before timing out.\n        \"\"\"\n        return self.__socket_timeout\n\n    @property\n    def wait_queue_timeout(self):\n        \"\"\"How long a thread will wait for a socket from the pool if the pool\n        has no free sockets.\n        \"\"\"\n        return self.__wait_queue_timeout\n\n    @property\n    def wait_queue_multiple(self):\n        \"\"\"Multiplied by max_pool_size to give the number of threads allowed\n        to wait for a socket at one time.\n        \"\"\"\n        return self.__wait_queue_multiple\n\n    @property\n    def ssl_context(self):\n        \"\"\"An SSLContext instance or None.\n        \"\"\"\n        return self.__ssl_context\n\n    @property\n    def ssl_match_hostname(self):\n        \"\"\"Call ssl.match_hostname if cert_reqs is not ssl.CERT_NONE.\n        \"\"\"\n        return self.__ssl_match_hostname\n\n    @property\n    def socket_keepalive(self):\n        \"\"\"Whether to send periodic messages to determine if a connection\n        is closed.\n        \"\"\"\n        return self.__socket_keepalive\n\n    @property\n    def event_listeners(self):\n        \"\"\"An instance of pymongo.monitoring._EventListeners.\n        \"\"\"\n        return self.__event_listeners\n\n    @property\n    def appname(self):\n        \"\"\"The application name, for sending with ismaster in server handshake.\n        \"\"\"\n        return self.__appname\n\n    @property\n    def driver(self):\n        \"\"\"Driver name and version, for sending with ismaster in handshake.\n        \"\"\"\n        return self.__driver\n\n    @property\n    def compression_settings(self):\n        return self.__compression_settings\n\n    @property\n    def metadata(self):\n        \"\"\"A dict of metadata about the application, driver, os, and platform.\n        \"\"\"\n        return self.__metadata.copy()\n\n\nclass SocketInfo(object):\n    \"\"\"Store a socket with some metadata.\n\n    :Parameters:\n      - `sock`: a raw socket object\n      - `pool`: a Pool instance\n      - `address`: the server's (host, port)\n      - `id`: the id of this socket in it's pool\n    \"\"\"\n    def __init__(self, sock, pool, address, id):\n        self.sock = sock\n        self.address = address\n        self.id = id\n        self.authset = set()\n        self.closed = False\n        self.last_checkin_time = _time()\n        self.performed_handshake = False\n        self.is_writable = False\n        self.max_wire_version = MAX_WIRE_VERSION\n        self.max_bson_size = MAX_BSON_SIZE\n        self.max_message_size = MAX_MESSAGE_SIZE\n        self.max_write_batch_size = MAX_WRITE_BATCH_SIZE\n        self.supports_sessions = False\n        self.is_mongos = False\n        self.op_msg_enabled = False\n        self.listeners = pool.opts.event_listeners\n        self.enabled_for_cmap = pool.enabled_for_cmap\n        self.compression_settings = pool.opts.compression_settings\n        self.compression_context = None\n\n        # The pool's pool_id changes with each reset() so we can close sockets\n        # created before the last reset.\n        self.pool_id = pool.pool_id\n        self.ready = False\n\n    def ismaster(self, metadata, cluster_time):\n        cmd = SON([('ismaster', 1)])\n        if not self.performed_handshake:\n            cmd['client'] = metadata\n            if self.compression_settings:\n                cmd['compression'] = self.compression_settings.compressors\n\n        if self.max_wire_version >= 6 and cluster_time is not None:\n            cmd['$clusterTime'] = cluster_time\n\n        ismaster = IsMaster(self.command('admin', cmd, publish_events=False))\n        self.is_writable = ismaster.is_writable\n        self.max_wire_version = ismaster.max_wire_version\n        self.max_bson_size = ismaster.max_bson_size\n        self.max_message_size = ismaster.max_message_size\n        self.max_write_batch_size = ismaster.max_write_batch_size\n        self.supports_sessions = (\n            ismaster.logical_session_timeout_minutes is not None)\n        self.is_mongos = ismaster.server_type == SERVER_TYPE.Mongos\n        if not self.performed_handshake and self.compression_settings:\n            ctx = self.compression_settings.get_compression_context(\n                ismaster.compressors)\n            self.compression_context = ctx\n\n        self.performed_handshake = True\n        self.op_msg_enabled = ismaster.max_wire_version >= 6\n        return ismaster\n\n    def command(self, dbname, spec, slave_ok=False,\n                read_preference=ReadPreference.PRIMARY,\n                codec_options=DEFAULT_CODEC_OPTIONS, check=True,\n                allowable_errors=None, check_keys=False,\n                read_concern=None,\n                write_concern=None,\n                parse_write_concern_error=False,\n                collation=None,\n                session=None,\n                client=None,\n                retryable_write=False,\n                publish_events=True,\n                user_fields=None):\n        \"\"\"Execute a command or raise an error.\n\n        :Parameters:\n          - `dbname`: name of the database on which to run the command\n          - `spec`: a command document as a dict, SON, or mapping object\n          - `slave_ok`: whether to set the SlaveOkay wire protocol bit\n          - `read_preference`: a read preference\n          - `codec_options`: a CodecOptions instance\n          - `check`: raise OperationFailure if there are errors\n          - `allowable_errors`: errors to ignore if `check` is True\n          - `check_keys`: if True, check `spec` for invalid keys\n          - `read_concern`: The read concern for this command.\n          - `write_concern`: The write concern for this command.\n          - `parse_write_concern_error`: Whether to parse the\n            ``writeConcernError`` field in the command response.\n          - `collation`: The collation for this command.\n          - `session`: optional ClientSession instance.\n          - `client`: optional MongoClient for gossipping $clusterTime.\n          - `retryable_write`: True if this command is a retryable write.\n          - `publish_events`: Should we publish events for this command?\n          - `user_fields` (optional): Response fields that should be decoded\n            using the TypeDecoders from codec_options, passed to\n            bson._decode_all_selective.\n        \"\"\"\n        self.validate_session(client, session)\n        session = _validate_session_write_concern(session, write_concern)\n\n        # Ensure command name remains in first place.\n        if not isinstance(spec, ORDERED_TYPES):\n            spec = SON(spec)\n\n        if (read_concern and self.max_wire_version < 4\n                and not read_concern.ok_for_legacy):\n            raise ConfigurationError(\n                'read concern level of %s is not valid '\n                'with a max wire version of %d.'\n                % (read_concern.level, self.max_wire_version))\n        if not (write_concern is None or write_concern.acknowledged or\n                collation is None):\n            raise ConfigurationError(\n                'Collation is unsupported for unacknowledged writes.')\n        if (self.max_wire_version >= 5 and\n                write_concern and\n                not write_concern.is_server_default):\n            spec['writeConcern'] = write_concern.document\n        elif self.max_wire_version < 5 and collation is not None:\n            raise ConfigurationError(\n                'Must be connected to MongoDB 3.4+ to use a collation.')\n\n        if session:\n            session._apply_to(spec, retryable_write, read_preference)\n        self.send_cluster_time(spec, session, client)\n        listeners = self.listeners if publish_events else None\n        unacknowledged = write_concern and not write_concern.acknowledged\n        if self.op_msg_enabled:\n            self._raise_if_not_writable(unacknowledged)\n        try:\n            return command(self.sock, dbname, spec, slave_ok,\n                           self.is_mongos, read_preference, codec_options,\n                           session, client, check, allowable_errors,\n                           self.address, check_keys, listeners,\n                           self.max_bson_size, read_concern,\n                           parse_write_concern_error=parse_write_concern_error,\n                           collation=collation,\n                           compression_ctx=self.compression_context,\n                           use_op_msg=self.op_msg_enabled,\n                           unacknowledged=unacknowledged,\n                           user_fields=user_fields)\n        except OperationFailure:\n            raise\n        # Catch socket.error, KeyboardInterrupt, etc. and close ourselves.\n        except BaseException as error:\n            self._raise_connection_failure(error)\n\n    def send_message(self, message, max_doc_size):\n        \"\"\"Send a raw BSON message or raise ConnectionFailure.\n\n        If a network exception is raised, the socket is closed.\n        \"\"\"\n        if (self.max_bson_size is not None\n                and max_doc_size > self.max_bson_size):\n            raise DocumentTooLarge(\n                \"BSON document too large (%d bytes) - the connected server \"\n                \"supports BSON document sizes up to %d bytes.\" %\n                (max_doc_size, self.max_bson_size))\n\n        try:\n            self.sock.sendall(message)\n        except BaseException as error:\n            self._raise_connection_failure(error)\n\n    def receive_message(self, request_id):\n        \"\"\"Receive a raw BSON message or raise ConnectionFailure.\n\n        If any exception is raised, the socket is closed.\n        \"\"\"\n        try:\n            return receive_message(self.sock, request_id,\n                                   self.max_message_size)\n        except BaseException as error:\n            self._raise_connection_failure(error)\n\n    def _raise_if_not_writable(self, unacknowledged):\n        \"\"\"Raise NotMasterError on unacknowledged write if this socket is not\n        writable.\n        \"\"\"\n        if unacknowledged and not self.is_writable:\n            # Write won't succeed, bail as if we'd received a not master error.\n            raise NotMasterError(\"not master\", {\n                \"ok\": 0, \"errmsg\": \"not master\", \"code\": 10107})\n\n    def legacy_write(self, request_id, msg, max_doc_size, with_last_error):\n        \"\"\"Send OP_INSERT, etc., optionally returning response as a dict.\n\n        Can raise ConnectionFailure or OperationFailure.\n\n        :Parameters:\n          - `request_id`: an int.\n          - `msg`: bytes, an OP_INSERT, OP_UPDATE, or OP_DELETE message,\n            perhaps with a getlasterror command appended.\n          - `max_doc_size`: size in bytes of the largest document in `msg`.\n          - `with_last_error`: True if a getlasterror command is appended.\n        \"\"\"\n        self._raise_if_not_writable(not with_last_error)\n\n        self.send_message(msg, max_doc_size)\n        if with_last_error:\n            reply = self.receive_message(request_id)\n            return helpers._check_gle_response(reply.command_response())\n\n    def write_command(self, request_id, msg):\n        \"\"\"Send \"insert\" etc. command, returning response as a dict.\n\n        Can raise ConnectionFailure or OperationFailure.\n\n        :Parameters:\n          - `request_id`: an int.\n          - `msg`: bytes, the command message.\n        \"\"\"\n        self.send_message(msg, 0)\n        reply = self.receive_message(request_id)\n        result = reply.command_response()\n\n        # Raises NotMasterError or OperationFailure.\n        helpers._check_command_response(result)\n        return result\n\n    def check_auth(self, all_credentials):\n        \"\"\"Update this socket's authentication.\n\n        Log in or out to bring this socket's credentials up to date with\n        those provided. Can raise ConnectionFailure or OperationFailure.\n\n        :Parameters:\n          - `all_credentials`: dict, maps auth source to MongoCredential.\n        \"\"\"\n        if all_credentials or self.authset:\n            cached = set(itervalues(all_credentials))\n            authset = self.authset.copy()\n\n            # Logout any credentials that no longer exist in the cache.\n            for credentials in authset - cached:\n                auth.logout(credentials.source, self)\n                self.authset.discard(credentials)\n\n            for credentials in cached - authset:\n                auth.authenticate(credentials, self)\n                self.authset.add(credentials)\n\n        # CMAP spec says to publish the ready event only after authenticating\n        # the connection.\n        if not self.ready:\n            self.ready = True\n            if self.enabled_for_cmap:\n                self.listeners.publish_connection_ready(self.address, self.id)\n\n    def authenticate(self, credentials):\n        \"\"\"Log in to the server and store these credentials in `authset`.\n\n        Can raise ConnectionFailure or OperationFailure.\n\n        :Parameters:\n          - `credentials`: A MongoCredential.\n        \"\"\"\n        auth.authenticate(credentials, self)\n        self.authset.add(credentials)\n\n    def validate_session(self, client, session):\n        \"\"\"Validate this session before use with client.\n\n        Raises error if this session is logged in as a different user or\n        the client is not the one that created the session.\n        \"\"\"\n        if session:\n            if session._client is not client:\n                raise InvalidOperation(\n                    'Can only use session with the MongoClient that'\n                    ' started it')\n            if session._authset != self.authset:\n                raise InvalidOperation(\n                    'Cannot use session after authenticating with different'\n                    ' credentials')\n\n    def close_socket(self, reason):\n        \"\"\"Close this connection with a reason.\"\"\"\n        if self.closed:\n            return\n        self.closed = True\n        # Avoid exceptions on interpreter shutdown.\n        try:\n            self.sock.close()\n        except Exception:\n            pass\n\n        if reason and self.enabled_for_cmap:\n            self.listeners.publish_connection_closed(\n                self.address, self.id, reason)\n\n    def send_cluster_time(self, command, session, client):\n        \"\"\"Add cluster time for MongoDB >= 3.6.\"\"\"\n        if self.max_wire_version >= 6 and client:\n            client._send_cluster_time(command, session)\n\n    def update_last_checkin_time(self):\n        self.last_checkin_time = _time()\n\n    def update_is_writable(self, is_writable):\n        self.is_writable = is_writable\n\n    def idle_time_seconds(self):\n        \"\"\"Seconds since this socket was last checked into its pool.\"\"\"\n        return _time() - self.last_checkin_time\n\n    def _raise_connection_failure(self, error):\n        # Catch *all* exceptions from socket methods and close the socket. In\n        # regular Python, socket operations only raise socket.error, even if\n        # the underlying cause was a Ctrl-C: a signal raised during socket.recv\n        # is expressed as an EINTR error from poll. See internal_select_ex() in\n        # socketmodule.c. All error codes from poll become socket.error at\n        # first. Eventually in PyEval_EvalFrameEx the interpreter checks for\n        # signals and throws KeyboardInterrupt into the current frame on the\n        # main thread.\n        #\n        # But in Gevent and Eventlet, the polling mechanism (epoll, kqueue,\n        # ...) is called in Python code, which experiences the signal as a\n        # KeyboardInterrupt from the start, rather than as an initial\n        # socket.error, so we catch that, close the socket, and reraise it.\n        self.close_socket(ConnectionClosedReason.ERROR)\n        if isinstance(error, socket.error):\n            _raise_connection_failure(self.address, error)\n        else:\n            raise\n\n    def __eq__(self, other):\n        return self.sock == other.sock\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __hash__(self):\n        return hash(self.sock)\n\n    def __repr__(self):\n        return \"SocketInfo(%s)%s at %s\" % (\n            repr(self.sock),\n            self.closed and \" CLOSED\" or \"\",\n            id(self)\n        )\n\n\ndef _create_connection(address, options):\n    \"\"\"Given (host, port) and PoolOptions, connect and return a socket object.\n\n    Can raise socket.error.\n\n    This is a modified version of create_connection from CPython >= 2.7.\n    \"\"\"\n    host, port = address\n\n    # Check if dealing with a unix domain socket\n    if host.endswith('.sock'):\n        if not hasattr(socket, \"AF_UNIX\"):\n            raise ConnectionFailure(\"UNIX-sockets are not supported \"\n                                    \"on this system\")\n        sock = socket.socket(socket.AF_UNIX)\n        # SOCK_CLOEXEC not supported for Unix sockets.\n        _set_non_inheritable_non_atomic(sock.fileno())\n        try:\n            sock.connect(host)\n            return sock\n        except socket.error:\n            sock.close()\n            raise\n\n    # Don't try IPv6 if we don't support it. Also skip it if host\n    # is 'localhost' (::1 is fine). Avoids slow connect issues\n    # like PYTHON-356.\n    family = socket.AF_INET\n    if socket.has_ipv6 and host != 'localhost':\n        family = socket.AF_UNSPEC\n\n    err = None\n    for res in socket.getaddrinfo(host, port, family, socket.SOCK_STREAM):\n        af, socktype, proto, dummy, sa = res\n        # SOCK_CLOEXEC was new in CPython 3.2, and only available on a limited\n        # number of platforms (newer Linux and *BSD). Starting with CPython 3.4\n        # all file descriptors are created non-inheritable. See PEP 446.\n        try:\n            sock = socket.socket(\n                af, socktype | getattr(socket, 'SOCK_CLOEXEC', 0), proto)\n        except socket.error:\n            # Can SOCK_CLOEXEC be defined even if the kernel doesn't support\n            # it?\n            sock = socket.socket(af, socktype, proto)\n        # Fallback when SOCK_CLOEXEC isn't available.\n        _set_non_inheritable_non_atomic(sock.fileno())\n        try:\n            sock.setsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY, 1)\n            sock.settimeout(options.connect_timeout)\n            sock.setsockopt(socket.SOL_SOCKET, socket.SO_KEEPALIVE,\n                            options.socket_keepalive)\n            if options.socket_keepalive:\n                _set_keepalive_times(sock)\n            sock.connect(sa)\n            return sock\n        except socket.error as e:\n            err = e\n            sock.close()\n\n    if err is not None:\n        raise err\n    else:\n        # This likely means we tried to connect to an IPv6 only\n        # host with an OS/kernel or Python interpreter that doesn't\n        # support IPv6. The test case is Jython2.5.1 which doesn't\n        # support IPv6 at all.\n        raise socket.error('getaddrinfo failed')\n\n\n_PY37PLUS = sys.version_info[:2] >= (3, 7)\n\n\ndef _configured_socket(address, options):\n    \"\"\"Given (host, port) and PoolOptions, return a configured socket.\n\n    Can raise socket.error, ConnectionFailure, or CertificateError.\n\n    Sets socket's SSL and timeout options.\n    \"\"\"\n    sock = _create_connection(address, options)\n    ssl_context = options.ssl_context\n\n    if ssl_context is not None:\n        host = address[0]\n        try:\n            # According to RFC6066, section 3, IPv4 and IPv6 literals are\n            # not permitted for SNI hostname.\n            # Previous to Python 3.7 wrap_socket would blindly pass\n            # IP addresses as SNI hostname.\n            # https://bugs.python.org/issue32185\n            # We have to pass hostname / ip address to wrap_socket\n            # to use SSLContext.check_hostname.\n            if _HAVE_SNI and (not is_ip_address(host) or _PY37PLUS):\n                sock = ssl_context.wrap_socket(sock, server_hostname=host)\n            else:\n                sock = ssl_context.wrap_socket(sock)\n        except _SSLCertificateError:\n            sock.close()\n            # Raise CertificateError directly like we do after match_hostname\n            # below.\n            raise\n        except IOError as exc:\n            sock.close()\n            # We raise AutoReconnect for transient and permanent SSL handshake\n            # failures alike. Permanent handshake failures, like protocol\n            # mismatch, will be turned into ServerSelectionTimeoutErrors later.\n            _raise_connection_failure(address, exc, \"SSL handshake failed: \")\n        if (ssl_context.verify_mode and not\n                getattr(ssl_context, \"check_hostname\", False) and\n                options.ssl_match_hostname):\n            try:\n                match_hostname(sock.getpeercert(), hostname=host)\n            except CertificateError:\n                sock.close()\n                raise\n\n    sock.settimeout(options.socket_timeout)\n    return sock\n\n\nclass _PoolClosedError(PyMongoError):\n    \"\"\"Internal error raised when a thread tries to get a connection from a\n    closed pool.\n    \"\"\"\n    pass\n\n\n# Do *not* explicitly inherit from object or Jython won't call __del__\n# http://bugs.jython.org/issue1057\nclass Pool:\n    def __init__(self, address, options, handshake=True):\n        \"\"\"\n        :Parameters:\n          - `address`: a (hostname, port) tuple\n          - `options`: a PoolOptions instance\n          - `handshake`: whether to call ismaster for each new SocketInfo\n        \"\"\"\n        # Check a socket's health with socket_closed() every once in a while.\n        # Can override for testing: 0 to always check, None to never check.\n        self._check_interval_seconds = 1\n        # LIFO pool. Sockets are ordered on idle time. Sockets claimed\n        # and returned to pool from the left side. Stale sockets removed\n        # from the right side.\n        self.sockets = collections.deque()\n        self.lock = threading.Lock()\n        self.active_sockets = 0\n        # Monotonically increasing connection ID required for CMAP Events.\n        self.next_connection_id = 1\n        self.closed = False\n        # Track whether the sockets in this pool are writeable or not.\n        self.is_writable = None\n\n        # Keep track of resets, so we notice sockets created before the most\n        # recent reset and close them.\n        self.pool_id = 0\n        self.pid = os.getpid()\n        self.address = address\n        self.opts = options\n        self.handshake = handshake\n        # Don't publish events in Monitor pools.\n        self.enabled_for_cmap = (\n                self.handshake and\n                self.opts.event_listeners is not None and\n                self.opts.event_listeners.enabled_for_cmap)\n\n        if (self.opts.wait_queue_multiple is None or\n                self.opts.max_pool_size is None):\n            max_waiters = None\n        else:\n            max_waiters = (\n                self.opts.max_pool_size * self.opts.wait_queue_multiple)\n\n        self._socket_semaphore = thread_util.create_semaphore(\n            self.opts.max_pool_size, max_waiters)\n        self.socket_checker = SocketChecker()\n        if self.enabled_for_cmap:\n            self.opts.event_listeners.publish_pool_created(\n                self.address, self.opts.non_default_options)\n\n    def _reset(self, close):\n        with self.lock:\n            if self.closed:\n                return\n            self.pool_id += 1\n            self.pid = os.getpid()\n            sockets, self.sockets = self.sockets, collections.deque()\n            self.active_sockets = 0\n            if close:\n                self.closed = True\n\n        listeners = self.opts.event_listeners\n        # CMAP spec says that close() MUST close sockets before publishing the\n        # PoolClosedEvent but that reset() SHOULD close sockets *after*\n        # publishing the PoolClearedEvent.\n        if close:\n            for sock_info in sockets:\n                sock_info.close_socket(ConnectionClosedReason.POOL_CLOSED)\n            if self.enabled_for_cmap:\n                listeners.publish_pool_closed(self.address)\n        else:\n            if self.enabled_for_cmap:\n                listeners.publish_pool_cleared(self.address)\n            for sock_info in sockets:\n                sock_info.close_socket(ConnectionClosedReason.STALE)\n\n    def update_is_writable(self, is_writable):\n        \"\"\"Updates the is_writable attribute on all sockets currently in the\n        Pool.\n        \"\"\"\n        self.is_writable = is_writable\n        with self.lock:\n            for socket in self.sockets:\n                socket.update_is_writable(self.is_writable)\n\n    def reset(self):\n        self._reset(close=False)\n\n    def close(self):\n        self._reset(close=True)\n\n    def remove_stale_sockets(self):\n        \"\"\"Removes stale sockets then adds new ones if pool is too small.\"\"\"\n        if self.opts.max_idle_time_seconds is not None:\n            with self.lock:\n                while (self.sockets and\n                       self.sockets[-1].idle_time_seconds() > self.opts.max_idle_time_seconds):\n                    sock_info = self.sockets.pop()\n                    sock_info.close_socket(ConnectionClosedReason.IDLE)\n        while True:\n            with self.lock:\n                if (len(self.sockets) + self.active_sockets >=\n                        self.opts.min_pool_size):\n                    # There are enough sockets in the pool.\n                    break\n\n            # We must acquire the semaphore to respect max_pool_size.\n            if not self._socket_semaphore.acquire(False):\n                break\n            try:\n                sock_info = self.connect()\n                with self.lock:\n                    self.sockets.appendleft(sock_info)\n            finally:\n                self._socket_semaphore.release()\n\n    def connect(self):\n        \"\"\"Connect to Mongo and return a new SocketInfo.\n\n        Can raise ConnectionFailure or CertificateError.\n\n        Note that the pool does not keep a reference to the socket -- you\n        must call return_socket() when you're done with it.\n        \"\"\"\n        with self.lock:\n            conn_id = self.next_connection_id\n            self.next_connection_id += 1\n\n        listeners = self.opts.event_listeners\n        if self.enabled_for_cmap:\n            listeners.publish_connection_created(self.address, conn_id)\n\n        sock = None\n        try:\n            sock = _configured_socket(self.address, self.opts)\n        except socket.error as error:\n            if sock is not None:\n                sock.close()\n\n            if self.enabled_for_cmap:\n                listeners.publish_connection_closed(\n                    self.address, conn_id, ConnectionClosedReason.ERROR)\n\n            _raise_connection_failure(self.address, error)\n\n        sock_info = SocketInfo(sock, self, self.address, conn_id)\n        if self.handshake:\n            sock_info.ismaster(self.opts.metadata, None)\n            self.is_writable = sock_info.is_writable\n\n        return sock_info\n\n    @contextlib.contextmanager\n    def get_socket(self, all_credentials, checkout=False):\n        \"\"\"Get a socket from the pool. Use with a \"with\" statement.\n\n        Returns a :class:`SocketInfo` object wrapping a connected\n        :class:`socket.socket`.\n\n        This method should always be used in a with-statement::\n\n            with pool.get_socket(credentials, checkout) as socket_info:\n                socket_info.send_message(msg)\n                data = socket_info.receive_message(op_code, request_id)\n\n        The socket is logged in or out as needed to match ``all_credentials``\n        using the correct authentication mechanism for the server's wire\n        protocol version.\n\n        Can raise ConnectionFailure or OperationFailure.\n\n        :Parameters:\n          - `all_credentials`: dict, maps auth source to MongoCredential.\n          - `checkout` (optional): keep socket checked out.\n        \"\"\"\n        listeners = self.opts.event_listeners\n        if self.enabled_for_cmap:\n            listeners.publish_connection_check_out_started(self.address)\n        # First get a socket, then attempt authentication. Simplifies\n        # semaphore management in the face of network errors during auth.\n        sock_info = self._get_socket_no_auth()\n        checked_auth = False\n        try:\n            sock_info.check_auth(all_credentials)\n            checked_auth = True\n            if self.enabled_for_cmap:\n                listeners.publish_connection_checked_out(\n                    self.address, sock_info.id)\n            yield sock_info\n        except:\n            # Exception in caller. Decrement semaphore.\n            self.return_socket(sock_info, publish_checkin=checked_auth)\n            if self.enabled_for_cmap and not checked_auth:\n                self.opts.event_listeners.publish_connection_check_out_failed(\n                    self.address, ConnectionCheckOutFailedReason.CONN_ERROR)\n            raise\n        else:\n            if not checkout:\n                self.return_socket(sock_info)\n\n    def _get_socket_no_auth(self):\n        \"\"\"Get or create a SocketInfo. Can raise ConnectionFailure.\"\"\"\n        # We use the pid here to avoid issues with fork / multiprocessing.\n        # See test.test_client:TestClient.test_fork for an example of\n        # what could go wrong otherwise\n        if self.pid != os.getpid():\n            self.reset()\n\n        if self.closed:\n            if self.enabled_for_cmap:\n                self.opts.event_listeners.publish_connection_check_out_failed(\n                    self.address, ConnectionCheckOutFailedReason.POOL_CLOSED)\n            raise _PoolClosedError(\n                'Attempted to check out a connection from closed connection '\n                'pool')\n\n        # Get a free socket or create one.\n        if not self._socket_semaphore.acquire(\n                True, self.opts.wait_queue_timeout):\n            self._raise_wait_queue_timeout()\n        with self.lock:\n            self.active_sockets += 1\n\n        # We've now acquired the semaphore and must release it on error.\n        try:\n            sock_info = None\n            while sock_info is None:\n                try:\n                    with self.lock:\n                        sock_info = self.sockets.popleft()\n                except IndexError:\n                    # Can raise ConnectionFailure or CertificateError.\n                    sock_info = self.connect()\n                else:\n                    if self._perished(sock_info):\n                        sock_info = None\n        except Exception:\n            self._socket_semaphore.release()\n            with self.lock:\n                self.active_sockets -= 1\n\n            if self.enabled_for_cmap:\n                self.opts.event_listeners.publish_connection_check_out_failed(\n                    self.address, ConnectionCheckOutFailedReason.CONN_ERROR)\n            raise\n\n        return sock_info\n\n    def return_socket(self, sock_info, publish_checkin=True):\n        \"\"\"Return the socket to the pool, or if it's closed discard it.\n\n        :Parameters:\n          - `sock_info`: The socket to check into the pool.\n          - `publish_checkin`: If False, a ConnectionCheckedInEvent will not\n            be published.\n        \"\"\"\n        listeners = self.opts.event_listeners\n        if self.enabled_for_cmap and publish_checkin:\n            listeners.publish_connection_checked_in(self.address, sock_info.id)\n        if self.pid != os.getpid():\n            self.reset()\n        else:\n            if self.closed:\n                sock_info.close_socket(ConnectionClosedReason.POOL_CLOSED)\n            elif sock_info.pool_id != self.pool_id:\n                sock_info.close_socket(ConnectionClosedReason.STALE)\n            elif not sock_info.closed:\n                sock_info.update_last_checkin_time()\n                sock_info.update_is_writable(self.is_writable)\n                with self.lock:\n                    self.sockets.appendleft(sock_info)\n\n        self._socket_semaphore.release()\n        with self.lock:\n            self.active_sockets -= 1\n\n    def _perished(self, sock_info):\n        \"\"\"This side-effecty function checks if this socket has been idle for\n        for longer than the max idle time, or if the socket has been closed by\n        some external network error.\n\n        Checking sockets lets us avoid seeing *some*\n        :class:`~pymongo.errors.AutoReconnect` exceptions on server\n        hiccups, etc. We only check if the socket was closed by an external\n        error if it has been > 1 second since the socket was checked into the\n        pool, to keep performance reasonable - we can't avoid AutoReconnects\n        completely anyway.\n        \"\"\"\n        idle_time_seconds = sock_info.idle_time_seconds()\n        # If socket is idle, open a new one.\n        if (self.opts.max_idle_time_seconds is not None and\n                idle_time_seconds > self.opts.max_idle_time_seconds):\n            sock_info.close_socket(ConnectionClosedReason.IDLE)\n            return True\n\n        if (self._check_interval_seconds is not None and (\n                0 == self._check_interval_seconds or\n                idle_time_seconds > self._check_interval_seconds)):\n            if self.socket_checker.socket_closed(sock_info.sock):\n                sock_info.close_socket(ConnectionClosedReason.ERROR)\n                return True\n\n        return False\n\n    def _raise_wait_queue_timeout(self):\n        listeners = self.opts.event_listeners\n        if self.enabled_for_cmap:\n            listeners.publish_connection_check_out_failed(\n                self.address, ConnectionCheckOutFailedReason.TIMEOUT)\n        raise ConnectionFailure(\n            'Timed out while checking out a connection from connection pool '\n            'with max_size %r and wait_queue_timeout %r' % (\n                self.opts.max_pool_size, self.opts.wait_queue_timeout))\n\n    def __del__(self):\n        # Avoid ResourceWarnings in Python 3\n        # Close all sockets without calling reset() or close() because it is\n        # not safe to acquire a lock in __del__.\n        for sock_info in self.sockets:\n            sock_info.close_socket(None)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/read_concern.py",
    "content": "# Copyright 2015 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\",\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for working with read concerns.\"\"\"\n\nfrom bson.py3compat import string_type\n\n\nclass ReadConcern(object):\n    \"\"\"ReadConcern\n\n    :Parameters:\n        - `level`: (string) The read concern level specifies the level of\n          isolation for read operations.  For example, a read operation using a\n          read concern level of ``majority`` will only return data that has been\n          written to a majority of nodes. If the level is left unspecified, the\n          server default will be used.\n\n    .. versionadded:: 3.2\n\n    \"\"\"\n\n    def __init__(self, level=None):\n        if level is None or isinstance(level, string_type):\n            self.__level = level\n        else:\n            raise TypeError(\n                'level must be a string or None.')\n\n    @property\n    def level(self):\n        \"\"\"The read concern level.\"\"\"\n        return self.__level\n\n    @property\n    def ok_for_legacy(self):\n        \"\"\"Return ``True`` if this read concern is compatible with\n        old wire protocol versions.\"\"\"\n        return self.level is None or self.level == 'local'\n\n    @property\n    def document(self):\n        \"\"\"The document representation of this read concern.\n\n        .. note::\n          :class:`ReadConcern` is immutable. Mutating the value of\n          :attr:`document` does not mutate this :class:`ReadConcern`.\n        \"\"\"\n        doc = {}\n        if self.__level:\n            doc['level'] = self.level\n        return doc\n\n    def __eq__(self, other):\n        if isinstance(other, ReadConcern):\n            return self.document == other.document\n        return NotImplemented\n\n    def __repr__(self):\n        if self.level:\n            return 'ReadConcern(%s)' % self.level\n        return 'ReadConcern()'\n\n\nDEFAULT_READ_CONCERN = ReadConcern()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/read_preferences.py",
    "content": "# Copyright 2012-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\",\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Utilities for choosing which member of a replica set to read from.\"\"\"\n\nfrom bson.py3compat import abc, integer_types\nfrom pymongo import max_staleness_selectors\nfrom pymongo.errors import ConfigurationError\nfrom pymongo.server_selectors import (member_with_tags_server_selector,\n                                      secondary_with_tags_server_selector)\n\n\n_PRIMARY = 0\n_PRIMARY_PREFERRED = 1\n_SECONDARY = 2\n_SECONDARY_PREFERRED = 3\n_NEAREST = 4\n\n\n_MONGOS_MODES = (\n    'primary',\n    'primaryPreferred',\n    'secondary',\n    'secondaryPreferred',\n    'nearest',\n)\n\n\ndef _validate_tag_sets(tag_sets):\n    \"\"\"Validate tag sets for a MongoReplicaSetClient.\n    \"\"\"\n    if tag_sets is None:\n        return tag_sets\n\n    if not isinstance(tag_sets, list):\n        raise TypeError((\n            \"Tag sets %r invalid, must be a list\") % (tag_sets,))\n    if len(tag_sets) == 0:\n        raise ValueError((\n            \"Tag sets %r invalid, must be None or contain at least one set of\"\n            \" tags\") % (tag_sets,))\n\n    for tags in tag_sets:\n        if not isinstance(tags, abc.Mapping):\n            raise TypeError(\n                \"Tag set %r invalid, must be an instance of dict, \"\n                \"bson.son.SON or other type that inherits from \"\n                \"collection.Mapping\" % (tags,))\n\n    return tag_sets\n\n\ndef _invalid_max_staleness_msg(max_staleness):\n    return (\"maxStalenessSeconds must be a positive integer, not %s\" %\n            max_staleness)\n\n\n# Some duplication with common.py to avoid import cycle.\ndef _validate_max_staleness(max_staleness):\n    \"\"\"Validate max_staleness.\"\"\"\n    if max_staleness == -1:\n        return -1\n\n    if not isinstance(max_staleness, integer_types):\n        raise TypeError(_invalid_max_staleness_msg(max_staleness))\n\n    if max_staleness <= 0:\n        raise ValueError(_invalid_max_staleness_msg(max_staleness))\n\n    return max_staleness\n\n\nclass _ServerMode(object):\n    \"\"\"Base class for all read preferences.\n    \"\"\"\n\n    __slots__ = (\"__mongos_mode\", \"__mode\", \"__tag_sets\", \"__max_staleness\")\n\n    def __init__(self, mode, tag_sets=None, max_staleness=-1):\n        self.__mongos_mode = _MONGOS_MODES[mode]\n        self.__mode = mode\n        self.__tag_sets = _validate_tag_sets(tag_sets)\n        self.__max_staleness = _validate_max_staleness(max_staleness)\n\n    @property\n    def name(self):\n        \"\"\"The name of this read preference.\n        \"\"\"\n        return self.__class__.__name__\n\n    @property\n    def mongos_mode(self):\n        \"\"\"The mongos mode of this read preference.\n        \"\"\"\n        return self.__mongos_mode\n\n    @property\n    def document(self):\n        \"\"\"Read preference as a document.\n        \"\"\"\n        doc = {'mode': self.__mongos_mode}\n        if self.__tag_sets not in (None, [{}]):\n            doc['tags'] = self.__tag_sets\n        if self.__max_staleness != -1:\n            doc['maxStalenessSeconds'] = self.__max_staleness\n        return doc\n\n    @property\n    def mode(self):\n        \"\"\"The mode of this read preference instance.\n        \"\"\"\n        return self.__mode\n\n    @property\n    def tag_sets(self):\n        \"\"\"Set ``tag_sets`` to a list of dictionaries like [{'dc': 'ny'}] to\n        read only from members whose ``dc`` tag has the value ``\"ny\"``.\n        To specify a priority-order for tag sets, provide a list of\n        tag sets: ``[{'dc': 'ny'}, {'dc': 'la'}, {}]``. A final, empty tag\n        set, ``{}``, means \"read from any member that matches the mode,\n        ignoring tags.\" MongoReplicaSetClient tries each set of tags in turn\n        until it finds a set of tags with at least one matching member.\n\n           .. seealso:: `Data-Center Awareness\n               <http://www.mongodb.org/display/DOCS/Data+Center+Awareness>`_\n        \"\"\"\n        return list(self.__tag_sets) if self.__tag_sets else [{}]\n\n    @property\n    def max_staleness(self):\n        \"\"\"The maximum estimated length of time (in seconds) a replica set\n        secondary can fall behind the primary in replication before it will\n        no longer be selected for operations, or -1 for no maximum.\"\"\"\n        return self.__max_staleness\n\n    @property\n    def min_wire_version(self):\n        \"\"\"The wire protocol version the server must support.\n\n        Some read preferences impose version requirements on all servers (e.g.\n        maxStalenessSeconds requires MongoDB 3.4 / maxWireVersion 5).\n\n        All servers' maxWireVersion must be at least this read preference's\n        `min_wire_version`, or the driver raises\n        :exc:`~pymongo.errors.ConfigurationError`.\n        \"\"\"\n        return 0 if self.__max_staleness == -1 else 5\n\n    def __repr__(self):\n        return \"%s(tag_sets=%r, max_staleness=%r)\" % (\n            self.name, self.__tag_sets, self.__max_staleness)\n\n    def __eq__(self, other):\n        if isinstance(other, _ServerMode):\n            return (self.mode == other.mode and\n                    self.tag_sets == other.tag_sets and\n                    self.max_staleness == other.max_staleness)\n        return NotImplemented\n\n    def __ne__(self, other):\n        return not self == other\n\n    def __getstate__(self):\n        \"\"\"Return value of object for pickling.\n\n        Needed explicitly because __slots__() defined.\n        \"\"\"\n        return {'mode': self.__mode,\n                'tag_sets': self.__tag_sets,\n                'max_staleness': self.__max_staleness}\n\n    def __setstate__(self, value):\n        \"\"\"Restore from pickling.\"\"\"\n        self.__mode = value['mode']\n        self.__mongos_mode = _MONGOS_MODES[self.__mode]\n        self.__tag_sets = _validate_tag_sets(value['tag_sets'])\n        self.__max_staleness = _validate_max_staleness(value['max_staleness'])\n\n\nclass Primary(_ServerMode):\n    \"\"\"Primary read preference.\n\n    * When directly connected to one mongod queries are allowed if the server\n      is standalone or a replica set primary.\n    * When connected to a mongos queries are sent to the primary of a shard.\n    * When connected to a replica set queries are sent to the primary of\n      the replica set.\n    \"\"\"\n\n    __slots__ = ()\n\n    def __init__(self):\n        super(Primary, self).__init__(_PRIMARY)\n\n    def __call__(self, selection):\n        \"\"\"Apply this read preference to a Selection.\"\"\"\n        return selection.primary_selection\n\n    def __repr__(self):\n        return \"Primary()\"\n\n    def __eq__(self, other):\n        if isinstance(other, _ServerMode):\n            return other.mode == _PRIMARY\n        return NotImplemented\n\n\nclass PrimaryPreferred(_ServerMode):\n    \"\"\"PrimaryPreferred read preference.\n\n    * When directly connected to one mongod queries are allowed to standalone\n      servers, to a replica set primary, or to replica set secondaries.\n    * When connected to a mongos queries are sent to the primary of a shard if\n      available, otherwise a shard secondary.\n    * When connected to a replica set queries are sent to the primary if\n      available, otherwise a secondary.\n\n    :Parameters:\n      - `tag_sets`: The :attr:`~tag_sets` to use if the primary is not\n        available.\n      - `max_staleness`: (integer, in seconds) The maximum estimated\n        length of time a replica set secondary can fall behind the primary in\n        replication before it will no longer be selected for operations.\n        Default -1, meaning no maximum. If it is set, it must be at least\n        90 seconds.\n    \"\"\"\n\n    __slots__ = ()\n\n    def __init__(self, tag_sets=None, max_staleness=-1):\n        super(PrimaryPreferred, self).__init__(_PRIMARY_PREFERRED,\n                                               tag_sets,\n                                               max_staleness)\n\n    def __call__(self, selection):\n        \"\"\"Apply this read preference to Selection.\"\"\"\n        if selection.primary:\n            return selection.primary_selection\n        else:\n            return secondary_with_tags_server_selector(\n                self.tag_sets,\n                max_staleness_selectors.select(\n                    self.max_staleness, selection))\n\n\nclass Secondary(_ServerMode):\n    \"\"\"Secondary read preference.\n\n    * When directly connected to one mongod queries are allowed to standalone\n      servers, to a replica set primary, or to replica set secondaries.\n    * When connected to a mongos queries are distributed among shard\n      secondaries. An error is raised if no secondaries are available.\n    * When connected to a replica set queries are distributed among\n      secondaries. An error is raised if no secondaries are available.\n\n    :Parameters:\n      - `tag_sets`: The :attr:`~tag_sets` for this read preference.\n      - `max_staleness`: (integer, in seconds) The maximum estimated\n        length of time a replica set secondary can fall behind the primary in\n        replication before it will no longer be selected for operations.\n        Default -1, meaning no maximum. If it is set, it must be at least\n        90 seconds.\n    \"\"\"\n\n    __slots__ = ()\n\n    def __init__(self, tag_sets=None, max_staleness=-1):\n        super(Secondary, self).__init__(_SECONDARY, tag_sets, max_staleness)\n\n    def __call__(self, selection):\n        \"\"\"Apply this read preference to Selection.\"\"\"\n        return secondary_with_tags_server_selector(\n            self.tag_sets,\n            max_staleness_selectors.select(\n                self.max_staleness, selection))\n\n\nclass SecondaryPreferred(_ServerMode):\n    \"\"\"SecondaryPreferred read preference.\n\n    * When directly connected to one mongod queries are allowed to standalone\n      servers, to a replica set primary, or to replica set secondaries.\n    * When connected to a mongos queries are distributed among shard\n      secondaries, or the shard primary if no secondary is available.\n    * When connected to a replica set queries are distributed among\n      secondaries, or the primary if no secondary is available.\n\n    :Parameters:\n      - `tag_sets`: The :attr:`~tag_sets` for this read preference.\n      - `max_staleness`: (integer, in seconds) The maximum estimated\n        length of time a replica set secondary can fall behind the primary in\n        replication before it will no longer be selected for operations.\n        Default -1, meaning no maximum. If it is set, it must be at least\n        90 seconds.\n    \"\"\"\n\n    __slots__ = ()\n\n    def __init__(self, tag_sets=None, max_staleness=-1):\n        super(SecondaryPreferred, self).__init__(_SECONDARY_PREFERRED,\n                                                 tag_sets,\n                                                 max_staleness)\n\n    def __call__(self, selection):\n        \"\"\"Apply this read preference to Selection.\"\"\"\n        secondaries = secondary_with_tags_server_selector(\n            self.tag_sets,\n            max_staleness_selectors.select(\n                self.max_staleness, selection))\n\n        if secondaries:\n            return secondaries\n        else:\n            return selection.primary_selection\n\n\nclass Nearest(_ServerMode):\n    \"\"\"Nearest read preference.\n\n    * When directly connected to one mongod queries are allowed to standalone\n      servers, to a replica set primary, or to replica set secondaries.\n    * When connected to a mongos queries are distributed among all members of\n      a shard.\n    * When connected to a replica set queries are distributed among all\n      members.\n\n    :Parameters:\n      - `tag_sets`: The :attr:`~tag_sets` for this read preference.\n      - `max_staleness`: (integer, in seconds) The maximum estimated\n        length of time a replica set secondary can fall behind the primary in\n        replication before it will no longer be selected for operations.\n        Default -1, meaning no maximum. If it is set, it must be at least\n        90 seconds.\n    \"\"\"\n\n    __slots__ = ()\n\n    def __init__(self, tag_sets=None, max_staleness=-1):\n        super(Nearest, self).__init__(_NEAREST, tag_sets, max_staleness)\n\n    def __call__(self, selection):\n        \"\"\"Apply this read preference to Selection.\"\"\"\n        return member_with_tags_server_selector(\n            self.tag_sets,\n            max_staleness_selectors.select(\n                self.max_staleness, selection))\n\n\n_ALL_READ_PREFERENCES = (Primary, PrimaryPreferred,\n                         Secondary, SecondaryPreferred, Nearest)\n\n\ndef make_read_preference(mode, tag_sets, max_staleness=-1):\n    if mode == _PRIMARY:\n        if tag_sets not in (None, [{}]):\n            raise ConfigurationError(\"Read preference primary \"\n                                     \"cannot be combined with tags\")\n        if max_staleness != -1:\n            raise ConfigurationError(\"Read preference primary cannot be \"\n                                     \"combined with maxStalenessSeconds\")\n        return Primary()\n    return _ALL_READ_PREFERENCES[mode](tag_sets, max_staleness)\n\n\n_MODES = (\n    'PRIMARY',\n    'PRIMARY_PREFERRED',\n    'SECONDARY',\n    'SECONDARY_PREFERRED',\n    'NEAREST',\n)\n\n\nclass ReadPreference(object):\n    \"\"\"An enum that defines the read preference modes supported by PyMongo.\n\n    See :doc:`/examples/high_availability` for code examples.\n\n    A read preference is used in three cases:\n\n    :class:`~pymongo.mongo_client.MongoClient` connected to a single mongod:\n\n    - ``PRIMARY``: Queries are allowed if the server is standalone or a replica\n      set primary.\n    - All other modes allow queries to standalone servers, to a replica set\n      primary, or to replica set secondaries.\n\n    :class:`~pymongo.mongo_client.MongoClient` initialized with the\n    ``replicaSet`` option:\n\n    - ``PRIMARY``: Read from the primary. This is the default, and provides the\n      strongest consistency. If no primary is available, raise\n      :class:`~pymongo.errors.AutoReconnect`.\n\n    - ``PRIMARY_PREFERRED``: Read from the primary if available, or if there is\n      none, read from a secondary.\n\n    - ``SECONDARY``: Read from a secondary. If no secondary is available,\n      raise :class:`~pymongo.errors.AutoReconnect`.\n\n    - ``SECONDARY_PREFERRED``: Read from a secondary if available, otherwise\n      from the primary.\n\n    - ``NEAREST``: Read from any member.\n\n    :class:`~pymongo.mongo_client.MongoClient` connected to a mongos, with a\n    sharded cluster of replica sets:\n\n    - ``PRIMARY``: Read from the primary of the shard, or raise\n      :class:`~pymongo.errors.OperationFailure` if there is none.\n      This is the default.\n\n    - ``PRIMARY_PREFERRED``: Read from the primary of the shard, or if there is\n      none, read from a secondary of the shard.\n\n    - ``SECONDARY``: Read from a secondary of the shard, or raise\n      :class:`~pymongo.errors.OperationFailure` if there is none.\n\n    - ``SECONDARY_PREFERRED``: Read from a secondary of the shard if available,\n      otherwise from the shard primary.\n\n    - ``NEAREST``: Read from any shard member.\n    \"\"\"\n    PRIMARY = Primary()\n    PRIMARY_PREFERRED = PrimaryPreferred()\n    SECONDARY = Secondary()\n    SECONDARY_PREFERRED = SecondaryPreferred()\n    NEAREST = Nearest()\n\n\ndef read_pref_mode_from_name(name):\n    \"\"\"Get the read preference mode from mongos/uri name.\n    \"\"\"\n    return _MONGOS_MODES.index(name)\n\n\nclass MovingAverage(object):\n    \"\"\"Tracks an exponentially-weighted moving average.\"\"\"\n    def __init__(self):\n        self.average = None\n\n    def add_sample(self, sample):\n        if sample < 0:\n            # Likely system time change while waiting for ismaster response\n            # and not using time.monotonic. Ignore it, the next one will\n            # probably be valid.\n            return\n        if self.average is None:\n            self.average = sample\n        else:\n            # The Server Selection Spec requires an exponentially weighted\n            # average with alpha = 0.2.\n            self.average = 0.8 * self.average + 0.2 * sample\n\n    def get(self):\n        \"\"\"Get the calculated average, or None if no samples yet.\"\"\"\n        return self.average\n\n    def reset(self):\n        self.average = None\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/response.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Represent a response from the server.\"\"\"\n\n\nclass Response(object):\n    __slots__ = ('_data', '_address', '_request_id', '_duration',\n                 '_from_command', '_docs')\n\n    def __init__(self, data, address, request_id, duration, from_command,\n                 docs):\n        \"\"\"Represent a response from the server.\n\n        :Parameters:\n          - `data`: A network response message.\n          - `address`: (host, port) of the source server.\n          - `request_id`: The request id of this operation.\n          - `duration`: The duration of the operation.\n          - `from_command`: if the response is the result of a db command.\n        \"\"\"\n        self._data = data\n        self._address = address\n        self._request_id = request_id\n        self._duration = duration\n        self._from_command = from_command\n        self._docs = docs\n\n    @property\n    def data(self):\n        \"\"\"Server response's raw BSON bytes.\"\"\"\n        return self._data\n\n    @property\n    def address(self):\n        \"\"\"(host, port) of the source server.\"\"\"\n        return self._address\n\n    @property\n    def request_id(self):\n        \"\"\"The request id of this operation.\"\"\"\n        return self._request_id\n\n    @property\n    def duration(self):\n        \"\"\"The duration of the operation.\"\"\"\n        return self._duration\n\n    @property\n    def from_command(self):\n        \"\"\"If the response is a result from a db command.\"\"\"\n        return self._from_command\n\n    @property\n    def docs(self):\n        \"\"\"The decoded document(s).\"\"\"\n        return self._docs\n\nclass ExhaustResponse(Response):\n    __slots__ = ('_socket_info', '_pool')\n\n    def __init__(self, data, address, socket_info, pool, request_id, duration,\n                 from_command, docs):\n        \"\"\"Represent a response to an exhaust cursor's initial query.\n\n        :Parameters:\n          - `data`:  A network response message.\n          - `address`: (host, port) of the source server.\n          - `socket_info`: The SocketInfo used for the initial query.\n          - `pool`: The Pool from which the SocketInfo came.\n          - `request_id`: The request id of this operation.\n          - `duration`: The duration of the operation.\n          - `from_command`: If the response is the result of a db command.\n        \"\"\"\n        super(ExhaustResponse, self).__init__(data,\n                                              address,\n                                              request_id,\n                                              duration,\n                                              from_command, docs)\n        self._socket_info = socket_info\n        self._pool = pool\n\n    @property\n    def socket_info(self):\n        \"\"\"The SocketInfo used for the initial query.\n\n        The server will send batches on this socket, without waiting for\n        getMores from the client, until the result set is exhausted or there\n        is an error.\n        \"\"\"\n        return self._socket_info\n\n    @property\n    def pool(self):\n        \"\"\"The Pool from which the SocketInfo came.\"\"\"\n        return self._pool\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/results.py",
    "content": "# Copyright 2015-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Result class definitions.\"\"\"\n\nfrom pymongo.errors import InvalidOperation\n\n\nclass _WriteResult(object):\n    \"\"\"Base class for write result classes.\"\"\"\n\n    __slots__ = (\"__acknowledged\",)\n\n    def __init__(self, acknowledged):\n        self.__acknowledged = acknowledged\n\n    def _raise_if_unacknowledged(self, property_name):\n        \"\"\"Raise an exception on property access if unacknowledged.\"\"\"\n        if not self.__acknowledged:\n            raise InvalidOperation(\"A value for %s is not available when \"\n                                   \"the write is unacknowledged. Check the \"\n                                   \"acknowledged attribute to avoid this \"\n                                   \"error.\" % (property_name,))\n\n    @property\n    def acknowledged(self):\n        \"\"\"Is this the result of an acknowledged write operation?\n\n        The :attr:`acknowledged` attribute will be ``False`` when using\n        ``WriteConcern(w=0)``, otherwise ``True``.\n\n        .. note::\n          If the :attr:`acknowledged` attribute is ``False`` all other\n          attibutes of this class will raise\n          :class:`~pymongo.errors.InvalidOperation` when accessed. Values for\n          other attributes cannot be determined if the write operation was\n          unacknowledged.\n\n        .. seealso::\n          :class:`~pymongo.write_concern.WriteConcern`\n        \"\"\"\n        return self.__acknowledged\n\n\nclass InsertOneResult(_WriteResult):\n    \"\"\"The return type for :meth:`~pymongo.collection.Collection.insert_one`.\n    \"\"\"\n\n    __slots__ = (\"__inserted_id\", \"__acknowledged\")\n\n    def __init__(self, inserted_id, acknowledged):\n        self.__inserted_id = inserted_id\n        super(InsertOneResult, self).__init__(acknowledged)\n\n    @property\n    def inserted_id(self):\n        \"\"\"The inserted document's _id.\"\"\"\n        return self.__inserted_id\n\n\nclass InsertManyResult(_WriteResult):\n    \"\"\"The return type for :meth:`~pymongo.collection.Collection.insert_many`.\n    \"\"\"\n\n    __slots__ = (\"__inserted_ids\", \"__acknowledged\")\n\n    def __init__(self, inserted_ids, acknowledged):\n        self.__inserted_ids = inserted_ids\n        super(InsertManyResult, self).__init__(acknowledged)\n\n    @property\n    def inserted_ids(self):\n        \"\"\"A list of _ids of the inserted documents, in the order provided.\n\n        .. note:: If ``False`` is passed for the `ordered` parameter to\n          :meth:`~pymongo.collection.Collection.insert_many` the server\n          may have inserted the documents in a different order than what\n          is presented here.\n        \"\"\"\n        return self.__inserted_ids\n\n\nclass UpdateResult(_WriteResult):\n    \"\"\"The return type for :meth:`~pymongo.collection.Collection.update_one`,\n    :meth:`~pymongo.collection.Collection.update_many`, and\n    :meth:`~pymongo.collection.Collection.replace_one`.\n    \"\"\"\n\n    __slots__ = (\"__raw_result\", \"__acknowledged\")\n\n    def __init__(self, raw_result, acknowledged):\n        self.__raw_result = raw_result\n        super(UpdateResult, self).__init__(acknowledged)\n\n    @property\n    def raw_result(self):\n        \"\"\"The raw result document returned by the server.\"\"\"\n        return self.__raw_result\n\n    @property\n    def matched_count(self):\n        \"\"\"The number of documents matched for this update.\"\"\"\n        self._raise_if_unacknowledged(\"matched_count\")\n        if self.upserted_id is not None:\n            return 0\n        return self.__raw_result.get(\"n\", 0)\n\n    @property\n    def modified_count(self):\n        \"\"\"The number of documents modified.\n\n        .. note:: modified_count is only reported by MongoDB 2.6 and later.\n          When connected to an earlier server version, or in certain mixed\n          version sharding configurations, this attribute will be set to\n          ``None``.\n        \"\"\"\n        self._raise_if_unacknowledged(\"modified_count\")\n        return self.__raw_result.get(\"nModified\")\n\n    @property\n    def upserted_id(self):\n        \"\"\"The _id of the inserted document if an upsert took place. Otherwise\n        ``None``.\n        \"\"\"\n        self._raise_if_unacknowledged(\"upserted_id\")\n        return self.__raw_result.get(\"upserted\")\n\n\nclass DeleteResult(_WriteResult):\n    \"\"\"The return type for :meth:`~pymongo.collection.Collection.delete_one`\n    and :meth:`~pymongo.collection.Collection.delete_many`\"\"\"\n\n    __slots__ = (\"__raw_result\", \"__acknowledged\")\n\n    def __init__(self, raw_result, acknowledged):\n        self.__raw_result = raw_result\n        super(DeleteResult, self).__init__(acknowledged)\n\n    @property\n    def raw_result(self):\n        \"\"\"The raw result document returned by the server.\"\"\"\n        return self.__raw_result\n\n    @property\n    def deleted_count(self):\n        \"\"\"The number of documents deleted.\"\"\"\n        self._raise_if_unacknowledged(\"deleted_count\")\n        return self.__raw_result.get(\"n\", 0)\n\n\nclass BulkWriteResult(_WriteResult):\n    \"\"\"An object wrapper for bulk API write results.\"\"\"\n\n    __slots__ = (\"__bulk_api_result\", \"__acknowledged\")\n\n    def __init__(self, bulk_api_result, acknowledged):\n        \"\"\"Create a BulkWriteResult instance.\n\n        :Parameters:\n          - `bulk_api_result`: A result dict from the bulk API\n          - `acknowledged`: Was this write result acknowledged? If ``False``\n            then all properties of this object will raise\n            :exc:`~pymongo.errors.InvalidOperation`.\n        \"\"\"\n        self.__bulk_api_result = bulk_api_result\n        super(BulkWriteResult, self).__init__(acknowledged)\n\n    @property\n    def bulk_api_result(self):\n        \"\"\"The raw bulk API result.\"\"\"\n        return self.__bulk_api_result\n\n    @property\n    def inserted_count(self):\n        \"\"\"The number of documents inserted.\"\"\"\n        self._raise_if_unacknowledged(\"inserted_count\")\n        return self.__bulk_api_result.get(\"nInserted\")\n\n    @property\n    def matched_count(self):\n        \"\"\"The number of documents matched for an update.\"\"\"\n        self._raise_if_unacknowledged(\"matched_count\")\n        return self.__bulk_api_result.get(\"nMatched\")\n\n    @property\n    def modified_count(self):\n        \"\"\"The number of documents modified.\n\n        .. note:: modified_count is only reported by MongoDB 2.6 and later.\n          When connected to an earlier server version, or in certain mixed\n          version sharding configurations, this attribute will be set to\n          ``None``.\n        \"\"\"\n        self._raise_if_unacknowledged(\"modified_count\")\n        return self.__bulk_api_result.get(\"nModified\")\n\n    @property\n    def deleted_count(self):\n        \"\"\"The number of documents deleted.\"\"\"\n        self._raise_if_unacknowledged(\"deleted_count\")\n        return self.__bulk_api_result.get(\"nRemoved\")\n\n    @property\n    def upserted_count(self):\n        \"\"\"The number of documents upserted.\"\"\"\n        self._raise_if_unacknowledged(\"upserted_count\")\n        return self.__bulk_api_result.get(\"nUpserted\")\n\n    @property\n    def upserted_ids(self):\n        \"\"\"A map of operation index to the _id of the upserted document.\"\"\"\n        self._raise_if_unacknowledged(\"upserted_ids\")\n        if self.__bulk_api_result:\n            return dict((upsert[\"index\"], upsert[\"_id\"])\n                        for upsert in self.bulk_api_result[\"upserted\"])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/saslprep.py",
    "content": "# Copyright 2016-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"An implementation of RFC4013 SASLprep.\"\"\"\n\nfrom bson.py3compat import text_type as _text_type\n\ntry:\n    import stringprep\nexcept ImportError:\n    HAVE_STRINGPREP = False\n    def saslprep(data):\n        \"\"\"SASLprep dummy\"\"\"\n        if isinstance(data, _text_type):\n            raise TypeError(\n                \"The stringprep module is not available. Usernames and \"\n                \"passwords must be ASCII strings.\")\n        return data\nelse:\n    HAVE_STRINGPREP = True\n    import unicodedata\n    # RFC4013 section 2.3 prohibited output.\n    _PROHIBITED = (\n        # A strict reading of RFC 4013 requires table c12 here, but\n        # characters from it are mapped to SPACE in the Map step. Can\n        # normalization reintroduce them somehow?\n        stringprep.in_table_c12,\n        stringprep.in_table_c21_c22,\n        stringprep.in_table_c3,\n        stringprep.in_table_c4,\n        stringprep.in_table_c5,\n        stringprep.in_table_c6,\n        stringprep.in_table_c7,\n        stringprep.in_table_c8,\n        stringprep.in_table_c9)\n\n    def saslprep(data, prohibit_unassigned_code_points=True):\n        \"\"\"An implementation of RFC4013 SASLprep.\n\n        :Parameters:\n          - `data`: The string to SASLprep. Unicode strings\n            (python 2.x unicode, 3.x str) are supported. Byte strings\n            (python 2.x str, 3.x bytes) are ignored.\n          - `prohibit_unassigned_code_points`: True / False. RFC 3454\n            and RFCs for various SASL mechanisms distinguish between\n            `queries` (unassigned code points allowed) and\n            `stored strings` (unassigned code points prohibited). Defaults\n            to ``True`` (unassigned code points are prohibited).\n\n        :Returns:\n        The SASLprep'ed version of `data`.\n        \"\"\"\n        if not isinstance(data, _text_type):\n            return data\n\n        if prohibit_unassigned_code_points:\n            prohibited = _PROHIBITED + (stringprep.in_table_a1,)\n        else:\n            prohibited = _PROHIBITED\n\n        # RFC3454 section 2, step 1 - Map\n        # RFC4013 section 2.1 mappings\n        # Map Non-ASCII space characters to SPACE (U+0020). Map\n        # commonly mapped to nothing characters to, well, nothing.\n        in_table_c12 = stringprep.in_table_c12\n        in_table_b1 = stringprep.in_table_b1\n        data = u\"\".join(\n            [u\"\\u0020\" if in_table_c12(elt) else elt\n             for elt in data if not in_table_b1(elt)])\n\n        # RFC3454 section 2, step 2 - Normalize\n        # RFC4013 section 2.2 normalization\n        data = unicodedata.ucd_3_2_0.normalize('NFKC', data)\n\n        in_table_d1 = stringprep.in_table_d1\n        if in_table_d1(data[0]):\n            if not in_table_d1(data[-1]):\n                # RFC3454, Section 6, #3. If a string contains any\n                # RandALCat character, the first and last characters\n                # MUST be RandALCat characters.\n                raise ValueError(\"SASLprep: failed bidirectional check\")\n            # RFC3454, Section 6, #2. If a string contains any RandALCat\n            # character, it MUST NOT contain any LCat character.\n            prohibited = prohibited + (stringprep.in_table_d2,)\n        else:\n            # RFC3454, Section 6, #3. Following the logic of #3, if\n            # the first character is not a RandALCat, no other character\n            # can be either.\n            prohibited = prohibited + (in_table_d1,)\n\n        # RFC3454 section 2, step 3 and 4 - Prohibit and check bidi\n        for char in data:\n            if any(in_table(char) for in_table in prohibited):\n                raise ValueError(\n                    \"SASLprep: failed prohibited character check\")\n\n        return data\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/server.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Communicate with one MongoDB server in a topology.\"\"\"\n\nfrom datetime import datetime\n\nfrom bson import _decode_all_selective\n\nfrom pymongo.errors import NotMasterError, OperationFailure\nfrom pymongo.helpers import _check_command_response\nfrom pymongo.message import _convert_exception\nfrom pymongo.response import Response, ExhaustResponse\nfrom pymongo.server_type import SERVER_TYPE\n\n_CURSOR_DOC_FIELDS = {'cursor': {'firstBatch': 1, 'nextBatch': 1}}\n\n\nclass Server(object):\n    def __init__(self, server_description, pool, monitor, topology_id=None,\n                 listeners=None, events=None):\n        \"\"\"Represent one MongoDB server.\"\"\"\n        self._description = server_description\n        self._pool = pool\n        self._monitor = monitor\n        self._topology_id = topology_id\n        self._publish = listeners is not None and listeners.enabled_for_server\n        self._listener = listeners\n        self._events = None\n        if self._publish:\n            self._events = events()\n\n    def open(self):\n        \"\"\"Start monitoring, or restart after a fork.\n\n        Multiple calls have no effect.\n        \"\"\"\n        self._monitor.open()\n\n    def reset(self):\n        \"\"\"Clear the connection pool.\"\"\"\n        self.pool.reset()\n\n    def close(self):\n        \"\"\"Clear the connection pool and stop the monitor.\n\n        Reconnect with open().\n        \"\"\"\n        if self._publish:\n            self._events.put((self._listener.publish_server_closed,\n                              (self._description.address, self._topology_id)))\n        self._monitor.close()\n        self._pool.reset()\n\n    def request_check(self):\n        \"\"\"Check the server's state soon.\"\"\"\n        self._monitor.request_check()\n\n    def run_operation_with_response(\n            self,\n            sock_info,\n            operation,\n            set_slave_okay,\n            listeners,\n            exhaust,\n            unpack_res):\n        \"\"\"Run a _Query or _GetMore operation and return a Response object.\n\n        This method is used only to run _Query/_GetMore operations from\n        cursors.\n        Can raise ConnectionFailure, OperationFailure, etc.\n\n        :Parameters:\n          - `operation`: A _Query or _GetMore object.\n          - `set_slave_okay`: Pass to operation.get_message.\n          - `all_credentials`: dict, maps auth source to MongoCredential.\n          - `listeners`: Instance of _EventListeners or None.\n          - `exhaust`: If True, then this is an exhaust cursor operation.\n          - `unpack_res`: A callable that decodes the wire protocol response.\n        \"\"\"\n        duration = None\n        publish = listeners.enabled_for_commands\n        if publish:\n            start = datetime.now()\n\n        send_message = not operation.exhaust_mgr\n\n        if send_message:\n            use_cmd = operation.use_command(sock_info, exhaust)\n            message = operation.get_message(\n                set_slave_okay, sock_info, use_cmd)\n            request_id, data, max_doc_size = self._split_message(message)\n        else:\n            use_cmd = False\n            request_id = 0\n\n        if publish:\n            cmd, dbn = operation.as_command(sock_info)\n            listeners.publish_command_start(\n                cmd, dbn, request_id, sock_info.address)\n            start = datetime.now()\n\n        try:\n            if send_message:\n                sock_info.send_message(data, max_doc_size)\n                reply = sock_info.receive_message(request_id)\n            else:\n                reply = sock_info.receive_message(None)\n\n            # Unpack and check for command errors.\n            if use_cmd:\n                user_fields = _CURSOR_DOC_FIELDS\n                legacy_response = False\n            else:\n                user_fields = None\n                legacy_response = True\n            docs = unpack_res(reply, operation.cursor_id,\n                              operation.codec_options,\n                              legacy_response=legacy_response,\n                              user_fields=user_fields)\n            if use_cmd:\n                first = docs[0]\n                operation.client._process_response(\n                    first, operation.session)\n                _check_command_response(first)\n        except Exception as exc:\n            if publish:\n                duration = datetime.now() - start\n                if isinstance(exc, (NotMasterError, OperationFailure)):\n                    failure = exc.details\n                else:\n                    failure = _convert_exception(exc)\n                listeners.publish_command_failure(\n                    duration, failure, operation.name,\n                    request_id, sock_info.address)\n            raise\n\n        if publish:\n            duration = datetime.now() - start\n            # Must publish in find / getMore / explain command response\n            # format.\n            if use_cmd:\n                res = docs[0]\n            elif operation.name == \"explain\":\n                res = docs[0] if docs else {}\n            else:\n                res = {\"cursor\": {\"id\": reply.cursor_id,\n                                  \"ns\": operation.namespace()},\n                       \"ok\": 1}\n                if operation.name == \"find\":\n                    res[\"cursor\"][\"firstBatch\"] = docs\n                else:\n                    res[\"cursor\"][\"nextBatch\"] = docs\n            listeners.publish_command_success(\n                duration, res, operation.name, request_id,\n                sock_info.address)\n\n        # Decrypt response.\n        client = operation.client\n        if client and client._encrypter:\n            if use_cmd:\n                decrypted = client._encrypter.decrypt(\n                    reply.raw_command_response())\n                docs = _decode_all_selective(\n                    decrypted, operation.codec_options, user_fields)\n\n        if exhaust:\n            response = ExhaustResponse(\n                data=reply,\n                address=self._description.address,\n                socket_info=sock_info,\n                pool=self._pool,\n                duration=duration,\n                request_id=request_id,\n                from_command=use_cmd,\n                docs=docs)\n        else:\n            response = Response(\n                data=reply,\n                address=self._description.address,\n                duration=duration,\n                request_id=request_id,\n                from_command=use_cmd,\n                docs=docs)\n\n        return response\n\n    def get_socket(self, all_credentials, checkout=False):\n        return self.pool.get_socket(all_credentials, checkout)\n\n    @property\n    def description(self):\n        return self._description\n\n    @description.setter\n    def description(self, server_description):\n        assert server_description.address == self._description.address\n        self._description = server_description\n\n    @property\n    def pool(self):\n        return self._pool\n\n    def _split_message(self, message):\n        \"\"\"Return request_id, data, max_doc_size.\n\n        :Parameters:\n          - `message`: (request_id, data, max_doc_size) or (request_id, data)\n        \"\"\"\n        if len(message) == 3:\n            return message\n        else:\n            # get_more and kill_cursors messages don't include BSON documents.\n            request_id, data = message\n            return request_id, data, 0\n\n    def __str__(self):\n        d = self._description\n        return '<Server \"%s:%s\" %s>' % (\n            d.address[0], d.address[1],\n            SERVER_TYPE._fields[d.server_type])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/server_description.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Represent one server the driver is connected to.\"\"\"\n\nfrom bson import EPOCH_NAIVE\nfrom pymongo.server_type import SERVER_TYPE\nfrom pymongo.ismaster import IsMaster\nfrom pymongo.monotonic import time as _time\n\n\nclass ServerDescription(object):\n    \"\"\"Immutable representation of one server.\n\n    :Parameters:\n      - `address`: A (host, port) pair\n      - `ismaster`: Optional IsMaster instance\n      - `round_trip_time`: Optional float\n      - `error`: Optional, the last error attempting to connect to the server\n    \"\"\"\n\n    __slots__ = (\n        '_address', '_server_type', '_all_hosts', '_tags', '_replica_set_name',\n        '_primary', '_max_bson_size', '_max_message_size',\n        '_max_write_batch_size', '_min_wire_version', '_max_wire_version',\n        '_round_trip_time', '_me', '_is_writable', '_is_readable',\n        '_ls_timeout_minutes', '_error', '_set_version', '_election_id',\n        '_cluster_time', '_last_write_date', '_last_update_time')\n\n    def __init__(\n            self,\n            address,\n            ismaster=None,\n            round_trip_time=None,\n            error=None):\n        self._address = address\n        if not ismaster:\n            ismaster = IsMaster({})\n\n        self._server_type = ismaster.server_type\n        self._all_hosts = ismaster.all_hosts\n        self._tags = ismaster.tags\n        self._replica_set_name = ismaster.replica_set_name\n        self._primary = ismaster.primary\n        self._max_bson_size = ismaster.max_bson_size\n        self._max_message_size = ismaster.max_message_size\n        self._max_write_batch_size = ismaster.max_write_batch_size\n        self._min_wire_version = ismaster.min_wire_version\n        self._max_wire_version = ismaster.max_wire_version\n        self._set_version = ismaster.set_version\n        self._election_id = ismaster.election_id\n        self._cluster_time = ismaster.cluster_time\n        self._is_writable = ismaster.is_writable\n        self._is_readable = ismaster.is_readable\n        self._ls_timeout_minutes = ismaster.logical_session_timeout_minutes\n        self._round_trip_time = round_trip_time\n        self._me = ismaster.me\n        self._last_update_time = _time()\n        self._error = error\n\n        if ismaster.last_write_date:\n            # Convert from datetime to seconds.\n            delta = ismaster.last_write_date - EPOCH_NAIVE\n            self._last_write_date = delta.total_seconds()\n        else:\n            self._last_write_date = None\n\n    @property\n    def address(self):\n        \"\"\"The address (host, port) of this server.\"\"\"\n        return self._address\n\n    @property\n    def server_type(self):\n        \"\"\"The type of this server.\"\"\"\n        return self._server_type\n\n    @property\n    def server_type_name(self):\n        \"\"\"The server type as a human readable string.\n\n        .. versionadded:: 3.4\n        \"\"\"\n        return SERVER_TYPE._fields[self._server_type]\n\n    @property\n    def all_hosts(self):\n        \"\"\"List of hosts, passives, and arbiters known to this server.\"\"\"\n        return self._all_hosts\n\n    @property\n    def tags(self):\n        return self._tags\n\n    @property\n    def replica_set_name(self):\n        \"\"\"Replica set name or None.\"\"\"\n        return self._replica_set_name\n\n    @property\n    def primary(self):\n        \"\"\"This server's opinion about who the primary is, or None.\"\"\"\n        return self._primary\n\n    @property\n    def max_bson_size(self):\n        return self._max_bson_size\n\n    @property\n    def max_message_size(self):\n        return self._max_message_size\n\n    @property\n    def max_write_batch_size(self):\n        return self._max_write_batch_size\n\n    @property\n    def min_wire_version(self):\n        return self._min_wire_version\n\n    @property\n    def max_wire_version(self):\n        return self._max_wire_version\n\n    @property\n    def set_version(self):\n        return self._set_version\n\n    @property\n    def election_id(self):\n        return self._election_id\n\n    @property\n    def cluster_time(self):\n        return self._cluster_time\n\n    @property\n    def election_tuple(self):\n        return self._set_version, self._election_id\n\n    @property\n    def me(self):\n        return self._me\n\n    @property\n    def logical_session_timeout_minutes(self):\n        return self._ls_timeout_minutes\n\n    @property\n    def last_write_date(self):\n        return self._last_write_date\n\n    @property\n    def last_update_time(self):\n        return self._last_update_time\n\n    @property\n    def round_trip_time(self):\n        \"\"\"The current average latency or None.\"\"\"\n        # This override is for unittesting only!\n        if self._address in self._host_to_round_trip_time:\n            return self._host_to_round_trip_time[self._address]\n\n        return self._round_trip_time\n\n    @property\n    def error(self):\n        \"\"\"The last error attempting to connect to the server, or None.\"\"\"\n        return self._error\n\n    @property\n    def is_writable(self):\n        return self._is_writable\n\n    @property\n    def is_readable(self):\n        return self._is_readable\n\n    @property\n    def mongos(self):\n        return self._server_type == SERVER_TYPE.Mongos\n\n    @property\n    def is_server_type_known(self):\n        return self.server_type != SERVER_TYPE.Unknown\n\n    @property\n    def retryable_writes_supported(self):\n        \"\"\"Checks if this server supports retryable writes.\"\"\"\n        return (\n            self._ls_timeout_minutes is not None and\n            self._server_type in (SERVER_TYPE.Mongos, SERVER_TYPE.RSPrimary))\n\n    @property\n    def retryable_reads_supported(self):\n        \"\"\"Checks if this server supports retryable writes.\"\"\"\n        return self._max_wire_version >= 6\n\n    # For unittesting only. Use under no circumstances!\n    _host_to_round_trip_time = {}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/server_selectors.py",
    "content": "# Copyright 2014-2016 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Criteria to select some ServerDescriptions from a TopologyDescription.\"\"\"\n\nfrom pymongo.server_type import SERVER_TYPE\n\n\nclass Selection(object):\n    \"\"\"Input or output of a server selector function.\"\"\"\n\n    @classmethod\n    def from_topology_description(cls, topology_description):\n        known_servers = topology_description.known_servers\n        primary = None\n        for sd in known_servers:\n            if sd.server_type == SERVER_TYPE.RSPrimary:\n                primary = sd\n                break\n\n        return Selection(topology_description,\n                         topology_description.known_servers,\n                         topology_description.common_wire_version,\n                         primary)\n\n    def __init__(self,\n                 topology_description,\n                 server_descriptions,\n                 common_wire_version,\n                 primary):\n        self.topology_description = topology_description\n        self.server_descriptions = server_descriptions\n        self.primary = primary\n        self.common_wire_version = common_wire_version\n\n    def with_server_descriptions(self, server_descriptions):\n        return Selection(self.topology_description,\n                         server_descriptions,\n                         self.common_wire_version,\n                         self.primary)\n\n    def secondary_with_max_last_write_date(self):\n        secondaries = secondary_server_selector(self)\n        if secondaries.server_descriptions:\n            return max(secondaries.server_descriptions,\n                       key=lambda sd: sd.last_write_date)\n\n    @property\n    def primary_selection(self):\n        primaries = [self.primary] if self.primary else []\n        return self.with_server_descriptions(primaries)\n\n    @property\n    def heartbeat_frequency(self):\n        return self.topology_description.heartbeat_frequency\n\n    @property\n    def topology_type(self):\n        return self.topology_description.topology_type\n\n    def __bool__(self):\n        return bool(self.server_descriptions)\n\n    __nonzero__ = __bool__  # Python 2.\n\n    def __getitem__(self, item):\n        return self.server_descriptions[item]\n\n\ndef any_server_selector(selection):\n    return selection\n\n\ndef readable_server_selector(selection):\n    return selection.with_server_descriptions(\n        [s for s in selection.server_descriptions if s.is_readable])\n\n\ndef writable_server_selector(selection):\n    return selection.with_server_descriptions(\n        [s for s in selection.server_descriptions if s.is_writable])\n\n\ndef secondary_server_selector(selection):\n    return selection.with_server_descriptions(\n        [s for s in selection.server_descriptions\n         if s.server_type == SERVER_TYPE.RSSecondary])\n\n\ndef arbiter_server_selector(selection):\n    return selection.with_server_descriptions(\n        [s for s in selection.server_descriptions\n         if s.server_type == SERVER_TYPE.RSArbiter])\n\n\ndef writable_preferred_server_selector(selection):\n    \"\"\"Like PrimaryPreferred but doesn't use tags or latency.\"\"\"\n    return (writable_server_selector(selection) or\n            secondary_server_selector(selection))\n\n\ndef apply_single_tag_set(tag_set, selection):\n    \"\"\"All servers matching one tag set.\n\n    A tag set is a dict. A server matches if its tags are a superset:\n    A server tagged {'a': '1', 'b': '2'} matches the tag set {'a': '1'}.\n\n    The empty tag set {} matches any server.\n    \"\"\"\n    def tags_match(server_tags):\n        for key, value in tag_set.items():\n            if key not in server_tags or server_tags[key] != value:\n                return False\n\n        return True\n\n    return selection.with_server_descriptions(\n        [s for s in selection.server_descriptions if tags_match(s.tags)])\n\n\ndef apply_tag_sets(tag_sets, selection):\n    \"\"\"All servers match a list of tag sets.\n\n    tag_sets is a list of dicts. The empty tag set {} matches any server,\n    and may be provided at the end of the list as a fallback. So\n    [{'a': 'value'}, {}] expresses a preference for servers tagged\n    {'a': 'value'}, but accepts any server if none matches the first\n    preference.\n    \"\"\"\n    for tag_set in tag_sets:\n        with_tag_set = apply_single_tag_set(tag_set, selection)\n        if with_tag_set:\n            return with_tag_set\n\n    return selection.with_server_descriptions([])\n\n\ndef secondary_with_tags_server_selector(tag_sets, selection):\n    \"\"\"All near-enough secondaries matching the tag sets.\"\"\"\n    return apply_tag_sets(tag_sets, secondary_server_selector(selection))\n\n\ndef member_with_tags_server_selector(tag_sets, selection):\n    \"\"\"All near-enough members matching the tag sets.\"\"\"\n    return apply_tag_sets(tag_sets, readable_server_selector(selection))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/server_type.py",
    "content": "# Copyright 2014-2015 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Type codes for MongoDB servers.\"\"\"\n\nfrom collections import namedtuple\n\n\nSERVER_TYPE = namedtuple('ServerType',\n                         ['Unknown', 'Mongos', 'RSPrimary', 'RSSecondary',\n                          'RSArbiter', 'RSOther', 'RSGhost',\n                          'Standalone'])(*range(8))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/settings.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Represent MongoClient's configuration.\"\"\"\n\nimport threading\n\nfrom bson.objectid import ObjectId\nfrom pymongo import common, monitor, pool\nfrom pymongo.common import LOCAL_THRESHOLD_MS, SERVER_SELECTION_TIMEOUT\nfrom pymongo.errors import ConfigurationError\nfrom pymongo.pool import PoolOptions\nfrom pymongo.server_description import ServerDescription\nfrom pymongo.topology_description import TOPOLOGY_TYPE\n\n\nclass TopologySettings(object):\n    def __init__(self,\n                 seeds=None,\n                 replica_set_name=None,\n                 pool_class=None,\n                 pool_options=None,\n                 monitor_class=None,\n                 condition_class=None,\n                 local_threshold_ms=LOCAL_THRESHOLD_MS,\n                 server_selection_timeout=SERVER_SELECTION_TIMEOUT,\n                 heartbeat_frequency=common.HEARTBEAT_FREQUENCY,\n                 server_selector=None,\n                 fqdn=None):\n        \"\"\"Represent MongoClient's configuration.\n\n        Take a list of (host, port) pairs and optional replica set name.\n        \"\"\"\n        if heartbeat_frequency < common.MIN_HEARTBEAT_INTERVAL:\n            raise ConfigurationError(\n                \"heartbeatFrequencyMS cannot be less than %d\" % (\n                    common.MIN_HEARTBEAT_INTERVAL * 1000,))\n\n        self._seeds = seeds or [('localhost', 27017)]\n        self._replica_set_name = replica_set_name\n        self._pool_class = pool_class or pool.Pool\n        self._pool_options = pool_options or PoolOptions()\n        self._monitor_class = monitor_class or monitor.Monitor\n        self._condition_class = condition_class or threading.Condition\n        self._local_threshold_ms = local_threshold_ms\n        self._server_selection_timeout = server_selection_timeout\n        self._server_selector = server_selector\n        self._fqdn = fqdn\n        self._heartbeat_frequency = heartbeat_frequency\n        self._direct = (len(self._seeds) == 1 and not replica_set_name)\n        self._topology_id = ObjectId()\n\n    @property\n    def seeds(self):\n        \"\"\"List of server addresses.\"\"\"\n        return self._seeds\n\n    @property\n    def replica_set_name(self):\n        return self._replica_set_name\n\n    @property\n    def pool_class(self):\n        return self._pool_class\n\n    @property\n    def pool_options(self):\n        return self._pool_options\n\n    @property\n    def monitor_class(self):\n        return self._monitor_class\n\n    @property\n    def condition_class(self):\n        return self._condition_class\n\n    @property\n    def local_threshold_ms(self):\n        return self._local_threshold_ms\n\n    @property\n    def server_selection_timeout(self):\n        return self._server_selection_timeout\n\n    @property\n    def server_selector(self):\n        return self._server_selector\n\n    @property\n    def heartbeat_frequency(self):\n        return self._heartbeat_frequency\n\n    @property\n    def fqdn(self):\n        return self._fqdn\n\n    @property\n    def direct(self):\n        \"\"\"Connect directly to a single server, or use a set of servers?\n\n        True if there is one seed and no replica_set_name.\n        \"\"\"\n        return self._direct\n\n    def get_topology_type(self):\n        if self.direct:\n            return TOPOLOGY_TYPE.Single\n        elif self.replica_set_name is not None:\n            return TOPOLOGY_TYPE.ReplicaSetNoPrimary\n        else:\n            return TOPOLOGY_TYPE.Unknown\n\n    def get_server_descriptions(self):\n        \"\"\"Initial dict of (address, ServerDescription) for all seeds.\"\"\"\n        return dict([\n            (address, ServerDescription(address))\n            for address in self.seeds])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/son_manipulator.py",
    "content": "# Copyright 2009-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"**DEPRECATED**: Manipulators that can edit SON objects as they enter and exit\na database.\n\nThe :class:`~pymongo.son_manipulator.SONManipulator` API has limitations as a\ntechnique for transforming your data. Instead, it is more flexible and\nstraightforward to transform outgoing documents in your own code before passing\nthem to PyMongo, and transform incoming documents after receiving them from\nPyMongo. SON Manipulators will be removed from PyMongo in 4.0.\n\nPyMongo does **not** apply SON manipulators to documents passed to\nthe modern methods :meth:`~pymongo.collection.Collection.bulk_write`,\n:meth:`~pymongo.collection.Collection.insert_one`,\n:meth:`~pymongo.collection.Collection.insert_many`,\n:meth:`~pymongo.collection.Collection.update_one`, or\n:meth:`~pymongo.collection.Collection.update_many`. SON manipulators are\n**not** applied to documents returned by the modern methods\n:meth:`~pymongo.collection.Collection.find_one_and_delete`,\n:meth:`~pymongo.collection.Collection.find_one_and_replace`, and\n:meth:`~pymongo.collection.Collection.find_one_and_update`.\n\"\"\"\n\nfrom bson.dbref import DBRef\nfrom bson.objectid import ObjectId\nfrom bson.py3compat import abc\nfrom bson.son import SON\n\n\nclass SONManipulator(object):\n    \"\"\"A base son manipulator.\n\n    This manipulator just saves and restores objects without changing them.\n    \"\"\"\n\n    def will_copy(self):\n        \"\"\"Will this SON manipulator make a copy of the incoming document?\n\n        Derived classes that do need to make a copy should override this\n        method, returning True instead of False. All non-copying manipulators\n        will be applied first (so that the user's document will be updated\n        appropriately), followed by copying manipulators.\n        \"\"\"\n        return False\n\n    def transform_incoming(self, son, collection):\n        \"\"\"Manipulate an incoming SON object.\n\n        :Parameters:\n          - `son`: the SON object to be inserted into the database\n          - `collection`: the collection the object is being inserted into\n        \"\"\"\n        if self.will_copy():\n            return SON(son)\n        return son\n\n    def transform_outgoing(self, son, collection):\n        \"\"\"Manipulate an outgoing SON object.\n\n        :Parameters:\n          - `son`: the SON object being retrieved from the database\n          - `collection`: the collection this object was stored in\n        \"\"\"\n        if self.will_copy():\n            return SON(son)\n        return son\n\n\nclass ObjectIdInjector(SONManipulator):\n    \"\"\"A son manipulator that adds the _id field if it is missing.\n\n    .. versionchanged:: 2.7\n       ObjectIdInjector is no longer used by PyMongo, but remains in this\n       module for backwards compatibility.\n    \"\"\"\n\n    def transform_incoming(self, son, collection):\n        \"\"\"Add an _id field if it is missing.\n        \"\"\"\n        if not \"_id\" in son:\n            son[\"_id\"] = ObjectId()\n        return son\n\n\n# This is now handled during BSON encoding (for performance reasons),\n# but I'm keeping this here as a reference for those implementing new\n# SONManipulators.\nclass ObjectIdShuffler(SONManipulator):\n    \"\"\"A son manipulator that moves _id to the first position.\n    \"\"\"\n\n    def will_copy(self):\n        \"\"\"We need to copy to be sure that we are dealing with SON, not a dict.\n        \"\"\"\n        return True\n\n    def transform_incoming(self, son, collection):\n        \"\"\"Move _id to the front if it's there.\n        \"\"\"\n        if not \"_id\" in son:\n            return son\n        transformed = SON({\"_id\": son[\"_id\"]})\n        transformed.update(son)\n        return transformed\n\n\nclass NamespaceInjector(SONManipulator):\n    \"\"\"A son manipulator that adds the _ns field.\n    \"\"\"\n\n    def transform_incoming(self, son, collection):\n        \"\"\"Add the _ns field to the incoming object\n        \"\"\"\n        son[\"_ns\"] = collection.name\n        return son\n\n\nclass AutoReference(SONManipulator):\n    \"\"\"Transparently reference and de-reference already saved embedded objects.\n\n    This manipulator should probably only be used when the NamespaceInjector is\n    also being used, otherwise it doesn't make too much sense - documents can\n    only be auto-referenced if they have an *_ns* field.\n\n    NOTE: this will behave poorly if you have a circular reference.\n\n    TODO: this only works for documents that are in the same database. To fix\n    this we'll need to add a DatabaseInjector that adds *_db* and then make\n    use of the optional *database* support for DBRefs.\n    \"\"\"\n\n    def __init__(self, db):\n        self.database = db\n\n    def will_copy(self):\n        \"\"\"We need to copy so the user's document doesn't get transformed refs.\n        \"\"\"\n        return True\n\n    def transform_incoming(self, son, collection):\n        \"\"\"Replace embedded documents with DBRefs.\n        \"\"\"\n\n        def transform_value(value):\n            if isinstance(value, abc.MutableMapping):\n                if \"_id\" in value and \"_ns\" in value:\n                    return DBRef(value[\"_ns\"], transform_value(value[\"_id\"]))\n                else:\n                    return transform_dict(SON(value))\n            elif isinstance(value, list):\n                return [transform_value(v) for v in value]\n            return value\n\n        def transform_dict(object):\n            for (key, value) in object.items():\n                object[key] = transform_value(value)\n            return object\n\n        return transform_dict(SON(son))\n\n    def transform_outgoing(self, son, collection):\n        \"\"\"Replace DBRefs with embedded documents.\n        \"\"\"\n\n        def transform_value(value):\n            if isinstance(value, DBRef):\n                return self.database.dereference(value)\n            elif isinstance(value, list):\n                return [transform_value(v) for v in value]\n            elif isinstance(value, abc.MutableMapping):\n                return transform_dict(SON(value))\n            return value\n\n        def transform_dict(object):\n            for (key, value) in object.items():\n                object[key] = transform_value(value)\n            return object\n\n        return transform_dict(SON(son))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/srv_resolver.py",
    "content": "# Copyright 2019-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Support for resolving hosts and options from mongodb+srv:// URIs.\"\"\"\n\ntry:\n    from dns import resolver\n    _HAVE_DNSPYTHON = True\nexcept ImportError:\n    _HAVE_DNSPYTHON = False\n\nfrom bson.py3compat import PY3\n\nfrom pymongo.common import CONNECT_TIMEOUT\nfrom pymongo.errors import ConfigurationError\n\n\nif PY3:\n    # dnspython can return bytes or str from various parts\n    # of its API depending on version. We always want str.\n    def maybe_decode(text):\n        if isinstance(text, bytes):\n            return text.decode()\n        return text\nelse:\n    def maybe_decode(text):\n        return text\n\n\nclass _SrvResolver(object):\n    def __init__(self, fqdn, connect_timeout=None):\n        self.__fqdn = fqdn\n        self.__connect_timeout = connect_timeout or CONNECT_TIMEOUT\n\n        # Validate the fully qualified domain name.\n        try:\n            self.__plist = self.__fqdn.split(\".\")[1:]\n        except Exception:\n            raise ConfigurationError(\"Invalid URI host: %s\" % (fqdn,))\n        self.__slen = len(self.__plist)\n        if self.__slen < 2:\n            raise ConfigurationError(\"Invalid URI host: %s\" % (fqdn,))\n\n    def get_options(self):\n        try:\n            results = resolver.query(self.__fqdn, 'TXT',\n                                     lifetime=self.__connect_timeout)\n        except (resolver.NoAnswer, resolver.NXDOMAIN):\n            # No TXT records\n            return None\n        except Exception as exc:\n            raise ConfigurationError(str(exc))\n        if len(results) > 1:\n            raise ConfigurationError('Only one TXT record is supported')\n        return (\n            b'&'.join([b''.join(res.strings) for res in results])).decode(\n            'utf-8')\n\n    def _resolve_uri(self, encapsulate_errors):\n        try:\n            results = resolver.query('_mongodb._tcp.' + self.__fqdn, 'SRV',\n                                     lifetime=self.__connect_timeout)\n        except Exception as exc:\n            if not encapsulate_errors:\n                # Raise the original error.\n                raise\n            # Else, raise all errors as ConfigurationError.\n            raise ConfigurationError(str(exc))\n        return results\n\n    def _get_srv_response_and_hosts(self, encapsulate_errors):\n        results = self._resolve_uri(encapsulate_errors)\n\n        # Construct address tuples\n        nodes = [\n            (maybe_decode(res.target.to_text(omit_final_dot=True)), res.port)\n            for res in results]\n\n        # Validate hosts\n        for node in nodes:\n            try:\n                nlist = node[0].split(\".\")[1:][-self.__slen:]\n            except Exception:\n                raise ConfigurationError(\"Invalid SRV host: %s\" % (node[0],))\n            if self.__plist != nlist:\n                raise ConfigurationError(\"Invalid SRV host: %s\" % (node[0],))\n\n        return results, nodes\n\n    def get_hosts(self):\n        _, nodes = self._get_srv_response_and_hosts(True)\n        return nodes\n\n    def get_hosts_and_min_ttl(self):\n        results, nodes = self._get_srv_response_and_hosts(False)\n        return nodes, results.rrset.ttl\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/ssl_context.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"A fake SSLContext implementation.\"\"\"\n\ntry:\n    import ssl\nexcept ImportError:\n    pass\n\n\nclass SSLContext(object):\n    \"\"\"A fake SSLContext.\n\n    This implements an API similar to ssl.SSLContext from python 3.2\n    but does not implement methods or properties that would be\n    incompatible with ssl.wrap_socket from python 2.7 < 2.7.9.\n\n    You must pass protocol which must be one of the PROTOCOL_* constants\n    defined in the ssl module. ssl.PROTOCOL_SSLv23 is recommended for maximum\n    interoperability.\n    \"\"\"\n\n    __slots__ = ('_cafile', '_certfile',\n                 '_keyfile', '_protocol', '_verify_mode')\n\n    def __init__(self, protocol):\n        self._cafile = None\n        self._certfile = None\n        self._keyfile = None\n        self._protocol = protocol\n        self._verify_mode = ssl.CERT_NONE\n\n    @property\n    def protocol(self):\n        \"\"\"The protocol version chosen when constructing the context.\n        This attribute is read-only.\n        \"\"\"\n        return self._protocol\n\n    def __get_verify_mode(self):\n        \"\"\"Whether to try to verify other peers' certificates and how to\n        behave if verification fails. This attribute must be one of\n        ssl.CERT_NONE, ssl.CERT_OPTIONAL or ssl.CERT_REQUIRED.\n        \"\"\"\n        return self._verify_mode\n\n    def __set_verify_mode(self, value):\n        \"\"\"Setter for verify_mode.\"\"\"\n        self._verify_mode = value\n\n    verify_mode = property(__get_verify_mode, __set_verify_mode)\n\n    def load_cert_chain(self, certfile, keyfile=None):\n        \"\"\"Load a private key and the corresponding certificate. The certfile\n        string must be the path to a single file in PEM format containing the\n        certificate as well as any number of CA certificates needed to\n        establish the certificate's authenticity. The keyfile string, if\n        present, must point to a file containing the private key. Otherwise\n        the private key will be taken from certfile as well.\n        \"\"\"\n        self._certfile = certfile\n        self._keyfile = keyfile\n\n    def load_verify_locations(self, cafile=None, dummy=None):\n        \"\"\"Load a set of \"certification authority\"(CA) certificates used to\n        validate other peers' certificates when `~verify_mode` is other than\n        ssl.CERT_NONE.\n        \"\"\"\n        self._cafile = cafile\n\n    def wrap_socket(self, sock, server_side=False,\n                    do_handshake_on_connect=True,\n                    suppress_ragged_eofs=True, dummy=None):\n        \"\"\"Wrap an existing Python socket sock and return an ssl.SSLSocket\n        object.\n        \"\"\"\n        return ssl.wrap_socket(sock, keyfile=self._keyfile,\n                               certfile=self._certfile,\n                               server_side=server_side,\n                               cert_reqs=self._verify_mode,\n                               ssl_version=self._protocol,\n                               ca_certs=self._cafile,\n                               do_handshake_on_connect=do_handshake_on_connect,\n                               suppress_ragged_eofs=suppress_ragged_eofs)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/ssl_match_hostname.py",
    "content": "# Backport of the match_hostname logic from python 3.5, with small\n# changes to support IP address matching on python 2.7 and 3.4.\n\nimport re\nimport sys\n\ntry:\n    # Python 3.4+, or the ipaddress module from pypi.\n    from ipaddress import ip_address\nexcept ImportError:\n    ip_address = lambda address: None\n\n# ipaddress.ip_address requires unicode\nif sys.version_info[0] < 3:\n    _unicode = unicode\nelse:\n    _unicode = lambda value: value\n\n\nclass CertificateError(ValueError):\n    pass\n\n\ndef _dnsname_match(dn, hostname, max_wildcards=1):\n    \"\"\"Matching according to RFC 6125, section 6.4.3\n\n    http://tools.ietf.org/html/rfc6125#section-6.4.3\n    \"\"\"\n    pats = []\n    if not dn:\n        return False\n\n    parts = dn.split(r'.')\n    leftmost = parts[0]\n    remainder = parts[1:]\n\n    wildcards = leftmost.count('*')\n    if wildcards > max_wildcards:\n        # Issue #17980: avoid denials of service by refusing more\n        # than one wildcard per fragment.  A survey of established\n        # policy among SSL implementations showed it to be a\n        # reasonable choice.\n        raise CertificateError(\n            \"too many wildcards in certificate DNS name: \" + repr(dn))\n\n    # speed up common case w/o wildcards\n    if not wildcards:\n        return dn.lower() == hostname.lower()\n\n    # RFC 6125, section 6.4.3, subitem 1.\n    # The client SHOULD NOT attempt to match a presented identifier in which\n    # the wildcard character comprises a label other than the left-most label.\n    if leftmost == '*':\n        # When '*' is a fragment by itself, it matches a non-empty dotless\n        # fragment.\n        pats.append('[^.]+')\n    elif leftmost.startswith('xn--') or hostname.startswith('xn--'):\n        # RFC 6125, section 6.4.3, subitem 3.\n        # The client SHOULD NOT attempt to match a presented identifier\n        # where the wildcard character is embedded within an A-label or\n        # U-label of an internationalized domain name.\n        pats.append(re.escape(leftmost))\n    else:\n        # Otherwise, '*' matches any dotless string, e.g. www*\n        pats.append(re.escape(leftmost).replace(r'\\*', '[^.]*'))\n\n    # add the remaining fragments, ignore any wildcards\n    for frag in remainder:\n        pats.append(re.escape(frag))\n\n    pat = re.compile(r'\\A' + r'\\.'.join(pats) + r'\\Z', re.IGNORECASE)\n    return pat.match(hostname)\n\n\ndef _ipaddress_match(ipname, host_ip):\n    \"\"\"Exact matching of IP addresses.\n\n    RFC 6125 explicitly doesn't define an algorithm for this\n    (section 1.7.2 - \"Out of Scope\").\n    \"\"\"\n    # OpenSSL may add a trailing newline to a subjectAltName's IP address\n    ip = ip_address(_unicode(ipname).rstrip())\n    return ip == host_ip\n\n\ndef match_hostname(cert, hostname):\n    \"\"\"Verify that *cert* (in decoded format as returned by\n    SSLSocket.getpeercert()) matches the *hostname*.  RFC 2818 and RFC 6125\n    rules are followed.\n\n    CertificateError is raised on failure. On success, the function\n    returns nothing.\n    \"\"\"\n    if not cert:\n        raise ValueError(\"empty or no certificate, match_hostname needs a \"\n                         \"SSL socket or SSL context with either \"\n                         \"CERT_OPTIONAL or CERT_REQUIRED\")\n    try:\n        host_ip = ip_address(_unicode(hostname))\n    except (ValueError, UnicodeError):\n        # Not an IP address (common case)\n        host_ip = None\n    dnsnames = []\n    san = cert.get('subjectAltName', ())\n    for key, value in san:\n        if key == 'DNS':\n            if host_ip is None and _dnsname_match(value, hostname):\n                return\n            dnsnames.append(value)\n        elif key == 'IP Address':\n            if host_ip is not None and _ipaddress_match(value, host_ip):\n                return\n            dnsnames.append(value)\n    if not dnsnames:\n        # The subject is only checked when there is no dNSName entry\n        # in subjectAltName\n        for sub in cert.get('subject', ()):\n            for key, value in sub:\n                # XXX according to RFC 2818, the most specific Common Name\n                # must be used.\n                if key == 'commonName':\n                    if _dnsname_match(value, hostname):\n                        return\n                    dnsnames.append(value)\n    if len(dnsnames) > 1:\n        raise CertificateError(\"hostname %r \"\n            \"doesn't match either of %s\"\n            % (hostname, ', '.join(map(repr, dnsnames))))\n    elif len(dnsnames) == 1:\n        raise CertificateError(\"hostname %r \"\n            \"doesn't match %r\"\n            % (hostname, dnsnames[0]))\n    else:\n        raise CertificateError(\"no appropriate commonName or \"\n            \"subjectAltName fields were found\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/ssl_support.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Support for SSL in PyMongo.\"\"\"\n\nimport atexit\nimport sys\nimport threading\n\nHAVE_SSL = True\ntry:\n    import ssl\nexcept ImportError:\n    HAVE_SSL = False\n\nHAVE_CERTIFI = False\ntry:\n    import certifi\n    HAVE_CERTIFI = True\nexcept ImportError:\n    pass\n\nHAVE_WINCERTSTORE = False\ntry:\n    from wincertstore import CertFile\n    HAVE_WINCERTSTORE = True\nexcept ImportError:\n    pass\n\nfrom bson.py3compat import string_type\nfrom pymongo.errors import ConfigurationError\n\n_WINCERTSLOCK = threading.Lock()\n_WINCERTS = None\n\n_PY37PLUS = sys.version_info[:2] >= (3, 7)\n\nif HAVE_SSL:\n    try:\n        # Python 2.7.9+, PyPy 2.5.1+, etc.\n        from ssl import SSLContext\n    except ImportError:\n        from pymongo.ssl_context import SSLContext\n\n    def validate_cert_reqs(option, value):\n        \"\"\"Validate the cert reqs are valid. It must be None or one of the\n        three values ``ssl.CERT_NONE``, ``ssl.CERT_OPTIONAL`` or\n        ``ssl.CERT_REQUIRED``.\n        \"\"\"\n        if value is None:\n            return value\n        elif isinstance(value, string_type) and hasattr(ssl, value):\n            value = getattr(ssl, value)\n\n        if value in (ssl.CERT_NONE, ssl.CERT_OPTIONAL, ssl.CERT_REQUIRED):\n            return value\n        raise ValueError(\"The value of %s must be one of: \"\n                         \"`ssl.CERT_NONE`, `ssl.CERT_OPTIONAL` or \"\n                         \"`ssl.CERT_REQUIRED`\" % (option,))\n\n    def validate_allow_invalid_certs(option, value):\n        \"\"\"Validate the option to allow invalid certificates is valid.\"\"\"\n        # Avoid circular import.\n        from pymongo.common import validate_boolean_or_string\n        boolean_cert_reqs = validate_boolean_or_string(option, value)\n        if boolean_cert_reqs:\n            return ssl.CERT_NONE\n        return ssl.CERT_REQUIRED\n\n    def _load_wincerts():\n        \"\"\"Set _WINCERTS to an instance of wincertstore.Certfile.\"\"\"\n        global _WINCERTS\n\n        certfile = CertFile()\n        certfile.addstore(\"CA\")\n        certfile.addstore(\"ROOT\")\n        atexit.register(certfile.close)\n\n        _WINCERTS = certfile\n\n    # XXX: Possible future work.\n    # - OCSP? Not supported by python at all.\n    #   http://bugs.python.org/issue17123\n    # - Adding an ssl_context keyword argument to MongoClient? This might\n    #   be useful for sites that have unusual requirements rather than\n    #   trying to expose every SSLContext option through a keyword/uri\n    #   parameter.\n    def get_ssl_context(*args):\n        \"\"\"Create and return an SSLContext object.\"\"\"\n        (certfile,\n         keyfile,\n         passphrase,\n         ca_certs,\n         cert_reqs,\n         crlfile,\n         match_hostname) = args\n        verify_mode = ssl.CERT_REQUIRED if cert_reqs is None else cert_reqs\n        # Note PROTOCOL_SSLv23 is about the most misleading name imaginable.\n        # This configures the server and client to negotiate the\n        # highest protocol version they both support. A very good thing.\n        # PROTOCOL_TLS_CLIENT was added in CPython 3.6, deprecating\n        # PROTOCOL_SSLv23.\n        ctx = SSLContext(\n            getattr(ssl, \"PROTOCOL_TLS_CLIENT\", ssl.PROTOCOL_SSLv23))\n        # SSLContext.check_hostname was added in CPython 2.7.9 and 3.4.\n        # PROTOCOL_TLS_CLIENT (added in Python 3.6) enables it by default.\n        if hasattr(ctx, \"check_hostname\"):\n            if _PY37PLUS and verify_mode != ssl.CERT_NONE:\n                # Python 3.7 uses OpenSSL's hostname matching implementation\n                # making it the obvious version to start using this with.\n                # Python 3.6 might have been a good version, but it suffers\n                # from https://bugs.python.org/issue32185.\n                # We'll use our bundled match_hostname for older Python\n                # versions, which also supports IP address matching\n                # with Python < 3.5.\n                ctx.check_hostname = match_hostname\n            else:\n                ctx.check_hostname = False\n        if hasattr(ctx, \"options\"):\n            # Explicitly disable SSLv2, SSLv3 and TLS compression. Note that\n            # up to date versions of MongoDB 2.4 and above already disable\n            # SSLv2 and SSLv3, python disables SSLv2 by default in >= 2.7.7\n            # and >= 3.3.4 and SSLv3 in >= 3.4.3. There is no way for us to do\n            # any of this explicitly for python 2.7 before 2.7.9.\n            ctx.options |= getattr(ssl, \"OP_NO_SSLv2\", 0)\n            ctx.options |= getattr(ssl, \"OP_NO_SSLv3\", 0)\n            # OpenSSL >= 1.0.0\n            ctx.options |= getattr(ssl, \"OP_NO_COMPRESSION\", 0)\n            # Python 3.7+ with OpenSSL >= 1.1.0h\n            ctx.options |= getattr(ssl, \"OP_NO_RENEGOTIATION\", 0)\n        if certfile is not None:\n            try:\n                if passphrase is not None:\n                    vi = sys.version_info\n                    # Since python just added a new parameter to an existing method\n                    # this seems to be about the best we can do.\n                    if (vi[0] == 2 and vi < (2, 7, 9) or\n                            vi[0] == 3 and vi < (3, 3)):\n                        raise ConfigurationError(\n                            \"Support for ssl_pem_passphrase requires \"\n                            \"python 2.7.9+ (pypy 2.5.1+) or 3.3+\")\n                    ctx.load_cert_chain(certfile, keyfile, passphrase)\n                else:\n                    ctx.load_cert_chain(certfile, keyfile)\n            except ssl.SSLError as exc:\n                raise ConfigurationError(\n                    \"Private key doesn't match certificate: %s\" % (exc,))\n        if crlfile is not None:\n            if not hasattr(ctx, \"verify_flags\"):\n                raise ConfigurationError(\n                    \"Support for ssl_crlfile requires \"\n                    \"python 2.7.9+ (pypy 2.5.1+) or  3.4+\")\n            # Match the server's behavior.\n            ctx.verify_flags = ssl.VERIFY_CRL_CHECK_LEAF\n            ctx.load_verify_locations(crlfile)\n        if ca_certs is not None:\n            ctx.load_verify_locations(ca_certs)\n        elif cert_reqs != ssl.CERT_NONE:\n            # CPython >= 2.7.9 or >= 3.4.0, pypy >= 2.5.1\n            if hasattr(ctx, \"load_default_certs\"):\n                ctx.load_default_certs()\n            # Python >= 3.2.0, useless on Windows.\n            elif (sys.platform != \"win32\" and\n                  hasattr(ctx, \"set_default_verify_paths\")):\n                ctx.set_default_verify_paths()\n            elif sys.platform == \"win32\" and HAVE_WINCERTSTORE:\n                with _WINCERTSLOCK:\n                    if _WINCERTS is None:\n                        _load_wincerts()\n                ctx.load_verify_locations(_WINCERTS.name)\n            elif HAVE_CERTIFI:\n                ctx.load_verify_locations(certifi.where())\n            else:\n                raise ConfigurationError(\n                    \"`ssl_cert_reqs` is not ssl.CERT_NONE and no system \"\n                    \"CA certificates could be loaded. `ssl_ca_certs` is \"\n                    \"required.\")\n        ctx.verify_mode = verify_mode\n        return ctx\nelse:\n    def validate_cert_reqs(option, dummy):\n        \"\"\"No ssl module, raise ConfigurationError.\"\"\"\n        raise ConfigurationError(\"The value of %s is set but can't be \"\n                                 \"validated. The ssl module is not available\"\n                                 % (option,))\n\n    def validate_allow_invalid_certs(option, dummy):\n        \"\"\"No ssl module, raise ConfigurationError.\"\"\"\n        return validate_cert_reqs(option, dummy)\n\n    def get_ssl_context(*dummy):\n        \"\"\"No ssl module, raise ConfigurationError.\"\"\"\n        raise ConfigurationError(\"The ssl module is not available.\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/thread_util.py",
    "content": "# Copyright 2012-2015 MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Utilities for multi-threading support.\"\"\"\n\nimport threading\ntry:\n    from time import monotonic as _time\nexcept ImportError:\n    from time import time as _time\n\nfrom pymongo.monotonic import time as _time\nfrom pymongo.errors import ExceededMaxWaiters\n\n\n### Begin backport from CPython 3.2 for timeout support for Semaphore.acquire\nclass Semaphore:\n\n    # After Tim Peters' semaphore class, but not quite the same (no maximum)\n\n    def __init__(self, value=1):\n        if value < 0:\n            raise ValueError(\"semaphore initial value must be >= 0\")\n        self._cond = threading.Condition(threading.Lock())\n        self._value = value\n\n    def acquire(self, blocking=True, timeout=None):\n        if not blocking and timeout is not None:\n            raise ValueError(\"can't specify timeout for non-blocking acquire\")\n        rc = False\n        endtime = None\n        self._cond.acquire()\n        while self._value == 0:\n            if not blocking:\n                break\n            if timeout is not None:\n                if endtime is None:\n                    endtime = _time() + timeout\n                else:\n                    timeout = endtime - _time()\n                    if timeout <= 0:\n                        break\n            self._cond.wait(timeout)\n        else:\n            self._value = self._value - 1\n            rc = True\n        self._cond.release()\n        return rc\n\n    __enter__ = acquire\n\n    def release(self):\n        self._cond.acquire()\n        self._value = self._value + 1\n        self._cond.notify()\n        self._cond.release()\n\n    def __exit__(self, t, v, tb):\n        self.release()\n\n    @property\n    def counter(self):\n        return self._value\n\n\nclass BoundedSemaphore(Semaphore):\n    \"\"\"Semaphore that checks that # releases is <= # acquires\"\"\"\n    def __init__(self, value=1):\n        Semaphore.__init__(self, value)\n        self._initial_value = value\n\n    def release(self):\n        if self._value >= self._initial_value:\n            raise ValueError(\"Semaphore released too many times\")\n        return Semaphore.release(self)\n### End backport from CPython 3.2\n\n\nclass DummySemaphore(object):\n    def __init__(self, value=None):\n        pass\n\n    def acquire(self, blocking=True, timeout=None):\n        return True\n\n    def release(self):\n        pass\n\n\nclass MaxWaitersBoundedSemaphore(object):\n    def __init__(self, semaphore_class, value=1, max_waiters=1):\n        self.waiter_semaphore = semaphore_class(max_waiters)\n        self.semaphore = semaphore_class(value)\n\n    def acquire(self, blocking=True, timeout=None):\n        if not self.waiter_semaphore.acquire(False):\n            raise ExceededMaxWaiters()\n        try:\n            return self.semaphore.acquire(blocking, timeout)\n        finally:\n            self.waiter_semaphore.release()\n\n    def __getattr__(self, name):\n        return getattr(self.semaphore, name)\n\n\nclass MaxWaitersBoundedSemaphoreThread(MaxWaitersBoundedSemaphore):\n    def __init__(self, value=1, max_waiters=1):\n        MaxWaitersBoundedSemaphore.__init__(\n            self, BoundedSemaphore, value, max_waiters)\n\n\ndef create_semaphore(max_size, max_waiters):\n    if max_size is None:\n        return DummySemaphore()\n    else:\n        if max_waiters is None:\n            return BoundedSemaphore(max_size)\n        else:\n            return MaxWaitersBoundedSemaphoreThread(max_size, max_waiters)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/topology.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Internal class to monitor a topology of one or more servers.\"\"\"\n\nimport os\nimport random\nimport threading\nimport warnings\nimport weakref\n\nfrom bson.py3compat import itervalues, PY3\nif PY3:\n    import queue as Queue\nelse:\n    import Queue\n\nfrom pymongo import common\nfrom pymongo import periodic_executor\nfrom pymongo.pool import PoolOptions\nfrom pymongo.topology_description import (updated_topology_description,\n                                          _updated_topology_description_srv_polling,\n                                          TopologyDescription,\n                                          SRV_POLLING_TOPOLOGIES, TOPOLOGY_TYPE)\nfrom pymongo.errors import ServerSelectionTimeoutError, ConfigurationError\nfrom pymongo.monitor import SrvMonitor\nfrom pymongo.monotonic import time as _time\nfrom pymongo.server import Server\nfrom pymongo.server_selectors import (any_server_selector,\n                                      arbiter_server_selector,\n                                      secondary_server_selector,\n                                      readable_server_selector,\n                                      writable_server_selector,\n                                      Selection)\nfrom pymongo.client_session import _ServerSessionPool\n\n\ndef process_events_queue(queue_ref):\n    q = queue_ref()\n    if not q:\n        return False  # Cancel PeriodicExecutor.\n\n    while True:\n        try:\n            event = q.get_nowait()\n        except Queue.Empty:\n            break\n        else:\n            fn, args = event\n            fn(*args)\n\n    return True  # Continue PeriodicExecutor.\n\n\nclass Topology(object):\n    \"\"\"Monitor a topology of one or more servers.\"\"\"\n    def __init__(self, topology_settings):\n        self._topology_id = topology_settings._topology_id\n        self._listeners = topology_settings._pool_options.event_listeners\n        pub = self._listeners is not None\n        self._publish_server = pub and self._listeners.enabled_for_server\n        self._publish_tp = pub and self._listeners.enabled_for_topology\n\n        # Create events queue if there are publishers.\n        self._events = None\n        self.__events_executor = None\n\n        if self._publish_server or self._publish_tp:\n            self._events = Queue.Queue(maxsize=100)\n\n        if self._publish_tp:\n            self._events.put((self._listeners.publish_topology_opened,\n                             (self._topology_id,)))\n        self._settings = topology_settings\n        topology_description = TopologyDescription(\n            topology_settings.get_topology_type(),\n            topology_settings.get_server_descriptions(),\n            topology_settings.replica_set_name,\n            None,\n            None,\n            topology_settings)\n\n        self._description = topology_description\n        if self._publish_tp:\n            initial_td = TopologyDescription(TOPOLOGY_TYPE.Unknown, {}, None,\n                                             None, None, self._settings)\n            self._events.put((\n                self._listeners.publish_topology_description_changed,\n                (initial_td, self._description, self._topology_id)))\n\n        for seed in topology_settings.seeds:\n            if self._publish_server:\n                self._events.put((self._listeners.publish_server_opened,\n                                 (seed, self._topology_id)))\n\n        # Store the seed list to help diagnose errors in _error_message().\n        self._seed_addresses = list(topology_description.server_descriptions())\n        self._opened = False\n        self._lock = threading.Lock()\n        self._condition = self._settings.condition_class(self._lock)\n        self._servers = {}\n        self._pid = None\n        self._max_cluster_time = None\n        self._session_pool = _ServerSessionPool()\n\n        if self._publish_server or self._publish_tp:\n            def target():\n                return process_events_queue(weak)\n\n            executor = periodic_executor.PeriodicExecutor(\n                interval=common.EVENTS_QUEUE_FREQUENCY,\n                min_interval=0.5,\n                target=target,\n                name=\"pymongo_events_thread\")\n\n            # We strongly reference the executor and it weakly references\n            # the queue via this closure. When the topology is freed, stop\n            # the executor soon.\n            weak = weakref.ref(self._events, executor.close)\n            self.__events_executor = executor\n            executor.open()\n\n        self._srv_monitor = None\n        if self._settings.fqdn is not None:\n            self._srv_monitor = SrvMonitor(self, self._settings)\n\n    def open(self):\n        \"\"\"Start monitoring, or restart after a fork.\n\n        No effect if called multiple times.\n\n        .. warning:: Topology is shared among multiple threads and is protected\n          by mutual exclusion. Using Topology from a process other than the one\n          that initialized it will emit a warning and may result in deadlock. To\n          prevent this from happening, MongoClient must be created after any\n          forking.\n\n        \"\"\"\n        if self._pid is None:\n            self._pid = os.getpid()\n        else:\n            if os.getpid() != self._pid:\n                warnings.warn(\n                    \"MongoClient opened before fork. Create MongoClient only \"\n                    \"after forking. See PyMongo's documentation for details: \"\n                    \"http://api.mongodb.org/python/current/faq.html#\"\n                    \"is-pymongo-fork-safe\")\n\n        with self._lock:\n            self._ensure_opened()\n\n    def select_servers(self,\n                       selector,\n                       server_selection_timeout=None,\n                       address=None):\n        \"\"\"Return a list of Servers matching selector, or time out.\n\n        :Parameters:\n          - `selector`: function that takes a list of Servers and returns\n            a subset of them.\n          - `server_selection_timeout` (optional): maximum seconds to wait.\n            If not provided, the default value common.SERVER_SELECTION_TIMEOUT\n            is used.\n          - `address`: optional server address to select.\n\n        Calls self.open() if needed.\n\n        Raises exc:`ServerSelectionTimeoutError` after\n        `server_selection_timeout` if no matching servers are found.\n        \"\"\"\n        if server_selection_timeout is None:\n            server_timeout = self._settings.server_selection_timeout\n        else:\n            server_timeout = server_selection_timeout\n\n        with self._lock:\n            server_descriptions = self._select_servers_loop(\n                selector, server_timeout, address)\n\n            return [self.get_server_by_address(sd.address)\n                    for sd in server_descriptions]\n\n    def _select_servers_loop(self, selector, timeout, address):\n        \"\"\"select_servers() guts. Hold the lock when calling this.\"\"\"\n        now = _time()\n        end_time = now + timeout\n        server_descriptions = self._description.apply_selector(\n            selector, address, custom_selector=self._settings.server_selector)\n\n        while not server_descriptions:\n            # No suitable servers.\n            if timeout == 0 or now > end_time:\n                raise ServerSelectionTimeoutError(\n                    self._error_message(selector))\n\n            self._ensure_opened()\n            self._request_check_all()\n\n            # Release the lock and wait for the topology description to\n            # change, or for a timeout. We won't miss any changes that\n            # came after our most recent apply_selector call, since we've\n            # held the lock until now.\n            self._condition.wait(common.MIN_HEARTBEAT_INTERVAL)\n            self._description.check_compatible()\n            now = _time()\n            server_descriptions = self._description.apply_selector(\n                selector, address,\n                custom_selector=self._settings.server_selector)\n\n        self._description.check_compatible()\n        return server_descriptions\n\n    def select_server(self,\n                      selector,\n                      server_selection_timeout=None,\n                      address=None):\n        \"\"\"Like select_servers, but choose a random server if several match.\"\"\"\n        return random.choice(self.select_servers(selector,\n                                                 server_selection_timeout,\n                                                 address))\n\n    def select_server_by_address(self, address,\n                                 server_selection_timeout=None):\n        \"\"\"Return a Server for \"address\", reconnecting if necessary.\n\n        If the server's type is not known, request an immediate check of all\n        servers. Time out after \"server_selection_timeout\" if the server\n        cannot be reached.\n\n        :Parameters:\n          - `address`: A (host, port) pair.\n          - `server_selection_timeout` (optional): maximum seconds to wait.\n            If not provided, the default value\n            common.SERVER_SELECTION_TIMEOUT is used.\n\n        Calls self.open() if needed.\n\n        Raises exc:`ServerSelectionTimeoutError` after\n        `server_selection_timeout` if no matching servers are found.\n        \"\"\"\n        return self.select_server(any_server_selector,\n                                  server_selection_timeout,\n                                  address)\n\n    def _process_change(self, server_description):\n        \"\"\"Process a new ServerDescription on an opened topology.\n\n        Hold the lock when calling this.\n        \"\"\"\n        td_old = self._description\n        if self._publish_server:\n            old_server_description = td_old._server_descriptions[\n                server_description.address]\n            self._events.put((\n                self._listeners.publish_server_description_changed,\n                (old_server_description, server_description,\n                 server_description.address, self._topology_id)))\n\n        self._description = updated_topology_description(\n            self._description, server_description)\n\n        self._update_servers()\n        self._receive_cluster_time_no_lock(server_description.cluster_time)\n\n        if self._publish_tp:\n            self._events.put((\n                self._listeners.publish_topology_description_changed,\n                (td_old, self._description, self._topology_id)))\n\n        # Shutdown SRV polling for unsupported cluster types.\n        # This is only applicable if the old topology was Unknown, and the\n        # new one is something other than Unknown or Sharded.\n        if self._srv_monitor and (td_old.topology_type == TOPOLOGY_TYPE.Unknown\n                                  and self._description.topology_type not in\n                                  SRV_POLLING_TOPOLOGIES):\n            self._srv_monitor.close()\n\n        # Wake waiters in select_servers().\n        self._condition.notify_all()\n\n    def on_change(self, server_description):\n        \"\"\"Process a new ServerDescription after an ismaster call completes.\"\"\"\n        # We do no I/O holding the lock.\n        with self._lock:\n            # Monitors may continue working on ismaster calls for some time\n            # after a call to Topology.close, so this method may be called at\n            # any time. Ensure the topology is open before processing the\n            # change.\n            # Any monitored server was definitely in the topology description\n            # once. Check if it's still in the description or if some state-\n            # change removed it. E.g., we got a host list from the primary\n            # that didn't include this server.\n            if (self._opened and\n                    self._description.has_server(server_description.address)):\n                self._process_change(server_description)\n\n    def _process_srv_update(self, seedlist):\n        \"\"\"Process a new seedlist on an opened topology.\n        Hold the lock when calling this.\n        \"\"\"\n        td_old = self._description\n        self._description = _updated_topology_description_srv_polling(\n            self._description, seedlist)\n\n        self._update_servers()\n\n        if self._publish_tp:\n            self._events.put((\n                self._listeners.publish_topology_description_changed,\n                (td_old, self._description, self._topology_id)))\n\n    def on_srv_update(self, seedlist):\n        \"\"\"Process a new list of nodes obtained from scanning SRV records.\"\"\"\n        # We do no I/O holding the lock.\n        with self._lock:\n            if self._opened:\n                self._process_srv_update(seedlist)\n\n    def get_server_by_address(self, address):\n        \"\"\"Get a Server or None.\n\n        Returns the current version of the server immediately, even if it's\n        Unknown or absent from the topology. Only use this in unittests.\n        In driver code, use select_server_by_address, since then you're\n        assured a recent view of the server's type and wire protocol version.\n        \"\"\"\n        return self._servers.get(address)\n\n    def has_server(self, address):\n        return address in self._servers\n\n    def get_primary(self):\n        \"\"\"Return primary's address or None.\"\"\"\n        # Implemented here in Topology instead of MongoClient, so it can lock.\n        with self._lock:\n            topology_type = self._description.topology_type\n            if topology_type != TOPOLOGY_TYPE.ReplicaSetWithPrimary:\n                return None\n\n            return writable_server_selector(self._new_selection())[0].address\n\n    def _get_replica_set_members(self, selector):\n        \"\"\"Return set of replica set member addresses.\"\"\"\n        # Implemented here in Topology instead of MongoClient, so it can lock.\n        with self._lock:\n            topology_type = self._description.topology_type\n            if topology_type not in (TOPOLOGY_TYPE.ReplicaSetWithPrimary,\n                                     TOPOLOGY_TYPE.ReplicaSetNoPrimary):\n                return set()\n\n            return set([sd.address for sd in selector(self._new_selection())])\n\n    def get_secondaries(self):\n        \"\"\"Return set of secondary addresses.\"\"\"\n        return self._get_replica_set_members(secondary_server_selector)\n\n    def get_arbiters(self):\n        \"\"\"Return set of arbiter addresses.\"\"\"\n        return self._get_replica_set_members(arbiter_server_selector)\n\n    def max_cluster_time(self):\n        \"\"\"Return a document, the highest seen $clusterTime.\"\"\"\n        return self._max_cluster_time\n\n    def _receive_cluster_time_no_lock(self, cluster_time):\n        # Driver Sessions Spec: \"Whenever a driver receives a cluster time from\n        # a server it MUST compare it to the current highest seen cluster time\n        # for the deployment. If the new cluster time is higher than the\n        # highest seen cluster time it MUST become the new highest seen cluster\n        # time. Two cluster times are compared using only the BsonTimestamp\n        # value of the clusterTime embedded field.\"\n        if cluster_time:\n            # \">\" uses bson.timestamp.Timestamp's comparison operator.\n            if (not self._max_cluster_time\n                or cluster_time['clusterTime'] >\n                    self._max_cluster_time['clusterTime']):\n                self._max_cluster_time = cluster_time\n\n    def receive_cluster_time(self, cluster_time):\n        with self._lock:\n            self._receive_cluster_time_no_lock(cluster_time)\n\n    def request_check_all(self, wait_time=5):\n        \"\"\"Wake all monitors, wait for at least one to check its server.\"\"\"\n        with self._lock:\n            self._request_check_all()\n            self._condition.wait(wait_time)\n\n    def reset_pool(self, address):\n        with self._lock:\n            server = self._servers.get(address)\n            if server:\n                server.pool.reset()\n\n    def reset_server(self, address):\n        \"\"\"Clear our pool for a server and mark it Unknown.\n\n        Do *not* request an immediate check.\n        \"\"\"\n        with self._lock:\n            self._reset_server(address, reset_pool=True)\n\n    def reset_server_and_request_check(self, address):\n        \"\"\"Clear our pool for a server, mark it Unknown, and check it soon.\"\"\"\n        with self._lock:\n            self._reset_server(address, reset_pool=True)\n            self._request_check(address)\n\n    def mark_server_unknown_and_request_check(self, address):\n        \"\"\"Mark a server Unknown, and check it soon.\"\"\"\n        with self._lock:\n            self._reset_server(address, reset_pool=False)\n            self._request_check(address)\n\n    def update_pool(self):\n        # Remove any stale sockets and add new sockets if pool is too small.\n        with self._lock:\n            for server in self._servers.values():\n                server._pool.remove_stale_sockets()\n\n    def close(self):\n        \"\"\"Clear pools and terminate monitors. Topology reopens on demand.\"\"\"\n        with self._lock:\n            for server in self._servers.values():\n                server.close()\n\n            # Mark all servers Unknown.\n            self._description = self._description.reset()\n            for address, sd in self._description.server_descriptions().items():\n                if address in self._servers:\n                    self._servers[address].description = sd\n\n            # Stop SRV polling thread.\n            if self._srv_monitor:\n                self._srv_monitor.close()\n\n            self._opened = False\n\n        # Publish only after releasing the lock.\n        if self._publish_tp:\n            self._events.put((self._listeners.publish_topology_closed,\n                              (self._topology_id,)))\n        if self._publish_server or self._publish_tp:\n            self.__events_executor.close()\n\n    @property\n    def description(self):\n        return self._description\n\n    def pop_all_sessions(self):\n        \"\"\"Pop all session ids from the pool.\"\"\"\n        with self._lock:\n            return self._session_pool.pop_all()\n\n    def get_server_session(self):\n        \"\"\"Start or resume a server session, or raise ConfigurationError.\"\"\"\n        with self._lock:\n            session_timeout = self._description.logical_session_timeout_minutes\n            if session_timeout is None:\n                # Maybe we need an initial scan? Can raise ServerSelectionError.\n                if self._description.topology_type == TOPOLOGY_TYPE.Single:\n                    if not self._description.has_known_servers:\n                        self._select_servers_loop(\n                            any_server_selector,\n                            self._settings.server_selection_timeout,\n                            None)\n                elif not self._description.readable_servers:\n                    self._select_servers_loop(\n                        readable_server_selector,\n                        self._settings.server_selection_timeout,\n                        None)\n\n            session_timeout = self._description.logical_session_timeout_minutes\n            if session_timeout is None:\n                raise ConfigurationError(\n                    \"Sessions are not supported by this MongoDB deployment\")\n\n            return self._session_pool.get_server_session(session_timeout)\n\n    def return_server_session(self, server_session, lock):\n        if lock:\n            with self._lock:\n                session_timeout = \\\n                    self._description.logical_session_timeout_minutes\n                if session_timeout is not None:\n                    self._session_pool.return_server_session(server_session,\n                                                             session_timeout)\n        else:\n            # Called from a __del__ method, can't use a lock.\n            self._session_pool.return_server_session_no_lock(server_session)\n\n    def _new_selection(self):\n        \"\"\"A Selection object, initially including all known servers.\n\n        Hold the lock when calling this.\n        \"\"\"\n        return Selection.from_topology_description(self._description)\n\n    def _ensure_opened(self):\n        \"\"\"Start monitors, or restart after a fork.\n\n        Hold the lock when calling this.\n        \"\"\"\n        if not self._opened:\n            self._opened = True\n            self._update_servers()\n\n            # Start or restart the events publishing thread.\n            if self._publish_tp or self._publish_server:\n                self.__events_executor.open()\n\n            # Start the SRV polling thread.\n            if self._srv_monitor and (self.description.topology_type in\n                                      SRV_POLLING_TOPOLOGIES):\n                self._srv_monitor.open()\n\n        # Ensure that the monitors are open.\n        for server in itervalues(self._servers):\n            server.open()\n\n    def _reset_server(self, address, reset_pool):\n        \"\"\"Mark a server Unknown and optionally reset it's pool.\n\n        Hold the lock when calling this. Does *not* request an immediate check.\n        \"\"\"\n        server = self._servers.get(address)\n\n        # \"server\" is None if another thread removed it from the topology.\n        if server:\n            if reset_pool:\n                server.reset()\n\n            # Mark this server Unknown.\n            self._description = self._description.reset_server(address)\n            self._update_servers()\n\n    def _request_check(self, address):\n        \"\"\"Wake one monitor. Hold the lock when calling this.\"\"\"\n        server = self._servers.get(address)\n\n        # \"server\" is None if another thread removed it from the topology.\n        if server:\n            server.request_check()\n\n    def _request_check_all(self):\n        \"\"\"Wake all monitors. Hold the lock when calling this.\"\"\"\n        for server in self._servers.values():\n            server.request_check()\n\n    def _update_servers(self):\n        \"\"\"Sync our Servers from TopologyDescription.server_descriptions.\n\n        Hold the lock while calling this.\n        \"\"\"\n        for address, sd in self._description.server_descriptions().items():\n            if address not in self._servers:\n                monitor = self._settings.monitor_class(\n                    server_description=sd,\n                    topology=self,\n                    pool=self._create_pool_for_monitor(address),\n                    topology_settings=self._settings)\n\n                weak = None\n                if self._publish_server:\n                    weak = weakref.ref(self._events)\n                server = Server(\n                    server_description=sd,\n                    pool=self._create_pool_for_server(address),\n                    monitor=monitor,\n                    topology_id=self._topology_id,\n                    listeners=self._listeners,\n                    events=weak)\n\n                self._servers[address] = server\n                server.open()\n            else:\n                # Cache old is_writable value.\n                was_writable = self._servers[address].description.is_writable\n                # Update server description.\n                self._servers[address].description = sd\n                # Update is_writable value of the pool, if it changed.\n                if was_writable != sd.is_writable:\n                    self._servers[address].pool.update_is_writable(\n                        sd.is_writable)\n\n        for address, server in list(self._servers.items()):\n            if not self._description.has_server(address):\n                server.close()\n                self._servers.pop(address)\n\n    def _create_pool_for_server(self, address):\n        return self._settings.pool_class(address, self._settings.pool_options)\n\n    def _create_pool_for_monitor(self, address):\n        options = self._settings.pool_options\n\n        # According to the Server Discovery And Monitoring Spec, monitors use\n        # connect_timeout for both connect_timeout and socket_timeout. The\n        # pool only has one socket so maxPoolSize and so on aren't needed.\n        monitor_pool_options = PoolOptions(\n            connect_timeout=options.connect_timeout,\n            socket_timeout=options.connect_timeout,\n            ssl_context=options.ssl_context,\n            ssl_match_hostname=options.ssl_match_hostname,\n            event_listeners=options.event_listeners,\n            appname=options.appname,\n            driver=options.driver)\n\n        return self._settings.pool_class(address, monitor_pool_options,\n                                         handshake=False)\n\n    def _error_message(self, selector):\n        \"\"\"Format an error message if server selection fails.\n\n        Hold the lock when calling this.\n        \"\"\"\n        is_replica_set = self._description.topology_type in (\n            TOPOLOGY_TYPE.ReplicaSetWithPrimary,\n            TOPOLOGY_TYPE.ReplicaSetNoPrimary)\n\n        if is_replica_set:\n            server_plural = 'replica set members'\n        elif self._description.topology_type == TOPOLOGY_TYPE.Sharded:\n            server_plural = 'mongoses'\n        else:\n            server_plural = 'servers'\n\n        if self._description.known_servers:\n            # We've connected, but no servers match the selector.\n            if selector is writable_server_selector:\n                if is_replica_set:\n                    return 'No primary available for writes'\n                else:\n                    return 'No %s available for writes' % server_plural\n            else:\n                return 'No %s match selector \"%s\"' % (server_plural, selector)\n        else:\n            addresses = list(self._description.server_descriptions())\n            servers = list(self._description.server_descriptions().values())\n            if not servers:\n                if is_replica_set:\n                    # We removed all servers because of the wrong setName?\n                    return 'No %s available for replica set name \"%s\"' % (\n                        server_plural, self._settings.replica_set_name)\n                else:\n                    return 'No %s available' % server_plural\n\n            # 1 or more servers, all Unknown. Are they unknown for one reason?\n            error = servers[0].error\n            same = all(server.error == error for server in servers[1:])\n            if same:\n                if error is None:\n                    # We're still discovering.\n                    return 'No %s found yet' % server_plural\n\n                if (is_replica_set and not\n                        set(addresses).intersection(self._seed_addresses)):\n                    # We replaced our seeds with new hosts but can't reach any.\n                    return (\n                        'Could not reach any servers in %s. Replica set is'\n                        ' configured with internal hostnames or IPs?' %\n                        addresses)\n\n                return str(error)\n            else:\n                return ','.join(str(server.error) for server in servers\n                                if server.error)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/topology_description.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\"\"\"Represent a deployment of MongoDB servers.\"\"\"\n\nfrom collections import namedtuple\n\nfrom pymongo import common\nfrom pymongo.errors import ConfigurationError\nfrom pymongo.read_preferences import ReadPreference\nfrom pymongo.server_description import ServerDescription\nfrom pymongo.server_selectors import Selection\nfrom pymongo.server_type import SERVER_TYPE\n\n\n# Enumeration for various kinds of MongoDB cluster topologies.\nTOPOLOGY_TYPE = namedtuple('TopologyType', ['Single', 'ReplicaSetNoPrimary',\n                                            'ReplicaSetWithPrimary', 'Sharded',\n                                            'Unknown'])(*range(5))\n\n# Topologies compatible with SRV record polling.\nSRV_POLLING_TOPOLOGIES = (TOPOLOGY_TYPE.Unknown, TOPOLOGY_TYPE.Sharded)\n\n\nclass TopologyDescription(object):\n    def __init__(self,\n                 topology_type,\n                 server_descriptions,\n                 replica_set_name,\n                 max_set_version,\n                 max_election_id,\n                 topology_settings):\n        \"\"\"Representation of a deployment of MongoDB servers.\n\n        :Parameters:\n          - `topology_type`: initial type\n          - `server_descriptions`: dict of (address, ServerDescription) for\n            all seeds\n          - `replica_set_name`: replica set name or None\n          - `max_set_version`: greatest setVersion seen from a primary, or None\n          - `max_election_id`: greatest electionId seen from a primary, or None\n          - `topology_settings`: a TopologySettings\n        \"\"\"\n        self._topology_type = topology_type\n        self._replica_set_name = replica_set_name\n        self._server_descriptions = server_descriptions\n        self._max_set_version = max_set_version\n        self._max_election_id = max_election_id\n\n        # The heartbeat_frequency is used in staleness estimates.\n        self._topology_settings = topology_settings\n\n        # Is PyMongo compatible with all servers' wire protocols?\n        self._incompatible_err = None\n\n        for s in self._server_descriptions.values():\n            if not s.is_server_type_known:\n                continue\n\n            # s.min/max_wire_version is the server's wire protocol.\n            # MIN/MAX_SUPPORTED_WIRE_VERSION is what PyMongo supports.\n            server_too_new = (\n                # Server too new.\n                s.min_wire_version is not None\n                and s.min_wire_version > common.MAX_SUPPORTED_WIRE_VERSION)\n\n            server_too_old = (\n                # Server too old.\n                s.max_wire_version is not None\n                and s.max_wire_version < common.MIN_SUPPORTED_WIRE_VERSION)\n\n            if server_too_new:\n                self._incompatible_err = (\n                    \"Server at %s:%d requires wire version %d, but this \"\n                    \"version of PyMongo only supports up to %d.\"\n                    % (s.address[0], s.address[1],\n                       s.min_wire_version, common.MAX_SUPPORTED_WIRE_VERSION))\n\n            elif server_too_old:\n                self._incompatible_err = (\n                    \"Server at %s:%d reports wire version %d, but this \"\n                    \"version of PyMongo requires at least %d (MongoDB %s).\"\n                    % (s.address[0], s.address[1],\n                       s.max_wire_version,\n                       common.MIN_SUPPORTED_WIRE_VERSION,\n                       common.MIN_SUPPORTED_SERVER_VERSION))\n\n                break\n\n        # Server Discovery And Monitoring Spec: Whenever a client updates the\n        # TopologyDescription from an ismaster response, it MUST set\n        # TopologyDescription.logicalSessionTimeoutMinutes to the smallest\n        # logicalSessionTimeoutMinutes value among ServerDescriptions of all\n        # data-bearing server types. If any have a null\n        # logicalSessionTimeoutMinutes, then\n        # TopologyDescription.logicalSessionTimeoutMinutes MUST be set to null.\n        readable_servers = self.readable_servers\n        if not readable_servers:\n            self._ls_timeout_minutes = None\n        elif any(s.logical_session_timeout_minutes is None\n                 for s in readable_servers):\n            self._ls_timeout_minutes = None\n        else:\n            self._ls_timeout_minutes = min(s.logical_session_timeout_minutes\n                                           for s in readable_servers)\n\n    def check_compatible(self):\n        \"\"\"Raise ConfigurationError if any server is incompatible.\n\n        A server is incompatible if its wire protocol version range does not\n        overlap with PyMongo's.\n        \"\"\"\n        if self._incompatible_err:\n            raise ConfigurationError(self._incompatible_err)\n\n    def has_server(self, address):\n        return address in self._server_descriptions\n\n    def reset_server(self, address):\n        \"\"\"A copy of this description, with one server marked Unknown.\"\"\"\n        return updated_topology_description(self, ServerDescription(address))\n\n    def reset(self):\n        \"\"\"A copy of this description, with all servers marked Unknown.\"\"\"\n        if self._topology_type == TOPOLOGY_TYPE.ReplicaSetWithPrimary:\n            topology_type = TOPOLOGY_TYPE.ReplicaSetNoPrimary\n        else:\n            topology_type = self._topology_type\n\n        # The default ServerDescription's type is Unknown.\n        sds = dict((address, ServerDescription(address))\n                   for address in self._server_descriptions)\n\n        return TopologyDescription(\n            topology_type,\n            sds,\n            self._replica_set_name,\n            self._max_set_version,\n            self._max_election_id,\n            self._topology_settings)\n\n    def server_descriptions(self):\n        \"\"\"Dict of (address,\n        :class:`~pymongo.server_description.ServerDescription`).\"\"\"\n        return self._server_descriptions.copy()\n\n    @property\n    def topology_type(self):\n        \"\"\"The type of this topology.\"\"\"\n        return self._topology_type\n\n    @property\n    def topology_type_name(self):\n        \"\"\"The topology type as a human readable string.\n\n        .. versionadded:: 3.4\n        \"\"\"\n        return TOPOLOGY_TYPE._fields[self._topology_type]\n\n    @property\n    def replica_set_name(self):\n        \"\"\"The replica set name.\"\"\"\n        return self._replica_set_name\n\n    @property\n    def max_set_version(self):\n        \"\"\"Greatest setVersion seen from a primary, or None.\"\"\"\n        return self._max_set_version\n\n    @property\n    def max_election_id(self):\n        \"\"\"Greatest electionId seen from a primary, or None.\"\"\"\n        return self._max_election_id\n\n    @property\n    def logical_session_timeout_minutes(self):\n        \"\"\"Minimum logical session timeout, or None.\"\"\"\n        return self._ls_timeout_minutes\n\n    @property\n    def known_servers(self):\n        \"\"\"List of Servers of types besides Unknown.\"\"\"\n        return [s for s in self._server_descriptions.values()\n                if s.is_server_type_known]\n\n    @property\n    def has_known_servers(self):\n        \"\"\"Whether there are any Servers of types besides Unknown.\"\"\"\n        return any(s for s in self._server_descriptions.values()\n                   if s.is_server_type_known)\n\n    @property\n    def readable_servers(self):\n        \"\"\"List of readable Servers.\"\"\"\n        return [s for s in self._server_descriptions.values() if s.is_readable]\n\n    @property\n    def common_wire_version(self):\n        \"\"\"Minimum of all servers' max wire versions, or None.\"\"\"\n        servers = self.known_servers\n        if servers:\n            return min(s.max_wire_version for s in self.known_servers)\n\n        return None\n\n    @property\n    def heartbeat_frequency(self):\n        return self._topology_settings.heartbeat_frequency\n\n    def apply_selector(self, selector, address, custom_selector=None):\n\n        def apply_local_threshold(selection):\n            if not selection:\n                return []\n\n            settings = self._topology_settings\n\n            # Round trip time in seconds.\n            fastest = min(\n                s.round_trip_time for s in selection.server_descriptions)\n            threshold = settings.local_threshold_ms / 1000.0\n            return [s for s in selection.server_descriptions\n                    if (s.round_trip_time - fastest) <= threshold]\n\n        if getattr(selector, 'min_wire_version', 0):\n            common_wv = self.common_wire_version\n            if common_wv and common_wv < selector.min_wire_version:\n                raise ConfigurationError(\n                    \"%s requires min wire version %d, but topology's min\"\n                    \" wire version is %d\" % (selector,\n                                             selector.min_wire_version,\n                                             common_wv))\n\n        if self.topology_type == TOPOLOGY_TYPE.Single:\n            # Ignore selectors for standalone.\n            return self.known_servers\n        elif address:\n            # Ignore selectors when explicit address is requested.\n            description = self.server_descriptions().get(address)\n            return [description] if description else []\n        elif self.topology_type == TOPOLOGY_TYPE.Sharded:\n            # Ignore read preference.\n            selection = Selection.from_topology_description(self)\n        else:\n            selection = selector(Selection.from_topology_description(self))\n\n        # Apply custom selector followed by localThresholdMS.\n        if custom_selector is not None and selection:\n            selection = selection.with_server_descriptions(\n                custom_selector(selection.server_descriptions))\n        return apply_local_threshold(selection)\n\n    def has_readable_server(self, read_preference=ReadPreference.PRIMARY):\n        \"\"\"Does this topology have any readable servers available matching the\n        given read preference?\n\n        :Parameters:\n          - `read_preference`: an instance of a read preference from\n            :mod:`~pymongo.read_preferences`. Defaults to\n            :attr:`~pymongo.read_preferences.ReadPreference.PRIMARY`.\n\n        .. note:: When connected directly to a single server this method\n          always returns ``True``.\n\n        .. versionadded:: 3.4\n        \"\"\"\n        common.validate_read_preference(\"read_preference\", read_preference)\n        return any(self.apply_selector(read_preference, None))\n\n    def has_writable_server(self):\n        \"\"\"Does this topology have a writable server available?\n\n        .. note:: When connected directly to a single server this method\n          always returns ``True``.\n\n        .. versionadded:: 3.4\n        \"\"\"\n        return self.has_readable_server(ReadPreference.PRIMARY)\n\n\n# If topology type is Unknown and we receive an ismaster response, what should\n# the new topology type be?\n_SERVER_TYPE_TO_TOPOLOGY_TYPE = {\n    SERVER_TYPE.Mongos: TOPOLOGY_TYPE.Sharded,\n    SERVER_TYPE.RSPrimary: TOPOLOGY_TYPE.ReplicaSetWithPrimary,\n    SERVER_TYPE.RSSecondary: TOPOLOGY_TYPE.ReplicaSetNoPrimary,\n    SERVER_TYPE.RSArbiter: TOPOLOGY_TYPE.ReplicaSetNoPrimary,\n    SERVER_TYPE.RSOther: TOPOLOGY_TYPE.ReplicaSetNoPrimary,\n}\n\n\ndef updated_topology_description(topology_description, server_description):\n    \"\"\"Return an updated copy of a TopologyDescription.\n\n    :Parameters:\n      - `topology_description`: the current TopologyDescription\n      - `server_description`: a new ServerDescription that resulted from\n        an ismaster call\n\n    Called after attempting (successfully or not) to call ismaster on the\n    server at server_description.address. Does not modify topology_description.\n    \"\"\"\n    address = server_description.address\n\n    # These values will be updated, if necessary, to form the new\n    # TopologyDescription.\n    topology_type = topology_description.topology_type\n    set_name = topology_description.replica_set_name\n    max_set_version = topology_description.max_set_version\n    max_election_id = topology_description.max_election_id\n    server_type = server_description.server_type\n\n    # Don't mutate the original dict of server descriptions; copy it.\n    sds = topology_description.server_descriptions()\n\n    # Replace this server's description with the new one.\n    sds[address] = server_description\n\n    if topology_type == TOPOLOGY_TYPE.Single:\n        # Single type never changes.\n        return TopologyDescription(\n            TOPOLOGY_TYPE.Single,\n            sds,\n            set_name,\n            max_set_version,\n            max_election_id,\n            topology_description._topology_settings)\n\n    if topology_type == TOPOLOGY_TYPE.Unknown:\n        if server_type == SERVER_TYPE.Standalone:\n            sds.pop(address)\n\n        elif server_type not in (SERVER_TYPE.Unknown, SERVER_TYPE.RSGhost):\n            topology_type = _SERVER_TYPE_TO_TOPOLOGY_TYPE[server_type]\n\n    if topology_type == TOPOLOGY_TYPE.Sharded:\n        if server_type not in (SERVER_TYPE.Mongos, SERVER_TYPE.Unknown):\n            sds.pop(address)\n\n    elif topology_type == TOPOLOGY_TYPE.ReplicaSetNoPrimary:\n        if server_type in (SERVER_TYPE.Standalone, SERVER_TYPE.Mongos):\n            sds.pop(address)\n\n        elif server_type == SERVER_TYPE.RSPrimary:\n            (topology_type,\n             set_name,\n             max_set_version,\n             max_election_id) = _update_rs_from_primary(sds,\n                                                        set_name,\n                                                        server_description,\n                                                        max_set_version,\n                                                        max_election_id)\n\n        elif server_type in (\n                SERVER_TYPE.RSSecondary,\n                SERVER_TYPE.RSArbiter,\n                SERVER_TYPE.RSOther):\n            topology_type, set_name = _update_rs_no_primary_from_member(\n                sds, set_name, server_description)\n\n    elif topology_type == TOPOLOGY_TYPE.ReplicaSetWithPrimary:\n        if server_type in (SERVER_TYPE.Standalone, SERVER_TYPE.Mongos):\n            sds.pop(address)\n            topology_type = _check_has_primary(sds)\n\n        elif server_type == SERVER_TYPE.RSPrimary:\n            (topology_type,\n             set_name,\n             max_set_version,\n             max_election_id) = _update_rs_from_primary(sds,\n                                                        set_name,\n                                                        server_description,\n                                                        max_set_version,\n                                                        max_election_id)\n\n        elif server_type in (\n                SERVER_TYPE.RSSecondary,\n                SERVER_TYPE.RSArbiter,\n                SERVER_TYPE.RSOther):\n            topology_type = _update_rs_with_primary_from_member(\n                sds, set_name, server_description)\n\n        else:\n            # Server type is Unknown or RSGhost: did we just lose the primary?\n            topology_type = _check_has_primary(sds)\n\n    # Return updated copy.\n    return TopologyDescription(topology_type,\n                               sds,\n                               set_name,\n                               max_set_version,\n                               max_election_id,\n                               topology_description._topology_settings)\n\n\ndef _updated_topology_description_srv_polling(topology_description, seedlist):\n    \"\"\"Return an updated copy of a TopologyDescription.\n\n    :Parameters:\n      - `topology_description`: the current TopologyDescription\n      - `seedlist`: a list of new seeds new ServerDescription that resulted from\n        an ismaster call\n    \"\"\"\n    # Create a copy of the server descriptions.\n    sds = topology_description.server_descriptions()\n\n    # If seeds haven't changed, don't do anything.\n    if set(sds.keys()) == set(seedlist):\n        return topology_description\n\n    # Add SDs corresponding to servers recently added to the SRV record.\n    for address in seedlist:\n        if address not in sds:\n            sds[address] = ServerDescription(address)\n\n    # Remove SDs corresponding to servers no longer part of the SRV record.\n    for address in list(sds.keys()):\n        if address not in seedlist:\n            sds.pop(address)\n\n    return TopologyDescription(\n        topology_description.topology_type,\n        sds,\n        topology_description.replica_set_name,\n        topology_description.max_set_version,\n        topology_description.max_election_id,\n        topology_description._topology_settings)\n\n\ndef _update_rs_from_primary(\n        sds,\n        replica_set_name,\n        server_description,\n        max_set_version,\n        max_election_id):\n    \"\"\"Update topology description from a primary's ismaster response.\n\n    Pass in a dict of ServerDescriptions, current replica set name, the\n    ServerDescription we are processing, and the TopologyDescription's\n    max_set_version and max_election_id if any.\n\n    Returns (new topology type, new replica_set_name, new max_set_version,\n    new max_election_id).\n    \"\"\"\n    if replica_set_name is None:\n        replica_set_name = server_description.replica_set_name\n\n    elif replica_set_name != server_description.replica_set_name:\n        # We found a primary but it doesn't have the replica_set_name\n        # provided by the user.\n        sds.pop(server_description.address)\n        return (_check_has_primary(sds),\n                replica_set_name,\n                max_set_version,\n                max_election_id)\n\n    max_election_tuple = max_set_version, max_election_id\n    if None not in server_description.election_tuple:\n        if (None not in max_election_tuple and\n                max_election_tuple > server_description.election_tuple):\n\n            # Stale primary, set to type Unknown.\n            address = server_description.address\n            sds[address] = ServerDescription(address)\n            return (_check_has_primary(sds),\n                    replica_set_name,\n                    max_set_version,\n                    max_election_id)\n\n        max_election_id = server_description.election_id\n\n    if (server_description.set_version is not None and\n        (max_set_version is None or\n            server_description.set_version > max_set_version)):\n\n        max_set_version = server_description.set_version\n\n    # We've heard from the primary. Is it the same primary as before?\n    for server in sds.values():\n        if (server.server_type is SERVER_TYPE.RSPrimary\n                and server.address != server_description.address):\n\n            # Reset old primary's type to Unknown.\n            sds[server.address] = ServerDescription(server.address)\n\n            # There can be only one prior primary.\n            break\n\n    # Discover new hosts from this primary's response.\n    for new_address in server_description.all_hosts:\n        if new_address not in sds:\n            sds[new_address] = ServerDescription(new_address)\n\n    # Remove hosts not in the response.\n    for addr in set(sds) - server_description.all_hosts:\n        sds.pop(addr)\n\n    # If the host list differs from the seed list, we may not have a primary\n    # after all.\n    return (_check_has_primary(sds),\n            replica_set_name,\n            max_set_version,\n            max_election_id)\n\n\ndef _update_rs_with_primary_from_member(\n        sds,\n        replica_set_name,\n        server_description):\n    \"\"\"RS with known primary. Process a response from a non-primary.\n\n    Pass in a dict of ServerDescriptions, current replica set name, and the\n    ServerDescription we are processing.\n\n    Returns new topology type.\n    \"\"\"\n    assert replica_set_name is not None\n\n    if replica_set_name != server_description.replica_set_name:\n        sds.pop(server_description.address)\n    elif (server_description.me and\n          server_description.address != server_description.me):\n        sds.pop(server_description.address)\n\n    # Had this member been the primary?\n    return _check_has_primary(sds)\n\n\ndef _update_rs_no_primary_from_member(\n        sds,\n        replica_set_name,\n        server_description):\n    \"\"\"RS without known primary. Update from a non-primary's response.\n\n    Pass in a dict of ServerDescriptions, current replica set name, and the\n    ServerDescription we are processing.\n\n    Returns (new topology type, new replica_set_name).\n    \"\"\"\n    topology_type = TOPOLOGY_TYPE.ReplicaSetNoPrimary\n    if replica_set_name is None:\n        replica_set_name = server_description.replica_set_name\n\n    elif replica_set_name != server_description.replica_set_name:\n        sds.pop(server_description.address)\n        return topology_type, replica_set_name\n\n    # This isn't the primary's response, so don't remove any servers\n    # it doesn't report. Only add new servers.\n    for address in server_description.all_hosts:\n        if address not in sds:\n            sds[address] = ServerDescription(address)\n\n    if (server_description.me and\n            server_description.address != server_description.me):\n        sds.pop(server_description.address)\n\n    return topology_type, replica_set_name\n\n\ndef _check_has_primary(sds):\n    \"\"\"Current topology type is ReplicaSetWithPrimary. Is primary still known?\n\n    Pass in a dict of ServerDescriptions.\n\n    Returns new topology type.\n    \"\"\"\n    for s in sds.values():\n        if s.server_type == SERVER_TYPE.RSPrimary:\n            return TOPOLOGY_TYPE.ReplicaSetWithPrimary\n    else:\n        return TOPOLOGY_TYPE.ReplicaSetNoPrimary\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/uri_parser.py",
    "content": "# Copyright 2011-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\"); you\n# may not use this file except in compliance with the License.  You\n# may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or\n# implied.  See the License for the specific language governing\n# permissions and limitations under the License.\n\n\n\"\"\"Tools to parse and validate a MongoDB URI.\"\"\"\nimport re\nimport warnings\n\nfrom bson.py3compat import string_type, PY3\n\nif PY3:\n    from urllib.parse import unquote_plus\nelse:\n    from urllib import unquote_plus\n\nfrom pymongo.common import (\n    get_validated_options, INTERNAL_URI_OPTION_NAME_MAP,\n    URI_OPTIONS_DEPRECATION_MAP, _CaseInsensitiveDictionary)\nfrom pymongo.errors import ConfigurationError, InvalidURI\nfrom pymongo.srv_resolver import _HAVE_DNSPYTHON, _SrvResolver\n\n\nSCHEME = 'mongodb://'\nSCHEME_LEN = len(SCHEME)\nSRV_SCHEME = 'mongodb+srv://'\nSRV_SCHEME_LEN = len(SRV_SCHEME)\nDEFAULT_PORT = 27017\n\n\ndef parse_userinfo(userinfo):\n    \"\"\"Validates the format of user information in a MongoDB URI.\n    Reserved characters like ':', '/', '+' and '@' must be escaped\n    following RFC 3986.\n\n    Returns a 2-tuple containing the unescaped username followed\n    by the unescaped password.\n\n    :Paramaters:\n        - `userinfo`: A string of the form <username>:<password>\n\n    .. versionchanged:: 2.2\n       Now uses `urllib.unquote_plus` so `+` characters must be escaped.\n    \"\"\"\n    if '@' in userinfo or userinfo.count(':') > 1:\n        if PY3:\n            quote_fn = \"urllib.parse.quote_plus\"\n        else:\n            quote_fn = \"urllib.quote_plus\"\n        raise InvalidURI(\"Username and password must be escaped according to \"\n                         \"RFC 3986, use %s().\" % quote_fn)\n    user, _, passwd = userinfo.partition(\":\")\n    # No password is expected with GSSAPI authentication.\n    if not user:\n        raise InvalidURI(\"The empty string is not valid username.\")\n    return unquote_plus(user), unquote_plus(passwd)\n\n\ndef parse_ipv6_literal_host(entity, default_port):\n    \"\"\"Validates an IPv6 literal host:port string.\n\n    Returns a 2-tuple of IPv6 literal followed by port where\n    port is default_port if it wasn't specified in entity.\n\n    :Parameters:\n        - `entity`: A string that represents an IPv6 literal enclosed\n                    in braces (e.g. '[::1]' or '[::1]:27017').\n        - `default_port`: The port number to use when one wasn't\n                          specified in entity.\n    \"\"\"\n    if entity.find(']') == -1:\n        raise ValueError(\"an IPv6 address literal must be \"\n                         \"enclosed in '[' and ']' according \"\n                         \"to RFC 2732.\")\n    i = entity.find(']:')\n    if i == -1:\n        return entity[1:-1], default_port\n    return entity[1: i], entity[i + 2:]\n\n\ndef parse_host(entity, default_port=DEFAULT_PORT):\n    \"\"\"Validates a host string\n\n    Returns a 2-tuple of host followed by port where port is default_port\n    if it wasn't specified in the string.\n\n    :Parameters:\n        - `entity`: A host or host:port string where host could be a\n                    hostname or IP address.\n        - `default_port`: The port number to use when one wasn't\n                          specified in entity.\n    \"\"\"\n    host = entity\n    port = default_port\n    if entity[0] == '[':\n        host, port = parse_ipv6_literal_host(entity, default_port)\n    elif entity.endswith(\".sock\"):\n        return entity, default_port\n    elif entity.find(':') != -1:\n        if entity.count(':') > 1:\n            raise ValueError(\"Reserved characters such as ':' must be \"\n                             \"escaped according RFC 2396. An IPv6 \"\n                             \"address literal must be enclosed in '[' \"\n                             \"and ']' according to RFC 2732.\")\n        host, port = host.split(':', 1)\n    if isinstance(port, string_type):\n        if not port.isdigit() or int(port) > 65535 or int(port) <= 0:\n            raise ValueError(\"Port must be an integer between 0 and 65535: %s\"\n                             % (port,))\n        port = int(port)\n\n    # Normalize hostname to lowercase, since DNS is case-insensitive:\n    # http://tools.ietf.org/html/rfc4343\n    # This prevents useless rediscovery if \"foo.com\" is in the seed list but\n    # \"FOO.com\" is in the ismaster response.\n    return host.lower(), port\n\n\n_IMPLICIT_TLSINSECURE_OPTS = {\"tlsallowinvalidcertificates\",\n                              \"tlsallowinvalidhostnames\"}\n\n_TLSINSECURE_EXCLUDE_OPTS = (_IMPLICIT_TLSINSECURE_OPTS |\n                             {INTERNAL_URI_OPTION_NAME_MAP[k] for k in\n                              _IMPLICIT_TLSINSECURE_OPTS})\n\n\ndef _parse_options(opts, delim):\n    \"\"\"Helper method for split_options which creates the options dict.\n    Also handles the creation of a list for the URI tag_sets/\n    readpreferencetags portion, and the use of a unicode options string.\"\"\"\n    options = _CaseInsensitiveDictionary()\n    for uriopt in opts.split(delim):\n        key, value = uriopt.split(\"=\")\n        if key.lower() == 'readpreferencetags':\n            options.setdefault(key, []).append(value)\n        else:\n            if key in options:\n                warnings.warn(\"Duplicate URI option '%s'.\" % (key,))\n            options[key] = unquote_plus(value)\n\n    return options\n\n\ndef _handle_security_options(options):\n    \"\"\"Raise appropriate errors when conflicting TLS options are present in\n    the options dictionary.\n\n    :Parameters:\n        - `options`: Instance of _CaseInsensitiveDictionary containing\n          MongoDB URI options.\n    \"\"\"\n    tlsinsecure = options.get('tlsinsecure')\n    if tlsinsecure is not None:\n        for opt in _TLSINSECURE_EXCLUDE_OPTS:\n            if opt in options:\n                err_msg = (\"URI options %s and %s cannot be specified \"\n                           \"simultaneously.\")\n                raise InvalidURI(err_msg % (\n                    options.cased_key('tlsinsecure'), options.cased_key(opt)))\n\n    if 'ssl' in options and 'tls' in options:\n        def truth_value(val):\n            if val in ('true', 'false'):\n                return val == 'true'\n            if isinstance(val, bool):\n                return val\n            return val\n        if truth_value(options.get('ssl')) != truth_value(options.get('tls')):\n            err_msg = (\"Can not specify conflicting values for URI options %s \"\n                      \"and %s.\")\n            raise InvalidURI(err_msg % (\n                options.cased_key('ssl'), options.cased_key('tls')))\n\n    return options\n\n\ndef _handle_option_deprecations(options):\n    \"\"\"Issue appropriate warnings when deprecated options are present in the\n    options dictionary. Removes deprecated option key, value pairs if the\n    options dictionary is found to also have the renamed option.\n\n    :Parameters:\n        - `options`: Instance of _CaseInsensitiveDictionary containing\n          MongoDB URI options.\n    \"\"\"\n    for optname in list(options):\n        if optname in URI_OPTIONS_DEPRECATION_MAP:\n            mode, message = URI_OPTIONS_DEPRECATION_MAP[optname]\n            if mode == 'renamed':\n                newoptname = message\n                if newoptname in options:\n                    warn_msg = (\"Deprecated option '%s' ignored in favor of \"\n                                \"'%s'.\")\n                    warnings.warn(\n                        warn_msg % (options.cased_key(optname),\n                                    options.cased_key(newoptname)),\n                        DeprecationWarning, stacklevel=2)\n                    options.pop(optname)\n                    continue\n                warn_msg = \"Option '%s' is deprecated, use '%s' instead.\"\n                warnings.warn(\n                    warn_msg % (options.cased_key(optname), newoptname),\n                    DeprecationWarning, stacklevel=2)\n            elif mode == 'removed':\n                warn_msg = \"Option '%s' is deprecated. %s.\"\n                warnings.warn(\n                    warn_msg % (options.cased_key(optname), message),\n                    DeprecationWarning, stacklevel=2)\n\n    return options\n\n\ndef _normalize_options(options):\n    \"\"\"Normalizes option names in the options dictionary by converting them to\n    their internally-used names. Also handles use of the tlsInsecure option.\n\n    :Parameters:\n        - `options`: Instance of _CaseInsensitiveDictionary containing\n          MongoDB URI options.\n    \"\"\"\n    tlsinsecure = options.get('tlsinsecure')\n    if tlsinsecure is not None:\n        for opt in _IMPLICIT_TLSINSECURE_OPTS:\n            intname = INTERNAL_URI_OPTION_NAME_MAP.get(opt, None)\n            # Internal options are logical inverse of public options.\n            options[intname] = not tlsinsecure\n\n    for optname in list(options):\n        intname = INTERNAL_URI_OPTION_NAME_MAP.get(optname, None)\n        if intname is not None:\n            options[intname] = options.pop(optname)\n\n    return options\n\n\ndef validate_options(opts, warn=False):\n    \"\"\"Validates and normalizes options passed in a MongoDB URI.\n\n    Returns a new dictionary of validated and normalized options. If warn is\n    False then errors will be thrown for invalid options, otherwise they will\n    be ignored and a warning will be issued.\n\n    :Parameters:\n        - `opts`: A dict of MongoDB URI options.\n        - `warn` (optional): If ``True`` then warnings will be logged and\n          invalid options will be ignored. Otherwise invalid options will\n          cause errors.\n    \"\"\"\n    return get_validated_options(opts, warn)\n\n\ndef split_options(opts, validate=True, warn=False, normalize=True):\n    \"\"\"Takes the options portion of a MongoDB URI, validates each option\n    and returns the options in a dictionary.\n\n    :Parameters:\n        - `opt`: A string representing MongoDB URI options.\n        - `validate`: If ``True`` (the default), validate and normalize all\n          options.\n        - `warn`: If ``False`` (the default), suppress all warnings raised\n          during validation of options.\n        - `normalize`: If ``True`` (the default), renames all options to their\n          internally-used names.\n    \"\"\"\n    and_idx = opts.find(\"&\")\n    semi_idx = opts.find(\";\")\n    try:\n        if and_idx >= 0 and semi_idx >= 0:\n            raise InvalidURI(\"Can not mix '&' and ';' for option separators.\")\n        elif and_idx >= 0:\n            options = _parse_options(opts, \"&\")\n        elif semi_idx >= 0:\n            options = _parse_options(opts, \";\")\n        elif opts.find(\"=\") != -1:\n            options = _parse_options(opts, None)\n        else:\n            raise ValueError\n    except ValueError:\n        raise InvalidURI(\"MongoDB URI options are key=value pairs.\")\n\n    options = _handle_security_options(options)\n\n    options = _handle_option_deprecations(options)\n\n    if validate:\n        options = validate_options(options, warn)\n\n    if normalize:\n        options = _normalize_options(options)\n\n    return options\n\n\ndef split_hosts(hosts, default_port=DEFAULT_PORT):\n    \"\"\"Takes a string of the form host1[:port],host2[:port]... and\n    splits it into (host, port) tuples. If [:port] isn't present the\n    default_port is used.\n\n    Returns a set of 2-tuples containing the host name (or IP) followed by\n    port number.\n\n    :Parameters:\n        - `hosts`: A string of the form host1[:port],host2[:port],...\n        - `default_port`: The port number to use when one wasn't specified\n          for a host.\n    \"\"\"\n    nodes = []\n    for entity in hosts.split(','):\n        if not entity:\n            raise ConfigurationError(\"Empty host \"\n                                     \"(or extra comma in host list).\")\n        port = default_port\n        # Unix socket entities don't have ports\n        if entity.endswith('.sock'):\n            port = None\n        nodes.append(parse_host(entity, port))\n    return nodes\n\n\n# Prohibited characters in database name. DB names also can't have \".\", but for\n# backward-compat we allow \"db.collection\" in URI.\n_BAD_DB_CHARS = re.compile('[' + re.escape(r'/ \"$') + ']')\n\n_ALLOWED_TXT_OPTS = frozenset(\n    ['authsource', 'authSource', 'replicaset', 'replicaSet'])\n\n\ndef parse_uri(uri, default_port=DEFAULT_PORT, validate=True, warn=False,\n              normalize=True, connect_timeout=None):\n    \"\"\"Parse and validate a MongoDB URI.\n\n    Returns a dict of the form::\n\n        {\n            'nodelist': <list of (host, port) tuples>,\n            'username': <username> or None,\n            'password': <password> or None,\n            'database': <database name> or None,\n            'collection': <collection name> or None,\n            'options': <dict of MongoDB URI options>,\n            'fqdn': <fqdn of the MongoDB+SRV URI> or None\n        }\n\n    If the URI scheme is \"mongodb+srv://\" DNS SRV and TXT lookups will be done\n    to build nodelist and options.\n\n    :Parameters:\n        - `uri`: The MongoDB URI to parse.\n        - `default_port`: The port number to use when one wasn't specified\n          for a host in the URI.\n        - `validate` (optional): If ``True`` (the default), validate and\n          normalize all options. Default: ``True``.\n        - `warn` (optional): When validating, if ``True`` then will warn\n          the user then ignore any invalid options or values. If ``False``,\n          validation will error when options are unsupported or values are\n          invalid. Default: ``False``.\n        - `normalize` (optional): If ``True``, convert names of URI options\n          to their internally-used names. Default: ``True``.\n        - `connect_timeout` (optional): The maximum time in milliseconds to\n          wait for a response from the DNS server.\n\n    .. versionchanged:: 3.9\n        Added the ``normalize`` parameter.\n\n    .. versionchanged:: 3.6\n        Added support for mongodb+srv:// URIs.\n\n    .. versionchanged:: 3.5\n        Return the original value of the ``readPreference`` MongoDB URI option\n        instead of the validated read preference mode.\n\n    .. versionchanged:: 3.1\n        ``warn`` added so invalid options can be ignored.\n    \"\"\"\n    if uri.startswith(SCHEME):\n        is_srv = False\n        scheme_free = uri[SCHEME_LEN:]\n    elif uri.startswith(SRV_SCHEME):\n        if not _HAVE_DNSPYTHON:\n            raise ConfigurationError('The \"dnspython\" module must be '\n                                     'installed to use mongodb+srv:// URIs')\n        is_srv = True\n        scheme_free = uri[SRV_SCHEME_LEN:]\n    else:\n        raise InvalidURI(\"Invalid URI scheme: URI must \"\n                         \"begin with '%s' or '%s'\" % (SCHEME, SRV_SCHEME))\n\n    if not scheme_free:\n        raise InvalidURI(\"Must provide at least one hostname or IP.\")\n\n    user = None\n    passwd = None\n    dbase = None\n    collection = None\n    options = _CaseInsensitiveDictionary()\n\n    host_part, _, path_part = scheme_free.partition('/')\n    if not host_part:\n        host_part = path_part\n        path_part = \"\"\n\n    if not path_part and '?' in host_part:\n        raise InvalidURI(\"A '/' is required between \"\n                         \"the host list and any options.\")\n\n    if path_part:\n        if path_part[0] == '?':\n            opts = unquote_plus(path_part[1:])\n        else:\n            dbase, _, opts = map(unquote_plus, path_part.partition('?'))\n            if '.' in dbase:\n                dbase, collection = dbase.split('.', 1)\n\n            if _BAD_DB_CHARS.search(dbase):\n                raise InvalidURI('Bad database name \"%s\"' % dbase)\n\n        if opts:\n            options.update(split_options(opts, validate, warn, normalize))\n\n    if dbase is not None:\n        dbase = unquote_plus(dbase)\n    if collection is not None:\n        collection = unquote_plus(collection)\n\n    if '@' in host_part:\n        userinfo, _, hosts = host_part.rpartition('@')\n        user, passwd = parse_userinfo(userinfo)\n    else:\n        hosts = host_part\n\n    if '/' in hosts:\n        raise InvalidURI(\"Any '/' in a unix domain socket must be\"\n                         \" percent-encoded: %s\" % host_part)\n\n    hosts = unquote_plus(hosts)\n    fqdn = None\n\n    if is_srv:\n        nodes = split_hosts(hosts, default_port=None)\n        if len(nodes) != 1:\n            raise InvalidURI(\n                \"%s URIs must include one, \"\n                \"and only one, hostname\" % (SRV_SCHEME,))\n        fqdn, port = nodes[0]\n        if port is not None:\n            raise InvalidURI(\n                \"%s URIs must not include a port number\" % (SRV_SCHEME,))\n\n        # Use the connection timeout. connectTimeoutMS passed as a keyword\n        # argument overrides the same option passed in the connection string.\n        connect_timeout = connect_timeout or options.get(\"connectTimeoutMS\")\n        dns_resolver = _SrvResolver(fqdn, connect_timeout=connect_timeout)\n        nodes = dns_resolver.get_hosts()\n        dns_options = dns_resolver.get_options()\n        if dns_options:\n            parsed_dns_options = split_options(\n                dns_options, validate, warn, normalize)\n            if set(parsed_dns_options) - _ALLOWED_TXT_OPTS:\n                raise ConfigurationError(\n                    \"Only authSource and replicaSet are supported from DNS\")\n            for opt, val in parsed_dns_options.items():\n                if opt not in options:\n                    options[opt] = val\n        if \"ssl\" not in options:\n            options[\"ssl\"] = True if validate else 'true'\n    else:\n        nodes = split_hosts(hosts, default_port=default_port)\n\n    return {\n        'nodelist': nodes,\n        'username': user,\n        'password': passwd,\n        'database': dbase,\n        'collection': collection,\n        'options': options,\n        'fqdn': fqdn\n    }\n\n\nif __name__ == '__main__':\n    import pprint\n    import sys\n    try:\n        pprint.pprint(parse_uri(sys.argv[1]))\n    except InvalidURI as exc:\n        print(exc)\n    sys.exit(0)"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo/write_concern.py",
    "content": "# Copyright 2014-present MongoDB, Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n# http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\n\"\"\"Tools for working with write concerns.\"\"\"\n\nfrom bson.py3compat import integer_types, string_type\nfrom pymongo.errors import ConfigurationError\n\n\nclass WriteConcern(object):\n    \"\"\"WriteConcern\n\n    :Parameters:\n        - `w`: (integer or string) Used with replication, write operations\n          will block until they have been replicated to the specified number\n          or tagged set of servers. `w=<integer>` always includes the replica\n          set primary (e.g. w=3 means write to the primary and wait until\n          replicated to **two** secondaries). **w=0 disables acknowledgement\n          of write operations and can not be used with other write concern\n          options.**\n        - `wtimeout`: (integer) Used in conjunction with `w`. Specify a value\n          in milliseconds to control how long to wait for write propagation\n          to complete. If replication does not complete in the given\n          timeframe, a timeout exception is raised.\n        - `j`: If ``True`` block until write operations have been committed\n          to the journal. Cannot be used in combination with `fsync`. Prior\n          to MongoDB 2.6 this option was ignored if the server was running\n          without journaling. Starting with MongoDB 2.6 write operations will\n          fail with an exception if this option is used when the server is\n          running without journaling.\n        - `fsync`: If ``True`` and the server is running without journaling,\n          blocks until the server has synced all data files to disk. If the\n          server is running with journaling, this acts the same as the `j`\n          option, blocking until write operations have been committed to the\n          journal. Cannot be used in combination with `j`.\n    \"\"\"\n\n    __slots__ = (\"__document\", \"__acknowledged\", \"__server_default\")\n\n    def __init__(self, w=None, wtimeout=None, j=None, fsync=None):\n        self.__document = {}\n        self.__acknowledged = True\n\n        if wtimeout is not None:\n            if not isinstance(wtimeout, integer_types):\n                raise TypeError(\"wtimeout must be an integer\")\n            if wtimeout < 0:\n                raise ValueError(\"wtimeout cannot be less than 0\")\n            self.__document[\"wtimeout\"] = wtimeout\n\n        if j is not None:\n            if not isinstance(j, bool):\n                raise TypeError(\"j must be True or False\")\n            self.__document[\"j\"] = j\n\n        if fsync is not None:\n            if not isinstance(fsync, bool):\n                raise TypeError(\"fsync must be True or False\")\n            if j and fsync:\n                raise ConfigurationError(\"Can't set both j \"\n                                         \"and fsync at the same time\")\n            self.__document[\"fsync\"] = fsync\n\n        if w == 0 and j is True:\n            raise ConfigurationError(\"Cannot set w to 0 and j to True\")\n\n        if w is not None:\n            if isinstance(w, integer_types):\n                if w < 0:\n                    raise ValueError(\"w cannot be less than 0\")\n                self.__acknowledged = w > 0\n            elif not isinstance(w, string_type):\n                raise TypeError(\"w must be an integer or string\")\n            self.__document[\"w\"] = w\n\n        self.__server_default = not self.__document\n\n    @property\n    def is_server_default(self):\n        \"\"\"Does this WriteConcern match the server default.\"\"\"\n        return self.__server_default\n\n    @property\n    def document(self):\n        \"\"\"The document representation of this write concern.\n\n        .. note::\n          :class:`WriteConcern` is immutable. Mutating the value of\n          :attr:`document` does not mutate this :class:`WriteConcern`.\n        \"\"\"\n        return self.__document.copy()\n\n    @property\n    def acknowledged(self):\n        \"\"\"If ``True`` write operations will wait for acknowledgement before\n        returning.\n        \"\"\"\n        return self.__acknowledged\n\n    def __repr__(self):\n        return (\"WriteConcern(%s)\" % (\n            \", \".join(\"%s=%s\" % kvt for kvt in self.__document.items()),))\n\n    def __eq__(self, other):\n        if isinstance(other, WriteConcern):\n            return self.__document == other.document\n        return NotImplemented\n\n    def __ne__(self, other):\n        if isinstance(other, WriteConcern):\n            return self.__document != other.document\n        return NotImplemented\n\n\nDEFAULT_WRITE_CONCERN = WriteConcern()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo-3.9.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo-3.9.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: pymongo\nVersion: 3.9.0\nSummary: Python driver for MongoDB <http://www.mongodb.org>\nHome-page: http://github.com/mongodb/mongo-python-driver\nAuthor: Mike Dirolf\nAuthor-email: mongodb-user@googlegroups.com\nMaintainer: Bernie Hackett\nMaintainer-email: bernie@mongodb.com\nLicense: Apache License, Version 2.0\nKeywords: mongo,mongodb,pymongo,gridfs,bson\nPlatform: UNKNOWN\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: Apache Software License\nClassifier: Operating System :: MacOS :: MacOS X\nClassifier: Operating System :: Microsoft :: Windows\nClassifier: Operating System :: POSIX\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nClassifier: Programming Language :: Python :: Implementation :: CPython\nClassifier: Programming Language :: Python :: Implementation :: PyPy\nClassifier: Topic :: Database\nRequires-Python: >=2.7,!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*\nProvides-Extra: gssapi\nProvides-Extra: tls\nProvides-Extra: zstd\nProvides-Extra: snappy\nProvides-Extra: encryption\nProvides-Extra: srv\nProvides-Extra: encryption\nRequires-Dist: pymongocrypt; extra == 'encryption'\nProvides-Extra: gssapi\nRequires-Dist: pykerberos; extra == 'gssapi'\nProvides-Extra: snappy\nRequires-Dist: python-snappy; extra == 'snappy'\nProvides-Extra: srv\nRequires-Dist: dnspython (<2.0.0,>=1.16.0); extra == 'srv'\nProvides-Extra: tls\nProvides-Extra: zstd\nRequires-Dist: zstandard; extra == 'zstd'\n\n=======\nPyMongo\n=======\n:Info: See `the mongo site <http://www.mongodb.org>`_ for more information. See `GitHub <http://github.com/mongodb/mongo-python-driver>`_ for the latest source.\n:Author: Mike Dirolf\n:Maintainer: Bernie Hackett <bernie@mongodb.com>\n\nAbout\n=====\n\nThe PyMongo distribution contains tools for interacting with MongoDB\ndatabase from Python.  The ``bson`` package is an implementation of\nthe `BSON format <http://bsonspec.org>`_ for Python. The ``pymongo``\npackage is a native Python driver for MongoDB. The ``gridfs`` package\nis a `gridfs\n<http://www.mongodb.org/display/DOCS/GridFS+Specification>`_\nimplementation on top of ``pymongo``.\n\nPyMongo supports MongoDB 2.6, 3.0, 3.2, 3.4, 3.6, 4.0 and 4.2.\n\nSupport / Feedback\n==================\n\nFor issues with, questions about, or feedback for PyMongo, please look into\nour `support channels <http://www.mongodb.org/about/support>`_. Please\ndo not email any of the PyMongo developers directly with issues or\nquestions - you're more likely to get an answer on the `mongodb-user\n<http://groups.google.com/group/mongodb-user>`_ list on Google Groups.\n\nBugs / Feature Requests\n=======================\n\nThink you’ve found a bug? Want to see a new feature in PyMongo? Please open a\ncase in our issue management tool, JIRA:\n\n- `Create an account and login <https://jira.mongodb.org>`_.\n- Navigate to `the PYTHON project <https://jira.mongodb.org/browse/PYTHON>`_.\n- Click **Create Issue** - Please provide as much information as possible about the issue type and how to reproduce it.\n\nBug reports in JIRA for all driver projects (i.e. PYTHON, CSHARP, JAVA) and the\nCore Server (i.e. SERVER) project are **public**.\n\nHow To Ask For Help\n-------------------\n\nPlease include all of the following information when opening an issue:\n\n- Detailed steps to reproduce the problem, including full traceback, if possible.\n- The exact python version used, with patch level::\n\n  $ python -c \"import sys; print(sys.version)\"\n\n- The exact version of PyMongo used, with patch level::\n\n  $ python -c \"import pymongo; print(pymongo.version); print(pymongo.has_c())\"\n\n- The operating system and version (e.g. Windows 7, OSX 10.8, ...)\n- Web framework or asynchronous network library used, if any, with version (e.g.\n  Django 1.7, mod_wsgi 4.3.0, gevent 1.0.1, Tornado 4.0.2, ...)\n\nSecurity Vulnerabilities\n------------------------\n\nIf you’ve identified a security vulnerability in a driver or any other\nMongoDB project, please report it according to the `instructions here\n<http://docs.mongodb.org/manual/tutorial/create-a-vulnerability-report>`_.\n\nInstallation\n============\n\nPyMongo can be installed with `pip <http://pypi.python.org/pypi/pip>`_::\n\n  $ python -m pip install pymongo\n\nOr ``easy_install`` from\n`setuptools <http://pypi.python.org/pypi/setuptools>`_::\n\n  $ python -m easy_install pymongo\n\nYou can also download the project source and do::\n\n  $ python setup.py install\n\nDo **not** install the \"bson\" package from pypi. PyMongo comes with its own\nbson package; doing \"easy_install bson\" installs a third-party package that\nis incompatible with PyMongo.\n\nDependencies\n============\n\nPyMongo supports CPython 2.7, 3.4+, PyPy, and PyPy3.5+.\n\nOptional dependencies:\n\nGSSAPI authentication requires `pykerberos\n<https://pypi.python.org/pypi/pykerberos>`_ on Unix or `WinKerberos\n<https://pypi.python.org/pypi/winkerberos>`_ on Windows. The correct\ndependency can be installed automatically along with PyMongo::\n\n  $ python -m pip install pymongo[gssapi]\n\nSupport for mongodb+srv:// URIs requires `dnspython\n<https://pypi.python.org/pypi/dnspython>`_::\n\n  $ python -m pip install pymongo[srv]\n\nTLS / SSL support may require `ipaddress\n<https://pypi.python.org/pypi/ipaddress>`_ and `certifi\n<https://pypi.python.org/pypi/certifi>`_ or `wincertstore\n<https://pypi.python.org/pypi/wincertstore>`_ depending on the Python\nversion in use. The necessary dependencies can be installed along with\nPyMongo::\n\n  $ python -m pip install pymongo[tls]\n\nWire protocol compression with snappy requires `python-snappy\n<https://pypi.org/project/python-snappy>`_::\n\n  $ python -m pip install pymongo[snappy]\n\nWire protocol compression with zstandard requires `zstandard\n<https://pypi.org/project/zstandard>`_::\n\n  $ python -m pip install pymongo[zstd]\n\nYou can install all dependencies automatically with the following\ncommand::\n\n  $ python -m pip install pymongo[snappy,gssapi,srv,tls,zstd]\n\nOther optional packages:\n\n- `backports.pbkdf2 <https://pypi.python.org/pypi/backports.pbkdf2/>`_,\n  improves authentication performance with SCRAM-SHA-1 and SCRAM-SHA-256.\n  It especially improves performance on Python versions older than 2.7.8.\n- `monotonic <https://pypi.python.org/pypi/monotonic>`_ adds support for\n  a monotonic clock, which improves reliability in environments\n  where clock adjustments are frequent. Not needed in Python 3.\n\n\nAdditional dependencies are:\n\n- (to generate documentation) sphinx_\n\nExamples\n========\nHere's a basic example (for more see the *examples* section of the docs):\n\n.. code-block:: python\n\n  >>> import pymongo\n  >>> client = pymongo.MongoClient(\"localhost\", 27017)\n  >>> db = client.test\n  >>> db.name\n  u'test'\n  >>> db.my_collection\n  Collection(Database(MongoClient('localhost', 27017), u'test'), u'my_collection')\n  >>> db.my_collection.insert_one({\"x\": 10}).inserted_id\n  ObjectId('4aba15ebe23f6b53b0000000')\n  >>> db.my_collection.insert_one({\"x\": 8}).inserted_id\n  ObjectId('4aba160ee23f6b543e000000')\n  >>> db.my_collection.insert_one({\"x\": 11}).inserted_id\n  ObjectId('4aba160ee23f6b543e000002')\n  >>> db.my_collection.find_one()\n  {u'x': 10, u'_id': ObjectId('4aba15ebe23f6b53b0000000')}\n  >>> for item in db.my_collection.find():\n  ...     print(item[\"x\"])\n  ...\n  10\n  8\n  11\n  >>> db.my_collection.create_index(\"x\")\n  u'x_1'\n  >>> for item in db.my_collection.find().sort(\"x\", pymongo.ASCENDING):\n  ...     print(item[\"x\"])\n  ...\n  8\n  10\n  11\n  >>> [item[\"x\"] for item in db.my_collection.find().limit(2).skip(1)]\n  [8, 11]\n\nDocumentation\n=============\n\nYou will need sphinx_ installed to generate the\ndocumentation. Documentation can be generated by running **python\nsetup.py doc**. Generated documentation can be found in the\n*doc/build/html/* directory.\n\nTesting\n=======\n\nThe easiest way to run the tests is to run **python setup.py test** in\nthe root of the distribution.\n\nTo verify that PyMongo works with Gevent's monkey-patching::\n\n    $ python green_framework_test.py gevent\n\nOr with Eventlet's::\n\n    $ python green_framework_test.py eventlet\n\n.. _sphinx: http://sphinx.pocoo.org/\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo-3.9.0.dist-info/RECORD",
    "content": "bson/__init__.py,sha256=zQgEvqEQFI_oDcs7OV7A-GVMb5SzM8TbqnBnlUQMM-E,46004\r\nbson/__pycache__/__init__.cpython-36.pyc,,\r\nbson/__pycache__/binary.cpython-36.pyc,,\r\nbson/__pycache__/code.cpython-36.pyc,,\r\nbson/__pycache__/codec_options.cpython-36.pyc,,\r\nbson/__pycache__/dbref.cpython-36.pyc,,\r\nbson/__pycache__/decimal128.cpython-36.pyc,,\r\nbson/__pycache__/errors.cpython-36.pyc,,\r\nbson/__pycache__/int64.cpython-36.pyc,,\r\nbson/__pycache__/json_util.cpython-36.pyc,,\r\nbson/__pycache__/max_key.cpython-36.pyc,,\r\nbson/__pycache__/min_key.cpython-36.pyc,,\r\nbson/__pycache__/objectid.cpython-36.pyc,,\r\nbson/__pycache__/py3compat.cpython-36.pyc,,\r\nbson/__pycache__/raw_bson.cpython-36.pyc,,\r\nbson/__pycache__/regex.cpython-36.pyc,,\r\nbson/__pycache__/son.cpython-36.pyc,,\r\nbson/__pycache__/timestamp.cpython-36.pyc,,\r\nbson/__pycache__/tz_util.cpython-36.pyc,,\r\nbson/_cbson.cpython-36m-x86_64-linux-gnu.so,sha256=ev9jqojqlpJ-5QXUksYwMtj9TkPpU4Ls5lvHD52-Yfs,263122\r\nbson/binary.py,sha256=kgDtGbVFJN_QAD52ChAELOBNVyITNY_-4xwql4x1L90,7377\r\nbson/code.py,sha256=Bj9q2xc3hJ-IuNwzUTSi1r0qshBU1J1pCjVJIJExquk,3360\r\nbson/codec_options.py,sha256=q-9JB_wMZeRFIl-N3iHE7HHnl1SorntWMROew64Uqws,13752\r\nbson/dbref.py,sha256=pMBnQj36MsJHr-OeTOnJ0gQBF239Mff5E3ioXp_x2vs,4733\r\nbson/decimal128.py,sha256=RA9r0OcH_XzxAW0Bdi8oD7axD6yIgRBSq69zBu-iDbI,10425\r\nbson/errors.py,sha256=AkDIISytky_6NFP-U2ecdXooIr53yt0ZiAT42DmuoI8,1159\r\nbson/int64.py,sha256=NNAMdrdFUMfrhmTfd9cGo2qLSpnS4xjSyVvDnJKmagc,1056\r\nbson/json_util.py,sha256=nxN_no7JiNSmbX4bs4CV8s5rAXCorC9P2LeSbRNprAc,31733\r\nbson/max_key.py,sha256=21OvVcOVm6sb7bd4oRFiapZMgmG1dqnTNOjEm1QaGZQ,1315\r\nbson/min_key.py,sha256=AIejvYyTgDFTJna81weTarOb5zBhZGWTW8M2fU1GZJQ,1315\r\nbson/objectid.py,sha256=-ZsHR0-A36uanDeYuHTh08Fz5sRDXS9znGymvNBiT68,9377\r\nbson/py3compat.py,sha256=nC6q-RwR7iCHN3NFVoiwO3s3Y6GeKe_qQAcIL4Gc9J4,2815\r\nbson/raw_bson.py,sha256=KypxfpfW4nRsQiLuRujy8wydks2LZj9KaKmrcZoGnBo,5039\r\nbson/regex.py,sha256=44nO3645IcX3gRQ9X9ChUDVkQErHSLzX67BLYsyyuII,4291\r\nbson/son.py,sha256=vv0ervx8YNBTIJpd1vao621OAZ5mss7MhWr031rUajQ,5788\r\nbson/timestamp.py,sha256=KmPD75UR8zE95sTOQxjvutIJ6A65UOcqfTRFL2MAE-k,3932\r\nbson/tz_util.py,sha256=Zy_bA8x2YWrTbIx08HQYYJVghKKwChcCkO4VSBwaNVU,1518\r\ngridfs/__init__.py,sha256=16Mn5rm1dVHCCA3Ur93Az6tMUdyQ9XnkeWCcDemQVe4,36320\r\ngridfs/__pycache__/__init__.cpython-36.pyc,,\r\ngridfs/__pycache__/errors.cpython-36.pyc,,\r\ngridfs/__pycache__/grid_file.cpython-36.pyc,,\r\ngridfs/errors.py,sha256=Z7E-XkxtrWNfob3cTBSgeRlTvHcG02DCPv4X_EmvBkQ,1056\r\ngridfs/grid_file.py,sha256=rlotGXCb3W4NRMNlsw-Dtb5yOCOz9eIIUsWuYddK3a4,30481\r\npymongo-3.9.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\npymongo-3.9.0.dist-info/METADATA,sha256=C8AxfynlpgPWM6r-fzWnBSozLFtS8Htip8tLQgSVUfs,8363\r\npymongo-3.9.0.dist-info/RECORD,,\r\npymongo-3.9.0.dist-info/WHEEL,sha256=d2ILPScH-y2UwGxsW1PeA2TT-KW0Git4AJ6LeOK8sQo,109\r\npymongo-3.9.0.dist-info/top_level.txt,sha256=OinVojDdOfo1Dsp-NRfrZdp6gcJJ4bPRq61vSg5vyAs,20\r\npymongo/__init__.py,sha256=oCq3aAng48CHljuplzt2v3akRZgIrmcRRrzcMzPvjR8,2821\r\npymongo/__pycache__/__init__.cpython-36.pyc,,\r\npymongo/__pycache__/aggregation.cpython-36.pyc,,\r\npymongo/__pycache__/auth.cpython-36.pyc,,\r\npymongo/__pycache__/bulk.cpython-36.pyc,,\r\npymongo/__pycache__/change_stream.cpython-36.pyc,,\r\npymongo/__pycache__/client_options.cpython-36.pyc,,\r\npymongo/__pycache__/client_session.cpython-36.pyc,,\r\npymongo/__pycache__/collation.cpython-36.pyc,,\r\npymongo/__pycache__/collection.cpython-36.pyc,,\r\npymongo/__pycache__/command_cursor.cpython-36.pyc,,\r\npymongo/__pycache__/common.cpython-36.pyc,,\r\npymongo/__pycache__/compression_support.cpython-36.pyc,,\r\npymongo/__pycache__/cursor.cpython-36.pyc,,\r\npymongo/__pycache__/cursor_manager.cpython-36.pyc,,\r\npymongo/__pycache__/database.cpython-36.pyc,,\r\npymongo/__pycache__/driver_info.cpython-36.pyc,,\r\npymongo/__pycache__/encryption.cpython-36.pyc,,\r\npymongo/__pycache__/encryption_options.cpython-36.pyc,,\r\npymongo/__pycache__/errors.cpython-36.pyc,,\r\npymongo/__pycache__/helpers.cpython-36.pyc,,\r\npymongo/__pycache__/ismaster.cpython-36.pyc,,\r\npymongo/__pycache__/max_staleness_selectors.cpython-36.pyc,,\r\npymongo/__pycache__/message.cpython-36.pyc,,\r\npymongo/__pycache__/mongo_client.cpython-36.pyc,,\r\npymongo/__pycache__/mongo_replica_set_client.cpython-36.pyc,,\r\npymongo/__pycache__/monitor.cpython-36.pyc,,\r\npymongo/__pycache__/monitoring.cpython-36.pyc,,\r\npymongo/__pycache__/monotonic.cpython-36.pyc,,\r\npymongo/__pycache__/network.cpython-36.pyc,,\r\npymongo/__pycache__/operations.cpython-36.pyc,,\r\npymongo/__pycache__/periodic_executor.cpython-36.pyc,,\r\npymongo/__pycache__/pool.cpython-36.pyc,,\r\npymongo/__pycache__/read_concern.cpython-36.pyc,,\r\npymongo/__pycache__/read_preferences.cpython-36.pyc,,\r\npymongo/__pycache__/response.cpython-36.pyc,,\r\npymongo/__pycache__/results.cpython-36.pyc,,\r\npymongo/__pycache__/saslprep.cpython-36.pyc,,\r\npymongo/__pycache__/server.cpython-36.pyc,,\r\npymongo/__pycache__/server_description.cpython-36.pyc,,\r\npymongo/__pycache__/server_selectors.cpython-36.pyc,,\r\npymongo/__pycache__/server_type.cpython-36.pyc,,\r\npymongo/__pycache__/settings.cpython-36.pyc,,\r\npymongo/__pycache__/son_manipulator.cpython-36.pyc,,\r\npymongo/__pycache__/srv_resolver.cpython-36.pyc,,\r\npymongo/__pycache__/ssl_context.cpython-36.pyc,,\r\npymongo/__pycache__/ssl_match_hostname.cpython-36.pyc,,\r\npymongo/__pycache__/ssl_support.cpython-36.pyc,,\r\npymongo/__pycache__/thread_util.cpython-36.pyc,,\r\npymongo/__pycache__/topology.cpython-36.pyc,,\r\npymongo/__pycache__/topology_description.cpython-36.pyc,,\r\npymongo/__pycache__/uri_parser.cpython-36.pyc,,\r\npymongo/__pycache__/write_concern.cpython-36.pyc,,\r\npymongo/_cmessage.cpython-36m-x86_64-linux-gnu.so,sha256=JjbAccQxv1yghoWbRxAY-9oZslSHvCUYNqfbFCHwoeg,136463\r\npymongo/aggregation.py,sha256=i1hwm3_-uz1Bdoh57wXLXAH9LPqltiv1nyjiROxNVVc,8796\r\npymongo/auth.py,sha256=_SaN1SjHEUbKxhrVDI397Wfy5hYBbsVgbe_Vs_p43NM,20547\r\npymongo/bulk.py,sha256=-zzz1LxWivPQGEQjSotgeHAfd5Vjd9c7Dvt9NF7avUo,26333\r\npymongo/change_stream.py,sha256=hbVjXfyrhSXmr3HyTnoBfkzeJoysy9kYCuj3j-uQSmE,14486\r\npymongo/client_options.py,sha256=2dlrgzqrcAXJOqaG60uy5cOa7m-5SSzKgBX4t5S0kQQ,9227\r\npymongo/client_session.py,sha256=3-Vt7tCsHmPDHr4HFXydlODBqJXDvNKv_uQuVpOvvlc,35501\r\npymongo/collation.py,sha256=-dQ4Aoclig9lx-nZTo92Jw5NsV8Q6QVWzzpxTb9FKvs,7808\r\npymongo/collection.py,sha256=YVBeFEpAevL-oRGYgYMT4mo-AVU9U2wEPo4481bKVCU,144111\r\npymongo/command_cursor.py,sha256=F_deYTVDOVt_Xr6qmNnbbd2NVKl2aCiegMXb1r7wM_s,10985\r\npymongo/common.py,sha256=2sb2SrLbRTeYtDmN5oCMO5tXrgpYSMayUsIj8ijKw2w,31951\r\npymongo/compression_support.py,sha256=qqeiICODM_9SVewXIU46pIvpSAhSAUuj9o9jF3W6CIg,5170\r\npymongo/cursor.py,sha256=NVvwxbLuVTGYD33v_w1KkCt5tIGYYqTgrG0mtzJGr0Y,46939\r\npymongo/cursor_manager.py,sha256=lJerbsskemaaB5bUy_Rv0Ola4BJqEEezSo3zOAoAGak,2088\r\npymongo/database.py,sha256=W8l1OY1Nyd-iw7rqu7forQECF-xLveRpeTuycTBf9PI,65893\r\npymongo/driver_info.py,sha256=fk9u7Ni4Ln-Rx1DkqZmvsJeI49l72o3kiRJvfHpcmlI,1703\r\npymongo/encryption.py,sha256=FvDhQ2QJra24zMLO_E7GfmP8te2bGr6lGT6gv9ml6iY,20051\r\npymongo/encryption_options.py,sha256=MMZ0HUHPv9Tk8yOXMhMUkffFfLW_RpJaGm6qd_aKdBU,6886\r\npymongo/errors.py,sha256=PYKAcJsOsEeabI6OdExCnZgUhbEXsw7LtN0MAyGiBPk,8250\r\npymongo/helpers.py,sha256=-rZq8sg4d1SKvI_xHF7klKbp37NTkfY8cDnNWs4KMgQ,10064\r\npymongo/ismaster.py,sha256=FOLjQm86XxBPiQ2sCRWHc1i_g-ap721tTBLX5X1WywQ,4527\r\npymongo/max_staleness_selectors.py,sha256=rXA_frTXGvAwAWY_pBbu4GvnLsOLlaG2xnIbYdCizgI,4326\r\npymongo/message.py,sha256=LzCbjQQlUrufPdGGLS65cz8EkIBub6bX3h8jT1hiZpo,59213\r\npymongo/mongo_client.py,sha256=3V5hUgxtGq8wlfkV3ikmwEFE7OwHMm_HBQOblOcX4eg,99178\r\npymongo/mongo_replica_set_client.py,sha256=sjv9GYkF-m_sTa9OeqALj0vnMT1s9C-Vo8yAbL6u_4M,1955\r\npymongo/monitor.py,sha256=LujVXZm8Yaur6JfCRvevEsFafVaDLG_CUyZlvxGthmU,9338\r\npymongo/monitoring.py,sha256=KXNZeBGClULrtweV-A4kTGz1Tk_gYBCQLs19iOTMCWo,50615\r\npymongo/monotonic.py,sha256=NOgK1fiHf-yqoF5vZ2xP0QhMLB0DYRvAc5U8q4utxSE,1100\r\npymongo/network.py,sha256=HAE6tBDNISbAgRsJJTYTlTd9WEfaSxNIHVMyJPawz6c,12349\r\npymongo/operations.py,sha256=cnZhmemp5EXDNv2X_dVKxQ79EW5EDuZiPBJu9EhEwts,13969\r\npymongo/periodic_executor.py,sha256=fQnzacxHA0W_AL1RhS8G_fjg0BzOt1VUoCHN42n2fdU,5619\r\npymongo/pool.py,sha256=HLz3vd7tt0vhNa-qnT2ILANmvFOdsweG65crDgNuIXI,49841\r\npymongo/read_concern.py,sha256=s-lPeqjpraky4TabOul_stU6ps9UELs1tHGGAPvaoIk,2337\r\npymongo/read_preferences.py,sha256=3FAArDFnwp4grk9Emv7lg2LECQ_Dmg8OILVnnK5Wp0U,16494\r\npymongo/response.py,sha256=QKznb9ALbuJyKMaxjeKFYsHCIJ1Go5ivgAEv5u0kHcw,3643\r\npymongo/results.py,sha256=FE8M0suvJW50LMMEEE1j6546dg6B_fRWkt2-uQkJq5Y,7818\r\npymongo/saslprep.py,sha256=Ybzpu66Rm4KRFIfbqooRocDNjFGJ3Xkpzu1uI0f7pc8,4275\r\npymongo/server.py,sha256=QoAmhMtfRe5eEM9pQmSRHfTOpdS-f70YU952WEf8dbc,8120\r\npymongo/server_description.py,sha256=FQ0WlM_Rv_FNL8sZOcqZJb_MxOwxqWlw1kbd7cF91uQ,6335\r\npymongo/server_selectors.py,sha256=KoItAlFYGYujfq_nrNaHjWVW_IDSCpKP7f-2YLl_k5I,5307\r\npymongo/server_type.py,sha256=AScVY81CujqY93-0kfnB1LG4OowXqO3Ts-CeXyMPa9g,882\r\npymongo/settings.py,sha256=V3qLV1E_VJL47BVlWi99ohjfPsKyb02ZGQws_enOkDM,4210\r\npymongo/son_manipulator.py,sha256=aINKIHNhAE_f6j1Do8ejNVYD0_u-Pa1e6oerKsMxe7s,6699\r\npymongo/srv_resolver.py,sha256=hWTVQcC_ZULbsGzUMi7cxxh-IoUFwmWzhAy8j-c7KW4,3686\r\npymongo/ssl_context.py,sha256=_iBrSiqyD7I0MQMIwOUOc1q_CxTODeALfepfZ3353rE,3670\r\npymongo/ssl_match_hostname.py,sha256=u5QdUf8wogzS0SzsfsKcOYcAwWXo97e8COGWJbbl7dY,4677\r\npymongo/ssl_support.py,sha256=iKV7lU_n0RlDEx2_Rt8-0MKupqFodJ6j2euk58QzEaY,8310\r\npymongo/thread_util.py,sha256=YF-_hCRZEH931lCfhBBIZBXQE39WPamHwG7BU_QHlzo,3959\r\npymongo/topology.py,sha256=vBFO83vgmRyynkc3t1uSWc98kwNcjq971HCnDzTjWN0,27490\r\npymongo/topology_description.py,sha256=vDJr81XZdSwkpHwFfSn5PiQeXBKa9BkrurzvfnA_pCU,22024\r\npymongo/uri_parser.py,sha256=CnBToGesNdljBmAREtgNndMUfgWtjJh46htJ1LcsUXI,18090\r\npymongo/write_concern.py,sha256=PQmoV6RqaTlMgvoKU-KoQ_oowJsH9Tabi8KF-kSCZTg,5000\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo-3.9.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.31.1)\nRoot-Is-Purelib: false\nTag: cp36-cp36m-manylinux1_x86_64\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/pymongo-3.9.0.dist-info/top_level.txt",
    "content": "bson\ngridfs\npymongo\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib/__init__.py",
    "content": "from queuelib.queue import FifoDiskQueue, LifoDiskQueue\nfrom queuelib.pqueue import PriorityQueue\nfrom queuelib.rrqueue import RoundRobinQueue"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib/pqueue.py",
    "content": "class PriorityQueue(object):\n    \"\"\"A priority queue implemented using multiple internal queues (typically,\n    FIFO queues). The internal queue must implement the following methods:\n\n        * push(obj)\n        * pop()\n        * close()\n        * __len__()\n\n    The constructor receives a qfactory argument, which is a callable used to\n    instantiate a new (internal) queue when a new priority is allocated. The\n    qfactory function is called with the priority number as first and only\n    argument.\n\n    Only integer priorities should be used. Lower numbers are higher\n    priorities.\n\n    startprios is a sequence of priorities to start with. If the queue was\n    previously closed leaving some priority buckets non-empty, those priorities\n    should be passed in startprios.\n\n    \"\"\"\n\n    def __init__(self, qfactory, startprios=()):\n        self.queues = {}\n        self.qfactory = qfactory\n        for p in startprios:\n            self.queues[p] = self.qfactory(p)\n        self.curprio = min(startprios) if startprios else None\n\n    def push(self, obj, priority=0):\n        if priority not in self.queues:\n            self.queues[priority] = self.qfactory(priority)\n        q = self.queues[priority]\n        q.push(obj) # this may fail (eg. serialization error)\n        if self.curprio is None or priority < self.curprio:\n            self.curprio = priority\n\n    def pop(self):\n        if self.curprio is None:\n            return\n        q = self.queues[self.curprio]\n        m = q.pop()\n        if len(q) == 0:\n            del self.queues[self.curprio]\n            q.close()\n            prios = [p for p, q in self.queues.items() if len(q) > 0]\n            self.curprio = min(prios) if prios else None\n        return m\n\n    def close(self):\n        active = []\n        for p, q in self.queues.items():\n            if len(q):\n                active.append(p)\n            q.close()\n        return active\n\n    def __len__(self):\n        return sum(len(x) for x in self.queues.values()) if self.queues else 0\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib/queue.py",
    "content": "import os\nimport glob\nimport json\nimport struct\nimport sqlite3\nfrom collections import deque\n\n\nclass FifoMemoryQueue(object):\n    \"\"\"In-memory FIFO queue, API compliant with FifoDiskQueue.\"\"\"\n\n    def __init__(self):\n        self.q = deque()\n        self.push = self.q.append\n\n    def pop(self):\n        q = self.q\n        return q.popleft() if q else None\n\n    def close(self):\n        pass\n\n    def __len__(self):\n        return len(self.q)\n\n\nclass LifoMemoryQueue(FifoMemoryQueue):\n    \"\"\"In-memory LIFO queue, API compliant with LifoDiskQueue.\"\"\"\n\n    def pop(self):\n        q = self.q\n        return q.pop() if q else None\n\n\nclass FifoDiskQueue(object):\n    \"\"\"Persistent FIFO queue.\"\"\"\n\n    szhdr_format = \">L\"\n    szhdr_size = struct.calcsize(szhdr_format)\n\n    def __init__(self, path, chunksize=100000):\n        self.path = path\n        if not os.path.exists(path):\n            os.makedirs(path)\n        self.info = self._loadinfo(chunksize)\n        self.chunksize = self.info['chunksize']\n        self.headf = self._openchunk(self.info['head'][0], 'ab+')\n        self.tailf = self._openchunk(self.info['tail'][0])\n        os.lseek(self.tailf.fileno(), self.info['tail'][2], os.SEEK_SET)\n\n    def push(self, string):\n        if not isinstance(string, bytes):\n            raise TypeError('Unsupported type: {}'.format(type(string).__name__))\n        hnum, hpos = self.info['head']\n        hpos += 1\n        szhdr = struct.pack(self.szhdr_format, len(string))\n        os.write(self.headf.fileno(), szhdr + string)\n        if hpos == self.chunksize:\n            hpos = 0\n            hnum += 1\n            self.headf.close()\n            self.headf = self._openchunk(hnum, 'ab+')\n        self.info['size'] += 1\n        self.info['head'] = [hnum, hpos]\n\n    def _openchunk(self, number, mode='rb'):\n        return open(os.path.join(self.path, 'q%05d' % number), mode)\n\n    def pop(self):\n        tnum, tcnt, toffset = self.info['tail']\n        if [tnum, tcnt] >= self.info['head']:\n            return\n        tfd = self.tailf.fileno()\n        szhdr = os.read(tfd, self.szhdr_size)\n        if not szhdr:\n            return\n        size, = struct.unpack(self.szhdr_format, szhdr)\n        data = os.read(tfd, size)\n        tcnt += 1\n        toffset += self.szhdr_size + size\n        if tcnt == self.chunksize and tnum <= self.info['head'][0]:\n            tcnt = toffset = 0\n            tnum += 1\n            self.tailf.close()\n            os.remove(self.tailf.name)\n            self.tailf = self._openchunk(tnum)\n        self.info['size'] -= 1\n        self.info['tail'] = [tnum, tcnt, toffset]\n        return data\n\n    def close(self):\n        self.headf.close()\n        self.tailf.close()\n        self._saveinfo(self.info)\n        if len(self) == 0:\n            self._cleanup()\n\n    def __len__(self):\n        return self.info['size']\n\n    def _loadinfo(self, chunksize):\n        infopath = self._infopath()\n        if os.path.exists(infopath):\n            with open(infopath) as f:\n                info = json.load(f)\n        else:\n            info = {\n                'chunksize': chunksize,\n                'size': 0,\n                'tail': [0, 0, 0],\n                'head': [0, 0],\n            }\n        return info\n\n    def _saveinfo(self, info):\n        with open(self._infopath(), 'w') as f:\n            json.dump(info, f)\n\n    def _infopath(self):\n        return os.path.join(self.path, 'info.json')\n\n    def _cleanup(self):\n        for x in glob.glob(os.path.join(self.path, 'q*')):\n            os.remove(x)\n        os.remove(os.path.join(self.path, 'info.json'))\n        if not os.listdir(self.path):\n            os.rmdir(self.path)\n\n\n\nclass LifoDiskQueue(object):\n    \"\"\"Persistent LIFO queue.\"\"\"\n\n    SIZE_FORMAT = \">L\"\n    SIZE_SIZE = struct.calcsize(SIZE_FORMAT)\n\n    def __init__(self, path):\n        self.path = path\n        if os.path.exists(path):\n            self.f = open(path, 'rb+')\n            qsize = self.f.read(self.SIZE_SIZE)\n            self.size, = struct.unpack(self.SIZE_FORMAT, qsize)\n            self.f.seek(0, os.SEEK_END)\n        else:\n            self.f = open(path, 'wb+')\n            self.f.write(struct.pack(self.SIZE_FORMAT, 0))\n            self.size = 0\n\n    def push(self, string):\n        if not isinstance(string, bytes):\n            raise TypeError('Unsupported type: {}'.format(type(string).__name__))\n        self.f.write(string)\n        ssize = struct.pack(self.SIZE_FORMAT, len(string))\n        self.f.write(ssize)\n        self.size += 1\n\n    def pop(self):\n        if not self.size:\n            return\n        self.f.seek(-self.SIZE_SIZE, os.SEEK_END)\n        size, = struct.unpack(self.SIZE_FORMAT, self.f.read())\n        self.f.seek(-size-self.SIZE_SIZE, os.SEEK_END)\n        data = self.f.read(size)\n        self.f.seek(-size, os.SEEK_CUR)\n        self.f.truncate()\n        self.size -= 1\n        return data\n\n    def close(self):\n        if self.size:\n            self.f.seek(0)\n            self.f.write(struct.pack(self.SIZE_FORMAT, self.size))\n        self.f.close()\n        if not self.size:\n            os.remove(self.path)\n\n    def __len__(self):\n        return self.size\n\n\nclass FifoSQLiteQueue(object):\n\n    _sql_create = (\n        'CREATE TABLE IF NOT EXISTS queue '\n        '(id INTEGER PRIMARY KEY AUTOINCREMENT, item BLOB)'\n    )\n    _sql_size = 'SELECT COUNT(*) FROM queue'\n    _sql_push = 'INSERT INTO queue (item) VALUES (?)'\n    _sql_pop = 'SELECT id, item FROM queue ORDER BY id LIMIT 1'\n    _sql_del = 'DELETE FROM queue WHERE id = ?'\n\n    def __init__(self, path):\n        self._path = os.path.abspath(path)\n        self._db = sqlite3.Connection(self._path, timeout=60)\n        self._db.text_factory = bytes\n        with self._db as conn:\n            conn.execute(self._sql_create)\n\n    def push(self, item):\n        if not isinstance(item, bytes):\n            raise TypeError('Unsupported type: {}'.format(type(item).__name__))\n\n        with self._db as conn:\n            conn.execute(self._sql_push, (item,))\n\n    def pop(self):\n        with self._db as conn:\n            for id_, item in conn.execute(self._sql_pop):\n                conn.execute(self._sql_del, (id_,))\n                return item\n\n    def close(self):\n        size = len(self)\n        self._db.close()\n        if not size:\n            os.remove(self._path)\n\n    def __len__(self):\n        with self._db as conn:\n            return next(conn.execute(self._sql_size))[0]\n\n\nclass LifoSQLiteQueue(FifoSQLiteQueue):\n\n    _sql_pop = 'SELECT id, item FROM queue ORDER BY id DESC LIMIT 1'\n\n\n#FifoDiskQueue = FifoSQLiteQueue  # noqa\n#LifoDiskQueue = LifoSQLiteQueue  # noqa\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib/rrqueue.py",
    "content": "from collections import deque\n\nclass RoundRobinQueue(object):\n    \"\"\"A round robin queue implemented using multiple internal queues (typically,\n    FIFO queues). The internal queue must implement the following methods:\n        * push(obj)\n        * pop()\n        * close()\n        * __len__()\n    The constructor receives a qfactory argument, which is a callable used to\n    instantiate a new (internal) queue when a new key is allocated. The\n    qfactory function is called with the key number as first and only\n    argument.\n    start_keys is a sequence of domains to start with. If the queue was\n    previously closed leaving some domain buckets non-empty, those domains\n    should be passed in start_keys.\n\n    The queue maintains a fifo queue of keys.  The key that went last is\n    poped first and the next queue for that key is then poped.  This allows\n    for a round robin\n    \"\"\"\n\n    def __init__(self, qfactory, start_domains=()):\n        self.queues = {}\n        self.qfactory = qfactory\n        for key in start_domains:\n            self.queues[key] = self.qfactory(key)\n\n        self.key_queue = deque(start_domains)\n\n    def push(self, obj, key):\n        if key not in self.key_queue:\n            self.queues[key] = self.qfactory(key)\n            self.key_queue.appendleft(key)  # it's new, might as well pop first\n\n        q = self.queues[key]\n        q.push(obj) # this may fail (eg. serialization error)\n\n    def pop(self):\n        m = None\n        # pop until we find a valid object, closing necessary queues\n        while m is None:\n            try:\n                key = self.key_queue.pop()\n            except IndexError:\n                return\n\n            q = self.queues[key]\n            m = q.pop()\n\n            if len(q) == 0:\n                del self.queues[key]\n                q.close()\n            else:\n                self.key_queue.appendleft(key)\n\n            if m:\n                return m\n\n    def close(self):\n        active = []\n        for k, q in self.queues.items():\n            if len(q):\n                active.append(k)\n            q.close()\n        return active\n\n    def __len__(self):\n        return sum(len(x) for x in self.queues.values()) if self.queues else 0\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib/tests/__init__.py",
    "content": "import unittest, tempfile, shutil\n\nclass QueuelibTestCase(unittest.TestCase):\n\n    def setUp(self):\n        self.tmpdir = tempfile.mkdtemp(prefix=\"queuelib-tests-\")\n        self.qpath = self.mktemp()\n        self.qdir = self.mkdtemp()\n\n    def tearDown(self):\n        shutil.rmtree(self.tmpdir)\n\n    def mktemp(self):\n        return tempfile.mktemp(dir=self.tmpdir)\n\n    def mkdtemp(self):\n        return tempfile.mkdtemp(dir=self.tmpdir)\n\n\ndef track_closed(cls):\n    \"\"\"Wraps a queue class to track down if close() method was called\"\"\"\n\n    class TrackingClosed(cls):\n\n        def __init__(self, *a, **kw):\n            super(TrackingClosed, self).__init__(*a, **kw)\n            self.closed = False\n\n        def close(self):\n            super(TrackingClosed, self).close()\n            self.closed = True\n\n    return TrackingClosed\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib/tests/test_pqueue.py",
    "content": "import os\nfrom queuelib.pqueue import PriorityQueue\nfrom queuelib.queue import (\n    FifoMemoryQueue, LifoMemoryQueue, FifoDiskQueue, LifoDiskQueue,\n    FifoSQLiteQueue, LifoSQLiteQueue,\n)\nfrom queuelib.tests import (QueuelibTestCase, track_closed)\n\n\n# hack to prevent py.test from discovering base test class\nclass base:\n    class PQueueTestBase(QueuelibTestCase):\n\n        def setUp(self):\n            QueuelibTestCase.setUp(self)\n            self.q = PriorityQueue(self.qfactory)\n\n        def qfactory(self, prio):\n            raise NotImplementedError\n\n        def test_len_nonzero(self):\n            assert not self.q\n            self.assertEqual(len(self.q), 0)\n            self.q.push(b'a', 3)\n            assert self.q\n            self.q.push(b'b', 1)\n            self.q.push(b'c', 2)\n            self.q.push(b'd', 1)\n            self.assertEqual(len(self.q), 4)\n            self.q.pop()\n            self.q.pop()\n            self.q.pop()\n            self.q.pop()\n            assert not self.q\n            self.assertEqual(len(self.q), 0)\n\n        def test_close(self):\n            self.q.push(b'a', 3)\n            self.q.push(b'b', 1)\n            self.q.push(b'c', 2)\n            self.q.push(b'd', 1)\n            iqueues = self.q.queues.values()\n            self.assertEqual(sorted(self.q.close()), [1, 2, 3])\n            assert all(q.closed for q in iqueues)\n\n        def test_close_return_active(self):\n            self.q.push(b'b', 1)\n            self.q.push(b'c', 2)\n            self.q.push(b'a', 3)\n            self.q.pop()\n            self.assertEqual(sorted(self.q.close()), [2, 3])\n\n        def test_popped_internal_queues_closed(self):\n            self.q.push(b'a', 3)\n            self.q.push(b'b', 1)\n            self.q.push(b'c', 2)\n            p1queue = self.q.queues[1]\n            self.assertEqual(self.q.pop(), b'b')\n            self.q.close()\n            assert p1queue.closed\n\n\nclass FifoTestMixin(object):\n\n    def test_push_pop_noprio(self):\n        self.q.push(b'a')\n        self.q.push(b'b')\n        self.q.push(b'c')\n        self.assertEqual(self.q.pop(), b'a')\n        self.assertEqual(self.q.pop(), b'b')\n        self.assertEqual(self.q.pop(), b'c')\n        self.assertEqual(self.q.pop(), None)\n\n    def test_push_pop_prio(self):\n        self.q.push(b'a', 3)\n        self.q.push(b'b', 1)\n        self.q.push(b'c', 2)\n        self.q.push(b'd', 1)\n        self.assertEqual(self.q.pop(), b'b')\n        self.assertEqual(self.q.pop(), b'd')\n        self.assertEqual(self.q.pop(), b'c')\n        self.assertEqual(self.q.pop(), b'a')\n        self.assertEqual(self.q.pop(), None)\n\n\nclass LifoTestMixin(object):\n\n    def test_push_pop_noprio(self):\n        self.q.push(b'a')\n        self.q.push(b'b')\n        self.q.push(b'c')\n        self.assertEqual(self.q.pop(), b'c')\n        self.assertEqual(self.q.pop(), b'b')\n        self.assertEqual(self.q.pop(), b'a')\n        self.assertEqual(self.q.pop(), None)\n\n    def test_push_pop_prio(self):\n        self.q.push(b'a', 3)\n        self.q.push(b'b', 1)\n        self.q.push(b'c', 2)\n        self.q.push(b'd', 1)\n        self.assertEqual(self.q.pop(), b'd')\n        self.assertEqual(self.q.pop(), b'b')\n        self.assertEqual(self.q.pop(), b'c')\n        self.assertEqual(self.q.pop(), b'a')\n        self.assertEqual(self.q.pop(), None)\n\n\nclass FifoMemoryPriorityQueueTest(FifoTestMixin, base.PQueueTestBase):\n\n    def qfactory(self, prio):\n        return track_closed(FifoMemoryQueue)()\n\n\nclass LifoMemoryPriorityQueueTest(LifoTestMixin, base.PQueueTestBase):\n\n    def qfactory(self, prio):\n        return track_closed(LifoMemoryQueue)()\n\n\nclass DiskTestMixin(object):\n\n    def test_nonserializable_object_one(self):\n        self.assertRaises(TypeError, self.q.push, lambda x: x, 0)\n        self.assertEqual(self.q.close(), [])\n\n    def test_nonserializable_object_many_close(self):\n        self.q.push(b'a', 3)\n        self.q.push(b'b', 1)\n        self.assertRaises(TypeError, self.q.push, lambda x: x, 0)\n        self.q.push(b'c', 2)\n        self.assertEqual(self.q.pop(), b'b')\n        self.assertEqual(sorted(self.q.close()), [2, 3])\n\n    def test_nonserializable_object_many_pop(self):\n        self.q.push(b'a', 3)\n        self.q.push(b'b', 1)\n        self.assertRaises(TypeError, self.q.push, lambda x: x, 0)\n        self.q.push(b'c', 2)\n        self.assertEqual(self.q.pop(), b'b')\n        self.assertEqual(self.q.pop(), b'c')\n        self.assertEqual(self.q.pop(), b'a')\n        self.assertEqual(self.q.pop(), None)\n        self.assertEqual(self.q.close(), [])\n\n    def test_reopen_with_prio(self):\n        q1 = PriorityQueue(self.qfactory)\n        q1.push(b'a', 3)\n        q1.push(b'b', 1)\n        q1.push(b'c', 2)\n        active = q1.close()\n        q2 = PriorityQueue(self.qfactory, startprios=active)\n        self.assertEqual(q2.pop(), b'b')\n        self.assertEqual(q2.pop(), b'c')\n        self.assertEqual(q2.pop(), b'a')\n        self.assertEqual(q2.close(), [])\n\n\nclass FifoDiskPriorityQueueTest(FifoTestMixin, DiskTestMixin, base.PQueueTestBase):\n\n    def qfactory(self, prio):\n        path = os.path.join(self.qdir, str(prio))\n        return track_closed(FifoDiskQueue)(path)\n\n\nclass LifoDiskPriorityQueueTest(LifoTestMixin, DiskTestMixin, base.PQueueTestBase):\n\n    def qfactory(self, prio):\n        path = os.path.join(self.qdir, str(prio))\n        return track_closed(LifoDiskQueue)(path)\n\n\nclass FifoSQLitePriorityQueueTest(FifoTestMixin, DiskTestMixin, base.PQueueTestBase):\n\n    def qfactory(self, prio):\n        path = os.path.join(self.qdir, str(prio))\n        return track_closed(FifoSQLiteQueue)(path)\n\n\nclass LifoSQLitePriorityQueueTest(LifoTestMixin, DiskTestMixin, base.PQueueTestBase):\n\n    def qfactory(self, prio):\n        path = os.path.join(self.qdir, str(prio))\n        return track_closed(LifoSQLiteQueue)(path)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib/tests/test_queue.py",
    "content": "import os\nimport glob\nimport pytest\n\nfrom queuelib.queue import (\n    FifoMemoryQueue, LifoMemoryQueue, FifoDiskQueue, LifoDiskQueue,\n    FifoSQLiteQueue, LifoSQLiteQueue,\n)\nfrom queuelib.tests import QueuelibTestCase\n\n\nclass BaseQueueTest(object):\n\n    def queue(self):\n        return NotImplementedError()\n\n    def test_empty(self):\n        \"\"\"Empty queue test\"\"\"\n        q = self.queue()\n        assert q.pop() is None\n\n    def test_single_pushpop(self):\n        q = self.queue()\n        q.push(b'a')\n        assert q.pop() == b'a'\n\n    def test_binary_element(self):\n        elem = (\n            b'\\x80\\x02}q\\x01(U\\x04bodyq\\x02U\\x00U\\t_encodingq\\x03U\\x05utf-'\n            b'8q\\x04U\\x07cookiesq\\x05}q\\x06U\\x04metaq\\x07}q\\x08U\\x07header'\n            b'sq\\t}U\\x03urlq\\nX\\x15\\x00\\x00\\x00file:///tmp/tmphDJYsgU\\x0bd'\n            b'ont_filterq\\x0b\\x89U\\x08priorityq\\x0cK\\x00U\\x08callbackq\\rNU'\n            b'\\x06methodq\\x0eU\\x03GETq\\x0fU\\x07errbackq\\x10Nu.'\n        )\n        q = self.queue()\n        q.push(elem)\n        assert q.pop() == elem\n\n    def test_len(self):\n        q = self.queue()\n        self.assertEqual(len(q), 0)\n        q.push(b'a')\n        self.assertEqual(len(q), 1)\n        q.push(b'b')\n        q.push(b'c')\n        self.assertEqual(len(q), 3)\n        q.pop()\n        q.pop()\n        q.pop()\n        self.assertEqual(len(q), 0)\n\n\nclass FifoTestMixin(BaseQueueTest):\n\n    def test_push_pop1(self):\n        \"\"\"Basic push/pop test\"\"\"\n        q = self.queue()\n        q.push(b'a')\n        q.push(b'b')\n        q.push(b'c')\n        self.assertEqual(q.pop(), b'a')\n        self.assertEqual(q.pop(), b'b')\n        self.assertEqual(q.pop(), b'c')\n        self.assertEqual(q.pop(), None)\n\n    def test_push_pop2(self):\n        \"\"\"Test interleaved push and pops\"\"\"\n        q = self.queue()\n        q.push(b'a')\n        q.push(b'b')\n        q.push(b'c')\n        q.push(b'd')\n        self.assertEqual(q.pop(), b'a')\n        self.assertEqual(q.pop(), b'b')\n        q.push(b'e')\n        self.assertEqual(q.pop(), b'c')\n        self.assertEqual(q.pop(), b'd')\n        self.assertEqual(q.pop(), b'e')\n\n\nclass LifoTestMixin(BaseQueueTest):\n\n    def test_push_pop1(self):\n        \"\"\"Basic push/pop test\"\"\"\n        q = self.queue()\n        q.push(b'a')\n        q.push(b'b')\n        q.push(b'c')\n        self.assertEqual(q.pop(), b'c')\n        self.assertEqual(q.pop(), b'b')\n        self.assertEqual(q.pop(), b'a')\n        self.assertEqual(q.pop(), None)\n\n    def test_push_pop2(self):\n        \"\"\"Test interleaved push and pops\"\"\"\n        q = self.queue()\n        q.push(b'a')\n        q.push(b'b')\n        q.push(b'c')\n        q.push(b'd')\n        self.assertEqual(q.pop(), b'd')\n        self.assertEqual(q.pop(), b'c')\n        q.push(b'e')\n        self.assertEqual(q.pop(), b'e')\n        self.assertEqual(q.pop(), b'b')\n        self.assertEqual(q.pop(), b'a')\n\n\nclass PersistentTestMixin(object):\n\n    chunksize = 100000\n\n    @pytest.mark.xfail(reason=\"Reenable once Scrapy.squeues stop\"\n                       \" extending from queuelib testsuite\")\n    def test_non_bytes_raises_typeerror(self):\n        q = self.queue()\n        self.assertRaises(TypeError, q.push, 0)\n        self.assertRaises(TypeError, q.push, u'')\n        self.assertRaises(TypeError, q.push, None)\n        self.assertRaises(TypeError, q.push, lambda x: x)\n\n    def test_text_in_windows(self):\n        e1 = b'\\r\\n'\n        q = self.queue()\n        q.push(e1)\n        q.close()\n        q = self.queue()\n        e2 = q.pop()\n        self.assertEqual(e1, e2)\n\n    def test_close_open(self):\n        \"\"\"Test closing and re-opening keeps state\"\"\"\n        q = self.queue()\n        q.push(b'a')\n        q.push(b'b')\n        q.push(b'c')\n        q.push(b'd')\n        q.pop()\n        q.pop()\n        q.close()\n        del q\n\n        q = self.queue()\n        self.assertEqual(len(q), 2)\n        q.push(b'e')\n        q.pop()\n        q.pop()\n        q.close()\n        del q\n\n        q = self.queue()\n        assert q.pop() is not None\n        self.assertEqual(len(q), 0)\n\n    def test_cleanup(self):\n        \"\"\"Test queue dir is removed if queue is empty\"\"\"\n        q = self.queue()\n        values = [b'0', b'1', b'2', b'3', b'4']\n        assert os.path.exists(self.qpath)\n        for x in values:\n            q.push(x)\n\n        for x in values:\n            q.pop()\n        q.close()\n        assert not os.path.exists(self.qpath)\n\n\nclass FifoMemoryQueueTest(FifoTestMixin, QueuelibTestCase):\n\n    def queue(self):\n        return FifoMemoryQueue()\n\n\nclass LifoMemoryQueueTest(LifoTestMixin, QueuelibTestCase):\n\n    def queue(self):\n        return LifoMemoryQueue()\n\n\nclass FifoDiskQueueTest(FifoTestMixin, PersistentTestMixin, QueuelibTestCase):\n\n    def queue(self):\n        return FifoDiskQueue(self.qpath, chunksize=self.chunksize)\n\n    def test_chunks(self):\n        \"\"\"Test chunks are created and removed\"\"\"\n        values = [b'0', b'1', b'2', b'3', b'4']\n        q = self.queue()\n        for x in values:\n            q.push(x)\n\n        chunks = glob.glob(os.path.join(self.qpath, 'q*'))\n        self.assertEqual(len(chunks), 5 // self.chunksize + 1)\n        for x in values:\n            q.pop()\n\n        chunks = glob.glob(os.path.join(self.qpath, 'q*'))\n        self.assertEqual(len(chunks), 1)\n\n\nclass ChunkSize1FifoDiskQueueTest(FifoDiskQueueTest):\n    chunksize = 1\n\n\nclass ChunkSize2FifoDiskQueueTest(FifoDiskQueueTest):\n    chunksize = 2\n\n\nclass ChunkSize3FifoDiskQueueTest(FifoDiskQueueTest):\n    chunksize = 3\n\n\nclass ChunkSize4FifoDiskQueueTest(FifoDiskQueueTest):\n    chunksize = 4\n\n\nclass LifoDiskQueueTest(LifoTestMixin, PersistentTestMixin, QueuelibTestCase):\n\n    def queue(self):\n        return LifoDiskQueue(self.qpath)\n\n    def test_file_size_shrinks(self):\n        \"\"\"Test size of queue file shrinks when popping items\"\"\"\n        q = self.queue()\n        q.push(b'a')\n        q.push(b'b')\n        q.close()\n        size = os.path.getsize(self.qpath)\n        q = self.queue()\n        q.pop()\n        q.close()\n        assert os.path.getsize(self.qpath), size\n\n\nclass FifoSQLiteQueueTest(FifoTestMixin, PersistentTestMixin, QueuelibTestCase):\n\n    def queue(self):\n        return FifoSQLiteQueue(self.qpath)\n\n\nclass LifoSQLiteQueueTest(LifoTestMixin, PersistentTestMixin, QueuelibTestCase):\n\n    def queue(self):\n        return LifoSQLiteQueue(self.qpath)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib/tests/test_rrqueue.py",
    "content": "import os\nfrom queuelib.rrqueue import RoundRobinQueue\nfrom queuelib.queue import (\n    FifoMemoryQueue, LifoMemoryQueue, FifoDiskQueue, LifoDiskQueue,\n    FifoSQLiteQueue, LifoSQLiteQueue,\n)\nfrom queuelib.tests import (QueuelibTestCase, track_closed)\n\n\n# hack to prevent py.test from discovering base test class\nclass base:\n    class RRQueueTestBase(QueuelibTestCase):\n\n        def setUp(self):\n            QueuelibTestCase.setUp(self)\n            self.q = RoundRobinQueue(self.qfactory)\n\n        def qfactory(self, key):\n            raise NotImplementedError\n\n        def test_len_nonzero(self):\n            assert not self.q\n            self.assertEqual(len(self.q), 0)\n            self.q.push(b'a', '3')\n            assert self.q\n            self.q.push(b'b', '1')\n            self.q.push(b'c', '2')\n            self.q.push(b'd', '1')\n            self.assertEqual(len(self.q), 4)\n            self.q.pop()\n            self.q.pop()\n            self.q.pop()\n            self.q.pop()\n            assert not self.q\n            self.assertEqual(len(self.q), 0)\n\n        def test_close(self):\n            self.q.push(b'a', '3')\n            self.q.push(b'b', '1')\n            self.q.push(b'c', '2')\n            self.q.push(b'd', '1')\n            iqueues = self.q.queues.values()\n            self.assertEqual(sorted(self.q.close()), ['1', '2', '3'])\n            assert all(q.closed for q in iqueues)\n\n        def test_close_return_active(self):\n            self.q.push(b'b', '1')\n            self.q.push(b'c', '2')\n            self.q.push(b'a', '3')\n            self.q.pop()\n            self.assertEqual(sorted(self.q.close()), ['2', '3'])\n\n\nclass FifoTestMixin(object):\n    def test_push_pop_key(self):\n        self.q.push(b'a', '1')\n        self.q.push(b'b', '1')\n        self.q.push(b'c', '2')\n        self.q.push(b'd', '2')\n        self.assertEqual(self.q.pop(), b'a')\n        self.assertEqual(self.q.pop(), b'c')\n        self.assertEqual(self.q.pop(), b'b')\n        self.assertEqual(self.q.pop(), b'd')\n        self.assertEqual(self.q.pop(), None)\n\n\nclass LifoTestMixin(object):\n\n    def test_push_pop_key(self):\n        self.q.push(b'a', '1')\n        self.q.push(b'b', '1')\n        self.q.push(b'c', '2')\n        self.q.push(b'd', '2')\n        self.assertEqual(self.q.pop(), b'b')\n        self.assertEqual(self.q.pop(), b'd')\n        self.assertEqual(self.q.pop(), b'a')\n        self.assertEqual(self.q.pop(), b'c')\n        self.assertEqual(self.q.pop(), None)\n\n\nclass FifoMemoryRRQueueTest(FifoTestMixin, base.RRQueueTestBase):\n\n    def qfactory(self, key):\n        return track_closed(FifoMemoryQueue)()\n\n\nclass LifoMemoryRRQueueTest(LifoTestMixin, base.RRQueueTestBase):\n\n    def qfactory(self, key):\n        return track_closed(LifoMemoryQueue)()\n\n\nclass DiskTestMixin(object):\n\n    def test_nonserializable_object_one(self):\n        self.assertRaises(TypeError, self.q.push, lambda x: x, '0')\n        self.assertEqual(self.q.close(), [])\n\n    def test_nonserializable_object_many_close(self):\n        self.q.push(b'a', '3')\n        self.q.push(b'b', '1')\n        self.assertRaises(TypeError, self.q.push, lambda x: x, '0')\n        self.q.push(b'c', '2')\n        self.assertEqual(self.q.pop(), b'a')\n        self.assertEqual(sorted(self.q.close()), ['1', '2'])\n\n    def test_nonserializable_object_many_pop(self):\n        self.q.push(b'a', '3')\n        self.q.push(b'b', '1')\n        self.assertRaises(TypeError, self.q.push, lambda x: x, '0')\n        self.q.push(b'c', '2')\n        self.assertEqual(self.q.pop(), b'a')\n        self.assertEqual(self.q.pop(), b'b')\n        self.assertEqual(self.q.pop(), b'c')\n        self.assertEqual(self.q.pop(), None)\n        self.assertEqual(self.q.close(), [])\n\n\nclass FifoDiskRRQueueTest(FifoTestMixin, DiskTestMixin, base.RRQueueTestBase):\n\n    def qfactory(self, key):\n        path = os.path.join(self.qdir, str(key))\n        return track_closed(FifoDiskQueue)(path)\n\n\nclass LifoDiskRRQueueTest(LifoTestMixin, DiskTestMixin, base.RRQueueTestBase):\n\n    def qfactory(self, key):\n        path = os.path.join(self.qdir, str(key))\n        return track_closed(LifoDiskQueue)(path)\n\n\nclass FifoSQLiteRRQueueTest(FifoTestMixin, DiskTestMixin, base.RRQueueTestBase):\n\n    def qfactory(self, key):\n        path = os.path.join(self.qdir, str(key))\n        return track_closed(FifoSQLiteQueue)(path)\n\n\nclass LifoSQLiteRRQueueTest(LifoTestMixin, DiskTestMixin, base.RRQueueTestBase):\n\n    def qfactory(self, key):\n        path = os.path.join(self.qdir, str(key))\n        return track_closed(LifoSQLiteQueue)(path)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib-1.5.0.dist-info/DESCRIPTION.rst",
    "content": "========\nqueuelib\n========\n\n.. image:: https://secure.travis-ci.org/scrapy/queuelib.png?branch=master\n   :target: http://travis-ci.org/scrapy/queuelib\n\n.. image:: https://img.shields.io/codecov/c/github/scrapy/queuelib/master.svg\n   :target: http://codecov.io/github/scrapy/queuelib?branch=master\n   :alt: Coverage report\n\n\nQueuelib is a collection of persistent (disk-based) queues for Python.\n\nQueuelib goals are speed and simplicity. It was originally part of the `Scrapy\nframework`_ and stripped out on its own library.\n\nNote: Queuelib isn't thread-safe.\n\nRequirements\n============\n\n* Python 2.7 or Python 3.3\n* no external library requirements\n\nInstallation\n============\n\nYou can install Queuelib either via the Python Package Index (PyPI) or from\nsource.\n\nTo install using pip::\n\n    $ pip install queuelib\n\nTo install using easy_install::\n\n    $ easy_install queuelib\n\nIf you have downloaded a source tarball you can install it by running the\nfollowing (as root)::\n\n    # python setup.py install\n\nFIFO/LIFO disk queues\n=====================\n\nQueuelib provides FIFO and LIFO queue implementations.\n\nHere is an example usage of the FIFO queue::\n\n    >>> from queuelib import FifoDiskQueue\n    >>> q = FifoDiskQueue(\"queuefile\")\n    >>> q.push(b'a')\n    >>> q.push(b'b')\n    >>> q.push(b'c')\n    >>> q.pop()\n    b'a'\n    >>> q.close()\n    >>> q = FifoDiskQueue(\"queuefile\")\n    >>> q.pop()\n    b'b'\n    >>> q.pop()\n    b'c'\n    >>> q.pop()\n    >>>\n\nThe LIFO queue is identical (API-wise), but importing ``LifoDiskQueue``\ninstead.\n\nPriorityQueue\n=============\n\nA discrete-priority queue implemented by combining multiple FIFO/LIFO queues\n(one per priority).\n\nFirst, select the type of queue to be used per priority (FIFO or LIFO)::\n\n    >>> from queuelib import FifoDiskQueue\n    >>> qfactory = lambda priority: FifoDiskQueue('queue-dir-%s' % priority)\n\nThen instantiate the Priority Queue with it::\n\n    >>> from queuelib import PriorityQueue\n    >>> pq = PriorityQueue(qfactory)\n\nAnd use it::\n\n    >>> pq.push(b'a', 3)\n    >>> pq.push(b'b', 1)\n    >>> pq.push(b'c', 2)\n    >>> pq.push(b'd', 2)\n    >>> pq.pop()\n    b'b'\n    >>> pq.pop()\n    b'c'\n    >>> pq.pop()\n    b'd'\n    >>> pq.pop()\n    b'a'\n\nRoundRobinQueue\n===============\n\nHas nearly the same interface and implementation as a Priority Queue except\nthat each element must be pushed with a (mandatory) key.  Popping from the\nqueue cycles through the keys \"round robin\".\n\nInstantiate the Round Robin Queue similarly to the Priority Queue::\n\n    >>> from queuelib import RoundRobinQueue\n    >>> rr = RoundRobinQueue(qfactory)\n\nAnd use it::\n\n    >>> rr.push(b'a', '1')\n    >>> rr.push(b'b', '1')\n    >>> rr.push(b'c', '2')\n    >>> rr.push(b'd', '2')\n    >>> rr.pop()\n    b'a'\n    >>> rr.pop()\n    b'c'\n    >>> rr.pop()\n    b'b'\n    >>> rr.pop()\n    b'd'\n\n\nMailing list\n============\n\nUse the `scrapy-users`_ mailing list for questions about Queuelib.\n\nBug tracker\n===========\n\nIf you have any suggestions, bug reports or annoyances please report them to\nour issue tracker at: http://github.com/scrapy/queuelib/issues/\n\nContributing\n============\n\nDevelopment of Queuelib happens at GitHub: http://github.com/scrapy/queuelib\n\nYou are highly encouraged to participate in the development. If you don't like\nGitHub (for some reason) you're welcome to send regular patches.\n\nAll changes require tests to be merged.\n\nTests\n=====\n\nTests are located in `queuelib/tests` directory. They can be run using\n`nosetests`_ with the following command::\n\n    nosetests\n\nThe output should be something like the following::\n\n    $ nosetests\n    .............................................................................\n    ----------------------------------------------------------------------\n    Ran 77 tests in 0.145s\n\n    OK\n\nLicense\n=======\n\nThis software is licensed under the BSD License. See the LICENSE file in the\ntop distribution directory for the full license text.\n\nVersioning\n==========\n\nThis software follows `Semantic Versioning`_\n\n.. _Scrapy framework: http://scrapy.org\n.. _scrapy-users: http://groups.google.com/group/scrapy-users\n.. _Semantic Versioning: http://semver.org/\n.. _nosetests: https://nose.readthedocs.org/en/latest/\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib-1.5.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib-1.5.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.0\nName: queuelib\nVersion: 1.5.0\nSummary: Collection of persistent (disk-based) queues\nHome-page: https://github.com/scrapy/queuelib\nAuthor: Scrapy project\nAuthor-email: info@scrapy.org\nLicense: BSD\nDescription-Content-Type: UNKNOWN\nPlatform: Any\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: License :: OSI Approved :: BSD License\nClassifier: Operating System :: OS Independent\nClassifier: Programming Language :: Python\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: Implementation :: CPython\nClassifier: Programming Language :: Python :: Implementation :: PyPy\n\n========\nqueuelib\n========\n\n.. image:: https://secure.travis-ci.org/scrapy/queuelib.png?branch=master\n   :target: http://travis-ci.org/scrapy/queuelib\n\n.. image:: https://img.shields.io/codecov/c/github/scrapy/queuelib/master.svg\n   :target: http://codecov.io/github/scrapy/queuelib?branch=master\n   :alt: Coverage report\n\n\nQueuelib is a collection of persistent (disk-based) queues for Python.\n\nQueuelib goals are speed and simplicity. It was originally part of the `Scrapy\nframework`_ and stripped out on its own library.\n\nNote: Queuelib isn't thread-safe.\n\nRequirements\n============\n\n* Python 2.7 or Python 3.3\n* no external library requirements\n\nInstallation\n============\n\nYou can install Queuelib either via the Python Package Index (PyPI) or from\nsource.\n\nTo install using pip::\n\n    $ pip install queuelib\n\nTo install using easy_install::\n\n    $ easy_install queuelib\n\nIf you have downloaded a source tarball you can install it by running the\nfollowing (as root)::\n\n    # python setup.py install\n\nFIFO/LIFO disk queues\n=====================\n\nQueuelib provides FIFO and LIFO queue implementations.\n\nHere is an example usage of the FIFO queue::\n\n    >>> from queuelib import FifoDiskQueue\n    >>> q = FifoDiskQueue(\"queuefile\")\n    >>> q.push(b'a')\n    >>> q.push(b'b')\n    >>> q.push(b'c')\n    >>> q.pop()\n    b'a'\n    >>> q.close()\n    >>> q = FifoDiskQueue(\"queuefile\")\n    >>> q.pop()\n    b'b'\n    >>> q.pop()\n    b'c'\n    >>> q.pop()\n    >>>\n\nThe LIFO queue is identical (API-wise), but importing ``LifoDiskQueue``\ninstead.\n\nPriorityQueue\n=============\n\nA discrete-priority queue implemented by combining multiple FIFO/LIFO queues\n(one per priority).\n\nFirst, select the type of queue to be used per priority (FIFO or LIFO)::\n\n    >>> from queuelib import FifoDiskQueue\n    >>> qfactory = lambda priority: FifoDiskQueue('queue-dir-%s' % priority)\n\nThen instantiate the Priority Queue with it::\n\n    >>> from queuelib import PriorityQueue\n    >>> pq = PriorityQueue(qfactory)\n\nAnd use it::\n\n    >>> pq.push(b'a', 3)\n    >>> pq.push(b'b', 1)\n    >>> pq.push(b'c', 2)\n    >>> pq.push(b'd', 2)\n    >>> pq.pop()\n    b'b'\n    >>> pq.pop()\n    b'c'\n    >>> pq.pop()\n    b'd'\n    >>> pq.pop()\n    b'a'\n\nRoundRobinQueue\n===============\n\nHas nearly the same interface and implementation as a Priority Queue except\nthat each element must be pushed with a (mandatory) key.  Popping from the\nqueue cycles through the keys \"round robin\".\n\nInstantiate the Round Robin Queue similarly to the Priority Queue::\n\n    >>> from queuelib import RoundRobinQueue\n    >>> rr = RoundRobinQueue(qfactory)\n\nAnd use it::\n\n    >>> rr.push(b'a', '1')\n    >>> rr.push(b'b', '1')\n    >>> rr.push(b'c', '2')\n    >>> rr.push(b'd', '2')\n    >>> rr.pop()\n    b'a'\n    >>> rr.pop()\n    b'c'\n    >>> rr.pop()\n    b'b'\n    >>> rr.pop()\n    b'd'\n\n\nMailing list\n============\n\nUse the `scrapy-users`_ mailing list for questions about Queuelib.\n\nBug tracker\n===========\n\nIf you have any suggestions, bug reports or annoyances please report them to\nour issue tracker at: http://github.com/scrapy/queuelib/issues/\n\nContributing\n============\n\nDevelopment of Queuelib happens at GitHub: http://github.com/scrapy/queuelib\n\nYou are highly encouraged to participate in the development. If you don't like\nGitHub (for some reason) you're welcome to send regular patches.\n\nAll changes require tests to be merged.\n\nTests\n=====\n\nTests are located in `queuelib/tests` directory. They can be run using\n`nosetests`_ with the following command::\n\n    nosetests\n\nThe output should be something like the following::\n\n    $ nosetests\n    .............................................................................\n    ----------------------------------------------------------------------\n    Ran 77 tests in 0.145s\n\n    OK\n\nLicense\n=======\n\nThis software is licensed under the BSD License. See the LICENSE file in the\ntop distribution directory for the full license text.\n\nVersioning\n==========\n\nThis software follows `Semantic Versioning`_\n\n.. _Scrapy framework: http://scrapy.org\n.. _scrapy-users: http://groups.google.com/group/scrapy-users\n.. _Semantic Versioning: http://semver.org/\n.. _nosetests: https://nose.readthedocs.org/en/latest/\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib-1.5.0.dist-info/RECORD",
    "content": "queuelib-1.5.0.dist-info/DESCRIPTION.rst,sha256=wOZ7gK30mFMXlJ7J8D1rN6AXg3XraFndPvDiikNde7c,4194\r\nqueuelib-1.5.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nqueuelib-1.5.0.dist-info/METADATA,sha256=Ww2su8fmp1uPwtuzpq1SLEvLnPoIv6BqS9WAIQXQj7Y,5045\r\nqueuelib-1.5.0.dist-info/RECORD,,\r\nqueuelib-1.5.0.dist-info/WHEEL,sha256=kdsN-5OJAZIiHN-iO4Rhl82KyS0bDWf4uBwMbkNafr8,110\r\nqueuelib-1.5.0.dist-info/metadata.json,sha256=j3xSzsedbmhNIvFA44r2hGF0WH3GQzPeQ_KzuiivuSc,983\r\nqueuelib-1.5.0.dist-info/top_level.txt,sha256=K5aGZGeeYAP2OiQ03OqirCqgGQU8rJwPVob9nju7wWY,9\r\nqueuelib/__init__.py,sha256=1c9YXkjG6tshmg3qUnkeP90SA4KUeFiBol5_S8M_1Aw,142\r\nqueuelib/__pycache__/__init__.cpython-36.pyc,,\r\nqueuelib/__pycache__/pqueue.cpython-36.pyc,,\r\nqueuelib/__pycache__/queue.cpython-36.pyc,,\r\nqueuelib/__pycache__/rrqueue.cpython-36.pyc,,\r\nqueuelib/pqueue.py,sha256=zgImA9IDcJCP0k_mIAHrombXJfEXdR1nNvgXLinXEsM,2014\r\nqueuelib/queue.py,sha256=gnv2nqzJNv8vEBaYP-HL-mQ5r9iVDmhK7iTeVJ4QAVw,6610\r\nqueuelib/rrqueue.py,sha256=TBH5JjEbaEHvzKhuDJ2FRextyDioBrotlWdgezpad2o,2213\r\nqueuelib/tests/__init__.py,sha256=ufueO6TUOg4XUcVA03Is2CYyHMALPHLmMSydpipzXuA,831\r\nqueuelib/tests/__pycache__/__init__.cpython-36.pyc,,\r\nqueuelib/tests/__pycache__/test_pqueue.cpython-36.pyc,,\r\nqueuelib/tests/__pycache__/test_queue.cpython-36.pyc,,\r\nqueuelib/tests/__pycache__/test_rrqueue.cpython-36.pyc,,\r\nqueuelib/tests/test_pqueue.py,sha256=g9g19guL1mtq5IDUFkcvlgs37GdbVjRJnNkjqx1DQ-o,5818\r\nqueuelib/tests/test_queue.py,sha256=d7GRbxkxjvOaEzZqhhwUSe5mrn892BPSd7KTPd7mwmU,6338\r\nqueuelib/tests/test_rrqueue.py,sha256=rxiCXIpjIAM9OlzUR3pRGYrGc9Xws06Bci3zeWiVsyo,4549\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib-1.5.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.30.0)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib-1.5.0.dist-info/metadata.json",
    "content": "{\"classifiers\": [\"Development Status :: 5 - Production/Stable\", \"License :: OSI Approved :: BSD License\", \"Operating System :: OS Independent\", \"Programming Language :: Python\", \"Programming Language :: Python :: 2\", \"Programming Language :: Python :: 2.7\", \"Programming Language :: Python :: 3\", \"Programming Language :: Python :: 3.3\", \"Programming Language :: Python :: 3.4\", \"Programming Language :: Python :: Implementation :: CPython\", \"Programming Language :: Python :: Implementation :: PyPy\"], \"description_content_type\": \"UNKNOWN\", \"extensions\": {\"python.details\": {\"contacts\": [{\"email\": \"info@scrapy.org\", \"name\": \"Scrapy project\", \"role\": \"author\"}], \"document_names\": {\"description\": \"DESCRIPTION.rst\"}, \"project_urls\": {\"Home\": \"https://github.com/scrapy/queuelib\"}}}, \"generator\": \"bdist_wheel (0.30.0)\", \"license\": \"BSD\", \"metadata_version\": \"2.0\", \"name\": \"queuelib\", \"platform\": \"Any\", \"summary\": \"Collection of persistent (disk-based) queues\", \"version\": \"1.5.0\"}"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/queuelib-1.5.0.dist-info/top_level.txt",
    "content": "queuelib\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis/__init__.py",
    "content": "from redis.client import Redis, StrictRedis\nfrom redis.connection import (\n    BlockingConnectionPool,\n    ConnectionPool,\n    Connection,\n    SSLConnection,\n    UnixDomainSocketConnection\n)\nfrom redis.utils import from_url\nfrom redis.exceptions import (\n    AuthenticationError,\n    BusyLoadingError,\n    ConnectionError,\n    DataError,\n    InvalidResponse,\n    PubSubError,\n    ReadOnlyError,\n    RedisError,\n    ResponseError,\n    TimeoutError,\n    WatchError\n)\n\n\ndef int_or_str(value):\n    try:\n        return int(value)\n    except ValueError:\n        return value\n\n\n__version__ = '3.3.11'\nVERSION = tuple(map(int_or_str, __version__.split('.')))\n\n__all__ = [\n    'Redis', 'StrictRedis', 'ConnectionPool', 'BlockingConnectionPool',\n    'Connection', 'SSLConnection', 'UnixDomainSocketConnection', 'from_url',\n    'AuthenticationError', 'BusyLoadingError', 'ConnectionError', 'DataError',\n    'InvalidResponse', 'PubSubError', 'ReadOnlyError', 'RedisError',\n    'ResponseError', 'TimeoutError', 'WatchError'\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis/_compat.py",
    "content": "\"\"\"Internal module for Python 2 backwards compatibility.\"\"\"\nimport errno\nimport socket\nimport sys\n\n\ndef sendall(sock, *args, **kwargs):\n    return sock.sendall(*args, **kwargs)\n\n\ndef shutdown(sock, *args, **kwargs):\n    return sock.shutdown(*args, **kwargs)\n\n\ndef ssl_wrap_socket(context, sock, *args, **kwargs):\n    return context.wrap_socket(sock, *args, **kwargs)\n\n\n# For Python older than 3.5, retry EINTR.\nif sys.version_info[0] < 3 or (sys.version_info[0] == 3 and\n                               sys.version_info[1] < 5):\n    # Adapted from https://bugs.python.org/review/23863/patch/14532/54418\n    import time\n\n    # Wrapper for handling interruptable system calls.\n    def _retryable_call(s, func, *args, **kwargs):\n        # Some modules (SSL) use the _fileobject wrapper directly and\n        # implement a smaller portion of the socket interface, thus we\n        # need to let them continue to do so.\n        timeout, deadline = None, 0.0\n        attempted = False\n        try:\n            timeout = s.gettimeout()\n        except AttributeError:\n            pass\n\n        if timeout:\n            deadline = time.time() + timeout\n\n        try:\n            while True:\n                if attempted and timeout:\n                    now = time.time()\n                    if now >= deadline:\n                        raise socket.error(errno.EWOULDBLOCK, \"timed out\")\n                    else:\n                        # Overwrite the timeout on the socket object\n                        # to take into account elapsed time.\n                        s.settimeout(deadline - now)\n                try:\n                    attempted = True\n                    return func(*args, **kwargs)\n                except socket.error as e:\n                    if e.args[0] == errno.EINTR:\n                        continue\n                    raise\n        finally:\n            # Set the existing timeout back for future\n            # calls.\n            if timeout:\n                s.settimeout(timeout)\n\n    def recv(sock, *args, **kwargs):\n        return _retryable_call(sock, sock.recv, *args, **kwargs)\n\n    def recv_into(sock, *args, **kwargs):\n        return _retryable_call(sock, sock.recv_into, *args, **kwargs)\n\nelse:  # Python 3.5 and above automatically retry EINTR\n    def recv(sock, *args, **kwargs):\n        return sock.recv(*args, **kwargs)\n\n    def recv_into(sock, *args, **kwargs):\n        return sock.recv_into(*args, **kwargs)\n\nif sys.version_info[0] < 3:\n    # In Python 3, the ssl module raises socket.timeout whereas it raises\n    # SSLError in Python 2. For compatibility between versions, ensure\n    # socket.timeout is raised for both.\n    import functools\n\n    try:\n        from ssl import SSLError as _SSLError\n    except ImportError:\n        class _SSLError(Exception):\n            \"\"\"A replacement in case ssl.SSLError is not available.\"\"\"\n            pass\n\n    _EXPECTED_SSL_TIMEOUT_MESSAGES = (\n        \"The handshake operation timed out\",\n        \"The read operation timed out\",\n        \"The write operation timed out\",\n    )\n\n    def _handle_ssl_timeout(func):\n        @functools.wraps(func)\n        def wrapper(*args, **kwargs):\n            try:\n                return func(*args, **kwargs)\n            except _SSLError as e:\n                message = len(e.args) == 1 and unicode(e.args[0]) or ''\n                if any(x in message for x in _EXPECTED_SSL_TIMEOUT_MESSAGES):\n                    # Raise socket.timeout for compatibility with Python 3.\n                    raise socket.timeout(*e.args)\n                raise\n        return wrapper\n\n    recv = _handle_ssl_timeout(recv)\n    recv_into = _handle_ssl_timeout(recv_into)\n    sendall = _handle_ssl_timeout(sendall)\n    shutdown = _handle_ssl_timeout(shutdown)\n    ssl_wrap_socket = _handle_ssl_timeout(ssl_wrap_socket)\n\nif sys.version_info[0] < 3:\n    from urllib import unquote\n    from urlparse import parse_qs, urlparse\n    from itertools import imap, izip\n    from string import letters as ascii_letters\n    from Queue import Queue\n\n    # special unicode handling for python2 to avoid UnicodeDecodeError\n    def safe_unicode(obj, *args):\n        \"\"\" return the unicode representation of obj \"\"\"\n        try:\n            return unicode(obj, *args)\n        except UnicodeDecodeError:\n            # obj is byte string\n            ascii_text = str(obj).encode('string_escape')\n            return unicode(ascii_text)\n\n    def iteritems(x):\n        return x.iteritems()\n\n    def iterkeys(x):\n        return x.iterkeys()\n\n    def itervalues(x):\n        return x.itervalues()\n\n    def nativestr(x):\n        return x if isinstance(x, str) else x.encode('utf-8', 'replace')\n\n    def next(x):\n        return x.next()\n\n    def byte_to_chr(x):\n        return x\n\n    unichr = unichr\n    xrange = xrange\n    basestring = basestring\n    unicode = unicode\n    long = long\n    BlockingIOError = socket.error\nelse:\n    from urllib.parse import parse_qs, unquote, urlparse\n    from string import ascii_letters\n    from queue import Queue\n\n    def iteritems(x):\n        return iter(x.items())\n\n    def iterkeys(x):\n        return iter(x.keys())\n\n    def itervalues(x):\n        return iter(x.values())\n\n    def byte_to_chr(x):\n        return chr(x)\n\n    def nativestr(x):\n        return x if isinstance(x, str) else x.decode('utf-8', 'replace')\n\n    next = next\n    unichr = chr\n    imap = map\n    izip = zip\n    xrange = range\n    basestring = str\n    unicode = str\n    safe_unicode = str\n    long = int\n    BlockingIOError = BlockingIOError\n\ntry:  # Python 3\n    from queue import LifoQueue, Empty, Full\nexcept ImportError:  # Python 2\n    from Queue import LifoQueue, Empty, Full\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis/client.py",
    "content": "from __future__ import unicode_literals\nfrom itertools import chain\nimport datetime\nimport sys\nimport warnings\nimport time\nimport threading\nimport time as mod_time\nimport re\nimport hashlib\nfrom redis._compat import (basestring, imap, iteritems, iterkeys,\n                           itervalues, izip, long, nativestr, safe_unicode)\nfrom redis.connection import (ConnectionPool, UnixDomainSocketConnection,\n                              SSLConnection)\nfrom redis.lock import Lock\nfrom redis.exceptions import (\n    ConnectionError,\n    DataError,\n    ExecAbortError,\n    NoScriptError,\n    PubSubError,\n    RedisError,\n    ResponseError,\n    TimeoutError,\n    WatchError,\n)\n\nSYM_EMPTY = b''\nEMPTY_RESPONSE = 'EMPTY_RESPONSE'\n\n\ndef list_or_args(keys, args):\n    # returns a single new list combining keys and args\n    try:\n        iter(keys)\n        # a string or bytes instance can be iterated, but indicates\n        # keys wasn't passed as a list\n        if isinstance(keys, (basestring, bytes)):\n            keys = [keys]\n        else:\n            keys = list(keys)\n    except TypeError:\n        keys = [keys]\n    if args:\n        keys.extend(args)\n    return keys\n\n\ndef timestamp_to_datetime(response):\n    \"Converts a unix timestamp to a Python datetime object\"\n    if not response:\n        return None\n    try:\n        response = int(response)\n    except ValueError:\n        return None\n    return datetime.datetime.fromtimestamp(response)\n\n\ndef string_keys_to_dict(key_string, callback):\n    return dict.fromkeys(key_string.split(), callback)\n\n\ndef dict_merge(*dicts):\n    merged = {}\n    for d in dicts:\n        merged.update(d)\n    return merged\n\n\nclass CaseInsensitiveDict(dict):\n    \"Case insensitive dict implementation. Assumes string keys only.\"\n\n    def __init__(self, data):\n        for k, v in iteritems(data):\n            self[k.upper()] = v\n\n    def __contains__(self, k):\n        return super(CaseInsensitiveDict, self).__contains__(k.upper())\n\n    def __delitem__(self, k):\n        super(CaseInsensitiveDict, self).__delitem__(k.upper())\n\n    def __getitem__(self, k):\n        return super(CaseInsensitiveDict, self).__getitem__(k.upper())\n\n    def get(self, k, default=None):\n        return super(CaseInsensitiveDict, self).get(k.upper(), default)\n\n    def __setitem__(self, k, v):\n        super(CaseInsensitiveDict, self).__setitem__(k.upper(), v)\n\n    def update(self, data):\n        data = CaseInsensitiveDict(data)\n        super(CaseInsensitiveDict, self).update(data)\n\n\ndef parse_debug_object(response):\n    \"Parse the results of Redis's DEBUG OBJECT command into a Python dict\"\n    # The 'type' of the object is the first item in the response, but isn't\n    # prefixed with a name\n    response = nativestr(response)\n    response = 'type:' + response\n    response = dict(kv.split(':') for kv in response.split())\n\n    # parse some expected int values from the string response\n    # note: this cmd isn't spec'd so these may not appear in all redis versions\n    int_fields = ('refcount', 'serializedlength', 'lru', 'lru_seconds_idle')\n    for field in int_fields:\n        if field in response:\n            response[field] = int(response[field])\n\n    return response\n\n\ndef parse_object(response, infotype):\n    \"Parse the results of an OBJECT command\"\n    if infotype in ('idletime', 'refcount'):\n        return int_or_none(response)\n    return response\n\n\ndef parse_info(response):\n    \"Parse the result of Redis's INFO command into a Python dict\"\n    info = {}\n    response = nativestr(response)\n\n    def get_value(value):\n        if ',' not in value or '=' not in value:\n            try:\n                if '.' in value:\n                    return float(value)\n                else:\n                    return int(value)\n            except ValueError:\n                return value\n        else:\n            sub_dict = {}\n            for item in value.split(','):\n                k, v = item.rsplit('=', 1)\n                sub_dict[k] = get_value(v)\n            return sub_dict\n\n    for line in response.splitlines():\n        if line and not line.startswith('#'):\n            if line.find(':') != -1:\n                # Split, the info fields keys and values.\n                # Note that the value may contain ':'. but the 'host:'\n                # pseudo-command is the only case where the key contains ':'\n                key, value = line.split(':', 1)\n                if key == 'cmdstat_host':\n                    key, value = line.rsplit(':', 1)\n                info[key] = get_value(value)\n            else:\n                # if the line isn't splittable, append it to the \"__raw__\" key\n                info.setdefault('__raw__', []).append(line)\n\n    return info\n\n\nSENTINEL_STATE_TYPES = {\n    'can-failover-its-master': int,\n    'config-epoch': int,\n    'down-after-milliseconds': int,\n    'failover-timeout': int,\n    'info-refresh': int,\n    'last-hello-message': int,\n    'last-ok-ping-reply': int,\n    'last-ping-reply': int,\n    'last-ping-sent': int,\n    'master-link-down-time': int,\n    'master-port': int,\n    'num-other-sentinels': int,\n    'num-slaves': int,\n    'o-down-time': int,\n    'pending-commands': int,\n    'parallel-syncs': int,\n    'port': int,\n    'quorum': int,\n    'role-reported-time': int,\n    's-down-time': int,\n    'slave-priority': int,\n    'slave-repl-offset': int,\n    'voted-leader-epoch': int\n}\n\n\ndef parse_sentinel_state(item):\n    result = pairs_to_dict_typed(item, SENTINEL_STATE_TYPES)\n    flags = set(result['flags'].split(','))\n    for name, flag in (('is_master', 'master'), ('is_slave', 'slave'),\n                       ('is_sdown', 's_down'), ('is_odown', 'o_down'),\n                       ('is_sentinel', 'sentinel'),\n                       ('is_disconnected', 'disconnected'),\n                       ('is_master_down', 'master_down')):\n        result[name] = flag in flags\n    return result\n\n\ndef parse_sentinel_master(response):\n    return parse_sentinel_state(imap(nativestr, response))\n\n\ndef parse_sentinel_masters(response):\n    result = {}\n    for item in response:\n        state = parse_sentinel_state(imap(nativestr, item))\n        result[state['name']] = state\n    return result\n\n\ndef parse_sentinel_slaves_and_sentinels(response):\n    return [parse_sentinel_state(imap(nativestr, item)) for item in response]\n\n\ndef parse_sentinel_get_master(response):\n    return response and (response[0], int(response[1])) or None\n\n\ndef pairs_to_dict(response, decode_keys=False):\n    \"Create a dict given a list of key/value pairs\"\n    if response is None:\n        return {}\n    if decode_keys:\n        # the iter form is faster, but I don't know how to make that work\n        # with a nativestr() map\n        return dict(izip(imap(nativestr, response[::2]), response[1::2]))\n    else:\n        it = iter(response)\n        return dict(izip(it, it))\n\n\ndef pairs_to_dict_typed(response, type_info):\n    it = iter(response)\n    result = {}\n    for key, value in izip(it, it):\n        if key in type_info:\n            try:\n                value = type_info[key](value)\n            except Exception:\n                # if for some reason the value can't be coerced, just use\n                # the string value\n                pass\n        result[key] = value\n    return result\n\n\ndef zset_score_pairs(response, **options):\n    \"\"\"\n    If ``withscores`` is specified in the options, return the response as\n    a list of (value, score) pairs\n    \"\"\"\n    if not response or not options.get('withscores'):\n        return response\n    score_cast_func = options.get('score_cast_func', float)\n    it = iter(response)\n    return list(izip(it, imap(score_cast_func, it)))\n\n\ndef sort_return_tuples(response, **options):\n    \"\"\"\n    If ``groups`` is specified, return the response as a list of\n    n-element tuples with n being the value found in options['groups']\n    \"\"\"\n    if not response or not options.get('groups'):\n        return response\n    n = options['groups']\n    return list(izip(*[response[i::n] for i in range(n)]))\n\n\ndef int_or_none(response):\n    if response is None:\n        return None\n    return int(response)\n\n\ndef nativestr_or_none(response):\n    if response is None:\n        return None\n    return nativestr(response)\n\n\ndef parse_stream_list(response):\n    if response is None:\n        return None\n    data = []\n    for r in response:\n        if r is not None:\n            data.append((r[0], pairs_to_dict(r[1])))\n        else:\n            data.append((None, None))\n    return data\n\n\ndef pairs_to_dict_with_nativestr_keys(response):\n    return pairs_to_dict(response, decode_keys=True)\n\n\ndef parse_list_of_dicts(response):\n    return list(imap(pairs_to_dict_with_nativestr_keys, response))\n\n\ndef parse_xclaim(response, **options):\n    if options.get('parse_justid', False):\n        return response\n    return parse_stream_list(response)\n\n\ndef parse_xinfo_stream(response):\n    data = pairs_to_dict(response, decode_keys=True)\n    first = data['first-entry']\n    if first is not None:\n        data['first-entry'] = (first[0], pairs_to_dict(first[1]))\n    last = data['last-entry']\n    if last is not None:\n        data['last-entry'] = (last[0], pairs_to_dict(last[1]))\n    return data\n\n\ndef parse_xread(response):\n    if response is None:\n        return []\n    return [[r[0], parse_stream_list(r[1])] for r in response]\n\n\ndef parse_xpending(response, **options):\n    if options.get('parse_detail', False):\n        return parse_xpending_range(response)\n    consumers = [{'name': n, 'pending': long(p)} for n, p in response[3] or []]\n    return {\n        'pending': response[0],\n        'min': response[1],\n        'max': response[2],\n        'consumers': consumers\n    }\n\n\ndef parse_xpending_range(response):\n    k = ('message_id', 'consumer', 'time_since_delivered', 'times_delivered')\n    return [dict(izip(k, r)) for r in response]\n\n\ndef float_or_none(response):\n    if response is None:\n        return None\n    return float(response)\n\n\ndef bool_ok(response):\n    return nativestr(response) == 'OK'\n\n\ndef parse_zadd(response, **options):\n    if response is None:\n        return None\n    if options.get('as_score'):\n        return float(response)\n    return int(response)\n\n\ndef parse_client_list(response, **options):\n    clients = []\n    for c in nativestr(response).splitlines():\n        # Values might contain '='\n        clients.append(dict(pair.split('=', 1) for pair in c.split(' ')))\n    return clients\n\n\ndef parse_config_get(response, **options):\n    response = [nativestr(i) if i is not None else None for i in response]\n    return response and pairs_to_dict(response) or {}\n\n\ndef parse_scan(response, **options):\n    cursor, r = response\n    return long(cursor), r\n\n\ndef parse_hscan(response, **options):\n    cursor, r = response\n    return long(cursor), r and pairs_to_dict(r) or {}\n\n\ndef parse_zscan(response, **options):\n    score_cast_func = options.get('score_cast_func', float)\n    cursor, r = response\n    it = iter(r)\n    return long(cursor), list(izip(it, imap(score_cast_func, it)))\n\n\ndef parse_slowlog_get(response, **options):\n    return [{\n        'id': item[0],\n        'start_time': int(item[1]),\n        'duration': int(item[2]),\n        'command': b' '.join(item[3])\n    } for item in response]\n\n\ndef parse_cluster_info(response, **options):\n    response = nativestr(response)\n    return dict(line.split(':') for line in response.splitlines() if line)\n\n\ndef _parse_node_line(line):\n    line_items = line.split(' ')\n    node_id, addr, flags, master_id, ping, pong, epoch, \\\n        connected = line.split(' ')[:8]\n    slots = [sl.split('-') for sl in line_items[8:]]\n    node_dict = {\n        'node_id': node_id,\n        'flags': flags,\n        'master_id': master_id,\n        'last_ping_sent': ping,\n        'last_pong_rcvd': pong,\n        'epoch': epoch,\n        'slots': slots,\n        'connected': True if connected == 'connected' else False\n    }\n    return addr, node_dict\n\n\ndef parse_cluster_nodes(response, **options):\n    response = nativestr(response)\n    raw_lines = response\n    if isinstance(response, basestring):\n        raw_lines = response.splitlines()\n    return dict(_parse_node_line(line) for line in raw_lines)\n\n\ndef parse_georadius_generic(response, **options):\n    if options['store'] or options['store_dist']:\n        # `store` and `store_diff` cant be combined\n        # with other command arguments.\n        return response\n\n    if type(response) != list:\n        response_list = [response]\n    else:\n        response_list = response\n\n    if not options['withdist'] and not options['withcoord']\\\n            and not options['withhash']:\n        # just a bunch of places\n        return response_list\n\n    cast = {\n        'withdist': float,\n        'withcoord': lambda ll: (float(ll[0]), float(ll[1])),\n        'withhash': int\n    }\n\n    # zip all output results with each casting functino to get\n    # the properly native Python value.\n    f = [lambda x: x]\n    f += [cast[o] for o in ['withdist', 'withhash', 'withcoord'] if options[o]]\n    return [\n        list(map(lambda fv: fv[0](fv[1]), zip(f, r))) for r in response_list\n    ]\n\n\ndef parse_pubsub_numsub(response, **options):\n    return list(zip(response[0::2], response[1::2]))\n\n\ndef parse_client_kill(response, **options):\n    if isinstance(response, (long, int)):\n        return int(response)\n    return nativestr(response) == 'OK'\n\n\nclass Redis(object):\n    \"\"\"\n    Implementation of the Redis protocol.\n\n    This abstract class provides a Python interface to all Redis commands\n    and an implementation of the Redis protocol.\n\n    Connection and Pipeline derive from this, implementing how\n    the commands are sent and received to the Redis server\n    \"\"\"\n    RESPONSE_CALLBACKS = dict_merge(\n        string_keys_to_dict(\n            'AUTH EXPIRE EXPIREAT HEXISTS HMSET MOVE MSETNX PERSIST '\n            'PSETEX RENAMENX SISMEMBER SMOVE SETEX SETNX',\n            bool\n        ),\n        string_keys_to_dict(\n            'BITCOUNT BITPOS DECRBY DEL EXISTS GEOADD GETBIT HDEL HLEN '\n            'HSTRLEN INCRBY LINSERT LLEN LPUSHX PFADD PFCOUNT RPUSHX SADD '\n            'SCARD SDIFFSTORE SETBIT SETRANGE SINTERSTORE SREM STRLEN '\n            'SUNIONSTORE UNLINK XACK XDEL XLEN XTRIM ZCARD ZLEXCOUNT ZREM '\n            'ZREMRANGEBYLEX ZREMRANGEBYRANK ZREMRANGEBYSCORE',\n            int\n        ),\n        string_keys_to_dict(\n            'INCRBYFLOAT HINCRBYFLOAT',\n            float\n        ),\n        string_keys_to_dict(\n            # these return OK, or int if redis-server is >=1.3.4\n            'LPUSH RPUSH',\n            lambda r: isinstance(r, (long, int)) and r or nativestr(r) == 'OK'\n        ),\n        string_keys_to_dict('SORT', sort_return_tuples),\n        string_keys_to_dict('ZSCORE ZINCRBY GEODIST', float_or_none),\n        string_keys_to_dict(\n            'FLUSHALL FLUSHDB LSET LTRIM MSET PFMERGE READONLY READWRITE '\n            'RENAME SAVE SELECT SHUTDOWN SLAVEOF SWAPDB WATCH UNWATCH ',\n            bool_ok\n        ),\n        string_keys_to_dict('BLPOP BRPOP', lambda r: r and tuple(r) or None),\n        string_keys_to_dict(\n            'SDIFF SINTER SMEMBERS SUNION',\n            lambda r: r and set(r) or set()\n        ),\n        string_keys_to_dict(\n            'ZPOPMAX ZPOPMIN ZRANGE ZRANGEBYSCORE ZREVRANGE ZREVRANGEBYSCORE',\n            zset_score_pairs\n        ),\n        string_keys_to_dict('BZPOPMIN BZPOPMAX', \\\n                            lambda r: r and (r[0], r[1], float(r[2])) or None),\n        string_keys_to_dict('ZRANK ZREVRANK', int_or_none),\n        string_keys_to_dict('XREVRANGE XRANGE', parse_stream_list),\n        string_keys_to_dict('XREAD XREADGROUP', parse_xread),\n        string_keys_to_dict('BGREWRITEAOF BGSAVE', lambda r: True),\n        {\n            'CLIENT GETNAME': lambda r: r and nativestr(r),\n            'CLIENT ID': int,\n            'CLIENT KILL': parse_client_kill,\n            'CLIENT LIST': parse_client_list,\n            'CLIENT SETNAME': bool_ok,\n            'CLIENT UNBLOCK': lambda r: r and int(r) == 1 or False,\n            'CLIENT PAUSE': bool_ok,\n            'CLUSTER ADDSLOTS': bool_ok,\n            'CLUSTER COUNT-FAILURE-REPORTS': lambda x: int(x),\n            'CLUSTER COUNTKEYSINSLOT': lambda x: int(x),\n            'CLUSTER DELSLOTS': bool_ok,\n            'CLUSTER FAILOVER': bool_ok,\n            'CLUSTER FORGET': bool_ok,\n            'CLUSTER INFO': parse_cluster_info,\n            'CLUSTER KEYSLOT': lambda x: int(x),\n            'CLUSTER MEET': bool_ok,\n            'CLUSTER NODES': parse_cluster_nodes,\n            'CLUSTER REPLICATE': bool_ok,\n            'CLUSTER RESET': bool_ok,\n            'CLUSTER SAVECONFIG': bool_ok,\n            'CLUSTER SET-CONFIG-EPOCH': bool_ok,\n            'CLUSTER SETSLOT': bool_ok,\n            'CLUSTER SLAVES': parse_cluster_nodes,\n            'CONFIG GET': parse_config_get,\n            'CONFIG RESETSTAT': bool_ok,\n            'CONFIG SET': bool_ok,\n            'DEBUG OBJECT': parse_debug_object,\n            'GEOHASH': lambda r: list(map(nativestr_or_none, r)),\n            'GEOPOS': lambda r: list(map(lambda ll: (float(ll[0]),\n                                         float(ll[1]))\n                                         if ll is not None else None, r)),\n            'GEORADIUS': parse_georadius_generic,\n            'GEORADIUSBYMEMBER': parse_georadius_generic,\n            'HGETALL': lambda r: r and pairs_to_dict(r) or {},\n            'HSCAN': parse_hscan,\n            'INFO': parse_info,\n            'LASTSAVE': timestamp_to_datetime,\n            'MEMORY PURGE': bool_ok,\n            'MEMORY USAGE': int_or_none,\n            'OBJECT': parse_object,\n            'PING': lambda r: nativestr(r) == 'PONG',\n            'PUBSUB NUMSUB': parse_pubsub_numsub,\n            'RANDOMKEY': lambda r: r and r or None,\n            'SCAN': parse_scan,\n            'SCRIPT EXISTS': lambda r: list(imap(bool, r)),\n            'SCRIPT FLUSH': bool_ok,\n            'SCRIPT KILL': bool_ok,\n            'SCRIPT LOAD': nativestr,\n            'SENTINEL GET-MASTER-ADDR-BY-NAME': parse_sentinel_get_master,\n            'SENTINEL MASTER': parse_sentinel_master,\n            'SENTINEL MASTERS': parse_sentinel_masters,\n            'SENTINEL MONITOR': bool_ok,\n            'SENTINEL REMOVE': bool_ok,\n            'SENTINEL SENTINELS': parse_sentinel_slaves_and_sentinels,\n            'SENTINEL SET': bool_ok,\n            'SENTINEL SLAVES': parse_sentinel_slaves_and_sentinels,\n            'SET': lambda r: r and nativestr(r) == 'OK',\n            'SLOWLOG GET': parse_slowlog_get,\n            'SLOWLOG LEN': int,\n            'SLOWLOG RESET': bool_ok,\n            'SSCAN': parse_scan,\n            'TIME': lambda x: (int(x[0]), int(x[1])),\n            'XCLAIM': parse_xclaim,\n            'XGROUP CREATE': bool_ok,\n            'XGROUP DELCONSUMER': int,\n            'XGROUP DESTROY': bool,\n            'XGROUP SETID': bool_ok,\n            'XINFO CONSUMERS': parse_list_of_dicts,\n            'XINFO GROUPS': parse_list_of_dicts,\n            'XINFO STREAM': parse_xinfo_stream,\n            'XPENDING': parse_xpending,\n            'ZADD': parse_zadd,\n            'ZSCAN': parse_zscan,\n        }\n    )\n\n    @classmethod\n    def from_url(cls, url, db=None, **kwargs):\n        \"\"\"\n        Return a Redis client object configured from the given URL\n\n        For example::\n\n            redis://[:password]@localhost:6379/0\n            rediss://[:password]@localhost:6379/0\n            unix://[:password]@/path/to/socket.sock?db=0\n\n        Three URL schemes are supported:\n\n        - ```redis://``\n          <http://www.iana.org/assignments/uri-schemes/prov/redis>`_ creates a\n          normal TCP socket connection\n        - ```rediss://``\n          <http://www.iana.org/assignments/uri-schemes/prov/rediss>`_ creates a\n          SSL wrapped TCP socket connection\n        - ``unix://`` creates a Unix Domain Socket connection\n\n        There are several ways to specify a database number. The parse function\n        will return the first specified option:\n            1. A ``db`` querystring option, e.g. redis://localhost?db=0\n            2. If using the redis:// scheme, the path argument of the url, e.g.\n               redis://localhost/0\n            3. The ``db`` argument to this function.\n\n        If none of these options are specified, db=0 is used.\n\n        Any additional querystring arguments and keyword arguments will be\n        passed along to the ConnectionPool class's initializer. In the case\n        of conflicting arguments, querystring arguments always win.\n        \"\"\"\n        connection_pool = ConnectionPool.from_url(url, db=db, **kwargs)\n        return cls(connection_pool=connection_pool)\n\n    def __init__(self, host='localhost', port=6379,\n                 db=0, password=None, socket_timeout=None,\n                 socket_connect_timeout=None,\n                 socket_keepalive=None, socket_keepalive_options=None,\n                 connection_pool=None, unix_socket_path=None,\n                 encoding='utf-8', encoding_errors='strict',\n                 charset=None, errors=None,\n                 decode_responses=False, retry_on_timeout=False,\n                 ssl=False, ssl_keyfile=None, ssl_certfile=None,\n                 ssl_cert_reqs='required', ssl_ca_certs=None,\n                 max_connections=None, single_connection_client=False,\n                 health_check_interval=0):\n        if not connection_pool:\n            if charset is not None:\n                warnings.warn(DeprecationWarning(\n                    '\"charset\" is deprecated. Use \"encoding\" instead'))\n                encoding = charset\n            if errors is not None:\n                warnings.warn(DeprecationWarning(\n                    '\"errors\" is deprecated. Use \"encoding_errors\" instead'))\n                encoding_errors = errors\n\n            kwargs = {\n                'db': db,\n                'password': password,\n                'socket_timeout': socket_timeout,\n                'encoding': encoding,\n                'encoding_errors': encoding_errors,\n                'decode_responses': decode_responses,\n                'retry_on_timeout': retry_on_timeout,\n                'max_connections': max_connections,\n                'health_check_interval': health_check_interval,\n            }\n            # based on input, setup appropriate connection args\n            if unix_socket_path is not None:\n                kwargs.update({\n                    'path': unix_socket_path,\n                    'connection_class': UnixDomainSocketConnection\n                })\n            else:\n                # TCP specific options\n                kwargs.update({\n                    'host': host,\n                    'port': port,\n                    'socket_connect_timeout': socket_connect_timeout,\n                    'socket_keepalive': socket_keepalive,\n                    'socket_keepalive_options': socket_keepalive_options,\n                })\n\n                if ssl:\n                    kwargs.update({\n                        'connection_class': SSLConnection,\n                        'ssl_keyfile': ssl_keyfile,\n                        'ssl_certfile': ssl_certfile,\n                        'ssl_cert_reqs': ssl_cert_reqs,\n                        'ssl_ca_certs': ssl_ca_certs,\n                    })\n            connection_pool = ConnectionPool(**kwargs)\n        self.connection_pool = connection_pool\n        self.connection = None\n        if single_connection_client:\n            self.connection = self.connection_pool.get_connection('_')\n\n        self.response_callbacks = CaseInsensitiveDict(\n            self.__class__.RESPONSE_CALLBACKS)\n\n    def __repr__(self):\n        return \"%s<%s>\" % (type(self).__name__, repr(self.connection_pool))\n\n    def set_response_callback(self, command, callback):\n        \"Set a custom Response Callback\"\n        self.response_callbacks[command] = callback\n\n    def pipeline(self, transaction=True, shard_hint=None):\n        \"\"\"\n        Return a new pipeline object that can queue multiple commands for\n        later execution. ``transaction`` indicates whether all commands\n        should be executed atomically. Apart from making a group of operations\n        atomic, pipelines are useful for reducing the back-and-forth overhead\n        between the client and server.\n        \"\"\"\n        return Pipeline(\n            self.connection_pool,\n            self.response_callbacks,\n            transaction,\n            shard_hint)\n\n    def transaction(self, func, *watches, **kwargs):\n        \"\"\"\n        Convenience method for executing the callable `func` as a transaction\n        while watching all keys specified in `watches`. The 'func' callable\n        should expect a single argument which is a Pipeline object.\n        \"\"\"\n        shard_hint = kwargs.pop('shard_hint', None)\n        value_from_callable = kwargs.pop('value_from_callable', False)\n        watch_delay = kwargs.pop('watch_delay', None)\n        with self.pipeline(True, shard_hint) as pipe:\n            while True:\n                try:\n                    if watches:\n                        pipe.watch(*watches)\n                    func_value = func(pipe)\n                    exec_value = pipe.execute()\n                    return func_value if value_from_callable else exec_value\n                except WatchError:\n                    if watch_delay is not None and watch_delay > 0:\n                        time.sleep(watch_delay)\n                    continue\n\n    def lock(self, name, timeout=None, sleep=0.1, blocking_timeout=None,\n             lock_class=None, thread_local=True):\n        \"\"\"\n        Return a new Lock object using key ``name`` that mimics\n        the behavior of threading.Lock.\n\n        If specified, ``timeout`` indicates a maximum life for the lock.\n        By default, it will remain locked until release() is called.\n\n        ``sleep`` indicates the amount of time to sleep per loop iteration\n        when the lock is in blocking mode and another client is currently\n        holding the lock.\n\n        ``blocking_timeout`` indicates the maximum amount of time in seconds to\n        spend trying to acquire the lock. A value of ``None`` indicates\n        continue trying forever. ``blocking_timeout`` can be specified as a\n        float or integer, both representing the number of seconds to wait.\n\n        ``lock_class`` forces the specified lock implementation.\n\n        ``thread_local`` indicates whether the lock token is placed in\n        thread-local storage. By default, the token is placed in thread local\n        storage so that a thread only sees its token, not a token set by\n        another thread. Consider the following timeline:\n\n            time: 0, thread-1 acquires `my-lock`, with a timeout of 5 seconds.\n                     thread-1 sets the token to \"abc\"\n            time: 1, thread-2 blocks trying to acquire `my-lock` using the\n                     Lock instance.\n            time: 5, thread-1 has not yet completed. redis expires the lock\n                     key.\n            time: 5, thread-2 acquired `my-lock` now that it's available.\n                     thread-2 sets the token to \"xyz\"\n            time: 6, thread-1 finishes its work and calls release(). if the\n                     token is *not* stored in thread local storage, then\n                     thread-1 would see the token value as \"xyz\" and would be\n                     able to successfully release the thread-2's lock.\n\n        In some use cases it's necessary to disable thread local storage. For\n        example, if you have code where one thread acquires a lock and passes\n        that lock instance to a worker thread to release later. If thread\n        local storage isn't disabled in this case, the worker thread won't see\n        the token set by the thread that acquired the lock. Our assumption\n        is that these cases aren't common and as such default to using\n        thread local storage.        \"\"\"\n        if lock_class is None:\n            lock_class = Lock\n        return lock_class(self, name, timeout=timeout, sleep=sleep,\n                          blocking_timeout=blocking_timeout,\n                          thread_local=thread_local)\n\n    def pubsub(self, **kwargs):\n        \"\"\"\n        Return a Publish/Subscribe object. With this object, you can\n        subscribe to channels and listen for messages that get published to\n        them.\n        \"\"\"\n        return PubSub(self.connection_pool, **kwargs)\n\n    def monitor(self):\n        return Monitor(self.connection_pool)\n\n    def client(self):\n        return self.__class__(connection_pool=self.connection_pool,\n                              single_connection_client=True)\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_value, traceback):\n        self.close()\n\n    def __del__(self):\n        self.close()\n\n    def close(self):\n        conn = self.connection\n        if conn:\n            self.connection = None\n            self.connection_pool.release(conn)\n\n    # COMMAND EXECUTION AND PROTOCOL PARSING\n    def execute_command(self, *args, **options):\n        \"Execute a command and return a parsed response\"\n        pool = self.connection_pool\n        command_name = args[0]\n        conn = self.connection or pool.get_connection(command_name, **options)\n        try:\n            conn.send_command(*args)\n            return self.parse_response(conn, command_name, **options)\n        except (ConnectionError, TimeoutError) as e:\n            conn.disconnect()\n            if not (conn.retry_on_timeout and isinstance(e, TimeoutError)):\n                raise\n            conn.send_command(*args)\n            return self.parse_response(conn, command_name, **options)\n        finally:\n            if not self.connection:\n                pool.release(conn)\n\n    def parse_response(self, connection, command_name, **options):\n        \"Parses a response from the Redis server\"\n        try:\n            response = connection.read_response()\n        except ResponseError:\n            if EMPTY_RESPONSE in options:\n                return options[EMPTY_RESPONSE]\n            raise\n        if command_name in self.response_callbacks:\n            return self.response_callbacks[command_name](response, **options)\n        return response\n\n    # SERVER INFORMATION\n    def bgrewriteaof(self):\n        \"Tell the Redis server to rewrite the AOF file from data in memory.\"\n        return self.execute_command('BGREWRITEAOF')\n\n    def bgsave(self):\n        \"\"\"\n        Tell the Redis server to save its data to disk.  Unlike save(),\n        this method is asynchronous and returns immediately.\n        \"\"\"\n        return self.execute_command('BGSAVE')\n\n    def client_kill(self, address):\n        \"Disconnects the client at ``address`` (ip:port)\"\n        return self.execute_command('CLIENT KILL', address)\n\n    def client_kill_filter(self, _id=None, _type=None, addr=None, skipme=None):\n        \"\"\"\n        Disconnects client(s) using a variety of filter options\n        :param id: Kills a client by its unique ID field\n        :param type: Kills a client by type where type is one of 'normal',\n        'master', 'slave' or 'pubsub'\n        :param addr: Kills a client by its 'address:port'\n        :param skipme: If True, then the client calling the command\n        will not get killed even if it is identified by one of the filter\n        options. If skipme is not provided, the server defaults to skipme=True\n        \"\"\"\n        args = []\n        if _type is not None:\n            client_types = ('normal', 'master', 'slave', 'pubsub')\n            if str(_type).lower() not in client_types:\n                raise DataError(\"CLIENT KILL type must be one of %r\" % (\n                                client_types,))\n            args.extend((b'TYPE', _type))\n        if skipme is not None:\n            if not isinstance(skipme, bool):\n                raise DataError(\"CLIENT KILL skipme must be a bool\")\n            if skipme:\n                args.extend((b'SKIPME', b'YES'))\n            else:\n                args.extend((b'SKIPME', b'NO'))\n        if _id is not None:\n            args.extend((b'ID', _id))\n        if addr is not None:\n            args.extend((b'ADDR', addr))\n        if not args:\n            raise DataError(\"CLIENT KILL <filter> <value> ... ... <filter> \"\n                            \"<value> must specify at least one filter\")\n        return self.execute_command('CLIENT KILL', *args)\n\n    def client_list(self, _type=None):\n        \"\"\"\n        Returns a list of currently connected clients.\n        If type of client specified, only that type will be returned.\n        :param _type: optional. one of the client types (normal, master,\n         replica, pubsub)\n        \"\"\"\n        \"Returns a list of currently connected clients\"\n        if _type is not None:\n            client_types = ('normal', 'master', 'replica', 'pubsub')\n            if str(_type).lower() not in client_types:\n                raise DataError(\"CLIENT LIST _type must be one of %r\" % (\n                                client_types,))\n            return self.execute_command('CLIENT LIST', b'TYPE', _type)\n        return self.execute_command('CLIENT LIST')\n\n    def client_getname(self):\n        \"Returns the current connection name\"\n        return self.execute_command('CLIENT GETNAME')\n\n    def client_id(self):\n        \"Returns the current connection id\"\n        return self.execute_command('CLIENT ID')\n\n    def client_setname(self, name):\n        \"Sets the current connection name\"\n        return self.execute_command('CLIENT SETNAME', name)\n\n    def client_unblock(self, client_id, error=False):\n        \"\"\"\n        Unblocks a connection by its client id.\n        If ``error`` is True, unblocks the client with a special error message.\n        If ``error`` is False (default), the client is unblocked using the\n        regular timeout mechanism.\n        \"\"\"\n        args = ['CLIENT UNBLOCK', int(client_id)]\n        if error:\n            args.append(b'ERROR')\n        return self.execute_command(*args)\n\n    def client_pause(self, timeout):\n        \"\"\"\n        Suspend all the Redis clients for the specified amount of time\n        :param timeout: milliseconds to pause clients\n        \"\"\"\n        if not isinstance(timeout, (int, long)):\n            raise DataError(\"CLIENT PAUSE timeout must be an integer\")\n        return self.execute_command('CLIENT PAUSE', str(timeout))\n\n    def readwrite(self):\n        \"Disables read queries for a connection to a Redis Cluster slave node\"\n        return self.execute_command('READWRITE')\n\n    def readonly(self):\n        \"Enables read queries for a connection to a Redis Cluster replica node\"\n        return self.execute_command('READONLY')\n\n    def config_get(self, pattern=\"*\"):\n        \"Return a dictionary of configuration based on the ``pattern``\"\n        return self.execute_command('CONFIG GET', pattern)\n\n    def config_set(self, name, value):\n        \"Set config item ``name`` with ``value``\"\n        return self.execute_command('CONFIG SET', name, value)\n\n    def config_resetstat(self):\n        \"Reset runtime statistics\"\n        return self.execute_command('CONFIG RESETSTAT')\n\n    def config_rewrite(self):\n        \"Rewrite config file with the minimal change to reflect running config\"\n        return self.execute_command('CONFIG REWRITE')\n\n    def dbsize(self):\n        \"Returns the number of keys in the current database\"\n        return self.execute_command('DBSIZE')\n\n    def debug_object(self, key):\n        \"Returns version specific meta information about a given key\"\n        return self.execute_command('DEBUG OBJECT', key)\n\n    def echo(self, value):\n        \"Echo the string back from the server\"\n        return self.execute_command('ECHO', value)\n\n    def flushall(self, asynchronous=False):\n        \"\"\"\n        Delete all keys in all databases on the current host.\n\n        ``asynchronous`` indicates whether the operation is\n        executed asynchronously by the server.\n        \"\"\"\n        args = []\n        if asynchronous:\n            args.append(b'ASYNC')\n        return self.execute_command('FLUSHALL', *args)\n\n    def flushdb(self, asynchronous=False):\n        \"\"\"\n        Delete all keys in the current database.\n\n        ``asynchronous`` indicates whether the operation is\n        executed asynchronously by the server.\n        \"\"\"\n        args = []\n        if asynchronous:\n            args.append(b'ASYNC')\n        return self.execute_command('FLUSHDB', *args)\n\n    def swapdb(self, first, second):\n        \"Swap two databases\"\n        return self.execute_command('SWAPDB', first, second)\n\n    def info(self, section=None):\n        \"\"\"\n        Returns a dictionary containing information about the Redis server\n\n        The ``section`` option can be used to select a specific section\n        of information\n\n        The section option is not supported by older versions of Redis Server,\n        and will generate ResponseError\n        \"\"\"\n        if section is None:\n            return self.execute_command('INFO')\n        else:\n            return self.execute_command('INFO', section)\n\n    def lastsave(self):\n        \"\"\"\n        Return a Python datetime object representing the last time the\n        Redis database was saved to disk\n        \"\"\"\n        return self.execute_command('LASTSAVE')\n\n    def migrate(self, host, port, keys, destination_db, timeout,\n                copy=False, replace=False, auth=None):\n        \"\"\"\n        Migrate 1 or more keys from the current Redis server to a different\n        server specified by the ``host``, ``port`` and ``destination_db``.\n\n        The ``timeout``, specified in milliseconds, indicates the maximum\n        time the connection between the two servers can be idle before the\n        command is interrupted.\n\n        If ``copy`` is True, the specified ``keys`` are NOT deleted from\n        the source server.\n\n        If ``replace`` is True, this operation will overwrite the keys\n        on the destination server if they exist.\n\n        If ``auth`` is specified, authenticate to the destination server with\n        the password provided.\n        \"\"\"\n        keys = list_or_args(keys, [])\n        if not keys:\n            raise DataError('MIGRATE requires at least one key')\n        pieces = []\n        if copy:\n            pieces.append(b'COPY')\n        if replace:\n            pieces.append(b'REPLACE')\n        if auth:\n            pieces.append(b'AUTH')\n            pieces.append(auth)\n        pieces.append(b'KEYS')\n        pieces.extend(keys)\n        return self.execute_command('MIGRATE', host, port, '', destination_db,\n                                    timeout, *pieces)\n\n    def object(self, infotype, key):\n        \"Return the encoding, idletime, or refcount about the key\"\n        return self.execute_command('OBJECT', infotype, key, infotype=infotype)\n\n    def memory_usage(self, key, samples=None):\n        \"\"\"\n        Return the total memory usage for key, its value and associated\n        administrative overheads.\n\n        For nested data structures, ``samples`` is the number of elements to\n        sample. If left unspecified, the server's default is 5. Use 0 to sample\n        all elements.\n        \"\"\"\n        args = []\n        if isinstance(samples, int):\n            args.extend([b'SAMPLES', samples])\n        return self.execute_command('MEMORY USAGE', key, *args)\n\n    def memory_purge(self):\n        \"Attempts to purge dirty pages for reclamation by allocator\"\n        return self.execute_command('MEMORY PURGE')\n\n    def ping(self):\n        \"Ping the Redis server\"\n        return self.execute_command('PING')\n\n    def save(self):\n        \"\"\"\n        Tell the Redis server to save its data to disk,\n        blocking until the save is complete\n        \"\"\"\n        return self.execute_command('SAVE')\n\n    def sentinel(self, *args):\n        \"Redis Sentinel's SENTINEL command.\"\n        warnings.warn(\n            DeprecationWarning('Use the individual sentinel_* methods'))\n\n    def sentinel_get_master_addr_by_name(self, service_name):\n        \"Returns a (host, port) pair for the given ``service_name``\"\n        return self.execute_command('SENTINEL GET-MASTER-ADDR-BY-NAME',\n                                    service_name)\n\n    def sentinel_master(self, service_name):\n        \"Returns a dictionary containing the specified masters state.\"\n        return self.execute_command('SENTINEL MASTER', service_name)\n\n    def sentinel_masters(self):\n        \"Returns a list of dictionaries containing each master's state.\"\n        return self.execute_command('SENTINEL MASTERS')\n\n    def sentinel_monitor(self, name, ip, port, quorum):\n        \"Add a new master to Sentinel to be monitored\"\n        return self.execute_command('SENTINEL MONITOR', name, ip, port, quorum)\n\n    def sentinel_remove(self, name):\n        \"Remove a master from Sentinel's monitoring\"\n        return self.execute_command('SENTINEL REMOVE', name)\n\n    def sentinel_sentinels(self, service_name):\n        \"Returns a list of sentinels for ``service_name``\"\n        return self.execute_command('SENTINEL SENTINELS', service_name)\n\n    def sentinel_set(self, name, option, value):\n        \"Set Sentinel monitoring parameters for a given master\"\n        return self.execute_command('SENTINEL SET', name, option, value)\n\n    def sentinel_slaves(self, service_name):\n        \"Returns a list of slaves for ``service_name``\"\n        return self.execute_command('SENTINEL SLAVES', service_name)\n\n    def shutdown(self, save=False, nosave=False):\n        \"\"\"Shutdown the Redis server.  If Redis has persistence configured,\n        data will be flushed before shutdown.  If the \"save\" option is set,\n        a data flush will be attempted even if there is no persistence\n        configured.  If the \"nosave\" option is set, no data flush will be\n        attempted.  The \"save\" and \"nosave\" options cannot both be set.\n        \"\"\"\n        if save and nosave:\n            raise DataError('SHUTDOWN save and nosave cannot both be set')\n        args = ['SHUTDOWN']\n        if save:\n            args.append('SAVE')\n        if nosave:\n            args.append('NOSAVE')\n        try:\n            self.execute_command(*args)\n        except ConnectionError:\n            # a ConnectionError here is expected\n            return\n        raise RedisError(\"SHUTDOWN seems to have failed.\")\n\n    def slaveof(self, host=None, port=None):\n        \"\"\"\n        Set the server to be a replicated slave of the instance identified\n        by the ``host`` and ``port``. If called without arguments, the\n        instance is promoted to a master instead.\n        \"\"\"\n        if host is None and port is None:\n            return self.execute_command('SLAVEOF', b'NO', b'ONE')\n        return self.execute_command('SLAVEOF', host, port)\n\n    def slowlog_get(self, num=None):\n        \"\"\"\n        Get the entries from the slowlog. If ``num`` is specified, get the\n        most recent ``num`` items.\n        \"\"\"\n        args = ['SLOWLOG GET']\n        if num is not None:\n            args.append(num)\n        return self.execute_command(*args)\n\n    def slowlog_len(self):\n        \"Get the number of items in the slowlog\"\n        return self.execute_command('SLOWLOG LEN')\n\n    def slowlog_reset(self):\n        \"Remove all items in the slowlog\"\n        return self.execute_command('SLOWLOG RESET')\n\n    def time(self):\n        \"\"\"\n        Returns the server time as a 2-item tuple of ints:\n        (seconds since epoch, microseconds into this second).\n        \"\"\"\n        return self.execute_command('TIME')\n\n    def wait(self, num_replicas, timeout):\n        \"\"\"\n        Redis synchronous replication\n        That returns the number of replicas that processed the query when\n        we finally have at least ``num_replicas``, or when the ``timeout`` was\n        reached.\n        \"\"\"\n        return self.execute_command('WAIT', num_replicas, timeout)\n\n    # BASIC KEY COMMANDS\n    def append(self, key, value):\n        \"\"\"\n        Appends the string ``value`` to the value at ``key``. If ``key``\n        doesn't already exist, create it with a value of ``value``.\n        Returns the new length of the value at ``key``.\n        \"\"\"\n        return self.execute_command('APPEND', key, value)\n\n    def bitcount(self, key, start=None, end=None):\n        \"\"\"\n        Returns the count of set bits in the value of ``key``.  Optional\n        ``start`` and ``end`` paramaters indicate which bytes to consider\n        \"\"\"\n        params = [key]\n        if start is not None and end is not None:\n            params.append(start)\n            params.append(end)\n        elif (start is not None and end is None) or \\\n                (end is not None and start is None):\n            raise DataError(\"Both start and end must be specified\")\n        return self.execute_command('BITCOUNT', *params)\n\n    def bitfield(self, key, default_overflow=None):\n        \"\"\"\n        Return a BitFieldOperation instance to conveniently construct one or\n        more bitfield operations on ``key``.\n        \"\"\"\n        return BitFieldOperation(self, key, default_overflow=default_overflow)\n\n    def bitop(self, operation, dest, *keys):\n        \"\"\"\n        Perform a bitwise operation using ``operation`` between ``keys`` and\n        store the result in ``dest``.\n        \"\"\"\n        return self.execute_command('BITOP', operation, dest, *keys)\n\n    def bitpos(self, key, bit, start=None, end=None):\n        \"\"\"\n        Return the position of the first bit set to 1 or 0 in a string.\n        ``start`` and ``end`` difines search range. The range is interpreted\n        as a range of bytes and not a range of bits, so start=0 and end=2\n        means to look at the first three bytes.\n        \"\"\"\n        if bit not in (0, 1):\n            raise DataError('bit must be 0 or 1')\n        params = [key, bit]\n\n        start is not None and params.append(start)\n\n        if start is not None and end is not None:\n            params.append(end)\n        elif start is None and end is not None:\n            raise DataError(\"start argument is not set, \"\n                            \"when end is specified\")\n        return self.execute_command('BITPOS', *params)\n\n    def decr(self, name, amount=1):\n        \"\"\"\n        Decrements the value of ``key`` by ``amount``.  If no key exists,\n        the value will be initialized as 0 - ``amount``\n        \"\"\"\n        # An alias for ``decr()``, because it is already implemented\n        # as DECRBY redis command.\n        return self.decrby(name, amount)\n\n    def decrby(self, name, amount=1):\n        \"\"\"\n        Decrements the value of ``key`` by ``amount``.  If no key exists,\n        the value will be initialized as 0 - ``amount``\n        \"\"\"\n        return self.execute_command('DECRBY', name, amount)\n\n    def delete(self, *names):\n        \"Delete one or more keys specified by ``names``\"\n        return self.execute_command('DEL', *names)\n\n    def __delitem__(self, name):\n        self.delete(name)\n\n    def dump(self, name):\n        \"\"\"\n        Return a serialized version of the value stored at the specified key.\n        If key does not exist a nil bulk reply is returned.\n        \"\"\"\n        return self.execute_command('DUMP', name)\n\n    def exists(self, *names):\n        \"Returns the number of ``names`` that exist\"\n        return self.execute_command('EXISTS', *names)\n    __contains__ = exists\n\n    def expire(self, name, time):\n        \"\"\"\n        Set an expire flag on key ``name`` for ``time`` seconds. ``time``\n        can be represented by an integer or a Python timedelta object.\n        \"\"\"\n        if isinstance(time, datetime.timedelta):\n            time = int(time.total_seconds())\n        return self.execute_command('EXPIRE', name, time)\n\n    def expireat(self, name, when):\n        \"\"\"\n        Set an expire flag on key ``name``. ``when`` can be represented\n        as an integer indicating unix time or a Python datetime object.\n        \"\"\"\n        if isinstance(when, datetime.datetime):\n            when = int(mod_time.mktime(when.timetuple()))\n        return self.execute_command('EXPIREAT', name, when)\n\n    def get(self, name):\n        \"\"\"\n        Return the value at key ``name``, or None if the key doesn't exist\n        \"\"\"\n        return self.execute_command('GET', name)\n\n    def __getitem__(self, name):\n        \"\"\"\n        Return the value at key ``name``, raises a KeyError if the key\n        doesn't exist.\n        \"\"\"\n        value = self.get(name)\n        if value is not None:\n            return value\n        raise KeyError(name)\n\n    def getbit(self, name, offset):\n        \"Returns a boolean indicating the value of ``offset`` in ``name``\"\n        return self.execute_command('GETBIT', name, offset)\n\n    def getrange(self, key, start, end):\n        \"\"\"\n        Returns the substring of the string value stored at ``key``,\n        determined by the offsets ``start`` and ``end`` (both are inclusive)\n        \"\"\"\n        return self.execute_command('GETRANGE', key, start, end)\n\n    def getset(self, name, value):\n        \"\"\"\n        Sets the value at key ``name`` to ``value``\n        and returns the old value at key ``name`` atomically.\n        \"\"\"\n        return self.execute_command('GETSET', name, value)\n\n    def incr(self, name, amount=1):\n        \"\"\"\n        Increments the value of ``key`` by ``amount``.  If no key exists,\n        the value will be initialized as ``amount``\n        \"\"\"\n        return self.incrby(name, amount)\n\n    def incrby(self, name, amount=1):\n        \"\"\"\n        Increments the value of ``key`` by ``amount``.  If no key exists,\n        the value will be initialized as ``amount``\n        \"\"\"\n        # An alias for ``incr()``, because it is already implemented\n        # as INCRBY redis command.\n        return self.execute_command('INCRBY', name, amount)\n\n    def incrbyfloat(self, name, amount=1.0):\n        \"\"\"\n        Increments the value at key ``name`` by floating ``amount``.\n        If no key exists, the value will be initialized as ``amount``\n        \"\"\"\n        return self.execute_command('INCRBYFLOAT', name, amount)\n\n    def keys(self, pattern='*'):\n        \"Returns a list of keys matching ``pattern``\"\n        return self.execute_command('KEYS', pattern)\n\n    def mget(self, keys, *args):\n        \"\"\"\n        Returns a list of values ordered identically to ``keys``\n        \"\"\"\n        args = list_or_args(keys, args)\n        options = {}\n        if not args:\n            options[EMPTY_RESPONSE] = []\n        return self.execute_command('MGET', *args, **options)\n\n    def mset(self, mapping):\n        \"\"\"\n        Sets key/values based on a mapping. Mapping is a dictionary of\n        key/value pairs. Both keys and values should be strings or types that\n        can be cast to a string via str().\n        \"\"\"\n        items = []\n        for pair in iteritems(mapping):\n            items.extend(pair)\n        return self.execute_command('MSET', *items)\n\n    def msetnx(self, mapping):\n        \"\"\"\n        Sets key/values based on a mapping if none of the keys are already set.\n        Mapping is a dictionary of key/value pairs. Both keys and values\n        should be strings or types that can be cast to a string via str().\n        Returns a boolean indicating if the operation was successful.\n        \"\"\"\n        items = []\n        for pair in iteritems(mapping):\n            items.extend(pair)\n        return self.execute_command('MSETNX', *items)\n\n    def move(self, name, db):\n        \"Moves the key ``name`` to a different Redis database ``db``\"\n        return self.execute_command('MOVE', name, db)\n\n    def persist(self, name):\n        \"Removes an expiration on ``name``\"\n        return self.execute_command('PERSIST', name)\n\n    def pexpire(self, name, time):\n        \"\"\"\n        Set an expire flag on key ``name`` for ``time`` milliseconds.\n        ``time`` can be represented by an integer or a Python timedelta\n        object.\n        \"\"\"\n        if isinstance(time, datetime.timedelta):\n            time = int(time.total_seconds() * 1000)\n        return self.execute_command('PEXPIRE', name, time)\n\n    def pexpireat(self, name, when):\n        \"\"\"\n        Set an expire flag on key ``name``. ``when`` can be represented\n        as an integer representing unix time in milliseconds (unix time * 1000)\n        or a Python datetime object.\n        \"\"\"\n        if isinstance(when, datetime.datetime):\n            ms = int(when.microsecond / 1000)\n            when = int(mod_time.mktime(when.timetuple())) * 1000 + ms\n        return self.execute_command('PEXPIREAT', name, when)\n\n    def psetex(self, name, time_ms, value):\n        \"\"\"\n        Set the value of key ``name`` to ``value`` that expires in ``time_ms``\n        milliseconds. ``time_ms`` can be represented by an integer or a Python\n        timedelta object\n        \"\"\"\n        if isinstance(time_ms, datetime.timedelta):\n            time_ms = int(time_ms.total_seconds() * 1000)\n        return self.execute_command('PSETEX', name, time_ms, value)\n\n    def pttl(self, name):\n        \"Returns the number of milliseconds until the key ``name`` will expire\"\n        return self.execute_command('PTTL', name)\n\n    def randomkey(self):\n        \"Returns the name of a random key\"\n        return self.execute_command('RANDOMKEY')\n\n    def rename(self, src, dst):\n        \"\"\"\n        Rename key ``src`` to ``dst``\n        \"\"\"\n        return self.execute_command('RENAME', src, dst)\n\n    def renamenx(self, src, dst):\n        \"Rename key ``src`` to ``dst`` if ``dst`` doesn't already exist\"\n        return self.execute_command('RENAMENX', src, dst)\n\n    def restore(self, name, ttl, value, replace=False):\n        \"\"\"\n        Create a key using the provided serialized value, previously obtained\n        using DUMP.\n        \"\"\"\n        params = [name, ttl, value]\n        if replace:\n            params.append('REPLACE')\n        return self.execute_command('RESTORE', *params)\n\n    def set(self, name, value, ex=None, px=None, nx=False, xx=False):\n        \"\"\"\n        Set the value at key ``name`` to ``value``\n\n        ``ex`` sets an expire flag on key ``name`` for ``ex`` seconds.\n\n        ``px`` sets an expire flag on key ``name`` for ``px`` milliseconds.\n\n        ``nx`` if set to True, set the value at key ``name`` to ``value`` only\n            if it does not exist.\n\n        ``xx`` if set to True, set the value at key ``name`` to ``value`` only\n            if it already exists.\n        \"\"\"\n        pieces = [name, value]\n        if ex is not None:\n            pieces.append('EX')\n            if isinstance(ex, datetime.timedelta):\n                ex = int(ex.total_seconds())\n            pieces.append(ex)\n        if px is not None:\n            pieces.append('PX')\n            if isinstance(px, datetime.timedelta):\n                px = int(px.total_seconds() * 1000)\n            pieces.append(px)\n\n        if nx:\n            pieces.append('NX')\n        if xx:\n            pieces.append('XX')\n        return self.execute_command('SET', *pieces)\n\n    def __setitem__(self, name, value):\n        self.set(name, value)\n\n    def setbit(self, name, offset, value):\n        \"\"\"\n        Flag the ``offset`` in ``name`` as ``value``. Returns a boolean\n        indicating the previous value of ``offset``.\n        \"\"\"\n        value = value and 1 or 0\n        return self.execute_command('SETBIT', name, offset, value)\n\n    def setex(self, name, time, value):\n        \"\"\"\n        Set the value of key ``name`` to ``value`` that expires in ``time``\n        seconds. ``time`` can be represented by an integer or a Python\n        timedelta object.\n        \"\"\"\n        if isinstance(time, datetime.timedelta):\n            time = int(time.total_seconds())\n        return self.execute_command('SETEX', name, time, value)\n\n    def setnx(self, name, value):\n        \"Set the value of key ``name`` to ``value`` if key doesn't exist\"\n        return self.execute_command('SETNX', name, value)\n\n    def setrange(self, name, offset, value):\n        \"\"\"\n        Overwrite bytes in the value of ``name`` starting at ``offset`` with\n        ``value``. If ``offset`` plus the length of ``value`` exceeds the\n        length of the original value, the new value will be larger than before.\n        If ``offset`` exceeds the length of the original value, null bytes\n        will be used to pad between the end of the previous value and the start\n        of what's being injected.\n\n        Returns the length of the new string.\n        \"\"\"\n        return self.execute_command('SETRANGE', name, offset, value)\n\n    def strlen(self, name):\n        \"Return the number of bytes stored in the value of ``name``\"\n        return self.execute_command('STRLEN', name)\n\n    def substr(self, name, start, end=-1):\n        \"\"\"\n        Return a substring of the string at key ``name``. ``start`` and ``end``\n        are 0-based integers specifying the portion of the string to return.\n        \"\"\"\n        return self.execute_command('SUBSTR', name, start, end)\n\n    def touch(self, *args):\n        \"\"\"\n        Alters the last access time of a key(s) ``*args``. A key is ignored\n        if it does not exist.\n        \"\"\"\n        return self.execute_command('TOUCH', *args)\n\n    def ttl(self, name):\n        \"Returns the number of seconds until the key ``name`` will expire\"\n        return self.execute_command('TTL', name)\n\n    def type(self, name):\n        \"Returns the type of key ``name``\"\n        return self.execute_command('TYPE', name)\n\n    def watch(self, *names):\n        \"\"\"\n        Watches the values at keys ``names``, or None if the key doesn't exist\n        \"\"\"\n        warnings.warn(DeprecationWarning('Call WATCH from a Pipeline object'))\n\n    def unwatch(self):\n        \"\"\"\n        Unwatches the value at key ``name``, or None of the key doesn't exist\n        \"\"\"\n        warnings.warn(\n            DeprecationWarning('Call UNWATCH from a Pipeline object'))\n\n    def unlink(self, *names):\n        \"Unlink one or more keys specified by ``names``\"\n        return self.execute_command('UNLINK', *names)\n\n    # LIST COMMANDS\n    def blpop(self, keys, timeout=0):\n        \"\"\"\n        LPOP a value off of the first non-empty list\n        named in the ``keys`` list.\n\n        If none of the lists in ``keys`` has a value to LPOP, then block\n        for ``timeout`` seconds, or until a value gets pushed on to one\n        of the lists.\n\n        If timeout is 0, then block indefinitely.\n        \"\"\"\n        if timeout is None:\n            timeout = 0\n        keys = list_or_args(keys, None)\n        keys.append(timeout)\n        return self.execute_command('BLPOP', *keys)\n\n    def brpop(self, keys, timeout=0):\n        \"\"\"\n        RPOP a value off of the first non-empty list\n        named in the ``keys`` list.\n\n        If none of the lists in ``keys`` has a value to RPOP, then block\n        for ``timeout`` seconds, or until a value gets pushed on to one\n        of the lists.\n\n        If timeout is 0, then block indefinitely.\n        \"\"\"\n        if timeout is None:\n            timeout = 0\n        keys = list_or_args(keys, None)\n        keys.append(timeout)\n        return self.execute_command('BRPOP', *keys)\n\n    def brpoplpush(self, src, dst, timeout=0):\n        \"\"\"\n        Pop a value off the tail of ``src``, push it on the head of ``dst``\n        and then return it.\n\n        This command blocks until a value is in ``src`` or until ``timeout``\n        seconds elapse, whichever is first. A ``timeout`` value of 0 blocks\n        forever.\n        \"\"\"\n        if timeout is None:\n            timeout = 0\n        return self.execute_command('BRPOPLPUSH', src, dst, timeout)\n\n    def lindex(self, name, index):\n        \"\"\"\n        Return the item from list ``name`` at position ``index``\n\n        Negative indexes are supported and will return an item at the\n        end of the list\n        \"\"\"\n        return self.execute_command('LINDEX', name, index)\n\n    def linsert(self, name, where, refvalue, value):\n        \"\"\"\n        Insert ``value`` in list ``name`` either immediately before or after\n        [``where``] ``refvalue``\n\n        Returns the new length of the list on success or -1 if ``refvalue``\n        is not in the list.\n        \"\"\"\n        return self.execute_command('LINSERT', name, where, refvalue, value)\n\n    def llen(self, name):\n        \"Return the length of the list ``name``\"\n        return self.execute_command('LLEN', name)\n\n    def lpop(self, name):\n        \"Remove and return the first item of the list ``name``\"\n        return self.execute_command('LPOP', name)\n\n    def lpush(self, name, *values):\n        \"Push ``values`` onto the head of the list ``name``\"\n        return self.execute_command('LPUSH', name, *values)\n\n    def lpushx(self, name, value):\n        \"Push ``value`` onto the head of the list ``name`` if ``name`` exists\"\n        return self.execute_command('LPUSHX', name, value)\n\n    def lrange(self, name, start, end):\n        \"\"\"\n        Return a slice of the list ``name`` between\n        position ``start`` and ``end``\n\n        ``start`` and ``end`` can be negative numbers just like\n        Python slicing notation\n        \"\"\"\n        return self.execute_command('LRANGE', name, start, end)\n\n    def lrem(self, name, count, value):\n        \"\"\"\n        Remove the first ``count`` occurrences of elements equal to ``value``\n        from the list stored at ``name``.\n\n        The count argument influences the operation in the following ways:\n            count > 0: Remove elements equal to value moving from head to tail.\n            count < 0: Remove elements equal to value moving from tail to head.\n            count = 0: Remove all elements equal to value.\n        \"\"\"\n        return self.execute_command('LREM', name, count, value)\n\n    def lset(self, name, index, value):\n        \"Set ``position`` of list ``name`` to ``value``\"\n        return self.execute_command('LSET', name, index, value)\n\n    def ltrim(self, name, start, end):\n        \"\"\"\n        Trim the list ``name``, removing all values not within the slice\n        between ``start`` and ``end``\n\n        ``start`` and ``end`` can be negative numbers just like\n        Python slicing notation\n        \"\"\"\n        return self.execute_command('LTRIM', name, start, end)\n\n    def rpop(self, name):\n        \"Remove and return the last item of the list ``name``\"\n        return self.execute_command('RPOP', name)\n\n    def rpoplpush(self, src, dst):\n        \"\"\"\n        RPOP a value off of the ``src`` list and atomically LPUSH it\n        on to the ``dst`` list.  Returns the value.\n        \"\"\"\n        return self.execute_command('RPOPLPUSH', src, dst)\n\n    def rpush(self, name, *values):\n        \"Push ``values`` onto the tail of the list ``name``\"\n        return self.execute_command('RPUSH', name, *values)\n\n    def rpushx(self, name, value):\n        \"Push ``value`` onto the tail of the list ``name`` if ``name`` exists\"\n        return self.execute_command('RPUSHX', name, value)\n\n    def sort(self, name, start=None, num=None, by=None, get=None,\n             desc=False, alpha=False, store=None, groups=False):\n        \"\"\"\n        Sort and return the list, set or sorted set at ``name``.\n\n        ``start`` and ``num`` allow for paging through the sorted data\n\n        ``by`` allows using an external key to weight and sort the items.\n            Use an \"*\" to indicate where in the key the item value is located\n\n        ``get`` allows for returning items from external keys rather than the\n            sorted data itself.  Use an \"*\" to indicate where int he key\n            the item value is located\n\n        ``desc`` allows for reversing the sort\n\n        ``alpha`` allows for sorting lexicographically rather than numerically\n\n        ``store`` allows for storing the result of the sort into\n            the key ``store``\n\n        ``groups`` if set to True and if ``get`` contains at least two\n            elements, sort will return a list of tuples, each containing the\n            values fetched from the arguments to ``get``.\n\n        \"\"\"\n        if (start is not None and num is None) or \\\n                (num is not None and start is None):\n            raise DataError(\"``start`` and ``num`` must both be specified\")\n\n        pieces = [name]\n        if by is not None:\n            pieces.append(b'BY')\n            pieces.append(by)\n        if start is not None and num is not None:\n            pieces.append(b'LIMIT')\n            pieces.append(start)\n            pieces.append(num)\n        if get is not None:\n            # If get is a string assume we want to get a single value.\n            # Otherwise assume it's an interable and we want to get multiple\n            # values. We can't just iterate blindly because strings are\n            # iterable.\n            if isinstance(get, (bytes, basestring)):\n                pieces.append(b'GET')\n                pieces.append(get)\n            else:\n                for g in get:\n                    pieces.append(b'GET')\n                    pieces.append(g)\n        if desc:\n            pieces.append(b'DESC')\n        if alpha:\n            pieces.append(b'ALPHA')\n        if store is not None:\n            pieces.append(b'STORE')\n            pieces.append(store)\n\n        if groups:\n            if not get or isinstance(get, (bytes, basestring)) or len(get) < 2:\n                raise DataError('when using \"groups\" the \"get\" argument '\n                                'must be specified and contain at least '\n                                'two keys')\n\n        options = {'groups': len(get) if groups else None}\n        return self.execute_command('SORT', *pieces, **options)\n\n    # SCAN COMMANDS\n    def scan(self, cursor=0, match=None, count=None):\n        \"\"\"\n        Incrementally return lists of key names. Also return a cursor\n        indicating the scan position.\n\n        ``match`` allows for filtering the keys by pattern\n\n        ``count`` allows for hint the minimum number of returns\n        \"\"\"\n        pieces = [cursor]\n        if match is not None:\n            pieces.extend([b'MATCH', match])\n        if count is not None:\n            pieces.extend([b'COUNT', count])\n        return self.execute_command('SCAN', *pieces)\n\n    def scan_iter(self, match=None, count=None):\n        \"\"\"\n        Make an iterator using the SCAN command so that the client doesn't\n        need to remember the cursor position.\n\n        ``match`` allows for filtering the keys by pattern\n\n        ``count`` allows for hint the minimum number of returns\n        \"\"\"\n        cursor = '0'\n        while cursor != 0:\n            cursor, data = self.scan(cursor=cursor, match=match, count=count)\n            for item in data:\n                yield item\n\n    def sscan(self, name, cursor=0, match=None, count=None):\n        \"\"\"\n        Incrementally return lists of elements in a set. Also return a cursor\n        indicating the scan position.\n\n        ``match`` allows for filtering the keys by pattern\n\n        ``count`` allows for hint the minimum number of returns\n        \"\"\"\n        pieces = [name, cursor]\n        if match is not None:\n            pieces.extend([b'MATCH', match])\n        if count is not None:\n            pieces.extend([b'COUNT', count])\n        return self.execute_command('SSCAN', *pieces)\n\n    def sscan_iter(self, name, match=None, count=None):\n        \"\"\"\n        Make an iterator using the SSCAN command so that the client doesn't\n        need to remember the cursor position.\n\n        ``match`` allows for filtering the keys by pattern\n\n        ``count`` allows for hint the minimum number of returns\n        \"\"\"\n        cursor = '0'\n        while cursor != 0:\n            cursor, data = self.sscan(name, cursor=cursor,\n                                      match=match, count=count)\n            for item in data:\n                yield item\n\n    def hscan(self, name, cursor=0, match=None, count=None):\n        \"\"\"\n        Incrementally return key/value slices in a hash. Also return a cursor\n        indicating the scan position.\n\n        ``match`` allows for filtering the keys by pattern\n\n        ``count`` allows for hint the minimum number of returns\n        \"\"\"\n        pieces = [name, cursor]\n        if match is not None:\n            pieces.extend([b'MATCH', match])\n        if count is not None:\n            pieces.extend([b'COUNT', count])\n        return self.execute_command('HSCAN', *pieces)\n\n    def hscan_iter(self, name, match=None, count=None):\n        \"\"\"\n        Make an iterator using the HSCAN command so that the client doesn't\n        need to remember the cursor position.\n\n        ``match`` allows for filtering the keys by pattern\n\n        ``count`` allows for hint the minimum number of returns\n        \"\"\"\n        cursor = '0'\n        while cursor != 0:\n            cursor, data = self.hscan(name, cursor=cursor,\n                                      match=match, count=count)\n            for item in data.items():\n                yield item\n\n    def zscan(self, name, cursor=0, match=None, count=None,\n              score_cast_func=float):\n        \"\"\"\n        Incrementally return lists of elements in a sorted set. Also return a\n        cursor indicating the scan position.\n\n        ``match`` allows for filtering the keys by pattern\n\n        ``count`` allows for hint the minimum number of returns\n\n        ``score_cast_func`` a callable used to cast the score return value\n        \"\"\"\n        pieces = [name, cursor]\n        if match is not None:\n            pieces.extend([b'MATCH', match])\n        if count is not None:\n            pieces.extend([b'COUNT', count])\n        options = {'score_cast_func': score_cast_func}\n        return self.execute_command('ZSCAN', *pieces, **options)\n\n    def zscan_iter(self, name, match=None, count=None,\n                   score_cast_func=float):\n        \"\"\"\n        Make an iterator using the ZSCAN command so that the client doesn't\n        need to remember the cursor position.\n\n        ``match`` allows for filtering the keys by pattern\n\n        ``count`` allows for hint the minimum number of returns\n\n        ``score_cast_func`` a callable used to cast the score return value\n        \"\"\"\n        cursor = '0'\n        while cursor != 0:\n            cursor, data = self.zscan(name, cursor=cursor, match=match,\n                                      count=count,\n                                      score_cast_func=score_cast_func)\n            for item in data:\n                yield item\n\n    # SET COMMANDS\n    def sadd(self, name, *values):\n        \"Add ``value(s)`` to set ``name``\"\n        return self.execute_command('SADD', name, *values)\n\n    def scard(self, name):\n        \"Return the number of elements in set ``name``\"\n        return self.execute_command('SCARD', name)\n\n    def sdiff(self, keys, *args):\n        \"Return the difference of sets specified by ``keys``\"\n        args = list_or_args(keys, args)\n        return self.execute_command('SDIFF', *args)\n\n    def sdiffstore(self, dest, keys, *args):\n        \"\"\"\n        Store the difference of sets specified by ``keys`` into a new\n        set named ``dest``.  Returns the number of keys in the new set.\n        \"\"\"\n        args = list_or_args(keys, args)\n        return self.execute_command('SDIFFSTORE', dest, *args)\n\n    def sinter(self, keys, *args):\n        \"Return the intersection of sets specified by ``keys``\"\n        args = list_or_args(keys, args)\n        return self.execute_command('SINTER', *args)\n\n    def sinterstore(self, dest, keys, *args):\n        \"\"\"\n        Store the intersection of sets specified by ``keys`` into a new\n        set named ``dest``.  Returns the number of keys in the new set.\n        \"\"\"\n        args = list_or_args(keys, args)\n        return self.execute_command('SINTERSTORE', dest, *args)\n\n    def sismember(self, name, value):\n        \"Return a boolean indicating if ``value`` is a member of set ``name``\"\n        return self.execute_command('SISMEMBER', name, value)\n\n    def smembers(self, name):\n        \"Return all members of the set ``name``\"\n        return self.execute_command('SMEMBERS', name)\n\n    def smove(self, src, dst, value):\n        \"Move ``value`` from set ``src`` to set ``dst`` atomically\"\n        return self.execute_command('SMOVE', src, dst, value)\n\n    def spop(self, name, count=None):\n        \"Remove and return a random member of set ``name``\"\n        args = (count is not None) and [count] or []\n        return self.execute_command('SPOP', name, *args)\n\n    def srandmember(self, name, number=None):\n        \"\"\"\n        If ``number`` is None, returns a random member of set ``name``.\n\n        If ``number`` is supplied, returns a list of ``number`` random\n        memebers of set ``name``. Note this is only available when running\n        Redis 2.6+.\n        \"\"\"\n        args = (number is not None) and [number] or []\n        return self.execute_command('SRANDMEMBER', name, *args)\n\n    def srem(self, name, *values):\n        \"Remove ``values`` from set ``name``\"\n        return self.execute_command('SREM', name, *values)\n\n    def sunion(self, keys, *args):\n        \"Return the union of sets specified by ``keys``\"\n        args = list_or_args(keys, args)\n        return self.execute_command('SUNION', *args)\n\n    def sunionstore(self, dest, keys, *args):\n        \"\"\"\n        Store the union of sets specified by ``keys`` into a new\n        set named ``dest``.  Returns the number of keys in the new set.\n        \"\"\"\n        args = list_or_args(keys, args)\n        return self.execute_command('SUNIONSTORE', dest, *args)\n\n    # STREAMS COMMANDS\n    def xack(self, name, groupname, *ids):\n        \"\"\"\n        Acknowledges the successful processing of one or more messages.\n        name: name of the stream.\n        groupname: name of the consumer group.\n        *ids: message ids to acknowlege.\n        \"\"\"\n        return self.execute_command('XACK', name, groupname, *ids)\n\n    def xadd(self, name, fields, id='*', maxlen=None, approximate=True):\n        \"\"\"\n        Add to a stream.\n        name: name of the stream\n        fields: dict of field/value pairs to insert into the stream\n        id: Location to insert this record. By default it is appended.\n        maxlen: truncate old stream members beyond this size\n        approximate: actual stream length may be slightly more than maxlen\n\n        \"\"\"\n        pieces = []\n        if maxlen is not None:\n            if not isinstance(maxlen, (int, long)) or maxlen < 1:\n                raise DataError('XADD maxlen must be a positive integer')\n            pieces.append(b'MAXLEN')\n            if approximate:\n                pieces.append(b'~')\n            pieces.append(str(maxlen))\n        pieces.append(id)\n        if not isinstance(fields, dict) or len(fields) == 0:\n            raise DataError('XADD fields must be a non-empty dict')\n        for pair in iteritems(fields):\n            pieces.extend(pair)\n        return self.execute_command('XADD', name, *pieces)\n\n    def xclaim(self, name, groupname, consumername, min_idle_time, message_ids,\n               idle=None, time=None, retrycount=None, force=False,\n               justid=False):\n        \"\"\"\n        Changes the ownership of a pending message.\n        name: name of the stream.\n        groupname: name of the consumer group.\n        consumername: name of a consumer that claims the message.\n        min_idle_time: filter messages that were idle less than this amount of\n        milliseconds\n        message_ids: non-empty list or tuple of message IDs to claim\n        idle: optional. Set the idle time (last time it was delivered) of the\n         message in ms\n        time: optional integer. This is the same as idle but instead of a\n         relative amount of milliseconds, it sets the idle time to a specific\n         Unix time (in milliseconds).\n        retrycount: optional integer. set the retry counter to the specified\n         value. This counter is incremented every time a message is delivered\n         again.\n        force: optional boolean, false by default. Creates the pending message\n         entry in the PEL even if certain specified IDs are not already in the\n         PEL assigned to a different client.\n        justid: optional boolean, false by default. Return just an array of IDs\n         of messages successfully claimed, without returning the actual message\n        \"\"\"\n        if not isinstance(min_idle_time, (int, long)) or min_idle_time < 0:\n            raise DataError(\"XCLAIM min_idle_time must be a non negative \"\n                            \"integer\")\n        if not isinstance(message_ids, (list, tuple)) or not message_ids:\n            raise DataError(\"XCLAIM message_ids must be a non empty list or \"\n                            \"tuple of message IDs to claim\")\n\n        kwargs = {}\n        pieces = [name, groupname, consumername, str(min_idle_time)]\n        pieces.extend(list(message_ids))\n\n        if idle is not None:\n            if not isinstance(idle, (int, long)):\n                raise DataError(\"XCLAIM idle must be an integer\")\n            pieces.extend((b'IDLE', str(idle)))\n        if time is not None:\n            if not isinstance(time, (int, long)):\n                raise DataError(\"XCLAIM time must be an integer\")\n            pieces.extend((b'TIME', str(time)))\n        if retrycount is not None:\n            if not isinstance(retrycount, (int, long)):\n                raise DataError(\"XCLAIM retrycount must be an integer\")\n            pieces.extend((b'RETRYCOUNT', str(retrycount)))\n\n        if force:\n            if not isinstance(force, bool):\n                raise DataError(\"XCLAIM force must be a boolean\")\n            pieces.append(b'FORCE')\n        if justid:\n            if not isinstance(justid, bool):\n                raise DataError(\"XCLAIM justid must be a boolean\")\n            pieces.append(b'JUSTID')\n            kwargs['parse_justid'] = True\n        return self.execute_command('XCLAIM', *pieces, **kwargs)\n\n    def xdel(self, name, *ids):\n        \"\"\"\n        Deletes one or more messages from a stream.\n        name: name of the stream.\n        *ids: message ids to delete.\n        \"\"\"\n        return self.execute_command('XDEL', name, *ids)\n\n    def xgroup_create(self, name, groupname, id='$', mkstream=False):\n        \"\"\"\n        Create a new consumer group associated with a stream.\n        name: name of the stream.\n        groupname: name of the consumer group.\n        id: ID of the last item in the stream to consider already delivered.\n        \"\"\"\n        pieces = ['XGROUP CREATE', name, groupname, id]\n        if mkstream:\n            pieces.append(b'MKSTREAM')\n        return self.execute_command(*pieces)\n\n    def xgroup_delconsumer(self, name, groupname, consumername):\n        \"\"\"\n        Remove a specific consumer from a consumer group.\n        Returns the number of pending messages that the consumer had before it\n        was deleted.\n        name: name of the stream.\n        groupname: name of the consumer group.\n        consumername: name of consumer to delete\n        \"\"\"\n        return self.execute_command('XGROUP DELCONSUMER', name, groupname,\n                                    consumername)\n\n    def xgroup_destroy(self, name, groupname):\n        \"\"\"\n        Destroy a consumer group.\n        name: name of the stream.\n        groupname: name of the consumer group.\n        \"\"\"\n        return self.execute_command('XGROUP DESTROY', name, groupname)\n\n    def xgroup_setid(self, name, groupname, id):\n        \"\"\"\n        Set the consumer group last delivered ID to something else.\n        name: name of the stream.\n        groupname: name of the consumer group.\n        id: ID of the last item in the stream to consider already delivered.\n        \"\"\"\n        return self.execute_command('XGROUP SETID', name, groupname, id)\n\n    def xinfo_consumers(self, name, groupname):\n        \"\"\"\n        Returns general information about the consumers in the group.\n        name: name of the stream.\n        groupname: name of the consumer group.\n        \"\"\"\n        return self.execute_command('XINFO CONSUMERS', name, groupname)\n\n    def xinfo_groups(self, name):\n        \"\"\"\n        Returns general information about the consumer groups of the stream.\n        name: name of the stream.\n        \"\"\"\n        return self.execute_command('XINFO GROUPS', name)\n\n    def xinfo_stream(self, name):\n        \"\"\"\n        Returns general information about the stream.\n        name: name of the stream.\n        \"\"\"\n        return self.execute_command('XINFO STREAM', name)\n\n    def xlen(self, name):\n        \"\"\"\n        Returns the number of elements in a given stream.\n        \"\"\"\n        return self.execute_command('XLEN', name)\n\n    def xpending(self, name, groupname):\n        \"\"\"\n        Returns information about pending messages of a group.\n        name: name of the stream.\n        groupname: name of the consumer group.\n        \"\"\"\n        return self.execute_command('XPENDING', name, groupname)\n\n    def xpending_range(self, name, groupname, min, max, count,\n                       consumername=None):\n        \"\"\"\n        Returns information about pending messages, in a range.\n        name: name of the stream.\n        groupname: name of the consumer group.\n        min: minimum stream ID.\n        max: maximum stream ID.\n        count: number of messages to return\n        consumername: name of a consumer to filter by (optional).\n        \"\"\"\n        pieces = [name, groupname]\n        if min is not None or max is not None or count is not None:\n            if min is None or max is None or count is None:\n                raise DataError(\"XPENDING must be provided with min, max \"\n                                \"and count parameters, or none of them. \")\n            if not isinstance(count, (int, long)) or count < -1:\n                raise DataError(\"XPENDING count must be a integer >= -1\")\n            pieces.extend((min, max, str(count)))\n        if consumername is not None:\n            if min is None or max is None or count is None:\n                raise DataError(\"if XPENDING is provided with consumername,\"\n                                \" it must be provided with min, max and\"\n                                \" count parameters\")\n            pieces.append(consumername)\n        return self.execute_command('XPENDING', *pieces, parse_detail=True)\n\n    def xrange(self, name, min='-', max='+', count=None):\n        \"\"\"\n        Read stream values within an interval.\n        name: name of the stream.\n        start: first stream ID. defaults to '-',\n               meaning the earliest available.\n        finish: last stream ID. defaults to '+',\n                meaning the latest available.\n        count: if set, only return this many items, beginning with the\n               earliest available.\n        \"\"\"\n        pieces = [min, max]\n        if count is not None:\n            if not isinstance(count, (int, long)) or count < 1:\n                raise DataError('XRANGE count must be a positive integer')\n            pieces.append(b'COUNT')\n            pieces.append(str(count))\n\n        return self.execute_command('XRANGE', name, *pieces)\n\n    def xread(self, streams, count=None, block=None):\n        \"\"\"\n        Block and monitor multiple streams for new data.\n        streams: a dict of stream names to stream IDs, where\n                   IDs indicate the last ID already seen.\n        count: if set, only return this many items, beginning with the\n               earliest available.\n        block: number of milliseconds to wait, if nothing already present.\n        \"\"\"\n        pieces = []\n        if block is not None:\n            if not isinstance(block, (int, long)) or block < 0:\n                raise DataError('XREAD block must be a non-negative integer')\n            pieces.append(b'BLOCK')\n            pieces.append(str(block))\n        if count is not None:\n            if not isinstance(count, (int, long)) or count < 1:\n                raise DataError('XREAD count must be a positive integer')\n            pieces.append(b'COUNT')\n            pieces.append(str(count))\n        if not isinstance(streams, dict) or len(streams) == 0:\n            raise DataError('XREAD streams must be a non empty dict')\n        pieces.append(b'STREAMS')\n        keys, values = izip(*iteritems(streams))\n        pieces.extend(keys)\n        pieces.extend(values)\n        return self.execute_command('XREAD', *pieces)\n\n    def xreadgroup(self, groupname, consumername, streams, count=None,\n                   block=None, noack=False):\n        \"\"\"\n        Read from a stream via a consumer group.\n        groupname: name of the consumer group.\n        consumername: name of the requesting consumer.\n        streams: a dict of stream names to stream IDs, where\n               IDs indicate the last ID already seen.\n        count: if set, only return this many items, beginning with the\n               earliest available.\n        block: number of milliseconds to wait, if nothing already present.\n        noack: do not add messages to the PEL\n        \"\"\"\n        pieces = [b'GROUP', groupname, consumername]\n        if count is not None:\n            if not isinstance(count, (int, long)) or count < 1:\n                raise DataError(\"XREADGROUP count must be a positive integer\")\n            pieces.append(b'COUNT')\n            pieces.append(str(count))\n        if block is not None:\n            if not isinstance(block, (int, long)) or block < 0:\n                raise DataError(\"XREADGROUP block must be a non-negative \"\n                                \"integer\")\n            pieces.append(b'BLOCK')\n            pieces.append(str(block))\n        if noack:\n            pieces.append(b'NOACK')\n        if not isinstance(streams, dict) or len(streams) == 0:\n            raise DataError('XREADGROUP streams must be a non empty dict')\n        pieces.append(b'STREAMS')\n        pieces.extend(streams.keys())\n        pieces.extend(streams.values())\n        return self.execute_command('XREADGROUP', *pieces)\n\n    def xrevrange(self, name, max='+', min='-', count=None):\n        \"\"\"\n        Read stream values within an interval, in reverse order.\n        name: name of the stream\n        start: first stream ID. defaults to '+',\n               meaning the latest available.\n        finish: last stream ID. defaults to '-',\n                meaning the earliest available.\n        count: if set, only return this many items, beginning with the\n               latest available.\n        \"\"\"\n        pieces = [max, min]\n        if count is not None:\n            if not isinstance(count, (int, long)) or count < 1:\n                raise DataError('XREVRANGE count must be a positive integer')\n            pieces.append(b'COUNT')\n            pieces.append(str(count))\n\n        return self.execute_command('XREVRANGE', name, *pieces)\n\n    def xtrim(self, name, maxlen, approximate=True):\n        \"\"\"\n        Trims old messages from a stream.\n        name: name of the stream.\n        maxlen: truncate old stream messages beyond this size\n        approximate: actual stream length may be slightly more than maxlen\n        \"\"\"\n        pieces = [b'MAXLEN']\n        if approximate:\n            pieces.append(b'~')\n        pieces.append(maxlen)\n        return self.execute_command('XTRIM', name, *pieces)\n\n    # SORTED SET COMMANDS\n    def zadd(self, name, mapping, nx=False, xx=False, ch=False, incr=False):\n        \"\"\"\n        Set any number of element-name, score pairs to the key ``name``. Pairs\n        are specified as a dict of element-names keys to score values.\n\n        ``nx`` forces ZADD to only create new elements and not to update\n        scores for elements that already exist.\n\n        ``xx`` forces ZADD to only update scores of elements that already\n        exist. New elements will not be added.\n\n        ``ch`` modifies the return value to be the numbers of elements changed.\n        Changed elements include new elements that were added and elements\n        whose scores changed.\n\n        ``incr`` modifies ZADD to behave like ZINCRBY. In this mode only a\n        single element/score pair can be specified and the score is the amount\n        the existing score will be incremented by. When using this mode the\n        return value of ZADD will be the new score of the element.\n\n        The return value of ZADD varies based on the mode specified. With no\n        options, ZADD returns the number of new elements added to the sorted\n        set.\n        \"\"\"\n        if not mapping:\n            raise DataError(\"ZADD requires at least one element/score pair\")\n        if nx and xx:\n            raise DataError(\"ZADD allows either 'nx' or 'xx', not both\")\n        if incr and len(mapping) != 1:\n            raise DataError(\"ZADD option 'incr' only works when passing a \"\n                            \"single element/score pair\")\n        pieces = []\n        options = {}\n        if nx:\n            pieces.append(b'NX')\n        if xx:\n            pieces.append(b'XX')\n        if ch:\n            pieces.append(b'CH')\n        if incr:\n            pieces.append(b'INCR')\n            options['as_score'] = True\n        for pair in iteritems(mapping):\n            pieces.append(pair[1])\n            pieces.append(pair[0])\n        return self.execute_command('ZADD', name, *pieces, **options)\n\n    def zcard(self, name):\n        \"Return the number of elements in the sorted set ``name``\"\n        return self.execute_command('ZCARD', name)\n\n    def zcount(self, name, min, max):\n        \"\"\"\n        Returns the number of elements in the sorted set at key ``name`` with\n        a score between ``min`` and ``max``.\n        \"\"\"\n        return self.execute_command('ZCOUNT', name, min, max)\n\n    def zincrby(self, name, amount, value):\n        \"Increment the score of ``value`` in sorted set ``name`` by ``amount``\"\n        return self.execute_command('ZINCRBY', name, amount, value)\n\n    def zinterstore(self, dest, keys, aggregate=None):\n        \"\"\"\n        Intersect multiple sorted sets specified by ``keys`` into\n        a new sorted set, ``dest``. Scores in the destination will be\n        aggregated based on the ``aggregate``, or SUM if none is provided.\n        \"\"\"\n        return self._zaggregate('ZINTERSTORE', dest, keys, aggregate)\n\n    def zlexcount(self, name, min, max):\n        \"\"\"\n        Return the number of items in the sorted set ``name`` between the\n        lexicographical range ``min`` and ``max``.\n        \"\"\"\n        return self.execute_command('ZLEXCOUNT', name, min, max)\n\n    def zpopmax(self, name, count=None):\n        \"\"\"\n        Remove and return up to ``count`` members with the highest scores\n        from the sorted set ``name``.\n        \"\"\"\n        args = (count is not None) and [count] or []\n        options = {\n            'withscores': True\n        }\n        return self.execute_command('ZPOPMAX', name, *args, **options)\n\n    def zpopmin(self, name, count=None):\n        \"\"\"\n        Remove and return up to ``count`` members with the lowest scores\n        from the sorted set ``name``.\n        \"\"\"\n        args = (count is not None) and [count] or []\n        options = {\n            'withscores': True\n        }\n        return self.execute_command('ZPOPMIN', name, *args, **options)\n\n    def bzpopmax(self, keys, timeout=0):\n        \"\"\"\n        ZPOPMAX a value off of the first non-empty sorted set\n        named in the ``keys`` list.\n\n        If none of the sorted sets in ``keys`` has a value to ZPOPMAX,\n        then block for ``timeout`` seconds, or until a member gets added\n        to one of the sorted sets.\n\n        If timeout is 0, then block indefinitely.\n        \"\"\"\n        if timeout is None:\n            timeout = 0\n        keys = list_or_args(keys, None)\n        keys.append(timeout)\n        return self.execute_command('BZPOPMAX', *keys)\n\n    def bzpopmin(self, keys, timeout=0):\n        \"\"\"\n        ZPOPMIN a value off of the first non-empty sorted set\n        named in the ``keys`` list.\n\n        If none of the sorted sets in ``keys`` has a value to ZPOPMIN,\n        then block for ``timeout`` seconds, or until a member gets added\n        to one of the sorted sets.\n\n        If timeout is 0, then block indefinitely.\n        \"\"\"\n        if timeout is None:\n            timeout = 0\n        keys = list_or_args(keys, None)\n        keys.append(timeout)\n        return self.execute_command('BZPOPMIN', *keys)\n\n    def zrange(self, name, start, end, desc=False, withscores=False,\n               score_cast_func=float):\n        \"\"\"\n        Return a range of values from sorted set ``name`` between\n        ``start`` and ``end`` sorted in ascending order.\n\n        ``start`` and ``end`` can be negative, indicating the end of the range.\n\n        ``desc`` a boolean indicating whether to sort the results descendingly\n\n        ``withscores`` indicates to return the scores along with the values.\n        The return type is a list of (value, score) pairs\n\n        ``score_cast_func`` a callable used to cast the score return value\n        \"\"\"\n        if desc:\n            return self.zrevrange(name, start, end, withscores,\n                                  score_cast_func)\n        pieces = ['ZRANGE', name, start, end]\n        if withscores:\n            pieces.append(b'WITHSCORES')\n        options = {\n            'withscores': withscores,\n            'score_cast_func': score_cast_func\n        }\n        return self.execute_command(*pieces, **options)\n\n    def zrangebylex(self, name, min, max, start=None, num=None):\n        \"\"\"\n        Return the lexicographical range of values from sorted set ``name``\n        between ``min`` and ``max``.\n\n        If ``start`` and ``num`` are specified, then return a slice of the\n        range.\n        \"\"\"\n        if (start is not None and num is None) or \\\n                (num is not None and start is None):\n            raise DataError(\"``start`` and ``num`` must both be specified\")\n        pieces = ['ZRANGEBYLEX', name, min, max]\n        if start is not None and num is not None:\n            pieces.extend([b'LIMIT', start, num])\n        return self.execute_command(*pieces)\n\n    def zrevrangebylex(self, name, max, min, start=None, num=None):\n        \"\"\"\n        Return the reversed lexicographical range of values from sorted set\n        ``name`` between ``max`` and ``min``.\n\n        If ``start`` and ``num`` are specified, then return a slice of the\n        range.\n        \"\"\"\n        if (start is not None and num is None) or \\\n                (num is not None and start is None):\n            raise DataError(\"``start`` and ``num`` must both be specified\")\n        pieces = ['ZREVRANGEBYLEX', name, max, min]\n        if start is not None and num is not None:\n            pieces.extend([b'LIMIT', start, num])\n        return self.execute_command(*pieces)\n\n    def zrangebyscore(self, name, min, max, start=None, num=None,\n                      withscores=False, score_cast_func=float):\n        \"\"\"\n        Return a range of values from the sorted set ``name`` with scores\n        between ``min`` and ``max``.\n\n        If ``start`` and ``num`` are specified, then return a slice\n        of the range.\n\n        ``withscores`` indicates to return the scores along with the values.\n        The return type is a list of (value, score) pairs\n\n        `score_cast_func`` a callable used to cast the score return value\n        \"\"\"\n        if (start is not None and num is None) or \\\n                (num is not None and start is None):\n            raise DataError(\"``start`` and ``num`` must both be specified\")\n        pieces = ['ZRANGEBYSCORE', name, min, max]\n        if start is not None and num is not None:\n            pieces.extend([b'LIMIT', start, num])\n        if withscores:\n            pieces.append(b'WITHSCORES')\n        options = {\n            'withscores': withscores,\n            'score_cast_func': score_cast_func\n        }\n        return self.execute_command(*pieces, **options)\n\n    def zrank(self, name, value):\n        \"\"\"\n        Returns a 0-based value indicating the rank of ``value`` in sorted set\n        ``name``\n        \"\"\"\n        return self.execute_command('ZRANK', name, value)\n\n    def zrem(self, name, *values):\n        \"Remove member ``values`` from sorted set ``name``\"\n        return self.execute_command('ZREM', name, *values)\n\n    def zremrangebylex(self, name, min, max):\n        \"\"\"\n        Remove all elements in the sorted set ``name`` between the\n        lexicographical range specified by ``min`` and ``max``.\n\n        Returns the number of elements removed.\n        \"\"\"\n        return self.execute_command('ZREMRANGEBYLEX', name, min, max)\n\n    def zremrangebyrank(self, name, min, max):\n        \"\"\"\n        Remove all elements in the sorted set ``name`` with ranks between\n        ``min`` and ``max``. Values are 0-based, ordered from smallest score\n        to largest. Values can be negative indicating the highest scores.\n        Returns the number of elements removed\n        \"\"\"\n        return self.execute_command('ZREMRANGEBYRANK', name, min, max)\n\n    def zremrangebyscore(self, name, min, max):\n        \"\"\"\n        Remove all elements in the sorted set ``name`` with scores\n        between ``min`` and ``max``. Returns the number of elements removed.\n        \"\"\"\n        return self.execute_command('ZREMRANGEBYSCORE', name, min, max)\n\n    def zrevrange(self, name, start, end, withscores=False,\n                  score_cast_func=float):\n        \"\"\"\n        Return a range of values from sorted set ``name`` between\n        ``start`` and ``end`` sorted in descending order.\n\n        ``start`` and ``end`` can be negative, indicating the end of the range.\n\n        ``withscores`` indicates to return the scores along with the values\n        The return type is a list of (value, score) pairs\n\n        ``score_cast_func`` a callable used to cast the score return value\n        \"\"\"\n        pieces = ['ZREVRANGE', name, start, end]\n        if withscores:\n            pieces.append(b'WITHSCORES')\n        options = {\n            'withscores': withscores,\n            'score_cast_func': score_cast_func\n        }\n        return self.execute_command(*pieces, **options)\n\n    def zrevrangebyscore(self, name, max, min, start=None, num=None,\n                         withscores=False, score_cast_func=float):\n        \"\"\"\n        Return a range of values from the sorted set ``name`` with scores\n        between ``min`` and ``max`` in descending order.\n\n        If ``start`` and ``num`` are specified, then return a slice\n        of the range.\n\n        ``withscores`` indicates to return the scores along with the values.\n        The return type is a list of (value, score) pairs\n\n        ``score_cast_func`` a callable used to cast the score return value\n        \"\"\"\n        if (start is not None and num is None) or \\\n                (num is not None and start is None):\n            raise DataError(\"``start`` and ``num`` must both be specified\")\n        pieces = ['ZREVRANGEBYSCORE', name, max, min]\n        if start is not None and num is not None:\n            pieces.extend([b'LIMIT', start, num])\n        if withscores:\n            pieces.append(b'WITHSCORES')\n        options = {\n            'withscores': withscores,\n            'score_cast_func': score_cast_func\n        }\n        return self.execute_command(*pieces, **options)\n\n    def zrevrank(self, name, value):\n        \"\"\"\n        Returns a 0-based value indicating the descending rank of\n        ``value`` in sorted set ``name``\n        \"\"\"\n        return self.execute_command('ZREVRANK', name, value)\n\n    def zscore(self, name, value):\n        \"Return the score of element ``value`` in sorted set ``name``\"\n        return self.execute_command('ZSCORE', name, value)\n\n    def zunionstore(self, dest, keys, aggregate=None):\n        \"\"\"\n        Union multiple sorted sets specified by ``keys`` into\n        a new sorted set, ``dest``. Scores in the destination will be\n        aggregated based on the ``aggregate``, or SUM if none is provided.\n        \"\"\"\n        return self._zaggregate('ZUNIONSTORE', dest, keys, aggregate)\n\n    def _zaggregate(self, command, dest, keys, aggregate=None):\n        pieces = [command, dest, len(keys)]\n        if isinstance(keys, dict):\n            keys, weights = iterkeys(keys), itervalues(keys)\n        else:\n            weights = None\n        pieces.extend(keys)\n        if weights:\n            pieces.append(b'WEIGHTS')\n            pieces.extend(weights)\n        if aggregate:\n            pieces.append(b'AGGREGATE')\n            pieces.append(aggregate)\n        return self.execute_command(*pieces)\n\n    # HYPERLOGLOG COMMANDS\n    def pfadd(self, name, *values):\n        \"Adds the specified elements to the specified HyperLogLog.\"\n        return self.execute_command('PFADD', name, *values)\n\n    def pfcount(self, *sources):\n        \"\"\"\n        Return the approximated cardinality of\n        the set observed by the HyperLogLog at key(s).\n        \"\"\"\n        return self.execute_command('PFCOUNT', *sources)\n\n    def pfmerge(self, dest, *sources):\n        \"Merge N different HyperLogLogs into a single one.\"\n        return self.execute_command('PFMERGE', dest, *sources)\n\n    # HASH COMMANDS\n    def hdel(self, name, *keys):\n        \"Delete ``keys`` from hash ``name``\"\n        return self.execute_command('HDEL', name, *keys)\n\n    def hexists(self, name, key):\n        \"Returns a boolean indicating if ``key`` exists within hash ``name``\"\n        return self.execute_command('HEXISTS', name, key)\n\n    def hget(self, name, key):\n        \"Return the value of ``key`` within the hash ``name``\"\n        return self.execute_command('HGET', name, key)\n\n    def hgetall(self, name):\n        \"Return a Python dict of the hash's name/value pairs\"\n        return self.execute_command('HGETALL', name)\n\n    def hincrby(self, name, key, amount=1):\n        \"Increment the value of ``key`` in hash ``name`` by ``amount``\"\n        return self.execute_command('HINCRBY', name, key, amount)\n\n    def hincrbyfloat(self, name, key, amount=1.0):\n        \"\"\"\n        Increment the value of ``key`` in hash ``name`` by floating ``amount``\n        \"\"\"\n        return self.execute_command('HINCRBYFLOAT', name, key, amount)\n\n    def hkeys(self, name):\n        \"Return the list of keys within hash ``name``\"\n        return self.execute_command('HKEYS', name)\n\n    def hlen(self, name):\n        \"Return the number of elements in hash ``name``\"\n        return self.execute_command('HLEN', name)\n\n    def hset(self, name, key, value):\n        \"\"\"\n        Set ``key`` to ``value`` within hash ``name``\n        Returns 1 if HSET created a new field, otherwise 0\n        \"\"\"\n        return self.execute_command('HSET', name, key, value)\n\n    def hsetnx(self, name, key, value):\n        \"\"\"\n        Set ``key`` to ``value`` within hash ``name`` if ``key`` does not\n        exist.  Returns 1 if HSETNX created a field, otherwise 0.\n        \"\"\"\n        return self.execute_command('HSETNX', name, key, value)\n\n    def hmset(self, name, mapping):\n        \"\"\"\n        Set key to value within hash ``name`` for each corresponding\n        key and value from the ``mapping`` dict.\n        \"\"\"\n        if not mapping:\n            raise DataError(\"'hmset' with 'mapping' of length 0\")\n        items = []\n        for pair in iteritems(mapping):\n            items.extend(pair)\n        return self.execute_command('HMSET', name, *items)\n\n    def hmget(self, name, keys, *args):\n        \"Returns a list of values ordered identically to ``keys``\"\n        args = list_or_args(keys, args)\n        return self.execute_command('HMGET', name, *args)\n\n    def hvals(self, name):\n        \"Return the list of values within hash ``name``\"\n        return self.execute_command('HVALS', name)\n\n    def hstrlen(self, name, key):\n        \"\"\"\n        Return the number of bytes stored in the value of ``key``\n        within hash ``name``\n        \"\"\"\n        return self.execute_command('HSTRLEN', name, key)\n\n    def publish(self, channel, message):\n        \"\"\"\n        Publish ``message`` on ``channel``.\n        Returns the number of subscribers the message was delivered to.\n        \"\"\"\n        return self.execute_command('PUBLISH', channel, message)\n\n    def pubsub_channels(self, pattern='*'):\n        \"\"\"\n        Return a list of channels that have at least one subscriber\n        \"\"\"\n        return self.execute_command('PUBSUB CHANNELS', pattern)\n\n    def pubsub_numpat(self):\n        \"\"\"\n        Returns the number of subscriptions to patterns\n        \"\"\"\n        return self.execute_command('PUBSUB NUMPAT')\n\n    def pubsub_numsub(self, *args):\n        \"\"\"\n        Return a list of (channel, number of subscribers) tuples\n        for each channel given in ``*args``\n        \"\"\"\n        return self.execute_command('PUBSUB NUMSUB', *args)\n\n    def cluster(self, cluster_arg, *args):\n        return self.execute_command('CLUSTER %s' % cluster_arg.upper(), *args)\n\n    def eval(self, script, numkeys, *keys_and_args):\n        \"\"\"\n        Execute the Lua ``script``, specifying the ``numkeys`` the script\n        will touch and the key names and argument values in ``keys_and_args``.\n        Returns the result of the script.\n\n        In practice, use the object returned by ``register_script``. This\n        function exists purely for Redis API completion.\n        \"\"\"\n        return self.execute_command('EVAL', script, numkeys, *keys_and_args)\n\n    def evalsha(self, sha, numkeys, *keys_and_args):\n        \"\"\"\n        Use the ``sha`` to execute a Lua script already registered via EVAL\n        or SCRIPT LOAD. Specify the ``numkeys`` the script will touch and the\n        key names and argument values in ``keys_and_args``. Returns the result\n        of the script.\n\n        In practice, use the object returned by ``register_script``. This\n        function exists purely for Redis API completion.\n        \"\"\"\n        return self.execute_command('EVALSHA', sha, numkeys, *keys_and_args)\n\n    def script_exists(self, *args):\n        \"\"\"\n        Check if a script exists in the script cache by specifying the SHAs of\n        each script as ``args``. Returns a list of boolean values indicating if\n        if each already script exists in the cache.\n        \"\"\"\n        return self.execute_command('SCRIPT EXISTS', *args)\n\n    def script_flush(self):\n        \"Flush all scripts from the script cache\"\n        return self.execute_command('SCRIPT FLUSH')\n\n    def script_kill(self):\n        \"Kill the currently executing Lua script\"\n        return self.execute_command('SCRIPT KILL')\n\n    def script_load(self, script):\n        \"Load a Lua ``script`` into the script cache. Returns the SHA.\"\n        return self.execute_command('SCRIPT LOAD', script)\n\n    def register_script(self, script):\n        \"\"\"\n        Register a Lua ``script`` specifying the ``keys`` it will touch.\n        Returns a Script object that is callable and hides the complexity of\n        deal with scripts, keys, and shas. This is the preferred way to work\n        with Lua scripts.\n        \"\"\"\n        return Script(self, script)\n\n    # GEO COMMANDS\n    def geoadd(self, name, *values):\n        \"\"\"\n        Add the specified geospatial items to the specified key identified\n        by the ``name`` argument. The Geospatial items are given as ordered\n        members of the ``values`` argument, each item or place is formed by\n        the triad longitude, latitude and name.\n        \"\"\"\n        if len(values) % 3 != 0:\n            raise DataError(\"GEOADD requires places with lon, lat and name\"\n                            \" values\")\n        return self.execute_command('GEOADD', name, *values)\n\n    def geodist(self, name, place1, place2, unit=None):\n        \"\"\"\n        Return the distance between ``place1`` and ``place2`` members of the\n        ``name`` key.\n        The units must be one of the following : m, km mi, ft. By default\n        meters are used.\n        \"\"\"\n        pieces = [name, place1, place2]\n        if unit and unit not in ('m', 'km', 'mi', 'ft'):\n            raise DataError(\"GEODIST invalid unit\")\n        elif unit:\n            pieces.append(unit)\n        return self.execute_command('GEODIST', *pieces)\n\n    def geohash(self, name, *values):\n        \"\"\"\n        Return the geo hash string for each item of ``values`` members of\n        the specified key identified by the ``name`` argument.\n        \"\"\"\n        return self.execute_command('GEOHASH', name, *values)\n\n    def geopos(self, name, *values):\n        \"\"\"\n        Return the positions of each item of ``values`` as members of\n        the specified key identified by the ``name`` argument. Each position\n        is represented by the pairs lon and lat.\n        \"\"\"\n        return self.execute_command('GEOPOS', name, *values)\n\n    def georadius(self, name, longitude, latitude, radius, unit=None,\n                  withdist=False, withcoord=False, withhash=False, count=None,\n                  sort=None, store=None, store_dist=None):\n        \"\"\"\n        Return the members of the specified key identified by the\n        ``name`` argument which are within the borders of the area specified\n        with the ``latitude`` and ``longitude`` location and the maximum\n        distance from the center specified by the ``radius`` value.\n\n        The units must be one of the following : m, km mi, ft. By default\n\n        ``withdist`` indicates to return the distances of each place.\n\n        ``withcoord`` indicates to return the latitude and longitude of\n        each place.\n\n        ``withhash`` indicates to return the geohash string of each place.\n\n        ``count`` indicates to return the number of elements up to N.\n\n        ``sort`` indicates to return the places in a sorted way, ASC for\n        nearest to fairest and DESC for fairest to nearest.\n\n        ``store`` indicates to save the places names in a sorted set named\n        with a specific key, each element of the destination sorted set is\n        populated with the score got from the original geo sorted set.\n\n        ``store_dist`` indicates to save the places names in a sorted set\n        named with a specific key, instead of ``store`` the sorted set\n        destination score is set with the distance.\n        \"\"\"\n        return self._georadiusgeneric('GEORADIUS',\n                                      name, longitude, latitude, radius,\n                                      unit=unit, withdist=withdist,\n                                      withcoord=withcoord, withhash=withhash,\n                                      count=count, sort=sort, store=store,\n                                      store_dist=store_dist)\n\n    def georadiusbymember(self, name, member, radius, unit=None,\n                          withdist=False, withcoord=False, withhash=False,\n                          count=None, sort=None, store=None, store_dist=None):\n        \"\"\"\n        This command is exactly like ``georadius`` with the sole difference\n        that instead of taking, as the center of the area to query, a longitude\n        and latitude value, it takes the name of a member already existing\n        inside the geospatial index represented by the sorted set.\n        \"\"\"\n        return self._georadiusgeneric('GEORADIUSBYMEMBER',\n                                      name, member, radius, unit=unit,\n                                      withdist=withdist, withcoord=withcoord,\n                                      withhash=withhash, count=count,\n                                      sort=sort, store=store,\n                                      store_dist=store_dist)\n\n    def _georadiusgeneric(self, command, *args, **kwargs):\n        pieces = list(args)\n        if kwargs['unit'] and kwargs['unit'] not in ('m', 'km', 'mi', 'ft'):\n            raise DataError(\"GEORADIUS invalid unit\")\n        elif kwargs['unit']:\n            pieces.append(kwargs['unit'])\n        else:\n            pieces.append('m',)\n\n        for arg_name, byte_repr in (\n                ('withdist', b'WITHDIST'),\n                ('withcoord', b'WITHCOORD'),\n                ('withhash', b'WITHHASH')):\n            if kwargs[arg_name]:\n                pieces.append(byte_repr)\n\n        if kwargs['count']:\n            pieces.extend([b'COUNT', kwargs['count']])\n\n        if kwargs['sort']:\n            if kwargs['sort'] == 'ASC':\n                pieces.append(b'ASC')\n            elif kwargs['sort'] == 'DESC':\n                pieces.append(b'DESC')\n            else:\n                raise DataError(\"GEORADIUS invalid sort\")\n\n        if kwargs['store'] and kwargs['store_dist']:\n            raise DataError(\"GEORADIUS store and store_dist cant be set\"\n                            \" together\")\n\n        if kwargs['store']:\n            pieces.extend([b'STORE', kwargs['store']])\n\n        if kwargs['store_dist']:\n            pieces.extend([b'STOREDIST', kwargs['store_dist']])\n\n        return self.execute_command(command, *pieces, **kwargs)\n\n\nStrictRedis = Redis\n\n\nclass Monitor(object):\n    \"\"\"\n    Monitor is useful for handling the MONITOR command to the redis server.\n    next_command() method returns one command from monitor\n    listen() method yields commands from monitor.\n    \"\"\"\n    monitor_re = re.compile(r'\\[(\\d+) (.*)\\] (.*)')\n    command_re = re.compile(r'\"(.*?)(?<!\\\\)\"')\n\n    def __init__(self, connection_pool):\n        self.connection_pool = connection_pool\n        self.connection = self.connection_pool.get_connection('MONITOR')\n\n    def __enter__(self):\n        self.connection.send_command('MONITOR')\n        # check that monitor returns 'OK', but don't return it to user\n        response = self.connection.read_response()\n        if not bool_ok(response):\n            raise RedisError('MONITOR failed: %s' % response)\n        return self\n\n    def __exit__(self, *args):\n        self.connection.disconnect()\n        self.connection_pool.release(self.connection)\n\n    def next_command(self):\n        \"Parse the response from a monitor command\"\n        response = self.connection.read_response()\n        if isinstance(response, bytes):\n            response = self.connection.encoder.decode(response, force=True)\n        command_time, command_data = response.split(' ', 1)\n        m = self.monitor_re.match(command_data)\n        db_id, client_info, command = m.groups()\n        command = ' '.join(self.command_re.findall(command))\n        command = command.replace('\\\\\"', '\"').replace('\\\\\\\\', '\\\\')\n\n        if client_info == 'lua':\n            client_address = 'lua'\n            client_port = ''\n            client_type = 'lua'\n        elif client_info.startswith('unix'):\n            client_address = 'unix'\n            client_port = client_info[5:]\n            client_type = 'unix'\n        else:\n            # use rsplit as ipv6 addresses contain colons\n            client_address, client_port = client_info.rsplit(':', 1)\n            client_type = 'tcp'\n        return {\n            'time': float(command_time),\n            'db': int(db_id),\n            'client_address': client_address,\n            'client_port': client_port,\n            'client_type': client_type,\n            'command': command\n        }\n\n    def listen(self):\n        \"Listen for commands coming to the server.\"\n        while True:\n            yield self.next_command()\n\n\nclass PubSub(object):\n    \"\"\"\n    PubSub provides publish, subscribe and listen support to Redis channels.\n\n    After subscribing to one or more channels, the listen() method will block\n    until a message arrives on one of the subscribed channels. That message\n    will be returned and it's safe to start listening again.\n    \"\"\"\n    PUBLISH_MESSAGE_TYPES = ('message', 'pmessage')\n    UNSUBSCRIBE_MESSAGE_TYPES = ('unsubscribe', 'punsubscribe')\n    HEALTH_CHECK_MESSAGE = 'redis-py-health-check'\n\n    def __init__(self, connection_pool, shard_hint=None,\n                 ignore_subscribe_messages=False):\n        self.connection_pool = connection_pool\n        self.shard_hint = shard_hint\n        self.ignore_subscribe_messages = ignore_subscribe_messages\n        self.connection = None\n        # we need to know the encoding options for this connection in order\n        # to lookup channel and pattern names for callback handlers.\n        self.encoder = self.connection_pool.get_encoder()\n        if self.encoder.decode_responses:\n            self.health_check_response = ['pong', self.HEALTH_CHECK_MESSAGE]\n        else:\n            self.health_check_response = [\n                b'pong',\n                self.encoder.encode(self.HEALTH_CHECK_MESSAGE)\n            ]\n        self.reset()\n\n    def __del__(self):\n        try:\n            # if this object went out of scope prior to shutting down\n            # subscriptions, close the connection manually before\n            # returning it to the connection pool\n            self.reset()\n        except Exception:\n            pass\n\n    def reset(self):\n        if self.connection:\n            self.connection.disconnect()\n            self.connection.clear_connect_callbacks()\n            self.connection_pool.release(self.connection)\n            self.connection = None\n        self.channels = {}\n        self.pending_unsubscribe_channels = set()\n        self.patterns = {}\n        self.pending_unsubscribe_patterns = set()\n\n    def close(self):\n        self.reset()\n\n    def on_connect(self, connection):\n        \"Re-subscribe to any channels and patterns previously subscribed to\"\n        # NOTE: for python3, we can't pass bytestrings as keyword arguments\n        # so we need to decode channel/pattern names back to unicode strings\n        # before passing them to [p]subscribe.\n        self.pending_unsubscribe_channels.clear()\n        self.pending_unsubscribe_patterns.clear()\n        if self.channels:\n            channels = {}\n            for k, v in iteritems(self.channels):\n                channels[self.encoder.decode(k, force=True)] = v\n            self.subscribe(**channels)\n        if self.patterns:\n            patterns = {}\n            for k, v in iteritems(self.patterns):\n                patterns[self.encoder.decode(k, force=True)] = v\n            self.psubscribe(**patterns)\n\n    @property\n    def subscribed(self):\n        \"Indicates if there are subscriptions to any channels or patterns\"\n        return bool(self.channels or self.patterns)\n\n    def execute_command(self, *args):\n        \"Execute a publish/subscribe command\"\n\n        # NOTE: don't parse the response in this function -- it could pull a\n        # legitimate message off the stack if the connection is already\n        # subscribed to one or more channels\n\n        if self.connection is None:\n            self.connection = self.connection_pool.get_connection(\n                'pubsub',\n                self.shard_hint\n            )\n            # register a callback that re-subscribes to any channels we\n            # were listening to when we were disconnected\n            self.connection.register_connect_callback(self.on_connect)\n        connection = self.connection\n        kwargs = {'check_health': not self.subscribed}\n        self._execute(connection, connection.send_command, *args, **kwargs)\n\n    def _execute(self, connection, command, *args, **kwargs):\n        try:\n            return command(*args, **kwargs)\n        except (ConnectionError, TimeoutError) as e:\n            connection.disconnect()\n            if not (connection.retry_on_timeout and\n                    isinstance(e, TimeoutError)):\n                raise\n            # Connect manually here. If the Redis server is down, this will\n            # fail and raise a ConnectionError as desired.\n            connection.connect()\n            # the ``on_connect`` callback should haven been called by the\n            # connection to resubscribe us to any channels and patterns we were\n            # previously listening to\n            return command(*args, **kwargs)\n\n    def parse_response(self, block=True, timeout=0):\n        \"Parse the response from a publish/subscribe command\"\n        conn = self.connection\n        if conn is None:\n            raise RuntimeError(\n                'pubsub connection not set: '\n                'did you forget to call subscribe() or psubscribe()?')\n\n        self.check_health()\n\n        if not block and not conn.can_read(timeout=timeout):\n            return None\n        response = self._execute(conn, conn.read_response)\n\n        if conn.health_check_interval and \\\n                response == self.health_check_response:\n            # ignore the health check message as user might not expect it\n            return None\n        return response\n\n    def check_health(self):\n        conn = self.connection\n        if conn is None:\n            raise RuntimeError(\n                'pubsub connection not set: '\n                'did you forget to call subscribe() or psubscribe()?')\n\n        if conn.health_check_interval and time.time() > conn.next_health_check:\n            conn.send_command('PING', self.HEALTH_CHECK_MESSAGE,\n                              check_health=False)\n\n    def _normalize_keys(self, data):\n        \"\"\"\n        normalize channel/pattern names to be either bytes or strings\n        based on whether responses are automatically decoded. this saves us\n        from coercing the value for each message coming in.\n        \"\"\"\n        encode = self.encoder.encode\n        decode = self.encoder.decode\n        return {decode(encode(k)): v for k, v in iteritems(data)}\n\n    def psubscribe(self, *args, **kwargs):\n        \"\"\"\n        Subscribe to channel patterns. Patterns supplied as keyword arguments\n        expect a pattern name as the key and a callable as the value. A\n        pattern's callable will be invoked automatically when a message is\n        received on that pattern rather than producing a message via\n        ``listen()``.\n        \"\"\"\n        if args:\n            args = list_or_args(args[0], args[1:])\n        new_patterns = dict.fromkeys(args)\n        new_patterns.update(kwargs)\n        ret_val = self.execute_command('PSUBSCRIBE', *iterkeys(new_patterns))\n        # update the patterns dict AFTER we send the command. we don't want to\n        # subscribe twice to these patterns, once for the command and again\n        # for the reconnection.\n        new_patterns = self._normalize_keys(new_patterns)\n        self.patterns.update(new_patterns)\n        self.pending_unsubscribe_patterns.difference_update(new_patterns)\n        return ret_val\n\n    def punsubscribe(self, *args):\n        \"\"\"\n        Unsubscribe from the supplied patterns. If empty, unsubscribe from\n        all patterns.\n        \"\"\"\n        if args:\n            args = list_or_args(args[0], args[1:])\n            patterns = self._normalize_keys(dict.fromkeys(args))\n        else:\n            patterns = self.patterns\n        self.pending_unsubscribe_patterns.update(patterns)\n        return self.execute_command('PUNSUBSCRIBE', *args)\n\n    def subscribe(self, *args, **kwargs):\n        \"\"\"\n        Subscribe to channels. Channels supplied as keyword arguments expect\n        a channel name as the key and a callable as the value. A channel's\n        callable will be invoked automatically when a message is received on\n        that channel rather than producing a message via ``listen()`` or\n        ``get_message()``.\n        \"\"\"\n        if args:\n            args = list_or_args(args[0], args[1:])\n        new_channels = dict.fromkeys(args)\n        new_channels.update(kwargs)\n        ret_val = self.execute_command('SUBSCRIBE', *iterkeys(new_channels))\n        # update the channels dict AFTER we send the command. we don't want to\n        # subscribe twice to these channels, once for the command and again\n        # for the reconnection.\n        new_channels = self._normalize_keys(new_channels)\n        self.channels.update(new_channels)\n        self.pending_unsubscribe_channels.difference_update(new_channels)\n        return ret_val\n\n    def unsubscribe(self, *args):\n        \"\"\"\n        Unsubscribe from the supplied channels. If empty, unsubscribe from\n        all channels\n        \"\"\"\n        if args:\n            args = list_or_args(args[0], args[1:])\n            channels = self._normalize_keys(dict.fromkeys(args))\n        else:\n            channels = self.channels\n        self.pending_unsubscribe_channels.update(channels)\n        return self.execute_command('UNSUBSCRIBE', *args)\n\n    def listen(self):\n        \"Listen for messages on channels this client has been subscribed to\"\n        while self.subscribed:\n            response = self.handle_message(self.parse_response(block=True))\n            if response is not None:\n                yield response\n\n    def get_message(self, ignore_subscribe_messages=False, timeout=0):\n        \"\"\"\n        Get the next message if one is available, otherwise None.\n\n        If timeout is specified, the system will wait for `timeout` seconds\n        before returning. Timeout should be specified as a floating point\n        number.\n        \"\"\"\n        response = self.parse_response(block=False, timeout=timeout)\n        if response:\n            return self.handle_message(response, ignore_subscribe_messages)\n        return None\n\n    def ping(self, message=None):\n        \"\"\"\n        Ping the Redis server\n        \"\"\"\n        message = '' if message is None else message\n        return self.execute_command('PING', message)\n\n    def handle_message(self, response, ignore_subscribe_messages=False):\n        \"\"\"\n        Parses a pub/sub message. If the channel or pattern was subscribed to\n        with a message handler, the handler is invoked instead of a parsed\n        message being returned.\n        \"\"\"\n        message_type = nativestr(response[0])\n        if message_type == 'pmessage':\n            message = {\n                'type': message_type,\n                'pattern': response[1],\n                'channel': response[2],\n                'data': response[3]\n            }\n        elif message_type == 'pong':\n            message = {\n                'type': message_type,\n                'pattern': None,\n                'channel': None,\n                'data': response[1]\n            }\n        else:\n            message = {\n                'type': message_type,\n                'pattern': None,\n                'channel': response[1],\n                'data': response[2]\n            }\n\n        # if this is an unsubscribe message, remove it from memory\n        if message_type in self.UNSUBSCRIBE_MESSAGE_TYPES:\n            if message_type == 'punsubscribe':\n                pattern = response[1]\n                if pattern in self.pending_unsubscribe_patterns:\n                    self.pending_unsubscribe_patterns.remove(pattern)\n                    self.patterns.pop(pattern, None)\n            else:\n                channel = response[1]\n                if channel in self.pending_unsubscribe_channels:\n                    self.pending_unsubscribe_channels.remove(channel)\n                    self.channels.pop(channel, None)\n\n        if message_type in self.PUBLISH_MESSAGE_TYPES:\n            # if there's a message handler, invoke it\n            if message_type == 'pmessage':\n                handler = self.patterns.get(message['pattern'], None)\n            else:\n                handler = self.channels.get(message['channel'], None)\n            if handler:\n                handler(message)\n                return None\n        elif message_type != 'pong':\n            # this is a subscribe/unsubscribe message. ignore if we don't\n            # want them\n            if ignore_subscribe_messages or self.ignore_subscribe_messages:\n                return None\n\n        return message\n\n    def run_in_thread(self, sleep_time=0, daemon=False):\n        for channel, handler in iteritems(self.channels):\n            if handler is None:\n                raise PubSubError(\"Channel: '%s' has no handler registered\" %\n                                  channel)\n        for pattern, handler in iteritems(self.patterns):\n            if handler is None:\n                raise PubSubError(\"Pattern: '%s' has no handler registered\" %\n                                  pattern)\n\n        thread = PubSubWorkerThread(self, sleep_time, daemon=daemon)\n        thread.start()\n        return thread\n\n\nclass PubSubWorkerThread(threading.Thread):\n    def __init__(self, pubsub, sleep_time, daemon=False):\n        super(PubSubWorkerThread, self).__init__()\n        self.daemon = daemon\n        self.pubsub = pubsub\n        self.sleep_time = sleep_time\n        self._running = threading.Event()\n\n    def run(self):\n        if self._running.is_set():\n            return\n        self._running.set()\n        pubsub = self.pubsub\n        sleep_time = self.sleep_time\n        while self._running.is_set():\n            pubsub.get_message(ignore_subscribe_messages=True,\n                               timeout=sleep_time)\n        pubsub.close()\n\n    def stop(self):\n        # trip the flag so the run loop exits. the run loop will\n        # close the pubsub connection, which disconnects the socket\n        # and returns the connection to the pool.\n        self._running.clear()\n\n\nclass Pipeline(Redis):\n    \"\"\"\n    Pipelines provide a way to transmit multiple commands to the Redis server\n    in one transmission.  This is convenient for batch processing, such as\n    saving all the values in a list to Redis.\n\n    All commands executed within a pipeline are wrapped with MULTI and EXEC\n    calls. This guarantees all commands executed in the pipeline will be\n    executed atomically.\n\n    Any command raising an exception does *not* halt the execution of\n    subsequent commands in the pipeline. Instead, the exception is caught\n    and its instance is placed into the response list returned by execute().\n    Code iterating over the response list should be able to deal with an\n    instance of an exception as a potential value. In general, these will be\n    ResponseError exceptions, such as those raised when issuing a command\n    on a key of a different datatype.\n    \"\"\"\n\n    UNWATCH_COMMANDS = {'DISCARD', 'EXEC', 'UNWATCH'}\n\n    def __init__(self, connection_pool, response_callbacks, transaction,\n                 shard_hint):\n        self.connection_pool = connection_pool\n        self.connection = None\n        self.response_callbacks = response_callbacks\n        self.transaction = transaction\n        self.shard_hint = shard_hint\n\n        self.watching = False\n        self.reset()\n\n    def __enter__(self):\n        return self\n\n    def __exit__(self, exc_type, exc_value, traceback):\n        self.reset()\n\n    def __del__(self):\n        try:\n            self.reset()\n        except Exception:\n            pass\n\n    def __len__(self):\n        return len(self.command_stack)\n\n    def reset(self):\n        self.command_stack = []\n        self.scripts = set()\n        # make sure to reset the connection state in the event that we were\n        # watching something\n        if self.watching and self.connection:\n            try:\n                # call this manually since our unwatch or\n                # immediate_execute_command methods can call reset()\n                self.connection.send_command('UNWATCH')\n                self.connection.read_response()\n            except ConnectionError:\n                # disconnect will also remove any previous WATCHes\n                self.connection.disconnect()\n        # clean up the other instance attributes\n        self.watching = False\n        self.explicit_transaction = False\n        # we can safely return the connection to the pool here since we're\n        # sure we're no longer WATCHing anything\n        if self.connection:\n            self.connection_pool.release(self.connection)\n            self.connection = None\n\n    def multi(self):\n        \"\"\"\n        Start a transactional block of the pipeline after WATCH commands\n        are issued. End the transactional block with `execute`.\n        \"\"\"\n        if self.explicit_transaction:\n            raise RedisError('Cannot issue nested calls to MULTI')\n        if self.command_stack:\n            raise RedisError('Commands without an initial WATCH have already '\n                             'been issued')\n        self.explicit_transaction = True\n\n    def execute_command(self, *args, **kwargs):\n        if (self.watching or args[0] == 'WATCH') and \\\n                not self.explicit_transaction:\n            return self.immediate_execute_command(*args, **kwargs)\n        return self.pipeline_execute_command(*args, **kwargs)\n\n    def immediate_execute_command(self, *args, **options):\n        \"\"\"\n        Execute a command immediately, but don't auto-retry on a\n        ConnectionError if we're already WATCHing a variable. Used when\n        issuing WATCH or subsequent commands retrieving their values but before\n        MULTI is called.\n        \"\"\"\n        command_name = args[0]\n        conn = self.connection\n        # if this is the first call, we need a connection\n        if not conn:\n            conn = self.connection_pool.get_connection(command_name,\n                                                       self.shard_hint)\n            self.connection = conn\n        try:\n            conn.send_command(*args)\n            return self.parse_response(conn, command_name, **options)\n        except (ConnectionError, TimeoutError) as e:\n            conn.disconnect()\n            # if we were already watching a variable, the watch is no longer\n            # valid since this connection has died. raise a WatchError, which\n            # indicates the user should retry this transaction.\n            if self.watching:\n                self.reset()\n                raise WatchError(\"A ConnectionError occured on while watching \"\n                                 \"one or more keys\")\n            # if retry_on_timeout is not set, or the error is not\n            # a TimeoutError, raise it\n            if not (conn.retry_on_timeout and isinstance(e, TimeoutError)):\n                self.reset()\n                raise\n\n            # retry_on_timeout is set, this is a TimeoutError and we are not\n            # already WATCHing any variables. retry the command.\n            try:\n                conn.send_command(*args)\n                return self.parse_response(conn, command_name, **options)\n            except (ConnectionError, TimeoutError):\n                # a subsequent failure should simply be raised\n                self.reset()\n                raise\n\n    def pipeline_execute_command(self, *args, **options):\n        \"\"\"\n        Stage a command to be executed when execute() is next called\n\n        Returns the current Pipeline object back so commands can be\n        chained together, such as:\n\n        pipe = pipe.set('foo', 'bar').incr('baz').decr('bang')\n\n        At some other point, you can then run: pipe.execute(),\n        which will execute all commands queued in the pipe.\n        \"\"\"\n        self.command_stack.append((args, options))\n        return self\n\n    def _execute_transaction(self, connection, commands, raise_on_error):\n        cmds = chain([(('MULTI', ), {})], commands, [(('EXEC', ), {})])\n        all_cmds = connection.pack_commands([args for args, options in cmds\n                                             if EMPTY_RESPONSE not in options])\n        connection.send_packed_command(all_cmds)\n        errors = []\n\n        # parse off the response for MULTI\n        # NOTE: we need to handle ResponseErrors here and continue\n        # so that we read all the additional command messages from\n        # the socket\n        try:\n            self.parse_response(connection, '_')\n        except ResponseError:\n            errors.append((0, sys.exc_info()[1]))\n\n        # and all the other commands\n        for i, command in enumerate(commands):\n            if EMPTY_RESPONSE in command[1]:\n                errors.append((i, command[1][EMPTY_RESPONSE]))\n            else:\n                try:\n                    self.parse_response(connection, '_')\n                except ResponseError:\n                    ex = sys.exc_info()[1]\n                    self.annotate_exception(ex, i + 1, command[0])\n                    errors.append((i, ex))\n\n        # parse the EXEC.\n        try:\n            response = self.parse_response(connection, '_')\n        except ExecAbortError:\n            if self.explicit_transaction:\n                self.immediate_execute_command('DISCARD')\n            if errors:\n                raise errors[0][1]\n            raise sys.exc_info()[1]\n\n        if response is None:\n            raise WatchError(\"Watched variable changed.\")\n\n        # put any parse errors into the response\n        for i, e in errors:\n            response.insert(i, e)\n\n        if len(response) != len(commands):\n            self.connection.disconnect()\n            raise ResponseError(\"Wrong number of response items from \"\n                                \"pipeline execution\")\n\n        # find any errors in the response and raise if necessary\n        if raise_on_error:\n            self.raise_first_error(commands, response)\n\n        # We have to run response callbacks manually\n        data = []\n        for r, cmd in izip(response, commands):\n            if not isinstance(r, Exception):\n                args, options = cmd\n                command_name = args[0]\n                if command_name in self.response_callbacks:\n                    r = self.response_callbacks[command_name](r, **options)\n            data.append(r)\n        return data\n\n    def _execute_pipeline(self, connection, commands, raise_on_error):\n        # build up all commands into a single request to increase network perf\n        all_cmds = connection.pack_commands([args for args, _ in commands])\n        connection.send_packed_command(all_cmds)\n\n        response = []\n        for args, options in commands:\n            try:\n                response.append(\n                    self.parse_response(connection, args[0], **options))\n            except ResponseError:\n                response.append(sys.exc_info()[1])\n\n        if raise_on_error:\n            self.raise_first_error(commands, response)\n        return response\n\n    def raise_first_error(self, commands, response):\n        for i, r in enumerate(response):\n            if isinstance(r, ResponseError):\n                self.annotate_exception(r, i + 1, commands[i][0])\n                raise r\n\n    def annotate_exception(self, exception, number, command):\n        cmd = ' '.join(imap(safe_unicode, command))\n        msg = 'Command # %d (%s) of pipeline caused error: %s' % (\n            number, cmd, safe_unicode(exception.args[0]))\n        exception.args = (msg,) + exception.args[1:]\n\n    def parse_response(self, connection, command_name, **options):\n        result = Redis.parse_response(\n            self, connection, command_name, **options)\n        if command_name in self.UNWATCH_COMMANDS:\n            self.watching = False\n        elif command_name == 'WATCH':\n            self.watching = True\n        return result\n\n    def load_scripts(self):\n        # make sure all scripts that are about to be run on this pipeline exist\n        scripts = list(self.scripts)\n        immediate = self.immediate_execute_command\n        shas = [s.sha for s in scripts]\n        # we can't use the normal script_* methods because they would just\n        # get buffered in the pipeline.\n        exists = immediate('SCRIPT EXISTS', *shas)\n        if not all(exists):\n            for s, exist in izip(scripts, exists):\n                if not exist:\n                    s.sha = immediate('SCRIPT LOAD', s.script)\n\n    def execute(self, raise_on_error=True):\n        \"Execute all the commands in the current pipeline\"\n        stack = self.command_stack\n        if not stack:\n            return []\n        if self.scripts:\n            self.load_scripts()\n        if self.transaction or self.explicit_transaction:\n            execute = self._execute_transaction\n        else:\n            execute = self._execute_pipeline\n\n        conn = self.connection\n        if not conn:\n            conn = self.connection_pool.get_connection('MULTI',\n                                                       self.shard_hint)\n            # assign to self.connection so reset() releases the connection\n            # back to the pool after we're done\n            self.connection = conn\n\n        try:\n            return execute(conn, stack, raise_on_error)\n        except (ConnectionError, TimeoutError) as e:\n            conn.disconnect()\n            # if we were watching a variable, the watch is no longer valid\n            # since this connection has died. raise a WatchError, which\n            # indicates the user should retry this transaction.\n            if self.watching:\n                raise WatchError(\"A ConnectionError occured on while watching \"\n                                 \"one or more keys\")\n            # if retry_on_timeout is not set, or the error is not\n            # a TimeoutError, raise it\n            if not (conn.retry_on_timeout and isinstance(e, TimeoutError)):\n                raise\n            # retry a TimeoutError when retry_on_timeout is set\n            return execute(conn, stack, raise_on_error)\n        finally:\n            self.reset()\n\n    def watch(self, *names):\n        \"Watches the values at keys ``names``\"\n        if self.explicit_transaction:\n            raise RedisError('Cannot issue a WATCH after a MULTI')\n        return self.execute_command('WATCH', *names)\n\n    def unwatch(self):\n        \"Unwatches all previously specified keys\"\n        return self.watching and self.execute_command('UNWATCH') or True\n\n\nclass Script(object):\n    \"An executable Lua script object returned by ``register_script``\"\n\n    def __init__(self, registered_client, script):\n        self.registered_client = registered_client\n        self.script = script\n        # Precalculate and store the SHA1 hex digest of the script.\n\n        if isinstance(script, basestring):\n            # We need the encoding from the client in order to generate an\n            # accurate byte representation of the script\n            encoder = registered_client.connection_pool.get_encoder()\n            script = encoder.encode(script)\n        self.sha = hashlib.sha1(script).hexdigest()\n\n    def __call__(self, keys=[], args=[], client=None):\n        \"Execute the script, passing any required ``args``\"\n        if client is None:\n            client = self.registered_client\n        args = tuple(keys) + tuple(args)\n        # make sure the Redis server knows about the script\n        if isinstance(client, Pipeline):\n            # Make sure the pipeline can register the script before executing.\n            client.scripts.add(self)\n        try:\n            return client.evalsha(self.sha, len(keys), *args)\n        except NoScriptError:\n            # Maybe the client is pointed to a differnet server than the client\n            # that created this instance?\n            # Overwrite the sha just in case there was a discrepancy.\n            self.sha = client.script_load(self.script)\n            return client.evalsha(self.sha, len(keys), *args)\n\n\nclass BitFieldOperation(object):\n    \"\"\"\n    Command builder for BITFIELD commands.\n    \"\"\"\n    def __init__(self, client, key, default_overflow=None):\n        self.client = client\n        self.key = key\n        self._default_overflow = default_overflow\n        self.reset()\n\n    def reset(self):\n        \"\"\"\n        Reset the state of the instance to when it was constructed\n        \"\"\"\n        self.operations = []\n        self._last_overflow = 'WRAP'\n        self.overflow(self._default_overflow or self._last_overflow)\n\n    def overflow(self, overflow):\n        \"\"\"\n        Update the overflow algorithm of successive INCRBY operations\n        :param overflow: Overflow algorithm, one of WRAP, SAT, FAIL. See the\n            Redis docs for descriptions of these algorithmsself.\n        :returns: a :py:class:`BitFieldOperation` instance.\n        \"\"\"\n        overflow = overflow.upper()\n        if overflow != self._last_overflow:\n            self._last_overflow = overflow\n            self.operations.append(('OVERFLOW', overflow))\n        return self\n\n    def incrby(self, fmt, offset, increment, overflow=None):\n        \"\"\"\n        Increment a bitfield by a given amount.\n        :param fmt: format-string for the bitfield being updated, e.g. 'u8'\n            for an unsigned 8-bit integer.\n        :param offset: offset (in number of bits). If prefixed with a\n            '#', this is an offset multiplier, e.g. given the arguments\n            fmt='u8', offset='#2', the offset will be 16.\n        :param int increment: value to increment the bitfield by.\n        :param str overflow: overflow algorithm. Defaults to WRAP, but other\n            acceptable values are SAT and FAIL. See the Redis docs for\n            descriptions of these algorithms.\n        :returns: a :py:class:`BitFieldOperation` instance.\n        \"\"\"\n        if overflow is not None:\n            self.overflow(overflow)\n\n        self.operations.append(('INCRBY', fmt, offset, increment))\n        return self\n\n    def get(self, fmt, offset):\n        \"\"\"\n        Get the value of a given bitfield.\n        :param fmt: format-string for the bitfield being read, e.g. 'u8' for\n            an unsigned 8-bit integer.\n        :param offset: offset (in number of bits). If prefixed with a\n            '#', this is an offset multiplier, e.g. given the arguments\n            fmt='u8', offset='#2', the offset will be 16.\n        :returns: a :py:class:`BitFieldOperation` instance.\n        \"\"\"\n        self.operations.append(('GET', fmt, offset))\n        return self\n\n    def set(self, fmt, offset, value):\n        \"\"\"\n        Set the value of a given bitfield.\n        :param fmt: format-string for the bitfield being read, e.g. 'u8' for\n            an unsigned 8-bit integer.\n        :param offset: offset (in number of bits). If prefixed with a\n            '#', this is an offset multiplier, e.g. given the arguments\n            fmt='u8', offset='#2', the offset will be 16.\n        :param int value: value to set at the given position.\n        :returns: a :py:class:`BitFieldOperation` instance.\n        \"\"\"\n        self.operations.append(('SET', fmt, offset, value))\n        return self\n\n    @property\n    def command(self):\n        cmd = ['BITFIELD', self.key]\n        for ops in self.operations:\n            cmd.extend(ops)\n        return cmd\n\n    def execute(self):\n        \"\"\"\n        Execute the operation(s) in a single BITFIELD command. The return value\n        is a list of values corresponding to each operation. If the client\n        used to create this instance was a pipeline, the list of values\n        will be present within the pipeline's execute.\n        \"\"\"\n        command = self.command\n        self.reset()\n        return self.client.execute_command(*command)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis/connection.py",
    "content": "from __future__ import unicode_literals\nfrom distutils.version import StrictVersion\nfrom itertools import chain\nfrom time import time\nimport errno\nimport io\nimport os\nimport socket\nimport sys\nimport threading\nimport warnings\n\nfrom redis._compat import (xrange, imap, byte_to_chr, unicode, long,\n                           nativestr, basestring, iteritems,\n                           LifoQueue, Empty, Full, urlparse, parse_qs,\n                           recv, recv_into, unquote, BlockingIOError,\n                           sendall, shutdown, ssl_wrap_socket)\nfrom redis.exceptions import (\n    AuthenticationError,\n    BusyLoadingError,\n    ConnectionError,\n    DataError,\n    ExecAbortError,\n    InvalidResponse,\n    NoScriptError,\n    ReadOnlyError,\n    RedisError,\n    ResponseError,\n    TimeoutError,\n)\nfrom redis.utils import HIREDIS_AVAILABLE\n\ntry:\n    import ssl\n    ssl_available = True\nexcept ImportError:\n    ssl_available = False\n\nNONBLOCKING_EXCEPTION_ERROR_NUMBERS = {\n    BlockingIOError: errno.EWOULDBLOCK,\n}\n\nif ssl_available:\n    if hasattr(ssl, 'SSLWantReadError'):\n        NONBLOCKING_EXCEPTION_ERROR_NUMBERS[ssl.SSLWantReadError] = 2\n        NONBLOCKING_EXCEPTION_ERROR_NUMBERS[ssl.SSLWantWriteError] = 2\n    else:\n        NONBLOCKING_EXCEPTION_ERROR_NUMBERS[ssl.SSLError] = 2\n\n# In Python 2.7 a socket.error is raised for a nonblocking read.\n# The _compat module aliases BlockingIOError to socket.error to be\n# Python 2/3 compatible.\n# However this means that all socket.error exceptions need to be handled\n# properly within these exception handlers.\n# We need to make sure socket.error is included in these handlers and\n# provide a dummy error number that will never match a real exception.\nif socket.error not in NONBLOCKING_EXCEPTION_ERROR_NUMBERS:\n    NONBLOCKING_EXCEPTION_ERROR_NUMBERS[socket.error] = -999999\n\nNONBLOCKING_EXCEPTIONS = tuple(NONBLOCKING_EXCEPTION_ERROR_NUMBERS.keys())\n\nif HIREDIS_AVAILABLE:\n    import hiredis\n\n    hiredis_version = StrictVersion(hiredis.__version__)\n    HIREDIS_SUPPORTS_CALLABLE_ERRORS = \\\n        hiredis_version >= StrictVersion('0.1.3')\n    HIREDIS_SUPPORTS_BYTE_BUFFER = \\\n        hiredis_version >= StrictVersion('0.1.4')\n    HIREDIS_SUPPORTS_ENCODING_ERRORS = \\\n        hiredis_version >= StrictVersion('1.0.0')\n\n    if not HIREDIS_SUPPORTS_BYTE_BUFFER:\n        msg = (\"redis-py works best with hiredis >= 0.1.4. You're running \"\n               \"hiredis %s. Please consider upgrading.\" % hiredis.__version__)\n        warnings.warn(msg)\n\n    HIREDIS_USE_BYTE_BUFFER = True\n    # only use byte buffer if hiredis supports it\n    if not HIREDIS_SUPPORTS_BYTE_BUFFER:\n        HIREDIS_USE_BYTE_BUFFER = False\n\nSYM_STAR = b'*'\nSYM_DOLLAR = b'$'\nSYM_CRLF = b'\\r\\n'\nSYM_EMPTY = b''\n\nSERVER_CLOSED_CONNECTION_ERROR = \"Connection closed by server.\"\n\nSENTINEL = object()\n\n\nclass Encoder(object):\n    \"Encode strings to bytes and decode bytes to strings\"\n\n    def __init__(self, encoding, encoding_errors, decode_responses):\n        self.encoding = encoding\n        self.encoding_errors = encoding_errors\n        self.decode_responses = decode_responses\n\n    def encode(self, value):\n        \"Return a bytestring representation of the value\"\n        if isinstance(value, bytes):\n            return value\n        elif isinstance(value, bool):\n            # special case bool since it is a subclass of int\n            raise DataError(\"Invalid input of type: 'bool'. Convert to a \"\n                            \"byte, string or number first.\")\n        elif isinstance(value, float):\n            value = repr(value).encode()\n        elif isinstance(value, (int, long)):\n            # python 2 repr() on longs is '123L', so use str() instead\n            value = str(value).encode()\n        elif not isinstance(value, basestring):\n            # a value we don't know how to deal with. throw an error\n            typename = type(value).__name__\n            raise DataError(\"Invalid input of type: '%s'. Convert to a \"\n                            \"byte, string or number first.\" % typename)\n        if isinstance(value, unicode):\n            value = value.encode(self.encoding, self.encoding_errors)\n        return value\n\n    def decode(self, value, force=False):\n        \"Return a unicode string from the byte representation\"\n        if (self.decode_responses or force) and isinstance(value, bytes):\n            value = value.decode(self.encoding, self.encoding_errors)\n        return value\n\n\nclass BaseParser(object):\n    EXCEPTION_CLASSES = {\n        'ERR': {\n            'max number of clients reached': ConnectionError,\n            'Client sent AUTH, but no password is set': AuthenticationError,\n            'invalid password': AuthenticationError,\n        },\n        'EXECABORT': ExecAbortError,\n        'LOADING': BusyLoadingError,\n        'NOSCRIPT': NoScriptError,\n        'READONLY': ReadOnlyError,\n        'NOAUTH': AuthenticationError,\n    }\n\n    def parse_error(self, response):\n        \"Parse an error response\"\n        error_code = response.split(' ')[0]\n        if error_code in self.EXCEPTION_CLASSES:\n            response = response[len(error_code) + 1:]\n            exception_class = self.EXCEPTION_CLASSES[error_code]\n            if isinstance(exception_class, dict):\n                exception_class = exception_class.get(response, ResponseError)\n            return exception_class(response)\n        return ResponseError(response)\n\n\nclass SocketBuffer(object):\n    def __init__(self, socket, socket_read_size, socket_timeout):\n        self._sock = socket\n        self.socket_read_size = socket_read_size\n        self.socket_timeout = socket_timeout\n        self._buffer = io.BytesIO()\n        # number of bytes written to the buffer from the socket\n        self.bytes_written = 0\n        # number of bytes read from the buffer\n        self.bytes_read = 0\n\n    @property\n    def length(self):\n        return self.bytes_written - self.bytes_read\n\n    def _read_from_socket(self, length=None, timeout=SENTINEL,\n                          raise_on_timeout=True):\n        sock = self._sock\n        socket_read_size = self.socket_read_size\n        buf = self._buffer\n        buf.seek(self.bytes_written)\n        marker = 0\n        custom_timeout = timeout is not SENTINEL\n\n        try:\n            if custom_timeout:\n                sock.settimeout(timeout)\n            while True:\n                data = recv(self._sock, socket_read_size)\n                # an empty string indicates the server shutdown the socket\n                if isinstance(data, bytes) and len(data) == 0:\n                    raise ConnectionError(SERVER_CLOSED_CONNECTION_ERROR)\n                buf.write(data)\n                data_length = len(data)\n                self.bytes_written += data_length\n                marker += data_length\n\n                if length is not None and length > marker:\n                    continue\n                return True\n        except socket.timeout:\n            if raise_on_timeout:\n                raise TimeoutError(\"Timeout reading from socket\")\n            return False\n        except NONBLOCKING_EXCEPTIONS as ex:\n            # if we're in nonblocking mode and the recv raises a\n            # blocking error, simply return False indicating that\n            # there's no data to be read. otherwise raise the\n            # original exception.\n            allowed = NONBLOCKING_EXCEPTION_ERROR_NUMBERS.get(ex.__class__, -1)\n            if not raise_on_timeout and ex.errno == allowed:\n                return False\n            raise ConnectionError(\"Error while reading from socket: %s\" %\n                                  (ex.args,))\n        finally:\n            if custom_timeout:\n                sock.settimeout(self.socket_timeout)\n\n    def can_read(self, timeout):\n        return bool(self.length) or \\\n            self._read_from_socket(timeout=timeout,\n                                   raise_on_timeout=False)\n\n    def read(self, length):\n        length = length + 2  # make sure to read the \\r\\n terminator\n        # make sure we've read enough data from the socket\n        if length > self.length:\n            self._read_from_socket(length - self.length)\n\n        self._buffer.seek(self.bytes_read)\n        data = self._buffer.read(length)\n        self.bytes_read += len(data)\n\n        # purge the buffer when we've consumed it all so it doesn't\n        # grow forever\n        if self.bytes_read == self.bytes_written:\n            self.purge()\n\n        return data[:-2]\n\n    def readline(self):\n        buf = self._buffer\n        buf.seek(self.bytes_read)\n        data = buf.readline()\n        while not data.endswith(SYM_CRLF):\n            # there's more data in the socket that we need\n            self._read_from_socket()\n            buf.seek(self.bytes_read)\n            data = buf.readline()\n\n        self.bytes_read += len(data)\n\n        # purge the buffer when we've consumed it all so it doesn't\n        # grow forever\n        if self.bytes_read == self.bytes_written:\n            self.purge()\n\n        return data[:-2]\n\n    def purge(self):\n        self._buffer.seek(0)\n        self._buffer.truncate()\n        self.bytes_written = 0\n        self.bytes_read = 0\n\n    def close(self):\n        try:\n            self.purge()\n            self._buffer.close()\n        except Exception:\n            # issue #633 suggests the purge/close somehow raised a\n            # BadFileDescriptor error. Perhaps the client ran out of\n            # memory or something else? It's probably OK to ignore\n            # any error being raised from purge/close since we're\n            # removing the reference to the instance below.\n            pass\n        self._buffer = None\n        self._sock = None\n\n\nclass PythonParser(BaseParser):\n    \"Plain Python parsing class\"\n    def __init__(self, socket_read_size):\n        self.socket_read_size = socket_read_size\n        self.encoder = None\n        self._sock = None\n        self._buffer = None\n\n    def __del__(self):\n        try:\n            self.on_disconnect()\n        except Exception:\n            pass\n\n    def on_connect(self, connection):\n        \"Called when the socket connects\"\n        self._sock = connection._sock\n        self._buffer = SocketBuffer(self._sock,\n                                    self.socket_read_size,\n                                    connection.socket_timeout)\n        self.encoder = connection.encoder\n\n    def on_disconnect(self):\n        \"Called when the socket disconnects\"\n        self._sock = None\n        if self._buffer is not None:\n            self._buffer.close()\n            self._buffer = None\n        self.encoder = None\n\n    def can_read(self, timeout):\n        return self._buffer and self._buffer.can_read(timeout)\n\n    def read_response(self):\n        response = self._buffer.readline()\n        if not response:\n            raise ConnectionError(SERVER_CLOSED_CONNECTION_ERROR)\n\n        byte, response = byte_to_chr(response[0]), response[1:]\n\n        if byte not in ('-', '+', ':', '$', '*'):\n            raise InvalidResponse(\"Protocol Error: %s, %s\" %\n                                  (str(byte), str(response)))\n\n        # server returned an error\n        if byte == '-':\n            response = nativestr(response)\n            error = self.parse_error(response)\n            # if the error is a ConnectionError, raise immediately so the user\n            # is notified\n            if isinstance(error, ConnectionError):\n                raise error\n            # otherwise, we're dealing with a ResponseError that might belong\n            # inside a pipeline response. the connection's read_response()\n            # and/or the pipeline's execute() will raise this error if\n            # necessary, so just return the exception instance here.\n            return error\n        # single value\n        elif byte == '+':\n            pass\n        # int value\n        elif byte == ':':\n            response = long(response)\n        # bulk response\n        elif byte == '$':\n            length = int(response)\n            if length == -1:\n                return None\n            response = self._buffer.read(length)\n        # multi-bulk response\n        elif byte == '*':\n            length = int(response)\n            if length == -1:\n                return None\n            response = [self.read_response() for i in xrange(length)]\n        if isinstance(response, bytes):\n            response = self.encoder.decode(response)\n        return response\n\n\nclass HiredisParser(BaseParser):\n    \"Parser class for connections using Hiredis\"\n    def __init__(self, socket_read_size):\n        if not HIREDIS_AVAILABLE:\n            raise RedisError(\"Hiredis is not installed\")\n        self.socket_read_size = socket_read_size\n\n        if HIREDIS_USE_BYTE_BUFFER:\n            self._buffer = bytearray(socket_read_size)\n\n    def __del__(self):\n        try:\n            self.on_disconnect()\n        except Exception:\n            pass\n\n    def on_connect(self, connection):\n        self._sock = connection._sock\n        self._socket_timeout = connection.socket_timeout\n        kwargs = {\n            'protocolError': InvalidResponse,\n            'replyError': self.parse_error,\n        }\n\n        # hiredis < 0.1.3 doesn't support functions that create exceptions\n        if not HIREDIS_SUPPORTS_CALLABLE_ERRORS:\n            kwargs['replyError'] = ResponseError\n\n        if connection.encoder.decode_responses:\n            kwargs['encoding'] = connection.encoder.encoding\n        if HIREDIS_SUPPORTS_ENCODING_ERRORS:\n            kwargs['errors'] = connection.encoder.encoding_errors\n        self._reader = hiredis.Reader(**kwargs)\n        self._next_response = False\n\n    def on_disconnect(self):\n        self._sock = None\n        self._reader = None\n        self._next_response = False\n\n    def can_read(self, timeout):\n        if not self._reader:\n            raise ConnectionError(SERVER_CLOSED_CONNECTION_ERROR)\n\n        if self._next_response is False:\n            self._next_response = self._reader.gets()\n            if self._next_response is False:\n                return self.read_from_socket(timeout=timeout,\n                                             raise_on_timeout=False)\n        return True\n\n    def read_from_socket(self, timeout=SENTINEL, raise_on_timeout=True):\n        sock = self._sock\n        custom_timeout = timeout is not SENTINEL\n        try:\n            if custom_timeout:\n                sock.settimeout(timeout)\n            if HIREDIS_USE_BYTE_BUFFER:\n                bufflen = recv_into(self._sock, self._buffer)\n                if bufflen == 0:\n                    raise ConnectionError(SERVER_CLOSED_CONNECTION_ERROR)\n                self._reader.feed(self._buffer, 0, bufflen)\n            else:\n                buffer = recv(self._sock, self.socket_read_size)\n                # an empty string indicates the server shutdown the socket\n                if not isinstance(buffer, bytes) or len(buffer) == 0:\n                    raise ConnectionError(SERVER_CLOSED_CONNECTION_ERROR)\n                self._reader.feed(buffer)\n            # data was read from the socket and added to the buffer.\n            # return True to indicate that data was read.\n            return True\n        except socket.timeout:\n            if raise_on_timeout:\n                raise TimeoutError(\"Timeout reading from socket\")\n            return False\n        except NONBLOCKING_EXCEPTIONS as ex:\n            # if we're in nonblocking mode and the recv raises a\n            # blocking error, simply return False indicating that\n            # there's no data to be read. otherwise raise the\n            # original exception.\n            allowed = NONBLOCKING_EXCEPTION_ERROR_NUMBERS.get(ex.__class__, -1)\n            if not raise_on_timeout and ex.errno == allowed:\n                return False\n            raise ConnectionError(\"Error while reading from socket: %s\" %\n                                  (ex.args,))\n        finally:\n            if custom_timeout:\n                sock.settimeout(self._socket_timeout)\n\n    def read_response(self):\n        if not self._reader:\n            raise ConnectionError(SERVER_CLOSED_CONNECTION_ERROR)\n\n        # _next_response might be cached from a can_read() call\n        if self._next_response is not False:\n            response = self._next_response\n            self._next_response = False\n            return response\n\n        response = self._reader.gets()\n        while response is False:\n            self.read_from_socket()\n            response = self._reader.gets()\n        # if an older version of hiredis is installed, we need to attempt\n        # to convert ResponseErrors to their appropriate types.\n        if not HIREDIS_SUPPORTS_CALLABLE_ERRORS:\n            if isinstance(response, ResponseError):\n                response = self.parse_error(response.args[0])\n            elif isinstance(response, list) and response and \\\n                    isinstance(response[0], ResponseError):\n                response[0] = self.parse_error(response[0].args[0])\n        # if the response is a ConnectionError or the response is a list and\n        # the first item is a ConnectionError, raise it as something bad\n        # happened\n        if isinstance(response, ConnectionError):\n            raise response\n        elif isinstance(response, list) and response and \\\n                isinstance(response[0], ConnectionError):\n            raise response[0]\n        return response\n\n\nif HIREDIS_AVAILABLE:\n    DefaultParser = HiredisParser\nelse:\n    DefaultParser = PythonParser\n\n\nclass Connection(object):\n    \"Manages TCP communication to and from a Redis server\"\n    description_format = \"Connection<host=%(host)s,port=%(port)s,db=%(db)s>\"\n\n    def __init__(self, host='localhost', port=6379, db=0, password=None,\n                 socket_timeout=None, socket_connect_timeout=None,\n                 socket_keepalive=False, socket_keepalive_options=None,\n                 socket_type=0, retry_on_timeout=False, encoding='utf-8',\n                 encoding_errors='strict', decode_responses=False,\n                 parser_class=DefaultParser, socket_read_size=65536,\n                 health_check_interval=0):\n        self.pid = os.getpid()\n        self.host = host\n        self.port = int(port)\n        self.db = db\n        self.password = password\n        self.socket_timeout = socket_timeout\n        self.socket_connect_timeout = socket_connect_timeout or socket_timeout\n        self.socket_keepalive = socket_keepalive\n        self.socket_keepalive_options = socket_keepalive_options or {}\n        self.socket_type = socket_type\n        self.retry_on_timeout = retry_on_timeout\n        self.health_check_interval = health_check_interval\n        self.next_health_check = 0\n        self.encoder = Encoder(encoding, encoding_errors, decode_responses)\n        self._sock = None\n        self._parser = parser_class(socket_read_size=socket_read_size)\n        self._description_args = {\n            'host': self.host,\n            'port': self.port,\n            'db': self.db,\n        }\n        self._connect_callbacks = []\n        self._buffer_cutoff = 6000\n\n    def __repr__(self):\n        return self.description_format % self._description_args\n\n    def __del__(self):\n        try:\n            self.disconnect()\n        except Exception:\n            pass\n\n    def register_connect_callback(self, callback):\n        self._connect_callbacks.append(callback)\n\n    def clear_connect_callbacks(self):\n        self._connect_callbacks = []\n\n    def connect(self):\n        \"Connects to the Redis server if not already connected\"\n        if self._sock:\n            return\n        try:\n            sock = self._connect()\n        except socket.timeout:\n            raise TimeoutError(\"Timeout connecting to server\")\n        except socket.error:\n            e = sys.exc_info()[1]\n            raise ConnectionError(self._error_message(e))\n\n        self._sock = sock\n        try:\n            self.on_connect()\n        except RedisError:\n            # clean up after any error in on_connect\n            self.disconnect()\n            raise\n\n        # run any user callbacks. right now the only internal callback\n        # is for pubsub channel/pattern resubscription\n        for callback in self._connect_callbacks:\n            callback(self)\n\n    def _connect(self):\n        \"Create a TCP socket connection\"\n        # we want to mimic what socket.create_connection does to support\n        # ipv4/ipv6, but we want to set options prior to calling\n        # socket.connect()\n        err = None\n        for res in socket.getaddrinfo(self.host, self.port, self.socket_type,\n                                      socket.SOCK_STREAM):\n            family, socktype, proto, canonname, socket_address = res\n            sock = None\n            try:\n                sock = socket.socket(family, socktype, proto)\n                # TCP_NODELAY\n                sock.setsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY, 1)\n\n                # TCP_KEEPALIVE\n                if self.socket_keepalive:\n                    sock.setsockopt(socket.SOL_SOCKET, socket.SO_KEEPALIVE, 1)\n                    for k, v in iteritems(self.socket_keepalive_options):\n                        sock.setsockopt(socket.IPPROTO_TCP, k, v)\n\n                # set the socket_connect_timeout before we connect\n                sock.settimeout(self.socket_connect_timeout)\n\n                # connect\n                sock.connect(socket_address)\n\n                # set the socket_timeout now that we're connected\n                sock.settimeout(self.socket_timeout)\n                return sock\n\n            except socket.error as _:\n                err = _\n                if sock is not None:\n                    sock.close()\n\n        if err is not None:\n            raise err\n        raise socket.error(\"socket.getaddrinfo returned an empty list\")\n\n    def _error_message(self, exception):\n        # args for socket.error can either be (errno, \"message\")\n        # or just \"message\"\n        if len(exception.args) == 1:\n            return \"Error connecting to %s:%s. %s.\" % \\\n                (self.host, self.port, exception.args[0])\n        else:\n            return \"Error %s connecting to %s:%s. %s.\" % \\\n                (exception.args[0], self.host, self.port, exception.args[1])\n\n    def on_connect(self):\n        \"Initialize the connection, authenticate and select a database\"\n        self._parser.on_connect(self)\n\n        # if a password is specified, authenticate\n        if self.password:\n            # avoid checking health here -- PING will fail if we try\n            # to check the health prior to the AUTH\n            self.send_command('AUTH', self.password, check_health=False)\n            if nativestr(self.read_response()) != 'OK':\n                raise AuthenticationError('Invalid Password')\n\n        # if a database is specified, switch to it\n        if self.db:\n            self.send_command('SELECT', self.db)\n            if nativestr(self.read_response()) != 'OK':\n                raise ConnectionError('Invalid Database')\n\n    def disconnect(self):\n        \"Disconnects from the Redis server\"\n        self._parser.on_disconnect()\n        if self._sock is None:\n            return\n        try:\n            if os.getpid() == self.pid:\n                shutdown(self._sock, socket.SHUT_RDWR)\n            self._sock.close()\n        except socket.error:\n            pass\n        self._sock = None\n\n    def check_health(self):\n        \"Check the health of the connection with a PING/PONG\"\n        if self.health_check_interval and time() > self.next_health_check:\n            try:\n                self.send_command('PING', check_health=False)\n                if nativestr(self.read_response()) != 'PONG':\n                    raise ConnectionError(\n                        'Bad response from PING health check')\n            except (ConnectionError, TimeoutError) as ex:\n                self.disconnect()\n                self.send_command('PING', check_health=False)\n                if nativestr(self.read_response()) != 'PONG':\n                    raise ConnectionError(\n                        'Bad response from PING health check')\n\n    def send_packed_command(self, command, check_health=True):\n        \"Send an already packed command to the Redis server\"\n        if not self._sock:\n            self.connect()\n        # guard against health check recurrsion\n        if check_health:\n            self.check_health()\n        try:\n            if isinstance(command, str):\n                command = [command]\n            for item in command:\n                sendall(self._sock, item)\n        except socket.timeout:\n            self.disconnect()\n            raise TimeoutError(\"Timeout writing to socket\")\n        except socket.error:\n            e = sys.exc_info()[1]\n            self.disconnect()\n            if len(e.args) == 1:\n                errno, errmsg = 'UNKNOWN', e.args[0]\n            else:\n                errno = e.args[0]\n                errmsg = e.args[1]\n            raise ConnectionError(\"Error %s while writing to socket. %s.\" %\n                                  (errno, errmsg))\n        except:  # noqa: E722\n            self.disconnect()\n            raise\n\n    def send_command(self, *args, **kwargs):\n        \"Pack and send a command to the Redis server\"\n        self.send_packed_command(self.pack_command(*args),\n                                 check_health=kwargs.get('check_health', True))\n\n    def can_read(self, timeout=0):\n        \"Poll the socket to see if there's data that can be read.\"\n        sock = self._sock\n        if not sock:\n            self.connect()\n            sock = self._sock\n        return self._parser.can_read(timeout)\n\n    def read_response(self):\n        \"Read the response from a previously sent command\"\n        try:\n            response = self._parser.read_response()\n        except socket.timeout:\n            self.disconnect()\n            raise TimeoutError(\"Timeout reading from %s:%s\" %\n                               (self.host, self.port))\n        except socket.error:\n            self.disconnect()\n            e = sys.exc_info()[1]\n            raise ConnectionError(\"Error while reading from %s:%s : %s\" %\n                                  (self.host, self.port, e.args))\n        except:  # noqa: E722\n            self.disconnect()\n            raise\n\n        if self.health_check_interval:\n            self.next_health_check = time() + self.health_check_interval\n\n        if isinstance(response, ResponseError):\n            raise response\n        return response\n\n    def pack_command(self, *args):\n        \"Pack a series of arguments into the Redis protocol\"\n        output = []\n        # the client might have included 1 or more literal arguments in\n        # the command name, e.g., 'CONFIG GET'. The Redis server expects these\n        # arguments to be sent separately, so split the first argument\n        # manually. These arguments should be bytestrings so that they are\n        # not encoded.\n        if isinstance(args[0], unicode):\n            args = tuple(args[0].encode().split()) + args[1:]\n        elif b' ' in args[0]:\n            args = tuple(args[0].split()) + args[1:]\n\n        buff = SYM_EMPTY.join((SYM_STAR, str(len(args)).encode(), SYM_CRLF))\n\n        buffer_cutoff = self._buffer_cutoff\n        for arg in imap(self.encoder.encode, args):\n            # to avoid large string mallocs, chunk the command into the\n            # output list if we're sending large values\n            if len(buff) > buffer_cutoff or len(arg) > buffer_cutoff:\n                buff = SYM_EMPTY.join(\n                    (buff, SYM_DOLLAR, str(len(arg)).encode(), SYM_CRLF))\n                output.append(buff)\n                output.append(arg)\n                buff = SYM_CRLF\n            else:\n                buff = SYM_EMPTY.join(\n                    (buff, SYM_DOLLAR, str(len(arg)).encode(),\n                     SYM_CRLF, arg, SYM_CRLF))\n        output.append(buff)\n        return output\n\n    def pack_commands(self, commands):\n        \"Pack multiple commands into the Redis protocol\"\n        output = []\n        pieces = []\n        buffer_length = 0\n        buffer_cutoff = self._buffer_cutoff\n\n        for cmd in commands:\n            for chunk in self.pack_command(*cmd):\n                chunklen = len(chunk)\n                if buffer_length > buffer_cutoff or chunklen > buffer_cutoff:\n                    output.append(SYM_EMPTY.join(pieces))\n                    buffer_length = 0\n                    pieces = []\n\n                if chunklen > self._buffer_cutoff:\n                    output.append(chunk)\n                else:\n                    pieces.append(chunk)\n                    buffer_length += chunklen\n\n        if pieces:\n            output.append(SYM_EMPTY.join(pieces))\n        return output\n\n\nclass SSLConnection(Connection):\n    description_format = \"SSLConnection<host=%(host)s,port=%(port)s,db=%(db)s>\"\n\n    def __init__(self, ssl_keyfile=None, ssl_certfile=None,\n                 ssl_cert_reqs='required', ssl_ca_certs=None, **kwargs):\n        if not ssl_available:\n            raise RedisError(\"Python wasn't built with SSL support\")\n\n        super(SSLConnection, self).__init__(**kwargs)\n\n        self.keyfile = ssl_keyfile\n        self.certfile = ssl_certfile\n        if ssl_cert_reqs is None:\n            ssl_cert_reqs = ssl.CERT_NONE\n        elif isinstance(ssl_cert_reqs, basestring):\n            CERT_REQS = {\n                'none': ssl.CERT_NONE,\n                'optional': ssl.CERT_OPTIONAL,\n                'required': ssl.CERT_REQUIRED\n            }\n            if ssl_cert_reqs not in CERT_REQS:\n                raise RedisError(\n                    \"Invalid SSL Certificate Requirements Flag: %s\" %\n                    ssl_cert_reqs)\n            ssl_cert_reqs = CERT_REQS[ssl_cert_reqs]\n        self.cert_reqs = ssl_cert_reqs\n        self.ca_certs = ssl_ca_certs\n\n    def _connect(self):\n        \"Wrap the socket with SSL support\"\n        sock = super(SSLConnection, self)._connect()\n        if hasattr(ssl, \"create_default_context\"):\n            context = ssl.create_default_context()\n            context.check_hostname = False\n            context.verify_mode = self.cert_reqs\n            if self.certfile and self.keyfile:\n                context.load_cert_chain(certfile=self.certfile,\n                                        keyfile=self.keyfile)\n            if self.ca_certs:\n                context.load_verify_locations(self.ca_certs)\n            sock = ssl_wrap_socket(context, sock, server_hostname=self.host)\n        else:\n            # In case this code runs in a version which is older than 2.7.9,\n            # we want to fall back to old code\n            sock = ssl_wrap_socket(ssl,\n                                   sock,\n                                   cert_reqs=self.cert_reqs,\n                                   keyfile=self.keyfile,\n                                   certfile=self.certfile,\n                                   ca_certs=self.ca_certs)\n        return sock\n\n\nclass UnixDomainSocketConnection(Connection):\n    description_format = \"UnixDomainSocketConnection<path=%(path)s,db=%(db)s>\"\n\n    def __init__(self, path='', db=0, password=None,\n                 socket_timeout=None, encoding='utf-8',\n                 encoding_errors='strict', decode_responses=False,\n                 retry_on_timeout=False,\n                 parser_class=DefaultParser, socket_read_size=65536,\n                 health_check_interval=0):\n        self.pid = os.getpid()\n        self.path = path\n        self.db = db\n        self.password = password\n        self.socket_timeout = socket_timeout\n        self.retry_on_timeout = retry_on_timeout\n        self.health_check_interval = health_check_interval\n        self.next_health_check = 0\n        self.encoder = Encoder(encoding, encoding_errors, decode_responses)\n        self._sock = None\n        self._parser = parser_class(socket_read_size=socket_read_size)\n        self._description_args = {\n            'path': self.path,\n            'db': self.db,\n        }\n        self._connect_callbacks = []\n        self._buffer_cutoff = 6000\n\n    def _connect(self):\n        \"Create a Unix domain socket connection\"\n        sock = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)\n        sock.settimeout(self.socket_timeout)\n        sock.connect(self.path)\n        return sock\n\n    def _error_message(self, exception):\n        # args for socket.error can either be (errno, \"message\")\n        # or just \"message\"\n        if len(exception.args) == 1:\n            return \"Error connecting to unix socket: %s. %s.\" % \\\n                (self.path, exception.args[0])\n        else:\n            return \"Error %s connecting to unix socket: %s. %s.\" % \\\n                (exception.args[0], self.path, exception.args[1])\n\n\nFALSE_STRINGS = ('0', 'F', 'FALSE', 'N', 'NO')\n\n\ndef to_bool(value):\n    if value is None or value == '':\n        return None\n    if isinstance(value, basestring) and value.upper() in FALSE_STRINGS:\n        return False\n    return bool(value)\n\n\nURL_QUERY_ARGUMENT_PARSERS = {\n    'socket_timeout': float,\n    'socket_connect_timeout': float,\n    'socket_keepalive': to_bool,\n    'retry_on_timeout': to_bool,\n    'max_connections': int,\n    'health_check_interval': int,\n}\n\n\nclass ConnectionPool(object):\n    \"Generic connection pool\"\n    @classmethod\n    def from_url(cls, url, db=None, decode_components=False, **kwargs):\n        \"\"\"\n        Return a connection pool configured from the given URL.\n\n        For example::\n\n            redis://[:password]@localhost:6379/0\n            rediss://[:password]@localhost:6379/0\n            unix://[:password]@/path/to/socket.sock?db=0\n\n        Three URL schemes are supported:\n\n        - ```redis://``\n          <https://www.iana.org/assignments/uri-schemes/prov/redis>`_ creates a\n          normal TCP socket connection\n        - ```rediss://``\n          <https://www.iana.org/assignments/uri-schemes/prov/rediss>`_ creates\n          a SSL wrapped TCP socket connection\n        - ``unix://`` creates a Unix Domain Socket connection\n\n        There are several ways to specify a database number. The parse function\n        will return the first specified option:\n            1. A ``db`` querystring option, e.g. redis://localhost?db=0\n            2. If using the redis:// scheme, the path argument of the url, e.g.\n               redis://localhost/0\n            3. The ``db`` argument to this function.\n\n        If none of these options are specified, db=0 is used.\n\n        The ``decode_components`` argument allows this function to work with\n        percent-encoded URLs. If this argument is set to ``True`` all ``%xx``\n        escapes will be replaced by their single-character equivalents after\n        the URL has been parsed. This only applies to the ``hostname``,\n        ``path``, and ``password`` components.\n\n        Any additional querystring arguments and keyword arguments will be\n        passed along to the ConnectionPool class's initializer. The querystring\n        arguments ``socket_connect_timeout`` and ``socket_timeout`` if supplied\n        are parsed as float values. The arguments ``socket_keepalive`` and\n        ``retry_on_timeout`` are parsed to boolean values that accept\n        True/False, Yes/No values to indicate state. Invalid types cause a\n        ``UserWarning`` to be raised. In the case of conflicting arguments,\n        querystring arguments always win.\n\n        \"\"\"\n        url = urlparse(url)\n        url_options = {}\n\n        for name, value in iteritems(parse_qs(url.query)):\n            if value and len(value) > 0:\n                parser = URL_QUERY_ARGUMENT_PARSERS.get(name)\n                if parser:\n                    try:\n                        url_options[name] = parser(value[0])\n                    except (TypeError, ValueError):\n                        warnings.warn(UserWarning(\n                            \"Invalid value for `%s` in connection URL.\" % name\n                        ))\n                else:\n                    url_options[name] = value[0]\n\n        if decode_components:\n            password = unquote(url.password) if url.password else None\n            path = unquote(url.path) if url.path else None\n            hostname = unquote(url.hostname) if url.hostname else None\n        else:\n            password = url.password\n            path = url.path\n            hostname = url.hostname\n\n        # We only support redis://, rediss:// and unix:// schemes.\n        if url.scheme == 'unix':\n            url_options.update({\n                'password': password,\n                'path': path,\n                'connection_class': UnixDomainSocketConnection,\n            })\n\n        elif url.scheme in ('redis', 'rediss'):\n            url_options.update({\n                'host': hostname,\n                'port': int(url.port or 6379),\n                'password': password,\n            })\n\n            # If there's a path argument, use it as the db argument if a\n            # querystring value wasn't specified\n            if 'db' not in url_options and path:\n                try:\n                    url_options['db'] = int(path.replace('/', ''))\n                except (AttributeError, ValueError):\n                    pass\n\n            if url.scheme == 'rediss':\n                url_options['connection_class'] = SSLConnection\n        else:\n            valid_schemes = ', '.join(('redis://', 'rediss://', 'unix://'))\n            raise ValueError('Redis URL must specify one of the following'\n                             'schemes (%s)' % valid_schemes)\n\n        # last shot at the db value\n        url_options['db'] = int(url_options.get('db', db or 0))\n\n        # update the arguments from the URL values\n        kwargs.update(url_options)\n\n        # backwards compatability\n        if 'charset' in kwargs:\n            warnings.warn(DeprecationWarning(\n                '\"charset\" is deprecated. Use \"encoding\" instead'))\n            kwargs['encoding'] = kwargs.pop('charset')\n        if 'errors' in kwargs:\n            warnings.warn(DeprecationWarning(\n                '\"errors\" is deprecated. Use \"encoding_errors\" instead'))\n            kwargs['encoding_errors'] = kwargs.pop('errors')\n\n        return cls(**kwargs)\n\n    def __init__(self, connection_class=Connection, max_connections=None,\n                 **connection_kwargs):\n        \"\"\"\n        Create a connection pool. If max_connections is set, then this\n        object raises redis.ConnectionError when the pool's limit is reached.\n\n        By default, TCP connections are created unless connection_class is\n        specified. Use redis.UnixDomainSocketConnection for unix sockets.\n\n        Any additional keyword arguments are passed to the constructor of\n        connection_class.\n        \"\"\"\n        max_connections = max_connections or 2 ** 31\n        if not isinstance(max_connections, (int, long)) or max_connections < 0:\n            raise ValueError('\"max_connections\" must be a positive integer')\n\n        self.connection_class = connection_class\n        self.connection_kwargs = connection_kwargs\n        self.max_connections = max_connections\n\n        self.reset()\n\n    def __repr__(self):\n        return \"%s<%s>\" % (\n            type(self).__name__,\n            repr(self.connection_class(**self.connection_kwargs)),\n        )\n\n    def reset(self):\n        self.pid = os.getpid()\n        self._created_connections = 0\n        self._available_connections = []\n        self._in_use_connections = set()\n        self._check_lock = threading.Lock()\n\n    def _checkpid(self):\n        if self.pid != os.getpid():\n            with self._check_lock:\n                if self.pid == os.getpid():\n                    # another thread already did the work while we waited\n                    # on the lock.\n                    return\n                self.reset()\n\n    def get_connection(self, command_name, *keys, **options):\n        \"Get a connection from the pool\"\n        self._checkpid()\n        try:\n            connection = self._available_connections.pop()\n        except IndexError:\n            connection = self.make_connection()\n        self._in_use_connections.add(connection)\n        try:\n            # ensure this connection is connected to Redis\n            connection.connect()\n            # connections that the pool provides should be ready to send\n            # a command. if not, the connection was either returned to the\n            # pool before all data has been read or the socket has been\n            # closed. either way, reconnect and verify everything is good.\n            try:\n                if connection.can_read():\n                    raise ConnectionError('Connection has data')\n            except ConnectionError:\n                connection.disconnect()\n                connection.connect()\n                if connection.can_read():\n                    raise ConnectionError('Connection not ready')\n        except:  # noqa: E722\n            # release the connection back to the pool so that we don't leak it\n            self.release(connection)\n            raise\n\n        return connection\n\n    def get_encoder(self):\n        \"Return an encoder based on encoding settings\"\n        kwargs = self.connection_kwargs\n        return Encoder(\n            encoding=kwargs.get('encoding', 'utf-8'),\n            encoding_errors=kwargs.get('encoding_errors', 'strict'),\n            decode_responses=kwargs.get('decode_responses', False)\n        )\n\n    def make_connection(self):\n        \"Create a new connection\"\n        if self._created_connections >= self.max_connections:\n            raise ConnectionError(\"Too many connections\")\n        self._created_connections += 1\n        return self.connection_class(**self.connection_kwargs)\n\n    def release(self, connection):\n        \"Releases the connection back to the pool\"\n        self._checkpid()\n        if connection.pid != self.pid:\n            return\n        self._in_use_connections.remove(connection)\n        self._available_connections.append(connection)\n\n    def disconnect(self):\n        \"Disconnects all connections in the pool\"\n        self._checkpid()\n        all_conns = chain(self._available_connections,\n                          self._in_use_connections)\n        for connection in all_conns:\n            connection.disconnect()\n\n\nclass BlockingConnectionPool(ConnectionPool):\n    \"\"\"\n    Thread-safe blocking connection pool::\n\n        >>> from redis.client import Redis\n        >>> client = Redis(connection_pool=BlockingConnectionPool())\n\n    It performs the same function as the default\n    ``:py:class: ~redis.connection.ConnectionPool`` implementation, in that,\n    it maintains a pool of reusable connections that can be shared by\n    multiple redis clients (safely across threads if required).\n\n    The difference is that, in the event that a client tries to get a\n    connection from the pool when all of connections are in use, rather than\n    raising a ``:py:class: ~redis.exceptions.ConnectionError`` (as the default\n    ``:py:class: ~redis.connection.ConnectionPool`` implementation does), it\n    makes the client wait (\"blocks\") for a specified number of seconds until\n    a connection becomes available.\n\n    Use ``max_connections`` to increase / decrease the pool size::\n\n        >>> pool = BlockingConnectionPool(max_connections=10)\n\n    Use ``timeout`` to tell it either how many seconds to wait for a connection\n    to become available, or to block forever:\n\n        # Block forever.\n        >>> pool = BlockingConnectionPool(timeout=None)\n\n        # Raise a ``ConnectionError`` after five seconds if a connection is\n        # not available.\n        >>> pool = BlockingConnectionPool(timeout=5)\n    \"\"\"\n    def __init__(self, max_connections=50, timeout=20,\n                 connection_class=Connection, queue_class=LifoQueue,\n                 **connection_kwargs):\n\n        self.queue_class = queue_class\n        self.timeout = timeout\n        super(BlockingConnectionPool, self).__init__(\n            connection_class=connection_class,\n            max_connections=max_connections,\n            **connection_kwargs)\n\n    def reset(self):\n        self.pid = os.getpid()\n        self._check_lock = threading.Lock()\n\n        # Create and fill up a thread safe queue with ``None`` values.\n        self.pool = self.queue_class(self.max_connections)\n        while True:\n            try:\n                self.pool.put_nowait(None)\n            except Full:\n                break\n\n        # Keep a list of actual connection instances so that we can\n        # disconnect them later.\n        self._connections = []\n\n    def make_connection(self):\n        \"Make a fresh connection.\"\n        connection = self.connection_class(**self.connection_kwargs)\n        self._connections.append(connection)\n        return connection\n\n    def get_connection(self, command_name, *keys, **options):\n        \"\"\"\n        Get a connection, blocking for ``self.timeout`` until a connection\n        is available from the pool.\n\n        If the connection returned is ``None`` then creates a new connection.\n        Because we use a last-in first-out queue, the existing connections\n        (having been returned to the pool after the initial ``None`` values\n        were added) will be returned before ``None`` values. This means we only\n        create new connections when we need to, i.e.: the actual number of\n        connections will only increase in response to demand.\n        \"\"\"\n        # Make sure we haven't changed process.\n        self._checkpid()\n\n        # Try and get a connection from the pool. If one isn't available within\n        # self.timeout then raise a ``ConnectionError``.\n        connection = None\n        try:\n            connection = self.pool.get(block=True, timeout=self.timeout)\n        except Empty:\n            # Note that this is not caught by the redis client and will be\n            # raised unless handled by application code. If you want never to\n            raise ConnectionError(\"No connection available.\")\n\n        # If the ``connection`` is actually ``None`` then that's a cue to make\n        # a new connection to add to the pool.\n        if connection is None:\n            connection = self.make_connection()\n\n        try:\n            # ensure this connection is connected to Redis\n            connection.connect()\n            # connections that the pool provides should be ready to send\n            # a command. if not, the connection was either returned to the\n            # pool before all data has been read or the socket has been\n            # closed. either way, reconnect and verify everything is good.\n            try:\n                if connection.can_read():\n                    raise ConnectionError('Connection has data')\n            except ConnectionError:\n                connection.disconnect()\n                connection.connect()\n                if connection.can_read():\n                    raise ConnectionError('Connection not ready')\n        except:  # noqa: E722\n            # release the connection back to the pool so that we don't leak it\n            self.release(connection)\n            raise\n\n        return connection\n\n    def release(self, connection):\n        \"Releases the connection back to the pool.\"\n        # Make sure we haven't changed process.\n        self._checkpid()\n        if connection.pid != self.pid:\n            return\n\n        # Put the connection back into the pool.\n        try:\n            self.pool.put_nowait(connection)\n        except Full:\n            # perhaps the pool has been reset() after a fork? regardless,\n            # we don't want this connection\n            pass\n\n    def disconnect(self):\n        \"Disconnects all connections in the pool.\"\n        self._checkpid()\n        for connection in self._connections:\n            connection.disconnect()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis/exceptions.py",
    "content": "\"Core exceptions raised by the Redis client\"\n\n\nclass RedisError(Exception):\n    pass\n\n\nclass ConnectionError(RedisError):\n    pass\n\n\nclass TimeoutError(RedisError):\n    pass\n\n\nclass AuthenticationError(ConnectionError):\n    pass\n\n\nclass BusyLoadingError(ConnectionError):\n    pass\n\n\nclass InvalidResponse(RedisError):\n    pass\n\n\nclass ResponseError(RedisError):\n    pass\n\n\nclass DataError(RedisError):\n    pass\n\n\nclass PubSubError(RedisError):\n    pass\n\n\nclass WatchError(RedisError):\n    pass\n\n\nclass NoScriptError(ResponseError):\n    pass\n\n\nclass ExecAbortError(ResponseError):\n    pass\n\n\nclass ReadOnlyError(ResponseError):\n    pass\n\n\nclass LockError(RedisError, ValueError):\n    \"Errors acquiring or releasing a lock\"\n    # NOTE: For backwards compatability, this class derives from ValueError.\n    # This was originally chosen to behave like threading.Lock.\n    pass\n\n\nclass LockNotOwnedError(LockError):\n    \"Error trying to extend or release a lock that is (no longer) owned\"\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis/lock.py",
    "content": "import threading\nimport time as mod_time\nimport uuid\nfrom redis.exceptions import LockError, LockNotOwnedError\nfrom redis.utils import dummy\n\n\nclass Lock(object):\n    \"\"\"\n    A shared, distributed Lock. Using Redis for locking allows the Lock\n    to be shared across processes and/or machines.\n\n    It's left to the user to resolve deadlock issues and make sure\n    multiple clients play nicely together.\n    \"\"\"\n\n    lua_release = None\n    lua_extend = None\n    lua_reacquire = None\n\n    # KEYS[1] - lock name\n    # ARGS[1] - token\n    # return 1 if the lock was released, otherwise 0\n    LUA_RELEASE_SCRIPT = \"\"\"\n        local token = redis.call('get', KEYS[1])\n        if not token or token ~= ARGV[1] then\n            return 0\n        end\n        redis.call('del', KEYS[1])\n        return 1\n    \"\"\"\n\n    # KEYS[1] - lock name\n    # ARGS[1] - token\n    # ARGS[2] - additional milliseconds\n    # return 1 if the locks time was extended, otherwise 0\n    LUA_EXTEND_SCRIPT = \"\"\"\n        local token = redis.call('get', KEYS[1])\n        if not token or token ~= ARGV[1] then\n            return 0\n        end\n        local expiration = redis.call('pttl', KEYS[1])\n        if not expiration then\n            expiration = 0\n        end\n        if expiration < 0 then\n            return 0\n        end\n        redis.call('pexpire', KEYS[1], expiration + ARGV[2])\n        return 1\n    \"\"\"\n\n    # KEYS[1] - lock name\n    # ARGS[1] - token\n    # ARGS[2] - milliseconds\n    # return 1 if the locks time was reacquired, otherwise 0\n    LUA_REACQUIRE_SCRIPT = \"\"\"\n        local token = redis.call('get', KEYS[1])\n        if not token or token ~= ARGV[1] then\n            return 0\n        end\n        redis.call('pexpire', KEYS[1], ARGV[2])\n        return 1\n    \"\"\"\n\n    def __init__(self, redis, name, timeout=None, sleep=0.1,\n                 blocking=True, blocking_timeout=None, thread_local=True):\n        \"\"\"\n        Create a new Lock instance named ``name`` using the Redis client\n        supplied by ``redis``.\n\n        ``timeout`` indicates a maximum life for the lock.\n        By default, it will remain locked until release() is called.\n        ``timeout`` can be specified as a float or integer, both representing\n        the number of seconds to wait.\n\n        ``sleep`` indicates the amount of time to sleep per loop iteration\n        when the lock is in blocking mode and another client is currently\n        holding the lock.\n\n        ``blocking`` indicates whether calling ``acquire`` should block until\n        the lock has been acquired or to fail immediately, causing ``acquire``\n        to return False and the lock not being acquired. Defaults to True.\n        Note this value can be overridden by passing a ``blocking``\n        argument to ``acquire``.\n\n        ``blocking_timeout`` indicates the maximum amount of time in seconds to\n        spend trying to acquire the lock. A value of ``None`` indicates\n        continue trying forever. ``blocking_timeout`` can be specified as a\n        float or integer, both representing the number of seconds to wait.\n\n        ``thread_local`` indicates whether the lock token is placed in\n        thread-local storage. By default, the token is placed in thread local\n        storage so that a thread only sees its token, not a token set by\n        another thread. Consider the following timeline:\n\n            time: 0, thread-1 acquires `my-lock`, with a timeout of 5 seconds.\n                     thread-1 sets the token to \"abc\"\n            time: 1, thread-2 blocks trying to acquire `my-lock` using the\n                     Lock instance.\n            time: 5, thread-1 has not yet completed. redis expires the lock\n                     key.\n            time: 5, thread-2 acquired `my-lock` now that it's available.\n                     thread-2 sets the token to \"xyz\"\n            time: 6, thread-1 finishes its work and calls release(). if the\n                     token is *not* stored in thread local storage, then\n                     thread-1 would see the token value as \"xyz\" and would be\n                     able to successfully release the thread-2's lock.\n\n        In some use cases it's necessary to disable thread local storage. For\n        example, if you have code where one thread acquires a lock and passes\n        that lock instance to a worker thread to release later. If thread\n        local storage isn't disabled in this case, the worker thread won't see\n        the token set by the thread that acquired the lock. Our assumption\n        is that these cases aren't common and as such default to using\n        thread local storage.\n        \"\"\"\n        self.redis = redis\n        self.name = name\n        self.timeout = timeout\n        self.sleep = sleep\n        self.blocking = blocking\n        self.blocking_timeout = blocking_timeout\n        self.thread_local = bool(thread_local)\n        self.local = threading.local() if self.thread_local else dummy()\n        self.local.token = None\n        if self.timeout and self.sleep > self.timeout:\n            raise LockError(\"'sleep' must be less than 'timeout'\")\n        self.register_scripts()\n\n    def register_scripts(self):\n        cls = self.__class__\n        client = self.redis\n        if cls.lua_release is None:\n            cls.lua_release = client.register_script(cls.LUA_RELEASE_SCRIPT)\n        if cls.lua_extend is None:\n            cls.lua_extend = client.register_script(cls.LUA_EXTEND_SCRIPT)\n        if cls.lua_reacquire is None:\n            cls.lua_reacquire = \\\n                client.register_script(cls.LUA_REACQUIRE_SCRIPT)\n\n    def __enter__(self):\n        # force blocking, as otherwise the user would have to check whether\n        # the lock was actually acquired or not.\n        if self.acquire(blocking=True):\n            return self\n        raise LockError(\"Unable to acquire lock within the time specified\")\n\n    def __exit__(self, exc_type, exc_value, traceback):\n        self.release()\n\n    def acquire(self, blocking=None, blocking_timeout=None, token=None):\n        \"\"\"\n        Use Redis to hold a shared, distributed lock named ``name``.\n        Returns True once the lock is acquired.\n\n        If ``blocking`` is False, always return immediately. If the lock\n        was acquired, return True, otherwise return False.\n\n        ``blocking_timeout`` specifies the maximum number of seconds to\n        wait trying to acquire the lock.\n\n        ``token`` specifies the token value to be used. If provided, token\n        must be a bytes object or a string that can be encoded to a bytes\n        object with the default encoding. If a token isn't specified, a UUID\n        will be generated.\n        \"\"\"\n        sleep = self.sleep\n        if token is None:\n            token = uuid.uuid1().hex.encode()\n        else:\n            encoder = self.redis.connection_pool.get_encoder()\n            token = encoder.encode(token)\n        if blocking is None:\n            blocking = self.blocking\n        if blocking_timeout is None:\n            blocking_timeout = self.blocking_timeout\n        stop_trying_at = None\n        if blocking_timeout is not None:\n            stop_trying_at = mod_time.time() + blocking_timeout\n        while True:\n            if self.do_acquire(token):\n                self.local.token = token\n                return True\n            if not blocking:\n                return False\n            if stop_trying_at is not None and mod_time.time() > stop_trying_at:\n                return False\n            mod_time.sleep(sleep)\n\n    def do_acquire(self, token):\n        if self.timeout:\n            # convert to milliseconds\n            timeout = int(self.timeout * 1000)\n        else:\n            timeout = None\n        if self.redis.set(self.name, token, nx=True, px=timeout):\n            return True\n        return False\n\n    def locked(self):\n        \"\"\"\n        Returns True if this key is locked by any process, otherwise False.\n        \"\"\"\n        return self.redis.get(self.name) is not None\n\n    def owned(self):\n        \"\"\"\n        Returns True if this key is locked by this lock, otherwise False.\n        \"\"\"\n        stored_token = self.redis.get(self.name)\n        # need to always compare bytes to bytes\n        # TODO: this can be simplified when the context manager is finished\n        if stored_token and not isinstance(stored_token, bytes):\n            encoder = self.redis.connection_pool.get_encoder()\n            stored_token = encoder.encode(stored_token)\n        return self.local.token is not None and \\\n            stored_token == self.local.token\n\n    def release(self):\n        \"Releases the already acquired lock\"\n        expected_token = self.local.token\n        if expected_token is None:\n            raise LockError(\"Cannot release an unlocked lock\")\n        self.local.token = None\n        self.do_release(expected_token)\n\n    def do_release(self, expected_token):\n        if not bool(self.lua_release(keys=[self.name],\n                                     args=[expected_token],\n                                     client=self.redis)):\n            raise LockNotOwnedError(\"Cannot release a lock\"\n                                    \" that's no longer owned\")\n\n    def extend(self, additional_time):\n        \"\"\"\n        Adds more time to an already acquired lock.\n\n        ``additional_time`` can be specified as an integer or a float, both\n        representing the number of seconds to add.\n        \"\"\"\n        if self.local.token is None:\n            raise LockError(\"Cannot extend an unlocked lock\")\n        if self.timeout is None:\n            raise LockError(\"Cannot extend a lock with no timeout\")\n        return self.do_extend(additional_time)\n\n    def do_extend(self, additional_time):\n        additional_time = int(additional_time * 1000)\n        if not bool(self.lua_extend(keys=[self.name],\n                                    args=[self.local.token, additional_time],\n                                    client=self.redis)):\n            raise LockNotOwnedError(\"Cannot extend a lock that's\"\n                                    \" no longer owned\")\n        return True\n\n    def reacquire(self):\n        \"\"\"\n        Resets a TTL of an already acquired lock back to a timeout value.\n        \"\"\"\n        if self.local.token is None:\n            raise LockError(\"Cannot reacquire an unlocked lock\")\n        if self.timeout is None:\n            raise LockError(\"Cannot reacquire a lock with no timeout\")\n        return self.do_reacquire()\n\n    def do_reacquire(self):\n        timeout = int(self.timeout * 1000)\n        if not bool(self.lua_reacquire(keys=[self.name],\n                                       args=[self.local.token, timeout],\n                                       client=self.redis)):\n            raise LockNotOwnedError(\"Cannot reacquire a lock that's\"\n                                    \" no longer owned\")\n        return True\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis/sentinel.py",
    "content": "import random\nimport weakref\n\nfrom redis.client import Redis\nfrom redis.connection import ConnectionPool, Connection\nfrom redis.exceptions import (ConnectionError, ResponseError, ReadOnlyError,\n                              TimeoutError)\nfrom redis._compat import iteritems, nativestr, xrange\n\n\nclass MasterNotFoundError(ConnectionError):\n    pass\n\n\nclass SlaveNotFoundError(ConnectionError):\n    pass\n\n\nclass SentinelManagedConnection(Connection):\n    def __init__(self, **kwargs):\n        self.connection_pool = kwargs.pop('connection_pool')\n        super(SentinelManagedConnection, self).__init__(**kwargs)\n\n    def __repr__(self):\n        pool = self.connection_pool\n        s = '%s<service=%s%%s>' % (type(self).__name__, pool.service_name)\n        if self.host:\n            host_info = ',host=%s,port=%s' % (self.host, self.port)\n            s = s % host_info\n        return s\n\n    def connect_to(self, address):\n        self.host, self.port = address\n        super(SentinelManagedConnection, self).connect()\n        if self.connection_pool.check_connection:\n            self.send_command('PING')\n            if nativestr(self.read_response()) != 'PONG':\n                raise ConnectionError('PING failed')\n\n    def connect(self):\n        if self._sock:\n            return  # already connected\n        if self.connection_pool.is_master:\n            self.connect_to(self.connection_pool.get_master_address())\n        else:\n            for slave in self.connection_pool.rotate_slaves():\n                try:\n                    return self.connect_to(slave)\n                except ConnectionError:\n                    continue\n            raise SlaveNotFoundError  # Never be here\n\n    def read_response(self):\n        try:\n            return super(SentinelManagedConnection, self).read_response()\n        except ReadOnlyError:\n            if self.connection_pool.is_master:\n                # When talking to a master, a ReadOnlyError when likely\n                # indicates that the previous master that we're still connected\n                # to has been demoted to a slave and there's a new master.\n                # calling disconnect will force the connection to re-query\n                # sentinel during the next connect() attempt.\n                self.disconnect()\n                raise ConnectionError('The previous master is now a slave')\n            raise\n\n\nclass SentinelConnectionPool(ConnectionPool):\n    \"\"\"\n    Sentinel backed connection pool.\n\n    If ``check_connection`` flag is set to True, SentinelManagedConnection\n    sends a PING command right after establishing the connection.\n    \"\"\"\n\n    def __init__(self, service_name, sentinel_manager, **kwargs):\n        kwargs['connection_class'] = kwargs.get(\n            'connection_class', SentinelManagedConnection)\n        self.is_master = kwargs.pop('is_master', True)\n        self.check_connection = kwargs.pop('check_connection', False)\n        super(SentinelConnectionPool, self).__init__(**kwargs)\n        self.connection_kwargs['connection_pool'] = weakref.proxy(self)\n        self.service_name = service_name\n        self.sentinel_manager = sentinel_manager\n\n    def __repr__(self):\n        return \"%s<service=%s(%s)\" % (\n            type(self).__name__,\n            self.service_name,\n            self.is_master and 'master' or 'slave',\n        )\n\n    def reset(self):\n        super(SentinelConnectionPool, self).reset()\n        self.master_address = None\n        self.slave_rr_counter = None\n\n    def get_master_address(self):\n        master_address = self.sentinel_manager.discover_master(\n            self.service_name)\n        if self.is_master:\n            if self.master_address is None:\n                self.master_address = master_address\n            elif master_address != self.master_address:\n                # Master address changed, disconnect all clients in this pool\n                self.disconnect()\n        return master_address\n\n    def rotate_slaves(self):\n        \"Round-robin slave balancer\"\n        slaves = self.sentinel_manager.discover_slaves(self.service_name)\n        if slaves:\n            if self.slave_rr_counter is None:\n                self.slave_rr_counter = random.randint(0, len(slaves) - 1)\n            for _ in xrange(len(slaves)):\n                self.slave_rr_counter = (\n                    self.slave_rr_counter + 1) % len(slaves)\n                slave = slaves[self.slave_rr_counter]\n                yield slave\n        # Fallback to the master connection\n        try:\n            yield self.get_master_address()\n        except MasterNotFoundError:\n            pass\n        raise SlaveNotFoundError('No slave found for %r' % (self.service_name))\n\n\nclass Sentinel(object):\n    \"\"\"\n    Redis Sentinel cluster client\n\n    >>> from redis.sentinel import Sentinel\n    >>> sentinel = Sentinel([('localhost', 26379)], socket_timeout=0.1)\n    >>> master = sentinel.master_for('mymaster', socket_timeout=0.1)\n    >>> master.set('foo', 'bar')\n    >>> slave = sentinel.slave_for('mymaster', socket_timeout=0.1)\n    >>> slave.get('foo')\n    'bar'\n\n    ``sentinels`` is a list of sentinel nodes. Each node is represented by\n    a pair (hostname, port).\n\n    ``min_other_sentinels`` defined a minimum number of peers for a sentinel.\n    When querying a sentinel, if it doesn't meet this threshold, responses\n    from that sentinel won't be considered valid.\n\n    ``sentinel_kwargs`` is a dictionary of connection arguments used when\n    connecting to sentinel instances. Any argument that can be passed to\n    a normal Redis connection can be specified here. If ``sentinel_kwargs`` is\n    not specified, any socket_timeout and socket_keepalive options specified\n    in ``connection_kwargs`` will be used.\n\n    ``connection_kwargs`` are keyword arguments that will be used when\n    establishing a connection to a Redis server.\n    \"\"\"\n\n    def __init__(self, sentinels, min_other_sentinels=0, sentinel_kwargs=None,\n                 **connection_kwargs):\n        # if sentinel_kwargs isn't defined, use the socket_* options from\n        # connection_kwargs\n        if sentinel_kwargs is None:\n            sentinel_kwargs = {\n                k: v\n                for k, v in iteritems(connection_kwargs)\n                if k.startswith('socket_')\n            }\n        self.sentinel_kwargs = sentinel_kwargs\n\n        self.sentinels = [Redis(hostname, port, **self.sentinel_kwargs)\n                          for hostname, port in sentinels]\n        self.min_other_sentinels = min_other_sentinels\n        self.connection_kwargs = connection_kwargs\n\n    def __repr__(self):\n        sentinel_addresses = []\n        for sentinel in self.sentinels:\n            sentinel_addresses.append('%s:%s' % (\n                sentinel.connection_pool.connection_kwargs['host'],\n                sentinel.connection_pool.connection_kwargs['port'],\n            ))\n        return '%s<sentinels=[%s]>' % (\n            type(self).__name__,\n            ','.join(sentinel_addresses))\n\n    def check_master_state(self, state, service_name):\n        if not state['is_master'] or state['is_sdown'] or state['is_odown']:\n            return False\n        # Check if our sentinel doesn't see other nodes\n        if state['num-other-sentinels'] < self.min_other_sentinels:\n            return False\n        return True\n\n    def discover_master(self, service_name):\n        \"\"\"\n        Asks sentinel servers for the Redis master's address corresponding\n        to the service labeled ``service_name``.\n\n        Returns a pair (address, port) or raises MasterNotFoundError if no\n        master is found.\n        \"\"\"\n        for sentinel_no, sentinel in enumerate(self.sentinels):\n            try:\n                masters = sentinel.sentinel_masters()\n            except (ConnectionError, TimeoutError):\n                continue\n            state = masters.get(service_name)\n            if state and self.check_master_state(state, service_name):\n                # Put this sentinel at the top of the list\n                self.sentinels[0], self.sentinels[sentinel_no] = (\n                    sentinel, self.sentinels[0])\n                return state['ip'], state['port']\n        raise MasterNotFoundError(\"No master found for %r\" % (service_name,))\n\n    def filter_slaves(self, slaves):\n        \"Remove slaves that are in an ODOWN or SDOWN state\"\n        slaves_alive = []\n        for slave in slaves:\n            if slave['is_odown'] or slave['is_sdown']:\n                continue\n            slaves_alive.append((slave['ip'], slave['port']))\n        return slaves_alive\n\n    def discover_slaves(self, service_name):\n        \"Returns a list of alive slaves for service ``service_name``\"\n        for sentinel in self.sentinels:\n            try:\n                slaves = sentinel.sentinel_slaves(service_name)\n            except (ConnectionError, ResponseError, TimeoutError):\n                continue\n            slaves = self.filter_slaves(slaves)\n            if slaves:\n                return slaves\n        return []\n\n    def master_for(self, service_name, redis_class=Redis,\n                   connection_pool_class=SentinelConnectionPool, **kwargs):\n        \"\"\"\n        Returns a redis client instance for the ``service_name`` master.\n\n        A SentinelConnectionPool class is used to retrive the master's\n        address before establishing a new connection.\n\n        NOTE: If the master's address has changed, any cached connections to\n        the old master are closed.\n\n        By default clients will be a redis.Redis instance. Specify a\n        different class to the ``redis_class`` argument if you desire\n        something different.\n\n        The ``connection_pool_class`` specifies the connection pool to use.\n        The SentinelConnectionPool will be used by default.\n\n        All other keyword arguments are merged with any connection_kwargs\n        passed to this class and passed to the connection pool as keyword\n        arguments to be used to initialize Redis connections.\n        \"\"\"\n        kwargs['is_master'] = True\n        connection_kwargs = dict(self.connection_kwargs)\n        connection_kwargs.update(kwargs)\n        return redis_class(connection_pool=connection_pool_class(\n            service_name, self, **connection_kwargs))\n\n    def slave_for(self, service_name, redis_class=Redis,\n                  connection_pool_class=SentinelConnectionPool, **kwargs):\n        \"\"\"\n        Returns redis client instance for the ``service_name`` slave(s).\n\n        A SentinelConnectionPool class is used to retrive the slave's\n        address before establishing a new connection.\n\n        By default clients will be a redis.Redis instance. Specify a\n        different class to the ``redis_class`` argument if you desire\n        something different.\n\n        The ``connection_pool_class`` specifies the connection pool to use.\n        The SentinelConnectionPool will be used by default.\n\n        All other keyword arguments are merged with any connection_kwargs\n        passed to this class and passed to the connection pool as keyword\n        arguments to be used to initialize Redis connections.\n        \"\"\"\n        kwargs['is_master'] = False\n        connection_kwargs = dict(self.connection_kwargs)\n        connection_kwargs.update(kwargs)\n        return redis_class(connection_pool=connection_pool_class(\n            service_name, self, **connection_kwargs))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis/utils.py",
    "content": "from contextlib import contextmanager\n\n\ntry:\n    import hiredis\n    HIREDIS_AVAILABLE = True\nexcept ImportError:\n    HIREDIS_AVAILABLE = False\n\n\ndef from_url(url, db=None, **kwargs):\n    \"\"\"\n    Returns an active Redis client generated from the given database URL.\n\n    Will attempt to extract the database id from the path url fragment, if\n    none is provided.\n    \"\"\"\n    from redis.client import Redis\n    return Redis.from_url(url, db, **kwargs)\n\n\n@contextmanager\ndef pipeline(redis_obj):\n    p = redis_obj.pipeline()\n    yield p\n    p.execute()\n\n\nclass dummy(object):\n    \"\"\"\n    Instances of this class can be used as an attribute container.\n    \"\"\"\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis-3.3.11.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis-3.3.11.dist-info/LICENSE",
    "content": "Copyright (c) 2012 Andy McCurdy\n\n Permission is hereby granted, free of charge, to any person\n obtaining a copy of this software and associated documentation\n files (the \"Software\"), to deal in the Software without\n restriction, including without limitation the rights to use,\n copy, modify, merge, publish, distribute, sublicense, and/or sell\n copies of the Software, and to permit persons to whom the\n Software is furnished to do so, subject to the following\n conditions:\n\n The above copyright notice and this permission notice shall be\n included in all copies or substantial portions of the Software.\n\n THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND,\n EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES\n OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND\n NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT\n HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,\n WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING\n FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR\n OTHER DEALINGS IN THE SOFTWARE.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis-3.3.11.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: redis\nVersion: 3.3.11\nSummary: Python client for Redis key-value store\nHome-page: https://github.com/andymccurdy/redis-py\nAuthor: Andy McCurdy\nAuthor-email: sedrik@gmail.com\nMaintainer: Andy McCurdy\nMaintainer-email: sedrik@gmail.com\nLicense: MIT\nKeywords: Redis,key-value store\nPlatform: UNKNOWN\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Environment :: Console\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: MIT License\nClassifier: Operating System :: OS Independent\nClassifier: Programming Language :: Python\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nRequires-Python: >=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*\nDescription-Content-Type: text/x-rst\nProvides-Extra: hiredis\nRequires-Dist: hiredis (>=0.1.3); extra == 'hiredis'\n\nredis-py\n========\n\nThe Python interface to the Redis key-value store.\n\n.. image:: https://secure.travis-ci.org/andymccurdy/redis-py.svg?branch=master\n        :target: https://travis-ci.org/andymccurdy/redis-py\n.. image:: https://readthedocs.org/projects/redis-py/badge/?version=latest&style=flat\n        :target: https://redis-py.readthedocs.io/en/latest/\n.. image:: https://badge.fury.io/py/redis.svg\n        :target: https://pypi.org/project/redis/\n.. image:: https://codecov.io/gh/andymccurdy/redis-py/branch/master/graph/badge.svg\n  :target: https://codecov.io/gh/andymccurdy/redis-py\n\nInstallation\n------------\n\nredis-py requires a running Redis server. See `Redis's quickstart\n<https://redis.io/topics/quickstart>`_ for installation instructions.\n\nredis-py can be installed using `pip` similar to other Python packages. Do not use `sudo`\nwith `pip`. It is usually good to work in a\n`virtualenv <https://virtualenv.pypa.io/en/latest/>`_ or\n`venv <https://docs.python.org/3/library/venv.html>`_ to avoid conflicts with other package\nmanagers and Python projects. For a quick introduction see\n`Python Virtual Environments in Five Minutes <https://bit.ly/py-env>`_.\n\nTo install redis-py, simply:\n\n.. code-block:: bash\n\n    $ pip install redis\n\nor from source:\n\n.. code-block:: bash\n\n    $ python setup.py install\n\n\nGetting Started\n---------------\n\n.. code-block:: pycon\n\n    >>> import redis\n    >>> r = redis.Redis(host='localhost', port=6379, db=0)\n    >>> r.set('foo', 'bar')\n    True\n    >>> r.get('foo')\n    'bar'\n\nBy default, all responses are returned as `bytes` in Python 3 and `str` in\nPython 2. The user is responsible for decoding to Python 3 strings or Python 2\nunicode objects.\n\nIf **all** string responses from a client should be decoded, the user can\nspecify `decode_responses=True` to `Redis.__init__`. In this case, any\nRedis command that returns a string type will be decoded with the `encoding`\nspecified.\n\n\nUpgrading from redis-py 2.X to 3.0\n----------------------------------\n\nredis-py 3.0 introduces many new features but required a number of backwards\nincompatible changes to be made in the process. This section attempts to\nprovide an upgrade path for users migrating from 2.X to 3.0.\n\n\nPython Version Support\n^^^^^^^^^^^^^^^^^^^^^^\n\nredis-py 3.0 now supports Python 2.7 and Python 3.4+. Python 2.6 and 3.3\nsupport has been dropped.\n\n\nClient Classes: Redis and StrictRedis\n^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n\nredis-py 3.0 drops support for the legacy \"Redis\" client class. \"StrictRedis\"\nhas been renamed to \"Redis\" and an alias named \"StrictRedis\" is provided so\nthat users previously using \"StrictRedis\" can continue to run unchanged.\n\nThe 2.X \"Redis\" class provided alternative implementations of a few commands.\nThis confused users (rightfully so) and caused a number of support issues. To\nmake things easier going forward, it was decided to drop support for these\nalternate implementations and instead focus on a single client class.\n\n2.X users that are already using StrictRedis don't have to change the class\nname. StrictRedis will continue to work for the forseeable future.\n\n2.X users that are using the Redis class will have to make changes if they\nuse any of the following commands:\n\n* SETEX: The argument order has changed. The new order is (name, time, value).\n* LREM: The argument order has changed. The new order is (name, num, value).\n* TTL and PTTL: The return value is now always an int and matches the\n  official Redis command (>0 indicates the timeout, -1 indicates that the key\n  exists but that it has no expire time set, -2 indicates that the key does\n  not exist)\n\n\nSSL Connections\n^^^^^^^^^^^^^^^\n\nredis-py 3.0 changes the default value of the `ssl_cert_reqs` option from\n`None` to `'required'`. See\n`Issue 1016 <https://github.com/andymccurdy/redis-py/issues/1016>`_. This\nchange enforces hostname validation when accepting a cert from a remote SSL\nterminator. If the terminator doesn't properly set the hostname on the cert\nthis will cause redis-py 3.0 to raise a ConnectionError.\n\nThis check can be disabled by setting `ssl_cert_reqs` to `None`. Note that\ndoing so removes the security check. Do so at your own risk.\n\nIt has been reported that SSL certs received from AWS ElastiCache do not have\nproper hostnames and turning off hostname verification is currently required.\n\n\nMSET, MSETNX and ZADD\n^^^^^^^^^^^^^^^^^^^^^\n\nThese commands all accept a mapping of key/value pairs. In redis-py 2.X\nthis mapping could be specified as ``*args`` or as ``**kwargs``. Both of these\nstyles caused issues when Redis introduced optional flags to ZADD. Relying on\n``*args`` caused issues with the optional argument order, especially in Python\n2.7. Relying on ``**kwargs`` caused potential collision issues of user keys with\nthe argument names in the method signature.\n\nTo resolve this, redis-py 3.0 has changed these three commands to all accept\na single positional argument named mapping that is expected to be a dict. For\nMSET and MSETNX, the dict is a mapping of key-names -> values. For ZADD, the\ndict is a mapping of element-names -> score.\n\nMSET, MSETNX and ZADD now look like:\n\n.. code-block:: pycon\n\n    def mset(self, mapping):\n    def msetnx(self, mapping):\n    def zadd(self, name, mapping, nx=False, xx=False, ch=False, incr=False):\n\nAll 2.X users that use these commands must modify their code to supply\nkeys and values as a dict to these commands.\n\n\nZINCRBY\n^^^^^^^\n\nredis-py 2.X accidentally modified the argument order of ZINCRBY, swapping the\norder of value and amount. ZINCRBY now looks like:\n\n.. code-block:: pycon\n\n    def zincrby(self, name, amount, value):\n\nAll 2.X users that rely on ZINCRBY must swap the order of amount and value\nfor the command to continue to work as intended.\n\n\nEncoding of User Input\n^^^^^^^^^^^^^^^^^^^^^^\n\nredis-py 3.0 only accepts user data as bytes, strings or numbers (ints, longs\nand floats). Attempting to specify a key or a value as any other type will\nraise a DataError exception.\n\nredis-py 2.X attempted to coerce any type of input into a string. While\noccasionally convenient, this caused all sorts of hidden errors when users\npassed boolean values (which were coerced to 'True' or 'False'), a None\nvalue (which was coerced to 'None') or other values, such as user defined\ntypes.\n\nAll 2.X users should make sure that the keys and values they pass into\nredis-py are either bytes, strings or numbers.\n\n\nLocks\n^^^^^\n\nredis-py 3.0 drops support for the pipeline-based Lock and now only supports\nthe Lua-based lock. In doing so, LuaLock has been renamed to Lock. This also\nmeans that redis-py Lock objects require Redis server 2.6 or greater.\n\n2.X users that were explicitly referring to \"LuaLock\" will have to now refer\nto \"Lock\" instead.\n\n\nLocks as Context Managers\n^^^^^^^^^^^^^^^^^^^^^^^^^\n\nredis-py 3.0 now raises a LockError when using a lock as a context manager and\nthe lock cannot be acquired within the specified timeout. This is more of a\nbug fix than a backwards incompatible change. However, given an error is now\nraised where none was before, this might alarm some users.\n\n2.X users should make sure they're wrapping their lock code in a try/catch\nlike this:\n\n.. code-block:: pycon\n\n    try:\n        with r.lock('my-lock-key', blocking_timeout=5) as lock:\n            # code you want executed only after the lock has been acquired\n    except LockError:\n        # the lock wasn't acquired\n\n\nAPI Reference\n-------------\n\nThe `official Redis command documentation <https://redis.io/commands>`_ does a\ngreat job of explaining each command in detail. redis-py attempts to adhere\nto the official command syntax. There are a few exceptions:\n\n* **SELECT**: Not implemented. See the explanation in the Thread Safety section\n  below.\n* **DEL**: 'del' is a reserved keyword in the Python syntax. Therefore redis-py\n  uses 'delete' instead.\n* **MULTI/EXEC**: These are implemented as part of the Pipeline class. The\n  pipeline is wrapped with the MULTI and EXEC statements by default when it\n  is executed, which can be disabled by specifying transaction=False.\n  See more about Pipelines below.\n* **SUBSCRIBE/LISTEN**: Similar to pipelines, PubSub is implemented as a separate\n  class as it places the underlying connection in a state where it can't\n  execute non-pubsub commands. Calling the pubsub method from the Redis client\n  will return a PubSub instance where you can subscribe to channels and listen\n  for messages. You can only call PUBLISH from the Redis client (see\n  `this comment on issue #151\n  <https://github.com/andymccurdy/redis-py/issues/151#issuecomment-1545015>`_\n  for details).\n* **SCAN/SSCAN/HSCAN/ZSCAN**: The \\*SCAN commands are implemented as they\n  exist in the Redis documentation. In addition, each command has an equivalent\n  iterator method. These are purely for convenience so the user doesn't have\n  to keep track of the cursor while iterating. Use the\n  scan_iter/sscan_iter/hscan_iter/zscan_iter methods for this behavior.\n\n\nMore Detail\n-----------\n\nConnection Pools\n^^^^^^^^^^^^^^^^\n\nBehind the scenes, redis-py uses a connection pool to manage connections to\na Redis server. By default, each Redis instance you create will in turn create\nits own connection pool. You can override this behavior and use an existing\nconnection pool by passing an already created connection pool instance to the\nconnection_pool argument of the Redis class. You may choose to do this in order\nto implement client side sharding or have finer grain control of how\nconnections are managed.\n\n.. code-block:: pycon\n\n    >>> pool = redis.ConnectionPool(host='localhost', port=6379, db=0)\n    >>> r = redis.Redis(connection_pool=pool)\n\nConnections\n^^^^^^^^^^^\n\nConnectionPools manage a set of Connection instances. redis-py ships with two\ntypes of Connections. The default, Connection, is a normal TCP socket based\nconnection. The UnixDomainSocketConnection allows for clients running on the\nsame device as the server to connect via a unix domain socket. To use a\nUnixDomainSocketConnection connection, simply pass the unix_socket_path\nargument, which is a string to the unix domain socket file. Additionally, make\nsure the unixsocket parameter is defined in your redis.conf file. It's\ncommented out by default.\n\n.. code-block:: pycon\n\n    >>> r = redis.Redis(unix_socket_path='/tmp/redis.sock')\n\nYou can create your own Connection subclasses as well. This may be useful if\nyou want to control the socket behavior within an async framework. To\ninstantiate a client class using your own connection, you need to create\na connection pool, passing your class to the connection_class argument.\nOther keyword parameters you pass to the pool will be passed to the class\nspecified during initialization.\n\n.. code-block:: pycon\n\n    >>> pool = redis.ConnectionPool(connection_class=YourConnectionClass,\n                                    your_arg='...', ...)\n\nConnections maintain an open socket to the Redis server. Sometimes these\nsockets are interrupted or disconnected for a variety of reasons. For example,\nnetwork appliances, load balancers and other services that sit between clients\nand servers are often configured to kill connections that remain idle for a\ngiven threshold.\n\nWhen a connection becomes disconnected, the next command issued on that\nconnection will fail and redis-py will raise a ConnectionError to the caller.\nThis allows each application that uses redis-py to handle errors in a way\nthat's fitting for that specific application. However, constant error\nhandling can be verbose and cumbersome, especially when socket disconnections\nhappen frequently in many production environments.\n\nTo combat this, redis-py can issue regular health checks to assess the\nliveliness of a connection just before issuing a command. Users can pass\n``health_check_interval=N`` to the Redis or ConnectionPool classes or\nas a query argument within a Redis URL. The value of ``health_check_interval``\nmust be an integer. A value of ``0``, the default, disables health checks.\nAny positive integer will enable health checks. Health checks are performed\njust before a command is executed if the underlying connection has been idle\nfor more than ``health_check_interval`` seconds. For example,\n``health_check_interval=30`` will ensure that a health check is run on any\nconnection that has been idle for 30 or more seconds just before a command\nis executed on that connection.\n\nIf your application is running in an environment that disconnects idle\nconnections after 30 seconds you should set the ``health_check_interval``\noption to a value less than 30.\n\nThis option also works on any PubSub connection that is created from a\nclient with ``health_check_interval`` enabled. PubSub users need to ensure\nthat ``get_message()`` or ``listen()`` are called more frequently than\n``health_check_interval`` seconds. It is assumed that most workloads already\ndo this.\n\nIf your PubSub use case doesn't call ``get_message()`` or ``listen()``\nfrequently, you should call ``pubsub.check_health()`` explicitly on a\nregularly basis.\n\nParsers\n^^^^^^^\n\nParser classes provide a way to control how responses from the Redis server\nare parsed. redis-py ships with two parser classes, the PythonParser and the\nHiredisParser. By default, redis-py will attempt to use the HiredisParser if\nyou have the hiredis module installed and will fallback to the PythonParser\notherwise.\n\nHiredis is a C library maintained by the core Redis team. Pieter Noordhuis was\nkind enough to create Python bindings. Using Hiredis can provide up to a\n10x speed improvement in parsing responses from the Redis server. The\nperformance increase is most noticeable when retrieving many pieces of data,\nsuch as from LRANGE or SMEMBERS operations.\n\nHiredis is available on PyPI, and can be installed via pip just like redis-py.\n\n.. code-block:: bash\n\n    $ pip install hiredis\n\nResponse Callbacks\n^^^^^^^^^^^^^^^^^^\n\nThe client class uses a set of callbacks to cast Redis responses to the\nappropriate Python type. There are a number of these callbacks defined on\nthe Redis client class in a dictionary called RESPONSE_CALLBACKS.\n\nCustom callbacks can be added on a per-instance basis using the\nset_response_callback method. This method accepts two arguments: a command\nname and the callback. Callbacks added in this manner are only valid on the\ninstance the callback is added to. If you want to define or override a callback\nglobally, you should make a subclass of the Redis client and add your callback\nto its RESPONSE_CALLBACKS class dictionary.\n\nResponse callbacks take at least one parameter: the response from the Redis\nserver. Keyword arguments may also be accepted in order to further control\nhow to interpret the response. These keyword arguments are specified during the\ncommand's call to execute_command. The ZRANGE implementation demonstrates the\nuse of response callback keyword arguments with its \"withscores\" argument.\n\nThread Safety\n^^^^^^^^^^^^^\n\nRedis client instances can safely be shared between threads. Internally,\nconnection instances are only retrieved from the connection pool during\ncommand execution, and returned to the pool directly after. Command execution\nnever modifies state on the client instance.\n\nHowever, there is one caveat: the Redis SELECT command. The SELECT command\nallows you to switch the database currently in use by the connection. That\ndatabase remains selected until another is selected or until the connection is\nclosed. This creates an issue in that connections could be returned to the pool\nthat are connected to a different database.\n\nAs a result, redis-py does not implement the SELECT command on client\ninstances. If you use multiple Redis databases within the same application, you\nshould create a separate client instance (and possibly a separate connection\npool) for each database.\n\nIt is not safe to pass PubSub or Pipeline objects between threads.\n\nPipelines\n^^^^^^^^^\n\nPipelines are a subclass of the base Redis class that provide support for\nbuffering multiple commands to the server in a single request. They can be used\nto dramatically increase the performance of groups of commands by reducing the\nnumber of back-and-forth TCP packets between the client and server.\n\nPipelines are quite simple to use:\n\n.. code-block:: pycon\n\n    >>> r = redis.Redis(...)\n    >>> r.set('bing', 'baz')\n    >>> # Use the pipeline() method to create a pipeline instance\n    >>> pipe = r.pipeline()\n    >>> # The following SET commands are buffered\n    >>> pipe.set('foo', 'bar')\n    >>> pipe.get('bing')\n    >>> # the EXECUTE call sends all buffered commands to the server, returning\n    >>> # a list of responses, one for each command.\n    >>> pipe.execute()\n    [True, 'baz']\n\nFor ease of use, all commands being buffered into the pipeline return the\npipeline object itself. Therefore calls can be chained like:\n\n.. code-block:: pycon\n\n    >>> pipe.set('foo', 'bar').sadd('faz', 'baz').incr('auto_number').execute()\n    [True, True, 6]\n\nIn addition, pipelines can also ensure the buffered commands are executed\natomically as a group. This happens by default. If you want to disable the\natomic nature of a pipeline but still want to buffer commands, you can turn\noff transactions.\n\n.. code-block:: pycon\n\n    >>> pipe = r.pipeline(transaction=False)\n\nA common issue occurs when requiring atomic transactions but needing to\nretrieve values in Redis prior for use within the transaction. For instance,\nlet's assume that the INCR command didn't exist and we need to build an atomic\nversion of INCR in Python.\n\nThe completely naive implementation could GET the value, increment it in\nPython, and SET the new value back. However, this is not atomic because\nmultiple clients could be doing this at the same time, each getting the same\nvalue from GET.\n\nEnter the WATCH command. WATCH provides the ability to monitor one or more keys\nprior to starting a transaction. If any of those keys change prior the\nexecution of that transaction, the entire transaction will be canceled and a\nWatchError will be raised. To implement our own client-side INCR command, we\ncould do something like this:\n\n.. code-block:: pycon\n\n    >>> with r.pipeline() as pipe:\n    ...     while True:\n    ...         try:\n    ...             # put a WATCH on the key that holds our sequence value\n    ...             pipe.watch('OUR-SEQUENCE-KEY')\n    ...             # after WATCHing, the pipeline is put into immediate execution\n    ...             # mode until we tell it to start buffering commands again.\n    ...             # this allows us to get the current value of our sequence\n    ...             current_value = pipe.get('OUR-SEQUENCE-KEY')\n    ...             next_value = int(current_value) + 1\n    ...             # now we can put the pipeline back into buffered mode with MULTI\n    ...             pipe.multi()\n    ...             pipe.set('OUR-SEQUENCE-KEY', next_value)\n    ...             # and finally, execute the pipeline (the set command)\n    ...             pipe.execute()\n    ...             # if a WatchError wasn't raised during execution, everything\n    ...             # we just did happened atomically.\n    ...             break\n    ...        except WatchError:\n    ...             # another client must have changed 'OUR-SEQUENCE-KEY' between\n    ...             # the time we started WATCHing it and the pipeline's execution.\n    ...             # our best bet is to just retry.\n    ...             continue\n\nNote that, because the Pipeline must bind to a single connection for the\nduration of a WATCH, care must be taken to ensure that the connection is\nreturned to the connection pool by calling the reset() method. If the\nPipeline is used as a context manager (as in the example above) reset()\nwill be called automatically. Of course you can do this the manual way by\nexplicitly calling reset():\n\n.. code-block:: pycon\n\n    >>> pipe = r.pipeline()\n    >>> while True:\n    ...     try:\n    ...         pipe.watch('OUR-SEQUENCE-KEY')\n    ...         ...\n    ...         pipe.execute()\n    ...         break\n    ...     except WatchError:\n    ...         continue\n    ...     finally:\n    ...         pipe.reset()\n\nA convenience method named \"transaction\" exists for handling all the\nboilerplate of handling and retrying watch errors. It takes a callable that\nshould expect a single parameter, a pipeline object, and any number of keys to\nbe WATCHed. Our client-side INCR command above can be written like this,\nwhich is much easier to read:\n\n.. code-block:: pycon\n\n    >>> def client_side_incr(pipe):\n    ...     current_value = pipe.get('OUR-SEQUENCE-KEY')\n    ...     next_value = int(current_value) + 1\n    ...     pipe.multi()\n    ...     pipe.set('OUR-SEQUENCE-KEY', next_value)\n    >>>\n    >>> r.transaction(client_side_incr, 'OUR-SEQUENCE-KEY')\n    [True]\n\nPublish / Subscribe\n^^^^^^^^^^^^^^^^^^^\n\nredis-py includes a `PubSub` object that subscribes to channels and listens\nfor new messages. Creating a `PubSub` object is easy.\n\n.. code-block:: pycon\n\n    >>> r = redis.Redis(...)\n    >>> p = r.pubsub()\n\nOnce a `PubSub` instance is created, channels and patterns can be subscribed\nto.\n\n.. code-block:: pycon\n\n    >>> p.subscribe('my-first-channel', 'my-second-channel', ...)\n    >>> p.psubscribe('my-*', ...)\n\nThe `PubSub` instance is now subscribed to those channels/patterns. The\nsubscription confirmations can be seen by reading messages from the `PubSub`\ninstance.\n\n.. code-block:: pycon\n\n    >>> p.get_message()\n    {'pattern': None, 'type': 'subscribe', 'channel': 'my-second-channel', 'data': 1L}\n    >>> p.get_message()\n    {'pattern': None, 'type': 'subscribe', 'channel': 'my-first-channel', 'data': 2L}\n    >>> p.get_message()\n    {'pattern': None, 'type': 'psubscribe', 'channel': 'my-*', 'data': 3L}\n\nEvery message read from a `PubSub` instance will be a dictionary with the\nfollowing keys.\n\n* **type**: One of the following: 'subscribe', 'unsubscribe', 'psubscribe',\n  'punsubscribe', 'message', 'pmessage'\n* **channel**: The channel [un]subscribed to or the channel a message was\n  published to\n* **pattern**: The pattern that matched a published message's channel. Will be\n  `None` in all cases except for 'pmessage' types.\n* **data**: The message data. With [un]subscribe messages, this value will be\n  the number of channels and patterns the connection is currently subscribed\n  to. With [p]message messages, this value will be the actual published\n  message.\n\nLet's send a message now.\n\n.. code-block:: pycon\n\n    # the publish method returns the number matching channel and pattern\n    # subscriptions. 'my-first-channel' matches both the 'my-first-channel'\n    # subscription and the 'my-*' pattern subscription, so this message will\n    # be delivered to 2 channels/patterns\n    >>> r.publish('my-first-channel', 'some data')\n    2\n    >>> p.get_message()\n    {'channel': 'my-first-channel', 'data': 'some data', 'pattern': None, 'type': 'message'}\n    >>> p.get_message()\n    {'channel': 'my-first-channel', 'data': 'some data', 'pattern': 'my-*', 'type': 'pmessage'}\n\nUnsubscribing works just like subscribing. If no arguments are passed to\n[p]unsubscribe, all channels or patterns will be unsubscribed from.\n\n.. code-block:: pycon\n\n    >>> p.unsubscribe()\n    >>> p.punsubscribe('my-*')\n    >>> p.get_message()\n    {'channel': 'my-second-channel', 'data': 2L, 'pattern': None, 'type': 'unsubscribe'}\n    >>> p.get_message()\n    {'channel': 'my-first-channel', 'data': 1L, 'pattern': None, 'type': 'unsubscribe'}\n    >>> p.get_message()\n    {'channel': 'my-*', 'data': 0L, 'pattern': None, 'type': 'punsubscribe'}\n\nredis-py also allows you to register callback functions to handle published\nmessages. Message handlers take a single argument, the message, which is a\ndictionary just like the examples above. To subscribe to a channel or pattern\nwith a message handler, pass the channel or pattern name as a keyword argument\nwith its value being the callback function.\n\nWhen a message is read on a channel or pattern with a message handler, the\nmessage dictionary is created and passed to the message handler. In this case,\na `None` value is returned from get_message() since the message was already\nhandled.\n\n.. code-block:: pycon\n\n    >>> def my_handler(message):\n    ...     print 'MY HANDLER: ', message['data']\n    >>> p.subscribe(**{'my-channel': my_handler})\n    # read the subscribe confirmation message\n    >>> p.get_message()\n    {'pattern': None, 'type': 'subscribe', 'channel': 'my-channel', 'data': 1L}\n    >>> r.publish('my-channel', 'awesome data')\n    1\n    # for the message handler to work, we need tell the instance to read data.\n    # this can be done in several ways (read more below). we'll just use\n    # the familiar get_message() function for now\n    >>> message = p.get_message()\n    MY HANDLER:  awesome data\n    # note here that the my_handler callback printed the string above.\n    # `message` is None because the message was handled by our handler.\n    >>> print message\n    None\n\nIf your application is not interested in the (sometimes noisy)\nsubscribe/unsubscribe confirmation messages, you can ignore them by passing\n`ignore_subscribe_messages=True` to `r.pubsub()`. This will cause all\nsubscribe/unsubscribe messages to be read, but they won't bubble up to your\napplication.\n\n.. code-block:: pycon\n\n    >>> p = r.pubsub(ignore_subscribe_messages=True)\n    >>> p.subscribe('my-channel')\n    >>> p.get_message()  # hides the subscribe message and returns None\n    >>> r.publish('my-channel', 'my data')\n    1\n    >>> p.get_message()\n    {'channel': 'my-channel', 'data': 'my data', 'pattern': None, 'type': 'message'}\n\nThere are three different strategies for reading messages.\n\nThe examples above have been using `pubsub.get_message()`. Behind the scenes,\n`get_message()` uses the system's 'select' module to quickly poll the\nconnection's socket. If there's data available to be read, `get_message()` will\nread it, format the message and return it or pass it to a message handler. If\nthere's no data to be read, `get_message()` will immediately return None. This\nmakes it trivial to integrate into an existing event loop inside your\napplication.\n\n.. code-block:: pycon\n\n    >>> while True:\n    >>>     message = p.get_message()\n    >>>     if message:\n    >>>         # do something with the message\n    >>>     time.sleep(0.001)  # be nice to the system :)\n\nOlder versions of redis-py only read messages with `pubsub.listen()`. listen()\nis a generator that blocks until a message is available. If your application\ndoesn't need to do anything else but receive and act on messages received from\nredis, listen() is an easy way to get up an running.\n\n.. code-block:: pycon\n\n    >>> for message in p.listen():\n    ...     # do something with the message\n\nThe third option runs an event loop in a separate thread.\n`pubsub.run_in_thread()` creates a new thread and starts the event loop. The\nthread object is returned to the caller of `run_in_thread()`. The caller can\nuse the `thread.stop()` method to shut down the event loop and thread. Behind\nthe scenes, this is simply a wrapper around `get_message()` that runs in a\nseparate thread, essentially creating a tiny non-blocking event loop for you.\n`run_in_thread()` takes an optional `sleep_time` argument. If specified, the\nevent loop will call `time.sleep()` with the value in each iteration of the\nloop.\n\nNote: Since we're running in a separate thread, there's no way to handle\nmessages that aren't automatically handled with registered message handlers.\nTherefore, redis-py prevents you from calling `run_in_thread()` if you're\nsubscribed to patterns or channels that don't have message handlers attached.\n\n.. code-block:: pycon\n\n    >>> p.subscribe(**{'my-channel': my_handler})\n    >>> thread = p.run_in_thread(sleep_time=0.001)\n    # the event loop is now running in the background processing messages\n    # when it's time to shut it down...\n    >>> thread.stop()\n\nA PubSub object adheres to the same encoding semantics as the client instance\nit was created from. Any channel or pattern that's unicode will be encoded\nusing the `charset` specified on the client before being sent to Redis. If the\nclient's `decode_responses` flag is set the False (the default), the\n'channel', 'pattern' and 'data' values in message dictionaries will be byte\nstrings (str on Python 2, bytes on Python 3). If the client's\n`decode_responses` is True, then the 'channel', 'pattern' and 'data' values\nwill be automatically decoded to unicode strings using the client's `charset`.\n\nPubSub objects remember what channels and patterns they are subscribed to. In\nthe event of a disconnection such as a network error or timeout, the\nPubSub object will re-subscribe to all prior channels and patterns when\nreconnecting. Messages that were published while the client was disconnected\ncannot be delivered. When you're finished with a PubSub object, call its\n`.close()` method to shutdown the connection.\n\n.. code-block:: pycon\n\n    >>> p = r.pubsub()\n    >>> ...\n    >>> p.close()\n\n\nThe PUBSUB set of subcommands CHANNELS, NUMSUB and NUMPAT are also\nsupported:\n\n.. code-block:: pycon\n\n    >>> r.pubsub_channels()\n    ['foo', 'bar']\n    >>> r.pubsub_numsub('foo', 'bar')\n    [('foo', 9001), ('bar', 42)]\n    >>> r.pubsub_numsub('baz')\n    [('baz', 0)]\n    >>> r.pubsub_numpat()\n    1204\n\nMonitor\n^^^^^^^\nredis-py includes a `Monitor` object that streams every command processed\nby the Redis server. Use `listen()` on the `Monitor` object to block\nuntil a command is received.\n\n.. code-block:: pycon\n\n    >>> r = redis.Redis(...)\n    >>> with r.monitor() as m:\n    >>>     for command in m.listen():\n    >>>         print(command)\n\nLua Scripting\n^^^^^^^^^^^^^\n\nredis-py supports the EVAL, EVALSHA, and SCRIPT commands. However, there are\na number of edge cases that make these commands tedious to use in real world\nscenarios. Therefore, redis-py exposes a Script object that makes scripting\nmuch easier to use.\n\nTo create a Script instance, use the `register_script` function on a client\ninstance passing the Lua code as the first argument. `register_script` returns\na Script instance that you can use throughout your code.\n\nThe following trivial Lua script accepts two parameters: the name of a key and\na multiplier value. The script fetches the value stored in the key, multiplies\nit with the multiplier value and returns the result.\n\n.. code-block:: pycon\n\n    >>> r = redis.Redis()\n    >>> lua = \"\"\"\n    ... local value = redis.call('GET', KEYS[1])\n    ... value = tonumber(value)\n    ... return value * ARGV[1]\"\"\"\n    >>> multiply = r.register_script(lua)\n\n`multiply` is now a Script instance that is invoked by calling it like a\nfunction. Script instances accept the following optional arguments:\n\n* **keys**: A list of key names that the script will access. This becomes the\n  KEYS list in Lua.\n* **args**: A list of argument values. This becomes the ARGV list in Lua.\n* **client**: A redis-py Client or Pipeline instance that will invoke the\n  script. If client isn't specified, the client that initially\n  created the Script instance (the one that `register_script` was\n  invoked from) will be used.\n\nContinuing the example from above:\n\n.. code-block:: pycon\n\n    >>> r.set('foo', 2)\n    >>> multiply(keys=['foo'], args=[5])\n    10\n\nThe value of key 'foo' is set to 2. When multiply is invoked, the 'foo' key is\npassed to the script along with the multiplier value of 5. Lua executes the\nscript and returns the result, 10.\n\nScript instances can be executed using a different client instance, even one\nthat points to a completely different Redis server.\n\n.. code-block:: pycon\n\n    >>> r2 = redis.Redis('redis2.example.com')\n    >>> r2.set('foo', 3)\n    >>> multiply(keys=['foo'], args=[5], client=r2)\n    15\n\nThe Script object ensures that the Lua script is loaded into Redis's script\ncache. In the event of a NOSCRIPT error, it will load the script and retry\nexecuting it.\n\nScript objects can also be used in pipelines. The pipeline instance should be\npassed as the client argument when calling the script. Care is taken to ensure\nthat the script is registered in Redis's script cache just prior to pipeline\nexecution.\n\n.. code-block:: pycon\n\n    >>> pipe = r.pipeline()\n    >>> pipe.set('foo', 5)\n    >>> multiply(keys=['foo'], args=[5], client=pipe)\n    >>> pipe.execute()\n    [True, 25]\n\nSentinel support\n^^^^^^^^^^^^^^^^\n\nredis-py can be used together with `Redis Sentinel <https://redis.io/topics/sentinel>`_\nto discover Redis nodes. You need to have at least one Sentinel daemon running\nin order to use redis-py's Sentinel support.\n\nConnecting redis-py to the Sentinel instance(s) is easy. You can use a\nSentinel connection to discover the master and slaves network addresses:\n\n.. code-block:: pycon\n\n    >>> from redis.sentinel import Sentinel\n    >>> sentinel = Sentinel([('localhost', 26379)], socket_timeout=0.1)\n    >>> sentinel.discover_master('mymaster')\n    ('127.0.0.1', 6379)\n    >>> sentinel.discover_slaves('mymaster')\n    [('127.0.0.1', 6380)]\n\nYou can also create Redis client connections from a Sentinel instance. You can\nconnect to either the master (for write operations) or a slave (for read-only\noperations).\n\n.. code-block:: pycon\n\n    >>> master = sentinel.master_for('mymaster', socket_timeout=0.1)\n    >>> slave = sentinel.slave_for('mymaster', socket_timeout=0.1)\n    >>> master.set('foo', 'bar')\n    >>> slave.get('foo')\n    'bar'\n\nThe master and slave objects are normal Redis instances with their\nconnection pool bound to the Sentinel instance. When a Sentinel backed client\nattempts to establish a connection, it first queries the Sentinel servers to\ndetermine an appropriate host to connect to. If no server is found,\na MasterNotFoundError or SlaveNotFoundError is raised. Both exceptions are\nsubclasses of ConnectionError.\n\nWhen trying to connect to a slave client, the Sentinel connection pool will\niterate over the list of slaves until it finds one that can be connected to.\nIf no slaves can be connected to, a connection will be established with the\nmaster.\n\nSee `Guidelines for Redis clients with support for Redis Sentinel\n<https://redis.io/topics/sentinel-clients>`_ to learn more about Redis Sentinel.\n\nScan Iterators\n^^^^^^^^^^^^^^\n\nThe \\*SCAN commands introduced in Redis 2.8 can be cumbersome to use. While\nthese commands are fully supported, redis-py also exposes the following methods\nthat return Python iterators for convenience: `scan_iter`, `hscan_iter`,\n`sscan_iter` and `zscan_iter`.\n\n.. code-block:: pycon\n\n    >>> for key, value in (('A', '1'), ('B', '2'), ('C', '3')):\n    ...     r.set(key, value)\n    >>> for key in r.scan_iter():\n    ...     print key, r.get(key)\n    A 1\n    B 2\n    C 3\n\nAuthor\n^^^^^^\n\nredis-py is developed and maintained by Andy McCurdy (sedrik@gmail.com).\nIt can be found here: https://github.com/andymccurdy/redis-py\n\nSpecial thanks to:\n\n* Ludovico Magnocavallo, author of the original Python Redis client, from\n  which some of the socket code is still used.\n* Alexander Solovyov for ideas on the generic response callback system.\n* Paul Hubbard for initial packaging support.\n\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis-3.3.11.dist-info/RECORD",
    "content": "redis-3.3.11.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nredis-3.3.11.dist-info/LICENSE,sha256=eQFI2MEvijiycHp0viNDMWutEmmV_1SAGhgbiyMboSQ,1074\r\nredis-3.3.11.dist-info/METADATA,sha256=anmknJnvfwzA0XAltuT0wTjbFncEr5OncX09yGy2_SM,36162\r\nredis-3.3.11.dist-info/RECORD,,\r\nredis-3.3.11.dist-info/WHEEL,sha256=CihQvCnsGZQBGAHLEUMf0IdA4fRduS_NBUTMgCTtvPM,110\r\nredis-3.3.11.dist-info/top_level.txt,sha256=OMAefszlde6ZoOtlM35AWzpRIrwtcqAMHGlRit-w2-4,6\r\nredis/__init__.py,sha256=xQ6zCSUS7Zpd_5H_GVuq86Ne4eFePX7G-vf4rYQbkMQ,1013\r\nredis/__pycache__/__init__.cpython-36.pyc,,\r\nredis/__pycache__/_compat.cpython-36.pyc,,\r\nredis/__pycache__/client.cpython-36.pyc,,\r\nredis/__pycache__/connection.cpython-36.pyc,,\r\nredis/__pycache__/exceptions.cpython-36.pyc,,\r\nredis/__pycache__/lock.cpython-36.pyc,,\r\nredis/__pycache__/sentinel.cpython-36.pyc,,\r\nredis/__pycache__/utils.cpython-36.pyc,,\r\nredis/_compat.py,sha256=BOO1ikpjMJbWOfqxDengdU5C5SnsZDeUHvKg-FjXmN0,5649\r\nredis/client.py,sha256=qEMEMQFlI5fu3xpuDHQpwr9w8IY9N5Y7Wc6SnnkHZ0Y,146267\r\nredis/connection.py,sha256=9nssHQg56x66thkuDMeBeivVJKCM5KUHyvJq4r5p3Us,47742\r\nredis/exceptions.py,sha256=YiguqCg2dCYUlIU7TjbxSLdKmSZYoO_Zhnv6nmHnWxo,992\r\nredis/lock.py,sha256=i4H8Lqb95NkRsAoKAYn71V164dnMAlStKUGja-zZVag,10845\r\nredis/sentinel.py,sha256=ql0-nMsqh_ZCidpWJv6blXSzbq9BPK3rp4LHoVJMZ64,11358\r\nredis/utils.py,sha256=yTyLWUi60KTfw4U4nWhbGvQdNpQb9Wpdf_Qcx_lUJJU,666\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis-3.3.11.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.32.2)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/redis-3.3.11.dist-info/top_level.txt",
    "content": "redis\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/VERSION",
    "content": "1.7.4\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/__init__.py",
    "content": "\"\"\"\nScrapy - a web crawling and web scraping framework written for Python\n\"\"\"\n\n__all__ = ['__version__', 'version_info', 'twisted_version',\n           'Spider', 'Request', 'FormRequest', 'Selector', 'Item', 'Field']\n\n# Scrapy version\nimport pkgutil\n__version__ = pkgutil.get_data(__package__, 'VERSION').decode('ascii').strip()\nversion_info = tuple(int(v) if v.isdigit() else v\n                     for v in __version__.split('.'))\ndel pkgutil\n\n# Check minimum required Python version\nimport sys\nif sys.version_info < (2, 7):\n    print(\"Scrapy %s requires Python 2.7\" % __version__)\n    sys.exit(1)\n\n# Ignore noisy twisted deprecation warnings\nimport warnings\nwarnings.filterwarnings('ignore', category=DeprecationWarning, module='twisted')\ndel warnings\n\n# Apply monkey patches to fix issues in external libraries\nfrom . import _monkeypatches\ndel _monkeypatches\n\nfrom twisted import version as _txv\ntwisted_version = (_txv.major, _txv.minor, _txv.micro)\n\n# Declare top-level shortcuts\nfrom scrapy.spiders import Spider\nfrom scrapy.http import Request, FormRequest\nfrom scrapy.selector import Selector\nfrom scrapy.item import Item, Field\n\ndel sys\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/__main__.py",
    "content": "from scrapy.cmdline import execute\n\nif __name__ == '__main__':\n    execute()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/_monkeypatches.py",
    "content": "import six\nfrom six.moves import copyreg\n\n\nif six.PY2:\n    from urlparse import urlparse\n\n    # workaround for https://bugs.python.org/issue7904 - Python < 2.7\n    if urlparse('s3://bucket/key').netloc != 'bucket':\n        from urlparse import uses_netloc\n        uses_netloc.append('s3')\n\n    # workaround for https://bugs.python.org/issue9374 - Python < 2.7.4\n    if urlparse('s3://bucket/key?key=value').query != 'key=value':\n        from urlparse import uses_query\n        uses_query.append('s3')\n\n\n# Undo what Twisted's perspective broker adds to pickle register\n# to prevent bugs like Twisted#7989 while serializing requests\nimport twisted.persisted.styles  # NOQA\n# Remove only entries with twisted serializers for non-twisted types.\nfor k, v in frozenset(copyreg.dispatch_table.items()):\n    if not str(getattr(k, '__module__', '')).startswith('twisted') \\\n            and str(getattr(v, '__module__', '')).startswith('twisted'):\n        copyreg.dispatch_table.pop(k)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/cmdline.py",
    "content": "from __future__ import print_function\nimport sys\nimport os\nimport optparse\nimport cProfile\nimport inspect\nimport pkg_resources\n\nimport scrapy\nfrom scrapy.crawler import CrawlerProcess\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.exceptions import UsageError\nfrom scrapy.utils.misc import walk_modules\nfrom scrapy.utils.project import inside_project, get_project_settings\nfrom scrapy.utils.python import garbage_collect\nfrom scrapy.settings.deprecated import check_deprecated_settings\n\n\ndef _iter_command_classes(module_name):\n    # TODO: add `name` attribute to commands and and merge this function with\n    # scrapy.utils.spider.iter_spider_classes\n    for module in walk_modules(module_name):\n        for obj in vars(module).values():\n            if inspect.isclass(obj) and \\\n                    issubclass(obj, ScrapyCommand) and \\\n                    obj.__module__ == module.__name__ and \\\n                    not obj == ScrapyCommand:\n                yield obj\n\n\ndef _get_commands_from_module(module, inproject):\n    d = {}\n    for cmd in _iter_command_classes(module):\n        if inproject or not cmd.requires_project:\n            cmdname = cmd.__module__.split('.')[-1]\n            d[cmdname] = cmd()\n    return d\n\n\ndef _get_commands_from_entry_points(inproject, group='scrapy.commands'):\n    cmds = {}\n    for entry_point in pkg_resources.iter_entry_points(group):\n        obj = entry_point.load()\n        if inspect.isclass(obj):\n            cmds[entry_point.name] = obj()\n        else:\n            raise Exception(\"Invalid entry point %s\" % entry_point.name)\n    return cmds\n\n\ndef _get_commands_dict(settings, inproject):\n    cmds = _get_commands_from_module('scrapy.commands', inproject)\n    cmds.update(_get_commands_from_entry_points(inproject))\n    cmds_module = settings['COMMANDS_MODULE']\n    if cmds_module:\n        cmds.update(_get_commands_from_module(cmds_module, inproject))\n    return cmds\n\n\ndef _pop_command_name(argv):\n    i = 0\n    for arg in argv[1:]:\n        if not arg.startswith('-'):\n            del argv[i]\n            return arg\n        i += 1\n\n\ndef _print_header(settings, inproject):\n    if inproject:\n        print(\"Scrapy %s - project: %s\\n\" % (scrapy.__version__, \\\n                                             settings['BOT_NAME']))\n    else:\n        print(\"Scrapy %s - no active project\\n\" % scrapy.__version__)\n\n\ndef _print_commands(settings, inproject):\n    _print_header(settings, inproject)\n    print(\"Usage:\")\n    print(\"  scrapy <command> [options] [args]\\n\")\n    print(\"Available commands:\")\n    cmds = _get_commands_dict(settings, inproject)\n    for cmdname, cmdclass in sorted(cmds.items()):\n        print(\"  %-13s %s\" % (cmdname, cmdclass.short_desc()))\n    if not inproject:\n        print()\n        print(\"  [ more ]      More commands available when run from project directory\")\n    print()\n    print('Use \"scrapy <command> -h\" to see more info about a command')\n\n\ndef _print_unknown_command(settings, cmdname, inproject):\n    _print_header(settings, inproject)\n    print(\"Unknown command: %s\\n\" % cmdname)\n    print('Use \"scrapy\" to see available commands')\n\n\ndef _run_print_help(parser, func, *a, **kw):\n    try:\n        func(*a, **kw)\n    except UsageError as e:\n        if str(e):\n            parser.error(str(e))\n        if e.print_help:\n            parser.print_help()\n        sys.exit(2)\n\n\ndef execute(argv=None, settings=None):\n    if argv is None:\n        argv = sys.argv\n\n    if settings is None:\n        settings = get_project_settings()\n        # set EDITOR from environment if available\n        try:\n            editor = os.environ['EDITOR']\n        except KeyError:\n            pass\n        else:\n            settings['EDITOR'] = editor\n    check_deprecated_settings(settings)\n\n    inproject = inside_project()\n    cmds = _get_commands_dict(settings, inproject)\n    cmdname = _pop_command_name(argv)\n    parser = optparse.OptionParser(formatter=optparse.TitledHelpFormatter(), \\\n                                   conflict_handler='resolve')\n    if not cmdname:\n        _print_commands(settings, inproject)\n        sys.exit(0)\n    elif cmdname not in cmds:\n        _print_unknown_command(settings, cmdname, inproject)\n        sys.exit(2)\n\n    cmd = cmds[cmdname]\n    parser.usage = \"scrapy %s %s\" % (cmdname, cmd.syntax())\n    parser.description = cmd.long_desc()\n    settings.setdict(cmd.default_settings, priority='command')\n    cmd.settings = settings\n    cmd.add_options(parser)\n    opts, args = parser.parse_args(args=argv[1:])\n    _run_print_help(parser, cmd.process_options, args, opts)\n\n    cmd.crawler_process = CrawlerProcess(settings)\n    _run_print_help(parser, _run_command, cmd, args, opts)\n    sys.exit(cmd.exitcode)\n\n\ndef _run_command(cmd, args, opts):\n    if opts.profile:\n        _run_command_profiled(cmd, args, opts)\n    else:\n        cmd.run(args, opts)\n\n\ndef _run_command_profiled(cmd, args, opts):\n    if opts.profile:\n        sys.stderr.write(\"scrapy: writing cProfile stats to %r\\n\" % opts.profile)\n    loc = locals()\n    p = cProfile.Profile()\n    p.runctx('cmd.run(args, opts)', globals(), loc)\n    if opts.profile:\n        p.dump_stats(opts.profile)\n\n\nif __name__ == '__main__':\n    try:\n        execute()\n    finally:\n        # Twisted prints errors in DebugInfo.__del__, but PyPy does not run gc.collect()\n        # on exit: http://doc.pypy.org/en/latest/cpython_differences.html?highlight=gc.collect#differences-related-to-garbage-collection-strategies\n        garbage_collect()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/__init__.py",
    "content": "\"\"\"\nBase class for Scrapy commands\n\"\"\"\nimport os\nfrom optparse import OptionGroup\nfrom twisted.python import failure\n\nfrom scrapy.utils.conf import arglist_to_dict\nfrom scrapy.exceptions import UsageError\n\n\nclass ScrapyCommand(object):\n\n    requires_project = False\n    crawler_process = None\n\n    # default settings to be used for this command instead of global defaults\n    default_settings = {}\n\n    exitcode = 0\n\n    def __init__(self):\n        self.settings = None  # set in scrapy.cmdline\n\n    def set_crawler(self, crawler):\n        assert not hasattr(self, '_crawler'), \"crawler already set\"\n        self._crawler = crawler\n\n    def syntax(self):\n        \"\"\"\n        Command syntax (preferably one-line). Do not include command name.\n        \"\"\"\n        return \"\"\n\n    def short_desc(self):\n        \"\"\"\n        A short description of the command\n        \"\"\"\n        return \"\"\n\n    def long_desc(self):\n        \"\"\"A long description of the command. Return short description when not\n        available. It cannot contain newlines, since contents will be formatted\n        by optparser which removes newlines and wraps text.\n        \"\"\"\n        return self.short_desc()\n\n    def help(self):\n        \"\"\"An extensive help for the command. It will be shown when using the\n        \"help\" command. It can contain newlines, since not post-formatting will\n        be applied to its contents.\n        \"\"\"\n        return self.long_desc()\n\n    def add_options(self, parser):\n        \"\"\"\n        Populate option parse with options available for this command\n        \"\"\"\n        group = OptionGroup(parser, \"Global Options\")\n        group.add_option(\"--logfile\", metavar=\"FILE\",\n            help=\"log file. if omitted stderr will be used\")\n        group.add_option(\"-L\", \"--loglevel\", metavar=\"LEVEL\", default=None,\n            help=\"log level (default: %s)\" % self.settings['LOG_LEVEL'])\n        group.add_option(\"--nolog\", action=\"store_true\",\n            help=\"disable logging completely\")\n        group.add_option(\"--profile\", metavar=\"FILE\", default=None,\n            help=\"write python cProfile stats to FILE\")\n        group.add_option(\"--pidfile\", metavar=\"FILE\",\n            help=\"write process ID to FILE\")\n        group.add_option(\"-s\", \"--set\", action=\"append\", default=[], metavar=\"NAME=VALUE\",\n            help=\"set/override setting (may be repeated)\")\n        group.add_option(\"--pdb\", action=\"store_true\", help=\"enable pdb on failure\")\n\n        parser.add_option_group(group)\n\n    def process_options(self, args, opts):\n        try:\n            self.settings.setdict(arglist_to_dict(opts.set),\n                                  priority='cmdline')\n        except ValueError:\n            raise UsageError(\"Invalid -s value, use -s NAME=VALUE\", print_help=False)\n\n        if opts.logfile:\n            self.settings.set('LOG_ENABLED', True, priority='cmdline')\n            self.settings.set('LOG_FILE', opts.logfile, priority='cmdline')\n\n        if opts.loglevel:\n            self.settings.set('LOG_ENABLED', True, priority='cmdline')\n            self.settings.set('LOG_LEVEL', opts.loglevel, priority='cmdline')\n\n        if opts.nolog:\n            self.settings.set('LOG_ENABLED', False, priority='cmdline')\n\n        if opts.pidfile:\n            with open(opts.pidfile, \"w\") as f:\n                f.write(str(os.getpid()) + os.linesep)\n\n        if opts.pdb:\n            failure.startDebugMode()\n\n    def run(self, args, opts):\n        \"\"\"\n        Entry point for running commands\n        \"\"\"\n        raise NotImplementedError\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/bench.py",
    "content": "import sys\nimport time\nimport subprocess\n\nfrom six.moves.urllib.parse import urlencode\n\nimport scrapy\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.linkextractors import LinkExtractor\n\n\nclass Command(ScrapyCommand):\n\n    default_settings = {\n        'LOG_LEVEL': 'INFO',\n        'LOGSTATS_INTERVAL': 1,\n        'CLOSESPIDER_TIMEOUT': 10,\n    }\n\n    def short_desc(self):\n        return \"Run quick benchmark test\"\n\n    def run(self, args, opts):\n        with _BenchServer():\n            self.crawler_process.crawl(_BenchSpider, total=100000)\n            self.crawler_process.start()\n\n\nclass _BenchServer(object):\n\n    def __enter__(self):\n        from scrapy.utils.test import get_testenv\n        pargs = [sys.executable, '-u', '-m', 'scrapy.utils.benchserver']\n        self.proc = subprocess.Popen(pargs, stdout=subprocess.PIPE,\n                                     env=get_testenv())\n        self.proc.stdout.readline()\n\n    def __exit__(self, exc_type, exc_value, traceback):\n        self.proc.kill()\n        self.proc.wait()\n        time.sleep(0.2)\n\n\nclass _BenchSpider(scrapy.Spider):\n    \"\"\"A spider that follows all links\"\"\"\n    name = 'follow'\n    total = 10000\n    show = 20\n    baseurl = 'http://localhost:8998'\n    link_extractor = LinkExtractor()\n\n    def start_requests(self):\n        qargs = {'total': self.total, 'show': self.show}\n        url = '{}?{}'.format(self.baseurl, urlencode(qargs, doseq=1))\n        return [scrapy.Request(url, dont_filter=True)]\n\n    def parse(self, response):\n        for link in self.link_extractor.extract_links(response):\n            yield scrapy.Request(link.url, callback=self.parse)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/check.py",
    "content": "from __future__ import print_function\nimport time\nimport sys\nfrom collections import defaultdict\nfrom unittest import TextTestRunner, TextTestResult as _TextTestResult\n\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.contracts import ContractsManager\nfrom scrapy.utils.misc import load_object, set_environ\nfrom scrapy.utils.conf import build_component_list\n\n\nclass TextTestResult(_TextTestResult):\n    def printSummary(self, start, stop):\n        write = self.stream.write\n        writeln = self.stream.writeln\n\n        run = self.testsRun\n        plural = \"s\" if run != 1 else \"\"\n\n        writeln(self.separator2)\n        writeln(\"Ran %d contract%s in %.3fs\" % (run, plural, stop - start))\n        writeln()\n\n        infos = []\n        if not self.wasSuccessful():\n            write(\"FAILED\")\n            failed, errored = map(len, (self.failures, self.errors))\n            if failed:\n                infos.append(\"failures=%d\" % failed)\n            if errored:\n                infos.append(\"errors=%d\" % errored)\n        else:\n            write(\"OK\")\n\n        if infos:\n            writeln(\" (%s)\" % (\", \".join(infos),))\n        else:\n            write(\"\\n\")\n\n\nclass Command(ScrapyCommand):\n    requires_project = True\n    default_settings = {'LOG_ENABLED': False}\n\n    def syntax(self):\n        return \"[options] <spider>\"\n\n    def short_desc(self):\n        return \"Check spider contracts\"\n\n    def add_options(self, parser):\n        ScrapyCommand.add_options(self, parser)\n        parser.add_option(\"-l\", \"--list\", dest=\"list\", action=\"store_true\",\n                          help=\"only list contracts, without checking them\")\n        parser.add_option(\"-v\", \"--verbose\", dest=\"verbose\", default=False, action='store_true',\n                          help=\"print contract tests for all spiders\")\n\n    def run(self, args, opts):\n        # load contracts\n        contracts = build_component_list(self.settings.getwithbase('SPIDER_CONTRACTS'))\n        conman = ContractsManager(load_object(c) for c in contracts)\n        runner = TextTestRunner(verbosity=2 if opts.verbose else 1)\n        result = TextTestResult(runner.stream, runner.descriptions, runner.verbosity)\n\n        # contract requests\n        contract_reqs = defaultdict(list)\n\n        spider_loader = self.crawler_process.spider_loader\n\n        with set_environ(SCRAPY_CHECK='true'):\n            for spidername in args or spider_loader.list():\n                spidercls = spider_loader.load(spidername)\n                spidercls.start_requests = lambda s: conman.from_spider(s, result)\n\n                tested_methods = conman.tested_methods_from_spidercls(spidercls)\n                if opts.list:\n                    for method in tested_methods:\n                        contract_reqs[spidercls.name].append(method)\n                elif tested_methods:\n                    self.crawler_process.crawl(spidercls)\n\n        # start checks\n        if opts.list:\n            for spider, methods in sorted(contract_reqs.items()):\n                if not methods and not opts.verbose:\n                    continue\n                print(spider)\n                for method in sorted(methods):\n                    print('  * %s' % method)\n        else:\n            start = time.time()\n            self.crawler_process.start()\n            stop = time.time()\n\n            result.printErrors()\n            result.printSummary(start, stop)\n            self.exitcode = int(not result.wasSuccessful())\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/crawl.py",
    "content": "import os\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.utils.conf import arglist_to_dict\nfrom scrapy.utils.python import without_none_values\nfrom scrapy.exceptions import UsageError\n\n\nclass Command(ScrapyCommand):\n\n    requires_project = True\n\n    def syntax(self):\n        return \"[options] <spider>\"\n\n    def short_desc(self):\n        return \"Run a spider\"\n\n    def add_options(self, parser):\n        ScrapyCommand.add_options(self, parser)\n        parser.add_option(\"-a\", dest=\"spargs\", action=\"append\", default=[], metavar=\"NAME=VALUE\",\n                          help=\"set spider argument (may be repeated)\")\n        parser.add_option(\"-o\", \"--output\", metavar=\"FILE\",\n                          help=\"dump scraped items into FILE (use - for stdout)\")\n        parser.add_option(\"-t\", \"--output-format\", metavar=\"FORMAT\",\n                          help=\"format to use for dumping items with -o\")\n\n    def process_options(self, args, opts):\n        ScrapyCommand.process_options(self, args, opts)\n        try:\n            opts.spargs = arglist_to_dict(opts.spargs)\n        except ValueError:\n            raise UsageError(\"Invalid -a value, use -a NAME=VALUE\", print_help=False)\n        if opts.output:\n            if opts.output == '-':\n                self.settings.set('FEED_URI', 'stdout:', priority='cmdline')\n            else:\n                self.settings.set('FEED_URI', opts.output, priority='cmdline')\n            feed_exporters = without_none_values(\n                self.settings.getwithbase('FEED_EXPORTERS'))\n            valid_output_formats = feed_exporters.keys()\n            if not opts.output_format:\n                opts.output_format = os.path.splitext(opts.output)[1].replace(\".\", \"\")\n            if opts.output_format not in valid_output_formats:\n                raise UsageError(\"Unrecognized output format '%s', set one\"\n                                 \" using the '-t' switch or as a file extension\"\n                                 \" from the supported list %s\" % (opts.output_format,\n                                                                  tuple(valid_output_formats)))\n            self.settings.set('FEED_FORMAT', opts.output_format, priority='cmdline')\n\n    def run(self, args, opts):\n        if len(args) < 1:\n            raise UsageError()\n        elif len(args) > 1:\n            raise UsageError(\"running 'scrapy crawl' with more than one spider is no longer supported\")\n        spname = args[0]\n\n        self.crawler_process.crawl(spname, **opts.spargs)\n        self.crawler_process.start()\n\n        if self.crawler_process.bootstrap_failed:\n            self.exitcode = 1\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/edit.py",
    "content": "import sys\nimport os\n\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.exceptions import UsageError\n\n\nclass Command(ScrapyCommand):\n\n    requires_project = True\n    default_settings = {'LOG_ENABLED': False}\n\n    def syntax(self):\n        return \"<spider>\"\n\n    def short_desc(self):\n        return \"Edit spider\"\n\n    def long_desc(self):\n        return (\"Edit a spider using the editor defined in the EDITOR environment\"\n                \" variable or else the EDITOR setting\")\n\n    def _err(self, msg):\n        sys.stderr.write(msg + os.linesep)\n        self.exitcode = 1\n\n    def run(self, args, opts):\n        if len(args) != 1:\n            raise UsageError()\n\n        editor = self.settings['EDITOR']\n        try:\n            spidercls = self.crawler_process.spider_loader.load(args[0])\n        except KeyError:\n            return self._err(\"Spider not found: %s\" % args[0])\n\n        sfile = sys.modules[spidercls.__module__].__file__\n        sfile = sfile.replace('.pyc', '.py')\n        self.exitcode = os.system('%s \"%s\"' % (editor, sfile))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/fetch.py",
    "content": "from __future__ import print_function\nimport sys, six\nfrom w3lib.url import is_url\n\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.http import Request\nfrom scrapy.exceptions import UsageError\nfrom scrapy.utils.datatypes import SequenceExclude\nfrom scrapy.utils.spider import spidercls_for_request, DefaultSpider\n\nclass Command(ScrapyCommand):\n\n    requires_project = False\n\n    def syntax(self):\n        return \"[options] <url>\"\n\n    def short_desc(self):\n        return \"Fetch a URL using the Scrapy downloader\"\n\n    def long_desc(self):\n        return \"Fetch a URL using the Scrapy downloader and print its content \" \\\n            \"to stdout. You may want to use --nolog to disable logging\"\n\n    def add_options(self, parser):\n        ScrapyCommand.add_options(self, parser)\n        parser.add_option(\"--spider\", dest=\"spider\",\n            help=\"use this spider\")\n        parser.add_option(\"--headers\", dest=\"headers\", action=\"store_true\", \\\n            help=\"print response HTTP headers instead of body\")\n        parser.add_option(\"--no-redirect\", dest=\"no_redirect\", action=\"store_true\", \\\n            default=False, help=\"do not handle HTTP 3xx status codes and print response as-is\")\n\n    def _print_headers(self, headers, prefix):\n        for key, values in headers.items():\n            for value in values:\n                self._print_bytes(prefix + b' ' + key + b': ' + value)\n\n    def _print_response(self, response, opts):\n        if opts.headers:\n            self._print_headers(response.request.headers, b'>')\n            print('>')\n            self._print_headers(response.headers, b'<')\n        else:\n            self._print_bytes(response.body)\n\n    def _print_bytes(self, bytes_):\n        bytes_writer = sys.stdout if six.PY2 else sys.stdout.buffer\n        bytes_writer.write(bytes_ + b'\\n')\n\n    def run(self, args, opts):\n        if len(args) != 1 or not is_url(args[0]):\n            raise UsageError()\n        cb = lambda x: self._print_response(x, opts)\n        request = Request(args[0], callback=cb, dont_filter=True)\n        # by default, let the framework handle redirects,\n        # i.e. command handles all codes expect 3xx\n        if not opts.no_redirect:\n            request.meta['handle_httpstatus_list'] = SequenceExclude(range(300, 400))\n        else:\n            request.meta['handle_httpstatus_all'] = True\n\n        spidercls = DefaultSpider\n        spider_loader = self.crawler_process.spider_loader\n        if opts.spider:\n            spidercls = spider_loader.load(opts.spider)\n        else:\n            spidercls = spidercls_for_request(spider_loader, request, spidercls)\n        self.crawler_process.crawl(spidercls, start_requests=lambda: [request])\n        self.crawler_process.start()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/genspider.py",
    "content": "from __future__ import print_function\nimport os\nimport shutil\nimport string\n\nfrom importlib import import_module\nfrom os.path import join, dirname, abspath, exists, splitext\n\nimport scrapy\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.utils.template import render_templatefile, string_camelcase\nfrom scrapy.exceptions import UsageError\n\n\ndef sanitize_module_name(module_name):\n    \"\"\"Sanitize the given module name, by replacing dashes and points\n    with underscores and prefixing it with a letter if it doesn't start\n    with one\n    \"\"\"\n    module_name = module_name.replace('-', '_').replace('.', '_')\n    if module_name[0] not in string.ascii_letters:\n        module_name = \"a\" + module_name\n    return module_name\n\n\nclass Command(ScrapyCommand):\n\n    requires_project = False\n    default_settings = {'LOG_ENABLED': False}\n\n    def syntax(self):\n        return \"[options] <name> <domain>\"\n\n    def short_desc(self):\n        return \"Generate new spider using pre-defined templates\"\n\n    def add_options(self, parser):\n        ScrapyCommand.add_options(self, parser)\n        parser.add_option(\"-l\", \"--list\", dest=\"list\", action=\"store_true\",\n            help=\"List available templates\")\n        parser.add_option(\"-e\", \"--edit\", dest=\"edit\", action=\"store_true\",\n            help=\"Edit spider after creating it\")\n        parser.add_option(\"-d\", \"--dump\", dest=\"dump\", metavar=\"TEMPLATE\",\n            help=\"Dump template to standard output\")\n        parser.add_option(\"-t\", \"--template\", dest=\"template\", default=\"basic\",\n            help=\"Uses a custom template.\")\n        parser.add_option(\"--force\", dest=\"force\", action=\"store_true\",\n            help=\"If the spider already exists, overwrite it with the template\")\n\n    def run(self, args, opts):\n        if opts.list:\n            self._list_templates()\n            return\n        if opts.dump:\n            template_file = self._find_template(opts.dump)\n            if template_file:\n                with open(template_file, \"r\") as f:\n                    print(f.read())\n            return\n        if len(args) != 2:\n            raise UsageError()\n\n        name, domain = args[0:2]\n        module = sanitize_module_name(name)\n\n        if self.settings.get('BOT_NAME') == module:\n            print(\"Cannot create a spider with the same name as your project\")\n            return\n\n        try:\n            spidercls = self.crawler_process.spider_loader.load(name)\n        except KeyError:\n            pass\n        else:\n            # if spider already exists and not --force then halt\n            if not opts.force:\n                print(\"Spider %r already exists in module:\" % name)\n                print(\"  %s\" % spidercls.__module__)\n                return\n        template_file = self._find_template(opts.template)\n        if template_file:\n            self._genspider(module, name, domain, opts.template, template_file)\n            if opts.edit:\n                self.exitcode = os.system('scrapy edit \"%s\"' % name)\n\n    def _genspider(self, module, name, domain, template_name, template_file):\n        \"\"\"Generate the spider module, based on the given template\"\"\"\n        tvars = {\n            'project_name': self.settings.get('BOT_NAME'),\n            'ProjectName': string_camelcase(self.settings.get('BOT_NAME')),\n            'module': module,\n            'name': name,\n            'domain': domain,\n            'classname': '%sSpider' % ''.join(s.capitalize() \\\n                for s in module.split('_'))\n        }\n        if self.settings.get('NEWSPIDER_MODULE'):\n            spiders_module = import_module(self.settings['NEWSPIDER_MODULE'])\n            spiders_dir = abspath(dirname(spiders_module.__file__))\n        else:\n            spiders_module = None\n            spiders_dir = \".\"\n        spider_file = \"%s.py\" % join(spiders_dir, module)\n        shutil.copyfile(template_file, spider_file)\n        render_templatefile(spider_file, **tvars)\n        print(\"Created spider %r using template %r \" % (name, \\\n            template_name), end=('' if spiders_module else '\\n'))\n        if spiders_module:\n            print(\"in module:\\n  %s.%s\" % (spiders_module.__name__, module))\n\n    def _find_template(self, template):\n        template_file = join(self.templates_dir, '%s.tmpl' % template)\n        if exists(template_file):\n            return template_file\n        print(\"Unable to find template: %s\\n\" % template)\n        print('Use \"scrapy genspider --list\" to see all available templates.')\n\n    def _list_templates(self):\n        print(\"Available templates:\")\n        for filename in sorted(os.listdir(self.templates_dir)):\n            if filename.endswith('.tmpl'):\n                print(\"  %s\" % splitext(filename)[0])\n\n    @property\n    def templates_dir(self):\n        _templates_base_dir = self.settings['TEMPLATES_DIR'] or \\\n            join(scrapy.__path__[0], 'templates')\n        return join(_templates_base_dir, 'spiders')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/list.py",
    "content": "from __future__ import print_function\nfrom scrapy.commands import ScrapyCommand\n\nclass Command(ScrapyCommand):\n\n    requires_project = True\n    default_settings = {'LOG_ENABLED': False}\n\n    def short_desc(self):\n        return \"List available spiders\"\n\n    def run(self, args, opts):\n        for s in sorted(self.crawler_process.spider_loader.list()):\n            print(s)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/parse.py",
    "content": "from __future__ import print_function\nimport json\nimport logging\n\nfrom w3lib.url import is_url\n\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.http import Request\nfrom scrapy.item import BaseItem\nfrom scrapy.utils import display\nfrom scrapy.utils.conf import arglist_to_dict\nfrom scrapy.utils.spider import iterate_spider_output, spidercls_for_request\nfrom scrapy.exceptions import UsageError\n\nlogger = logging.getLogger(__name__)\n\n\nclass Command(ScrapyCommand):\n\n    requires_project = True\n\n    spider = None\n    items = {}\n    requests = {}\n\n    first_response = None\n\n    def syntax(self):\n        return \"[options] <url>\"\n\n    def short_desc(self):\n        return \"Parse URL (using its spider) and print the results\"\n\n    def add_options(self, parser):\n        ScrapyCommand.add_options(self, parser)\n        parser.add_option(\"--spider\", dest=\"spider\", default=None,\n            help=\"use this spider without looking for one\")\n        parser.add_option(\"-a\", dest=\"spargs\", action=\"append\", default=[], metavar=\"NAME=VALUE\",\n            help=\"set spider argument (may be repeated)\")\n        parser.add_option(\"--pipelines\", action=\"store_true\",\n            help=\"process items through pipelines\")\n        parser.add_option(\"--nolinks\", dest=\"nolinks\", action=\"store_true\",\n            help=\"don't show links to follow (extracted requests)\")\n        parser.add_option(\"--noitems\", dest=\"noitems\", action=\"store_true\",\n            help=\"don't show scraped items\")\n        parser.add_option(\"--nocolour\", dest=\"nocolour\", action=\"store_true\",\n            help=\"avoid using pygments to colorize the output\")\n        parser.add_option(\"-r\", \"--rules\", dest=\"rules\", action=\"store_true\",\n            help=\"use CrawlSpider rules to discover the callback\")\n        parser.add_option(\"-c\", \"--callback\", dest=\"callback\",\n            help=\"use this callback for parsing, instead looking for a callback\")\n        parser.add_option(\"-m\", \"--meta\", dest=\"meta\",\n            help=\"inject extra meta into the Request, it must be a valid raw json string\")\n        parser.add_option(\"--cbkwargs\", dest=\"cbkwargs\",\n            help=\"inject extra callback kwargs into the Request, it must be a valid raw json string\")\n        parser.add_option(\"-d\", \"--depth\", dest=\"depth\", type=\"int\", default=1,\n            help=\"maximum depth for parsing requests [default: %default]\")\n        parser.add_option(\"-v\", \"--verbose\", dest=\"verbose\", action=\"store_true\",\n            help=\"print each depth level one by one\")\n\n    @property\n    def max_level(self):\n        levels = list(self.items.keys()) + list(self.requests.keys())\n        if not levels:\n            return 0\n        return max(levels)\n\n    def add_items(self, lvl, new_items):\n        old_items = self.items.get(lvl, [])\n        self.items[lvl] = old_items + new_items\n\n    def add_requests(self, lvl, new_reqs):\n        old_reqs = self.requests.get(lvl, [])\n        self.requests[lvl] = old_reqs + new_reqs\n\n    def print_items(self, lvl=None, colour=True):\n        if lvl is None:\n            items = [item for lst in self.items.values() for item in lst]\n        else:\n            items = self.items.get(lvl, [])\n\n        print(\"# Scraped Items \", \"-\"*60)\n        display.pprint([dict(x) for x in items], colorize=colour)\n\n    def print_requests(self, lvl=None, colour=True):\n        if lvl is None:\n            levels = list(self.requests.keys())\n            if levels:\n                requests = self.requests[max(levels)]\n            else:\n                requests = []\n        else:\n            requests = self.requests.get(lvl, [])\n\n        print(\"# Requests \", \"-\"*65)\n        display.pprint(requests, colorize=colour)\n\n    def print_results(self, opts):\n        colour = not opts.nocolour\n\n        if opts.verbose:\n            for level in range(1, self.max_level+1):\n                print('\\n>>> DEPTH LEVEL: %s <<<' % level)\n                if not opts.noitems:\n                    self.print_items(level, colour)\n                if not opts.nolinks:\n                    self.print_requests(level, colour)\n        else:\n            print('\\n>>> STATUS DEPTH LEVEL %s <<<' % self.max_level)\n            if not opts.noitems:\n                self.print_items(colour=colour)\n            if not opts.nolinks:\n                self.print_requests(colour=colour)\n\n    def run_callback(self, response, callback, cb_kwargs=None):\n        cb_kwargs = cb_kwargs or {}\n        items, requests = [], []\n\n        for x in iterate_spider_output(callback(response, **cb_kwargs)):\n            if isinstance(x, (BaseItem, dict)):\n                items.append(x)\n            elif isinstance(x, Request):\n                requests.append(x)\n        return items, requests\n\n    def get_callback_from_rules(self, spider, response):\n        if getattr(spider, 'rules', None):\n            for rule in spider.rules:\n                if rule.link_extractor.matches(response.url):\n                    return rule.callback or \"parse\"\n        else:\n            logger.error('No CrawlSpider rules found in spider %(spider)r, '\n                         'please specify a callback to use for parsing',\n                         {'spider': spider.name})\n\n    def set_spidercls(self, url, opts):\n        spider_loader = self.crawler_process.spider_loader\n        if opts.spider:\n            try:\n                self.spidercls = spider_loader.load(opts.spider)\n            except KeyError:\n                logger.error('Unable to find spider: %(spider)s',\n                             {'spider': opts.spider})\n        else:\n            self.spidercls = spidercls_for_request(spider_loader, Request(url))\n            if not self.spidercls:\n                logger.error('Unable to find spider for: %(url)s', {'url': url})\n\n        # Request requires callback argument as callable or None, not string\n        request = Request(url, None)\n        _start_requests = lambda s: [self.prepare_request(s, request, opts)]\n        self.spidercls.start_requests = _start_requests\n\n    def start_parsing(self, url, opts):\n        self.crawler_process.crawl(self.spidercls, **opts.spargs)\n        self.pcrawler = list(self.crawler_process.crawlers)[0]\n        self.crawler_process.start()\n\n        if not self.first_response:\n            logger.error('No response downloaded for: %(url)s',\n                         {'url': url})\n\n    def prepare_request(self, spider, request, opts):\n        def callback(response, **cb_kwargs):\n            # memorize first request\n            if not self.first_response:\n                self.first_response = response\n\n            # determine real callback\n            cb = response.meta['_callback']\n            if not cb:\n                if opts.callback:\n                    cb = opts.callback\n                elif opts.rules and self.first_response == response:\n                    cb = self.get_callback_from_rules(spider, response)\n\n                    if not cb:\n                        logger.error('Cannot find a rule that matches %(url)r in spider: %(spider)s',\n                                     {'url': response.url, 'spider': spider.name})\n                        return\n                else:\n                    cb = 'parse'\n\n            if not callable(cb):\n                cb_method = getattr(spider, cb, None)\n                if callable(cb_method):\n                    cb = cb_method\n                else:\n                    logger.error('Cannot find callback %(callback)r in spider: %(spider)s',\n                                 {'callback': cb, 'spider': spider.name})\n                    return\n\n            # parse items and requests\n            depth = response.meta['_depth']\n\n            items, requests = self.run_callback(response, cb, cb_kwargs)\n            if opts.pipelines:\n                itemproc = self.pcrawler.engine.scraper.itemproc\n                for item in items:\n                    itemproc.process_item(item, spider)\n            self.add_items(depth, items)\n            self.add_requests(depth, requests)\n\n            if depth < opts.depth:\n                for req in requests:\n                    req.meta['_depth'] = depth + 1\n                    req.meta['_callback'] = req.callback\n                    req.callback = callback\n                return requests\n\n        # update request meta if any extra meta was passed through the --meta/-m opts.\n        if opts.meta:\n            request.meta.update(opts.meta)\n\n        # update cb_kwargs if any extra values were was passed through the --cbkwargs option.\n        if opts.cbkwargs:\n            request.cb_kwargs.update(opts.cbkwargs)\n\n        request.meta['_depth'] = 1\n        request.meta['_callback'] = request.callback\n        request.callback = callback\n        return request\n\n    def process_options(self, args, opts):\n        ScrapyCommand.process_options(self, args, opts)\n\n        self.process_spider_arguments(opts)\n        self.process_request_meta(opts)\n        self.process_request_cb_kwargs(opts)\n\n    def process_spider_arguments(self, opts):\n        try:\n            opts.spargs = arglist_to_dict(opts.spargs)\n        except ValueError:\n            raise UsageError(\"Invalid -a value, use -a NAME=VALUE\", print_help=False)\n\n    def process_request_meta(self, opts):\n        if opts.meta:\n            try:\n                opts.meta = json.loads(opts.meta)\n            except ValueError:\n                raise UsageError(\"Invalid -m/--meta value, pass a valid json string to -m or --meta. \"\n                                 \"Example: --meta='{\\\"foo\\\" : \\\"bar\\\"}'\", print_help=False)\n\n    def process_request_cb_kwargs(self, opts):\n        if opts.cbkwargs:\n            try:\n                opts.cbkwargs = json.loads(opts.cbkwargs)\n            except ValueError:\n                raise UsageError(\"Invalid --cbkwargs value, pass a valid json string to --cbkwargs. \"\n                                 \"Example: --cbkwargs='{\\\"foo\\\" : \\\"bar\\\"}'\", print_help=False)\n\n    def run(self, args, opts):\n        # parse arguments\n        if not len(args) == 1 or not is_url(args[0]):\n            raise UsageError()\n        else:\n            url = args[0]\n\n        # prepare spidercls\n        self.set_spidercls(url, opts)\n\n        if self.spidercls and opts.depth > 0:\n            self.start_parsing(url, opts)\n            self.print_results(opts)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/runspider.py",
    "content": "import sys\nimport os\nfrom importlib import import_module\n\nfrom scrapy.utils.spider import iter_spider_classes\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.exceptions import UsageError\nfrom scrapy.utils.conf import arglist_to_dict\nfrom scrapy.utils.python import without_none_values\n\n\ndef _import_file(filepath):\n    abspath = os.path.abspath(filepath)\n    dirname, file = os.path.split(abspath)\n    fname, fext = os.path.splitext(file)\n    if fext != '.py':\n        raise ValueError(\"Not a Python source file: %s\" % abspath)\n    if dirname:\n        sys.path = [dirname] + sys.path\n    try:\n        module = import_module(fname)\n    finally:\n        if dirname:\n            sys.path.pop(0)\n    return module\n\n\nclass Command(ScrapyCommand):\n\n    requires_project = False\n    default_settings = {'SPIDER_LOADER_WARN_ONLY': True}\n\n    def syntax(self):\n        return \"[options] <spider_file>\"\n\n    def short_desc(self):\n        return \"Run a self-contained spider (without creating a project)\"\n\n    def long_desc(self):\n        return \"Run the spider defined in the given file\"\n\n    def add_options(self, parser):\n        ScrapyCommand.add_options(self, parser)\n        parser.add_option(\"-a\", dest=\"spargs\", action=\"append\", default=[], metavar=\"NAME=VALUE\",\n                          help=\"set spider argument (may be repeated)\")\n        parser.add_option(\"-o\", \"--output\", metavar=\"FILE\",\n                          help=\"dump scraped items into FILE (use - for stdout)\")\n        parser.add_option(\"-t\", \"--output-format\", metavar=\"FORMAT\",\n                          help=\"format to use for dumping items with -o\")\n\n    def process_options(self, args, opts):\n        ScrapyCommand.process_options(self, args, opts)\n        try:\n            opts.spargs = arglist_to_dict(opts.spargs)\n        except ValueError:\n            raise UsageError(\"Invalid -a value, use -a NAME=VALUE\", print_help=False)\n        if opts.output:\n            if opts.output == '-':\n                self.settings.set('FEED_URI', 'stdout:', priority='cmdline')\n            else:\n                self.settings.set('FEED_URI', opts.output, priority='cmdline')\n            feed_exporters = without_none_values(self.settings.getwithbase('FEED_EXPORTERS'))\n            valid_output_formats = feed_exporters.keys()\n            if not opts.output_format:\n                opts.output_format = os.path.splitext(opts.output)[1].replace(\".\", \"\")\n            if opts.output_format not in valid_output_formats:\n                raise UsageError(\"Unrecognized output format '%s', set one\"\n                                 \" using the '-t' switch or as a file extension\"\n                                 \" from the supported list %s\" % (opts.output_format,\n                                                                  tuple(valid_output_formats)))\n            self.settings.set('FEED_FORMAT', opts.output_format, priority='cmdline')\n\n    def run(self, args, opts):\n        if len(args) != 1:\n            raise UsageError()\n        filename = args[0]\n        if not os.path.exists(filename):\n            raise UsageError(\"File not found: %s\\n\" % filename)\n        try:\n            module = _import_file(filename)\n        except (ImportError, ValueError) as e:\n            raise UsageError(\"Unable to load %r: %s\\n\" % (filename, e))\n        spclasses = list(iter_spider_classes(module))\n        if not spclasses:\n            raise UsageError(\"No spider found in file: %s\\n\" % filename)\n        spidercls = spclasses.pop()\n\n        self.crawler_process.crawl(spidercls, **opts.spargs)\n        self.crawler_process.start()\n\n        if self.crawler_process.bootstrap_failed:\n            self.exitcode = 1\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/settings.py",
    "content": "from __future__ import print_function\nimport json\n\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.settings import BaseSettings\n\nclass Command(ScrapyCommand):\n\n    requires_project = False\n    default_settings = {'LOG_ENABLED': False,\n                        'SPIDER_LOADER_WARN_ONLY': True}\n\n    def syntax(self):\n        return \"[options]\"\n\n    def short_desc(self):\n        return \"Get settings values\"\n\n    def add_options(self, parser):\n        ScrapyCommand.add_options(self, parser)\n        parser.add_option(\"--get\", dest=\"get\", metavar=\"SETTING\",\n            help=\"print raw setting value\")\n        parser.add_option(\"--getbool\", dest=\"getbool\", metavar=\"SETTING\",\n            help=\"print setting value, interpreted as a boolean\")\n        parser.add_option(\"--getint\", dest=\"getint\", metavar=\"SETTING\",\n            help=\"print setting value, interpreted as an integer\")\n        parser.add_option(\"--getfloat\", dest=\"getfloat\", metavar=\"SETTING\",\n            help=\"print setting value, interpreted as a float\")\n        parser.add_option(\"--getlist\", dest=\"getlist\", metavar=\"SETTING\",\n            help=\"print setting value, interpreted as a list\")\n\n    def run(self, args, opts):\n        settings = self.crawler_process.settings\n        if opts.get:\n            s = settings.get(opts.get)\n            if isinstance(s, BaseSettings):\n                print(json.dumps(s.copy_to_dict()))\n            else:\n                print(s)\n        elif opts.getbool:\n            print(settings.getbool(opts.getbool))\n        elif opts.getint:\n            print(settings.getint(opts.getint))\n        elif opts.getfloat:\n            print(settings.getfloat(opts.getfloat))\n        elif opts.getlist:\n            print(settings.getlist(opts.getlist))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/shell.py",
    "content": "\"\"\"\nScrapy Shell\n\nSee documentation in docs/topics/shell.rst\n\"\"\"\nfrom threading import Thread\n\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.shell import Shell\nfrom scrapy.http import Request\nfrom scrapy.utils.spider import spidercls_for_request, DefaultSpider\nfrom scrapy.utils.url import guess_scheme\n\n\nclass Command(ScrapyCommand):\n\n    requires_project = False\n    default_settings = {\n        'KEEP_ALIVE': True,\n        'LOGSTATS_INTERVAL': 0,\n        'DUPEFILTER_CLASS': 'scrapy.dupefilters.BaseDupeFilter',\n    }\n\n    def syntax(self):\n        return \"[url|file]\"\n\n    def short_desc(self):\n        return \"Interactive scraping console\"\n\n    def long_desc(self):\n        return (\"Interactive console for scraping the given url or file. \"\n                \"Use ./file.html syntax or full path for local file.\")\n\n    def add_options(self, parser):\n        ScrapyCommand.add_options(self, parser)\n        parser.add_option(\"-c\", dest=\"code\",\n            help=\"evaluate the code in the shell, print the result and exit\")\n        parser.add_option(\"--spider\", dest=\"spider\",\n            help=\"use this spider\")\n        parser.add_option(\"--no-redirect\", dest=\"no_redirect\", action=\"store_true\", \\\n            default=False, help=\"do not handle HTTP 3xx status codes and print response as-is\")\n\n    def update_vars(self, vars):\n        \"\"\"You can use this function to update the Scrapy objects that will be\n        available in the shell\n        \"\"\"\n        pass\n\n    def run(self, args, opts):\n        url = args[0] if args else None\n        if url:\n            # first argument may be a local file\n            url = guess_scheme(url)\n\n        spider_loader = self.crawler_process.spider_loader\n\n        spidercls = DefaultSpider\n        if opts.spider:\n            spidercls = spider_loader.load(opts.spider)\n        elif url:\n            spidercls = spidercls_for_request(spider_loader, Request(url),\n                                              spidercls, log_multiple=True)\n\n        # The crawler is created this way since the Shell manually handles the\n        # crawling engine, so the set up in the crawl method won't work\n        crawler = self.crawler_process._create_crawler(spidercls)\n        # The Shell class needs a persistent engine in the crawler\n        crawler.engine = crawler._create_engine()\n        crawler.engine.start()\n\n        self._start_crawler_thread()\n\n        shell = Shell(crawler, update_vars=self.update_vars, code=opts.code)\n        shell.start(url=url, redirect=not opts.no_redirect)\n\n    def _start_crawler_thread(self):\n        t = Thread(target=self.crawler_process.start,\n                   kwargs={'stop_after_crawl': False})\n        t.daemon = True\n        t.start()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/startproject.py",
    "content": "from __future__ import print_function\nimport re\nimport os\nimport string\nfrom importlib import import_module\nfrom os.path import join, exists, abspath\nfrom shutil import ignore_patterns, move, copy2, copystat\n\nimport scrapy\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.utils.template import render_templatefile, string_camelcase\nfrom scrapy.exceptions import UsageError\n\n\nTEMPLATES_TO_RENDER = (\n    ('scrapy.cfg',),\n    ('${project_name}', 'settings.py.tmpl'),\n    ('${project_name}', 'items.py.tmpl'),\n    ('${project_name}', 'pipelines.py.tmpl'),\n    ('${project_name}', 'middlewares.py.tmpl'),\n)\n\nIGNORE = ignore_patterns('*.pyc', '.svn')\n\n\nclass Command(ScrapyCommand):\n\n    requires_project = False\n    default_settings = {'LOG_ENABLED': False,\n                        'SPIDER_LOADER_WARN_ONLY': True}\n\n    def syntax(self):\n        return \"<project_name> [project_dir]\"\n\n    def short_desc(self):\n        return \"Create new project\"\n\n    def _is_valid_name(self, project_name):\n        def _module_exists(module_name):\n            try:\n                import_module(module_name)\n                return True\n            except ImportError:\n                return False\n\n        if not re.search(r'^[_a-zA-Z]\\w*$', project_name):\n            print('Error: Project names must begin with a letter and contain'\\\n                    ' only\\nletters, numbers and underscores')\n        elif _module_exists(project_name):\n            print('Error: Module %r already exists' % project_name)\n        else:\n            return True\n        return False\n\n    def _copytree(self, src, dst):\n        \"\"\"\n        Since the original function always creates the directory, to resolve\n        the issue a new function had to be created. It's a simple copy and\n        was reduced for this case.\n\n        More info at:\n        https://github.com/scrapy/scrapy/pull/2005\n        \"\"\"\n        ignore = IGNORE\n        names = os.listdir(src)\n        ignored_names = ignore(src, names)\n\n        if not os.path.exists(dst):\n            os.makedirs(dst)\n\n        for name in names:\n            if name in ignored_names:\n                continue\n\n            srcname = os.path.join(src, name)\n            dstname = os.path.join(dst, name)\n            if os.path.isdir(srcname):\n                self._copytree(srcname, dstname)\n            else:\n                copy2(srcname, dstname)\n        copystat(src, dst)\n\n    def run(self, args, opts):\n        if len(args) not in (1, 2):\n            raise UsageError()\n\n        project_name = args[0]\n        project_dir = args[0]\n\n        if len(args) == 2:\n            project_dir = args[1]\n\n        if exists(join(project_dir, 'scrapy.cfg')):\n            self.exitcode = 1\n            print('Error: scrapy.cfg already exists in %s' % abspath(project_dir))\n            return\n\n        if not self._is_valid_name(project_name):\n            self.exitcode = 1\n            return\n\n        self._copytree(self.templates_dir, abspath(project_dir))\n        move(join(project_dir, 'module'), join(project_dir, project_name))\n        for paths in TEMPLATES_TO_RENDER:\n            path = join(*paths)\n            tplfile = join(project_dir,\n                string.Template(path).substitute(project_name=project_name))\n            render_templatefile(tplfile, project_name=project_name,\n                ProjectName=string_camelcase(project_name))\n        print(\"New Scrapy project '%s', using template directory '%s', \"\n              \"created in:\" % (project_name, self.templates_dir))\n        print(\"    %s\\n\" % abspath(project_dir))\n        print(\"You can start your first spider with:\")\n        print(\"    cd %s\" % project_dir)\n        print(\"    scrapy genspider example example.com\")\n\n    @property\n    def templates_dir(self):\n        _templates_base_dir = self.settings['TEMPLATES_DIR'] or \\\n            join(scrapy.__path__[0], 'templates')\n        return join(_templates_base_dir, 'project')\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/version.py",
    "content": "from __future__ import print_function\n\nimport scrapy\nfrom scrapy.commands import ScrapyCommand\nfrom scrapy.utils.versions import scrapy_components_versions\n\n\nclass Command(ScrapyCommand):\n\n    default_settings = {'LOG_ENABLED': False,\n                        'SPIDER_LOADER_WARN_ONLY': True}\n\n    def syntax(self):\n        return \"[-v]\"\n\n    def short_desc(self):\n        return \"Print Scrapy version\"\n\n    def add_options(self, parser):\n        ScrapyCommand.add_options(self, parser)\n        parser.add_option(\"--verbose\", \"-v\", dest=\"verbose\", action=\"store_true\",\n            help=\"also display twisted/python/platform info (useful for bug reports)\")\n\n    def run(self, args, opts):\n        if opts.verbose:\n            versions = scrapy_components_versions()\n            width = max(len(n) for (n, _) in versions)\n            patt = \"%-{}s : %s\".format(width)\n            for name, version in versions:\n                print(patt % (name, version))\n        else:\n            print(\"Scrapy %s\" % scrapy.__version__)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/commands/view.py",
    "content": "from scrapy.commands import fetch, ScrapyCommand\nfrom scrapy.utils.response import open_in_browser\n\nclass Command(fetch.Command):\n\n    def short_desc(self):\n        return \"Open URL in browser, as seen by Scrapy\"\n\n    def long_desc(self):\n        return \"Fetch a URL using the Scrapy downloader and show its \" \\\n            \"contents in a browser\"\n\n    def add_options(self, parser):\n        super(Command, self).add_options(parser)\n        parser.remove_option(\"--headers\")\n\n    def _print_response(self, response, opts):\n        open_in_browser(response)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/contracts/__init__.py",
    "content": "import sys\nimport re\nfrom functools import wraps\nfrom inspect import getmembers\nfrom unittest import TestCase\n\nfrom scrapy.http import Request\nfrom scrapy.utils.spider import iterate_spider_output\nfrom scrapy.utils.python import get_spec\n\n\nclass ContractsManager(object):\n    contracts = {}\n\n    def __init__(self, contracts):\n        for contract in contracts:\n            self.contracts[contract.name] = contract\n\n    def tested_methods_from_spidercls(self, spidercls):\n        methods = []\n        for key, value in getmembers(spidercls):\n            if (callable(value) and value.__doc__ and\n                    re.search(r'^\\s*@', value.__doc__, re.MULTILINE)):\n                methods.append(key)\n\n        return methods\n\n    def extract_contracts(self, method):\n        contracts = []\n        for line in method.__doc__.split('\\n'):\n            line = line.strip()\n\n            if line.startswith('@'):\n                name, args = re.match(r'@(\\w+)\\s*(.*)', line).groups()\n                args = re.split(r'\\s+', args)\n\n                contracts.append(self.contracts[name](method, *args))\n\n        return contracts\n\n    def from_spider(self, spider, results):\n        requests = []\n        for method in self.tested_methods_from_spidercls(type(spider)):\n            bound_method = spider.__getattribute__(method)\n            try:\n                requests.append(self.from_method(bound_method, results))\n            except Exception:\n                case = _create_testcase(bound_method, 'contract')\n                results.addError(case, sys.exc_info())\n\n        return requests\n\n    def from_method(self, method, results):\n        contracts = self.extract_contracts(method)\n        if contracts:\n            request_cls = Request\n            for contract in contracts:\n                if contract.request_cls is not None:\n                    request_cls = contract.request_cls\n\n            # calculate request args\n            args, kwargs = get_spec(request_cls.__init__)\n\n            # Don't filter requests to allow\n            # testing different callbacks on the same URL.\n            kwargs['dont_filter'] = True\n            kwargs['callback'] = method\n\n            for contract in contracts:\n                kwargs = contract.adjust_request_args(kwargs)\n\n            args.remove('self')\n\n            # check if all positional arguments are defined in kwargs\n            if set(args).issubset(set(kwargs)):\n                request = request_cls(**kwargs)\n\n                # execute pre and post hooks in order\n                for contract in reversed(contracts):\n                    request = contract.add_pre_hook(request, results)\n                for contract in contracts:\n                    request = contract.add_post_hook(request, results)\n\n                self._clean_req(request, method, results)\n                return request\n\n    def _clean_req(self, request, method, results):\n        \"\"\" stop the request from returning objects and records any errors \"\"\"\n\n        cb = request.callback\n\n        @wraps(cb)\n        def cb_wrapper(response):\n            try:\n                output = cb(response)\n                output = list(iterate_spider_output(output))\n            except Exception:\n                case = _create_testcase(method, 'callback')\n                results.addError(case, sys.exc_info())\n\n        def eb_wrapper(failure):\n            case = _create_testcase(method, 'errback')\n            exc_info = failure.type, failure.value, failure.getTracebackObject()\n            results.addError(case, exc_info)\n\n        request.callback = cb_wrapper\n        request.errback = eb_wrapper\n\n\nclass Contract(object):\n    \"\"\" Abstract class for contracts \"\"\"\n    request_cls = None\n\n    def __init__(self, method, *args):\n        self.testcase_pre = _create_testcase(method, '@%s pre-hook' % self.name)\n        self.testcase_post = _create_testcase(method, '@%s post-hook' % self.name)\n        self.args = args\n\n    def add_pre_hook(self, request, results):\n        if hasattr(self, 'pre_process'):\n            cb = request.callback\n\n            @wraps(cb)\n            def wrapper(response):\n                try:\n                    results.startTest(self.testcase_pre)\n                    self.pre_process(response)\n                    results.stopTest(self.testcase_pre)\n                except AssertionError:\n                    results.addFailure(self.testcase_pre, sys.exc_info())\n                except Exception:\n                    results.addError(self.testcase_pre, sys.exc_info())\n                else:\n                    results.addSuccess(self.testcase_pre)\n                finally:\n                    return list(iterate_spider_output(cb(response)))\n\n            request.callback = wrapper\n\n        return request\n\n    def add_post_hook(self, request, results):\n        if hasattr(self, 'post_process'):\n            cb = request.callback\n\n            @wraps(cb)\n            def wrapper(response):\n                output = list(iterate_spider_output(cb(response)))\n                try:\n                    results.startTest(self.testcase_post)\n                    self.post_process(output)\n                    results.stopTest(self.testcase_post)\n                except AssertionError:\n                    results.addFailure(self.testcase_post, sys.exc_info())\n                except Exception:\n                    results.addError(self.testcase_post, sys.exc_info())\n                else:\n                    results.addSuccess(self.testcase_post)\n                finally:\n                    return output\n\n            request.callback = wrapper\n\n        return request\n\n    def adjust_request_args(self, args):\n        return args\n\n\ndef _create_testcase(method, desc):\n    spider = method.__self__.name\n\n    class ContractTestCase(TestCase):\n        def __str__(_self):\n            return \"[%s] %s (%s)\" % (spider, method.__name__, desc)\n\n    name = '%s_%s' % (spider, method.__name__)\n    setattr(ContractTestCase, name, lambda x: x)\n    return ContractTestCase(name)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/contracts/default.py",
    "content": "from scrapy.item import BaseItem\nfrom scrapy.http import Request\nfrom scrapy.exceptions import ContractFail\n\nfrom . import Contract\n\n\n# contracts\nclass UrlContract(Contract):\n    \"\"\" Contract to set the url of the request (mandatory)\n        @url http://scrapy.org\n    \"\"\"\n\n    name = 'url'\n\n    def adjust_request_args(self, args):\n        args['url'] = self.args[0]\n        return args\n\n\nclass ReturnsContract(Contract):\n    \"\"\" Contract to check the output of a callback\n\n        general form:\n        @returns request(s)/item(s) [min=1 [max]]\n\n        e.g.:\n        @returns request\n        @returns request 2\n        @returns request 2 10\n        @returns request 0 10\n    \"\"\"\n\n    name = 'returns'\n    objects = {\n        'request': Request,\n        'requests': Request,\n        'item': (BaseItem, dict),\n        'items': (BaseItem, dict),\n    }\n\n    def __init__(self, *args, **kwargs):\n        super(ReturnsContract, self).__init__(*args, **kwargs)\n\n        assert len(self.args) in [1, 2, 3]\n        self.obj_name = self.args[0] or None\n        self.obj_type = self.objects[self.obj_name]\n\n        try:\n            self.min_bound = int(self.args[1])\n        except IndexError:\n            self.min_bound = 1\n\n        try:\n            self.max_bound = int(self.args[2])\n        except IndexError:\n            self.max_bound = float('inf')\n\n    def post_process(self, output):\n        occurrences = 0\n        for x in output:\n            if isinstance(x, self.obj_type):\n                occurrences += 1\n\n        assertion = (self.min_bound <= occurrences <= self.max_bound)\n\n        if not assertion:\n            if self.min_bound == self.max_bound:\n                expected = self.min_bound\n            else:\n                expected = '%s..%s' % (self.min_bound, self.max_bound)\n\n            raise ContractFail(\"Returned %s %s, expected %s\" % \\\n                (occurrences, self.obj_name, expected))\n\n\nclass ScrapesContract(Contract):\n    \"\"\" Contract to check presence of fields in scraped items\n        @scrapes page_name page_body\n    \"\"\"\n\n    name = 'scrapes'\n\n    def post_process(self, output):\n        for x in output:\n            if isinstance(x, (BaseItem, dict)):\n                for arg in self.args:\n                    if not arg in x:\n                        raise ContractFail(\"'%s' field is missing\" % arg)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/__init__.py",
    "content": "\"\"\"\nScrapy core library classes and functions.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/__init__.py",
    "content": "from __future__ import absolute_import\nimport random\nimport warnings\nfrom time import time\nfrom datetime import datetime\nfrom collections import deque\n\nimport six\nfrom twisted.internet import reactor, defer, task\n\nfrom scrapy.utils.defer import mustbe_deferred\nfrom scrapy.utils.httpobj import urlparse_cached\nfrom scrapy.resolver import dnscache\nfrom scrapy import signals\nfrom .middleware import DownloaderMiddlewareManager\nfrom .handlers import DownloadHandlers\n\n\nclass Slot(object):\n    \"\"\"Downloader slot\"\"\"\n\n    def __init__(self, concurrency, delay, randomize_delay):\n        self.concurrency = concurrency\n        self.delay = delay\n        self.randomize_delay = randomize_delay\n\n        self.active = set()\n        self.queue = deque()\n        self.transferring = set()\n        self.lastseen = 0\n        self.latercall = None\n\n    def free_transfer_slots(self):\n        return self.concurrency - len(self.transferring)\n\n    def download_delay(self):\n        if self.randomize_delay:\n            return random.uniform(0.5 * self.delay, 1.5 * self.delay)\n        return self.delay\n\n    def close(self):\n        if self.latercall and self.latercall.active():\n            self.latercall.cancel()\n\n    def __repr__(self):\n        cls_name = self.__class__.__name__\n        return \"%s(concurrency=%r, delay=%0.2f, randomize_delay=%r)\" % (\n            cls_name, self.concurrency, self.delay, self.randomize_delay)\n\n    def __str__(self):\n        return (\n            \"<downloader.Slot concurrency=%r delay=%0.2f randomize_delay=%r \"\n            \"len(active)=%d len(queue)=%d len(transferring)=%d lastseen=%s>\" % (\n                self.concurrency, self.delay, self.randomize_delay,\n                len(self.active), len(self.queue), len(self.transferring),\n                datetime.fromtimestamp(self.lastseen).isoformat()\n            )\n        )\n\n\ndef _get_concurrency_delay(concurrency, spider, settings):\n    delay = settings.getfloat('DOWNLOAD_DELAY')\n    if hasattr(spider, 'download_delay'):\n        delay = spider.download_delay\n\n    if hasattr(spider, 'max_concurrent_requests'):\n        concurrency = spider.max_concurrent_requests\n\n    return concurrency, delay\n\n\nclass Downloader(object):\n\n    DOWNLOAD_SLOT = 'download_slot'\n\n    def __init__(self, crawler):\n        self.settings = crawler.settings\n        self.signals = crawler.signals\n        self.slots = {}\n        self.active = set()\n        self.handlers = DownloadHandlers(crawler)\n        self.total_concurrency = self.settings.getint('CONCURRENT_REQUESTS')\n        self.domain_concurrency = self.settings.getint('CONCURRENT_REQUESTS_PER_DOMAIN')\n        self.ip_concurrency = self.settings.getint('CONCURRENT_REQUESTS_PER_IP')\n        self.randomize_delay = self.settings.getbool('RANDOMIZE_DOWNLOAD_DELAY')\n        self.middleware = DownloaderMiddlewareManager.from_crawler(crawler)\n        self._slot_gc_loop = task.LoopingCall(self._slot_gc)\n        self._slot_gc_loop.start(60)\n\n    def fetch(self, request, spider):\n        def _deactivate(response):\n            self.active.remove(request)\n            return response\n\n        self.active.add(request)\n        dfd = self.middleware.download(self._enqueue_request, request, spider)\n        return dfd.addBoth(_deactivate)\n\n    def needs_backout(self):\n        return len(self.active) >= self.total_concurrency\n\n    def _get_slot(self, request, spider):\n        key = self._get_slot_key(request, spider)\n        if key not in self.slots:\n            conc = self.ip_concurrency if self.ip_concurrency else self.domain_concurrency\n            conc, delay = _get_concurrency_delay(conc, spider, self.settings)\n            self.slots[key] = Slot(conc, delay, self.randomize_delay)\n\n        return key, self.slots[key]\n\n    def _get_slot_key(self, request, spider):\n        if self.DOWNLOAD_SLOT in request.meta:\n            return request.meta[self.DOWNLOAD_SLOT]\n\n        key = urlparse_cached(request).hostname or ''\n        if self.ip_concurrency:\n            key = dnscache.get(key, key)\n\n        return key\n\n    def _enqueue_request(self, request, spider):\n        key, slot = self._get_slot(request, spider)\n        request.meta[self.DOWNLOAD_SLOT] = key\n\n        def _deactivate(response):\n            slot.active.remove(request)\n            return response\n\n        slot.active.add(request)\n        self.signals.send_catch_log(signal=signals.request_reached_downloader,\n                                    request=request,\n                                    spider=spider)\n        deferred = defer.Deferred().addBoth(_deactivate)\n        slot.queue.append((request, deferred))\n        self._process_queue(spider, slot)\n        return deferred\n\n    def _process_queue(self, spider, slot):\n        if slot.latercall and slot.latercall.active():\n            return\n\n        # Delay queue processing if a download_delay is configured\n        now = time()\n        delay = slot.download_delay()\n        if delay:\n            penalty = delay - now + slot.lastseen\n            if penalty > 0:\n                slot.latercall = reactor.callLater(penalty, self._process_queue, spider, slot)\n                return\n\n        # Process enqueued requests if there are free slots to transfer for this slot\n        while slot.queue and slot.free_transfer_slots() > 0:\n            slot.lastseen = now\n            request, deferred = slot.queue.popleft()\n            dfd = self._download(slot, request, spider)\n            dfd.chainDeferred(deferred)\n            # prevent burst if inter-request delays were configured\n            if delay:\n                self._process_queue(spider, slot)\n                break\n\n    def _download(self, slot, request, spider):\n        # The order is very important for the following deferreds. Do not change!\n\n        # 1. Create the download deferred\n        dfd = mustbe_deferred(self.handlers.download_request, request, spider)\n\n        # 2. Notify response_downloaded listeners about the recent download\n        # before querying queue for next request\n        def _downloaded(response):\n            self.signals.send_catch_log(signal=signals.response_downloaded,\n                                        response=response,\n                                        request=request,\n                                        spider=spider)\n            return response\n        dfd.addCallback(_downloaded)\n\n        # 3. After response arrives,  remove the request from transferring\n        # state to free up the transferring slot so it can be used by the\n        # following requests (perhaps those which came from the downloader\n        # middleware itself)\n        slot.transferring.add(request)\n\n        def finish_transferring(_):\n            slot.transferring.remove(request)\n            self._process_queue(spider, slot)\n            return _\n\n        return dfd.addBoth(finish_transferring)\n\n    def close(self):\n        self._slot_gc_loop.stop()\n        for slot in six.itervalues(self.slots):\n            slot.close()\n\n    def _slot_gc(self, age=60):\n        mintime = time() - age\n        for key, slot in list(self.slots.items()):\n            if not slot.active and slot.lastseen + slot.delay < mintime:\n                self.slots.pop(key).close()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/contextfactory.py",
    "content": "from OpenSSL import SSL\nfrom twisted.internet.ssl import ClientContextFactory\n\nfrom scrapy import twisted_version\n\nif twisted_version >= (14, 0, 0):\n\n    from zope.interface.declarations import implementer\n\n    from twisted.internet.ssl import (optionsForClientTLS,\n                                      CertificateOptions,\n                                      platformTrust)\n    from twisted.web.client import BrowserLikePolicyForHTTPS\n    from twisted.web.iweb import IPolicyForHTTPS\n\n    from scrapy.core.downloader.tls import ScrapyClientTLSOptions, DEFAULT_CIPHERS\n\n\n    @implementer(IPolicyForHTTPS)\n    class ScrapyClientContextFactory(BrowserLikePolicyForHTTPS):\n        \"\"\"\n        Non-peer-certificate verifying HTTPS context factory\n\n        Default OpenSSL method is TLS_METHOD (also called SSLv23_METHOD)\n        which allows TLS protocol negotiation\n\n        'A TLS/SSL connection established with [this method] may\n         understand the SSLv3, TLSv1, TLSv1.1 and TLSv1.2 protocols.'\n        \"\"\"\n\n        def __init__(self, method=SSL.SSLv23_METHOD, *args, **kwargs):\n            super(ScrapyClientContextFactory, self).__init__(*args, **kwargs)\n            self._ssl_method = method\n\n        def getCertificateOptions(self):\n            # setting verify=True will require you to provide CAs\n            # to verify against; in other words: it's not that simple\n\n            # backward-compatible SSL/TLS method:\n            #\n            # * this will respect `method` attribute in often recommended\n            #   `ScrapyClientContextFactory` subclass\n            #   (https://github.com/scrapy/scrapy/issues/1429#issuecomment-131782133)\n            #\n            # * getattr() for `_ssl_method` attribute for context factories\n            #   not calling super(..., self).__init__\n            return CertificateOptions(verify=False,\n                        method=getattr(self, 'method',\n                                       getattr(self, '_ssl_method', None)),\n                        fixBrokenPeers=True,\n                        acceptableCiphers=DEFAULT_CIPHERS)\n\n        # kept for old-style HTTP/1.0 downloader context twisted calls,\n        # e.g. connectSSL()\n        def getContext(self, hostname=None, port=None):\n            return self.getCertificateOptions().getContext()\n\n        def creatorForNetloc(self, hostname, port):\n            return ScrapyClientTLSOptions(hostname.decode(\"ascii\"), self.getContext())\n\n\n    @implementer(IPolicyForHTTPS)\n    class BrowserLikeContextFactory(ScrapyClientContextFactory):\n        \"\"\"\n        Twisted-recommended context factory for web clients.\n\n        Quoting https://twistedmatrix.com/documents/current/api/twisted.web.client.Agent.html:\n        \"The default is to use a BrowserLikePolicyForHTTPS,\n        so unless you have special requirements you can leave this as-is.\"\n\n        creatorForNetloc() is the same as BrowserLikePolicyForHTTPS\n        except this context factory allows setting the TLS/SSL method to use.\n\n        Default OpenSSL method is TLS_METHOD (also called SSLv23_METHOD)\n        which allows TLS protocol negotiation.\n        \"\"\"\n        def creatorForNetloc(self, hostname, port):\n\n            # trustRoot set to platformTrust() will use the platform's root CAs.\n            #\n            # This means that a website like https://www.cacert.org will be rejected\n            # by default, since CAcert.org CA certificate is seldom shipped.\n            return optionsForClientTLS(hostname.decode(\"ascii\"),\n                                       trustRoot=platformTrust(),\n                                       extraCertificateOptions={\n                                            'method': self._ssl_method,\n                                       })\n\nelse:\n\n    class ScrapyClientContextFactory(ClientContextFactory):\n        \"A SSL context factory which is more permissive against SSL bugs.\"\n        # see https://github.com/scrapy/scrapy/issues/82\n        # and https://github.com/scrapy/scrapy/issues/26\n        # and https://github.com/scrapy/scrapy/issues/981\n\n        def __init__(self, method=SSL.SSLv23_METHOD):\n            self.method = method\n\n        def getContext(self, hostname=None, port=None):\n            ctx = ClientContextFactory.getContext(self)\n            # Enable all workarounds to SSL bugs as documented by\n            # https://www.openssl.org/docs/manmaster/man3/SSL_CTX_set_options.html\n            ctx.set_options(SSL.OP_ALL)\n            return ctx\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/handlers/__init__.py",
    "content": "\"\"\"Download handlers for different schemes\"\"\"\n\nimport logging\nfrom twisted.internet import defer\nimport six\nfrom scrapy.exceptions import NotSupported, NotConfigured\nfrom scrapy.utils.httpobj import urlparse_cached\nfrom scrapy.utils.misc import load_object\nfrom scrapy.utils.python import without_none_values\nfrom scrapy import signals\n\n\nlogger = logging.getLogger(__name__)\n\n\nclass DownloadHandlers(object):\n\n    def __init__(self, crawler):\n        self._crawler = crawler\n        self._schemes = {}  # stores acceptable schemes on instancing\n        self._handlers = {}  # stores instanced handlers for schemes\n        self._notconfigured = {}  # remembers failed handlers\n        handlers = without_none_values(\n            crawler.settings.getwithbase('DOWNLOAD_HANDLERS'))\n        for scheme, clspath in six.iteritems(handlers):\n            self._schemes[scheme] = clspath\n            self._load_handler(scheme, skip_lazy=True)\n\n        crawler.signals.connect(self._close, signals.engine_stopped)\n\n    def _get_handler(self, scheme):\n        \"\"\"Lazy-load the downloadhandler for a scheme\n        only on the first request for that scheme.\n        \"\"\"\n        if scheme in self._handlers:\n            return self._handlers[scheme]\n        if scheme in self._notconfigured:\n            return None\n        if scheme not in self._schemes:\n            self._notconfigured[scheme] = 'no handler available for that scheme'\n            return None\n\n        return self._load_handler(scheme)\n\n    def _load_handler(self, scheme, skip_lazy=False):\n        path = self._schemes[scheme]\n        try:\n            dhcls = load_object(path)\n            if skip_lazy and getattr(dhcls, 'lazy', True):\n                return None\n            dh = dhcls(self._crawler.settings)\n        except NotConfigured as ex:\n            self._notconfigured[scheme] = str(ex)\n            return None\n        except Exception as ex:\n            logger.error('Loading \"%(clspath)s\" for scheme \"%(scheme)s\"',\n                         {\"clspath\": path, \"scheme\": scheme},\n                         exc_info=True, extra={'crawler': self._crawler})\n            self._notconfigured[scheme] = str(ex)\n            return None\n        else:\n            self._handlers[scheme] = dh\n            return dh\n\n    def download_request(self, request, spider):\n        scheme = urlparse_cached(request).scheme\n        handler = self._get_handler(scheme)\n        if not handler:\n            raise NotSupported(\"Unsupported URL scheme '%s': %s\" %\n                               (scheme, self._notconfigured[scheme]))\n        return handler.download_request(request, spider)\n\n    @defer.inlineCallbacks\n    def _close(self, *_a, **_kw):\n        for dh in self._handlers.values():\n            if hasattr(dh, 'close'):\n                yield dh.close()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/handlers/datauri.py",
    "content": "from w3lib.url import parse_data_uri\n\nfrom scrapy.http import TextResponse\nfrom scrapy.responsetypes import responsetypes\nfrom scrapy.utils.decorators import defers\n\n\nclass DataURIDownloadHandler(object):\n    lazy = False\n\n    def __init__(self, settings):\n        super(DataURIDownloadHandler, self).__init__()\n\n    @defers\n    def download_request(self, request, spider):\n        uri = parse_data_uri(request.url)\n        respcls = responsetypes.from_mimetype(uri.media_type)\n\n        resp_kwargs = {}\n        if (issubclass(respcls, TextResponse) and\n                uri.media_type.split('/')[0] == 'text'):\n            charset = uri.media_type_parameters.get('charset')\n            resp_kwargs['encoding'] = charset\n\n        return respcls(url=request.url, body=uri.data, **resp_kwargs)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/handlers/file.py",
    "content": "from w3lib.url import file_uri_to_path\nfrom scrapy.responsetypes import responsetypes\nfrom scrapy.utils.decorators import defers\n\n\nclass FileDownloadHandler(object):\n    lazy = False\n\n    def __init__(self, settings):\n        pass\n\n    @defers\n    def download_request(self, request, spider):\n        filepath = file_uri_to_path(request.url)\n        with open(filepath, 'rb') as fo:\n            body = fo.read()\n        respcls = responsetypes.from_args(filename=filepath, body=body)\n        return respcls(url=request.url, body=body)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/handlers/ftp.py",
    "content": "\"\"\"\nAn asynchronous FTP file download handler for scrapy which somehow emulates an http response.\n\nFTP connection parameters are passed using the request meta field:\n- ftp_user (required)\n- ftp_password (required)\n- ftp_passive (by default, enabled) sets FTP connection passive mode\n- ftp_local_filename\n        - If not given, file data will come in the response.body, as a normal scrapy Response,\n        which will imply that the entire file will be on memory.\n        - if given, file data will be saved in a local file with the given name\n        This helps when downloading very big files to avoid memory issues. In addition, for\n        convenience the local file name will also be given in the response body.\n\nThe status of the built html response will be, by default\n- 200 in case of success\n- 404 in case specified file was not found in the server (ftp code 550)\n\nor raise corresponding ftp exception otherwise\n\nThe matching from server ftp command return codes to html response codes is defined in the\nCODE_MAPPING attribute of the handler class. The key 'default' is used for any code\nthat is not explicitly present among the map keys. You may need to overwrite this\nmapping if want a different behaviour than default.\n\nIn case of status 200 request, response.headers will come with two keys:\n    'Local Filename' - with the value of the local filename if given\n    'Size' - with size of the downloaded data\n\"\"\"\n\nimport re\nfrom io import BytesIO\nfrom six.moves.urllib.parse import unquote\n\nfrom twisted.internet import reactor\nfrom twisted.protocols.ftp import FTPClient, CommandFailed\nfrom twisted.internet.protocol import Protocol, ClientCreator\n\nfrom scrapy.http import Response\nfrom scrapy.responsetypes import responsetypes\nfrom scrapy.utils.httpobj import urlparse_cached\nfrom scrapy.utils.python import to_bytes\n\n\nclass ReceivedDataProtocol(Protocol):\n    def __init__(self, filename=None):\n        self.__filename = filename\n        self.body = open(filename, \"wb\") if filename else BytesIO()\n        self.size = 0\n\n    def dataReceived(self, data):\n        self.body.write(data)\n        self.size += len(data)\n\n    @property\n    def filename(self):\n        return self.__filename\n\n    def close(self):\n        self.body.close() if self.filename else self.body.seek(0)\n\n_CODE_RE = re.compile(r\"\\d+\")\n\n\nclass FTPDownloadHandler(object):\n    lazy = False\n\n    CODE_MAPPING = {\n        \"550\": 404,\n        \"default\": 503,\n    }\n\n    def __init__(self, settings):\n        self.default_user = settings['FTP_USER']\n        self.default_password = settings['FTP_PASSWORD']\n        self.passive_mode = settings['FTP_PASSIVE_MODE']\n\n    def download_request(self, request, spider):\n        parsed_url = urlparse_cached(request)\n        user = request.meta.get(\"ftp_user\", self.default_user)\n        password = request.meta.get(\"ftp_password\", self.default_password)\n        passive_mode = 1 if bool(request.meta.get(\"ftp_passive\",\n                                                  self.passive_mode)) else 0\n        creator = ClientCreator(reactor, FTPClient, user, password,\n            passive=passive_mode)\n        return creator.connectTCP(parsed_url.hostname, parsed_url.port or 21).addCallback(self.gotClient,\n                                request, unquote(parsed_url.path))\n\n    def gotClient(self, client, request, filepath):\n        self.client = client\n        protocol = ReceivedDataProtocol(request.meta.get(\"ftp_local_filename\"))\n        return client.retrieveFile(filepath, protocol)\\\n                .addCallbacks(callback=self._build_response,\n                        callbackArgs=(request, protocol),\n                        errback=self._failed,\n                        errbackArgs=(request,))\n\n    def _build_response(self, result, request, protocol):\n        self.result = result\n        respcls = responsetypes.from_args(url=request.url)\n        protocol.close()\n        body = protocol.filename or protocol.body.read()\n        headers = {\"local filename\": protocol.filename or '', \"size\": protocol.size}\n        return respcls(url=request.url, status=200, body=to_bytes(body), headers=headers)\n\n    def _failed(self, result, request):\n        message = result.getErrorMessage()\n        if result.type == CommandFailed:\n            m = _CODE_RE.search(message)\n            if m:\n                ftpcode = m.group()\n                httpcode = self.CODE_MAPPING.get(ftpcode, self.CODE_MAPPING[\"default\"])\n                return Response(url=request.url, status=httpcode, body=to_bytes(message))\n        raise result.type(result.value)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/handlers/http.py",
    "content": "from __future__ import absolute_import\nfrom .http10 import HTTP10DownloadHandler\nfrom .http11 import HTTP11DownloadHandler as HTTPDownloadHandler\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/handlers/http10.py",
    "content": "\"\"\"Download handlers for http and https schemes\n\"\"\"\nfrom twisted.internet import reactor\nfrom scrapy.utils.misc import load_object\nfrom scrapy.utils.python import to_unicode\n\n\nclass HTTP10DownloadHandler(object):\n    lazy = False\n\n    def __init__(self, settings):\n        self.HTTPClientFactory = load_object(settings['DOWNLOADER_HTTPCLIENTFACTORY'])\n        self.ClientContextFactory = load_object(settings['DOWNLOADER_CLIENTCONTEXTFACTORY'])\n\n    def download_request(self, request, spider):\n        \"\"\"Return a deferred for the HTTP download\"\"\"\n        factory = self.HTTPClientFactory(request)\n        self._connect(factory)\n        return factory.deferred\n\n    def _connect(self, factory):\n        host, port = to_unicode(factory.host), factory.port\n        if factory.scheme == b'https':\n            return reactor.connectSSL(host, port, factory,\n                                      self.ClientContextFactory())\n        else:\n            return reactor.connectTCP(host, port, factory)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/handlers/http11.py",
    "content": "\"\"\"Download handlers for http and https schemes\"\"\"\n\nimport re\nimport logging\nfrom io import BytesIO\nfrom time import time\nimport warnings\nfrom six.moves.urllib.parse import urldefrag\n\nfrom zope.interface import implementer\nfrom twisted.internet import defer, reactor, protocol\nfrom twisted.web.http_headers import Headers as TxHeaders\nfrom twisted.web.iweb import IBodyProducer, UNKNOWN_LENGTH\nfrom twisted.internet.error import TimeoutError\nfrom twisted.web.http import _DataLoss, PotentialDataLoss\nfrom twisted.web.client import Agent, ProxyAgent, ResponseDone, \\\n    HTTPConnectionPool, ResponseFailed\ntry:\n    from twisted.web.client import URI\nexcept ImportError:\n    from twisted.web.client import _URI as URI\nfrom twisted.internet.endpoints import TCP4ClientEndpoint\n\nfrom scrapy.http import Headers\nfrom scrapy.responsetypes import responsetypes\nfrom scrapy.core.downloader.webclient import _parse\nfrom scrapy.core.downloader.tls import openssl_methods\nfrom scrapy.utils.misc import load_object\nfrom scrapy.utils.python import to_bytes, to_unicode\nfrom scrapy import twisted_version\n\nlogger = logging.getLogger(__name__)\n\n\nclass HTTP11DownloadHandler(object):\n    lazy = False\n\n    def __init__(self, settings):\n        self._pool = HTTPConnectionPool(reactor, persistent=True)\n        self._pool.maxPersistentPerHost = settings.getint('CONCURRENT_REQUESTS_PER_DOMAIN')\n        self._pool._factory.noisy = False\n\n        self._sslMethod = openssl_methods[settings.get('DOWNLOADER_CLIENT_TLS_METHOD')]\n        self._contextFactoryClass = load_object(settings['DOWNLOADER_CLIENTCONTEXTFACTORY'])\n        # try method-aware context factory\n        try:\n            self._contextFactory = self._contextFactoryClass(method=self._sslMethod)\n        except TypeError:\n            # use context factory defaults\n            self._contextFactory = self._contextFactoryClass()\n            msg = \"\"\"\n '%s' does not accept `method` argument (type OpenSSL.SSL method,\\\n e.g. OpenSSL.SSL.SSLv23_METHOD).\\\n Please upgrade your context factory class to handle it or ignore it.\"\"\" % (\n                settings['DOWNLOADER_CLIENTCONTEXTFACTORY'],)\n            warnings.warn(msg)\n        self._default_maxsize = settings.getint('DOWNLOAD_MAXSIZE')\n        self._default_warnsize = settings.getint('DOWNLOAD_WARNSIZE')\n        self._fail_on_dataloss = settings.getbool('DOWNLOAD_FAIL_ON_DATALOSS')\n        self._disconnect_timeout = 1\n\n    def download_request(self, request, spider):\n        \"\"\"Return a deferred for the HTTP download\"\"\"\n        agent = ScrapyAgent(contextFactory=self._contextFactory, pool=self._pool,\n            maxsize=getattr(spider, 'download_maxsize', self._default_maxsize),\n            warnsize=getattr(spider, 'download_warnsize', self._default_warnsize),\n            fail_on_dataloss=self._fail_on_dataloss)\n        return agent.download_request(request)\n\n    def close(self):\n        d = self._pool.closeCachedConnections()\n        # closeCachedConnections will hang on network or server issues, so\n        # we'll manually timeout the deferred.\n        #\n        # Twisted issue addressing this problem can be found here:\n        # https://twistedmatrix.com/trac/ticket/7738.\n        #\n        # closeCachedConnections doesn't handle external errbacks, so we'll\n        # issue a callback after `_disconnect_timeout` seconds.\n        delayed_call = reactor.callLater(self._disconnect_timeout, d.callback, [])\n\n        def cancel_delayed_call(result):\n            if delayed_call.active():\n                delayed_call.cancel()\n            return result\n\n        d.addBoth(cancel_delayed_call)\n        return d\n\n\nclass TunnelError(Exception):\n    \"\"\"An HTTP CONNECT tunnel could not be established by the proxy.\"\"\"\n\n\nclass TunnelingTCP4ClientEndpoint(TCP4ClientEndpoint):\n    \"\"\"An endpoint that tunnels through proxies to allow HTTPS downloads. To\n    accomplish that, this endpoint sends an HTTP CONNECT to the proxy.\n    The HTTP CONNECT is always sent when using this endpoint, I think this could\n    be improved as the CONNECT will be redundant if the connection associated\n    with this endpoint comes from the pool and a CONNECT has already been issued\n    for it.\n    \"\"\"\n\n    _responseMatcher = re.compile(br'HTTP/1\\.. (?P<status>\\d{3})(?P<reason>.{,32})')\n\n    def __init__(self, reactor, host, port, proxyConf, contextFactory,\n                 timeout=30, bindAddress=None):\n        proxyHost, proxyPort, self._proxyAuthHeader = proxyConf\n        super(TunnelingTCP4ClientEndpoint, self).__init__(reactor, proxyHost,\n            proxyPort, timeout, bindAddress)\n        self._tunnelReadyDeferred = defer.Deferred()\n        self._tunneledHost = host\n        self._tunneledPort = port\n        self._contextFactory = contextFactory\n        self._connectBuffer = bytearray()\n\n    def requestTunnel(self, protocol):\n        \"\"\"Asks the proxy to open a tunnel.\"\"\"\n        tunnelReq = tunnel_request_data(self._tunneledHost, self._tunneledPort,\n                                        self._proxyAuthHeader)\n        protocol.transport.write(tunnelReq)\n        self._protocolDataReceived = protocol.dataReceived\n        protocol.dataReceived = self.processProxyResponse\n        self._protocol = protocol\n        return protocol\n\n    def processProxyResponse(self, rcvd_bytes):\n        \"\"\"Processes the response from the proxy. If the tunnel is successfully\n        created, notifies the client that we are ready to send requests. If not\n        raises a TunnelError.\n        \"\"\"\n        self._connectBuffer += rcvd_bytes\n        # make sure that enough (all) bytes are consumed\n        # and that we've got all HTTP headers (ending with a blank line)\n        # from the proxy so that we don't send those bytes to the TLS layer\n        #\n        # see https://github.com/scrapy/scrapy/issues/2491\n        if b'\\r\\n\\r\\n' not in self._connectBuffer:\n            return\n        self._protocol.dataReceived = self._protocolDataReceived\n        respm = TunnelingTCP4ClientEndpoint._responseMatcher.match(self._connectBuffer)\n        if respm and int(respm.group('status')) == 200:\n            try:\n                # this sets proper Server Name Indication extension\n                # but is only available for Twisted>=14.0\n                sslOptions = self._contextFactory.creatorForNetloc(\n                    self._tunneledHost, self._tunneledPort)\n            except AttributeError:\n                # fall back to non-SNI SSL context factory\n                sslOptions = self._contextFactory\n            self._protocol.transport.startTLS(sslOptions,\n                                              self._protocolFactory)\n            self._tunnelReadyDeferred.callback(self._protocol)\n        else:\n            if respm:\n                extra = {'status': int(respm.group('status')),\n                         'reason': respm.group('reason').strip()}\n            else:\n                extra = rcvd_bytes[:32]\n            self._tunnelReadyDeferred.errback(\n                TunnelError('Could not open CONNECT tunnel with proxy %s:%s [%r]' % (\n                    self._host, self._port, extra)))\n\n    def connectFailed(self, reason):\n        \"\"\"Propagates the errback to the appropriate deferred.\"\"\"\n        self._tunnelReadyDeferred.errback(reason)\n\n    def connect(self, protocolFactory):\n        self._protocolFactory = protocolFactory\n        connectDeferred = super(TunnelingTCP4ClientEndpoint,\n                                self).connect(protocolFactory)\n        connectDeferred.addCallback(self.requestTunnel)\n        connectDeferred.addErrback(self.connectFailed)\n        return self._tunnelReadyDeferred\n\n\ndef tunnel_request_data(host, port, proxy_auth_header=None):\n    r\"\"\"\n    Return binary content of a CONNECT request.\n\n    >>> from scrapy.utils.python import to_native_str as s\n    >>> s(tunnel_request_data(\"example.com\", 8080))\n    'CONNECT example.com:8080 HTTP/1.1\\r\\nHost: example.com:8080\\r\\n\\r\\n'\n    >>> s(tunnel_request_data(\"example.com\", 8080, b\"123\"))\n    'CONNECT example.com:8080 HTTP/1.1\\r\\nHost: example.com:8080\\r\\nProxy-Authorization: 123\\r\\n\\r\\n'\n    >>> s(tunnel_request_data(b\"example.com\", \"8090\"))\n    'CONNECT example.com:8090 HTTP/1.1\\r\\nHost: example.com:8090\\r\\n\\r\\n'\n    \"\"\"\n    host_value = to_bytes(host, encoding='ascii') + b':' + to_bytes(str(port))\n    tunnel_req = b'CONNECT ' + host_value + b' HTTP/1.1\\r\\n'\n    tunnel_req += b'Host: ' + host_value + b'\\r\\n'\n    if proxy_auth_header:\n        tunnel_req += b'Proxy-Authorization: ' + proxy_auth_header + b'\\r\\n'\n    tunnel_req += b'\\r\\n'\n    return tunnel_req\n\n\nclass TunnelingAgent(Agent):\n    \"\"\"An agent that uses a L{TunnelingTCP4ClientEndpoint} to make HTTPS\n    downloads. It may look strange that we have chosen to subclass Agent and not\n    ProxyAgent but consider that after the tunnel is opened the proxy is\n    transparent to the client; thus the agent should behave like there is no\n    proxy involved.\n    \"\"\"\n\n    def __init__(self, reactor, proxyConf, contextFactory=None,\n                 connectTimeout=None, bindAddress=None, pool=None):\n        super(TunnelingAgent, self).__init__(reactor, contextFactory,\n            connectTimeout, bindAddress, pool)\n        self._proxyConf = proxyConf\n        self._contextFactory = contextFactory\n\n    if twisted_version >= (15, 0, 0):\n        def _getEndpoint(self, uri):\n            return TunnelingTCP4ClientEndpoint(\n                self._reactor, uri.host, uri.port, self._proxyConf,\n                self._contextFactory, self._endpointFactory._connectTimeout,\n                self._endpointFactory._bindAddress)\n    else:\n        def _getEndpoint(self, scheme, host, port):\n            return TunnelingTCP4ClientEndpoint(\n                self._reactor, host, port, self._proxyConf,\n                self._contextFactory, self._connectTimeout,\n                self._bindAddress)\n\n    def _requestWithEndpoint(self, key, endpoint, method, parsedURI,\n            headers, bodyProducer, requestPath):\n        # proxy host and port are required for HTTP pool `key`\n        # otherwise, same remote host connection request could reuse\n        # a cached tunneled connection to a different proxy\n        key = key + self._proxyConf\n        return super(TunnelingAgent, self)._requestWithEndpoint(key, endpoint, method, parsedURI,\n            headers, bodyProducer, requestPath)\n\n\nclass ScrapyProxyAgent(Agent):\n\n    def __init__(self, reactor, proxyURI,\n                 connectTimeout=None, bindAddress=None, pool=None):\n        super(ScrapyProxyAgent, self).__init__(reactor,\n                                               connectTimeout=connectTimeout,\n                                               bindAddress=bindAddress,\n                                               pool=pool)\n        self._proxyURI = URI.fromBytes(proxyURI)\n\n    def request(self, method, uri, headers=None, bodyProducer=None):\n        \"\"\"\n        Issue a new request via the configured proxy.\n        \"\"\"\n        # Cache *all* connections under the same key, since we are only\n        # connecting to a single destination, the proxy:\n        if twisted_version >= (15, 0, 0):\n            proxyEndpoint = self._getEndpoint(self._proxyURI)\n        else:\n            proxyEndpoint = self._getEndpoint(self._proxyURI.scheme,\n                                              self._proxyURI.host,\n                                              self._proxyURI.port)\n        key = (\"http-proxy\", self._proxyURI.host, self._proxyURI.port)\n        return self._requestWithEndpoint(key, proxyEndpoint, method,\n                                         URI.fromBytes(uri), headers,\n                                         bodyProducer, uri)\n\n\nclass ScrapyAgent(object):\n\n    _Agent = Agent\n    _ProxyAgent = ScrapyProxyAgent\n    _TunnelingAgent = TunnelingAgent\n\n    def __init__(self, contextFactory=None, connectTimeout=10, bindAddress=None, pool=None,\n                 maxsize=0, warnsize=0, fail_on_dataloss=True):\n        self._contextFactory = contextFactory\n        self._connectTimeout = connectTimeout\n        self._bindAddress = bindAddress\n        self._pool = pool\n        self._maxsize = maxsize\n        self._warnsize = warnsize\n        self._fail_on_dataloss = fail_on_dataloss\n        self._txresponse = None\n\n    def _get_agent(self, request, timeout):\n        bindaddress = request.meta.get('bindaddress') or self._bindAddress\n        proxy = request.meta.get('proxy')\n        if proxy:\n            _, _, proxyHost, proxyPort, proxyParams = _parse(proxy)\n            scheme = _parse(request.url)[0]\n            proxyHost = to_unicode(proxyHost)\n            omitConnectTunnel = b'noconnect' in proxyParams\n            if  scheme == b'https' and not omitConnectTunnel:\n                proxyConf = (proxyHost, proxyPort,\n                             request.headers.get(b'Proxy-Authorization', None))\n                return self._TunnelingAgent(reactor, proxyConf,\n                    contextFactory=self._contextFactory, connectTimeout=timeout,\n                    bindAddress=bindaddress, pool=self._pool)\n            else:\n                return self._ProxyAgent(reactor, proxyURI=to_bytes(proxy, encoding='ascii'),\n                    connectTimeout=timeout, bindAddress=bindaddress, pool=self._pool)\n\n        return self._Agent(reactor, contextFactory=self._contextFactory,\n            connectTimeout=timeout, bindAddress=bindaddress, pool=self._pool)\n\n    def download_request(self, request):\n        timeout = request.meta.get('download_timeout') or self._connectTimeout\n        agent = self._get_agent(request, timeout)\n\n        # request details\n        url = urldefrag(request.url)[0]\n        method = to_bytes(request.method)\n        headers = TxHeaders(request.headers)\n        if isinstance(agent, self._TunnelingAgent):\n            headers.removeHeader(b'Proxy-Authorization')\n        if request.body:\n            bodyproducer = _RequestBodyProducer(request.body)\n        elif method == b'POST':\n            # Setting Content-Length: 0 even for POST requests is not a\n            # MUST per HTTP RFCs, but it's common behavior, and some\n            # servers require this, otherwise returning HTTP 411 Length required\n            #\n            # RFC 7230#section-3.3.2:\n            # \"a Content-Length header field is normally sent in a POST\n            # request even when the value is 0 (indicating an empty payload body).\"\n            #\n            # Twisted < 17 will not add \"Content-Length: 0\" by itself;\n            # Twisted >= 17 fixes this;\n            # Using a producer with an empty-string sends `0` as Content-Length\n            # for all versions of Twisted.\n            bodyproducer = _RequestBodyProducer(b'')\n        else:\n            bodyproducer = None\n        start_time = time()\n        d = agent.request(\n            method, to_bytes(url, encoding='ascii'), headers, bodyproducer)\n        # set download latency\n        d.addCallback(self._cb_latency, request, start_time)\n        # response body is ready to be consumed\n        d.addCallback(self._cb_bodyready, request)\n        d.addCallback(self._cb_bodydone, request, url)\n        # check download timeout\n        self._timeout_cl = reactor.callLater(timeout, d.cancel)\n        d.addBoth(self._cb_timeout, request, url, timeout)\n        return d\n\n    def _cb_timeout(self, result, request, url, timeout):\n        if self._timeout_cl.active():\n            self._timeout_cl.cancel()\n            return result\n        # needed for HTTPS requests, otherwise _ResponseReader doesn't\n        # receive connectionLost()\n        if self._txresponse:\n            self._txresponse._transport.stopProducing()\n\n        raise TimeoutError(\"Getting %s took longer than %s seconds.\" % (url, timeout))\n\n    def _cb_latency(self, result, request, start_time):\n        request.meta['download_latency'] = time() - start_time\n        return result\n\n    def _cb_bodyready(self, txresponse, request):\n        # deliverBody hangs for responses without body\n        if txresponse.length == 0:\n            return txresponse, b'', None\n\n        maxsize = request.meta.get('download_maxsize', self._maxsize)\n        warnsize = request.meta.get('download_warnsize', self._warnsize)\n        expected_size = txresponse.length if txresponse.length != UNKNOWN_LENGTH else -1\n        fail_on_dataloss = request.meta.get('download_fail_on_dataloss', self._fail_on_dataloss)\n\n        if maxsize and expected_size > maxsize:\n            error_msg = (\"Cancelling download of %(url)s: expected response \"\n                         \"size (%(size)s) larger than download max size (%(maxsize)s).\")\n            error_args = {'url': request.url, 'size': expected_size, 'maxsize': maxsize}\n\n            logger.error(error_msg, error_args)\n            txresponse._transport._producer.loseConnection()\n            raise defer.CancelledError(error_msg % error_args)\n\n        if warnsize and expected_size > warnsize:\n            logger.warning(\"Expected response size (%(size)s) larger than \"\n                           \"download warn size (%(warnsize)s) in request %(request)s.\",\n                           {'size': expected_size, 'warnsize': warnsize, 'request': request})\n\n        def _cancel(_):\n            # Abort connection immediately.\n            txresponse._transport._producer.abortConnection()\n\n        d = defer.Deferred(_cancel)\n        txresponse.deliverBody(_ResponseReader(\n            d, txresponse, request, maxsize, warnsize, fail_on_dataloss))\n\n        # save response for timeouts\n        self._txresponse = txresponse\n\n        return d\n\n    def _cb_bodydone(self, result, request, url):\n        txresponse, body, flags = result\n        status = int(txresponse.code)\n        headers = Headers(txresponse.headers.getAllRawHeaders())\n        respcls = responsetypes.from_args(headers=headers, url=url, body=body)\n        return respcls(url=url, status=status, headers=headers, body=body, flags=flags)\n\n\n@implementer(IBodyProducer)\nclass _RequestBodyProducer(object):\n\n    def __init__(self, body):\n        self.body = body\n        self.length = len(body)\n\n    def startProducing(self, consumer):\n        consumer.write(self.body)\n        return defer.succeed(None)\n\n    def pauseProducing(self):\n        pass\n\n    def stopProducing(self):\n        pass\n\n\nclass _ResponseReader(protocol.Protocol):\n\n    def __init__(self, finished, txresponse, request, maxsize, warnsize,\n                 fail_on_dataloss):\n        self._finished = finished\n        self._txresponse = txresponse\n        self._request = request\n        self._bodybuf = BytesIO()\n        self._maxsize  = maxsize\n        self._warnsize  = warnsize\n        self._fail_on_dataloss = fail_on_dataloss\n        self._fail_on_dataloss_warned = False\n        self._reached_warnsize = False\n        self._bytes_received = 0\n\n    def dataReceived(self, bodyBytes):\n        # This maybe called several times after cancel was called with buffered\n        # data.\n        if self._finished.called:\n            return\n\n        self._bodybuf.write(bodyBytes)\n        self._bytes_received += len(bodyBytes)\n\n        if self._maxsize and self._bytes_received > self._maxsize:\n            logger.error(\"Received (%(bytes)s) bytes larger than download \"\n                         \"max size (%(maxsize)s) in request %(request)s.\",\n                         {'bytes': self._bytes_received,\n                          'maxsize': self._maxsize,\n                          'request': self._request})\n            # Clear buffer earlier to avoid keeping data in memory for a long\n            # time.\n            self._bodybuf.truncate(0)\n            self._finished.cancel()\n\n        if self._warnsize and self._bytes_received > self._warnsize and not self._reached_warnsize:\n            self._reached_warnsize = True\n            logger.warning(\"Received more bytes than download \"\n                           \"warn size (%(warnsize)s) in request %(request)s.\",\n                           {'warnsize': self._warnsize,\n                            'request': self._request})\n\n    def connectionLost(self, reason):\n        if self._finished.called:\n            return\n\n        body = self._bodybuf.getvalue()\n        if reason.check(ResponseDone):\n            self._finished.callback((self._txresponse, body, None))\n            return\n\n        if reason.check(PotentialDataLoss):\n            self._finished.callback((self._txresponse, body, ['partial']))\n            return\n\n        if reason.check(ResponseFailed) and any(r.check(_DataLoss) for r in reason.value.reasons):\n            if not self._fail_on_dataloss:\n                self._finished.callback((self._txresponse, body, ['dataloss']))\n                return\n\n            elif not self._fail_on_dataloss_warned:\n                logger.warning(\"Got data loss in %s. If you want to process broken \"\n                               \"responses set the setting DOWNLOAD_FAIL_ON_DATALOSS = False\"\n                               \" -- This message won't be shown in further requests\",\n                               self._txresponse.request.absoluteURI.decode())\n                self._fail_on_dataloss_warned = True\n\n        self._finished.errback(reason)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/handlers/s3.py",
    "content": "from six.moves.urllib.parse import unquote\n\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy.utils.httpobj import urlparse_cached\nfrom scrapy.utils.boto import is_botocore\nfrom .http import HTTPDownloadHandler\n\n\ndef _get_boto_connection():\n    from boto.s3.connection import S3Connection\n\n    class _v19_S3Connection(S3Connection):\n        \"\"\"A dummy S3Connection wrapper that doesn't do any synchronous download\"\"\"\n        def _mexe(self, method, bucket, key, headers, *args, **kwargs):\n            return headers\n\n    class _v20_S3Connection(S3Connection):\n        \"\"\"A dummy S3Connection wrapper that doesn't do any synchronous download\"\"\"\n        def _mexe(self, http_request, *args, **kwargs):\n            http_request.authorize(connection=self)\n            return http_request.headers\n\n    try:\n        import boto.auth\n    except ImportError:\n        _S3Connection = _v19_S3Connection\n    else:\n        _S3Connection = _v20_S3Connection\n\n    return _S3Connection\n\n\nclass S3DownloadHandler(object):\n\n    def __init__(self, settings, aws_access_key_id=None, aws_secret_access_key=None, \\\n            httpdownloadhandler=HTTPDownloadHandler, **kw):\n\n        if not aws_access_key_id:\n            aws_access_key_id = settings['AWS_ACCESS_KEY_ID']\n        if not aws_secret_access_key:\n            aws_secret_access_key = settings['AWS_SECRET_ACCESS_KEY']\n\n        # If no credentials could be found anywhere,\n        # consider this an anonymous connection request by default;\n        # unless 'anon' was set explicitly (True/False).\n        anon = kw.get('anon')\n        if anon is None and not aws_access_key_id and not aws_secret_access_key:\n            kw['anon'] = True\n        self.anon = kw.get('anon')\n\n        self._signer = None\n        if is_botocore():\n            import botocore.auth\n            import botocore.credentials\n            kw.pop('anon', None)\n            if kw:\n                raise TypeError('Unexpected keyword arguments: %s' % kw)\n            if not self.anon:\n                SignerCls = botocore.auth.AUTH_TYPE_MAPS['s3']\n                self._signer = SignerCls(botocore.credentials.Credentials(\n                    aws_access_key_id, aws_secret_access_key))\n        else:\n            _S3Connection = _get_boto_connection()\n            try:\n                self.conn = _S3Connection(\n                    aws_access_key_id, aws_secret_access_key, **kw)\n            except Exception as ex:\n                raise NotConfigured(str(ex))\n\n        self._download_http = httpdownloadhandler(settings).download_request\n\n    def download_request(self, request, spider):\n        p = urlparse_cached(request)\n        scheme = 'https' if request.meta.get('is_secure') else 'http'\n        bucket = p.hostname\n        path = p.path + '?' + p.query if p.query else p.path\n        url = '%s://%s.s3.amazonaws.com%s' % (scheme, bucket, path)\n        if self.anon:\n            request = request.replace(url=url)\n        elif self._signer is not None:\n            import botocore.awsrequest\n            awsrequest = botocore.awsrequest.AWSRequest(\n                method=request.method,\n                url='%s://s3.amazonaws.com/%s%s' % (scheme, bucket, path),\n                headers=request.headers.to_unicode_dict(),\n                data=request.body)\n            self._signer.add_auth(awsrequest)\n            request = request.replace(\n                url=url, headers=awsrequest.headers.items())\n        else:\n            signed_headers = self.conn.make_request(\n                    method=request.method,\n                    bucket=bucket,\n                    key=unquote(p.path),\n                    query_args=unquote(p.query),\n                    headers=request.headers,\n                    data=request.body)\n            request = request.replace(url=url, headers=signed_headers)\n        return self._download_http(request, spider)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/middleware.py",
    "content": "\"\"\"\nDownloader Middleware manager\n\nSee documentation in docs/topics/downloader-middleware.rst\n\"\"\"\nimport six\n\nfrom twisted.internet import defer\n\nfrom scrapy.exceptions import _InvalidOutput\nfrom scrapy.http import Request, Response\nfrom scrapy.middleware import MiddlewareManager\nfrom scrapy.utils.defer import mustbe_deferred\nfrom scrapy.utils.conf import build_component_list\n\n\nclass DownloaderMiddlewareManager(MiddlewareManager):\n\n    component_name = 'downloader middleware'\n\n    @classmethod\n    def _get_mwlist_from_settings(cls, settings):\n        return build_component_list(\n            settings.getwithbase('DOWNLOADER_MIDDLEWARES'))\n\n    def _add_middleware(self, mw):\n        if hasattr(mw, 'process_request'):\n            self.methods['process_request'].append(mw.process_request)\n        if hasattr(mw, 'process_response'):\n            self.methods['process_response'].appendleft(mw.process_response)\n        if hasattr(mw, 'process_exception'):\n            self.methods['process_exception'].appendleft(mw.process_exception)\n\n    def download(self, download_func, request, spider):\n        @defer.inlineCallbacks\n        def process_request(request):\n            for method in self.methods['process_request']:\n                response = yield method(request=request, spider=spider)\n                if response is not None and not isinstance(response, (Response, Request)):\n                    raise _InvalidOutput('Middleware %s.process_request must return None, Response or Request, got %s' % \\\n                                         (six.get_method_self(method).__class__.__name__, response.__class__.__name__))\n                if response:\n                    defer.returnValue(response)\n            defer.returnValue((yield download_func(request=request, spider=spider)))\n\n        @defer.inlineCallbacks\n        def process_response(response):\n            assert response is not None, 'Received None in process_response'\n            if isinstance(response, Request):\n                defer.returnValue(response)\n\n            for method in self.methods['process_response']:\n                response = yield method(request=request, response=response, spider=spider)\n                if not isinstance(response, (Response, Request)):\n                    raise _InvalidOutput('Middleware %s.process_response must return Response or Request, got %s' % \\\n                                         (six.get_method_self(method).__class__.__name__, type(response)))\n                if isinstance(response, Request):\n                    defer.returnValue(response)\n            defer.returnValue(response)\n\n        @defer.inlineCallbacks\n        def process_exception(_failure):\n            exception = _failure.value\n            for method in self.methods['process_exception']:\n                response = yield method(request=request, exception=exception, spider=spider)\n                if response is not None and not isinstance(response, (Response, Request)):\n                    raise _InvalidOutput('Middleware %s.process_exception must return None, Response or Request, got %s' % \\\n                                         (six.get_method_self(method).__class__.__name__, type(response)))\n                if response:\n                    defer.returnValue(response)\n            defer.returnValue(_failure)\n\n        deferred = mustbe_deferred(process_request, request)\n        deferred.addErrback(process_exception)\n        deferred.addCallback(process_response)\n        return deferred\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/tls.py",
    "content": "import logging\nfrom OpenSSL import SSL\n\nfrom scrapy import twisted_version\n\n\nlogger = logging.getLogger(__name__)\n\nMETHOD_SSLv3 = 'SSLv3'\nMETHOD_TLS = 'TLS'\nMETHOD_TLSv10 = 'TLSv1.0'\nMETHOD_TLSv11 = 'TLSv1.1'\nMETHOD_TLSv12 = 'TLSv1.2'\n\nopenssl_methods = {\n    METHOD_TLS:    SSL.SSLv23_METHOD,                   # protocol negotiation (recommended)\n    METHOD_SSLv3:  SSL.SSLv3_METHOD,                    # SSL 3 (NOT recommended)\n    METHOD_TLSv10: SSL.TLSv1_METHOD,                    # TLS 1.0 only\n    METHOD_TLSv11: getattr(SSL, 'TLSv1_1_METHOD', 5),   # TLS 1.1 only\n    METHOD_TLSv12: getattr(SSL, 'TLSv1_2_METHOD', 6),   # TLS 1.2 only\n}\n\nif twisted_version >= (14, 0, 0):\n    # ClientTLSOptions requires a recent-enough version of Twisted.\n    # Not having ScrapyClientTLSOptions should not matter for older\n    # Twisted versions because it is not used in the fallback\n    # ScrapyClientContextFactory.\n\n    # taken from twisted/twisted/internet/_sslverify.py\n\n    try:\n        # XXX: this try-except is not needed in Twisted 17.0.0+ because\n        # it requires pyOpenSSL 0.16+.\n        from OpenSSL.SSL import SSL_CB_HANDSHAKE_DONE, SSL_CB_HANDSHAKE_START\n    except ImportError:\n        SSL_CB_HANDSHAKE_START = 0x10\n        SSL_CB_HANDSHAKE_DONE = 0x20\n\n    from twisted.internet.ssl import AcceptableCiphers\n    from twisted.internet._sslverify import (ClientTLSOptions,\n                                             verifyHostname,\n                                             VerificationError)\n    try:\n        # XXX: this import would fail on Debian jessie with system installed\n        # service_identity library, due to lack of cryptography.x509 dependency\n        # See https://github.com/pyca/service_identity/issues/21\n        from service_identity.exceptions import CertificateError\n        verification_errors = (CertificateError, VerificationError)\n    except ImportError:\n        verification_errors = VerificationError\n\n    if twisted_version < (17, 0, 0):\n        from twisted.internet._sslverify import _maybeSetHostNameIndication\n        set_tlsext_host_name = _maybeSetHostNameIndication\n    else:\n        def set_tlsext_host_name(connection, hostNameBytes):\n            connection.set_tlsext_host_name(hostNameBytes)\n\n\n    class ScrapyClientTLSOptions(ClientTLSOptions):\n        \"\"\"\n        SSL Client connection creator ignoring certificate verification errors\n        (for genuinely invalid certificates or bugs in verification code).\n\n        Same as Twisted's private _sslverify.ClientTLSOptions,\n        except that VerificationError, CertificateError and ValueError\n        exceptions are caught, so that the connection is not closed, only\n        logging warnings.\n        \"\"\"\n\n        def _identityVerifyingInfoCallback(self, connection, where, ret):\n            if where & SSL_CB_HANDSHAKE_START:\n                set_tlsext_host_name(connection, self._hostnameBytes)\n            elif where & SSL_CB_HANDSHAKE_DONE:\n                try:\n                    verifyHostname(connection, self._hostnameASCII)\n                except verification_errors as e:\n                    logger.warning(\n                        'Remote certificate is not valid for hostname \"{}\"; {}'.format(\n                            self._hostnameASCII, e))\n\n                except ValueError as e:\n                    logger.warning(\n                        'Ignoring error while verifying certificate '\n                        'from host \"{}\" (exception: {})'.format(\n                            self._hostnameASCII, repr(e)))\n\n    DEFAULT_CIPHERS = AcceptableCiphers.fromOpenSSLCipherString('DEFAULT')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/downloader/webclient.py",
    "content": "from time import time\nfrom six.moves.urllib.parse import urlparse, urlunparse, urldefrag\n\nfrom twisted.web.client import HTTPClientFactory\nfrom twisted.web.http import HTTPClient\nfrom twisted.internet import defer\n\nfrom scrapy.http import Headers\nfrom scrapy.utils.httpobj import urlparse_cached\nfrom scrapy.utils.python import to_bytes\nfrom scrapy.responsetypes import responsetypes\n\n\ndef _parsed_url_args(parsed):\n    # Assume parsed is urlparse-d from Request.url,\n    # which was passed via safe_url_string and is ascii-only.\n    b = lambda s: to_bytes(s, encoding='ascii')\n    path = urlunparse(('', '', parsed.path or '/', parsed.params, parsed.query, ''))\n    path = b(path)\n    host = b(parsed.hostname)\n    port = parsed.port\n    scheme = b(parsed.scheme)\n    netloc = b(parsed.netloc)\n    if port is None:\n        port = 443 if scheme == b'https' else 80\n    return scheme, netloc, host, port, path\n\n\ndef _parse(url):\n    \"\"\" Return tuple of (scheme, netloc, host, port, path),\n    all in bytes except for port which is int.\n    Assume url is from Request.url, which was passed via safe_url_string\n    and is ascii-only.\n    \"\"\"\n    url = url.strip()\n    parsed = urlparse(url)\n    return _parsed_url_args(parsed)\n\n\nclass ScrapyHTTPPageGetter(HTTPClient):\n\n    delimiter = b'\\n'\n\n    def connectionMade(self):\n        self.headers = Headers() # bucket for response headers\n\n        # Method command\n        self.sendCommand(self.factory.method, self.factory.path)\n        # Headers\n        for key, values in self.factory.headers.items():\n            for value in values:\n                self.sendHeader(key, value)\n        self.endHeaders()\n        # Body\n        if self.factory.body is not None:\n            self.transport.write(self.factory.body)\n\n    def lineReceived(self, line):\n        return HTTPClient.lineReceived(self, line.rstrip())\n\n    def handleHeader(self, key, value):\n        self.headers.appendlist(key, value)\n\n    def handleStatus(self, version, status, message):\n        self.factory.gotStatus(version, status, message)\n\n    def handleEndHeaders(self):\n        self.factory.gotHeaders(self.headers)\n\n    def connectionLost(self, reason):\n        self._connection_lost_reason = reason\n        HTTPClient.connectionLost(self, reason)\n        self.factory.noPage(reason)\n\n    def handleResponse(self, response):\n        if self.factory.method.upper() == b'HEAD':\n            self.factory.page(b'')\n        elif self.length is not None and self.length > 0:\n            self.factory.noPage(self._connection_lost_reason)\n        else:\n            self.factory.page(response)\n        self.transport.loseConnection()\n\n    def timeout(self):\n        self.transport.loseConnection()\n\n        # transport cleanup needed for HTTPS connections\n        if self.factory.url.startswith(b'https'):\n            self.transport.stopProducing()\n\n        self.factory.noPage(\\\n                defer.TimeoutError(\"Getting %s took longer than %s seconds.\" % \\\n                (self.factory.url, self.factory.timeout)))\n\n\nclass ScrapyHTTPClientFactory(HTTPClientFactory):\n    \"\"\"Scrapy implementation of the HTTPClientFactory overwriting the\n    serUrl method to make use of our Url object that cache the parse\n    result.\n    \"\"\"\n\n    protocol = ScrapyHTTPPageGetter\n    waiting = 1\n    noisy = False\n    followRedirect = False\n    afterFoundGet = False\n\n    def __init__(self, request, timeout=180):\n        self._url = urldefrag(request.url)[0]\n        # converting to bytes to comply to Twisted interface\n        self.url = to_bytes(self._url, encoding='ascii')\n        self.method = to_bytes(request.method, encoding='ascii')\n        self.body = request.body or None\n        self.headers = Headers(request.headers)\n        self.response_headers = None\n        self.timeout = request.meta.get('download_timeout') or timeout\n        self.start_time = time()\n        self.deferred = defer.Deferred().addCallback(self._build_response, request)\n\n        # Fixes Twisted 11.1.0+ support as HTTPClientFactory is expected\n        # to have _disconnectedDeferred. See Twisted r32329.\n        # As Scrapy implements it's own logic to handle redirects is not\n        # needed to add the callback _waitForDisconnect.\n        # Specifically this avoids the AttributeError exception when\n        # clientConnectionFailed method is called.\n        self._disconnectedDeferred = defer.Deferred()\n\n        self._set_connection_attributes(request)\n\n        # set Host header based on url\n        self.headers.setdefault('Host', self.netloc)\n\n        # set Content-Length based len of body\n        if self.body is not None:\n            self.headers['Content-Length'] = len(self.body)\n            # just in case a broken http/1.1 decides to keep connection alive\n            self.headers.setdefault(\"Connection\", \"close\")\n        # Content-Length must be specified in POST method even with no body\n        elif self.method == b'POST':\n            self.headers['Content-Length'] = 0\n\n    def _build_response(self, body, request):\n        request.meta['download_latency'] = self.headers_time-self.start_time\n        status = int(self.status)\n        headers = Headers(self.response_headers)\n        respcls = responsetypes.from_args(headers=headers, url=self._url)\n        return respcls(url=self._url, status=status, headers=headers, body=body)\n\n    def _set_connection_attributes(self, request):\n        parsed = urlparse_cached(request)\n        self.scheme, self.netloc, self.host, self.port, self.path = _parsed_url_args(parsed)\n        proxy = request.meta.get('proxy')\n        if proxy:\n            self.scheme, _, self.host, self.port, _ = _parse(proxy)\n            self.path = self.url\n\n    def gotHeaders(self, headers):\n        self.headers_time = time()\n        self.response_headers = headers\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/engine.py",
    "content": "\"\"\"\nThis is the Scrapy engine which controls the Scheduler, Downloader and Spiders.\n\nFor more information see docs/topics/architecture.rst\n\n\"\"\"\nimport logging\nfrom time import time\n\nfrom twisted.internet import defer, task\nfrom twisted.python.failure import Failure\n\nfrom scrapy import signals\nfrom scrapy.core.scraper import Scraper\nfrom scrapy.exceptions import DontCloseSpider\nfrom scrapy.http import Response, Request\nfrom scrapy.utils.misc import load_object\nfrom scrapy.utils.reactor import CallLaterOnce\nfrom scrapy.utils.log import logformatter_adapter, failure_to_exc_info\n\nlogger = logging.getLogger(__name__)\n\n\nclass Slot(object):\n\n    def __init__(self, start_requests, close_if_idle, nextcall, scheduler):\n        self.closing = False\n        self.inprogress = set() # requests in progress\n        self.start_requests = iter(start_requests)\n        self.close_if_idle = close_if_idle\n        self.nextcall = nextcall\n        self.scheduler = scheduler\n        self.heartbeat = task.LoopingCall(nextcall.schedule)\n\n    def add_request(self, request):\n        self.inprogress.add(request)\n\n    def remove_request(self, request):\n        self.inprogress.remove(request)\n        self._maybe_fire_closing()\n\n    def close(self):\n        self.closing = defer.Deferred()\n        self._maybe_fire_closing()\n        return self.closing\n\n    def _maybe_fire_closing(self):\n        if self.closing and not self.inprogress:\n            if self.nextcall:\n                self.nextcall.cancel()\n                if self.heartbeat.running:\n                    self.heartbeat.stop()\n            self.closing.callback(None)\n\n\nclass ExecutionEngine(object):\n\n    def __init__(self, crawler, spider_closed_callback):\n        self.crawler = crawler\n        self.settings = crawler.settings\n        self.signals = crawler.signals\n        self.logformatter = crawler.logformatter\n        self.slot = None\n        self.spider = None\n        self.running = False\n        self.paused = False\n        self.scheduler_cls = load_object(self.settings['SCHEDULER'])\n        downloader_cls = load_object(self.settings['DOWNLOADER'])\n        self.downloader = downloader_cls(crawler)\n        self.scraper = Scraper(crawler)\n        self._spider_closed_callback = spider_closed_callback\n\n    @defer.inlineCallbacks\n    def start(self):\n        \"\"\"Start the execution engine\"\"\"\n        assert not self.running, \"Engine already running\"\n        self.start_time = time()\n        yield self.signals.send_catch_log_deferred(signal=signals.engine_started)\n        self.running = True\n        self._closewait = defer.Deferred()\n        yield self._closewait\n\n    def stop(self):\n        \"\"\"Stop the execution engine gracefully\"\"\"\n        assert self.running, \"Engine not running\"\n        self.running = False\n        dfd = self._close_all_spiders()\n        return dfd.addBoth(lambda _: self._finish_stopping_engine())\n\n    def close(self):\n        \"\"\"Close the execution engine gracefully.\n\n        If it has already been started, stop it. In all cases, close all spiders\n        and the downloader.\n        \"\"\"\n        if self.running:\n            # Will also close spiders and downloader\n            return self.stop()\n        elif self.open_spiders:\n            # Will also close downloader\n            return self._close_all_spiders()\n        else:\n            return defer.succeed(self.downloader.close())\n\n    def pause(self):\n        \"\"\"Pause the execution engine\"\"\"\n        self.paused = True\n\n    def unpause(self):\n        \"\"\"Resume the execution engine\"\"\"\n        self.paused = False\n\n    def _next_request(self, spider):\n        slot = self.slot\n        if not slot:\n            return\n\n        if self.paused:\n            return\n\n        while not self._needs_backout(spider):\n            if not self._next_request_from_scheduler(spider):\n                break\n\n        if slot.start_requests and not self._needs_backout(spider):\n            try:\n                request = next(slot.start_requests)\n            except StopIteration:\n                slot.start_requests = None\n            except Exception:\n                slot.start_requests = None\n                logger.error('Error while obtaining start requests',\n                             exc_info=True, extra={'spider': spider})\n            else:\n                self.crawl(request, spider)\n\n        if self.spider_is_idle(spider) and slot.close_if_idle:\n            self._spider_idle(spider)\n\n    def _needs_backout(self, spider):\n        slot = self.slot\n        return not self.running \\\n            or slot.closing \\\n            or self.downloader.needs_backout() \\\n            or self.scraper.slot.needs_backout()\n\n    def _next_request_from_scheduler(self, spider):\n        slot = self.slot\n        request = slot.scheduler.next_request()\n        if not request:\n            return\n        d = self._download(request, spider)\n        d.addBoth(self._handle_downloader_output, request, spider)\n        d.addErrback(lambda f: logger.info('Error while handling downloader output',\n                                           exc_info=failure_to_exc_info(f),\n                                           extra={'spider': spider}))\n        d.addBoth(lambda _: slot.remove_request(request))\n        d.addErrback(lambda f: logger.info('Error while removing request from slot',\n                                           exc_info=failure_to_exc_info(f),\n                                           extra={'spider': spider}))\n        d.addBoth(lambda _: slot.nextcall.schedule())\n        d.addErrback(lambda f: logger.info('Error while scheduling new request',\n                                           exc_info=failure_to_exc_info(f),\n                                           extra={'spider': spider}))\n        return d\n\n    def _handle_downloader_output(self, response, request, spider):\n        assert isinstance(response, (Request, Response, Failure)), response\n        # downloader middleware can return requests (for example, redirects)\n        if isinstance(response, Request):\n            self.crawl(response, spider)\n            return\n        # response is a Response or Failure\n        d = self.scraper.enqueue_scrape(response, request, spider)\n        d.addErrback(lambda f: logger.error('Error while enqueuing downloader output',\n                                            exc_info=failure_to_exc_info(f),\n                                            extra={'spider': spider}))\n        return d\n\n    def spider_is_idle(self, spider):\n        if not self.scraper.slot.is_idle():\n            # scraper is not idle\n            return False\n\n        if self.downloader.active:\n            # downloader has pending requests\n            return False\n\n        if self.slot.start_requests is not None:\n            # not all start requests are handled\n            return False\n\n        if self.slot.scheduler.has_pending_requests():\n            # scheduler has pending requests\n            return False\n\n        return True\n\n    @property\n    def open_spiders(self):\n        return [self.spider] if self.spider else []\n\n    def has_capacity(self):\n        \"\"\"Does the engine have capacity to handle more spiders\"\"\"\n        return not bool(self.slot)\n\n    def crawl(self, request, spider):\n        assert spider in self.open_spiders, \\\n            \"Spider %r not opened when crawling: %s\" % (spider.name, request)\n        self.schedule(request, spider)\n        self.slot.nextcall.schedule()\n\n    def schedule(self, request, spider):\n        self.signals.send_catch_log(signal=signals.request_scheduled,\n                request=request, spider=spider)\n        if not self.slot.scheduler.enqueue_request(request):\n            self.signals.send_catch_log(signal=signals.request_dropped,\n                                        request=request, spider=spider)\n\n    def download(self, request, spider):\n        d = self._download(request, spider)\n        d.addBoth(self._downloaded, self.slot, request, spider)\n        return d\n\n    def _downloaded(self, response, slot, request, spider):\n        slot.remove_request(request)\n        return self.download(response, spider) \\\n                if isinstance(response, Request) else response\n\n    def _download(self, request, spider):\n        slot = self.slot\n        slot.add_request(request)\n        def _on_success(response):\n            assert isinstance(response, (Response, Request))\n            if isinstance(response, Response):\n                response.request = request # tie request to response received\n                logkws = self.logformatter.crawled(request, response, spider)\n                logger.log(*logformatter_adapter(logkws), extra={'spider': spider})\n                self.signals.send_catch_log(signal=signals.response_received, \\\n                    response=response, request=request, spider=spider)\n            return response\n\n        def _on_complete(_):\n            slot.nextcall.schedule()\n            return _\n\n        dwld = self.downloader.fetch(request, spider)\n        dwld.addCallbacks(_on_success)\n        dwld.addBoth(_on_complete)\n        return dwld\n\n    @defer.inlineCallbacks\n    def open_spider(self, spider, start_requests=(), close_if_idle=True):\n        assert self.has_capacity(), \"No free spider slot when opening %r\" % \\\n            spider.name\n        logger.info(\"Spider opened\", extra={'spider': spider})\n        nextcall = CallLaterOnce(self._next_request, spider)\n        scheduler = self.scheduler_cls.from_crawler(self.crawler)\n        start_requests = yield self.scraper.spidermw.process_start_requests(start_requests, spider)\n        slot = Slot(start_requests, close_if_idle, nextcall, scheduler)\n        self.slot = slot\n        self.spider = spider\n        yield scheduler.open(spider)\n        yield self.scraper.open_spider(spider)\n        self.crawler.stats.open_spider(spider)\n        yield self.signals.send_catch_log_deferred(signals.spider_opened, spider=spider)\n        slot.nextcall.schedule()\n        slot.heartbeat.start(5)\n\n    def _spider_idle(self, spider):\n        \"\"\"Called when a spider gets idle. This function is called when there\n        are no remaining pages to download or schedule. It can be called\n        multiple times. If some extension raises a DontCloseSpider exception\n        (in the spider_idle signal handler) the spider is not closed until the\n        next loop and this function is guaranteed to be called (at least) once\n        again for this spider.\n        \"\"\"\n        res = self.signals.send_catch_log(signal=signals.spider_idle, \\\n            spider=spider, dont_log=DontCloseSpider)\n        if any(isinstance(x, Failure) and isinstance(x.value, DontCloseSpider) \\\n                for _, x in res):\n            return\n\n        if self.spider_is_idle(spider):\n            self.close_spider(spider, reason='finished')\n\n    def close_spider(self, spider, reason='cancelled'):\n        \"\"\"Close (cancel) spider and clear all its outstanding requests\"\"\"\n\n        slot = self.slot\n        if slot.closing:\n            return slot.closing\n        logger.info(\"Closing spider (%(reason)s)\",\n                    {'reason': reason},\n                    extra={'spider': spider})\n\n        dfd = slot.close()\n\n        def log_failure(msg):\n            def errback(failure):\n                logger.error(\n                    msg,\n                    exc_info=failure_to_exc_info(failure),\n                    extra={'spider': spider}\n                )\n            return errback\n\n        dfd.addBoth(lambda _: self.downloader.close())\n        dfd.addErrback(log_failure('Downloader close failure'))\n\n        dfd.addBoth(lambda _: self.scraper.close_spider(spider))\n        dfd.addErrback(log_failure('Scraper close failure'))\n\n        dfd.addBoth(lambda _: slot.scheduler.close(reason))\n        dfd.addErrback(log_failure('Scheduler close failure'))\n\n        dfd.addBoth(lambda _: self.signals.send_catch_log_deferred(\n            signal=signals.spider_closed, spider=spider, reason=reason))\n        dfd.addErrback(log_failure('Error while sending spider_close signal'))\n\n        dfd.addBoth(lambda _: self.crawler.stats.close_spider(spider, reason=reason))\n        dfd.addErrback(log_failure('Stats close failure'))\n\n        dfd.addBoth(lambda _: logger.info(\"Spider closed (%(reason)s)\",\n                                          {'reason': reason},\n                                          extra={'spider': spider}))\n\n        dfd.addBoth(lambda _: setattr(self, 'slot', None))\n        dfd.addErrback(log_failure('Error while unassigning slot'))\n\n        dfd.addBoth(lambda _: setattr(self, 'spider', None))\n        dfd.addErrback(log_failure('Error while unassigning spider'))\n\n        dfd.addBoth(lambda _: self._spider_closed_callback(spider))\n\n        return dfd\n\n    def _close_all_spiders(self):\n        dfds = [self.close_spider(s, reason='shutdown') for s in self.open_spiders]\n        dlist = defer.DeferredList(dfds)\n        return dlist\n\n    @defer.inlineCallbacks\n    def _finish_stopping_engine(self):\n        yield self.signals.send_catch_log_deferred(signal=signals.engine_stopped)\n        self._closewait.callback(None)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/scheduler.py",
    "content": "import os\nimport json\nimport logging\nimport warnings\nfrom os.path import join, exists\n\nfrom queuelib import PriorityQueue\n\nfrom scrapy.utils.misc import load_object, create_instance\nfrom scrapy.utils.job import job_dir\nfrom scrapy.utils.deprecate import ScrapyDeprecationWarning\n\n\nlogger = logging.getLogger(__name__)\n\n\nclass Scheduler(object):\n    \"\"\"\n    Scrapy Scheduler. It allows to enqueue requests and then get\n    a next request to download. Scheduler is also handling duplication\n    filtering, via dupefilter.\n\n    Prioritization and queueing is not performed by the Scheduler.\n    User sets ``priority`` field for each Request, and a PriorityQueue\n    (defined by :setting:`SCHEDULER_PRIORITY_QUEUE`) uses these priorities\n    to dequeue requests in a desired order.\n\n    Scheduler uses two PriorityQueue instances, configured to work in-memory\n    and on-disk (optional). When on-disk queue is present, it is used by\n    default, and an in-memory queue is used as a fallback for cases where\n    a disk queue can't handle a request (can't serialize it).\n\n    :setting:`SCHEDULER_MEMORY_QUEUE` and\n    :setting:`SCHEDULER_DISK_QUEUE` allow to specify lower-level queue classes\n    which PriorityQueue instances would be instantiated with, to keep requests\n    on disk and in memory respectively.\n\n    Overall, Scheduler is an object which holds several PriorityQueue instances\n    (in-memory and on-disk) and implements fallback logic for them.\n    Also, it handles dupefilters.\n    \"\"\"\n    def __init__(self, dupefilter, jobdir=None, dqclass=None, mqclass=None,\n                 logunser=False, stats=None, pqclass=None, crawler=None):\n        self.df = dupefilter\n        self.dqdir = self._dqdir(jobdir)\n        self.pqclass = pqclass\n        self.dqclass = dqclass\n        self.mqclass = mqclass\n        self.logunser = logunser\n        self.stats = stats\n        self.crawler = crawler\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        settings = crawler.settings\n        dupefilter_cls = load_object(settings['DUPEFILTER_CLASS'])\n        dupefilter = create_instance(dupefilter_cls, settings, crawler)\n        pqclass = load_object(settings['SCHEDULER_PRIORITY_QUEUE'])\n        if pqclass is PriorityQueue:\n            warnings.warn(\"SCHEDULER_PRIORITY_QUEUE='queuelib.PriorityQueue'\"\n                          \" is no longer supported because of API changes; \"\n                          \"please use 'scrapy.pqueues.ScrapyPriorityQueue'\",\n                          ScrapyDeprecationWarning)\n            from scrapy.pqueues import ScrapyPriorityQueue\n            pqclass = ScrapyPriorityQueue\n\n        dqclass = load_object(settings['SCHEDULER_DISK_QUEUE'])\n        mqclass = load_object(settings['SCHEDULER_MEMORY_QUEUE'])\n        logunser = settings.getbool('LOG_UNSERIALIZABLE_REQUESTS',\n                                    settings.getbool('SCHEDULER_DEBUG'))\n        return cls(dupefilter, jobdir=job_dir(settings), logunser=logunser,\n                   stats=crawler.stats, pqclass=pqclass, dqclass=dqclass,\n                   mqclass=mqclass, crawler=crawler)\n\n    def has_pending_requests(self):\n        return len(self) > 0\n\n    def open(self, spider):\n        self.spider = spider\n        self.mqs = self._mq()\n        self.dqs = self._dq() if self.dqdir else None\n        return self.df.open()\n\n    def close(self, reason):\n        if self.dqs:\n            state = self.dqs.close()\n            self._write_dqs_state(self.dqdir, state)\n        return self.df.close(reason)\n\n    def enqueue_request(self, request):\n        if not request.dont_filter and self.df.request_seen(request):\n            self.df.log(request, self.spider)\n            return False\n        dqok = self._dqpush(request)\n        if dqok:\n            self.stats.inc_value('scheduler/enqueued/disk', spider=self.spider)\n        else:\n            self._mqpush(request)\n            self.stats.inc_value('scheduler/enqueued/memory', spider=self.spider)\n        self.stats.inc_value('scheduler/enqueued', spider=self.spider)\n        return True\n\n    def next_request(self):\n        request = self.mqs.pop()\n        if request:\n            self.stats.inc_value('scheduler/dequeued/memory', spider=self.spider)\n        else:\n            request = self._dqpop()\n            if request:\n                self.stats.inc_value('scheduler/dequeued/disk', spider=self.spider)\n        if request:\n            self.stats.inc_value('scheduler/dequeued', spider=self.spider)\n        return request\n\n    def __len__(self):\n        return len(self.dqs) + len(self.mqs) if self.dqs else len(self.mqs)\n\n    def _dqpush(self, request):\n        if self.dqs is None:\n            return\n        try:\n            self.dqs.push(request, -request.priority)\n        except ValueError as e:  # non serializable request\n            if self.logunser:\n                msg = (\"Unable to serialize request: %(request)s - reason:\"\n                       \" %(reason)s - no more unserializable requests will be\"\n                       \" logged (stats being collected)\")\n                logger.warning(msg, {'request': request, 'reason': e},\n                               exc_info=True, extra={'spider': self.spider})\n                self.logunser = False\n            self.stats.inc_value('scheduler/unserializable',\n                                 spider=self.spider)\n            return\n        else:\n            return True\n\n    def _mqpush(self, request):\n        self.mqs.push(request, -request.priority)\n\n    def _dqpop(self):\n        if self.dqs:\n            return self.dqs.pop()\n\n    def _newmq(self, priority):\n        \"\"\" Factory for creating memory queues. \"\"\"\n        return self.mqclass()\n\n    def _newdq(self, priority):\n        \"\"\" Factory for creating disk queues. \"\"\"\n        path = join(self.dqdir, 'p%s' % (priority, ))\n        return self.dqclass(path)\n\n    def _mq(self):\n        \"\"\" Create a new priority queue instance, with in-memory storage \"\"\"\n        return create_instance(self.pqclass, None, self.crawler, self._newmq,\n                               serialize=False)\n\n    def _dq(self):\n        \"\"\" Create a new priority queue instance, with disk storage \"\"\"\n        state = self._read_dqs_state(self.dqdir)\n        q = create_instance(self.pqclass,\n                            None,\n                            self.crawler,\n                            self._newdq,\n                            state,\n                            serialize=True)\n        if q:\n            logger.info(\"Resuming crawl (%(queuesize)d requests scheduled)\",\n                        {'queuesize': len(q)}, extra={'spider': self.spider})\n        return q\n\n    def _dqdir(self, jobdir):\n        \"\"\" Return a folder name to keep disk queue state at \"\"\"\n        if jobdir:\n            dqdir = join(jobdir, 'requests.queue')\n            if not exists(dqdir):\n                os.makedirs(dqdir)\n            return dqdir\n\n    def _read_dqs_state(self, dqdir):\n        path = join(dqdir, 'active.json')\n        if not exists(path):\n            return ()\n        with open(path) as f:\n            return json.load(f)\n\n    def _write_dqs_state(self, dqdir, state):\n        with open(join(dqdir, 'active.json'), 'w') as f:\n            json.dump(state, f)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/scraper.py",
    "content": "\"\"\"This module implements the Scraper component which parses responses and\nextracts information from them\"\"\"\n\nimport logging\nfrom collections import deque\n\nfrom twisted.python.failure import Failure\nfrom twisted.internet import defer\n\nfrom scrapy.utils.defer import defer_result, defer_succeed, parallel, iter_errback\nfrom scrapy.utils.spider import iterate_spider_output\nfrom scrapy.utils.misc import load_object\nfrom scrapy.utils.log import logformatter_adapter, failure_to_exc_info\nfrom scrapy.exceptions import CloseSpider, DropItem, IgnoreRequest\nfrom scrapy import signals\nfrom scrapy.http import Request, Response\nfrom scrapy.item import BaseItem\nfrom scrapy.core.spidermw import SpiderMiddlewareManager\nfrom scrapy.utils.request import referer_str\n\nlogger = logging.getLogger(__name__)\n\n\nclass Slot(object):\n    \"\"\"Scraper slot (one per running spider)\"\"\"\n\n    MIN_RESPONSE_SIZE = 1024\n\n    def __init__(self, max_active_size=5000000):\n        self.max_active_size = max_active_size\n        self.queue = deque()\n        self.active = set()\n        self.active_size = 0\n        self.itemproc_size = 0\n        self.closing = None\n\n    def add_response_request(self, response, request):\n        deferred = defer.Deferred()\n        self.queue.append((response, request, deferred))\n        if isinstance(response, Response):\n            self.active_size += max(len(response.body), self.MIN_RESPONSE_SIZE)\n        else:\n            self.active_size += self.MIN_RESPONSE_SIZE\n        return deferred\n\n    def next_response_request_deferred(self):\n        response, request, deferred = self.queue.popleft()\n        self.active.add(request)\n        return response, request, deferred\n\n    def finish_response(self, response, request):\n        self.active.remove(request)\n        if isinstance(response, Response):\n            self.active_size -= max(len(response.body), self.MIN_RESPONSE_SIZE)\n        else:\n            self.active_size -= self.MIN_RESPONSE_SIZE\n\n    def is_idle(self):\n        return not (self.queue or self.active)\n\n    def needs_backout(self):\n        return self.active_size > self.max_active_size\n\n\nclass Scraper(object):\n\n    def __init__(self, crawler):\n        self.slot = None\n        self.spidermw = SpiderMiddlewareManager.from_crawler(crawler)\n        itemproc_cls = load_object(crawler.settings['ITEM_PROCESSOR'])\n        self.itemproc = itemproc_cls.from_crawler(crawler)\n        self.concurrent_items = crawler.settings.getint('CONCURRENT_ITEMS')\n        self.crawler = crawler\n        self.signals = crawler.signals\n        self.logformatter = crawler.logformatter\n\n    @defer.inlineCallbacks\n    def open_spider(self, spider):\n        \"\"\"Open the given spider for scraping and allocate resources for it\"\"\"\n        self.slot = Slot()\n        yield self.itemproc.open_spider(spider)\n\n    def close_spider(self, spider):\n        \"\"\"Close a spider being scraped and release its resources\"\"\"\n        slot = self.slot\n        slot.closing = defer.Deferred()\n        slot.closing.addCallback(self.itemproc.close_spider)\n        self._check_if_closing(spider, slot)\n        return slot.closing\n\n    def is_idle(self):\n        \"\"\"Return True if there isn't any more spiders to process\"\"\"\n        return not self.slot\n\n    def _check_if_closing(self, spider, slot):\n        if slot.closing and slot.is_idle():\n            slot.closing.callback(spider)\n\n    def enqueue_scrape(self, response, request, spider):\n        slot = self.slot\n        dfd = slot.add_response_request(response, request)\n        def finish_scraping(_):\n            slot.finish_response(response, request)\n            self._check_if_closing(spider, slot)\n            self._scrape_next(spider, slot)\n            return _\n        dfd.addBoth(finish_scraping)\n        dfd.addErrback(\n            lambda f: logger.error('Scraper bug processing %(request)s',\n                                   {'request': request},\n                                   exc_info=failure_to_exc_info(f),\n                                   extra={'spider': spider}))\n        self._scrape_next(spider, slot)\n        return dfd\n\n    def _scrape_next(self, spider, slot):\n        while slot.queue:\n            response, request, deferred = slot.next_response_request_deferred()\n            self._scrape(response, request, spider).chainDeferred(deferred)\n\n    def _scrape(self, response, request, spider):\n        \"\"\"Handle the downloaded response or failure through the spider\n        callback/errback\"\"\"\n        assert isinstance(response, (Response, Failure))\n\n        dfd = self._scrape2(response, request, spider) # returns spiders processed output\n        dfd.addErrback(self.handle_spider_error, request, response, spider)\n        dfd.addCallback(self.handle_spider_output, request, response, spider)\n        return dfd\n\n    def _scrape2(self, request_result, request, spider):\n        \"\"\"Handle the different cases of request's result been a Response or a\n        Failure\"\"\"\n        if not isinstance(request_result, Failure):\n            return self.spidermw.scrape_response(\n                self.call_spider, request_result, request, spider)\n        else:\n            dfd = self.call_spider(request_result, request, spider)\n            return dfd.addErrback(\n                self._log_download_errors, request_result, request, spider)\n\n    def call_spider(self, result, request, spider):\n        result.request = request\n        dfd = defer_result(result)\n        dfd.addCallbacks(callback=request.callback or spider.parse,\n                         errback=request.errback,\n                         callbackKeywords=request.cb_kwargs)\n        return dfd.addCallback(iterate_spider_output)\n\n    def handle_spider_error(self, _failure, request, response, spider):\n        exc = _failure.value\n        if isinstance(exc, CloseSpider):\n            self.crawler.engine.close_spider(spider, exc.reason or 'cancelled')\n            return\n        logger.error(\n            \"Spider error processing %(request)s (referer: %(referer)s)\",\n            {'request': request, 'referer': referer_str(request)},\n            exc_info=failure_to_exc_info(_failure),\n            extra={'spider': spider}\n        )\n        self.signals.send_catch_log(\n            signal=signals.spider_error,\n            failure=_failure, response=response,\n            spider=spider\n        )\n        self.crawler.stats.inc_value(\n            \"spider_exceptions/%s\" % _failure.value.__class__.__name__,\n            spider=spider\n        )\n\n    def handle_spider_output(self, result, request, response, spider):\n        if not result:\n            return defer_succeed(None)\n        it = iter_errback(result, self.handle_spider_error, request, response, spider)\n        dfd = parallel(it, self.concurrent_items,\n            self._process_spidermw_output, request, response, spider)\n        return dfd\n\n    def _process_spidermw_output(self, output, request, response, spider):\n        \"\"\"Process each Request/Item (given in the output parameter) returned\n        from the given spider\n        \"\"\"\n        if isinstance(output, Request):\n            self.crawler.engine.crawl(request=output, spider=spider)\n        elif isinstance(output, (BaseItem, dict)):\n            self.slot.itemproc_size += 1\n            dfd = self.itemproc.process_item(output, spider)\n            dfd.addBoth(self._itemproc_finished, output, response, spider)\n            return dfd\n        elif output is None:\n            pass\n        else:\n            typename = type(output).__name__\n            logger.error('Spider must return Request, BaseItem, dict or None, '\n                         'got %(typename)r in %(request)s',\n                         {'request': request, 'typename': typename},\n                         extra={'spider': spider})\n\n    def _log_download_errors(self, spider_failure, download_failure, request, spider):\n        \"\"\"Log and silence errors that come from the engine (typically download\n        errors that got propagated thru here)\n        \"\"\"\n        if (isinstance(download_failure, Failure) and\n                not download_failure.check(IgnoreRequest)):\n            if download_failure.frames:\n                logger.error('Error downloading %(request)s',\n                             {'request': request},\n                             exc_info=failure_to_exc_info(download_failure),\n                             extra={'spider': spider})\n            else:\n                errmsg = download_failure.getErrorMessage()\n                if errmsg:\n                    logger.error('Error downloading %(request)s: %(errmsg)s',\n                                 {'request': request, 'errmsg': errmsg},\n                                 extra={'spider': spider})\n\n        if spider_failure is not download_failure:\n            return spider_failure\n\n    def _itemproc_finished(self, output, item, response, spider):\n        \"\"\"ItemProcessor finished for the given ``item`` and returned ``output``\n        \"\"\"\n        self.slot.itemproc_size -= 1\n        if isinstance(output, Failure):\n            ex = output.value\n            if isinstance(ex, DropItem):\n                logkws = self.logformatter.dropped(item, ex, response, spider)\n                logger.log(*logformatter_adapter(logkws), extra={'spider': spider})\n                return self.signals.send_catch_log_deferred(\n                    signal=signals.item_dropped, item=item, response=response,\n                    spider=spider, exception=output.value)\n            else:\n                logger.error('Error processing %(item)s', {'item': item},\n                             exc_info=failure_to_exc_info(output),\n                             extra={'spider': spider})\n                return self.signals.send_catch_log_deferred(\n                    signal=signals.item_error, item=item, response=response,\n                    spider=spider, failure=output)\n        else:\n            logkws = self.logformatter.scraped(output, response, spider)\n            logger.log(*logformatter_adapter(logkws), extra={'spider': spider})\n            return self.signals.send_catch_log_deferred(\n                signal=signals.item_scraped, item=output, response=response,\n                spider=spider)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/core/spidermw.py",
    "content": "\"\"\"\nSpider Middleware manager\n\nSee documentation in docs/topics/spider-middleware.rst\n\"\"\"\nfrom itertools import chain, islice\n\nimport six\nfrom twisted.python.failure import Failure\nfrom scrapy.exceptions import _InvalidOutput\nfrom scrapy.middleware import MiddlewareManager\nfrom scrapy.utils.defer import mustbe_deferred\nfrom scrapy.utils.conf import build_component_list\nfrom scrapy.utils.python import MutableChain\n\n\ndef _isiterable(possible_iterator):\n    return hasattr(possible_iterator, '__iter__')\n\n\nclass SpiderMiddlewareManager(MiddlewareManager):\n\n    component_name = 'spider middleware'\n\n    @classmethod\n    def _get_mwlist_from_settings(cls, settings):\n        return build_component_list(settings.getwithbase('SPIDER_MIDDLEWARES'))\n\n    def _add_middleware(self, mw):\n        super(SpiderMiddlewareManager, self)._add_middleware(mw)\n        if hasattr(mw, 'process_spider_input'):\n            self.methods['process_spider_input'].append(mw.process_spider_input)\n        if hasattr(mw, 'process_start_requests'):\n            self.methods['process_start_requests'].appendleft(mw.process_start_requests)\n        self.methods['process_spider_output'].appendleft(getattr(mw, 'process_spider_output', None))\n        self.methods['process_spider_exception'].appendleft(getattr(mw, 'process_spider_exception', None))\n\n    def scrape_response(self, scrape_func, response, request, spider):\n        fname = lambda f:'%s.%s' % (\n                six.get_method_self(f).__class__.__name__,\n                six.get_method_function(f).__name__)\n\n        def process_spider_input(response):\n            for method in self.methods['process_spider_input']:\n                try:\n                    result = method(response=response, spider=spider)\n                    if result is not None:\n                        raise _InvalidOutput('Middleware {} must return None or raise an exception, got {}' \\\n                                             .format(fname(method), type(result)))\n                except _InvalidOutput:\n                    raise\n                except Exception:\n                    return scrape_func(Failure(), request, spider)\n            return scrape_func(response, request, spider)\n\n        def process_spider_exception(_failure, start_index=0):\n            exception = _failure.value\n            # don't handle _InvalidOutput exception\n            if isinstance(exception, _InvalidOutput):\n                return _failure\n            method_list = islice(self.methods['process_spider_exception'], start_index, None)\n            for method_index, method in enumerate(method_list, start=start_index):\n                if method is None:\n                    continue\n                result = method(response=response, exception=exception, spider=spider)\n                if _isiterable(result):\n                    # stop exception handling by handing control over to the\n                    # process_spider_output chain if an iterable has been returned\n                    return process_spider_output(result, method_index+1)\n                elif result is None:\n                    continue\n                else:\n                    raise _InvalidOutput('Middleware {} must return None or an iterable, got {}' \\\n                                         .format(fname(method), type(result)))\n            return _failure\n\n        def process_spider_output(result, start_index=0):\n            # items in this iterable do not need to go through the process_spider_output\n            # chain, they went through it already from the process_spider_exception method\n            recovered = MutableChain()\n\n            def evaluate_iterable(iterable, index):\n                try:\n                    for r in iterable:\n                        yield r\n                except Exception as ex:\n                    exception_result = process_spider_exception(Failure(ex), index+1)\n                    if isinstance(exception_result, Failure):\n                        raise\n                    recovered.extend(exception_result)\n\n            method_list = islice(self.methods['process_spider_output'], start_index, None)\n            for method_index, method in enumerate(method_list, start=start_index):\n                if method is None:\n                    continue\n                # the following might fail directly if the output value is not a generator\n                try:\n                    result = method(response=response, result=result, spider=spider)\n                except Exception as ex:\n                    exception_result = process_spider_exception(Failure(ex), method_index+1)\n                    if isinstance(exception_result, Failure):\n                        raise\n                    return exception_result\n                if _isiterable(result):\n                    result = evaluate_iterable(result, method_index)\n                else:\n                    raise _InvalidOutput('Middleware {} must return an iterable, got {}' \\\n                                         .format(fname(method), type(result)))\n\n            return chain(result, recovered)\n\n        dfd = mustbe_deferred(process_spider_input, response)\n        dfd.addCallbacks(callback=process_spider_output, errback=process_spider_exception)\n        return dfd\n\n    def process_start_requests(self, start_requests, spider):\n        return self._process_chain('process_start_requests', start_requests, spider)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/crawler.py",
    "content": "import six\nimport signal\nimport logging\nimport warnings\n\nimport sys\nfrom twisted.internet import reactor, defer\nfrom zope.interface.verify import verifyClass, DoesNotImplement\n\nfrom scrapy import Spider\nfrom scrapy.core.engine import ExecutionEngine\nfrom scrapy.resolver import CachingThreadedResolver\nfrom scrapy.interfaces import ISpiderLoader\nfrom scrapy.extension import ExtensionManager\nfrom scrapy.settings import overridden_settings, Settings\nfrom scrapy.signalmanager import SignalManager\nfrom scrapy.exceptions import ScrapyDeprecationWarning\nfrom scrapy.utils.ossignal import install_shutdown_handlers, signal_names\nfrom scrapy.utils.misc import load_object\nfrom scrapy.utils.log import (\n    LogCounterHandler, configure_logging, log_scrapy_info,\n    get_scrapy_root_handler, install_scrapy_root_handler)\nfrom scrapy import signals\n\nlogger = logging.getLogger(__name__)\n\n\nclass Crawler(object):\n\n    def __init__(self, spidercls, settings=None):\n        if isinstance(spidercls, Spider):\n            raise ValueError(\n                'The spidercls argument must be a class, not an object')\n\n        if isinstance(settings, dict) or settings is None:\n            settings = Settings(settings)\n\n        self.spidercls = spidercls\n        self.settings = settings.copy()\n        self.spidercls.update_settings(self.settings)\n\n        self.signals = SignalManager(self)\n        self.stats = load_object(self.settings['STATS_CLASS'])(self)\n\n        handler = LogCounterHandler(self, level=self.settings.get('LOG_LEVEL'))\n        logging.root.addHandler(handler)\n\n        d = dict(overridden_settings(self.settings))\n        logger.info(\"Overridden settings: %(settings)r\", {'settings': d})\n\n        if get_scrapy_root_handler() is not None:\n            # scrapy root handler already installed: update it with new settings\n            install_scrapy_root_handler(self.settings)\n        # lambda is assigned to Crawler attribute because this way it is not\n        # garbage collected after leaving __init__ scope\n        self.__remove_handler = lambda: logging.root.removeHandler(handler)\n        self.signals.connect(self.__remove_handler, signals.engine_stopped)\n\n        lf_cls = load_object(self.settings['LOG_FORMATTER'])\n        self.logformatter = lf_cls.from_crawler(self)\n        self.extensions = ExtensionManager.from_crawler(self)\n\n        self.settings.freeze()\n        self.crawling = False\n        self.spider = None\n        self.engine = None\n\n    @property\n    def spiders(self):\n        if not hasattr(self, '_spiders'):\n            warnings.warn(\"Crawler.spiders is deprecated, use \"\n                          \"CrawlerRunner.spider_loader or instantiate \"\n                          \"scrapy.spiderloader.SpiderLoader with your \"\n                          \"settings.\",\n                          category=ScrapyDeprecationWarning, stacklevel=2)\n            self._spiders = _get_spider_loader(self.settings.frozencopy())\n        return self._spiders\n\n    @defer.inlineCallbacks\n    def crawl(self, *args, **kwargs):\n        assert not self.crawling, \"Crawling already taking place\"\n        self.crawling = True\n\n        try:\n            self.spider = self._create_spider(*args, **kwargs)\n            self.engine = self._create_engine()\n            start_requests = iter(self.spider.start_requests())\n            yield self.engine.open_spider(self.spider, start_requests)\n            yield defer.maybeDeferred(self.engine.start)\n        except Exception:\n            # In Python 2 reraising an exception after yield discards\n            # the original traceback (see https://bugs.python.org/issue7563),\n            # so sys.exc_info() workaround is used.\n            # This workaround also works in Python 3, but it is not needed,\n            # and it is slower, so in Python 3 we use native `raise`.\n            if six.PY2:\n                exc_info = sys.exc_info()\n\n            self.crawling = False\n            if self.engine is not None:\n                yield self.engine.close()\n\n            if six.PY2:\n                six.reraise(*exc_info)\n            raise\n\n    def _create_spider(self, *args, **kwargs):\n        return self.spidercls.from_crawler(self, *args, **kwargs)\n\n    def _create_engine(self):\n        return ExecutionEngine(self, lambda _: self.stop())\n\n    @defer.inlineCallbacks\n    def stop(self):\n        \"\"\"Starts a graceful stop of the crawler and returns a deferred that is\n        fired when the crawler is stopped.\"\"\"\n        if self.crawling:\n            self.crawling = False\n            yield defer.maybeDeferred(self.engine.stop)\n\n\nclass CrawlerRunner(object):\n    \"\"\"\n    This is a convenient helper class that keeps track of, manages and runs\n    crawlers inside an already setup Twisted `reactor`_.\n\n    The CrawlerRunner object must be instantiated with a\n    :class:`~scrapy.settings.Settings` object.\n\n    This class shouldn't be needed (since Scrapy is responsible of using it\n    accordingly) unless writing scripts that manually handle the crawling\n    process. See :ref:`run-from-script` for an example.\n    \"\"\"\n\n    crawlers = property(\n        lambda self: self._crawlers,\n        doc=\"Set of :class:`crawlers <scrapy.crawler.Crawler>` started by \"\n            \":meth:`crawl` and managed by this class.\"\n    )\n\n    def __init__(self, settings=None):\n        if isinstance(settings, dict) or settings is None:\n            settings = Settings(settings)\n        self.settings = settings\n        self.spider_loader = _get_spider_loader(settings)\n        self._crawlers = set()\n        self._active = set()\n        self.bootstrap_failed = False\n\n    @property\n    def spiders(self):\n        warnings.warn(\"CrawlerRunner.spiders attribute is renamed to \"\n                      \"CrawlerRunner.spider_loader.\",\n                      category=ScrapyDeprecationWarning, stacklevel=2)\n        return self.spider_loader\n\n    def crawl(self, crawler_or_spidercls, *args, **kwargs):\n        \"\"\"\n        Run a crawler with the provided arguments.\n\n        It will call the given Crawler's :meth:`~Crawler.crawl` method, while\n        keeping track of it so it can be stopped later.\n\n        If ``crawler_or_spidercls`` isn't a :class:`~scrapy.crawler.Crawler`\n        instance, this method will try to create one using this parameter as\n        the spider class given to it.\n\n        Returns a deferred that is fired when the crawling is finished.\n\n        :param crawler_or_spidercls: already created crawler, or a spider class\n            or spider's name inside the project to create it\n        :type crawler_or_spidercls: :class:`~scrapy.crawler.Crawler` instance,\n            :class:`~scrapy.spiders.Spider` subclass or string\n\n        :param list args: arguments to initialize the spider\n\n        :param dict kwargs: keyword arguments to initialize the spider\n        \"\"\"\n        if isinstance(crawler_or_spidercls, Spider):\n            raise ValueError(\n                'The crawler_or_spidercls argument cannot be a spider object, '\n                'it must be a spider class (or a Crawler object)')\n        crawler = self.create_crawler(crawler_or_spidercls)\n        return self._crawl(crawler, *args, **kwargs)\n\n    def _crawl(self, crawler, *args, **kwargs):\n        self.crawlers.add(crawler)\n        d = crawler.crawl(*args, **kwargs)\n        self._active.add(d)\n\n        def _done(result):\n            self.crawlers.discard(crawler)\n            self._active.discard(d)\n            self.bootstrap_failed |= not getattr(crawler, 'spider', None)\n            return result\n\n        return d.addBoth(_done)\n\n    def create_crawler(self, crawler_or_spidercls):\n        \"\"\"\n        Return a :class:`~scrapy.crawler.Crawler` object.\n\n        * If ``crawler_or_spidercls`` is a Crawler, it is returned as-is.\n        * If ``crawler_or_spidercls`` is a Spider subclass, a new Crawler\n          is constructed for it.\n        * If ``crawler_or_spidercls`` is a string, this function finds\n          a spider with this name in a Scrapy project (using spider loader),\n          then creates a Crawler instance for it.\n        \"\"\"\n        if isinstance(crawler_or_spidercls, Spider):\n            raise ValueError(\n                'The crawler_or_spidercls argument cannot be a spider object, '\n                'it must be a spider class (or a Crawler object)')\n        if isinstance(crawler_or_spidercls, Crawler):\n            return crawler_or_spidercls\n        return self._create_crawler(crawler_or_spidercls)\n\n    def _create_crawler(self, spidercls):\n        if isinstance(spidercls, six.string_types):\n            spidercls = self.spider_loader.load(spidercls)\n        return Crawler(spidercls, self.settings)\n\n    def stop(self):\n        \"\"\"\n        Stops simultaneously all the crawling jobs taking place.\n\n        Returns a deferred that is fired when they all have ended.\n        \"\"\"\n        return defer.DeferredList([c.stop() for c in list(self.crawlers)])\n\n    @defer.inlineCallbacks\n    def join(self):\n        \"\"\"\n        join()\n\n        Returns a deferred that is fired when all managed :attr:`crawlers` have\n        completed their executions.\n        \"\"\"\n        while self._active:\n            yield defer.DeferredList(self._active)\n\n\nclass CrawlerProcess(CrawlerRunner):\n    \"\"\"\n    A class to run multiple scrapy crawlers in a process simultaneously.\n\n    This class extends :class:`~scrapy.crawler.CrawlerRunner` by adding support\n    for starting a Twisted `reactor`_ and handling shutdown signals, like the\n    keyboard interrupt command Ctrl-C. It also configures top-level logging.\n\n    This utility should be a better fit than\n    :class:`~scrapy.crawler.CrawlerRunner` if you aren't running another\n    Twisted `reactor`_ within your application.\n\n    The CrawlerProcess object must be instantiated with a\n    :class:`~scrapy.settings.Settings` object.\n\n    :param install_root_handler: whether to install root logging handler\n        (default: True)\n\n    This class shouldn't be needed (since Scrapy is responsible of using it\n    accordingly) unless writing scripts that manually handle the crawling\n    process. See :ref:`run-from-script` for an example.\n    \"\"\"\n\n    def __init__(self, settings=None, install_root_handler=True):\n        super(CrawlerProcess, self).__init__(settings)\n        install_shutdown_handlers(self._signal_shutdown)\n        configure_logging(self.settings, install_root_handler)\n        log_scrapy_info(self.settings)\n\n    def _signal_shutdown(self, signum, _):\n        install_shutdown_handlers(self._signal_kill)\n        signame = signal_names[signum]\n        logger.info(\"Received %(signame)s, shutting down gracefully. Send again to force \",\n                    {'signame': signame})\n        reactor.callFromThread(self._graceful_stop_reactor)\n\n    def _signal_kill(self, signum, _):\n        install_shutdown_handlers(signal.SIG_IGN)\n        signame = signal_names[signum]\n        logger.info('Received %(signame)s twice, forcing unclean shutdown',\n                    {'signame': signame})\n        reactor.callFromThread(self._stop_reactor)\n\n    def start(self, stop_after_crawl=True):\n        \"\"\"\n        This method starts a Twisted `reactor`_, adjusts its pool size to\n        :setting:`REACTOR_THREADPOOL_MAXSIZE`, and installs a DNS cache based\n        on :setting:`DNSCACHE_ENABLED` and :setting:`DNSCACHE_SIZE`.\n\n        If ``stop_after_crawl`` is True, the reactor will be stopped after all\n        crawlers have finished, using :meth:`join`.\n\n        :param boolean stop_after_crawl: stop or not the reactor when all\n            crawlers have finished\n        \"\"\"\n        if stop_after_crawl:\n            d = self.join()\n            # Don't start the reactor if the deferreds are already fired\n            if d.called:\n                return\n            d.addBoth(self._stop_reactor)\n\n        reactor.installResolver(self._get_dns_resolver())\n        tp = reactor.getThreadPool()\n        tp.adjustPoolsize(maxthreads=self.settings.getint('REACTOR_THREADPOOL_MAXSIZE'))\n        reactor.addSystemEventTrigger('before', 'shutdown', self.stop)\n        reactor.run(installSignalHandlers=False)  # blocking call\n\n    def _get_dns_resolver(self):\n        if self.settings.getbool('DNSCACHE_ENABLED'):\n            cache_size = self.settings.getint('DNSCACHE_SIZE')\n        else:\n            cache_size = 0\n        return CachingThreadedResolver(\n            reactor=reactor,\n            cache_size=cache_size,\n            timeout=self.settings.getfloat('DNS_TIMEOUT')\n        )\n\n    def _graceful_stop_reactor(self):\n        d = self.stop()\n        d.addBoth(self._stop_reactor)\n        return d\n\n    def _stop_reactor(self, _=None):\n        try:\n            reactor.stop()\n        except RuntimeError:  # raised if already stopped or in shutdown stage\n            pass\n\n\ndef _get_spider_loader(settings):\n    \"\"\" Get SpiderLoader instance from settings \"\"\"\n    cls_path = settings.get('SPIDER_LOADER_CLASS')\n    loader_cls = load_object(cls_path)\n    try:\n        verifyClass(ISpiderLoader, loader_cls)\n    except DoesNotImplement:\n        warnings.warn(\n            'SPIDER_LOADER_CLASS (previously named SPIDER_MANAGER_CLASS) does '\n            'not fully implement scrapy.interfaces.ISpiderLoader interface. '\n            'Please add all missing methods to avoid unexpected runtime errors.',\n            category=ScrapyDeprecationWarning, stacklevel=2\n        )\n    return loader_cls.from_settings(settings.frozencopy())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/ajaxcrawl.py",
    "content": "# -*- coding: utf-8 -*-\nfrom __future__ import absolute_import\nimport re\nimport logging\n\nimport six\nfrom w3lib import html\n\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy.http import HtmlResponse\n\n\nlogger = logging.getLogger(__name__)\n\n\nclass AjaxCrawlMiddleware(object):\n    \"\"\"\n    Handle 'AJAX crawlable' pages marked as crawlable via meta tag.\n    For more info see https://developers.google.com/webmasters/ajax-crawling/docs/getting-started.\n    \"\"\"\n\n    def __init__(self, settings):\n        if not settings.getbool('AJAXCRAWL_ENABLED'):\n            raise NotConfigured\n\n        # XXX: Google parses at least first 100k bytes; scrapy's redirect\n        # middleware parses first 4k. 4k turns out to be insufficient\n        # for this middleware, and parsing 100k could be slow.\n        # We use something in between (32K) by default.\n        self.lookup_bytes = settings.getint('AJAXCRAWL_MAXSIZE', 32768)\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls(crawler.settings)\n\n    def process_response(self, request, response, spider):\n\n        if not isinstance(response, HtmlResponse) or response.status != 200:\n            return response\n\n        if request.method != 'GET':\n            # other HTTP methods are either not safe or don't have a body\n            return response\n\n        if 'ajax_crawlable' in request.meta:  # prevent loops\n            return response\n\n        if not self._has_ajax_crawlable_variant(response):\n            return response\n\n        # scrapy already handles #! links properly\n        ajax_crawl_request = request.replace(url=request.url+'#!')\n        logger.debug(\"Downloading AJAX crawlable %(ajax_crawl_request)s instead of %(request)s\",\n                     {'ajax_crawl_request': ajax_crawl_request, 'request': request},\n                     extra={'spider': spider})\n\n        ajax_crawl_request.meta['ajax_crawlable'] = True\n        return ajax_crawl_request\n\n    def _has_ajax_crawlable_variant(self, response):\n        \"\"\"\n        Return True if a page without hash fragment could be \"AJAX crawlable\"\n        according to https://developers.google.com/webmasters/ajax-crawling/docs/getting-started.\n        \"\"\"\n        body = response.text[:self.lookup_bytes]\n        return _has_ajaxcrawlable_meta(body)\n\n\n# XXX: move it to w3lib?\n_ajax_crawlable_re = re.compile(six.u(r'<meta\\s+name=[\"\\']fragment[\"\\']\\s+content=[\"\\']![\"\\']/?>'))\ndef _has_ajaxcrawlable_meta(text):\n    \"\"\"\n    >>> _has_ajaxcrawlable_meta('<html><head><meta name=\"fragment\"  content=\"!\"/></head><body></body></html>')\n    True\n    >>> _has_ajaxcrawlable_meta(\"<html><head><meta name='fragment' content='!'></head></html>\")\n    True\n    >>> _has_ajaxcrawlable_meta('<html><head><!--<meta name=\"fragment\"  content=\"!\"/>--></head><body></body></html>')\n    False\n    >>> _has_ajaxcrawlable_meta('<html></html>')\n    False\n    \"\"\"\n\n    # Stripping scripts and comments is slow (about 20x slower than\n    # just checking if a string is in text); this is a quick fail-fast\n    # path that should work for most pages.\n    if 'fragment' not in text:\n        return False\n    if 'content' not in text:\n        return False\n\n    text = html.remove_tags_with_content(text, ('script', 'noscript'))\n    text = html.replace_entities(text)\n    text = html.remove_comments(text)\n    return _ajax_crawlable_re.search(text) is not None\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/chunked.py",
    "content": "import warnings\n\nfrom scrapy.exceptions import ScrapyDeprecationWarning\nfrom scrapy.utils.http import decode_chunked_transfer\n\n\nwarnings.warn(\"Module `scrapy.downloadermiddlewares.chunked` is deprecated, \"\n              \"chunked transfers are supported by default.\",\n              ScrapyDeprecationWarning, stacklevel=2)\n\n\nclass ChunkedTransferMiddleware(object):\n    \"\"\"This middleware adds support for chunked transfer encoding, as\n    documented in: https://en.wikipedia.org/wiki/Chunked_transfer_encoding\n    \"\"\"\n\n    def process_response(self, request, response, spider):\n        if response.headers.get('Transfer-Encoding') == 'chunked':\n            body = decode_chunked_transfer(response.body)\n            return response.replace(body=body)\n        return response\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/cookies.py",
    "content": "import os\nimport six\nimport logging\nfrom collections import defaultdict\n\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy.http import Response\nfrom scrapy.http.cookies import CookieJar\nfrom scrapy.utils.python import to_native_str\n\nlogger = logging.getLogger(__name__)\n\n\nclass CookiesMiddleware(object):\n    \"\"\"This middleware enables working with sites that need cookies\"\"\"\n\n    def __init__(self, debug=False):\n        self.jars = defaultdict(CookieJar)\n        self.debug = debug\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        if not crawler.settings.getbool('COOKIES_ENABLED'):\n            raise NotConfigured\n        return cls(crawler.settings.getbool('COOKIES_DEBUG'))\n\n    def process_request(self, request, spider):\n        if request.meta.get('dont_merge_cookies', False):\n            return\n\n        cookiejarkey = request.meta.get(\"cookiejar\")\n        jar = self.jars[cookiejarkey]\n        cookies = self._get_request_cookies(jar, request)\n        for cookie in cookies:\n            jar.set_cookie_if_ok(cookie, request)\n\n        # set Cookie header\n        request.headers.pop('Cookie', None)\n        jar.add_cookie_header(request)\n        self._debug_cookie(request, spider)\n\n    def process_response(self, request, response, spider):\n        if request.meta.get('dont_merge_cookies', False):\n            return response\n\n        # extract cookies from Set-Cookie and drop invalid/expired cookies\n        cookiejarkey = request.meta.get(\"cookiejar\")\n        jar = self.jars[cookiejarkey]\n        jar.extract_cookies(response, request)\n        self._debug_set_cookie(response, spider)\n\n        return response\n\n    def _debug_cookie(self, request, spider):\n        if self.debug:\n            cl = [to_native_str(c, errors='replace')\n                  for c in request.headers.getlist('Cookie')]\n            if cl:\n                cookies = \"\\n\".join(\"Cookie: {}\\n\".format(c) for c in cl)\n                msg = \"Sending cookies to: {}\\n{}\".format(request, cookies)\n                logger.debug(msg, extra={'spider': spider})\n\n    def _debug_set_cookie(self, response, spider):\n        if self.debug:\n            cl = [to_native_str(c, errors='replace')\n                  for c in response.headers.getlist('Set-Cookie')]\n            if cl:\n                cookies = \"\\n\".join(\"Set-Cookie: {}\\n\".format(c) for c in cl)\n                msg = \"Received cookies from: {}\\n{}\".format(response, cookies)\n                logger.debug(msg, extra={'spider': spider})\n\n    def _format_cookie(self, cookie):\n        # build cookie string\n        cookie_str = '%s=%s' % (cookie['name'], cookie['value'])\n\n        if cookie.get('path', None):\n            cookie_str += '; Path=%s' % cookie['path']\n        if cookie.get('domain', None):\n            cookie_str += '; Domain=%s' % cookie['domain']\n\n        return cookie_str\n\n    def _get_request_cookies(self, jar, request):\n        if isinstance(request.cookies, dict):\n            cookie_list = [{'name': k, 'value': v} for k, v in \\\n                    six.iteritems(request.cookies)]\n        else:\n            cookie_list = request.cookies\n\n        cookies = [self._format_cookie(x) for x in cookie_list]\n        headers = {'Set-Cookie': cookies}\n        response = Response(request.url, headers=headers)\n\n        return jar.make_cookies(response, request)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/decompression.py",
    "content": "\"\"\" This module implements the DecompressionMiddleware which tries to recognise\nand extract the potentially compressed responses that may arrive.\n\"\"\"\n\nimport bz2\nimport gzip\nimport zipfile\nimport tarfile\nimport logging\nfrom tempfile import mktemp\n\nimport six\n\ntry:\n    from cStringIO import StringIO as BytesIO\nexcept ImportError:\n    from io import BytesIO\n\nfrom scrapy.responsetypes import responsetypes\n\nlogger = logging.getLogger(__name__)\n\n\nclass DecompressionMiddleware(object):\n    \"\"\" This middleware tries to recognise and extract the possibly compressed\n    responses that may arrive. \"\"\"\n\n    def __init__(self):\n        self._formats = {\n            'tar': self._is_tar,\n            'zip': self._is_zip,\n            'gz': self._is_gzip,\n            'bz2': self._is_bzip2\n        }\n\n    def _is_tar(self, response):\n        archive = BytesIO(response.body)\n        try:\n            tar_file = tarfile.open(name=mktemp(), fileobj=archive)\n        except tarfile.ReadError:\n            return\n\n        body = tar_file.extractfile(tar_file.members[0]).read()\n        respcls = responsetypes.from_args(filename=tar_file.members[0].name, body=body)\n        return response.replace(body=body, cls=respcls)\n\n    def _is_zip(self, response):\n        archive = BytesIO(response.body)\n        try:\n            zip_file = zipfile.ZipFile(archive)\n        except zipfile.BadZipfile:\n            return\n\n        namelist = zip_file.namelist()\n        body = zip_file.read(namelist[0])\n        respcls = responsetypes.from_args(filename=namelist[0], body=body)\n        return response.replace(body=body, cls=respcls)\n\n    def _is_gzip(self, response):\n        archive = BytesIO(response.body)\n        try:\n            body = gzip.GzipFile(fileobj=archive).read()\n        except IOError:\n            return\n\n        respcls = responsetypes.from_args(body=body)\n        return response.replace(body=body, cls=respcls)\n\n    def _is_bzip2(self, response):\n        try:\n            body = bz2.decompress(response.body)\n        except IOError:\n            return\n\n        respcls = responsetypes.from_args(body=body)\n        return response.replace(body=body, cls=respcls)\n\n    def process_response(self, request, response, spider):\n        if not response.body:\n            return response\n\n        for fmt, func in six.iteritems(self._formats):\n            new_response = func(response)\n            if new_response:\n                logger.debug('Decompressed response with format: %(responsefmt)s',\n                             {'responsefmt': fmt}, extra={'spider': spider})\n                return new_response\n        return response\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/defaultheaders.py",
    "content": "\"\"\"\nDefaultHeaders downloader middleware\n\nSee documentation in docs/topics/downloader-middleware.rst\n\"\"\"\n\nfrom scrapy.utils.python import without_none_values\n\n\nclass DefaultHeadersMiddleware(object):\n\n    def __init__(self, headers):\n        self._headers = headers\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        headers = without_none_values(crawler.settings['DEFAULT_REQUEST_HEADERS'])\n        return cls(headers.items())\n\n    def process_request(self, request, spider):\n        for k, v in self._headers:\n            request.headers.setdefault(k, v)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/downloadtimeout.py",
    "content": "\"\"\"\nDownload timeout middleware\n\nSee documentation in docs/topics/downloader-middleware.rst\n\"\"\"\n\nfrom scrapy import signals\n\n\nclass DownloadTimeoutMiddleware(object):\n\n    def __init__(self, timeout=180):\n        self._timeout = timeout\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        o = cls(crawler.settings.getfloat('DOWNLOAD_TIMEOUT'))\n        crawler.signals.connect(o.spider_opened, signal=signals.spider_opened)\n        return o\n\n    def spider_opened(self, spider):\n        self._timeout = getattr(spider, 'download_timeout', self._timeout)\n\n    def process_request(self, request, spider):\n        if self._timeout:\n            request.meta.setdefault('download_timeout', self._timeout)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/httpauth.py",
    "content": "\"\"\"\nHTTP basic auth downloader middleware\n\nSee documentation in docs/topics/downloader-middleware.rst\n\"\"\"\n\nfrom w3lib.http import basic_auth_header\n\nfrom scrapy import signals\n\n\nclass HttpAuthMiddleware(object):\n    \"\"\"Set Basic HTTP Authorization header\n    (http_user and http_pass spider class attributes)\"\"\"\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        o = cls()\n        crawler.signals.connect(o.spider_opened, signal=signals.spider_opened)\n        return o\n\n    def spider_opened(self, spider):\n        usr = getattr(spider, 'http_user', '')\n        pwd = getattr(spider, 'http_pass', '')\n        if usr or pwd:\n            self.auth = basic_auth_header(usr, pwd)\n\n    def process_request(self, request, spider):\n        auth = getattr(self, 'auth', None)\n        if auth and b'Authorization' not in request.headers:\n            request.headers[b'Authorization'] = auth\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/httpcache.py",
    "content": "from email.utils import formatdate\nfrom twisted.internet import defer\nfrom twisted.internet.error import TimeoutError, DNSLookupError, \\\n        ConnectionRefusedError, ConnectionDone, ConnectError, \\\n        ConnectionLost, TCPTimedOutError\nfrom twisted.web.client import ResponseFailed\nfrom scrapy import signals\nfrom scrapy.exceptions import NotConfigured, IgnoreRequest\nfrom scrapy.utils.misc import load_object\n\n\nclass HttpCacheMiddleware(object):\n\n    DOWNLOAD_EXCEPTIONS = (defer.TimeoutError, TimeoutError, DNSLookupError,\n                           ConnectionRefusedError, ConnectionDone, ConnectError,\n                           ConnectionLost, TCPTimedOutError, ResponseFailed,\n                           IOError)\n\n    def __init__(self, settings, stats):\n        if not settings.getbool('HTTPCACHE_ENABLED'):\n            raise NotConfigured\n        self.policy = load_object(settings['HTTPCACHE_POLICY'])(settings)\n        self.storage = load_object(settings['HTTPCACHE_STORAGE'])(settings)\n        self.ignore_missing = settings.getbool('HTTPCACHE_IGNORE_MISSING')\n        self.stats = stats\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        o = cls(crawler.settings, crawler.stats)\n        crawler.signals.connect(o.spider_opened, signal=signals.spider_opened)\n        crawler.signals.connect(o.spider_closed, signal=signals.spider_closed)\n        return o\n\n    def spider_opened(self, spider):\n        self.storage.open_spider(spider)\n\n    def spider_closed(self, spider):\n        self.storage.close_spider(spider)\n\n    def process_request(self, request, spider):\n        if request.meta.get('dont_cache', False):\n            return\n\n        # Skip uncacheable requests\n        if not self.policy.should_cache_request(request):\n            request.meta['_dont_cache'] = True  # flag as uncacheable\n            return\n\n        # Look for cached response and check if expired\n        cachedresponse = self.storage.retrieve_response(spider, request)\n        if cachedresponse is None:\n            self.stats.inc_value('httpcache/miss', spider=spider)\n            if self.ignore_missing:\n                self.stats.inc_value('httpcache/ignore', spider=spider)\n                raise IgnoreRequest(\"Ignored request not in cache: %s\" % request)\n            return  # first time request\n\n        # Return cached response only if not expired\n        cachedresponse.flags.append('cached')\n        if self.policy.is_cached_response_fresh(cachedresponse, request):\n            self.stats.inc_value('httpcache/hit', spider=spider)\n            return cachedresponse\n\n        # Keep a reference to cached response to avoid a second cache lookup on\n        # process_response hook\n        request.meta['cached_response'] = cachedresponse\n\n    def process_response(self, request, response, spider):\n        if request.meta.get('dont_cache', False):\n            return response\n\n        # Skip cached responses and uncacheable requests\n        if 'cached' in response.flags or '_dont_cache' in request.meta:\n            request.meta.pop('_dont_cache', None)\n            return response\n\n        # RFC2616 requires origin server to set Date header,\n        # https://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.18\n        if 'Date' not in response.headers:\n            response.headers['Date'] = formatdate(usegmt=1)\n\n        # Do not validate first-hand responses\n        cachedresponse = request.meta.pop('cached_response', None)\n        if cachedresponse is None:\n            self.stats.inc_value('httpcache/firsthand', spider=spider)\n            self._cache_response(spider, response, request, cachedresponse)\n            return response\n\n        if self.policy.is_cached_response_valid(cachedresponse, response, request):\n            self.stats.inc_value('httpcache/revalidate', spider=spider)\n            return cachedresponse\n\n        self.stats.inc_value('httpcache/invalidate', spider=spider)\n        self._cache_response(spider, response, request, cachedresponse)\n        return response\n\n    def process_exception(self, request, exception, spider):\n        cachedresponse = request.meta.pop('cached_response', None)\n        if cachedresponse is not None and isinstance(exception, self.DOWNLOAD_EXCEPTIONS):\n            self.stats.inc_value('httpcache/errorrecovery', spider=spider)\n            return cachedresponse\n\n    def _cache_response(self, spider, response, request, cachedresponse):\n        if self.policy.should_cache_response(response, request):\n            self.stats.inc_value('httpcache/store', spider=spider)\n            self.storage.store_response(spider, request, response)\n        else:\n            self.stats.inc_value('httpcache/uncacheable', spider=spider)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/httpcompression.py",
    "content": "import zlib\n\nfrom scrapy.utils.gz import gunzip\nfrom scrapy.http import Response, TextResponse\nfrom scrapy.responsetypes import responsetypes\nfrom scrapy.exceptions import NotConfigured\n\n\nACCEPTED_ENCODINGS = [b'gzip', b'deflate']\n\ntry:\n    import brotli\n    ACCEPTED_ENCODINGS.append(b'br')\nexcept ImportError:\n    pass\n\n\nclass HttpCompressionMiddleware(object):\n    \"\"\"This middleware allows compressed (gzip, deflate) traffic to be\n    sent/received from web sites\"\"\"\n    @classmethod\n    def from_crawler(cls, crawler):\n        if not crawler.settings.getbool('COMPRESSION_ENABLED'):\n            raise NotConfigured\n        return cls()\n\n    def process_request(self, request, spider):\n        request.headers.setdefault('Accept-Encoding',\n                                   b\",\".join(ACCEPTED_ENCODINGS))\n\n    def process_response(self, request, response, spider):\n\n        if request.method == 'HEAD':\n            return response\n        if isinstance(response, Response):\n            content_encoding = response.headers.getlist('Content-Encoding')\n            if content_encoding:\n                encoding = content_encoding.pop()\n                decoded_body = self._decode(response.body, encoding.lower())\n                respcls = responsetypes.from_args(headers=response.headers, \\\n                    url=response.url, body=decoded_body)\n                kwargs = dict(cls=respcls, body=decoded_body)\n                if issubclass(respcls, TextResponse):\n                    # force recalculating the encoding until we make sure the\n                    # responsetypes guessing is reliable\n                    kwargs['encoding'] = None\n                response = response.replace(**kwargs)\n                if not content_encoding:\n                    del response.headers['Content-Encoding']\n\n        return response\n\n    def _decode(self, body, encoding):\n        if encoding == b'gzip' or encoding == b'x-gzip':\n            body = gunzip(body)\n\n        if encoding == b'deflate':\n            try:\n                body = zlib.decompress(body)\n            except zlib.error:\n                # ugly hack to work with raw deflate content that may\n                # be sent by microsoft servers. For more information, see:\n                # http://carsten.codimi.de/gzip.yaws/\n                # http://www.port80software.com/200ok/archive/2005/10/31/868.aspx\n                # http://www.gzip.org/zlib/zlib_faq.html#faq38\n                body = zlib.decompress(body, -15)\n        if encoding == b'br' and b'br' in ACCEPTED_ENCODINGS:\n            body = brotli.decompress(body)\n        return body\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/httpproxy.py",
    "content": "import base64\nfrom six.moves.urllib.parse import unquote, urlunparse\nfrom six.moves.urllib.request import getproxies, proxy_bypass\ntry:\n    from urllib2 import _parse_proxy\nexcept ImportError:\n    from urllib.request import _parse_proxy\n\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy.utils.httpobj import urlparse_cached\nfrom scrapy.utils.python import to_bytes\n\n\nclass HttpProxyMiddleware(object):\n\n    def __init__(self, auth_encoding='latin-1'):\n        self.auth_encoding = auth_encoding\n        self.proxies = {}\n        for type_, url in getproxies().items():\n            self.proxies[type_] = self._get_proxy(url, type_)\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        if not crawler.settings.getbool('HTTPPROXY_ENABLED'):\n            raise NotConfigured\n        auth_encoding = crawler.settings.get('HTTPPROXY_AUTH_ENCODING')\n        return cls(auth_encoding)\n\n    def _basic_auth_header(self, username, password):\n        user_pass = to_bytes(\n            '%s:%s' % (unquote(username), unquote(password)),\n            encoding=self.auth_encoding)\n        return base64.b64encode(user_pass)\n\n    def _get_proxy(self, url, orig_type):\n        proxy_type, user, password, hostport = _parse_proxy(url)\n        proxy_url = urlunparse((proxy_type or orig_type, hostport, '', '', '', ''))\n\n        if user:\n            creds = self._basic_auth_header(user, password)\n        else:\n            creds = None\n\n        return creds, proxy_url\n\n    def process_request(self, request, spider):\n        # ignore if proxy is already set\n        if 'proxy' in request.meta:\n            if request.meta['proxy'] is None:\n                return\n            # extract credentials if present\n            creds, proxy_url = self._get_proxy(request.meta['proxy'], '')\n            request.meta['proxy'] = proxy_url\n            if creds and not request.headers.get('Proxy-Authorization'):\n                request.headers['Proxy-Authorization'] = b'Basic ' + creds\n            return\n        elif not self.proxies:\n            return\n\n        parsed = urlparse_cached(request)\n        scheme = parsed.scheme\n\n        # 'no_proxy' is only supported by http schemes\n        if scheme in ('http', 'https') and proxy_bypass(parsed.hostname):\n            return\n\n        if scheme in self.proxies:\n            self._set_proxy(request, scheme)\n\n    def _set_proxy(self, request, scheme):\n        creds, proxy = self.proxies[scheme]\n        request.meta['proxy'] = proxy\n        if creds:\n            request.headers['Proxy-Authorization'] = b'Basic ' + creds\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/redirect.py",
    "content": "import logging\nfrom six.moves.urllib.parse import urljoin\n\nfrom w3lib.url import safe_url_string\n\nfrom scrapy.http import HtmlResponse\nfrom scrapy.utils.response import get_meta_refresh\nfrom scrapy.exceptions import IgnoreRequest, NotConfigured\n\nlogger = logging.getLogger(__name__)\n\n\nclass BaseRedirectMiddleware(object):\n\n    enabled_setting = 'REDIRECT_ENABLED'\n\n    def __init__(self, settings):\n        if not settings.getbool(self.enabled_setting):\n            raise NotConfigured\n\n        self.max_redirect_times = settings.getint('REDIRECT_MAX_TIMES')\n        self.priority_adjust = settings.getint('REDIRECT_PRIORITY_ADJUST')\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls(crawler.settings)\n\n    def _redirect(self, redirected, request, spider, reason):\n        ttl = request.meta.setdefault('redirect_ttl', self.max_redirect_times)\n        redirects = request.meta.get('redirect_times', 0) + 1\n\n        if ttl and redirects <= self.max_redirect_times:\n            redirected.meta['redirect_times'] = redirects\n            redirected.meta['redirect_ttl'] = ttl - 1\n            redirected.meta['redirect_urls'] = request.meta.get('redirect_urls', []) + \\\n                [request.url]\n            redirected.meta['redirect_reasons'] = request.meta.get('redirect_reasons', []) + \\\n                [reason]\n            redirected.dont_filter = request.dont_filter\n            redirected.priority = request.priority + self.priority_adjust\n            logger.debug(\"Redirecting (%(reason)s) to %(redirected)s from %(request)s\",\n                         {'reason': reason, 'redirected': redirected, 'request': request},\n                         extra={'spider': spider})\n            return redirected\n        else:\n            logger.debug(\"Discarding %(request)s: max redirections reached\",\n                         {'request': request}, extra={'spider': spider})\n            raise IgnoreRequest(\"max redirections reached\")\n\n    def _redirect_request_using_get(self, request, redirect_url):\n        redirected = request.replace(url=redirect_url, method='GET', body='')\n        redirected.headers.pop('Content-Type', None)\n        redirected.headers.pop('Content-Length', None)\n        return redirected\n\n\nclass RedirectMiddleware(BaseRedirectMiddleware):\n    \"\"\"\n    Handle redirection of requests based on response status\n    and meta-refresh html tag.\n    \"\"\"\n    def process_response(self, request, response, spider):\n        if (request.meta.get('dont_redirect', False) or\n                response.status in getattr(spider, 'handle_httpstatus_list', []) or\n                response.status in request.meta.get('handle_httpstatus_list', []) or\n                request.meta.get('handle_httpstatus_all', False)):\n            return response\n\n        allowed_status = (301, 302, 303, 307, 308)\n        if 'Location' not in response.headers or response.status not in allowed_status:\n            return response\n\n        location = safe_url_string(response.headers['location'])\n\n        redirected_url = urljoin(request.url, location)\n\n        if response.status in (301, 307, 308) or request.method == 'HEAD':\n            redirected = request.replace(url=redirected_url)\n            return self._redirect(redirected, request, spider, response.status)\n\n        redirected = self._redirect_request_using_get(request, redirected_url)\n        return self._redirect(redirected, request, spider, response.status)\n\n\nclass MetaRefreshMiddleware(BaseRedirectMiddleware):\n\n    enabled_setting = 'METAREFRESH_ENABLED'\n\n    def __init__(self, settings):\n        super(MetaRefreshMiddleware, self).__init__(settings)\n        self._ignore_tags = settings.getlist('METAREFRESH_IGNORE_TAGS')\n        self._maxdelay = settings.getint('REDIRECT_MAX_METAREFRESH_DELAY',\n                                         settings.getint('METAREFRESH_MAXDELAY'))\n\n    def process_response(self, request, response, spider):\n        if request.meta.get('dont_redirect', False) or request.method == 'HEAD' or \\\n                not isinstance(response, HtmlResponse):\n            return response\n\n        interval, url = get_meta_refresh(response,\n                                         ignore_tags=self._ignore_tags)\n        if url and interval < self._maxdelay:\n            redirected = self._redirect_request_using_get(request, url)\n            return self._redirect(redirected, request, spider, 'meta refresh')\n\n        return response\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/retry.py",
    "content": "\"\"\"\nAn extension to retry failed requests that are potentially caused by temporary\nproblems such as a connection timeout or HTTP 500 error.\n\nYou can change the behaviour of this middleware by modifing the scraping settings:\nRETRY_TIMES - how many times to retry a failed page\nRETRY_HTTP_CODES - which HTTP response codes to retry\n\nFailed pages are collected on the scraping process and rescheduled at the end,\nonce the spider has finished crawling all regular (non failed) pages.\n\"\"\"\nimport logging\n\nfrom twisted.internet import defer\nfrom twisted.internet.error import TimeoutError, DNSLookupError, \\\n        ConnectionRefusedError, ConnectionDone, ConnectError, \\\n        ConnectionLost, TCPTimedOutError\nfrom twisted.web.client import ResponseFailed\n\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy.utils.response import response_status_message\nfrom scrapy.core.downloader.handlers.http11 import TunnelError\nfrom scrapy.utils.python import global_object_name\n\nlogger = logging.getLogger(__name__)\n\n\nclass RetryMiddleware(object):\n\n    # IOError is raised by the HttpCompression middleware when trying to\n    # decompress an empty response\n    EXCEPTIONS_TO_RETRY = (defer.TimeoutError, TimeoutError, DNSLookupError,\n                           ConnectionRefusedError, ConnectionDone, ConnectError,\n                           ConnectionLost, TCPTimedOutError, ResponseFailed,\n                           IOError, TunnelError)\n\n    def __init__(self, settings):\n        if not settings.getbool('RETRY_ENABLED'):\n            raise NotConfigured\n        self.max_retry_times = settings.getint('RETRY_TIMES')\n        self.retry_http_codes = set(int(x) for x in settings.getlist('RETRY_HTTP_CODES'))\n        self.priority_adjust = settings.getint('RETRY_PRIORITY_ADJUST')\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls(crawler.settings)\n\n    def process_response(self, request, response, spider):\n        if request.meta.get('dont_retry', False):\n            return response\n        if response.status in self.retry_http_codes:\n            reason = response_status_message(response.status)\n            return self._retry(request, reason, spider) or response\n        return response\n\n    def process_exception(self, request, exception, spider):\n        if isinstance(exception, self.EXCEPTIONS_TO_RETRY) \\\n                and not request.meta.get('dont_retry', False):\n            return self._retry(request, exception, spider)\n\n    def _retry(self, request, reason, spider):\n        retries = request.meta.get('retry_times', 0) + 1\n\n        retry_times = self.max_retry_times\n\n        if 'max_retry_times' in request.meta:\n            retry_times = request.meta['max_retry_times']\n\n        stats = spider.crawler.stats\n        if retries <= retry_times:\n            logger.debug(\"Retrying %(request)s (failed %(retries)d times): %(reason)s\",\n                         {'request': request, 'retries': retries, 'reason': reason},\n                         extra={'spider': spider})\n            retryreq = request.copy()\n            retryreq.meta['retry_times'] = retries\n            retryreq.dont_filter = True\n            retryreq.priority = request.priority + self.priority_adjust\n\n            if isinstance(reason, Exception):\n                reason = global_object_name(reason.__class__)\n\n            stats.inc_value('retry/count')\n            stats.inc_value('retry/reason_count/%s' % reason)\n            return retryreq\n        else:\n            stats.inc_value('retry/max_reached')\n            logger.debug(\"Gave up retrying %(request)s (failed %(retries)d times): %(reason)s\",\n                         {'request': request, 'retries': retries, 'reason': reason},\n                         extra={'spider': spider})\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/robotstxt.py",
    "content": "\"\"\"\nThis is a middleware to respect robots.txt policies. To activate it you must\nenable this middleware and enable the ROBOTSTXT_OBEY setting.\n\n\"\"\"\n\nimport logging\n\nfrom six.moves.urllib import robotparser\n\nfrom twisted.internet.defer import Deferred, maybeDeferred\nfrom scrapy.exceptions import NotConfigured, IgnoreRequest\nfrom scrapy.http import Request\nfrom scrapy.utils.httpobj import urlparse_cached\nfrom scrapy.utils.log import failure_to_exc_info\nfrom scrapy.utils.python import to_native_str\n\nlogger = logging.getLogger(__name__)\n\n\nclass RobotsTxtMiddleware(object):\n    DOWNLOAD_PRIORITY = 1000\n\n    def __init__(self, crawler):\n        if not crawler.settings.getbool('ROBOTSTXT_OBEY'):\n            raise NotConfigured\n\n        self.crawler = crawler\n        self._useragent = crawler.settings.get('USER_AGENT')\n        self._parsers = {}\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls(crawler)\n\n    def process_request(self, request, spider):\n        if request.meta.get('dont_obey_robotstxt'):\n            return\n        d = maybeDeferred(self.robot_parser, request, spider)\n        d.addCallback(self.process_request_2, request, spider)\n        return d\n\n    def process_request_2(self, rp, request, spider):\n        if rp is None:\n            return\n        if not rp.can_fetch(to_native_str(self._useragent), request.url):\n            logger.debug(\"Forbidden by robots.txt: %(request)s\",\n                         {'request': request}, extra={'spider': spider})\n            self.crawler.stats.inc_value('robotstxt/forbidden')\n            raise IgnoreRequest(\"Forbidden by robots.txt\")\n\n    def robot_parser(self, request, spider):\n        url = urlparse_cached(request)\n        netloc = url.netloc\n\n        if netloc not in self._parsers:\n            self._parsers[netloc] = Deferred()\n            robotsurl = \"%s://%s/robots.txt\" % (url.scheme, url.netloc)\n            robotsreq = Request(\n                robotsurl,\n                priority=self.DOWNLOAD_PRIORITY,\n                meta={'dont_obey_robotstxt': True}\n            )\n            dfd = self.crawler.engine.download(robotsreq, spider)\n            dfd.addCallback(self._parse_robots, netloc)\n            dfd.addErrback(self._logerror, robotsreq, spider)\n            dfd.addErrback(self._robots_error, netloc)\n            self.crawler.stats.inc_value('robotstxt/request_count')\n\n        if isinstance(self._parsers[netloc], Deferred):\n            d = Deferred()\n            def cb(result):\n                d.callback(result)\n                return result\n            self._parsers[netloc].addCallback(cb)\n            return d\n        else:\n            return self._parsers[netloc]\n\n    def _logerror(self, failure, request, spider):\n        if failure.type is not IgnoreRequest:\n            logger.error(\"Error downloading %(request)s: %(f_exception)s\",\n                         {'request': request, 'f_exception': failure.value},\n                         exc_info=failure_to_exc_info(failure),\n                         extra={'spider': spider})\n        return failure\n\n    def _parse_robots(self, response, netloc):\n        self.crawler.stats.inc_value('robotstxt/response_count')\n        self.crawler.stats.inc_value(\n            'robotstxt/response_status_count/{}'.format(response.status))\n        rp = robotparser.RobotFileParser(response.url)\n        body = ''\n        if hasattr(response, 'text'):\n            body = response.text\n        else:  # last effort try\n            try:\n                body = response.body.decode('utf-8')\n            except UnicodeDecodeError:\n                # If we found garbage, disregard it:,\n                # but keep the lookup cached (in self._parsers)\n                # Running rp.parse() will set rp state from\n                # 'disallow all' to 'allow any'.\n                self.crawler.stats.inc_value('robotstxt/unicode_error_count')\n        # stdlib's robotparser expects native 'str' ;\n        # with unicode input, non-ASCII encoded bytes decoding fails in Python2\n        rp.parse(to_native_str(body).splitlines())\n\n        rp_dfd = self._parsers[netloc]\n        self._parsers[netloc] = rp\n        rp_dfd.callback(rp)\n\n    def _robots_error(self, failure, netloc):\n        if failure.type is not IgnoreRequest:\n            key = 'robotstxt/exception_count/{}'.format(failure.type)\n            self.crawler.stats.inc_value(key)\n        rp_dfd = self._parsers[netloc]\n        self._parsers[netloc] = None\n        rp_dfd.callback(None)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/stats.py",
    "content": "from scrapy.exceptions import NotConfigured\nfrom scrapy.utils.request import request_httprepr\nfrom scrapy.utils.response import response_httprepr\nfrom scrapy.utils.python import global_object_name\n\n\nclass DownloaderStats(object):\n\n    def __init__(self, stats):\n        self.stats = stats\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        if not crawler.settings.getbool('DOWNLOADER_STATS'):\n            raise NotConfigured\n        return cls(crawler.stats)\n\n    def process_request(self, request, spider):\n        self.stats.inc_value('downloader/request_count', spider=spider)\n        self.stats.inc_value('downloader/request_method_count/%s' % request.method, spider=spider)\n        reqlen = len(request_httprepr(request))\n        self.stats.inc_value('downloader/request_bytes', reqlen, spider=spider)\n\n    def process_response(self, request, response, spider):\n        self.stats.inc_value('downloader/response_count', spider=spider)\n        self.stats.inc_value('downloader/response_status_count/%s' % response.status, spider=spider)\n        reslen = len(response_httprepr(response))\n        self.stats.inc_value('downloader/response_bytes', reslen, spider=spider)\n        return response\n\n    def process_exception(self, request, exception, spider):\n        ex_class = global_object_name(exception.__class__)\n        self.stats.inc_value('downloader/exception_count', spider=spider)\n        self.stats.inc_value('downloader/exception_type_count/%s' % ex_class, spider=spider)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/downloadermiddlewares/useragent.py",
    "content": "\"\"\"Set User-Agent header per spider or use a default value from settings\"\"\"\n\nfrom scrapy import signals\n\n\nclass UserAgentMiddleware(object):\n    \"\"\"This middleware allows spiders to override the user_agent\"\"\"\n\n    def __init__(self, user_agent='Scrapy'):\n        self.user_agent = user_agent\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        o = cls(crawler.settings['USER_AGENT'])\n        crawler.signals.connect(o.spider_opened, signal=signals.spider_opened)\n        return o\n\n    def spider_opened(self, spider):\n        self.user_agent = getattr(spider, 'user_agent', self.user_agent)\n\n    def process_request(self, request, spider):\n        if self.user_agent:\n            request.headers.setdefault(b'User-Agent', self.user_agent)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/dupefilters.py",
    "content": "from __future__ import print_function\nimport os\nimport logging\n\nfrom scrapy.utils.job import job_dir\nfrom scrapy.utils.request import referer_str, request_fingerprint\n\nclass BaseDupeFilter(object):\n\n    @classmethod\n    def from_settings(cls, settings):\n        return cls()\n\n    def request_seen(self, request):\n        return False\n\n    def open(self):  # can return deferred\n        pass\n\n    def close(self, reason):  # can return a deferred\n        pass\n\n    def log(self, request, spider):  # log that a request has been filtered\n        pass\n\n\nclass RFPDupeFilter(BaseDupeFilter):\n    \"\"\"Request Fingerprint duplicates filter\"\"\"\n\n    def __init__(self, path=None, debug=False):\n        self.file = None\n        self.fingerprints = set()\n        self.logdupes = True\n        self.debug = debug\n        self.logger = logging.getLogger(__name__)\n        if path:\n            self.file = open(os.path.join(path, 'requests.seen'), 'a+')\n            self.file.seek(0)\n            self.fingerprints.update(x.rstrip() for x in self.file)\n\n    @classmethod\n    def from_settings(cls, settings):\n        debug = settings.getbool('DUPEFILTER_DEBUG')\n        return cls(job_dir(settings), debug)\n\n    def request_seen(self, request):\n        fp = self.request_fingerprint(request)\n        if fp in self.fingerprints:\n            return True\n        self.fingerprints.add(fp)\n        if self.file:\n            self.file.write(fp + os.linesep)\n\n    def request_fingerprint(self, request):\n        return request_fingerprint(request)\n\n    def close(self, reason):\n        if self.file:\n            self.file.close()\n\n    def log(self, request, spider):\n        if self.debug:\n            msg = \"Filtered duplicate request: %(request)s (referer: %(referer)s)\"\n            args = {'request': request, 'referer': referer_str(request) }\n            self.logger.debug(msg, args, extra={'spider': spider})\n        elif self.logdupes:\n            msg = (\"Filtered duplicate request: %(request)s\"\n                   \" - no more duplicates will be shown\"\n                   \" (see DUPEFILTER_DEBUG to show all duplicates)\")\n            self.logger.debug(msg, {'request': request}, extra={'spider': spider})\n            self.logdupes = False\n\n        spider.crawler.stats.inc_value('dupefilter/filtered', spider=spider)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/exceptions.py",
    "content": "\"\"\"\nScrapy core exceptions\n\nThese exceptions are documented in docs/topics/exceptions.rst. Please don't add\nnew exceptions here without documenting them there.\n\"\"\"\n\n# Internal\n\nclass NotConfigured(Exception):\n    \"\"\"Indicates a missing configuration situation\"\"\"\n    pass\n\nclass _InvalidOutput(TypeError):\n    \"\"\"\n    Indicates an invalid value has been returned by a middleware's processing method.\n    Internal and undocumented, it should not be raised or caught by user code.\n    \"\"\"\n    pass\n\n# HTTP and crawling\n\nclass IgnoreRequest(Exception):\n    \"\"\"Indicates a decision was made not to process a request\"\"\"\n\nclass DontCloseSpider(Exception):\n    \"\"\"Request the spider not to be closed yet\"\"\"\n    pass\n\nclass CloseSpider(Exception):\n    \"\"\"Raise this from callbacks to request the spider to be closed\"\"\"\n\n    def __init__(self, reason='cancelled'):\n        super(CloseSpider, self).__init__()\n        self.reason = reason\n\n# Items\n\nclass DropItem(Exception):\n    \"\"\"Drop item from the item pipeline\"\"\"\n    pass\n\nclass NotSupported(Exception):\n    \"\"\"Indicates a feature or method is not supported\"\"\"\n    pass\n\n# Commands\n\nclass UsageError(Exception):\n    \"\"\"To indicate a command-line usage error\"\"\"\n    def __init__(self, *a, **kw):\n        self.print_help = kw.pop('print_help', True)\n        super(UsageError, self).__init__(*a, **kw)\n\nclass ScrapyDeprecationWarning(Warning):\n    \"\"\"Warning category for deprecated features, since the default\n    DeprecationWarning is silenced on Python 2.7+\n    \"\"\"\n    pass\n\nclass ContractFail(AssertionError):\n    \"\"\"Error raised in case of a failing contract\"\"\"\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/exporters.py",
    "content": "\"\"\"\nItem Exporters are used to export/serialize items into different formats.\n\"\"\"\n\nimport csv\nimport io\nimport sys\nimport pprint\nimport marshal\nimport six\nfrom six.moves import cPickle as pickle\nfrom xml.sax.saxutils import XMLGenerator\n\nfrom scrapy.utils.serialize import ScrapyJSONEncoder\nfrom scrapy.utils.python import to_bytes, to_unicode, to_native_str, is_listlike\nfrom scrapy.item import BaseItem\nfrom scrapy.exceptions import ScrapyDeprecationWarning\nimport warnings\n\n\n__all__ = ['BaseItemExporter', 'PprintItemExporter', 'PickleItemExporter',\n           'CsvItemExporter', 'XmlItemExporter', 'JsonLinesItemExporter',\n           'JsonItemExporter', 'MarshalItemExporter']\n\n\nclass BaseItemExporter(object):\n\n    def __init__(self, **kwargs):\n        self._configure(kwargs)\n\n    def _configure(self, options, dont_fail=False):\n        \"\"\"Configure the exporter by poping options from the ``options`` dict.\n        If dont_fail is set, it won't raise an exception on unexpected options\n        (useful for using with keyword arguments in subclasses constructors)\n        \"\"\"\n        self.encoding = options.pop('encoding', None)\n        self.fields_to_export = options.pop('fields_to_export', None)\n        self.export_empty_fields = options.pop('export_empty_fields', False)\n        self.indent = options.pop('indent', None)\n        if not dont_fail and options:\n            raise TypeError(\"Unexpected options: %s\" % ', '.join(options.keys()))\n\n    def export_item(self, item):\n        raise NotImplementedError\n\n    def serialize_field(self, field, name, value):\n        serializer = field.get('serializer', lambda x: x)\n        return serializer(value)\n\n    def start_exporting(self):\n        pass\n\n    def finish_exporting(self):\n        pass\n\n    def _get_serialized_fields(self, item, default_value=None, include_empty=None):\n        \"\"\"Return the fields to export as an iterable of tuples\n        (name, serialized_value)\n        \"\"\"\n        if include_empty is None:\n            include_empty = self.export_empty_fields\n        if self.fields_to_export is None:\n            if include_empty and not isinstance(item, dict):\n                field_iter = six.iterkeys(item.fields)\n            else:\n                field_iter = six.iterkeys(item)\n        else:\n            if include_empty:\n                field_iter = self.fields_to_export\n            else:\n                field_iter = (x for x in self.fields_to_export if x in item)\n\n        for field_name in field_iter:\n            if field_name in item:\n                field = {} if isinstance(item, dict) else item.fields[field_name]\n                value = self.serialize_field(field, field_name, item[field_name])\n            else:\n                value = default_value\n\n            yield field_name, value\n\n\nclass JsonLinesItemExporter(BaseItemExporter):\n\n    def __init__(self, file, **kwargs):\n        self._configure(kwargs, dont_fail=True)\n        self.file = file\n        kwargs.setdefault('ensure_ascii', not self.encoding)\n        self.encoder = ScrapyJSONEncoder(**kwargs)\n\n    def export_item(self, item):\n        itemdict = dict(self._get_serialized_fields(item))\n        data = self.encoder.encode(itemdict) + '\\n'\n        self.file.write(to_bytes(data, self.encoding))\n\n\nclass JsonItemExporter(BaseItemExporter):\n\n    def __init__(self, file, **kwargs):\n        self._configure(kwargs, dont_fail=True)\n        self.file = file\n        # there is a small difference between the behaviour or JsonItemExporter.indent\n        # and ScrapyJSONEncoder.indent. ScrapyJSONEncoder.indent=None is needed to prevent\n        # the addition of newlines everywhere\n        json_indent = self.indent if self.indent is not None and self.indent > 0 else None\n        kwargs.setdefault('indent', json_indent)\n        kwargs.setdefault('ensure_ascii', not self.encoding)\n        self.encoder = ScrapyJSONEncoder(**kwargs)\n        self.first_item = True\n\n    def _beautify_newline(self):\n        if self.indent is not None:\n            self.file.write(b'\\n')\n\n    def start_exporting(self):\n        self.file.write(b\"[\")\n        self._beautify_newline()\n\n    def finish_exporting(self):\n        self._beautify_newline()\n        self.file.write(b\"]\")\n\n    def export_item(self, item):\n        if self.first_item:\n            self.first_item = False\n        else:\n            self.file.write(b',')\n            self._beautify_newline()\n        itemdict = dict(self._get_serialized_fields(item))\n        data = self.encoder.encode(itemdict)\n        self.file.write(to_bytes(data, self.encoding))\n\n\nclass XmlItemExporter(BaseItemExporter):\n\n    def __init__(self, file, **kwargs):\n        self.item_element = kwargs.pop('item_element', 'item')\n        self.root_element = kwargs.pop('root_element', 'items')\n        self._configure(kwargs)\n        if not self.encoding:\n            self.encoding = 'utf-8'\n        self.xg = XMLGenerator(file, encoding=self.encoding)\n\n    def _beautify_newline(self, new_item=False):\n        if self.indent is not None and (self.indent > 0 or new_item):\n            self._xg_characters('\\n')\n\n    def _beautify_indent(self, depth=1):\n        if self.indent:\n            self._xg_characters(' ' * self.indent * depth)\n\n    def start_exporting(self):\n        self.xg.startDocument()\n        self.xg.startElement(self.root_element, {})\n        self._beautify_newline(new_item=True)\n\n    def export_item(self, item):\n        self._beautify_indent(depth=1)\n        self.xg.startElement(self.item_element, {})\n        self._beautify_newline()\n        for name, value in self._get_serialized_fields(item, default_value=''):\n            self._export_xml_field(name, value, depth=2)\n        self._beautify_indent(depth=1)\n        self.xg.endElement(self.item_element)\n        self._beautify_newline(new_item=True)\n\n    def finish_exporting(self):\n        self.xg.endElement(self.root_element)\n        self.xg.endDocument()\n\n    def _export_xml_field(self, name, serialized_value, depth):\n        self._beautify_indent(depth=depth)\n        self.xg.startElement(name, {})\n        if hasattr(serialized_value, 'items'):\n            self._beautify_newline()\n            for subname, value in serialized_value.items():\n                self._export_xml_field(subname, value, depth=depth+1)\n            self._beautify_indent(depth=depth)\n        elif is_listlike(serialized_value):\n            self._beautify_newline()\n            for value in serialized_value:\n                self._export_xml_field('value', value, depth=depth+1)\n            self._beautify_indent(depth=depth)\n        elif isinstance(serialized_value, six.text_type):\n            self._xg_characters(serialized_value)\n        else:\n            self._xg_characters(str(serialized_value))\n        self.xg.endElement(name)\n        self._beautify_newline()\n\n    # Workaround for https://bugs.python.org/issue17606\n    # Before Python 2.7.4 xml.sax.saxutils required bytes;\n    # since 2.7.4 it requires unicode. The bug is likely to be\n    # fixed in 2.7.6, but 2.7.6 will still support unicode,\n    # and Python 3.x will require unicode, so \">= 2.7.4\" should be fine.\n    if sys.version_info[:3] >= (2, 7, 4):\n        def _xg_characters(self, serialized_value):\n            if not isinstance(serialized_value, six.text_type):\n                serialized_value = serialized_value.decode(self.encoding)\n            return self.xg.characters(serialized_value)\n    else:  # pragma: no cover\n        def _xg_characters(self, serialized_value):\n            return self.xg.characters(serialized_value)\n\n\nclass CsvItemExporter(BaseItemExporter):\n\n    def __init__(self, file, include_headers_line=True, join_multivalued=',', **kwargs):\n        self._configure(kwargs, dont_fail=True)\n        if not self.encoding:\n            self.encoding = 'utf-8'\n        self.include_headers_line = include_headers_line\n        self.stream = io.TextIOWrapper(\n            file,\n            line_buffering=False,\n            write_through=True,\n            encoding=self.encoding,\n            newline='' # Windows needs this https://github.com/scrapy/scrapy/issues/3034\n        ) if six.PY3 else file\n        self.csv_writer = csv.writer(self.stream, **kwargs)\n        self._headers_not_written = True\n        self._join_multivalued = join_multivalued\n\n    def serialize_field(self, field, name, value):\n        serializer = field.get('serializer', self._join_if_needed)\n        return serializer(value)\n\n    def _join_if_needed(self, value):\n        if isinstance(value, (list, tuple)):\n            try:\n                return self._join_multivalued.join(value)\n            except TypeError:  # list in value may not contain strings\n                pass\n        return value\n\n    def export_item(self, item):\n        if self._headers_not_written:\n            self._headers_not_written = False\n            self._write_headers_and_set_fields_to_export(item)\n\n        fields = self._get_serialized_fields(item, default_value='',\n                                             include_empty=True)\n        values = list(self._build_row(x for _, x in fields))\n        self.csv_writer.writerow(values)\n\n    def _build_row(self, values):\n        for s in values:\n            try:\n                yield to_native_str(s, self.encoding)\n            except TypeError:\n                yield s\n\n    def _write_headers_and_set_fields_to_export(self, item):\n        if self.include_headers_line:\n            if not self.fields_to_export:\n                if isinstance(item, dict):\n                    # for dicts try using fields of the first item\n                    self.fields_to_export = list(item.keys())\n                else:\n                    # use fields declared in Item\n                    self.fields_to_export = list(item.fields.keys())\n            row = list(self._build_row(self.fields_to_export))\n            self.csv_writer.writerow(row)\n\n\nclass PickleItemExporter(BaseItemExporter):\n\n    def __init__(self, file, protocol=2, **kwargs):\n        self._configure(kwargs)\n        self.file = file\n        self.protocol = protocol\n\n    def export_item(self, item):\n        d = dict(self._get_serialized_fields(item))\n        pickle.dump(d, self.file, self.protocol)\n\n\nclass MarshalItemExporter(BaseItemExporter):\n\n    def __init__(self, file, **kwargs):\n        self._configure(kwargs)\n        self.file = file\n\n    def export_item(self, item):\n        marshal.dump(dict(self._get_serialized_fields(item)), self.file)\n\n\nclass PprintItemExporter(BaseItemExporter):\n\n    def __init__(self, file, **kwargs):\n        self._configure(kwargs)\n        self.file = file\n\n    def export_item(self, item):\n        itemdict = dict(self._get_serialized_fields(item))\n        self.file.write(to_bytes(pprint.pformat(itemdict) + '\\n'))\n\n\nclass PythonItemExporter(BaseItemExporter):\n    \"\"\"The idea behind this exporter is to have a mechanism to serialize items\n    to built-in python types so any serialization library (like\n    json, msgpack, binc, etc) can be used on top of it. Its main goal is to\n    seamless support what BaseItemExporter does plus nested items.\n    \"\"\"\n    def _configure(self, options, dont_fail=False):\n        self.binary = options.pop('binary', True)\n        super(PythonItemExporter, self)._configure(options, dont_fail)\n        if self.binary:\n            warnings.warn(\n                \"PythonItemExporter will drop support for binary export in the future\",\n                ScrapyDeprecationWarning)\n        if not self.encoding:\n            self.encoding = 'utf-8'\n\n    def serialize_field(self, field, name, value):\n        serializer = field.get('serializer', self._serialize_value)\n        return serializer(value)\n\n    def _serialize_value(self, value):\n        if isinstance(value, BaseItem):\n            return self.export_item(value)\n        if isinstance(value, dict):\n            return dict(self._serialize_dict(value))\n        if is_listlike(value):\n            return [self._serialize_value(v) for v in value]\n        encode_func = to_bytes if self.binary else to_unicode\n        if isinstance(value, (six.text_type, bytes)):\n            return encode_func(value, encoding=self.encoding)\n        return value\n\n    def _serialize_dict(self, value):\n        for key, val in six.iteritems(value):\n            key = to_bytes(key) if self.binary else key\n            yield key, self._serialize_value(val)\n\n    def export_item(self, item):\n        result = dict(self._get_serialized_fields(item))\n        if self.binary:\n            result = dict(self._serialize_dict(result))\n        return result\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extension.py",
    "content": "\"\"\"\nThe Extension Manager\n\nSee documentation in docs/topics/extensions.rst\n\"\"\"\nfrom scrapy.middleware import MiddlewareManager\nfrom scrapy.utils.conf import build_component_list\n\nclass ExtensionManager(MiddlewareManager):\n\n    component_name = 'extension'\n\n    @classmethod\n    def _get_mwlist_from_settings(cls, settings):\n        return build_component_list(settings.getwithbase('EXTENSIONS'))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/closespider.py",
    "content": "\"\"\"CloseSpider is an extension that forces spiders to be closed after certain\nconditions are met.\n\nSee documentation in docs/topics/extensions.rst\n\"\"\"\n\nfrom collections import defaultdict\n\nfrom twisted.internet import reactor\n\nfrom scrapy import signals\nfrom scrapy.exceptions import NotConfigured\n\n\nclass CloseSpider(object):\n\n    def __init__(self, crawler):\n        self.crawler = crawler\n\n        self.close_on = {\n            'timeout': crawler.settings.getfloat('CLOSESPIDER_TIMEOUT'),\n            'itemcount': crawler.settings.getint('CLOSESPIDER_ITEMCOUNT'),\n            'pagecount': crawler.settings.getint('CLOSESPIDER_PAGECOUNT'),\n            'errorcount': crawler.settings.getint('CLOSESPIDER_ERRORCOUNT'),\n            }\n\n        if not any(self.close_on.values()):\n            raise NotConfigured\n\n        self.counter = defaultdict(int)\n\n        if self.close_on.get('errorcount'):\n            crawler.signals.connect(self.error_count, signal=signals.spider_error)\n        if self.close_on.get('pagecount'):\n            crawler.signals.connect(self.page_count, signal=signals.response_received)\n        if self.close_on.get('timeout'):\n            crawler.signals.connect(self.spider_opened, signal=signals.spider_opened)\n        if self.close_on.get('itemcount'):\n            crawler.signals.connect(self.item_scraped, signal=signals.item_scraped)\n        crawler.signals.connect(self.spider_closed, signal=signals.spider_closed)\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls(crawler)\n\n    def error_count(self, failure, response, spider):\n        self.counter['errorcount'] += 1\n        if self.counter['errorcount'] == self.close_on['errorcount']:\n            self.crawler.engine.close_spider(spider, 'closespider_errorcount')\n\n    def page_count(self, response, request, spider):\n        self.counter['pagecount'] += 1\n        if self.counter['pagecount'] == self.close_on['pagecount']:\n            self.crawler.engine.close_spider(spider, 'closespider_pagecount')\n\n    def spider_opened(self, spider):\n        self.task = reactor.callLater(self.close_on['timeout'], \\\n            self.crawler.engine.close_spider, spider, \\\n            reason='closespider_timeout')\n\n    def item_scraped(self, item, spider):\n        self.counter['itemcount'] += 1\n        if self.counter['itemcount'] == self.close_on['itemcount']:\n            self.crawler.engine.close_spider(spider, 'closespider_itemcount')\n\n    def spider_closed(self, spider):\n        task = getattr(self, 'task', False)\n        if task and task.active():\n            task.cancel()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/corestats.py",
    "content": "\"\"\"\nExtension for collecting core stats like items scraped and start/finish times\n\"\"\"\nimport datetime\n\nfrom scrapy import signals\n\nclass CoreStats(object):\n\n    def __init__(self, stats):\n        self.stats = stats\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        o = cls(crawler.stats)\n        crawler.signals.connect(o.spider_opened, signal=signals.spider_opened)\n        crawler.signals.connect(o.spider_closed, signal=signals.spider_closed)\n        crawler.signals.connect(o.item_scraped, signal=signals.item_scraped)\n        crawler.signals.connect(o.item_dropped, signal=signals.item_dropped)\n        crawler.signals.connect(o.response_received, signal=signals.response_received)\n        return o\n\n    def spider_opened(self, spider):\n        self.stats.set_value('start_time', datetime.datetime.utcnow(), spider=spider)\n\n    def spider_closed(self, spider, reason):\n        finish_time = datetime.datetime.utcnow()\n        elapsed_time = finish_time - self.stats.get_value('start_time')\n        elapsed_time_seconds = elapsed_time.total_seconds()\n        self.stats.set_value('elapsed_time_seconds', elapsed_time_seconds, spider=spider)\n        self.stats.set_value('finish_time', finish_time, spider=spider)\n        self.stats.set_value('finish_reason', reason, spider=spider)\n\n    def item_scraped(self, item, spider):\n        self.stats.inc_value('item_scraped_count', spider=spider)\n\n    def response_received(self, spider):\n        self.stats.inc_value('response_received_count', spider=spider)\n\n    def item_dropped(self, item, spider, exception):\n        reason = exception.__class__.__name__\n        self.stats.inc_value('item_dropped_count', spider=spider)\n        self.stats.inc_value('item_dropped_reasons_count/%s' % reason, spider=spider)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/debug.py",
    "content": "\"\"\"\nExtensions for debugging Scrapy\n\nSee documentation in docs/topics/extensions.rst\n\"\"\"\n\nimport sys\nimport signal\nimport logging\nimport traceback\nimport threading\nfrom pdb import Pdb\n\nfrom scrapy.utils.engine import format_engine_status\nfrom scrapy.utils.trackref import format_live_refs\n\nlogger = logging.getLogger(__name__)\n\n\nclass StackTraceDump(object):\n\n    def __init__(self, crawler=None):\n        self.crawler = crawler\n        try:\n            signal.signal(signal.SIGUSR2, self.dump_stacktrace)\n            signal.signal(signal.SIGQUIT, self.dump_stacktrace)\n        except AttributeError:\n            # win32 platforms don't support SIGUSR signals\n            pass\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls(crawler)\n\n    def dump_stacktrace(self, signum, frame):\n        log_args = {\n            'stackdumps': self._thread_stacks(),\n            'enginestatus': format_engine_status(self.crawler.engine),\n            'liverefs': format_live_refs(),\n        }\n        logger.info(\"Dumping stack trace and engine status\\n\"\n                    \"%(enginestatus)s\\n%(liverefs)s\\n%(stackdumps)s\",\n                    log_args, extra={'crawler': self.crawler})\n\n    def _thread_stacks(self):\n        id2name = dict((th.ident, th.name) for th in threading.enumerate())\n        dumps = ''\n        for id_, frame in sys._current_frames().items():\n            name = id2name.get(id_, '')\n            dump = ''.join(traceback.format_stack(frame))\n            dumps += \"# Thread: {0}({1})\\n{2}\\n\".format(name, id_, dump)\n        return dumps\n\n\nclass Debugger(object):\n    def __init__(self):\n        try:\n            signal.signal(signal.SIGUSR2, self._enter_debugger)\n        except AttributeError:\n            # win32 platforms don't support SIGUSR signals\n            pass\n\n    def _enter_debugger(self, signum, frame):\n        Pdb().set_trace(frame.f_back)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/feedexport.py",
    "content": "\"\"\"\nFeed Exports extension\n\nSee documentation in docs/topics/feed-exports.rst\n\"\"\"\n\nimport os\nimport sys\nimport logging\nimport posixpath\nfrom tempfile import NamedTemporaryFile\nfrom datetime import datetime\nimport six\nfrom six.moves.urllib.parse import urlparse\nfrom ftplib import FTP\n\nfrom zope.interface import Interface, implementer\nfrom twisted.internet import defer, threads\nfrom w3lib.url import file_uri_to_path\n\nfrom scrapy import signals\nfrom scrapy.utils.ftp import ftp_makedirs_cwd\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy.utils.misc import create_instance, load_object\nfrom scrapy.utils.log import failure_to_exc_info\nfrom scrapy.utils.python import without_none_values\nfrom scrapy.utils.boto import is_botocore\n\nlogger = logging.getLogger(__name__)\n\n\nclass IFeedStorage(Interface):\n    \"\"\"Interface that all Feed Storages must implement\"\"\"\n\n    def __init__(uri):\n        \"\"\"Initialize the storage with the parameters given in the URI\"\"\"\n\n    def open(spider):\n        \"\"\"Open the storage for the given spider. It must return a file-like\n        object that will be used for the exporters\"\"\"\n\n    def store(file):\n        \"\"\"Store the given file stream\"\"\"\n\n\n@implementer(IFeedStorage)\nclass BlockingFeedStorage(object):\n\n    def open(self, spider):\n        path = spider.crawler.settings['FEED_TEMPDIR']\n        if path and not os.path.isdir(path):\n            raise OSError('Not a Directory: ' + str(path))\n\n        return NamedTemporaryFile(prefix='feed-', dir=path)\n\n    def store(self, file):\n        return threads.deferToThread(self._store_in_thread, file)\n\n    def _store_in_thread(self, file):\n        raise NotImplementedError\n\n\n@implementer(IFeedStorage)\nclass StdoutFeedStorage(object):\n\n    def __init__(self, uri, _stdout=None):\n        if not _stdout:\n            _stdout = sys.stdout if six.PY2 else sys.stdout.buffer\n        self._stdout = _stdout\n\n    def open(self, spider):\n        return self._stdout\n\n    def store(self, file):\n        pass\n\n\n@implementer(IFeedStorage)\nclass FileFeedStorage(object):\n\n    def __init__(self, uri):\n        self.path = file_uri_to_path(uri)\n\n    def open(self, spider):\n        dirname = os.path.dirname(self.path)\n        if dirname and not os.path.exists(dirname):\n            os.makedirs(dirname)\n        return open(self.path, 'ab')\n\n    def store(self, file):\n        file.close()\n\n\nclass S3FeedStorage(BlockingFeedStorage):\n\n    def __init__(self, uri, access_key=None, secret_key=None, acl=None):\n        # BEGIN Backward compatibility for initialising without keys (and\n        # without using from_crawler)\n        no_defaults = access_key is None and secret_key is None\n        if no_defaults:\n            from scrapy.utils.project import get_project_settings\n            settings = get_project_settings()\n            if 'AWS_ACCESS_KEY_ID' in settings or 'AWS_SECRET_ACCESS_KEY' in settings:\n                import warnings\n                from scrapy.exceptions import ScrapyDeprecationWarning\n                warnings.warn(\n                    \"Initialising `scrapy.extensions.feedexport.S3FeedStorage` \"\n                    \"without AWS keys is deprecated. Please supply credentials or \"\n                    \"use the `from_crawler()` constructor.\",\n                    category=ScrapyDeprecationWarning,\n                    stacklevel=2\n                )\n                access_key = settings['AWS_ACCESS_KEY_ID']\n                secret_key = settings['AWS_SECRET_ACCESS_KEY']\n        # END Backward compatibility\n        u = urlparse(uri)\n        self.bucketname = u.hostname\n        self.access_key = u.username or access_key\n        self.secret_key = u.password or secret_key\n        self.is_botocore = is_botocore()\n        self.keyname = u.path[1:]  # remove first \"/\"\n        self.acl = acl\n        if self.is_botocore:\n            import botocore.session\n            session = botocore.session.get_session()\n            self.s3_client = session.create_client(\n                's3', aws_access_key_id=self.access_key,\n                aws_secret_access_key=self.secret_key)\n        else:\n            import boto\n            self.connect_s3 = boto.connect_s3\n\n    @classmethod\n    def from_crawler(cls, crawler, uri):\n        return cls(\n            uri=uri,\n            access_key=crawler.settings['AWS_ACCESS_KEY_ID'],\n            secret_key=crawler.settings['AWS_SECRET_ACCESS_KEY'],\n            acl=crawler.settings['FEED_STORAGE_S3_ACL'] or None\n        )\n\n    def _store_in_thread(self, file):\n        file.seek(0)\n        if self.is_botocore:\n            kwargs = {'ACL': self.acl} if self.acl else {}\n            self.s3_client.put_object(\n                Bucket=self.bucketname, Key=self.keyname, Body=file,\n                **kwargs)\n        else:\n            conn = self.connect_s3(self.access_key, self.secret_key)\n            bucket = conn.get_bucket(self.bucketname, validate=False)\n            key = bucket.new_key(self.keyname)\n            kwargs = {'policy': self.acl} if self.acl else {}\n            key.set_contents_from_file(file, **kwargs)\n            key.close()\n\n\nclass FTPFeedStorage(BlockingFeedStorage):\n\n    def __init__(self, uri, use_active_mode=False):\n        u = urlparse(uri)\n        self.host = u.hostname\n        self.port = int(u.port or '21')\n        self.username = u.username\n        self.password = u.password\n        self.path = u.path\n        self.use_active_mode = use_active_mode\n\n    @classmethod\n    def from_crawler(cls, crawler, uri):\n        return cls(\n            uri=uri,\n            use_active_mode=crawler.settings.getbool('FEED_STORAGE_FTP_ACTIVE')\n        )\n\n    def _store_in_thread(self, file):\n        file.seek(0)\n        ftp = FTP()\n        ftp.connect(self.host, self.port)\n        ftp.login(self.username, self.password)\n        if self.use_active_mode:\n            ftp.set_pasv(False)\n        dirname, filename = posixpath.split(self.path)\n        ftp_makedirs_cwd(ftp, dirname)\n        ftp.storbinary('STOR %s' % filename, file)\n        ftp.quit()\n\n\nclass SpiderSlot(object):\n    def __init__(self, file, exporter, storage, uri):\n        self.file = file\n        self.exporter = exporter\n        self.storage = storage\n        self.uri = uri\n        self.itemcount = 0\n\n\nclass FeedExporter(object):\n\n    def __init__(self, settings):\n        self.settings = settings\n        self.urifmt = settings['FEED_URI']\n        if not self.urifmt:\n            raise NotConfigured\n        self.format = settings['FEED_FORMAT'].lower()\n        self.export_encoding = settings['FEED_EXPORT_ENCODING']\n        self.storages = self._load_components('FEED_STORAGES')\n        self.exporters = self._load_components('FEED_EXPORTERS')\n        if not self._storage_supported(self.urifmt):\n            raise NotConfigured\n        if not self._exporter_supported(self.format):\n            raise NotConfigured\n        self.store_empty = settings.getbool('FEED_STORE_EMPTY')\n        self._exporting = False\n        self.export_fields = settings.getlist('FEED_EXPORT_FIELDS') or None\n        self.indent = None\n        if settings.get('FEED_EXPORT_INDENT') is not None:\n            self.indent = settings.getint('FEED_EXPORT_INDENT')\n        uripar = settings['FEED_URI_PARAMS']\n        self._uripar = load_object(uripar) if uripar else lambda x, y: None\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        o = cls(crawler.settings)\n        o.crawler = crawler\n        crawler.signals.connect(o.open_spider, signals.spider_opened)\n        crawler.signals.connect(o.close_spider, signals.spider_closed)\n        crawler.signals.connect(o.item_scraped, signals.item_scraped)\n        return o\n\n    def open_spider(self, spider):\n        uri = self.urifmt % self._get_uri_params(spider)\n        storage = self._get_storage(uri)\n        file = storage.open(spider)\n        exporter = self._get_exporter(file, fields_to_export=self.export_fields,\n            encoding=self.export_encoding, indent=self.indent)\n        if self.store_empty:\n            exporter.start_exporting()\n            self._exporting = True\n        self.slot = SpiderSlot(file, exporter, storage, uri)\n\n    def close_spider(self, spider):\n        slot = self.slot\n        if not slot.itemcount and not self.store_empty:\n            return\n        if self._exporting:\n            slot.exporter.finish_exporting()\n            self._exporting = False\n        logfmt = \"%s %%(format)s feed (%%(itemcount)d items) in: %%(uri)s\"\n        log_args = {'format': self.format,\n                    'itemcount': slot.itemcount,\n                    'uri': slot.uri}\n        d = defer.maybeDeferred(slot.storage.store, slot.file)\n        d.addCallback(lambda _: logger.info(logfmt % \"Stored\", log_args,\n                                            extra={'spider': spider}))\n        d.addErrback(lambda f: logger.error(logfmt % \"Error storing\", log_args,\n                                            exc_info=failure_to_exc_info(f),\n                                            extra={'spider': spider}))\n        return d\n\n    def item_scraped(self, item, spider):\n        slot = self.slot\n        if not self._exporting:\n            slot.exporter.start_exporting()\n            self._exporting = True\n        slot.exporter.export_item(item)\n        slot.itemcount += 1\n        return item\n\n    def _load_components(self, setting_prefix):\n        conf = without_none_values(self.settings.getwithbase(setting_prefix))\n        d = {}\n        for k, v in conf.items():\n            try:\n                d[k] = load_object(v)\n            except NotConfigured:\n                pass\n        return d\n\n    def _exporter_supported(self, format):\n        if format in self.exporters:\n            return True\n        logger.error(\"Unknown feed format: %(format)s\", {'format': format})\n\n    def _storage_supported(self, uri):\n        scheme = urlparse(uri).scheme\n        if scheme in self.storages:\n            try:\n                self._get_storage(uri)\n                return True\n            except NotConfigured as e:\n                logger.error(\"Disabled feed storage scheme: %(scheme)s. \"\n                             \"Reason: %(reason)s\",\n                             {'scheme': scheme, 'reason': str(e)})\n        else:\n            logger.error(\"Unknown feed storage scheme: %(scheme)s\",\n                         {'scheme': scheme})\n\n    def _get_instance(self, objcls, *args, **kwargs):\n        return create_instance(\n            objcls, self.settings, getattr(self, 'crawler', None),\n            *args, **kwargs)\n\n    def _get_exporter(self, *args, **kwargs):\n        return self._get_instance(self.exporters[self.format], *args, **kwargs)\n\n    def _get_storage(self, uri):\n        return self._get_instance(self.storages[urlparse(uri).scheme], uri)\n\n    def _get_uri_params(self, spider):\n        params = {}\n        for k in dir(spider):\n            params[k] = getattr(spider, k)\n        ts = datetime.utcnow().replace(microsecond=0).isoformat().replace(':', '-')\n        params['time'] = ts\n        self._uripar(params, spider)\n        return params\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/httpcache.py",
    "content": "from __future__ import print_function\nimport os\nimport gzip\nimport logging\nfrom six.moves import cPickle as pickle\nfrom importlib import import_module\nfrom time import time\nfrom weakref import WeakKeyDictionary\nfrom email.utils import mktime_tz, parsedate_tz\nfrom w3lib.http import headers_raw_to_dict, headers_dict_to_raw\nfrom scrapy.http import Headers, Response\nfrom scrapy.responsetypes import responsetypes\nfrom scrapy.utils.request import request_fingerprint\nfrom scrapy.utils.project import data_path\nfrom scrapy.utils.httpobj import urlparse_cached\nfrom scrapy.utils.python import to_bytes, to_unicode, garbage_collect\n\n\nlogger = logging.getLogger(__name__)\n\n\nclass DummyPolicy(object):\n\n    def __init__(self, settings):\n        self.ignore_schemes = settings.getlist('HTTPCACHE_IGNORE_SCHEMES')\n        self.ignore_http_codes = [int(x) for x in settings.getlist('HTTPCACHE_IGNORE_HTTP_CODES')]\n\n    def should_cache_request(self, request):\n        return urlparse_cached(request).scheme not in self.ignore_schemes\n\n    def should_cache_response(self, response, request):\n        return response.status not in self.ignore_http_codes\n\n    def is_cached_response_fresh(self, cachedresponse, request):\n        return True\n\n    def is_cached_response_valid(self, cachedresponse, response, request):\n        return True\n\n\nclass RFC2616Policy(object):\n\n    MAXAGE = 3600 * 24 * 365  # one year\n\n    def __init__(self, settings):\n        self.always_store = settings.getbool('HTTPCACHE_ALWAYS_STORE')\n        self.ignore_schemes = settings.getlist('HTTPCACHE_IGNORE_SCHEMES')\n        self.ignore_response_cache_controls = [to_bytes(cc) for cc in\n            settings.getlist('HTTPCACHE_IGNORE_RESPONSE_CACHE_CONTROLS')]\n        self._cc_parsed = WeakKeyDictionary()\n\n    def _parse_cachecontrol(self, r):\n        if r not in self._cc_parsed:\n            cch = r.headers.get(b'Cache-Control', b'')\n            parsed = parse_cachecontrol(cch)\n            if isinstance(r, Response):\n                for key in self.ignore_response_cache_controls:\n                    parsed.pop(key, None)\n            self._cc_parsed[r] = parsed\n        return self._cc_parsed[r]\n\n    def should_cache_request(self, request):\n        if urlparse_cached(request).scheme in self.ignore_schemes:\n            return False\n        cc = self._parse_cachecontrol(request)\n        # obey user-agent directive \"Cache-Control: no-store\"\n        if b'no-store' in cc:\n            return False\n        # Any other is eligible for caching\n        return True\n\n    def should_cache_response(self, response, request):\n        # What is cacheable - https://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.9.1\n        # Response cacheability - https://www.w3.org/Protocols/rfc2616/rfc2616-sec13.html#sec13.4\n        # Status code 206 is not included because cache can not deal with partial contents\n        cc = self._parse_cachecontrol(response)\n        # obey directive \"Cache-Control: no-store\"\n        if b'no-store' in cc:\n            return False\n        # Never cache 304 (Not Modified) responses\n        elif response.status == 304:\n            return False\n        # Cache unconditionally if configured to do so\n        elif self.always_store:\n            return True\n        # Any hint on response expiration is good\n        elif b'max-age' in cc or b'Expires' in response.headers:\n            return True\n        # Firefox fallbacks this statuses to one year expiration if none is set\n        elif response.status in (300, 301, 308):\n            return True\n        # Other statuses without expiration requires at least one validator\n        elif response.status in (200, 203, 401):\n            return b'Last-Modified' in response.headers or b'ETag' in response.headers\n        # Any other is probably not eligible for caching\n        # Makes no sense to cache responses that does not contain expiration\n        # info and can not be revalidated\n        else:\n            return False\n\n    def is_cached_response_fresh(self, cachedresponse, request):\n        cc = self._parse_cachecontrol(cachedresponse)\n        ccreq = self._parse_cachecontrol(request)\n        if b'no-cache' in cc or b'no-cache' in ccreq:\n            return False\n\n        now = time()\n        freshnesslifetime = self._compute_freshness_lifetime(cachedresponse, request, now)\n        currentage = self._compute_current_age(cachedresponse, request, now)\n\n        reqmaxage = self._get_max_age(ccreq)\n        if reqmaxage is not None:\n            freshnesslifetime = min(freshnesslifetime, reqmaxage)\n\n        if currentage < freshnesslifetime:\n            return True\n\n        if b'max-stale' in ccreq and b'must-revalidate' not in cc:\n            # From RFC2616: \"Indicates that the client is willing to\n            # accept a response that has exceeded its expiration time.\n            # If max-stale is assigned a value, then the client is\n            # willing to accept a response that has exceeded its\n            # expiration time by no more than the specified number of\n            # seconds. If no value is assigned to max-stale, then the\n            # client is willing to accept a stale response of any age.\"\n            staleage = ccreq[b'max-stale']\n            if staleage is None:\n                return True\n\n            try:\n                if currentage < freshnesslifetime + max(0, int(staleage)):\n                    return True\n            except ValueError:\n                pass\n\n        # Cached response is stale, try to set validators if any\n        self._set_conditional_validators(request, cachedresponse)\n        return False\n\n    def is_cached_response_valid(self, cachedresponse, response, request):\n        # Use the cached response if the new response is a server error,\n        # as long as the old response didn't specify must-revalidate.\n        if response.status >= 500:\n            cc = self._parse_cachecontrol(cachedresponse)\n            if b'must-revalidate' not in cc:\n                return True\n\n        # Use the cached response if the server says it hasn't changed.\n        return response.status == 304\n\n    def _set_conditional_validators(self, request, cachedresponse):\n        if b'Last-Modified' in cachedresponse.headers:\n            request.headers[b'If-Modified-Since'] = cachedresponse.headers[b'Last-Modified']\n\n        if b'ETag' in cachedresponse.headers:\n            request.headers[b'If-None-Match'] = cachedresponse.headers[b'ETag']\n\n    def _get_max_age(self, cc):\n        try:\n            return max(0, int(cc[b'max-age']))\n        except (KeyError, ValueError):\n            return None\n\n    def _compute_freshness_lifetime(self, response, request, now):\n        # Reference nsHttpResponseHead::ComputeFreshnessLifetime\n        # https://dxr.mozilla.org/mozilla-central/source/netwerk/protocol/http/nsHttpResponseHead.cpp#706\n        cc = self._parse_cachecontrol(response)\n        maxage = self._get_max_age(cc)\n        if maxage is not None:\n            return maxage\n\n        # Parse date header or synthesize it if none exists\n        date = rfc1123_to_epoch(response.headers.get(b'Date')) or now\n\n        # Try HTTP/1.0 Expires header\n        if b'Expires' in response.headers:\n            expires = rfc1123_to_epoch(response.headers[b'Expires'])\n            # When parsing Expires header fails RFC 2616 section 14.21 says we\n            # should treat this as an expiration time in the past.\n            return max(0, expires - date) if expires else 0\n\n        # Fallback to heuristic using last-modified header\n        # This is not in RFC but on Firefox caching implementation\n        lastmodified = rfc1123_to_epoch(response.headers.get(b'Last-Modified'))\n        if lastmodified and lastmodified <= date:\n            return (date - lastmodified) / 10\n\n        # This request can be cached indefinitely\n        if response.status in (300, 301, 308):\n            return self.MAXAGE\n\n        # Insufficient information to compute fresshness lifetime\n        return 0\n\n    def _compute_current_age(self, response, request, now):\n        # Reference nsHttpResponseHead::ComputeCurrentAge\n        # https://dxr.mozilla.org/mozilla-central/source/netwerk/protocol/http/nsHttpResponseHead.cpp#658\n        currentage = 0\n        # If Date header is not set we assume it is a fast connection, and\n        # clock is in sync with the server\n        date = rfc1123_to_epoch(response.headers.get(b'Date')) or now\n        if now > date:\n            currentage = now - date\n\n        if b'Age' in response.headers:\n            try:\n                age = int(response.headers[b'Age'])\n                currentage = max(currentage, age)\n            except ValueError:\n                pass\n\n        return currentage\n\n\nclass DbmCacheStorage(object):\n\n    def __init__(self, settings):\n        self.cachedir = data_path(settings['HTTPCACHE_DIR'], createdir=True)\n        self.expiration_secs = settings.getint('HTTPCACHE_EXPIRATION_SECS')\n        self.dbmodule = import_module(settings['HTTPCACHE_DBM_MODULE'])\n        self.db = None\n\n    def open_spider(self, spider):\n        dbpath = os.path.join(self.cachedir, '%s.db' % spider.name)\n        self.db = self.dbmodule.open(dbpath, 'c')\n\n        logger.debug(\"Using DBM cache storage in %(cachepath)s\" % {'cachepath': dbpath}, extra={'spider': spider})\n\n    def close_spider(self, spider):\n        self.db.close()\n\n    def retrieve_response(self, spider, request):\n        data = self._read_data(spider, request)\n        if data is None:\n            return  # not cached\n        url = data['url']\n        status = data['status']\n        headers = Headers(data['headers'])\n        body = data['body']\n        respcls = responsetypes.from_args(headers=headers, url=url)\n        response = respcls(url=url, headers=headers, status=status, body=body)\n        return response\n\n    def store_response(self, spider, request, response):\n        key = self._request_key(request)\n        data = {\n            'status': response.status,\n            'url': response.url,\n            'headers': dict(response.headers),\n            'body': response.body,\n        }\n        self.db['%s_data' % key] = pickle.dumps(data, protocol=2)\n        self.db['%s_time' % key] = str(time())\n\n    def _read_data(self, spider, request):\n        key = self._request_key(request)\n        db = self.db\n        tkey = '%s_time' % key\n        if tkey not in db:\n            return  # not found\n\n        ts = db[tkey]\n        if 0 < self.expiration_secs < time() - float(ts):\n            return  # expired\n\n        return pickle.loads(db['%s_data' % key])\n\n    def _request_key(self, request):\n        return request_fingerprint(request)\n\n\nclass FilesystemCacheStorage(object):\n\n    def __init__(self, settings):\n        self.cachedir = data_path(settings['HTTPCACHE_DIR'])\n        self.expiration_secs = settings.getint('HTTPCACHE_EXPIRATION_SECS')\n        self.use_gzip = settings.getbool('HTTPCACHE_GZIP')\n        self._open = gzip.open if self.use_gzip else open\n\n    def open_spider(self, spider):\n        logger.debug(\"Using filesystem cache storage in %(cachedir)s\" % {'cachedir': self.cachedir},\n                     extra={'spider': spider})\n\n    def close_spider(self, spider):\n        pass\n\n    def retrieve_response(self, spider, request):\n        \"\"\"Return response if present in cache, or None otherwise.\"\"\"\n        metadata = self._read_meta(spider, request)\n        if metadata is None:\n            return  # not cached\n        rpath = self._get_request_path(spider, request)\n        with self._open(os.path.join(rpath, 'response_body'), 'rb') as f:\n            body = f.read()\n        with self._open(os.path.join(rpath, 'response_headers'), 'rb') as f:\n            rawheaders = f.read()\n        url = metadata.get('response_url')\n        status = metadata['status']\n        headers = Headers(headers_raw_to_dict(rawheaders))\n        respcls = responsetypes.from_args(headers=headers, url=url)\n        response = respcls(url=url, headers=headers, status=status, body=body)\n        return response\n\n    def store_response(self, spider, request, response):\n        \"\"\"Store the given response in the cache.\"\"\"\n        rpath = self._get_request_path(spider, request)\n        if not os.path.exists(rpath):\n            os.makedirs(rpath)\n        metadata = {\n            'url': request.url,\n            'method': request.method,\n            'status': response.status,\n            'response_url': response.url,\n            'timestamp': time(),\n        }\n        with self._open(os.path.join(rpath, 'meta'), 'wb') as f:\n            f.write(to_bytes(repr(metadata)))\n        with self._open(os.path.join(rpath, 'pickled_meta'), 'wb') as f:\n            pickle.dump(metadata, f, protocol=2)\n        with self._open(os.path.join(rpath, 'response_headers'), 'wb') as f:\n            f.write(headers_dict_to_raw(response.headers))\n        with self._open(os.path.join(rpath, 'response_body'), 'wb') as f:\n            f.write(response.body)\n        with self._open(os.path.join(rpath, 'request_headers'), 'wb') as f:\n            f.write(headers_dict_to_raw(request.headers))\n        with self._open(os.path.join(rpath, 'request_body'), 'wb') as f:\n            f.write(request.body)\n\n    def _get_request_path(self, spider, request):\n        key = request_fingerprint(request)\n        return os.path.join(self.cachedir, spider.name, key[0:2], key)\n\n    def _read_meta(self, spider, request):\n        rpath = self._get_request_path(spider, request)\n        metapath = os.path.join(rpath, 'pickled_meta')\n        if not os.path.exists(metapath):\n            return  # not found\n        mtime = os.stat(metapath).st_mtime\n        if 0 < self.expiration_secs < time() - mtime:\n            return  # expired\n        with self._open(metapath, 'rb') as f:\n            return pickle.load(f)\n\n\nclass LeveldbCacheStorage(object):\n\n    def __init__(self, settings):\n        import leveldb\n        self._leveldb = leveldb\n        self.cachedir = data_path(settings['HTTPCACHE_DIR'], createdir=True)\n        self.expiration_secs = settings.getint('HTTPCACHE_EXPIRATION_SECS')\n        self.db = None\n\n    def open_spider(self, spider):\n        dbpath = os.path.join(self.cachedir, '%s.leveldb' % spider.name)\n        self.db = self._leveldb.LevelDB(dbpath)\n\n        logger.debug(\"Using LevelDB cache storage in %(cachepath)s\" % {'cachepath': dbpath}, extra={'spider': spider})\n\n    def close_spider(self, spider):\n        # Do compactation each time to save space and also recreate files to\n        # avoid them being removed in storages with timestamp-based autoremoval.\n        self.db.CompactRange()\n        del self.db\n        garbage_collect()\n\n    def retrieve_response(self, spider, request):\n        data = self._read_data(spider, request)\n        if data is None:\n            return  # not cached\n        url = data['url']\n        status = data['status']\n        headers = Headers(data['headers'])\n        body = data['body']\n        respcls = responsetypes.from_args(headers=headers, url=url)\n        response = respcls(url=url, headers=headers, status=status, body=body)\n        return response\n\n    def store_response(self, spider, request, response):\n        key = self._request_key(request)\n        data = {\n            'status': response.status,\n            'url': response.url,\n            'headers': dict(response.headers),\n            'body': response.body,\n        }\n        batch = self._leveldb.WriteBatch()\n        batch.Put(key + b'_data', pickle.dumps(data, protocol=2))\n        batch.Put(key + b'_time', to_bytes(str(time())))\n        self.db.Write(batch)\n\n    def _read_data(self, spider, request):\n        key = self._request_key(request)\n        try:\n            ts = self.db.Get(key + b'_time')\n        except KeyError:\n            return  # not found or invalid entry\n\n        if 0 < self.expiration_secs < time() - float(ts):\n            return  # expired\n\n        try:\n            data = self.db.Get(key + b'_data')\n        except KeyError:\n            return  # invalid entry\n        else:\n            return pickle.loads(data)\n\n    def _request_key(self, request):\n        return to_bytes(request_fingerprint(request))\n\n\n\ndef parse_cachecontrol(header):\n    \"\"\"Parse Cache-Control header\n\n    https://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.9\n\n    >>> parse_cachecontrol(b'public, max-age=3600') == {b'public': None,\n    ...                                                 b'max-age': b'3600'}\n    True\n    >>> parse_cachecontrol(b'') == {}\n    True\n\n    \"\"\"\n    directives = {}\n    for directive in header.split(b','):\n        key, sep, val = directive.strip().partition(b'=')\n        if key:\n            directives[key.lower()] = val if sep else None\n    return directives\n\n\ndef rfc1123_to_epoch(date_str):\n    try:\n        date_str = to_unicode(date_str, encoding='ascii')\n        return mktime_tz(parsedate_tz(date_str))\n    except Exception:\n        return None\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/logstats.py",
    "content": "import logging\n\nfrom twisted.internet import task\n\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy import signals\n\nlogger = logging.getLogger(__name__)\n\n\nclass LogStats(object):\n    \"\"\"Log basic scraping stats periodically\"\"\"\n\n    def __init__(self, stats, interval=60.0):\n        self.stats = stats\n        self.interval = interval\n        self.multiplier = 60.0 / self.interval\n        self.task = None\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        interval = crawler.settings.getfloat('LOGSTATS_INTERVAL')\n        if not interval:\n            raise NotConfigured\n        o = cls(crawler.stats, interval)\n        crawler.signals.connect(o.spider_opened, signal=signals.spider_opened)\n        crawler.signals.connect(o.spider_closed, signal=signals.spider_closed)\n        return o\n\n    def spider_opened(self, spider):\n        self.pagesprev = 0\n        self.itemsprev = 0\n\n        self.task = task.LoopingCall(self.log, spider)\n        self.task.start(self.interval)\n\n    def log(self, spider):\n        items = self.stats.get_value('item_scraped_count', 0)\n        pages = self.stats.get_value('response_received_count', 0)\n        irate = (items - self.itemsprev) * self.multiplier\n        prate = (pages - self.pagesprev) * self.multiplier\n        self.pagesprev, self.itemsprev = pages, items\n\n        msg = (\"Crawled %(pages)d pages (at %(pagerate)d pages/min), \"\n               \"scraped %(items)d items (at %(itemrate)d items/min)\")\n        log_args = {'pages': pages, 'pagerate': prate,\n                    'items': items, 'itemrate': irate}\n        logger.info(msg, log_args, extra={'spider': spider})\n\n    def spider_closed(self, spider, reason):\n        if self.task and self.task.running:\n            self.task.stop()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/memdebug.py",
    "content": "\"\"\"\nMemoryDebugger extension\n\nSee documentation in docs/topics/extensions.rst\n\"\"\"\n\nimport gc\nimport six\n\nfrom scrapy import signals\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy.utils.trackref import live_refs\n\n\nclass MemoryDebugger(object):\n\n    def __init__(self, stats):\n        self.stats = stats\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        if not crawler.settings.getbool('MEMDEBUG_ENABLED'):\n            raise NotConfigured\n        o = cls(crawler.stats)\n        crawler.signals.connect(o.spider_closed, signal=signals.spider_closed)\n        return o\n\n    def spider_closed(self, spider, reason):\n        gc.collect()\n        self.stats.set_value('memdebug/gc_garbage_count', len(gc.garbage), spider=spider)\n        for cls, wdict in six.iteritems(live_refs):\n            if not wdict:\n                continue\n            self.stats.set_value('memdebug/live_refs/%s' % cls.__name__, len(wdict), spider=spider)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/memusage.py",
    "content": "\"\"\"\nMemoryUsage extension\n\nSee documentation in docs/topics/extensions.rst\n\"\"\"\nimport sys\nimport socket\nimport logging\nfrom pprint import pformat\nfrom importlib import import_module\n\nfrom twisted.internet import task\n\nfrom scrapy import signals\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy.mail import MailSender\nfrom scrapy.utils.engine import get_engine_status\n\nlogger = logging.getLogger(__name__)\n\n\nclass MemoryUsage(object):\n\n    def __init__(self, crawler):\n        if not crawler.settings.getbool('MEMUSAGE_ENABLED'):\n            raise NotConfigured\n        try:\n            # stdlib's resource module is only available on unix platforms.\n            self.resource = import_module('resource')\n        except ImportError:\n            raise NotConfigured\n\n        self.crawler = crawler\n        self.warned = False\n        self.notify_mails = crawler.settings.getlist('MEMUSAGE_NOTIFY_MAIL')\n        self.limit = crawler.settings.getint('MEMUSAGE_LIMIT_MB')*1024*1024\n        self.warning = crawler.settings.getint('MEMUSAGE_WARNING_MB')*1024*1024\n        self.check_interval = crawler.settings.getfloat('MEMUSAGE_CHECK_INTERVAL_SECONDS')\n        self.mail = MailSender.from_settings(crawler.settings)\n        crawler.signals.connect(self.engine_started, signal=signals.engine_started)\n        crawler.signals.connect(self.engine_stopped, signal=signals.engine_stopped)\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls(crawler)\n\n    def get_virtual_size(self):\n        size = self.resource.getrusage(self.resource.RUSAGE_SELF).ru_maxrss\n        if sys.platform != 'darwin':\n            # on Mac OS X ru_maxrss is in bytes, on Linux it is in KB\n            size *= 1024\n        return size\n\n    def engine_started(self):\n        self.crawler.stats.set_value('memusage/startup', self.get_virtual_size())\n        self.tasks = []\n        tsk = task.LoopingCall(self.update)\n        self.tasks.append(tsk)\n        tsk.start(self.check_interval, now=True)\n        if self.limit:\n            tsk = task.LoopingCall(self._check_limit)\n            self.tasks.append(tsk)\n            tsk.start(self.check_interval, now=True)\n        if self.warning:\n            tsk = task.LoopingCall(self._check_warning)\n            self.tasks.append(tsk)\n            tsk.start(self.check_interval, now=True)\n\n    def engine_stopped(self):\n        for tsk in self.tasks:\n            if tsk.running:\n                tsk.stop()\n\n    def update(self):\n        self.crawler.stats.max_value('memusage/max', self.get_virtual_size())\n\n    def _check_limit(self):\n        if self.get_virtual_size() > self.limit:\n            self.crawler.stats.set_value('memusage/limit_reached', 1)\n            mem = self.limit/1024/1024\n            logger.error(\"Memory usage exceeded %(memusage)dM. Shutting down Scrapy...\",\n                         {'memusage': mem}, extra={'crawler': self.crawler})\n            if self.notify_mails:\n                subj = \"%s terminated: memory usage exceeded %dM at %s\" % \\\n                        (self.crawler.settings['BOT_NAME'], mem, socket.gethostname())\n                self._send_report(self.notify_mails, subj)\n                self.crawler.stats.set_value('memusage/limit_notified', 1)\n\n            open_spiders = self.crawler.engine.open_spiders\n            if open_spiders:\n                for spider in open_spiders:\n                    self.crawler.engine.close_spider(spider, 'memusage_exceeded')\n            else:\n                self.crawler.stop()\n\n    def _check_warning(self):\n        if self.warned: # warn only once\n            return\n        if self.get_virtual_size() > self.warning:\n            self.crawler.stats.set_value('memusage/warning_reached', 1)\n            mem = self.warning/1024/1024\n            logger.warning(\"Memory usage reached %(memusage)dM\",\n                           {'memusage': mem}, extra={'crawler': self.crawler})\n            if self.notify_mails:\n                subj = \"%s warning: memory usage reached %dM at %s\" % \\\n                        (self.crawler.settings['BOT_NAME'], mem, socket.gethostname())\n                self._send_report(self.notify_mails, subj)\n                self.crawler.stats.set_value('memusage/warning_notified', 1)\n            self.warned = True\n\n    def _send_report(self, rcpts, subject):\n        \"\"\"send notification mail with some additional useful info\"\"\"\n        stats = self.crawler.stats\n        s = \"Memory usage at engine startup : %dM\\r\\n\" % (stats.get_value('memusage/startup')/1024/1024)\n        s += \"Maximum memory usage           : %dM\\r\\n\" % (stats.get_value('memusage/max')/1024/1024)\n        s += \"Current memory usage           : %dM\\r\\n\" % (self.get_virtual_size()/1024/1024)\n\n        s += \"ENGINE STATUS ------------------------------------------------------- \\r\\n\"\n        s += \"\\r\\n\"\n        s += pformat(get_engine_status(self.crawler.engine))\n        s += \"\\r\\n\"\n        self.mail.send(rcpts, subject, s)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/spiderstate.py",
    "content": "import os\nfrom six.moves import cPickle as pickle\n\nfrom scrapy import signals\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy.utils.job import job_dir\n\nclass SpiderState(object):\n    \"\"\"Store and load spider state during a scraping job\"\"\"\n\n    def __init__(self, jobdir=None):\n        self.jobdir = jobdir\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        jobdir = job_dir(crawler.settings)\n        if not jobdir:\n            raise NotConfigured\n\n        obj = cls(jobdir)\n        crawler.signals.connect(obj.spider_closed, signal=signals.spider_closed)\n        crawler.signals.connect(obj.spider_opened, signal=signals.spider_opened)\n        return obj\n\n    def spider_closed(self, spider):\n        if self.jobdir:\n            with open(self.statefn, 'wb') as f:\n                pickle.dump(spider.state, f, protocol=2)\n\n    def spider_opened(self, spider):\n        if self.jobdir and os.path.exists(self.statefn):\n            with open(self.statefn, 'rb') as f:\n                spider.state = pickle.load(f)\n        else:\n            spider.state = {}\n\n    @property\n    def statefn(self):\n        return os.path.join(self.jobdir, 'spider.state')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/statsmailer.py",
    "content": "\"\"\"\nStatsMailer extension sends an email when a spider finishes scraping.\n\nUse STATSMAILER_RCPTS setting to enable and give the recipient mail address\n\"\"\"\n\nfrom scrapy import signals\nfrom scrapy.mail import MailSender\nfrom scrapy.exceptions import NotConfigured\n\nclass StatsMailer(object):\n\n    def __init__(self, stats, recipients, mail):\n        self.stats = stats\n        self.recipients = recipients\n        self.mail = mail\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        recipients = crawler.settings.getlist(\"STATSMAILER_RCPTS\")\n        if not recipients:\n            raise NotConfigured\n        mail = MailSender.from_settings(crawler.settings)\n        o = cls(crawler.stats, recipients, mail)\n        crawler.signals.connect(o.spider_closed, signal=signals.spider_closed)\n        return o\n        \n    def spider_closed(self, spider):\n        spider_stats = self.stats.get_stats(spider)\n        body = \"Global stats\\n\\n\"\n        body += \"\\n\".join(\"%-50s : %s\" % i for i in self.stats.get_stats().items())\n        body += \"\\n\\n%s stats\\n\\n\" % spider.name\n        body += \"\\n\".join(\"%-50s : %s\" % i for i in spider_stats.items())\n        return self.mail.send(self.recipients, \"Scrapy stats for: %s\" % spider.name, body)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/telnet.py",
    "content": "\"\"\"\nScrapy Telnet Console extension\n\nSee documentation in docs/topics/telnetconsole.rst\n\"\"\"\n\nimport pprint\nimport logging\nimport traceback\nimport binascii\nimport os\n\nfrom twisted.internet import protocol\ntry:\n    from twisted.conch import manhole, telnet\n    from twisted.conch.insults import insults\n    TWISTED_CONCH_AVAILABLE = True\nexcept (ImportError, SyntaxError):\n    _TWISTED_CONCH_TRACEBACK = traceback.format_exc()\n    TWISTED_CONCH_AVAILABLE = False\n\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy import signals\nfrom scrapy.utils.trackref import print_live_refs\nfrom scrapy.utils.engine import print_engine_status\nfrom scrapy.utils.reactor import listen_tcp\nfrom scrapy.utils.decorators import defers\n\ntry:\n    import guppy\n    hpy = guppy.hpy()\nexcept ImportError:\n    hpy = None\n\nlogger = logging.getLogger(__name__)\n\n# signal to update telnet variables\n# args: telnet_vars\nupdate_telnet_vars = object()\n\n\nclass TelnetConsole(protocol.ServerFactory):\n\n    def __init__(self, crawler):\n        if not crawler.settings.getbool('TELNETCONSOLE_ENABLED'):\n            raise NotConfigured\n        if not TWISTED_CONCH_AVAILABLE:\n            raise NotConfigured(\n                'TELNETCONSOLE_ENABLED setting is True but required twisted '\n                'modules failed to import:\\n' + _TWISTED_CONCH_TRACEBACK)\n        self.crawler = crawler\n        self.noisy = False\n        self.portrange = [int(x) for x in crawler.settings.getlist('TELNETCONSOLE_PORT')]\n        self.host = crawler.settings['TELNETCONSOLE_HOST']\n        self.username = crawler.settings['TELNETCONSOLE_USERNAME']\n        self.password = crawler.settings['TELNETCONSOLE_PASSWORD']\n\n        if not self.password:\n            self.password = binascii.hexlify(os.urandom(8)).decode('utf8')\n            logger.info('Telnet Password: %s', self.password)\n\n        self.crawler.signals.connect(self.start_listening, signals.engine_started)\n        self.crawler.signals.connect(self.stop_listening, signals.engine_stopped)\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls(crawler)\n\n    def start_listening(self):\n        self.port = listen_tcp(self.portrange, self.host, self)\n        h = self.port.getHost()\n        logger.info(\"Telnet console listening on %(host)s:%(port)d\",\n                    {'host': h.host, 'port': h.port},\n                    extra={'crawler': self.crawler})\n\n    def stop_listening(self):\n        self.port.stopListening()\n\n    def protocol(self):\n        class Portal:\n            \"\"\"An implementation of IPortal\"\"\"\n            @defers\n            def login(self_, credentials, mind, *interfaces):\n                if not (credentials.username == self.username.encode('utf8') and\n                        credentials.checkPassword(self.password.encode('utf8'))):\n                    raise ValueError(\"Invalid credentials\")\n\n                protocol = telnet.TelnetBootstrapProtocol(\n                    insults.ServerProtocol,\n                    manhole.Manhole,\n                    self._get_telnet_vars()\n                )\n                return (interfaces[0], protocol, lambda: None)\n\n        return telnet.TelnetTransport(\n            telnet.AuthenticatingTelnetProtocol,\n            Portal()\n        )\n\n    def _get_telnet_vars(self):\n        # Note: if you add entries here also update topics/telnetconsole.rst\n        telnet_vars = {\n            'engine': self.crawler.engine,\n            'spider': self.crawler.engine.spider,\n            'slot': self.crawler.engine.slot,\n            'crawler': self.crawler,\n            'extensions': self.crawler.extensions,\n            'stats': self.crawler.stats,\n            'settings': self.crawler.settings,\n            'est': lambda: print_engine_status(self.crawler.engine),\n            'p': pprint.pprint,\n            'prefs': print_live_refs,\n            'hpy': hpy,\n            'help': \"This is Scrapy telnet console. For more info see: \"\n                    \"https://docs.scrapy.org/en/latest/topics/telnetconsole.html\",\n        }\n        self.crawler.signals.send_catch_log(update_telnet_vars, telnet_vars=telnet_vars)\n        return telnet_vars\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/extensions/throttle.py",
    "content": "import logging\n\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy import signals\n\nlogger = logging.getLogger(__name__)\n\n\nclass AutoThrottle(object):\n\n    def __init__(self, crawler):\n        self.crawler = crawler\n        if not crawler.settings.getbool('AUTOTHROTTLE_ENABLED'):\n            raise NotConfigured\n\n        self.debug = crawler.settings.getbool(\"AUTOTHROTTLE_DEBUG\")\n        self.target_concurrency = crawler.settings.getfloat(\"AUTOTHROTTLE_TARGET_CONCURRENCY\")\n        crawler.signals.connect(self._spider_opened, signal=signals.spider_opened)\n        crawler.signals.connect(self._response_downloaded, signal=signals.response_downloaded)\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls(crawler)\n\n    def _spider_opened(self, spider):\n        self.mindelay = self._min_delay(spider)\n        self.maxdelay = self._max_delay(spider)\n        spider.download_delay = self._start_delay(spider)\n\n    def _min_delay(self, spider):\n        s = self.crawler.settings\n        return getattr(spider, 'download_delay', s.getfloat('DOWNLOAD_DELAY'))\n\n    def _max_delay(self, spider):\n        return self.crawler.settings.getfloat('AUTOTHROTTLE_MAX_DELAY')\n\n    def _start_delay(self, spider):\n        return max(self.mindelay, self.crawler.settings.getfloat('AUTOTHROTTLE_START_DELAY'))\n\n    def _response_downloaded(self, response, request, spider):\n        key, slot = self._get_slot(request, spider)\n        latency = request.meta.get('download_latency')\n        if latency is None or slot is None:\n            return\n\n        olddelay = slot.delay\n        self._adjust_delay(slot, latency, response)\n        if self.debug:\n            diff = slot.delay - olddelay\n            size = len(response.body)\n            conc = len(slot.transferring)\n            logger.info(\n                \"slot: %(slot)s | conc:%(concurrency)2d | \"\n                \"delay:%(delay)5d ms (%(delaydiff)+d) | \"\n                \"latency:%(latency)5d ms | size:%(size)6d bytes\",\n                {\n                    'slot': key, 'concurrency': conc,\n                    'delay': slot.delay * 1000, 'delaydiff': diff * 1000,\n                    'latency': latency * 1000, 'size': size\n                },\n                extra={'spider': spider}\n            )\n\n    def _get_slot(self, request, spider):\n        key = request.meta.get('download_slot')\n        return key, self.crawler.engine.downloader.slots.get(key)\n\n    def _adjust_delay(self, slot, latency, response):\n        \"\"\"Define delay adjustment policy\"\"\"\n\n        # If a server needs `latency` seconds to respond then\n        # we should send a request each `latency/N` seconds\n        # to have N requests processed in parallel\n        target_delay = latency / self.target_concurrency\n\n        # Adjust the delay to make it closer to target_delay\n        new_delay = (slot.delay + target_delay) / 2.0\n\n        # If target delay is bigger than old delay, then use it instead of mean.\n        # It works better with problematic sites.\n        new_delay = max(target_delay, new_delay)\n\n        # Make sure self.mindelay <= new_delay <= self.max_delay\n        new_delay = min(max(self.mindelay, new_delay), self.maxdelay)\n\n        # Dont adjust delay if response status != 200 and new delay is smaller\n        # than old one, as error pages (and redirections) are usually small and\n        # so tend to reduce latency, thus provoking a positive feedback by\n        # reducing delay instead of increase.\n        if response.status != 200 and new_delay <= slot.delay:\n            return\n\n        slot.delay = new_delay\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/http/__init__.py",
    "content": "\"\"\"\nModule containing all HTTP related classes\n\nUse this module (instead of the more specific ones) when importing Headers,\nRequest and Response outside this module.\n\"\"\"\n\nfrom scrapy.http.headers import Headers\n\nfrom scrapy.http.request import Request\nfrom scrapy.http.request.form import FormRequest\nfrom scrapy.http.request.rpc import XmlRpcRequest\nfrom scrapy.http.request.json_request import JSONRequest\n\nfrom scrapy.http.response import Response\nfrom scrapy.http.response.html import HtmlResponse\nfrom scrapy.http.response.xml import XmlResponse\nfrom scrapy.http.response.text import TextResponse\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/http/common.py",
    "content": "def obsolete_setter(setter, attrname):\n    def newsetter(self, value):\n        c = self.__class__.__name__\n        msg = \"%s.%s is not modifiable, use %s.replace() instead\" % (c, attrname, c)\n        raise AttributeError(msg)\n    return newsetter\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/http/cookies.py",
    "content": "import time\nfrom six.moves.http_cookiejar import (\n    CookieJar as _CookieJar, DefaultCookiePolicy, IPV4_RE\n)\nfrom scrapy.utils.httpobj import urlparse_cached\nfrom scrapy.utils.python import to_native_str\n\n\nclass CookieJar(object):\n    def __init__(self, policy=None, check_expired_frequency=10000):\n        self.policy = policy or DefaultCookiePolicy()\n        self.jar = _CookieJar(self.policy)\n        self.jar._cookies_lock = _DummyLock()\n        self.check_expired_frequency = check_expired_frequency\n        self.processed = 0\n\n    def extract_cookies(self, response, request):\n        wreq = WrappedRequest(request)\n        wrsp = WrappedResponse(response)\n        return self.jar.extract_cookies(wrsp, wreq)\n\n    def add_cookie_header(self, request):\n        wreq = WrappedRequest(request)\n        self.policy._now = self.jar._now = int(time.time())\n\n        # the cookiejar implementation iterates through all domains\n        # instead we restrict to potential matches on the domain\n        req_host = urlparse_cached(request).hostname\n        if not req_host:\n            return\n\n        if not IPV4_RE.search(req_host):\n            hosts = potential_domain_matches(req_host)\n            if '.' not in req_host:\n                hosts += [req_host + \".local\"]\n        else:\n            hosts = [req_host]\n\n        cookies = []\n        for host in hosts:\n            if host in self.jar._cookies:\n                cookies += self.jar._cookies_for_domain(host, wreq)\n\n        attrs = self.jar._cookie_attrs(cookies)\n        if attrs:\n            if not wreq.has_header(\"Cookie\"):\n                wreq.add_unredirected_header(\"Cookie\", \"; \".join(attrs))\n\n        self.processed += 1\n        if self.processed % self.check_expired_frequency == 0:\n            # This is still quite inefficient for large number of cookies\n            self.jar.clear_expired_cookies()\n\n    @property\n    def _cookies(self):\n        return self.jar._cookies\n\n    def clear_session_cookies(self, *args, **kwargs):\n        return self.jar.clear_session_cookies(*args, **kwargs)\n\n    def clear(self, domain=None, path=None, name=None):\n        return self.jar.clear(domain, path, name)\n\n    def __iter__(self):\n        return iter(self.jar)\n\n    def __len__(self):\n        return len(self.jar)\n\n    def set_policy(self, pol):\n        return self.jar.set_policy(pol)\n\n    def make_cookies(self, response, request):\n        wreq = WrappedRequest(request)\n        wrsp = WrappedResponse(response)\n        return self.jar.make_cookies(wrsp, wreq)\n\n    def set_cookie(self, cookie):\n        self.jar.set_cookie(cookie)\n\n    def set_cookie_if_ok(self, cookie, request):\n        self.jar.set_cookie_if_ok(cookie, WrappedRequest(request))\n\n\ndef potential_domain_matches(domain):\n    \"\"\"Potential domain matches for a cookie\n\n    >>> potential_domain_matches('www.example.com')\n    ['www.example.com', 'example.com', '.www.example.com', '.example.com']\n\n    \"\"\"\n    matches = [domain]\n    try:\n        start = domain.index('.') + 1\n        end = domain.rindex('.')\n        while start < end:\n            matches.append(domain[start:])\n            start = domain.index('.', start) + 1\n    except ValueError:\n        pass\n    return matches + ['.' + d for d in matches]\n\n\nclass _DummyLock(object):\n    def acquire(self):\n        pass\n\n    def release(self):\n        pass\n\n\nclass WrappedRequest(object):\n    \"\"\"Wraps a scrapy Request class with methods defined by urllib2.Request class to interact with CookieJar class\n\n    see http://docs.python.org/library/urllib2.html#urllib2.Request\n    \"\"\"\n\n    def __init__(self, request):\n        self.request = request\n\n    def get_full_url(self):\n        return self.request.url\n\n    def get_host(self):\n        return urlparse_cached(self.request).netloc\n\n    def get_type(self):\n        return urlparse_cached(self.request).scheme\n\n    def is_unverifiable(self):\n        \"\"\"Unverifiable should indicate whether the request is unverifiable, as defined by RFC 2965.\n\n        It defaults to False. An unverifiable request is one whose URL the user did not have the\n        option to approve. For example, if the request is for an image in an\n        HTML document, and the user had no option to approve the automatic\n        fetching of the image, this should be true.\n        \"\"\"\n        return self.request.meta.get('is_unverifiable', False)\n\n    def get_origin_req_host(self):\n        return urlparse_cached(self.request).hostname\n\n    # python3 uses attributes instead of methods\n    @property\n    def full_url(self):\n        return self.get_full_url()\n\n    @property\n    def host(self):\n        return self.get_host()\n\n    @property\n    def type(self):\n        return self.get_type()\n\n    @property\n    def unverifiable(self):\n        return self.is_unverifiable()\n\n    @property\n    def origin_req_host(self):\n        return self.get_origin_req_host()\n\n    def has_header(self, name):\n        return name in self.request.headers\n\n    def get_header(self, name, default=None):\n        return to_native_str(self.request.headers.get(name, default),\n                             errors='replace')\n\n    def header_items(self):\n        return [\n            (to_native_str(k, errors='replace'),\n             [to_native_str(x, errors='replace') for x in v])\n            for k, v in self.request.headers.items()\n        ]\n\n    def add_unredirected_header(self, name, value):\n        self.request.headers.appendlist(name, value)\n\n\nclass WrappedResponse(object):\n\n    def __init__(self, response):\n        self.response = response\n\n    def info(self):\n        return self\n\n    # python3 cookiejars calls get_all\n    def get_all(self, name, default=None):\n        return [to_native_str(v, errors='replace')\n                for v in self.response.headers.getlist(name)]\n    # python2 cookiejars calls getheaders\n    getheaders = get_all\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/http/headers.py",
    "content": "import six\nfrom w3lib.http import headers_dict_to_raw\nfrom scrapy.utils.datatypes import CaselessDict\nfrom scrapy.utils.python import to_unicode\n\n\nclass Headers(CaselessDict):\n    \"\"\"Case insensitive http headers dictionary\"\"\"\n\n    def __init__(self, seq=None, encoding='utf-8'):\n        self.encoding = encoding\n        super(Headers, self).__init__(seq)\n\n    def normkey(self, key):\n        \"\"\"Normalize key to bytes\"\"\"\n        return self._tobytes(key.title())\n\n    def normvalue(self, value):\n        \"\"\"Normalize values to bytes\"\"\"\n        if value is None:\n            value = []\n        elif isinstance(value, (six.text_type, bytes)):\n            value = [value]\n        elif not hasattr(value, '__iter__'):\n            value = [value]\n\n        return [self._tobytes(x) for x in value]\n\n    def _tobytes(self, x):\n        if isinstance(x, bytes):\n            return x\n        elif isinstance(x, six.text_type):\n            return x.encode(self.encoding)\n        elif isinstance(x, int):\n            return six.text_type(x).encode(self.encoding)\n        else:\n            raise TypeError('Unsupported value type: {}'.format(type(x)))\n\n    def __getitem__(self, key):\n        try:\n            return super(Headers, self).__getitem__(key)[-1]\n        except IndexError:\n            return None\n\n    def get(self, key, def_val=None):\n        try:\n            return super(Headers, self).get(key, def_val)[-1]\n        except IndexError:\n            return None\n\n    def getlist(self, key, def_val=None):\n        try:\n            return super(Headers, self).__getitem__(key)\n        except KeyError:\n            if def_val is not None:\n                return self.normvalue(def_val)\n            return []\n\n    def setlist(self, key, list_):\n        self[key] = list_\n\n    def setlistdefault(self, key, default_list=()):\n        return self.setdefault(key, default_list)\n\n    def appendlist(self, key, value):\n        lst = self.getlist(key)\n        lst.extend(self.normvalue(value))\n        self[key] = lst\n\n    def items(self):\n        return list(self.iteritems())\n\n    def iteritems(self):\n        return ((k, self.getlist(k)) for k in self.keys())\n\n    def values(self):\n        return [self[k] for k in self.keys()]\n\n    def to_string(self):\n        return headers_dict_to_raw(self)\n\n    def to_unicode_dict(self):\n        \"\"\" Return headers as a CaselessDict with unicode keys\n        and unicode values. Multiple values are joined with ','.\n        \"\"\"\n        return CaselessDict(\n            (to_unicode(key, encoding=self.encoding),\n             to_unicode(b','.join(value), encoding=self.encoding))\n            for key, value in self.items())\n\n    def __copy__(self):\n        return self.__class__(self)\n    copy = __copy__\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/http/request/__init__.py",
    "content": "\"\"\"\nThis module implements the Request class which is used to represent HTTP\nrequests in Scrapy.\n\nSee documentation in docs/topics/request-response.rst\n\"\"\"\nimport six\nfrom w3lib.url import safe_url_string\n\nfrom scrapy.http.headers import Headers\nfrom scrapy.utils.python import to_bytes\nfrom scrapy.utils.trackref import object_ref\nfrom scrapy.utils.url import escape_ajax\nfrom scrapy.http.common import obsolete_setter\n\n\nclass Request(object_ref):\n\n    def __init__(self, url, callback=None, method='GET', headers=None, body=None,\n                 cookies=None, meta=None, encoding='utf-8', priority=0,\n                 dont_filter=False, errback=None, flags=None, cb_kwargs=None):\n\n        self._encoding = encoding  # this one has to be set first\n        self.method = str(method).upper()\n        self._set_url(url)\n        self._set_body(body)\n        assert isinstance(priority, int), \"Request priority not an integer: %r\" % priority\n        self.priority = priority\n\n        if callback is not None and not callable(callback):\n            raise TypeError('callback must be a callable, got %s' % type(callback).__name__)\n        if errback is not None and not callable(errback):\n            raise TypeError('errback must be a callable, got %s' % type(errback).__name__)\n        assert callback or not errback, \"Cannot use errback without a callback\"\n        self.callback = callback\n        self.errback = errback\n\n        self.cookies = cookies or {}\n        self.headers = Headers(headers or {}, encoding=encoding)\n        self.dont_filter = dont_filter\n\n        self._meta = dict(meta) if meta else None\n        self._cb_kwargs = dict(cb_kwargs) if cb_kwargs else None\n        self.flags = [] if flags is None else list(flags)\n\n    @property\n    def cb_kwargs(self):\n        if self._cb_kwargs is None:\n            self._cb_kwargs = {}\n        return self._cb_kwargs\n\n    @property\n    def meta(self):\n        if self._meta is None:\n            self._meta = {}\n        return self._meta\n\n    def _get_url(self):\n        return self._url\n\n    def _set_url(self, url):\n        if not isinstance(url, six.string_types):\n            raise TypeError('Request url must be str or unicode, got %s:' % type(url).__name__)\n\n        s = safe_url_string(url, self.encoding)\n        self._url = escape_ajax(s)\n\n        if ':' not in self._url:\n            raise ValueError('Missing scheme in request url: %s' % self._url)\n\n    url = property(_get_url, obsolete_setter(_set_url, 'url'))\n\n    def _get_body(self):\n        return self._body\n\n    def _set_body(self, body):\n        if body is None:\n            self._body = b''\n        else:\n            self._body = to_bytes(body, self.encoding)\n\n    body = property(_get_body, obsolete_setter(_set_body, 'body'))\n\n    @property\n    def encoding(self):\n        return self._encoding\n\n    def __str__(self):\n        return \"<%s %s>\" % (self.method, self.url)\n\n    __repr__ = __str__\n\n    def copy(self):\n        \"\"\"Return a copy of this Request\"\"\"\n        return self.replace()\n\n    def replace(self, *args, **kwargs):\n        \"\"\"Create a new Request with the same attributes except for those\n        given new values.\n        \"\"\"\n        for x in ['url', 'method', 'headers', 'body', 'cookies', 'meta', 'flags',\n                  'encoding', 'priority', 'dont_filter', 'callback', 'errback', 'cb_kwargs']:\n            kwargs.setdefault(x, getattr(self, x))\n        cls = kwargs.pop('cls', self.__class__)\n        return cls(*args, **kwargs)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/http/request/form.py",
    "content": "\"\"\"\nThis module implements the FormRequest class which is a more convenient class\n(than Request) to generate Requests based on form data.\n\nSee documentation in docs/topics/request-response.rst\n\"\"\"\n\nimport six\nfrom six.moves.urllib.parse import urljoin, urlencode\n\nimport lxml.html\nfrom parsel.selector import create_root_node\nfrom w3lib.html import strip_html5_whitespace\n\nfrom scrapy.http.request import Request\nfrom scrapy.utils.python import to_bytes, is_listlike\nfrom scrapy.utils.response import get_base_url\n\n\nclass FormRequest(Request):\n    valid_form_methods = ['GET', 'POST']\n\n    def __init__(self, *args, **kwargs):\n        formdata = kwargs.pop('formdata', None)\n        if formdata and kwargs.get('method') is None:\n            kwargs['method'] = 'POST'\n\n        super(FormRequest, self).__init__(*args, **kwargs)\n\n        if formdata:\n            items = formdata.items() if isinstance(formdata, dict) else formdata\n            querystr = _urlencode(items, self.encoding)\n            if self.method == 'POST':\n                self.headers.setdefault(b'Content-Type', b'application/x-www-form-urlencoded')\n                self._set_body(querystr)\n            else:\n                self._set_url(self.url + ('&' if '?' in self.url else '?') + querystr)\n\n    @classmethod\n    def from_response(cls, response, formname=None, formid=None, formnumber=0, formdata=None,\n                      clickdata=None, dont_click=False, formxpath=None, formcss=None, **kwargs):\n\n        kwargs.setdefault('encoding', response.encoding)\n\n        if formcss is not None:\n            from parsel.csstranslator import HTMLTranslator\n            formxpath = HTMLTranslator().css_to_xpath(formcss)\n\n        form = _get_form(response, formname, formid, formnumber, formxpath)\n        formdata = _get_inputs(form, formdata, dont_click, clickdata, response)\n        url = _get_form_url(form, kwargs.pop('url', None))\n\n        method = kwargs.pop('method', form.method)\n        if method is not None:\n            method = method.upper()\n            if method not in cls.valid_form_methods:\n                method = 'GET'\n\n        return cls(url=url, method=method, formdata=formdata, **kwargs)\n\n\ndef _get_form_url(form, url):\n    if url is None:\n        action = form.get('action')\n        if action is None:\n            return form.base_url\n        return urljoin(form.base_url, strip_html5_whitespace(action))\n    return urljoin(form.base_url, url)\n\n\ndef _urlencode(seq, enc):\n    values = [(to_bytes(k, enc), to_bytes(v, enc))\n              for k, vs in seq\n              for v in (vs if is_listlike(vs) else [vs])]\n    return urlencode(values, doseq=1)\n\n\ndef _get_form(response, formname, formid, formnumber, formxpath):\n    \"\"\"Find the form element \"\"\"\n    root = create_root_node(response.text, lxml.html.HTMLParser,\n                            base_url=get_base_url(response))\n    forms = root.xpath('//form')\n    if not forms:\n        raise ValueError(\"No <form> element found in %s\" % response)\n\n    if formname is not None:\n        f = root.xpath('//form[@name=\"%s\"]' % formname)\n        if f:\n            return f[0]\n\n    if formid is not None:\n        f = root.xpath('//form[@id=\"%s\"]' % formid)\n        if f:\n            return f[0]\n\n    # Get form element from xpath, if not found, go up\n    if formxpath is not None:\n        nodes = root.xpath(formxpath)\n        if nodes:\n            el = nodes[0]\n            while True:\n                if el.tag == 'form':\n                    return el\n                el = el.getparent()\n                if el is None:\n                    break\n        encoded = formxpath if six.PY3 else formxpath.encode('unicode_escape')\n        raise ValueError('No <form> element found with %s' % encoded)\n\n    # If we get here, it means that either formname was None\n    # or invalid\n    if formnumber is not None:\n        try:\n            form = forms[formnumber]\n        except IndexError:\n            raise IndexError(\"Form number %d not found in %s\" %\n                             (formnumber, response))\n        else:\n            return form\n\n\ndef _get_inputs(form, formdata, dont_click, clickdata, response):\n    try:\n        formdata_keys = dict(formdata or ()).keys()\n    except (ValueError, TypeError):\n        raise ValueError('formdata should be a dict or iterable of tuples')\n\n    if not formdata:\n        formdata = ()\n    inputs = form.xpath('descendant::textarea'\n                        '|descendant::select'\n                        '|descendant::input[not(@type) or @type['\n                        ' not(re:test(., \"^(?:submit|image|reset)$\", \"i\"))'\n                        ' and (../@checked or'\n                        '  not(re:test(., \"^(?:checkbox|radio)$\", \"i\")))]]',\n                        namespaces={\n                            \"re\": \"http://exslt.org/regular-expressions\"})\n    values = [(k, u'' if v is None else v)\n              for k, v in (_value(e) for e in inputs)\n              if k and k not in formdata_keys]\n\n    if not dont_click:\n        clickable = _get_clickable(clickdata, form)\n        if clickable and clickable[0] not in formdata and not clickable[0] is None:\n            values.append(clickable)\n\n    if isinstance(formdata, dict):\n        formdata = formdata.items()\n\n    values.extend((k, v) for k, v in formdata if v is not None)\n    return values\n\n\ndef _value(ele):\n    n = ele.name\n    v = ele.value\n    if ele.tag == 'select':\n        return _select_value(ele, n, v)\n    return n, v\n\n\ndef _select_value(ele, n, v):\n    multiple = ele.multiple\n    if v is None and not multiple:\n        # Match browser behaviour on simple select tag without options selected\n        # And for select tags wihout options\n        o = ele.value_options\n        return (n, o[0]) if o else (None, None)\n    elif v is not None and multiple:\n        # This is a workround to bug in lxml fixed 2.3.1\n        # fix https://github.com/lxml/lxml/commit/57f49eed82068a20da3db8f1b18ae00c1bab8b12#L1L1139\n        selected_options = ele.xpath('.//option[@selected]')\n        v = [(o.get('value') or o.text or u'').strip() for o in selected_options]\n    return n, v\n\n\ndef _get_clickable(clickdata, form):\n    \"\"\"\n    Returns the clickable element specified in clickdata,\n    if the latter is given. If not, it returns the first\n    clickable element found\n    \"\"\"\n    clickables = [\n        el for el in form.xpath(\n            'descendant::input[re:test(@type, \"^(submit|image)$\", \"i\")]'\n            '|descendant::button[not(@type) or re:test(@type, \"^submit$\", \"i\")]',\n            namespaces={\"re\": \"http://exslt.org/regular-expressions\"})\n        ]\n    if not clickables:\n        return\n\n    # If we don't have clickdata, we just use the first clickable element\n    if clickdata is None:\n        el = clickables[0]\n        return (el.get('name'), el.get('value') or '')\n\n    # If clickdata is given, we compare it to the clickable elements to find a\n    # match. We first look to see if the number is specified in clickdata,\n    # because that uniquely identifies the element\n    nr = clickdata.get('nr', None)\n    if nr is not None:\n        try:\n            el = list(form.inputs)[nr]\n        except IndexError:\n            pass\n        else:\n            return (el.get('name'), el.get('value') or '')\n\n    # We didn't find it, so now we build an XPath expression out of the other\n    # arguments, because they can be used as such\n    xpath = u'.//*' + \\\n            u''.join(u'[@%s=\"%s\"]' % c for c in six.iteritems(clickdata))\n    el = form.xpath(xpath)\n    if len(el) == 1:\n        return (el[0].get('name'), el[0].get('value') or '')\n    elif len(el) > 1:\n        raise ValueError(\"Multiple elements found (%r) matching the criteria \"\n                         \"in clickdata: %r\" % (el, clickdata))\n    else:\n        raise ValueError('No clickable element matching clickdata: %r' % (clickdata,))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/http/request/json_request.py",
    "content": "\"\"\"\nThis module implements the JSONRequest class which is a more convenient class\n(than Request) to generate JSON Requests.\n\nSee documentation in docs/topics/request-response.rst\n\"\"\"\n\nimport copy\nimport json\nimport warnings\n\nfrom scrapy.http.request import Request\n\n\nclass JSONRequest(Request):\n    def __init__(self, *args, **kwargs):\n        dumps_kwargs = copy.deepcopy(kwargs.pop('dumps_kwargs', {}))\n        dumps_kwargs.setdefault('sort_keys', True)\n        self._dumps_kwargs = dumps_kwargs\n\n        body_passed = kwargs.get('body', None) is not None\n        data = kwargs.pop('data', None)\n        data_passed = data is not None\n\n        if body_passed and data_passed:\n            warnings.warn('Both body and data passed. data will be ignored')\n\n        elif not body_passed and data_passed:\n            kwargs['body'] = self._dumps(data)\n\n            if 'method' not in kwargs:\n                kwargs['method'] = 'POST'\n\n        super(JSONRequest, self).__init__(*args, **kwargs)\n        self.headers.setdefault('Content-Type', 'application/json')\n        self.headers.setdefault('Accept', 'application/json, text/javascript, */*; q=0.01')\n\n    def replace(self, *args, **kwargs):\n        body_passed = kwargs.get('body', None) is not None\n        data = kwargs.pop('data', None)\n        data_passed = data is not None\n\n        if body_passed and data_passed:\n            warnings.warn('Both body and data passed. data will be ignored')\n\n        elif not body_passed and data_passed:\n            kwargs['body'] = self._dumps(data)\n\n        return super(JSONRequest, self).replace(*args, **kwargs)\n\n    def _dumps(self, data):\n        \"\"\"Convert to JSON \"\"\"\n        return json.dumps(data, **self._dumps_kwargs)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/http/request/rpc.py",
    "content": "\"\"\"\nThis module implements the XmlRpcRequest class which is a more convenient class\n(that Request) to generate xml-rpc requests.\n\nSee documentation in docs/topics/request-response.rst\n\"\"\"\nfrom six.moves import xmlrpc_client as xmlrpclib\n\nfrom scrapy.http.request import Request\nfrom scrapy.utils.python import get_func_args\n\n\nDUMPS_ARGS = get_func_args(xmlrpclib.dumps)\n\n\nclass XmlRpcRequest(Request):\n\n    def __init__(self, *args, **kwargs):\n        encoding = kwargs.get('encoding', None)\n        if 'body' not in kwargs and 'params' in kwargs:\n            kw = dict((k, kwargs.pop(k)) for k in DUMPS_ARGS if k in kwargs)\n            kwargs['body'] = xmlrpclib.dumps(**kw)\n\n        # spec defines that requests must use POST method\n        kwargs.setdefault('method', 'POST')\n\n        # xmlrpc query multiples times over the same url\n        kwargs.setdefault('dont_filter', True)\n\n        # restore encoding\n        if encoding is not None:\n            kwargs['encoding'] = encoding\n\n        super(XmlRpcRequest, self).__init__(*args, **kwargs)\n        self.headers.setdefault('Content-Type', 'text/xml')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/http/response/__init__.py",
    "content": "\"\"\"\nThis module implements the Response class which is used to represent HTTP\nresponses in Scrapy.\n\nSee documentation in docs/topics/request-response.rst\n\"\"\"\nfrom six.moves.urllib.parse import urljoin\n\nfrom scrapy.http.request import Request\nfrom scrapy.http.headers import Headers\nfrom scrapy.link import Link\nfrom scrapy.utils.trackref import object_ref\nfrom scrapy.http.common import obsolete_setter\nfrom scrapy.exceptions import NotSupported\n\n\nclass Response(object_ref):\n\n    def __init__(self, url, status=200, headers=None, body=b'', flags=None, request=None):\n        self.headers = Headers(headers or {})\n        self.status = int(status)\n        self._set_body(body)\n        self._set_url(url)\n        self.request = request\n        self.flags = [] if flags is None else list(flags)\n\n    @property\n    def meta(self):\n        try:\n            return self.request.meta\n        except AttributeError:\n            raise AttributeError(\n                \"Response.meta not available, this response \"\n                \"is not tied to any request\"\n            )\n\n    def _get_url(self):\n        return self._url\n\n    def _set_url(self, url):\n        if isinstance(url, str):\n            self._url = url\n        else:\n            raise TypeError('%s url must be str, got %s:' % (type(self).__name__,\n                type(url).__name__))\n\n    url = property(_get_url, obsolete_setter(_set_url, 'url'))\n\n    def _get_body(self):\n        return self._body\n\n    def _set_body(self, body):\n        if body is None:\n            self._body = b''\n        elif not isinstance(body, bytes):\n            raise TypeError(\n                \"Response body must be bytes. \"\n                \"If you want to pass unicode body use TextResponse \"\n                \"or HtmlResponse.\")\n        else:\n            self._body = body\n\n    body = property(_get_body, obsolete_setter(_set_body, 'body'))\n\n    def __str__(self):\n        return \"<%d %s>\" % (self.status, self.url)\n\n    __repr__ = __str__\n\n    def copy(self):\n        \"\"\"Return a copy of this Response\"\"\"\n        return self.replace()\n\n    def replace(self, *args, **kwargs):\n        \"\"\"Create a new Response with the same attributes except for those\n        given new values.\n        \"\"\"\n        for x in ['url', 'status', 'headers', 'body', 'request', 'flags']:\n            kwargs.setdefault(x, getattr(self, x))\n        cls = kwargs.pop('cls', self.__class__)\n        return cls(*args, **kwargs)\n\n    def urljoin(self, url):\n        \"\"\"Join this Response's url with a possible relative url to form an\n        absolute interpretation of the latter.\"\"\"\n        return urljoin(self.url, url)\n\n    @property\n    def text(self):\n        \"\"\"For subclasses of TextResponse, this will return the body\n        as text (unicode object in Python 2 and str in Python 3)\n        \"\"\"\n        raise AttributeError(\"Response content isn't text\")\n\n    def css(self, *a, **kw):\n        \"\"\"Shortcut method implemented only by responses whose content\n        is text (subclasses of TextResponse).\n        \"\"\"\n        raise NotSupported(\"Response content isn't text\")\n\n    def xpath(self, *a, **kw):\n        \"\"\"Shortcut method implemented only by responses whose content\n        is text (subclasses of TextResponse).\n        \"\"\"\n        raise NotSupported(\"Response content isn't text\")\n\n    def follow(self, url, callback=None, method='GET', headers=None, body=None,\n               cookies=None, meta=None, encoding='utf-8', priority=0,\n               dont_filter=False, errback=None, cb_kwargs=None):\n        # type: (...) -> Request\n        \"\"\"\n        Return a :class:`~.Request` instance to follow a link ``url``.\n        It accepts the same arguments as ``Request.__init__`` method,\n        but ``url`` can be a relative URL or a ``scrapy.link.Link`` object,\n        not only an absolute URL.\n        \n        :class:`~.TextResponse` provides a :meth:`~.TextResponse.follow` \n        method which supports selectors in addition to absolute/relative URLs\n        and Link objects.\n        \"\"\"\n        if isinstance(url, Link):\n            url = url.url\n        elif url is None:\n            raise ValueError(\"url can't be None\")\n        url = self.urljoin(url)\n        return Request(url, callback,\n                       method=method,\n                       headers=headers,\n                       body=body,\n                       cookies=cookies,\n                       meta=meta,\n                       encoding=encoding,\n                       priority=priority,\n                       dont_filter=dont_filter,\n                       errback=errback,\n                       cb_kwargs=cb_kwargs)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/http/response/html.py",
    "content": "\"\"\"\nThis module implements the HtmlResponse class which adds encoding\ndiscovering through HTML encoding declarations to the TextResponse class.\n\nSee documentation in docs/topics/request-response.rst\n\"\"\"\n\nfrom scrapy.http.response.text import TextResponse\n\nclass HtmlResponse(TextResponse):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/http/response/text.py",
    "content": "\"\"\"\nThis module implements the TextResponse class which adds encoding handling and\ndiscovering (through HTTP headers) to base Response class.\n\nSee documentation in docs/topics/request-response.rst\n\"\"\"\n\nimport six\nfrom six.moves.urllib.parse import urljoin\n\nimport parsel\nfrom w3lib.encoding import html_to_unicode, resolve_encoding, \\\n    html_body_declared_encoding, http_content_type_encoding\nfrom w3lib.html import strip_html5_whitespace\n\nfrom scrapy.http.request import Request\nfrom scrapy.http.response import Response\nfrom scrapy.utils.response import get_base_url\nfrom scrapy.utils.python import memoizemethod_noargs, to_native_str\n\n\nclass TextResponse(Response):\n\n    _DEFAULT_ENCODING = 'ascii'\n\n    def __init__(self, *args, **kwargs):\n        self._encoding = kwargs.pop('encoding', None)\n        self._cached_benc = None\n        self._cached_ubody = None\n        self._cached_selector = None\n        super(TextResponse, self).__init__(*args, **kwargs)\n\n    def _set_url(self, url):\n        if isinstance(url, six.text_type):\n            if six.PY2 and self.encoding is None:\n                raise TypeError(\"Cannot convert unicode url - %s \"\n                                \"has no encoding\" % type(self).__name__)\n            self._url = to_native_str(url, self.encoding)\n        else:\n            super(TextResponse, self)._set_url(url)\n\n    def _set_body(self, body):\n        self._body = b''  # used by encoding detection\n        if isinstance(body, six.text_type):\n            if self._encoding is None:\n                raise TypeError('Cannot convert unicode body - %s has no encoding' %\n                    type(self).__name__)\n            self._body = body.encode(self._encoding)\n        else:\n            super(TextResponse, self)._set_body(body)\n\n    def replace(self, *args, **kwargs):\n        kwargs.setdefault('encoding', self.encoding)\n        return Response.replace(self, *args, **kwargs)\n\n    @property\n    def encoding(self):\n        return self._declared_encoding() or self._body_inferred_encoding()\n\n    def _declared_encoding(self):\n        return self._encoding or self._headers_encoding() \\\n            or self._body_declared_encoding()\n\n    def body_as_unicode(self):\n        \"\"\"Return body as unicode\"\"\"\n        return self.text\n\n    @property\n    def text(self):\n        \"\"\" Body as unicode \"\"\"\n        # access self.encoding before _cached_ubody to make sure\n        # _body_inferred_encoding is called\n        benc = self.encoding\n        if self._cached_ubody is None:\n            charset = 'charset=%s' % benc\n            self._cached_ubody = html_to_unicode(charset, self.body)[1]\n        return self._cached_ubody\n\n    def urljoin(self, url):\n        \"\"\"Join this Response's url with a possible relative url to form an\n        absolute interpretation of the latter.\"\"\"\n        return urljoin(get_base_url(self), url)\n\n    @memoizemethod_noargs\n    def _headers_encoding(self):\n        content_type = self.headers.get(b'Content-Type', b'')\n        return http_content_type_encoding(to_native_str(content_type))\n\n    def _body_inferred_encoding(self):\n        if self._cached_benc is None:\n            content_type = to_native_str(self.headers.get(b'Content-Type', b''))\n            benc, ubody = html_to_unicode(content_type, self.body,\n                    auto_detect_fun=self._auto_detect_fun,\n                    default_encoding=self._DEFAULT_ENCODING)\n            self._cached_benc = benc\n            self._cached_ubody = ubody\n        return self._cached_benc\n\n    def _auto_detect_fun(self, text):\n        for enc in (self._DEFAULT_ENCODING, 'utf-8', 'cp1252'):\n            try:\n                text.decode(enc)\n            except UnicodeError:\n                continue\n            return resolve_encoding(enc)\n\n    @memoizemethod_noargs\n    def _body_declared_encoding(self):\n        return html_body_declared_encoding(self.body)\n\n    @property\n    def selector(self):\n        from scrapy.selector import Selector\n        if self._cached_selector is None:\n            self._cached_selector = Selector(self)\n        return self._cached_selector\n\n    def xpath(self, query, **kwargs):\n        return self.selector.xpath(query, **kwargs)\n\n    def css(self, query):\n        return self.selector.css(query)\n\n    def follow(self, url, callback=None, method='GET', headers=None, body=None,\n               cookies=None, meta=None, encoding=None, priority=0,\n               dont_filter=False, errback=None, cb_kwargs=None):\n        # type: (...) -> Request\n        \"\"\"\n        Return a :class:`~.Request` instance to follow a link ``url``.\n        It accepts the same arguments as ``Request.__init__`` method,\n        but ``url`` can be not only an absolute URL, but also\n        \n        * a relative URL;\n        * a scrapy.link.Link object (e.g. a link extractor result);\n        * an attribute Selector (not SelectorList) - e.g.\n          ``response.css('a::attr(href)')[0]`` or\n          ``response.xpath('//img/@src')[0]``.\n        * a Selector for ``<a>`` or ``<link>`` element, e.g.\n          ``response.css('a.my_link')[0]``.\n          \n        See :ref:`response-follow-example` for usage examples.\n        \"\"\"\n        if isinstance(url, parsel.Selector):\n            url = _url_from_selector(url)\n        elif isinstance(url, parsel.SelectorList):\n            raise ValueError(\"SelectorList is not supported\")\n        encoding = self.encoding if encoding is None else encoding\n        return super(TextResponse, self).follow(url, callback,\n            method=method,\n            headers=headers,\n            body=body,\n            cookies=cookies,\n            meta=meta,\n            encoding=encoding,\n            priority=priority,\n            dont_filter=dont_filter,\n            errback=errback,\n            cb_kwargs=cb_kwargs,\n        )\n\n\ndef _url_from_selector(sel):\n    # type: (parsel.Selector) -> str\n    if isinstance(sel.root, six.string_types):\n        # e.g. ::attr(href) result\n        return strip_html5_whitespace(sel.root)\n    if not hasattr(sel.root, 'tag'):\n        raise ValueError(\"Unsupported selector: %s\" % sel)\n    if sel.root.tag not in ('a', 'link'):\n        raise ValueError(\"Only <a> and <link> elements are supported; got <%s>\" %\n                         sel.root.tag)\n    href = sel.root.get('href')\n    if href is None:\n        raise ValueError(\"<%s> element has no href attribute: %s\" %\n                         (sel.root.tag, sel))\n    return strip_html5_whitespace(href)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/http/response/xml.py",
    "content": "\"\"\"\nThis module implements the XmlResponse class which adds encoding\ndiscovering through XML encoding declarations to the TextResponse class.\n\nSee documentation in docs/topics/request-response.rst\n\"\"\"\n\nfrom scrapy.http.response.text import TextResponse\n\nclass XmlResponse(TextResponse):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/interfaces.py",
    "content": "from zope.interface import Interface\n\nclass ISpiderLoader(Interface):\n\n    def from_settings(settings):\n        \"\"\"Return an instance of the class for the given settings\"\"\"\n\n    def load(spider_name):\n        \"\"\"Return the Spider class for the given spider name. If the spider\n        name is not found, it must raise a KeyError.\"\"\"\n\n    def list():\n        \"\"\"Return a list with the names of all spiders available in the\n        project\"\"\"\n\n    def find_by_request(request):\n        \"\"\"Return the list of spiders names that can handle the given request\"\"\"\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/item.py",
    "content": "\"\"\"\nScrapy Item\n\nSee documentation in docs/topics/item.rst\n\"\"\"\n\nfrom abc import ABCMeta\nfrom pprint import pformat\nfrom copy import deepcopy\nimport collections\n\nimport six\n\nfrom scrapy.utils.trackref import object_ref\n\n\nif six.PY2:\n    MutableMapping = collections.MutableMapping\nelse:\n    MutableMapping = collections.abc.MutableMapping\n\n\nclass BaseItem(object_ref):\n    \"\"\"Base class for all scraped items.\"\"\"\n    pass\n\n\nclass Field(dict):\n    \"\"\"Container of field metadata\"\"\"\n\n\nclass ItemMeta(ABCMeta):\n\n    def __new__(mcs, class_name, bases, attrs):\n        classcell = attrs.pop('__classcell__', None)\n        new_bases = tuple(base._class for base in bases if hasattr(base, '_class'))\n        _class = super(ItemMeta, mcs).__new__(mcs, 'x_' + class_name, new_bases, attrs)\n\n        fields = getattr(_class, 'fields', {})\n        new_attrs = {}\n        for n in dir(_class):\n            v = getattr(_class, n)\n            if isinstance(v, Field):\n                fields[n] = v\n            elif n in attrs:\n                new_attrs[n] = attrs[n]\n\n        new_attrs['fields'] = fields\n        new_attrs['_class'] = _class\n        if classcell is not None:\n            new_attrs['__classcell__'] = classcell\n        return super(ItemMeta, mcs).__new__(mcs, class_name, bases, new_attrs)\n\n\nclass DictItem(MutableMapping, BaseItem):\n\n    fields = {}\n\n    def __init__(self, *args, **kwargs):\n        self._values = {}\n        if args or kwargs:  # avoid creating dict for most common case\n            for k, v in six.iteritems(dict(*args, **kwargs)):\n                self[k] = v\n\n    def __getitem__(self, key):\n        return self._values[key]\n\n    def __setitem__(self, key, value):\n        if key in self.fields:\n            self._values[key] = value\n        else:\n            raise KeyError(\"%s does not support field: %s\" %\n                (self.__class__.__name__, key))\n\n    def __delitem__(self, key):\n        del self._values[key]\n\n    def __getattr__(self, name):\n        if name in self.fields:\n            raise AttributeError(\"Use item[%r] to get field value\" % name)\n        raise AttributeError(name)\n\n    def __setattr__(self, name, value):\n        if not name.startswith('_'):\n            raise AttributeError(\"Use item[%r] = %r to set field value\" %\n                (name, value))\n        super(DictItem, self).__setattr__(name, value)\n\n    def __len__(self):\n        return len(self._values)\n\n    def __iter__(self):\n        return iter(self._values)\n\n    __hash__ = BaseItem.__hash__\n\n    def keys(self):\n        return self._values.keys()\n\n    def __repr__(self):\n        return pformat(dict(self))\n\n    def copy(self):\n        return self.__class__(self)\n\n    def deepcopy(self):\n        \"\"\"Return a `deep copy`_ of this item.\n\n        .. _deep copy: https://docs.python.org/library/copy.html#copy.deepcopy\n        \"\"\"\n        return deepcopy(self)\n\n\n@six.add_metaclass(ItemMeta)\nclass Item(DictItem):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/link.py",
    "content": "\"\"\"\nThis module defines the Link object used in Link extractors.\n\nFor actual link extractors implementation see scrapy.linkextractors, or\nits documentation in: docs/topics/link-extractors.rst\n\"\"\"\nimport warnings\nimport six\n\nfrom scrapy.utils.python import to_bytes\n\n\nclass Link(object):\n    \"\"\"Link objects represent an extracted link by the LinkExtractor.\"\"\"\n\n    __slots__ = ['url', 'text', 'fragment', 'nofollow']\n\n    def __init__(self, url, text='', fragment='', nofollow=False):\n        if not isinstance(url, str):\n            if six.PY2:\n                warnings.warn(\"Link urls must be str objects. \"\n                              \"Assuming utf-8 encoding (which could be wrong)\")\n                url = to_bytes(url, encoding='utf8')\n            else:\n                got = url.__class__.__name__\n                raise TypeError(\"Link urls must be str objects, got %s\" % got)\n        self.url = url\n        self.text = text\n        self.fragment = fragment\n        self.nofollow = nofollow\n\n    def __eq__(self, other):\n        return self.url == other.url and self.text == other.text and \\\n            self.fragment == other.fragment and self.nofollow == other.nofollow\n\n    def __hash__(self):\n        return hash(self.url) ^ hash(self.text) ^ hash(self.fragment) ^ hash(self.nofollow)\n\n    def __repr__(self):\n        return 'Link(url=%r, text=%r, fragment=%r, nofollow=%r)' % \\\n            (self.url, self.text, self.fragment, self.nofollow)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/linkextractors/__init__.py",
    "content": "\"\"\"\nscrapy.linkextractors\n\nThis package contains a collection of Link Extractors.\n\nFor more info see docs/topics/link-extractors.rst\n\"\"\"\nimport re\n\nfrom six.moves.urllib.parse import urlparse\nfrom parsel.csstranslator import HTMLTranslator\nfrom w3lib.url import canonicalize_url\n\nfrom scrapy.utils.misc import arg_to_iter\nfrom scrapy.utils.url import (\n    url_is_from_any_domain, url_has_any_extension,\n)\n\n\n# common file extensions that are not followed if they occur in links\nIGNORED_EXTENSIONS = [\n    # images\n    'mng', 'pct', 'bmp', 'gif', 'jpg', 'jpeg', 'png', 'pst', 'psp', 'tif',\n    'tiff', 'ai', 'drw', 'dxf', 'eps', 'ps', 'svg',\n\n    # audio\n    'mp3', 'wma', 'ogg', 'wav', 'ra', 'aac', 'mid', 'au', 'aiff',\n\n    # video\n    '3gp', 'asf', 'asx', 'avi', 'mov', 'mp4', 'mpg', 'qt', 'rm', 'swf', 'wmv',\n    'm4a', 'm4v', 'flv',\n\n    # office suites\n    'xls', 'xlsx', 'ppt', 'pptx', 'pps', 'doc', 'docx', 'odt', 'ods', 'odg',\n    'odp',\n\n    # other\n    'css', 'pdf', 'exe', 'bin', 'rss', 'zip', 'rar',\n]\n\n\n_re_type = type(re.compile(\"\", 0))\n_matches = lambda url, regexs: any(r.search(url) for r in regexs)\n_is_valid_url = lambda url: url.split('://', 1)[0] in {'http', 'https', \\\n                                                       'file', 'ftp'}\n\n\nclass FilteringLinkExtractor(object):\n\n    _csstranslator = HTMLTranslator()\n\n    def __init__(self, link_extractor, allow, deny, allow_domains, deny_domains,\n                 restrict_xpaths, canonicalize, deny_extensions, restrict_css, restrict_text):\n\n        self.link_extractor = link_extractor\n\n        self.allow_res = [x if isinstance(x, _re_type) else re.compile(x)\n                          for x in arg_to_iter(allow)]\n        self.deny_res = [x if isinstance(x, _re_type) else re.compile(x)\n                         for x in arg_to_iter(deny)]\n\n        self.allow_domains = set(arg_to_iter(allow_domains))\n        self.deny_domains = set(arg_to_iter(deny_domains))\n\n        self.restrict_xpaths = tuple(arg_to_iter(restrict_xpaths))\n        self.restrict_xpaths += tuple(map(self._csstranslator.css_to_xpath,\n                                          arg_to_iter(restrict_css)))\n\n        self.canonicalize = canonicalize\n        if deny_extensions is None:\n            deny_extensions = IGNORED_EXTENSIONS\n        self.deny_extensions = {'.' + e for e in arg_to_iter(deny_extensions)}\n        self.restrict_text = [x if isinstance(x, _re_type) else re.compile(x)\n                              for x in arg_to_iter(restrict_text)]\n\n    def _link_allowed(self, link):\n        if not _is_valid_url(link.url):\n            return False\n        if self.allow_res and not _matches(link.url, self.allow_res):\n            return False\n        if self.deny_res and _matches(link.url, self.deny_res):\n            return False\n        parsed_url = urlparse(link.url)\n        if self.allow_domains and not url_is_from_any_domain(parsed_url, self.allow_domains):\n            return False\n        if self.deny_domains and url_is_from_any_domain(parsed_url, self.deny_domains):\n            return False\n        if self.deny_extensions and url_has_any_extension(parsed_url, self.deny_extensions):\n            return False\n        if self.restrict_text and not _matches(link.text, self.restrict_text):\n            return False\n        return True\n\n    def matches(self, url):\n\n        if self.allow_domains and not url_is_from_any_domain(url, self.allow_domains):\n            return False\n        if self.deny_domains and url_is_from_any_domain(url, self.deny_domains):\n            return False\n\n        allowed = (regex.search(url) for regex in self.allow_res) if self.allow_res else [True]\n        denied = (regex.search(url) for regex in self.deny_res) if self.deny_res else []\n        return any(allowed) and not any(denied)\n\n    def _process_links(self, links):\n        links = [x for x in links if self._link_allowed(x)]\n        if self.canonicalize:\n            for link in links:\n                link.url = canonicalize_url(link.url)\n        links = self.link_extractor._process_links(links)\n        return links\n\n    def _extract_links(self, *args, **kwargs):\n        return self.link_extractor._extract_links(*args, **kwargs)\n\n\n# Top-level imports\nfrom .lxmlhtml import LxmlLinkExtractor as LinkExtractor\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/linkextractors/htmlparser.py",
    "content": "\"\"\"\nHTMLParser-based link extractor\n\"\"\"\nimport warnings\nimport six\nfrom six.moves.html_parser import HTMLParser\nfrom six.moves.urllib.parse import urljoin\n\nfrom w3lib.url import safe_url_string\nfrom w3lib.html import strip_html5_whitespace\n\nfrom scrapy.link import Link\nfrom scrapy.utils.python import unique as unique_list\nfrom scrapy.exceptions import ScrapyDeprecationWarning\n\n\nclass HtmlParserLinkExtractor(HTMLParser):\n\n    def __init__(self, tag=\"a\", attr=\"href\", process=None, unique=False,\n                 strip=True):\n        HTMLParser.__init__(self)\n\n        warnings.warn(\n            \"HtmlParserLinkExtractor is deprecated and will be removed in \"\n            \"future releases. Please use scrapy.linkextractors.LinkExtractor\",\n            ScrapyDeprecationWarning, stacklevel=2,\n        )\n\n        self.scan_tag = tag if callable(tag) else lambda t: t == tag\n        self.scan_attr = attr if callable(attr) else lambda a: a == attr\n        self.process_attr = process if callable(process) else lambda v: v\n        self.unique = unique\n        self.strip = strip\n\n    def _extract_links(self, response_text, response_url, response_encoding):\n        self.reset()\n        self.feed(response_text)\n        self.close()\n\n        links = unique_list(self.links, key=lambda link: link.url) if self.unique else self.links\n\n        ret = []\n        base_url = urljoin(response_url, self.base_url) if self.base_url else response_url\n        for link in links:\n            if isinstance(link.url, six.text_type):\n                link.url = link.url.encode(response_encoding)\n            try:\n                link.url = urljoin(base_url, link.url)\n            except ValueError:\n                continue\n            link.url = safe_url_string(link.url, response_encoding)\n            link.text = link.text.decode(response_encoding)\n            ret.append(link)\n\n        return ret\n\n    def extract_links(self, response):\n        # wrapper needed to allow to work directly with text\n        return self._extract_links(response.body, response.url, response.encoding)\n\n    def reset(self):\n        HTMLParser.reset(self)\n\n        self.base_url = None\n        self.current_link = None\n        self.links = []\n\n    def handle_starttag(self, tag, attrs):\n        if tag == 'base':\n            self.base_url = dict(attrs).get('href')\n        if self.scan_tag(tag):\n            for attr, value in attrs:\n                if self.scan_attr(attr):\n                    if self.strip:\n                        value = strip_html5_whitespace(value)\n                    url = self.process_attr(value)\n                    link = Link(url=url)\n                    self.links.append(link)\n                    self.current_link = link\n\n    def handle_endtag(self, tag):\n        if self.scan_tag(tag):\n            self.current_link = None\n\n    def handle_data(self, data):\n        if self.current_link:\n            self.current_link.text = self.current_link.text + data\n\n    def matches(self, url):\n        \"\"\"This extractor matches with any url, since\n        it doesn't contain any patterns\"\"\"\n        return True\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/linkextractors/lxmlhtml.py",
    "content": "\"\"\"\nLink extractor based on lxml.html\n\"\"\"\nimport six\nfrom six.moves.urllib.parse import urljoin\n\nimport lxml.etree as etree\nfrom w3lib.html import strip_html5_whitespace\nfrom w3lib.url import canonicalize_url\n\nfrom scrapy.link import Link\nfrom scrapy.utils.misc import arg_to_iter, rel_has_nofollow\nfrom scrapy.utils.python import unique as unique_list, to_native_str\nfrom scrapy.utils.response import get_base_url\nfrom scrapy.linkextractors import FilteringLinkExtractor\n\n\n# from lxml/src/lxml/html/__init__.py\nXHTML_NAMESPACE = \"http://www.w3.org/1999/xhtml\"\n\n_collect_string_content = etree.XPath(\"string()\")\n\n\ndef _nons(tag):\n    if isinstance(tag, six.string_types):\n        if tag[0] == '{' and tag[1:len(XHTML_NAMESPACE)+1] == XHTML_NAMESPACE:\n            return tag.split('}')[-1]\n    return tag\n\n\nclass LxmlParserLinkExtractor(object):\n    def __init__(self, tag=\"a\", attr=\"href\", process=None, unique=False,\n                 strip=True, canonicalized=False):\n        self.scan_tag = tag if callable(tag) else lambda t: t == tag\n        self.scan_attr = attr if callable(attr) else lambda a: a == attr\n        self.process_attr = process if callable(process) else lambda v: v\n        self.unique = unique\n        self.strip = strip\n        if canonicalized:\n            self.link_key = lambda link: link.url\n        else:\n            self.link_key = lambda link: canonicalize_url(link.url,\n                                                          keep_fragments=True)\n\n    def _iter_links(self, document):\n        for el in document.iter(etree.Element):\n            if not self.scan_tag(_nons(el.tag)):\n                continue\n            attribs = el.attrib\n            for attrib in attribs:\n                if not self.scan_attr(attrib):\n                    continue\n                yield (el, attrib, attribs[attrib])\n\n    def _extract_links(self, selector, response_url, response_encoding, base_url):\n        links = []\n        # hacky way to get the underlying lxml parsed document\n        for el, attr, attr_val in self._iter_links(selector.root):\n            # pseudo lxml.html.HtmlElement.make_links_absolute(base_url)\n            try:\n                if self.strip:\n                    attr_val = strip_html5_whitespace(attr_val)\n                attr_val = urljoin(base_url, attr_val)\n            except ValueError:\n                continue  # skipping bogus links\n            else:\n                url = self.process_attr(attr_val)\n                if url is None:\n                    continue\n            url = to_native_str(url, encoding=response_encoding)\n            # to fix relative links after process_value\n            url = urljoin(response_url, url)\n            link = Link(url, _collect_string_content(el) or u'',\n                        nofollow=rel_has_nofollow(el.get('rel')))\n            links.append(link)\n        return self._deduplicate_if_needed(links)\n\n    def extract_links(self, response):\n        base_url = get_base_url(response)\n        return self._extract_links(response.selector, response.url, response.encoding, base_url)\n\n    def _process_links(self, links):\n        \"\"\" Normalize and filter extracted links\n\n        The subclass should override it if neccessary\n        \"\"\"\n        return self._deduplicate_if_needed(links)\n\n    def _deduplicate_if_needed(self, links):\n        if self.unique:\n            return unique_list(links, key=self.link_key)\n        return links\n\n\nclass LxmlLinkExtractor(FilteringLinkExtractor):\n\n    def __init__(self, allow=(), deny=(), allow_domains=(), deny_domains=(), restrict_xpaths=(),\n                 tags=('a', 'area'), attrs=('href',), canonicalize=False,\n                 unique=True, process_value=None, deny_extensions=None, restrict_css=(),\n                 strip=True, restrict_text=None):\n        tags, attrs = set(arg_to_iter(tags)), set(arg_to_iter(attrs))\n        tag_func = lambda x: x in tags\n        attr_func = lambda x: x in attrs\n        lx = LxmlParserLinkExtractor(\n            tag=tag_func,\n            attr=attr_func,\n            unique=unique,\n            process=process_value,\n            strip=strip,\n            canonicalized=canonicalize\n        )\n\n        super(LxmlLinkExtractor, self).__init__(lx, allow=allow, deny=deny,\n                                                allow_domains=allow_domains, deny_domains=deny_domains,\n                                                restrict_xpaths=restrict_xpaths, restrict_css=restrict_css,\n                                                canonicalize=canonicalize, deny_extensions=deny_extensions,\n                                                restrict_text=restrict_text)\n\n    def extract_links(self, response):\n        base_url = get_base_url(response)\n        if self.restrict_xpaths:\n            docs = [subdoc\n                    for x in self.restrict_xpaths\n                    for subdoc in response.xpath(x)]\n        else:\n            docs = [response.selector]\n        all_links = []\n        for doc in docs:\n            links = self._extract_links(doc, response.url, response.encoding, base_url)\n            all_links.extend(self._process_links(links))\n        return unique_list(all_links)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/linkextractors/regex.py",
    "content": "import re\nfrom six.moves.urllib.parse import urljoin\n\nfrom w3lib.html import remove_tags, replace_entities, replace_escape_chars, get_base_url\n\nfrom scrapy.link import Link\nfrom .sgml import SgmlLinkExtractor\n\nlinkre = re.compile(\n        \"<a\\s.*?href=(\\\"[.#]+?\\\"|\\'[.#]+?\\'|[^\\s]+?)(>|\\s.*?>)(.*?)<[/ ]?a>\",\n        re.DOTALL | re.IGNORECASE)\n\n\ndef clean_link(link_text):\n    \"\"\"Remove leading and trailing whitespace and punctuation\"\"\"\n    return link_text.strip(\"\\t\\r\\n '\\\"\\x0c\")\n\n\nclass RegexLinkExtractor(SgmlLinkExtractor):\n    \"\"\"High performant link extractor\"\"\"\n\n    def _extract_links(self, response_text, response_url, response_encoding, base_url=None):\n        def clean_text(text):\n            return replace_escape_chars(remove_tags(text.decode(response_encoding))).strip()\n\n        def clean_url(url):\n            clean_url = ''\n            try:\n                clean_url = urljoin(base_url, replace_entities(clean_link(url.decode(response_encoding))))\n            except ValueError:\n                pass\n            return clean_url\n\n        if base_url is None:\n            base_url = get_base_url(response_text, response_url, response_encoding)\n\n        links_text = linkre.findall(response_text)\n        return [Link(clean_url(url).encode(response_encoding),\n                     clean_text(text))\n                for url, _, text in links_text]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/linkextractors/sgml.py",
    "content": "\"\"\"\nSGMLParser-based Link extractors\n\"\"\"\nimport six\nfrom six.moves.urllib.parse import urljoin\nimport warnings\nfrom sgmllib import SGMLParser\n\nfrom w3lib.url import safe_url_string, canonicalize_url\nfrom w3lib.html import strip_html5_whitespace\n\nfrom scrapy.link import Link\nfrom scrapy.linkextractors import FilteringLinkExtractor\nfrom scrapy.utils.misc import arg_to_iter, rel_has_nofollow\nfrom scrapy.utils.python import unique as unique_list, to_unicode\nfrom scrapy.utils.response import get_base_url\nfrom scrapy.exceptions import ScrapyDeprecationWarning\n\n\nclass BaseSgmlLinkExtractor(SGMLParser):\n\n    def __init__(self, tag=\"a\", attr=\"href\", unique=False, process_value=None,\n                 strip=True, canonicalized=False):\n        warnings.warn(\n            \"BaseSgmlLinkExtractor is deprecated and will be removed in future releases. \"\n            \"Please use scrapy.linkextractors.LinkExtractor\",\n            ScrapyDeprecationWarning, stacklevel=2,\n        )\n        SGMLParser.__init__(self)\n        self.scan_tag = tag if callable(tag) else lambda t: t == tag\n        self.scan_attr = attr if callable(attr) else lambda a: a == attr\n        self.process_value = (lambda v: v) if process_value is None else process_value\n        self.current_link = None\n        self.unique = unique\n        self.strip = strip\n        if canonicalized:\n            self.link_key = lambda link: link.url\n        else:\n            self.link_key = lambda link: canonicalize_url(link.url,\n                                                          keep_fragments=True)\n\n    def _extract_links(self, response_text, response_url, response_encoding, base_url=None):\n        \"\"\" Do the real extraction work \"\"\"\n        self.reset()\n        self.feed(response_text)\n        self.close()\n\n        ret = []\n        if base_url is None:\n            base_url = urljoin(response_url, self.base_url) if self.base_url else response_url\n        for link in self.links:\n            if isinstance(link.url, six.text_type):\n                link.url = link.url.encode(response_encoding)\n            try:\n                link.url = urljoin(base_url, link.url)\n            except ValueError:\n                continue\n            link.url = safe_url_string(link.url, response_encoding)\n            link.text = to_unicode(link.text, response_encoding, errors='replace').strip()\n            ret.append(link)\n\n        return ret\n\n    def _process_links(self, links):\n        \"\"\" Normalize and filter extracted links\n\n        The subclass should override it if necessary\n        \"\"\"\n        return unique_list(links, key=self.link_key) if self.unique else links\n\n    def extract_links(self, response):\n        # wrapper needed to allow to work directly with text\n        links = self._extract_links(response.body, response.url, response.encoding)\n        links = self._process_links(links)\n        return links\n\n    def reset(self):\n        SGMLParser.reset(self)\n        self.links = []\n        self.base_url = None\n        self.current_link = None\n\n    def unknown_starttag(self, tag, attrs):\n        if tag == 'base':\n            self.base_url = dict(attrs).get('href')\n        if self.scan_tag(tag):\n            for attr, value in attrs:\n                if self.scan_attr(attr):\n                    if self.strip and value is not None:\n                        value = strip_html5_whitespace(value)\n                    url = self.process_value(value)\n                    if url is not None:\n                        link = Link(url=url, nofollow=rel_has_nofollow(dict(attrs).get('rel')))\n                        self.links.append(link)\n                        self.current_link = link\n\n    def unknown_endtag(self, tag):\n        if self.scan_tag(tag):\n            self.current_link = None\n\n    def handle_data(self, data):\n        if self.current_link:\n            self.current_link.text = self.current_link.text + data\n\n    def matches(self, url):\n        \"\"\"This extractor matches with any url, since\n        it doesn't contain any patterns\"\"\"\n        return True\n\n\nclass SgmlLinkExtractor(FilteringLinkExtractor):\n\n    def __init__(self, allow=(), deny=(), allow_domains=(), deny_domains=(), restrict_xpaths=(),\n                 tags=('a', 'area'), attrs=('href',), canonicalize=False, unique=True,\n                 process_value=None, deny_extensions=None, restrict_css=(),\n                 strip=True, restrict_text=()):\n        warnings.warn(\n            \"SgmlLinkExtractor is deprecated and will be removed in future releases. \"\n            \"Please use scrapy.linkextractors.LinkExtractor\",\n            ScrapyDeprecationWarning, stacklevel=2,\n        )\n\n        tags, attrs = set(arg_to_iter(tags)), set(arg_to_iter(attrs))\n        tag_func = lambda x: x in tags\n        attr_func = lambda x: x in attrs\n\n        with warnings.catch_warnings():\n            warnings.simplefilter('ignore', ScrapyDeprecationWarning)\n            lx = BaseSgmlLinkExtractor(tag=tag_func, attr=attr_func,\n                                       unique=unique, process_value=process_value, strip=strip,\n                                       canonicalized=canonicalize)\n\n        super(SgmlLinkExtractor, self).__init__(lx, allow=allow, deny=deny,\n                                                allow_domains=allow_domains, deny_domains=deny_domains,\n                                                restrict_xpaths=restrict_xpaths, restrict_css=restrict_css,\n                                                canonicalize=canonicalize, deny_extensions=deny_extensions,\n                                                restrict_text=restrict_text)\n\n    def extract_links(self, response):\n        base_url = None\n        if self.restrict_xpaths:\n            base_url = get_base_url(response)\n            body = u''.join(f\n                            for x in self.restrict_xpaths\n                            for f in response.xpath(x).getall()\n                            ).encode(response.encoding, errors='xmlcharrefreplace')\n        else:\n            body = response.body\n\n        links = self._extract_links(body, response.url, response.encoding, base_url)\n        links = self._process_links(links)\n        return links\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/loader/__init__.py",
    "content": "\"\"\"Item Loader\n\nSee documentation in docs/topics/loaders.rst\n\n\"\"\"\nfrom collections import defaultdict\nimport six\n\nfrom scrapy.item import Item\nfrom scrapy.selector import Selector\nfrom scrapy.utils.misc import arg_to_iter, extract_regex\nfrom scrapy.utils.python import flatten\n\nfrom .common import wrap_loader_context\nfrom .processors import Identity\n\n\nclass ItemLoader(object):\n\n    default_item_class = Item\n    default_input_processor = Identity()\n    default_output_processor = Identity()\n    default_selector_class = Selector\n\n    def __init__(self, item=None, selector=None, response=None, parent=None, **context):\n        if selector is None and response is not None:\n            selector = self.default_selector_class(response)\n        self.selector = selector\n        context.update(selector=selector, response=response)\n        if item is None:\n            item = self.default_item_class()\n        self.context = context\n        self.parent = parent\n        self._local_item = context['item'] = item\n        self._local_values = defaultdict(list)\n\n    @property\n    def _values(self):\n        if self.parent is not None:\n            return self.parent._values\n        else:\n            return self._local_values\n\n    @property\n    def item(self):\n        if self.parent is not None:\n            return self.parent.item\n        else:\n            return self._local_item\n\n    def nested_xpath(self, xpath, **context):\n        selector = self.selector.xpath(xpath)\n        context.update(selector=selector)\n        subloader = self.__class__(\n            item=self.item, parent=self, **context\n        )\n        return subloader\n\n    def nested_css(self, css, **context):\n        selector = self.selector.css(css)\n        context.update(selector=selector)\n        subloader = self.__class__(\n            item=self.item, parent=self, **context\n        )\n        return subloader\n\n    def add_value(self, field_name, value, *processors, **kw):\n        value = self.get_value(value, *processors, **kw)\n        if value is None:\n            return\n        if not field_name:\n            for k, v in six.iteritems(value):\n                self._add_value(k, v)\n        else:\n            self._add_value(field_name, value)\n\n    def replace_value(self, field_name, value, *processors, **kw):\n        value = self.get_value(value, *processors, **kw)\n        if value is None:\n            return\n        if not field_name:\n            for k, v in six.iteritems(value):\n                self._replace_value(k, v)\n        else:\n            self._replace_value(field_name, value)\n\n    def _add_value(self, field_name, value):\n        value = arg_to_iter(value)\n        processed_value = self._process_input_value(field_name, value)\n        if processed_value:\n            self._values[field_name] += arg_to_iter(processed_value)\n\n    def _replace_value(self, field_name, value):\n        self._values.pop(field_name, None)\n        self._add_value(field_name, value)\n\n    def get_value(self, value, *processors, **kw):\n        regex = kw.get('re', None)\n        if regex:\n            value = arg_to_iter(value)\n            value = flatten(extract_regex(regex, x) for x in value)\n\n        for proc in processors:\n            if value is None:\n                break\n            _proc = proc\n            proc = wrap_loader_context(proc, self.context)\n            try:\n                value = proc(value)\n            except Exception as e:\n                raise ValueError(\"Error with processor %s value=%r error='%s: %s'\" %\n                                 (_proc.__class__.__name__, value,\n                                  type(e).__name__, str(e)))\n        return value\n\n    def load_item(self):\n        item = self.item\n        for field_name in tuple(self._values):\n            value = self.get_output_value(field_name)\n            if value is not None:\n                item[field_name] = value\n\n        return item\n\n    def get_output_value(self, field_name):\n        proc = self.get_output_processor(field_name)\n        proc = wrap_loader_context(proc, self.context)\n        try:\n            return proc(self._values[field_name])\n        except Exception as e:\n            raise ValueError(\"Error with output processor: field=%r value=%r error='%s: %s'\" % \\\n                (field_name, self._values[field_name], type(e).__name__, str(e)))\n\n    def get_collected_values(self, field_name):\n        return self._values[field_name]\n\n    def get_input_processor(self, field_name):\n        proc = getattr(self, '%s_in' % field_name, None)\n        if not proc:\n            proc = self._get_item_field_attr(field_name, 'input_processor', \\\n                self.default_input_processor)\n        return proc\n\n    def get_output_processor(self, field_name):\n        proc = getattr(self, '%s_out' % field_name, None)\n        if not proc:\n            proc = self._get_item_field_attr(field_name, 'output_processor', \\\n                self.default_output_processor)\n        return proc\n\n    def _process_input_value(self, field_name, value):\n        proc = self.get_input_processor(field_name)\n        _proc = proc\n        proc = wrap_loader_context(proc, self.context)\n        try:\n            return proc(value)\n        except Exception as e:\n            raise ValueError(\n                \"Error with input processor %s: field=%r value=%r \"\n                \"error='%s: %s'\" % (_proc.__class__.__name__, field_name,\n                                    value, type(e).__name__, str(e)))\n\n    def _get_item_field_attr(self, field_name, key, default=None):\n        if isinstance(self.item, Item):\n            value = self.item.fields[field_name].get(key, default)\n        else:\n            value = default\n        return value\n\n    def _check_selector_method(self):\n        if self.selector is None:\n            raise RuntimeError(\"To use XPath or CSS selectors, \"\n                \"%s must be instantiated with a selector \"\n                \"or a response\" % self.__class__.__name__)\n\n    def add_xpath(self, field_name, xpath, *processors, **kw):\n        values = self._get_xpathvalues(xpath, **kw)\n        self.add_value(field_name, values, *processors, **kw)\n\n    def replace_xpath(self, field_name, xpath, *processors, **kw):\n        values = self._get_xpathvalues(xpath, **kw)\n        self.replace_value(field_name, values, *processors, **kw)\n\n    def get_xpath(self, xpath, *processors, **kw):\n        values = self._get_xpathvalues(xpath, **kw)\n        return self.get_value(values, *processors, **kw)\n\n    def _get_xpathvalues(self, xpaths, **kw):\n        self._check_selector_method()\n        xpaths = arg_to_iter(xpaths)\n        return flatten(self.selector.xpath(xpath).getall() for xpath in xpaths)\n\n    def add_css(self, field_name, css, *processors, **kw):\n        values = self._get_cssvalues(css, **kw)\n        self.add_value(field_name, values, *processors, **kw)\n\n    def replace_css(self, field_name, css, *processors, **kw):\n        values = self._get_cssvalues(css, **kw)\n        self.replace_value(field_name, values, *processors, **kw)\n\n    def get_css(self, css, *processors, **kw):\n        values = self._get_cssvalues(css, **kw)\n        return self.get_value(values, *processors, **kw)\n\n    def _get_cssvalues(self, csss, **kw):\n        self._check_selector_method()\n        csss = arg_to_iter(csss)\n        return flatten(self.selector.css(css).getall() for css in csss)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/loader/common.py",
    "content": "\"\"\"Common functions used in Item Loaders code\"\"\"\n\nfrom functools import partial\nfrom scrapy.utils.python import get_func_args\n\ndef wrap_loader_context(function, context):\n    \"\"\"Wrap functions that receive loader_context to contain the context\n    \"pre-loaded\" and expose a interface that receives only one argument\n    \"\"\"\n    if 'loader_context' in get_func_args(function):\n        return partial(function, loader_context=context)\n    else:\n        return function\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/loader/processors.py",
    "content": "\"\"\"\nThis module provides some commonly used processors for Item Loaders.\n\nSee documentation in docs/topics/loaders.rst\n\"\"\"\ntry:\n    from collections import ChainMap\nexcept ImportError:\n    from scrapy.utils.datatypes import MergeDict as ChainMap\n\nfrom scrapy.utils.misc import arg_to_iter\nfrom scrapy.loader.common import wrap_loader_context\n\n\nclass MapCompose(object):\n\n    def __init__(self, *functions, **default_loader_context):\n        self.functions = functions\n        self.default_loader_context = default_loader_context\n\n    def __call__(self, value, loader_context=None):\n        values = arg_to_iter(value)\n        if loader_context:\n            context = ChainMap(loader_context, self.default_loader_context)\n        else:\n            context = self.default_loader_context\n        wrapped_funcs = [wrap_loader_context(f, context) for f in self.functions]\n        for func in wrapped_funcs:\n            next_values = []\n            for v in values:\n                try:\n                    next_values += arg_to_iter(func(v))\n                except Exception as e:\n                    raise ValueError(\"Error in MapCompose with \"\n                                     \"%s value=%r error='%s: %s'\" %\n                                     (str(func), value, type(e).__name__,\n                                      str(e)))\n            values = next_values\n        return values\n\n\nclass Compose(object):\n\n    def __init__(self, *functions, **default_loader_context):\n        self.functions = functions\n        self.stop_on_none = default_loader_context.get('stop_on_none', True)\n        self.default_loader_context = default_loader_context\n\n    def __call__(self, value, loader_context=None):\n        if loader_context:\n            context = ChainMap(loader_context, self.default_loader_context)\n        else:\n            context = self.default_loader_context\n        wrapped_funcs = [wrap_loader_context(f, context) for f in self.functions]\n        for func in wrapped_funcs:\n            if value is None and self.stop_on_none:\n                break\n            try:\n                value = func(value)\n            except Exception as e:\n                raise ValueError(\"Error in Compose with \"\n                                 \"%s value=%r error='%s: %s'\" %\n                                 (str(func), value, type(e).__name__, str(e)))\n        return value\n\n\nclass TakeFirst(object):\n\n    def __call__(self, values):\n        for value in values:\n            if value is not None and value != '':\n                return value\n\n\nclass Identity(object):\n\n    def __call__(self, values):\n        return values\n\n\nclass SelectJmes(object):\n    \"\"\"\n        Query the input string for the jmespath (given at instantiation),\n        and return the answer\n        Requires : jmespath(https://github.com/jmespath/jmespath)\n        Note: SelectJmes accepts only one input element at a time.\n    \"\"\"\n    def __init__(self, json_path):\n        self.json_path = json_path\n        import jmespath\n        self.compiled_path = jmespath.compile(self.json_path)\n\n    def __call__(self, value):\n        \"\"\"Query value for the jmespath query and return answer\n        :param value: a data structure (dict, list) to extract from\n        :return: Element extracted according to jmespath query\n        \"\"\"\n        return self.compiled_path.search(value)\n\n\nclass Join(object):\n\n    def __init__(self, separator=u' '):\n        self.separator = separator\n\n    def __call__(self, values):\n        return self.separator.join(values)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/logformatter.py",
    "content": "import os\nimport logging\n\nfrom twisted.python.failure import Failure\n\nfrom scrapy.utils.request import referer_str\n\nSCRAPEDMSG = u\"Scraped from %(src)s\" + os.linesep + \"%(item)s\"\nDROPPEDMSG = u\"Dropped: %(exception)s\" + os.linesep + \"%(item)s\"\nCRAWLEDMSG = u\"Crawled (%(status)s) %(request)s%(request_flags)s (referer: %(referer)s)%(response_flags)s\"\n\n\nclass LogFormatter(object):\n    \"\"\"Class for generating log messages for different actions.\n\n    All methods must return a dictionary listing the parameters ``level``,\n    ``msg`` and ``args`` which are going to be used for constructing the log\n    message when calling logging.log.\n\n    Dictionary keys for the method outputs:\n        * ``level`` should be the log level for that action, you can use those\n        from the python logging library: logging.DEBUG, logging.INFO,\n        logging.WARNING, logging.ERROR and logging.CRITICAL.\n\n        * ``msg`` should be a string that can contain different formatting\n        placeholders. This string, formatted with the provided ``args``, is\n        going to be the log message for that action.\n\n        * ``args`` should be a tuple or dict with the formatting placeholders\n        for ``msg``.  The final log message is computed as output['msg'] %\n        output['args'].\n    \"\"\"\n\n    def crawled(self, request, response, spider):\n        request_flags = ' %s' % str(request.flags) if request.flags else ''\n        response_flags = ' %s' % str(response.flags) if response.flags else ''\n        return {\n            'level': logging.DEBUG,\n            'msg': CRAWLEDMSG,\n            'args': {\n                'status': response.status,\n                'request': request,\n                'request_flags' : request_flags,\n                'referer': referer_str(request),\n                'response_flags': response_flags,\n                # backward compatibility with Scrapy logformatter below 1.4 version\n                'flags': response_flags\n            }\n        }\n\n    def scraped(self, item, response, spider):\n        if isinstance(response, Failure):\n            src = response.getErrorMessage()\n        else:\n            src = response\n        return {\n            'level': logging.DEBUG,\n            'msg': SCRAPEDMSG,\n            'args': {\n                'src': src,\n                'item': item,\n            }\n        }\n\n    def dropped(self, item, exception, response, spider):\n        return {\n            'level': logging.WARNING,\n            'msg': DROPPEDMSG,\n            'args': {\n                'exception': exception,\n                'item': item,\n            }\n        }\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/mail.py",
    "content": "\"\"\"\nMail sending helpers\n\nSee documentation in docs/topics/email.rst\n\"\"\"\nimport logging\n\ntry:\n    from cStringIO import StringIO as BytesIO\nexcept ImportError:\n    from io import BytesIO\nimport six\n\nfrom email.utils import COMMASPACE, formatdate\nfrom six.moves.email_mime_multipart import MIMEMultipart\nfrom six.moves.email_mime_text import MIMEText\nfrom six.moves.email_mime_base import MIMEBase\nif six.PY2:\n    from email.MIMENonMultipart import MIMENonMultipart\n    from email import Encoders\nelse:\n    from email.mime.nonmultipart import MIMENonMultipart\n    from email import encoders as Encoders\n\nfrom twisted.internet import defer, reactor, ssl\n\nfrom scrapy.utils.misc import arg_to_iter\nfrom scrapy.utils.python import to_bytes\n\nlogger = logging.getLogger(__name__)\n\n\ndef _to_bytes_or_none(text):\n    if text is None:\n        return None\n    return to_bytes(text)\n\n\nclass MailSender(object):\n\n    def __init__(self, smtphost='localhost', mailfrom='scrapy@localhost',\n            smtpuser=None, smtppass=None, smtpport=25, smtptls=False, smtpssl=False, debug=False):\n        self.smtphost = smtphost\n        self.smtpport = smtpport\n        self.smtpuser = _to_bytes_or_none(smtpuser)\n        self.smtppass = _to_bytes_or_none(smtppass)\n        self.smtptls = smtptls\n        self.smtpssl = smtpssl\n        self.mailfrom = mailfrom\n        self.debug = debug\n\n    @classmethod\n    def from_settings(cls, settings):\n        return cls(settings['MAIL_HOST'], settings['MAIL_FROM'], settings['MAIL_USER'],\n            settings['MAIL_PASS'], settings.getint('MAIL_PORT'),\n            settings.getbool('MAIL_TLS'), settings.getbool('MAIL_SSL'))\n\n    def send(self, to, subject, body, cc=None, attachs=(), mimetype='text/plain', charset=None, _callback=None):\n        if attachs:\n            msg = MIMEMultipart()\n        else:\n            msg = MIMENonMultipart(*mimetype.split('/', 1))\n\n        to = list(arg_to_iter(to))\n        cc = list(arg_to_iter(cc))\n\n        msg['From'] = self.mailfrom\n        msg['To'] = COMMASPACE.join(to)\n        msg['Date'] = formatdate(localtime=True)\n        msg['Subject'] = subject\n        rcpts = to[:]\n        if cc:\n            rcpts.extend(cc)\n            msg['Cc'] = COMMASPACE.join(cc)\n\n        if charset:\n            msg.set_charset(charset)\n\n        if attachs:\n            msg.attach(MIMEText(body, 'plain', charset or 'us-ascii'))\n            for attach_name, mimetype, f in attachs:\n                part = MIMEBase(*mimetype.split('/'))\n                part.set_payload(f.read())\n                Encoders.encode_base64(part)\n                part.add_header('Content-Disposition', 'attachment; filename=\"%s\"' \\\n                    % attach_name)\n                msg.attach(part)\n        else:\n            msg.set_payload(body)\n\n        if _callback:\n            _callback(to=to, subject=subject, body=body, cc=cc, attach=attachs, msg=msg)\n\n        if self.debug:\n            logger.debug('Debug mail sent OK: To=%(mailto)s Cc=%(mailcc)s '\n                         'Subject=\"%(mailsubject)s\" Attachs=%(mailattachs)d',\n                         {'mailto': to, 'mailcc': cc, 'mailsubject': subject,\n                          'mailattachs': len(attachs)})\n            return\n\n        dfd = self._sendmail(rcpts, msg.as_string().encode(charset or 'utf-8'))\n        dfd.addCallbacks(self._sent_ok, self._sent_failed,\n            callbackArgs=[to, cc, subject, len(attachs)],\n            errbackArgs=[to, cc, subject, len(attachs)])\n        reactor.addSystemEventTrigger('before', 'shutdown', lambda: dfd)\n        return dfd\n\n    def _sent_ok(self, result, to, cc, subject, nattachs):\n        logger.info('Mail sent OK: To=%(mailto)s Cc=%(mailcc)s '\n                    'Subject=\"%(mailsubject)s\" Attachs=%(mailattachs)d',\n                    {'mailto': to, 'mailcc': cc, 'mailsubject': subject,\n                     'mailattachs': nattachs})\n\n    def _sent_failed(self, failure, to, cc, subject, nattachs):\n        errstr = str(failure.value)\n        logger.error('Unable to send mail: To=%(mailto)s Cc=%(mailcc)s '\n                     'Subject=\"%(mailsubject)s\" Attachs=%(mailattachs)d'\n                     '- %(mailerr)s',\n                     {'mailto': to, 'mailcc': cc, 'mailsubject': subject,\n                      'mailattachs': nattachs, 'mailerr': errstr})\n\n    def _sendmail(self, to_addrs, msg):\n        # Import twisted.mail here because it is not available in python3\n        from twisted.mail.smtp import ESMTPSenderFactory\n        msg = BytesIO(msg)\n        d = defer.Deferred()\n        factory = ESMTPSenderFactory(self.smtpuser, self.smtppass, self.mailfrom, \\\n            to_addrs, msg, d, heloFallback=True, requireAuthentication=False, \\\n            requireTransportSecurity=self.smtptls)\n        factory.noisy = False\n\n        if self.smtpssl:\n            reactor.connectSSL(self.smtphost, self.smtpport, factory, ssl.ClientContextFactory())\n        else:\n            reactor.connectTCP(self.smtphost, self.smtpport, factory)\n\n        return d\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/middleware.py",
    "content": "from collections import defaultdict, deque\nimport logging\nimport pprint\n\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy.utils.misc import create_instance, load_object\nfrom scrapy.utils.defer import process_parallel, process_chain, process_chain_both\n\nlogger = logging.getLogger(__name__)\n\n\nclass MiddlewareManager(object):\n    \"\"\"Base class for implementing middleware managers\"\"\"\n\n    component_name = 'foo middleware'\n\n    def __init__(self, *middlewares):\n        self.middlewares = middlewares\n        self.methods = defaultdict(deque)\n        for mw in middlewares:\n            self._add_middleware(mw)\n\n    @classmethod\n    def _get_mwlist_from_settings(cls, settings):\n        raise NotImplementedError\n\n    @classmethod\n    def from_settings(cls, settings, crawler=None):\n        mwlist = cls._get_mwlist_from_settings(settings)\n        middlewares = []\n        enabled = []\n        for clspath in mwlist:\n            try:\n                mwcls = load_object(clspath)\n                mw = create_instance(mwcls, settings, crawler)\n                middlewares.append(mw)\n                enabled.append(clspath)\n            except NotConfigured as e:\n                if e.args:\n                    clsname = clspath.split('.')[-1]\n                    logger.warning(\"Disabled %(clsname)s: %(eargs)s\",\n                                   {'clsname': clsname, 'eargs': e.args[0]},\n                                   extra={'crawler': crawler})\n\n        logger.info(\"Enabled %(componentname)ss:\\n%(enabledlist)s\",\n                    {'componentname': cls.component_name,\n                     'enabledlist': pprint.pformat(enabled)},\n                    extra={'crawler': crawler})\n        return cls(*middlewares)\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls.from_settings(crawler.settings, crawler)\n\n    def _add_middleware(self, mw):\n        if hasattr(mw, 'open_spider'):\n            self.methods['open_spider'].append(mw.open_spider)\n        if hasattr(mw, 'close_spider'):\n            self.methods['close_spider'].appendleft(mw.close_spider)\n\n    def _process_parallel(self, methodname, obj, *args):\n        return process_parallel(self.methods[methodname], obj, *args)\n\n    def _process_chain(self, methodname, obj, *args):\n        return process_chain(self.methods[methodname], obj, *args)\n\n    def _process_chain_both(self, cb_methodname, eb_methodname, obj, *args):\n        return process_chain_both(self.methods[cb_methodname], \\\n            self.methods[eb_methodname], obj, *args)\n\n    def open_spider(self, spider):\n        return self._process_parallel('open_spider', spider)\n\n    def close_spider(self, spider):\n        return self._process_parallel('close_spider', spider)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/mime.types",
    "content": "###############################################################################\n#\n#  MIME-TYPES and the extensions that represent them\n#\n###############################################################################\n\n\napplication/activemessage\napplication/andrew-inset\t\t\tez\napplication/annodex\t\t\t\tanx\napplication/applefile\napplication/atom+xml\t\t\t\tatom\napplication/atomcat+xml\t\t\t\tatomcat\napplication/atomserv+xml\t\t\tatomsrv\napplication/atomicmail\napplication/batch-SMTP\napplication/beep+xml\napplication/bbolin\t\t\t\tlin\napplication/cals-1840\napplication/cap\t\t\t\t\tcap pcap\napplication/commonground\napplication/cu-seeme\t\t\t\tcu\napplication/cybercash\napplication/davmount+xml\t\t\tdavmount\napplication/dca-rft\napplication/dec-dx\napplication/docbook+xml\napplication/dsptype\t\t\t\ttsp\napplication/dvcs\napplication/ecmascript\t\t\t\tes\napplication/edi-consent\napplication/edi-x12\napplication/edifact\napplication/eshop\napplication/font-tdpfr\napplication/futuresplash\t\t\tspl\napplication/ghostview\napplication/hta\t\t\t\t\thta\napplication/http\napplication/hyperstudio\napplication/iges\napplication/index\napplication/index.cmd\napplication/index.obj\napplication/index.response\napplication/index.vnd\napplication/iotp\napplication/ipp\napplication/isup\napplication/java-archive\t\t\tjar\napplication/java-serialized-object\t\tser\napplication/java-vm\t\t\t\tclass\napplication/javascript\t\t\t\tjs\napplication/m3g\t\t\t\t\tm3g\napplication/mac-binhex40\t\t\thqx\napplication/mac-compactpro\t\t\tcpt\napplication/macwriteii\napplication/marc\napplication/mathematica\t\t\t\tnb nbp\napplication/ms-tnef\napplication/msaccess\t\t\t\tmdb\napplication/msword\t\t\t\tdoc dot\napplication/news-message-id\napplication/news-transmission\napplication/ocsp-request\napplication/ocsp-response\napplication/octet-stream\t\t\tbin\napplication/oda\t\t\t\t\toda\napplication/ogg\t\t\t\t\togx\napplication/parityfec\napplication/pdf\t\t\t\t\tpdf\napplication/pgp-encrypted\napplication/pgp-keys\t\t\t\tkey\napplication/pgp-signature\t\t\tpgp\napplication/pics-rules\t\t\t\tprf\napplication/pkcs10\napplication/pkcs7-mime\napplication/pkcs7-signature\napplication/pkix-cert\napplication/pkix-crl\napplication/pkixcmp\napplication/postscript\t\t\t\tps ai eps espi epsf eps2 eps3\napplication/prs.alvestrand.titrax-sheet\napplication/prs.cww\napplication/prs.nprend\napplication/qsig\napplication/rar\t\t\t\t\trar\napplication/rdf+xml\t\t\t\trdf\napplication/remote-printing\napplication/riscos\napplication/rss+xml\t\t\t\trss\napplication/rtf\t\t\t\t\trtf\napplication/sdp\napplication/set-payment\napplication/set-payment-initiation\napplication/set-registration\napplication/set-registration-initiation\napplication/sgml\napplication/sgml-open-catalog\napplication/sieve\napplication/slate\napplication/smil\t\t\t\tsmi smil\napplication/timestamp-query\napplication/timestamp-reply\napplication/vemmi\napplication/whoispp-query\napplication/whoispp-response\napplication/wita\napplication/x400-bp\napplication/xhtml+xml\t\t\t\txhtml xht\napplication/xml\t\t\t\t\txml xsl xsd\napplication/xml-dtd\napplication/xml-external-parsed-entity\napplication/xspf+xml\t\t\t\txspf\napplication/zip\t\t\t\t\tzip\napplication/vnd.3M.Post-it-Notes\napplication/vnd.accpac.simply.aso\napplication/vnd.accpac.simply.imp\napplication/vnd.acucobol\napplication/vnd.aether.imp\napplication/vnd.anser-web-certificate-issue-initiation\napplication/vnd.anser-web-funds-transfer-initiation\napplication/vnd.audiograph\napplication/vnd.bmi\napplication/vnd.businessobjects\napplication/vnd.canon-cpdl\napplication/vnd.canon-lips\napplication/vnd.cinderella\t\t\tcdy\napplication/vnd.claymore\napplication/vnd.commerce-battelle\napplication/vnd.commonspace\napplication/vnd.comsocaller\napplication/vnd.contact.cmsg\napplication/vnd.cosmocaller\napplication/vnd.ctc-posml\napplication/vnd.cups-postscript\napplication/vnd.cups-raster\napplication/vnd.cups-raw\napplication/vnd.cybank\napplication/vnd.dna\napplication/vnd.dpgraph\napplication/vnd.dxr\napplication/vnd.ecdis-update\napplication/vnd.ecowin.chart\napplication/vnd.ecowin.filerequest\napplication/vnd.ecowin.fileupdate\napplication/vnd.ecowin.series\napplication/vnd.ecowin.seriesrequest\napplication/vnd.ecowin.seriesupdate\napplication/vnd.enliven\napplication/vnd.epson.esf\napplication/vnd.epson.msf\napplication/vnd.epson.quickanime\napplication/vnd.epson.salt\napplication/vnd.epson.ssf\napplication/vnd.ericsson.quickcall\napplication/vnd.eudora.data\napplication/vnd.fdf\napplication/vnd.ffsns\napplication/vnd.flographit\napplication/vnd.framemaker\napplication/vnd.fsc.weblaunch\napplication/vnd.fujitsu.oasys\napplication/vnd.fujitsu.oasys2\napplication/vnd.fujitsu.oasys3\napplication/vnd.fujitsu.oasysgp\napplication/vnd.fujitsu.oasysprs\napplication/vnd.fujixerox.ddd\napplication/vnd.fujixerox.docuworks\napplication/vnd.fujixerox.docuworks.binder\napplication/vnd.fut-misnet\napplication/vnd.google-earth.kml+xml\t\tkml\napplication/vnd.google-earth.kmz\t\tkmz\napplication/vnd.grafeq\napplication/vnd.groove-account\napplication/vnd.groove-identity-message\napplication/vnd.groove-injector\napplication/vnd.groove-tool-message\napplication/vnd.groove-tool-template\napplication/vnd.groove-vcard\napplication/vnd.hhe.lesson-player\napplication/vnd.hp-HPGL\napplication/vnd.hp-PCL\napplication/vnd.hp-PCLXL\napplication/vnd.hp-hpid\napplication/vnd.hp-hps\napplication/vnd.httphone\napplication/vnd.hzn-3d-crossword\napplication/vnd.ibm.MiniPay\napplication/vnd.ibm.afplinedata\napplication/vnd.ibm.modcap\napplication/vnd.informix-visionary\napplication/vnd.intercon.formnet\napplication/vnd.intertrust.digibox\napplication/vnd.intertrust.nncp\napplication/vnd.intu.qbo\napplication/vnd.intu.qfx\napplication/vnd.irepository.package+xml\napplication/vnd.is-xpr\napplication/vnd.japannet-directory-service\napplication/vnd.japannet-jpnstore-wakeup\napplication/vnd.japannet-payment-wakeup\napplication/vnd.japannet-registration\napplication/vnd.japannet-registration-wakeup\napplication/vnd.japannet-setstore-wakeup\napplication/vnd.japannet-verification\napplication/vnd.japannet-verification-wakeup\napplication/vnd.koan\napplication/vnd.lotus-1-2-3\napplication/vnd.lotus-approach\napplication/vnd.lotus-freelance\napplication/vnd.lotus-notes\napplication/vnd.lotus-organizer\napplication/vnd.lotus-screencam\napplication/vnd.lotus-wordpro\napplication/vnd.mcd\napplication/vnd.mediastation.cdkey\napplication/vnd.meridian-slingshot\napplication/vnd.mif\napplication/vnd.minisoft-hp3000-save\napplication/vnd.mitsubishi.misty-guard.trustweb\napplication/vnd.mobius.daf\napplication/vnd.mobius.dis\napplication/vnd.mobius.msl\napplication/vnd.mobius.plc\napplication/vnd.mobius.txf\napplication/vnd.motorola.flexsuite\napplication/vnd.motorola.flexsuite.adsi\napplication/vnd.motorola.flexsuite.fis\napplication/vnd.motorola.flexsuite.gotap\napplication/vnd.motorola.flexsuite.kmr\napplication/vnd.motorola.flexsuite.ttc\napplication/vnd.motorola.flexsuite.wem\napplication/vnd.mozilla.xul+xml\t\t\txul\napplication/vnd.ms-artgalry\napplication/vnd.ms-asf\napplication/vnd.ms-excel\t\t\txls xlb xlt\napplication/vnd.ms-lrm\napplication/vnd.ms-pki.seccat\t\t\tcat\napplication/vnd.ms-pki.stl\t\t\tstl\napplication/vnd.ms-powerpoint\t\t\tppt pps\napplication/vnd.ms-project\napplication/vnd.ms-tnef\napplication/vnd.ms-works\napplication/vnd.mseq\napplication/vnd.msign\napplication/vnd.music-niff\napplication/vnd.musician\napplication/vnd.netfpx\napplication/vnd.noblenet-directory\napplication/vnd.noblenet-sealer\napplication/vnd.noblenet-web\napplication/vnd.novadigm.EDM\napplication/vnd.novadigm.EDX\napplication/vnd.novadigm.EXT\napplication/vnd.oasis.opendocument.chart\t\t\todc\napplication/vnd.oasis.opendocument.database\t\t\todb\napplication/vnd.oasis.opendocument.formula\t\t\todf\napplication/vnd.oasis.opendocument.graphics\t\t\todg\napplication/vnd.oasis.opendocument.graphics-template\t\totg\napplication/vnd.oasis.opendocument.image\t\t\todi\napplication/vnd.oasis.opendocument.presentation\t\t\todp\napplication/vnd.oasis.opendocument.presentation-template\totp\napplication/vnd.oasis.opendocument.spreadsheet\t\t\tods\napplication/vnd.oasis.opendocument.spreadsheet-template\t\tots\napplication/vnd.oasis.opendocument.text\t\t\t\todt\napplication/vnd.oasis.opendocument.text-master\t\t\todm\napplication/vnd.oasis.opendocument.text-template\t\tott\napplication/vnd.oasis.opendocument.text-web\t\t\toth\napplication/vnd.osa.netdeploy\napplication/vnd.palm\napplication/vnd.pg.format\napplication/vnd.pg.osasli\napplication/vnd.powerbuilder6\napplication/vnd.powerbuilder6-s\napplication/vnd.powerbuilder7\napplication/vnd.powerbuilder7-s\napplication/vnd.powerbuilder75\napplication/vnd.powerbuilder75-s\napplication/vnd.previewsystems.box\napplication/vnd.publishare-delta-tree\napplication/vnd.pvi.ptid1\napplication/vnd.pwg-xhtml-print+xml\napplication/vnd.rapid\napplication/vnd.rim.cod\t\t\t\tcod\napplication/vnd.s3sms\napplication/vnd.seemail\napplication/vnd.shana.informed.formdata\napplication/vnd.shana.informed.formtemplate\napplication/vnd.shana.informed.interchange\napplication/vnd.shana.informed.package\napplication/vnd.smaf\t\t\t\tmmf\napplication/vnd.sss-cod\napplication/vnd.sss-dtf\napplication/vnd.sss-ntf\napplication/vnd.stardivision.calc\t\tsdc\napplication/vnd.stardivision.chart\t\tsds\napplication/vnd.stardivision.draw\t\tsda\napplication/vnd.stardivision.impress\t\tsdd\napplication/vnd.stardivision.math\t\tsdf\napplication/vnd.stardivision.writer\t\tsdw\napplication/vnd.stardivision.writer-global\tsgl\napplication/vnd.street-stream\napplication/vnd.sun.xml.calc\t\t\tsxc\napplication/vnd.sun.xml.calc.template\t\tstc\napplication/vnd.sun.xml.draw\t\t\tsxd\napplication/vnd.sun.xml.draw.template\t\tstd\napplication/vnd.sun.xml.impress\t\t\tsxi\napplication/vnd.sun.xml.impress.template\tsti\napplication/vnd.sun.xml.math\t\t\tsxm\napplication/vnd.sun.xml.writer\t\t\tsxw\napplication/vnd.sun.xml.writer.global\t\tsxg\napplication/vnd.sun.xml.writer.template\t\tstw\napplication/vnd.svd\napplication/vnd.swiftview-ics\napplication/vnd.symbian.install\t\t\tsis\napplication/vnd.triscape.mxs\napplication/vnd.trueapp\napplication/vnd.truedoc\napplication/vnd.tve-trigger\napplication/vnd.ufdl\napplication/vnd.uplanet.alert\napplication/vnd.uplanet.alert-wbxml\napplication/vnd.uplanet.bearer-choice\napplication/vnd.uplanet.bearer-choice-wbxml\napplication/vnd.uplanet.cacheop\napplication/vnd.uplanet.cacheop-wbxml\napplication/vnd.uplanet.channel\napplication/vnd.uplanet.channel-wbxml\napplication/vnd.uplanet.list\napplication/vnd.uplanet.list-wbxml\napplication/vnd.uplanet.listcmd\napplication/vnd.uplanet.listcmd-wbxml\napplication/vnd.uplanet.signal\napplication/vnd.vcx\napplication/vnd.vectorworks\napplication/vnd.vidsoft.vidconference\napplication/vnd.visio\t\t\t\tvsd\napplication/vnd.vividence.scriptfile\napplication/vnd.wap.sic\napplication/vnd.wap.slc\napplication/vnd.wap.wbxml\t\t\twbxml\napplication/vnd.wap.wmlc\t\t\twmlc\napplication/vnd.wap.wmlscriptc\t\t\twmlsc\napplication/vnd.webturbo\napplication/vnd.wordperfect\t\t\twpd\napplication/vnd.wordperfect5.1\t\t\twp5\napplication/vnd.wrq-hp3000-labelled\napplication/vnd.wt.stf\napplication/vnd.xara\napplication/vnd.xfdl\napplication/vnd.yellowriver-custom-menu\napplication/x-123\t\t\t\twk\napplication/x-7z-compressed\t\t\t7z\napplication/x-abiword\t\t\t\tabw\napplication/x-apple-diskimage\t\t\tdmg\napplication/x-bcpio\t\t\t\tbcpio\napplication/x-bittorrent\t\t\ttorrent\napplication/x-cab\t\t\t\tcab\napplication/x-cbr\t\t\t\tcbr\napplication/x-cbz\t\t\t\tcbz\napplication/x-cdf\t\t\t\tcdf cda\napplication/x-cdlink\t\t\t\tvcd\napplication/x-chess-pgn\t\t\t\tpgn\napplication/x-core\napplication/x-cpio\t\t\t\tcpio\napplication/x-csh\t\t\t\tcsh\napplication/x-debian-package\t\t\tdeb udeb\napplication/x-director\t\t\t\tdcr dir dxr\napplication/x-dms\t\t\t\tdms\napplication/x-doom\t\t\t\twad\napplication/x-dvi\t\t\t\tdvi\napplication/x-httpd-eruby\t\t\trhtml\napplication/x-executable\napplication/x-font\t\t\t\tpfa pfb gsf pcf pcf.Z\napplication/x-freemind\t\t\t\tmm\napplication/x-futuresplash\t\t\tspl\napplication/x-gnumeric\t\t\t\tgnumeric\napplication/x-go-sgf\t\t\t\tsgf\napplication/x-graphing-calculator\t\tgcf\napplication/x-gtar\t\t\t\tgtar tgz taz\napplication/x-hdf\t\t\t\thdf\napplication/x-httpd-php\t\t\t\tphtml pht php\napplication/x-httpd-php-source\t\t\tphps\napplication/x-httpd-php3\t\t\tphp3\napplication/x-httpd-php3-preprocessed\t\tphp3p\napplication/x-httpd-php4\t\t\tphp4\napplication/x-ica\t\t\t\tica\napplication/x-info\t\t\t\tinfo\napplication/x-internet-signup\t\t\tins isp\napplication/x-iphone\t\t\t\tiii\napplication/x-iso9660-image\t\t\tiso\napplication/x-jam\t\t\t\tjam\napplication/x-java-applet\napplication/x-java-bean\napplication/x-java-jnlp-file\t\t\tjnlp\napplication/x-jmol\t\t\t\tjmz\napplication/x-kchart\t\t\t\tchrt\napplication/x-kdelnk\napplication/x-killustrator\t\t\tkil\napplication/x-koan\t\t\t\tskp skd skt skm\napplication/x-kpresenter\t\t\tkpr kpt\napplication/x-kspread\t\t\t\tksp\napplication/x-kword\t\t\t\tkwd kwt\napplication/x-latex\t\t\t\tlatex\napplication/x-lha\t\t\t\tlha\napplication/x-lyx\t\t\t\tlyx\napplication/x-lzh\t\t\t\tlzh\napplication/x-lzx\t\t\t\tlzx\napplication/x-maker\t\t\t\tfrm maker frame fm fb book fbdoc\napplication/x-mif\t\t\t\tmif\napplication/x-ms-wmd\t\t\t\twmd\napplication/x-ms-wmz\t\t\t\twmz\napplication/x-msdos-program\t\t\tcom exe bat dll\napplication/x-msi\t\t\t\tmsi\napplication/x-netcdf\t\t\t\tnc\napplication/x-ns-proxy-autoconfig\t\tpac dat\napplication/x-nwc\t\t\t\tnwc\napplication/x-object\t\t\t\to\napplication/x-oz-application\t\t\toza\napplication/x-pkcs7-certreqresp\t\t\tp7r\napplication/x-pkcs7-crl\t\t\t\tcrl\napplication/x-python-code\t\t\tpyc pyo\napplication/x-qgis\t\t\t\tqgs shp shx\napplication/x-quicktimeplayer\t\t\tqtl\napplication/x-redhat-package-manager\t\trpm\napplication/x-ruby\t\t\t\trb\napplication/x-rx\napplication/x-sh\t\t\t\tsh\napplication/x-shar\t\t\t\tshar\napplication/x-shellscript\napplication/x-shockwave-flash\t\t\tswf swfl\napplication/x-stuffit\t\t\t\tsit sitx\napplication/x-sv4cpio\t\t\t\tsv4cpio\napplication/x-sv4crc\t\t\t\tsv4crc\napplication/x-tar\t\t\t\ttar\napplication/x-tcl\t\t\t\ttcl\napplication/x-tex-gf\t\t\t\tgf\napplication/x-tex-pk\t\t\t\tpk\napplication/x-texinfo\t\t\t\ttexinfo texi\napplication/x-trash\t\t\t\t~ % bak old sik\napplication/x-troff\t\t\t\tt tr roff\napplication/x-troff-man\t\t\t\tman\napplication/x-troff-me\t\t\t\tme\napplication/x-troff-ms\t\t\t\tms\napplication/x-ustar\t\t\t\tustar\napplication/x-videolan\napplication/x-wais-source\t\t\tsrc\napplication/x-wingz\t\t\t\twz\napplication/x-x509-ca-cert\t\t\tcrt\napplication/x-xcf\t\t\t\txcf\napplication/x-xfig\t\t\t\tfig\napplication/x-xpinstall\t\t\t\txpi\n\naudio/32kadpcm\naudio/3gpp\naudio/amr\t\t\t\t\tamr\naudio/amr-wb\t\t\t\t\tawb\naudio/amr\t\t\t\t\tamr\naudio/amr-wb\t\t\t\t\tawb\naudio/annodex\t\t\t\t\taxa\naudio/basic\t\t\t\t\tau snd\naudio/flac\t\t\t\t\tflac\naudio/g.722.1\naudio/l16\naudio/midi\t\t\t\t\tmid midi kar\naudio/mp4a-latm\naudio/mpa-robust\naudio/mpeg\t\t\t\t\tmpga mpega mp2 mp3 m4a\naudio/mpegurl\t\t\t\t\tm3u\naudio/ogg\t\t\t\t\toga ogg spx\naudio/parityfec\naudio/prs.sid\t\t\t\t\tsid\naudio/telephone-event\naudio/tone\naudio/vnd.cisco.nse\naudio/vnd.cns.anp1\naudio/vnd.cns.inf1\naudio/vnd.digital-winds\naudio/vnd.everad.plj\naudio/vnd.lucent.voice\naudio/vnd.nortel.vbk\naudio/vnd.nuera.ecelp4800\naudio/vnd.nuera.ecelp7470\naudio/vnd.nuera.ecelp9600\naudio/vnd.octel.sbc\naudio/vnd.qcelp\naudio/vnd.rhetorex.32kadpcm\naudio/vnd.vmx.cvsd\naudio/x-aiff\t\t\t\t\taif aiff aifc\naudio/x-gsm\t\t\t\t\tgsm\naudio/x-mpegurl\t\t\t\t\tm3u\naudio/x-ms-wma\t\t\t\t\twma\naudio/x-ms-wax\t\t\t\t\twax\naudio/x-pn-realaudio-plugin\naudio/x-pn-realaudio\t\t\t\tra rm ram\naudio/x-realaudio\t\t\t\tra\naudio/x-scpls\t\t\t\t\tpls\naudio/x-sd2\t\t\t\t\tsd2\naudio/x-wav\t\t\t\t\twav\n\nchemical/x-alchemy\t\t\t\talc\nchemical/x-cache\t\t\t\tcac cache\nchemical/x-cache-csf\t\t\t\tcsf\nchemical/x-cactvs-binary\t\t\tcbin cascii ctab\nchemical/x-cdx\t\t\t\t\tcdx\nchemical/x-cerius\t\t\t\tcer\nchemical/x-chem3d\t\t\t\tc3d\nchemical/x-chemdraw\t\t\t\tchm\nchemical/x-cif\t\t\t\t\tcif\nchemical/x-cmdf\t\t\t\t\tcmdf\nchemical/x-cml\t\t\t\t\tcml\nchemical/x-compass\t\t\t\tcpa\nchemical/x-crossfire\t\t\t\tbsd\nchemical/x-csml\t\t\t\t\tcsml csm\nchemical/x-ctx\t\t\t\t\tctx\nchemical/x-cxf\t\t\t\t\tcxf cef\n#chemical/x-daylight-smiles\t\t\tsmi\nchemical/x-embl-dl-nucleotide\t\t\temb embl\nchemical/x-galactic-spc\t\t\t\tspc\nchemical/x-gamess-input\t\t\t\tinp gam gamin\nchemical/x-gaussian-checkpoint\t\t\tfch fchk\nchemical/x-gaussian-cube\t\t\tcub\nchemical/x-gaussian-input\t\t\tgau gjc gjf\nchemical/x-gaussian-log\t\t\t\tgal\nchemical/x-gcg8-sequence\t\t\tgcg\nchemical/x-genbank\t\t\t\tgen\nchemical/x-hin\t\t\t\t\thin\nchemical/x-isostar\t\t\t\tistr ist\nchemical/x-jcamp-dx\t\t\t\tjdx dx\nchemical/x-kinemage\t\t\t\tkin\nchemical/x-macmolecule\t\t\t\tmcm\nchemical/x-macromodel-input\t\t\tmmd mmod\nchemical/x-mdl-molfile\t\t\t\tmol\nchemical/x-mdl-rdfile\t\t\t\trd\nchemical/x-mdl-rxnfile\t\t\t\trxn\nchemical/x-mdl-sdfile\t\t\t\tsd sdf\nchemical/x-mdl-tgf\t\t\t\ttgf\n#chemical/x-mif\t\t\t\t\tmif\nchemical/x-mmcif\t\t\t\tmcif\nchemical/x-mol2\t\t\t\t\tmol2\nchemical/x-molconn-Z\t\t\t\tb\nchemical/x-mopac-graph\t\t\t\tgpt\nchemical/x-mopac-input\t\t\t\tmop mopcrt mpc zmt\nchemical/x-mopac-out\t\t\t\tmoo\nchemical/x-mopac-vib\t\t\t\tmvb\nchemical/x-ncbi-asn1\t\t\t\tasn\nchemical/x-ncbi-asn1-ascii\t\t\tprt ent\nchemical/x-ncbi-asn1-binary\t\t\tval aso\nchemical/x-ncbi-asn1-spec\t\t\tasn\nchemical/x-pdb\t\t\t\t\tpdb ent\nchemical/x-rosdal\t\t\t\tros\nchemical/x-swissprot\t\t\t\tsw\nchemical/x-vamas-iso14976\t\t\tvms\nchemical/x-vmd\t\t\t\t\tvmd\nchemical/x-xtel\t\t\t\t\txtel\nchemical/x-xyz\t\t\t\t\txyz\n\nimage/cgm\nimage/g3fax\nimage/gif\t\t\t\t\tgif\nimage/ief\t\t\t\t\tief\nimage/jpeg\t\t\t\t\tjpeg jpg jpe\nimage/naplps\nimage/pcx\t\t\t\t\tpcx\nimage/png\t\t\t\t\tpng\nimage/prs.btif\nimage/prs.pti\nimage/svg+xml\t\t\t\t\tsvg svgz\nimage/tiff\t\t\t\t\ttiff tif\nimage/vnd.cns.inf2\nimage/vnd.djvu\t\t\t\t\tdjvu djv\nimage/vnd.dwg\nimage/vnd.dxf\nimage/vnd.fastbidsheet\nimage/vnd.fpx\nimage/vnd.fst\nimage/vnd.fujixerox.edmics-mmr\nimage/vnd.fujixerox.edmics-rlc\nimage/vnd.mix\nimage/vnd.net-fpx\nimage/vnd.svf\nimage/vnd.wap.wbmp\t\t\t\twbmp\nimage/vnd.xiff\nimage/x-cmu-raster\t\t\t\tras\nimage/x-coreldraw\t\t\t\tcdr\nimage/x-coreldrawpattern\t\t\tpat\nimage/x-coreldrawtemplate\t\t\tcdt\nimage/x-corelphotopaint\t\t\t\tcpt\nimage/x-icon\t\t\t\t\tico\nimage/x-jg\t\t\t\t\tart\nimage/x-jng\t\t\t\t\tjng\nimage/x-ms-bmp\t\t\t\t\tbmp\nimage/x-photoshop\t\t\t\tpsd\nimage/x-portable-anymap\t\t\t\tpnm\nimage/x-portable-bitmap\t\t\t\tpbm\nimage/x-portable-graymap\t\t\tpgm\nimage/x-portable-pixmap\t\t\t\tppm\nimage/x-rgb\t\t\t\t\trgb\nimage/x-xbitmap\t\t\t\t\txbm\nimage/x-xpixmap\t\t\t\t\txpm\nimage/x-xwindowdump\t\t\t\txwd\n\ninode/chardevice\ninode/blockdevice\ninode/directory-locked\ninode/directory\ninode/fifo\ninode/socket\n\nmessage/delivery-status\nmessage/disposition-notification\nmessage/external-body\nmessage/http\nmessage/s-http\nmessage/news\nmessage/partial\nmessage/rfc822\t\t\t\t\teml\n\nmodel/iges\t\t\t\t\tigs iges\nmodel/mesh\t\t\t\t\tmsh mesh silo\nmodel/vnd.dwf\nmodel/vnd.flatland.3dml\nmodel/vnd.gdl\nmodel/vnd.gs-gdl\nmodel/vnd.gtw\nmodel/vnd.mts\nmodel/vnd.vtu\nmodel/vrml\t\t\t\t\twrl vrml\n\nmultipart/alternative\nmultipart/appledouble\nmultipart/byteranges\nmultipart/digest\nmultipart/encrypted\nmultipart/form-data\nmultipart/header-set\nmultipart/mixed\nmultipart/parallel\nmultipart/related\nmultipart/report\nmultipart/signed\nmultipart/voice-message\n\ntext/calendar\t\t\t\t\tics icz\ntext/css\t\t\t\t\tcss\ntext/csv\t\t\t\t\tcsv\ntext/directory\ntext/english\ntext/enriched\ntext/h323\t\t\t\t\t323\ntext/html\t\t\t\t\thtml htm shtml\ntext/iuls\t\t\t\t\tuls\ntext/mathml\t\t\t\t\tmml\ntext/parityfec\ntext/plain\t\t\t\t\tasc txt text pot brf\ntext/prs.lines.tag\ntext/rfc822-headers\ntext/richtext\t\t\t\t\trtx\ntext/rtf\ntext/scriptlet\t\t\t\t\tsct wsc\ntext/t140\ntext/texmacs\t\t\t\t\ttm ts\ntext/tab-separated-values\t\t\ttsv\ntext/uri-list\ntext/vnd.abc\ntext/vnd.curl\ntext/vnd.DMClientScript\ntext/vnd.flatland.3dml\ntext/vnd.fly\ntext/vnd.fmi.flexstor\ntext/vnd.in3d.3dml\ntext/vnd.in3d.spot\ntext/vnd.IPTC.NewsML\ntext/vnd.IPTC.NITF\ntext/vnd.latex-z\ntext/vnd.motorola.reflex\ntext/vnd.ms-mediapackage\ntext/vnd.sun.j2me.app-descriptor\t\tjad\ntext/vnd.wap.si\ntext/vnd.wap.sl\ntext/vnd.wap.wml\t\t\t\twml\ntext/vnd.wap.wmlscript\t\t\t\twmls\ntext/x-bibtex\t\t\t\t\tbib\ntext/x-boo\t\t\t\t\tboo\ntext/x-c++hdr\t\t\t\t\th++ hpp hxx hh\ntext/x-c++src\t\t\t\t\tc++ cpp cxx cc\ntext/x-chdr\t\t\t\t\th\ntext/x-component\t\t\t\thtc\ntext/x-crontab\ntext/x-csh\t\t\t\t\tcsh\ntext/x-csrc\t\t\t\t\tc\ntext/x-dsrc\t\t\t\t\td\ntext/x-diff\t\t\t\t\tdiff patch\ntext/x-haskell\t\t\t\t\ths\ntext/x-java\t\t\t\t\tjava\ntext/x-literate-haskell\t\t\t\tlhs\ntext/x-makefile\ntext/x-moc\t\t\t\t\tmoc\ntext/x-pascal\t\t\t\t\tp pas\ntext/x-pcs-gcd\t\t\t\t\tgcd\ntext/x-perl\t\t\t\t\tpl pm\ntext/x-python\t\t\t\t\tpy\ntext/x-scala\t\t\t\t\tscala\ntext/x-server-parsed-html\ntext/x-setext\t\t\t\t\tetx\ntext/x-sh\t\t\t\t\tsh\ntext/x-tcl\t\t\t\t\ttcl tk\ntext/x-tex\t\t\t\t\ttex ltx sty cls\ntext/x-vcalendar\t\t\t\tvcs\ntext/x-vcard\t\t\t\t\tvcf\n\nvideo/3gpp\t\t\t\t\t3gp\nvideo/annodex\t\t\t\t\taxv\nvideo/dl\t\t\t\t\tdl\nvideo/dv\t\t\t\t\tdif dv\nvideo/fli\t\t\t\t\tfli\nvideo/gl\t\t\t\t\tgl\nvideo/mpeg\t\t\t\t\tmpeg mpg mpe\nvideo/mp4\t\t\t\t\tmp4\nvideo/quicktime\t\t\t\t\tqt mov\nvideo/mp4v-es\nvideo/ogg\t\t\t\t\togv\nvideo/parityfec\nvideo/pointer\nvideo/vnd.fvt\nvideo/vnd.motorola.video\nvideo/vnd.motorola.videop\nvideo/vnd.mpegurl\t\t\t\tmxu\nvideo/vnd.mts\nvideo/vnd.nokia.interleaved-multimedia\nvideo/vnd.vivo\nvideo/x-flv\t\t\t\t\tflv\nvideo/x-la-asf\t\t\t\t\tlsf lsx\nvideo/x-mng\t\t\t\t\tmng\nvideo/x-ms-asf\t\t\t\t\tasf asx\nvideo/x-ms-wm\t\t\t\t\twm\nvideo/x-ms-wmv\t\t\t\t\twmv\nvideo/x-ms-wmx\t\t\t\t\twmx\nvideo/x-ms-wvx\t\t\t\t\twvx\nvideo/x-msvideo\t\t\t\t\tavi\nvideo/x-sgi-movie\t\t\t\tmovie\nvideo/x-matroska\t\t\t\tmpv\n\nx-conference/x-cooltalk\t\t\t\tice\n\nx-epoc/x-sisx-app\t\t\t\tsisx\nx-world/x-vrml\t\t\t\t\tvrm vrml wrl\n\nx-scrapy/test                                   scrapytest\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/pipelines/__init__.py",
    "content": "\"\"\"\nItem pipeline\n\nSee documentation in docs/item-pipeline.rst\n\"\"\"\n\nfrom scrapy.middleware import MiddlewareManager\nfrom scrapy.utils.conf import build_component_list\n\nclass ItemPipelineManager(MiddlewareManager):\n\n    component_name = 'item pipeline'\n\n    @classmethod\n    def _get_mwlist_from_settings(cls, settings):\n        return build_component_list(settings.getwithbase('ITEM_PIPELINES'))\n\n    def _add_middleware(self, pipe):\n        super(ItemPipelineManager, self)._add_middleware(pipe)\n        if hasattr(pipe, 'process_item'):\n            self.methods['process_item'].append(pipe.process_item)\n\n    def process_item(self, item, spider):\n        return self._process_chain('process_item', item, spider)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/pipelines/files.py",
    "content": "\"\"\"\nFiles Pipeline\n\nSee documentation in topics/media-pipeline.rst\n\"\"\"\nimport functools\nimport hashlib\nimport os\nimport os.path\nimport time\nimport logging\nfrom email.utils import parsedate_tz, mktime_tz\nfrom six.moves.urllib.parse import urlparse\nfrom collections import defaultdict\nimport six\n\ntry:\n    from cStringIO import StringIO as BytesIO\nexcept ImportError:\n    from io import BytesIO\n\nfrom twisted.internet import defer, threads\n\nfrom scrapy.pipelines.media import MediaPipeline\nfrom scrapy.settings import Settings\nfrom scrapy.exceptions import NotConfigured, IgnoreRequest\nfrom scrapy.http import Request\nfrom scrapy.utils.misc import md5sum\nfrom scrapy.utils.log import failure_to_exc_info\nfrom scrapy.utils.python import to_bytes\nfrom scrapy.utils.request import referer_str\nfrom scrapy.utils.boto import is_botocore\nfrom scrapy.utils.datatypes import CaselessDict\n\nlogger = logging.getLogger(__name__)\n\n\nclass FileException(Exception):\n    \"\"\"General media error exception\"\"\"\n\n\nclass FSFilesStore(object):\n    def __init__(self, basedir):\n        if '://' in basedir:\n            basedir = basedir.split('://', 1)[1]\n        self.basedir = basedir\n        self._mkdir(self.basedir)\n        self.created_directories = defaultdict(set)\n\n    def persist_file(self, path, buf, info, meta=None, headers=None):\n        absolute_path = self._get_filesystem_path(path)\n        self._mkdir(os.path.dirname(absolute_path), info)\n        with open(absolute_path, 'wb') as f:\n            f.write(buf.getvalue())\n\n    def stat_file(self, path, info):\n        absolute_path = self._get_filesystem_path(path)\n        try:\n            last_modified = os.path.getmtime(absolute_path)\n        except os.error:\n            return {}\n\n        with open(absolute_path, 'rb') as f:\n            checksum = md5sum(f)\n\n        return {'last_modified': last_modified, 'checksum': checksum}\n\n    def _get_filesystem_path(self, path):\n        path_comps = path.split('/')\n        return os.path.join(self.basedir, *path_comps)\n\n    def _mkdir(self, dirname, domain=None):\n        seen = self.created_directories[domain] if domain else set()\n        if dirname not in seen:\n            if not os.path.exists(dirname):\n                os.makedirs(dirname)\n            seen.add(dirname)\n\n\nclass S3FilesStore(object):\n    AWS_ACCESS_KEY_ID = None\n    AWS_SECRET_ACCESS_KEY = None\n    AWS_ENDPOINT_URL = None\n    AWS_REGION_NAME = None\n    AWS_USE_SSL = None\n    AWS_VERIFY = None\n\n    POLICY = 'private'  # Overriden from settings.FILES_STORE_S3_ACL in\n                        # FilesPipeline.from_settings.\n    HEADERS = {\n        'Cache-Control': 'max-age=172800',\n    }\n\n    def __init__(self, uri):\n        self.is_botocore = is_botocore()\n        if self.is_botocore:\n            import botocore.session\n            session = botocore.session.get_session()\n            self.s3_client = session.create_client(\n                's3',\n                aws_access_key_id=self.AWS_ACCESS_KEY_ID,\n                aws_secret_access_key=self.AWS_SECRET_ACCESS_KEY,\n                endpoint_url=self.AWS_ENDPOINT_URL,\n                region_name=self.AWS_REGION_NAME,\n                use_ssl=self.AWS_USE_SSL,\n                verify=self.AWS_VERIFY\n            )\n        else:\n            from boto.s3.connection import S3Connection\n            self.S3Connection = S3Connection\n        assert uri.startswith('s3://')\n        self.bucket, self.prefix = uri[5:].split('/', 1)\n\n    def stat_file(self, path, info):\n        def _onsuccess(boto_key):\n            if self.is_botocore:\n                checksum = boto_key['ETag'].strip('\"')\n                last_modified = boto_key['LastModified']\n                modified_stamp = time.mktime(last_modified.timetuple())\n            else:\n                checksum = boto_key.etag.strip('\"')\n                last_modified = boto_key.last_modified\n                modified_tuple = parsedate_tz(last_modified)\n                modified_stamp = int(mktime_tz(modified_tuple))\n            return {'checksum': checksum, 'last_modified': modified_stamp}\n\n        return self._get_boto_key(path).addCallback(_onsuccess)\n\n    def _get_boto_bucket(self):\n        # disable ssl (is_secure=False) because of this python bug:\n        # https://bugs.python.org/issue5103\n        c = self.S3Connection(self.AWS_ACCESS_KEY_ID, self.AWS_SECRET_ACCESS_KEY, is_secure=False)\n        return c.get_bucket(self.bucket, validate=False)\n\n    def _get_boto_key(self, path):\n        key_name = '%s%s' % (self.prefix, path)\n        if self.is_botocore:\n            return threads.deferToThread(\n                self.s3_client.head_object,\n                Bucket=self.bucket,\n                Key=key_name)\n        else:\n            b = self._get_boto_bucket()\n            return threads.deferToThread(b.get_key, key_name)\n\n    def persist_file(self, path, buf, info, meta=None, headers=None):\n        \"\"\"Upload file to S3 storage\"\"\"\n        key_name = '%s%s' % (self.prefix, path)\n        buf.seek(0)\n        if self.is_botocore:\n            extra = self._headers_to_botocore_kwargs(self.HEADERS)\n            if headers:\n                extra.update(self._headers_to_botocore_kwargs(headers))\n            return threads.deferToThread(\n                self.s3_client.put_object,\n                Bucket=self.bucket,\n                Key=key_name,\n                Body=buf,\n                Metadata={k: str(v) for k, v in six.iteritems(meta or {})},\n                ACL=self.POLICY,\n                **extra)\n        else:\n            b = self._get_boto_bucket()\n            k = b.new_key(key_name)\n            if meta:\n                for metakey, metavalue in six.iteritems(meta):\n                    k.set_metadata(metakey, str(metavalue))\n            h = self.HEADERS.copy()\n            if headers:\n                h.update(headers)\n            return threads.deferToThread(\n                k.set_contents_from_string, buf.getvalue(),\n                headers=h, policy=self.POLICY)\n\n    def _headers_to_botocore_kwargs(self, headers):\n        \"\"\" Convert headers to botocore keyword agruments.\n        \"\"\"\n        # This is required while we need to support both boto and botocore.\n        mapping = CaselessDict({\n            'Content-Type': 'ContentType',\n            'Cache-Control': 'CacheControl',\n            'Content-Disposition': 'ContentDisposition',\n            'Content-Encoding': 'ContentEncoding',\n            'Content-Language': 'ContentLanguage',\n            'Content-Length': 'ContentLength',\n            'Content-MD5': 'ContentMD5',\n            'Expires': 'Expires',\n            'X-Amz-Grant-Full-Control': 'GrantFullControl',\n            'X-Amz-Grant-Read': 'GrantRead',\n            'X-Amz-Grant-Read-ACP': 'GrantReadACP',\n            'X-Amz-Grant-Write-ACP': 'GrantWriteACP',\n        })\n        extra = {}\n        for key, value in six.iteritems(headers):\n            try:\n                kwarg = mapping[key]\n            except KeyError:\n                raise TypeError(\n                    'Header \"%s\" is not supported by botocore' % key)\n            else:\n                extra[kwarg] = value\n        return extra\n\n\nclass GCSFilesStore(object):\n\n    GCS_PROJECT_ID = None\n\n    CACHE_CONTROL = 'max-age=172800'\n\n    # The bucket's default object ACL will be applied to the object.\n    # Overriden from settings.FILES_STORE_GCS_ACL in FilesPipeline.from_settings.\n    POLICY = None\n\n    def __init__(self, uri):\n        from google.cloud import storage\n        client = storage.Client(project=self.GCS_PROJECT_ID)\n        bucket, prefix = uri[5:].split('/', 1)\n        self.bucket = client.bucket(bucket)\n        self.prefix = prefix\n\n    def stat_file(self, path, info):\n        def _onsuccess(blob):\n            if blob:\n                checksum = blob.md5_hash\n                last_modified = time.mktime(blob.updated.timetuple())\n                return {'checksum': checksum, 'last_modified': last_modified}\n            else:\n                return {}\n\n        return threads.deferToThread(self.bucket.get_blob, path).addCallback(_onsuccess)\n\n    def _get_content_type(self, headers):\n        if headers and 'Content-Type' in headers:\n            return headers['Content-Type']\n        else:\n            return 'application/octet-stream'\n\n    def persist_file(self, path, buf, info, meta=None, headers=None):\n        blob = self.bucket.blob(self.prefix + path)\n        blob.cache_control = self.CACHE_CONTROL\n        blob.metadata = {k: str(v) for k, v in six.iteritems(meta or {})}\n        return threads.deferToThread(\n            blob.upload_from_string,\n            data=buf.getvalue(),\n            content_type=self._get_content_type(headers),\n            predefined_acl=self.POLICY\n        )\n\n\nclass FilesPipeline(MediaPipeline):\n    \"\"\"Abstract pipeline that implement the file downloading\n\n    This pipeline tries to minimize network transfers and file processing,\n    doing stat of the files and determining if file is new, uptodate or\n    expired.\n\n    ``new`` files are those that pipeline never processed and needs to be\n        downloaded from supplier site the first time.\n\n    ``uptodate`` files are the ones that the pipeline processed and are still\n        valid files.\n\n    ``expired`` files are those that pipeline already processed but the last\n        modification was made long time ago, so a reprocessing is recommended to\n        refresh it in case of change.\n\n    \"\"\"\n\n    MEDIA_NAME = \"file\"\n    EXPIRES = 90\n    STORE_SCHEMES = {\n        '': FSFilesStore,\n        'file': FSFilesStore,\n        's3': S3FilesStore,\n        'gs': GCSFilesStore,\n    }\n    DEFAULT_FILES_URLS_FIELD = 'file_urls'\n    DEFAULT_FILES_RESULT_FIELD = 'files'\n\n    def __init__(self, store_uri, download_func=None, settings=None):\n        if not store_uri:\n            raise NotConfigured\n\n        if isinstance(settings, dict) or settings is None:\n            settings = Settings(settings)\n\n        cls_name = \"FilesPipeline\"\n        self.store = self._get_store(store_uri)\n        resolve = functools.partial(self._key_for_pipe,\n                                    base_class_name=cls_name,\n                                    settings=settings)\n        self.expires = settings.getint(\n            resolve('FILES_EXPIRES'), self.EXPIRES\n        )\n        if not hasattr(self, \"FILES_URLS_FIELD\"):\n            self.FILES_URLS_FIELD = self.DEFAULT_FILES_URLS_FIELD\n        if not hasattr(self, \"FILES_RESULT_FIELD\"):\n            self.FILES_RESULT_FIELD = self.DEFAULT_FILES_RESULT_FIELD\n        self.files_urls_field = settings.get(\n            resolve('FILES_URLS_FIELD'), self.FILES_URLS_FIELD\n        )\n        self.files_result_field = settings.get(\n            resolve('FILES_RESULT_FIELD'), self.FILES_RESULT_FIELD\n        )\n\n        super(FilesPipeline, self).__init__(download_func=download_func, settings=settings)\n\n    @classmethod\n    def from_settings(cls, settings):\n        s3store = cls.STORE_SCHEMES['s3']\n        s3store.AWS_ACCESS_KEY_ID = settings['AWS_ACCESS_KEY_ID']\n        s3store.AWS_SECRET_ACCESS_KEY = settings['AWS_SECRET_ACCESS_KEY']\n        s3store.AWS_ENDPOINT_URL = settings['AWS_ENDPOINT_URL']\n        s3store.AWS_REGION_NAME = settings['AWS_REGION_NAME']\n        s3store.AWS_USE_SSL = settings['AWS_USE_SSL']\n        s3store.AWS_VERIFY = settings['AWS_VERIFY']\n        s3store.POLICY = settings['FILES_STORE_S3_ACL']\n\n        gcs_store = cls.STORE_SCHEMES['gs']\n        gcs_store.GCS_PROJECT_ID = settings['GCS_PROJECT_ID']\n        gcs_store.POLICY = settings['FILES_STORE_GCS_ACL'] or None\n\n        store_uri = settings['FILES_STORE']\n        return cls(store_uri, settings=settings)\n\n    def _get_store(self, uri):\n        if os.path.isabs(uri):  # to support win32 paths like: C:\\\\some\\dir\n            scheme = 'file'\n        else:\n            scheme = urlparse(uri).scheme\n        store_cls = self.STORE_SCHEMES[scheme]\n        return store_cls(uri)\n\n    def media_to_download(self, request, info):\n        def _onsuccess(result):\n            if not result:\n                return  # returning None force download\n\n            last_modified = result.get('last_modified', None)\n            if not last_modified:\n                return  # returning None force download\n\n            age_seconds = time.time() - last_modified\n            age_days = age_seconds / 60 / 60 / 24\n            if age_days > self.expires:\n                return  # returning None force download\n\n            referer = referer_str(request)\n            logger.debug(\n                'File (uptodate): Downloaded %(medianame)s from %(request)s '\n                'referred in <%(referer)s>',\n                {'medianame': self.MEDIA_NAME, 'request': request,\n                 'referer': referer},\n                extra={'spider': info.spider}\n            )\n            self.inc_stats(info.spider, 'uptodate')\n\n            checksum = result.get('checksum', None)\n            return {'url': request.url, 'path': path, 'checksum': checksum}\n\n        path = self.file_path(request, info=info)\n        dfd = defer.maybeDeferred(self.store.stat_file, path, info)\n        dfd.addCallbacks(_onsuccess, lambda _: None)\n        dfd.addErrback(\n            lambda f:\n            logger.error(self.__class__.__name__ + '.store.stat_file',\n                         exc_info=failure_to_exc_info(f),\n                         extra={'spider': info.spider})\n        )\n        return dfd\n\n    def media_failed(self, failure, request, info):\n        if not isinstance(failure.value, IgnoreRequest):\n            referer = referer_str(request)\n            logger.warning(\n                'File (unknown-error): Error downloading %(medianame)s from '\n                '%(request)s referred in <%(referer)s>: %(exception)s',\n                {'medianame': self.MEDIA_NAME, 'request': request,\n                 'referer': referer, 'exception': failure.value},\n                extra={'spider': info.spider}\n            )\n\n        raise FileException\n\n    def media_downloaded(self, response, request, info):\n        referer = referer_str(request)\n\n        if response.status != 200:\n            logger.warning(\n                'File (code: %(status)s): Error downloading file from '\n                '%(request)s referred in <%(referer)s>',\n                {'status': response.status,\n                 'request': request, 'referer': referer},\n                extra={'spider': info.spider}\n            )\n            raise FileException('download-error')\n\n        if not response.body:\n            logger.warning(\n                'File (empty-content): Empty file from %(request)s referred '\n                'in <%(referer)s>: no-content',\n                {'request': request, 'referer': referer},\n                extra={'spider': info.spider}\n            )\n            raise FileException('empty-content')\n\n        status = 'cached' if 'cached' in response.flags else 'downloaded'\n        logger.debug(\n            'File (%(status)s): Downloaded file from %(request)s referred in '\n            '<%(referer)s>',\n            {'status': status, 'request': request, 'referer': referer},\n            extra={'spider': info.spider}\n        )\n        self.inc_stats(info.spider, status)\n\n        try:\n            path = self.file_path(request, response=response, info=info)\n            checksum = self.file_downloaded(response, request, info)\n        except FileException as exc:\n            logger.warning(\n                'File (error): Error processing file from %(request)s '\n                'referred in <%(referer)s>: %(errormsg)s',\n                {'request': request, 'referer': referer, 'errormsg': str(exc)},\n                extra={'spider': info.spider}, exc_info=True\n            )\n            raise\n        except Exception as exc:\n            logger.error(\n                'File (unknown-error): Error processing file from %(request)s '\n                'referred in <%(referer)s>',\n                {'request': request, 'referer': referer},\n                exc_info=True, extra={'spider': info.spider}\n            )\n            raise FileException(str(exc))\n\n        return {'url': request.url, 'path': path, 'checksum': checksum}\n\n    def inc_stats(self, spider, status):\n        spider.crawler.stats.inc_value('file_count', spider=spider)\n        spider.crawler.stats.inc_value('file_status_count/%s' % status, spider=spider)\n\n    ### Overridable Interface\n    def get_media_requests(self, item, info):\n        return [Request(x) for x in item.get(self.files_urls_field, [])]\n\n    def file_downloaded(self, response, request, info):\n        path = self.file_path(request, response=response, info=info)\n        buf = BytesIO(response.body)\n        checksum = md5sum(buf)\n        buf.seek(0)\n        self.store.persist_file(path, buf, info)\n        return checksum\n\n    def item_completed(self, results, item, info):\n        if isinstance(item, dict) or self.files_result_field in item.fields:\n            item[self.files_result_field] = [x for ok, x in results if ok]\n        return item\n\n    def file_path(self, request, response=None, info=None):\n        media_guid = hashlib.sha1(to_bytes(request.url)).hexdigest()\n        media_ext = os.path.splitext(request.url)[1]\n        return 'full/%s%s' % (media_guid, media_ext)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/pipelines/images.py",
    "content": "\"\"\"\nImages Pipeline\n\nSee documentation in topics/media-pipeline.rst\n\"\"\"\nimport functools\nimport hashlib\nimport six\n\ntry:\n    from cStringIO import StringIO as BytesIO\nexcept ImportError:\n    from io import BytesIO\n\nfrom PIL import Image\n\nfrom scrapy.utils.misc import md5sum\nfrom scrapy.utils.python import to_bytes\nfrom scrapy.http import Request\nfrom scrapy.settings import Settings\nfrom scrapy.exceptions import DropItem\n#TODO: from scrapy.pipelines.media import MediaPipeline\nfrom scrapy.pipelines.files import FileException, FilesPipeline\n\n\nclass NoimagesDrop(DropItem):\n    \"\"\"Product with no images exception\"\"\"\n\n\nclass ImageException(FileException):\n    \"\"\"General image error exception\"\"\"\n\n\nclass ImagesPipeline(FilesPipeline):\n    \"\"\"Abstract pipeline that implement the image thumbnail generation logic\n\n    \"\"\"\n\n    MEDIA_NAME = 'image'\n\n    # Uppercase attributes kept for backward compatibility with code that subclasses\n    # ImagesPipeline. They may be overridden by settings.\n    MIN_WIDTH = 0\n    MIN_HEIGHT = 0\n    EXPIRES = 90\n    THUMBS = {}\n    DEFAULT_IMAGES_URLS_FIELD = 'image_urls'\n    DEFAULT_IMAGES_RESULT_FIELD = 'images'\n\n    def __init__(self, store_uri, download_func=None, settings=None):\n        super(ImagesPipeline, self).__init__(store_uri, settings=settings,\n                                             download_func=download_func)\n\n        if isinstance(settings, dict) or settings is None:\n            settings = Settings(settings)\n\n        resolve = functools.partial(self._key_for_pipe,\n                                    base_class_name=\"ImagesPipeline\",\n                                    settings=settings)\n        self.expires = settings.getint(\n            resolve(\"IMAGES_EXPIRES\"), self.EXPIRES\n        )\n\n        if not hasattr(self, \"IMAGES_RESULT_FIELD\"):\n            self.IMAGES_RESULT_FIELD = self.DEFAULT_IMAGES_RESULT_FIELD\n        if not hasattr(self, \"IMAGES_URLS_FIELD\"):\n            self.IMAGES_URLS_FIELD = self.DEFAULT_IMAGES_URLS_FIELD\n\n        self.images_urls_field = settings.get(\n            resolve('IMAGES_URLS_FIELD'),\n            self.IMAGES_URLS_FIELD\n        )\n        self.images_result_field = settings.get(\n            resolve('IMAGES_RESULT_FIELD'),\n            self.IMAGES_RESULT_FIELD\n        )\n        self.min_width = settings.getint(\n            resolve('IMAGES_MIN_WIDTH'), self.MIN_WIDTH\n        )\n        self.min_height = settings.getint(\n            resolve('IMAGES_MIN_HEIGHT'), self.MIN_HEIGHT\n        )\n        self.thumbs = settings.get(\n            resolve('IMAGES_THUMBS'), self.THUMBS\n        )\n\n    @classmethod\n    def from_settings(cls, settings):\n        s3store = cls.STORE_SCHEMES['s3']\n        s3store.AWS_ACCESS_KEY_ID = settings['AWS_ACCESS_KEY_ID']\n        s3store.AWS_SECRET_ACCESS_KEY = settings['AWS_SECRET_ACCESS_KEY']\n        s3store.AWS_ENDPOINT_URL = settings['AWS_ENDPOINT_URL']\n        s3store.AWS_REGION_NAME = settings['AWS_REGION_NAME']\n        s3store.AWS_USE_SSL = settings['AWS_USE_SSL']\n        s3store.AWS_VERIFY = settings['AWS_VERIFY']\n        s3store.POLICY = settings['IMAGES_STORE_S3_ACL']\n\n        gcs_store = cls.STORE_SCHEMES['gs']\n        gcs_store.GCS_PROJECT_ID = settings['GCS_PROJECT_ID']\n        gcs_store.POLICY = settings['IMAGES_STORE_GCS_ACL'] or None\n\n        store_uri = settings['IMAGES_STORE']\n        return cls(store_uri, settings=settings)\n\n    def file_downloaded(self, response, request, info):\n        return self.image_downloaded(response, request, info)\n\n    def image_downloaded(self, response, request, info):\n        checksum = None\n        for path, image, buf in self.get_images(response, request, info):\n            if checksum is None:\n                buf.seek(0)\n                checksum = md5sum(buf)\n            width, height = image.size\n            self.store.persist_file(\n                path, buf, info,\n                meta={'width': width, 'height': height},\n                headers={'Content-Type': 'image/jpeg'})\n        return checksum\n\n    def get_images(self, response, request, info):\n        path = self.file_path(request, response=response, info=info)\n        orig_image = Image.open(BytesIO(response.body))\n\n        width, height = orig_image.size\n        if width < self.min_width or height < self.min_height:\n            raise ImageException(\"Image too small (%dx%d < %dx%d)\" %\n                                 (width, height, self.min_width, self.min_height))\n\n        image, buf = self.convert_image(orig_image)\n        yield path, image, buf\n\n        for thumb_id, size in six.iteritems(self.thumbs):\n            thumb_path = self.thumb_path(request, thumb_id, response=response, info=info)\n            thumb_image, thumb_buf = self.convert_image(image, size)\n            yield thumb_path, thumb_image, thumb_buf\n\n    def convert_image(self, image, size=None):\n        if image.format == 'PNG' and image.mode == 'RGBA':\n            background = Image.new('RGBA', image.size, (255, 255, 255))\n            background.paste(image, image)\n            image = background.convert('RGB')\n        elif image.mode == 'P':\n            image = image.convert(\"RGBA\")\n            background = Image.new('RGBA', image.size, (255, 255, 255))\n            background.paste(image, image)\n            image = background.convert('RGB')\n        elif image.mode != 'RGB':\n            image = image.convert('RGB')\n\n        if size:\n            image = image.copy()\n            image.thumbnail(size, Image.ANTIALIAS)\n\n        buf = BytesIO()\n        image.save(buf, 'JPEG')\n        return image, buf\n\n    def get_media_requests(self, item, info):\n        return [Request(x) for x in item.get(self.images_urls_field, [])]\n\n    def item_completed(self, results, item, info):\n        if isinstance(item, dict) or self.images_result_field in item.fields:\n            item[self.images_result_field] = [x for ok, x in results if ok]\n        return item\n\n    def file_path(self, request, response=None, info=None):\n        image_guid = hashlib.sha1(to_bytes(request.url)).hexdigest()\n        return 'full/%s.jpg' % (image_guid)\n\n    def thumb_path(self, request, thumb_id, response=None, info=None):\n        thumb_guid = hashlib.sha1(to_bytes(request.url)).hexdigest()\n        return 'thumbs/%s/%s.jpg' % (thumb_id, thumb_guid)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/pipelines/media.py",
    "content": "from __future__ import print_function\n\nimport functools\nimport logging\nfrom collections import defaultdict\nfrom twisted.internet.defer import Deferred, DeferredList, _DefGen_Return\nfrom twisted.python.failure import Failure\n\nfrom scrapy.settings import Settings\nfrom scrapy.utils.datatypes import SequenceExclude\nfrom scrapy.utils.defer import mustbe_deferred, defer_result\nfrom scrapy.utils.request import request_fingerprint\nfrom scrapy.utils.misc import arg_to_iter\nfrom scrapy.utils.log import failure_to_exc_info\n\nlogger = logging.getLogger(__name__)\n\n\nclass MediaPipeline(object):\n\n    LOG_FAILED_RESULTS = True\n\n    class SpiderInfo(object):\n        def __init__(self, spider):\n            self.spider = spider\n            self.downloading = set()\n            self.downloaded = {}\n            self.waiting = defaultdict(list)\n\n    def __init__(self, download_func=None, settings=None):\n        self.download_func = download_func\n\n        if isinstance(settings, dict) or settings is None:\n            settings = Settings(settings)\n        resolve = functools.partial(self._key_for_pipe,\n                                    base_class_name=\"MediaPipeline\",\n                                    settings=settings)\n        self.allow_redirects = settings.getbool(\n            resolve('MEDIA_ALLOW_REDIRECTS'), False\n        )\n        self._handle_statuses(self.allow_redirects)\n\n    def _handle_statuses(self, allow_redirects):\n        self.handle_httpstatus_list = None\n        if allow_redirects:\n            self.handle_httpstatus_list = SequenceExclude(range(300, 400))\n\n    def _key_for_pipe(self, key, base_class_name=None,\n                      settings=None):\n        \"\"\"\n        >>> MediaPipeline()._key_for_pipe(\"IMAGES\")\n        'IMAGES'\n        >>> class MyPipe(MediaPipeline):\n        ...     pass\n        >>> MyPipe()._key_for_pipe(\"IMAGES\", base_class_name=\"MediaPipeline\")\n        'MYPIPE_IMAGES'\n        \"\"\"\n        class_name = self.__class__.__name__\n        formatted_key = \"{}_{}\".format(class_name.upper(), key)\n        if class_name == base_class_name or not base_class_name \\\n            or (settings and not settings.get(formatted_key)):\n            return key\n        return formatted_key\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        try:\n            pipe = cls.from_settings(crawler.settings)\n        except AttributeError:\n            pipe = cls()\n        pipe.crawler = crawler\n        return pipe\n\n    def open_spider(self, spider):\n        self.spiderinfo = self.SpiderInfo(spider)\n\n    def process_item(self, item, spider):\n        info = self.spiderinfo\n        requests = arg_to_iter(self.get_media_requests(item, info))\n        dlist = [self._process_request(r, info) for r in requests]\n        dfd = DeferredList(dlist, consumeErrors=1)\n        return dfd.addCallback(self.item_completed, item, info)\n\n    def _process_request(self, request, info):\n        fp = request_fingerprint(request)\n        cb = request.callback or (lambda _: _)\n        eb = request.errback\n        request.callback = None\n        request.errback = None\n\n        # Return cached result if request was already seen\n        if fp in info.downloaded:\n            return defer_result(info.downloaded[fp]).addCallbacks(cb, eb)\n\n        # Otherwise, wait for result\n        wad = Deferred().addCallbacks(cb, eb)\n        info.waiting[fp].append(wad)\n\n        # Check if request is downloading right now to avoid doing it twice\n        if fp in info.downloading:\n            return wad\n\n        # Download request checking media_to_download hook output first\n        info.downloading.add(fp)\n        dfd = mustbe_deferred(self.media_to_download, request, info)\n        dfd.addCallback(self._check_media_to_download, request, info)\n        dfd.addBoth(self._cache_result_and_execute_waiters, fp, info)\n        dfd.addErrback(lambda f: logger.error(\n            f.value, exc_info=failure_to_exc_info(f), extra={'spider': info.spider})\n        )\n        return dfd.addBoth(lambda _: wad)  # it must return wad at last\n\n    def _modify_media_request(self, request):\n        if self.handle_httpstatus_list:\n            request.meta['handle_httpstatus_list'] = self.handle_httpstatus_list\n        else:\n            request.meta['handle_httpstatus_all'] = True\n\n    def _check_media_to_download(self, result, request, info):\n        if result is not None:\n            return result\n        if self.download_func:\n            # this ugly code was left only to support tests. TODO: remove\n            dfd = mustbe_deferred(self.download_func, request, info.spider)\n            dfd.addCallbacks(\n                callback=self.media_downloaded, callbackArgs=(request, info),\n                errback=self.media_failed, errbackArgs=(request, info))\n        else:\n            self._modify_media_request(request)\n            dfd = self.crawler.engine.download(request, info.spider)\n            dfd.addCallbacks(\n                callback=self.media_downloaded, callbackArgs=(request, info),\n                errback=self.media_failed, errbackArgs=(request, info))\n        return dfd\n\n    def _cache_result_and_execute_waiters(self, result, fp, info):\n        if isinstance(result, Failure):\n            # minimize cached information for failure\n            result.cleanFailure()\n            result.frames = []\n            result.stack = None\n\n            # This code fixes a memory leak by avoiding to keep references to\n            # the Request and Response objects on the Media Pipeline cache.\n            #\n            # Twisted inline callbacks pass return values using the function\n            # twisted.internet.defer.returnValue, which encapsulates the return\n            # value inside a _DefGen_Return base exception.\n            #\n            # What happens when the media_downloaded callback raises another\n            # exception, for example a FileException('download-error') when\n            # the Response status code is not 200 OK, is that it stores the\n            # _DefGen_Return exception on the FileException context.\n            #\n            # To avoid keeping references to the Response and therefore Request\n            # objects on the Media Pipeline cache, we should wipe the context of\n            # the exception encapsulated by the Twisted Failure when its a\n            # _DefGen_Return instance.\n            #\n            # This problem does not occur in Python 2.7 since we don't have\n            # Exception Chaining (https://www.python.org/dev/peps/pep-3134/).\n            context = getattr(result.value, '__context__', None)\n            if isinstance(context, _DefGen_Return):\n                setattr(result.value, '__context__', None)\n\n        info.downloading.remove(fp)\n        info.downloaded[fp] = result  # cache result\n        for wad in info.waiting.pop(fp):\n            defer_result(result).chainDeferred(wad)\n\n    ### Overridable Interface\n    def media_to_download(self, request, info):\n        \"\"\"Check request before starting download\"\"\"\n        pass\n\n    def get_media_requests(self, item, info):\n        \"\"\"Returns the media requests to download\"\"\"\n        pass\n\n    def media_downloaded(self, response, request, info):\n        \"\"\"Handler for success downloads\"\"\"\n        return response\n\n    def media_failed(self, failure, request, info):\n        \"\"\"Handler for failed downloads\"\"\"\n        return failure\n\n    def item_completed(self, results, item, info):\n        \"\"\"Called per item when all media requests has been processed\"\"\"\n        if self.LOG_FAILED_RESULTS:\n            for ok, value in results:\n                if not ok:\n                    logger.error(\n                        '%(class)s found errors processing %(item)s',\n                        {'class': self.__class__.__name__, 'item': item},\n                        exc_info=failure_to_exc_info(value),\n                        extra={'spider': info.spider}\n                    )\n        return item\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/pqueues.py",
    "content": "import hashlib\nimport logging\nfrom collections import namedtuple\n\nfrom queuelib import PriorityQueue\n\nfrom scrapy.utils.reqser import request_to_dict, request_from_dict\n\n\nlogger = logging.getLogger(__name__)\n\n\ndef _path_safe(text):\n    \"\"\"\n    Return a filesystem-safe version of a string ``text``\n\n    >>> _path_safe('simple.org').startswith('simple.org')\n    True\n    >>> _path_safe('dash-underscore_.org').startswith('dash-underscore_.org')\n    True\n    >>> _path_safe('some@symbol?').startswith('some_symbol_')\n    True\n    \"\"\"\n    pathable_slot = \"\".join([c if c.isalnum() or c in '-._' else '_'\n                             for c in text])\n    # as we replace some letters we can get collision for different slots\n    # add we add unique part\n    unique_slot = hashlib.md5(text.encode('utf8')).hexdigest()\n    return '-'.join([pathable_slot, unique_slot])\n\n\nclass _Priority(namedtuple(\"_Priority\", [\"priority\", \"slot\"])):\n    \"\"\" Slot-specific priority. It is a hack - ``(priority, slot)`` tuple\n    which can be used instead of int priorities in queues:\n\n    * they are ordered in the same way - order is still by priority value,\n      min(prios) works;\n    * str(p) representation is guaranteed to be different when slots\n      are different - this is important because str(p) is used to create\n      queue files on disk;\n    * they have readable str(p) representation which is safe\n      to use as a file name.\n    \"\"\"\n    __slots__ = ()\n\n    def __str__(self):\n        return '%s_%s' % (self.priority, _path_safe(str(self.slot)))\n\n\nclass _SlotPriorityQueues(object):\n    \"\"\" Container for multiple priority queues. \"\"\"\n    def __init__(self, pqfactory, slot_startprios=None):\n        \"\"\"\n        ``pqfactory`` is a factory for creating new PriorityQueues.\n        It must be a function which accepts a single optional ``startprios``\n        argument, with a list of priorities to create queues for.\n\n        ``slot_startprios`` is a ``{slot: startprios}`` dict.\n        \"\"\"\n        self.pqfactory = pqfactory\n        self.pqueues = {}  # slot -> priority queue\n        for slot, startprios in (slot_startprios or {}).items():\n            self.pqueues[slot] = self.pqfactory(startprios)\n\n    def pop_slot(self, slot):\n        \"\"\" Pop an object from a priority queue for this slot \"\"\"\n        queue = self.pqueues[slot]\n        request = queue.pop()\n        if len(queue) == 0:\n            del self.pqueues[slot]\n        return request\n\n    def push_slot(self, slot, obj, priority):\n        \"\"\" Push an object to a priority queue for this slot \"\"\"\n        if slot not in self.pqueues:\n            self.pqueues[slot] = self.pqfactory()\n        queue = self.pqueues[slot]\n        queue.push(obj, priority)\n\n    def close(self):\n        active = {slot: queue.close()\n                  for slot, queue in self.pqueues.items()}\n        self.pqueues.clear()\n        return active\n\n    def __len__(self):\n        return sum(len(x) for x in self.pqueues.values()) if self.pqueues else 0\n\n    def __contains__(self, slot):\n        return slot in self.pqueues\n\n\nclass ScrapyPriorityQueue(PriorityQueue):\n    \"\"\"\n    PriorityQueue which works with scrapy.Request instances and\n    can optionally convert them to/from dicts before/after putting to a queue.\n    \"\"\"\n    def __init__(self, crawler, qfactory, startprios=(), serialize=False):\n        super(ScrapyPriorityQueue, self).__init__(qfactory, startprios)\n        self.serialize = serialize\n        self.spider = crawler.spider\n\n    @classmethod\n    def from_crawler(cls, crawler, qfactory, startprios=(), serialize=False):\n        return cls(crawler, qfactory, startprios, serialize)\n\n    def push(self, request, priority=0):\n        if self.serialize:\n            request = request_to_dict(request, self.spider)\n        super(ScrapyPriorityQueue, self).push(request, priority)\n\n    def pop(self):\n        request = super(ScrapyPriorityQueue, self).pop()\n        if request and self.serialize:\n            request = request_from_dict(request, self.spider)\n        return request\n\n\nclass DownloaderInterface(object):\n\n    def __init__(self, crawler):\n        self.downloader = crawler.engine.downloader\n\n    def stats(self, possible_slots):\n        return [(self._active_downloads(slot), slot)\n                for slot in possible_slots]\n\n    def get_slot_key(self, request):\n        return self.downloader._get_slot_key(request, None)\n\n    def _active_downloads(self, slot):\n        \"\"\" Return a number of requests in a Downloader for a given slot \"\"\"\n        if slot not in self.downloader.slots:\n            return 0\n        return len(self.downloader.slots[slot].active)\n\n\nclass DownloaderAwarePriorityQueue(object):\n    \"\"\" PriorityQueue which takes Downlaoder activity in account:\n    domains (slots) with the least amount of active downloads are dequeued\n    first.\n    \"\"\"\n\n    @classmethod\n    def from_crawler(cls, crawler, qfactory, slot_startprios=None, serialize=False):\n        return cls(crawler, qfactory, slot_startprios, serialize)\n\n    def __init__(self, crawler, qfactory, slot_startprios=None, serialize=False):\n        if crawler.settings.getint('CONCURRENT_REQUESTS_PER_IP') != 0:\n            raise ValueError('\"%s\" does not support CONCURRENT_REQUESTS_PER_IP'\n                             % (self.__class__,))\n\n        if slot_startprios and not isinstance(slot_startprios, dict):\n            raise ValueError(\"DownloaderAwarePriorityQueue accepts \"\n                             \"``slot_startprios`` as a dict; %r instance \"\n                             \"is passed. Most likely, it means the state is\"\n                             \"created by an incompatible priority queue. \"\n                             \"Only a crawl started with the same priority \"\n                             \"queue class can be resumed.\" %\n                             slot_startprios.__class__)\n\n        slot_startprios = {\n            slot: [_Priority(p, slot) for p in startprios]\n            for slot, startprios in (slot_startprios or {}).items()}\n\n        def pqfactory(startprios=()):\n            return ScrapyPriorityQueue(crawler, qfactory, startprios, serialize)\n        self._slot_pqueues = _SlotPriorityQueues(pqfactory, slot_startprios)\n        self.serialize = serialize\n        self._downloader_interface = DownloaderInterface(crawler)\n\n    def pop(self):\n        stats = self._downloader_interface.stats(self._slot_pqueues.pqueues)\n\n        if not stats:\n            return\n\n        slot = min(stats)[1]\n        request = self._slot_pqueues.pop_slot(slot)\n        return request\n\n    def push(self, request, priority):\n        slot = self._downloader_interface.get_slot_key(request)\n        priority_slot = _Priority(priority=priority, slot=slot)\n        self._slot_pqueues.push_slot(slot, request, priority_slot)\n\n    def close(self):\n        active = self._slot_pqueues.close()\n        return {slot: [p.priority for p in startprios]\n                for slot, startprios in active.items()}\n\n    def __len__(self):\n        return len(self._slot_pqueues)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/resolver.py",
    "content": "from twisted.internet import defer\nfrom twisted.internet.base import ThreadedResolver\n\nfrom scrapy.utils.datatypes import LocalCache\n\n# TODO: cache misses\n\ndnscache = LocalCache(10000)\n\nclass CachingThreadedResolver(ThreadedResolver):\n    def __init__(self, reactor, cache_size, timeout):\n        super(CachingThreadedResolver, self).__init__(reactor)\n        dnscache.limit = cache_size\n        self.timeout = timeout\n\n    def getHostByName(self, name, timeout=None):\n        if name in dnscache:\n            return defer.succeed(dnscache[name])\n        # in Twisted<=16.6, getHostByName() is always called with\n        # a default timeout of 60s (actually passed as (1, 3, 11, 45) tuple),\n        # so the input argument above is simply overridden\n        # to enforce Scrapy's DNS_TIMEOUT setting's value\n        timeout = (self.timeout,)\n        d = super(CachingThreadedResolver, self).getHostByName(name, timeout)\n        if dnscache.limit:\n            d.addCallback(self._cache_result, name)\n        return d\n\n    def _cache_result(self, result, name):\n        dnscache[name] = result\n        return result\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/responsetypes.py",
    "content": "\"\"\"\nThis module implements a class which returns the appropriate Response class\nbased on different criteria.\n\"\"\"\nfrom __future__ import absolute_import\nfrom mimetypes import MimeTypes\nfrom pkgutil import get_data\nfrom io import StringIO\nimport six\n\nfrom scrapy.http import Response\nfrom scrapy.utils.misc import load_object\nfrom scrapy.utils.python import binary_is_text, to_bytes, to_native_str\n\n\nclass ResponseTypes(object):\n\n    CLASSES = {\n        'text/html': 'scrapy.http.HtmlResponse',\n        'application/atom+xml': 'scrapy.http.XmlResponse',\n        'application/rdf+xml': 'scrapy.http.XmlResponse',\n        'application/rss+xml': 'scrapy.http.XmlResponse',\n        'application/xhtml+xml': 'scrapy.http.HtmlResponse',\n        'application/vnd.wap.xhtml+xml': 'scrapy.http.HtmlResponse',\n        'application/xml': 'scrapy.http.XmlResponse',\n        'application/json': 'scrapy.http.TextResponse',\n        'application/x-json': 'scrapy.http.TextResponse',\n        'application/json-amazonui-streaming': 'scrapy.http.TextResponse',\n        'application/javascript': 'scrapy.http.TextResponse',\n        'application/x-javascript': 'scrapy.http.TextResponse',\n        'text/xml': 'scrapy.http.XmlResponse',\n        'text/*': 'scrapy.http.TextResponse',\n    }\n\n    def __init__(self):\n        self.classes = {}\n        self.mimetypes = MimeTypes()\n        mimedata = get_data('scrapy', 'mime.types').decode('utf8')\n        self.mimetypes.readfp(StringIO(mimedata))\n        for mimetype, cls in six.iteritems(self.CLASSES):\n            self.classes[mimetype] = load_object(cls)\n\n    def from_mimetype(self, mimetype):\n        \"\"\"Return the most appropriate Response class for the given mimetype\"\"\"\n        if mimetype is None:\n            return Response\n        elif mimetype in self.classes:\n            return self.classes[mimetype]\n        else:\n            basetype = \"%s/*\" % mimetype.split('/')[0]\n            return self.classes.get(basetype, Response)\n\n    def from_content_type(self, content_type, content_encoding=None):\n        \"\"\"Return the most appropriate Response class from an HTTP Content-Type\n        header \"\"\"\n        if content_encoding:\n            return Response\n        mimetype = to_native_str(content_type).split(';')[0].strip().lower()\n        return self.from_mimetype(mimetype)\n\n    def from_content_disposition(self, content_disposition):\n        try:\n            filename = to_native_str(content_disposition,\n                encoding='latin-1', errors='replace').split(';')[1].split('=')[1]\n            filename = filename.strip('\"\\'')\n            return self.from_filename(filename)\n        except IndexError:\n            return Response\n\n    def from_headers(self, headers):\n        \"\"\"Return the most appropriate Response class by looking at the HTTP\n        headers\"\"\"\n        cls = Response\n        if b'Content-Type' in headers:\n            cls = self.from_content_type(\n                content_type=headers[b'Content-type'],\n                content_encoding=headers.get(b'Content-Encoding')\n            )\n        if cls is Response and b'Content-Disposition' in headers:\n            cls = self.from_content_disposition(headers[b'Content-Disposition'])\n        return cls\n\n    def from_filename(self, filename):\n        \"\"\"Return the most appropriate Response class from a file name\"\"\"\n        mimetype, encoding = self.mimetypes.guess_type(filename)\n        if mimetype and not encoding:\n            return self.from_mimetype(mimetype)\n        else:\n            return Response\n\n    def from_body(self, body):\n        \"\"\"Try to guess the appropriate response based on the body content.\n        This method is a bit magic and could be improved in the future, but\n        it's not meant to be used except for special cases where response types\n        cannot be guess using more straightforward methods.\"\"\"\n        chunk = body[:5000]\n        chunk = to_bytes(chunk)\n        if not binary_is_text(chunk):\n            return self.from_mimetype('application/octet-stream')\n        elif b\"<html>\" in chunk.lower():\n            return self.from_mimetype('text/html')\n        elif b\"<?xml\" in chunk.lower():\n            return self.from_mimetype('text/xml')\n        else:\n            return self.from_mimetype('text')\n\n    def from_args(self, headers=None, url=None, filename=None, body=None):\n        \"\"\"Guess the most appropriate Response class based on\n        the given arguments.\"\"\"\n        cls = Response\n        if headers is not None:\n            cls = self.from_headers(headers)\n        if cls is Response and url is not None:\n            cls = self.from_filename(url)\n        if cls is Response and filename is not None:\n            cls = self.from_filename(filename)\n        if cls is Response and body is not None:\n            cls = self.from_body(body)\n        return cls\n\nresponsetypes = ResponseTypes()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/selector/__init__.py",
    "content": "\"\"\"\nSelectors\n\"\"\"\nfrom scrapy.selector.unified import *\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/selector/unified.py",
    "content": "\"\"\"\nXPath selectors based on lxml\n\"\"\"\n\nimport warnings\nfrom parsel import Selector as _ParselSelector\nfrom scrapy.utils.trackref import object_ref\nfrom scrapy.utils.python import to_bytes\nfrom scrapy.http import HtmlResponse, XmlResponse\nfrom scrapy.utils.decorators import deprecated\n\n\n__all__ = ['Selector', 'SelectorList']\n\n\ndef _st(response, st):\n    if st is None:\n        return 'xml' if isinstance(response, XmlResponse) else 'html'\n    return st\n\n\ndef _response_from_text(text, st):\n    rt = XmlResponse if st == 'xml' else HtmlResponse\n    return rt(url='about:blank', encoding='utf-8',\n              body=to_bytes(text, 'utf-8'))\n\n\nclass SelectorList(_ParselSelector.selectorlist_cls, object_ref):\n    \"\"\"\n    The :class:`SelectorList` class is a subclass of the builtin ``list``\n    class, which provides a few additional methods.\n    \"\"\"\n\n\nclass Selector(_ParselSelector, object_ref):\n    \"\"\"\n    An instance of :class:`Selector` is a wrapper over response to select\n    certain parts of its content.\n\n    ``response`` is an :class:`~scrapy.http.HtmlResponse` or an\n    :class:`~scrapy.http.XmlResponse` object that will be used for selecting\n    and extracting data.\n\n    ``text`` is a unicode string or utf-8 encoded text for cases when a\n    ``response`` isn't available. Using ``text`` and ``response`` together is\n    undefined behavior.\n\n    ``type`` defines the selector type, it can be ``\"html\"``, ``\"xml\"``\n    or ``None`` (default).\n\n    If ``type`` is ``None``, the selector automatically chooses the best type\n    based on ``response`` type (see below), or defaults to ``\"html\"`` in case it\n    is used together with ``text``.\n\n    If ``type`` is ``None`` and a ``response`` is passed, the selector type is\n    inferred from the response type as follows:\n\n    * ``\"html\"`` for :class:`~scrapy.http.HtmlResponse` type\n    * ``\"xml\"`` for :class:`~scrapy.http.XmlResponse` type\n    * ``\"html\"`` for anything else\n\n    Otherwise, if ``type`` is set, the selector type will be forced and no\n    detection will occur.\n    \"\"\"\n\n    __slots__ = ['response']\n    selectorlist_cls = SelectorList\n\n    def __init__(self, response=None, text=None, type=None, root=None, **kwargs):\n        if not(response is None or text is None):\n           raise ValueError('%s.__init__() received both response and text'\n                            % self.__class__.__name__)\n\n        st = _st(response, type or self._default_type)\n\n        if text is not None:\n            response = _response_from_text(text, st)\n\n        if response is not None:\n            text = response.text\n            kwargs.setdefault('base_url', response.url)\n\n        self.response = response\n        super(Selector, self).__init__(text=text, type=st, root=root, **kwargs)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/settings/__init__.py",
    "content": "import six\nimport json\nimport copy\nimport collections\nfrom importlib import import_module\nfrom pprint import pformat\n\nfrom scrapy.settings import default_settings\n\n\nif six.PY2:\n    MutableMapping = collections.MutableMapping\nelse:\n    MutableMapping = collections.abc.MutableMapping\n\n\nSETTINGS_PRIORITIES = {\n    'default': 0,\n    'command': 10,\n    'project': 20,\n    'spider': 30,\n    'cmdline': 40,\n}\n\n\ndef get_settings_priority(priority):\n    \"\"\"\n    Small helper function that looks up a given string priority in the\n    :attr:`~scrapy.settings.SETTINGS_PRIORITIES` dictionary and returns its\n    numerical value, or directly returns a given numerical priority.\n    \"\"\"\n    if isinstance(priority, six.string_types):\n        return SETTINGS_PRIORITIES[priority]\n    else:\n        return priority\n\n\nclass SettingsAttribute(object):\n\n    \"\"\"Class for storing data related to settings attributes.\n\n    This class is intended for internal usage, you should try Settings class\n    for settings configuration, not this one.\n    \"\"\"\n\n    def __init__(self, value, priority):\n        self.value = value\n        if isinstance(self.value, BaseSettings):\n            self.priority = max(self.value.maxpriority(), priority)\n        else:\n            self.priority = priority\n\n    def set(self, value, priority):\n        \"\"\"Sets value if priority is higher or equal than current priority.\"\"\"\n        if priority >= self.priority:\n            if isinstance(self.value, BaseSettings):\n                value = BaseSettings(value, priority=priority)\n            self.value = value\n            self.priority = priority\n\n    def __str__(self):\n        return \"<SettingsAttribute value={self.value!r} \" \\\n               \"priority={self.priority}>\".format(self=self)\n\n    __repr__ = __str__\n\n\nclass BaseSettings(MutableMapping):\n    \"\"\"\n    Instances of this class behave like dictionaries, but store priorities\n    along with their ``(key, value)`` pairs, and can be frozen (i.e. marked\n    immutable).\n\n    Key-value entries can be passed on initialization with the ``values``\n    argument, and they would take the ``priority`` level (unless ``values`` is\n    already an instance of :class:`~scrapy.settings.BaseSettings`, in which\n    case the existing priority levels will be kept).  If the ``priority``\n    argument is a string, the priority name will be looked up in\n    :attr:`~scrapy.settings.SETTINGS_PRIORITIES`. Otherwise, a specific integer\n    should be provided.\n\n    Once the object is created, new settings can be loaded or updated with the\n    :meth:`~scrapy.settings.BaseSettings.set` method, and can be accessed with\n    the square bracket notation of dictionaries, or with the\n    :meth:`~scrapy.settings.BaseSettings.get` method of the instance and its\n    value conversion variants. When requesting a stored key, the value with the\n    highest priority will be retrieved.\n    \"\"\"\n\n    def __init__(self, values=None, priority='project'):\n        self.frozen = False\n        self.attributes = {}\n        self.update(values, priority)\n\n    def __getitem__(self, opt_name):\n        if opt_name not in self:\n            return None\n        return self.attributes[opt_name].value\n\n    def __contains__(self, name):\n        return name in self.attributes\n\n    def get(self, name, default=None):\n        \"\"\"\n        Get a setting value without affecting its original type.\n\n        :param name: the setting name\n        :type name: string\n\n        :param default: the value to return if no setting is found\n        :type default: any\n        \"\"\"\n        return self[name] if self[name] is not None else default\n\n    def getbool(self, name, default=False):\n        \"\"\"\n        Get a setting value as a boolean.\n\n        ``1``, ``'1'``, `True`` and ``'True'`` return ``True``,\n        while ``0``, ``'0'``, ``False``, ``'False'`` and ``None`` return ``False``.\n\n        For example, settings populated through environment variables set to\n        ``'0'`` will return ``False`` when using this method.\n\n        :param name: the setting name\n        :type name: string\n\n        :param default: the value to return if no setting is found\n        :type default: any\n        \"\"\"\n        got = self.get(name, default)\n        try:\n            return bool(int(got))\n        except ValueError:\n            if got in (\"True\", \"true\"):\n                return True\n            if got in (\"False\", \"false\"):\n                return False\n            raise ValueError(\"Supported values for boolean settings \"\n                             \"are 0/1, True/False, '0'/'1', \"\n                             \"'True'/'False' and 'true'/'false'\")\n\n    def getint(self, name, default=0):\n        \"\"\"\n        Get a setting value as an int.\n\n        :param name: the setting name\n        :type name: string\n\n        :param default: the value to return if no setting is found\n        :type default: any\n        \"\"\"\n        return int(self.get(name, default))\n\n    def getfloat(self, name, default=0.0):\n        \"\"\"\n        Get a setting value as a float.\n\n        :param name: the setting name\n        :type name: string\n\n        :param default: the value to return if no setting is found\n        :type default: any\n        \"\"\"\n        return float(self.get(name, default))\n\n    def getlist(self, name, default=None):\n        \"\"\"\n        Get a setting value as a list. If the setting original type is a list, a\n        copy of it will be returned. If it's a string it will be split by \",\".\n\n        For example, settings populated through environment variables set to\n        ``'one,two'`` will return a list ['one', 'two'] when using this method.\n\n        :param name: the setting name\n        :type name: string\n\n        :param default: the value to return if no setting is found\n        :type default: any\n        \"\"\"\n        value = self.get(name, default or [])\n        if isinstance(value, six.string_types):\n            value = value.split(',')\n        return list(value)\n\n    def getdict(self, name, default=None):\n        \"\"\"\n        Get a setting value as a dictionary. If the setting original type is a\n        dictionary, a copy of it will be returned. If it is a string it will be\n        evaluated as a JSON dictionary. In the case that it is a\n        :class:`~scrapy.settings.BaseSettings` instance itself, it will be\n        converted to a dictionary, containing all its current settings values\n        as they would be returned by :meth:`~scrapy.settings.BaseSettings.get`,\n        and losing all information about priority and mutability.\n\n        :param name: the setting name\n        :type name: string\n\n        :param default: the value to return if no setting is found\n        :type default: any\n        \"\"\"\n        value = self.get(name, default or {})\n        if isinstance(value, six.string_types):\n            value = json.loads(value)\n        return dict(value)\n\n    def getwithbase(self, name):\n        \"\"\"Get a composition of a dictionary-like setting and its `_BASE`\n        counterpart.\n\n        :param name: name of the dictionary-like setting\n        :type name: string\n        \"\"\"\n        compbs = BaseSettings()\n        compbs.update(self[name + '_BASE'])\n        compbs.update(self[name])\n        return compbs\n\n    def getpriority(self, name):\n        \"\"\"\n        Return the current numerical priority value of a setting, or ``None`` if\n        the given ``name`` does not exist.\n\n        :param name: the setting name\n        :type name: string\n        \"\"\"\n        if name not in self:\n            return None\n        return self.attributes[name].priority\n\n    def maxpriority(self):\n        \"\"\"\n        Return the numerical value of the highest priority present throughout\n        all settings, or the numerical value for ``default`` from\n        :attr:`~scrapy.settings.SETTINGS_PRIORITIES` if there are no settings\n        stored.\n        \"\"\"\n        if len(self) > 0:\n            return max(self.getpriority(name) for name in self)\n        else:\n            return get_settings_priority('default')\n\n    def __setitem__(self, name, value):\n        self.set(name, value)\n\n    def set(self, name, value, priority='project'):\n        \"\"\"\n        Store a key/value attribute with a given priority.\n\n        Settings should be populated *before* configuring the Crawler object\n        (through the :meth:`~scrapy.crawler.Crawler.configure` method),\n        otherwise they won't have any effect.\n\n        :param name: the setting name\n        :type name: string\n\n        :param value: the value to associate with the setting\n        :type value: any\n\n        :param priority: the priority of the setting. Should be a key of\n            :attr:`~scrapy.settings.SETTINGS_PRIORITIES` or an integer\n        :type priority: string or int\n        \"\"\"\n        self._assert_mutability()\n        priority = get_settings_priority(priority)\n        if name not in self:\n            if isinstance(value, SettingsAttribute):\n                self.attributes[name] = value\n            else:\n                self.attributes[name] = SettingsAttribute(value, priority)\n        else:\n            self.attributes[name].set(value, priority)\n\n    def setdict(self, values, priority='project'):\n        self.update(values, priority)\n\n    def setmodule(self, module, priority='project'):\n        \"\"\"\n        Store settings from a module with a given priority.\n\n        This is a helper function that calls\n        :meth:`~scrapy.settings.BaseSettings.set` for every globally declared\n        uppercase variable of ``module`` with the provided ``priority``.\n\n        :param module: the module or the path of the module\n        :type module: module object or string\n\n        :param priority: the priority of the settings. Should be a key of\n            :attr:`~scrapy.settings.SETTINGS_PRIORITIES` or an integer\n        :type priority: string or int\n        \"\"\"\n        self._assert_mutability()\n        if isinstance(module, six.string_types):\n            module = import_module(module)\n        for key in dir(module):\n            if key.isupper():\n                self.set(key, getattr(module, key), priority)\n\n    def update(self, values, priority='project'):\n        \"\"\"\n        Store key/value pairs with a given priority.\n\n        This is a helper function that calls\n        :meth:`~scrapy.settings.BaseSettings.set` for every item of ``values``\n        with the provided ``priority``.\n\n        If ``values`` is a string, it is assumed to be JSON-encoded and parsed\n        into a dict with ``json.loads()`` first. If it is a\n        :class:`~scrapy.settings.BaseSettings` instance, the per-key priorities\n        will be used and the ``priority`` parameter ignored. This allows\n        inserting/updating settings with different priorities with a single\n        command.\n\n        :param values: the settings names and values\n        :type values: dict or string or :class:`~scrapy.settings.BaseSettings`\n\n        :param priority: the priority of the settings. Should be a key of\n            :attr:`~scrapy.settings.SETTINGS_PRIORITIES` or an integer\n        :type priority: string or int\n        \"\"\"\n        self._assert_mutability()\n        if isinstance(values, six.string_types):\n            values = json.loads(values)\n        if values is not None:\n            if isinstance(values, BaseSettings):\n                for name, value in six.iteritems(values):\n                    self.set(name, value, values.getpriority(name))\n            else:\n                for name, value in six.iteritems(values):\n                    self.set(name, value, priority)\n\n    def delete(self, name, priority='project'):\n        self._assert_mutability()\n        priority = get_settings_priority(priority)\n        if priority >= self.getpriority(name):\n            del self.attributes[name]\n\n    def __delitem__(self, name):\n        self._assert_mutability()\n        del self.attributes[name]\n\n    def _assert_mutability(self):\n        if self.frozen:\n            raise TypeError(\"Trying to modify an immutable Settings object\")\n\n    def copy(self):\n        \"\"\"\n        Make a deep copy of current settings.\n\n        This method returns a new instance of the :class:`Settings` class,\n        populated with the same values and their priorities.\n\n        Modifications to the new object won't be reflected on the original\n        settings.\n        \"\"\"\n        return copy.deepcopy(self)\n\n    def freeze(self):\n        \"\"\"\n        Disable further changes to the current settings.\n\n        After calling this method, the present state of the settings will become\n        immutable. Trying to change values through the :meth:`~set` method and\n        its variants won't be possible and will be alerted.\n        \"\"\"\n        self.frozen = True\n\n    def frozencopy(self):\n        \"\"\"\n        Return an immutable copy of the current settings.\n\n        Alias for a :meth:`~freeze` call in the object returned by :meth:`copy`.\n        \"\"\"\n        copy = self.copy()\n        copy.freeze()\n        return copy\n\n    def __iter__(self):\n        return iter(self.attributes)\n\n    def __len__(self):\n        return len(self.attributes)\n\n    def _to_dict(self):\n        return {k: (v._to_dict() if isinstance(v, BaseSettings) else v)\n                for k, v in six.iteritems(self)}\n\n    def copy_to_dict(self):\n        \"\"\"\n        Make a copy of current settings and convert to a dict.\n\n        This method returns a new dict populated with the same values\n        and their priorities as the current settings.\n\n        Modifications to the returned dict won't be reflected on the original\n        settings.\n\n        This method can be useful for example for printing settings\n        in Scrapy shell.\n        \"\"\"\n        settings = self.copy()\n        return settings._to_dict()\n\n    def _repr_pretty_(self, p, cycle):\n        if cycle:\n            p.text(repr(self))\n        else:\n            p.text(pformat(self.copy_to_dict()))\n\n\nclass _DictProxy(MutableMapping):\n\n    def __init__(self, settings, priority):\n        self.o = {}\n        self.settings = settings\n        self.priority = priority\n\n    def __len__(self):\n        return len(self.o)\n\n    def __getitem__(self, k):\n        return self.o[k]\n\n    def __setitem__(self, k, v):\n        self.settings.set(k, v, priority=self.priority)\n        self.o[k] = v\n\n    def __delitem__(self, k):\n        del self.o[k]\n\n    def __iter__(self, k, v):\n        return iter(self.o)\n\n\nclass Settings(BaseSettings):\n    \"\"\"\n    This object stores Scrapy settings for the configuration of internal\n    components, and can be used for any further customization.\n\n    It is a direct subclass and supports all methods of\n    :class:`~scrapy.settings.BaseSettings`. Additionally, after instantiation\n    of this class, the new object will have the global default settings\n    described on :ref:`topics-settings-ref` already populated.\n    \"\"\"\n\n    def __init__(self, values=None, priority='project'):\n        # Do not pass kwarg values here. We don't want to promote user-defined\n        # dicts, and we want to update, not replace, default dicts with the\n        # values given by the user\n        super(Settings, self).__init__()\n        self.setmodule(default_settings, 'default')\n        # Promote default dictionaries to BaseSettings instances for per-key\n        # priorities\n        for name, val in six.iteritems(self):\n            if isinstance(val, dict):\n                self.set(name, BaseSettings(val, 'default'), 'default')\n        self.update(values, priority)\n\n\ndef iter_default_settings():\n    \"\"\"Return the default settings as an iterator of (name, value) tuples\"\"\"\n    for name in dir(default_settings):\n        if name.isupper():\n            yield name, getattr(default_settings, name)\n\n\ndef overridden_settings(settings):\n    \"\"\"Return a dict of the settings that have been overridden\"\"\"\n    for name, defvalue in iter_default_settings():\n        value = settings[name]\n        if not isinstance(defvalue, dict) and value != defvalue:\n            yield name, value\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/settings/default_settings.py",
    "content": "\"\"\"\nThis module contains the default values for all settings used by Scrapy.\n\nFor more information about these settings you can read the settings\ndocumentation in docs/topics/settings.rst\n\nScrapy developers, if you add a setting here remember to:\n\n* add it in alphabetical order\n* group similar settings without leaving blank lines\n* add its documentation to the available settings documentation\n  (docs/topics/settings.rst)\n\n\"\"\"\n\nimport sys\nfrom importlib import import_module\nfrom os.path import join, abspath, dirname\n\nimport six\n\nAJAXCRAWL_ENABLED = False\n\nAUTOTHROTTLE_ENABLED = False\nAUTOTHROTTLE_DEBUG = False\nAUTOTHROTTLE_MAX_DELAY = 60.0\nAUTOTHROTTLE_START_DELAY = 5.0\nAUTOTHROTTLE_TARGET_CONCURRENCY = 1.0\n\nBOT_NAME = 'scrapybot'\n\nCLOSESPIDER_TIMEOUT = 0\nCLOSESPIDER_PAGECOUNT = 0\nCLOSESPIDER_ITEMCOUNT = 0\nCLOSESPIDER_ERRORCOUNT = 0\n\nCOMMANDS_MODULE = ''\n\nCOMPRESSION_ENABLED = True\n\nCONCURRENT_ITEMS = 100\n\nCONCURRENT_REQUESTS = 16\nCONCURRENT_REQUESTS_PER_DOMAIN = 8\nCONCURRENT_REQUESTS_PER_IP = 0\n\nCOOKIES_ENABLED = True\nCOOKIES_DEBUG = False\n\nDEFAULT_ITEM_CLASS = 'scrapy.item.Item'\n\nDEFAULT_REQUEST_HEADERS = {\n    'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',\n    'Accept-Language': 'en',\n}\n\nDEPTH_LIMIT = 0\nDEPTH_STATS_VERBOSE = False\nDEPTH_PRIORITY = 0\n\nDNSCACHE_ENABLED = True\nDNSCACHE_SIZE = 10000\nDNS_TIMEOUT = 60\n\nDOWNLOAD_DELAY = 0\n\nDOWNLOAD_HANDLERS = {}\nDOWNLOAD_HANDLERS_BASE = {\n    'data': 'scrapy.core.downloader.handlers.datauri.DataURIDownloadHandler',\n    'file': 'scrapy.core.downloader.handlers.file.FileDownloadHandler',\n    'http': 'scrapy.core.downloader.handlers.http.HTTPDownloadHandler',\n    'https': 'scrapy.core.downloader.handlers.http.HTTPDownloadHandler',\n    's3': 'scrapy.core.downloader.handlers.s3.S3DownloadHandler',\n    'ftp': 'scrapy.core.downloader.handlers.ftp.FTPDownloadHandler',\n}\n\nDOWNLOAD_TIMEOUT = 180      # 3mins\n\nDOWNLOAD_MAXSIZE = 1024*1024*1024   # 1024m\nDOWNLOAD_WARNSIZE = 32*1024*1024    # 32m\n\nDOWNLOAD_FAIL_ON_DATALOSS = True\n\nDOWNLOADER = 'scrapy.core.downloader.Downloader'\n\nDOWNLOADER_HTTPCLIENTFACTORY = 'scrapy.core.downloader.webclient.ScrapyHTTPClientFactory'\nDOWNLOADER_CLIENTCONTEXTFACTORY = 'scrapy.core.downloader.contextfactory.ScrapyClientContextFactory'\nDOWNLOADER_CLIENT_TLS_METHOD = 'TLS' # Use highest TLS/SSL protocol version supported by the platform,\n                                     # also allowing negotiation\n\nDOWNLOADER_MIDDLEWARES = {}\n\nDOWNLOADER_MIDDLEWARES_BASE = {\n    # Engine side\n    'scrapy.downloadermiddlewares.robotstxt.RobotsTxtMiddleware': 100,\n    'scrapy.downloadermiddlewares.httpauth.HttpAuthMiddleware': 300,\n    'scrapy.downloadermiddlewares.downloadtimeout.DownloadTimeoutMiddleware': 350,\n    'scrapy.downloadermiddlewares.defaultheaders.DefaultHeadersMiddleware': 400,\n    'scrapy.downloadermiddlewares.useragent.UserAgentMiddleware': 500,\n    'scrapy.downloadermiddlewares.retry.RetryMiddleware': 550,\n    'scrapy.downloadermiddlewares.ajaxcrawl.AjaxCrawlMiddleware': 560,\n    'scrapy.downloadermiddlewares.redirect.MetaRefreshMiddleware': 580,\n    'scrapy.downloadermiddlewares.httpcompression.HttpCompressionMiddleware': 590,\n    'scrapy.downloadermiddlewares.redirect.RedirectMiddleware': 600,\n    'scrapy.downloadermiddlewares.cookies.CookiesMiddleware': 700,\n    'scrapy.downloadermiddlewares.httpproxy.HttpProxyMiddleware': 750,\n    'scrapy.downloadermiddlewares.stats.DownloaderStats': 850,\n    'scrapy.downloadermiddlewares.httpcache.HttpCacheMiddleware': 900,\n    # Downloader side\n}\n\nDOWNLOADER_STATS = True\n\nDUPEFILTER_CLASS = 'scrapy.dupefilters.RFPDupeFilter'\n\nEDITOR = 'vi'\nif sys.platform == 'win32':\n    EDITOR = '%s -m idlelib.idle'\n\nEXTENSIONS = {}\n\nEXTENSIONS_BASE = {\n    'scrapy.extensions.corestats.CoreStats': 0,\n    'scrapy.extensions.telnet.TelnetConsole': 0,\n    'scrapy.extensions.memusage.MemoryUsage': 0,\n    'scrapy.extensions.memdebug.MemoryDebugger': 0,\n    'scrapy.extensions.closespider.CloseSpider': 0,\n    'scrapy.extensions.feedexport.FeedExporter': 0,\n    'scrapy.extensions.logstats.LogStats': 0,\n    'scrapy.extensions.spiderstate.SpiderState': 0,\n    'scrapy.extensions.throttle.AutoThrottle': 0,\n}\n\nFEED_TEMPDIR = None\nFEED_URI = None\nFEED_URI_PARAMS = None  # a function to extend uri arguments\nFEED_FORMAT = 'jsonlines'\nFEED_STORE_EMPTY = False\nFEED_EXPORT_ENCODING = None\nFEED_EXPORT_FIELDS = None\nFEED_STORAGES = {}\nFEED_STORAGES_BASE = {\n    '': 'scrapy.extensions.feedexport.FileFeedStorage',\n    'file': 'scrapy.extensions.feedexport.FileFeedStorage',\n    'stdout': 'scrapy.extensions.feedexport.StdoutFeedStorage',\n    's3': 'scrapy.extensions.feedexport.S3FeedStorage',\n    'ftp': 'scrapy.extensions.feedexport.FTPFeedStorage',\n}\nFEED_EXPORTERS = {}\nFEED_EXPORTERS_BASE = {\n    'json': 'scrapy.exporters.JsonItemExporter',\n    'jsonlines': 'scrapy.exporters.JsonLinesItemExporter',\n    'jl': 'scrapy.exporters.JsonLinesItemExporter',\n    'csv': 'scrapy.exporters.CsvItemExporter',\n    'xml': 'scrapy.exporters.XmlItemExporter',\n    'marshal': 'scrapy.exporters.MarshalItemExporter',\n    'pickle': 'scrapy.exporters.PickleItemExporter',\n}\nFEED_EXPORT_INDENT = 0\n\nFEED_STORAGE_FTP_ACTIVE = False\nFEED_STORAGE_S3_ACL = ''\n\nFILES_STORE_S3_ACL = 'private'\nFILES_STORE_GCS_ACL = ''\n\nFTP_USER = 'anonymous'\nFTP_PASSWORD = 'guest'\nFTP_PASSIVE_MODE = True\n\nHTTPCACHE_ENABLED = False\nHTTPCACHE_DIR = 'httpcache'\nHTTPCACHE_IGNORE_MISSING = False\nHTTPCACHE_STORAGE = 'scrapy.extensions.httpcache.FilesystemCacheStorage'\nHTTPCACHE_EXPIRATION_SECS = 0\nHTTPCACHE_ALWAYS_STORE = False\nHTTPCACHE_IGNORE_HTTP_CODES = []\nHTTPCACHE_IGNORE_SCHEMES = ['file']\nHTTPCACHE_IGNORE_RESPONSE_CACHE_CONTROLS = []\nHTTPCACHE_DBM_MODULE = 'anydbm' if six.PY2 else 'dbm'\nHTTPCACHE_POLICY = 'scrapy.extensions.httpcache.DummyPolicy'\nHTTPCACHE_GZIP = False\n\nHTTPPROXY_ENABLED = True\nHTTPPROXY_AUTH_ENCODING = 'latin-1'\n\nIMAGES_STORE_S3_ACL = 'private'\nIMAGES_STORE_GCS_ACL = ''\n\nITEM_PROCESSOR = 'scrapy.pipelines.ItemPipelineManager'\n\nITEM_PIPELINES = {}\nITEM_PIPELINES_BASE = {}\n\nLOG_ENABLED = True\nLOG_ENCODING = 'utf-8'\nLOG_FORMATTER = 'scrapy.logformatter.LogFormatter'\nLOG_FORMAT = '%(asctime)s [%(name)s] %(levelname)s: %(message)s'\nLOG_DATEFORMAT = '%Y-%m-%d %H:%M:%S'\nLOG_STDOUT = False\nLOG_LEVEL = 'DEBUG'\nLOG_FILE = None\nLOG_SHORT_NAMES = False\n\nSCHEDULER_DEBUG = False\n\nLOGSTATS_INTERVAL = 60.0\n\nMAIL_HOST = 'localhost'\nMAIL_PORT = 25\nMAIL_FROM = 'scrapy@localhost'\nMAIL_PASS = None\nMAIL_USER = None\n\nMEMDEBUG_ENABLED = False        # enable memory debugging\nMEMDEBUG_NOTIFY = []            # send memory debugging report by mail at engine shutdown\n\nMEMUSAGE_CHECK_INTERVAL_SECONDS = 60.0\nMEMUSAGE_ENABLED = True\nMEMUSAGE_LIMIT_MB = 0\nMEMUSAGE_NOTIFY_MAIL = []\nMEMUSAGE_WARNING_MB = 0\n\nMETAREFRESH_ENABLED = True\nMETAREFRESH_IGNORE_TAGS = ['script', 'noscript']\nMETAREFRESH_MAXDELAY = 100\n\nNEWSPIDER_MODULE = ''\n\nRANDOMIZE_DOWNLOAD_DELAY = True\n\nREACTOR_THREADPOOL_MAXSIZE = 10\n\nREDIRECT_ENABLED = True\nREDIRECT_MAX_TIMES = 20  # uses Firefox default setting\nREDIRECT_PRIORITY_ADJUST = +2\n\nREFERER_ENABLED = True\nREFERRER_POLICY = 'scrapy.spidermiddlewares.referer.DefaultReferrerPolicy'\n\nRETRY_ENABLED = True\nRETRY_TIMES = 2  # initial response + 2 retries = 3 requests\nRETRY_HTTP_CODES = [500, 502, 503, 504, 522, 524, 408, 429]\nRETRY_PRIORITY_ADJUST = -1\n\nROBOTSTXT_OBEY = False\n\nSCHEDULER = 'scrapy.core.scheduler.Scheduler'\nSCHEDULER_DISK_QUEUE = 'scrapy.squeues.PickleLifoDiskQueue'\nSCHEDULER_MEMORY_QUEUE = 'scrapy.squeues.LifoMemoryQueue'\nSCHEDULER_PRIORITY_QUEUE = 'scrapy.pqueues.ScrapyPriorityQueue'\n\nSPIDER_LOADER_CLASS = 'scrapy.spiderloader.SpiderLoader'\nSPIDER_LOADER_WARN_ONLY = False\n\nSPIDER_MIDDLEWARES = {}\n\nSPIDER_MIDDLEWARES_BASE = {\n    # Engine side\n    'scrapy.spidermiddlewares.httperror.HttpErrorMiddleware': 50,\n    'scrapy.spidermiddlewares.offsite.OffsiteMiddleware': 500,\n    'scrapy.spidermiddlewares.referer.RefererMiddleware': 700,\n    'scrapy.spidermiddlewares.urllength.UrlLengthMiddleware': 800,\n    'scrapy.spidermiddlewares.depth.DepthMiddleware': 900,\n    # Spider side\n}\n\nSPIDER_MODULES = []\n\nSTATS_CLASS = 'scrapy.statscollectors.MemoryStatsCollector'\nSTATS_DUMP = True\n\nSTATSMAILER_RCPTS = []\n\nTEMPLATES_DIR = abspath(join(dirname(__file__), '..', 'templates'))\n\nURLLENGTH_LIMIT = 2083\n\nUSER_AGENT = 'Scrapy/%s (+https://scrapy.org)' % import_module('scrapy').__version__\n\nTELNETCONSOLE_ENABLED = 1\nTELNETCONSOLE_PORT = [6023, 6073]\nTELNETCONSOLE_HOST = '127.0.0.1'\nTELNETCONSOLE_USERNAME = 'scrapy'\nTELNETCONSOLE_PASSWORD = None\n\nSPIDER_CONTRACTS = {}\nSPIDER_CONTRACTS_BASE = {\n    'scrapy.contracts.default.UrlContract': 1,\n    'scrapy.contracts.default.ReturnsContract': 2,\n    'scrapy.contracts.default.ScrapesContract': 3,\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/settings/deprecated.py",
    "content": "import warnings\nfrom scrapy.exceptions import ScrapyDeprecationWarning\n\nDEPRECATED_SETTINGS = [\n    ('TRACK_REFS', 'no longer needed (trackref is always enabled)'),\n    ('RESPONSE_CLASSES', 'no longer supported'),\n    ('DEFAULT_RESPONSE_ENCODING', 'no longer supported'),\n    ('BOT_VERSION', 'no longer used (user agent defaults to Scrapy now)'),\n    ('ENCODING_ALIASES', 'no longer needed (encoding discovery uses w3lib now)'),\n    ('STATS_ENABLED', 'no longer supported (change STATS_CLASS instead)'),\n    ('SQLITE_DB', 'no longer supported'),\n    ('SELECTORS_BACKEND', 'use SCRAPY_SELECTORS_BACKEND environment variable instead'),\n    ('AUTOTHROTTLE_MIN_DOWNLOAD_DELAY', 'use DOWNLOAD_DELAY instead'),\n    ('AUTOTHROTTLE_MAX_CONCURRENCY', 'use CONCURRENT_REQUESTS_PER_DOMAIN instead'),\n    ('AUTOTHROTTLE_MAX_CONCURRENCY', 'use CONCURRENT_REQUESTS_PER_DOMAIN instead'),\n    ('REDIRECT_MAX_METAREFRESH_DELAY', 'use METAREFRESH_MAXDELAY instead'),\n    ('LOG_UNSERIALIZABLE_REQUESTS', 'use SCHEDULER_DEBUG instead'),\n]\n\n\ndef check_deprecated_settings(settings):\n    deprecated = [x for x in DEPRECATED_SETTINGS if settings[x[0]] is not None]\n    if deprecated:\n        msg = \"You are using the following settings which are deprecated or obsolete\"\n        msg += \" (ask scrapy-users@googlegroups.com for alternatives):\"\n        msg = msg + \"\\n    \" + \"\\n    \".join(\"%s: %s\" % x for x in deprecated)\n        warnings.warn(msg, ScrapyDeprecationWarning)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/shell.py",
    "content": "\"\"\"Scrapy Shell\n\nSee documentation in docs/topics/shell.rst\n\n\"\"\"\nfrom __future__ import print_function\n\nimport os\nimport signal\nimport warnings\n\nfrom twisted.internet import reactor, threads, defer\nfrom twisted.python import threadable\nfrom w3lib.url import any_to_uri\n\nfrom scrapy.crawler import Crawler\nfrom scrapy.exceptions import IgnoreRequest, ScrapyDeprecationWarning\nfrom scrapy.http import Request, Response\nfrom scrapy.item import BaseItem\nfrom scrapy.settings import Settings\nfrom scrapy.spiders import Spider\nfrom scrapy.utils.console import start_python_console\nfrom scrapy.utils.datatypes import SequenceExclude\nfrom scrapy.utils.misc import load_object\nfrom scrapy.utils.response import open_in_browser\nfrom scrapy.utils.conf import get_config\nfrom scrapy.utils.console import DEFAULT_PYTHON_SHELLS\n\n\nclass Shell(object):\n\n    relevant_classes = (Crawler, Spider, Request, Response, BaseItem,\n                        Settings)\n\n    def __init__(self, crawler, update_vars=None, code=None):\n        self.crawler = crawler\n        self.update_vars = update_vars or (lambda x: None)\n        self.item_class = load_object(crawler.settings['DEFAULT_ITEM_CLASS'])\n        self.spider = None\n        self.inthread = not threadable.isInIOThread()\n        self.code = code\n        self.vars = {}\n\n    def start(self, url=None, request=None, response=None, spider=None, redirect=True):\n        # disable accidental Ctrl-C key press from shutting down the engine\n        signal.signal(signal.SIGINT, signal.SIG_IGN)\n        if url:\n            self.fetch(url, spider, redirect=redirect)\n        elif request:\n            self.fetch(request, spider)\n        elif response:\n            request = response.request\n            self.populate_vars(response, request, spider)\n        else:\n            self.populate_vars()\n        if self.code:\n            print(eval(self.code, globals(), self.vars))\n        else:\n            \"\"\"\n            Detect interactive shell setting in scrapy.cfg\n            e.g.: ~/.config/scrapy.cfg or ~/.scrapy.cfg\n            [settings]\n            # shell can be one of ipython, bpython or python;\n            # to be used as the interactive python console, if available.\n            # (default is ipython, fallbacks in the order listed above)\n            shell = python\n            \"\"\"\n            cfg = get_config()\n            section, option = 'settings', 'shell'\n            env = os.environ.get('SCRAPY_PYTHON_SHELL')\n            shells = []\n            if env:\n                shells += env.strip().lower().split(',')\n            elif cfg.has_option(section, option):\n                shells += [cfg.get(section, option).strip().lower()]\n            else:  # try all by default\n                shells += DEFAULT_PYTHON_SHELLS.keys()\n            # always add standard shell as fallback\n            shells += ['python']\n            start_python_console(self.vars, shells=shells,\n                                 banner=self.vars.pop('banner', ''))\n\n    def _schedule(self, request, spider):\n        spider = self._open_spider(request, spider)\n        d = _request_deferred(request)\n        d.addCallback(lambda x: (x, spider))\n        self.crawler.engine.crawl(request, spider)\n        return d\n\n    def _open_spider(self, request, spider):\n        if self.spider:\n            return self.spider\n\n        if spider is None:\n            spider = self.crawler.spider or self.crawler._create_spider()\n\n        self.crawler.spider = spider\n        self.crawler.engine.open_spider(spider, close_if_idle=False)\n        self.spider = spider\n        return spider\n\n    def fetch(self, request_or_url, spider=None, redirect=True, **kwargs):\n        if isinstance(request_or_url, Request):\n            request = request_or_url\n        else:\n            url = any_to_uri(request_or_url)\n            request = Request(url, dont_filter=True, **kwargs)\n            if redirect:\n                request.meta['handle_httpstatus_list'] = SequenceExclude(range(300, 400))\n            else:\n                request.meta['handle_httpstatus_all'] = True\n        response = None\n        try:\n            response, spider = threads.blockingCallFromThread(\n                reactor, self._schedule, request, spider)\n        except IgnoreRequest:\n            pass\n        self.populate_vars(response, request, spider)\n\n    def populate_vars(self, response=None, request=None, spider=None):\n        import scrapy\n\n        self.vars['scrapy'] = scrapy\n        self.vars['crawler'] = self.crawler\n        self.vars['item'] = self.item_class()\n        self.vars['settings'] = self.crawler.settings\n        self.vars['spider'] = spider\n        self.vars['request'] = request\n        self.vars['response'] = response\n        self.vars['sel'] = _SelectorProxy(response)\n        if self.inthread:\n            self.vars['fetch'] = self.fetch\n        self.vars['view'] = open_in_browser\n        self.vars['shelp'] = self.print_help\n        self.update_vars(self.vars)\n        if not self.code:\n            self.vars['banner'] = self.get_help()\n\n    def print_help(self):\n        print(self.get_help())\n\n    def get_help(self):\n        b = []\n        b.append(\"Available Scrapy objects:\")\n        b.append(\"  scrapy     scrapy module (contains scrapy.Request, scrapy.Selector, etc)\")\n        for k, v in sorted(self.vars.items()):\n            if self._is_relevant(v):\n                b.append(\"  %-10s %s\" % (k, v))\n        b.append(\"Useful shortcuts:\")\n        if self.inthread:\n            b.append(\"  fetch(url[, redirect=True]) \"\n                     \"Fetch URL and update local objects \"\n                     \"(by default, redirects are followed)\")\n            b.append(\"  fetch(req)                  \"\n                     \"Fetch a scrapy.Request and update local objects \")\n        b.append(\"  shelp()           Shell help (print this help)\")\n        b.append(\"  view(response)    View response in a browser\")\n\n        return \"\\n\".join(\"[s] %s\" % l for l in b)\n\n    def _is_relevant(self, value):\n        return isinstance(value, self.relevant_classes)\n\n\ndef inspect_response(response, spider):\n    \"\"\"Open a shell to inspect the given response\"\"\"\n    Shell(spider.crawler).start(response=response, spider=spider)\n\n\ndef _request_deferred(request):\n    \"\"\"Wrap a request inside a Deferred.\n\n    This function is harmful, do not use it until you know what you are doing.\n\n    This returns a Deferred whose first pair of callbacks are the request\n    callback and errback. The Deferred also triggers when the request\n    callback/errback is executed (ie. when the request is downloaded)\n\n    WARNING: Do not call request.replace() until after the deferred is called.\n    \"\"\"\n    request_callback = request.callback\n    request_errback = request.errback\n\n    def _restore_callbacks(result):\n        request.callback = request_callback\n        request.errback = request_errback\n        return result\n\n    d = defer.Deferred()\n    d.addBoth(_restore_callbacks)\n    if request.callback:\n        d.addCallbacks(request.callback, request.errback)\n\n    request.callback, request.errback = d.callback, d.errback\n    return d\n\n\nclass _SelectorProxy(object):\n\n    def __init__(self, response):\n        self._proxiedresponse = response\n\n    def __getattr__(self, name):\n        warnings.warn('\"sel\" shortcut is deprecated. Use \"response.xpath()\", '\n                      '\"response.css()\" or \"response.selector\" instead',\n                      category=ScrapyDeprecationWarning, stacklevel=2)\n        return getattr(self._proxiedresponse.selector, name)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/signalmanager.py",
    "content": "from __future__ import absolute_import\nfrom pydispatch import dispatcher\nfrom scrapy.utils import signal as _signal\n\n\nclass SignalManager(object):\n\n    def __init__(self, sender=dispatcher.Anonymous):\n        self.sender = sender\n\n    def connect(self, receiver, signal, **kwargs):\n        \"\"\"\n        Connect a receiver function to a signal.\n\n        The signal can be any object, although Scrapy comes with some\n        predefined signals that are documented in the :ref:`topics-signals`\n        section.\n\n        :param receiver: the function to be connected\n        :type receiver: callable\n\n        :param signal: the signal to connect to\n        :type signal: object\n        \"\"\"\n        kwargs.setdefault('sender', self.sender)\n        return dispatcher.connect(receiver, signal, **kwargs)\n\n    def disconnect(self, receiver, signal, **kwargs):\n        \"\"\"\n        Disconnect a receiver function from a signal. This has the\n        opposite effect of the :meth:`connect` method, and the arguments\n        are the same.\n        \"\"\"\n        kwargs.setdefault('sender', self.sender)\n        return dispatcher.disconnect(receiver, signal, **kwargs)\n\n    def send_catch_log(self, signal, **kwargs):\n        \"\"\"\n        Send a signal, catch exceptions and log them.\n\n        The keyword arguments are passed to the signal handlers (connected\n        through the :meth:`connect` method).\n        \"\"\"\n        kwargs.setdefault('sender', self.sender)\n        return _signal.send_catch_log(signal, **kwargs)\n\n    def send_catch_log_deferred(self, signal, **kwargs):\n        \"\"\"\n        Like :meth:`send_catch_log` but supports returning `deferreds`_ from\n        signal handlers.\n\n        Returns a Deferred that gets fired once all signal handlers\n        deferreds were fired. Send a signal, catch exceptions and log them.\n\n        The keyword arguments are passed to the signal handlers (connected\n        through the :meth:`connect` method).\n\n        .. _deferreds: https://twistedmatrix.com/documents/current/core/howto/defer.html\n        \"\"\"\n        kwargs.setdefault('sender', self.sender)\n        return _signal.send_catch_log_deferred(signal, **kwargs)\n\n    def disconnect_all(self, signal, **kwargs):\n        \"\"\"\n        Disconnect all receivers from the given signal.\n\n        :param signal: the signal to disconnect from\n        :type signal: object\n        \"\"\"\n        kwargs.setdefault('sender', self.sender)\n        return _signal.disconnect_all(signal, **kwargs)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/signals.py",
    "content": "\"\"\"\nScrapy signals\n\nThese signals are documented in docs/topics/signals.rst. Please don't add new\nsignals here without documenting them there.\n\"\"\"\n\nengine_started = object()\nengine_stopped = object()\nspider_opened = object()\nspider_idle = object()\nspider_closed = object()\nspider_error = object()\nrequest_scheduled = object()\nrequest_dropped = object()\nrequest_reached_downloader = object()\nresponse_received = object()\nresponse_downloaded = object()\nitem_scraped = object()\nitem_dropped = object()\nitem_error = object()\n\n# for backward compatibility\nstats_spider_opened = spider_opened\nstats_spider_closing = spider_closed\nstats_spider_closed = spider_closed\n\nitem_passed = item_scraped\n\nrequest_received = request_scheduled\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/spiderloader.py",
    "content": "# -*- coding: utf-8 -*-\nfrom __future__ import absolute_import\nfrom collections import defaultdict\nimport traceback\nimport warnings\n\nfrom zope.interface import implementer\n\nfrom scrapy.interfaces import ISpiderLoader\nfrom scrapy.utils.misc import walk_modules\nfrom scrapy.utils.spider import iter_spider_classes\n\n\n@implementer(ISpiderLoader)\nclass SpiderLoader(object):\n    \"\"\"\n    SpiderLoader is a class which locates and loads spiders\n    in a Scrapy project.\n    \"\"\"\n    def __init__(self, settings):\n        self.spider_modules = settings.getlist('SPIDER_MODULES')\n        self.warn_only = settings.getbool('SPIDER_LOADER_WARN_ONLY')\n        self._spiders = {}\n        self._found = defaultdict(list)\n        self._load_all_spiders()\n\n    def _check_name_duplicates(self):\n        dupes = [\"\\n\".join(\"  {cls} named {name!r} (in {module})\".format(\n                                module=mod, cls=cls, name=name)\n                           for (mod, cls) in locations)\n                 for name, locations in self._found.items()\n                 if len(locations)>1]\n        if dupes:\n            msg = (\"There are several spiders with the same name:\\n\\n\"\n                   \"{}\\n\\n  This can cause unexpected behavior.\".format(\n                        \"\\n\\n\".join(dupes)))\n            warnings.warn(msg, UserWarning)\n\n    def _load_spiders(self, module):\n        for spcls in iter_spider_classes(module):\n            self._found[spcls.name].append((module.__name__, spcls.__name__))\n            self._spiders[spcls.name] = spcls\n\n    def _load_all_spiders(self):\n        for name in self.spider_modules:\n            try:\n                for module in walk_modules(name):\n                    self._load_spiders(module)\n            except ImportError as e:\n                if self.warn_only:\n                    msg = (\"\\n{tb}Could not load spiders from module '{modname}'. \"\n                           \"See above traceback for details.\".format(\n                                modname=name, tb=traceback.format_exc()))\n                    warnings.warn(msg, RuntimeWarning)\n                else:\n                    raise\n        self._check_name_duplicates()\n\n    @classmethod\n    def from_settings(cls, settings):\n        return cls(settings)\n\n    def load(self, spider_name):\n        \"\"\"\n        Return the Spider class for the given spider name. If the spider\n        name is not found, raise a KeyError.\n        \"\"\"\n        try:\n            return self._spiders[spider_name]\n        except KeyError:\n            raise KeyError(\"Spider not found: {}\".format(spider_name))\n\n    def find_by_request(self, request):\n        \"\"\"\n        Return the list of spider names that can handle the given request.\n        \"\"\"\n        return [name for name, cls in self._spiders.items()\n                if cls.handles_request(request)]\n\n    def list(self):\n        \"\"\"\n        Return a list with the names of all spiders available in the project.\n        \"\"\"\n        return list(self._spiders.keys())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/spidermiddlewares/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/spidermiddlewares/depth.py",
    "content": "\"\"\"\nDepth Spider Middleware\n\nSee documentation in docs/topics/spider-middleware.rst\n\"\"\"\n\nimport logging\n\nfrom scrapy.http import Request\n\nlogger = logging.getLogger(__name__)\n\n\nclass DepthMiddleware(object):\n\n    def __init__(self, maxdepth, stats, verbose_stats=False, prio=1):\n        self.maxdepth = maxdepth\n        self.stats = stats\n        self.verbose_stats = verbose_stats\n        self.prio = prio\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        settings = crawler.settings\n        maxdepth = settings.getint('DEPTH_LIMIT')\n        verbose = settings.getbool('DEPTH_STATS_VERBOSE')\n        prio = settings.getint('DEPTH_PRIORITY')\n        return cls(maxdepth, crawler.stats, verbose, prio)\n\n    def process_spider_output(self, response, result, spider):\n        def _filter(request):\n            if isinstance(request, Request):\n                depth = response.meta['depth'] + 1\n                request.meta['depth'] = depth\n                if self.prio:\n                    request.priority -= depth * self.prio\n                if self.maxdepth and depth > self.maxdepth:\n                    logger.debug(\n                        \"Ignoring link (depth > %(maxdepth)d): %(requrl)s \",\n                        {'maxdepth': self.maxdepth, 'requrl': request.url},\n                        extra={'spider': spider}\n                    )\n                    return False\n                else:\n                    if self.verbose_stats:\n                        self.stats.inc_value('request_depth_count/%s' % depth,\n                                             spider=spider)\n                    self.stats.max_value('request_depth_max', depth,\n                                         spider=spider)\n            return True\n\n        # base case (depth=0)\n        if 'depth' not in response.meta:\n            response.meta['depth'] = 0\n            if self.verbose_stats:\n                self.stats.inc_value('request_depth_count/0', spider=spider)\n\n        return (r for r in result or () if _filter(r))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/spidermiddlewares/httperror.py",
    "content": "\"\"\"\nHttpError Spider Middleware\n\nSee documentation in docs/topics/spider-middleware.rst\n\"\"\"\nimport logging\n\nfrom scrapy.exceptions import IgnoreRequest\n\nlogger = logging.getLogger(__name__)\n\n\nclass HttpError(IgnoreRequest):\n    \"\"\"A non-200 response was filtered\"\"\"\n\n    def __init__(self, response, *args, **kwargs):\n        self.response = response\n        super(HttpError, self).__init__(*args, **kwargs)\n\n\nclass HttpErrorMiddleware(object):\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls(crawler.settings)\n\n    def __init__(self, settings):\n        self.handle_httpstatus_all = settings.getbool('HTTPERROR_ALLOW_ALL')\n        self.handle_httpstatus_list = settings.getlist('HTTPERROR_ALLOWED_CODES')\n\n    def process_spider_input(self, response, spider):\n        if 200 <= response.status < 300:  # common case\n            return\n        meta = response.meta\n        if 'handle_httpstatus_all' in meta:\n            return\n        if 'handle_httpstatus_list' in meta:\n            allowed_statuses = meta['handle_httpstatus_list']\n        elif self.handle_httpstatus_all:\n            return\n        else:\n            allowed_statuses = getattr(spider, 'handle_httpstatus_list', self.handle_httpstatus_list)\n        if response.status in allowed_statuses:\n            return\n        raise HttpError(response, 'Ignoring non-200 response')\n\n    def process_spider_exception(self, response, exception, spider):\n        if isinstance(exception, HttpError):\n            spider.crawler.stats.inc_value('httperror/response_ignored_count')\n            spider.crawler.stats.inc_value(\n                'httperror/response_ignored_status_count/%s' % response.status\n            )\n            logger.info(\n                \"Ignoring response %(response)r: HTTP status code is not handled or not allowed\",\n                {'response': response}, extra={'spider': spider},\n            )\n            return []\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/spidermiddlewares/offsite.py",
    "content": "\"\"\"\nOffsite Spider Middleware\n\nSee documentation in docs/topics/spider-middleware.rst\n\"\"\"\nimport re\nimport logging\nimport warnings\n\nfrom scrapy import signals\nfrom scrapy.http import Request\nfrom scrapy.utils.httpobj import urlparse_cached\n\nlogger = logging.getLogger(__name__)\n\n\nclass OffsiteMiddleware(object):\n\n    def __init__(self, stats):\n        self.stats = stats\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        o = cls(crawler.stats)\n        crawler.signals.connect(o.spider_opened, signal=signals.spider_opened)\n        return o\n\n    def process_spider_output(self, response, result, spider):\n        for x in result:\n            if isinstance(x, Request):\n                if x.dont_filter or self.should_follow(x, spider):\n                    yield x\n                else:\n                    domain = urlparse_cached(x).hostname\n                    if domain and domain not in self.domains_seen:\n                        self.domains_seen.add(domain)\n                        logger.debug(\n                            \"Filtered offsite request to %(domain)r: %(request)s\",\n                            {'domain': domain, 'request': x}, extra={'spider': spider})\n                        self.stats.inc_value('offsite/domains', spider=spider)\n                    self.stats.inc_value('offsite/filtered', spider=spider)\n            else:\n                yield x\n\n    def should_follow(self, request, spider):\n        regex = self.host_regex\n        # hostname can be None for wrong urls (like javascript links)\n        host = urlparse_cached(request).hostname or ''\n        return bool(regex.search(host))\n\n    def get_host_regex(self, spider):\n        \"\"\"Override this method to implement a different offsite policy\"\"\"\n        allowed_domains = getattr(spider, 'allowed_domains', None)\n        if not allowed_domains:\n            return re.compile('')  # allow all by default\n        url_pattern = re.compile(\"^https?://.*$\")\n        for domain in allowed_domains:\n            if url_pattern.match(domain):\n                message = (\"allowed_domains accepts only domains, not URLs. \"\n                           \"Ignoring URL entry %s in allowed_domains.\" % domain)\n                warnings.warn(message, URLWarning)\n        domains = [re.escape(d) for d in allowed_domains if d is not None]\n        regex = r'^(.*\\.)?(%s)$' % '|'.join(domains)\n        return re.compile(regex)\n\n    def spider_opened(self, spider):\n        self.host_regex = self.get_host_regex(spider)\n        self.domains_seen = set()\n\n\nclass URLWarning(Warning):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/spidermiddlewares/referer.py",
    "content": "\"\"\"\nRefererMiddleware: populates Request referer field, based on the Response which\noriginated it.\n\"\"\"\nfrom six.moves.urllib.parse import urlparse\nimport warnings\n\nfrom w3lib.url import safe_url_string\n\nfrom scrapy.http import Request, Response\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy import signals\nfrom scrapy.utils.python import to_native_str\nfrom scrapy.utils.httpobj import urlparse_cached\nfrom scrapy.utils.misc import load_object\nfrom scrapy.utils.url import strip_url\n\n\nLOCAL_SCHEMES = ('about', 'blob', 'data', 'filesystem',)\n\nPOLICY_NO_REFERRER = \"no-referrer\"\nPOLICY_NO_REFERRER_WHEN_DOWNGRADE = \"no-referrer-when-downgrade\"\nPOLICY_SAME_ORIGIN = \"same-origin\"\nPOLICY_ORIGIN = \"origin\"\nPOLICY_STRICT_ORIGIN = \"strict-origin\"\nPOLICY_ORIGIN_WHEN_CROSS_ORIGIN = \"origin-when-cross-origin\"\nPOLICY_STRICT_ORIGIN_WHEN_CROSS_ORIGIN = \"strict-origin-when-cross-origin\"\nPOLICY_UNSAFE_URL = \"unsafe-url\"\nPOLICY_SCRAPY_DEFAULT = \"scrapy-default\"\n\n\nclass ReferrerPolicy(object):\n\n    NOREFERRER_SCHEMES = LOCAL_SCHEMES\n\n    def referrer(self, response_url, request_url):\n        raise NotImplementedError()\n\n    def stripped_referrer(self, url):\n        if urlparse(url).scheme not in self.NOREFERRER_SCHEMES:\n            return self.strip_url(url)\n\n    def origin_referrer(self, url):\n        if urlparse(url).scheme not in self.NOREFERRER_SCHEMES:\n            return self.origin(url)\n\n    def strip_url(self, url, origin_only=False):\n        \"\"\"\n        https://www.w3.org/TR/referrer-policy/#strip-url\n\n        If url is null, return no referrer.\n        If url's scheme is a local scheme, then return no referrer.\n        Set url's username to the empty string.\n        Set url's password to null.\n        Set url's fragment to null.\n        If the origin-only flag is true, then:\n            Set url's path to null.\n            Set url's query to null.\n        Return url.\n        \"\"\"\n        if not url:\n            return None\n        return strip_url(url,\n                         strip_credentials=True,\n                         strip_fragment=True,\n                         strip_default_port=True,\n                         origin_only=origin_only)\n\n    def origin(self, url):\n        \"\"\"Return serialized origin (scheme, host, path) for a request or response URL.\"\"\"\n        return self.strip_url(url, origin_only=True)\n\n    def potentially_trustworthy(self, url):\n        # Note: this does not follow https://w3c.github.io/webappsec-secure-contexts/#is-url-trustworthy\n        parsed_url = urlparse(url)\n        if parsed_url.scheme in ('data',):\n            return False\n        return self.tls_protected(url)\n\n    def tls_protected(self, url):\n        return urlparse(url).scheme in ('https', 'ftps')\n\n\nclass NoReferrerPolicy(ReferrerPolicy):\n    \"\"\"\n    https://www.w3.org/TR/referrer-policy/#referrer-policy-no-referrer\n\n    The simplest policy is \"no-referrer\", which specifies that no referrer information\n    is to be sent along with requests made from a particular request client to any origin.\n    The header will be omitted entirely.\n    \"\"\"\n    name = POLICY_NO_REFERRER\n\n    def referrer(self, response_url, request_url):\n        return None\n\n\nclass NoReferrerWhenDowngradePolicy(ReferrerPolicy):\n    \"\"\"\n    https://www.w3.org/TR/referrer-policy/#referrer-policy-no-referrer-when-downgrade\n\n    The \"no-referrer-when-downgrade\" policy sends a full URL along with requests\n    from a TLS-protected environment settings object to a potentially trustworthy URL,\n    and requests from clients which are not TLS-protected to any origin.\n\n    Requests from TLS-protected clients to non-potentially trustworthy URLs,\n    on the other hand, will contain no referrer information.\n    A Referer HTTP header will not be sent.\n\n    This is a user agent's default behavior, if no policy is otherwise specified.\n    \"\"\"\n    name = POLICY_NO_REFERRER_WHEN_DOWNGRADE\n\n    def referrer(self, response_url, request_url):\n        if not self.tls_protected(response_url) or self.tls_protected(request_url):\n            return self.stripped_referrer(response_url)\n\n\nclass SameOriginPolicy(ReferrerPolicy):\n    \"\"\"\n    https://www.w3.org/TR/referrer-policy/#referrer-policy-same-origin\n\n    The \"same-origin\" policy specifies that a full URL, stripped for use as a referrer,\n    is sent as referrer information when making same-origin requests from a particular request client.\n\n    Cross-origin requests, on the other hand, will contain no referrer information.\n    A Referer HTTP header will not be sent.\n    \"\"\"\n    name = POLICY_SAME_ORIGIN\n\n    def referrer(self, response_url, request_url):\n        if self.origin(response_url) == self.origin(request_url):\n            return self.stripped_referrer(response_url)\n\n\nclass OriginPolicy(ReferrerPolicy):\n    \"\"\"\n    https://www.w3.org/TR/referrer-policy/#referrer-policy-origin\n\n    The \"origin\" policy specifies that only the ASCII serialization\n    of the origin of the request client is sent as referrer information\n    when making both same-origin requests and cross-origin requests\n    from a particular request client.\n    \"\"\"\n    name = POLICY_ORIGIN\n\n    def referrer(self, response_url, request_url):\n        return self.origin_referrer(response_url)\n\n\nclass StrictOriginPolicy(ReferrerPolicy):\n    \"\"\"\n    https://www.w3.org/TR/referrer-policy/#referrer-policy-strict-origin\n\n    The \"strict-origin\" policy sends the ASCII serialization\n    of the origin of the request client when making requests:\n    - from a TLS-protected environment settings object to a potentially trustworthy URL, and\n    - from non-TLS-protected environment settings objects to any origin.\n\n    Requests from TLS-protected request clients to non- potentially trustworthy URLs,\n    on the other hand, will contain no referrer information.\n    A Referer HTTP header will not be sent.\n    \"\"\"\n    name = POLICY_STRICT_ORIGIN\n\n    def referrer(self, response_url, request_url):\n        if ((self.tls_protected(response_url) and\n             self.potentially_trustworthy(request_url))\n            or not self.tls_protected(response_url)):\n            return self.origin_referrer(response_url)\n\n\nclass OriginWhenCrossOriginPolicy(ReferrerPolicy):\n    \"\"\"\n    https://www.w3.org/TR/referrer-policy/#referrer-policy-origin-when-cross-origin\n\n    The \"origin-when-cross-origin\" policy specifies that a full URL,\n    stripped for use as a referrer, is sent as referrer information\n    when making same-origin requests from a particular request client,\n    and only the ASCII serialization of the origin of the request client\n    is sent as referrer information when making cross-origin requests\n    from a particular request client.\n    \"\"\"\n    name = POLICY_ORIGIN_WHEN_CROSS_ORIGIN\n\n    def referrer(self, response_url, request_url):\n        origin = self.origin(response_url)\n        if origin == self.origin(request_url):\n            return self.stripped_referrer(response_url)\n        else:\n            return origin\n\n\nclass StrictOriginWhenCrossOriginPolicy(ReferrerPolicy):\n    \"\"\"\n    https://www.w3.org/TR/referrer-policy/#referrer-policy-strict-origin-when-cross-origin\n\n    The \"strict-origin-when-cross-origin\" policy specifies that a full URL,\n    stripped for use as a referrer, is sent as referrer information\n    when making same-origin requests from a particular request client,\n    and only the ASCII serialization of the origin of the request client\n    when making cross-origin requests:\n\n    - from a TLS-protected environment settings object to a potentially trustworthy URL, and\n    - from non-TLS-protected environment settings objects to any origin.\n\n    Requests from TLS-protected clients to non- potentially trustworthy URLs,\n    on the other hand, will contain no referrer information.\n    A Referer HTTP header will not be sent.\n    \"\"\"\n    name = POLICY_STRICT_ORIGIN_WHEN_CROSS_ORIGIN\n\n    def referrer(self, response_url, request_url):\n        origin = self.origin(response_url)\n        if origin == self.origin(request_url):\n            return self.stripped_referrer(response_url)\n        elif ((self.tls_protected(response_url) and\n               self.potentially_trustworthy(request_url))\n              or not self.tls_protected(response_url)):\n            return self.origin_referrer(response_url)\n\n\nclass UnsafeUrlPolicy(ReferrerPolicy):\n    \"\"\"\n    https://www.w3.org/TR/referrer-policy/#referrer-policy-unsafe-url\n\n    The \"unsafe-url\" policy specifies that a full URL, stripped for use as a referrer,\n    is sent along with both cross-origin requests\n    and same-origin requests made from a particular request client.\n\n    Note: The policy's name doesn't lie; it is unsafe.\n    This policy will leak origins and paths from TLS-protected resources\n    to insecure origins.\n    Carefully consider the impact of setting such a policy for potentially sensitive documents.\n    \"\"\"\n    name = POLICY_UNSAFE_URL\n\n    def referrer(self, response_url, request_url):\n        return self.stripped_referrer(response_url)\n\n\nclass DefaultReferrerPolicy(NoReferrerWhenDowngradePolicy):\n    \"\"\"\n    A variant of \"no-referrer-when-downgrade\",\n    with the addition that \"Referer\" is not sent if the parent request was\n    using ``file://`` or ``s3://`` scheme.\n    \"\"\"\n    NOREFERRER_SCHEMES = LOCAL_SCHEMES + ('file', 's3')\n    name = POLICY_SCRAPY_DEFAULT\n\n\n_policy_classes = {p.name: p for p in (\n    NoReferrerPolicy,\n    NoReferrerWhenDowngradePolicy,\n    SameOriginPolicy,\n    OriginPolicy,\n    StrictOriginPolicy,\n    OriginWhenCrossOriginPolicy,\n    StrictOriginWhenCrossOriginPolicy,\n    UnsafeUrlPolicy,\n    DefaultReferrerPolicy,\n)}\n\n# Reference: https://www.w3.org/TR/referrer-policy/#referrer-policy-empty-string\n_policy_classes[''] = NoReferrerWhenDowngradePolicy\n\n\ndef _load_policy_class(policy, warning_only=False):\n    \"\"\"\n    Expect a string for the path to the policy class,\n    otherwise try to interpret the string as a standard value\n    from https://www.w3.org/TR/referrer-policy/#referrer-policies\n    \"\"\"\n    try:\n        return load_object(policy)\n    except ValueError:\n        try:\n            return _policy_classes[policy.lower()]\n        except KeyError:\n            msg = \"Could not load referrer policy %r\" % policy\n            if not warning_only:\n                raise RuntimeError(msg)\n            else:\n                warnings.warn(msg, RuntimeWarning)\n                return None\n\n\nclass RefererMiddleware(object):\n\n    def __init__(self, settings=None):\n        self.default_policy = DefaultReferrerPolicy\n        if settings is not None:\n            self.default_policy = _load_policy_class(\n                settings.get('REFERRER_POLICY'))\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        if not crawler.settings.getbool('REFERER_ENABLED'):\n            raise NotConfigured\n        mw = cls(crawler.settings)\n\n        # Note: this hook is a bit of a hack to intercept redirections\n        crawler.signals.connect(mw.request_scheduled, signal=signals.request_scheduled)\n\n        return mw\n\n    def policy(self, resp_or_url, request):\n        \"\"\"\n        Determine Referrer-Policy to use from a parent Response (or URL),\n        and a Request to be sent.\n\n        - if a valid policy is set in Request meta, it is used.\n        - if the policy is set in meta but is wrong (e.g. a typo error),\n          the policy from settings is used\n        - if the policy is not set in Request meta,\n          but there is a Referrer-policy header in the parent response,\n          it is used if valid\n        - otherwise, the policy from settings is used.\n        \"\"\"\n        policy_name = request.meta.get('referrer_policy')\n        if policy_name is None:\n            if isinstance(resp_or_url, Response):\n                policy_header = resp_or_url.headers.get('Referrer-Policy')\n                if policy_header is not None:\n                    policy_name = to_native_str(policy_header.decode('latin1'))\n        if policy_name is None:\n            return self.default_policy()\n\n        cls = _load_policy_class(policy_name, warning_only=True)\n        return cls() if cls else self.default_policy()\n\n    def process_spider_output(self, response, result, spider):\n        def _set_referer(r):\n            if isinstance(r, Request):\n                referrer = self.policy(response, r).referrer(response.url, r.url)\n                if referrer is not None:\n                    r.headers.setdefault('Referer', referrer)\n            return r\n        return (_set_referer(r) for r in result or ())\n\n    def request_scheduled(self, request, spider):\n        # check redirected request to patch \"Referer\" header if necessary\n        redirected_urls = request.meta.get('redirect_urls', [])\n        if redirected_urls:\n            request_referrer = request.headers.get('Referer')\n            # we don't patch the referrer value if there is none\n            if request_referrer is not None:\n                # the request's referrer header value acts as a surrogate\n                # for the parent response URL\n                #\n                # Note: if the 3xx response contained a Referrer-Policy header,\n                #       the information is not available using this hook\n                parent_url = safe_url_string(request_referrer)\n                policy_referrer = self.policy(parent_url, request).referrer(\n                    parent_url, request.url)\n                if policy_referrer != request_referrer:\n                    if policy_referrer is None:\n                        request.headers.pop('Referer')\n                    else:\n                        request.headers['Referer'] = policy_referrer\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/spidermiddlewares/urllength.py",
    "content": "\"\"\"\nUrl Length Spider Middleware\n\nSee documentation in docs/topics/spider-middleware.rst\n\"\"\"\n\nimport logging\n\nfrom scrapy.http import Request\nfrom scrapy.exceptions import NotConfigured\n\nlogger = logging.getLogger(__name__)\n\n\nclass UrlLengthMiddleware(object):\n\n    def __init__(self, maxlength):\n        self.maxlength = maxlength\n\n    @classmethod\n    def from_settings(cls, settings):\n        maxlength = settings.getint('URLLENGTH_LIMIT')\n        if not maxlength:\n            raise NotConfigured\n        return cls(maxlength)\n\n    def process_spider_output(self, response, result, spider):\n        def _filter(request):\n            if isinstance(request, Request) and len(request.url) > self.maxlength:\n                logger.debug(\"Ignoring link (url length > %(maxlength)d): %(url)s \",\n                             {'maxlength': self.maxlength, 'url': request.url},\n                             extra={'spider': spider})\n                return False\n            else:\n                return True\n\n        return (r for r in result or () if _filter(r))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/spiders/__init__.py",
    "content": "\"\"\"\nBase class for Scrapy spiders\n\nSee documentation in docs/topics/spiders.rst\n\"\"\"\nimport logging\nimport warnings\n\nfrom scrapy import signals\nfrom scrapy.http import Request\nfrom scrapy.utils.trackref import object_ref\nfrom scrapy.utils.url import url_is_from_spider\nfrom scrapy.exceptions import ScrapyDeprecationWarning\nfrom scrapy.utils.deprecate import method_is_overridden\n\n\nclass Spider(object_ref):\n    \"\"\"Base class for scrapy spiders. All spiders must inherit from this\n    class.\n    \"\"\"\n\n    name = None\n    custom_settings = None\n\n    def __init__(self, name=None, **kwargs):\n        if name is not None:\n            self.name = name\n        elif not getattr(self, 'name', None):\n            raise ValueError(\"%s must have a name\" % type(self).__name__)\n        self.__dict__.update(kwargs)\n        if not hasattr(self, 'start_urls'):\n            self.start_urls = []\n\n    @property\n    def logger(self):\n        logger = logging.getLogger(self.name)\n        return logging.LoggerAdapter(logger, {'spider': self})\n\n    def log(self, message, level=logging.DEBUG, **kw):\n        \"\"\"Log the given message at the given log level\n\n        This helper wraps a log call to the logger within the spider, but you\n        can use it directly (e.g. Spider.logger.info('msg')) or use any other\n        Python logger too.\n        \"\"\"\n        self.logger.log(level, message, **kw)\n\n    @classmethod\n    def from_crawler(cls, crawler, *args, **kwargs):\n        spider = cls(*args, **kwargs)\n        spider._set_crawler(crawler)\n        return spider\n\n    def _set_crawler(self, crawler):\n        self.crawler = crawler\n        self.settings = crawler.settings\n        crawler.signals.connect(self.close, signals.spider_closed)\n\n    def start_requests(self):\n        cls = self.__class__\n        if method_is_overridden(cls, Spider, 'make_requests_from_url'):\n            warnings.warn(\n                \"Spider.make_requests_from_url method is deprecated; it \"\n                \"won't be called in future Scrapy releases. Please \"\n                \"override Spider.start_requests method instead (see %s.%s).\" % (\n                    cls.__module__, cls.__name__\n                ),\n            )\n            for url in self.start_urls:\n                yield self.make_requests_from_url(url)\n        else:\n            for url in self.start_urls:\n                yield Request(url, dont_filter=True)\n\n    def make_requests_from_url(self, url):\n        \"\"\" This method is deprecated. \"\"\"\n        return Request(url, dont_filter=True)\n\n    def parse(self, response):\n        raise NotImplementedError('{}.parse callback is not defined'.format(self.__class__.__name__))\n\n    @classmethod\n    def update_settings(cls, settings):\n        settings.setdict(cls.custom_settings or {}, priority='spider')\n\n    @classmethod\n    def handles_request(cls, request):\n        return url_is_from_spider(request.url, cls)\n\n    @staticmethod\n    def close(spider, reason):\n        closed = getattr(spider, 'closed', None)\n        if callable(closed):\n            return closed(reason)\n\n    def __str__(self):\n        return \"<%s %r at 0x%0x>\" % (type(self).__name__, self.name, id(self))\n\n    __repr__ = __str__\n\n\n# Top-level imports\nfrom scrapy.spiders.crawl import CrawlSpider, Rule\nfrom scrapy.spiders.feed import XMLFeedSpider, CSVFeedSpider\nfrom scrapy.spiders.sitemap import SitemapSpider\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/spiders/crawl.py",
    "content": "\"\"\"\nThis modules implements the CrawlSpider which is the recommended spider to use\nfor scraping typical web sites that requires crawling pages.\n\nSee documentation in docs/topics/spiders.rst\n\"\"\"\n\nimport copy\nimport warnings\n\nimport six\n\nfrom scrapy.exceptions import ScrapyDeprecationWarning\nfrom scrapy.http import Request, HtmlResponse\nfrom scrapy.utils.spider import iterate_spider_output\nfrom scrapy.utils.python import get_func_args\nfrom scrapy.spiders import Spider\n\n\ndef _identity(request, response):\n    return request\n\n\ndef _get_method(method, spider):\n    if callable(method):\n        return method\n    elif isinstance(method, six.string_types):\n        return getattr(spider, method, None)\n\n\nclass Rule(object):\n\n    def __init__(self, link_extractor, callback=None, cb_kwargs=None, follow=None, process_links=None, process_request=None):\n        self.link_extractor = link_extractor\n        self.callback = callback\n        self.cb_kwargs = cb_kwargs or {}\n        self.process_links = process_links\n        self.process_request = process_request or _identity\n        self.process_request_argcount = None\n        self.follow = follow if follow is not None else not callback\n\n    def _compile(self, spider):\n        self.callback = _get_method(self.callback, spider)\n        self.process_links = _get_method(self.process_links, spider)\n        self.process_request = _get_method(self.process_request, spider)\n        self.process_request_argcount = len(get_func_args(self.process_request))\n        if self.process_request_argcount == 1:\n            msg = 'Rule.process_request should accept two arguments (request, response), accepting only one is deprecated'\n            warnings.warn(msg, category=ScrapyDeprecationWarning, stacklevel=2)\n\n    def _process_request(self, request, response):\n        \"\"\"\n        Wrapper around the request processing function to maintain backward\n        compatibility with functions that do not take a Response object\n        \"\"\"\n        args = [request] if self.process_request_argcount == 1 else [request, response]\n        return self.process_request(*args)\n\n\nclass CrawlSpider(Spider):\n\n    rules = ()\n\n    def __init__(self, *a, **kw):\n        super(CrawlSpider, self).__init__(*a, **kw)\n        self._compile_rules()\n\n    def parse(self, response):\n        return self._parse_response(response, self.parse_start_url, cb_kwargs={}, follow=True)\n\n    def parse_start_url(self, response):\n        return []\n\n    def process_results(self, response, results):\n        return results\n\n    def _build_request(self, rule, link):\n        r = Request(url=link.url, callback=self._response_downloaded)\n        r.meta.update(rule=rule, link_text=link.text)\n        return r\n\n    def _requests_to_follow(self, response):\n        if not isinstance(response, HtmlResponse):\n            return\n        seen = set()\n        for n, rule in enumerate(self._rules):\n            links = [lnk for lnk in rule.link_extractor.extract_links(response)\n                     if lnk not in seen]\n            if links and rule.process_links:\n                links = rule.process_links(links)\n            for link in links:\n                seen.add(link)\n                request = self._build_request(n, link)\n                yield rule._process_request(request, response)\n\n    def _response_downloaded(self, response):\n        rule = self._rules[response.meta['rule']]\n        return self._parse_response(response, rule.callback, rule.cb_kwargs, rule.follow)\n\n    def _parse_response(self, response, callback, cb_kwargs, follow=True):\n        if callback:\n            cb_res = callback(response, **cb_kwargs) or ()\n            cb_res = self.process_results(response, cb_res)\n            for requests_or_item in iterate_spider_output(cb_res):\n                yield requests_or_item\n\n        if follow and self._follow_links:\n            for request_or_item in self._requests_to_follow(response):\n                yield request_or_item\n\n    def _compile_rules(self):\n        self._rules = [copy.copy(r) for r in self.rules]\n        for rule in self._rules:\n            rule._compile(self)\n\n    @classmethod\n    def from_crawler(cls, crawler, *args, **kwargs):\n        spider = super(CrawlSpider, cls).from_crawler(crawler, *args, **kwargs)\n        spider._follow_links = crawler.settings.getbool(\n            'CRAWLSPIDER_FOLLOW_LINKS', True)\n        return spider\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/spiders/feed.py",
    "content": "\"\"\"\nThis module implements the XMLFeedSpider which is the recommended spider to use\nfor scraping from an XML feed.\n\nSee documentation in docs/topics/spiders.rst\n\"\"\"\nfrom scrapy.spiders import Spider\nfrom scrapy.utils.iterators import xmliter, csviter\nfrom scrapy.utils.spider import iterate_spider_output\nfrom scrapy.selector import Selector\nfrom scrapy.exceptions import NotConfigured, NotSupported\n\n\nclass XMLFeedSpider(Spider):\n    \"\"\"\n    This class intends to be the base class for spiders that scrape\n    from XML feeds.\n\n    You can choose whether to parse the file using the 'iternodes' iterator, an\n    'xml' selector, or an 'html' selector.  In most cases, it's convenient to\n    use iternodes, since it's a faster and cleaner.\n    \"\"\"\n\n    iterator = 'iternodes'\n    itertag = 'item'\n    namespaces = ()\n\n    def process_results(self, response, results):\n        \"\"\"This overridable method is called for each result (item or request)\n        returned by the spider, and it's intended to perform any last time\n        processing required before returning the results to the framework core,\n        for example setting the item GUIDs. It receives a list of results and\n        the response which originated that results. It must return a list of\n        results (Items or Requests).\n        \"\"\"\n        return results\n\n    def adapt_response(self, response):\n        \"\"\"You can override this function in order to make any changes you want\n        to into the feed before parsing it. This function must return a\n        response.\n        \"\"\"\n        return response\n\n    def parse_node(self, response, selector):\n        \"\"\"This method must be overriden with your custom spider functionality\"\"\"\n        if hasattr(self, 'parse_item'):  # backward compatibility\n            return self.parse_item(response, selector)\n        raise NotImplementedError\n\n    def parse_nodes(self, response, nodes):\n        \"\"\"This method is called for the nodes matching the provided tag name\n        (itertag). Receives the response and an Selector for each node.\n        Overriding this method is mandatory. Otherwise, you spider won't work.\n        This method must return either a BaseItem, a Request, or a list\n        containing any of them.\n        \"\"\"\n\n        for selector in nodes:\n            ret = iterate_spider_output(self.parse_node(response, selector))\n            for result_item in self.process_results(response, ret):\n                yield result_item\n\n    def parse(self, response):\n        if not hasattr(self, 'parse_node'):\n            raise NotConfigured('You must define parse_node method in order to scrape this XML feed')\n\n        response = self.adapt_response(response)\n        if self.iterator == 'iternodes':\n            nodes = self._iternodes(response)\n        elif self.iterator == 'xml':\n            selector = Selector(response, type='xml')\n            self._register_namespaces(selector)\n            nodes = selector.xpath('//%s' % self.itertag)\n        elif self.iterator == 'html':\n            selector = Selector(response, type='html')\n            self._register_namespaces(selector)\n            nodes = selector.xpath('//%s' % self.itertag)\n        else:\n            raise NotSupported('Unsupported node iterator')\n\n        return self.parse_nodes(response, nodes)\n\n    def _iternodes(self, response):\n        for node in xmliter(response, self.itertag):\n            self._register_namespaces(node)\n            yield node\n\n    def _register_namespaces(self, selector):\n        for (prefix, uri) in self.namespaces:\n            selector.register_namespace(prefix, uri)\n\n\nclass CSVFeedSpider(Spider):\n    \"\"\"Spider for parsing CSV feeds.\n    It receives a CSV file in a response; iterates through each of its rows,\n    and calls parse_row with a dict containing each field's data.\n\n    You can set some options regarding the CSV file, such as the delimiter, quotechar\n    and the file's headers.\n    \"\"\"\n\n    delimiter = None # When this is None, python's csv module's default delimiter is used\n    quotechar = None # When this is None, python's csv module's default quotechar is used\n    headers = None\n\n    def process_results(self, response, results):\n        \"\"\"This method has the same purpose as the one in XMLFeedSpider\"\"\"\n        return results\n\n    def adapt_response(self, response):\n        \"\"\"This method has the same purpose as the one in XMLFeedSpider\"\"\"\n        return response\n\n    def parse_row(self, response, row):\n        \"\"\"This method must be overriden with your custom spider functionality\"\"\"\n        raise NotImplementedError\n\n    def parse_rows(self, response):\n        \"\"\"Receives a response and a dict (representing each row) with a key for\n        each provided (or detected) header of the CSV file.  This spider also\n        gives the opportunity to override adapt_response and\n        process_results methods for pre and post-processing purposes.\n        \"\"\"\n\n        for row in csviter(response, self.delimiter, self.headers, self.quotechar):\n            ret = iterate_spider_output(self.parse_row(response, row))\n            for result_item in self.process_results(response, ret):\n                yield result_item\n\n    def parse(self, response):\n        if not hasattr(self, 'parse_row'):\n            raise NotConfigured('You must define parse_row method in order to scrape this CSV feed')\n        response = self.adapt_response(response)\n        return self.parse_rows(response)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/spiders/init.py",
    "content": "from scrapy.spiders import Spider\nfrom scrapy.utils.spider import iterate_spider_output\n\n\nclass InitSpider(Spider):\n    \"\"\"Base Spider with initialization facilities\"\"\"\n\n    def start_requests(self):\n        self._postinit_reqs = super(InitSpider, self).start_requests()\n        return iterate_spider_output(self.init_request())\n\n    def initialized(self, response=None):\n        \"\"\"This method must be set as the callback of your last initialization\n        request. See self.init_request() docstring for more info.\n        \"\"\"\n        return self.__dict__.pop('_postinit_reqs')\n\n    def init_request(self):\n        \"\"\"This function should return one initialization request, with the\n        self.initialized method as callback. When the self.initialized method\n        is called this spider is considered initialized. If you need to perform\n        several requests for initializing your spider, you can do so by using\n        different callbacks. The only requirement is that the final callback\n        (of the last initialization request) must be self.initialized.\n\n        The default implementation calls self.initialized immediately, and\n        means that no initialization is needed. This method should be\n        overridden only when you need to perform requests to initialize your\n        spider\n        \"\"\"\n        return self.initialized()\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/spiders/sitemap.py",
    "content": "import re\nimport logging\nimport six\n\nfrom scrapy.spiders import Spider\nfrom scrapy.http import Request, XmlResponse\nfrom scrapy.utils.sitemap import Sitemap, sitemap_urls_from_robots\nfrom scrapy.utils.gz import gunzip, gzip_magic_number\n\n\nlogger = logging.getLogger(__name__)\n\n\nclass SitemapSpider(Spider):\n\n    sitemap_urls = ()\n    sitemap_rules = [('', 'parse')]\n    sitemap_follow = ['']\n    sitemap_alternate_links = False\n\n    def __init__(self, *a, **kw):\n        super(SitemapSpider, self).__init__(*a, **kw)\n        self._cbs = []\n        for r, c in self.sitemap_rules:\n            if isinstance(c, six.string_types):\n                c = getattr(self, c)\n            self._cbs.append((regex(r), c))\n        self._follow = [regex(x) for x in self.sitemap_follow]\n\n    def start_requests(self):\n        for url in self.sitemap_urls:\n            yield Request(url, self._parse_sitemap)\n\n    def sitemap_filter(self, entries):\n        \"\"\"This method can be used to filter sitemap entries by their\n        attributes, for example, you can filter locs with lastmod greater\n        than a given date (see docs).\n        \"\"\"\n        for entry in entries:\n            yield entry\n\n    def _parse_sitemap(self, response):\n        if response.url.endswith('/robots.txt'):\n            for url in sitemap_urls_from_robots(response.text, base_url=response.url):\n                yield Request(url, callback=self._parse_sitemap)\n        else:\n            body = self._get_sitemap_body(response)\n            if body is None:\n                logger.warning(\"Ignoring invalid sitemap: %(response)s\",\n                               {'response': response}, extra={'spider': self})\n                return\n\n            s = Sitemap(body)\n            it = self.sitemap_filter(s)\n\n            if s.type == 'sitemapindex':\n                for loc in iterloc(it, self.sitemap_alternate_links):\n                    if any(x.search(loc) for x in self._follow):\n                        yield Request(loc, callback=self._parse_sitemap)\n            elif s.type == 'urlset':\n                for loc in iterloc(it, self.sitemap_alternate_links):\n                    for r, c in self._cbs:\n                        if r.search(loc):\n                            yield Request(loc, callback=c)\n                            break\n\n    def _get_sitemap_body(self, response):\n        \"\"\"Return the sitemap body contained in the given response,\n        or None if the response is not a sitemap.\n        \"\"\"\n        if isinstance(response, XmlResponse):\n            return response.body\n        elif gzip_magic_number(response):\n            return gunzip(response.body)\n        # actual gzipped sitemap files are decompressed above ;\n        # if we are here (response body is not gzipped)\n        # and have a response for .xml.gz,\n        # it usually means that it was already gunzipped\n        # by HttpCompression middleware,\n        # the HTTP response being sent with \"Content-Encoding: gzip\"\n        # without actually being a .xml.gz file in the first place,\n        # merely XML gzip-compressed on the fly,\n        # in other word, here, we have plain XML\n        elif response.url.endswith('.xml') or response.url.endswith('.xml.gz'):\n            return response.body\n\n\ndef regex(x):\n    if isinstance(x, six.string_types):\n        return re.compile(x)\n    return x\n\n\ndef iterloc(it, alt=False):\n    for d in it:\n        yield d['loc']\n\n        # Also consider alternate URLs (xhtml:link rel=\"alternate\")\n        if alt and 'alternate' in d:\n            for l in d['alternate']:\n                yield l\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/squeues.py",
    "content": "\"\"\"\nScheduler queues\n\"\"\"\n\nimport marshal\nfrom six.moves import cPickle as pickle\n\nfrom queuelib import queue\n\n\ndef _serializable_queue(queue_class, serialize, deserialize):\n\n    class SerializableQueue(queue_class):\n\n        def push(self, obj):\n            s = serialize(obj)\n            super(SerializableQueue, self).push(s)\n\n        def pop(self):\n            s = super(SerializableQueue, self).pop()\n            if s:\n                return deserialize(s)\n\n    return SerializableQueue\n\n\ndef _pickle_serialize(obj):\n    try:\n        return pickle.dumps(obj, protocol=2)\n    # Python <= 3.4 raises pickle.PicklingError here while\n    # 3.5 <= Python < 3.6 raises AttributeError and\n    # Python >= 3.6 raises TypeError\n    except (pickle.PicklingError, AttributeError, TypeError) as e:\n        raise ValueError(str(e))\n\n\nPickleFifoDiskQueue = _serializable_queue(queue.FifoDiskQueue,\n    _pickle_serialize, pickle.loads)\nPickleLifoDiskQueue = _serializable_queue(queue.LifoDiskQueue,\n    _pickle_serialize, pickle.loads)\nMarshalFifoDiskQueue = _serializable_queue(queue.FifoDiskQueue,\n    marshal.dumps, marshal.loads)\nMarshalLifoDiskQueue = _serializable_queue(queue.LifoDiskQueue,\n    marshal.dumps, marshal.loads)\nFifoMemoryQueue = queue.FifoMemoryQueue\nLifoMemoryQueue = queue.LifoMemoryQueue\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/statscollectors.py",
    "content": "\"\"\"\nScrapy extension for collecting scraping stats\n\"\"\"\nimport pprint\nimport logging\n\nlogger = logging.getLogger(__name__)\n\n\nclass StatsCollector(object):\n\n    def __init__(self, crawler):\n        self._dump = crawler.settings.getbool('STATS_DUMP')\n        self._stats = {}\n\n    def get_value(self, key, default=None, spider=None):\n        return self._stats.get(key, default)\n\n    def get_stats(self, spider=None):\n        return self._stats\n\n    def set_value(self, key, value, spider=None):\n        self._stats[key] = value\n\n    def set_stats(self, stats, spider=None):\n        self._stats = stats\n\n    def inc_value(self, key, count=1, start=0, spider=None):\n        d = self._stats\n        d[key] = d.setdefault(key, start) + count\n\n    def max_value(self, key, value, spider=None):\n        self._stats[key] = max(self._stats.setdefault(key, value), value)\n\n    def min_value(self, key, value, spider=None):\n        self._stats[key] = min(self._stats.setdefault(key, value), value)\n\n    def clear_stats(self, spider=None):\n        self._stats.clear()\n\n    def open_spider(self, spider):\n        pass\n\n    def close_spider(self, spider, reason):\n        if self._dump:\n            logger.info(\"Dumping Scrapy stats:\\n\" + pprint.pformat(self._stats),\n                        extra={'spider': spider})\n        self._persist_stats(self._stats, spider)\n\n    def _persist_stats(self, stats, spider):\n        pass\n\n\nclass MemoryStatsCollector(StatsCollector):\n\n    def __init__(self, crawler):\n        super(MemoryStatsCollector, self).__init__(crawler)\n        self.spider_stats = {}\n\n    def _persist_stats(self, stats, spider):\n        self.spider_stats[spider.name] = stats\n\n\nclass DummyStatsCollector(StatsCollector):\n\n    def get_value(self, key, default=None, spider=None):\n        return default\n\n    def set_value(self, key, value, spider=None):\n        pass\n\n    def set_stats(self, stats, spider=None):\n        pass\n\n    def inc_value(self, key, count=1, start=0, spider=None):\n        pass\n\n    def max_value(self, key, value, spider=None):\n        pass\n\n    def min_value(self, key, value, spider=None):\n        pass\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/templates/project/module/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/templates/project/module/items.py.tmpl",
    "content": "# -*- coding: utf-8 -*-\n\n# Define here the models for your scraped items\n#\n# See documentation in:\n# https://docs.scrapy.org/en/latest/topics/items.html\n\nimport scrapy\n\n\nclass ${ProjectName}Item(scrapy.Item):\n    # define the fields for your item here like:\n    # name = scrapy.Field()\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/templates/project/module/middlewares.py.tmpl",
    "content": "# -*- coding: utf-8 -*-\n\n# Define here the models for your spider middleware\n#\n# See documentation in:\n# https://docs.scrapy.org/en/latest/topics/spider-middleware.html\n\nfrom scrapy import signals\n\n\nclass ${ProjectName}SpiderMiddleware(object):\n    # Not all methods need to be defined. If a method is not defined,\n    # scrapy acts as if the spider middleware does not modify the\n    # passed objects.\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        # This method is used by Scrapy to create your spiders.\n        s = cls()\n        crawler.signals.connect(s.spider_opened, signal=signals.spider_opened)\n        return s\n\n    def process_spider_input(self, response, spider):\n        # Called for each response that goes through the spider\n        # middleware and into the spider.\n\n        # Should return None or raise an exception.\n        return None\n\n    def process_spider_output(self, response, result, spider):\n        # Called with the results returned from the Spider, after\n        # it has processed the response.\n\n        # Must return an iterable of Request, dict or Item objects.\n        for i in result:\n            yield i\n\n    def process_spider_exception(self, response, exception, spider):\n        # Called when a spider or process_spider_input() method\n        # (from other spider middleware) raises an exception.\n\n        # Should return either None or an iterable of Request, dict\n        # or Item objects.\n        pass\n\n    def process_start_requests(self, start_requests, spider):\n        # Called with the start requests of the spider, and works\n        # similarly to the process_spider_output() method, except\n        # that it doesn’t have a response associated.\n\n        # Must return only requests (not items).\n        for r in start_requests:\n            yield r\n\n    def spider_opened(self, spider):\n        spider.logger.info('Spider opened: %s' % spider.name)\n\n\nclass ${ProjectName}DownloaderMiddleware(object):\n    # Not all methods need to be defined. If a method is not defined,\n    # scrapy acts as if the downloader middleware does not modify the\n    # passed objects.\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        # This method is used by Scrapy to create your spiders.\n        s = cls()\n        crawler.signals.connect(s.spider_opened, signal=signals.spider_opened)\n        return s\n\n    def process_request(self, request, spider):\n        # Called for each request that goes through the downloader\n        # middleware.\n\n        # Must either:\n        # - return None: continue processing this request\n        # - or return a Response object\n        # - or return a Request object\n        # - or raise IgnoreRequest: process_exception() methods of\n        #   installed downloader middleware will be called\n        return None\n\n    def process_response(self, request, response, spider):\n        # Called with the response returned from the downloader.\n\n        # Must either;\n        # - return a Response object\n        # - return a Request object\n        # - or raise IgnoreRequest\n        return response\n\n    def process_exception(self, request, exception, spider):\n        # Called when a download handler or a process_request()\n        # (from other downloader middleware) raises an exception.\n\n        # Must either:\n        # - return None: continue processing this exception\n        # - return a Response object: stops process_exception() chain\n        # - return a Request object: stops process_exception() chain\n        pass\n\n    def spider_opened(self, spider):\n        spider.logger.info('Spider opened: %s' % spider.name)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/templates/project/module/pipelines.py.tmpl",
    "content": "# -*- coding: utf-8 -*-\n\n# Define your item pipelines here\n#\n# Don't forget to add your pipeline to the ITEM_PIPELINES setting\n# See: https://docs.scrapy.org/en/latest/topics/item-pipeline.html\n\n\nclass ${ProjectName}Pipeline(object):\n    def process_item(self, item, spider):\n        return item\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/templates/project/module/settings.py.tmpl",
    "content": "# -*- coding: utf-8 -*-\n\n# Scrapy settings for $project_name project\n#\n# For simplicity, this file contains only settings considered important or\n# commonly used. You can find more settings consulting the documentation:\n#\n#     https://docs.scrapy.org/en/latest/topics/settings.html\n#     https://docs.scrapy.org/en/latest/topics/downloader-middleware.html\n#     https://docs.scrapy.org/en/latest/topics/spider-middleware.html\n\nBOT_NAME = '$project_name'\n\nSPIDER_MODULES = ['$project_name.spiders']\nNEWSPIDER_MODULE = '$project_name.spiders'\n\n\n# Crawl responsibly by identifying yourself (and your website) on the user-agent\n#USER_AGENT = '$project_name (+http://www.yourdomain.com)'\n\n# Obey robots.txt rules\nROBOTSTXT_OBEY = True\n\n# Configure maximum concurrent requests performed by Scrapy (default: 16)\n#CONCURRENT_REQUESTS = 32\n\n# Configure a delay for requests for the same website (default: 0)\n# See https://docs.scrapy.org/en/latest/topics/settings.html#download-delay\n# See also autothrottle settings and docs\n#DOWNLOAD_DELAY = 3\n# The download delay setting will honor only one of:\n#CONCURRENT_REQUESTS_PER_DOMAIN = 16\n#CONCURRENT_REQUESTS_PER_IP = 16\n\n# Disable cookies (enabled by default)\n#COOKIES_ENABLED = False\n\n# Disable Telnet Console (enabled by default)\n#TELNETCONSOLE_ENABLED = False\n\n# Override the default request headers:\n#DEFAULT_REQUEST_HEADERS = {\n#   'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',\n#   'Accept-Language': 'en',\n#}\n\n# Enable or disable spider middlewares\n# See https://docs.scrapy.org/en/latest/topics/spider-middleware.html\n#SPIDER_MIDDLEWARES = {\n#    '$project_name.middlewares.${ProjectName}SpiderMiddleware': 543,\n#}\n\n# Enable or disable downloader middlewares\n# See https://docs.scrapy.org/en/latest/topics/downloader-middleware.html\n#DOWNLOADER_MIDDLEWARES = {\n#    '$project_name.middlewares.${ProjectName}DownloaderMiddleware': 543,\n#}\n\n# Enable or disable extensions\n# See https://docs.scrapy.org/en/latest/topics/extensions.html\n#EXTENSIONS = {\n#    'scrapy.extensions.telnet.TelnetConsole': None,\n#}\n\n# Configure item pipelines\n# See https://docs.scrapy.org/en/latest/topics/item-pipeline.html\n#ITEM_PIPELINES = {\n#    '$project_name.pipelines.${ProjectName}Pipeline': 300,\n#}\n\n# Enable and configure the AutoThrottle extension (disabled by default)\n# See https://docs.scrapy.org/en/latest/topics/autothrottle.html\n#AUTOTHROTTLE_ENABLED = True\n# The initial download delay\n#AUTOTHROTTLE_START_DELAY = 5\n# The maximum download delay to be set in case of high latencies\n#AUTOTHROTTLE_MAX_DELAY = 60\n# The average number of requests Scrapy should be sending in parallel to\n# each remote server\n#AUTOTHROTTLE_TARGET_CONCURRENCY = 1.0\n# Enable showing throttling stats for every response received:\n#AUTOTHROTTLE_DEBUG = False\n\n# Enable and configure HTTP caching (disabled by default)\n# See https://docs.scrapy.org/en/latest/topics/downloader-middleware.html#httpcache-middleware-settings\n#HTTPCACHE_ENABLED = True\n#HTTPCACHE_EXPIRATION_SECS = 0\n#HTTPCACHE_DIR = 'httpcache'\n#HTTPCACHE_IGNORE_HTTP_CODES = []\n#HTTPCACHE_STORAGE = 'scrapy.extensions.httpcache.FilesystemCacheStorage'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/templates/project/module/spiders/__init__.py",
    "content": "# This package will contain the spiders of your Scrapy project\n#\n# Please refer to the documentation for information on how to create and manage\n# your spiders.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/templates/project/scrapy.cfg",
    "content": "# Automatically created by: scrapy startproject\n#\n# For more information about the [deploy] section see:\n# https://scrapyd.readthedocs.io/en/latest/deploy.html\n\n[settings]\ndefault = ${project_name}.settings\n\n[deploy]\n#url = http://localhost:6800/\nproject = ${project_name}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/templates/spiders/basic.tmpl",
    "content": "# -*- coding: utf-8 -*-\nimport scrapy\n\n\nclass $classname(scrapy.Spider):\n    name = '$name'\n    allowed_domains = ['$domain']\n    start_urls = ['http://$domain/']\n\n    def parse(self, response):\n        pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/templates/spiders/crawl.tmpl",
    "content": "# -*- coding: utf-8 -*-\nimport scrapy\nfrom scrapy.linkextractors import LinkExtractor\nfrom scrapy.spiders import CrawlSpider, Rule\n\n\nclass $classname(CrawlSpider):\n    name = '$name'\n    allowed_domains = ['$domain']\n    start_urls = ['http://$domain/']\n\n    rules = (\n        Rule(LinkExtractor(allow=r'Items/'), callback='parse_item', follow=True),\n    )\n\n    def parse_item(self, response):\n        item = {}\n        #item['domain_id'] = response.xpath('//input[@id=\"sid\"]/@value').get()\n        #item['name'] = response.xpath('//div[@id=\"name\"]').get()\n        #item['description'] = response.xpath('//div[@id=\"description\"]').get()\n        return item\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/templates/spiders/csvfeed.tmpl",
    "content": "# -*- coding: utf-8 -*-\nfrom scrapy.spiders import CSVFeedSpider\n\n\nclass $classname(CSVFeedSpider):\n    name = '$name'\n    allowed_domains = ['$domain']\n    start_urls = ['http://$domain/feed.csv']\n    # headers = ['id', 'name', 'description', 'image_link']\n    # delimiter = '\\t'\n\n    # Do any adaptations you need here\n    #def adapt_response(self, response):\n    #    return response\n\n    def parse_row(self, response, row):\n        i = {}\n        #i['url'] = row['url']\n        #i['name'] = row['name']\n        #i['description'] = row['description']\n        return i\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/templates/spiders/xmlfeed.tmpl",
    "content": "# -*- coding: utf-8 -*-\nfrom scrapy.spiders import XMLFeedSpider\n\n\nclass $classname(XMLFeedSpider):\n    name = '$name'\n    allowed_domains = ['$domain']\n    start_urls = ['http://$domain/feed.xml']\n    iterator = 'iternodes' # you can change this; see the docs\n    itertag = 'item' # change it accordingly\n\n    def parse_node(self, response, selector):\n        item = {}\n        #item['url'] = selector.select('url').get()\n        #item['name'] = selector.select('name').get()\n        #item['description'] = selector.select('description').get()\n        return item\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/__init__.py",
    "content": ""
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/benchserver.py",
    "content": "import random\nfrom six.moves.urllib.parse import urlencode\nfrom twisted.web.server import Site\nfrom twisted.web.resource import Resource\nfrom twisted.internet import reactor\n\n\nclass Root(Resource):\n\n    isLeaf = True\n\n    def getChild(self, name, request):\n        return self\n\n    def render(self, request):\n        total = _getarg(request, b'total', 100, int)\n        show = _getarg(request, b'show', 10, int)\n        nlist = [random.randint(1, total) for _ in range(show)]\n        request.write(b\"<html><head></head><body>\")\n        args = request.args.copy()\n        for nl in nlist:\n            args['n'] = nl\n            argstr = urlencode(args, doseq=True)\n            request.write(\"<a href='/follow?{0}'>follow {1}</a><br>\"\n                          .format(argstr, nl).encode('utf8'))\n        request.write(b\"</body></html>\")\n        return b''\n\n\ndef _getarg(request, name, default=None, type=str):\n    return type(request.args[name][0]) \\\n        if name in request.args else default\n\n\nif __name__ == '__main__':\n    root = Root()\n    factory = Site(root)\n    httpPort = reactor.listenTCP(8998, Site(root))\n\n    def _print_listening():\n        httpHost = httpPort.getHost()\n        print(\"Bench server at http://{}:{}\".format(httpHost.host, httpHost.port))\n    reactor.callWhenRunning(_print_listening)\n    reactor.run()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/boto.py",
    "content": "\"\"\"Boto/botocore helpers\"\"\"\n\nfrom __future__ import absolute_import\nimport six\n\nfrom scrapy.exceptions import NotConfigured\n\n\ndef is_botocore():\n    try:\n        import botocore\n        return True\n    except ImportError:\n        if six.PY2:\n            try:\n                import boto\n                return False\n            except ImportError:\n                raise NotConfigured('missing botocore or boto library')\n        else:\n            raise NotConfigured('missing botocore library')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/conf.py",
    "content": "import os\nimport sys\nimport numbers\nfrom operator import itemgetter\n\nimport six\nif six.PY2:\n    from ConfigParser import SafeConfigParser as ConfigParser\nelse:\n    from configparser import ConfigParser\n\nfrom scrapy.settings import BaseSettings\nfrom scrapy.utils.deprecate import update_classpath\nfrom scrapy.utils.python import without_none_values\n\n\ndef build_component_list(compdict, custom=None, convert=update_classpath):\n    \"\"\"Compose a component list from a { class: order } dictionary.\"\"\"\n\n    def _check_components(complist):\n        if len({convert(c) for c in complist}) != len(complist):\n            raise ValueError('Some paths in {!r} convert to the same object, '\n                             'please update your settings'.format(complist))\n\n    def _map_keys(compdict):\n        if isinstance(compdict, BaseSettings):\n            compbs = BaseSettings()\n            for k, v in six.iteritems(compdict):\n                prio = compdict.getpriority(k)\n                if compbs.getpriority(convert(k)) == prio:\n                    raise ValueError('Some paths in {!r} convert to the same '\n                                     'object, please update your settings'\n                                     ''.format(list(compdict.keys())))\n                else:\n                    compbs.set(convert(k), v, priority=prio)\n            return compbs\n        else:\n            _check_components(compdict)\n            return {convert(k): v for k, v in six.iteritems(compdict)}\n\n    def _validate_values(compdict):\n        \"\"\"Fail if a value in the components dict is not a real number or None.\"\"\"\n        for name, value in six.iteritems(compdict):\n            if value is not None and not isinstance(value, numbers.Real):\n                raise ValueError('Invalid value {} for component {}, please provide ' \\\n                                 'a real number or None instead'.format(value, name))\n\n    # BEGIN Backward compatibility for old (base, custom) call signature\n    if isinstance(custom, (list, tuple)):\n        _check_components(custom)\n        return type(custom)(convert(c) for c in custom)\n\n    if custom is not None:\n        compdict.update(custom)\n    # END Backward compatibility\n\n    _validate_values(compdict)\n    compdict = without_none_values(_map_keys(compdict))\n    return [k for k, v in sorted(six.iteritems(compdict), key=itemgetter(1))]\n\n\ndef arglist_to_dict(arglist):\n    \"\"\"Convert a list of arguments like ['arg1=val1', 'arg2=val2', ...] to a\n    dict\n    \"\"\"\n    return dict(x.split('=', 1) for x in arglist)\n\n\ndef closest_scrapy_cfg(path='.', prevpath=None):\n    \"\"\"Return the path to the closest scrapy.cfg file by traversing the current\n    directory and its parents\n    \"\"\"\n    if path == prevpath:\n        return ''\n    path = os.path.abspath(path)\n    cfgfile = os.path.join(path, 'scrapy.cfg')\n    if os.path.exists(cfgfile):\n        return cfgfile\n    return closest_scrapy_cfg(os.path.dirname(path), path)\n\n\ndef init_env(project='default', set_syspath=True):\n    \"\"\"Initialize environment to use command-line tool from inside a project\n    dir. This sets the Scrapy settings module and modifies the Python path to\n    be able to locate the project module.\n    \"\"\"\n    cfg = get_config()\n    if cfg.has_option('settings', project):\n        os.environ['SCRAPY_SETTINGS_MODULE'] = cfg.get('settings', project)\n    closest = closest_scrapy_cfg()\n    if closest:\n        projdir = os.path.dirname(closest)\n        if set_syspath and projdir not in sys.path:\n            sys.path.append(projdir)\n\n\ndef get_config(use_closest=True):\n    \"\"\"Get Scrapy config file as a ConfigParser\"\"\"\n    sources = get_sources(use_closest)\n    cfg = ConfigParser()\n    cfg.read(sources)\n    return cfg\n\n\ndef get_sources(use_closest=True):\n    xdg_config_home = os.environ.get('XDG_CONFIG_HOME') or \\\n        os.path.expanduser('~/.config')\n    sources = ['/etc/scrapy.cfg', r'c:\\scrapy\\scrapy.cfg',\n               xdg_config_home + '/scrapy.cfg',\n               os.path.expanduser('~/.scrapy.cfg')]\n    if use_closest:\n        sources.append(closest_scrapy_cfg())\n    return sources\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/console.py",
    "content": "from functools import wraps\nfrom collections import OrderedDict\n\ndef _embed_ipython_shell(namespace={}, banner=''):\n    \"\"\"Start an IPython Shell\"\"\"\n    try:\n        from IPython.terminal.embed import InteractiveShellEmbed\n        from IPython.terminal.ipapp import load_default_config\n    except ImportError:\n        from IPython.frontend.terminal.embed import InteractiveShellEmbed\n        from IPython.frontend.terminal.ipapp import load_default_config\n\n    @wraps(_embed_ipython_shell)\n    def wrapper(namespace=namespace, banner=''):\n        config = load_default_config()\n        # Always use .instace() to ensure _instance propagation to all parents\n        # this is needed for <TAB> completion works well for new imports\n        # and clear the instance to always have the fresh env\n        # on repeated breaks like with inspect_response()\n        InteractiveShellEmbed.clear_instance()\n        shell = InteractiveShellEmbed.instance(\n            banner1=banner, user_ns=namespace, config=config)\n        shell()\n    return wrapper\n\ndef _embed_bpython_shell(namespace={}, banner=''):\n    \"\"\"Start a bpython shell\"\"\"\n    import bpython\n    @wraps(_embed_bpython_shell)\n    def wrapper(namespace=namespace, banner=''):\n        bpython.embed(locals_=namespace, banner=banner)\n    return wrapper\n\ndef _embed_ptpython_shell(namespace={}, banner=''):\n    \"\"\"Start a ptpython shell\"\"\"\n    import ptpython.repl\n    @wraps(_embed_ptpython_shell)\n    def wrapper(namespace=namespace, banner=''):\n        print(banner)\n        ptpython.repl.embed(locals=namespace)\n    return wrapper\n\ndef _embed_standard_shell(namespace={}, banner=''):\n    \"\"\"Start a standard python shell\"\"\"\n    import code\n    try: # readline module is only available on unix systems\n        import readline\n    except ImportError:\n        pass\n    else:\n        import rlcompleter\n        readline.parse_and_bind(\"tab:complete\")\n    @wraps(_embed_standard_shell)\n    def wrapper(namespace=namespace, banner=''):\n        code.interact(banner=banner, local=namespace)\n    return wrapper\n\nDEFAULT_PYTHON_SHELLS = OrderedDict([\n    ('ptpython', _embed_ptpython_shell),\n    ('ipython', _embed_ipython_shell),\n    ('bpython', _embed_bpython_shell),\n    ('python', _embed_standard_shell),\n])\n\ndef get_shell_embed_func(shells=None, known_shells=None):\n    \"\"\"Return the first acceptable shell-embed function\n    from a given list of shell names.\n    \"\"\"\n    if shells is None: # list, preference order of shells\n        shells = DEFAULT_PYTHON_SHELLS.keys()\n    if known_shells is None: # available embeddable shells\n        known_shells = DEFAULT_PYTHON_SHELLS.copy()\n    for shell in shells:\n        if shell in known_shells:\n            try:\n                # function test: run all setup code (imports),\n                # but dont fall into the shell\n                return known_shells[shell]()\n            except ImportError:\n                continue\n\ndef start_python_console(namespace=None, banner='', shells=None):\n    \"\"\"Start Python console bound to the given namespace.\n    Readline support and tab completion will be used on Unix, if available.\n    \"\"\"\n    if namespace is None:\n        namespace = {}\n\n    try:\n        shell = get_shell_embed_func(shells)\n        if shell is not None:\n            shell(namespace=namespace, banner=banner)\n    except SystemExit: # raised when using exit() in python code.interact\n        pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/datatypes.py",
    "content": "\"\"\"\nThis module contains data types used by Scrapy which are not included in the\nPython Standard Library.\n\nThis module must not depend on any module outside the Standard Library.\n\"\"\"\n\nimport copy\nimport collections\nimport warnings\n\nimport six\n\nfrom scrapy.exceptions import ScrapyDeprecationWarning\n\n\nif six.PY2:\n    Mapping = collections.Mapping\nelse:\n    Mapping = collections.abc.Mapping\n\n\nclass MultiValueDictKeyError(KeyError):\n    def __init__(self, *args, **kwargs):\n        warnings.warn(\n            \"scrapy.utils.datatypes.MultiValueDictKeyError is deprecated \"\n            \"and will be removed in future releases.\",\n            category=ScrapyDeprecationWarning,\n            stacklevel=2\n        )\n        super(MultiValueDictKeyError, self).__init__(*args, **kwargs)\n\n\nclass MultiValueDict(dict):\n    \"\"\"\n    A subclass of dictionary customized to handle multiple values for the same key.\n\n    >>> d = MultiValueDict({'name': ['Adrian', 'Simon'], 'position': ['Developer']})\n    >>> d['name']\n    'Simon'\n    >>> d.getlist('name')\n    ['Adrian', 'Simon']\n    >>> d.get('lastname', 'nonexistent')\n    'nonexistent'\n    >>> d.setlist('lastname', ['Holovaty', 'Willison'])\n\n    This class exists to solve the irritating problem raised by cgi.parse_qs,\n    which returns a list for every key, even though most Web forms submit\n    single name-value pairs.\n    \"\"\"\n    def __init__(self, key_to_list_mapping=()):\n        warnings.warn(\"scrapy.utils.datatypes.MultiValueDict is deprecated \"\n                      \"and will be removed in future releases.\",\n                      category=ScrapyDeprecationWarning,\n                      stacklevel=2)\n        dict.__init__(self, key_to_list_mapping)\n\n    def __repr__(self):\n        return \"<%s: %s>\" % (self.__class__.__name__, dict.__repr__(self))\n\n    def __getitem__(self, key):\n        \"\"\"\n        Returns the last data value for this key, or [] if it's an empty list;\n        raises KeyError if not found.\n        \"\"\"\n        try:\n            list_ = dict.__getitem__(self, key)\n        except KeyError:\n            raise MultiValueDictKeyError(\"Key %r not found in %r\" % (key, self))\n        try:\n            return list_[-1]\n        except IndexError:\n            return []\n\n    def __setitem__(self, key, value):\n        dict.__setitem__(self, key, [value])\n\n    def __copy__(self):\n        return self.__class__(dict.items(self))\n\n    def __deepcopy__(self, memo=None):\n        if memo is None:\n            memo = {}\n        result = self.__class__()\n        memo[id(self)] = result\n        for key, value in dict.items(self):\n            dict.__setitem__(result, copy.deepcopy(key, memo), copy.deepcopy(value, memo))\n        return result\n\n    def get(self, key, default=None):\n        \"Returns the default value if the requested data doesn't exist\"\n        try:\n            val = self[key]\n        except KeyError:\n            return default\n        if val == []:\n            return default\n        return val\n\n    def getlist(self, key):\n        \"Returns an empty list if the requested data doesn't exist\"\n        try:\n            return dict.__getitem__(self, key)\n        except KeyError:\n            return []\n\n    def setlist(self, key, list_):\n        dict.__setitem__(self, key, list_)\n\n    def setdefault(self, key, default=None):\n        if key not in self:\n            self[key] = default\n        return self[key]\n\n    def setlistdefault(self, key, default_list=()):\n        if key not in self:\n            self.setlist(key, default_list)\n        return self.getlist(key)\n\n    def appendlist(self, key, value):\n        \"Appends an item to the internal list associated with key\"\n        self.setlistdefault(key, [])\n        dict.__setitem__(self, key, self.getlist(key) + [value])\n\n    def items(self):\n        \"\"\"\n        Returns a list of (key, value) pairs, where value is the last item in\n        the list associated with the key.\n        \"\"\"\n        return [(key, self[key]) for key in self.keys()]\n\n    def lists(self):\n        \"Returns a list of (key, list) pairs.\"\n        return dict.items(self)\n\n    def values(self):\n        \"Returns a list of the last value on every key list.\"\n        return [self[key] for key in self.keys()]\n\n    def copy(self):\n        \"Returns a copy of this object.\"\n        return self.__deepcopy__()\n\n    def update(self, *args, **kwargs):\n        \"update() extends rather than replaces existing key lists. Also accepts keyword args.\"\n        if len(args) > 1:\n            raise TypeError(\"update expected at most 1 arguments, got %d\" % len(args))\n        if args:\n            other_dict = args[0]\n            if isinstance(other_dict, MultiValueDict):\n                for key, value_list in other_dict.lists():\n                    self.setlistdefault(key, []).extend(value_list)\n            else:\n                try:\n                    for key, value in other_dict.items():\n                        self.setlistdefault(key, []).append(value)\n                except TypeError:\n                    raise ValueError(\"MultiValueDict.update() takes either a MultiValueDict or dictionary\")\n        for key, value in six.iteritems(kwargs):\n            self.setlistdefault(key, []).append(value)\n\n\nclass SiteNode(object):\n    \"\"\"Class to represent a site node (page, image or any other file)\"\"\"\n\n    def __init__(self, url):\n        warnings.warn(\n            \"scrapy.utils.datatypes.SiteNode is deprecated \"\n            \"and will be removed in future releases.\",\n            category=ScrapyDeprecationWarning,\n            stacklevel=2\n        )\n\n        self.url = url\n        self.itemnames = []\n        self.children = []\n        self.parent = None\n\n    def add_child(self, node):\n        self.children.append(node)\n        node.parent = self\n\n    def to_string(self, level=0):\n        s = \"%s%s\\n\" % ('  '*level, self.url)\n        if self.itemnames:\n            for n in self.itemnames:\n                s += \"%sScraped: %s\\n\" % ('  '*(level+1), n)\n        for node in self.children:\n            s += node.to_string(level+1)\n        return s\n\n\nclass CaselessDict(dict):\n\n    __slots__ = ()\n\n    def __init__(self, seq=None):\n        super(CaselessDict, self).__init__()\n        if seq:\n            self.update(seq)\n\n    def __getitem__(self, key):\n        return dict.__getitem__(self, self.normkey(key))\n\n    def __setitem__(self, key, value):\n        dict.__setitem__(self, self.normkey(key), self.normvalue(value))\n\n    def __delitem__(self, key):\n        dict.__delitem__(self, self.normkey(key))\n\n    def __contains__(self, key):\n        return dict.__contains__(self, self.normkey(key))\n    has_key = __contains__\n\n    def __copy__(self):\n        return self.__class__(self)\n    copy = __copy__\n\n    def normkey(self, key):\n        \"\"\"Method to normalize dictionary key access\"\"\"\n        return key.lower()\n\n    def normvalue(self, value):\n        \"\"\"Method to normalize values prior to be setted\"\"\"\n        return value\n\n    def get(self, key, def_val=None):\n        return dict.get(self, self.normkey(key), self.normvalue(def_val))\n\n    def setdefault(self, key, def_val=None):\n        return dict.setdefault(self, self.normkey(key), self.normvalue(def_val))\n\n    def update(self, seq):\n        seq = seq.items() if isinstance(seq, Mapping) else seq\n        iseq = ((self.normkey(k), self.normvalue(v)) for k, v in seq)\n        super(CaselessDict, self).update(iseq)\n\n    @classmethod\n    def fromkeys(cls, keys, value=None):\n        return cls((k, value) for k in keys)\n\n    def pop(self, key, *args):\n        return dict.pop(self, self.normkey(key), *args)\n\n\nclass MergeDict(object):\n    \"\"\"\n    A simple class for creating new \"virtual\" dictionaries that actually look\n    up values in more than one dictionary, passed in the constructor.\n\n    If a key appears in more than one of the given dictionaries, only the\n    first occurrence will be used.\n    \"\"\"\n    def __init__(self, *dicts):\n        if not six.PY2:\n            warnings.warn(\n                \"scrapy.utils.datatypes.MergeDict is deprecated in favor \"\n                \"of collections.ChainMap (introduced in Python 3.3)\",\n                category=ScrapyDeprecationWarning,\n                stacklevel=2,\n            )\n        self.dicts = dicts\n\n    def __getitem__(self, key):\n        for dict_ in self.dicts:\n            try:\n                return dict_[key]\n            except KeyError:\n                pass\n        raise KeyError\n\n    def __copy__(self):\n        return self.__class__(*self.dicts)\n\n    def get(self, key, default=None):\n        try:\n            return self[key]\n        except KeyError:\n            return default\n\n    def getlist(self, key):\n        for dict_ in self.dicts:\n            if key in dict_.keys():\n                return dict_.getlist(key)\n        return []\n\n    def items(self):\n        item_list = []\n        for dict_ in self.dicts:\n            item_list.extend(dict_.items())\n        return item_list\n\n    def has_key(self, key):\n        for dict_ in self.dicts:\n            if key in dict_:\n                return True\n        return False\n\n    __contains__ = has_key\n\n    def copy(self):\n        \"\"\"Returns a copy of this object.\"\"\"\n        return self.__copy__()\n\n\nclass LocalCache(collections.OrderedDict):\n    \"\"\"Dictionary with a finite number of keys.\n\n    Older items expires first.\n\n    \"\"\"\n\n    def __init__(self, limit=None):\n        super(LocalCache, self).__init__()\n        self.limit = limit\n\n    def __setitem__(self, key, value):\n        while len(self) >= self.limit:\n            self.popitem(last=False)\n        super(LocalCache, self).__setitem__(key, value)\n\n\nclass SequenceExclude(object):\n    \"\"\"Object to test if an item is NOT within some sequence.\"\"\"\n\n    def __init__(self, seq):\n        self.seq = seq\n\n    def __contains__(self, item):\n        return item not in self.seq\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/decorators.py",
    "content": "import warnings\nfrom functools import wraps\n\nfrom twisted.internet import defer, threads\n\nfrom scrapy.exceptions import ScrapyDeprecationWarning\n\n\ndef deprecated(use_instead=None):\n    \"\"\"This is a decorator which can be used to mark functions\n    as deprecated. It will result in a warning being emitted\n    when the function is used.\"\"\"\n\n    def deco(func):\n        @wraps(func)\n        def wrapped(*args, **kwargs):\n            message = \"Call to deprecated function %s.\" % func.__name__\n            if use_instead:\n                message += \" Use %s instead.\" % use_instead\n            warnings.warn(message, category=ScrapyDeprecationWarning, stacklevel=2)\n            return func(*args, **kwargs)\n        return wrapped\n\n    if callable(use_instead):\n        deco = deco(use_instead)\n        use_instead = None\n    return deco\n\n\ndef defers(func):\n    \"\"\"Decorator to make sure a function always returns a deferred\"\"\"\n    @wraps(func)\n    def wrapped(*a, **kw):\n        return defer.maybeDeferred(func, *a, **kw)\n    return wrapped\n\ndef inthread(func):\n    \"\"\"Decorator to call a function in a thread and return a deferred with the\n    result\n    \"\"\"\n    @wraps(func)\n    def wrapped(*a, **kw):\n        return threads.deferToThread(func, *a, **kw)\n    return wrapped\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/defer.py",
    "content": "\"\"\"\nHelper functions for dealing with Twisted deferreds\n\"\"\"\n\nfrom twisted.internet import defer, reactor, task\nfrom twisted.python import failure\n\nfrom scrapy.exceptions import IgnoreRequest\n\ndef defer_fail(_failure):\n    \"\"\"Same as twisted.internet.defer.fail but delay calling errback until\n    next reactor loop\n\n    It delays by 100ms so reactor has a chance to go through readers and writers\n    before attending pending delayed calls, so do not set delay to zero.\n    \"\"\"\n    d = defer.Deferred()\n    reactor.callLater(0.1, d.errback, _failure)\n    return d\n\ndef defer_succeed(result):\n    \"\"\"Same as twisted.internet.defer.succeed but delay calling callback until\n    next reactor loop\n\n    It delays by 100ms so reactor has a chance to go trough readers and writers\n    before attending pending delayed calls, so do not set delay to zero.\n    \"\"\"\n    d = defer.Deferred()\n    reactor.callLater(0.1, d.callback, result)\n    return d\n\ndef defer_result(result):\n    if isinstance(result, defer.Deferred):\n        return result\n    elif isinstance(result, failure.Failure):\n        return defer_fail(result)\n    else:\n        return defer_succeed(result)\n\ndef mustbe_deferred(f, *args, **kw):\n    \"\"\"Same as twisted.internet.defer.maybeDeferred, but delay calling\n    callback/errback to next reactor loop\n    \"\"\"\n    try:\n        result = f(*args, **kw)\n    # FIXME: Hack to avoid introspecting tracebacks. This to speed up\n    # processing of IgnoreRequest errors which are, by far, the most common\n    # exception in Scrapy - see #125\n    except IgnoreRequest as e:\n        return defer_fail(failure.Failure(e))\n    except Exception:\n        return defer_fail(failure.Failure())\n    else:\n        return defer_result(result)\n\ndef parallel(iterable, count, callable, *args, **named):\n    \"\"\"Execute a callable over the objects in the given iterable, in parallel,\n    using no more than ``count`` concurrent calls.\n\n    Taken from: https://jcalderone.livejournal.com/24285.html\n    \"\"\"\n    coop = task.Cooperator()\n    work = (callable(elem, *args, **named) for elem in iterable)\n    return defer.DeferredList([coop.coiterate(work) for _ in range(count)])\n\ndef process_chain(callbacks, input, *a, **kw):\n    \"\"\"Return a Deferred built by chaining the given callbacks\"\"\"\n    d = defer.Deferred()\n    for x in callbacks:\n        d.addCallback(x, *a, **kw)\n    d.callback(input)\n    return d\n\ndef process_chain_both(callbacks, errbacks, input, *a, **kw):\n    \"\"\"Return a Deferred built by chaining the given callbacks and errbacks\"\"\"\n    d = defer.Deferred()\n    for cb, eb in zip(callbacks, errbacks):\n        d.addCallbacks(cb, eb, callbackArgs=a, callbackKeywords=kw,\n            errbackArgs=a, errbackKeywords=kw)\n    if isinstance(input, failure.Failure):\n        d.errback(input)\n    else:\n        d.callback(input)\n    return d\n\ndef process_parallel(callbacks, input, *a, **kw):\n    \"\"\"Return a Deferred with the output of all successful calls to the given\n    callbacks\n    \"\"\"\n    dfds = [defer.succeed(input).addCallback(x, *a, **kw) for x in callbacks]\n    d = defer.DeferredList(dfds, fireOnOneErrback=1, consumeErrors=1)\n    d.addCallbacks(lambda r: [x[1] for x in r], lambda f: f.value.subFailure)\n    return d\n\ndef iter_errback(iterable, errback, *a, **kw):\n    \"\"\"Wraps an iterable calling an errback if an error is caught while\n    iterating it.\n    \"\"\"\n    it = iter(iterable)\n    while True:\n        try:\n            yield next(it)\n        except StopIteration:\n            break\n        except Exception:\n            errback(failure.Failure(), *a, **kw)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/deprecate.py",
    "content": "\"\"\"Some helpers for deprecation messages\"\"\"\n\nimport warnings\nimport inspect\nfrom scrapy.exceptions import ScrapyDeprecationWarning\n\n\ndef attribute(obj, oldattr, newattr, version='0.12'):\n    cname = obj.__class__.__name__\n    warnings.warn(\"%s.%s attribute is deprecated and will be no longer supported \"\n        \"in Scrapy %s, use %s.%s attribute instead\" % \\\n        (cname, oldattr, version, cname, newattr), ScrapyDeprecationWarning, stacklevel=3)\n\n\ndef create_deprecated_class(name, new_class, clsdict=None,\n                            warn_category=ScrapyDeprecationWarning,\n                            warn_once=True,\n                            old_class_path=None,\n                            new_class_path=None,\n                            subclass_warn_message=\"{cls} inherits from \"\\\n                                    \"deprecated class {old}, please inherit \"\\\n                                    \"from {new}.\",\n                            instance_warn_message=\"{cls} is deprecated, \"\\\n                                    \"instantiate {new} instead.\"):\n    \"\"\"\n    Return a \"deprecated\" class that causes its subclasses to issue a warning.\n    Subclasses of ``new_class`` are considered subclasses of this class.\n    It also warns when the deprecated class is instantiated, but do not when\n    its subclasses are instantiated.\n\n    It can be used to rename a base class in a library. For example, if we\n    have\n\n        class OldName(SomeClass):\n            # ...\n\n    and we want to rename it to NewName, we can do the following::\n\n        class NewName(SomeClass):\n            # ...\n\n        OldName = create_deprecated_class('OldName', NewName)\n\n    Then, if user class inherits from OldName, warning is issued. Also, if\n    some code uses ``issubclass(sub, OldName)`` or ``isinstance(sub(), OldName)``\n    checks they'll still return True if sub is a subclass of NewName instead of\n    OldName.\n    \"\"\"\n\n    class DeprecatedClass(new_class.__class__):\n\n        deprecated_class = None\n        warned_on_subclass = False\n\n        def __new__(metacls, name, bases, clsdict_):\n            cls = super(DeprecatedClass, metacls).__new__(metacls, name, bases, clsdict_)\n            if metacls.deprecated_class is None:\n                metacls.deprecated_class = cls\n            return cls\n\n        def __init__(cls, name, bases, clsdict_):\n            meta = cls.__class__\n            old = meta.deprecated_class\n            if old in bases and not (warn_once and meta.warned_on_subclass):\n                meta.warned_on_subclass = True\n                msg = subclass_warn_message.format(cls=_clspath(cls),\n                                                   old=_clspath(old, old_class_path),\n                                                   new=_clspath(new_class, new_class_path))\n                if warn_once:\n                    msg += ' (warning only on first subclass, there may be others)'\n                warnings.warn(msg, warn_category, stacklevel=2)\n            super(DeprecatedClass, cls).__init__(name, bases, clsdict_)\n\n        # see https://www.python.org/dev/peps/pep-3119/#overloading-isinstance-and-issubclass\n        # and https://docs.python.org/reference/datamodel.html#customizing-instance-and-subclass-checks\n        # for implementation details\n        def __instancecheck__(cls, inst):\n            return any(cls.__subclasscheck__(c)\n                       for c in {type(inst), inst.__class__})\n\n        def __subclasscheck__(cls, sub):\n            if cls is not DeprecatedClass.deprecated_class:\n                # we should do the magic only if second `issubclass` argument\n                # is the deprecated class itself - subclasses of the\n                # deprecated class should not use custom `__subclasscheck__`\n                # method.\n                return super(DeprecatedClass, cls).__subclasscheck__(sub)\n\n            if not inspect.isclass(sub):\n                raise TypeError(\"issubclass() arg 1 must be a class\")\n\n            mro = getattr(sub, '__mro__', ())\n            return any(c in {cls, new_class} for c in mro)\n\n        def __call__(cls, *args, **kwargs):\n            old = DeprecatedClass.deprecated_class\n            if cls is old:\n                msg = instance_warn_message.format(cls=_clspath(cls, old_class_path),\n                                                   new=_clspath(new_class, new_class_path))\n                warnings.warn(msg, warn_category, stacklevel=2)\n            return super(DeprecatedClass, cls).__call__(*args, **kwargs)\n\n    deprecated_cls = DeprecatedClass(name, (new_class,), clsdict or {})\n\n    try:\n        frm = inspect.stack()[1]\n        parent_module = inspect.getmodule(frm[0])\n        if parent_module is not None:\n            deprecated_cls.__module__ = parent_module.__name__\n    except Exception as e:\n        # Sometimes inspect.stack() fails (e.g. when the first import of\n        # deprecated class is in jinja2 template). __module__ attribute is not\n        # important enough to raise an exception as users may be unable\n        # to fix inspect.stack() errors.\n        warnings.warn(\"Error detecting parent module: %r\" % e)\n\n    return deprecated_cls\n\n\ndef _clspath(cls, forced=None):\n    if forced is not None:\n        return forced\n    return '{}.{}'.format(cls.__module__, cls.__name__)\n\n\nDEPRECATION_RULES = [\n    ('scrapy.telnet.', 'scrapy.extensions.telnet.'),\n]\n\n\ndef update_classpath(path):\n    \"\"\"Update a deprecated path from an object with its new location\"\"\"\n    for prefix, replacement in DEPRECATION_RULES:\n        if path.startswith(prefix):\n            new_path = path.replace(prefix, replacement, 1)\n            warnings.warn(\"`{}` class is deprecated, use `{}` instead\".format(path, new_path),\n                          ScrapyDeprecationWarning)\n            return new_path\n    return path\n\n\ndef method_is_overridden(subclass, base_class, method_name):\n    \"\"\"\n    Return True if a method named ``method_name`` of a ``base_class``\n    is overridden in a ``subclass``.\n\n    >>> class Base(object):\n    ...     def foo(self):\n    ...         pass\n    >>> class Sub1(Base):\n    ...     pass\n    >>> class Sub2(Base):\n    ...     def foo(self):\n    ...         pass\n    >>> class Sub3(Sub1):\n    ...     def foo(self):\n    ...         pass\n    >>> class Sub4(Sub2):\n    ...     pass\n    >>> method_is_overridden(Sub1, Base, 'foo')\n    False\n    >>> method_is_overridden(Sub2, Base, 'foo')\n    True\n    >>> method_is_overridden(Sub3, Base, 'foo')\n    True\n    >>> method_is_overridden(Sub4, Base, 'foo')\n    True\n    \"\"\"\n    base_method = getattr(base_class, method_name)\n    sub_method = getattr(subclass, method_name)\n    return base_method.__code__ is not sub_method.__code__\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/display.py",
    "content": "\"\"\"\npprint and pformat wrappers with colorization support\n\"\"\"\n\nfrom __future__ import print_function\nimport sys\nfrom pprint import pformat as pformat_\n\ndef _colorize(text, colorize=True):\n    if not colorize or not sys.stdout.isatty():\n        return text\n    try:\n        from pygments import highlight\n        from pygments.formatters import TerminalFormatter\n        from pygments.lexers import PythonLexer\n        return highlight(text, PythonLexer(), TerminalFormatter())\n    except ImportError:\n        return text\n\ndef pformat(obj, *args, **kwargs):\n    return _colorize(pformat_(obj), kwargs.pop('colorize', True))\n\ndef pprint(obj, *args, **kwargs):\n    print(pformat(obj, *args, **kwargs))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/engine.py",
    "content": "\"\"\"Some debugging functions for working with the Scrapy engine\"\"\"\n\nfrom __future__ import print_function\nfrom time import time # used in global tests code\n\ndef get_engine_status(engine):\n    \"\"\"Return a report of the current engine status\"\"\"\n    tests = [\n        \"time()-engine.start_time\",\n        \"engine.has_capacity()\",\n        \"len(engine.downloader.active)\",\n        \"engine.scraper.is_idle()\",\n        \"engine.spider.name\",\n        \"engine.spider_is_idle(engine.spider)\",\n        \"engine.slot.closing\",\n        \"len(engine.slot.inprogress)\",\n        \"len(engine.slot.scheduler.dqs or [])\",\n        \"len(engine.slot.scheduler.mqs)\",\n        \"len(engine.scraper.slot.queue)\",\n        \"len(engine.scraper.slot.active)\",\n        \"engine.scraper.slot.active_size\",\n        \"engine.scraper.slot.itemproc_size\",\n        \"engine.scraper.slot.needs_backout()\",\n    ]\n\n    checks = []\n    for test in tests:\n        try:\n            checks += [(test, eval(test))]\n        except Exception as e:\n            checks += [(test, \"%s (exception)\" % type(e).__name__)]\n\n    return checks\n\ndef format_engine_status(engine=None):\n    checks = get_engine_status(engine)\n    s = \"Execution engine status\\n\\n\"\n    for test, result in checks:\n        s += \"%-47s : %s\\n\" % (test, result)\n    s += \"\\n\"\n\n    return s\n\ndef print_engine_status(engine):\n    print(format_engine_status(engine))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/ftp.py",
    "content": "from ftplib import error_perm\nfrom posixpath import dirname\n\ndef ftp_makedirs_cwd(ftp, path, first_call=True):\n    \"\"\"Set the current directory of the FTP connection given in the ``ftp``\n    argument (as a ftplib.FTP object), creating all parent directories if they\n    don't exist. The ftplib.FTP object must be already connected and logged in.\n    \"\"\"\n    try:\n        ftp.cwd(path)\n    except error_perm:\n        ftp_makedirs_cwd(ftp, dirname(path), False)\n        ftp.mkd(path)\n        if first_call:\n            ftp.cwd(path)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/gz.py",
    "content": "import struct\n\ntry:\n    from cStringIO import StringIO as BytesIO\nexcept ImportError:\n    from io import BytesIO\nfrom gzip import GzipFile\n\nimport six\nimport re\n\nfrom scrapy.utils.decorators import deprecated\n\n\n# - Python>=3.5 GzipFile's read() has issues returning leftover\n#   uncompressed data when input is corrupted\n#   (regression or bug-fix compared to Python 3.4)\n# - read1(), which fetches data before raising EOFError on next call\n#   works here but is only available from Python>=3.3\n# - scrapy does not support Python 3.2\n# - Python 2.7 GzipFile works fine with standard read() + extrabuf\nif six.PY2:\n    def read1(gzf, size=-1):\n        return gzf.read(size)\nelse:\n    def read1(gzf, size=-1):\n        return gzf.read1(size)\n\n\ndef gunzip(data):\n    \"\"\"Gunzip the given data and return as much data as possible.\n\n    This is resilient to CRC checksum errors.\n    \"\"\"\n    f = GzipFile(fileobj=BytesIO(data))\n    output_list = []\n    chunk = b'.'\n    while chunk:\n        try:\n            chunk = read1(f, 8196)\n            output_list.append(chunk)\n        except (IOError, EOFError, struct.error):\n            # complete only if there is some data, otherwise re-raise\n            # see issue 87 about catching struct.error\n            # some pages are quite small so output_list is empty and f.extrabuf\n            # contains the whole page content\n            if output_list or getattr(f, 'extrabuf', None):\n                try:\n                    output_list.append(f.extrabuf[-f.extrasize:])\n                finally:\n                    break\n            else:\n                raise\n    return b''.join(output_list)\n\n_is_gzipped = re.compile(br'^application/(x-)?gzip\\b', re.I).search\n_is_octetstream = re.compile(br'^(application|binary)/octet-stream\\b', re.I).search\n\n@deprecated\ndef is_gzipped(response):\n    \"\"\"Return True if the response is gzipped, or False otherwise\"\"\"\n    ctype = response.headers.get('Content-Type', b'')\n    cenc = response.headers.get('Content-Encoding', b'').lower()\n    return (_is_gzipped(ctype) or\n            (_is_octetstream(ctype) and cenc in (b'gzip', b'x-gzip')))\n\n\ndef gzip_magic_number(response):\n    return response.body[:3] == b'\\x1f\\x8b\\x08'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/http.py",
    "content": "\"\"\"\nTransitional module for moving to the w3lib library.\n\nFor new code, always import from w3lib.http instead of this module\n\"\"\"\n\nimport warnings\n\nfrom scrapy.exceptions import ScrapyDeprecationWarning\nfrom scrapy.utils.decorators import deprecated\nfrom w3lib.http import *\n\n\nwarnings.warn(\"Module `scrapy.utils.http` is deprecated, \"\n              \"Please import from `w3lib.http` instead.\",\n              ScrapyDeprecationWarning, stacklevel=2)\n\n\n@deprecated\ndef decode_chunked_transfer(chunked_body):\n    \"\"\"Parsed body received with chunked transfer encoding, and return the\n    decoded body.\n\n    For more info see:\n    https://en.wikipedia.org/wiki/Chunked_transfer_encoding\n\n    \"\"\"\n    body, h, t = '', '', chunked_body\n    while t:\n        h, t = t.split('\\r\\n', 1)\n        if h == '0':\n            break\n        size = int(h, 16)\n        body += t[:size]\n        t = t[size+2:]\n    return body\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/httpobj.py",
    "content": "\"\"\"Helper functions for scrapy.http objects (Request, Response)\"\"\"\n\nimport weakref\n\nfrom six.moves.urllib.parse import urlparse\n\n_urlparse_cache = weakref.WeakKeyDictionary()\ndef urlparse_cached(request_or_response):\n    \"\"\"Return urlparse.urlparse caching the result, where the argument can be a\n    Request or Response object\n    \"\"\"\n    if request_or_response not in _urlparse_cache:\n        _urlparse_cache[request_or_response] = urlparse(request_or_response.url)\n    return _urlparse_cache[request_or_response]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/iterators.py",
    "content": "import re\nimport csv\nimport logging\ntry:\n    from cStringIO import StringIO as BytesIO\nexcept ImportError:\n    from io import BytesIO\nfrom io import StringIO\nimport six\n\nfrom scrapy.http import TextResponse, Response\nfrom scrapy.selector import Selector\nfrom scrapy.utils.python import re_rsearch, to_unicode\n\nlogger = logging.getLogger(__name__)\n\n\ndef xmliter(obj, nodename):\n    \"\"\"Return a iterator of Selector's over all nodes of a XML document,\n       given the name of the node to iterate. Useful for parsing XML feeds.\n\n    obj can be:\n    - a Response object\n    - a unicode string\n    - a string encoded as utf-8\n    \"\"\"\n    nodename_patt = re.escape(nodename)\n\n    HEADER_START_RE = re.compile(r'^(.*?)<\\s*%s(?:\\s|>)' % nodename_patt, re.S)\n    HEADER_END_RE = re.compile(r'<\\s*/%s\\s*>' % nodename_patt, re.S)\n    text = _body_or_str(obj)\n\n    header_start = re.search(HEADER_START_RE, text)\n    header_start = header_start.group(1).strip() if header_start else ''\n    header_end = re_rsearch(HEADER_END_RE, text)\n    header_end = text[header_end[1]:].strip() if header_end else ''\n\n    r = re.compile(r'<%(np)s[\\s>].*?</%(np)s>' % {'np': nodename_patt}, re.DOTALL)\n    for match in r.finditer(text):\n        nodetext = header_start + match.group() + header_end\n        yield Selector(text=nodetext, type='xml').xpath('//' + nodename)[0]\n\n\ndef xmliter_lxml(obj, nodename, namespace=None, prefix='x'):\n    from lxml import etree\n    reader = _StreamReader(obj)\n    tag = '{%s}%s' % (namespace, nodename) if namespace else nodename\n    iterable = etree.iterparse(reader, tag=tag, encoding=reader.encoding)\n    selxpath = '//' + ('%s:%s' % (prefix, nodename) if namespace else nodename)\n    for _, node in iterable:\n        nodetext = etree.tostring(node, encoding='unicode')\n        node.clear()\n        xs = Selector(text=nodetext, type='xml')\n        if namespace:\n            xs.register_namespace(prefix, namespace)\n        yield xs.xpath(selxpath)[0]\n\n\nclass _StreamReader(object):\n\n    def __init__(self, obj):\n        self._ptr = 0\n        if isinstance(obj, Response):\n            self._text, self.encoding = obj.body, obj.encoding\n        else:\n            self._text, self.encoding = obj, 'utf-8'\n        self._is_unicode = isinstance(self._text, six.text_type)\n\n    def read(self, n=65535):\n        self.read = self._read_unicode if self._is_unicode else self._read_string\n        return self.read(n).lstrip()\n\n    def _read_string(self, n=65535):\n        s, e = self._ptr, self._ptr + n\n        self._ptr = e\n        return self._text[s:e]\n\n    def _read_unicode(self, n=65535):\n        s, e = self._ptr, self._ptr + n\n        self._ptr = e\n        return self._text[s:e].encode('utf-8')\n\n\ndef csviter(obj, delimiter=None, headers=None, encoding=None, quotechar=None):\n    \"\"\" Returns an iterator of dictionaries from the given csv object\n\n    obj can be:\n    - a Response object\n    - a unicode string\n    - a string encoded as utf-8\n\n    delimiter is the character used to separate fields on the given obj.\n\n    headers is an iterable that when provided offers the keys\n    for the returned dictionaries, if not the first row is used.\n\n    quotechar is the character used to enclosure fields on the given obj.\n    \"\"\"\n\n    encoding = obj.encoding if isinstance(obj, TextResponse) else encoding or 'utf-8'\n\n    def row_to_unicode(row_):\n        return [to_unicode(field, encoding) for field in row_]\n\n    # Python 3 csv reader input object needs to return strings\n    if six.PY3:\n        lines = StringIO(_body_or_str(obj, unicode=True))\n    else:\n        lines = BytesIO(_body_or_str(obj, unicode=False))\n\n    kwargs = {}\n    if delimiter: kwargs[\"delimiter\"] = delimiter\n    if quotechar: kwargs[\"quotechar\"] = quotechar\n    csv_r = csv.reader(lines, **kwargs)\n\n    if not headers:\n        try:\n            row = next(csv_r)\n        except StopIteration:\n            return\n        headers = row_to_unicode(row)\n\n    for row in csv_r:\n        row = row_to_unicode(row)\n        if len(row) != len(headers):\n            logger.warning(\"ignoring row %(csvlnum)d (length: %(csvrow)d, \"\n                           \"should be: %(csvheader)d)\",\n                           {'csvlnum': csv_r.line_num, 'csvrow': len(row),\n                            'csvheader': len(headers)})\n            continue\n        else:\n            yield dict(zip(headers, row))\n\n\ndef _body_or_str(obj, unicode=True):\n    expected_types = (Response, six.text_type, six.binary_type)\n    assert isinstance(obj, expected_types), \\\n        \"obj must be %s, not %s\" % (\n            \" or \".join(t.__name__ for t in expected_types),\n            type(obj).__name__)\n    if isinstance(obj, Response):\n        if not unicode:\n            return obj.body\n        elif isinstance(obj, TextResponse):\n            return obj.text\n        else:\n            return obj.body.decode('utf-8')\n    elif isinstance(obj, six.text_type):\n        return obj if unicode else obj.encode('utf-8')\n    else:\n        return obj.decode('utf-8') if unicode else obj\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/job.py",
    "content": "import os\n\ndef job_dir(settings):\n    path = settings['JOBDIR']\n    if path and not os.path.exists(path):\n        os.makedirs(path)\n    return path\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/log.py",
    "content": "# -*- coding: utf-8 -*-\n\nimport sys\nimport logging\nimport warnings\nfrom logging.config import dictConfig\n\nfrom twisted.python.failure import Failure\nfrom twisted.python import log as twisted_log\n\nimport scrapy\nfrom scrapy.settings import Settings\nfrom scrapy.exceptions import ScrapyDeprecationWarning\nfrom scrapy.utils.versions import scrapy_components_versions\n\n\nlogger = logging.getLogger(__name__)\n\n\ndef failure_to_exc_info(failure):\n    \"\"\"Extract exc_info from Failure instances\"\"\"\n    if isinstance(failure, Failure):\n        return (failure.type, failure.value, failure.getTracebackObject())\n\n\nclass TopLevelFormatter(logging.Filter):\n    \"\"\"Keep only top level loggers's name (direct children from root) from\n    records.\n\n    This filter will replace Scrapy loggers' names with 'scrapy'. This mimics\n    the old Scrapy log behaviour and helps shortening long names.\n\n    Since it can't be set for just one logger (it won't propagate for its\n    children), it's going to be set in the root handler, with a parametrized\n    ``loggers`` list where it should act.\n    \"\"\"\n\n    def __init__(self, loggers=None):\n        self.loggers = loggers or []\n\n    def filter(self, record):\n        if any(record.name.startswith(l + '.') for l in self.loggers):\n            record.name = record.name.split('.', 1)[0]\n        return True\n\n\nDEFAULT_LOGGING = {\n    'version': 1,\n    'disable_existing_loggers': False,\n    'loggers': {\n        'scrapy': {\n            'level': 'DEBUG',\n        },\n        'twisted': {\n            'level': 'ERROR',\n        },\n    }\n}\n\n\ndef configure_logging(settings=None, install_root_handler=True):\n    \"\"\"\n    Initialize logging defaults for Scrapy.\n\n    :param settings: settings used to create and configure a handler for the\n        root logger (default: None).\n    :type settings: dict, :class:`~scrapy.settings.Settings` object or ``None``\n\n    :param install_root_handler: whether to install root logging handler\n        (default: True)\n    :type install_root_handler: bool\n\n    This function does:\n\n    - Route warnings and twisted logging through Python standard logging\n    - Assign DEBUG and ERROR level to Scrapy and Twisted loggers respectively\n    - Route stdout to log if LOG_STDOUT setting is True\n\n    When ``install_root_handler`` is True (default), this function also\n    creates a handler for the root logger according to given settings\n    (see :ref:`topics-logging-settings`). You can override default options\n    using ``settings`` argument. When ``settings`` is empty or None, defaults\n    are used.\n    \"\"\"\n    if not sys.warnoptions:\n        # Route warnings through python logging\n        logging.captureWarnings(True)\n\n    observer = twisted_log.PythonLoggingObserver('twisted')\n    observer.start()\n\n    dictConfig(DEFAULT_LOGGING)\n\n    if isinstance(settings, dict) or settings is None:\n        settings = Settings(settings)\n\n    if settings.getbool('LOG_STDOUT'):\n        sys.stdout = StreamLogger(logging.getLogger('stdout'))\n\n    if install_root_handler:\n        install_scrapy_root_handler(settings)\n\n\ndef install_scrapy_root_handler(settings):\n    global _scrapy_root_handler\n\n    if (_scrapy_root_handler is not None\n            and _scrapy_root_handler in logging.root.handlers):\n        logging.root.removeHandler(_scrapy_root_handler)\n    logging.root.setLevel(logging.NOTSET)\n    _scrapy_root_handler = _get_handler(settings)\n    logging.root.addHandler(_scrapy_root_handler)\n\n\ndef get_scrapy_root_handler():\n    return _scrapy_root_handler\n\n\n_scrapy_root_handler = None\n\n\ndef _get_handler(settings):\n    \"\"\" Return a log handler object according to settings \"\"\"\n    filename = settings.get('LOG_FILE')\n    if filename:\n        encoding = settings.get('LOG_ENCODING')\n        handler = logging.FileHandler(filename, encoding=encoding)\n    elif settings.getbool('LOG_ENABLED'):\n        handler = logging.StreamHandler()\n    else:\n        handler = logging.NullHandler()\n\n    formatter = logging.Formatter(\n        fmt=settings.get('LOG_FORMAT'),\n        datefmt=settings.get('LOG_DATEFORMAT')\n    )\n    handler.setFormatter(formatter)\n    handler.setLevel(settings.get('LOG_LEVEL'))\n    if settings.getbool('LOG_SHORT_NAMES'):\n        handler.addFilter(TopLevelFormatter(['scrapy']))\n    return handler\n\n\ndef log_scrapy_info(settings):\n    logger.info(\"Scrapy %(version)s started (bot: %(bot)s)\",\n                {'version': scrapy.__version__, 'bot': settings['BOT_NAME']})\n    logger.info(\"Versions: %(versions)s\",\n                {'versions': \", \".join(\"%s %s\" % (name, version)\n                    for name, version in scrapy_components_versions()\n                    if name != \"Scrapy\")})\n\n\nclass StreamLogger(object):\n    \"\"\"Fake file-like stream object that redirects writes to a logger instance\n\n    Taken from:\n        https://www.electricmonk.nl/log/2011/08/14/redirect-stdout-and-stderr-to-a-logger-in-python/\n    \"\"\"\n    def __init__(self, logger, log_level=logging.INFO):\n        self.logger = logger\n        self.log_level = log_level\n        self.linebuf = ''\n\n    def write(self, buf):\n        for line in buf.rstrip().splitlines():\n            self.logger.log(self.log_level, line.rstrip())\n\n    def flush(self):\n        for h in self.logger.handlers:\n            h.flush()\n\n\nclass LogCounterHandler(logging.Handler):\n    \"\"\"Record log levels count into a crawler stats\"\"\"\n\n    def __init__(self, crawler, *args, **kwargs):\n        super(LogCounterHandler, self).__init__(*args, **kwargs)\n        self.crawler = crawler\n\n    def emit(self, record):\n        sname = 'log_count/{}'.format(record.levelname)\n        self.crawler.stats.inc_value(sname)\n\n\ndef logformatter_adapter(logkws):\n    \"\"\"\n    Helper that takes the dictionary output from the methods in LogFormatter\n    and adapts it into a tuple of positional arguments for logger.log calls,\n    handling backward compatibility as well.\n    \"\"\"\n    if not {'level', 'msg', 'args'} <= set(logkws):\n        warnings.warn('Missing keys in LogFormatter method',\n                      ScrapyDeprecationWarning)\n\n    if 'format' in logkws:\n        warnings.warn('`format` key in LogFormatter methods has been '\n                      'deprecated, use `msg` instead',\n                      ScrapyDeprecationWarning)\n\n    level = logkws.get('level', logging.INFO)\n    message = logkws.get('format', logkws.get('msg'))\n    # NOTE: This also handles 'args' being an empty dict, that case doesn't\n    # play well in logger.log calls\n    args = logkws if not logkws.get('args') else logkws['args']\n\n    return (level, message, args)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/markup.py",
    "content": "\"\"\"\nTransitional module for moving to the w3lib library.\n\nFor new code, always import from w3lib.html instead of this module\n\"\"\"\nimport warnings\n\nfrom scrapy.exceptions import ScrapyDeprecationWarning\nfrom w3lib.html import *\n\n\nwarnings.warn(\"Module `scrapy.utils.markup` is deprecated. \"\n              \"Please import from `w3lib.html` instead.\",\n              ScrapyDeprecationWarning, stacklevel=2)"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/misc.py",
    "content": "\"\"\"Helper functions which don't fit anywhere else\"\"\"\nimport os\nimport re\nimport hashlib\nfrom contextlib import contextmanager\nfrom importlib import import_module\nfrom pkgutil import iter_modules\n\nimport six\nfrom w3lib.html import replace_entities\n\nfrom scrapy.utils.python import flatten, to_unicode\nfrom scrapy.item import BaseItem\n\n\n_ITERABLE_SINGLE_VALUES = dict, BaseItem, six.text_type, bytes\n\n\ndef arg_to_iter(arg):\n    \"\"\"Convert an argument to an iterable. The argument can be a None, single\n    value, or an iterable.\n\n    Exception: if arg is a dict, [arg] will be returned\n    \"\"\"\n    if arg is None:\n        return []\n    elif not isinstance(arg, _ITERABLE_SINGLE_VALUES) and hasattr(arg, '__iter__'):\n        return arg\n    else:\n        return [arg]\n\n\ndef load_object(path):\n    \"\"\"Load an object given its absolute object path, and return it.\n\n    object can be a class, function, variable or an instance.\n    path ie: 'scrapy.downloadermiddlewares.redirect.RedirectMiddleware'\n    \"\"\"\n\n    try:\n        dot = path.rindex('.')\n    except ValueError:\n        raise ValueError(\"Error loading object '%s': not a full path\" % path)\n\n    module, name = path[:dot], path[dot+1:]\n    mod = import_module(module)\n\n    try:\n        obj = getattr(mod, name)\n    except AttributeError:\n        raise NameError(\"Module '%s' doesn't define any object named '%s'\" % (module, name))\n\n    return obj\n\n\ndef walk_modules(path):\n    \"\"\"Loads a module and all its submodules from the given module path and\n    returns them. If *any* module throws an exception while importing, that\n    exception is thrown back.\n\n    For example: walk_modules('scrapy.utils')\n    \"\"\"\n\n    mods = []\n    mod = import_module(path)\n    mods.append(mod)\n    if hasattr(mod, '__path__'):\n        for _, subpath, ispkg in iter_modules(mod.__path__):\n            fullpath = path + '.' + subpath\n            if ispkg:\n                mods += walk_modules(fullpath)\n            else:\n                submod = import_module(fullpath)\n                mods.append(submod)\n    return mods\n\n\ndef extract_regex(regex, text, encoding='utf-8'):\n    \"\"\"Extract a list of unicode strings from the given text/encoding using the following policies:\n\n    * if the regex contains a named group called \"extract\" that will be returned\n    * if the regex contains multiple numbered groups, all those will be returned (flattened)\n    * if the regex doesn't contain any group the entire regex matching is returned\n    \"\"\"\n\n    if isinstance(regex, six.string_types):\n        regex = re.compile(regex, re.UNICODE)\n\n    try:\n        strings = [regex.search(text).group('extract')]   # named group\n    except Exception:\n        strings = regex.findall(text)    # full regex or numbered groups\n    strings = flatten(strings)\n\n    if isinstance(text, six.text_type):\n        return [replace_entities(s, keep=['lt', 'amp']) for s in strings]\n    else:\n        return [replace_entities(to_unicode(s, encoding), keep=['lt', 'amp'])\n                for s in strings]\n\n\ndef md5sum(file):\n    \"\"\"Calculate the md5 checksum of a file-like object without reading its\n    whole content in memory.\n\n    >>> from io import BytesIO\n    >>> md5sum(BytesIO(b'file content to hash'))\n    '784406af91dd5a54fbb9c84c2236595a'\n    \"\"\"\n    m = hashlib.md5()\n    while True:\n        d = file.read(8096)\n        if not d:\n            break\n        m.update(d)\n    return m.hexdigest()\n\n\ndef rel_has_nofollow(rel):\n    \"\"\"Return True if link rel attribute has nofollow type\"\"\"\n    return rel is not None and 'nofollow' in rel.split()\n\n\ndef create_instance(objcls, settings, crawler, *args, **kwargs):\n    \"\"\"Construct a class instance using its ``from_crawler`` or\n    ``from_settings`` constructors, if available.\n\n    At least one of ``settings`` and ``crawler`` needs to be different from\n    ``None``. If ``settings `` is ``None``, ``crawler.settings`` will be used.\n    If ``crawler`` is ``None``, only the ``from_settings`` constructor will be\n    tried.\n\n    ``*args`` and ``**kwargs`` are forwarded to the constructors.\n\n    Raises ``ValueError`` if both ``settings`` and ``crawler`` are ``None``.\n    \"\"\"\n    if settings is None:\n        if crawler is None:\n            raise ValueError(\"Specifiy at least one of settings and crawler.\")\n        settings = crawler.settings\n    if crawler and hasattr(objcls, 'from_crawler'):\n        return objcls.from_crawler(crawler, *args, **kwargs)\n    elif hasattr(objcls, 'from_settings'):\n        return objcls.from_settings(settings, *args, **kwargs)\n    else:\n        return objcls(*args, **kwargs)\n\n\n@contextmanager\ndef set_environ(**kwargs):\n    \"\"\"Temporarily set environment variables inside the context manager and\n    fully restore previous environment afterwards\n    \"\"\"\n\n    original_env = {k: os.environ.get(k) for k in kwargs}\n    os.environ.update(kwargs)\n    try:\n        yield\n    finally:\n        for k, v in original_env.items():\n            if v is None:\n                del os.environ[k]\n            else:\n                os.environ[k] = v\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/multipart.py",
    "content": "\"\"\"\nTransitional module for moving to the w3lib library.\n\nFor new code, always import from w3lib.form instead of this module\n\"\"\"\nimport warnings\n\nfrom scrapy.exceptions import ScrapyDeprecationWarning\nfrom w3lib.form import *\n\n\nwarnings.warn(\"Module `scrapy.utils.multipart` is deprecated. \"\n              \"If you're using `encode_multipart` function, please use \"\n              \"`urllib3.filepost.encode_multipart_formdata` instead\",\n              ScrapyDeprecationWarning, stacklevel=2)"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/ossignal.py",
    "content": "\nfrom __future__ import absolute_import\nimport signal\n\nfrom twisted.internet import reactor\n\n\nsignal_names = {}\nfor signame in dir(signal):\n    if signame.startswith('SIG') and not signame.startswith('SIG_'):\n        signum = getattr(signal, signame)\n        if isinstance(signum, int):\n            signal_names[signum] = signame\n\n\ndef install_shutdown_handlers(function, override_sigint=True):\n    \"\"\"Install the given function as a signal handler for all common shutdown\n    signals (such as SIGINT, SIGTERM, etc). If override_sigint is ``False`` the\n    SIGINT handler won't be install if there is already a handler in place\n    (e.g.  Pdb)\n    \"\"\"\n    reactor._handleSignals()\n    signal.signal(signal.SIGTERM, function)\n    if signal.getsignal(signal.SIGINT) == signal.default_int_handler or \\\n            override_sigint:\n        signal.signal(signal.SIGINT, function)\n    # Catch Ctrl-Break in windows\n    if hasattr(signal, 'SIGBREAK'):\n        signal.signal(signal.SIGBREAK, function)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/project.py",
    "content": "import os\nfrom six.moves import cPickle as pickle\nimport warnings\n\nfrom importlib import import_module\nfrom os.path import join, dirname, abspath, isabs, exists\n\nfrom scrapy.utils.conf import closest_scrapy_cfg, get_config, init_env\nfrom scrapy.settings import Settings\nfrom scrapy.exceptions import NotConfigured\n\nENVVAR = 'SCRAPY_SETTINGS_MODULE'\nDATADIR_CFG_SECTION = 'datadir'\n\n\ndef inside_project():\n    scrapy_module = os.environ.get('SCRAPY_SETTINGS_MODULE')\n    if scrapy_module is not None:\n        try:\n            import_module(scrapy_module)\n        except ImportError as exc:\n            warnings.warn(\"Cannot import scrapy settings module %s: %s\" % (scrapy_module, exc))\n        else:\n            return True\n    return bool(closest_scrapy_cfg())\n\n\ndef project_data_dir(project='default'):\n    \"\"\"Return the current project data dir, creating it if it doesn't exist\"\"\"\n    if not inside_project():\n        raise NotConfigured(\"Not inside a project\")\n    cfg = get_config()\n    if cfg.has_option(DATADIR_CFG_SECTION, project):\n        d = cfg.get(DATADIR_CFG_SECTION, project)\n    else:\n        scrapy_cfg = closest_scrapy_cfg()\n        if not scrapy_cfg:\n            raise NotConfigured(\"Unable to find scrapy.cfg file to infer project data dir\")\n        d = abspath(join(dirname(scrapy_cfg), '.scrapy'))\n    if not exists(d):\n        os.makedirs(d)\n    return d\n\n\ndef data_path(path, createdir=False):\n    \"\"\"\n    Return the given path joined with the .scrapy data directory.\n    If given an absolute path, return it unmodified.\n    \"\"\"\n    if not isabs(path):\n        if inside_project():\n            path = join(project_data_dir(), path)\n        else:\n            path = join('.scrapy', path)\n    if createdir and not exists(path):\n        os.makedirs(path)\n    return path\n\n\ndef get_project_settings():\n    if ENVVAR not in os.environ:\n        project = os.environ.get('SCRAPY_PROJECT', 'default')\n        init_env(project)\n\n    settings = Settings()\n    settings_module_path = os.environ.get(ENVVAR)\n    if settings_module_path:\n        settings.setmodule(settings_module_path, priority='project')\n\n    # XXX: remove this hack\n    pickled_settings = os.environ.get(\"SCRAPY_PICKLED_SETTINGS_TO_OVERRIDE\")\n    if pickled_settings:\n        settings.setdict(pickle.loads(pickled_settings), priority='project')\n\n    # XXX: deprecate and remove this functionality\n    env_overrides = {k[7:]: v for k, v in os.environ.items() if\n                     k.startswith('SCRAPY_')}\n    if env_overrides:\n        settings.setdict(env_overrides, priority='project')\n\n    return settings\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/python.py",
    "content": "\"\"\"\nThis module contains essential stuff that should've come with Python itself ;)\n\"\"\"\nimport gc\nimport os\nimport re\nimport inspect\nimport weakref\nimport errno\nimport six\nfrom functools import partial, wraps\nfrom itertools import chain\nimport sys\n\nfrom scrapy.utils.decorators import deprecated\n\n\ndef flatten(x):\n    \"\"\"flatten(sequence) -> list\n\n    Returns a single, flat list which contains all elements retrieved\n    from the sequence and all recursively contained sub-sequences\n    (iterables).\n\n    Examples:\n    >>> [1, 2, [3,4], (5,6)]\n    [1, 2, [3, 4], (5, 6)]\n    >>> flatten([[[1,2,3], (42,None)], [4,5], [6], 7, (8,9,10)])\n    [1, 2, 3, 42, None, 4, 5, 6, 7, 8, 9, 10]\n    >>> flatten([\"foo\", \"bar\"])\n    ['foo', 'bar']\n    >>> flatten([\"foo\", [\"baz\", 42], \"bar\"])\n    ['foo', 'baz', 42, 'bar']\n    \"\"\"\n    return list(iflatten(x))\n\n\ndef iflatten(x):\n    \"\"\"iflatten(sequence) -> iterator\n\n    Similar to ``.flatten()``, but returns iterator instead\"\"\"\n    for el in x:\n        if is_listlike(el):\n            for el_ in iflatten(el):\n                yield el_\n        else:\n            yield el\n\n\ndef is_listlike(x):\n    \"\"\"\n    >>> is_listlike(\"foo\")\n    False\n    >>> is_listlike(5)\n    False\n    >>> is_listlike(b\"foo\")\n    False\n    >>> is_listlike([b\"foo\"])\n    True\n    >>> is_listlike((b\"foo\",))\n    True\n    >>> is_listlike({})\n    True\n    >>> is_listlike(set())\n    True\n    >>> is_listlike((x for x in range(3)))\n    True\n    >>> is_listlike(six.moves.xrange(5))\n    True\n    \"\"\"\n    return hasattr(x, \"__iter__\") and not isinstance(x, (six.text_type, bytes))\n\n\ndef unique(list_, key=lambda x: x):\n    \"\"\"efficient function to uniquify a list preserving item order\"\"\"\n    seen = set()\n    result = []\n    for item in list_:\n        seenkey = key(item)\n        if seenkey in seen:\n            continue\n        seen.add(seenkey)\n        result.append(item)\n    return result\n\n\ndef to_unicode(text, encoding=None, errors='strict'):\n    \"\"\"Return the unicode representation of a bytes object ``text``. If\n    ``text`` is already an unicode object, return it as-is.\"\"\"\n    if isinstance(text, six.text_type):\n        return text\n    if not isinstance(text, (bytes, six.text_type)):\n        raise TypeError('to_unicode must receive a bytes, str or unicode '\n                        'object, got %s' % type(text).__name__)\n    if encoding is None:\n        encoding = 'utf-8'\n    return text.decode(encoding, errors)\n\n\ndef to_bytes(text, encoding=None, errors='strict'):\n    \"\"\"Return the binary representation of ``text``. If ``text``\n    is already a bytes object, return it as-is.\"\"\"\n    if isinstance(text, bytes):\n        return text\n    if not isinstance(text, six.string_types):\n        raise TypeError('to_bytes must receive a unicode, str or bytes '\n                        'object, got %s' % type(text).__name__)\n    if encoding is None:\n        encoding = 'utf-8'\n    return text.encode(encoding, errors)\n\n\ndef to_native_str(text, encoding=None, errors='strict'):\n    \"\"\" Return str representation of ``text``\n    (bytes in Python 2.x and unicode in Python 3.x). \"\"\"\n    if six.PY2:\n        return to_bytes(text, encoding, errors)\n    else:\n        return to_unicode(text, encoding, errors)\n\n\ndef re_rsearch(pattern, text, chunk_size=1024):\n    \"\"\"\n    This function does a reverse search in a text using a regular expression\n    given in the attribute 'pattern'.\n    Since the re module does not provide this functionality, we have to find for\n    the expression into chunks of text extracted from the end (for the sake of efficiency).\n    At first, a chunk of 'chunk_size' kilobytes is extracted from the end, and searched for\n    the pattern. If the pattern is not found, another chunk is extracted, and another\n    search is performed.\n    This process continues until a match is found, or until the whole file is read.\n    In case the pattern wasn't found, None is returned, otherwise it returns a tuple containing\n    the start position of the match, and the ending (regarding the entire text).\n    \"\"\"\n    def _chunk_iter():\n        offset = len(text)\n        while True:\n            offset -= (chunk_size * 1024)\n            if offset <= 0:\n                break\n            yield (text[offset:], offset)\n        yield (text, 0)\n\n    if isinstance(pattern, six.string_types):\n        pattern = re.compile(pattern)\n\n    for chunk, offset in _chunk_iter():\n        matches = [match for match in pattern.finditer(chunk)]\n        if matches:\n            start, end = matches[-1].span()\n            return offset + start, offset + end\n    return None\n\n\ndef memoizemethod_noargs(method):\n    \"\"\"Decorator to cache the result of a method (without arguments) using a\n    weak reference to its object\n    \"\"\"\n    cache = weakref.WeakKeyDictionary()\n    @wraps(method)\n    def new_method(self, *args, **kwargs):\n        if self not in cache:\n            cache[self] = method(self, *args, **kwargs)\n        return cache[self]\n    return new_method\n\n\n_BINARYCHARS = {six.b(chr(i)) for i in range(32)} - {b\"\\0\", b\"\\t\", b\"\\n\", b\"\\r\"}\n_BINARYCHARS |= {ord(ch) for ch in _BINARYCHARS}\n\n@deprecated(\"scrapy.utils.python.binary_is_text\")\ndef isbinarytext(text):\n    \"\"\" This function is deprecated.\n    Please use scrapy.utils.python.binary_is_text, which was created to be more\n    clear about the functions behavior: it is behaving inverted to this one. \"\"\"\n    return not binary_is_text(text)\n\n\ndef binary_is_text(data):\n    \"\"\" Returns ``True`` if the given ``data`` argument (a ``bytes`` object)\n    does not contain unprintable control characters.\n    \"\"\"\n    if not isinstance(data, bytes):\n        raise TypeError(\"data must be bytes, got '%s'\" % type(data).__name__)\n    return all(c not in _BINARYCHARS for c in data)\n\n\ndef _getargspec_py23(func):\n    \"\"\"_getargspec_py23(function) -> named tuple ArgSpec(args, varargs, keywords,\n                                                        defaults)\n\n    Identical to inspect.getargspec() in python2, but uses\n    inspect.getfullargspec() for python3 behind the scenes to avoid\n    DeprecationWarning.\n\n    >>> def f(a, b=2, *ar, **kw):\n    ...     pass\n\n    >>> _getargspec_py23(f)\n    ArgSpec(args=['a', 'b'], varargs='ar', keywords='kw', defaults=(2,))\n    \"\"\"\n    if six.PY2:\n        return inspect.getargspec(func)\n\n    return inspect.ArgSpec(*inspect.getfullargspec(func)[:4])\n\n\ndef get_func_args(func, stripself=False):\n    \"\"\"Return the argument name list of a callable\"\"\"\n    if inspect.isfunction(func):\n        func_args, _, _, _ = _getargspec_py23(func)\n    elif inspect.isclass(func):\n        return get_func_args(func.__init__, True)\n    elif inspect.ismethod(func):\n        return get_func_args(func.__func__, True)\n    elif inspect.ismethoddescriptor(func):\n        return []\n    elif isinstance(func, partial):\n        return [x for x in get_func_args(func.func)[len(func.args):]\n                if not (func.keywords and x in func.keywords)]\n    elif hasattr(func, '__call__'):\n        if inspect.isroutine(func):\n            return []\n        elif getattr(func, '__name__', None) == '__call__':\n            return []\n        else:\n            return get_func_args(func.__call__, True)\n    else:\n        raise TypeError('%s is not callable' % type(func))\n    if stripself:\n        func_args.pop(0)\n    return func_args\n\n\ndef get_spec(func):\n    \"\"\"Returns (args, kwargs) tuple for a function\n    >>> import re\n    >>> get_spec(re.match)\n    (['pattern', 'string'], {'flags': 0})\n\n    >>> class Test(object):\n    ...     def __call__(self, val):\n    ...         pass\n    ...     def method(self, val, flags=0):\n    ...         pass\n\n    >>> get_spec(Test)\n    (['self', 'val'], {})\n\n    >>> get_spec(Test.method)\n    (['self', 'val'], {'flags': 0})\n\n    >>> get_spec(Test().method)\n    (['self', 'val'], {'flags': 0})\n    \"\"\"\n\n    if inspect.isfunction(func) or inspect.ismethod(func):\n        spec = _getargspec_py23(func)\n    elif hasattr(func, '__call__'):\n        spec = _getargspec_py23(func.__call__)\n    else:\n        raise TypeError('%s is not callable' % type(func))\n\n    defaults = spec.defaults or []\n\n    firstdefault = len(spec.args) - len(defaults)\n    args = spec.args[:firstdefault]\n    kwargs = dict(zip(spec.args[firstdefault:], defaults))\n    return args, kwargs\n\n\ndef equal_attributes(obj1, obj2, attributes):\n    \"\"\"Compare two objects attributes\"\"\"\n    # not attributes given return False by default\n    if not attributes:\n        return False\n\n    temp1, temp2 = object(), object()\n    for attr in attributes:\n        # support callables like itemgetter\n        if callable(attr):\n            if attr(obj1) != attr(obj2):\n                return False\n        elif getattr(obj1, attr, temp1) != getattr(obj2, attr, temp2):\n            return False\n    # all attributes equal\n    return True\n\n\nclass WeakKeyCache(object):\n\n    def __init__(self, default_factory):\n        self.default_factory = default_factory\n        self._weakdict = weakref.WeakKeyDictionary()\n\n    def __getitem__(self, key):\n        if key not in self._weakdict:\n            self._weakdict[key] = self.default_factory(key)\n        return self._weakdict[key]\n\n\n@deprecated\ndef stringify_dict(dct_or_tuples, encoding='utf-8', keys_only=True):\n    \"\"\"Return a (new) dict with unicode keys (and values when \"keys_only\" is\n    False) of the given dict converted to strings. ``dct_or_tuples`` can be a\n    dict or a list of tuples, like any dict constructor supports.\n    \"\"\"\n    d = {}\n    for k, v in six.iteritems(dict(dct_or_tuples)):\n        k = k.encode(encoding) if isinstance(k, six.text_type) else k\n        if not keys_only:\n            v = v.encode(encoding) if isinstance(v, six.text_type) else v\n        d[k] = v\n    return d\n\n\n@deprecated\ndef is_writable(path):\n    \"\"\"Return True if the given path can be written (if it exists) or created\n    (if it doesn't exist)\n    \"\"\"\n    if os.path.exists(path):\n        return os.access(path, os.W_OK)\n    else:\n        return os.access(os.path.dirname(path), os.W_OK)\n\n\n@deprecated\ndef setattr_default(obj, name, value):\n    \"\"\"Set attribute value, but only if it's not already set. Similar to\n    setdefault() for dicts.\n    \"\"\"\n    if not hasattr(obj, name):\n        setattr(obj, name, value)\n\n\ndef retry_on_eintr(function, *args, **kw):\n    \"\"\"Run a function and retry it while getting EINTR errors\"\"\"\n    while True:\n        try:\n            return function(*args, **kw)\n        except IOError as e:\n            if e.errno != errno.EINTR:\n                raise\n\n\ndef without_none_values(iterable):\n    \"\"\"Return a copy of ``iterable`` with all ``None`` entries removed.\n\n    If ``iterable`` is a mapping, return a dictionary where all pairs that have\n    value ``None`` have been removed.\n    \"\"\"\n    try:\n        return {k: v for k, v in six.iteritems(iterable) if v is not None}\n    except AttributeError:\n        return type(iterable)((v for v in iterable if v is not None))\n\n\ndef global_object_name(obj):\n    \"\"\"\n    Return full name of a global object.\n\n    >>> from scrapy import Request\n    >>> global_object_name(Request)\n    'scrapy.http.request.Request'\n    \"\"\"\n    return \"%s.%s\" % (obj.__module__, obj.__name__)\n\n\nif hasattr(sys, \"pypy_version_info\"):\n    def garbage_collect():\n        # Collecting weakreferences can take two collections on PyPy.\n        gc.collect()\n        gc.collect()\nelse:\n    def garbage_collect():\n        gc.collect()\n\n\nclass MutableChain(object):\n    \"\"\"\n    Thin wrapper around itertools.chain, allowing to add iterables \"in-place\"\n    \"\"\"\n    def __init__(self, *args):\n        self.data = chain(*args)\n\n    def extend(self, *iterables):\n        self.data = chain(self.data, *iterables)\n\n    def __iter__(self):\n        return self.data.__iter__()\n\n    def __next__(self):\n        return next(self.data)\n\n    next = __next__\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/reactor.py",
    "content": "from twisted.internet import reactor, error\n\ndef listen_tcp(portrange, host, factory):\n    \"\"\"Like reactor.listenTCP but tries different ports in a range.\"\"\"\n    assert len(portrange) <= 2, \"invalid portrange: %s\" % portrange\n    if not hasattr(portrange, '__iter__'):\n        return reactor.listenTCP(portrange, factory, interface=host)\n    if not portrange:\n        return reactor.listenTCP(0, factory, interface=host)\n    if len(portrange) == 1:\n        return reactor.listenTCP(portrange[0], factory, interface=host)\n    for x in range(portrange[0], portrange[1]+1):\n        try:\n            return reactor.listenTCP(x, factory, interface=host)\n        except error.CannotListenError:\n            if x == portrange[1]:\n                raise\n\n\nclass CallLaterOnce(object):\n    \"\"\"Schedule a function to be called in the next reactor loop, but only if\n    it hasn't been already scheduled since the last time it ran.\n    \"\"\"\n\n    def __init__(self, func, *a, **kw):\n        self._func = func\n        self._a = a\n        self._kw = kw\n        self._call = None\n\n    def schedule(self, delay=0):\n        if self._call is None:\n            self._call = reactor.callLater(delay, self)\n\n    def cancel(self):\n        if self._call:\n            self._call.cancel()\n\n    def __call__(self):\n        self._call = None\n        return self._func(*self._a, **self._kw)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/reqser.py",
    "content": "\"\"\"\nHelper functions for serializing (and deserializing) requests.\n\"\"\"\nimport six\n\nfrom scrapy.http import Request\nfrom scrapy.utils.python import to_unicode, to_native_str\nfrom scrapy.utils.misc import load_object\n\n\ndef request_to_dict(request, spider=None):\n    \"\"\"Convert Request object to a dict.\n\n    If a spider is given, it will try to find out the name of the spider method\n    used in the callback and store that as the callback.\n    \"\"\"\n    cb = request.callback\n    if callable(cb):\n        cb = _find_method(spider, cb)\n    eb = request.errback\n    if callable(eb):\n        eb = _find_method(spider, eb)\n    d = {\n        'url': to_unicode(request.url),  # urls should be safe (safe_string_url)\n        'callback': cb,\n        'errback': eb,\n        'method': request.method,\n        'headers': dict(request.headers),\n        'body': request.body,\n        'cookies': request.cookies,\n        'meta': request.meta,\n        '_encoding': request._encoding,\n        'priority': request.priority,\n        'dont_filter': request.dont_filter,\n        'flags': request.flags,\n        'cb_kwargs': request.cb_kwargs,\n    }\n    if type(request) is not Request:\n        d['_class'] = request.__module__ + '.' + request.__class__.__name__\n    return d\n\n\ndef request_from_dict(d, spider=None):\n    \"\"\"Create Request object from a dict.\n\n    If a spider is given, it will try to resolve the callbacks looking at the\n    spider for methods with the same name.\n    \"\"\"\n    cb = d['callback']\n    if cb and spider:\n        cb = _get_method(spider, cb)\n    eb = d['errback']\n    if eb and spider:\n        eb = _get_method(spider, eb)\n    request_cls = load_object(d['_class']) if '_class' in d else Request\n    return request_cls(\n        url=to_native_str(d['url']),\n        callback=cb,\n        errback=eb,\n        method=d['method'],\n        headers=d['headers'],\n        body=d['body'],\n        cookies=d['cookies'],\n        meta=d['meta'],\n        encoding=d['_encoding'],\n        priority=d['priority'],\n        dont_filter=d['dont_filter'],\n        flags=d.get('flags'),\n        cb_kwargs=d.get('cb_kwargs'),\n    )\n\n\ndef _is_private_method(name):\n    return name.startswith('__') and not name.endswith('__')\n\n\ndef _mangle_private_name(obj, func, name):\n    qualname = getattr(func, '__qualname__', None)\n    if qualname is None:\n        classname = obj.__class__.__name__.lstrip('_')\n        return '_%s%s' % (classname, name)\n    else:\n        splits = qualname.split('.')\n        return '_%s%s' % (splits[-2], splits[-1])\n\n\ndef _find_method(obj, func):\n    if obj:\n        try:\n            func_self = six.get_method_self(func)\n        except AttributeError:  # func has no __self__\n            pass\n        else:\n            if func_self is obj:\n                name = six.get_method_function(func).__name__\n                if _is_private_method(name):\n                    return _mangle_private_name(obj, func, name)\n                return name\n    raise ValueError(\"Function %s is not a method of: %s\" % (func, obj))\n\n\ndef _get_method(obj, name):\n    name = str(name)\n    try:\n        return getattr(obj, name)\n    except AttributeError:\n        raise ValueError(\"Method %r not found in: %s\" % (name, obj))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/request.py",
    "content": "\"\"\"\nThis module provides some useful functions for working with\nscrapy.http.Request objects\n\"\"\"\n\nfrom __future__ import print_function\nimport hashlib\nimport weakref\nfrom six.moves.urllib.parse import urlunparse\n\nfrom w3lib.http import basic_auth_header\nfrom scrapy.utils.python import to_bytes, to_native_str\n\nfrom w3lib.url import canonicalize_url\nfrom scrapy.utils.httpobj import urlparse_cached\n\n\n_fingerprint_cache = weakref.WeakKeyDictionary()\ndef request_fingerprint(request, include_headers=None):\n    \"\"\"\n    Return the request fingerprint.\n\n    The request fingerprint is a hash that uniquely identifies the resource the\n    request points to. For example, take the following two urls:\n\n    http://www.example.com/query?id=111&cat=222\n    http://www.example.com/query?cat=222&id=111\n\n    Even though those are two different URLs both point to the same resource\n    and are equivalent (ie. they should return the same response).\n\n    Another example are cookies used to store session ids. Suppose the\n    following page is only accesible to authenticated users:\n\n    http://www.example.com/members/offers.html\n\n    Lot of sites use a cookie to store the session id, which adds a random\n    component to the HTTP Request and thus should be ignored when calculating\n    the fingerprint.\n\n    For this reason, request headers are ignored by default when calculating\n    the fingeprint. If you want to include specific headers use the\n    include_headers argument, which is a list of Request headers to include.\n\n    \"\"\"\n    if include_headers:\n        include_headers = tuple(to_bytes(h.lower())\n                                 for h in sorted(include_headers))\n    cache = _fingerprint_cache.setdefault(request, {})\n    if include_headers not in cache:\n        fp = hashlib.sha1()\n        fp.update(to_bytes(request.method))\n        fp.update(to_bytes(canonicalize_url(request.url)))\n        fp.update(request.body or b'')\n        if include_headers:\n            for hdr in include_headers:\n                if hdr in request.headers:\n                    fp.update(hdr)\n                    for v in request.headers.getlist(hdr):\n                        fp.update(v)\n        cache[include_headers] = fp.hexdigest()\n    return cache[include_headers]\n\n\ndef request_authenticate(request, username, password):\n    \"\"\"Autenticate the given request (in place) using the HTTP basic access\n    authentication mechanism (RFC 2617) and the given username and password\n    \"\"\"\n    request.headers['Authorization'] = basic_auth_header(username, password)\n\n\ndef request_httprepr(request):\n    \"\"\"Return the raw HTTP representation (as bytes) of the given request.\n    This is provided only for reference since it's not the actual stream of\n    bytes that will be send when performing the request (that's controlled\n    by Twisted).\n    \"\"\"\n    parsed = urlparse_cached(request)\n    path = urlunparse(('', '', parsed.path or '/', parsed.params, parsed.query, ''))\n    s = to_bytes(request.method) + b\" \" + to_bytes(path) + b\" HTTP/1.1\\r\\n\"\n    s += b\"Host: \" + to_bytes(parsed.hostname or b'') + b\"\\r\\n\"\n    if request.headers:\n        s += request.headers.to_string() + b\"\\r\\n\"\n    s += b\"\\r\\n\"\n    s += request.body\n    return s\n\n\ndef referer_str(request):\n    \"\"\" Return Referer HTTP header suitable for logging. \"\"\"\n    referrer = request.headers.get('Referer')\n    if referrer is None:\n        return referrer\n    return to_native_str(referrer, errors='replace')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/response.py",
    "content": "\"\"\"\nThis module provides some useful functions for working with\nscrapy.http.Response objects\n\"\"\"\nimport os\nimport weakref\nimport webbrowser\nimport tempfile\n\nfrom twisted.web import http\nfrom scrapy.utils.python import to_bytes, to_native_str\nfrom w3lib import html\n\n\n_baseurl_cache = weakref.WeakKeyDictionary()\ndef get_base_url(response):\n    \"\"\"Return the base url of the given response, joined with the response url\"\"\"\n    if response not in _baseurl_cache:\n        text = response.text[0:4096]\n        _baseurl_cache[response] = html.get_base_url(text, response.url,\n            response.encoding)\n    return _baseurl_cache[response]\n\n\n_metaref_cache = weakref.WeakKeyDictionary()\ndef get_meta_refresh(response, ignore_tags=('script', 'noscript')):\n    \"\"\"Parse the http-equiv refrsh parameter from the given response\"\"\"\n    if response not in _metaref_cache:\n        text = response.text[0:4096]\n        _metaref_cache[response] = html.get_meta_refresh(text, response.url,\n            response.encoding, ignore_tags=ignore_tags)\n    return _metaref_cache[response]\n\n\ndef response_status_message(status):\n    \"\"\"Return status code plus status text descriptive message\n    \"\"\"\n    message = http.RESPONSES.get(int(status), \"Unknown Status\")\n    return '%s %s' % (status, to_native_str(message))\n\n\ndef response_httprepr(response):\n    \"\"\"Return raw HTTP representation (as bytes) of the given response. This\n    is provided only for reference, since it's not the exact stream of bytes\n    that was received (that's not exposed by Twisted).\n    \"\"\"\n    s = b\"HTTP/1.1 \" + to_bytes(str(response.status)) + b\" \" + \\\n        to_bytes(http.RESPONSES.get(response.status, b'')) + b\"\\r\\n\"\n    if response.headers:\n        s += response.headers.to_string() + b\"\\r\\n\"\n    s += b\"\\r\\n\"\n    s += response.body\n    return s\n\n\ndef open_in_browser(response, _openfunc=webbrowser.open):\n    \"\"\"Open the given response in a local web browser, populating the <base>\n    tag for external links to work\n    \"\"\"\n    from scrapy.http import HtmlResponse, TextResponse\n    # XXX: this implementation is a bit dirty and could be improved\n    body = response.body\n    if isinstance(response, HtmlResponse):\n        if b'<base' not in body:\n            repl = '<head><base href=\"%s\">' % response.url\n            body = body.replace(b'<head>', to_bytes(repl))\n        ext = '.html'\n    elif isinstance(response, TextResponse):\n        ext = '.txt'\n    else:\n        raise TypeError(\"Unsupported response type: %s\" %\n                        response.__class__.__name__)\n    fd, fname = tempfile.mkstemp(ext)\n    os.write(fd, body)\n    os.close(fd)\n    return _openfunc(\"file://%s\" % fname)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/serialize.py",
    "content": "import json\nimport datetime\nimport decimal\n\nfrom twisted.internet import defer\n\nfrom scrapy.http import Request, Response\nfrom scrapy.item import BaseItem\n\n\nclass ScrapyJSONEncoder(json.JSONEncoder):\n\n    DATE_FORMAT = \"%Y-%m-%d\"\n    TIME_FORMAT = \"%H:%M:%S\"\n\n    def default(self, o):\n        if isinstance(o, set):\n            return list(o)\n        elif isinstance(o, datetime.datetime):\n            return o.strftime(\"%s %s\" % (self.DATE_FORMAT, self.TIME_FORMAT))\n        elif isinstance(o, datetime.date):\n            return o.strftime(self.DATE_FORMAT)\n        elif isinstance(o, datetime.time):\n            return o.strftime(self.TIME_FORMAT)\n        elif isinstance(o, decimal.Decimal):\n            return str(o)\n        elif isinstance(o, defer.Deferred):\n            return str(o)\n        elif isinstance(o, BaseItem):\n            return dict(o)\n        elif isinstance(o, Request):\n            return \"<%s %s %s>\" % (type(o).__name__, o.method, o.url)\n        elif isinstance(o, Response):\n            return \"<%s %s %s>\" % (type(o).__name__, o.status, o.url)\n        else:\n            return super(ScrapyJSONEncoder, self).default(o)\n\n\nclass ScrapyJSONDecoder(json.JSONDecoder):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/signal.py",
    "content": "\"\"\"Helper functions for working with signals\"\"\"\n\nimport logging\n\nfrom twisted.internet.defer import maybeDeferred, DeferredList, Deferred\nfrom twisted.python.failure import Failure\n\nfrom pydispatch.dispatcher import Any, Anonymous, liveReceivers, \\\n    getAllReceivers, disconnect\nfrom pydispatch.robustapply import robustApply\nfrom scrapy.utils.log import failure_to_exc_info\n\nlogger = logging.getLogger(__name__)\n\n\nclass _IgnoredException(Exception):\n    pass\n\n\ndef send_catch_log(signal=Any, sender=Anonymous, *arguments, **named):\n    \"\"\"Like pydispatcher.robust.sendRobust but it also logs errors and returns\n    Failures instead of exceptions.\n    \"\"\"\n    dont_log = named.pop('dont_log', _IgnoredException)\n    spider = named.get('spider', None)\n    responses = []\n    for receiver in liveReceivers(getAllReceivers(sender, signal)):\n        try:\n            response = robustApply(receiver, signal=signal, sender=sender,\n                *arguments, **named)\n            if isinstance(response, Deferred):\n                logger.error(\"Cannot return deferreds from signal handler: %(receiver)s\",\n                             {'receiver': receiver}, extra={'spider': spider})\n        except dont_log:\n            result = Failure()\n        except Exception:\n            result = Failure()\n            logger.error(\"Error caught on signal handler: %(receiver)s\",\n                         {'receiver': receiver},\n                         exc_info=True, extra={'spider': spider})\n        else:\n            result = response\n        responses.append((receiver, result))\n    return responses\n\n\ndef send_catch_log_deferred(signal=Any, sender=Anonymous, *arguments, **named):\n    \"\"\"Like send_catch_log but supports returning deferreds on signal handlers.\n    Returns a deferred that gets fired once all signal handlers deferreds were\n    fired.\n    \"\"\"\n    def logerror(failure, recv):\n        if dont_log is None or not isinstance(failure.value, dont_log):\n            logger.error(\"Error caught on signal handler: %(receiver)s\",\n                         {'receiver': recv},\n                         exc_info=failure_to_exc_info(failure),\n                         extra={'spider': spider})\n        return failure\n\n    dont_log = named.pop('dont_log', None)\n    spider = named.get('spider', None)\n    dfds = []\n    for receiver in liveReceivers(getAllReceivers(sender, signal)):\n        d = maybeDeferred(robustApply, receiver, signal=signal, sender=sender,\n                *arguments, **named)\n        d.addErrback(logerror, receiver)\n        d.addBoth(lambda result: (receiver, result))\n        dfds.append(d)\n    d = DeferredList(dfds)\n    d.addCallback(lambda out: [x[1] for x in out])\n    return d\n\n\ndef disconnect_all(signal=Any, sender=Any):\n    \"\"\"Disconnect all signal handlers. Useful for cleaning up after running\n    tests\n    \"\"\"\n    for receiver in liveReceivers(getAllReceivers(sender, signal)):\n        disconnect(receiver, signal=signal, sender=sender)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/sitemap.py",
    "content": "\"\"\"\nModule for processing Sitemaps.\n\nNote: The main purpose of this module is to provide support for the\nSitemapSpider, its API is subject to change without notice.\n\"\"\"\n\nimport lxml.etree\nfrom six.moves.urllib.parse import urljoin\n\n\nclass Sitemap(object):\n    \"\"\"Class to parse Sitemap (type=urlset) and Sitemap Index\n    (type=sitemapindex) files\"\"\"\n\n    def __init__(self, xmltext):\n        xmlp = lxml.etree.XMLParser(recover=True, remove_comments=True, resolve_entities=False)\n        self._root = lxml.etree.fromstring(xmltext, parser=xmlp)\n        rt = self._root.tag\n        self.type = self._root.tag.split('}', 1)[1] if '}' in rt else rt\n\n    def __iter__(self):\n        for elem in self._root.getchildren():\n            d = {}\n            for el in elem.getchildren():\n                tag = el.tag\n                name = tag.split('}', 1)[1] if '}' in tag else tag\n\n                if name == 'link':\n                    if 'href' in el.attrib:\n                        d.setdefault('alternate', []).append(el.get('href'))\n                else:\n                    d[name] = el.text.strip() if el.text else ''\n\n            if 'loc' in d:\n                yield d\n\n\ndef sitemap_urls_from_robots(robots_text, base_url=None):\n    \"\"\"Return an iterator over all sitemap urls contained in the given\n    robots.txt file\n    \"\"\"\n    for line in robots_text.splitlines():\n        if line.lstrip().lower().startswith('sitemap:'):\n            url = line.split(':', 1)[1].strip()\n            yield urljoin(base_url, url)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/spider.py",
    "content": "import logging\nimport inspect\n\nimport six\n\nfrom scrapy.spiders import Spider\nfrom scrapy.utils.misc import  arg_to_iter\n\nlogger = logging.getLogger(__name__)\n\n\ndef iterate_spider_output(result):\n    return arg_to_iter(result)\n\n\ndef iter_spider_classes(module):\n    \"\"\"Return an iterator over all spider classes defined in the given module\n    that can be instantiated (ie. which have name)\n    \"\"\"\n    # this needs to be imported here until get rid of the spider manager\n    # singleton in scrapy.spider.spiders\n    from scrapy.spiders import Spider\n\n    for obj in six.itervalues(vars(module)):\n        if inspect.isclass(obj) and \\\n           issubclass(obj, Spider) and \\\n           obj.__module__ == module.__name__ and \\\n           getattr(obj, 'name', None):\n            yield obj\n\ndef spidercls_for_request(spider_loader, request, default_spidercls=None,\n                          log_none=False, log_multiple=False):\n    \"\"\"Return a spider class that handles the given Request.\n\n    This will look for the spiders that can handle the given request (using\n    the spider loader) and return a Spider class if (and only if) there is\n    only one Spider able to handle the Request.\n\n    If multiple spiders (or no spider) are found, it will return the\n    default_spidercls passed. It can optionally log if multiple or no spiders\n    are found.\n    \"\"\"\n    snames = spider_loader.find_by_request(request)\n    if len(snames) == 1:\n        return spider_loader.load(snames[0])\n\n    if len(snames) > 1 and log_multiple:\n        logger.error('More than one spider can handle: %(request)s - %(snames)s',\n                     {'request': request, 'snames': ', '.join(snames)})\n\n    if len(snames) == 0 and log_none:\n        logger.error('Unable to find spider that handles: %(request)s',\n                     {'request': request})\n\n    return default_spidercls\n\n\nclass DefaultSpider(Spider):\n    name = 'default'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/template.py",
    "content": "\"\"\"Helper functions for working with templates\"\"\"\n\nimport os\nimport re\nimport string\n\n\ndef render_templatefile(path, **kwargs):\n    with open(path, 'rb') as fp:\n        raw = fp.read().decode('utf8')\n\n    content = string.Template(raw).substitute(**kwargs)\n\n    render_path = path[:-len('.tmpl')] if path.endswith('.tmpl') else path\n    with open(render_path, 'wb') as fp:\n        fp.write(content.encode('utf8'))\n    if path.endswith('.tmpl'):\n        os.remove(path)\n\n\nCAMELCASE_INVALID_CHARS = re.compile(r'[^a-zA-Z\\d]')\ndef string_camelcase(string):\n    \"\"\" Convert a word  to its CamelCase version and remove invalid chars\n\n    >>> string_camelcase('lost-pound')\n    'LostPound'\n\n    >>> string_camelcase('missing_images')\n    'MissingImages'\n\n    \"\"\"\n    return CAMELCASE_INVALID_CHARS.sub('', string.title())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/test.py",
    "content": "\"\"\"\nThis module contains some assorted functions used in tests\n\"\"\"\n\nfrom __future__ import absolute_import\nimport os\n\nfrom importlib import import_module\nfrom twisted.trial.unittest import SkipTest\n\nfrom scrapy.exceptions import NotConfigured\nfrom scrapy.utils.boto import is_botocore\n\n\ndef assert_aws_environ():\n    \"\"\"Asserts the current environment is suitable for running AWS testsi.\n    Raises SkipTest with the reason if it's not.\n    \"\"\"\n    skip_if_no_boto()\n    if 'AWS_ACCESS_KEY_ID' not in os.environ:\n        raise SkipTest(\"AWS keys not found\")\n\n\ndef assert_gcs_environ():\n    if 'GCS_PROJECT_ID' not in os.environ:\n        raise SkipTest(\"GCS_PROJECT_ID not found\")\n\n\ndef skip_if_no_boto():\n    try:\n        is_botocore()\n    except NotConfigured as e:\n        raise SkipTest(e)\n\ndef get_s3_content_and_delete(bucket, path, with_key=False):\n    \"\"\" Get content from s3 key, and delete key afterwards.\n    \"\"\"\n    if is_botocore():\n        import botocore.session\n        session = botocore.session.get_session()\n        client = session.create_client('s3')\n        key = client.get_object(Bucket=bucket, Key=path)\n        content = key['Body'].read()\n        client.delete_object(Bucket=bucket, Key=path)\n    else:\n        import boto\n        # assuming boto=2.2.2\n        bucket = boto.connect_s3().get_bucket(bucket, validate=False)\n        key = bucket.get_key(path)\n        content = key.get_contents_as_string()\n        bucket.delete_key(path)\n    return (content, key) if with_key else content\n\ndef get_gcs_content_and_delete(bucket, path):\n    from google.cloud import storage\n    client = storage.Client(project=os.environ.get('GCS_PROJECT_ID'))\n    bucket = client.get_bucket(bucket)\n    blob = bucket.get_blob(path)\n    content = blob.download_as_string()\n    acl = list(blob.acl)  # loads acl before it will be deleted\n    bucket.delete_blob(path)\n    return content, acl, blob\n\ndef get_crawler(spidercls=None, settings_dict=None):\n    \"\"\"Return an unconfigured Crawler object. If settings_dict is given, it\n    will be used to populate the crawler settings with a project level\n    priority.\n    \"\"\"\n    from scrapy.crawler import CrawlerRunner\n    from scrapy.spiders import Spider\n\n    runner = CrawlerRunner(settings_dict)\n    return runner.create_crawler(spidercls or Spider)\n\ndef get_pythonpath():\n    \"\"\"Return a PYTHONPATH suitable to use in processes so that they find this\n    installation of Scrapy\"\"\"\n    scrapy_path = import_module('scrapy').__path__[0]\n    return os.path.dirname(scrapy_path) + os.pathsep + os.environ.get('PYTHONPATH', '')\n\ndef get_testenv():\n    \"\"\"Return a OS environment dict suitable to fork processes that need to import\n    this installation of Scrapy, instead of a system installed one.\n    \"\"\"\n    env = os.environ.copy()\n    env['PYTHONPATH'] = get_pythonpath()\n    return env\n\ndef assert_samelines(testcase, text1, text2, msg=None):\n    \"\"\"Asserts text1 and text2 have the same lines, ignoring differences in\n    line endings between platforms\n    \"\"\"\n    testcase.assertEqual(text1.splitlines(), text2.splitlines(), msg)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/testproc.py",
    "content": "from __future__ import absolute_import\nimport sys\nimport os\n\nfrom twisted.internet import reactor, defer, protocol\n\n\nclass ProcessTest(object):\n\n    command = None\n    prefix = [sys.executable, '-m', 'scrapy.cmdline']\n    cwd = os.getcwd()  # trial chdirs to temp dir\n\n    def execute(self, args, check_code=True, settings=None):\n        env = os.environ.copy()\n        if settings is not None:\n            env['SCRAPY_SETTINGS_MODULE'] = settings\n        cmd = self.prefix + [self.command] + list(args)\n        pp = TestProcessProtocol()\n        pp.deferred.addBoth(self._process_finished, cmd, check_code)\n        reactor.spawnProcess(pp, cmd[0], cmd, env=env, path=self.cwd)\n        return pp.deferred\n\n    def _process_finished(self, pp, cmd, check_code):\n        if pp.exitcode and check_code:\n            msg = \"process %s exit with code %d\" % (cmd, pp.exitcode)\n            msg += \"\\n>>> stdout <<<\\n%s\" % pp.out\n            msg += \"\\n\"\n            msg += \"\\n>>> stderr <<<\\n%s\" % pp.err\n            raise RuntimeError(msg)\n        return pp.exitcode, pp.out, pp.err\n\n\nclass TestProcessProtocol(protocol.ProcessProtocol):\n\n    def __init__(self):\n        self.deferred = defer.Deferred()\n        self.out = b''\n        self.err = b''\n        self.exitcode = None\n\n    def outReceived(self, data):\n        self.out += data\n\n    def errReceived(self, data):\n        self.err += data\n\n    def processEnded(self, status):\n        self.exitcode = status.value.exitCode\n        self.deferred.callback(self)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/testsite.py",
    "content": "from __future__ import print_function\nfrom six.moves.urllib.parse import urljoin\n\nfrom twisted.internet import reactor\nfrom twisted.web import server, resource, static, util\n\n\nclass SiteTest(object):\n\n    def setUp(self):\n        super(SiteTest, self).setUp()\n        self.site = reactor.listenTCP(0, test_site(), interface=\"127.0.0.1\")\n        self.baseurl = \"http://localhost:%d/\" % self.site.getHost().port\n\n    def tearDown(self):\n        super(SiteTest, self).tearDown()\n        self.site.stopListening()\n\n    def url(self, path):\n        return urljoin(self.baseurl, path)\n\n\nclass NoMetaRefreshRedirect(util.Redirect):\n    def render(self, request):\n        content = util.Redirect.render(self, request)\n        return content.replace(b'http-equiv=\\\"refresh\\\"',\n            b'http-no-equiv=\\\"do-not-refresh-me\\\"')\n\n\ndef test_site():\n    r = resource.Resource()\n    r.putChild(b\"text\", static.Data(b\"Works\", \"text/plain\"))\n    r.putChild(b\"html\", static.Data(b\"<body><p class='one'>Works</p><p class='two'>World</p></body>\", \"text/html\"))\n    r.putChild(b\"enc-gb18030\", static.Data(b\"<p>gb18030 encoding</p>\", \"text/html; charset=gb18030\"))\n    r.putChild(b\"redirect\", util.Redirect(b\"/redirected\"))\n    r.putChild(b\"redirect-no-meta-refresh\", NoMetaRefreshRedirect(b\"/redirected\"))\n    r.putChild(b\"redirected\", static.Data(b\"Redirected here\", \"text/plain\"))\n    return server.Site(r)\n\n\nif __name__ == '__main__':\n    port = reactor.listenTCP(0, test_site(), interface=\"127.0.0.1\")\n    print(\"http://localhost:%d/\" % port.getHost().port)\n    reactor.run()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/trackref.py",
    "content": "\"\"\"This module provides some functions and classes to record and report\nreferences to live object instances.\n\nIf you want live objects for a particular class to be tracked, you only have to\nsubclass from object_ref (instead of object).\n\nAbout performance: This library has a minimal performance impact when enabled,\nand no performance penalty at all when disabled (as object_ref becomes just an\nalias to object in that case).\n\"\"\"\n\nfrom __future__ import print_function\nimport weakref\nfrom time import time\nfrom operator import itemgetter\nfrom collections import defaultdict\nimport six\n\n\nNoneType = type(None)\nlive_refs = defaultdict(weakref.WeakKeyDictionary)\n\n\nclass object_ref(object):\n    \"\"\"Inherit from this class (instead of object) to a keep a record of live\n    instances\"\"\"\n\n    __slots__ = ()\n\n    def __new__(cls, *args, **kwargs):\n        obj = object.__new__(cls)\n        live_refs[cls][obj] = time()\n        return obj\n\n\ndef format_live_refs(ignore=NoneType):\n    \"\"\"Return a tabular representation of tracked objects\"\"\"\n    s = \"Live References\\n\\n\"\n    now = time()\n    for cls, wdict in sorted(six.iteritems(live_refs),\n                             key=lambda x: x[0].__name__):\n        if not wdict:\n            continue\n        if issubclass(cls, ignore):\n            continue\n        oldest = min(six.itervalues(wdict))\n        s += \"%-30s %6d   oldest: %ds ago\\n\" % (\n            cls.__name__, len(wdict), now - oldest\n        )\n    return s\n\n\ndef print_live_refs(*a, **kw):\n    \"\"\"Print tracked objects\"\"\"\n    print(format_live_refs(*a, **kw))\n\n\ndef get_oldest(class_name):\n    \"\"\"Get the oldest object for a specific class name\"\"\"\n    for cls, wdict in six.iteritems(live_refs):\n        if cls.__name__ == class_name:\n            if not wdict:\n                break\n            return min(six.iteritems(wdict), key=itemgetter(1))[0]\n\n\ndef iter_all(class_name):\n    \"\"\"Iterate over all objects of the same class by its class name\"\"\"\n    for cls, wdict in six.iteritems(live_refs):\n        if cls.__name__ == class_name:\n            return six.iterkeys(wdict)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/url.py",
    "content": "\"\"\"\nThis module contains general purpose URL functions not found in the standard\nlibrary.\n\nSome of the functions that used to be imported from this module have been moved\nto the w3lib.url module. Always import those from there instead.\n\"\"\"\nimport posixpath\nimport re\nfrom six.moves.urllib.parse import (ParseResult, urldefrag, urlparse, urlunparse)\n\n# scrapy.utils.url was moved to w3lib.url and import * ensures this\n# move doesn't break old code\nfrom w3lib.url import *\nfrom w3lib.url import _safe_chars, _unquotepath\nfrom scrapy.utils.python import to_unicode\n\n\ndef url_is_from_any_domain(url, domains):\n    \"\"\"Return True if the url belongs to any of the given domains\"\"\"\n    host = parse_url(url).netloc.lower()\n    if not host:\n        return False\n    domains = [d.lower() for d in domains]\n    return any((host == d) or (host.endswith('.%s' % d)) for d in domains)\n\n\ndef url_is_from_spider(url, spider):\n    \"\"\"Return True if the url belongs to the given spider\"\"\"\n    return url_is_from_any_domain(url,\n        [spider.name] + list(getattr(spider, 'allowed_domains', [])))\n\n\ndef url_has_any_extension(url, extensions):\n    return posixpath.splitext(parse_url(url).path)[1].lower() in extensions\n\n\ndef parse_url(url, encoding=None):\n    \"\"\"Return urlparsed url from the given argument (which could be an already\n    parsed url)\n    \"\"\"\n    if isinstance(url, ParseResult):\n        return url\n    return urlparse(to_unicode(url, encoding))\n\n\ndef escape_ajax(url):\n    \"\"\"\n    Return the crawleable url according to:\n    https://developers.google.com/webmasters/ajax-crawling/docs/getting-started\n\n    >>> escape_ajax(\"www.example.com/ajax.html#!key=value\")\n    'www.example.com/ajax.html?_escaped_fragment_=key%3Dvalue'\n    >>> escape_ajax(\"www.example.com/ajax.html?k1=v1&k2=v2#!key=value\")\n    'www.example.com/ajax.html?k1=v1&k2=v2&_escaped_fragment_=key%3Dvalue'\n    >>> escape_ajax(\"www.example.com/ajax.html?#!key=value\")\n    'www.example.com/ajax.html?_escaped_fragment_=key%3Dvalue'\n    >>> escape_ajax(\"www.example.com/ajax.html#!\")\n    'www.example.com/ajax.html?_escaped_fragment_='\n\n    URLs that are not \"AJAX crawlable\" (according to Google) returned as-is:\n\n    >>> escape_ajax(\"www.example.com/ajax.html#key=value\")\n    'www.example.com/ajax.html#key=value'\n    >>> escape_ajax(\"www.example.com/ajax.html#\")\n    'www.example.com/ajax.html#'\n    >>> escape_ajax(\"www.example.com/ajax.html\")\n    'www.example.com/ajax.html'\n    \"\"\"\n    defrag, frag = urldefrag(url)\n    if not frag.startswith('!'):\n        return url\n    return add_or_replace_parameter(defrag, '_escaped_fragment_', frag[1:])\n\n\ndef add_http_if_no_scheme(url):\n    \"\"\"Add http as the default scheme if it is missing from the url.\"\"\"\n    match = re.match(r\"^\\w+://\", url, flags=re.I)\n    if not match:\n        parts = urlparse(url)\n        scheme = \"http:\" if parts.netloc else \"http://\"\n        url = scheme + url\n\n    return url\n\n\ndef guess_scheme(url):\n    \"\"\"Add an URL scheme if missing: file:// for filepath-like input or http:// otherwise.\"\"\"\n    parts = urlparse(url)\n    if parts.scheme:\n        return url\n    # Note: this does not match Windows filepath\n    if re.match(r'''^                   # start with...\n                    (\n                        \\.              # ...a single dot,\n                        (\n                            \\. | [^/\\.]+  # optionally followed by\n                        )?                # either a second dot or some characters\n                    )?      # optional match of \".\", \"..\" or \".blabla\"\n                    /       # at least one \"/\" for a file path,\n                    .       # and something after the \"/\"\n                    ''', parts.path, flags=re.VERBOSE):\n        return any_to_uri(url)\n    else:\n        return add_http_if_no_scheme(url)\n\n\ndef strip_url(url, strip_credentials=True, strip_default_port=True, origin_only=False, strip_fragment=True):\n\n    \"\"\"Strip URL string from some of its components:\n\n    - ``strip_credentials`` removes \"user:password@\"\n    - ``strip_default_port`` removes \":80\" (resp. \":443\", \":21\")\n      from http:// (resp. https://, ftp://) URLs\n    - ``origin_only`` replaces path component with \"/\", also dropping\n      query and fragment components ; it also strips credentials\n    - ``strip_fragment`` drops any #fragment component\n    \"\"\"\n\n    parsed_url = urlparse(url)\n    netloc = parsed_url.netloc\n    if (strip_credentials or origin_only) and (parsed_url.username or parsed_url.password):\n        netloc = netloc.split('@')[-1]\n    if strip_default_port and parsed_url.port:\n        if (parsed_url.scheme, parsed_url.port) in (('http', 80),\n                                                    ('https', 443),\n                                                    ('ftp', 21)):\n            netloc = netloc.replace(':{p.port}'.format(p=parsed_url), '')\n    return urlunparse((\n        parsed_url.scheme,\n        netloc,\n        '/' if origin_only else parsed_url.path,\n        '' if origin_only else parsed_url.params,\n        '' if origin_only else parsed_url.query,\n        '' if strip_fragment else parsed_url.fragment\n    ))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/utils/versions.py",
    "content": "import platform\nimport sys\n\nimport cssselect\nimport lxml.etree\nimport parsel\nimport twisted\nimport w3lib\n\nimport scrapy\n\n\ndef scrapy_components_versions():\n    lxml_version = \".\".join(map(str, lxml.etree.LXML_VERSION))\n    libxml2_version = \".\".join(map(str, lxml.etree.LIBXML_VERSION))\n    try:\n        w3lib_version = w3lib.__version__\n    except AttributeError:\n        w3lib_version = \"<1.14.3\"\n    try:\n        import cryptography\n        cryptography_version = cryptography.__version__\n    except ImportError:\n        cryptography_version = \"unknown\"\n\n    return [\n        (\"Scrapy\", scrapy.__version__),\n        (\"lxml\", lxml_version),\n        (\"libxml2\", libxml2_version),\n        (\"cssselect\", cssselect.__version__),\n        (\"parsel\", parsel.__version__),\n        (\"w3lib\", w3lib_version),\n        (\"Twisted\", twisted.version.short()),\n        (\"Python\", sys.version.replace(\"\\n\", \"- \")),\n        (\"pyOpenSSL\", _get_openssl_version()),\n        (\"cryptography\", cryptography_version),\n        (\"Platform\",  platform.platform()),\n    ]\n\n\ndef _get_openssl_version():\n    try:\n        import OpenSSL\n        openssl = OpenSSL.SSL.SSLeay_version(OpenSSL.SSL.SSLEAY_VERSION)\\\n            .decode('ascii', errors='replace')\n    # pyOpenSSL 0.12 does not expose openssl version\n    except AttributeError:\n        openssl = 'Unknown OpenSSL version'\n\n    return '{} ({})'.format(OpenSSL.version.__version__, openssl)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/xlib/__init__.py",
    "content": "\"\"\"This package contains some third party modules that are distributed along\nwith Scrapy\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/xlib/pydispatch.py",
    "content": "from __future__ import absolute_import\n\nimport warnings\nfrom scrapy.exceptions import ScrapyDeprecationWarning\n\nfrom pydispatch import (\n    dispatcher,\n    errors,\n    robust,\n    robustapply,\n    saferef,\n)\n\nwarnings.warn(\"Importing from scrapy.xlib.pydispatch is deprecated and will\"\n              \" no longer be supported in future Scrapy versions.\"\n              \" If you just want to connect signals use the from_crawler class method,\"\n              \" otherwise import pydispatch directly if needed.\"\n              \" See: https://github.com/scrapy/scrapy/issues/1762\",\n              ScrapyDeprecationWarning, stacklevel=2)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy/xlib/tx.py",
    "content": "from __future__ import absolute_import\n\nimport warnings\nfrom scrapy.exceptions import ScrapyDeprecationWarning\n\nfrom twisted.web import client\nfrom twisted.internet import endpoints\n\nAgent = client.Agent  # since < 11.1\nProxyAgent = client.ProxyAgent  # since 11.1\nResponseDone = client.ResponseDone  # since 11.1\nResponseFailed = client.ResponseFailed  # since 11.1\nHTTPConnectionPool = client.HTTPConnectionPool  # since 12.1\nTCP4ClientEndpoint = endpoints.TCP4ClientEndpoint  # since 10.1\n\nwarnings.warn(\"Importing from scrapy.xlib.tx is deprecated and will\"\n              \" no longer be supported in future Scrapy versions.\"\n              \" Update your code to import from twisted proper.\",\n              ScrapyDeprecationWarning, stacklevel=2)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis/__init__.py",
    "content": "# -*- coding: utf-8 -*-\nfrom .connection import (  # NOQA\n    get_redis,\n    get_redis_from_settings,\n)\n\n\n__author__ = 'Rolando Espinoza'\n__email__ = 'rolando at rmax.io'\n__version__ = '0.6.8'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis/connection.py",
    "content": "import six\n\nfrom scrapy.utils.misc import load_object\n\nfrom . import defaults\n\n\n# Shortcut maps 'setting name' -> 'parmater name'.\nSETTINGS_PARAMS_MAP = {\n    'REDIS_URL': 'url',\n    'REDIS_HOST': 'host',\n    'REDIS_PORT': 'port',\n    'REDIS_ENCODING': 'encoding',\n}\n\n\ndef get_redis_from_settings(settings):\n    \"\"\"Returns a redis client instance from given Scrapy settings object.\n\n    This function uses ``get_client`` to instantiate the client and uses\n    ``defaults.REDIS_PARAMS`` global as defaults values for the parameters. You\n    can override them using the ``REDIS_PARAMS`` setting.\n\n    Parameters\n    ----------\n    settings : Settings\n        A scrapy settings object. See the supported settings below.\n\n    Returns\n    -------\n    server\n        Redis client instance.\n\n    Other Parameters\n    ----------------\n    REDIS_URL : str, optional\n        Server connection URL.\n    REDIS_HOST : str, optional\n        Server host.\n    REDIS_PORT : str, optional\n        Server port.\n    REDIS_ENCODING : str, optional\n        Data encoding.\n    REDIS_PARAMS : dict, optional\n        Additional client parameters.\n\n    \"\"\"\n    params = defaults.REDIS_PARAMS.copy()\n    params.update(settings.getdict('REDIS_PARAMS'))\n    # XXX: Deprecate REDIS_* settings.\n    for source, dest in SETTINGS_PARAMS_MAP.items():\n        val = settings.get(source)\n        if val:\n            params[dest] = val\n\n    # Allow ``redis_cls`` to be a path to a class.\n    if isinstance(params.get('redis_cls'), six.string_types):\n        params['redis_cls'] = load_object(params['redis_cls'])\n\n    return get_redis(**params)\n\n\n# Backwards compatible alias.\nfrom_settings = get_redis_from_settings\n\n\ndef get_redis(**kwargs):\n    \"\"\"Returns a redis client instance.\n\n    Parameters\n    ----------\n    redis_cls : class, optional\n        Defaults to ``redis.StrictRedis``.\n    url : str, optional\n        If given, ``redis_cls.from_url`` is used to instantiate the class.\n    **kwargs\n        Extra parameters to be passed to the ``redis_cls`` class.\n\n    Returns\n    -------\n    server\n        Redis client instance.\n\n    \"\"\"\n    redis_cls = kwargs.pop('redis_cls', defaults.REDIS_CLS)\n    url = kwargs.pop('url', None)\n    if url:\n        return redis_cls.from_url(url, **kwargs)\n    else:\n        return redis_cls(**kwargs)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis/defaults.py",
    "content": "import redis\n\n\n# For standalone use.\nDUPEFILTER_KEY = 'dupefilter:%(timestamp)s'\n\nPIPELINE_KEY = '%(spider)s:items'\n\nREDIS_CLS = redis.StrictRedis\nREDIS_ENCODING = 'utf-8'\n# Sane connection defaults.\nREDIS_PARAMS = {\n    'socket_timeout': 30,\n    'socket_connect_timeout': 30,\n    'retry_on_timeout': True,\n    'encoding': REDIS_ENCODING,\n}\n\nSCHEDULER_QUEUE_KEY = '%(spider)s:requests'\nSCHEDULER_QUEUE_CLASS = 'scrapy_redis.queue.PriorityQueue'\nSCHEDULER_DUPEFILTER_KEY = '%(spider)s:dupefilter'\nSCHEDULER_DUPEFILTER_CLASS = 'scrapy_redis.dupefilter.RFPDupeFilter'\n\nSTART_URLS_KEY = '%(name)s:start_urls'\nSTART_URLS_AS_SET = False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis/dupefilter.py",
    "content": "import logging\nimport time\n\nfrom scrapy.dupefilters import BaseDupeFilter\nfrom scrapy.utils.request import request_fingerprint\n\nfrom . import defaults\nfrom .connection import get_redis_from_settings\n\n\nlogger = logging.getLogger(__name__)\n\n\n# TODO: Rename class to RedisDupeFilter.\nclass RFPDupeFilter(BaseDupeFilter):\n    \"\"\"Redis-based request duplicates filter.\n\n    This class can also be used with default Scrapy's scheduler.\n\n    \"\"\"\n\n    logger = logger\n\n    def __init__(self, server, key, debug=False):\n        \"\"\"Initialize the duplicates filter.\n\n        Parameters\n        ----------\n        server : redis.StrictRedis\n            The redis server instance.\n        key : str\n            Redis key Where to store fingerprints.\n        debug : bool, optional\n            Whether to log filtered requests.\n\n        \"\"\"\n        self.server = server\n        self.key = key\n        self.debug = debug\n        self.logdupes = True\n\n    @classmethod\n    def from_settings(cls, settings):\n        \"\"\"Returns an instance from given settings.\n\n        This uses by default the key ``dupefilter:<timestamp>``. When using the\n        ``scrapy_redis.scheduler.Scheduler`` class, this method is not used as\n        it needs to pass the spider name in the key.\n\n        Parameters\n        ----------\n        settings : scrapy.settings.Settings\n\n        Returns\n        -------\n        RFPDupeFilter\n            A RFPDupeFilter instance.\n\n\n        \"\"\"\n        server = get_redis_from_settings(settings)\n        # XXX: This creates one-time key. needed to support to use this\n        # class as standalone dupefilter with scrapy's default scheduler\n        # if scrapy passes spider on open() method this wouldn't be needed\n        # TODO: Use SCRAPY_JOB env as default and fallback to timestamp.\n        key = defaults.DUPEFILTER_KEY % {'timestamp': int(time.time())}\n        debug = settings.getbool('DUPEFILTER_DEBUG')\n        return cls(server, key=key, debug=debug)\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        \"\"\"Returns instance from crawler.\n\n        Parameters\n        ----------\n        crawler : scrapy.crawler.Crawler\n\n        Returns\n        -------\n        RFPDupeFilter\n            Instance of RFPDupeFilter.\n\n        \"\"\"\n        return cls.from_settings(crawler.settings)\n\n    def request_seen(self, request):\n        \"\"\"Returns True if request was already seen.\n\n        Parameters\n        ----------\n        request : scrapy.http.Request\n\n        Returns\n        -------\n        bool\n\n        \"\"\"\n        fp = self.request_fingerprint(request)\n        # This returns the number of values added, zero if already exists.\n        added = self.server.sadd(self.key, fp)\n        return added == 0\n\n    def request_fingerprint(self, request):\n        \"\"\"Returns a fingerprint for a given request.\n\n        Parameters\n        ----------\n        request : scrapy.http.Request\n\n        Returns\n        -------\n        str\n\n        \"\"\"\n        return request_fingerprint(request)\n\n    def close(self, reason=''):\n        \"\"\"Delete data on close. Called by Scrapy's scheduler.\n\n        Parameters\n        ----------\n        reason : str, optional\n\n        \"\"\"\n        self.clear()\n\n    def clear(self):\n        \"\"\"Clears fingerprints data.\"\"\"\n        self.server.delete(self.key)\n\n    def log(self, request, spider):\n        \"\"\"Logs given request.\n\n        Parameters\n        ----------\n        request : scrapy.http.Request\n        spider : scrapy.spiders.Spider\n\n        \"\"\"\n        if self.debug:\n            msg = \"Filtered duplicate request: %(request)s\"\n            self.logger.debug(msg, {'request': request}, extra={'spider': spider})\n        elif self.logdupes:\n            msg = (\"Filtered duplicate request %(request)s\"\n                   \" - no more duplicates will be shown\"\n                   \" (see DUPEFILTER_DEBUG to show all duplicates)\")\n            self.logger.debug(msg, {'request': request}, extra={'spider': spider})\n            self.logdupes = False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis/picklecompat.py",
    "content": "\"\"\"A pickle wrapper module with protocol=-1 by default.\"\"\"\n\ntry:\n    import cPickle as pickle  # PY2\nexcept ImportError:\n    import pickle\n\n\ndef loads(s):\n    return pickle.loads(s)\n\n\ndef dumps(obj):\n    return pickle.dumps(obj, protocol=-1)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis/pipelines.py",
    "content": "from scrapy.utils.misc import load_object\nfrom scrapy.utils.serialize import ScrapyJSONEncoder\nfrom twisted.internet.threads import deferToThread\n\nfrom . import connection, defaults\n\n\ndefault_serialize = ScrapyJSONEncoder().encode\n\n\nclass RedisPipeline(object):\n    \"\"\"Pushes serialized item into a redis list/queue\n\n    Settings\n    --------\n    REDIS_ITEMS_KEY : str\n        Redis key where to store items.\n    REDIS_ITEMS_SERIALIZER : str\n        Object path to serializer function.\n\n    \"\"\"\n\n    def __init__(self, server,\n                 key=defaults.PIPELINE_KEY,\n                 serialize_func=default_serialize):\n        \"\"\"Initialize pipeline.\n\n        Parameters\n        ----------\n        server : StrictRedis\n            Redis client instance.\n        key : str\n            Redis key where to store items.\n        serialize_func : callable\n            Items serializer function.\n\n        \"\"\"\n        self.server = server\n        self.key = key\n        self.serialize = serialize_func\n\n    @classmethod\n    def from_settings(cls, settings):\n        params = {\n            'server': connection.from_settings(settings),\n        }\n        if settings.get('REDIS_ITEMS_KEY'):\n            params['key'] = settings['REDIS_ITEMS_KEY']\n        if settings.get('REDIS_ITEMS_SERIALIZER'):\n            params['serialize_func'] = load_object(\n                settings['REDIS_ITEMS_SERIALIZER']\n            )\n\n        return cls(**params)\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        return cls.from_settings(crawler.settings)\n\n    def process_item(self, item, spider):\n        return deferToThread(self._process_item, item, spider)\n\n    def _process_item(self, item, spider):\n        key = self.item_key(item, spider)\n        data = self.serialize(item)\n        self.server.rpush(key, data)\n        return item\n\n    def item_key(self, item, spider):\n        \"\"\"Returns redis key based on given spider.\n\n        Override this function to use a different key depending on the item\n        and/or spider.\n\n        \"\"\"\n        return self.key % {'spider': spider.name}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis/queue.py",
    "content": "from scrapy.utils.reqser import request_to_dict, request_from_dict\n\nfrom . import picklecompat\n\n\nclass Base(object):\n    \"\"\"Per-spider base queue class\"\"\"\n\n    def __init__(self, server, spider, key, serializer=None):\n        \"\"\"Initialize per-spider redis queue.\n\n        Parameters\n        ----------\n        server : StrictRedis\n            Redis client instance.\n        spider : Spider\n            Scrapy spider instance.\n        key: str\n            Redis key where to put and get messages.\n        serializer : object\n            Serializer object with ``loads`` and ``dumps`` methods.\n\n        \"\"\"\n        if serializer is None:\n            # Backward compatibility.\n            # TODO: deprecate pickle.\n            serializer = picklecompat\n        if not hasattr(serializer, 'loads'):\n            raise TypeError(\"serializer does not implement 'loads' function: %r\"\n                            % serializer)\n        if not hasattr(serializer, 'dumps'):\n            raise TypeError(\"serializer '%s' does not implement 'dumps' function: %r\"\n                            % serializer)\n\n        self.server = server\n        self.spider = spider\n        self.key = key % {'spider': spider.name}\n        self.serializer = serializer\n\n    def _encode_request(self, request):\n        \"\"\"Encode a request object\"\"\"\n        obj = request_to_dict(request, self.spider)\n        return self.serializer.dumps(obj)\n\n    def _decode_request(self, encoded_request):\n        \"\"\"Decode an request previously encoded\"\"\"\n        obj = self.serializer.loads(encoded_request)\n        return request_from_dict(obj, self.spider)\n\n    def __len__(self):\n        \"\"\"Return the length of the queue\"\"\"\n        raise NotImplementedError\n\n    def push(self, request):\n        \"\"\"Push a request\"\"\"\n        raise NotImplementedError\n\n    def pop(self, timeout=0):\n        \"\"\"Pop a request\"\"\"\n        raise NotImplementedError\n\n    def clear(self):\n        \"\"\"Clear queue/stack\"\"\"\n        self.server.delete(self.key)\n\n\nclass FifoQueue(Base):\n    \"\"\"Per-spider FIFO queue\"\"\"\n\n    def __len__(self):\n        \"\"\"Return the length of the queue\"\"\"\n        return self.server.llen(self.key)\n\n    def push(self, request):\n        \"\"\"Push a request\"\"\"\n        self.server.lpush(self.key, self._encode_request(request))\n\n    def pop(self, timeout=0):\n        \"\"\"Pop a request\"\"\"\n        if timeout > 0:\n            data = self.server.brpop(self.key, timeout)\n            if isinstance(data, tuple):\n                data = data[1]\n        else:\n            data = self.server.rpop(self.key)\n        if data:\n            return self._decode_request(data)\n\n\nclass PriorityQueue(Base):\n    \"\"\"Per-spider priority queue abstraction using redis' sorted set\"\"\"\n\n    def __len__(self):\n        \"\"\"Return the length of the queue\"\"\"\n        return self.server.zcard(self.key)\n\n    def push(self, request):\n        \"\"\"Push a request\"\"\"\n        data = self._encode_request(request)\n        score = -request.priority\n        # We don't use zadd method as the order of arguments change depending on\n        # whether the class is Redis or StrictRedis, and the option of using\n        # kwargs only accepts strings, not bytes.\n        self.server.execute_command('ZADD', self.key, score, data)\n\n    def pop(self, timeout=0):\n        \"\"\"\n        Pop a request\n        timeout not support in this queue class\n        \"\"\"\n        # use atomic range/remove using multi/exec\n        pipe = self.server.pipeline()\n        pipe.multi()\n        pipe.zrange(self.key, 0, 0).zremrangebyrank(self.key, 0, 0)\n        results, count = pipe.execute()\n        if results:\n            return self._decode_request(results[0])\n\n\nclass LifoQueue(Base):\n    \"\"\"Per-spider LIFO queue.\"\"\"\n\n    def __len__(self):\n        \"\"\"Return the length of the stack\"\"\"\n        return self.server.llen(self.key)\n\n    def push(self, request):\n        \"\"\"Push a request\"\"\"\n        self.server.lpush(self.key, self._encode_request(request))\n\n    def pop(self, timeout=0):\n        \"\"\"Pop a request\"\"\"\n        if timeout > 0:\n            data = self.server.blpop(self.key, timeout)\n            if isinstance(data, tuple):\n                data = data[1]\n        else:\n            data = self.server.lpop(self.key)\n\n        if data:\n            return self._decode_request(data)\n\n\n# TODO: Deprecate the use of these names.\nSpiderQueue = FifoQueue\nSpiderStack = LifoQueue\nSpiderPriorityQueue = PriorityQueue\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis/scheduler.py",
    "content": "import importlib\nimport six\n\nfrom scrapy.utils.misc import load_object\n\nfrom . import connection, defaults\n\n\n# TODO: add SCRAPY_JOB support.\nclass Scheduler(object):\n    \"\"\"Redis-based scheduler\n\n    Settings\n    --------\n    SCHEDULER_PERSIST : bool (default: False)\n        Whether to persist or clear redis queue.\n    SCHEDULER_FLUSH_ON_START : bool (default: False)\n        Whether to flush redis queue on start.\n    SCHEDULER_IDLE_BEFORE_CLOSE : int (default: 0)\n        How many seconds to wait before closing if no message is received.\n    SCHEDULER_QUEUE_KEY : str\n        Scheduler redis key.\n    SCHEDULER_QUEUE_CLASS : str\n        Scheduler queue class.\n    SCHEDULER_DUPEFILTER_KEY : str\n        Scheduler dupefilter redis key.\n    SCHEDULER_DUPEFILTER_CLASS : str\n        Scheduler dupefilter class.\n    SCHEDULER_SERIALIZER : str\n        Scheduler serializer.\n\n    \"\"\"\n\n    def __init__(self, server,\n                 persist=False,\n                 flush_on_start=False,\n                 queue_key=defaults.SCHEDULER_QUEUE_KEY,\n                 queue_cls=defaults.SCHEDULER_QUEUE_CLASS,\n                 dupefilter_key=defaults.SCHEDULER_DUPEFILTER_KEY,\n                 dupefilter_cls=defaults.SCHEDULER_DUPEFILTER_CLASS,\n                 idle_before_close=0,\n                 serializer=None):\n        \"\"\"Initialize scheduler.\n\n        Parameters\n        ----------\n        server : Redis\n            The redis server instance.\n        persist : bool\n            Whether to flush requests when closing. Default is False.\n        flush_on_start : bool\n            Whether to flush requests on start. Default is False.\n        queue_key : str\n            Requests queue key.\n        queue_cls : str\n            Importable path to the queue class.\n        dupefilter_key : str\n            Duplicates filter key.\n        dupefilter_cls : str\n            Importable path to the dupefilter class.\n        idle_before_close : int\n            Timeout before giving up.\n\n        \"\"\"\n        if idle_before_close < 0:\n            raise TypeError(\"idle_before_close cannot be negative\")\n\n        self.server = server\n        self.persist = persist\n        self.flush_on_start = flush_on_start\n        self.queue_key = queue_key\n        self.queue_cls = queue_cls\n        self.dupefilter_cls = dupefilter_cls\n        self.dupefilter_key = dupefilter_key\n        self.idle_before_close = idle_before_close\n        self.serializer = serializer\n        self.stats = None\n\n    def __len__(self):\n        return len(self.queue)\n\n    @classmethod\n    def from_settings(cls, settings):\n        kwargs = {\n            'persist': settings.getbool('SCHEDULER_PERSIST'),\n            'flush_on_start': settings.getbool('SCHEDULER_FLUSH_ON_START'),\n            'idle_before_close': settings.getint('SCHEDULER_IDLE_BEFORE_CLOSE'),\n        }\n\n        # If these values are missing, it means we want to use the defaults.\n        optional = {\n            # TODO: Use custom prefixes for this settings to note that are\n            # specific to scrapy-redis.\n            'queue_key': 'SCHEDULER_QUEUE_KEY',\n            'queue_cls': 'SCHEDULER_QUEUE_CLASS',\n            'dupefilter_key': 'SCHEDULER_DUPEFILTER_KEY',\n            # We use the default setting name to keep compatibility.\n            'dupefilter_cls': 'DUPEFILTER_CLASS',\n            'serializer': 'SCHEDULER_SERIALIZER',\n        }\n        for name, setting_name in optional.items():\n            val = settings.get(setting_name)\n            if val:\n                kwargs[name] = val\n\n        # Support serializer as a path to a module.\n        if isinstance(kwargs.get('serializer'), six.string_types):\n            kwargs['serializer'] = importlib.import_module(kwargs['serializer'])\n\n        server = connection.from_settings(settings)\n        # Ensure the connection is working.\n        server.ping()\n\n        return cls(server=server, **kwargs)\n\n    @classmethod\n    def from_crawler(cls, crawler):\n        instance = cls.from_settings(crawler.settings)\n        # FIXME: for now, stats are only supported from this constructor\n        instance.stats = crawler.stats\n        return instance\n\n    def open(self, spider):\n        self.spider = spider\n\n        try:\n            self.queue = load_object(self.queue_cls)(\n                server=self.server,\n                spider=spider,\n                key=self.queue_key % {'spider': spider.name},\n                serializer=self.serializer,\n            )\n        except TypeError as e:\n            raise ValueError(\"Failed to instantiate queue class '%s': %s\",\n                             self.queue_cls, e)\n\n        try:\n            self.df = load_object(self.dupefilter_cls)(\n                server=self.server,\n                key=self.dupefilter_key % {'spider': spider.name},\n                debug=spider.settings.getbool('DUPEFILTER_DEBUG'),\n            )\n        except TypeError as e:\n            raise ValueError(\"Failed to instantiate dupefilter class '%s': %s\",\n                             self.dupefilter_cls, e)\n\n        if self.flush_on_start:\n            self.flush()\n        # notice if there are requests already in the queue to resume the crawl\n        if len(self.queue):\n            spider.log(\"Resuming crawl (%d requests scheduled)\" % len(self.queue))\n\n    def close(self, reason):\n        if not self.persist:\n            self.flush()\n\n    def flush(self):\n        self.df.clear()\n        self.queue.clear()\n\n    def enqueue_request(self, request):\n        if not request.dont_filter and self.df.request_seen(request):\n            self.df.log(request, self.spider)\n            return False\n        if self.stats:\n            self.stats.inc_value('scheduler/enqueued/redis', spider=self.spider)\n        self.queue.push(request)\n        return True\n\n    def next_request(self):\n        block_pop_timeout = self.idle_before_close\n        request = self.queue.pop(block_pop_timeout)\n        if request and self.stats:\n            self.stats.inc_value('scheduler/dequeued/redis', spider=self.spider)\n        return request\n\n    def has_pending_requests(self):\n        return len(self) > 0\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis/spiders.py",
    "content": "from scrapy import signals\nfrom scrapy.exceptions import DontCloseSpider\nfrom scrapy.spiders import Spider, CrawlSpider\n\nfrom . import connection, defaults\nfrom .utils import bytes_to_str\n\n\nclass RedisMixin(object):\n    \"\"\"Mixin class to implement reading urls from a redis queue.\"\"\"\n    redis_key = None\n    redis_batch_size = None\n    redis_encoding = None\n\n    # Redis client placeholder.\n    server = None\n\n    def start_requests(self):\n        \"\"\"Returns a batch of start requests from redis.\"\"\"\n        return self.next_requests()\n\n    def setup_redis(self, crawler=None):\n        \"\"\"Setup redis connection and idle signal.\n\n        This should be called after the spider has set its crawler object.\n        \"\"\"\n        if self.server is not None:\n            return\n\n        if crawler is None:\n            # We allow optional crawler argument to keep backwards\n            # compatibility.\n            # XXX: Raise a deprecation warning.\n            crawler = getattr(self, 'crawler', None)\n\n        if crawler is None:\n            raise ValueError(\"crawler is required\")\n\n        settings = crawler.settings\n\n        if self.redis_key is None:\n            self.redis_key = settings.get(\n                'REDIS_START_URLS_KEY', defaults.START_URLS_KEY,\n            )\n\n        self.redis_key = self.redis_key % {'name': self.name}\n\n        if not self.redis_key.strip():\n            raise ValueError(\"redis_key must not be empty\")\n\n        if self.redis_batch_size is None:\n            # TODO: Deprecate this setting (REDIS_START_URLS_BATCH_SIZE).\n            self.redis_batch_size = settings.getint(\n                'REDIS_START_URLS_BATCH_SIZE',\n                settings.getint('CONCURRENT_REQUESTS'),\n            )\n\n        try:\n            self.redis_batch_size = int(self.redis_batch_size)\n        except (TypeError, ValueError):\n            raise ValueError(\"redis_batch_size must be an integer\")\n\n        if self.redis_encoding is None:\n            self.redis_encoding = settings.get('REDIS_ENCODING', defaults.REDIS_ENCODING)\n\n        self.logger.info(\"Reading start URLs from redis key '%(redis_key)s' \"\n                         \"(batch size: %(redis_batch_size)s, encoding: %(redis_encoding)s\",\n                         self.__dict__)\n\n        self.server = connection.from_settings(crawler.settings)\n        # The idle signal is called when the spider has no requests left,\n        # that's when we will schedule new requests from redis queue\n        crawler.signals.connect(self.spider_idle, signal=signals.spider_idle)\n\n    def next_requests(self):\n        \"\"\"Returns a request to be scheduled or none.\"\"\"\n        use_set = self.settings.getbool('REDIS_START_URLS_AS_SET', defaults.START_URLS_AS_SET)\n        fetch_one = self.server.spop if use_set else self.server.lpop\n        # XXX: Do we need to use a timeout here?\n        found = 0\n        # TODO: Use redis pipeline execution.\n        while found < self.redis_batch_size:\n            data = fetch_one(self.redis_key)\n            if not data:\n                # Queue empty.\n                break\n            req = self.make_request_from_data(data)\n            if req:\n                yield req\n                found += 1\n            else:\n                self.logger.debug(\"Request not made from data: %r\", data)\n\n        if found:\n            self.logger.debug(\"Read %s requests from '%s'\", found, self.redis_key)\n\n    def make_request_from_data(self, data):\n        \"\"\"Returns a Request instance from data coming from Redis.\n\n        By default, ``data`` is an encoded URL. You can override this method to\n        provide your own message decoding.\n\n        Parameters\n        ----------\n        data : bytes\n            Message from redis.\n\n        \"\"\"\n        url = bytes_to_str(data, self.redis_encoding)\n        return self.make_requests_from_url(url)\n\n    def schedule_next_requests(self):\n        \"\"\"Schedules a request if available\"\"\"\n        # TODO: While there is capacity, schedule a batch of redis requests.\n        for req in self.next_requests():\n            self.crawler.engine.crawl(req, spider=self)\n\n    def spider_idle(self):\n        \"\"\"Schedules a request if available, otherwise waits.\"\"\"\n        # XXX: Handle a sentinel to close the spider.\n        self.schedule_next_requests()\n        raise DontCloseSpider\n\n\nclass RedisSpider(RedisMixin, Spider):\n    \"\"\"Spider that reads urls from redis queue when idle.\n\n    Attributes\n    ----------\n    redis_key : str (default: REDIS_START_URLS_KEY)\n        Redis key where to fetch start URLs from..\n    redis_batch_size : int (default: CONCURRENT_REQUESTS)\n        Number of messages to fetch from redis on each attempt.\n    redis_encoding : str (default: REDIS_ENCODING)\n        Encoding to use when decoding messages from redis queue.\n\n    Settings\n    --------\n    REDIS_START_URLS_KEY : str (default: \"<spider.name>:start_urls\")\n        Default Redis key where to fetch start URLs from..\n    REDIS_START_URLS_BATCH_SIZE : int (deprecated by CONCURRENT_REQUESTS)\n        Default number of messages to fetch from redis on each attempt.\n    REDIS_START_URLS_AS_SET : bool (default: False)\n        Use SET operations to retrieve messages from the redis queue. If False,\n        the messages are retrieve using the LPOP command.\n    REDIS_ENCODING : str (default: \"utf-8\")\n        Default encoding to use when decoding messages from redis queue.\n\n    \"\"\"\n\n    @classmethod\n    def from_crawler(self, crawler, *args, **kwargs):\n        obj = super(RedisSpider, self).from_crawler(crawler, *args, **kwargs)\n        obj.setup_redis(crawler)\n        return obj\n\n\nclass RedisCrawlSpider(RedisMixin, CrawlSpider):\n    \"\"\"Spider that reads urls from redis queue when idle.\n\n    Attributes\n    ----------\n    redis_key : str (default: REDIS_START_URLS_KEY)\n        Redis key where to fetch start URLs from..\n    redis_batch_size : int (default: CONCURRENT_REQUESTS)\n        Number of messages to fetch from redis on each attempt.\n    redis_encoding : str (default: REDIS_ENCODING)\n        Encoding to use when decoding messages from redis queue.\n\n    Settings\n    --------\n    REDIS_START_URLS_KEY : str (default: \"<spider.name>:start_urls\")\n        Default Redis key where to fetch start URLs from..\n    REDIS_START_URLS_BATCH_SIZE : int (deprecated by CONCURRENT_REQUESTS)\n        Default number of messages to fetch from redis on each attempt.\n    REDIS_START_URLS_AS_SET : bool (default: True)\n        Use SET operations to retrieve messages from the redis queue.\n    REDIS_ENCODING : str (default: \"utf-8\")\n        Default encoding to use when decoding messages from redis queue.\n\n    \"\"\"\n\n    @classmethod\n    def from_crawler(self, crawler, *args, **kwargs):\n        obj = super(RedisCrawlSpider, self).from_crawler(crawler, *args, **kwargs)\n        obj.setup_redis(crawler)\n        return obj\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis/utils.py",
    "content": "import six\n\n\ndef bytes_to_str(s, encoding='utf-8'):\n    \"\"\"Returns a str if a bytes object is given.\"\"\"\n    if six.PY3 and isinstance(s, bytes):\n        return s.decode(encoding)\n    return s\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis-0.6.8.dist-info/DESCRIPTION.rst",
    "content": "============\nScrapy-Redis\n============\n\n.. image:: https://readthedocs.org/projects/scrapy-redis/badge/?version=latest\n        :target: https://readthedocs.org/projects/scrapy-redis/?badge=latest\n        :alt: Documentation Status\n\n.. image:: https://img.shields.io/pypi/v/scrapy-redis.svg\n        :target: https://pypi.python.org/pypi/scrapy-redis\n\n.. image:: https://img.shields.io/pypi/pyversions/scrapy-redis.svg\n        :target: https://pypi.python.org/pypi/scrapy-redis\n\n.. image:: https://img.shields.io/travis/rolando/scrapy-redis.svg\n        :target: https://travis-ci.org/rolando/scrapy-redis\n\n.. image:: https://codecov.io/github/rolando/scrapy-redis/coverage.svg?branch=master\n    :alt: Coverage Status\n    :target: https://codecov.io/github/rolando/scrapy-redis\n\n.. image:: https://landscape.io/github/rolando/scrapy-redis/master/landscape.svg?style=flat\n    :target: https://landscape.io/github/rolando/scrapy-redis/master\n    :alt: Code Quality Status\n\n.. image:: https://requires.io/github/rolando/scrapy-redis/requirements.svg?branch=master\n    :alt: Requirements Status\n    :target: https://requires.io/github/rolando/scrapy-redis/requirements/?branch=master\n\nRedis-based components for Scrapy.\n\n* Free software: MIT license\n* Documentation: https://scrapy-redis.readthedocs.org.\n* Python versions: 2.7, 3.4+\n\nFeatures\n--------\n\n* Distributed crawling/scraping\n\n    You can start multiple spider instances that share a single redis queue.\n    Best suitable for broad multi-domain crawls.\n\n* Distributed post-processing\n\n    Scraped items gets pushed into a redis queued meaning that you can start as\n    many as needed post-processing processes sharing the items queue.\n\n* Scrapy plug-and-play components\n\n    Scheduler + Duplication Filter, Item Pipeline, Base Spiders.\n\nRequirements\n------------\n\n* Python 2.7, 3.4 or 3.5\n* Redis >= 2.8\n* ``Scrapy`` >= 1.0\n* ``redis-py`` >= 2.10\n\nUsage\n-----\n\nUse the following settings in your project:\n\n.. code-block:: python\n\n  # Enables scheduling storing requests queue in redis.\n  SCHEDULER = \"scrapy_redis.scheduler.Scheduler\"\n\n  # Ensure all spiders share same duplicates filter through redis.\n  DUPEFILTER_CLASS = \"scrapy_redis.dupefilter.RFPDupeFilter\"\n\n  # Default requests serializer is pickle, but it can be changed to any module\n  # with loads and dumps functions. Note that pickle is not compatible between\n  # python versions.\n  # Caveat: In python 3.x, the serializer must return strings keys and support\n  # bytes as values. Because of this reason the json or msgpack module will not\n  # work by default. In python 2.x there is no such issue and you can use\n  # 'json' or 'msgpack' as serializers.\n  #SCHEDULER_SERIALIZER = \"scrapy_redis.picklecompat\"\n\n  # Don't cleanup redis queues, allows to pause/resume crawls.\n  #SCHEDULER_PERSIST = True\n\n  # Schedule requests using a priority queue. (default)\n  #SCHEDULER_QUEUE_CLASS = 'scrapy_redis.queue.PriorityQueue'\n\n  # Alternative queues.\n  #SCHEDULER_QUEUE_CLASS = 'scrapy_redis.queue.FifoQueue'\n  #SCHEDULER_QUEUE_CLASS = 'scrapy_redis.queue.LifoQueue'\n\n  # Max idle time to prevent the spider from being closed when distributed crawling.\n  # This only works if queue class is SpiderQueue or SpiderStack,\n  # and may also block the same time when your spider start at the first time (because the queue is empty).\n  #SCHEDULER_IDLE_BEFORE_CLOSE = 10\n\n  # Store scraped item in redis for post-processing.\n  ITEM_PIPELINES = {\n      'scrapy_redis.pipelines.RedisPipeline': 300\n  }\n\n  # The item pipeline serializes and stores the items in this redis key.\n  #REDIS_ITEMS_KEY = '%(spider)s:items'\n\n  # The items serializer is by default ScrapyJSONEncoder. You can use any\n  # importable path to a callable object.\n  #REDIS_ITEMS_SERIALIZER = 'json.dumps'\n\n  # Specify the host and port to use when connecting to Redis (optional).\n  #REDIS_HOST = 'localhost'\n  #REDIS_PORT = 6379\n\n  # Specify the full Redis URL for connecting (optional).\n  # If set, this takes precedence over the REDIS_HOST and REDIS_PORT settings.\n  #REDIS_URL = 'redis://user:pass@hostname:9001'\n\n  # Custom redis client parameters (i.e.: socket timeout, etc.)\n  #REDIS_PARAMS  = {}\n  # Use custom redis client class.\n  #REDIS_PARAMS['redis_cls'] = 'myproject.RedisClient'\n\n  # If True, it uses redis' ``spop`` operation. This could be useful if you\n  # want to avoid duplicates in your start urls list. In this cases, urls must\n  # be added via ``sadd`` command or you will get a type error from redis.\n  #REDIS_START_URLS_AS_SET = False\n\n  # Default start urls key for RedisSpider and RedisCrawlSpider.\n  #REDIS_START_URLS_KEY = '%(name)s:start_urls'\n\n  # Use other encoding than utf-8 for redis.\n  #REDIS_ENCODING = 'latin1'\n\n.. note::\n\n  Version 0.3 changed the requests serialization from `marshal` to `cPickle`,\n  therefore persisted requests using version 0.2 will not able to work on 0.3.\n\n\nRunning the example project\n---------------------------\n\nThis example illustrates how to share a spider's requests queue\nacross multiple spider instances, highly suitable for broad crawls.\n\n1. Setup scrapy_redis package in your PYTHONPATH\n\n2. Run the crawler for first time then stop it::\n\n    $ cd example-project\n    $ scrapy crawl dmoz\n    ... [dmoz] ...\n    ^C\n\n3. Run the crawler again to resume stopped crawling::\n\n    $ scrapy crawl dmoz\n    ... [dmoz] DEBUG: Resuming crawl (9019 requests scheduled)\n\n4. Start one or more additional scrapy crawlers::\n\n    $ scrapy crawl dmoz\n    ... [dmoz] DEBUG: Resuming crawl (8712 requests scheduled)\n\n5. Start one or more post-processing workers::\n\n    $ python process_items.py dmoz:items -v\n    ...\n    Processing: Kilani Giftware (http://www.dmoz.org/Computers/Shopping/Gifts/)\n    Processing: NinjaGizmos.com (http://www.dmoz.org/Computers/Shopping/Gifts/)\n    ...\n\n\nFeeding a Spider from Redis\n---------------------------\n\nThe class `scrapy_redis.spiders.RedisSpider` enables a spider to read the\nurls from redis. The urls in the redis queue will be processed one\nafter another, if the first request yields more requests, the spider\nwill process those requests before fetching another url from redis.\n\nFor example, create a file `myspider.py` with the code below:\n\n.. code-block:: python\n\n    from scrapy_redis.spiders import RedisSpider\n\n    class MySpider(RedisSpider):\n        name = 'myspider'\n\n        def parse(self, response):\n            # do stuff\n            pass\n\n\nThen:\n\n1. run the spider::\n\n    scrapy runspider myspider.py\n\n2. push urls to redis::\n\n    redis-cli lpush myspider:start_urls http://google.com\n\n\n.. note::\n\n    These spiders rely on the spider idle signal to fetch start urls, hence it\n    may have a few seconds of delay between the time you push a new url and the\n    spider starts crawling it.\n\n=======\nHistory\n=======\n\n\n0.6.8 (2017-02-14)\n------------------\n* Fixed automated release due to not matching registered email.\n\n0.6.7 (2016-12-27)\n------------------\n* Fixes bad formatting in logging message.\n\n0.6.6 (2016-12-20)\n------------------\n* Fixes wrong message on dupefilter duplicates.\n\n0.6.5 (2016-12-19)\n------------------\n* Fixed typo in default settings.\n\n\n0.6.4 (2016-12-18)\n------------------\n* Fixed data decoding in Python 3.x.\n* Added ``REDIS_ENCODING`` setting (default ``utf-8``).\n* Default to ``CONCURRENT_REQUESTS`` value for ``REDIS_START_URLS_BATCH_SIZE``.\n* Renamed queue classes to a proper naming conventiong (backwards compatible).\n\n0.6.3 (2016-07-03)\n------------------\n* Added ``REDIS_START_URLS_KEY`` setting.\n* Fixed spider method ``from_crawler`` signature.\n\n0.6.2 (2016-06-26)\n------------------\n* Support ``redis_cls`` parameter in ``REDIS_PARAMS`` setting.\n* Python 3.x compatibility fixed.\n* Added ``SCHEDULER_SERIALIZER`` setting.\n\n0.6.1 (2016-06-25)\n------------------\n* **Backwards incompatible change:** Require explicit ``DUPEFILTER_CLASS``\n  setting.\n* Added ``SCHEDULER_FLUSH_ON_START`` setting.\n* Added ``REDIS_START_URLS_AS_SET`` setting.\n* Added ``REDIS_ITEMS_KEY`` setting.\n* Added ``REDIS_ITEMS_SERIALIZER`` setting.\n* Added ``REDIS_PARAMS`` setting.\n* Added ``REDIS_START_URLS_BATCH_SIZE`` spider attribute to read start urls\n  in batches.\n* Added ``RedisCrawlSpider``.\n\n0.6.0 (2015-07-05)\n------------------\n* Updated code to be compatible with Scrapy 1.0.\n* Added `-a domain=...` option for example spiders.\n\n0.5.0 (2013-09-02)\n------------------\n* Added `REDIS_URL` setting to support Redis connection string.\n* Added `SCHEDULER_IDLE_BEFORE_CLOSE` setting to prevent the spider closing too\n  quickly when the queue is empty. Default value is zero keeping the previous\n  behavior.\n* Schedule preemptively requests on item scraped.\n* This version is the latest release compatible with Scrapy 0.24.x.\n\n0.4.0 (2013-04-19)\n------------------\n* Added `RedisSpider` and `RedisMixin` classes as building blocks for spiders\n  to be fed through a redis queue.\n* Added redis queue stats.\n* Let the encoder handle the item as it comes instead converting it to a dict.\n\n0.3.0 (2013-02-18)\n------------------\n* Added support for different queue classes.\n* Changed requests serialization from `marshal` to `cPickle`.\n\n0.2.0 (2013-02-17)\n------------------\n* Improved backward compatibility.\n* Added example project.\n\n0.1.0 (2011-09-01)\n------------------\n* First release on PyPI.\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis-0.6.8.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis-0.6.8.dist-info/METADATA",
    "content": "Metadata-Version: 2.0\nName: scrapy-redis\nVersion: 0.6.8\nSummary: Redis-based components for Scrapy.\nHome-page: https://github.com/rolando/scrapy-redis\nAuthor: Rolando Espinoza\nAuthor-email: rolando@rmax.io\nLicense: MIT\nKeywords: scrapy-redis\nPlatform: UNKNOWN\nClassifier: Development Status :: 4 - Beta\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: MIT License\nClassifier: Natural Language :: English\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nRequires-Dist: Scrapy (>=1.0)\nRequires-Dist: redis (>=2.10)\nRequires-Dist: six (>=1.5.2)\n\n============\nScrapy-Redis\n============\n\n.. image:: https://readthedocs.org/projects/scrapy-redis/badge/?version=latest\n        :target: https://readthedocs.org/projects/scrapy-redis/?badge=latest\n        :alt: Documentation Status\n\n.. image:: https://img.shields.io/pypi/v/scrapy-redis.svg\n        :target: https://pypi.python.org/pypi/scrapy-redis\n\n.. image:: https://img.shields.io/pypi/pyversions/scrapy-redis.svg\n        :target: https://pypi.python.org/pypi/scrapy-redis\n\n.. image:: https://img.shields.io/travis/rolando/scrapy-redis.svg\n        :target: https://travis-ci.org/rolando/scrapy-redis\n\n.. image:: https://codecov.io/github/rolando/scrapy-redis/coverage.svg?branch=master\n    :alt: Coverage Status\n    :target: https://codecov.io/github/rolando/scrapy-redis\n\n.. image:: https://landscape.io/github/rolando/scrapy-redis/master/landscape.svg?style=flat\n    :target: https://landscape.io/github/rolando/scrapy-redis/master\n    :alt: Code Quality Status\n\n.. image:: https://requires.io/github/rolando/scrapy-redis/requirements.svg?branch=master\n    :alt: Requirements Status\n    :target: https://requires.io/github/rolando/scrapy-redis/requirements/?branch=master\n\nRedis-based components for Scrapy.\n\n* Free software: MIT license\n* Documentation: https://scrapy-redis.readthedocs.org.\n* Python versions: 2.7, 3.4+\n\nFeatures\n--------\n\n* Distributed crawling/scraping\n\n    You can start multiple spider instances that share a single redis queue.\n    Best suitable for broad multi-domain crawls.\n\n* Distributed post-processing\n\n    Scraped items gets pushed into a redis queued meaning that you can start as\n    many as needed post-processing processes sharing the items queue.\n\n* Scrapy plug-and-play components\n\n    Scheduler + Duplication Filter, Item Pipeline, Base Spiders.\n\nRequirements\n------------\n\n* Python 2.7, 3.4 or 3.5\n* Redis >= 2.8\n* ``Scrapy`` >= 1.0\n* ``redis-py`` >= 2.10\n\nUsage\n-----\n\nUse the following settings in your project:\n\n.. code-block:: python\n\n  # Enables scheduling storing requests queue in redis.\n  SCHEDULER = \"scrapy_redis.scheduler.Scheduler\"\n\n  # Ensure all spiders share same duplicates filter through redis.\n  DUPEFILTER_CLASS = \"scrapy_redis.dupefilter.RFPDupeFilter\"\n\n  # Default requests serializer is pickle, but it can be changed to any module\n  # with loads and dumps functions. Note that pickle is not compatible between\n  # python versions.\n  # Caveat: In python 3.x, the serializer must return strings keys and support\n  # bytes as values. Because of this reason the json or msgpack module will not\n  # work by default. In python 2.x there is no such issue and you can use\n  # 'json' or 'msgpack' as serializers.\n  #SCHEDULER_SERIALIZER = \"scrapy_redis.picklecompat\"\n\n  # Don't cleanup redis queues, allows to pause/resume crawls.\n  #SCHEDULER_PERSIST = True\n\n  # Schedule requests using a priority queue. (default)\n  #SCHEDULER_QUEUE_CLASS = 'scrapy_redis.queue.PriorityQueue'\n\n  # Alternative queues.\n  #SCHEDULER_QUEUE_CLASS = 'scrapy_redis.queue.FifoQueue'\n  #SCHEDULER_QUEUE_CLASS = 'scrapy_redis.queue.LifoQueue'\n\n  # Max idle time to prevent the spider from being closed when distributed crawling.\n  # This only works if queue class is SpiderQueue or SpiderStack,\n  # and may also block the same time when your spider start at the first time (because the queue is empty).\n  #SCHEDULER_IDLE_BEFORE_CLOSE = 10\n\n  # Store scraped item in redis for post-processing.\n  ITEM_PIPELINES = {\n      'scrapy_redis.pipelines.RedisPipeline': 300\n  }\n\n  # The item pipeline serializes and stores the items in this redis key.\n  #REDIS_ITEMS_KEY = '%(spider)s:items'\n\n  # The items serializer is by default ScrapyJSONEncoder. You can use any\n  # importable path to a callable object.\n  #REDIS_ITEMS_SERIALIZER = 'json.dumps'\n\n  # Specify the host and port to use when connecting to Redis (optional).\n  #REDIS_HOST = 'localhost'\n  #REDIS_PORT = 6379\n\n  # Specify the full Redis URL for connecting (optional).\n  # If set, this takes precedence over the REDIS_HOST and REDIS_PORT settings.\n  #REDIS_URL = 'redis://user:pass@hostname:9001'\n\n  # Custom redis client parameters (i.e.: socket timeout, etc.)\n  #REDIS_PARAMS  = {}\n  # Use custom redis client class.\n  #REDIS_PARAMS['redis_cls'] = 'myproject.RedisClient'\n\n  # If True, it uses redis' ``spop`` operation. This could be useful if you\n  # want to avoid duplicates in your start urls list. In this cases, urls must\n  # be added via ``sadd`` command or you will get a type error from redis.\n  #REDIS_START_URLS_AS_SET = False\n\n  # Default start urls key for RedisSpider and RedisCrawlSpider.\n  #REDIS_START_URLS_KEY = '%(name)s:start_urls'\n\n  # Use other encoding than utf-8 for redis.\n  #REDIS_ENCODING = 'latin1'\n\n.. note::\n\n  Version 0.3 changed the requests serialization from `marshal` to `cPickle`,\n  therefore persisted requests using version 0.2 will not able to work on 0.3.\n\n\nRunning the example project\n---------------------------\n\nThis example illustrates how to share a spider's requests queue\nacross multiple spider instances, highly suitable for broad crawls.\n\n1. Setup scrapy_redis package in your PYTHONPATH\n\n2. Run the crawler for first time then stop it::\n\n    $ cd example-project\n    $ scrapy crawl dmoz\n    ... [dmoz] ...\n    ^C\n\n3. Run the crawler again to resume stopped crawling::\n\n    $ scrapy crawl dmoz\n    ... [dmoz] DEBUG: Resuming crawl (9019 requests scheduled)\n\n4. Start one or more additional scrapy crawlers::\n\n    $ scrapy crawl dmoz\n    ... [dmoz] DEBUG: Resuming crawl (8712 requests scheduled)\n\n5. Start one or more post-processing workers::\n\n    $ python process_items.py dmoz:items -v\n    ...\n    Processing: Kilani Giftware (http://www.dmoz.org/Computers/Shopping/Gifts/)\n    Processing: NinjaGizmos.com (http://www.dmoz.org/Computers/Shopping/Gifts/)\n    ...\n\n\nFeeding a Spider from Redis\n---------------------------\n\nThe class `scrapy_redis.spiders.RedisSpider` enables a spider to read the\nurls from redis. The urls in the redis queue will be processed one\nafter another, if the first request yields more requests, the spider\nwill process those requests before fetching another url from redis.\n\nFor example, create a file `myspider.py` with the code below:\n\n.. code-block:: python\n\n    from scrapy_redis.spiders import RedisSpider\n\n    class MySpider(RedisSpider):\n        name = 'myspider'\n\n        def parse(self, response):\n            # do stuff\n            pass\n\n\nThen:\n\n1. run the spider::\n\n    scrapy runspider myspider.py\n\n2. push urls to redis::\n\n    redis-cli lpush myspider:start_urls http://google.com\n\n\n.. note::\n\n    These spiders rely on the spider idle signal to fetch start urls, hence it\n    may have a few seconds of delay between the time you push a new url and the\n    spider starts crawling it.\n\n=======\nHistory\n=======\n\n\n0.6.8 (2017-02-14)\n------------------\n* Fixed automated release due to not matching registered email.\n\n0.6.7 (2016-12-27)\n------------------\n* Fixes bad formatting in logging message.\n\n0.6.6 (2016-12-20)\n------------------\n* Fixes wrong message on dupefilter duplicates.\n\n0.6.5 (2016-12-19)\n------------------\n* Fixed typo in default settings.\n\n\n0.6.4 (2016-12-18)\n------------------\n* Fixed data decoding in Python 3.x.\n* Added ``REDIS_ENCODING`` setting (default ``utf-8``).\n* Default to ``CONCURRENT_REQUESTS`` value for ``REDIS_START_URLS_BATCH_SIZE``.\n* Renamed queue classes to a proper naming conventiong (backwards compatible).\n\n0.6.3 (2016-07-03)\n------------------\n* Added ``REDIS_START_URLS_KEY`` setting.\n* Fixed spider method ``from_crawler`` signature.\n\n0.6.2 (2016-06-26)\n------------------\n* Support ``redis_cls`` parameter in ``REDIS_PARAMS`` setting.\n* Python 3.x compatibility fixed.\n* Added ``SCHEDULER_SERIALIZER`` setting.\n\n0.6.1 (2016-06-25)\n------------------\n* **Backwards incompatible change:** Require explicit ``DUPEFILTER_CLASS``\n  setting.\n* Added ``SCHEDULER_FLUSH_ON_START`` setting.\n* Added ``REDIS_START_URLS_AS_SET`` setting.\n* Added ``REDIS_ITEMS_KEY`` setting.\n* Added ``REDIS_ITEMS_SERIALIZER`` setting.\n* Added ``REDIS_PARAMS`` setting.\n* Added ``REDIS_START_URLS_BATCH_SIZE`` spider attribute to read start urls\n  in batches.\n* Added ``RedisCrawlSpider``.\n\n0.6.0 (2015-07-05)\n------------------\n* Updated code to be compatible with Scrapy 1.0.\n* Added `-a domain=...` option for example spiders.\n\n0.5.0 (2013-09-02)\n------------------\n* Added `REDIS_URL` setting to support Redis connection string.\n* Added `SCHEDULER_IDLE_BEFORE_CLOSE` setting to prevent the spider closing too\n  quickly when the queue is empty. Default value is zero keeping the previous\n  behavior.\n* Schedule preemptively requests on item scraped.\n* This version is the latest release compatible with Scrapy 0.24.x.\n\n0.4.0 (2013-04-19)\n------------------\n* Added `RedisSpider` and `RedisMixin` classes as building blocks for spiders\n  to be fed through a redis queue.\n* Added redis queue stats.\n* Let the encoder handle the item as it comes instead converting it to a dict.\n\n0.3.0 (2013-02-18)\n------------------\n* Added support for different queue classes.\n* Changed requests serialization from `marshal` to `cPickle`.\n\n0.2.0 (2013-02-17)\n------------------\n* Improved backward compatibility.\n* Added example project.\n\n0.1.0 (2011-09-01)\n------------------\n* First release on PyPI.\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis-0.6.8.dist-info/RECORD",
    "content": "scrapy_redis-0.6.8.dist-info/DESCRIPTION.rst,sha256=zgZOZynUZpnCItcHRgDLRHcBrun0R6qDEAWbJU3vSzc,9285\r\nscrapy_redis-0.6.8.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nscrapy_redis-0.6.8.dist-info/METADATA,sha256=5lVxJDTdtQ6WYAHpF5FNmMik2MeV9H1NQ4_tPDd3_VM,10059\r\nscrapy_redis-0.6.8.dist-info/RECORD,,\r\nscrapy_redis-0.6.8.dist-info/WHEEL,sha256=o2k-Qa-RMNIJmUdIc7KU6VWR_ErNRbWNlxDIpl7lm34,110\r\nscrapy_redis-0.6.8.dist-info/metadata.json,sha256=gC10AU7gcov6IeYyYNgmkkSbS49CdZZPiAYc2DEz4oQ,915\r\nscrapy_redis-0.6.8.dist-info/top_level.txt,sha256=Sz48Fwtrrort4ebSUHT7u3etgn_Iox3gmWv_D-unNd4,13\r\nscrapy_redis/__init__.py,sha256=YxuAmBUho0fn46cQjU1UBiAaSn9uM4mRqq3LR2TM910,193\r\nscrapy_redis/__pycache__/__init__.cpython-36.pyc,,\r\nscrapy_redis/__pycache__/connection.cpython-36.pyc,,\r\nscrapy_redis/__pycache__/defaults.cpython-36.pyc,,\r\nscrapy_redis/__pycache__/dupefilter.cpython-36.pyc,,\r\nscrapy_redis/__pycache__/picklecompat.cpython-36.pyc,,\r\nscrapy_redis/__pycache__/pipelines.cpython-36.pyc,,\r\nscrapy_redis/__pycache__/queue.cpython-36.pyc,,\r\nscrapy_redis/__pycache__/scheduler.cpython-36.pyc,,\r\nscrapy_redis/__pycache__/spiders.cpython-36.pyc,,\r\nscrapy_redis/__pycache__/utils.cpython-36.pyc,,\r\nscrapy_redis/connection.py,sha256=rEqkwwSBNrC4r7Zn8-UTUZlEF06LWp-WK0qqS7Gmi8Y,2307\r\nscrapy_redis/defaults.py,sha256=uKPK8b1E-enicYgfJXB8E27yNN7xid5WzXDO9OvAWUo,631\r\nscrapy_redis/dupefilter.py,sha256=pGfaR_VibSrkZJblivru5NXddIzdNoFOrFERW21RHGU,3992\r\nscrapy_redis/picklecompat.py,sha256=yny-2gjbzFyU8O2g4yVQ1_NP9kRP_2DZ2tdfWJcgi30,242\r\nscrapy_redis/pipelines.py,sha256=feyTU15Xm1Y5QYvyaAIEcdu2OBNvwRfB9A9ZKZu9wOI,2083\r\nscrapy_redis/queue.py,sha256=XJEFCEpNNjOQF4uuWeRGSluK9JD-bJWGtNUK4QVpqyE,4419\r\nscrapy_redis/scheduler.py,sha256=oJfxn9XERedaq7D-EozRUnKGHP3Nx8m9DQzOWhPtCSw,6110\r\nscrapy_redis/spiders.py,sha256=XYLRTza5hHJxGoPOPEegukXyFCr1AZID7YNJuGhOU_o,6835\r\nscrapy_redis/utils.py,sha256=VilhHKbMSn3c7ZO429NlnvMKN_aefK84ooG84f5BA8U,192\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis-0.6.8.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.29.0)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis-0.6.8.dist-info/metadata.json",
    "content": "{\"classifiers\": [\"Development Status :: 4 - Beta\", \"Intended Audience :: Developers\", \"License :: OSI Approved :: MIT License\", \"Natural Language :: English\", \"Programming Language :: Python :: 2\", \"Programming Language :: Python :: 2.7\", \"Programming Language :: Python :: 3\", \"Programming Language :: Python :: 3.4\", \"Programming Language :: Python :: 3.5\"], \"extensions\": {\"python.details\": {\"contacts\": [{\"email\": \"rolando@rmax.io\", \"name\": \"Rolando Espinoza\", \"role\": \"author\"}], \"document_names\": {\"description\": \"DESCRIPTION.rst\"}, \"project_urls\": {\"Home\": \"https://github.com/rolando/scrapy-redis\"}}}, \"extras\": [], \"generator\": \"bdist_wheel (0.29.0)\", \"keywords\": [\"scrapy-redis\"], \"license\": \"MIT\", \"metadata_version\": \"2.0\", \"name\": \"scrapy-redis\", \"run_requires\": [{\"requires\": [\"Scrapy (>=1.0)\", \"redis (>=2.10)\", \"six (>=1.5.2)\"]}], \"summary\": \"Redis-based components for Scrapy.\", \"version\": \"0.6.8\"}"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/scrapy_redis-0.6.8.dist-info/top_level.txt",
    "content": "scrapy_redis\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/service_identity/__init__.py",
    "content": "\"\"\"\nVerify service identities.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom . import cryptography, pyopenssl\nfrom .exceptions import (\n    CertificateError,\n    SubjectAltNameWarning,\n    VerificationError,\n)\n\n\n__version__ = \"18.1.0\"\n\n__title__ = \"service_identity\"\n__description__ = \"Service identity verification for pyOpenSSL & cryptography.\"\n__uri__ = \"https://service-identity.readthedocs.io/\"\n\n__author__ = \"Hynek Schlawack\"\n__email__ = \"hs@ox.cx\"\n\n__license__ = \"MIT\"\n__copyright__ = \"Copyright (c) 2014 Hynek Schlawack\"\n\n\n__all__ = [\n    \"CertificateError\",\n    \"SubjectAltNameWarning\",\n    \"VerificationError\",\n    \"cryptography\",\n    \"pyopenssl\",\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/service_identity/_common.py",
    "content": "\"\"\"\nCommon verification code.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nimport ipaddress\nimport re\n\nimport attr\n\nfrom ._compat import maketrans, text_type\nfrom .exceptions import (\n    CertificateError,\n    DNSMismatch,\n    IPAddressMismatch,\n    SRVMismatch,\n    URIMismatch,\n    VerificationError,\n)\n\n\ntry:\n    import idna\nexcept ImportError:  # pragma: nocover\n    idna = None\n\n\n@attr.s(slots=True)\nclass ServiceMatch(object):\n    \"\"\"\n    A match of a service id and a certificate pattern.\n    \"\"\"\n\n    service_id = attr.ib()\n    cert_pattern = attr.ib()\n\n\ndef verify_service_identity(cert_patterns, obligatory_ids, optional_ids):\n    \"\"\"\n    Verify whether *cert_patterns* are valid for *obligatory_ids* and\n    *optional_ids*.\n\n    *obligatory_ids* must be both present and match.  *optional_ids* must match\n    if a pattern of the respective type is present.\n    \"\"\"\n    errors = []\n    matches = _find_matches(cert_patterns, obligatory_ids) + _find_matches(\n        cert_patterns, optional_ids\n    )\n\n    matched_ids = [match.service_id for match in matches]\n    for i in obligatory_ids:\n        if i not in matched_ids:\n            errors.append(i.error_on_mismatch(mismatched_id=i))\n\n    for i in optional_ids:\n        # If an optional ID is not matched by a certificate pattern *but* there\n        # is a pattern of the same type , it is an error and the verification\n        # fails.  Example: the user passes a SRV-ID for \"_mail.domain.com\" but\n        # the certificate contains an SRV-Pattern for \"_xmpp.domain.com\".\n        if i not in matched_ids and _contains_instance_of(\n            cert_patterns, i.pattern_class\n        ):\n            errors.append(i.error_on_mismatch(mismatched_id=i))\n\n    if errors:\n        raise VerificationError(errors=errors)\n\n    return matches\n\n\ndef _find_matches(cert_patterns, service_ids):\n    \"\"\"\n    Search for matching certificate patterns and service_ids.\n\n    :param cert_ids: List certificate IDs like DNSPattern.\n    :type cert_ids: `list`\n\n    :param service_ids: List of service IDs like DNS_ID.\n    :type service_ids: `list`\n\n    :rtype: `list` of `ServiceMatch`\n    \"\"\"\n    matches = []\n    for sid in service_ids:\n        for cid in cert_patterns:\n            if sid.verify(cid):\n                matches.append(ServiceMatch(cert_pattern=cid, service_id=sid))\n    return matches\n\n\ndef _contains_instance_of(seq, cl):\n    \"\"\"\n    :type seq: iterable\n    :type cl: type\n\n    :rtype: bool\n    \"\"\"\n    for e in seq:\n        if isinstance(e, cl):\n            return True\n    return False\n\n\ndef _is_ip_address(pattern):\n    \"\"\"\n    Check whether *pattern* could be/match an IP address.\n\n    :param pattern: A pattern for a host name.\n    :type pattern: `bytes` or `unicode`\n\n    :return: `True` if *pattern* could be an IP address, else `False`.\n    :rtype: bool\n    \"\"\"\n    if isinstance(pattern, bytes):\n        try:\n            pattern = pattern.decode(\"ascii\")\n        except UnicodeError:\n            return False\n\n    try:\n        int(pattern)\n        return True\n    except ValueError:\n        pass\n\n    try:\n        ipaddress.ip_address(pattern.replace(\"*\", \"1\"))\n    except ValueError:\n        return False\n\n    return True\n\n\n@attr.s(init=False, slots=True)\nclass DNSPattern(object):\n    \"\"\"\n    A DNS pattern as extracted from certificates.\n    \"\"\"\n\n    pattern = attr.ib()\n\n    _RE_LEGAL_CHARS = re.compile(br\"^[a-z0-9\\-_.]+$\")\n\n    def __init__(self, pattern):\n        \"\"\"\n        :type pattern: `bytes`\n        \"\"\"\n        if not isinstance(pattern, bytes):\n            raise TypeError(\"The DNS pattern must be a bytes string.\")\n\n        pattern = pattern.strip()\n\n        if pattern == b\"\" or _is_ip_address(pattern) or b\"\\0\" in pattern:\n            raise CertificateError(\n                \"Invalid DNS pattern {0!r}.\".format(pattern)\n            )\n\n        self.pattern = pattern.translate(_TRANS_TO_LOWER)\n        if b\"*\" in self.pattern:\n            _validate_pattern(self.pattern)\n\n\n@attr.s(slots=True)\nclass IPAddressPattern(object):\n    \"\"\"\n    An IP address pattern as extracted from certificates.\n    \"\"\"\n\n    pattern = attr.ib()\n\n    @classmethod\n    def from_bytes(cls, bs):\n        try:\n            return cls(pattern=ipaddress.ip_address(bs))\n        except ValueError:\n            raise CertificateError(\n                \"Invalid IP address pattern {!r}.\".format(bs)\n            )\n\n\n@attr.s(init=False, slots=True)\nclass URIPattern(object):\n    \"\"\"\n    An URI pattern as extracted from certificates.\n    \"\"\"\n\n    protocol_pattern = attr.ib()\n    dns_pattern = attr.ib()\n\n    def __init__(self, pattern):\n        \"\"\"\n        :type pattern: `bytes`\n        \"\"\"\n        if not isinstance(pattern, bytes):\n            raise TypeError(\"The URI pattern must be a bytes string.\")\n\n        pattern = pattern.strip().translate(_TRANS_TO_LOWER)\n\n        if b\":\" not in pattern or b\"*\" in pattern or _is_ip_address(pattern):\n            raise CertificateError(\n                \"Invalid URI pattern {0!r}.\".format(pattern)\n            )\n        self.protocol_pattern, hostname = pattern.split(b\":\")\n        self.dns_pattern = DNSPattern(hostname)\n\n\n@attr.s(init=False, slots=True)\nclass SRVPattern(object):\n    \"\"\"\n    An SRV pattern as extracted from certificates.\n    \"\"\"\n\n    name_pattern = attr.ib()\n    dns_pattern = attr.ib()\n\n    def __init__(self, pattern):\n        \"\"\"\n        :type pattern: `bytes`\n        \"\"\"\n        if not isinstance(pattern, bytes):\n            raise TypeError(\"The SRV pattern must be a bytes string.\")\n\n        pattern = pattern.strip().translate(_TRANS_TO_LOWER)\n\n        if (\n            pattern[0] != b\"_\"[0]\n            or b\".\" not in pattern\n            or b\"*\" in pattern\n            or _is_ip_address(pattern)\n        ):\n            raise CertificateError(\n                \"Invalid SRV pattern {0!r}.\".format(pattern)\n            )\n        name, hostname = pattern.split(b\".\", 1)\n        self.name_pattern = name[1:]\n        self.dns_pattern = DNSPattern(hostname)\n\n\n@attr.s(init=False, slots=True)\nclass DNS_ID(object):\n    \"\"\"\n    A DNS service ID, aka hostname.\n    \"\"\"\n\n    hostname = attr.ib()\n\n    # characters that are legal in a normalized hostname\n    _RE_LEGAL_CHARS = re.compile(br\"^[a-z0-9\\-_.]+$\")\n    pattern_class = DNSPattern\n    error_on_mismatch = DNSMismatch\n\n    def __init__(self, hostname):\n        \"\"\"\n        :type hostname: `unicode`\n        \"\"\"\n        if not isinstance(hostname, text_type):\n            raise TypeError(\"DNS-ID must be a unicode string.\")\n\n        hostname = hostname.strip()\n        if hostname == u\"\" or _is_ip_address(hostname):\n            raise ValueError(\"Invalid DNS-ID.\")\n\n        if any(ord(c) > 127 for c in hostname):\n            if idna:\n                ascii_id = idna.encode(hostname)\n            else:\n                raise ImportError(\n                    \"idna library is required for non-ASCII IDs.\"\n                )\n        else:\n            ascii_id = hostname.encode(\"ascii\")\n\n        self.hostname = ascii_id.translate(_TRANS_TO_LOWER)\n        if self._RE_LEGAL_CHARS.match(self.hostname) is None:\n            raise ValueError(\"Invalid DNS-ID.\")\n\n    def verify(self, pattern):\n        \"\"\"\n        https://tools.ietf.org/search/rfc6125#section-6.4\n        \"\"\"\n        if isinstance(pattern, self.pattern_class):\n            return _hostname_matches(pattern.pattern, self.hostname)\n        else:\n            return False\n\n\n@attr.s(slots=True)\nclass IPAddress_ID(object):\n    \"\"\"\n    An IP address service ID.\n    \"\"\"\n\n    ip = attr.ib(converter=ipaddress.ip_address)\n\n    pattern_class = IPAddressPattern\n    error_on_mismatch = IPAddressMismatch\n\n    def verify(self, pattern):\n        \"\"\"\n        https://tools.ietf.org/search/rfc2818#section-3.1\n        \"\"\"\n        return self.ip == pattern.pattern\n\n\n@attr.s(init=False, slots=True)\nclass URI_ID(object):\n    \"\"\"\n    An URI service ID.\n    \"\"\"\n\n    protocol = attr.ib()\n    dns_id = attr.ib()\n\n    pattern_class = URIPattern\n    error_on_mismatch = URIMismatch\n\n    def __init__(self, uri):\n        \"\"\"\n        :type uri: `unicode`\n        \"\"\"\n        if not isinstance(uri, text_type):\n            raise TypeError(\"URI-ID must be a unicode string.\")\n\n        uri = uri.strip()\n        if u\":\" not in uri or _is_ip_address(uri):\n            raise ValueError(\"Invalid URI-ID.\")\n\n        prot, hostname = uri.split(u\":\")\n\n        self.protocol = prot.encode(\"ascii\").translate(_TRANS_TO_LOWER)\n        self.dns_id = DNS_ID(hostname.strip(u\"/\"))\n\n    def verify(self, pattern):\n        \"\"\"\n        https://tools.ietf.org/search/rfc6125#section-6.5.2\n        \"\"\"\n        if isinstance(pattern, self.pattern_class):\n            return (\n                pattern.protocol_pattern == self.protocol\n                and self.dns_id.verify(pattern.dns_pattern)\n            )\n        else:\n            return False\n\n\n@attr.s(init=False, slots=True)\nclass SRV_ID(object):\n    \"\"\"\n    An SRV service ID.\n    \"\"\"\n\n    name = attr.ib()\n    dns_id = attr.ib()\n\n    pattern_class = SRVPattern\n    error_on_mismatch = SRVMismatch\n\n    def __init__(self, srv):\n        \"\"\"\n        :type srv: `unicode`\n        \"\"\"\n        if not isinstance(srv, text_type):\n            raise TypeError(\"SRV-ID must be a unicode string.\")\n\n        srv = srv.strip()\n        if u\".\" not in srv or _is_ip_address(srv) or srv[0] != u\"_\":\n            raise ValueError(\"Invalid SRV-ID.\")\n\n        name, hostname = srv.split(u\".\", 1)\n\n        self.name = name[1:].encode(\"ascii\").translate(_TRANS_TO_LOWER)\n        self.dns_id = DNS_ID(hostname)\n\n    def verify(self, pattern):\n        \"\"\"\n        https://tools.ietf.org/search/rfc6125#section-6.5.1\n        \"\"\"\n        if isinstance(pattern, self.pattern_class):\n            return self.name == pattern.name_pattern and self.dns_id.verify(\n                pattern.dns_pattern\n            )\n        else:\n            return False\n\n\ndef _hostname_matches(cert_pattern, actual_hostname):\n    \"\"\"\n    :type cert_pattern: `bytes`\n    :type actual_hostname: `bytes`\n\n    :return: `True` if *cert_pattern* matches *actual_hostname*, else `False`.\n    :rtype: `bool`\n    \"\"\"\n    if b\"*\" in cert_pattern:\n        cert_head, cert_tail = cert_pattern.split(b\".\", 1)\n        actual_head, actual_tail = actual_hostname.split(b\".\", 1)\n        if cert_tail != actual_tail:\n            return False\n        # No patterns for IDNA\n        if actual_head.startswith(b\"xn--\"):\n            return False\n\n        return cert_head == b\"*\" or cert_head == actual_head\n    else:\n        return cert_pattern == actual_hostname\n\n\ndef _validate_pattern(cert_pattern):\n    \"\"\"\n    Check whether the usage of wildcards within *cert_pattern* conforms with\n    our expectations.\n\n    :type hostname: `bytes`\n\n    :return: None\n    \"\"\"\n    cnt = cert_pattern.count(b\"*\")\n    if cnt > 1:\n        raise CertificateError(\n            \"Certificate's DNS-ID {0!r} contains too many wildcards.\".format(\n                cert_pattern\n            )\n        )\n    parts = cert_pattern.split(b\".\")\n    if len(parts) < 3:\n        raise CertificateError(\n            \"Certificate's DNS-ID {0!r} has too few host components for \"\n            \"wildcard usage.\".format(cert_pattern)\n        )\n    # We assume there will always be only one wildcard allowed.\n    if b\"*\" not in parts[0]:\n        raise CertificateError(\n            \"Certificate's DNS-ID {0!r} has a wildcard outside the left-most \"\n            \"part.\".format(cert_pattern)\n        )\n    if any(not len(p) for p in parts):\n        raise CertificateError(\n            \"Certificate's DNS-ID {0!r} contains empty parts.\".format(\n                cert_pattern\n            )\n        )\n\n\n# Ensure no locale magic interferes.\n_TRANS_TO_LOWER = maketrans(\n    b\"ABCDEFGHIJKLMNOPQRSTUVWXYZ\", b\"abcdefghijklmnopqrstuvwxyz\"\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/service_identity/_compat.py",
    "content": "\"\"\"\nAvoid depending on any particular Python 3 compatibility approach.\n\"\"\"\n\nimport sys\n\n\nPY3 = sys.version_info[0] == 3\nif PY3:  # pragma: nocover\n    maketrans = bytes.maketrans\n    text_type = str\nelse:  # pragma: nocover\n    import string\n\n    maketrans = string.maketrans\n    text_type = unicode  # noqa\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/service_identity/cryptography.py",
    "content": "\"\"\"\n`cryptography.x509 <https://github.com/pyca/cryptography>`_-specific code.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nimport warnings\n\nfrom cryptography.x509 import (\n    DNSName,\n    ExtensionOID,\n    IPAddress,\n    NameOID,\n    ObjectIdentifier,\n    OtherName,\n    UniformResourceIdentifier,\n)\nfrom cryptography.x509.extensions import ExtensionNotFound\nfrom pyasn1.codec.der.decoder import decode\nfrom pyasn1.type.char import IA5String\n\nfrom ._common import (\n    DNS_ID,\n    CertificateError,\n    DNSPattern,\n    IPAddress_ID,\n    IPAddressPattern,\n    SRVPattern,\n    URIPattern,\n    verify_service_identity,\n)\nfrom .exceptions import SubjectAltNameWarning\n\n\n__all__ = [\"verify_certificate_hostname\"]\n\n\ndef verify_certificate_hostname(certificate, hostname):\n    \"\"\"\n    Verify whether *certificate* is valid for *hostname*.\n\n    .. note:: Nothing is verified about the *authority* of the certificate;\n       the caller must verify that the certificate chains to an appropriate\n       trust root themselves.\n\n    :param cryptography.x509.Certificate certificate: A cryptography X509\n        certificate object.\n    :param unicode hostname: The hostname that *certificate* should be valid\n        for.\n\n    :raises service_identity.VerificationError: If *certificate* is not valid\n        for *hostname*.\n    :raises service_identity.CertificateError: If *certificate* contains\n        invalid/unexpected data.\n\n    :returns: ``None``\n    \"\"\"\n    verify_service_identity(\n        cert_patterns=extract_ids(certificate),\n        obligatory_ids=[DNS_ID(hostname)],\n        optional_ids=[],\n    )\n\n\ndef verify_certificate_ip_address(certificate, ip_address):\n    \"\"\"\n    Verify whether *certificate* is valid for *ip_address*.\n\n    .. note:: Nothing is verified about the *authority* of the certificate;\n       the caller must verify that the certificate chains to an appropriate\n       trust root themselves.\n\n    :param cryptography.x509.Certificate certificate: A cryptography X509\n        certificate object.\n    :param unicode ip_address: The IP address that *connection* should be valid\n        for.  Can be an IPv4 or IPv6 address.\n\n    :raises service_identity.VerificationError: If *certificate* is not valid\n        for *ip_address*.\n    :raises service_identity.CertificateError: If *certificate* contains\n        invalid/unexpected data.\n\n    :returns: ``None``\n\n    .. versionadded:: 18.1.0\n    \"\"\"\n    verify_service_identity(\n        cert_patterns=extract_ids(certificate),\n        obligatory_ids=[IPAddress_ID(ip_address)],\n        optional_ids=[],\n    )\n\n\nID_ON_DNS_SRV = ObjectIdentifier(\"1.3.6.1.5.5.7.8.7\")  # id_on_dnsSRV\n\n\ndef extract_ids(cert):\n    \"\"\"\n    Extract all valid IDs from a certificate for service verification.\n\n    If *cert* doesn't contain any identifiers, the ``CN``s are used as DNS-IDs\n    as fallback.\n\n    :param cryptography.x509.Certificate cert: The certificate to be dissected.\n\n    :return: List of IDs.\n    \"\"\"\n    ids = []\n    try:\n        ext = cert.extensions.get_extension_for_oid(\n            ExtensionOID.SUBJECT_ALTERNATIVE_NAME\n        )\n    except ExtensionNotFound:\n        pass\n    else:\n        ids.extend(\n            [\n                DNSPattern(name.encode(\"utf-8\"))\n                for name in ext.value.get_values_for_type(DNSName)\n            ]\n        )\n        ids.extend(\n            [\n                URIPattern(uri.encode(\"utf-8\"))\n                for uri in ext.value.get_values_for_type(\n                    UniformResourceIdentifier\n                )\n            ]\n        )\n        ids.extend(\n            [\n                IPAddressPattern(ip)\n                for ip in ext.value.get_values_for_type(IPAddress)\n            ]\n        )\n        for other in ext.value.get_values_for_type(OtherName):\n            if other.type_id == ID_ON_DNS_SRV:\n                srv, _ = decode(other.value)\n                if isinstance(srv, IA5String):\n                    ids.append(SRVPattern(srv.asOctets()))\n                else:  # pragma: nocover\n                    raise CertificateError(\"Unexpected certificate content.\")\n\n    if not ids:\n        # https://tools.ietf.org/search/rfc6125#section-6.4.4\n        # A client MUST NOT seek a match for a reference identifier of CN-ID if\n        # the presented identifiers include a DNS-ID, SRV-ID, URI-ID, or any\n        # application-specific identifier types supported by the client.\n        cns = [\n            n.value\n            for n in cert.subject.get_attributes_for_oid(NameOID.COMMON_NAME)\n        ]\n        cn = next(iter(cns), b\"<not given>\")\n        ids = [DNSPattern(n.encode(\"utf-8\")) for n in cns]\n        warnings.warn(\n            \"Certificate with CN {!r} has no `subjectAltName`, falling back \"\n            \"to check for a `commonName` for now.  This feature is being \"\n            \"removed by major browsers and deprecated by RFC 2818.\".format(cn),\n            SubjectAltNameWarning,\n        )\n    return ids\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/service_identity/exceptions.py",
    "content": "\"\"\"\nAll exceptions and warnings thrown by ``service_identity``.\n\nSeparated into an own package for nicer tracebacks, you should still import\nthem from __init__.py.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nimport attr\n\n\nclass SubjectAltNameWarning(DeprecationWarning):\n    \"\"\"\n    Server Certificate does not contain a ``SubjectAltName``.\n\n    Hostname matching is performed on the ``CommonName`` which is deprecated.\n    \"\"\"\n\n\n@attr.s\nclass VerificationError(Exception):\n    \"\"\"\n    Service identity verification failed.\n    \"\"\"\n\n    errors = attr.ib()\n\n    def __str__(self):\n        return self.__repr__()\n\n\n@attr.s\nclass DNSMismatch(object):\n    \"\"\"\n    No matching DNSPattern could be found.\n    \"\"\"\n\n    mismatched_id = attr.ib()\n\n\n@attr.s\nclass SRVMismatch(object):\n    \"\"\"\n    No matching SRVPattern could be found.\n    \"\"\"\n\n    mismatched_id = attr.ib()\n\n\n@attr.s\nclass URIMismatch(object):\n    \"\"\"\n    No matching URIPattern could be found.\n    \"\"\"\n\n    mismatched_id = attr.ib()\n\n\n@attr.s\nclass IPAddressMismatch(object):\n    \"\"\"\n    No matching IPAddressPattern could be found.\n    \"\"\"\n\n    mismatched_id = attr.ib()\n\n\nclass CertificateError(Exception):\n    \"\"\"\n    Certificate contains invalid or unexpected data.\n    \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/service_identity/pyopenssl.py",
    "content": "\"\"\"\n`pyOpenSSL <https://github.com/pyca/pyopenssl>`_-specific code.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nimport warnings\n\nimport six\n\nfrom pyasn1.codec.der.decoder import decode\nfrom pyasn1.type.char import IA5String\nfrom pyasn1.type.univ import ObjectIdentifier\nfrom pyasn1_modules.rfc2459 import GeneralNames\n\nfrom ._common import (\n    DNS_ID,\n    CertificateError,\n    DNSPattern,\n    IPAddress_ID,\n    IPAddressPattern,\n    SRVPattern,\n    URIPattern,\n    verify_service_identity,\n)\nfrom .exceptions import SubjectAltNameWarning\n\n\n__all__ = [\"verify_hostname\"]\n\n\ndef verify_hostname(connection, hostname):\n    \"\"\"\n    Verify whether the certificate of *connection* is valid for *hostname*.\n\n    :param OpenSSL.SSL.Connection connection: A pyOpenSSL connection object.\n    :param unicode hostname: The hostname that *connection* should be connected\n        to.\n\n    :raises service_identity.VerificationError: If *connection* does not\n        provide a certificate that is valid for *hostname*.\n    :raises service_identity.CertificateError: If the certificate chain of\n        *connection* contains a certificate that contains invalid/unexpected\n        data.\n\n    :returns: ``None``\n    \"\"\"\n    verify_service_identity(\n        cert_patterns=extract_ids(connection.get_peer_certificate()),\n        obligatory_ids=[DNS_ID(hostname)],\n        optional_ids=[],\n    )\n\n\ndef verify_ip_address(connection, ip_address):\n    \"\"\"\n    Verify whether the certificate of *connection* is valid for *ip_address*.\n\n    :param OpenSSL.SSL.Connection connection: A pyOpenSSL connection object.\n    :param unicode ip_address: The IP address that *connection* should be\n        connected to.  Can be an IPv4 or IPv6 address.\n\n    :raises service_identity.VerificationError: If *connection* does not\n        provide a certificate that is valid for *ip_address*.\n    :raises service_identity.CertificateError: If the certificate chain of\n        *connection* contains a certificate that contains invalid/unexpected\n        data.\n\n    :returns: ``None``\n\n    .. versionadded:: 18.1.0\n    \"\"\"\n    verify_service_identity(\n        cert_patterns=extract_ids(connection.get_peer_certificate()),\n        obligatory_ids=[IPAddress_ID(ip_address)],\n        optional_ids=[],\n    )\n\n\nID_ON_DNS_SRV = ObjectIdentifier(\"1.3.6.1.5.5.7.8.7\")  # id_on_dnsSRV\n\n\ndef extract_ids(cert):\n    \"\"\"\n    Extract all valid IDs from a certificate for service verification.\n\n    If *cert* doesn't contain any identifiers, the ``CN``s are used as DNS-IDs\n    as fallback.\n\n    :param OpenSSL.SSL.X509 cert: The certificate to be dissected.\n\n    :return: List of IDs.\n    \"\"\"\n    ids = []\n    for i in six.moves.range(cert.get_extension_count()):\n        ext = cert.get_extension(i)\n        if ext.get_short_name() == b\"subjectAltName\":\n            names, _ = decode(ext.get_data(), asn1Spec=GeneralNames())\n            for n in names:\n                name_string = n.getName()\n                if name_string == \"dNSName\":\n                    ids.append(DNSPattern(n.getComponent().asOctets()))\n                elif name_string == \"iPAddress\":\n                    ids.append(\n                        IPAddressPattern.from_bytes(\n                            n.getComponent().asOctets()\n                        )\n                    )\n                elif name_string == \"uniformResourceIdentifier\":\n                    ids.append(URIPattern(n.getComponent().asOctets()))\n                elif name_string == \"otherName\":\n                    comp = n.getComponent()\n                    oid = comp.getComponentByPosition(0)\n                    if oid == ID_ON_DNS_SRV:\n                        srv, _ = decode(comp.getComponentByPosition(1))\n                        if isinstance(srv, IA5String):\n                            ids.append(SRVPattern(srv.asOctets()))\n                        else:  # pragma: nocover\n                            raise CertificateError(\n                                \"Unexpected certificate content.\"\n                            )\n                    else:  # pragma: nocover\n                        pass\n                else:  # pragma: nocover\n                    pass\n\n    if not ids:\n        # https://tools.ietf.org/search/rfc6125#section-6.4.4\n        # A client MUST NOT seek a match for a reference identifier of CN-ID if\n        # the presented identifiers include a DNS-ID, SRV-ID, URI-ID, or any\n        # application-specific identifier types supported by the client.\n        components = [\n            c[1] for c in cert.get_subject().get_components() if c[0] == b\"CN\"\n        ]\n        cn = next(iter(components), b\"<not given>\")\n        ids = [DNSPattern(c) for c in components]\n        warnings.warn(\n            \"Certificate with CN '%s' has no `subjectAltName`, falling back \"\n            \"to check for a `commonName` for now.  This feature is being \"\n            \"removed by major browsers and deprecated by RFC 2818.  \"\n            \"service_identity will remove the support for it in mid-2018.\"\n            % (cn.decode(\"utf-8\"),),\n            SubjectAltNameWarning,\n            stacklevel=2,\n        )\n    return ids\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/service_identity-18.1.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/service_identity-18.1.0.dist-info/LICENSE",
    "content": "Copyright (c) 2014 Hynek Schlawack\n\nPermission is hereby granted, free of charge, to any person obtaining a copy of\nthis software and associated documentation files (the \"Software\"), to deal in\nthe Software without restriction, including without limitation the rights to\nuse, copy, modify, merge, publish, distribute, sublicense, and/or sell copies\nof the Software, and to permit persons to whom the Software is furnished to do\nso, subject to the following conditions:\n\nThe above copyright notice and this permission notice shall be included in all\ncopies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\nIMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\nFITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\nAUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\nLIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\nOUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\nSOFTWARE.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/service_identity-18.1.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: service-identity\nVersion: 18.1.0\nSummary: Service identity verification for pyOpenSSL & cryptography.\nHome-page: https://service-identity.readthedocs.io/\nAuthor: Hynek Schlawack\nAuthor-email: hs@ox.cx\nMaintainer: Hynek Schlawack\nMaintainer-email: hs@ox.cx\nLicense: MIT\nKeywords: cryptography,openssl,pyopenssl\nPlatform: UNKNOWN\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: MIT License\nClassifier: Natural Language :: English\nClassifier: Operating System :: MacOS :: MacOS X\nClassifier: Operating System :: Microsoft :: Windows\nClassifier: Operating System :: POSIX :: BSD\nClassifier: Operating System :: POSIX :: Linux\nClassifier: Operating System :: POSIX\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 2.7\nClassifier: Programming Language :: Python :: 3\nClassifier: Programming Language :: Python :: 3.4\nClassifier: Programming Language :: Python :: 3.5\nClassifier: Programming Language :: Python :: 3.6\nClassifier: Programming Language :: Python :: 3.7\nClassifier: Programming Language :: Python :: Implementation :: CPython\nClassifier: Programming Language :: Python :: Implementation :: PyPy\nClassifier: Programming Language :: Python\nClassifier: Topic :: Security :: Cryptography\nClassifier: Topic :: Software Development :: Libraries :: Python Modules\nRequires-Dist: attrs (>=16.0.0)\nRequires-Dist: pyasn1-modules\nRequires-Dist: pyasn1\nRequires-Dist: cryptography\nRequires-Dist: ipaddress ; python_version < \"3.3\"\nProvides-Extra: dev\nRequires-Dist: coverage (>=4.2.0) ; extra == 'dev'\nRequires-Dist: pytest ; extra == 'dev'\nRequires-Dist: sphinx ; extra == 'dev'\nRequires-Dist: idna ; extra == 'dev'\nRequires-Dist: pyOpenSSL ; extra == 'dev'\nProvides-Extra: docs\nRequires-Dist: sphinx ; extra == 'docs'\nProvides-Extra: idna\nRequires-Dist: idna ; extra == 'idna'\nProvides-Extra: tests\nRequires-Dist: coverage (>=4.2.0) ; extra == 'tests'\nRequires-Dist: pytest ; extra == 'tests'\n\n=============================\nService Identity Verification\n=============================\n\n.. image:: https://readthedocs.org/projects/service-identity/badge/?version=stable\n   :target: https://service-identity.readthedocs.io/en/stable/?badge=stable\n   :alt: Documentation Status\n\n.. image:: https://travis-ci.org/pyca/service_identity.svg?branch=master\n   :target: https://travis-ci.org/pyca/service_identity\n   :alt: CI status\n\n.. image:: https://codecov.io/github/pyca/service_identity/branch/master/graph/badge.svg\n   :target: https://codecov.io/github/pyca/service_identity\n   :alt: Test Coverage\n\n.. image:: https://img.shields.io/badge/code%20style-black-000000.svg\n   :target: https://github.com/ambv/black\n   :alt: Code style: black\n\n.. image:: https://www.irccloud.com/invite-svg?channel=%23cryptography-dev&amp;hostname=irc.freenode.net&amp;port=6697&amp;ssl=1\n    :target: https://www.irccloud.com/invite?channel=%23cryptography-dev&amp;hostname=irc.freenode.net&amp;port=6697&amp;ssl=1\n\n.. begin\n\nUse this package if:\n\n- you use pyOpenSSL_ and don’t want to be MITM_\\ ed or\n- if you want to verify that a `PyCA cryptography`_ certificate is valid for a certain hostname or IP address.\n\n``service_identity`` aspires to give you all the tools you need for verifying whether a certificate is valid for the intended purposes.\n\nIn the simplest case, this means *host name verification*.\nHowever, ``service_identity`` implements `RFC 6125`_ fully and plans to add other relevant RFCs too.\n\n``service_identity``\\ ’s documentation lives at `Read the Docs <https://service-identity.readthedocs.io/>`_, the code on `GitHub <https://github.com/pyca/service_identity>`_.\n\n\n.. _Twisted: https://twistedmatrix.com/\n.. _pyOpenSSL: https://pypi.org/project/pyOpenSSL/\n.. _MITM: https://en.wikipedia.org/wiki/Man-in-the-middle_attack\n.. _RFC 6125: https://www.rfc-editor.org/info/rfc6125\n.. _PyCA cryptography: https://cryptography.io/\n\n\nRelease Information\n===================\n\n18.1.0 (2018-12-05)\n-------------------\n\nChanges:\n^^^^^^^^\n\n- pyOpenSSL is optional now if you use ``service_identity.cryptography.*`` only.\n- Added support for ``iPAddress`` ``subjectAltName``\\ s.\n  You can now verify whether a connection or a certificate is valid for an IP address using ``service_identity.pyopenssl.verify_ip_address()`` and ``service_identity.cryptography.verify_certificate_ip_address()``.\n  `#12 <https://github.com/pyca/service_identity/pull/12>`_\n\n`Full changelog <https://service-identity.readthedocs.io/en/stable/changelog.html>`_.\n\nAuthors\n=======\n\n``service_identity`` is written and maintained by `Hynek Schlawack <https://hynek.me/>`_.\n\nThe development is kindly supported by `Variomedia AG <https://www.variomedia.de/>`_.\n\nOther contributors can be found in `GitHub's overview <https://github.com/pyca/service_identity/graphs/contributors>`_.\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/service_identity-18.1.0.dist-info/RECORD",
    "content": "service_identity-18.1.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nservice_identity-18.1.0.dist-info/LICENSE,sha256=xQdRJuEnKxdlBONq82l4GpXFwRJCOdqOT2Gw-cFaVs8,1059\r\nservice_identity-18.1.0.dist-info/METADATA,sha256=hYfAMfI6CS-YCXzLSc7qMDAt98OOKeYYBkRFjRlMDLE,4911\r\nservice_identity-18.1.0.dist-info/RECORD,,\r\nservice_identity-18.1.0.dist-info/WHEEL,sha256=_wJFdOYk7i3xxT8ElOkUJvOdOvfNGbR9g-bf6UQT6sU,110\r\nservice_identity-18.1.0.dist-info/top_level.txt,sha256=P6bIiS8KYZ578xc05rqjHu3RL3ZoPRbOkLQmrEmM9F0,17\r\nservice_identity/__init__.py,sha256=Qw2IDTTklC-sDjFZdP7UJcLHGnLXmcjCyHOGtzA7Pu4,690\r\nservice_identity/__pycache__/__init__.cpython-36.pyc,,\r\nservice_identity/__pycache__/_common.cpython-36.pyc,,\r\nservice_identity/__pycache__/_compat.cpython-36.pyc,,\r\nservice_identity/__pycache__/cryptography.cpython-36.pyc,,\r\nservice_identity/__pycache__/exceptions.cpython-36.pyc,,\r\nservice_identity/__pycache__/pyopenssl.cpython-36.pyc,,\r\nservice_identity/_common.py,sha256=0-J60f6bK7RCoXQ9C3X9xDgxVe_yvVWEiMe51CUtTsA,11796\r\nservice_identity/_compat.py,sha256=6UqJSNJ3hDuONvI9eNz_1iwKvr_-U1eoMCclIpTP0tc,308\r\nservice_identity/cryptography.py,sha256=zkhLSewg3rjcD4PTLNFkbThnBzGAmLKnYbVe8wgHHBA,4977\r\nservice_identity/exceptions.py,sha256=q6-wKWm4qEPlNZ7ALvazs60Yw7IzSPfF7IZyaTX0pGc,1264\r\nservice_identity/pyopenssl.py,sha256=7XYtxl4FriQg_C4_rJtEQ182i0g53Dg0qy8bYJtKiS4,5154\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/service_identity-18.1.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.32.3)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/service_identity-18.1.0.dist-info/top_level.txt",
    "content": "service_identity\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/setuptools.pth",
    "content": "./setuptools-40.8.0-py3.6.egg\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/six-1.12.0.dist-info/INSTALLER",
    "content": "pip\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/six-1.12.0.dist-info/LICENSE",
    "content": "Copyright (c) 2010-2018 Benjamin Peterson\n\nPermission is hereby granted, free of charge, to any person obtaining a copy of\nthis software and associated documentation files (the \"Software\"), to deal in\nthe Software without restriction, including without limitation the rights to\nuse, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of\nthe Software, and to permit persons to whom the Software is furnished to do so,\nsubject to the following conditions:\n\nThe above copyright notice and this permission notice shall be included in all\ncopies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\nIMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS\nFOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR\nCOPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER\nIN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN\nCONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/six-1.12.0.dist-info/METADATA",
    "content": "Metadata-Version: 2.1\nName: six\nVersion: 1.12.0\nSummary: Python 2 and 3 compatibility utilities\nHome-page: https://github.com/benjaminp/six\nAuthor: Benjamin Peterson\nAuthor-email: benjamin@python.org\nLicense: MIT\nPlatform: UNKNOWN\nClassifier: Development Status :: 5 - Production/Stable\nClassifier: Programming Language :: Python :: 2\nClassifier: Programming Language :: Python :: 3\nClassifier: Intended Audience :: Developers\nClassifier: License :: OSI Approved :: MIT License\nClassifier: Topic :: Software Development :: Libraries\nClassifier: Topic :: Utilities\nRequires-Python: >=2.6, !=3.0.*, !=3.1.*\n\n.. image:: https://img.shields.io/pypi/v/six.svg\n   :target: https://pypi.org/project/six/\n   :alt: six on PyPI\n\n.. image:: https://travis-ci.org/benjaminp/six.svg?branch=master\n   :target: https://travis-ci.org/benjaminp/six\n   :alt: six on TravisCI\n\n.. image:: https://readthedocs.org/projects/six/badge/?version=latest\n   :target: https://six.readthedocs.io/\n   :alt: six's documentation on Read the Docs\n\n.. image:: https://img.shields.io/badge/license-MIT-green.svg\n   :target: https://github.com/benjaminp/six/blob/master/LICENSE\n   :alt: MIT License badge\n\nSix is a Python 2 and 3 compatibility library.  It provides utility functions\nfor smoothing over the differences between the Python versions with the goal of\nwriting Python code that is compatible on both Python versions.  See the\ndocumentation for more information on what is provided.\n\nSix supports every Python version since 2.6.  It is contained in only one Python\nfile, so it can be easily copied into your project. (The copyright and license\nnotice must be retained.)\n\nOnline documentation is at https://six.readthedocs.io/.\n\nBugs can be reported to https://github.com/benjaminp/six.  The code can also\nbe found there.\n\nFor questions about six or porting in general, email the python-porting mailing\nlist: https://mail.python.org/mailman/listinfo/python-porting\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/six-1.12.0.dist-info/RECORD",
    "content": "__pycache__/six.cpython-36.pyc,,\r\nsix-1.12.0.dist-info/INSTALLER,sha256=zuuue4knoyJ-UwPPXg8fezS7VCrXJQrAP7zeNuwvFQg,4\r\nsix-1.12.0.dist-info/LICENSE,sha256=5zL1TaWPPpzwxI6LUSlIk2_Pc2G9WK-mOpo8OSv3lK0,1066\r\nsix-1.12.0.dist-info/METADATA,sha256=CRdYkKPKCFJr7-qA8PDpBklGXfXJ3xu4mu5tkLBDL04,1940\r\nsix-1.12.0.dist-info/RECORD,,\r\nsix-1.12.0.dist-info/WHEEL,sha256=_wJFdOYk7i3xxT8ElOkUJvOdOvfNGbR9g-bf6UQT6sU,110\r\nsix-1.12.0.dist-info/top_level.txt,sha256=_iVH_iYEtEXnD8nYGQYpYFUvkUW9sEO1GYbkeKSAais,4\r\nsix.py,sha256=h9jch2pS86y4R36pKRS3LOYUCVFNIJMRwjZ4fJDtJ44,32452\r\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/six-1.12.0.dist-info/WHEEL",
    "content": "Wheel-Version: 1.0\nGenerator: bdist_wheel (0.32.3)\nRoot-Is-Purelib: true\nTag: py2-none-any\nTag: py3-none-any\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/six-1.12.0.dist-info/top_level.txt",
    "content": "six\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/six.py",
    "content": "# Copyright (c) 2010-2018 Benjamin Peterson\n#\n# Permission is hereby granted, free of charge, to any person obtaining a copy\n# of this software and associated documentation files (the \"Software\"), to deal\n# in the Software without restriction, including without limitation the rights\n# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n# copies of the Software, and to permit persons to whom the Software is\n# furnished to do so, subject to the following conditions:\n#\n# The above copyright notice and this permission notice shall be included in all\n# copies or substantial portions of the Software.\n#\n# THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\n# SOFTWARE.\n\n\"\"\"Utilities for writing code that runs on Python 2 and 3\"\"\"\n\nfrom __future__ import absolute_import\n\nimport functools\nimport itertools\nimport operator\nimport sys\nimport types\n\n__author__ = \"Benjamin Peterson <benjamin@python.org>\"\n__version__ = \"1.12.0\"\n\n\n# Useful for very coarse version differentiation.\nPY2 = sys.version_info[0] == 2\nPY3 = sys.version_info[0] == 3\nPY34 = sys.version_info[0:2] >= (3, 4)\n\nif PY3:\n    string_types = str,\n    integer_types = int,\n    class_types = type,\n    text_type = str\n    binary_type = bytes\n\n    MAXSIZE = sys.maxsize\nelse:\n    string_types = basestring,\n    integer_types = (int, long)\n    class_types = (type, types.ClassType)\n    text_type = unicode\n    binary_type = str\n\n    if sys.platform.startswith(\"java\"):\n        # Jython always uses 32 bits.\n        MAXSIZE = int((1 << 31) - 1)\n    else:\n        # It's possible to have sizeof(long) != sizeof(Py_ssize_t).\n        class X(object):\n\n            def __len__(self):\n                return 1 << 31\n        try:\n            len(X())\n        except OverflowError:\n            # 32-bit\n            MAXSIZE = int((1 << 31) - 1)\n        else:\n            # 64-bit\n            MAXSIZE = int((1 << 63) - 1)\n        del X\n\n\ndef _add_doc(func, doc):\n    \"\"\"Add documentation to a function.\"\"\"\n    func.__doc__ = doc\n\n\ndef _import_module(name):\n    \"\"\"Import module, returning the module after the last dot.\"\"\"\n    __import__(name)\n    return sys.modules[name]\n\n\nclass _LazyDescr(object):\n\n    def __init__(self, name):\n        self.name = name\n\n    def __get__(self, obj, tp):\n        result = self._resolve()\n        setattr(obj, self.name, result)  # Invokes __set__.\n        try:\n            # This is a bit ugly, but it avoids running this again by\n            # removing this descriptor.\n            delattr(obj.__class__, self.name)\n        except AttributeError:\n            pass\n        return result\n\n\nclass MovedModule(_LazyDescr):\n\n    def __init__(self, name, old, new=None):\n        super(MovedModule, self).__init__(name)\n        if PY3:\n            if new is None:\n                new = name\n            self.mod = new\n        else:\n            self.mod = old\n\n    def _resolve(self):\n        return _import_module(self.mod)\n\n    def __getattr__(self, attr):\n        _module = self._resolve()\n        value = getattr(_module, attr)\n        setattr(self, attr, value)\n        return value\n\n\nclass _LazyModule(types.ModuleType):\n\n    def __init__(self, name):\n        super(_LazyModule, self).__init__(name)\n        self.__doc__ = self.__class__.__doc__\n\n    def __dir__(self):\n        attrs = [\"__doc__\", \"__name__\"]\n        attrs += [attr.name for attr in self._moved_attributes]\n        return attrs\n\n    # Subclasses should override this\n    _moved_attributes = []\n\n\nclass MovedAttribute(_LazyDescr):\n\n    def __init__(self, name, old_mod, new_mod, old_attr=None, new_attr=None):\n        super(MovedAttribute, self).__init__(name)\n        if PY3:\n            if new_mod is None:\n                new_mod = name\n            self.mod = new_mod\n            if new_attr is None:\n                if old_attr is None:\n                    new_attr = name\n                else:\n                    new_attr = old_attr\n            self.attr = new_attr\n        else:\n            self.mod = old_mod\n            if old_attr is None:\n                old_attr = name\n            self.attr = old_attr\n\n    def _resolve(self):\n        module = _import_module(self.mod)\n        return getattr(module, self.attr)\n\n\nclass _SixMetaPathImporter(object):\n\n    \"\"\"\n    A meta path importer to import six.moves and its submodules.\n\n    This class implements a PEP302 finder and loader. It should be compatible\n    with Python 2.5 and all existing versions of Python3\n    \"\"\"\n\n    def __init__(self, six_module_name):\n        self.name = six_module_name\n        self.known_modules = {}\n\n    def _add_module(self, mod, *fullnames):\n        for fullname in fullnames:\n            self.known_modules[self.name + \".\" + fullname] = mod\n\n    def _get_module(self, fullname):\n        return self.known_modules[self.name + \".\" + fullname]\n\n    def find_module(self, fullname, path=None):\n        if fullname in self.known_modules:\n            return self\n        return None\n\n    def __get_module(self, fullname):\n        try:\n            return self.known_modules[fullname]\n        except KeyError:\n            raise ImportError(\"This loader does not know module \" + fullname)\n\n    def load_module(self, fullname):\n        try:\n            # in case of a reload\n            return sys.modules[fullname]\n        except KeyError:\n            pass\n        mod = self.__get_module(fullname)\n        if isinstance(mod, MovedModule):\n            mod = mod._resolve()\n        else:\n            mod.__loader__ = self\n        sys.modules[fullname] = mod\n        return mod\n\n    def is_package(self, fullname):\n        \"\"\"\n        Return true, if the named module is a package.\n\n        We need this method to get correct spec objects with\n        Python 3.4 (see PEP451)\n        \"\"\"\n        return hasattr(self.__get_module(fullname), \"__path__\")\n\n    def get_code(self, fullname):\n        \"\"\"Return None\n\n        Required, if is_package is implemented\"\"\"\n        self.__get_module(fullname)  # eventually raises ImportError\n        return None\n    get_source = get_code  # same as get_code\n\n_importer = _SixMetaPathImporter(__name__)\n\n\nclass _MovedItems(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects\"\"\"\n    __path__ = []  # mark as package\n\n\n_moved_attributes = [\n    MovedAttribute(\"cStringIO\", \"cStringIO\", \"io\", \"StringIO\"),\n    MovedAttribute(\"filter\", \"itertools\", \"builtins\", \"ifilter\", \"filter\"),\n    MovedAttribute(\"filterfalse\", \"itertools\", \"itertools\", \"ifilterfalse\", \"filterfalse\"),\n    MovedAttribute(\"input\", \"__builtin__\", \"builtins\", \"raw_input\", \"input\"),\n    MovedAttribute(\"intern\", \"__builtin__\", \"sys\"),\n    MovedAttribute(\"map\", \"itertools\", \"builtins\", \"imap\", \"map\"),\n    MovedAttribute(\"getcwd\", \"os\", \"os\", \"getcwdu\", \"getcwd\"),\n    MovedAttribute(\"getcwdb\", \"os\", \"os\", \"getcwd\", \"getcwdb\"),\n    MovedAttribute(\"getoutput\", \"commands\", \"subprocess\"),\n    MovedAttribute(\"range\", \"__builtin__\", \"builtins\", \"xrange\", \"range\"),\n    MovedAttribute(\"reload_module\", \"__builtin__\", \"importlib\" if PY34 else \"imp\", \"reload\"),\n    MovedAttribute(\"reduce\", \"__builtin__\", \"functools\"),\n    MovedAttribute(\"shlex_quote\", \"pipes\", \"shlex\", \"quote\"),\n    MovedAttribute(\"StringIO\", \"StringIO\", \"io\"),\n    MovedAttribute(\"UserDict\", \"UserDict\", \"collections\"),\n    MovedAttribute(\"UserList\", \"UserList\", \"collections\"),\n    MovedAttribute(\"UserString\", \"UserString\", \"collections\"),\n    MovedAttribute(\"xrange\", \"__builtin__\", \"builtins\", \"xrange\", \"range\"),\n    MovedAttribute(\"zip\", \"itertools\", \"builtins\", \"izip\", \"zip\"),\n    MovedAttribute(\"zip_longest\", \"itertools\", \"itertools\", \"izip_longest\", \"zip_longest\"),\n    MovedModule(\"builtins\", \"__builtin__\"),\n    MovedModule(\"configparser\", \"ConfigParser\"),\n    MovedModule(\"copyreg\", \"copy_reg\"),\n    MovedModule(\"dbm_gnu\", \"gdbm\", \"dbm.gnu\"),\n    MovedModule(\"_dummy_thread\", \"dummy_thread\", \"_dummy_thread\"),\n    MovedModule(\"http_cookiejar\", \"cookielib\", \"http.cookiejar\"),\n    MovedModule(\"http_cookies\", \"Cookie\", \"http.cookies\"),\n    MovedModule(\"html_entities\", \"htmlentitydefs\", \"html.entities\"),\n    MovedModule(\"html_parser\", \"HTMLParser\", \"html.parser\"),\n    MovedModule(\"http_client\", \"httplib\", \"http.client\"),\n    MovedModule(\"email_mime_base\", \"email.MIMEBase\", \"email.mime.base\"),\n    MovedModule(\"email_mime_image\", \"email.MIMEImage\", \"email.mime.image\"),\n    MovedModule(\"email_mime_multipart\", \"email.MIMEMultipart\", \"email.mime.multipart\"),\n    MovedModule(\"email_mime_nonmultipart\", \"email.MIMENonMultipart\", \"email.mime.nonmultipart\"),\n    MovedModule(\"email_mime_text\", \"email.MIMEText\", \"email.mime.text\"),\n    MovedModule(\"BaseHTTPServer\", \"BaseHTTPServer\", \"http.server\"),\n    MovedModule(\"CGIHTTPServer\", \"CGIHTTPServer\", \"http.server\"),\n    MovedModule(\"SimpleHTTPServer\", \"SimpleHTTPServer\", \"http.server\"),\n    MovedModule(\"cPickle\", \"cPickle\", \"pickle\"),\n    MovedModule(\"queue\", \"Queue\"),\n    MovedModule(\"reprlib\", \"repr\"),\n    MovedModule(\"socketserver\", \"SocketServer\"),\n    MovedModule(\"_thread\", \"thread\", \"_thread\"),\n    MovedModule(\"tkinter\", \"Tkinter\"),\n    MovedModule(\"tkinter_dialog\", \"Dialog\", \"tkinter.dialog\"),\n    MovedModule(\"tkinter_filedialog\", \"FileDialog\", \"tkinter.filedialog\"),\n    MovedModule(\"tkinter_scrolledtext\", \"ScrolledText\", \"tkinter.scrolledtext\"),\n    MovedModule(\"tkinter_simpledialog\", \"SimpleDialog\", \"tkinter.simpledialog\"),\n    MovedModule(\"tkinter_tix\", \"Tix\", \"tkinter.tix\"),\n    MovedModule(\"tkinter_ttk\", \"ttk\", \"tkinter.ttk\"),\n    MovedModule(\"tkinter_constants\", \"Tkconstants\", \"tkinter.constants\"),\n    MovedModule(\"tkinter_dnd\", \"Tkdnd\", \"tkinter.dnd\"),\n    MovedModule(\"tkinter_colorchooser\", \"tkColorChooser\",\n                \"tkinter.colorchooser\"),\n    MovedModule(\"tkinter_commondialog\", \"tkCommonDialog\",\n                \"tkinter.commondialog\"),\n    MovedModule(\"tkinter_tkfiledialog\", \"tkFileDialog\", \"tkinter.filedialog\"),\n    MovedModule(\"tkinter_font\", \"tkFont\", \"tkinter.font\"),\n    MovedModule(\"tkinter_messagebox\", \"tkMessageBox\", \"tkinter.messagebox\"),\n    MovedModule(\"tkinter_tksimpledialog\", \"tkSimpleDialog\",\n                \"tkinter.simpledialog\"),\n    MovedModule(\"urllib_parse\", __name__ + \".moves.urllib_parse\", \"urllib.parse\"),\n    MovedModule(\"urllib_error\", __name__ + \".moves.urllib_error\", \"urllib.error\"),\n    MovedModule(\"urllib\", __name__ + \".moves.urllib\", __name__ + \".moves.urllib\"),\n    MovedModule(\"urllib_robotparser\", \"robotparser\", \"urllib.robotparser\"),\n    MovedModule(\"xmlrpc_client\", \"xmlrpclib\", \"xmlrpc.client\"),\n    MovedModule(\"xmlrpc_server\", \"SimpleXMLRPCServer\", \"xmlrpc.server\"),\n]\n# Add windows specific modules.\nif sys.platform == \"win32\":\n    _moved_attributes += [\n        MovedModule(\"winreg\", \"_winreg\"),\n    ]\n\nfor attr in _moved_attributes:\n    setattr(_MovedItems, attr.name, attr)\n    if isinstance(attr, MovedModule):\n        _importer._add_module(attr, \"moves.\" + attr.name)\ndel attr\n\n_MovedItems._moved_attributes = _moved_attributes\n\nmoves = _MovedItems(__name__ + \".moves\")\n_importer._add_module(moves, \"moves\")\n\n\nclass Module_six_moves_urllib_parse(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_parse\"\"\"\n\n\n_urllib_parse_moved_attributes = [\n    MovedAttribute(\"ParseResult\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"SplitResult\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"parse_qs\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"parse_qsl\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urldefrag\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urljoin\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urlparse\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urlsplit\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urlunparse\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"urlunsplit\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"quote\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"quote_plus\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"unquote\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"unquote_plus\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"unquote_to_bytes\", \"urllib\", \"urllib.parse\", \"unquote\", \"unquote_to_bytes\"),\n    MovedAttribute(\"urlencode\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"splitquery\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"splittag\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"splituser\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"splitvalue\", \"urllib\", \"urllib.parse\"),\n    MovedAttribute(\"uses_fragment\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"uses_netloc\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"uses_params\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"uses_query\", \"urlparse\", \"urllib.parse\"),\n    MovedAttribute(\"uses_relative\", \"urlparse\", \"urllib.parse\"),\n]\nfor attr in _urllib_parse_moved_attributes:\n    setattr(Module_six_moves_urllib_parse, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_parse._moved_attributes = _urllib_parse_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_parse(__name__ + \".moves.urllib_parse\"),\n                      \"moves.urllib_parse\", \"moves.urllib.parse\")\n\n\nclass Module_six_moves_urllib_error(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_error\"\"\"\n\n\n_urllib_error_moved_attributes = [\n    MovedAttribute(\"URLError\", \"urllib2\", \"urllib.error\"),\n    MovedAttribute(\"HTTPError\", \"urllib2\", \"urllib.error\"),\n    MovedAttribute(\"ContentTooShortError\", \"urllib\", \"urllib.error\"),\n]\nfor attr in _urllib_error_moved_attributes:\n    setattr(Module_six_moves_urllib_error, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_error._moved_attributes = _urllib_error_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_error(__name__ + \".moves.urllib.error\"),\n                      \"moves.urllib_error\", \"moves.urllib.error\")\n\n\nclass Module_six_moves_urllib_request(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_request\"\"\"\n\n\n_urllib_request_moved_attributes = [\n    MovedAttribute(\"urlopen\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"install_opener\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"build_opener\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"pathname2url\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"url2pathname\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"getproxies\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"Request\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"OpenerDirector\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPDefaultErrorHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPRedirectHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPCookieProcessor\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"ProxyHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"BaseHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPPasswordMgr\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPPasswordMgrWithDefaultRealm\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"AbstractBasicAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPBasicAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"ProxyBasicAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"AbstractDigestAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPDigestAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"ProxyDigestAuthHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPSHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"FileHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"FTPHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"CacheFTPHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"UnknownHandler\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"HTTPErrorProcessor\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"urlretrieve\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"urlcleanup\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"URLopener\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"FancyURLopener\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"proxy_bypass\", \"urllib\", \"urllib.request\"),\n    MovedAttribute(\"parse_http_list\", \"urllib2\", \"urllib.request\"),\n    MovedAttribute(\"parse_keqv_list\", \"urllib2\", \"urllib.request\"),\n]\nfor attr in _urllib_request_moved_attributes:\n    setattr(Module_six_moves_urllib_request, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_request._moved_attributes = _urllib_request_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_request(__name__ + \".moves.urllib.request\"),\n                      \"moves.urllib_request\", \"moves.urllib.request\")\n\n\nclass Module_six_moves_urllib_response(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_response\"\"\"\n\n\n_urllib_response_moved_attributes = [\n    MovedAttribute(\"addbase\", \"urllib\", \"urllib.response\"),\n    MovedAttribute(\"addclosehook\", \"urllib\", \"urllib.response\"),\n    MovedAttribute(\"addinfo\", \"urllib\", \"urllib.response\"),\n    MovedAttribute(\"addinfourl\", \"urllib\", \"urllib.response\"),\n]\nfor attr in _urllib_response_moved_attributes:\n    setattr(Module_six_moves_urllib_response, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_response._moved_attributes = _urllib_response_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_response(__name__ + \".moves.urllib.response\"),\n                      \"moves.urllib_response\", \"moves.urllib.response\")\n\n\nclass Module_six_moves_urllib_robotparser(_LazyModule):\n\n    \"\"\"Lazy loading of moved objects in six.moves.urllib_robotparser\"\"\"\n\n\n_urllib_robotparser_moved_attributes = [\n    MovedAttribute(\"RobotFileParser\", \"robotparser\", \"urllib.robotparser\"),\n]\nfor attr in _urllib_robotparser_moved_attributes:\n    setattr(Module_six_moves_urllib_robotparser, attr.name, attr)\ndel attr\n\nModule_six_moves_urllib_robotparser._moved_attributes = _urllib_robotparser_moved_attributes\n\n_importer._add_module(Module_six_moves_urllib_robotparser(__name__ + \".moves.urllib.robotparser\"),\n                      \"moves.urllib_robotparser\", \"moves.urllib.robotparser\")\n\n\nclass Module_six_moves_urllib(types.ModuleType):\n\n    \"\"\"Create a six.moves.urllib namespace that resembles the Python 3 namespace\"\"\"\n    __path__ = []  # mark as package\n    parse = _importer._get_module(\"moves.urllib_parse\")\n    error = _importer._get_module(\"moves.urllib_error\")\n    request = _importer._get_module(\"moves.urllib_request\")\n    response = _importer._get_module(\"moves.urllib_response\")\n    robotparser = _importer._get_module(\"moves.urllib_robotparser\")\n\n    def __dir__(self):\n        return ['parse', 'error', 'request', 'response', 'robotparser']\n\n_importer._add_module(Module_six_moves_urllib(__name__ + \".moves.urllib\"),\n                      \"moves.urllib\")\n\n\ndef add_move(move):\n    \"\"\"Add an item to six.moves.\"\"\"\n    setattr(_MovedItems, move.name, move)\n\n\ndef remove_move(name):\n    \"\"\"Remove item from six.moves.\"\"\"\n    try:\n        delattr(_MovedItems, name)\n    except AttributeError:\n        try:\n            del moves.__dict__[name]\n        except KeyError:\n            raise AttributeError(\"no such move, %r\" % (name,))\n\n\nif PY3:\n    _meth_func = \"__func__\"\n    _meth_self = \"__self__\"\n\n    _func_closure = \"__closure__\"\n    _func_code = \"__code__\"\n    _func_defaults = \"__defaults__\"\n    _func_globals = \"__globals__\"\nelse:\n    _meth_func = \"im_func\"\n    _meth_self = \"im_self\"\n\n    _func_closure = \"func_closure\"\n    _func_code = \"func_code\"\n    _func_defaults = \"func_defaults\"\n    _func_globals = \"func_globals\"\n\n\ntry:\n    advance_iterator = next\nexcept NameError:\n    def advance_iterator(it):\n        return it.next()\nnext = advance_iterator\n\n\ntry:\n    callable = callable\nexcept NameError:\n    def callable(obj):\n        return any(\"__call__\" in klass.__dict__ for klass in type(obj).__mro__)\n\n\nif PY3:\n    def get_unbound_function(unbound):\n        return unbound\n\n    create_bound_method = types.MethodType\n\n    def create_unbound_method(func, cls):\n        return func\n\n    Iterator = object\nelse:\n    def get_unbound_function(unbound):\n        return unbound.im_func\n\n    def create_bound_method(func, obj):\n        return types.MethodType(func, obj, obj.__class__)\n\n    def create_unbound_method(func, cls):\n        return types.MethodType(func, None, cls)\n\n    class Iterator(object):\n\n        def next(self):\n            return type(self).__next__(self)\n\n    callable = callable\n_add_doc(get_unbound_function,\n         \"\"\"Get the function out of a possibly unbound function\"\"\")\n\n\nget_method_function = operator.attrgetter(_meth_func)\nget_method_self = operator.attrgetter(_meth_self)\nget_function_closure = operator.attrgetter(_func_closure)\nget_function_code = operator.attrgetter(_func_code)\nget_function_defaults = operator.attrgetter(_func_defaults)\nget_function_globals = operator.attrgetter(_func_globals)\n\n\nif PY3:\n    def iterkeys(d, **kw):\n        return iter(d.keys(**kw))\n\n    def itervalues(d, **kw):\n        return iter(d.values(**kw))\n\n    def iteritems(d, **kw):\n        return iter(d.items(**kw))\n\n    def iterlists(d, **kw):\n        return iter(d.lists(**kw))\n\n    viewkeys = operator.methodcaller(\"keys\")\n\n    viewvalues = operator.methodcaller(\"values\")\n\n    viewitems = operator.methodcaller(\"items\")\nelse:\n    def iterkeys(d, **kw):\n        return d.iterkeys(**kw)\n\n    def itervalues(d, **kw):\n        return d.itervalues(**kw)\n\n    def iteritems(d, **kw):\n        return d.iteritems(**kw)\n\n    def iterlists(d, **kw):\n        return d.iterlists(**kw)\n\n    viewkeys = operator.methodcaller(\"viewkeys\")\n\n    viewvalues = operator.methodcaller(\"viewvalues\")\n\n    viewitems = operator.methodcaller(\"viewitems\")\n\n_add_doc(iterkeys, \"Return an iterator over the keys of a dictionary.\")\n_add_doc(itervalues, \"Return an iterator over the values of a dictionary.\")\n_add_doc(iteritems,\n         \"Return an iterator over the (key, value) pairs of a dictionary.\")\n_add_doc(iterlists,\n         \"Return an iterator over the (key, [values]) pairs of a dictionary.\")\n\n\nif PY3:\n    def b(s):\n        return s.encode(\"latin-1\")\n\n    def u(s):\n        return s\n    unichr = chr\n    import struct\n    int2byte = struct.Struct(\">B\").pack\n    del struct\n    byte2int = operator.itemgetter(0)\n    indexbytes = operator.getitem\n    iterbytes = iter\n    import io\n    StringIO = io.StringIO\n    BytesIO = io.BytesIO\n    _assertCountEqual = \"assertCountEqual\"\n    if sys.version_info[1] <= 1:\n        _assertRaisesRegex = \"assertRaisesRegexp\"\n        _assertRegex = \"assertRegexpMatches\"\n    else:\n        _assertRaisesRegex = \"assertRaisesRegex\"\n        _assertRegex = \"assertRegex\"\nelse:\n    def b(s):\n        return s\n    # Workaround for standalone backslash\n\n    def u(s):\n        return unicode(s.replace(r'\\\\', r'\\\\\\\\'), \"unicode_escape\")\n    unichr = unichr\n    int2byte = chr\n\n    def byte2int(bs):\n        return ord(bs[0])\n\n    def indexbytes(buf, i):\n        return ord(buf[i])\n    iterbytes = functools.partial(itertools.imap, ord)\n    import StringIO\n    StringIO = BytesIO = StringIO.StringIO\n    _assertCountEqual = \"assertItemsEqual\"\n    _assertRaisesRegex = \"assertRaisesRegexp\"\n    _assertRegex = \"assertRegexpMatches\"\n_add_doc(b, \"\"\"Byte literal\"\"\")\n_add_doc(u, \"\"\"Text literal\"\"\")\n\n\ndef assertCountEqual(self, *args, **kwargs):\n    return getattr(self, _assertCountEqual)(*args, **kwargs)\n\n\ndef assertRaisesRegex(self, *args, **kwargs):\n    return getattr(self, _assertRaisesRegex)(*args, **kwargs)\n\n\ndef assertRegex(self, *args, **kwargs):\n    return getattr(self, _assertRegex)(*args, **kwargs)\n\n\nif PY3:\n    exec_ = getattr(moves.builtins, \"exec\")\n\n    def reraise(tp, value, tb=None):\n        try:\n            if value is None:\n                value = tp()\n            if value.__traceback__ is not tb:\n                raise value.with_traceback(tb)\n            raise value\n        finally:\n            value = None\n            tb = None\n\nelse:\n    def exec_(_code_, _globs_=None, _locs_=None):\n        \"\"\"Execute code in a namespace.\"\"\"\n        if _globs_ is None:\n            frame = sys._getframe(1)\n            _globs_ = frame.f_globals\n            if _locs_ is None:\n                _locs_ = frame.f_locals\n            del frame\n        elif _locs_ is None:\n            _locs_ = _globs_\n        exec(\"\"\"exec _code_ in _globs_, _locs_\"\"\")\n\n    exec_(\"\"\"def reraise(tp, value, tb=None):\n    try:\n        raise tp, value, tb\n    finally:\n        tb = None\n\"\"\")\n\n\nif sys.version_info[:2] == (3, 2):\n    exec_(\"\"\"def raise_from(value, from_value):\n    try:\n        if from_value is None:\n            raise value\n        raise value from from_value\n    finally:\n        value = None\n\"\"\")\nelif sys.version_info[:2] > (3, 2):\n    exec_(\"\"\"def raise_from(value, from_value):\n    try:\n        raise value from from_value\n    finally:\n        value = None\n\"\"\")\nelse:\n    def raise_from(value, from_value):\n        raise value\n\n\nprint_ = getattr(moves.builtins, \"print\", None)\nif print_ is None:\n    def print_(*args, **kwargs):\n        \"\"\"The new-style print function for Python 2.4 and 2.5.\"\"\"\n        fp = kwargs.pop(\"file\", sys.stdout)\n        if fp is None:\n            return\n\n        def write(data):\n            if not isinstance(data, basestring):\n                data = str(data)\n            # If the file has an encoding, encode unicode with it.\n            if (isinstance(fp, file) and\n                    isinstance(data, unicode) and\n                    fp.encoding is not None):\n                errors = getattr(fp, \"errors\", None)\n                if errors is None:\n                    errors = \"strict\"\n                data = data.encode(fp.encoding, errors)\n            fp.write(data)\n        want_unicode = False\n        sep = kwargs.pop(\"sep\", None)\n        if sep is not None:\n            if isinstance(sep, unicode):\n                want_unicode = True\n            elif not isinstance(sep, str):\n                raise TypeError(\"sep must be None or a string\")\n        end = kwargs.pop(\"end\", None)\n        if end is not None:\n            if isinstance(end, unicode):\n                want_unicode = True\n            elif not isinstance(end, str):\n                raise TypeError(\"end must be None or a string\")\n        if kwargs:\n            raise TypeError(\"invalid keyword arguments to print()\")\n        if not want_unicode:\n            for arg in args:\n                if isinstance(arg, unicode):\n                    want_unicode = True\n                    break\n        if want_unicode:\n            newline = unicode(\"\\n\")\n            space = unicode(\" \")\n        else:\n            newline = \"\\n\"\n            space = \" \"\n        if sep is None:\n            sep = space\n        if end is None:\n            end = newline\n        for i, arg in enumerate(args):\n            if i:\n                write(sep)\n            write(arg)\n        write(end)\nif sys.version_info[:2] < (3, 3):\n    _print = print_\n\n    def print_(*args, **kwargs):\n        fp = kwargs.get(\"file\", sys.stdout)\n        flush = kwargs.pop(\"flush\", False)\n        _print(*args, **kwargs)\n        if flush and fp is not None:\n            fp.flush()\n\n_add_doc(reraise, \"\"\"Reraise an exception.\"\"\")\n\nif sys.version_info[0:2] < (3, 4):\n    def wraps(wrapped, assigned=functools.WRAPPER_ASSIGNMENTS,\n              updated=functools.WRAPPER_UPDATES):\n        def wrapper(f):\n            f = functools.wraps(wrapped, assigned, updated)(f)\n            f.__wrapped__ = wrapped\n            return f\n        return wrapper\nelse:\n    wraps = functools.wraps\n\n\ndef with_metaclass(meta, *bases):\n    \"\"\"Create a base class with a metaclass.\"\"\"\n    # This requires a bit of explanation: the basic idea is to make a dummy\n    # metaclass for one level of class instantiation that replaces itself with\n    # the actual metaclass.\n    class metaclass(type):\n\n        def __new__(cls, name, this_bases, d):\n            return meta(name, bases, d)\n\n        @classmethod\n        def __prepare__(cls, name, this_bases):\n            return meta.__prepare__(name, bases)\n    return type.__new__(metaclass, 'temporary_class', (), {})\n\n\ndef add_metaclass(metaclass):\n    \"\"\"Class decorator for creating a class with a metaclass.\"\"\"\n    def wrapper(cls):\n        orig_vars = cls.__dict__.copy()\n        slots = orig_vars.get('__slots__')\n        if slots is not None:\n            if isinstance(slots, str):\n                slots = [slots]\n            for slots_var in slots:\n                orig_vars.pop(slots_var)\n        orig_vars.pop('__dict__', None)\n        orig_vars.pop('__weakref__', None)\n        if hasattr(cls, '__qualname__'):\n            orig_vars['__qualname__'] = cls.__qualname__\n        return metaclass(cls.__name__, cls.__bases__, orig_vars)\n    return wrapper\n\n\ndef ensure_binary(s, encoding='utf-8', errors='strict'):\n    \"\"\"Coerce **s** to six.binary_type.\n\n    For Python 2:\n      - `unicode` -> encoded to `str`\n      - `str` -> `str`\n\n    For Python 3:\n      - `str` -> encoded to `bytes`\n      - `bytes` -> `bytes`\n    \"\"\"\n    if isinstance(s, text_type):\n        return s.encode(encoding, errors)\n    elif isinstance(s, binary_type):\n        return s\n    else:\n        raise TypeError(\"not expecting type '%s'\" % type(s))\n\n\ndef ensure_str(s, encoding='utf-8', errors='strict'):\n    \"\"\"Coerce *s* to `str`.\n\n    For Python 2:\n      - `unicode` -> encoded to `str`\n      - `str` -> `str`\n\n    For Python 3:\n      - `str` -> `str`\n      - `bytes` -> decoded to `str`\n    \"\"\"\n    if not isinstance(s, (text_type, binary_type)):\n        raise TypeError(\"not expecting type '%s'\" % type(s))\n    if PY2 and isinstance(s, text_type):\n        s = s.encode(encoding, errors)\n    elif PY3 and isinstance(s, binary_type):\n        s = s.decode(encoding, errors)\n    return s\n\n\ndef ensure_text(s, encoding='utf-8', errors='strict'):\n    \"\"\"Coerce *s* to six.text_type.\n\n    For Python 2:\n      - `unicode` -> `unicode`\n      - `str` -> `unicode`\n\n    For Python 3:\n      - `str` -> `str`\n      - `bytes` -> decoded to `str`\n    \"\"\"\n    if isinstance(s, binary_type):\n        return s.decode(encoding, errors)\n    elif isinstance(s, text_type):\n        return s\n    else:\n        raise TypeError(\"not expecting type '%s'\" % type(s))\n\n\n\ndef python_2_unicode_compatible(klass):\n    \"\"\"\n    A decorator that defines __unicode__ and __str__ methods under Python 2.\n    Under Python 3 it does nothing.\n\n    To support Python 2 and 3 with a single code base, define a __str__ method\n    returning text and apply this decorator to the class.\n    \"\"\"\n    if PY2:\n        if '__str__' not in klass.__dict__:\n            raise ValueError(\"@python_2_unicode_compatible cannot be applied \"\n                             \"to %s because it doesn't define __str__().\" %\n                             klass.__name__)\n        klass.__unicode__ = klass.__str__\n        klass.__str__ = lambda self: self.__unicode__().encode('utf-8')\n    return klass\n\n\n# Complete the moves implementation.\n# This code is at the end of this module to speed up module loading.\n# Turn this module into a package.\n__path__ = []  # required for PEP 302 and PEP 451\n__package__ = __name__  # see PEP 366 @ReservedAssignment\nif globals().get(\"__spec__\") is not None:\n    __spec__.submodule_search_locations = []  # PEP 451 @UndefinedVariable\n# Remove other six meta path importers, since they cause problems. This can\n# happen if six is removed from sys.modules and then reloaded. (Setuptools does\n# this for some reason.)\nif sys.meta_path:\n    for i, importer in enumerate(sys.meta_path):\n        # Here's some real nastiness: Another \"instance\" of the six module might\n        # be floating around. Therefore, we can't use isinstance() to check for\n        # the six meta path importer, since the other six instance will have\n        # inserted an importer with different class.\n        if (type(importer).__name__ == \"_SixMetaPathImporter\" and\n                importer.name == __name__):\n            del sys.meta_path[i]\n            break\n    del i, importer\n# Finally, add the importer to the meta path import hook.\nsys.meta_path.append(_importer)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/__init__.py",
    "content": "# -*- test-case-name: twisted -*-\n\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTwisted: The Framework Of Your Internet.\n\"\"\"\n\n# setup version\nfrom twisted._version import __version__ as version\n__version__ = version.short()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/__main__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n# Make the twisted module executable with the default behaviour of\n# running twist.\n# This is not a docstring to avoid changing the string output of twist.\n\nfrom __future__ import division, absolute_import\n\nimport sys\nfrom pkg_resources import load_entry_point\n\nif __name__ == '__main__':\n    sys.exit(\n        load_entry_point('Twisted', 'console_scripts', 'twist')()\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_threads/__init__.py",
    "content": "# -*- test-case-name: twisted.test.test_paths -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTwisted integration with operating system threads.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom ._threadworker import ThreadWorker, LockWorker\nfrom ._ithreads import IWorker, AlreadyQuit\nfrom ._team import Team\nfrom ._memory import createMemoryWorker\nfrom ._pool import pool\n\n__all__ = [\n    \"ThreadWorker\",\n    \"LockWorker\",\n    \"IWorker\",\n    \"AlreadyQuit\",\n    \"Team\",\n    \"createMemoryWorker\",\n    \"pool\",\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_threads/_convenience.py",
    "content": "# -*- test-case-name: twisted._threads.test.test_convenience -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nCommon functionality used within the implementation of various workers.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom ._ithreads import AlreadyQuit\n\n\nclass Quit(object):\n    \"\"\"\n    A flag representing whether a worker has been quit.\n\n    @ivar isSet: Whether this flag is set.\n    @type isSet: L{bool}\n    \"\"\"\n\n    def __init__(self):\n        \"\"\"\n        Create a L{Quit} un-set.\n        \"\"\"\n        self.isSet = False\n\n\n    def set(self):\n        \"\"\"\n        Set the flag if it has not been set.\n\n        @raise AlreadyQuit: If it has been set.\n        \"\"\"\n        self.check()\n        self.isSet = True\n\n\n    def check(self):\n        \"\"\"\n        Check if the flag has been set.\n\n        @raise AlreadyQuit: If it has been set.\n        \"\"\"\n        if self.isSet:\n            raise AlreadyQuit()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_threads/_ithreads.py",
    "content": "# -*- test-case-name: twisted._threads.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nInterfaces related to threads.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom zope.interface import Interface\n\n\nclass AlreadyQuit(Exception):\n    \"\"\"\n    This worker worker is dead and cannot execute more instructions.\n    \"\"\"\n\n\n\nclass IWorker(Interface):\n    \"\"\"\n    A worker that can perform some work concurrently.\n\n    All methods on this interface must be thread-safe.\n    \"\"\"\n\n    def do(task):\n        \"\"\"\n        Perform the given task.\n\n        As an interface, this method makes no specific claims about concurrent\n        execution.  An L{IWorker}'s C{do} implementation may defer execution\n        for later on the same thread, immediately on a different thread, or\n        some combination of the two.  It is valid for a C{do} method to\n        schedule C{task} in such a way that it may never be executed.\n\n        It is important for some implementations to provide specific properties\n        with respect to where C{task} is executed, of course, and client code\n        may rely on a more specific implementation of C{do} than L{IWorker}.\n\n        @param task: a task to call in a thread or other concurrent context.\n        @type task: 0-argument callable\n\n        @raise AlreadyQuit: if C{quit} has been called.\n        \"\"\"\n\n    def quit():\n        \"\"\"\n        Free any resources associated with this L{IWorker} and cause it to\n        reject all future work.\n\n        @raise: L{AlreadyQuit} if this method has already been called.\n        \"\"\"\n\n\nclass IExclusiveWorker(IWorker):\n    \"\"\"\n    Like L{IWorker}, but with the additional guarantee that the callables\n    passed to C{do} will not be called exclusively with each other.\n    \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_threads/_memory.py",
    "content": "# -*- test-case-name: twisted._threads.test.test_memory -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nImplementation of an in-memory worker that defers execution.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom zope.interface import implementer\n\nfrom . import IWorker\nfrom ._convenience import Quit\n\nNoMoreWork = object()\n\n@implementer(IWorker)\nclass MemoryWorker(object):\n    \"\"\"\n    An L{IWorker} that queues work for later performance.\n\n    @ivar _quit: a flag indicating\n    @type _quit: L{Quit}\n    \"\"\"\n\n    def __init__(self, pending=list):\n        \"\"\"\n        Create a L{MemoryWorker}.\n        \"\"\"\n        self._quit = Quit()\n        self._pending = pending()\n\n\n    def do(self, work):\n        \"\"\"\n        Queue some work for to perform later; see L{createMemoryWorker}.\n\n        @param work: The work to perform.\n        \"\"\"\n        self._quit.check()\n        self._pending.append(work)\n\n\n    def quit(self):\n        \"\"\"\n        Quit this worker.\n        \"\"\"\n        self._quit.set()\n        self._pending.append(NoMoreWork)\n\n\n\ndef createMemoryWorker():\n    \"\"\"\n    Create an L{IWorker} that does nothing but defer work, to be performed\n    later.\n\n    @return: a worker that will enqueue work to perform later, and a callable\n        that will perform one element of that work.\n    @rtype: 2-L{tuple} of (L{IWorker}, L{callable})\n    \"\"\"\n    def perform():\n        if not worker._pending:\n            return False\n        if worker._pending[0] is NoMoreWork:\n            return False\n        worker._pending.pop(0)()\n        return True\n    worker = MemoryWorker()\n    return (worker, perform)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_threads/_pool.py",
    "content": "# -*- test-case-name: twisted._threads.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTop level thread pool interface, used to implement\nL{twisted.python.threadpool}.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom threading import Thread, Lock, local as LocalStorage\ntry:\n    from Queue import Queue\nexcept ImportError:\n    from queue import Queue\n\nfrom twisted.python.log import err\n\nfrom ._threadworker import LockWorker\nfrom ._team import Team\nfrom ._threadworker import ThreadWorker\n\n\ndef pool(currentLimit, threadFactory=Thread):\n    \"\"\"\n    Construct a L{Team} that spawns threads as a thread pool, with the given\n    limiting function.\n\n    @note: Future maintainers: while the public API for the eventual move to\n        twisted.threads should look I{something} like this, and while this\n        function is necessary to implement the API described by\n        L{twisted.python.threadpool}, I am starting to think the idea of a hard\n        upper limit on threadpool size is just bad (turning memory performance\n        issues into correctness issues well before we run into memory\n        pressure), and instead we should build something with reactor\n        integration for slowly releasing idle threads when they're not needed\n        and I{rate} limiting the creation of new threads rather than just\n        hard-capping it.\n\n    @param currentLimit: a callable that returns the current limit on the\n        number of workers that the returned L{Team} should create; if it\n        already has more workers than that value, no new workers will be\n        created.\n    @type currentLimit: 0-argument callable returning L{int}\n\n    @param reactor: If passed, the L{IReactorFromThreads} / L{IReactorCore} to\n        be used to coordinate actions on the L{Team} itself.  Otherwise, a\n        L{LockWorker} will be used.\n\n    @return: a new L{Team}.\n    \"\"\"\n\n    def startThread(target):\n        return threadFactory(target=target).start()\n\n    def limitedWorkerCreator():\n        stats = team.statistics()\n        if stats.busyWorkerCount + stats.idleWorkerCount >= currentLimit():\n            return None\n        return ThreadWorker(startThread, Queue())\n\n    team = Team(coordinator=LockWorker(Lock(), LocalStorage()),\n                createWorker=limitedWorkerCreator,\n                logException=err)\n    return team\n\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_threads/_team.py",
    "content": "# -*- test-case-name: twisted._threads.test.test_team -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nImplementation of a L{Team} of workers; a thread-pool that can allocate work to\nworkers.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom collections import deque\nfrom zope.interface import implementer\n\nfrom . import IWorker\nfrom ._convenience import Quit\n\n\n\nclass Statistics(object):\n    \"\"\"\n    Statistics about a L{Team}'s current activity.\n\n    @ivar idleWorkerCount: The number of idle workers.\n    @type idleWorkerCount: L{int}\n\n    @ivar busyWorkerCount: The number of busy workers.\n    @type busyWorkerCount: L{int}\n\n    @ivar backloggedWorkCount: The number of work items passed to L{Team.do}\n        which have not yet been sent to a worker to be performed because not\n        enough workers are available.\n    @type backloggedWorkCount: L{int}\n    \"\"\"\n\n    def __init__(self, idleWorkerCount, busyWorkerCount,\n                 backloggedWorkCount):\n        self.idleWorkerCount = idleWorkerCount\n        self.busyWorkerCount = busyWorkerCount\n        self.backloggedWorkCount = backloggedWorkCount\n\n\n\n@implementer(IWorker)\nclass Team(object):\n    \"\"\"\n    A composite L{IWorker} implementation.\n\n    @ivar _quit: A L{Quit} flag indicating whether this L{Team} has been quit\n        yet.  This may be set by an arbitrary thread since L{Team.quit} may be\n        called from anywhere.\n\n    @ivar _coordinator: the L{IExclusiveWorker} coordinating access to this\n        L{Team}'s internal resources.\n\n    @ivar _createWorker: a callable that will create new workers.\n\n    @ivar _logException: a 0-argument callable called in an exception context\n        when there is an unhandled error from a task passed to L{Team.do}\n\n    @ivar _idle: a L{set} of idle workers.\n\n    @ivar _busyCount: the number of workers currently busy.\n\n    @ivar _pending: a C{deque} of tasks - that is, 0-argument callables passed\n        to L{Team.do} - that are outstanding.\n\n    @ivar _shouldQuitCoordinator: A flag indicating that the coordinator should\n        be quit at the next available opportunity.  Unlike L{Team._quit}, this\n        flag is only set by the coordinator.\n\n    @ivar _toShrink: the number of workers to shrink this L{Team} by at the\n        next available opportunity; set in the coordinator.\n    \"\"\"\n\n    def __init__(self, coordinator, createWorker, logException):\n        \"\"\"\n        @param coordinator: an L{IExclusiveWorker} which will coordinate access\n            to resources on this L{Team}; that is to say, an\n            L{IExclusiveWorker} whose C{do} method ensures that its given work\n            will be executed in a mutually exclusive context, not in parallel\n            with other work enqueued by C{do} (although possibly in parallel\n            with the caller).\n\n        @param createWorker: A 0-argument callable that will create an\n            L{IWorker} to perform work.\n\n        @param logException: A 0-argument callable called in an exception\n            context when the work passed to C{do} raises an exception.\n        \"\"\"\n        self._quit = Quit()\n        self._coordinator = coordinator\n        self._createWorker = createWorker\n        self._logException = logException\n\n        # Don't touch these except from the coordinator.\n        self._idle = set()\n        self._busyCount = 0\n        self._pending = deque()\n        self._shouldQuitCoordinator = False\n        self._toShrink = 0\n\n\n    def statistics(self):\n        \"\"\"\n        Gather information on the current status of this L{Team}.\n\n        @return: a L{Statistics} describing the current state of this L{Team}.\n        \"\"\"\n        return Statistics(len(self._idle), self._busyCount, len(self._pending))\n\n\n    def grow(self, n):\n        \"\"\"\n        Increase the the number of idle workers by C{n}.\n\n        @param n: The number of new idle workers to create.\n        @type n: L{int}\n        \"\"\"\n        self._quit.check()\n        @self._coordinator.do\n        def createOneWorker():\n            for x in range(n):\n                worker = self._createWorker()\n                if worker is None:\n                    return\n                self._recycleWorker(worker)\n\n\n    def shrink(self, n=None):\n        \"\"\"\n        Decrease the number of idle workers by C{n}.\n\n        @param n: The number of idle workers to shut down, or L{None} (or\n            unspecified) to shut down all workers.\n        @type n: L{int} or L{None}\n        \"\"\"\n        self._quit.check()\n        self._coordinator.do(lambda: self._quitIdlers(n))\n\n\n    def _quitIdlers(self, n=None):\n        \"\"\"\n        The implmentation of C{shrink}, performed by the coordinator worker.\n\n        @param n: see L{Team.shrink}\n        \"\"\"\n        if n is None:\n            n = len(self._idle) + self._busyCount\n        for x in range(n):\n            if self._idle:\n                self._idle.pop().quit()\n            else:\n                self._toShrink += 1\n        if self._shouldQuitCoordinator and self._busyCount == 0:\n            self._coordinator.quit()\n\n\n    def do(self, task):\n        \"\"\"\n        Perform some work in a worker created by C{createWorker}.\n\n        @param task: the callable to run\n        \"\"\"\n        self._quit.check()\n        self._coordinator.do(lambda: self._coordinateThisTask(task))\n\n\n    def _coordinateThisTask(self, task):\n        \"\"\"\n        Select a worker to dispatch to, either an idle one or a new one, and\n        perform it.\n\n        This method should run on the coordinator worker.\n\n        @param task: the task to dispatch\n        @type task: 0-argument callable\n        \"\"\"\n        worker = (self._idle.pop() if self._idle\n                  else self._createWorker())\n        if worker is None:\n            # The createWorker method may return None if we're out of resources\n            # to create workers.\n            self._pending.append(task)\n            return\n        self._busyCount += 1\n        @worker.do\n        def doWork():\n            try:\n                task()\n            except:\n                self._logException()\n\n            @self._coordinator.do\n            def idleAndPending():\n                self._busyCount -= 1\n                self._recycleWorker(worker)\n\n\n    def _recycleWorker(self, worker):\n        \"\"\"\n        Called only from coordinator.\n\n        Recycle the given worker into the idle pool.\n\n        @param worker: a worker created by C{createWorker} and now idle.\n        @type worker: L{IWorker}\n        \"\"\"\n        self._idle.add(worker)\n        if self._pending:\n            # Re-try the first enqueued thing.\n            # (Explicitly do _not_ honor _quit.)\n            self._coordinateThisTask(self._pending.popleft())\n        elif self._shouldQuitCoordinator:\n            self._quitIdlers()\n        elif self._toShrink > 0:\n            self._toShrink -= 1\n            self._idle.remove(worker)\n            worker.quit()\n\n\n    def quit(self):\n        \"\"\"\n        Stop doing work and shut down all idle workers.\n        \"\"\"\n        self._quit.set()\n        # In case all the workers are idle when we do this.\n        @self._coordinator.do\n        def startFinishing():\n            self._shouldQuitCoordinator = True\n            self._quitIdlers()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_threads/_threadworker.py",
    "content": "# -*- test-case-name: twisted._threads.test.test_threadworker -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nImplementation of an L{IWorker} based on native threads and queues.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom zope.interface import implementer\nfrom ._ithreads import IExclusiveWorker\nfrom ._convenience import Quit\n\n\n_stop = object()\n\n@implementer(IExclusiveWorker)\nclass ThreadWorker(object):\n    \"\"\"\n    An L{IExclusiveWorker} implemented based on a single thread and a queue.\n\n    This worker ensures exclusivity (i.e. it is an L{IExclusiveWorker} and not\n    an L{IWorker}) by performing all of the work passed to C{do} on the I{same}\n    thread.\n    \"\"\"\n\n    def __init__(self, startThread, queue):\n        \"\"\"\n        Create a L{ThreadWorker} with a function to start a thread and a queue\n        to use to communicate with that thread.\n\n        @param startThread: a callable that takes a callable to run in another\n            thread.\n        @type startThread: callable taking a 0-argument callable and returning\n            nothing.\n\n        @param queue: A L{Queue} to use to give tasks to the thread created by\n            C{startThread}.\n        @param queue: L{Queue}\n        \"\"\"\n        self._q = queue\n        self._hasQuit = Quit()\n        def work():\n            for task in iter(queue.get, _stop):\n                task()\n        startThread(work)\n\n\n    def do(self, task):\n        \"\"\"\n        Perform the given task on the thread owned by this L{ThreadWorker}.\n\n        @param task: the function to call on a thread.\n        \"\"\"\n        self._hasQuit.check()\n        self._q.put(task)\n\n\n    def quit(self):\n        \"\"\"\n        Reject all future work and stop the thread started by C{__init__}.\n        \"\"\"\n        # Reject all future work.  Set this _before_ enqueueing _stop, so\n        # that no work is ever enqueued _after_ _stop.\n        self._hasQuit.set()\n        self._q.put(_stop)\n\n\n\n@implementer(IExclusiveWorker)\nclass LockWorker(object):\n    \"\"\"\n    An L{IWorker} implemented based on a mutual-exclusion lock.\n    \"\"\"\n\n    def __init__(self, lock, local):\n        \"\"\"\n        @param lock: A mutual-exclusion lock, with C{acquire} and C{release}\n            methods.\n        @type lock: L{threading.Lock}\n\n        @param local: Local storage.\n        @type local: L{threading.local}\n        \"\"\"\n        self._quit = Quit()\n        self._lock = lock\n        self._local = local\n\n\n    def do(self, work):\n        \"\"\"\n        Do the given work on this thread, with the mutex acquired.  If this is\n        called re-entrantly, return and wait for the outer invocation to do the\n        work.\n\n        @param work: the work to do with the lock held.\n        \"\"\"\n        lock = self._lock\n        local = self._local\n        self._quit.check()\n        working = getattr(local, \"working\", None)\n        if working is None:\n            working = local.working = []\n            working.append(work)\n            lock.acquire()\n            try:\n                while working:\n                    working.pop(0)()\n            finally:\n                lock.release()\n                local.working = None\n        else:\n            working.append(work)\n\n\n    def quit(self):\n        \"\"\"\n        Quit this L{LockWorker}.\n        \"\"\"\n        self._quit.set()\n        self._lock = None\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_threads/test/__init__.py",
    "content": "# -*- test-case-name: twisted._threads.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted._threads}.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_threads/test/test_convenience.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for convenience functionality in L{twisted._threads._convenience}.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom twisted.trial.unittest import SynchronousTestCase\n\nfrom .._convenience import Quit\nfrom .._ithreads import AlreadyQuit\n\n\nclass QuitTests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{Quit}\n    \"\"\"\n\n    def test_isInitiallySet(self):\n        \"\"\"\n        L{Quit.isSet} starts as L{False}.\n        \"\"\"\n        quit = Quit()\n        self.assertEqual(quit.isSet, False)\n\n\n    def test_setSetsSet(self):\n        \"\"\"\n        L{Quit.set} sets L{Quit.isSet} to L{True}.\n        \"\"\"\n        quit = Quit()\n        quit.set()\n        self.assertEqual(quit.isSet, True)\n\n\n    def test_checkDoesNothing(self):\n        \"\"\"\n        L{Quit.check} initially does nothing and returns L{None}.\n        \"\"\"\n        quit = Quit()\n        self.assertIs(quit.check(), None)\n\n\n    def test_checkAfterSetRaises(self):\n        \"\"\"\n        L{Quit.check} raises L{AlreadyQuit} if L{Quit.set} has been called.\n        \"\"\"\n        quit = Quit()\n        quit.set()\n        self.assertRaises(AlreadyQuit, quit.check)\n\n\n    def test_setTwiceRaises(self):\n        \"\"\"\n        L{Quit.set} raises L{AlreadyQuit} if it has been called previously.\n        \"\"\"\n        quit = Quit()\n        quit.set()\n        self.assertRaises(AlreadyQuit, quit.set)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_threads/test/test_memory.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted._threads._memory}.\n\"\"\"\nfrom __future__ import absolute_import, division, print_function\n\nfrom zope.interface.verify import verifyObject\n\nfrom twisted.trial.unittest import SynchronousTestCase\nfrom .. import AlreadyQuit, IWorker, createMemoryWorker\n\n\nclass MemoryWorkerTests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{MemoryWorker}.\n    \"\"\"\n\n    def test_createWorkerAndPerform(self):\n        \"\"\"\n        L{createMemoryWorker} creates an L{IWorker} and a callable that can\n        perform work on it.  The performer returns C{True} if it accomplished\n        useful work.\n        \"\"\"\n        worker, performer = createMemoryWorker()\n        verifyObject(IWorker, worker)\n        done = []\n        worker.do(lambda: done.append(3))\n        worker.do(lambda: done.append(4))\n        self.assertEqual(done, [])\n        self.assertEqual(performer(), True)\n        self.assertEqual(done, [3])\n        self.assertEqual(performer(), True)\n        self.assertEqual(done, [3, 4])\n\n\n    def test_quitQuits(self):\n        \"\"\"\n        Calling C{quit} on the worker returned by L{createMemoryWorker} causes\n        its C{do} and C{quit} methods to raise L{AlreadyQuit}; its C{perform}\n        callable will start raising L{AlreadyQuit} when the work already\n        provided to C{do} has been exhausted.\n        \"\"\"\n        worker, performer = createMemoryWorker()\n        done = []\n        def moreWork():\n            done.append(7)\n        worker.do(moreWork)\n        worker.quit()\n        self.assertRaises(AlreadyQuit, worker.do, moreWork)\n        self.assertRaises(AlreadyQuit, worker.quit)\n        performer()\n        self.assertEqual(done, [7])\n        self.assertEqual(performer(), False)\n\n\n    def test_performWhenNothingToDoYet(self):\n        \"\"\"\n        The C{perform} callable returned by L{createMemoryWorker} will return\n        no result when there's no work to do yet.  Since there is no work to\n        do, the performer returns C{False}.\n        \"\"\"\n        worker, performer = createMemoryWorker()\n        self.assertEqual(performer(), False)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_threads/test/test_team.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted._threads._team}.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nfrom twisted.trial.unittest import SynchronousTestCase\n\nfrom twisted.python.context import call, get\nfrom twisted.python.components import proxyForInterface\n\nfrom twisted.python.failure import Failure\nfrom .. import IWorker, Team, createMemoryWorker, AlreadyQuit\n\nclass ContextualWorker(proxyForInterface(IWorker, \"_realWorker\")):\n    \"\"\"\n    A worker implementation that supplies a context.\n    \"\"\"\n\n    def __init__(self, realWorker, **ctx):\n        \"\"\"\n        Create with a real worker and a context.\n        \"\"\"\n        self._realWorker = realWorker\n        self._context = ctx\n\n\n    def do(self, work):\n        \"\"\"\n        Perform the given work with the context given to __init__.\n\n        @param work: the work to pass on to the real worker.\n        \"\"\"\n        super(ContextualWorker, self).do(lambda: call(self._context, work))\n\n\n\nclass TeamTests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{Team}\n    \"\"\"\n\n    def setUp(self):\n        \"\"\"\n        Set up a L{Team} with inspectable, synchronous workers that can be\n        single-stepped.\n        \"\"\"\n        coordinator, self.coordinateOnce = createMemoryWorker()\n        self.coordinator = ContextualWorker(coordinator, worker=\"coordinator\")\n        self.workerPerformers = []\n        self.allWorkersEver = []\n        self.allUnquitWorkers = []\n        self.activePerformers = []\n        self.noMoreWorkers = lambda: False\n\n        def createWorker():\n            if self.noMoreWorkers():\n                return None\n            worker, performer = createMemoryWorker()\n            self.workerPerformers.append(performer)\n            self.activePerformers.append(performer)\n            cw = ContextualWorker(worker, worker=len(self.workerPerformers))\n            self.allWorkersEver.append(cw)\n            self.allUnquitWorkers.append(cw)\n            realQuit = cw.quit\n            def quitAndRemove():\n                realQuit()\n                self.allUnquitWorkers.remove(cw)\n                self.activePerformers.remove(performer)\n            cw.quit = quitAndRemove\n            return cw\n\n        self.failures = []\n        def logException():\n            self.failures.append(Failure())\n        self.team = Team(coordinator, createWorker, logException)\n\n\n    def coordinate(self):\n        \"\"\"\n        Perform all work currently scheduled in the coordinator.\n\n        @return: whether any coordination work was performed; if the\n            coordinator was idle when this was called, return L{False}\n            (otherwise L{True}).\n        @rtype: L{bool}\n        \"\"\"\n        did = False\n        while self.coordinateOnce():\n            did = True\n        return did\n\n\n    def performAllOutstandingWork(self):\n        \"\"\"\n        Perform all work on the coordinator and worker performers that needs to\n        be done.\n        \"\"\"\n        continuing = True\n        while continuing:\n            continuing = self.coordinate()\n            for performer in self.workerPerformers:\n                if performer in self.activePerformers:\n                    performer()\n            continuing = continuing or self.coordinate()\n\n\n    def test_doDoesWorkInWorker(self):\n        \"\"\"\n        L{Team.do} does the work in a worker created by the createWorker\n        callable.\n        \"\"\"\n        def something():\n            something.who = get(\"worker\")\n        self.team.do(something)\n        self.coordinate()\n        self.assertEqual(self.team.statistics().busyWorkerCount, 1)\n        self.performAllOutstandingWork()\n        self.assertEqual(something.who, 1)\n        self.assertEqual(self.team.statistics().busyWorkerCount, 0)\n\n\n    def test_initialStatistics(self):\n        \"\"\"\n        L{Team.statistics} returns an object with idleWorkerCount,\n        busyWorkerCount, and backloggedWorkCount integer attributes.\n        \"\"\"\n        stats = self.team.statistics()\n        self.assertEqual(stats.idleWorkerCount, 0)\n        self.assertEqual(stats.busyWorkerCount, 0)\n        self.assertEqual(stats.backloggedWorkCount, 0)\n\n\n    def test_growCreatesIdleWorkers(self):\n        \"\"\"\n        L{Team.grow} increases the number of available idle workers.\n        \"\"\"\n        self.team.grow(5)\n        self.performAllOutstandingWork()\n        self.assertEqual(len(self.workerPerformers), 5)\n\n\n    def test_growCreateLimit(self):\n        \"\"\"\n        L{Team.grow} increases the number of available idle workers until the\n        C{createWorker} callable starts returning None.\n        \"\"\"\n        self.noMoreWorkers = lambda: len(self.allWorkersEver) >= 3\n        self.team.grow(5)\n        self.performAllOutstandingWork()\n        self.assertEqual(len(self.allWorkersEver), 3)\n        self.assertEqual(self.team.statistics().idleWorkerCount, 3)\n\n\n    def test_shrinkQuitsWorkers(self):\n        \"\"\"\n        L{Team.shrink} will quit the given number of workers.\n        \"\"\"\n        self.team.grow(5)\n        self.performAllOutstandingWork()\n        self.team.shrink(3)\n        self.performAllOutstandingWork()\n        self.assertEqual(len(self.allUnquitWorkers), 2)\n\n\n    def test_shrinkToZero(self):\n        \"\"\"\n        L{Team.shrink} with no arguments will stop all outstanding workers.\n        \"\"\"\n        self.team.grow(10)\n        self.performAllOutstandingWork()\n        self.assertEqual(len(self.allUnquitWorkers), 10)\n        self.team.shrink()\n        self.assertEqual(len(self.allUnquitWorkers), 10)\n        self.performAllOutstandingWork()\n        self.assertEqual(len(self.allUnquitWorkers), 0)\n\n\n    def test_moreWorkWhenNoWorkersAvailable(self):\n        \"\"\"\n        When no additional workers are available, the given work is backlogged,\n        and then performed later when the work was.\n        \"\"\"\n        self.team.grow(3)\n        self.coordinate()\n        def something():\n            something.times += 1\n        something.times = 0\n        self.assertEqual(self.team.statistics().idleWorkerCount, 3)\n        for i in range(3):\n            self.team.do(something)\n        # Make progress on the coordinator but do _not_ actually complete the\n        # work, yet.\n        self.coordinate()\n        self.assertEqual(self.team.statistics().idleWorkerCount, 0)\n        self.noMoreWorkers = lambda: True\n        self.team.do(something)\n        self.coordinate()\n        self.assertEqual(self.team.statistics().idleWorkerCount, 0)\n        self.assertEqual(self.team.statistics().backloggedWorkCount, 1)\n        self.performAllOutstandingWork()\n        self.assertEqual(self.team.statistics().backloggedWorkCount, 0)\n        self.assertEqual(something.times, 4)\n\n\n    def test_exceptionInTask(self):\n        \"\"\"\n        When an exception is raised in a task passed to L{Team.do}, the\n        C{logException} given to the L{Team} at construction is invoked in the\n        exception context.\n        \"\"\"\n        self.team.do(lambda: 1/0)\n        self.performAllOutstandingWork()\n        self.assertEqual(len(self.failures), 1)\n        self.assertEqual(self.failures[0].type, ZeroDivisionError)\n\n\n    def test_quit(self):\n        \"\"\"\n        L{Team.quit} causes future invocations of L{Team.do} and L{Team.quit}\n        to raise L{AlreadyQuit}.\n        \"\"\"\n        self.team.quit()\n        self.assertRaises(AlreadyQuit, self.team.quit)\n        self.assertRaises(AlreadyQuit, self.team.do, list)\n\n\n    def test_quitQuits(self):\n        \"\"\"\n        L{Team.quit} causes all idle workers, as well as the coordinator\n        worker, to quit.\n        \"\"\"\n        for x in range(10):\n            self.team.do(list)\n        self.performAllOutstandingWork()\n        self.team.quit()\n        self.performAllOutstandingWork()\n        self.assertEqual(len(self.allUnquitWorkers), 0)\n        self.assertRaises(AlreadyQuit, self.coordinator.quit)\n\n\n    def test_quitQuitsLaterWhenBusy(self):\n        \"\"\"\n        L{Team.quit} causes all busy workers to be quit once they've finished\n        the work they've been given.\n        \"\"\"\n        self.team.grow(10)\n        for x in range(5):\n            self.team.do(list)\n        self.coordinate()\n        self.team.quit()\n        self.coordinate()\n        self.assertEqual(len(self.allUnquitWorkers), 5)\n        self.performAllOutstandingWork()\n        self.assertEqual(len(self.allUnquitWorkers), 0)\n        self.assertRaises(AlreadyQuit, self.coordinator.quit)\n\n\n    def test_quitConcurrentWithWorkHappening(self):\n        \"\"\"\n        If work happens after L{Team.quit} sets its C{Quit} flag, but before\n        any other work takes place, the L{Team} should still exit gracefully.\n        \"\"\"\n        self.team.do(list)\n        originalSet = self.team._quit.set\n        def performWorkConcurrently():\n            originalSet()\n            self.performAllOutstandingWork()\n        self.team._quit.set = performWorkConcurrently\n        self.team.quit()\n        self.assertRaises(AlreadyQuit, self.team.quit)\n        self.assertRaises(AlreadyQuit, self.team.do, list)\n\n\n    def test_shrinkWhenBusy(self):\n        \"\"\"\n        L{Team.shrink} will wait for busy workers to finish being busy and then\n        quit them.\n        \"\"\"\n        for x in range(10):\n            self.team.do(list)\n        self.coordinate()\n        self.assertEqual(len(self.allUnquitWorkers), 10)\n        # There should be 10 busy workers at this point.\n        self.team.shrink(7)\n        self.performAllOutstandingWork()\n        self.assertEqual(len(self.allUnquitWorkers), 3)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_threads/test/test_threadworker.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted._threads._threadworker}.\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nimport gc\nimport weakref\n\nfrom twisted.trial.unittest import SynchronousTestCase\nfrom threading import ThreadError, local\n\nfrom .. import ThreadWorker, LockWorker, AlreadyQuit\n\nclass FakeQueueEmpty(Exception):\n    \"\"\"\n    L{FakeQueue}'s C{get} has exhausted the queue.\n    \"\"\"\n\n\n\nclass WouldDeadlock(Exception):\n    \"\"\"\n    If this were a real lock, you'd be deadlocked because the lock would be\n    double-acquired.\n    \"\"\"\n\n\n\nclass FakeThread(object):\n    \"\"\"\n    A fake L{threading.Thread}.\n\n    @ivar target: A target function to run.\n    @type target: L{callable}\n\n    @ivar started: Has this thread been started?\n    @type started: L{bool}\n    \"\"\"\n\n    def __init__(self, target):\n        \"\"\"\n        Create a L{FakeThread} with a target.\n        \"\"\"\n        self.target = target\n        self.started = False\n\n\n    def start(self):\n        \"\"\"\n        Set the \"started\" flag.\n        \"\"\"\n        self.started = True\n\n\n\nclass FakeQueue(object):\n    \"\"\"\n    A fake L{Queue} implementing C{put} and C{get}.\n\n    @ivar items: A lit of items placed by C{put} but not yet retrieved by\n        C{get}.\n    @type items: L{list}\n    \"\"\"\n\n    def __init__(self):\n        \"\"\"\n        Create a L{FakeQueue}.\n        \"\"\"\n        self.items = []\n\n\n    def put(self, item):\n        \"\"\"\n        Put an item into the queue for later retrieval by L{FakeQueue.get}.\n\n        @param item: any object\n        \"\"\"\n        self.items.append(item)\n\n\n    def get(self):\n        \"\"\"\n        Get an item.\n\n        @return: an item previously put by C{put}.\n        \"\"\"\n        if not self.items:\n            raise FakeQueueEmpty()\n        return self.items.pop(0)\n\n\n\nclass FakeLock(object):\n    \"\"\"\n    A stand-in for L{threading.Lock}.\n\n    @ivar acquired: Whether this lock is presently acquired.\n    \"\"\"\n\n    def __init__(self):\n        \"\"\"\n        Create a lock in the un-acquired state.\n        \"\"\"\n        self.acquired = False\n\n\n    def acquire(self):\n        \"\"\"\n        Acquire the lock.  Raise an exception if the lock is already acquired.\n        \"\"\"\n        if self.acquired:\n            raise WouldDeadlock()\n        self.acquired = True\n\n\n    def release(self):\n        \"\"\"\n        Release the lock.  Raise an exception if the lock is not presently\n        acquired.\n        \"\"\"\n        if not self.acquired:\n            raise ThreadError()\n        self.acquired = False\n\n\n\nclass ThreadWorkerTests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{ThreadWorker}.\n    \"\"\"\n\n    def setUp(self):\n        \"\"\"\n        Create a worker with fake threads.\n        \"\"\"\n        self.fakeThreads = []\n        self.fakeQueue = FakeQueue()\n        def startThread(target):\n            newThread = FakeThread(target=target)\n            newThread.start()\n            self.fakeThreads.append(newThread)\n            return newThread\n        self.worker = ThreadWorker(startThread, self.fakeQueue)\n\n\n    def test_startsThreadAndPerformsWork(self):\n        \"\"\"\n        L{ThreadWorker} calls its C{createThread} callable to create a thread,\n        its C{createQueue} callable to create a queue, and then the thread's\n        target pulls work from that queue.\n        \"\"\"\n        self.assertEqual(len(self.fakeThreads), 1)\n        self.assertEqual(self.fakeThreads[0].started, True)\n        def doIt():\n            doIt.done = True\n        doIt.done = False\n        self.worker.do(doIt)\n        self.assertEqual(doIt.done, False)\n        self.assertRaises(FakeQueueEmpty, self.fakeThreads[0].target)\n        self.assertEqual(doIt.done, True)\n\n\n    def test_quitPreventsFutureCalls(self):\n        \"\"\"\n        L{ThreadWorker.quit} causes future calls to L{ThreadWorker.do} and\n        L{ThreadWorker.quit} to raise L{AlreadyQuit}.\n        \"\"\"\n        self.worker.quit()\n        self.assertRaises(AlreadyQuit, self.worker.quit)\n        self.assertRaises(AlreadyQuit, self.worker.do, list)\n\n\n\nclass LockWorkerTests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{LockWorker}.\n    \"\"\"\n\n    def test_fakeDeadlock(self):\n        \"\"\"\n        The L{FakeLock} test fixture will alert us if there's a potential\n        deadlock.\n        \"\"\"\n        lock = FakeLock()\n        lock.acquire()\n        self.assertRaises(WouldDeadlock, lock.acquire)\n\n\n    def test_fakeDoubleRelease(self):\n        \"\"\"\n        The L{FakeLock} test fixture will alert us if there's a potential\n        double-release.\n        \"\"\"\n        lock = FakeLock()\n        self.assertRaises(ThreadError, lock.release)\n        lock.acquire()\n        self.assertEqual(None, lock.release())\n        self.assertRaises(ThreadError, lock.release)\n\n\n    def test_doExecutesImmediatelyWithLock(self):\n        \"\"\"\n        L{LockWorker.do} immediately performs the work it's given, while the\n        lock is acquired.\n        \"\"\"\n        storage = local()\n        lock = FakeLock()\n        worker = LockWorker(lock, storage)\n        def work():\n            work.done = True\n            work.acquired = lock.acquired\n        work.done = False\n        worker.do(work)\n        self.assertEqual(work.done, True)\n        self.assertEqual(work.acquired, True)\n        self.assertEqual(lock.acquired, False)\n\n\n    def test_doUnwindsReentrancy(self):\n        \"\"\"\n        If L{LockWorker.do} is called recursively, it postpones the inner call\n        until the outer one is complete.\n        \"\"\"\n        lock = FakeLock()\n        worker = LockWorker(lock, local())\n        levels = []\n        acquired = []\n        def work():\n            work.level += 1\n            levels.append(work.level)\n            acquired.append(lock.acquired)\n            if len(levels) < 2:\n                worker.do(work)\n            work.level -= 1\n        work.level = 0\n        worker.do(work)\n        self.assertEqual(levels, [1, 1])\n        self.assertEqual(acquired, [True, True])\n\n\n    def test_quit(self):\n        \"\"\"\n        L{LockWorker.quit} frees the resources associated with its lock and\n        causes further calls to C{do} and C{quit} to fail.\n        \"\"\"\n        lock = FakeLock()\n        ref = weakref.ref(lock)\n        worker = LockWorker(lock, local())\n        lock = None\n        self.assertIsNot(ref(), None)\n        worker.quit()\n        gc.collect()\n        self.assertIs(ref(), None)\n        self.assertRaises(AlreadyQuit, worker.quit)\n        self.assertRaises(AlreadyQuit, worker.do, list)\n\n\n    def test_quitWhileWorking(self):\n        \"\"\"\n        If L{LockWorker.quit} is invoked during a call to L{LockWorker.do}, all\n        recursive work scheduled with L{LockWorker.do} will be completed and\n        the lock will be released.\n        \"\"\"\n        lock = FakeLock()\n        ref = weakref.ref(lock)\n        worker = LockWorker(lock, local())\n\n        def phase1():\n            worker.do(phase2)\n            worker.quit()\n            self.assertRaises(AlreadyQuit, worker.do, list)\n            phase1.complete = True\n        phase1.complete = False\n        def phase2():\n            phase2.complete = True\n            phase2.acquired = lock.acquired\n        phase2.complete = False\n        worker.do(phase1)\n        self.assertEqual(phase1.complete, True)\n        self.assertEqual(phase2.complete, True)\n        self.assertEqual(lock.acquired, False)\n        lock = None\n        gc.collect()\n        self.assertIs(ref(), None)\n\n\n    def test_quitWhileGettingLock(self):\n        \"\"\"\n        If L{LockWorker.do} is called concurrently with L{LockWorker.quit}, and\n        C{quit} wins the race before C{do} gets the lock attribute, then\n        L{AlreadyQuit} will be raised.\n        \"\"\"\n        class RacyLockWorker(LockWorker):\n            def _lock_get(self):\n                self.quit()\n                return self.__dict__['_lock']\n            def _lock_set(self, value):\n                self.__dict__['_lock'] = value\n\n            _lock = property(_lock_get, _lock_set)\n\n        worker = RacyLockWorker(FakeLock(), local())\n        self.assertRaises(AlreadyQuit, worker.do, list)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/_version.py",
    "content": "\"\"\"\nProvides Twisted version information.\n\"\"\"\n\n# This file is auto-generated! Do not edit!\n# Use `python -m incremental.update Twisted` to change this file.\n\nfrom incremental import Version\n\n__version__ = Version('Twisted', 19, 7, 0)\n__all__ = [\"__version__\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nConfiguration objects for Twisted Applications.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/app.py",
    "content": "# -*- test-case-name: twisted.test.test_application,twisted.test.test_twistd -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom __future__ import absolute_import, division, print_function\n\nimport sys\nimport os\nimport pdb\nimport getpass\nimport traceback\nimport signal\nimport warnings\n\nfrom operator import attrgetter\n\nfrom twisted import copyright, plugin, logger\nfrom twisted.application import service, reactors\nfrom twisted.internet import defer\nfrom twisted.persisted import sob\nfrom twisted.python import runtime, log, usage, failure, util, logfile\nfrom twisted.python._oldstyle import _oldStyle\nfrom twisted.python.reflect import (qual, namedAny, namedModule)\nfrom twisted.internet.interfaces import _ISupportsExitSignalCapturing\n\n# Expose the new implementation of installReactor at the old location.\nfrom twisted.application.reactors import installReactor\nfrom twisted.application.reactors import NoSuchReactor\n\n\nclass _BasicProfiler(object):\n    \"\"\"\n    @ivar saveStats: if C{True}, save the stats information instead of the\n        human readable format\n    @type saveStats: C{bool}\n\n    @ivar profileOutput: the name of the file use to print profile data.\n    @type profileOutput: C{str}\n    \"\"\"\n\n    def __init__(self, profileOutput, saveStats):\n        self.profileOutput = profileOutput\n        self.saveStats = saveStats\n\n\n    def _reportImportError(self, module, e):\n        \"\"\"\n        Helper method to report an import error with a profile module. This\n        has to be explicit because some of these modules are removed by\n        distributions due to them being non-free.\n        \"\"\"\n        s = \"Failed to import module %s: %s\" % (module, e)\n        s += \"\"\"\nThis is most likely caused by your operating system not including\nthe module due to it being non-free. Either do not use the option\n--profile, or install the module; your operating system vendor\nmay provide it in a separate package.\n\"\"\"\n        raise SystemExit(s)\n\n\n\nclass ProfileRunner(_BasicProfiler):\n    \"\"\"\n    Runner for the standard profile module.\n    \"\"\"\n\n    def run(self, reactor):\n        \"\"\"\n        Run reactor under the standard profiler.\n        \"\"\"\n        try:\n            import profile\n        except ImportError as e:\n            self._reportImportError(\"profile\", e)\n\n        p = profile.Profile()\n        p.runcall(reactor.run)\n        if self.saveStats:\n            p.dump_stats(self.profileOutput)\n        else:\n            tmp, sys.stdout = sys.stdout, open(self.profileOutput, 'a')\n            try:\n                p.print_stats()\n            finally:\n                sys.stdout, tmp = tmp, sys.stdout\n                tmp.close()\n\n\n\nclass CProfileRunner(_BasicProfiler):\n    \"\"\"\n    Runner for the cProfile module.\n    \"\"\"\n\n    def run(self, reactor):\n        \"\"\"\n        Run reactor under the cProfile profiler.\n        \"\"\"\n        try:\n            import cProfile\n            import pstats\n        except ImportError as e:\n            self._reportImportError(\"cProfile\", e)\n\n        p = cProfile.Profile()\n        p.runcall(reactor.run)\n        if self.saveStats:\n            p.dump_stats(self.profileOutput)\n        else:\n            with open(self.profileOutput, 'w') as stream:\n                s = pstats.Stats(p, stream=stream)\n                s.strip_dirs()\n                s.sort_stats(-1)\n                s.print_stats()\n\n\n\nclass AppProfiler(object):\n    \"\"\"\n    Class which selects a specific profile runner based on configuration\n    options.\n\n    @ivar profiler: the name of the selected profiler.\n    @type profiler: C{str}\n    \"\"\"\n    profilers = {\"profile\": ProfileRunner, \"cprofile\": CProfileRunner}\n\n    def __init__(self, options):\n        saveStats = options.get(\"savestats\", False)\n        profileOutput = options.get(\"profile\", None)\n        self.profiler = options.get(\"profiler\", \"cprofile\").lower()\n        if self.profiler in self.profilers:\n            profiler = self.profilers[self.profiler](profileOutput, saveStats)\n            self.run = profiler.run\n        else:\n            raise SystemExit(\"Unsupported profiler name: %s\" %\n                             (self.profiler,))\n\n\n\nclass AppLogger(object):\n    \"\"\"\n    An L{AppLogger} attaches the configured log observer specified on the\n    commandline to a L{ServerOptions} object, a custom L{logger.ILogObserver},\n    or a legacy custom {log.ILogObserver}.\n\n    @ivar _logfilename: The name of the file to which to log, if other than the\n        default.\n    @type _logfilename: C{str}\n\n    @ivar _observerFactory: Callable object that will create a log observer, or\n        None.\n\n    @ivar _observer: log observer added at C{start} and removed at C{stop}.\n    @type _observer: a callable that implements L{logger.ILogObserver} or\n        L{log.ILogObserver}.\n    \"\"\"\n    _observer = None\n\n    def __init__(self, options):\n        \"\"\"\n        Initialize an L{AppLogger} with a L{ServerOptions}.\n        \"\"\"\n        self._logfilename = options.get(\"logfile\", \"\")\n        self._observerFactory = options.get(\"logger\") or None\n\n\n    def start(self, application):\n        \"\"\"\n        Initialize the global logging system for the given application.\n\n        If a custom logger was specified on the command line it will be used.\n        If not, and an L{logger.ILogObserver} or legacy L{log.ILogObserver}\n        component has been set on C{application}, then it will be used as the\n        log observer. Otherwise a log observer will be created based on the\n        command line options for built-in loggers (e.g. C{--logfile}).\n\n        @param application: The application on which to check for an\n            L{logger.ILogObserver} or legacy L{log.ILogObserver}.\n        @type application: L{twisted.python.components.Componentized}\n        \"\"\"\n        if self._observerFactory is not None:\n            observer = self._observerFactory()\n        else:\n            observer = application.getComponent(logger.ILogObserver, None)\n            if observer is None:\n                # If there's no new ILogObserver, try the legacy one\n                observer = application.getComponent(log.ILogObserver, None)\n\n        if observer is None:\n            observer = self._getLogObserver()\n        self._observer = observer\n\n        if logger.ILogObserver.providedBy(self._observer):\n            observers = [self._observer]\n        elif log.ILogObserver.providedBy(self._observer):\n            observers = [logger.LegacyLogObserverWrapper(self._observer)]\n        else:\n            warnings.warn(\n                (\"Passing a logger factory which makes log observers which do \"\n                 \"not implement twisted.logger.ILogObserver or \"\n                 \"twisted.python.log.ILogObserver to \"\n                 \"twisted.application.app.AppLogger was deprecated in \"\n                 \"Twisted 16.2. Please use a factory that produces \"\n                 \"twisted.logger.ILogObserver (or the legacy \"\n                 \"twisted.python.log.ILogObserver) implementing objects \"\n                 \"instead.\"),\n                DeprecationWarning,\n                stacklevel=2)\n            observers = [logger.LegacyLogObserverWrapper(self._observer)]\n\n        logger.globalLogBeginner.beginLoggingTo(observers)\n        self._initialLog()\n\n\n    def _initialLog(self):\n        \"\"\"\n        Print twistd start log message.\n        \"\"\"\n        from twisted.internet import reactor\n        logger._loggerFor(self).info(\n            \"twistd {version} ({exe} {pyVersion}) starting up.\",\n            version=copyright.version, exe=sys.executable,\n            pyVersion=runtime.shortPythonVersion())\n        logger._loggerFor(self).info('reactor class: {reactor}.',\n                                     reactor=qual(reactor.__class__))\n\n\n    def _getLogObserver(self):\n        \"\"\"\n        Create a log observer to be added to the logging system before running\n        this application.\n        \"\"\"\n        if self._logfilename == '-' or not self._logfilename:\n            logFile = sys.stdout\n        else:\n            logFile = logfile.LogFile.fromFullPath(self._logfilename)\n        return logger.textFileLogObserver(logFile)\n\n\n    def stop(self):\n        \"\"\"\n        Remove all log observers previously set up by L{AppLogger.start}.\n        \"\"\"\n        logger._loggerFor(self).info(\"Server Shut Down.\")\n        if self._observer is not None:\n            logger.globalLogPublisher.removeObserver(self._observer)\n            self._observer = None\n\n\n\ndef fixPdb():\n    def do_stop(self, arg):\n        self.clear_all_breaks()\n        self.set_continue()\n        from twisted.internet import reactor\n        reactor.callLater(0, reactor.stop)\n        return 1\n\n\n    def help_stop(self):\n        print(\"stop - Continue execution, then cleanly shutdown the twisted \"\n              \"reactor.\")\n\n\n    def set_quit(self):\n        os._exit(0)\n\n    pdb.Pdb.set_quit = set_quit\n    pdb.Pdb.do_stop = do_stop\n    pdb.Pdb.help_stop = help_stop\n\n\n\ndef runReactorWithLogging(config, oldstdout, oldstderr, profiler=None,\n                          reactor=None):\n    \"\"\"\n    Start the reactor, using profiling if specified by the configuration, and\n    log any error happening in the process.\n\n    @param config: configuration of the twistd application.\n    @type config: L{ServerOptions}\n\n    @param oldstdout: initial value of C{sys.stdout}.\n    @type oldstdout: C{file}\n\n    @param oldstderr: initial value of C{sys.stderr}.\n    @type oldstderr: C{file}\n\n    @param profiler: object used to run the reactor with profiling.\n    @type profiler: L{AppProfiler}\n\n    @param reactor: The reactor to use.  If L{None}, the global reactor will\n        be used.\n    \"\"\"\n    if reactor is None:\n        from twisted.internet import reactor\n    try:\n        if config['profile']:\n            if profiler is not None:\n                profiler.run(reactor)\n        elif config['debug']:\n            sys.stdout = oldstdout\n            sys.stderr = oldstderr\n            if runtime.platformType == 'posix':\n                signal.signal(signal.SIGUSR2, lambda *args: pdb.set_trace())\n                signal.signal(signal.SIGINT, lambda *args: pdb.set_trace())\n            fixPdb()\n            pdb.runcall(reactor.run)\n        else:\n            reactor.run()\n    except:\n        close = False\n        if config['nodaemon']:\n            file = oldstdout\n        else:\n            file = open(\"TWISTD-CRASH.log\", \"a\")\n            close = True\n        try:\n            traceback.print_exc(file=file)\n            file.flush()\n        finally:\n            if close:\n                file.close()\n\n\n\ndef getPassphrase(needed):\n    if needed:\n        return getpass.getpass('Passphrase: ')\n    else:\n        return None\n\n\n\ndef getSavePassphrase(needed):\n    if needed:\n        return util.getPassword(\"Encryption passphrase: \")\n    else:\n        return None\n\n\n\nclass ApplicationRunner(object):\n    \"\"\"\n    An object which helps running an application based on a config object.\n\n    Subclass me and implement preApplication and postApplication\n    methods. postApplication generally will want to run the reactor\n    after starting the application.\n\n    @ivar config: The config object, which provides a dict-like interface.\n\n    @ivar application: Available in postApplication, but not\n       preApplication. This is the application object.\n\n    @ivar profilerFactory: Factory for creating a profiler object, able to\n        profile the application if options are set accordingly.\n\n    @ivar profiler: Instance provided by C{profilerFactory}.\n\n    @ivar loggerFactory: Factory for creating object responsible for logging.\n\n    @ivar logger: Instance provided by C{loggerFactory}.\n    \"\"\"\n    profilerFactory = AppProfiler\n    loggerFactory = AppLogger\n\n    def __init__(self, config):\n        self.config = config\n        self.profiler = self.profilerFactory(config)\n        self.logger = self.loggerFactory(config)\n\n\n    def run(self):\n        \"\"\"\n        Run the application.\n        \"\"\"\n        self.preApplication()\n        self.application = self.createOrGetApplication()\n\n        self.logger.start(self.application)\n\n        self.postApplication()\n        self.logger.stop()\n\n\n    def startReactor(self, reactor, oldstdout, oldstderr):\n        \"\"\"\n        Run the reactor with the given configuration.  Subclasses should\n        probably call this from C{postApplication}.\n\n        @see: L{runReactorWithLogging}\n        \"\"\"\n        if reactor is None:\n            from twisted.internet import reactor\n        runReactorWithLogging(\n            self.config, oldstdout, oldstderr, self.profiler, reactor)\n\n        if _ISupportsExitSignalCapturing.providedBy(reactor):\n            self._exitSignal = reactor._exitSignal\n        else:\n            self._exitSignal = None\n\n\n    def preApplication(self):\n        \"\"\"\n        Override in subclass.\n\n        This should set up any state necessary before loading and\n        running the Application.\n        \"\"\"\n        raise NotImplementedError()\n\n\n    def postApplication(self):\n        \"\"\"\n        Override in subclass.\n\n        This will be called after the application has been loaded (so\n        the C{application} attribute will be set). Generally this\n        should start the application and run the reactor.\n        \"\"\"\n        raise NotImplementedError()\n\n\n    def createOrGetApplication(self):\n        \"\"\"\n        Create or load an Application based on the parameters found in the\n        given L{ServerOptions} instance.\n\n        If a subcommand was used, the L{service.IServiceMaker} that it\n        represents will be used to construct a service to be added to\n        a newly-created Application.\n\n        Otherwise, an application will be loaded based on parameters in\n        the config.\n        \"\"\"\n        if self.config.subCommand:\n            # If a subcommand was given, it's our responsibility to create\n            # the application, instead of load it from a file.\n\n            # loadedPlugins is set up by the ServerOptions.subCommands\n            # property, which is iterated somewhere in the bowels of\n            # usage.Options.\n            plg = self.config.loadedPlugins[self.config.subCommand]\n            ser = plg.makeService(self.config.subOptions)\n            application = service.Application(plg.tapname)\n            ser.setServiceParent(application)\n        else:\n            passphrase = getPassphrase(self.config['encrypted'])\n            application = getApplication(self.config, passphrase)\n        return application\n\n\n\ndef getApplication(config, passphrase):\n    s = [(config[t], t)\n         for t in ['python', 'source', 'file'] if config[t]][0]\n    filename, style = s[0], {'file': 'pickle'}.get(s[1], s[1])\n    try:\n        log.msg(\"Loading %s...\" % filename)\n        application = service.loadApplication(filename, style, passphrase)\n        log.msg(\"Loaded.\")\n    except Exception as e:\n        s = \"Failed to load application: %s\" % e\n        if isinstance(e, KeyError) and e.args[0] == \"application\":\n            s += \"\"\"\nCould not find 'application' in the file. To use 'twistd -y', your .tac\nfile must create a suitable object (e.g., by calling service.Application())\nand store it in a variable named 'application'. twistd loads your .tac file\nand scans the global variables for one of this name.\n\nPlease read the 'Using Application' HOWTO for details.\n\"\"\"\n        traceback.print_exc(file=log.logfile)\n        log.msg(s)\n        log.deferr()\n        sys.exit('\\n' + s + '\\n')\n    return application\n\n\n\ndef _reactorAction():\n    return usage.CompleteList([r.shortName for r in\n                               reactors.getReactorTypes()])\n\n\n\n@_oldStyle\nclass ReactorSelectionMixin:\n    \"\"\"\n    Provides options for selecting a reactor to install.\n\n    If a reactor is installed, the short name which was used to locate it is\n    saved as the value for the C{\"reactor\"} key.\n    \"\"\"\n    compData = usage.Completions(\n        optActions={\"reactor\": _reactorAction})\n\n    messageOutput = sys.stdout\n    _getReactorTypes = staticmethod(reactors.getReactorTypes)\n\n\n    def opt_help_reactors(self):\n        \"\"\"\n        Display a list of possibly available reactor names.\n        \"\"\"\n        rcts = sorted(self._getReactorTypes(), key=attrgetter('shortName'))\n        notWorkingReactors = \"\"\n        for r in rcts:\n            try:\n                namedModule(r.moduleName)\n                self.messageOutput.write('    %-4s\\t%s\\n' %\n                                         (r.shortName, r.description))\n            except ImportError as e:\n                notWorkingReactors += ('    !%-4s\\t%s (%s)\\n' %\n                                       (r.shortName, r.description, e.args[0]))\n\n        if notWorkingReactors:\n            self.messageOutput.write('\\n')\n            self.messageOutput.write('    reactors not available '\n                                     'on this platform:\\n\\n')\n            self.messageOutput.write(notWorkingReactors)\n        raise SystemExit(0)\n\n\n    def opt_reactor(self, shortName):\n        \"\"\"\n        Which reactor to use (see --help-reactors for a list of possibilities)\n        \"\"\"\n        # Actually actually actually install the reactor right at this very\n        # moment, before any other code (for example, a sub-command plugin)\n        # runs and accidentally imports and installs the default reactor.\n        #\n        # This could probably be improved somehow.\n        try:\n            installReactor(shortName)\n        except NoSuchReactor:\n            msg = (\"The specified reactor does not exist: '%s'.\\n\"\n                   \"See the list of available reactors with \"\n                   \"--help-reactors\" % (shortName,))\n            raise usage.UsageError(msg)\n        except Exception as e:\n            msg = (\"The specified reactor cannot be used, failed with error: \"\n                   \"%s.\\nSee the list of available reactors with \"\n                   \"--help-reactors\" % (e,))\n            raise usage.UsageError(msg)\n        else:\n            self[\"reactor\"] = shortName\n    opt_r = opt_reactor\n\n\n\nclass ServerOptions(usage.Options, ReactorSelectionMixin):\n\n    longdesc = (\"twistd reads a twisted.application.service.Application out \"\n                \"of a file and runs it.\")\n\n    optFlags = [['savestats', None,\n                 \"save the Stats object rather than the text output of \"\n                 \"the profiler.\"],\n                ['no_save', 'o', \"do not save state on shutdown\"],\n                ['encrypted', 'e',\n                 \"The specified tap/aos file is encrypted.\"]]\n\n    optParameters = [['logfile', 'l', None,\n                      \"log to a specified file, - for stdout\"],\n                     ['logger', None, None,\n                      \"A fully-qualified name to a log observer factory to \"\n                      \"use for the initial log observer.  Takes precedence \"\n                      \"over --logfile and --syslog (when available).\"],\n                     ['profile', 'p', None,\n                      \"Run in profile mode, dumping results to specified \"\n                      \"file.\"],\n                     ['profiler', None, \"cprofile\",\n                      \"Name of the profiler to use (%s).\" %\n                      \", \".join(AppProfiler.profilers)],\n                     ['file', 'f', 'twistd.tap',\n                      \"read the given .tap file\"],\n                     ['python', 'y', None,\n                      \"read an application from within a Python file \"\n                      \"(implies -o)\"],\n                     ['source', 's', None,\n                      \"Read an application from a .tas file (AOT format).\"],\n                     ['rundir', 'd', '.',\n                      'Change to a supplied directory before running']]\n\n    compData = usage.Completions(\n        mutuallyExclusive=[(\"file\", \"python\", \"source\")],\n        optActions={\"file\": usage.CompleteFiles(\"*.tap\"),\n                    \"python\": usage.CompleteFiles(\"*.(tac|py)\"),\n                    \"source\": usage.CompleteFiles(\"*.tas\"),\n                    \"rundir\": usage.CompleteDirs()}\n    )\n\n    _getPlugins = staticmethod(plugin.getPlugins)\n\n    def __init__(self, *a, **kw):\n        self['debug'] = False\n        if 'stdout' in kw:\n            self.stdout = kw['stdout']\n        else:\n            self.stdout = sys.stdout\n        usage.Options.__init__(self)\n\n\n    def opt_debug(self):\n        \"\"\"\n        Run the application in the Python Debugger (implies nodaemon),\n        sending SIGUSR2 will drop into debugger\n        \"\"\"\n        defer.setDebugging(True)\n        failure.startDebugMode()\n        self['debug'] = True\n    opt_b = opt_debug\n\n\n    def opt_spew(self):\n        \"\"\"\n        Print an insanely verbose log of everything that happens.\n        Useful when debugging freezes or locks in complex code.\n        \"\"\"\n        sys.settrace(util.spewer)\n        try:\n            import threading\n        except ImportError:\n            return\n        threading.settrace(util.spewer)\n\n\n    def parseOptions(self, options=None):\n        if options is None:\n            options = sys.argv[1:] or [\"--help\"]\n        usage.Options.parseOptions(self, options)\n\n\n    def postOptions(self):\n        if self.subCommand or self['python']:\n            self['no_save'] = True\n        if self['logger'] is not None:\n            try:\n                self['logger'] = namedAny(self['logger'])\n            except Exception as e:\n                raise usage.UsageError(\"Logger '%s' could not be imported: %s\"\n                                       % (self['logger'], e))\n\n\n    def subCommands(self):\n        plugins = self._getPlugins(service.IServiceMaker)\n        self.loadedPlugins = {}\n        for plug in sorted(plugins, key=attrgetter('tapname')):\n            self.loadedPlugins[plug.tapname] = plug\n            yield (plug.tapname,\n                   None,\n                   # Avoid resolving the options attribute right away, in case\n                   # it's a property with a non-trivial getter (eg, one which\n                   # imports modules).\n                   lambda plug=plug: plug.options(),\n                   plug.description)\n    subCommands = property(subCommands)\n\n\n\ndef run(runApp, ServerOptions):\n    config = ServerOptions()\n    try:\n        config.parseOptions()\n    except usage.error as ue:\n        print(config)\n        print(\"%s: %s\" % (sys.argv[0], ue))\n    else:\n        runApp(config)\n\n\n\ndef convertStyle(filein, typein, passphrase, fileout, typeout, encrypt):\n    application = service.loadApplication(filein, typein, passphrase)\n    sob.IPersistable(application).setStyle(typeout)\n    passphrase = getSavePassphrase(encrypt)\n    if passphrase:\n        fileout = None\n    sob.IPersistable(application).save(filename=fileout, passphrase=passphrase)\n\n\n\ndef startApplication(application, save):\n    from twisted.internet import reactor\n    service.IService(application).startService()\n    if save:\n        p = sob.IPersistable(application)\n        reactor.addSystemEventTrigger('after', 'shutdown', p.save, 'shutdown')\n    reactor.addSystemEventTrigger('before', 'shutdown',\n                                  service.IService(application).stopService)\n\n\n\ndef _exitWithSignal(sig):\n    \"\"\"\n    Force the application to terminate with the specified signal by replacing\n    the signal handler with the default and sending the signal to ourselves.\n\n    @param sig:  Signal to use to terminate the process with C{os.kill}.\n    @type sig:  C{int}\n    \"\"\"\n    signal.signal(sig, signal.SIG_DFL)\n    os.kill(os.getpid(), sig)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/internet.py",
    "content": "# -*- test-case-name: twisted.application.test.test_internet,twisted.test.test_application,twisted.test.test_cooperator -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nReactor-based Services\n\nHere are services to run clients, servers and periodic services using\nthe reactor.\n\nIf you want to run a server service, L{StreamServerEndpointService} defines a\nservice that can wrap an arbitrary L{IStreamServerEndpoint\n<twisted.internet.interfaces.IStreamServerEndpoint>}\nas an L{IService}. See also L{twisted.application.strports.service} for\nconstructing one of these directly from a descriptive string.\n\nAdditionally, this module (dynamically) defines various Service subclasses that\nlet you represent clients and servers in a Service hierarchy.  Endpoints APIs\nshould be preferred for stream server services, but since those APIs do not yet\nexist for clients or datagram services, many of these are still useful.\n\nThey are as follows::\n\n  TCPServer, TCPClient,\n  UNIXServer, UNIXClient,\n  SSLServer, SSLClient,\n  UDPServer,\n  UNIXDatagramServer, UNIXDatagramClient,\n  MulticastServer\n\nThese classes take arbitrary arguments in their constructors and pass\nthem straight on to their respective reactor.listenXXX or\nreactor.connectXXX calls.\n\nFor example, the following service starts a web server on port 8080:\nC{TCPServer(8080, server.Site(r))}.  See the documentation for the\nreactor.listen/connect* methods for more information.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom random import random as _goodEnoughRandom\n\nfrom twisted.python import log\nfrom twisted.logger import Logger\n\nfrom twisted.application import service\nfrom twisted.internet import task\nfrom twisted.python.failure import Failure\nfrom twisted.internet.defer import (\n    CancelledError, Deferred, succeed, fail, maybeDeferred\n)\n\nfrom automat import MethodicalMachine\n\n\ndef _maybeGlobalReactor(maybeReactor):\n    \"\"\"\n    @return: the argument, or the global reactor if the argument is L{None}.\n    \"\"\"\n    if maybeReactor is None:\n        from twisted.internet import reactor\n        return reactor\n    else:\n        return maybeReactor\n\n\n\nclass _VolatileDataService(service.Service):\n\n    volatile = []\n\n    def __getstate__(self):\n        d = service.Service.__getstate__(self)\n        for attr in self.volatile:\n            if attr in d:\n                del d[attr]\n        return d\n\n\n\nclass _AbstractServer(_VolatileDataService):\n    \"\"\"\n    @cvar volatile: list of attribute to remove from pickling.\n    @type volatile: C{list}\n\n    @ivar method: the type of method to call on the reactor, one of B{TCP},\n        B{UDP}, B{SSL} or B{UNIX}.\n    @type method: C{str}\n\n    @ivar reactor: the current running reactor.\n    @type reactor: a provider of C{IReactorTCP}, C{IReactorUDP},\n        C{IReactorSSL} or C{IReactorUnix}.\n\n    @ivar _port: instance of port set when the service is started.\n    @type _port: a provider of L{twisted.internet.interfaces.IListeningPort}.\n    \"\"\"\n\n    volatile = ['_port']\n    method = None\n    reactor = None\n\n    _port = None\n\n    def __init__(self, *args, **kwargs):\n        self.args = args\n        if 'reactor' in kwargs:\n            self.reactor = kwargs.pop(\"reactor\")\n        self.kwargs = kwargs\n\n\n    def privilegedStartService(self):\n        service.Service.privilegedStartService(self)\n        self._port = self._getPort()\n\n\n    def startService(self):\n        service.Service.startService(self)\n        if self._port is None:\n            self._port = self._getPort()\n\n\n    def stopService(self):\n        service.Service.stopService(self)\n        # TODO: if startup failed, should shutdown skip stopListening?\n        # _port won't exist\n        if self._port is not None:\n            d = self._port.stopListening()\n            del self._port\n            return d\n\n\n    def _getPort(self):\n        \"\"\"\n        Wrapper around the appropriate listen method of the reactor.\n\n        @return: the port object returned by the listen method.\n        @rtype: an object providing\n            L{twisted.internet.interfaces.IListeningPort}.\n        \"\"\"\n        return getattr(_maybeGlobalReactor(self.reactor),\n                       'listen%s' % (self.method,))(*self.args, **self.kwargs)\n\n\n\nclass _AbstractClient(_VolatileDataService):\n    \"\"\"\n    @cvar volatile: list of attribute to remove from pickling.\n    @type volatile: C{list}\n\n    @ivar method: the type of method to call on the reactor, one of B{TCP},\n        B{UDP}, B{SSL} or B{UNIX}.\n    @type method: C{str}\n\n    @ivar reactor: the current running reactor.\n    @type reactor: a provider of C{IReactorTCP}, C{IReactorUDP},\n        C{IReactorSSL} or C{IReactorUnix}.\n\n    @ivar _connection: instance of connection set when the service is started.\n    @type _connection: a provider of L{twisted.internet.interfaces.IConnector}.\n    \"\"\"\n\n    volatile = ['_connection']\n    method = None\n    reactor = None\n\n    _connection = None\n\n    def __init__(self, *args, **kwargs):\n        self.args = args\n        if 'reactor' in kwargs:\n            self.reactor = kwargs.pop(\"reactor\")\n        self.kwargs = kwargs\n\n\n    def startService(self):\n        service.Service.startService(self)\n        self._connection = self._getConnection()\n\n\n    def stopService(self):\n        service.Service.stopService(self)\n        if self._connection is not None:\n            self._connection.disconnect()\n            del self._connection\n\n\n    def _getConnection(self):\n        \"\"\"\n        Wrapper around the appropriate connect method of the reactor.\n\n        @return: the port object returned by the connect method.\n        @rtype: an object providing L{twisted.internet.interfaces.IConnector}.\n        \"\"\"\n        return getattr(_maybeGlobalReactor(self.reactor),\n                       'connect%s' % (self.method,))(*self.args, **self.kwargs)\n\n\n\n_doc={\n'Client':\n\"\"\"Connect to %(tran)s\n\nCall reactor.connect%(tran)s when the service starts, with the\narguments given to the constructor.\n\"\"\",\n'Server':\n\"\"\"Serve %(tran)s clients\n\nCall reactor.listen%(tran)s when the service starts, with the\narguments given to the constructor. When the service stops,\nstop listening. See twisted.internet.interfaces for documentation\non arguments to the reactor method.\n\"\"\",\n}\n\nfor tran in 'TCP UNIX SSL UDP UNIXDatagram Multicast'.split():\n    for side in 'Server Client'.split():\n        if tran == \"Multicast\" and side == \"Client\":\n            continue\n        if tran == \"UDP\" and side == \"Client\":\n            continue\n        base = globals()['_Abstract'+side]\n        doc = _doc[side] % vars()\n\n        klass = type(tran+side, (base,), {'method': tran, '__doc__': doc})\n        globals()[tran+side] = klass\n\n\n\nclass TimerService(_VolatileDataService):\n    \"\"\"\n    Service to periodically call a function\n\n    Every C{step} seconds call the given function with the given arguments.\n    The service starts the calls when it starts, and cancels them\n    when it stops.\n\n    @ivar clock: Source of time. This defaults to L{None} which is\n        causes L{twisted.internet.reactor} to be used.\n        Feel free to set this to something else, but it probably ought to be\n        set *before* calling L{startService}.\n    @type clock: L{IReactorTime<twisted.internet.interfaces.IReactorTime>}\n\n    @ivar call: Function and arguments to call periodically.\n    @type call: L{tuple} of C{(callable, args, kwargs)}\n    \"\"\"\n\n    volatile = ['_loop', '_loopFinished']\n\n    def __init__(self, step, callable, *args, **kwargs):\n        \"\"\"\n        @param step: The number of seconds between calls.\n        @type step: L{float}\n\n        @param callable: Function to call\n        @type callable: L{callable}\n\n        @param args: Positional arguments to pass to function\n        @param kwargs: Keyword arguments to pass to function\n        \"\"\"\n        self.step = step\n        self.call = (callable, args, kwargs)\n        self.clock = None\n\n    def startService(self):\n        service.Service.startService(self)\n        callable, args, kwargs = self.call\n        # we have to make a new LoopingCall each time we're started, because\n        # an active LoopingCall remains active when serialized. If\n        # LoopingCall were a _VolatileDataService, we wouldn't need to do\n        # this.\n        self._loop = task.LoopingCall(callable, *args, **kwargs)\n        self._loop.clock = _maybeGlobalReactor(self.clock)\n        self._loopFinished = self._loop.start(self.step, now=True)\n        self._loopFinished.addErrback(self._failed)\n\n    def _failed(self, why):\n        # make a note that the LoopingCall is no longer looping, so we don't\n        # try to shut it down a second time in stopService. I think this\n        # should be in LoopingCall. -warner\n        self._loop.running = False\n        log.err(why)\n\n    def stopService(self):\n        \"\"\"\n        Stop the service.\n\n        @rtype: L{Deferred<defer.Deferred>}\n        @return: a L{Deferred<defer.Deferred>} which is fired when the\n            currently running call (if any) is finished.\n        \"\"\"\n        if self._loop.running:\n            self._loop.stop()\n        self._loopFinished.addCallback(lambda _:\n                service.Service.stopService(self))\n        return self._loopFinished\n\n\n\nclass CooperatorService(service.Service):\n    \"\"\"\n    Simple L{service.IService} which starts and stops a L{twisted.internet.task.Cooperator}.\n    \"\"\"\n    def __init__(self):\n        self.coop = task.Cooperator(started=False)\n\n\n    def coiterate(self, iterator):\n        return self.coop.coiterate(iterator)\n\n\n    def startService(self):\n        self.coop.start()\n\n\n    def stopService(self):\n        self.coop.stop()\n\n\n\nclass StreamServerEndpointService(service.Service, object):\n    \"\"\"\n    A L{StreamServerEndpointService} is an L{IService} which runs a server on a\n    listening port described by an L{IStreamServerEndpoint\n    <twisted.internet.interfaces.IStreamServerEndpoint>}.\n\n    @ivar factory: A server factory which will be used to listen on the\n        endpoint.\n\n    @ivar endpoint: An L{IStreamServerEndpoint\n        <twisted.internet.interfaces.IStreamServerEndpoint>} provider\n        which will be used to listen when the service starts.\n\n    @ivar _waitingForPort: a Deferred, if C{listen} has yet been invoked on the\n        endpoint, otherwise None.\n\n    @ivar _raiseSynchronously: Defines error-handling behavior for the case\n        where C{listen(...)} raises an exception before C{startService} or\n        C{privilegedStartService} have completed.\n\n    @type _raiseSynchronously: C{bool}\n\n    @since: 10.2\n    \"\"\"\n\n    _raiseSynchronously = False\n\n    def __init__(self, endpoint, factory):\n        self.endpoint = endpoint\n        self.factory = factory\n        self._waitingForPort = None\n\n\n    def privilegedStartService(self):\n        \"\"\"\n        Start listening on the endpoint.\n        \"\"\"\n        service.Service.privilegedStartService(self)\n        self._waitingForPort = self.endpoint.listen(self.factory)\n        raisedNow = []\n        def handleIt(err):\n            if self._raiseSynchronously:\n                raisedNow.append(err)\n            elif not err.check(CancelledError):\n                log.err(err)\n        self._waitingForPort.addErrback(handleIt)\n        if raisedNow:\n            raisedNow[0].raiseException()\n        self._raiseSynchronously = False\n\n\n    def startService(self):\n        \"\"\"\n        Start listening on the endpoint, unless L{privilegedStartService} got\n        around to it already.\n        \"\"\"\n        service.Service.startService(self)\n        if self._waitingForPort is None:\n            self.privilegedStartService()\n\n\n    def stopService(self):\n        \"\"\"\n        Stop listening on the port if it is already listening, otherwise,\n        cancel the attempt to listen.\n\n        @return: a L{Deferred<twisted.internet.defer.Deferred>} which fires\n            with L{None} when the port has stopped listening.\n        \"\"\"\n        self._waitingForPort.cancel()\n        def stopIt(port):\n            if port is not None:\n                return port.stopListening()\n        d = self._waitingForPort.addCallback(stopIt)\n        def stop(passthrough):\n            self.running = False\n            return passthrough\n        d.addBoth(stop)\n        return d\n\n\n\nclass _ReconnectingProtocolProxy(object):\n    \"\"\"\n    A proxy for a Protocol to provide connectionLost notification to a client\n    connection service, in support of reconnecting when connections are lost.\n    \"\"\"\n\n    def __init__(self, protocol, lostNotification):\n        \"\"\"\n        Create a L{_ReconnectingProtocolProxy}.\n\n        @param protocol: the application-provided L{interfaces.IProtocol}\n            provider.\n        @type protocol: provider of L{interfaces.IProtocol} which may\n            additionally provide L{interfaces.IHalfCloseableProtocol} and\n            L{interfaces.IFileDescriptorReceiver}.\n\n        @param lostNotification: a 1-argument callable to invoke with the\n            C{reason} when the connection is lost.\n        \"\"\"\n        self._protocol = protocol\n        self._lostNotification = lostNotification\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        The connection was lost.  Relay this information.\n\n        @param reason: The reason the connection was lost.\n\n        @return: the underlying protocol's result\n        \"\"\"\n        try:\n            return self._protocol.connectionLost(reason)\n        finally:\n            self._lostNotification(reason)\n\n\n    def __getattr__(self, item):\n        return getattr(self._protocol, item)\n\n\n    def __repr__(self):\n        return '<%s wrapping %r>' % (\n            self.__class__.__name__, self._protocol)\n\n\n\nclass _DisconnectFactory(object):\n    \"\"\"\n    A L{_DisconnectFactory} is a proxy for L{IProtocolFactory} that catches\n    C{connectionLost} notifications and relays them.\n    \"\"\"\n\n    def __init__(self, protocolFactory, protocolDisconnected):\n        self._protocolFactory = protocolFactory\n        self._protocolDisconnected = protocolDisconnected\n\n\n    def buildProtocol(self, addr):\n        \"\"\"\n        Create a L{_ReconnectingProtocolProxy} with the disconnect-notification\n        callback we were called with.\n\n        @param addr: The address the connection is coming from.\n\n        @return: a L{_ReconnectingProtocolProxy} for a protocol produced by\n            C{self._protocolFactory}\n        \"\"\"\n        return _ReconnectingProtocolProxy(\n            self._protocolFactory.buildProtocol(addr),\n            self._protocolDisconnected\n        )\n\n\n    def __getattr__(self, item):\n        return getattr(self._protocolFactory, item)\n\n\n    def __repr__(self):\n        return '<%s wrapping %r>' % (\n            self.__class__.__name__, self._protocolFactory)\n\n\n\ndef backoffPolicy(initialDelay=1.0, maxDelay=60.0, factor=1.5,\n                  jitter=_goodEnoughRandom):\n    \"\"\"\n    A timeout policy for L{ClientService} which computes an exponential backoff\n    interval with configurable parameters.\n\n    @since: 16.1.0\n\n    @param initialDelay: Delay for the first reconnection attempt (default\n        1.0s).\n    @type initialDelay: L{float}\n\n    @param maxDelay: Maximum number of seconds between connection attempts\n        (default 60 seconds, or one minute).  Note that this value is before\n        jitter is applied, so the actual maximum possible delay is this value\n        plus the maximum possible result of C{jitter()}.\n    @type maxDelay: L{float}\n\n    @param factor: A multiplicative factor by which the delay grows on each\n        failed reattempt.  Default: 1.5.\n    @type factor: L{float}\n\n    @param jitter: A 0-argument callable that introduces noise into the delay.\n        By default, C{random.random}, i.e. a pseudorandom floating-point value\n        between zero and one.\n    @type jitter: 0-argument callable returning L{float}\n\n    @return: a 1-argument callable that, given an attempt count, returns a\n        floating point number; the number of seconds to delay.\n    @rtype: see L{ClientService.__init__}'s C{retryPolicy} argument.\n    \"\"\"\n    def policy(attempt):\n        try:\n            delay = min(initialDelay * (factor ** min(100, attempt)), maxDelay)\n        except OverflowError:\n            delay = maxDelay\n        return delay + jitter()\n    return policy\n\n\n\n_defaultPolicy = backoffPolicy()\n\n\ndef _firstResult(gen):\n    \"\"\"\n    Return the first element of a generator and exhaust it.\n\n    C{MethodicalMachine.upon}'s C{collector} argument takes a generator of\n    output results. If the generator is exhausted, the later outputs aren't\n    actually run.\n\n    @param gen: Generator to extract values from\n\n    @return: The first element of the generator.\n    \"\"\"\n    return list(gen)[0]\n\n\n\nclass _ClientMachine(object):\n    \"\"\"\n    State machine for maintaining a single outgoing connection to an endpoint.\n\n    @see: L{ClientService}\n    \"\"\"\n\n    _machine = MethodicalMachine()\n\n    def __init__(self, endpoint, factory, retryPolicy, clock,\n                 prepareConnection, log):\n        \"\"\"\n        @see: L{ClientService.__init__}\n\n        @param log: The logger for the L{ClientService} instance this state\n            machine is associated to.\n        @type log: L{Logger}\n\n        @ivar _awaitingConnected: notifications to make when connection\n            succeeds, fails, or is cancelled\n        @type _awaitingConnected: list of (Deferred, count) tuples\n        \"\"\"\n        self._endpoint = endpoint\n        self._failedAttempts = 0\n        self._stopped = False\n        self._factory = factory\n        self._timeoutForAttempt = retryPolicy\n        self._clock = clock\n        self._prepareConnection = prepareConnection\n        self._connectionInProgress = succeed(None)\n\n        self._awaitingConnected = []\n\n        self._stopWaiters = []\n        self._log = log\n\n\n    @_machine.state(initial=True)\n    def _init(self):\n        \"\"\"\n        The service has not been started.\n        \"\"\"\n\n    @_machine.state()\n    def _connecting(self):\n        \"\"\"\n        The service has started connecting.\n        \"\"\"\n\n    @_machine.state()\n    def _waiting(self):\n        \"\"\"\n        The service is waiting for the reconnection period\n        before reconnecting.\n        \"\"\"\n\n    @_machine.state()\n    def _connected(self):\n        \"\"\"\n        The service is connected.\n        \"\"\"\n\n    @_machine.state()\n    def _disconnecting(self):\n        \"\"\"\n        The service is disconnecting after being asked to shutdown.\n        \"\"\"\n\n    @_machine.state()\n    def _restarting(self):\n        \"\"\"\n        The service is disconnecting and has been asked to restart.\n        \"\"\"\n\n    @_machine.state()\n    def _stopped(self):\n        \"\"\"\n        The service has been stopped and is disconnected.\n        \"\"\"\n\n    @_machine.input()\n    def start(self):\n        \"\"\"\n        Start this L{ClientService}, initiating the connection retry loop.\n        \"\"\"\n\n    @_machine.output()\n    def _connect(self):\n        \"\"\"\n        Start a connection attempt.\n        \"\"\"\n        factoryProxy = _DisconnectFactory(self._factory,\n                                          lambda _: self._clientDisconnected())\n\n        self._connectionInProgress = (\n            self._endpoint.connect(factoryProxy)\n            .addCallback(self._runPrepareConnection)\n            .addCallback(self._connectionMade)\n            .addErrback(self._connectionFailed))\n\n\n    def _runPrepareConnection(self, protocol):\n        \"\"\"\n        Run any C{prepareConnection} callback with the connected protocol,\n        ignoring its return value but propagating any failure.\n\n        @param protocol: The protocol of the connection.\n        @type protocol: L{IProtocol}\n\n        @return: Either:\n\n            - A L{Deferred} that succeeds with the protocol when the\n              C{prepareConnection} callback has executed successfully.\n\n            - A L{Deferred} that fails when the C{prepareConnection} callback\n              throws or returns a failed L{Deferred}.\n\n            - The protocol, when no C{prepareConnection} callback is defined.\n        \"\"\"\n        if self._prepareConnection:\n            return (maybeDeferred(self._prepareConnection, protocol)\n                    .addCallback(lambda _: protocol))\n        return protocol\n\n\n    @_machine.output()\n    def _resetFailedAttempts(self):\n        \"\"\"\n        Reset the number of failed attempts.\n        \"\"\"\n        self._failedAttempts = 0\n\n\n    @_machine.input()\n    def stop(self):\n        \"\"\"\n        Stop trying to connect and disconnect any current connection.\n\n        @return: a L{Deferred} that fires when all outstanding connections are\n            closed and all in-progress connection attempts halted.\n        \"\"\"\n\n    @_machine.output()\n    def _waitForStop(self):\n        \"\"\"\n        Return a deferred that will fire when the service has finished\n        disconnecting.\n\n        @return: L{Deferred} that fires when the service has finished\n            disconnecting.\n        \"\"\"\n        self._stopWaiters.append(Deferred())\n        return self._stopWaiters[-1]\n\n\n    @_machine.output()\n    def _stopConnecting(self):\n        \"\"\"\n        Stop pending connection attempt.\n        \"\"\"\n        self._connectionInProgress.cancel()\n\n\n    @_machine.output()\n    def _stopRetrying(self):\n        \"\"\"\n        Stop pending attempt to reconnect.\n        \"\"\"\n        self._retryCall.cancel()\n        del self._retryCall\n\n\n    @_machine.output()\n    def _disconnect(self):\n        \"\"\"\n        Disconnect the current connection.\n        \"\"\"\n        self._currentConnection.transport.loseConnection()\n\n\n    @_machine.input()\n    def _connectionMade(self, protocol):\n        \"\"\"\n        A connection has been made.\n\n        @param protocol: The protocol of the connection.\n        @type protocol: L{IProtocol}\n        \"\"\"\n\n    @_machine.output()\n    def _notifyWaiters(self, protocol):\n        \"\"\"\n        Notify all pending requests for a connection that a connection has been\n        made.\n\n        @param protocol: The protocol of the connection.\n        @type protocol: L{IProtocol}\n        \"\"\"\n        # This should be in _resetFailedAttempts but the signature doesn't\n        # match.\n        self._failedAttempts = 0\n\n        self._currentConnection = protocol._protocol\n        self._unawait(self._currentConnection)\n\n\n    @_machine.input()\n    def _connectionFailed(self, f):\n        \"\"\"\n        The current connection attempt failed.\n        \"\"\"\n\n\n    @_machine.output()\n    def _wait(self):\n        \"\"\"\n        Schedule a retry attempt.\n        \"\"\"\n        self._doWait()\n\n    @_machine.output()\n    def _ignoreAndWait(self, f):\n        \"\"\"\n        Schedule a retry attempt, and ignore the Failure passed in.\n        \"\"\"\n        return self._doWait()\n\n    def _doWait(self):\n        self._failedAttempts += 1\n        delay = self._timeoutForAttempt(self._failedAttempts)\n        self._log.info(\"Scheduling retry {attempt} to connect {endpoint} \"\n                       \"in {delay} seconds.\", attempt=self._failedAttempts,\n                       endpoint=self._endpoint, delay=delay)\n        self._retryCall = self._clock.callLater(delay, self._reconnect)\n\n\n    @_machine.input()\n    def _reconnect(self):\n        \"\"\"\n        The wait between connection attempts is done.\n        \"\"\"\n\n    @_machine.input()\n    def _clientDisconnected(self):\n        \"\"\"\n        The current connection has been disconnected.\n        \"\"\"\n\n    @_machine.output()\n    def _forgetConnection(self):\n        \"\"\"\n        Forget the current connection.\n        \"\"\"\n        del self._currentConnection\n\n\n    @_machine.output()\n    def _cancelConnectWaiters(self):\n        \"\"\"\n        Notify all pending requests for a connection that no more connections\n        are expected.\n        \"\"\"\n        self._unawait(Failure(CancelledError()))\n\n    @_machine.output()\n    def _ignoreAndCancelConnectWaiters(self, f):\n        \"\"\"\n        Notify all pending requests for a connection that no more connections\n        are expected, after ignoring the Failure passed in.\n        \"\"\"\n        self._unawait(Failure(CancelledError()))\n\n\n    @_machine.output()\n    def _finishStopping(self):\n        \"\"\"\n        Notify all deferreds waiting on the service stopping.\n        \"\"\"\n        self._doFinishStopping()\n\n    @_machine.output()\n    def _ignoreAndFinishStopping(self, f):\n        \"\"\"\n        Notify all deferreds waiting on the service stopping, and ignore the\n        Failure passed in.\n        \"\"\"\n        self._doFinishStopping()\n\n    def _doFinishStopping(self):\n        self._stopWaiters, waiting = [], self._stopWaiters\n        for w in waiting:\n            w.callback(None)\n\n\n    @_machine.input()\n    def whenConnected(self, failAfterFailures=None):\n        \"\"\"\n        Retrieve the currently-connected L{Protocol}, or the next one to\n        connect.\n\n        @param failAfterFailures: number of connection failures after which\n            the Deferred will deliver a Failure (None means the Deferred will\n            only fail if/when the service is stopped).  Set this to 1 to make\n            the very first connection failure signal an error.  Use 2 to\n            allow one failure but signal an error if the subsequent retry\n            then fails.\n        @type failAfterFailures: L{int} or None\n\n        @return: a Deferred that fires with a protocol produced by the\n            factory passed to C{__init__}\n        @rtype: L{Deferred} that may:\n\n            - fire with L{IProtocol}\n\n            - fail with L{CancelledError} when the service is stopped\n\n            - fail with e.g.\n              L{DNSLookupError<twisted.internet.error.DNSLookupError>} or\n              L{ConnectionRefusedError<twisted.internet.error.ConnectionRefusedError>}\n              when the number of consecutive failed connection attempts\n              equals the value of \"failAfterFailures\"\n        \"\"\"\n\n    @_machine.output()\n    def _currentConnection(self, failAfterFailures=None):\n        \"\"\"\n        Return the currently connected protocol.\n\n        @return: L{Deferred} that is fired with currently connected protocol.\n        \"\"\"\n        return succeed(self._currentConnection)\n\n\n    @_machine.output()\n    def _noConnection(self, failAfterFailures=None):\n        \"\"\"\n        Notify the caller that no connection is expected.\n\n        @return: L{Deferred} that is fired with L{CancelledError}.\n        \"\"\"\n        return fail(CancelledError())\n\n\n    @_machine.output()\n    def _awaitingConnection(self, failAfterFailures=None):\n        \"\"\"\n        Return a deferred that will fire with the next connected protocol.\n\n        @return: L{Deferred} that will fire with the next connected protocol.\n        \"\"\"\n        result = Deferred()\n        self._awaitingConnected.append((result, failAfterFailures))\n        return result\n\n\n    @_machine.output()\n    def _deferredSucceededWithNone(self):\n        \"\"\"\n        Return a deferred that has already fired with L{None}.\n\n        @return: A L{Deferred} that has already fired with L{None}.\n        \"\"\"\n        return succeed(None)\n\n\n    def _unawait(self, value):\n        \"\"\"\n        Fire all outstanding L{ClientService.whenConnected} L{Deferred}s.\n\n        @param value: the value to fire the L{Deferred}s with.\n        \"\"\"\n        self._awaitingConnected, waiting = [], self._awaitingConnected\n        for (w, remaining) in waiting:\n            w.callback(value)\n\n    @_machine.output()\n    def _deliverConnectionFailure(self, f):\n        \"\"\"\n        Deliver connection failures to any L{ClientService.whenConnected}\n        L{Deferred}s that have met their failAfterFailures threshold.\n\n        @param f: the Failure to fire the L{Deferred}s with.\n        \"\"\"\n        ready = []\n        notReady = []\n        for (w, remaining) in self._awaitingConnected:\n            if remaining is None:\n                notReady.append((w, remaining))\n            elif remaining <= 1:\n                ready.append(w)\n            else:\n                notReady.append((w, remaining-1))\n        self._awaitingConnected = notReady\n        for w in ready:\n            w.callback(f)\n\n    # State Transitions\n\n    _init.upon(start, enter=_connecting,\n               outputs=[_connect])\n    _init.upon(stop, enter=_stopped,\n               outputs=[_deferredSucceededWithNone],\n               collector=_firstResult)\n\n    _connecting.upon(start, enter=_connecting, outputs=[])\n    # Note that this synchonously triggers _connectionFailed in the\n    # _disconnecting state.\n    _connecting.upon(stop, enter=_disconnecting,\n                     outputs=[_waitForStop, _stopConnecting],\n                     collector=_firstResult)\n    _connecting.upon(_connectionMade, enter=_connected,\n                     outputs=[_notifyWaiters])\n    _connecting.upon(_connectionFailed, enter=_waiting,\n                     outputs=[_ignoreAndWait, _deliverConnectionFailure])\n\n    _waiting.upon(start, enter=_waiting,\n                  outputs=[])\n    _waiting.upon(stop, enter=_stopped,\n                  outputs=[_waitForStop,\n                           _cancelConnectWaiters,\n                           _stopRetrying,\n                           _finishStopping],\n                  collector=_firstResult)\n    _waiting.upon(_reconnect, enter=_connecting,\n                  outputs=[_connect])\n\n    _connected.upon(start, enter=_connected,\n                    outputs=[])\n    _connected.upon(stop, enter=_disconnecting,\n                    outputs=[_waitForStop, _disconnect],\n                    collector=_firstResult)\n    _connected.upon(_clientDisconnected, enter=_waiting,\n                    outputs=[_forgetConnection, _wait])\n\n    _disconnecting.upon(start, enter=_restarting,\n                        outputs=[_resetFailedAttempts])\n    _disconnecting.upon(stop, enter=_disconnecting,\n                        outputs=[_waitForStop],\n                        collector=_firstResult)\n    _disconnecting.upon(_clientDisconnected, enter=_stopped,\n                        outputs=[_cancelConnectWaiters,\n                                 _finishStopping,\n                                 _forgetConnection])\n    # Note that this is triggered synchonously with the transition from\n    # _connecting\n    _disconnecting.upon(_connectionFailed, enter=_stopped,\n                        outputs=[_ignoreAndCancelConnectWaiters,\n                                 _ignoreAndFinishStopping])\n\n    _restarting.upon(start, enter=_restarting,\n                     outputs=[])\n    _restarting.upon(stop, enter=_disconnecting,\n                     outputs=[_waitForStop],\n                     collector=_firstResult)\n    _restarting.upon(_clientDisconnected, enter=_connecting,\n                     outputs=[_finishStopping, _connect])\n\n    _stopped.upon(start, enter=_connecting,\n                  outputs=[_connect])\n    _stopped.upon(stop, enter=_stopped,\n                  outputs=[_deferredSucceededWithNone],\n                  collector=_firstResult)\n\n    _init.upon(whenConnected, enter=_init,\n               outputs=[_awaitingConnection],\n               collector=_firstResult)\n    _connecting.upon(whenConnected, enter=_connecting,\n                     outputs=[_awaitingConnection],\n                     collector=_firstResult)\n    _waiting.upon(whenConnected, enter=_waiting,\n                  outputs=[_awaitingConnection],\n                  collector=_firstResult)\n    _connected.upon(whenConnected, enter=_connected,\n                    outputs=[_currentConnection],\n                    collector=_firstResult)\n    _disconnecting.upon(whenConnected, enter=_disconnecting,\n                        outputs=[_awaitingConnection],\n                        collector=_firstResult)\n    _restarting.upon(whenConnected, enter=_restarting,\n                     outputs=[_awaitingConnection],\n                     collector=_firstResult)\n    _stopped.upon(whenConnected, enter=_stopped,\n                  outputs=[_noConnection],\n                  collector=_firstResult)\n\n\n\nclass ClientService(service.Service, object):\n    \"\"\"\n    A L{ClientService} maintains a single outgoing connection to a client\n    endpoint, reconnecting after a configurable timeout when a connection\n    fails, either before or after connecting.\n\n    @since: 16.1.0\n    \"\"\"\n\n    _log = Logger()\n\n    def __init__(self, endpoint, factory, retryPolicy=None, clock=None,\n                 prepareConnection=None):\n        \"\"\"\n        @param endpoint: A L{stream client endpoint\n            <interfaces.IStreamClientEndpoint>} provider which will be used to\n            connect when the service starts.\n\n        @param factory: A L{protocol factory <interfaces.IProtocolFactory>}\n            which will be used to create clients for the endpoint.\n\n        @param retryPolicy: A policy configuring how long L{ClientService} will\n            wait between attempts to connect to C{endpoint}.\n        @type retryPolicy: callable taking (the number of failed connection\n            attempts made in a row (L{int})) and returning the number of\n            seconds to wait before making another attempt.\n\n        @param clock: The clock used to schedule reconnection.  It's mainly\n            useful to be parametrized in tests.  If the factory is serialized,\n            this attribute will not be serialized, and the default value (the\n            reactor) will be restored when deserialized.\n        @type clock: L{IReactorTime}\n\n        @param prepareConnection: A single argument L{callable} that may return\n            a L{Deferred}. It will be called once with the L{protocol\n            <interfaces.IProtocol>} each time a new connection is made.  It may\n            call methods on the protocol to prepare it for use (e.g.\n            authenticate) or validate it (check its health).\n\n            The C{prepareConnection} callable may raise an exception or return\n            a L{Deferred} which fails to reject the connection.  A rejected\n            connection is not used to fire an L{Deferred} returned by\n            L{whenConnected}.  Instead, L{ClientService} handles the failure\n            and continues as if the connection attempt were a failure\n            (incrementing the counter passed to C{retryPolicy}).\n\n            L{Deferred}s returned by L{whenConnected} will not fire until\n            any L{Deferred} returned by the C{prepareConnection} callable\n            fire. Otherwise its successful return value is consumed, but\n            ignored.\n\n            Present Since Twisted 18.7.0\n\n        @type prepareConnection: L{callable}\n\n        \"\"\"\n        clock = _maybeGlobalReactor(clock)\n        retryPolicy = _defaultPolicy if retryPolicy is None else retryPolicy\n\n        self._machine = _ClientMachine(\n            endpoint, factory, retryPolicy, clock,\n            prepareConnection=prepareConnection, log=self._log,\n        )\n\n\n    def whenConnected(self, failAfterFailures=None):\n        \"\"\"\n        Retrieve the currently-connected L{Protocol}, or the next one to\n        connect.\n\n        @param failAfterFailures: number of connection failures after which\n            the Deferred will deliver a Failure (None means the Deferred will\n            only fail if/when the service is stopped).  Set this to 1 to make\n            the very first connection failure signal an error.  Use 2 to\n            allow one failure but signal an error if the subsequent retry\n            then fails.\n        @type failAfterFailures: L{int} or None\n\n        @return: a Deferred that fires with a protocol produced by the\n            factory passed to C{__init__}\n        @rtype: L{Deferred} that may:\n\n            - fire with L{IProtocol}\n\n            - fail with L{CancelledError} when the service is stopped\n\n            - fail with e.g.\n              L{DNSLookupError<twisted.internet.error.DNSLookupError>} or\n              L{ConnectionRefusedError<twisted.internet.error.ConnectionRefusedError>}\n              when the number of consecutive failed connection attempts\n              equals the value of \"failAfterFailures\"\n        \"\"\"\n        return self._machine.whenConnected(failAfterFailures)\n\n\n    def startService(self):\n        \"\"\"\n        Start this L{ClientService}, initiating the connection retry loop.\n        \"\"\"\n        if self.running:\n            self._log.warn(\"Duplicate ClientService.startService {log_source}\")\n            return\n        super(ClientService, self).startService()\n        self._machine.start()\n\n\n    def stopService(self):\n        \"\"\"\n        Stop attempting to reconnect and close any existing connections.\n\n        @return: a L{Deferred} that fires when all outstanding connections are\n            closed and all in-progress connection attempts halted.\n        \"\"\"\n        super(ClientService, self).stopService()\n        return self._machine.stop()\n\n\n__all__ = (['TimerService', 'CooperatorService', 'MulticastServer',\n            'StreamServerEndpointService', 'UDPServer',\n            'ClientService'] +\n           [tran + side\n            for tran in 'TCP UNIX SSL UNIXDatagram'.split()\n            for side in 'Server Client'.split()])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/reactors.py",
    "content": "# -*- test-case-name: twisted.test.test_application -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nPlugin-based system for enumerating available reactors and installing one of\nthem.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom zope.interface import Interface, Attribute, implementer\n\nfrom twisted.plugin import IPlugin, getPlugins\nfrom twisted.python.reflect import namedAny\n\n\nclass IReactorInstaller(Interface):\n    \"\"\"\n    Definition of a reactor which can probably be installed.\n    \"\"\"\n    shortName = Attribute(\"\"\"\n    A brief string giving the user-facing name of this reactor.\n    \"\"\")\n\n    description = Attribute(\"\"\"\n    A longer string giving a user-facing description of this reactor.\n    \"\"\")\n\n    def install():\n        \"\"\"\n        Install this reactor.\n        \"\"\"\n\n    # TODO - A method which provides a best-guess as to whether this reactor\n    # can actually be used in the execution environment.\n\n\n\nclass NoSuchReactor(KeyError):\n    \"\"\"\n    Raised when an attempt is made to install a reactor which cannot be found.\n    \"\"\"\n\n\n\n@implementer(IPlugin, IReactorInstaller)\nclass Reactor(object):\n    \"\"\"\n    @ivar moduleName: The fully-qualified Python name of the module of which\n    the install callable is an attribute.\n    \"\"\"\n    def __init__(self, shortName, moduleName, description):\n        self.shortName = shortName\n        self.moduleName = moduleName\n        self.description = description\n\n\n    def install(self):\n        namedAny(self.moduleName).install()\n\n\n\ndef getReactorTypes():\n    \"\"\"\n    Return an iterator of L{IReactorInstaller} plugins.\n    \"\"\"\n    return getPlugins(IReactorInstaller)\n\n\n\ndef installReactor(shortName):\n    \"\"\"\n    Install the reactor with the given C{shortName} attribute.\n\n    @raise NoSuchReactor: If no reactor is found with a matching C{shortName}.\n\n    @raise: anything that the specified reactor can raise when installed.\n    \"\"\"\n    for installer in getReactorTypes():\n        if installer.shortName == shortName:\n            installer.install()\n            from twisted.internet import reactor\n            return reactor\n    raise NoSuchReactor(shortName)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/runner/__init__.py",
    "content": "# -*- test-case-name: twisted.application.runner.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nFacilities for running a Twisted application.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/runner/_exit.py",
    "content": "# -*- test-case-name: twisted.application.runner.test.test_exit -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nSystem exit support.\n\"\"\"\n\nfrom sys import stdout, stderr, exit as sysexit\n\nfrom constantly import Values, ValueConstant\n\n\n\ndef exit(status, message=None):\n    \"\"\"\n    Exit the python interpreter with the given status and an optional message.\n\n    @param status: An exit status.\n    @type status: L{int} or L{ValueConstant} from L{ExitStatus}.\n\n    @param message: An options message to print.\n    @type status: L{str}\n    \"\"\"\n    if isinstance(status, ValueConstant):\n        code = status.value\n    else:\n        code = int(status)\n\n    if message:\n        if code == 0:\n            out = stdout\n        else:\n            out = stderr\n        out.write(message)\n        out.write(\"\\n\")\n\n    sysexit(code)\n\n\n\ntry:\n    import posix as Status\nexcept ImportError:\n    class Status(object):\n        \"\"\"\n        Object to hang C{EX_*} values off of as a substitute for L{posix}.\n        \"\"\"\n        EX__BASE = 64\n\n        EX_OK          = 0\n        EX_USAGE       = EX__BASE\n        EX_DATAERR     = EX__BASE + 1\n        EX_NOINPUT     = EX__BASE + 2\n        EX_NOUSER      = EX__BASE + 3\n        EX_NOHOST      = EX__BASE + 4\n        EX_UNAVAILABLE = EX__BASE + 5\n        EX_SOFTWARE    = EX__BASE + 6\n        EX_OSERR       = EX__BASE + 7\n        EX_OSFILE      = EX__BASE + 8\n        EX_CANTCREAT   = EX__BASE + 9\n        EX_IOERR       = EX__BASE + 10\n        EX_TEMPFAIL    = EX__BASE + 11\n        EX_PROTOCOL    = EX__BASE + 12\n        EX_NOPERM      = EX__BASE + 13\n        EX_CONFIG      = EX__BASE + 14\n\n\n\nclass ExitStatus(Values):\n    \"\"\"\n    Standard exit status codes for system programs.\n\n    @cvar EX_OK: Successful termination.\n    @type EX_OK: L{ValueConstant}\n\n    @cvar EX_USAGE: Command line usage error.\n    @type EX_USAGE: L{ValueConstant}\n\n    @cvar EX_DATAERR: Data format error.\n    @type EX_DATAERR: L{ValueConstant}\n\n    @cvar EX_NOINPUT: Cannot open input.\n    @type EX_NOINPUT: L{ValueConstant}\n\n    @cvar EX_NOUSER: Addressee unknown.\n    @type EX_NOUSER: L{ValueConstant}\n\n    @cvar EX_NOHOST: Host name unknown.\n    @type EX_NOHOST: L{ValueConstant}\n\n    @cvar EX_UNAVAILABLE: Service unavailable.\n    @type EX_UNAVAILABLE: L{ValueConstant}\n\n    @cvar EX_SOFTWARE: Internal software error.\n    @type EX_SOFTWARE: L{ValueConstant}\n\n    @cvar EX_OSERR: System error (e.g., can't fork).\n    @type EX_OSERR: L{ValueConstant}\n\n    @cvar EX_OSFILE: Critical OS file missing.\n    @type EX_OSFILE: L{ValueConstant}\n\n    @cvar EX_CANTCREAT: Can't create (user) output file.\n    @type EX_CANTCREAT: L{ValueConstant}\n\n    @cvar EX_IOERR: Input/output error.\n    @type EX_IOERR: L{ValueConstant}\n\n    @cvar EX_TEMPFAIL: Temporary failure; the user is invited to retry.\n    @type EX_TEMPFAIL: L{ValueConstant}\n\n    @cvar EX_PROTOCOL: Remote error in protocol.\n    @type EX_PROTOCOL: L{ValueConstant}\n\n    @cvar EX_NOPERM: Permission denied.\n    @type EX_NOPERM: L{ValueConstant}\n\n    @cvar EX_CONFIG: Configuration error.\n    @type EX_CONFIG: L{ValueConstant}\n    \"\"\"\n\n    EX_OK          = ValueConstant(Status.EX_OK)\n    EX_USAGE       = ValueConstant(Status.EX_USAGE)\n    EX_DATAERR     = ValueConstant(Status.EX_DATAERR)\n    EX_NOINPUT     = ValueConstant(Status.EX_NOINPUT)\n    EX_NOUSER      = ValueConstant(Status.EX_NOUSER)\n    EX_NOHOST      = ValueConstant(Status.EX_NOHOST)\n    EX_UNAVAILABLE = ValueConstant(Status.EX_UNAVAILABLE)\n    EX_SOFTWARE    = ValueConstant(Status.EX_SOFTWARE)\n    EX_OSERR       = ValueConstant(Status.EX_OSERR)\n    EX_OSFILE      = ValueConstant(Status.EX_OSFILE)\n    EX_CANTCREAT   = ValueConstant(Status.EX_CANTCREAT)\n    EX_IOERR       = ValueConstant(Status.EX_IOERR)\n    EX_TEMPFAIL    = ValueConstant(Status.EX_TEMPFAIL)\n    EX_PROTOCOL    = ValueConstant(Status.EX_PROTOCOL)\n    EX_NOPERM      = ValueConstant(Status.EX_NOPERM)\n    EX_CONFIG      = ValueConstant(Status.EX_CONFIG)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/runner/_pidfile.py",
    "content": "# -*- test-case-name: twisted.application.runner.test.test_pidfile -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nPID file.\n\"\"\"\n\nimport errno\nfrom os import getpid, kill, name as SYSTEM_NAME\n\nfrom zope.interface import Interface, implementer\n\nfrom twisted.logger import Logger\n\n\n\nclass IPIDFile(Interface):\n    \"\"\"\n    Manages a file that remembers a process ID.\n    \"\"\"\n\n    def read():\n        \"\"\"\n        Read the process ID stored in this PID file.\n\n        @return: The contained process ID.\n        @rtype: L{int}\n\n        @raise NoPIDFound: If this PID file does not exist.\n        @raise EnvironmentError: If this PID file cannot be read.\n        @raise ValueError: If this PID file's content is invalid.\n        \"\"\"\n\n\n    def writeRunningPID():\n        \"\"\"\n        Store the PID of the current process in this PID file.\n\n        @raise EnvironmentError: If this PID file cannot be written.\n        \"\"\"\n\n\n    def remove():\n        \"\"\"\n        Remove this PID file.\n\n        @raise EnvironmentError: If this PID file cannot be removed.\n        \"\"\"\n\n\n    def isRunning():\n        \"\"\"\n        Determine whether there is a running process corresponding to the PID\n        in this PID file.\n\n        @return: True if this PID file contains a PID and a process with that\n        PID is currently running; false otherwise.\n        @rtype: L{bool}\n\n        @raise EnvironmentError: If this PID file cannot be read.\n        @raise InvalidPIDFileError: If this PID file's content is invalid.\n        @raise StalePIDFileError: If this PID file's content refers to a PID\n            for which there is no corresponding running process.\n        \"\"\"\n\n\n    def __enter__():\n        \"\"\"\n        Enter a context using this PIDFile.\n\n        Writes the PID file with the PID of the running process.\n\n        @raise AlreadyRunningError: A process corresponding to the PID in this\n            PID file is already running.\n        \"\"\"\n\n\n    def __exit__(excType, excValue, traceback):\n        \"\"\"\n        Exit a context using this PIDFile.\n\n        Removes the PID file.\n        \"\"\"\n\n\n\n@implementer(IPIDFile)\nclass PIDFile(object):\n    \"\"\"\n    Concrete implementation of L{IPIDFile} based on C{IFilePath}.\n\n    This implementation is presently not supported on non-POSIX platforms.\n    Specifically, calling L{PIDFile.isRunning} will raise\n    L{NotImplementedError}.\n    \"\"\"\n\n    _log = Logger()\n\n\n    @staticmethod\n    def _format(pid):\n        \"\"\"\n        Format a PID file's content.\n\n        @param pid: A process ID.\n        @type pid: int\n\n        @return: Formatted PID file contents.\n        @rtype: L{bytes}\n        \"\"\"\n        return u\"{}\\n\".format(int(pid)).encode(\"utf-8\")\n\n\n    def __init__(self, filePath):\n        \"\"\"\n        @param filePath: The path to the PID file on disk.\n        @type filePath: L{IFilePath}\n        \"\"\"\n        self.filePath = filePath\n\n\n    def read(self):\n        pidString = b\"\"\n        try:\n            with self.filePath.open() as fh:\n                for pidString in fh:\n                    break\n        except OSError as e:\n            if e.errno == errno.ENOENT:  # No such file\n                raise NoPIDFound(\"PID file does not exist\")\n            raise\n\n        try:\n            return int(pidString)\n        except ValueError:\n            raise InvalidPIDFileError(\n                \"non-integer PID value in PID file: {!r}\".format(pidString)\n            )\n\n\n    def _write(self, pid):\n        \"\"\"\n        Store a PID in this PID file.\n\n        @param pid: A PID to store.\n        @type pid: L{int}\n\n        @raise EnvironmentError: If this PID file cannot be written.\n        \"\"\"\n        self.filePath.setContent(self._format(pid=pid))\n\n\n    def writeRunningPID(self):\n        self._write(getpid())\n\n\n    def remove(self):\n        self.filePath.remove()\n\n\n    def isRunning(self):\n        try:\n            pid = self.read()\n        except NoPIDFound:\n            return False\n\n        if SYSTEM_NAME == \"posix\":\n            return self._pidIsRunningPOSIX(pid)\n        else:\n            raise NotImplementedError(\n                \"isRunning is not implemented on {}\".format(SYSTEM_NAME)\n            )\n\n\n    @staticmethod\n    def _pidIsRunningPOSIX(pid):\n        \"\"\"\n        POSIX implementation for running process check.\n\n        Determine whether there is a running process corresponding to the given\n        PID.\n\n        @return: True if the given PID is currently running; false otherwise.\n        @rtype: L{bool}\n\n        @raise EnvironmentError: If this PID file cannot be read.\n        @raise InvalidPIDFileError: If this PID file's content is invalid.\n        @raise StalePIDFileError: If this PID file's content refers to a PID\n            for which there is no corresponding running process.\n        \"\"\"\n        try:\n            kill(pid, 0)\n        except OSError as e:\n            if e.errno == errno.ESRCH:  # No such process\n                raise StalePIDFileError(\n                    \"PID file refers to non-existing process\"\n                )\n            elif e.errno == errno.EPERM:  # Not permitted to kill\n                return True\n            else:\n                raise\n        else:\n            return True\n\n\n    def __enter__(self):\n        try:\n            if self.isRunning():\n                raise AlreadyRunningError()\n        except StalePIDFileError:\n            self._log.info(\"Replacing stale PID file: {log_source}\")\n        self.writeRunningPID()\n        return self\n\n\n    def __exit__(self, excType, excValue, traceback):\n        self.remove()\n\n\n\n@implementer(IPIDFile)\nclass NonePIDFile(object):\n    \"\"\"\n    PID file implementation that does nothing.\n\n    This is meant to be used as a \"active None\" object in place of a PID file\n    when no PID file is desired.\n    \"\"\"\n\n    def __init__(self):\n        pass\n\n\n    def read(self):\n        raise NoPIDFound(\"PID file does not exist\")\n\n\n    def _write(self, pid):\n        \"\"\"\n        Store a PID in this PID file.\n\n        @param pid: A PID to store.\n        @type pid: L{int}\n\n        @raise EnvironmentError: If this PID file cannot be written.\n\n        @note: This implementation always raises an L{EnvironmentError}.\n        \"\"\"\n        raise OSError(errno.EPERM, \"Operation not permitted\")\n\n\n    def writeRunningPID(self):\n        self._write(0)\n\n\n    def remove(self):\n        raise OSError(errno.ENOENT, \"No such file or directory\")\n\n\n    def isRunning(self):\n        return False\n\n\n    def __enter__(self):\n        return self\n\n\n    def __exit__(self, excType, excValue, traceback):\n        pass\n\n\n\nnonePIDFile = NonePIDFile()\n\n\n\nclass AlreadyRunningError(Exception):\n    \"\"\"\n    Process is already running.\n    \"\"\"\n\n\n\nclass InvalidPIDFileError(Exception):\n    \"\"\"\n    PID file contents are invalid.\n    \"\"\"\n\n\n\nclass StalePIDFileError(Exception):\n    \"\"\"\n    PID file contents are valid, but there is no process with the referenced\n    PID.\n    \"\"\"\n\n\n\nclass NoPIDFound(Exception):\n    \"\"\"\n    No PID found in PID file.\n    \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/runner/_runner.py",
    "content": "# -*- test-case-name: twisted.application.runner.test.test_runner -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTwisted application runner.\n\"\"\"\n\nfrom sys import stderr\nfrom signal import SIGTERM\nfrom os import kill\n\nfrom attr import attrib, attrs, Factory\n\nfrom twisted.logger import (\n    globalLogBeginner, textFileLogObserver,\n    FilteringLogObserver, LogLevelFilterPredicate,\n    LogLevel, Logger,\n)\n\nfrom ._exit import exit, ExitStatus\nfrom ._pidfile import nonePIDFile, AlreadyRunningError, InvalidPIDFileError\n\n\n\n@attrs(frozen=True)\nclass Runner(object):\n    \"\"\"\n    Twisted application runner.\n\n    @cvar _log: The logger attached to this class.\n    @type _log: L{Logger}\n\n    @ivar _reactor: The reactor to start and run the application in.\n    @type _reactor: L{IReactorCore}\n\n    @ivar _pidFile: The file to store the running process ID in.\n    @type _pidFile: L{IPIDFile}\n\n    @ivar _kill: Whether this runner should kill an existing running\n        instance of the application.\n    @type _kill: L{bool}\n\n    @ivar _defaultLogLevel: The default log level to start the logging\n        system with.\n    @type _defaultLogLevel: L{constantly.NamedConstant} from L{LogLevel}\n\n    @ivar _logFile: A file stream to write logging output to.\n    @type _logFile: writable file-like object\n\n    @ivar _fileLogObserverFactory: A factory for the file log observer to\n        use when starting the logging system.\n    @type _pidFile: callable that takes a single writable file-like object\n        argument and returns a L{twisted.logger.FileLogObserver}\n\n    @ivar _whenRunning: Hook to call after the reactor is running;\n        this is where the application code that relies on the reactor gets\n        called.\n    @type _whenRunning: callable that takes the keyword arguments specified\n        by C{whenRunningArguments}\n\n    @ivar _whenRunningArguments: Keyword arguments to pass to\n        C{whenRunning} when it is called.\n    @type _whenRunningArguments: L{dict}\n\n    @ivar _reactorExited: Hook to call after the reactor exits.\n    @type _reactorExited: callable that takes the keyword arguments\n        specified by C{reactorExitedArguments}\n\n    @ivar _reactorExitedArguments: Keyword arguments to pass to\n        C{reactorExited} when it is called.\n    @type _reactorExitedArguments: L{dict}\n    \"\"\"\n\n    _log = Logger()\n\n    _reactor                = attrib()\n    _pidFile                = attrib(default=nonePIDFile)\n    _kill                   = attrib(default=False)\n    _defaultLogLevel        = attrib(default=LogLevel.info)\n    _logFile                = attrib(default=stderr)\n    _fileLogObserverFactory = attrib(default=textFileLogObserver)\n    _whenRunning            = attrib(default=lambda **_: None)\n    _whenRunningArguments   = attrib(default=Factory(dict))\n    _reactorExited          = attrib(default=lambda **_: None)\n    _reactorExitedArguments = attrib(default=Factory(dict))\n\n\n    def run(self):\n        \"\"\"\n        Run this command.\n        \"\"\"\n        pidFile = self._pidFile\n\n        self.killIfRequested()\n\n        try:\n            with pidFile:\n                self.startLogging()\n                self.startReactor()\n                self.reactorExited()\n\n        except AlreadyRunningError:\n            exit(ExitStatus.EX_CONFIG, \"Already running.\")\n            return  # When testing, patched exit doesn't exit\n\n\n    def killIfRequested(self):\n        \"\"\"\n        If C{self._kill} is true, attempt to kill a running instance of the\n        application.\n        \"\"\"\n        pidFile = self._pidFile\n\n        if self._kill:\n            if pidFile is nonePIDFile:\n                exit(ExitStatus.EX_USAGE, \"No PID file specified.\")\n                return  # When testing, patched exit doesn't exit\n\n            try:\n                pid = pidFile.read()\n            except EnvironmentError:\n                exit(ExitStatus.EX_IOERR, \"Unable to read PID file.\")\n                return  # When testing, patched exit doesn't exit\n            except InvalidPIDFileError:\n                exit(ExitStatus.EX_DATAERR, \"Invalid PID file.\")\n                return  # When testing, patched exit doesn't exit\n\n            self.startLogging()\n            self._log.info(\"Terminating process: {pid}\", pid=pid)\n\n            kill(pid, SIGTERM)\n\n            exit(ExitStatus.EX_OK)\n            return  # When testing, patched exit doesn't exit\n\n\n    def startLogging(self):\n        \"\"\"\n        Start the L{twisted.logger} logging system.\n        \"\"\"\n        logFile = self._logFile\n\n        fileLogObserverFactory = self._fileLogObserverFactory\n\n        fileLogObserver = fileLogObserverFactory(logFile)\n\n        logLevelPredicate = LogLevelFilterPredicate(\n            defaultLogLevel=self._defaultLogLevel\n        )\n\n        filteringObserver = FilteringLogObserver(\n            fileLogObserver, [logLevelPredicate]\n        )\n\n        globalLogBeginner.beginLoggingTo([filteringObserver])\n\n\n    def startReactor(self):\n        \"\"\"\n        Register C{self._whenRunning} with the reactor so that it is called\n        once the reactor is running, then start the reactor.\n        \"\"\"\n        self._reactor.callWhenRunning(self.whenRunning)\n\n        self._log.info(\"Starting reactor...\")\n        self._reactor.run()\n\n\n    def whenRunning(self):\n        \"\"\"\n        Call C{self._whenRunning} with C{self._whenRunningArguments}.\n\n        @note: This method is called after the reactor starts running.\n        \"\"\"\n        self._whenRunning(**self._whenRunningArguments)\n\n\n    def reactorExited(self):\n        \"\"\"\n        Call C{self._reactorExited} with C{self._reactorExitedArguments}.\n\n        @note: This method is called after the reactor exits.\n        \"\"\"\n        self._reactorExited(**self._reactorExitedArguments)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/runner/test/__init__.py",
    "content": "# -*- test-case-name: twisted.application.runner.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.application.runner}.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/runner/test/test_exit.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.application.runner._exit}.\n\"\"\"\n\nfrom twisted.python.compat import NativeStringIO\nfrom ...runner import _exit\nfrom .._exit import exit, ExitStatus\n\nimport twisted.trial.unittest\n\n\n\nclass ExitTests(twisted.trial.unittest.TestCase):\n    \"\"\"\n    Tests for L{exit}.\n    \"\"\"\n\n    def setUp(self):\n        self.exit = DummyExit()\n        self.patch(_exit, \"sysexit\", self.exit)\n\n\n    def test_exitStatusInt(self):\n        \"\"\"\n        L{exit} given an L{int} status code will pass it to L{sys.exit}.\n        \"\"\"\n        status = 1234\n        exit(status)\n        self.assertEqual(self.exit.arg, status)\n\n\n    def test_exitStatusStringNotInt(self):\n        \"\"\"\n        L{exit} given a L{str} status code that isn't a string integer raises\n        L{ValueError}.\n        \"\"\"\n        self.assertRaises(ValueError, exit, \"foo\")\n\n\n    def test_exitStatusStringInt(self):\n        \"\"\"\n        L{exit} given a L{str} status code that is a string integer passes the\n        corresponding L{int} to L{sys.exit}.\n        \"\"\"\n        exit(\"1234\")\n        self.assertEqual(self.exit.arg, 1234)\n\n\n    def test_exitConstant(self):\n        \"\"\"\n        L{exit} given a L{ValueConstant} status code passes the corresponding\n        value to L{sys.exit}.\n        \"\"\"\n        status = ExitStatus.EX_CONFIG\n        exit(status)\n        self.assertEqual(self.exit.arg, status.value)\n\n\n    def test_exitMessageZero(self):\n        \"\"\"\n        L{exit} given a status code of zero (C{0}) writes the given message to\n        standard output.\n        \"\"\"\n        out = NativeStringIO()\n        self.patch(_exit, \"stdout\", out)\n\n        message = \"Hello, world.\"\n        exit(0, message)\n\n        self.assertEqual(out.getvalue(), message + \"\\n\")\n\n\n    def test_exitMessageNonZero(self):\n        \"\"\"\n        L{exit} given a non-zero status code writes the given message to\n        standard error.\n        \"\"\"\n        out = NativeStringIO()\n        self.patch(_exit, \"stderr\", out)\n\n        message = \"Hello, world.\"\n        exit(64, message)\n\n        self.assertEqual(out.getvalue(), message + \"\\n\")\n\n\n\nclass DummyExit(object):\n    \"\"\"\n    Stub for L{sys.exit} that remembers whether it's been called and, if it\n    has, what argument it was given.\n    \"\"\"\n    def __init__(self):\n        self.exited = False\n\n\n    def __call__(self, arg=None):\n        assert not self.exited\n\n        self.arg    = arg\n        self.exited = True\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/runner/test/test_pidfile.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.application.runner._pidfile}.\n\"\"\"\n\nfrom functools import wraps\nimport errno\nfrom os import getpid, name as SYSTEM_NAME\nfrom io import BytesIO\n\nfrom zope.interface import implementer\nfrom zope.interface.verify import verifyObject\n\nfrom twisted.python.filepath import IFilePath\nfrom twisted.python.runtime import platform\n\nfrom ...runner import _pidfile\nfrom .._pidfile import (\n    IPIDFile, PIDFile, NonePIDFile,\n    AlreadyRunningError, InvalidPIDFileError, StalePIDFileError,\n    NoPIDFound,\n)\n\nimport twisted.trial.unittest\nfrom twisted.trial.unittest import SkipTest\n\n\ndef ifPlatformSupported(f):\n    \"\"\"\n    Decorator for tests that are not expected to work on all platforms.\n\n    Calling L{PIDFile.isRunning} currently raises L{NotImplementedError} on\n    non-POSIX platforms.\n\n    On an unsupported platform, we expect to see any test that calls\n    L{PIDFile.isRunning} to raise either L{NotImplementedError}, L{SkipTest},\n    or C{self.failureException}.\n    (C{self.failureException} may occur in a test that checks for a specific\n    exception but it gets NotImplementedError instead.)\n\n    @param f: The test method to decorate.\n    @type f: method\n\n    @return: The wrapped callable.\n    \"\"\"\n    @wraps(f)\n    def wrapper(self, *args, **kwargs):\n        supported = platform.getType() == \"posix\"\n\n        if supported:\n            return f(self, *args, **kwargs)\n        else:\n            e = self.assertRaises(\n                (NotImplementedError, SkipTest, self.failureException),\n                f, self, *args, **kwargs\n            )\n            if isinstance(e, NotImplementedError):\n                self.assertTrue(\n                    str(e).startswith(\"isRunning is not implemented on \")\n                )\n\n    return wrapper\n\n\n\nclass PIDFileTests(twisted.trial.unittest.TestCase):\n    \"\"\"\n    Tests for L{PIDFile}.\n    \"\"\"\n\n    def test_interface(self):\n        \"\"\"\n        L{PIDFile} conforms to L{IPIDFile}.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n        verifyObject(IPIDFile, pidFile)\n\n\n    def test_formatWithPID(self):\n        \"\"\"\n        L{PIDFile._format} returns the expected format when given a PID.\n        \"\"\"\n        self.assertEqual(PIDFile._format(pid=1337), b\"1337\\n\")\n\n\n    def test_readWithPID(self):\n        \"\"\"\n        L{PIDFile.read} returns the PID from the given file path.\n        \"\"\"\n        pid = 1337\n\n        pidFile = PIDFile(DummyFilePath(PIDFile._format(pid=pid)))\n\n        self.assertEqual(pid, pidFile.read())\n\n\n    def test_readEmptyPID(self):\n        \"\"\"\n        L{PIDFile.read} raises L{InvalidPIDFileError} when given an empty file\n        path.\n        \"\"\"\n        pidValue = b\"\"\n        pidFile = PIDFile(DummyFilePath(b\"\"))\n\n        e = self.assertRaises(InvalidPIDFileError, pidFile.read)\n        self.assertEqual(\n            str(e),\n            \"non-integer PID value in PID file: {!r}\".format(pidValue)\n        )\n\n\n    def test_readWithBogusPID(self):\n        \"\"\"\n        L{PIDFile.read} raises L{InvalidPIDFileError} when given an empty file\n        path.\n        \"\"\"\n        pidValue = b\"$foo!\"\n        pidFile = PIDFile(DummyFilePath(pidValue))\n\n        e = self.assertRaises(InvalidPIDFileError, pidFile.read)\n        self.assertEqual(\n            str(e),\n            \"non-integer PID value in PID file: {!r}\".format(pidValue)\n        )\n\n\n    def test_readDoesntExist(self):\n        \"\"\"\n        L{PIDFile.read} raises L{NoPIDFound} when given a non-existing file\n        path.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n\n        e = self.assertRaises(NoPIDFound, pidFile.read)\n        self.assertEqual(str(e), \"PID file does not exist\")\n\n\n    def test_readOpenRaisesOSErrorNotENOENT(self):\n        \"\"\"\n        L{PIDFile.read} re-raises L{OSError} if the associated C{errno} is\n        anything other than L{errno.ENOENT}.\n        \"\"\"\n        def oops(mode=\"r\"):\n            raise OSError(errno.EIO, \"I/O error\")\n\n        self.patch(DummyFilePath, \"open\", oops)\n\n        pidFile = PIDFile(DummyFilePath())\n\n        error = self.assertRaises(OSError, pidFile.read)\n        self.assertEqual(error.errno, errno.EIO)\n\n\n    def test_writePID(self):\n        \"\"\"\n        L{PIDFile._write} stores the given PID.\n        \"\"\"\n        pid = 1995\n\n        pidFile = PIDFile(DummyFilePath())\n        pidFile._write(pid)\n\n        self.assertEqual(pidFile.read(), pid)\n\n\n    def test_writePIDInvalid(self):\n        \"\"\"\n        L{PIDFile._write} raises L{ValueError} when given an invalid PID.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n\n        self.assertRaises(ValueError, pidFile._write, u\"burp\")\n\n\n    def test_writeRunningPID(self):\n        \"\"\"\n        L{PIDFile.writeRunningPID} stores the PID for the current process.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n        pidFile.writeRunningPID()\n\n        self.assertEqual(pidFile.read(), getpid())\n\n\n    def test_remove(self):\n        \"\"\"\n        L{PIDFile.remove} removes the PID file.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath(b\"\"))\n        self.assertTrue(pidFile.filePath.exists())\n\n        pidFile.remove()\n        self.assertFalse(pidFile.filePath.exists())\n\n\n    @ifPlatformSupported\n    def test_isRunningDoesExist(self):\n        \"\"\"\n        L{PIDFile.isRunning} returns true for a process that does exist.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n        pidFile._write(1337)\n\n        def kill(pid, signal):\n            return  # Don't actually kill anything\n\n        self.patch(_pidfile, \"kill\", kill)\n\n        self.assertTrue(pidFile.isRunning())\n\n\n    @ifPlatformSupported\n    def test_isRunningThis(self):\n        \"\"\"\n        L{PIDFile.isRunning} returns true for this process (which is running).\n\n        @note: This differs from L{PIDFileTests.test_isRunningDoesExist} in\n        that it actually invokes the C{kill} system call, which is useful for\n        testing of our chosen method for probing the existence of a process.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n        pidFile.writeRunningPID()\n\n        self.assertTrue(pidFile.isRunning())\n\n\n    @ifPlatformSupported\n    def test_isRunningDoesNotExist(self):\n        \"\"\"\n        L{PIDFile.isRunning} raises L{StalePIDFileError} for a process that\n        does not exist (errno=ESRCH).\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n        pidFile._write(1337)\n\n        def kill(pid, signal):\n            raise OSError(errno.ESRCH, \"No such process\")\n\n        self.patch(_pidfile, \"kill\", kill)\n\n        self.assertRaises(StalePIDFileError, pidFile.isRunning)\n\n\n    @ifPlatformSupported\n    def test_isRunningNotAllowed(self):\n        \"\"\"\n        L{PIDFile.isRunning} returns true for a process that we are not allowed\n        to kill (errno=EPERM).\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n        pidFile._write(1337)\n\n        def kill(pid, signal):\n            raise OSError(errno.EPERM, \"Operation not permitted\")\n\n        self.patch(_pidfile, \"kill\", kill)\n\n        self.assertTrue(pidFile.isRunning())\n\n\n    @ifPlatformSupported\n    def test_isRunningInit(self):\n        \"\"\"\n        L{PIDFile.isRunning} returns true for a process that we are not allowed\n        to kill (errno=EPERM).\n\n        @note: This differs from L{PIDFileTests.test_isRunningNotAllowed} in\n        that it actually invokes the C{kill} system call, which is useful for\n        testing of our chosen method for probing the existence of a process\n        that we are not allowed to kill.\n\n        @note: In this case, we try killing C{init}, which is process #1 on\n        POSIX systems, so this test is not portable.  C{init} should always be\n        running and should not be killable by non-root users.\n        \"\"\"\n        if SYSTEM_NAME != \"posix\":\n            raise SkipTest(\"This test assumes POSIX\")\n\n        pidFile = PIDFile(DummyFilePath())\n        pidFile._write(1)  # PID 1 is init on POSIX systems\n\n        self.assertTrue(pidFile.isRunning())\n\n\n    @ifPlatformSupported\n    def test_isRunningUnknownErrno(self):\n        \"\"\"\n        L{PIDFile.isRunning} re-raises L{OSError} if the attached C{errno}\n        value from L{os.kill} is not an expected one.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n        pidFile.writeRunningPID()\n\n        def kill(pid, signal):\n            raise OSError(errno.EEXIST, \"File exists\")\n\n        self.patch(_pidfile, \"kill\", kill)\n\n        self.assertRaises(OSError, pidFile.isRunning)\n\n\n    def test_isRunningNoPIDFile(self):\n        \"\"\"\n        L{PIDFile.isRunning} returns false if the PID file doesn't exist.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n\n        self.assertFalse(pidFile.isRunning())\n\n\n    def test_contextManager(self):\n        \"\"\"\n        When used as a context manager, a L{PIDFile} will store the current pid\n        on entry, then removes the PID file on exit.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n        self.assertFalse(pidFile.filePath.exists())\n\n        with pidFile:\n            self.assertTrue(pidFile.filePath.exists())\n            self.assertEqual(pidFile.read(), getpid())\n\n        self.assertFalse(pidFile.filePath.exists())\n\n\n    @ifPlatformSupported\n    def test_contextManagerDoesntExist(self):\n        \"\"\"\n        When used as a context manager, a L{PIDFile} will replace the\n        underlying PIDFile rather than raising L{AlreadyRunningError} if the\n        contained PID file exists but refers to a non-running PID.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n        pidFile._write(1337)\n\n        def kill(pid, signal):\n            raise OSError(errno.ESRCH, \"No such process\")\n\n        self.patch(_pidfile, \"kill\", kill)\n\n        e = self.assertRaises(StalePIDFileError, pidFile.isRunning)\n        self.assertEqual(str(e), \"PID file refers to non-existing process\")\n\n        with pidFile:\n            self.assertEqual(pidFile.read(), getpid())\n\n\n    @ifPlatformSupported\n    def test_contextManagerAlreadyRunning(self):\n        \"\"\"\n        When used as a context manager, a L{PIDFile} will raise\n        L{AlreadyRunningError} if the there is already a running process with\n        the contained PID.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath())\n        pidFile._write(1337)\n\n        def kill(pid, signal):\n            return  # Don't actually kill anything\n\n        self.patch(_pidfile, \"kill\", kill)\n\n        self.assertTrue(pidFile.isRunning())\n\n        self.assertRaises(AlreadyRunningError, pidFile.__enter__)\n\n\n\nclass NonePIDFileTests(twisted.trial.unittest.TestCase):\n    \"\"\"\n    Tests for L{NonePIDFile}.\n    \"\"\"\n\n    def test_interface(self):\n        \"\"\"\n        L{NonePIDFile} conforms to L{IPIDFile}.\n        \"\"\"\n        pidFile = NonePIDFile()\n        verifyObject(IPIDFile, pidFile)\n\n\n    def test_read(self):\n        \"\"\"\n        L{NonePIDFile.read} raises L{NoPIDFound}.\n        \"\"\"\n        pidFile = NonePIDFile()\n\n        e = self.assertRaises(NoPIDFound, pidFile.read)\n        self.assertEqual(str(e), \"PID file does not exist\")\n\n\n    def test_write(self):\n        \"\"\"\n        L{NonePIDFile._write} raises L{OSError} with an errno of L{errno.EPERM}.\n        \"\"\"\n        pidFile = NonePIDFile()\n\n        error = self.assertRaises(OSError, pidFile._write, 0)\n        self.assertEqual(error.errno, errno.EPERM)\n\n\n    def test_writeRunningPID(self):\n        \"\"\"\n        L{NonePIDFile.writeRunningPID} raises L{OSError} with an errno of\n        L{errno.EPERM}.\n        \"\"\"\n        pidFile = NonePIDFile()\n\n        error = self.assertRaises(OSError, pidFile.writeRunningPID)\n        self.assertEqual(error.errno, errno.EPERM)\n\n\n    def test_remove(self):\n        \"\"\"\n        L{NonePIDFile.remove} raises L{OSError} with an errno of L{errno.EPERM}.\n        \"\"\"\n        pidFile = NonePIDFile()\n\n        error = self.assertRaises(OSError, pidFile.remove)\n        self.assertEqual(error.errno, errno.ENOENT)\n\n\n    def test_isRunning(self):\n        \"\"\"\n        L{NonePIDFile.isRunning} returns L{False}.\n        \"\"\"\n        pidFile = NonePIDFile()\n\n        self.assertEqual(pidFile.isRunning(), False)\n\n\n    def test_contextManager(self):\n        \"\"\"\n        When used as a context manager, a L{NonePIDFile} doesn't raise, despite\n        not existing.\n        \"\"\"\n        pidFile = NonePIDFile()\n\n        with pidFile:\n            pass\n\n\n\n@implementer(IFilePath)\nclass DummyFilePath(object):\n    \"\"\"\n    In-memory L{IFilePath}.\n    \"\"\"\n\n    def __init__(self, content=None):\n        self.setContent(content)\n\n\n    def open(self, mode=\"r\"):\n        if not self._exists:\n            raise OSError(errno.ENOENT, \"No such file or directory\")\n        return BytesIO(self.getContent())\n\n\n    def setContent(self, content):\n        self._exists = content is not None\n        self._content = content\n\n\n    def getContent(self):\n        return self._content\n\n\n    def remove(self):\n        self.setContent(None)\n\n\n    def exists(self):\n        return self._exists\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/runner/test/test_runner.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.application.runner._runner}.\n\"\"\"\n\nfrom signal import SIGTERM\nfrom io import BytesIO\nimport errno\n\nfrom attr import attrib, attrs, Factory\n\nfrom twisted.logger import (\n    LogLevel, LogPublisher, LogBeginner,\n    FileLogObserver, FilteringLogObserver, LogLevelFilterPredicate,\n)\nfrom twisted.test.proto_helpers import MemoryReactor\n\nfrom ...runner import _runner\nfrom .._exit import ExitStatus\nfrom .._pidfile import PIDFile, NonePIDFile\nfrom .._runner import Runner\nfrom .test_pidfile import DummyFilePath\n\nimport twisted.trial.unittest\n\n\n\nclass RunnerTests(twisted.trial.unittest.TestCase):\n    \"\"\"\n    Tests for L{Runner}.\n    \"\"\"\n\n    def setUp(self):\n        # Patch exit and kill so we can capture usage and prevent actual exits\n        # and kills.\n\n        self.exit = DummyExit()\n        self.kill = DummyKill()\n\n        self.patch(_runner, \"exit\", self.exit)\n        self.patch(_runner, \"kill\", self.kill)\n\n        # Patch getpid so we get a known result\n\n        self.pid = 1337\n        self.pidFileContent = u\"{}\\n\".format(self.pid).encode(\"utf-8\")\n\n        # Patch globalLogBeginner so that we aren't trying to install multiple\n        # global log observers.\n\n        self.stdout = BytesIO()\n        self.stderr = BytesIO()\n        self.stdio = DummyStandardIO(self.stdout, self.stderr)\n        self.warnings = DummyWarningsModule()\n\n        self.globalLogPublisher = LogPublisher()\n        self.globalLogBeginner = LogBeginner(\n            self.globalLogPublisher,\n            self.stdio.stderr, self.stdio,\n            self.warnings,\n        )\n\n        self.patch(_runner, \"stderr\", self.stderr)\n        self.patch(_runner, \"globalLogBeginner\", self.globalLogBeginner)\n\n\n    def test_runInOrder(self):\n        \"\"\"\n        L{Runner.run} calls the expected methods in order.\n        \"\"\"\n        runner = DummyRunner(reactor=MemoryReactor())\n        runner.run()\n\n        self.assertEqual(\n            runner.calledMethods,\n            [\n                \"killIfRequested\",\n                \"startLogging\",\n                \"startReactor\",\n                \"reactorExited\",\n            ]\n        )\n\n\n    def test_runUsesPIDFile(self):\n        \"\"\"\n        L{Runner.run} uses the provided PID file.\n        \"\"\"\n        pidFile = DummyPIDFile()\n\n        runner = Runner(reactor=MemoryReactor(), pidFile=pidFile)\n\n        self.assertFalse(pidFile.entered)\n        self.assertFalse(pidFile.exited)\n\n        runner.run()\n\n        self.assertTrue(pidFile.entered)\n        self.assertTrue(pidFile.exited)\n\n\n    def test_runAlreadyRunning(self):\n        \"\"\"\n        L{Runner.run} exits with L{ExitStatus.EX_USAGE} and the expected\n        message if a process is already running that corresponds to the given\n        PID file.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath(self.pidFileContent))\n        pidFile.isRunning = lambda: True\n\n        runner = Runner(reactor=MemoryReactor(), pidFile=pidFile)\n        runner.run()\n\n        self.assertEqual(self.exit.status, ExitStatus.EX_CONFIG)\n        self.assertEqual(self.exit.message, \"Already running.\")\n\n\n    def test_killNotRequested(self):\n        \"\"\"\n        L{Runner.killIfRequested} when C{kill} is false doesn't exit and\n        doesn't indiscriminately murder anyone.\n        \"\"\"\n        runner = Runner(reactor=MemoryReactor())\n        runner.killIfRequested()\n\n        self.assertEqual(self.kill.calls, [])\n        self.assertFalse(self.exit.exited)\n\n\n    def test_killRequestedWithoutPIDFile(self):\n        \"\"\"\n        L{Runner.killIfRequested} when C{kill} is true but C{pidFile} is\n        L{nonePIDFile} exits with L{ExitStatus.EX_USAGE} and the expected\n        message; and also doesn't indiscriminately murder anyone.\n        \"\"\"\n        runner = Runner(reactor=MemoryReactor(), kill=True)\n        runner.killIfRequested()\n\n        self.assertEqual(self.kill.calls, [])\n        self.assertEqual(self.exit.status, ExitStatus.EX_USAGE)\n        self.assertEqual(self.exit.message, \"No PID file specified.\")\n\n\n    def test_killRequestedWithPIDFile(self):\n        \"\"\"\n        L{Runner.killIfRequested} when C{kill} is true and given a C{pidFile}\n        performs a targeted killing of the appropriate process.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath(self.pidFileContent))\n        runner = Runner(reactor=MemoryReactor(), kill=True, pidFile=pidFile)\n        runner.killIfRequested()\n\n        self.assertEqual(self.kill.calls, [(self.pid, SIGTERM)])\n        self.assertEqual(self.exit.status, ExitStatus.EX_OK)\n        self.assertIdentical(self.exit.message, None)\n\n\n    def test_killRequestedWithPIDFileCantRead(self):\n        \"\"\"\n        L{Runner.killIfRequested} when C{kill} is true and given a C{pidFile}\n        that it can't read exits with L{ExitStatus.EX_IOERR}.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath(None))\n\n        def read():\n            raise OSError(errno.EACCES, \"Permission denied\")\n\n        pidFile.read = read\n\n        runner = Runner(reactor=MemoryReactor(), kill=True, pidFile=pidFile)\n        runner.killIfRequested()\n\n        self.assertEqual(self.exit.status, ExitStatus.EX_IOERR)\n        self.assertEqual(self.exit.message, \"Unable to read PID file.\")\n\n\n    def test_killRequestedWithPIDFileEmpty(self):\n        \"\"\"\n        L{Runner.killIfRequested} when C{kill} is true and given a C{pidFile}\n        containing no value exits with L{ExitStatus.EX_DATAERR}.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath(b\"\"))\n        runner = Runner(reactor=MemoryReactor(), kill=True, pidFile=pidFile)\n        runner.killIfRequested()\n\n        self.assertEqual(self.exit.status, ExitStatus.EX_DATAERR)\n        self.assertEqual(self.exit.message, \"Invalid PID file.\")\n\n\n    def test_killRequestedWithPIDFileNotAnInt(self):\n        \"\"\"\n        L{Runner.killIfRequested} when C{kill} is true and given a C{pidFile}\n        containing a non-integer value exits with L{ExitStatus.EX_DATAERR}.\n        \"\"\"\n        pidFile = PIDFile(DummyFilePath(b\"** totally not a number, dude **\"))\n        runner = Runner(reactor=MemoryReactor(), kill=True, pidFile=pidFile)\n        runner.killIfRequested()\n\n        self.assertEqual(self.exit.status, ExitStatus.EX_DATAERR)\n        self.assertEqual(self.exit.message, \"Invalid PID file.\")\n\n\n    def test_startLogging(self):\n        \"\"\"\n        L{Runner.startLogging} sets up a filtering observer with a log level\n        predicate set to the given log level that contains a file observer of\n        the given type which writes to the given file.\n        \"\"\"\n        logFile = BytesIO()\n\n        # Patch the log beginner so that we don't try to start the already\n        # running (started by trial) logging system.\n\n        class LogBeginner(object):\n            def beginLoggingTo(self, observers):\n                LogBeginner.observers = observers\n\n        self.patch(_runner, \"globalLogBeginner\", LogBeginner())\n\n        # Patch FilteringLogObserver so we can capture its arguments\n\n        class MockFilteringLogObserver(FilteringLogObserver):\n            def __init__(\n                self, observer, predicates,\n                negativeObserver=lambda event: None\n            ):\n                MockFilteringLogObserver.observer = observer\n                MockFilteringLogObserver.predicates = predicates\n                FilteringLogObserver.__init__(\n                    self, observer, predicates, negativeObserver\n                )\n\n        self.patch(_runner, \"FilteringLogObserver\", MockFilteringLogObserver)\n\n        # Patch FileLogObserver so we can capture its arguments\n\n        class MockFileLogObserver(FileLogObserver):\n            def __init__(self, outFile):\n                MockFileLogObserver.outFile = outFile\n                FileLogObserver.__init__(self, outFile, str)\n\n        # Start logging\n        runner = Runner(\n            reactor=MemoryReactor(),\n            defaultLogLevel=LogLevel.critical,\n            logFile=logFile,\n            fileLogObserverFactory=MockFileLogObserver,\n        )\n        runner.startLogging()\n\n        # Check for a filtering observer\n        self.assertEqual(len(LogBeginner.observers), 1)\n        self.assertIsInstance(LogBeginner.observers[0], FilteringLogObserver)\n\n        # Check log level predicate with the correct default log level\n        self.assertEqual(len(MockFilteringLogObserver.predicates), 1)\n        self.assertIsInstance(\n            MockFilteringLogObserver.predicates[0],\n            LogLevelFilterPredicate\n        )\n        self.assertIdentical(\n            MockFilteringLogObserver.predicates[0].defaultLogLevel,\n            LogLevel.critical\n        )\n\n        # Check for a file observer attached to the filtering observer\n        self.assertIsInstance(\n            MockFilteringLogObserver.observer, MockFileLogObserver\n        )\n\n        # Check for the file we gave it\n        self.assertIdentical(\n            MockFilteringLogObserver.observer.outFile, logFile\n        )\n\n\n    def test_startReactorWithReactor(self):\n        \"\"\"\n        L{Runner.startReactor} with the C{reactor} argument runs the given\n        reactor.\n        \"\"\"\n        reactor = MemoryReactor()\n        runner = Runner(reactor=reactor)\n        runner.startReactor()\n\n        self.assertTrue(reactor.hasRun)\n\n\n    def test_startReactorWhenRunning(self):\n        \"\"\"\n        L{Runner.startReactor} ensures that C{whenRunning} is called with\n        C{whenRunningArguments} when the reactor is running.\n        \"\"\"\n        self._testHook(\"whenRunning\", \"startReactor\")\n\n\n    def test_whenRunningWithArguments(self):\n        \"\"\"\n        L{Runner.whenRunning} calls C{whenRunning} with\n        C{whenRunningArguments}.\n        \"\"\"\n        self._testHook(\"whenRunning\")\n\n\n    def test_reactorExitedWithArguments(self):\n        \"\"\"\n        L{Runner.whenRunning} calls C{reactorExited} with\n        C{reactorExitedArguments}.\n        \"\"\"\n        self._testHook(\"reactorExited\")\n\n\n    def _testHook(self, methodName, callerName=None):\n        \"\"\"\n        Verify that the named hook is run with the expected arguments as\n        specified by the arguments used to create the L{Runner}, when the\n        specified caller is invoked.\n\n        @param methodName: The name of the hook to verify.\n        @type methodName: L{str}\n\n        @param callerName: The name of the method that is expected to cause the\n            hook to be called.\n            If C{None}, use the L{Runner} method with the same name as the\n            hook.\n        @type callerName: L{str}\n        \"\"\"\n        if callerName is None:\n            callerName = methodName\n\n        arguments = dict(a=object(), b=object(), c=object())\n        argumentsSeen = []\n\n        def hook(**arguments):\n            argumentsSeen.append(arguments)\n\n        runnerArguments = {\n            methodName: hook,\n            \"{}Arguments\".format(methodName): arguments.copy(),\n        }\n        runner = Runner(reactor=MemoryReactor(), **runnerArguments)\n\n        hookCaller = getattr(runner, callerName)\n        hookCaller()\n\n        self.assertEqual(len(argumentsSeen), 1)\n        self.assertEqual(argumentsSeen[0], arguments)\n\n\n\n@attrs(frozen=True)\nclass DummyRunner(Runner):\n    \"\"\"\n    Stub for L{Runner}.\n\n    Keep track of calls to some methods without actually doing anything.\n    \"\"\"\n\n    calledMethods = attrib(default=Factory(list))\n\n\n    def killIfRequested(self):\n        self.calledMethods.append(\"killIfRequested\")\n\n\n    def startLogging(self):\n        self.calledMethods.append(\"startLogging\")\n\n\n    def startReactor(self):\n        self.calledMethods.append(\"startReactor\")\n\n\n    def reactorExited(self):\n        self.calledMethods.append(\"reactorExited\")\n\n\n\nclass DummyPIDFile(NonePIDFile):\n    \"\"\"\n    Stub for L{PIDFile}.\n\n    Tracks context manager entry/exit without doing anything.\n    \"\"\"\n    def __init__(self):\n        NonePIDFile.__init__(self)\n\n        self.entered = False\n        self.exited  = False\n\n\n    def __enter__(self):\n        self.entered = True\n        return self\n\n\n    def __exit__(self, excType, excValue, traceback):\n        self.exited  = True\n\n\n\nclass DummyExit(object):\n    \"\"\"\n    Stub for L{exit} that remembers whether it's been called and, if it has,\n    what arguments it was given.\n    \"\"\"\n\n    def __init__(self):\n        self.exited = False\n\n\n    def __call__(self, status, message=None):\n        assert not self.exited\n\n        self.status  = status\n        self.message = message\n        self.exited  = True\n\n\n\nclass DummyKill(object):\n    \"\"\"\n    Stub for L{os.kill} that remembers whether it's been called and, if it has,\n    what arguments it was given.\n    \"\"\"\n\n    def __init__(self):\n        self.calls = []\n\n\n    def __call__(self, pid, sig):\n        self.calls.append((pid, sig))\n\n\n\nclass DummyStandardIO(object):\n    \"\"\"\n    Stub for L{sys} which provides L{BytesIO} streams as stdout and stderr.\n    \"\"\"\n\n    def __init__(self, stdout, stderr):\n        self.stdout = stdout\n        self.stderr = stderr\n\n\n\nclass DummyWarningsModule(object):\n    \"\"\"\n    Stub for L{warnings} which provides a C{showwarning} method that is a no-op.\n    \"\"\"\n\n    def showwarning(*args, **kwargs):\n        \"\"\"\n        Do nothing.\n\n        @param args: ignored.\n        @param kwargs: ignored.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/service.py",
    "content": "# -*- test-case-name: twisted.application.test.test_service -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nService architecture for Twisted.\n\nServices are arranged in a hierarchy. At the leafs of the hierarchy,\nthe services which actually interact with the outside world are started.\nServices can be named or anonymous -- usually, they will be named if\nthere is need to access them through the hierarchy (from a parent or\na sibling).\n\nMaintainer: Moshe Zadka\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom zope.interface import implementer, Interface, Attribute\n\nfrom twisted.persisted import sob\nfrom twisted.python.reflect import namedAny\nfrom twisted.python import components\nfrom twisted.python._oldstyle import _oldStyle\nfrom twisted.internet import defer\nfrom twisted.plugin import IPlugin\n\n\nclass IServiceMaker(Interface):\n    \"\"\"\n    An object which can be used to construct services in a flexible\n    way.\n\n    This interface should most often be implemented along with\n    L{twisted.plugin.IPlugin}, and will most often be used by the\n    'twistd' command.\n    \"\"\"\n    tapname = Attribute(\n        \"A short string naming this Twisted plugin, for example 'web' or \"\n        \"'pencil'. This name will be used as the subcommand of 'twistd'.\")\n\n    description = Attribute(\n        \"A brief summary of the features provided by this \"\n        \"Twisted application plugin.\")\n\n    options = Attribute(\n        \"A C{twisted.python.usage.Options} subclass defining the \"\n        \"configuration options for this application.\")\n\n\n    def makeService(options):\n        \"\"\"\n        Create and return an object providing\n        L{twisted.application.service.IService}.\n\n        @param options: A mapping (typically a C{dict} or\n        L{twisted.python.usage.Options} instance) of configuration\n        options to desired configuration values.\n        \"\"\"\n\n\n\n@implementer(IPlugin, IServiceMaker)\nclass ServiceMaker(object):\n    \"\"\"\n    Utility class to simplify the definition of L{IServiceMaker} plugins.\n    \"\"\"\n    def __init__(self, name, module, description, tapname):\n        self.name = name\n        self.module = module\n        self.description = description\n        self.tapname = tapname\n\n\n    def options():\n        def get(self):\n            return namedAny(self.module).Options\n        return get,\n    options = property(*options())\n\n\n    def makeService():\n        def get(self):\n            return namedAny(self.module).makeService\n        return get,\n    makeService = property(*makeService())\n\n\n\nclass IService(Interface):\n    \"\"\"\n    A service.\n\n    Run start-up and shut-down code at the appropriate times.\n    \"\"\"\n\n    name = Attribute(\n        \"A C{str} which is the name of the service or C{None}.\")\n\n    running = Attribute(\n        \"A C{boolean} which indicates whether the service is running.\")\n\n    parent = Attribute(\n        \"An C{IServiceCollection} which is the parent or C{None}.\")\n\n    def setName(name):\n        \"\"\"\n        Set the name of the service.\n\n        @type name: C{str}\n        @raise RuntimeError: Raised if the service already has a parent.\n        \"\"\"\n\n    def setServiceParent(parent):\n        \"\"\"\n        Set the parent of the service.  This method is responsible for setting\n        the C{parent} attribute on this service (the child service).\n\n        @type parent: L{IServiceCollection}\n        @raise RuntimeError: Raised if the service already has a parent\n            or if the service has a name and the parent already has a child\n            by that name.\n        \"\"\"\n\n    def disownServiceParent():\n        \"\"\"\n        Use this API to remove an L{IService} from an L{IServiceCollection}.\n\n        This method is used symmetrically with L{setServiceParent} in that it\n        sets the C{parent} attribute on the child.\n\n        @rtype: L{Deferred<defer.Deferred>}\n        @return: a L{Deferred<defer.Deferred>} which is triggered when the\n            service has finished shutting down. If shutting down is immediate,\n            a value can be returned (usually, L{None}).\n        \"\"\"\n\n    def startService():\n        \"\"\"\n        Start the service.\n        \"\"\"\n\n    def stopService():\n        \"\"\"\n        Stop the service.\n\n        @rtype: L{Deferred<defer.Deferred>}\n        @return: a L{Deferred<defer.Deferred>} which is triggered when the\n            service has finished shutting down. If shutting down is immediate,\n            a value can be returned (usually, L{None}).\n        \"\"\"\n\n    def privilegedStartService():\n        \"\"\"\n        Do preparation work for starting the service.\n\n        Here things which should be done before changing directory,\n        root or shedding privileges are done.\n        \"\"\"\n\n\n\n@implementer(IService)\nclass Service(object):\n    \"\"\"\n    Base class for services.\n\n    Most services should inherit from this class. It handles the\n    book-keeping responsibilities of starting and stopping, as well\n    as not serializing this book-keeping information.\n    \"\"\"\n\n    running = 0\n    name = None\n    parent = None\n\n    def __getstate__(self):\n        dict = self.__dict__.copy()\n        if \"running\" in dict:\n            del dict['running']\n        return dict\n\n    def setName(self, name):\n        if self.parent is not None:\n            raise RuntimeError(\"cannot change name when parent exists\")\n        self.name = name\n\n    def setServiceParent(self, parent):\n        if self.parent is not None:\n            self.disownServiceParent()\n        parent = IServiceCollection(parent, parent)\n        self.parent = parent\n        self.parent.addService(self)\n\n    def disownServiceParent(self):\n        d = self.parent.removeService(self)\n        self.parent = None\n        return d\n\n    def privilegedStartService(self):\n        pass\n\n    def startService(self):\n        self.running = 1\n\n    def stopService(self):\n        self.running = 0\n\n\n\nclass IServiceCollection(Interface):\n    \"\"\"\n    Collection of services.\n\n    Contain several services, and manage their start-up/shut-down.\n    Services can be accessed by name if they have a name, and it\n    is always possible to iterate over them.\n    \"\"\"\n\n    def getServiceNamed(name):\n        \"\"\"\n        Get the child service with a given name.\n\n        @type name: C{str}\n        @rtype: L{IService}\n        @raise KeyError: Raised if the service has no child with the\n            given name.\n        \"\"\"\n\n    def __iter__():\n        \"\"\"\n        Get an iterator over all child services.\n        \"\"\"\n\n    def addService(service):\n        \"\"\"\n        Add a child service.\n\n        Only implementations of L{IService.setServiceParent} should use this\n        method.\n\n        @type service: L{IService}\n        @raise RuntimeError: Raised if the service has a child with\n            the given name.\n        \"\"\"\n\n    def removeService(service):\n        \"\"\"\n        Remove a child service.\n\n        Only implementations of L{IService.disownServiceParent} should\n        use this method.\n\n        @type service: L{IService}\n        @raise ValueError: Raised if the given service is not a child.\n        @rtype: L{Deferred<defer.Deferred>}\n        @return: a L{Deferred<defer.Deferred>} which is triggered when the\n            service has finished shutting down. If shutting down is immediate,\n            a value can be returned (usually, L{None}).\n        \"\"\"\n\n\n\n@implementer(IServiceCollection)\nclass MultiService(Service):\n    \"\"\"\n    Straightforward Service Container.\n\n    Hold a collection of services, and manage them in a simplistic\n    way. No service will wait for another, but this object itself\n    will not finish shutting down until all of its child services\n    will finish.\n    \"\"\"\n\n    def __init__(self):\n        self.services = []\n        self.namedServices = {}\n        self.parent = None\n\n    def privilegedStartService(self):\n        Service.privilegedStartService(self)\n        for service in self:\n            service.privilegedStartService()\n\n    def startService(self):\n        Service.startService(self)\n        for service in self:\n            service.startService()\n\n    def stopService(self):\n        Service.stopService(self)\n        l = []\n        services = list(self)\n        services.reverse()\n        for service in services:\n            l.append(defer.maybeDeferred(service.stopService))\n        return defer.DeferredList(l)\n\n    def getServiceNamed(self, name):\n        return self.namedServices[name]\n\n    def __iter__(self):\n        return iter(self.services)\n\n    def addService(self, service):\n        if service.name is not None:\n            if service.name in self.namedServices:\n                raise RuntimeError(\"cannot have two services with same name\"\n                                   \" '%s'\" % service.name)\n            self.namedServices[service.name] = service\n        self.services.append(service)\n        if self.running:\n            # It may be too late for that, but we will do our best\n            service.privilegedStartService()\n            service.startService()\n\n    def removeService(self, service):\n        if service.name:\n            del self.namedServices[service.name]\n        self.services.remove(service)\n        if self.running:\n            # Returning this so as not to lose information from the\n            # MultiService.stopService deferred.\n            return service.stopService()\n        else:\n            return None\n\n\n\nclass IProcess(Interface):\n    \"\"\"\n    Process running parameters.\n\n    Represents parameters for how processes should be run.\n    \"\"\"\n    processName = Attribute(\n        \"\"\"\n        A C{str} giving the name the process should have in ps (or L{None}\n        to leave the name alone).\n        \"\"\")\n\n    uid = Attribute(\n        \"\"\"\n        An C{int} giving the user id as which the process should run (or\n        L{None} to leave the UID alone).\n        \"\"\")\n\n    gid = Attribute(\n        \"\"\"\n        An C{int} giving the group id as which the process should run (or\n        L{None} to leave the GID alone).\n        \"\"\")\n\n\n\n@implementer(IProcess)\n@_oldStyle\nclass Process:\n    \"\"\"\n    Process running parameters.\n\n    Sets up uid/gid in the constructor, and has a default\n    of L{None} as C{processName}.\n    \"\"\"\n    processName = None\n\n    def __init__(self, uid=None, gid=None):\n        \"\"\"\n        Set uid and gid.\n\n        @param uid: The user ID as whom to execute the process.  If\n            this is L{None}, no attempt will be made to change the UID.\n\n        @param gid: The group ID as whom to execute the process.  If\n            this is L{None}, no attempt will be made to change the GID.\n        \"\"\"\n        self.uid = uid\n        self.gid = gid\n\n\n\ndef Application(name, uid=None, gid=None):\n    \"\"\"\n    Return a compound class.\n\n    Return an object supporting the L{IService}, L{IServiceCollection},\n    L{IProcess} and L{sob.IPersistable} interfaces, with the given\n    parameters. Always access the return value by explicit casting to\n    one of the interfaces.\n    \"\"\"\n    ret = components.Componentized()\n    availableComponents = [MultiService(), Process(uid, gid),\n                           sob.Persistent(ret, name)]\n\n    for comp in availableComponents:\n        ret.addComponent(comp, ignoreClass=1)\n    IService(ret).setName(name)\n    return ret\n\n\n\ndef loadApplication(filename, kind, passphrase=None):\n    \"\"\"\n    Load Application from a given file.\n\n    The serialization format it was saved in should be given as\n    C{kind}, and is one of C{pickle}, C{source}, C{xml} or C{python}. If\n    C{passphrase} is given, the application was encrypted with the\n    given passphrase.\n\n    @type filename: C{str}\n    @type kind: C{str}\n    @type passphrase: C{str}\n    \"\"\"\n    if kind == 'python':\n        application = sob.loadValueFromFile(filename, 'application')\n    else:\n        application = sob.load(filename, kind)\n    return application\n\n\n__all__ = ['IServiceMaker', 'IService', 'Service',\n           'IServiceCollection', 'MultiService',\n           'IProcess', 'Process', 'Application', 'loadApplication']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/strports.py",
    "content": "# -*- test-case-name: twisted.test.test_strports -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nConstruct listening port services from a simple string description.\n\n@see: L{twisted.internet.endpoints.serverFromString}\n@see: L{twisted.internet.endpoints.clientFromString}\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom twisted.application.internet import StreamServerEndpointService\nfrom twisted.internet import endpoints\n\n\ndef service(description, factory, reactor=None):\n    \"\"\"\n    Return the service corresponding to a description.\n\n    @param description: The description of the listening port, in the syntax\n        described by L{twisted.internet.endpoints.serverFromString}.\n    @type description: C{str}\n\n    @param factory: The protocol factory which will build protocols for\n        connections to this service.\n    @type factory: L{twisted.internet.interfaces.IProtocolFactory}\n\n    @rtype: C{twisted.application.service.IService}\n    @return: the service corresponding to a description of a reliable stream\n        server.\n\n    @see: L{twisted.internet.endpoints.serverFromString}\n    \"\"\"\n    if reactor is None:\n        from twisted.internet import reactor\n\n    svc = StreamServerEndpointService(\n        endpoints.serverFromString(reactor, description), factory)\n    svc._raiseSynchronously = True\n    return svc\n\n\n\ndef listen(description, factory):\n    \"\"\"\n    Listen on a port corresponding to a description.\n\n    @param description: The description of the connecting port, in the syntax\n        described by L{twisted.internet.endpoints.serverFromString}.\n    @type description: L{str}\n\n    @param factory: The protocol factory which will build protocols on\n        connection.\n    @type factory: L{twisted.internet.interfaces.IProtocolFactory}\n\n    @rtype: L{twisted.internet.interfaces.IListeningPort}\n    @return: the port corresponding to a description of a reliable virtual\n        circuit server.\n\n    @see: L{twisted.internet.endpoints.serverFromString}\n    \"\"\"\n    from twisted.internet import reactor\n    name, args, kw = endpoints._parseServer(description, factory)\n    return getattr(reactor, 'listen' + name)(*args, **kw)\n\n\n\n__all__ = ['service', 'listen']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/test/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet.application}.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/test/test_internet.py",
    "content": "# -*- test-case-name: twisted.application.test.test_internet -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for (new code in) L{twisted.application.internet}.\n\n@var AT_LEAST_ONE_ATTEMPT: At least enough seconds for L{ClientService} to make\n    one attempt.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport pickle\n\nfrom zope.interface import implementer\nfrom zope.interface.verify import verifyClass\n\nfrom twisted.internet.protocol import Factory, Protocol\nfrom twisted.internet.task import Clock\nfrom twisted.trial.unittest import TestCase, SynchronousTestCase\nfrom twisted.application import internet\nfrom twisted.application.internet import (\n    StreamServerEndpointService, TimerService, ClientService)\nfrom twisted.internet.defer import Deferred, CancelledError\nfrom twisted.internet.interfaces import (\n    IStreamServerEndpoint, IStreamClientEndpoint, IListeningPort,\n    IHalfCloseableProtocol, IFileDescriptorReceiver\n)\nfrom twisted.internet import task\nfrom twisted.python.failure import Failure\nfrom twisted.logger import globalLogPublisher, formatEvent\nfrom twisted.test.proto_helpers import StringTransport\n\n\ndef fakeTargetFunction():\n    \"\"\"\n    A fake target function for testing TimerService which does nothing.\n    \"\"\"\n    pass\n\n\n\n@implementer(IStreamServerEndpoint)\nclass FakeServer(object):\n    \"\"\"\n    In-memory implementation of L{IStreamServerEndpoint}.\n\n    @ivar result: The L{Deferred} resulting from the call to C{listen}, after\n        C{listen} has been called.\n\n    @ivar factory: The factory passed to C{listen}.\n\n    @ivar cancelException: The exception to errback C{self.result} when it is\n        cancelled.\n\n    @ivar port: The L{IListeningPort} which C{listen}'s L{Deferred} will fire\n        with.\n\n    @ivar listenAttempts: The number of times C{listen} has been invoked.\n\n    @ivar failImmediately: If set, the exception to fail the L{Deferred}\n        returned from C{listen} before it is returned.\n    \"\"\"\n    result = None\n    factory = None\n    failImmediately = None\n    cancelException = CancelledError()\n    listenAttempts = 0\n\n    def __init__(self):\n        self.port = FakePort()\n\n\n    def listen(self, factory):\n        \"\"\"\n        Return a Deferred and store it for future use.  (Implementation of\n        L{IStreamServerEndpoint}).\n\n        @param factory: the factory to listen with\n\n        @return: a L{Deferred} stored in L{FakeServer.result}\n        \"\"\"\n        self.listenAttempts += 1\n        self.factory = factory\n        self.result = Deferred(\n            canceller=lambda d: d.errback(self.cancelException))\n        if self.failImmediately is not None:\n            self.result.errback(self.failImmediately)\n        return self.result\n\n\n    def startedListening(self):\n        \"\"\"\n        Test code should invoke this method after causing C{listen} to be\n        invoked in order to fire the L{Deferred} previously returned from\n        C{listen}.\n        \"\"\"\n        self.result.callback(self.port)\n\n\n    def stoppedListening(self):\n        \"\"\"\n        Test code should invoke this method after causing C{stopListening} to\n        be invoked on the port fired from the L{Deferred} returned from\n        C{listen} in order to cause the L{Deferred} returned from\n        C{stopListening} to fire.\n        \"\"\"\n        self.port.deferred.callback(None)\n\nverifyClass(IStreamServerEndpoint, FakeServer)\n\n\n\n@implementer(IListeningPort)\nclass FakePort(object):\n    \"\"\"\n    Fake L{IListeningPort} implementation.\n\n    @ivar deferred: The L{Deferred} returned by C{stopListening}.\n    \"\"\"\n    deferred = None\n\n    def stopListening(self):\n        \"\"\"\n        Stop listening.\n\n        @return: a L{Deferred} stored in L{FakePort.deferred}\n        \"\"\"\n        self.deferred = Deferred()\n        return self.deferred\n\nverifyClass(IStreamServerEndpoint, FakeServer)\n\n\n\nclass EndpointServiceTests(TestCase):\n    \"\"\"\n    Tests for L{twisted.application.internet}.\n    \"\"\"\n\n    def setUp(self):\n        \"\"\"\n        Construct a stub server, a stub factory, and a\n        L{StreamServerEndpointService} to test.\n        \"\"\"\n        self.fakeServer = FakeServer()\n        self.factory = Factory()\n        self.svc = StreamServerEndpointService(self.fakeServer, self.factory)\n\n\n    def test_privilegedStartService(self):\n        \"\"\"\n        L{StreamServerEndpointService.privilegedStartService} calls its\n        endpoint's C{listen} method with its factory.\n        \"\"\"\n        self.svc.privilegedStartService()\n        self.assertIdentical(self.factory, self.fakeServer.factory)\n\n\n    def test_synchronousRaiseRaisesSynchronously(self, thunk=None):\n        \"\"\"\n        L{StreamServerEndpointService.startService} should raise synchronously\n        if the L{Deferred} returned by its wrapped\n        L{IStreamServerEndpoint.listen} has already fired with an errback and\n        the L{StreamServerEndpointService}'s C{_raiseSynchronously} flag has\n        been set.  This feature is necessary to preserve compatibility with old\n        behavior of L{twisted.internet.strports.service}, which is to return a\n        service which synchronously raises an exception from C{startService}\n        (so that, among other things, twistd will not start running).  However,\n        since L{IStreamServerEndpoint.listen} may fail asynchronously, it is a\n        bad idea to rely on this behavior.\n\n        @param thunk: If specified, a callable to execute in place of\n            C{startService}.\n        \"\"\"\n        self.fakeServer.failImmediately = ZeroDivisionError()\n        self.svc._raiseSynchronously = True\n        self.assertRaises(ZeroDivisionError, thunk or self.svc.startService)\n\n\n    def test_synchronousRaisePrivileged(self):\n        \"\"\"\n        L{StreamServerEndpointService.privilegedStartService} should behave the\n        same as C{startService} with respect to\n        L{EndpointServiceTests.test_synchronousRaiseRaisesSynchronously}.\n        \"\"\"\n        self.test_synchronousRaiseRaisesSynchronously(\n            self.svc.privilegedStartService)\n\n\n    def test_failReportsError(self):\n        \"\"\"\n        L{StreamServerEndpointService.startService} and\n        L{StreamServerEndpointService.privilegedStartService} should both log\n        an exception when the L{Deferred} returned from their wrapped\n        L{IStreamServerEndpoint.listen} fails.\n        \"\"\"\n        self.svc.startService()\n        self.fakeServer.result.errback(ZeroDivisionError())\n        logged = self.flushLoggedErrors(ZeroDivisionError)\n        self.assertEqual(len(logged), 1)\n\n\n    def test_asynchronousFailReportsError(self):\n        \"\"\"\n        L{StreamServerEndpointService.startService} and\n        L{StreamServerEndpointService.privilegedStartService} should both log\n        an exception when the L{Deferred} returned from their wrapped\n        L{IStreamServerEndpoint.listen} fails asynchronously, even if\n        C{_raiseSynchronously} is set.\n        \"\"\"\n        self.svc._raiseSynchronously = True\n        self.svc.startService()\n        self.fakeServer.result.errback(ZeroDivisionError())\n        logged = self.flushLoggedErrors(ZeroDivisionError)\n        self.assertEqual(len(logged), 1)\n\n\n    def test_synchronousFailReportsError(self):\n        \"\"\"\n        Without the C{_raiseSynchronously} compatibility flag, failing\n        immediately has the same behavior as failing later; it logs the error.\n        \"\"\"\n        self.fakeServer.failImmediately = ZeroDivisionError()\n        self.svc.startService()\n        logged = self.flushLoggedErrors(ZeroDivisionError)\n        self.assertEqual(len(logged), 1)\n\n\n    def test_startServiceUnstarted(self):\n        \"\"\"\n        L{StreamServerEndpointService.startService} sets the C{running} flag,\n        and calls its endpoint's C{listen} method with its factory, if it\n        has not yet been started.\n        \"\"\"\n        self.svc.startService()\n        self.assertIdentical(self.factory, self.fakeServer.factory)\n        self.assertEqual(self.svc.running, True)\n\n\n    def test_startServiceStarted(self):\n        \"\"\"\n        L{StreamServerEndpointService.startService} sets the C{running} flag,\n        but nothing else, if the service has already been started.\n        \"\"\"\n        self.test_privilegedStartService()\n        self.svc.startService()\n        self.assertEqual(self.fakeServer.listenAttempts, 1)\n        self.assertEqual(self.svc.running, True)\n\n\n    def test_stopService(self):\n        \"\"\"\n        L{StreamServerEndpointService.stopService} calls C{stopListening} on\n        the L{IListeningPort} returned from its endpoint, returns the\n        C{Deferred} from stopService, and sets C{running} to C{False}.\n        \"\"\"\n        self.svc.privilegedStartService()\n        self.fakeServer.startedListening()\n        # Ensure running gets set to true\n        self.svc.startService()\n        result = self.svc.stopService()\n        l = []\n        result.addCallback(l.append)\n        self.assertEqual(len(l), 0)\n        self.fakeServer.stoppedListening()\n        self.assertEqual(len(l), 1)\n        self.assertFalse(self.svc.running)\n\n\n    def test_stopServiceBeforeStartFinished(self):\n        \"\"\"\n        L{StreamServerEndpointService.stopService} cancels the L{Deferred}\n        returned by C{listen} if it has not yet fired.  No error will be logged\n        about the cancellation of the listen attempt.\n        \"\"\"\n        self.svc.privilegedStartService()\n        result = self.svc.stopService()\n        l = []\n        result.addBoth(l.append)\n        self.assertEqual(l, [None])\n        self.assertEqual(self.flushLoggedErrors(CancelledError), [])\n\n\n    def test_stopServiceCancelStartError(self):\n        \"\"\"\n        L{StreamServerEndpointService.stopService} cancels the L{Deferred}\n        returned by C{listen} if it has not fired yet.  An error will be logged\n        if the resulting exception is not L{CancelledError}.\n        \"\"\"\n        self.fakeServer.cancelException = ZeroDivisionError()\n        self.svc.privilegedStartService()\n        result = self.svc.stopService()\n        l = []\n        result.addCallback(l.append)\n        self.assertEqual(l, [None])\n        stoppingErrors = self.flushLoggedErrors(ZeroDivisionError)\n        self.assertEqual(len(stoppingErrors), 1)\n\n\n\nclass TimerServiceTests(TestCase):\n    \"\"\"\n    Tests for L{twisted.application.internet.TimerService}.\n\n    @type timer: L{TimerService}\n    @ivar timer: service to test\n\n    @type clock: L{task.Clock}\n    @ivar clock: source of time\n\n    @type deferred: L{Deferred}\n    @ivar deferred: deferred returned by L{TimerServiceTests.call}.\n    \"\"\"\n\n    def setUp(self):\n        \"\"\"\n        Set up a timer service to test.\n        \"\"\"\n        self.timer = TimerService(2, self.call)\n        self.clock = self.timer.clock = task.Clock()\n        self.deferred = Deferred()\n\n\n    def call(self):\n        \"\"\"\n        Function called by L{TimerService} being tested.\n\n        @returns: C{self.deferred}\n        @rtype: L{Deferred}\n        \"\"\"\n        return self.deferred\n\n\n    def test_startService(self):\n        \"\"\"\n        When L{TimerService.startService} is called, it marks itself\n        as running, creates a L{task.LoopingCall} and starts it.\n        \"\"\"\n        self.timer.startService()\n        self.assertTrue(self.timer.running, \"Service is started\")\n        self.assertIsInstance(self.timer._loop, task.LoopingCall)\n        self.assertIdentical(self.clock, self.timer._loop.clock)\n        self.assertTrue(self.timer._loop.running, \"LoopingCall is started\")\n\n\n    def test_startServiceRunsCallImmediately(self):\n        \"\"\"\n        When L{TimerService.startService} is called, it calls the function\n        immediately.\n        \"\"\"\n        result = []\n        self.timer.call = (result.append, (None,), {})\n        self.timer.startService()\n        self.assertEqual([None], result)\n\n\n    def test_startServiceUsesGlobalReactor(self):\n        \"\"\"\n        L{TimerService.startService} uses L{internet._maybeGlobalReactor} to\n        choose the reactor to pass to L{task.LoopingCall}\n        uses the global reactor.\n        \"\"\"\n        otherClock = task.Clock()\n        def getOtherClock(maybeReactor):\n            return otherClock\n        self.patch(internet, \"_maybeGlobalReactor\", getOtherClock)\n        self.timer.startService()\n        self.assertIdentical(otherClock, self.timer._loop.clock)\n\n\n    def test_stopServiceWaits(self):\n        \"\"\"\n        When L{TimerService.stopService} is called while a call is in progress.\n        the L{Deferred} returned doesn't fire until after the call finishes.\n        \"\"\"\n        self.timer.startService()\n        d = self.timer.stopService()\n        self.assertNoResult(d)\n        self.assertEqual(True, self.timer.running)\n        self.deferred.callback(object())\n        self.assertIdentical(self.successResultOf(d), None)\n\n\n    def test_stopServiceImmediately(self):\n        \"\"\"\n        When L{TimerService.stopService} is called while a call isn't in progress.\n        the L{Deferred} returned has already been fired.\n        \"\"\"\n        self.timer.startService()\n        self.deferred.callback(object())\n        d = self.timer.stopService()\n        self.assertIdentical(self.successResultOf(d), None)\n\n\n    def test_failedCallLogsError(self):\n        \"\"\"\n        When function passed to L{TimerService} returns a deferred that errbacks,\n        the exception is logged, and L{TimerService.stopService} doesn't raise an error.\n        \"\"\"\n        self.timer.startService()\n        self.deferred.errback(Failure(ZeroDivisionError()))\n        errors = self.flushLoggedErrors(ZeroDivisionError)\n        self.assertEqual(1, len(errors))\n        d = self.timer.stopService()\n        self.assertIdentical(self.successResultOf(d), None)\n\n\n    def test_pickleTimerServiceNotPickleLoop(self):\n        \"\"\"\n        When pickling L{internet.TimerService}, it won't pickle\n        L{internet.TimerService._loop}.\n        \"\"\"\n        # We need a pickleable callable to test pickling TimerService. So we\n        # can't use self.timer\n        timer = TimerService(1, fakeTargetFunction)\n        timer.startService()\n        dumpedTimer = pickle.dumps(timer)\n        timer.stopService()\n        loadedTimer = pickle.loads(dumpedTimer)\n        nothing = object()\n        value = getattr(loadedTimer, \"_loop\", nothing)\n        self.assertIdentical(nothing, value)\n\n\n    def test_pickleTimerServiceNotPickleLoopFinished(self):\n        \"\"\"\n        When pickling L{internet.TimerService}, it won't pickle\n        L{internet.TimerService._loopFinished}.\n        \"\"\"\n        # We need a pickleable callable to test pickling TimerService. So we\n        # can't use self.timer\n        timer = TimerService(1, fakeTargetFunction)\n        timer.startService()\n        dumpedTimer = pickle.dumps(timer)\n        timer.stopService()\n        loadedTimer = pickle.loads(dumpedTimer)\n        nothing = object()\n        value = getattr(loadedTimer, \"_loopFinished\", nothing)\n        self.assertIdentical(nothing, value)\n\n\n\nclass ConnectInformation(object):\n    \"\"\"\n    Information about C{endpointForTesting}\n\n    @ivar connectQueue: a L{list} of L{Deferred} returned from C{connect}.  If\n        these are not already fired, you can fire them with no value and they\n        will trigger building a factory.\n\n    @ivar constructedProtocols: a L{list} of protocols constructed.\n\n    @ivar passedFactories: a L{list} of L{IProtocolFactory}; the ones actually\n        passed to the underlying endpoint / i.e. the reactor.\n    \"\"\"\n    def __init__(self):\n        self.connectQueue = []\n        self.constructedProtocols = []\n        self.passedFactories = []\n\n\n\ndef endpointForTesting(fireImmediately=False):\n    \"\"\"\n    Make a sample endpoint for testing.\n\n    @param fireImmediately: If true, fire all L{Deferred}s returned from\n        C{connect} immedaitely.\n\n    @return: a 2-tuple of C{(information, endpoint)}, where C{information} is a\n        L{ConnectInformation} describing the operations in progress on\n        C{endpoint}.\n    \"\"\"\n    @implementer(IStreamClientEndpoint)\n    class ClientTestEndpoint(object):\n        def connect(self, factory):\n            result = Deferred()\n            info.passedFactories.append(factory)\n            @result.addCallback\n            def createProtocol(ignored):\n                protocol = factory.buildProtocol(None)\n                info.constructedProtocols.append(protocol)\n                transport = StringTransport()\n                protocol.makeConnection(transport)\n                return protocol\n            info.connectQueue.append(result)\n            if fireImmediately:\n                result.callback(None)\n            return result\n    info = ConnectInformation()\n    return info, ClientTestEndpoint()\n\n\n\ndef catchLogs(testCase, logPublisher=globalLogPublisher):\n    \"\"\"\n    Catch the global log stream.\n\n    @param testCase: The test case to add a cleanup to.\n\n    @param logPublisher: the log publisher to add and remove observers for.\n\n    @return: a 0-argument callable that returns a list of textual log messages\n        for comparison.\n    @rtype: L{list} of L{unicode}\n    \"\"\"\n    logs = []\n    logPublisher.addObserver(logs.append)\n    testCase.addCleanup(lambda: logPublisher.removeObserver(logs.append))\n    return lambda: [formatEvent(event) for event in logs]\n\n\n\nAT_LEAST_ONE_ATTEMPT = 100.\n\nclass ClientServiceTests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{ClientService}.\n    \"\"\"\n\n    def makeReconnector(self, fireImmediately=True, startService=True,\n                        protocolType=Protocol, **kw):\n        \"\"\"\n        Create a L{ClientService} along with a L{ConnectInformation} indicating\n        the connections in progress on its endpoint.\n\n        @param fireImmediately: Should all of the endpoint connection attempts\n            fire synchronously?\n        @type fireImmediately: L{bool}\n\n        @param startService: Should the L{ClientService} be started before\n            being returned?\n        @type startService: L{bool}\n\n        @param protocolType: a 0-argument callable returning a new L{IProtocol}\n            provider to be used for application-level protocol connections.\n\n        @param kw: Arbitrary keyword arguments to be passed on to\n            L{ClientService}\n\n        @return: a 2-tuple of L{ConnectInformation} (for information about test\n            state) and L{ClientService} (the system under test).  The\n            L{ConnectInformation} has 2 additional attributes;\n            C{applicationFactory} and C{applicationProtocols}, which refer to\n            the unwrapped protocol factory and protocol instances passed in to\n            L{ClientService} respectively.\n        \"\"\"\n        nkw = {}\n        nkw.update(clock=Clock())\n        nkw.update(kw)\n        clock = nkw['clock']\n        cq, endpoint = endpointForTesting(fireImmediately=fireImmediately)\n\n        # `endpointForTesting` is totally generic to any LLPI client that uses\n        # endpoints, and maintains all its state internally; however,\n        # applicationProtocols and applicationFactory are bonus attributes that\n        # are only specifically interesitng to tests that use wrapper\n        # protocols.  For now, set them here, externally.\n\n        applicationProtocols = cq.applicationProtocols = []\n\n        class RememberingFactory(Factory, object):\n            protocol = protocolType\n            def buildProtocol(self, addr):\n                result = super(RememberingFactory, self).buildProtocol(addr)\n                applicationProtocols.append(result)\n                return result\n\n        cq.applicationFactory = factory = RememberingFactory()\n\n        service = ClientService(endpoint, factory, **nkw)\n        def stop():\n            service._protocol = None\n            if service.running:\n                service.stopService()\n            # Ensure that we don't leave any state in the reactor after\n            # stopService.\n            self.assertEqual(clock.getDelayedCalls(), [])\n        self.addCleanup(stop)\n        if startService:\n            service.startService()\n        return cq, service\n\n\n    def test_startService(self):\n        \"\"\"\n        When the service is started, a connection attempt is made.\n        \"\"\"\n        cq, service = self.makeReconnector(fireImmediately=False)\n        self.assertEqual(len(cq.connectQueue), 1)\n\n\n    def test_startStopFactory(self):\n        \"\"\"\n        Although somewhat obscure, L{IProtocolFactory} includes both C{doStart}\n        and C{doStop} methods; ensure that when these methods are called on the\n        factory that was passed to the reactor, the factory that was passed\n        from the application receives them.\n        \"\"\"\n        cq, service = self.makeReconnector()\n        firstAppFactory = cq.applicationFactory\n        self.assertEqual(firstAppFactory.numPorts, 0)\n        firstPassedFactory = cq.passedFactories[0]\n        firstPassedFactory.doStart()\n        self.assertEqual(firstAppFactory.numPorts, 1)\n\n\n    def test_stopServiceWhileConnected(self):\n        \"\"\"\n        When the service is stopped, no further connect attempts are made.  The\n        returned L{Deferred} fires when all outstanding connections have been\n        stopped.\n        \"\"\"\n        cq, service = self.makeReconnector()\n        d = service.stopService()\n        self.assertNoResult(d)\n        protocol = cq.constructedProtocols[0]\n        self.assertEqual(protocol.transport.disconnecting, True)\n        protocol.connectionLost(Failure(Exception()))\n        self.successResultOf(d)\n\n\n    def test_startServiceWaitsForDisconnect(self):\n        \"\"\"\n        When L{ClientService} is restarted after having been connected, it\n        waits to start connecting until after having disconnected.\n        \"\"\"\n        cq, service = self.makeReconnector()\n        d = service.stopService()\n        self.assertNoResult(d)\n        protocol = cq.constructedProtocols[0]\n        self.assertEqual(protocol.transport.disconnecting, True)\n        service.startService()\n        self.assertNoResult(d)\n        self.assertEqual(len(cq.constructedProtocols), 1)\n        protocol.connectionLost(Failure(Exception()))\n        self.assertEqual(len(cq.constructedProtocols), 2)\n\n\n    def test_startServiceWhileStopping(self):\n        \"\"\"\n        When L{ClientService} is stopping - that is,\n        L{ClientService.stopService} has been called, but the L{Deferred} it\n        returns has not fired yet - calling L{startService} will cause a new\n        connection to be made, and new calls to L{whenConnected} to succeed.\n        \"\"\"\n        cq, service = self.makeReconnector(fireImmediately=False)\n        cq.connectQueue[0].callback(None)\n        first = cq.constructedProtocols[0]\n        stopped = service.stopService()\n        self.assertNoResult(stopped)\n        nextProtocol = service.whenConnected()\n        self.assertNoResult(nextProtocol)\n        service.startService()\n        self.assertNoResult(nextProtocol)\n        self.assertNoResult(stopped)\n        self.assertEqual(first.transport.disconnecting, True)\n        first.connectionLost(Failure(Exception()))\n        self.successResultOf(stopped)\n        cq.connectQueue[1].callback(None)\n        self.assertEqual(len(cq.constructedProtocols), 2)\n        self.assertIdentical(self.successResultOf(nextProtocol),\n                             cq.applicationProtocols[1])\n        secondStopped = service.stopService()\n        self.assertNoResult(secondStopped)\n\n\n    def test_startServiceWhileStopped(self):\n        \"\"\"\n        When L{ClientService} is stopped - that is,\n        L{ClientService.stopService} has been called and the L{Deferred} it\n        returns has fired - calling L{startService} will cause a new connection\n        to be made, and new calls to L{whenConnected} to succeed.\n        \"\"\"\n        cq, service = self.makeReconnector(fireImmediately=False)\n        stopped = service.stopService()\n        self.successResultOf(stopped)\n        self.failureResultOf(service.whenConnected(), CancelledError)\n        service.startService()\n        cq.connectQueue[-1].callback(None)\n        self.assertIdentical(cq.applicationProtocols[-1],\n                             self.successResultOf(service.whenConnected()))\n\n\n    def test_interfacesForTransport(self):\n        \"\"\"\n        If the protocol objects returned by the factory given to\n        L{ClientService} provide special \"marker\" interfaces for their\n        transport - L{IHalfCloseableProtocol} or L{IFileDescriptorReceiver} -\n        those interfaces will be provided by the protocol objects passed on to\n        the reactor.\n        \"\"\"\n        @implementer(IHalfCloseableProtocol, IFileDescriptorReceiver)\n        class FancyProtocol(Protocol, object):\n            \"\"\"\n            Provider of various interfaces.\n            \"\"\"\n        cq, service = self.makeReconnector(protocolType=FancyProtocol)\n        reactorFacing = cq.constructedProtocols[0]\n        self.assertTrue(IFileDescriptorReceiver.providedBy(reactorFacing))\n        self.assertTrue(IHalfCloseableProtocol.providedBy(reactorFacing))\n\n\n    def test_stopServiceWhileRetrying(self):\n        \"\"\"\n        When the service is stopped while retrying, the retry is cancelled.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(fireImmediately=False, clock=clock)\n        cq.connectQueue[0].errback(Exception())\n        clock.advance(AT_LEAST_ONE_ATTEMPT)\n        self.assertEqual(len(cq.connectQueue), 2)\n        d = service.stopService()\n        cq.connectQueue[1].errback(Exception())\n        self.successResultOf(d)\n\n\n    def test_stopServiceWhileConnecting(self):\n        \"\"\"\n        When the service is stopped while initially connecting, the connection\n        attempt is cancelled.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(fireImmediately=False, clock=clock)\n        self.assertEqual(len(cq.connectQueue), 1)\n        self.assertNoResult(cq.connectQueue[0])\n        d = service.stopService()\n        self.successResultOf(d)\n\n\n    def test_clientConnected(self):\n        \"\"\"\n        When a client connects, the service keeps a reference to the new\n        protocol and resets the delay.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(clock=clock)\n        awaitingProtocol = service.whenConnected()\n        self.assertEqual(clock.getDelayedCalls(), [])\n        self.assertIdentical(self.successResultOf(awaitingProtocol),\n                             cq.applicationProtocols[0])\n\n\n    def test_clientConnectionFailed(self):\n        \"\"\"\n        When a client connection fails, the service removes its reference\n        to the protocol and tries again after a timeout.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(fireImmediately=False,\n                                           clock=clock)\n        self.assertEqual(len(cq.connectQueue), 1)\n        cq.connectQueue[0].errback(Failure(Exception()))\n        whenConnected = service.whenConnected()\n        self.assertNoResult(whenConnected)\n        # Don't fail during test tear-down when service shutdown causes all\n        # waiting connections to fail.\n        whenConnected.addErrback(lambda ignored: ignored.trap(CancelledError))\n        clock.advance(AT_LEAST_ONE_ATTEMPT)\n        self.assertEqual(len(cq.connectQueue), 2)\n\n\n    def test_clientConnectionLost(self):\n        \"\"\"\n        When a client connection is lost, the service removes its reference\n        to the protocol and calls retry.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(clock=clock, fireImmediately=False)\n        self.assertEqual(len(cq.connectQueue), 1)\n        cq.connectQueue[0].callback(None)\n        self.assertEqual(len(cq.connectQueue), 1)\n        self.assertIdentical(self.successResultOf(service.whenConnected()),\n                             cq.applicationProtocols[0])\n        cq.constructedProtocols[0].connectionLost(Failure(Exception()))\n        clock.advance(AT_LEAST_ONE_ATTEMPT)\n        self.assertEqual(len(cq.connectQueue), 2)\n        cq.connectQueue[1].callback(None)\n        self.assertIdentical(self.successResultOf(service.whenConnected()),\n                             cq.applicationProtocols[1])\n\n\n    def test_clientConnectionLostWhileStopping(self):\n        \"\"\"\n        When a client connection is lost while the service is stopping, the\n        protocol stopping deferred is called and the reference to the protocol\n        is removed.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(clock=clock)\n        d = service.stopService()\n        cq.constructedProtocols[0].connectionLost(Failure(IndentationError()))\n        self.failureResultOf(service.whenConnected(), CancelledError)\n        self.assertTrue(d.called)\n\n\n    def test_startTwice(self):\n        \"\"\"\n        If L{ClientService} is started when it's already started, it will log a\n        complaint and do nothing else (in particular it will not make\n        additional connections).\n        \"\"\"\n        cq, service = self.makeReconnector(fireImmediately=False,\n                                           startService=False)\n        self.assertEqual(len(cq.connectQueue), 0)\n        service.startService()\n        self.assertEqual(len(cq.connectQueue), 1)\n        messages = catchLogs(self)\n        service.startService()\n        self.assertEqual(len(cq.connectQueue), 1)\n        self.assertIn(\"Duplicate ClientService.startService\", messages()[0])\n\n\n    def test_whenConnectedLater(self):\n        \"\"\"\n        L{ClientService.whenConnected} returns a L{Deferred} that fires when a\n        connection is established.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(fireImmediately=False, clock=clock)\n        a = service.whenConnected()\n        b = service.whenConnected()\n        c = service.whenConnected(failAfterFailures=1)\n        self.assertNoResult(a)\n        self.assertNoResult(b)\n        self.assertNoResult(c)\n        cq.connectQueue[0].callback(None)\n        resultA = self.successResultOf(a)\n        resultB = self.successResultOf(b)\n        resultC = self.successResultOf(c)\n        self.assertIdentical(resultA, resultB)\n        self.assertIdentical(resultA, resultC)\n        self.assertIdentical(resultA, cq.applicationProtocols[0])\n\n\n    def test_whenConnectedFails(self):\n        \"\"\"\n        L{ClientService.whenConnected} returns a L{Deferred} that fails, if\n        asked, when some number of connections have failed.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(fireImmediately=False, clock=clock)\n        a0 = service.whenConnected()\n        a1 = service.whenConnected(failAfterFailures=1)\n        a2 = service.whenConnected(failAfterFailures=2)\n        a3 = service.whenConnected(failAfterFailures=3)\n        self.assertNoResult(a0)\n        self.assertNoResult(a1)\n        self.assertNoResult(a2)\n        self.assertNoResult(a3)\n\n        f1 = Failure(Exception())\n        cq.connectQueue[0].errback(f1)\n\n        self.assertNoResult(a0)\n        self.assertIdentical(self.failureResultOf(a1, Exception), f1)\n        self.assertNoResult(a2)\n        self.assertNoResult(a3)\n\n        clock.advance(AT_LEAST_ONE_ATTEMPT)\n        self.assertEqual(len(cq.connectQueue), 2)\n\n        self.assertNoResult(a0)\n        self.assertNoResult(a2)\n        self.assertNoResult(a3)\n\n        f2 = Failure(Exception())\n        cq.connectQueue[1].errback(f2)\n\n        self.assertNoResult(a0)\n        self.assertIdentical(self.failureResultOf(a2, Exception), f2)\n        self.assertNoResult(a3)\n\n        AT_LEAST_TWO_ATTEMPTS = AT_LEAST_ONE_ATTEMPT # close enough\n        clock.advance(AT_LEAST_TWO_ATTEMPTS)\n        self.assertEqual(len(cq.connectQueue), 3)\n\n        self.assertNoResult(a0)\n        self.assertNoResult(a3)\n\n        cq.connectQueue[2].callback(None)\n\n        resultA0 = self.successResultOf(a0)\n        resultA3 = self.successResultOf(a3)\n        self.assertIdentical(resultA0, resultA3)\n        self.assertIdentical(resultA0, cq.applicationProtocols[0])\n\n        # a new whenConnected Deferred, obtained after we're connected,\n        # should have fired already, even if failAfterFailures is set\n        a4 = service.whenConnected(failAfterFailures=1)\n        resultA4 = self.successResultOf(a4)\n        self.assertIdentical(resultA0, resultA4)\n\n\n    def test_whenConnectedStopService(self):\n        \"\"\"\n        L{ClientService.whenConnected} returns a L{Deferred} that fails when\n        L{ClientService.stopService} is called.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(fireImmediately=False, clock=clock)\n        a = service.whenConnected()\n        b = service.whenConnected()\n        c = service.whenConnected(failAfterFailures=1)\n        self.assertNoResult(a)\n        self.assertNoResult(b)\n        self.assertNoResult(c)\n        service.stopService()\n        clock.advance(AT_LEAST_ONE_ATTEMPT)\n        self.failureResultOf(a, CancelledError)\n        self.failureResultOf(b, CancelledError)\n        self.failureResultOf(c, CancelledError)\n\n\n    def test_retryCancelled(self):\n        \"\"\"\n        When L{ClientService.stopService} is called while waiting between\n        connection attempts, the pending reconnection attempt is cancelled and\n        the service is stopped immediately.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(fireImmediately=False, clock=clock)\n        cq.connectQueue[0].errback(Exception(\"no connection\"))\n        d = service.stopService()\n        self.assertEqual(clock.getDelayedCalls(), [])\n        self.successResultOf(d)\n\n\n    def test_stopServiceBeforeStartService(self):\n        \"\"\"\n        Calling L{ClientService.stopService} before\n        L{ClientService.startService} returns a L{Deferred} that has\n        already fired with L{None}.\n        \"\"\"\n        clock = Clock()\n        _, service = self.makeReconnector(fireImmediately=False,\n                                          startService=False,\n                                          clock=clock)\n        d = service.stopService()\n        self.assertIsNone(self.successResultOf(d))\n\n\n    def test_whenConnectedErrbacksOnStopService(self):\n        \"\"\"\n        L{ClientService.whenConnected} returns a L{Deferred} that\n        errbacks with L{CancelledError} if\n        L{ClientService.stopService} is called between connection\n        attempts.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(fireImmediately=False,\n                                           clock=clock)\n        beforeErrbackAndStop = service.whenConnected()\n\n        # The protocol fails to connect, and the service is waiting to\n        # reconnect.\n        cq.connectQueue[0].errback(Exception(\"no connection\"))\n\n        service.stopService()\n        afterErrbackAndStop = service.whenConnected()\n\n        self.assertIsInstance(self.failureResultOf(beforeErrbackAndStop).value,\n                              CancelledError)\n        self.assertIsInstance(self.failureResultOf(afterErrbackAndStop).value,\n                              CancelledError)\n\n\n    def test_stopServiceWhileDisconnecting(self):\n        \"\"\"\n        Calling L{ClientService.stopService} twice after it has\n        connected (that is, stopping it while it is disconnecting)\n        returns a L{Deferred} each time that fires when the\n        disconnection has completed.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(fireImmediately=False,\n                                           clock=clock)\n        # The protocol connects\n        cq.connectQueue[0].callback(None)\n\n        # The protocol begins disconnecting\n        firstStopDeferred = service.stopService()\n        # The protocol continues disconnecting\n        secondStopDeferred = service.stopService()\n\n        # The protocol is disconnected\n        cq.constructedProtocols[0].connectionLost(Failure(IndentationError()))\n\n        self.successResultOf(firstStopDeferred)\n        self.successResultOf(secondStopDeferred)\n\n\n    def test_stopServiceWhileRestarting(self):\n        \"\"\"\n        Calling L{ClientService.stopService} after calling a\n        reconnection attempt returns a L{Deferred} that fires when the\n        disconnection has completed.\n        \"\"\"\n        clock = Clock()\n        cq, service = self.makeReconnector(fireImmediately=False,\n                                           clock=clock)\n        # The protocol connects\n        cq.connectQueue[0].callback(None)\n\n        # The protocol begins disconnecting\n        firstStopDeferred = service.stopService()\n        # The protocol begins reconnecting\n        service.startService()\n        # The protocol begins disconnecting again\n        secondStopDeferred = service.stopService()\n\n        # The protocol is disconnected\n        cq.constructedProtocols[0].connectionLost(Failure(IndentationError()))\n\n        self.successResultOf(firstStopDeferred)\n        self.successResultOf(secondStopDeferred)\n\n\n    def test_stopServiceOnStoppedService(self):\n        \"\"\"\n        Calling L{ClientService.stopService} on a stopped service\n        returns a L{Deferred} that has already fired with L{None}.\n        \"\"\"\n        clock = Clock()\n        _, service = self.makeReconnector(fireImmediately=False,\n                                          clock=clock)\n        firstStopDeferred = service.stopService()\n        secondStopDeferred = service.stopService()\n\n        self.assertIsNone(self.successResultOf(firstStopDeferred))\n        self.assertIsNone(self.successResultOf(secondStopDeferred))\n\n\n    def test_prepareConnectionCalledWhenServiceStarts(self):\n        \"\"\"\n        The C{prepareConnection} callable is called after\n        L{ClientService.startService} once the connection is made.\n        \"\"\"\n        prepares = [0]\n\n        def prepareConnection(_proto):\n            prepares[0] += 1\n\n        cq, service = self.makeReconnector(prepareConnection=prepareConnection,\n                                           startService=True)\n        self.assertEqual(1, prepares[0])\n\n\n    def test_prepareConnectionCalledWithProtocol(self):\n        \"\"\"\n        The C{prepareConnection} callable is passed the connected protocol\n        instance.\n        \"\"\"\n        newProtocols = []\n\n        def prepareConnection(proto):\n            newProtocols.append(proto)\n\n        cq, service = self.makeReconnector(\n            prepareConnection=prepareConnection,\n        )\n        self.assertIdentical(cq.constructedProtocols[0], newProtocols[0])\n\n\n    def test_prepareConnectionCalledAfterConnectionMade(self):\n        \"\"\"\n        The C{prepareConnection} callback is invoked only once a connection is\n        made.\n        \"\"\"\n        prepares = [0]\n\n        def prepareConnection(_proto):\n            prepares[0] += 1\n\n        clock = Clock()\n        cq, service = self.makeReconnector(prepareConnection=prepareConnection,\n                                           fireImmediately=False,\n                                           clock=clock)\n\n        cq.connectQueue[0].errback(Exception('connection attempt failed'))\n        self.assertEqual(0, prepares[0])  # Not called yet.\n\n        clock.advance(AT_LEAST_ONE_ATTEMPT)\n        cq.connectQueue[1].callback(None)\n\n        self.assertEqual(1, prepares[0])  # Was called.\n\n\n    def test_prepareConnectionCalledOnReconnect(self):\n        \"\"\"\n        The C{prepareConnection} callback is invoked each time a connection is\n        made, including on reconnection.\n        \"\"\"\n        prepares = [0]\n\n        def prepareConnection(_proto):\n            prepares[0] += 1\n\n        clock = Clock()\n        cq, service = self.makeReconnector(prepareConnection=prepareConnection,\n                                           clock=clock)\n\n        self.assertEqual(1, prepares[0])  # Called once.\n\n        # Protocol disconnects.\n        cq.constructedProtocols[0].connectionLost(Failure(IndentationError()))\n        clock.advance(AT_LEAST_ONE_ATTEMPT)\n\n        self.assertEqual(2, prepares[0])  # Called again.\n\n\n    def test_prepareConnectionReturnValueIgnored(self):\n        \"\"\"\n        The C{prepareConnection} return value is ignored when it does not\n        indicate a failure. Even though the callback participates in the\n        internal new-connection L{Deferred} chain for error propagation\n        purposes, any successful result does not affect the ultimate return\n        value.\n        \"\"\"\n        # Sentinel object returned by prepareConnection.\n        sentinel = object()\n\n        def prepareConnection(proto):\n            return sentinel\n\n        cq, service = self.makeReconnector(prepareConnection=prepareConnection)\n\n        result = self.successResultOf(service.whenConnected())\n        self.assertNotIdentical(sentinel, result)\n\n\n    def test_prepareConnectionReturningADeferred(self):\n        \"\"\"\n        The C{prepareConnection} callable returns a deferred and calls to\n        L{ClientService.whenConnected} wait until it fires.\n        \"\"\"\n        newProtocols = []\n        newProtocolDeferred = Deferred()\n\n        def prepareConnection(proto):\n            newProtocols.append(proto)\n            return newProtocolDeferred\n\n        cq, service = self.makeReconnector(prepareConnection=prepareConnection)\n\n        whenConnectedDeferred = service.whenConnected()\n        self.assertNoResult(whenConnectedDeferred)\n\n        newProtocolDeferred.callback(None)\n\n        self.assertIdentical(cq.applicationProtocols[0],\n                             self.successResultOf(whenConnectedDeferred))\n\n\n    def test_prepareConnectionThrows(self):\n        \"\"\"\n        The connection attempt counts as a failure when the\n        C{prepareConnection} callable throws.\n        \"\"\"\n        clock = Clock()\n\n        def prepareConnection(_proto):\n            raise IndentationError()\n\n        cq, service = self.makeReconnector(prepareConnection=prepareConnection,\n                                           clock=clock)\n\n        whenConnectedDeferred = service.whenConnected(failAfterFailures=2)\n        self.assertNoResult(whenConnectedDeferred)\n\n        clock.advance(AT_LEAST_ONE_ATTEMPT)\n        self.assertNoResult(whenConnectedDeferred)\n\n        clock.advance(AT_LEAST_ONE_ATTEMPT)\n        self.assertIdentical(IndentationError,\n                             self.failureResultOf(whenConnectedDeferred).type)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/test/test_service.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.application.service}.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom zope.interface import implementer\nfrom zope.interface.exceptions import BrokenImplementation\nfrom zope.interface.verify import verifyObject\n\nfrom twisted.persisted.sob import IPersistable\nfrom twisted.application.service import Application, IProcess\nfrom twisted.application.service import IService, IServiceCollection\nfrom twisted.application.service import Service\nfrom twisted.trial.unittest import TestCase\n\n\n@implementer(IService)\nclass AlmostService(object):\n    \"\"\"\n    Implement IService in a way that can fail.\n\n    In general, classes should maintain invariants that adhere\n    to the interfaces that they claim to implement --\n    otherwise, it is a bug.\n\n    This is a buggy class -- the IService implementation is fragile,\n    and several methods will break it. These bugs are intentional,\n    as the tests trigger them -- and then check that the class,\n    indeed, no longer complies with the interface (IService)\n    that it claims to comply with.\n\n    Since the verification will, by definition, only fail on buggy classes --\n    in other words, those which do not actually support the interface they\n    claim to support, we have to write a buggy class to properly verify\n    the interface.\n    \"\"\"\n\n    def __init__(self, name, parent, running):\n        self.name = name\n        self.parent = parent\n        self.running = running\n\n\n    def makeInvalidByDeletingName(self):\n        \"\"\"\n        Probably not a wise method to call.\n\n        This method removes the :code:`name` attribute,\n        which has to exist in IService classes.\n        \"\"\"\n        del self.name\n\n\n    def makeInvalidByDeletingParent(self):\n        \"\"\"\n        Probably not a wise method to call.\n\n        This method removes the :code:`parent` attribute,\n        which has to exist in IService classes.\n        \"\"\"\n        del self.parent\n\n\n    def makeInvalidByDeletingRunning(self):\n        \"\"\"\n        Probably not a wise method to call.\n\n        This method removes the :code:`running` attribute,\n        which has to exist in IService classes.\n        \"\"\"\n        del self.running\n\n\n    def setName(self, name):\n        \"\"\"\n        See L{twisted.application.service.IService}.\n\n        @param name: ignored\n        \"\"\"\n\n\n    def setServiceParent(self, parent):\n        \"\"\"\n        See L{twisted.application.service.IService}.\n\n        @param parent: ignored\n        \"\"\"\n\n\n    def disownServiceParent(self):\n        \"\"\"\n        See L{twisted.application.service.IService}.\n        \"\"\"\n\n\n    def privilegedStartService(self):\n        \"\"\"\n        See L{twisted.application.service.IService}.\n        \"\"\"\n\n\n    def startService(self):\n        \"\"\"\n        See L{twisted.application.service.IService}.\n        \"\"\"\n\n\n    def stopService(self):\n        \"\"\"\n        See L{twisted.application.service.IService}.\n        \"\"\"\n\n\n\nclass ServiceInterfaceTests(TestCase):\n    \"\"\"\n    Tests for L{twisted.application.service.IService} implementation.\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Build something that implements IService.\n        \"\"\"\n        self.almostService = AlmostService(parent=None, running=False,\n                                           name=None)\n\n\n    def test_realService(self):\n        \"\"\"\n        Service implements IService.\n        \"\"\"\n        myService = Service()\n        verifyObject(IService, myService)\n\n\n    def test_hasAll(self):\n        \"\"\"\n        AlmostService implements IService.\n        \"\"\"\n        verifyObject(IService, self.almostService)\n\n\n    def test_noName(self):\n        \"\"\"\n        AlmostService with no name does not implement IService.\n        \"\"\"\n        self.almostService.makeInvalidByDeletingName()\n        with self.assertRaises(BrokenImplementation):\n            verifyObject(IService, self.almostService)\n\n\n    def test_noParent(self):\n        \"\"\"\n        AlmostService with no parent does not implement IService.\n        \"\"\"\n        self.almostService.makeInvalidByDeletingParent()\n        with self.assertRaises(BrokenImplementation):\n            verifyObject(IService, self.almostService)\n\n\n    def test_noRunning(self):\n        \"\"\"\n        AlmostService with no running does not implement IService.\n        \"\"\"\n        self.almostService.makeInvalidByDeletingRunning()\n        with self.assertRaises(BrokenImplementation):\n            verifyObject(IService, self.almostService)\n\n\n\nclass ApplicationTests(TestCase):\n    \"\"\"\n    Tests for L{twisted.application.service.Application}.\n    \"\"\"\n    def test_applicationComponents(self):\n        \"\"\"\n        Check L{twisted.application.service.Application} instantiation.\n        \"\"\"\n        app = Application('app-name')\n\n        self.assertTrue(verifyObject(IService, IService(app)))\n        self.assertTrue(\n            verifyObject(IServiceCollection, IServiceCollection(app)))\n        self.assertTrue(verifyObject(IProcess, IProcess(app)))\n        self.assertTrue(verifyObject(IPersistable, IPersistable(app)))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/twist/__init__.py",
    "content": "# -*- test-case-name: twisted.application.twist.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nC{twist} command line tool.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/twist/_options.py",
    "content": "# -*- test-case-name: twisted.application.twist.test.test_options -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nCommand line options for C{twist}.\n\"\"\"\n\nfrom sys import stdout, stderr\nfrom textwrap import dedent\n\nfrom twisted.copyright import version\nfrom twisted.python.usage import Options, UsageError\nfrom twisted.logger import (\n    LogLevel, InvalidLogLevelError,\n    textFileLogObserver, jsonFileLogObserver,\n)\nfrom twisted.plugin import getPlugins\n\nfrom ..reactors import installReactor, NoSuchReactor, getReactorTypes\nfrom ..runner._exit import exit, ExitStatus\nfrom ..service import IServiceMaker\n\nopenFile = open\n\n\n\nclass TwistOptions(Options):\n    \"\"\"\n    Command line options for C{twist}.\n    \"\"\"\n\n    defaultReactorName = \"default\"\n    defaultLogLevel = LogLevel.info\n\n\n    def __init__(self):\n        Options.__init__(self)\n\n        self[\"reactorName\"] = self.defaultReactorName\n        self[\"logLevel\"] = self.defaultLogLevel\n        self[\"logFile\"] = stdout\n\n\n    def getSynopsis(self):\n        return \"{} plugin [plugin_options]\".format(\n            Options.getSynopsis(self)\n        )\n\n\n    def opt_version(self):\n        \"\"\"\n        Print version and exit.\n        \"\"\"\n        exit(ExitStatus.EX_OK, \"{}\".format(version))\n\n\n    def opt_reactor(self, name):\n        \"\"\"\n        The name of the reactor to use.\n        (options: {options})\n        \"\"\"\n        # Actually actually actually install the reactor right at this very\n        # moment, before any other code (for example, a sub-command plugin)\n        # runs and accidentally imports and installs the default reactor.\n        try:\n            self[\"reactor\"] = self.installReactor(name)\n        except NoSuchReactor:\n            raise UsageError(\"Unknown reactor: {}\".format(name))\n        else:\n            self[\"reactorName\"] = name\n\n    opt_reactor.__doc__ = dedent(opt_reactor.__doc__).format(\n        options=\", \".join(\n            '\"{}\"'.format(rt.shortName) for rt in getReactorTypes()\n        ),\n    )\n\n\n    def installReactor(self, name):\n        \"\"\"\n        Install the reactor.\n        \"\"\"\n        if name == self.defaultReactorName:\n            from twisted.internet import reactor\n            return reactor\n        else:\n            return installReactor(name)\n\n\n    def opt_log_level(self, levelName):\n        \"\"\"\n        Set default log level.\n        (options: {options}; default: \"{default}\")\n        \"\"\"\n        try:\n            self[\"logLevel\"] = LogLevel.levelWithName(levelName)\n        except InvalidLogLevelError:\n            raise UsageError(\"Invalid log level: {}\".format(levelName))\n\n    opt_log_level.__doc__ = dedent(opt_log_level.__doc__).format(\n        options=\", \".join(\n            '\"{}\"'.format(l.name) for l in LogLevel.iterconstants()\n        ),\n        default=defaultLogLevel.name,\n    )\n\n\n    def opt_log_file(self, fileName):\n        \"\"\"\n        Log to file. (\"-\" for stdout, \"+\" for stderr; default: \"-\")\n        \"\"\"\n        if fileName == \"-\":\n            self[\"logFile\"] = stdout\n            return\n\n        if fileName == \"+\":\n            self[\"logFile\"] = stderr\n            return\n\n        try:\n            self[\"logFile\"] = openFile(fileName, \"a\")\n        except EnvironmentError as e:\n            exit(\n                ExitStatus.EX_IOERR,\n                \"Unable to open log file {!r}: {}\".format(fileName, e)\n            )\n\n\n    def opt_log_format(self, format):\n        \"\"\"\n        Log file format.\n        (options: \"text\", \"json\"; default: \"text\" if the log file is a tty,\n        otherwise \"json\")\n        \"\"\"\n        format = format.lower()\n\n        if format == \"text\":\n            self[\"fileLogObserverFactory\"] = textFileLogObserver\n        elif format == \"json\":\n            self[\"fileLogObserverFactory\"] = jsonFileLogObserver\n        else:\n            raise UsageError(\"Invalid log format: {}\".format(format))\n        self[\"logFormat\"] = format\n\n    opt_log_format.__doc__ = dedent(opt_log_format.__doc__)\n\n\n    def selectDefaultLogObserver(self):\n        \"\"\"\n        Set C{fileLogObserverFactory} to the default appropriate for the\n        chosen C{logFile}.\n        \"\"\"\n        if \"fileLogObserverFactory\" not in self:\n            logFile = self[\"logFile\"]\n\n            if hasattr(logFile, \"isatty\") and logFile.isatty():\n                self[\"fileLogObserverFactory\"] = textFileLogObserver\n                self[\"logFormat\"] = \"text\"\n            else:\n                self[\"fileLogObserverFactory\"] = jsonFileLogObserver\n                self[\"logFormat\"] = \"json\"\n\n\n    def parseOptions(self, options=None):\n        self.selectDefaultLogObserver()\n\n        Options.parseOptions(self, options=options)\n\n        if \"reactor\" not in self:\n            self[\"reactor\"] = self.installReactor(self[\"reactorName\"])\n\n\n    @property\n    def plugins(self):\n        if \"plugins\" not in self:\n            plugins = {}\n            for plugin in getPlugins(IServiceMaker):\n                plugins[plugin.tapname] = plugin\n            self[\"plugins\"] = plugins\n\n        return self[\"plugins\"]\n\n\n    @property\n    def subCommands(self):\n        plugins = self.plugins\n        for name in sorted(plugins):\n            plugin = plugins[name]\n            yield (\n                plugin.tapname,\n                None,\n                # Avoid resolving the options attribute right away, in case\n                # it's a property with a non-trivial getter (eg, one which\n                # imports modules).\n                lambda plugin=plugin: plugin.options(),\n                plugin.description,\n            )\n\n\n    def postOptions(self):\n        Options.postOptions(self)\n\n        if self.subCommand is None:\n            raise UsageError(\"No plugin specified.\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/twist/_twist.py",
    "content": "# -*- test-case-name: twisted.application.twist.test.test_twist -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nRun a Twisted application.\n\"\"\"\n\nimport sys\n\nfrom twisted.python.usage import UsageError\nfrom ..service import Application, IService\nfrom ..runner._exit import exit, ExitStatus\nfrom ..runner._runner import Runner\nfrom ._options import TwistOptions\nfrom twisted.application.app import _exitWithSignal\nfrom twisted.internet.interfaces import _ISupportsExitSignalCapturing\n\n\n\nclass Twist(object):\n    \"\"\"\n    Run a Twisted application.\n    \"\"\"\n\n    @staticmethod\n    def options(argv):\n        \"\"\"\n        Parse command line options.\n\n        @param argv: Command line arguments.\n        @type argv: L{list}\n\n        @return: The parsed options.\n        @rtype: L{TwistOptions}\n        \"\"\"\n        options = TwistOptions()\n\n        try:\n            options.parseOptions(argv[1:])\n        except UsageError as e:\n            exit(ExitStatus.EX_USAGE, \"Error: {}\\n\\n{}\".format(e, options))\n\n        return options\n\n\n    @staticmethod\n    def service(plugin, options):\n        \"\"\"\n        Create the application service.\n\n        @param plugin: The name of the plugin that implements the service\n            application to run.\n        @type plugin: L{str}\n\n        @param options: Options to pass to the application.\n        @type options: L{twisted.python.usage.Options}\n\n        @return: The created application service.\n        @rtype: L{IService}\n        \"\"\"\n        service = plugin.makeService(options)\n        application = Application(plugin.tapname)\n        service.setServiceParent(application)\n\n        return IService(application)\n\n\n    @staticmethod\n    def startService(reactor, service):\n        \"\"\"\n        Start the application service.\n\n        @param reactor: The reactor to run the service with.\n        @type reactor: L{twisted.internet.interfaces.IReactorCore}\n\n        @param service: The application service to run.\n        @type service: L{IService}\n        \"\"\"\n        service.startService()\n\n        # Ask the reactor to stop the service before shutting down\n        reactor.addSystemEventTrigger(\n            \"before\", \"shutdown\", service.stopService\n        )\n\n\n    @staticmethod\n    def run(twistOptions):\n        \"\"\"\n        Run the application service.\n\n        @param twistOptions: Command line options to convert to runner\n            arguments.\n        @type twistOptions: L{TwistOptions}\n        \"\"\"\n        runner = Runner(\n            reactor=twistOptions[\"reactor\"],\n            defaultLogLevel=twistOptions[\"logLevel\"],\n            logFile=twistOptions[\"logFile\"],\n            fileLogObserverFactory=twistOptions[\"fileLogObserverFactory\"],\n        )\n        runner.run()\n        reactor = twistOptions[\"reactor\"]\n        if _ISupportsExitSignalCapturing.providedBy(reactor):\n            if reactor._exitSignal is not None:\n                _exitWithSignal(reactor._exitSignal)\n\n\n    @classmethod\n    def main(cls, argv=sys.argv):\n        \"\"\"\n        Executable entry point for L{Twist}.\n        Processes options and run a twisted reactor with a service.\n\n        @param argv: Command line arguments.\n        @type argv: L{list}\n        \"\"\"\n        options = cls.options(argv)\n\n        reactor = options[\"reactor\"]\n        service = cls.service(\n            plugin=options.plugins[options.subCommand],\n            options=options.subOptions,\n        )\n\n        cls.startService(reactor, service)\n        cls.run(options)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/twist/test/__init__.py",
    "content": "# -*- test-case-name: twisted.application.twist.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.application.twist}.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/twist/test/test_options.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.application.twist._options}.\n\"\"\"\n\nfrom sys import stdout, stderr\n\nfrom twisted.internet import reactor\nfrom twisted.copyright import version\nfrom twisted.python.usage import UsageError\nfrom twisted.logger import LogLevel, textFileLogObserver, jsonFileLogObserver\nfrom twisted.test.proto_helpers import MemoryReactor\nfrom ...reactors import NoSuchReactor\nfrom ...service import ServiceMaker\nfrom ...runner._exit import ExitStatus\nfrom ...runner.test.test_runner import DummyExit\nfrom ...twist import _options\nfrom .._options import TwistOptions\n\nimport twisted.trial.unittest\n\n\n\nclass OptionsTests(twisted.trial.unittest.TestCase):\n    \"\"\"\n    Tests for L{TwistOptions}.\n    \"\"\"\n\n    def patchExit(self):\n        \"\"\"\n        Patch L{_twist.exit} so we can capture usage and prevent actual exits.\n        \"\"\"\n        self.exit = DummyExit()\n        self.patch(_options, \"exit\", self.exit)\n\n\n    def patchOpen(self):\n        \"\"\"\n        Patch L{_options.open} so we can capture usage and prevent actual opens.\n        \"\"\"\n        self.opened = []\n\n        def fakeOpen(name, mode=None):\n            if name == \"nocanopen\":\n                raise IOError(None, None, name)\n\n            self.opened.append((name, mode))\n            return NotImplemented\n\n        self.patch(_options, \"openFile\", fakeOpen)\n\n\n    def patchInstallReactor(self):\n        \"\"\"\n        Patch C{_options.installReactor} so we can capture usage and prevent\n        actual installs.\n        \"\"\"\n        self.installedReactors = {}\n\n        def installReactor(name):\n            if name != \"fusion\":\n                raise NoSuchReactor()\n\n            reactor = MemoryReactor()\n            self.installedReactors[name] = reactor\n            return reactor\n\n        self.patch(_options, \"installReactor\", installReactor)\n\n\n    def test_synopsis(self):\n        \"\"\"\n        L{TwistOptions.getSynopsis} appends arguments.\n        \"\"\"\n        options = TwistOptions()\n\n        self.assertTrue(\n            options.getSynopsis().endswith(\" plugin [plugin_options]\")\n        )\n\n\n    def test_version(self):\n        \"\"\"\n        L{TwistOptions.opt_version} exits with L{ExitStatus.EX_OK} and prints\n        the version.\n        \"\"\"\n        self.patchExit()\n\n        options = TwistOptions()\n        options.opt_version()\n\n        self.assertEquals(self.exit.status, ExitStatus.EX_OK)\n        self.assertEquals(self.exit.message, version)\n\n\n    def test_reactor(self):\n        \"\"\"\n        L{TwistOptions.installReactor} installs the chosen reactor and sets\n        the reactor name.\n        \"\"\"\n        self.patchInstallReactor()\n\n        options = TwistOptions()\n        options.opt_reactor(\"fusion\")\n\n        self.assertEqual(set(self.installedReactors), set([\"fusion\"]))\n        self.assertEquals(options[\"reactorName\"], \"fusion\")\n\n\n    def test_installCorrectReactor(self):\n        \"\"\"\n        L{TwistOptions.installReactor} installs the chosen reactor after the\n        command line options have been parsed.\n        \"\"\"\n        self.patchInstallReactor()\n\n        options = TwistOptions()\n        options.subCommand = \"test-subcommand\"\n        options.parseOptions([\"--reactor=fusion\"])\n\n        self.assertEqual(set(self.installedReactors), set([\"fusion\"]))\n\n\n    def test_installReactorBogus(self):\n        \"\"\"\n        L{TwistOptions.installReactor} raises UsageError if an unknown reactor\n        is specified.\n        \"\"\"\n        self.patchInstallReactor()\n\n        options = TwistOptions()\n        self.assertRaises(UsageError, options.opt_reactor, \"coal\")\n\n\n    def test_installReactorDefault(self):\n        \"\"\"\n        L{TwistOptions.installReactor} returns the currently installed reactor\n        when the default reactor name is specified.\n        \"\"\"\n        options = TwistOptions()\n        self.assertIdentical(reactor, options.installReactor('default'))\n\n\n    def test_logLevelValid(self):\n        \"\"\"\n        L{TwistOptions.opt_log_level} sets the corresponding log level.\n        \"\"\"\n        options = TwistOptions()\n        options.opt_log_level(\"warn\")\n\n        self.assertIdentical(options[\"logLevel\"], LogLevel.warn)\n\n\n    def test_logLevelInvalid(self):\n        \"\"\"\n        L{TwistOptions.opt_log_level} with an invalid log level name raises\n        UsageError.\n        \"\"\"\n        options = TwistOptions()\n\n        self.assertRaises(UsageError, options.opt_log_level, \"cheese\")\n\n\n    def _testLogFile(self, name, expectedStream):\n        \"\"\"\n        Set log file name and check the selected output stream.\n\n        @param name: The name of the file.\n        @param expectedStream: The expected stream.\n        \"\"\"\n        options = TwistOptions()\n        options.opt_log_file(name)\n\n        self.assertIdentical(options[\"logFile\"], expectedStream)\n\n\n    def test_logFileStdout(self):\n        \"\"\"\n        L{TwistOptions.opt_log_file} given C{\"-\"} as a file name uses stdout.\n        \"\"\"\n        self._testLogFile(\"-\", stdout)\n\n\n    def test_logFileStderr(self):\n        \"\"\"\n        L{TwistOptions.opt_log_file} given C{\"+\"} as a file name uses stderr.\n        \"\"\"\n        self._testLogFile(\"+\", stderr)\n\n\n    def test_logFileNamed(self):\n        \"\"\"\n        L{TwistOptions.opt_log_file} opens the given file name in append mode.\n        \"\"\"\n        self.patchOpen()\n\n        options = TwistOptions()\n        options.opt_log_file(\"mylog\")\n\n        self.assertEqual([(\"mylog\", \"a\")], self.opened)\n\n\n    def test_logFileCantOpen(self):\n        \"\"\"\n        L{TwistOptions.opt_log_file} exits with L{ExitStatus.EX_IOERR} if\n        unable to open the log file due to an L{EnvironmentError}.\n        \"\"\"\n        self.patchExit()\n        self.patchOpen()\n\n        options = TwistOptions()\n        options.opt_log_file(\"nocanopen\")\n\n        self.assertEquals(self.exit.status, ExitStatus.EX_IOERR)\n        self.assertTrue(\n            self.exit.message.startswith(\n                \"Unable to open log file 'nocanopen': \"\n            )\n        )\n\n\n    def _testLogFormat(self, format, expectedObserver):\n        \"\"\"\n        Set log file format and check the selected observer.\n\n        @param format: The format of the file.\n        @param expectedObserver: The expected observer.\n        \"\"\"\n        options = TwistOptions()\n        options.opt_log_format(format)\n\n        self.assertIdentical(\n            options[\"fileLogObserverFactory\"], expectedObserver\n        )\n        self.assertEqual(options[\"logFormat\"], format)\n\n\n    def test_logFormatText(self):\n        \"\"\"\n        L{TwistOptions.opt_log_format} given C{\"text\"} uses a\n        L{textFileLogObserver}.\n        \"\"\"\n        self._testLogFormat(\"text\", textFileLogObserver)\n\n\n    def test_logFormatJSON(self):\n        \"\"\"\n        L{TwistOptions.opt_log_format} given C{\"text\"} uses a\n        L{textFileLogObserver}.\n        \"\"\"\n        self._testLogFormat(\"json\", jsonFileLogObserver)\n\n\n    def test_logFormatInvalid(self):\n        \"\"\"\n        L{TwistOptions.opt_log_format} given an invalid format name raises\n        L{UsageError}.\n        \"\"\"\n        options = TwistOptions()\n\n        self.assertRaises(UsageError, options.opt_log_format, \"frommage\")\n\n\n    def test_selectDefaultLogObserverNoOverride(self):\n        \"\"\"\n        L{TwistOptions.selectDefaultLogObserver} will not override an already\n        selected observer.\n        \"\"\"\n        self.patchOpen()\n\n        options = TwistOptions()\n        options.opt_log_format(\"text\")  # Ask for text\n        options.opt_log_file(\"queso\")   # File, not a tty\n        options.selectDefaultLogObserver()\n\n        # Because we didn't select a file that is a tty, the default is JSON,\n        # but since we asked for text, we should get text.\n        self.assertIdentical(\n            options[\"fileLogObserverFactory\"], textFileLogObserver\n        )\n        self.assertEqual(options[\"logFormat\"], \"text\")\n\n\n    def test_selectDefaultLogObserverDefaultWithTTY(self):\n        \"\"\"\n        L{TwistOptions.selectDefaultLogObserver} will not override an already\n        selected observer.\n        \"\"\"\n        class TTYFile(object):\n            def isatty(self):\n                return True\n\n        # stdout may not be a tty, so let's make sure it thinks it is\n        self.patch(_options, \"stdout\", TTYFile())\n\n        options = TwistOptions()\n        options.opt_log_file(\"-\")  # stdout, a tty\n        options.selectDefaultLogObserver()\n\n        self.assertIdentical(\n            options[\"fileLogObserverFactory\"], textFileLogObserver\n        )\n        self.assertEqual(options[\"logFormat\"], \"text\")\n\n\n    def test_selectDefaultLogObserverDefaultWithoutTTY(self):\n        \"\"\"\n        L{TwistOptions.selectDefaultLogObserver} will not override an already\n        selected observer.\n        \"\"\"\n        self.patchOpen()\n\n        options = TwistOptions()\n        options.opt_log_file(\"queso\")  # File, not a tty\n        options.selectDefaultLogObserver()\n\n        self.assertIdentical(\n            options[\"fileLogObserverFactory\"], jsonFileLogObserver\n        )\n        self.assertEqual(options[\"logFormat\"], \"json\")\n\n\n    def test_pluginsType(self):\n        \"\"\"\n        L{TwistOptions.plugins} is a mapping of available plug-ins.\n        \"\"\"\n        options = TwistOptions()\n        plugins = options.plugins\n\n        for name in plugins:\n            self.assertIsInstance(name, str)\n            self.assertIsInstance(plugins[name], ServiceMaker)\n\n\n    def test_pluginsIncludeWeb(self):\n        \"\"\"\n        L{TwistOptions.plugins} includes a C{\"web\"} plug-in.\n        This is an attempt to verify that something we expect to be in the list\n        is in there without enumerating all of the built-in plug-ins.\n        \"\"\"\n        options = TwistOptions()\n\n        self.assertIn(\"web\", options.plugins)\n\n\n    def test_subCommandsType(self):\n        \"\"\"\n        L{TwistOptions.subCommands} is an iterable of tuples as expected by\n        L{twisted.python.usage.Options}.\n        \"\"\"\n        options = TwistOptions()\n\n        for name, shortcut, parser, doc in options.subCommands:\n            self.assertIsInstance(name, str)\n            self.assertIdentical(shortcut, None)\n            self.assertTrue(callable(parser))\n            self.assertIsInstance(doc, str)\n\n\n    def test_subCommandsIncludeWeb(self):\n        \"\"\"\n        L{TwistOptions.subCommands} includes a sub-command for every plug-in.\n        \"\"\"\n        options = TwistOptions()\n\n        plugins = set(options.plugins)\n        subCommands = set(\n            name for name, shortcut, parser, doc in options.subCommands\n        )\n\n        self.assertEqual(subCommands, plugins)\n\n\n    def test_postOptionsNoSubCommand(self):\n        \"\"\"\n        L{TwistOptions.postOptions} raises L{UsageError} is it has no\n        sub-command.\n        \"\"\"\n        self.patchInstallReactor()\n\n        options = TwistOptions()\n\n        self.assertRaises(UsageError, options.postOptions)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/application/twist/test/test_twist.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.application.twist._twist}.\n\"\"\"\n\nfrom sys import stdout\n\nfrom twisted.logger import LogLevel, jsonFileLogObserver\nfrom twisted.test.proto_helpers import MemoryReactor\nfrom ...service import IService, MultiService\nfrom ...runner._exit import ExitStatus\nfrom ...runner._runner import Runner\nfrom ...runner.test.test_runner import DummyExit\nfrom ...twist import _twist\nfrom .._options import TwistOptions\nfrom .._twist import Twist\nfrom twisted.test.test_twistd import SignalCapturingMemoryReactor\n\nimport twisted.trial.unittest\n\n\n\nclass TwistTests(twisted.trial.unittest.TestCase):\n    \"\"\"\n    Tests for L{Twist}.\n    \"\"\"\n\n    def setUp(self):\n        self.patchInstallReactor()\n\n\n    def patchExit(self):\n        \"\"\"\n        Patch L{_twist.exit} so we can capture usage and prevent actual exits.\n        \"\"\"\n        self.exit = DummyExit()\n        self.patch(_twist, \"exit\", self.exit)\n\n\n    def patchInstallReactor(self):\n        \"\"\"\n        Patch C{_options.installReactor} so we can capture usage and prevent\n        actual installs.\n        \"\"\"\n        self.installedReactors = {}\n\n        def installReactor(_, name):\n            reactor = MemoryReactor()\n            self.installedReactors[name] = reactor\n            return reactor\n\n        self.patch(TwistOptions, \"installReactor\", installReactor)\n\n\n    def patchStartService(self):\n        \"\"\"\n        Patch L{MultiService.startService} so we can capture usage and prevent\n        actual starts.\n        \"\"\"\n        self.serviceStarts = []\n\n        def startService(service):\n            self.serviceStarts.append(service)\n\n        self.patch(MultiService, \"startService\", startService)\n\n\n    def test_optionsValidArguments(self):\n        \"\"\"\n        L{Twist.options} given valid arguments returns options.\n        \"\"\"\n        options = Twist.options([\"twist\", \"web\"])\n\n        self.assertIsInstance(options, TwistOptions)\n\n\n    def test_optionsInvalidArguments(self):\n        \"\"\"\n        L{Twist.options} given invalid arguments exits with\n        L{ExitStatus.EX_USAGE} and an error/usage message.\n        \"\"\"\n        self.patchExit()\n\n        Twist.options([\"twist\", \"--bogus-bagels\"])\n\n        self.assertIdentical(self.exit.status, ExitStatus.EX_USAGE)\n        self.assertTrue(self.exit.message.startswith(\"Error: \"))\n        self.assertTrue(self.exit.message.endswith(\n            \"\\n\\n{}\".format(TwistOptions())\n        ))\n\n\n    def test_service(self):\n        \"\"\"\n        L{Twist.service} returns an L{IService}.\n        \"\"\"\n        options = Twist.options([\"twist\", \"web\"])  # web should exist\n        service = Twist.service(options.plugins[\"web\"], options.subOptions)\n        self.assertTrue(IService.providedBy(service))\n\n\n    def test_startService(self):\n        \"\"\"\n        L{Twist.startService} starts the service and registers a trigger to\n        stop the service when the reactor shuts down.\n        \"\"\"\n        options = Twist.options([\"twist\", \"web\"])\n\n        reactor = options[\"reactor\"]\n        service = Twist.service(\n            plugin=options.plugins[options.subCommand],\n            options=options.subOptions,\n        )\n\n        self.patchStartService()\n\n        Twist.startService(reactor, service)\n\n        self.assertEqual(self.serviceStarts, [service])\n        self.assertEqual(\n            reactor.triggers[\"before\"][\"shutdown\"],\n            [(service.stopService, (), {})]\n        )\n\n\n    def test_run(self):\n        \"\"\"\n        L{Twist.run} runs the runner with arguments corresponding to the given\n        options.\n        \"\"\"\n        argsSeen = []\n\n        self.patch(\n            Runner, \"__init__\", lambda self, **args: argsSeen.append(args)\n        )\n        self.patch(\n            Runner, \"run\", lambda self: None\n        )\n\n        twistOptions = Twist.options([\n            \"twist\", \"--reactor=default\", \"--log-format=json\", \"web\"\n        ])\n        Twist.run(twistOptions)\n\n        self.assertEqual(len(argsSeen), 1)\n        self.assertEqual(\n            argsSeen[0],\n            dict(\n                reactor=self.installedReactors[\"default\"],\n                defaultLogLevel=LogLevel.info,\n                logFile=stdout,\n                fileLogObserverFactory=jsonFileLogObserver,\n            )\n        )\n\n\n    def test_main(self):\n        \"\"\"\n        L{Twist.main} runs the runner with arguments corresponding to the given\n        command line arguments.\n        \"\"\"\n        self.patchStartService()\n\n        runners = []\n\n        class Runner(object):\n            def __init__(self, **kwargs):\n                self.args = kwargs\n                self.runs = 0\n                runners.append(self)\n\n            def run(self):\n                self.runs += 1\n\n        self.patch(_twist, \"Runner\", Runner)\n\n        Twist.main([\n            \"twist\", \"--reactor=default\", \"--log-format=json\", \"web\"\n        ])\n\n        self.assertEqual(len(self.serviceStarts), 1)\n        self.assertEqual(len(runners), 1)\n        self.assertEqual(\n            runners[0].args,\n            dict(\n                reactor=self.installedReactors[\"default\"],\n                defaultLogLevel=LogLevel.info,\n                logFile=stdout,\n                fileLogObserverFactory=jsonFileLogObserver,\n            )\n        )\n        self.assertEqual(runners[0].runs, 1)\n\n\n\nclass TwistExitTests(twisted.trial.unittest.TestCase):\n    \"\"\"\n    Tests to verify that the Twist script takes the expected actions related\n    to signals and the reactor.\n    \"\"\"\n\n    def setUp(self):\n        self.exitWithSignalCalled = False\n\n        def fakeExitWithSignal(sig):\n            \"\"\"\n            Fake to capture whether L{twisted.application._exitWithSignal\n            was called.\n\n            @param sig: Signal value\n            @type sig: C{int}\n            \"\"\"\n            self.exitWithSignalCalled = True\n\n        self.patch(_twist, '_exitWithSignal', fakeExitWithSignal)\n\n        def startLogging(_):\n            \"\"\"\n            Prevent Runner from adding new log observers or other\n            tests outside this module will fail.\n\n            @param _: Unused self param\n            \"\"\"\n\n        self.patch(Runner, 'startLogging', startLogging)\n\n\n    def test_twistReactorDoesntExitWithSignal(self):\n        \"\"\"\n        _exitWithSignal is not called if the reactor's _exitSignal attribute\n        is zero.\n        \"\"\"\n        reactor = SignalCapturingMemoryReactor()\n        reactor._exitSignal = None\n        options = TwistOptions()\n        options[\"reactor\"] = reactor\n        options[\"fileLogObserverFactory\"] = jsonFileLogObserver\n\n        Twist.run(options)\n        self.assertFalse(self.exitWithSignalCalled)\n\n\n    def test_twistReactorHasNoExitSignalAttr(self):\n        \"\"\"\n        _exitWithSignal is not called if the runner's reactor does not\n        implement L{twisted.internet.interfaces._ISupportsExitSignalCapturing}\n        \"\"\"\n        reactor = MemoryReactor()\n        options = TwistOptions()\n        options[\"reactor\"] = reactor\n        options[\"fileLogObserverFactory\"] = jsonFileLogObserver\n        Twist.run(options)\n        self.assertFalse(self.exitWithSignalCalled)\n\n\n    def test_twistReactorExitsWithSignal(self):\n        \"\"\"\n        _exitWithSignal is called if the runner's reactor exits due\n        to a signal.\n        \"\"\"\n        reactor = SignalCapturingMemoryReactor()\n        reactor._exitSignal = 2\n        options = TwistOptions()\n        options[\"reactor\"] = reactor\n        options[\"fileLogObserverFactory\"] = jsonFileLogObserver\n        Twist.run(options)\n        self.assertTrue(self.exitWithSignalCalled)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/__init__.py",
    "content": "# -*- test-case-name: twisted.conch.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTwisted Conch: The Twisted Shell. Terminal emulation, SSHv2 and telnet.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/avatar.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_conch -*-\n\nfrom __future__ import absolute_import, division\n\nfrom zope.interface import implementer\n\nfrom twisted.conch.error import ConchError\nfrom twisted.conch.interfaces import IConchUser\nfrom twisted.conch.ssh.connection import OPEN_UNKNOWN_CHANNEL_TYPE\nfrom twisted.python import log\nfrom twisted.python.compat import nativeString\n\n\n@implementer(IConchUser)\nclass ConchUser:\n    def __init__(self):\n        self.channelLookup = {}\n        self.subsystemLookup = {}\n\n\n    def lookupChannel(self, channelType, windowSize, maxPacket, data):\n        klass = self.channelLookup.get(channelType, None)\n        if not klass:\n            raise ConchError(OPEN_UNKNOWN_CHANNEL_TYPE, \"unknown channel\")\n        else:\n            return klass(remoteWindow=windowSize,\n                         remoteMaxPacket=maxPacket,\n                         data=data, avatar=self)\n\n\n    def lookupSubsystem(self, subsystem, data):\n        log.msg(repr(self.subsystemLookup))\n        klass = self.subsystemLookup.get(subsystem, None)\n        if not klass:\n            return False\n        return klass(data, avatar=self)\n\n\n    def gotGlobalRequest(self, requestType, data):\n        # XXX should this use method dispatch?\n        requestType = nativeString(requestType.replace(b'-', b'_'))\n        f = getattr(self, \"global_%s\" % requestType, None)\n        if not f:\n            return 0\n        return f(data)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/checkers.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_checkers -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nProvide L{ICredentialsChecker} implementations to be used in Conch protocols.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport sys\nimport binascii\nimport errno\n\ntry:\n    import pwd\nexcept ImportError:\n    pwd = None\nelse:\n    import crypt\n\ntry:\n    import spwd\nexcept ImportError:\n    spwd = None\n\nfrom zope.interface import providedBy, implementer, Interface\n\nfrom incremental import Version\n\nfrom twisted.conch import error\nfrom twisted.conch.ssh import keys\nfrom twisted.cred.checkers import ICredentialsChecker\nfrom twisted.cred.credentials import IUsernamePassword, ISSHPrivateKey\nfrom twisted.cred.error import UnauthorizedLogin, UnhandledCredentials\nfrom twisted.internet import defer\nfrom twisted.python.compat import _keys, _PY3, _b64decodebytes\nfrom twisted.python import failure, reflect, log\nfrom twisted.python.deprecate import deprecatedModuleAttribute\nfrom twisted.python.util import runAsEffectiveUser\nfrom twisted.python.filepath import FilePath\n\n\n\n\ndef verifyCryptedPassword(crypted, pw):\n    \"\"\"\n    Check that the password, when crypted, matches the stored crypted password.\n\n    @param crypted: The stored crypted password.\n    @type crypted: L{str}\n    @param pw: The password the user has given.\n    @type pw: L{str}\n\n    @rtype: L{bool}\n    \"\"\"\n    return crypt.crypt(pw, crypted) == crypted\n\n\n\ndef _pwdGetByName(username):\n    \"\"\"\n    Look up a user in the /etc/passwd database using the pwd module.  If the\n    pwd module is not available, return None.\n\n    @param username: the username of the user to return the passwd database\n        information for.\n    @type username: L{str}\n    \"\"\"\n    if pwd is None:\n        return None\n    return pwd.getpwnam(username)\n\n\n\ndef _shadowGetByName(username):\n    \"\"\"\n    Look up a user in the /etc/shadow database using the spwd module. If it is\n    not available, return L{None}.\n\n    @param username: the username of the user to return the shadow database\n        information for.\n    @type username: L{str}\n    \"\"\"\n    if spwd is not None:\n        f = spwd.getspnam\n    else:\n        return None\n    return runAsEffectiveUser(0, 0, f, username)\n\n\n\n@implementer(ICredentialsChecker)\nclass UNIXPasswordDatabase:\n    \"\"\"\n    A checker which validates users out of the UNIX password databases, or\n    databases of a compatible format.\n\n    @ivar _getByNameFunctions: a C{list} of functions which are called in order\n        to valid a user.  The default value is such that the C{/etc/passwd}\n        database will be tried first, followed by the C{/etc/shadow} database.\n    \"\"\"\n    credentialInterfaces = IUsernamePassword,\n\n    def __init__(self, getByNameFunctions=None):\n        if getByNameFunctions is None:\n            getByNameFunctions = [_pwdGetByName, _shadowGetByName]\n        self._getByNameFunctions = getByNameFunctions\n\n\n    def requestAvatarId(self, credentials):\n        # We get bytes, but the Py3 pwd module uses str. So attempt to decode\n        # it using the same method that CPython does for the file on disk.\n        if _PY3:\n            username = credentials.username.decode(sys.getfilesystemencoding())\n            password = credentials.password.decode(sys.getfilesystemencoding())\n        else:\n            username = credentials.username\n            password = credentials.password\n\n        for func in self._getByNameFunctions:\n            try:\n                pwnam = func(username)\n            except KeyError:\n                return defer.fail(UnauthorizedLogin(\"invalid username\"))\n            else:\n                if pwnam is not None:\n                    crypted = pwnam[1]\n                    if crypted == '':\n                        continue\n\n                    if verifyCryptedPassword(crypted, password):\n                        return defer.succeed(credentials.username)\n        # fallback\n        return defer.fail(UnauthorizedLogin(\"unable to verify password\"))\n\n\n\n@implementer(ICredentialsChecker)\nclass SSHPublicKeyDatabase:\n    \"\"\"\n    Checker that authenticates SSH public keys, based on public keys listed in\n    authorized_keys and authorized_keys2 files in user .ssh/ directories.\n    \"\"\"\n    credentialInterfaces = (ISSHPrivateKey,)\n\n    _userdb = pwd\n\n    def requestAvatarId(self, credentials):\n        d = defer.maybeDeferred(self.checkKey, credentials)\n        d.addCallback(self._cbRequestAvatarId, credentials)\n        d.addErrback(self._ebRequestAvatarId)\n        return d\n\n\n    def _cbRequestAvatarId(self, validKey, credentials):\n        \"\"\"\n        Check whether the credentials themselves are valid, now that we know\n        if the key matches the user.\n\n        @param validKey: A boolean indicating whether or not the public key\n            matches a key in the user's authorized_keys file.\n\n        @param credentials: The credentials offered by the user.\n        @type credentials: L{ISSHPrivateKey} provider\n\n        @raise UnauthorizedLogin: (as a failure) if the key does not match the\n            user in C{credentials}. Also raised if the user provides an invalid\n            signature.\n\n        @raise ValidPublicKey: (as a failure) if the key matches the user but\n            the credentials do not include a signature. See\n            L{error.ValidPublicKey} for more information.\n\n        @return: The user's username, if authentication was successful.\n        \"\"\"\n        if not validKey:\n            return failure.Failure(UnauthorizedLogin(\"invalid key\"))\n        if not credentials.signature:\n            return failure.Failure(error.ValidPublicKey())\n        else:\n            try:\n                pubKey = keys.Key.fromString(credentials.blob)\n                if pubKey.verify(credentials.signature, credentials.sigData):\n                    return credentials.username\n            except: # any error should be treated as a failed login\n                log.err()\n                return failure.Failure(UnauthorizedLogin('error while verifying key'))\n        return failure.Failure(UnauthorizedLogin(\"unable to verify key\"))\n\n\n    def getAuthorizedKeysFiles(self, credentials):\n        \"\"\"\n        Return a list of L{FilePath} instances for I{authorized_keys} files\n        which might contain information about authorized keys for the given\n        credentials.\n\n        On OpenSSH servers, the default location of the file containing the\n        list of authorized public keys is\n        U{$HOME/.ssh/authorized_keys<http://www.openbsd.org/cgi-bin/man.cgi?query=sshd_config>}.\n\n        I{$HOME/.ssh/authorized_keys2} is also returned, though it has been\n        U{deprecated by OpenSSH since\n        2001<http://marc.info/?m=100508718416162>}.\n\n        @return: A list of L{FilePath} instances to files with the authorized keys.\n        \"\"\"\n        pwent = self._userdb.getpwnam(credentials.username)\n        root = FilePath(pwent.pw_dir).child('.ssh')\n        files = ['authorized_keys', 'authorized_keys2']\n        return [root.child(f) for f in files]\n\n\n    def checkKey(self, credentials):\n        \"\"\"\n        Retrieve files containing authorized keys and check against user\n        credentials.\n        \"\"\"\n        ouid, ogid = self._userdb.getpwnam(credentials.username)[2:4]\n        for filepath in self.getAuthorizedKeysFiles(credentials):\n            if not filepath.exists():\n                continue\n            try:\n                lines = filepath.open()\n            except IOError as e:\n                if e.errno == errno.EACCES:\n                    lines = runAsEffectiveUser(ouid, ogid, filepath.open)\n                else:\n                    raise\n            with lines:\n                for l in lines:\n                    l2 = l.split()\n                    if len(l2) < 2:\n                        continue\n                    try:\n                        if _b64decodebytes(l2[1]) == credentials.blob:\n                            return True\n                    except binascii.Error:\n                        continue\n        return False\n\n\n    def _ebRequestAvatarId(self, f):\n        if not f.check(UnauthorizedLogin):\n            log.msg(f)\n            return failure.Failure(UnauthorizedLogin(\"unable to get avatar id\"))\n        return f\n\n\n\n@implementer(ICredentialsChecker)\nclass SSHProtocolChecker:\n    \"\"\"\n    SSHProtocolChecker is a checker that requires multiple authentications\n    to succeed.  To add a checker, call my registerChecker method with\n    the checker and the interface.\n\n    After each successful authenticate, I call my areDone method with the\n    avatar id.  To get a list of the successful credentials for an avatar id,\n    use C{SSHProcotolChecker.successfulCredentials[avatarId]}.  If L{areDone}\n    returns True, the authentication has succeeded.\n    \"\"\"\n\n    def __init__(self):\n        self.checkers = {}\n        self.successfulCredentials = {}\n\n\n    def get_credentialInterfaces(self):\n        return _keys(self.checkers)\n\n    credentialInterfaces = property(get_credentialInterfaces)\n\n    def registerChecker(self, checker, *credentialInterfaces):\n        if not credentialInterfaces:\n            credentialInterfaces = checker.credentialInterfaces\n        for credentialInterface in credentialInterfaces:\n            self.checkers[credentialInterface] = checker\n\n\n    def requestAvatarId(self, credentials):\n        \"\"\"\n        Part of the L{ICredentialsChecker} interface.  Called by a portal with\n        some credentials to check if they'll authenticate a user.  We check the\n        interfaces that the credentials provide against our list of acceptable\n        checkers.  If one of them matches, we ask that checker to verify the\n        credentials.  If they're valid, we call our L{_cbGoodAuthentication}\n        method to continue.\n\n        @param credentials: the credentials the L{Portal} wants us to verify\n        \"\"\"\n        ifac = providedBy(credentials)\n        for i in ifac:\n            c = self.checkers.get(i)\n            if c is not None:\n                d = defer.maybeDeferred(c.requestAvatarId, credentials)\n                return d.addCallback(self._cbGoodAuthentication,\n                        credentials)\n        return defer.fail(UnhandledCredentials(\"No checker for %s\" % \\\n            ', '.join(map(reflect.qual, ifac))))\n\n\n    def _cbGoodAuthentication(self, avatarId, credentials):\n        \"\"\"\n        Called if a checker has verified the credentials.  We call our\n        L{areDone} method to see if the whole of the successful authentications\n        are enough.  If they are, we return the avatar ID returned by the first\n        checker.\n        \"\"\"\n        if avatarId not in self.successfulCredentials:\n            self.successfulCredentials[avatarId] = []\n        self.successfulCredentials[avatarId].append(credentials)\n        if self.areDone(avatarId):\n            del self.successfulCredentials[avatarId]\n            return avatarId\n        else:\n            raise error.NotEnoughAuthentication()\n\n\n    def areDone(self, avatarId):\n        \"\"\"\n        Override to determine if the authentication is finished for a given\n        avatarId.\n\n        @param avatarId: the avatar returned by the first checker.  For\n            this checker to function correctly, all the checkers must\n            return the same avatar ID.\n        \"\"\"\n        return True\n\n\n\ndeprecatedModuleAttribute(\n        Version(\"Twisted\", 15, 0, 0),\n        (\"Please use twisted.conch.checkers.SSHPublicKeyChecker, \"\n         \"initialized with an instance of \"\n         \"twisted.conch.checkers.UNIXAuthorizedKeysFiles instead.\"),\n        __name__, \"SSHPublicKeyDatabase\")\n\n\n\nclass IAuthorizedKeysDB(Interface):\n    \"\"\"\n    An object that provides valid authorized ssh keys mapped to usernames.\n\n    @since: 15.0\n    \"\"\"\n    def getAuthorizedKeys(avatarId):\n        \"\"\"\n        Gets an iterable of authorized keys that are valid for the given\n        C{avatarId}.\n\n        @param avatarId: the ID of the avatar\n        @type avatarId: valid return value of\n            L{twisted.cred.checkers.ICredentialsChecker.requestAvatarId}\n\n        @return: an iterable of L{twisted.conch.ssh.keys.Key}\n        \"\"\"\n\n\n\ndef readAuthorizedKeyFile(fileobj, parseKey=keys.Key.fromString):\n    \"\"\"\n    Reads keys from an authorized keys file.  Any non-comment line that cannot\n    be parsed as a key will be ignored, although that particular line will\n    be logged.\n\n    @param fileobj: something from which to read lines which can be parsed\n        as keys\n    @type fileobj: L{file}-like object\n\n    @param parseKey: a callable that takes a string and returns a\n        L{twisted.conch.ssh.keys.Key}, mainly to be used for testing.  The\n        default is L{twisted.conch.ssh.keys.Key.fromString}.\n    @type parseKey: L{callable}\n\n    @return: an iterable of L{twisted.conch.ssh.keys.Key}\n    @rtype: iterable\n\n    @since: 15.0\n    \"\"\"\n    for line in fileobj:\n        line = line.strip()\n        if line and not line.startswith(b'#'):  # for comments\n            try:\n                yield parseKey(line)\n            except keys.BadKeyError as e:\n                log.msg('Unable to parse line \"{0}\" as a key: {1!s}'\n                        .format(line, e))\n\n\n\ndef _keysFromFilepaths(filepaths, parseKey):\n    \"\"\"\n    Helper function that turns an iterable of filepaths into a generator of\n    keys.  If any file cannot be read, a message is logged but it is\n    otherwise ignored.\n\n    @param filepaths: iterable of L{twisted.python.filepath.FilePath}.\n    @type filepaths: iterable\n\n    @param parseKey: a callable that takes a string and returns a\n        L{twisted.conch.ssh.keys.Key}\n    @type parseKey: L{callable}\n\n    @return: generator of L{twisted.conch.ssh.keys.Key}\n    @rtype: generator\n\n    @since: 15.0\n    \"\"\"\n    for fp in filepaths:\n        if fp.exists():\n            try:\n                with fp.open() as f:\n                    for key in readAuthorizedKeyFile(f, parseKey):\n                        yield key\n            except (IOError, OSError) as e:\n                log.msg(\"Unable to read {0}: {1!s}\".format(fp.path, e))\n\n\n\n@implementer(IAuthorizedKeysDB)\nclass InMemorySSHKeyDB(object):\n    \"\"\"\n    Object that provides SSH public keys based on a dictionary of usernames\n    mapped to L{twisted.conch.ssh.keys.Key}s.\n\n    @since: 15.0\n    \"\"\"\n    def __init__(self, mapping):\n        \"\"\"\n        Initializes a new L{InMemorySSHKeyDB}.\n\n        @param mapping: mapping of usernames to iterables of\n            L{twisted.conch.ssh.keys.Key}s\n        @type mapping: L{dict}\n\n        \"\"\"\n        self._mapping = mapping\n\n\n    def getAuthorizedKeys(self, username):\n        return self._mapping.get(username, [])\n\n\n\n@implementer(IAuthorizedKeysDB)\nclass UNIXAuthorizedKeysFiles(object):\n    \"\"\"\n    Object that provides SSH public keys based on public keys listed in\n    authorized_keys and authorized_keys2 files in UNIX user .ssh/ directories.\n    If any of the files cannot be read, a message is logged but that file is\n    otherwise ignored.\n\n    @since: 15.0\n    \"\"\"\n    def __init__(self, userdb=None, parseKey=keys.Key.fromString):\n        \"\"\"\n        Initializes a new L{UNIXAuthorizedKeysFiles}.\n\n        @param userdb: access to the Unix user account and password database\n            (default is the Python module L{pwd})\n        @type userdb: L{pwd}-like object\n\n        @param parseKey: a callable that takes a string and returns a\n            L{twisted.conch.ssh.keys.Key}, mainly to be used for testing.  The\n            default is L{twisted.conch.ssh.keys.Key.fromString}.\n        @type parseKey: L{callable}\n        \"\"\"\n        self._userdb = userdb\n        self._parseKey = parseKey\n        if userdb is None:\n            self._userdb = pwd\n\n\n    def getAuthorizedKeys(self, username):\n        try:\n            passwd = self._userdb.getpwnam(username)\n        except KeyError:\n            return ()\n\n        root = FilePath(passwd.pw_dir).child('.ssh')\n        files = ['authorized_keys', 'authorized_keys2']\n        return _keysFromFilepaths((root.child(f) for f in files),\n                                  self._parseKey)\n\n\n\n@implementer(ICredentialsChecker)\nclass SSHPublicKeyChecker(object):\n    \"\"\"\n    Checker that authenticates SSH public keys, based on public keys listed in\n    authorized_keys and authorized_keys2 files in user .ssh/ directories.\n\n    Initializing this checker with a L{UNIXAuthorizedKeysFiles} should be\n    used instead of L{twisted.conch.checkers.SSHPublicKeyDatabase}.\n\n    @since: 15.0\n    \"\"\"\n    credentialInterfaces = (ISSHPrivateKey,)\n\n    def __init__(self, keydb):\n        \"\"\"\n        Initializes a L{SSHPublicKeyChecker}.\n\n        @param keydb: a provider of L{IAuthorizedKeysDB}\n        @type keydb: L{IAuthorizedKeysDB} provider\n        \"\"\"\n        self._keydb = keydb\n\n\n    def requestAvatarId(self, credentials):\n        d = defer.maybeDeferred(self._sanityCheckKey, credentials)\n        d.addCallback(self._checkKey, credentials)\n        d.addCallback(self._verifyKey, credentials)\n        return d\n\n\n    def _sanityCheckKey(self, credentials):\n        \"\"\"\n        Checks whether the provided credentials are a valid SSH key with a\n        signature (does not actually verify the signature).\n\n        @param credentials: the credentials offered by the user\n        @type credentials: L{ISSHPrivateKey} provider\n\n        @raise ValidPublicKey: the credentials do not include a signature. See\n            L{error.ValidPublicKey} for more information.\n\n        @raise BadKeyError: The key included with the credentials is not\n            recognized as a key.\n\n        @return: the key in the credentials\n        @rtype: L{twisted.conch.ssh.keys.Key}\n        \"\"\"\n        if not credentials.signature:\n            raise error.ValidPublicKey()\n\n        return keys.Key.fromString(credentials.blob)\n\n\n    def _checkKey(self, pubKey, credentials):\n        \"\"\"\n        Checks the public key against all authorized keys (if any) for the\n        user.\n\n        @param pubKey: the key in the credentials (just to prevent it from\n            having to be calculated again)\n        @type pubKey:\n\n        @param credentials: the credentials offered by the user\n        @type credentials: L{ISSHPrivateKey} provider\n\n        @raise UnauthorizedLogin: If the key is not authorized, or if there\n            was any error obtaining a list of authorized keys for the user.\n\n        @return: C{pubKey} if the key is authorized\n        @rtype: L{twisted.conch.ssh.keys.Key}\n        \"\"\"\n        if any(key == pubKey for key in\n               self._keydb.getAuthorizedKeys(credentials.username)):\n            return pubKey\n\n        raise UnauthorizedLogin(\"Key not authorized\")\n\n\n    def _verifyKey(self, pubKey, credentials):\n        \"\"\"\n        Checks whether the credentials themselves are valid, now that we know\n        if the key matches the user.\n\n        @param pubKey: the key in the credentials (just to prevent it from\n            having to be calculated again)\n        @type pubKey: L{twisted.conch.ssh.keys.Key}\n\n        @param credentials: the credentials offered by the user\n        @type credentials: L{ISSHPrivateKey} provider\n\n        @raise UnauthorizedLogin: If the key signature is invalid or there\n            was any error verifying the signature.\n\n        @return: The user's username, if authentication was successful\n        @rtype: L{bytes}\n        \"\"\"\n        try:\n            if pubKey.verify(credentials.signature, credentials.sigData):\n                return credentials.username\n        except:  # Any error should be treated as a failed login\n            log.err()\n            raise UnauthorizedLogin('Error while verifying key')\n\n        raise UnauthorizedLogin(\"Key signature invalid.\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/client/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n#\n\"\"\"\nClient support code for Conch.\n\nMaintainer: Paul Swartz\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/client/agent.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_default -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAccesses the key agent for user authentication.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nimport os\n\nfrom twisted.conch.ssh import agent, channel, keys\nfrom twisted.internet import protocol, reactor\nfrom twisted.python import log\n\n\n\nclass SSHAgentClient(agent.SSHAgentClient):\n\n    def __init__(self):\n        agent.SSHAgentClient.__init__(self)\n        self.blobs = []\n\n\n    def getPublicKeys(self):\n        return self.requestIdentities().addCallback(self._cbPublicKeys)\n\n\n    def _cbPublicKeys(self, blobcomm):\n        log.msg('got %i public keys' % len(blobcomm))\n        self.blobs = [x[0] for x in blobcomm]\n\n\n    def getPublicKey(self):\n        \"\"\"\n        Return a L{Key} from the first blob in C{self.blobs}, if any, or\n        return L{None}.\n        \"\"\"\n        if self.blobs:\n            return keys.Key.fromString(self.blobs.pop(0))\n        return None\n\n\n\nclass SSHAgentForwardingChannel(channel.SSHChannel):\n\n    def channelOpen(self, specificData):\n        cc = protocol.ClientCreator(reactor, SSHAgentForwardingLocal)\n        d = cc.connectUNIX(os.environ['SSH_AUTH_SOCK'])\n        d.addCallback(self._cbGotLocal)\n        d.addErrback(lambda x:self.loseConnection())\n        self.buf = ''\n\n\n    def _cbGotLocal(self, local):\n        self.local = local\n        self.dataReceived = self.local.transport.write\n        self.local.dataReceived = self.write\n\n\n    def dataReceived(self, data):\n        self.buf += data\n\n\n    def closed(self):\n        if self.local:\n            self.local.loseConnection()\n            self.local = None\n\n\nclass SSHAgentForwardingLocal(protocol.Protocol):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/client/connect.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n#\nfrom twisted.conch.client import direct\n\nconnectTypes = {\"direct\" : direct.connect}\n\ndef connect(host, port, options, verifyHostKey, userAuthObject):\n    useConnects = ['direct']\n    return _ebConnect(None, useConnects, host, port, options, verifyHostKey,\n                      userAuthObject)\n\ndef _ebConnect(f, useConnects, host, port, options, vhk, uao):\n    if not useConnects:\n        return f\n    connectType = useConnects.pop(0)\n    f = connectTypes[connectType]\n    d = f(host, port, options, vhk, uao)\n    d.addErrback(_ebConnect, useConnects, host, port, options, vhk, uao)\n    return d\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/client/default.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_knownhosts,twisted.conch.test.test_default -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nVarious classes and functions for implementing user-interaction in the\ncommand-line conch client.\n\nYou probably shouldn't use anything in this module directly, since it assumes\nyou are sitting at an interactive terminal.  For example, to programmatically\ninteract with a known_hosts database, use L{twisted.conch.client.knownhosts}.\n\"\"\"\n\nfrom __future__ import print_function\n\nfrom twisted.python import log\nfrom twisted.python.compat import (\n    nativeString, raw_input, _PY3, _b64decodebytes as decodebytes)\nfrom twisted.python.filepath import FilePath\n\nfrom twisted.conch.error import ConchError\nfrom twisted.conch.ssh import common, keys, userauth\nfrom twisted.internet import defer, protocol, reactor\n\nfrom twisted.conch.client.knownhosts import KnownHostsFile, ConsoleUI\n\nfrom twisted.conch.client import agent\n\nimport os, sys, getpass, contextlib\n\nif _PY3:\n    import io\n\n# The default location of the known hosts file (probably should be parsed out\n# of an ssh config file someday).\n_KNOWN_HOSTS = \"~/.ssh/known_hosts\"\n\n\n# This name is bound so that the unit tests can use 'patch' to override it.\n_open = open\n\ndef verifyHostKey(transport, host, pubKey, fingerprint):\n    \"\"\"\n    Verify a host's key.\n\n    This function is a gross vestige of some bad factoring in the client\n    internals.  The actual implementation, and a better signature of this logic\n    is in L{KnownHostsFile.verifyHostKey}.  This function is not deprecated yet\n    because the callers have not yet been rehabilitated, but they should\n    eventually be changed to call that method instead.\n\n    However, this function does perform two functions not implemented by\n    L{KnownHostsFile.verifyHostKey}.  It determines the path to the user's\n    known_hosts file based on the options (which should really be the options\n    object's job), and it provides an opener to L{ConsoleUI} which opens\n    '/dev/tty' so that the user will be prompted on the tty of the process even\n    if the input and output of the process has been redirected.  This latter\n    part is, somewhat obviously, not portable, but I don't know of a portable\n    equivalent that could be used.\n\n    @param host: Due to a bug in L{SSHClientTransport.verifyHostKey}, this is\n    always the dotted-quad IP address of the host being connected to.\n    @type host: L{str}\n\n    @param transport: the client transport which is attempting to connect to\n    the given host.\n    @type transport: L{SSHClientTransport}\n\n    @param fingerprint: the fingerprint of the given public key, in\n    xx:xx:xx:... format.  This is ignored in favor of getting the fingerprint\n    from the key itself.\n    @type fingerprint: L{str}\n\n    @param pubKey: The public key of the server being connected to.\n    @type pubKey: L{str}\n\n    @return: a L{Deferred} which fires with C{1} if the key was successfully\n    verified, or fails if the key could not be successfully verified.  Failure\n    types may include L{HostKeyChanged}, L{UserRejectedKey}, L{IOError} or\n    L{KeyboardInterrupt}.\n    \"\"\"\n    actualHost = transport.factory.options['host']\n    actualKey = keys.Key.fromString(pubKey)\n    kh = KnownHostsFile.fromPath(FilePath(\n            transport.factory.options['known-hosts']\n            or os.path.expanduser(_KNOWN_HOSTS)\n            ))\n    ui = ConsoleUI(lambda : _open(\"/dev/tty\", \"r+b\", buffering=0))\n    return kh.verifyHostKey(ui, actualHost, host, actualKey)\n\n\n\ndef isInKnownHosts(host, pubKey, options):\n    \"\"\"\n    Checks to see if host is in the known_hosts file for the user.\n\n    @return: 0 if it isn't, 1 if it is and is the same, 2 if it's changed.\n    @rtype: L{int}\n    \"\"\"\n    keyType = common.getNS(pubKey)[0]\n    retVal = 0\n\n    if not options['known-hosts'] and not os.path.exists(os.path.expanduser('~/.ssh/')):\n        print('Creating ~/.ssh directory...')\n        os.mkdir(os.path.expanduser('~/.ssh'))\n    kh_file = options['known-hosts'] or _KNOWN_HOSTS\n    try:\n        known_hosts = open(os.path.expanduser(kh_file), 'rb')\n    except IOError:\n        return 0\n    with known_hosts:\n        for line in known_hosts.readlines():\n            split = line.split()\n            if len(split) < 3:\n                continue\n            hosts, hostKeyType, encodedKey = split[:3]\n            if host not in hosts.split(b','): # incorrect host\n                continue\n            if hostKeyType != keyType: # incorrect type of key\n                continue\n            try:\n                decodedKey = decodebytes(encodedKey)\n            except:\n                continue\n            if decodedKey == pubKey:\n                return 1\n            else:\n                retVal = 2\n    return retVal\n\n\n\ndef getHostKeyAlgorithms(host, options):\n    \"\"\"\n    Look in known_hosts for a key corresponding to C{host}.\n    This can be used to change the order of supported key types\n    in the KEXINIT packet.\n\n    @type host: L{str}\n    @param host: the host to check in known_hosts\n    @type options: L{twisted.conch.client.options.ConchOptions}\n    @param options: options passed to client\n    @return: L{list} of L{str} representing key types or L{None}.\n    \"\"\"\n    knownHosts = KnownHostsFile.fromPath(FilePath(\n        options['known-hosts']\n        or os.path.expanduser(_KNOWN_HOSTS)\n        ))\n    keyTypes = []\n    for entry in knownHosts.iterentries():\n        if entry.matchesHost(host):\n            if entry.keyType not in keyTypes:\n                keyTypes.append(entry.keyType)\n    return keyTypes or None\n\n\n\nclass SSHUserAuthClient(userauth.SSHUserAuthClient):\n\n    def __init__(self, user, options, *args):\n        userauth.SSHUserAuthClient.__init__(self, user, *args)\n        self.keyAgent = None\n        self.options = options\n        self.usedFiles = []\n        if not options.identitys:\n            options.identitys = ['~/.ssh/id_rsa', '~/.ssh/id_dsa']\n\n\n    def serviceStarted(self):\n        if 'SSH_AUTH_SOCK' in os.environ and not self.options['noagent']:\n            log.msg('using agent')\n            cc = protocol.ClientCreator(reactor, agent.SSHAgentClient)\n            d = cc.connectUNIX(os.environ['SSH_AUTH_SOCK'])\n            d.addCallback(self._setAgent)\n            d.addErrback(self._ebSetAgent)\n        else:\n            userauth.SSHUserAuthClient.serviceStarted(self)\n\n\n    def serviceStopped(self):\n        if self.keyAgent:\n            self.keyAgent.transport.loseConnection()\n            self.keyAgent = None\n\n\n    def _setAgent(self, a):\n        self.keyAgent = a\n        d = self.keyAgent.getPublicKeys()\n        d.addBoth(self._ebSetAgent)\n        return d\n\n\n    def _ebSetAgent(self, f):\n        userauth.SSHUserAuthClient.serviceStarted(self)\n\n\n    def _getPassword(self, prompt):\n        \"\"\"\n        Prompt for a password using L{getpass.getpass}.\n\n        @param prompt: Written on tty to ask for the input.\n        @type prompt: L{str}\n        @return: The input.\n        @rtype: L{str}\n        \"\"\"\n        with self._replaceStdoutStdin():\n            try:\n                p = getpass.getpass(prompt)\n                return p\n            except (KeyboardInterrupt, IOError):\n                print()\n                raise ConchError('PEBKAC')\n\n\n    def getPassword(self, prompt = None):\n        if prompt:\n            prompt = nativeString(prompt)\n        else:\n            prompt = (\"%s@%s's password: \" %\n                (nativeString(self.user), self.transport.transport.getPeer().host))\n        try:\n            # We don't know the encoding the other side is using,\n            # signaling that is not part of the SSH protocol. But\n            # using our defaultencoding is better than just going for\n            # ASCII.\n            p = self._getPassword(prompt).encode(sys.getdefaultencoding())\n            return defer.succeed(p)\n        except ConchError:\n            return defer.fail()\n\n\n    def getPublicKey(self):\n        \"\"\"\n        Get a public key from the key agent if possible, otherwise look in\n        the next configured identity file for one.\n        \"\"\"\n        if self.keyAgent:\n            key = self.keyAgent.getPublicKey()\n            if key is not None:\n                return key\n        files = [x for x in self.options.identitys if x not in self.usedFiles]\n        log.msg(str(self.options.identitys))\n        log.msg(str(files))\n        if not files:\n            return None\n        file = files[0]\n        log.msg(file)\n        self.usedFiles.append(file)\n        file = os.path.expanduser(file)\n        file += '.pub'\n        if not os.path.exists(file):\n            return self.getPublicKey() # try again\n        try:\n            return keys.Key.fromFile(file)\n        except keys.BadKeyError:\n            return self.getPublicKey() # try again\n\n\n    def signData(self, publicKey, signData):\n        \"\"\"\n        Extend the base signing behavior by using an SSH agent to sign the\n        data, if one is available.\n\n        @type publicKey: L{Key}\n        @type signData: L{bytes}\n        \"\"\"\n        if not self.usedFiles: # agent key\n            return self.keyAgent.signData(publicKey.blob(), signData)\n        else:\n            return userauth.SSHUserAuthClient.signData(self, publicKey, signData)\n\n\n    def getPrivateKey(self):\n        \"\"\"\n        Try to load the private key from the last used file identified by\n        C{getPublicKey}, potentially asking for the passphrase if the key is\n        encrypted.\n        \"\"\"\n        file = os.path.expanduser(self.usedFiles[-1])\n        if not os.path.exists(file):\n            return None\n        try:\n            return defer.succeed(keys.Key.fromFile(file))\n        except keys.EncryptedKeyError:\n            for i in range(3):\n                prompt = \"Enter passphrase for key '%s': \" % self.usedFiles[-1]\n                try:\n                    p = self._getPassword(prompt).encode(\n                        sys.getfilesystemencoding())\n                    return defer.succeed(keys.Key.fromFile(file, passphrase=p))\n                except (keys.BadKeyError, ConchError):\n                    pass\n                return defer.fail(ConchError('bad password'))\n            raise\n        except KeyboardInterrupt:\n            print()\n            reactor.stop()\n\n\n    def getGenericAnswers(self, name, instruction, prompts):\n        responses = []\n        with self._replaceStdoutStdin():\n            if name:\n                print(name.decode(\"utf-8\"))\n            if instruction:\n                print(instruction.decode(\"utf-8\"))\n            for prompt, echo in prompts:\n                prompt = prompt.decode(\"utf-8\")\n                if echo:\n                    responses.append(raw_input(prompt))\n                else:\n                    responses.append(getpass.getpass(prompt))\n        return defer.succeed(responses)\n\n\n    @classmethod\n    def _openTty(cls):\n        \"\"\"\n        Open /dev/tty as two streams one in read, one in write mode,\n        and return them.\n\n        @return: File objects for reading and writing to /dev/tty,\n                 corresponding to standard input and standard output.\n        @rtype: A L{tuple} of L{io.TextIOWrapper} on Python 3.\n                A L{tuple} of binary files on Python 2.\n        \"\"\"\n        stdin = open(\"/dev/tty\", \"rb\")\n        stdout = open(\"/dev/tty\", \"wb\")\n        if _PY3:\n            stdin = io.TextIOWrapper(stdin)\n            stdout = io.TextIOWrapper(stdout)\n        return stdin, stdout\n\n\n    @classmethod\n    @contextlib.contextmanager\n    def _replaceStdoutStdin(cls):\n        \"\"\"\n        Contextmanager that replaces stdout and stdin with /dev/tty\n        and resets them when it is done.\n        \"\"\"\n        oldout, oldin = sys.stdout, sys.stdin\n        sys.stdin, sys.stdout = cls._openTty()\n        try:\n            yield\n        finally:\n            sys.stdout.close()\n            sys.stdin.close()\n            sys.stdout, sys.stdin = oldout, oldin\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/client/direct.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\nfrom __future__ import print_function\n\nfrom twisted.internet import defer, protocol, reactor\nfrom twisted.conch import error\nfrom twisted.conch.ssh import transport\nfrom twisted.python import log\n\n\n\nclass SSHClientFactory(protocol.ClientFactory):\n\n    def __init__(self, d, options, verifyHostKey, userAuthObject):\n        self.d = d\n        self.options = options\n        self.verifyHostKey = verifyHostKey\n        self.userAuthObject = userAuthObject\n\n\n    def clientConnectionLost(self, connector, reason):\n        if self.options['reconnect']:\n            connector.connect()\n\n\n    def clientConnectionFailed(self, connector, reason):\n        if self.d is None:\n            return\n        d, self.d = self.d, None\n        d.errback(reason)\n\n\n    def buildProtocol(self, addr):\n        trans = SSHClientTransport(self)\n        if self.options['ciphers']:\n            trans.supportedCiphers = self.options['ciphers']\n        if self.options['macs']:\n            trans.supportedMACs = self.options['macs']\n        if self.options['compress']:\n            trans.supportedCompressions[0:1] = ['zlib']\n        if self.options['host-key-algorithms']:\n            trans.supportedPublicKeys = self.options['host-key-algorithms']\n        return trans\n\n\n\nclass SSHClientTransport(transport.SSHClientTransport):\n\n    def __init__(self, factory):\n        self.factory = factory\n        self.unixServer = None\n\n\n    def connectionLost(self, reason):\n        if self.unixServer:\n            d = self.unixServer.stopListening()\n            self.unixServer = None\n        else:\n            d = defer.succeed(None)\n        d.addCallback(lambda x:\n            transport.SSHClientTransport.connectionLost(self, reason))\n\n\n    def receiveError(self, code, desc):\n        if self.factory.d is None:\n            return\n        d, self.factory.d = self.factory.d, None\n        d.errback(error.ConchError(desc, code))\n\n\n    def sendDisconnect(self, code, reason):\n        if self.factory.d is None:\n            return\n        d, self.factory.d = self.factory.d, None\n        transport.SSHClientTransport.sendDisconnect(self, code, reason)\n        d.errback(error.ConchError(reason, code))\n\n\n    def receiveDebug(self, alwaysDisplay, message, lang):\n        log.msg('Received Debug Message: %s' % message)\n        if alwaysDisplay: # XXX what should happen here?\n            print(message)\n\n\n    def verifyHostKey(self, pubKey, fingerprint):\n        return self.factory.verifyHostKey(self, self.transport.getPeer().host, pubKey,\n                                          fingerprint)\n\n\n    def setService(self, service):\n        log.msg('setting client server to %s' % service)\n        transport.SSHClientTransport.setService(self, service)\n        if service.name != 'ssh-userauth' and self.factory.d is not None:\n            d, self.factory.d = self.factory.d, None\n            d.callback(None)\n\n\n    def connectionSecure(self):\n        self.requestService(self.factory.userAuthObject)\n\n\n\ndef connect(host, port, options, verifyHostKey, userAuthObject):\n    d = defer.Deferred()\n    factory = SSHClientFactory(d, options, verifyHostKey, userAuthObject)\n    reactor.connectTCP(host, port, factory)\n    return d\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/client/knownhosts.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_knownhosts -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAn implementation of the OpenSSH known_hosts database.\n\n@since: 8.2\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport hmac\nfrom binascii import Error as DecodeError, b2a_base64, a2b_base64\nfrom contextlib import closing\nfrom hashlib import sha1\nimport sys\n\nfrom zope.interface import implementer\n\nfrom twisted.conch.interfaces import IKnownHostEntry\nfrom twisted.conch.error import HostKeyChanged, UserRejectedKey, InvalidEntry\nfrom twisted.conch.ssh.keys import Key, BadKeyError, FingerprintFormats\nfrom twisted.internet import defer\nfrom twisted.python import log\nfrom twisted.python.compat import nativeString, unicode\nfrom twisted.python.randbytes import secureRandom\nfrom twisted.python.util import FancyEqMixin\n\n\ndef _b64encode(s):\n    \"\"\"\n    Encode a binary string as base64 with no trailing newline.\n\n    @param s: The string to encode.\n    @type s: L{bytes}\n\n    @return: The base64-encoded string.\n    @rtype: L{bytes}\n    \"\"\"\n    return b2a_base64(s).strip()\n\n\n\ndef _extractCommon(string):\n    \"\"\"\n    Extract common elements of base64 keys from an entry in a hosts file.\n\n    @param string: A known hosts file entry (a single line).\n    @type string: L{bytes}\n\n    @return: a 4-tuple of hostname data (L{bytes}), ssh key type (L{bytes}), key\n        (L{Key}), and comment (L{bytes} or L{None}).  The hostname data is\n        simply the beginning of the line up to the first occurrence of\n        whitespace.\n    @rtype: L{tuple}\n    \"\"\"\n    elements = string.split(None, 2)\n    if len(elements) != 3:\n        raise InvalidEntry()\n    hostnames, keyType, keyAndComment = elements\n    splitkey = keyAndComment.split(None, 1)\n    if len(splitkey) == 2:\n        keyString, comment = splitkey\n        comment = comment.rstrip(b\"\\n\")\n    else:\n        keyString = splitkey[0]\n        comment = None\n    key = Key.fromString(a2b_base64(keyString))\n    return hostnames, keyType, key, comment\n\n\n\nclass _BaseEntry(object):\n    \"\"\"\n    Abstract base of both hashed and non-hashed entry objects, since they\n    represent keys and key types the same way.\n\n    @ivar keyType: The type of the key; either ssh-dss or ssh-rsa.\n    @type keyType: L{bytes}\n\n    @ivar publicKey: The server public key indicated by this line.\n    @type publicKey: L{twisted.conch.ssh.keys.Key}\n\n    @ivar comment: Trailing garbage after the key line.\n    @type comment: L{bytes}\n    \"\"\"\n\n    def __init__(self, keyType, publicKey, comment):\n        self.keyType = keyType\n        self.publicKey = publicKey\n        self.comment = comment\n\n\n    def matchesKey(self, keyObject):\n        \"\"\"\n        Check to see if this entry matches a given key object.\n\n        @param keyObject: A public key object to check.\n        @type keyObject: L{Key}\n\n        @return: C{True} if this entry's key matches C{keyObject}, C{False}\n            otherwise.\n        @rtype: L{bool}\n        \"\"\"\n        return self.publicKey == keyObject\n\n\n\n@implementer(IKnownHostEntry)\nclass PlainEntry(_BaseEntry):\n    \"\"\"\n    A L{PlainEntry} is a representation of a plain-text entry in a known_hosts\n    file.\n\n    @ivar _hostnames: the list of all host-names associated with this entry.\n    @type _hostnames: L{list} of L{bytes}\n    \"\"\"\n\n    def __init__(self, hostnames, keyType, publicKey, comment):\n        self._hostnames = hostnames\n        super(PlainEntry, self).__init__(keyType, publicKey, comment)\n\n\n    @classmethod\n    def fromString(cls, string):\n        \"\"\"\n        Parse a plain-text entry in a known_hosts file, and return a\n        corresponding L{PlainEntry}.\n\n        @param string: a space-separated string formatted like \"hostname\n        key-type base64-key-data comment\".\n\n        @type string: L{bytes}\n\n        @raise DecodeError: if the key is not valid encoded as valid base64.\n\n        @raise InvalidEntry: if the entry does not have the right number of\n        elements and is therefore invalid.\n\n        @raise BadKeyError: if the key, once decoded from base64, is not\n        actually an SSH key.\n\n        @return: an IKnownHostEntry representing the hostname and key in the\n        input line.\n\n        @rtype: L{PlainEntry}\n        \"\"\"\n        hostnames, keyType, key, comment = _extractCommon(string)\n        self = cls(hostnames.split(b\",\"), keyType, key, comment)\n        return self\n\n\n    def matchesHost(self, hostname):\n        \"\"\"\n        Check to see if this entry matches a given hostname.\n\n        @param hostname: A hostname or IP address literal to check against this\n            entry.\n        @type hostname: L{bytes}\n\n        @return: C{True} if this entry is for the given hostname or IP address,\n            C{False} otherwise.\n        @rtype: L{bool}\n        \"\"\"\n        if isinstance(hostname, unicode):\n            hostname = hostname.encode(\"utf-8\")\n        return hostname in self._hostnames\n\n\n    def toString(self):\n        \"\"\"\n        Implement L{IKnownHostEntry.toString} by recording the comma-separated\n        hostnames, key type, and base-64 encoded key.\n\n        @return: The string representation of this entry, with unhashed hostname\n            information.\n        @rtype: L{bytes}\n        \"\"\"\n        fields = [b','.join(self._hostnames),\n                  self.keyType,\n                  _b64encode(self.publicKey.blob())]\n        if self.comment is not None:\n            fields.append(self.comment)\n        return b' '.join(fields)\n\n\n\n@implementer(IKnownHostEntry)\nclass UnparsedEntry(object):\n    \"\"\"\n    L{UnparsedEntry} is an entry in a L{KnownHostsFile} which can't actually be\n    parsed; therefore it matches no keys and no hosts.\n    \"\"\"\n\n    def __init__(self, string):\n        \"\"\"\n        Create an unparsed entry from a line in a known_hosts file which cannot\n        otherwise be parsed.\n        \"\"\"\n        self._string = string\n\n\n    def matchesHost(self, hostname):\n        \"\"\"\n        Always returns False.\n        \"\"\"\n        return False\n\n\n    def matchesKey(self, key):\n        \"\"\"\n        Always returns False.\n        \"\"\"\n        return False\n\n\n    def toString(self):\n        \"\"\"\n        Returns the input line, without its newline if one was given.\n\n        @return: The string representation of this entry, almost exactly as was\n            used to initialize this entry but without a trailing newline.\n        @rtype: L{bytes}\n        \"\"\"\n        return self._string.rstrip(b\"\\n\")\n\n\n\ndef _hmacedString(key, string):\n    \"\"\"\n    Return the SHA-1 HMAC hash of the given key and string.\n\n    @param key: The HMAC key.\n    @type key: L{bytes}\n\n    @param string: The string to be hashed.\n    @type string: L{bytes}\n\n    @return: The keyed hash value.\n    @rtype: L{bytes}\n    \"\"\"\n    hash = hmac.HMAC(key, digestmod=sha1)\n    if isinstance(string, unicode):\n        string = string.encode(\"utf-8\")\n    hash.update(string)\n    return hash.digest()\n\n\n\n@implementer(IKnownHostEntry)\nclass HashedEntry(_BaseEntry, FancyEqMixin):\n    \"\"\"\n    A L{HashedEntry} is a representation of an entry in a known_hosts file\n    where the hostname has been hashed and salted.\n\n    @ivar _hostSalt: the salt to combine with a hostname for hashing.\n\n    @ivar _hostHash: the hashed representation of the hostname.\n\n    @cvar MAGIC: the 'hash magic' string used to identify a hashed line in a\n    known_hosts file as opposed to a plaintext one.\n    \"\"\"\n\n    MAGIC = b'|1|'\n\n    compareAttributes = (\n        \"_hostSalt\", \"_hostHash\", \"keyType\", \"publicKey\", \"comment\")\n\n    def __init__(self, hostSalt, hostHash, keyType, publicKey, comment):\n        self._hostSalt = hostSalt\n        self._hostHash = hostHash\n        super(HashedEntry, self).__init__(keyType, publicKey, comment)\n\n\n    @classmethod\n    def fromString(cls, string):\n        \"\"\"\n        Load a hashed entry from a string representing a line in a known_hosts\n        file.\n\n        @param string: A complete single line from a I{known_hosts} file,\n            formatted as defined by OpenSSH.\n        @type string: L{bytes}\n\n        @raise DecodeError: if the key, the hostname, or the is not valid\n            encoded as valid base64\n\n        @raise InvalidEntry: if the entry does not have the right number of\n            elements and is therefore invalid, or the host/hash portion contains\n            more items than just the host and hash.\n\n        @raise BadKeyError: if the key, once decoded from base64, is not\n            actually an SSH key.\n\n        @return: The newly created L{HashedEntry} instance, initialized with the\n            information from C{string}.\n        \"\"\"\n        stuff, keyType, key, comment = _extractCommon(string)\n        saltAndHash = stuff[len(cls.MAGIC):].split(b\"|\")\n        if len(saltAndHash) != 2:\n            raise InvalidEntry()\n        hostSalt, hostHash = saltAndHash\n        self = cls(a2b_base64(hostSalt), a2b_base64(hostHash),\n                   keyType, key, comment)\n        return self\n\n\n    def matchesHost(self, hostname):\n        \"\"\"\n        Implement L{IKnownHostEntry.matchesHost} to compare the hash of the\n        input to the stored hash.\n\n        @param hostname: A hostname or IP address literal to check against this\n            entry.\n        @type hostname: L{bytes}\n\n        @return: C{True} if this entry is for the given hostname or IP address,\n            C{False} otherwise.\n        @rtype: L{bool}\n        \"\"\"\n        return (_hmacedString(self._hostSalt, hostname) == self._hostHash)\n\n\n    def toString(self):\n        \"\"\"\n        Implement L{IKnownHostEntry.toString} by base64-encoding the salt, host\n        hash, and key.\n\n        @return: The string representation of this entry, with the hostname part\n            hashed.\n        @rtype: L{bytes}\n        \"\"\"\n        fields = [self.MAGIC + b'|'.join([_b64encode(self._hostSalt),\n                                          _b64encode(self._hostHash)]),\n                  self.keyType,\n                  _b64encode(self.publicKey.blob())]\n        if self.comment is not None:\n            fields.append(self.comment)\n        return b' '.join(fields)\n\n\n\nclass KnownHostsFile(object):\n    \"\"\"\n    A structured representation of an OpenSSH-format ~/.ssh/known_hosts file.\n\n    @ivar _added: A list of L{IKnownHostEntry} providers which have been added\n        to this instance in memory but not yet saved.\n\n    @ivar _clobber: A flag indicating whether the current contents of the save\n        path will be disregarded and potentially overwritten or not.  If\n        C{True}, this will be done.  If C{False}, entries in the save path will\n        be read and new entries will be saved by appending rather than\n        overwriting.\n    @type _clobber: L{bool}\n\n    @ivar _savePath: See C{savePath} parameter of L{__init__}.\n    \"\"\"\n\n    def __init__(self, savePath):\n        \"\"\"\n        Create a new, empty KnownHostsFile.\n\n        Unless you want to erase the current contents of C{savePath}, you want\n        to use L{KnownHostsFile.fromPath} instead.\n\n        @param savePath: The L{FilePath} to which to save new entries.\n        @type savePath: L{FilePath}\n        \"\"\"\n        self._added = []\n        self._savePath = savePath\n        self._clobber = True\n\n\n    @property\n    def savePath(self):\n        \"\"\"\n        @see: C{savePath} parameter of L{__init__}\n        \"\"\"\n        return self._savePath\n\n\n    def iterentries(self):\n        \"\"\"\n        Iterate over the host entries in this file.\n\n        @return: An iterable the elements of which provide L{IKnownHostEntry}.\n            There is an element for each entry in the file as well as an element\n            for each added but not yet saved entry.\n        @rtype: iterable of L{IKnownHostEntry} providers\n        \"\"\"\n        for entry in self._added:\n            yield entry\n\n        if self._clobber:\n            return\n\n        try:\n            fp = self._savePath.open()\n        except IOError:\n            return\n\n        with fp:\n            for line in fp:\n                try:\n                    if line.startswith(HashedEntry.MAGIC):\n                        entry = HashedEntry.fromString(line)\n                    else:\n                        entry = PlainEntry.fromString(line)\n                except (DecodeError, InvalidEntry, BadKeyError):\n                    entry = UnparsedEntry(line)\n                yield entry\n\n\n    def hasHostKey(self, hostname, key):\n        \"\"\"\n        Check for an entry with matching hostname and key.\n\n        @param hostname: A hostname or IP address literal to check for.\n        @type hostname: L{bytes}\n\n        @param key: The public key to check for.\n        @type key: L{Key}\n\n        @return: C{True} if the given hostname and key are present in this file,\n            C{False} if they are not.\n        @rtype: L{bool}\n\n        @raise HostKeyChanged: if the host key found for the given hostname\n            does not match the given key.\n        \"\"\"\n        for lineidx, entry in enumerate(self.iterentries(), -len(self._added)):\n            if entry.matchesHost(hostname) and entry.keyType == key.sshType():\n                if entry.matchesKey(key):\n                    return True\n                else:\n                    # Notice that lineidx is 0-based but HostKeyChanged.lineno\n                    # is 1-based.\n                    if lineidx < 0:\n                        line = None\n                        path = None\n                    else:\n                        line = lineidx + 1\n                        path = self._savePath\n                    raise HostKeyChanged(entry, path, line)\n        return False\n\n\n    def verifyHostKey(self, ui, hostname, ip, key):\n        \"\"\"\n        Verify the given host key for the given IP and host, asking for\n        confirmation from, and notifying, the given UI about changes to this\n        file.\n\n        @param ui: The user interface to request an IP address from.\n\n        @param hostname: The hostname that the user requested to connect to.\n\n        @param ip: The string representation of the IP address that is actually\n        being connected to.\n\n        @param key: The public key of the server.\n\n        @return: a L{Deferred} that fires with True when the key has been\n            verified, or fires with an errback when the key either cannot be\n            verified or has changed.\n        @rtype: L{Deferred}\n        \"\"\"\n        hhk = defer.maybeDeferred(self.hasHostKey, hostname, key)\n        def gotHasKey(result):\n            if result:\n                if not self.hasHostKey(ip, key):\n                    ui.warn(\"Warning: Permanently added the %s host key for \"\n                            \"IP address '%s' to the list of known hosts.\" %\n                            (key.type(), nativeString(ip)))\n                    self.addHostKey(ip, key)\n                    self.save()\n                return result\n            else:\n                def promptResponse(response):\n                    if response:\n                        self.addHostKey(hostname, key)\n                        self.addHostKey(ip, key)\n                        self.save()\n                        return response\n                    else:\n                        raise UserRejectedKey()\n\n                keytype = key.type()\n\n                if keytype == \"EC\":\n                    keytype = \"ECDSA\"\n\n                prompt = (\n                    \"The authenticity of host '%s (%s)' \"\n                    \"can't be established.\\n\"\n                    \"%s key fingerprint is SHA256:%s.\\n\"\n                    \"Are you sure you want to continue connecting (yes/no)? \" %\n                    (nativeString(hostname), nativeString(ip), keytype,\n                     key.fingerprint(format=FingerprintFormats.SHA256_BASE64)))\n                proceed = ui.prompt(prompt.encode(sys.getdefaultencoding()))\n                return proceed.addCallback(promptResponse)\n        return hhk.addCallback(gotHasKey)\n\n\n    def addHostKey(self, hostname, key):\n        \"\"\"\n        Add a new L{HashedEntry} to the key database.\n\n        Note that you still need to call L{KnownHostsFile.save} if you wish\n        these changes to be persisted.\n\n        @param hostname: A hostname or IP address literal to associate with the\n            new entry.\n        @type hostname: L{bytes}\n\n        @param key: The public key to associate with the new entry.\n        @type key: L{Key}\n\n        @return: The L{HashedEntry} that was added.\n        @rtype: L{HashedEntry}\n        \"\"\"\n        salt = secureRandom(20)\n        keyType = key.sshType()\n        entry = HashedEntry(salt, _hmacedString(salt, hostname),\n                            keyType, key, None)\n        self._added.append(entry)\n        return entry\n\n\n    def save(self):\n        \"\"\"\n        Save this L{KnownHostsFile} to the path it was loaded from.\n        \"\"\"\n        p = self._savePath.parent()\n        if not p.isdir():\n            p.makedirs()\n\n        if self._clobber:\n            mode = \"wb\"\n        else:\n            mode = \"ab\"\n\n        with self._savePath.open(mode) as hostsFileObj:\n            if self._added:\n                hostsFileObj.write(\n                    b\"\\n\".join([entry.toString() for entry in self._added]) +\n                    b\"\\n\")\n                self._added = []\n        self._clobber = False\n\n\n    @classmethod\n    def fromPath(cls, path):\n        \"\"\"\n        Create a new L{KnownHostsFile}, potentially reading existing known\n        hosts information from the given file.\n\n        @param path: A path object to use for both reading contents from and\n            later saving to.  If no file exists at this path, it is not an\n            error; a L{KnownHostsFile} with no entries is returned.\n        @type path: L{FilePath}\n\n        @return: A L{KnownHostsFile} initialized with entries from C{path}.\n        @rtype: L{KnownHostsFile}\n        \"\"\"\n        knownHosts = cls(path)\n        knownHosts._clobber = False\n        return knownHosts\n\n\n\nclass ConsoleUI(object):\n    \"\"\"\n    A UI object that can ask true/false questions and post notifications on the\n    console, to be used during key verification.\n    \"\"\"\n    def __init__(self, opener):\n        \"\"\"\n        @param opener: A no-argument callable which should open a console\n            binary-mode file-like object to be used for reading and writing.\n            This initializes the C{opener} attribute.\n        @type opener: callable taking no arguments and returning a read/write\n            file-like object\n        \"\"\"\n        self.opener = opener\n\n\n    def prompt(self, text):\n        \"\"\"\n        Write the given text as a prompt to the console output, then read a\n        result from the console input.\n\n        @param text: Something to present to a user to solicit a yes or no\n            response.\n        @type text: L{bytes}\n\n        @return: a L{Deferred} which fires with L{True} when the user answers\n            'yes' and L{False} when the user answers 'no'.  It may errback if\n            there were any I/O errors.\n        \"\"\"\n        d = defer.succeed(None)\n        def body(ignored):\n            with closing(self.opener()) as f:\n                f.write(text)\n                while True:\n                    answer = f.readline().strip().lower()\n                    if answer == b'yes':\n                        return True\n                    elif answer == b'no':\n                        return False\n                    else:\n                        f.write(b\"Please type 'yes' or 'no': \")\n        return d.addCallback(body)\n\n\n    def warn(self, text):\n        \"\"\"\n        Notify the user (non-interactively) of the provided text, by writing it\n        to the console.\n\n        @param text: Some information the user is to be made aware of.\n        @type text: L{bytes}\n        \"\"\"\n        try:\n            with closing(self.opener()) as f:\n                f.write(text)\n        except:\n            log.err()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/client/options.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n#\nfrom twisted.conch.ssh.transport import SSHClientTransport, SSHCiphers\nfrom twisted.python import usage\nfrom twisted.python.compat import unicode\n\nimport sys\n\nclass ConchOptions(usage.Options):\n\n    optParameters = [['user', 'l', None, 'Log in using this user name.'],\n                     ['identity', 'i', None],\n                     ['ciphers', 'c', None],\n                     ['macs', 'm', None],\n                     ['port', 'p', None, 'Connect to this port.  Server must be on the same port.'],\n                     ['option', 'o', None, 'Ignored OpenSSH options'],\n                     ['host-key-algorithms', '', None],\n                     ['known-hosts', '', None, 'File to check for host keys'],\n                     ['user-authentications', '', None, 'Types of user authentications to use.'],\n                     ['logfile', '', None, 'File to log to, or - for stdout'],\n                   ]\n\n    optFlags = [['version', 'V', 'Display version number only.'],\n                ['compress', 'C', 'Enable compression.'],\n                ['log', 'v', 'Enable logging (defaults to stderr)'],\n                ['nox11', 'x', 'Disable X11 connection forwarding (default)'],\n                ['agent', 'A', 'Enable authentication agent forwarding'],\n                ['noagent', 'a', 'Disable authentication agent forwarding (default)'],\n                ['reconnect', 'r', 'Reconnect to the server if the connection is lost.'],\n               ]\n\n    compData = usage.Completions(\n        mutuallyExclusive=[(\"agent\", \"noagent\")],\n        optActions={\n            \"user\": usage.CompleteUsernames(),\n            \"ciphers\": usage.CompleteMultiList(\n                SSHCiphers.cipherMap.keys(),\n                descr='ciphers to choose from'),\n            \"macs\": usage.CompleteMultiList(\n                SSHCiphers.macMap.keys(),\n                descr='macs to choose from'),\n            \"host-key-algorithms\": usage.CompleteMultiList(\n                SSHClientTransport.supportedPublicKeys,\n                descr='host key algorithms to choose from'),\n            #\"user-authentications\": usage.CompleteMultiList(?\n            # descr='user authentication types' ),\n            },\n        extraActions=[usage.CompleteUserAtHost(),\n                      usage.Completer(descr=\"command\"),\n                      usage.Completer(descr='argument',\n                                      repeat=True)]\n        )\n\n    def __init__(self, *args, **kw):\n        usage.Options.__init__(self, *args, **kw)\n        self.identitys = []\n        self.conns = None\n\n    def opt_identity(self, i):\n        \"\"\"Identity for public-key authentication\"\"\"\n        self.identitys.append(i)\n\n    def opt_ciphers(self, ciphers):\n        \"Select encryption algorithms\"\n        ciphers = ciphers.split(',')\n        for cipher in ciphers:\n            if cipher not in SSHCiphers.cipherMap:\n                sys.exit(\"Unknown cipher type '%s'\" % cipher)\n        self['ciphers'] = ciphers\n\n\n    def opt_macs(self, macs):\n        \"Specify MAC algorithms\"\n        if isinstance(macs, unicode):\n            macs = macs.encode(\"utf-8\")\n        macs = macs.split(b',')\n        for mac in macs:\n            if mac not in SSHCiphers.macMap:\n                sys.exit(\"Unknown mac type '%r'\" % mac)\n        self['macs'] = macs\n\n    def opt_host_key_algorithms(self, hkas):\n        \"Select host key algorithms\"\n        if isinstance(hkas, unicode):\n            hkas = hkas.encode(\"utf-8\")\n        hkas = hkas.split(b',')\n        for hka in hkas:\n            if hka not in SSHClientTransport.supportedPublicKeys:\n                sys.exit(\"Unknown host key type '%r'\" % hka)\n        self['host-key-algorithms'] = hkas\n\n    def opt_user_authentications(self, uas):\n        \"Choose how to authenticate to the remote server\"\n        if isinstance(uas, unicode):\n            uas = uas.encode(\"utf-8\")\n        self['user-authentications'] = uas.split(b',')\n\n#    def opt_compress(self):\n#        \"Enable compression\"\n#        self.enableCompression = 1\n#        SSHClientTransport.supportedCompressions[0:1] = ['zlib']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/endpoints.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_endpoints -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nEndpoint implementations of various SSH interactions.\n\"\"\"\n\n__all__ = [\n    'AuthenticationFailed', 'SSHCommandAddress', 'SSHCommandClientEndpoint']\n\nfrom struct import unpack\nfrom os.path import expanduser\n\nimport signal\n\nfrom zope.interface import Interface, implementer\n\nfrom twisted.logger import Logger\nfrom twisted.python.compat import nativeString, networkString\nfrom twisted.python.filepath import FilePath\nfrom twisted.python.failure import Failure\nfrom twisted.internet.error import ConnectionDone, ProcessTerminated\nfrom twisted.internet.interfaces import IStreamClientEndpoint\nfrom twisted.internet.protocol import Factory\nfrom twisted.internet.defer import Deferred, succeed, CancelledError\nfrom twisted.internet.endpoints import TCP4ClientEndpoint, connectProtocol\n\nfrom twisted.conch.ssh.keys import Key\nfrom twisted.conch.ssh.common import getNS, NS\nfrom twisted.conch.ssh.transport import SSHClientTransport\nfrom twisted.conch.ssh.connection import SSHConnection\nfrom twisted.conch.ssh.userauth import SSHUserAuthClient\nfrom twisted.conch.ssh.channel import SSHChannel\nfrom twisted.conch.client.knownhosts import ConsoleUI, KnownHostsFile\nfrom twisted.conch.client.agent import SSHAgentClient\nfrom twisted.conch.client.default import _KNOWN_HOSTS\n\n\nclass AuthenticationFailed(Exception):\n    \"\"\"\n    An SSH session could not be established because authentication was not\n    successful.\n    \"\"\"\n\n\n\n# This should be public.  See #6541.\nclass _ISSHConnectionCreator(Interface):\n    \"\"\"\n    An L{_ISSHConnectionCreator} knows how to create SSH connections somehow.\n    \"\"\"\n    def secureConnection():\n        \"\"\"\n        Return a new, connected, secured, but not yet authenticated instance of\n        L{twisted.conch.ssh.transport.SSHServerTransport} or\n        L{twisted.conch.ssh.transport.SSHClientTransport}.\n        \"\"\"\n\n\n    def cleanupConnection(connection, immediate):\n        \"\"\"\n        Perform cleanup necessary for a connection object previously returned\n        from this creator's C{secureConnection} method.\n\n        @param connection: An L{twisted.conch.ssh.transport.SSHServerTransport}\n            or L{twisted.conch.ssh.transport.SSHClientTransport} returned by a\n            previous call to C{secureConnection}.  It is no longer needed by\n            the caller of that method and may be closed or otherwise cleaned up\n            as necessary.\n\n        @param immediate: If C{True} don't wait for any network communication,\n            just close the connection immediately and as aggressively as\n            necessary.\n        \"\"\"\n\n\n\nclass SSHCommandAddress(object):\n    \"\"\"\n    An L{SSHCommandAddress} instance represents the address of an SSH server, a\n    username which was used to authenticate with that server, and a command\n    which was run there.\n\n    @ivar server: See L{__init__}\n    @ivar username: See L{__init__}\n    @ivar command: See L{__init__}\n    \"\"\"\n    def __init__(self, server, username, command):\n        \"\"\"\n        @param server: The address of the SSH server on which the command is\n            running.\n        @type server: L{IAddress} provider\n\n        @param username: An authentication username which was used to\n            authenticate against the server at the given address.\n        @type username: L{bytes}\n\n        @param command: A command which was run in a session channel on the\n            server at the given address.\n        @type command: L{bytes}\n        \"\"\"\n        self.server = server\n        self.username = username\n        self.command = command\n\n\n\nclass _CommandChannel(SSHChannel):\n    \"\"\"\n    A L{_CommandChannel} executes a command in a session channel and connects\n    its input and output to an L{IProtocol} provider.\n\n    @ivar _creator: See L{__init__}\n    @ivar _command: See L{__init__}\n    @ivar _protocolFactory:  See L{__init__}\n    @ivar _commandConnected:  See L{__init__}\n    @ivar _protocol: An L{IProtocol} provider created using C{_protocolFactory}\n        which is hooked up to the running command's input and output streams.\n    \"\"\"\n    name = b'session'\n    _log = Logger()\n\n    def __init__(self, creator, command, protocolFactory, commandConnected):\n        \"\"\"\n        @param creator: The L{_ISSHConnectionCreator} provider which was used\n            to get the connection which this channel exists on.\n        @type creator: L{_ISSHConnectionCreator} provider\n\n        @param command: The command to be executed.\n        @type command: L{bytes}\n\n        @param protocolFactory: A client factory to use to build a L{IProtocol}\n            provider to use to associate with the running command.\n\n        @param commandConnected: A L{Deferred} to use to signal that execution\n            of the command has failed or that it has succeeded and the command\n            is now running.\n        @type commandConnected: L{Deferred}\n        \"\"\"\n        SSHChannel.__init__(self)\n        self._creator = creator\n        self._command = command\n        self._protocolFactory = protocolFactory\n        self._commandConnected = commandConnected\n        self._reason = None\n\n\n    def openFailed(self, reason):\n        \"\"\"\n        When the request to open a new channel to run this command in fails,\n        fire the C{commandConnected} deferred with a failure indicating that.\n        \"\"\"\n        self._commandConnected.errback(reason)\n\n\n    def channelOpen(self, ignored):\n        \"\"\"\n        When the request to open a new channel to run this command in succeeds,\n        issue an C{\"exec\"} request to run the command.\n        \"\"\"\n        command = self.conn.sendRequest(\n            self, b'exec', NS(self._command), wantReply=True)\n        command.addCallbacks(self._execSuccess, self._execFailure)\n\n\n    def _execFailure(self, reason):\n        \"\"\"\n        When the request to execute the command in this channel fails, fire the\n        C{commandConnected} deferred with a failure indicating this.\n\n        @param reason: The cause of the command execution failure.\n        @type reason: L{Failure}\n        \"\"\"\n        self._commandConnected.errback(reason)\n\n\n    def _execSuccess(self, ignored):\n        \"\"\"\n        When the request to execute the command in this channel succeeds, use\n        C{protocolFactory} to build a protocol to handle the command's input\n        and output and connect the protocol to a transport representing those\n        streams.\n\n        Also fire C{commandConnected} with the created protocol after it is\n        connected to its transport.\n\n        @param ignored: The (ignored) result of the execute request\n        \"\"\"\n        self._protocol = self._protocolFactory.buildProtocol(\n            SSHCommandAddress(\n                self.conn.transport.transport.getPeer(),\n                self.conn.transport.creator.username,\n                self.conn.transport.creator.command))\n        self._protocol.makeConnection(self)\n        self._commandConnected.callback(self._protocol)\n\n\n    def dataReceived(self, data):\n        \"\"\"\n        When the command's stdout data arrives over the channel, deliver it to\n        the protocol instance.\n\n        @param data: The bytes from the command's stdout.\n        @type data: L{bytes}\n        \"\"\"\n        self._protocol.dataReceived(data)\n\n\n    def request_exit_status(self, data):\n        \"\"\"\n        When the server sends the command's exit status, record it for later\n        delivery to the protocol.\n\n        @param data: The network-order four byte representation of the exit\n            status of the command.\n        @type data: L{bytes}\n        \"\"\"\n        (status,) = unpack('>L', data)\n        if status != 0:\n            self._reason = ProcessTerminated(status, None, None)\n\n\n    def request_exit_signal(self, data):\n        \"\"\"\n        When the server sends the command's exit status, record it for later\n        delivery to the protocol.\n\n        @param data: The network-order four byte representation of the exit\n            signal of the command.\n        @type data: L{bytes}\n        \"\"\"\n        shortSignalName, data = getNS(data)\n        coreDumped, data = bool(ord(data[0:1])), data[1:]\n        errorMessage, data = getNS(data)\n        languageTag, data = getNS(data)\n        signalName = \"SIG%s\" % (nativeString(shortSignalName),)\n        signalID = getattr(signal, signalName, -1)\n        self._log.info(\n            \"Process exited with signal {shortSignalName!r};\"\n            \" core dumped: {coreDumped};\"\n            \" error message: {errorMessage};\"\n            \" language: {languageTag!r}\",\n            shortSignalName=shortSignalName,\n            coreDumped=coreDumped,\n            errorMessage=errorMessage.decode('utf-8'),\n            languageTag=languageTag,\n        )\n        self._reason = ProcessTerminated(None, signalID, None)\n\n\n    def closed(self):\n        \"\"\"\n        When the channel closes, deliver disconnection notification to the\n        protocol.\n        \"\"\"\n        self._creator.cleanupConnection(self.conn, False)\n        if self._reason is None:\n            reason = ConnectionDone(\"ssh channel closed\")\n        else:\n            reason = self._reason\n        self._protocol.connectionLost(Failure(reason))\n\n\n\nclass _ConnectionReady(SSHConnection):\n    \"\"\"\n    L{_ConnectionReady} is an L{SSHConnection} (an SSH service) which only\n    propagates the I{serviceStarted} event to a L{Deferred} to be handled\n    elsewhere.\n    \"\"\"\n    def __init__(self, ready):\n        \"\"\"\n        @param ready: A L{Deferred} which should be fired when\n            I{serviceStarted} happens.\n        \"\"\"\n        SSHConnection.__init__(self)\n        self._ready = ready\n\n\n    def serviceStarted(self):\n        \"\"\"\n        When the SSH I{connection} I{service} this object represents is ready\n        to be used, fire the C{connectionReady} L{Deferred} to publish that\n        event to some other interested party.\n\n        \"\"\"\n        self._ready.callback(self)\n        del self._ready\n\n\n\nclass _UserAuth(SSHUserAuthClient):\n    \"\"\"\n    L{_UserAuth} implements the client part of SSH user authentication in the\n    convenient way a user might expect if they are familiar with the\n    interactive I{ssh} command line client.\n\n    L{_UserAuth} supports key-based authentication, password-based\n    authentication, and delegating authentication to an agent.\n    \"\"\"\n    password = None\n    keys = None\n    agent = None\n\n    def getPublicKey(self):\n        \"\"\"\n        Retrieve the next public key object to offer to the server, possibly\n        delegating to an authentication agent if there is one.\n\n        @return: The public part of a key pair that could be used to\n            authenticate with the server, or L{None} if there are no more\n            public keys to try.\n        @rtype: L{twisted.conch.ssh.keys.Key} or L{None}\n        \"\"\"\n        if self.agent is not None:\n            return self.agent.getPublicKey()\n\n        if self.keys:\n            self.key = self.keys.pop(0)\n        else:\n            self.key = None\n        return self.key.public()\n\n\n    def signData(self, publicKey, signData):\n        \"\"\"\n        Extend the base signing behavior by using an SSH agent to sign the\n        data, if one is available.\n\n        @type publicKey: L{Key}\n        @type signData: L{str}\n        \"\"\"\n        if self.agent is not None:\n            return self.agent.signData(publicKey.blob(), signData)\n        else:\n            return SSHUserAuthClient.signData(self, publicKey, signData)\n\n\n    def getPrivateKey(self):\n        \"\"\"\n        Get the private part of a key pair to use for authentication.  The key\n        corresponds to the public part most recently returned from\n        C{getPublicKey}.\n\n        @return: A L{Deferred} which fires with the private key.\n        @rtype: L{Deferred}\n        \"\"\"\n        return succeed(self.key)\n\n\n    def getPassword(self):\n        \"\"\"\n        Get the password to use for authentication.\n\n        @return: A L{Deferred} which fires with the password, or L{None} if the\n            password was not specified.\n        \"\"\"\n        if self.password is None:\n            return\n        return succeed(self.password)\n\n\n    def ssh_USERAUTH_SUCCESS(self, packet):\n        \"\"\"\n        Handle user authentication success in the normal way, but also make a\n        note of the state change on the L{_CommandTransport}.\n        \"\"\"\n        self.transport._state = b'CHANNELLING'\n        return SSHUserAuthClient.ssh_USERAUTH_SUCCESS(self, packet)\n\n\n    def connectToAgent(self, endpoint):\n        \"\"\"\n        Set up a connection to the authentication agent and trigger its\n        initialization.\n\n        @param endpoint: An endpoint which can be used to connect to the\n            authentication agent.\n        @type endpoint: L{IStreamClientEndpoint} provider\n\n        @return: A L{Deferred} which fires when the agent connection is ready\n            for use.\n        \"\"\"\n        factory = Factory()\n        factory.protocol = SSHAgentClient\n        d = endpoint.connect(factory)\n        def connected(agent):\n            self.agent = agent\n            return agent.getPublicKeys()\n        d.addCallback(connected)\n        return d\n\n\n    def loseAgentConnection(self):\n        \"\"\"\n        Disconnect the agent.\n        \"\"\"\n        if self.agent is None:\n            return\n        self.agent.transport.loseConnection()\n\n\n\nclass _CommandTransport(SSHClientTransport):\n    \"\"\"\n    L{_CommandTransport} is an SSH client I{transport} which includes a host\n    key verification step before it will proceed to secure the connection.\n\n    L{_CommandTransport} also knows how to set up a connection to an\n    authentication agent if it is told where it can connect to one.\n\n    @ivar _userauth: The L{_UserAuth} instance which is in charge of the\n        overall authentication process or L{None} if the SSH connection has not\n        reach yet the C{user-auth} service.\n    @type _userauth: L{_UserAuth}\n    \"\"\"\n    # STARTING -> SECURING -> AUTHENTICATING -> CHANNELLING -> RUNNING\n    _state = b'STARTING'\n\n    _hostKeyFailure = None\n\n    _userauth = None\n\n\n    def __init__(self, creator):\n        \"\"\"\n        @param creator: The L{_NewConnectionHelper} that created this\n            connection.\n\n        @type creator: L{_NewConnectionHelper}.\n        \"\"\"\n        self.connectionReady = Deferred(\n            lambda d: self.transport.abortConnection())\n        # Clear the reference to that deferred to help the garbage collector\n        # and to signal to other parts of this implementation (in particular\n        # connectionLost) that it has already been fired and does not need to\n        # be fired again.\n        def readyFired(result):\n            self.connectionReady = None\n            return result\n        self.connectionReady.addBoth(readyFired)\n        self.creator = creator\n\n\n    def verifyHostKey(self, hostKey, fingerprint):\n        \"\"\"\n        Ask the L{KnownHostsFile} provider available on the factory which\n        created this protocol this protocol to verify the given host key.\n\n        @return: A L{Deferred} which fires with the result of\n            L{KnownHostsFile.verifyHostKey}.\n        \"\"\"\n        hostname = self.creator.hostname\n        ip = networkString(self.transport.getPeer().host)\n\n        self._state = b'SECURING'\n        d = self.creator.knownHosts.verifyHostKey(\n            self.creator.ui, hostname, ip, Key.fromString(hostKey))\n        d.addErrback(self._saveHostKeyFailure)\n        return d\n\n\n    def _saveHostKeyFailure(self, reason):\n        \"\"\"\n        When host key verification fails, record the reason for the failure in\n        order to fire a L{Deferred} with it later.\n\n        @param reason: The cause of the host key verification failure.\n        @type reason: L{Failure}\n\n        @return: C{reason}\n        @rtype: L{Failure}\n        \"\"\"\n        self._hostKeyFailure = reason\n        return reason\n\n\n    def connectionSecure(self):\n        \"\"\"\n        When the connection is secure, start the authentication process.\n        \"\"\"\n        self._state = b'AUTHENTICATING'\n\n        command = _ConnectionReady(self.connectionReady)\n\n        self._userauth = _UserAuth(self.creator.username, command)\n        self._userauth.password = self.creator.password\n        if self.creator.keys:\n            self._userauth.keys = list(self.creator.keys)\n\n        if self.creator.agentEndpoint is not None:\n            d = self._userauth.connectToAgent(self.creator.agentEndpoint)\n        else:\n            d = succeed(None)\n\n        def maybeGotAgent(ignored):\n            self.requestService(self._userauth)\n        d.addBoth(maybeGotAgent)\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        When the underlying connection to the SSH server is lost, if there were\n        any connection setup errors, propagate them. Also, clean up the\n        connection to the ssh agent if one was created.\n        \"\"\"\n        if self._userauth:\n            self._userauth.loseAgentConnection()\n\n        if self._state == b'RUNNING' or self.connectionReady is None:\n            return\n        if self._state == b'SECURING' and self._hostKeyFailure is not None:\n            reason = self._hostKeyFailure\n        elif self._state == b'AUTHENTICATING':\n            reason = Failure(\n                AuthenticationFailed(\"Connection lost while authenticating\"))\n        self.connectionReady.errback(reason)\n\n\n\n@implementer(IStreamClientEndpoint)\nclass SSHCommandClientEndpoint(object):\n    \"\"\"\n    L{SSHCommandClientEndpoint} exposes the command-executing functionality of\n    SSH servers.\n\n    L{SSHCommandClientEndpoint} can set up a new SSH connection, authenticate\n    it in any one of a number of different ways (keys, passwords, agents),\n    launch a command over that connection and then associate its input and\n    output with a protocol.\n\n    It can also re-use an existing, already-authenticated SSH connection\n    (perhaps one which already has some SSH channels being used for other\n    purposes).  In this case it creates a new SSH channel to use to execute the\n    command.  Notably this means it supports multiplexing several different\n    command invocations over a single SSH connection.\n    \"\"\"\n\n    def __init__(self, creator, command):\n        \"\"\"\n        @param creator: An L{_ISSHConnectionCreator} provider which will be\n            used to set up the SSH connection which will be used to run a\n            command.\n        @type creator: L{_ISSHConnectionCreator} provider\n\n        @param command: The command line to execute on the SSH server.  This\n            byte string is interpreted by a shell on the SSH server, so it may\n            have a value like C{\"ls /\"}.  Take care when trying to run a\n            command like C{\"/Volumes/My Stuff/a-program\"} - spaces (and other\n            special bytes) may require escaping.\n        @type command: L{bytes}\n\n        \"\"\"\n        self._creator = creator\n        self._command = command\n\n\n    @classmethod\n    def newConnection(cls, reactor, command, username, hostname, port=None,\n                      keys=None, password=None, agentEndpoint=None,\n                      knownHosts=None, ui=None):\n        \"\"\"\n        Create and return a new endpoint which will try to create a new\n        connection to an SSH server and run a command over it.  It will also\n        close the connection if there are problems leading up to the command\n        being executed, after the command finishes, or if the connection\n        L{Deferred} is cancelled.\n\n        @param reactor: The reactor to use to establish the connection.\n        @type reactor: L{IReactorTCP} provider\n\n        @param command: See L{__init__}'s C{command} argument.\n\n        @param username: The username with which to authenticate to the SSH\n            server.\n        @type username: L{bytes}\n\n        @param hostname: The hostname of the SSH server.\n        @type hostname: L{bytes}\n\n        @param port: The port number of the SSH server.  By default, the\n            standard SSH port number is used.\n        @type port: L{int}\n\n        @param keys: Private keys with which to authenticate to the SSH server,\n            if key authentication is to be attempted (otherwise L{None}).\n        @type keys: L{list} of L{Key}\n\n        @param password: The password with which to authenticate to the SSH\n            server, if password authentication is to be attempted (otherwise\n            L{None}).\n        @type password: L{bytes} or L{None}\n\n        @param agentEndpoint: An L{IStreamClientEndpoint} provider which may be\n            used to connect to an SSH agent, if one is to be used to help with\n            authentication.\n        @type agentEndpoint: L{IStreamClientEndpoint} provider\n\n        @param knownHosts: The currently known host keys, used to check the\n            host key presented by the server we actually connect to.\n        @type knownHosts: L{KnownHostsFile}\n\n        @param ui: An object for interacting with users to make decisions about\n            whether to accept the server host keys.  If L{None}, a L{ConsoleUI}\n            connected to /dev/tty will be used; if /dev/tty is unavailable, an\n            object which answers C{b\"no\"} to all prompts will be used.\n        @type ui: L{None} or L{ConsoleUI}\n\n        @return: A new instance of C{cls} (probably\n            L{SSHCommandClientEndpoint}).\n        \"\"\"\n        helper = _NewConnectionHelper(\n            reactor, hostname, port, command, username, keys, password,\n            agentEndpoint, knownHosts, ui)\n        return cls(helper, command)\n\n\n    @classmethod\n    def existingConnection(cls, connection, command):\n        \"\"\"\n        Create and return a new endpoint which will try to open a new channel\n        on an existing SSH connection and run a command over it.  It will\n        B{not} close the connection if there is a problem executing the command\n        or after the command finishes.\n\n        @param connection: An existing connection to an SSH server.\n        @type connection: L{SSHConnection}\n\n        @param command: See L{SSHCommandClientEndpoint.newConnection}'s\n            C{command} parameter.\n        @type command: L{bytes}\n\n        @return: A new instance of C{cls} (probably\n            L{SSHCommandClientEndpoint}).\n        \"\"\"\n        helper = _ExistingConnectionHelper(connection)\n        return cls(helper, command)\n\n\n    def connect(self, protocolFactory):\n        \"\"\"\n        Set up an SSH connection, use a channel from that connection to launch\n        a command, and hook the stdin and stdout of that command up as a\n        transport for a protocol created by the given factory.\n\n        @param protocolFactory: A L{Factory} to use to create the protocol\n            which will be connected to the stdin and stdout of the command on\n            the SSH server.\n\n        @return: A L{Deferred} which will fire with an error if the connection\n            cannot be set up for any reason or with the protocol instance\n            created by C{protocolFactory} once it has been connected to the\n            command.\n        \"\"\"\n        d = self._creator.secureConnection()\n        d.addCallback(self._executeCommand, protocolFactory)\n        return d\n\n\n    def _executeCommand(self, connection, protocolFactory):\n        \"\"\"\n        Given a secured SSH connection, try to execute a command in a new\n        channel created on it and associate the result with a protocol from the\n        given factory.\n\n        @param connection: See L{SSHCommandClientEndpoint.existingConnection}'s\n            C{connection} parameter.\n\n        @param protocolFactory: See L{SSHCommandClientEndpoint.connect}'s\n            C{protocolFactory} parameter.\n\n        @return: See L{SSHCommandClientEndpoint.connect}'s return value.\n        \"\"\"\n        commandConnected = Deferred()\n\n        def disconnectOnFailure(passthrough):\n            # Close the connection immediately in case of cancellation, since\n            # that implies user wants it gone immediately (e.g. a timeout):\n            immediate = passthrough.check(CancelledError)\n            self._creator.cleanupConnection(connection, immediate)\n            return passthrough\n        commandConnected.addErrback(disconnectOnFailure)\n\n        channel = _CommandChannel(\n            self._creator, self._command, protocolFactory, commandConnected)\n        connection.openChannel(channel)\n        return commandConnected\n\n\n\nclass _ReadFile(object):\n    \"\"\"\n    A weakly file-like object which can be used with L{KnownHostsFile} to\n    respond in the negative to all prompts for decisions.\n    \"\"\"\n    def __init__(self, contents):\n        \"\"\"\n        @param contents: L{bytes} which will be returned from every C{readline}\n            call.\n        \"\"\"\n        self._contents = contents\n\n\n    def write(self, data):\n        \"\"\"\n        No-op.\n\n        @param data: ignored\n        \"\"\"\n\n\n    def readline(self, count=-1):\n        \"\"\"\n        Always give back the byte string that this L{_ReadFile} was initialized\n        with.\n\n        @param count: ignored\n\n        @return: A fixed byte-string.\n        @rtype: L{bytes}\n        \"\"\"\n        return self._contents\n\n\n    def close(self):\n        \"\"\"\n        No-op.\n        \"\"\"\n\n\n\n@implementer(_ISSHConnectionCreator)\nclass _NewConnectionHelper(object):\n    \"\"\"\n    L{_NewConnectionHelper} implements L{_ISSHConnectionCreator} by\n    establishing a brand new SSH connection, securing it, and authenticating.\n    \"\"\"\n    _KNOWN_HOSTS = _KNOWN_HOSTS\n    port = 22\n\n    def __init__(self, reactor, hostname, port, command, username, keys,\n                 password, agentEndpoint, knownHosts, ui,\n                 tty=FilePath(b\"/dev/tty\")):\n        \"\"\"\n        @param tty: The path of the tty device to use in case C{ui} is L{None}.\n        @type tty: L{FilePath}\n\n        @see: L{SSHCommandClientEndpoint.newConnection}\n        \"\"\"\n        self.reactor = reactor\n        self.hostname = hostname\n        if port is not None:\n            self.port = port\n        self.command = command\n        self.username = username\n        self.keys = keys\n        self.password = password\n        self.agentEndpoint = agentEndpoint\n        if knownHosts is None:\n            knownHosts = self._knownHosts()\n        self.knownHosts = knownHosts\n\n        if ui is None:\n            ui = ConsoleUI(self._opener)\n        self.ui = ui\n        self.tty = tty\n\n\n    def _opener(self):\n        \"\"\"\n        Open the tty if possible, otherwise give back a file-like object from\n        which C{b\"no\"} can be read.\n\n        For use as the opener argument to L{ConsoleUI}.\n        \"\"\"\n        try:\n            return self.tty.open(\"rb+\")\n        except:\n            # Give back a file-like object from which can be read a byte string\n            # that KnownHostsFile recognizes as rejecting some option (b\"no\").\n            return _ReadFile(b\"no\")\n\n\n    @classmethod\n    def _knownHosts(cls):\n        \"\"\"\n\n        @return: A L{KnownHostsFile} instance pointed at the user's personal\n            I{known hosts} file.\n        @type: L{KnownHostsFile}\n        \"\"\"\n        return KnownHostsFile.fromPath(FilePath(expanduser(cls._KNOWN_HOSTS)))\n\n\n    def secureConnection(self):\n        \"\"\"\n        Create and return a new SSH connection which has been secured and on\n        which authentication has already happened.\n\n        @return: A L{Deferred} which fires with the ready-to-use connection or\n            with a failure if something prevents the connection from being\n            setup, secured, or authenticated.\n        \"\"\"\n        protocol = _CommandTransport(self)\n        ready = protocol.connectionReady\n\n        sshClient = TCP4ClientEndpoint(\n            self.reactor, nativeString(self.hostname), self.port)\n\n        d = connectProtocol(sshClient, protocol)\n        d.addCallback(lambda ignored: ready)\n        return d\n\n\n    def cleanupConnection(self, connection, immediate):\n        \"\"\"\n        Clean up the connection by closing it.  The command running on the\n        endpoint has ended so the connection is no longer needed.\n\n        @param connection: The L{SSHConnection} to close.\n        @type connection: L{SSHConnection}\n\n        @param immediate: Whether to close connection immediately.\n        @type immediate: L{bool}.\n        \"\"\"\n        if immediate:\n            # We're assuming the underlying connection is an ITCPTransport,\n            # which is what the current implementation is restricted to:\n            connection.transport.transport.abortConnection()\n        else:\n            connection.transport.loseConnection()\n\n\n\n@implementer(_ISSHConnectionCreator)\nclass _ExistingConnectionHelper(object):\n    \"\"\"\n    L{_ExistingConnectionHelper} implements L{_ISSHConnectionCreator} by\n    handing out an existing SSH connection which is supplied to its\n    initializer.\n    \"\"\"\n\n    def __init__(self, connection):\n        \"\"\"\n        @param connection: See L{SSHCommandClientEndpoint.existingConnection}'s\n            C{connection} parameter.\n        \"\"\"\n        self.connection = connection\n\n\n    def secureConnection(self):\n        \"\"\"\n\n        @return: A L{Deferred} that fires synchronously with the\n            already-established connection object.\n        \"\"\"\n        return succeed(self.connection)\n\n\n    def cleanupConnection(self, connection, immediate):\n        \"\"\"\n        Do not do any cleanup on the connection.  Leave that responsibility to\n        whatever code created it in the first place.\n\n        @param connection: The L{SSHConnection} which will not be modified in\n            any way.\n        @type connection: L{SSHConnection}\n\n        @param immediate: An argument which will be ignored.\n        @type immediate: L{bool}.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/error.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAn error to represent bad things happening in Conch.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom twisted.cred.error import UnauthorizedLogin\n\n\nclass ConchError(Exception):\n    def __init__(self, value, data = None):\n        Exception.__init__(self, value, data)\n        self.value = value\n        self.data = data\n\n\n\nclass NotEnoughAuthentication(Exception):\n    \"\"\"\n    This is thrown if the authentication is valid, but is not enough to\n    successfully verify the user.  i.e. don't retry this type of\n    authentication, try another one.\n    \"\"\"\n\n\n\nclass ValidPublicKey(UnauthorizedLogin):\n    \"\"\"\n    Raised by public key checkers when they receive public key credentials\n    that don't contain a signature at all, but are valid in every other way.\n    (e.g. the public key matches one in the user's authorized_keys file).\n\n    Protocol code (eg\n    L{SSHUserAuthServer<twisted.conch.ssh.userauth.SSHUserAuthServer>}) which\n    attempts to log in using\n    L{ISSHPrivateKey<twisted.cred.credentials.ISSHPrivateKey>} credentials\n    should be prepared to handle a failure of this type by telling the user to\n    re-authenticate using the same key and to include a signature with the new\n    attempt.\n\n    See U{http://www.ietf.org/rfc/rfc4252.txt} section 7 for more details.\n    \"\"\"\n\n\n\nclass IgnoreAuthentication(Exception):\n    \"\"\"\n    This is thrown to let the UserAuthServer know it doesn't need to handle the\n    authentication anymore.\n    \"\"\"\n\n\n\nclass MissingKeyStoreError(Exception):\n    \"\"\"\n    Raised if an SSHAgentServer starts receiving data without its factory\n    providing a keys dict on which to read/write key data.\n    \"\"\"\n\n\n\nclass UserRejectedKey(Exception):\n    \"\"\"\n    The user interactively rejected a key.\n    \"\"\"\n\n\n\nclass InvalidEntry(Exception):\n    \"\"\"\n    An entry in a known_hosts file could not be interpreted as a valid entry.\n    \"\"\"\n\n\n\nclass HostKeyChanged(Exception):\n    \"\"\"\n    The host key of a remote host has changed.\n\n    @ivar offendingEntry: The entry which contains the persistent host key that\n    disagrees with the given host key.\n\n    @type offendingEntry: L{twisted.conch.interfaces.IKnownHostEntry}\n\n    @ivar path: a reference to the known_hosts file that the offending entry\n    was loaded from\n\n    @type path: L{twisted.python.filepath.FilePath}\n\n    @ivar lineno: The line number of the offending entry in the given path.\n\n    @type lineno: L{int}\n    \"\"\"\n    def __init__(self, offendingEntry, path, lineno):\n        Exception.__init__(self)\n        self.offendingEntry = offendingEntry\n        self.path = path\n        self.lineno = lineno\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/insults/__init__.py",
    "content": "\"\"\"\nInsults: a replacement for Curses/S-Lang.\n\nVery basic at the moment.\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/insults/helper.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_helper -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nPartial in-memory terminal emulator\n\n@author: Jp Calderone\n\"\"\"\n\nfrom __future__ import print_function\n\nimport re, string\n\nfrom zope.interface import implementer\n\nfrom incremental import Version\n\nfrom twisted.internet import defer, protocol, reactor\nfrom twisted.python import log, _textattributes\nfrom twisted.python.compat import iterbytes\nfrom twisted.python.deprecate import deprecated, deprecatedModuleAttribute\nfrom twisted.conch.insults import insults\n\nFOREGROUND = 30\nBACKGROUND = 40\nBLACK, RED, GREEN, YELLOW, BLUE, MAGENTA, CYAN, WHITE, N_COLORS = range(9)\n\n\n\nclass _FormattingState(_textattributes._FormattingStateMixin):\n    \"\"\"\n    Represents the formatting state/attributes of a single character.\n\n    Character set, intensity, underlinedness, blinkitude, video\n    reversal, as well as foreground and background colors made up a\n    character's attributes.\n    \"\"\"\n    compareAttributes = (\n        'charset', 'bold', 'underline', 'blink', 'reverseVideo', 'foreground',\n        'background', '_subtracting')\n\n\n    def __init__(self, charset=insults.G0, bold=False, underline=False,\n                 blink=False, reverseVideo=False, foreground=WHITE,\n                 background=BLACK, _subtracting=False):\n        self.charset = charset\n        self.bold = bold\n        self.underline = underline\n        self.blink = blink\n        self.reverseVideo = reverseVideo\n        self.foreground = foreground\n        self.background = background\n        self._subtracting = _subtracting\n\n\n    @deprecated(Version('Twisted', 13, 1, 0))\n    def wantOne(self, **kw):\n        \"\"\"\n        Add a character attribute to a copy of this formatting state.\n\n        @param **kw: An optional attribute name and value can be provided with\n            a keyword argument.\n\n        @return: A formatting state instance with the new attribute.\n\n        @see: L{DefaultFormattingState._withAttribute}.\n        \"\"\"\n        k, v = kw.popitem()\n        return self._withAttribute(k, v)\n\n\n    def toVT102(self):\n        # Spit out a vt102 control sequence that will set up\n        # all the attributes set here.  Except charset.\n        attrs = []\n        if self._subtracting:\n            attrs.append(0)\n        if self.bold:\n            attrs.append(insults.BOLD)\n        if self.underline:\n            attrs.append(insults.UNDERLINE)\n        if self.blink:\n            attrs.append(insults.BLINK)\n        if self.reverseVideo:\n            attrs.append(insults.REVERSE_VIDEO)\n        if self.foreground != WHITE:\n            attrs.append(FOREGROUND + self.foreground)\n        if self.background != BLACK:\n            attrs.append(BACKGROUND + self.background)\n        if attrs:\n            return '\\x1b[' + ';'.join(map(str, attrs)) + 'm'\n        return ''\n\nCharacterAttribute = _FormattingState\n\ndeprecatedModuleAttribute(\n    Version('Twisted', 13, 1, 0),\n    'Use twisted.conch.insults.text.assembleFormattedText instead.',\n    'twisted.conch.insults.helper',\n    'CharacterAttribute')\n\n\n\n# XXX - need to support scroll regions and scroll history\n@implementer(insults.ITerminalTransport)\nclass TerminalBuffer(protocol.Protocol):\n    \"\"\"\n    An in-memory terminal emulator.\n    \"\"\"\n    for keyID in (b'UP_ARROW', b'DOWN_ARROW', b'RIGHT_ARROW', b'LEFT_ARROW',\n                  b'HOME', b'INSERT', b'DELETE', b'END', b'PGUP', b'PGDN',\n                  b'F1', b'F2', b'F3', b'F4', b'F5', b'F6', b'F7', b'F8', b'F9',\n                  b'F10', b'F11', b'F12'):\n        execBytes = keyID + b\" = object()\"\n        execStr = execBytes.decode(\"ascii\")\n        exec(execStr)\n\n    TAB = b'\\t'\n    BACKSPACE = b'\\x7f'\n\n    width = 80\n    height = 24\n\n    fill = b' '\n    void = object()\n\n    def getCharacter(self, x, y):\n        return self.lines[y][x]\n\n\n    def connectionMade(self):\n        self.reset()\n\n\n    def write(self, data):\n        \"\"\"\n        Add the given printable bytes to the terminal.\n\n        Line feeds in L{bytes} will be replaced with carriage return / line\n        feed pairs.\n        \"\"\"\n        for b in iterbytes(data.replace(b'\\n', b'\\r\\n')):\n            self.insertAtCursor(b)\n\n\n    def _currentFormattingState(self):\n        return _FormattingState(self.activeCharset, **self.graphicRendition)\n\n\n    def insertAtCursor(self, b):\n        \"\"\"\n        Add one byte to the terminal at the cursor and make consequent state\n        updates.\n\n        If b is a carriage return, move the cursor to the beginning of the\n        current row.\n\n        If b is a line feed, move the cursor to the next row or scroll down if\n        the cursor is already in the last row.\n\n        Otherwise, if b is printable, put it at the cursor position (inserting\n        or overwriting as dictated by the current mode) and move the cursor.\n        \"\"\"\n        if b == b'\\r':\n            self.x = 0\n        elif b == b'\\n':\n            self._scrollDown()\n        elif b in string.printable.encode(\"ascii\"):\n            if self.x >= self.width:\n                self.nextLine()\n            ch = (b, self._currentFormattingState())\n            if self.modes.get(insults.modes.IRM):\n                self.lines[self.y][self.x:self.x] = [ch]\n                self.lines[self.y].pop()\n            else:\n                self.lines[self.y][self.x] = ch\n            self.x += 1\n\n\n    def _emptyLine(self, width):\n        return [(self.void, self._currentFormattingState())\n                for i in range(width)]\n\n\n    def _scrollDown(self):\n        self.y += 1\n        if self.y >= self.height:\n            self.y -= 1\n            del self.lines[0]\n            self.lines.append(self._emptyLine(self.width))\n\n\n    def _scrollUp(self):\n        self.y -= 1\n        if self.y < 0:\n            self.y = 0\n            del self.lines[-1]\n            self.lines.insert(0, self._emptyLine(self.width))\n\n\n    def cursorUp(self, n=1):\n        self.y = max(0, self.y - n)\n\n\n    def cursorDown(self, n=1):\n        self.y = min(self.height - 1, self.y + n)\n\n\n    def cursorBackward(self, n=1):\n        self.x = max(0, self.x - n)\n\n\n    def cursorForward(self, n=1):\n        self.x = min(self.width, self.x + n)\n\n\n    def cursorPosition(self, column, line):\n        self.x = column\n        self.y = line\n\n\n    def cursorHome(self):\n        self.x = self.home.x\n        self.y = self.home.y\n\n\n    def index(self):\n        self._scrollDown()\n\n\n    def reverseIndex(self):\n        self._scrollUp()\n\n\n    def nextLine(self):\n        \"\"\"\n        Update the cursor position attributes and scroll down if appropriate.\n        \"\"\"\n        self.x = 0\n        self._scrollDown()\n\n\n    def saveCursor(self):\n        self._savedCursor = (self.x, self.y)\n\n\n    def restoreCursor(self):\n        self.x, self.y = self._savedCursor\n        del self._savedCursor\n\n\n    def setModes(self, modes):\n        for m in modes:\n            self.modes[m] = True\n\n\n    def resetModes(self, modes):\n        for m in modes:\n            try:\n                del self.modes[m]\n            except KeyError:\n                pass\n\n\n    def setPrivateModes(self, modes):\n        \"\"\"\n        Enable the given modes.\n\n        Track which modes have been enabled so that the implementations of\n        other L{insults.ITerminalTransport} methods can be properly implemented\n        to respect these settings.\n\n        @see: L{resetPrivateModes}\n        @see: L{insults.ITerminalTransport.setPrivateModes}\n        \"\"\"\n        for m in modes:\n            self.privateModes[m] = True\n\n\n    def resetPrivateModes(self, modes):\n        \"\"\"\n        Disable the given modes.\n\n        @see: L{setPrivateModes}\n        @see: L{insults.ITerminalTransport.resetPrivateModes}\n        \"\"\"\n        for m in modes:\n            try:\n                del self.privateModes[m]\n            except KeyError:\n                pass\n\n\n    def applicationKeypadMode(self):\n        self.keypadMode = 'app'\n\n\n    def numericKeypadMode(self):\n        self.keypadMode = 'num'\n\n\n    def selectCharacterSet(self, charSet, which):\n        self.charsets[which] = charSet\n\n\n    def shiftIn(self):\n        self.activeCharset = insults.G0\n\n\n    def shiftOut(self):\n        self.activeCharset = insults.G1\n\n\n    def singleShift2(self):\n        oldActiveCharset = self.activeCharset\n        self.activeCharset = insults.G2\n        f = self.insertAtCursor\n        def insertAtCursor(b):\n            f(b)\n            del self.insertAtCursor\n            self.activeCharset = oldActiveCharset\n        self.insertAtCursor = insertAtCursor\n\n\n    def singleShift3(self):\n        oldActiveCharset = self.activeCharset\n        self.activeCharset = insults.G3\n        f = self.insertAtCursor\n        def insertAtCursor(b):\n            f(b)\n            del self.insertAtCursor\n            self.activeCharset = oldActiveCharset\n        self.insertAtCursor = insertAtCursor\n\n\n    def selectGraphicRendition(self, *attributes):\n        for a in attributes:\n            if a == insults.NORMAL:\n                self.graphicRendition = {\n                    'bold': False,\n                    'underline': False,\n                    'blink': False,\n                    'reverseVideo': False,\n                    'foreground': WHITE,\n                    'background': BLACK}\n            elif a == insults.BOLD:\n                self.graphicRendition['bold'] = True\n            elif a == insults.UNDERLINE:\n                self.graphicRendition['underline'] = True\n            elif a == insults.BLINK:\n                self.graphicRendition['blink'] = True\n            elif a == insults.REVERSE_VIDEO:\n                self.graphicRendition['reverseVideo'] = True\n            else:\n                try:\n                    v = int(a)\n                except ValueError:\n                    log.msg(\"Unknown graphic rendition attribute: \" + repr(a))\n                else:\n                    if FOREGROUND <= v <= FOREGROUND + N_COLORS:\n                        self.graphicRendition['foreground'] = v - FOREGROUND\n                    elif BACKGROUND <= v <= BACKGROUND + N_COLORS:\n                        self.graphicRendition['background'] = v - BACKGROUND\n                    else:\n                        log.msg(\"Unknown graphic rendition attribute: \" + repr(a))\n\n\n    def eraseLine(self):\n        self.lines[self.y] = self._emptyLine(self.width)\n\n\n    def eraseToLineEnd(self):\n        width = self.width - self.x\n        self.lines[self.y][self.x:] = self._emptyLine(width)\n\n\n    def eraseToLineBeginning(self):\n        self.lines[self.y][:self.x + 1] = self._emptyLine(self.x + 1)\n\n\n    def eraseDisplay(self):\n        self.lines = [self._emptyLine(self.width) for i in range(self.height)]\n\n\n    def eraseToDisplayEnd(self):\n        self.eraseToLineEnd()\n        height = self.height - self.y - 1\n        self.lines[self.y + 1:] = [self._emptyLine(self.width) for i in range(height)]\n\n\n    def eraseToDisplayBeginning(self):\n        self.eraseToLineBeginning()\n        self.lines[:self.y] = [self._emptyLine(self.width) for i in range(self.y)]\n\n\n    def deleteCharacter(self, n=1):\n        del self.lines[self.y][self.x:self.x+n]\n        self.lines[self.y].extend(self._emptyLine(min(self.width - self.x, n)))\n\n\n    def insertLine(self, n=1):\n        self.lines[self.y:self.y] = [self._emptyLine(self.width) for i in range(n)]\n        del self.lines[self.height:]\n\n\n    def deleteLine(self, n=1):\n        del self.lines[self.y:self.y+n]\n        self.lines.extend([self._emptyLine(self.width) for i in range(n)])\n\n\n    def reportCursorPosition(self):\n        return (self.x, self.y)\n\n\n    def reset(self):\n        self.home = insults.Vector(0, 0)\n        self.x = self.y = 0\n        self.modes = {}\n        self.privateModes = {}\n        self.setPrivateModes([insults.privateModes.AUTO_WRAP,\n                              insults.privateModes.CURSOR_MODE])\n        self.numericKeypad = 'app'\n        self.activeCharset = insults.G0\n        self.graphicRendition = {\n            'bold': False,\n            'underline': False,\n            'blink': False,\n            'reverseVideo': False,\n            'foreground': WHITE,\n            'background': BLACK}\n        self.charsets = {\n            insults.G0: insults.CS_US,\n            insults.G1: insults.CS_US,\n            insults.G2: insults.CS_ALTERNATE,\n            insults.G3: insults.CS_ALTERNATE_SPECIAL}\n        self.eraseDisplay()\n\n\n    def unhandledControlSequence(self, buf):\n        print('Could not handle', repr(buf))\n\n\n    def __bytes__(self):\n        lines = []\n        for L in self.lines:\n            buf = []\n            length = 0\n            for (ch, attr) in L:\n                if ch is not self.void:\n                    buf.append(ch)\n                    length = len(buf)\n                else:\n                    buf.append(self.fill)\n            lines.append(b''.join(buf[:length]))\n        return b'\\n'.join(lines)\n\n\n\nclass ExpectationTimeout(Exception):\n    pass\n\n\n\nclass ExpectableBuffer(TerminalBuffer):\n    _mark = 0\n\n    def connectionMade(self):\n        TerminalBuffer.connectionMade(self)\n        self._expecting = []\n\n\n    def write(self, data):\n        TerminalBuffer.write(self, data)\n        self._checkExpected()\n\n\n    def cursorHome(self):\n        TerminalBuffer.cursorHome(self)\n        self._mark = 0\n\n\n    def _timeoutExpected(self, d):\n        d.errback(ExpectationTimeout())\n        self._checkExpected()\n\n\n    def _checkExpected(self):\n        s = self.__bytes__()[self._mark:]\n        while self._expecting:\n            expr, timer, deferred = self._expecting[0]\n            if timer and not timer.active():\n                del self._expecting[0]\n                continue\n            for match in expr.finditer(s):\n                if timer:\n                    timer.cancel()\n                del self._expecting[0]\n                self._mark += match.end()\n                s = s[match.end():]\n                deferred.callback(match)\n                break\n            else:\n                return\n\n\n    def expect(self, expression, timeout=None, scheduler=reactor):\n        d = defer.Deferred()\n        timer = None\n        if timeout:\n            timer = scheduler.callLater(timeout, self._timeoutExpected, d)\n        self._expecting.append((re.compile(expression), timer, d))\n        self._checkExpected()\n        return d\n\n__all__ = [\n    'CharacterAttribute',  'TerminalBuffer', 'ExpectableBuffer']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/insults/insults.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_insults -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nVT102 and VT220 terminal manipulation.\n\n@author: Jp Calderone\n\"\"\"\n\nfrom zope.interface import implementer, Interface\n\nfrom twisted.internet import protocol, defer, interfaces as iinternet\nfrom twisted.python.compat import intToBytes, iterbytes, networkString\n\n\n\nclass ITerminalProtocol(Interface):\n    def makeConnection(transport):\n        \"\"\"\n        Called with an L{ITerminalTransport} when a connection is established.\n        \"\"\"\n\n    def keystrokeReceived(keyID, modifier):\n        \"\"\"\n        A keystroke was received.\n\n        Each keystroke corresponds to one invocation of this method.\n        keyID is a string identifier for that key.  Printable characters\n        are represented by themselves.  Control keys, such as arrows and\n        function keys, are represented with symbolic constants on\n        L{ServerProtocol}.\n        \"\"\"\n\n    def terminalSize(width, height):\n        \"\"\"\n        Called to indicate the size of the terminal.\n\n        A terminal of 80x24 should be assumed if this method is not\n        called.  This method might not be called for real terminals.\n        \"\"\"\n\n    def unhandledControlSequence(seq):\n        \"\"\"\n        Called when an unsupported control sequence is received.\n\n        @type seq: L{str}\n        @param seq: The whole control sequence which could not be interpreted.\n        \"\"\"\n\n    def connectionLost(reason):\n        \"\"\"\n        Called when the connection has been lost.\n\n        reason is a Failure describing why.\n        \"\"\"\n\n\n\n@implementer(ITerminalProtocol)\nclass TerminalProtocol(object):\n    def makeConnection(self, terminal):\n        # assert ITerminalTransport.providedBy(transport), \"TerminalProtocol.makeConnection must be passed an ITerminalTransport implementor\"\n        self.terminal = terminal\n        self.connectionMade()\n\n\n    def connectionMade(self):\n        \"\"\"\n        Called after a connection has been established.\n        \"\"\"\n\n\n    def keystrokeReceived(self, keyID, modifier):\n        pass\n\n\n    def terminalSize(self, width, height):\n        pass\n\n\n    def unhandledControlSequence(self, seq):\n        pass\n\n\n    def connectionLost(self, reason):\n        pass\n\n\n\nclass ITerminalTransport(iinternet.ITransport):\n    def cursorUp(n=1):\n        \"\"\"\n        Move the cursor up n lines.\n        \"\"\"\n\n\n    def cursorDown(n=1):\n        \"\"\"\n        Move the cursor down n lines.\n        \"\"\"\n\n\n    def cursorForward(n=1):\n        \"\"\"\n        Move the cursor right n columns.\n        \"\"\"\n\n\n    def cursorBackward(n=1):\n        \"\"\"\n        Move the cursor left n columns.\n        \"\"\"\n\n\n    def cursorPosition(column, line):\n        \"\"\"\n        Move the cursor to the given line and column.\n        \"\"\"\n\n\n    def cursorHome():\n        \"\"\"\n        Move the cursor home.\n        \"\"\"\n\n\n    def index():\n        \"\"\"\n        Move the cursor down one line, performing scrolling if necessary.\n        \"\"\"\n\n\n    def reverseIndex():\n        \"\"\"\n        Move the cursor up one line, performing scrolling if necessary.\n        \"\"\"\n\n\n    def nextLine():\n        \"\"\"\n        Move the cursor to the first position on the next line, performing scrolling if necessary.\n        \"\"\"\n\n\n    def saveCursor():\n        \"\"\"\n        Save the cursor position, character attribute, character set, and origin mode selection.\n        \"\"\"\n\n\n    def restoreCursor():\n        \"\"\"\n        Restore the previously saved cursor position, character attribute, character set, and origin mode selection.\n\n        If no cursor state was previously saved, move the cursor to the home position.\n        \"\"\"\n\n\n    def setModes(modes):\n        \"\"\"\n        Set the given modes on the terminal.\n        \"\"\"\n\n    def resetModes(mode):\n        \"\"\"\n        Reset the given modes on the terminal.\n        \"\"\"\n\n\n    def setPrivateModes(modes):\n        \"\"\"\n        Set the given DEC private modes on the terminal.\n        \"\"\"\n\n\n    def resetPrivateModes(modes):\n        \"\"\"\n        Reset the given DEC private modes on the terminal.\n        \"\"\"\n\n\n    def applicationKeypadMode():\n        \"\"\"\n        Cause keypad to generate control functions.\n\n        Cursor key mode selects the type of characters generated by cursor keys.\n        \"\"\"\n\n\n    def numericKeypadMode():\n        \"\"\"\n        Cause keypad to generate normal characters.\n        \"\"\"\n\n\n    def selectCharacterSet(charSet, which):\n        \"\"\"\n        Select a character set.\n\n        charSet should be one of CS_US, CS_UK, CS_DRAWING, CS_ALTERNATE, or\n        CS_ALTERNATE_SPECIAL.\n\n        which should be one of G0 or G1.\n        \"\"\"\n\n\n    def shiftIn():\n        \"\"\"\n        Activate the G0 character set.\n        \"\"\"\n\n\n    def shiftOut():\n        \"\"\"\n        Activate the G1 character set.\n        \"\"\"\n\n\n    def singleShift2():\n        \"\"\"\n        Shift to the G2 character set for a single character.\n        \"\"\"\n\n\n    def singleShift3():\n        \"\"\"\n        Shift to the G3 character set for a single character.\n        \"\"\"\n\n\n    def selectGraphicRendition(*attributes):\n        \"\"\"\n        Enabled one or more character attributes.\n\n        Arguments should be one or more of UNDERLINE, REVERSE_VIDEO, BLINK, or BOLD.\n        NORMAL may also be specified to disable all character attributes.\n        \"\"\"\n\n\n    def horizontalTabulationSet():\n        \"\"\"\n        Set a tab stop at the current cursor position.\n        \"\"\"\n\n\n    def tabulationClear():\n        \"\"\"\n        Clear the tab stop at the current cursor position.\n        \"\"\"\n\n\n    def tabulationClearAll():\n        \"\"\"\n        Clear all tab stops.\n        \"\"\"\n\n\n    def doubleHeightLine(top=True):\n        \"\"\"\n        Make the current line the top or bottom half of a double-height, double-width line.\n\n        If top is True, the current line is the top half.  Otherwise, it is the bottom half.\n        \"\"\"\n\n\n    def singleWidthLine():\n        \"\"\"\n        Make the current line a single-width, single-height line.\n        \"\"\"\n\n\n    def doubleWidthLine():\n        \"\"\"\n        Make the current line a double-width line.\n        \"\"\"\n\n\n    def eraseToLineEnd():\n        \"\"\"\n        Erase from the cursor to the end of line, including cursor position.\n        \"\"\"\n\n\n    def eraseToLineBeginning():\n        \"\"\"\n        Erase from the cursor to the beginning of the line, including the cursor position.\n        \"\"\"\n\n\n    def eraseLine():\n        \"\"\"\n        Erase the entire cursor line.\n        \"\"\"\n\n\n    def eraseToDisplayEnd():\n        \"\"\"\n        Erase from the cursor to the end of the display, including the cursor position.\n        \"\"\"\n\n\n    def eraseToDisplayBeginning():\n        \"\"\"\n        Erase from the cursor to the beginning of the display, including the cursor position.\n        \"\"\"\n\n\n    def eraseDisplay():\n        \"\"\"\n        Erase the entire display.\n        \"\"\"\n\n\n    def deleteCharacter(n=1):\n        \"\"\"\n        Delete n characters starting at the cursor position.\n\n        Characters to the right of deleted characters are shifted to the left.\n        \"\"\"\n\n\n    def insertLine(n=1):\n        \"\"\"\n        Insert n lines at the cursor position.\n\n        Lines below the cursor are shifted down.  Lines moved past the bottom margin are lost.\n        This command is ignored when the cursor is outside the scroll region.\n        \"\"\"\n\n\n    def deleteLine(n=1):\n        \"\"\"\n        Delete n lines starting at the cursor position.\n\n        Lines below the cursor are shifted up.  This command is ignored when the cursor is outside\n        the scroll region.\n        \"\"\"\n\n\n    def reportCursorPosition():\n        \"\"\"\n        Return a Deferred that fires with a two-tuple of (x, y) indicating the cursor position.\n        \"\"\"\n\n\n    def reset():\n        \"\"\"\n        Reset the terminal to its initial state.\n        \"\"\"\n\n\n    def unhandledControlSequence(seq):\n        \"\"\"\n        Called when an unsupported control sequence is received.\n\n        @type seq: L{str}\n        @param seq: The whole control sequence which could not be interpreted.\n        \"\"\"\n\n\nCSI = b'\\x1b'\nCST = {b'~': b'tilde'}\n\nclass modes:\n    \"\"\"\n    ECMA 48 standardized modes\n    \"\"\"\n\n    # BREAKS YOPUR KEYBOARD MOFO\n    KEYBOARD_ACTION = KAM = 2\n\n    # When set, enables character insertion. New display characters\n    # move old display characters to the right. Characters moved past\n    # the right margin are lost.\n\n    # When reset, enables replacement mode (disables character\n    # insertion). New display characters replace old display\n    # characters at cursor position. The old character is erased.\n    INSERTION_REPLACEMENT = IRM = 4\n\n    # Set causes a received linefeed, form feed, or vertical tab to\n    # move cursor to first column of next line. RETURN transmits both\n    # a carriage return and linefeed. This selection is also called\n    # new line option.\n\n    # Reset causes a received linefeed, form feed, or vertical tab to\n    # move cursor to next line in current column. RETURN transmits a\n    # carriage return.\n    LINEFEED_NEWLINE = LNM = 20\n\n\n\nclass privateModes:\n    \"\"\"\n    ANSI-Compatible Private Modes\n    \"\"\"\n    ERROR = 0\n    CURSOR_KEY = 1\n    ANSI_VT52 = 2\n    COLUMN = 3\n    SCROLL = 4\n    SCREEN = 5\n    ORIGIN = 6\n    AUTO_WRAP = 7\n    AUTO_REPEAT = 8\n    PRINTER_FORM_FEED = 18\n    PRINTER_EXTENT = 19\n\n    # Toggle cursor visibility (reset hides it)\n    CURSOR_MODE = 25\n\n\n# Character sets\nCS_US = b'CS_US'\nCS_UK = b'CS_UK'\nCS_DRAWING = b'CS_DRAWING'\nCS_ALTERNATE = b'CS_ALTERNATE'\nCS_ALTERNATE_SPECIAL = b'CS_ALTERNATE_SPECIAL'\n\n# Groupings (or something?? These are like variables that can be bound to character sets)\nG0 = b'G0'\nG1 = b'G1'\n\n# G2 and G3 cannot be changed, but they can be shifted to.\nG2 = b'G2'\nG3 = b'G3'\n\n# Character attributes\n\nNORMAL = 0\nBOLD = 1\nUNDERLINE = 4\nBLINK = 5\nREVERSE_VIDEO = 7\n\nclass Vector:\n    def __init__(self, x, y):\n        self.x = x\n        self.y = y\n\n\n\ndef log(s):\n    with open('log', 'a') as f:\n        f.write(str(s) + '\\n')\n\n# XXX TODO - These attributes are really part of the\n# ITerminalTransport interface, I think.\n_KEY_NAMES = ('UP_ARROW', 'DOWN_ARROW', 'RIGHT_ARROW', 'LEFT_ARROW',\n              'HOME', 'INSERT', 'DELETE', 'END', 'PGUP', 'PGDN', 'NUMPAD_MIDDLE',\n              'F1', 'F2', 'F3', 'F4', 'F5', 'F6', 'F7', 'F8', 'F9',\n              'F10', 'F11', 'F12',\n\n              'ALT', 'SHIFT', 'CONTROL')\n\nclass _const(object):\n    \"\"\"\n    @ivar name: A string naming this constant\n    \"\"\"\n    def __init__(self, name):\n        self.name = name\n\n\n    def __repr__(self):\n        return '[' + self.name + ']'\n\n\n    def __bytes__(self):\n        return ('[' + self.name + ']').encode(\"ascii\")\n\n\nFUNCTION_KEYS = [\n    _const(_name).__bytes__() for _name in _KEY_NAMES]\n\n\n\n@implementer(ITerminalTransport)\nclass ServerProtocol(protocol.Protocol):\n    protocolFactory = None\n    terminalProtocol = None\n\n    TAB = b'\\t'\n    BACKSPACE = b'\\x7f'\n    ##\n\n    lastWrite = b''\n\n    state = b'data'\n\n    termSize = Vector(80, 24)\n    cursorPos = Vector(0, 0)\n    scrollRegion = None\n\n    # Factory who instantiated me\n    factory = None\n\n    def __init__(self, protocolFactory=None, *a, **kw):\n        \"\"\"\n        @param protocolFactory: A callable which will be invoked with\n        *a, **kw and should return an ITerminalProtocol implementor.\n        This will be invoked when a connection to this ServerProtocol\n        is established.\n\n        @param a: Any positional arguments to pass to protocolFactory.\n        @param kw: Any keyword arguments to pass to protocolFactory.\n        \"\"\"\n        # assert protocolFactory is None or ITerminalProtocol.implementedBy(protocolFactory), \"ServerProtocol.__init__ must be passed an ITerminalProtocol implementor\"\n        if protocolFactory is not None:\n            self.protocolFactory = protocolFactory\n        self.protocolArgs = a\n        self.protocolKwArgs = kw\n\n        self._cursorReports = []\n\n\n    def connectionMade(self):\n        if self.protocolFactory is not None:\n            self.terminalProtocol = self.protocolFactory(*self.protocolArgs, **self.protocolKwArgs)\n\n            try:\n                factory = self.factory\n            except AttributeError:\n                pass\n            else:\n                self.terminalProtocol.factory = factory\n\n            self.terminalProtocol.makeConnection(self)\n\n\n    def dataReceived(self, data):\n        for ch in iterbytes(data):\n            if self.state == b'data':\n                if ch == b'\\x1b':\n                    self.state = b'escaped'\n                else:\n                    self.terminalProtocol.keystrokeReceived(ch, None)\n            elif self.state == b'escaped':\n                if ch == b'[':\n                    self.state = b'bracket-escaped'\n                    self.escBuf = []\n                elif ch == b'O':\n                    self.state = b'low-function-escaped'\n                else:\n                    self.state = b'data'\n                    self._handleShortControlSequence(ch)\n            elif self.state == b'bracket-escaped':\n                if ch == b'O':\n                    self.state = b'low-function-escaped'\n                elif ch.isalpha() or ch == b'~':\n                    self._handleControlSequence(b''.join(self.escBuf) + ch)\n                    del self.escBuf\n                    self.state = b'data'\n                else:\n                    self.escBuf.append(ch)\n            elif self.state == b'low-function-escaped':\n                self._handleLowFunctionControlSequence(ch)\n                self.state = b'data'\n            else:\n                raise ValueError(\"Illegal state\")\n\n\n    def _handleShortControlSequence(self, ch):\n        self.terminalProtocol.keystrokeReceived(ch, self.ALT)\n\n\n    def _handleControlSequence(self, buf):\n        buf = b'\\x1b[' + buf\n        f = getattr(self.controlSequenceParser,\n                    CST.get(buf[-1:], buf[-1:]).decode(\"ascii\"),\n                    None)\n        if f is None:\n            self.unhandledControlSequence(buf)\n        else:\n            f(self, self.terminalProtocol, buf[:-1])\n\n\n    def unhandledControlSequence(self, buf):\n        self.terminalProtocol.unhandledControlSequence(buf)\n\n\n    def _handleLowFunctionControlSequence(self, ch):\n        functionKeys = {b'P': self.F1, b'Q': self.F2,\n                        b'R': self.F3, b'S': self.F4}\n        keyID = functionKeys.get(ch)\n        if keyID is not None:\n            self.terminalProtocol.keystrokeReceived(keyID, None)\n        else:\n            self.terminalProtocol.unhandledControlSequence(b'\\x1b[O' + ch)\n\n\n    class ControlSequenceParser:\n        def A(self, proto, handler, buf):\n            if buf == b'\\x1b[':\n                handler.keystrokeReceived(proto.UP_ARROW, None)\n            else:\n                handler.unhandledControlSequence(buf + b'A')\n\n\n        def B(self, proto, handler, buf):\n            if buf == b'\\x1b[':\n                handler.keystrokeReceived(proto.DOWN_ARROW, None)\n            else:\n                handler.unhandledControlSequence(buf + b'B')\n\n\n        def C(self, proto, handler, buf):\n            if buf == b'\\x1b[':\n                handler.keystrokeReceived(proto.RIGHT_ARROW, None)\n            else:\n                handler.unhandledControlSequence(buf + b'C')\n\n\n        def D(self, proto, handler, buf):\n            if buf == b'\\x1b[':\n                handler.keystrokeReceived(proto.LEFT_ARROW, None)\n            else:\n                handler.unhandledControlSequence(buf + b'D')\n\n\n        def E(self, proto, handler, buf):\n            if buf == b'\\x1b[':\n                handler.keystrokeReceived(proto.NUMPAD_MIDDLE, None)\n            else:\n                handler.unhandledControlSequence(buf + b'E')\n\n\n        def F(self, proto, handler, buf):\n            if buf == b'\\x1b[':\n                handler.keystrokeReceived(proto.END, None)\n            else:\n                handler.unhandledControlSequence(buf + b'F')\n\n\n        def H(self, proto, handler, buf):\n            if buf == b'\\x1b[':\n                handler.keystrokeReceived(proto.HOME, None)\n            else:\n                handler.unhandledControlSequence(buf + b'H')\n\n\n        def R(self, proto, handler, buf):\n            if not proto._cursorReports:\n                handler.unhandledControlSequence(buf + b'R')\n            elif buf.startswith(b'\\x1b['):\n                report = buf[2:]\n                parts = report.split(b';')\n                if len(parts) != 2:\n                    handler.unhandledControlSequence(buf + b'R')\n                else:\n                    Pl, Pc = parts\n                    try:\n                        Pl, Pc = int(Pl), int(Pc)\n                    except ValueError:\n                        handler.unhandledControlSequence(buf + b'R')\n                    else:\n                        d = proto._cursorReports.pop(0)\n                        d.callback((Pc - 1, Pl - 1))\n            else:\n                handler.unhandledControlSequence(buf + b'R')\n\n\n        def Z(self, proto, handler, buf):\n            if buf == b'\\x1b[':\n                handler.keystrokeReceived(proto.TAB, proto.SHIFT)\n            else:\n                handler.unhandledControlSequence(buf + b'Z')\n\n\n        def tilde(self, proto, handler, buf):\n            map = {1: proto.HOME, 2: proto.INSERT, 3: proto.DELETE,\n                   4: proto.END,  5: proto.PGUP,   6: proto.PGDN,\n\n                   15: proto.F5,  17: proto.F6, 18: proto.F7,\n                   19: proto.F8,  20: proto.F9, 21: proto.F10,\n                   23: proto.F11, 24: proto.F12}\n\n            if buf.startswith(b'\\x1b['):\n                ch = buf[2:]\n                try:\n                    v = int(ch)\n                except ValueError:\n                    handler.unhandledControlSequence(buf + b'~')\n                else:\n                    symbolic = map.get(v)\n                    if symbolic is not None:\n                        handler.keystrokeReceived(map[v], None)\n                    else:\n                        handler.unhandledControlSequence(buf + b'~')\n            else:\n                handler.unhandledControlSequence(buf + b'~')\n\n    controlSequenceParser = ControlSequenceParser()\n\n\n # ITerminalTransport\n    def cursorUp(self, n=1):\n        assert n >= 1\n        self.cursorPos.y = max(self.cursorPos.y - n, 0)\n        self.write(b'\\x1b[' + intToBytes(n) +  b'A')\n\n\n    def cursorDown(self, n=1):\n        assert n >= 1\n        self.cursorPos.y = min(self.cursorPos.y + n, self.termSize.y - 1)\n        self.write(b'\\x1b[' + intToBytes(n) + b'B')\n\n\n    def cursorForward(self, n=1):\n        assert n >= 1\n        self.cursorPos.x = min(self.cursorPos.x + n, self.termSize.x - 1)\n        self.write(b'\\x1b[' + intToBytes(n) + b'C')\n\n\n    def cursorBackward(self, n=1):\n        assert n >= 1\n        self.cursorPos.x = max(self.cursorPos.x - n, 0)\n        self.write(b'\\x1b[' + intToBytes(n) + b'D')\n\n\n    def cursorPosition(self, column, line):\n        self.write(b'\\x1b[' +\n                   intToBytes(line + 1)  +\n                   b';' +\n                   intToBytes(column + 1) +\n                   b'H')\n\n\n    def cursorHome(self):\n        self.cursorPos.x = self.cursorPos.y = 0\n        self.write(b'\\x1b[H')\n\n\n    def index(self):\n        # ECMA48 5th Edition removes this\n        self.cursorPos.y = min(self.cursorPos.y + 1, self.termSize.y - 1)\n        self.write(b'\\x1bD')\n\n\n    def reverseIndex(self):\n        self.cursorPos.y = max(self.cursorPos.y - 1, 0)\n        self.write(b'\\x1bM')\n\n\n    def nextLine(self):\n        self.cursorPos.x = 0\n        self.cursorPos.y = min(self.cursorPos.y + 1, self.termSize.y - 1)\n        self.write(b'\\n')\n\n\n    def saveCursor(self):\n        self._savedCursorPos = Vector(self.cursorPos.x, self.cursorPos.y)\n        self.write(b'\\x1b7')\n\n\n    def restoreCursor(self):\n        self.cursorPos = self._savedCursorPos\n        del self._savedCursorPos\n        self.write(b'\\x1b8')\n\n\n    def setModes(self, modes):\n        # XXX Support ANSI-Compatible private modes\n        modesBytes = b';'.join([intToBytes(mode) for mode in modes])\n        self.write(b'\\x1b[' + modesBytes + b'h')\n\n\n    def setPrivateModes(self, modes):\n        modesBytes = b';'.join([intToBytes(mode) for mode in modes])\n        self.write(b'\\x1b[?' + modesBytes + b'h')\n\n\n    def resetModes(self, modes):\n        # XXX Support ANSI-Compatible private modes\n        modesBytes = b';'.join([intToBytes(mode) for mode in modes])\n        self.write(b'\\x1b[' + modesBytes + b'l')\n\n\n    def resetPrivateModes(self, modes):\n        modesBytes = b';'.join([intToBytes(mode) for mode in modes])\n        self.write(b'\\x1b[?' + modesBytes + b'l')\n\n\n    def applicationKeypadMode(self):\n        self.write(b'\\x1b=')\n\n\n    def numericKeypadMode(self):\n        self.write(b'\\x1b>')\n\n\n    def selectCharacterSet(self, charSet, which):\n        # XXX Rewrite these as dict lookups\n        if which == G0:\n            which = b'('\n        elif which == G1:\n            which = b')'\n        else:\n            raise ValueError(\"`which' argument to selectCharacterSet must be G0 or G1\")\n        if charSet == CS_UK:\n            charSet = b'A'\n        elif charSet == CS_US:\n            charSet = b'B'\n        elif charSet == CS_DRAWING:\n            charSet = b'0'\n        elif charSet == CS_ALTERNATE:\n            charSet = b'1'\n        elif charSet == CS_ALTERNATE_SPECIAL:\n            charSet = b'2'\n        else:\n            raise ValueError(\"Invalid `charSet' argument to selectCharacterSet\")\n        self.write(b'\\x1b' + which + charSet)\n\n\n    def shiftIn(self):\n        self.write(b'\\x15')\n\n\n    def shiftOut(self):\n        self.write(b'\\x14')\n\n\n    def singleShift2(self):\n        self.write(b'\\x1bN')\n\n\n    def singleShift3(self):\n        self.write(b'\\x1bO')\n\n\n    def selectGraphicRendition(self, *attributes):\n        # each member of attributes must be a native string\n        attrs = []\n        for a in attributes:\n            attrs.append(networkString(a))\n        self.write(b'\\x1b[' +\n                   b';'.join(attrs) +\n                   b'm')\n\n\n    def horizontalTabulationSet(self):\n        self.write(b'\\x1bH')\n\n\n    def tabulationClear(self):\n        self.write(b'\\x1b[q')\n\n\n    def tabulationClearAll(self):\n        self.write(b'\\x1b[3q')\n\n\n    def doubleHeightLine(self, top=True):\n        if top:\n            self.write(b'\\x1b#3')\n        else:\n            self.write(b'\\x1b#4')\n\n\n    def singleWidthLine(self):\n        self.write(b'\\x1b#5')\n\n\n    def doubleWidthLine(self):\n        self.write(b'\\x1b#6')\n\n\n    def eraseToLineEnd(self):\n        self.write(b'\\x1b[K')\n\n\n    def eraseToLineBeginning(self):\n        self.write(b'\\x1b[1K')\n\n\n    def eraseLine(self):\n        self.write(b'\\x1b[2K')\n\n\n    def eraseToDisplayEnd(self):\n        self.write(b'\\x1b[J')\n\n\n    def eraseToDisplayBeginning(self):\n        self.write(b'\\x1b[1J')\n\n\n    def eraseDisplay(self):\n        self.write(b'\\x1b[2J')\n\n\n    def deleteCharacter(self, n=1):\n        self.write(b'\\x1b[' + intToBytes(n) + b'P')\n\n\n    def insertLine(self, n=1):\n        self.write(b'\\x1b[' + intToBytes(n) + b'L')\n\n\n    def deleteLine(self, n=1):\n        self.write(b'\\x1b[' + intToBytes(n) + b'M')\n\n\n    def setScrollRegion(self, first=None, last=None):\n        if first is not None:\n            first = intToBytes(first)\n        else:\n            first = b''\n        if last is not None:\n            last = intToBytes(last)\n        else:\n            last = b''\n        self.write(b'\\x1b[' + first + b';' + last + b'r')\n\n\n    def resetScrollRegion(self):\n        self.setScrollRegion()\n\n\n    def reportCursorPosition(self):\n        d = defer.Deferred()\n        self._cursorReports.append(d)\n        self.write(b'\\x1b[6n')\n        return d\n\n\n    def reset(self):\n        self.cursorPos.x = self.cursorPos.y = 0\n        try:\n            del self._savedCursorPos\n        except AttributeError:\n            pass\n        self.write(b'\\x1bc')\n\n\n    # ITransport\n    def write(self, data):\n        if data:\n            if not isinstance(data, bytes):\n                data = data.encode(\"utf-8\")\n            self.lastWrite = data\n            self.transport.write(b'\\r\\n'.join(data.split(b'\\n')))\n\n\n    def writeSequence(self, data):\n        self.write(b''.join(data))\n\n\n    def loseConnection(self):\n        self.reset()\n        self.transport.loseConnection()\n\n\n    def connectionLost(self, reason):\n        if self.terminalProtocol is not None:\n            try:\n                self.terminalProtocol.connectionLost(reason)\n            finally:\n                self.terminalProtocol = None\n# Add symbolic names for function keys\nfor name, const in zip(_KEY_NAMES, FUNCTION_KEYS):\n    setattr(ServerProtocol, name, const)\n\n\n\nclass ClientProtocol(protocol.Protocol):\n\n    terminalFactory = None\n    terminal = None\n\n    state = b'data'\n\n    _escBuf = None\n\n    _shorts = {\n        b'D': b'index',\n        b'M': b'reverseIndex',\n        b'E': b'nextLine',\n        b'7': b'saveCursor',\n        b'8': b'restoreCursor',\n        b'=': b'applicationKeypadMode',\n        b'>': b'numericKeypadMode',\n        b'N': b'singleShift2',\n        b'O': b'singleShift3',\n        b'H': b'horizontalTabulationSet',\n        b'c': b'reset'}\n\n    _longs = {\n        b'[': b'bracket-escape',\n        b'(': b'select-g0',\n        b')': b'select-g1',\n        b'#': b'select-height-width'}\n\n    _charsets = {\n        b'A': CS_UK,\n        b'B': CS_US,\n        b'0': CS_DRAWING,\n        b'1': CS_ALTERNATE,\n        b'2': CS_ALTERNATE_SPECIAL}\n\n    # Factory who instantiated me\n    factory = None\n\n    def __init__(self, terminalFactory=None, *a, **kw):\n        \"\"\"\n        @param terminalFactory: A callable which will be invoked with\n        *a, **kw and should return an ITerminalTransport provider.\n        This will be invoked when this ClientProtocol establishes a\n        connection.\n\n        @param a: Any positional arguments to pass to terminalFactory.\n        @param kw: Any keyword arguments to pass to terminalFactory.\n        \"\"\"\n        # assert terminalFactory is None or ITerminalTransport.implementedBy(terminalFactory), \"ClientProtocol.__init__ must be passed an ITerminalTransport implementor\"\n        if terminalFactory is not None:\n            self.terminalFactory = terminalFactory\n        self.terminalArgs = a\n        self.terminalKwArgs = kw\n\n\n    def connectionMade(self):\n        if self.terminalFactory is not None:\n            self.terminal = self.terminalFactory(*self.terminalArgs, **self.terminalKwArgs)\n            self.terminal.factory = self.factory\n            self.terminal.makeConnection(self)\n\n\n    def connectionLost(self, reason):\n        if self.terminal is not None:\n            try:\n                self.terminal.connectionLost(reason)\n            finally:\n                del self.terminal\n\n\n    def dataReceived(self, data):\n        \"\"\"\n        Parse the given data from a terminal server, dispatching to event\n        handlers defined by C{self.terminal}.\n        \"\"\"\n        toWrite = []\n        for b in iterbytes(data):\n            if self.state == b'data':\n                if b == b'\\x1b':\n                    if toWrite:\n                        self.terminal.write(b''.join(toWrite))\n                        del toWrite[:]\n                    self.state = b'escaped'\n                elif b == b'\\x14':\n                    if toWrite:\n                        self.terminal.write(b''.join(toWrite))\n                        del toWrite[:]\n                    self.terminal.shiftOut()\n                elif b == b'\\x15':\n                    if toWrite:\n                        self.terminal.write(b''.join(toWrite))\n                        del toWrite[:]\n                    self.terminal.shiftIn()\n                elif b == b'\\x08':\n                    if toWrite:\n                        self.terminal.write(b''.join(toWrite))\n                        del toWrite[:]\n                    self.terminal.cursorBackward()\n                else:\n                    toWrite.append(b)\n            elif self.state == b'escaped':\n                fName = self._shorts.get(b)\n                if fName is not None:\n                    self.state = b'data'\n                    getattr(self.terminal, fName.decode(\"ascii\"))()\n                else:\n                    state = self._longs.get(b)\n                    if state is not None:\n                        self.state = state\n                    else:\n                        self.terminal.unhandledControlSequence(b'\\x1b' + b)\n                        self.state = b'data'\n            elif self.state == b'bracket-escape':\n                if self._escBuf is None:\n                    self._escBuf = []\n                if b.isalpha() or b == b'~':\n                    self._handleControlSequence(b''.join(self._escBuf), b)\n                    del self._escBuf\n                    self.state = b'data'\n                else:\n                    self._escBuf.append(b)\n            elif self.state == b'select-g0':\n                self.terminal.selectCharacterSet(self._charsets.get(b, b), G0)\n                self.state = b'data'\n            elif self.state == b'select-g1':\n                self.terminal.selectCharacterSet(self._charsets.get(b, b), G1)\n                self.state = b'data'\n            elif self.state == b'select-height-width':\n                self._handleHeightWidth(b)\n                self.state = b'data'\n            else:\n                raise ValueError(\"Illegal state\")\n        if toWrite:\n            self.terminal.write(b''.join(toWrite))\n\n\n    def _handleControlSequence(self, buf, terminal):\n        f = getattr(self.controlSequenceParser, CST.get(terminal, terminal).decode(\"ascii\"), None)\n        if f is None:\n            self.terminal.unhandledControlSequence(b'\\x1b[' + buf + terminal)\n        else:\n            f(self, self.terminal, buf)\n\n\n    class ControlSequenceParser:\n        def _makeSimple(ch, fName):\n            n = 'cursor' + fName\n            def simple(self, proto, handler, buf):\n                if not buf:\n                    getattr(handler, n)(1)\n                else:\n                    try:\n                        m = int(buf)\n                    except ValueError:\n                        handler.unhandledControlSequence(b'\\x1b[' + buf + ch)\n                    else:\n                        getattr(handler, n)(m)\n            return simple\n\n        for (ch, fName) in (('A', 'Up'),\n                            ('B', 'Down'),\n                            ('C', 'Forward'),\n                            ('D', 'Backward')):\n            exec(ch + \" = _makeSimple(ch, fName)\")\n        del _makeSimple\n\n\n        def h(self, proto, handler, buf):\n            # XXX - Handle '?' to introduce ANSI-Compatible private modes.\n            try:\n                modes = [int(mode) for mode in buf.split(b';')]\n            except ValueError:\n                handler.unhandledControlSequence(b'\\x1b[' + buf + b'h')\n            else:\n                handler.setModes(modes)\n\n\n        def l(self, proto, handler, buf):\n            # XXX - Handle '?' to introduce ANSI-Compatible private modes.\n            try:\n                modes = [int(mode) for mode in buf.split(b';')]\n            except ValueError:\n                handler.unhandledControlSequence(b'\\x1b[' + buf + 'l')\n            else:\n                handler.resetModes(modes)\n\n\n        def r(self, proto, handler, buf):\n            parts = buf.split(b';')\n            if len(parts) == 1:\n                handler.setScrollRegion(None, None)\n            elif len(parts) == 2:\n                try:\n                    if parts[0]:\n                        pt = int(parts[0])\n                    else:\n                        pt = None\n                    if parts[1]:\n                        pb = int(parts[1])\n                    else:\n                        pb = None\n                except ValueError:\n                    handler.unhandledControlSequence(b'\\x1b[' + buf + b'r')\n                else:\n                    handler.setScrollRegion(pt, pb)\n            else:\n                handler.unhandledControlSequence(b'\\x1b[' + buf + b'r')\n\n        def K(self, proto, handler, buf):\n            if not buf:\n                handler.eraseToLineEnd()\n            elif buf == b'1':\n                handler.eraseToLineBeginning()\n            elif buf == b'2':\n                handler.eraseLine()\n            else:\n                handler.unhandledControlSequence(b'\\x1b[' + buf + b'K')\n\n\n        def H(self, proto, handler, buf):\n            handler.cursorHome()\n\n\n        def J(self, proto, handler, buf):\n            if not buf:\n                handler.eraseToDisplayEnd()\n            elif buf == b'1':\n                handler.eraseToDisplayBeginning()\n            elif buf == b'2':\n                handler.eraseDisplay()\n            else:\n                handler.unhandledControlSequence(b'\\x1b[' + buf + b'J')\n\n\n        def P(self, proto, handler, buf):\n            if not buf:\n                handler.deleteCharacter(1)\n            else:\n                try:\n                    n = int(buf)\n                except ValueError:\n                    handler.unhandledControlSequence(b'\\x1b[' + buf + b'P')\n                else:\n                    handler.deleteCharacter(n)\n\n        def L(self, proto, handler, buf):\n            if not buf:\n                handler.insertLine(1)\n            else:\n                try:\n                    n = int(buf)\n                except ValueError:\n                    handler.unhandledControlSequence(b'\\x1b[' + buf + b'L')\n                else:\n                    handler.insertLine(n)\n\n\n        def M(self, proto, handler, buf):\n            if not buf:\n                handler.deleteLine(1)\n            else:\n                try:\n                    n = int(buf)\n                except ValueError:\n                    handler.unhandledControlSequence(b'\\x1b[' + buf + b'M')\n                else:\n                    handler.deleteLine(n)\n\n\n        def n(self, proto, handler, buf):\n            if buf == b'6':\n                x, y = handler.reportCursorPosition()\n                proto.transport.write(b'\\x1b['\n                                      + intToBytes(x+1)\n                                      + b';'\n                                      + intToBytes(y+1)\n                                      + b'R')\n            else:\n                handler.unhandledControlSequence(b'\\x1b[' + buf + b'n')\n\n\n        def m(self, proto, handler, buf):\n            if not buf:\n                handler.selectGraphicRendition(NORMAL)\n            else:\n                attrs = []\n                for a in buf.split(b';'):\n                    try:\n                        a = int(a)\n                    except ValueError:\n                        pass\n                    attrs.append(a)\n                handler.selectGraphicRendition(*attrs)\n\n    controlSequenceParser = ControlSequenceParser()\n\n\n    def _handleHeightWidth(self, b):\n        if b == b'3':\n            self.terminal.doubleHeightLine(True)\n        elif b == b'4':\n            self.terminal.doubleHeightLine(False)\n        elif b == b'5':\n            self.terminal.singleWidthLine()\n        elif b == b'6':\n            self.terminal.doubleWidthLine()\n        else:\n            self.terminal.unhandledControlSequence(b'\\x1b#' + b)\n\n\n__all__ = [\n    # Interfaces\n    'ITerminalProtocol', 'ITerminalTransport',\n\n    # Symbolic constants\n    'modes', 'privateModes', 'FUNCTION_KEYS',\n\n    'CS_US', 'CS_UK', 'CS_DRAWING', 'CS_ALTERNATE', 'CS_ALTERNATE_SPECIAL',\n    'G0', 'G1', 'G2', 'G3',\n\n    'UNDERLINE', 'REVERSE_VIDEO', 'BLINK', 'BOLD', 'NORMAL',\n\n    # Protocol classes\n    'ServerProtocol', 'ClientProtocol']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/insults/text.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_text -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nCharacter attribute manipulation API.\n\nThis module provides a domain-specific language (using Python syntax)\nfor the creation of text with additional display attributes associated\nwith it.  It is intended as an alternative to manually building up\nstrings containing ECMA 48 character attribute control codes.  It\ncurrently supports foreground and background colors (black, red,\ngreen, yellow, blue, magenta, cyan, and white), intensity selection,\nunderlining, blinking and reverse video.  Character set selection\nsupport is planned.\n\nCharacter attributes are specified by using two Python operations:\nattribute lookup and indexing.  For example, the string \\\"Hello\nworld\\\" with red foreground and all other attributes set to their\ndefaults, assuming the name twisted.conch.insults.text.attributes has\nbeen imported and bound to the name \\\"A\\\" (with the statement C{from\ntwisted.conch.insults.text import attributes as A}, for example) one\nuses this expression::\n\n    A.fg.red[\\\"Hello world\\\"]\n\nOther foreground colors are set by substituting their name for\n\\\"red\\\".  To set both a foreground and a background color, this\nexpression is used::\n\n    A.fg.red[A.bg.green[\\\"Hello world\\\"]]\n\nNote that either A.bg.green can be nested within A.fg.red or vice\nversa.  Also note that multiple items can be nested within a single\nindex operation by separating them with commas::\n\n    A.bg.green[A.fg.red[\\\"Hello\\\"], \" \", A.fg.blue[\\\"world\\\"]]\n\nOther character attributes are set in a similar fashion.  To specify a\nblinking version of the previous expression::\n\n    A.blink[A.bg.green[A.fg.red[\\\"Hello\\\"], \" \", A.fg.blue[\\\"world\\\"]]]\n\nC{A.reverseVideo}, C{A.underline}, and C{A.bold} are also valid.\n\nA third operation is actually supported: unary negation.  This turns\noff an attribute when an enclosing expression would otherwise have\ncaused it to be on.  For example::\n\n    A.underline[A.fg.red[\\\"Hello\\\", -A.underline[\\\" world\\\"]]]\n\nA formatting structure can then be serialized into a string containing the\nnecessary VT102 control codes with L{assembleFormattedText}.\n\n@see: L{twisted.conch.insults.text._CharacterAttributes}\n@author: Jp Calderone\n\"\"\"\n\nfrom incremental import Version\n\nfrom twisted.conch.insults import helper, insults\nfrom twisted.python import _textattributes\nfrom twisted.python.deprecate import deprecatedModuleAttribute\n\n\n\nflatten = _textattributes.flatten\n\ndeprecatedModuleAttribute(\n    Version('Twisted', 13, 1, 0),\n    'Use twisted.conch.insults.text.assembleFormattedText instead.',\n    'twisted.conch.insults.text',\n    'flatten')\n\n_TEXT_COLORS = {\n    'black': helper.BLACK,\n    'red': helper.RED,\n    'green': helper.GREEN,\n    'yellow': helper.YELLOW,\n    'blue': helper.BLUE,\n    'magenta': helper.MAGENTA,\n    'cyan': helper.CYAN,\n    'white': helper.WHITE}\n\n\n\nclass _CharacterAttributes(_textattributes.CharacterAttributesMixin):\n    \"\"\"\n    Factory for character attributes, including foreground and background color\n    and non-color attributes such as bold, reverse video and underline.\n\n    Character attributes are applied to actual text by using object\n    indexing-syntax (C{obj['abc']}) after accessing a factory attribute, for\n    example::\n\n        attributes.bold['Some text']\n\n    These can be nested to mix attributes::\n\n        attributes.bold[attributes.underline['Some text']]\n\n    And multiple values can be passed::\n\n        attributes.normal[attributes.bold['Some'], ' text']\n\n    Non-color attributes can be accessed by attribute name, available\n    attributes are:\n\n        - bold\n        - blink\n        - reverseVideo\n        - underline\n\n    Available colors are:\n\n        0. black\n        1. red\n        2. green\n        3. yellow\n        4. blue\n        5. magenta\n        6. cyan\n        7. white\n\n    @ivar fg: Foreground colors accessed by attribute name, see above\n        for possible names.\n\n    @ivar bg: Background colors accessed by attribute name, see above\n        for possible names.\n    \"\"\"\n    fg = _textattributes._ColorAttribute(\n        _textattributes._ForegroundColorAttr, _TEXT_COLORS)\n    bg = _textattributes._ColorAttribute(\n        _textattributes._BackgroundColorAttr, _TEXT_COLORS)\n\n    attrs = {\n        'bold': insults.BOLD,\n        'blink': insults.BLINK,\n        'underline': insults.UNDERLINE,\n        'reverseVideo': insults.REVERSE_VIDEO}\n\n\n\ndef assembleFormattedText(formatted):\n    \"\"\"\n    Assemble formatted text from structured information.\n\n    Currently handled formatting includes: bold, blink, reverse, underline and\n    color codes.\n\n    For example::\n\n        from twisted.conch.insults.text import attributes as A\n        assembleFormattedText(\n            A.normal[A.bold['Time: '], A.fg.lightRed['Now!']])\n\n    Would produce \"Time: \" in bold formatting, followed by \"Now!\" with a\n    foreground color of light red and without any additional formatting.\n\n    @param formatted: Structured text and attributes.\n\n    @rtype: L{str}\n    @return: String containing VT102 control sequences that mimic those\n        specified by C{formatted}.\n\n    @see: L{twisted.conch.insults.text._CharacterAttributes}\n    @since: 13.1\n    \"\"\"\n    return _textattributes.flatten(\n        formatted, helper._FormattingState(), 'toVT102')\n\n\n\nattributes = _CharacterAttributes()\n\n__all__ = ['attributes', 'flatten']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/insults/window.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_window -*-\n\n\"\"\"\nSimple insults-based widget library\n\n@author: Jp Calderone\n\"\"\"\n\nimport array\n\nfrom twisted.conch.insults import insults, helper\nfrom twisted.python import text as tptext\nfrom twisted.python.compat import (_PY3, _bytesChr as chr)\n\nclass YieldFocus(Exception):\n    \"\"\"\n    Input focus manipulation exception\n    \"\"\"\n\n\n\nclass BoundedTerminalWrapper(object):\n    def __init__(self, terminal, width, height, xoff, yoff):\n        self.width = width\n        self.height = height\n        self.xoff = xoff\n        self.yoff = yoff\n        self.terminal = terminal\n        self.cursorForward = terminal.cursorForward\n        self.selectCharacterSet = terminal.selectCharacterSet\n        self.selectGraphicRendition = terminal.selectGraphicRendition\n        self.saveCursor = terminal.saveCursor\n        self.restoreCursor = terminal.restoreCursor\n\n\n    def cursorPosition(self, x, y):\n        return self.terminal.cursorPosition(\n            self.xoff + min(self.width, x),\n            self.yoff + min(self.height, y)\n            )\n\n\n    def cursorHome(self):\n        return self.terminal.cursorPosition(\n            self.xoff, self.yoff)\n\n\n    def write(self, data):\n        return self.terminal.write(data)\n\n\n\nclass Widget(object):\n    focused = False\n    parent = None\n    dirty = False\n    width = height = None\n\n    def repaint(self):\n        if not self.dirty:\n            self.dirty = True\n        if self.parent is not None and not self.parent.dirty:\n            self.parent.repaint()\n\n\n    def filthy(self):\n        self.dirty = True\n\n\n    def redraw(self, width, height, terminal):\n        self.filthy()\n        self.draw(width, height, terminal)\n\n\n    def draw(self, width, height, terminal):\n        if width != self.width or height != self.height or self.dirty:\n            self.width = width\n            self.height = height\n            self.dirty = False\n            self.render(width, height, terminal)\n\n\n    def render(self, width, height, terminal):\n        pass\n\n\n    def sizeHint(self):\n        return None\n\n\n    def keystrokeReceived(self, keyID, modifier):\n        if keyID == b'\\t':\n            self.tabReceived(modifier)\n        elif keyID == b'\\x7f':\n            self.backspaceReceived()\n        elif keyID in insults.FUNCTION_KEYS:\n            self.functionKeyReceived(keyID, modifier)\n        else:\n            self.characterReceived(keyID, modifier)\n\n\n    def tabReceived(self, modifier):\n        # XXX TODO - Handle shift+tab\n        raise YieldFocus()\n\n\n    def focusReceived(self):\n        \"\"\"\n        Called when focus is being given to this widget.\n\n        May raise YieldFocus is this widget does not want focus.\n        \"\"\"\n        self.focused = True\n        self.repaint()\n\n\n    def focusLost(self):\n        self.focused = False\n        self.repaint()\n\n\n    def backspaceReceived(self):\n        pass\n\n\n    def functionKeyReceived(self, keyID, modifier):\n        name = keyID\n        if not isinstance(keyID, str):\n            name = name.decode(\"utf-8\")\n        func = getattr(self, 'func_' + name, None)\n        if func is not None:\n            func(modifier)\n\n\n    def characterReceived(self, keyID, modifier):\n        pass\n\n\n\nclass ContainerWidget(Widget):\n    \"\"\"\n    @ivar focusedChild: The contained widget which currently has\n    focus, or None.\n    \"\"\"\n    focusedChild = None\n    focused = False\n\n    def __init__(self):\n        Widget.__init__(self)\n        self.children = []\n\n\n    def addChild(self, child):\n        assert child.parent is None\n        child.parent = self\n        self.children.append(child)\n        if self.focusedChild is None and self.focused:\n            try:\n                child.focusReceived()\n            except YieldFocus:\n                pass\n            else:\n                self.focusedChild = child\n        self.repaint()\n\n\n    def remChild(self, child):\n        assert child.parent is self\n        child.parent = None\n        self.children.remove(child)\n        self.repaint()\n\n\n    def filthy(self):\n        for ch in self.children:\n            ch.filthy()\n        Widget.filthy(self)\n\n\n    def render(self, width, height, terminal):\n        for ch in self.children:\n            ch.draw(width, height, terminal)\n\n\n    def changeFocus(self):\n        self.repaint()\n\n        if self.focusedChild is not None:\n            self.focusedChild.focusLost()\n            focusedChild = self.focusedChild\n            self.focusedChild = None\n            try:\n                curFocus = self.children.index(focusedChild) + 1\n            except ValueError:\n                raise YieldFocus()\n        else:\n            curFocus = 0\n        while curFocus < len(self.children):\n            try:\n                self.children[curFocus].focusReceived()\n            except YieldFocus:\n                curFocus += 1\n            else:\n                self.focusedChild = self.children[curFocus]\n                return\n        # None of our children wanted focus\n        raise YieldFocus()\n\n\n    def focusReceived(self):\n        self.changeFocus()\n        self.focused = True\n\n\n    def keystrokeReceived(self, keyID, modifier):\n        if self.focusedChild is not None:\n            try:\n                self.focusedChild.keystrokeReceived(keyID, modifier)\n            except YieldFocus:\n                self.changeFocus()\n                self.repaint()\n        else:\n            Widget.keystrokeReceived(self, keyID, modifier)\n\n\n\nclass TopWindow(ContainerWidget):\n    \"\"\"\n    A top-level container object which provides focus wrap-around and paint\n    scheduling.\n\n    @ivar painter: A no-argument callable which will be invoked when this\n    widget needs to be redrawn.\n\n    @ivar scheduler: A one-argument callable which will be invoked with a\n    no-argument callable and should arrange for it to invoked at some point in\n    the near future.  The no-argument callable will cause this widget and all\n    its children to be redrawn.  It is typically beneficial for the no-argument\n    callable to be invoked at the end of handling for whatever event is\n    currently active; for example, it might make sense to call it at the end of\n    L{twisted.conch.insults.insults.ITerminalProtocol.keystrokeReceived}.\n    Note, however, that since calls to this may also be made in response to no\n    apparent event, arrangements should be made for the function to be called\n    even if an event handler such as C{keystrokeReceived} is not on the call\n    stack (eg, using\n    L{reactor.callLater<twisted.internet.interfaces.IReactorTime.callLater>}\n    with a short timeout).\n    \"\"\"\n    focused = True\n\n    def __init__(self, painter, scheduler):\n        ContainerWidget.__init__(self)\n        self.painter = painter\n        self.scheduler = scheduler\n\n    _paintCall = None\n\n\n    def repaint(self):\n        if self._paintCall is None:\n            self._paintCall = object()\n            self.scheduler(self._paint)\n        ContainerWidget.repaint(self)\n\n\n    def _paint(self):\n        self._paintCall = None\n        self.painter()\n\n\n    def changeFocus(self):\n        try:\n            ContainerWidget.changeFocus(self)\n        except YieldFocus:\n            try:\n                ContainerWidget.changeFocus(self)\n            except YieldFocus:\n                pass\n\n\n    def keystrokeReceived(self, keyID, modifier):\n        try:\n            ContainerWidget.keystrokeReceived(self, keyID, modifier)\n        except YieldFocus:\n            self.changeFocus()\n\n\n\nclass AbsoluteBox(ContainerWidget):\n    def moveChild(self, child, x, y):\n        for n in range(len(self.children)):\n            if self.children[n][0] is child:\n                self.children[n] = (child, x, y)\n                break\n        else:\n            raise ValueError(\"No such child\", child)\n\n\n    def render(self, width, height, terminal):\n        for (ch, x, y) in self.children:\n            wrap = BoundedTerminalWrapper(terminal, width - x, height - y, x, y)\n            ch.draw(width, height, wrap)\n\n\n\nclass _Box(ContainerWidget):\n    TOP, CENTER, BOTTOM = range(3)\n\n    def __init__(self, gravity=CENTER):\n        ContainerWidget.__init__(self)\n        self.gravity = gravity\n\n\n    def sizeHint(self):\n        height = 0\n        width = 0\n        for ch in self.children:\n            hint = ch.sizeHint()\n            if hint is None:\n                hint = (None, None)\n\n            if self.variableDimension == 0:\n                if hint[0] is None:\n                    width = None\n                elif width is not None:\n                    width += hint[0]\n                if hint[1] is None:\n                    height = None\n                elif height is not None:\n                    height = max(height, hint[1])\n            else:\n                if hint[0] is None:\n                    width = None\n                elif width is not None:\n                    width = max(width, hint[0])\n                if hint[1] is None:\n                    height = None\n                elif height is not None:\n                    height += hint[1]\n\n        return width, height\n\n\n    def render(self, width, height, terminal):\n        if not self.children:\n            return\n\n        greedy = 0\n        wants = []\n        for ch in self.children:\n            hint = ch.sizeHint()\n            if hint is None:\n                hint = (None, None)\n            if hint[self.variableDimension] is None:\n                greedy += 1\n            wants.append(hint[self.variableDimension])\n\n        length = (width, height)[self.variableDimension]\n        totalWant = sum([w for w in wants if w is not None])\n        if greedy:\n            leftForGreedy = int((length - totalWant) / greedy)\n\n        widthOffset = heightOffset = 0\n\n        for want, ch in zip(wants, self.children):\n            if want is None:\n                want = leftForGreedy\n\n            subWidth, subHeight = width, height\n            if self.variableDimension == 0:\n                subWidth = want\n            else:\n                subHeight = want\n\n            wrap = BoundedTerminalWrapper(\n                terminal,\n                subWidth,\n                subHeight,\n                widthOffset,\n                heightOffset,\n                )\n            ch.draw(subWidth, subHeight, wrap)\n            if self.variableDimension == 0:\n                widthOffset += want\n            else:\n                heightOffset += want\n\n\n\nclass HBox(_Box):\n    variableDimension = 0\n\n\n\nclass VBox(_Box):\n    variableDimension = 1\n\n\n\nclass Packer(ContainerWidget):\n    def render(self, width, height, terminal):\n        if not self.children:\n            return\n\n        root = int(len(self.children) ** 0.5 + 0.5)\n        boxes = [VBox() for n in range(root)]\n        for n, ch in enumerate(self.children):\n            boxes[n % len(boxes)].addChild(ch)\n        h = HBox()\n        map(h.addChild, boxes)\n        h.render(width, height, terminal)\n\n\n\nclass Canvas(Widget):\n    focused = False\n\n    contents = None\n\n    def __init__(self):\n        Widget.__init__(self)\n        self.resize(1, 1)\n\n\n    def resize(self, width, height):\n        contents = array.array('B', b' ' * width * height)\n        if self.contents is not None:\n            for x in range(min(width, self._width)):\n                for y in range(min(height, self._height)):\n                    contents[width * y + x] = self[x, y]\n        self.contents = contents\n        self._width = width\n        self._height = height\n        if self.x >= width:\n            self.x = width - 1\n        if self.y >= height:\n            self.y = height - 1\n\n\n    def __getitem__(self, index):\n        (x, y) = index\n        return self.contents[(self._width * y) + x]\n\n\n    def __setitem__(self, index, value):\n        (x, y) = index\n        self.contents[(self._width * y) + x] = value\n\n\n    def clear(self):\n        self.contents = array.array('B', b' ' * len(self.contents))\n\n\n    def render(self, width, height, terminal):\n        if not width or not height:\n            return\n\n        if width != self._width or height != self._height:\n            self.resize(width, height)\n        for i in range(height):\n            terminal.cursorPosition(0, i)\n            if _PY3:\n                text = self.contents[self._width * i:\n                                     self._width * i + self._width\n                                    ].tobytes()\n            else:\n                text = self.contents[self._width * i:\n                                     self._width * i + self._width\n                                    ].tostring()\n            text = text[:width]\n            terminal.write(text)\n\n\n\ndef horizontalLine(terminal, y, left, right):\n    terminal.selectCharacterSet(insults.CS_DRAWING, insults.G0)\n    terminal.cursorPosition(left, y)\n    terminal.write(chr(0o161) * (right - left))\n    terminal.selectCharacterSet(insults.CS_US, insults.G0)\n\n\n\ndef verticalLine(terminal, x, top, bottom):\n    terminal.selectCharacterSet(insults.CS_DRAWING, insults.G0)\n    for n in range(top, bottom):\n        terminal.cursorPosition(x, n)\n        terminal.write(chr(0o170))\n    terminal.selectCharacterSet(insults.CS_US, insults.G0)\n\n\ndef rectangle(terminal, position, dimension):\n    \"\"\"\n    Draw a rectangle\n\n    @type position: L{tuple}\n    @param position: A tuple of the (top, left) coordinates of the rectangle.\n    @type dimension: L{tuple}\n    @param dimension: A tuple of the (width, height) size of the rectangle.\n    \"\"\"\n    (top, left) = position\n    (width, height) = dimension\n    terminal.selectCharacterSet(insults.CS_DRAWING, insults.G0)\n\n    terminal.cursorPosition(top, left)\n    terminal.write(chr(0o154))\n    terminal.write(chr(0o161) * (width - 2))\n    terminal.write(chr(0o153))\n    for n in range(height - 2):\n        terminal.cursorPosition(left, top + n + 1)\n        terminal.write(chr(0o170))\n        terminal.cursorForward(width - 2)\n        terminal.write(chr(0o170))\n    terminal.cursorPosition(0, top + height - 1)\n    terminal.write(chr(0o155))\n    terminal.write(chr(0o161) * (width - 2))\n    terminal.write(chr(0o152))\n\n    terminal.selectCharacterSet(insults.CS_US, insults.G0)\n\n\n\nclass Border(Widget):\n    def __init__(self, containee):\n        Widget.__init__(self)\n        self.containee = containee\n        self.containee.parent = self\n\n\n    def focusReceived(self):\n        return self.containee.focusReceived()\n\n\n    def focusLost(self):\n        return self.containee.focusLost()\n\n\n    def keystrokeReceived(self, keyID, modifier):\n        return self.containee.keystrokeReceived(keyID, modifier)\n\n\n    def sizeHint(self):\n        hint = self.containee.sizeHint()\n        if hint is None:\n            hint = (None, None)\n        if hint[0] is None:\n            x = None\n        else:\n            x = hint[0] + 2\n        if hint[1] is None:\n            y = None\n        else:\n            y = hint[1] + 2\n        return x, y\n\n\n    def filthy(self):\n        self.containee.filthy()\n        Widget.filthy(self)\n\n\n    def render(self, width, height, terminal):\n        if self.containee.focused:\n            terminal.write(b'\\x1b[31m')\n        rectangle(terminal, (0, 0), (width, height))\n        terminal.write(b'\\x1b[0m')\n        wrap = BoundedTerminalWrapper(terminal, width - 2, height - 2, 1, 1)\n        self.containee.draw(width - 2, height - 2, wrap)\n\n\n\nclass Button(Widget):\n    def __init__(self, label, onPress):\n        Widget.__init__(self)\n        self.label = label\n        self.onPress = onPress\n\n\n    def sizeHint(self):\n        return len(self.label), 1\n\n\n    def characterReceived(self, keyID, modifier):\n        if keyID == b'\\r':\n            self.onPress()\n\n\n    def render(self, width, height, terminal):\n        terminal.cursorPosition(0, 0)\n        if self.focused:\n            terminal.write(b'\\x1b[1m' + self.label + b'\\x1b[0m')\n        else:\n            terminal.write(self.label)\n\n\n\nclass TextInput(Widget):\n    def __init__(self, maxwidth, onSubmit):\n        Widget.__init__(self)\n        self.onSubmit = onSubmit\n        self.maxwidth = maxwidth\n        self.buffer = b''\n        self.cursor = 0\n\n\n    def setText(self, text):\n        self.buffer = text[:self.maxwidth]\n        self.cursor = len(self.buffer)\n        self.repaint()\n\n\n    def func_LEFT_ARROW(self, modifier):\n        if self.cursor > 0:\n            self.cursor -= 1\n            self.repaint()\n\n\n    def func_RIGHT_ARROW(self, modifier):\n        if self.cursor < len(self.buffer):\n            self.cursor += 1\n            self.repaint()\n\n\n    def backspaceReceived(self):\n        if self.cursor > 0:\n            self.buffer = self.buffer[:self.cursor - 1] + self.buffer[self.cursor:]\n            self.cursor -= 1\n            self.repaint()\n\n\n    def characterReceived(self, keyID, modifier):\n        if keyID == b'\\r':\n            self.onSubmit(self.buffer)\n        else:\n            if len(self.buffer) < self.maxwidth:\n                self.buffer = self.buffer[:self.cursor] + keyID + self.buffer[self.cursor:]\n                self.cursor += 1\n                self.repaint()\n\n\n    def sizeHint(self):\n        return self.maxwidth + 1, 1\n\n\n    def render(self, width, height, terminal):\n        currentText = self._renderText()\n        terminal.cursorPosition(0, 0)\n        if self.focused:\n            terminal.write(currentText[:self.cursor])\n            cursor(terminal, currentText[self.cursor:self.cursor+1] or b' ')\n            terminal.write(currentText[self.cursor+1:])\n            terminal.write(b' ' * (self.maxwidth - len(currentText) + 1))\n        else:\n            more = self.maxwidth - len(currentText)\n            terminal.write(currentText + b'_' * more)\n\n\n    def _renderText(self):\n        return self.buffer\n\n\n\nclass PasswordInput(TextInput):\n    def _renderText(self):\n        return '*' * len(self.buffer)\n\n\n\nclass TextOutput(Widget):\n    text = b''\n\n    def __init__(self, size=None):\n        Widget.__init__(self)\n        self.size = size\n\n\n\n    def sizeHint(self):\n        return self.size\n\n\n\n    def render(self, width, height, terminal):\n        terminal.cursorPosition(0, 0)\n        text = self.text[:width]\n        terminal.write(text + b' ' * (width - len(text)))\n\n\n\n    def setText(self, text):\n        self.text = text\n        self.repaint()\n\n\n    def focusReceived(self):\n        raise YieldFocus()\n\n\n\nclass TextOutputArea(TextOutput):\n    WRAP, TRUNCATE = range(2)\n\n    def __init__(self, size=None, longLines=WRAP):\n        TextOutput.__init__(self, size)\n        self.longLines = longLines\n\n\n    def render(self, width, height, terminal):\n        n = 0\n        inputLines = self.text.splitlines()\n        outputLines = []\n        while inputLines:\n            if self.longLines == self.WRAP:\n                line = inputLines.pop(0)\n                if not isinstance(line, str):\n                    line = line.decode(\"utf-8\")\n                wrappedLines = []\n                for wrappedLine in tptext.greedyWrap(line, width):\n                    if not isinstance(wrappedLine, bytes):\n                        wrappedLine = wrappedLine.encode(\"utf-8\")\n                    wrappedLines.append(wrappedLine)\n                outputLines.extend(wrappedLines or [b''])\n            else:\n                outputLines.append(inputLines.pop(0)[:width])\n            if len(outputLines) >= height:\n                break\n        for n, L in enumerate(outputLines[:height]):\n            terminal.cursorPosition(0, n)\n            terminal.write(L)\n\n\n\nclass Viewport(Widget):\n    _xOffset = 0\n    _yOffset = 0\n\n    def xOffset():\n        def get(self):\n            return self._xOffset\n        def set(self, value):\n            if self._xOffset != value:\n                self._xOffset = value\n                self.repaint()\n        return get, set\n    xOffset = property(*xOffset())\n\n\n    def yOffset():\n        def get(self):\n            return self._yOffset\n        def set(self, value):\n            if self._yOffset != value:\n                self._yOffset = value\n                self.repaint()\n        return get, set\n    yOffset = property(*yOffset())\n\n    _width = 160\n    _height = 24\n\n\n    def __init__(self, containee):\n        Widget.__init__(self)\n        self.containee = containee\n        self.containee.parent = self\n\n        self._buf = helper.TerminalBuffer()\n        self._buf.width = self._width\n        self._buf.height = self._height\n        self._buf.connectionMade()\n\n\n    def filthy(self):\n        self.containee.filthy()\n        Widget.filthy(self)\n\n\n    def render(self, width, height, terminal):\n        self.containee.draw(self._width, self._height, self._buf)\n\n        # XXX /Lame/\n        for y, line in enumerate(self._buf.lines[self._yOffset:self._yOffset + height]):\n            terminal.cursorPosition(0, y)\n            n = 0\n            for n, (ch, attr) in enumerate(line[self._xOffset:self._xOffset + width]):\n                if ch is self._buf.void:\n                    ch = b' '\n                terminal.write(ch)\n            if n < width:\n                terminal.write(b' ' * (width - n - 1))\n\n\n\nclass _Scrollbar(Widget):\n    def __init__(self, onScroll):\n        Widget.__init__(self)\n        self.onScroll = onScroll\n        self.percent = 0.0\n\n\n    def smaller(self):\n        self.percent = min(1.0, max(0.0, self.onScroll(-1)))\n        self.repaint()\n\n\n    def bigger(self):\n        self.percent = min(1.0, max(0.0, self.onScroll(+1)))\n        self.repaint()\n\n\n\nclass HorizontalScrollbar(_Scrollbar):\n    def sizeHint(self):\n        return (None, 1)\n\n\n    def func_LEFT_ARROW(self, modifier):\n        self.smaller()\n\n\n    def func_RIGHT_ARROW(self, modifier):\n        self.bigger()\n\n    _left = u'\\N{BLACK LEFT-POINTING TRIANGLE}'\n    _right = u'\\N{BLACK RIGHT-POINTING TRIANGLE}'\n    _bar = u'\\N{LIGHT SHADE}'\n    _slider = u'\\N{DARK SHADE}'\n\n\n    def render(self, width, height, terminal):\n        terminal.cursorPosition(0, 0)\n        n = width - 3\n        before = int(n * self.percent)\n        after = n - before\n        me = self._left + (self._bar * before) + self._slider + (self._bar * after) + self._right\n        terminal.write(me.encode('utf-8'))\n\n\n\nclass VerticalScrollbar(_Scrollbar):\n    def sizeHint(self):\n        return (1, None)\n\n\n    def func_UP_ARROW(self, modifier):\n        self.smaller()\n\n\n    def func_DOWN_ARROW(self, modifier):\n        self.bigger()\n\n    _up = u'\\N{BLACK UP-POINTING TRIANGLE}'\n    _down = u'\\N{BLACK DOWN-POINTING TRIANGLE}'\n    _bar = u'\\N{LIGHT SHADE}'\n    _slider = u'\\N{DARK SHADE}'\n\n\n    def render(self, width, height, terminal):\n        terminal.cursorPosition(0, 0)\n        knob = int(self.percent * (height - 2))\n        terminal.write(self._up.encode('utf-8'))\n        for i in range(1, height - 1):\n            terminal.cursorPosition(0, i)\n            if i != (knob + 1):\n                terminal.write(self._bar.encode('utf-8'))\n            else:\n                terminal.write(self._slider.encode('utf-8'))\n        terminal.cursorPosition(0, height - 1)\n        terminal.write(self._down.encode('utf-8'))\n\n\n\nclass ScrolledArea(Widget):\n    \"\"\"\n    A L{ScrolledArea} contains another widget wrapped in a viewport and\n    vertical and horizontal scrollbars for moving the viewport around.\n    \"\"\"\n    def __init__(self, containee):\n        Widget.__init__(self)\n        self._viewport = Viewport(containee)\n        self._horiz = HorizontalScrollbar(self._horizScroll)\n        self._vert = VerticalScrollbar(self._vertScroll)\n\n        for w in self._viewport, self._horiz, self._vert:\n            w.parent = self\n\n\n    def _horizScroll(self, n):\n        self._viewport.xOffset += n\n        self._viewport.xOffset = max(0, self._viewport.xOffset)\n        return self._viewport.xOffset / 25.0\n\n\n    def _vertScroll(self, n):\n        self._viewport.yOffset += n\n        self._viewport.yOffset = max(0, self._viewport.yOffset)\n        return self._viewport.yOffset / 25.0\n\n\n    def func_UP_ARROW(self, modifier):\n        self._vert.smaller()\n\n\n    def func_DOWN_ARROW(self, modifier):\n        self._vert.bigger()\n\n\n    def func_LEFT_ARROW(self, modifier):\n        self._horiz.smaller()\n\n\n    def func_RIGHT_ARROW(self, modifier):\n        self._horiz.bigger()\n\n\n    def filthy(self):\n        self._viewport.filthy()\n        self._horiz.filthy()\n        self._vert.filthy()\n        Widget.filthy(self)\n\n\n    def render(self, width, height, terminal):\n        wrapper = BoundedTerminalWrapper(terminal, width - 2, height - 2, 1, 1)\n        self._viewport.draw(width - 2, height - 2, wrapper)\n        if self.focused:\n            terminal.write(b'\\x1b[31m')\n        horizontalLine(terminal, 0, 1, width - 1)\n        verticalLine(terminal, 0, 1, height - 1)\n        self._vert.draw(1, height - 1, BoundedTerminalWrapper(terminal, 1, height - 1, width - 1, 0))\n        self._horiz.draw(width, 1, BoundedTerminalWrapper(terminal, width, 1, 0, height - 1))\n        terminal.write(b'\\x1b[0m')\n\n\n\ndef cursor(terminal, ch):\n    terminal.saveCursor()\n    terminal.selectGraphicRendition(str(insults.REVERSE_VIDEO))\n    terminal.write(ch)\n    terminal.restoreCursor()\n    terminal.cursorForward()\n\n\n\nclass Selection(Widget):\n    # Index into the sequence\n    focusedIndex = 0\n\n    # Offset into the displayed subset of the sequence\n    renderOffset = 0\n\n    def __init__(self, sequence, onSelect, minVisible=None):\n        Widget.__init__(self)\n        self.sequence = sequence\n        self.onSelect = onSelect\n        self.minVisible = minVisible\n        if minVisible is not None:\n            self._width = max(map(len, self.sequence))\n\n\n    def sizeHint(self):\n        if self.minVisible is not None:\n            return self._width, self.minVisible\n\n\n    def func_UP_ARROW(self, modifier):\n        if self.focusedIndex > 0:\n            self.focusedIndex -= 1\n            if self.renderOffset > 0:\n                self.renderOffset -= 1\n            self.repaint()\n\n\n    def func_PGUP(self, modifier):\n        if self.renderOffset != 0:\n            self.focusedIndex -= self.renderOffset\n            self.renderOffset = 0\n        else:\n            self.focusedIndex = max(0, self.focusedIndex - self.height)\n        self.repaint()\n\n\n    def func_DOWN_ARROW(self, modifier):\n        if self.focusedIndex < len(self.sequence) - 1:\n            self.focusedIndex += 1\n            if self.renderOffset < self.height - 1:\n                self.renderOffset += 1\n            self.repaint()\n\n\n    def func_PGDN(self, modifier):\n        if self.renderOffset != self.height - 1:\n            change = self.height - self.renderOffset - 1\n            if change + self.focusedIndex >= len(self.sequence):\n                change = len(self.sequence) - self.focusedIndex - 1\n            self.focusedIndex += change\n            self.renderOffset = self.height - 1\n        else:\n            self.focusedIndex = min(len(self.sequence) - 1, self.focusedIndex + self.height)\n        self.repaint()\n\n\n    def characterReceived(self, keyID, modifier):\n        if keyID == b'\\r':\n            self.onSelect(self.sequence[self.focusedIndex])\n\n\n    def render(self, width, height, terminal):\n        self.height = height\n        start = self.focusedIndex - self.renderOffset\n        if start > len(self.sequence) - height:\n            start = max(0, len(self.sequence) - height)\n\n        elements = self.sequence[start:start+height]\n\n        for n, ele in enumerate(elements):\n            terminal.cursorPosition(0, n)\n            if n == self.renderOffset:\n                terminal.saveCursor()\n                if self.focused:\n                    modes = str(insults.REVERSE_VIDEO), str(insults.BOLD)\n                else:\n                    modes = str(insults.REVERSE_VIDEO),\n                terminal.selectGraphicRendition(*modes)\n            text = ele[:width]\n            terminal.write(text + (b' ' * (width - len(text))))\n            if n == self.renderOffset:\n                terminal.restoreCursor()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/interfaces.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module contains interfaces defined for the L{twisted.conch} package.\n\"\"\"\n\nfrom zope.interface import Interface, Attribute\n\nclass IConchUser(Interface):\n    \"\"\"\n    A user who has been authenticated to Cred through Conch.  This is\n    the interface between the SSH connection and the user.\n    \"\"\"\n\n    conn = Attribute('The SSHConnection object for this user.')\n\n    def lookupChannel(channelType, windowSize, maxPacket, data):\n        \"\"\"\n        The other side requested a channel of some sort.\n\n        C{channelType} is the type of channel being requested,\n        as an ssh connection protocol channel type.\n        C{data} is any other packet data (often nothing).\n\n        We return a subclass of L{SSHChannel<ssh.channel.SSHChannel>}.  If\n        the channel type is unknown, we return C{None}.\n\n        For other failures, we raise an exception. If a\n        L{ConchError<error.ConchError>} is raised, the C{.value} will\n        be the message, and the C{.data} will be the error code.\n\n        @param channelType: The requested channel type\n        @type channelType:  L{bytes}\n        @param windowSize:  The initial size of the remote window\n        @type windowSize:   L{int}\n        @param maxPacket:   The largest packet we should send\n        @type maxPacket:    L{int}\n        @param data:        Additional request data\n        @type data:         L{bytes}\n        @rtype:             a subclass of L{SSHChannel} or L{None}\n        \"\"\"\n\n    def lookupSubsystem(subsystem, data):\n        \"\"\"\n        The other side requested a subsystem.\n\n        We return a L{Protocol} implementing the requested subsystem.\n        If the subsystem is not available, we return C{None}.\n\n        @param subsystem: The name of the subsystem being requested\n        @type subsystem: L{bytes}\n        @param data:     Additional request data (often nothing)\n        @type data:      L{bytes}\n        @rtype:          L{Protocol} or L{None}\n        \"\"\"\n\n    def gotGlobalRequest(requestType, data):\n        \"\"\"\n        A global request was sent from the other side.\n\n        We return a true value on success or a false value on failure.\n        If we indicate success by returning a tuple, its second item\n        will be sent to the other side as additional response data.\n\n        @param requestType: The type of the request\n        @type requestType:  L{bytes}\n        @param data:        Additional request data\n        @type data:         L{bytes}\n        @rtype:             boolean or L{tuple}\n        \"\"\"\n\n\n\nclass ISession(Interface):\n\n    def getPty(term, windowSize, modes):\n        \"\"\"\n        Get a pseudo-terminal for use by a shell or command.\n\n        If a pseudo-terminal is not available, or the request otherwise\n        fails, raise an exception.\n        \"\"\"\n\n    def openShell(proto):\n        \"\"\"\n        Open a shell and connect it to proto.\n\n        @param proto: a L{ProcessProtocol} instance.\n        \"\"\"\n\n    def execCommand(proto, command):\n        \"\"\"\n        Execute a command.\n\n        @param proto: a L{ProcessProtocol} instance.\n        \"\"\"\n\n    def windowChanged(newWindowSize):\n        \"\"\"\n        Called when the size of the remote screen has changed.\n        \"\"\"\n\n    def eofReceived():\n        \"\"\"\n        Called when the other side has indicated no more data will be sent.\n        \"\"\"\n\n    def closed():\n        \"\"\"\n        Called when the session is closed.\n        \"\"\"\n\n\n\nclass ISFTPServer(Interface):\n    \"\"\"\n    SFTP subsystem for server-side communication.\n\n    Each method should check to verify that the user has permission for\n    their actions.\n    \"\"\"\n\n    avatar = Attribute(\n        \"\"\"\n        The avatar returned by the Realm that we are authenticated with,\n        and represents the logged-in user.\n        \"\"\")\n\n\n    def gotVersion(otherVersion, extData):\n        \"\"\"\n        Called when the client sends their version info.\n\n        otherVersion is an integer representing the version of the SFTP\n        protocol they are claiming.\n        extData is a dictionary of extended_name : extended_data items.\n        These items are sent by the client to indicate additional features.\n\n        This method should return a dictionary of extended_name : extended_data\n        items.  These items are the additional features (if any) supported\n        by the server.\n        \"\"\"\n        return {}\n\n\n    def openFile(filename, flags, attrs):\n        \"\"\"\n        Called when the clients asks to open a file.\n\n        @param filename: a string representing the file to open.\n\n        @param flags: an integer of the flags to open the file with, ORed together.\n        The flags and their values are listed at the bottom of this file.\n\n        @param attrs: a list of attributes to open the file with.  It is a\n        dictionary, consisting of 0 or more keys.  The possible keys are::\n\n            size: the size of the file in bytes\n            uid: the user ID of the file as an integer\n            gid: the group ID of the file as an integer\n            permissions: the permissions of the file with as an integer.\n            the bit representation of this field is defined by POSIX.\n            atime: the access time of the file as seconds since the epoch.\n            mtime: the modification time of the file as seconds since the epoch.\n            ext_*: extended attributes.  The server is not required to\n            understand this, but it may.\n\n        NOTE: there is no way to indicate text or binary files.  it is up\n        to the SFTP client to deal with this.\n\n        This method returns an object that meets the ISFTPFile interface.\n        Alternatively, it can return a L{Deferred} that will be called back\n        with the object.\n        \"\"\"\n\n\n    def removeFile(filename):\n        \"\"\"\n        Remove the given file.\n\n        This method returns when the remove succeeds, or a Deferred that is\n        called back when it succeeds.\n\n        @param filename: the name of the file as a string.\n        \"\"\"\n\n\n    def renameFile(oldpath, newpath):\n        \"\"\"\n        Rename the given file.\n\n        This method returns when the rename succeeds, or a L{Deferred} that is\n        called back when it succeeds. If the rename fails, C{renameFile} will\n        raise an implementation-dependent exception.\n\n        @param oldpath: the current location of the file.\n        @param newpath: the new file name.\n        \"\"\"\n\n\n    def makeDirectory(path, attrs):\n        \"\"\"\n        Make a directory.\n\n        This method returns when the directory is created, or a Deferred that\n        is called back when it is created.\n\n        @param path: the name of the directory to create as a string.\n        @param attrs: a dictionary of attributes to create the directory with.\n        Its meaning is the same as the attrs in the L{openFile} method.\n        \"\"\"\n\n\n    def removeDirectory(path):\n        \"\"\"\n        Remove a directory (non-recursively)\n\n        It is an error to remove a directory that has files or directories in\n        it.\n\n        This method returns when the directory is removed, or a Deferred that\n        is called back when it is removed.\n\n        @param path: the directory to remove.\n        \"\"\"\n\n\n    def openDirectory(path):\n        \"\"\"\n        Open a directory for scanning.\n\n        This method returns an iterable object that has a close() method,\n        or a Deferred that is called back with same.\n\n        The close() method is called when the client is finished reading\n        from the directory.  At this point, the iterable will no longer\n        be used.\n\n        The iterable should return triples of the form (filename,\n        longname, attrs) or Deferreds that return the same.  The\n        sequence must support __getitem__, but otherwise may be any\n        'sequence-like' object.\n\n        filename is the name of the file relative to the directory.\n        logname is an expanded format of the filename.  The recommended format\n        is:\n        -rwxr-xr-x   1 mjos     staff      348911 Mar 25 14:29 t-filexfer\n        1234567890 123 12345678 12345678 12345678 123456789012\n\n        The first line is sample output, the second is the length of the field.\n        The fields are: permissions, link count, user owner, group owner,\n        size in bytes, modification time.\n\n        attrs is a dictionary in the format of the attrs argument to openFile.\n\n        @param path: the directory to open.\n        \"\"\"\n\n\n    def getAttrs(path, followLinks):\n        \"\"\"\n        Return the attributes for the given path.\n\n        This method returns a dictionary in the same format as the attrs\n        argument to openFile or a Deferred that is called back with same.\n\n        @param path: the path to return attributes for as a string.\n        @param followLinks: a boolean.  If it is True, follow symbolic links\n        and return attributes for the real path at the base.  If it is False,\n        return attributes for the specified path.\n        \"\"\"\n\n\n    def setAttrs(path, attrs):\n        \"\"\"\n        Set the attributes for the path.\n\n        This method returns when the attributes are set or a Deferred that is\n        called back when they are.\n\n        @param path: the path to set attributes for as a string.\n        @param attrs: a dictionary in the same format as the attrs argument to\n        L{openFile}.\n        \"\"\"\n\n\n    def readLink(path):\n        \"\"\"\n        Find the root of a set of symbolic links.\n\n        This method returns the target of the link, or a Deferred that\n        returns the same.\n\n        @param path: the path of the symlink to read.\n        \"\"\"\n\n\n    def makeLink(linkPath, targetPath):\n        \"\"\"\n        Create a symbolic link.\n\n        This method returns when the link is made, or a Deferred that\n        returns the same.\n\n        @param linkPath: the pathname of the symlink as a string.\n        @param targetPath: the path of the target of the link as a string.\n        \"\"\"\n\n\n    def realPath(path):\n        \"\"\"\n        Convert any path to an absolute path.\n\n        This method returns the absolute path as a string, or a Deferred\n        that returns the same.\n\n        @param path: the path to convert as a string.\n        \"\"\"\n\n\n    def extendedRequest(extendedName, extendedData):\n        \"\"\"\n        This is the extension mechanism for SFTP.  The other side can send us\n        arbitrary requests.\n\n        If we don't implement the request given by extendedName, raise\n        NotImplementedError.\n\n        The return value is a string, or a Deferred that will be called\n        back with a string.\n\n        @param extendedName: the name of the request as a string.\n        @param extendedData: the data the other side sent with the request,\n        as a string.\n        \"\"\"\n\n\n\nclass IKnownHostEntry(Interface):\n    \"\"\"\n    A L{IKnownHostEntry} is an entry in an OpenSSH-formatted C{known_hosts}\n    file.\n\n    @since: 8.2\n    \"\"\"\n\n    def matchesKey(key):\n        \"\"\"\n        Return True if this entry matches the given Key object, False\n        otherwise.\n\n        @param key: The key object to match against.\n        @type key: L{twisted.conch.ssh.keys.Key}\n        \"\"\"\n\n\n    def matchesHost(hostname):\n        \"\"\"\n        Return True if this entry matches the given hostname, False otherwise.\n\n        Note that this does no name resolution; if you want to match an IP\n        address, you have to resolve it yourself, and pass it in as a dotted\n        quad string.\n\n        @param key: The hostname to match against.\n        @type key: L{str}\n        \"\"\"\n\n\n    def toString():\n        \"\"\"\n\n        @return: a serialized string representation of this entry, suitable for\n        inclusion in a known_hosts file.  (Newline not included.)\n\n        @rtype: L{str}\n        \"\"\"\n\n\n\nclass ISFTPFile(Interface):\n    \"\"\"\n    This represents an open file on the server.  An object adhering to this\n    interface should be returned from L{openFile}().\n    \"\"\"\n\n    def close():\n        \"\"\"\n        Close the file.\n\n        This method returns nothing if the close succeeds immediately, or a\n        Deferred that is called back when the close succeeds.\n        \"\"\"\n\n\n    def readChunk(offset, length):\n        \"\"\"\n        Read from the file.\n\n        If EOF is reached before any data is read, raise EOFError.\n\n        This method returns the data as a string, or a Deferred that is\n        called back with same.\n\n        @param offset: an integer that is the index to start from in the file.\n        @param length: the maximum length of data to return.  The actual amount\n        returned may less than this.  For normal disk files, however,\n        this should read the requested number (up to the end of the file).\n        \"\"\"\n\n\n    def writeChunk(offset, data):\n        \"\"\"\n        Write to the file.\n\n        This method returns when the write completes, or a Deferred that is\n        called when it completes.\n\n        @param offset: an integer that is the index to start from in the file.\n        @param data: a string that is the data to write.\n        \"\"\"\n\n\n    def getAttrs():\n        \"\"\"\n        Return the attributes for the file.\n\n        This method returns a dictionary in the same format as the attrs\n        argument to L{openFile} or a L{Deferred} that is called back with same.\n        \"\"\"\n\n\n    def setAttrs(attrs):\n        \"\"\"\n        Set the attributes for the file.\n\n        This method returns when the attributes are set or a Deferred that is\n        called back when they are.\n\n        @param attrs: a dictionary in the same format as the attrs argument to\n        L{openFile}.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ls.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_cftp -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nimport array\nimport stat\n\nfrom time import time, strftime, localtime\nfrom twisted.python.compat import _PY3\n\n# Locale-independent month names to use instead of strftime's\n_MONTH_NAMES = dict(list(zip(\n        list(range(1, 13)),\n        \"Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec\".split())))\n\n\ndef lsLine(name, s):\n    \"\"\"\n    Build an 'ls' line for a file ('file' in its generic sense, it\n    can be of any type).\n    \"\"\"\n    mode = s.st_mode\n    perms = array.array('B', b'-'*10)\n    ft = stat.S_IFMT(mode)\n    if stat.S_ISDIR(ft): perms[0] = ord('d')\n    elif stat.S_ISCHR(ft): perms[0] = ord('c')\n    elif stat.S_ISBLK(ft): perms[0] = ord('b')\n    elif stat.S_ISREG(ft): perms[0] = ord('-')\n    elif stat.S_ISFIFO(ft): perms[0] = ord('f')\n    elif stat.S_ISLNK(ft): perms[0] = ord('l')\n    elif stat.S_ISSOCK(ft): perms[0] = ord('s')\n    else: perms[0] = ord('!')\n    # User\n    if mode&stat.S_IRUSR:perms[1] = ord('r')\n    if mode&stat.S_IWUSR:perms[2] = ord('w')\n    if mode&stat.S_IXUSR:perms[3] = ord('x')\n    # Group\n    if mode&stat.S_IRGRP:perms[4] = ord('r')\n    if mode&stat.S_IWGRP:perms[5] = ord('w')\n    if mode&stat.S_IXGRP:perms[6] = ord('x')\n    # Other\n    if mode&stat.S_IROTH:perms[7] = ord('r')\n    if mode&stat.S_IWOTH:perms[8] = ord('w')\n    if mode&stat.S_IXOTH:perms[9] = ord('x')\n    # Suid/sgid\n    if mode&stat.S_ISUID:\n        if perms[3] == ord('x'): perms[3] = ord('s')\n        else: perms[3] = ord('S')\n    if mode&stat.S_ISGID:\n        if perms[6] == ord('x'): perms[6] = ord('s')\n        else: perms[6] = ord('S')\n\n    if _PY3:\n        if isinstance(name, bytes):\n            name = name.decode(\"utf-8\")\n        lsPerms = perms.tobytes()\n        lsPerms = lsPerms.decode(\"utf-8\")\n    else:\n        lsPerms = perms.tostring()\n\n    lsresult = [\n        lsPerms,\n        str(s.st_nlink).rjust(5),\n        ' ',\n        str(s.st_uid).ljust(9),\n        str(s.st_gid).ljust(9),\n        str(s.st_size).rjust(8),\n        ' ',\n    ]\n    # Need to specify the month manually, as strftime depends on locale\n    ttup = localtime(s.st_mtime)\n    sixmonths = 60 * 60 * 24 * 7 * 26\n    if s.st_mtime + sixmonths < time(): # Last edited more than 6mo ago\n        strtime = strftime(\"%%s %d  %Y \", ttup)\n    else:\n        strtime = strftime(\"%%s %d %H:%M \", ttup)\n    lsresult.append(strtime % (_MONTH_NAMES[ttup[1]],))\n\n    lsresult.append(name)\n    return ''.join(lsresult)\n\n\n__all__ = ['lsLine']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/manhole.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_manhole -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nLine-input oriented interactive interpreter loop.\n\nProvides classes for handling Python source input and arbitrary output\ninteractively from a Twisted application.  Also included is syntax coloring\ncode with support for VT102 terminals, control code handling (^C, ^D, ^Q),\nand reasonable handling of Deferreds.\n\n@author: Jp Calderone\n\"\"\"\n\nimport code, sys, tokenize\nfrom io import BytesIO\n\nfrom twisted.conch import recvline\n\nfrom twisted.internet import defer\nfrom twisted.python.compat import _tokenize, _get_async_param\nfrom twisted.python.htmlizer import TokenPrinter\n\n\n\nclass FileWrapper:\n    \"\"\"\n    Minimal write-file-like object.\n\n    Writes are translated into addOutput calls on an object passed to\n    __init__.  Newlines are also converted from network to local style.\n    \"\"\"\n\n    softspace = 0\n    state = 'normal'\n\n    def __init__(self, o):\n        self.o = o\n\n\n    def flush(self):\n        pass\n\n\n    def write(self, data):\n        self.o.addOutput(data.replace('\\r\\n', '\\n'))\n\n\n    def writelines(self, lines):\n        self.write(''.join(lines))\n\n\n\nclass ManholeInterpreter(code.InteractiveInterpreter):\n    \"\"\"\n    Interactive Interpreter with special output and Deferred support.\n\n    Aside from the features provided by L{code.InteractiveInterpreter}, this\n    class captures sys.stdout output and redirects it to the appropriate\n    location (the Manhole protocol instance).  It also treats Deferreds\n    which reach the top-level specially: each is formatted to the user with\n    a unique identifier and a new callback and errback added to it, each of\n    which will format the unique identifier and the result with which the\n    Deferred fires and then pass it on to the next participant in the\n    callback chain.\n    \"\"\"\n\n    numDeferreds = 0\n    def __init__(self, handler, locals=None, filename=\"<console>\"):\n        code.InteractiveInterpreter.__init__(self, locals)\n        self._pendingDeferreds = {}\n        self.handler = handler\n        self.filename = filename\n        self.resetBuffer()\n\n\n    def resetBuffer(self):\n        \"\"\"\n        Reset the input buffer.\n        \"\"\"\n        self.buffer = []\n\n\n    def push(self, line):\n        \"\"\"\n        Push a line to the interpreter.\n\n        The line should not have a trailing newline; it may have\n        internal newlines.  The line is appended to a buffer and the\n        interpreter's runsource() method is called with the\n        concatenated contents of the buffer as source.  If this\n        indicates that the command was executed or invalid, the buffer\n        is reset; otherwise, the command is incomplete, and the buffer\n        is left as it was after the line was appended.  The return\n        value is 1 if more input is required, 0 if the line was dealt\n        with in some way (this is the same as runsource()).\n\n        @param line: line of text\n        @type line: L{bytes}\n        @return: L{bool} from L{code.InteractiveInterpreter.runsource}\n        \"\"\"\n        self.buffer.append(line)\n        source = b\"\\n\".join(self.buffer)\n        source = source.decode(\"utf-8\")\n        more = self.runsource(source, self.filename)\n        if not more:\n            self.resetBuffer()\n        return more\n\n\n    def runcode(self, *a, **kw):\n        orighook, sys.displayhook = sys.displayhook, self.displayhook\n        try:\n            origout, sys.stdout = sys.stdout, FileWrapper(self.handler)\n            try:\n                code.InteractiveInterpreter.runcode(self, *a, **kw)\n            finally:\n                sys.stdout = origout\n        finally:\n            sys.displayhook = orighook\n\n\n    def displayhook(self, obj):\n        self.locals['_'] = obj\n        if isinstance(obj, defer.Deferred):\n            # XXX Ick, where is my \"hasFired()\" interface?\n            if hasattr(obj, \"result\"):\n                self.write(repr(obj))\n            elif id(obj) in self._pendingDeferreds:\n                self.write(\"<Deferred #%d>\" % (self._pendingDeferreds[id(obj)][0],))\n            else:\n                d = self._pendingDeferreds\n                k = self.numDeferreds\n                d[id(obj)] = (k, obj)\n                self.numDeferreds += 1\n                obj.addCallbacks(self._cbDisplayDeferred, self._ebDisplayDeferred,\n                                 callbackArgs=(k, obj), errbackArgs=(k, obj))\n                self.write(\"<Deferred #%d>\" % (k,))\n        elif obj is not None:\n            self.write(repr(obj))\n\n\n    def _cbDisplayDeferred(self, result, k, obj):\n        self.write(\"Deferred #%d called back: %r\" % (k, result), True)\n        del self._pendingDeferreds[id(obj)]\n        return result\n\n\n    def _ebDisplayDeferred(self, failure, k, obj):\n        self.write(\"Deferred #%d failed: %r\" % (k, failure.getErrorMessage()), True)\n        del self._pendingDeferreds[id(obj)]\n        return failure\n\n\n    def write(self, data, isAsync=None, **kwargs):\n        isAsync = _get_async_param(isAsync, **kwargs)\n        self.handler.addOutput(data, isAsync)\n\n\n\nCTRL_C = b'\\x03'\nCTRL_D = b'\\x04'\nCTRL_BACKSLASH = b'\\x1c'\nCTRL_L = b'\\x0c'\nCTRL_A = b'\\x01'\nCTRL_E = b'\\x05'\n\n\n\nclass Manhole(recvline.HistoricRecvLine):\n    \"\"\"\n    Mediator between a fancy line source and an interactive interpreter.\n\n    This accepts lines from its transport and passes them on to a\n    L{ManholeInterpreter}.  Control commands (^C, ^D, ^\\) are also handled\n    with something approximating their normal terminal-mode behavior.  It\n    can optionally be constructed with a dict which will be used as the\n    local namespace for any code executed.\n    \"\"\"\n\n    namespace = None\n\n    def __init__(self, namespace=None):\n        recvline.HistoricRecvLine.__init__(self)\n        if namespace is not None:\n            self.namespace = namespace.copy()\n\n\n    def connectionMade(self):\n        recvline.HistoricRecvLine.connectionMade(self)\n        self.interpreter = ManholeInterpreter(self, self.namespace)\n        self.keyHandlers[CTRL_C] = self.handle_INT\n        self.keyHandlers[CTRL_D] = self.handle_EOF\n        self.keyHandlers[CTRL_L] = self.handle_FF\n        self.keyHandlers[CTRL_A] = self.handle_HOME\n        self.keyHandlers[CTRL_E] = self.handle_END\n        self.keyHandlers[CTRL_BACKSLASH] = self.handle_QUIT\n\n\n    def handle_INT(self):\n        \"\"\"\n        Handle ^C as an interrupt keystroke by resetting the current input\n        variables to their initial state.\n        \"\"\"\n        self.pn = 0\n        self.lineBuffer = []\n        self.lineBufferIndex = 0\n        self.interpreter.resetBuffer()\n\n        self.terminal.nextLine()\n        self.terminal.write(b\"KeyboardInterrupt\")\n        self.terminal.nextLine()\n        self.terminal.write(self.ps[self.pn])\n\n\n    def handle_EOF(self):\n        if self.lineBuffer:\n            self.terminal.write(b'\\a')\n        else:\n            self.handle_QUIT()\n\n\n    def handle_FF(self):\n        \"\"\"\n        Handle a 'form feed' byte - generally used to request a screen\n        refresh/redraw.\n        \"\"\"\n        self.terminal.eraseDisplay()\n        self.terminal.cursorHome()\n        self.drawInputLine()\n\n\n    def handle_QUIT(self):\n        self.terminal.loseConnection()\n\n\n    def _needsNewline(self):\n        w = self.terminal.lastWrite\n        return not w.endswith(b'\\n') and not w.endswith(b'\\x1bE')\n\n\n    def addOutput(self, data, isAsync=None, **kwargs):\n        isAsync = _get_async_param(isAsync, **kwargs)\n        if isAsync:\n            self.terminal.eraseLine()\n            self.terminal.cursorBackward(len(self.lineBuffer) +\n                                         len(self.ps[self.pn]))\n\n        self.terminal.write(data)\n\n        if isAsync:\n            if self._needsNewline():\n                self.terminal.nextLine()\n\n            self.terminal.write(self.ps[self.pn])\n\n            if self.lineBuffer:\n                oldBuffer = self.lineBuffer\n                self.lineBuffer = []\n                self.lineBufferIndex = 0\n\n                self._deliverBuffer(oldBuffer)\n\n\n    def lineReceived(self, line):\n        more = self.interpreter.push(line)\n        self.pn = bool(more)\n        if self._needsNewline():\n            self.terminal.nextLine()\n        self.terminal.write(self.ps[self.pn])\n\n\n\nclass VT102Writer:\n    \"\"\"\n    Colorizer for Python tokens.\n\n    A series of tokens are written to instances of this object.  Each is\n    colored in a particular way.  The final line of the result of this is\n    generally added to the output.\n    \"\"\"\n\n    typeToColor = {\n        'identifier': b'\\x1b[31m',\n        'keyword': b'\\x1b[32m',\n        'parameter': b'\\x1b[33m',\n        'variable': b'\\x1b[1;33m',\n        'string': b'\\x1b[35m',\n        'number': b'\\x1b[36m',\n        'op': b'\\x1b[37m'}\n\n    normalColor = b'\\x1b[0m'\n\n    def __init__(self):\n        self.written = []\n\n\n    def color(self, type):\n        r = self.typeToColor.get(type, b'')\n        return r\n\n\n    def write(self, token, type=None):\n        if token and token != b'\\r':\n            c = self.color(type)\n            if c:\n                self.written.append(c)\n            self.written.append(token)\n            if c:\n                self.written.append(self.normalColor)\n\n\n    def __bytes__(self):\n        s = b''.join(self.written)\n        return s.strip(b'\\n').splitlines()[-1]\n\n    if bytes == str:\n        # Compat with Python 2.7\n        __str__ = __bytes__\n\n\n\ndef lastColorizedLine(source):\n    \"\"\"\n    Tokenize and colorize the given Python source.\n\n    Returns a VT102-format colorized version of the last line of C{source}.\n\n    @param source: Python source code\n    @type source: L{str} or L{bytes}\n    @return: L{bytes} of colorized source\n    \"\"\"\n    if not isinstance(source, bytes):\n        source = source.encode(\"utf-8\")\n    w = VT102Writer()\n    p = TokenPrinter(w.write).printtoken\n    s = BytesIO(source)\n\n    for token in _tokenize(s.readline):\n        (tokenType, string, start, end, line) = token\n        p(tokenType, string, start, end, line)\n\n    return bytes(w)\n\n\n\nclass ColoredManhole(Manhole):\n    \"\"\"\n    A REPL which syntax colors input as users type it.\n    \"\"\"\n\n    def getSource(self):\n        \"\"\"\n        Return a string containing the currently entered source.\n\n        This is only the code which will be considered for execution\n        next.\n        \"\"\"\n        return (b'\\n'.join(self.interpreter.buffer) +\n                b'\\n' +\n                b''.join(self.lineBuffer))\n\n\n    def characterReceived(self, ch, moreCharactersComing):\n        if self.mode == 'insert':\n            self.lineBuffer.insert(self.lineBufferIndex, ch)\n        else:\n            self.lineBuffer[self.lineBufferIndex:self.lineBufferIndex+1] = [ch]\n        self.lineBufferIndex += 1\n\n        if moreCharactersComing:\n            # Skip it all, we'll get called with another character in\n            # like 2 femtoseconds.\n            return\n\n        if ch == b' ':\n            # Don't bother to try to color whitespace\n            self.terminal.write(ch)\n            return\n\n        source = self.getSource()\n\n        # Try to write some junk\n        try:\n            coloredLine = lastColorizedLine(source)\n        except tokenize.TokenError:\n            # We couldn't do it.  Strange.  Oh well, just add the character.\n            self.terminal.write(ch)\n        else:\n            # Success!  Clear the source on this line.\n            self.terminal.eraseLine()\n            self.terminal.cursorBackward(len(self.lineBuffer) + len(self.ps[self.pn]) - 1)\n\n            # And write a new, colorized one.\n            self.terminal.write(self.ps[self.pn] + coloredLine)\n\n            # And move the cursor to where it belongs\n            n = len(self.lineBuffer) - self.lineBufferIndex\n            if n:\n                self.terminal.cursorBackward(n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/manhole_ssh.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_manhole -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\ninsults/SSH integration support.\n\n@author: Jp Calderone\n\"\"\"\n\nfrom zope.interface import implementer\n\nfrom twisted.conch import avatar, interfaces as iconch, error as econch\nfrom twisted.conch.ssh import factory, session\nfrom twisted.python import components\n\nfrom twisted.conch.insults import insults\n\n\nclass _Glue:\n    \"\"\"\n    A feeble class for making one attribute look like another.\n\n    This should be replaced with a real class at some point, probably.\n    Try not to write new code that uses it.\n    \"\"\"\n    def __init__(self, **kw):\n        self.__dict__.update(kw)\n\n\n    def __getattr__(self, name):\n        raise AttributeError(self.name, \"has no attribute\", name)\n\n\n\nclass TerminalSessionTransport:\n    def __init__(self, proto, chainedProtocol, avatar, width, height):\n        self.proto = proto\n        self.avatar = avatar\n        self.chainedProtocol = chainedProtocol\n\n        protoSession = self.proto.session\n\n        self.proto.makeConnection(\n            _Glue(write=self.chainedProtocol.dataReceived,\n                  loseConnection=lambda: avatar.conn.sendClose(protoSession),\n                  name=\"SSH Proto Transport\"))\n\n        def loseConnection():\n            self.proto.loseConnection()\n\n        self.chainedProtocol.makeConnection(\n            _Glue(write=self.proto.write,\n                  loseConnection=loseConnection,\n                  name=\"Chained Proto Transport\"))\n\n        # XXX TODO\n        # chainedProtocol is supposed to be an ITerminalTransport,\n        # maybe.  That means perhaps its terminalProtocol attribute is\n        # an ITerminalProtocol, it could be.  So calling terminalSize\n        # on that should do the right thing But it'd be nice to clean\n        # this bit up.\n        self.chainedProtocol.terminalProtocol.terminalSize(width, height)\n\n\n\n@implementer(iconch.ISession)\nclass TerminalSession(components.Adapter):\n    transportFactory = TerminalSessionTransport\n    chainedProtocolFactory = insults.ServerProtocol\n\n    def getPty(self, term, windowSize, attrs):\n        self.height, self.width = windowSize[:2]\n\n\n    def openShell(self, proto):\n        self.transportFactory(\n            proto, self.chainedProtocolFactory(),\n            iconch.IConchUser(self.original),\n            self.width, self.height)\n\n\n    def execCommand(self, proto, cmd):\n        raise econch.ConchError(\"Cannot execute commands\")\n\n\n    def closed(self):\n        pass\n\n\n\nclass TerminalUser(avatar.ConchUser, components.Adapter):\n    def __init__(self, original, avatarId):\n        components.Adapter.__init__(self, original)\n        avatar.ConchUser.__init__(self)\n        self.channelLookup[b'session'] = session.SSHSession\n\n\n\nclass TerminalRealm:\n    userFactory = TerminalUser\n    sessionFactory = TerminalSession\n\n    transportFactory = TerminalSessionTransport\n    chainedProtocolFactory = insults.ServerProtocol\n\n    def _getAvatar(self, avatarId):\n        comp = components.Componentized()\n        user = self.userFactory(comp, avatarId)\n        sess = self.sessionFactory(comp)\n\n        sess.transportFactory = self.transportFactory\n        sess.chainedProtocolFactory = self.chainedProtocolFactory\n\n        comp.setComponent(iconch.IConchUser, user)\n        comp.setComponent(iconch.ISession, sess)\n\n        return user\n\n\n    def __init__(self, transportFactory=None):\n        if transportFactory is not None:\n            self.transportFactory = transportFactory\n\n\n    def requestAvatar(self, avatarId, mind, *interfaces):\n        for i in interfaces:\n            if i is iconch.IConchUser:\n                return (iconch.IConchUser,\n                        self._getAvatar(avatarId),\n                        lambda: None)\n        raise NotImplementedError()\n\n\n\nclass ConchFactory(factory.SSHFactory):\n    publicKeys = {}\n    privateKeys = {}\n\n    def __init__(self, portal):\n        self.portal = portal\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/manhole_tap.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTAP plugin for creating telnet- and ssh-accessible manhole servers.\n\n@author: Jp Calderone\n\"\"\"\n\nfrom zope.interface import implementer\n\nfrom twisted.internet import protocol\nfrom twisted.application import service, strports\nfrom twisted.cred import portal, checkers\nfrom twisted.python import usage, filepath\n\nfrom twisted.conch import manhole, manhole_ssh, telnet\nfrom twisted.conch.insults import insults\nfrom twisted.conch.ssh import keys\n\n\n\nclass makeTelnetProtocol:\n    def __init__(self, portal):\n        self.portal = portal\n\n    def __call__(self):\n        auth = telnet.AuthenticatingTelnetProtocol\n        args = (self.portal,)\n        return telnet.TelnetTransport(auth, *args)\n\n\n\nclass chainedProtocolFactory:\n    def __init__(self, namespace):\n        self.namespace = namespace\n\n    def __call__(self):\n        return insults.ServerProtocol(manhole.ColoredManhole, self.namespace)\n\n\n\n@implementer(portal.IRealm)\nclass _StupidRealm:\n    def __init__(self, proto, *a, **kw):\n        self.protocolFactory = proto\n        self.protocolArgs = a\n        self.protocolKwArgs = kw\n\n    def requestAvatar(self, avatarId, *interfaces):\n        if telnet.ITelnetProtocol in interfaces:\n            return (telnet.ITelnetProtocol,\n                    self.protocolFactory(*self.protocolArgs,\n                                         **self.protocolKwArgs),\n                    lambda: None)\n        raise NotImplementedError()\n\n\n\nclass Options(usage.Options):\n    optParameters = [\n        [\"telnetPort\", \"t\", None,\n         (\"strports description of the address on which to listen for telnet \"\n          \"connections\")],\n        [\"sshPort\", \"s\", None,\n         (\"strports description of the address on which to listen for ssh \"\n          \"connections\")],\n        [\"passwd\", \"p\", \"/etc/passwd\",\n         \"name of a passwd(5)-format username/password file\"],\n        [\"sshKeyDir\", None, \"<USER DATA DIR>\",\n         \"Directory where the autogenerated SSH key is kept.\"],\n        [\"sshKeyName\", None, \"server.key\",\n         \"Filename of the autogenerated SSH key.\"],\n        [\"sshKeySize\", None, 4096,\n         \"Size of the automatically generated SSH key.\"],\n    ]\n\n    def __init__(self):\n        usage.Options.__init__(self)\n        self['namespace'] = None\n\n    def postOptions(self):\n        if self['telnetPort'] is None and self['sshPort'] is None:\n            raise usage.UsageError(\n                \"At least one of --telnetPort and --sshPort must be specified\")\n\n\n\ndef makeService(options):\n    \"\"\"\n    Create a manhole server service.\n\n    @type options: L{dict}\n    @param options: A mapping describing the configuration of\n    the desired service.  Recognized key/value pairs are::\n\n        \"telnetPort\": strports description of the address on which\n                      to listen for telnet connections.  If None,\n                      no telnet service will be started.\n\n        \"sshPort\": strports description of the address on which to\n                   listen for ssh connections.  If None, no ssh\n                   service will be started.\n\n        \"namespace\": dictionary containing desired initial locals\n                     for manhole connections.  If None, an empty\n                     dictionary will be used.\n\n        \"passwd\": Name of a passwd(5)-format username/password file.\n\n        \"sshKeyDir\": The folder that the SSH server key will be kept in.\n\n        \"sshKeyName\": The filename of the key.\n\n        \"sshKeySize\": The size of the key, in bits. Default is 4096.\n\n    @rtype: L{twisted.application.service.IService}\n    @return: A manhole service.\n    \"\"\"\n    svc = service.MultiService()\n\n    namespace = options['namespace']\n    if namespace is None:\n        namespace = {}\n\n    checker = checkers.FilePasswordDB(options['passwd'])\n\n    if options['telnetPort']:\n        telnetRealm = _StupidRealm(telnet.TelnetBootstrapProtocol,\n                                   insults.ServerProtocol,\n                                   manhole.ColoredManhole,\n                                   namespace)\n\n        telnetPortal = portal.Portal(telnetRealm, [checker])\n\n        telnetFactory = protocol.ServerFactory()\n        telnetFactory.protocol = makeTelnetProtocol(telnetPortal)\n        telnetService = strports.service(options['telnetPort'],\n                                         telnetFactory)\n        telnetService.setServiceParent(svc)\n\n    if options['sshPort']:\n        sshRealm = manhole_ssh.TerminalRealm()\n        sshRealm.chainedProtocolFactory = chainedProtocolFactory(namespace)\n\n        sshPortal = portal.Portal(sshRealm, [checker])\n        sshFactory = manhole_ssh.ConchFactory(sshPortal)\n\n        if options['sshKeyDir'] != \"<USER DATA DIR>\":\n            keyDir = options['sshKeyDir']\n        else:\n            from twisted.python._appdirs import getDataDirectory\n            keyDir = getDataDirectory()\n\n        keyLocation = filepath.FilePath(keyDir).child(options['sshKeyName'])\n\n        sshKey = keys._getPersistentRSAKey(keyLocation,\n                                           int(options['sshKeySize']))\n        sshFactory.publicKeys[b\"ssh-rsa\"] = sshKey\n        sshFactory.privateKeys[b\"ssh-rsa\"] = sshKey\n\n        sshService = strports.service(options['sshPort'], sshFactory)\n        sshService.setServiceParent(svc)\n\n    return svc\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/mixin.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_mixin -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nExperimental optimization\n\nThis module provides a single mixin class which allows protocols to\ncollapse numerous small writes into a single larger one.\n\n@author: Jp Calderone\n\"\"\"\n\nfrom twisted.internet import reactor\n\nclass BufferingMixin:\n    \"\"\"\n    Mixin which adds write buffering.\n    \"\"\"\n    _delayedWriteCall = None\n    data = None\n\n    DELAY = 0.0\n\n    def schedule(self):\n        return reactor.callLater(self.DELAY, self.flush)\n\n\n    def reschedule(self, token):\n        token.reset(self.DELAY)\n\n\n    def write(self, data):\n        \"\"\"\n        Buffer some bytes to be written soon.\n\n        Every call to this function delays the real write by C{self.DELAY}\n        seconds.  When the delay expires, all collected bytes are written\n        to the underlying transport using L{ITransport.writeSequence}.\n        \"\"\"\n        if self._delayedWriteCall is None:\n            self.data = []\n            self._delayedWriteCall = self.schedule()\n        else:\n            self.reschedule(self._delayedWriteCall)\n        self.data.append(data)\n\n\n    def flush(self):\n        \"\"\"\n        Flush the buffer immediately.\n        \"\"\"\n        self._delayedWriteCall = None\n        self.transport.writeSequence(self.data)\n        self.data = None\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/openssh_compat/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n# \n\n\"\"\"\nSupport for OpenSSH configuration files.\n\nMaintainer: Paul Swartz\n\"\"\"\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/openssh_compat/factory.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_openssh_compat -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nFactory for reading openssh configuration files: public keys, private keys, and\nmoduli file.\n\"\"\"\n\nimport os, errno\n\nfrom twisted.python import log\nfrom twisted.python.util import runAsEffectiveUser\n\nfrom twisted.conch.ssh import keys, factory, common\nfrom twisted.conch.openssh_compat import primes\n\n\n\nclass OpenSSHFactory(factory.SSHFactory):\n    dataRoot = '/usr/local/etc'\n    # For openbsd which puts moduli in a different directory from keys.\n    moduliRoot = '/usr/local/etc'\n\n\n    def getPublicKeys(self):\n        \"\"\"\n        Return the server public keys.\n        \"\"\"\n        ks = {}\n        for filename in os.listdir(self.dataRoot):\n            if filename[:9] == 'ssh_host_' and filename[-8:]=='_key.pub':\n                try:\n                    k = keys.Key.fromFile(\n                        os.path.join(self.dataRoot, filename))\n                    t = common.getNS(k.blob())[0]\n                    ks[t] = k\n                except Exception as e:\n                    log.msg('bad public key file %s: %s' % (filename, e))\n        return ks\n\n\n    def getPrivateKeys(self):\n        \"\"\"\n        Return the server private keys.\n        \"\"\"\n        privateKeys = {}\n        for filename in os.listdir(self.dataRoot):\n            if filename[:9] == 'ssh_host_' and filename[-4:]=='_key':\n                fullPath = os.path.join(self.dataRoot, filename)\n                try:\n                    key = keys.Key.fromFile(fullPath)\n                except IOError as e:\n                    if e.errno == errno.EACCES:\n                        # Not allowed, let's switch to root\n                        key = runAsEffectiveUser(\n                            0, 0, keys.Key.fromFile, fullPath)\n                        privateKeys[key.sshType()] = key\n                    else:\n                        raise\n                except Exception as e:\n                    log.msg('bad private key file %s: %s' % (filename, e))\n                else:\n                    privateKeys[key.sshType()] = key\n        return privateKeys\n\n\n    def getPrimes(self):\n        try:\n            return primes.parseModuliFile(self.moduliRoot+'/moduli')\n        except IOError:\n            return None\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/openssh_compat/primes.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n# \n\n\"\"\"\nParsing for the moduli file, which contains Diffie-Hellman prime groups.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nfrom twisted.python.compat import long\n\n\ndef parseModuliFile(filename):\n    with open(filename) as f:\n        lines = f.readlines()\n    primes = {}\n    for l in lines:\n        l = l.strip()\n        if  not l or l[0]=='#':\n            continue\n        tim, typ, tst, tri, size, gen, mod = l.split()\n        size = int(size) + 1\n        gen = long(gen)\n        mod = long(mod, 16)\n        if size not in primes:\n            primes[size] = []\n        primes[size].append((gen, mod))\n    return primes\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/recvline.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_recvline -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nBasic line editing support.\n\n@author: Jp Calderone\n\"\"\"\n\nimport string\n\nfrom zope.interface import implementer\n\nfrom twisted.conch.insults import insults, helper\n\nfrom twisted.python import log, reflect\nfrom twisted.python.compat import iterbytes\n\n_counters = {}\nclass Logging(object):\n    \"\"\"\n    Wrapper which logs attribute lookups.\n\n    This was useful in debugging something, I guess.  I forget what.\n    It can probably be deleted or moved somewhere more appropriate.\n    Nothing special going on here, really.\n    \"\"\"\n    def __init__(self, original):\n        self.original = original\n        key = reflect.qual(original.__class__)\n        count = _counters.get(key, 0)\n        _counters[key] = count + 1\n        self._logFile = open(key + '-' + str(count), 'w')\n\n\n    def __str__(self):\n        return str(super(Logging, self).__getattribute__('original'))\n\n\n    def __repr__(self):\n        return repr(super(Logging, self).__getattribute__('original'))\n\n\n    def __getattribute__(self, name):\n        original = super(Logging, self).__getattribute__('original')\n        logFile = super(Logging, self).__getattribute__('_logFile')\n        logFile.write(name + '\\n')\n        return getattr(original, name)\n\n\n\n@implementer(insults.ITerminalTransport)\nclass TransportSequence(object):\n    \"\"\"\n    An L{ITerminalTransport} implementation which forwards calls to\n    one or more other L{ITerminalTransport}s.\n\n    This is a cheap way for servers to keep track of the state they\n    expect the client to see, since all terminal manipulations can be\n    send to the real client and to a terminal emulator that lives in\n    the server process.\n    \"\"\"\n\n    for keyID in (b'UP_ARROW', b'DOWN_ARROW', b'RIGHT_ARROW', b'LEFT_ARROW',\n                  b'HOME', b'INSERT', b'DELETE', b'END', b'PGUP', b'PGDN',\n                  b'F1', b'F2', b'F3', b'F4', b'F5', b'F6', b'F7', b'F8',\n                  b'F9', b'F10', b'F11', b'F12'):\n        execBytes = keyID + b\" = object()\"\n        execStr = execBytes.decode(\"ascii\")\n        exec(execStr)\n\n    TAB = b'\\t'\n    BACKSPACE = b'\\x7f'\n\n    def __init__(self, *transports):\n        assert transports, (\n            \"Cannot construct a TransportSequence with no transports\")\n        self.transports = transports\n\n    for method in insults.ITerminalTransport:\n        exec(\"\"\"\\\ndef %s(self, *a, **kw):\n    for tpt in self.transports:\n        result = tpt.%s(*a, **kw)\n    return result\n\"\"\" % (method, method))\n\n\n\nclass LocalTerminalBufferMixin(object):\n    \"\"\"\n    A mixin for RecvLine subclasses which records the state of the terminal.\n\n    This is accomplished by performing all L{ITerminalTransport} operations on both\n    the transport passed to makeConnection and an instance of helper.TerminalBuffer.\n\n    @ivar terminalCopy: A L{helper.TerminalBuffer} instance which efforts\n    will be made to keep up to date with the actual terminal\n    associated with this protocol instance.\n    \"\"\"\n\n    def makeConnection(self, transport):\n        self.terminalCopy = helper.TerminalBuffer()\n        self.terminalCopy.connectionMade()\n        return super(LocalTerminalBufferMixin, self).makeConnection(\n            TransportSequence(transport, self.terminalCopy))\n\n\n    def __str__(self):\n        return str(self.terminalCopy)\n\n\n\nclass RecvLine(insults.TerminalProtocol):\n    \"\"\"\n    L{TerminalProtocol} which adds line editing features.\n\n    Clients will be prompted for lines of input with all the usual\n    features: character echoing, left and right arrow support for\n    moving the cursor to different areas of the line buffer, backspace\n    and delete for removing characters, and insert for toggling\n    between typeover and insert mode.  Tabs will be expanded to enough\n    spaces to move the cursor to the next tabstop (every four\n    characters by default).  Enter causes the line buffer to be\n    cleared and the line to be passed to the lineReceived() method\n    which, by default, does nothing.  Subclasses are responsible for\n    redrawing the input prompt (this will probably change).\n    \"\"\"\n    width = 80\n    height = 24\n\n    TABSTOP = 4\n\n    ps = (b'>>> ', b'... ')\n    pn = 0\n    _printableChars = string.printable.encode(\"ascii\")\n\n    def connectionMade(self):\n        # A list containing the characters making up the current line\n        self.lineBuffer = []\n\n        # A zero-based (wtf else?) index into self.lineBuffer.\n        # Indicates the current cursor position.\n        self.lineBufferIndex = 0\n\n        t = self.terminal\n        # A map of keyIDs to bound instance methods.\n        self.keyHandlers = {\n            t.LEFT_ARROW: self.handle_LEFT,\n            t.RIGHT_ARROW: self.handle_RIGHT,\n            t.TAB: self.handle_TAB,\n\n            # Both of these should not be necessary, but figuring out\n            # which is necessary is a huge hassle.\n            b'\\r': self.handle_RETURN,\n            b'\\n': self.handle_RETURN,\n\n            t.BACKSPACE: self.handle_BACKSPACE,\n            t.DELETE: self.handle_DELETE,\n            t.INSERT: self.handle_INSERT,\n            t.HOME: self.handle_HOME,\n            t.END: self.handle_END}\n\n        self.initializeScreen()\n\n\n    def initializeScreen(self):\n        # Hmm, state sucks.  Oh well.\n        # For now we will just take over the whole terminal.\n        self.terminal.reset()\n        self.terminal.write(self.ps[self.pn])\n        # XXX Note: I would prefer to default to starting in insert\n        # mode, however this does not seem to actually work!  I do not\n        # know why.  This is probably of interest to implementors\n        # subclassing RecvLine.\n\n        # XXX XXX Note: But the unit tests all expect the initial mode\n        # to be insert right now.  Fuck, there needs to be a way to\n        # query the current mode or something.\n        # self.setTypeoverMode()\n        self.setInsertMode()\n\n\n    def currentLineBuffer(self):\n        s = b''.join(self.lineBuffer)\n        return s[:self.lineBufferIndex], s[self.lineBufferIndex:]\n\n\n    def setInsertMode(self):\n        self.mode = 'insert'\n        self.terminal.setModes([insults.modes.IRM])\n\n\n    def setTypeoverMode(self):\n        self.mode = 'typeover'\n        self.terminal.resetModes([insults.modes.IRM])\n\n\n    def drawInputLine(self):\n        \"\"\"\n        Write a line containing the current input prompt and the current line\n        buffer at the current cursor position.\n        \"\"\"\n        self.terminal.write(self.ps[self.pn] + b''.join(self.lineBuffer))\n\n\n    def terminalSize(self, width, height):\n        # XXX - Clear the previous input line, redraw it at the new\n        # cursor position\n        self.terminal.eraseDisplay()\n        self.terminal.cursorHome()\n        self.width = width\n        self.height = height\n        self.drawInputLine()\n\n\n    def unhandledControlSequence(self, seq):\n        pass\n\n\n    def keystrokeReceived(self, keyID, modifier):\n        m = self.keyHandlers.get(keyID)\n        if m is not None:\n            m()\n        elif keyID in self._printableChars:\n            self.characterReceived(keyID, False)\n        else:\n            log.msg(\"Received unhandled keyID: %r\" % (keyID,))\n\n\n    def characterReceived(self, ch, moreCharactersComing):\n        if self.mode == 'insert':\n            self.lineBuffer.insert(self.lineBufferIndex, ch)\n        else:\n            self.lineBuffer[self.lineBufferIndex:self.lineBufferIndex+1] = [ch]\n        self.lineBufferIndex += 1\n        self.terminal.write(ch)\n\n\n    def handle_TAB(self):\n        n = self.TABSTOP - (len(self.lineBuffer) % self.TABSTOP)\n        self.terminal.cursorForward(n)\n        self.lineBufferIndex += n\n        self.lineBuffer.extend(iterbytes(b' ' * n))\n\n\n    def handle_LEFT(self):\n        if self.lineBufferIndex > 0:\n            self.lineBufferIndex -= 1\n            self.terminal.cursorBackward()\n\n\n    def handle_RIGHT(self):\n        if self.lineBufferIndex < len(self.lineBuffer):\n            self.lineBufferIndex += 1\n            self.terminal.cursorForward()\n\n\n    def handle_HOME(self):\n        if self.lineBufferIndex:\n            self.terminal.cursorBackward(self.lineBufferIndex)\n            self.lineBufferIndex = 0\n\n\n    def handle_END(self):\n        offset = len(self.lineBuffer) - self.lineBufferIndex\n        if offset:\n            self.terminal.cursorForward(offset)\n            self.lineBufferIndex = len(self.lineBuffer)\n\n\n    def handle_BACKSPACE(self):\n        if self.lineBufferIndex > 0:\n            self.lineBufferIndex -= 1\n            del self.lineBuffer[self.lineBufferIndex]\n            self.terminal.cursorBackward()\n            self.terminal.deleteCharacter()\n\n\n    def handle_DELETE(self):\n        if self.lineBufferIndex < len(self.lineBuffer):\n            del self.lineBuffer[self.lineBufferIndex]\n            self.terminal.deleteCharacter()\n\n\n    def handle_RETURN(self):\n        line = b''.join(self.lineBuffer)\n        self.lineBuffer = []\n        self.lineBufferIndex = 0\n        self.terminal.nextLine()\n        self.lineReceived(line)\n\n\n    def handle_INSERT(self):\n        assert self.mode in ('typeover', 'insert')\n        if self.mode == 'typeover':\n            self.setInsertMode()\n        else:\n            self.setTypeoverMode()\n\n\n    def lineReceived(self, line):\n        pass\n\n\n\nclass HistoricRecvLine(RecvLine):\n    \"\"\"\n    L{TerminalProtocol} which adds both basic line-editing features and input history.\n\n    Everything supported by L{RecvLine} is also supported by this class.  In addition, the\n    up and down arrows traverse the input history.  Each received line is automatically\n    added to the end of the input history.\n    \"\"\"\n    def connectionMade(self):\n        RecvLine.connectionMade(self)\n\n        self.historyLines = []\n        self.historyPosition = 0\n\n        t = self.terminal\n        self.keyHandlers.update({t.UP_ARROW: self.handle_UP,\n                                 t.DOWN_ARROW: self.handle_DOWN})\n\n\n    def currentHistoryBuffer(self):\n        b = tuple(self.historyLines)\n        return b[:self.historyPosition], b[self.historyPosition:]\n\n\n    def _deliverBuffer(self, buf):\n        if buf:\n            for ch in iterbytes(buf[:-1]):\n                self.characterReceived(ch, True)\n            self.characterReceived(buf[-1:], False)\n\n\n    def handle_UP(self):\n        if self.lineBuffer and self.historyPosition == len(self.historyLines):\n            self.historyLines.append(b''.join(self.lineBuffer))\n        if self.historyPosition > 0:\n            self.handle_HOME()\n            self.terminal.eraseToLineEnd()\n\n            self.historyPosition -= 1\n            self.lineBuffer = []\n\n            self._deliverBuffer(self.historyLines[self.historyPosition])\n\n\n    def handle_DOWN(self):\n        if self.historyPosition < len(self.historyLines) - 1:\n            self.handle_HOME()\n            self.terminal.eraseToLineEnd()\n\n            self.historyPosition += 1\n            self.lineBuffer = []\n\n            self._deliverBuffer(self.historyLines[self.historyPosition])\n        else:\n            self.handle_HOME()\n            self.terminal.eraseToLineEnd()\n\n            self.historyPosition = len(self.historyLines)\n            self.lineBuffer = []\n            self.lineBufferIndex = 0\n\n\n    def handle_RETURN(self):\n        if self.lineBuffer:\n            self.historyLines.append(b''.join(self.lineBuffer))\n        self.historyPosition = len(self.historyLines)\n        return RecvLine.handle_RETURN(self)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/scripts/__init__.py",
    "content": "'conch scripts'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/scripts/cftp.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_cftp -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nImplementation module for the I{cftp} command.\n\"\"\"\nfrom __future__ import division, print_function\nimport os, sys, getpass, struct, tty, fcntl, stat\nimport fnmatch, pwd, glob\n\nfrom twisted.conch.client import connect, default, options\nfrom twisted.conch.ssh import connection, common\nfrom twisted.conch.ssh import channel, filetransfer\nfrom twisted.protocols import basic\nfrom twisted.python.compat import _PY3, unicode\nfrom twisted.internet import reactor, stdio, defer, utils\nfrom twisted.python import log, usage, failure\nfrom twisted.python.filepath import FilePath\n\nclass ClientOptions(options.ConchOptions):\n\n    synopsis = \"\"\"Usage:   cftp [options] [user@]host\n         cftp [options] [user@]host[:dir[/]]\n         cftp [options] [user@]host[:file [localfile]]\n\"\"\"\n    longdesc = (\"cftp is a client for logging into a remote machine and \"\n                \"executing commands to send and receive file information\")\n\n    optParameters = [\n                    ['buffersize', 'B', 32768, 'Size of the buffer to use for sending/receiving.'],\n                    ['batchfile', 'b', None, 'File to read commands from, or \\'-\\' for stdin.'],\n                    ['requests', 'R', 5, 'Number of requests to make before waiting for a reply.'],\n                    ['subsystem', 's', 'sftp', 'Subsystem/server program to connect to.']]\n\n    compData = usage.Completions(\n        descriptions={\n            \"buffersize\": \"Size of send/receive buffer (default: 32768)\"},\n        extraActions=[usage.CompleteUserAtHost(),\n                      usage.CompleteFiles(descr=\"local file\")])\n\n    def parseArgs(self, host, localPath=None):\n        self['remotePath'] = ''\n        if ':' in host:\n            host, self['remotePath'] = host.split(':', 1)\n            self['remotePath'].rstrip('/')\n        self['host'] = host\n        self['localPath'] = localPath\n\ndef run():\n#    import hotshot\n#    prof = hotshot.Profile('cftp.prof')\n#    prof.start()\n    args = sys.argv[1:]\n    if '-l' in args: # cvs is an idiot\n        i = args.index('-l')\n        args = args[i:i+2]+args\n        del args[i+2:i+4]\n    options = ClientOptions()\n    try:\n        options.parseOptions(args)\n    except usage.UsageError as u:\n        print('ERROR: %s' % u)\n        sys.exit(1)\n    if options['log']:\n        realout = sys.stdout\n        log.startLogging(sys.stderr)\n        sys.stdout = realout\n    else:\n        log.discardLogs()\n    doConnect(options)\n    reactor.run()\n#    prof.stop()\n#    prof.close()\n\ndef handleError():\n    global exitStatus\n    exitStatus = 2\n    try:\n        reactor.stop()\n    except: pass\n    log.err(failure.Failure())\n    raise\n\ndef doConnect(options):\n#    log.deferr = handleError # HACK\n    if '@' in options['host']:\n        options['user'], options['host'] = options['host'].split('@',1)\n    host = options['host']\n    if not options['user']:\n        options['user'] = getpass.getuser()\n    if not options['port']:\n        options['port'] = 22\n    else:\n        options['port'] = int(options['port'])\n    host = options['host']\n    port = options['port']\n    conn = SSHConnection()\n    conn.options = options\n    vhk = default.verifyHostKey\n    uao = default.SSHUserAuthClient(options['user'], options, conn)\n    connect.connect(host, port, options, vhk, uao).addErrback(_ebExit)\n\ndef _ebExit(f):\n    #global exitStatus\n    if hasattr(f.value, 'value'):\n        s = f.value.value\n    else:\n        s = str(f)\n    print(s)\n    #exitStatus = \"conch: exiting with error %s\" % f\n    try:\n        reactor.stop()\n    except: pass\n\ndef _ignore(*args): pass\n\nclass FileWrapper:\n\n    def __init__(self, f):\n        self.f = f\n        self.total = 0.0\n        f.seek(0, 2) # seek to the end\n        self.size = f.tell()\n\n    def __getattr__(self, attr):\n        return getattr(self.f, attr)\n\nclass StdioClient(basic.LineReceiver):\n\n    _pwd = pwd\n\n    ps = 'cftp> '\n    delimiter = b'\\n'\n\n    reactor = reactor\n\n    def __init__(self, client, f = None):\n        self.client = client\n        self.currentDirectory = ''\n        self.file = f\n        self.useProgressBar = (not f and 1) or 0\n\n    def connectionMade(self):\n        self.client.realPath('').addCallback(self._cbSetCurDir)\n\n    def _cbSetCurDir(self, path):\n        self.currentDirectory = path\n        self._newLine()\n\n    def _writeToTransport(self, msg):\n        if isinstance(msg, unicode):\n            msg = msg.encode(\"utf-8\")\n        return self.transport.write(msg)\n\n    def lineReceived(self, line):\n        if self.client.transport.localClosed:\n            return\n        if _PY3 and isinstance(line, bytes):\n            line = line.decode(\"utf-8\")\n        log.msg('got line %s' % line)\n        line = line.lstrip()\n        if not line:\n            self._newLine()\n            return\n        if self.file and line.startswith('-'):\n            self.ignoreErrors = 1\n            line = line[1:]\n        else:\n            self.ignoreErrors = 0\n        d = self._dispatchCommand(line)\n        if d is not None:\n            d.addCallback(self._cbCommand)\n            d.addErrback(self._ebCommand)\n\n\n    def _dispatchCommand(self, line):\n        if ' ' in line:\n            command, rest = line.split(' ', 1)\n            rest = rest.lstrip()\n        else:\n            command, rest = line, ''\n        if command.startswith('!'): # command\n            f = self.cmd_EXEC\n            rest = (command[1:] + ' ' + rest).strip()\n        else:\n            command = command.upper()\n            log.msg('looking up cmd %s' % command)\n            f = getattr(self, 'cmd_%s' % command, None)\n        if f is not None:\n            return defer.maybeDeferred(f, rest)\n        else:\n            errMsg = \"No command called `%s'\" % (command)\n            self._ebCommand(failure.Failure(NotImplementedError(errMsg)))\n            self._newLine()\n\n    def _printFailure(self, f):\n        log.msg(f)\n        e = f.trap(NotImplementedError, filetransfer.SFTPError, OSError, IOError)\n        if e == NotImplementedError:\n            self._writeToTransport(self.cmd_HELP(''))\n        elif e == filetransfer.SFTPError:\n            errMsg = \"remote error %i: %s\\n\" % (f.value.code, f.value.message)\n            self._writeToTransport(errMsg)\n        elif e in (OSError, IOError):\n            errMsg = \"local error %i: %s\\n\" % (f.value.errno, f.value.strerror)\n            self._writeToTransport(errMsg)\n\n    def _newLine(self):\n        if self.client.transport.localClosed:\n            return\n        self._writeToTransport(self.ps)\n        self.ignoreErrors = 0\n        if self.file:\n            l = self.file.readline()\n            if not l:\n                self.client.transport.loseConnection()\n            else:\n                self._writeToTransport(l)\n                self.lineReceived(l.strip())\n\n    def _cbCommand(self, result):\n        if result is not None:\n            if isinstance(result, unicode):\n                result = result.encode(\"utf-8\")\n            self._writeToTransport(result)\n            if not result.endswith(b'\\n'):\n                self._writeToTransport(b'\\n')\n        self._newLine()\n\n    def _ebCommand(self, f):\n        self._printFailure(f)\n        if self.file and not self.ignoreErrors:\n            self.client.transport.loseConnection()\n        self._newLine()\n\n    def cmd_CD(self, path):\n        path, rest = self._getFilename(path)\n        if not path.endswith('/'):\n            path += '/'\n        newPath = path and os.path.join(self.currentDirectory, path) or ''\n        d = self.client.openDirectory(newPath)\n        d.addCallback(self._cbCd)\n        d.addErrback(self._ebCommand)\n        return d\n\n    def _cbCd(self, directory):\n        directory.close()\n        d = self.client.realPath(directory.name)\n        d.addCallback(self._cbCurDir)\n        return d\n\n    def _cbCurDir(self, path):\n        self.currentDirectory = path\n\n    def cmd_CHGRP(self, rest):\n        grp, rest = rest.split(None, 1)\n        path, rest = self._getFilename(rest)\n        grp = int(grp)\n        d = self.client.getAttrs(path)\n        d.addCallback(self._cbSetUsrGrp, path, grp=grp)\n        return d\n\n    def cmd_CHMOD(self, rest):\n        mod, rest = rest.split(None, 1)\n        path, rest = self._getFilename(rest)\n        mod = int(mod, 8)\n        d = self.client.setAttrs(path, {'permissions':mod})\n        d.addCallback(_ignore)\n        return d\n\n    def cmd_CHOWN(self, rest):\n        usr, rest = rest.split(None, 1)\n        path, rest = self._getFilename(rest)\n        usr = int(usr)\n        d = self.client.getAttrs(path)\n        d.addCallback(self._cbSetUsrGrp, path, usr=usr)\n        return d\n\n    def _cbSetUsrGrp(self, attrs, path, usr=None, grp=None):\n        new = {}\n        new['uid'] = (usr is not None) and usr or attrs['uid']\n        new['gid'] = (grp is not None) and grp or attrs['gid']\n        d = self.client.setAttrs(path, new)\n        d.addCallback(_ignore)\n        return d\n\n    def cmd_GET(self, rest):\n        remote, rest = self._getFilename(rest)\n        if '*' in remote or '?' in remote: # wildcard\n            if rest:\n                local, rest = self._getFilename(rest)\n                if not os.path.isdir(local):\n                    return \"Wildcard get with non-directory target.\"\n            else:\n                local = b''\n            d = self._remoteGlob(remote)\n            d.addCallback(self._cbGetMultiple, local)\n            return d\n        if rest:\n            local, rest = self._getFilename(rest)\n        else:\n            local = os.path.split(remote)[1]\n        log.msg((remote, local))\n        lf = open(local, 'wb', 0)\n        path = FilePath(self.currentDirectory).child(remote)\n        d = self.client.openFile(path.path, filetransfer.FXF_READ, {})\n        d.addCallback(self._cbGetOpenFile, lf)\n        d.addErrback(self._ebCloseLf, lf)\n        return d\n\n    def _cbGetMultiple(self, files, local):\n        #if self._useProgressBar: # one at a time\n        # XXX this can be optimized for times w/o progress bar\n        return self._cbGetMultipleNext(None, files, local)\n\n    def _cbGetMultipleNext(self, res, files, local):\n        if isinstance(res, failure.Failure):\n            self._printFailure(res)\n        elif res:\n            self._writeToTransport(res)\n            if not res.endswith('\\n'):\n                self._writeToTransport('\\n')\n        if not files:\n            return\n        f = files.pop(0)[0]\n        lf = open(os.path.join(local, os.path.split(f)[1]), 'wb', 0)\n        path = FilePath(self.currentDirectory).child(f)\n        d = self.client.openFile(path.path, filetransfer.FXF_READ, {})\n        d.addCallback(self._cbGetOpenFile, lf)\n        d.addErrback(self._ebCloseLf, lf)\n        d.addBoth(self._cbGetMultipleNext, files, local)\n        return d\n\n    def _ebCloseLf(self, f, lf):\n        lf.close()\n        return f\n\n    def _cbGetOpenFile(self, rf, lf):\n        return rf.getAttrs().addCallback(self._cbGetFileSize, rf, lf)\n\n    def _cbGetFileSize(self, attrs, rf, lf):\n        if not stat.S_ISREG(attrs['permissions']):\n            rf.close()\n            lf.close()\n            return \"Can't get non-regular file: %s\" % rf.name\n        rf.size = attrs['size']\n        bufferSize = self.client.transport.conn.options['buffersize']\n        numRequests = self.client.transport.conn.options['requests']\n        rf.total = 0.0\n        dList = []\n        chunks = []\n        startTime = self.reactor.seconds()\n        for i in range(numRequests):\n            d = self._cbGetRead('', rf, lf, chunks, 0, bufferSize, startTime)\n            dList.append(d)\n        dl = defer.DeferredList(dList, fireOnOneErrback=1)\n        dl.addCallback(self._cbGetDone, rf, lf)\n        return dl\n\n    def _getNextChunk(self, chunks):\n        end = 0\n        for chunk in chunks:\n            if end == 'eof':\n                return # nothing more to get\n            if end != chunk[0]:\n                i = chunks.index(chunk)\n                chunks.insert(i, (end, chunk[0]))\n                return (end, chunk[0] - end)\n            end = chunk[1]\n        bufSize = int(self.client.transport.conn.options['buffersize'])\n        chunks.append((end, end + bufSize))\n        return (end, bufSize)\n\n    def _cbGetRead(self, data, rf, lf, chunks, start, size, startTime):\n        if data and isinstance(data, failure.Failure):\n            log.msg('get read err: %s' % data)\n            reason = data\n            reason.trap(EOFError)\n            i = chunks.index((start, start + size))\n            del chunks[i]\n            chunks.insert(i, (start, 'eof'))\n        elif data:\n            log.msg('get read data: %i' % len(data))\n            lf.seek(start)\n            lf.write(data)\n            if len(data) != size:\n                log.msg('got less than we asked for: %i < %i' %\n                        (len(data), size))\n                i = chunks.index((start, start + size))\n                del chunks[i]\n                chunks.insert(i, (start, start + len(data)))\n            rf.total += len(data)\n        if self.useProgressBar:\n            self._printProgressBar(rf, startTime)\n        chunk = self._getNextChunk(chunks)\n        if not chunk:\n            return\n        else:\n            start, length = chunk\n        log.msg('asking for %i -> %i' % (start, start+length))\n        d = rf.readChunk(start, length)\n        d.addBoth(self._cbGetRead, rf, lf, chunks, start, length, startTime)\n        return d\n\n    def _cbGetDone(self, ignored, rf, lf):\n        log.msg('get done')\n        rf.close()\n        lf.close()\n        if self.useProgressBar:\n            self._writeToTransport('\\n')\n        return \"Transferred %s to %s\" % (rf.name, lf.name)\n\n\n    def cmd_PUT(self, rest):\n        \"\"\"\n        Do an upload request for a single local file or a globing expression.\n\n        @param rest: Requested command line for the PUT command.\n        @type rest: L{str}\n\n        @return: A deferred which fires with L{None} when transfer is done.\n        @rtype: L{defer.Deferred}\n        \"\"\"\n        local, rest = self._getFilename(rest)\n\n        # FIXME: https://twistedmatrix.com/trac/ticket/7241\n        # Use a better check for globbing expression.\n        if '*' in local or '?' in local:\n            if rest:\n                remote, rest = self._getFilename(rest)\n                remote = os.path.join(self.currentDirectory, remote)\n            else:\n                remote = ''\n\n            files = glob.glob(local)\n            return self._putMultipleFiles(files, remote)\n\n        else:\n            if rest:\n                remote, rest = self._getFilename(rest)\n            else:\n                remote = os.path.split(local)[1]\n            return self._putSingleFile(local, remote)\n\n\n    def _putSingleFile(self, local, remote):\n        \"\"\"\n        Perform an upload for a single file.\n\n        @param local: Path to local file.\n        @type local: L{str}.\n\n        @param remote: Remote path for the request relative to current working\n            directory.\n        @type remote: L{str}\n\n        @return: A deferred which fires when transfer is done.\n        \"\"\"\n        return self._cbPutMultipleNext(None, [local], remote, single=True)\n\n\n    def _putMultipleFiles(self, files, remote):\n        \"\"\"\n        Perform an upload for a list of local files.\n\n        @param files: List of local files.\n        @type files: C{list} of L{str}.\n\n        @param remote: Remote path for the request relative to current working\n            directory.\n        @type remote: L{str}\n\n        @return: A deferred which fires when transfer is done.\n        \"\"\"\n        return self._cbPutMultipleNext(None, files, remote)\n\n\n    def _cbPutMultipleNext(\n            self, previousResult, files, remotePath, single=False):\n        \"\"\"\n        Perform an upload for the next file in the list of local files.\n\n        @param previousResult: Result form previous file form the list.\n        @type previousResult: L{str}\n\n        @param files: List of local files.\n        @type files: C{list} of L{str}\n\n        @param remotePath: Remote path for the request relative to current\n            working directory.\n        @type remotePath: L{str}\n\n        @param single: A flag which signals if this is a transfer for a single\n            file in which case we use the exact remote path\n        @type single: L{bool}\n\n        @return: A deferred which fires when transfer is done.\n        \"\"\"\n        if isinstance(previousResult, failure.Failure):\n            self._printFailure(previousResult)\n        elif previousResult:\n            if isinstance(previousResult, unicode):\n                previousResult = previousResult.encode(\"utf-8\")\n            self._writeToTransport(previousResult)\n            if not previousResult.endswith(b'\\n'):\n                self._writeToTransport(b'\\n')\n\n        currentFile = None\n        while files and not currentFile:\n            try:\n                currentFile = files.pop(0)\n                localStream = open(currentFile, 'rb')\n            except:\n                self._printFailure(failure.Failure())\n                currentFile = None\n\n        # No more files to transfer.\n        if not currentFile:\n            return None\n\n        if single:\n            remote = remotePath\n        else:\n            name = os.path.split(currentFile)[1]\n            remote = os.path.join(remotePath, name)\n            log.msg((name, remote, remotePath))\n\n        d = self._putRemoteFile(localStream, remote)\n        d.addBoth(self._cbPutMultipleNext, files, remotePath)\n        return d\n\n\n    def _putRemoteFile(self, localStream, remotePath):\n        \"\"\"\n        Do an upload request.\n\n        @param localStream: Local stream from where data is read.\n        @type localStream: File like object.\n\n        @param remotePath: Remote path for the request relative to current working directory.\n        @type remotePath: L{str}\n\n        @return: A deferred which fires when transfer is done.\n        \"\"\"\n        remote = os.path.join(self.currentDirectory, remotePath)\n        flags = (\n            filetransfer.FXF_WRITE |\n            filetransfer.FXF_CREAT |\n            filetransfer.FXF_TRUNC\n            )\n        d = self.client.openFile(remote, flags, {})\n        d.addCallback(self._cbPutOpenFile, localStream)\n        d.addErrback(self._ebCloseLf, localStream)\n        return d\n\n\n    def _cbPutOpenFile(self, rf, lf):\n        numRequests = self.client.transport.conn.options['requests']\n        if self.useProgressBar:\n            lf = FileWrapper(lf)\n        dList = []\n        chunks = []\n        startTime = self.reactor.seconds()\n        for i in range(numRequests):\n            d = self._cbPutWrite(None, rf, lf, chunks, startTime)\n            if d:\n                dList.append(d)\n        dl = defer.DeferredList(dList, fireOnOneErrback=1)\n        dl.addCallback(self._cbPutDone, rf, lf)\n        return dl\n\n    def _cbPutWrite(self, ignored, rf, lf, chunks, startTime):\n        chunk = self._getNextChunk(chunks)\n        start, size = chunk\n        lf.seek(start)\n        data = lf.read(size)\n        if self.useProgressBar:\n            lf.total += len(data)\n            self._printProgressBar(lf, startTime)\n        if data:\n            d = rf.writeChunk(start, data)\n            d.addCallback(self._cbPutWrite, rf, lf, chunks, startTime)\n            return d\n        else:\n            return\n\n    def _cbPutDone(self, ignored, rf, lf):\n        lf.close()\n        rf.close()\n        if self.useProgressBar:\n            self._writeToTransport('\\n')\n        return 'Transferred %s to %s' % (lf.name, rf.name)\n\n    def cmd_LCD(self, path):\n        os.chdir(path)\n\n    def cmd_LN(self, rest):\n        linkpath, rest = self._getFilename(rest)\n        targetpath, rest = self._getFilename(rest)\n        linkpath, targetpath = map(\n                lambda x: os.path.join(self.currentDirectory, x),\n                (linkpath, targetpath))\n        return self.client.makeLink(linkpath, targetpath).addCallback(_ignore)\n\n    def cmd_LS(self, rest):\n        # possible lines:\n        # ls                    current directory\n        # ls name_of_file       that file\n        # ls name_of_directory  that directory\n        # ls some_glob_string   current directory, globbed for that string\n        options = []\n        rest = rest.split()\n        while rest and rest[0] and rest[0][0] == '-':\n            opts = rest.pop(0)[1:]\n            for o in opts:\n                if o == 'l':\n                    options.append('verbose')\n                elif o == 'a':\n                    options.append('all')\n        rest = ' '.join(rest)\n        path, rest = self._getFilename(rest)\n        if not path:\n            fullPath = self.currentDirectory + '/'\n        else:\n            fullPath = os.path.join(self.currentDirectory, path)\n        d = self._remoteGlob(fullPath)\n        d.addCallback(self._cbDisplayFiles, options)\n        return d\n\n    def _cbDisplayFiles(self, files, options):\n        files.sort()\n        if 'all' not in options:\n            files = [f for f in files if not f[0].startswith(b'.')]\n        if 'verbose' in options:\n            lines = [f[1] for f in files]\n        else:\n            lines = [f[0] for f in files]\n        if not lines:\n            return None\n        else:\n            return b'\\n'.join(lines)\n\n    def cmd_MKDIR(self, path):\n        path, rest = self._getFilename(path)\n        path = os.path.join(self.currentDirectory, path)\n        return self.client.makeDirectory(path, {}).addCallback(_ignore)\n\n    def cmd_RMDIR(self, path):\n        path, rest = self._getFilename(path)\n        path = os.path.join(self.currentDirectory, path)\n        return self.client.removeDirectory(path).addCallback(_ignore)\n\n    def cmd_LMKDIR(self, path):\n        os.system(\"mkdir %s\" % path)\n\n    def cmd_RM(self, path):\n        path, rest = self._getFilename(path)\n        path = os.path.join(self.currentDirectory, path)\n        return self.client.removeFile(path).addCallback(_ignore)\n\n    def cmd_LLS(self, rest):\n        os.system(\"ls %s\" % rest)\n\n    def cmd_RENAME(self, rest):\n        oldpath, rest = self._getFilename(rest)\n        newpath, rest = self._getFilename(rest)\n        oldpath, newpath = map (\n                lambda x: os.path.join(self.currentDirectory, x),\n                (oldpath, newpath))\n        return self.client.renameFile(oldpath, newpath).addCallback(_ignore)\n\n    def cmd_EXIT(self, ignored):\n        self.client.transport.loseConnection()\n\n    cmd_QUIT = cmd_EXIT\n\n    def cmd_VERSION(self, ignored):\n        version = \"SFTP version %i\" % self.client.version\n        if isinstance(version, unicode):\n            version = version.encode(\"utf-8\")\n        return version\n\n    def cmd_HELP(self, ignored):\n        return \"\"\"Available commands:\ncd path                         Change remote directory to 'path'.\nchgrp gid path                  Change gid of 'path' to 'gid'.\nchmod mode path                 Change mode of 'path' to 'mode'.\nchown uid path                  Change uid of 'path' to 'uid'.\nexit                            Disconnect from the server.\nget remote-path [local-path]    Get remote file.\nhelp                            Get a list of available commands.\nlcd path                        Change local directory to 'path'.\nlls [ls-options] [path]         Display local directory listing.\nlmkdir path                     Create local directory.\nln linkpath targetpath          Symlink remote file.\nlpwd                            Print the local working directory.\nls [-l] [path]                  Display remote directory listing.\nmkdir path                      Create remote directory.\nprogress                        Toggle progress bar.\nput local-path [remote-path]    Put local file.\npwd                             Print the remote working directory.\nquit                            Disconnect from the server.\nrename oldpath newpath          Rename remote file.\nrmdir path                      Remove remote directory.\nrm path                         Remove remote file.\nversion                         Print the SFTP version.\n?                               Synonym for 'help'.\n\"\"\"\n\n    def cmd_PWD(self, ignored):\n        return self.currentDirectory\n\n    def cmd_LPWD(self, ignored):\n        return os.getcwd()\n\n    def cmd_PROGRESS(self, ignored):\n        self.useProgressBar = not self.useProgressBar\n        return \"%ssing progess bar.\" % (self.useProgressBar and \"U\" or \"Not u\")\n\n    def cmd_EXEC(self, rest):\n        \"\"\"\n        Run C{rest} using the user's shell (or /bin/sh if they do not have\n        one).\n        \"\"\"\n        shell = self._pwd.getpwnam(getpass.getuser())[6]\n        if not shell:\n            shell = '/bin/sh'\n        if rest:\n            cmds = ['-c', rest]\n            return utils.getProcessOutput(shell, cmds, errortoo=1)\n        else:\n            os.system(shell)\n\n    # accessory functions\n\n    def _remoteGlob(self, fullPath):\n        log.msg('looking up %s' % fullPath)\n        head, tail = os.path.split(fullPath)\n        if '*' in tail or '?' in tail:\n            glob = 1\n        else:\n            glob = 0\n        if tail and not glob: # could be file or directory\n            # try directory first\n            d = self.client.openDirectory(fullPath)\n            d.addCallback(self._cbOpenList, '')\n            d.addErrback(self._ebNotADirectory, head, tail)\n        else:\n            d = self.client.openDirectory(head)\n            d.addCallback(self._cbOpenList, tail)\n        return d\n\n    def _cbOpenList(self, directory, glob):\n        files = []\n        d = directory.read()\n        d.addBoth(self._cbReadFile, files, directory, glob)\n        return d\n\n    def _ebNotADirectory(self, reason, path, glob):\n        d = self.client.openDirectory(path)\n        d.addCallback(self._cbOpenList, glob)\n        return d\n\n    def _cbReadFile(self, files, l, directory, glob):\n        if not isinstance(files, failure.Failure):\n            if glob:\n                if _PY3:\n                    glob = glob.encode(\"utf-8\")\n                l.extend([f for f in files if fnmatch.fnmatch(f[0], glob)])\n            else:\n                l.extend(files)\n            d = directory.read()\n            d.addBoth(self._cbReadFile, l, directory, glob)\n            return d\n        else:\n            reason = files\n            reason.trap(EOFError)\n            directory.close()\n            return l\n\n    def _abbrevSize(self, size):\n        # from http://mail.python.org/pipermail/python-list/1999-December/018395.html\n        _abbrevs = [\n            (1<<50, 'PB'),\n            (1<<40, 'TB'),\n            (1<<30, 'GB'),\n            (1<<20, 'MB'),\n            (1<<10, 'kB'),\n            (1, 'B')\n            ]\n\n        for factor, suffix in _abbrevs:\n            if size > factor:\n                break\n        return '%.1f' % (size/factor) + suffix\n\n    def _abbrevTime(self, t):\n        if t > 3600: # 1 hour\n            hours = int(t / 3600)\n            t -= (3600 * hours)\n            mins = int(t / 60)\n            t -= (60 * mins)\n            return \"%i:%02i:%02i\" % (hours, mins, t)\n        else:\n            mins = int(t/60)\n            t -= (60 * mins)\n            return \"%02i:%02i\" % (mins, t)\n\n\n    def _printProgressBar(self, f, startTime):\n        \"\"\"\n        Update a console progress bar on this L{StdioClient}'s transport, based\n        on the difference between the start time of the operation and the\n        current time according to the reactor, and appropriate to the size of\n        the console window.\n\n        @param f: a wrapper around the file which is being written or read\n        @type f: L{FileWrapper}\n\n        @param startTime: The time at which the operation being tracked began.\n        @type startTime: L{float}\n        \"\"\"\n        diff = self.reactor.seconds() - startTime\n        total = f.total\n        try:\n            winSize = struct.unpack('4H',\n                fcntl.ioctl(0, tty.TIOCGWINSZ, '12345679'))\n        except IOError:\n            winSize = [None, 80]\n        if diff == 0.0:\n            speed = 0.0\n        else:\n            speed = total / diff\n        if speed:\n            timeLeft = (f.size - total) / speed\n        else:\n            timeLeft = 0\n        front = f.name\n        if f.size:\n            percentage = (total / f.size) * 100\n        else:\n            percentage = 100\n        back = '%3i%% %s %sps %s ' % (percentage,\n                                      self._abbrevSize(total),\n                                      self._abbrevSize(speed),\n                                      self._abbrevTime(timeLeft))\n        spaces = (winSize[1] - (len(front) + len(back) + 1)) * ' '\n        command = '\\r%s%s%s' % (front, spaces, back)\n        self._writeToTransport(command)\n\n\n    def _getFilename(self, line):\n        \"\"\"\n        Parse line received as command line input and return first filename\n        together with the remaining line.\n\n        @param line: Arguments received from command line input.\n        @type line: L{str}\n\n        @return: Tupple with filename and rest. Return empty values when no path was not found.\n        @rtype: C{tupple}\n        \"\"\"\n        line = line.strip()\n        if not line:\n            return '', ''\n        if line[0] in '\\'\"':\n            ret = []\n            line = list(line)\n            try:\n                for i in range(1,len(line)):\n                    c = line[i]\n                    if c == line[0]:\n                        return ''.join(ret), ''.join(line[i+1:]).lstrip()\n                    elif c == '\\\\': # quoted character\n                        del line[i]\n                        if line[i] not in '\\'\"\\\\':\n                            raise IndexError(\"bad quote: \\\\%s\" % (line[i],))\n                        ret.append(line[i])\n                    else:\n                        ret.append(line[i])\n            except IndexError:\n                raise IndexError(\"unterminated quote\")\n        ret = line.split(None, 1)\n        if len(ret) == 1:\n            return ret[0], ''\n        else:\n            return ret[0], ret[1]\n\nsetattr(StdioClient, 'cmd_?', StdioClient.cmd_HELP)\n\nclass SSHConnection(connection.SSHConnection):\n    def serviceStarted(self):\n        self.openChannel(SSHSession())\n\nclass SSHSession(channel.SSHChannel):\n\n    name = b'session'\n\n    def channelOpen(self, foo):\n        log.msg('session %s open' % self.id)\n        if self.conn.options['subsystem'].startswith('/'):\n            request = 'exec'\n        else:\n            request = 'subsystem'\n        d = self.conn.sendRequest(self, request, \\\n            common.NS(self.conn.options['subsystem']), wantReply=1)\n        d.addCallback(self._cbSubsystem)\n        d.addErrback(_ebExit)\n\n    def _cbSubsystem(self, result):\n        self.client = filetransfer.FileTransferClient()\n        self.client.makeConnection(self)\n        self.dataReceived = self.client.dataReceived\n        f = None\n        if self.conn.options['batchfile']:\n            fn = self.conn.options['batchfile']\n            if fn != '-':\n                f = open(fn)\n        self.stdio = stdio.StandardIO(StdioClient(self.client, f))\n\n    def extReceived(self, t, data):\n        if t==connection.EXTENDED_DATA_STDERR:\n            log.msg('got %s stderr data' % len(data))\n            sys.stderr.write(data)\n            sys.stderr.flush()\n\n    def eofReceived(self):\n        log.msg('got eof')\n        self.stdio.loseWriteConnection()\n\n    def closeReceived(self):\n        log.msg('remote side closed %s' % self)\n        self.conn.sendClose(self)\n\n    def closed(self):\n        try:\n            reactor.stop()\n        except:\n            pass\n\n    def stopWriting(self):\n        self.stdio.pauseProducing()\n\n    def startWriting(self):\n        self.stdio.resumeProducing()\n\nif __name__ == '__main__':\n    run()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/scripts/ckeygen.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_ckeygen -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nImplementation module for the `ckeygen` command.\n\"\"\"\n\nfrom __future__ import print_function\n\nimport sys, os, getpass, socket\nfrom functools import wraps\nfrom imp import reload\n\nif getpass.getpass == getpass.unix_getpass:\n    try:\n        import termios # hack around broken termios\n        termios.tcgetattr, termios.tcsetattr\n    except (ImportError, AttributeError):\n        sys.modules['termios'] = None\n        reload(getpass)\n\nfrom twisted.conch.ssh import keys\nfrom twisted.python import failure, filepath, log, usage\nfrom twisted.python.compat import raw_input, _PY3\n\n\n\nsupportedKeyTypes = dict()\ndef _keyGenerator(keyType):\n    def assignkeygenerator(keygenerator):\n        @wraps(keygenerator)\n        def wrapper(*args, **kwargs):\n            return keygenerator(*args, **kwargs)\n        supportedKeyTypes[keyType] = wrapper\n        return wrapper\n    return assignkeygenerator\n\n\n\nclass GeneralOptions(usage.Options):\n    synopsis = \"\"\"Usage:    ckeygen [options]\n \"\"\"\n\n    longdesc = \"ckeygen manipulates public/private keys in various ways.\"\n\n    optParameters = [['bits', 'b', None, 'Number of bits in the key to create.'],\n                     ['filename', 'f', None, 'Filename of the key file.'],\n                     ['type', 't', None, 'Specify type of key to create.'],\n                     ['comment', 'C', None, 'Provide new comment.'],\n                     ['newpass', 'N', None, 'Provide new passphrase.'],\n                     ['pass', 'P', None, 'Provide old passphrase.'],\n                     ['format', 'o', 'sha256-base64', 'Fingerprint format of key file.']]\n\n    optFlags = [['fingerprint', 'l', 'Show fingerprint of key file.'],\n                ['changepass', 'p', 'Change passphrase of private key file.'],\n                ['quiet', 'q', 'Quiet.'],\n                ['no-passphrase', None, \"Create the key with no passphrase.\"],\n                ['showpub', 'y', 'Read private key file and print public key.']]\n\n    compData = usage.Completions(\n        optActions={\"type\": usage.CompleteList(list(supportedKeyTypes.keys()))})\n\n\n\ndef run():\n    options = GeneralOptions()\n    try:\n        options.parseOptions(sys.argv[1:])\n    except usage.UsageError as u:\n        print('ERROR: %s' % u)\n        options.opt_help()\n        sys.exit(1)\n    log.discardLogs()\n    log.deferr = handleError # HACK\n    if options['type']:\n        if options['type'].lower() in supportedKeyTypes:\n            print('Generating public/private %s key pair.' % (options['type']))\n            supportedKeyTypes[options['type'].lower()](options)\n        else:\n            sys.exit(\n                'Key type was %s, must be one of %s'\n                    % (options['type'], ', '.join(supportedKeyTypes.keys())))\n    elif options['fingerprint']:\n        printFingerprint(options)\n    elif options['changepass']:\n        changePassPhrase(options)\n    elif options['showpub']:\n        displayPublicKey(options)\n    else:\n        options.opt_help()\n        sys.exit(1)\n\n\ndef enumrepresentation(options):\n    if options['format'] == 'md5-hex':\n        options['format'] = keys.FingerprintFormats.MD5_HEX\n        return options\n    elif options['format'] == 'sha256-base64':\n        options['format'] = keys.FingerprintFormats.SHA256_BASE64\n        return options\n    else:\n        raise keys.BadFingerPrintFormat(\n            'Unsupported fingerprint format: %s' % (options['format'],))\n\n\n\ndef handleError():\n    global exitStatus\n    exitStatus = 2\n    log.err(failure.Failure())\n    raise\n\n\n@_keyGenerator('rsa')\ndef generateRSAkey(options):\n    from cryptography.hazmat.backends import default_backend\n    from cryptography.hazmat.primitives.asymmetric import rsa\n\n    if not options['bits']:\n        options['bits'] = 1024\n    keyPrimitive = rsa.generate_private_key(\n        key_size=int(options['bits']),\n        public_exponent=65537,\n        backend=default_backend(),\n        )\n    key = keys.Key(keyPrimitive)\n    _saveKey(key, options)\n\n\n\n@_keyGenerator('dsa')\ndef generateDSAkey(options):\n    from cryptography.hazmat.backends import default_backend\n    from cryptography.hazmat.primitives.asymmetric import dsa\n\n    if not options['bits']:\n        options['bits'] = 1024\n    keyPrimitive = dsa.generate_private_key(\n        key_size=int(options['bits']),\n        backend=default_backend(),\n        )\n    key = keys.Key(keyPrimitive)\n    _saveKey(key, options)\n\n\n\n@_keyGenerator('ecdsa')\ndef generateECDSAkey(options):\n    from cryptography.hazmat.backends import default_backend\n    from cryptography.hazmat.primitives.asymmetric import ec\n\n    if not options['bits']:\n        options['bits'] = 256\n    # OpenSSH supports only mandatory sections of RFC5656.\n    # See https://www.openssh.com/txt/release-5.7\n    curve  = b'ecdsa-sha2-nistp' + str(options['bits']).encode('ascii')\n    keyPrimitive = ec.generate_private_key(\n        curve=keys._curveTable[curve],\n        backend=default_backend()\n        )\n    key = keys.Key(keyPrimitive)\n    _saveKey(key, options)\n\n\n\ndef printFingerprint(options):\n    if not options['filename']:\n        filename = os.path.expanduser('~/.ssh/id_rsa')\n        options['filename'] = raw_input('Enter file in which the key is (%s): ' % filename)\n    if os.path.exists(options['filename']+'.pub'):\n        options['filename'] += '.pub'\n    options = enumrepresentation(options)\n    try:\n        key = keys.Key.fromFile(options['filename'])\n        print('%s %s %s' % (\n            key.size(),\n            key.fingerprint(options['format']),\n            os.path.basename(options['filename'])))\n    except keys.BadKeyError:\n        sys.exit('bad key')\n\n\n\ndef changePassPhrase(options):\n    if not options['filename']:\n        filename = os.path.expanduser('~/.ssh/id_rsa')\n        options['filename'] = raw_input(\n            'Enter file in which the key is (%s): ' % filename)\n    try:\n        key = keys.Key.fromFile(options['filename'])\n    except keys.EncryptedKeyError:\n        # Raised if password not supplied for an encrypted key\n        if not options.get('pass'):\n            options['pass'] = getpass.getpass('Enter old passphrase: ')\n        try:\n            key = keys.Key.fromFile(\n                options['filename'], passphrase=options['pass'])\n        except keys.BadKeyError:\n            sys.exit('Could not change passphrase: old passphrase error')\n        except keys.EncryptedKeyError as e:\n            sys.exit('Could not change passphrase: %s' % (e,))\n    except keys.BadKeyError as e:\n        sys.exit('Could not change passphrase: %s' % (e,))\n\n    if not options.get('newpass'):\n        while 1:\n            p1 = getpass.getpass(\n                'Enter new passphrase (empty for no passphrase): ')\n            p2 = getpass.getpass('Enter same passphrase again: ')\n            if p1 == p2:\n                break\n            print('Passphrases do not match.  Try again.')\n        options['newpass'] = p1\n\n    try:\n        newkeydata = key.toString('openssh', extra=options['newpass'])\n    except Exception as e:\n        sys.exit('Could not change passphrase: %s' % (e,))\n\n    try:\n        keys.Key.fromString(newkeydata, passphrase=options['newpass'])\n    except (keys.EncryptedKeyError, keys.BadKeyError) as e:\n        sys.exit('Could not change passphrase: %s' % (e,))\n\n    with open(options['filename'], 'wb') as fd:\n        fd.write(newkeydata)\n\n    print('Your identification has been saved with the new passphrase.')\n\n\n\ndef displayPublicKey(options):\n    if not options['filename']:\n        filename = os.path.expanduser('~/.ssh/id_rsa')\n        options['filename'] = raw_input('Enter file in which the key is (%s): ' % filename)\n    try:\n        key = keys.Key.fromFile(options['filename'])\n    except keys.EncryptedKeyError:\n        if not options.get('pass'):\n            options['pass'] = getpass.getpass('Enter passphrase: ')\n        key = keys.Key.fromFile(\n            options['filename'], passphrase = options['pass'])\n    displayKey = key.public().toString('openssh')\n    if _PY3:\n        displayKey = displayKey.decode(\"ascii\")\n    print(displayKey)\n\n\n\ndef _saveKey(key, options):\n    \"\"\"\n    Persist a SSH key on local filesystem.\n\n    @param key: Key which is persisted on local filesystem.\n    @type key: C{keys.Key} implementation.\n\n    @param options:\n    @type options: L{dict}\n    \"\"\"\n    KeyTypeMapping = {'EC': 'ecdsa', 'RSA': 'rsa', 'DSA': 'dsa'}\n    keyTypeName = KeyTypeMapping[key.type()]\n    if not options['filename']:\n        defaultPath = os.path.expanduser(u'~/.ssh/id_%s' % (keyTypeName,))\n        newPath = raw_input(\n            'Enter file in which to save the key (%s): ' % (defaultPath,))\n\n        options['filename'] = newPath.strip() or defaultPath\n\n    if os.path.exists(options['filename']):\n        print('%s already exists.' % (options['filename'],))\n        yn = raw_input('Overwrite (y/n)? ')\n        if yn[0].lower() != 'y':\n            sys.exit()\n\n    if options.get('no-passphrase'):\n        options['pass'] = b''\n    elif not options['pass']:\n        while 1:\n            p1 = getpass.getpass('Enter passphrase (empty for no passphrase): ')\n            p2 = getpass.getpass('Enter same passphrase again: ')\n            if p1 == p2:\n                break\n            print('Passphrases do not match.  Try again.')\n        options['pass'] = p1\n\n    comment = '%s@%s' % (getpass.getuser(), socket.gethostname())\n\n    filepath.FilePath(options['filename']).setContent(\n        key.toString('openssh', options['pass']))\n    os.chmod(options['filename'], 33152)\n\n    filepath.FilePath(options['filename'] + '.pub').setContent(\n        key.public().toString('openssh', comment))\n    options = enumrepresentation(options)\n\n    print('Your identification has been saved in %s' % (options['filename'],))\n    print('Your public key has been saved in %s.pub' % (options['filename'],))\n    print('The key fingerprint in %s is:' % (options['format'],))\n    print(key.fingerprint(options['format']))\n\n\n\nif __name__ == '__main__':\n    run()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/scripts/conch.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_conch -*-\n#\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n#\n# $Id: conch.py,v 1.65 2004/03/11 00:29:14 z3p Exp $\n\n#\"\"\" Implementation module for the `conch` command.\n#\"\"\"\nfrom __future__ import print_function\n\nfrom twisted.conch.client import connect, default, options\nfrom twisted.conch.error import ConchError\nfrom twisted.conch.ssh import connection, common\nfrom twisted.conch.ssh import session, forwarding, channel\nfrom twisted.internet import reactor, stdio, task\nfrom twisted.python import log, usage\nfrom twisted.python.compat import ioType, networkString, unicode\n\nimport os\nimport sys\nimport getpass\nimport struct\nimport tty\nimport fcntl\nimport signal\n\n\n\nclass ClientOptions(options.ConchOptions):\n\n    synopsis = \"\"\"Usage:   conch [options] host [command]\n\"\"\"\n    longdesc = (\"conch is a SSHv2 client that allows logging into a remote \"\n                \"machine and executing commands.\")\n\n    optParameters = [['escape', 'e', '~'],\n                      ['localforward', 'L', None, 'listen-port:host:port   Forward local port to remote address'],\n                      ['remoteforward', 'R', None, 'listen-port:host:port   Forward remote port to local address'],\n                     ]\n\n    optFlags = [['null', 'n', 'Redirect input from /dev/null.'],\n                 ['fork', 'f', 'Fork to background after authentication.'],\n                 ['tty', 't', 'Tty; allocate a tty even if command is given.'],\n                 ['notty', 'T', 'Do not allocate a tty.'],\n                 ['noshell', 'N', 'Do not execute a shell or command.'],\n                 ['subsystem', 's', 'Invoke command (mandatory) as SSH2 subsystem.'],\n                ]\n\n    compData = usage.Completions(\n        mutuallyExclusive=[(\"tty\", \"notty\")],\n        optActions={\n            \"localforward\": usage.Completer(descr=\"listen-port:host:port\"),\n            \"remoteforward\": usage.Completer(descr=\"listen-port:host:port\")},\n        extraActions=[usage.CompleteUserAtHost(),\n                      usage.Completer(descr=\"command\"),\n                      usage.Completer(descr=\"argument\", repeat=True)]\n        )\n\n    localForwards = []\n    remoteForwards = []\n\n    def opt_escape(self, esc):\n        \"\"\"\n        Set escape character; ``none'' = disable\n        \"\"\"\n        if esc == 'none':\n            self['escape'] = None\n        elif esc[0] == '^' and len(esc) == 2:\n            self['escape'] = chr(ord(esc[1])-64)\n        elif len(esc) == 1:\n            self['escape'] = esc\n        else:\n            sys.exit(\"Bad escape character '{}'.\".format(esc))\n\n\n    def opt_localforward(self, f):\n        \"\"\"\n        Forward local port to remote address (lport:host:port)\n        \"\"\"\n        localPort, remoteHost, remotePort = f.split(':')  # Doesn't do v6 yet\n        localPort = int(localPort)\n        remotePort = int(remotePort)\n        self.localForwards.append((localPort, (remoteHost, remotePort)))\n\n\n    def opt_remoteforward(self, f):\n        \"\"\"\n        Forward remote port to local address (rport:host:port)\n        \"\"\"\n        remotePort, connHost, connPort = f.split(':')  # Doesn't do v6 yet\n        remotePort = int(remotePort)\n        connPort = int(connPort)\n        self.remoteForwards.append((remotePort, (connHost, connPort)))\n\n\n    def parseArgs(self, host, *command):\n        self['host'] = host\n        self['command'] = ' '.join(command)\n\n\n\n# Rest of code in \"run\"\noptions = None\nconn = None\nexitStatus = 0\nold = None\n_inRawMode = 0\n_savedRawMode = None\n\n\n\ndef run():\n    global options, old\n    args = sys.argv[1:]\n    if '-l' in args:  # CVS is an idiot\n        i = args.index('-l')\n        args = args[i:i+2]+args\n        del args[i+2:i+4]\n    for arg in args[:]:\n        try:\n            i = args.index(arg)\n            if arg[:2] == '-o' and args[i+1][0] != '-':\n                args[i:i+2] = []  # Suck on it scp\n        except ValueError:\n            pass\n    options = ClientOptions()\n    try:\n        options.parseOptions(args)\n    except usage.UsageError as u:\n        print('ERROR: {}'.format(u))\n        options.opt_help()\n        sys.exit(1)\n    if options['log']:\n        if options['logfile']:\n            if options['logfile'] == '-':\n                f = sys.stdout\n            else:\n                f = open(options['logfile'], 'a+')\n        else:\n            f = sys.stderr\n        realout = sys.stdout\n        log.startLogging(f)\n        sys.stdout = realout\n    else:\n        log.discardLogs()\n    doConnect()\n    fd = sys.stdin.fileno()\n    try:\n        old = tty.tcgetattr(fd)\n    except:\n        old = None\n    try:\n        oldUSR1 = signal.signal(signal.SIGUSR1, lambda *a: reactor.callLater(0, reConnect))\n    except:\n        oldUSR1 = None\n    try:\n        reactor.run()\n    finally:\n        if old:\n            tty.tcsetattr(fd, tty.TCSANOW, old)\n        if oldUSR1:\n            signal.signal(signal.SIGUSR1, oldUSR1)\n        if (options['command'] and options['tty']) or not options['notty']:\n            signal.signal(signal.SIGWINCH, signal.SIG_DFL)\n    if sys.stdout.isatty() and not options['command']:\n        print('Connection to {} closed.'.format(options['host']))\n    sys.exit(exitStatus)\n\n\n\ndef handleError():\n    from twisted.python import failure\n    global exitStatus\n    exitStatus = 2\n    reactor.callLater(0.01, _stopReactor)\n    log.err(failure.Failure())\n    raise\n\n\n\ndef _stopReactor():\n    try:\n        reactor.stop()\n    except: pass\n\n\n\ndef doConnect():\n    if '@' in options['host']:\n        options['user'], options['host'] = options['host'].split('@', 1)\n    if not options.identitys:\n        options.identitys = ['~/.ssh/id_rsa', '~/.ssh/id_dsa']\n    host = options['host']\n    if not options['user']:\n        options['user'] = getpass.getuser()\n    if not options['port']:\n        options['port'] = 22\n    else:\n        options['port'] = int(options['port'])\n    host = options['host']\n    port = options['port']\n    vhk = default.verifyHostKey\n    if not options['host-key-algorithms']:\n        options['host-key-algorithms'] = default.getHostKeyAlgorithms(\n                                             host, options)\n    uao = default.SSHUserAuthClient(options['user'], options, SSHConnection())\n    connect.connect(host, port, options, vhk, uao).addErrback(_ebExit)\n\n\n\ndef _ebExit(f):\n    global exitStatus\n    exitStatus = \"conch: exiting with error {}\".format(f)\n    reactor.callLater(0.1, _stopReactor)\n\n\n\ndef onConnect():\n#    if keyAgent and options['agent']:\n#        cc = protocol.ClientCreator(reactor, SSHAgentForwardingLocal, conn)\n#        cc.connectUNIX(os.environ['SSH_AUTH_SOCK'])\n    if hasattr(conn.transport, 'sendIgnore'):\n        _KeepAlive(conn)\n    if options.localForwards:\n        for localPort, hostport in options.localForwards:\n            s = reactor.listenTCP(localPort,\n                        forwarding.SSHListenForwardingFactory(conn,\n                            hostport,\n                            SSHListenClientForwardingChannel))\n            conn.localForwards.append(s)\n    if options.remoteForwards:\n        for remotePort, hostport in options.remoteForwards:\n            log.msg('asking for remote forwarding for {}:{}'.format(\n                remotePort, hostport))\n            conn.requestRemoteForwarding(remotePort, hostport)\n        reactor.addSystemEventTrigger('before', 'shutdown', beforeShutdown)\n    if not options['noshell'] or options['agent']:\n        conn.openChannel(SSHSession())\n    if options['fork']:\n        if os.fork():\n            os._exit(0)\n        os.setsid()\n        for i in range(3):\n            try:\n                os.close(i)\n            except OSError as e:\n                import errno\n                if e.errno != errno.EBADF:\n                    raise\n\n\n\ndef reConnect():\n    beforeShutdown()\n    conn.transport.transport.loseConnection()\n\n\n\ndef beforeShutdown():\n    remoteForwards = options.remoteForwards\n    for remotePort, hostport in remoteForwards:\n        log.msg('cancelling {}:{}'.format(remotePort, hostport))\n        conn.cancelRemoteForwarding(remotePort)\n\n\n\ndef stopConnection():\n    if not options['reconnect']:\n        reactor.callLater(0.1, _stopReactor)\n\n\n\nclass _KeepAlive:\n\n    def __init__(self, conn):\n        self.conn = conn\n        self.globalTimeout = None\n        self.lc = task.LoopingCall(self.sendGlobal)\n        self.lc.start(300)\n\n\n    def sendGlobal(self):\n        d = self.conn.sendGlobalRequest(b\"conch-keep-alive@twistedmatrix.com\",\n                                        b\"\", wantReply=1)\n        d.addBoth(self._cbGlobal)\n        self.globalTimeout = reactor.callLater(30, self._ebGlobal)\n\n\n    def _cbGlobal(self, res):\n        if self.globalTimeout:\n            self.globalTimeout.cancel()\n            self.globalTimeout = None\n\n\n    def _ebGlobal(self):\n        if self.globalTimeout:\n            self.globalTimeout = None\n            self.conn.transport.loseConnection()\n\n\n\nclass SSHConnection(connection.SSHConnection):\n    def serviceStarted(self):\n        global conn\n        conn = self\n        self.localForwards = []\n        self.remoteForwards = {}\n        if not isinstance(self, connection.SSHConnection):\n            # make these fall through\n            del self.__class__.requestRemoteForwarding\n            del self.__class__.cancelRemoteForwarding\n        onConnect()\n\n\n    def serviceStopped(self):\n        lf = self.localForwards\n        self.localForwards = []\n        for s in lf:\n            s.loseConnection()\n        stopConnection()\n\n\n    def requestRemoteForwarding(self, remotePort, hostport):\n        data = forwarding.packGlobal_tcpip_forward(('0.0.0.0', remotePort))\n        d = self.sendGlobalRequest(b'tcpip-forward', data,\n                                   wantReply=1)\n        log.msg('requesting remote forwarding {}:{}'.format(\n            remotePort, hostport))\n        d.addCallback(self._cbRemoteForwarding, remotePort, hostport)\n        d.addErrback(self._ebRemoteForwarding, remotePort, hostport)\n\n\n    def _cbRemoteForwarding(self, result, remotePort, hostport):\n        log.msg('accepted remote forwarding {}:{}'.format(\n            remotePort, hostport))\n        self.remoteForwards[remotePort] = hostport\n        log.msg(repr(self.remoteForwards))\n\n\n    def _ebRemoteForwarding(self, f, remotePort, hostport):\n        log.msg('remote forwarding {}:{} failed'.format(\n            remotePort, hostport))\n        log.msg(f)\n\n\n    def cancelRemoteForwarding(self, remotePort):\n        data = forwarding.packGlobal_tcpip_forward(('0.0.0.0', remotePort))\n        self.sendGlobalRequest(b'cancel-tcpip-forward', data)\n        log.msg('cancelling remote forwarding {}'.format(remotePort))\n        try:\n            del self.remoteForwards[remotePort]\n        except Exception:\n            pass\n        log.msg(repr(self.remoteForwards))\n\n\n    def channel_forwarded_tcpip(self, windowSize, maxPacket, data):\n        log.msg('FTCP {!r}'.format(data))\n        remoteHP, origHP = forwarding.unpackOpen_forwarded_tcpip(data)\n        log.msg(self.remoteForwards)\n        log.msg(remoteHP)\n        if remoteHP[1] in self.remoteForwards:\n            connectHP = self.remoteForwards[remoteHP[1]]\n            log.msg('connect forwarding {}'.format(connectHP))\n            return SSHConnectForwardingChannel(connectHP,\n                                               remoteWindow=windowSize,\n                                               remoteMaxPacket=maxPacket,\n                                               conn=self)\n        else:\n            raise ConchError(connection.OPEN_CONNECT_FAILED,\n                             \"don't know about that port\")\n\n\n    def channelClosed(self, channel):\n        log.msg('connection closing {}'.format(channel))\n        log.msg(self.channels)\n        if len(self.channels) == 1:  # Just us left\n            log.msg('stopping connection')\n            stopConnection()\n        else:\n            # Because of the unix thing\n            self.__class__.__bases__[0].channelClosed(self, channel)\n\n\n\nclass SSHSession(channel.SSHChannel):\n\n    name = b'session'\n\n    def channelOpen(self, foo):\n        log.msg('session {} open'.format(self.id))\n        if options['agent']:\n            d = self.conn.sendRequest(self, b'auth-agent-req@openssh.com',\n                                      b'', wantReply=1)\n            d.addBoth(lambda x: log.msg(x))\n        if options['noshell']:\n            return\n        if (options['command'] and options['tty']) or not options['notty']:\n            _enterRawMode()\n        c = session.SSHSessionClient()\n        if options['escape'] and not options['notty']:\n            self.escapeMode = 1\n            c.dataReceived = self.handleInput\n        else:\n            c.dataReceived = self.write\n        c.connectionLost = lambda x: self.sendEOF()\n        self.stdio = stdio.StandardIO(c)\n        fd = 0\n        if options['subsystem']:\n            self.conn.sendRequest(self, b'subsystem',\n                                  common.NS(options['command']))\n        elif options['command']:\n            if options['tty']:\n                term = os.environ['TERM']\n                winsz = fcntl.ioctl(fd, tty.TIOCGWINSZ, '12345678')\n                winSize = struct.unpack('4H', winsz)\n                ptyReqData = session.packRequest_pty_req(term, winSize, '')\n                self.conn.sendRequest(self, b'pty-req', ptyReqData)\n                signal.signal(signal.SIGWINCH, self._windowResized)\n            self.conn.sendRequest(self, b'exec', common.NS(options['command']))\n        else:\n            if not options['notty']:\n                term = os.environ['TERM']\n                winsz = fcntl.ioctl(fd, tty.TIOCGWINSZ, '12345678')\n                winSize = struct.unpack('4H', winsz)\n                ptyReqData = session.packRequest_pty_req(term, winSize, '')\n                self.conn.sendRequest(self, b'pty-req', ptyReqData)\n                signal.signal(signal.SIGWINCH, self._windowResized)\n            self.conn.sendRequest(self, b'shell', b'')\n            #if hasattr(conn.transport, 'transport'):\n            #    conn.transport.transport.setTcpNoDelay(1)\n\n\n    def handleInput(self, char):\n        if char in (b'\\n', b'\\r'):\n            self.escapeMode = 1\n            self.write(char)\n        elif self.escapeMode == 1 and char == options['escape']:\n            self.escapeMode = 2\n        elif self.escapeMode == 2:\n            self.escapeMode = 1  # So we can chain escapes together\n            if char == b'.':  # Disconnect\n                log.msg('disconnecting from escape')\n                stopConnection()\n                return\n            elif char == b'\\x1a':  # ^Z, suspend\n                def _():\n                    _leaveRawMode()\n                    sys.stdout.flush()\n                    sys.stdin.flush()\n                    os.kill(os.getpid(), signal.SIGTSTP)\n                    _enterRawMode()\n                reactor.callLater(0, _)\n                return\n            elif char == b'R':  # Rekey connection\n                log.msg('rekeying connection')\n                self.conn.transport.sendKexInit()\n                return\n            elif char == b'#':  # Display connections\n                self.stdio.write(\n                    b'\\r\\nThe following connections are open:\\r\\n')\n                channels = self.conn.channels.keys()\n                channels.sort()\n                for channelId in channels:\n                    self.stdio.write(networkString('  #{} {}\\r\\n'.format(\n                                     channelId,\n                                     self.conn.channels[channelId])))\n                return\n            self.write(b'~' + char)\n        else:\n            self.escapeMode = 0\n            self.write(char)\n\n\n    def dataReceived(self, data):\n        self.stdio.write(data)\n\n\n    def extReceived(self, t, data):\n        if t == connection.EXTENDED_DATA_STDERR:\n            log.msg('got {} stderr data'.format(len(data)))\n            if ioType(sys.stderr) == unicode:\n                sys.stderr.buffer.write(data)\n            else:\n                sys.stderr.write(data)\n\n\n    def eofReceived(self):\n        log.msg('got eof')\n        self.stdio.loseWriteConnection()\n\n\n    def closeReceived(self):\n        log.msg('remote side closed {}'.format(self))\n        self.conn.sendClose(self)\n\n\n    def closed(self):\n        global old\n        log.msg('closed {}'.format(self))\n        log.msg(repr(self.conn.channels))\n\n\n    def request_exit_status(self, data):\n        global exitStatus\n        exitStatus = int(struct.unpack('>L', data)[0])\n        log.msg('exit status: {}'.format(exitStatus))\n\n\n    def sendEOF(self):\n        self.conn.sendEOF(self)\n\n\n    def stopWriting(self):\n        self.stdio.pauseProducing()\n\n\n    def startWriting(self):\n        self.stdio.resumeProducing()\n\n\n    def _windowResized(self, *args):\n        winsz = fcntl.ioctl(0, tty.TIOCGWINSZ, '12345678')\n        winSize = struct.unpack('4H', winsz)\n        newSize = winSize[1], winSize[0], winSize[2], winSize[3]\n        self.conn.sendRequest(self, b'window-change', struct.pack('!4L', *newSize))\n\n\n\nclass SSHListenClientForwardingChannel(forwarding.SSHListenClientForwardingChannel): pass\nclass SSHConnectForwardingChannel(forwarding.SSHConnectForwardingChannel): pass\n\n\n\ndef _leaveRawMode():\n    global _inRawMode\n    if not _inRawMode:\n        return\n    fd = sys.stdin.fileno()\n    tty.tcsetattr(fd, tty.TCSANOW, _savedRawMode)\n    _inRawMode = 0\n\n\n\ndef _enterRawMode():\n    global _inRawMode, _savedRawMode\n    if _inRawMode:\n        return\n    fd = sys.stdin.fileno()\n    try:\n        old = tty.tcgetattr(fd)\n        new = old[:]\n    except:\n        log.msg('not a typewriter!')\n    else:\n        # iflage\n        new[0] = new[0] | tty.IGNPAR\n        new[0] = new[0] & ~(tty.ISTRIP | tty.INLCR | tty.IGNCR | tty.ICRNL |\n                            tty.IXON | tty.IXANY | tty.IXOFF)\n        if hasattr(tty, 'IUCLC'):\n            new[0] = new[0] & ~tty.IUCLC\n\n        # lflag\n        new[3] = new[3] & ~(tty.ISIG | tty.ICANON | tty.ECHO | tty.ECHO |\n                            tty.ECHOE | tty.ECHOK | tty.ECHONL)\n        if hasattr(tty, 'IEXTEN'):\n            new[3] = new[3] & ~tty.IEXTEN\n\n        #oflag\n        new[1] = new[1] & ~tty.OPOST\n\n        new[6][tty.VMIN] = 1\n        new[6][tty.VTIME] = 0\n\n        _savedRawMode = old\n        tty.tcsetattr(fd, tty.TCSANOW, new)\n        #tty.setraw(fd)\n        _inRawMode = 1\n\n\n\nif __name__ == '__main__':\n    run()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/scripts/tkconch.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_scripts -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nImplementation module for the `tkconch` command.\n\"\"\"\n\nfrom __future__ import print_function\n\nfrom twisted.conch import error\nfrom twisted.conch.ui import tkvt100\nfrom twisted.conch.ssh import transport, userauth, connection, common, keys\nfrom twisted.conch.ssh import session, forwarding, channel\nfrom twisted.conch.client.default import isInKnownHosts\nfrom twisted.internet import reactor, defer, protocol, tksupport\nfrom twisted.python import usage, log\nfrom twisted.python.compat import _PY3\n\nimport os, sys, getpass, struct, base64, signal\n\nif _PY3:\n    import tkinter as Tkinter\n    import tkinter.filedialog as tkFileDialog\n    import tkinter.messagebox as tkMessageBox\nelse:\n    import Tkinter, tkFileDialog, tkMessageBox\n\nclass TkConchMenu(Tkinter.Frame):\n    def __init__(self, *args, **params):\n        ## Standard heading: initialization\n        Tkinter.Frame.__init__(self, *args, **params)\n\n        self.master.title('TkConch')\n        self.localRemoteVar = Tkinter.StringVar()\n        self.localRemoteVar.set('local')\n\n        Tkinter.Label(self, anchor='w', justify='left', text='Hostname').grid(column=1, row=1, sticky='w')\n        self.host = Tkinter.Entry(self)\n        self.host.grid(column=2, columnspan=2, row=1, sticky='nesw')\n\n        Tkinter.Label(self, anchor='w', justify='left', text='Port').grid(column=1, row=2, sticky='w')\n        self.port = Tkinter.Entry(self)\n        self.port.grid(column=2, columnspan=2, row=2, sticky='nesw')\n\n        Tkinter.Label(self, anchor='w', justify='left', text='Username').grid(column=1, row=3, sticky='w')\n        self.user = Tkinter.Entry(self)\n        self.user.grid(column=2, columnspan=2, row=3, sticky='nesw')\n\n        Tkinter.Label(self, anchor='w', justify='left', text='Command').grid(column=1, row=4, sticky='w')\n        self.command = Tkinter.Entry(self)\n        self.command.grid(column=2, columnspan=2, row=4, sticky='nesw')\n\n        Tkinter.Label(self, anchor='w', justify='left', text='Identity').grid(column=1, row=5, sticky='w')\n        self.identity = Tkinter.Entry(self)\n        self.identity.grid(column=2, row=5, sticky='nesw')\n        Tkinter.Button(self, command=self.getIdentityFile, text='Browse').grid(column=3, row=5, sticky='nesw')\n\n        Tkinter.Label(self, text='Port Forwarding').grid(column=1, row=6, sticky='w')\n        self.forwards = Tkinter.Listbox(self, height=0, width=0)\n        self.forwards.grid(column=2, columnspan=2, row=6, sticky='nesw')\n        Tkinter.Button(self, text='Add', command=self.addForward).grid(column=1, row=7)\n        Tkinter.Button(self, text='Remove', command=self.removeForward).grid(column=1, row=8)\n        self.forwardPort = Tkinter.Entry(self)\n        self.forwardPort.grid(column=2, row=7, sticky='nesw')\n        Tkinter.Label(self, text='Port').grid(column=3, row=7, sticky='nesw')\n        self.forwardHost = Tkinter.Entry(self)\n        self.forwardHost.grid(column=2, row=8, sticky='nesw')\n        Tkinter.Label(self, text='Host').grid(column=3, row=8, sticky='nesw')\n        self.localForward = Tkinter.Radiobutton(self, text='Local', variable=self.localRemoteVar, value='local')\n        self.localForward.grid(column=2, row=9)\n        self.remoteForward = Tkinter.Radiobutton(self, text='Remote', variable=self.localRemoteVar, value='remote')\n        self.remoteForward.grid(column=3, row=9)\n\n        Tkinter.Label(self, text='Advanced Options').grid(column=1, columnspan=3, row=10, sticky='nesw')\n\n        Tkinter.Label(self, anchor='w', justify='left', text='Cipher').grid(column=1, row=11, sticky='w')\n        self.cipher = Tkinter.Entry(self, name='cipher')\n        self.cipher.grid(column=2, columnspan=2, row=11, sticky='nesw')\n\n        Tkinter.Label(self, anchor='w', justify='left', text='MAC').grid(column=1, row=12, sticky='w')\n        self.mac = Tkinter.Entry(self, name='mac')\n        self.mac.grid(column=2, columnspan=2, row=12, sticky='nesw')\n\n        Tkinter.Label(self, anchor='w', justify='left', text='Escape Char').grid(column=1, row=13, sticky='w')\n        self.escape = Tkinter.Entry(self, name='escape')\n        self.escape.grid(column=2, columnspan=2, row=13, sticky='nesw')\n        Tkinter.Button(self, text='Connect!', command=self.doConnect).grid(column=1, columnspan=3, row=14, sticky='nesw')\n\n        # Resize behavior(s)\n        self.grid_rowconfigure(6, weight=1, minsize=64)\n        self.grid_columnconfigure(2, weight=1, minsize=2)\n\n        self.master.protocol(\"WM_DELETE_WINDOW\", sys.exit)\n\n\n    def getIdentityFile(self):\n        r = tkFileDialog.askopenfilename()\n        if r:\n            self.identity.delete(0, Tkinter.END)\n            self.identity.insert(Tkinter.END, r)\n\n    def addForward(self):\n        port = self.forwardPort.get()\n        self.forwardPort.delete(0, Tkinter.END)\n        host = self.forwardHost.get()\n        self.forwardHost.delete(0, Tkinter.END)\n        if self.localRemoteVar.get() == 'local':\n            self.forwards.insert(Tkinter.END, 'L:%s:%s' % (port, host))\n        else:\n            self.forwards.insert(Tkinter.END, 'R:%s:%s' % (port, host))\n\n    def removeForward(self):\n        cur = self.forwards.curselection()\n        if cur:\n            self.forwards.remove(cur[0])\n\n    def doConnect(self):\n        finished = 1\n        options['host'] = self.host.get()\n        options['port'] = self.port.get()\n        options['user'] = self.user.get()\n        options['command'] = self.command.get()\n        cipher = self.cipher.get()\n        mac = self.mac.get()\n        escape = self.escape.get()\n        if cipher:\n            if cipher in SSHClientTransport.supportedCiphers:\n                SSHClientTransport.supportedCiphers = [cipher]\n            else:\n                tkMessageBox.showerror('TkConch', 'Bad cipher.')\n                finished = 0\n\n        if mac:\n            if mac in SSHClientTransport.supportedMACs:\n                SSHClientTransport.supportedMACs = [mac]\n            elif finished:\n                tkMessageBox.showerror('TkConch', 'Bad MAC.')\n                finished = 0\n\n        if escape:\n            if escape == 'none':\n                options['escape'] = None\n            elif escape[0] == '^' and len(escape) == 2:\n                options['escape'] = chr(ord(escape[1])-64)\n            elif len(escape) == 1:\n                options['escape'] = escape\n            elif finished:\n                tkMessageBox.showerror('TkConch', \"Bad escape character '%s'.\" % escape)\n                finished = 0\n\n        if self.identity.get():\n            options.identitys.append(self.identity.get())\n\n        for line in self.forwards.get(0,Tkinter.END):\n            if line[0]=='L':\n                options.opt_localforward(line[2:])\n            else:\n                options.opt_remoteforward(line[2:])\n\n        if '@' in options['host']:\n            options['user'], options['host'] = options['host'].split('@',1)\n\n        if (not options['host'] or not options['user']) and finished:\n            tkMessageBox.showerror('TkConch', 'Missing host or username.')\n            finished = 0\n        if finished:\n            self.master.quit()\n            self.master.destroy()\n            if options['log']:\n                realout = sys.stdout\n                log.startLogging(sys.stderr)\n                sys.stdout = realout\n            else:\n                log.discardLogs()\n            log.deferr = handleError # HACK\n            if not options.identitys:\n                options.identitys = ['~/.ssh/id_rsa', '~/.ssh/id_dsa']\n            host = options['host']\n            port = int(options['port'] or 22)\n            log.msg((host,port))\n            reactor.connectTCP(host, port, SSHClientFactory())\n            frame.master.deiconify()\n            frame.master.title('%s@%s - TkConch' % (options['user'], options['host']))\n        else:\n            self.focus()\n\nclass GeneralOptions(usage.Options):\n    synopsis = \"\"\"Usage:    tkconch [options] host [command]\n \"\"\"\n\n    optParameters = [['user', 'l', None, 'Log in using this user name.'],\n                    ['identity', 'i', '~/.ssh/identity', 'Identity for public key authentication'],\n                    ['escape', 'e', '~', \"Set escape character; ``none'' = disable\"],\n                    ['cipher', 'c', None, 'Select encryption algorithm.'],\n                    ['macs', 'm', None, 'Specify MAC algorithms for protocol version 2.'],\n                    ['port', 'p', None, 'Connect to this port.  Server must be on the same port.'],\n                    ['localforward', 'L', None, 'listen-port:host:port   Forward local port to remote address'],\n                    ['remoteforward', 'R', None, 'listen-port:host:port   Forward remote port to local address'],\n                    ]\n\n    optFlags = [['tty', 't', 'Tty; allocate a tty even if command is given.'],\n                ['notty', 'T', 'Do not allocate a tty.'],\n                ['version', 'V', 'Display version number only.'],\n                ['compress', 'C', 'Enable compression.'],\n                ['noshell', 'N', 'Do not execute a shell or command.'],\n                ['subsystem', 's', 'Invoke command (mandatory) as SSH2 subsystem.'],\n                ['log', 'v', 'Log to stderr'],\n                ['ansilog', 'a', 'Print the received data to stdout']]\n\n    _ciphers = transport.SSHClientTransport.supportedCiphers\n    _macs = transport.SSHClientTransport.supportedMACs\n\n    compData = usage.Completions(\n        mutuallyExclusive=[(\"tty\", \"notty\")],\n        optActions={\n            \"cipher\": usage.CompleteList(_ciphers),\n            \"macs\": usage.CompleteList(_macs),\n            \"localforward\": usage.Completer(descr=\"listen-port:host:port\"),\n            \"remoteforward\": usage.Completer(descr=\"listen-port:host:port\")},\n        extraActions=[usage.CompleteUserAtHost(),\n                      usage.Completer(descr=\"command\"),\n                      usage.Completer(descr=\"argument\", repeat=True)]\n        )\n\n    identitys = []\n    localForwards = []\n    remoteForwards = []\n\n    def opt_identity(self, i):\n        self.identitys.append(i)\n\n    def opt_localforward(self, f):\n        localPort, remoteHost, remotePort = f.split(':') # doesn't do v6 yet\n        localPort = int(localPort)\n        remotePort = int(remotePort)\n        self.localForwards.append((localPort, (remoteHost, remotePort)))\n\n    def opt_remoteforward(self, f):\n        remotePort, connHost, connPort = f.split(':') # doesn't do v6 yet\n        remotePort = int(remotePort)\n        connPort = int(connPort)\n        self.remoteForwards.append((remotePort, (connHost, connPort)))\n\n    def opt_compress(self):\n        SSHClientTransport.supportedCompressions[0:1] = ['zlib']\n\n    def parseArgs(self, *args):\n        if args:\n            self['host'] = args[0]\n            self['command'] = ' '.join(args[1:])\n        else:\n            self['host'] = ''\n            self['command'] = ''\n\n# Rest of code in \"run\"\noptions = None\nmenu = None\nexitStatus = 0\nframe = None\n\ndef deferredAskFrame(question, echo):\n    if frame.callback:\n        raise ValueError(\"can't ask 2 questions at once!\")\n    d = defer.Deferred()\n    resp = []\n    def gotChar(ch, resp=resp):\n        if not ch: return\n        if ch=='\\x03': # C-c\n            reactor.stop()\n        if ch=='\\r':\n            frame.write('\\r\\n')\n            stresp = ''.join(resp)\n            del resp\n            frame.callback = None\n            d.callback(stresp)\n            return\n        elif 32 <= ord(ch) < 127:\n            resp.append(ch)\n            if echo:\n                frame.write(ch)\n        elif ord(ch) == 8 and resp: # BS\n            if echo: frame.write('\\x08 \\x08')\n            resp.pop()\n    frame.callback = gotChar\n    frame.write(question)\n    frame.canvas.focus_force()\n    return d\n\ndef run():\n    global menu, options, frame\n    args = sys.argv[1:]\n    if '-l' in args: # cvs is an idiot\n        i = args.index('-l')\n        args = args[i:i+2]+args\n        del args[i+2:i+4]\n    for arg in args[:]:\n        try:\n            i = args.index(arg)\n            if arg[:2] == '-o' and args[i+1][0]!='-':\n                args[i:i+2] = [] # suck on it scp\n        except ValueError:\n            pass\n    root = Tkinter.Tk()\n    root.withdraw()\n    top = Tkinter.Toplevel()\n    menu = TkConchMenu(top)\n    menu.pack(side=Tkinter.TOP, fill=Tkinter.BOTH, expand=1)\n    options = GeneralOptions()\n    try:\n        options.parseOptions(args)\n    except usage.UsageError as u:\n        print('ERROR: %s' % u)\n        options.opt_help()\n        sys.exit(1)\n    for k,v in options.items():\n        if v and hasattr(menu, k):\n            getattr(menu,k).insert(Tkinter.END, v)\n    for (p, (rh, rp)) in options.localForwards:\n        menu.forwards.insert(Tkinter.END, 'L:%s:%s:%s' % (p, rh, rp))\n    options.localForwards = []\n    for (p, (rh, rp)) in options.remoteForwards:\n        menu.forwards.insert(Tkinter.END, 'R:%s:%s:%s' % (p, rh, rp))\n    options.remoteForwards = []\n    frame = tkvt100.VT100Frame(root, callback=None)\n    root.geometry('%dx%d'%(tkvt100.fontWidth*frame.width+3, tkvt100.fontHeight*frame.height+3))\n    frame.pack(side = Tkinter.TOP)\n    tksupport.install(root)\n    root.withdraw()\n    if (options['host'] and options['user']) or '@' in options['host']:\n        menu.doConnect()\n    else:\n        top.mainloop()\n    reactor.run()\n    sys.exit(exitStatus)\n\ndef handleError():\n    from twisted.python import failure\n    global exitStatus\n    exitStatus = 2\n    log.err(failure.Failure())\n    reactor.stop()\n    raise\n\nclass SSHClientFactory(protocol.ClientFactory):\n    noisy = 1\n\n    def stopFactory(self):\n        reactor.stop()\n\n    def buildProtocol(self, addr):\n        return SSHClientTransport()\n\n    def clientConnectionFailed(self, connector, reason):\n        tkMessageBox.showwarning('TkConch','Connection Failed, Reason:\\n %s: %s' % (reason.type, reason.value))\n\nclass SSHClientTransport(transport.SSHClientTransport):\n\n    def receiveError(self, code, desc):\n        global exitStatus\n        exitStatus = 'conch:\\tRemote side disconnected with error code %i\\nconch:\\treason: %s' % (code, desc)\n\n    def sendDisconnect(self, code, reason):\n        global exitStatus\n        exitStatus = 'conch:\\tSending disconnect with error code %i\\nconch:\\treason: %s' % (code, reason)\n        transport.SSHClientTransport.sendDisconnect(self, code, reason)\n\n    def receiveDebug(self, alwaysDisplay, message, lang):\n        global options\n        if alwaysDisplay or options['log']:\n            log.msg('Received Debug Message: %s' % message)\n\n    def verifyHostKey(self, pubKey, fingerprint):\n        #d = defer.Deferred()\n        #d.addCallback(lambda x:defer.succeed(1))\n        #d.callback(2)\n        #return d\n        goodKey = isInKnownHosts(options['host'], pubKey, {'known-hosts': None})\n        if goodKey == 1: # good key\n            return defer.succeed(1)\n        elif goodKey == 2: # AAHHHHH changed\n            return defer.fail(error.ConchError('bad host key'))\n        else:\n            if options['host'] == self.transport.getPeer().host:\n                host = options['host']\n                khHost = options['host']\n            else:\n                host = '%s (%s)' % (options['host'],\n                                    self.transport.getPeer().host)\n                khHost = '%s,%s' % (options['host'],\n                                    self.transport.getPeer().host)\n            keyType = common.getNS(pubKey)[0]\n            ques = \"\"\"The authenticity of host '%s' can't be established.\\r\n%s key fingerprint is %s.\"\"\" % (host,\n                                {b'ssh-dss':'DSA', b'ssh-rsa':'RSA'}[keyType],\n                                fingerprint)\n            ques+='\\r\\nAre you sure you want to continue connecting (yes/no)? '\n            return deferredAskFrame(ques, 1).addCallback(self._cbVerifyHostKey, pubKey, khHost, keyType)\n\n    def _cbVerifyHostKey(self, ans, pubKey, khHost, keyType):\n        if ans.lower() not in ('yes', 'no'):\n            return deferredAskFrame(\"Please type  'yes' or 'no': \",1).addCallback(self._cbVerifyHostKey, pubKey, khHost, keyType)\n        if ans.lower() == 'no':\n            frame.write('Host key verification failed.\\r\\n')\n            raise error.ConchError('bad host key')\n        try:\n            frame.write(\n                \"Warning: Permanently added '%s' (%s) to the list of \"\n                \"known hosts.\\r\\n\" %\n                (khHost, {b'ssh-dss':'DSA', b'ssh-rsa':'RSA'}[keyType]))\n            with open(os.path.expanduser('~/.ssh/known_hosts'), 'a') as known_hosts:\n                encodedKey = base64.encodestring(pubKey).replace(b'\\n', b'')\n                known_hosts.write('\\n%s %s %s' % (khHost, keyType, encodedKey))\n        except:\n            log.deferr()\n            raise error.ConchError\n\n    def connectionSecure(self):\n        if options['user']:\n            user = options['user']\n        else:\n            user = getpass.getuser()\n        self.requestService(SSHUserAuthClient(user, SSHConnection()))\n\nclass SSHUserAuthClient(userauth.SSHUserAuthClient):\n    usedFiles = []\n\n    def getPassword(self, prompt = None):\n        if not prompt:\n            prompt = \"%s@%s's password: \" % (self.user, options['host'])\n        return deferredAskFrame(prompt,0)\n\n    def getPublicKey(self):\n        files = [x for x in options.identitys if x not in self.usedFiles]\n        if not files:\n            return None\n        file = files[0]\n        log.msg(file)\n        self.usedFiles.append(file)\n        file = os.path.expanduser(file)\n        file += '.pub'\n        if not os.path.exists(file):\n            return\n        try:\n            return keys.Key.fromFile(file).blob()\n        except:\n            return self.getPublicKey() # try again\n\n    def getPrivateKey(self):\n        file = os.path.expanduser(self.usedFiles[-1])\n        if not os.path.exists(file):\n            return None\n        try:\n            return defer.succeed(keys.Key.fromFile(file).keyObject)\n        except keys.BadKeyError as e:\n            if e.args[0] == 'encrypted key with no password':\n                prompt = \"Enter passphrase for key '%s': \" % \\\n                       self.usedFiles[-1]\n                return deferredAskFrame(prompt, 0).addCallback(self._cbGetPrivateKey, 0)\n    def _cbGetPrivateKey(self, ans, count):\n        file = os.path.expanduser(self.usedFiles[-1])\n        try:\n            return keys.Key.fromFile(file, password = ans).keyObject\n        except keys.BadKeyError:\n            if count == 2:\n                raise\n            prompt = \"Enter passphrase for key '%s': \" % \\\n                   self.usedFiles[-1]\n            return deferredAskFrame(prompt, 0).addCallback(self._cbGetPrivateKey, count+1)\n\nclass SSHConnection(connection.SSHConnection):\n    def serviceStarted(self):\n        if not options['noshell']:\n            self.openChannel(SSHSession())\n        if options.localForwards:\n            for localPort, hostport in options.localForwards:\n                reactor.listenTCP(localPort,\n                            forwarding.SSHListenForwardingFactory(self,\n                                hostport,\n                                forwarding.SSHListenClientForwardingChannel))\n        if options.remoteForwards:\n            for remotePort, hostport in options.remoteForwards:\n                log.msg('asking for remote forwarding for %s:%s' %\n                        (remotePort, hostport))\n                data = forwarding.packGlobal_tcpip_forward(\n                    ('0.0.0.0', remotePort))\n                self.sendGlobalRequest('tcpip-forward', data)\n                self.remoteForwards[remotePort] = hostport\n\nclass SSHSession(channel.SSHChannel):\n\n    name = b'session'\n\n    def channelOpen(self, foo):\n        #global globalSession\n        #globalSession = self\n        # turn off local echo\n        self.escapeMode = 1\n        c = session.SSHSessionClient()\n        if options['escape']:\n            c.dataReceived = self.handleInput\n        else:\n            c.dataReceived = self.write\n        c.connectionLost = self.sendEOF\n        frame.callback = c.dataReceived\n        frame.canvas.focus_force()\n        if options['subsystem']:\n            self.conn.sendRequest(self, b'subsystem', \\\n                common.NS(options['command']))\n        elif options['command']:\n            if options['tty']:\n                term = os.environ.get('TERM', 'xterm')\n                #winsz = fcntl.ioctl(fd, tty.TIOCGWINSZ, '12345678')\n                winSize = (25,80,0,0) #struct.unpack('4H', winsz)\n                ptyReqData = session.packRequest_pty_req(term, winSize, '')\n                self.conn.sendRequest(self, b'pty-req', ptyReqData)\n            self.conn.sendRequest(self, 'exec', \\\n                common.NS(options['command']))\n        else:\n            if not options['notty']:\n                term = os.environ.get('TERM', 'xterm')\n                #winsz = fcntl.ioctl(fd, tty.TIOCGWINSZ, '12345678')\n                winSize = (25,80,0,0) #struct.unpack('4H', winsz)\n                ptyReqData = session.packRequest_pty_req(term, winSize, '')\n                self.conn.sendRequest(self, b'pty-req', ptyReqData)\n            self.conn.sendRequest(self, b'shell', b'')\n        self.conn.transport.transport.setTcpNoDelay(1)\n\n    def handleInput(self, char):\n        #log.msg('handling %s' % repr(char))\n        if char in ('\\n', '\\r'):\n            self.escapeMode = 1\n            self.write(char)\n        elif self.escapeMode == 1 and char == options['escape']:\n            self.escapeMode = 2\n        elif self.escapeMode == 2:\n            self.escapeMode = 1 # so we can chain escapes together\n            if char == '.': # disconnect\n                log.msg('disconnecting from escape')\n                reactor.stop()\n                return\n            elif char == '\\x1a': # ^Z, suspend\n                # following line courtesy of Erwin@freenode\n                os.kill(os.getpid(), signal.SIGSTOP)\n                return\n            elif char == 'R': # rekey connection\n                log.msg('rekeying connection')\n                self.conn.transport.sendKexInit()\n                return\n            self.write('~' + char)\n        else:\n            self.escapeMode = 0\n            self.write(char)\n\n    def dataReceived(self, data):\n        if _PY3 and isinstance(data, bytes):\n            data = data.decode(\"utf-8\")\n        if options['ansilog']:\n            print(repr(data))\n        frame.write(data)\n\n    def extReceived(self, t, data):\n        if t==connection.EXTENDED_DATA_STDERR:\n            log.msg('got %s stderr data' % len(data))\n            sys.stderr.write(data)\n            sys.stderr.flush()\n\n    def eofReceived(self):\n        log.msg('got eof')\n        sys.stdin.close()\n\n    def closed(self):\n        log.msg('closed %s' % self)\n        if len(self.conn.channels) == 1: # just us left\n            reactor.stop()\n\n    def request_exit_status(self, data):\n        global exitStatus\n        exitStatus = int(struct.unpack('>L', data)[0])\n        log.msg('exit status: %s' % exitStatus)\n\n    def sendEOF(self):\n        self.conn.sendEOF(self)\n\nif __name__==\"__main__\":\n    run()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n# \n\n\"\"\"\nAn SSHv2 implementation for Twisted.  Part of the Twisted.Conch package.\n\nMaintainer: Paul Swartz\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/_kex.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_transport -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nSSH key exchange handling.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom hashlib import sha1, sha256, sha384, sha512\n\nfrom zope.interface import Attribute, implementer, Interface\n\nfrom twisted.conch import error\nfrom twisted.python.compat import long\n\n\nclass _IKexAlgorithm(Interface):\n    \"\"\"\n    An L{_IKexAlgorithm} describes a key exchange algorithm.\n    \"\"\"\n\n    preference = Attribute(\n        \"An L{int} giving the preference of the algorithm when negotiating \"\n        \"key exchange. Algorithms with lower precedence values are more \"\n        \"preferred.\")\n\n    hashProcessor = Attribute(\n        \"A callable hash algorithm constructor (e.g. C{hashlib.sha256}) \"\n        \"suitable for use with this key exchange algorithm.\")\n\n\n\nclass _IFixedGroupKexAlgorithm(_IKexAlgorithm):\n    \"\"\"\n    An L{_IFixedGroupKexAlgorithm} describes a key exchange algorithm with a\n    fixed prime / generator group.\n    \"\"\"\n\n    prime = Attribute(\n        \"A L{long} giving the prime number used in Diffie-Hellman key \"\n        \"exchange, or L{None} if not applicable.\")\n\n    generator = Attribute(\n        \"A L{long} giving the generator number used in Diffie-Hellman key \"\n        \"exchange, or L{None} if not applicable. (This is not related to \"\n        \"Python generator functions.)\")\n\n\n\nclass _IEllipticCurveExchangeKexAlgorithm(_IKexAlgorithm):\n    \"\"\"\n    An L{_IEllipticCurveExchangeKexAlgorithm} describes a key exchange algorithm\n    that uses an elliptic curve exchange between the client and server.\n    \"\"\"\n\n\n\nclass _IGroupExchangeKexAlgorithm(_IKexAlgorithm):\n    \"\"\"\n    An L{_IGroupExchangeKexAlgorithm} describes a key exchange algorithm\n    that uses group exchange between the client and server.\n\n    A prime / generator group should be chosen at run time based on the\n    requested size. See RFC 4419.\n    \"\"\"\n\n\n\n@implementer(_IEllipticCurveExchangeKexAlgorithm)\nclass _ECDH256(object):\n    \"\"\"\n    Elliptic Curve Key Exchange with SHA-256 as HASH. Defined in\n    RFC 5656.\n    \"\"\"\n    preference = 1\n    hashProcessor = sha256\n\n\n\n@implementer(_IEllipticCurveExchangeKexAlgorithm)\nclass _ECDH384(object):\n    \"\"\"\n    Elliptic Curve Key Exchange with SHA-384 as HASH. Defined in\n    RFC 5656.\n    \"\"\"\n    preference = 2\n    hashProcessor = sha384\n\n\n\n@implementer(_IEllipticCurveExchangeKexAlgorithm)\nclass _ECDH512(object):\n    \"\"\"\n    Elliptic Curve Key Exchange with SHA-512 as HASH. Defined in\n    RFC 5656.\n    \"\"\"\n    preference = 3\n    hashProcessor = sha512\n\n\n\n@implementer(_IGroupExchangeKexAlgorithm)\nclass _DHGroupExchangeSHA256(object):\n    \"\"\"\n    Diffie-Hellman Group and Key Exchange with SHA-256 as HASH. Defined in\n    RFC 4419, 4.2.\n    \"\"\"\n\n    preference = 4\n    hashProcessor = sha256\n\n\n\n@implementer(_IGroupExchangeKexAlgorithm)\nclass _DHGroupExchangeSHA1(object):\n    \"\"\"\n    Diffie-Hellman Group and Key Exchange with SHA-1 as HASH. Defined in\n    RFC 4419, 4.1.\n    \"\"\"\n\n    preference = 5\n    hashProcessor = sha1\n\n\n\n@implementer(_IFixedGroupKexAlgorithm)\nclass _DHGroup14SHA1(object):\n    \"\"\"\n    Diffie-Hellman key exchange with SHA-1 as HASH and Oakley Group 14\n    (2048-bit MODP Group). Defined in RFC 4253, 8.2.\n    \"\"\"\n\n    preference = 7\n    hashProcessor = sha1\n    # Diffie-Hellman primes from Oakley Group 14 (RFC 3526, 3).\n    prime = long('32317006071311007300338913926423828248817941241140239112842'\n        '00975140074170663435422261968941736356934711790173790970419175460587'\n        '32091950288537589861856221532121754125149017745202702357960782362488'\n        '84246189477587641105928646099411723245426622522193230540919037680524'\n        '23551912567971587011700105805587765103886184728025797605490356973256'\n        '15261670813393617995413364765591603683178967290731783845896806396719'\n        '00977202194168647225871031411336429319536193471636533209717077448227'\n        '98858856536920864529663607725026895550592836275112117409697299806841'\n        '05543595848665832916421362182310789909994486524682624169720359118525'\n        '07045361090559')\n    generator = 2\n\n\n\n# Which ECDH hash function to use is dependent on the size.\n_kexAlgorithms = {\n    b\"diffie-hellman-group-exchange-sha256\": _DHGroupExchangeSHA256(),\n    b\"diffie-hellman-group-exchange-sha1\": _DHGroupExchangeSHA1(),\n    b\"diffie-hellman-group14-sha1\": _DHGroup14SHA1(),\n    b\"ecdh-sha2-nistp256\": _ECDH256(),\n    b\"ecdh-sha2-nistp384\": _ECDH384(),\n    b\"ecdh-sha2-nistp521\": _ECDH512(),\n    }\n\n\n\ndef getKex(kexAlgorithm):\n    \"\"\"\n    Get a description of a named key exchange algorithm.\n\n    @param kexAlgorithm: The key exchange algorithm name.\n    @type kexAlgorithm: L{bytes}\n\n    @return: A description of the key exchange algorithm named by\n        C{kexAlgorithm}.\n    @rtype: L{_IKexAlgorithm}\n\n    @raises ConchError: if the key exchange algorithm is not found.\n    \"\"\"\n    if kexAlgorithm not in _kexAlgorithms:\n        raise error.ConchError(\n            \"Unsupported key exchange algorithm: %s\" % (kexAlgorithm,))\n    return _kexAlgorithms[kexAlgorithm]\n\n\n\ndef isEllipticCurve(kexAlgorithm):\n    \"\"\"\n    Returns C{True} if C{kexAlgorithm} is an elliptic curve.\n\n    @param kexAlgorithm: The key exchange algorithm name.\n    @type kexAlgorithm: C{str}\n\n    @return: C{True} if C{kexAlgorithm} is an elliptic curve,\n        otherwise C{False}.\n    @rtype: C{bool}\n    \"\"\"\n    return _IEllipticCurveExchangeKexAlgorithm.providedBy(getKex(kexAlgorithm))\n\n\n\ndef isFixedGroup(kexAlgorithm):\n    \"\"\"\n    Returns C{True} if C{kexAlgorithm} has a fixed prime / generator group.\n\n    @param kexAlgorithm: The key exchange algorithm name.\n    @type kexAlgorithm: L{bytes}\n\n    @return: C{True} if C{kexAlgorithm} has a fixed prime / generator group,\n        otherwise C{False}.\n    @rtype: L{bool}\n    \"\"\"\n    return _IFixedGroupKexAlgorithm.providedBy(getKex(kexAlgorithm))\n\n\n\ndef getHashProcessor(kexAlgorithm):\n    \"\"\"\n    Get the hash algorithm callable to use in key exchange.\n\n    @param kexAlgorithm: The key exchange algorithm name.\n    @type kexAlgorithm: L{bytes}\n\n    @return: A callable hash algorithm constructor (e.g. C{hashlib.sha256}).\n    @rtype: C{callable}\n    \"\"\"\n    kex = getKex(kexAlgorithm)\n    return kex.hashProcessor\n\n\n\ndef getDHGeneratorAndPrime(kexAlgorithm):\n    \"\"\"\n    Get the generator and the prime to use in key exchange.\n\n    @param kexAlgorithm: The key exchange algorithm name.\n    @type kexAlgorithm: L{bytes}\n\n    @return: A L{tuple} containing L{long} generator and L{long} prime.\n    @rtype: L{tuple}\n    \"\"\"\n    kex = getKex(kexAlgorithm)\n    return kex.generator, kex.prime\n\n\n\ndef getSupportedKeyExchanges():\n    \"\"\"\n    Get a list of supported key exchange algorithm names in order of\n    preference.\n\n    @return: A C{list} of supported key exchange algorithm names.\n    @rtype: C{list} of L{bytes}\n    \"\"\"\n    from cryptography.hazmat.backends import default_backend\n    from cryptography.hazmat.primitives.asymmetric import ec\n    from twisted.conch.ssh.keys import _curveTable\n\n    backend = default_backend()\n    kexAlgorithms = _kexAlgorithms.copy()\n    for keyAlgorithm in list(kexAlgorithms):\n        if keyAlgorithm.startswith(b\"ecdh\"):\n            keyAlgorithmDsa = keyAlgorithm.replace(b\"ecdh\", b\"ecdsa\")\n            supported = backend.elliptic_curve_exchange_algorithm_supported(\n                ec.ECDH(), _curveTable[keyAlgorithmDsa])\n            if not supported:\n                kexAlgorithms.pop(keyAlgorithm)\n    return sorted(\n        kexAlgorithms,\n        key = lambda kexAlgorithm: kexAlgorithms[kexAlgorithm].preference)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/address.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_address -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAddress object for SSH network connections.\n\nMaintainer: Paul Swartz\n\n@since: 12.1\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom zope.interface import implementer\n\nfrom twisted.internet.interfaces import IAddress\nfrom twisted.python import util\n\n\n\n@implementer(IAddress)\nclass SSHTransportAddress(util.FancyEqMixin, object):\n    \"\"\"\n    Object representing an SSH Transport endpoint.\n\n    This is used to ensure that any code inspecting this address and\n    attempting to construct a similar connection based upon it is not\n    mislead into creating a transport which is not similar to the one it is\n    indicating.\n\n    @ivar address: An instance of an object which implements I{IAddress} to\n        which this transport address is connected.\n    \"\"\"\n\n    compareAttributes = ('address',)\n\n    def __init__(self, address):\n        self.address = address\n\n\n    def __repr__(self):\n        return 'SSHTransportAddress(%r)' % (self.address,)\n\n\n    def __hash__(self):\n        return hash(('SSH', self.address))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/agent.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nImplements the SSH v2 key agent protocol.  This protocol is documented in the\nSSH source code, in the file\nU{PROTOCOL.agent<http://www.openbsd.org/cgi-bin/cvsweb/src/usr.bin/ssh/PROTOCOL.agent>}.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport struct\n\nfrom twisted.conch.ssh.common import NS, getNS, getMP\nfrom twisted.conch.error import ConchError, MissingKeyStoreError\nfrom twisted.conch.ssh import keys\nfrom twisted.internet import defer, protocol\nfrom twisted.python.compat import itervalues\n\n\n\nclass SSHAgentClient(protocol.Protocol):\n    \"\"\"\n    The client side of the SSH agent protocol.  This is equivalent to\n    ssh-add(1) and can be used with either ssh-agent(1) or the SSHAgentServer\n    protocol, also in this package.\n    \"\"\"\n\n    def __init__(self):\n        self.buf = b''\n        self.deferreds = []\n\n\n    def dataReceived(self, data):\n        self.buf += data\n        while 1:\n            if len(self.buf) <= 4:\n                return\n            packLen = struct.unpack('!L', self.buf[:4])[0]\n            if len(self.buf) < 4 + packLen:\n                return\n            packet, self.buf = self.buf[4:4 + packLen], self.buf[4 + packLen:]\n            reqType = ord(packet[0:1])\n            d = self.deferreds.pop(0)\n            if reqType == AGENT_FAILURE:\n                d.errback(ConchError('agent failure'))\n            elif reqType == AGENT_SUCCESS:\n                d.callback(b'')\n            else:\n                d.callback(packet)\n\n\n    def sendRequest(self, reqType, data):\n        pack = struct.pack('!LB',len(data) + 1, reqType) + data\n        self.transport.write(pack)\n        d = defer.Deferred()\n        self.deferreds.append(d)\n        return d\n\n\n    def requestIdentities(self):\n        \"\"\"\n        @return: A L{Deferred} which will fire with a list of all keys found in\n            the SSH agent. The list of keys is comprised of (public key blob,\n            comment) tuples.\n        \"\"\"\n        d = self.sendRequest(AGENTC_REQUEST_IDENTITIES, b'')\n        d.addCallback(self._cbRequestIdentities)\n        return d\n\n\n    def _cbRequestIdentities(self, data):\n        \"\"\"\n        Unpack a collection of identities into a list of tuples comprised of\n        public key blobs and comments.\n        \"\"\"\n        if ord(data[0:1]) != AGENT_IDENTITIES_ANSWER:\n            raise ConchError('unexpected response: %i' % ord(data[0:1]))\n        numKeys = struct.unpack('!L', data[1:5])[0]\n        result = []\n        data = data[5:]\n        for i in range(numKeys):\n            blob, data = getNS(data)\n            comment, data = getNS(data)\n            result.append((blob, comment))\n        return result\n\n\n    def addIdentity(self, blob, comment = b''):\n        \"\"\"\n        Add a private key blob to the agent's collection of keys.\n        \"\"\"\n        req = blob\n        req += NS(comment)\n        return self.sendRequest(AGENTC_ADD_IDENTITY, req)\n\n\n    def signData(self, blob, data):\n        \"\"\"\n        Request that the agent sign the given C{data} with the private key\n        which corresponds to the public key given by C{blob}.  The private\n        key should have been added to the agent already.\n\n        @type blob: L{bytes}\n        @type data: L{bytes}\n        @return: A L{Deferred} which fires with a signature for given data\n            created with the given key.\n        \"\"\"\n        req = NS(blob)\n        req += NS(data)\n        req += b'\\000\\000\\000\\000' # flags\n        return self.sendRequest(AGENTC_SIGN_REQUEST, req).addCallback(self._cbSignData)\n\n\n    def _cbSignData(self, data):\n        if ord(data[0:1]) != AGENT_SIGN_RESPONSE:\n            raise ConchError('unexpected data: %i' % ord(data[0:1]))\n        signature = getNS(data[1:])[0]\n        return signature\n\n\n    def removeIdentity(self, blob):\n        \"\"\"\n        Remove the private key corresponding to the public key in blob from the\n        running agent.\n        \"\"\"\n        req = NS(blob)\n        return self.sendRequest(AGENTC_REMOVE_IDENTITY, req)\n\n\n    def removeAllIdentities(self):\n        \"\"\"\n        Remove all keys from the running agent.\n        \"\"\"\n        return self.sendRequest(AGENTC_REMOVE_ALL_IDENTITIES, b'')\n\n\n\nclass SSHAgentServer(protocol.Protocol):\n    \"\"\"\n    The server side of the SSH agent protocol.  This is equivalent to\n    ssh-agent(1) and can be used with either ssh-add(1) or the SSHAgentClient\n    protocol, also in this package.\n    \"\"\"\n\n    def __init__(self):\n        self.buf = b''\n\n\n    def dataReceived(self, data):\n        self.buf += data\n        while 1:\n            if len(self.buf) <= 4:\n                return\n            packLen = struct.unpack('!L', self.buf[:4])[0]\n            if len(self.buf) < 4 + packLen:\n                return\n            packet, self.buf = self.buf[4:4 + packLen], self.buf[4 + packLen:]\n            reqType = ord(packet[0:1])\n            reqName = messages.get(reqType, None)\n            if not reqName:\n                self.sendResponse(AGENT_FAILURE, b'')\n            else:\n                f = getattr(self, 'agentc_%s' % reqName)\n                if getattr(self.factory, 'keys', None) is None:\n                    self.sendResponse(AGENT_FAILURE, b'')\n                    raise MissingKeyStoreError()\n                f(packet[1:])\n\n\n    def sendResponse(self, reqType, data):\n        pack = struct.pack('!LB', len(data) + 1, reqType) + data\n        self.transport.write(pack)\n\n\n    def agentc_REQUEST_IDENTITIES(self, data):\n        \"\"\"\n        Return all of the identities that have been added to the server\n        \"\"\"\n        assert data == b''\n        numKeys = len(self.factory.keys)\n        resp = []\n\n        resp.append(struct.pack('!L', numKeys))\n        for key, comment in itervalues(self.factory.keys):\n            resp.append(NS(key.blob())) # yes, wrapped in an NS\n            resp.append(NS(comment))\n        self.sendResponse(AGENT_IDENTITIES_ANSWER, b''.join(resp))\n\n\n    def agentc_SIGN_REQUEST(self, data):\n        \"\"\"\n        Data is a structure with a reference to an already added key object and\n        some data that the clients wants signed with that key.  If the key\n        object wasn't loaded, return AGENT_FAILURE, else return the signature.\n        \"\"\"\n        blob, data = getNS(data)\n        if blob not in self.factory.keys:\n            return self.sendResponse(AGENT_FAILURE, b'')\n        signData, data = getNS(data)\n        assert data == b'\\000\\000\\000\\000'\n        self.sendResponse(AGENT_SIGN_RESPONSE, NS(self.factory.keys[blob][0].sign(signData)))\n\n\n    def agentc_ADD_IDENTITY(self, data):\n        \"\"\"\n        Adds a private key to the agent's collection of identities.  On\n        subsequent interactions, the private key can be accessed using only the\n        corresponding public key.\n        \"\"\"\n\n        # need to pre-read the key data so we can get past it to the comment string\n        keyType, rest = getNS(data)\n        if keyType == b'ssh-rsa':\n            nmp = 6\n        elif keyType == b'ssh-dss':\n            nmp = 5\n        else:\n            raise keys.BadKeyError('unknown blob type: %s' % keyType)\n\n        rest = getMP(rest, nmp)[-1] # ignore the key data for now, we just want the comment\n        comment, rest = getNS(rest) # the comment, tacked onto the end of the key blob\n\n        k = keys.Key.fromString(data, type='private_blob') # not wrapped in NS here\n        self.factory.keys[k.blob()] = (k, comment)\n        self.sendResponse(AGENT_SUCCESS, b'')\n\n\n    def agentc_REMOVE_IDENTITY(self, data):\n        \"\"\"\n        Remove a specific key from the agent's collection of identities.\n        \"\"\"\n        blob, _ = getNS(data)\n        k = keys.Key.fromString(blob, type='blob')\n        del self.factory.keys[k.blob()]\n        self.sendResponse(AGENT_SUCCESS, b'')\n\n\n    def agentc_REMOVE_ALL_IDENTITIES(self, data):\n        \"\"\"\n        Remove all keys from the agent's collection of identities.\n        \"\"\"\n        assert data == b''\n        self.factory.keys = {}\n        self.sendResponse(AGENT_SUCCESS, b'')\n\n    # v1 messages that we ignore because we don't keep v1 keys\n    # open-ssh sends both v1 and v2 commands, so we have to\n    # do no-ops for v1 commands or we'll get \"bad request\" errors\n\n    def agentc_REQUEST_RSA_IDENTITIES(self, data):\n        \"\"\"\n        v1 message for listing RSA1 keys; superseded by\n        agentc_REQUEST_IDENTITIES, which handles different key types.\n        \"\"\"\n        self.sendResponse(AGENT_RSA_IDENTITIES_ANSWER, struct.pack('!L', 0))\n\n\n    def agentc_REMOVE_RSA_IDENTITY(self, data):\n        \"\"\"\n        v1 message for removing RSA1 keys; superseded by\n        agentc_REMOVE_IDENTITY, which handles different key types.\n        \"\"\"\n        self.sendResponse(AGENT_SUCCESS, b'')\n\n\n    def agentc_REMOVE_ALL_RSA_IDENTITIES(self, data):\n        \"\"\"\n        v1 message for removing all RSA1 keys; superseded by\n        agentc_REMOVE_ALL_IDENTITIES, which handles different key types.\n        \"\"\"\n        self.sendResponse(AGENT_SUCCESS, b'')\n\n\nAGENTC_REQUEST_RSA_IDENTITIES   = 1\nAGENT_RSA_IDENTITIES_ANSWER     = 2\nAGENT_FAILURE                   = 5\nAGENT_SUCCESS                   = 6\n\nAGENTC_REMOVE_RSA_IDENTITY         = 8\nAGENTC_REMOVE_ALL_RSA_IDENTITIES   = 9\n\nAGENTC_REQUEST_IDENTITIES       = 11\nAGENT_IDENTITIES_ANSWER         = 12\nAGENTC_SIGN_REQUEST             = 13\nAGENT_SIGN_RESPONSE             = 14\nAGENTC_ADD_IDENTITY             = 17\nAGENTC_REMOVE_IDENTITY          = 18\nAGENTC_REMOVE_ALL_IDENTITIES    = 19\n\nmessages = {}\nfor name, value in locals().copy().items():\n    if name[:7] == 'AGENTC_':\n        messages[value] = name[7:] # doesn't handle doubles\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/channel.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_channel -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThe parent class for all the SSH Channels.  Currently implemented channels\nare session, direct-tcp, and forwarded-tcp.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom zope.interface import implementer\n\nfrom twisted.python import log\nfrom twisted.python.compat import nativeString, intToBytes\nfrom twisted.internet import interfaces\n\n\n\n@implementer(interfaces.ITransport)\nclass SSHChannel(log.Logger):\n    \"\"\"\n    A class that represents a multiplexed channel over an SSH connection.\n    The channel has a local window which is the maximum amount of data it will\n    receive, and a remote which is the maximum amount of data the remote side\n    will accept.  There is also a maximum packet size for any individual data\n    packet going each way.\n\n    @ivar name: the name of the channel.\n    @type name: L{bytes}\n    @ivar localWindowSize: the maximum size of the local window in bytes.\n    @type localWindowSize: L{int}\n    @ivar localWindowLeft: how many bytes are left in the local window.\n    @type localWindowLeft: L{int}\n    @ivar localMaxPacket: the maximum size of packet we will accept in bytes.\n    @type localMaxPacket: L{int}\n    @ivar remoteWindowLeft: how many bytes are left in the remote window.\n    @type remoteWindowLeft: L{int}\n    @ivar remoteMaxPacket: the maximum size of a packet the remote side will\n        accept in bytes.\n    @type remoteMaxPacket: L{int}\n    @ivar conn: the connection this channel is multiplexed through.\n    @type conn: L{SSHConnection}\n    @ivar data: any data to send to the other side when the channel is\n        requested.\n    @type data: L{bytes}\n    @ivar avatar: an avatar for the logged-in user (if a server channel)\n    @ivar localClosed: True if we aren't accepting more data.\n    @type localClosed: L{bool}\n    @ivar remoteClosed: True if the other side isn't accepting more data.\n    @type remoteClosed: L{bool}\n    \"\"\"\n\n    name = None # only needed for client channels\n\n    def __init__(self, localWindow = 0, localMaxPacket = 0,\n                       remoteWindow = 0, remoteMaxPacket = 0,\n                       conn = None, data=None, avatar = None):\n        self.localWindowSize = localWindow or 131072\n        self.localWindowLeft = self.localWindowSize\n        self.localMaxPacket = localMaxPacket or 32768\n        self.remoteWindowLeft = remoteWindow\n        self.remoteMaxPacket = remoteMaxPacket\n        self.areWriting = 1\n        self.conn = conn\n        self.data = data\n        self.avatar = avatar\n        self.specificData = b''\n        self.buf = b''\n        self.extBuf = []\n        self.closing = 0\n        self.localClosed = 0\n        self.remoteClosed = 0\n        self.id = None # gets set later by SSHConnection\n\n\n    def __str__(self):\n        return nativeString(self.__bytes__())\n\n\n    def __bytes__(self):\n        \"\"\"\n        Return a byte string representation of the channel\n        \"\"\"\n        name = self.name\n        if not name:\n            name = b'None'\n\n        return (b'<SSHChannel ' + name +\n                b' (lw ' + intToBytes(self.localWindowLeft) +\n                b' rw ' + intToBytes(self.remoteWindowLeft) +\n                b')>')\n\n\n    def logPrefix(self):\n        id = (self.id is not None and str(self.id)) or \"unknown\"\n        name = self.name\n        if name:\n            name = nativeString(name)\n        return \"SSHChannel %s (%s) on %s\" % (name, id,\n                self.conn.logPrefix())\n\n\n    def channelOpen(self, specificData):\n        \"\"\"\n        Called when the channel is opened.  specificData is any data that the\n        other side sent us when opening the channel.\n\n        @type specificData: L{bytes}\n        \"\"\"\n        log.msg('channel open')\n\n\n    def openFailed(self, reason):\n        \"\"\"\n        Called when the open failed for some reason.\n        reason.desc is a string descrption, reason.code the SSH error code.\n\n        @type reason: L{error.ConchError}\n        \"\"\"\n        log.msg('other side refused open\\nreason: %s'% reason)\n\n\n    def addWindowBytes(self, data):\n        \"\"\"\n        Called when bytes are added to the remote window.  By default it clears\n        the data buffers.\n\n        @type data:    L{bytes}\n        \"\"\"\n        self.remoteWindowLeft = self.remoteWindowLeft+data\n        if not self.areWriting and not self.closing:\n            self.areWriting = True\n            self.startWriting()\n        if self.buf:\n            b = self.buf\n            self.buf = b''\n            self.write(b)\n        if self.extBuf:\n            b = self.extBuf\n            self.extBuf = []\n            for (type, data) in b:\n                self.writeExtended(type, data)\n\n\n    def requestReceived(self, requestType, data):\n        \"\"\"\n        Called when a request is sent to this channel.  By default it delegates\n        to self.request_<requestType>.\n        If this function returns true, the request succeeded, otherwise it\n        failed.\n\n        @type requestType:  L{bytes}\n        @type data:         L{bytes}\n        @rtype:             L{bool}\n        \"\"\"\n        foo = nativeString(requestType.replace(b'-', b'_'))\n        f = getattr(self, 'request_%s'%foo, None)\n        if f:\n            return f(data)\n        log.msg('unhandled request for %s'%requestType)\n        return 0\n\n\n    def dataReceived(self, data):\n        \"\"\"\n        Called when we receive data.\n\n        @type data: L{bytes}\n        \"\"\"\n        log.msg('got data %s'%repr(data))\n\n\n    def extReceived(self, dataType, data):\n        \"\"\"\n        Called when we receive extended data (usually standard error).\n\n        @type dataType: L{int}\n        @type data:     L{str}\n        \"\"\"\n        log.msg('got extended data %s %s'%(dataType, repr(data)))\n\n\n    def eofReceived(self):\n        \"\"\"\n        Called when the other side will send no more data.\n        \"\"\"\n        log.msg('remote eof')\n\n\n    def closeReceived(self):\n        \"\"\"\n        Called when the other side has closed the channel.\n        \"\"\"\n        log.msg('remote close')\n        self.loseConnection()\n\n\n    def closed(self):\n        \"\"\"\n        Called when the channel is closed.  This means that both our side and\n        the remote side have closed the channel.\n        \"\"\"\n        log.msg('closed')\n\n\n    def write(self, data):\n        \"\"\"\n        Write some data to the channel.  If there is not enough remote window\n        available, buffer until it is.  Otherwise, split the data into\n        packets of length remoteMaxPacket and send them.\n\n        @type data: L{bytes}\n        \"\"\"\n        if self.buf:\n            self.buf += data\n            return\n        top = len(data)\n        if top > self.remoteWindowLeft:\n            data, self.buf = (data[:self.remoteWindowLeft],\n                data[self.remoteWindowLeft:])\n            self.areWriting = 0\n            self.stopWriting()\n            top = self.remoteWindowLeft\n        rmp = self.remoteMaxPacket\n        write = self.conn.sendData\n        r = range(0, top, rmp)\n        for offset in r:\n            write(self, data[offset: offset+rmp])\n        self.remoteWindowLeft -= top\n        if self.closing and not self.buf:\n            self.loseConnection() # try again\n\n\n    def writeExtended(self, dataType, data):\n        \"\"\"\n        Send extended data to this channel.  If there is not enough remote\n        window available, buffer until there is.  Otherwise, split the data\n        into packets of length remoteMaxPacket and send them.\n\n        @type dataType: L{int}\n        @type data:     L{bytes}\n        \"\"\"\n        if self.extBuf:\n            if self.extBuf[-1][0] == dataType:\n                self.extBuf[-1][1] += data\n            else:\n                self.extBuf.append([dataType, data])\n            return\n        if len(data) > self.remoteWindowLeft:\n            data, self.extBuf = (data[:self.remoteWindowLeft],\n                                [[dataType, data[self.remoteWindowLeft:]]])\n            self.areWriting = 0\n            self.stopWriting()\n        while len(data) > self.remoteMaxPacket:\n            self.conn.sendExtendedData(self, dataType,\n                                             data[:self.remoteMaxPacket])\n            data = data[self.remoteMaxPacket:]\n            self.remoteWindowLeft -= self.remoteMaxPacket\n        if data:\n            self.conn.sendExtendedData(self, dataType, data)\n            self.remoteWindowLeft -= len(data)\n        if self.closing:\n            self.loseConnection() # try again\n\n\n    def writeSequence(self, data):\n        \"\"\"\n        Part of the Transport interface.  Write a list of strings to the\n        channel.\n\n        @type data: C{list} of L{str}\n        \"\"\"\n        self.write(b''.join(data))\n\n\n    def loseConnection(self):\n        \"\"\"\n        Close the channel if there is no buferred data.  Otherwise, note the\n        request and return.\n        \"\"\"\n        self.closing = 1\n        if not self.buf and not self.extBuf:\n            self.conn.sendClose(self)\n\n\n    def getPeer(self):\n        \"\"\"\n        See: L{ITransport.getPeer}\n\n        @return: The remote address of this connection.\n        @rtype: L{SSHTransportAddress}.\n        \"\"\"\n        return self.conn.transport.getPeer()\n\n\n    def getHost(self):\n        \"\"\"\n        See: L{ITransport.getHost}\n\n        @return: An address describing this side of the connection.\n        @rtype: L{SSHTransportAddress}.\n        \"\"\"\n        return self.conn.transport.getHost()\n\n\n    def stopWriting(self):\n        \"\"\"\n        Called when the remote buffer is full, as a hint to stop writing.\n        This can be ignored, but it can be helpful.\n        \"\"\"\n\n\n    def startWriting(self):\n        \"\"\"\n        Called when the remote buffer has more room, as a hint to continue\n        writing.\n        \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/common.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_ssh -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nCommon functions for the SSH classes.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport struct\n\nfrom cryptography.utils import int_from_bytes, int_to_bytes\n\nfrom twisted.python.compat import unicode\nfrom twisted.python.deprecate import deprecated\nfrom twisted.python.versions import Version\n\n__all__ = [\"NS\", \"getNS\", \"MP\", \"getMP\", \"ffs\"]\n\n\n\ndef NS(t):\n    \"\"\"\n    net string\n    \"\"\"\n    if isinstance(t, unicode):\n        t = t.encode(\"utf-8\")\n    return struct.pack('!L', len(t)) + t\n\n\n\ndef getNS(s, count=1):\n    \"\"\"\n    get net string\n    \"\"\"\n    ns = []\n    c = 0\n    for i in range(count):\n        l, = struct.unpack('!L', s[c:c + 4])\n        ns.append(s[c + 4:4 + l + c])\n        c += 4 + l\n    return tuple(ns) + (s[c:],)\n\n\n\ndef MP(number):\n    if number == 0:\n        return b'\\000' * 4\n    assert number > 0\n    bn = int_to_bytes(number)\n    if ord(bn[0:1]) & 128:\n        bn = b'\\000' + bn\n    return struct.pack('>L', len(bn)) + bn\n\n\n\ndef getMP(data, count=1):\n    \"\"\"\n    Get multiple precision integer out of the string.  A multiple precision\n    integer is stored as a 4-byte length followed by length bytes of the\n    integer.  If count is specified, get count integers out of the string.\n    The return value is a tuple of count integers followed by the rest of\n    the data.\n    \"\"\"\n    mp = []\n    c = 0\n    for i in range(count):\n        length, = struct.unpack('>L', data[c:c + 4])\n        mp.append(int_from_bytes(data[c + 4:c + 4 + length], 'big'))\n        c += 4 + length\n    return tuple(mp) + (data[c:],)\n\n\n\ndef ffs(c, s):\n    \"\"\"\n    first from second\n    goes through the first list, looking for items in the second, returns the first one\n    \"\"\"\n    for i in c:\n        if i in s:\n            return i\n\n\n\n@deprecated(Version(\"Twisted\", 16, 5, 0))\ndef install():\n    # This used to install gmpy, but is technically public API, so just do\n    # nothing.\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/connection.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_connection -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module contains the implementation of the ssh-connection service, which\nallows access to the shell and port-forwarding.\n\nMaintainer: Paul Swartz\n\"\"\"\nfrom __future__ import division, absolute_import\n\nimport string\nimport struct\n\nimport twisted.internet.error\nfrom twisted.conch.ssh import service, common\nfrom twisted.conch import error\nfrom twisted.internet import defer\nfrom twisted.python import log\nfrom twisted.python.compat import (\n    nativeString, networkString, long, _bytesChr as chr)\n\n\n\nclass SSHConnection(service.SSHService):\n    \"\"\"\n    An implementation of the 'ssh-connection' service.  It is used to\n    multiplex multiple channels over the single SSH connection.\n\n    @ivar localChannelID: the next number to use as a local channel ID.\n    @type localChannelID: L{int}\n    @ivar channels: a L{dict} mapping a local channel ID to C{SSHChannel}\n        subclasses.\n    @type channels: L{dict}\n    @ivar localToRemoteChannel: a L{dict} mapping a local channel ID to a\n        remote channel ID.\n    @type localToRemoteChannel: L{dict}\n    @ivar channelsToRemoteChannel: a L{dict} mapping a C{SSHChannel} subclass\n        to remote channel ID.\n    @type channelsToRemoteChannel: L{dict}\n    @ivar deferreds: a L{dict} mapping a local channel ID to a C{list} of\n        C{Deferreds} for outstanding channel requests.  Also, the 'global'\n        key stores the C{list} of pending global request C{Deferred}s.\n    \"\"\"\n    name = b'ssh-connection'\n\n    def __init__(self):\n        self.localChannelID = 0 # this is the current # to use for channel ID\n        self.localToRemoteChannel = {} # local channel ID -> remote channel ID\n        self.channels = {} # local channel ID -> subclass of SSHChannel\n        self.channelsToRemoteChannel = {} # subclass of SSHChannel ->\n                                          # remote channel ID\n        self.deferreds = {\"global\": []} # local channel -> list of deferreds\n                            # for pending requests or 'global' -> list of\n                            # deferreds for global requests\n        self.transport = None # gets set later\n\n\n    def serviceStarted(self):\n        if hasattr(self.transport, 'avatar'):\n            self.transport.avatar.conn = self\n\n\n    def serviceStopped(self):\n        \"\"\"\n        Called when the connection is stopped.\n        \"\"\"\n        # Close any fully open channels\n        for channel in list(self.channelsToRemoteChannel.keys()):\n            self.channelClosed(channel)\n        # Indicate failure to any channels that were in the process of\n        # opening but not yet open.\n        while self.channels:\n            (_, channel) = self.channels.popitem()\n            log.callWithLogger(channel, channel.openFailed,\n                               twisted.internet.error.ConnectionLost())\n        # Errback any unfinished global requests.\n        self._cleanupGlobalDeferreds()\n\n\n    def _cleanupGlobalDeferreds(self):\n        \"\"\"\n        All pending requests that have returned a deferred must be errbacked\n        when this service is stopped, otherwise they might be left uncalled and\n        uncallable.\n        \"\"\"\n        for d in self.deferreds[\"global\"]:\n            d.errback(error.ConchError(\"Connection stopped.\"))\n        del self.deferreds[\"global\"][:]\n\n\n    # packet methods\n    def ssh_GLOBAL_REQUEST(self, packet):\n        \"\"\"\n        The other side has made a global request.  Payload::\n            string  request type\n            bool    want reply\n            <request specific data>\n\n        This dispatches to self.gotGlobalRequest.\n        \"\"\"\n        requestType, rest = common.getNS(packet)\n        wantReply, rest = ord(rest[0:1]), rest[1:]\n        ret = self.gotGlobalRequest(requestType, rest)\n        if wantReply:\n            reply = MSG_REQUEST_FAILURE\n            data = b''\n            if ret:\n                reply = MSG_REQUEST_SUCCESS\n                if isinstance(ret, (tuple, list)):\n                    data = ret[1]\n            self.transport.sendPacket(reply, data)\n\n    def ssh_REQUEST_SUCCESS(self, packet):\n        \"\"\"\n        Our global request succeeded.  Get the appropriate Deferred and call\n        it back with the packet we received.\n        \"\"\"\n        log.msg('RS')\n        self.deferreds['global'].pop(0).callback(packet)\n\n    def ssh_REQUEST_FAILURE(self, packet):\n        \"\"\"\n        Our global request failed.  Get the appropriate Deferred and errback\n        it with the packet we received.\n        \"\"\"\n        log.msg('RF')\n        self.deferreds['global'].pop(0).errback(\n            error.ConchError('global request failed', packet))\n\n    def ssh_CHANNEL_OPEN(self, packet):\n        \"\"\"\n        The other side wants to get a channel.  Payload::\n            string  channel name\n            uint32  remote channel number\n            uint32  remote window size\n            uint32  remote maximum packet size\n            <channel specific data>\n\n        We get a channel from self.getChannel(), give it a local channel number\n        and notify the other side.  Then notify the channel by calling its\n        channelOpen method.\n        \"\"\"\n        channelType, rest = common.getNS(packet)\n        senderChannel, windowSize, maxPacket = struct.unpack('>3L', rest[:12])\n        packet = rest[12:]\n        try:\n            channel = self.getChannel(channelType, windowSize, maxPacket,\n                            packet)\n            localChannel = self.localChannelID\n            self.localChannelID += 1\n            channel.id = localChannel\n            self.channels[localChannel] = channel\n            self.channelsToRemoteChannel[channel] = senderChannel\n            self.localToRemoteChannel[localChannel] = senderChannel\n            self.transport.sendPacket(MSG_CHANNEL_OPEN_CONFIRMATION,\n                struct.pack('>4L', senderChannel, localChannel,\n                    channel.localWindowSize,\n                    channel.localMaxPacket)+channel.specificData)\n            log.callWithLogger(channel, channel.channelOpen, packet)\n        except Exception as e:\n            log.err(e, 'channel open failed')\n            if isinstance(e, error.ConchError):\n                textualInfo, reason = e.args\n                if isinstance(textualInfo, (int, long)):\n                    # See #3657 and #3071\n                    textualInfo, reason = reason, textualInfo\n            else:\n                reason = OPEN_CONNECT_FAILED\n                textualInfo = \"unknown failure\"\n            self.transport.sendPacket(\n                MSG_CHANNEL_OPEN_FAILURE,\n                struct.pack('>2L', senderChannel, reason) +\n                common.NS(networkString(textualInfo)) + common.NS(b''))\n\n    def ssh_CHANNEL_OPEN_CONFIRMATION(self, packet):\n        \"\"\"\n        The other side accepted our MSG_CHANNEL_OPEN request.  Payload::\n            uint32  local channel number\n            uint32  remote channel number\n            uint32  remote window size\n            uint32  remote maximum packet size\n            <channel specific data>\n\n        Find the channel using the local channel number and notify its\n        channelOpen method.\n        \"\"\"\n        (localChannel, remoteChannel, windowSize,\n                maxPacket) = struct.unpack('>4L', packet[: 16])\n        specificData = packet[16:]\n        channel = self.channels[localChannel]\n        channel.conn = self\n        self.localToRemoteChannel[localChannel] = remoteChannel\n        self.channelsToRemoteChannel[channel] = remoteChannel\n        channel.remoteWindowLeft = windowSize\n        channel.remoteMaxPacket = maxPacket\n        log.callWithLogger(channel, channel.channelOpen, specificData)\n\n    def ssh_CHANNEL_OPEN_FAILURE(self, packet):\n        \"\"\"\n        The other side did not accept our MSG_CHANNEL_OPEN request.  Payload::\n            uint32  local channel number\n            uint32  reason code\n            string  reason description\n\n        Find the channel using the local channel number and notify it by\n        calling its openFailed() method.\n        \"\"\"\n        localChannel, reasonCode = struct.unpack('>2L', packet[:8])\n        reasonDesc = common.getNS(packet[8:])[0]\n        channel = self.channels[localChannel]\n        del self.channels[localChannel]\n        channel.conn = self\n        reason = error.ConchError(reasonDesc, reasonCode)\n        log.callWithLogger(channel, channel.openFailed, reason)\n\n    def ssh_CHANNEL_WINDOW_ADJUST(self, packet):\n        \"\"\"\n        The other side is adding bytes to its window.  Payload::\n            uint32  local channel number\n            uint32  bytes to add\n\n        Call the channel's addWindowBytes() method to add new bytes to the\n        remote window.\n        \"\"\"\n        localChannel, bytesToAdd = struct.unpack('>2L', packet[:8])\n        channel = self.channels[localChannel]\n        log.callWithLogger(channel, channel.addWindowBytes, bytesToAdd)\n\n    def ssh_CHANNEL_DATA(self, packet):\n        \"\"\"\n        The other side is sending us data.  Payload::\n            uint32 local channel number\n            string data\n\n        Check to make sure the other side hasn't sent too much data (more\n        than what's in the window, or more than the maximum packet size).  If\n        they have, close the channel.  Otherwise, decrease the available\n        window and pass the data to the channel's dataReceived().\n        \"\"\"\n        localChannel, dataLength = struct.unpack('>2L', packet[:8])\n        channel = self.channels[localChannel]\n        # XXX should this move to dataReceived to put client in charge?\n        if (dataLength > channel.localWindowLeft or\n           dataLength > channel.localMaxPacket): # more data than we want\n            log.callWithLogger(channel, log.msg, 'too much data')\n            self.sendClose(channel)\n            return\n            #packet = packet[:channel.localWindowLeft+4]\n        data = common.getNS(packet[4:])[0]\n        channel.localWindowLeft -= dataLength\n        if channel.localWindowLeft < channel.localWindowSize // 2:\n            self.adjustWindow(channel, channel.localWindowSize - \\\n                                       channel.localWindowLeft)\n            #log.msg('local window left: %s/%s' % (channel.localWindowLeft,\n            #                                    channel.localWindowSize))\n        log.callWithLogger(channel, channel.dataReceived, data)\n\n    def ssh_CHANNEL_EXTENDED_DATA(self, packet):\n        \"\"\"\n        The other side is sending us exteneded data.  Payload::\n            uint32  local channel number\n            uint32  type code\n            string  data\n\n        Check to make sure the other side hasn't sent too much data (more\n        than what's in the window, or than the maximum packet size).  If\n        they have, close the channel.  Otherwise, decrease the available\n        window and pass the data and type code to the channel's\n        extReceived().\n        \"\"\"\n        localChannel, typeCode, dataLength = struct.unpack('>3L', packet[:12])\n        channel = self.channels[localChannel]\n        if (dataLength > channel.localWindowLeft or\n                dataLength > channel.localMaxPacket):\n            log.callWithLogger(channel, log.msg, 'too much extdata')\n            self.sendClose(channel)\n            return\n        data = common.getNS(packet[8:])[0]\n        channel.localWindowLeft -= dataLength\n        if channel.localWindowLeft < channel.localWindowSize // 2:\n            self.adjustWindow(channel, channel.localWindowSize -\n                                       channel.localWindowLeft)\n        log.callWithLogger(channel, channel.extReceived, typeCode, data)\n\n    def ssh_CHANNEL_EOF(self, packet):\n        \"\"\"\n        The other side is not sending any more data.  Payload::\n            uint32  local channel number\n\n        Notify the channel by calling its eofReceived() method.\n        \"\"\"\n        localChannel = struct.unpack('>L', packet[:4])[0]\n        channel = self.channels[localChannel]\n        log.callWithLogger(channel, channel.eofReceived)\n\n    def ssh_CHANNEL_CLOSE(self, packet):\n        \"\"\"\n        The other side is closing its end; it does not want to receive any\n        more data.  Payload::\n            uint32  local channel number\n\n        Notify the channnel by calling its closeReceived() method.  If\n        the channel has also sent a close message, call self.channelClosed().\n        \"\"\"\n        localChannel = struct.unpack('>L', packet[:4])[0]\n        channel = self.channels[localChannel]\n        log.callWithLogger(channel, channel.closeReceived)\n        channel.remoteClosed = True\n        if channel.localClosed and channel.remoteClosed:\n            self.channelClosed(channel)\n\n    def ssh_CHANNEL_REQUEST(self, packet):\n        \"\"\"\n        The other side is sending a request to a channel.  Payload::\n            uint32  local channel number\n            string  request name\n            bool    want reply\n            <request specific data>\n\n        Pass the message to the channel's requestReceived method.  If the\n        other side wants a reply, add callbacks which will send the\n        reply.\n        \"\"\"\n        localChannel = struct.unpack('>L', packet[:4])[0]\n        requestType, rest = common.getNS(packet[4:])\n        wantReply = ord(rest[0:1])\n        channel = self.channels[localChannel]\n        d = defer.maybeDeferred(log.callWithLogger, channel,\n                channel.requestReceived, requestType, rest[1:])\n        if wantReply:\n            d.addCallback(self._cbChannelRequest, localChannel)\n            d.addErrback(self._ebChannelRequest, localChannel)\n            return d\n\n    def _cbChannelRequest(self, result, localChannel):\n        \"\"\"\n        Called back if the other side wanted a reply to a channel request.  If\n        the result is true, send a MSG_CHANNEL_SUCCESS.  Otherwise, raise\n        a C{error.ConchError}\n\n        @param result: the value returned from the channel's requestReceived()\n            method.  If it's False, the request failed.\n        @type result: L{bool}\n        @param localChannel: the local channel ID of the channel to which the\n            request was made.\n        @type localChannel: L{int}\n        @raises ConchError: if the result is False.\n        \"\"\"\n        if not result:\n            raise error.ConchError('failed request')\n        self.transport.sendPacket(MSG_CHANNEL_SUCCESS, struct.pack('>L',\n                                self.localToRemoteChannel[localChannel]))\n\n    def _ebChannelRequest(self, result, localChannel):\n        \"\"\"\n        Called if the other wisde wanted a reply to the channel requeset and\n        the channel request failed.\n\n        @param result: a Failure, but it's not used.\n        @param localChannel: the local channel ID of the channel to which the\n            request was made.\n        @type localChannel: L{int}\n        \"\"\"\n        self.transport.sendPacket(MSG_CHANNEL_FAILURE, struct.pack('>L',\n                                self.localToRemoteChannel[localChannel]))\n\n    def ssh_CHANNEL_SUCCESS(self, packet):\n        \"\"\"\n        Our channel request to the other side succeeded.  Payload::\n            uint32  local channel number\n\n        Get the C{Deferred} out of self.deferreds and call it back.\n        \"\"\"\n        localChannel = struct.unpack('>L', packet[:4])[0]\n        if self.deferreds.get(localChannel):\n            d = self.deferreds[localChannel].pop(0)\n            log.callWithLogger(self.channels[localChannel],\n                               d.callback, '')\n\n    def ssh_CHANNEL_FAILURE(self, packet):\n        \"\"\"\n        Our channel request to the other side failed.  Payload::\n            uint32  local channel number\n\n        Get the C{Deferred} out of self.deferreds and errback it with a\n        C{error.ConchError}.\n        \"\"\"\n        localChannel = struct.unpack('>L', packet[:4])[0]\n        if self.deferreds.get(localChannel):\n            d = self.deferreds[localChannel].pop(0)\n            log.callWithLogger(self.channels[localChannel],\n                               d.errback,\n                               error.ConchError('channel request failed'))\n\n    # methods for users of the connection to call\n\n    def sendGlobalRequest(self, request, data, wantReply=0):\n        \"\"\"\n        Send a global request for this connection.  Current this is only used\n        for remote->local TCP forwarding.\n\n        @type request:      L{bytes}\n        @type data:         L{bytes}\n        @type wantReply:    L{bool}\n        @rtype              C{Deferred}/L{None}\n        \"\"\"\n        self.transport.sendPacket(MSG_GLOBAL_REQUEST,\n                                  common.NS(request)\n                                  + (wantReply and b'\\xff' or b'\\x00')\n                                  + data)\n        if wantReply:\n            d = defer.Deferred()\n            self.deferreds['global'].append(d)\n            return d\n\n    def openChannel(self, channel, extra=b''):\n        \"\"\"\n        Open a new channel on this connection.\n\n        @type channel:  subclass of C{SSHChannel}\n        @type extra:    L{bytes}\n        \"\"\"\n        log.msg('opening channel %s with %s %s'%(self.localChannelID,\n                channel.localWindowSize, channel.localMaxPacket))\n        self.transport.sendPacket(MSG_CHANNEL_OPEN, common.NS(channel.name)\n                    + struct.pack('>3L', self.localChannelID,\n                    channel.localWindowSize, channel.localMaxPacket)\n                    + extra)\n        channel.id = self.localChannelID\n        self.channels[self.localChannelID] = channel\n        self.localChannelID += 1\n\n    def sendRequest(self, channel, requestType, data, wantReply=0):\n        \"\"\"\n        Send a request to a channel.\n\n        @type channel:      subclass of C{SSHChannel}\n        @type requestType:  L{bytes}\n        @type data:         L{bytes}\n        @type wantReply:    L{bool}\n        @rtype              C{Deferred}/L{None}\n        \"\"\"\n        if channel.localClosed:\n            return\n        log.msg('sending request %r' % (requestType))\n        self.transport.sendPacket(MSG_CHANNEL_REQUEST, struct.pack('>L',\n                                    self.channelsToRemoteChannel[channel])\n                                  + common.NS(requestType)+chr(wantReply)\n                                  + data)\n        if wantReply:\n            d = defer.Deferred()\n            self.deferreds.setdefault(channel.id, []).append(d)\n            return d\n\n    def adjustWindow(self, channel, bytesToAdd):\n        \"\"\"\n        Tell the other side that we will receive more data.  This should not\n        normally need to be called as it is managed automatically.\n\n        @type channel:      subclass of L{SSHChannel}\n        @type bytesToAdd:   L{int}\n        \"\"\"\n        if channel.localClosed:\n            return # we're already closed\n        self.transport.sendPacket(MSG_CHANNEL_WINDOW_ADJUST, struct.pack('>2L',\n                                    self.channelsToRemoteChannel[channel],\n                                    bytesToAdd))\n        log.msg('adding %i to %i in channel %i' % (bytesToAdd,\n            channel.localWindowLeft, channel.id))\n        channel.localWindowLeft += bytesToAdd\n\n    def sendData(self, channel, data):\n        \"\"\"\n        Send data to a channel.  This should not normally be used: instead use\n        channel.write(data) as it manages the window automatically.\n\n        @type channel:  subclass of L{SSHChannel}\n        @type data:     L{bytes}\n        \"\"\"\n        if channel.localClosed:\n            return # we're already closed\n        self.transport.sendPacket(MSG_CHANNEL_DATA, struct.pack('>L',\n                                    self.channelsToRemoteChannel[channel]) +\n                                   common.NS(data))\n\n    def sendExtendedData(self, channel, dataType, data):\n        \"\"\"\n        Send extended data to a channel.  This should not normally be used:\n        instead use channel.writeExtendedData(data, dataType) as it manages\n        the window automatically.\n\n        @type channel:  subclass of L{SSHChannel}\n        @type dataType: L{int}\n        @type data:     L{bytes}\n        \"\"\"\n        if channel.localClosed:\n            return # we're already closed\n        self.transport.sendPacket(MSG_CHANNEL_EXTENDED_DATA, struct.pack('>2L',\n                            self.channelsToRemoteChannel[channel],dataType) \\\n                            + common.NS(data))\n\n    def sendEOF(self, channel):\n        \"\"\"\n        Send an EOF (End of File) for a channel.\n\n        @type channel:  subclass of L{SSHChannel}\n        \"\"\"\n        if channel.localClosed:\n            return # we're already closed\n        log.msg('sending eof')\n        self.transport.sendPacket(MSG_CHANNEL_EOF, struct.pack('>L',\n                                    self.channelsToRemoteChannel[channel]))\n\n    def sendClose(self, channel):\n        \"\"\"\n        Close a channel.\n\n        @type channel:  subclass of L{SSHChannel}\n        \"\"\"\n        if channel.localClosed:\n            return # we're already closed\n        log.msg('sending close %i' % channel.id)\n        self.transport.sendPacket(MSG_CHANNEL_CLOSE, struct.pack('>L',\n                self.channelsToRemoteChannel[channel]))\n        channel.localClosed = True\n        if channel.localClosed and channel.remoteClosed:\n            self.channelClosed(channel)\n\n    # methods to override\n    def getChannel(self, channelType, windowSize, maxPacket, data):\n        \"\"\"\n        The other side requested a channel of some sort.\n        channelType is the type of channel being requested,\n        windowSize is the initial size of the remote window,\n        maxPacket is the largest packet we should send,\n        data is any other packet data (often nothing).\n\n        We return a subclass of L{SSHChannel}.\n\n        By default, this dispatches to a method 'channel_channelType' with any\n        non-alphanumerics in the channelType replace with _'s.  If it cannot\n        find a suitable method, it returns an OPEN_UNKNOWN_CHANNEL_TYPE error.\n        The method is called with arguments of windowSize, maxPacket, data.\n\n        @type channelType:  L{bytes}\n        @type windowSize:   L{int}\n        @type maxPacket:    L{int}\n        @type data:         L{bytes}\n        @rtype:             subclass of L{SSHChannel}/L{tuple}\n        \"\"\"\n        log.msg('got channel %r request' % (channelType))\n        if hasattr(self.transport, \"avatar\"): # this is a server!\n            chan = self.transport.avatar.lookupChannel(channelType,\n                                                       windowSize,\n                                                       maxPacket,\n                                                       data)\n        else:\n            channelType = channelType.translate(TRANSLATE_TABLE)\n            attr = 'channel_%s' % nativeString(channelType)\n            f = getattr(self, attr, None)\n            if f is not None:\n                chan = f(windowSize, maxPacket, data)\n            else:\n                chan = None\n        if chan is None:\n            raise error.ConchError('unknown channel',\n                    OPEN_UNKNOWN_CHANNEL_TYPE)\n        else:\n            chan.conn = self\n            return chan\n\n    def gotGlobalRequest(self, requestType, data):\n        \"\"\"\n        We got a global request.  pretty much, this is just used by the client\n        to request that we forward a port from the server to the client.\n        Returns either:\n            - 1: request accepted\n            - 1, <data>: request accepted with request specific data\n            - 0: request denied\n\n        By default, this dispatches to a method 'global_requestType' with\n        -'s in requestType replaced with _'s.  The found method is passed data.\n        If this method cannot be found, this method returns 0.  Otherwise, it\n        returns the return value of that method.\n\n        @type requestType:  L{bytes}\n        @type data:         L{bytes}\n        @rtype:             L{int}/L{tuple}\n        \"\"\"\n        log.msg('got global %s request' % requestType)\n        if hasattr(self.transport, 'avatar'): # this is a server!\n            return self.transport.avatar.gotGlobalRequest(requestType, data)\n\n        requestType = nativeString(requestType.replace(b'-',b'_'))\n        f = getattr(self, 'global_%s' % requestType, None)\n        if not f:\n            return 0\n        return f(data)\n\n    def channelClosed(self, channel):\n        \"\"\"\n        Called when a channel is closed.\n        It clears the local state related to the channel, and calls\n        channel.closed().\n        MAKE SURE YOU CALL THIS METHOD, even if you subclass L{SSHConnection}.\n        If you don't, things will break mysteriously.\n\n        @type channel: L{SSHChannel}\n        \"\"\"\n        if channel in self.channelsToRemoteChannel: # actually open\n            channel.localClosed = channel.remoteClosed = True\n            del self.localToRemoteChannel[channel.id]\n            del self.channels[channel.id]\n            del self.channelsToRemoteChannel[channel]\n            for d in self.deferreds.pop(channel.id, []):\n                d.errback(error.ConchError(\"Channel closed.\"))\n            log.callWithLogger(channel, channel.closed)\n\n\n\nMSG_GLOBAL_REQUEST = 80\nMSG_REQUEST_SUCCESS = 81\nMSG_REQUEST_FAILURE = 82\nMSG_CHANNEL_OPEN = 90\nMSG_CHANNEL_OPEN_CONFIRMATION = 91\nMSG_CHANNEL_OPEN_FAILURE = 92\nMSG_CHANNEL_WINDOW_ADJUST = 93\nMSG_CHANNEL_DATA = 94\nMSG_CHANNEL_EXTENDED_DATA = 95\nMSG_CHANNEL_EOF = 96\nMSG_CHANNEL_CLOSE = 97\nMSG_CHANNEL_REQUEST = 98\nMSG_CHANNEL_SUCCESS = 99\nMSG_CHANNEL_FAILURE = 100\n\nOPEN_ADMINISTRATIVELY_PROHIBITED = 1\nOPEN_CONNECT_FAILED = 2\nOPEN_UNKNOWN_CHANNEL_TYPE = 3\nOPEN_RESOURCE_SHORTAGE = 4\n\nEXTENDED_DATA_STDERR = 1\n\nmessages = {}\nfor name, value in locals().copy().items():\n    if name[:4] == 'MSG_':\n        messages[value] = name  # Doesn't handle doubles\n\nalphanums = networkString(string.ascii_letters + string.digits)\nTRANSLATE_TABLE = b''.join([chr(i) in alphanums and chr(i) or b'_'\n                            for i in range(256)])\nSSHConnection.protocolMessages = messages\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/factory.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nA Factory for SSH servers.\n\nSee also L{twisted.conch.openssh_compat.factory} for OpenSSH compatibility.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.internet import protocol\nfrom twisted.python import log\n\nfrom twisted.conch import error\nfrom twisted.conch.ssh import (_kex, transport, userauth, connection)\n\nimport random\n\n\nclass SSHFactory(protocol.Factory):\n    \"\"\"\n    A Factory for SSH servers.\n    \"\"\"\n    protocol = transport.SSHServerTransport\n\n    services = {\n        b'ssh-userauth':userauth.SSHUserAuthServer,\n        b'ssh-connection':connection.SSHConnection\n    }\n    def startFactory(self):\n        \"\"\"\n        Check for public and private keys.\n        \"\"\"\n        if not hasattr(self,'publicKeys'):\n            self.publicKeys = self.getPublicKeys()\n        if not hasattr(self,'privateKeys'):\n            self.privateKeys = self.getPrivateKeys()\n        if not self.publicKeys or not self.privateKeys:\n            raise error.ConchError('no host keys, failing')\n        if not hasattr(self,'primes'):\n            self.primes = self.getPrimes()\n\n\n    def buildProtocol(self, addr):\n        \"\"\"\n        Create an instance of the server side of the SSH protocol.\n\n        @type addr: L{twisted.internet.interfaces.IAddress} provider\n        @param addr: The address at which the server will listen.\n\n        @rtype: L{twisted.conch.ssh.transport.SSHServerTransport}\n        @return: The built transport.\n        \"\"\"\n        t = protocol.Factory.buildProtocol(self, addr)\n        t.supportedPublicKeys = self.privateKeys.keys()\n        if not self.primes:\n            log.msg('disabling non-fixed-group key exchange algorithms '\n                    'because we cannot find moduli file')\n            t.supportedKeyExchanges = [\n                kexAlgorithm for kexAlgorithm in t.supportedKeyExchanges\n                if _kex.isFixedGroup(kexAlgorithm) or\n                     _kex.isEllipticCurve(kexAlgorithm)]\n        return t\n\n\n    def getPublicKeys(self):\n        \"\"\"\n        Called when the factory is started to get the public portions of the\n        servers host keys.  Returns a dictionary mapping SSH key types to\n        public key strings.\n\n        @rtype: L{dict}\n        \"\"\"\n        raise NotImplementedError('getPublicKeys unimplemented')\n\n\n    def getPrivateKeys(self):\n        \"\"\"\n        Called when the factory is started to get the  private portions of the\n        servers host keys.  Returns a dictionary mapping SSH key types to\n        L{twisted.conch.ssh.keys.Key} objects.\n\n        @rtype: L{dict}\n        \"\"\"\n        raise NotImplementedError('getPrivateKeys unimplemented')\n\n\n    def getPrimes(self):\n        \"\"\"\n        Called when the factory is started to get Diffie-Hellman generators and\n        primes to use.  Returns a dictionary mapping number of bits to lists\n        of tuple of (generator, prime).\n\n        @rtype: L{dict}\n        \"\"\"\n\n\n    def getDHPrime(self, bits):\n        \"\"\"\n        Return a tuple of (g, p) for a Diffe-Hellman process, with p being as\n        close to bits bits as possible.\n\n        @type bits: L{int}\n        @rtype:     L{tuple}\n        \"\"\"\n        primesKeys = sorted(self.primes.keys(), key=lambda i: abs(i - bits))\n        realBits = primesKeys[0]\n        return random.choice(self.primes[realBits])\n\n\n    def getService(self, transport, service):\n        \"\"\"\n        Return a class to use as a service for the given transport.\n\n        @type transport:    L{transport.SSHServerTransport}\n        @type service:      L{bytes}\n        @rtype:             subclass of L{service.SSHService}\n        \"\"\"\n        if service == b'ssh-userauth' or hasattr(transport, 'avatar'):\n            return self.services[service]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/filetransfer.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_filetransfer -*-\n#\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom __future__ import division, absolute_import\n\nimport errno\nimport struct\nimport warnings\n\nfrom zope.interface import implementer\n\nfrom twisted.conch.interfaces import ISFTPServer, ISFTPFile\nfrom twisted.conch.ssh.common import NS, getNS\nfrom twisted.internet import defer, protocol\nfrom twisted.python import failure, log\nfrom twisted.python.compat import (\n    _PY3, range, itervalues, nativeString, networkString)\n\n\n\nclass FileTransferBase(protocol.Protocol):\n\n    versions = (3, )\n\n    packetTypes = {}\n\n    def __init__(self):\n        self.buf = b''\n        self.otherVersion = None  # This gets set\n\n\n    def sendPacket(self, kind, data):\n        self.transport.write(struct.pack('!LB', len(data)+1, kind) + data)\n\n\n    def dataReceived(self, data):\n        self.buf += data\n        while len(self.buf) > 5:\n            length, kind = struct.unpack('!LB', self.buf[:5])\n            if len(self.buf) < 4 + length:\n                return\n            data, self.buf = self.buf[5:4+length], self.buf[4+length:]\n            packetType = self.packetTypes.get(kind, None)\n            if not packetType:\n                log.msg('no packet type for', kind)\n                continue\n            f = getattr(self, 'packet_{}'.format(packetType), None)\n            if not f:\n                log.msg('not implemented: {}'.format(packetType))\n                log.msg(repr(data[4:]))\n                reqId, = struct.unpack('!L', data[:4])\n                self._sendStatus(reqId, FX_OP_UNSUPPORTED,\n                                 \"don't understand {}\".format(packetType))\n                # XXX not implemented\n                continue\n            try:\n                f(data)\n            except Exception:\n                log.err()\n                continue\n\n\n    def _parseAttributes(self, data):\n        (flags,) = struct.unpack('!L', data[:4])\n        attrs = {}\n        data = data[4:]\n        if flags & FILEXFER_ATTR_SIZE == FILEXFER_ATTR_SIZE:\n            (size,) = struct.unpack('!Q', data[:8])\n            attrs['size'] = size\n            data = data[8:]\n        if flags & FILEXFER_ATTR_OWNERGROUP == FILEXFER_ATTR_OWNERGROUP:\n            uid, gid = struct.unpack('!2L', data[:8])\n            attrs['uid'] = uid\n            attrs['gid'] = gid\n            data = data[8:]\n        if flags & FILEXFER_ATTR_PERMISSIONS == FILEXFER_ATTR_PERMISSIONS:\n            (perms,) = struct.unpack('!L', data[:4])\n            attrs['permissions'] = perms\n            data = data[4:]\n        if flags & FILEXFER_ATTR_ACMODTIME == FILEXFER_ATTR_ACMODTIME:\n            atime, mtime = struct.unpack('!2L', data[:8])\n            attrs['atime'] = atime\n            attrs['mtime'] = mtime\n            data = data[8:]\n        if flags & FILEXFER_ATTR_EXTENDED == FILEXFER_ATTR_EXTENDED:\n            (extendedCount,) = struct.unpack('!L', data[:4])\n            data = data[4:]\n            for i in range(extendedCount):\n                (extendedType, data) = getNS(data)\n                (extendedData, data) = getNS(data)\n                attrs['ext_{}'.format(nativeString(extendedType))] = \\\n                    extendedData\n        return attrs, data\n\n\n    def _packAttributes(self, attrs):\n        flags = 0\n        data = b''\n        if 'size' in attrs:\n            data += struct.pack('!Q', attrs['size'])\n            flags |= FILEXFER_ATTR_SIZE\n        if 'uid' in attrs and 'gid' in attrs:\n            data += struct.pack('!2L', attrs['uid'], attrs['gid'])\n            flags |= FILEXFER_ATTR_OWNERGROUP\n        if 'permissions' in attrs:\n            data += struct.pack('!L', attrs['permissions'])\n            flags |= FILEXFER_ATTR_PERMISSIONS\n        if 'atime' in attrs and 'mtime' in attrs:\n            data += struct.pack('!2L', attrs['atime'], attrs['mtime'])\n            flags |= FILEXFER_ATTR_ACMODTIME\n        extended = []\n        for k in attrs:\n            if k.startswith('ext_'):\n                extType = NS(networkString(k[4:]))\n                extData = NS(attrs[k])\n                extended.append(extType + extData)\n        if extended:\n            data += struct.pack('!L', len(extended))\n            data += b''.join(extended)\n            flags |= FILEXFER_ATTR_EXTENDED\n        return struct.pack('!L', flags) + data\n\n\n\nclass FileTransferServer(FileTransferBase):\n\n    def __init__(self, data=None, avatar=None):\n        FileTransferBase.__init__(self)\n        self.client = ISFTPServer(avatar) # yay interfaces\n        self.openFiles = {}\n        self.openDirs = {}\n\n\n    def packet_INIT(self, data):\n        (version,) = struct.unpack('!L', data[:4])\n        self.version = min(list(self.versions) + [version])\n        data = data[4:]\n        ext = {}\n        while data:\n            extName, data = getNS(data)\n            extData, data = getNS(data)\n            ext[extName] = extData\n        ourExt = self.client.gotVersion(version, ext)\n        ourExtData = b\"\"\n        for (k, v) in ourExt.items():\n            ourExtData += NS(k) + NS(v)\n        self.sendPacket(FXP_VERSION, struct.pack('!L', self.version) +\n                        ourExtData)\n\n\n    def packet_OPEN(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        filename, data = getNS(data)\n        (flags,) = struct.unpack('!L', data[:4])\n        data = data[4:]\n        attrs, data = self._parseAttributes(data)\n        assert data == b'', 'still have data in OPEN: {!r}'.format(data)\n        d = defer.maybeDeferred(self.client.openFile, filename, flags, attrs)\n        d.addCallback(self._cbOpenFile, requestId)\n        d.addErrback(self._ebStatus, requestId, b\"open failed\")\n\n\n    def _cbOpenFile(self, fileObj, requestId):\n        fileId = networkString(str(hash(fileObj)))\n        if fileId in self.openFiles:\n            raise KeyError('id already open')\n        self.openFiles[fileId] = fileObj\n        self.sendPacket(FXP_HANDLE, requestId + NS(fileId))\n\n\n    def packet_CLOSE(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        handle, data = getNS(data)\n        assert data == b'', 'still have data in CLOSE: {!r}'.format(data)\n        if handle in self.openFiles:\n            fileObj = self.openFiles[handle]\n            d = defer.maybeDeferred(fileObj.close)\n            d.addCallback(self._cbClose, handle, requestId)\n            d.addErrback(self._ebStatus, requestId, b\"close failed\")\n        elif handle in self.openDirs:\n            dirObj = self.openDirs[handle][0]\n            d = defer.maybeDeferred(dirObj.close)\n            d.addCallback(self._cbClose, handle, requestId, 1)\n            d.addErrback(self._ebStatus, requestId, b\"close failed\")\n        else:\n            self._ebClose(failure.Failure(KeyError()), requestId)\n\n\n    def _cbClose(self, result, handle, requestId, isDir=0):\n        if isDir:\n            del self.openDirs[handle]\n        else:\n            del self.openFiles[handle]\n        self._sendStatus(requestId, FX_OK, b'file closed')\n\n\n    def packet_READ(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        handle, data = getNS(data)\n        (offset, length), data = struct.unpack('!QL', data[:12]), data[12:]\n        assert data == b'', 'still have data in READ: {!r}'.format(data)\n        if handle not in self.openFiles:\n            self._ebRead(failure.Failure(KeyError()), requestId)\n        else:\n            fileObj = self.openFiles[handle]\n            d = defer.maybeDeferred(fileObj.readChunk, offset, length)\n            d.addCallback(self._cbRead, requestId)\n            d.addErrback(self._ebStatus, requestId, b\"read failed\")\n\n\n    def _cbRead(self, result, requestId):\n        if result == b'':  # Python's read will return this for EOF\n            raise EOFError()\n        self.sendPacket(FXP_DATA, requestId + NS(result))\n\n\n    def packet_WRITE(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        handle, data = getNS(data)\n        offset, = struct.unpack('!Q', data[:8])\n        data = data[8:]\n        writeData, data = getNS(data)\n        assert data == b'', 'still have data in WRITE: {!r}'.format(data)\n        if handle not in self.openFiles:\n            self._ebWrite(failure.Failure(KeyError()), requestId)\n        else:\n            fileObj = self.openFiles[handle]\n            d = defer.maybeDeferred(fileObj.writeChunk, offset, writeData)\n            d.addCallback(self._cbStatus, requestId, b\"write succeeded\")\n            d.addErrback(self._ebStatus, requestId, b\"write failed\")\n\n\n    def packet_REMOVE(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        filename, data = getNS(data)\n        assert data == b'', 'still have data in REMOVE: {!r}'.format(data)\n        d = defer.maybeDeferred(self.client.removeFile, filename)\n        d.addCallback(self._cbStatus, requestId, b\"remove succeeded\")\n        d.addErrback(self._ebStatus, requestId, b\"remove failed\")\n\n\n    def packet_RENAME(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        oldPath, data = getNS(data)\n        newPath, data = getNS(data)\n        assert data == b'', 'still have data in RENAME: {!r}'.format(data)\n        d = defer.maybeDeferred(self.client.renameFile, oldPath, newPath)\n        d.addCallback(self._cbStatus, requestId, b\"rename succeeded\")\n        d.addErrback(self._ebStatus, requestId, b\"rename failed\")\n\n\n    def packet_MKDIR(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        path, data = getNS(data)\n        attrs, data = self._parseAttributes(data)\n        assert data == b'', 'still have data in MKDIR: {!r}'.format(data)\n        d = defer.maybeDeferred(self.client.makeDirectory, path, attrs)\n        d.addCallback(self._cbStatus, requestId, b\"mkdir succeeded\")\n        d.addErrback(self._ebStatus, requestId, b\"mkdir failed\")\n\n\n    def packet_RMDIR(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        path, data = getNS(data)\n        assert data == b'', 'still have data in RMDIR: {!r}'.format(data)\n        d = defer.maybeDeferred(self.client.removeDirectory, path)\n        d.addCallback(self._cbStatus, requestId, b\"rmdir succeeded\")\n        d.addErrback(self._ebStatus, requestId, b\"rmdir failed\")\n\n\n    def packet_OPENDIR(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        path, data = getNS(data)\n        assert data == b'', 'still have data in OPENDIR: {!r}'.format(data)\n        d = defer.maybeDeferred(self.client.openDirectory, path)\n        d.addCallback(self._cbOpenDirectory, requestId)\n        d.addErrback(self._ebStatus, requestId, b\"opendir failed\")\n\n\n    def _cbOpenDirectory(self, dirObj, requestId):\n        handle = networkString((str(hash(dirObj))))\n        if handle in self.openDirs:\n            raise KeyError(\"already opened this directory\")\n        self.openDirs[handle] = [dirObj, iter(dirObj)]\n        self.sendPacket(FXP_HANDLE, requestId + NS(handle))\n\n\n    def packet_READDIR(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        handle, data = getNS(data)\n        assert data == b'', 'still have data in READDIR: {!r}'.format(data)\n        if handle not in self.openDirs:\n            self._ebStatus(failure.Failure(KeyError()), requestId)\n        else:\n            dirObj, dirIter = self.openDirs[handle]\n            d = defer.maybeDeferred(self._scanDirectory, dirIter, [])\n            d.addCallback(self._cbSendDirectory, requestId)\n            d.addErrback(self._ebStatus, requestId, b\"scan directory failed\")\n\n\n    def _scanDirectory(self, dirIter, f):\n        while len(f) < 250:\n            try:\n                info = next(dirIter)\n            except StopIteration:\n                if not f:\n                    raise EOFError\n                return f\n            if isinstance(info, defer.Deferred):\n                info.addCallback(self._cbScanDirectory, dirIter, f)\n                return\n            else:\n                f.append(info)\n        return f\n\n\n    def _cbScanDirectory(self, result, dirIter, f):\n        f.append(result)\n        return self._scanDirectory(dirIter, f)\n\n\n    def _cbSendDirectory(self, result, requestId):\n        data = b''\n        for (filename, longname, attrs) in result:\n            data += NS(filename)\n            data += NS(longname)\n            data += self._packAttributes(attrs)\n        self.sendPacket(FXP_NAME, requestId +\n                        struct.pack('!L', len(result))+data)\n\n\n    def packet_STAT(self, data, followLinks=1):\n        requestId = data[:4]\n        data = data[4:]\n        path, data = getNS(data)\n        assert data == b'', 'still have data in STAT/LSTAT: {!r}'.format(data)\n        d = defer.maybeDeferred(self.client.getAttrs, path, followLinks)\n        d.addCallback(self._cbStat, requestId)\n        d.addErrback(self._ebStatus, requestId, b'stat/lstat failed')\n\n\n    def packet_LSTAT(self, data):\n        self.packet_STAT(data, 0)\n\n\n    def packet_FSTAT(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        handle, data = getNS(data)\n        assert data == b'', 'still have data in FSTAT: {!r}'.format(data)\n        if handle not in self.openFiles:\n            self._ebStatus(failure.Failure(KeyError(\n                '{} not in self.openFiles'.format(handle))), requestId)\n        else:\n            fileObj = self.openFiles[handle]\n            d = defer.maybeDeferred(fileObj.getAttrs)\n            d.addCallback(self._cbStat, requestId)\n            d.addErrback(self._ebStatus, requestId, b'fstat failed')\n\n\n    def _cbStat(self, result, requestId):\n        data = requestId + self._packAttributes(result)\n        self.sendPacket(FXP_ATTRS, data)\n\n\n    def packet_SETSTAT(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        path, data = getNS(data)\n        attrs, data = self._parseAttributes(data)\n        if data != b'':\n            log.msg('WARN: still have data in SETSTAT: {!r}'.format(data))\n        d = defer.maybeDeferred(self.client.setAttrs, path, attrs)\n        d.addCallback(self._cbStatus, requestId, b'setstat succeeded')\n        d.addErrback(self._ebStatus, requestId, b'setstat failed')\n\n\n    def packet_FSETSTAT(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        handle, data = getNS(data)\n        attrs, data = self._parseAttributes(data)\n        assert data == b'', 'still have data in FSETSTAT: {!r}'.format(data)\n        if handle not in self.openFiles:\n            self._ebStatus(failure.Failure(KeyError()), requestId)\n        else:\n            fileObj = self.openFiles[handle]\n            d = defer.maybeDeferred(fileObj.setAttrs, attrs)\n            d.addCallback(self._cbStatus, requestId, b'fsetstat succeeded')\n            d.addErrback(self._ebStatus, requestId, b'fsetstat failed')\n\n\n    def packet_READLINK(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        path, data = getNS(data)\n        assert data == b'', 'still have data in READLINK: {!r}'.format(data)\n        d = defer.maybeDeferred(self.client.readLink, path)\n        d.addCallback(self._cbReadLink, requestId)\n        d.addErrback(self._ebStatus, requestId, b'readlink failed')\n\n\n    def _cbReadLink(self, result, requestId):\n        self._cbSendDirectory([(result, b'', {})], requestId)\n\n\n    def packet_SYMLINK(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        linkPath, data = getNS(data)\n        targetPath, data = getNS(data)\n        d = defer.maybeDeferred(self.client.makeLink, linkPath, targetPath)\n        d.addCallback(self._cbStatus, requestId, b'symlink succeeded')\n        d.addErrback(self._ebStatus, requestId, b'symlink failed')\n\n\n    def packet_REALPATH(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        path, data = getNS(data)\n        assert data == b'', 'still have data in REALPATH: {!r}'.format(data)\n        d = defer.maybeDeferred(self.client.realPath, path)\n        d.addCallback(self._cbReadLink, requestId)  # Same return format\n        d.addErrback(self._ebStatus, requestId, b'realpath failed')\n\n\n    def packet_EXTENDED(self, data):\n        requestId = data[:4]\n        data = data[4:]\n        extName, extData = getNS(data)\n        d = defer.maybeDeferred(self.client.extendedRequest, extName, extData)\n        d.addCallback(self._cbExtended, requestId)\n        d.addErrback(self._ebStatus, requestId,\n                     b'extended ' + extName + b' failed')\n\n\n    def _cbExtended(self, data, requestId):\n        self.sendPacket(FXP_EXTENDED_REPLY, requestId + data)\n\n\n    def _cbStatus(self, result, requestId, msg=b\"request succeeded\"):\n        self._sendStatus(requestId, FX_OK, msg)\n\n\n    def _ebStatus(self, reason, requestId, msg=b\"request failed\"):\n        code = FX_FAILURE\n        message = msg\n        if isinstance(reason.value, (IOError, OSError)):\n            if reason.value.errno == errno.ENOENT:  # No such file\n                code = FX_NO_SUCH_FILE\n                message = networkString(reason.value.strerror)\n            elif reason.value.errno == errno.EACCES:  # Permission denied\n                code = FX_PERMISSION_DENIED\n                message = networkString(reason.value.strerror)\n            elif reason.value.errno == errno.EEXIST:\n                code = FX_FILE_ALREADY_EXISTS\n            else:\n                log.err(reason)\n        elif isinstance(reason.value, EOFError):  # EOF\n            code = FX_EOF\n            if reason.value.args:\n                message = networkString(reason.value.args[0])\n        elif isinstance(reason.value, NotImplementedError):\n            code = FX_OP_UNSUPPORTED\n            if reason.value.args:\n                message = networkString(reason.value.args[0])\n        elif isinstance(reason.value, SFTPError):\n            code = reason.value.code\n            message = networkString(reason.value.message)\n        else:\n            log.err(reason)\n        self._sendStatus(requestId, code, message)\n\n\n    def _sendStatus(self, requestId, code, message, lang=b''):\n        \"\"\"\n        Helper method to send a FXP_STATUS message.\n        \"\"\"\n        data = requestId + struct.pack('!L', code)\n        data += NS(message)\n        data += NS(lang)\n        self.sendPacket(FXP_STATUS, data)\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Clean all opened files and directories.\n        \"\"\"\n        for fileObj in self.openFiles.values():\n            fileObj.close()\n        self.openFiles = {}\n        for (dirObj, dirIter) in self.openDirs.values():\n            dirObj.close()\n        self.openDirs = {}\n\n\n\nclass FileTransferClient(FileTransferBase):\n\n    def __init__(self, extData={}):\n        \"\"\"\n        @param extData: a dict of extended_name : extended_data items\n        to be sent to the server.\n        \"\"\"\n        FileTransferBase.__init__(self)\n        self.extData = {}\n        self.counter = 0\n        self.openRequests = {} # id -> Deferred\n\n\n    def connectionMade(self):\n        data = struct.pack('!L', max(self.versions))\n        for (k, v) in itervalues(self.extData):\n            data += NS(k) + NS(v)\n        self.sendPacket(FXP_INIT, data)\n\n\n    def _sendRequest(self, msg, data):\n        data = struct.pack('!L', self.counter) + data\n        d = defer.Deferred()\n        self.openRequests[self.counter] = d\n        self.counter += 1\n        self.sendPacket(msg, data)\n        return d\n\n\n    def _parseRequest(self, data):\n        (id,) = struct.unpack('!L', data[:4])\n        d = self.openRequests[id]\n        del self.openRequests[id]\n        return d, data[4:]\n\n\n    def openFile(self, filename, flags, attrs):\n        \"\"\"\n        Open a file.\n\n        This method returns a L{Deferred} that is called back with an object\n        that provides the L{ISFTPFile} interface.\n\n        @type filename: L{bytes}\n        @param filename: a string representing the file to open.\n\n        @param flags: an integer of the flags to open the file with, ORed together.\n        The flags and their values are listed at the bottom of this file.\n\n        @param attrs: a list of attributes to open the file with.  It is a\n        dictionary, consisting of 0 or more keys.  The possible keys are::\n\n            size: the size of the file in bytes\n            uid: the user ID of the file as an integer\n            gid: the group ID of the file as an integer\n            permissions: the permissions of the file with as an integer.\n            the bit representation of this field is defined by POSIX.\n            atime: the access time of the file as seconds since the epoch.\n            mtime: the modification time of the file as seconds since the epoch.\n            ext_*: extended attributes.  The server is not required to\n            understand this, but it may.\n\n        NOTE: there is no way to indicate text or binary files.  it is up\n        to the SFTP client to deal with this.\n        \"\"\"\n        data = NS(filename) + struct.pack('!L', flags) + self._packAttributes(attrs)\n        d = self._sendRequest(FXP_OPEN, data)\n        d.addCallback(self._cbOpenHandle, ClientFile, filename)\n        return d\n\n\n    def _cbOpenHandle(self, handle, handleClass, name):\n        \"\"\"\n        Callback invoked when an OPEN or OPENDIR request succeeds.\n\n        @param handle: The handle returned by the server\n        @type handle: L{bytes}\n        @param handleClass: The class that will represent the\n        newly-opened file or directory to the user (either L{ClientFile} or\n        L{ClientDirectory}).\n        @param name: The name of the file or directory represented\n        by C{handle}.\n        @type name: L{bytes}\n        \"\"\"\n        cb = handleClass(self, handle)\n        cb.name = name\n        return cb\n\n\n    def removeFile(self, filename):\n        \"\"\"\n        Remove the given file.\n\n        This method returns a Deferred that is called back when it succeeds.\n\n        @type filename: L{bytes}\n        @param filename: the name of the file as a string.\n        \"\"\"\n        return self._sendRequest(FXP_REMOVE, NS(filename))\n\n\n    def renameFile(self, oldpath, newpath):\n        \"\"\"\n        Rename the given file.\n\n        This method returns a Deferred that is called back when it succeeds.\n\n        @type oldpath: L{bytes}\n        @param oldpath: the current location of the file.\n        @type newpath: L{bytes}\n        @param newpath: the new file name.\n        \"\"\"\n        return self._sendRequest(FXP_RENAME, NS(oldpath)+NS(newpath))\n\n\n    def makeDirectory(self, path, attrs):\n        \"\"\"\n        Make a directory.\n\n        This method returns a Deferred that is called back when it is\n        created.\n\n        @type path: L{bytes}\n        @param path: the name of the directory to create as a string.\n\n        @param attrs: a dictionary of attributes to create the directory\n        with.  Its meaning is the same as the attrs in the openFile method.\n        \"\"\"\n        return self._sendRequest(FXP_MKDIR, NS(path)+self._packAttributes(attrs))\n\n\n    def removeDirectory(self, path):\n        \"\"\"\n        Remove a directory (non-recursively)\n\n        It is an error to remove a directory that has files or directories in\n        it.\n\n        This method returns a Deferred that is called back when it is removed.\n\n        @type path: L{bytes}\n        @param path: the directory to remove.\n        \"\"\"\n        return self._sendRequest(FXP_RMDIR, NS(path))\n\n\n    def openDirectory(self, path):\n        \"\"\"\n        Open a directory for scanning.\n\n        This method returns a Deferred that is called back with an iterable\n        object that has a close() method.\n\n        The close() method is called when the client is finished reading\n        from the directory.  At this point, the iterable will no longer\n        be used.\n\n        The iterable returns triples of the form (filename, longname, attrs)\n        or a Deferred that returns the same.  The sequence must support\n        __getitem__, but otherwise may be any 'sequence-like' object.\n\n        filename is the name of the file relative to the directory.\n        logname is an expanded format of the filename.  The recommended format\n        is:\n        -rwxr-xr-x   1 mjos     staff      348911 Mar 25 14:29 t-filexfer\n        1234567890 123 12345678 12345678 12345678 123456789012\n\n        The first line is sample output, the second is the length of the field.\n        The fields are: permissions, link count, user owner, group owner,\n        size in bytes, modification time.\n\n        attrs is a dictionary in the format of the attrs argument to openFile.\n\n        @type path: L{bytes}\n        @param path: the directory to open.\n        \"\"\"\n        d = self._sendRequest(FXP_OPENDIR, NS(path))\n        d.addCallback(self._cbOpenHandle, ClientDirectory, path)\n        return d\n\n\n    def getAttrs(self, path, followLinks=0):\n        \"\"\"\n        Return the attributes for the given path.\n\n        This method returns a dictionary in the same format as the attrs\n        argument to openFile or a Deferred that is called back with same.\n\n        @type path: L{bytes}\n        @param path: the path to return attributes for as a string.\n        @param followLinks: a boolean.  if it is True, follow symbolic links\n        and return attributes for the real path at the base.  if it is False,\n        return attributes for the specified path.\n        \"\"\"\n        if followLinks: m = FXP_STAT\n        else: m = FXP_LSTAT\n        return self._sendRequest(m, NS(path))\n\n\n    def setAttrs(self, path, attrs):\n        \"\"\"\n        Set the attributes for the path.\n\n        This method returns when the attributes are set or a Deferred that is\n        called back when they are.\n\n        @type path: L{bytes}\n        @param path: the path to set attributes for as a string.\n        @param attrs: a dictionary in the same format as the attrs argument to\n        openFile.\n        \"\"\"\n        data = NS(path) + self._packAttributes(attrs)\n        return self._sendRequest(FXP_SETSTAT, data)\n\n\n    def readLink(self, path):\n        \"\"\"\n        Find the root of a set of symbolic links.\n\n        This method returns the target of the link, or a Deferred that\n        returns the same.\n\n        @type path: L{bytes}\n        @param path: the path of the symlink to read.\n        \"\"\"\n        d = self._sendRequest(FXP_READLINK, NS(path))\n        return d.addCallback(self._cbRealPath)\n\n\n    def makeLink(self, linkPath, targetPath):\n        \"\"\"\n        Create a symbolic link.\n\n        This method returns when the link is made, or a Deferred that\n        returns the same.\n\n        @type linkPath: L{bytes}\n        @param linkPath: the pathname of the symlink as a string\n        @type targetPath: L{bytes}\n        @param targetPath: the path of the target of the link as a string.\n        \"\"\"\n        return self._sendRequest(FXP_SYMLINK, NS(linkPath)+NS(targetPath))\n\n\n    def realPath(self, path):\n        \"\"\"\n        Convert any path to an absolute path.\n\n        This method returns the absolute path as a string, or a Deferred\n        that returns the same.\n\n        @type path: L{bytes}\n        @param path: the path to convert as a string.\n        \"\"\"\n        d = self._sendRequest(FXP_REALPATH, NS(path))\n        return d.addCallback(self._cbRealPath)\n\n\n    def _cbRealPath(self, result):\n        name, longname, attrs = result[0]\n        if _PY3:\n            name = name.decode(\"utf-8\")\n        return name\n\n\n    def extendedRequest(self, request, data):\n        \"\"\"\n        Make an extended request of the server.\n\n        The method returns a Deferred that is called back with\n        the result of the extended request.\n\n        @type request: L{bytes}\n        @param request: the name of the extended request to make.\n        @type data: L{bytes}\n        @param data: any other data that goes along with the request.\n        \"\"\"\n        return self._sendRequest(FXP_EXTENDED, NS(request) + data)\n\n\n    def packet_VERSION(self, data):\n        version, = struct.unpack('!L', data[:4])\n        data = data[4:]\n        d = {}\n        while data:\n            k, data = getNS(data)\n            v, data = getNS(data)\n            d[k]=v\n        self.version = version\n        self.gotServerVersion(version, d)\n\n\n    def packet_STATUS(self, data):\n        d, data = self._parseRequest(data)\n        code, = struct.unpack('!L', data[:4])\n        data = data[4:]\n        if len(data) >= 4:\n            msg, data = getNS(data)\n            if len(data) >= 4:\n                lang, data = getNS(data)\n            else:\n                lang = b''\n        else:\n            msg = b''\n            lang = b''\n        if code == FX_OK:\n            d.callback((msg, lang))\n        elif code == FX_EOF:\n            d.errback(EOFError(msg))\n        elif code == FX_OP_UNSUPPORTED:\n            d.errback(NotImplementedError(msg))\n        else:\n            d.errback(SFTPError(code, nativeString(msg), lang))\n\n\n    def packet_HANDLE(self, data):\n        d, data = self._parseRequest(data)\n        handle, _ = getNS(data)\n        d.callback(handle)\n\n\n    def packet_DATA(self, data):\n        d, data = self._parseRequest(data)\n        d.callback(getNS(data)[0])\n\n\n    def packet_NAME(self, data):\n        d, data = self._parseRequest(data)\n        count, = struct.unpack('!L', data[:4])\n        data = data[4:]\n        files = []\n        for i in range(count):\n            filename, data = getNS(data)\n            longname, data = getNS(data)\n            attrs, data = self._parseAttributes(data)\n            files.append((filename, longname, attrs))\n        d.callback(files)\n\n\n    def packet_ATTRS(self, data):\n        d, data = self._parseRequest(data)\n        d.callback(self._parseAttributes(data)[0])\n\n\n    def packet_EXTENDED_REPLY(self, data):\n        d, data = self._parseRequest(data)\n        d.callback(data)\n\n\n    def gotServerVersion(self, serverVersion, extData):\n        \"\"\"\n        Called when the client sends their version info.\n\n        @param otherVersion: an integer representing the version of the SFTP\n        protocol they are claiming.\n        @param extData: a dictionary of extended_name : extended_data items.\n        These items are sent by the client to indicate additional features.\n        \"\"\"\n\n\n\n@implementer(ISFTPFile)\nclass ClientFile:\n    def __init__(self, parent, handle):\n        self.parent = parent\n        self.handle = NS(handle)\n\n\n    def close(self):\n        return self.parent._sendRequest(FXP_CLOSE, self.handle)\n\n\n    def readChunk(self, offset, length):\n        data = self.handle + struct.pack(\"!QL\", offset, length)\n        return self.parent._sendRequest(FXP_READ, data)\n\n\n    def writeChunk(self, offset, chunk):\n        data = self.handle + struct.pack(\"!Q\", offset) + NS(chunk)\n        return self.parent._sendRequest(FXP_WRITE, data)\n\n\n    def getAttrs(self):\n        return self.parent._sendRequest(FXP_FSTAT, self.handle)\n\n\n    def setAttrs(self, attrs):\n        data = self.handle + self.parent._packAttributes(attrs)\n        return self.parent._sendRequest(FXP_FSTAT, data)\n\n\n\nclass ClientDirectory:\n\n    def __init__(self, parent, handle):\n        self.parent = parent\n        self.handle = NS(handle)\n        self.filesCache = []\n\n\n    def read(self):\n        return self.parent._sendRequest(FXP_READDIR, self.handle)\n\n\n    def close(self):\n        if self.handle is None:\n            return defer.succeed(None)\n        d = self.parent._sendRequest(FXP_CLOSE, self.handle)\n        self.handle = None\n        return d\n\n\n    def __iter__(self):\n        return self\n\n\n    def __next__(self):\n        warnings.warn(\n            ('Using twisted.conch.ssh.filetransfer.ClientDirectory '\n             'as an iterator was deprecated in Twisted 18.9.0.'),\n            category=DeprecationWarning,\n            stacklevel=2)\n        if self.filesCache:\n            return self.filesCache.pop(0)\n        if self.filesCache is None:\n            raise StopIteration()\n        d = self.read()\n        d.addCallbacks(self._cbReadDir, self._ebReadDir)\n        return d\n\n    next = __next__\n\n\n    def _cbReadDir(self, names):\n        self.filesCache = names[1:]\n        return names[0]\n\n\n    def _ebReadDir(self, reason):\n        reason.trap(EOFError)\n        self.filesCache = None\n        return failure.Failure(StopIteration())\n\n\n\nclass SFTPError(Exception):\n\n    def __init__(self, errorCode, errorMessage, lang=''):\n        Exception.__init__(self)\n        self.code = errorCode\n        self._message = errorMessage\n        self.lang = lang\n\n\n    def message(self):\n        \"\"\"\n        A string received over the network that explains the error to a human.\n        \"\"\"\n        # Python 2.6 deprecates assigning to the 'message' attribute of an\n        # exception. We define this read-only property here in order to\n        # prevent the warning about deprecation while maintaining backwards\n        # compatibility with object clients that rely on the 'message'\n        # attribute being set correctly. See bug #3897.\n        return self._message\n    message = property(message)\n\n\n    def __str__(self):\n        return 'SFTPError {}: {}'.format(self.code, self.message)\n\n\n\nFXP_INIT = 1\nFXP_VERSION = 2\nFXP_OPEN = 3\nFXP_CLOSE = 4\nFXP_READ = 5\nFXP_WRITE = 6\nFXP_LSTAT = 7\nFXP_FSTAT = 8\nFXP_SETSTAT = 9\nFXP_FSETSTAT = 10\nFXP_OPENDIR = 11\nFXP_READDIR = 12\nFXP_REMOVE = 13\nFXP_MKDIR = 14\nFXP_RMDIR = 15\nFXP_REALPATH = 16\nFXP_STAT = 17\nFXP_RENAME = 18\nFXP_READLINK = 19\nFXP_SYMLINK = 20\nFXP_STATUS = 101\nFXP_HANDLE = 102\nFXP_DATA = 103\nFXP_NAME = 104\nFXP_ATTRS = 105\nFXP_EXTENDED = 200\nFXP_EXTENDED_REPLY = 201\n\nFILEXFER_ATTR_SIZE = 0x00000001\nFILEXFER_ATTR_UIDGID = 0x00000002\nFILEXFER_ATTR_OWNERGROUP = FILEXFER_ATTR_UIDGID\nFILEXFER_ATTR_PERMISSIONS = 0x00000004\nFILEXFER_ATTR_ACMODTIME = 0x00000008\nFILEXFER_ATTR_EXTENDED = 0x80000000\n\nFILEXFER_TYPE_REGULAR = 1\nFILEXFER_TYPE_DIRECTORY = 2\nFILEXFER_TYPE_SYMLINK = 3\nFILEXFER_TYPE_SPECIAL = 4\nFILEXFER_TYPE_UNKNOWN = 5\n\nFXF_READ = 0x00000001\nFXF_WRITE = 0x00000002\nFXF_APPEND = 0x00000004\nFXF_CREAT = 0x00000008\nFXF_TRUNC = 0x00000010\nFXF_EXCL = 0x00000020\nFXF_TEXT = 0x00000040\n\nFX_OK = 0\nFX_EOF = 1\nFX_NO_SUCH_FILE = 2\nFX_PERMISSION_DENIED = 3\nFX_FAILURE = 4\nFX_BAD_MESSAGE = 5\nFX_NO_CONNECTION = 6\nFX_CONNECTION_LOST = 7\nFX_OP_UNSUPPORTED = 8\nFX_FILE_ALREADY_EXISTS = 11\n# http://tools.ietf.org/wg/secsh/draft-ietf-secsh-filexfer/ defines more\n# useful error codes, but so far OpenSSH doesn't implement them. We use them\n# internally for clarity, but for now define them all as FX_FAILURE to be\n# compatible with existing software.\nFX_NOT_A_DIRECTORY = FX_FAILURE\nFX_FILE_IS_A_DIRECTORY = FX_FAILURE\n\n\n# initialize FileTransferBase.packetTypes:\ng = globals()\nfor name in list(g.keys()):\n    if name.startswith('FXP_'):\n        value = g[name]\n        FileTransferBase.packetTypes[value] = name[4:]\ndel g, name, value\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/forwarding.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module contains the implementation of the TCP forwarding, which allows\nclients and servers to forward arbitrary TCP data across the connection.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport struct\n\nfrom twisted.internet import protocol, reactor\nfrom twisted.internet.endpoints import HostnameEndpoint, connectProtocol\nfrom twisted.python import log\nfrom twisted.python.compat import _PY3, unicode\n\nfrom twisted.conch.ssh import common, channel\n\nclass SSHListenForwardingFactory(protocol.Factory):\n    def __init__(self, connection, hostport, klass):\n        self.conn = connection\n        self.hostport = hostport # tuple\n        self.klass = klass\n\n    def buildProtocol(self, addr):\n        channel = self.klass(conn = self.conn)\n        client = SSHForwardingClient(channel)\n        channel.client = client\n        addrTuple = (addr.host, addr.port)\n        channelOpenData = packOpen_direct_tcpip(self.hostport, addrTuple)\n        self.conn.openChannel(channel, channelOpenData)\n        return client\n\nclass SSHListenForwardingChannel(channel.SSHChannel):\n\n    def channelOpen(self, specificData):\n        log.msg('opened forwarding channel %s' % self.id)\n        if len(self.client.buf)>1:\n            b = self.client.buf[1:]\n            self.write(b)\n        self.client.buf = b''\n\n    def openFailed(self, reason):\n        self.closed()\n\n    def dataReceived(self, data):\n        self.client.transport.write(data)\n\n    def eofReceived(self):\n        self.client.transport.loseConnection()\n\n    def closed(self):\n        if hasattr(self, 'client'):\n            log.msg('closing local forwarding channel %s' % self.id)\n            self.client.transport.loseConnection()\n            del self.client\n\nclass SSHListenClientForwardingChannel(SSHListenForwardingChannel):\n\n    name = b'direct-tcpip'\n\nclass SSHListenServerForwardingChannel(SSHListenForwardingChannel):\n\n    name = b'forwarded-tcpip'\n\n\n\nclass SSHConnectForwardingChannel(channel.SSHChannel):\n    \"\"\"\n    Channel used for handling server side forwarding request.\n    It acts as a client for the remote forwarding destination.\n\n    @ivar hostport: C{(host, port)} requested by client as forwarding\n        destination.\n    @type hostport: L{tuple} or a C{sequence}\n\n    @ivar client: Protocol connected to the forwarding destination.\n    @type client: L{protocol.Protocol}\n\n    @ivar clientBuf: Data received while forwarding channel is not yet\n        connected.\n    @type clientBuf: L{bytes}\n\n    @var  _reactor: Reactor used for TCP connections.\n    @type _reactor: A reactor.\n\n    @ivar _channelOpenDeferred: Deferred used in testing to check the\n        result of C{channelOpen}.\n    @type _channelOpenDeferred: L{twisted.internet.defer.Deferred}\n    \"\"\"\n    _reactor = reactor\n\n    def __init__(self, hostport, *args, **kw):\n        channel.SSHChannel.__init__(self, *args, **kw)\n        self.hostport = hostport\n        self.client = None\n        self.clientBuf = b''\n\n\n    def channelOpen(self, specificData):\n        \"\"\"\n        See: L{channel.SSHChannel}\n        \"\"\"\n        log.msg(\"connecting to %s:%i\" % self.hostport)\n        ep = HostnameEndpoint(\n            self._reactor, self.hostport[0], self.hostport[1])\n        d = connectProtocol(ep, SSHForwardingClient(self))\n        d.addCallbacks(self._setClient, self._close)\n        self._channelOpenDeferred = d\n\n    def _setClient(self, client):\n        \"\"\"\n        Called when the connection was established to the forwarding\n        destination.\n\n        @param client: Client protocol connected to the forwarding destination.\n        @type  client: L{protocol.Protocol}\n        \"\"\"\n        self.client = client\n        log.msg(\"connected to %s:%i\" % self.hostport)\n        if self.clientBuf:\n            self.client.transport.write(self.clientBuf)\n            self.clientBuf = None\n        if self.client.buf[1:]:\n            self.write(self.client.buf[1:])\n        self.client.buf = b''\n\n\n    def _close(self, reason):\n        \"\"\"\n        Called when failed to connect to the forwarding destination.\n\n        @param reason: Reason why connection failed.\n        @type  reason: L{twisted.python.failure.Failure}\n        \"\"\"\n        log.msg(\"failed to connect: %s\" % reason)\n        self.loseConnection()\n\n\n    def dataReceived(self, data):\n        \"\"\"\n        See: L{channel.SSHChannel}\n        \"\"\"\n        if self.client:\n            self.client.transport.write(data)\n        else:\n            self.clientBuf += data\n\n\n    def closed(self):\n        \"\"\"\n        See: L{channel.SSHChannel}\n        \"\"\"\n        if self.client:\n            log.msg('closed remote forwarding channel %s' % self.id)\n            if self.client.channel:\n                self.loseConnection()\n            self.client.transport.loseConnection()\n            del self.client\n\n\n\ndef openConnectForwardingClient(remoteWindow, remoteMaxPacket, data, avatar):\n    remoteHP, origHP = unpackOpen_direct_tcpip(data)\n    return SSHConnectForwardingChannel(remoteHP, \n                                       remoteWindow=remoteWindow,\n                                       remoteMaxPacket=remoteMaxPacket,\n                                       avatar=avatar)\n\nclass SSHForwardingClient(protocol.Protocol):\n\n    def __init__(self, channel):\n        self.channel = channel\n        self.buf = b'\\000'\n\n    def dataReceived(self, data):\n        if self.buf:\n            self.buf += data\n        else:\n            self.channel.write(data)\n\n    def connectionLost(self, reason):\n        if self.channel:\n            self.channel.loseConnection()\n            self.channel = None\n\n\ndef packOpen_direct_tcpip(destination, source):\n    \"\"\"\n    Pack the data suitable for sending in a CHANNEL_OPEN packet.\n\n    @type destination: L{tuple}\n    @param destination: A tuple of the (host, port) of the destination host.\n\n    @type source: L{tuple}\n    @param source: A tuple of the (host, port) of the source host.\n    \"\"\"\n    (connHost, connPort) = destination\n    (origHost, origPort) = source\n    if isinstance(connHost, unicode):\n        connHost = connHost.encode(\"utf-8\")\n    if isinstance(origHost, unicode):\n        origHost = origHost.encode(\"utf-8\")\n    conn = common.NS(connHost) + struct.pack('>L', connPort)\n    orig = common.NS(origHost) + struct.pack('>L', origPort)\n    return conn + orig\n\npackOpen_forwarded_tcpip = packOpen_direct_tcpip\n\ndef unpackOpen_direct_tcpip(data):\n    \"\"\"Unpack the data to a usable format.\n    \"\"\"\n    connHost, rest = common.getNS(data)\n    if _PY3 and isinstance(connHost, bytes):\n        connHost = connHost.decode(\"utf-8\")\n    connPort = int(struct.unpack('>L', rest[:4])[0])\n    origHost, rest = common.getNS(rest[4:])\n    if _PY3 and isinstance(origHost, bytes):\n        origHost = origHost.decode(\"utf-8\")\n    origPort = int(struct.unpack('>L', rest[:4])[0])\n    return (connHost, connPort), (origHost, origPort)\n\nunpackOpen_forwarded_tcpip = unpackOpen_direct_tcpip\n\n\n\ndef packGlobal_tcpip_forward(peer):\n    \"\"\"\n    Pack the data for tcpip forwarding.\n\n    @param peer: A tuple of the (host, port) .\n    @type peer: L{tuple}\n    \"\"\"\n    (host, port) = peer\n    return common.NS(host) + struct.pack('>L', port)\n\n\n\ndef unpackGlobal_tcpip_forward(data):\n    host, rest = common.getNS(data)\n    if _PY3 and isinstance(host, bytes):\n        host = host.decode(\"utf-8\")\n    port = int(struct.unpack('>L', rest[:4])[0])\n    return host, port\n\n\"\"\"This is how the data -> eof -> close stuff /should/ work.\n\ndebug3: channel 1: waiting for connection\ndebug1: channel 1: connected\ndebug1: channel 1: read<=0 rfd 7 len 0\ndebug1: channel 1: read failed\ndebug1: channel 1: close_read\ndebug1: channel 1: input open -> drain\ndebug1: channel 1: ibuf empty\ndebug1: channel 1: send eof\ndebug1: channel 1: input drain -> closed\ndebug1: channel 1: rcvd eof\ndebug1: channel 1: output open -> drain\ndebug1: channel 1: obuf empty\ndebug1: channel 1: close_write\ndebug1: channel 1: output drain -> closed\ndebug1: channel 1: rcvd close\ndebug3: channel 1: will not send data after close\ndebug1: channel 1: send close\ndebug1: channel 1: is dead\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/keys.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_keys -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nHandling of RSA, DSA, and EC keys.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport binascii\nimport itertools\n\nfrom hashlib import md5, sha256\nimport base64\nimport struct\n\nimport bcrypt\nfrom cryptography.exceptions import InvalidSignature\nfrom cryptography.hazmat.backends import default_backend\nfrom cryptography.hazmat.primitives import hashes, serialization\nfrom cryptography.hazmat.primitives.asymmetric import dsa, rsa, padding, ec\nfrom cryptography.hazmat.primitives.serialization import (\n    load_pem_private_key, load_ssh_public_key)\nfrom cryptography import utils\n\ntry:\n\n    from cryptography.hazmat.primitives.asymmetric.utils import (\n        encode_dss_signature, decode_dss_signature)\nexcept ImportError:\n    from cryptography.hazmat.primitives.asymmetric.utils import (\n        encode_rfc6979_signature as encode_dss_signature,\n        decode_rfc6979_signature as decode_dss_signature)\nfrom cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes\n\nfrom pyasn1.error import PyAsn1Error\nfrom pyasn1.type import univ\nfrom pyasn1.codec.ber import decoder as berDecoder\nfrom pyasn1.codec.ber import encoder as berEncoder\n\nfrom twisted.conch.ssh import common, sexpy\nfrom twisted.conch.ssh.common import int_from_bytes, int_to_bytes\nfrom twisted.python import randbytes\nfrom twisted.python.compat import (\n    iterbytes, long, izip, nativeString, unicode, _PY3,\n    _b64decodebytes as decodebytes, _b64encodebytes as encodebytes)\nfrom twisted.python.constants import NamedConstant, Names\n\n# Curve lookup table\n_curveTable = {\n    b'ecdsa-sha2-nistp256': ec.SECP256R1(),\n    b'ecdsa-sha2-nistp384': ec.SECP384R1(),\n    b'ecdsa-sha2-nistp521': ec.SECP521R1(),\n}\n\n_secToNist = {\n    b'secp256r1' : b'nistp256',\n    b'secp384r1' : b'nistp384',\n    b'secp521r1' : b'nistp521',\n}\n\n\n\n\n\nclass BadKeyError(Exception):\n    \"\"\"\n    Raised when a key isn't what we expected from it.\n\n    XXX: we really need to check for bad keys\n    \"\"\"\n\n\n\nclass EncryptedKeyError(Exception):\n    \"\"\"\n    Raised when an encrypted key is presented to fromString/fromFile without\n    a password.\n    \"\"\"\n\n\n\nclass BadFingerPrintFormat(Exception):\n    \"\"\"\n    Raises when unsupported fingerprint formats are presented to fingerprint.\n    \"\"\"\n\n\n\nclass FingerprintFormats(Names):\n    \"\"\"\n    Constants representing the supported formats of key fingerprints.\n\n    @cvar MD5_HEX: Named constant representing fingerprint format generated\n        using md5[RFC1321] algorithm in hexadecimal encoding.\n    @type MD5_HEX: L{twisted.python.constants.NamedConstant}\n\n    @cvar SHA256_BASE64: Named constant representing fingerprint format\n        generated using sha256[RFC4634] algorithm in base64 encoding\n    @type SHA256_BASE64: L{twisted.python.constants.NamedConstant}\n    \"\"\"\n    MD5_HEX = NamedConstant()\n    SHA256_BASE64 = NamedConstant()\n\n\n\nclass Key(object):\n    \"\"\"\n    An object representing a key.  A key can be either a public or\n    private key.  A public key can verify a signature; a private key can\n    create or verify a signature.  To generate a string that can be stored\n    on disk, use the toString method.  If you have a private key, but want\n    the string representation of the public key, use Key.public().toString().\n    \"\"\"\n\n    @classmethod\n    def fromFile(cls, filename, type=None, passphrase=None):\n        \"\"\"\n        Load a key from a file.\n\n        @param filename: The path to load key data from.\n\n        @type type: L{str} or L{None}\n        @param type: A string describing the format the key data is in, or\n        L{None} to attempt detection of the type.\n\n        @type passphrase: L{bytes} or L{None}\n        @param passphrase: The passphrase the key is encrypted with, or L{None}\n        if there is no encryption.\n\n        @rtype: L{Key}\n        @return: The loaded key.\n        \"\"\"\n        with open(filename, 'rb') as f:\n            return cls.fromString(f.read(), type, passphrase)\n\n\n    @classmethod\n    def fromString(cls, data, type=None, passphrase=None):\n        \"\"\"\n        Return a Key object corresponding to the string data.\n        type is optionally the type of string, matching a _fromString_*\n        method.  Otherwise, the _guessStringType() classmethod will be used\n        to guess a type.  If the key is encrypted, passphrase is used as\n        the decryption key.\n\n        @type data: L{bytes}\n        @param data: The key data.\n\n        @type type: L{str} or L{None}\n        @param type: A string describing the format the key data is in, or\n        L{None} to attempt detection of the type.\n\n        @type passphrase: L{bytes} or L{None}\n        @param passphrase: The passphrase the key is encrypted with, or L{None}\n        if there is no encryption.\n\n        @rtype: L{Key}\n        @return: The loaded key.\n        \"\"\"\n        if isinstance(data, unicode):\n            data = data.encode(\"utf-8\")\n        if isinstance(passphrase, unicode):\n            passphrase = passphrase.encode(\"utf-8\")\n        if type is None:\n            type = cls._guessStringType(data)\n        if type is None:\n            raise BadKeyError('cannot guess the type of %r' % (data,))\n        method = getattr(cls, '_fromString_%s' % (type.upper(),), None)\n        if method is None:\n            raise BadKeyError('no _fromString method for %s' % (type,))\n        if method.__code__.co_argcount == 2:  # No passphrase\n            if passphrase:\n                raise BadKeyError('key not encrypted')\n            return method(data)\n        else:\n            return method(data, passphrase)\n\n\n    @classmethod\n    def _fromString_BLOB(cls, blob):\n        \"\"\"\n        Return a public key object corresponding to this public key blob.\n        The format of a RSA public key blob is::\n            string 'ssh-rsa'\n            integer e\n            integer n\n\n        The format of a DSA public key blob is::\n            string 'ssh-dss'\n            integer p\n            integer q\n            integer g\n            integer y\n\n        The format of ECDSA-SHA2-* public key blob is::\n            string 'ecdsa-sha2-[identifier]'\n            integer x\n            integer y\n\n            identifier is the standard NIST curve name.\n\n        @type blob: L{bytes}\n        @param blob: The key data.\n\n        @return: A new key.\n        @rtype: L{twisted.conch.ssh.keys.Key}\n        @raises BadKeyError: if the key type (the first string) is unknown.\n        \"\"\"\n        keyType, rest = common.getNS(blob)\n        if keyType == b'ssh-rsa':\n            e, n, rest = common.getMP(rest, 2)\n            return cls(\n                rsa.RSAPublicNumbers(e, n).public_key(default_backend()))\n        elif keyType == b'ssh-dss':\n            p, q, g, y, rest = common.getMP(rest, 4)\n            return cls(\n                dsa.DSAPublicNumbers(\n                    y=y,\n                    parameter_numbers=dsa.DSAParameterNumbers(\n                        p=p,\n                        q=q,\n                        g=g\n                    )\n                ).public_key(default_backend())\n            )\n        elif keyType in _curveTable:\n            return cls(\n                ec.EllipticCurvePublicKey.from_encoded_point(\n                    _curveTable[keyType], common.getNS(rest, 2)[1]\n                )\n            )\n        else:\n            raise BadKeyError('unknown blob type: %s' % (keyType,))\n\n\n    @classmethod\n    def _fromString_PRIVATE_BLOB(cls, blob):\n        \"\"\"\n        Return a private key object corresponding to this private key blob.\n        The blob formats are as follows:\n\n        RSA keys::\n            string 'ssh-rsa'\n            integer n\n            integer e\n            integer d\n            integer u\n            integer p\n            integer q\n\n        DSA keys::\n            string 'ssh-dss'\n            integer p\n            integer q\n            integer g\n            integer y\n            integer x\n\n        EC keys::\n            string 'ecdsa-sha2-[identifier]'\n            string identifier\n            string q\n            integer privateValue\n\n            identifier is the standard NIST curve name.\n\n\n        @type blob: L{bytes}\n        @param blob: The key data.\n\n        @return: A new key.\n        @rtype: L{twisted.conch.ssh.keys.Key}\n        @raises BadKeyError: if\n            * the key type (the first string) is unknown\n            * the curve name of an ECDSA key does not match the key type\n        \"\"\"\n        keyType, rest = common.getNS(blob)\n\n        if keyType == b'ssh-rsa':\n            n, e, d, u, p, q, rest = common.getMP(rest, 6)\n            return cls._fromRSAComponents(n=n, e=e, d=d, p=p, q=q)\n        elif keyType == b'ssh-dss':\n            p, q, g, y, x, rest = common.getMP(rest, 5)\n            return cls._fromDSAComponents(y=y, g=g, p=p, q=q, x=x)\n        elif keyType in _curveTable:\n            curve = _curveTable[keyType]\n            curveName, q, rest = common.getNS(rest, 2)\n            if curveName != _secToNist[curve.name.encode('ascii')]:\n                raise BadKeyError('ECDSA curve name %r does not match key '\n                                  'type %r' % (curveName, keyType))\n            privateValue, rest = common.getMP(rest)\n            return cls._fromECEncodedPoint(\n                encodedPoint=q, curve=keyType, privateValue=privateValue)\n        else:\n            raise BadKeyError('unknown blob type: %s' % (keyType,))\n\n\n    @classmethod\n    def _fromString_PUBLIC_OPENSSH(cls, data):\n        \"\"\"\n        Return a public key object corresponding to this OpenSSH public key\n        string.  The format of an OpenSSH public key string is::\n            <key type> <base64-encoded public key blob>\n\n        @type data: L{bytes}\n        @param data: The key data.\n\n        @return: A new key.\n        @rtype: L{twisted.conch.ssh.keys.Key}\n        @raises BadKeyError: if the blob type is unknown.\n        \"\"\"\n        # ECDSA keys don't need base64 decoding which is required\n        # for RSA or DSA key.\n        if data.startswith(b'ecdsa-sha2'):\n            return cls(load_ssh_public_key(data, default_backend()))\n        blob = decodebytes(data.split()[1])\n        return cls._fromString_BLOB(blob)\n\n\n    @classmethod\n    def _fromPrivateOpenSSH_v1(cls, data, passphrase):\n        \"\"\"\n        Return a private key object corresponding to this OpenSSH private key\n        string, in the \"openssh-key-v1\" format introduced in OpenSSH 6.5.\n\n        The format of an openssh-key-v1 private key string is::\n            -----BEGIN OPENSSH PRIVATE KEY-----\n            <base64-encoded SSH protocol string>\n            -----END OPENSSH PRIVATE KEY-----\n\n        The SSH protocol string is as described in\n        U{PROTOCOL.key<https://cvsweb.openbsd.org/cgi-bin/cvsweb/src/usr.bin/ssh/PROTOCOL.key>}.\n\n        @type data: L{bytes}\n        @param data: The key data.\n\n        @type passphrase: L{bytes} or L{None}\n        @param passphrase: The passphrase the key is encrypted with, or L{None}\n        if it is not encrypted.\n\n        @return: A new key.\n        @rtype: L{twisted.conch.ssh.keys.Key}\n        @raises BadKeyError: if\n            * a passphrase is provided for an unencrypted key\n            * the SSH protocol encoding is incorrect\n        @raises EncryptedKeyError: if\n            * a passphrase is not provided for an encrypted key\n        \"\"\"\n        lines = data.strip().splitlines()\n        keyList = decodebytes(b''.join(lines[1:-1]))\n        if not keyList.startswith(b'openssh-key-v1\\0'):\n            raise BadKeyError('unknown OpenSSH private key format')\n        keyList = keyList[len(b'openssh-key-v1\\0'):]\n        cipher, kdf, kdfOptions, rest = common.getNS(keyList, 3)\n        n = struct.unpack('!L', rest[:4])[0]\n        if n != 1:\n            raise BadKeyError('only OpenSSH private key files containing '\n                              'a single key are supported')\n        # Ignore public key\n        _, encPrivKeyList, _ = common.getNS(rest[4:], 2)\n        if cipher != b'none':\n            if not passphrase:\n                raise EncryptedKeyError('Passphrase must be provided '\n                                        'for an encrypted key')\n            # Determine cipher\n            if cipher in (b'aes128-ctr', b'aes192-ctr', b'aes256-ctr'):\n                algorithmClass = algorithms.AES\n                blockSize = 16\n                keySize = int(cipher[3:6]) // 8\n                ivSize = blockSize\n            else:\n                raise BadKeyError('unknown encryption type %r' % (cipher,))\n            if kdf == b'bcrypt':\n                salt, rest = common.getNS(kdfOptions)\n                rounds = struct.unpack('!L', rest[:4])[0]\n                decKey = bcrypt.kdf(\n                    passphrase, salt, keySize + ivSize, rounds,\n                    # We can only use the number of rounds that OpenSSH used.\n                    ignore_few_rounds=True)\n            else:\n                raise BadKeyError('unknown KDF type %r' % (kdf,))\n            if (len(encPrivKeyList) % blockSize) != 0:\n                raise BadKeyError('bad padding')\n            decryptor = Cipher(\n                algorithmClass(decKey[:keySize]),\n                modes.CTR(decKey[keySize:keySize + ivSize]),\n                backend=default_backend()\n            ).decryptor()\n            privKeyList = (\n                decryptor.update(encPrivKeyList) + decryptor.finalize())\n        else:\n            if kdf != b'none':\n                raise BadKeyError('private key specifies KDF %r but no '\n                                  'cipher' % (kdf,))\n            privKeyList = encPrivKeyList\n        check1 = struct.unpack('!L', privKeyList[:4])[0]\n        check2 = struct.unpack('!L', privKeyList[4:8])[0]\n        if check1 != check2:\n            raise BadKeyError('check values do not match: %d != %d' %\n                              (check1, check2))\n        return cls._fromString_PRIVATE_BLOB(privKeyList[8:])\n\n\n    @classmethod\n    def _fromPrivateOpenSSH_PEM(cls, data, passphrase):\n        \"\"\"\n        Return a private key object corresponding to this OpenSSH private key\n        string, in the old PEM-based format.\n\n        The format of a PEM-based OpenSSH private key string is::\n            -----BEGIN <key type> PRIVATE KEY-----\n            [Proc-Type: 4,ENCRYPTED\n            DEK-Info: DES-EDE3-CBC,<initialization value>]\n            <base64-encoded ASN.1 structure>\n            ------END <key type> PRIVATE KEY------\n\n        The ASN.1 structure of a RSA key is::\n            (0, n, e, d, p, q)\n\n        The ASN.1 structure of a DSA key is::\n            (0, p, q, g, y, x)\n\n        The ASN.1 structure of a ECDSA key is::\n            (ECParameters, OID, NULL)\n\n        @type data: L{bytes}\n        @param data: The key data.\n\n        @type passphrase: L{bytes} or L{None}\n        @param passphrase: The passphrase the key is encrypted with, or L{None}\n        if it is not encrypted.\n\n        @return: A new key.\n        @rtype: L{twisted.conch.ssh.keys.Key}\n        @raises BadKeyError: if\n            * a passphrase is provided for an unencrypted key\n            * the ASN.1 encoding is incorrect\n        @raises EncryptedKeyError: if\n            * a passphrase is not provided for an encrypted key\n        \"\"\"\n        lines = data.strip().splitlines()\n        kind = lines[0][11:-17]\n        if lines[1].startswith(b'Proc-Type: 4,ENCRYPTED'):\n            if not passphrase:\n                raise EncryptedKeyError('Passphrase must be provided '\n                                        'for an encrypted key')\n\n            # Determine cipher and initialization vector\n            try:\n                _, cipherIVInfo = lines[2].split(b' ', 1)\n                cipher, ivdata = cipherIVInfo.rstrip().split(b',', 1)\n            except ValueError:\n                raise BadKeyError('invalid DEK-info %r' % (lines[2],))\n\n            if cipher in (b'AES-128-CBC', b'AES-256-CBC'):\n                algorithmClass = algorithms.AES\n                keySize = int(cipher.split(b'-')[1]) // 8\n                if len(ivdata) != 32:\n                    raise BadKeyError('AES encrypted key with a bad IV')\n            elif cipher == b'DES-EDE3-CBC':\n                algorithmClass = algorithms.TripleDES\n                keySize = 24\n                if len(ivdata) != 16:\n                    raise BadKeyError('DES encrypted key with a bad IV')\n            else:\n                raise BadKeyError('unknown encryption type %r' % (cipher,))\n\n            # Extract keyData for decoding\n            iv = bytes(bytearray([int(ivdata[i:i + 2], 16)\n                                  for i in range(0, len(ivdata), 2)]))\n            ba = md5(passphrase + iv[:8]).digest()\n            bb = md5(ba + passphrase + iv[:8]).digest()\n            decKey = (ba + bb)[:keySize]\n            b64Data = decodebytes(b''.join(lines[3:-1]))\n\n            decryptor = Cipher(\n                algorithmClass(decKey),\n                modes.CBC(iv),\n                backend=default_backend()\n            ).decryptor()\n            keyData = decryptor.update(b64Data) + decryptor.finalize()\n\n            removeLen = ord(keyData[-1:])\n            keyData = keyData[:-removeLen]\n        else:\n            b64Data = b''.join(lines[1:-1])\n            keyData = decodebytes(b64Data)\n\n        try:\n            decodedKey = berDecoder.decode(keyData)[0]\n        except PyAsn1Error as e:\n            raise BadKeyError(\n                'Failed to decode key (Bad Passphrase?): %s' % (e,))\n\n        if kind == b'EC':\n            return cls(\n                load_pem_private_key(data, passphrase, default_backend()))\n\n        if kind == b'RSA':\n            if len(decodedKey) == 2:  # Alternate RSA key\n                decodedKey = decodedKey[0]\n            if len(decodedKey) < 6:\n                raise BadKeyError('RSA key failed to decode properly')\n\n            n, e, d, p, q, dmp1, dmq1, iqmp = [\n                long(value) for value in decodedKey[1:9]\n                ]\n            return cls(\n                rsa.RSAPrivateNumbers(\n                    p=p,\n                    q=q,\n                    d=d,\n                    dmp1=dmp1,\n                    dmq1=dmq1,\n                    iqmp=iqmp,\n                    public_numbers=rsa.RSAPublicNumbers(e=e, n=n),\n                ).private_key(default_backend())\n            )\n        elif kind == b'DSA':\n            p, q, g, y, x = [long(value) for value in decodedKey[1: 6]]\n            if len(decodedKey) < 6:\n                raise BadKeyError('DSA key failed to decode properly')\n            return cls(\n                dsa.DSAPrivateNumbers(\n                    x=x,\n                    public_numbers=dsa.DSAPublicNumbers(\n                        y=y,\n                        parameter_numbers=dsa.DSAParameterNumbers(\n                            p=p,\n                            q=q,\n                            g=g\n                        )\n                    )\n                ).private_key(backend=default_backend())\n            )\n        else:\n            raise BadKeyError(\"unknown key type %s\" % (kind,))\n\n\n    @classmethod\n    def _fromString_PRIVATE_OPENSSH(cls, data, passphrase):\n        \"\"\"\n        Return a private key object corresponding to this OpenSSH private key\n        string.  If the key is encrypted, passphrase MUST be provided.\n        Providing a passphrase for an unencrypted key is an error.\n\n        @type data: L{bytes}\n        @param data: The key data.\n\n        @type passphrase: L{bytes} or L{None}\n        @param passphrase: The passphrase the key is encrypted with, or L{None}\n        if it is not encrypted.\n\n        @return: A new key.\n        @rtype: L{twisted.conch.ssh.keys.Key}\n        @raises BadKeyError: if\n            * a passphrase is provided for an unencrypted key\n            * the encoding is incorrect\n        @raises EncryptedKeyError: if\n            * a passphrase is not provided for an encrypted key\n        \"\"\"\n        if data.strip().splitlines()[0][11:-17] == b'OPENSSH':\n            # New-format (openssh-key-v1) key\n            return cls._fromPrivateOpenSSH_v1(data, passphrase)\n        else:\n            # Old-format (PEM) key\n            return cls._fromPrivateOpenSSH_PEM(data, passphrase)\n\n    @classmethod\n    def _fromString_PUBLIC_LSH(cls, data):\n        \"\"\"\n        Return a public key corresponding to this LSH public key string.\n        The LSH public key string format is::\n            <s-expression: ('public-key', (<key type>, (<name, <value>)+))>\n\n        The names for a RSA (key type 'rsa-pkcs1-sha1') key are: n, e.\n        The names for a DSA (key type 'dsa') key are: y, g, p, q.\n\n        @type data: L{bytes}\n        @param data: The key data.\n\n        @return: A new key.\n        @rtype: L{twisted.conch.ssh.keys.Key}\n        @raises BadKeyError: if the key type is unknown\n        \"\"\"\n        sexp = sexpy.parse(decodebytes(data[1:-1]))\n        assert sexp[0] == b'public-key'\n        kd = {}\n        for name, data in sexp[1][1:]:\n            kd[name] = common.getMP(common.NS(data))[0]\n        if sexp[1][0] == b'dsa':\n            return cls._fromDSAComponents(\n                y=kd[b'y'], g=kd[b'g'], p=kd[b'p'], q=kd[b'q'])\n\n        elif sexp[1][0] == b'rsa-pkcs1-sha1':\n            return cls._fromRSAComponents(n=kd[b'n'], e=kd[b'e'])\n        else:\n            raise BadKeyError('unknown lsh key type %s' % (sexp[1][0],))\n\n    @classmethod\n    def _fromString_PRIVATE_LSH(cls, data):\n        \"\"\"\n        Return a private key corresponding to this LSH private key string.\n        The LSH private key string format is::\n            <s-expression: ('private-key', (<key type>, (<name>, <value>)+))>\n\n        The names for a RSA (key type 'rsa-pkcs1-sha1') key are: n, e, d, p, q.\n        The names for a DSA (key type 'dsa') key are: y, g, p, q, x.\n\n        @type data: L{bytes}\n        @param data: The key data.\n\n        @return: A new key.\n        @rtype: L{twisted.conch.ssh.keys.Key}\n        @raises BadKeyError: if the key type is unknown\n        \"\"\"\n        sexp = sexpy.parse(data)\n        assert sexp[0] == b'private-key'\n        kd = {}\n        for name, data in sexp[1][1:]:\n            kd[name] = common.getMP(common.NS(data))[0]\n        if sexp[1][0] == b'dsa':\n            assert len(kd) == 5, len(kd)\n            return cls._fromDSAComponents(\n                y=kd[b'y'], g=kd[b'g'], p=kd[b'p'], q=kd[b'q'], x=kd[b'x'])\n        elif sexp[1][0] == b'rsa-pkcs1':\n            assert len(kd) == 8, len(kd)\n            if kd[b'p'] > kd[b'q']:  # Make p smaller than q\n                kd[b'p'], kd[b'q'] = kd[b'q'], kd[b'p']\n            return cls._fromRSAComponents(\n                n=kd[b'n'], e=kd[b'e'], d=kd[b'd'], p=kd[b'p'], q=kd[b'q'])\n\n        else:\n            raise BadKeyError('unknown lsh key type %s' % (sexp[1][0],))\n\n    @classmethod\n    def _fromString_AGENTV3(cls, data):\n        \"\"\"\n        Return a private key object corresponsing to the Secure Shell Key\n        Agent v3 format.\n\n        The SSH Key Agent v3 format for a RSA key is::\n            string 'ssh-rsa'\n            integer e\n            integer d\n            integer n\n            integer u\n            integer p\n            integer q\n\n        The SSH Key Agent v3 format for a DSA key is::\n            string 'ssh-dss'\n            integer p\n            integer q\n            integer g\n            integer y\n            integer x\n\n        @type data: L{bytes}\n        @param data: The key data.\n\n        @return: A new key.\n        @rtype: L{twisted.conch.ssh.keys.Key}\n        @raises BadKeyError: if the key type (the first string) is unknown\n        \"\"\"\n        keyType, data = common.getNS(data)\n        if keyType == b'ssh-dss':\n            p, data = common.getMP(data)\n            q, data = common.getMP(data)\n            g, data = common.getMP(data)\n            y, data = common.getMP(data)\n            x, data = common.getMP(data)\n            return cls._fromDSAComponents(y=y, g=g, p=p, q=q, x=x)\n        elif keyType == b'ssh-rsa':\n            e, data = common.getMP(data)\n            d, data = common.getMP(data)\n            n, data = common.getMP(data)\n            u, data = common.getMP(data)\n            p, data = common.getMP(data)\n            q, data = common.getMP(data)\n            return cls._fromRSAComponents(n=n, e=e, d=d, p=p, q=q, u=u)\n        else:\n            raise BadKeyError(\"unknown key type %s\" % (keyType,))\n\n    @classmethod\n    def _guessStringType(cls, data):\n        \"\"\"\n        Guess the type of key in data.  The types map to _fromString_*\n        methods.\n\n        @type data: L{bytes}\n        @param data: The key data.\n        \"\"\"\n        if data.startswith(b'ssh-') or data.startswith(b'ecdsa-sha2-'):\n            return 'public_openssh'\n        elif data.startswith(b'-----BEGIN'):\n            return 'private_openssh'\n        elif data.startswith(b'{'):\n            return 'public_lsh'\n        elif data.startswith(b'('):\n            return 'private_lsh'\n        elif data.startswith(b'\\x00\\x00\\x00\\x07ssh-') or data.startswith(b'\\x00\\x00\\x00\\x13ecdsa-'):\n            ignored, rest = common.getNS(data)\n            count = 0\n            while rest:\n                count += 1\n                ignored, rest = common.getMP(rest)\n            if count > 4:\n                return 'agentv3'\n            else:\n                return 'blob'\n\n    @classmethod\n    def _fromRSAComponents(cls, n, e, d=None, p=None, q=None, u=None):\n        \"\"\"\n        Build a key from RSA numerical components.\n\n        @type n: L{int}\n        @param n: The 'n' RSA variable.\n\n        @type e: L{int}\n        @param e: The 'e' RSA variable.\n\n        @type d: L{int} or L{None}\n        @param d: The 'd' RSA variable (optional for a public key).\n\n        @type p: L{int} or L{None}\n        @param p: The 'p' RSA variable (optional for a public key).\n\n        @type q: L{int} or L{None}\n        @param q: The 'q' RSA variable (optional for a public key).\n\n        @type u: L{int} or L{None}\n        @param u: The 'u' RSA variable. Ignored, as its value is determined by\n        p and q.\n\n        @rtype: L{Key}\n        @return: An RSA key constructed from the values as given.\n        \"\"\"\n        publicNumbers = rsa.RSAPublicNumbers(e=e, n=n)\n        if d is None:\n            # We have public components.\n            keyObject = publicNumbers.public_key(default_backend())\n        else:\n            privateNumbers = rsa.RSAPrivateNumbers(\n                p=p,\n                q=q,\n                d=d,\n                dmp1=rsa.rsa_crt_dmp1(d, p),\n                dmq1=rsa.rsa_crt_dmq1(d, q),\n                iqmp=rsa.rsa_crt_iqmp(p, q),\n                public_numbers=publicNumbers,\n            )\n            keyObject = privateNumbers.private_key(default_backend())\n\n        return cls(keyObject)\n\n    @classmethod\n    def _fromDSAComponents(cls, y, p, q, g, x=None):\n        \"\"\"\n        Build a key from DSA numerical components.\n\n        @type y: L{int}\n        @param y: The 'y' DSA variable.\n\n        @type p: L{int}\n        @param p: The 'p' DSA variable.\n\n        @type q: L{int}\n        @param q: The 'q' DSA variable.\n\n        @type g: L{int}\n        @param g: The 'g' DSA variable.\n\n        @type x: L{int} or L{None}\n        @param x: The 'x' DSA variable (optional for a public key)\n\n        @rtype: L{Key}\n        @return: A DSA key constructed from the values as given.\n        \"\"\"\n        publicNumbers = dsa.DSAPublicNumbers(\n            y=y, parameter_numbers=dsa.DSAParameterNumbers(p=p, q=q, g=g))\n        if x is None:\n            # We have public components.\n            keyObject = publicNumbers.public_key(default_backend())\n        else:\n            privateNumbers = dsa.DSAPrivateNumbers(\n                x=x, public_numbers=publicNumbers)\n            keyObject = privateNumbers.private_key(default_backend())\n\n        return cls(keyObject)\n\n    @classmethod\n    def _fromECComponents(cls, x, y, curve, privateValue=None):\n        \"\"\"\n        Build a key from EC components.\n\n        @param x: The affine x component of the public point used for verifying.\n        @type x: L{int}\n\n        @param y: The affine y component of the public point used for verifying.\n        @type y: L{int}\n\n        @param curve: NIST name of elliptic curve.\n        @type curve: L{bytes}\n\n        @param privateValue: The private value.\n        @type privateValue: L{int}\n        \"\"\"\n\n        publicNumbers = ec.EllipticCurvePublicNumbers(\n            x=x, y=y, curve=_curveTable[curve])\n        if privateValue is None:\n            # We have public components.\n            keyObject = publicNumbers.public_key(default_backend())\n        else:\n            privateNumbers = ec.EllipticCurvePrivateNumbers(\n                private_value=privateValue, public_numbers=publicNumbers)\n            keyObject = privateNumbers.private_key(default_backend())\n\n        return cls(keyObject)\n\n    @classmethod\n    def _fromECEncodedPoint(cls, encodedPoint, curve, privateValue=None):\n        \"\"\"\n        Build a key from an EC encoded point.\n\n        @param encodedPoint: The public point encoded as in SEC 1 v2.0\n        section 2.3.3.\n        @type encodedPoint: L{bytes}\n\n        @param curve: NIST name of elliptic curve.\n        @type curve: L{bytes}\n\n        @param privateValue: The private value.\n        @type privateValue: L{int}\n        \"\"\"\n\n        if privateValue is None:\n            # We have public components.\n            keyObject = ec.EllipticCurvePublicKey.from_encoded_point(\n                _curveTable[curve], encodedPoint\n            )\n        else:\n            keyObject = ec.derive_private_key(\n                privateValue, _curveTable[curve], default_backend()\n            )\n\n        return cls(keyObject)\n\n    def __init__(self, keyObject):\n        \"\"\"\n        Initialize with a private or public\n        C{cryptography.hazmat.primitives.asymmetric} key.\n\n        @param keyObject: Low level key.\n        @type keyObject: C{cryptography.hazmat.primitives.asymmetric} key.\n        \"\"\"\n        self._keyObject = keyObject\n\n    def __eq__(self, other):\n        \"\"\"\n        Return True if other represents an object with the same key.\n        \"\"\"\n        if type(self) == type(other):\n            return self.type() == other.type() and self.data() == other.data()\n        else:\n            return NotImplemented\n\n    def __ne__(self, other):\n        \"\"\"\n        Return True if other represents anything other than this key.\n        \"\"\"\n        result = self.__eq__(other)\n        if result == NotImplemented:\n            return result\n        return not result\n\n    def __repr__(self):\n        \"\"\"\n        Return a pretty representation of this object.\n        \"\"\"\n        if self.type() == 'EC':\n            data = self.data()\n            name = data['curve'].decode('utf-8')\n\n            if self.isPublic():\n                out = '<Elliptic Curve Public Key (%s bits)' % (name[-3:],)\n            else:\n                out = '<Elliptic Curve Private Key (%s bits)' % (name[-3:],)\n\n            for k, v in sorted(data.items()):\n                if _PY3 and k == 'curve':\n                    out += \"\\ncurve:\\n\\t%s\" % (name,)\n                else:\n                    out += \"\\n%s:\\n\\t%s\" % (k, v)\n\n            return out + \">\\n\"\n        else:\n            lines = [\n                '<%s %s (%s bits)' % (\n                    nativeString(self.type()),\n                    self.isPublic() and 'Public Key' or 'Private Key',\n                    self._keyObject.key_size)]\n            for k, v in sorted(self.data().items()):\n                lines.append('attr %s:' % (k,))\n                by = common.MP(v)[4:]\n                while by:\n                    m = by[:15]\n                    by = by[15:]\n                    o = ''\n                    for c in iterbytes(m):\n                        o = o + '%02x:' % (ord(c),)\n                    if len(m) < 15:\n                        o = o[:-1]\n                    lines.append('\\t' + o)\n            lines[-1] = lines[-1] + '>'\n            return '\\n'.join(lines)\n\n    def isPublic(self):\n        \"\"\"\n        Check if this instance is a public key.\n\n        @return: C{True} if this is a public key.\n        \"\"\"\n        return isinstance(\n            self._keyObject,\n            (rsa.RSAPublicKey, dsa.DSAPublicKey, ec.EllipticCurvePublicKey))\n\n    def public(self):\n        \"\"\"\n        Returns a version of this key containing only the public key data.\n        If this is a public key, this may or may not be the same object\n        as self.\n\n        @rtype: L{Key}\n        @return: A public key.\n        \"\"\"\n        if self.isPublic():\n            return self\n        else:\n            return Key(self._keyObject.public_key())\n\n    def fingerprint(self, format=FingerprintFormats.MD5_HEX):\n        \"\"\"\n        The fingerprint of a public key consists of the output of the\n        message-digest algorithm in the specified format.\n        Supported formats include L{FingerprintFormats.MD5_HEX} and\n        L{FingerprintFormats.SHA256_BASE64}\n\n        The input to the algorithm is the public key data as specified by [RFC4253].\n\n        The output of sha256[RFC4634] algorithm is presented to the\n        user in the form of base64 encoded sha256 hashes.\n        Example: C{US5jTUa0kgX5ZxdqaGF0yGRu8EgKXHNmoT8jHKo1StM=}\n\n        The output of the MD5[RFC1321](default) algorithm is presented to the user as\n        a sequence of 16 octets printed as hexadecimal with lowercase letters\n        and separated by colons.\n        Example: C{c1:b1:30:29:d7:b8:de:6c:97:77:10:d7:46:41:63:87}\n\n        @param format: Format for fingerprint generation. Consists\n            hash function and representation format.\n            Default is L{FingerprintFormats.MD5_HEX}\n\n        @since: 8.2\n\n        @return: the user presentation of this L{Key}'s fingerprint, as a\n        string.\n\n        @rtype: L{str}\n        \"\"\"\n        if format is FingerprintFormats.SHA256_BASE64:\n            return nativeString(base64.b64encode(\n                sha256(self.blob()).digest()))\n        elif format is FingerprintFormats.MD5_HEX:\n            return nativeString(\n                b':'.join([binascii.hexlify(x)\n                           for x in iterbytes(md5(self.blob()).digest())]))\n        else:\n            raise BadFingerPrintFormat(\n                'Unsupported fingerprint format: %s' % (format,))\n\n    def type(self):\n        \"\"\"\n        Return the type of the object we wrap.  Currently this can only be\n        'RSA', 'DSA', or 'EC'.\n\n        @rtype: L{str}\n        @raises RuntimeError: If the object type is unknown.\n        \"\"\"\n        if isinstance(\n                self._keyObject, (rsa.RSAPublicKey, rsa.RSAPrivateKey)):\n            return 'RSA'\n        elif isinstance(\n                self._keyObject, (dsa.DSAPublicKey, dsa.DSAPrivateKey)):\n            return 'DSA'\n        elif isinstance(\n                self._keyObject, (ec.EllipticCurvePublicKey, ec.EllipticCurvePrivateKey)):\n            return 'EC'\n        else:\n            raise RuntimeError(\n                'unknown type of object: %r' % (self._keyObject,))\n\n    def sshType(self):\n        \"\"\"\n        Get the type of the object we wrap as defined in the SSH protocol,\n        defined in RFC 4253, Section 6.6. Currently this can only be b'ssh-rsa',\n        b'ssh-dss' or b'ecdsa-sha2-[identifier]'.\n\n        identifier is the standard NIST curve name\n\n        @return: The key type format.\n        @rtype: L{bytes}\n        \"\"\"\n        if self.type() == 'EC':\n            return b'ecdsa-sha2-' + _secToNist[self._keyObject.curve.name.encode('ascii')]\n        else:\n            return {'RSA': b'ssh-rsa', 'DSA': b'ssh-dss'}[self.type()]\n\n    def size(self):\n        \"\"\"\n        Return the size of the object we wrap.\n\n        @return: The size of the key.\n        @rtype: L{int}\n        \"\"\"\n        if self._keyObject is None:\n            return 0\n        elif self.type() == 'EC':\n            return self._keyObject.curve.key_size\n        return self._keyObject.key_size\n\n    def data(self):\n        \"\"\"\n        Return the values of the public key as a dictionary.\n\n        @rtype: L{dict}\n        \"\"\"\n        if isinstance(self._keyObject, rsa.RSAPublicKey):\n            numbers = self._keyObject.public_numbers()\n            return {\n                \"n\": numbers.n,\n                \"e\": numbers.e,\n            }\n        elif isinstance(self._keyObject, rsa.RSAPrivateKey):\n            numbers = self._keyObject.private_numbers()\n            return {\n                \"n\": numbers.public_numbers.n,\n                \"e\": numbers.public_numbers.e,\n                \"d\": numbers.d,\n                \"p\": numbers.p,\n                \"q\": numbers.q,\n                # Use a trick: iqmp is q^-1 % p, u is p^-1 % q\n                \"u\": rsa.rsa_crt_iqmp(numbers.q, numbers.p),\n            }\n        elif isinstance(self._keyObject, dsa.DSAPublicKey):\n            numbers = self._keyObject.public_numbers()\n            return {\n                \"y\": numbers.y,\n                \"g\": numbers.parameter_numbers.g,\n                \"p\": numbers.parameter_numbers.p,\n                \"q\": numbers.parameter_numbers.q,\n            }\n        elif isinstance(self._keyObject, dsa.DSAPrivateKey):\n            numbers = self._keyObject.private_numbers()\n            return {\n                \"x\": numbers.x,\n                \"y\": numbers.public_numbers.y,\n                \"g\": numbers.public_numbers.parameter_numbers.g,\n                \"p\": numbers.public_numbers.parameter_numbers.p,\n                \"q\": numbers.public_numbers.parameter_numbers.q,\n            }\n        elif isinstance(self._keyObject, ec.EllipticCurvePublicKey):\n            numbers = self._keyObject.public_numbers()\n            return {\n                \"x\": numbers.x,\n                \"y\": numbers.y,\n                \"curve\": self.sshType(),\n            }\n        elif isinstance(self._keyObject, ec.EllipticCurvePrivateKey):\n            numbers = self._keyObject.private_numbers()\n            return {\n                \"x\": numbers.public_numbers.x,\n                \"y\": numbers.public_numbers.y,\n                \"privateValue\": numbers.private_value,\n                \"curve\": self.sshType(),\n            }\n\n        else:\n            raise RuntimeError(\"Unexpected key type: %s\" % (self._keyObject,))\n\n    def blob(self):\n        \"\"\"\n        Return the public key blob for this key. The blob is the\n        over-the-wire format for public keys.\n\n        SECSH-TRANS RFC 4253 Section 6.6.\n\n        RSA keys::\n            string 'ssh-rsa'\n            integer e\n            integer n\n\n        DSA keys::\n            string 'ssh-dss'\n            integer p\n            integer q\n            integer g\n            integer y\n\n        EC keys::\n            string 'ecdsa-sha2-[identifier]'\n            integer x\n            integer y\n\n            identifier is the standard NIST curve name\n\n        @rtype: L{bytes}\n        \"\"\"\n        type = self.type()\n        data = self.data()\n        if type == 'RSA':\n            return (common.NS(b'ssh-rsa') + common.MP(data['e']) +\n                    common.MP(data['n']))\n        elif type == 'DSA':\n            return (common.NS(b'ssh-dss') + common.MP(data['p']) +\n                    common.MP(data['q']) + common.MP(data['g']) +\n                    common.MP(data['y']))\n        else: # EC\n            byteLength = (self._keyObject.curve.key_size + 7) // 8\n            return (common.NS(data['curve']) + common.NS(data[\"curve\"][-8:]) +\n                common.NS(b'\\x04' + utils.int_to_bytes(data['x'], byteLength) +\n                utils.int_to_bytes(data['y'], byteLength)))\n\n\n    def privateBlob(self):\n        \"\"\"\n        Return the private key blob for this key. The blob is the\n        over-the-wire format for private keys:\n\n        Specification in OpenSSH PROTOCOL.agent\n\n        RSA keys::\n            string 'ssh-rsa'\n            integer n\n            integer e\n            integer d\n            integer u\n            integer p\n            integer q\n\n        DSA keys::\n            string 'ssh-dss'\n            integer p\n            integer q\n            integer g\n            integer y\n            integer x\n\n        EC keys::\n            string 'ecdsa-sha2-[identifier]'\n            integer x\n            integer y\n            integer privateValue\n\n            identifier is the NIST standard curve name.\n        \"\"\"\n        type = self.type()\n        data = self.data()\n        if type == 'RSA':\n            return (common.NS(b'ssh-rsa') + common.MP(data['n']) +\n                    common.MP(data['e']) + common.MP(data['d']) +\n                    common.MP(data['u']) + common.MP(data['p']) +\n                    common.MP(data['q']))\n        elif type == 'DSA':\n            return (common.NS(b'ssh-dss') + common.MP(data['p']) +\n                    common.MP(data['q']) + common.MP(data['g']) +\n                    common.MP(data['y']) + common.MP(data['x']))\n        else: # EC\n            return (common.NS(data['curve']) + common.MP(data['x']) +\n                    common.MP(data['y']) + common.MP(data['privateValue']))\n\n    def toString(self, type, extra=None):\n        \"\"\"\n        Create a string representation of this key.  If the key is a private\n        key and you want the representation of its public key, use\n        C{key.public().toString()}.  type maps to a _toString_* method.\n\n        @param type: The type of string to emit.  Currently supported values\n            are C{'OPENSSH'}, C{'LSH'}, and C{'AGENTV3'}.\n        @type type: L{str}\n\n        @param extra: Any extra data supported by the selected format which\n            is not part of the key itself.  For public OpenSSH keys, this is\n            a comment.  For private OpenSSH keys, this is a passphrase to\n            encrypt with.\n        @type extra: L{bytes} or L{unicode} or L{None}\n\n        @rtype: L{bytes}\n        \"\"\"\n        if isinstance(extra, unicode):\n            extra = extra.encode(\"utf-8\")\n        method = getattr(self, '_toString_%s' % (type.upper(),), None)\n        if method is None:\n            raise BadKeyError('unknown key type: %s' % (type,))\n        if method.__code__.co_argcount == 2:\n            return method(extra)\n        else:\n            return method()\n\n    def _toString_OPENSSH(self, extra):\n        \"\"\"\n        Return a public or private OpenSSH string.  See\n        _fromString_PUBLIC_OPENSSH and _fromString_PRIVATE_OPENSSH for the\n        string formats.  If extra is present, it represents a comment for a\n        public key, or a passphrase for a private key.\n\n        @param extra: Comment for a public key or passphrase for a\n            private key\n        @type extra: L{bytes}\n\n        @rtype: L{bytes}\n        \"\"\"\n        data = self.data()\n        if self.isPublic():\n            if self.type() == 'EC':\n                if not extra:\n                    extra = b''\n                return (self._keyObject.public_bytes(\n                    serialization.Encoding.OpenSSH,\n                    serialization.PublicFormat.OpenSSH\n                    ) + b' ' + extra).strip()\n\n            b64Data = encodebytes(self.blob()).replace(b'\\n', b'')\n            if not extra:\n                extra = b''\n            return (self.sshType() + b' ' + b64Data + b' ' + extra).strip()\n        else:\n\n            if self.type() == 'EC':\n                # EC keys has complex ASN.1 structure hence we do this this way.\n                if not extra:\n                    # unencrypted private key\n                    encryptor = serialization.NoEncryption()\n                else:\n                    encryptor = serialization.BestAvailableEncryption(extra)\n\n                return self._keyObject.private_bytes(\n                    serialization.Encoding.PEM,\n                    serialization.PrivateFormat.TraditionalOpenSSL,\n                    encryptor)\n\n            lines = [b''.join((b'-----BEGIN ', self.type().encode('ascii'),\n                               b' PRIVATE KEY-----'))]\n            if self.type() == 'RSA':\n                p, q = data['p'], data['q']\n                objData = (0, data['n'], data['e'], data['d'], p, q,\n                           data['d'] % (p - 1), data['d'] % (q - 1),\n                           data['u'])\n            else:\n                objData = (0, data['p'], data['q'], data['g'], data['y'],\n                           data['x'])\n            asn1Sequence = univ.Sequence()\n            for index, value in izip(itertools.count(), objData):\n                asn1Sequence.setComponentByPosition(index, univ.Integer(value))\n            asn1Data = berEncoder.encode(asn1Sequence)\n            if extra:\n                iv = randbytes.secureRandom(8)\n                hexiv = ''.join(['%02X' % (ord(x),) for x in iterbytes(iv)])\n                hexiv = hexiv.encode('ascii')\n                lines.append(b'Proc-Type: 4,ENCRYPTED')\n                lines.append(b'DEK-Info: DES-EDE3-CBC,' + hexiv + b'\\n')\n                ba = md5(extra + iv).digest()\n                bb = md5(ba + extra + iv).digest()\n                encKey = (ba + bb)[:24]\n                padLen = 8 - (len(asn1Data) % 8)\n                asn1Data += (chr(padLen) * padLen).encode('ascii')\n\n                encryptor = Cipher(\n                    algorithms.TripleDES(encKey),\n                    modes.CBC(iv),\n                    backend=default_backend()\n                ).encryptor()\n\n                asn1Data = encryptor.update(asn1Data) + encryptor.finalize()\n\n            b64Data = encodebytes(asn1Data).replace(b'\\n', b'')\n            lines += [b64Data[i:i + 64] for i in range(0, len(b64Data), 64)]\n            lines.append(b''.join((b'-----END ', self.type().encode('ascii'),\n                                   b' PRIVATE KEY-----')))\n            return b'\\n'.join(lines)\n\n    def _toString_LSH(self):\n        \"\"\"\n        Return a public or private LSH key.  See _fromString_PUBLIC_LSH and\n        _fromString_PRIVATE_LSH for the key formats.\n\n        @rtype: L{bytes}\n        \"\"\"\n        data = self.data()\n        type = self.type()\n        if self.isPublic():\n            if type == 'RSA':\n                keyData = sexpy.pack([[b'public-key',\n                                       [b'rsa-pkcs1-sha1',\n                                        [b'n', common.MP(data['n'])[4:]],\n                                        [b'e', common.MP(data['e'])[4:]]]]])\n            elif type == 'DSA':\n                keyData = sexpy.pack([[b'public-key',\n                                       [b'dsa',\n                                        [b'p', common.MP(data['p'])[4:]],\n                                        [b'q', common.MP(data['q'])[4:]],\n                                        [b'g', common.MP(data['g'])[4:]],\n                                        [b'y', common.MP(data['y'])[4:]]]]])\n            else:\n                raise BadKeyError(\"unknown key type %s\" % (type,))\n            return (b'{' + encodebytes(keyData).replace(b'\\n', b'') +\n                    b'}')\n        else:\n            if type == 'RSA':\n                p, q = data['p'], data['q']\n                return sexpy.pack([[b'private-key',\n                                    [b'rsa-pkcs1',\n                                     [b'n', common.MP(data['n'])[4:]],\n                                     [b'e', common.MP(data['e'])[4:]],\n                                     [b'd', common.MP(data['d'])[4:]],\n                                     [b'p', common.MP(q)[4:]],\n                                     [b'q', common.MP(p)[4:]],\n                                     [b'a', common.MP(\n                                         data['d'] % (q - 1))[4:]],\n                                     [b'b', common.MP(\n                                         data['d'] % (p - 1))[4:]],\n                                     [b'c', common.MP(data['u'])[4:]]]]])\n            elif type == 'DSA':\n                return sexpy.pack([[b'private-key',\n                                    [b'dsa',\n                                     [b'p', common.MP(data['p'])[4:]],\n                                     [b'q', common.MP(data['q'])[4:]],\n                                     [b'g', common.MP(data['g'])[4:]],\n                                     [b'y', common.MP(data['y'])[4:]],\n                                     [b'x', common.MP(data['x'])[4:]]]]])\n            else:\n                raise BadKeyError(\"unknown key type %s'\" % (type,))\n\n    def _toString_AGENTV3(self):\n        \"\"\"\n        Return a private Secure Shell Agent v3 key.  See\n        _fromString_AGENTV3 for the key format.\n\n        @rtype: L{bytes}\n        \"\"\"\n        data = self.data()\n        if not self.isPublic():\n            if self.type() == 'RSA':\n                values = (data['e'], data['d'], data['n'], data['u'],\n                          data['p'], data['q'])\n            elif self.type() == 'DSA':\n                values = (data['p'], data['q'], data['g'], data['y'],\n                          data['x'])\n            return common.NS(self.sshType()) + b''.join(map(common.MP, values))\n\n    def sign(self, data):\n        \"\"\"\n        Sign some data with this key.\n\n        SECSH-TRANS RFC 4253 Section 6.6.\n\n        @type data: L{bytes}\n        @param data: The data to sign.\n\n        @rtype: L{bytes}\n        @return: A signature for the given data.\n        \"\"\"\n        keyType = self.type()\n        if keyType == 'RSA':\n            sig = self._keyObject.sign(data, padding.PKCS1v15(), hashes.SHA1())\n            ret = common.NS(sig)\n\n        elif keyType == 'DSA':\n            sig = self._keyObject.sign(data, hashes.SHA1())\n            (r, s) = decode_dss_signature(sig)\n            # SSH insists that the DSS signature blob be two 160-bit integers\n            # concatenated together. The sig[0], [1] numbers from obj.sign\n            # are just numbers, and could be any length from 0 to 160 bits.\n            # Make sure they are padded out to 160 bits (20 bytes each)\n            ret = common.NS(int_to_bytes(r, 20) + int_to_bytes(s, 20))\n\n        elif keyType == 'EC':  # Pragma: no branch\n            # Hash size depends on key size\n            keySize = self.size()\n            if keySize <= 256:\n                hashSize = hashes.SHA256()\n            elif keySize <= 384:\n                hashSize = hashes.SHA384()\n            else:\n                hashSize = hashes.SHA512()\n            signature = self._keyObject.sign(data, ec.ECDSA(hashSize))\n            (r, s) = decode_dss_signature(signature)\n\n            rb = int_to_bytes(r)\n            sb = int_to_bytes(s)\n\n            # Int_to_bytes returns rb[0] as a str in python2\n            # and an as int in python3\n            if type(rb[0]) is str:\n                rcomp = ord(rb[0])\n            else:\n                rcomp = rb[0]\n\n            # If the MSB is set, prepend a null byte for correct formatting.\n            if rcomp & 0x80:\n                rb = b\"\\x00\" + rb\n\n            if type(sb[0]) is str:\n                scomp = ord(sb[0])\n            else:\n                scomp = sb[0]\n\n            if scomp & 0x80:\n                sb = b\"\\x00\" + sb\n\n            ret = common.NS(common.NS(rb) + common.NS(sb))\n        return common.NS(self.sshType()) + ret\n\n    def verify(self, signature, data):\n        \"\"\"\n        Verify a signature using this key.\n\n        @type signature: L{bytes}\n        @param signature: The signature to verify.\n\n        @type data: L{bytes}\n        @param data: The signed data.\n\n        @rtype: L{bool}\n        @return: C{True} if the signature is valid.\n        \"\"\"\n        if len(signature) == 40:\n            # DSA key with no padding\n            signatureType, signature = b'ssh-dss', common.NS(signature)\n        else:\n            signatureType, signature = common.getNS(signature)\n\n        if signatureType != self.sshType():\n            return False\n\n        keyType = self.type()\n        if keyType == 'RSA':\n            k = self._keyObject\n            if not self.isPublic():\n                k = k.public_key()\n            args = (\n                common.getNS(signature)[0],\n                data,\n                padding.PKCS1v15(),\n                hashes.SHA1(),\n            )\n        elif keyType == 'DSA':\n            concatenatedSignature = common.getNS(signature)[0]\n            r = int_from_bytes(concatenatedSignature[:20], 'big')\n            s = int_from_bytes(concatenatedSignature[20:], 'big')\n            signature = encode_dss_signature(r, s)\n            k = self._keyObject\n            if not self.isPublic():\n                k = k.public_key()\n            args = (signature, data, hashes.SHA1())\n\n        elif keyType == 'EC':  # Pragma: no branch\n            concatenatedSignature = common.getNS(signature)[0]\n            rstr, sstr, rest = common.getNS(concatenatedSignature, 2)\n            r = int_from_bytes(rstr, 'big')\n            s = int_from_bytes(sstr, 'big')\n            signature = encode_dss_signature(r, s)\n\n            k = self._keyObject\n            if not self.isPublic():\n                k = k.public_key()\n\n            keySize = self.size()\n            if keySize <= 256:  # Hash size depends on key size\n                hashSize = hashes.SHA256()\n            elif keySize <= 384:\n                hashSize = hashes.SHA384()\n            else:\n                hashSize = hashes.SHA512()\n            args = (signature, data, ec.ECDSA(hashSize))\n\n        try:\n            k.verify(*args)\n        except InvalidSignature:\n            return False\n        else:\n            return True\n\n\ndef _getPersistentRSAKey(location, keySize=4096):\n    \"\"\"\n    This function returns a persistent L{Key}.\n\n    The key is loaded from a PEM file in C{location}. If it does not exist, a\n    key with the key size of C{keySize} is generated and saved.\n\n    @param location: Where the key is stored.\n    @type location: L{twisted.python.filepath.FilePath}\n\n    @param keySize: The size of the key, if it needs to be generated.\n    @type keySize: L{int}\n\n    @returns: A persistent key.\n    @rtype: L{Key}\n    \"\"\"\n    location.parent().makedirs(ignoreExistingDirectory=True)\n\n    # If it doesn't exist, we want to generate a new key and save it\n    if not location.exists():\n        privateKey = rsa.generate_private_key(\n            public_exponent=65537,\n            key_size=keySize,\n            backend=default_backend()\n        )\n\n        pem = privateKey.private_bytes(\n            encoding=serialization.Encoding.PEM,\n            format=serialization.PrivateFormat.TraditionalOpenSSL,\n            encryption_algorithm=serialization.NoEncryption()\n        )\n\n        location.setContent(pem)\n\n    # By this point (save any hilarious race conditions) we should have a\n    # working PEM file. Load it!\n    # (Future archaeological readers: I chose not to short circuit above,\n    # because then there's two exit paths to this code!)\n    with location.open(\"rb\") as keyFile:\n        privateKey = serialization.load_pem_private_key(\n            keyFile.read(),\n            password=None,\n            backend=default_backend()\n        )\n        return Key(privateKey)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/service.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThe parent class for all the SSH services.  Currently implemented services\nare ssh-userauth and ssh-connection.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.python import log\n\nclass SSHService(log.Logger):\n    name = None # this is the ssh name for the service\n    protocolMessages = {} # these map #'s -> protocol names\n    transport = None # gets set later\n\n    def serviceStarted(self):\n        \"\"\"\n        called when the service is active on the transport.\n        \"\"\"\n\n    def serviceStopped(self):\n        \"\"\"\n        called when the service is stopped, either by the connection ending\n        or by another service being started\n        \"\"\"\n\n    def logPrefix(self):\n        return \"SSHService %r on %s\" % (self.name,\n                self.transport.transport.logPrefix())\n\n    def packetReceived(self, messageNum, packet):\n        \"\"\"\n        called when we receive a packet on the transport\n        \"\"\"\n        #print self.protocolMessages\n        if messageNum in self.protocolMessages:\n            messageType = self.protocolMessages[messageNum]\n            f = getattr(self,'ssh_%s' % messageType[4:],\n                        None)\n            if f is not None:\n                return f(packet)\n        log.msg(\"couldn't handle %r\" % messageNum)\n        log.msg(repr(packet))\n        self.transport.sendUnimplemented()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/session.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_session -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module contains the implementation of SSHSession, which (by default)\nallows access to a shell and a python interpreter over SSH.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport struct\nimport signal\nimport sys\nimport os\n\nfrom zope.interface import implementer\n\nfrom twisted.internet import interfaces, protocol\nfrom twisted.python import log\nfrom twisted.python.compat import _bytesChr as chr, networkString\nfrom twisted.conch.interfaces import ISession\nfrom twisted.conch.ssh import common, channel, connection\n\n\nclass SSHSession(channel.SSHChannel):\n\n    name = b'session'\n    def __init__(self, *args, **kw):\n        channel.SSHChannel.__init__(self, *args, **kw)\n        self.buf = b''\n        self.client = None\n        self.session = None\n\n    def request_subsystem(self, data):\n        subsystem, ignored= common.getNS(data)\n        log.msg('asking for subsystem \"%s\"' % subsystem)\n        client = self.avatar.lookupSubsystem(subsystem, data)\n        if client:\n            pp = SSHSessionProcessProtocol(self)\n            proto = wrapProcessProtocol(pp)\n            client.makeConnection(proto)\n            pp.makeConnection(wrapProtocol(client))\n            self.client = pp\n            return 1\n        else:\n            log.msg('failed to get subsystem')\n            return 0\n\n    def request_shell(self, data):\n        log.msg('getting shell')\n        if not self.session:\n            self.session = ISession(self.avatar)\n        try:\n            pp = SSHSessionProcessProtocol(self)\n            self.session.openShell(pp)\n        except:\n            log.deferr()\n            return 0\n        else:\n            self.client = pp\n            return 1\n\n    def request_exec(self, data):\n        if not self.session:\n            self.session = ISession(self.avatar)\n        f,data = common.getNS(data)\n        log.msg('executing command \"%s\"' % f)\n        try:\n            pp = SSHSessionProcessProtocol(self)\n            self.session.execCommand(pp, f)\n        except:\n            log.deferr()\n            return 0\n        else:\n            self.client = pp\n            return 1\n\n    def request_pty_req(self, data):\n        if not self.session:\n            self.session = ISession(self.avatar)\n        term, windowSize, modes = parseRequest_pty_req(data)\n        log.msg('pty request: %r %r' % (term, windowSize))\n        try:\n            self.session.getPty(term, windowSize, modes)\n        except:\n            log.err()\n            return 0\n        else:\n            return 1\n\n    def request_window_change(self, data):\n        if not self.session:\n            self.session = ISession(self.avatar)\n        winSize = parseRequest_window_change(data)\n        try:\n            self.session.windowChanged(winSize)\n        except:\n            log.msg('error changing window size')\n            log.err()\n            return 0\n        else:\n            return 1\n\n    def dataReceived(self, data):\n        if not self.client:\n            #self.conn.sendClose(self)\n            self.buf += data\n            return\n        self.client.transport.write(data)\n\n    def extReceived(self, dataType, data):\n        if dataType == connection.EXTENDED_DATA_STDERR:\n            if self.client and hasattr(self.client.transport, 'writeErr'):\n                self.client.transport.writeErr(data)\n        else:\n            log.msg('weird extended data: %s'%dataType)\n\n    def eofReceived(self):\n        if self.session:\n            self.session.eofReceived()\n        elif self.client:\n            self.conn.sendClose(self)\n\n    def closed(self):\n        if self.session:\n            self.session.closed()\n        elif self.client:\n            self.client.transport.loseConnection()\n\n    #def closeReceived(self):\n    #    self.loseConnection() # don't know what to do with this\n\n    def loseConnection(self):\n        if self.client:\n            self.client.transport.loseConnection()\n        channel.SSHChannel.loseConnection(self)\n\nclass _ProtocolWrapper(protocol.ProcessProtocol):\n    \"\"\"\n    This class wraps a L{Protocol} instance in a L{ProcessProtocol} instance.\n    \"\"\"\n    def __init__(self, proto):\n        self.proto = proto\n\n    def connectionMade(self): self.proto.connectionMade()\n\n    def outReceived(self, data): self.proto.dataReceived(data)\n\n    def processEnded(self, reason): self.proto.connectionLost(reason)\n\nclass _DummyTransport:\n\n    def __init__(self, proto):\n        self.proto = proto\n\n    def dataReceived(self, data):\n        self.proto.transport.write(data)\n\n    def write(self, data):\n        self.proto.dataReceived(data)\n\n    def writeSequence(self, seq):\n        self.write(b''.join(seq))\n\n    def loseConnection(self):\n        self.proto.connectionLost(protocol.connectionDone)\n\ndef wrapProcessProtocol(inst):\n    if isinstance(inst, protocol.Protocol):\n        return _ProtocolWrapper(inst)\n    else:\n        return inst\n\ndef wrapProtocol(proto):\n    return _DummyTransport(proto)\n\n\n\n# SUPPORTED_SIGNALS is a list of signals that every session channel is supposed\n# to accept.  See RFC 4254\nSUPPORTED_SIGNALS = [\"ABRT\", \"ALRM\", \"FPE\", \"HUP\", \"ILL\", \"INT\", \"KILL\",\n                     \"PIPE\", \"QUIT\", \"SEGV\", \"TERM\", \"USR1\", \"USR2\"]\n\n\n\n@implementer(interfaces.ITransport)\nclass SSHSessionProcessProtocol(protocol.ProcessProtocol):\n    \"\"\"I am both an L{IProcessProtocol} and an L{ITransport}.\n\n    I am a transport to the remote endpoint and a process protocol to the\n    local subsystem.\n    \"\"\"\n\n    # once initialized, a dictionary mapping signal values to strings\n    # that follow RFC 4254.\n    _signalValuesToNames = None\n\n    def __init__(self, session):\n        self.session = session\n        self.lostOutOrErrFlag = False\n\n    def connectionMade(self):\n        if self.session.buf:\n            self.transport.write(self.session.buf)\n            self.session.buf = None\n\n    def outReceived(self, data):\n        self.session.write(data)\n\n    def errReceived(self, err):\n        self.session.writeExtended(connection.EXTENDED_DATA_STDERR, err)\n\n    def outConnectionLost(self):\n        \"\"\"\n        EOF should only be sent when both STDOUT and STDERR have been closed.\n        \"\"\"\n        if self.lostOutOrErrFlag:\n            self.session.conn.sendEOF(self.session)\n        else:\n            self.lostOutOrErrFlag = True\n\n    def errConnectionLost(self):\n        \"\"\"\n        See outConnectionLost().\n        \"\"\"\n        self.outConnectionLost()\n\n    def connectionLost(self, reason = None):\n        self.session.loseConnection()\n\n\n    def _getSignalName(self, signum):\n        \"\"\"\n        Get a signal name given a signal number.\n        \"\"\"\n        if self._signalValuesToNames is None:\n            self._signalValuesToNames = {}\n            # make sure that the POSIX ones are the defaults\n            for signame in SUPPORTED_SIGNALS:\n                signame = 'SIG' + signame\n                sigvalue = getattr(signal, signame, None)\n                if sigvalue is not None:\n                    self._signalValuesToNames[sigvalue] = signame\n            for k, v in signal.__dict__.items():\n                # Check for platform specific signals, ignoring Python specific\n                # SIG_DFL and SIG_IGN\n                if k.startswith('SIG') and not k.startswith('SIG_'):\n                    if v not in self._signalValuesToNames:\n                        self._signalValuesToNames[v] = k + '@' + sys.platform\n        return self._signalValuesToNames[signum]\n\n\n    def processEnded(self, reason=None):\n        \"\"\"\n        When we are told the process ended, try to notify the other side about\n        how the process ended using the exit-signal or exit-status requests.\n        Also, close the channel.\n        \"\"\"\n        if reason is not None:\n            err = reason.value\n            if err.signal is not None:\n                signame = self._getSignalName(err.signal)\n                if (getattr(os, 'WCOREDUMP', None) is not None and\n                    os.WCOREDUMP(err.status)):\n                    log.msg('exitSignal: %s (core dumped)' % (signame,))\n                    coreDumped = 1\n                else:\n                    log.msg('exitSignal: %s' % (signame,))\n                    coreDumped = 0\n                self.session.conn.sendRequest(\n                    self.session, b'exit-signal',\n                    common.NS(networkString(signame[3:])) + chr(coreDumped) +\n                    common.NS(b'') + common.NS(b''))\n            elif err.exitCode is not None:\n                log.msg('exitCode: %r' % (err.exitCode,))\n                self.session.conn.sendRequest(self.session, b'exit-status',\n                        struct.pack('>L', err.exitCode))\n        self.session.loseConnection()\n\n\n    def getHost(self):\n        \"\"\"\n        Return the host from my session's transport.\n        \"\"\"\n        return self.session.conn.transport.getHost()\n\n\n    def getPeer(self):\n        \"\"\"\n        Return the peer from my session's transport.\n        \"\"\"\n        return self.session.conn.transport.getPeer()\n\n\n    def write(self, data):\n        self.session.write(data)\n\n\n    def writeSequence(self, seq):\n        self.session.write(b''.join(seq))\n\n\n    def loseConnection(self):\n        self.session.loseConnection()\n\n\n\nclass SSHSessionClient(protocol.Protocol):\n\n    def dataReceived(self, data):\n        if self.transport:\n            self.transport.write(data)\n\n# methods factored out to make live easier on server writers\ndef parseRequest_pty_req(data):\n    \"\"\"Parse the data from a pty-req request into usable data.\n\n    @returns: a tuple of (terminal type, (rows, cols, xpixel, ypixel), modes)\n    \"\"\"\n    term, rest = common.getNS(data)\n    cols, rows, xpixel, ypixel = struct.unpack('>4L', rest[: 16])\n    modes, ignored= common.getNS(rest[16:])\n    winSize = (rows, cols, xpixel, ypixel)\n    modes = [(ord(modes[i:i+1]), struct.unpack('>L', modes[i+1: i+5])[0])\n             for i in range(0, len(modes)-1, 5)]\n    return term, winSize, modes\n\ndef packRequest_pty_req(term, geometry, modes):\n    \"\"\"\n    Pack a pty-req request so that it is suitable for sending.\n\n    NOTE: modes must be packed before being sent here.\n\n    @type geometry: L{tuple}\n    @param geometry: A tuple of (rows, columns, xpixel, ypixel)\n    \"\"\"\n    (rows, cols, xpixel, ypixel) = geometry\n    termPacked = common.NS(term)\n    winSizePacked = struct.pack('>4L', cols, rows, xpixel, ypixel)\n    modesPacked = common.NS(modes) # depend on the client packing modes\n    return termPacked + winSizePacked + modesPacked\n\ndef parseRequest_window_change(data):\n    \"\"\"Parse the data from a window-change request into usuable data.\n\n    @returns: a tuple of (rows, cols, xpixel, ypixel)\n    \"\"\"\n    cols, rows, xpixel, ypixel = struct.unpack('>4L', data)\n    return rows, cols, xpixel, ypixel\n\ndef packRequest_window_change(geometry):\n    \"\"\"\n    Pack a window-change request so that it is suitable for sending.\n\n    @type geometry: L{tuple}\n    @param geometry: A tuple of (rows, columns, xpixel, ypixel)\n    \"\"\"\n    (rows, cols, xpixel, ypixel) = geometry\n    return struct.pack('>4L', cols, rows, xpixel, ypixel)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/sexpy.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom __future__ import absolute_import, division\n\nfrom twisted.python.compat import intToBytes\n\n\ndef parse(s):\n    s = s.strip()\n    expr = []\n    while s:\n        if s[0:1] == b'(':\n            newSexp = []\n            if expr:\n                expr[-1].append(newSexp)\n            expr.append(newSexp)\n            s = s[1:]\n            continue\n        if s[0:1] == b')':\n            aList = expr.pop()\n            s=s[1:]\n            if not expr:\n                assert not s\n                return aList\n            continue\n        i = 0\n        while s[i:i+1].isdigit(): i+=1\n        assert i\n        length = int(s[:i])\n        data = s[i+1:i+1+length]\n        expr[-1].append(data)\n        s=s[i+1+length:]\n    assert 0, \"this should not happen\"\n\ndef pack(sexp):\n    s = b\"\"\n    for o in sexp:\n        if type(o) in (type(()), type([])):\n            s+=b'('\n            s+=pack(o)\n            s+=b')'\n        else:\n            s+=intToBytes(len(o)) + b\":\" + o\n    return s\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/transport.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_transport -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThe lowest level SSH protocol.  This handles the key negotiation, the\nencryption and the compression.  The transport layer is described in\nRFC 4253.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport binascii\nimport hmac\nimport struct\nimport zlib\n\nfrom hashlib import md5, sha1, sha256, sha384, sha512\n\nfrom cryptography.exceptions import UnsupportedAlgorithm\nfrom cryptography.hazmat.backends import default_backend\nfrom cryptography.hazmat.primitives import serialization\nfrom cryptography.hazmat.primitives.ciphers import algorithms, modes, Cipher\nfrom cryptography.hazmat.primitives.asymmetric import dh, ec\n\nfrom twisted import __version__ as twisted_version\nfrom twisted.internet import protocol, defer\nfrom twisted.python import log, randbytes\nfrom twisted.python.compat import iterbytes, _bytesChr as chr, networkString\n\n# This import is needed if SHA256 hashing is used.\n# from twisted.python.compat import nativeString\n\nfrom twisted.conch.ssh import address, keys, _kex\nfrom twisted.conch.ssh.common import (\n    NS, getNS, MP, getMP, ffs\n)\n\n\n\nclass _MACParams(tuple):\n    \"\"\"\n    L{_MACParams} represents the parameters necessary to compute SSH MAC\n    (Message Authenticate Codes).\n\n    L{_MACParams} is a L{tuple} subclass to maintain compatibility with older\n    versions of the code.  The elements of a L{_MACParams} are::\n\n        0. The digest object used for the MAC\n        1. The inner pad (\"ipad\") string\n        2. The outer pad (\"opad\") string\n        3. The size of the digest produced by the digest object\n\n    L{_MACParams} is also an object lesson in why tuples are a bad type for\n    public APIs.\n\n    @ivar key: The HMAC key which will be used.\n    \"\"\"\n\n\n\nclass SSHCiphers:\n    \"\"\"\n    SSHCiphers represents all the encryption operations that need to occur\n    to encrypt and authenticate the SSH connection.\n\n    @cvar cipherMap: A dictionary mapping SSH encryption names to 3-tuples of\n        (<cryptography.hazmat.primitives.interfaces.CipherAlgorithm>,\n        <block size>, <cryptography.hazmat.primitives.interfaces.Mode>)\n    @cvar macMap: A dictionary mapping SSH MAC names to hash modules.\n\n    @ivar outCipType: the string type of the outgoing cipher.\n    @ivar inCipType: the string type of the incoming cipher.\n    @ivar outMACType: the string type of the incoming MAC.\n    @ivar inMACType: the string type of the incoming MAC.\n    @ivar encBlockSize: the block size of the outgoing cipher.\n    @ivar decBlockSize: the block size of the incoming cipher.\n    @ivar verifyDigestSize: the size of the incoming MAC.\n    @ivar outMAC: a tuple of (<hash module>, <inner key>, <outer key>,\n        <digest size>) representing the outgoing MAC.\n    @ivar inMAc: see outMAC, but for the incoming MAC.\n    \"\"\"\n\n    cipherMap = {\n        b'3des-cbc': (algorithms.TripleDES, 24, modes.CBC),\n        b'blowfish-cbc': (algorithms.Blowfish, 16, modes.CBC),\n        b'aes256-cbc': (algorithms.AES, 32, modes.CBC),\n        b'aes192-cbc': (algorithms.AES, 24, modes.CBC),\n        b'aes128-cbc': (algorithms.AES, 16, modes.CBC),\n        b'cast128-cbc': (algorithms.CAST5, 16, modes.CBC),\n        b'aes128-ctr': (algorithms.AES, 16, modes.CTR),\n        b'aes192-ctr': (algorithms.AES, 24, modes.CTR),\n        b'aes256-ctr': (algorithms.AES, 32, modes.CTR),\n        b'3des-ctr': (algorithms.TripleDES, 24, modes.CTR),\n        b'blowfish-ctr': (algorithms.Blowfish, 16, modes.CTR),\n        b'cast128-ctr': (algorithms.CAST5, 16, modes.CTR),\n        b'none': (None, 0, modes.CBC),\n    }\n    macMap = {\n        b'hmac-sha2-512': sha512,\n        b'hmac-sha2-384': sha384,\n        b'hmac-sha2-256': sha256,\n        b'hmac-sha1': sha1,\n        b'hmac-md5': md5,\n        b'none': None\n     }\n\n\n    def __init__(self, outCip, inCip, outMac, inMac):\n        self.outCipType = outCip\n        self.inCipType = inCip\n        self.outMACType = outMac\n        self.inMACType = inMac\n        self.encBlockSize = 0\n        self.decBlockSize = 0\n        self.verifyDigestSize = 0\n        self.outMAC = (None, b'', b'', 0)\n        self.inMAC = (None, b'', b'', 0)\n\n\n    def setKeys(self, outIV, outKey, inIV, inKey, outInteg, inInteg):\n        \"\"\"\n        Set up the ciphers and hashes using the given keys,\n\n        @param outIV: the outgoing initialization vector\n        @param outKey: the outgoing encryption key\n        @param inIV: the incoming initialization vector\n        @param inKey: the incoming encryption key\n        @param outInteg: the outgoing integrity key\n        @param inInteg: the incoming integrity key.\n        \"\"\"\n        o = self._getCipher(self.outCipType, outIV, outKey)\n        self.encryptor = o.encryptor()\n        self.encBlockSize = o.algorithm.block_size // 8\n        o = self._getCipher(self.inCipType, inIV, inKey)\n        self.decryptor = o.decryptor()\n        self.decBlockSize = o.algorithm.block_size // 8\n        self.outMAC = self._getMAC(self.outMACType, outInteg)\n        self.inMAC = self._getMAC(self.inMACType, inInteg)\n        if self.inMAC:\n            self.verifyDigestSize = self.inMAC[3]\n\n\n    def _getCipher(self, cip, iv, key):\n        \"\"\"\n        Creates an initialized cipher object.\n\n        @param cip: the name of the cipher, maps into cipherMap\n        @param iv: the initialzation vector\n        @param key: the encryption key\n\n        @return: the cipher object.\n        \"\"\"\n        algorithmClass, keySize, modeClass = self.cipherMap[cip]\n        if algorithmClass is None:\n            return _DummyCipher()\n\n        return Cipher(\n            algorithmClass(key[:keySize]),\n            modeClass(iv[:algorithmClass.block_size // 8]),\n            backend=default_backend(),\n        )\n\n\n    def _getMAC(self, mac, key):\n        \"\"\"\n        Gets a 4-tuple representing the message authentication code.\n        (<hash module>, <inner hash value>, <outer hash value>,\n        <digest size>)\n\n        @type mac: L{bytes}\n        @param mac: a key mapping into macMap\n\n        @type key: L{bytes}\n        @param key: the MAC key.\n\n        @rtype: L{bytes}\n        @return: The MAC components.\n        \"\"\"\n        mod = self.macMap[mac]\n        if not mod:\n            return (None, b'', b'', 0)\n\n        # With stdlib we can only get attributes fron an instantiated object.\n        hashObject = mod()\n        digestSize = hashObject.digest_size\n        blockSize = hashObject.block_size\n\n        # Truncation here appears to contravene RFC 2104, section 2.  However,\n        # implementing the hashing behavior prescribed by the RFC breaks\n        # interoperability with OpenSSH (at least version 5.5p1).\n        key = key[:digestSize] + (b'\\x00' * (blockSize - digestSize))\n        i = key.translate(hmac.trans_36)\n        o = key.translate(hmac.trans_5C)\n        result = _MACParams((mod, i, o, digestSize))\n        result.key = key\n        return result\n\n\n    def encrypt(self, blocks):\n        \"\"\"\n        Encrypt some data.\n\n        @type blocks: L{bytes}\n        @param blocks: The data to encrypt.\n\n        @rtype: L{bytes}\n        @return: The encrypted data.\n        \"\"\"\n        return self.encryptor.update(blocks)\n\n\n    def decrypt(self, blocks):\n        \"\"\"\n        Decrypt some data.\n\n        @type blocks: L{bytes}\n        @param blocks: The data to decrypt.\n\n        @rtype: L{bytes}\n        @return: The decrypted data.\n        \"\"\"\n        return self.decryptor.update(blocks)\n\n\n    def makeMAC(self, seqid, data):\n        \"\"\"\n        Create a message authentication code (MAC) for the given packet using\n        the outgoing MAC values.\n\n        @type seqid: L{int}\n        @param seqid: The sequence ID of the outgoing packet.\n\n        @type data: L{bytes}\n        @param data: The data to create a MAC for.\n\n        @rtype: L{str}\n        @return: The serialized MAC.\n        \"\"\"\n        if not self.outMAC[0]:\n            return b''\n        data = struct.pack('>L', seqid) + data\n        return hmac.HMAC(self.outMAC.key, data, self.outMAC[0]).digest()\n\n\n    def verify(self, seqid, data, mac):\n        \"\"\"\n        Verify an incoming MAC using the incoming MAC values.\n\n        @type seqid: L{int}\n        @param seqid: The sequence ID of the incoming packet.\n\n        @type data: L{bytes}\n        @param data: The packet data to verify.\n\n        @type mac: L{bytes}\n        @param mac: The MAC sent with the packet.\n\n        @rtype: L{bool}\n        @return: C{True} if the MAC is valid.\n        \"\"\"\n        if not self.inMAC[0]:\n            return mac == b''\n        data = struct.pack('>L', seqid) + data\n        outer = hmac.HMAC(self.inMAC.key, data, self.inMAC[0]).digest()\n        return mac == outer\n\n\n\ndef _getSupportedCiphers():\n    \"\"\"\n    Build a list of ciphers that are supported by the backend in use.\n\n    @return: a list of supported ciphers.\n    @rtype: L{list} of L{str}\n    \"\"\"\n    supportedCiphers = []\n    cs = [b'aes256-ctr', b'aes256-cbc', b'aes192-ctr', b'aes192-cbc',\n          b'aes128-ctr', b'aes128-cbc', b'cast128-ctr', b'cast128-cbc',\n          b'blowfish-ctr', b'blowfish-cbc', b'3des-ctr', b'3des-cbc']\n    for cipher in cs:\n        algorithmClass, keySize, modeClass = SSHCiphers.cipherMap[cipher]\n        try:\n            Cipher(\n                algorithmClass(b' ' * keySize),\n                modeClass(b' ' * (algorithmClass.block_size // 8)),\n                backend=default_backend(),\n            ).encryptor()\n        except UnsupportedAlgorithm:\n            pass\n        else:\n            supportedCiphers.append(cipher)\n    return supportedCiphers\n\n\n\nclass SSHTransportBase(protocol.Protocol):\n    \"\"\"\n    Protocol supporting basic SSH functionality: sending/receiving packets\n    and message dispatch.  To connect to or run a server, you must use\n    SSHClientTransport or SSHServerTransport.\n\n    @ivar protocolVersion: A string representing the version of the SSH\n        protocol we support.  Currently defaults to '2.0'.\n\n    @ivar version: A string representing the version of the server or client.\n        Currently defaults to 'Twisted'.\n\n    @ivar comment: An optional string giving more information about the\n        server or client.\n\n    @ivar supportedCiphers: A list of strings representing the encryption\n        algorithms supported, in order from most-preferred to least.\n\n    @ivar supportedMACs: A list of strings representing the message\n        authentication codes (hashes) supported, in order from most-preferred\n        to least.  Both this and supportedCiphers can include 'none' to use\n        no encryption or authentication, but that must be done manually,\n\n    @ivar supportedKeyExchanges: A list of strings representing the\n        key exchanges supported, in order from most-preferred to least.\n\n    @ivar supportedPublicKeys:  A list of strings representing the\n        public key types supported, in order from most-preferred to least.\n\n    @ivar supportedCompressions: A list of strings representing compression\n        types supported, from most-preferred to least.\n\n    @ivar supportedLanguages: A list of strings representing languages\n        supported, from most-preferred to least.\n\n    @ivar supportedVersions: A container of strings representing supported ssh\n        protocol version numbers.\n\n    @ivar isClient: A boolean indicating whether this is a client or server.\n\n    @ivar gotVersion: A boolean indicating whether we have received the\n        version string from the other side.\n\n    @ivar buf: Data we've received but hasn't been parsed into a packet.\n\n    @ivar outgoingPacketSequence: the sequence number of the next packet we\n        will send.\n\n    @ivar incomingPacketSequence: the sequence number of the next packet we\n        are expecting from the other side.\n\n    @ivar outgoingCompression: an object supporting the .compress(str) and\n        .flush() methods, or None if there is no outgoing compression.  Used to\n        compress outgoing data.\n\n    @ivar outgoingCompressionType: A string representing the outgoing\n        compression type.\n\n    @ivar incomingCompression: an object supporting the .decompress(str)\n        method, or None if there is no incoming compression.  Used to\n        decompress incoming data.\n\n    @ivar incomingCompressionType: A string representing the incoming\n        compression type.\n\n    @ivar ourVersionString: the version string that we sent to the other side.\n        Used in the key exchange.\n\n    @ivar otherVersionString: the version string sent by the other side.  Used\n        in the key exchange.\n\n    @ivar ourKexInitPayload: the MSG_KEXINIT payload we sent.  Used in the key\n        exchange.\n\n    @ivar otherKexInitPayload: the MSG_KEXINIT payload we received.  Used in\n        the key exchange\n\n    @ivar sessionID: a string that is unique to this SSH session.  Created as\n        part of the key exchange, sessionID is used to generate the various\n        encryption and authentication keys.\n\n    @ivar service: an SSHService instance, or None.  If it's set to an object,\n        it's the currently running service.\n\n    @ivar kexAlg: the agreed-upon key exchange algorithm.\n\n    @ivar keyAlg: the agreed-upon public key type for the key exchange.\n\n    @ivar currentEncryptions: an SSHCiphers instance.  It represents the\n        current encryption and authentication options for the transport.\n\n    @ivar nextEncryptions: an SSHCiphers instance.  Held here until the\n        MSG_NEWKEYS messages are exchanged, when nextEncryptions is\n        transitioned to currentEncryptions.\n\n    @ivar first: the first bytes of the next packet.  In order to avoid\n        decrypting data twice, the first bytes are decrypted and stored until\n        the whole packet is available.\n\n    @ivar _keyExchangeState: The current protocol state with respect to key\n        exchange.  This is either C{_KEY_EXCHANGE_NONE} if no key exchange is\n        in progress (and returns to this value after any key exchange\n        completqes), C{_KEY_EXCHANGE_REQUESTED} if this side of the connection\n        initiated a key exchange, and C{_KEY_EXCHANGE_PROGRESSING} if the other\n        side of the connection initiated a key exchange.  C{_KEY_EXCHANGE_NONE}\n        is the initial value (however SSH connections begin with key exchange,\n        so it will quickly change to another state).\n\n    @ivar _blockedByKeyExchange: Whenever C{_keyExchangeState} is not\n        C{_KEY_EXCHANGE_NONE}, this is a C{list} of pending messages which were\n        passed to L{sendPacket} but could not be sent because it is not legal\n        to send them while a key exchange is in progress.  When the key\n        exchange completes, another attempt is made to send these messages.\n    \"\"\"\n    protocolVersion = b'2.0'\n    version = b'Twisted_' + twisted_version.encode('ascii')\n    comment = b''\n    ourVersionString = (b'SSH-' + protocolVersion + b'-' + version + b' '\n            + comment).strip()\n\n    # L{None} is supported as cipher and hmac. For security they are disabled\n    # by default. To enable them, subclass this class and add it, or do:\n    # SSHTransportBase.supportedCiphers.append('none')\n    # List ordered by preference.\n    supportedCiphers = _getSupportedCiphers()\n    supportedMACs = [\n        b'hmac-sha2-512',\n        b'hmac-sha2-384',\n        b'hmac-sha2-256',\n        b'hmac-sha1',\n        b'hmac-md5',\n        # `none`,\n    ]\n\n    supportedKeyExchanges = _kex.getSupportedKeyExchanges()\n    supportedPublicKeys = []\n\n    # Add the supported EC keys, and change the name from ecdh* to ecdsa*\n    for eckey in supportedKeyExchanges:\n        if eckey.find(b'ecdh') != -1:\n            supportedPublicKeys += [eckey.replace(b'ecdh', b'ecdsa')]\n\n    supportedPublicKeys += [b'ssh-rsa', b'ssh-dss']\n\n    supportedCompressions = [b'none', b'zlib']\n    supportedLanguages = ()\n    supportedVersions = (b'1.99', b'2.0')\n    isClient = False\n    gotVersion = False\n    buf = b''\n    outgoingPacketSequence = 0\n    incomingPacketSequence = 0\n    outgoingCompression = None\n    incomingCompression = None\n    sessionID = None\n    service = None\n\n    # There is no key exchange activity in progress.\n    _KEY_EXCHANGE_NONE = '_KEY_EXCHANGE_NONE'\n\n    # Key exchange is in progress and we started it.\n    _KEY_EXCHANGE_REQUESTED = '_KEY_EXCHANGE_REQUESTED'\n\n    # Key exchange is in progress and both sides have sent KEXINIT messages.\n    _KEY_EXCHANGE_PROGRESSING = '_KEY_EXCHANGE_PROGRESSING'\n\n    # There is a fourth conceptual state not represented here: KEXINIT received\n    # but not sent.  Since we always send a KEXINIT as soon as we get it, we\n    # can't ever be in that state.\n\n    # The current key exchange state.\n    _keyExchangeState = _KEY_EXCHANGE_NONE\n    _blockedByKeyExchange = None\n\n    def connectionLost(self, reason):\n        \"\"\"\n        When the underlying connection is closed, stop the running service (if\n        any), and log out the avatar (if any).\n\n        @type reason: L{twisted.python.failure.Failure}\n        @param reason: The cause of the connection being closed.\n        \"\"\"\n        if self.service:\n            self.service.serviceStopped()\n        if hasattr(self, 'avatar'):\n            self.logoutFunction()\n        log.msg('connection lost')\n\n\n    def connectionMade(self):\n        \"\"\"\n        Called when the connection is made to the other side.  We sent our\n        version and the MSG_KEXINIT packet.\n        \"\"\"\n        self.transport.write(self.ourVersionString + b'\\r\\n')\n        self.currentEncryptions = SSHCiphers(b'none', b'none', b'none',\n                                             b'none')\n        self.currentEncryptions.setKeys(b'', b'', b'', b'', b'', b'')\n        self.sendKexInit()\n\n\n    def sendKexInit(self):\n        \"\"\"\n        Send a I{KEXINIT} message to initiate key exchange or to respond to a\n        key exchange initiated by the peer.\n\n        @raise RuntimeError: If a key exchange has already been started and it\n            is not appropriate to send a I{KEXINIT} message at this time.\n\n        @return: L{None}\n        \"\"\"\n        if self._keyExchangeState != self._KEY_EXCHANGE_NONE:\n            raise RuntimeError(\n                \"Cannot send KEXINIT while key exchange state is %r\" % (\n                    self._keyExchangeState,))\n\n        self.ourKexInitPayload = b''.join([\n            chr(MSG_KEXINIT),\n            randbytes.secureRandom(16),\n            NS(b','.join(self.supportedKeyExchanges)),\n            NS(b','.join(self.supportedPublicKeys)),\n            NS(b','.join(self.supportedCiphers)),\n            NS(b','.join(self.supportedCiphers)),\n            NS(b','.join(self.supportedMACs)),\n            NS(b','.join(self.supportedMACs)),\n            NS(b','.join(self.supportedCompressions)),\n            NS(b','.join(self.supportedCompressions)),\n            NS(b','.join(self.supportedLanguages)),\n            NS(b','.join(self.supportedLanguages)),\n            b'\\000\\000\\000\\000\\000'])\n        self.sendPacket(MSG_KEXINIT, self.ourKexInitPayload[1:])\n        self._keyExchangeState = self._KEY_EXCHANGE_REQUESTED\n        self._blockedByKeyExchange = []\n\n\n    def _allowedKeyExchangeMessageType(self, messageType):\n        \"\"\"\n        Determine if the given message type may be sent while key exchange is\n        in progress.\n\n        @param messageType: The type of message\n        @type messageType: L{int}\n\n        @return: C{True} if the given type of message may be sent while key\n            exchange is in progress, C{False} if it may not.\n        @rtype: L{bool}\n\n        @see: U{http://tools.ietf.org/html/rfc4253#section-7.1}\n        \"\"\"\n        # Written somewhat peculularly to reflect the way the specification\n        # defines the allowed message types.\n        if 1 <= messageType <= 19:\n            return messageType not in (MSG_SERVICE_REQUEST, MSG_SERVICE_ACCEPT)\n        if 20 <= messageType <= 29:\n            return messageType not in (MSG_KEXINIT,)\n        return 30 <= messageType <= 49\n\n\n    def sendPacket(self, messageType, payload):\n        \"\"\"\n        Sends a packet.  If it's been set up, compress the data, encrypt it,\n        and authenticate it before sending.  If key exchange is in progress and\n        the message is not part of key exchange, queue it to be sent later.\n\n        @param messageType: The type of the packet; generally one of the\n                            MSG_* values.\n        @type messageType: L{int}\n        @param payload: The payload for the message.\n        @type payload: L{str}\n        \"\"\"\n        if self._keyExchangeState != self._KEY_EXCHANGE_NONE:\n            if not self._allowedKeyExchangeMessageType(messageType):\n                self._blockedByKeyExchange.append((messageType, payload))\n                return\n\n        payload = chr(messageType) + payload\n        if self.outgoingCompression:\n            payload = (self.outgoingCompression.compress(payload)\n                       + self.outgoingCompression.flush(2))\n        bs = self.currentEncryptions.encBlockSize\n        # 4 for the packet length and 1 for the padding length\n        totalSize = 5 + len(payload)\n        lenPad = bs - (totalSize % bs)\n        if lenPad < 4:\n            lenPad = lenPad + bs\n        packet = (struct.pack('!LB',\n                              totalSize + lenPad - 4, lenPad) +\n                  payload + randbytes.secureRandom(lenPad))\n        encPacket = (\n            self.currentEncryptions.encrypt(packet) +\n            self.currentEncryptions.makeMAC(\n                self.outgoingPacketSequence, packet))\n        self.transport.write(encPacket)\n        self.outgoingPacketSequence += 1\n\n\n    def getPacket(self):\n        \"\"\"\n        Try to return a decrypted, authenticated, and decompressed packet\n        out of the buffer.  If there is not enough data, return None.\n\n        @rtype: L{str} or L{None}\n        @return: The decoded packet, if any.\n        \"\"\"\n        bs = self.currentEncryptions.decBlockSize\n        ms = self.currentEncryptions.verifyDigestSize\n        if len(self.buf) < bs:\n            # Not enough data for a block\n            return\n        if not hasattr(self, 'first'):\n            first = self.currentEncryptions.decrypt(self.buf[:bs])\n        else:\n            first = self.first\n            del self.first\n        packetLen, paddingLen = struct.unpack('!LB', first[:5])\n        if packetLen > 1048576:  # 1024 ** 2\n            self.sendDisconnect(\n                DISCONNECT_PROTOCOL_ERROR,\n                networkString('bad packet length {}'.format(packetLen)))\n            return\n        if len(self.buf) < packetLen + 4 + ms:\n            # Not enough data for a packet\n            self.first = first\n            return\n        if (packetLen + 4) % bs != 0:\n            self.sendDisconnect(\n                DISCONNECT_PROTOCOL_ERROR,\n                networkString(\n                    'bad packet mod (%i%%%i == %i)' % (\n                        packetLen + 4, bs, (packetLen + 4) % bs)))\n            return\n        encData, self.buf = self.buf[:4 + packetLen], self.buf[4 + packetLen:]\n        packet = first + self.currentEncryptions.decrypt(encData[bs:])\n        if len(packet) != 4 + packetLen:\n            self.sendDisconnect(DISCONNECT_PROTOCOL_ERROR,\n                                b'bad decryption')\n            return\n        if ms:\n            macData, self.buf = self.buf[:ms], self.buf[ms:]\n            if not self.currentEncryptions.verify(self.incomingPacketSequence,\n                                                  packet, macData):\n                self.sendDisconnect(DISCONNECT_MAC_ERROR, b'bad MAC')\n                return\n        payload = packet[5:-paddingLen]\n        if self.incomingCompression:\n            try:\n                payload = self.incomingCompression.decompress(payload)\n            except:\n                # Tolerate any errors in decompression\n                log.err()\n                self.sendDisconnect(DISCONNECT_COMPRESSION_ERROR,\n                                    b'compression error')\n                return\n        self.incomingPacketSequence += 1\n        return payload\n\n\n    def _unsupportedVersionReceived(self, remoteVersion):\n        \"\"\"\n        Called when an unsupported version of the ssh protocol is received from\n        the remote endpoint.\n\n        @param remoteVersion: remote ssh protocol version which is unsupported\n            by us.\n        @type remoteVersion: L{str}\n        \"\"\"\n        self.sendDisconnect(DISCONNECT_PROTOCOL_VERSION_NOT_SUPPORTED,\n            b'bad version ' + remoteVersion)\n\n\n    def dataReceived(self, data):\n        \"\"\"\n        First, check for the version string (SSH-2.0-*).  After that has been\n        received, this method adds data to the buffer, and pulls out any\n        packets.\n\n        @type data: L{bytes}\n        @param data: The data that was received.\n        \"\"\"\n        self.buf = self.buf + data\n        if not self.gotVersion:\n            if self.buf.find(b'\\n', self.buf.find(b'SSH-')) == -1:\n                return\n\n            # RFC 4253 section 4.2 ask for strict `\\r\\n` line ending.\n            # Here we are a bit more relaxed and accept implementations ending\n            # only in '\\n'.\n            # https://tools.ietf.org/html/rfc4253#section-4.2\n            lines = self.buf.split(b'\\n')\n            for p in lines:\n                if p.startswith(b'SSH-'):\n                    self.gotVersion = True\n                    # Since the line was split on '\\n' and most of the time\n                    # it uses '\\r\\n' we may get an extra '\\r'.\n                    self.otherVersionString = p.rstrip(b'\\r')\n                    remoteVersion = p.split(b'-')[1]\n                    if remoteVersion not in self.supportedVersions:\n                        self._unsupportedVersionReceived(remoteVersion)\n                        return\n                    i = lines.index(p)\n                    self.buf = b'\\n'.join(lines[i + 1:])\n        packet = self.getPacket()\n        while packet:\n            messageNum = ord(packet[0:1])\n            self.dispatchMessage(messageNum, packet[1:])\n            packet = self.getPacket()\n\n\n    def dispatchMessage(self, messageNum, payload):\n        \"\"\"\n        Send a received message to the appropriate method.\n\n        @type messageNum: L{int}\n        @param messageNum: The message number.\n\n        @type payload: L{bytes}\n        @param payload: The message payload.\n        \"\"\"\n        if messageNum < 50 and messageNum in messages:\n            messageType = messages[messageNum][4:]\n            f = getattr(self, 'ssh_%s' % (messageType,), None)\n            if f is not None:\n                f(payload)\n            else:\n                log.msg(\"couldn't handle %s\" % messageType)\n                log.msg(repr(payload))\n                self.sendUnimplemented()\n        elif self.service:\n            log.callWithLogger(self.service, self.service.packetReceived,\n                               messageNum, payload)\n        else:\n            log.msg(\"couldn't handle %s\" % messageNum)\n            log.msg(repr(payload))\n            self.sendUnimplemented()\n\n\n    def getPeer(self):\n        \"\"\"\n        Returns an L{SSHTransportAddress} corresponding to the other (peer)\n        side of this transport.\n\n        @return: L{SSHTransportAddress} for the peer\n        @rtype: L{SSHTransportAddress}\n        @since: 12.1\n        \"\"\"\n        return address.SSHTransportAddress(self.transport.getPeer())\n\n\n    def getHost(self):\n        \"\"\"\n        Returns an L{SSHTransportAddress} corresponding to the this side of\n        transport.\n\n        @return: L{SSHTransportAddress} for the peer\n        @rtype: L{SSHTransportAddress}\n        @since: 12.1\n        \"\"\"\n        return address.SSHTransportAddress(self.transport.getHost())\n\n\n    @property\n    def kexAlg(self):\n        \"\"\"\n        The key exchange algorithm name agreed between client and server.\n        \"\"\"\n        return self._kexAlg\n\n\n    @kexAlg.setter\n    def kexAlg(self, value):\n        \"\"\"\n        Set the key exchange algorithm name.\n        \"\"\"\n        self._kexAlg = value\n\n    # Client-initiated rekeying looks like this:\n    #\n    #  C> MSG_KEXINIT\n    #  S> MSG_KEXINIT\n    #  C> MSG_KEX_DH_GEX_REQUEST  or   MSG_KEXDH_INIT\n    #  S> MSG_KEX_DH_GEX_GROUP    or   MSG_KEXDH_REPLY\n    #  C> MSG_KEX_DH_GEX_INIT     or   --\n    #  S> MSG_KEX_DH_GEX_REPLY    or   --\n    #  C> MSG_NEWKEYS\n    #  S> MSG_NEWKEYS\n    #\n    # Server-initiated rekeying is the same, only the first two messages are\n    # switched.\n\n\n    def ssh_KEXINIT(self, packet):\n        \"\"\"\n        Called when we receive a MSG_KEXINIT message.  Payload::\n            bytes[16] cookie\n            string keyExchangeAlgorithms\n            string keyAlgorithms\n            string incomingEncryptions\n            string outgoingEncryptions\n            string incomingAuthentications\n            string outgoingAuthentications\n            string incomingCompressions\n            string outgoingCompressions\n            string incomingLanguages\n            string outgoingLanguages\n            bool firstPacketFollows\n            unit32 0 (reserved)\n\n        Starts setting up the key exchange, keys, encryptions, and\n        authentications.  Extended by ssh_KEXINIT in SSHServerTransport and\n        SSHClientTransport.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n\n        @return: A L{tuple} of negotiated key exchange algorithms, key\n        algorithms, and unhandled data, or L{None} if something went wrong.\n        \"\"\"\n        self.otherKexInitPayload = chr(MSG_KEXINIT) + packet\n        # This is useless to us:\n        # cookie = packet[: 16]\n        k = getNS(packet[16:], 10)\n        strings, rest = k[:-1], k[-1]\n        (kexAlgs, keyAlgs, encCS, encSC, macCS, macSC, compCS, compSC, langCS,\n         langSC) = [s.split(b',') for s in strings]\n        # These are the server directions\n        outs = [encSC, macSC, compSC]\n        ins = [encCS, macSC, compCS]\n        if self.isClient:\n            outs, ins = ins, outs # Switch directions\n        server = (self.supportedKeyExchanges, self.supportedPublicKeys,\n                self.supportedCiphers, self.supportedCiphers,\n                self.supportedMACs, self.supportedMACs,\n                self.supportedCompressions, self.supportedCompressions)\n        client = (kexAlgs, keyAlgs, outs[0], ins[0], outs[1], ins[1],\n                outs[2], ins[2])\n        if self.isClient:\n            server, client = client, server\n        self.kexAlg = ffs(client[0], server[0])\n        self.keyAlg = ffs(client[1], server[1])\n        self.nextEncryptions = SSHCiphers(\n            ffs(client[2], server[2]),\n            ffs(client[3], server[3]),\n            ffs(client[4], server[4]),\n            ffs(client[5], server[5]))\n        self.outgoingCompressionType = ffs(client[6], server[6])\n        self.incomingCompressionType = ffs(client[7], server[7])\n        if None in (self.kexAlg, self.keyAlg, self.outgoingCompressionType,\n                    self.incomingCompressionType):\n            self.sendDisconnect(DISCONNECT_KEY_EXCHANGE_FAILED,\n                                b\"couldn't match all kex parts\")\n            return\n        if None in self.nextEncryptions.__dict__.values():\n            self.sendDisconnect(DISCONNECT_KEY_EXCHANGE_FAILED,\n                                b\"couldn't match all kex parts\")\n            return\n        log.msg('kex alg, key alg: %r %r' % (self.kexAlg, self.keyAlg))\n        log.msg('outgoing: %r %r %r' % (self.nextEncryptions.outCipType,\n                                        self.nextEncryptions.outMACType,\n                                        self.outgoingCompressionType))\n        log.msg('incoming: %r %r %r' % (self.nextEncryptions.inCipType,\n                                        self.nextEncryptions.inMACType,\n                                        self.incomingCompressionType))\n\n        if self._keyExchangeState == self._KEY_EXCHANGE_REQUESTED:\n            self._keyExchangeState = self._KEY_EXCHANGE_PROGRESSING\n        else:\n            self.sendKexInit()\n\n        return kexAlgs, keyAlgs, rest # For SSHServerTransport to use\n\n\n    def ssh_DISCONNECT(self, packet):\n        \"\"\"\n        Called when we receive a MSG_DISCONNECT message.  Payload::\n            long code\n            string description\n\n        This means that the other side has disconnected.  Pass the message up\n        and disconnect ourselves.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n        reasonCode = struct.unpack('>L', packet[: 4])[0]\n        description, foo = getNS(packet[4:])\n        self.receiveError(reasonCode, description)\n        self.transport.loseConnection()\n\n\n    def ssh_IGNORE(self, packet):\n        \"\"\"\n        Called when we receive a MSG_IGNORE message.  No payload.\n        This means nothing; we simply return.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n\n\n    def ssh_UNIMPLEMENTED(self, packet):\n        \"\"\"\n        Called when we receive a MSG_UNIMPLEMENTED message.  Payload::\n            long packet\n\n        This means that the other side did not implement one of our packets.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n        seqnum, = struct.unpack('>L', packet)\n        self.receiveUnimplemented(seqnum)\n\n\n    def ssh_DEBUG(self, packet):\n        \"\"\"\n        Called when we receive a MSG_DEBUG message.  Payload::\n            bool alwaysDisplay\n            string message\n            string language\n\n        This means the other side has passed along some debugging info.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n        alwaysDisplay = bool(ord(packet[0:1]))\n        message, lang, foo = getNS(packet[1:], 2)\n        self.receiveDebug(alwaysDisplay, message, lang)\n\n\n    def setService(self, service):\n        \"\"\"\n        Set our service to service and start it running.  If we were\n        running a service previously, stop it first.\n\n        @type service: C{SSHService}\n        @param service: The service to attach.\n        \"\"\"\n        log.msg('starting service %r' % (service.name,))\n        if self.service:\n            self.service.serviceStopped()\n        self.service = service\n        service.transport = self\n        self.service.serviceStarted()\n\n\n    def sendDebug(self, message, alwaysDisplay=False, language=b''):\n        \"\"\"\n        Send a debug message to the other side.\n\n        @param message: the message to send.\n        @type message: L{str}\n        @param alwaysDisplay: if True, tell the other side to always\n                              display this message.\n        @type alwaysDisplay: L{bool}\n        @param language: optionally, the language the message is in.\n        @type language: L{str}\n        \"\"\"\n        self.sendPacket(MSG_DEBUG, chr(alwaysDisplay) + NS(message) +\n                        NS(language))\n\n\n    def sendIgnore(self, message):\n        \"\"\"\n        Send a message that will be ignored by the other side.  This is\n        useful to fool attacks based on guessing packet sizes in the\n        encrypted stream.\n\n        @param message: data to send with the message\n        @type message: L{str}\n        \"\"\"\n        self.sendPacket(MSG_IGNORE, NS(message))\n\n\n    def sendUnimplemented(self):\n        \"\"\"\n        Send a message to the other side that the last packet was not\n        understood.\n        \"\"\"\n        seqnum = self.incomingPacketSequence\n        self.sendPacket(MSG_UNIMPLEMENTED, struct.pack('!L', seqnum))\n\n\n    def sendDisconnect(self, reason, desc):\n        \"\"\"\n        Send a disconnect message to the other side and then disconnect.\n\n        @param reason: the reason for the disconnect.  Should be one of the\n                       DISCONNECT_* values.\n        @type reason: L{int}\n        @param desc: a descrption of the reason for the disconnection.\n        @type desc: L{str}\n        \"\"\"\n        self.sendPacket(\n            MSG_DISCONNECT, struct.pack('>L', reason) + NS(desc) + NS(b''))\n        log.msg('Disconnecting with error, code %s\\nreason: %s' % (reason,\n                                                                   desc))\n        self.transport.loseConnection()\n\n\n    def _startEphemeralDH(self):\n        \"\"\"\n        Prepares for a Diffie-Hellman key agreement exchange.\n\n        Creates an ephemeral keypair in the group defined by (self.g,\n        self.p) and stores it.\n        \"\"\"\n\n        numbers = dh.DHParameterNumbers(self.p, self.g)\n        parameters = numbers.parameters(default_backend())\n        self.dhSecretKey = parameters.generate_private_key()\n        y = self.dhSecretKey.public_key().public_numbers().y\n        self.dhSecretKeyPublicMP = MP(y)\n\n\n    def _finishEphemeralDH(self, remoteDHpublicKey):\n        \"\"\"\n        Completes the Diffie-Hellman key agreement started by\n        _startEphemeralDH, and forgets the ephemeral secret key.\n\n        @type remoteDHpublicKey: L{int}\n        @rtype: L{bytes}\n        @return: The new shared secret, in SSH C{mpint} format.\n\n        \"\"\"\n\n        remoteKey = dh.DHPublicNumbers(\n            remoteDHpublicKey,\n            dh.DHParameterNumbers(self.p, self.g)\n        ).public_key(default_backend())\n        secret = self.dhSecretKey.exchange(remoteKey)\n        del self.dhSecretKey\n\n        # The result of a Diffie-Hellman exchange is an integer, but\n        # the Cryptography module returns it as bytes in a form that\n        # is only vaguely documented. We fix it up to match the SSH\n        # MP-integer format as described in RFC4251.\n        secret = secret.lstrip(b'\\x00')\n        ch = ord(secret[0:1])\n        if ch & 0x80:  # High bit set?\n            # Make room for the sign bit\n            prefix = struct.pack('>L', len(secret) + 1) + b'\\x00'\n        else:\n            prefix = struct.pack('>L', len(secret))\n        return prefix + secret\n\n\n    def _getKey(self, c, sharedSecret, exchangeHash):\n        \"\"\"\n        Get one of the keys for authentication/encryption.\n\n        @type c: L{bytes}\n        @param c: The letter identifying which key this is.\n\n        @type sharedSecret: L{bytes}\n        @param sharedSecret: The shared secret K.\n\n        @type exchangeHash: L{bytes}\n        @param exchangeHash: The hash H from key exchange.\n\n        @rtype: L{bytes}\n        @return: The derived key.\n        \"\"\"\n        hashProcessor = _kex.getHashProcessor(self.kexAlg)\n        k1 = hashProcessor(sharedSecret + exchangeHash + c + self.sessionID)\n        k1 = k1.digest()\n        k2 = hashProcessor(sharedSecret + exchangeHash + k1).digest()\n        k3 = hashProcessor(sharedSecret + exchangeHash + k1 + k2).digest()\n        k4 = hashProcessor(sharedSecret + exchangeHash + k1 + k2 + k3).digest()\n        return k1 + k2 + k3 + k4\n\n\n    def _keySetup(self, sharedSecret, exchangeHash):\n        \"\"\"\n        Set up the keys for the connection and sends MSG_NEWKEYS when\n        finished,\n\n        @param sharedSecret: a secret string agreed upon using a Diffie-\n                             Hellman exchange, so it is only shared between\n                             the server and the client.\n        @type sharedSecret: L{str}\n        @param exchangeHash: A hash of various data known by both sides.\n        @type exchangeHash: L{str}\n        \"\"\"\n        if not self.sessionID:\n            self.sessionID = exchangeHash\n        initIVCS = self._getKey(b'A', sharedSecret, exchangeHash)\n        initIVSC = self._getKey(b'B', sharedSecret, exchangeHash)\n        encKeyCS = self._getKey(b'C', sharedSecret, exchangeHash)\n        encKeySC = self._getKey(b'D', sharedSecret, exchangeHash)\n        integKeyCS = self._getKey(b'E', sharedSecret, exchangeHash)\n        integKeySC = self._getKey(b'F', sharedSecret, exchangeHash)\n        outs = [initIVSC, encKeySC, integKeySC]\n        ins = [initIVCS, encKeyCS, integKeyCS]\n        if self.isClient: # Reverse for the client\n            log.msg('REVERSE')\n            outs, ins = ins, outs\n        self.nextEncryptions.setKeys(outs[0], outs[1], ins[0], ins[1],\n                                     outs[2], ins[2])\n        self.sendPacket(MSG_NEWKEYS, b'')\n\n\n    def _newKeys(self):\n        \"\"\"\n        Called back by a subclass once a I{MSG_NEWKEYS} message has been\n        received.  This indicates key exchange has completed and new encryption\n        and compression parameters should be adopted.  Any messages which were\n        queued during key exchange will also be flushed.\n        \"\"\"\n        log.msg('NEW KEYS')\n        self.currentEncryptions = self.nextEncryptions\n        if self.outgoingCompressionType == b'zlib':\n            self.outgoingCompression = zlib.compressobj(6)\n        if self.incomingCompressionType == b'zlib':\n            self.incomingCompression = zlib.decompressobj()\n\n        self._keyExchangeState = self._KEY_EXCHANGE_NONE\n        messages = self._blockedByKeyExchange\n        self._blockedByKeyExchange = None\n        for (messageType, payload) in messages:\n            self.sendPacket(messageType, payload)\n\n\n    def isEncrypted(self, direction=\"out\"):\n        \"\"\"\n        Check if the connection is encrypted in the given direction.\n\n        @type direction: L{str}\n        @param direction: The direction: one of 'out', 'in', or 'both'.\n\n        @rtype: L{bool}\n        @return: C{True} if it is encrypted.\n        \"\"\"\n        if direction == \"out\":\n            return self.currentEncryptions.outCipType != b'none'\n        elif direction == \"in\":\n            return self.currentEncryptions.inCipType != b'none'\n        elif direction == \"both\":\n            return self.isEncrypted(\"in\") and self.isEncrypted(\"out\")\n        else:\n            raise TypeError('direction must be \"out\", \"in\", or \"both\"')\n\n\n    def isVerified(self, direction=\"out\"):\n        \"\"\"\n        Check if the connection is verified/authentication in the given direction.\n\n        @type direction: L{str}\n        @param direction: The direction: one of 'out', 'in', or 'both'.\n\n        @rtype: L{bool}\n        @return: C{True} if it is verified.\n        \"\"\"\n        if direction == \"out\":\n            return self.currentEncryptions.outMACType != b'none'\n        elif direction == \"in\":\n            return self.currentEncryptions.inMACType != b'none'\n        elif direction == \"both\":\n            return self.isVerified(\"in\") and self.isVerified(\"out\")\n        else:\n            raise TypeError('direction must be \"out\", \"in\", or \"both\"')\n\n\n    def loseConnection(self):\n        \"\"\"\n        Lose the connection to the other side, sending a\n        DISCONNECT_CONNECTION_LOST message.\n        \"\"\"\n        self.sendDisconnect(DISCONNECT_CONNECTION_LOST,\n                            b\"user closed connection\")\n\n    # Client methods\n\n\n    def receiveError(self, reasonCode, description):\n        \"\"\"\n        Called when we receive a disconnect error message from the other\n        side.\n\n        @param reasonCode: the reason for the disconnect, one of the\n                           DISCONNECT_ values.\n        @type reasonCode: L{int}\n        @param description: a human-readable description of the\n                            disconnection.\n        @type description: L{str}\n        \"\"\"\n        log.msg('Got remote error, code %s\\nreason: %s' % (reasonCode,\n                                                           description))\n\n\n    def receiveUnimplemented(self, seqnum):\n        \"\"\"\n        Called when we receive an unimplemented packet message from the other\n        side.\n\n        @param seqnum: the sequence number that was not understood.\n        @type seqnum: L{int}\n        \"\"\"\n        log.msg('other side unimplemented packet #%s' % (seqnum,))\n\n\n    def receiveDebug(self, alwaysDisplay, message, lang):\n        \"\"\"\n        Called when we receive a debug message from the other side.\n\n        @param alwaysDisplay: if True, this message should always be\n                              displayed.\n        @type alwaysDisplay: L{bool}\n        @param message: the debug message\n        @type message: L{str}\n        @param lang: optionally the language the message is in.\n        @type lang: L{str}\n        \"\"\"\n        if alwaysDisplay:\n            log.msg('Remote Debug Message: %s' % (message,))\n\n\n\nclass SSHServerTransport(SSHTransportBase):\n    \"\"\"\n    SSHServerTransport implements the server side of the SSH protocol.\n\n    @ivar isClient: since we are never the client, this is always False.\n\n    @ivar ignoreNextPacket: if True, ignore the next key exchange packet.  This\n        is set when the client sends a guessed key exchange packet but with\n        an incorrect guess.\n\n    @ivar dhGexRequest: the KEX_DH_GEX_REQUEST(_OLD) that the client sent.\n        The key generation needs this to be stored.\n\n    @ivar g: the Diffie-Hellman group generator.\n\n    @ivar p: the Diffie-Hellman group prime.\n    \"\"\"\n    isClient = False\n    ignoreNextPacket = 0\n\n\n    def ssh_KEXINIT(self, packet):\n        \"\"\"\n        Called when we receive a MSG_KEXINIT message.  For a description\n        of the packet, see SSHTransportBase.ssh_KEXINIT().  Additionally,\n        this method checks if a guessed key exchange packet was sent.  If\n        it was sent, and it guessed incorrectly, the next key exchange\n        packet MUST be ignored.\n        \"\"\"\n        retval = SSHTransportBase.ssh_KEXINIT(self, packet)\n        if not retval: # Disconnected\n            return\n        else:\n            kexAlgs, keyAlgs, rest = retval\n        if ord(rest[0:1]): # Flag first_kex_packet_follows?\n            if (kexAlgs[0] != self.supportedKeyExchanges[0] or\n                keyAlgs[0] != self.supportedPublicKeys[0]):\n                self.ignoreNextPacket = True # Guess was wrong\n\n\n    def _ssh_KEX_ECDH_INIT(self, packet):\n        \"\"\"\n        Called from L{ssh_KEX_DH_GEX_REQUEST_OLD} to handle\n        elliptic curve key exchanges.\n\n        Payload::\n\n            string client Elliptic Curve Diffie-Hellman public key\n\n        Just like L{_ssh_KEXDH_INIT} this message type is also not dispatched\n        directly. Extra check to determine if this is really KEX_ECDH_INIT\n        is required.\n\n        First we load the host's public/private keys.\n        Then we generate the ECDH public/private keypair for the given curve.\n        With that we generate the shared secret key.\n        Then we compute the hash to sign and send back to the client\n        Along with the server's public key and the ECDH public key.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n\n        @return: None.\n        \"\"\"\n        # Get the raw client public key.\n        pktPub, packet = getNS(packet)\n\n        # Get the host's public and private keys\n        pubHostKey = self.factory.publicKeys[self.keyAlg]\n        privHostKey = self.factory.privateKeys[self.keyAlg]\n\n        # Get the curve instance\n        try:\n            curve = keys._curveTable[b'ecdsa' + self.kexAlg[4:]]\n        except KeyError:\n            raise UnsupportedAlgorithm('unused-key')\n\n        # Generate the private key\n        ecPriv = ec.generate_private_key(curve, default_backend())\n\n        # Get the public key\n        ecPub = ecPriv.public_key()\n        encPub = ecPub.public_bytes(\n            serialization.Encoding.X962,\n            serialization.PublicFormat.UncompressedPoint\n        )\n\n        # Take the provided public key and transform it into\n        # a format for the cryptography module\n        theirECPub = ec.EllipticCurvePublicKey.from_encoded_point(curve,\n                                                                  pktPub)\n\n        # We need to convert to hex,\n        # so we can convert to an int\n        # so we can make it a multiple precision int.\n        sharedSecret = MP(\n                       int(\n                        binascii.hexlify(\n                          ecPriv.exchange(ec.ECDH(), theirECPub)), 16))\n\n        # Finish update and digest\n        h = _kex.getHashProcessor(self.kexAlg)()\n        h.update(NS(self.otherVersionString))\n        h.update(NS(self.ourVersionString))\n        h.update(NS(self.otherKexInitPayload))\n        h.update(NS(self.ourKexInitPayload))\n        h.update(NS(pubHostKey.blob()))\n        h.update(NS(pktPub))\n        h.update(NS(encPub))\n        h.update(sharedSecret)\n        exchangeHash = h.digest()\n\n        self.sendPacket(\n            MSG_KEXDH_REPLY,\n            NS(pubHostKey.blob()) + NS(encPub) +\n            NS(privHostKey.sign(exchangeHash)))\n        self._keySetup(sharedSecret, exchangeHash)\n\n\n    def _ssh_KEXDH_INIT(self, packet):\n        \"\"\"\n        Called to handle the beginning of a non-group key exchange.\n\n        Unlike other message types, this is not dispatched automatically.  It\n        is called from C{ssh_KEX_DH_GEX_REQUEST_OLD} because an extra check is\n        required to determine if this is really a KEXDH_INIT message or if it\n        is a KEX_DH_GEX_REQUEST_OLD message.\n\n        The KEXDH_INIT payload::\n\n                integer e (the client's Diffie-Hellman public key)\n\n        We send the KEXDH_REPLY with our host key and signature.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n        clientDHpublicKey, foo = getMP(packet)\n        self.g, self.p = _kex.getDHGeneratorAndPrime(self.kexAlg)\n        self._startEphemeralDH()\n        sharedSecret = self._finishEphemeralDH(clientDHpublicKey)\n        h = sha1()\n        h.update(NS(self.otherVersionString))\n        h.update(NS(self.ourVersionString))\n        h.update(NS(self.otherKexInitPayload))\n        h.update(NS(self.ourKexInitPayload))\n        h.update(NS(self.factory.publicKeys[self.keyAlg].blob()))\n        h.update(MP(clientDHpublicKey))\n        h.update(self.dhSecretKeyPublicMP)\n        h.update(sharedSecret)\n        exchangeHash = h.digest()\n        self.sendPacket(\n            MSG_KEXDH_REPLY,\n            NS(self.factory.publicKeys[self.keyAlg].blob()) +\n            self.dhSecretKeyPublicMP +\n            NS(self.factory.privateKeys[self.keyAlg].sign(exchangeHash)))\n        self._keySetup(sharedSecret, exchangeHash)\n\n\n    def ssh_KEX_DH_GEX_REQUEST_OLD(self, packet):\n        \"\"\"\n        This represents different key exchange methods that share the same\n        integer value.  If the message is determined to be a KEXDH_INIT,\n        L{_ssh_KEXDH_INIT} is called to handle it. If it is a KEX_ECDH_INIT,\n        L{_ssh_KEX_ECDH_INIT} is called.\n        Otherwise, for KEX_DH_GEX_REQUEST_OLD payload::\n\n                integer ideal (ideal size for the Diffie-Hellman prime)\n\n            We send the KEX_DH_GEX_GROUP message with the group that is\n            closest in size to ideal.\n\n        If we were told to ignore the next key exchange packet by ssh_KEXINIT,\n        drop it on the floor and return.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n        if self.ignoreNextPacket:\n            self.ignoreNextPacket = 0\n            return\n\n        # KEXDH_INIT, KEX_ECDH_INIT, and KEX_DH_GEX_REQUEST_OLD\n        # have the same value, so use another cue\n        # to decide what kind of message the peer sent us.\n        if _kex.isFixedGroup(self.kexAlg):\n            return self._ssh_KEXDH_INIT(packet)\n        elif _kex.isEllipticCurve(self.kexAlg):\n            return self._ssh_KEX_ECDH_INIT(packet)\n        else:\n            self.dhGexRequest = packet\n            ideal = struct.unpack('>L', packet)[0]\n            self.g, self.p = self.factory.getDHPrime(ideal)\n            self._startEphemeralDH()\n            self.sendPacket(MSG_KEX_DH_GEX_GROUP, MP(self.p) + MP(self.g))\n\n\n    def ssh_KEX_DH_GEX_REQUEST(self, packet):\n        \"\"\"\n        Called when we receive a MSG_KEX_DH_GEX_REQUEST message.  Payload::\n            integer minimum\n            integer ideal\n            integer maximum\n\n        The client is asking for a Diffie-Hellman group between minimum and\n        maximum size, and close to ideal if possible.  We reply with a\n        MSG_KEX_DH_GEX_GROUP message.\n\n        If we were told to ignore the next key exchange packet by ssh_KEXINIT,\n        drop it on the floor and return.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n        if self.ignoreNextPacket:\n            self.ignoreNextPacket = 0\n            return\n        self.dhGexRequest = packet\n        min, ideal, max = struct.unpack('>3L', packet)\n        self.g, self.p = self.factory.getDHPrime(ideal)\n        self._startEphemeralDH()\n        self.sendPacket(MSG_KEX_DH_GEX_GROUP, MP(self.p) + MP(self.g))\n\n\n    def ssh_KEX_DH_GEX_INIT(self, packet):\n        \"\"\"\n        Called when we get a MSG_KEX_DH_GEX_INIT message.  Payload::\n            integer e (client DH public key)\n\n        We send the MSG_KEX_DH_GEX_REPLY message with our host key and\n        signature.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n        clientDHpublicKey, foo = getMP(packet)\n        # TODO: we should also look at the value they send to us and reject\n        # insecure values of f (if g==2 and f has a single '1' bit while the\n        # rest are '0's, then they must have used a small y also).\n\n        # TODO: This could be computed when self.p is set up\n        #  or do as openssh does and scan f for a single '1' bit instead\n\n        sharedSecret = self._finishEphemeralDH(clientDHpublicKey)\n        h = _kex.getHashProcessor(self.kexAlg)()\n        h.update(NS(self.otherVersionString))\n        h.update(NS(self.ourVersionString))\n        h.update(NS(self.otherKexInitPayload))\n        h.update(NS(self.ourKexInitPayload))\n        h.update(NS(self.factory.publicKeys[self.keyAlg].blob()))\n        h.update(self.dhGexRequest)\n        h.update(MP(self.p))\n        h.update(MP(self.g))\n        h.update(MP(clientDHpublicKey))\n        h.update(self.dhSecretKeyPublicMP)\n        h.update(sharedSecret)\n        exchangeHash = h.digest()\n        self.sendPacket(\n            MSG_KEX_DH_GEX_REPLY,\n            NS(self.factory.publicKeys[self.keyAlg].blob()) +\n            self.dhSecretKeyPublicMP +\n            NS(self.factory.privateKeys[self.keyAlg].sign(exchangeHash)))\n        self._keySetup(sharedSecret, exchangeHash)\n\n\n    def ssh_NEWKEYS(self, packet):\n        \"\"\"\n        Called when we get a MSG_NEWKEYS message.  No payload.\n        When we get this, the keys have been set on both sides, and we\n        start using them to encrypt and authenticate the connection.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n        if packet != b'':\n            self.sendDisconnect(DISCONNECT_PROTOCOL_ERROR,\n                                b\"NEWKEYS takes no data\")\n            return\n        self._newKeys()\n\n\n    def ssh_SERVICE_REQUEST(self, packet):\n        \"\"\"\n        Called when we get a MSG_SERVICE_REQUEST message.  Payload::\n            string serviceName\n\n        The client has requested a service.  If we can start the service,\n        start it; otherwise, disconnect with\n        DISCONNECT_SERVICE_NOT_AVAILABLE.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n        service, rest = getNS(packet)\n        cls = self.factory.getService(self, service)\n        if not cls:\n            self.sendDisconnect(DISCONNECT_SERVICE_NOT_AVAILABLE,\n                                b\"don't have service \" + service)\n            return\n        else:\n            self.sendPacket(MSG_SERVICE_ACCEPT, NS(service))\n            self.setService(cls())\n\n\n\nclass SSHClientTransport(SSHTransportBase):\n    \"\"\"\n    SSHClientTransport implements the client side of the SSH protocol.\n\n    @ivar isClient: since we are always the client, this is always True.\n\n    @ivar _gotNewKeys: if we receive a MSG_NEWKEYS message before we are\n        ready to transition to the new keys, this is set to True so we\n        can transition when the keys are ready locally.\n\n    @ivar x: our Diffie-Hellman private key.\n\n    @ivar e: our Diffie-Hellman public key.\n\n    @ivar g: the Diffie-Hellman group generator.\n\n    @ivar p: the Diffie-Hellman group prime\n\n    @ivar instance: the SSHService object we are requesting.\n\n    @ivar _dhMinimalGroupSize: Minimal acceptable group size advertised by the\n        client in MSG_KEX_DH_GEX_REQUEST.\n    @type _dhMinimalGroupSize: int\n\n    @ivar _dhMaximalGroupSize: Maximal acceptable group size advertised by the\n        client in MSG_KEX_DH_GEX_REQUEST.\n    @type _dhMaximalGroupSize: int\n\n    @ivar _dhPreferredGroupSize: Preferred group size advertised by the client\n        in MSG_KEX_DH_GEX_REQUEST.\n    @type _dhPreferredGroupSize: int\n    \"\"\"\n    isClient = True\n\n    # Recommended minimal and maximal values from RFC 4419, 3.\n    _dhMinimalGroupSize = 1024\n    _dhMaximalGroupSize = 8192\n    # FIXME: https://twistedmatrix.com/trac/ticket/8103\n    # This may need to be more dynamic; compare kexgex_client in\n    # OpenSSH.\n    _dhPreferredGroupSize = 2048\n\n    def connectionMade(self):\n        \"\"\"\n        Called when the connection is started with the server.  Just sets\n        up a private instance variable.\n        \"\"\"\n        SSHTransportBase.connectionMade(self)\n        self._gotNewKeys = 0\n\n\n    def ssh_KEXINIT(self, packet):\n        \"\"\"\n        Called when we receive a MSG_KEXINIT message.  For a description\n        of the packet, see SSHTransportBase.ssh_KEXINIT().  Additionally,\n        this method sends the first key exchange packet.\n\n        If the agreed-upon exchange is ECDH, generate a key pair for the\n        corresponding curve and send the public key.\n\n        If the agreed-upon exchange has a fixed prime/generator group,\n        generate a public key and send it in a MSG_KEXDH_INIT message.\n        Otherwise, ask for a 2048 bit group with a MSG_KEX_DH_GEX_REQUEST\n        message.\n        \"\"\"\n        if SSHTransportBase.ssh_KEXINIT(self, packet) is None:\n            # Connection was disconnected while doing base processing.\n            # Maybe no common protocols were agreed.\n            return\n        # Are we using ECDH?\n        if _kex.isEllipticCurve(self.kexAlg):\n            # Find the base curve info\n            self.curve = keys._curveTable[b'ecdsa' + self.kexAlg[4:]]\n\n            # Generate the keys\n            self.ecPriv = ec.generate_private_key(self.curve,\n                                                  default_backend())\n            self.ecPub = self.ecPriv.public_key()\n\n            # DH_GEX_REQUEST_OLD is the same number we need.\n            self.sendPacket(\n                MSG_KEX_DH_GEX_REQUEST_OLD,\n                NS(self.ecPub.public_bytes(\n                    serialization.Encoding.X962,\n                    serialization.PublicFormat.UncompressedPoint\n                ))\n            )\n        elif _kex.isFixedGroup(self.kexAlg):\n            # We agreed on a fixed group key exchange algorithm.\n            self.g, self.p = _kex.getDHGeneratorAndPrime(self.kexAlg)\n            self._startEphemeralDH()\n            self.sendPacket(MSG_KEXDH_INIT, self.dhSecretKeyPublicMP)\n        else:\n            # We agreed on a dynamic group. Tell the server what range of\n            # group sizes we accept, and what size we prefer; the server\n            # will then select a group.\n            self.sendPacket(\n                MSG_KEX_DH_GEX_REQUEST,\n                struct.pack(\n                    '!LLL',\n                    self._dhMinimalGroupSize,\n                    self._dhPreferredGroupSize,\n                    self._dhMaximalGroupSize,\n                    ))\n\n\n    def _ssh_KEX_ECDH_REPLY(self, packet):\n        \"\"\"\n        Called to handle a reply to a ECDH exchange message(KEX_ECDH_INIT).\n\n        Like the handler for I{KEXDH_INIT}, this message type has an\n        overlapping value.  This method is called from C{ssh_KEX_DH_GEX_GROUP}\n        if that method detects a non-group key exchange is in progress.\n\n        Payload::\n\n            string serverHostKey\n            string server Elliptic Curve Diffie-Hellman public key\n            string signature\n\n        We verify the host key and continue if it passes verificiation.\n        Otherwise raise an exception and return.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n\n        @return: A deferred firing when key exchange is complete.\n        \"\"\"\n        def _continue_KEX_ECDH_REPLY(ignored, hostKey, pubKey, signature):\n            # Save off the host public key.\n            theirECHost = hostKey\n\n            # Take the provided public key and transform it into a format\n            # for the cryptography module\n            theirECPub = ec.EllipticCurvePublicKey.from_encoded_point(\n                self.curve, pubKey\n            )\n\n            # We need to convert to hex,\n            # so we can convert to an int\n            # so we can make a multiple precision int.\n            sharedSecret = MP(\n                           int(\n                           binascii.hexlify(\n                             self.ecPriv.exchange(ec.ECDH(), theirECPub)), 16))\n\n            h = _kex.getHashProcessor(self.kexAlg)()\n            h.update(NS(self.ourVersionString))\n            h.update(NS(self.otherVersionString))\n            h.update(NS(self.ourKexInitPayload))\n            h.update(NS(self.otherKexInitPayload))\n            h.update(NS(theirECHost))\n            h.update(NS(self.ecPub.public_bytes(\n                serialization.Encoding.X962,\n                serialization.PublicFormat.UncompressedPoint\n            )))\n            h.update(NS(pubKey))\n            h.update(sharedSecret)\n\n            exchangeHash = h.digest()\n\n            if not keys.Key.fromString(theirECHost).verify(\n                                                      signature, exchangeHash):\n                self.sendDisconnect(DISCONNECT_KEY_EXCHANGE_FAILED,\n                                    b'bad signature')\n            else:\n                self._keySetup(sharedSecret, exchangeHash)\n\n        # Get the host public key,\n        # the raw ECDH public key bytes and the signature\n        hostKey, pubKey, signature, packet = getNS(packet, 3)\n\n        # Easier to comment this out for now than to update all of the tests.\n        #fingerprint = nativeString(base64.b64encode(\n        #        sha256(hostKey).digest()))\n\n        fingerprint = b':'.join(\n             [binascii.hexlify(ch) for ch in iterbytes(md5(hostKey).digest())])\n        d = self.verifyHostKey(hostKey, fingerprint)\n        d.addCallback(_continue_KEX_ECDH_REPLY, hostKey, pubKey, signature)\n        d.addErrback(\n            lambda unused: self.sendDisconnect(\n                DISCONNECT_HOST_KEY_NOT_VERIFIABLE, b'bad host key'))\n        return d\n\n\n    def _ssh_KEXDH_REPLY(self, packet):\n        \"\"\"\n        Called to handle a reply to a non-group key exchange message\n        (KEXDH_INIT).\n\n        Like the handler for I{KEXDH_INIT}, this message type has an\n        overlapping value.  This method is called from C{ssh_KEX_DH_GEX_GROUP}\n        if that method detects a non-group key exchange is in progress.\n\n        Payload::\n\n            string serverHostKey\n            integer f (server Diffie-Hellman public key)\n            string signature\n\n        We verify the host key by calling verifyHostKey, then continue in\n        _continueKEXDH_REPLY.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n\n        @return: A deferred firing when key exchange is complete.\n        \"\"\"\n        pubKey, packet = getNS(packet)\n        f, packet = getMP(packet)\n        signature, packet = getNS(packet)\n        fingerprint = b':'.join([binascii.hexlify(ch) for ch in\n                                 iterbytes(md5(pubKey).digest())])\n        d = self.verifyHostKey(pubKey, fingerprint)\n        d.addCallback(self._continueKEXDH_REPLY, pubKey, f, signature)\n        d.addErrback(\n            lambda unused: self.sendDisconnect(\n                DISCONNECT_HOST_KEY_NOT_VERIFIABLE, b'bad host key'))\n        return d\n\n\n    def ssh_KEX_DH_GEX_GROUP(self, packet):\n        \"\"\"\n        This handles different messages which share an integer value.\n\n        If the key exchange does not have a fixed prime/generator group,\n        we generate a Diffie-Hellman public key and send it in a\n        MSG_KEX_DH_GEX_INIT message.\n\n        Payload::\n            string g (group generator)\n            string p (group prime)\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n        if _kex.isFixedGroup(self.kexAlg):\n            return self._ssh_KEXDH_REPLY(packet)\n        elif _kex.isEllipticCurve(self.kexAlg):\n            return self._ssh_KEX_ECDH_REPLY(packet)\n        else:\n            self.p, rest = getMP(packet)\n            self.g, rest = getMP(rest)\n            self._startEphemeralDH()\n            self.sendPacket(MSG_KEX_DH_GEX_INIT, self.dhSecretKeyPublicMP)\n\n\n    def _continueKEXDH_REPLY(self, ignored, pubKey, f, signature):\n        \"\"\"\n        The host key has been verified, so we generate the keys.\n\n        @param ignored: Ignored.\n\n        @param pubKey: the public key blob for the server's public key.\n        @type pubKey: L{str}\n        @param f: the server's Diffie-Hellman public key.\n        @type f: L{long}\n        @param signature: the server's signature, verifying that it has the\n            correct private key.\n        @type signature: L{str}\n        \"\"\"\n        serverKey = keys.Key.fromString(pubKey)\n        sharedSecret = self._finishEphemeralDH(f)\n        h = sha1()\n        h.update(NS(self.ourVersionString))\n        h.update(NS(self.otherVersionString))\n        h.update(NS(self.ourKexInitPayload))\n        h.update(NS(self.otherKexInitPayload))\n        h.update(NS(pubKey))\n        h.update(self.dhSecretKeyPublicMP)\n        h.update(MP(f))\n        h.update(sharedSecret)\n        exchangeHash = h.digest()\n        if not serverKey.verify(signature, exchangeHash):\n            self.sendDisconnect(DISCONNECT_KEY_EXCHANGE_FAILED,\n                                b'bad signature')\n            return\n        self._keySetup(sharedSecret, exchangeHash)\n\n\n    def ssh_KEX_DH_GEX_REPLY(self, packet):\n        \"\"\"\n        Called when we receive a MSG_KEX_DH_GEX_REPLY message.  Payload::\n            string server host key\n            integer f (server DH public key)\n\n        We verify the host key by calling verifyHostKey, then continue in\n        _continueGEX_REPLY.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n\n        @return: A deferred firing once key exchange is complete.\n        \"\"\"\n        pubKey, packet = getNS(packet)\n        f, packet = getMP(packet)\n        signature, packet = getNS(packet)\n        fingerprint = b':'.join(\n            [binascii.hexlify(c) for c in iterbytes(md5(pubKey).digest())])\n        d = self.verifyHostKey(pubKey, fingerprint)\n        d.addCallback(self._continueGEX_REPLY, pubKey, f, signature)\n        d.addErrback(\n            lambda unused: self.sendDisconnect(\n                DISCONNECT_HOST_KEY_NOT_VERIFIABLE, b'bad host key'))\n        return d\n\n\n    def _continueGEX_REPLY(self, ignored, pubKey, f, signature):\n        \"\"\"\n        The host key has been verified, so we generate the keys.\n\n        @param ignored: Ignored.\n\n        @param pubKey: the public key blob for the server's public key.\n        @type pubKey: L{str}\n        @param f: the server's Diffie-Hellman public key.\n        @type f: L{long}\n        @param signature: the server's signature, verifying that it has the\n            correct private key.\n        @type signature: L{str}\n        \"\"\"\n        serverKey = keys.Key.fromString(pubKey)\n        sharedSecret = self._finishEphemeralDH(f)\n        h = _kex.getHashProcessor(self.kexAlg)()\n        h.update(NS(self.ourVersionString))\n        h.update(NS(self.otherVersionString))\n        h.update(NS(self.ourKexInitPayload))\n        h.update(NS(self.otherKexInitPayload))\n        h.update(NS(pubKey))\n        h.update(struct.pack(\n            '!LLL',\n            self._dhMinimalGroupSize,\n            self._dhPreferredGroupSize,\n            self._dhMaximalGroupSize,\n            ))\n        h.update(MP(self.p))\n        h.update(MP(self.g))\n        h.update(self.dhSecretKeyPublicMP)\n        h.update(MP(f))\n        h.update(sharedSecret)\n        exchangeHash = h.digest()\n        if not serverKey.verify(signature, exchangeHash):\n            self.sendDisconnect(DISCONNECT_KEY_EXCHANGE_FAILED,\n                                b'bad signature')\n            return\n        self._keySetup(sharedSecret, exchangeHash)\n\n\n    def _keySetup(self, sharedSecret, exchangeHash):\n        \"\"\"\n        See SSHTransportBase._keySetup().\n        \"\"\"\n        SSHTransportBase._keySetup(self, sharedSecret, exchangeHash)\n        if self._gotNewKeys:\n            self.ssh_NEWKEYS(b'')\n\n\n    def ssh_NEWKEYS(self, packet):\n        \"\"\"\n        Called when we receive a MSG_NEWKEYS message.  No payload.\n        If we've finished setting up our own keys, start using them.\n        Otherwise, remember that we've received this message.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n        if packet != b'':\n            self.sendDisconnect(DISCONNECT_PROTOCOL_ERROR,\n                                b\"NEWKEYS takes no data\")\n            return\n        if not self.nextEncryptions.encBlockSize:\n            self._gotNewKeys = 1\n            return\n        self._newKeys()\n        self.connectionSecure()\n\n\n    def ssh_SERVICE_ACCEPT(self, packet):\n        \"\"\"\n        Called when we receive a MSG_SERVICE_ACCEPT message.  Payload::\n            string service name\n\n        Start the service we requested.\n\n        @type packet: L{bytes}\n        @param packet: The message data.\n        \"\"\"\n        if packet == b'':\n            log.msg('got SERVICE_ACCEPT without payload')\n        else:\n            name = getNS(packet)[0]\n            if name != self.instance.name:\n                self.sendDisconnect(\n                    DISCONNECT_PROTOCOL_ERROR,\n                    b\"received accept for service we did not request\")\n        self.setService(self.instance)\n\n\n    def requestService(self, instance):\n        \"\"\"\n        Request that a service be run over this transport.\n\n        @type instance: subclass of L{twisted.conch.ssh.service.SSHService}\n        @param instance: The service to run.\n        \"\"\"\n        self.sendPacket(MSG_SERVICE_REQUEST, NS(instance.name))\n        self.instance = instance\n\n    # Client methods\n\n\n    def verifyHostKey(self, hostKey, fingerprint):\n        \"\"\"\n        Returns a Deferred that gets a callback if it is a valid key, or\n        an errback if not.\n\n        @type hostKey: L{bytes}\n        @param hostKey: The host key to verify.\n\n        @type fingerprint: L{bytes}\n        @param fingerprint: The fingerprint of the key.\n\n        @return: A deferred firing with C{True} if the key is valid.\n        \"\"\"\n        return defer.fail(NotImplementedError())\n\n\n    def connectionSecure(self):\n        \"\"\"\n        Called when the encryption has been set up.  Generally,\n        requestService() is called to run another service over the transport.\n        \"\"\"\n        raise NotImplementedError()\n\n\n\nclass _NullEncryptionContext(object):\n    \"\"\"\n    An encryption context that does not actually encrypt anything.\n    \"\"\"\n    def update(self, data):\n        \"\"\"\n        'Encrypt' new data by doing nothing.\n\n        @type data: L{bytes}\n        @param data: The data to 'encrypt'.\n\n        @rtype: L{bytes}\n        @return: The 'encrypted' data.\n        \"\"\"\n        return data\n\n\n\nclass _DummyAlgorithm(object):\n    \"\"\"\n    An encryption algorithm that does not actually encrypt anything.\n    \"\"\"\n    block_size = 64\n\n\n\nclass _DummyCipher(object):\n    \"\"\"\n    A cipher for the none encryption method.\n\n    @ivar block_size: the block size of the encryption.  In the case of the\n    none cipher, this is 8 bytes.\n    \"\"\"\n    algorithm = _DummyAlgorithm()\n\n\n    def encryptor(self):\n        \"\"\"\n        Construct a noop encryptor.\n\n        @return: The encryptor.\n        \"\"\"\n        return _NullEncryptionContext()\n\n\n    def decryptor(self):\n        \"\"\"\n        Construct a noop decryptor.\n\n        @return: The decryptor.\n        \"\"\"\n        return _NullEncryptionContext()\n\n\n\nDH_GENERATOR, DH_PRIME = _kex.getDHGeneratorAndPrime(\n    b'diffie-hellman-group14-sha1')\n\n\nMSG_DISCONNECT = 1\nMSG_IGNORE = 2\nMSG_UNIMPLEMENTED = 3\nMSG_DEBUG = 4\nMSG_SERVICE_REQUEST = 5\nMSG_SERVICE_ACCEPT = 6\nMSG_KEXINIT = 20\nMSG_NEWKEYS = 21\nMSG_KEXDH_INIT = 30\nMSG_KEXDH_REPLY = 31\nMSG_KEX_DH_GEX_REQUEST_OLD = 30\nMSG_KEX_DH_GEX_REQUEST = 34\nMSG_KEX_DH_GEX_GROUP = 31\nMSG_KEX_DH_GEX_INIT = 32\nMSG_KEX_DH_GEX_REPLY = 33\n\n\n\nDISCONNECT_HOST_NOT_ALLOWED_TO_CONNECT = 1\nDISCONNECT_PROTOCOL_ERROR = 2\nDISCONNECT_KEY_EXCHANGE_FAILED = 3\nDISCONNECT_RESERVED = 4\nDISCONNECT_MAC_ERROR = 5\nDISCONNECT_COMPRESSION_ERROR = 6\nDISCONNECT_SERVICE_NOT_AVAILABLE = 7\nDISCONNECT_PROTOCOL_VERSION_NOT_SUPPORTED = 8\nDISCONNECT_HOST_KEY_NOT_VERIFIABLE = 9\nDISCONNECT_CONNECTION_LOST = 10\nDISCONNECT_BY_APPLICATION = 11\nDISCONNECT_TOO_MANY_CONNECTIONS = 12\nDISCONNECT_AUTH_CANCELLED_BY_USER = 13\nDISCONNECT_NO_MORE_AUTH_METHODS_AVAILABLE = 14\nDISCONNECT_ILLEGAL_USER_NAME = 15\n\n\n\nmessages = {}\nfor name, value in list(globals().items()):\n    # Avoid legacy messages which overlap with never ones\n    if name.startswith('MSG_') and not name.startswith('MSG_KEXDH_'):\n        messages[value] = name\n# Check for regressions (#5352)\nif 'MSG_KEXDH_INIT' in messages or 'MSG_KEXDH_REPLY' in messages:\n    raise RuntimeError(\n        \"legacy SSH mnemonics should not end up in messages dict\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ssh/userauth.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_userauth -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nImplementation of the ssh-userauth service.\nCurrently implemented authentication types are public-key and password.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport struct\n\nfrom twisted.conch import error, interfaces\nfrom twisted.conch.ssh import keys, transport, service\nfrom twisted.conch.ssh.common import NS, getNS\nfrom twisted.cred import credentials\nfrom twisted.cred.error import UnauthorizedLogin\nfrom twisted.internet import defer, reactor\nfrom twisted.python import failure, log\nfrom twisted.python.compat import nativeString, _bytesChr as chr\n\n\n\nclass SSHUserAuthServer(service.SSHService):\n    \"\"\"\n    A service implementing the server side of the 'ssh-userauth' service.  It\n    is used to authenticate the user on the other side as being able to access\n    this server.\n\n    @ivar name: the name of this service: 'ssh-userauth'\n    @type name: L{bytes}\n    @ivar authenticatedWith: a list of authentication methods that have\n        already been used.\n    @type authenticatedWith: L{list}\n    @ivar loginTimeout: the number of seconds we wait before disconnecting\n        the user for taking too long to authenticate\n    @type loginTimeout: L{int}\n    @ivar attemptsBeforeDisconnect: the number of failed login attempts we\n        allow before disconnecting.\n    @type attemptsBeforeDisconnect: L{int}\n    @ivar loginAttempts: the number of login attempts that have been made\n    @type loginAttempts: L{int}\n    @ivar passwordDelay: the number of seconds to delay when the user gives\n        an incorrect password\n    @type passwordDelay: L{int}\n    @ivar interfaceToMethod: a L{dict} mapping credential interfaces to\n        authentication methods.  The server checks to see which of the\n        cred interfaces have checkers and tells the client that those methods\n        are valid for authentication.\n    @type interfaceToMethod: L{dict}\n    @ivar supportedAuthentications: A list of the supported authentication\n        methods.\n    @type supportedAuthentications: L{list} of L{bytes}\n    @ivar user: the last username the client tried to authenticate with\n    @type user: L{bytes}\n    @ivar method: the current authentication method\n    @type method: L{bytes}\n    @ivar nextService: the service the user wants started after authentication\n        has been completed.\n    @type nextService: L{bytes}\n    @ivar portal: the L{twisted.cred.portal.Portal} we are using for\n        authentication\n    @type portal: L{twisted.cred.portal.Portal}\n    @ivar clock: an object with a callLater method.  Stubbed out for testing.\n    \"\"\"\n\n    name = b'ssh-userauth'\n    loginTimeout = 10 * 60 * 60\n    # 10 minutes before we disconnect them\n    attemptsBeforeDisconnect = 20\n    # 20 login attempts before a disconnect\n    passwordDelay = 1 # number of seconds to delay on a failed password\n    clock = reactor\n    interfaceToMethod = {\n        credentials.ISSHPrivateKey : b'publickey',\n        credentials.IUsernamePassword : b'password',\n    }\n\n\n    def serviceStarted(self):\n        \"\"\"\n        Called when the userauth service is started.  Set up instance\n        variables, check if we should allow password authentication (only\n        allow if the outgoing connection is encrypted) and set up a login\n        timeout.\n        \"\"\"\n        self.authenticatedWith = []\n        self.loginAttempts = 0\n        self.user = None\n        self.nextService = None\n        self.portal = self.transport.factory.portal\n\n        self.supportedAuthentications = []\n        for i in self.portal.listCredentialsInterfaces():\n            if i in self.interfaceToMethod:\n                self.supportedAuthentications.append(self.interfaceToMethod[i])\n\n        if not self.transport.isEncrypted('in'):\n            # don't let us transport password in plaintext\n            if b'password' in self.supportedAuthentications:\n                self.supportedAuthentications.remove(b'password')\n        self._cancelLoginTimeout = self.clock.callLater(\n            self.loginTimeout,\n            self.timeoutAuthentication)\n\n\n    def serviceStopped(self):\n        \"\"\"\n        Called when the userauth service is stopped.  Cancel the login timeout\n        if it's still going.\n        \"\"\"\n        if self._cancelLoginTimeout:\n            self._cancelLoginTimeout.cancel()\n            self._cancelLoginTimeout = None\n\n\n    def timeoutAuthentication(self):\n        \"\"\"\n        Called when the user has timed out on authentication.  Disconnect\n        with a DISCONNECT_NO_MORE_AUTH_METHODS_AVAILABLE message.\n        \"\"\"\n        self._cancelLoginTimeout = None\n        self.transport.sendDisconnect(\n            transport.DISCONNECT_NO_MORE_AUTH_METHODS_AVAILABLE,\n            b'you took too long')\n\n\n    def tryAuth(self, kind, user, data):\n        \"\"\"\n        Try to authenticate the user with the given method.  Dispatches to a\n        auth_* method.\n\n        @param kind: the authentication method to try.\n        @type kind: L{bytes}\n        @param user: the username the client is authenticating with.\n        @type user: L{bytes}\n        @param data: authentication specific data sent by the client.\n        @type data: L{bytes}\n        @return: A Deferred called back if the method succeeded, or erred back\n            if it failed.\n        @rtype: C{defer.Deferred}\n        \"\"\"\n        log.msg('%r trying auth %r' % (user, kind))\n        if kind not in self.supportedAuthentications:\n            return defer.fail(\n                    error.ConchError('unsupported authentication, failing'))\n        kind = nativeString(kind.replace(b'-', b'_'))\n        f = getattr(self, 'auth_%s' % (kind,), None)\n        if f:\n            ret = f(data)\n            if not ret:\n                return defer.fail(\n                        error.ConchError(\n                            '%s return None instead of a Deferred'\n                            % (kind, )))\n            else:\n                return ret\n        return defer.fail(error.ConchError('bad auth type: %s' % (kind,)))\n\n\n    def ssh_USERAUTH_REQUEST(self, packet):\n        \"\"\"\n        The client has requested authentication.  Payload::\n            string user\n            string next service\n            string method\n            <authentication specific data>\n\n        @type packet: L{bytes}\n        \"\"\"\n        user, nextService, method, rest = getNS(packet, 3)\n        if user != self.user or nextService != self.nextService:\n            self.authenticatedWith = [] # clear auth state\n        self.user = user\n        self.nextService = nextService\n        self.method = method\n        d = self.tryAuth(method, user, rest)\n        if not d:\n            self._ebBadAuth(\n                failure.Failure(error.ConchError('auth returned none')))\n            return\n        d.addCallback(self._cbFinishedAuth)\n        d.addErrback(self._ebMaybeBadAuth)\n        d.addErrback(self._ebBadAuth)\n        return d\n\n\n    def _cbFinishedAuth(self, result):\n        \"\"\"\n        The callback when user has successfully been authenticated.  For a\n        description of the arguments, see L{twisted.cred.portal.Portal.login}.\n        We start the service requested by the user.\n        \"\"\"\n        (interface, avatar, logout) = result\n        self.transport.avatar = avatar\n        self.transport.logoutFunction = logout\n        service = self.transport.factory.getService(self.transport,\n                self.nextService)\n        if not service:\n            raise error.ConchError('could not get next service: %s'\n                                  % self.nextService)\n        log.msg('%r authenticated with %r' % (self.user, self.method))\n        self.transport.sendPacket(MSG_USERAUTH_SUCCESS, b'')\n        self.transport.setService(service())\n\n\n    def _ebMaybeBadAuth(self, reason):\n        \"\"\"\n        An intermediate errback.  If the reason is\n        error.NotEnoughAuthentication, we send a MSG_USERAUTH_FAILURE, but\n        with the partial success indicator set.\n\n        @type reason: L{twisted.python.failure.Failure}\n        \"\"\"\n        reason.trap(error.NotEnoughAuthentication)\n        self.transport.sendPacket(MSG_USERAUTH_FAILURE,\n                NS(b','.join(self.supportedAuthentications)) + b'\\xff')\n\n\n    def _ebBadAuth(self, reason):\n        \"\"\"\n        The final errback in the authentication chain.  If the reason is\n        error.IgnoreAuthentication, we simply return; the authentication\n        method has sent its own response.  Otherwise, send a failure message\n        and (if the method is not 'none') increment the number of login\n        attempts.\n\n        @type reason: L{twisted.python.failure.Failure}\n        \"\"\"\n        if reason.check(error.IgnoreAuthentication):\n            return\n        if self.method != b'none':\n            log.msg('%r failed auth %r' % (self.user, self.method))\n            if reason.check(UnauthorizedLogin):\n                log.msg('unauthorized login: %s' % reason.getErrorMessage())\n            elif reason.check(error.ConchError):\n                log.msg('reason: %s' % reason.getErrorMessage())\n            else:\n                log.msg(reason.getTraceback())\n            self.loginAttempts += 1\n            if self.loginAttempts > self.attemptsBeforeDisconnect:\n                self.transport.sendDisconnect(\n                        transport.DISCONNECT_NO_MORE_AUTH_METHODS_AVAILABLE,\n                        b'too many bad auths')\n                return\n        self.transport.sendPacket(\n                MSG_USERAUTH_FAILURE,\n                NS(b','.join(self.supportedAuthentications)) + b'\\x00')\n\n\n    def auth_publickey(self, packet):\n        \"\"\"\n        Public key authentication.  Payload::\n            byte has signature\n            string algorithm name\n            string key blob\n            [string signature] (if has signature is True)\n\n        Create a SSHPublicKey credential and verify it using our portal.\n        \"\"\"\n        hasSig = ord(packet[0:1])\n        algName, blob, rest = getNS(packet[1:], 2)\n\n        try:\n            pubKey = keys.Key.fromString(blob)\n        except keys.BadKeyError:\n            error = \"Unsupported key type %s or bad key\" % (\n                algName.decode('ascii'),)\n            log.msg(error)\n            return defer.fail(UnauthorizedLogin(error))\n\n        signature = hasSig and getNS(rest)[0] or None\n        if hasSig:\n            b = (NS(self.transport.sessionID) + chr(MSG_USERAUTH_REQUEST) +\n                NS(self.user) + NS(self.nextService) + NS(b'publickey') +\n                chr(hasSig) +  NS(pubKey.sshType()) + NS(blob))\n            c = credentials.SSHPrivateKey(self.user, algName, blob, b,\n                    signature)\n            return self.portal.login(c, None, interfaces.IConchUser)\n        else:\n            c = credentials.SSHPrivateKey(self.user, algName, blob, None, None)\n            return self.portal.login(c, None,\n                    interfaces.IConchUser).addErrback(self._ebCheckKey,\n                            packet[1:])\n\n\n    def _ebCheckKey(self, reason, packet):\n        \"\"\"\n        Called back if the user did not sent a signature.  If reason is\n        error.ValidPublicKey then this key is valid for the user to\n        authenticate with.  Send MSG_USERAUTH_PK_OK.\n        \"\"\"\n        reason.trap(error.ValidPublicKey)\n        # if we make it here, it means that the publickey is valid\n        self.transport.sendPacket(MSG_USERAUTH_PK_OK, packet)\n        return failure.Failure(error.IgnoreAuthentication())\n\n\n    def auth_password(self, packet):\n        \"\"\"\n        Password authentication.  Payload::\n            string password\n\n        Make a UsernamePassword credential and verify it with our portal.\n        \"\"\"\n        password = getNS(packet[1:])[0]\n        c = credentials.UsernamePassword(self.user, password)\n        return self.portal.login(c, None, interfaces.IConchUser).addErrback(\n                                                        self._ebPassword)\n\n\n    def _ebPassword(self, f):\n        \"\"\"\n        If the password is invalid, wait before sending the failure in order\n        to delay brute-force password guessing.\n        \"\"\"\n        d = defer.Deferred()\n        self.clock.callLater(self.passwordDelay, d.callback, f)\n        return d\n\n\n\nclass SSHUserAuthClient(service.SSHService):\n    \"\"\"\n    A service implementing the client side of 'ssh-userauth'.\n\n    This service will try all authentication methods provided by the server,\n    making callbacks for more information when necessary.\n\n    @ivar name: the name of this service: 'ssh-userauth'\n    @type name: L{str}\n    @ivar preferredOrder: a list of authentication methods that should be used\n        first, in order of preference, if supported by the server\n    @type preferredOrder: L{list}\n    @ivar user: the name of the user to authenticate as\n    @type user: L{bytes}\n    @ivar instance: the service to start after authentication has finished\n    @type instance: L{service.SSHService}\n    @ivar authenticatedWith: a list of strings of authentication methods we've tried\n    @type authenticatedWith: L{list} of L{bytes}\n    @ivar triedPublicKeys: a list of public key objects that we've tried to\n        authenticate with\n    @type triedPublicKeys: L{list} of L{Key}\n    @ivar lastPublicKey: the last public key object we've tried to authenticate\n        with\n    @type lastPublicKey: L{Key}\n    \"\"\"\n\n    name = b'ssh-userauth'\n    preferredOrder = [b'publickey', b'password', b'keyboard-interactive']\n\n\n    def __init__(self, user, instance):\n        self.user = user\n        self.instance = instance\n\n\n    def serviceStarted(self):\n        self.authenticatedWith = []\n        self.triedPublicKeys = []\n        self.lastPublicKey = None\n        self.askForAuth(b'none', b'')\n\n\n    def askForAuth(self, kind, extraData):\n        \"\"\"\n        Send a MSG_USERAUTH_REQUEST.\n\n        @param kind: the authentication method to try.\n        @type kind: L{bytes}\n        @param extraData: method-specific data to go in the packet\n        @type extraData: L{bytes}\n        \"\"\"\n        self.lastAuth = kind\n        self.transport.sendPacket(MSG_USERAUTH_REQUEST, NS(self.user) +\n                NS(self.instance.name) + NS(kind) + extraData)\n\n\n    def tryAuth(self, kind):\n        \"\"\"\n        Dispatch to an authentication method.\n\n        @param kind: the authentication method\n        @type kind: L{bytes}\n        \"\"\"\n        kind = nativeString(kind.replace(b'-', b'_'))\n        log.msg('trying to auth with %s' % (kind,))\n        f = getattr(self,'auth_%s' % (kind,), None)\n        if f:\n            return f()\n\n\n    def _ebAuth(self, ignored, *args):\n        \"\"\"\n        Generic callback for a failed authentication attempt.  Respond by\n        asking for the list of accepted methods (the 'none' method)\n        \"\"\"\n        self.askForAuth(b'none', b'')\n\n\n    def ssh_USERAUTH_SUCCESS(self, packet):\n        \"\"\"\n        We received a MSG_USERAUTH_SUCCESS.  The server has accepted our\n        authentication, so start the next service.\n        \"\"\"\n        self.transport.setService(self.instance)\n\n\n    def ssh_USERAUTH_FAILURE(self, packet):\n        \"\"\"\n        We received a MSG_USERAUTH_FAILURE.  Payload::\n            string methods\n            byte partial success\n\n        If partial success is C{True}, then the previous method succeeded but is\n        not sufficient for authentication. C{methods} is a comma-separated list\n        of accepted authentication methods.\n\n        We sort the list of methods by their position in C{self.preferredOrder},\n        removing methods that have already succeeded. We then call\n        C{self.tryAuth} with the most preferred method.\n\n        @param packet: the C{MSG_USERAUTH_FAILURE} payload.\n        @type packet: L{bytes}\n\n        @return: a L{defer.Deferred} that will be callbacked with L{None} as\n            soon as all authentication methods have been tried, or L{None} if no\n            more authentication methods are available.\n        @rtype: C{defer.Deferred} or L{None}\n        \"\"\"\n        canContinue, partial = getNS(packet)\n        partial = ord(partial)\n        if partial:\n            self.authenticatedWith.append(self.lastAuth)\n\n        def orderByPreference(meth):\n            \"\"\"\n            Invoked once per authentication method in order to extract a\n            comparison key which is then used for sorting.\n\n            @param meth: the authentication method.\n            @type meth: L{bytes}\n\n            @return: the comparison key for C{meth}.\n            @rtype: L{int}\n            \"\"\"\n            if meth in self.preferredOrder:\n                return self.preferredOrder.index(meth)\n            else:\n                # put the element at the end of the list.\n                return len(self.preferredOrder)\n\n        canContinue = sorted([meth for meth in canContinue.split(b',')\n                              if meth not in self.authenticatedWith],\n                             key=orderByPreference)\n\n        log.msg('can continue with: %s' % canContinue)\n        return self._cbUserauthFailure(None, iter(canContinue))\n\n\n    def _cbUserauthFailure(self, result, iterator):\n        if result:\n            return\n        try:\n            method = next(iterator)\n        except StopIteration:\n            self.transport.sendDisconnect(\n                transport.DISCONNECT_NO_MORE_AUTH_METHODS_AVAILABLE,\n                b'no more authentication methods available')\n        else:\n            d = defer.maybeDeferred(self.tryAuth, method)\n            d.addCallback(self._cbUserauthFailure, iterator)\n            return d\n\n\n    def ssh_USERAUTH_PK_OK(self, packet):\n        \"\"\"\n        This message (number 60) can mean several different messages depending\n        on the current authentication type.  We dispatch to individual methods\n        in order to handle this request.\n        \"\"\"\n        func = getattr(self, 'ssh_USERAUTH_PK_OK_%s' %\n                       nativeString(self.lastAuth.replace(b'-', b'_')), None)\n        if func is not None:\n            return func(packet)\n        else:\n            self.askForAuth(b'none', b'')\n\n\n    def ssh_USERAUTH_PK_OK_publickey(self, packet):\n        \"\"\"\n        This is MSG_USERAUTH_PK.  Our public key is valid, so we create a\n        signature and try to authenticate with it.\n        \"\"\"\n        publicKey = self.lastPublicKey\n        b = (NS(self.transport.sessionID) + chr(MSG_USERAUTH_REQUEST) +\n             NS(self.user) + NS(self.instance.name) + NS(b'publickey') +\n             b'\\x01' + NS(publicKey.sshType()) + NS(publicKey.blob()))\n        d  = self.signData(publicKey, b)\n        if not d:\n            self.askForAuth(b'none', b'')\n            # this will fail, we'll move on\n            return\n        d.addCallback(self._cbSignedData)\n        d.addErrback(self._ebAuth)\n\n\n    def ssh_USERAUTH_PK_OK_password(self, packet):\n        \"\"\"\n        This is MSG_USERAUTH_PASSWD_CHANGEREQ.  The password given has expired.\n        We ask for an old password and a new password, then send both back to\n        the server.\n        \"\"\"\n        prompt, language, rest = getNS(packet, 2)\n        self._oldPass = self._newPass = None\n        d = self.getPassword(b'Old Password: ')\n        d = d.addCallbacks(self._setOldPass, self._ebAuth)\n        d.addCallback(lambda ignored: self.getPassword(prompt))\n        d.addCallbacks(self._setNewPass, self._ebAuth)\n\n\n    def ssh_USERAUTH_PK_OK_keyboard_interactive(self, packet):\n        \"\"\"\n        This is MSG_USERAUTH_INFO_RESPONSE.  The server has sent us the\n        questions it wants us to answer, so we ask the user and sent the\n        responses.\n        \"\"\"\n        name, instruction, lang, data = getNS(packet, 3)\n        numPrompts = struct.unpack('!L', data[:4])[0]\n        data = data[4:]\n        prompts = []\n        for i in range(numPrompts):\n            prompt, data = getNS(data)\n            echo = bool(ord(data[0:1]))\n            data = data[1:]\n            prompts.append((prompt, echo))\n        d = self.getGenericAnswers(name, instruction, prompts)\n        d.addCallback(self._cbGenericAnswers)\n        d.addErrback(self._ebAuth)\n\n\n    def _cbSignedData(self, signedData):\n        \"\"\"\n        Called back out of self.signData with the signed data.  Send the\n        authentication request with the signature.\n\n        @param signedData: the data signed by the user's private key.\n        @type signedData: L{bytes}\n        \"\"\"\n        publicKey = self.lastPublicKey\n        self.askForAuth(b'publickey', b'\\x01' + NS(publicKey.sshType()) +\n                NS(publicKey.blob()) + NS(signedData))\n\n\n    def _setOldPass(self, op):\n        \"\"\"\n        Called back when we are choosing a new password.  Simply store the old\n        password for now.\n\n        @param op: the old password as entered by the user\n        @type op: L{bytes}\n        \"\"\"\n        self._oldPass = op\n\n\n    def _setNewPass(self, np):\n        \"\"\"\n        Called back when we are choosing a new password.  Get the old password\n        and send the authentication message with both.\n\n        @param np: the new password as entered by the user\n        @type np: L{bytes}\n        \"\"\"\n        op = self._oldPass\n        self._oldPass = None\n        self.askForAuth(b'password', b'\\xff' + NS(op) + NS(np))\n\n\n    def _cbGenericAnswers(self, responses):\n        \"\"\"\n        Called back when we are finished answering keyboard-interactive\n        questions.  Send the info back to the server in a\n        MSG_USERAUTH_INFO_RESPONSE.\n\n        @param responses: a list of L{bytes} responses\n        @type responses: L{list}\n        \"\"\"\n        data = struct.pack('!L', len(responses))\n        for r in responses:\n            data += NS(r.encode('UTF8'))\n        self.transport.sendPacket(MSG_USERAUTH_INFO_RESPONSE, data)\n\n\n    def auth_publickey(self):\n        \"\"\"\n        Try to authenticate with a public key.  Ask the user for a public key;\n        if the user has one, send the request to the server and return True.\n        Otherwise, return False.\n\n        @rtype: L{bool}\n        \"\"\"\n        d = defer.maybeDeferred(self.getPublicKey)\n        d.addBoth(self._cbGetPublicKey)\n        return d\n\n\n    def _cbGetPublicKey(self, publicKey):\n        if not isinstance(publicKey, keys.Key): # failure or None\n            publicKey = None\n        if publicKey is not None:\n            self.lastPublicKey = publicKey\n            self.triedPublicKeys.append(publicKey)\n            log.msg('using key of type %s' % publicKey.type())\n            self.askForAuth(b'publickey', b'\\x00' + NS(publicKey.sshType()) +\n                            NS(publicKey.blob()))\n            return True\n        else:\n            return False\n\n\n    def auth_password(self):\n        \"\"\"\n        Try to authenticate with a password.  Ask the user for a password.\n        If the user will return a password, return True.  Otherwise, return\n        False.\n\n        @rtype: L{bool}\n        \"\"\"\n        d = self.getPassword()\n        if d:\n            d.addCallbacks(self._cbPassword, self._ebAuth)\n            return True\n        else: # returned None, don't do password auth\n            return False\n\n\n    def auth_keyboard_interactive(self):\n        \"\"\"\n        Try to authenticate with keyboard-interactive authentication.  Send\n        the request to the server and return True.\n\n        @rtype: L{bool}\n        \"\"\"\n        log.msg('authing with keyboard-interactive')\n        self.askForAuth(b'keyboard-interactive', NS(b'') + NS(b''))\n        return True\n\n\n    def _cbPassword(self, password):\n        \"\"\"\n        Called back when the user gives a password.  Send the request to the\n        server.\n\n        @param password: the password the user entered\n        @type password: L{bytes}\n        \"\"\"\n        self.askForAuth(b'password', b'\\x00' + NS(password))\n\n\n    def signData(self, publicKey, signData):\n        \"\"\"\n        Sign the given data with the given public key.\n\n        By default, this will call getPrivateKey to get the private key,\n        then sign the data using Key.sign().\n\n        This method is factored out so that it can be overridden to use\n        alternate methods, such as a key agent.\n\n        @param publicKey: The public key object returned from L{getPublicKey}\n        @type publicKey: L{keys.Key}\n\n        @param signData: the data to be signed by the private key.\n        @type signData: L{bytes}\n        @return: a Deferred that's called back with the signature\n        @rtype: L{defer.Deferred}\n        \"\"\"\n        key = self.getPrivateKey()\n        if not key:\n            return\n        return key.addCallback(self._cbSignData, signData)\n\n\n    def _cbSignData(self, privateKey, signData):\n        \"\"\"\n        Called back when the private key is returned.  Sign the data and\n        return the signature.\n\n        @param privateKey: the private key object\n        @type publicKey: L{keys.Key}\n        @param signData: the data to be signed by the private key.\n        @type signData: L{bytes}\n        @return: the signature\n        @rtype: L{bytes}\n        \"\"\"\n        return privateKey.sign(signData)\n\n\n    def getPublicKey(self):\n        \"\"\"\n        Return a public key for the user.  If no more public keys are\n        available, return L{None}.\n\n        This implementation always returns L{None}.  Override it in a\n        subclass to actually find and return a public key object.\n\n        @rtype: L{Key} or L{None}\n        \"\"\"\n        return None\n\n\n    def getPrivateKey(self):\n        \"\"\"\n        Return a L{Deferred} that will be called back with the private key\n        object corresponding to the last public key from getPublicKey().\n        If the private key is not available, errback on the Deferred.\n\n        @rtype: L{Deferred} called back with L{Key}\n        \"\"\"\n        return defer.fail(NotImplementedError())\n\n\n    def getPassword(self, prompt = None):\n        \"\"\"\n        Return a L{Deferred} that will be called back with a password.\n        prompt is a string to display for the password, or None for a generic\n        'user@hostname's password: '.\n\n        @type prompt: L{bytes}/L{None}\n        @rtype: L{defer.Deferred}\n        \"\"\"\n        return defer.fail(NotImplementedError())\n\n\n    def getGenericAnswers(self, name, instruction, prompts):\n        \"\"\"\n        Returns a L{Deferred} with the responses to the promopts.\n\n        @param name: The name of the authentication currently in progress.\n        @param instruction: Describes what the authentication wants.\n        @param prompts: A list of (prompt, echo) pairs, where prompt is a\n        string to display and echo is a boolean indicating whether the\n        user's response should be echoed as they type it.\n        \"\"\"\n        return defer.fail(NotImplementedError())\n\n\nMSG_USERAUTH_REQUEST          = 50\nMSG_USERAUTH_FAILURE          = 51\nMSG_USERAUTH_SUCCESS          = 52\nMSG_USERAUTH_BANNER           = 53\nMSG_USERAUTH_INFO_RESPONSE    = 61\nMSG_USERAUTH_PK_OK            = 60\n\nmessages = {}\nfor k, v in list(locals().items()):\n    if k[:4] == 'MSG_':\n        messages[v] = k\n\nSSHUserAuthServer.protocolMessages = messages\nSSHUserAuthClient.protocolMessages = messages\ndel messages\ndel v\n\n# Doubles, not included in the protocols' mappings\nMSG_USERAUTH_PASSWD_CHANGEREQ = 60\nMSG_USERAUTH_INFO_REQUEST     = 60\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/stdio.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_manhole -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAsynchronous local terminal input handling\n\n@author: Jp Calderone\n\"\"\"\n\nimport os, tty, sys, termios\n\nfrom twisted.internet import reactor, stdio, protocol, defer\nfrom twisted.python import failure, reflect, log\n\nfrom twisted.conch.insults.insults import ServerProtocol\nfrom twisted.conch.manhole import ColoredManhole\n\nclass UnexpectedOutputError(Exception):\n    pass\n\n\n\nclass TerminalProcessProtocol(protocol.ProcessProtocol):\n    def __init__(self, proto):\n        self.proto = proto\n        self.onConnection = defer.Deferred()\n\n\n    def connectionMade(self):\n        self.proto.makeConnection(self)\n        self.onConnection.callback(None)\n        self.onConnection = None\n\n\n    def write(self, data):\n        \"\"\"\n        Write to the terminal.\n\n        @param data: Data to write.\n        @type data: L{bytes}\n        \"\"\"\n        self.transport.write(data)\n\n\n    def outReceived(self, data):\n        \"\"\"\n        Receive data from the terminal.\n\n        @param data: Data received.\n        @type data: L{bytes}\n        \"\"\"\n        self.proto.dataReceived(data)\n\n\n    def errReceived(self, data):\n        \"\"\"\n        Report an error.\n\n        @param data: Data to include in L{Failure}.\n        @type data: L{bytes}\n        \"\"\"\n        self.transport.loseConnection()\n        if self.proto is not None:\n            self.proto.connectionLost(failure.Failure(UnexpectedOutputError(data)))\n            self.proto = None\n\n\n    def childConnectionLost(self, childFD):\n        if self.proto is not None:\n            self.proto.childConnectionLost(childFD)\n\n\n    def processEnded(self, reason):\n        if self.proto is not None:\n            self.proto.connectionLost(reason)\n            self.proto = None\n\n\n\nclass ConsoleManhole(ColoredManhole):\n    \"\"\"\n    A manhole protocol specifically for use with L{stdio.StandardIO}.\n    \"\"\"\n    def connectionLost(self, reason):\n        \"\"\"\n        When the connection is lost, there is nothing more to do.  Stop the\n        reactor so that the process can exit.\n        \"\"\"\n        reactor.stop()\n\n\n\ndef runWithProtocol(klass):\n    fd = sys.__stdin__.fileno()\n    oldSettings = termios.tcgetattr(fd)\n    tty.setraw(fd)\n    try:\n        stdio.StandardIO(ServerProtocol(klass))\n        reactor.run()\n    finally:\n        termios.tcsetattr(fd, termios.TCSANOW, oldSettings)\n        os.write(fd, b\"\\r\\x1bc\\r\")\n\n\n\ndef main(argv=None):\n    log.startLogging(open('child.log', 'w'))\n\n    if argv is None:\n        argv = sys.argv[1:]\n    if argv:\n        klass = reflect.namedClass(argv[0])\n    else:\n        klass = ConsoleManhole\n    runWithProtocol(klass)\n\n\nif __name__ == '__main__':\n    main()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/tap.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_tap -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nSupport module for making SSH servers with twistd.\n\"\"\"\n\nfrom twisted.conch import unix\nfrom twisted.conch import checkers as conch_checkers\nfrom twisted.conch.openssh_compat import factory\nfrom twisted.cred import portal, strcred\nfrom twisted.python import usage\nfrom twisted.application import strports\n\n\nclass Options(usage.Options, strcred.AuthOptionMixin):\n    synopsis = \"[-i <interface>] [-p <port>] [-d <dir>] \"\n    longdesc = (\"Makes a Conch SSH server.  If no authentication methods are \"\n        \"specified, the default authentication methods are UNIX passwords \"\n        \"and SSH public keys.  If --auth options are \"\n        \"passed, only the measures specified will be used.\")\n    optParameters = [\n        [\"interface\", \"i\", \"\", \"local interface to which we listen\"],\n        [\"port\", \"p\", \"tcp:22\", \"Port on which to listen\"],\n        [\"data\", \"d\", \"/etc\", \"directory to look for host keys in\"],\n        [\"moduli\", \"\", None, \"directory to look for moduli in \"\n            \"(if different from --data)\"]\n    ]\n    compData = usage.Completions(\n        optActions={\"data\": usage.CompleteDirs(descr=\"data directory\"),\n                    \"moduli\": usage.CompleteDirs(descr=\"moduli directory\"),\n                    \"interface\": usage.CompleteNetInterfaces()}\n        )\n\n\n    def __init__(self, *a, **kw):\n        usage.Options.__init__(self, *a, **kw)\n\n        # Call the default addCheckers (for backwards compatibility) that will\n        # be used if no --auth option is provided - note that conch's\n        # UNIXPasswordDatabase is used, instead of twisted.plugins.cred_unix's\n        # checker\n        super(Options, self).addChecker(conch_checkers.UNIXPasswordDatabase())\n        super(Options, self).addChecker(conch_checkers.SSHPublicKeyChecker(\n            conch_checkers.UNIXAuthorizedKeysFiles()))\n        self._usingDefaultAuth = True\n\n\n    def addChecker(self, checker):\n        \"\"\"\n        Add the checker specified.  If any checkers are added, the default\n        checkers are automatically cleared and the only checkers will be the\n        specified one(s).\n        \"\"\"\n        if self._usingDefaultAuth:\n            self['credCheckers'] = []\n            self['credInterfaces'] = {}\n            self._usingDefaultAuth = False\n        super(Options, self).addChecker(checker)\n\n\n\ndef makeService(config):\n    \"\"\"\n    Construct a service for operating a SSH server.\n\n    @param config: An L{Options} instance specifying server options, including\n        where server keys are stored and what authentication methods to use.\n\n    @return: A L{twisted.application.service.IService} provider which contains\n        the requested SSH server.\n    \"\"\"\n\n    t = factory.OpenSSHFactory()\n\n    r = unix.UnixSSHRealm()\n    t.portal = portal.Portal(r, config.get('credCheckers', []))\n    t.dataRoot = config['data']\n    t.moduliRoot = config['moduli'] or config['data']\n\n    port = config['port']\n    if config['interface']:\n        # Add warning here\n        port += ':interface=' + config['interface']\n    return strports.service(port, t)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/telnet.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_telnet -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTelnet protocol implementation.\n\n@author: Jean-Paul Calderone\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport struct\n\nfrom zope.interface import implementer\n\nfrom twisted.internet import protocol, interfaces as iinternet, defer\nfrom twisted.python import log\nfrom twisted.python.compat import _bytesChr as chr, iterbytes\n\nMODE = chr(1)\nEDIT = 1\nTRAPSIG = 2\nMODE_ACK = 4\nSOFT_TAB = 8\nLIT_ECHO = 16\n\n# Characters gleaned from the various (and conflicting) RFCs.  Not all of these are correct.\n\nNULL =           chr(0)   # No operation.\nBEL =            chr(7)   # Produces an audible or\n                          # visible signal (which does\n                          # NOT move the print head).\nBS =             chr(8)   # Moves the print head one\n                          # character position towards\n                          # the left margin.\nHT =             chr(9)   # Moves the printer to the\n                          # next horizontal tab stop.\n                          # It remains unspecified how\n                          # either party determines or\n                          # establishes where such tab\n                          # stops are located.\nLF =             chr(10)  # Moves the printer to the\n                          # next print line, keeping the\n                          # same horizontal position.\nVT =             chr(11)  # Moves the printer to the\n                          # next vertical tab stop.  It\n                          # remains unspecified how\n                          # either party determines or\n                          # establishes where such tab\n                          # stops are located.\nFF =             chr(12)  # Moves the printer to the top\n                          # of the next page, keeping\n                          # the same horizontal position.\nCR =             chr(13)  # Moves the printer to the left\n                          # margin of the current line.\n\nECHO  =          chr(1)   # User-to-Server:  Asks the server to send\n                          # Echos of the transmitted data.\nSGA =            chr(3)   # Suppress Go Ahead.  Go Ahead is silly\n                          # and most modern servers should suppress\n                          # it.\nNAWS =           chr(31)  # Negotiate About Window Size.  Indicate that\n                          # information about the size of the terminal\n                          # can be communicated.\nLINEMODE =       chr(34)  # Allow line buffering to be\n                          # negotiated about.\n\nSE =             chr(240) # End of subnegotiation parameters.\nNOP =            chr(241) # No operation.\nDM =             chr(242) # \"Data Mark\": The data stream portion\n                          # of a Synch.  This should always be\n                          # accompanied by a TCP Urgent\n                          # notification.\nBRK =            chr(243) # NVT character Break.\nIP =             chr(244) # The function Interrupt Process.\nAO =             chr(245) # The function Abort Output\nAYT =            chr(246) # The function Are You There.\nEC =             chr(247) # The function Erase Character.\nEL =             chr(248) # The function Erase Line\nGA =             chr(249) # The Go Ahead signal.\nSB =             chr(250) # Indicates that what follows is\n                          # subnegotiation of the indicated\n                          # option.\nWILL =           chr(251) # Indicates the desire to begin\n                          # performing, or confirmation that\n                          # you are now performing, the\n                          # indicated option.\nWONT =           chr(252) # Indicates the refusal to perform,\n                          # or continue performing, the\n                          # indicated option.\nDO =             chr(253) # Indicates the request that the\n                          # other party perform, or\n                          # confirmation that you are expecting\n                          # the other party to perform, the\n                          # indicated option.\nDONT =           chr(254) # Indicates the demand that the\n                          # other party stop performing,\n                          # or confirmation that you are no\n                          # longer expecting the other party\n                          # to perform, the indicated option.\nIAC =            chr(255) # Data Byte 255.  Introduces a\n                          # telnet command.\n\nLINEMODE_MODE = chr(1)\nLINEMODE_EDIT = chr(1)\nLINEMODE_TRAPSIG = chr(2)\nLINEMODE_MODE_ACK = chr(4)\nLINEMODE_SOFT_TAB = chr(8)\nLINEMODE_LIT_ECHO = chr(16)\nLINEMODE_FORWARDMASK = chr(2)\nLINEMODE_SLC = chr(3)\nLINEMODE_SLC_SYNCH = chr(1)\nLINEMODE_SLC_BRK = chr(2)\nLINEMODE_SLC_IP = chr(3)\nLINEMODE_SLC_AO = chr(4)\nLINEMODE_SLC_AYT = chr(5)\nLINEMODE_SLC_EOR = chr(6)\nLINEMODE_SLC_ABORT = chr(7)\nLINEMODE_SLC_EOF = chr(8)\nLINEMODE_SLC_SUSP = chr(9)\nLINEMODE_SLC_EC = chr(10)\nLINEMODE_SLC_EL = chr(11)\n\nLINEMODE_SLC_EW = chr(12)\nLINEMODE_SLC_RP = chr(13)\nLINEMODE_SLC_LNEXT = chr(14)\nLINEMODE_SLC_XON = chr(15)\nLINEMODE_SLC_XOFF = chr(16)\nLINEMODE_SLC_FORW1 = chr(17)\nLINEMODE_SLC_FORW2 = chr(18)\nLINEMODE_SLC_MCL = chr(19)\nLINEMODE_SLC_MCR = chr(20)\nLINEMODE_SLC_MCWL = chr(21)\nLINEMODE_SLC_MCWR = chr(22)\nLINEMODE_SLC_MCBOL = chr(23)\nLINEMODE_SLC_MCEOL = chr(24)\nLINEMODE_SLC_INSRT = chr(25)\nLINEMODE_SLC_OVER = chr(26)\nLINEMODE_SLC_ECR = chr(27)\nLINEMODE_SLC_EWR = chr(28)\nLINEMODE_SLC_EBOL = chr(29)\nLINEMODE_SLC_EEOL = chr(30)\n\nLINEMODE_SLC_DEFAULT = chr(3)\nLINEMODE_SLC_VALUE = chr(2)\nLINEMODE_SLC_CANTCHANGE = chr(1)\nLINEMODE_SLC_NOSUPPORT = chr(0)\nLINEMODE_SLC_LEVELBITS = chr(3)\n\nLINEMODE_SLC_ACK = chr(128)\nLINEMODE_SLC_FLUSHIN = chr(64)\nLINEMODE_SLC_FLUSHOUT = chr(32)\nLINEMODE_EOF = chr(236)\nLINEMODE_SUSP = chr(237)\nLINEMODE_ABORT = chr(238)\n\nclass ITelnetProtocol(iinternet.IProtocol):\n    def unhandledCommand(command, argument):\n        \"\"\"\n        A command was received but not understood.\n\n        @param command: the command received.\n        @type command: L{str}, a single character.\n        @param argument: the argument to the received command.\n        @type argument: L{str}, a single character, or None if the command that\n            was unhandled does not provide an argument.\n        \"\"\"\n\n\n    def unhandledSubnegotiation(command, data):\n        \"\"\"\n        A subnegotiation command was received but not understood.\n\n        @param command: the command being subnegotiated. That is, the first\n            byte after the SB command.\n        @type command: L{str}, a single character.\n        @param data: all other bytes of the subneogation. That is, all but the\n            first bytes between SB and SE, with IAC un-escaping applied.\n        @type data: L{bytes}, each a single character\n        \"\"\"\n\n\n    def enableLocal(option):\n        \"\"\"\n        Enable the given option locally.\n\n        This should enable the given option on this side of the\n        telnet connection and return True.  If False is returned,\n        the option will be treated as still disabled and the peer\n        will be notified.\n\n        @param option: the option to be enabled.\n        @type option: L{bytes}, a single character.\n        \"\"\"\n\n\n    def enableRemote(option):\n        \"\"\"\n        Indicate whether the peer should be allowed to enable this option.\n\n        Returns True if the peer should be allowed to enable this option,\n        False otherwise.\n\n        @param option: the option to be enabled.\n        @type option: L{bytes}, a single character.\n        \"\"\"\n\n\n    def disableLocal(option):\n        \"\"\"\n        Disable the given option locally.\n\n        Unlike enableLocal, this method cannot fail.  The option must be\n        disabled.\n\n        @param option: the option to be disabled.\n        @type option: L{bytes}, a single character.\n        \"\"\"\n\n\n    def disableRemote(option):\n        \"\"\"\n        Indicate that the peer has disabled this option.\n\n        @param option: the option to be disabled.\n        @type option: L{bytes}, a single character.\n        \"\"\"\n\n\n\nclass ITelnetTransport(iinternet.ITransport):\n    def do(option):\n        \"\"\"\n        Indicate a desire for the peer to begin performing the given option.\n\n        Returns a Deferred that fires with True when the peer begins performing\n        the option, or fails with L{OptionRefused} when the peer refuses to\n        perform it.  If the peer is already performing the given option, the\n        Deferred will fail with L{AlreadyEnabled}.  If a negotiation regarding\n        this option is already in progress, the Deferred will fail with\n        L{AlreadyNegotiating}.\n\n        Note: It is currently possible that this Deferred will never fire,\n        if the peer never responds, or if the peer believes the option to\n        already be enabled.\n        \"\"\"\n\n\n    def dont(option):\n        \"\"\"\n        Indicate a desire for the peer to cease performing the given option.\n\n        Returns a Deferred that fires with True when the peer ceases performing\n        the option.  If the peer is not performing the given option, the\n        Deferred will fail with L{AlreadyDisabled}.  If negotiation regarding\n        this option is already in progress, the Deferred will fail with\n        L{AlreadyNegotiating}.\n\n        Note: It is currently possible that this Deferred will never fire,\n        if the peer never responds, or if the peer believes the option to\n        already be disabled.\n        \"\"\"\n\n\n    def will(option):\n        \"\"\"\n        Indicate our willingness to begin performing this option locally.\n\n        Returns a Deferred that fires with True when the peer agrees to allow us\n        to begin performing this option, or fails with L{OptionRefused} if the\n        peer refuses to allow us to begin performing it.  If the option is\n        already enabled locally, the Deferred will fail with L{AlreadyEnabled}.\n        If negotiation regarding this option is already in progress, the\n        Deferred will fail with L{AlreadyNegotiating}.\n\n        Note: It is currently possible that this Deferred will never fire,\n        if the peer never responds, or if the peer believes the option to\n        already be enabled.\n        \"\"\"\n\n\n    def wont(option):\n        \"\"\"\n        Indicate that we will stop performing the given option.\n\n        Returns a Deferred that fires with True when the peer acknowledges\n        we have stopped performing this option.  If the option is already\n        disabled locally, the Deferred will fail with L{AlreadyDisabled}.\n        If negotiation regarding this option is already in progress,\n        the Deferred will fail with L{AlreadyNegotiating}.\n\n        Note: It is currently possible that this Deferred will never fire,\n        if the peer never responds, or if the peer believes the option to\n        already be disabled.\n        \"\"\"\n\n\n    def requestNegotiation(about, data):\n        \"\"\"\n        Send a subnegotiation request.\n\n        @param about: A byte indicating the feature being negotiated.\n        @param data: Any number of L{bytes} containing specific information\n        about the negotiation being requested.  No values in this string\n        need to be escaped, as this function will escape any value which\n        requires it.\n        \"\"\"\n\n\n\nclass TelnetError(Exception):\n    pass\n\n\n\nclass NegotiationError(TelnetError):\n    def __str__(self):\n        return self.__class__.__module__ + '.' + self.__class__.__name__ + ':' + repr(self.args[0])\n\n\n\nclass OptionRefused(NegotiationError):\n    pass\n\n\n\nclass AlreadyEnabled(NegotiationError):\n    pass\n\n\n\nclass AlreadyDisabled(NegotiationError):\n    pass\n\n\n\nclass AlreadyNegotiating(NegotiationError):\n    pass\n\n\n\n@implementer(ITelnetProtocol)\nclass TelnetProtocol(protocol.Protocol):\n    def unhandledCommand(self, command, argument):\n        pass\n\n\n    def unhandledSubnegotiation(self, command, data):\n        pass\n\n\n    def enableLocal(self, option):\n        pass\n\n\n    def enableRemote(self, option):\n        pass\n\n\n    def disableLocal(self, option):\n        pass\n\n\n    def disableRemote(self, option):\n        pass\n\n\n\nclass Telnet(protocol.Protocol):\n    \"\"\"\n    @ivar commandMap: A mapping of bytes to callables.  When a\n    telnet command is received, the command byte (the first byte\n    after IAC) is looked up in this dictionary.  If a callable is\n    found, it is invoked with the argument of the command, or None\n    if the command takes no argument.  Values should be added to\n    this dictionary if commands wish to be handled.  By default,\n    only WILL, WONT, DO, and DONT are handled.  These should not\n    be overridden, as this class handles them correctly and\n    provides an API for interacting with them.\n\n    @ivar negotiationMap: A mapping of bytes to callables.  When\n    a subnegotiation command is received, the command byte (the\n    first byte after SB) is looked up in this dictionary.  If\n    a callable is found, it is invoked with the argument of the\n    subnegotiation.  Values should be added to this dictionary if\n    subnegotiations are to be handled.  By default, no values are\n    handled.\n\n    @ivar options: A mapping of option bytes to their current\n    state.  This state is likely of little use to user code.\n    Changes should not be made to it.\n\n    @ivar state: A string indicating the current parse state.  It\n    can take on the values \"data\", \"escaped\", \"command\", \"newline\",\n    \"subnegotiation\", and \"subnegotiation-escaped\".  Changes\n    should not be made to it.\n\n    @ivar transport: This protocol's transport object.\n    \"\"\"\n\n    # One of a lot of things\n    state = 'data'\n\n    def __init__(self):\n        self.options = {}\n        self.negotiationMap = {}\n        self.commandMap = {\n            WILL: self.telnet_WILL,\n            WONT: self.telnet_WONT,\n            DO: self.telnet_DO,\n            DONT: self.telnet_DONT}\n\n\n    def _write(self, data):\n        self.transport.write(data)\n\n\n    class _OptionState:\n        \"\"\"\n        Represents the state of an option on both sides of a telnet\n        connection.\n\n        @ivar us: The state of the option on this side of the connection.\n\n        @ivar him: The state of the option on the other side of the\n            connection.\n        \"\"\"\n        class _Perspective:\n            \"\"\"\n            Represents the state of an option on side of the telnet\n            connection.  Some options can be enabled on a particular side of\n            the connection (RFC 1073 for example: only the client can have\n            NAWS enabled).  Other options can be enabled on either or both\n            sides (such as RFC 1372: each side can have its own flow control\n            state).\n\n            @ivar state: C{'yes'} or C{'no'} indicating whether or not this\n                option is enabled on one side of the connection.\n\n            @ivar negotiating: A boolean tracking whether negotiation about\n                this option is in progress.\n\n            @ivar onResult: When negotiation about this option has been\n                initiated by this side of the connection, a L{Deferred}\n                which will fire with the result of the negotiation.  L{None}\n                at other times.\n            \"\"\"\n            state = 'no'\n            negotiating = False\n            onResult = None\n\n            def __str__(self):\n                return self.state + ('*' * self.negotiating)\n\n\n        def __init__(self):\n            self.us = self._Perspective()\n            self.him = self._Perspective()\n\n\n        def __repr__(self):\n            return '<_OptionState us=%s him=%s>' % (self.us, self.him)\n\n\n    def getOptionState(self, opt):\n        return self.options.setdefault(opt, self._OptionState())\n\n\n    def _do(self, option):\n        self._write(IAC + DO + option)\n\n\n    def _dont(self, option):\n        self._write(IAC + DONT + option)\n\n\n    def _will(self, option):\n        self._write(IAC + WILL + option)\n\n\n    def _wont(self, option):\n        self._write(IAC + WONT + option)\n\n\n    def will(self, option):\n        \"\"\"\n        Indicate our willingness to enable an option.\n        \"\"\"\n        s = self.getOptionState(option)\n        if s.us.negotiating or s.him.negotiating:\n            return defer.fail(AlreadyNegotiating(option))\n        elif s.us.state == 'yes':\n            return defer.fail(AlreadyEnabled(option))\n        else:\n            s.us.negotiating = True\n            s.us.onResult = d = defer.Deferred()\n            self._will(option)\n            return d\n\n\n    def wont(self, option):\n        \"\"\"\n        Indicate we are not willing to enable an option.\n        \"\"\"\n        s = self.getOptionState(option)\n        if s.us.negotiating or s.him.negotiating:\n            return defer.fail(AlreadyNegotiating(option))\n        elif s.us.state == 'no':\n            return defer.fail(AlreadyDisabled(option))\n        else:\n            s.us.negotiating = True\n            s.us.onResult = d = defer.Deferred()\n            self._wont(option)\n            return d\n\n\n    def do(self, option):\n        s = self.getOptionState(option)\n        if s.us.negotiating or s.him.negotiating:\n            return defer.fail(AlreadyNegotiating(option))\n        elif s.him.state == 'yes':\n            return defer.fail(AlreadyEnabled(option))\n        else:\n            s.him.negotiating = True\n            s.him.onResult = d = defer.Deferred()\n            self._do(option)\n            return d\n\n\n    def dont(self, option):\n        s = self.getOptionState(option)\n        if s.us.negotiating or s.him.negotiating:\n            return defer.fail(AlreadyNegotiating(option))\n        elif s.him.state == 'no':\n            return defer.fail(AlreadyDisabled(option))\n        else:\n            s.him.negotiating = True\n            s.him.onResult = d = defer.Deferred()\n            self._dont(option)\n            return d\n\n\n    def requestNegotiation(self, about, data):\n        \"\"\"\n        Send a negotiation message for the option C{about} with C{data} as the\n        payload.\n\n        @param data: the payload\n        @type data: L{bytes}\n        @see: L{ITelnetTransport.requestNegotiation}\n        \"\"\"\n        data = data.replace(IAC, IAC * 2)\n        self._write(IAC + SB + about + data + IAC + SE)\n\n\n    def dataReceived(self, data):\n        appDataBuffer = []\n\n        for b in iterbytes(data):\n            if self.state == 'data':\n                if b == IAC:\n                    self.state = 'escaped'\n                elif b == b'\\r':\n                    self.state = 'newline'\n                else:\n                    appDataBuffer.append(b)\n            elif self.state == 'escaped':\n                if b == IAC:\n                    appDataBuffer.append(b)\n                    self.state = 'data'\n                elif b == SB:\n                    self.state = 'subnegotiation'\n                    self.commands = []\n                elif b in (NOP, DM, BRK, IP, AO, AYT, EC, EL, GA):\n                    self.state = 'data'\n                    if appDataBuffer:\n                        self.applicationDataReceived(b''.join(appDataBuffer))\n                        del appDataBuffer[:]\n                    self.commandReceived(b, None)\n                elif b in (WILL, WONT, DO, DONT):\n                    self.state = 'command'\n                    self.command = b\n                else:\n                    raise ValueError(\"Stumped\", b)\n            elif self.state == 'command':\n                self.state = 'data'\n                command = self.command\n                del self.command\n                if appDataBuffer:\n                    self.applicationDataReceived(b''.join(appDataBuffer))\n                    del appDataBuffer[:]\n                self.commandReceived(command, b)\n            elif self.state == 'newline':\n                self.state = 'data'\n                if b == b'\\n':\n                    appDataBuffer.append(b'\\n')\n                elif b == b'\\0':\n                    appDataBuffer.append(b'\\r')\n                elif b == IAC:\n                    # IAC isn't really allowed after \\r, according to the\n                    # RFC, but handling it this way is less surprising than\n                    # delivering the IAC to the app as application data.\n                    # The purpose of the restriction is to allow terminals\n                    # to unambiguously interpret the behavior of the CR\n                    # after reading only one more byte.  CR LF is supposed\n                    # to mean one thing (cursor to next line, first column),\n                    # CR NUL another (cursor to first column).  Absent the\n                    # NUL, it still makes sense to interpret this as CR and\n                    # then apply all the usual interpretation to the IAC.\n                    appDataBuffer.append(b'\\r')\n                    self.state = 'escaped'\n                else:\n                    appDataBuffer.append(b'\\r' + b)\n            elif self.state == 'subnegotiation':\n                if b == IAC:\n                    self.state = 'subnegotiation-escaped'\n                else:\n                    self.commands.append(b)\n            elif self.state == 'subnegotiation-escaped':\n                if b == SE:\n                    self.state = 'data'\n                    commands = self.commands\n                    del self.commands\n                    if appDataBuffer:\n                        self.applicationDataReceived(b''.join(appDataBuffer))\n                        del appDataBuffer[:]\n                    self.negotiate(commands)\n                else:\n                    self.state = 'subnegotiation'\n                    self.commands.append(b)\n            else:\n                raise ValueError(\"How'd you do this?\")\n\n        if appDataBuffer:\n            self.applicationDataReceived(b''.join(appDataBuffer))\n\n\n    def connectionLost(self, reason):\n        for state in self.options.values():\n            if state.us.onResult is not None:\n                d = state.us.onResult\n                state.us.onResult = None\n                d.errback(reason)\n            if state.him.onResult is not None:\n                d = state.him.onResult\n                state.him.onResult = None\n                d.errback(reason)\n\n\n    def applicationDataReceived(self, data):\n        \"\"\"\n        Called with application-level data.\n        \"\"\"\n\n    def unhandledCommand(self, command, argument):\n        \"\"\"\n        Called for commands for which no handler is installed.\n        \"\"\"\n\n\n    def commandReceived(self, command, argument):\n        cmdFunc = self.commandMap.get(command)\n        if cmdFunc is None:\n            self.unhandledCommand(command, argument)\n        else:\n            cmdFunc(argument)\n\n\n    def unhandledSubnegotiation(self, command, data):\n        \"\"\"\n        Called for subnegotiations for which no handler is installed.\n        \"\"\"\n\n\n    def negotiate(self, data):\n        command, data = data[0], data[1:]\n        cmdFunc = self.negotiationMap.get(command)\n        if cmdFunc is None:\n            self.unhandledSubnegotiation(command, data)\n        else:\n            cmdFunc(data)\n\n\n    def telnet_WILL(self, option):\n        s = self.getOptionState(option)\n        self.willMap[s.him.state, s.him.negotiating](self, s, option)\n\n\n    def will_no_false(self, state, option):\n        # He is unilaterally offering to enable an option.\n        if self.enableRemote(option):\n            state.him.state = 'yes'\n            self._do(option)\n        else:\n            self._dont(option)\n\n\n    def will_no_true(self, state, option):\n        # Peer agreed to enable an option in response to our request.\n        state.him.state = 'yes'\n        state.him.negotiating = False\n        d = state.him.onResult\n        state.him.onResult = None\n        d.callback(True)\n        assert self.enableRemote(option), \"enableRemote must return True in this context (for option %r)\" % (option,)\n\n\n    def will_yes_false(self, state, option):\n        # He is unilaterally offering to enable an already-enabled option.\n        # Ignore this.\n        pass\n\n\n    def will_yes_true(self, state, option):\n        # This is a bogus state.  It is here for completeness.  It will\n        # never be entered.\n        assert False, \"will_yes_true can never be entered, but was called with %r, %r\" % (state, option)\n\n    willMap = {('no', False): will_no_false,   ('no', True): will_no_true,\n               ('yes', False): will_yes_false, ('yes', True): will_yes_true}\n\n\n    def telnet_WONT(self, option):\n        s = self.getOptionState(option)\n        self.wontMap[s.him.state, s.him.negotiating](self, s, option)\n\n\n    def wont_no_false(self, state, option):\n        # He is unilaterally demanding that an already-disabled option be/remain disabled.\n        # Ignore this (although we could record it and refuse subsequent enable attempts\n        # from our side - he can always refuse them again though, so we won't)\n        pass\n\n\n    def wont_no_true(self, state, option):\n        # Peer refused to enable an option in response to our request.\n        state.him.negotiating = False\n        d = state.him.onResult\n        state.him.onResult = None\n        d.errback(OptionRefused(option))\n\n\n    def wont_yes_false(self, state, option):\n        # Peer is unilaterally demanding that an option be disabled.\n        state.him.state = 'no'\n        self.disableRemote(option)\n        self._dont(option)\n\n\n    def wont_yes_true(self, state, option):\n        # Peer agreed to disable an option at our request.\n        state.him.state = 'no'\n        state.him.negotiating = False\n        d = state.him.onResult\n        state.him.onResult = None\n        d.callback(True)\n        self.disableRemote(option)\n\n    wontMap = {('no', False): wont_no_false,   ('no', True): wont_no_true,\n               ('yes', False): wont_yes_false, ('yes', True): wont_yes_true}\n\n\n    def telnet_DO(self, option):\n        s = self.getOptionState(option)\n        self.doMap[s.us.state, s.us.negotiating](self, s, option)\n\n\n    def do_no_false(self, state, option):\n        # Peer is unilaterally requesting that we enable an option.\n        if self.enableLocal(option):\n            state.us.state = 'yes'\n            self._will(option)\n        else:\n            self._wont(option)\n\n\n    def do_no_true(self, state, option):\n        # Peer agreed to allow us to enable an option at our request.\n        state.us.state = 'yes'\n        state.us.negotiating = False\n        d = state.us.onResult\n        state.us.onResult = None\n        d.callback(True)\n        self.enableLocal(option)\n\n\n    def do_yes_false(self, state, option):\n        # Peer is unilaterally requesting us to enable an already-enabled option.\n        # Ignore this.\n        pass\n\n\n    def do_yes_true(self, state, option):\n        # This is a bogus state.  It is here for completeness.  It will never be\n        # entered.\n        assert False, \"do_yes_true can never be entered, but was called with %r, %r\" % (state, option)\n\n    doMap = {('no', False): do_no_false,   ('no', True): do_no_true,\n             ('yes', False): do_yes_false, ('yes', True): do_yes_true}\n\n\n    def telnet_DONT(self, option):\n        s = self.getOptionState(option)\n        self.dontMap[s.us.state, s.us.negotiating](self, s, option)\n\n\n    def dont_no_false(self, state, option):\n        # Peer is unilaterally demanding us to disable an already-disabled option.\n        # Ignore this.\n        pass\n\n\n    def dont_no_true(self, state, option):\n        # Offered option was refused.  Fail the Deferred returned by the\n        # previous will() call.\n        state.us.negotiating = False\n        d = state.us.onResult\n        state.us.onResult = None\n        d.errback(OptionRefused(option))\n\n\n    def dont_yes_false(self, state, option):\n        # Peer is unilaterally demanding we disable an option.\n        state.us.state = 'no'\n        self.disableLocal(option)\n        self._wont(option)\n\n\n    def dont_yes_true(self, state, option):\n        # Peer acknowledged our notice that we will disable an option.\n        state.us.state = 'no'\n        state.us.negotiating = False\n        d = state.us.onResult\n        state.us.onResult = None\n        d.callback(True)\n        self.disableLocal(option)\n\n    dontMap = {('no', False): dont_no_false,   ('no', True): dont_no_true,\n               ('yes', False): dont_yes_false, ('yes', True): dont_yes_true}\n\n\n    def enableLocal(self, option):\n        \"\"\"\n        Reject all attempts to enable options.\n        \"\"\"\n        return False\n\n\n    def enableRemote(self, option):\n        \"\"\"\n        Reject all attempts to enable options.\n        \"\"\"\n        return False\n\n\n    def disableLocal(self, option):\n        \"\"\"\n        Signal a programming error by raising an exception.\n\n        L{enableLocal} must return true for the given value of C{option} in\n        order for this method to be called.  If a subclass of L{Telnet}\n        overrides enableLocal to allow certain options to be enabled, it must\n        also override disableLocal to disable those options.\n\n        @raise NotImplementedError: Always raised.\n        \"\"\"\n        raise NotImplementedError(\n            \"Don't know how to disable local telnet option %r\" % (option,))\n\n\n    def disableRemote(self, option):\n        \"\"\"\n        Signal a programming error by raising an exception.\n\n        L{enableRemote} must return true for the given value of C{option} in\n        order for this method to be called.  If a subclass of L{Telnet}\n        overrides enableRemote to allow certain options to be enabled, it must\n        also override disableRemote tto disable those options.\n\n        @raise NotImplementedError: Always raised.\n        \"\"\"\n        raise NotImplementedError(\n            \"Don't know how to disable remote telnet option %r\" % (option,))\n\n\n\nclass ProtocolTransportMixin:\n    def write(self, data):\n        self.transport.write(data.replace(b'\\n', b'\\r\\n'))\n\n\n    def writeSequence(self, seq):\n        self.transport.writeSequence(seq)\n\n\n    def loseConnection(self):\n        self.transport.loseConnection()\n\n\n    def getHost(self):\n        return self.transport.getHost()\n\n\n    def getPeer(self):\n        return self.transport.getPeer()\n\n\n\nclass TelnetTransport(Telnet, ProtocolTransportMixin):\n    \"\"\"\n    @ivar protocol: An instance of the protocol to which this\n    transport is connected, or None before the connection is\n    established and after it is lost.\n\n    @ivar protocolFactory: A callable which returns protocol instances\n    which provide L{ITelnetProtocol}.  This will be invoked when a\n    connection is established.  It is passed *protocolArgs and\n    **protocolKwArgs.\n\n    @ivar protocolArgs: A tuple of additional arguments to\n    pass to protocolFactory.\n\n    @ivar protocolKwArgs: A dictionary of additional arguments\n    to pass to protocolFactory.\n    \"\"\"\n\n    disconnecting = False\n\n    protocolFactory = None\n    protocol = None\n\n    def __init__(self, protocolFactory=None, *a, **kw):\n        Telnet.__init__(self)\n        if protocolFactory is not None:\n            self.protocolFactory = protocolFactory\n            self.protocolArgs = a\n            self.protocolKwArgs = kw\n\n\n    def connectionMade(self):\n        if self.protocolFactory is not None:\n            self.protocol = self.protocolFactory(*self.protocolArgs, **self.protocolKwArgs)\n            assert ITelnetProtocol.providedBy(self.protocol)\n            try:\n                factory = self.factory\n            except AttributeError:\n                pass\n            else:\n                self.protocol.factory = factory\n            self.protocol.makeConnection(self)\n\n\n    def connectionLost(self, reason):\n        Telnet.connectionLost(self, reason)\n        if self.protocol is not None:\n            try:\n                self.protocol.connectionLost(reason)\n            finally:\n                del self.protocol\n\n\n    def enableLocal(self, option):\n        return self.protocol.enableLocal(option)\n\n\n    def enableRemote(self, option):\n        return self.protocol.enableRemote(option)\n\n\n    def disableLocal(self, option):\n        return self.protocol.disableLocal(option)\n\n\n    def disableRemote(self, option):\n        return self.protocol.disableRemote(option)\n\n\n    def unhandledSubnegotiation(self, command, data):\n        self.protocol.unhandledSubnegotiation(command, data)\n\n\n    def unhandledCommand(self, command, argument):\n        self.protocol.unhandledCommand(command, argument)\n\n\n    def applicationDataReceived(self, data):\n        self.protocol.dataReceived(data)\n\n\n    def write(self, data):\n        ProtocolTransportMixin.write(self, data.replace(b'\\xff', b'\\xff\\xff'))\n\n\n\nclass TelnetBootstrapProtocol(TelnetProtocol, ProtocolTransportMixin):\n    protocol = None\n\n    def __init__(self, protocolFactory, *args, **kw):\n        self.protocolFactory = protocolFactory\n        self.protocolArgs = args\n        self.protocolKwArgs = kw\n\n\n    def connectionMade(self):\n        self.transport.negotiationMap[NAWS] = self.telnet_NAWS\n        self.transport.negotiationMap[LINEMODE] = self.telnet_LINEMODE\n\n        for opt in (LINEMODE, NAWS, SGA):\n            self.transport.do(opt).addErrback(log.err)\n        for opt in (ECHO,):\n            self.transport.will(opt).addErrback(log.err)\n\n        self.protocol = self.protocolFactory(*self.protocolArgs, **self.protocolKwArgs)\n\n        try:\n            factory = self.factory\n        except AttributeError:\n            pass\n        else:\n            self.protocol.factory = factory\n\n        self.protocol.makeConnection(self)\n\n\n    def connectionLost(self, reason):\n        if self.protocol is not None:\n            try:\n                self.protocol.connectionLost(reason)\n            finally:\n                del self.protocol\n\n\n    def dataReceived(self, data):\n        self.protocol.dataReceived(data)\n\n\n    def enableLocal(self, opt):\n        if opt == ECHO:\n            return True\n        elif opt == SGA:\n            return True\n        else:\n            return False\n\n\n    def enableRemote(self, opt):\n        if opt == LINEMODE:\n            self.transport.requestNegotiation(LINEMODE, MODE + chr(TRAPSIG))\n            return True\n        elif opt == NAWS:\n            return True\n        elif opt == SGA:\n            return True\n        else:\n            return False\n\n\n    def telnet_NAWS(self, data):\n        # NAWS is client -> server *only*.  self.protocol will\n        # therefore be an ITerminalTransport, the `.protocol'\n        # attribute of which will be an ITerminalProtocol.  Maybe.\n        # You know what, XXX TODO clean this up.\n        if len(data) == 4:\n            width, height = struct.unpack('!HH', b''.join(data))\n            self.protocol.terminalProtocol.terminalSize(width, height)\n        else:\n            log.msg(\"Wrong number of NAWS bytes\")\n\n    linemodeSubcommands = {\n        LINEMODE_SLC: 'SLC'}\n    def telnet_LINEMODE(self, data):\n        linemodeSubcommand = data[0]\n        if 0:\n            # XXX TODO: This should be enabled to parse linemode subnegotiation.\n            getattr(self, 'linemode_' + self.linemodeSubcommands[linemodeSubcommand])(data[1:])\n\n\n    def linemode_SLC(self, data):\n        chunks = zip(*[iter(data)]*3)\n        for slcFunction, slcValue, slcWhat in chunks:\n            # Later, we should parse stuff.\n            'SLC', ord(slcFunction), ord(slcValue), ord(slcWhat)\n\n\nfrom twisted.protocols import basic\n\nclass StatefulTelnetProtocol(basic.LineReceiver, TelnetProtocol):\n    delimiter = b'\\n'\n\n    state = 'Discard'\n\n    def connectionLost(self, reason):\n        basic.LineReceiver.connectionLost(self, reason)\n        TelnetProtocol.connectionLost(self, reason)\n\n\n    def lineReceived(self, line):\n        oldState = self.state\n        newState = getattr(self, \"telnet_\" + oldState)(line)\n        if newState is not None:\n            if self.state == oldState:\n                self.state = newState\n            else:\n                log.msg(\"Warning: state changed and new state returned\")\n\n\n    def telnet_Discard(self, line):\n        pass\n\n\nfrom twisted.cred import credentials\n\nclass AuthenticatingTelnetProtocol(StatefulTelnetProtocol):\n    \"\"\"\n    A protocol which prompts for credentials and attempts to authenticate them.\n\n    Username and password prompts are given (the password is obscured).  When the\n    information is collected, it is passed to a portal and an avatar implementing\n    L{ITelnetProtocol} is requested.  If an avatar is returned, it connected to this\n    protocol's transport, and this protocol's transport is connected to it.\n    Otherwise, the user is re-prompted for credentials.\n    \"\"\"\n\n    state = \"User\"\n    protocol = None\n\n    def __init__(self, portal):\n        self.portal = portal\n\n\n    def connectionMade(self):\n        self.transport.write(b\"Username: \")\n\n\n    def connectionLost(self, reason):\n        StatefulTelnetProtocol.connectionLost(self, reason)\n        if self.protocol is not None:\n            try:\n                self.protocol.connectionLost(reason)\n                self.logout()\n            finally:\n                del self.protocol, self.logout\n\n\n    def telnet_User(self, line):\n        self.username = line\n        self.transport.will(ECHO)\n        self.transport.write(b\"Password: \")\n        return 'Password'\n\n\n    def telnet_Password(self, line):\n        username, password = self.username, line\n        del self.username\n        def login(ignored):\n            creds = credentials.UsernamePassword(username, password)\n            d = self.portal.login(creds, None, ITelnetProtocol)\n            d.addCallback(self._cbLogin)\n            d.addErrback(self._ebLogin)\n        self.transport.wont(ECHO).addCallback(login)\n        return 'Discard'\n\n\n    def _cbLogin(self, ial):\n        interface, protocol, logout = ial\n        assert interface is ITelnetProtocol\n        self.protocol = protocol\n        self.logout = logout\n        self.state = 'Command'\n\n        protocol.makeConnection(self.transport)\n        self.transport.protocol = protocol\n\n\n    def _ebLogin(self, failure):\n        self.transport.write(b\"\\nAuthentication failed\\n\")\n        self.transport.write(b\"Username: \")\n        self.state = \"User\"\n\n\n__all__ = [\n    # Exceptions\n    'TelnetError', 'NegotiationError', 'OptionRefused',\n    'AlreadyNegotiating', 'AlreadyEnabled', 'AlreadyDisabled',\n\n    # Interfaces\n    'ITelnetProtocol', 'ITelnetTransport',\n\n    # Other stuff, protocols, etc.\n    'Telnet', 'TelnetProtocol', 'TelnetTransport',\n    'TelnetBootstrapProtocol',\n\n    ]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/__init__.py",
    "content": "'conch tests'\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/keydata.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_keys -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n# pylint: disable=I0011,C0103,W9401,W9402\n\n\"\"\"\nData used by test_keys as well as others.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom twisted.python.compat import long, _b64decodebytes as decodebytes\n\nRSAData = {\n    'n': long('269413617238113438198661010376758399219880277968382122687862697'\n              '296942471209955603071120391975773283844560230371884389952067978'\n              '789684135947515341209478065209455427327369102356204259106807047'\n              '964139525310539133073743116175821417513079706301100600025815509'\n              '786721808719302671068052414466483676821987505720384645561708425'\n              '794379383191274856941628512616355437197560712892001107828247792'\n              '561858327085521991407807015047750218508971611590850575870321007'\n              '991909043252470730134547038841839367764074379439843108550888709'\n              '430958143271417044750314742880542002948053835745429446485015316'\n              '60749404403945254975473896534482849256068133525751'),\n    'e': long(65537),\n    'd': long('420335724286999695680502438485489819800002417295071059780489811'\n              '840828351636754206234982682752076205397047218449504537476523960'\n              '987613148307573487322720481066677105211155388802079519869249746'\n              '774085882219244493290663802569201213676433159425782937159766786'\n              '329742053214957933941260042101377175565683849732354700525628975'\n              '239000548651346620826136200952740446562751690924335365940810658'\n              '931238410612521441739702170503547025018016868116037053013935451'\n              '477930426013703886193016416453215950072147440344656137718959053'\n              '897268663969428680144841987624962928576808352739627262941675617'\n              '7724661940425316604626522633351193810751757014073'),\n    'p': long('152689878451107675391723141129365667732639179427453246378763774'\n              '448531436802867910180261906924087589684175595016060014593521649'\n              '964959248408388984465569934780790357826811592229318702991401054'\n              '226302790395714901636384511513449977061729214247279176398290513'\n              '085108930550446985490864812445551198848562639933888780317'),\n    'q': long('176444974592327996338888725079951900172097062203378367409936859'\n              '072670162290963119826394224277287608693818012745872307600855894'\n              '647300295516866118620024751601329775653542084052616260193174546'\n              '400544176890518564317596334518015173606460860373958663673307503'\n              '231977779632583864454001476729233959405710696795574874403'),\n    'u': long('936018002388095842969518498561007090965136403384715613439364803'\n              '229386793506402222847415019772053080458257034241832795210460612'\n              '924445085372678524176842007912276654532773301546269997020970818'\n              '155956828553418266110329867222673040098885651348225673298948529'\n              '93885224775891490070400861134282266967852120152546563278')\n}\n\nDSAData = {\n    'g': long(\"10253261326864117157640690761723586967382334319435778695\"\n              \"29171533815411392477819921538350732400350395446211982054\"\n              \"96512489289702949127531056893725702005035043292195216541\"\n              \"11525058911428414042792836395195432445511200566318251789\"\n              \"10575695836669396181746841141924498545494149998282951407\"\n              \"18645344764026044855941864175\"),\n    'p': long(\"10292031726231756443208850082191198787792966516790381991\"\n              \"77502076899763751166291092085666022362525614129374702633\"\n              \"26262930887668422949051881895212412718444016917144560705\"\n              \"45675251775747156453237145919794089496168502517202869160\"\n              \"78674893099371444940800865897607102159386345313384716752\"\n              \"18590012064772045092956919481\"),\n    'q': long(1393384845225358996250882900535419012502712821577),\n    'x': long(1220877188542930584999385210465204342686893855021),\n    'y': long(\"14604423062661947579790240720337570315008549983452208015\"\n              \"39426429789435409684914513123700756086453120500041882809\"\n              \"10283610277194188071619191739512379408443695946763554493\"\n              \"86398594314468629823767964702559709430618263927529765769\"\n              \"10270265745700231533660131769648708944711006508965764877\"\n              \"684264272082256183140297951\")\n}\n\nECDatanistp256 = {\n  'x': long('762825130203920963171185031449647317742997734817505505433829043'\n            '45687059013883'),\n  'y': long('815431978646028526322656647694416475343443758943143196810611371'\n            '59310646683104'),\n  'privateValue': long('3463874347721034170096400845565569825355565567882605'\n                        '9678074967909361042656500'),\n  'curve': b'ecdsa-sha2-nistp256'\n}\n\nECDatanistp384 = {\n  'privateValue': long('280814107134858470598753916394807521398239633534281633982576099083'\n                        '35787109896602102090002196616273211495718603965098'),\n  'x': long('10036914308591746758780165503819213553101287571902957054148542'\n            '504671046744460374996612408381962208627004841444205030'),\n  'y': long('17337335659928075994560513699823544906448896792102247714689323'\n            '575406618073069185107088229463828921069465902299522926'),\n  'curve': b'ecdsa-sha2-nistp384'\n}\n\nECDatanistp521 = {\n  'x': long('12944742826257420846659527752683763193401384271391513286022917'\n            '29910013082920512632908350502247952686156279140016049549948975'\n            '670668730618745449113644014505462'),\n  'y': long('10784108810271976186737587749436295782985563640368689081052886'\n            '16296815984553198866894145509329328086635278430266482551941240'\n            '591605833440825557820439734509311'),\n  'privateValue': long('662751235215460886290293902658128847495347691199214706697089140769'\n                        '672273950767961331442265530524063943548846724348048614239791498442'\n                        '5997823106818915698960565'),\n  'curve': b'ecdsa-sha2-nistp521'\n}\n\nprivateECDSA_openssh521 = b\"\"\"-----BEGIN EC PRIVATE KEY-----\nMIHcAgEBBEIAjn0lSVF6QweS4bjOGP9RHwqxUiTastSE0MVuLtFvkxygZqQ712oZ\newMvqKkxthMQgxzSpGtRBcmkL7RqZ94+18qgBwYFK4EEACOhgYkDgYYABAFpX/6B\nmxxglwD+VpEvw0hcyxVzLxNnMGzxZGF7xmNj8nlF7M+TQctdlR2Xv/J+AgIeVGmB\nj2p84bkV9jBzrUNJEACsJjttZw8NbUrhxjkLT/3rMNtuwjE4vLja0P7DMTE0EV8X\nf09ETdku/z/1tOSSrSvRwmUcM9nQUJtHHAZlr5Q0fw==\n-----END EC PRIVATE KEY-----\"\"\"\n\n# New format introduced in OpenSSH 6.5\nprivateECDSA_openssh521_new = b\"\"\"-----BEGIN OPENSSH PRIVATE KEY-----\nb3BlbnNzaC1rZXktdjEAAAAABG5vbmUAAAAEbm9uZQAAAAAAAAABAAAArAAAABNlY2RzYS\n1zaGEyLW5pc3RwNTIxAAAACG5pc3RwNTIxAAAAhQQBaV/+gZscYJcA/laRL8NIXMsVcy8T\nZzBs8WRhe8ZjY/J5RezPk0HLXZUdl7/yfgICHlRpgY9qfOG5FfYwc61DSRAArCY7bWcPDW\n1K4cY5C0/96zDbbsIxOLy42tD+wzExNBFfF39PRE3ZLv8/9bTkkq0r0cJlHDPZ0FCbRxwG\nZa+UNH8AAAEAeRISlnkSEpYAAAATZWNkc2Etc2hhMi1uaXN0cDUyMQAAAAhuaXN0cDUyMQ\nAAAIUEAWlf/oGbHGCXAP5WkS/DSFzLFXMvE2cwbPFkYXvGY2PyeUXsz5NBy12VHZe/8n4C\nAh5UaYGPanzhuRX2MHOtQ0kQAKwmO21nDw1tSuHGOQtP/esw227CMTi8uNrQ/sMxMTQRXx\nd/T0RN2S7/P/W05JKtK9HCZRwz2dBQm0ccBmWvlDR/AAAAQgCOfSVJUXpDB5LhuM4Y/1Ef\nCrFSJNqy1ITQxW4u0W+THKBmpDvXahl7Ay+oqTG2ExCDHNKka1EFyaQvtGpn3j7XygAAAA\nABAg==\n-----END OPENSSH PRIVATE KEY-----\"\"\"\n\npublicECDSA_openssh521 = (\n    b\"ecdsa-sha2-nistp521 AAAAE2VjZHNhLXNoYTItbmlzdHA1MjEAAAAIbmlzdHA1MjEAAACF\"\n    b\"BAFpX/6BmxxglwD+VpEvw0hcyxVzLxNnMGzxZGF7xmNj8nlF7M+TQctdlR2Xv/J+AgIeVGmB\"\n    b\"j2p84bkV9jBzrUNJEACsJjttZw8NbUrhxjkLT/3rMNtuwjE4vLja0P7DMTE0EV8Xf09ETdku\"\n    b\"/z/1tOSSrSvRwmUcM9nQUJtHHAZlr5Q0fw== comment\"\n)\n\nprivateECDSA_openssh384 = b\"\"\"-----BEGIN EC PRIVATE KEY-----\nMIGkAgEBBDAtAi7I8j73WCX20qUM5hhHwHuFzYWYYILs2Sh8UZ+awNkARZ/Fu2LU\nLLl5RtOQpbWgBwYFK4EEACKhZANiAATU17sA9P5FRwSknKcFsjjsk0+E3CeXPYX0\nTk/M0HK3PpWQWgrO8JdRHP9eFE9O/23P8BumwFt7F/AvPlCzVd35VfraFT0o4cCW\nG0RqpQ+np31aKmeJshkcYALEchnU+tQ=\n-----END EC PRIVATE KEY-----\"\"\"\n\n# New format introduced in OpenSSH 6.5\nprivateECDSA_openssh384_new = b\"\"\"-----BEGIN OPENSSH PRIVATE KEY-----\nb3BlbnNzaC1rZXktdjEAAAAABG5vbmUAAAAEbm9uZQAAAAAAAAABAAAAiAAAABNlY2RzYS\n1zaGEyLW5pc3RwMzg0AAAACG5pc3RwMzg0AAAAYQTU17sA9P5FRwSknKcFsjjsk0+E3CeX\nPYX0Tk/M0HK3PpWQWgrO8JdRHP9eFE9O/23P8BumwFt7F/AvPlCzVd35VfraFT0o4cCWG0\nRqpQ+np31aKmeJshkcYALEchnU+tQAAADIiktpWIpLaVgAAAATZWNkc2Etc2hhMi1uaXN0\ncDM4NAAAAAhuaXN0cDM4NAAAAGEE1Ne7APT+RUcEpJynBbI47JNPhNwnlz2F9E5PzNBytz\n6VkFoKzvCXURz/XhRPTv9tz/AbpsBbexfwLz5Qs1Xd+VX62hU9KOHAlhtEaqUPp6d9Wipn\nibIZHGACxHIZ1PrUAAAAMC0CLsjyPvdYJfbSpQzmGEfAe4XNhZhgguzZKHxRn5rA2QBFn8\nW7YtQsuXlG05CltQAAAAA=\n-----END OPENSSH PRIVATE KEY-----\"\"\"\n\npublicECDSA_openssh384 = (\n    b\"ecdsa-sha2-nistp384 AAAAE2VjZHNhLXNoYTItbmlzdHAzODQAAAAIbmlzdHAzODQAAABh\"\n    b\"BNTXuwD0/kVHBKScpwWyOOyTT4TcJ5c9hfROT8zQcrc+lZBaCs7wl1Ec/14UT07/bc/wG6bA\"\n    b\"W3sX8C8+ULNV3flV+toVPSjhwJYbRGqlD6enfVoqZ4myGRxgAsRyGdT61A== comment\"\n)\n\npublicECDSA_openssh = (\n    b\"ecdsa-sha2-nistp256 AAAAE2VjZHNhLXNoYTItbmlzdHAyNTYAAAAIbmlzdHAyNTYAAABB\"\n    b\"BKimX1DZ7+Qj0SpfePMbo1pb6yGkAb5l7duC1l855yD7tEfQfqk7bc7v46We1hLMyz6ObUBY\"\n    b\"gkN/34n42F4vpeA= comment\"\n)\n\nprivateECDSA_openssh = b\"\"\"-----BEGIN EC PRIVATE KEY-----\nMHcCAQEEIEyU1YOT2JxxofwbJXIjGftdNcJK55aQdNrhIt2xYQz0oAoGCCqGSM49\nAwEHoUQDQgAEqKZfUNnv5CPRKl948xujWlvrIaQBvmXt24LWXznnIPu0R9B+qTtt\nzu/jpZ7WEszLPo5tQFiCQ3/fifjYXi+l4A==\n-----END EC PRIVATE KEY-----\"\"\"\n\n# New format introduced in OpenSSH 6.5\nprivateECDSA_openssh_new = b\"\"\"-----BEGIN OPENSSH PRIVATE KEY-----\nb3BlbnNzaC1rZXktdjEAAAAABG5vbmUAAAAEbm9uZQAAAAAAAAABAAAAaAAAABNlY2RzYS\n1zaGEyLW5pc3RwMjU2AAAACG5pc3RwMjU2AAAAQQSopl9Q2e/kI9EqX3jzG6NaW+shpAG+\nZe3bgtZfOecg+7RH0H6pO23O7+OlntYSzMs+jm1AWIJDf9+J+NheL6XgAAAAmCKU4hcilO\nIXAAAAE2VjZHNhLXNoYTItbmlzdHAyNTYAAAAIbmlzdHAyNTYAAABBBKimX1DZ7+Qj0Spf\nePMbo1pb6yGkAb5l7duC1l855yD7tEfQfqk7bc7v46We1hLMyz6ObUBYgkN/34n42F4vpe\nAAAAAgTJTVg5PYnHGh/BslciMZ+101wkrnlpB02uEi3bFhDPQAAAAA\n-----END OPENSSH PRIVATE KEY-----\"\"\"\n\npublicRSA_openssh = (\n    b\"ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQDVaqx4I9bWG+wloVDEd2NQhEUBVUIUKirg\"\n    b\"0GDu1OmjrUr6OQZehFV1XwA2v2+qKj+DJjfBaS5b/fDz0n3WmM06QHjVyqgYwBGTJAkMgUyP\"\n    b\"95ztExZqpATpSXfD5FVks3loniwI66zoBC0hdwWnju9TMA2l5bs9auIJNm/9NNN9b0b/h9qp\"\n    b\"KSeq/631heY+Grh6HUqx6sBa9zDfH8Kk5O8/kUmWQNUZdy03w17snaY6RKXCpCnd1bqcPUWz\"\n    b\"xiwYZNW6Pd+rf81CrKfxGAugWBViC6QqbkPD5ASfNaNHjkbtM6Vlvbw7KW4CC1ffdOgTtDc1\"\n    b\"foNfICZgptyti8ZseZj3 comment\"\n)\n\nprivateRSA_openssh = b'''-----BEGIN RSA PRIVATE KEY-----\nMIIEowIBAAKCAQEA1WqseCPW1hvsJaFQxHdjUIRFAVVCFCoq4NBg7tTpo61K+jkG\nXoRVdV8ANr9vqio/gyY3wWkuW/3w89J91pjNOkB41cqoGMARkyQJDIFMj/ec7RMW\naqQE6Ul3w+RVZLN5aJ4sCOus6AQtIXcFp47vUzANpeW7PWriCTZv/TTTfW9G/4fa\nqSknqv+t9YXmPhq4eh1KserAWvcw3x/CpOTvP5FJlkDVGXctN8Ne7J2mOkSlwqQp\n3dW6nD1Fs8YsGGTVuj3fq3/NQqyn8RgLoFgVYgukKm5Dw+QEnzWjR45G7TOlZb28\nOyluAgtX33ToE7Q3NX6DXyAmYKbcrYvGbHmY9wIDAQABAoIBACFMCGaiKNW0+44P\nchuFCQC58k438BxXS+NRf54jp+Q6mFUb6ot6mB682Lqx+YkSGGCs6MwLTglaQGq6\nL5n4syRghLnOaZWa+eL8H1FNJxXbKyet77RprL59EOuGR3BztACHlRU7N/nnFOeA\nu2geG+bdu3NjuWfmsid/z88wm8KY/dkYNi82LvE9gXqf4QMtR9s0UWI53U/prKiL\n2dbzhMQXuXGdBghCeE27xSr0w1jNVSvtvjNfBOp75gQkY/It1z0bbNWcY0MvkoiN\nPm7aGDfYDyVniR25RjReyc7Ei+2SWjMHD9+GCPmS6dvrOAg2yc3NCgFIWzk+esrG\ngKnc1DkCgYEA2XAG2OK81HiRUJTUwRuJOGxGZFpRoJoHPUiPA1HMaxKOfRqxZedx\ndTngMgV1jRhMr5OxSbFmX3hietEMyuZNQ7Oc9Gt95gyY3M8hYo7VLhLeBK7XJG6D\nMaIVokQ9IqliJiK5su1UCp0Ig6cHDf8ZGI7Yqx3aSJwxaBGhZm3j2B0CgYEA+0QX\ni6Q2vh43Haf2YWwExKrdeD4HjB4zAq4DFIeDeuWefQhnqPKqvxJwz3Kpp8cLHYjV\nIP2cY8pHMFVOi8TP9H8WpJISdKEJwsRunIwz76Xl9+ArrU9cEaoahDdb/Xrqw818\nsMjkH1Rjtcev3/QJp/zHJfxc6ZHXksWYHlbTsSMCgYBRr+mSn5QLSoRlPpSzO5IQ\ntXS4jMnvyQ4BMvovaBKhAyauz1FoFEwmmyikAjMIX+GncJgBNHleUo7Ezza8H0tV\nrOvBU4TH4WGoStSi/0ANgB8SqVDAKhh1lAwGmxZQqEvsQc177/dLyXUCaMSYuIaI\nGFpD5wIzlyJkk4MMRSp87QKBgGlmN8ZA3SHFBPOwuD5HlHx2/C3rPzk8lcNDAVHE\nQpfz6Bakxu7s1EkQUDgE7jvN19DMzDJpkAegG1qf/jHNHjp+cR4ZlBpOTwzfX1LV\n0Rdu7NectlWd244hX7wkiLb8r6vw76QssNyfhrADEriL4t0PwO4jPUpQ/i+4KUZY\nv7YnAoGBAIVLG3qbEhA3nh+tXtr+xpb+3zVruTTiFpeSJgm9vXAgA6c1vS0boNIH\nRyvU3qioBwcbuAQgpydBPGw5OelBzucXHdFMXLw90iYm/mrW/Uhyrkb6e8PTGWBE\nHaUTp4D1YynUel0GBxZd9os9y2Q64oRaTYwGLS2dHOuDTHg9eVTO\n-----END RSA PRIVATE KEY-----'''\n\n# Some versions of OpenSSH generate these (slightly different keys): the PKCS#1\n# structure is wrapped in an extra ASN.1 SEQUENCE and there's an empty SEQUENCE\n# following it. It is not any standard key format and was probably a bug in\n# OpenSSH at some point.\nprivateRSA_openssh_alternate = b\"\"\"-----BEGIN RSA PRIVATE KEY-----\nMIIEqTCCBKMCAQACggEBANVqrHgj1tYb7CWhUMR3Y1CERQFVQhQqKuDQYO7U6aOtSvo5Bl6EVXVf\nADa/b6oqP4MmN8FpLlv98PPSfdaYzTpAeNXKqBjAEZMkCQyBTI/3nO0TFmqkBOlJd8PkVWSzeWie\nLAjrrOgELSF3BaeO71MwDaXluz1q4gk2b/00031vRv+H2qkpJ6r/rfWF5j4auHodSrHqwFr3MN8f\nwqTk7z+RSZZA1Rl3LTfDXuydpjpEpcKkKd3Vupw9RbPGLBhk1bo936t/zUKsp/EYC6BYFWILpCpu\nQ8PkBJ81o0eORu0zpWW9vDspbgILV9906BO0NzV+g18gJmCm3K2Lxmx5mPcCAwEAAQKCAQAhTAhm\noijVtPuOD3IbhQkAufJON/AcV0vjUX+eI6fkOphVG+qLepgevNi6sfmJEhhgrOjMC04JWkBqui+Z\n+LMkYIS5zmmVmvni/B9RTScV2ysnre+0aay+fRDrhkdwc7QAh5UVOzf55xTngLtoHhvm3btzY7ln\n5rInf8/PMJvCmP3ZGDYvNi7xPYF6n+EDLUfbNFFiOd1P6ayoi9nW84TEF7lxnQYIQnhNu8Uq9MNY\nzVUr7b4zXwTqe+YEJGPyLdc9G2zVnGNDL5KIjT5u2hg32A8lZ4kduUY0XsnOxIvtklozBw/fhgj5\nkunb6zgINsnNzQoBSFs5PnrKxoCp3NQ5AoGBANlwBtjivNR4kVCU1MEbiThsRmRaUaCaBz1IjwNR\nzGsSjn0asWXncXU54DIFdY0YTK+TsUmxZl94YnrRDMrmTUOznPRrfeYMmNzPIWKO1S4S3gSu1yRu\ngzGiFaJEPSKpYiYiubLtVAqdCIOnBw3/GRiO2Ksd2kicMWgRoWZt49gdAoGBAPtEF4ukNr4eNx2n\n9mFsBMSq3Xg+B4weMwKuAxSHg3rlnn0IZ6jyqr8ScM9yqafHCx2I1SD9nGPKRzBVTovEz/R/FqSS\nEnShCcLEbpyMM++l5ffgK61PXBGqGoQ3W/166sPNfLDI5B9UY7XHr9/0Caf8xyX8XOmR15LFmB5W\n07EjAoGAUa/pkp+UC0qEZT6UszuSELV0uIzJ78kOATL6L2gSoQMmrs9RaBRMJpsopAIzCF/hp3CY\nATR5XlKOxM82vB9LVazrwVOEx+FhqErUov9ADYAfEqlQwCoYdZQMBpsWUKhL7EHNe+/3S8l1AmjE\nmLiGiBhaQ+cCM5ciZJODDEUqfO0CgYBpZjfGQN0hxQTzsLg+R5R8dvwt6z85PJXDQwFRxEKX8+gW\npMbu7NRJEFA4BO47zdfQzMwyaZAHoBtan/4xzR46fnEeGZQaTk8M319S1dEXbuzXnLZVnduOIV+8\nJIi2/K+r8O+kLLDcn4awAxK4i+LdD8DuIz1KUP4vuClGWL+2JwKBgQCFSxt6mxIQN54frV7a/saW\n/t81a7k04haXkiYJvb1wIAOnNb0tG6DSB0cr1N6oqAcHG7gEIKcnQTxsOTnpQc7nFx3RTFy8PdIm\nJv5q1v1Icq5G+nvD0xlgRB2lE6eA9WMp1HpdBgcWXfaLPctkOuKEWk2MBi0tnRzrg0x4PXlUzjAA\n-----END RSA PRIVATE KEY-----\"\"\"\n\n# New format introduced in OpenSSH 6.5\nprivateRSA_openssh_new = b'''-----BEGIN OPENSSH PRIVATE KEY-----\nb3BlbnNzaC1rZXktdjEAAAAABG5vbmUAAAAEbm9uZQAAAAAAAAABAAABFwAAAAdzc2gtcn\nNhAAAAAwEAAQAAAQEA1WqseCPW1hvsJaFQxHdjUIRFAVVCFCoq4NBg7tTpo61K+jkGXoRV\ndV8ANr9vqio/gyY3wWkuW/3w89J91pjNOkB41cqoGMARkyQJDIFMj/ec7RMWaqQE6Ul3w+\nRVZLN5aJ4sCOus6AQtIXcFp47vUzANpeW7PWriCTZv/TTTfW9G/4faqSknqv+t9YXmPhq4\neh1KserAWvcw3x/CpOTvP5FJlkDVGXctN8Ne7J2mOkSlwqQp3dW6nD1Fs8YsGGTVuj3fq3\n/NQqyn8RgLoFgVYgukKm5Dw+QEnzWjR45G7TOlZb28OyluAgtX33ToE7Q3NX6DXyAmYKbc\nrYvGbHmY9wAAA7gXkBoMF5AaDAAAAAdzc2gtcnNhAAABAQDVaqx4I9bWG+wloVDEd2NQhE\nUBVUIUKirg0GDu1OmjrUr6OQZehFV1XwA2v2+qKj+DJjfBaS5b/fDz0n3WmM06QHjVyqgY\nwBGTJAkMgUyP95ztExZqpATpSXfD5FVks3loniwI66zoBC0hdwWnju9TMA2l5bs9auIJNm\n/9NNN9b0b/h9qpKSeq/631heY+Grh6HUqx6sBa9zDfH8Kk5O8/kUmWQNUZdy03w17snaY6\nRKXCpCnd1bqcPUWzxiwYZNW6Pd+rf81CrKfxGAugWBViC6QqbkPD5ASfNaNHjkbtM6Vlvb\nw7KW4CC1ffdOgTtDc1foNfICZgptyti8ZseZj3AAAAAwEAAQAAAQAhTAhmoijVtPuOD3Ib\nhQkAufJON/AcV0vjUX+eI6fkOphVG+qLepgevNi6sfmJEhhgrOjMC04JWkBqui+Z+LMkYI\nS5zmmVmvni/B9RTScV2ysnre+0aay+fRDrhkdwc7QAh5UVOzf55xTngLtoHhvm3btzY7ln\n5rInf8/PMJvCmP3ZGDYvNi7xPYF6n+EDLUfbNFFiOd1P6ayoi9nW84TEF7lxnQYIQnhNu8\nUq9MNYzVUr7b4zXwTqe+YEJGPyLdc9G2zVnGNDL5KIjT5u2hg32A8lZ4kduUY0XsnOxIvt\nklozBw/fhgj5kunb6zgINsnNzQoBSFs5PnrKxoCp3NQ5AAAAgQCFSxt6mxIQN54frV7a/s\naW/t81a7k04haXkiYJvb1wIAOnNb0tG6DSB0cr1N6oqAcHG7gEIKcnQTxsOTnpQc7nFx3R\nTFy8PdImJv5q1v1Icq5G+nvD0xlgRB2lE6eA9WMp1HpdBgcWXfaLPctkOuKEWk2MBi0tnR\nzrg0x4PXlUzgAAAIEA2XAG2OK81HiRUJTUwRuJOGxGZFpRoJoHPUiPA1HMaxKOfRqxZedx\ndTngMgV1jRhMr5OxSbFmX3hietEMyuZNQ7Oc9Gt95gyY3M8hYo7VLhLeBK7XJG6DMaIVok\nQ9IqliJiK5su1UCp0Ig6cHDf8ZGI7Yqx3aSJwxaBGhZm3j2B0AAACBAPtEF4ukNr4eNx2n\n9mFsBMSq3Xg+B4weMwKuAxSHg3rlnn0IZ6jyqr8ScM9yqafHCx2I1SD9nGPKRzBVTovEz/\nR/FqSSEnShCcLEbpyMM++l5ffgK61PXBGqGoQ3W/166sPNfLDI5B9UY7XHr9/0Caf8xyX8\nXOmR15LFmB5W07EjAAAAAAEC\n-----END OPENSSH PRIVATE KEY-----'''\n\n# Encrypted with the passphrase 'encrypted'\nprivateRSA_openssh_encrypted = b\"\"\"-----BEGIN RSA PRIVATE KEY-----\nProc-Type: 4,ENCRYPTED\nDEK-Info: DES-EDE3-CBC,FFFFFFFFFFFFFFFF\n\nqRwdy/fEJQbRccoyOdhJCQv5FpsbSJWtvOTLjrURDrjpO0WvOsvwV/ltLAZtD8b3\nCSlgi8eGZk+rFKNMn1uUWuVeQR3Mfn2PE2hgB0Qc0HkdfG92cnVzoRjKRQxxJM5o\nF4/1MSLhwQxLF53DHWfyzK8rFNUBRyRRBFevXwPfbp6DhFy+TkqOcrLufJT7x7BC\nMvMNjILVhNr9hnIMkzmAiBo9lhJ0CHdWhcQHaX7Wk6UcGNDsYrwBoLlKPQlEGMU1\n2scCi1UAbCilVLyUpHFuQeCzJHBl0YuLjwmo1kSv9U5E4ysh/FIuRf3aW91OK1+y\n5rPE+zJYnzNAZ/Rl9xqtvTh8hlMwjdt582HbiJb6zJw5/NEz9OKyaJjjqZsZQ1TY\nGOhV0Oqwx54jpkCh0XwJ2ofmcNuiO8LoUVBE124pa6ePSxLorqBhtq9nTgwUv1Mx\nlFioAM6xGBSugCRZgbapHAw0M/I8Fa95A2ocRgx0N6TMp3ZBVltovb8pZrAGld3L\nT5VWGDl3ZX/eM8YlXDupewOpb56g55Aevl0jERktqJdl+g9D+PXnCsJgxMcJbfl5\ntWY9KoMxV+2Fj68SHdr/acCp7xgUMwHvVLFfYCeK/hpEe9O8vOAMTlXuq9zCMDAx\nkL2kcSFbZHerc4TijtjXEALo06gYHEcLRtI6lvYrzbbmpCD7J7AnMzS3SQ2FzbFM\nGARKfxBnYp0dZTDiY5HE45r8xWzUupoFcIuxKtuhBEtT7H2Ynv1NmU9qQRj8C1U5\nLgM3lVEkrh4o1aBIAqX0OA4do08h2pdp9v0E4HKtCjSL5EBC6xrxmIY6b6dwCDLU\nn16mv4jeKGy2IKvnF9r8HXdUG0yisNGxeq5Uf7STGH5KcCRrJCBZbawAbwURaLRo\nHVydDP+5uEMMVjULpYgtuNo6gw6NczOhzgYAm3v2ZMjmZ8gclOsbRrH74XiOV8kd\n89oYN5yNHD2EBqP5271kbmsYZ3VwBGN+HUdWIDi3gbFfHcmy59YQt09mZIMMwD7r\nnRK+AKfBnNeMK9yZkkTRs3FwY4ZJdYn58pWfe4DNqMI7U5BQ9QZnLkfGLUqWtghX\njrselJrtSEMkll+feFf7jxiCKAwC/cWe1cvukjYPA6k75Wv7RaDENfwMlZtN+pfl\npzKqId20HhMNOceaeZagL+xzM1RRj+VcXR9BWfHI2AXZPcpTGAJwDOoQA64L9YGW\n7QzxHmcDTlV0e59CpAdCLj//rQxFpYnuuJlwV2YyHYnvzfxsVge7u5ApcuBpNTjf\nN46Heh24xXfqfM7OcO3BB71VfcvCNQavsp70PAtj4loShX6FpzatNX0iZasB988E\nTtuiJ+9e7vH0xEhBLJIUJT9LvMto25KLHFHwSQXKEXM+hiY2nfObc1Cku4lBmy+7\nuWpZrh3hkmKUtfdiyeqUUj1ypwZ6boZO1UZo0xTrpubmKQEvd2957YrEEVsi0LeB\nuEzSlUXrwIV7Qw2VhoLxIaCyl5j4nOKetUeAjqVNi9makh0x4Ion5osxxYvYS9s/\nY48ATMnwm3+CdN6LE3IykHyHs7JuZmawWDR4CKJB6M1r0X+Xwgs0tQ==\n-----END RSA PRIVATE KEY-----\"\"\"\n\n# Encrypted with the passphrase 'encrypted', and using the new format\n# introduced in OpenSSH 6.5\nprivateRSA_openssh_encrypted_new = b\"\"\"-----BEGIN OPENSSH PRIVATE KEY-----\nb3BlbnNzaC1rZXktdjEAAAAACmFlczI1Ni1jdHIAAAAGYmNyeXB0AAAAGAAAABD0f9WAof\nDTbmwztb8pdrSeAAAAEAAAAAEAAAEXAAAAB3NzaC1yc2EAAAADAQABAAABAQDVaqx4I9bW\nG+wloVDEd2NQhEUBVUIUKirg0GDu1OmjrUr6OQZehFV1XwA2v2+qKj+DJjfBaS5b/fDz0n\n3WmM06QHjVyqgYwBGTJAkMgUyP95ztExZqpATpSXfD5FVks3loniwI66zoBC0hdwWnju9T\nMA2l5bs9auIJNm/9NNN9b0b/h9qpKSeq/631heY+Grh6HUqx6sBa9zDfH8Kk5O8/kUmWQN\nUZdy03w17snaY6RKXCpCnd1bqcPUWzxiwYZNW6Pd+rf81CrKfxGAugWBViC6QqbkPD5ASf\nNaNHjkbtM6Vlvbw7KW4CC1ffdOgTtDc1foNfICZgptyti8ZseZj3AAADwPQaac8s1xX3af\nhQTQexj0vEAWDQsLYzDHN9G7W+UP5WHUu7igeu2GqAC/TOnjUXDP73I+EN3n7T3JFeDRfs\nU1Z6Zqb0NKHSRVYwDIdIi8qVohFv85g6+xQ01OpaoOzz+vI34OUvCRHQGTgR6L9fQShZyC\nMcopYMYfbIse6KcqkfxX3KSdG1Pao6Njx/ShFRbgvmALpR/z0EaGCzHCDxpfUyAdnxm621\nJzaf+LverWdN7sfrfMptaS9//9iJb70sL67K+YIB64qhDnA/w9UOQfXGQFL+AEtdM0BPv8\nthP1bs7T0yucBl+ZXdrDKVLZfaS3S/w85Jlgfu+a1DG73pOBOuag435iEJ9EnspjXiiydx\nGrfSRk2C+/c4fBDZVGFscK5bfQuUUZyU1qOagekxX7WLHFKk9xajnud+nrAN070SeNwlX8\nFZ2CI4KGlQfDvVUpKanYn8Kkj3fZ+YBGyx4M+19clF65FKSM0x1Rrh5tAmNT/SNDbSc28m\nASxrBhztzxUFTrIn3tp+uqkJniFLmFsUtiAUmj8fNyE9blykU7dqq+CqpLA872nQ9bOHHA\nJsS1oBYmQ0n6AJz8WrYMdcepqWVld6Q8QSD1zdrY/sAWUovuBA1s4oIEXZhpXSS4ZJiMfh\nPVktKBwj5bmoG/mmwYLbo0JHntK8N3TGTzTGLq5TpSBBdVvWSWo7tnfEkrFObmhi1uJSrQ\n3zfPVP6BguboxBv+oxhaUBK8UOANe6ZwM4vfiu+QN+sZqWymHIfAktz7eWzwlToe4cKpdG\nUv+e3/7Lo2dyMl3nke5HsSUrlsMGPREuGkBih8+o85ii6D+cuCiVtus3f5c78Cir80zLIr\nZ0wWvEAjciEvml00DWaA+JIaOrWwvXySaOzFGpCqC9SQjao379bvn9P3b7kVZsy6zBfHqm\nbNEJUOuhBZaY8Okz36chh1xqh4sz7m3nsZ3GYGcvM+3mvRY72QnqsQEG0Sp1XYIn2bHa29\ntqp7CG9X8J6dqMcPeoPRDWIX9gw7EPl/M0LP6xgewGJ9bgxwle6Mnr9kNITIswjAJqrLec\nzx7dfixjAPc42ADqrw/tEdFQcSqxigcfJNKO1LbDBjh+Hk/cSBou2PoxbIcl0qfQfbGcqI\nDbpd695IEuiW9pYR22txNoIi+7cbMsuFHxQ/OqbrX/jCsprGNNJLAjgGsVEI1JnHWDH0db\n3UbqbOHAeY3ufoYXNY1utVOIACpW3r9wBw3FjRi04d70VcKr16OXvOAHGN2G++Y+kMya84\nHl/Kt/gA==\n-----END OPENSSH PRIVATE KEY-----\"\"\"\n\n# Encrypted with the passphrase 'testxp'. NB: this key was generated by\n# OpenSSH, so it doesn't use the same key data as the other keys here.\nprivateRSA_openssh_encrypted_aes = b\"\"\"-----BEGIN RSA PRIVATE KEY-----\nProc-Type: 4,ENCRYPTED\nDEK-Info: AES-128-CBC,0673309A6ACCAB4B77DEE1C1E536AC26\n\n4Ed/a9OgJWHJsne7yOGWeWMzHYKsxuP9w1v0aYcp+puS75wvhHLiUnNwxz0KDi6n\nT3YkKLBsoCWS68ApR2J9yeQ6R+EyS+UQDrO9nwqo3DB5BT3Ggt8S1wE7vjNLQD0H\ng/SJnlqwsECNhh8aAx+Ag0m3ZKOZiRD5mCkcDQsZET7URSmFytDKOjhFn3u6ZFVB\nsXrfpYc6TJtOQlHd/52JB6aAbjt6afSv955Z7enIi+5yEJ5y7oYQTaE5zrFMP7N5\n9LbfJFlKXxEddy/DErRLxEjmC+t4svHesoJKc2jjjyNPiOoGGF3kJXea62vsjdNV\ngMK5Eged3TBVIk2dv8rtJUvyFeCUtjQ1UJZIebScRR47KrbsIpCmU8I4/uHWm5hW\n0mOwvdx1L/mqx/BHqVU9Dw2COhOdLbFxlFI92chkovkmNk4P48ziyVnpm7ME22sE\nvfCMsyirdqB1mrL4CSM7FXONv+CgfBfeYVkYW8RfJac9U1L/O+JNn7yee414O/rS\nhRYw4UdWnH6Gg6niklVKWNY0ZwUZC8zgm2iqy8YCYuneS37jC+OEKP+/s6HSKuqk\n2bzcl3/TcZXNSM815hnFRpz0anuyAsvwPNRyvxG2/DacJHL1f6luV4B0o6W410yf\nqXQx01DLo7nuyhJqoH3UGCyyXB+/QUs0mbG2PAEn3f5dVs31JMdbt+PrxURXXjKk\n4cexpUcIpqqlfpIRe3RD0sDVbH4OXsGhi2kiTfPZu7mgyFxKopRbn1KwU1qKinfY\nEU9O4PoTak/tPT+5jFNhaP+HrURoi/pU8EAUNSktl7xAkHYwkN/9Cm7DeBghgf3n\n8+tyCGYDsB5utPD0/Xe9yx0Qhc/kMm4xIyQDyA937dk3mUvLC9vulnAP8I+Izim0\nfZ182+D1bWwykoD0997mUHG/AUChWR01V1OLwRyPv2wUtiS8VNG76Y2aqKlgqP1P\nV+IvIEqR4ERvSBVFzXNF8Y6j/sVxo8+aZw+d0L1Ns/R55deErGg3B8i/2EqGd3r+\n0jps9BqFHHWW87n3VyEB3jWCMj8Vi2EJIfa/7pSaViFIQn8LiBLf+zxG5LTOToK5\nxkN42fReDcqi3UNfKNGnv4dsplyTR2hyx65lsj4bRKDGLKOuB1y7iB0AGb0LtcAI\ndcsVlcCeUquDXtqKvRnwfIMg+ZunyjqHBhj3qgRgbXbT6zjaSdNnih569aTg0Vup\nVykzZ7+n/KVcGLmvX0NesdoI7TKbq4TnEIOynuG5Sf+2GpARO5bjcWKSZeN/Ybgk\ngccf8Cqf6XWqiwlWd0B7BR3SymeHIaSymC45wmbgdstrbk7Ppa2Tp9AZku8M2Y7c\n8mY9b+onK075/ypiwBm4L4GRNTFLnoNQJXx0OSl4FNRWsn6ztbD+jZhu8Seu10Jw\nSEJVJ+gmTKdRLYORJKyqhDet6g7kAxs4EoJ25WsOnX5nNr00rit+NkMPA7xbJT+7\nCfI51GQLw7pUPeO2WNt6yZO/YkzZrqvTj5FEwybkUyBv7L0gkqu9wjfDdUw0fVHE\nxEm4DxjEoaIp8dW/JOzXQ2EF+WaSOgdYsw3Ac+rnnjnNptCdOEDGP6QBkt+oXj4P\n-----END RSA PRIVATE KEY-----\"\"\"\n\npublicRSA_lsh = (\n    b'{KDEwOnB1YmxpYy1rZXkoMTQ6cnNhLXBrY3MxLXNoYTEoMTpuMjU3OgDVaqx4I9bWG+wloVD'\n    b'Ed2NQhEUBVUIUKirg0GDu1OmjrUr6OQZehFV1XwA2v2+qKj+DJjfBaS5b/fDz0n3WmM06QHj'\n    b'VyqgYwBGTJAkMgUyP95ztExZqpATpSXfD5FVks3loniwI66zoBC0hdwWnju9TMA2l5bs9auI'\n    b'JNm/9NNN9b0b/h9qpKSeq/631heY+Grh6HUqx6sBa9zDfH8Kk5O8/kUmWQNUZdy03w17snaY'\n    b'6RKXCpCnd1bqcPUWzxiwYZNW6Pd+rf81CrKfxGAugWBViC6QqbkPD5ASfNaNHjkbtM6Vlvbw'\n    b'7KW4CC1ffdOgTtDc1foNfICZgptyti8ZseZj3KSgxOmUzOgEAASkpKQ==}'\n)\n\nprivateRSA_lsh = (\n    b\"(11:private-key(9:rsa-pkcs1(1:n257:\\x00\\xd5j\\xacx#\\xd6\\xd6\\x1b\\xec%\\xa1P\"\n    b\"\\xc4wcP\\x84E\\x01UB\\x14**\\xe0\\xd0`\\xee\\xd4\\xe9\\xa3\\xadJ\\xfa9\\x06^\\x84Uu_\"\n    b\"\\x006\\xbfo\\xaa*?\\x83&7\\xc1i.[\\xfd\\xf0\\xf3\\xd2}\\xd6\\x98\\xcd:@x\\xd5\\xca\"\n    b\"\\xa8\\x18\\xc0\\x11\\x93$\\t\\x0c\\x81L\\x8f\\xf7\\x9c\\xed\\x13\\x16j\\xa4\\x04\\xe9Iw\"\n    b\"\\xc3\\xe4Ud\\xb3yh\\x9e,\\x08\\xeb\\xac\\xe8\\x04-!w\\x05\\xa7\\x8e\\xefS0\\r\\xa5\\xe5\"\n    b\"\\xbb=j\\xe2\\t6o\\xfd4\\xd3}oF\\xff\\x87\\xda\\xa9)'\\xaa\\xff\\xad\\xf5\\x85\\xe6>\"\n    b\"\\x1a\\xb8z\\x1dJ\\xb1\\xea\\xc0Z\\xf70\\xdf\\x1f\\xc2\\xa4\\xe4\\xef?\\x91I\\x96@\\xd5\"\n    b\"\\x19w-7\\xc3^\\xec\\x9d\\xa6:D\\xa5\\xc2\\xa4)\\xdd\\xd5\\xba\\x9c=E\\xb3\\xc6,\\x18d\"\n    b\"\\xd5\\xba=\\xdf\\xab\\x7f\\xcdB\\xac\\xa7\\xf1\\x18\\x0b\\xa0X\\x15b\\x0b\\xa4*nC\\xc3\"\n    b\"\\xe4\\x04\\x9f5\\xa3G\\x8eF\\xed3\\xa5e\\xbd\\xbc;)n\\x02\\x0bW\\xdft\\xe8\\x13\\xb475\"\n    b\"~\\x83_ &`\\xa6\\xdc\\xad\\x8b\\xc6ly\\x98\\xf7)(1:e3:\\x01\\x00\\x01)(1:d256:!L\"\n    b\"\\x08f\\xa2(\\xd5\\xb4\\xfb\\x8e\\x0fr\\x1b\\x85\\t\\x00\\xb9\\xf2N7\\xf0\\x1cWK\\xe3Q\"\n    b\"\\x7f\\x9e#\\xa7\\xe4:\\x98U\\x1b\\xea\\x8bz\\x98\\x1e\\xbc\\xd8\\xba\\xb1\\xf9\\x89\\x12\"\n    b\"\\x18`\\xac\\xe8\\xcc\\x0bN\\tZ@j\\xba/\\x99\\xf8\\xb3$`\\x84\\xb9\\xcei\\x95\\x9a\\xf9\"\n    b\"\\xe2\\xfc\\x1fQM'\\x15\\xdb+'\\xad\\xef\\xb4i\\xac\\xbe}\\x10\\xeb\\x86Gps\\xb4\\x00\"\n    b\"\\x87\\x95\\x15;7\\xf9\\xe7\\x14\\xe7\\x80\\xbbh\\x1e\\x1b\\xe6\\xdd\\xbbsc\\xb9g\\xe6\"\n    b\"\\xb2'\\x7f\\xcf\\xcf0\\x9b\\xc2\\x98\\xfd\\xd9\\x186/6.\\xf1=\\x81z\\x9f\\xe1\\x03-G\"\n    b\"\\xdb4Qb9\\xddO\\xe9\\xac\\xa8\\x8b\\xd9\\xd6\\xf3\\x84\\xc4\\x17\\xb9q\\x9d\\x06\\x08Bx\"\n    b\"M\\xbb\\xc5*\\xf4\\xc3X\\xcdU+\\xed\\xbe3_\\x04\\xea{\\xe6\\x04$c\\xf2-\\xd7=\\x1bl\"\n    b\"\\xd5\\x9ccC/\\x92\\x88\\x8d>n\\xda\\x187\\xd8\\x0f%g\\x89\\x1d\\xb9F4^\\xc9\\xce\\xc4\"\n    b\"\\x8b\\xed\\x92Z3\\x07\\x0f\\xdf\\x86\\x08\\xf9\\x92\\xe9\\xdb\\xeb8\\x086\\xc9\\xcd\\xcd\"\n    b\"\\n\\x01H[9>z\\xca\\xc6\\x80\\xa9\\xdc\\xd49)(1:p129:\\x00\\xfbD\\x17\\x8b\\xa46\\xbe\"\n    b\"\\x1e7\\x1d\\xa7\\xf6al\\x04\\xc4\\xaa\\xddx>\\x07\\x8c\\x1e3\\x02\\xae\\x03\\x14\\x87\"\n    b\"\\x83z\\xe5\\x9e}\\x08g\\xa8\\xf2\\xaa\\xbf\\x12p\\xcfr\\xa9\\xa7\\xc7\\x0b\\x1d\\x88\"\n    b\"\\xd5 \\xfd\\x9cc\\xcaG0UN\\x8b\\xc4\\xcf\\xf4\\x7f\\x16\\xa4\\x92\\x12t\\xa1\\t\\xc2\"\n    b\"\\xc4n\\x9c\\x8c3\\xef\\xa5\\xe5\\xf7\\xe0+\\xadO\\\\\\x11\\xaa\\x1a\\x847[\\xfdz\\xea\"\n    b\"\\xc3\\xcd|\\xb0\\xc8\\xe4\\x1fTc\\xb5\\xc7\\xaf\\xdf\\xf4\\t\\xa7\\xfc\\xc7%\\xfc\\\\\\xe9\"\n    b\"\\x91\\xd7\\x92\\xc5\\x98\\x1eV\\xd3\\xb1#)(1:q129:\\x00\\xd9p\\x06\\xd8\\xe2\\xbc\\xd4\"\n    b\"x\\x91P\\x94\\xd4\\xc1\\x1b\\x898lFdZQ\\xa0\\x9a\\x07=H\\x8f\\x03Q\\xcck\\x12\\x8e}\"\n    b\"\\x1a\\xb1e\\xe7qu9\\xe02\\x05u\\x8d\\x18L\\xaf\\x93\\xb1I\\xb1f_xbz\\xd1\\x0c\\xca\"\n    b\"\\xe6MC\\xb3\\x9c\\xf4k}\\xe6\\x0c\\x98\\xdc\\xcf!b\\x8e\\xd5.\\x12\\xde\\x04\\xae\\xd7$\"\n    b\"n\\x831\\xa2\\x15\\xa2D=\\\"\\xa9b&\\\"\\xb9\\xb2\\xedT\\n\\x9d\\x08\\x83\\xa7\\x07\\r\\xff\"\n    b\"\\x19\\x18\\x8e\\xd8\\xab\\x1d\\xdaH\\x9c1h\\x11\\xa1fm\\xe3\\xd8\\x1d)(1:a128:if7\"\n    b\"\\xc6@\\xdd!\\xc5\\x04\\xf3\\xb0\\xb8>G\\x94|v\\xfc-\\xeb?9<\\x95\\xc3C\\x01Q\\xc4B\"\n    b\"\\x97\\xf3\\xe8\\x16\\xa4\\xc6\\xee\\xec\\xd4I\\x10P8\\x04\\xee;\\xcd\\xd7\\xd0\\xcc\\xcc\"\n    b\"2i\\x90\\x07\\xa0\\x1bZ\\x9f\\xfe1\\xcd\\x1e:~q\\x1e\\x19\\x94\\x1aNO\\x0c\\xdf_R\\xd5\"\n    b\"\\xd1\\x17n\\xec\\xd7\\x9c\\xb6U\\x9d\\xdb\\x8e!_\\xbc$\\x88\\xb6\\xfc\\xaf\\xab\\xf0\"\n    b\"\\xef\\xa4,\\xb0\\xdc\\x9f\\x86\\xb0\\x03\\x12\\xb8\\x8b\\xe2\\xdd\\x0f\\xc0\\xee#=JP\"\n    b\"\\xfe/\\xb8)FX\\xbf\\xb6')(1:b128:Q\\xaf\\xe9\\x92\\x9f\\x94\\x0bJ\\x84e>\\x94\\xb3;\"\n    b\"\\x92\\x10\\xb5t\\xb8\\x8c\\xc9\\xef\\xc9\\x0e\\x012\\xfa/h\\x12\\xa1\\x03&\\xae\\xcfQh\"\n    b\"\\x14L&\\x9b(\\xa4\\x023\\x08_\\xe1\\xa7p\\x98\\x014y^R\\x8e\\xc4\\xcf6\\xbc\\x1fKU\"\n    b\"\\xac\\xeb\\xc1S\\x84\\xc7\\xe1a\\xa8J\\xd4\\xa2\\xff@\\r\\x80\\x1f\\x12\\xa9P\\xc0*\\x18\"\n    b\"u\\x94\\x0c\\x06\\x9b\\x16P\\xa8K\\xecA\\xcd{\\xef\\xf7K\\xc9u\\x02h\\xc4\\x98\\xb8\\x86\"\n    b\"\\x88\\x18ZC\\xe7\\x023\\x97\\\"d\\x93\\x83\\x0cE*|\\xed)(1:c129:\\x00\\x85K\\x1bz\\x9b\"\n    b\"\\x12\\x107\\x9e\\x1f\\xad^\\xda\\xfe\\xc6\\x96\\xfe\\xdf5k\\xb94\\xe2\\x16\\x97\\x92&\\t\"\n    b\"\\xbd\\xbdp \\x03\\xa75\\xbd-\\x1b\\xa0\\xd2\\x07G+\\xd4\\xde\\xa8\\xa8\\x07\\x07\\x1b\"\n    b\"\\xb8\\x04 \\xa7'A<l99\\xe9A\\xce\\xe7\\x17\\x1d\\xd1L\\\\\\xbc=\\xd2&&\\xfej\\xd6\\xfd\"\n    b\"Hr\\xaeF\\xfa{\\xc3\\xd3\\x19`D\\x1d\\xa5\\x13\\xa7\\x80\\xf5c)\\xd4z]\\x06\\x07\\x16]\"\n    b\"\\xf6\\x8b=\\xcbd:\\xe2\\x84ZM\\x8c\\x06--\\x9d\\x1c\\xeb\\x83Lx=yT\\xce)))\"\n)\n\nprivateRSA_agentv3 = (\n    b\"\\x00\\x00\\x00\\x07ssh-rsa\\x00\\x00\\x00\\x03\\x01\\x00\\x01\\x00\\x00\\x01\\x00!L\"\n    b\"\\x08f\\xa2(\\xd5\\xb4\\xfb\\x8e\\x0fr\\x1b\\x85\\t\\x00\\xb9\\xf2N7\\xf0\\x1cWK\\xe3Q\"\n    b\"\\x7f\\x9e#\\xa7\\xe4:\\x98U\\x1b\\xea\\x8bz\\x98\\x1e\\xbc\\xd8\\xba\\xb1\\xf9\\x89\\x12\"\n    b\"\\x18`\\xac\\xe8\\xcc\\x0bN\\tZ@j\\xba/\\x99\\xf8\\xb3$`\\x84\\xb9\\xcei\\x95\\x9a\\xf9\"\n    b\"\\xe2\\xfc\\x1fQM'\\x15\\xdb+'\\xad\\xef\\xb4i\\xac\\xbe}\\x10\\xeb\\x86Gps\\xb4\\x00\"\n    b\"\\x87\\x95\\x15;7\\xf9\\xe7\\x14\\xe7\\x80\\xbbh\\x1e\\x1b\\xe6\\xdd\\xbbsc\\xb9g\\xe6\"\n    b\"\\xb2'\\x7f\\xcf\\xcf0\\x9b\\xc2\\x98\\xfd\\xd9\\x186/6.\\xf1=\\x81z\\x9f\\xe1\\x03-G\"\n    b\"\\xdb4Qb9\\xddO\\xe9\\xac\\xa8\\x8b\\xd9\\xd6\\xf3\\x84\\xc4\\x17\\xb9q\\x9d\\x06\\x08Bx\"\n    b\"M\\xbb\\xc5*\\xf4\\xc3X\\xcdU+\\xed\\xbe3_\\x04\\xea{\\xe6\\x04$c\\xf2-\\xd7=\\x1bl\"\n    b\"\\xd5\\x9ccC/\\x92\\x88\\x8d>n\\xda\\x187\\xd8\\x0f%g\\x89\\x1d\\xb9F4^\\xc9\\xce\\xc4\"\n    b\"\\x8b\\xed\\x92Z3\\x07\\x0f\\xdf\\x86\\x08\\xf9\\x92\\xe9\\xdb\\xeb8\\x086\\xc9\\xcd\\xcd\"\n    b\"\\n\\x01H[9>z\\xca\\xc6\\x80\\xa9\\xdc\\xd49\\x00\\x00\\x01\\x01\\x00\\xd5j\\xacx#\\xd6\"\n    b\"\\xd6\\x1b\\xec%\\xa1P\\xc4wcP\\x84E\\x01UB\\x14**\\xe0\\xd0`\\xee\\xd4\\xe9\\xa3\\xadJ\"\n    b\"\\xfa9\\x06^\\x84Uu_\\x006\\xbfo\\xaa*?\\x83&7\\xc1i.[\\xfd\\xf0\\xf3\\xd2}\\xd6\\x98\"\n    b\"\\xcd:@x\\xd5\\xca\\xa8\\x18\\xc0\\x11\\x93$\\t\\x0c\\x81L\\x8f\\xf7\\x9c\\xed\\x13\\x16j\"\n    b\"\\xa4\\x04\\xe9Iw\\xc3\\xe4Ud\\xb3yh\\x9e,\\x08\\xeb\\xac\\xe8\\x04-!w\\x05\\xa7\\x8e\"\n    b\"\\xefS0\\r\\xa5\\xe5\\xbb=j\\xe2\\t6o\\xfd4\\xd3}oF\\xff\\x87\\xda\\xa9)'\\xaa\\xff\\xad\"\n    b\"\\xf5\\x85\\xe6>\\x1a\\xb8z\\x1dJ\\xb1\\xea\\xc0Z\\xf70\\xdf\\x1f\\xc2\\xa4\\xe4\\xef?\"\n    b\"\\x91I\\x96@\\xd5\\x19w-7\\xc3^\\xec\\x9d\\xa6:D\\xa5\\xc2\\xa4)\\xdd\\xd5\\xba\\x9c=E\"\n    b\"\\xb3\\xc6,\\x18d\\xd5\\xba=\\xdf\\xab\\x7f\\xcdB\\xac\\xa7\\xf1\\x18\\x0b\\xa0X\\x15b\"\n    b\"\\x0b\\xa4*nC\\xc3\\xe4\\x04\\x9f5\\xa3G\\x8eF\\xed3\\xa5e\\xbd\\xbc;)n\\x02\\x0bW\\xdf\"\n    b\"t\\xe8\\x13\\xb475~\\x83_ &`\\xa6\\xdc\\xad\\x8b\\xc6ly\\x98\\xf7\\x00\\x00\\x00\\x81\"\n    b\"\\x00\\x85K\\x1bz\\x9b\\x12\\x107\\x9e\\x1f\\xad^\\xda\\xfe\\xc6\\x96\\xfe\\xdf5k\\xb94\"\n    b\"\\xe2\\x16\\x97\\x92&\\t\\xbd\\xbdp \\x03\\xa75\\xbd-\\x1b\\xa0\\xd2\\x07G+\\xd4\\xde\"\n    b\"\\xa8\\xa8\\x07\\x07\\x1b\\xb8\\x04 \\xa7'A<l99\\xe9A\\xce\\xe7\\x17\\x1d\\xd1L\\\\\\xbc=\"\n    b\"\\xd2&&\\xfej\\xd6\\xfdHr\\xaeF\\xfa{\\xc3\\xd3\\x19`D\\x1d\\xa5\\x13\\xa7\\x80\\xf5c)\"\n    b\"\\xd4z]\\x06\\x07\\x16]\\xf6\\x8b=\\xcbd:\\xe2\\x84ZM\\x8c\\x06--\\x9d\\x1c\\xeb\\x83Lx\"\n    b\"=yT\\xce\\x00\\x00\\x00\\x81\\x00\\xd9p\\x06\\xd8\\xe2\\xbc\\xd4x\\x91P\\x94\\xd4\\xc1\"\n    b\"\\x1b\\x898lFdZQ\\xa0\\x9a\\x07=H\\x8f\\x03Q\\xcck\\x12\\x8e}\\x1a\\xb1e\\xe7qu9\\xe02\"\n    b\"\\x05u\\x8d\\x18L\\xaf\\x93\\xb1I\\xb1f_xbz\\xd1\\x0c\\xca\\xe6MC\\xb3\\x9c\\xf4k}\\xe6\"\n    b\"\\x0c\\x98\\xdc\\xcf!b\\x8e\\xd5.\\x12\\xde\\x04\\xae\\xd7$n\\x831\\xa2\\x15\\xa2D=\\\"\"\n    b\"\\xa9b&\\\"\\xb9\\xb2\\xedT\\n\\x9d\\x08\\x83\\xa7\\x07\\r\\xff\\x19\\x18\\x8e\\xd8\\xab\"\n    b\"\\x1d\\xdaH\\x9c1h\\x11\\xa1fm\\xe3\\xd8\\x1d\\x00\\x00\\x00\\x81\\x00\\xfbD\\x17\\x8b\"\n    b\"\\xa46\\xbe\\x1e7\\x1d\\xa7\\xf6al\\x04\\xc4\\xaa\\xddx>\\x07\\x8c\\x1e3\\x02\\xae\\x03\"\n    b\"\\x14\\x87\\x83z\\xe5\\x9e}\\x08g\\xa8\\xf2\\xaa\\xbf\\x12p\\xcfr\\xa9\\xa7\\xc7\\x0b\"\n    b\"\\x1d\\x88\\xd5 \\xfd\\x9cc\\xcaG0UN\\x8b\\xc4\\xcf\\xf4\\x7f\\x16\\xa4\\x92\\x12t\\xa1\"\n    b\"\\t\\xc2\\xc4n\\x9c\\x8c3\\xef\\xa5\\xe5\\xf7\\xe0+\\xadO\\\\\\x11\\xaa\\x1a\\x847[\\xfdz\"\n    b\"\\xea\\xc3\\xcd|\\xb0\\xc8\\xe4\\x1fTc\\xb5\\xc7\\xaf\\xdf\\xf4\\t\\xa7\\xfc\\xc7%\\xfc\\\\\"\n    b\"\\xe9\\x91\\xd7\\x92\\xc5\\x98\\x1eV\\xd3\\xb1#\"\n)\n\npublicDSA_openssh = b\"\"\"\\\nssh-dss AAAAB3NzaC1kc3MAAACBAJKQOsVERVDQIpANHH+JAAylo9\\\nLvFYmFFVMIuHFGlZpIL7sh3IMkqy+cssINM/lnHD3fmsAyLlUXZtt6PD9LgZRazsPOgptuH+Gu48G\\\n+yFuE8l0fVVUivos/MmYVJ66qT99htcZKatrTWZnpVW7gFABoqw+he2LZ0gkeU0+Sx9a5AAAAFQD0\\\nEYmTNaFJ8CS0+vFSF4nYcyEnSQAAAIEAkgLjxHJAE7qFWdTqf7EZngu7jAGmdB9k3YzMHe1ldMxEB\\\n7zNw5aOnxjhoYLtiHeoEcOk2XOyvnE+VfhIWwWAdOiKRTEZlmizkvhGbq0DCe2EPMXirjqWACI5nD\\\nioQX1oEMonR8N3AEO5v9SfBqS2Q9R6OBr6lf04RvwpHZ0UGu8AAACAAhRpxGMIWEyaEh8YnjiazQT\\\nNEpklRZqeBGo1gotJggNmVaIQNIClGlLyCi359efEUuQcZ9SXxM59P+hecc/GU/GHakW5YWE4dP2G\\\ngdgMQWC7S6WFIXePGGXqNQDdWxlX8umhenvQqa1PnKrFRhDrJw8Z7GjdHxflsxCEmXPoLN8= \\\ncomment\\\n\"\"\"\n\nprivateDSA_openssh = b\"\"\"\\\n-----BEGIN DSA PRIVATE KEY-----\nMIIBvAIBAAKBgQCSkDrFREVQ0CKQDRx/iQAMpaPS7xWJhRVTCLhxRpWaSC+7IdyD\nJKsvnLLCDTP5Zxw935rAMi5VF2bbejw/S4GUWs7DzoKbbh/hruPBvshbhPJdH1VV\nIr6LPzJmFSeuqk/fYbXGSmra01mZ6VVu4BQAaKsPoXti2dIJHlNPksfWuQIVAPQR\niZM1oUnwJLT68VIXidhzISdJAoGBAJIC48RyQBO6hVnU6n+xGZ4Lu4wBpnQfZN2M\nzB3tZXTMRAe8zcOWjp8Y4aGC7Yh3qBHDpNlzsr5xPlX4SFsFgHToikUxGZZos5L4\nRm6tAwnthDzF4q46lgAiOZw4qEF9aBDKJ0fDdwBDub/UnwaktkPUejga+pX9OEb8\nKR2dFBrvAoGAAhRpxGMIWEyaEh8YnjiazQTNEpklRZqeBGo1gotJggNmVaIQNICl\nGlLyCi359efEUuQcZ9SXxM59P+hecc/GU/GHakW5YWE4dP2GgdgMQWC7S6WFIXeP\nGGXqNQDdWxlX8umhenvQqa1PnKrFRhDrJw8Z7GjdHxflsxCEmXPoLN8CFQDV2gbL\nczUdxCus0pfEP1bddaXRLQ==\n-----END DSA PRIVATE KEY-----\\\n\"\"\"\n\nprivateDSA_openssh_new = b\"\"\"\\\n-----BEGIN OPENSSH PRIVATE KEY-----\nb3BlbnNzaC1rZXktdjEAAAAABG5vbmUAAAAEbm9uZQAAAAAAAAABAAABsgAAAAdzc2gtZH\nNzAAAAgQCSkDrFREVQ0CKQDRx/iQAMpaPS7xWJhRVTCLhxRpWaSC+7IdyDJKsvnLLCDTP5\nZxw935rAMi5VF2bbejw/S4GUWs7DzoKbbh/hruPBvshbhPJdH1VVIr6LPzJmFSeuqk/fYb\nXGSmra01mZ6VVu4BQAaKsPoXti2dIJHlNPksfWuQAAABUA9BGJkzWhSfAktPrxUheJ2HMh\nJ0kAAACBAJIC48RyQBO6hVnU6n+xGZ4Lu4wBpnQfZN2MzB3tZXTMRAe8zcOWjp8Y4aGC7Y\nh3qBHDpNlzsr5xPlX4SFsFgHToikUxGZZos5L4Rm6tAwnthDzF4q46lgAiOZw4qEF9aBDK\nJ0fDdwBDub/UnwaktkPUejga+pX9OEb8KR2dFBrvAAAAgAIUacRjCFhMmhIfGJ44ms0EzR\nKZJUWangRqNYKLSYIDZlWiEDSApRpS8got+fXnxFLkHGfUl8TOfT/oXnHPxlPxh2pFuWFh\nOHT9hoHYDEFgu0ulhSF3jxhl6jUA3VsZV/LpoXp70KmtT5yqxUYQ6ycPGexo3R8X5bMQhJ\nlz6CzfAAAB2MVcBjzFXAY8AAAAB3NzaC1kc3MAAACBAJKQOsVERVDQIpANHH+JAAylo9Lv\nFYmFFVMIuHFGlZpIL7sh3IMkqy+cssINM/lnHD3fmsAyLlUXZtt6PD9LgZRazsPOgptuH+\nGu48G+yFuE8l0fVVUivos/MmYVJ66qT99htcZKatrTWZnpVW7gFABoqw+he2LZ0gkeU0+S\nx9a5AAAAFQD0EYmTNaFJ8CS0+vFSF4nYcyEnSQAAAIEAkgLjxHJAE7qFWdTqf7EZngu7jA\nGmdB9k3YzMHe1ldMxEB7zNw5aOnxjhoYLtiHeoEcOk2XOyvnE+VfhIWwWAdOiKRTEZlmiz\nkvhGbq0DCe2EPMXirjqWACI5nDioQX1oEMonR8N3AEO5v9SfBqS2Q9R6OBr6lf04RvwpHZ\n0UGu8AAACAAhRpxGMIWEyaEh8YnjiazQTNEpklRZqeBGo1gotJggNmVaIQNIClGlLyCi35\n9efEUuQcZ9SXxM59P+hecc/GU/GHakW5YWE4dP2GgdgMQWC7S6WFIXePGGXqNQDdWxlX8u\nmhenvQqa1PnKrFRhDrJw8Z7GjdHxflsxCEmXPoLN8AAAAVANXaBstzNR3EK6zSl8Q/Vt11\npdEtAAAAAAE=\n-----END OPENSSH PRIVATE KEY-----\\\n\"\"\"\n\npublicDSA_lsh = decodebytes(b\"\"\"\\\ne0tERXdPbkIxWW14cFl5MXJaWGtvTXpwa2MyRW9NVHB3TVRJNU9nQ1NrRHJGUkVWUTBDS1FEUngv\naVFBTXBhUFM3eFdKaFJWVENMaHhScFdhU0MrN0lkeURKS3N2bkxMQ0RUUDVaeHc5MzVyQU1pNVZG\nMmJiZWp3L1M0R1VXczdEem9LYmJoL2hydVBCdnNoYmhQSmRIMVZWSXI2TFB6Sm1GU2V1cWsvZlli\nWEdTbXJhMDFtWjZWVnU0QlFBYUtzUG9YdGkyZElKSGxOUGtzZld1U2tvTVRweE1qRTZBUFFSaVpN\nMW9VbndKTFQ2OFZJWGlkaHpJU2RKS1NneE9tY3hNams2QUpJQzQ4UnlRQk82aFZuVTZuK3hHWjRM\ndTR3QnBuUWZaTjJNekIzdFpYVE1SQWU4emNPV2pwOFk0YUdDN1loM3FCSERwTmx6c3I1eFBsWDRT\nRnNGZ0hUb2lrVXhHWlpvczVMNFJtNnRBd250aER6RjRxNDZsZ0FpT1p3NHFFRjlhQkRLSjBmRGR3\nQkR1Yi9Vbndha3RrUFVlamdhK3BYOU9FYjhLUjJkRkJydktTZ3hPbmt4TWpnNkFoUnB4R01JV0V5\nYUVoOFluamlhelFUTkVwa2xSWnFlQkdvMWdvdEpnZ05tVmFJUU5JQ2xHbEx5Q2kzNTllZkVVdVFj\nWjlTWHhNNTlQK2hlY2MvR1UvR0hha1c1WVdFNGRQMkdnZGdNUVdDN1M2V0ZJWGVQR0dYcU5RRGRX\neGxYOHVtaGVudlFxYTFQbktyRlJoRHJKdzhaN0dqZEh4ZmxzeENFbVhQb0xOOHBLU2s9fQ==\n\"\"\")\n\nprivateDSA_lsh = decodebytes(b\"\"\"\\\nKDExOnByaXZhdGUta2V5KDM6ZHNhKDE6cDEyOToAkpA6xURFUNAikA0cf4kADKWj0u8ViYUVUwi4\ncUaVmkgvuyHcgySrL5yywg0z+WccPd+awDIuVRdm23o8P0uBlFrOw86Cm24f4a7jwb7IW4TyXR9V\nVSK+iz8yZhUnrqpP32G1xkpq2tNZmelVbuAUAGirD6F7YtnSCR5TT5LH1rkpKDE6cTIxOgD0EYmT\nNaFJ8CS0+vFSF4nYcyEnSSkoMTpnMTI5OgCSAuPEckATuoVZ1Op/sRmeC7uMAaZ0H2TdjMwd7WV0\nzEQHvM3Dlo6fGOGhgu2Id6gRw6TZc7K+cT5V+EhbBYB06IpFMRmWaLOS+EZurQMJ7YQ8xeKuOpYA\nIjmcOKhBfWgQyidHw3cAQ7m/1J8GpLZD1Ho4GvqV/ThG/CkdnRQa7ykoMTp5MTI4OgIUacRjCFhM\nmhIfGJ44ms0EzRKZJUWangRqNYKLSYIDZlWiEDSApRpS8got+fXnxFLkHGfUl8TOfT/oXnHPxlPx\nh2pFuWFhOHT9hoHYDEFgu0ulhSF3jxhl6jUA3VsZV/LpoXp70KmtT5yqxUYQ6ycPGexo3R8X5bMQ\nhJlz6CzfKSgxOngyMToA1doGy3M1HcQrrNKXxD9W3XWl0S0pKSk=\n\"\"\")\n\nprivateDSA_agentv3 = decodebytes(b\"\"\"\\\nAAAAB3NzaC1kc3MAAACBAJKQOsVERVDQIpANHH+JAAylo9LvFYmFFVMIuHFGlZpIL7sh3IMkqy+c\nssINM/lnHD3fmsAyLlUXZtt6PD9LgZRazsPOgptuH+Gu48G+yFuE8l0fVVUivos/MmYVJ66qT99h\ntcZKatrTWZnpVW7gFABoqw+he2LZ0gkeU0+Sx9a5AAAAFQD0EYmTNaFJ8CS0+vFSF4nYcyEnSQAA\nAIEAkgLjxHJAE7qFWdTqf7EZngu7jAGmdB9k3YzMHe1ldMxEB7zNw5aOnxjhoYLtiHeoEcOk2XOy\nvnE+VfhIWwWAdOiKRTEZlmizkvhGbq0DCe2EPMXirjqWACI5nDioQX1oEMonR8N3AEO5v9SfBqS2\nQ9R6OBr6lf04RvwpHZ0UGu8AAACAAhRpxGMIWEyaEh8YnjiazQTNEpklRZqeBGo1gotJggNmVaIQ\nNIClGlLyCi359efEUuQcZ9SXxM59P+hecc/GU/GHakW5YWE4dP2GgdgMQWC7S6WFIXePGGXqNQDd\nWxlX8umhenvQqa1PnKrFRhDrJw8Z7GjdHxflsxCEmXPoLN8AAAAVANXaBstzNR3EK6zSl8Q/Vt11\npdEt\n\"\"\")\n\n__all__ = ['DSAData', 'RSAData', 'privateDSA_agentv3', 'privateDSA_lsh',\n        'privateDSA_openssh', 'privateRSA_agentv3', 'privateRSA_lsh',\n        'privateRSA_openssh', 'publicDSA_lsh', 'publicDSA_openssh',\n        'publicRSA_lsh', 'publicRSA_openssh', 'privateRSA_openssh_alternate']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/loopback.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\"\"\"\nLoopback helper used in test_ssh and test_recvline\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.protocols import loopback\nclass LoopbackRelay(loopback.LoopbackRelay):\n    clearCall = None\n\n    def logPrefix(self):\n        return \"LoopbackRelay(%r)\" % (self.target.__class__.__name__,)\n\n\n    def write(self, data):\n        loopback.LoopbackRelay.write(self, data)\n        if self.clearCall is not None:\n            self.clearCall.cancel()\n\n        from twisted.internet import reactor\n        self.clearCall = reactor.callLater(0, self._clearBuffer)\n\n\n    def _clearBuffer(self):\n        self.clearCall = None\n        loopback.LoopbackRelay.clearBuffer(self)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_address.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{SSHTransportAddrress} in ssh/address.py\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.trial import unittest\nfrom twisted.internet.address import IPv4Address\nfrom twisted.internet.test.test_address import AddressTestCaseMixin\n\nfrom twisted.conch.ssh.address import SSHTransportAddress\n\n\n\nclass SSHTransportAddressTests(unittest.TestCase, AddressTestCaseMixin):\n    \"\"\"\n    L{twisted.conch.ssh.address.SSHTransportAddress} is what Conch transports\n    use to represent the other side of the SSH connection.  This tests the\n    basic functionality of that class (string representation, comparison, &c).\n    \"\"\"\n\n\n    def _stringRepresentation(self, stringFunction):\n        \"\"\"\n        The string representation of C{SSHTransportAddress} should be\n        \"SSHTransportAddress(<stringFunction on address>)\".\n        \"\"\"\n        addr = self.buildAddress()\n        stringValue = stringFunction(addr)\n        addressValue = stringFunction(addr.address)\n        self.assertEqual(stringValue,\n                         \"SSHTransportAddress(%s)\" % addressValue)\n\n\n    def buildAddress(self):\n        \"\"\"\n        Create an arbitrary new C{SSHTransportAddress}.  A new instance is\n        created for each call, but always for the same address.\n        \"\"\"\n        return SSHTransportAddress(IPv4Address(\"TCP\", \"127.0.0.1\", 22))\n\n\n    def buildDifferentAddress(self):\n        \"\"\"\n        Like C{buildAddress}, but with a different fixed address.\n        \"\"\"\n        return SSHTransportAddress(IPv4Address(\"TCP\", \"127.0.0.2\", 22))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_agent.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.ssh.agent}.\n\"\"\"\nfrom __future__ import absolute_import, division\n\nimport struct\n\nfrom twisted.trial import unittest\nfrom twisted.test import iosim\n\ntry:\n    import cryptography\nexcept ImportError:\n    cryptography = None\n\ntry:\n    import pyasn1\nexcept ImportError:\n    pyasn1 = None\n\nif cryptography and pyasn1:\n    from twisted.conch.ssh import keys, agent\nelse:\n    keys = agent = None\n\nfrom twisted.conch.test import keydata\nfrom twisted.conch.error import ConchError, MissingKeyStoreError\n\n\nclass StubFactory(object):\n    \"\"\"\n    Mock factory that provides the keys attribute required by the\n    SSHAgentServerProtocol\n    \"\"\"\n    def __init__(self):\n        self.keys = {}\n\n\n\nclass AgentTestBase(unittest.TestCase):\n    \"\"\"\n    Tests for SSHAgentServer/Client.\n    \"\"\"\n    if iosim is None:\n        skip = \"iosim requires SSL, but SSL is not available\"\n    elif agent is None or keys is None:\n        skip = \"Cannot run without cryptography or PyASN1\"\n\n    def setUp(self):\n        # wire up our client <-> server\n        self.client, self.server, self.pump = iosim.connectedServerAndClient(\n            agent.SSHAgentServer, agent.SSHAgentClient)\n\n        # the server's end of the protocol is stateful and we store it on the\n        # factory, for which we only need a mock\n        self.server.factory = StubFactory()\n\n        # pub/priv keys of each kind\n        self.rsaPrivate = keys.Key.fromString(keydata.privateRSA_openssh)\n        self.dsaPrivate = keys.Key.fromString(keydata.privateDSA_openssh)\n\n        self.rsaPublic = keys.Key.fromString(keydata.publicRSA_openssh)\n        self.dsaPublic = keys.Key.fromString(keydata.publicDSA_openssh)\n\n\n\nclass ServerProtocolContractWithFactoryTests(AgentTestBase):\n    \"\"\"\n    The server protocol is stateful and so uses its factory to track state\n    across requests.  This test asserts that the protocol raises if its factory\n    doesn't provide the necessary storage for that state.\n    \"\"\"\n    def test_factorySuppliesKeyStorageForServerProtocol(self):\n        # need a message to send into the server\n        msg = struct.pack('!LB',1, agent.AGENTC_REQUEST_IDENTITIES)\n        del self.server.factory.__dict__['keys']\n        self.assertRaises(MissingKeyStoreError,\n                          self.server.dataReceived, msg)\n\n\n\nclass UnimplementedVersionOneServerTests(AgentTestBase):\n    \"\"\"\n    Tests for methods with no-op implementations on the server. We need these\n    for clients, such as openssh, that try v1 methods before going to v2.\n\n    Because the client doesn't expose these operations with nice method names,\n    we invoke sendRequest directly with an op code.\n    \"\"\"\n\n    def test_agentc_REQUEST_RSA_IDENTITIES(self):\n        \"\"\"\n        assert that we get the correct op code for an RSA identities request\n        \"\"\"\n        d = self.client.sendRequest(agent.AGENTC_REQUEST_RSA_IDENTITIES, b'')\n        self.pump.flush()\n        def _cb(packet):\n            self.assertEqual(\n                agent.AGENT_RSA_IDENTITIES_ANSWER, ord(packet[0:1]))\n        return d.addCallback(_cb)\n\n\n    def test_agentc_REMOVE_RSA_IDENTITY(self):\n        \"\"\"\n        assert that we get the correct op code for an RSA remove identity request\n        \"\"\"\n        d = self.client.sendRequest(agent.AGENTC_REMOVE_RSA_IDENTITY, b'')\n        self.pump.flush()\n        return d.addCallback(self.assertEqual, b'')\n\n\n    def test_agentc_REMOVE_ALL_RSA_IDENTITIES(self):\n        \"\"\"\n        assert that we get the correct op code for an RSA remove all identities\n        request.\n        \"\"\"\n        d = self.client.sendRequest(agent.AGENTC_REMOVE_ALL_RSA_IDENTITIES, b'')\n        self.pump.flush()\n        return d.addCallback(self.assertEqual, b'')\n\n\n\nif agent is not None:\n    class CorruptServer(agent.SSHAgentServer):\n        \"\"\"\n        A misbehaving server that returns bogus response op codes so that we can\n        verify that our callbacks that deal with these op codes handle such\n        miscreants.\n        \"\"\"\n        def agentc_REQUEST_IDENTITIES(self, data):\n            self.sendResponse(254, b'')\n\n\n        def agentc_SIGN_REQUEST(self, data):\n            self.sendResponse(254, b'')\n\n\n\nclass ClientWithBrokenServerTests(AgentTestBase):\n    \"\"\"\n    verify error handling code in the client using a misbehaving server\n    \"\"\"\n\n    def setUp(self):\n        AgentTestBase.setUp(self)\n        self.client, self.server, self.pump = iosim.connectedServerAndClient(\n            CorruptServer, agent.SSHAgentClient)\n        # the server's end of the protocol is stateful and we store it on the\n        # factory, for which we only need a mock\n        self.server.factory = StubFactory()\n\n\n    def test_signDataCallbackErrorHandling(self):\n        \"\"\"\n        Assert that L{SSHAgentClient.signData} raises a ConchError\n        if we get a response from the server whose opcode doesn't match\n        the protocol for data signing requests.\n        \"\"\"\n        d = self.client.signData(self.rsaPublic.blob(), b\"John Hancock\")\n        self.pump.flush()\n        return self.assertFailure(d, ConchError)\n\n\n    def test_requestIdentitiesCallbackErrorHandling(self):\n        \"\"\"\n        Assert that L{SSHAgentClient.requestIdentities} raises a ConchError\n        if we get a response from the server whose opcode doesn't match\n        the protocol for identity requests.\n        \"\"\"\n        d = self.client.requestIdentities()\n        self.pump.flush()\n        return self.assertFailure(d, ConchError)\n\n\n\nclass AgentKeyAdditionTests(AgentTestBase):\n    \"\"\"\n    Test adding different flavors of keys to an agent.\n    \"\"\"\n\n    def test_addRSAIdentityNoComment(self):\n        \"\"\"\n        L{SSHAgentClient.addIdentity} adds the private key it is called\n        with to the SSH agent server to which it is connected, associating\n        it with the comment it is called with.\n\n        This test asserts that omitting the comment produces an\n        empty string for the comment on the server.\n        \"\"\"\n        d = self.client.addIdentity(self.rsaPrivate.privateBlob())\n        self.pump.flush()\n        def _check(ignored):\n            serverKey = self.server.factory.keys[self.rsaPrivate.blob()]\n            self.assertEqual(self.rsaPrivate, serverKey[0])\n            self.assertEqual(b'', serverKey[1])\n        return d.addCallback(_check)\n\n\n    def test_addDSAIdentityNoComment(self):\n        \"\"\"\n        L{SSHAgentClient.addIdentity} adds the private key it is called\n        with to the SSH agent server to which it is connected, associating\n        it with the comment it is called with.\n\n        This test asserts that omitting the comment produces an\n        empty string for the comment on the server.\n        \"\"\"\n        d = self.client.addIdentity(self.dsaPrivate.privateBlob())\n        self.pump.flush()\n        def _check(ignored):\n            serverKey = self.server.factory.keys[self.dsaPrivate.blob()]\n            self.assertEqual(self.dsaPrivate, serverKey[0])\n            self.assertEqual(b'', serverKey[1])\n        return d.addCallback(_check)\n\n\n    def test_addRSAIdentityWithComment(self):\n        \"\"\"\n        L{SSHAgentClient.addIdentity} adds the private key it is called\n        with to the SSH agent server to which it is connected, associating\n        it with the comment it is called with.\n\n        This test asserts that the server receives/stores the comment\n        as sent by the client.\n        \"\"\"\n        d = self.client.addIdentity(\n            self.rsaPrivate.privateBlob(), comment=b'My special key')\n        self.pump.flush()\n        def _check(ignored):\n            serverKey = self.server.factory.keys[self.rsaPrivate.blob()]\n            self.assertEqual(self.rsaPrivate, serverKey[0])\n            self.assertEqual(b'My special key', serverKey[1])\n        return d.addCallback(_check)\n\n\n    def test_addDSAIdentityWithComment(self):\n        \"\"\"\n        L{SSHAgentClient.addIdentity} adds the private key it is called\n        with to the SSH agent server to which it is connected, associating\n        it with the comment it is called with.\n\n        This test asserts that the server receives/stores the comment\n        as sent by the client.\n        \"\"\"\n        d = self.client.addIdentity(\n            self.dsaPrivate.privateBlob(), comment=b'My special key')\n        self.pump.flush()\n        def _check(ignored):\n            serverKey = self.server.factory.keys[self.dsaPrivate.blob()]\n            self.assertEqual(self.dsaPrivate, serverKey[0])\n            self.assertEqual(b'My special key', serverKey[1])\n        return d.addCallback(_check)\n\n\n\nclass AgentClientFailureTests(AgentTestBase):\n    def test_agentFailure(self):\n        \"\"\"\n        verify that the client raises ConchError on AGENT_FAILURE\n        \"\"\"\n        d = self.client.sendRequest(254, b'')\n        self.pump.flush()\n        return self.assertFailure(d, ConchError)\n\n\n\nclass AgentIdentityRequestsTests(AgentTestBase):\n    \"\"\"\n    Test operations against a server with identities already loaded.\n    \"\"\"\n\n    def setUp(self):\n        AgentTestBase.setUp(self)\n        self.server.factory.keys[self.dsaPrivate.blob()] = (\n            self.dsaPrivate, b'a comment')\n        self.server.factory.keys[self.rsaPrivate.blob()] = (\n            self.rsaPrivate, b'another comment')\n\n\n    def test_signDataRSA(self):\n        \"\"\"\n        Sign data with an RSA private key and then verify it with the public\n        key.\n        \"\"\"\n        d = self.client.signData(self.rsaPublic.blob(), b\"John Hancock\")\n        self.pump.flush()\n        signature = self.successResultOf(d)\n\n        expected = self.rsaPrivate.sign(b\"John Hancock\")\n        self.assertEqual(expected, signature)\n        self.assertTrue(self.rsaPublic.verify(signature, b\"John Hancock\"))\n\n\n    def test_signDataDSA(self):\n        \"\"\"\n        Sign data with a DSA private key and then verify it with the public\n        key.\n        \"\"\"\n        d = self.client.signData(self.dsaPublic.blob(), b\"John Hancock\")\n        self.pump.flush()\n        def _check(sig):\n            # Cannot do this b/c DSA uses random numbers when signing\n            #   expected = self.dsaPrivate.sign(\"John Hancock\")\n            #   self.assertEqual(expected, sig)\n            self.assertTrue(self.dsaPublic.verify(sig, b\"John Hancock\"))\n        return d.addCallback(_check)\n\n\n    def test_signDataRSAErrbackOnUnknownBlob(self):\n        \"\"\"\n        Assert that we get an errback if we try to sign data using a key that\n        wasn't added.\n        \"\"\"\n        del self.server.factory.keys[self.rsaPublic.blob()]\n        d = self.client.signData(self.rsaPublic.blob(), b\"John Hancock\")\n        self.pump.flush()\n        return self.assertFailure(d, ConchError)\n\n\n    def test_requestIdentities(self):\n        \"\"\"\n        Assert that we get all of the keys/comments that we add when we issue a\n        request for all identities.\n        \"\"\"\n        d = self.client.requestIdentities()\n        self.pump.flush()\n        def _check(keyt):\n            expected = {}\n            expected[self.dsaPublic.blob()] = b'a comment'\n            expected[self.rsaPublic.blob()] = b'another comment'\n\n            received = {}\n            for k in keyt:\n                received[keys.Key.fromString(k[0], type='blob').blob()] = k[1]\n            self.assertEqual(expected, received)\n        return d.addCallback(_check)\n\n\n\nclass AgentKeyRemovalTests(AgentTestBase):\n    \"\"\"\n    Test support for removing keys in a remote server.\n    \"\"\"\n\n    def setUp(self):\n        AgentTestBase.setUp(self)\n        self.server.factory.keys[self.dsaPrivate.blob()] = (\n            self.dsaPrivate, b'a comment')\n        self.server.factory.keys[self.rsaPrivate.blob()] = (\n            self.rsaPrivate, b'another comment')\n\n\n    def test_removeRSAIdentity(self):\n        \"\"\"\n        Assert that we can remove an RSA identity.\n        \"\"\"\n        # only need public key for this\n        d = self.client.removeIdentity(self.rsaPrivate.blob())\n        self.pump.flush()\n\n        def _check(ignored):\n            self.assertEqual(1, len(self.server.factory.keys))\n            self.assertIn(self.dsaPrivate.blob(), self.server.factory.keys)\n            self.assertNotIn(self.rsaPrivate.blob(), self.server.factory.keys)\n        return d.addCallback(_check)\n\n\n    def test_removeDSAIdentity(self):\n        \"\"\"\n        Assert that we can remove a DSA identity.\n        \"\"\"\n        # only need public key for this\n        d = self.client.removeIdentity(self.dsaPrivate.blob())\n        self.pump.flush()\n\n        def _check(ignored):\n            self.assertEqual(1, len(self.server.factory.keys))\n            self.assertIn(self.rsaPrivate.blob(), self.server.factory.keys)\n        return d.addCallback(_check)\n\n\n    def test_removeAllIdentities(self):\n        \"\"\"\n        Assert that we can remove all identities.\n        \"\"\"\n        d = self.client.removeAllIdentities()\n        self.pump.flush()\n\n        def _check(ignored):\n            self.assertEqual(0, len(self.server.factory.keys))\n        return d.addCallback(_check)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_cftp.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_cftp -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE file for details.\n\n\"\"\"\nTests for L{twisted.conch.scripts.cftp}.\n\"\"\"\n\nimport locale\nimport time, sys, os, operator, getpass, struct\nfrom io import BytesIO\n\nfrom twisted.python.filepath import FilePath\nfrom twisted.python.reflect import requireModule\nfrom zope.interface import implementer\n\npyasn1 = requireModule('pyasn1')\ncryptography = requireModule('cryptography')\nunix = requireModule('twisted.conch.unix')\n\n_reason = None\nif cryptography and pyasn1:\n    try:\n        from twisted.conch.scripts import cftp\n        from twisted.conch.scripts.cftp import SSHSession\n        from twisted.conch.ssh import filetransfer\n        from twisted.conch.test.test_filetransfer import FileTransferForTestAvatar\n        from twisted.conch.test import test_ssh, test_conch\n        from twisted.conch.test.test_conch import FakeStdio\n    except ImportError:\n        pass\n\nfrom twisted.conch import ls\nfrom twisted.conch.interfaces import ISFTPFile\nfrom twisted.conch.test.test_filetransfer import SFTPTestBase\nfrom twisted.conch.test.test_filetransfer import FileTransferTestAvatar\nfrom twisted.cred import portal\nfrom twisted.internet import reactor, protocol, interfaces, defer, error\nfrom twisted.internet.utils import getProcessOutputAndValue, getProcessValue\nfrom twisted.python import log\nfrom twisted.python.compat import _PY3, unicode\nfrom twisted.python.fakepwd import UserDatabase\nfrom twisted.test.proto_helpers import StringTransport\nfrom twisted.internet.task import Clock\nfrom twisted.trial.unittest import TestCase\n\n\n\n\nclass SSHSessionTests(TestCase):\n    \"\"\"\n    Tests for L{twisted.conch.scripts.cftp.SSHSession}.\n    \"\"\"\n    def test_eofReceived(self):\n        \"\"\"\n        L{twisted.conch.scripts.cftp.SSHSession.eofReceived} loses the write\n        half of its stdio connection.\n        \"\"\"\n        stdio = FakeStdio()\n        channel = SSHSession()\n        channel.stdio = stdio\n        channel.eofReceived()\n        self.assertTrue(stdio.writeConnLost)\n\n\n\nclass ListingTests(TestCase):\n    \"\"\"\n    Tests for L{lsLine}, the function which generates an entry for a file or\n    directory in an SFTP I{ls} command's output.\n    \"\"\"\n    if getattr(time, 'tzset', None) is None:\n        skip = \"Cannot test timestamp formatting code without time.tzset\"\n\n\n    def setUp(self):\n        \"\"\"\n        Patch the L{ls} module's time function so the results of L{lsLine} are\n        deterministic.\n        \"\"\"\n        self.now = 123456789\n        def fakeTime():\n            return self.now\n        self.patch(ls, 'time', fakeTime)\n\n        # Make sure that the timezone ends up the same after these tests as\n        # it was before.\n        if 'TZ' in os.environ:\n            self.addCleanup(operator.setitem, os.environ, 'TZ', os.environ['TZ'])\n            self.addCleanup(time.tzset)\n        else:\n            def cleanup():\n                # os.environ.pop is broken!  Don't use it!  Ever!  Or die!\n                try:\n                    del os.environ['TZ']\n                except KeyError:\n                    pass\n                time.tzset()\n            self.addCleanup(cleanup)\n\n\n    def _lsInTimezone(self, timezone, stat):\n        \"\"\"\n        Call L{ls.lsLine} after setting the timezone to C{timezone} and return\n        the result.\n        \"\"\"\n        # Set the timezone to a well-known value so the timestamps are\n        # predictable.\n        os.environ['TZ'] = timezone\n        time.tzset()\n        return ls.lsLine('foo', stat)\n\n\n    def test_oldFile(self):\n        \"\"\"\n        A file with an mtime six months (approximately) or more in the past has\n        a listing including a low-resolution timestamp.\n        \"\"\"\n        # Go with 7 months.  That's more than 6 months.\n        then = self.now - (60 * 60 * 24 * 31 * 7)\n        stat = os.stat_result((0, 0, 0, 0, 0, 0, 0, 0, then, 0))\n\n        self.assertEqual(\n            self._lsInTimezone('America/New_York', stat),\n            '!---------    0 0        0               0 Apr 26  1973 foo')\n        self.assertEqual(\n            self._lsInTimezone('Pacific/Auckland', stat),\n            '!---------    0 0        0               0 Apr 27  1973 foo')\n\n\n    def test_oldSingleDigitDayOfMonth(self):\n        \"\"\"\n        A file with a high-resolution timestamp which falls on a day of the\n        month which can be represented by one decimal digit is formatted with\n        one padding 0 to preserve the columns which come after it.\n        \"\"\"\n        # A point about 7 months in the past, tweaked to fall on the first of a\n        # month so we test the case we want to test.\n        then = self.now - (60 * 60 * 24 * 31 * 7) + (60 * 60 * 24 * 5)\n        stat = os.stat_result((0, 0, 0, 0, 0, 0, 0, 0, then, 0))\n\n        self.assertEqual(\n            self._lsInTimezone('America/New_York', stat),\n            '!---------    0 0        0               0 May 01  1973 foo')\n        self.assertEqual(\n            self._lsInTimezone('Pacific/Auckland', stat),\n            '!---------    0 0        0               0 May 02  1973 foo')\n\n\n    def test_newFile(self):\n        \"\"\"\n        A file with an mtime fewer than six months (approximately) in the past\n        has a listing including a high-resolution timestamp excluding the year.\n        \"\"\"\n        # A point about three months in the past.\n        then = self.now - (60 * 60 * 24 * 31 * 3)\n        stat = os.stat_result((0, 0, 0, 0, 0, 0, 0, 0, then, 0))\n\n        self.assertEqual(\n            self._lsInTimezone('America/New_York', stat),\n            '!---------    0 0        0               0 Aug 28 17:33 foo')\n        self.assertEqual(\n            self._lsInTimezone('Pacific/Auckland', stat),\n            '!---------    0 0        0               0 Aug 29 09:33 foo')\n\n\n    def test_localeIndependent(self):\n        \"\"\"\n        The month name in the date is locale independent.\n        \"\"\"\n        # A point about three months in the past.\n        then = self.now - (60 * 60 * 24 * 31 * 3)\n        stat = os.stat_result((0, 0, 0, 0, 0, 0, 0, 0, then, 0))\n\n        # Fake that we're in a language where August is not Aug (e.g.: Spanish)\n        currentLocale = locale.getlocale()\n        locale.setlocale(locale.LC_ALL, \"es_AR.UTF8\")\n        self.addCleanup(locale.setlocale, locale.LC_ALL, currentLocale)\n\n        self.assertEqual(\n            self._lsInTimezone('America/New_York', stat),\n            '!---------    0 0        0               0 Aug 28 17:33 foo')\n        self.assertEqual(\n            self._lsInTimezone('Pacific/Auckland', stat),\n            '!---------    0 0        0               0 Aug 29 09:33 foo')\n\n    # If alternate locale is not available, the previous test will be\n    # skipped, please install this locale for it to run\n    currentLocale = locale.getlocale()\n    try:\n        try:\n            locale.setlocale(locale.LC_ALL, \"es_AR.UTF8\")\n        except locale.Error:\n            test_localeIndependent.skip = \"The es_AR.UTF8 locale is not installed.\"\n    finally:\n        locale.setlocale(locale.LC_ALL, currentLocale)\n\n\n    def test_newSingleDigitDayOfMonth(self):\n        \"\"\"\n        A file with a high-resolution timestamp which falls on a day of the\n        month which can be represented by one decimal digit is formatted with\n        one padding 0 to preserve the columns which come after it.\n        \"\"\"\n        # A point about three months in the past, tweaked to fall on the first\n        # of a month so we test the case we want to test.\n        then = self.now - (60 * 60 * 24 * 31 * 3) + (60 * 60 * 24 * 4)\n        stat = os.stat_result((0, 0, 0, 0, 0, 0, 0, 0, then, 0))\n\n        self.assertEqual(\n            self._lsInTimezone('America/New_York', stat),\n            '!---------    0 0        0               0 Sep 01 17:33 foo')\n        self.assertEqual(\n            self._lsInTimezone('Pacific/Auckland', stat),\n            '!---------    0 0        0               0 Sep 02 09:33 foo')\n\n\n\nclass InMemorySSHChannel(StringTransport, object):\n    \"\"\"\n    Minimal implementation of a L{SSHChannel} like class which only reads and\n    writes data from memory.\n    \"\"\"\n\n    def __init__(self, conn):\n        \"\"\"\n        @param conn: The SSH connection associated with this channel.\n        @type conn: L{SSHConnection}\n        \"\"\"\n        self.conn = conn\n        self.localClosed = 0\n        super(InMemorySSHChannel, self).__init__()\n\n\n\nclass FilesystemAccessExpectations(object):\n    \"\"\"\n    A test helper used to support expected filesystem access.\n    \"\"\"\n\n    def __init__(self):\n        self._cache = {}\n\n\n    def put(self, path, flags, stream):\n        \"\"\"\n\n        @param path: Path at which the stream is requested.\n        @type path: L{str}\n\n        @param path: Flags with which the stream is requested.\n        @type path: L{str}\n\n        @param stream: A stream.\n        @type stream: C{File}\n        \"\"\"\n        self._cache[(path, flags)] = stream\n\n\n    def pop(self, path, flags):\n        \"\"\"\n        Remove a stream from the memory.\n\n        @param path: Path at which the stream is requested.\n        @type path: L{str}\n\n        @param path: Flags with which the stream is requested.\n        @type path: L{str}\n\n        @return: A stream.\n        @rtype: C{File}\n        \"\"\"\n        return self._cache.pop((path, flags))\n\n\n\nclass InMemorySFTPClient(object):\n    \"\"\"\n    A L{filetransfer.FileTransferClient} which does filesystem operations in\n    memory, without touching the local disc or the network interface.\n\n    @ivar _availableFiles: File like objects which are available to the SFTP\n        client.\n    @type _availableFiles: L{FilesystemRegister}\n    \"\"\"\n\n    def __init__(self, availableFiles):\n        self.transport = InMemorySSHChannel(self)\n        self.options = {\n            'requests': 1,\n            'buffersize': 10,\n            }\n        self._availableFiles = availableFiles\n\n\n    def openFile(self, filename, flags, attrs):\n        \"\"\"\n        @see: L{filetransfer.FileTransferClient.openFile}.\n\n        Retrieve and remove cached file based on flags.\n        \"\"\"\n        return self._availableFiles.pop(filename, flags)\n\n\n\n@implementer(ISFTPFile)\nclass InMemoryRemoteFile(BytesIO):\n    \"\"\"\n    An L{ISFTPFile} which handles all data in memory.\n    \"\"\"\n\n    def __init__(self, name):\n        \"\"\"\n        @param name: Name of this file.\n        @type name: L{str}\n        \"\"\"\n        self.name = name\n        BytesIO.__init__(self)\n\n\n    def writeChunk(self, start, data):\n        \"\"\"\n        @see: L{ISFTPFile.writeChunk}\n        \"\"\"\n        self.seek(start)\n        self.write(data)\n        return defer.succeed(self)\n\n\n    def close(self):\n        \"\"\"\n        @see: L{ISFTPFile.writeChunk}\n\n        Keeps data after file was closed to help with testing.\n        \"\"\"\n        self._closed = True\n\n\n    def getvalue(self):\n        \"\"\"\n        Get current data of file.\n\n        Allow reading data event when file is closed.\n        \"\"\"\n        return BytesIO.getvalue(self)\n\n\n\nclass StdioClientTests(TestCase):\n    \"\"\"\n    Tests for L{cftp.StdioClient}.\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Create a L{cftp.StdioClient} hooked up to dummy transport and a fake\n        user database.\n        \"\"\"\n        self.fakeFilesystem = FilesystemAccessExpectations()\n        sftpClient = InMemorySFTPClient(self.fakeFilesystem )\n        self.client = cftp.StdioClient(sftpClient)\n        self.client.currentDirectory = '/'\n        self.database = self.client._pwd = UserDatabase()\n        # Use a fixed width for all tests so that we get the same results when\n        # running these tests from different terminals.\n        # Run tests in a wide console so that all items are delimited by at\n        # least one space character.\n        self.setKnownConsoleSize(500, 24)\n        # Intentionally bypassing makeConnection - that triggers some code\n        # which uses features not provided by our dumb Connection fake.\n        self.client.transport = self.client.client.transport\n\n\n    def test_exec(self):\n        \"\"\"\n        The I{exec} command runs its arguments locally in a child process\n        using the user's shell.\n        \"\"\"\n        self.database.addUser(\n            getpass.getuser(), 'secret', os.getuid(), 1234, 'foo', 'bar',\n            sys.executable)\n\n        d = self.client._dispatchCommand(\"exec print(1 + 2)\")\n        d.addCallback(self.assertEqual, b\"3\\n\")\n        return d\n\n\n    def test_execWithoutShell(self):\n        \"\"\"\n        If the local user has no shell, the I{exec} command runs its arguments\n        using I{/bin/sh}.\n        \"\"\"\n        self.database.addUser(\n            getpass.getuser(), 'secret', os.getuid(), 1234, 'foo', 'bar', '')\n\n        d = self.client._dispatchCommand(\"exec echo hello\")\n        d.addCallback(self.assertEqual, b\"hello\\n\")\n        return d\n\n\n    def test_bang(self):\n        \"\"\"\n        The I{exec} command is run for lines which start with C{\"!\"}.\n        \"\"\"\n        self.database.addUser(\n            getpass.getuser(), 'secret', os.getuid(), 1234, 'foo', 'bar',\n            '/bin/sh')\n\n        d = self.client._dispatchCommand(\"!echo hello\")\n        d.addCallback(self.assertEqual, b\"hello\\n\")\n        return d\n\n\n    def setKnownConsoleSize(self, width, height):\n        \"\"\"\n        For the duration of this test, patch C{cftp}'s C{fcntl} module to return\n        a fixed width and height.\n\n        @param width: the width in characters\n        @type width: L{int}\n        @param height: the height in characters\n        @type height: L{int}\n        \"\"\"\n        # Local import to avoid win32 issues.\n        import tty\n        class FakeFcntl(object):\n            def ioctl(self, fd, opt, mutate):\n                if opt != tty.TIOCGWINSZ:\n                    self.fail(\"Only window-size queries supported.\")\n                return struct.pack(\"4H\", height, width, 0, 0)\n        self.patch(cftp, \"fcntl\", FakeFcntl())\n\n\n    def test_printProgressBarReporting(self):\n        \"\"\"\n        L{StdioClient._printProgressBar} prints a progress description,\n        including percent done, amount transferred, transfer rate, and time\n        remaining, all based the given start time, the given L{FileWrapper}'s\n        progress information and the reactor's current time.\n        \"\"\"\n        # Use a short, known console width because this simple test doesn't\n        # need to test the console padding.\n        self.setKnownConsoleSize(10, 34)\n        clock = self.client.reactor = Clock()\n        wrapped = BytesIO(b\"x\")\n        wrapped.name = b\"sample\"\n        wrapper = cftp.FileWrapper(wrapped)\n        wrapper.size = 1024 * 10\n        startTime = clock.seconds()\n        clock.advance(2.0)\n        wrapper.total += 4096\n\n        self.client._printProgressBar(wrapper, startTime)\n\n        if _PY3:\n            result = b\"\\rb'sample' 40% 4.0kB 2.0kBps 00:03 \"\n        else:\n            result = \"\\rsample 40% 4.0kB 2.0kBps 00:03 \"\n        self.assertEqual(self.client.transport.value(), result)\n\n\n    def test_printProgressBarNoProgress(self):\n        \"\"\"\n        L{StdioClient._printProgressBar} prints a progress description that\n        indicates 0 bytes transferred if no bytes have been transferred and no\n        time has passed.\n        \"\"\"\n        self.setKnownConsoleSize(10, 34)\n        clock = self.client.reactor = Clock()\n        wrapped = BytesIO(b\"x\")\n        wrapped.name = b\"sample\"\n        wrapper = cftp.FileWrapper(wrapped)\n        startTime = clock.seconds()\n\n        self.client._printProgressBar(wrapper, startTime)\n\n        if _PY3:\n            result = b\"\\rb'sample'  0% 0.0B 0.0Bps 00:00 \"\n        else:\n            result = \"\\rsample  0% 0.0B 0.0Bps 00:00 \"\n        self.assertEqual(self.client.transport.value(), result)\n\n\n    def test_printProgressBarEmptyFile(self):\n        \"\"\"\n        Print the progress for empty files.\n        \"\"\"\n        self.setKnownConsoleSize(10, 34)\n        wrapped = BytesIO()\n        wrapped.name = b'empty-file'\n        wrapper = cftp.FileWrapper(wrapped)\n\n        self.client._printProgressBar(wrapper, 0)\n\n        if _PY3:\n            result = b\"\\rb'empty-file'100% 0.0B 0.0Bps 00:00 \"\n        else:\n            result = \"\\rempty-file100% 0.0B 0.0Bps 00:00 \"\n        self.assertEqual(result, self.client.transport.value())\n\n\n    def test_getFilenameEmpty(self):\n        \"\"\"\n        Returns empty value for both filename and remaining data.\n        \"\"\"\n        result = self.client._getFilename('  ')\n\n        self.assertEqual(('', ''), result)\n\n\n    def test_getFilenameOnlyLocal(self):\n        \"\"\"\n        Returns empty value for remaining data when line contains\n        only a filename.\n        \"\"\"\n        result = self.client._getFilename('only-local')\n\n        self.assertEqual(('only-local', ''), result)\n\n\n    def test_getFilenameNotQuoted(self):\n        \"\"\"\n        Returns filename and remaining data striped of leading and trailing\n        spaces.\n        \"\"\"\n        result = self.client._getFilename(' local  remote file  ')\n\n        self.assertEqual(('local', 'remote file'), result)\n\n\n    def test_getFilenameQuoted(self):\n        \"\"\"\n        Returns filename and remaining data not striped of leading and trailing\n        spaces when quoted paths are requested.\n        \"\"\"\n        result = self.client._getFilename(' \" local file \"  \" remote  file \" ')\n\n        self.assertEqual((' local file ', '\" remote  file \"'), result)\n\n\n    def makeFile(self, path=None, content=b''):\n        \"\"\"\n        Create a local file and return its path.\n\n        When `path` is L{None}, it will create a new temporary file.\n\n        @param path: Optional path for the new file.\n        @type path: L{str}\n\n        @param content: Content to be written in the new file.\n        @type content: L{bytes}\n\n        @return: Path to the newly create file.\n        \"\"\"\n        if path is None:\n            path = self.mktemp()\n        with open(path, 'wb') as file:\n            file.write(content)\n        return path\n\n\n    def checkPutMessage(self, transfers, randomOrder=False):\n        \"\"\"\n        Check output of cftp client for a put request.\n\n\n        @param transfers: List with tuple of (local, remote, progress).\n        @param randomOrder: When set to C{True}, it will ignore the order\n            in which put reposes are received\n\n        \"\"\"\n        output = self.client.transport.value()\n        if _PY3:\n            output = output.decode(\"utf-8\")\n        output = output.split('\\n\\r')\n\n        expectedOutput = []\n        actualOutput = []\n\n        for local, remote, expected in transfers:\n            # For each transfer we have a list of reported progress which\n            # ends with the final message informing that file was transferred.\n            expectedTransfer = []\n            for line in expected:\n                expectedTransfer.append('%s %s' % (local, line))\n            expectedTransfer.append('Transferred %s to %s' % (local, remote))\n            expectedOutput.append(expectedTransfer)\n\n            progressParts = output.pop(0).strip('\\r').split('\\r')\n            actual = progressParts[:-1]\n\n            last = progressParts[-1].strip('\\n').split('\\n')\n            actual.extend(last)\n\n            actualTransfer = []\n            # Each transferred file is on a line with summary on the last\n            # line. Summary is copying at the end.\n            for line in actual[:-1]:\n                # Output line is in the format\n                # NAME PROGRESS_PERCENTAGE PROGRESS_BYTES SPEED ETA.\n                # For testing we only care about the\n                # PROGRESS_PERCENTAGE and PROGRESS values.\n\n                # Ignore SPPED and ETA.\n                line = line.strip().rsplit(' ', 2)[0]\n                # NAME can be followed by a lot of spaces so we need to\n                # reduce them to single space.\n                line = line.strip().split(' ', 1)\n                actualTransfer.append('%s %s' % (line[0], line[1].strip()))\n            actualTransfer.append(actual[-1])\n            actualOutput.append(actualTransfer)\n\n        if randomOrder:\n            self.assertEqual(sorted(expectedOutput), sorted(actualOutput))\n        else:\n            self.assertEqual(expectedOutput, actualOutput)\n\n        self.assertEqual(\n            0, len(output),\n            'There are still put responses which were not checked.',\n            )\n\n\n    def test_cmd_PUTSingleNoRemotePath(self):\n        \"\"\"\n        A name based on local path is used when remote path is not\n        provided.\n\n        The progress is updated while chunks are transferred.\n        \"\"\"\n        content = b'Test\\r\\nContent'\n        localPath = self.makeFile(content=content)\n        flags = (\n            filetransfer.FXF_WRITE |\n            filetransfer.FXF_CREAT |\n            filetransfer.FXF_TRUNC\n            )\n        remoteName = os.path.join('/', os.path.basename(localPath))\n        remoteFile = InMemoryRemoteFile(remoteName)\n        self.fakeFilesystem.put(remoteName, flags, defer.succeed(remoteFile))\n        self.client.client.options['buffersize'] = 10\n\n        deferred = self.client.cmd_PUT(localPath)\n        self.successResultOf(deferred)\n\n        self.assertEqual(content, remoteFile.getvalue())\n        self.assertTrue(remoteFile._closed)\n        self.checkPutMessage(\n            [(localPath, remoteName,\n                ['76% 10.0B', '100% 13.0B', '100% 13.0B'])])\n\n\n    def test_cmd_PUTSingleRemotePath(self):\n        \"\"\"\n        Remote path is extracted from first filename after local file.\n\n        Any other data in the line is ignored.\n        \"\"\"\n        localPath = self.makeFile()\n        flags = (\n            filetransfer.FXF_WRITE |\n            filetransfer.FXF_CREAT |\n            filetransfer.FXF_TRUNC\n            )\n        remoteName = '/remote-path'\n        remoteFile = InMemoryRemoteFile(remoteName)\n        self.fakeFilesystem.put(remoteName, flags, defer.succeed(remoteFile))\n\n        deferred = self.client.cmd_PUT(\n            '%s %s ignored' % (localPath, remoteName))\n        self.successResultOf(deferred)\n\n        self.checkPutMessage([(localPath, remoteName, ['100% 0.0B'])])\n        self.assertTrue(remoteFile._closed)\n        self.assertEqual(b'', remoteFile.getvalue())\n\n\n    def test_cmd_PUTMultipleNoRemotePath(self):\n        \"\"\"\n        When a gobbing expression is used local files are transferred with\n        remote file names based on local names.\n        \"\"\"\n        first = self.makeFile()\n        firstName = os.path.basename(first)\n        secondName = 'second-name'\n        parent = os.path.dirname(first)\n        second = self.makeFile(path=os.path.join(parent, secondName))\n        flags = (\n            filetransfer.FXF_WRITE |\n            filetransfer.FXF_CREAT |\n            filetransfer.FXF_TRUNC\n            )\n        firstRemotePath = '/%s' % (firstName,)\n        secondRemotePath = '/%s' % (secondName,)\n        firstRemoteFile = InMemoryRemoteFile(firstRemotePath)\n        secondRemoteFile = InMemoryRemoteFile(secondRemotePath)\n        self.fakeFilesystem.put(\n            firstRemotePath, flags, defer.succeed(firstRemoteFile))\n        self.fakeFilesystem.put(\n            secondRemotePath, flags, defer.succeed(secondRemoteFile))\n\n        deferred = self.client.cmd_PUT(os.path.join(parent, '*'))\n        self.successResultOf(deferred)\n\n        self.assertTrue(firstRemoteFile._closed)\n        self.assertEqual(b'', firstRemoteFile.getvalue())\n        self.assertTrue(secondRemoteFile._closed)\n        self.assertEqual(b'', secondRemoteFile.getvalue())\n        self.checkPutMessage([\n            (first, firstRemotePath, ['100% 0.0B']),\n            (second, secondRemotePath, ['100% 0.0B']),\n            ],\n            randomOrder=True,\n            )\n\n\n    def test_cmd_PUTMultipleWithRemotePath(self):\n        \"\"\"\n        When a gobbing expression is used local files are transferred with\n        remote file names based on local names.\n        when a remote folder is requested remote paths are composed from\n        remote path and local filename.\n        \"\"\"\n        first = self.makeFile()\n        firstName = os.path.basename(first)\n        secondName = 'second-name'\n        parent = os.path.dirname(first)\n        second = self.makeFile(path=os.path.join(parent, secondName))\n        flags = (\n            filetransfer.FXF_WRITE |\n            filetransfer.FXF_CREAT |\n            filetransfer.FXF_TRUNC\n            )\n        firstRemoteFile = InMemoryRemoteFile(firstName)\n        secondRemoteFile = InMemoryRemoteFile(secondName)\n        firstRemotePath = '/remote/%s' % (firstName,)\n        secondRemotePath = '/remote/%s' % (secondName,)\n        self.fakeFilesystem.put(\n            firstRemotePath, flags, defer.succeed(firstRemoteFile))\n        self.fakeFilesystem.put(\n            secondRemotePath, flags, defer.succeed(secondRemoteFile))\n\n        deferred = self.client.cmd_PUT(\n            '%s remote' % (os.path.join(parent, '*'),))\n        self.successResultOf(deferred)\n\n        self.assertTrue(firstRemoteFile._closed)\n        self.assertEqual(b'', firstRemoteFile.getvalue())\n        self.assertTrue(secondRemoteFile._closed)\n        self.assertEqual(b'', secondRemoteFile.getvalue())\n        self.checkPutMessage([\n            (first, firstName, ['100% 0.0B']),\n            (second, secondName, ['100% 0.0B']),\n            ],\n            randomOrder=True,\n            )\n\n\n\nclass FileTransferTestRealm:\n    def __init__(self, testDir):\n        self.testDir = testDir\n\n\n    def requestAvatar(self, avatarID, mind, *interfaces):\n        a = FileTransferTestAvatar(self.testDir)\n        return interfaces[0], a, lambda: None\n\n\n\nclass SFTPTestProcess(protocol.ProcessProtocol):\n    \"\"\"\n    Protocol for testing cftp. Provides an interface between Python (where all\n    the tests are) and the cftp client process (which does the work that is\n    being tested).\n    \"\"\"\n\n    def __init__(self, onOutReceived):\n        \"\"\"\n        @param onOutReceived: A L{Deferred} to be fired as soon as data is\n        received from stdout.\n        \"\"\"\n        self.clearBuffer()\n        self.onOutReceived = onOutReceived\n        self.onProcessEnd = None\n        self._expectingCommand = None\n        self._processEnded = False\n\n\n    def clearBuffer(self):\n        \"\"\"\n        Clear any buffered data received from stdout. Should be private.\n        \"\"\"\n        self.buffer = b''\n        self._linesReceived = []\n        self._lineBuffer = b''\n\n\n    def outReceived(self, data):\n        \"\"\"\n        Called by Twisted when the cftp client prints data to stdout.\n        \"\"\"\n        log.msg('got %r' % data)\n        lines = (self._lineBuffer + data).split(b'\\n')\n        self._lineBuffer = lines.pop(-1)\n        self._linesReceived.extend(lines)\n        # XXX - not strictly correct.\n        # We really want onOutReceived to fire after the first 'cftp>' prompt\n        # has been received. (See use in OurServerCmdLineClientTests.setUp)\n        if self.onOutReceived is not None:\n            d, self.onOutReceived = self.onOutReceived, None\n            d.callback(data)\n        self.buffer += data\n        self._checkForCommand()\n\n\n    def _checkForCommand(self):\n        prompt = b'cftp> '\n        if self._expectingCommand and self._lineBuffer == prompt:\n            buf = b'\\n'.join(self._linesReceived)\n            if buf.startswith(prompt):\n                buf = buf[len(prompt):]\n            self.clearBuffer()\n            d, self._expectingCommand = self._expectingCommand, None\n            d.callback(buf)\n\n\n    def errReceived(self, data):\n        \"\"\"\n        Called by Twisted when the cftp client prints data to stderr.\n        \"\"\"\n        log.msg('err: %s' % data)\n\n\n    def getBuffer(self):\n        \"\"\"\n        Return the contents of the buffer of data received from stdout.\n        \"\"\"\n        return self.buffer\n\n\n    def runCommand(self, command):\n        \"\"\"\n        Issue the given command via the cftp client. Return a C{Deferred} that\n        fires when the server returns a result. Note that the C{Deferred} will\n        callback even if the server returns some kind of error.\n\n        @param command: A string containing an sftp command.\n\n        @return: A C{Deferred} that fires when the sftp server returns a\n        result. The payload is the server's response string.\n        \"\"\"\n        self._expectingCommand = defer.Deferred()\n        self.clearBuffer()\n        if isinstance(command, unicode):\n            command = command.encode(\"utf-8\")\n        self.transport.write(command + b'\\n')\n        return self._expectingCommand\n\n\n    def runScript(self, commands):\n        \"\"\"\n        Run each command in sequence and return a Deferred that fires when all\n        commands are completed.\n\n        @param commands: A list of strings containing sftp commands.\n\n        @return: A C{Deferred} that fires when all commands are completed. The\n        payload is a list of response strings from the server, in the same\n        order as the commands.\n        \"\"\"\n        sem = defer.DeferredSemaphore(1)\n        dl = [sem.run(self.runCommand, command) for command in commands]\n        return defer.gatherResults(dl)\n\n\n    def killProcess(self):\n        \"\"\"\n        Kill the process if it is still running.\n\n        If the process is still running, sends a KILL signal to the transport\n        and returns a C{Deferred} which fires when L{processEnded} is called.\n\n        @return: a C{Deferred}.\n        \"\"\"\n        if self._processEnded:\n            return defer.succeed(None)\n        self.onProcessEnd = defer.Deferred()\n        self.transport.signalProcess('KILL')\n        return self.onProcessEnd\n\n\n    def processEnded(self, reason):\n        \"\"\"\n        Called by Twisted when the cftp client process ends.\n        \"\"\"\n        self._processEnded = True\n        if self.onProcessEnd:\n            d, self.onProcessEnd = self.onProcessEnd, None\n            d.callback(None)\n\n\n\nclass CFTPClientTestBase(SFTPTestBase):\n    def setUp(self):\n        with open('dsa_test.pub', 'wb') as f:\n            f.write(test_ssh.publicDSA_openssh)\n        with open('dsa_test', 'wb') as f:\n            f.write(test_ssh.privateDSA_openssh)\n        os.chmod('dsa_test', 33152)\n        with open('kh_test', 'wb') as f:\n            f.write(b'127.0.0.1 ' + test_ssh.publicRSA_openssh)\n        return SFTPTestBase.setUp(self)\n\n\n    def startServer(self):\n        realm = FileTransferTestRealm(self.testDir)\n        p = portal.Portal(realm)\n        p.registerChecker(test_ssh.conchTestPublicKeyChecker())\n        fac = test_ssh.ConchTestServerFactory()\n        fac.portal = p\n        self.server = reactor.listenTCP(0, fac, interface=\"127.0.0.1\")\n\n\n    def stopServer(self):\n        if not hasattr(self.server.factory, 'proto'):\n            return self._cbStopServer(None)\n        self.server.factory.proto.expectedLoseConnection = 1\n        d = defer.maybeDeferred(\n            self.server.factory.proto.transport.loseConnection)\n        d.addCallback(self._cbStopServer)\n        return d\n\n\n    def _cbStopServer(self, ignored):\n        return defer.maybeDeferred(self.server.stopListening)\n\n\n    def tearDown(self):\n        for f in ['dsa_test.pub', 'dsa_test', 'kh_test']:\n            try:\n                os.remove(f)\n            except:\n                pass\n        return SFTPTestBase.tearDown(self)\n\n\n\nclass OurServerCmdLineClientTests(CFTPClientTestBase):\n    \"\"\"\n    Functional tests which launch a SFTP server over TCP on localhost and check\n    cftp command line interface using a spawned process.\n\n    Due to the spawned process you can not add a debugger breakpoint for the\n    client code.\n    \"\"\"\n\n    def setUp(self):\n        CFTPClientTestBase.setUp(self)\n\n        self.startServer()\n        cmds = ('-p %i -l testuser '\n               '--known-hosts kh_test '\n               '--user-authentications publickey '\n               '--host-key-algorithms ssh-rsa '\n               '-i dsa_test '\n               '-a '\n               '-v '\n               '127.0.0.1')\n        port = self.server.getHost().port\n        cmds = test_conch._makeArgs((cmds % port).split(), mod='cftp')\n        log.msg('running %s %s' % (sys.executable, cmds))\n        d = defer.Deferred()\n        self.processProtocol = SFTPTestProcess(d)\n        d.addCallback(lambda _: self.processProtocol.clearBuffer())\n        env = os.environ.copy()\n        env['PYTHONPATH'] = os.pathsep.join(sys.path)\n        encodedCmds = []\n        encodedEnv = {}\n        for cmd in cmds:\n            if isinstance(cmd, unicode):\n                cmd = cmd.encode(\"utf-8\")\n            encodedCmds.append(cmd)\n        for var in env:\n            val = env[var]\n            if isinstance(var, unicode):\n                var = var.encode(\"utf-8\")\n            if isinstance(val, unicode):\n                val = val.encode(\"utf-8\")\n            encodedEnv[var] = val\n        log.msg(encodedCmds)\n        log.msg(encodedEnv)\n        reactor.spawnProcess(self.processProtocol, sys.executable, encodedCmds,\n                             env=encodedEnv)\n        return d\n\n\n    def tearDown(self):\n        d = self.stopServer()\n        d.addCallback(lambda _: self.processProtocol.killProcess())\n        return d\n\n\n    def _killProcess(self, ignored):\n        try:\n            self.processProtocol.transport.signalProcess('KILL')\n        except error.ProcessExitedAlready:\n            pass\n\n\n    def runCommand(self, command):\n        \"\"\"\n        Run the given command with the cftp client. Return a C{Deferred} that\n        fires when the command is complete. Payload is the server's output for\n        that command.\n        \"\"\"\n        return self.processProtocol.runCommand(command)\n\n\n    def runScript(self, *commands):\n        \"\"\"\n        Run the given commands with the cftp client. Returns a C{Deferred}\n        that fires when the commands are all complete. The C{Deferred}'s\n        payload is a list of output for each command.\n        \"\"\"\n        return self.processProtocol.runScript(commands)\n\n\n    def testCdPwd(self):\n        \"\"\"\n        Test that 'pwd' reports the current remote directory, that 'lpwd'\n        reports the current local directory, and that changing to a\n        subdirectory then changing to its parent leaves you in the original\n        remote directory.\n        \"\"\"\n        # XXX - not actually a unit test, see docstring.\n        homeDir = self.testDir\n        d = self.runScript('pwd', 'lpwd', 'cd testDirectory', 'cd ..', 'pwd')\n\n        def cmdOutput(output):\n            \"\"\"\n            Callback function for handling command output.\n            \"\"\"\n            cmds = []\n            for cmd in output:\n                if _PY3 and isinstance(cmd, bytes):\n                    cmd = cmd.decode(\"utf-8\")\n                cmds.append(cmd)\n            return cmds[:3] + cmds[4:]\n\n        d.addCallback(cmdOutput)\n        d.addCallback(self.assertEqual,\n                      [homeDir.path, os.getcwd(), '', homeDir.path])\n        return d\n\n\n    def testChAttrs(self):\n        \"\"\"\n        Check that 'ls -l' output includes the access permissions and that\n        this output changes appropriately with 'chmod'.\n        \"\"\"\n        def _check(results):\n            self.flushLoggedErrors()\n            self.assertTrue(results[0].startswith(b'-rw-r--r--'))\n            self.assertEqual(results[1], b'')\n            self.assertTrue(results[2].startswith(b'----------'), results[2])\n            self.assertEqual(results[3], b'')\n\n        d = self.runScript('ls -l testfile1', 'chmod 0 testfile1',\n                           'ls -l testfile1', 'chmod 644 testfile1')\n        return d.addCallback(_check)\n        # XXX test chgrp/own\n\n\n    def testList(self):\n        \"\"\"\n        Check 'ls' works as expected. Checks for wildcards, hidden files,\n        listing directories and listing empty directories.\n        \"\"\"\n        def _check(results):\n            self.assertEqual(results[0], [b'testDirectory', b'testRemoveFile',\n                                          b'testRenameFile', b'testfile1'])\n            self.assertEqual(results[1], [b'testDirectory', b'testRemoveFile',\n                                          b'testRenameFile', b'testfile1'])\n            self.assertEqual(results[2], [b'testRemoveFile', b'testRenameFile'])\n            self.assertEqual(results[3], [b'.testHiddenFile', b'testRemoveFile',\n                                          b'testRenameFile'])\n            self.assertEqual(results[4], [b''])\n        d = self.runScript('ls', 'ls ../' + self.testDir.basename(),\n                           'ls *File', 'ls -a *File', 'ls -l testDirectory')\n        d.addCallback(lambda xs: [x.split(b'\\n') for x in xs])\n        return d.addCallback(_check)\n\n\n    def testHelp(self):\n        \"\"\"\n        Check that running the '?' command returns help.\n        \"\"\"\n        d = self.runCommand('?')\n\n        helpText = cftp.StdioClient(None).cmd_HELP('').strip()\n        if isinstance(helpText, unicode):\n            helpText = helpText.encode(\"utf-8\")\n        d.addCallback(self.assertEqual, helpText)\n        return d\n\n\n    def assertFilesEqual(self, name1, name2, msg=None):\n        \"\"\"\n        Assert that the files at C{name1} and C{name2} contain exactly the\n        same data.\n        \"\"\"\n        self.assertEqual(name1.getContent(), name2.getContent(), msg)\n\n\n    def testGet(self):\n        \"\"\"\n        Test that 'get' saves the remote file to the correct local location,\n        that the output of 'get' is correct and that 'rm' actually removes\n        the file.\n        \"\"\"\n        # XXX - not actually a unit test\n        expectedOutput = (\"Transferred %s/testfile1 to %s/test file2\"\n                          % (self.testDir.path, self.testDir.path))\n        if isinstance(expectedOutput, unicode):\n            expectedOutput = expectedOutput.encode(\"utf-8\")\n        def _checkGet(result):\n            self.assertTrue(result.endswith(expectedOutput))\n            self.assertFilesEqual(self.testDir.child('testfile1'),\n                                  self.testDir.child('test file2'),\n                                  \"get failed\")\n            return self.runCommand('rm \"test file2\"')\n\n        d = self.runCommand('get testfile1 \"%s/test file2\"' % (self.testDir.path,))\n        d.addCallback(_checkGet)\n        d.addCallback(lambda _: self.assertFalse(\n            self.testDir.child('test file2').exists()))\n        return d\n\n\n    def testWildcardGet(self):\n        \"\"\"\n        Test that 'get' works correctly when given wildcard parameters.\n        \"\"\"\n        def _check(ignored):\n            self.assertFilesEqual(self.testDir.child('testRemoveFile'),\n                                  FilePath('testRemoveFile'),\n                                  'testRemoveFile get failed')\n            self.assertFilesEqual(self.testDir.child('testRenameFile'),\n                                  FilePath('testRenameFile'),\n                                  'testRenameFile get failed')\n\n        d = self.runCommand('get testR*')\n        return d.addCallback(_check)\n\n\n    def testPut(self):\n        \"\"\"\n        Check that 'put' uploads files correctly and that they can be\n        successfully removed. Also check the output of the put command.\n        \"\"\"\n        # XXX - not actually a unit test\n        expectedOutput = (b'Transferred ' + self.testDir.asBytesMode().path +\n                          b'/testfile1 to ' + self.testDir.asBytesMode().path +\n                          b'/test\"file2')\n        def _checkPut(result):\n            self.assertFilesEqual(self.testDir.child('testfile1'),\n                                  self.testDir.child('test\"file2'))\n            self.assertTrue(result.endswith(expectedOutput))\n            return self.runCommand('rm \"test\\\\\"file2\"')\n\n        d = self.runCommand('put %s/testfile1 \"test\\\\\"file2\"'\n                            % (self.testDir.path,))\n        d.addCallback(_checkPut)\n        d.addCallback(lambda _: self.assertFalse(\n            self.testDir.child('test\"file2').exists()))\n        return d\n\n\n    def test_putOverLongerFile(self):\n        \"\"\"\n        Check that 'put' uploads files correctly when overwriting a longer\n        file.\n        \"\"\"\n        # XXX - not actually a unit test\n        with self.testDir.child('shorterFile').open(mode='w') as f:\n            f.write(b\"a\")\n        with self.testDir.child('longerFile').open(mode='w') as f:\n            f.write(b\"bb\")\n        def _checkPut(result):\n            self.assertFilesEqual(self.testDir.child('shorterFile'),\n                                  self.testDir.child('longerFile'))\n\n        d = self.runCommand('put %s/shorterFile longerFile'\n                            % (self.testDir.path,))\n        d.addCallback(_checkPut)\n        return d\n\n\n    def test_putMultipleOverLongerFile(self):\n        \"\"\"\n        Check that 'put' uploads files correctly when overwriting a longer\n        file and you use a wildcard to specify the files to upload.\n        \"\"\"\n        # XXX - not actually a unit test\n        someDir = self.testDir.child('dir')\n        someDir.createDirectory()\n        with someDir.child('file').open(mode='w') as f:\n            f.write(b\"a\")\n        with self.testDir.child('file').open(mode='w') as f:\n            f.write(b\"bb\")\n        def _checkPut(result):\n            self.assertFilesEqual(someDir.child('file'),\n                                  self.testDir.child('file'))\n\n        d = self.runCommand('put %s/dir/*'\n                            % (self.testDir.path,))\n        d.addCallback(_checkPut)\n        return d\n\n\n    def testWildcardPut(self):\n        \"\"\"\n        What happens if you issue a 'put' command and include a wildcard (i.e.\n        '*') in parameter? Check that all files matching the wildcard are\n        uploaded to the correct directory.\n        \"\"\"\n        def check(results):\n            self.assertEqual(results[0], b'')\n            self.assertEqual(results[2], b'')\n\n            self.assertFilesEqual(self.testDir.child('testRemoveFile'),\n                                  self.testDir.parent().child('testRemoveFile'),\n                                  'testRemoveFile get failed')\n            self.assertFilesEqual(self.testDir.child('testRenameFile'),\n                                  self.testDir.parent().child('testRenameFile'),\n                                  'testRenameFile get failed')\n\n        d = self.runScript('cd ..',\n                           'put %s/testR*' % (self.testDir.path,),\n                           'cd %s' % self.testDir.basename())\n        d.addCallback(check)\n        return d\n\n\n    def testLink(self):\n        \"\"\"\n        Test that 'ln' creates a file which appears as a link in the output of\n        'ls'. Check that removing the new file succeeds without output.\n        \"\"\"\n        def _check(results):\n            self.flushLoggedErrors()\n            self.assertEqual(results[0], b'')\n            self.assertTrue(results[1].startswith(b'l'), 'link failed')\n            return self.runCommand('rm testLink')\n\n        d = self.runScript('ln testLink testfile1', 'ls -l testLink')\n        d.addCallback(_check)\n        d.addCallback(self.assertEqual, b'')\n        return d\n\n\n    def testRemoteDirectory(self):\n        \"\"\"\n        Test that we can create and remove directories with the cftp client.\n        \"\"\"\n        def _check(results):\n            self.assertEqual(results[0], b'')\n            self.assertTrue(results[1].startswith(b'd'))\n            return self.runCommand('rmdir testMakeDirectory')\n\n        d = self.runScript('mkdir testMakeDirectory',\n                           'ls -l testMakeDirector?')\n        d.addCallback(_check)\n        d.addCallback(self.assertEqual, b'')\n        return d\n\n\n    def test_existingRemoteDirectory(self):\n        \"\"\"\n        Test that a C{mkdir} on an existing directory fails with the\n        appropriate error, and doesn't log an useless error server side.\n        \"\"\"\n        def _check(results):\n            self.assertEqual(results[0], b'')\n            self.assertEqual(results[1],\n                              b'remote error 11: mkdir failed')\n\n        d = self.runScript('mkdir testMakeDirectory',\n                           'mkdir testMakeDirectory')\n        d.addCallback(_check)\n        return d\n\n\n    def testLocalDirectory(self):\n        \"\"\"\n        Test that we can create a directory locally and remove it with the\n        cftp client. This test works because the 'remote' server is running\n        out of a local directory.\n        \"\"\"\n        d = self.runCommand('lmkdir %s/testLocalDirectory' % (self.testDir.path,))\n        d.addCallback(self.assertEqual, b'')\n        d.addCallback(lambda _: self.runCommand('rmdir testLocalDirectory'))\n        d.addCallback(self.assertEqual, b'')\n        return d\n\n\n    def testRename(self):\n        \"\"\"\n        Test that we can rename a file.\n        \"\"\"\n        def _check(results):\n            self.assertEqual(results[0], b'')\n            self.assertEqual(results[1], b'testfile2')\n            return self.runCommand('rename testfile2 testfile1')\n\n        d = self.runScript('rename testfile1 testfile2', 'ls testfile?')\n        d.addCallback(_check)\n        d.addCallback(self.assertEqual, b'')\n        return d\n\n\n\nclass OurServerBatchFileTests(CFTPClientTestBase):\n    \"\"\"\n    Functional tests which launch a SFTP server over localhost and checks csftp\n    in batch interface.\n    \"\"\"\n\n    def setUp(self):\n        CFTPClientTestBase.setUp(self)\n        self.startServer()\n\n\n    def tearDown(self):\n        CFTPClientTestBase.tearDown(self)\n        return self.stopServer()\n\n\n    def _getBatchOutput(self, f):\n        fn = self.mktemp()\n        with open(fn, 'w') as fp:\n            fp.write(f)\n        port = self.server.getHost().port\n        cmds = ('-p %i -l testuser '\n                    '--known-hosts kh_test '\n                    '--user-authentications publickey '\n                    '--host-key-algorithms ssh-rsa '\n                    '-i dsa_test '\n                    '-a '\n                    '-v -b %s 127.0.0.1') % (port, fn)\n        cmds = test_conch._makeArgs(cmds.split(), mod='cftp')[1:]\n        log.msg('running %s %s' % (sys.executable, cmds))\n        env = os.environ.copy()\n        env['PYTHONPATH'] = os.pathsep.join(sys.path)\n\n        self.server.factory.expectedLoseConnection = 1\n\n        d = getProcessOutputAndValue(sys.executable, cmds, env=env)\n\n        def _cleanup(res):\n            os.remove(fn)\n            return res\n\n        d.addCallback(lambda res: res[0])\n        d.addBoth(_cleanup)\n\n        return d\n\n\n    def testBatchFile(self):\n        \"\"\"\n        Test whether batch file function of cftp ('cftp -b batchfile').\n        This works by treating the file as a list of commands to be run.\n        \"\"\"\n        cmds = \"\"\"pwd\nls\nexit\n\"\"\"\n\n        def _cbCheckResult(res):\n            res = res.split(b'\\n')\n            log.msg('RES %s' % repr(res))\n            self.assertIn(self.testDir.asBytesMode().path, res[1])\n            self.assertEqual(res[3:-2], [b'testDirectory', b'testRemoveFile',\n                                             b'testRenameFile', b'testfile1'])\n\n        d = self._getBatchOutput(cmds)\n        d.addCallback(_cbCheckResult)\n        return d\n\n\n    def testError(self):\n        \"\"\"\n        Test that an error in the batch file stops running the batch.\n        \"\"\"\n        cmds = \"\"\"chown 0 missingFile\npwd\nexit\n\"\"\"\n\n        def _cbCheckResult(res):\n            self.assertNotIn(self.testDir.asBytesMode().path, res)\n\n        d = self._getBatchOutput(cmds)\n        d.addCallback(_cbCheckResult)\n        return d\n\n\n    def testIgnoredError(self):\n        \"\"\"\n        Test that a minus sign '-' at the front of a line ignores\n        any errors.\n        \"\"\"\n        cmds = \"\"\"-chown 0 missingFile\npwd\nexit\n\"\"\"\n        def _cbCheckResult(res):\n            self.assertIn(self.testDir.asBytesMode().path, res)\n\n        d = self._getBatchOutput(cmds)\n        d.addCallback(_cbCheckResult)\n        return d\n\n\n\nclass OurServerSftpClientTests(CFTPClientTestBase):\n    \"\"\"\n    Test the sftp server against sftp command line client.\n    \"\"\"\n\n    def setUp(self):\n        CFTPClientTestBase.setUp(self)\n        return self.startServer()\n\n\n    def tearDown(self):\n        return self.stopServer()\n\n\n    def test_extendedAttributes(self):\n        \"\"\"\n        Test the return of extended attributes by the server: the sftp client\n        should ignore them, but still be able to parse the response correctly.\n\n        This test is mainly here to check that\n        L{filetransfer.FILEXFER_ATTR_EXTENDED} has the correct value.\n        \"\"\"\n        fn = self.mktemp()\n        with open(fn, 'w') as f:\n            f.write(\"ls .\\nexit\")\n        port = self.server.getHost().port\n\n        oldGetAttr = FileTransferForTestAvatar._getAttrs\n        def _getAttrs(self, s):\n            attrs = oldGetAttr(self, s)\n            attrs[\"ext_foo\"] = \"bar\"\n            return attrs\n\n        self.patch(FileTransferForTestAvatar, \"_getAttrs\", _getAttrs)\n        self.server.factory.expectedLoseConnection = True\n\n        # PubkeyAcceptedKeyTypes does not exist prior to OpenSSH 7.0 so we\n        # first need to check if we can set it. If we can, -V will just print\n        # the version without doing anything else; if we can't, we will get a\n        # configuration error.\n        d = getProcessValue(\n            'ssh', ('-o', 'PubkeyAcceptedKeyTypes=ssh-dss', '-V'))\n        def hasPAKT(status):\n            if status == 0:\n                args = ('-o', 'PubkeyAcceptedKeyTypes=ssh-dss')\n            else:\n                args = ()\n            # Pass -F /dev/null to avoid the user's configuration file from\n            # being loaded, as it may contain settings that cause our tests to\n            # fail or hang.\n            args += ('-F', '/dev/null',\n                     '-o', 'IdentityFile=dsa_test',\n                     '-o', 'UserKnownHostsFile=kh_test',\n                     '-o', 'HostKeyAlgorithms=ssh-rsa',\n                     '-o', 'Port=%i' % (port,), '-b', fn, 'testuser@127.0.0.1')\n            return args\n\n        def check(result):\n            self.assertEqual(result[2], 0)\n            for i in [b'testDirectory', b'testRemoveFile',\n                      b'testRenameFile', b'testfile1']:\n                self.assertIn(i, result[0])\n        d.addCallback(hasPAKT)\n        d.addCallback(lambda args: getProcessOutputAndValue('sftp', args))\n        return d.addCallback(check)\n\n\n\nif None in (unix, cryptography, pyasn1,\n            interfaces.IReactorProcess(reactor, None)):\n    if _reason is None:\n        _reason = \"don't run w/o spawnProcess or cryptography or pyasn1\"\n    OurServerCmdLineClientTests.skip = _reason\n    OurServerBatchFileTests.skip = _reason\n    OurServerSftpClientTests.skip = _reason\n    StdioClientTests.skip = _reason\n    SSHSessionTests.skip = _reason\nelse:\n    from twisted.python.procutils import which\n    if not which('sftp'):\n        OurServerSftpClientTests.skip = \"no sftp command-line client available\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_channel.py",
    "content": "# Copyright Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest ssh/channel.py.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom zope.interface.verify import verifyObject\n\ntry:\n    from twisted.conch.ssh import channel\n    from twisted.conch.ssh.address import SSHTransportAddress\n    from twisted.conch.ssh.transport import SSHServerTransport\n    from twisted.conch.ssh.service import SSHService\n    from twisted.internet import interfaces\n    from twisted.internet.address import IPv4Address\n    from twisted.test.proto_helpers import StringTransport\n    skipTest = None\nexcept ImportError:\n    skipTest = 'Conch SSH not supported.'\n    SSHService = object\nfrom twisted.trial import unittest\nfrom twisted.python.compat import intToBytes\n\n\nclass MockConnection(SSHService):\n    \"\"\"\n    A mock for twisted.conch.ssh.connection.SSHConnection.  Record the data\n    that channels send, and when they try to close the connection.\n\n    @ivar data: a L{dict} mapping channel id #s to lists of data sent by that\n        channel.\n    @ivar extData: a L{dict} mapping channel id #s to lists of 2-tuples\n        (extended data type, data) sent by that channel.\n    @ivar closes: a L{dict} mapping channel id #s to True if that channel sent\n        a close message.\n    \"\"\"\n\n    def __init__(self):\n        self.data = {}\n        self.extData = {}\n        self.closes = {}\n\n\n    def logPrefix(self):\n        \"\"\"\n        Return our logging prefix.\n        \"\"\"\n        return \"MockConnection\"\n\n\n    def sendData(self, channel, data):\n        \"\"\"\n        Record the sent data.\n        \"\"\"\n        self.data.setdefault(channel, []).append(data)\n\n\n    def sendExtendedData(self, channel, type, data):\n        \"\"\"\n        Record the sent extended data.\n        \"\"\"\n        self.extData.setdefault(channel, []).append((type, data))\n\n\n    def sendClose(self, channel):\n        \"\"\"\n        Record that the channel sent a close message.\n        \"\"\"\n        self.closes[channel] = True\n\n\n\ndef connectSSHTransport(service, hostAddress=None, peerAddress=None):\n    \"\"\"\n    Connect a SSHTransport which is already connected to a remote peer to\n    the channel under test.\n\n    @param service: Service used over the connected transport.\n    @type service: L{SSHService}\n\n    @param hostAddress: Local address of the connected transport.\n    @type hostAddress: L{interfaces.IAddress}\n\n    @param peerAddress: Remote address of the connected transport.\n    @type peerAddress: L{interfaces.IAddress}\n    \"\"\"\n    transport = SSHServerTransport()\n    transport.makeConnection(StringTransport(\n        hostAddress=hostAddress, peerAddress=peerAddress))\n    transport.setService(service)\n\n\n\nclass ChannelTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{SSHChannel}.\n    \"\"\"\n\n    skip = skipTest\n\n    def setUp(self):\n        \"\"\"\n        Initialize the channel.  remoteMaxPacket is 10 so that data is able\n        to be sent (the default of 0 means no data is sent because no packets\n        are made).\n        \"\"\"\n        self.conn = MockConnection()\n        self.channel = channel.SSHChannel(conn=self.conn,\n                remoteMaxPacket=10)\n        self.channel.name = b'channel'\n\n\n    def test_interface(self):\n        \"\"\"\n        L{SSHChannel} instances provide L{interfaces.ITransport}.\n        \"\"\"\n        self.assertTrue(verifyObject(interfaces.ITransport, self.channel))\n\n\n    def test_init(self):\n        \"\"\"\n        Test that SSHChannel initializes correctly.  localWindowSize defaults\n        to 131072 (2**17) and localMaxPacket to 32768 (2**15) as reasonable\n        defaults (what OpenSSH uses for those variables).\n\n        The values in the second set of assertions are meaningless; they serve\n        only to verify that the instance variables are assigned in the correct\n        order.\n        \"\"\"\n        c = channel.SSHChannel(conn=self.conn)\n        self.assertEqual(c.localWindowSize, 131072)\n        self.assertEqual(c.localWindowLeft, 131072)\n        self.assertEqual(c.localMaxPacket, 32768)\n        self.assertEqual(c.remoteWindowLeft, 0)\n        self.assertEqual(c.remoteMaxPacket, 0)\n        self.assertEqual(c.conn, self.conn)\n        self.assertIsNone(c.data)\n        self.assertIsNone(c.avatar)\n\n        c2 = channel.SSHChannel(1, 2, 3, 4, 5, 6, 7)\n        self.assertEqual(c2.localWindowSize, 1)\n        self.assertEqual(c2.localWindowLeft, 1)\n        self.assertEqual(c2.localMaxPacket, 2)\n        self.assertEqual(c2.remoteWindowLeft, 3)\n        self.assertEqual(c2.remoteMaxPacket, 4)\n        self.assertEqual(c2.conn, 5)\n        self.assertEqual(c2.data, 6)\n        self.assertEqual(c2.avatar, 7)\n\n\n    def test_str(self):\n        \"\"\"\n        Test that str(SSHChannel) works gives the channel name and local and\n        remote windows at a glance..\n        \"\"\"\n        self.assertEqual(\n                str(self.channel), '<SSHChannel channel (lw 131072 rw 0)>')\n        self.assertEqual(\n                str(channel.SSHChannel(localWindow=1)),\n                '<SSHChannel None (lw 1 rw 0)>')\n\n\n    def test_bytes(self):\n        \"\"\"\n        Test that bytes(SSHChannel) works, gives the channel name and\n        local and remote windows at a glance..\n\n        \"\"\"\n        self.assertEqual(\n            self.channel.__bytes__(),\n            b'<SSHChannel channel (lw 131072 rw 0)>')\n        self.assertEqual(\n            channel.SSHChannel(localWindow=1).__bytes__(),\n            b'<SSHChannel None (lw 1 rw 0)>')\n\n\n    def test_logPrefix(self):\n        \"\"\"\n        Test that SSHChannel.logPrefix gives the name of the channel, the\n        local channel ID and the underlying connection.\n        \"\"\"\n        self.assertEqual(self.channel.logPrefix(), 'SSHChannel channel '\n                '(unknown) on MockConnection')\n\n\n    def test_addWindowBytes(self):\n        \"\"\"\n        Test that addWindowBytes adds bytes to the window and resumes writing\n        if it was paused.\n        \"\"\"\n        cb = [False]\n        def stubStartWriting():\n            cb[0] = True\n        self.channel.startWriting = stubStartWriting\n        self.channel.write(b'test')\n        self.channel.writeExtended(1, b'test')\n        self.channel.addWindowBytes(50)\n        self.assertEqual(self.channel.remoteWindowLeft, 50 - 4 - 4)\n        self.assertTrue(self.channel.areWriting)\n        self.assertTrue(cb[0])\n        self.assertEqual(self.channel.buf, b'')\n        self.assertEqual(self.conn.data[self.channel], [b'test'])\n        self.assertEqual(self.channel.extBuf, [])\n        self.assertEqual(self.conn.extData[self.channel], [(1, b'test')])\n\n        cb[0] = False\n        self.channel.addWindowBytes(20)\n        self.assertFalse(cb[0])\n\n        self.channel.write(b'a'*80)\n        self.channel.loseConnection()\n        self.channel.addWindowBytes(20)\n        self.assertFalse(cb[0])\n\n\n    def test_requestReceived(self):\n        \"\"\"\n        Test that requestReceived handles requests by dispatching them to\n        request_* methods.\n        \"\"\"\n        self.channel.request_test_method = lambda data: data == b''\n        self.assertTrue(self.channel.requestReceived(b'test-method', b''))\n        self.assertFalse(self.channel.requestReceived(b'test-method', b'a'))\n        self.assertFalse(self.channel.requestReceived(b'bad-method', b''))\n\n\n    def test_closeReceieved(self):\n        \"\"\"\n        Test that the default closeReceieved closes the connection.\n        \"\"\"\n        self.assertFalse(self.channel.closing)\n        self.channel.closeReceived()\n        self.assertTrue(self.channel.closing)\n\n\n    def test_write(self):\n        \"\"\"\n        Test that write handles data correctly.  Send data up to the size\n        of the remote window, splitting the data into packets of length\n        remoteMaxPacket.\n        \"\"\"\n        cb = [False]\n        def stubStopWriting():\n            cb[0] = True\n        # no window to start with\n        self.channel.stopWriting = stubStopWriting\n        self.channel.write(b'd')\n        self.channel.write(b'a')\n        self.assertFalse(self.channel.areWriting)\n        self.assertTrue(cb[0])\n        # regular write\n        self.channel.addWindowBytes(20)\n        self.channel.write(b'ta')\n        data = self.conn.data[self.channel]\n        self.assertEqual(data, [b'da', b'ta'])\n        self.assertEqual(self.channel.remoteWindowLeft, 16)\n        # larger than max packet\n        self.channel.write(b'12345678901')\n        self.assertEqual(data, [b'da', b'ta', b'1234567890', b'1'])\n        self.assertEqual(self.channel.remoteWindowLeft, 5)\n        # running out of window\n        cb[0] = False\n        self.channel.write(b'123456')\n        self.assertFalse(self.channel.areWriting)\n        self.assertTrue(cb[0])\n        self.assertEqual(data, [b'da', b'ta', b'1234567890', b'1', b'12345'])\n        self.assertEqual(self.channel.buf, b'6')\n        self.assertEqual(self.channel.remoteWindowLeft, 0)\n\n\n    def test_writeExtended(self):\n        \"\"\"\n        Test that writeExtended handles data correctly.  Send extended data\n        up to the size of the window, splitting the extended data into packets\n        of length remoteMaxPacket.\n        \"\"\"\n        cb = [False]\n        def stubStopWriting():\n            cb[0] = True\n        # no window to start with\n        self.channel.stopWriting = stubStopWriting\n        self.channel.writeExtended(1, b'd')\n        self.channel.writeExtended(1, b'a')\n        self.channel.writeExtended(2, b't')\n        self.assertFalse(self.channel.areWriting)\n        self.assertTrue(cb[0])\n        # regular write\n        self.channel.addWindowBytes(20)\n        self.channel.writeExtended(2, b'a')\n        data = self.conn.extData[self.channel]\n        self.assertEqual(data, [(1, b'da'), (2, b't'), (2, b'a')])\n        self.assertEqual(self.channel.remoteWindowLeft, 16)\n        # larger than max packet\n        self.channel.writeExtended(3, b'12345678901')\n        self.assertEqual(data, [(1, b'da'), (2, b't'), (2, b'a'),\n            (3, b'1234567890'), (3, b'1')])\n        self.assertEqual(self.channel.remoteWindowLeft, 5)\n        # running out of window\n        cb[0] = False\n        self.channel.writeExtended(4, b'123456')\n        self.assertFalse(self.channel.areWriting)\n        self.assertTrue(cb[0])\n        self.assertEqual(data, [(1, b'da'), (2, b't'), (2, b'a'),\n            (3, b'1234567890'), (3, b'1'), (4, b'12345')])\n        self.assertEqual(self.channel.extBuf, [[4, b'6']])\n        self.assertEqual(self.channel.remoteWindowLeft, 0)\n\n\n    def test_writeSequence(self):\n        \"\"\"\n        Test that writeSequence is equivalent to write(''.join(sequece)).\n        \"\"\"\n        self.channel.addWindowBytes(20)\n        self.channel.writeSequence(map(intToBytes, range(10)))\n        self.assertEqual(self.conn.data[self.channel], [b'0123456789'])\n\n\n    def test_loseConnection(self):\n        \"\"\"\n        Tesyt that loseConnection() doesn't close the channel until all\n        the data is sent.\n        \"\"\"\n        self.channel.write(b'data')\n        self.channel.writeExtended(1, b'datadata')\n        self.channel.loseConnection()\n        self.assertIsNone(self.conn.closes.get(self.channel))\n        self.channel.addWindowBytes(4) # send regular data\n        self.assertIsNone(self.conn.closes.get(self.channel))\n        self.channel.addWindowBytes(8) # send extended data\n        self.assertTrue(self.conn.closes.get(self.channel))\n\n\n    def test_getPeer(self):\n        \"\"\"\n        L{SSHChannel.getPeer} returns the same object as the underlying\n        transport's C{getPeer} method returns.\n        \"\"\"\n        peer = IPv4Address('TCP', '192.168.0.1', 54321)\n        connectSSHTransport(service=self.channel.conn, peerAddress=peer)\n\n        self.assertEqual(SSHTransportAddress(peer), self.channel.getPeer())\n\n\n    def test_getHost(self):\n        \"\"\"\n        L{SSHChannel.getHost} returns the same object as the underlying\n        transport's C{getHost} method returns.\n        \"\"\"\n        host = IPv4Address('TCP', '127.0.0.1', 12345)\n        connectSSHTransport(service=self.channel.conn, hostAddress=host)\n\n        self.assertEqual(SSHTransportAddress(host), self.channel.getHost())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_checkers.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.checkers}.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\ntry:\n    import crypt\nexcept ImportError:\n    cryptSkip = 'cannot run without crypt module'\nelse:\n    cryptSkip = None\n\nimport os\n\nfrom collections import namedtuple\nfrom io import BytesIO\n\nfrom zope.interface.verify import verifyObject\n\nfrom twisted.python import util\nfrom twisted.python.compat import _b64encodebytes\nfrom twisted.python.failure import Failure\nfrom twisted.python.reflect import requireModule\nfrom twisted.trial.unittest import TestCase\nfrom twisted.python.filepath import FilePath\nfrom twisted.cred.checkers import InMemoryUsernamePasswordDatabaseDontUse\nfrom twisted.cred.credentials import UsernamePassword, IUsernamePassword, \\\n    SSHPrivateKey, ISSHPrivateKey\nfrom twisted.cred.error import UnhandledCredentials, UnauthorizedLogin\nfrom twisted.python.fakepwd import UserDatabase, ShadowDatabase\nfrom twisted.test.test_process import MockOS\n\n\nif requireModule('cryptography') and requireModule('pyasn1'):\n    dependencySkip = None\n    from twisted.conch.ssh import keys\n    from twisted.conch import checkers\n    from twisted.conch.error import NotEnoughAuthentication, ValidPublicKey\n    from twisted.conch.test import keydata\nelse:\n    dependencySkip = \"can't run without cryptography and PyASN1\"\n\nif getattr(os, 'geteuid', None) is None:\n    euidSkip = \"Cannot run without effective UIDs (questionable)\"\nelse:\n    euidSkip = None\n\n\nclass HelperTests(TestCase):\n    \"\"\"\n    Tests for helper functions L{verifyCryptedPassword}, L{_pwdGetByName} and\n    L{_shadowGetByName}.\n    \"\"\"\n    skip = cryptSkip or dependencySkip\n\n    def setUp(self):\n        self.mockos = MockOS()\n\n\n    def test_verifyCryptedPassword(self):\n        \"\"\"\n        L{verifyCryptedPassword} returns C{True} if the plaintext password\n        passed to it matches the encrypted password passed to it.\n        \"\"\"\n        password = 'secret string'\n        salt = 'salty'\n        crypted = crypt.crypt(password, salt)\n        self.assertTrue(\n            checkers.verifyCryptedPassword(crypted, password),\n            '%r supposed to be valid encrypted password for %r' % (\n                crypted, password))\n\n\n    def test_verifyCryptedPasswordMD5(self):\n        \"\"\"\n        L{verifyCryptedPassword} returns True if the provided cleartext password\n        matches the provided MD5 password hash.\n        \"\"\"\n        password = 'password'\n        salt = '$1$salt'\n        crypted = crypt.crypt(password, salt)\n        self.assertTrue(\n            checkers.verifyCryptedPassword(crypted, password),\n            '%r supposed to be valid encrypted password for %s' % (\n                crypted, password))\n\n\n    def test_refuteCryptedPassword(self):\n        \"\"\"\n        L{verifyCryptedPassword} returns C{False} if the plaintext password\n        passed to it does not match the encrypted password passed to it.\n        \"\"\"\n        password = 'string secret'\n        wrong = 'secret string'\n        crypted = crypt.crypt(password, password)\n        self.assertFalse(\n            checkers.verifyCryptedPassword(crypted, wrong),\n            '%r not supposed to be valid encrypted password for %s' % (\n                crypted, wrong))\n\n\n    def test_pwdGetByName(self):\n        \"\"\"\n        L{_pwdGetByName} returns a tuple of items from the UNIX /etc/passwd\n        database if the L{pwd} module is present.\n        \"\"\"\n        userdb = UserDatabase()\n        userdb.addUser(\n            'alice', 'secrit', 1, 2, 'first last', '/foo', '/bin/sh')\n        self.patch(checkers, 'pwd', userdb)\n        self.assertEqual(\n            checkers._pwdGetByName('alice'), userdb.getpwnam('alice'))\n\n\n    def test_pwdGetByNameWithoutPwd(self):\n        \"\"\"\n        If the C{pwd} module isn't present, L{_pwdGetByName} returns L{None}.\n        \"\"\"\n        self.patch(checkers, 'pwd', None)\n        self.assertIsNone(checkers._pwdGetByName('alice'))\n\n\n    def test_shadowGetByName(self):\n        \"\"\"\n        L{_shadowGetByName} returns a tuple of items from the UNIX /etc/shadow\n        database if the L{spwd} is present.\n        \"\"\"\n        userdb = ShadowDatabase()\n        userdb.addUser('bob', 'passphrase', 1, 2, 3, 4, 5, 6, 7)\n        self.patch(checkers, 'spwd', userdb)\n\n        self.mockos.euid = 2345\n        self.mockos.egid = 1234\n        self.patch(util, 'os', self.mockos)\n\n        self.assertEqual(\n            checkers._shadowGetByName('bob'), userdb.getspnam('bob'))\n        self.assertEqual(self.mockos.seteuidCalls, [0, 2345])\n        self.assertEqual(self.mockos.setegidCalls, [0, 1234])\n\n\n    def test_shadowGetByNameWithoutSpwd(self):\n        \"\"\"\n        L{_shadowGetByName} returns L{None} if C{spwd} is not present.\n        \"\"\"\n        self.patch(checkers, 'spwd', None)\n\n        self.assertIsNone(checkers._shadowGetByName('bob'))\n        self.assertEqual(self.mockos.seteuidCalls, [])\n        self.assertEqual(self.mockos.setegidCalls, [])\n\n\n\nclass SSHPublicKeyDatabaseTests(TestCase):\n    \"\"\"\n    Tests for L{SSHPublicKeyDatabase}.\n    \"\"\"\n    skip = euidSkip or dependencySkip\n\n    def setUp(self):\n        self.checker = checkers.SSHPublicKeyDatabase()\n        self.key1 = _b64encodebytes(b\"foobar\")\n        self.key2 = _b64encodebytes(b\"eggspam\")\n        self.content = (b\"t1 \" + self.key1 + b\" foo\\nt2 \" + self.key2 +\n                        b\" egg\\n\")\n\n        self.mockos = MockOS()\n        self.mockos.path = FilePath(self.mktemp())\n        self.mockos.path.makedirs()\n        self.patch(util, 'os', self.mockos)\n        self.sshDir = self.mockos.path.child('.ssh')\n        self.sshDir.makedirs()\n\n        userdb = UserDatabase()\n        userdb.addUser(\n            b'user', b'password', 1, 2, b'first last',\n            self.mockos.path.path, b'/bin/shell')\n        self.checker._userdb = userdb\n\n\n    def test_deprecated(self):\n        \"\"\"\n        L{SSHPublicKeyDatabase} is deprecated as of version 15.0\n        \"\"\"\n        warningsShown = self.flushWarnings(\n            offendingFunctions=[self.setUp])\n        self.assertEqual(warningsShown[0]['category'], DeprecationWarning)\n        self.assertEqual(\n            warningsShown[0]['message'],\n            \"twisted.conch.checkers.SSHPublicKeyDatabase \"\n            \"was deprecated in Twisted 15.0.0: Please use \"\n            \"twisted.conch.checkers.SSHPublicKeyChecker, \"\n            \"initialized with an instance of \"\n            \"twisted.conch.checkers.UNIXAuthorizedKeysFiles instead.\")\n        self.assertEqual(len(warningsShown), 1)\n\n\n    def _testCheckKey(self, filename):\n        self.sshDir.child(filename).setContent(self.content)\n        user = UsernamePassword(b\"user\", b\"password\")\n        user.blob = b\"foobar\"\n        self.assertTrue(self.checker.checkKey(user))\n        user.blob = b\"eggspam\"\n        self.assertTrue(self.checker.checkKey(user))\n        user.blob = b\"notallowed\"\n        self.assertFalse(self.checker.checkKey(user))\n\n\n    def test_checkKey(self):\n        \"\"\"\n        L{SSHPublicKeyDatabase.checkKey} should retrieve the content of the\n        authorized_keys file and check the keys against that file.\n        \"\"\"\n        self._testCheckKey(\"authorized_keys\")\n        self.assertEqual(self.mockos.seteuidCalls, [])\n        self.assertEqual(self.mockos.setegidCalls, [])\n\n\n    def test_checkKey2(self):\n        \"\"\"\n        L{SSHPublicKeyDatabase.checkKey} should retrieve the content of the\n        authorized_keys2 file and check the keys against that file.\n        \"\"\"\n        self._testCheckKey(\"authorized_keys2\")\n        self.assertEqual(self.mockos.seteuidCalls, [])\n        self.assertEqual(self.mockos.setegidCalls, [])\n\n\n    def test_checkKeyAsRoot(self):\n        \"\"\"\n        If the key file is readable, L{SSHPublicKeyDatabase.checkKey} should\n        switch its uid/gid to the ones of the authenticated user.\n        \"\"\"\n        keyFile = self.sshDir.child(\"authorized_keys\")\n        keyFile.setContent(self.content)\n        # Fake permission error by changing the mode\n        keyFile.chmod(0o000)\n        self.addCleanup(keyFile.chmod, 0o777)\n        # And restore the right mode when seteuid is called\n        savedSeteuid = self.mockos.seteuid\n        def seteuid(euid):\n            keyFile.chmod(0o777)\n            return savedSeteuid(euid)\n        self.mockos.euid = 2345\n        self.mockos.egid = 1234\n        self.patch(self.mockos, \"seteuid\", seteuid)\n        self.patch(util, 'os', self.mockos)\n        user = UsernamePassword(b\"user\", b\"password\")\n        user.blob = b\"foobar\"\n        self.assertTrue(self.checker.checkKey(user))\n        self.assertEqual(self.mockos.seteuidCalls, [0, 1, 0, 2345])\n        self.assertEqual(self.mockos.setegidCalls, [2, 1234])\n\n\n    def test_requestAvatarId(self):\n        \"\"\"\n        L{SSHPublicKeyDatabase.requestAvatarId} should return the avatar id\n        passed in if its C{_checkKey} method returns True.\n        \"\"\"\n        def _checkKey(ignored):\n            return True\n        self.patch(self.checker, 'checkKey', _checkKey)\n        credentials = SSHPrivateKey(\n            b'test', b'ssh-rsa', keydata.publicRSA_openssh, b'foo',\n            keys.Key.fromString(keydata.privateRSA_openssh).sign(b'foo'))\n        d = self.checker.requestAvatarId(credentials)\n        def _verify(avatarId):\n            self.assertEqual(avatarId, b'test')\n        return d.addCallback(_verify)\n\n\n    def test_requestAvatarIdWithoutSignature(self):\n        \"\"\"\n        L{SSHPublicKeyDatabase.requestAvatarId} should raise L{ValidPublicKey}\n        if the credentials represent a valid key without a signature.  This\n        tells the user that the key is valid for login, but does not actually\n        allow that user to do so without a signature.\n        \"\"\"\n        def _checkKey(ignored):\n            return True\n        self.patch(self.checker, 'checkKey', _checkKey)\n        credentials = SSHPrivateKey(\n            b'test', b'ssh-rsa', keydata.publicRSA_openssh, None, None)\n        d = self.checker.requestAvatarId(credentials)\n        return self.assertFailure(d, ValidPublicKey)\n\n\n    def test_requestAvatarIdInvalidKey(self):\n        \"\"\"\n        If L{SSHPublicKeyDatabase.checkKey} returns False,\n        C{_cbRequestAvatarId} should raise L{UnauthorizedLogin}.\n        \"\"\"\n        def _checkKey(ignored):\n            return False\n        self.patch(self.checker, 'checkKey', _checkKey)\n        d = self.checker.requestAvatarId(None);\n        return self.assertFailure(d, UnauthorizedLogin)\n\n\n    def test_requestAvatarIdInvalidSignature(self):\n        \"\"\"\n        Valid keys with invalid signatures should cause\n        L{SSHPublicKeyDatabase.requestAvatarId} to return a {UnauthorizedLogin}\n        failure\n        \"\"\"\n        def _checkKey(ignored):\n            return True\n        self.patch(self.checker, 'checkKey', _checkKey)\n        credentials = SSHPrivateKey(\n            b'test', b'ssh-rsa', keydata.publicRSA_openssh, b'foo',\n            keys.Key.fromString(keydata.privateDSA_openssh).sign(b'foo'))\n        d = self.checker.requestAvatarId(credentials)\n        return self.assertFailure(d, UnauthorizedLogin)\n\n\n    def test_requestAvatarIdNormalizeException(self):\n        \"\"\"\n        Exceptions raised while verifying the key should be normalized into an\n        C{UnauthorizedLogin} failure.\n        \"\"\"\n        def _checkKey(ignored):\n            return True\n        self.patch(self.checker, 'checkKey', _checkKey)\n        credentials = SSHPrivateKey(b'test', None, b'blob', b'sigData', b'sig')\n        d = self.checker.requestAvatarId(credentials)\n        def _verifyLoggedException(failure):\n            errors = self.flushLoggedErrors(keys.BadKeyError)\n            self.assertEqual(len(errors), 1)\n            return failure\n        d.addErrback(_verifyLoggedException)\n        return self.assertFailure(d, UnauthorizedLogin)\n\n\n\nclass SSHProtocolCheckerTests(TestCase):\n    \"\"\"\n    Tests for L{SSHProtocolChecker}.\n    \"\"\"\n\n    skip = dependencySkip\n\n    def test_registerChecker(self):\n        \"\"\"\n        L{SSHProcotolChecker.registerChecker} should add the given checker to\n        the list of registered checkers.\n        \"\"\"\n        checker = checkers.SSHProtocolChecker()\n        self.assertEqual(checker.credentialInterfaces, [])\n        checker.registerChecker(checkers.SSHPublicKeyDatabase(), )\n        self.assertEqual(checker.credentialInterfaces, [ISSHPrivateKey])\n        self.assertIsInstance(checker.checkers[ISSHPrivateKey],\n                              checkers.SSHPublicKeyDatabase)\n\n\n    def test_registerCheckerWithInterface(self):\n        \"\"\"\n        If a specific interface is passed into\n        L{SSHProtocolChecker.registerChecker}, that interface should be\n        registered instead of what the checker specifies in\n        credentialIntefaces.\n        \"\"\"\n        checker = checkers.SSHProtocolChecker()\n        self.assertEqual(checker.credentialInterfaces, [])\n        checker.registerChecker(checkers.SSHPublicKeyDatabase(),\n                                IUsernamePassword)\n        self.assertEqual(checker.credentialInterfaces, [IUsernamePassword])\n        self.assertIsInstance(checker.checkers[IUsernamePassword],\n                              checkers.SSHPublicKeyDatabase)\n\n\n    def test_requestAvatarId(self):\n        \"\"\"\n        L{SSHProtocolChecker.requestAvatarId} should defer to one if its\n        registered checkers to authenticate a user.\n        \"\"\"\n        checker = checkers.SSHProtocolChecker()\n        passwordDatabase = InMemoryUsernamePasswordDatabaseDontUse()\n        passwordDatabase.addUser(b'test', b'test')\n        checker.registerChecker(passwordDatabase)\n        d = checker.requestAvatarId(UsernamePassword(b'test', b'test'))\n        def _callback(avatarId):\n            self.assertEqual(avatarId, b'test')\n        return d.addCallback(_callback)\n\n\n    def test_requestAvatarIdWithNotEnoughAuthentication(self):\n        \"\"\"\n        If the client indicates that it is never satisfied, by always returning\n        False from _areDone, then L{SSHProtocolChecker} should raise\n        L{NotEnoughAuthentication}.\n        \"\"\"\n        checker = checkers.SSHProtocolChecker()\n        def _areDone(avatarId):\n            return False\n        self.patch(checker, 'areDone', _areDone)\n\n        passwordDatabase = InMemoryUsernamePasswordDatabaseDontUse()\n        passwordDatabase.addUser(b'test', b'test')\n        checker.registerChecker(passwordDatabase)\n        d = checker.requestAvatarId(UsernamePassword(b'test', b'test'))\n        return self.assertFailure(d, NotEnoughAuthentication)\n\n\n    def test_requestAvatarIdInvalidCredential(self):\n        \"\"\"\n        If the passed credentials aren't handled by any registered checker,\n        L{SSHProtocolChecker} should raise L{UnhandledCredentials}.\n        \"\"\"\n        checker = checkers.SSHProtocolChecker()\n        d = checker.requestAvatarId(UsernamePassword(b'test', b'test'))\n        return self.assertFailure(d, UnhandledCredentials)\n\n\n    def test_areDone(self):\n        \"\"\"\n        The default L{SSHProcotolChecker.areDone} should simply return True.\n        \"\"\"\n        self.assertTrue(checkers.SSHProtocolChecker().areDone(None))\n\n\n\nclass UNIXPasswordDatabaseTests(TestCase):\n    \"\"\"\n    Tests for L{UNIXPasswordDatabase}.\n    \"\"\"\n    skip = cryptSkip or dependencySkip\n\n    def assertLoggedIn(self, d, username):\n        \"\"\"\n        Assert that the L{Deferred} passed in is called back with the value\n        'username'.  This represents a valid login for this TestCase.\n\n        NOTE: To work, this method's return value must be returned from the\n        test method, or otherwise hooked up to the test machinery.\n\n        @param d: a L{Deferred} from an L{IChecker.requestAvatarId} method.\n        @type d: L{Deferred}\n        @rtype: L{Deferred}\n        \"\"\"\n        result = []\n        d.addBoth(result.append)\n        self.assertEqual(len(result), 1, \"login incomplete\")\n        if isinstance(result[0], Failure):\n            result[0].raiseException()\n        self.assertEqual(result[0], username)\n\n\n    def test_defaultCheckers(self):\n        \"\"\"\n        L{UNIXPasswordDatabase} with no arguments has checks the C{pwd} database\n        and then the C{spwd} database.\n        \"\"\"\n        checker = checkers.UNIXPasswordDatabase()\n\n        def crypted(username, password):\n            salt = crypt.crypt(password, username)\n            crypted = crypt.crypt(password, '$1$' + salt)\n            return crypted\n\n        pwd = UserDatabase()\n        pwd.addUser('alice', crypted('alice', 'password'),\n                    1, 2, 'foo', '/foo', '/bin/sh')\n        # x and * are convention for \"look elsewhere for the password\"\n        pwd.addUser('bob', 'x', 1, 2, 'bar', '/bar', '/bin/sh')\n        spwd = ShadowDatabase()\n        spwd.addUser('alice', 'wrong', 1, 2, 3, 4, 5, 6, 7)\n        spwd.addUser('bob', crypted('bob', 'password'),\n                     8, 9, 10, 11, 12, 13, 14)\n\n        self.patch(checkers, 'pwd', pwd)\n        self.patch(checkers, 'spwd', spwd)\n\n        mockos = MockOS()\n        self.patch(util, 'os', mockos)\n\n        mockos.euid = 2345\n        mockos.egid = 1234\n\n        cred = UsernamePassword(b\"alice\", b\"password\")\n        self.assertLoggedIn(checker.requestAvatarId(cred), b'alice')\n        self.assertEqual(mockos.seteuidCalls, [])\n        self.assertEqual(mockos.setegidCalls, [])\n        cred.username = b\"bob\"\n        self.assertLoggedIn(checker.requestAvatarId(cred), b'bob')\n        self.assertEqual(mockos.seteuidCalls, [0, 2345])\n        self.assertEqual(mockos.setegidCalls, [0, 1234])\n\n\n    def assertUnauthorizedLogin(self, d):\n        \"\"\"\n        Asserts that the L{Deferred} passed in is erred back with an\n        L{UnauthorizedLogin} L{Failure}.  This reprsents an invalid login for\n        this TestCase.\n\n        NOTE: To work, this method's return value must be returned from the\n        test method, or otherwise hooked up to the test machinery.\n\n        @param d: a L{Deferred} from an L{IChecker.requestAvatarId} method.\n        @type d: L{Deferred}\n        @rtype: L{None}\n        \"\"\"\n        self.assertRaises(\n            checkers.UnauthorizedLogin, self.assertLoggedIn, d, 'bogus value')\n\n\n    def test_passInCheckers(self):\n        \"\"\"\n        L{UNIXPasswordDatabase} takes a list of functions to check for UNIX\n        user information.\n        \"\"\"\n        password = crypt.crypt('secret', 'secret')\n        userdb = UserDatabase()\n        userdb.addUser('anybody', password, 1, 2, 'foo', '/bar', '/bin/sh')\n        checker = checkers.UNIXPasswordDatabase([userdb.getpwnam])\n        self.assertLoggedIn(\n            checker.requestAvatarId(UsernamePassword(b'anybody', b'secret')),\n            b'anybody')\n\n\n    def test_verifyPassword(self):\n        \"\"\"\n        If the encrypted password provided by the getpwnam function is valid\n        (verified by the L{verifyCryptedPassword} function), we callback the\n        C{requestAvatarId} L{Deferred} with the username.\n        \"\"\"\n        def verifyCryptedPassword(crypted, pw):\n            return crypted == pw\n        def getpwnam(username):\n            return [username, username]\n        self.patch(checkers, 'verifyCryptedPassword', verifyCryptedPassword)\n        checker = checkers.UNIXPasswordDatabase([getpwnam])\n        credential = UsernamePassword(b'username', b'username')\n        self.assertLoggedIn(checker.requestAvatarId(credential), b'username')\n\n\n    def test_failOnKeyError(self):\n        \"\"\"\n        If the getpwnam function raises a KeyError, the login fails with an\n        L{UnauthorizedLogin} exception.\n        \"\"\"\n        def getpwnam(username):\n            raise KeyError(username)\n        checker = checkers.UNIXPasswordDatabase([getpwnam])\n        credential = UsernamePassword(b'username', b'username')\n        self.assertUnauthorizedLogin(checker.requestAvatarId(credential))\n\n\n    def test_failOnBadPassword(self):\n        \"\"\"\n        If the verifyCryptedPassword function doesn't verify the password, the\n        login fails with an L{UnauthorizedLogin} exception.\n        \"\"\"\n        def verifyCryptedPassword(crypted, pw):\n            return False\n        def getpwnam(username):\n            return [username, username]\n        self.patch(checkers, 'verifyCryptedPassword', verifyCryptedPassword)\n        checker = checkers.UNIXPasswordDatabase([getpwnam])\n        credential = UsernamePassword(b'username', b'username')\n        self.assertUnauthorizedLogin(checker.requestAvatarId(credential))\n\n\n    def test_loopThroughFunctions(self):\n        \"\"\"\n        UNIXPasswordDatabase.requestAvatarId loops through each getpwnam\n        function associated with it and returns a L{Deferred} which fires with\n        the result of the first one which returns a value other than None.\n        ones do not verify the password.\n        \"\"\"\n        def verifyCryptedPassword(crypted, pw):\n            return crypted == pw\n        def getpwnam1(username):\n            return [username, 'not the password']\n        def getpwnam2(username):\n            return [username, username]\n        self.patch(checkers, 'verifyCryptedPassword', verifyCryptedPassword)\n        checker = checkers.UNIXPasswordDatabase([getpwnam1, getpwnam2])\n        credential = UsernamePassword(b'username', b'username')\n        self.assertLoggedIn(checker.requestAvatarId(credential), b'username')\n\n\n    def test_failOnSpecial(self):\n        \"\"\"\n        If the password returned by any function is C{\"\"}, C{\"x\"}, or C{\"*\"} it\n        is not compared against the supplied password.  Instead it is skipped.\n        \"\"\"\n        pwd = UserDatabase()\n        pwd.addUser('alice', '', 1, 2, '', 'foo', 'bar')\n        pwd.addUser('bob', 'x', 1, 2, '', 'foo', 'bar')\n        pwd.addUser('carol', '*', 1, 2, '', 'foo', 'bar')\n        self.patch(checkers, 'pwd', pwd)\n\n        checker = checkers.UNIXPasswordDatabase([checkers._pwdGetByName])\n        cred = UsernamePassword(b'alice', b'')\n        self.assertUnauthorizedLogin(checker.requestAvatarId(cred))\n\n        cred = UsernamePassword(b'bob', b'x')\n        self.assertUnauthorizedLogin(checker.requestAvatarId(cred))\n\n        cred = UsernamePassword(b'carol', b'*')\n        self.assertUnauthorizedLogin(checker.requestAvatarId(cred))\n\n\n\nclass AuthorizedKeyFileReaderTests(TestCase):\n    \"\"\"\n    Tests for L{checkers.readAuthorizedKeyFile}\n    \"\"\"\n    skip = dependencySkip\n\n\n    def test_ignoresComments(self):\n        \"\"\"\n        L{checkers.readAuthorizedKeyFile} does not attempt to turn comments\n        into keys\n        \"\"\"\n        fileobj = BytesIO(b'# this comment is ignored\\n'\n                          b'this is not\\n'\n                          b'# this is again\\n'\n                          b'and this is not')\n        result = checkers.readAuthorizedKeyFile(fileobj, lambda x: x)\n        self.assertEqual([b'this is not', b'and this is not'], list(result))\n\n\n    def test_ignoresLeadingWhitespaceAndEmptyLines(self):\n        \"\"\"\n        L{checkers.readAuthorizedKeyFile} ignores leading whitespace in\n        lines, as well as empty lines\n        \"\"\"\n        fileobj = BytesIO(b\"\"\"\n                           # ignore\n                           not ignored\n                           \"\"\")\n        result = checkers.readAuthorizedKeyFile(fileobj, parseKey=lambda x: x)\n        self.assertEqual([b'not ignored'], list(result))\n\n\n    def test_ignoresUnparsableKeys(self):\n        \"\"\"\n        L{checkers.readAuthorizedKeyFile} does not raise an exception\n        when a key fails to parse (raises a\n        L{twisted.conch.ssh.keys.BadKeyError}), but rather just keeps going\n        \"\"\"\n        def failOnSome(line):\n            if line.startswith(b'f'):\n                raise keys.BadKeyError('failed to parse')\n            return line\n\n        fileobj = BytesIO(b'failed key\\ngood key')\n        result = checkers.readAuthorizedKeyFile(fileobj,\n                                                parseKey=failOnSome)\n        self.assertEqual([b'good key'], list(result))\n\n\n\nclass InMemorySSHKeyDBTests(TestCase):\n    \"\"\"\n    Tests for L{checkers.InMemorySSHKeyDB}\n    \"\"\"\n    skip = dependencySkip\n\n\n    def test_implementsInterface(self):\n        \"\"\"\n        L{checkers.InMemorySSHKeyDB} implements\n        L{checkers.IAuthorizedKeysDB}\n        \"\"\"\n        keydb = checkers.InMemorySSHKeyDB({b'alice': [b'key']})\n        verifyObject(checkers.IAuthorizedKeysDB, keydb)\n\n\n    def test_noKeysForUnauthorizedUser(self):\n        \"\"\"\n        If the user is not in the mapping provided to\n        L{checkers.InMemorySSHKeyDB}, an empty iterator is returned\n        by L{checkers.InMemorySSHKeyDB.getAuthorizedKeys}\n        \"\"\"\n        keydb = checkers.InMemorySSHKeyDB({b'alice': [b'keys']})\n        self.assertEqual([], list(keydb.getAuthorizedKeys(b'bob')))\n\n\n    def test_allKeysForAuthorizedUser(self):\n        \"\"\"\n        If the user is in the mapping provided to\n        L{checkers.InMemorySSHKeyDB}, an iterator with all the keys\n        is returned by L{checkers.InMemorySSHKeyDB.getAuthorizedKeys}\n        \"\"\"\n        keydb = checkers.InMemorySSHKeyDB({b'alice': [b'a', b'b']})\n        self.assertEqual([b'a', b'b'], list(keydb.getAuthorizedKeys(b'alice')))\n\n\n\nclass UNIXAuthorizedKeysFilesTests(TestCase):\n    \"\"\"\n    Tests for L{checkers.UNIXAuthorizedKeysFiles}.\n    \"\"\"\n    skip = dependencySkip\n\n\n    def setUp(self):\n        mockos = MockOS()\n        mockos.path = FilePath(self.mktemp())\n        mockos.path.makedirs()\n\n        self.userdb = UserDatabase()\n        self.userdb.addUser(b'alice', b'password', 1, 2, b'alice lastname',\n                            mockos.path.path, b'/bin/shell')\n\n        self.sshDir = mockos.path.child('.ssh')\n        self.sshDir.makedirs()\n        authorizedKeys = self.sshDir.child('authorized_keys')\n        authorizedKeys.setContent(b'key 1\\nkey 2')\n\n        self.expectedKeys = [b'key 1', b'key 2']\n\n\n    def test_implementsInterface(self):\n        \"\"\"\n        L{checkers.UNIXAuthorizedKeysFiles} implements\n        L{checkers.IAuthorizedKeysDB}.\n        \"\"\"\n        keydb = checkers.UNIXAuthorizedKeysFiles(self.userdb)\n        verifyObject(checkers.IAuthorizedKeysDB, keydb)\n\n\n    def test_noKeysForUnauthorizedUser(self):\n        \"\"\"\n        If the user is not in the user database provided to\n        L{checkers.UNIXAuthorizedKeysFiles}, an empty iterator is returned\n        by L{checkers.UNIXAuthorizedKeysFiles.getAuthorizedKeys}.\n        \"\"\"\n        keydb = checkers.UNIXAuthorizedKeysFiles(self.userdb,\n                                                 parseKey=lambda x: x)\n        self.assertEqual([], list(keydb.getAuthorizedKeys('bob')))\n\n\n    def test_allKeysInAllAuthorizedFilesForAuthorizedUser(self):\n        \"\"\"\n        If the user is in the user database provided to\n        L{checkers.UNIXAuthorizedKeysFiles}, an iterator with all the keys in\n        C{~/.ssh/authorized_keys} and C{~/.ssh/authorized_keys2} is returned\n        by L{checkers.UNIXAuthorizedKeysFiles.getAuthorizedKeys}.\n        \"\"\"\n        self.sshDir.child('authorized_keys2').setContent(b'key 3')\n        keydb = checkers.UNIXAuthorizedKeysFiles(self.userdb,\n                                                 parseKey=lambda x: x)\n        self.assertEqual(self.expectedKeys + [b'key 3'],\n                         list(keydb.getAuthorizedKeys(b'alice')))\n\n\n    def test_ignoresNonexistantFile(self):\n        \"\"\"\n        L{checkers.UNIXAuthorizedKeysFiles.getAuthorizedKeys} returns only\n        the keys in C{~/.ssh/authorized_keys} and C{~/.ssh/authorized_keys2}\n        if they exist.\n        \"\"\"\n        keydb = checkers.UNIXAuthorizedKeysFiles(self.userdb,\n                                                 parseKey=lambda x: x)\n        self.assertEqual(self.expectedKeys,\n                         list(keydb.getAuthorizedKeys(b'alice')))\n\n\n    def test_ignoresUnreadableFile(self):\n        \"\"\"\n        L{checkers.UNIXAuthorizedKeysFiles.getAuthorizedKeys} returns only\n        the keys in C{~/.ssh/authorized_keys} and C{~/.ssh/authorized_keys2}\n        if they are readable.\n        \"\"\"\n        self.sshDir.child('authorized_keys2').makedirs()\n        keydb = checkers.UNIXAuthorizedKeysFiles(self.userdb,\n                                                 parseKey=lambda x: x)\n        self.assertEqual(self.expectedKeys,\n                         list(keydb.getAuthorizedKeys(b'alice')))\n\n\n\n_KeyDB = namedtuple('KeyDB', ['getAuthorizedKeys'])\n\n\n\nclass _DummyException(Exception):\n    \"\"\"\n    Fake exception to be used for testing.\n    \"\"\"\n    pass\n\n\n\nclass SSHPublicKeyCheckerTests(TestCase):\n    \"\"\"\n    Tests for L{checkers.SSHPublicKeyChecker}.\n    \"\"\"\n    skip = dependencySkip\n\n\n    def setUp(self):\n        self.credentials = SSHPrivateKey(\n             b'alice', b'ssh-rsa', keydata.publicRSA_openssh, b'foo',\n             keys.Key.fromString(keydata.privateRSA_openssh).sign(b'foo'))\n        self.keydb = _KeyDB(lambda _: [\n            keys.Key.fromString(keydata.publicRSA_openssh)])\n        self.checker = checkers.SSHPublicKeyChecker(self.keydb)\n\n\n    def test_credentialsWithoutSignature(self):\n        \"\"\"\n        Calling L{checkers.SSHPublicKeyChecker.requestAvatarId} with\n        credentials that do not have a signature fails with L{ValidPublicKey}.\n        \"\"\"\n        self.credentials.signature = None\n        self.failureResultOf(self.checker.requestAvatarId(self.credentials),\n                             ValidPublicKey)\n\n\n    def test_credentialsWithBadKey(self):\n        \"\"\"\n        Calling L{checkers.SSHPublicKeyChecker.requestAvatarId} with\n        credentials that have a bad key fails with L{keys.BadKeyError}.\n        \"\"\"\n        self.credentials.blob = b''\n        self.failureResultOf(self.checker.requestAvatarId(self.credentials),\n                             keys.BadKeyError)\n\n\n    def test_credentialsNoMatchingKey(self):\n        \"\"\"\n        If L{checkers.IAuthorizedKeysDB.getAuthorizedKeys} returns no keys\n        that match the credentials,\n        L{checkers.SSHPublicKeyChecker.requestAvatarId} fails with\n        L{UnauthorizedLogin}.\n        \"\"\"\n        self.credentials.blob = keydata.publicDSA_openssh\n        self.failureResultOf(self.checker.requestAvatarId(self.credentials),\n                             UnauthorizedLogin)\n\n\n    def test_credentialsInvalidSignature(self):\n        \"\"\"\n        Calling L{checkers.SSHPublicKeyChecker.requestAvatarId} with\n        credentials that are incorrectly signed fails with\n        L{UnauthorizedLogin}.\n        \"\"\"\n        self.credentials.signature = (\n            keys.Key.fromString(keydata.privateDSA_openssh).sign(b'foo'))\n        self.failureResultOf(self.checker.requestAvatarId(self.credentials),\n                             UnauthorizedLogin)\n\n\n    def test_failureVerifyingKey(self):\n        \"\"\"\n        If L{keys.Key.verify} raises an exception,\n        L{checkers.SSHPublicKeyChecker.requestAvatarId} fails with\n        L{UnauthorizedLogin}.\n        \"\"\"\n        def fail(*args, **kwargs):\n            raise _DummyException()\n\n        self.patch(keys.Key, 'verify', fail)\n\n        self.failureResultOf(self.checker.requestAvatarId(self.credentials),\n                             UnauthorizedLogin)\n        self.flushLoggedErrors(_DummyException)\n\n\n    def test_usernameReturnedOnSuccess(self):\n        \"\"\"\n        L{checker.SSHPublicKeyChecker.requestAvatarId}, if successful,\n        callbacks with the username.\n        \"\"\"\n        d = self.checker.requestAvatarId(self.credentials)\n        self.assertEqual(b'alice', self.successResultOf(d))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_ckeygen.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.scripts.ckeygen}.\n\"\"\"\n\nimport getpass\nimport sys\nimport subprocess\n\nfrom io import BytesIO, StringIO\n\nfrom twisted.python.compat import unicode, _PY3\nfrom twisted.python.reflect import requireModule\n\nif requireModule('cryptography') and requireModule('pyasn1'):\n    from twisted.conch.ssh.keys import (Key, BadKeyError,\n        BadFingerPrintFormat, FingerprintFormats)\n    from twisted.conch.scripts.ckeygen import (\n        changePassPhrase, displayPublicKey, printFingerprint,\n        _saveKey, enumrepresentation)\nelse:\n    skip = \"cryptography and pyasn1 required for twisted.conch.scripts.ckeygen\"\n\nfrom twisted.python.filepath import FilePath\nfrom twisted.trial.unittest import TestCase\nfrom twisted.conch.test.keydata import (\n    publicRSA_openssh, privateRSA_openssh, privateRSA_openssh_encrypted, privateECDSA_openssh)\n\n\n\ndef makeGetpass(*passphrases):\n    \"\"\"\n    Return a callable to patch C{getpass.getpass}.  Yields a passphrase each\n    time called. Use case is to provide an old, then new passphrase(s) as if\n    requested interactively.\n\n    @param passphrases: The list of passphrases returned, one per each call.\n\n    @return: A callable to patch C{getpass.getpass}.\n    \"\"\"\n    passphrases = iter(passphrases)\n\n    def fakeGetpass(_):\n        return next(passphrases)\n\n    return fakeGetpass\n\n\n\nclass KeyGenTests(TestCase):\n    \"\"\"\n    Tests for various functions used to implement the I{ckeygen} script.\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Patch C{sys.stdout} so tests can make assertions about what's printed.\n        \"\"\"\n        if _PY3:\n            self.stdout = StringIO()\n        else:\n            self.stdout = BytesIO()\n        self.patch(sys, 'stdout', self.stdout)\n\n\n\n    def _testrun(self, keyType, keySize=None):\n        filename = self.mktemp()\n        if keySize is None:\n            subprocess.call(['ckeygen', '-t', keyType, '-f', filename, '--no-passphrase'])\n        else:\n            subprocess.call(['ckeygen', '-t', keyType, '-f', filename, '--no-passphrase',\n                '-b', keySize])\n        privKey = Key.fromFile(filename)\n        pubKey = Key.fromFile(filename + '.pub')\n        if keyType == 'ecdsa':\n            self.assertEqual(privKey.type(), 'EC')\n        else:\n            self.assertEqual(privKey.type(), keyType.upper())\n        self.assertTrue(pubKey.isPublic())\n\n\n    def test_keygeneration(self):\n        self._testrun('ecdsa', '384')\n        self._testrun('ecdsa')\n        self._testrun('dsa', '2048')\n        self._testrun('dsa')\n        self._testrun('rsa', '2048')\n        self._testrun('rsa')\n\n\n\n    def test_runBadKeytype(self):\n        filename = self.mktemp()\n        with self.assertRaises(subprocess.CalledProcessError):\n            subprocess.check_call(['ckeygen', '-t', 'foo', '-f', filename])\n\n\n\n    def test_enumrepresentation(self):\n        \"\"\"\n        L{enumrepresentation} takes a dictionary as input and returns a\n        dictionary with its attributes changed to enum representation.\n        \"\"\"\n        options = enumrepresentation({'format': 'md5-hex'})\n        self.assertIs(options['format'],\n            FingerprintFormats.MD5_HEX)\n\n\n    def test_enumrepresentationsha256(self):\n        \"\"\"\n        Test for format L{FingerprintFormats.SHA256-BASE64}.\n        \"\"\"\n        options = enumrepresentation({'format': 'sha256-base64'})\n        self.assertIs(options['format'],\n            FingerprintFormats.SHA256_BASE64)\n\n\n\n    def test_enumrepresentationBadFormat(self):\n        \"\"\"\n        Test for unsupported fingerprint format\n        \"\"\"\n        with self.assertRaises(BadFingerPrintFormat) as em:\n            enumrepresentation({'format': 'sha-base64'})\n        self.assertEqual('Unsupported fingerprint format: sha-base64',\n            em.exception.args[0])\n\n\n\n    def test_printFingerprint(self):\n        \"\"\"\n        L{printFingerprint} writes a line to standard out giving the number of\n        bits of the key, its fingerprint, and the basename of the file from it\n        was read.\n        \"\"\"\n        filename = self.mktemp()\n        FilePath(filename).setContent(publicRSA_openssh)\n        printFingerprint({'filename': filename,\n            'format': 'md5-hex'})\n        self.assertEqual(\n            self.stdout.getvalue(),\n            '2048 85:25:04:32:58:55:96:9f:57:ee:fb:a8:1a:ea:69:da temp\\n')\n\n\n    def test_printFingerprintsha256(self):\n        \"\"\"\n        L{printFigerprint} will print key fingerprint in\n        L{FingerprintFormats.SHA256-BASE64} format if explicitly specified.\n        \"\"\"\n        filename = self.mktemp()\n        FilePath(filename).setContent(publicRSA_openssh)\n        printFingerprint({'filename': filename,\n            'format': 'sha256-base64'})\n        self.assertEqual(\n            self.stdout.getvalue(),\n            '2048 FBTCOoknq0mHy+kpfnY9tDdcAJuWtCpuQMaV3EsvbUI= temp\\n')\n\n\n    def test_printFingerprintBadFingerPrintFormat(self):\n        \"\"\"\n        L{printFigerprint} raises C{keys.BadFingerprintFormat} when unsupported\n        formats are requested.\n        \"\"\"\n        filename = self.mktemp()\n        FilePath(filename).setContent(publicRSA_openssh)\n        with self.assertRaises(BadFingerPrintFormat) as em:\n            printFingerprint({'filename': filename, 'format':'sha-base64'})\n        self.assertEqual('Unsupported fingerprint format: sha-base64',\n            em.exception.args[0])\n\n\n\n    def test_saveKey(self):\n        \"\"\"\n        L{_saveKey} writes the private and public parts of a key to two\n        different files and writes a report of this to standard out.\n        \"\"\"\n        base = FilePath(self.mktemp())\n        base.makedirs()\n        filename = base.child('id_rsa').path\n        key = Key.fromString(privateRSA_openssh)\n        _saveKey(key, {'filename': filename, 'pass': 'passphrase',\n            'format': 'md5-hex'})\n        self.assertEqual(\n            self.stdout.getvalue(),\n            \"Your identification has been saved in %s\\n\"\n            \"Your public key has been saved in %s.pub\\n\"\n            \"The key fingerprint in <FingerprintFormats=MD5_HEX> is:\\n\"\n            \"85:25:04:32:58:55:96:9f:57:ee:fb:a8:1a:ea:69:da\\n\" % (\n                filename,\n                filename))\n        self.assertEqual(\n            key.fromString(\n                base.child('id_rsa').getContent(), None, 'passphrase'),\n            key)\n        self.assertEqual(\n            Key.fromString(base.child('id_rsa.pub').getContent()),\n            key.public())\n\n\n    def test_saveKeyECDSA(self):\n        \"\"\"\n        L{_saveKey} writes the private and public parts of a key to two\n        different files and writes a report of this to standard out.\n        Test with ECDSA key.\n        \"\"\"\n        base = FilePath(self.mktemp())\n        base.makedirs()\n        filename = base.child('id_ecdsa').path\n        key = Key.fromString(privateECDSA_openssh)\n        _saveKey(key, {'filename': filename, 'pass': 'passphrase',\n            'format': 'md5-hex'})\n        self.assertEqual(\n            self.stdout.getvalue(),\n            \"Your identification has been saved in %s\\n\"\n            \"Your public key has been saved in %s.pub\\n\"\n            \"The key fingerprint in <FingerprintFormats=MD5_HEX> is:\\n\"\n            \"1e:ab:83:a6:f2:04:22:99:7c:64:14:d2:ab:fa:f5:16\\n\" % (\n                filename,\n                filename))\n        self.assertEqual(\n            key.fromString(\n                base.child('id_ecdsa').getContent(), None, 'passphrase'),\n            key)\n        self.assertEqual(\n            Key.fromString(base.child('id_ecdsa.pub').getContent()),\n            key.public())\n\n\n    def test_saveKeysha256(self):\n        \"\"\"\n        L{_saveKey} will generate key fingerprint in\n        L{FingerprintFormats.SHA256-BASE64} format if explicitly specified.\n        \"\"\"\n        base = FilePath(self.mktemp())\n        base.makedirs()\n        filename = base.child('id_rsa').path\n        key = Key.fromString(privateRSA_openssh)\n        _saveKey(key, {'filename': filename, 'pass': 'passphrase',\n            'format': 'sha256-base64'})\n        self.assertEqual(\n            self.stdout.getvalue(),\n            \"Your identification has been saved in %s\\n\"\n            \"Your public key has been saved in %s.pub\\n\"\n            \"The key fingerprint in <FingerprintFormats=SHA256_BASE64> is:\\n\"\n            \"FBTCOoknq0mHy+kpfnY9tDdcAJuWtCpuQMaV3EsvbUI=\\n\" % (\n                filename,\n                filename))\n        self.assertEqual(\n            key.fromString(\n                base.child('id_rsa').getContent(), None, 'passphrase'),\n            key)\n        self.assertEqual(\n            Key.fromString(base.child('id_rsa.pub').getContent()),\n            key.public())\n\n\n    def test_saveKeyBadFingerPrintformat(self):\n        \"\"\"\n        L{_saveKey} raises C{keys.BadFingerprintFormat} when unsupported\n        formats are requested.\n        \"\"\"\n        base = FilePath(self.mktemp())\n        base.makedirs()\n        filename = base.child('id_rsa').path\n        key = Key.fromString(privateRSA_openssh)\n        with self.assertRaises(BadFingerPrintFormat) as em:\n            _saveKey(key, {'filename': filename, 'pass': 'passphrase',\n                'format': 'sha-base64'})\n        self.assertEqual('Unsupported fingerprint format: sha-base64',\n            em.exception.args[0])\n\n\n    def test_saveKeyEmptyPassphrase(self):\n        \"\"\"\n        L{_saveKey} will choose an empty string for the passphrase if\n        no-passphrase is C{True}.\n        \"\"\"\n        base = FilePath(self.mktemp())\n        base.makedirs()\n        filename = base.child('id_rsa').path\n        key = Key.fromString(privateRSA_openssh)\n        _saveKey(key, {'filename': filename, 'no-passphrase': True,\n            'format': 'md5-hex'})\n        self.assertEqual(\n            key.fromString(\n                base.child('id_rsa').getContent(), None, b''),\n            key)\n\n\n    def test_saveKeyECDSAEmptyPassphrase(self):\n        \"\"\"\n        L{_saveKey} will choose an empty string for the passphrase if\n        no-passphrase is C{True}.\n        \"\"\"\n        base = FilePath(self.mktemp())\n        base.makedirs()\n        filename = base.child('id_ecdsa').path\n        key = Key.fromString(privateECDSA_openssh)\n        _saveKey(key, {'filename': filename, 'no-passphrase': True,\n            'format': 'md5-hex'})\n        self.assertEqual(\n            key.fromString(\n                base.child('id_ecdsa').getContent(), None),\n            key)\n\n\n\n    def test_saveKeyNoFilename(self):\n        \"\"\"\n        When no path is specified, it will ask for the path used to store the\n        key.\n        \"\"\"\n        base = FilePath(self.mktemp())\n        base.makedirs()\n        keyPath = base.child('custom_key').path\n\n        import twisted.conch.scripts.ckeygen\n        self.patch(twisted.conch.scripts.ckeygen, 'raw_input', lambda _: keyPath)\n        key = Key.fromString(privateRSA_openssh)\n        _saveKey(key, {'filename': None, 'no-passphrase': True,\n            'format': 'md5-hex'})\n\n        persistedKeyContent = base.child('custom_key').getContent()\n        persistedKey = key.fromString(persistedKeyContent, None, b'')\n        self.assertEqual(key, persistedKey)\n\n\n    def test_displayPublicKey(self):\n        \"\"\"\n        L{displayPublicKey} prints out the public key associated with a given\n        private key.\n        \"\"\"\n        filename = self.mktemp()\n        pubKey = Key.fromString(publicRSA_openssh)\n        FilePath(filename).setContent(privateRSA_openssh)\n        displayPublicKey({'filename': filename})\n        displayed = self.stdout.getvalue().strip('\\n')\n        if isinstance(displayed, unicode):\n            displayed = displayed.encode(\"ascii\")\n        self.assertEqual(\n            displayed,\n            pubKey.toString('openssh'))\n\n\n    def test_displayPublicKeyEncrypted(self):\n        \"\"\"\n        L{displayPublicKey} prints out the public key associated with a given\n        private key using the given passphrase when it's encrypted.\n        \"\"\"\n        filename = self.mktemp()\n        pubKey = Key.fromString(publicRSA_openssh)\n        FilePath(filename).setContent(privateRSA_openssh_encrypted)\n        displayPublicKey({'filename': filename, 'pass': 'encrypted'})\n        displayed = self.stdout.getvalue().strip('\\n')\n        if isinstance(displayed, unicode):\n            displayed = displayed.encode(\"ascii\")\n        self.assertEqual(\n            displayed,\n            pubKey.toString('openssh'))\n\n\n    def test_displayPublicKeyEncryptedPassphrasePrompt(self):\n        \"\"\"\n        L{displayPublicKey} prints out the public key associated with a given\n        private key, asking for the passphrase when it's encrypted.\n        \"\"\"\n        filename = self.mktemp()\n        pubKey = Key.fromString(publicRSA_openssh)\n        FilePath(filename).setContent(privateRSA_openssh_encrypted)\n        self.patch(getpass, 'getpass', lambda x: 'encrypted')\n        displayPublicKey({'filename': filename})\n        displayed = self.stdout.getvalue().strip('\\n')\n        if isinstance(displayed, unicode):\n            displayed = displayed.encode(\"ascii\")\n        self.assertEqual(\n            displayed,\n            pubKey.toString('openssh'))\n\n\n    def test_displayPublicKeyWrongPassphrase(self):\n        \"\"\"\n        L{displayPublicKey} fails with a L{BadKeyError} when trying to decrypt\n        an encrypted key with the wrong password.\n        \"\"\"\n        filename = self.mktemp()\n        FilePath(filename).setContent(privateRSA_openssh_encrypted)\n        self.assertRaises(\n            BadKeyError, displayPublicKey,\n            {'filename': filename, 'pass': 'wrong'})\n\n\n    def test_changePassphrase(self):\n        \"\"\"\n        L{changePassPhrase} allows a user to change the passphrase of a\n        private key interactively.\n        \"\"\"\n        oldNewConfirm = makeGetpass('encrypted', 'newpass', 'newpass')\n        self.patch(getpass, 'getpass', oldNewConfirm)\n\n        filename = self.mktemp()\n        FilePath(filename).setContent(privateRSA_openssh_encrypted)\n\n        changePassPhrase({'filename': filename})\n        self.assertEqual(\n            self.stdout.getvalue().strip('\\n'),\n            'Your identification has been saved with the new passphrase.')\n        self.assertNotEqual(privateRSA_openssh_encrypted,\n                            FilePath(filename).getContent())\n\n\n    def test_changePassphraseWithOld(self):\n        \"\"\"\n        L{changePassPhrase} allows a user to change the passphrase of a\n        private key, providing the old passphrase and prompting for new one.\n        \"\"\"\n        newConfirm = makeGetpass('newpass', 'newpass')\n        self.patch(getpass, 'getpass', newConfirm)\n\n        filename = self.mktemp()\n        FilePath(filename).setContent(privateRSA_openssh_encrypted)\n\n        changePassPhrase({'filename': filename, 'pass': 'encrypted'})\n        self.assertEqual(\n            self.stdout.getvalue().strip('\\n'),\n            'Your identification has been saved with the new passphrase.')\n        self.assertNotEqual(privateRSA_openssh_encrypted,\n                            FilePath(filename).getContent())\n\n\n    def test_changePassphraseWithBoth(self):\n        \"\"\"\n        L{changePassPhrase} allows a user to change the passphrase of a private\n        key by providing both old and new passphrases without prompting.\n        \"\"\"\n        filename = self.mktemp()\n        FilePath(filename).setContent(privateRSA_openssh_encrypted)\n\n        changePassPhrase(\n            {'filename': filename, 'pass': 'encrypted',\n             'newpass': 'newencrypt'})\n        self.assertEqual(\n            self.stdout.getvalue().strip('\\n'),\n            'Your identification has been saved with the new passphrase.')\n        self.assertNotEqual(privateRSA_openssh_encrypted,\n                            FilePath(filename).getContent())\n\n\n    def test_changePassphraseWrongPassphrase(self):\n        \"\"\"\n        L{changePassPhrase} exits if passed an invalid old passphrase when\n        trying to change the passphrase of a private key.\n        \"\"\"\n        filename = self.mktemp()\n        FilePath(filename).setContent(privateRSA_openssh_encrypted)\n        error = self.assertRaises(\n            SystemExit, changePassPhrase,\n            {'filename': filename, 'pass': 'wrong'})\n        self.assertEqual('Could not change passphrase: old passphrase error',\n                         str(error))\n        self.assertEqual(privateRSA_openssh_encrypted,\n                         FilePath(filename).getContent())\n\n\n    def test_changePassphraseEmptyGetPass(self):\n        \"\"\"\n        L{changePassPhrase} exits if no passphrase is specified for the\n        C{getpass} call and the key is encrypted.\n        \"\"\"\n        self.patch(getpass, 'getpass', makeGetpass(''))\n        filename = self.mktemp()\n        FilePath(filename).setContent(privateRSA_openssh_encrypted)\n        error = self.assertRaises(\n            SystemExit, changePassPhrase, {'filename': filename})\n        self.assertEqual(\n            'Could not change passphrase: Passphrase must be provided '\n            'for an encrypted key',\n            str(error))\n        self.assertEqual(privateRSA_openssh_encrypted,\n                         FilePath(filename).getContent())\n\n\n    def test_changePassphraseBadKey(self):\n        \"\"\"\n        L{changePassPhrase} exits if the file specified points to an invalid\n        key.\n        \"\"\"\n        filename = self.mktemp()\n        FilePath(filename).setContent(b'foobar')\n        error = self.assertRaises(\n            SystemExit, changePassPhrase, {'filename': filename})\n\n        if _PY3:\n            expected = \"Could not change passphrase: cannot guess the type of b'foobar'\"\n        else:\n            expected = \"Could not change passphrase: cannot guess the type of 'foobar'\"\n        self.assertEqual(expected, str(error))\n        self.assertEqual(b'foobar', FilePath(filename).getContent())\n\n\n    def test_changePassphraseCreateError(self):\n        \"\"\"\n        L{changePassPhrase} doesn't modify the key file if an unexpected error\n        happens when trying to create the key with the new passphrase.\n        \"\"\"\n        filename = self.mktemp()\n        FilePath(filename).setContent(privateRSA_openssh)\n\n        def toString(*args, **kwargs):\n            raise RuntimeError('oops')\n\n        self.patch(Key, 'toString', toString)\n\n        error = self.assertRaises(\n            SystemExit, changePassPhrase,\n            {'filename': filename,\n             'newpass': 'newencrypt'})\n\n        self.assertEqual(\n            'Could not change passphrase: oops', str(error))\n\n        self.assertEqual(privateRSA_openssh, FilePath(filename).getContent())\n\n\n    def test_changePassphraseEmptyStringError(self):\n        \"\"\"\n        L{changePassPhrase} doesn't modify the key file if C{toString} returns\n        an empty string.\n        \"\"\"\n        filename = self.mktemp()\n        FilePath(filename).setContent(privateRSA_openssh)\n\n        def toString(*args, **kwargs):\n            return ''\n\n        self.patch(Key, 'toString', toString)\n\n        error = self.assertRaises(\n            SystemExit, changePassPhrase,\n            {'filename': filename, 'newpass': 'newencrypt'})\n\n        if _PY3:\n            expected = (\n                \"Could not change passphrase: cannot guess the type of b''\")\n        else:\n            expected = (\n                \"Could not change passphrase: cannot guess the type of ''\")\n        self.assertEqual(expected, str(error))\n\n        self.assertEqual(privateRSA_openssh, FilePath(filename).getContent())\n\n\n    def test_changePassphrasePublicKey(self):\n        \"\"\"\n        L{changePassPhrase} exits when trying to change the passphrase on a\n        public key, and doesn't change the file.\n        \"\"\"\n        filename = self.mktemp()\n        FilePath(filename).setContent(publicRSA_openssh)\n        error = self.assertRaises(\n            SystemExit, changePassPhrase,\n            {'filename': filename, 'newpass': 'pass'})\n        self.assertEqual(\n            'Could not change passphrase: key not encrypted', str(error))\n        self.assertEqual(publicRSA_openssh, FilePath(filename).getContent())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_conch.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_conch -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nimport os, sys, socket\nimport subprocess\nfrom itertools import count\n\nfrom zope.interface import implementer\nfrom twisted.python.reflect import requireModule\n\ncryptography = requireModule(\"cryptography\")\n\nfrom twisted.conch.error import ConchError\nif cryptography:\n    from twisted.conch.avatar import ConchUser\n    from twisted.conch.ssh.session import ISession, SSHSession, wrapProtocol\nelse:\n    from twisted.conch.interfaces import ISession\n    class ConchUser: pass\n\nfrom twisted.cred import portal\nfrom twisted.internet import reactor, defer, protocol\nfrom twisted.internet.error import ProcessExitedAlready\nfrom twisted.internet.task import LoopingCall\nfrom twisted.internet.utils import getProcessValue\nfrom twisted.python import filepath, log, runtime\nfrom twisted.python.compat import unicode\nfrom twisted.trial import unittest\n\ntry:\n    from twisted.conch.scripts.conch import SSHSession as StdioInteractingSession\nexcept ImportError as e:\n    StdioInteractingSession = None\n    _reason = str(e)\n    del e\n\nfrom twisted.conch.test.test_ssh import ConchTestRealm\nfrom twisted.python.procutils import which\n\nfrom twisted.conch.test.keydata import publicRSA_openssh, privateRSA_openssh\nfrom twisted.conch.test.keydata import publicDSA_openssh, privateDSA_openssh\n\ntry:\n    from twisted.conch.test.test_ssh import ConchTestServerFactory, \\\n        conchTestPublicKeyChecker\nexcept ImportError:\n    pass\n\ntry:\n    import cryptography\nexcept ImportError:\n    cryptography = None\ntry:\n    import pyasn1\nexcept ImportError:\n    pyasn1 = None\n\n\ndef _has_ipv6():\n    \"\"\" Returns True if the system can bind an IPv6 address.\"\"\"\n    sock = None\n    has_ipv6 = False\n\n    try:\n        sock = socket.socket(socket.AF_INET6)\n        sock.bind(('::1', 0))\n        has_ipv6 = True\n    except socket.error:\n        pass\n\n    if sock:\n        sock.close()\n    return has_ipv6\n\n\nHAS_IPV6 = _has_ipv6()\n\n\nclass FakeStdio(object):\n    \"\"\"\n    A fake for testing L{twisted.conch.scripts.conch.SSHSession.eofReceived} and\n    L{twisted.conch.scripts.cftp.SSHSession.eofReceived}.\n\n    @ivar writeConnLost: A flag which records whether L{loserWriteConnection}\n        has been called.\n    \"\"\"\n    writeConnLost = False\n\n    def loseWriteConnection(self):\n        \"\"\"\n        Record the call to loseWriteConnection.\n        \"\"\"\n        self.writeConnLost = True\n\n\n\nclass StdioInteractingSessionTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{twisted.conch.scripts.conch.SSHSession}.\n    \"\"\"\n    if StdioInteractingSession is None:\n        skip = _reason\n\n\n    def test_eofReceived(self):\n        \"\"\"\n        L{twisted.conch.scripts.conch.SSHSession.eofReceived} loses the\n        write half of its stdio connection.\n        \"\"\"\n        stdio = FakeStdio()\n        channel = StdioInteractingSession()\n        channel.stdio = stdio\n        channel.eofReceived()\n        self.assertTrue(stdio.writeConnLost)\n\n\n\nclass Echo(protocol.Protocol):\n    def connectionMade(self):\n        log.msg('ECHO CONNECTION MADE')\n\n\n    def connectionLost(self, reason):\n        log.msg('ECHO CONNECTION DONE')\n\n\n    def dataReceived(self, data):\n        self.transport.write(data)\n        if b'\\n' in data:\n            self.transport.loseConnection()\n\n\n\nclass EchoFactory(protocol.Factory):\n    protocol = Echo\n\n\n\nclass ConchTestOpenSSHProcess(protocol.ProcessProtocol):\n    \"\"\"\n    Test protocol for launching an OpenSSH client process.\n\n    @ivar deferred: Set by whatever uses this object. Accessed using\n    L{_getDeferred}, which destroys the value so the Deferred is not\n    fired twice. Fires when the process is terminated.\n    \"\"\"\n\n    deferred = None\n    buf = b''\n\n    def _getDeferred(self):\n        d, self.deferred = self.deferred, None\n        return d\n\n\n    def outReceived(self, data):\n        self.buf += data\n\n\n    def processEnded(self, reason):\n        \"\"\"\n        Called when the process has ended.\n\n        @param reason: a Failure giving the reason for the process' end.\n        \"\"\"\n        if reason.value.exitCode != 0:\n            self._getDeferred().errback(\n                ConchError(\"exit code was not 0: {}\".format(\n                                 reason.value.exitCode)))\n        else:\n            buf = self.buf.replace(b'\\r\\n', b'\\n')\n            self._getDeferred().callback(buf)\n\n\n\nclass ConchTestForwardingProcess(protocol.ProcessProtocol):\n    \"\"\"\n    Manages a third-party process which launches a server.\n\n    Uses L{ConchTestForwardingPort} to connect to the third-party server.\n    Once L{ConchTestForwardingPort} has disconnected, kill the process and fire\n    a Deferred with the data received by the L{ConchTestForwardingPort}.\n\n    @ivar deferred: Set by whatever uses this object. Accessed using\n    L{_getDeferred}, which destroys the value so the Deferred is not\n    fired twice. Fires when the process is terminated.\n    \"\"\"\n\n    deferred = None\n\n    def __init__(self, port, data):\n        \"\"\"\n        @type port: L{int}\n        @param port: The port on which the third-party server is listening.\n        (it is assumed that the server is running on localhost).\n\n        @type data: L{str}\n        @param data: This is sent to the third-party server. Must end with '\\n'\n        in order to trigger a disconnect.\n        \"\"\"\n        self.port = port\n        self.buffer = None\n        self.data = data\n\n\n    def _getDeferred(self):\n        d, self.deferred = self.deferred, None\n        return d\n\n\n    def connectionMade(self):\n        self._connect()\n\n\n    def _connect(self):\n        \"\"\"\n        Connect to the server, which is often a third-party process.\n        Tries to reconnect if it fails because we have no way of determining\n        exactly when the port becomes available for listening -- we can only\n        know when the process starts.\n        \"\"\"\n        cc = protocol.ClientCreator(reactor, ConchTestForwardingPort, self,\n                                    self.data)\n        d = cc.connectTCP('127.0.0.1', self.port)\n        d.addErrback(self._ebConnect)\n        return d\n\n\n    def _ebConnect(self, f):\n        reactor.callLater(.1, self._connect)\n\n\n    def forwardingPortDisconnected(self, buffer):\n        \"\"\"\n        The network connection has died; save the buffer of output\n        from the network and attempt to quit the process gracefully,\n        and then (after the reactor has spun) send it a KILL signal.\n        \"\"\"\n        self.buffer = buffer\n        self.transport.write(b'\\x03')\n        self.transport.loseConnection()\n        reactor.callLater(0, self._reallyDie)\n\n\n    def _reallyDie(self):\n        try:\n            self.transport.signalProcess('KILL')\n        except ProcessExitedAlready:\n            pass\n\n\n    def processEnded(self, reason):\n        \"\"\"\n        Fire the Deferred at self.deferred with the data collected\n        from the L{ConchTestForwardingPort} connection, if any.\n        \"\"\"\n        self._getDeferred().callback(self.buffer)\n\n\n\nclass ConchTestForwardingPort(protocol.Protocol):\n    \"\"\"\n    Connects to server launched by a third-party process (managed by\n    L{ConchTestForwardingProcess}) sends data, then reports whatever it\n    received back to the L{ConchTestForwardingProcess} once the connection\n    is ended.\n    \"\"\"\n\n    def __init__(self, protocol, data):\n        \"\"\"\n        @type protocol: L{ConchTestForwardingProcess}\n        @param protocol: The L{ProcessProtocol} which made this connection.\n\n        @type data: str\n        @param data: The data to be sent to the third-party server.\n        \"\"\"\n        self.protocol = protocol\n        self.data = data\n\n\n    def connectionMade(self):\n        self.buffer = b''\n        self.transport.write(self.data)\n\n\n    def dataReceived(self, data):\n        self.buffer += data\n\n\n    def connectionLost(self, reason):\n        self.protocol.forwardingPortDisconnected(self.buffer)\n\n\n\ndef _makeArgs(args, mod=\"conch\"):\n    start = [sys.executable, '-c'\n\"\"\"\n### Twisted Preamble\nimport sys, os\npath = os.path.abspath(sys.argv[0])\nwhile os.path.dirname(path) != path:\n    if os.path.basename(path).startswith('Twisted'):\n        sys.path.insert(0, path)\n        break\n    path = os.path.dirname(path)\n\nfrom twisted.conch.scripts.%s import run\nrun()\"\"\" % mod]\n    madeArgs = []\n    for arg in start + list(args):\n        if isinstance(arg, unicode):\n            arg = arg.encode(\"utf-8\")\n        madeArgs.append(arg)\n    return madeArgs\n\n\n\nclass ConchServerSetupMixin:\n    if not cryptography:\n        skip = \"can't run without cryptography\"\n\n    if not pyasn1:\n        skip = \"Cannot run without PyASN1\"\n\n    realmFactory = staticmethod(lambda: ConchTestRealm(b'testuser'))\n\n    def _createFiles(self):\n        for f in ['rsa_test','rsa_test.pub','dsa_test','dsa_test.pub',\n                  'kh_test']:\n            if os.path.exists(f):\n                os.remove(f)\n        with open('rsa_test','wb') as f:\n            f.write(privateRSA_openssh)\n        with open('rsa_test.pub','wb') as f:\n            f.write(publicRSA_openssh)\n        with open('dsa_test.pub','wb') as f:\n            f.write(publicDSA_openssh)\n        with open('dsa_test','wb') as f:\n            f.write(privateDSA_openssh)\n        os.chmod('dsa_test', 33152)\n        os.chmod('rsa_test', 33152)\n        with open('kh_test','wb') as f:\n            f.write(b'127.0.0.1 '+publicRSA_openssh)\n\n\n    def _getFreePort(self):\n        s = socket.socket()\n        s.bind(('', 0))\n        port = s.getsockname()[1]\n        s.close()\n        return port\n\n\n    def _makeConchFactory(self):\n        \"\"\"\n        Make a L{ConchTestServerFactory}, which allows us to start a\n        L{ConchTestServer} -- i.e. an actually listening conch.\n        \"\"\"\n        realm = self.realmFactory()\n        p = portal.Portal(realm)\n        p.registerChecker(conchTestPublicKeyChecker())\n        factory = ConchTestServerFactory()\n        factory.portal = p\n        return factory\n\n\n    def setUp(self):\n        self._createFiles()\n        self.conchFactory = self._makeConchFactory()\n        self.conchFactory.expectedLoseConnection = 1\n        self.conchServer = reactor.listenTCP(0, self.conchFactory,\n                                             interface=\"127.0.0.1\")\n        self.echoServer = reactor.listenTCP(0, EchoFactory())\n        self.echoPort = self.echoServer.getHost().port\n        if HAS_IPV6:\n            self.echoServerV6 = reactor.listenTCP(0, EchoFactory(), interface=\"::1\")\n            self.echoPortV6 = self.echoServerV6.getHost().port\n\n\n    def tearDown(self):\n        try:\n            self.conchFactory.proto.done = 1\n        except AttributeError:\n            pass\n        else:\n            self.conchFactory.proto.transport.loseConnection()\n        deferreds = [\n            defer.maybeDeferred(self.conchServer.stopListening),\n            defer.maybeDeferred(self.echoServer.stopListening),\n        ]\n        if HAS_IPV6:\n            deferreds.append(defer.maybeDeferred(self.echoServerV6.stopListening))\n        return defer.gatherResults(deferreds)\n\n\n\nclass ForwardingMixin(ConchServerSetupMixin):\n    \"\"\"\n    Template class for tests of the Conch server's ability to forward arbitrary\n    protocols over SSH.\n\n    These tests are integration tests, not unit tests. They launch a Conch\n    server, a custom TCP server (just an L{EchoProtocol}) and then call\n    L{execute}.\n\n    L{execute} is implemented by subclasses of L{ForwardingMixin}. It should\n    cause an SSH client to connect to the Conch server, asking it to forward\n    data to the custom TCP server.\n    \"\"\"\n\n    def test_exec(self):\n        \"\"\"\n        Test that we can use whatever client to send the command \"echo goodbye\"\n        to the Conch server. Make sure we receive \"goodbye\" back from the\n        server.\n        \"\"\"\n        d = self.execute('echo goodbye', ConchTestOpenSSHProcess())\n        return d.addCallback(self.assertEqual, b'goodbye\\n')\n\n\n    def test_localToRemoteForwarding(self):\n        \"\"\"\n        Test that we can use whatever client to forward a local port to a\n        specified port on the server.\n        \"\"\"\n        localPort = self._getFreePort()\n        process = ConchTestForwardingProcess(localPort, b'test\\n')\n        d = self.execute('', process,\n                         sshArgs='-N -L%i:127.0.0.1:%i'\n                         % (localPort, self.echoPort))\n        d.addCallback(self.assertEqual, b'test\\n')\n        return d\n\n\n    def test_remoteToLocalForwarding(self):\n        \"\"\"\n        Test that we can use whatever client to forward a port from the server\n        to a port locally.\n        \"\"\"\n        localPort = self._getFreePort()\n        process = ConchTestForwardingProcess(localPort, b'test\\n')\n        d = self.execute('', process,\n                         sshArgs='-N -R %i:127.0.0.1:%i'\n                         % (localPort, self.echoPort))\n        d.addCallback(self.assertEqual, b'test\\n')\n        return d\n\n\n\n# Conventionally there is a separate adapter object which provides ISession for\n# the user, but making the user provide ISession directly works too. This isn't\n# a full implementation of ISession though, just enough to make these tests\n# pass.\n@implementer(ISession)\nclass RekeyAvatar(ConchUser):\n    \"\"\"\n    This avatar implements a shell which sends 60 numbered lines to whatever\n    connects to it, then closes the session with a 0 exit status.\n\n    60 lines is selected as being enough to send more than 2kB of traffic, the\n    amount the client is configured to initiate a rekey after.\n    \"\"\"\n    def __init__(self):\n        ConchUser.__init__(self)\n        self.channelLookup[b'session'] = SSHSession\n\n\n    def openShell(self, transport):\n        \"\"\"\n        Write 60 lines of data to the transport, then exit.\n        \"\"\"\n        proto = protocol.Protocol()\n        proto.makeConnection(transport)\n        transport.makeConnection(wrapProtocol(proto))\n\n        # Send enough bytes to the connection so that a rekey is triggered in\n        # the client.\n        def write(counter):\n            i = next(counter)\n            if i == 60:\n                call.stop()\n                transport.session.conn.sendRequest(\n                    transport.session, b'exit-status', b'\\x00\\x00\\x00\\x00')\n                transport.loseConnection()\n            else:\n                line = \"line #%02d\\n\" % (i,)\n                line = line.encode(\"utf-8\")\n                transport.write(line)\n\n        # The timing for this loop is an educated guess (and/or the result of\n        # experimentation) to exercise the case where a packet is generated\n        # mid-rekey.  Since the other side of the connection is (so far) the\n        # OpenSSH command line client, there's no easy way to determine when the\n        # rekey has been initiated.  If there were, then generating a packet\n        # immediately at that time would be a better way to test the\n        # functionality being tested here.\n        call = LoopingCall(write, count())\n        call.start(0.01)\n\n\n    def closed(self):\n        \"\"\"\n        Ignore the close of the session.\n        \"\"\"\n\n\n\nclass RekeyRealm:\n    \"\"\"\n    This realm gives out new L{RekeyAvatar} instances for any avatar request.\n    \"\"\"\n    def requestAvatar(self, avatarID, mind, *interfaces):\n        return interfaces[0], RekeyAvatar(), lambda: None\n\n\n\nclass RekeyTestsMixin(ConchServerSetupMixin):\n    \"\"\"\n    TestCase mixin which defines tests exercising L{SSHTransportBase}'s handling\n    of rekeying messages.\n    \"\"\"\n    realmFactory = RekeyRealm\n\n    def test_clientRekey(self):\n        \"\"\"\n        After a client-initiated rekey is completed, application data continues\n        to be passed over the SSH connection.\n        \"\"\"\n        process = ConchTestOpenSSHProcess()\n        d = self.execute(\"\", process, '-o RekeyLimit=2K')\n        def finished(result):\n            expectedResult = '\\n'.join(['line #%02d' % (i,) for i in range(60)]) + '\\n'\n            expectedResult = expectedResult.encode(\"utf-8\")\n            self.assertEqual(result, expectedResult)\n        d.addCallback(finished)\n        return d\n\n\n\nclass OpenSSHClientMixin:\n    if not which('ssh'):\n        skip = \"no ssh command-line client available\"\n\n\n    def execute(self, remoteCommand, process, sshArgs=''):\n        \"\"\"\n        Connects to the SSH server started in L{ConchServerSetupMixin.setUp} by\n        running the 'ssh' command line tool.\n\n        @type remoteCommand: str\n        @param remoteCommand: The command (with arguments) to run on the\n        remote end.\n\n        @type process: L{ConchTestOpenSSHProcess}\n\n        @type sshArgs: str\n        @param sshArgs: Arguments to pass to the 'ssh' process.\n\n        @return: L{defer.Deferred}\n        \"\"\"\n        # PubkeyAcceptedKeyTypes does not exist prior to OpenSSH 7.0 so we\n        # first need to check if we can set it. If we can, -V will just print\n        # the version without doing anything else; if we can't, we will get a\n        # configuration error.\n        d = getProcessValue(\n            which('ssh')[0], ('-o', 'PubkeyAcceptedKeyTypes=ssh-dss', '-V'))\n        def hasPAKT(status):\n            if status == 0:\n                opts = '-oPubkeyAcceptedKeyTypes=ssh-dss '\n            else:\n                opts = ''\n\n            process.deferred = defer.Deferred()\n            # Pass -F /dev/null to avoid the user's configuration file from\n            # being loaded, as it may contain settings that cause our tests to\n            # fail or hang.\n            cmdline = ('ssh -2 -l testuser -p %i '\n                       '-F /dev/null '\n                       '-oUserKnownHostsFile=kh_test '\n                       '-oPasswordAuthentication=no '\n                       # Always use the RSA key, since that's the one in kh_test.\n                       '-oHostKeyAlgorithms=ssh-rsa '\n                       '-a '\n                       '-i dsa_test ') + opts + sshArgs + \\\n                       ' 127.0.0.1 ' + remoteCommand\n            port = self.conchServer.getHost().port\n            cmds = (cmdline % port).split()\n            encodedCmds = []\n            for cmd in cmds:\n                if isinstance(cmd, unicode):\n                    cmd = cmd.encode(\"utf-8\")\n                encodedCmds.append(cmd)\n            reactor.spawnProcess(process, which('ssh')[0], encodedCmds)\n            return process.deferred\n        return d.addCallback(hasPAKT)\n\n\n\nclass OpenSSHKeyExchangeTests(ConchServerSetupMixin, OpenSSHClientMixin,\n                              unittest.TestCase):\n    \"\"\"\n    Tests L{SSHTransportBase}'s key exchange algorithm compatibility with\n    OpenSSH.\n    \"\"\"\n\n    def assertExecuteWithKexAlgorithm(self, keyExchangeAlgo):\n        \"\"\"\n        Call execute() method of L{OpenSSHClientMixin} with an ssh option that\n        forces the exclusive use of the key exchange algorithm specified by\n        keyExchangeAlgo\n\n        @type keyExchangeAlgo: L{str}\n        @param keyExchangeAlgo: The key exchange algorithm to use\n\n        @return: L{defer.Deferred}\n        \"\"\"\n        kexAlgorithms = []\n        try:\n            output = subprocess.check_output([which('ssh')[0], '-Q', 'kex'],\n                                             stderr=subprocess.STDOUT)\n            if not isinstance(output, str):\n                output = output.decode(\"utf-8\")\n            kexAlgorithms = output.split()\n        except:\n            pass\n\n        if keyExchangeAlgo not in kexAlgorithms:\n            raise unittest.SkipTest(\n                \"{} not supported by ssh client\".format(\n                    keyExchangeAlgo))\n\n        d = self.execute('echo hello', ConchTestOpenSSHProcess(),\n                         '-oKexAlgorithms=' + keyExchangeAlgo)\n        return d.addCallback(self.assertEqual, b'hello\\n')\n\n\n    def test_ECDHSHA256(self):\n        \"\"\"\n        The ecdh-sha2-nistp256 key exchange algorithm is compatible with\n        OpenSSH\n        \"\"\"\n        return self.assertExecuteWithKexAlgorithm(\n            'ecdh-sha2-nistp256')\n\n\n    def test_ECDHSHA384(self):\n        \"\"\"\n        The ecdh-sha2-nistp384 key exchange algorithm is compatible with\n        OpenSSH\n        \"\"\"\n        return self.assertExecuteWithKexAlgorithm(\n            'ecdh-sha2-nistp384')\n\n\n    def test_ECDHSHA521(self):\n        \"\"\"\n        The ecdh-sha2-nistp521 key exchange algorithm is compatible with\n        OpenSSH\n        \"\"\"\n        return self.assertExecuteWithKexAlgorithm(\n            'ecdh-sha2-nistp521')\n\n\n    def test_DH_GROUP14(self):\n        \"\"\"\n        The diffie-hellman-group14-sha1 key exchange algorithm is compatible\n        with OpenSSH.\n        \"\"\"\n        return self.assertExecuteWithKexAlgorithm(\n            'diffie-hellman-group14-sha1')\n\n\n    def test_DH_GROUP_EXCHANGE_SHA1(self):\n        \"\"\"\n        The diffie-hellman-group-exchange-sha1 key exchange algorithm is\n        compatible with OpenSSH.\n        \"\"\"\n        return self.assertExecuteWithKexAlgorithm(\n            'diffie-hellman-group-exchange-sha1')\n\n\n    def test_DH_GROUP_EXCHANGE_SHA256(self):\n        \"\"\"\n        The diffie-hellman-group-exchange-sha256 key exchange algorithm is\n        compatible with OpenSSH.\n        \"\"\"\n        return self.assertExecuteWithKexAlgorithm(\n            'diffie-hellman-group-exchange-sha256')\n\n\n    def test_unsupported_algorithm(self):\n        \"\"\"\n        The list of key exchange algorithms supported\n        by OpenSSH client is obtained with C{ssh -Q kex}.\n        \"\"\"\n        self.assertRaises(unittest.SkipTest,\n                          self.assertExecuteWithKexAlgorithm,\n                          'unsupported-algorithm')\n\n\n\nclass OpenSSHClientForwardingTests(ForwardingMixin, OpenSSHClientMixin,\n                                      unittest.TestCase):\n    \"\"\"\n    Connection forwarding tests run against the OpenSSL command line client.\n    \"\"\"\n    def test_localToRemoteForwardingV6(self):\n        \"\"\"\n        Forwarding of arbitrary IPv6 TCP connections via SSH.\n        \"\"\"\n        localPort = self._getFreePort()\n        process = ConchTestForwardingProcess(localPort, b'test\\n')\n        d = self.execute('', process,\n                         sshArgs='-N -L%i:[::1]:%i'\n                         % (localPort, self.echoPortV6))\n        d.addCallback(self.assertEqual, b'test\\n')\n        return d\n    if not HAS_IPV6:\n        test_localToRemoteForwardingV6.skip = \"Requires IPv6 support\"\n\n\n\nclass OpenSSHClientRekeyTests(RekeyTestsMixin, OpenSSHClientMixin,\n                                 unittest.TestCase):\n    \"\"\"\n    Rekeying tests run against the OpenSSL command line client.\n    \"\"\"\n\n\n\nclass CmdLineClientTests(ForwardingMixin, unittest.TestCase):\n    \"\"\"\n    Connection forwarding tests run against the Conch command line client.\n    \"\"\"\n    if runtime.platformType == 'win32':\n        skip = \"can't run cmdline client on win32\"\n\n\n    def execute(self, remoteCommand, process, sshArgs='', conchArgs=None):\n        \"\"\"\n        As for L{OpenSSHClientTestCase.execute}, except it runs the 'conch'\n        command line tool, not 'ssh'.\n        \"\"\"\n        if conchArgs is None:\n            conchArgs = []\n\n        process.deferred = defer.Deferred()\n        port = self.conchServer.getHost().port\n        cmd = ('-p {} -l testuser '\n               '--known-hosts kh_test '\n               '--user-authentications publickey '\n               '-a '\n               '-i dsa_test '\n               '-v '.format(port) + sshArgs +\n               ' 127.0.0.1 ' + remoteCommand)\n        cmds = _makeArgs(conchArgs + cmd.split())\n        env = os.environ.copy()\n        env['PYTHONPATH'] = os.pathsep.join(sys.path)\n        encodedCmds = []\n        encodedEnv = {}\n        for cmd in cmds:\n            if isinstance(cmd, unicode):\n                cmd = cmd.encode(\"utf-8\")\n            encodedCmds.append(cmd)\n        for var in env:\n            val = env[var]\n            if isinstance(var, unicode):\n                var = var.encode(\"utf-8\")\n            if isinstance(val, unicode):\n                val = val.encode(\"utf-8\")\n            encodedEnv[var] = val\n        reactor.spawnProcess(process, sys.executable, encodedCmds, env=encodedEnv)\n        return process.deferred\n\n\n    def test_runWithLogFile(self):\n        \"\"\"\n        It can store logs to a local file.\n        \"\"\"\n        def cb_check_log(result):\n            logContent = logPath.getContent()\n            self.assertIn(b'Log opened.', logContent)\n\n        logPath = filepath.FilePath(self.mktemp())\n\n        d = self.execute(\n            remoteCommand='echo goodbye',\n            process=ConchTestOpenSSHProcess(),\n            conchArgs=['--log', '--logfile', logPath.path,\n                       '--host-key-algorithms', 'ssh-rsa']\n            )\n\n        d.addCallback(self.assertEqual, b'goodbye\\n')\n        d.addCallback(cb_check_log)\n        return d\n\n\n    def test_runWithNoHostAlgorithmsSpecified(self):\n        \"\"\"\n        Do not use --host-key-algorithms flag on command line.\n        \"\"\"\n        d = self.execute(\n            remoteCommand='echo goodbye',\n            process=ConchTestOpenSSHProcess()\n            )\n\n        d.addCallback(self.assertEqual, b'goodbye\\n')\n        return d\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_connection.py",
    "content": "# Copyright (c) 2007-2010 Twisted Matrix Laboratories.\n# See LICENSE for details\n\n\"\"\"\nThis module tests twisted.conch.ssh.connection.\n\"\"\"\nfrom __future__ import division, absolute_import\n\nimport struct\n\nfrom twisted.python.reflect import requireModule\n\ncryptography = requireModule(\"cryptography\")\n\nfrom twisted.conch import error\nif cryptography:\n    from twisted.conch.ssh import common, connection\nelse:\n    class connection:\n        class SSHConnection: pass\n\nfrom twisted.conch.ssh import channel\nfrom twisted.python.compat import long\nfrom twisted.trial import unittest\nfrom twisted.conch.test import test_userauth\n\n\nclass TestChannel(channel.SSHChannel):\n    \"\"\"\n    A mocked-up version of twisted.conch.ssh.channel.SSHChannel.\n\n    @ivar gotOpen: True if channelOpen has been called.\n    @type gotOpen: L{bool}\n    @ivar specificData: the specific channel open data passed to channelOpen.\n    @type specificData: L{bytes}\n    @ivar openFailureReason: the reason passed to openFailed.\n    @type openFailed: C{error.ConchError}\n    @ivar inBuffer: a C{list} of strings received by the channel.\n    @type inBuffer: C{list}\n    @ivar extBuffer: a C{list} of 2-tuples (type, extended data) of received by\n        the channel.\n    @type extBuffer: C{list}\n    @ivar numberRequests: the number of requests that have been made to this\n        channel.\n    @type numberRequests: L{int}\n    @ivar gotEOF: True if the other side sent EOF.\n    @type gotEOF: L{bool}\n    @ivar gotOneClose: True if the other side closed the connection.\n    @type gotOneClose: L{bool}\n    @ivar gotClosed: True if the channel is closed.\n    @type gotClosed: L{bool}\n    \"\"\"\n    name = b\"TestChannel\"\n    gotOpen = False\n    gotClosed = False\n\n    def logPrefix(self):\n        return \"TestChannel %i\" % self.id\n\n    def channelOpen(self, specificData):\n        \"\"\"\n        The channel is open.  Set up the instance variables.\n        \"\"\"\n        self.gotOpen = True\n        self.specificData = specificData\n        self.inBuffer = []\n        self.extBuffer = []\n        self.numberRequests = 0\n        self.gotEOF = False\n        self.gotOneClose = False\n        self.gotClosed = False\n\n    def openFailed(self, reason):\n        \"\"\"\n        Opening the channel failed.  Store the reason why.\n        \"\"\"\n        self.openFailureReason = reason\n\n    def request_test(self, data):\n        \"\"\"\n        A test request.  Return True if data is 'data'.\n\n        @type data: L{bytes}\n        \"\"\"\n        self.numberRequests += 1\n        return data == b'data'\n\n    def dataReceived(self, data):\n        \"\"\"\n        Data was received.  Store it in the buffer.\n        \"\"\"\n        self.inBuffer.append(data)\n\n    def extReceived(self, code, data):\n        \"\"\"\n        Extended data was received.  Store it in the buffer.\n        \"\"\"\n        self.extBuffer.append((code, data))\n\n    def eofReceived(self):\n        \"\"\"\n        EOF was received.  Remember it.\n        \"\"\"\n        self.gotEOF = True\n\n    def closeReceived(self):\n        \"\"\"\n        Close was received.  Remember it.\n        \"\"\"\n        self.gotOneClose = True\n\n    def closed(self):\n        \"\"\"\n        The channel is closed.  Rembember it.\n        \"\"\"\n        self.gotClosed = True\n\nclass TestAvatar:\n    \"\"\"\n    A mocked-up version of twisted.conch.avatar.ConchUser\n    \"\"\"\n    _ARGS_ERROR_CODE = 123\n\n    def lookupChannel(self, channelType, windowSize, maxPacket, data):\n        \"\"\"\n        The server wants us to return a channel.  If the requested channel is\n        our TestChannel, return it, otherwise return None.\n        \"\"\"\n        if channelType == TestChannel.name:\n            return TestChannel(remoteWindow=windowSize,\n                    remoteMaxPacket=maxPacket,\n                    data=data, avatar=self)\n        elif channelType == b\"conch-error-args\":\n            # Raise a ConchError with backwards arguments to make sure the\n            # connection fixes it for us.  This case should be deprecated and\n            # deleted eventually, but only after all of Conch gets the argument\n            # order right.\n            raise error.ConchError(\n                self._ARGS_ERROR_CODE, \"error args in wrong order\")\n\n\n    def gotGlobalRequest(self, requestType, data):\n        \"\"\"\n        The client has made a global request.  If the global request is\n        'TestGlobal', return True.  If the global request is 'TestData',\n        return True and the request-specific data we received.  Otherwise,\n        return False.\n        \"\"\"\n        if requestType == b'TestGlobal':\n            return True\n        elif requestType == b'TestData':\n            return True, data\n        else:\n            return False\n\n\n\nclass TestConnection(connection.SSHConnection):\n    \"\"\"\n    A subclass of SSHConnection for testing.\n\n    @ivar channel: the current channel.\n    @type channel. C{TestChannel}\n    \"\"\"\n\n    if not cryptography:\n        skip = \"Cannot run without cryptography\"\n\n    def logPrefix(self):\n        return \"TestConnection\"\n\n    def global_TestGlobal(self, data):\n        \"\"\"\n        The other side made the 'TestGlobal' global request.  Return True.\n        \"\"\"\n        return True\n\n    def global_Test_Data(self, data):\n        \"\"\"\n        The other side made the 'Test-Data' global request.  Return True and\n        the data we received.\n        \"\"\"\n        return True, data\n\n    def channel_TestChannel(self, windowSize, maxPacket, data):\n        \"\"\"\n        The other side is requesting the TestChannel.  Create a C{TestChannel}\n        instance, store it, and return it.\n        \"\"\"\n        self.channel = TestChannel(remoteWindow=windowSize,\n                remoteMaxPacket=maxPacket, data=data)\n        return self.channel\n\n    def channel_ErrorChannel(self, windowSize, maxPacket, data):\n        \"\"\"\n        The other side is requesting the ErrorChannel.  Raise an exception.\n        \"\"\"\n        raise AssertionError('no such thing')\n\n\n\nclass ConnectionTests(unittest.TestCase):\n\n    if not cryptography:\n        skip = \"Cannot run without cryptography\"\n    if test_userauth.transport is None:\n        skip = \"Cannot run without both cryptography and pyasn1\"\n\n    def setUp(self):\n        self.transport = test_userauth.FakeTransport(None)\n        self.transport.avatar = TestAvatar()\n        self.conn = TestConnection()\n        self.conn.transport = self.transport\n        self.conn.serviceStarted()\n\n    def _openChannel(self, channel):\n        \"\"\"\n        Open the channel with the default connection.\n        \"\"\"\n        self.conn.openChannel(channel)\n        self.transport.packets = self.transport.packets[:-1]\n        self.conn.ssh_CHANNEL_OPEN_CONFIRMATION(struct.pack('>2L',\n            channel.id, 255) + b'\\x00\\x02\\x00\\x00\\x00\\x00\\x80\\x00')\n\n    def tearDown(self):\n        self.conn.serviceStopped()\n\n    def test_linkAvatar(self):\n        \"\"\"\n        Test that the connection links itself to the avatar in the\n        transport.\n        \"\"\"\n        self.assertIs(self.transport.avatar.conn, self.conn)\n\n    def test_serviceStopped(self):\n        \"\"\"\n        Test that serviceStopped() closes any open channels.\n        \"\"\"\n        channel1 = TestChannel()\n        channel2 = TestChannel()\n        self.conn.openChannel(channel1)\n        self.conn.openChannel(channel2)\n        self.conn.ssh_CHANNEL_OPEN_CONFIRMATION(b'\\x00\\x00\\x00\\x00' * 4)\n        self.assertTrue(channel1.gotOpen)\n        self.assertFalse(channel1.gotClosed)\n        self.assertFalse(channel2.gotOpen)\n        self.assertFalse(channel2.gotClosed)\n        self.conn.serviceStopped()\n        self.assertTrue(channel1.gotClosed)\n        self.assertFalse(channel2.gotOpen)\n        self.assertFalse(channel2.gotClosed)\n        from twisted.internet.error import ConnectionLost\n        self.assertIsInstance(channel2.openFailureReason,\n                              ConnectionLost)\n\n    def test_GLOBAL_REQUEST(self):\n        \"\"\"\n        Test that global request packets are dispatched to the global_*\n        methods and the return values are translated into success or failure\n        messages.\n        \"\"\"\n        self.conn.ssh_GLOBAL_REQUEST(common.NS(b'TestGlobal') + b'\\xff')\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_REQUEST_SUCCESS, b'')])\n        self.transport.packets = []\n        self.conn.ssh_GLOBAL_REQUEST(common.NS(b'TestData') + b'\\xff' +\n                b'test data')\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_REQUEST_SUCCESS, b'test data')])\n        self.transport.packets = []\n        self.conn.ssh_GLOBAL_REQUEST(common.NS(b'TestBad') + b'\\xff')\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_REQUEST_FAILURE, b'')])\n        self.transport.packets = []\n        self.conn.ssh_GLOBAL_REQUEST(common.NS(b'TestGlobal') + b'\\x00')\n        self.assertEqual(self.transport.packets, [])\n\n    def test_REQUEST_SUCCESS(self):\n        \"\"\"\n        Test that global request success packets cause the Deferred to be\n        called back.\n        \"\"\"\n        d = self.conn.sendGlobalRequest(b'request', b'data', True)\n        self.conn.ssh_REQUEST_SUCCESS(b'data')\n        def check(data):\n            self.assertEqual(data, b'data')\n        d.addCallback(check)\n        d.addErrback(self.fail)\n        return d\n\n    def test_REQUEST_FAILURE(self):\n        \"\"\"\n        Test that global request failure packets cause the Deferred to be\n        erred back.\n        \"\"\"\n        d = self.conn.sendGlobalRequest(b'request', b'data', True)\n        self.conn.ssh_REQUEST_FAILURE(b'data')\n        def check(f):\n            self.assertEqual(f.value.data, b'data')\n        d.addCallback(self.fail)\n        d.addErrback(check)\n        return d\n\n    def test_CHANNEL_OPEN(self):\n        \"\"\"\n        Test that open channel packets cause a channel to be created and\n        opened or a failure message to be returned.\n        \"\"\"\n        del self.transport.avatar\n        self.conn.ssh_CHANNEL_OPEN(common.NS(b'TestChannel') +\n               b'\\x00\\x00\\x00\\x01' * 4)\n        self.assertTrue(self.conn.channel.gotOpen)\n        self.assertEqual(self.conn.channel.conn, self.conn)\n        self.assertEqual(self.conn.channel.data, b'\\x00\\x00\\x00\\x01')\n        self.assertEqual(self.conn.channel.specificData, b'\\x00\\x00\\x00\\x01')\n        self.assertEqual(self.conn.channel.remoteWindowLeft, 1)\n        self.assertEqual(self.conn.channel.remoteMaxPacket, 1)\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_OPEN_CONFIRMATION,\n                    b'\\x00\\x00\\x00\\x01\\x00\\x00\\x00\\x00\\x00\\x02\\x00\\x00'\n                    b'\\x00\\x00\\x80\\x00')])\n        self.transport.packets = []\n        self.conn.ssh_CHANNEL_OPEN(common.NS(b'BadChannel') +\n                b'\\x00\\x00\\x00\\x02' * 4)\n        self.flushLoggedErrors()\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_OPEN_FAILURE,\n                    b'\\x00\\x00\\x00\\x02\\x00\\x00\\x00\\x03' + common.NS(\n                    b'unknown channel') + common.NS(b''))])\n        self.transport.packets = []\n        self.conn.ssh_CHANNEL_OPEN(common.NS(b'ErrorChannel') +\n                b'\\x00\\x00\\x00\\x02' * 4)\n        self.flushLoggedErrors()\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_OPEN_FAILURE,\n                    b'\\x00\\x00\\x00\\x02\\x00\\x00\\x00\\x02' + common.NS(\n                    b'unknown failure') + common.NS(b''))])\n\n\n    def _lookupChannelErrorTest(self, code):\n        \"\"\"\n        Deliver a request for a channel open which will result in an exception\n        being raised during channel lookup.  Assert that an error response is\n        delivered as a result.\n        \"\"\"\n        self.transport.avatar._ARGS_ERROR_CODE = code\n        self.conn.ssh_CHANNEL_OPEN(\n            common.NS(b'conch-error-args') + b'\\x00\\x00\\x00\\x01' * 4)\n        errors = self.flushLoggedErrors(error.ConchError)\n        self.assertEqual(\n            len(errors), 1, \"Expected one error, got: %r\" % (errors,))\n        self.assertEqual(errors[0].value.args, (long(123), \"error args in wrong order\"))\n        self.assertEqual(\n            self.transport.packets,\n            [(connection.MSG_CHANNEL_OPEN_FAILURE,\n              # The response includes some bytes which identifying the\n              # associated request, as well as the error code (7b in hex) and\n              # the error message.\n              b'\\x00\\x00\\x00\\x01\\x00\\x00\\x00\\x7b' + common.NS(\n                        b'error args in wrong order') + common.NS(b''))])\n\n\n    def test_lookupChannelError(self):\n        \"\"\"\n        If a C{lookupChannel} implementation raises L{error.ConchError} with the\n        arguments in the wrong order, a C{MSG_CHANNEL_OPEN} failure is still\n        sent in response to the message.\n\n        This is a temporary work-around until L{error.ConchError} is given\n        better attributes and all of the Conch code starts constructing\n        instances of it properly.  Eventually this functionality should be\n        deprecated and then removed.\n        \"\"\"\n        self._lookupChannelErrorTest(123)\n\n\n    def test_lookupChannelErrorLongCode(self):\n        \"\"\"\n        Like L{test_lookupChannelError}, but for the case where the failure code\n        is represented as a L{long} instead of a L{int}.\n        \"\"\"\n        self._lookupChannelErrorTest(long(123))\n\n\n    def test_CHANNEL_OPEN_CONFIRMATION(self):\n        \"\"\"\n        Test that channel open confirmation packets cause the channel to be\n        notified that it's open.\n        \"\"\"\n        channel = TestChannel()\n        self.conn.openChannel(channel)\n        self.conn.ssh_CHANNEL_OPEN_CONFIRMATION(b'\\x00\\x00\\x00\\x00'*5)\n        self.assertEqual(channel.remoteWindowLeft, 0)\n        self.assertEqual(channel.remoteMaxPacket, 0)\n        self.assertEqual(channel.specificData, b'\\x00\\x00\\x00\\x00')\n        self.assertEqual(self.conn.channelsToRemoteChannel[channel],\n                0)\n        self.assertEqual(self.conn.localToRemoteChannel[0], 0)\n\n    def test_CHANNEL_OPEN_FAILURE(self):\n        \"\"\"\n        Test that channel open failure packets cause the channel to be\n        notified that its opening failed.\n        \"\"\"\n        channel = TestChannel()\n        self.conn.openChannel(channel)\n        self.conn.ssh_CHANNEL_OPEN_FAILURE(b'\\x00\\x00\\x00\\x00\\x00\\x00\\x00'\n                b'\\x01' + common.NS(b'failure!'))\n        self.assertEqual(channel.openFailureReason.args, (b'failure!', 1))\n        self.assertIsNone(self.conn.channels.get(channel))\n\n\n    def test_CHANNEL_WINDOW_ADJUST(self):\n        \"\"\"\n        Test that channel window adjust messages add bytes to the channel\n        window.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n        oldWindowSize = channel.remoteWindowLeft\n        self.conn.ssh_CHANNEL_WINDOW_ADJUST(b'\\x00\\x00\\x00\\x00\\x00\\x00\\x00'\n                b'\\x01')\n        self.assertEqual(channel.remoteWindowLeft, oldWindowSize + 1)\n\n    def test_CHANNEL_DATA(self):\n        \"\"\"\n        Test that channel data messages are passed up to the channel, or\n        cause the channel to be closed if the data is too large.\n        \"\"\"\n        channel = TestChannel(localWindow=6, localMaxPacket=5)\n        self._openChannel(channel)\n        self.conn.ssh_CHANNEL_DATA(b'\\x00\\x00\\x00\\x00' + common.NS(b'data'))\n        self.assertEqual(channel.inBuffer, [b'data'])\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_WINDOW_ADJUST, b'\\x00\\x00\\x00\\xff'\n                    b'\\x00\\x00\\x00\\x04')])\n        self.transport.packets = []\n        longData = b'a' * (channel.localWindowLeft + 1)\n        self.conn.ssh_CHANNEL_DATA(b'\\x00\\x00\\x00\\x00' + common.NS(longData))\n        self.assertEqual(channel.inBuffer, [b'data'])\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_CLOSE, b'\\x00\\x00\\x00\\xff')])\n        channel = TestChannel()\n        self._openChannel(channel)\n        bigData = b'a' * (channel.localMaxPacket + 1)\n        self.transport.packets = []\n        self.conn.ssh_CHANNEL_DATA(b'\\x00\\x00\\x00\\x01' + common.NS(bigData))\n        self.assertEqual(channel.inBuffer, [])\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_CLOSE, b'\\x00\\x00\\x00\\xff')])\n\n    def test_CHANNEL_EXTENDED_DATA(self):\n        \"\"\"\n        Test that channel extended data messages are passed up to the channel,\n        or cause the channel to be closed if they're too big.\n        \"\"\"\n        channel = TestChannel(localWindow=6, localMaxPacket=5)\n        self._openChannel(channel)\n        self.conn.ssh_CHANNEL_EXTENDED_DATA(b'\\x00\\x00\\x00\\x00\\x00\\x00\\x00'\n                                            b'\\x00' + common.NS(b'data'))\n        self.assertEqual(channel.extBuffer, [(0, b'data')])\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_WINDOW_ADJUST, b'\\x00\\x00\\x00\\xff'\n                    b'\\x00\\x00\\x00\\x04')])\n        self.transport.packets = []\n        longData = b'a' * (channel.localWindowLeft + 1)\n        self.conn.ssh_CHANNEL_EXTENDED_DATA(b'\\x00\\x00\\x00\\x00\\x00\\x00\\x00'\n                                            b'\\x00' + common.NS(longData))\n        self.assertEqual(channel.extBuffer, [(0, b'data')])\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_CLOSE, b'\\x00\\x00\\x00\\xff')])\n        channel = TestChannel()\n        self._openChannel(channel)\n        bigData = b'a' * (channel.localMaxPacket + 1)\n        self.transport.packets = []\n        self.conn.ssh_CHANNEL_EXTENDED_DATA(b'\\x00\\x00\\x00\\x01\\x00\\x00\\x00'\n                                            b'\\x00' + common.NS(bigData))\n        self.assertEqual(channel.extBuffer, [])\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_CLOSE, b'\\x00\\x00\\x00\\xff')])\n\n    def test_CHANNEL_EOF(self):\n        \"\"\"\n        Test that channel eof messages are passed up to the channel.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n        self.conn.ssh_CHANNEL_EOF(b'\\x00\\x00\\x00\\x00')\n        self.assertTrue(channel.gotEOF)\n\n    def test_CHANNEL_CLOSE(self):\n        \"\"\"\n        Test that channel close messages are passed up to the channel.  Also,\n        test that channel.close() is called if both sides are closed when this\n        message is received.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n        self.assertTrue(channel.gotOpen)\n        self.assertFalse(channel.gotOneClose)\n        self.assertFalse(channel.gotClosed)\n        self.conn.sendClose(channel)\n        self.conn.ssh_CHANNEL_CLOSE(b'\\x00\\x00\\x00\\x00')\n        self.assertTrue(channel.gotOneClose)\n        self.assertTrue(channel.gotClosed)\n\n    def test_CHANNEL_REQUEST_success(self):\n        \"\"\"\n        Test that channel requests that succeed send MSG_CHANNEL_SUCCESS.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n        self.conn.ssh_CHANNEL_REQUEST(b'\\x00\\x00\\x00\\x00' + common.NS(b'test')\n                + b'\\x00')\n        self.assertEqual(channel.numberRequests, 1)\n        d = self.conn.ssh_CHANNEL_REQUEST(b'\\x00\\x00\\x00\\x00' + common.NS(\n            b'test') + b'\\xff' + b'data')\n        def check(result):\n            self.assertEqual(self.transport.packets,\n                    [(connection.MSG_CHANNEL_SUCCESS, b'\\x00\\x00\\x00\\xff')])\n        d.addCallback(check)\n        return d\n\n    def test_CHANNEL_REQUEST_failure(self):\n        \"\"\"\n        Test that channel requests that fail send MSG_CHANNEL_FAILURE.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n        d = self.conn.ssh_CHANNEL_REQUEST(b'\\x00\\x00\\x00\\x00' + common.NS(\n            b'test') + b'\\xff')\n        def check(result):\n            self.assertEqual(self.transport.packets,\n                    [(connection.MSG_CHANNEL_FAILURE, b'\\x00\\x00\\x00\\xff'\n                        )])\n        d.addCallback(self.fail)\n        d.addErrback(check)\n        return d\n\n    def test_CHANNEL_REQUEST_SUCCESS(self):\n        \"\"\"\n        Test that channel request success messages cause the Deferred to be\n        called back.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n        d = self.conn.sendRequest(channel, b'test', b'data', True)\n        self.conn.ssh_CHANNEL_SUCCESS(b'\\x00\\x00\\x00\\x00')\n        def check(result):\n            self.assertTrue(result)\n        return d\n\n    def test_CHANNEL_REQUEST_FAILURE(self):\n        \"\"\"\n        Test that channel request failure messages cause the Deferred to be\n        erred back.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n        d = self.conn.sendRequest(channel, b'test', b'', True)\n        self.conn.ssh_CHANNEL_FAILURE(b'\\x00\\x00\\x00\\x00')\n        def check(result):\n            self.assertEqual(result.value.value, 'channel request failed')\n        d.addCallback(self.fail)\n        d.addErrback(check)\n        return d\n\n    def test_sendGlobalRequest(self):\n        \"\"\"\n        Test that global request messages are sent in the right format.\n        \"\"\"\n        d = self.conn.sendGlobalRequest(b'wantReply', b'data', True)\n        # must be added to prevent errbacking during teardown\n        d.addErrback(lambda failure: None)\n        self.conn.sendGlobalRequest(b'noReply', b'', False)\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_GLOBAL_REQUEST, common.NS(b'wantReply') +\n                    b'\\xffdata'),\n                 (connection.MSG_GLOBAL_REQUEST, common.NS(b'noReply') +\n                     b'\\x00')])\n        self.assertEqual(self.conn.deferreds, {'global':[d]})\n\n    def test_openChannel(self):\n        \"\"\"\n        Test that open channel messages are sent in the right format.\n        \"\"\"\n        channel = TestChannel()\n        self.conn.openChannel(channel, b'aaaa')\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_OPEN, common.NS(b'TestChannel') +\n                    b'\\x00\\x00\\x00\\x00\\x00\\x02\\x00\\x00\\x00\\x00\\x80\\x00aaaa')])\n        self.assertEqual(channel.id, 0)\n        self.assertEqual(self.conn.localChannelID, 1)\n\n    def test_sendRequest(self):\n        \"\"\"\n        Test that channel request messages are sent in the right format.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n        d = self.conn.sendRequest(channel, b'test', b'test', True)\n        # needed to prevent errbacks during teardown.\n        d.addErrback(lambda failure: None)\n        self.conn.sendRequest(channel, b'test2', b'', False)\n        channel.localClosed = True # emulate sending a close message\n        self.conn.sendRequest(channel, b'test3', b'', True)\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_REQUEST, b'\\x00\\x00\\x00\\xff' +\n                    common.NS(b'test') + b'\\x01test'),\n                 (connection.MSG_CHANNEL_REQUEST, b'\\x00\\x00\\x00\\xff' +\n                     common.NS(b'test2') + b'\\x00')])\n        self.assertEqual(self.conn.deferreds[0], [d])\n\n    def test_adjustWindow(self):\n        \"\"\"\n        Test that channel window adjust messages cause bytes to be added\n        to the window.\n        \"\"\"\n        channel = TestChannel(localWindow=5)\n        self._openChannel(channel)\n        channel.localWindowLeft = 0\n        self.conn.adjustWindow(channel, 1)\n        self.assertEqual(channel.localWindowLeft, 1)\n        channel.localClosed = True\n        self.conn.adjustWindow(channel, 2)\n        self.assertEqual(channel.localWindowLeft, 1)\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_WINDOW_ADJUST, b'\\x00\\x00\\x00\\xff'\n                    b'\\x00\\x00\\x00\\x01')])\n\n    def test_sendData(self):\n        \"\"\"\n        Test that channel data messages are sent in the right format.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n        self.conn.sendData(channel, b'a')\n        channel.localClosed = True\n        self.conn.sendData(channel, b'b')\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_DATA, b'\\x00\\x00\\x00\\xff' +\n                    common.NS(b'a'))])\n\n    def test_sendExtendedData(self):\n        \"\"\"\n        Test that channel extended data messages are sent in the right format.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n        self.conn.sendExtendedData(channel, 1, b'test')\n        channel.localClosed = True\n        self.conn.sendExtendedData(channel, 2, b'test2')\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_EXTENDED_DATA, b'\\x00\\x00\\x00\\xff' +\n                    b'\\x00\\x00\\x00\\x01' + common.NS(b'test'))])\n\n    def test_sendEOF(self):\n        \"\"\"\n        Test that channel EOF messages are sent in the right format.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n        self.conn.sendEOF(channel)\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_EOF, b'\\x00\\x00\\x00\\xff')])\n        channel.localClosed = True\n        self.conn.sendEOF(channel)\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_EOF, b'\\x00\\x00\\x00\\xff')])\n\n    def test_sendClose(self):\n        \"\"\"\n        Test that channel close messages are sent in the right format.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n        self.conn.sendClose(channel)\n        self.assertTrue(channel.localClosed)\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_CLOSE, b'\\x00\\x00\\x00\\xff')])\n        self.conn.sendClose(channel)\n        self.assertEqual(self.transport.packets,\n                [(connection.MSG_CHANNEL_CLOSE, b'\\x00\\x00\\x00\\xff')])\n\n        channel2 = TestChannel()\n        self._openChannel(channel2)\n        self.assertTrue(channel2.gotOpen)\n        self.assertFalse(channel2.gotClosed)\n        channel2.remoteClosed = True\n        self.conn.sendClose(channel2)\n        self.assertTrue(channel2.gotClosed)\n\n    def test_getChannelWithAvatar(self):\n        \"\"\"\n        Test that getChannel dispatches to the avatar when an avatar is\n        present. Correct functioning without the avatar is verified in\n        test_CHANNEL_OPEN.\n        \"\"\"\n        channel = self.conn.getChannel(b'TestChannel', 50, 30, b'data')\n        self.assertEqual(channel.data, b'data')\n        self.assertEqual(channel.remoteWindowLeft, 50)\n        self.assertEqual(channel.remoteMaxPacket, 30)\n        self.assertRaises(error.ConchError, self.conn.getChannel,\n                b'BadChannel', 50, 30, b'data')\n\n    def test_gotGlobalRequestWithoutAvatar(self):\n        \"\"\"\n        Test that gotGlobalRequests dispatches to global_* without an avatar.\n        \"\"\"\n        del self.transport.avatar\n        self.assertTrue(self.conn.gotGlobalRequest(b'TestGlobal', b'data'))\n        self.assertEqual(self.conn.gotGlobalRequest(b'Test-Data', b'data'),\n                (True, b'data'))\n        self.assertFalse(self.conn.gotGlobalRequest(b'BadGlobal', b'data'))\n\n\n    def test_channelClosedCausesLeftoverChannelDeferredsToErrback(self):\n        \"\"\"\n        Whenever an SSH channel gets closed any Deferred that was returned by a\n        sendRequest() on its parent connection must be errbacked.\n        \"\"\"\n        channel = TestChannel()\n        self._openChannel(channel)\n\n        d = self.conn.sendRequest(\n            channel, b\"dummyrequest\", b\"dummydata\", wantReply=1)\n        d = self.assertFailure(d, error.ConchError)\n        self.conn.channelClosed(channel)\n        return d\n\n\n\nclass CleanConnectionShutdownTests(unittest.TestCase):\n    \"\"\"\n    Check whether correct cleanup is performed on connection shutdown.\n    \"\"\"\n    if not cryptography:\n        skip = \"Cannot run without cryptography\"\n\n    if test_userauth.transport is None:\n        skip = \"Cannot run without both cryptography and pyasn1\"\n\n    def setUp(self):\n        self.transport = test_userauth.FakeTransport(None)\n        self.transport.avatar = TestAvatar()\n        self.conn = TestConnection()\n        self.conn.transport = self.transport\n\n\n    def test_serviceStoppedCausesLeftoverGlobalDeferredsToErrback(self):\n        \"\"\"\n        Once the service is stopped any leftover global deferred returned by\n        a sendGlobalRequest() call must be errbacked.\n        \"\"\"\n        self.conn.serviceStarted()\n\n        d = self.conn.sendGlobalRequest(\n            b\"dummyrequest\", b\"dummydata\", wantReply=1)\n        d = self.assertFailure(d, error.ConchError)\n        self.conn.serviceStopped()\n        return d\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_default.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.client.default}.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport sys\n\nfrom twisted.python.reflect import requireModule\n\nif requireModule('cryptography') and requireModule('pyasn1'):\n    from twisted.conch.client.agent import SSHAgentClient\n    from twisted.conch.client.default import SSHUserAuthClient\n    from twisted.conch.client.options import ConchOptions\n    from twisted.conch.client import default\n    from twisted.conch.ssh.keys import Key\n    skip = None\nelse:\n    skip = \"cryptography and PyASN1 required for twisted.conch.client.default.\"\n\nfrom twisted.trial.unittest import TestCase\nfrom twisted.python.filepath import FilePath\nfrom twisted.conch.error import ConchError\nfrom twisted.conch.test import keydata\nfrom twisted.test.proto_helpers import StringTransport\nfrom twisted.python.compat import nativeString\nfrom twisted.python.runtime import platform\n\nif platform.isWindows():\n    windowsSkip = (\n        \"genericAnswers and getPassword does not work on Windows.\"\n        \" Should be fixed as part of fixing bug 6409 and 6410\")\nelse:\n    windowsSkip = skip\n\nttySkip = None\nif not sys.stdin.isatty():\n    ttySkip = \"sys.stdin is not an interactive tty\"\nif not sys.stdout.isatty():\n    ttySkip = \"sys.stdout is not an interactive tty\"\n\n\n\nclass SSHUserAuthClientTests(TestCase):\n    \"\"\"\n    Tests for L{SSHUserAuthClient}.\n\n    @type rsaPublic: L{Key}\n    @ivar rsaPublic: A public RSA key.\n    \"\"\"\n\n    def setUp(self):\n        self.rsaPublic = Key.fromString(keydata.publicRSA_openssh)\n        self.tmpdir = FilePath(self.mktemp())\n        self.tmpdir.makedirs()\n        self.rsaFile = self.tmpdir.child('id_rsa')\n        self.rsaFile.setContent(keydata.privateRSA_openssh)\n        self.tmpdir.child('id_rsa.pub').setContent(keydata.publicRSA_openssh)\n\n\n    def test_signDataWithAgent(self):\n        \"\"\"\n        When connected to an agent, L{SSHUserAuthClient} can use it to\n        request signatures of particular data with a particular L{Key}.\n        \"\"\"\n        client = SSHUserAuthClient(b\"user\", ConchOptions(), None)\n        agent = SSHAgentClient()\n        transport = StringTransport()\n        agent.makeConnection(transport)\n        client.keyAgent = agent\n        cleartext = b\"Sign here\"\n        client.signData(self.rsaPublic, cleartext)\n        self.assertEqual(\n            transport.value(),\n            b\"\\x00\\x00\\x01\\x2d\\r\\x00\\x00\\x01\\x17\" + self.rsaPublic.blob() +\n            b\"\\x00\\x00\\x00\\t\" + cleartext +\n            b\"\\x00\\x00\\x00\\x00\")\n\n\n    def test_agentGetPublicKey(self):\n        \"\"\"\n        L{SSHUserAuthClient} looks up public keys from the agent using the\n        L{SSHAgentClient} class.  That L{SSHAgentClient.getPublicKey} returns a\n        L{Key} object with one of the public keys in the agent.  If no more\n        keys are present, it returns L{None}.\n        \"\"\"\n        agent = SSHAgentClient()\n        agent.blobs = [self.rsaPublic.blob()]\n        key = agent.getPublicKey()\n        self.assertTrue(key.isPublic())\n        self.assertEqual(key, self.rsaPublic)\n        self.assertIsNone(agent.getPublicKey())\n\n\n    def test_getPublicKeyFromFile(self):\n        \"\"\"\n        L{SSHUserAuthClient.getPublicKey()} is able to get a public key from\n        the first file described by its options' C{identitys} list, and return\n        the corresponding public L{Key} object.\n        \"\"\"\n        options = ConchOptions()\n        options.identitys = [self.rsaFile.path]\n        client = SSHUserAuthClient(b\"user\",  options, None)\n        key = client.getPublicKey()\n        self.assertTrue(key.isPublic())\n        self.assertEqual(key, self.rsaPublic)\n\n\n    def test_getPublicKeyAgentFallback(self):\n        \"\"\"\n        If an agent is present, but doesn't return a key,\n        L{SSHUserAuthClient.getPublicKey} continue with the normal key lookup.\n        \"\"\"\n        options = ConchOptions()\n        options.identitys = [self.rsaFile.path]\n        agent = SSHAgentClient()\n        client = SSHUserAuthClient(b\"user\",  options, None)\n        client.keyAgent = agent\n        key = client.getPublicKey()\n        self.assertTrue(key.isPublic())\n        self.assertEqual(key, self.rsaPublic)\n\n\n    def test_getPublicKeyBadKeyError(self):\n        \"\"\"\n        If L{keys.Key.fromFile} raises a L{keys.BadKeyError}, the\n        L{SSHUserAuthClient.getPublicKey} tries again to get a public key by\n        calling itself recursively.\n        \"\"\"\n        options = ConchOptions()\n        self.tmpdir.child('id_dsa.pub').setContent(keydata.publicDSA_openssh)\n        dsaFile = self.tmpdir.child('id_dsa')\n        dsaFile.setContent(keydata.privateDSA_openssh)\n        options.identitys = [self.rsaFile.path, dsaFile.path]\n        self.tmpdir.child('id_rsa.pub').setContent(b'not a key!')\n        client = SSHUserAuthClient(b\"user\",  options, None)\n        key = client.getPublicKey()\n        self.assertTrue(key.isPublic())\n        self.assertEqual(key, Key.fromString(keydata.publicDSA_openssh))\n        self.assertEqual(client.usedFiles, [self.rsaFile.path, dsaFile.path])\n\n\n    def test_getPrivateKey(self):\n        \"\"\"\n        L{SSHUserAuthClient.getPrivateKey} will load a private key from the\n        last used file populated by L{SSHUserAuthClient.getPublicKey}, and\n        return a L{Deferred} which fires with the corresponding private L{Key}.\n        \"\"\"\n        rsaPrivate = Key.fromString(keydata.privateRSA_openssh)\n        options = ConchOptions()\n        options.identitys = [self.rsaFile.path]\n        client = SSHUserAuthClient(b\"user\",  options, None)\n        # Populate the list of used files\n        client.getPublicKey()\n\n        def _cbGetPrivateKey(key):\n            self.assertFalse(key.isPublic())\n            self.assertEqual(key, rsaPrivate)\n\n        return client.getPrivateKey().addCallback(_cbGetPrivateKey)\n\n\n    def test_getPrivateKeyPassphrase(self):\n        \"\"\"\n        L{SSHUserAuthClient} can get a private key from a file, and return a\n        Deferred called back with a private L{Key} object, even if the key is\n        encrypted.\n        \"\"\"\n        rsaPrivate = Key.fromString(keydata.privateRSA_openssh)\n        passphrase = b'this is the passphrase'\n        self.rsaFile.setContent(rsaPrivate.toString('openssh', passphrase))\n        options = ConchOptions()\n        options.identitys = [self.rsaFile.path]\n        client = SSHUserAuthClient(b\"user\",  options, None)\n        # Populate the list of used files\n        client.getPublicKey()\n\n        def _getPassword(prompt):\n            self.assertEqual(\n                prompt,\n                \"Enter passphrase for key '%s': \" % (self.rsaFile.path,))\n            return nativeString(passphrase)\n\n        def _cbGetPrivateKey(key):\n            self.assertFalse(key.isPublic())\n            self.assertEqual(key, rsaPrivate)\n\n        self.patch(client, '_getPassword', _getPassword)\n        return client.getPrivateKey().addCallback(_cbGetPrivateKey)\n\n\n    def test_getPassword(self):\n        \"\"\"\n        Get the password using\n        L{twisted.conch.client.default.SSHUserAuthClient.getPassword}\n        \"\"\"\n        class FakeTransport:\n            def __init__(self, host):\n                self.transport = self\n                self.host = host\n            def getPeer(self):\n                return self\n\n        options = ConchOptions()\n        client = SSHUserAuthClient(b\"user\",  options, None)\n        client.transport = FakeTransport(\"127.0.0.1\")\n\n        def getpass(prompt):\n            self.assertEqual(prompt, \"user@127.0.0.1's password: \")\n            return 'bad password'\n\n        self.patch(default.getpass, 'getpass', getpass)\n        d = client.getPassword()\n        d.addCallback(self.assertEqual, b'bad password')\n        return d\n\n    test_getPassword.skip = windowsSkip or ttySkip\n\n\n    def test_getPasswordPrompt(self):\n        \"\"\"\n        Get the password using\n        L{twisted.conch.client.default.SSHUserAuthClient.getPassword}\n        using a different prompt.\n        \"\"\"\n        options = ConchOptions()\n        client = SSHUserAuthClient(b\"user\",  options, None)\n        prompt = b\"Give up your password\"\n\n        def getpass(p):\n            self.assertEqual(p, nativeString(prompt))\n            return 'bad password'\n\n        self.patch(default.getpass, 'getpass', getpass)\n        d = client.getPassword(prompt)\n        d.addCallback(self.assertEqual, b'bad password')\n        return d\n\n    test_getPasswordPrompt.skip = windowsSkip or ttySkip\n\n\n    def test_getPasswordConchError(self):\n        \"\"\"\n        Get the password using\n        L{twisted.conch.client.default.SSHUserAuthClient.getPassword}\n        and trigger a {twisted.conch.error import ConchError}.\n        \"\"\"\n        options = ConchOptions()\n        client = SSHUserAuthClient(b\"user\",  options, None)\n\n        def getpass(prompt):\n            raise KeyboardInterrupt(\"User pressed CTRL-C\")\n\n        self.patch(default.getpass, 'getpass', getpass)\n        stdout, stdin = sys.stdout, sys.stdin\n        d = client.getPassword(b'?')\n        @d.addErrback\n        def check_sys(fail):\n            self.assertEqual(\n                [stdout, stdin], [sys.stdout, sys.stdin])\n            return fail\n        self.assertFailure(d, ConchError)\n\n    test_getPasswordConchError.skip = windowsSkip or ttySkip\n\n\n    def test_getGenericAnswers(self):\n        \"\"\"\n        L{twisted.conch.client.default.SSHUserAuthClient.getGenericAnswers}\n        \"\"\"\n        options = ConchOptions()\n        client = SSHUserAuthClient(b\"user\",  options, None)\n\n        def getpass(prompt):\n            self.assertEqual(prompt, \"pass prompt\")\n            return \"getpass\"\n\n        self.patch(default.getpass, 'getpass', getpass)\n\n        def raw_input(prompt):\n            self.assertEqual(prompt, \"raw_input prompt\")\n            return \"raw_input\"\n\n        self.patch(default, 'raw_input', raw_input)\n        d = client.getGenericAnswers(\n            b\"Name\", b\"Instruction\", [\n                (b\"pass prompt\", False), (b\"raw_input prompt\", True)])\n        d.addCallback(\n            self.assertListEqual, [\"getpass\", \"raw_input\"])\n        return d\n\n    test_getGenericAnswers.skip = windowsSkip or ttySkip\n\n\n\n\nclass ConchOptionsParsing(TestCase):\n    \"\"\"\n    Options parsing.\n    \"\"\"\n    def test_macs(self):\n        \"\"\"\n        Specify MAC algorithms.\n        \"\"\"\n        opts = ConchOptions()\n        e = self.assertRaises(SystemExit, opts.opt_macs, \"invalid-mac\")\n        self.assertIn(\"Unknown mac type\", e.code)\n        opts = ConchOptions()\n        opts.opt_macs(\"hmac-sha2-512\")\n        self.assertEqual(opts['macs'], [b\"hmac-sha2-512\"])\n        opts.opt_macs(b\"hmac-sha2-512\")\n        self.assertEqual(opts['macs'], [b\"hmac-sha2-512\"])\n        opts.opt_macs(\"hmac-sha2-256,hmac-sha1,hmac-md5\")\n        self.assertEqual(opts['macs'], [b\"hmac-sha2-256\", b\"hmac-sha1\", b\"hmac-md5\"])\n\n\n    def test_host_key_algorithms(self):\n        \"\"\"\n        Specify host key algorithms.\n        \"\"\"\n        opts = ConchOptions()\n        e = self.assertRaises(SystemExit, opts.opt_host_key_algorithms, \"invalid-key\")\n        self.assertIn(\"Unknown host key type\", e.code)\n        opts = ConchOptions()\n        opts.opt_host_key_algorithms(\"ssh-rsa\")\n        self.assertEqual(opts['host-key-algorithms'], [b\"ssh-rsa\"])\n        opts.opt_host_key_algorithms(b\"ssh-dss\")\n        self.assertEqual(opts['host-key-algorithms'], [b\"ssh-dss\"])\n        opts.opt_host_key_algorithms(\"ssh-rsa,ssh-dss\")\n        self.assertEqual(opts['host-key-algorithms'], [b\"ssh-rsa\", b\"ssh-dss\"])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_endpoints.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.endpoints}.\n\"\"\"\n\nimport os.path\nfrom struct import pack\nfrom errno import ENOSYS\n\nimport hamcrest\n\nfrom zope.interface.verify import verifyObject, verifyClass\nfrom zope.interface import implementer\n\nfrom twisted.logger import globalLogPublisher, LogLevel\nfrom twisted.python.compat import iteritems, networkString\nfrom twisted.python.failure import Failure\nfrom twisted.python.filepath import FilePath\nfrom twisted.python.log import msg\nfrom twisted.python.reflect import requireModule\nfrom twisted.internet.interfaces import IAddress, IStreamClientEndpoint\nfrom twisted.internet.protocol import Factory, Protocol\nfrom twisted.internet.defer import CancelledError, Deferred, succeed, fail\nfrom twisted.internet.error import ConnectionDone, ConnectionRefusedError\nfrom twisted.internet.address import IPv4Address\nfrom twisted.trial.unittest import TestCase\nfrom twisted.test.proto_helpers import EventLoggingObserver, MemoryReactorClock\nfrom twisted.internet.error import ProcessTerminated, ConnectingCancelledError\n\nfrom twisted.cred.portal import Portal\nfrom twisted.cred.checkers import InMemoryUsernamePasswordDatabaseDontUse\n\nfrom twisted.conch.interfaces import IConchUser\nfrom twisted.conch.error import ConchError, UserRejectedKey, HostKeyChanged\n\nif requireModule('cryptography') and requireModule('pyasn1.type'):\n    from twisted.conch.ssh import common\n    from twisted.conch.ssh.factory import SSHFactory\n    from twisted.conch.ssh.userauth import SSHUserAuthServer\n    from twisted.conch.ssh.connection import SSHConnection\n    from twisted.conch.ssh.keys import Key\n    from twisted.conch.ssh.channel import SSHChannel\n    from twisted.conch.ssh.agent import SSHAgentServer\n    from twisted.conch.client.knownhosts import KnownHostsFile, ConsoleUI\n    from twisted.conch.checkers import SSHPublicKeyChecker, InMemorySSHKeyDB\n    from twisted.conch.avatar import ConchUser\n\n    from twisted.conch.test.keydata import (\n        publicRSA_openssh, privateRSA_openssh,\n        privateRSA_openssh_encrypted_aes,\n        privateDSA_openssh)\n\n    from twisted.conch.endpoints import (\n        _ISSHConnectionCreator, AuthenticationFailed, SSHCommandAddress,\n        SSHCommandClientEndpoint, _ReadFile, _NewConnectionHelper,\n        _ExistingConnectionHelper)\n\n    from twisted.conch.ssh.transport import SSHClientTransport\nelse:\n    skip = \"can't run w/o cryptography and pyasn1\"\n    SSHFactory = SSHUserAuthServer = SSHConnection = Key = SSHChannel = \\\n        SSHAgentServer = KnownHostsFile = SSHPublicKeyChecker = ConchUser = \\\n        object\n\nfrom twisted.test.proto_helpers import StringTransport\nfrom twisted.test.iosim import FakeTransport, connect\n\n\nclass AbortableFakeTransport(FakeTransport):\n    \"\"\"\n    A L{FakeTransport} with added C{abortConnection} support.\n    \"\"\"\n    aborted = False\n\n\n    def abortConnection(self):\n        \"\"\"\n        Abort the connection in a fake manner.\n\n        This should really be implemented in the underlying module.\n        \"\"\"\n        self.aborted = True\n\n\n\nclass BrokenExecSession(SSHChannel):\n    \"\"\"\n    L{BrokenExecSession} is a session on which exec requests always fail.\n    \"\"\"\n    def request_exec(self, data):\n        \"\"\"\n        Fail all exec requests.\n\n        @param data: Information about what is being executed.\n        @type data: L{bytes}\n\n        @return: C{0} to indicate failure\n        @rtype: L{int}\n        \"\"\"\n        return 0\n\n\n\nclass WorkingExecSession(SSHChannel):\n    \"\"\"\n    L{WorkingExecSession} is a session on which exec requests always succeed.\n    \"\"\"\n    def request_exec(self, data):\n        \"\"\"\n        Succeed all exec requests.\n\n        @param data: Information about what is being executed.\n        @type data: L{bytes}\n\n        @return: C{1} to indicate success\n        @rtype: L{int}\n        \"\"\"\n        return 1\n\n\n\nclass UnsatisfiedExecSession(SSHChannel):\n    \"\"\"\n    L{UnsatisfiedExecSession} is a session on which exec requests are always\n    delayed indefinitely, never succeeding or failing.\n    \"\"\"\n    def request_exec(self, data):\n        \"\"\"\n        Delay all exec requests indefinitely.\n\n        @param data: Information about what is being executed.\n        @type data: L{bytes}\n\n        @return: A L{Deferred} which will never fire.\n        @rtype: L{Deferred}\n        \"\"\"\n        return Deferred()\n\n\n\nclass TrivialRealm(object):\n    def __init__(self):\n        self.channelLookup = {}\n\n\n    def requestAvatar(self, avatarId, mind, *interfaces):\n        avatar = ConchUser()\n        avatar.channelLookup = self.channelLookup\n        return (IConchUser, avatar, lambda: None)\n\n\n\nclass AddressSpyFactory(Factory):\n    address = None\n\n    def buildProtocol(self, address):\n        self.address = address\n        return Factory.buildProtocol(self, address)\n\n\n\nclass FixedResponseUI(object):\n    def __init__(self, result):\n        self.result = result\n\n\n    def prompt(self, text):\n        return succeed(self.result)\n\n\n    def warn(self, text):\n        pass\n\n\n\nclass FakeClockSSHUserAuthServer(SSHUserAuthServer):\n\n    # Delegate this setting to the factory to simplify tweaking it\n    @property\n    def attemptsBeforeDisconnect(self):\n        \"\"\"\n        Use the C{attemptsBeforeDisconnect} value defined by the factory to make\n        it easier to override.\n        \"\"\"\n        return self.transport.factory.attemptsBeforeDisconnect\n\n\n    @property\n    def clock(self):\n        \"\"\"\n        Use the reactor defined by the factory, rather than the default global\n        reactor, to simplify testing (by allowing an alternate implementation\n        to be supplied by tests).\n        \"\"\"\n        return self.transport.factory.reactor\n\n\n\nclass CommandFactory(SSHFactory):\n    @property\n    def publicKeys(self):\n        return {\n            b'ssh-rsa': Key.fromString(data=publicRSA_openssh)\n            }\n\n\n    @property\n    def privateKeys(self):\n        return {\n            b'ssh-rsa': Key.fromString(data=privateRSA_openssh)\n            }\n\n    services = {\n        b'ssh-userauth': FakeClockSSHUserAuthServer,\n        b'ssh-connection': SSHConnection\n    }\n\n    # Simplify the tests by disconnecting after the first authentication\n    # failure.  One attempt should be sufficient to test authentication success\n    # and failure.  There is an off-by-one in the implementation of this\n    # feature in Conch, so set it to 0 in order to allow 1 attempt.\n    attemptsBeforeDisconnect = 0\n\n\n\n@implementer(IAddress)\nclass MemoryAddress(object):\n    pass\n\n\n\n@implementer(IStreamClientEndpoint)\nclass SingleUseMemoryEndpoint(object):\n    \"\"\"\n    L{SingleUseMemoryEndpoint} is a client endpoint which allows one connection\n    to be set up and then exposes an API for moving around bytes related to\n    that connection.\n\n    @ivar pump: L{None} until a connection is attempted, then a L{IOPump}\n        instance associated with the protocol which is connected.\n    @type pump: L{IOPump}\n    \"\"\"\n    def __init__(self, server):\n        \"\"\"\n        @param server: An L{IProtocol} provider to which the client will be\n            connected.\n        @type server: L{IProtocol} provider\n        \"\"\"\n        self.pump = None\n        self._server = server\n\n\n    def connect(self, factory):\n        if self.pump is not None:\n            raise Exception(\"SingleUseMemoryEndpoint was already used\")\n\n        try:\n            protocol = factory.buildProtocol(MemoryAddress())\n        except:\n            return fail()\n        else:\n            self.pump = connect(\n                self._server, AbortableFakeTransport(\n                    self._server, isServer=True),\n                protocol, AbortableFakeTransport(protocol, isServer=False))\n            return succeed(protocol)\n\n\n\nclass SSHCommandClientEndpointTestsMixin(object):\n    \"\"\"\n    Tests for L{SSHCommandClientEndpoint}, an L{IStreamClientEndpoint}\n    implementations which connects a protocol with the stdin and stdout of a\n    command running in an SSH session.\n\n    These tests apply to L{SSHCommandClientEndpoint} whether it is constructed\n    using L{SSHCommandClientEndpoint.existingConnection} or\n    L{SSHCommandClientEndpoint.newConnection}.\n\n    Subclasses must override L{create}, L{assertClientTransportState}, and\n    L{finishConnection}.\n    \"\"\"\n    def setUp(self):\n        self.hostname = b\"ssh.example.com\"\n        self.port = 42022\n        self.user = b\"user\"\n        self.password = b\"password\"\n        self.reactor = MemoryReactorClock()\n        self.realm = TrivialRealm()\n        self.portal = Portal(self.realm)\n        self.passwdDB = InMemoryUsernamePasswordDatabaseDontUse()\n        self.passwdDB.addUser(self.user, self.password)\n        self.portal.registerChecker(self.passwdDB)\n        self.factory = CommandFactory()\n        self.factory.reactor = self.reactor\n        self.factory.portal = self.portal\n        self.factory.doStart()\n        self.addCleanup(self.factory.doStop)\n\n        self.clientAddress = IPv4Address(\"TCP\", \"10.0.0.1\", 12345)\n        self.serverAddress = IPv4Address(\"TCP\", \"192.168.100.200\", 54321)\n\n\n    def create(self):\n        \"\"\"\n        Create and return a new L{SSHCommandClientEndpoint} to be tested.\n        Override this to implement creation in an interesting way the endpoint.\n        \"\"\"\n        raise NotImplementedError(\n            \"%r did not implement create\" % (self.__class__.__name__,))\n\n\n    def assertClientTransportState(self, client, immediateClose):\n        \"\"\"\n        Make an assertion about the connectedness of the given protocol's\n        transport.  Override this to implement either a check for the\n        connection still being open or having been closed as appropriate.\n\n        @param client: The client whose state is being checked.\n\n        @param immediateClose: Boolean indicating whether the connection was\n            closed immediately or not.\n        \"\"\"\n        raise NotImplementedError(\n            \"%r did not implement assertClientTransportState\" % (\n                self.__class__.__name__,))\n\n\n    def finishConnection(self):\n        \"\"\"\n        Do any remaining work necessary to complete an in-memory connection\n        attempted initiated using C{self.reactor}.\n        \"\"\"\n        raise NotImplementedError(\n            \"%r did not implement finishConnection\" % (\n                self.__class__.__name__,))\n\n\n    def connectedServerAndClient(self, serverFactory, clientFactory):\n        \"\"\"\n        Set up an in-memory connection between protocols created by\n        C{serverFactory} and C{clientFactory}.\n\n        @return: A three-tuple.  The first element is the protocol created by\n            C{serverFactory}.  The second element is the protocol created by\n            C{clientFactory}.  The third element is the L{IOPump} connecting\n            them.\n        \"\"\"\n        clientProtocol = clientFactory.buildProtocol(None)\n        serverProtocol = serverFactory.buildProtocol(None)\n\n        clientTransport = AbortableFakeTransport(\n            clientProtocol, isServer=False, hostAddress=self.clientAddress,\n            peerAddress=self.serverAddress)\n        serverTransport = AbortableFakeTransport(\n            serverProtocol, isServer=True, hostAddress=self.serverAddress,\n            peerAddress=self.clientAddress)\n\n        pump = connect(\n            serverProtocol, serverTransport, clientProtocol, clientTransport)\n        return serverProtocol, clientProtocol, pump\n\n\n    def test_channelOpenFailure(self):\n        \"\"\"\n        If a channel cannot be opened on the authenticated SSH connection, the\n        L{Deferred} returned by L{SSHCommandClientEndpoint.connect} fires with\n        a L{Failure} wrapping the reason given by the server.\n        \"\"\"\n        endpoint = self.create()\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.finishConnection()\n\n        # The server logs the channel open failure - this is expected.\n        errors = self.flushLoggedErrors(ConchError)\n        self.assertIn(\n            'unknown channel', (errors[0].value.data, errors[0].value.value))\n        self.assertEqual(1, len(errors))\n\n        # Now deal with the results on the endpoint side.\n        f = self.failureResultOf(connected)\n        f.trap(ConchError)\n        self.assertEqual(b'unknown channel', f.value.value)\n\n        self.assertClientTransportState(client, False)\n\n\n    def test_execFailure(self):\n        \"\"\"\n        If execution of the command fails, the L{Deferred} returned by\n        L{SSHCommandClientEndpoint.connect} fires with a L{Failure} wrapping\n        the reason given by the server.\n        \"\"\"\n        self.realm.channelLookup[b'session'] = BrokenExecSession\n        endpoint = self.create()\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.finishConnection()\n\n        f = self.failureResultOf(connected)\n        f.trap(ConchError)\n        self.assertEqual('channel request failed', f.value.value)\n\n        self.assertClientTransportState(client, False)\n\n\n    def test_execCancelled(self):\n        \"\"\"\n        If execution of the command is cancelled via the L{Deferred} returned\n        by L{SSHCommandClientEndpoint.connect}, the connection is closed\n        immediately.\n        \"\"\"\n        self.realm.channelLookup[b'session'] = UnsatisfiedExecSession\n        endpoint = self.create()\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n        server, client, pump = self.finishConnection()\n\n        connected.cancel()\n\n        f = self.failureResultOf(connected)\n        f.trap(CancelledError)\n\n        self.assertClientTransportState(client, True)\n\n\n    def test_buildProtocol(self):\n        \"\"\"\n        Once the necessary SSH actions have completed successfully,\n        L{SSHCommandClientEndpoint.connect} uses the factory passed to it to\n        construct a protocol instance by calling its C{buildProtocol} method\n        with an address object representing the SSH connection and command\n        executed.\n        \"\"\"\n        self.realm.channelLookup[b'session'] = WorkingExecSession\n        endpoint = self.create()\n\n        factory = AddressSpyFactory()\n        factory.protocol = Protocol\n\n        endpoint.connect(factory)\n\n        server, client, pump = self.finishConnection()\n\n        self.assertIsInstance(factory.address, SSHCommandAddress)\n        self.assertEqual(server.transport.getHost(), factory.address.server)\n        self.assertEqual(self.user, factory.address.username)\n        self.assertEqual(b\"/bin/ls -l\", factory.address.command)\n\n\n    def test_makeConnection(self):\n        \"\"\"\n        L{SSHCommandClientEndpoint} establishes an SSH connection, creates a\n        channel in it, runs a command in that channel, and uses the protocol's\n        C{makeConnection} to associate it with a protocol representing that\n        command's stdin and stdout.\n        \"\"\"\n        self.realm.channelLookup[b'session'] = WorkingExecSession\n        endpoint = self.create()\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.finishConnection()\n\n        protocol = self.successResultOf(connected)\n        self.assertIsNotNone(protocol.transport)\n\n\n    def test_dataReceived(self):\n        \"\"\"\n        After establishing the connection, when the command on the SSH server\n        produces output, it is delivered to the protocol's C{dataReceived}\n        method.\n        \"\"\"\n        self.realm.channelLookup[b'session'] = WorkingExecSession\n        endpoint = self.create()\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.finishConnection()\n\n        protocol = self.successResultOf(connected)\n        dataReceived = []\n        protocol.dataReceived = dataReceived.append\n\n        # Figure out which channel on the connection this protocol is\n        # associated with so the test can do a write on it.\n        channelId = protocol.transport.id\n\n        server.service.channels[channelId].write(b\"hello, world\")\n        pump.pump()\n        self.assertEqual(b\"hello, world\", b\"\".join(dataReceived))\n\n\n    def test_connectionLost(self):\n        \"\"\"\n        When the command closes the channel, the protocol's C{connectionLost}\n        method is called.\n        \"\"\"\n        self.realm.channelLookup[b'session'] = WorkingExecSession\n        endpoint = self.create()\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.finishConnection()\n\n        protocol = self.successResultOf(connected)\n        connectionLost = []\n        protocol.connectionLost = connectionLost.append\n\n        # Figure out which channel on the connection this protocol is\n        # associated with so the test can do a write on it.\n        channelId = protocol.transport.id\n        server.service.channels[channelId].loseConnection()\n\n        pump.pump()\n        connectionLost[0].trap(ConnectionDone)\n\n        self.assertClientTransportState(client, False)\n\n\n    def _exitStatusTest(self, request, requestArg):\n        \"\"\"\n        Test handling of non-zero exit statuses or exit signals.\n        \"\"\"\n        self.realm.channelLookup[b'session'] = WorkingExecSession\n        endpoint = self.create()\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.finishConnection()\n\n        protocol = self.successResultOf(connected)\n        connectionLost = []\n        protocol.connectionLost = connectionLost.append\n\n        # Figure out which channel on the connection this protocol is\n        # associated with so the test can simulate command exit and\n        # channel close.\n        channelId = protocol.transport.id\n        channel = server.service.channels[channelId]\n\n        server.service.sendRequest(channel, request, requestArg)\n        channel.loseConnection()\n        pump.pump()\n        self.assertClientTransportState(client, False)\n        return connectionLost[0]\n\n\n    def test_zeroExitCode(self):\n        \"\"\"\n        When the command exits with a non-zero status, the protocol's\n        C{connectionLost} method is called with a L{Failure} wrapping an\n        exception which encapsulates that status.\n        \"\"\"\n        exitCode = 0\n        exc = self._exitStatusTest(b'exit-status', pack('>L', exitCode))\n        exc.trap(ConnectionDone)\n\n\n    def test_nonZeroExitStatus(self):\n        \"\"\"\n        When the command exits with a non-zero status, the protocol's\n        C{connectionLost} method is called with a L{Failure} wrapping an\n        exception which encapsulates that status.\n        \"\"\"\n        exitCode = 123\n        signal = None\n        exc = self._exitStatusTest(b'exit-status', pack('>L', exitCode))\n        exc.trap(ProcessTerminated)\n        self.assertEqual(exitCode, exc.value.exitCode)\n        self.assertEqual(signal, exc.value.signal)\n\n\n    def test_nonZeroExitSignal(self):\n        \"\"\"\n        When the command exits with a non-zero signal, the protocol's\n        C{connectionLost} method is called with a L{Failure} wrapping an\n        exception which encapsulates that status.\n\n        Additional packet contents are logged at the C{info} level.\n        \"\"\"\n        logObserver = EventLoggingObserver()\n        globalLogPublisher.addObserver(logObserver)\n        self.addCleanup(globalLogPublisher.removeObserver, logObserver)\n\n        exitCode = None\n        signal = 15\n        # See https://tools.ietf.org/html/rfc4254#section-6.10\n        packet = b\"\".join([\n            common.NS(b'TERM'),     # Signal name (without \"SIG\" prefix);\n                                    # string\n            b'\\x01',                # Core dumped; boolean\n            common.NS(b'message'),  # Error message; string (UTF-8 encoded)\n            common.NS(b'en-US'),    # Language tag; string\n        ])\n        exc = self._exitStatusTest(b'exit-signal', packet)\n        exc.trap(ProcessTerminated)\n        self.assertEqual(exitCode, exc.value.exitCode)\n        self.assertEqual(signal, exc.value.signal)\n\n        logNamespace = \"twisted.conch.endpoints._CommandChannel\"\n        hamcrest.assert_that(\n            logObserver,\n            hamcrest.has_item(\n                hamcrest.has_entries(\n                    {\n                        \"log_level\": hamcrest.equal_to(LogLevel.info),\n                        \"log_namespace\": logNamespace,\n                        \"shortSignalName\": b\"TERM\",\n                        \"coreDumped\": True,\n                        \"errorMessage\": u\"message\",\n                        \"languageTag\": b\"en-US\",\n                    },\n                )))\n\n\n    def record(self, server, protocol, event, noArgs=False):\n        \"\"\"\n        Hook into and record events which happen to C{protocol}.\n\n        @param server: The SSH server protocol over which C{protocol} is\n            running.\n        @type server: L{IProtocol} provider\n\n        @param protocol:\n\n        @param event:\n\n        @param noArgs:\n        \"\"\"\n        # Figure out which channel the test is going to send data over\n        # so we can look for it to arrive at the right place on the server.\n        channelId = protocol.transport.id\n\n        recorder = []\n        if noArgs:\n            f = lambda: recorder.append(None)\n        else:\n            f = recorder.append\n\n        setattr(server.service.channels[channelId], event, f)\n        return recorder\n\n\n    def test_write(self):\n        \"\"\"\n        The transport connected to the protocol has a C{write} method which\n        sends bytes to the input of the command executing on the SSH server.\n        \"\"\"\n        self.realm.channelLookup[b'session'] = WorkingExecSession\n        endpoint = self.create()\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.finishConnection()\n\n        protocol = self.successResultOf(connected)\n\n        dataReceived = self.record(server, protocol, 'dataReceived')\n        protocol.transport.write(b\"hello, world\")\n        pump.pump()\n        self.assertEqual(b\"hello, world\", b\"\".join(dataReceived))\n\n\n    def test_writeSequence(self):\n        \"\"\"\n        The transport connected to the protocol has a C{writeSequence} method which\n        sends bytes to the input of the command executing on the SSH server.\n        \"\"\"\n        self.realm.channelLookup[b'session'] = WorkingExecSession\n        endpoint = self.create()\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.finishConnection()\n\n        protocol = self.successResultOf(connected)\n\n        dataReceived = self.record(server, protocol, 'dataReceived')\n        protocol.transport.writeSequence([b\"hello, world\"])\n        pump.pump()\n        self.assertEqual(b\"hello, world\", b\"\".join(dataReceived))\n\n\n\nclass NewConnectionTests(TestCase, SSHCommandClientEndpointTestsMixin):\n    \"\"\"\n    Tests for L{SSHCommandClientEndpoint} when using the C{newConnection}\n    constructor.\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Configure an SSH server with password authentication enabled for a\n        well-known (to the tests) account.\n        \"\"\"\n        SSHCommandClientEndpointTestsMixin.setUp(self)\n        # Make the server's host key available to be verified by the client.\n        self.hostKeyPath = FilePath(self.mktemp())\n        self.knownHosts = KnownHostsFile(self.hostKeyPath)\n        self.knownHosts.addHostKey(\n            self.hostname, self.factory.publicKeys[b'ssh-rsa'])\n        self.knownHosts.addHostKey(\n            networkString(self.serverAddress.host),\n            self.factory.publicKeys[b'ssh-rsa'])\n        self.knownHosts.save()\n\n\n    def create(self):\n        \"\"\"\n        Create and return a new L{SSHCommandClientEndpoint} using the\n        C{newConnection} constructor.\n        \"\"\"\n        return SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", self.user, self.hostname, self.port,\n            password=self.password, knownHosts=self.knownHosts,\n            ui=FixedResponseUI(False))\n\n\n    def finishConnection(self):\n        \"\"\"\n        Establish the first attempted TCP connection using the SSH server which\n        C{self.factory} can create.\n        \"\"\"\n        return self.connectedServerAndClient(\n            self.factory, self.reactor.tcpClients[0][2])\n\n\n    def loseConnectionToServer(self, server, client, protocol, pump):\n        \"\"\"\n        Lose the connection to a server and pump the L{IOPump} sufficiently for\n        the client to handle the lost connection. Asserts that the client\n        disconnects its transport.\n\n        @param server: The SSH server protocol over which C{protocol} is\n            running.\n        @type server: L{IProtocol} provider\n\n        @param client: The SSH client protocol over which C{protocol} is\n            running.\n        @type client: L{IProtocol} provider\n\n        @param protocol: The protocol created by calling connect on the ssh\n            endpoint under test.\n        @type protocol: L{IProtocol} provider\n\n        @param pump: The L{IOPump} connecting client to server.\n        @type pump: L{IOPump}\n        \"\"\"\n        closed = self.record(server, protocol, 'closed', noArgs=True)\n        protocol.transport.loseConnection()\n        pump.pump()\n        self.assertEqual([None], closed)\n\n        # Let the last bit of network traffic flow.  This lets the server's\n        # close acknowledgement through, at which point the client can close\n        # the overall SSH connection.\n        pump.pump()\n\n        # Given that the client transport is disconnecting, report the\n        # disconnect from up to the ssh protocol.\n        client.transport.reportDisconnect()\n\n\n    def assertClientTransportState(self, client, immediateClose):\n        \"\"\"\n        Assert that the transport for the given protocol has been disconnected.\n        L{SSHCommandClientEndpoint.newConnection} creates a new dedicated SSH\n        connection and cleans it up after the command exits.\n        \"\"\"\n        # Nothing useful can be done with the connection at this point, so the\n        # endpoint should close it.\n        if immediateClose:\n            self.assertTrue(client.transport.aborted)\n        else:\n            self.assertTrue(client.transport.disconnecting)\n\n\n    def test_interface(self):\n        \"\"\"\n        L{SSHCommandClientEndpoint} instances provide L{IStreamClientEndpoint}.\n        \"\"\"\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"dummy command\", b\"dummy user\",\n            self.hostname, self.port)\n        self.assertTrue(verifyObject(IStreamClientEndpoint, endpoint))\n\n\n    def test_defaultPort(self):\n        \"\"\"\n        L{SSHCommandClientEndpoint} uses the default port number for SSH when\n        the C{port} argument is not specified.\n        \"\"\"\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"dummy command\", b\"dummy user\", self.hostname)\n        self.assertEqual(22, endpoint._creator.port)\n\n\n    def test_specifiedPort(self):\n        \"\"\"\n        L{SSHCommandClientEndpoint} uses the C{port} argument if specified.\n        \"\"\"\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"dummy command\", b\"dummy user\",\n            self.hostname, port=2222)\n        self.assertEqual(2222, endpoint._creator.port)\n\n\n    def test_destination(self):\n        \"\"\"\n        L{SSHCommandClientEndpoint} uses the L{IReactorTCP} passed to it to\n        attempt a connection to the host/port address also passed to it.\n        \"\"\"\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", self.user, self.hostname, self.port,\n            password=self.password, knownHosts=self.knownHosts,\n            ui=FixedResponseUI(False))\n        factory = Factory()\n        factory.protocol = Protocol\n        endpoint.connect(factory)\n\n        host, port, factory, timeout, bindAddress = self.reactor.tcpClients[0]\n        self.assertEqual(self.hostname, networkString(host))\n        self.assertEqual(self.port, port)\n        self.assertEqual(1, len(self.reactor.tcpClients))\n\n\n    def test_connectionFailed(self):\n        \"\"\"\n        If a connection cannot be established, the L{Deferred} returned by\n        L{SSHCommandClientEndpoint.connect} fires with a L{Failure}\n        representing the reason for the connection setup failure.\n        \"\"\"\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", b\"dummy user\",\n            self.hostname, self.port, knownHosts=self.knownHosts,\n            ui=FixedResponseUI(False))\n        factory = Factory()\n        factory.protocol = Protocol\n        d = endpoint.connect(factory)\n\n        factory = self.reactor.tcpClients[0][2]\n        factory.clientConnectionFailed(None, Failure(ConnectionRefusedError()))\n\n        self.failureResultOf(d).trap(ConnectionRefusedError)\n\n\n    def test_userRejectedHostKey(self):\n        \"\"\"\n        If the L{KnownHostsFile} instance used to construct\n        L{SSHCommandClientEndpoint} rejects the SSH public key presented by the\n        server, the L{Deferred} returned by L{SSHCommandClientEndpoint.connect}\n        fires with a L{Failure} wrapping L{UserRejectedKey}.\n        \"\"\"\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", b\"dummy user\",\n            self.hostname, self.port, knownHosts=KnownHostsFile(self.mktemp()),\n            ui=FixedResponseUI(False))\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.connectedServerAndClient(\n            self.factory, self.reactor.tcpClients[0][2])\n\n        f = self.failureResultOf(connected)\n        f.trap(UserRejectedKey)\n\n\n    def test_mismatchedHostKey(self):\n        \"\"\"\n        If the SSH public key presented by the SSH server does not match the\n        previously remembered key, as reported by the L{KnownHostsFile}\n        instance use to construct the endpoint, for that server, the\n        L{Deferred} returned by L{SSHCommandClientEndpoint.connect} fires with\n        a L{Failure} wrapping L{HostKeyChanged}.\n        \"\"\"\n        firstKey = Key.fromString(privateRSA_openssh).public()\n        knownHosts = KnownHostsFile(FilePath(self.mktemp()))\n        knownHosts.addHostKey(\n            networkString(self.serverAddress.host), firstKey)\n        # Add a different RSA key with the same hostname\n        differentKey = Key.fromString(privateRSA_openssh_encrypted_aes,\n                                      passphrase=b'testxp').public()\n        knownHosts.addHostKey(self.hostname, differentKey)\n\n        # The UI may answer true to any questions asked of it; they should\n        # make no difference, since a *mismatched* key is not even optionally\n        # allowed to complete a connection.\n        ui = FixedResponseUI(True)\n\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", b\"dummy user\",\n            self.hostname, self.port, password=b\"dummy password\",\n            knownHosts=knownHosts, ui=ui)\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.connectedServerAndClient(\n            self.factory, self.reactor.tcpClients[0][2])\n\n        f = self.failureResultOf(connected)\n        f.trap(HostKeyChanged)\n\n\n    def test_connectionClosedBeforeSecure(self):\n        \"\"\"\n        If the connection closes at any point before the SSH transport layer\n        has finished key exchange (ie, gotten to the point where we may attempt\n        to authenticate), the L{Deferred} returned by\n        L{SSHCommandClientEndpoint.connect} fires with a L{Failure} wrapping\n        the reason for the lost connection.\n        \"\"\"\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", b\"dummy user\",\n            self.hostname, self.port, knownHosts=self.knownHosts,\n            ui=FixedResponseUI(False))\n\n        factory = Factory()\n        factory.protocol = Protocol\n        d = endpoint.connect(factory)\n\n        transport = StringTransport()\n        factory = self.reactor.tcpClients[0][2]\n        client = factory.buildProtocol(None)\n        client.makeConnection(transport)\n\n        client.connectionLost(Failure(ConnectionDone()))\n        self.failureResultOf(d).trap(ConnectionDone)\n\n\n    def test_connectionCancelledBeforeSecure(self):\n        \"\"\"\n        If the connection is cancelled before the SSH transport layer has\n        finished key exchange (ie, gotten to the point where we may attempt to\n        authenticate), the L{Deferred} returned by\n        L{SSHCommandClientEndpoint.connect} fires with a L{Failure} wrapping\n        L{CancelledError} and the connection is aborted.\n        \"\"\"\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", b\"dummy user\",\n            self.hostname, self.port, knownHosts=self.knownHosts,\n            ui=FixedResponseUI(False))\n\n        factory = Factory()\n        factory.protocol = Protocol\n        d = endpoint.connect(factory)\n\n        transport = AbortableFakeTransport(None, isServer=False)\n        factory = self.reactor.tcpClients[0][2]\n        client = factory.buildProtocol(None)\n        client.makeConnection(transport)\n        d.cancel()\n\n        self.failureResultOf(d).trap(CancelledError)\n        self.assertTrue(transport.aborted)\n        # Make sure the connection closing doesn't result in unexpected\n        # behavior when due to cancellation:\n        client.connectionLost(Failure(ConnectionDone()))\n\n\n    def test_connectionCancelledBeforeConnected(self):\n        \"\"\"\n        If the connection is cancelled before it finishes connecting, the\n        connection attempt is stopped.\n        \"\"\"\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", b\"dummy user\",\n            self.hostname, self.port, knownHosts=self.knownHosts,\n            ui=FixedResponseUI(False))\n\n        factory = Factory()\n        factory.protocol = Protocol\n        d = endpoint.connect(factory)\n        d.cancel()\n        self.failureResultOf(d).trap(ConnectingCancelledError)\n        self.assertTrue(self.reactor.connectors[0].stoppedConnecting)\n\n\n    def test_passwordAuthenticationFailure(self):\n        \"\"\"\n        If the SSH server rejects the password presented during authentication,\n        the L{Deferred} returned by L{SSHCommandClientEndpoint.connect} fires\n        with a L{Failure} wrapping L{AuthenticationFailed}.\n        \"\"\"\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", b\"dummy user\",\n            self.hostname, self.port,  password=b\"dummy password\",\n            knownHosts=self.knownHosts, ui=FixedResponseUI(False))\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.connectedServerAndClient(\n            self.factory, self.reactor.tcpClients[0][2])\n\n        # For security, the server delays password authentication failure\n        # response.  Advance the simulation clock so the client sees the\n        # failure.\n        self.reactor.advance(server.service.passwordDelay)\n\n        # Let the failure response traverse the \"network\"\n        pump.flush()\n\n        f = self.failureResultOf(connected)\n        f.trap(AuthenticationFailed)\n        # XXX Should assert something specific about the arguments of the\n        # exception\n\n        self.assertClientTransportState(client, False)\n\n\n    def setupKeyChecker(self, portal, users):\n        \"\"\"\n        Create an L{ISSHPrivateKey} checker which recognizes C{users} and add it\n        to C{portal}.\n\n        @param portal: A L{Portal} to which to add the checker.\n        @type portal: L{Portal}\n\n        @param users: The users and their keys the checker will recognize.  Keys\n            are byte strings giving user names.  Values are byte strings giving\n            OpenSSH-formatted private keys.\n        @type users: L{dict}\n        \"\"\"\n        mapping = dict([(k,[Key.fromString(v).public()])\n                        for k, v in iteritems(users)])\n        checker = SSHPublicKeyChecker(InMemorySSHKeyDB(mapping))\n        portal.registerChecker(checker)\n\n\n    def test_publicKeyAuthenticationFailure(self):\n        \"\"\"\n        If the SSH server rejects the key pair presented during authentication,\n        the L{Deferred} returned by L{SSHCommandClientEndpoint.connect} fires\n        with a L{Failure} wrapping L{AuthenticationFailed}.\n        \"\"\"\n        badKey = Key.fromString(privateRSA_openssh)\n        self.setupKeyChecker(self.portal, {self.user: privateDSA_openssh})\n\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", self.user,\n            self.hostname, self.port, keys=[badKey],\n            knownHosts=self.knownHosts, ui=FixedResponseUI(False))\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.connectedServerAndClient(\n            self.factory, self.reactor.tcpClients[0][2])\n\n        f = self.failureResultOf(connected)\n        f.trap(AuthenticationFailed)\n        # XXX Should assert something specific about the arguments of the\n        # exception\n\n        # Nothing useful can be done with the connection at this point, so the\n        # endpoint should close it.\n        self.assertTrue(client.transport.disconnecting)\n\n\n    def test_authenticationFallback(self):\n        \"\"\"\n        If the SSH server does not accept any of the specified SSH keys, the\n        specified password is tried.\n        \"\"\"\n        badKey = Key.fromString(privateRSA_openssh)\n        self.setupKeyChecker(self.portal, {self.user: privateDSA_openssh})\n\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", self.user, self.hostname, self.port,\n            keys=[badKey], password=self.password, knownHosts=self.knownHosts,\n            ui=FixedResponseUI(False))\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        # Exercising fallback requires a failed authentication attempt.  Allow\n        # one.\n        self.factory.attemptsBeforeDisconnect += 1\n\n        server, client, pump = self.connectedServerAndClient(\n            self.factory, self.reactor.tcpClients[0][2])\n\n        pump.pump()\n\n        # The server logs the channel open failure - this is expected.\n        errors = self.flushLoggedErrors(ConchError)\n        self.assertIn(\n            'unknown channel', (errors[0].value.data, errors[0].value.value))\n        self.assertEqual(1, len(errors))\n\n        # Now deal with the results on the endpoint side.\n        f = self.failureResultOf(connected)\n        f.trap(ConchError)\n        self.assertEqual(b'unknown channel', f.value.value)\n\n        # Nothing useful can be done with the connection at this point, so the\n        # endpoint should close it.\n        self.assertTrue(client.transport.disconnecting)\n\n\n    def test_publicKeyAuthentication(self):\n        \"\"\"\n        If L{SSHCommandClientEndpoint} is initialized with any private keys, it\n        will try to use them to authenticate with the SSH server.\n        \"\"\"\n        key = Key.fromString(privateDSA_openssh)\n        self.setupKeyChecker(self.portal, {self.user: privateDSA_openssh})\n\n        self.realm.channelLookup[b'session'] = WorkingExecSession\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", self.user, self.hostname, self.port,\n            keys=[key], knownHosts=self.knownHosts, ui=FixedResponseUI(False))\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.connectedServerAndClient(\n            self.factory, self.reactor.tcpClients[0][2])\n\n        protocol = self.successResultOf(connected)\n        self.assertIsNotNone(protocol.transport)\n\n\n    def test_skipPasswordAuthentication(self):\n        \"\"\"\n        If the password is not specified, L{SSHCommandClientEndpoint} doesn't\n        try it as an authentication mechanism.\n        \"\"\"\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", self.user, self.hostname, self.port,\n            knownHosts=self.knownHosts, ui=FixedResponseUI(False))\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.connectedServerAndClient(\n            self.factory, self.reactor.tcpClients[0][2])\n\n        pump.pump()\n\n        # Now deal with the results on the endpoint side.\n        f = self.failureResultOf(connected)\n        f.trap(AuthenticationFailed)\n\n        # Nothing useful can be done with the connection at this point, so the\n        # endpoint should close it.\n        self.assertTrue(client.transport.disconnecting)\n\n\n    def test_agentAuthentication(self):\n        \"\"\"\n        If L{SSHCommandClientEndpoint} is initialized with an\n        L{SSHAgentClient}, the agent is used to authenticate with the SSH\n        server. Once the connection with the SSH server has concluded, the\n        connection to the agent is disconnected.\n        \"\"\"\n        key = Key.fromString(privateRSA_openssh)\n        agentServer = SSHAgentServer()\n        agentServer.factory = Factory()\n        agentServer.factory.keys = {key.blob(): (key, b\"\")}\n\n        self.setupKeyChecker(self.portal, {self.user: privateRSA_openssh})\n\n        agentEndpoint = SingleUseMemoryEndpoint(agentServer)\n        endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", self.user, self.hostname, self.port,\n            knownHosts=self.knownHosts, ui=FixedResponseUI(False),\n            agentEndpoint=agentEndpoint)\n\n        self.realm.channelLookup[b'session'] = WorkingExecSession\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.connectedServerAndClient(\n            self.factory, self.reactor.tcpClients[0][2])\n\n        # Let the agent client talk with the agent server and the ssh client\n        # talk with the ssh server.\n        for i in range(14):\n            agentEndpoint.pump.pump()\n            pump.pump()\n\n        protocol = self.successResultOf(connected)\n        self.assertIsNotNone(protocol.transport)\n\n        # Ensure the connection with the agent is cleaned up after the\n        # connection with the server is lost.\n        self.loseConnectionToServer(server, client, protocol, pump)\n        self.assertTrue(client.transport.disconnecting)\n        self.assertTrue(agentEndpoint.pump.clientIO.disconnecting)\n\n\n    def test_loseConnection(self):\n        \"\"\"\n        The transport connected to the protocol has a C{loseConnection} method\n        which causes the channel in which the command is running to close and\n        the overall connection to be closed.\n        \"\"\"\n        self.realm.channelLookup[b'session'] = WorkingExecSession\n        endpoint = self.create()\n\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = endpoint.connect(factory)\n\n        server, client, pump = self.finishConnection()\n\n        protocol = self.successResultOf(connected)\n        self.loseConnectionToServer(server, client, protocol, pump)\n\n        # Nothing useful can be done with the connection at this point, so the\n        # endpoint should close it.\n        self.assertTrue(client.transport.disconnecting)\n\n\n\nclass ExistingConnectionTests(TestCase, SSHCommandClientEndpointTestsMixin):\n    \"\"\"\n    Tests for L{SSHCommandClientEndpoint} when using the C{existingConnection}\n    constructor.\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Configure an SSH server with password authentication enabled for a\n        well-known (to the tests) account.\n        \"\"\"\n        SSHCommandClientEndpointTestsMixin.setUp(self)\n\n        knownHosts = KnownHostsFile(FilePath(self.mktemp()))\n        knownHosts.addHostKey(\n            self.hostname, self.factory.publicKeys[b'ssh-rsa'])\n        knownHosts.addHostKey(\n            networkString(self.serverAddress.host),\n            self.factory.publicKeys[b'ssh-rsa'])\n\n        self.endpoint = SSHCommandClientEndpoint.newConnection(\n            self.reactor, b\"/bin/ls -l\", self.user, self.hostname, self.port,\n            password=self.password, knownHosts=knownHosts,\n            ui=FixedResponseUI(False))\n\n\n    def create(self):\n        \"\"\"\n        Create and return a new L{SSHCommandClientEndpoint} using the\n        C{existingConnection} constructor.\n        \"\"\"\n        factory = Factory()\n        factory.protocol = Protocol\n        connected = self.endpoint.connect(factory)\n\n        # Please, let me in.  This kinda sucks.\n        channelLookup = self.realm.channelLookup.copy()\n        try:\n            self.realm.channelLookup[b'session'] = WorkingExecSession\n\n            server, client, pump = self.connectedServerAndClient(\n                self.factory, self.reactor.tcpClients[0][2])\n\n        finally:\n            self.realm.channelLookup.clear()\n            self.realm.channelLookup.update(channelLookup)\n\n        self._server = server\n        self._client = client\n        self._pump = pump\n\n        protocol = self.successResultOf(connected)\n        connection = protocol.transport.conn\n        return SSHCommandClientEndpoint.existingConnection(\n            connection, b\"/bin/ls -l\")\n\n\n    def finishConnection(self):\n        \"\"\"\n        Give back the connection established in L{create} over which the new\n        command channel being tested will exchange data.\n        \"\"\"\n        # The connection was set up and the first command channel set up, but\n        # some more I/O needs to happen for the second command channel to be\n        # ready.  Make that I/O happen before giving back the objects.\n        self._pump.pump()\n        self._pump.pump()\n        self._pump.pump()\n        self._pump.pump()\n        return self._server, self._client, self._pump\n\n\n    def assertClientTransportState(self, client, immediateClose):\n        \"\"\"\n        Assert that the transport for the given protocol is still connected.\n        L{SSHCommandClientEndpoint.existingConnection} re-uses an SSH connected\n        created by some other code, so other code is responsible for cleaning\n        it up.\n        \"\"\"\n        self.assertFalse(client.transport.disconnecting)\n        self.assertFalse(client.transport.aborted)\n\n\n\nclass ExistingConnectionHelperTests(TestCase):\n    \"\"\"\n    Tests for L{_ExistingConnectionHelper}.\n    \"\"\"\n    def test_interface(self):\n        \"\"\"\n        L{_ExistingConnectionHelper} implements L{_ISSHConnectionCreator}.\n        \"\"\"\n        self.assertTrue(\n            verifyClass(_ISSHConnectionCreator, _ExistingConnectionHelper))\n\n\n    def test_secureConnection(self):\n        \"\"\"\n        L{_ExistingConnectionHelper.secureConnection} returns a L{Deferred}\n        which fires with whatever object was fed to\n        L{_ExistingConnectionHelper.__init__}.\n        \"\"\"\n        result = object()\n        helper = _ExistingConnectionHelper(result)\n        self.assertIs(\n            result, self.successResultOf(helper.secureConnection()))\n\n\n    def test_cleanupConnectionNotImmediately(self):\n        \"\"\"\n        L{_ExistingConnectionHelper.cleanupConnection} does nothing to the\n        existing connection if called with C{immediate} set to C{False}.\n        \"\"\"\n        helper = _ExistingConnectionHelper(object())\n        # Bit hard to test nothing happens. However, since object() has no\n        # relevant methods or attributes, if the code is incorrect we can\n        # expect an AttributeError.\n        helper.cleanupConnection(object(), False)\n\n\n    def test_cleanupConnectionImmediately(self):\n        \"\"\"\n        L{_ExistingConnectionHelper.cleanupConnection} does nothing to the\n        existing connection if called with C{immediate} set to C{True}.\n        \"\"\"\n        helper = _ExistingConnectionHelper(object())\n        # Bit hard to test nothing happens. However, since object() has no\n        # relevant methods or attributes, if the code is incorrect we can\n        # expect an AttributeError.\n        helper.cleanupConnection(object(), True)\n\n\n\nclass _PTYPath(object):\n    \"\"\"\n    A L{FilePath}-like object which can be opened to create a L{_ReadFile} with\n    certain contents.\n    \"\"\"\n    def __init__(self, contents):\n        \"\"\"\n        @param contents: L{bytes} which will be the contents of the\n            L{_ReadFile} this path can open.\n        \"\"\"\n        self.contents = contents\n\n\n    def open(self, mode):\n        \"\"\"\n        If the mode is r+, return a L{_ReadFile} with the contents given to\n        this path's initializer.\n\n        @raise OSError: If the mode is unsupported.\n\n        @return: A L{_ReadFile} instance\n        \"\"\"\n        if mode == \"rb+\":\n            return _ReadFile(self.contents)\n        raise OSError(ENOSYS, \"Function not implemented\")\n\n\n\nclass NewConnectionHelperTests(TestCase):\n    \"\"\"\n    Tests for L{_NewConnectionHelper}.\n    \"\"\"\n    def test_interface(self):\n        \"\"\"\n        L{_NewConnectionHelper} implements L{_ISSHConnectionCreator}.\n        \"\"\"\n        self.assertTrue(\n            verifyClass(_ISSHConnectionCreator, _NewConnectionHelper))\n\n\n    def test_defaultPath(self):\n        \"\"\"\n        The default I{known_hosts} path is I{~/.ssh/known_hosts}.\n        \"\"\"\n        self.assertEqual(\n            \"~/.ssh/known_hosts\", _NewConnectionHelper._KNOWN_HOSTS)\n\n\n    def test_defaultKnownHosts(self):\n        \"\"\"\n        L{_NewConnectionHelper._knownHosts} is used to create a\n        L{KnownHostsFile} if one is not passed to the initializer.\n        \"\"\"\n        result = object()\n        self.patch(_NewConnectionHelper, '_knownHosts', lambda cls: result)\n\n        helper = _NewConnectionHelper(\n            None, None, None, None, None, None, None, None, None, None)\n\n        self.assertIs(result, helper.knownHosts)\n\n\n    def test_readExisting(self):\n        \"\"\"\n        Existing entries in the I{known_hosts} file are reflected by the\n        L{KnownHostsFile} created by L{_NewConnectionHelper} when none is\n        supplied to it.\n        \"\"\"\n        key = CommandFactory().publicKeys[b'ssh-rsa']\n        path = FilePath(self.mktemp())\n        knownHosts = KnownHostsFile(path)\n        knownHosts.addHostKey(b\"127.0.0.1\", key)\n        knownHosts.save()\n\n        msg(\"Created known_hosts file at %r\" % (path.path,))\n\n        # Unexpand ${HOME} to make sure ~ syntax is respected.\n        home = os.path.expanduser(\"~/\")\n        default = path.path.replace(home, \"~/\")\n        self.patch(_NewConnectionHelper, \"_KNOWN_HOSTS\", default)\n        msg(\"Patched _KNOWN_HOSTS with %r\" % (default,))\n\n        loaded = _NewConnectionHelper._knownHosts()\n        self.assertTrue(loaded.hasHostKey(b\"127.0.0.1\", key))\n\n\n    def test_defaultConsoleUI(self):\n        \"\"\"\n        If L{None} is passed for the C{ui} parameter to\n        L{_NewConnectionHelper}, a L{ConsoleUI} is used.\n        \"\"\"\n        helper = _NewConnectionHelper(\n            None, None, None, None, None, None, None, None, None, None)\n        self.assertIsInstance(helper.ui, ConsoleUI)\n\n\n    def test_ttyConsoleUI(self):\n        \"\"\"\n        If L{None} is passed for the C{ui} parameter to L{_NewConnectionHelper}\n        and /dev/tty is available, the L{ConsoleUI} used is associated with\n        /dev/tty.\n        \"\"\"\n        tty = _PTYPath(b\"yes\")\n        helper = _NewConnectionHelper(\n            None, None, None, None, None, None, None, None, None, None, tty)\n        result = self.successResultOf(helper.ui.prompt(b\"does this work?\"))\n        self.assertTrue(result)\n\n\n    def test_nottyUI(self):\n        \"\"\"\n        If L{None} is passed for the C{ui} parameter to L{_NewConnectionHelper}\n        and /dev/tty is not available, the L{ConsoleUI} used is associated with\n        some file which always produces a C{b\"no\"} response.\n        \"\"\"\n        tty = FilePath(self.mktemp())\n        helper = _NewConnectionHelper(\n            None, None, None, None, None, None, None, None, None, None, tty)\n        result = self.successResultOf(helper.ui.prompt(b\"did this break?\"))\n        self.assertFalse(result)\n\n\n    def test_defaultTTYFilename(self):\n        \"\"\"\n        If not passed the name of a tty in the filesystem,\n        L{_NewConnectionHelper} uses C{b\"/dev/tty\"}.\n        \"\"\"\n        helper = _NewConnectionHelper(\n            None, None, None, None, None, None, None, None, None, None)\n        self.assertEqual(FilePath(b\"/dev/tty\"), helper.tty)\n\n\n    def test_cleanupConnectionNotImmediately(self):\n        \"\"\"\n        L{_NewConnectionHelper.cleanupConnection} closes the transport cleanly\n        if called with C{immediate} set to C{False}.\n        \"\"\"\n        helper = _NewConnectionHelper(\n            None, None, None, None, None, None, None, None, None, None)\n        connection = SSHConnection()\n        connection.transport = StringTransport()\n        helper.cleanupConnection(connection, False)\n        self.assertTrue(connection.transport.disconnecting)\n\n\n    def test_cleanupConnectionImmediately(self):\n        \"\"\"\n        L{_NewConnectionHelper.cleanupConnection} closes the transport with\n        C{abortConnection} if called with C{immediate} set to C{True}.\n        \"\"\"\n        class Abortable:\n            aborted = False\n            def abortConnection(self):\n                \"\"\"\n                Abort the connection.\n                \"\"\"\n                self.aborted = True\n\n        helper = _NewConnectionHelper(\n            None, None, None, None, None, None, None, None, None, None)\n        connection = SSHConnection()\n        connection.transport = SSHClientTransport()\n        connection.transport.transport = Abortable()\n        helper.cleanupConnection(connection, True)\n        self.assertTrue(connection.transport.transport.aborted)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_filetransfer.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_filetransfer -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE file for details.\n\n\"\"\"\nTests for L{twisted.conch.ssh.filetransfer}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport os\nimport re\nimport struct\n\nfrom twisted.python.reflect import requireModule\nfrom twisted.trial import unittest\n\ncryptography = requireModule(\"cryptography\")\nunix = requireModule(\"twisted.conch.unix\")\n\nif cryptography:\n    from twisted.conch import avatar\n    from twisted.conch.ssh import common, connection, filetransfer, session\nelse:\n    class avatar:\n        class ConchUser: pass\n\nfrom twisted.internet import defer\nfrom twisted.protocols import loopback\nfrom twisted.python import components\nfrom twisted.python.compat import long, _PY37PLUS\nfrom twisted.python.filepath import FilePath\n\n\nclass TestAvatar(avatar.ConchUser):\n    def __init__(self):\n        avatar.ConchUser.__init__(self)\n        self.channelLookup[b'session'] = session.SSHSession\n        self.subsystemLookup[b'sftp'] = filetransfer.FileTransferServer\n\n    def _runAsUser(self, f, *args, **kw):\n        try:\n            f = iter(f)\n        except TypeError:\n            f = [(f, args, kw)]\n        for i in f:\n            func = i[0]\n            args = len(i)>1 and i[1] or ()\n            kw = len(i)>2 and i[2] or {}\n            r = func(*args, **kw)\n        return r\n\n\nclass FileTransferTestAvatar(TestAvatar):\n\n    def __init__(self, homeDir):\n        TestAvatar.__init__(self)\n        self.homeDir = homeDir\n\n    def getHomeDir(self):\n        return FilePath(os.getcwd()).preauthChild(self.homeDir.path)\n\n\nclass ConchSessionForTestAvatar:\n\n    def __init__(self, avatar):\n        self.avatar = avatar\n\nif unix:\n    if not hasattr(unix, 'SFTPServerForUnixConchUser'):\n        # unix should either be a fully working module, or None.  I'm not sure\n        # how this happens, but on win32 it does.  Try to cope.  --spiv.\n        import warnings\n        warnings.warn((\"twisted.conch.unix imported %r, \"\n                       \"but doesn't define SFTPServerForUnixConchUser'\")\n                      % (unix,))\n        unix = None\n    else:\n        class FileTransferForTestAvatar(unix.SFTPServerForUnixConchUser):\n\n            def gotVersion(self, version, otherExt):\n                return {b'conchTest' : b'ext data'}\n\n            def extendedRequest(self, extName, extData):\n                if extName == b'testExtendedRequest':\n                    return b'bar'\n                raise NotImplementedError\n\n        components.registerAdapter(FileTransferForTestAvatar,\n                                   TestAvatar,\n                                   filetransfer.ISFTPServer)\n\nclass SFTPTestBase(unittest.TestCase):\n\n    def setUp(self):\n        self.testDir = FilePath(self.mktemp())\n        # Give the testDir another level so we can safely \"cd ..\" from it in\n        # tests.\n        self.testDir = self.testDir.child('extra')\n        self.testDir.child('testDirectory').makedirs(True)\n\n        with self.testDir.child('testfile1').open(mode='wb') as f:\n            f.write(b'a'*10+b'b'*10)\n            with open('/dev/urandom', 'rb') as f2:\n                f.write(f2.read(1024*64)) # random data\n        self.testDir.child('testfile1').chmod(0o644)\n        with self.testDir.child('testRemoveFile').open(mode='wb') as f:\n            f.write(b'a')\n        with self.testDir.child('testRenameFile').open(mode='wb') as f:\n            f.write(b'a')\n        with self.testDir.child('.testHiddenFile').open(mode='wb') as f:\n            f.write(b'a')\n\n\nclass OurServerOurClientTests(SFTPTestBase):\n\n    if not unix:\n        skip = \"can't run on non-posix computers\"\n\n    def setUp(self):\n        SFTPTestBase.setUp(self)\n\n        self.avatar = FileTransferTestAvatar(self.testDir)\n        self.server = filetransfer.FileTransferServer(avatar=self.avatar)\n        clientTransport = loopback.LoopbackRelay(self.server)\n\n        self.client = filetransfer.FileTransferClient()\n        self._serverVersion = None\n        self._extData = None\n        def _(serverVersion, extData):\n            self._serverVersion = serverVersion\n            self._extData = extData\n        self.client.gotServerVersion = _\n        serverTransport = loopback.LoopbackRelay(self.client)\n        self.client.makeConnection(clientTransport)\n        self.server.makeConnection(serverTransport)\n\n        self.clientTransport = clientTransport\n        self.serverTransport = serverTransport\n\n        self._emptyBuffers()\n\n\n    def _emptyBuffers(self):\n        while self.serverTransport.buffer or self.clientTransport.buffer:\n            self.serverTransport.clearBuffer()\n            self.clientTransport.clearBuffer()\n\n\n    def tearDown(self):\n        self.serverTransport.loseConnection()\n        self.clientTransport.loseConnection()\n        self.serverTransport.clearBuffer()\n        self.clientTransport.clearBuffer()\n\n\n    def test_serverVersion(self):\n        self.assertEqual(self._serverVersion, 3)\n        self.assertEqual(self._extData, {b'conchTest': b'ext data'})\n\n\n    def test_interface_implementation(self):\n        \"\"\"\n        It implements the ISFTPServer interface.\n        \"\"\"\n        self.assertTrue(\n            filetransfer.ISFTPServer.providedBy(self.server.client),\n            \"ISFTPServer not provided by %r\" % (self.server.client,))\n\n\n    def test_openedFileClosedWithConnection(self):\n        \"\"\"\n        A file opened with C{openFile} is close when the connection is lost.\n        \"\"\"\n        d = self.client.openFile(b\"testfile1\", filetransfer.FXF_READ |\n                                 filetransfer.FXF_WRITE, {})\n        self._emptyBuffers()\n\n        oldClose = os.close\n        closed = []\n        def close(fd):\n            closed.append(fd)\n            oldClose(fd)\n\n        self.patch(os, \"close\", close)\n\n        def _fileOpened(openFile):\n            fd = self.server.openFiles[openFile.handle[4:]].fd\n            self.serverTransport.loseConnection()\n            self.clientTransport.loseConnection()\n            self.serverTransport.clearBuffer()\n            self.clientTransport.clearBuffer()\n            self.assertEqual(self.server.openFiles, {})\n            self.assertIn(fd, closed)\n\n        d.addCallback(_fileOpened)\n        return d\n\n\n    def test_openedDirectoryClosedWithConnection(self):\n        \"\"\"\n        A directory opened with C{openDirectory} is close when the connection\n        is lost.\n        \"\"\"\n        d = self.client.openDirectory('')\n        self._emptyBuffers()\n\n        def _getFiles(openDir):\n            self.serverTransport.loseConnection()\n            self.clientTransport.loseConnection()\n            self.serverTransport.clearBuffer()\n            self.clientTransport.clearBuffer()\n            self.assertEqual(self.server.openDirs, {})\n\n        d.addCallback(_getFiles)\n        return d\n\n\n    def test_openFileIO(self):\n        d = self.client.openFile(b\"testfile1\", filetransfer.FXF_READ |\n                                 filetransfer.FXF_WRITE, {})\n        self._emptyBuffers()\n\n        def _fileOpened(openFile):\n            self.assertEqual(openFile, filetransfer.ISFTPFile(openFile))\n            d = _readChunk(openFile)\n            d.addCallback(_writeChunk, openFile)\n            return d\n\n        def _readChunk(openFile):\n            d = openFile.readChunk(0, 20)\n            self._emptyBuffers()\n            d.addCallback(self.assertEqual, b'a'*10 + b'b'*10)\n            return d\n\n        def _writeChunk(_, openFile):\n            d = openFile.writeChunk(20, b'c'*10)\n            self._emptyBuffers()\n            d.addCallback(_readChunk2, openFile)\n            return d\n\n        def _readChunk2(_, openFile):\n            d = openFile.readChunk(0, 30)\n            self._emptyBuffers()\n            d.addCallback(self.assertEqual, b'a'*10 + b'b'*10 + b'c'*10)\n            return d\n\n        d.addCallback(_fileOpened)\n        return d\n\n\n    def test_closedFileGetAttrs(self):\n        d = self.client.openFile(b\"testfile1\", filetransfer.FXF_READ |\n                                 filetransfer.FXF_WRITE, {})\n        self._emptyBuffers()\n\n        def _getAttrs(_, openFile):\n            d = openFile.getAttrs()\n            self._emptyBuffers()\n            return d\n\n        def _err(f):\n            self.flushLoggedErrors()\n            return f\n\n        def _close(openFile):\n            d = openFile.close()\n            self._emptyBuffers()\n            d.addCallback(_getAttrs, openFile)\n            d.addErrback(_err)\n            return self.assertFailure(d, filetransfer.SFTPError)\n\n        d.addCallback(_close)\n        return d\n\n\n    def test_openFileAttributes(self):\n        d = self.client.openFile(b\"testfile1\", filetransfer.FXF_READ |\n                                 filetransfer.FXF_WRITE, {})\n        self._emptyBuffers()\n\n        def _getAttrs(openFile):\n            d = openFile.getAttrs()\n            self._emptyBuffers()\n            d.addCallback(_getAttrs2)\n            return d\n\n        def _getAttrs2(attrs1):\n            d = self.client.getAttrs(b'testfile1')\n            self._emptyBuffers()\n            d.addCallback(self.assertEqual, attrs1)\n            return d\n\n        return d.addCallback(_getAttrs)\n\n\n    def test_openFileSetAttrs(self):\n        # XXX test setAttrs\n        # Ok, how about this for a start?  It caught a bug :)  -- spiv.\n        d = self.client.openFile(b\"testfile1\", filetransfer.FXF_READ |\n                                 filetransfer.FXF_WRITE, {})\n        self._emptyBuffers()\n\n        def _getAttrs(openFile):\n            d = openFile.getAttrs()\n            self._emptyBuffers()\n            d.addCallback(_setAttrs)\n            return d\n\n        def _setAttrs(attrs):\n            attrs['atime'] = 0\n            d = self.client.setAttrs(b'testfile1', attrs)\n            self._emptyBuffers()\n            d.addCallback(_getAttrs2)\n            d.addCallback(self.assertEqual, attrs)\n            return d\n\n        def _getAttrs2(_):\n            d = self.client.getAttrs(b'testfile1')\n            self._emptyBuffers()\n            return d\n\n        d.addCallback(_getAttrs)\n        return d\n\n\n    def test_openFileExtendedAttributes(self):\n        \"\"\"\n        Check that L{filetransfer.FileTransferClient.openFile} can send\n        extended attributes, that should be extracted server side. By default,\n        they are ignored, so we just verify they are correctly parsed.\n        \"\"\"\n        savedAttributes = {}\n        oldOpenFile = self.server.client.openFile\n        def openFile(filename, flags, attrs):\n            savedAttributes.update(attrs)\n            return oldOpenFile(filename, flags, attrs)\n        self.server.client.openFile = openFile\n\n        d = self.client.openFile(b\"testfile1\", filetransfer.FXF_READ |\n                filetransfer.FXF_WRITE, {\"ext_foo\": b\"bar\"})\n        self._emptyBuffers()\n\n        def check(ign):\n            self.assertEqual(savedAttributes, {\"ext_foo\": b\"bar\"})\n\n        return d.addCallback(check)\n\n\n    def test_removeFile(self):\n        d = self.client.getAttrs(b\"testRemoveFile\")\n        self._emptyBuffers()\n\n        def _removeFile(ignored):\n            d = self.client.removeFile(b\"testRemoveFile\")\n            self._emptyBuffers()\n            return d\n\n        d.addCallback(_removeFile)\n        d.addCallback(_removeFile)\n        return self.assertFailure(d, filetransfer.SFTPError)\n\n\n    def test_renameFile(self):\n        d = self.client.getAttrs(b\"testRenameFile\")\n        self._emptyBuffers()\n\n        def _rename(attrs):\n            d = self.client.renameFile(b\"testRenameFile\", b\"testRenamedFile\")\n            self._emptyBuffers()\n            d.addCallback(_testRenamed, attrs)\n            return d\n\n        def _testRenamed(_, attrs):\n            d = self.client.getAttrs(b\"testRenamedFile\")\n            self._emptyBuffers()\n            d.addCallback(self.assertEqual, attrs)\n\n        return d.addCallback(_rename)\n\n\n    def test_directoryBad(self):\n        d = self.client.getAttrs(b\"testMakeDirectory\")\n        self._emptyBuffers()\n        return self.assertFailure(d, filetransfer.SFTPError)\n\n\n    def test_directoryCreation(self):\n        d = self.client.makeDirectory(b\"testMakeDirectory\", {})\n        self._emptyBuffers()\n\n        def _getAttrs(_):\n            d = self.client.getAttrs(b\"testMakeDirectory\")\n            self._emptyBuffers()\n            return d\n\n        # XXX not until version 4/5\n        # self.assertEqual(filetransfer.FILEXFER_TYPE_DIRECTORY&attrs['type'],\n        #                     filetransfer.FILEXFER_TYPE_DIRECTORY)\n\n        def _removeDirectory(_):\n            d = self.client.removeDirectory(b\"testMakeDirectory\")\n            self._emptyBuffers()\n            return d\n\n        d.addCallback(_getAttrs)\n        d.addCallback(_removeDirectory)\n        d.addCallback(_getAttrs)\n        return self.assertFailure(d, filetransfer.SFTPError)\n\n\n    def test_openDirectory(self):\n        d = self.client.openDirectory(b'')\n        self._emptyBuffers()\n        files = []\n\n        def _getFiles(openDir):\n            def append(f):\n                files.append(f)\n                return openDir\n            d = defer.maybeDeferred(openDir.next)\n            self._emptyBuffers()\n            d.addCallback(append)\n            d.addCallback(_getFiles)\n            d.addErrback(_close, openDir)\n            return d\n\n        def _checkFiles(ignored):\n            fs = list(list(zip(*files))[0])\n            fs.sort()\n            self.assertEqual(fs,\n                                 [b'.testHiddenFile', b'testDirectory',\n                                  b'testRemoveFile', b'testRenameFile',\n                                  b'testfile1'])\n\n        def _close(_, openDir):\n            d = openDir.close()\n            self._emptyBuffers()\n            return d\n\n        d.addCallback(_getFiles)\n        d.addCallback(_checkFiles)\n        return d\n\n\n    def test_linkDoesntExist(self):\n        d = self.client.getAttrs(b'testLink')\n        self._emptyBuffers()\n        return self.assertFailure(d, filetransfer.SFTPError)\n\n\n    def test_linkSharesAttrs(self):\n        d = self.client.makeLink(b'testLink', b'testfile1')\n        self._emptyBuffers()\n\n        def _getFirstAttrs(_):\n            d = self.client.getAttrs(b'testLink', 1)\n            self._emptyBuffers()\n            return d\n\n        def _getSecondAttrs(firstAttrs):\n            d = self.client.getAttrs(b'testfile1')\n            self._emptyBuffers()\n            d.addCallback(self.assertEqual, firstAttrs)\n            return d\n\n        d.addCallback(_getFirstAttrs)\n        return d.addCallback(_getSecondAttrs)\n\n\n    def test_linkPath(self):\n        d = self.client.makeLink(b'testLink', b'testfile1')\n        self._emptyBuffers()\n\n        def _readLink(_):\n            d = self.client.readLink(b'testLink')\n            self._emptyBuffers()\n            testFile = FilePath(os.getcwd()).preauthChild(self.testDir.path)\n            testFile = testFile.child('testfile1')\n            d.addCallback(\n                self.assertEqual,\n                testFile.path)\n            return d\n\n        def _realPath(_):\n            d = self.client.realPath(b'testLink')\n            self._emptyBuffers()\n            testLink = FilePath(os.getcwd()).preauthChild(self.testDir.path)\n            testLink = testLink.child('testfile1')\n            d.addCallback(\n                self.assertEqual,\n                testLink.path)\n            return d\n\n        d.addCallback(_readLink)\n        d.addCallback(_realPath)\n        return d\n\n\n    def test_extendedRequest(self):\n        d = self.client.extendedRequest(b'testExtendedRequest', b'foo')\n        self._emptyBuffers()\n        d.addCallback(self.assertEqual, b'bar')\n        d.addCallback(self._cbTestExtendedRequest)\n        return d\n\n\n    def _cbTestExtendedRequest(self, ignored):\n        d = self.client.extendedRequest(b'testBadRequest', b'')\n        self._emptyBuffers()\n        return self.assertFailure(d, NotImplementedError)\n\n\n    @defer.inlineCallbacks\n    def test_openDirectoryIterator(self):\n        \"\"\"\n        Check that the object returned by\n        L{filetransfer.FileTransferClient.openDirectory} can be used\n        as an iterator.\n        \"\"\"\n\n        # This function is a little more complicated than it would be\n        # normally, since we need to call _emptyBuffers() after\n        # creating any SSH-related Deferreds, but before waiting on\n        # them via yield.\n\n        d = self.client.openDirectory(b'')\n        self._emptyBuffers()\n        openDir = yield d\n\n        filenames = set()\n        try:\n            for f in openDir:\n                self._emptyBuffers()\n                (filename, _, fileattrs) = yield f\n                filenames.add(filename)\n        finally:\n            d = openDir.close()\n            self._emptyBuffers()\n            yield d\n\n        self._emptyBuffers()\n\n        self.assertEqual(filenames,\n                         set([b'.testHiddenFile', b'testDirectory',\n                              b'testRemoveFile', b'testRenameFile',\n                              b'testfile1']))\n\n\n    if _PY37PLUS:\n        test_openDirectoryIterator.skip = (\n            \"Broken by PEP 479 and deprecated.\")\n\n\n    @defer.inlineCallbacks\n    def test_openDirectoryIteratorDeprecated(self):\n        \"\"\"\n        Using client.openDirectory as an iterator is deprecated.\n        \"\"\"\n        d = self.client.openDirectory(b'')\n        self._emptyBuffers()\n        openDir = yield d\n        openDir.next()\n\n        warnings = self.flushWarnings()\n        message = (\n            'Using twisted.conch.ssh.filetransfer.ClientDirectory'\n            ' as an iterator was deprecated in Twisted 18.9.0.'\n            )\n        self.assertEqual(1, len(warnings))\n        self.assertEqual(DeprecationWarning, warnings[0]['category'])\n        self.assertEqual(message, warnings[0]['message'])\n\n\n\nclass FakeConn:\n    def sendClose(self, channel):\n        pass\n\n\nclass FileTransferCloseTests(unittest.TestCase):\n\n    if not unix:\n        skip = \"can't run on non-posix computers\"\n\n    def setUp(self):\n        self.avatar = TestAvatar()\n\n    def buildServerConnection(self):\n        # make a server connection\n        conn = connection.SSHConnection()\n        # server connections have a 'self.transport.avatar'.\n        class DummyTransport:\n            def __init__(self):\n                self.transport = self\n            def sendPacket(self, kind, data):\n                pass\n            def logPrefix(self):\n                return 'dummy transport'\n        conn.transport = DummyTransport()\n        conn.transport.avatar = self.avatar\n        return conn\n\n\n    def interceptConnectionLost(self, sftpServer):\n        self.connectionLostFired = False\n        origConnectionLost = sftpServer.connectionLost\n        def connectionLost(reason):\n            self.connectionLostFired = True\n            origConnectionLost(reason)\n        sftpServer.connectionLost = connectionLost\n\n\n    def assertSFTPConnectionLost(self):\n        self.assertTrue(self.connectionLostFired,\n                        \"sftpServer's connectionLost was not called\")\n\n\n    def test_sessionClose(self):\n        \"\"\"\n        Closing a session should notify an SFTP subsystem launched by that\n        session.\n        \"\"\"\n        # make a session\n        testSession = session.SSHSession(conn=FakeConn(), avatar=self.avatar)\n\n        # start an SFTP subsystem on the session\n        testSession.request_subsystem(common.NS(b'sftp'))\n        sftpServer = testSession.client.transport.proto\n\n        # intercept connectionLost so we can check that it's called\n        self.interceptConnectionLost(sftpServer)\n\n        # close session\n        testSession.closeReceived()\n\n        self.assertSFTPConnectionLost()\n\n\n    def test_clientClosesChannelOnConnnection(self):\n        \"\"\"\n        A client sending CHANNEL_CLOSE should trigger closeReceived on the\n        associated channel instance.\n        \"\"\"\n        conn = self.buildServerConnection()\n\n        # somehow get a session\n        packet = common.NS(b'session') + struct.pack('>L', 0) * 3\n        conn.ssh_CHANNEL_OPEN(packet)\n        sessionChannel = conn.channels[0]\n\n        sessionChannel.request_subsystem(common.NS(b'sftp'))\n        sftpServer = sessionChannel.client.transport.proto\n        self.interceptConnectionLost(sftpServer)\n\n        # intercept closeReceived\n        self.interceptConnectionLost(sftpServer)\n\n        # close the connection\n        conn.ssh_CHANNEL_CLOSE(struct.pack('>L', 0))\n\n        self.assertSFTPConnectionLost()\n\n\n    def test_stopConnectionServiceClosesChannel(self):\n        \"\"\"\n        Closing an SSH connection should close all sessions within it.\n        \"\"\"\n        conn = self.buildServerConnection()\n\n        # somehow get a session\n        packet = common.NS(b'session') + struct.pack('>L', 0) * 3\n        conn.ssh_CHANNEL_OPEN(packet)\n        sessionChannel = conn.channels[0]\n\n        sessionChannel.request_subsystem(common.NS(b'sftp'))\n        sftpServer = sessionChannel.client.transport.proto\n        self.interceptConnectionLost(sftpServer)\n\n        # close the connection\n        conn.serviceStopped()\n\n        self.assertSFTPConnectionLost()\n\n\n\nclass ConstantsTests(unittest.TestCase):\n    \"\"\"\n    Tests for the constants used by the SFTP protocol implementation.\n\n    @ivar filexferSpecExcerpts: Excerpts from the\n        draft-ietf-secsh-filexfer-02.txt (draft) specification of the SFTP\n        protocol.  There are more recent drafts of the specification, but this\n        one describes version 3, which is what conch (and OpenSSH) implements.\n    \"\"\"\n    if not cryptography:\n        skip = \"Cannot run without cryptography\"\n\n    filexferSpecExcerpts = [\n        \"\"\"\n           The following values are defined for packet types.\n\n                #define SSH_FXP_INIT                1\n                #define SSH_FXP_VERSION             2\n                #define SSH_FXP_OPEN                3\n                #define SSH_FXP_CLOSE               4\n                #define SSH_FXP_READ                5\n                #define SSH_FXP_WRITE               6\n                #define SSH_FXP_LSTAT               7\n                #define SSH_FXP_FSTAT               8\n                #define SSH_FXP_SETSTAT             9\n                #define SSH_FXP_FSETSTAT           10\n                #define SSH_FXP_OPENDIR            11\n                #define SSH_FXP_READDIR            12\n                #define SSH_FXP_REMOVE             13\n                #define SSH_FXP_MKDIR              14\n                #define SSH_FXP_RMDIR              15\n                #define SSH_FXP_REALPATH           16\n                #define SSH_FXP_STAT               17\n                #define SSH_FXP_RENAME             18\n                #define SSH_FXP_READLINK           19\n                #define SSH_FXP_SYMLINK            20\n                #define SSH_FXP_STATUS            101\n                #define SSH_FXP_HANDLE            102\n                #define SSH_FXP_DATA              103\n                #define SSH_FXP_NAME              104\n                #define SSH_FXP_ATTRS             105\n                #define SSH_FXP_EXTENDED          200\n                #define SSH_FXP_EXTENDED_REPLY    201\n\n           Additional packet types should only be defined if the protocol\n           version number (see Section ``Protocol Initialization'') is\n           incremented, and their use MUST be negotiated using the version\n           number.  However, the SSH_FXP_EXTENDED and SSH_FXP_EXTENDED_REPLY\n           packets can be used to implement vendor-specific extensions.  See\n           Section ``Vendor-Specific-Extensions'' for more details.\n        \"\"\",\n        \"\"\"\n            The flags bits are defined to have the following values:\n\n                #define SSH_FILEXFER_ATTR_SIZE          0x00000001\n                #define SSH_FILEXFER_ATTR_UIDGID        0x00000002\n                #define SSH_FILEXFER_ATTR_PERMISSIONS   0x00000004\n                #define SSH_FILEXFER_ATTR_ACMODTIME     0x00000008\n                #define SSH_FILEXFER_ATTR_EXTENDED      0x80000000\n\n        \"\"\",\n        \"\"\"\n            The `pflags' field is a bitmask.  The following bits have been\n           defined.\n\n                #define SSH_FXF_READ            0x00000001\n                #define SSH_FXF_WRITE           0x00000002\n                #define SSH_FXF_APPEND          0x00000004\n                #define SSH_FXF_CREAT           0x00000008\n                #define SSH_FXF_TRUNC           0x00000010\n                #define SSH_FXF_EXCL            0x00000020\n        \"\"\",\n        \"\"\"\n            Currently, the following values are defined (other values may be\n           defined by future versions of this protocol):\n\n                #define SSH_FX_OK                            0\n                #define SSH_FX_EOF                           1\n                #define SSH_FX_NO_SUCH_FILE                  2\n                #define SSH_FX_PERMISSION_DENIED             3\n                #define SSH_FX_FAILURE                       4\n                #define SSH_FX_BAD_MESSAGE                   5\n                #define SSH_FX_NO_CONNECTION                 6\n                #define SSH_FX_CONNECTION_LOST               7\n                #define SSH_FX_OP_UNSUPPORTED                8\n        \"\"\"]\n\n\n    def test_constantsAgainstSpec(self):\n        \"\"\"\n        The constants used by the SFTP protocol implementation match those\n        found by searching through the spec.\n        \"\"\"\n        constants = {}\n        for excerpt in self.filexferSpecExcerpts:\n            for line in excerpt.splitlines():\n                m = re.match('^\\s*#define SSH_([A-Z_]+)\\s+([0-9x]*)\\s*$', line)\n                if m:\n                    constants[m.group(1)] = long(m.group(2), 0)\n        self.assertTrue(\n            len(constants) > 0, \"No constants found (the test must be buggy).\")\n        for k, v in constants.items():\n            self.assertEqual(v, getattr(filetransfer, k))\n\n\n\nclass RawPacketDataTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{filetransfer.FileTransferClient} which explicitly craft certain\n    less common protocol messages to exercise their handling.\n    \"\"\"\n\n    if not cryptography:\n        skip = \"Cannot run without cryptography\"\n\n    def setUp(self):\n        self.ftc = filetransfer.FileTransferClient()\n\n\n    def test_packetSTATUS(self):\n        \"\"\"\n        A STATUS packet containing a result code, a message, and a language is\n        parsed to produce the result of an outstanding request L{Deferred}.\n\n        @see: U{section 9.1<http://tools.ietf.org/html/draft-ietf-secsh-filexfer-13#section-9.1>}\n            of the SFTP Internet-Draft.\n        \"\"\"\n        d = defer.Deferred()\n        d.addCallback(self._cbTestPacketSTATUS)\n        self.ftc.openRequests[1] = d\n        data = struct.pack('!LL', 1, filetransfer.FX_OK) + common.NS(b'msg') + common.NS(b'lang')\n        self.ftc.packet_STATUS(data)\n        return d\n\n\n    def _cbTestPacketSTATUS(self, result):\n        \"\"\"\n        Assert that the result is a two-tuple containing the message and\n        language from the STATUS packet.\n        \"\"\"\n        self.assertEqual(result[0], b'msg')\n        self.assertEqual(result[1], b'lang')\n\n\n    def test_packetSTATUSShort(self):\n        \"\"\"\n        A STATUS packet containing only a result code can also be parsed to\n        produce the result of an outstanding request L{Deferred}.  Such packets\n        are sent by some SFTP implementations, though not strictly legal.\n\n        @see: U{section 9.1<http://tools.ietf.org/html/draft-ietf-secsh-filexfer-13#section-9.1>}\n            of the SFTP Internet-Draft.\n        \"\"\"\n        d = defer.Deferred()\n        d.addCallback(self._cbTestPacketSTATUSShort)\n        self.ftc.openRequests[1] = d\n        data = struct.pack('!LL', 1, filetransfer.FX_OK)\n        self.ftc.packet_STATUS(data)\n        return d\n\n\n    def _cbTestPacketSTATUSShort(self, result):\n        \"\"\"\n        Assert that the result is a two-tuple containing empty strings, since\n        the STATUS packet had neither a message nor a language.\n        \"\"\"\n        self.assertEqual(result[0], b'')\n        self.assertEqual(result[1], b'')\n\n\n    def test_packetSTATUSWithoutLang(self):\n        \"\"\"\n        A STATUS packet containing a result code and a message but no language\n        can also be parsed to produce the result of an outstanding request\n        L{Deferred}.  Such packets are sent by some SFTP implementations, though\n        not strictly legal.\n\n        @see: U{section 9.1<http://tools.ietf.org/html/draft-ietf-secsh-filexfer-13#section-9.1>}\n            of the SFTP Internet-Draft.\n        \"\"\"\n        d = defer.Deferred()\n        d.addCallback(self._cbTestPacketSTATUSWithoutLang)\n        self.ftc.openRequests[1] = d\n        data = struct.pack('!LL', 1, filetransfer.FX_OK) + common.NS(b'msg')\n        self.ftc.packet_STATUS(data)\n        return d\n\n\n    def _cbTestPacketSTATUSWithoutLang(self, result):\n        \"\"\"\n        Assert that the result is a two-tuple containing the message from the\n        STATUS packet and an empty string, since the language was missing.\n        \"\"\"\n        self.assertEqual(result[0], b'msg')\n        self.assertEqual(result[1], b'')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_forwarding.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.ssh.forwarding}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.python.reflect import requireModule\n\ncryptography = requireModule(\"cryptography\")\nif cryptography:\n    from twisted.conch.ssh import forwarding\n\nfrom twisted.internet.address import IPv6Address\nfrom twisted.trial import unittest\nfrom twisted.internet.test.test_endpoints import deterministicResolvingReactor\nfrom twisted.test.proto_helpers import MemoryReactorClock, StringTransport\n\n\nclass TestSSHConnectForwardingChannel(unittest.TestCase):\n    \"\"\"\n    Unit and integration tests for L{SSHConnectForwardingChannel}.\n    \"\"\"\n\n    if not cryptography:\n        skip = \"Cannot run without cryptography\"\n\n    def makeTCPConnection(self, reactor):\n        \"\"\"\n        Fake that connection was established for first connectTCP request made\n        on C{reactor}.\n\n        @param reactor: Reactor on which to fake the connection.\n        @type  reactor: A reactor.\n        \"\"\"\n        factory = reactor.tcpClients[0][2]\n        connector = reactor.connectors[0]\n        protocol = factory.buildProtocol(None)\n        transport = StringTransport(peerAddress=connector.getDestination())\n        protocol.makeConnection(transport)\n\n\n    def test_channelOpenHostnameRequests(self):\n        \"\"\"\n        When a hostname is sent as part of forwarding requests, it\n        is resolved using HostnameEndpoint's resolver.\n        \"\"\"\n        sut = forwarding.SSHConnectForwardingChannel(\n            hostport=('fwd.example.org', 1234))\n        # Patch channel and resolver to not touch the network.\n        memoryReactor = MemoryReactorClock()\n        sut._reactor = deterministicResolvingReactor(memoryReactor, ['::1'])\n        sut.channelOpen(None)\n\n        self.makeTCPConnection(memoryReactor)\n        self.successResultOf(sut._channelOpenDeferred)\n        # Channel is connected using a forwarding client to the resolved\n        # address of the requested host.\n        self.assertIsInstance(sut.client, forwarding.SSHForwardingClient)\n        self.assertEqual(\n            IPv6Address('TCP', '::1', 1234), sut.client.transport.getPeer())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_helper.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_helper -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom twisted.conch.insults import helper\nfrom twisted.conch.insults.insults import G0, G1, G2, G3\nfrom twisted.conch.insults.insults import modes, privateModes\nfrom twisted.conch.insults.insults import (\n    NORMAL, BOLD, UNDERLINE, BLINK, REVERSE_VIDEO)\n\nfrom twisted.python.compat import _PY3\nfrom twisted.trial import unittest\n\nWIDTH = 80\nHEIGHT = 24\n\nclass BufferTests(unittest.TestCase):\n    def setUp(self):\n        self.term = helper.TerminalBuffer()\n        self.term.connectionMade()\n\n    def testInitialState(self):\n        self.assertEqual(self.term.width, WIDTH)\n        self.assertEqual(self.term.height, HEIGHT)\n        self.assertEqual(self.term.__bytes__(),\n                          b'\\n' * (HEIGHT - 1))\n        self.assertEqual(self.term.reportCursorPosition(), (0, 0))\n\n\n    def test_initialPrivateModes(self):\n        \"\"\"\n        Verify that only DEC Auto Wrap Mode (DECAWM) and DEC Text Cursor Enable\n        Mode (DECTCEM) are initially in the Set Mode (SM) state.\n        \"\"\"\n        self.assertEqual(\n            {privateModes.AUTO_WRAP: True,\n             privateModes.CURSOR_MODE: True},\n            self.term.privateModes)\n\n\n    def test_carriageReturn(self):\n        \"\"\"\n        C{\"\\r\"} moves the cursor to the first column in the current row.\n        \"\"\"\n        self.term.cursorForward(5)\n        self.term.cursorDown(3)\n        self.assertEqual(self.term.reportCursorPosition(), (5, 3))\n        self.term.insertAtCursor(b\"\\r\")\n        self.assertEqual(self.term.reportCursorPosition(), (0, 3))\n\n\n    def test_linefeed(self):\n        \"\"\"\n        C{\"\\n\"} moves the cursor to the next row without changing the column.\n        \"\"\"\n        self.term.cursorForward(5)\n        self.assertEqual(self.term.reportCursorPosition(), (5, 0))\n        self.term.insertAtCursor(b\"\\n\")\n        self.assertEqual(self.term.reportCursorPosition(), (5, 1))\n\n\n    def test_newline(self):\n        \"\"\"\n        C{write} transforms C{\"\\n\"} into C{\"\\r\\n\"}.\n        \"\"\"\n        self.term.cursorForward(5)\n        self.term.cursorDown(3)\n        self.assertEqual(self.term.reportCursorPosition(), (5, 3))\n        self.term.write(b\"\\n\")\n        self.assertEqual(self.term.reportCursorPosition(), (0, 4))\n\n\n    def test_setPrivateModes(self):\n        \"\"\"\n        Verify that L{helper.TerminalBuffer.setPrivateModes} changes the Set\n        Mode (SM) state to \"set\" for the private modes it is passed.\n        \"\"\"\n        expected = self.term.privateModes.copy()\n        self.term.setPrivateModes([privateModes.SCROLL, privateModes.SCREEN])\n        expected[privateModes.SCROLL] = True\n        expected[privateModes.SCREEN] = True\n        self.assertEqual(expected, self.term.privateModes)\n\n\n    def test_resetPrivateModes(self):\n        \"\"\"\n        Verify that L{helper.TerminalBuffer.resetPrivateModes} changes the Set\n        Mode (SM) state to \"reset\" for the private modes it is passed.\n        \"\"\"\n        expected = self.term.privateModes.copy()\n        self.term.resetPrivateModes([privateModes.AUTO_WRAP, privateModes.CURSOR_MODE])\n        del expected[privateModes.AUTO_WRAP]\n        del expected[privateModes.CURSOR_MODE]\n        self.assertEqual(expected, self.term.privateModes)\n\n\n    def testCursorDown(self):\n        self.term.cursorDown(3)\n        self.assertEqual(self.term.reportCursorPosition(), (0, 3))\n        self.term.cursorDown()\n        self.assertEqual(self.term.reportCursorPosition(), (0, 4))\n        self.term.cursorDown(HEIGHT)\n        self.assertEqual(self.term.reportCursorPosition(), (0, HEIGHT - 1))\n\n    def testCursorUp(self):\n        self.term.cursorUp(5)\n        self.assertEqual(self.term.reportCursorPosition(), (0, 0))\n\n        self.term.cursorDown(20)\n        self.term.cursorUp(1)\n        self.assertEqual(self.term.reportCursorPosition(), (0, 19))\n\n        self.term.cursorUp(19)\n        self.assertEqual(self.term.reportCursorPosition(), (0, 0))\n\n    def testCursorForward(self):\n        self.term.cursorForward(2)\n        self.assertEqual(self.term.reportCursorPosition(), (2, 0))\n        self.term.cursorForward(2)\n        self.assertEqual(self.term.reportCursorPosition(), (4, 0))\n        self.term.cursorForward(WIDTH)\n        self.assertEqual(self.term.reportCursorPosition(), (WIDTH, 0))\n\n    def testCursorBackward(self):\n        self.term.cursorForward(10)\n        self.term.cursorBackward(2)\n        self.assertEqual(self.term.reportCursorPosition(), (8, 0))\n        self.term.cursorBackward(7)\n        self.assertEqual(self.term.reportCursorPosition(), (1, 0))\n        self.term.cursorBackward(1)\n        self.assertEqual(self.term.reportCursorPosition(), (0, 0))\n        self.term.cursorBackward(1)\n        self.assertEqual(self.term.reportCursorPosition(), (0, 0))\n\n\n    def testCursorPositioning(self):\n        self.term.cursorPosition(3, 9)\n        self.assertEqual(self.term.reportCursorPosition(), (3, 9))\n\n\n    def testSimpleWriting(self):\n        s = b\"Hello, world.\"\n        self.term.write(s)\n        self.assertEqual(\n            self.term.__bytes__(),\n            s + b'\\n' +\n            b'\\n' * (HEIGHT - 2))\n\n\n    def testOvertype(self):\n        s = b\"hello, world.\"\n        self.term.write(s)\n        self.term.cursorBackward(len(s))\n        self.term.resetModes([modes.IRM])\n        self.term.write(b\"H\")\n        self.assertEqual(\n            self.term.__bytes__(),\n            (b\"H\" + s[1:]) + b'\\n' +\n            b'\\n' * (HEIGHT - 2))\n\n\n    def testInsert(self):\n        s = b\"ello, world.\"\n        self.term.write(s)\n        self.term.cursorBackward(len(s))\n        self.term.setModes([modes.IRM])\n        self.term.write(b\"H\")\n        self.assertEqual(\n            self.term.__bytes__(),\n            (b\"H\" + s) + b'\\n' +\n            b'\\n' * (HEIGHT - 2))\n\n\n    def testWritingInTheMiddle(self):\n        s = b\"Hello, world.\"\n        self.term.cursorDown(5)\n        self.term.cursorForward(5)\n        self.term.write(s)\n        self.assertEqual(\n            self.term.__bytes__(),\n            b'\\n' * 5 +\n            (self.term.fill * 5) + s + b'\\n' +\n            b'\\n' * (HEIGHT - 7))\n\n\n    def testWritingWrappedAtEndOfLine(self):\n        s = b\"Hello, world.\"\n        self.term.cursorForward(WIDTH - 5)\n        self.term.write(s)\n        self.assertEqual(\n            self.term.__bytes__(),\n            s[:5].rjust(WIDTH) + b'\\n' +\n            s[5:] + b'\\n' +\n            b'\\n' * (HEIGHT - 3))\n\n\n    def testIndex(self):\n        self.term.index()\n        self.assertEqual(self.term.reportCursorPosition(), (0, 1))\n        self.term.cursorDown(HEIGHT)\n        self.assertEqual(self.term.reportCursorPosition(), (0, HEIGHT - 1))\n        self.term.index()\n        self.assertEqual(self.term.reportCursorPosition(), (0, HEIGHT - 1))\n\n\n    def testReverseIndex(self):\n        self.term.reverseIndex()\n        self.assertEqual(self.term.reportCursorPosition(), (0, 0))\n        self.term.cursorDown(2)\n        self.assertEqual(self.term.reportCursorPosition(), (0, 2))\n        self.term.reverseIndex()\n        self.assertEqual(self.term.reportCursorPosition(), (0, 1))\n\n\n    def test_nextLine(self):\n        \"\"\"\n        C{nextLine} positions the cursor at the beginning of the row below the\n        current row.\n        \"\"\"\n        self.term.nextLine()\n        self.assertEqual(self.term.reportCursorPosition(), (0, 1))\n        self.term.cursorForward(5)\n        self.assertEqual(self.term.reportCursorPosition(), (5, 1))\n        self.term.nextLine()\n        self.assertEqual(self.term.reportCursorPosition(), (0, 2))\n\n\n    def testSaveCursor(self):\n        self.term.cursorDown(5)\n        self.term.cursorForward(7)\n        self.assertEqual(self.term.reportCursorPosition(), (7, 5))\n        self.term.saveCursor()\n        self.term.cursorDown(7)\n        self.term.cursorBackward(3)\n        self.assertEqual(self.term.reportCursorPosition(), (4, 12))\n        self.term.restoreCursor()\n        self.assertEqual(self.term.reportCursorPosition(), (7, 5))\n\n\n    def testSingleShifts(self):\n        self.term.singleShift2()\n        self.term.write(b'Hi')\n\n        ch = self.term.getCharacter(0, 0)\n        self.assertEqual(ch[0], b'H')\n        self.assertEqual(ch[1].charset, G2)\n\n        ch = self.term.getCharacter(1, 0)\n        self.assertEqual(ch[0], b'i')\n        self.assertEqual(ch[1].charset, G0)\n\n        self.term.singleShift3()\n        self.term.write(b'!!')\n\n        ch = self.term.getCharacter(2, 0)\n        self.assertEqual(ch[0], b'!')\n        self.assertEqual(ch[1].charset, G3)\n\n        ch = self.term.getCharacter(3, 0)\n        self.assertEqual(ch[0], b'!')\n        self.assertEqual(ch[1].charset, G0)\n\n\n    def testShifting(self):\n        s1 = b\"Hello\"\n        s2 = b\"World\"\n        s3 = b\"Bye!\"\n        self.term.write(b\"Hello\\n\")\n        self.term.shiftOut()\n        self.term.write(b\"World\\n\")\n        self.term.shiftIn()\n        self.term.write(b\"Bye!\\n\")\n\n        g = G0\n        h = 0\n        for s in (s1, s2, s3):\n            for i in range(len(s)):\n                ch = self.term.getCharacter(i, h)\n                self.assertEqual(ch[0], s[i:i+1])\n                self.assertEqual(ch[1].charset, g)\n            g = g == G0 and G1 or G0\n            h += 1\n\n\n    def testGraphicRendition(self):\n        self.term.selectGraphicRendition(BOLD, UNDERLINE, BLINK, REVERSE_VIDEO)\n        self.term.write(b'W')\n        self.term.selectGraphicRendition(NORMAL)\n        self.term.write(b'X')\n        self.term.selectGraphicRendition(BLINK)\n        self.term.write(b'Y')\n        self.term.selectGraphicRendition(BOLD)\n        self.term.write(b'Z')\n\n        ch = self.term.getCharacter(0, 0)\n        self.assertEqual(ch[0], b'W')\n        self.assertTrue(ch[1].bold)\n        self.assertTrue(ch[1].underline)\n        self.assertTrue(ch[1].blink)\n        self.assertTrue(ch[1].reverseVideo)\n\n        ch = self.term.getCharacter(1, 0)\n        self.assertEqual(ch[0], b'X')\n        self.assertFalse(ch[1].bold)\n        self.assertFalse(ch[1].underline)\n        self.assertFalse(ch[1].blink)\n        self.assertFalse(ch[1].reverseVideo)\n\n        ch = self.term.getCharacter(2, 0)\n        self.assertEqual(ch[0], b'Y')\n        self.assertTrue(ch[1].blink)\n        self.assertFalse(ch[1].bold)\n        self.assertFalse(ch[1].underline)\n        self.assertFalse(ch[1].reverseVideo)\n\n        ch = self.term.getCharacter(3, 0)\n        self.assertEqual(ch[0], b'Z')\n        self.assertTrue(ch[1].blink)\n        self.assertTrue(ch[1].bold)\n        self.assertFalse(ch[1].underline)\n        self.assertFalse(ch[1].reverseVideo)\n\n\n    def testColorAttributes(self):\n        s1 = b\"Merry xmas\"\n        s2 = b\"Just kidding\"\n        self.term.selectGraphicRendition(helper.FOREGROUND + helper.RED,\n                                         helper.BACKGROUND + helper.GREEN)\n        self.term.write(s1 + b\"\\n\")\n        self.term.selectGraphicRendition(NORMAL)\n        self.term.write(s2 + b\"\\n\")\n\n        for i in range(len(s1)):\n            ch = self.term.getCharacter(i, 0)\n            self.assertEqual(ch[0], s1[i:i+1])\n            self.assertEqual(ch[1].charset, G0)\n            self.assertFalse(ch[1].bold)\n            self.assertFalse(ch[1].underline)\n            self.assertFalse(ch[1].blink)\n            self.assertFalse(ch[1].reverseVideo)\n            self.assertEqual(ch[1].foreground, helper.RED)\n            self.assertEqual(ch[1].background, helper.GREEN)\n\n        for i in range(len(s2)):\n            ch = self.term.getCharacter(i, 1)\n            self.assertEqual(ch[0], s2[i:i+1])\n            self.assertEqual(ch[1].charset, G0)\n            self.assertFalse(ch[1].bold)\n            self.assertFalse(ch[1].underline)\n            self.assertFalse(ch[1].blink)\n            self.assertFalse(ch[1].reverseVideo)\n            self.assertEqual(ch[1].foreground, helper.WHITE)\n            self.assertEqual(ch[1].background, helper.BLACK)\n\n\n    def testEraseLine(self):\n        s1 = b'line 1'\n        s2 = b'line 2'\n        s3 = b'line 3'\n        self.term.write(b'\\n'.join((s1, s2, s3)) + b'\\n')\n        self.term.cursorPosition(1, 1)\n        self.term.eraseLine()\n\n        self.assertEqual(\n            self.term.__bytes__(),\n            s1 + b'\\n' +\n            b'\\n' +\n            s3 + b'\\n' +\n            b'\\n' * (HEIGHT - 4))\n\n\n    def testEraseToLineEnd(self):\n        s = b'Hello, world.'\n        self.term.write(s)\n        self.term.cursorBackward(5)\n        self.term.eraseToLineEnd()\n        self.assertEqual(\n            self.term.__bytes__(),\n            s[:-5] + b'\\n' +\n            b'\\n' * (HEIGHT - 2))\n\n\n    def testEraseToLineBeginning(self):\n        s = b'Hello, world.'\n        self.term.write(s)\n        self.term.cursorBackward(5)\n        self.term.eraseToLineBeginning()\n        self.assertEqual(\n            self.term.__bytes__(),\n            s[-4:].rjust(len(s)) + b'\\n' +\n            b'\\n' * (HEIGHT - 2))\n\n\n    def testEraseDisplay(self):\n        self.term.write(b'Hello world\\n')\n        self.term.write(b'Goodbye world\\n')\n        self.term.eraseDisplay()\n\n        self.assertEqual(\n            self.term.__bytes__(),\n            b'\\n' * (HEIGHT - 1))\n\n\n    def testEraseToDisplayEnd(self):\n        s1 = b\"Hello world\"\n        s2 = b\"Goodbye world\"\n        self.term.write(b'\\n'.join((s1, s2, b'')))\n        self.term.cursorPosition(5, 1)\n        self.term.eraseToDisplayEnd()\n\n        self.assertEqual(\n            self.term.__bytes__(),\n            s1 + b'\\n' +\n            s2[:5] + b'\\n' +\n            b'\\n' * (HEIGHT - 3))\n\n\n    def testEraseToDisplayBeginning(self):\n        s1 = b\"Hello world\"\n        s2 = b\"Goodbye world\"\n        self.term.write(b'\\n'.join((s1, s2)))\n        self.term.cursorPosition(5, 1)\n        self.term.eraseToDisplayBeginning()\n\n        self.assertEqual(\n            self.term.__bytes__(),\n            b'\\n' +\n            s2[6:].rjust(len(s2)) + b'\\n' +\n            b'\\n' * (HEIGHT - 3))\n\n\n    def testLineInsertion(self):\n        s1 = b\"Hello world\"\n        s2 = b\"Goodbye world\"\n        self.term.write(b'\\n'.join((s1, s2)))\n        self.term.cursorPosition(7, 1)\n        self.term.insertLine()\n\n        self.assertEqual(\n            self.term.__bytes__(),\n            s1 + b'\\n' +\n            b'\\n' +\n            s2 + b'\\n' +\n            b'\\n' * (HEIGHT - 4))\n\n\n    def testLineDeletion(self):\n        s1 = b\"Hello world\"\n        s2 = b\"Middle words\"\n        s3 = b\"Goodbye world\"\n        self.term.write(b'\\n'.join((s1, s2, s3)))\n        self.term.cursorPosition(9, 1)\n        self.term.deleteLine()\n\n        self.assertEqual(\n            self.term.__bytes__(),\n            s1 + b'\\n' +\n            s3 + b'\\n' +\n            b'\\n' * (HEIGHT - 3))\n\n\n\nclass FakeDelayedCall:\n    called = False\n    cancelled = False\n    def __init__(self, fs, timeout, f, a, kw):\n        self.fs = fs\n        self.timeout = timeout\n        self.f = f\n        self.a = a\n        self.kw = kw\n\n\n    def active(self):\n        return not (self.cancelled or self.called)\n\n\n    def cancel(self):\n        self.cancelled = True\n#        self.fs.calls.remove(self)\n\n\n    def call(self):\n        self.called = True\n        self.f(*self.a, **self.kw)\n\n\n\nclass FakeScheduler:\n    def __init__(self):\n        self.calls = []\n\n\n    def callLater(self, timeout, f, *a, **kw):\n        self.calls.append(FakeDelayedCall(self, timeout, f, a, kw))\n        return self.calls[-1]\n\n\n\nclass ExpectTests(unittest.TestCase):\n    def setUp(self):\n        self.term = helper.ExpectableBuffer()\n        self.term.connectionMade()\n        self.fs = FakeScheduler()\n\n\n    def testSimpleString(self):\n        result = []\n        d = self.term.expect(b\"hello world\", timeout=1, scheduler=self.fs)\n        d.addCallback(result.append)\n\n        self.term.write(b\"greeting puny earthlings\\n\")\n        self.assertFalse(result)\n        self.term.write(b\"hello world\\n\")\n        self.assertTrue(result)\n        self.assertEqual(result[0].group(), b\"hello world\")\n        self.assertEqual(len(self.fs.calls), 1)\n        self.assertFalse(self.fs.calls[0].active())\n\n\n    def testBrokenUpString(self):\n        result = []\n        d = self.term.expect(b\"hello world\")\n        d.addCallback(result.append)\n\n        self.assertFalse(result)\n        self.term.write(b\"hello \")\n        self.assertFalse(result)\n        self.term.write(b\"worl\")\n        self.assertFalse(result)\n        self.term.write(b\"d\")\n        self.assertTrue(result)\n        self.assertEqual(result[0].group(), b\"hello world\")\n\n\n    def testMultiple(self):\n        result = []\n        d1 = self.term.expect(b\"hello \")\n        d1.addCallback(result.append)\n        d2 = self.term.expect(b\"world\")\n        d2.addCallback(result.append)\n\n        self.assertFalse(result)\n        self.term.write(b\"hello\")\n        self.assertFalse(result)\n        self.term.write(b\" \")\n        self.assertEqual(len(result), 1)\n        self.term.write(b\"world\")\n        self.assertEqual(len(result), 2)\n        self.assertEqual(result[0].group(), b\"hello \")\n        self.assertEqual(result[1].group(), b\"world\")\n\n\n    def testSynchronous(self):\n        self.term.write(b\"hello world\")\n\n        result = []\n        d = self.term.expect(b\"hello world\")\n        d.addCallback(result.append)\n        self.assertTrue(result)\n        self.assertEqual(result[0].group(), b\"hello world\")\n\n\n    def testMultipleSynchronous(self):\n        self.term.write(b\"goodbye world\")\n\n        result = []\n        d1 = self.term.expect(b\"bye\")\n        d1.addCallback(result.append)\n        d2 = self.term.expect(b\"world\")\n        d2.addCallback(result.append)\n\n        self.assertEqual(len(result), 2)\n        self.assertEqual(result[0].group(), b\"bye\")\n        self.assertEqual(result[1].group(), b\"world\")\n\n\n    def _cbTestTimeoutFailure(self, res):\n        self.assertTrue(hasattr(res, 'type'))\n        self.assertEqual(res.type, helper.ExpectationTimeout)\n\n\n    def testTimeoutFailure(self):\n        d = self.term.expect(b\"hello world\", timeout=1, scheduler=self.fs)\n        d.addBoth(self._cbTestTimeoutFailure)\n        self.fs.calls[0].call()\n\n\n    def testOverlappingTimeout(self):\n        self.term.write(b\"not zoomtastic\")\n\n        result = []\n        d1 = self.term.expect(b\"hello world\", timeout=1, scheduler=self.fs)\n        d1.addBoth(self._cbTestTimeoutFailure)\n        d2 = self.term.expect(b\"zoom\")\n        d2.addCallback(result.append)\n\n        self.fs.calls[0].call()\n\n        self.assertEqual(len(result), 1)\n        self.assertEqual(result[0].group(), b\"zoom\")\n\n\n\nclass CharacterAttributeTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{twisted.conch.insults.helper.CharacterAttribute}.\n    \"\"\"\n    def test_equality(self):\n        \"\"\"\n        L{CharacterAttribute}s must have matching character attribute values\n        (bold, blink, underline, etc) with the same values to be considered\n        equal.\n        \"\"\"\n        self.assertEqual(\n            helper.CharacterAttribute(),\n            helper.CharacterAttribute())\n\n        self.assertEqual(\n            helper.CharacterAttribute(),\n            helper.CharacterAttribute(charset=G0))\n\n        self.assertEqual(\n            helper.CharacterAttribute(\n                bold=True, underline=True, blink=False, reverseVideo=True,\n                foreground=helper.BLUE),\n            helper.CharacterAttribute(\n                bold=True, underline=True, blink=False, reverseVideo=True,\n                foreground=helper.BLUE))\n\n        self.assertNotEqual(\n            helper.CharacterAttribute(),\n            helper.CharacterAttribute(charset=G1))\n\n        self.assertNotEqual(\n            helper.CharacterAttribute(bold=True),\n            helper.CharacterAttribute(bold=False))\n\n\n    def test_wantOneDeprecated(self):\n        \"\"\"\n        L{twisted.conch.insults.helper.CharacterAttribute.wantOne} emits\n        a deprecation warning when invoked.\n        \"\"\"\n        # Trigger the deprecation warning.\n        helper._FormattingState().wantOne(bold=True)\n\n        warningsShown = self.flushWarnings([self.test_wantOneDeprecated])\n        self.assertEqual(len(warningsShown), 1)\n        self.assertEqual(warningsShown[0]['category'], DeprecationWarning)\n        if _PY3:\n            deprecatedClass = (\n                \"twisted.conch.insults.helper._FormattingState.wantOne\")\n        else:\n            deprecatedClass = \"twisted.conch.insults.helper.wantOne\"\n        self.assertEqual(\n            warningsShown[0]['message'],\n            '%s was deprecated in Twisted 13.1.0' % (deprecatedClass))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_insults.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_insults -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom twisted.trial import unittest\nfrom twisted.test.proto_helpers import StringTransport\n\nfrom twisted.conch.insults.insults import ServerProtocol, ClientProtocol\nfrom twisted.conch.insults.insults import (CS_UK, CS_US, CS_DRAWING,\n                                           CS_ALTERNATE,\n                                           CS_ALTERNATE_SPECIAL,\n                                           BLINK, UNDERLINE)\nfrom twisted.conch.insults.insults import G0, G1\nfrom twisted.conch.insults.insults import modes, privateModes\nfrom twisted.python.compat import intToBytes, iterbytes\nfrom twisted.python.constants import ValueConstant, Values\n\nimport textwrap\n\n\ndef _getattr(mock, name):\n    return super(Mock, mock).__getattribute__(name)\n\n\ndef occurrences(mock):\n    return _getattr(mock, 'occurrences')\n\n\ndef methods(mock):\n    return _getattr(mock, 'methods')\n\n\ndef _append(mock, obj):\n    occurrences(mock).append(obj)\n\ndefault = object()\n\n\ndef _ecmaCodeTableCoordinate(column, row):\n    \"\"\"\n    Return the byte in 7- or 8-bit code table identified by C{column}\n    and C{row}.\n\n    \"An 8-bit code table consists of 256 positions arranged in 16\n    columns and 16 rows.  The columns and rows are numbered 00 to 15.\"\n\n    \"A 7-bit code table consists of 128 positions arranged in 8\n    columns and 16 rows.  The columns are numbered 00 to 07 and the\n    rows 00 to 15 (see figure 1).\"\n\n    p.5 of \"Standard ECMA-35: Character Code Structure and Extension\n    Techniques\", 6th Edition (December 1994).\n    \"\"\"\n    # 8 and 15 both happen to take up 4 bits, so the first number\n    # should be shifted by 4 for both the 7- and 8-bit tables.\n    return bytes(bytearray([(column << 4) | row]))\n\n\ndef _makeControlFunctionSymbols(name, colOffset, names, doc):\n    # the value for each name is the concatenation of the bit values\n    # of its x, y locations, with an offset of 4 added to its x value.\n    # so CUP is (0 + 4, 8) = (4, 8) = 4||8 = 1001000 = 72 = b\"H\"\n    # this is how it's defined in the standard!\n    attrs = {name: ValueConstant(_ecmaCodeTableCoordinate(i + colOffset, j))\n             for j, row in enumerate(names)\n             for i, name in enumerate(row)\n             if name}\n    attrs[\"__doc__\"] = doc\n    return type(name, (Values,), attrs)\n\n\nCSFinalByte = _makeControlFunctionSymbols(\n    \"CSFinalByte\",\n    colOffset=4,\n    names=[\n        # 4,     5,     6\n        ['ICH', 'DCH', 'HPA'],\n        ['CUU', 'SSE', 'HPR'],\n        ['CUD', 'CPR', 'REP'],\n        ['CUF', 'SU', 'DA'],\n        ['CUB', 'SD', 'VPA'],\n        ['CNL', 'NP', 'VPR'],\n        ['CPL', 'PP', 'HVP'],\n        ['CHA', 'CTC', 'TBC'],\n        ['CUP', 'ECH', 'SM'],\n        ['CHT', 'CVT', 'MC'],\n        ['ED', 'CBT', 'HPB'],\n        ['EL', 'SRS', 'VPB'],\n        ['IL', 'PTX', 'RM'],\n        ['DL', 'SDS', 'SGR'],\n        ['EF', 'SIMD', 'DSR'],\n        ['EA',  None, 'DAQ'],\n    ],\n    doc=textwrap.dedent(\"\"\"\n    Symbolic constants for all control sequence final bytes\n    that do not imply intermediate bytes.  This happens to cover\n    movement control sequences.\n\n    See page 11 of \"Standard ECMA 48: Control Functions for Coded\n    Character Sets\", 5th Edition (June 1991).\n\n    Each L{ValueConstant} maps a control sequence name to L{bytes}\n    \"\"\"))\n\n\nC1SevenBit = _makeControlFunctionSymbols(\n    \"C1SevenBit\",\n    colOffset=4,\n    names=[\n        [None, \"DCS\"],\n        [None, \"PU1\"],\n        [\"BPH\", \"PU2\"],\n        [\"NBH\", \"STS\"],\n        [None, \"CCH\"],\n        [\"NEL\", \"MW\"],\n        [\"SSA\", \"SPA\"],\n        [\"ESA\", \"EPA\"],\n        [\"HTS\", \"SOS\"],\n        [\"HTJ\", None],\n        [\"VTS\", \"SCI\"],\n        [\"PLD\", \"CSI\"],\n        [\"PLU\", \"ST\"],\n        [\"RI\", \"OSC\"],\n        [\"SS2\", \"PM\"],\n        [\"SS3\", \"APC\"],\n    ],\n    doc=textwrap.dedent(\"\"\"\n    Symbolic constants for all 7 bit versions of the C1 control functions\n\n    See page 9 \"Standard ECMA 48: Control Functions for Coded\n    Character Sets\", 5th Edition (June 1991).\n\n    Each L{ValueConstant} maps a control sequence name to L{bytes}\n    \"\"\"))\n\n\n\nclass Mock(object):\n    callReturnValue = default\n\n    def __init__(self, methods=None, callReturnValue=default):\n        \"\"\"\n        @param methods: Mapping of names to return values\n        @param callReturnValue: object __call__ should return\n        \"\"\"\n        self.occurrences = []\n        if methods is None:\n            methods = {}\n        self.methods = methods\n        if callReturnValue is not default:\n            self.callReturnValue = callReturnValue\n\n\n    def __call__(self, *a, **kw):\n        returnValue = _getattr(self, 'callReturnValue')\n        if returnValue is default:\n            returnValue = Mock()\n        # _getattr(self, 'occurrences').append(('__call__', returnValue, a, kw))\n        _append(self, ('__call__', returnValue, a, kw))\n        return returnValue\n\n\n    def __getattribute__(self, name):\n        methods = _getattr(self, 'methods')\n        if name in methods:\n            attrValue = Mock(callReturnValue=methods[name])\n        else:\n            attrValue = Mock()\n        # _getattr(self, 'occurrences').append((name, attrValue))\n        _append(self, (name, attrValue))\n        return attrValue\n\n\n\nclass MockMixin:\n    def assertCall(self, occurrence, methodName, expectedPositionalArgs=(),\n                   expectedKeywordArgs={}):\n        attr, mock = occurrence\n        self.assertEqual(attr, methodName)\n        self.assertEqual(len(occurrences(mock)), 1)\n        [(call, result, args, kw)] = occurrences(mock)\n        self.assertEqual(call, \"__call__\")\n        self.assertEqual(args, expectedPositionalArgs)\n        self.assertEqual(kw, expectedKeywordArgs)\n        return result\n\n\n_byteGroupingTestTemplate = \"\"\"\\\ndef testByte%(groupName)s(self):\n    transport = StringTransport()\n    proto = Mock()\n    parser = self.protocolFactory(lambda: proto)\n    parser.factory = self\n    parser.makeConnection(transport)\n\n    bytes = self.TEST_BYTES\n    while bytes:\n        chunk = bytes[:%(bytesPer)d]\n        bytes = bytes[%(bytesPer)d:]\n        parser.dataReceived(chunk)\n\n    self.verifyResults(transport, proto, parser)\n\"\"\"\nclass ByteGroupingsMixin(MockMixin):\n    protocolFactory = None\n\n    for word, n in [('Pairs', 2), ('Triples', 3), ('Quads', 4), ('Quints', 5), ('Sexes', 6)]:\n        exec(_byteGroupingTestTemplate % {'groupName': word, 'bytesPer': n})\n    del word, n\n\n    def verifyResults(self, transport, proto, parser):\n        result = self.assertCall(occurrences(proto).pop(0), \"makeConnection\", (parser,))\n        self.assertEqual(occurrences(result), [])\n\ndel _byteGroupingTestTemplate\n\nclass ServerArrowKeysTests(ByteGroupingsMixin, unittest.TestCase):\n    protocolFactory = ServerProtocol\n\n    # All the arrow keys once\n    TEST_BYTES = b'\\x1b[A\\x1b[B\\x1b[C\\x1b[D'\n\n    def verifyResults(self, transport, proto, parser):\n        ByteGroupingsMixin.verifyResults(self, transport, proto, parser)\n\n        for arrow in (parser.UP_ARROW, parser.DOWN_ARROW,\n                      parser.RIGHT_ARROW, parser.LEFT_ARROW):\n            result = self.assertCall(occurrences(proto).pop(0), \"keystrokeReceived\", (arrow, None))\n            self.assertEqual(occurrences(result), [])\n        self.assertFalse(occurrences(proto))\n\n\nclass PrintableCharactersTests(ByteGroupingsMixin, unittest.TestCase):\n    protocolFactory = ServerProtocol\n\n    # Some letters and digits, first on their own, then capitalized,\n    # then modified with alt\n\n    TEST_BYTES = b'abc123ABC!@#\\x1ba\\x1bb\\x1bc\\x1b1\\x1b2\\x1b3'\n\n    def verifyResults(self, transport, proto, parser):\n        ByteGroupingsMixin.verifyResults(self, transport, proto, parser)\n\n        for char in iterbytes(b'abc123ABC!@#'):\n            result = self.assertCall(occurrences(proto).pop(0), \"keystrokeReceived\", (char, None))\n            self.assertEqual(occurrences(result), [])\n\n        for char in iterbytes(b'abc123'):\n            result = self.assertCall(occurrences(proto).pop(0), \"keystrokeReceived\", (char, parser.ALT))\n            self.assertEqual(occurrences(result), [])\n\n        occs = occurrences(proto)\n        self.assertFalse(occs, \"%r should have been []\" % (occs,))\n\n\n\nclass ServerFunctionKeysTests(ByteGroupingsMixin, unittest.TestCase):\n    \"\"\"Test for parsing and dispatching function keys (F1 - F12)\n    \"\"\"\n    protocolFactory = ServerProtocol\n\n    byteList = []\n    for byteCodes in (b'OP', b'OQ', b'OR', b'OS', # F1 - F4\n                  b'15~', b'17~', b'18~', b'19~', # F5 - F8\n                  b'20~', b'21~', b'23~', b'24~'): # F9 - F12\n        byteList.append(b'\\x1b[' + byteCodes)\n    TEST_BYTES = b''.join(byteList)\n    del byteList, byteCodes\n\n    def verifyResults(self, transport, proto, parser):\n        ByteGroupingsMixin.verifyResults(self, transport, proto, parser)\n        for funcNum in range(1, 13):\n            funcArg = getattr(parser, 'F%d' % (funcNum,))\n            result = self.assertCall(occurrences(proto).pop(0), \"keystrokeReceived\", (funcArg, None))\n            self.assertEqual(occurrences(result), [])\n        self.assertFalse(occurrences(proto))\n\n\n\nclass ClientCursorMovementTests(ByteGroupingsMixin, unittest.TestCase):\n    protocolFactory = ClientProtocol\n\n    d2 = b\"\\x1b[2B\"\n    r4 = b\"\\x1b[4C\"\n    u1 = b\"\\x1b[A\"\n    l2 = b\"\\x1b[2D\"\n    # Move the cursor down two, right four, up one, left two, up one, left two\n    TEST_BYTES = d2 + r4 + u1 + l2 + u1 + l2\n    del d2, r4, u1, l2\n\n    def verifyResults(self, transport, proto, parser):\n        ByteGroupingsMixin.verifyResults(self, transport, proto, parser)\n\n        for (method, count) in [('Down', 2), ('Forward', 4), ('Up', 1),\n                                ('Backward', 2), ('Up', 1), ('Backward', 2)]:\n            result = self.assertCall(occurrences(proto).pop(0), \"cursor\" + method, (count,))\n            self.assertEqual(occurrences(result), [])\n        self.assertFalse(occurrences(proto))\n\n\n\nclass ClientControlSequencesTests(unittest.TestCase, MockMixin):\n    def setUp(self):\n        self.transport = StringTransport()\n        self.proto = Mock()\n        self.parser = ClientProtocol(lambda: self.proto)\n        self.parser.factory = self\n        self.parser.makeConnection(self.transport)\n        result = self.assertCall(occurrences(self.proto).pop(0), \"makeConnection\", (self.parser,))\n        self.assertFalse(occurrences(result))\n\n    def testSimpleCardinals(self):\n        self.parser.dataReceived(\n            b''.join(\n                    [b''.join([b'\\x1b[' + n + ch\n                             for n in (b'', intToBytes(2), intToBytes(20), intToBytes(200))]\n                           ) for ch in iterbytes(b'BACD')\n                    ]))\n        occs = occurrences(self.proto)\n\n        for meth in (\"Down\", \"Up\", \"Forward\", \"Backward\"):\n            for count in (1, 2, 20, 200):\n                result = self.assertCall(occs.pop(0), \"cursor\" + meth, (count,))\n                self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n    def testScrollRegion(self):\n        self.parser.dataReceived(b'\\x1b[5;22r\\x1b[r')\n        occs = occurrences(self.proto)\n\n        result = self.assertCall(occs.pop(0), \"setScrollRegion\", (5, 22))\n        self.assertFalse(occurrences(result))\n\n        result = self.assertCall(occs.pop(0), \"setScrollRegion\", (None, None))\n        self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n    def testHeightAndWidth(self):\n        self.parser.dataReceived(b\"\\x1b#3\\x1b#4\\x1b#5\\x1b#6\")\n        occs = occurrences(self.proto)\n\n        result = self.assertCall(occs.pop(0), \"doubleHeightLine\", (True,))\n        self.assertFalse(occurrences(result))\n\n        result = self.assertCall(occs.pop(0), \"doubleHeightLine\", (False,))\n        self.assertFalse(occurrences(result))\n\n        result = self.assertCall(occs.pop(0), \"singleWidthLine\")\n        self.assertFalse(occurrences(result))\n\n        result = self.assertCall(occs.pop(0), \"doubleWidthLine\")\n        self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n    def testCharacterSet(self):\n        self.parser.dataReceived(\n            b''.join(\n                [b''.join([b'\\x1b' + g + n for n in iterbytes(b'AB012')])\n                    for g in iterbytes(b'()')\n                ]))\n        occs = occurrences(self.proto)\n\n        for which in (G0, G1):\n            for charset in (CS_UK, CS_US, CS_DRAWING, CS_ALTERNATE, CS_ALTERNATE_SPECIAL):\n                result = self.assertCall(occs.pop(0), \"selectCharacterSet\", (charset, which))\n                self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n\n    def testShifting(self):\n        self.parser.dataReceived(b\"\\x15\\x14\")\n        occs = occurrences(self.proto)\n\n        result = self.assertCall(occs.pop(0), \"shiftIn\")\n        self.assertFalse(occurrences(result))\n\n        result = self.assertCall(occs.pop(0), \"shiftOut\")\n        self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n\n    def testSingleShifts(self):\n        self.parser.dataReceived(b\"\\x1bN\\x1bO\")\n        occs = occurrences(self.proto)\n\n        result = self.assertCall(occs.pop(0), \"singleShift2\")\n        self.assertFalse(occurrences(result))\n\n        result = self.assertCall(occs.pop(0), \"singleShift3\")\n        self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n\n    def testKeypadMode(self):\n        self.parser.dataReceived(b\"\\x1b=\\x1b>\")\n        occs = occurrences(self.proto)\n\n        result = self.assertCall(occs.pop(0), \"applicationKeypadMode\")\n        self.assertFalse(occurrences(result))\n\n        result = self.assertCall(occs.pop(0), \"numericKeypadMode\")\n        self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n\n    def testCursor(self):\n        self.parser.dataReceived(b\"\\x1b7\\x1b8\")\n        occs = occurrences(self.proto)\n\n        result = self.assertCall(occs.pop(0), \"saveCursor\")\n        self.assertFalse(occurrences(result))\n\n        result = self.assertCall(occs.pop(0), \"restoreCursor\")\n        self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n\n    def testReset(self):\n        self.parser.dataReceived(b\"\\x1bc\")\n        occs = occurrences(self.proto)\n\n        result = self.assertCall(occs.pop(0), \"reset\")\n        self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n\n    def testIndex(self):\n        self.parser.dataReceived(b\"\\x1bD\\x1bM\\x1bE\")\n        occs = occurrences(self.proto)\n\n        result = self.assertCall(occs.pop(0), \"index\")\n        self.assertFalse(occurrences(result))\n\n        result = self.assertCall(occs.pop(0), \"reverseIndex\")\n        self.assertFalse(occurrences(result))\n\n        result = self.assertCall(occs.pop(0), \"nextLine\")\n        self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n\n    def testModes(self):\n        self.parser.dataReceived(\n            b\"\\x1b[\" + b';'.join(map(intToBytes, [modes.KAM, modes.IRM, modes.LNM])) + b\"h\")\n        self.parser.dataReceived(\n            b\"\\x1b[\" + b';'.join(map(intToBytes, [modes.KAM, modes.IRM, modes.LNM])) + b\"l\")\n        occs = occurrences(self.proto)\n\n        result = self.assertCall(occs.pop(0), \"setModes\", ([modes.KAM, modes.IRM, modes.LNM],))\n        self.assertFalse(occurrences(result))\n\n        result = self.assertCall(occs.pop(0), \"resetModes\", ([modes.KAM, modes.IRM, modes.LNM],))\n        self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n\n    def testErasure(self):\n        self.parser.dataReceived(\n            b\"\\x1b[K\\x1b[1K\\x1b[2K\\x1b[J\\x1b[1J\\x1b[2J\\x1b[3P\")\n        occs = occurrences(self.proto)\n\n        for meth in (\"eraseToLineEnd\", \"eraseToLineBeginning\", \"eraseLine\",\n                     \"eraseToDisplayEnd\", \"eraseToDisplayBeginning\",\n                     \"eraseDisplay\"):\n            result = self.assertCall(occs.pop(0), meth)\n            self.assertFalse(occurrences(result))\n\n        result = self.assertCall(occs.pop(0), \"deleteCharacter\", (3,))\n        self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n\n    def testLineDeletion(self):\n        self.parser.dataReceived(b\"\\x1b[M\\x1b[3M\")\n        occs = occurrences(self.proto)\n\n        for arg in (1, 3):\n            result = self.assertCall(occs.pop(0), \"deleteLine\", (arg,))\n            self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n\n    def testLineInsertion(self):\n        self.parser.dataReceived(b\"\\x1b[L\\x1b[3L\")\n        occs = occurrences(self.proto)\n\n        for arg in (1, 3):\n            result = self.assertCall(occs.pop(0), \"insertLine\", (arg,))\n            self.assertFalse(occurrences(result))\n        self.assertFalse(occs)\n\n\n    def testCursorPosition(self):\n        methods(self.proto)['reportCursorPosition'] = (6, 7)\n        self.parser.dataReceived(b\"\\x1b[6n\")\n        self.assertEqual(self.transport.value(), b\"\\x1b[7;8R\")\n        occs = occurrences(self.proto)\n\n        result = self.assertCall(occs.pop(0), \"reportCursorPosition\")\n        # This isn't really an interesting assert, since it only tests that\n        # our mock setup is working right, but I'll include it anyway.\n        self.assertEqual(result, (6, 7))\n\n\n    def test_applicationDataBytes(self):\n        \"\"\"\n        Contiguous non-control bytes are passed to a single call to the\n        C{write} method of the terminal to which the L{ClientProtocol} is\n        connected.\n        \"\"\"\n        occs = occurrences(self.proto)\n        self.parser.dataReceived(b'a')\n        self.assertCall(occs.pop(0), \"write\", (b\"a\",))\n        self.parser.dataReceived(b'bc')\n        self.assertCall(occs.pop(0), \"write\", (b\"bc\",))\n\n\n    def _applicationDataTest(self, data, calls):\n        occs = occurrences(self.proto)\n        self.parser.dataReceived(data)\n        while calls:\n            self.assertCall(occs.pop(0), *calls.pop(0))\n        self.assertFalse(occs, \"No other calls should happen: %r\" % (occs,))\n\n\n    def test_shiftInAfterApplicationData(self):\n        \"\"\"\n        Application data bytes followed by a shift-in command are passed to a\n        call to C{write} before the terminal's C{shiftIn} method is called.\n        \"\"\"\n        self._applicationDataTest(\n            b'ab\\x15', [\n                (\"write\", (b\"ab\",)),\n                (\"shiftIn\",)])\n\n\n    def test_shiftOutAfterApplicationData(self):\n        \"\"\"\n        Application data bytes followed by a shift-out command are passed to a\n        call to C{write} before the terminal's C{shiftOut} method is called.\n        \"\"\"\n        self._applicationDataTest(\n            b'ab\\x14', [\n                (\"write\", (b\"ab\",)),\n                (\"shiftOut\",)])\n\n\n    def test_cursorBackwardAfterApplicationData(self):\n        \"\"\"\n        Application data bytes followed by a cursor-backward command are passed\n        to a call to C{write} before the terminal's C{cursorBackward} method is\n        called.\n        \"\"\"\n        self._applicationDataTest(\n            b'ab\\x08', [\n                (\"write\", (b\"ab\",)),\n                (\"cursorBackward\",)])\n\n\n    def test_escapeAfterApplicationData(self):\n        \"\"\"\n        Application data bytes followed by an escape character are passed to a\n        call to C{write} before the terminal's handler method for the escape is\n        called.\n        \"\"\"\n        # Test a short escape\n        self._applicationDataTest(\n            b'ab\\x1bD', [\n                (\"write\", (b\"ab\",)),\n                (\"index\",)])\n\n        # And a long escape\n        self._applicationDataTest(\n            b'ab\\x1b[4h', [\n                (\"write\", (b\"ab\",)),\n                (\"setModes\", ([4],))])\n\n        # There's some other cases too, but they're all handled by the same\n        # codepaths as above.\n\n\n\nclass ServerProtocolOutputTests(unittest.TestCase):\n    \"\"\"\n    Tests for the bytes L{ServerProtocol} writes to its transport when its\n    methods are called.\n    \"\"\"\n    # From ECMA 48: CSI is represented by bit combinations 01/11\n    # (representing ESC) and 05/11 in a 7-bit code or by bit\n    # combination 09/11 in an 8-bit code\n    ESC = _ecmaCodeTableCoordinate(1, 11)\n    CSI = ESC + _ecmaCodeTableCoordinate(5, 11)\n\n    def setUp(self):\n        self.protocol = ServerProtocol()\n        self.transport = StringTransport()\n        self.protocol.makeConnection(self.transport)\n\n\n    def test_cursorUp(self):\n        \"\"\"\n        L{ServerProtocol.cursorUp} writes the control sequence\n        ending with L{CSFinalByte.CUU} to its transport.\n        \"\"\"\n        self.protocol.cursorUp(1)\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'1' + CSFinalByte.CUU.value)\n\n\n    def test_cursorDown(self):\n        \"\"\"\n        L{ServerProtocol.cursorDown} writes the control sequence\n        ending with L{CSFinalByte.CUD} to its transport.\n        \"\"\"\n        self.protocol.cursorDown(1)\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'1' + CSFinalByte.CUD.value)\n\n\n    def test_cursorForward(self):\n        \"\"\"\n        L{ServerProtocol.cursorForward} writes the control sequence\n        ending with L{CSFinalByte.CUF} to its transport.\n        \"\"\"\n        self.protocol.cursorForward(1)\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'1' + CSFinalByte.CUF.value)\n\n\n    def test_cursorBackward(self):\n        \"\"\"\n        L{ServerProtocol.cursorBackward} writes the control sequence\n        ending with L{CSFinalByte.CUB} to its transport.\n        \"\"\"\n        self.protocol.cursorBackward(1)\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'1' + CSFinalByte.CUB.value)\n\n\n    def test_cursorPosition(self):\n        \"\"\"\n        L{ServerProtocol.cursorPosition} writes a control sequence\n        ending with L{CSFinalByte.CUP} and containing the expected\n        coordinates to its transport.\n        \"\"\"\n        self.protocol.cursorPosition(0, 0)\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'1;1' + CSFinalByte.CUP.value)\n\n\n    def test_cursorHome(self):\n        \"\"\"\n        L{ServerProtocol.cursorHome} writes a control sequence ending\n        with L{CSFinalByte.CUP} and no parameters, so that the client\n        defaults to (1, 1).\n        \"\"\"\n        self.protocol.cursorHome()\n        self.assertEqual(self.transport.value(),\n                         self.CSI + CSFinalByte.CUP.value)\n\n\n    def test_index(self):\n        \"\"\"\n        L{ServerProtocol.index} writes the control sequence ending in\n        the 8-bit code table coordinates 4, 4.\n\n        Note that ECMA48 5th Edition removes C{IND}.\n        \"\"\"\n        self.protocol.index()\n        self.assertEqual(self.transport.value(),\n                         self.ESC + _ecmaCodeTableCoordinate(4, 4))\n\n\n    def test_reverseIndex(self):\n        \"\"\"\n        L{ServerProtocol.reverseIndex} writes the control sequence\n        ending in the L{C1SevenBit.RI}.\n        \"\"\"\n        self.protocol.reverseIndex()\n        self.assertEqual(self.transport.value(),\n                         self.ESC + C1SevenBit.RI.value)\n\n\n    def test_nextLine(self):\n        \"\"\"\n        L{ServerProtocol.nextLine} writes C{\"\\r\\n\"} to its transport.\n        \"\"\"\n        # Why doesn't it write ESC E?  Because ESC E is poorly supported.  For\n        # example, gnome-terminal (many different versions) fails to scroll if\n        # it receives ESC E and the cursor is already on the last row.\n        self.protocol.nextLine()\n        self.assertEqual(self.transport.value(), b\"\\r\\n\")\n\n\n    def test_setModes(self):\n        \"\"\"\n        L{ServerProtocol.setModes} writes a control sequence\n        containing the requested modes and ending in the\n        L{CSFinalByte.SM}.\n        \"\"\"\n        modesToSet = [modes.KAM, modes.IRM, modes.LNM]\n        self.protocol.setModes(modesToSet)\n        self.assertEqual(self.transport.value(),\n                         self.CSI +\n                         b';'.join(map(intToBytes, modesToSet)) +\n                         CSFinalByte.SM.value)\n\n\n    def test_setPrivateModes(self):\n        \"\"\"\n        L{ServerProtocol.setPrivatesModes} writes a control sequence\n        containing the requested private modes and ending in the\n        L{CSFinalByte.SM}.\n        \"\"\"\n        privateModesToSet = [privateModes.ERROR,\n                             privateModes.COLUMN,\n                             privateModes.ORIGIN]\n        self.protocol.setModes(privateModesToSet)\n        self.assertEqual(self.transport.value(),\n                         self.CSI +\n                         b';'.join(map(intToBytes, privateModesToSet)) +\n                         CSFinalByte.SM.value)\n\n\n    def test_resetModes(self):\n        \"\"\"\n        L{ServerProtocol.resetModes} writes the control sequence\n        ending in the L{CSFinalByte.RM}.\n        \"\"\"\n        modesToSet = [modes.KAM, modes.IRM, modes.LNM]\n        self.protocol.resetModes(modesToSet)\n        self.assertEqual(self.transport.value(),\n                         self.CSI +\n                         b';'.join(map(intToBytes, modesToSet)) +\n                         CSFinalByte.RM.value)\n\n\n    def test_singleShift2(self):\n        \"\"\"\n        L{ServerProtocol.singleShift2} writes an escape sequence\n        followed by L{C1SevenBit.SS2}\n        \"\"\"\n        self.protocol.singleShift2()\n        self.assertEqual(self.transport.value(),\n                         self.ESC + C1SevenBit.SS2.value)\n\n\n    def test_singleShift3(self):\n        \"\"\"\n        L{ServerProtocol.singleShift3} writes an escape sequence\n        followed by L{C1SevenBit.SS3}\n        \"\"\"\n        self.protocol.singleShift3()\n        self.assertEqual(self.transport.value(),\n                         self.ESC + C1SevenBit.SS3.value)\n\n\n    def test_selectGraphicRendition(self):\n        \"\"\"\n        L{ServerProtocol.selectGraphicRendition} writes a control\n        sequence containing the requested attributes and ending with\n        L{CSFinalByte.SGR}\n        \"\"\"\n        self.protocol.selectGraphicRendition(str(BLINK), str(UNDERLINE))\n        self.assertEqual(self.transport.value(),\n                         self.CSI +\n                         intToBytes(BLINK) + b';' + intToBytes(UNDERLINE) +\n                         CSFinalByte.SGR.value)\n\n\n    def test_horizontalTabulationSet(self):\n        \"\"\"\n        L{ServerProtocol.horizontalTabulationSet} writes the escape\n        sequence ending in L{C1SevenBit.HTS}\n        \"\"\"\n        self.protocol.horizontalTabulationSet()\n        self.assertEqual(self.transport.value(),\n                         self.ESC +\n                         C1SevenBit.HTS.value)\n\n\n    def test_eraseToLineEnd(self):\n        \"\"\"\n        L{ServerProtocol.eraseToLineEnd} writes the control sequence\n        sequence ending in L{CSFinalByte.EL} and no parameters,\n        forcing the client to default to 0 (from the active present\n        position's current location to the end of the line.)\n        \"\"\"\n        self.protocol.eraseToLineEnd()\n        self.assertEqual(self.transport.value(),\n                         self.CSI + CSFinalByte.EL.value)\n\n\n    def test_eraseToLineBeginning(self):\n        \"\"\"\n        L{ServerProtocol.eraseToLineBeginning} writes the control\n        sequence sequence ending in L{CSFinalByte.EL} and a parameter\n        of 1 (from the beginning of the line up to and include the\n        active present position's current location.)\n        \"\"\"\n        self.protocol.eraseToLineBeginning()\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'1' + CSFinalByte.EL.value)\n\n\n    def test_eraseLine(self):\n        \"\"\"\n        L{ServerProtocol.eraseLine} writes the control\n        sequence sequence ending in L{CSFinalByte.EL} and a parameter\n        of 2 (the entire line.)\n        \"\"\"\n        self.protocol.eraseLine()\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'2' + CSFinalByte.EL.value)\n\n\n    def test_eraseToDisplayEnd(self):\n        \"\"\"\n        L{ServerProtocol.eraseToDisplayEnd} writes the control\n        sequence sequence ending in L{CSFinalByte.ED} and no parameters,\n        forcing the client to default to 0 (from the active present\n        position's current location to the end of the page.)\n        \"\"\"\n        self.protocol.eraseToDisplayEnd()\n        self.assertEqual(self.transport.value(),\n                         self.CSI + CSFinalByte.ED.value)\n\n\n    def test_eraseToDisplayBeginning(self):\n        \"\"\"\n        L{ServerProtocol.eraseToDisplayBeginning} writes the control\n        sequence sequence ending in L{CSFinalByte.ED} a parameter of 1\n        (from the beginning of the page up to and include the active\n        present position's current location.)\n        \"\"\"\n        self.protocol.eraseToDisplayBeginning()\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'1' + CSFinalByte.ED.value)\n\n\n    def test_eraseToDisplay(self):\n        \"\"\"\n        L{ServerProtocol.eraseDisplay} writes the control sequence\n        sequence ending in L{CSFinalByte.ED} a parameter of 2 (the\n        entire page)\n        \"\"\"\n        self.protocol.eraseDisplay()\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'2' + CSFinalByte.ED.value)\n\n\n    def test_deleteCharacter(self):\n        \"\"\"\n        L{ServerProtocol.deleteCharacter} writes the control sequence\n        containing the number of characters to delete and ending in\n        L{CSFinalByte.DCH}\n        \"\"\"\n        self.protocol.deleteCharacter(4)\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'4' + CSFinalByte.DCH.value)\n\n\n    def test_insertLine(self):\n        \"\"\"\n        L{ServerProtocol.insertLine} writes the control sequence\n        containing the number of lines to insert and ending in\n        L{CSFinalByte.IL}\n        \"\"\"\n        self.protocol.insertLine(5)\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'5' + CSFinalByte.IL.value)\n\n\n    def test_deleteLine(self):\n        \"\"\"\n        L{ServerProtocol.deleteLine} writes the control sequence\n        containing the number of lines to delete and ending in\n        L{CSFinalByte.DL}\n        \"\"\"\n        self.protocol.deleteLine(6)\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'6' + CSFinalByte.DL.value)\n\n\n    def test_setScrollRegionNoArgs(self):\n        \"\"\"\n        With no arguments, L{ServerProtocol.setScrollRegion} writes a\n        control sequence with no parameters, but a parameter\n        separator, and ending in C{b'r'}.\n        \"\"\"\n        self.protocol.setScrollRegion()\n        self.assertEqual(self.transport.value(), self.CSI + b';' + b'r')\n\n\n    def test_setScrollRegionJustFirst(self):\n        \"\"\"\n        With just a value for its C{first} argument,\n        L{ServerProtocol.setScrollRegion} writes a control sequence with\n        that parameter, a parameter separator, and finally a C{b'r'}.\n        \"\"\"\n        self.protocol.setScrollRegion(first=1)\n        self.assertEqual(self.transport.value(), self.CSI + b'1;' + b'r')\n\n\n    def test_setScrollRegionJustLast(self):\n        \"\"\"\n        With just a value for its C{last} argument,\n        L{ServerProtocol.setScrollRegion} writes a control sequence with\n        a parameter separator, that parameter, and finally a C{b'r'}.\n        \"\"\"\n        self.protocol.setScrollRegion(last=1)\n        self.assertEqual(self.transport.value(), self.CSI + b';1' + b'r')\n\n\n    def test_setScrollRegionFirstAndLast(self):\n        \"\"\"\n        When given both C{first} and C{last}\n        L{ServerProtocol.setScrollRegion} writes a control sequence with\n        the first parameter, a parameter separator, the last\n        parameter, and finally a C{b'r'}.\n        \"\"\"\n        self.protocol.setScrollRegion(first=1, last=2)\n        self.assertEqual(self.transport.value(), self.CSI + b'1;2' + b'r')\n\n\n    def test_reportCursorPosition(self):\n        \"\"\"\n        L{ServerProtocol.reportCursorPosition} writes a control\n        sequence ending in L{CSFinalByte.DSR} with a parameter of 6\n        (the Device Status Report returns the current active\n        position.)\n        \"\"\"\n        self.protocol.reportCursorPosition()\n        self.assertEqual(self.transport.value(),\n                         self.CSI + b'6' + CSFinalByte.DSR.value)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_keys.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.ssh.keys}.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom twisted.python.reflect import requireModule\n\ncryptography = requireModule(\"cryptography\")\nif cryptography is None:\n    skipCryptography = 'Cannot run without cryptography.'\n\npyasn1 = requireModule(\"pyasn1\")\n\n\nif cryptography and pyasn1:\n    from twisted.conch.ssh import keys, common, sexpy\n\nimport base64\nimport os\n\nfrom twisted.conch.test import keydata\nfrom twisted.python import randbytes\nfrom twisted.trial import unittest\nfrom twisted.python.compat import long\nfrom twisted.python.filepath import FilePath\n\n\n\nclass KeyTests(unittest.TestCase):\n\n    if cryptography is None:\n        skip = skipCryptography\n    if pyasn1 is None:\n        skip = \"Cannot run without PyASN1\"\n\n\n    def setUp(self):\n        self.rsaObj = keys.Key._fromRSAComponents(\n            n=keydata.RSAData['n'],\n            e=keydata.RSAData['e'],\n            d=keydata.RSAData['d'],\n            p=keydata.RSAData['p'],\n            q=keydata.RSAData['q'],\n            u=keydata.RSAData['u'],\n            )._keyObject\n        self.dsaObj = keys.Key._fromDSAComponents(\n            y=keydata.DSAData['y'],\n            p=keydata.DSAData['p'],\n            q=keydata.DSAData['q'],\n            g=keydata.DSAData['g'],\n            x=keydata.DSAData['x'],\n            )._keyObject\n        self.ecObj = keys.Key._fromECComponents(\n            x=keydata.ECDatanistp256['x'],\n            y=keydata.ECDatanistp256['y'],\n            privateValue=keydata.ECDatanistp256['privateValue'],\n            curve=keydata.ECDatanistp256['curve']\n        )._keyObject\n        self.ecObj384 = keys.Key._fromECComponents(\n            x=keydata.ECDatanistp384['x'],\n            y=keydata.ECDatanistp384['y'],\n            privateValue=keydata.ECDatanistp384['privateValue'],\n            curve=keydata.ECDatanistp384['curve']\n        )._keyObject\n        self.ecObj521 = keys.Key._fromECComponents(\n            x=keydata.ECDatanistp521['x'],\n            y=keydata.ECDatanistp521['y'],\n            privateValue=keydata.ECDatanistp521['privateValue'],\n            curve=keydata.ECDatanistp521['curve']\n        )._keyObject\n        self.rsaSignature = (\n            b\"\\x00\\x00\\x00\\x07ssh-rsa\\x00\\x00\\x01\\x00~Y\\xa3\\xd7\\xfdW\\xc6pu@\"\n            b\"\\xd81\\xa1S\\xf3O\\xdaE\\xf4/\\x1ex\\x1d\\xf1\\x9a\\xe1G3\\xd9\\xd6U\\x1f\"\n            b\"\\x8c\\xd9\\x1b\\x8b\\x90\\x0e\\x8a\\xc1\\x91\\xd8\\x0cd\\xc9\\x0c\\xe7\\xb2\"\n            b\"\\xc9,'=\\x15\\x1cQg\\xe7x\\xb5j\\xdbI\\xc0\\xde\\xafb\\xd7@\\xcar\\x0b\"\n            b\"\\xce\\xa3zM\\x151q5\\xde\\xfa\\x0c{wjKN\\x88\\xcbC\\xe5\\x89\\xc3\\xf9i\"\n            b\"\\x96\\x91\\xdb\\xca}\\xdbR\\x1a\\x13T\\xf9\\x0cDJH\\x0b\\x06\\xcfl\\xf3\"\n            b\"\\x13[\\x82\\xa2\\x9d\\x93\\xfd\\x8e\\xce|\\xfb^n\\xd4\\xed\\xe2\\xd1\\x8a\"\n            b\"\\xb7aY\\x9bB\\x8f\\xa4\\xc7\\xbe7\\xb5\\x0b9j\\xa4.\\x87\\x13\\xf7\\xf0\"\n            b\"\\xda\\xd7\\xd2\\xf9\\x1f9p\\xfd?\\x18\\x0f\\xf2N\\x9b\\xcf/\\x1e)\\n>A\\x19\"\n            b\"\\xc2\\xb5j\\xf9UW\\xd4\\xae\\x87B\\xe6\\x99t\\xa2y\\x90\\x98\\xa2\\xaaf\\xcb\"\n            b\"\\x86\\xe5k\\xe3\\xce\\xe0u\\x1c\\xeb\\x93\\x1aN\\x88\\xc9\\x93Y\\xc3.V\\xb1L\"\n            b\"44`C\\xc7\\xa66\\xaf\\xfa\\x7f\\x04Y\\x92\\xfa\\xa4\\x1a\\x18%\\x19\\xd5 4^\"\n            b\"\\xb9rY\\xba \\x01\\xf9.\\x89%H\\xbe\\x1c\\x83A\\x96\"\n        )\n        self.dsaSignature = (\n            b'\\x00\\x00\\x00\\x07ssh-dss\\x00\\x00\\x00(?\\xc7\\xeb\\x86;\\xd5TFA\\xb4'\n            b'\\xdf\\x0c\\xc4E@4,d\\xbc\\t\\xd9\\xae\\xdd[\\xed-\\x82nQ\\x8cf\\x9b\\xe8\\xe1'\n            b'jrg\\x84p<'\n        )\n        self.patch(randbytes, 'secureRandom', lambda x: b'\\xff' * x)\n        self.keyFile = self.mktemp()\n        with open(self.keyFile, 'wb') as f:\n            f.write(keydata.privateRSA_lsh)\n\n\n    def tearDown(self):\n        os.unlink(self.keyFile)\n\n    def test_size(self):\n        \"\"\"\n        The L{keys.Key.size} method returns the size of key object in bits.\n        \"\"\"\n        self.assertEqual(keys.Key(self.rsaObj).size(), 2048)\n        self.assertEqual(keys.Key(self.dsaObj).size(), 1024)\n        self.assertEqual(keys.Key(self.ecObj).size(), 256)\n        self.assertEqual(keys.Key(self.ecObj384).size(), 384)\n        self.assertEqual(keys.Key(self.ecObj521).size(), 521)\n\n\n\n    def test__guessStringType(self):\n        \"\"\"\n        Test that the _guessStringType method guesses string types\n        correctly.\n        \"\"\"\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.publicRSA_openssh),\n            'public_openssh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.publicDSA_openssh),\n            'public_openssh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.publicECDSA_openssh),\n            'public_openssh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.privateRSA_openssh),\n            'private_openssh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.privateRSA_openssh_new),\n            'private_openssh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.privateDSA_openssh),\n            'private_openssh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.privateDSA_openssh_new),\n            'private_openssh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.privateECDSA_openssh),\n            'private_openssh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.privateECDSA_openssh_new),\n            'private_openssh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.publicRSA_lsh), 'public_lsh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.publicDSA_lsh), 'public_lsh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.privateRSA_lsh), 'private_lsh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.privateDSA_lsh), 'private_lsh')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.privateRSA_agentv3), 'agentv3')\n        self.assertEqual(\n            keys.Key._guessStringType(keydata.privateDSA_agentv3), 'agentv3')\n        self.assertEqual(\n            keys.Key._guessStringType(\n                b'\\x00\\x00\\x00\\x07ssh-rsa\\x00\\x00\\x00\\x01\\x01'),\n            'blob')\n        self.assertEqual(\n            keys.Key._guessStringType(\n                b'\\x00\\x00\\x00\\x07ssh-dss\\x00\\x00\\x00\\x01\\x01'),\n            'blob')\n        self.assertEqual(keys.Key._guessStringType(b'not a key'), None)\n\n\n    def test_public(self):\n        \"\"\"\n        The L{keys.Key.public} method returns a public key for both\n        public and private keys.\n        \"\"\"\n        # NB: This assumes that the private and public keys correspond\n        # to each other.\n        privateRSAKey = keys.Key.fromString(keydata.privateRSA_openssh)\n        publicRSAKey = keys.Key.fromString(keydata.publicRSA_openssh)\n        self.assertEqual(privateRSAKey.public(), publicRSAKey.public())\n\n        privateDSAKey = keys.Key.fromString(keydata.privateDSA_openssh)\n        publicDSAKey = keys.Key.fromString(keydata.publicDSA_openssh)\n        self.assertEqual(privateDSAKey.public(), publicDSAKey.public())\n\n        privateECDSAKey = keys.Key.fromString(keydata.privateECDSA_openssh)\n        publicECDSAKey = keys.Key.fromString(keydata.publicECDSA_openssh)\n        self.assertEqual(privateECDSAKey.public(), publicECDSAKey.public())\n\n\n    def test_isPublic(self):\n        \"\"\"\n        The L{keys.Key.isPublic} method returns True for public keys\n        otherwise False.\n        \"\"\"\n        rsaKey = keys.Key.fromString(keydata.privateRSA_openssh)\n        dsaKey = keys.Key.fromString(keydata.privateDSA_openssh)\n        ecdsaKey = keys.Key.fromString(keydata.privateECDSA_openssh)\n        self.assertTrue(rsaKey.public().isPublic())\n        self.assertFalse(rsaKey.isPublic())\n        self.assertTrue(dsaKey.public().isPublic())\n        self.assertFalse(dsaKey.isPublic())\n        self.assertTrue(ecdsaKey.public().isPublic())\n        self.assertFalse(ecdsaKey.isPublic())\n\n\n\n    def _testPublicPrivateFromString(self, public, private, type, data):\n        self._testPublicFromString(public, type, data)\n        self._testPrivateFromString(private, type, data)\n\n\n    def _testPublicFromString(self, public, type, data):\n        publicKey = keys.Key.fromString(public)\n        self.assertTrue(publicKey.isPublic())\n        self.assertEqual(publicKey.type(), type)\n        for k, v in publicKey.data().items():\n            self.assertEqual(data[k], v)\n\n\n    def _testPrivateFromString(self, private, type, data):\n        privateKey = keys.Key.fromString(private)\n        self.assertFalse(privateKey.isPublic())\n        self.assertEqual(privateKey.type(), type)\n        for k, v in data.items():\n            self.assertEqual(privateKey.data()[k], v)\n\n\n    def test_fromOpenSSH(self):\n        \"\"\"\n        Test that keys are correctly generated from OpenSSH strings.\n        \"\"\"\n        self._testPublicPrivateFromString(keydata.publicECDSA_openssh,\n                keydata.privateECDSA_openssh, 'EC', keydata.ECDatanistp256)\n        self._testPublicPrivateFromString(keydata.publicRSA_openssh,\n                keydata.privateRSA_openssh, 'RSA', keydata.RSAData)\n        self.assertEqual(keys.Key.fromString(\n            keydata.privateRSA_openssh_encrypted,\n            passphrase=b'encrypted'),\n            keys.Key.fromString(keydata.privateRSA_openssh))\n        self.assertEqual(keys.Key.fromString(\n            keydata.privateRSA_openssh_alternate),\n            keys.Key.fromString(keydata.privateRSA_openssh))\n        self._testPublicPrivateFromString(keydata.publicDSA_openssh,\n                keydata.privateDSA_openssh, 'DSA', keydata.DSAData)\n\n    def test_fromOpenSSHErrors(self):\n        \"\"\"\n        Tests for invalid key types.\n        \"\"\"\n        badKey = b\"\"\"-----BEGIN FOO PRIVATE KEY-----\nMIGkAgEBBDAtAi7I8j73WCX20qUM5hhHwHuFzYWYYILs2Sh8UZ+awNkARZ/Fu2LU\nLLl5RtOQpbWgBwYFK4EEACKhZANiAATU17sA9P5FRwSknKcFsjjsk0+E3CeXPYX0\nTk/M0HK3PpWQWgrO8JdRHP9eFE9O/23P8BumwFt7F/AvPlCzVd35VfraFT0o4cCW\nG0RqpQ+np31aKmeJshkcYALEchnU+tQ=\n-----END EC PRIVATE KEY-----\"\"\"\n        self.assertRaises(keys.BadKeyError,\n            keys.Key._fromString_PRIVATE_OPENSSH, badKey, None)\n\n\n    def test_fromOpenSSH_with_whitespace(self):\n        \"\"\"\n        If key strings have trailing whitespace, it should be ignored.\n        \"\"\"\n        # from bug #3391, since our test key data doesn't have\n        # an issue with appended newlines\n        privateDSAData = b\"\"\"-----BEGIN DSA PRIVATE KEY-----\nMIIBuwIBAAKBgQDylESNuc61jq2yatCzZbenlr9llG+p9LhIpOLUbXhhHcwC6hrh\nEZIdCKqTO0USLrGoP5uS9UHAUoeN62Z0KXXWTwOWGEQn/syyPzNJtnBorHpNUT9D\nQzwl1yUa53NNgEctpo4NoEFOx8PuU6iFLyvgHCjNn2MsuGuzkZm7sI9ZpQIVAJiR\n9dPc08KLdpJyRxz8T74b4FQRAoGAGBc4Z5Y6R/HZi7AYM/iNOM8su6hrk8ypkBwR\na3Dbhzk97fuV3SF1SDrcQu4zF7c4CtH609N5nfZs2SUjLLGPWln83Ysb8qhh55Em\nAcHXuROrHS/sDsnqu8FQp86MaudrqMExCOYyVPE7jaBWW+/JWFbKCxmgOCSdViUJ\nesJpBFsCgYEA7+jtVvSt9yrwsS/YU1QGP5wRAiDYB+T5cK4HytzAqJKRdC5qS4zf\nC7R0eKcDHHLMYO39aPnCwXjscisnInEhYGNblTDyPyiyNxAOXuC8x7luTmwzMbNJ\n/ow0IqSj0VF72VJN9uSoPpFd4lLT0zN8v42RWja0M8ohWNf+YNJluPgCFE0PT4Vm\nSUrCyZXsNh6VXwjs3gKQ\n-----END DSA PRIVATE KEY-----\"\"\"\n        self.assertEqual(keys.Key.fromString(privateDSAData),\n                         keys.Key.fromString(privateDSAData + b'\\n'))\n\n\n    def test_fromNewerOpenSSH(self):\n        \"\"\"\n        Newer versions of OpenSSH generate encrypted keys which have a longer\n        IV than the older versions.  These newer keys are also loaded.\n        \"\"\"\n        key = keys.Key.fromString(keydata.privateRSA_openssh_encrypted_aes,\n                                  passphrase=b'testxp')\n        self.assertEqual(key.type(), 'RSA')\n        key2 = keys.Key.fromString(\n            keydata.privateRSA_openssh_encrypted_aes + b'\\n',\n            passphrase=b'testxp')\n        self.assertEqual(key, key2)\n\n\n    def test_fromOpenSSH_v1_format(self):\n        \"\"\"\n        OpenSSH 6.5 introduced a newer \"openssh-key-v1\" private key format\n        (made the default in OpenSSH 7.8).  Loading keys in this format\n        produces identical results to loading the same keys in the old\n        PEM-based format.\n        \"\"\"\n        for old, new in (\n                (keydata.privateRSA_openssh, keydata.privateRSA_openssh_new),\n                (keydata.privateDSA_openssh, keydata.privateDSA_openssh_new),\n                (keydata.privateECDSA_openssh,\n                 keydata.privateECDSA_openssh_new),\n                (keydata.privateECDSA_openssh384,\n                 keydata.privateECDSA_openssh384_new),\n                (keydata.privateECDSA_openssh521,\n                 keydata.privateECDSA_openssh521_new)):\n            self.assertEqual(\n                keys.Key.fromString(new), keys.Key.fromString(old))\n        self.assertEqual(\n            keys.Key.fromString(\n                keydata.privateRSA_openssh_encrypted_new,\n                passphrase=b'encrypted'),\n            keys.Key.fromString(\n                keydata.privateRSA_openssh_encrypted,\n                passphrase=b'encrypted'))\n\n\n    def test_fromOpenSSH_windows_line_endings(self):\n        \"\"\"\n        Test that keys are correctly generated from OpenSSH strings with\n        Windows line endings.\n        \"\"\"\n        privateDSAData = b\"\"\"-----BEGIN DSA PRIVATE KEY-----\nMIIBuwIBAAKBgQDylESNuc61jq2yatCzZbenlr9llG+p9LhIpOLUbXhhHcwC6hrh\nEZIdCKqTO0USLrGoP5uS9UHAUoeN62Z0KXXWTwOWGEQn/syyPzNJtnBorHpNUT9D\nQzwl1yUa53NNgEctpo4NoEFOx8PuU6iFLyvgHCjNn2MsuGuzkZm7sI9ZpQIVAJiR\n9dPc08KLdpJyRxz8T74b4FQRAoGAGBc4Z5Y6R/HZi7AYM/iNOM8su6hrk8ypkBwR\na3Dbhzk97fuV3SF1SDrcQu4zF7c4CtH609N5nfZs2SUjLLGPWln83Ysb8qhh55Em\nAcHXuROrHS/sDsnqu8FQp86MaudrqMExCOYyVPE7jaBWW+/JWFbKCxmgOCSdViUJ\nesJpBFsCgYEA7+jtVvSt9yrwsS/YU1QGP5wRAiDYB+T5cK4HytzAqJKRdC5qS4zf\nC7R0eKcDHHLMYO39aPnCwXjscisnInEhYGNblTDyPyiyNxAOXuC8x7luTmwzMbNJ\n/ow0IqSj0VF72VJN9uSoPpFd4lLT0zN8v42RWja0M8ohWNf+YNJluPgCFE0PT4Vm\nSUrCyZXsNh6VXwjs3gKQ\n-----END DSA PRIVATE KEY-----\"\"\"\n        self.assertEqual(\n            keys.Key.fromString(privateDSAData),\n            keys.Key.fromString(privateDSAData.replace(b'\\n', b'\\r\\n')))\n\n\n    def test_fromLSHPublicUnsupportedType(self):\n        \"\"\"\n        C{BadKeyError} exception is raised when public key has an unknown\n        type.\n        \"\"\"\n        sexp = sexpy.pack([[b'public-key', [b'bad-key', [b'p', b'2']]]])\n\n        self.assertRaises(\n            keys.BadKeyError,\n            keys.Key.fromString, data=b'{' + base64.encodestring(sexp) + b'}',\n            )\n\n\n    def test_fromLSHPrivateUnsupportedType(self):\n        \"\"\"\n        C{BadKeyError} exception is raised when private key has an unknown\n        type.\n        \"\"\"\n        sexp = sexpy.pack([[b'private-key', [b'bad-key', [b'p', b'2']]]])\n\n        self.assertRaises(\n            keys.BadKeyError,\n            keys.Key.fromString, sexp,\n            )\n\n\n    def test_fromLSHRSA(self):\n        \"\"\"\n        RSA public and private keys can be generated from a LSH strings.\n        \"\"\"\n        self._testPublicPrivateFromString(\n            keydata.publicRSA_lsh,\n            keydata.privateRSA_lsh,\n            'RSA',\n            keydata.RSAData,\n            )\n\n\n    def test_fromLSHDSA(self):\n        \"\"\"\n        DSA public and private key can be generated from LSHs.\n        \"\"\"\n        self._testPublicPrivateFromString(\n            keydata.publicDSA_lsh,\n            keydata.privateDSA_lsh,\n            'DSA',\n            keydata.DSAData,\n            )\n\n\n    def test_fromAgentv3(self):\n        \"\"\"\n        Test that keys are correctly generated from Agent v3 strings.\n        \"\"\"\n        self._testPrivateFromString(keydata.privateRSA_agentv3, 'RSA',\n                keydata.RSAData)\n        self._testPrivateFromString(keydata.privateDSA_agentv3, 'DSA',\n                keydata.DSAData)\n        self.assertRaises(keys.BadKeyError, keys.Key.fromString,\n                b'\\x00\\x00\\x00\\x07ssh-foo'+ b'\\x00\\x00\\x00\\x01\\x01'*5)\n\n\n    def test_fromStringErrors(self):\n        \"\"\"\n        keys.Key.fromString should raise BadKeyError when the key is invalid.\n        \"\"\"\n        self.assertRaises(keys.BadKeyError, keys.Key.fromString, b'')\n        # no key data with a bad key type\n        self.assertRaises(keys.BadKeyError, keys.Key.fromString, b'',\n                'bad_type')\n        # trying to decrypt a key which doesn't support encryption\n        self.assertRaises(keys.BadKeyError, keys.Key.fromString,\n                keydata.publicRSA_lsh, passphrase = b'unencrypted')\n        # trying to decrypt a key with the wrong passphrase\n        self.assertRaises(keys.EncryptedKeyError, keys.Key.fromString,\n                keys.Key(self.rsaObj).toString('openssh', b'encrypted'))\n        # key with no key data\n        self.assertRaises(keys.BadKeyError, keys.Key.fromString,\n                b'-----BEGIN RSA KEY-----\\nwA==\\n')\n        # key with invalid DEK Info\n        self.assertRaises(\n            keys.BadKeyError, keys.Key.fromString,\n            b\"\"\"-----BEGIN ENCRYPTED RSA KEY-----\nProc-Type: 4,ENCRYPTED\nDEK-Info: weird type\n\n4Ed/a9OgJWHJsne7yOGWeWMzHYKsxuP9w1v0aYcp+puS75wvhHLiUnNwxz0KDi6n\nT3YkKLBsoCWS68ApR2J9yeQ6R+EyS+UQDrO9nwqo3DB5BT3Ggt8S1wE7vjNLQD0H\ng/SJnlqwsECNhh8aAx+Ag0m3ZKOZiRD5mCkcDQsZET7URSmFytDKOjhFn3u6ZFVB\nsXrfpYc6TJtOQlHd/52JB6aAbjt6afSv955Z7enIi+5yEJ5y7oYQTaE5zrFMP7N5\n9LbfJFlKXxEddy/DErRLxEjmC+t4svHesoJKc2jjjyNPiOoGGF3kJXea62vsjdNV\ngMK5Eged3TBVIk2dv8rtJUvyFeCUtjQ1UJZIebScRR47KrbsIpCmU8I4/uHWm5hW\n0mOwvdx1L/mqx/BHqVU9Dw2COhOdLbFxlFI92chkovkmNk4P48ziyVnpm7ME22sE\nvfCMsyirdqB1mrL4CSM7FXONv+CgfBfeYVkYW8RfJac9U1L/O+JNn7yee414O/rS\nhRYw4UdWnH6Gg6niklVKWNY0ZwUZC8zgm2iqy8YCYuneS37jC+OEKP+/s6HSKuqk\n2bzcl3/TcZXNSM815hnFRpz0anuyAsvwPNRyvxG2/DacJHL1f6luV4B0o6W410yf\nqXQx01DLo7nuyhJqoH3UGCyyXB+/QUs0mbG2PAEn3f5dVs31JMdbt+PrxURXXjKk\n4cexpUcIpqqlfpIRe3RD0sDVbH4OXsGhi2kiTfPZu7mgyFxKopRbn1KwU1qKinfY\nEU9O4PoTak/tPT+5jFNhaP+HrURoi/pU8EAUNSktl7xAkHYwkN/9Cm7DeBghgf3n\n8+tyCGYDsB5utPD0/Xe9yx0Qhc/kMm4xIyQDyA937dk3mUvLC9vulnAP8I+Izim0\nfZ182+D1bWwykoD0997mUHG/AUChWR01V1OLwRyPv2wUtiS8VNG76Y2aqKlgqP1P\nV+IvIEqR4ERvSBVFzXNF8Y6j/sVxo8+aZw+d0L1Ns/R55deErGg3B8i/2EqGd3r+\n0jps9BqFHHWW87n3VyEB3jWCMj8Vi2EJIfa/7pSaViFIQn8LiBLf+zxG5LTOToK5\nxkN42fReDcqi3UNfKNGnv4dsplyTR2hyx65lsj4bRKDGLKOuB1y7iB0AGb0LtcAI\ndcsVlcCeUquDXtqKvRnwfIMg+ZunyjqHBhj3qgRgbXbT6zjaSdNnih569aTg0Vup\nVykzZ7+n/KVcGLmvX0NesdoI7TKbq4TnEIOynuG5Sf+2GpARO5bjcWKSZeN/Ybgk\ngccf8Cqf6XWqiwlWd0B7BR3SymeHIaSymC45wmbgdstrbk7Ppa2Tp9AZku8M2Y7c\n8mY9b+onK075/ypiwBm4L4GRNTFLnoNQJXx0OSl4FNRWsn6ztbD+jZhu8Seu10Jw\nSEJVJ+gmTKdRLYORJKyqhDet6g7kAxs4EoJ25WsOnX5nNr00rit+NkMPA7xbJT+7\nCfI51GQLw7pUPeO2WNt6yZO/YkzZrqvTj5FEwybkUyBv7L0gkqu9wjfDdUw0fVHE\nxEm4DxjEoaIp8dW/JOzXQ2EF+WaSOgdYsw3Ac+rnnjnNptCdOEDGP6QBkt+oXj4P\n-----END RSA PRIVATE KEY-----\"\"\", passphrase='encrypted')\n        # key with invalid encryption type\n        self.assertRaises(\n            keys.BadKeyError, keys.Key.fromString,\n            b\"\"\"-----BEGIN ENCRYPTED RSA KEY-----\nProc-Type: 4,ENCRYPTED\nDEK-Info: FOO-123-BAR,01234567\n\n4Ed/a9OgJWHJsne7yOGWeWMzHYKsxuP9w1v0aYcp+puS75wvhHLiUnNwxz0KDi6n\nT3YkKLBsoCWS68ApR2J9yeQ6R+EyS+UQDrO9nwqo3DB5BT3Ggt8S1wE7vjNLQD0H\ng/SJnlqwsECNhh8aAx+Ag0m3ZKOZiRD5mCkcDQsZET7URSmFytDKOjhFn3u6ZFVB\nsXrfpYc6TJtOQlHd/52JB6aAbjt6afSv955Z7enIi+5yEJ5y7oYQTaE5zrFMP7N5\n9LbfJFlKXxEddy/DErRLxEjmC+t4svHesoJKc2jjjyNPiOoGGF3kJXea62vsjdNV\ngMK5Eged3TBVIk2dv8rtJUvyFeCUtjQ1UJZIebScRR47KrbsIpCmU8I4/uHWm5hW\n0mOwvdx1L/mqx/BHqVU9Dw2COhOdLbFxlFI92chkovkmNk4P48ziyVnpm7ME22sE\nvfCMsyirdqB1mrL4CSM7FXONv+CgfBfeYVkYW8RfJac9U1L/O+JNn7yee414O/rS\nhRYw4UdWnH6Gg6niklVKWNY0ZwUZC8zgm2iqy8YCYuneS37jC+OEKP+/s6HSKuqk\n2bzcl3/TcZXNSM815hnFRpz0anuyAsvwPNRyvxG2/DacJHL1f6luV4B0o6W410yf\nqXQx01DLo7nuyhJqoH3UGCyyXB+/QUs0mbG2PAEn3f5dVs31JMdbt+PrxURXXjKk\n4cexpUcIpqqlfpIRe3RD0sDVbH4OXsGhi2kiTfPZu7mgyFxKopRbn1KwU1qKinfY\nEU9O4PoTak/tPT+5jFNhaP+HrURoi/pU8EAUNSktl7xAkHYwkN/9Cm7DeBghgf3n\n8+tyCGYDsB5utPD0/Xe9yx0Qhc/kMm4xIyQDyA937dk3mUvLC9vulnAP8I+Izim0\nfZ182+D1bWwykoD0997mUHG/AUChWR01V1OLwRyPv2wUtiS8VNG76Y2aqKlgqP1P\nV+IvIEqR4ERvSBVFzXNF8Y6j/sVxo8+aZw+d0L1Ns/R55deErGg3B8i/2EqGd3r+\n0jps9BqFHHWW87n3VyEB3jWCMj8Vi2EJIfa/7pSaViFIQn8LiBLf+zxG5LTOToK5\nxkN42fReDcqi3UNfKNGnv4dsplyTR2hyx65lsj4bRKDGLKOuB1y7iB0AGb0LtcAI\ndcsVlcCeUquDXtqKvRnwfIMg+ZunyjqHBhj3qgRgbXbT6zjaSdNnih569aTg0Vup\nVykzZ7+n/KVcGLmvX0NesdoI7TKbq4TnEIOynuG5Sf+2GpARO5bjcWKSZeN/Ybgk\ngccf8Cqf6XWqiwlWd0B7BR3SymeHIaSymC45wmbgdstrbk7Ppa2Tp9AZku8M2Y7c\n8mY9b+onK075/ypiwBm4L4GRNTFLnoNQJXx0OSl4FNRWsn6ztbD+jZhu8Seu10Jw\nSEJVJ+gmTKdRLYORJKyqhDet6g7kAxs4EoJ25WsOnX5nNr00rit+NkMPA7xbJT+7\nCfI51GQLw7pUPeO2WNt6yZO/YkzZrqvTj5FEwybkUyBv7L0gkqu9wjfDdUw0fVHE\nxEm4DxjEoaIp8dW/JOzXQ2EF+WaSOgdYsw3Ac+rnnjnNptCdOEDGP6QBkt+oXj4P\n-----END RSA PRIVATE KEY-----\"\"\", passphrase='encrypted')\n        # key with bad IV (AES)\n        self.assertRaises(\n            keys.BadKeyError, keys.Key.fromString,\n            b\"\"\"-----BEGIN ENCRYPTED RSA KEY-----\nProc-Type: 4,ENCRYPTED\nDEK-Info: AES-128-CBC,01234\n\n4Ed/a9OgJWHJsne7yOGWeWMzHYKsxuP9w1v0aYcp+puS75wvhHLiUnNwxz0KDi6n\nT3YkKLBsoCWS68ApR2J9yeQ6R+EyS+UQDrO9nwqo3DB5BT3Ggt8S1wE7vjNLQD0H\ng/SJnlqwsECNhh8aAx+Ag0m3ZKOZiRD5mCkcDQsZET7URSmFytDKOjhFn3u6ZFVB\nsXrfpYc6TJtOQlHd/52JB6aAbjt6afSv955Z7enIi+5yEJ5y7oYQTaE5zrFMP7N5\n9LbfJFlKXxEddy/DErRLxEjmC+t4svHesoJKc2jjjyNPiOoGGF3kJXea62vsjdNV\ngMK5Eged3TBVIk2dv8rtJUvyFeCUtjQ1UJZIebScRR47KrbsIpCmU8I4/uHWm5hW\n0mOwvdx1L/mqx/BHqVU9Dw2COhOdLbFxlFI92chkovkmNk4P48ziyVnpm7ME22sE\nvfCMsyirdqB1mrL4CSM7FXONv+CgfBfeYVkYW8RfJac9U1L/O+JNn7yee414O/rS\nhRYw4UdWnH6Gg6niklVKWNY0ZwUZC8zgm2iqy8YCYuneS37jC+OEKP+/s6HSKuqk\n2bzcl3/TcZXNSM815hnFRpz0anuyAsvwPNRyvxG2/DacJHL1f6luV4B0o6W410yf\nqXQx01DLo7nuyhJqoH3UGCyyXB+/QUs0mbG2PAEn3f5dVs31JMdbt+PrxURXXjKk\n4cexpUcIpqqlfpIRe3RD0sDVbH4OXsGhi2kiTfPZu7mgyFxKopRbn1KwU1qKinfY\nEU9O4PoTak/tPT+5jFNhaP+HrURoi/pU8EAUNSktl7xAkHYwkN/9Cm7DeBghgf3n\n8+tyCGYDsB5utPD0/Xe9yx0Qhc/kMm4xIyQDyA937dk3mUvLC9vulnAP8I+Izim0\nfZ182+D1bWwykoD0997mUHG/AUChWR01V1OLwRyPv2wUtiS8VNG76Y2aqKlgqP1P\nV+IvIEqR4ERvSBVFzXNF8Y6j/sVxo8+aZw+d0L1Ns/R55deErGg3B8i/2EqGd3r+\n0jps9BqFHHWW87n3VyEB3jWCMj8Vi2EJIfa/7pSaViFIQn8LiBLf+zxG5LTOToK5\nxkN42fReDcqi3UNfKNGnv4dsplyTR2hyx65lsj4bRKDGLKOuB1y7iB0AGb0LtcAI\ndcsVlcCeUquDXtqKvRnwfIMg+ZunyjqHBhj3qgRgbXbT6zjaSdNnih569aTg0Vup\nVykzZ7+n/KVcGLmvX0NesdoI7TKbq4TnEIOynuG5Sf+2GpARO5bjcWKSZeN/Ybgk\ngccf8Cqf6XWqiwlWd0B7BR3SymeHIaSymC45wmbgdstrbk7Ppa2Tp9AZku8M2Y7c\n8mY9b+onK075/ypiwBm4L4GRNTFLnoNQJXx0OSl4FNRWsn6ztbD+jZhu8Seu10Jw\nSEJVJ+gmTKdRLYORJKyqhDet6g7kAxs4EoJ25WsOnX5nNr00rit+NkMPA7xbJT+7\nCfI51GQLw7pUPeO2WNt6yZO/YkzZrqvTj5FEwybkUyBv7L0gkqu9wjfDdUw0fVHE\nxEm4DxjEoaIp8dW/JOzXQ2EF+WaSOgdYsw3Ac+rnnjnNptCdOEDGP6QBkt+oXj4P\n-----END RSA PRIVATE KEY-----\"\"\", passphrase='encrypted')\n        # key with bad IV (DES3)\n        self.assertRaises(\n            keys.BadKeyError, keys.Key.fromString,\n            b\"\"\"-----BEGIN ENCRYPTED RSA KEY-----\nProc-Type: 4,ENCRYPTED\nDEK-Info: DES-EDE3-CBC,01234\n\n4Ed/a9OgJWHJsne7yOGWeWMzHYKsxuP9w1v0aYcp+puS75wvhHLiUnNwxz0KDi6n\nT3YkKLBsoCWS68ApR2J9yeQ6R+EyS+UQDrO9nwqo3DB5BT3Ggt8S1wE7vjNLQD0H\ng/SJnlqwsECNhh8aAx+Ag0m3ZKOZiRD5mCkcDQsZET7URSmFytDKOjhFn3u6ZFVB\nsXrfpYc6TJtOQlHd/52JB6aAbjt6afSv955Z7enIi+5yEJ5y7oYQTaE5zrFMP7N5\n9LbfJFlKXxEddy/DErRLxEjmC+t4svHesoJKc2jjjyNPiOoGGF3kJXea62vsjdNV\ngMK5Eged3TBVIk2dv8rtJUvyFeCUtjQ1UJZIebScRR47KrbsIpCmU8I4/uHWm5hW\n0mOwvdx1L/mqx/BHqVU9Dw2COhOdLbFxlFI92chkovkmNk4P48ziyVnpm7ME22sE\nvfCMsyirdqB1mrL4CSM7FXONv+CgfBfeYVkYW8RfJac9U1L/O+JNn7yee414O/rS\nhRYw4UdWnH6Gg6niklVKWNY0ZwUZC8zgm2iqy8YCYuneS37jC+OEKP+/s6HSKuqk\n2bzcl3/TcZXNSM815hnFRpz0anuyAsvwPNRyvxG2/DacJHL1f6luV4B0o6W410yf\nqXQx01DLo7nuyhJqoH3UGCyyXB+/QUs0mbG2PAEn3f5dVs31JMdbt+PrxURXXjKk\n4cexpUcIpqqlfpIRe3RD0sDVbH4OXsGhi2kiTfPZu7mgyFxKopRbn1KwU1qKinfY\nEU9O4PoTak/tPT+5jFNhaP+HrURoi/pU8EAUNSktl7xAkHYwkN/9Cm7DeBghgf3n\n8+tyCGYDsB5utPD0/Xe9yx0Qhc/kMm4xIyQDyA937dk3mUvLC9vulnAP8I+Izim0\nfZ182+D1bWwykoD0997mUHG/AUChWR01V1OLwRyPv2wUtiS8VNG76Y2aqKlgqP1P\nV+IvIEqR4ERvSBVFzXNF8Y6j/sVxo8+aZw+d0L1Ns/R55deErGg3B8i/2EqGd3r+\n0jps9BqFHHWW87n3VyEB3jWCMj8Vi2EJIfa/7pSaViFIQn8LiBLf+zxG5LTOToK5\nxkN42fReDcqi3UNfKNGnv4dsplyTR2hyx65lsj4bRKDGLKOuB1y7iB0AGb0LtcAI\ndcsVlcCeUquDXtqKvRnwfIMg+ZunyjqHBhj3qgRgbXbT6zjaSdNnih569aTg0Vup\nVykzZ7+n/KVcGLmvX0NesdoI7TKbq4TnEIOynuG5Sf+2GpARO5bjcWKSZeN/Ybgk\ngccf8Cqf6XWqiwlWd0B7BR3SymeHIaSymC45wmbgdstrbk7Ppa2Tp9AZku8M2Y7c\n8mY9b+onK075/ypiwBm4L4GRNTFLnoNQJXx0OSl4FNRWsn6ztbD+jZhu8Seu10Jw\nSEJVJ+gmTKdRLYORJKyqhDet6g7kAxs4EoJ25WsOnX5nNr00rit+NkMPA7xbJT+7\nCfI51GQLw7pUPeO2WNt6yZO/YkzZrqvTj5FEwybkUyBv7L0gkqu9wjfDdUw0fVHE\nxEm4DxjEoaIp8dW/JOzXQ2EF+WaSOgdYsw3Ac+rnnjnNptCdOEDGP6QBkt+oXj4P\n-----END RSA PRIVATE KEY-----\"\"\", passphrase='encrypted')\n\n\n    def test_fromFile(self):\n        \"\"\"\n        Test that fromFile works correctly.\n        \"\"\"\n        self.assertEqual(keys.Key.fromFile(self.keyFile),\n                keys.Key.fromString(keydata.privateRSA_lsh))\n        self.assertRaises(keys.BadKeyError, keys.Key.fromFile,\n                self.keyFile, 'bad_type')\n        self.assertRaises(keys.BadKeyError, keys.Key.fromFile,\n                self.keyFile, passphrase='unencrypted')\n\n\n    def test_init(self):\n        \"\"\"\n        Test that the PublicKey object is initialized correctly.\n        \"\"\"\n        obj = keys.Key._fromRSAComponents(n=long(5), e=long(3))._keyObject\n        key = keys.Key(obj)\n        self.assertEqual(key._keyObject, obj)\n\n\n    def test_equal(self):\n        \"\"\"\n        Test that Key objects are compared correctly.\n        \"\"\"\n        rsa1 = keys.Key(self.rsaObj)\n        rsa2 = keys.Key(self.rsaObj)\n        rsa3 = keys.Key(\n            keys.Key._fromRSAComponents(n=long(5), e=long(3))._keyObject)\n        dsa = keys.Key(self.dsaObj)\n        self.assertTrue(rsa1 == rsa2)\n        self.assertFalse(rsa1 == rsa3)\n        self.assertFalse(rsa1 == dsa)\n        self.assertFalse(rsa1 == object)\n        self.assertFalse(rsa1 == None)\n\n\n    def test_notEqual(self):\n        \"\"\"\n        Test that Key objects are not-compared correctly.\n        \"\"\"\n        rsa1 = keys.Key(self.rsaObj)\n        rsa2 = keys.Key(self.rsaObj)\n        rsa3 = keys.Key(\n            keys.Key._fromRSAComponents(n=long(5), e=long(3))._keyObject)\n        dsa = keys.Key(self.dsaObj)\n        self.assertFalse(rsa1 != rsa2)\n        self.assertTrue(rsa1 != rsa3)\n        self.assertTrue(rsa1 != dsa)\n        self.assertTrue(rsa1 != object)\n        self.assertTrue(rsa1 != None)\n\n\n    def test_dataError(self):\n        \"\"\"\n        The L{keys.Key.data} method raises RuntimeError for bad keys.\n        \"\"\"\n        badKey = keys.Key(b'')\n        self.assertRaises(RuntimeError, badKey.data)\n\n\n    def test_fingerprintdefault(self):\n        \"\"\"\n        Test that the fingerprint method returns fingerprint in\n        L{FingerprintFormats.MD5-HEX} format by default.\n        \"\"\"\n        self.assertEqual(keys.Key(self.rsaObj).fingerprint(),\n            '85:25:04:32:58:55:96:9f:57:ee:fb:a8:1a:ea:69:da')\n        self.assertEqual(keys.Key(self.dsaObj).fingerprint(),\n            '63:15:b3:0e:e6:4f:50:de:91:48:3d:01:6b:b3:13:c1')\n\n\n    def test_fingerprint_md5_hex(self):\n        \"\"\"\n        fingerprint method generates key fingerprint in\n        L{FingerprintFormats.MD5-HEX} format if explicitly specified.\n        \"\"\"\n        self.assertEqual(\n            keys.Key(self.rsaObj).fingerprint(\n                keys.FingerprintFormats.MD5_HEX),\n            '85:25:04:32:58:55:96:9f:57:ee:fb:a8:1a:ea:69:da')\n        self.assertEqual(\n            keys.Key(self.dsaObj).fingerprint(\n                keys.FingerprintFormats.MD5_HEX),\n            '63:15:b3:0e:e6:4f:50:de:91:48:3d:01:6b:b3:13:c1')\n\n\n    def test_fingerprintsha256(self):\n        \"\"\"\n        fingerprint method generates key fingerprint in\n        L{FingerprintFormats.SHA256-BASE64} format if explicitly specified.\n        \"\"\"\n        self.assertEqual(\n            keys.Key(self.rsaObj).fingerprint(\n                keys.FingerprintFormats.SHA256_BASE64),\n            'FBTCOoknq0mHy+kpfnY9tDdcAJuWtCpuQMaV3EsvbUI=')\n        self.assertEqual(\n            keys.Key(self.dsaObj).fingerprint(\n                keys.FingerprintFormats.SHA256_BASE64),\n            'Wz5o2YbKyxOEcJn1au/UaALSVruUzfz0vaLI1xiIGyY=')\n\n\n    def test_fingerprintBadFormat(self):\n        \"\"\"\n        A C{BadFingerPrintFormat} error is raised when unsupported\n        formats are requested.\n        \"\"\"\n        with self.assertRaises(keys.BadFingerPrintFormat) as em:\n            keys.Key(self.rsaObj).fingerprint('sha256-base')\n        self.assertEqual('Unsupported fingerprint format: sha256-base',\n            em.exception.args[0])\n\n\n    def test_type(self):\n        \"\"\"\n        Test that the type method returns the correct type for an object.\n        \"\"\"\n        self.assertEqual(keys.Key(self.rsaObj).type(), 'RSA')\n        self.assertEqual(keys.Key(self.rsaObj).sshType(), b'ssh-rsa')\n        self.assertEqual(keys.Key(self.dsaObj).type(), 'DSA')\n        self.assertEqual(keys.Key(self.dsaObj).sshType(), b'ssh-dss')\n        self.assertEqual(keys.Key(self.ecObj).type(), 'EC')\n        self.assertEqual(keys.Key(self.ecObj).sshType(),\n                        keydata.ECDatanistp256['curve'])\n        self.assertRaises(RuntimeError, keys.Key(None).type)\n        self.assertRaises(RuntimeError, keys.Key(None).sshType)\n        self.assertRaises(RuntimeError, keys.Key(self).type)\n        self.assertRaises(RuntimeError, keys.Key(self).sshType)\n\n    def test_fromBlobUnsupportedType(self):\n        \"\"\"\n        A C{BadKeyError} error is raised whey the blob has an unsupported\n        key type.\n        \"\"\"\n        badBlob = common.NS(b'ssh-bad')\n\n        self.assertRaises(keys.BadKeyError,\n                keys.Key.fromString, badBlob)\n\n    def test_fromBlobRSA(self):\n        \"\"\"\n        A public RSA key is correctly generated from a public key blob.\n        \"\"\"\n        rsaPublicData = {\n            'n': keydata.RSAData['n'],\n            'e': keydata.RSAData['e'],\n            }\n        rsaBlob = (\n            common.NS(b'ssh-rsa') +\n            common.MP(rsaPublicData['e']) +\n            common.MP(rsaPublicData['n'])\n            )\n\n        rsaKey = keys.Key.fromString(rsaBlob)\n\n        self.assertTrue(rsaKey.isPublic())\n        self.assertEqual(rsaPublicData, rsaKey.data())\n\n\n    def test_fromBlobDSA(self):\n        \"\"\"\n        A public DSA key is correctly generated from a public key blob.\n        \"\"\"\n        dsaPublicData = {\n            'p': keydata.DSAData['p'],\n            'q': keydata.DSAData['q'],\n            'g': keydata.DSAData['g'],\n            'y': keydata.DSAData['y'],\n            }\n        dsaBlob = (\n            common.NS(b'ssh-dss') +\n            common.MP(dsaPublicData['p']) +\n            common.MP(dsaPublicData['q']) +\n            common.MP(dsaPublicData['g']) +\n            common.MP(dsaPublicData['y'])\n            )\n\n        dsaKey = keys.Key.fromString(dsaBlob)\n\n        self.assertTrue(dsaKey.isPublic())\n        self.assertEqual(dsaPublicData, dsaKey.data())\n\n    def test_fromBlobECDSA(self):\n        \"\"\"\n        Key.fromString generates ECDSA keys from blobs.\n        \"\"\"\n        from cryptography import utils\n\n        ecPublicData = {\n            'x': keydata.ECDatanistp256['x'],\n            'y': keydata.ECDatanistp256['y'],\n            'curve': keydata.ECDatanistp256['curve']\n            }\n\n        ecblob = (common.NS(ecPublicData['curve']) +\n                  common.NS(ecPublicData['curve'][-8:]) +\n                  common.NS(b'\\x04' +\n                    utils.int_to_bytes(ecPublicData['x'],  32) +\n                    utils.int_to_bytes(ecPublicData['y'],  32))\n            )\n\n        eckey = keys.Key.fromString(ecblob)\n        self.assertTrue(eckey.isPublic())\n        self.assertEqual(ecPublicData, eckey.data())\n\n    def test_fromPrivateBlobUnsupportedType(self):\n        \"\"\"\n        C{BadKeyError} is raised when loading a private blob with an\n        unsupported type.\n        \"\"\"\n        badBlob = common.NS(b'ssh-bad')\n\n        self.assertRaises(\n            keys.BadKeyError, keys.Key._fromString_PRIVATE_BLOB, badBlob)\n\n\n    def test_fromPrivateBlobRSA(self):\n        \"\"\"\n        A private RSA key is correctly generated from a private key blob.\n        \"\"\"\n        rsaBlob = (\n            common.NS(b'ssh-rsa') +\n            common.MP(keydata.RSAData['n']) +\n            common.MP(keydata.RSAData['e']) +\n            common.MP(keydata.RSAData['d']) +\n            common.MP(keydata.RSAData['u']) +\n            common.MP(keydata.RSAData['p']) +\n            common.MP(keydata.RSAData['q'])\n            )\n\n        rsaKey = keys.Key._fromString_PRIVATE_BLOB(rsaBlob)\n\n        self.assertFalse(rsaKey.isPublic())\n        self.assertEqual(keydata.RSAData, rsaKey.data())\n\n\n    def test_fromPrivateBlobDSA(self):\n        \"\"\"\n        A private DSA key is correctly generated from a private key blob.\n        \"\"\"\n        dsaBlob = (\n            common.NS(b'ssh-dss') +\n            common.MP(keydata.DSAData['p']) +\n            common.MP(keydata.DSAData['q']) +\n            common.MP(keydata.DSAData['g']) +\n            common.MP(keydata.DSAData['y']) +\n            common.MP(keydata.DSAData['x'])\n            )\n\n        dsaKey = keys.Key._fromString_PRIVATE_BLOB(dsaBlob)\n\n        self.assertFalse(dsaKey.isPublic())\n        self.assertEqual(keydata.DSAData, dsaKey.data())\n\n\n    def test_fromPrivateBlobECDSA(self):\n        \"\"\"\n        A private EC key is correctly generated from a private key blob.\n        \"\"\"\n        from cryptography.hazmat.backends import default_backend\n        from cryptography.hazmat.primitives.asymmetric import ec\n        from cryptography.hazmat.primitives import serialization\n        publicNumbers = ec.EllipticCurvePublicNumbers(\n            x=keydata.ECDatanistp256['x'], y=keydata.ECDatanistp256['y'],\n            curve=ec.SECP256R1())\n        ecblob = (\n            common.NS(keydata.ECDatanistp256['curve']) +\n            common.NS(keydata.ECDatanistp256['curve'][-8:]) +\n            common.NS(publicNumbers.public_key(default_backend()).public_bytes(\n                serialization.Encoding.X962,\n                serialization.PublicFormat.UncompressedPoint\n            )) +\n            common.MP(keydata.ECDatanistp256['privateValue'])\n        )\n\n        eckey = keys.Key._fromString_PRIVATE_BLOB(ecblob)\n\n        self.assertFalse(eckey.isPublic())\n        self.assertEqual(keydata.ECDatanistp256, eckey.data())\n\n\n    def test_blobRSA(self):\n        \"\"\"\n        Return the over-the-wire SSH format of the RSA public key.\n        \"\"\"\n        self.assertEqual(\n            keys.Key(self.rsaObj).blob(),\n            common.NS(b'ssh-rsa') +\n            common.MP(self.rsaObj.private_numbers().public_numbers.e) +\n            common.MP(self.rsaObj.private_numbers().public_numbers.n)\n            )\n\n\n    def test_blobDSA(self):\n        \"\"\"\n        Return the over-the-wire SSH format of the DSA public key.\n        \"\"\"\n        publicNumbers = self.dsaObj.private_numbers().public_numbers\n\n        self.assertEqual(\n            keys.Key(self.dsaObj).blob(),\n            common.NS(b'ssh-dss') +\n            common.MP(publicNumbers.parameter_numbers.p) +\n            common.MP(publicNumbers.parameter_numbers.q) +\n            common.MP(publicNumbers.parameter_numbers.g) +\n            common.MP(publicNumbers.y)\n            )\n\n\n    def test_blobEC(self):\n        \"\"\"\n        Return the over-the-wire SSH format of the EC public key.\n        \"\"\"\n        from cryptography import utils\n\n        byteLength = (self.ecObj.curve.key_size + 7) // 8\n        self.assertEqual(\n            keys.Key(self.ecObj).blob(),\n            common.NS(keydata.ECDatanistp256['curve']) +\n            common.NS(keydata.ECDatanistp256['curve'][-8:]) +\n            common.NS(b'\\x04' +\n               utils.int_to_bytes(\n                 self.ecObj.private_numbers().public_numbers.x, byteLength) +\n                   utils.int_to_bytes(\n                   self.ecObj.private_numbers().public_numbers.y, byteLength))\n            )\n\n\n    def test_blobNoKey(self):\n        \"\"\"\n        C{RuntimeError} is raised when the blob is requested for a Key\n        which is not wrapping anything.\n        \"\"\"\n        badKey = keys.Key(None)\n\n        self.assertRaises(RuntimeError, badKey.blob)\n\n\n    def test_privateBlobRSA(self):\n        \"\"\"\n        L{keys.Key.privateBlob} returns the SSH protocol-level format of an\n        RSA private key.\n        \"\"\"\n        from cryptography.hazmat.primitives.asymmetric import rsa\n        numbers = self.rsaObj.private_numbers()\n        u = rsa.rsa_crt_iqmp(numbers.q, numbers.p)\n        self.assertEqual(\n            keys.Key(self.rsaObj).privateBlob(),\n            common.NS(b'ssh-rsa') +\n            common.MP(self.rsaObj.private_numbers().public_numbers.n) +\n            common.MP(self.rsaObj.private_numbers().public_numbers.e) +\n            common.MP(self.rsaObj.private_numbers().d) +\n            common.MP(u) +\n            common.MP(self.rsaObj.private_numbers().p) +\n            common.MP(self.rsaObj.private_numbers().q)\n            )\n\n\n    def test_privateBlobDSA(self):\n        \"\"\"\n        L{keys.Key.privateBlob} returns the SSH protocol-level format of a DSA\n        private key.\n        \"\"\"\n        publicNumbers = self.dsaObj.private_numbers().public_numbers\n\n        self.assertEqual(\n            keys.Key(self.dsaObj).privateBlob(),\n            common.NS(b'ssh-dss') +\n            common.MP(publicNumbers.parameter_numbers.p) +\n            common.MP(publicNumbers.parameter_numbers.q) +\n            common.MP(publicNumbers.parameter_numbers.g) +\n            common.MP(publicNumbers.y) +\n            common.MP(self.dsaObj.private_numbers().x)\n            )\n\n\n    def test_privateBlobEC(self):\n        \"\"\"\n        L{keys.Key.privateBlob} returns the SSH ptotocol-level format of EC\n        private key.\n        \"\"\"\n        self.assertEqual(\n            keys.Key(self.ecObj).privateBlob(),\n            common.NS(keydata.ECDatanistp256['curve']) +\n            common.MP(self.ecObj.private_numbers().public_numbers.x) +\n            common.MP(self.ecObj.private_numbers().public_numbers.y) +\n            common.MP(self.ecObj.private_numbers().private_value)\n            )\n\n\n    def test_privateBlobNoKeyObject(self):\n        \"\"\"\n        Raises L{RuntimeError} if the underlying key object does not exists.\n        \"\"\"\n        badKey = keys.Key(None)\n\n        self.assertRaises(RuntimeError, badKey.privateBlob)\n\n\n    def test_toOpenSSHRSA(self):\n        \"\"\"\n        L{keys.Key.toString} serializes an RSA key in OpenSSH format.\n        \"\"\"\n        key = keys.Key.fromString(keydata.privateRSA_agentv3)\n        self.assertEqual(key.toString('openssh'), keydata.privateRSA_openssh)\n        self.assertEqual(key.toString('openssh', b'encrypted'),\n                keydata.privateRSA_openssh_encrypted)\n        self.assertEqual(key.public().toString('openssh'),\n                keydata.publicRSA_openssh[:-8]) # no comment\n        self.assertEqual(key.public().toString('openssh', b'comment'),\n                keydata.publicRSA_openssh)\n\n\n    def test_toOpenSSHDSA(self):\n        \"\"\"\n        L{keys.Key.toString} serializes a DSA key in OpenSSH format.\n        \"\"\"\n        key = keys.Key.fromString(keydata.privateDSA_lsh)\n        self.assertEqual(key.toString('openssh'), keydata.privateDSA_openssh)\n        self.assertEqual(key.public().toString('openssh', b'comment'),\n                keydata.publicDSA_openssh)\n        self.assertEqual(key.public().toString('openssh'),\n                keydata.publicDSA_openssh[:-8]) # no comment\n\n\n    def test_toOpenSSHECDSA(self):\n        \"\"\"\n        L{keys.Key.toString} serializes a ECDSA key in OpenSSH format.\n        \"\"\"\n        key = keys.Key.fromString(keydata.privateECDSA_openssh)\n        self.assertEqual(key.public().toString('openssh', b'comment'),\n                keydata.publicECDSA_openssh)\n        self.assertEqual(key.public().toString('openssh'),\n                keydata.publicECDSA_openssh[:-8]) # no comment\n\n\n    def test_toLSHRSA(self):\n        \"\"\"\n        L{keys.Key.toString} serializes an RSA key in LSH format.\n        \"\"\"\n        key = keys.Key.fromString(keydata.privateRSA_openssh)\n        self.assertEqual(key.toString('lsh'), keydata.privateRSA_lsh)\n        self.assertEqual(key.public().toString('lsh'),\n                keydata.publicRSA_lsh)\n\n\n    def test_toLSHDSA(self):\n        \"\"\"\n        L{keys.Key.toString} serializes a DSA key in LSH format.\n        \"\"\"\n        key = keys.Key.fromString(keydata.privateDSA_openssh)\n        self.assertEqual(key.toString('lsh'), keydata.privateDSA_lsh)\n        self.assertEqual(key.public().toString('lsh'),\n                keydata.publicDSA_lsh)\n\n\n    def test_toAgentv3RSA(self):\n        \"\"\"\n        L{keys.Key.toString} serializes an RSA key in Agent v3 format.\n        \"\"\"\n        key = keys.Key.fromString(keydata.privateRSA_openssh)\n        self.assertEqual(key.toString('agentv3'), keydata.privateRSA_agentv3)\n\n\n    def test_toAgentv3DSA(self):\n        \"\"\"\n        L{keys.Key.toString} serializes a DSA key in Agent v3 format.\n        \"\"\"\n        key = keys.Key.fromString(keydata.privateDSA_openssh)\n        self.assertEqual(key.toString('agentv3'), keydata.privateDSA_agentv3)\n\n\n    def test_toStringErrors(self):\n        \"\"\"\n        L{keys.Key.toString} raises L{keys.BadKeyError} when passed an invalid\n        format type.\n        \"\"\"\n        self.assertRaises(keys.BadKeyError, keys.Key(self.rsaObj).toString,\n                'bad_type')\n\n\n    def test_signAndVerifyRSA(self):\n        \"\"\"\n        Signed data can be verified using RSA.\n        \"\"\"\n        data = b'some-data'\n        key = keys.Key.fromString(keydata.privateRSA_openssh)\n        signature = key.sign(data)\n        self.assertTrue(key.public().verify(signature, data))\n        self.assertTrue(key.verify(signature, data))\n\n\n    def test_signAndVerifyDSA(self):\n        \"\"\"\n        Signed data can be verified using DSA.\n        \"\"\"\n        data = b'some-data'\n        key = keys.Key.fromString(keydata.privateDSA_openssh)\n        signature = key.sign(data)\n        self.assertTrue(key.public().verify(signature, data))\n        self.assertTrue(key.verify(signature, data))\n\n\n    def test_signAndVerifyEC(self):\n        \"\"\"\n        Signed data can be verified using EC.\n        \"\"\"\n        data = b'some-data'\n        key = keys.Key.fromString(keydata.privateECDSA_openssh)\n        signature = key.sign(data)\n\n        key384 = keys.Key.fromString(keydata.privateECDSA_openssh384)\n        signature384 = key384.sign(data)\n\n        key521 = keys.Key.fromString(keydata.privateECDSA_openssh521)\n        signature521 = key521.sign(data)\n\n        self.assertTrue(key.public().verify(signature, data))\n        self.assertTrue(key.verify(signature, data))\n        self.assertTrue(key384.public().verify(signature384, data))\n        self.assertTrue(key384.verify(signature384, data))\n        self.assertTrue(key521.public().verify(signature521, data))\n        self.assertTrue(key521.verify(signature521, data))\n\n\n    def test_verifyRSA(self):\n        \"\"\"\n        A known-good RSA signature verifies successfully.\n        \"\"\"\n        key = keys.Key.fromString(keydata.publicRSA_openssh)\n        self.assertTrue(key.verify(self.rsaSignature, b''))\n        self.assertFalse(key.verify(self.rsaSignature, b'a'))\n        self.assertFalse(key.verify(self.dsaSignature, b''))\n\n\n    def test_verifyDSA(self):\n        \"\"\"\n        A known-good DSA signature verifies successfully.\n        \"\"\"\n        key = keys.Key.fromString(keydata.publicDSA_openssh)\n        self.assertTrue(key.verify(self.dsaSignature, b''))\n        self.assertFalse(key.verify(self.dsaSignature, b'a'))\n        self.assertFalse(key.verify(self.rsaSignature, b''))\n\n\n    def test_verifyDSANoPrefix(self):\n        \"\"\"\n        Some commercial SSH servers send DSA keys as 2 20-byte numbers;\n        they are still verified as valid keys.\n        \"\"\"\n        key = keys.Key.fromString(keydata.publicDSA_openssh)\n        self.assertTrue(key.verify(self.dsaSignature[-40:], b''))\n\n\n    def test_reprPrivateRSA(self):\n        \"\"\"\n        The repr of a L{keys.Key} contains all of the RSA components for an RSA\n        private key.\n        \"\"\"\n        self.assertEqual(repr(keys.Key(self.rsaObj)),\n\"\"\"<RSA Private Key (2048 bits)\nattr d:\n\\t21:4c:08:66:a2:28:d5:b4:fb:8e:0f:72:1b:85:09:\n\\t00:b9:f2:4e:37:f0:1c:57:4b:e3:51:7f:9e:23:a7:\n\\te4:3a:98:55:1b:ea:8b:7a:98:1e:bc:d8:ba:b1:f9:\n\\t89:12:18:60:ac:e8:cc:0b:4e:09:5a:40:6a:ba:2f:\n\\t99:f8:b3:24:60:84:b9:ce:69:95:9a:f9:e2:fc:1f:\n\\t51:4d:27:15:db:2b:27:ad:ef:b4:69:ac:be:7d:10:\n\\teb:86:47:70:73:b4:00:87:95:15:3b:37:f9:e7:14:\n\\te7:80:bb:68:1e:1b:e6:dd:bb:73:63:b9:67:e6:b2:\n\\t27:7f:cf:cf:30:9b:c2:98:fd:d9:18:36:2f:36:2e:\n\\tf1:3d:81:7a:9f:e1:03:2d:47:db:34:51:62:39:dd:\n\\t4f:e9:ac:a8:8b:d9:d6:f3:84:c4:17:b9:71:9d:06:\n\\t08:42:78:4d:bb:c5:2a:f4:c3:58:cd:55:2b:ed:be:\n\\t33:5f:04:ea:7b:e6:04:24:63:f2:2d:d7:3d:1b:6c:\n\\td5:9c:63:43:2f:92:88:8d:3e:6e:da:18:37:d8:0f:\n\\t25:67:89:1d:b9:46:34:5e:c9:ce:c4:8b:ed:92:5a:\n\\t33:07:0f:df:86:08:f9:92:e9:db:eb:38:08:36:c9:\n\\tcd:cd:0a:01:48:5b:39:3e:7a:ca:c6:80:a9:dc:d4:\n\\t39\nattr e:\n\\t01:00:01\nattr n:\n\\t00:d5:6a:ac:78:23:d6:d6:1b:ec:25:a1:50:c4:77:\n\\t63:50:84:45:01:55:42:14:2a:2a:e0:d0:60:ee:d4:\n\\te9:a3:ad:4a:fa:39:06:5e:84:55:75:5f:00:36:bf:\n\\t6f:aa:2a:3f:83:26:37:c1:69:2e:5b:fd:f0:f3:d2:\n\\t7d:d6:98:cd:3a:40:78:d5:ca:a8:18:c0:11:93:24:\n\\t09:0c:81:4c:8f:f7:9c:ed:13:16:6a:a4:04:e9:49:\n\\t77:c3:e4:55:64:b3:79:68:9e:2c:08:eb:ac:e8:04:\n\\t2d:21:77:05:a7:8e:ef:53:30:0d:a5:e5:bb:3d:6a:\n\\te2:09:36:6f:fd:34:d3:7d:6f:46:ff:87:da:a9:29:\n\\t27:aa:ff:ad:f5:85:e6:3e:1a:b8:7a:1d:4a:b1:ea:\n\\tc0:5a:f7:30:df:1f:c2:a4:e4:ef:3f:91:49:96:40:\n\\td5:19:77:2d:37:c3:5e:ec:9d:a6:3a:44:a5:c2:a4:\n\\t29:dd:d5:ba:9c:3d:45:b3:c6:2c:18:64:d5:ba:3d:\n\\tdf:ab:7f:cd:42:ac:a7:f1:18:0b:a0:58:15:62:0b:\n\\ta4:2a:6e:43:c3:e4:04:9f:35:a3:47:8e:46:ed:33:\n\\ta5:65:bd:bc:3b:29:6e:02:0b:57:df:74:e8:13:b4:\n\\t37:35:7e:83:5f:20:26:60:a6:dc:ad:8b:c6:6c:79:\n\\t98:f7\nattr p:\n\\t00:d9:70:06:d8:e2:bc:d4:78:91:50:94:d4:c1:1b:\n\\t89:38:6c:46:64:5a:51:a0:9a:07:3d:48:8f:03:51:\n\\tcc:6b:12:8e:7d:1a:b1:65:e7:71:75:39:e0:32:05:\n\\t75:8d:18:4c:af:93:b1:49:b1:66:5f:78:62:7a:d1:\n\\t0c:ca:e6:4d:43:b3:9c:f4:6b:7d:e6:0c:98:dc:cf:\n\\t21:62:8e:d5:2e:12:de:04:ae:d7:24:6e:83:31:a2:\n\\t15:a2:44:3d:22:a9:62:26:22:b9:b2:ed:54:0a:9d:\n\\t08:83:a7:07:0d:ff:19:18:8e:d8:ab:1d:da:48:9c:\n\\t31:68:11:a1:66:6d:e3:d8:1d\nattr q:\n\\t00:fb:44:17:8b:a4:36:be:1e:37:1d:a7:f6:61:6c:\n\\t04:c4:aa:dd:78:3e:07:8c:1e:33:02:ae:03:14:87:\n\\t83:7a:e5:9e:7d:08:67:a8:f2:aa:bf:12:70:cf:72:\n\\ta9:a7:c7:0b:1d:88:d5:20:fd:9c:63:ca:47:30:55:\n\\t4e:8b:c4:cf:f4:7f:16:a4:92:12:74:a1:09:c2:c4:\n\\t6e:9c:8c:33:ef:a5:e5:f7:e0:2b:ad:4f:5c:11:aa:\n\\t1a:84:37:5b:fd:7a:ea:c3:cd:7c:b0:c8:e4:1f:54:\n\\t63:b5:c7:af:df:f4:09:a7:fc:c7:25:fc:5c:e9:91:\n\\td7:92:c5:98:1e:56:d3:b1:23\nattr u:\n\\t00:85:4b:1b:7a:9b:12:10:37:9e:1f:ad:5e:da:fe:\n\\tc6:96:fe:df:35:6b:b9:34:e2:16:97:92:26:09:bd:\n\\tbd:70:20:03:a7:35:bd:2d:1b:a0:d2:07:47:2b:d4:\n\\tde:a8:a8:07:07:1b:b8:04:20:a7:27:41:3c:6c:39:\n\\t39:e9:41:ce:e7:17:1d:d1:4c:5c:bc:3d:d2:26:26:\n\\tfe:6a:d6:fd:48:72:ae:46:fa:7b:c3:d3:19:60:44:\n\\t1d:a5:13:a7:80:f5:63:29:d4:7a:5d:06:07:16:5d:\n\\tf6:8b:3d:cb:64:3a:e2:84:5a:4d:8c:06:2d:2d:9d:\n\\t1c:eb:83:4c:78:3d:79:54:ce>\"\"\")\n\n\n    def test_reprPublicRSA(self):\n        \"\"\"\n        The repr of a L{keys.Key} contains all of the RSA components for an RSA\n        public key.\n        \"\"\"\n        self.assertEqual(repr(keys.Key(self.rsaObj).public()),\n\"\"\"<RSA Public Key (2048 bits)\nattr e:\n\\t01:00:01\nattr n:\n\\t00:d5:6a:ac:78:23:d6:d6:1b:ec:25:a1:50:c4:77:\n\\t63:50:84:45:01:55:42:14:2a:2a:e0:d0:60:ee:d4:\n\\te9:a3:ad:4a:fa:39:06:5e:84:55:75:5f:00:36:bf:\n\\t6f:aa:2a:3f:83:26:37:c1:69:2e:5b:fd:f0:f3:d2:\n\\t7d:d6:98:cd:3a:40:78:d5:ca:a8:18:c0:11:93:24:\n\\t09:0c:81:4c:8f:f7:9c:ed:13:16:6a:a4:04:e9:49:\n\\t77:c3:e4:55:64:b3:79:68:9e:2c:08:eb:ac:e8:04:\n\\t2d:21:77:05:a7:8e:ef:53:30:0d:a5:e5:bb:3d:6a:\n\\te2:09:36:6f:fd:34:d3:7d:6f:46:ff:87:da:a9:29:\n\\t27:aa:ff:ad:f5:85:e6:3e:1a:b8:7a:1d:4a:b1:ea:\n\\tc0:5a:f7:30:df:1f:c2:a4:e4:ef:3f:91:49:96:40:\n\\td5:19:77:2d:37:c3:5e:ec:9d:a6:3a:44:a5:c2:a4:\n\\t29:dd:d5:ba:9c:3d:45:b3:c6:2c:18:64:d5:ba:3d:\n\\tdf:ab:7f:cd:42:ac:a7:f1:18:0b:a0:58:15:62:0b:\n\\ta4:2a:6e:43:c3:e4:04:9f:35:a3:47:8e:46:ed:33:\n\\ta5:65:bd:bc:3b:29:6e:02:0b:57:df:74:e8:13:b4:\n\\t37:35:7e:83:5f:20:26:60:a6:dc:ad:8b:c6:6c:79:\n\\t98:f7>\"\"\")\n\n\n    def test_reprPublicECDSA(self):\n        \"\"\"\n        The repr of a L{keys.Key} contains all the OpenSSH format for an ECDSA\n        public key.\n        \"\"\"\n        self.assertEqual(repr(keys.Key(self.ecObj).public()),\n\"\"\"<Elliptic Curve Public Key (256 bits)\ncurve:\n\\tecdsa-sha2-nistp256\nx:\n\\t76282513020392096317118503144964731774299773481750550543382904345687059013883\ny:\"\"\" +\n\"\\n\\t8154319786460285263226566476944164753434437589431431968106113715931064\" +\n\"6683104>\\n\")\n\n\n    def test_reprPrivateECDSA(self):\n        \"\"\"\n        The repr of a L{keys.Key} contains all the OpenSSH format for an ECDSA\n        private key.\n        \"\"\"\n        self.assertEqual(repr(keys.Key(self.ecObj)),\n\"\"\"<Elliptic Curve Private Key (256 bits)\ncurve:\n\\tecdsa-sha2-nistp256\nprivateValue:\n\\t34638743477210341700964008455655698253555655678826059678074967909361042656500\nx:\n\\t76282513020392096317118503144964731774299773481750550543382904345687059013883\ny:\"\"\" +\n\"\\n\\t8154319786460285263226566476944164753434437589431431968106113715931064\" +\n\"6683104>\\n\")\n\n\n\nclass PersistentRSAKeyTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{keys._getPersistentRSAKey}.\n    \"\"\"\n\n    if cryptography is None:\n        skip = skipCryptography\n\n\n    def test_providedArguments(self):\n        \"\"\"\n        L{keys._getPersistentRSAKey} will put the key in\n        C{directory}/C{filename}, with the key length of C{keySize}.\n        \"\"\"\n        tempDir = FilePath(self.mktemp())\n        keyFile = tempDir.child(\"mykey.pem\")\n\n        key = keys._getPersistentRSAKey(keyFile, keySize=512)\n        self.assertEqual(key.size(), 512)\n        self.assertTrue(keyFile.exists())\n\n\n    def test_noRegeneration(self):\n        \"\"\"\n        L{keys._getPersistentRSAKey} will not regenerate the key if the key\n        already exists.\n        \"\"\"\n        tempDir = FilePath(self.mktemp())\n        keyFile = tempDir.child(\"mykey.pem\")\n\n        key = keys._getPersistentRSAKey(keyFile, keySize=512)\n        self.assertEqual(key.size(), 512)\n        self.assertTrue(keyFile.exists())\n        keyContent = keyFile.getContent()\n\n        # Set the key size to 1024 bits. Since it exists already, it will find\n        # the 512 bit key, and not generate a 1024 bit key.\n        key = keys._getPersistentRSAKey(keyFile, keySize=1024)\n        self.assertEqual(key.size(), 512)\n        self.assertEqual(keyFile.getContent(), keyContent)\n\n\n    def test_keySizeZero(self):\n        \"\"\"\n        If the key generated by L{keys.getPersistentRSAKey} is set to None\n        the key size should then become 0.\n        \"\"\"\n        tempDir = FilePath(self.mktemp())\n        keyFile = tempDir.child(\"mykey.pem\")\n\n        key = keys._getPersistentRSAKey(keyFile, keySize=512)\n        key._keyObject = None\n        self.assertEqual( key.size(), 0)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_knownhosts.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.client.knownhosts}.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport os\nfrom binascii import Error as BinasciiError, b2a_base64, a2b_base64\n\nfrom zope.interface.verify import verifyObject\n\nfrom twisted.python.compat import networkString\nfrom twisted.python.reflect import requireModule\nfrom twisted.python.filepath import FilePath\nfrom twisted.trial.unittest import TestCase\nfrom twisted.internet.defer import Deferred\nfrom twisted.conch.interfaces import IKnownHostEntry\nfrom twisted.conch.error import HostKeyChanged, UserRejectedKey, InvalidEntry\nfrom twisted.test.testutils import ComparisonTestsMixin\n\nif requireModule('cryptography') and requireModule('pyasn1'):\n    from twisted.conch.ssh.keys import Key, BadKeyError\n    from twisted.conch.client.knownhosts import \\\n        PlainEntry, HashedEntry, KnownHostsFile, UnparsedEntry, ConsoleUI\n    from twisted.conch.client import default\n    from twisted.conch.test import keydata\nelse:\n    skip = \"cryptography and PyASN1 required for twisted.conch.knownhosts.\"\n\n\n\n\nsampleEncodedKey = (\n   b'AAAAB3NzaC1yc2EAAAABIwAAAQEAsV0VMRbGmzhqxxayLRHmvnFvtyNqgbNKV46dU1bVFB+3y'\n   b'tNvue4Riqv/SVkPRNwMb7eWH29SviXaBxUhYyzKkDoNUq3rTNnH1Vnif6d6X4JCrUb5d3W+Dm'\n   b'YClyJrZ5HgD/hUpdSkTRqdbQ2TrvSAxRacj+vHHT4F4dm1bJSewm3B2D8HVOoi/CbVh3dsIiC'\n   b'dp8VltdZx4qYVfYe2LwVINCbAa3d3tj9ma7RVfw3OH2Mfb+toLd1N5tBQFb7oqTt2nC6I/6Bd'\n   b'4JwPUld+IEitw/suElq/AIJVQXXujeyiZlea90HE65U2mF1ytr17HTAIT2ySokJWyuBANGACk'\n   b'6iIaw==')\n\notherSampleEncodedKey = (\n   b'AAAAB3NzaC1yc2EAAAABIwAAAIEAwaeCZd3UCuPXhX39+/p9qO028jTF76DMVd9mPvYVDVXuf'\n   b'WckKZauF7+0b7qm+ChT7kan6BzRVo4++gCVNfAlMzLysSt3ylmOR48tFpAfygg9UCX3DjHz0E'\n   b'lOOUKh3iifc9aUShD0OPaK3pR5JJ8jfiBfzSYWt/hDi/iZ4igsSs8=')\n\nthirdSampleEncodedKey = (\n  b'AAAAB3NzaC1yc2EAAAABIwAAAQEAl/TQakPkePlnwCBRPitIVUTg6Z8VzN1en+DGkyo/evkmLw'\n  b'7o4NWR5qbysk9A9jXW332nxnEuAnbcCam9SHe1su1liVfyIK0+3bdn0YRB0sXIbNEtMs2LtCho'\n  b'/aV3cXPS+Cf1yut3wvIpaRnAzXxuKPCTXQ7/y0IXa8TwkRBH58OJa3RqfQ/NsSp5SAfdsrHyH2'\n  b'aitiVKm2jfbTKzSEqOQG/zq4J9GXTkq61gZugory/Tvl5/yPgSnOR6C9jVOMHf27ZPoRtyj9SY'\n  b'343Hd2QHiIE0KPZJEgCynKeWoKz8v6eTSK8n4rBnaqWdp8MnGZK1WGy05MguXbyCDuTC8AmJXQ'\n  b'==')\n\necdsaSampleEncodedKey = (\n   b'AAAAE2VjZHNhLXNoYTItbmlzdHAyNTYAAAAIbmlzdHAyNTYAAABBBIFwh3/zBANyPPIE60'\n   b'SMMfdKMYo3OvfvzGLZphzuKrzSt0q4uF+/iYqtYiHhryAwU/fDWlUQ9kck9f+IlpsNtY4=')\n\nsampleKey = a2b_base64(sampleEncodedKey)\notherSampleKey = a2b_base64(otherSampleEncodedKey)\nthirdSampleKey = a2b_base64(thirdSampleEncodedKey)\necdsaSampleKey =  a2b_base64(ecdsaSampleEncodedKey)\n\nsamplePlaintextLine = (\n    b\"www.twistedmatrix.com ssh-rsa \" + sampleEncodedKey + b\"\\n\")\n\notherSamplePlaintextLine = (\n    b\"divmod.com ssh-rsa \" + otherSampleEncodedKey + b\"\\n\")\n\nsampleHostIPLine = (\n    b\"www.twistedmatrix.com,198.49.126.131 ssh-rsa \" + sampleEncodedKey + b\"\\n\")\n\nsampleHashedLine = (\n    b\"|1|gJbSEPBG9ZSBoZpHNtZBD1bHKBA=|bQv+0Xa0dByrwkA1EB0E7Xop/Fo= ssh-rsa \" +\n    sampleEncodedKey + b\"\\n\")\n\n\nclass EntryTestsMixin:\n    \"\"\"\n    Tests for implementations of L{IKnownHostEntry}.  Subclasses must set the\n    'entry' attribute to a provider of that interface, the implementation of\n    that interface under test.\n\n    @ivar entry: a provider of L{IKnownHostEntry} with a hostname of\n    www.twistedmatrix.com and an RSA key of sampleKey.\n    \"\"\"\n\n    def test_providesInterface(self):\n        \"\"\"\n        The given entry should provide IKnownHostEntry.\n        \"\"\"\n        verifyObject(IKnownHostEntry, self.entry)\n\n\n    def test_fromString(self):\n        \"\"\"\n        Constructing a plain text entry from an unhashed known_hosts entry will\n        result in an L{IKnownHostEntry} provider with 'keyString', 'hostname',\n        and 'keyType' attributes.  While outside the interface in question,\n        these attributes are held in common by L{PlainEntry} and L{HashedEntry}\n        implementations; other implementations should override this method in\n        subclasses.\n        \"\"\"\n        entry = self.entry\n        self.assertEqual(entry.publicKey, Key.fromString(sampleKey))\n        self.assertEqual(entry.keyType, b\"ssh-rsa\")\n\n\n    def test_matchesKey(self):\n        \"\"\"\n        L{IKnownHostEntry.matchesKey} checks to see if an entry matches a given\n        SSH key.\n        \"\"\"\n        twistedmatrixDotCom = Key.fromString(sampleKey)\n        divmodDotCom = Key.fromString(otherSampleKey)\n        self.assertEqual(\n            True,\n            self.entry.matchesKey(twistedmatrixDotCom))\n        self.assertEqual(\n            False,\n            self.entry.matchesKey(divmodDotCom))\n\n\n    def test_matchesHost(self):\n        \"\"\"\n        L{IKnownHostEntry.matchesHost} checks to see if an entry matches a\n        given hostname.\n        \"\"\"\n        self.assertTrue(self.entry.matchesHost(b\"www.twistedmatrix.com\"))\n        self.assertFalse(self.entry.matchesHost(b\"www.divmod.com\"))\n\n\n\nclass PlainEntryTests(EntryTestsMixin, TestCase):\n    \"\"\"\n    Test cases for L{PlainEntry}.\n    \"\"\"\n    plaintextLine = samplePlaintextLine\n    hostIPLine = sampleHostIPLine\n\n    def setUp(self):\n        \"\"\"\n        Set 'entry' to a sample plain-text entry with sampleKey as its key.\n        \"\"\"\n        self.entry = PlainEntry.fromString(self.plaintextLine)\n\n\n    def test_matchesHostIP(self):\n        \"\"\"\n        A \"hostname,ip\" formatted line will match both the host and the IP.\n        \"\"\"\n        self.entry = PlainEntry.fromString(self.hostIPLine)\n        self.assertTrue(self.entry.matchesHost(b\"198.49.126.131\"))\n        self.test_matchesHost()\n\n\n    def test_toString(self):\n        \"\"\"\n        L{PlainEntry.toString} generates the serialized OpenSSL format string\n        for the entry, sans newline.\n        \"\"\"\n        self.assertEqual(self.entry.toString(), self.plaintextLine.rstrip(b\"\\n\"))\n        multiHostEntry = PlainEntry.fromString(self.hostIPLine)\n        self.assertEqual(multiHostEntry.toString(),\n                         self.hostIPLine.rstrip(b\"\\n\"))\n\n\n\nclass PlainTextWithCommentTests(PlainEntryTests):\n    \"\"\"\n    Test cases for L{PlainEntry} when parsed from a line with a comment.\n    \"\"\"\n\n    plaintextLine = samplePlaintextLine[:-1] + b\" plain text comment.\\n\"\n    hostIPLine = sampleHostIPLine[:-1] + b\" text following host/IP line\\n\"\n\n\n\nclass HashedEntryTests(EntryTestsMixin, ComparisonTestsMixin, TestCase):\n    \"\"\"\n    Tests for L{HashedEntry}.\n\n    This suite doesn't include any tests for host/IP pairs because hashed\n    entries store IP addresses the same way as hostnames and does not support\n    comma-separated lists.  (If you hash the IP and host together you can't\n    tell if you've got the key already for one or the other.)\n    \"\"\"\n    hashedLine = sampleHashedLine\n\n    def setUp(self):\n        \"\"\"\n        Set 'entry' to a sample hashed entry for twistedmatrix.com with\n        sampleKey as its key.\n        \"\"\"\n        self.entry = HashedEntry.fromString(self.hashedLine)\n\n\n    def test_toString(self):\n        \"\"\"\n        L{HashedEntry.toString} generates the serialized OpenSSL format string\n        for the entry, sans the newline.\n        \"\"\"\n        self.assertEqual(self.entry.toString(), self.hashedLine.rstrip(b\"\\n\"))\n\n\n    def test_equality(self):\n        \"\"\"\n        Two L{HashedEntry} instances compare equal if and only if they represent\n        the same host and key in exactly the same way: the host salt, host hash,\n        public key type, public key, and comment fields must all be equal.\n        \"\"\"\n        hostSalt = b\"gJbSEPBG9ZSBoZpHNtZBD1bHKBA\"\n        hostHash = b\"bQv+0Xa0dByrwkA1EB0E7Xop/Fo\"\n        publicKey = Key.fromString(sampleKey)\n        keyType = networkString(publicKey.type())\n        comment = b\"hello, world\"\n\n        entry = HashedEntry(\n            hostSalt, hostHash, keyType, publicKey, comment)\n        duplicate = HashedEntry(\n            hostSalt, hostHash, keyType, publicKey, comment)\n\n        # Vary the host salt\n        self.assertNormalEqualityImplementation(\n            entry, duplicate,\n            HashedEntry(\n                hostSalt[::-1], hostHash, keyType, publicKey,\n                comment))\n\n        # Vary the host hash\n        self.assertNormalEqualityImplementation(\n            entry, duplicate,\n            HashedEntry(\n                hostSalt, hostHash[::-1], keyType, publicKey,\n                comment))\n\n        # Vary the key type\n        self.assertNormalEqualityImplementation(\n            entry, duplicate,\n            HashedEntry(\n                hostSalt, hostHash, keyType[::-1], publicKey,\n                comment))\n\n        # Vary the key\n        self.assertNormalEqualityImplementation(\n            entry, duplicate,\n            HashedEntry(\n                hostSalt, hostHash, keyType,\n                Key.fromString(otherSampleKey), comment))\n\n        # Vary the comment\n        self.assertNormalEqualityImplementation(\n            entry, duplicate,\n            HashedEntry(\n                hostSalt, hostHash, keyType, publicKey,\n                comment[::-1]))\n\n\n\nclass HashedEntryWithCommentTests(HashedEntryTests):\n    \"\"\"\n    Test cases for L{PlainEntry} when parsed from a line with a comment.\n    \"\"\"\n\n    hashedLine = sampleHashedLine[:-1] + b\" plain text comment.\\n\"\n\n\n\nclass UnparsedEntryTests(TestCase, EntryTestsMixin):\n    \"\"\"\n    Tests for L{UnparsedEntry}\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Set up the 'entry' to be an unparsed entry for some random text.\n        \"\"\"\n        self.entry = UnparsedEntry(b\"    This is a bogus entry.  \\n\")\n\n\n    def test_fromString(self):\n        \"\"\"\n        Creating an L{UnparsedEntry} should simply record the string it was\n        passed.\n        \"\"\"\n        self.assertEqual(b\"    This is a bogus entry.  \\n\",\n                         self.entry._string)\n\n\n    def test_matchesHost(self):\n        \"\"\"\n        An unparsed entry can't match any hosts.\n        \"\"\"\n        self.assertFalse(self.entry.matchesHost(b\"www.twistedmatrix.com\"))\n\n\n    def test_matchesKey(self):\n        \"\"\"\n        An unparsed entry can't match any keys.\n        \"\"\"\n        self.assertFalse(self.entry.matchesKey(Key.fromString(sampleKey)))\n\n\n    def test_toString(self):\n        \"\"\"\n        L{UnparsedEntry.toString} returns its input string, sans trailing\n        newline.\n        \"\"\"\n        self.assertEqual(b\"    This is a bogus entry.  \", self.entry.toString())\n\n\n\nclass ParseErrorTests(TestCase):\n    \"\"\"\n    L{HashedEntry.fromString} and L{PlainEntry.fromString} can raise a variety\n    of errors depending on misformattings of certain strings.  These tests make\n    sure those errors are caught.  Since many of the ways that this can go\n    wrong are in the lower-level APIs being invoked by the parsing logic,\n    several of these are integration tests with the C{base64} and\n    L{twisted.conch.ssh.keys} modules.\n    \"\"\"\n\n    def invalidEntryTest(self, cls):\n        \"\"\"\n        If there are fewer than three elements, C{fromString} should raise\n        L{InvalidEntry}.\n        \"\"\"\n        self.assertRaises(InvalidEntry, cls.fromString, b\"invalid\")\n\n\n    def notBase64Test(self, cls):\n        \"\"\"\n        If the key is not base64, C{fromString} should raise L{BinasciiError}.\n        \"\"\"\n        self.assertRaises(BinasciiError, cls.fromString, b\"x x x\")\n\n\n    def badKeyTest(self, cls, prefix):\n        \"\"\"\n        If the key portion of the entry is valid base64, but is not actually an\n        SSH key, C{fromString} should raise L{BadKeyError}.\n        \"\"\"\n        self.assertRaises(BadKeyError, cls.fromString, b' '.join(\n                [prefix, b\"ssh-rsa\", b2a_base64(\n                    b\"Hey, this isn't an SSH key!\").strip()]))\n\n\n    def test_invalidPlainEntry(self):\n        \"\"\"\n        If there are fewer than three whitespace-separated elements in an\n        entry, L{PlainEntry.fromString} should raise L{InvalidEntry}.\n        \"\"\"\n        self.invalidEntryTest(PlainEntry)\n\n\n    def test_invalidHashedEntry(self):\n        \"\"\"\n        If there are fewer than three whitespace-separated elements in an\n        entry, or the hostname salt/hash portion has more than two elements,\n        L{HashedEntry.fromString} should raise L{InvalidEntry}.\n        \"\"\"\n        self.invalidEntryTest(HashedEntry)\n        a, b, c = sampleHashedLine.split()\n        self.assertRaises(InvalidEntry, HashedEntry.fromString, b' '.join(\n                [a + b\"||\", b, c]))\n\n\n    def test_plainNotBase64(self):\n        \"\"\"\n        If the key portion of a plain entry is not decodable as base64,\n        C{fromString} should raise L{BinasciiError}.\n        \"\"\"\n        self.notBase64Test(PlainEntry)\n\n\n    def test_hashedNotBase64(self):\n        \"\"\"\n        If the key, host salt, or host hash portion of a hashed entry is not\n        encoded, it will raise L{BinasciiError}.\n        \"\"\"\n        self.notBase64Test(HashedEntry)\n        a, b, c = sampleHashedLine.split()\n        # Salt not valid base64.\n        self.assertRaises(\n            BinasciiError, HashedEntry.fromString,\n            b' '.join([b\"|1|x|\" + b2a_base64(b\"stuff\").strip(), b, c]))\n        # Host hash not valid base64.\n        self.assertRaises(\n            BinasciiError, HashedEntry.fromString,\n            b' '.join(\n                [HashedEntry.MAGIC + b2a_base64(b\"stuff\").strip() + b\"|x\",\n            b, c]))\n        # Neither salt nor hash valid base64.\n        self.assertRaises(\n            BinasciiError, HashedEntry.fromString,\n            b' '.join([b\"|1|x|x\", b, c]))\n\n\n    def test_hashedBadKey(self):\n        \"\"\"\n        If the key portion of the entry is valid base64, but is not actually an\n        SSH key, C{HashedEntry.fromString} should raise L{BadKeyError}.\n        \"\"\"\n        a, b, c = sampleHashedLine.split()\n        self.badKeyTest(HashedEntry, a)\n\n\n    def test_plainBadKey(self):\n        \"\"\"\n        If the key portion of the entry is valid base64, but is not actually an\n        SSH key, C{PlainEntry.fromString} should raise L{BadKeyError}.\n        \"\"\"\n        self.badKeyTest(PlainEntry, b\"hostname\")\n\n\n\nclass KnownHostsDatabaseTests(TestCase):\n    \"\"\"\n    Tests for L{KnownHostsFile}.\n    \"\"\"\n\n    def pathWithContent(self, content):\n        \"\"\"\n        Return a FilePath with the given initial content.\n        \"\"\"\n        fp = FilePath(self.mktemp())\n        fp.setContent(content)\n        return fp\n\n\n    def loadSampleHostsFile(self, content=(\n            sampleHashedLine + otherSamplePlaintextLine +\n            b\"\\n# That was a blank line.\\n\"\n            b\"This is just unparseable.\\n\"\n            b\"|1|This also unparseable.\\n\")):\n        \"\"\"\n        Return a sample hosts file, with keys for www.twistedmatrix.com and\n        divmod.com present.\n        \"\"\"\n        return KnownHostsFile.fromPath(self.pathWithContent(content))\n\n\n    def test_readOnlySavePath(self):\n        \"\"\"\n        L{KnownHostsFile.savePath} is read-only; if an assignment is made to\n        it, L{AttributeError} is raised and the value is unchanged.\n        \"\"\"\n        path = FilePath(self.mktemp())\n        new = FilePath(self.mktemp())\n        hostsFile = KnownHostsFile(path)\n        self.assertRaises(AttributeError, setattr, hostsFile, \"savePath\", new)\n        self.assertEqual(path, hostsFile.savePath)\n\n\n    def test_defaultInitializerIgnoresExisting(self):\n        \"\"\"\n        The default initializer for L{KnownHostsFile} disregards any existing\n        contents in the save path.\n        \"\"\"\n        hostsFile = KnownHostsFile(self.pathWithContent(sampleHashedLine))\n        self.assertEqual([], list(hostsFile.iterentries()))\n\n\n    def test_defaultInitializerClobbersExisting(self):\n        \"\"\"\n        After using the default initializer for L{KnownHostsFile}, the first use\n        of L{KnownHostsFile.save} overwrites any existing contents in the save\n        path.\n        \"\"\"\n        path = self.pathWithContent(sampleHashedLine)\n        hostsFile = KnownHostsFile(path)\n        entry = hostsFile.addHostKey(\n            b\"www.example.com\", Key.fromString(otherSampleKey))\n        hostsFile.save()\n        # Check KnownHostsFile to see what it thinks the state is\n        self.assertEqual([entry], list(hostsFile.iterentries()))\n        # And also directly check the underlying file itself\n        self.assertEqual(entry.toString() + b\"\\n\", path.getContent())\n\n\n    def test_saveResetsClobberState(self):\n        \"\"\"\n        After L{KnownHostsFile.save} is used once with an instance initialized\n        by the default initializer, contents of the save path are respected and\n        preserved.\n        \"\"\"\n        hostsFile = KnownHostsFile(self.pathWithContent(sampleHashedLine))\n        preSave = hostsFile.addHostKey(\n            b\"www.example.com\", Key.fromString(otherSampleKey))\n        hostsFile.save()\n        postSave = hostsFile.addHostKey(\n            b\"another.example.com\", Key.fromString(thirdSampleKey))\n        hostsFile.save()\n\n        self.assertEqual([preSave, postSave], list(hostsFile.iterentries()))\n\n\n    def test_loadFromPath(self):\n        \"\"\"\n        Loading a L{KnownHostsFile} from a path with six entries in it will\n        result in a L{KnownHostsFile} object with six L{IKnownHostEntry}\n        providers in it.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile()\n        self.assertEqual(6, len(list(hostsFile.iterentries())))\n\n\n    def test_iterentriesUnsaved(self):\n        \"\"\"\n        If the save path for a L{KnownHostsFile} does not exist,\n        L{KnownHostsFile.iterentries} still returns added but unsaved entries.\n        \"\"\"\n        hostsFile = KnownHostsFile(FilePath(self.mktemp()))\n        hostsFile.addHostKey(b\"www.example.com\", Key.fromString(sampleKey))\n        self.assertEqual(1, len(list(hostsFile.iterentries())))\n\n\n    def test_verifyHashedEntry(self):\n        \"\"\"\n        Loading a L{KnownHostsFile} from a path containing a single valid\n        L{HashedEntry} entry will result in a L{KnownHostsFile} object\n        with one L{IKnownHostEntry} provider.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile((sampleHashedLine))\n        entries = list(hostsFile.iterentries())\n        self.assertIsInstance(entries[0], HashedEntry)\n        self.assertTrue(entries[0].matchesHost(b\"www.twistedmatrix.com\"))\n        self.assertEqual(1, len(entries))\n\n\n    def test_verifyPlainEntry(self):\n        \"\"\"\n        Loading a L{KnownHostsFile} from a path containing a single valid\n        L{PlainEntry} entry will result in a L{KnownHostsFile} object\n        with one L{IKnownHostEntry} provider.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile((otherSamplePlaintextLine))\n        entries = list(hostsFile.iterentries())\n        self.assertIsInstance(entries[0], PlainEntry)\n        self.assertTrue(entries[0].matchesHost(b\"divmod.com\"))\n        self.assertEqual(1, len(entries))\n\n\n    def test_verifyUnparsedEntry(self):\n        \"\"\"\n        Loading a L{KnownHostsFile} from a path that only contains '\\n' will\n        result in a L{KnownHostsFile} object containing a L{UnparsedEntry}\n        object.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile((b\"\\n\"))\n        entries = list(hostsFile.iterentries())\n        self.assertIsInstance(entries[0], UnparsedEntry)\n        self.assertEqual(entries[0].toString(), b\"\")\n        self.assertEqual(1, len(entries))\n\n\n    def test_verifyUnparsedComment(self):\n        \"\"\"\n        Loading a L{KnownHostsFile} from a path that contains a comment will\n        result in a L{KnownHostsFile} object containing a L{UnparsedEntry}\n        object.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile((b\"# That was a blank line.\\n\"))\n        entries = list(hostsFile.iterentries())\n        self.assertIsInstance(entries[0], UnparsedEntry)\n        self.assertEqual(entries[0].toString(), b\"# That was a blank line.\")\n\n\n    def test_verifyUnparsableLine(self):\n        \"\"\"\n        Loading a L{KnownHostsFile} from a path that contains an unparseable\n        line will be represented as an L{UnparsedEntry} instance.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile((b\"This is just unparseable.\\n\"))\n        entries = list(hostsFile.iterentries())\n        self.assertIsInstance(entries[0], UnparsedEntry)\n        self.assertEqual(entries[0].toString(), b\"This is just unparseable.\")\n        self.assertEqual(1, len(entries))\n\n\n    def test_verifyUnparsableEncryptionMarker(self):\n        \"\"\"\n        Loading a L{KnownHostsFile} from a path containing an unparseable line\n        that starts with an encryption marker will be represented as an\n        L{UnparsedEntry} instance.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile((b\"|1|This is unparseable.\\n\"))\n        entries = list(hostsFile.iterentries())\n        self.assertIsInstance(entries[0], UnparsedEntry)\n        self.assertEqual(entries[0].toString(), b\"|1|This is unparseable.\")\n        self.assertEqual(1, len(entries))\n\n\n    def test_loadNonExistent(self):\n        \"\"\"\n        Loading a L{KnownHostsFile} from a path that does not exist should\n        result in an empty L{KnownHostsFile} that will save back to that path.\n        \"\"\"\n        pn = self.mktemp()\n        knownHostsFile = KnownHostsFile.fromPath(FilePath(pn))\n        entries = list(knownHostsFile.iterentries())\n        self.assertEqual([], entries)\n        self.assertFalse(FilePath(pn).exists())\n        knownHostsFile.save()\n        self.assertTrue(FilePath(pn).exists())\n\n\n    def test_loadNonExistentParent(self):\n        \"\"\"\n        Loading a L{KnownHostsFile} from a path whose parent directory does not\n        exist should result in an empty L{KnownHostsFile} that will save back\n        to that path, creating its parent directory(ies) in the process.\n        \"\"\"\n        thePath = FilePath(self.mktemp())\n        knownHostsPath = thePath.child(\"foo\").child(b\"known_hosts\")\n        knownHostsFile = KnownHostsFile.fromPath(knownHostsPath)\n        knownHostsFile.save()\n        knownHostsPath.restat(False)\n        self.assertTrue(knownHostsPath.exists())\n\n\n    def test_savingAddsEntry(self):\n        \"\"\"\n        L{KnownHostsFile.save} will write out a new file with any entries\n        that have been added.\n        \"\"\"\n        path = self.pathWithContent(sampleHashedLine +\n                                    otherSamplePlaintextLine)\n        knownHostsFile = KnownHostsFile.fromPath(path)\n        newEntry = knownHostsFile.addHostKey(b\"some.example.com\",\n            Key.fromString(thirdSampleKey))\n        expectedContent = (\n            sampleHashedLine +\n            otherSamplePlaintextLine + HashedEntry.MAGIC +\n            b2a_base64(newEntry._hostSalt).strip() + b\"|\" +\n            b2a_base64(newEntry._hostHash).strip() + b\" ssh-rsa \" +\n            thirdSampleEncodedKey + b\"\\n\")\n\n        # Sanity check, let's make sure the base64 API being used for the test\n        # isn't inserting spurious newlines.\n        self.assertEqual(3, expectedContent.count(b\"\\n\"))\n        knownHostsFile.save()\n        self.assertEqual(expectedContent, path.getContent())\n\n\n    def test_savingAvoidsDuplication(self):\n        \"\"\"\n        L{KnownHostsFile.save} only writes new entries to the save path, not\n        entries which were added and already written by a previous call to\n        C{save}.\n        \"\"\"\n        path = FilePath(self.mktemp())\n        knownHosts = KnownHostsFile(path)\n        entry = knownHosts.addHostKey(\n            b\"some.example.com\", Key.fromString(sampleKey))\n        knownHosts.save()\n        knownHosts.save()\n\n        knownHosts = KnownHostsFile.fromPath(path)\n        self.assertEqual([entry], list(knownHosts.iterentries()))\n\n\n    def test_savingsPreservesExisting(self):\n        \"\"\"\n        L{KnownHostsFile.save} will not overwrite existing entries in its save\n        path, even if they were only added after the L{KnownHostsFile} instance\n        was initialized.\n        \"\"\"\n        # Start off with one host/key pair in the file\n        path = self.pathWithContent(sampleHashedLine)\n        knownHosts = KnownHostsFile.fromPath(path)\n\n        # After initializing the KnownHostsFile instance, add a second host/key\n        # pair to the file directly - without the instance's help or knowledge.\n        with path.open(\"a\") as hostsFileObj:\n            hostsFileObj.write(otherSamplePlaintextLine)\n\n        # Add a third host/key pair using the KnownHostsFile instance\n        key = Key.fromString(thirdSampleKey)\n        knownHosts.addHostKey(b\"brandnew.example.com\", key)\n        knownHosts.save()\n\n        # Check that all three host/key pairs are present.\n        knownHosts = KnownHostsFile.fromPath(path)\n        self.assertEqual([True, True, True], [\n                knownHosts.hasHostKey(\n                    b\"www.twistedmatrix.com\", Key.fromString(sampleKey)),\n                knownHosts.hasHostKey(\n                    b\"divmod.com\", Key.fromString(otherSampleKey)),\n                knownHosts.hasHostKey(b\"brandnew.example.com\", key)])\n\n\n    def test_hasPresentKey(self):\n        \"\"\"\n        L{KnownHostsFile.hasHostKey} returns C{True} when a key for the given\n        hostname is present and matches the expected key.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile()\n        self.assertTrue(hostsFile.hasHostKey(\n                b\"www.twistedmatrix.com\", Key.fromString(sampleKey)))\n\n\n    def test_notPresentKey(self):\n        \"\"\"\n        L{KnownHostsFile.hasHostKey} returns C{False} when a key for the given\n        hostname is not present.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile()\n        self.assertFalse(hostsFile.hasHostKey(\n                b\"non-existent.example.com\", Key.fromString(sampleKey)))\n        self.assertTrue(hostsFile.hasHostKey(\n                b\"www.twistedmatrix.com\", Key.fromString(sampleKey)))\n        self.assertFalse(hostsFile.hasHostKey(\n                b\"www.twistedmatrix.com\", Key.fromString(ecdsaSampleKey)))\n\n\n    def test_hasLaterAddedKey(self):\n        \"\"\"\n        L{KnownHostsFile.hasHostKey} returns C{True} when a key for the given\n        hostname is present in the file, even if it is only added to the file\n        after the L{KnownHostsFile} instance is initialized.\n        \"\"\"\n        key = Key.fromString(sampleKey)\n        entry = PlainEntry([b\"brandnew.example.com\"], key.sshType(), key, b\"\")\n        hostsFile = self.loadSampleHostsFile()\n        with hostsFile.savePath.open(\"a\") as hostsFileObj:\n            hostsFileObj.write(entry.toString() + b\"\\n\")\n        self.assertEqual(\n            True, hostsFile.hasHostKey(b\"brandnew.example.com\", key))\n\n\n    def test_savedEntryHasKeyMismatch(self):\n        \"\"\"\n        L{KnownHostsFile.hasHostKey} raises L{HostKeyChanged} if the host key is\n        present in the underlying file, but different from the expected one.\n        The resulting exception should have an C{offendingEntry} indicating the\n        given entry.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile()\n        entries = list(hostsFile.iterentries())\n        exception = self.assertRaises(\n            HostKeyChanged, hostsFile.hasHostKey,\n            b\"www.twistedmatrix.com\", Key.fromString(otherSampleKey))\n        self.assertEqual(exception.offendingEntry, entries[0])\n        self.assertEqual(exception.lineno, 1)\n        self.assertEqual(exception.path, hostsFile.savePath)\n\n\n    def test_savedEntryAfterAddHasKeyMismatch(self):\n        \"\"\"\n        Even after a new entry has been added in memory but not yet saved, the\n        L{HostKeyChanged} exception raised by L{KnownHostsFile.hasHostKey} has a\n        C{lineno} attribute which indicates the 1-based line number of the\n        offending entry in the underlying file when the given host key does not\n        match the expected host key.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile()\n        hostsFile.addHostKey(\n            b\"www.example.com\", Key.fromString(otherSampleKey))\n        exception = self.assertRaises(\n            HostKeyChanged, hostsFile.hasHostKey,\n            b\"www.twistedmatrix.com\", Key.fromString(otherSampleKey))\n        self.assertEqual(exception.lineno, 1)\n        self.assertEqual(exception.path, hostsFile.savePath)\n\n\n    def test_unsavedEntryHasKeyMismatch(self):\n        \"\"\"\n        L{KnownHostsFile.hasHostKey} raises L{HostKeyChanged} if the host key is\n        present in memory (but not yet saved), but different from the expected\n        one.  The resulting exception has a C{offendingEntry} indicating the\n        given entry, but no filename or line number information (reflecting the\n        fact that the entry exists only in memory).\n        \"\"\"\n        hostsFile = KnownHostsFile(FilePath(self.mktemp()))\n        entry = hostsFile.addHostKey(\n            b\"www.example.com\", Key.fromString(otherSampleKey))\n        exception = self.assertRaises(\n            HostKeyChanged, hostsFile.hasHostKey,\n            b\"www.example.com\", Key.fromString(thirdSampleKey))\n        self.assertEqual(exception.offendingEntry, entry)\n        self.assertIsNone(exception.lineno)\n        self.assertIsNone(exception.path)\n\n\n    def test_addHostKey(self):\n        \"\"\"\n        L{KnownHostsFile.addHostKey} adds a new L{HashedEntry} to the host\n        file, and returns it.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile()\n        aKey = Key.fromString(thirdSampleKey)\n        self.assertEqual(False,\n                         hostsFile.hasHostKey(b\"somewhere.example.com\", aKey))\n        newEntry = hostsFile.addHostKey(b\"somewhere.example.com\", aKey)\n\n        # The code in OpenSSH requires host salts to be 20 characters long.\n        # This is the required length of a SHA-1 HMAC hash, so it's just a\n        # sanity check.\n        self.assertEqual(20, len(newEntry._hostSalt))\n        self.assertEqual(True,\n                         newEntry.matchesHost(b\"somewhere.example.com\"))\n        self.assertEqual(newEntry.keyType, b\"ssh-rsa\")\n        self.assertEqual(aKey, newEntry.publicKey)\n        self.assertEqual(True,\n                         hostsFile.hasHostKey(b\"somewhere.example.com\", aKey))\n\n\n    def test_randomSalts(self):\n        \"\"\"\n        L{KnownHostsFile.addHostKey} generates a random salt for each new key,\n        so subsequent salts will be different.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile()\n        aKey = Key.fromString(thirdSampleKey)\n        self.assertNotEqual(\n            hostsFile.addHostKey(b\"somewhere.example.com\", aKey)._hostSalt,\n            hostsFile.addHostKey(b\"somewhere-else.example.com\", aKey)._hostSalt)\n\n\n    def test_verifyValidKey(self):\n        \"\"\"\n        Verifying a valid key should return a L{Deferred} which fires with\n        True.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile()\n        hostsFile.addHostKey(b\"1.2.3.4\", Key.fromString(sampleKey))\n        ui = FakeUI()\n        d = hostsFile.verifyHostKey(ui, b\"www.twistedmatrix.com\", b\"1.2.3.4\",\n                                    Key.fromString(sampleKey))\n        l = []\n        d.addCallback(l.append)\n        self.assertEqual(l, [True])\n\n\n    def test_verifyInvalidKey(self):\n        \"\"\"\n        Verifying an invalid key should return a L{Deferred} which fires with a\n        L{HostKeyChanged} failure.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile()\n        wrongKey = Key.fromString(thirdSampleKey)\n        ui = FakeUI()\n        hostsFile.addHostKey(b\"1.2.3.4\", Key.fromString(sampleKey))\n        d = hostsFile.verifyHostKey(\n            ui, b\"www.twistedmatrix.com\", b\"1.2.3.4\", wrongKey)\n        return self.assertFailure(d, HostKeyChanged)\n\n\n    def verifyNonPresentKey(self):\n        \"\"\"\n        Set up a test to verify a key that isn't present.  Return a 3-tuple of\n        the UI, a list set up to collect the result of the verifyHostKey call,\n        and the sample L{KnownHostsFile} being used.\n\n        This utility method avoids returning a L{Deferred}, and records results\n        in the returned list instead, because the events which get generated\n        here are pre-recorded in the 'ui' object.  If the L{Deferred} in\n        question does not fire, the it will fail quickly with an empty list.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile()\n        absentKey = Key.fromString(thirdSampleKey)\n        ui = FakeUI()\n        l = []\n        d = hostsFile.verifyHostKey(\n            ui, b\"sample-host.example.com\", b\"4.3.2.1\", absentKey)\n        d.addBoth(l.append)\n        self.assertEqual([], l)\n        self.assertEqual(\n            ui.promptText,\n            b\"The authenticity of host 'sample-host.example.com (4.3.2.1)' \"\n            b\"can't be established.\\n\"\n            b\"RSA key fingerprint is \"\n            b\"SHA256:mS7mDBGhewdzJkaKRkx+wMjUdZb/GzvgcdoYjX5Js9I=.\\n\"\n            b\"Are you sure you want to continue connecting (yes/no)? \")\n        return ui, l, hostsFile\n\n\n    def test_verifyNonPresentKey_Yes(self):\n        \"\"\"\n        Verifying a key where neither the hostname nor the IP are present\n        should result in the UI being prompted with a message explaining as\n        much.  If the UI says yes, the Deferred should fire with True.\n        \"\"\"\n        ui, l, knownHostsFile = self.verifyNonPresentKey()\n        ui.promptDeferred.callback(True)\n        self.assertEqual([True], l)\n        reloaded = KnownHostsFile.fromPath(knownHostsFile.savePath)\n        self.assertEqual(\n            True,\n            reloaded.hasHostKey(b\"4.3.2.1\", Key.fromString(thirdSampleKey)))\n        self.assertEqual(\n            True,\n            reloaded.hasHostKey(b\"sample-host.example.com\",\n                                Key.fromString(thirdSampleKey)))\n\n\n    def test_verifyNonPresentKey_No(self):\n        \"\"\"\n        Verifying a key where neither the hostname nor the IP are present\n        should result in the UI being prompted with a message explaining as\n        much.  If the UI says no, the Deferred should fail with\n        UserRejectedKey.\n        \"\"\"\n        ui, l, knownHostsFile = self.verifyNonPresentKey()\n        ui.promptDeferred.callback(False)\n        l[0].trap(UserRejectedKey)\n\n\n    def test_verifyNonPresentECKey(self):\n        \"\"\"\n        Set up a test to verify an ECDSA key that isn't present.\n        Return a 3-tuple of the UI, a list set up to collect the result\n        of the verifyHostKey call, and the sample L{KnownHostsFile} being used.\n        \"\"\"\n        ecObj = Key._fromECComponents(\n            x=keydata.ECDatanistp256['x'],\n            y=keydata.ECDatanistp256['y'],\n            privateValue=keydata.ECDatanistp256['privateValue'],\n            curve=keydata.ECDatanistp256['curve']\n        )\n\n        hostsFile = self.loadSampleHostsFile()\n        ui = FakeUI()\n        l = []\n        d = hostsFile.verifyHostKey(\n            ui, b\"sample-host.example.com\", b\"4.3.2.1\", ecObj)\n        d.addBoth(l.append)\n        self.assertEqual([], l)\n        self.assertEqual(\n            ui.promptText,\n            b\"The authenticity of host 'sample-host.example.com (4.3.2.1)' \"\n            b\"can't be established.\\n\"\n            b\"ECDSA key fingerprint is \"\n            b\"SHA256:fJnSpgCcYoYYsaBbnWj1YBghGh/QTDgfe4w4U5M5tEo=.\\n\"\n            b\"Are you sure you want to continue connecting (yes/no)? \")\n\n\n    def test_verifyHostIPMismatch(self):\n        \"\"\"\n        Verifying a key where the host is present (and correct), but the IP is\n        present and different, should result the deferred firing in a\n        HostKeyChanged failure.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile()\n        wrongKey = Key.fromString(thirdSampleKey)\n        ui = FakeUI()\n        d = hostsFile.verifyHostKey(\n            ui, b\"www.twistedmatrix.com\", b\"4.3.2.1\", wrongKey)\n        return self.assertFailure(d, HostKeyChanged)\n\n\n    def test_verifyKeyForHostAndIP(self):\n        \"\"\"\n        Verifying a key where the hostname is present but the IP is not should\n        result in the key being added for the IP and the user being warned\n        about the change.\n        \"\"\"\n        ui = FakeUI()\n        hostsFile = self.loadSampleHostsFile()\n        expectedKey = Key.fromString(sampleKey)\n        hostsFile.verifyHostKey(\n            ui, b\"www.twistedmatrix.com\", b\"5.4.3.2\", expectedKey)\n        self.assertEqual(\n            True, KnownHostsFile.fromPath(hostsFile.savePath).hasHostKey(\n                b\"5.4.3.2\", expectedKey))\n        self.assertEqual(\n            [\"Warning: Permanently added the RSA host key for IP address \"\n             \"'5.4.3.2' to the list of known hosts.\"],\n            ui.userWarnings)\n\n\n    def test_getHostKeyAlgorithms(self):\n        \"\"\"\n        For a given host, get the host key algorithms for that\n        host in the known_hosts file.\n        \"\"\"\n        hostsFile = self.loadSampleHostsFile()\n        hostsFile.addHostKey(\n            b\"www.twistedmatrix.com\", Key.fromString(otherSampleKey))\n        hostsFile.addHostKey(\n            b\"www.twistedmatrix.com\", Key.fromString(ecdsaSampleKey))\n        hostsFile.save()\n        options = {}\n        options['known-hosts'] = hostsFile.savePath.path\n        algorithms = default.getHostKeyAlgorithms(\n                         b\"www.twistedmatrix.com\", options)\n        expectedAlgorithms = [b'ssh-rsa', b'ecdsa-sha2-nistp256']\n        self.assertEqual(algorithms, expectedAlgorithms)\n\n\n\nclass FakeFile(object):\n    \"\"\"\n    A fake file-like object that acts enough like a file for\n    L{ConsoleUI.prompt}.\n    \"\"\"\n\n    def __init__(self):\n        self.inlines = []\n        self.outchunks = []\n        self.closed = False\n\n\n    def readline(self):\n        \"\"\"\n        Return a line from the 'inlines' list.\n        \"\"\"\n        return self.inlines.pop(0)\n\n\n    def write(self, chunk):\n        \"\"\"\n        Append the given item to the 'outchunks' list.\n        \"\"\"\n        if self.closed:\n            raise IOError(\"the file was closed\")\n        self.outchunks.append(chunk)\n\n\n    def close(self):\n        \"\"\"\n        Set the 'closed' flag to True, explicitly marking that it has been\n        closed.\n        \"\"\"\n        self.closed = True\n\n\n\nclass ConsoleUITests(TestCase):\n    \"\"\"\n    Test cases for L{ConsoleUI}.\n    \"\"\"\n\n    def setUp(self):\n        \"\"\"\n        Create a L{ConsoleUI} pointed at a L{FakeFile}.\n        \"\"\"\n        self.fakeFile = FakeFile()\n        self.ui = ConsoleUI(self.openFile)\n\n\n    def openFile(self):\n        \"\"\"\n        Return the current fake file.\n        \"\"\"\n        return self.fakeFile\n\n\n    def newFile(self, lines):\n        \"\"\"\n        Create a new fake file (the next file that self.ui will open) with the\n        given list of lines to be returned from readline().\n        \"\"\"\n        self.fakeFile = FakeFile()\n        self.fakeFile.inlines = lines\n\n\n    def test_promptYes(self):\n        \"\"\"\n        L{ConsoleUI.prompt} writes a message to the console, then reads a line.\n        If that line is 'yes', then it returns a L{Deferred} that fires with\n        True.\n        \"\"\"\n        for okYes in [b'yes', b'Yes', b'yes\\n']:\n            self.newFile([okYes])\n            l = []\n            self.ui.prompt(\"Hello, world!\").addCallback(l.append)\n            self.assertEqual([\"Hello, world!\"], self.fakeFile.outchunks)\n            self.assertEqual([True], l)\n            self.assertTrue(self.fakeFile.closed)\n\n\n    def test_promptNo(self):\n        \"\"\"\n        L{ConsoleUI.prompt} writes a message to the console, then reads a line.\n        If that line is 'no', then it returns a L{Deferred} that fires with\n        False.\n        \"\"\"\n        for okNo in [b'no', b'No', b'no\\n']:\n            self.newFile([okNo])\n            l = []\n            self.ui.prompt(\"Goodbye, world!\").addCallback(l.append)\n            self.assertEqual([\"Goodbye, world!\"], self.fakeFile.outchunks)\n            self.assertEqual([False], l)\n            self.assertTrue(self.fakeFile.closed)\n\n\n    def test_promptRepeatedly(self):\n        \"\"\"\n        L{ConsoleUI.prompt} writes a message to the console, then reads a line.\n        If that line is neither 'yes' nor 'no', then it says \"Please enter\n        'yes' or 'no'\" until it gets a 'yes' or a 'no', at which point it\n        returns a Deferred that answers either True or False.\n        \"\"\"\n        self.newFile([b'what', b'uh', b'okay', b'yes'])\n        l = []\n        self.ui.prompt(b\"Please say something useful.\").addCallback(l.append)\n        self.assertEqual([True], l)\n        self.assertEqual(self.fakeFile.outchunks,\n                         [b\"Please say something useful.\"] +\n                         [b\"Please type 'yes' or 'no': \"] * 3)\n        self.assertTrue(self.fakeFile.closed)\n        self.newFile([b'blah', b'stuff', b'feh', b'no'])\n        l = []\n        self.ui.prompt(b\"Please say something negative.\").addCallback(l.append)\n        self.assertEqual([False], l)\n        self.assertEqual(self.fakeFile.outchunks,\n                         [b\"Please say something negative.\"] +\n                         [b\"Please type 'yes' or 'no': \"] * 3)\n        self.assertTrue(self.fakeFile.closed)\n\n\n    def test_promptOpenFailed(self):\n        \"\"\"\n        If the C{opener} passed to L{ConsoleUI} raises an exception, that\n        exception will fail the L{Deferred} returned from L{ConsoleUI.prompt}.\n        \"\"\"\n        def raiseIt():\n            raise IOError()\n        ui = ConsoleUI(raiseIt)\n        d = ui.prompt(\"This is a test.\")\n        return self.assertFailure(d, IOError)\n\n\n    def test_warn(self):\n        \"\"\"\n        L{ConsoleUI.warn} should output a message to the console object.\n        \"\"\"\n        self.ui.warn(\"Test message.\")\n        self.assertEqual([\"Test message.\"], self.fakeFile.outchunks)\n        self.assertTrue(self.fakeFile.closed)\n\n\n    def test_warnOpenFailed(self):\n        \"\"\"\n        L{ConsoleUI.warn} should log a traceback if the output can't be opened.\n        \"\"\"\n        def raiseIt():\n            1 / 0\n        ui = ConsoleUI(raiseIt)\n        ui.warn(\"This message never makes it.\")\n        self.assertEqual(len(self.flushLoggedErrors(ZeroDivisionError)), 1)\n\n\n\nclass FakeUI(object):\n    \"\"\"\n    A fake UI object, adhering to the interface expected by\n    L{KnownHostsFile.verifyHostKey}\n\n    @ivar userWarnings: inputs provided to 'warn'.\n\n    @ivar promptDeferred: last result returned from 'prompt'.\n\n    @ivar promptText: the last input provided to 'prompt'.\n    \"\"\"\n\n    def __init__(self):\n        self.userWarnings = []\n        self.promptDeferred = None\n        self.promptText = None\n\n\n    def prompt(self, text):\n        \"\"\"\n        Issue the user an interactive prompt, which they can accept or deny.\n        \"\"\"\n        self.promptText = text\n        self.promptDeferred = Deferred()\n        return self.promptDeferred\n\n\n    def warn(self, text):\n        \"\"\"\n        Issue a non-interactive warning to the user.\n        \"\"\"\n        self.userWarnings.append(text)\n\n\n\nclass FakeObject(object):\n    \"\"\"\n    A fake object that can have some attributes.  Used to fake\n    L{SSHClientTransport} and L{SSHClientFactory}.\n    \"\"\"\n\n\nclass DefaultAPITests(TestCase):\n    \"\"\"\n    The API in L{twisted.conch.client.default.verifyHostKey} is the integration\n    point between the code in the rest of conch and L{KnownHostsFile}.\n    \"\"\"\n\n    def patchedOpen(self, fname, mode, **kwargs):\n        \"\"\"\n        The patched version of 'open'; this returns a L{FakeFile} that the\n        instantiated L{ConsoleUI} can use.\n        \"\"\"\n        self.assertEqual(fname, \"/dev/tty\")\n        self.assertEqual(mode, \"r+b\")\n        self.assertEqual(kwargs['buffering'], 0)\n        return self.fakeFile\n\n\n    def setUp(self):\n        \"\"\"\n        Patch 'open' in verifyHostKey.\n        \"\"\"\n        self.fakeFile = FakeFile()\n        self.patch(default, \"_open\", self.patchedOpen)\n        self.hostsOption = self.mktemp()\n        self.hashedEntries = {}\n        knownHostsFile = KnownHostsFile(FilePath(self.hostsOption))\n        for host in (b\"exists.example.com\", b\"4.3.2.1\"):\n            entry = knownHostsFile.addHostKey(host, Key.fromString(sampleKey))\n            self.hashedEntries[host] = entry\n        knownHostsFile.save()\n        self.fakeTransport = FakeObject()\n        self.fakeTransport.factory = FakeObject()\n        self.options = self.fakeTransport.factory.options = {\n            'host': b\"exists.example.com\",\n            'known-hosts': self.hostsOption\n            }\n\n\n    def test_verifyOKKey(self):\n        \"\"\"\n        L{default.verifyHostKey} should return a L{Deferred} which fires with\n        C{1} when passed a host, IP, and key which already match the\n        known_hosts file it is supposed to check.\n        \"\"\"\n        l = []\n        default.verifyHostKey(self.fakeTransport, b\"4.3.2.1\", sampleKey,\n                              b\"I don't care.\").addCallback(l.append)\n        self.assertEqual([1], l)\n\n\n    def replaceHome(self, tempHome):\n        \"\"\"\n        Replace the HOME environment variable until the end of the current\n        test, with the given new home-directory, so that L{os.path.expanduser}\n        will yield controllable, predictable results.\n\n        @param tempHome: the pathname to replace the HOME variable with.\n\n        @type tempHome: L{str}\n        \"\"\"\n        oldHome = os.environ.get('HOME')\n        def cleanupHome():\n            if oldHome is None:\n                del os.environ['HOME']\n            else:\n                os.environ['HOME'] = oldHome\n        self.addCleanup(cleanupHome)\n        os.environ['HOME'] = tempHome\n\n\n    def test_noKnownHostsOption(self):\n        \"\"\"\n        L{default.verifyHostKey} should find your known_hosts file in\n        ~/.ssh/known_hosts if you don't specify one explicitly on the command\n        line.\n        \"\"\"\n        l = []\n        tmpdir = self.mktemp()\n        oldHostsOption = self.hostsOption\n        hostsNonOption = FilePath(tmpdir).child(\".ssh\").child(\"known_hosts\")\n        hostsNonOption.parent().makedirs()\n        FilePath(oldHostsOption).moveTo(hostsNonOption)\n        self.replaceHome(tmpdir)\n        self.options['known-hosts'] = None\n        default.verifyHostKey(self.fakeTransport, b\"4.3.2.1\", sampleKey,\n                              b\"I don't care.\").addCallback(l.append)\n        self.assertEqual([1], l)\n\n\n    def test_verifyHostButNotIP(self):\n        \"\"\"\n        L{default.verifyHostKey} should return a L{Deferred} which fires with\n        C{1} when passed a host which matches with an IP is not present in its\n        known_hosts file, and should also warn the user that it has added the\n        IP address.\n        \"\"\"\n        l = []\n        default.verifyHostKey(self.fakeTransport, b\"8.7.6.5\", sampleKey,\n                              b\"Fingerprint not required.\").addCallback(l.append)\n        self.assertEqual(\n            [\"Warning: Permanently added the RSA host key for IP address \"\n            \"'8.7.6.5' to the list of known hosts.\"],\n            self.fakeFile.outchunks)\n        self.assertEqual([1], l)\n        knownHostsFile = KnownHostsFile.fromPath(FilePath(self.hostsOption))\n        self.assertTrue(knownHostsFile.hasHostKey(b\"8.7.6.5\",\n                                             Key.fromString(sampleKey)))\n\n\n    def test_verifyQuestion(self):\n        \"\"\"\n        L{default.verifyHostKey} should return a L{Default} which fires with\n        C{0} when passed an unknown host that the user refuses to acknowledge.\n        \"\"\"\n        self.fakeTransport.factory.options['host'] = b'fake.example.com'\n        self.fakeFile.inlines.append(b\"no\")\n        d = default.verifyHostKey(\n            self.fakeTransport, b\"9.8.7.6\", otherSampleKey,\n            b\"No fingerprint!\")\n        self.assertEqual(\n            [b\"The authenticity of host 'fake.example.com (9.8.7.6)' \"\n             b\"can't be established.\\n\"\n             b\"RSA key fingerprint is \"\n             b\"SHA256:vD0YydsNIUYJa7yLZl3tIL8h0vZvQ8G+HPG7JLmQV0s=.\\n\"\n             b\"Are you sure you want to continue connecting (yes/no)? \"],\n             self.fakeFile.outchunks)\n        return self.assertFailure(d, UserRejectedKey)\n\n\n    def test_verifyBadKey(self):\n        \"\"\"\n        L{default.verifyHostKey} should return a L{Deferred} which fails with\n        L{HostKeyChanged} if the host key is incorrect.\n        \"\"\"\n        d = default.verifyHostKey(\n            self.fakeTransport, b\"4.3.2.1\", otherSampleKey,\n            \"Again, not required.\")\n        return self.assertFailure(d, HostKeyChanged)\n\n\n    def test_inKnownHosts(self):\n        \"\"\"\n        L{default.isInKnownHosts} should return C{1} when a host with a key\n        is in the known hosts file.\n        \"\"\"\n        host = self.hashedEntries[b\"4.3.2.1\"].toString().split()[0]\n        r = default.isInKnownHosts(\n            host, Key.fromString(sampleKey).blob(),\n            {\"known-hosts\": FilePath(self.hostsOption).path})\n        self.assertEqual(1, r)\n\n\n    def test_notInKnownHosts(self):\n        \"\"\"\n        L{default.isInKnownHosts} should return C{0} when a host with a key\n        is not in the known hosts file.\n        \"\"\"\n        r = default.isInKnownHosts(\n            \"not.there\", b\"irrelevant\",\n            {\"known-hosts\": FilePath(self.hostsOption).path})\n        self.assertEqual(0, r)\n\n\n    def test_inKnownHostsKeyChanged(self):\n        \"\"\"\n        L{default.isInKnownHosts} should return C{2} when a host with a key\n        other than the given one is in the known hosts file.\n        \"\"\"\n        host = self.hashedEntries[b\"4.3.2.1\"].toString().split()[0]\n        r = default.isInKnownHosts(\n            host, Key.fromString(otherSampleKey).blob(),\n            {\"known-hosts\": FilePath(self.hostsOption).path})\n        self.assertEqual(2, r)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_manhole.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_manhole -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n# pylint: disable=I0011,W9401,W9402\n\n\"\"\"\nTests for L{twisted.conch.manhole}.\n\"\"\"\n\nimport traceback\n\nfrom twisted.trial import unittest\nfrom twisted.internet import error, defer\nfrom twisted.test.proto_helpers import StringTransport\nfrom twisted.conch.test.test_recvline import (\n    _TelnetMixin, _SSHMixin, _StdioMixin, stdio, ssh)\nfrom twisted.conch import manhole\nfrom twisted.conch.insults import insults\n\n\ndef determineDefaultFunctionName():\n    \"\"\"\n    Return the string used by Python as the name for code objects which are\n    compiled from interactive input or at the top-level of modules.\n    \"\"\"\n    try:\n        1 // 0\n    except:\n        # The last frame is this function.  The second to last frame is this\n        # function's caller, which is module-scope, which is what we want,\n        # so -2.\n        return traceback.extract_stack()[-2][2]\ndefaultFunctionName = determineDefaultFunctionName()\n\n\n\nclass ManholeInterpreterTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{manhole.ManholeInterpreter}.\n    \"\"\"\n    def test_resetBuffer(self):\n        \"\"\"\n        L{ManholeInterpreter.resetBuffer} should empty the input buffer.\n        \"\"\"\n        interpreter = manhole.ManholeInterpreter(None)\n        interpreter.buffer.extend([\"1\", \"2\"])\n        interpreter.resetBuffer()\n        self.assertFalse(interpreter.buffer)\n\n\n\nclass ManholeProtocolTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{manhole.Manhole}.\n    \"\"\"\n    def test_interruptResetsInterpreterBuffer(self):\n        \"\"\"\n        L{manhole.Manhole.handle_INT} should cause the interpreter input buffer\n        to be reset.\n        \"\"\"\n        transport = StringTransport()\n        terminal = insults.ServerProtocol(manhole.Manhole)\n        terminal.makeConnection(transport)\n        protocol = terminal.terminalProtocol\n        interpreter = protocol.interpreter\n        interpreter.buffer.extend([\"1\", \"2\"])\n        protocol.handle_INT()\n        self.assertFalse(interpreter.buffer)\n\n\n\nclass WriterTests(unittest.TestCase):\n    def test_Integer(self):\n        \"\"\"\n        Colorize an integer.\n        \"\"\"\n        manhole.lastColorizedLine(\"1\")\n\n\n    def test_DoubleQuoteString(self):\n        \"\"\"\n        Colorize an integer in double quotes.\n        \"\"\"\n        manhole.lastColorizedLine('\"1\"')\n\n\n    def test_SingleQuoteString(self):\n        \"\"\"\n        Colorize an integer in single quotes.\n        \"\"\"\n        manhole.lastColorizedLine(\"'1'\")\n\n\n    def test_TripleSingleQuotedString(self):\n        \"\"\"\n        Colorize an integer in triple quotes.\n        \"\"\"\n        manhole.lastColorizedLine(\"'''1'''\")\n\n\n    def test_TripleDoubleQuotedString(self):\n        \"\"\"\n        Colorize an integer in triple and double quotes.\n        \"\"\"\n        manhole.lastColorizedLine('\"\"\"1\"\"\"')\n\n\n    def test_FunctionDefinition(self):\n        \"\"\"\n        Colorize a function definition.\n        \"\"\"\n        manhole.lastColorizedLine(\"def foo():\")\n\n\n    def test_ClassDefinition(self):\n        \"\"\"\n        Colorize a class definition.\n        \"\"\"\n        manhole.lastColorizedLine(\"class foo:\")\n\n\n    def test_unicode(self):\n        \"\"\"\n        Colorize a Unicode string.\n        \"\"\"\n        res = manhole.lastColorizedLine(u\"\\u0438\")\n        self.assertTrue(isinstance(res, bytes))\n\n\n    def test_bytes(self):\n        \"\"\"\n        Colorize a UTF-8 byte string.\n        \"\"\"\n        res = manhole.lastColorizedLine(b\"\\xd0\\xb8\")\n        self.assertTrue(isinstance(res, bytes))\n\n\n    def test_identicalOutput(self):\n        \"\"\"\n        The output of UTF-8 bytestrings and Unicode strings are identical.\n        \"\"\"\n        self.assertEqual(manhole.lastColorizedLine(b\"\\xd0\\xb8\"),\n                         manhole.lastColorizedLine(u\"\\u0438\"))\n\n\n\nclass ManholeLoopbackMixin:\n    serverProtocol = manhole.ColoredManhole\n\n\n    def wfd(self, d):\n        return defer.waitForDeferred(d)\n\n\n    def test_SimpleExpression(self):\n        \"\"\"\n        Evaluate simple expression.\n        \"\"\"\n        done = self.recvlineClient.expect(b\"done\")\n\n        self._testwrite(\n            b\"1 + 1\\n\"\n            b\"done\")\n\n        def finished(ign):\n            self._assertBuffer(\n                [b\">>> 1 + 1\",\n                 b\"2\",\n                 b\">>> done\"])\n\n        return done.addCallback(finished)\n\n\n    def test_TripleQuoteLineContinuation(self):\n        \"\"\"\n        Evaluate line continuation in triple quotes.\n        \"\"\"\n        done = self.recvlineClient.expect(b\"done\")\n\n        self._testwrite(\n            b\"'''\\n'''\\n\"\n            b\"done\")\n\n        def finished(ign):\n            self._assertBuffer(\n                [b\">>> '''\",\n                 b\"... '''\",\n                 b\"'\\\\n'\",\n                 b\">>> done\"])\n\n        return done.addCallback(finished)\n\n\n    def test_FunctionDefinition(self):\n        \"\"\"\n        Evaluate function definition.\n        \"\"\"\n        done = self.recvlineClient.expect(b\"done\")\n\n        self._testwrite(\n            b\"def foo(bar):\\n\"\n            b\"\\tprint(bar)\\n\\n\"\n            b\"foo(42)\\n\"\n            b\"done\")\n\n        def finished(ign):\n            self._assertBuffer(\n                [b\">>> def foo(bar):\",\n                 b\"...     print(bar)\",\n                 b\"... \",\n                 b\">>> foo(42)\",\n                 b\"42\",\n                 b\">>> done\"])\n\n        return done.addCallback(finished)\n\n\n    def test_ClassDefinition(self):\n        \"\"\"\n        Evaluate class definition.\n        \"\"\"\n        done = self.recvlineClient.expect(b\"done\")\n        self._testwrite(\n            b\"class Foo:\\n\"\n            b\"\\tdef bar(self):\\n\"\n            b\"\\t\\tprint('Hello, world!')\\n\\n\"\n            b\"Foo().bar()\\n\"\n            b\"done\")\n\n        def finished(ign):\n            self._assertBuffer(\n                [b\">>> class Foo:\",\n                 b\"...     def bar(self):\",\n                 b\"...         print('Hello, world!')\",\n                 b\"... \",\n                 b\">>> Foo().bar()\",\n                 b\"Hello, world!\",\n                 b\">>> done\"])\n\n        return done.addCallback(finished)\n\n\n    def test_Exception(self):\n        \"\"\"\n        Evaluate raising an exception.\n        \"\"\"\n        done = self.recvlineClient.expect(b\"done\")\n\n        self._testwrite(\n            b\"raise Exception('foo bar baz')\\n\"\n            b\"done\")\n\n        def finished(ign):\n            self._assertBuffer(\n                [b\">>> raise Exception('foo bar baz')\",\n                 b\"Traceback (most recent call last):\",\n                 b'  File \"<console>\", line 1, in ' +\n                 defaultFunctionName.encode(\"utf-8\"),\n                 b\"Exception: foo bar baz\",\n                 b\">>> done\"])\n\n        return done.addCallback(finished)\n\n\n    def test_ControlC(self):\n        \"\"\"\n        Evaluate interrupting with CTRL-C.\n        \"\"\"\n        done = self.recvlineClient.expect(b\"done\")\n\n        self._testwrite(\n            b\"cancelled line\" + manhole.CTRL_C +\n            b\"done\")\n\n        def finished(ign):\n            self._assertBuffer(\n                [b\">>> cancelled line\",\n                 b\"KeyboardInterrupt\",\n                 b\">>> done\"])\n\n        return done.addCallback(finished)\n\n\n    def test_interruptDuringContinuation(self):\n        \"\"\"\n        Sending ^C to Manhole while in a state where more input is required to\n        complete a statement should discard the entire ongoing statement and\n        reset the input prompt to the non-continuation prompt.\n        \"\"\"\n        continuing = self.recvlineClient.expect(b\"things\")\n\n        self._testwrite(b\"(\\nthings\")\n\n        def gotContinuation(ignored):\n            self._assertBuffer(\n                [b\">>> (\",\n                 b\"... things\"])\n            interrupted = self.recvlineClient.expect(b\">>> \")\n            self._testwrite(manhole.CTRL_C)\n            return interrupted\n        continuing.addCallback(gotContinuation)\n\n        def gotInterruption(ignored):\n            self._assertBuffer(\n                [b\">>> (\",\n                 b\"... things\",\n                 b\"KeyboardInterrupt\",\n                 b\">>> \"])\n        continuing.addCallback(gotInterruption)\n        return continuing\n\n\n    def test_ControlBackslash(self):\n        \"\"\"\n        Evaluate cancelling with CTRL-\\.\n        \"\"\"\n        self._testwrite(b\"cancelled line\")\n        partialLine = self.recvlineClient.expect(b\"cancelled line\")\n\n        def gotPartialLine(ign):\n            self._assertBuffer(\n                [b\">>> cancelled line\"])\n            self._testwrite(manhole.CTRL_BACKSLASH)\n\n            d = self.recvlineClient.onDisconnection\n            return self.assertFailure(d, error.ConnectionDone)\n\n        def gotClearedLine(ign):\n            self._assertBuffer(\n                [b\"\"])\n\n        return partialLine.addCallback(gotPartialLine).addCallback(\n            gotClearedLine)\n\n\n    @defer.inlineCallbacks\n    def test_controlD(self):\n        \"\"\"\n        A CTRL+D in the middle of a line doesn't close a connection,\n        but at the beginning of a line it does.\n        \"\"\"\n        self._testwrite(b\"1 + 1\")\n        yield self.recvlineClient.expect(br\"\\+ 1\")\n        self._assertBuffer([b\">>> 1 + 1\"])\n\n        self._testwrite(manhole.CTRL_D + b\" + 1\")\n        yield self.recvlineClient.expect(br\"\\+ 1\")\n        self._assertBuffer([b\">>> 1 + 1 + 1\"])\n\n        self._testwrite(b\"\\n\")\n        yield self.recvlineClient.expect(b\"3\\n>>> \")\n\n        self._testwrite(manhole.CTRL_D)\n        d = self.recvlineClient.onDisconnection\n        yield self.assertFailure(d, error.ConnectionDone)\n\n\n    @defer.inlineCallbacks\n    def test_ControlL(self):\n        \"\"\"\n        CTRL+L is generally used as a redraw-screen command in terminal\n        applications.  Manhole doesn't currently respect this usage of it,\n        but it should at least do something reasonable in response to this\n        event (rather than, say, eating your face).\n        \"\"\"\n        # Start off with a newline so that when we clear the display we can\n        # tell by looking for the missing first empty prompt line.\n        self._testwrite(b\"\\n1 + 1\")\n        yield self.recvlineClient.expect(br\"\\+ 1\")\n        self._assertBuffer([b\">>> \", b\">>> 1 + 1\"])\n\n        self._testwrite(manhole.CTRL_L + b\" + 1\")\n        yield self.recvlineClient.expect(br\"1 \\+ 1 \\+ 1\")\n        self._assertBuffer([b\">>> 1 + 1 + 1\"])\n\n\n    def test_controlA(self):\n        \"\"\"\n        CTRL-A can be used as HOME - returning cursor to beginning of\n        current line buffer.\n        \"\"\"\n        self._testwrite(b'rint \"hello\"' + b'\\x01' + b'p')\n        d = self.recvlineClient.expect(b'print \"hello\"')\n        def cb(ignore):\n            self._assertBuffer([b'>>> print \"hello\"'])\n        return d.addCallback(cb)\n\n\n    def test_controlE(self):\n        \"\"\"\n        CTRL-E can be used as END - setting cursor to end of current\n        line buffer.\n        \"\"\"\n        self._testwrite(b'rint \"hello' + b'\\x01' + b'p' + b'\\x05' + b'\"')\n        d = self.recvlineClient.expect(b'print \"hello\"')\n        def cb(ignore):\n            self._assertBuffer([b'>>> print \"hello\"'])\n        return d.addCallback(cb)\n\n\n    @defer.inlineCallbacks\n    def test_deferred(self):\n        \"\"\"\n        When a deferred is returned to the manhole REPL, it is displayed with\n        a sequence number, and when the deferred fires, the result is printed.\n        \"\"\"\n        self._testwrite(\n            b\"from twisted.internet import defer, reactor\\n\"\n            b\"d = defer.Deferred()\\n\"\n            b\"d\\n\")\n\n        yield self.recvlineClient.expect(b\"<Deferred #0>\")\n\n        self._testwrite(\n            b\"c = reactor.callLater(0.1, d.callback, 'Hi!')\\n\")\n        yield self.recvlineClient.expect(b\">>> \")\n\n        yield self.recvlineClient.expect(\n            b\"Deferred #0 called back: 'Hi!'\\n>>> \")\n        self._assertBuffer(\n            [b\">>> from twisted.internet import defer, reactor\",\n             b\">>> d = defer.Deferred()\",\n             b\">>> d\",\n             b\"<Deferred #0>\",\n             b\">>> c = reactor.callLater(0.1, d.callback, 'Hi!')\",\n             b\"Deferred #0 called back: 'Hi!'\",\n             b\">>> \"])\n\n\n\nclass ManholeLoopbackTelnetTests(_TelnetMixin, unittest.TestCase,\n                                 ManholeLoopbackMixin):\n    \"\"\"\n    Test manhole loopback over Telnet.\n    \"\"\"\n    pass\n\n\n\nclass ManholeLoopbackSSHTests(_SSHMixin, unittest.TestCase,\n                              ManholeLoopbackMixin):\n    \"\"\"\n    Test manhole loopback over SSH.\n    \"\"\"\n    if ssh is None:\n        skip = \"cryptography requirements missing\"\n\n\n\nclass ManholeLoopbackStdioTests(_StdioMixin, unittest.TestCase,\n                                ManholeLoopbackMixin):\n    \"\"\"\n    Test manhole loopback over standard IO.\n    \"\"\"\n    if stdio is None:\n        skip = \"Terminal requirements missing\"\n    else:\n        serverProtocol = stdio.ConsoleManhole\n\n\n\nclass ManholeMainTests(unittest.TestCase):\n    \"\"\"\n    Test the I{main} method from the I{manhole} module.\n    \"\"\"\n    if stdio is None:\n        skip = \"Terminal requirements missing\"\n\n\n    def test_mainClassNotFound(self):\n        \"\"\"\n        Will raise an exception when called with an argument which is a\n        dotted patch which can not be imported..\n        \"\"\"\n        exception = self.assertRaises(\n            ValueError,\n            stdio.main, argv=['no-such-class'],\n            )\n\n        self.assertEqual('Empty module name', exception.args[0])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_manhole_tap.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.manhole_tap}.\n\"\"\"\n\ntry:\n    import cryptography\nexcept ImportError:\n    cryptography = None\n\ntry:\n    import pyasn1\nexcept ImportError:\n    pyasn1 = None\n\nif cryptography and pyasn1:\n    from twisted.conch import manhole_tap, manhole_ssh\n\nfrom twisted.application.internet import StreamServerEndpointService\nfrom twisted.application.service import MultiService\n\nfrom twisted.cred import error\nfrom twisted.cred.credentials import UsernamePassword\n\nfrom twisted.conch import telnet\n\nfrom twisted.python import usage\n\nfrom twisted.trial.unittest import TestCase\n\n\n\nclass MakeServiceTests(TestCase):\n    \"\"\"\n    Tests for L{manhole_tap.makeService}.\n    \"\"\"\n\n    if not cryptography:\n        skip = \"can't run without cryptography\"\n\n    if not pyasn1:\n        skip = \"Cannot run without PyASN1\"\n\n    usernamePassword = (b'iamuser', b'thisispassword')\n\n    def setUp(self):\n        \"\"\"\n        Create a passwd-like file with a user.\n        \"\"\"\n        self.filename = self.mktemp()\n        with open(self.filename, 'wb') as f:\n            f.write(b':'.join(self.usernamePassword))\n        self.options = manhole_tap.Options()\n\n\n    def test_requiresPort(self):\n        \"\"\"\n        L{manhole_tap.makeService} requires either 'telnetPort' or 'sshPort' to\n        be given.\n        \"\"\"\n        with self.assertRaises(usage.UsageError) as e:\n            manhole_tap.Options().parseOptions([])\n\n        self.assertEqual(e.exception.args[0], (\"At least one of --telnetPort \"\n                         \"and --sshPort must be specified\"))\n\n\n    def test_telnetPort(self):\n        \"\"\"\n        L{manhole_tap.makeService} will make a telnet service on the port\n        defined by C{--telnetPort}. It will not make a SSH service.\n        \"\"\"\n        self.options.parseOptions([\"--telnetPort\", \"tcp:222\"])\n        service = manhole_tap.makeService(self.options)\n        self.assertIsInstance(service, MultiService)\n        self.assertEqual(len(service.services), 1)\n        self.assertIsInstance(service.services[0], StreamServerEndpointService)\n        self.assertIsInstance(service.services[0].factory.protocol,\n                              manhole_tap.makeTelnetProtocol)\n        self.assertEqual(service.services[0].endpoint._port, 222)\n\n\n    def test_sshPort(self):\n        \"\"\"\n        L{manhole_tap.makeService} will make a SSH service on the port\n        defined by C{--sshPort}. It will not make a telnet service.\n        \"\"\"\n        # Why the sshKeyDir and sshKeySize params? To prevent it stomping over\n        # (or using!) the user's private key, we just make a super small one\n        # which will never be used in a temp directory.\n        self.options.parseOptions([\"--sshKeyDir\", self.mktemp(),\n                                   \"--sshKeySize\", \"512\",\n                                   \"--sshPort\", \"tcp:223\"])\n        service = manhole_tap.makeService(self.options)\n        self.assertIsInstance(service, MultiService)\n        self.assertEqual(len(service.services), 1)\n        self.assertIsInstance(service.services[0], StreamServerEndpointService)\n        self.assertIsInstance(service.services[0].factory,\n                              manhole_ssh.ConchFactory)\n        self.assertEqual(service.services[0].endpoint._port, 223)\n\n\n    def test_passwd(self):\n        \"\"\"\n        The C{--passwd} command-line option will load a passwd-like file.\n        \"\"\"\n        self.options.parseOptions(['--telnetPort', 'tcp:22',\n                                   '--passwd', self.filename])\n        service = manhole_tap.makeService(self.options)\n        portal = service.services[0].factory.protocol.portal\n\n        self.assertEqual(len(portal.checkers.keys()), 2)\n\n        # Ensure it's the passwd file we wanted by trying to authenticate\n        self.assertTrue(self.successResultOf(\n            portal.login(UsernamePassword(*self.usernamePassword),\n                         None, telnet.ITelnetProtocol)))\n        self.assertIsInstance(self.failureResultOf(\n            portal.login(UsernamePassword(b\"wrong\", b\"user\"),\n                         None, telnet.ITelnetProtocol)).value,\n                         error.UnauthorizedLogin)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_mixin.py",
    "content": "# -*- twisted.conch.test.test_mixin -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom twisted.trial import unittest\nfrom twisted.test.proto_helpers import StringTransport\n\nfrom twisted.conch import mixin\n\n\nclass TestBufferingProto(mixin.BufferingMixin):\n    scheduled = False\n    rescheduled = 0\n    def schedule(self):\n        self.scheduled = True\n        return object()\n\n    def reschedule(self, token):\n        self.rescheduled += 1\n\n\n\nclass BufferingTests(unittest.TestCase):\n    def testBuffering(self):\n        p = TestBufferingProto()\n        t = p.transport = StringTransport()\n\n        self.assertFalse(p.scheduled)\n\n        L = [b'foo', b'bar', b'baz', b'quux']\n\n        p.write(b'foo')\n        self.assertTrue(p.scheduled)\n        self.assertFalse(p.rescheduled)\n\n        for s in L:\n            n = p.rescheduled\n            p.write(s)\n            self.assertEqual(p.rescheduled, n + 1)\n            self.assertEqual(t.value(), b'')\n\n        p.flush()\n        self.assertEqual(t.value(), b'foo' + b''.join(L))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_openssh_compat.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.openssh_compat}.\n\"\"\"\n\nimport os\n\nfrom twisted.trial.unittest import TestCase\nfrom twisted.python.filepath import FilePath\nfrom twisted.python.reflect import requireModule\n\nif requireModule('cryptography') and requireModule('pyasn1'):\n    from twisted.conch.openssh_compat.factory import OpenSSHFactory\nelse:\n    OpenSSHFactory = None\n\nfrom twisted.conch.ssh._kex import getDHGeneratorAndPrime\nfrom twisted.conch.test import keydata\nfrom twisted.test.test_process import MockOS\n\n\nclass OpenSSHFactoryTests(TestCase):\n    \"\"\"\n    Tests for L{OpenSSHFactory}.\n    \"\"\"\n    if getattr(os, \"geteuid\", None) is None:\n        skip = \"geteuid/seteuid not available\"\n    elif OpenSSHFactory is None:\n        skip = \"Cannot run without cryptography or PyASN1\"\n\n\n    def setUp(self):\n        self.factory = OpenSSHFactory()\n        self.keysDir = FilePath(self.mktemp())\n        self.keysDir.makedirs()\n        self.factory.dataRoot = self.keysDir.path\n        self.moduliDir = FilePath(self.mktemp())\n        self.moduliDir.makedirs()\n        self.factory.moduliRoot = self.moduliDir.path\n\n        self.keysDir.child(\"ssh_host_foo\").setContent(b\"foo\")\n        self.keysDir.child(\"bar_key\").setContent(b\"foo\")\n        self.keysDir.child(\"ssh_host_one_key\").setContent(\n            keydata.privateRSA_openssh)\n        self.keysDir.child(\"ssh_host_two_key\").setContent(\n            keydata.privateDSA_openssh)\n        self.keysDir.child(\"ssh_host_three_key\").setContent(\n            b\"not a key content\")\n\n        self.keysDir.child(\"ssh_host_one_key.pub\").setContent(\n            keydata.publicRSA_openssh)\n\n        self.moduliDir.child(\"moduli\").setContent(b\"\"\"\n#    $OpenBSD: moduli,v 1.xx 2016/07/26 12:34:56 jhacker Exp $\n# Time Type Tests Tries Size Generator Modulus\n20030501000000 2 6 100 2047 2 FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7EDEE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3DC2007CB8A163BF0598DA48361C55D39A69163FA8FD24CF5F83655D23DCA3AD961C62F356208552BB9ED529077096966D670C354E4ABC9804F1746C08CA18217C32905E462E36CE3BE39E772C180E86039B2783A2EC07A28FB5C55DF06F4C52C9DE2BCBF6955817183995497CEA956AE515D2261898FA051015728E5A8AACAA68FFFFFFFFFFFFFFFF\n\n\"\"\")\n\n        self.mockos = MockOS()\n        self.patch(os, \"seteuid\", self.mockos.seteuid)\n        self.patch(os, \"setegid\", self.mockos.setegid)\n\n\n    def test_getPublicKeys(self):\n        \"\"\"\n        L{OpenSSHFactory.getPublicKeys} should return the available public keys\n        in the data directory\n        \"\"\"\n        keys = self.factory.getPublicKeys()\n        self.assertEqual(len(keys), 1)\n        keyTypes = keys.keys()\n        self.assertEqual(list(keyTypes), [b'ssh-rsa'])\n\n\n    def test_getPrivateKeys(self):\n        \"\"\"\n        Will return the available private keys in the data directory, ignoring\n        key files which failed to be loaded.\n        \"\"\"\n        keys = self.factory.getPrivateKeys()\n        self.assertEqual(len(keys), 2)\n        keyTypes = keys.keys()\n        self.assertEqual(set(keyTypes), set([b'ssh-rsa', b'ssh-dss']))\n        self.assertEqual(self.mockos.seteuidCalls, [])\n        self.assertEqual(self.mockos.setegidCalls, [])\n\n\n    def test_getPrivateKeysAsRoot(self):\n        \"\"\"\n        L{OpenSSHFactory.getPrivateKeys} should switch to root if the keys\n        aren't readable by the current user.\n        \"\"\"\n        keyFile = self.keysDir.child(\"ssh_host_two_key\")\n        # Fake permission error by changing the mode\n        keyFile.chmod(0000)\n        self.addCleanup(keyFile.chmod, 0o777)\n        # And restore the right mode when seteuid is called\n        savedSeteuid = os.seteuid\n        def seteuid(euid):\n            keyFile.chmod(0o777)\n            return savedSeteuid(euid)\n        self.patch(os, \"seteuid\", seteuid)\n        keys = self.factory.getPrivateKeys()\n        self.assertEqual(len(keys), 2)\n        keyTypes = keys.keys()\n        self.assertEqual(set(keyTypes), set([b'ssh-rsa', b'ssh-dss']))\n        self.assertEqual(self.mockos.seteuidCalls, [0, os.geteuid()])\n        self.assertEqual(self.mockos.setegidCalls, [0, os.getegid()])\n\n\n    def test_getPrimes(self):\n        \"\"\"\n        L{OpenSSHFactory.getPrimes} should return the available primes\n        in the moduli directory.\n        \"\"\"\n        primes = self.factory.getPrimes()\n        self.assertEqual(primes, {\n            2048: [getDHGeneratorAndPrime(b\"diffie-hellman-group14-sha1\")],\n        })\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_recvline.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_recvline -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.recvline} and fixtures for testing related\nfunctionality.\n\"\"\"\n\nimport os\nimport sys\n\nfrom twisted.conch.insults import insults\nfrom twisted.conch import recvline\n\nfrom twisted.python import reflect, components, filepath\nfrom twisted.python.compat import iterbytes, bytesEnviron\nfrom twisted.python.runtime import platform\nfrom twisted.internet import defer, error\nfrom twisted.trial import unittest\nfrom twisted.cred import portal\nfrom twisted.test.proto_helpers import StringTransport\n\nif platform.isWindows():\n    properEnv = dict(os.environ)\n    properEnv[\"PYTHONPATH\"] = os.pathsep.join(sys.path)\nelse:\n    properEnv = bytesEnviron()\n    properEnv[b\"PYTHONPATH\"] = os.pathsep.join(sys.path).encode(\n        sys.getfilesystemencoding())\n\n\n\nclass ArrowsTests(unittest.TestCase):\n    def setUp(self):\n        self.underlyingTransport = StringTransport()\n        self.pt = insults.ServerProtocol()\n        self.p = recvline.HistoricRecvLine()\n        self.pt.protocolFactory = lambda: self.p\n        self.pt.factory = self\n        self.pt.makeConnection(self.underlyingTransport)\n\n\n    def test_printableCharacters(self):\n        \"\"\"\n        When L{HistoricRecvLine} receives a printable character,\n        it adds it to the current line buffer.\n        \"\"\"\n        self.p.keystrokeReceived(b'x', None)\n        self.p.keystrokeReceived(b'y', None)\n        self.p.keystrokeReceived(b'z', None)\n\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyz', b''))\n\n\n    def test_horizontalArrows(self):\n        \"\"\"\n        When L{HistoricRecvLine} receives a LEFT_ARROW or\n        RIGHT_ARROW keystroke it moves the cursor left or right\n        in the current line buffer, respectively.\n        \"\"\"\n        kR = lambda ch: self.p.keystrokeReceived(ch, None)\n        for ch in iterbytes(b'xyz'):\n            kR(ch)\n\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyz', b''))\n\n        kR(self.pt.RIGHT_ARROW)\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyz', b''))\n\n        kR(self.pt.LEFT_ARROW)\n        self.assertEqual(self.p.currentLineBuffer(), (b'xy', b'z'))\n\n        kR(self.pt.LEFT_ARROW)\n        self.assertEqual(self.p.currentLineBuffer(), (b'x', b'yz'))\n\n        kR(self.pt.LEFT_ARROW)\n        self.assertEqual(self.p.currentLineBuffer(), (b'', b'xyz'))\n\n        kR(self.pt.LEFT_ARROW)\n        self.assertEqual(self.p.currentLineBuffer(), (b'', b'xyz'))\n\n        kR(self.pt.RIGHT_ARROW)\n        self.assertEqual(self.p.currentLineBuffer(), (b'x', b'yz'))\n\n        kR(self.pt.RIGHT_ARROW)\n        self.assertEqual(self.p.currentLineBuffer(), (b'xy', b'z'))\n\n        kR(self.pt.RIGHT_ARROW)\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyz', b''))\n\n        kR(self.pt.RIGHT_ARROW)\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyz', b''))\n\n\n    def test_newline(self):\n        \"\"\"\n        When {HistoricRecvLine} receives a newline, it adds the current\n        line buffer to the end of its history buffer.\n        \"\"\"\n        kR = lambda ch: self.p.keystrokeReceived(ch, None)\n\n        for ch in iterbytes(b'xyz\\nabc\\n123\\n'):\n            kR(ch)\n\n        self.assertEqual(self.p.currentHistoryBuffer(),\n                          ((b'xyz', b'abc', b'123'), ()))\n\n        kR(b'c')\n        kR(b'b')\n        kR(b'a')\n        self.assertEqual(self.p.currentHistoryBuffer(),\n                          ((b'xyz', b'abc', b'123'), ()))\n\n        kR(b'\\n')\n        self.assertEqual(self.p.currentHistoryBuffer(),\n                          ((b'xyz', b'abc', b'123', b'cba'), ()))\n\n\n    def test_verticalArrows(self):\n        \"\"\"\n        When L{HistoricRecvLine} receives UP_ARROW or DOWN_ARROW\n        keystrokes it move the current index in the current history\n        buffer up or down, and resets the current line buffer to the\n        previous or next line in history, respectively for each.\n        \"\"\"\n        kR = lambda ch: self.p.keystrokeReceived(ch, None)\n\n        for ch in iterbytes(b'xyz\\nabc\\n123\\n'):\n            kR(ch)\n\n        self.assertEqual(self.p.currentHistoryBuffer(),\n                          ((b'xyz', b'abc', b'123'), ()))\n        self.assertEqual(self.p.currentLineBuffer(), (b'', b''))\n\n        kR(self.pt.UP_ARROW)\n        self.assertEqual(self.p.currentHistoryBuffer(),\n                          ((b'xyz', b'abc'), (b'123',)))\n        self.assertEqual(self.p.currentLineBuffer(), (b'123', b''))\n\n        kR(self.pt.UP_ARROW)\n        self.assertEqual(self.p.currentHistoryBuffer(),\n                          ((b'xyz',), (b'abc', b'123')))\n        self.assertEqual(self.p.currentLineBuffer(), (b'abc', b''))\n\n        kR(self.pt.UP_ARROW)\n        self.assertEqual(self.p.currentHistoryBuffer(),\n                          ((), (b'xyz', b'abc', b'123')))\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyz', b''))\n\n        kR(self.pt.UP_ARROW)\n        self.assertEqual(self.p.currentHistoryBuffer(),\n                          ((), (b'xyz', b'abc', b'123')))\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyz', b''))\n\n        for i in range(4):\n            kR(self.pt.DOWN_ARROW)\n        self.assertEqual(self.p.currentHistoryBuffer(),\n                          ((b'xyz', b'abc', b'123'), ()))\n\n\n    def test_home(self):\n        \"\"\"\n        When L{HistoricRecvLine} receives a HOME keystroke it moves the\n        cursor to the beginning of the current line buffer.\n        \"\"\"\n        kR = lambda ch: self.p.keystrokeReceived(ch, None)\n\n        for ch in iterbytes(b'hello, world'):\n            kR(ch)\n        self.assertEqual(self.p.currentLineBuffer(), (b'hello, world', b''))\n\n        kR(self.pt.HOME)\n        self.assertEqual(self.p.currentLineBuffer(), (b'', b'hello, world'))\n\n\n    def test_end(self):\n        \"\"\"\n        When L{HistoricRecvLine} receives an END keystroke it moves the cursor\n        to the end of the current line buffer.\n        \"\"\"\n        kR = lambda ch: self.p.keystrokeReceived(ch, None)\n\n        for ch in iterbytes(b'hello, world'):\n            kR(ch)\n        self.assertEqual(self.p.currentLineBuffer(), (b'hello, world', b''))\n\n        kR(self.pt.HOME)\n        kR(self.pt.END)\n        self.assertEqual(self.p.currentLineBuffer(), (b'hello, world', b''))\n\n\n    def test_backspace(self):\n        \"\"\"\n        When L{HistoricRecvLine} receives a BACKSPACE keystroke it deletes\n        the character immediately before the cursor.\n        \"\"\"\n        kR = lambda ch: self.p.keystrokeReceived(ch, None)\n\n        for ch in iterbytes(b'xyz'):\n            kR(ch)\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyz', b''))\n\n        kR(self.pt.BACKSPACE)\n        self.assertEqual(self.p.currentLineBuffer(), (b'xy', b''))\n\n        kR(self.pt.LEFT_ARROW)\n        kR(self.pt.BACKSPACE)\n        self.assertEqual(self.p.currentLineBuffer(), (b'', b'y'))\n\n        kR(self.pt.BACKSPACE)\n        self.assertEqual(self.p.currentLineBuffer(), (b'', b'y'))\n\n\n    def test_delete(self):\n        \"\"\"\n        When L{HistoricRecvLine} receives a DELETE keystroke, it\n        delets the character immediately after the cursor.\n        \"\"\"\n        kR = lambda ch: self.p.keystrokeReceived(ch, None)\n\n        for ch in iterbytes(b'xyz'):\n            kR(ch)\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyz', b''))\n\n        kR(self.pt.DELETE)\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyz', b''))\n\n        kR(self.pt.LEFT_ARROW)\n        kR(self.pt.DELETE)\n        self.assertEqual(self.p.currentLineBuffer(), (b'xy', b''))\n\n        kR(self.pt.LEFT_ARROW)\n        kR(self.pt.DELETE)\n        self.assertEqual(self.p.currentLineBuffer(), (b'x', b''))\n\n        kR(self.pt.LEFT_ARROW)\n        kR(self.pt.DELETE)\n        self.assertEqual(self.p.currentLineBuffer(), (b'', b''))\n\n        kR(self.pt.DELETE)\n        self.assertEqual(self.p.currentLineBuffer(), (b'', b''))\n\n\n    def test_insert(self):\n        \"\"\"\n        When not in INSERT mode, L{HistoricRecvLine} inserts the typed\n        character at the cursor before the next character.\n        \"\"\"\n        kR = lambda ch: self.p.keystrokeReceived(ch, None)\n\n        for ch in iterbytes(b'xyz'):\n            kR(ch)\n\n        kR(self.pt.LEFT_ARROW)\n        kR(b'A')\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyA', b'z'))\n\n        kR(self.pt.LEFT_ARROW)\n        kR(b'B')\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyB', b'Az'))\n\n\n    def test_typeover(self):\n        \"\"\"\n        When in INSERT mode and upon receiving a keystroke with a printable\n        character, L{HistoricRecvLine} replaces the character at\n        the cursor with the typed character rather than inserting before.\n        Ah, the ironies of INSERT mode.\n        \"\"\"\n        kR = lambda ch: self.p.keystrokeReceived(ch, None)\n\n        for ch in iterbytes(b'xyz'):\n            kR(ch)\n\n        kR(self.pt.INSERT)\n\n        kR(self.pt.LEFT_ARROW)\n        kR(b'A')\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyA', b''))\n\n        kR(self.pt.LEFT_ARROW)\n        kR(b'B')\n        self.assertEqual(self.p.currentLineBuffer(), (b'xyB', b''))\n\n\n    def test_unprintableCharacters(self):\n        \"\"\"\n        When L{HistoricRecvLine} receives a keystroke for an unprintable\n        function key with no assigned behavior, the line buffer is unmodified.\n        \"\"\"\n        kR = lambda ch: self.p.keystrokeReceived(ch, None)\n        pt = self.pt\n\n        for ch in (pt.F1, pt.F2, pt.F3, pt.F4, pt.F5, pt.F6, pt.F7, pt.F8,\n                   pt.F9, pt.F10, pt.F11, pt.F12, pt.PGUP, pt.PGDN):\n            kR(ch)\n            self.assertEqual(self.p.currentLineBuffer(), (b'', b''))\n\n\n\nfrom twisted.conch import telnet\nfrom twisted.conch.insults import helper\nfrom twisted.conch.test.loopback import LoopbackRelay\n\nclass EchoServer(recvline.HistoricRecvLine):\n    def lineReceived(self, line):\n        self.terminal.write(line + b'\\n' + self.ps[self.pn])\n\n# An insults API for this would be nice.\nleft = b\"\\x1b[D\"\nright = b\"\\x1b[C\"\nup = b\"\\x1b[A\"\ndown = b\"\\x1b[B\"\ninsert = b\"\\x1b[2~\"\nhome = b\"\\x1b[1~\"\ndelete = b\"\\x1b[3~\"\nend = b\"\\x1b[4~\"\nbackspace = b\"\\x7f\"\n\nfrom twisted.cred import checkers\n\ntry:\n    from twisted.conch.ssh import (userauth, transport, channel, connection,\n                                   session, keys)\n    from twisted.conch.manhole_ssh import TerminalUser, TerminalSession, TerminalRealm, TerminalSessionTransport, ConchFactory\nexcept ImportError:\n    ssh = False\nelse:\n    ssh = True\n    class SessionChannel(channel.SSHChannel):\n        name = b'session'\n\n        def __init__(self, protocolFactory, protocolArgs, protocolKwArgs, width, height, *a, **kw):\n            channel.SSHChannel.__init__(self, *a, **kw)\n\n            self.protocolFactory = protocolFactory\n            self.protocolArgs = protocolArgs\n            self.protocolKwArgs = protocolKwArgs\n\n            self.width = width\n            self.height = height\n\n\n        def channelOpen(self, data):\n            term = session.packRequest_pty_req(b\"vt102\", (self.height, self.width, 0, 0), b'')\n            self.conn.sendRequest(self, b'pty-req', term)\n            self.conn.sendRequest(self, b'shell', b'')\n\n            self._protocolInstance = self.protocolFactory(*self.protocolArgs, **self.protocolKwArgs)\n            self._protocolInstance.factory = self\n            self._protocolInstance.makeConnection(self)\n\n\n        def closed(self):\n            self._protocolInstance.connectionLost(error.ConnectionDone())\n\n\n        def dataReceived(self, data):\n            self._protocolInstance.dataReceived(data)\n\n\n    class TestConnection(connection.SSHConnection):\n        def __init__(self, protocolFactory, protocolArgs, protocolKwArgs, width, height, *a, **kw):\n            connection.SSHConnection.__init__(self, *a, **kw)\n\n            self.protocolFactory = protocolFactory\n            self.protocolArgs = protocolArgs\n            self.protocolKwArgs = protocolKwArgs\n\n            self.width = width\n            self.height = height\n\n\n        def serviceStarted(self):\n            self.__channel = SessionChannel(self.protocolFactory, self.protocolArgs, self.protocolKwArgs, self.width, self.height)\n            self.openChannel(self.__channel)\n\n\n        def write(self, data):\n            return self.__channel.write(data)\n\n\n    class TestAuth(userauth.SSHUserAuthClient):\n        def __init__(self, username, password, *a, **kw):\n            userauth.SSHUserAuthClient.__init__(self, username, *a, **kw)\n            self.password = password\n\n\n        def getPassword(self):\n            return defer.succeed(self.password)\n\n\n    class TestTransport(transport.SSHClientTransport):\n        def __init__(self, protocolFactory, protocolArgs, protocolKwArgs, username, password, width, height, *a, **kw):\n            self.protocolFactory = protocolFactory\n            self.protocolArgs = protocolArgs\n            self.protocolKwArgs = protocolKwArgs\n            self.username = username\n            self.password = password\n            self.width = width\n            self.height = height\n\n\n        def verifyHostKey(self, hostKey, fingerprint):\n            return defer.succeed(True)\n\n\n        def connectionSecure(self):\n            self.__connection = TestConnection(self.protocolFactory, self.protocolArgs, self.protocolKwArgs, self.width, self.height)\n            self.requestService(\n                TestAuth(self.username, self.password, self.__connection))\n\n\n        def write(self, data):\n            return self.__connection.write(data)\n\n\n    class TestSessionTransport(TerminalSessionTransport):\n        def protocolFactory(self):\n            return self.avatar.conn.transport.factory.serverProtocol()\n\n\n    class TestSession(TerminalSession):\n        transportFactory = TestSessionTransport\n\n\n    class TestUser(TerminalUser):\n        pass\n\n    components.registerAdapter(TestSession, TestUser, session.ISession)\n\n\n\nclass NotifyingExpectableBuffer(helper.ExpectableBuffer):\n    def __init__(self):\n        self.onConnection = defer.Deferred()\n        self.onDisconnection = defer.Deferred()\n\n\n    def connectionMade(self):\n        helper.ExpectableBuffer.connectionMade(self)\n        self.onConnection.callback(self)\n\n\n    def connectionLost(self, reason):\n        self.onDisconnection.errback(reason)\n\n\n\nclass _BaseMixin:\n    WIDTH = 80\n    HEIGHT = 24\n\n    def _assertBuffer(self, lines):\n        receivedLines = self.recvlineClient.__bytes__().splitlines()\n        expectedLines = lines + ([b''] * (self.HEIGHT - len(lines) - 1))\n        self.assertEqual(len(receivedLines), len(expectedLines))\n        for i in range(len(receivedLines)):\n            self.assertEqual(\n                receivedLines[i], expectedLines[i],\n                b\"\".join(receivedLines[max(0, i-1):i+1]) +\n                b\" != \" +\n                b\"\".join(expectedLines[max(0, i-1):i+1]))\n\n\n    def _trivialTest(self, inputLine, output):\n        done = self.recvlineClient.expect(b\"done\")\n\n        self._testwrite(inputLine)\n\n        def finished(ign):\n            self._assertBuffer(output)\n\n        return done.addCallback(finished)\n\n\n\nclass _SSHMixin(_BaseMixin):\n    def setUp(self):\n        if not ssh:\n            raise unittest.SkipTest(\n                \"cryptography requirements missing, can't run historic \"\n                \"recvline tests over ssh\")\n\n        u, p = b'testuser', b'testpass'\n        rlm = TerminalRealm()\n        rlm.userFactory = TestUser\n        rlm.chainedProtocolFactory = lambda: insultsServer\n\n        checker = checkers.InMemoryUsernamePasswordDatabaseDontUse()\n        checker.addUser(u, p)\n        ptl = portal.Portal(rlm)\n        ptl.registerChecker(checker)\n        sshFactory = ConchFactory(ptl)\n\n        sshKey = keys._getPersistentRSAKey(filepath.FilePath(self.mktemp()),\n                                           keySize=512)\n        sshFactory.publicKeys[b\"ssh-rsa\"] = sshKey\n        sshFactory.privateKeys[b\"ssh-rsa\"] = sshKey\n\n        sshFactory.serverProtocol = self.serverProtocol\n        sshFactory.startFactory()\n\n        recvlineServer = self.serverProtocol()\n        insultsServer = insults.ServerProtocol(lambda: recvlineServer)\n        sshServer = sshFactory.buildProtocol(None)\n        clientTransport = LoopbackRelay(sshServer)\n\n        recvlineClient = NotifyingExpectableBuffer()\n        insultsClient = insults.ClientProtocol(lambda: recvlineClient)\n        sshClient = TestTransport(lambda: insultsClient, (), {}, u, p, self.WIDTH, self.HEIGHT)\n        serverTransport = LoopbackRelay(sshClient)\n\n        sshClient.makeConnection(clientTransport)\n        sshServer.makeConnection(serverTransport)\n\n        self.recvlineClient = recvlineClient\n        self.sshClient = sshClient\n        self.sshServer = sshServer\n        self.clientTransport = clientTransport\n        self.serverTransport = serverTransport\n\n        return recvlineClient.onConnection\n\n\n    def _testwrite(self, data):\n        self.sshClient.write(data)\n\n\n\nfrom twisted.conch.test import test_telnet\n\nclass TestInsultsClientProtocol(insults.ClientProtocol,\n                                test_telnet.TestProtocol):\n    pass\n\n\n\nclass TestInsultsServerProtocol(insults.ServerProtocol,\n                                test_telnet.TestProtocol):\n    pass\n\n\n\nclass _TelnetMixin(_BaseMixin):\n    def setUp(self):\n        recvlineServer = self.serverProtocol()\n        insultsServer = TestInsultsServerProtocol(lambda: recvlineServer)\n        telnetServer = telnet.TelnetTransport(lambda: insultsServer)\n        clientTransport = LoopbackRelay(telnetServer)\n\n        recvlineClient = NotifyingExpectableBuffer()\n        insultsClient = TestInsultsClientProtocol(lambda: recvlineClient)\n        telnetClient = telnet.TelnetTransport(lambda: insultsClient)\n        serverTransport = LoopbackRelay(telnetClient)\n\n        telnetClient.makeConnection(clientTransport)\n        telnetServer.makeConnection(serverTransport)\n\n        serverTransport.clearBuffer()\n        clientTransport.clearBuffer()\n\n        self.recvlineClient = recvlineClient\n        self.telnetClient = telnetClient\n        self.clientTransport = clientTransport\n        self.serverTransport = serverTransport\n\n        return recvlineClient.onConnection\n\n\n    def _testwrite(self, data):\n        self.telnetClient.write(data)\n\ntry:\n    from twisted.conch import stdio\nexcept ImportError:\n    stdio = None\n\n\n\nclass _StdioMixin(_BaseMixin):\n    def setUp(self):\n        # A memory-only terminal emulator, into which the server will\n        # write things and make other state changes.  What ends up\n        # here is basically what a user would have seen on their\n        # screen.\n        testTerminal = NotifyingExpectableBuffer()\n\n        # An insults client protocol which will translate bytes\n        # received from the child process into keystroke commands for\n        # an ITerminalProtocol.\n        insultsClient = insults.ClientProtocol(lambda: testTerminal)\n\n        # A process protocol which will translate stdout and stderr\n        # received from the child process to dataReceived calls and\n        # error reporting on an insults client protocol.\n        processClient = stdio.TerminalProcessProtocol(insultsClient)\n\n        # Run twisted/conch/stdio.py with the name of a class\n        # implementing ITerminalProtocol.  This class will be used to\n        # handle bytes we send to the child process.\n        exe = sys.executable\n        module = stdio.__file__\n        if module.endswith('.pyc') or module.endswith('.pyo'):\n            module = module[:-1]\n        args = [exe, module, reflect.qual(self.serverProtocol)]\n        if not platform.isWindows():\n            args = [arg.encode(sys.getfilesystemencoding()) for arg in args]\n\n        from twisted.internet import reactor\n        clientTransport = reactor.spawnProcess(processClient, exe, args,\n                                               env=properEnv, usePTY=True)\n\n        self.recvlineClient = self.testTerminal = testTerminal\n        self.processClient = processClient\n        self.clientTransport = clientTransport\n\n        # Wait for the process protocol and test terminal to become\n        # connected before proceeding.  The former should always\n        # happen first, but it doesn't hurt to be safe.\n        return defer.gatherResults(filter(None, [\n            processClient.onConnection,\n            testTerminal.expect(b\">>> \")]))\n\n\n    def tearDown(self):\n        # Kill the child process.  We're done with it.\n        try:\n            self.clientTransport.signalProcess(\"KILL\")\n        except (error.ProcessExitedAlready, OSError):\n            pass\n        def trap(failure):\n            failure.trap(error.ProcessTerminated)\n            self.assertIsNone(failure.value.exitCode)\n            self.assertEqual(failure.value.status, 9)\n        return self.testTerminal.onDisconnection.addErrback(trap)\n\n\n    def _testwrite(self, data):\n        self.clientTransport.write(data)\n\n\n\nclass RecvlineLoopbackMixin:\n    serverProtocol = EchoServer\n\n    def testSimple(self):\n        return self._trivialTest(\n            b\"first line\\ndone\",\n            [b\">>> first line\",\n             b\"first line\",\n             b\">>> done\"])\n\n\n    def testLeftArrow(self):\n        return self._trivialTest(\n            insert + b'first line' + left * 4 + b\"xxxx\\ndone\",\n            [b\">>> first xxxx\",\n             b\"first xxxx\",\n             b\">>> done\"])\n\n\n    def testRightArrow(self):\n        return self._trivialTest(\n            insert + b'right line' + left * 4 + right * 2 + b\"xx\\ndone\",\n            [b\">>> right lixx\",\n             b\"right lixx\",\n            b\">>> done\"])\n\n\n    def testBackspace(self):\n        return self._trivialTest(\n            b\"second line\" + backspace * 4 + b\"xxxx\\ndone\",\n            [b\">>> second xxxx\",\n             b\"second xxxx\",\n             b\">>> done\"])\n\n\n    def testDelete(self):\n        return self._trivialTest(\n            b\"delete xxxx\" + left * 4 + delete * 4 + b\"line\\ndone\",\n            [b\">>> delete line\",\n             b\"delete line\",\n             b\">>> done\"])\n\n\n    def testInsert(self):\n        return self._trivialTest(\n            b\"third ine\" + left * 3 + b\"l\\ndone\",\n            [b\">>> third line\",\n             b\"third line\",\n             b\">>> done\"])\n\n\n    def testTypeover(self):\n        return self._trivialTest(\n            b\"fourth xine\" + left * 4 + insert + b\"l\\ndone\",\n            [b\">>> fourth line\",\n             b\"fourth line\",\n             b\">>> done\"])\n\n\n    def testHome(self):\n        return self._trivialTest(\n            insert + b\"blah line\" + home + b\"home\\ndone\",\n            [b\">>> home line\",\n             b\"home line\",\n             b\">>> done\"])\n\n\n    def testEnd(self):\n        return self._trivialTest(\n            b\"end \" + left * 4 + end + b\"line\\ndone\",\n            [b\">>> end line\",\n             b\"end line\",\n             b\">>> done\"])\n\n\n\nclass RecvlineLoopbackTelnetTests(_TelnetMixin, unittest.TestCase, RecvlineLoopbackMixin):\n    pass\n\n\n\nclass RecvlineLoopbackSSHTests(_SSHMixin, unittest.TestCase, RecvlineLoopbackMixin):\n    pass\n\n\n\nclass RecvlineLoopbackStdioTests(_StdioMixin, unittest.TestCase, RecvlineLoopbackMixin):\n    if stdio is None:\n        skip = \"Terminal requirements missing, can't run recvline tests over stdio\"\n\n\n\nclass HistoricRecvlineLoopbackMixin:\n    serverProtocol = EchoServer\n\n    def testUpArrow(self):\n        return self._trivialTest(\n            b\"first line\\n\" + up + b\"\\ndone\",\n            [b\">>> first line\",\n             b\"first line\",\n             b\">>> first line\",\n             b\"first line\",\n             b\">>> done\"])\n\n\n    def test_DownArrowToPartialLineInHistory(self):\n        \"\"\"\n        Pressing down arrow to visit an entry that was added to the\n        history by pressing the up arrow instead of return does not\n        raise a L{TypeError}.\n\n        @see: U{http://twistedmatrix.com/trac/ticket/9031}\n\n        @return: A L{defer.Deferred} that fires when C{b\"done\"} is\n            echoed back.\n        \"\"\"\n\n        return self._trivialTest(\n            b\"first line\\n\" + b\"partial line\" + up + down + b\"\\ndone\",\n            [b\">>> first line\",\n             b\"first line\",\n             b\">>> partial line\",\n             b\"partial line\",\n             b\">>> done\"])\n\n\n    def testDownArrow(self):\n        return self._trivialTest(\n            b\"first line\\nsecond line\\n\" + up * 2 + down + b\"\\ndone\",\n            [b\">>> first line\",\n             b\"first line\",\n             b\">>> second line\",\n             b\"second line\",\n             b\">>> second line\",\n             b\"second line\",\n             b\">>> done\"])\n\n\n\nclass HistoricRecvlineLoopbackTelnetTests(_TelnetMixin, unittest.TestCase, HistoricRecvlineLoopbackMixin):\n    pass\n\n\n\nclass HistoricRecvlineLoopbackSSHTests(_SSHMixin, unittest.TestCase, HistoricRecvlineLoopbackMixin):\n    pass\n\n\n\nclass HistoricRecvlineLoopbackStdioTests(_StdioMixin, unittest.TestCase, HistoricRecvlineLoopbackMixin):\n    if stdio is None:\n        skip = \"Terminal requirements missing, can't run historic recvline tests over stdio\"\n\n\n\nclass TransportSequenceTests(unittest.TestCase):\n    \"\"\"\n    L{twisted.conch.recvline.TransportSequence}\n    \"\"\"\n\n    def test_invalidSequence(self):\n        \"\"\"\n        Initializing a L{recvline.TransportSequence} with no args\n        raises an assertion.\n        \"\"\"\n        self.assertRaises(AssertionError, recvline.TransportSequence)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_scripts.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for the command-line interfaces to conch.\n\"\"\"\nfrom twisted.python.reflect import requireModule\n\nif requireModule('pyasn1'):\n    pyasn1Skip = None\nelse:\n    pyasn1Skip =  \"Cannot run without PyASN1\"\n\nif requireModule('cryptography'):\n    cryptoSkip = None\nelse:\n    cryptoSkip = \"can't run w/o cryptography\"\n\nif requireModule('tty'):\n    ttySkip = None\nelse:\n    ttySkip = \"can't run w/o tty\"\n\ntry:\n    import Tkinter\nexcept ImportError:\n    tkskip = \"can't run w/o Tkinter\"\nelse:\n    try:\n        Tkinter.Tk().destroy()\n    except Tkinter.TclError as e:\n        tkskip = \"Can't test Tkinter: \" + str(e)\n    else:\n        tkskip = None\n\nfrom twisted.trial.unittest import TestCase\nfrom twisted.scripts.test.test_scripts import ScriptTestsMixin\nfrom twisted.python.test.test_shellcomp import ZshScriptTestMixin\n\n\n\nclass ScriptTests(TestCase, ScriptTestsMixin):\n    \"\"\"\n    Tests for the Conch scripts.\n    \"\"\"\n    skip = pyasn1Skip or cryptoSkip\n\n\n    def test_conch(self):\n        self.scriptTest(\"conch/conch\")\n    test_conch.skip = ttySkip or skip\n\n\n    def test_cftp(self):\n        self.scriptTest(\"conch/cftp\")\n    test_cftp.skip = ttySkip or skip\n\n\n    def test_ckeygen(self):\n        self.scriptTest(\"conch/ckeygen\")\n\n\n    def test_tkconch(self):\n        self.scriptTest(\"conch/tkconch\")\n    test_tkconch.skip = tkskip or skip\n\n\n\nclass ZshIntegrationTests(TestCase, ZshScriptTestMixin):\n    \"\"\"\n    Test that zsh completion functions are generated without error\n    \"\"\"\n    generateFor = [('conch', 'twisted.conch.scripts.conch.ClientOptions'),\n                   ('cftp', 'twisted.conch.scripts.cftp.ClientOptions'),\n                   ('ckeygen', 'twisted.conch.scripts.ckeygen.GeneralOptions'),\n                   ('tkconch', 'twisted.conch.scripts.tkconch.GeneralOptions'),\n                   ]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_session.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for the 'session' channel implementation in twisted.conch.ssh.session.\n\nSee also RFC 4254.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport os, signal, sys, struct\n\nfrom zope.interface import implementer\n\nfrom twisted.python.reflect import requireModule\n\ncryptography = requireModule(\"cryptography\")\nif cryptography:\n    from twisted.conch.ssh import common, session, connection\nelse:\n    class session:\n        from twisted.conch.interfaces import ISession\n\nfrom twisted.internet.address import IPv4Address\nfrom twisted.internet.error import ProcessTerminated, ProcessDone\nfrom twisted.python.failure import Failure\nfrom twisted.internet import defer, protocol, error\nfrom twisted.python import components, failure\nfrom twisted.trial import unittest\n\n\n\nclass SubsystemOnlyAvatar(object):\n    \"\"\"\n    A stub class representing an avatar that is only useful for\n    getting a subsystem.\n    \"\"\"\n\n\n    def lookupSubsystem(self, name, data):\n        \"\"\"\n        If the other side requests the 'subsystem' subsystem, allow it by\n        returning a MockProtocol to implement it. Otherwise raise an assertion.\n        \"\"\"\n        assert name == b'subsystem'\n        return MockProtocol()\n\n\n\nclass StubAvatar:\n    \"\"\"\n    A stub class representing the avatar representing the authenticated user.\n    It implements the I{ISession} interface.\n    \"\"\"\n\n\n    def lookupSubsystem(self, name, data):\n        \"\"\"\n        If the user requests the TestSubsystem subsystem, connect them to a\n        MockProtocol.  If they request neither, then None is returned which is\n        interpreted by SSHSession as a failure.\n        \"\"\"\n        if name == b'TestSubsystem':\n            self.subsystem = MockProtocol()\n            self.subsystem.packetData = data\n            return self.subsystem\n\n\n\n@implementer(session.ISession)\nclass StubSessionForStubAvatar(object):\n    \"\"\"\n    A stub ISession implementation for our StubAvatar.  The instance\n    variables generally keep track of method invocations so that we can test\n    that the methods were called.\n\n    @ivar avatar: the L{StubAvatar} we are adapting.\n    @ivar ptyRequest: if present, the terminal, window size, and modes passed\n        to the getPty method.\n    @ivar windowChange: if present, the window size passed to the\n        windowChangned method.\n    @ivar shellProtocol: if present, the L{SSHSessionProcessProtocol} passed\n        to the openShell method.\n    @ivar shellTransport: if present, the L{EchoTransport} connected to\n        shellProtocol.\n    @ivar execProtocol: if present, the L{SSHSessionProcessProtocol} passed\n        to the execCommand method.\n    @ivar execTransport: if present, the L{EchoTransport} connected to\n        execProtocol.\n    @ivar execCommandLine: if present, the command line passed to the\n        execCommand method.\n    @ivar gotEOF: if present, an EOF message was received.\n    @ivar gotClosed: if present, a closed message was received.\n    \"\"\"\n    def __init__(self, avatar):\n        \"\"\"\n        Store the avatar we're adapting.\n        \"\"\"\n        self.avatar = avatar\n        self.shellProtocol = None\n\n\n    def getPty(self, terminal, window, modes):\n        \"\"\"\n        If the terminal is 'bad', fail.  Otherwise, store the information in\n        the ptyRequest variable.\n        \"\"\"\n        if terminal != b'bad':\n            self.ptyRequest = (terminal, window, modes)\n        else:\n            raise RuntimeError('not getting a pty')\n\n\n    def windowChanged(self, window):\n        \"\"\"\n        If all the window sizes are 0, fail.  Otherwise, store the size in the\n        windowChange variable.\n        \"\"\"\n        if window == (0, 0, 0, 0):\n            raise RuntimeError('not changing the window size')\n        else:\n            self.windowChange = window\n\n\n    def openShell(self, pp):\n        \"\"\"\n        If we have gotten a shell request before, fail.  Otherwise, store the\n        process protocol in the shellProtocol variable, connect it to the\n        EchoTransport and store that as shellTransport.\n        \"\"\"\n        if self.shellProtocol is not None:\n            raise RuntimeError('not getting a shell this time')\n        else:\n            self.shellProtocol = pp\n            self.shellTransport = EchoTransport(pp)\n\n\n    def execCommand(self, pp, command):\n        \"\"\"\n        If the command is 'true', store the command, the process protocol, and\n        the transport we connect to the process protocol.  Otherwise, just\n        store the command and raise an error.\n        \"\"\"\n        self.execCommandLine = command\n        if command == b'success':\n            self.execProtocol = pp\n        elif command[:6] == b'repeat':\n            self.execProtocol = pp\n            self.execTransport = EchoTransport(pp)\n            pp.outReceived(command[7:])\n        else:\n            raise RuntimeError('not getting a command')\n\n\n    def eofReceived(self):\n        \"\"\"\n        Note that EOF has been received.\n        \"\"\"\n        self.gotEOF = True\n\n\n    def closed(self):\n        \"\"\"\n        Note that close has been received.\n        \"\"\"\n        self.gotClosed = True\n\n\nif cryptography:\n    components.registerAdapter(StubSessionForStubAvatar, StubAvatar,\n        session.ISession)\n\n\n\nclass EchoTransport:\n    \"\"\"\n    A transport for a ProcessProtocol which echos data that is sent to it with\n    a Window newline (CR LF) appended to it.  If a null byte is in the data,\n    disconnect.  When we are asked to disconnect, disconnect the\n    C{ProcessProtocol} with a 0 exit code.\n\n    @ivar proto: the C{ProcessProtocol} connected to us.\n    @ivar data: a L{bytes} of data written to us.\n    \"\"\"\n\n\n    def __init__(self, processProtocol):\n        \"\"\"\n        Initialize our instance variables.\n\n        @param processProtocol: a C{ProcessProtocol} to connect to ourself.\n        \"\"\"\n        self.proto = processProtocol\n        self.closed = False\n        self.data = b''\n        processProtocol.makeConnection(self)\n\n\n    def write(self, data):\n        \"\"\"\n        We got some data.  Give it back to our C{ProcessProtocol} with\n        a newline attached.  Disconnect if there's a null byte.\n        \"\"\"\n        self.data += data\n        self.proto.outReceived(data)\n        self.proto.outReceived(b'\\r\\n')\n        if b'\\x00' in data: # mimic 'exit' for the shell test\n            self.loseConnection()\n\n\n    def loseConnection(self):\n        \"\"\"\n        If we're asked to disconnect (and we haven't already) shut down\n        the C{ProcessProtocol} with a 0 exit code.\n        \"\"\"\n        if self.closed:\n            return\n        self.closed = 1\n        self.proto.inConnectionLost()\n        self.proto.outConnectionLost()\n        self.proto.errConnectionLost()\n        self.proto.processEnded(failure.Failure(\n                error.ProcessTerminated(0, None, None)))\n\n\n\nclass MockProtocol(protocol.Protocol):\n    \"\"\"\n    A sample Protocol which stores the data passed to it.\n\n    @ivar packetData: a L{bytes} of data to be sent when the connection is\n        made.\n    @ivar data: a L{bytes} of the data passed to us.\n    @ivar open: True if the channel is open.\n    @ivar reason: if not None, the reason the protocol was closed.\n    \"\"\"\n    packetData = b''\n\n\n    def connectionMade(self):\n        \"\"\"\n        Set up the instance variables.  If we have any packetData, send it\n        along.\n        \"\"\"\n\n        self.data = b''\n        self.open = True\n        self.reason = None\n        if self.packetData:\n            self.dataReceived(self.packetData)\n\n\n    def dataReceived(self, data):\n        \"\"\"\n        Store the received data and write it back with a tilde appended.\n        The tilde is appended so that the tests can verify that we processed\n        the data.\n        \"\"\"\n        self.data += data\n        self.transport.write(data + b'~')\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Close the protocol and store the reason.\n        \"\"\"\n        self.open = False\n        self.reason = reason\n\n\n\nclass StubConnection(object):\n    \"\"\"\n    A stub for twisted.conch.ssh.connection.SSHConnection.  Record the data\n    that channels send, and when they try to close the connection.\n\n    @ivar data: a L{dict} mapping C{SSHChannel}s to a C{list} of L{bytes} of\n        data they sent.\n    @ivar extData: a L{dict} mapping L{SSHChannel}s to a C{list} of L{tuple} of\n        (L{int}, L{bytes}) of extended data they sent.\n    @ivar requests: a L{dict} mapping L{SSHChannel}s to a C{list} of L{tuple}\n        of (L{str}, L{bytes}) of channel requests they made.\n    @ivar eofs: a L{dict} mapping L{SSHChannel}s to C{true} if they have sent\n        an EOF.\n    @ivar closes: a L{dict} mapping L{SSHChannel}s to C{true} if they have sent\n        a close.\n    \"\"\"\n\n\n    def __init__(self, transport=None):\n        \"\"\"\n        Initialize our instance variables.\n        \"\"\"\n        self.data = {}\n        self.extData = {}\n        self.requests = {}\n        self.eofs = {}\n        self.closes = {}\n        self.transport = transport\n\n\n    def logPrefix(self):\n        \"\"\"\n        Return our logging prefix.\n        \"\"\"\n        return \"MockConnection\"\n\n\n    def sendData(self, channel, data):\n        \"\"\"\n        Record the sent data.\n        \"\"\"\n        self.data.setdefault(channel, []).append(data)\n\n\n    def sendExtendedData(self, channel, type, data):\n        \"\"\"\n        Record the sent extended data.\n        \"\"\"\n        self.extData.setdefault(channel, []).append((type, data))\n\n\n    def sendRequest(self, channel, request, data, wantReply=False):\n        \"\"\"\n        Record the sent channel request.\n        \"\"\"\n        self.requests.setdefault(channel, []).append((request, data,\n            wantReply))\n        if wantReply:\n            return defer.succeed(None)\n\n\n    def sendEOF(self, channel):\n        \"\"\"\n        Record the sent EOF.\n        \"\"\"\n        self.eofs[channel] = True\n\n\n    def sendClose(self, channel):\n        \"\"\"\n        Record the sent close.\n        \"\"\"\n        self.closes[channel] = True\n\n\n\nclass StubTransport:\n    \"\"\"\n    A stub transport which records the data written.\n\n    @ivar buf: the data sent to the transport.\n    @type buf: L{bytes}\n\n    @ivar close: flags indicating if the transport has been closed.\n    @type close: L{bool}\n    \"\"\"\n\n    buf = b''\n    close = False\n\n\n    def getPeer(self):\n        \"\"\"\n        Return an arbitrary L{IAddress}.\n        \"\"\"\n        return IPv4Address('TCP', 'remotehost', 8888)\n\n\n    def getHost(self):\n        \"\"\"\n        Return an arbitrary L{IAddress}.\n        \"\"\"\n        return IPv4Address('TCP', 'localhost', 9999)\n\n\n    def write(self, data):\n        \"\"\"\n        Record data in the buffer.\n        \"\"\"\n        self.buf += data\n\n\n    def loseConnection(self):\n        \"\"\"\n        Note that the connection was closed.\n        \"\"\"\n        self.close = True\n\n\n    def setTcpNoDelay(self, enabled):\n        \"\"\"\n        Pretend to set C{TCP_NODELAY}.\n        \"\"\"\n        # Required for testing SSHSessionForUnixConchUser.\n\n\nclass StubTransportWithWriteErr(StubTransport):\n    \"\"\"\n    A version of StubTransport which records the error data sent to it.\n\n    @ivar err: the extended data sent to the transport.\n    @type err: L{bytes}\n    \"\"\"\n\n    err = b''\n\n\n    def writeErr(self, data):\n        \"\"\"\n        Record the extended data in the buffer.  This was an old interface\n        that allowed the Transports from ISession.openShell() or\n        ISession.execCommand() to receive extended data from the client.\n        \"\"\"\n        self.err += data\n\n\n\nclass StubClient(object):\n    \"\"\"\n    A stub class representing the client to a SSHSession.\n\n    @ivar transport: A L{StubTransport} object which keeps track of the data\n        passed to it.\n    \"\"\"\n\n\n    def __init__(self):\n        self.transport = StubTransportWithWriteErr()\n\n\n\nclass SessionInterfaceTests(unittest.TestCase):\n    \"\"\"\n    Tests for the SSHSession class interface.  This interface is not ideal, but\n    it is tested in order to maintain backwards compatibility.\n    \"\"\"\n    if not cryptography:\n        skip = \"cannot run without cryptography\"\n\n\n    def setUp(self):\n        \"\"\"\n        Make an SSHSession object to test.  Give the channel some window\n        so that it's allowed to send packets.  500 and 100 are arbitrary\n        values.\n        \"\"\"\n        self.session = session.SSHSession(remoteWindow=500,\n                remoteMaxPacket=100, conn=StubConnection(),\n                avatar=StubAvatar())\n\n\n    def assertSessionIsStubSession(self):\n        \"\"\"\n        Asserts that self.session.session is an instance of\n        StubSessionForStubOldAvatar.\n        \"\"\"\n        self.assertIsInstance(self.session.session,\n                              StubSessionForStubAvatar)\n\n\n    def test_init(self):\n        \"\"\"\n        SSHSession initializes its buffer (buf), client, and ISession adapter.\n        The avatar should not need to be adaptable to an ISession immediately.\n        \"\"\"\n        s = session.SSHSession(avatar=object) # use object because it doesn't\n                                              # have an adapter\n        self.assertEqual(s.buf, b'')\n        self.assertIsNone(s.client)\n        self.assertIsNone(s.session)\n\n\n    def test_client_dataReceived(self):\n        \"\"\"\n        SSHSession.dataReceived() passes data along to a client.  If the data\n        comes before there is a client, the data should be discarded.\n        \"\"\"\n        self.session.dataReceived(b'1')\n        self.session.client = StubClient()\n        self.session.dataReceived(b'2')\n        self.assertEqual(self.session.client.transport.buf, b'2')\n\n    def test_client_extReceived(self):\n        \"\"\"\n        SSHSession.extReceived() passed data of type EXTENDED_DATA_STDERR along\n        to the client.  If the data comes before there is a client, or if the\n        data is not of type EXTENDED_DATA_STDERR, it is discared.\n        \"\"\"\n        self.session.extReceived(connection.EXTENDED_DATA_STDERR, b'1')\n        self.session.extReceived(255, b'2') # 255 is arbitrary\n        self.session.client = StubClient()\n        self.session.extReceived(connection.EXTENDED_DATA_STDERR, b'3')\n        self.assertEqual(self.session.client.transport.err, b'3')\n\n\n    def test_client_extReceivedWithoutWriteErr(self):\n        \"\"\"\n        SSHSession.extReceived() should handle the case where the transport\n        on the client doesn't have a writeErr method.\n        \"\"\"\n        client = self.session.client = StubClient()\n        client.transport = StubTransport() # doesn't have writeErr\n\n        # should not raise an error\n        self.session.extReceived(connection.EXTENDED_DATA_STDERR, b'ignored')\n\n\n\n    def test_client_closed(self):\n        \"\"\"\n        SSHSession.closed() should tell the transport connected to the client\n        that the connection was lost.\n        \"\"\"\n        self.session.client = StubClient()\n        self.session.closed()\n        self.assertTrue(self.session.client.transport.close)\n        self.session.client.transport.close = False\n\n\n    def test_badSubsystemDoesNotCreateClient(self):\n        \"\"\"\n        When a subsystem request fails, SSHSession.client should not be set.\n        \"\"\"\n        ret = self.session.requestReceived(\n            b'subsystem', common.NS(b'BadSubsystem'))\n        self.assertFalse(ret)\n        self.assertIsNone(self.session.client)\n\n\n    def test_lookupSubsystem(self):\n        \"\"\"\n        When a client requests a subsystem, the SSHSession object should get\n        the subsystem by calling avatar.lookupSubsystem, and attach it as\n        the client.\n        \"\"\"\n        ret = self.session.requestReceived(\n            b'subsystem', common.NS(b'TestSubsystem') + b'data')\n        self.assertTrue(ret)\n        self.assertIsInstance(self.session.client, protocol.ProcessProtocol)\n        self.assertIs(self.session.client.transport.proto,\n                      self.session.avatar.subsystem)\n\n\n\n    def test_lookupSubsystemDoesNotNeedISession(self):\n        \"\"\"\n        Previously, if one only wanted to implement a subsystem, an ISession\n        adapter wasn't needed because subsystems were looked up using the\n        lookupSubsystem method on the avatar.\n        \"\"\"\n        s = session.SSHSession(avatar=SubsystemOnlyAvatar(),\n                               conn=StubConnection())\n        ret = s.request_subsystem(\n            common.NS(b'subsystem') + b'data')\n        self.assertTrue(ret)\n        self.assertIsNotNone(s.client)\n        self.assertIsNone(s.conn.closes.get(s))\n        s.eofReceived()\n        self.assertTrue(s.conn.closes.get(s))\n        # these should not raise errors\n        s.loseConnection()\n        s.closed()\n\n\n    def test_lookupSubsystem_data(self):\n        \"\"\"\n        After having looked up a subsystem, data should be passed along to the\n        client.  Additionally, subsystems were passed the entire request packet\n        as data, instead of just the additional data.\n\n        We check for the additional tidle to verify that the data passed\n        through the client.\n        \"\"\"\n        #self.session.dataReceived('1')\n        # subsystems didn't get extended data\n        #self.session.extReceived(connection.EXTENDED_DATA_STDERR, '2')\n\n        self.session.requestReceived(b'subsystem',\n                                     common.NS(b'TestSubsystem') + b'data')\n\n        self.assertEqual(self.session.conn.data[self.session],\n                [b'\\x00\\x00\\x00\\x0dTestSubsystemdata~'])\n        self.session.dataReceived(b'more data')\n        self.assertEqual(self.session.conn.data[self.session][-1],\n                b'more data~')\n\n\n    def test_lookupSubsystem_closeReceived(self):\n        \"\"\"\n        SSHSession.closeReceived() should sent a close message to the remote\n        side.\n        \"\"\"\n        self.session.requestReceived(b'subsystem',\n                                     common.NS(b'TestSubsystem') + b'data')\n\n        self.session.closeReceived()\n        self.assertTrue(self.session.conn.closes[self.session])\n\n\n    def assertRequestRaisedRuntimeError(self):\n        \"\"\"\n        Assert that the request we just made raised a RuntimeError (and only a\n        RuntimeError).\n        \"\"\"\n        errors = self.flushLoggedErrors(RuntimeError)\n        self.assertEqual(len(errors), 1, \"Multiple RuntimeErrors raised: %s\" %\n                          '\\n'.join([repr(error) for error in errors]))\n        errors[0].trap(RuntimeError)\n\n\n    def test_requestShell(self):\n        \"\"\"\n        When a client requests a shell, the SSHSession object should get\n        the shell by getting an ISession adapter for the avatar, then\n        calling openShell() with a ProcessProtocol to attach.\n        \"\"\"\n        # gets a shell the first time\n        ret = self.session.requestReceived(b'shell', b'')\n        self.assertTrue(ret)\n        self.assertSessionIsStubSession()\n        self.assertIsInstance(self.session.client,\n                              session.SSHSessionProcessProtocol)\n        self.assertIs(self.session.session.shellProtocol, self.session.client)\n        # doesn't get a shell the second time\n        self.assertFalse(self.session.requestReceived(b'shell', b''))\n        self.assertRequestRaisedRuntimeError()\n\n\n    def test_requestShellWithData(self):\n        \"\"\"\n        When a client executes a shell, it should be able to give pass data\n        back and forth between the local and the remote side.\n        \"\"\"\n        ret = self.session.requestReceived(b'shell', b'')\n        self.assertTrue(ret)\n        self.assertSessionIsStubSession()\n        self.session.dataReceived(b'some data\\x00')\n        self.assertEqual(self.session.session.shellTransport.data,\n                          b'some data\\x00')\n        self.assertEqual(self.session.conn.data[self.session],\n                          [b'some data\\x00', b'\\r\\n'])\n        self.assertTrue(self.session.session.shellTransport.closed)\n        self.assertEqual(self.session.conn.requests[self.session],\n                          [(b'exit-status', b'\\x00\\x00\\x00\\x00', False)])\n\n\n    def test_requestExec(self):\n        \"\"\"\n        When a client requests a command, the SSHSession object should get\n        the command by getting an ISession adapter for the avatar, then\n        calling execCommand with a ProcessProtocol to attach and the\n        command line.\n        \"\"\"\n        ret = self.session.requestReceived(b'exec',\n                                           common.NS(b'failure'))\n        self.assertFalse(ret)\n        self.assertRequestRaisedRuntimeError()\n        self.assertIsNone(self.session.client)\n\n        self.assertTrue(self.session.requestReceived(b'exec',\n                                                     common.NS(b'success')))\n        self.assertSessionIsStubSession()\n        self.assertIsInstance(self.session.client,\n                              session.SSHSessionProcessProtocol)\n        self.assertIs(self.session.session.execProtocol, self.session.client)\n        self.assertEqual(self.session.session.execCommandLine,\n                b'success')\n\n\n    def test_requestExecWithData(self):\n        \"\"\"\n        When a client executes a command, it should be able to give pass data\n        back and forth.\n        \"\"\"\n        ret = self.session.requestReceived(b'exec',\n                                           common.NS(b'repeat hello'))\n        self.assertTrue(ret)\n        self.assertSessionIsStubSession()\n        self.session.dataReceived(b'some data')\n        self.assertEqual(self.session.session.execTransport.data, b'some data')\n        self.assertEqual(self.session.conn.data[self.session],\n                          [b'hello', b'some data', b'\\r\\n'])\n        self.session.eofReceived()\n        self.session.closeReceived()\n        self.session.closed()\n        self.assertTrue(self.session.session.execTransport.closed)\n        self.assertEqual(self.session.conn.requests[self.session],\n                          [(b'exit-status', b'\\x00\\x00\\x00\\x00', False)])\n\n\n    def test_requestPty(self):\n        \"\"\"\n        When a client requests a PTY, the SSHSession object should make\n        the request by getting an ISession adapter for the avatar, then\n        calling getPty with the terminal type, the window size, and any modes\n        the client gave us.\n        \"\"\"\n        # 'bad' terminal type fails\n        ret = self.session.requestReceived(\n            b'pty_req',  session.packRequest_pty_req(\n                b'bad', (1, 2, 3, 4), b''))\n        self.assertFalse(ret)\n        self.assertSessionIsStubSession()\n        self.assertRequestRaisedRuntimeError()\n        # 'good' terminal type succeeds\n        self.assertTrue(self.session.requestReceived(b'pty_req',\n            session.packRequest_pty_req(b'good', (1, 2, 3, 4), b'')))\n        self.assertEqual(self.session.session.ptyRequest,\n                (b'good', (1, 2, 3, 4), []))\n\n\n    def test_requestWindowChange(self):\n        \"\"\"\n        When the client requests to change the window size, the SSHSession\n        object should make the request by getting an ISession adapter for the\n        avatar, then calling windowChanged with the new window size.\n        \"\"\"\n        ret = self.session.requestReceived(\n            b'window_change',\n            session.packRequest_window_change((0, 0, 0, 0)))\n        self.assertFalse(ret)\n        self.assertRequestRaisedRuntimeError()\n        self.assertSessionIsStubSession()\n        self.assertTrue(self.session.requestReceived(b'window_change',\n            session.packRequest_window_change((1, 2, 3, 4))))\n        self.assertEqual(self.session.session.windowChange,\n                (1, 2, 3, 4))\n\n\n    def test_eofReceived(self):\n        \"\"\"\n        When an EOF is received and an ISession adapter is present, it should\n        be notified of the EOF message.\n        \"\"\"\n        self.session.session = session.ISession(self.session.avatar)\n        self.session.eofReceived()\n        self.assertTrue(self.session.session.gotEOF)\n\n\n    def test_closeReceived(self):\n        \"\"\"\n        When a close is received, the session should send a close message.\n        \"\"\"\n        ret = self.session.closeReceived()\n        self.assertIsNone(ret)\n        self.assertTrue(self.session.conn.closes[self.session])\n\n\n    def test_closed(self):\n        \"\"\"\n        When a close is received and an ISession adapter is present, it should\n        be notified of the close message.\n        \"\"\"\n        self.session.session = session.ISession(self.session.avatar)\n        self.session.closed()\n        self.assertTrue(self.session.session.gotClosed)\n\n\n\nclass SessionWithNoAvatarTests(unittest.TestCase):\n    \"\"\"\n    Test for the SSHSession interface.  Several of the methods (request_shell,\n    request_exec, request_pty_req, request_window_change) would create a\n    'session' instance variable from the avatar if one didn't exist when they\n    were called.\n    \"\"\"\n\n    if not cryptography:\n        skip = \"cannot run without cryptography\"\n\n    def setUp(self):\n        self.session = session.SSHSession()\n        self.session.avatar = StubAvatar()\n        self.assertIsNone(self.session.session)\n\n\n    def assertSessionProvidesISession(self):\n        \"\"\"\n        self.session.session should provide I{ISession}.\n        \"\"\"\n        self.assertTrue(session.ISession.providedBy(self.session.session),\n                        \"ISession not provided by %r\" % self.session.session)\n\n\n    def test_requestShellGetsSession(self):\n        \"\"\"\n        If an ISession adapter isn't already present, request_shell should get\n        one.\n        \"\"\"\n        self.session.requestReceived(b'shell', b'')\n        self.assertSessionProvidesISession()\n\n\n    def test_requestExecGetsSession(self):\n        \"\"\"\n        If an ISession adapter isn't already present, request_exec should get\n        one.\n        \"\"\"\n        self.session.requestReceived(b'exec',\n                                     common.NS(b'success'))\n        self.assertSessionProvidesISession()\n\n\n    def test_requestPtyReqGetsSession(self):\n        \"\"\"\n        If an ISession adapter isn't already present, request_pty_req should\n        get one.\n        \"\"\"\n        self.session.requestReceived(b'pty_req',\n                                     session.packRequest_pty_req(\n                b'term', (0, 0, 0, 0), b''))\n        self.assertSessionProvidesISession()\n\n\n    def test_requestWindowChangeGetsSession(self):\n        \"\"\"\n        If an ISession adapter isn't already present, request_window_change\n        should get one.\n        \"\"\"\n        self.session.requestReceived(\n            b'window_change',\n            session.packRequest_window_change(\n                (1, 1, 1, 1)))\n        self.assertSessionProvidesISession()\n\n\n\nclass WrappersTests(unittest.TestCase):\n    \"\"\"\n    A test for the wrapProtocol and wrapProcessProtocol functions.\n    \"\"\"\n    if not cryptography:\n        skip = \"cannot run without cryptography\"\n\n    def test_wrapProtocol(self):\n        \"\"\"\n        L{wrapProtocol}, when passed a L{Protocol} should return something that\n        has write(), writeSequence(), loseConnection() methods which call the\n        Protocol's dataReceived() and connectionLost() methods, respectively.\n        \"\"\"\n        protocol = MockProtocol()\n        protocol.transport = StubTransport()\n        protocol.connectionMade()\n        wrapped = session.wrapProtocol(protocol)\n        wrapped.dataReceived(b'dataReceived')\n        self.assertEqual(protocol.transport.buf, b'dataReceived')\n        wrapped.write(b'data')\n        wrapped.writeSequence([b'1', b'2'])\n        wrapped.loseConnection()\n        self.assertEqual(protocol.data, b'data12')\n        protocol.reason.trap(error.ConnectionDone)\n\n    def test_wrapProcessProtocol_Protocol(self):\n        \"\"\"\n        L{wrapPRocessProtocol}, when passed a L{Protocol} should return\n        something that follows the L{IProcessProtocol} interface, with\n        connectionMade() mapping to connectionMade(), outReceived() mapping to\n        dataReceived() and processEnded() mapping to connectionLost().\n        \"\"\"\n        protocol = MockProtocol()\n        protocol.transport = StubTransport()\n        process_protocol = session.wrapProcessProtocol(protocol)\n        process_protocol.connectionMade()\n        process_protocol.outReceived(b'data')\n        self.assertEqual(protocol.transport.buf, b'data~')\n        process_protocol.processEnded(failure.Failure(\n            error.ProcessTerminated(0, None, None)))\n        protocol.reason.trap(error.ProcessTerminated)\n\n\n\nclass HelpersTests(unittest.TestCase):\n    \"\"\"\n    Tests for the 4 helper functions: parseRequest_* and packRequest_*.\n    \"\"\"\n\n    if not cryptography:\n        skip = \"cannot run without cryptography\"\n\n    def test_parseRequest_pty_req(self):\n        \"\"\"\n        The payload of a pty-req message is::\n            string  terminal\n            uint32  columns\n            uint32  rows\n            uint32  x pixels\n            uint32  y pixels\n            string  modes\n\n        Modes are::\n            byte    mode number\n            uint32  mode value\n        \"\"\"\n        self.assertEqual(session.parseRequest_pty_req(common.NS(b'xterm') +\n                                                       struct.pack('>4L',\n                                                                   1, 2, 3, 4)\n                                                       + common.NS(\n                    struct.pack('>BL', 5, 6))),\n                          (b'xterm', (2, 1, 3, 4), [(5, 6)]))\n\n\n    def test_packRequest_pty_req_old(self):\n        \"\"\"\n        See test_parseRequest_pty_req for the payload format.\n        \"\"\"\n        packed = session.packRequest_pty_req(b'xterm', (2, 1, 3, 4),\n                                             b'\\x05\\x00\\x00\\x00\\x06')\n\n        self.assertEqual(packed,\n                          common.NS(b'xterm') +\n                          struct.pack('>4L', 1, 2, 3, 4) +\n                          common.NS(struct.pack('>BL', 5, 6)))\n\n\n    def test_packRequest_pty_req(self):\n        \"\"\"\n        See test_parseRequest_pty_req for the payload format.\n        \"\"\"\n        packed = session.packRequest_pty_req(b'xterm', (2, 1, 3, 4),\n                                             b'\\x05\\x00\\x00\\x00\\x06')\n        self.assertEqual(packed,\n                          common.NS(b'xterm') +\n                          struct.pack('>4L', 1, 2, 3, 4) +\n                          common.NS(struct.pack('>BL', 5, 6)))\n\n\n    def test_parseRequest_window_change(self):\n        \"\"\"\n        The payload of a window_change request is::\n            uint32  columns\n            uint32  rows\n            uint32  x pixels\n            uint32  y pixels\n\n        parseRequest_window_change() returns (rows, columns, x pixels,\n        y pixels).\n        \"\"\"\n        self.assertEqual(session.parseRequest_window_change(\n                struct.pack('>4L', 1, 2, 3, 4)), (2, 1, 3, 4))\n\n\n    def test_packRequest_window_change(self):\n        \"\"\"\n        See test_parseRequest_window_change for the payload format.\n        \"\"\"\n        self.assertEqual(session.packRequest_window_change((2, 1, 3, 4)),\n                          struct.pack('>4L', 1, 2, 3, 4))\n\n\n\nclass SSHSessionProcessProtocolTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{SSHSessionProcessProtocol}.\n    \"\"\"\n    if not cryptography:\n        skip = \"cannot run without cryptography\"\n\n    def setUp(self):\n        self.transport = StubTransport()\n        self.session = session.SSHSession(\n            conn=StubConnection(self.transport), remoteWindow=500,\n            remoteMaxPacket=100)\n        self.pp = session.SSHSessionProcessProtocol(self.session)\n        self.pp.makeConnection(self.transport)\n\n\n    def assertSessionClosed(self):\n        \"\"\"\n        Assert that C{self.session} is closed.\n        \"\"\"\n        self.assertTrue(self.session.conn.closes[self.session])\n\n\n    def assertRequestsEqual(self, expectedRequests):\n        \"\"\"\n        Assert that C{self.session} has sent the C{expectedRequests}.\n        \"\"\"\n        self.assertEqual(\n            self.session.conn.requests[self.session],\n            expectedRequests)\n\n\n    def test_init(self):\n        \"\"\"\n        SSHSessionProcessProtocol should set self.session to the session passed\n        to the __init__ method.\n        \"\"\"\n        self.assertEqual(self.pp.session, self.session)\n\n\n    def test_getHost(self):\n        \"\"\"\n        SSHSessionProcessProtocol.getHost() just delegates to its\n        session.conn.transport.getHost().\n        \"\"\"\n        self.assertEqual(\n            self.session.conn.transport.getHost(), self.pp.getHost())\n\n\n    def test_getPeer(self):\n        \"\"\"\n        SSHSessionProcessProtocol.getPeer() just delegates to its\n        session.conn.transport.getPeer().\n        \"\"\"\n        self.assertEqual(\n            self.session.conn.transport.getPeer(), self.pp.getPeer())\n\n\n    def test_connectionMade(self):\n        \"\"\"\n        SSHSessionProcessProtocol.connectionMade() should check if there's a\n        'buf' attribute on its session and write it to the transport if so.\n        \"\"\"\n        self.session.buf = b'buffer'\n        self.pp.connectionMade()\n        self.assertEqual(self.transport.buf, b'buffer')\n\n\n    def test_getSignalName(self):\n        \"\"\"\n        _getSignalName should return the name of a signal when given the\n        signal number.\n        \"\"\"\n        for signalName in session.SUPPORTED_SIGNALS:\n            signalName = 'SIG' + signalName\n            signalValue = getattr(signal, signalName)\n            sshName = self.pp._getSignalName(signalValue)\n            self.assertEqual(sshName, signalName,\n                              \"%i: %s != %s\" % (signalValue, sshName,\n                                                signalName))\n\n\n    def test_getSignalNameWithLocalSignal(self):\n        \"\"\"\n        If there are signals in the signal module which aren't in the SSH RFC,\n        we map their name to [signal name]@[platform].\n        \"\"\"\n        signal.SIGTwistedTest = signal.NSIG + 1 # value can't exist normally\n        # Force reinitialization of signals\n        self.pp._signalValuesToNames = None\n        self.assertEqual(self.pp._getSignalName(signal.SIGTwistedTest),\n                          'SIGTwistedTest@' + sys.platform)\n\n\n    if getattr(signal, 'SIGALRM', None) is None:\n        test_getSignalName.skip = test_getSignalNameWithLocalSignal.skip = \\\n            \"Not all signals available\"\n\n\n    def test_outReceived(self):\n        \"\"\"\n        When data is passed to the outReceived method, it should be sent to\n        the session's write method.\n        \"\"\"\n        self.pp.outReceived(b'test data')\n        self.assertEqual(self.session.conn.data[self.session],\n                [b'test data'])\n\n\n    def test_write(self):\n        \"\"\"\n        When data is passed to the write method, it should be sent to the\n        session channel's write method.\n        \"\"\"\n        self.pp.write(b'test data')\n        self.assertEqual(self.session.conn.data[self.session],\n                [b'test data'])\n\n    def test_writeSequence(self):\n        \"\"\"\n        When a sequence is passed to the writeSequence method, it should be\n        joined together and sent to the session channel's write method.\n        \"\"\"\n        self.pp.writeSequence([b'test ', b'data'])\n        self.assertEqual(self.session.conn.data[self.session],\n                [b'test data'])\n\n\n    def test_errReceived(self):\n        \"\"\"\n        When data is passed to the errReceived method, it should be sent to\n        the session's writeExtended method.\n        \"\"\"\n        self.pp.errReceived(b'test data')\n        self.assertEqual(self.session.conn.extData[self.session],\n                [(1, b'test data')])\n\n\n    def test_outConnectionLost(self):\n        \"\"\"\n        When outConnectionLost and errConnectionLost are both called, we should\n        send an EOF message.\n        \"\"\"\n        self.pp.outConnectionLost()\n        self.assertFalse(self.session in self.session.conn.eofs)\n        self.pp.errConnectionLost()\n        self.assertTrue(self.session.conn.eofs[self.session])\n\n\n    def test_errConnectionLost(self):\n        \"\"\"\n        Make sure reverse ordering of events in test_outConnectionLost also\n        sends EOF.\n        \"\"\"\n        self.pp.errConnectionLost()\n        self.assertFalse(self.session in self.session.conn.eofs)\n        self.pp.outConnectionLost()\n        self.assertTrue(self.session.conn.eofs[self.session])\n\n\n    def test_loseConnection(self):\n        \"\"\"\n        When loseConnection() is called, it should call loseConnection\n        on the session channel.\n        \"\"\"\n        self.pp.loseConnection()\n        self.assertTrue(self.session.conn.closes[self.session])\n\n\n    def test_connectionLost(self):\n        \"\"\"\n        When connectionLost() is called, it should call loseConnection()\n        on the session channel.\n        \"\"\"\n        self.pp.connectionLost(failure.Failure(\n                ProcessDone(0)))\n\n\n    def test_processEndedWithExitCode(self):\n        \"\"\"\n        When processEnded is called, if there is an exit code in the reason\n        it should be sent in an exit-status method.  The connection should be\n        closed.\n        \"\"\"\n        self.pp.processEnded(Failure(ProcessDone(None)))\n        self.assertRequestsEqual(\n            [(b'exit-status', struct.pack('>I', 0) , False)])\n        self.assertSessionClosed()\n\n\n    def test_processEndedWithExitSignalCoreDump(self):\n        \"\"\"\n        When processEnded is called, if there is an exit signal in the reason\n        it should be sent in an exit-signal message.  The connection should be\n        closed.\n        \"\"\"\n        self.pp.processEnded(\n            Failure(ProcessTerminated(1,\n                signal.SIGTERM, 1 << 7))) # 7th bit means core dumped\n        self.assertRequestsEqual(\n            [(b'exit-signal',\n              common.NS(b'TERM') # signal name\n              + b'\\x01' # core dumped is true\n              + common.NS(b'') # error message\n              + common.NS(b''), # language tag\n              False)])\n        self.assertSessionClosed()\n\n\n    def test_processEndedWithExitSignalNoCoreDump(self):\n        \"\"\"\n        When processEnded is called, if there is an exit signal in the\n        reason it should be sent in an exit-signal message.  If no\n        core was dumped, don't set the core-dump bit.\n        \"\"\"\n        self.pp.processEnded(\n            Failure(ProcessTerminated(1, signal.SIGTERM, 0)))\n        # see comments in test_processEndedWithExitSignalCoreDump for the\n        # meaning of the parts in the request\n        self.assertRequestsEqual(\n             [(b'exit-signal', common.NS(b'TERM') + b'\\x00' + common.NS(b'') +\n               common.NS(b''), False)])\n        self.assertSessionClosed()\n\n\n    if getattr(os, 'WCOREDUMP', None) is None:\n        skipMsg = \"can't run this w/o os.WCOREDUMP\"\n        test_processEndedWithExitSignalCoreDump.skip = skipMsg\n        test_processEndedWithExitSignalNoCoreDump.skip = skipMsg\n\n\n\nclass SSHSessionClientTests(unittest.TestCase):\n    \"\"\"\n    SSHSessionClient is an obsolete class used to connect standard IO to\n    an SSHSession.\n    \"\"\"\n    if not cryptography:\n        skip = \"cannot run without cryptography\"\n\n    def test_dataReceived(self):\n        \"\"\"\n        When data is received, it should be sent to the transport.\n        \"\"\"\n        client = session.SSHSessionClient()\n        client.transport = StubTransport()\n        client.dataReceived(b'test data')\n        self.assertEqual(client.transport.buf, b'test data')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_ssh.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.ssh}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport struct\n\nfrom twisted.python.reflect import requireModule\n\ncryptography = requireModule(\"cryptography\")\npyasn1 = requireModule(\"pyasn1\")\n\nif cryptography:\n    from twisted.conch.ssh import common, forwarding, session, _kex\n    from twisted.conch import avatar, error\nelse:\n    class avatar:\n        class  ConchUser: pass\n\nfrom twisted.conch.test.keydata import publicRSA_openssh, privateRSA_openssh\nfrom twisted.conch.test.keydata import publicDSA_openssh, privateDSA_openssh\nfrom twisted.cred import portal\nfrom twisted.cred.error import UnauthorizedLogin\nfrom twisted.internet import defer, protocol, reactor\nfrom twisted.internet.error import ProcessTerminated\nfrom twisted.python import failure, log\nfrom twisted.trial import unittest\n\nfrom twisted.conch.test.loopback import LoopbackRelay\n\n\n\nclass ConchTestRealm(object):\n    \"\"\"\n    A realm which expects a particular avatarId to log in once and creates a\n    L{ConchTestAvatar} for that request.\n\n    @ivar expectedAvatarID: The only avatarID that this realm will produce an\n        avatar for.\n\n    @ivar avatar: A reference to the avatar after it is requested.\n    \"\"\"\n    avatar = None\n\n    def __init__(self, expectedAvatarID):\n        self.expectedAvatarID = expectedAvatarID\n\n\n    def requestAvatar(self, avatarID, mind, *interfaces):\n        \"\"\"\n        Return a new L{ConchTestAvatar} if the avatarID matches the expected one\n        and this is the first avatar request.\n        \"\"\"\n        if avatarID == self.expectedAvatarID:\n            if self.avatar is not None:\n                raise UnauthorizedLogin(\"Only one login allowed\")\n            self.avatar = ConchTestAvatar()\n            return interfaces[0], self.avatar, self.avatar.logout\n        raise UnauthorizedLogin(\n            \"Only %r may log in, not %r\" % (self.expectedAvatarID, avatarID))\n\n\n\nclass ConchTestAvatar(avatar.ConchUser):\n    \"\"\"\n    An avatar against which various SSH features can be tested.\n\n    @ivar loggedOut: A flag indicating whether the avatar logout method has been\n        called.\n    \"\"\"\n    if not cryptography:\n        skip = \"cannot run without cryptography\"\n\n    loggedOut = False\n\n    def __init__(self):\n        avatar.ConchUser.__init__(self)\n        self.listeners = {}\n        self.globalRequests = {}\n        self.channelLookup.update(\n            {b'session': session.SSHSession,\n             b'direct-tcpip':forwarding.openConnectForwardingClient})\n        self.subsystemLookup.update({b'crazy': CrazySubsystem})\n\n\n    def global_foo(self, data):\n        self.globalRequests['foo'] = data\n        return 1\n\n\n    def global_foo_2(self, data):\n        self.globalRequests['foo_2'] = data\n        return 1, b'data'\n\n\n    def global_tcpip_forward(self, data):\n        host, port = forwarding.unpackGlobal_tcpip_forward(data)\n        try:\n            listener = reactor.listenTCP(\n                port, forwarding.SSHListenForwardingFactory(\n                    self.conn, (host, port),\n                    forwarding.SSHListenServerForwardingChannel),\n                interface=host)\n        except:\n            log.err(None, \"something went wrong with remote->local forwarding\")\n            return 0\n        else:\n            self.listeners[(host, port)] = listener\n            return 1\n\n\n    def global_cancel_tcpip_forward(self, data):\n        host, port = forwarding.unpackGlobal_tcpip_forward(data)\n        listener = self.listeners.get((host, port), None)\n        if not listener:\n            return 0\n        del self.listeners[(host, port)]\n        listener.stopListening()\n        return 1\n\n\n    def logout(self):\n        self.loggedOut = True\n        for listener in self.listeners.values():\n            log.msg('stopListening %s' % listener)\n            listener.stopListening()\n\n\n\nclass ConchSessionForTestAvatar(object):\n    \"\"\"\n    An ISession adapter for ConchTestAvatar.\n    \"\"\"\n    def __init__(self, avatar):\n        \"\"\"\n        Initialize the session and create a reference to it on the avatar for\n        later inspection.\n        \"\"\"\n        self.avatar = avatar\n        self.avatar._testSession = self\n        self.cmd = None\n        self.proto = None\n        self.ptyReq = False\n        self.eof = 0\n        self.onClose = defer.Deferred()\n\n\n    def getPty(self, term, windowSize, attrs):\n        log.msg('pty req')\n        self._terminalType = term\n        self._windowSize = windowSize\n        self.ptyReq = True\n\n\n    def openShell(self, proto):\n        log.msg('opening shell')\n        self.proto = proto\n        EchoTransport(proto)\n        self.cmd = b'shell'\n\n\n    def execCommand(self, proto, cmd):\n        self.cmd = cmd\n        self.proto = proto\n        f = cmd.split()[0]\n        if f == b'false':\n            t = FalseTransport(proto)\n            # Avoid disconnecting this immediately.  If the channel is closed\n            # before execCommand even returns the caller gets confused.\n            reactor.callLater(0, t.loseConnection)\n        elif f == b'echo':\n            t = EchoTransport(proto)\n            t.write(cmd[5:])\n            t.loseConnection()\n        elif f == b'secho':\n            t = SuperEchoTransport(proto)\n            t.write(cmd[6:])\n            t.loseConnection()\n        elif f == b'eecho':\n            t = ErrEchoTransport(proto)\n            t.write(cmd[6:])\n            t.loseConnection()\n        else:\n            raise error.ConchError('bad exec')\n        self.avatar.conn.transport.expectedLoseConnection = 1\n\n\n    def eofReceived(self):\n        self.eof = 1\n\n\n    def closed(self):\n        log.msg('closed cmd \"%s\"' % self.cmd)\n        self.remoteWindowLeftAtClose = self.proto.session.remoteWindowLeft\n        self.onClose.callback(None)\n\nfrom twisted.python import components\n\nif cryptography:\n    components.registerAdapter(ConchSessionForTestAvatar, ConchTestAvatar,\n                               session.ISession)\n\nclass CrazySubsystem(protocol.Protocol):\n\n    def __init__(self, *args, **kw):\n        pass\n\n    def connectionMade(self):\n        \"\"\"\n        good ... good\n        \"\"\"\n\n\n\nclass FalseTransport:\n    \"\"\"\n    False transport should act like a /bin/false execution, i.e. just exit with\n    nonzero status, writing nothing to the terminal.\n\n    @ivar proto: The protocol associated with this transport.\n    @ivar closed: A flag tracking whether C{loseConnection} has been called yet.\n    \"\"\"\n\n    def __init__(self, p):\n        \"\"\"\n        @type p L{twisted.conch.ssh.session.SSHSessionProcessProtocol} instance\n        \"\"\"\n        self.proto = p\n        p.makeConnection(self)\n        self.closed = 0\n\n\n    def loseConnection(self):\n        \"\"\"\n        Disconnect the protocol associated with this transport.\n        \"\"\"\n        if self.closed:\n            return\n        self.closed = 1\n        self.proto.inConnectionLost()\n        self.proto.outConnectionLost()\n        self.proto.errConnectionLost()\n        self.proto.processEnded(failure.Failure(ProcessTerminated(255, None, None)))\n\n\n\nclass EchoTransport:\n\n    def __init__(self, p):\n        self.proto = p\n        p.makeConnection(self)\n        self.closed = 0\n\n    def write(self, data):\n        log.msg(repr(data))\n        self.proto.outReceived(data)\n        self.proto.outReceived(b'\\r\\n')\n        if b'\\x00' in data: # mimic 'exit' for the shell test\n            self.loseConnection()\n\n    def loseConnection(self):\n        if self.closed: return\n        self.closed = 1\n        self.proto.inConnectionLost()\n        self.proto.outConnectionLost()\n        self.proto.errConnectionLost()\n        self.proto.processEnded(failure.Failure(ProcessTerminated(0, None, None)))\n\nclass ErrEchoTransport:\n\n    def __init__(self, p):\n        self.proto = p\n        p.makeConnection(self)\n        self.closed = 0\n\n    def write(self, data):\n        self.proto.errReceived(data)\n        self.proto.errReceived(b'\\r\\n')\n\n    def loseConnection(self):\n        if self.closed: return\n        self.closed = 1\n        self.proto.inConnectionLost()\n        self.proto.outConnectionLost()\n        self.proto.errConnectionLost()\n        self.proto.processEnded(failure.Failure(ProcessTerminated(0, None, None)))\n\nclass SuperEchoTransport:\n\n    def __init__(self, p):\n        self.proto = p\n        p.makeConnection(self)\n        self.closed = 0\n\n    def write(self, data):\n        self.proto.outReceived(data)\n        self.proto.outReceived(b'\\r\\n')\n        self.proto.errReceived(data)\n        self.proto.errReceived(b'\\r\\n')\n\n    def loseConnection(self):\n        if self.closed: return\n        self.closed = 1\n        self.proto.inConnectionLost()\n        self.proto.outConnectionLost()\n        self.proto.errConnectionLost()\n        self.proto.processEnded(failure.Failure(ProcessTerminated(0, None, None)))\n\n\nif cryptography is not None and pyasn1 is not None:\n    from twisted.conch import checkers\n    from twisted.conch.ssh import channel, connection, factory, keys\n    from twisted.conch.ssh import transport, userauth\n\n    class ConchTestPasswordChecker:\n        credentialInterfaces = checkers.IUsernamePassword,\n\n        def requestAvatarId(self, credentials):\n            if credentials.username == b'testuser' and credentials.password == b'testpass':\n                return defer.succeed(credentials.username)\n            return defer.fail(Exception(\"Bad credentials\"))\n\n\n    class ConchTestSSHChecker(checkers.SSHProtocolChecker):\n\n        def areDone(self, avatarId):\n            if avatarId != b'testuser' or len(self.successfulCredentials[avatarId]) < 2:\n                return False\n            return True\n\n    class ConchTestServerFactory(factory.SSHFactory):\n        noisy = 0\n\n        services = {\n            b'ssh-userauth':userauth.SSHUserAuthServer,\n            b'ssh-connection':connection.SSHConnection\n        }\n\n        def buildProtocol(self, addr):\n            proto = ConchTestServer()\n            proto.supportedPublicKeys = self.privateKeys.keys()\n            proto.factory = self\n\n            if hasattr(self, 'expectedLoseConnection'):\n                proto.expectedLoseConnection = self.expectedLoseConnection\n\n            self.proto = proto\n            return proto\n\n        def getPublicKeys(self):\n            return {\n                b'ssh-rsa': keys.Key.fromString(publicRSA_openssh),\n                b'ssh-dss': keys.Key.fromString(publicDSA_openssh)\n            }\n\n        def getPrivateKeys(self):\n            return {\n                b'ssh-rsa': keys.Key.fromString(privateRSA_openssh),\n                b'ssh-dss': keys.Key.fromString(privateDSA_openssh)\n            }\n\n        def getPrimes(self):\n            \"\"\"\n            Diffie-Hellman primes that can be used for the\n            diffie-hellman-group-exchange-sha1 key exchange.\n\n            @return: The primes and generators.\n            @rtype: L{dict} mapping the key size to a C{list} of\n                C{(generator, prime)} tupple.\n            \"\"\"\n            # In these tests, we hardwire the prime values to those defined by\n            # the diffie-hellman-group14-sha1 key exchange algorithm, to avoid\n            # requiring a moduli file when running tests.\n            # See OpenSSHFactory.getPrimes.\n            return {\n                2048: [\n                    _kex.getDHGeneratorAndPrime(\n                        b'diffie-hellman-group14-sha1')]\n            }\n\n        def getService(self, trans, name):\n            return factory.SSHFactory.getService(self, trans, name)\n\n    class ConchTestBase:\n\n        done = 0\n\n        def connectionLost(self, reason):\n            if self.done:\n                return\n            if not hasattr(self, 'expectedLoseConnection'):\n                raise unittest.FailTest(\n                    'unexpectedly lost connection %s\\n%s' % (self, reason))\n            self.done = 1\n\n        def receiveError(self, reasonCode, desc):\n            self.expectedLoseConnection = 1\n            # Some versions of OpenSSH (for example, OpenSSH_5.3p1) will\n            # send a DISCONNECT_BY_APPLICATION error before closing the\n            # connection.  Other, older versions (for example,\n            # OpenSSH_5.1p1), won't.  So accept this particular error here,\n            # but no others.\n            if reasonCode != transport.DISCONNECT_BY_APPLICATION:\n                log.err(\n                    Exception(\n                        'got disconnect for %s: reason %s, desc: %s' % (\n                            self, reasonCode, desc)))\n            self.loseConnection()\n\n        def receiveUnimplemented(self, seqID):\n            raise unittest.FailTest('got unimplemented: seqid %s' % (seqID,))\n            self.expectedLoseConnection = 1\n            self.loseConnection()\n\n    class ConchTestServer(ConchTestBase, transport.SSHServerTransport):\n\n        def connectionLost(self, reason):\n            ConchTestBase.connectionLost(self, reason)\n            transport.SSHServerTransport.connectionLost(self, reason)\n\n\n    class ConchTestClient(ConchTestBase, transport.SSHClientTransport):\n        \"\"\"\n        @ivar _channelFactory: A callable which accepts an SSH connection and\n            returns a channel which will be attached to a new channel on that\n            connection.\n        \"\"\"\n        def __init__(self, channelFactory):\n            self._channelFactory = channelFactory\n\n        def connectionLost(self, reason):\n            ConchTestBase.connectionLost(self, reason)\n            transport.SSHClientTransport.connectionLost(self, reason)\n\n        def verifyHostKey(self, key, fp):\n            keyMatch = key == keys.Key.fromString(publicRSA_openssh).blob()\n            fingerprintMatch = (\n                fp == b'85:25:04:32:58:55:96:9f:57:ee:fb:a8:1a:ea:69:da')\n            if keyMatch and fingerprintMatch:\n                return defer.succeed(1)\n            return defer.fail(Exception(\"Key or fingerprint mismatch\"))\n\n        def connectionSecure(self):\n            self.requestService(ConchTestClientAuth(b'testuser',\n                ConchTestClientConnection(self._channelFactory)))\n\n\n    class ConchTestClientAuth(userauth.SSHUserAuthClient):\n\n        hasTriedNone = 0 # have we tried the 'none' auth yet?\n        canSucceedPublicKey = 0 # can we succeed with this yet?\n        canSucceedPassword = 0\n\n        def ssh_USERAUTH_SUCCESS(self, packet):\n            if not self.canSucceedPassword and self.canSucceedPublicKey:\n                raise unittest.FailTest(\n                    'got USERAUTH_SUCCESS before password and publickey')\n            userauth.SSHUserAuthClient.ssh_USERAUTH_SUCCESS(self, packet)\n\n        def getPassword(self):\n            self.canSucceedPassword = 1\n            return defer.succeed(b'testpass')\n\n        def getPrivateKey(self):\n            self.canSucceedPublicKey = 1\n            return defer.succeed(keys.Key.fromString(privateDSA_openssh))\n\n        def getPublicKey(self):\n            return keys.Key.fromString(publicDSA_openssh)\n\n\n    class ConchTestClientConnection(connection.SSHConnection):\n        \"\"\"\n        @ivar _completed: A L{Deferred} which will be fired when the number of\n            results collected reaches C{totalResults}.\n        \"\"\"\n        name = b'ssh-connection'\n        results = 0\n        totalResults = 8\n\n        def __init__(self, channelFactory):\n            connection.SSHConnection.__init__(self)\n            self._channelFactory = channelFactory\n\n        def serviceStarted(self):\n            self.openChannel(self._channelFactory(conn=self))\n\n\n    class SSHTestChannel(channel.SSHChannel):\n\n        def __init__(self, name, opened, *args, **kwargs):\n            self.name = name\n            self._opened = opened\n            self.received = []\n            self.receivedExt = []\n            self.onClose = defer.Deferred()\n            channel.SSHChannel.__init__(self, *args, **kwargs)\n\n\n        def openFailed(self, reason):\n            self._opened.errback(reason)\n\n\n        def channelOpen(self, ignore):\n            self._opened.callback(self)\n\n\n        def dataReceived(self, data):\n            self.received.append(data)\n\n\n        def extReceived(self, dataType, data):\n            if dataType == connection.EXTENDED_DATA_STDERR:\n                self.receivedExt.append(data)\n            else:\n                log.msg(\"Unrecognized extended data: %r\" % (dataType,))\n\n\n        def request_exit_status(self, status):\n            [self.status] = struct.unpack('>L', status)\n\n\n        def eofReceived(self):\n            self.eofCalled = True\n\n\n        def closed(self):\n            self.onClose.callback(None)\n\n\n    def conchTestPublicKeyChecker():\n        \"\"\"\n        Produces a SSHPublicKeyChecker with an in-memory key mapping with\n        a single use: 'testuser'\n\n        @return: L{twisted.conch.checkers.SSHPublicKeyChecker}\n        \"\"\"\n        conchTestPublicKeyDB = checkers.InMemorySSHKeyDB(\n            {b'testuser': [keys.Key.fromString(publicDSA_openssh)]})\n        return checkers.SSHPublicKeyChecker(conchTestPublicKeyDB)\n\n\n\nclass SSHProtocolTests(unittest.TestCase):\n    \"\"\"\n    Tests for communication between L{SSHServerTransport} and\n    L{SSHClientTransport}.\n    \"\"\"\n\n    if not cryptography:\n        skip = \"can't run without cryptography\"\n\n    if not pyasn1:\n        skip = \"Cannot run without PyASN1\"\n\n    def _ourServerOurClientTest(self, name=b'session', **kwargs):\n        \"\"\"\n        Create a connected SSH client and server protocol pair and return a\n        L{Deferred} which fires with an L{SSHTestChannel} instance connected to\n        a channel on that SSH connection.\n        \"\"\"\n        result = defer.Deferred()\n        self.realm = ConchTestRealm(b'testuser')\n        p = portal.Portal(self.realm)\n        sshpc = ConchTestSSHChecker()\n        sshpc.registerChecker(ConchTestPasswordChecker())\n        sshpc.registerChecker(conchTestPublicKeyChecker())\n        p.registerChecker(sshpc)\n        fac = ConchTestServerFactory()\n        fac.portal = p\n        fac.startFactory()\n        self.server = fac.buildProtocol(None)\n        self.clientTransport = LoopbackRelay(self.server)\n        self.client = ConchTestClient(\n            lambda conn: SSHTestChannel(name, result, conn=conn, **kwargs))\n\n        self.serverTransport = LoopbackRelay(self.client)\n\n        self.server.makeConnection(self.serverTransport)\n        self.client.makeConnection(self.clientTransport)\n        return result\n\n\n    def test_subsystemsAndGlobalRequests(self):\n        \"\"\"\n        Run the Conch server against the Conch client.  Set up several different\n        channels which exercise different behaviors and wait for them to\n        complete.  Verify that the channels with errors log them.\n        \"\"\"\n        channel = self._ourServerOurClientTest()\n\n        def cbSubsystem(channel):\n            self.channel = channel\n            return self.assertFailure(\n                channel.conn.sendRequest(\n                    channel, b'subsystem', common.NS(b'not-crazy'), 1),\n                Exception)\n        channel.addCallback(cbSubsystem)\n\n        def cbNotCrazyFailed(ignored):\n            channel = self.channel\n            return channel.conn.sendRequest(\n                channel, b'subsystem', common.NS(b'crazy'), 1)\n        channel.addCallback(cbNotCrazyFailed)\n\n        def cbGlobalRequests(ignored):\n            channel = self.channel\n            d1 = channel.conn.sendGlobalRequest(b'foo', b'bar', 1)\n\n            d2 = channel.conn.sendGlobalRequest(b'foo-2', b'bar2', 1)\n            d2.addCallback(self.assertEqual, b'data')\n\n            d3 = self.assertFailure(\n                channel.conn.sendGlobalRequest(b'bar', b'foo', 1),\n                Exception)\n\n            return defer.gatherResults([d1, d2, d3])\n        channel.addCallback(cbGlobalRequests)\n\n        def disconnect(ignored):\n            self.assertEqual(\n                self.realm.avatar.globalRequests,\n                {\"foo\": b\"bar\", \"foo_2\": b\"bar2\"})\n            channel = self.channel\n            channel.conn.transport.expectedLoseConnection = True\n            channel.conn.serviceStopped()\n            channel.loseConnection()\n        channel.addCallback(disconnect)\n\n        return channel\n\n\n    def test_shell(self):\n        \"\"\"\n        L{SSHChannel.sendRequest} can open a shell with a I{pty-req} request,\n        specifying a terminal type and window size.\n        \"\"\"\n        channel = self._ourServerOurClientTest()\n\n        data = session.packRequest_pty_req(\n            b'conch-test-term', (24, 80, 0, 0), b'')\n        def cbChannel(channel):\n            self.channel = channel\n            return channel.conn.sendRequest(channel, b'pty-req', data, 1)\n        channel.addCallback(cbChannel)\n\n        def cbPty(ignored):\n            # The server-side object corresponding to our client side channel.\n            session = self.realm.avatar.conn.channels[0].session\n            self.assertIs(session.avatar, self.realm.avatar)\n            self.assertEqual(session._terminalType, b'conch-test-term')\n            self.assertEqual(session._windowSize, (24, 80, 0, 0))\n            self.assertTrue(session.ptyReq)\n            channel = self.channel\n            return channel.conn.sendRequest(channel, b'shell', b'', 1)\n        channel.addCallback(cbPty)\n\n        def cbShell(ignored):\n            self.channel.write(b'testing the shell!\\x00')\n            self.channel.conn.sendEOF(self.channel)\n            return defer.gatherResults([\n                    self.channel.onClose,\n                    self.realm.avatar._testSession.onClose])\n        channel.addCallback(cbShell)\n\n        def cbExited(ignored):\n            if self.channel.status != 0:\n                log.msg(\n                    'shell exit status was not 0: %i' % (self.channel.status,))\n            self.assertEqual(\n                b\"\".join(self.channel.received),\n                b'testing the shell!\\x00\\r\\n')\n            self.assertTrue(self.channel.eofCalled)\n            self.assertTrue(\n                self.realm.avatar._testSession.eof)\n        channel.addCallback(cbExited)\n        return channel\n\n\n    def test_failedExec(self):\n        \"\"\"\n        If L{SSHChannel.sendRequest} issues an exec which the server responds to\n        with an error, the L{Deferred} it returns fires its errback.\n        \"\"\"\n        channel = self._ourServerOurClientTest()\n\n        def cbChannel(channel):\n            self.channel = channel\n            return self.assertFailure(\n                channel.conn.sendRequest(\n                    channel, b'exec', common.NS(b'jumboliah'), 1),\n                Exception)\n        channel.addCallback(cbChannel)\n\n        def cbFailed(ignored):\n            # The server logs this exception when it cannot perform the\n            # requested exec.\n            errors = self.flushLoggedErrors(error.ConchError)\n            self.assertEqual(errors[0].value.args, ('bad exec', None))\n        channel.addCallback(cbFailed)\n        return channel\n\n\n    def test_falseChannel(self):\n        \"\"\"\n        When the process started by a L{SSHChannel.sendRequest} exec request\n        exits, the exit status is reported to the channel.\n        \"\"\"\n        channel = self._ourServerOurClientTest()\n\n        def cbChannel(channel):\n            self.channel = channel\n            return channel.conn.sendRequest(\n                channel, b'exec', common.NS(b'false'), 1)\n        channel.addCallback(cbChannel)\n\n        def cbExec(ignored):\n            return self.channel.onClose\n        channel.addCallback(cbExec)\n\n        def cbClosed(ignored):\n            # No data is expected\n            self.assertEqual(self.channel.received, [])\n            self.assertNotEqual(self.channel.status, 0)\n        channel.addCallback(cbClosed)\n        return channel\n\n\n    def test_errorChannel(self):\n        \"\"\"\n        Bytes sent over the extended channel for stderr data are delivered to\n        the channel's C{extReceived} method.\n        \"\"\"\n        channel = self._ourServerOurClientTest(localWindow=4, localMaxPacket=5)\n\n        def cbChannel(channel):\n            self.channel = channel\n            return channel.conn.sendRequest(\n                channel, b'exec', common.NS(b'eecho hello'), 1)\n        channel.addCallback(cbChannel)\n\n        def cbExec(ignored):\n            return defer.gatherResults([\n                    self.channel.onClose,\n                    self.realm.avatar._testSession.onClose])\n        channel.addCallback(cbExec)\n\n        def cbClosed(ignored):\n            self.assertEqual(self.channel.received, [])\n            self.assertEqual(b\"\".join(self.channel.receivedExt), b\"hello\\r\\n\")\n            self.assertEqual(self.channel.status, 0)\n            self.assertTrue(self.channel.eofCalled)\n            self.assertEqual(self.channel.localWindowLeft, 4)\n            self.assertEqual(\n                self.channel.localWindowLeft,\n                self.realm.avatar._testSession.remoteWindowLeftAtClose)\n        channel.addCallback(cbClosed)\n        return channel\n\n\n    def test_unknownChannel(self):\n        \"\"\"\n        When an attempt is made to open an unknown channel type, the L{Deferred}\n        returned by L{SSHChannel.sendRequest} fires its errback.\n        \"\"\"\n        d = self.assertFailure(\n            self._ourServerOurClientTest(b'crazy-unknown-channel'), Exception)\n        def cbFailed(ignored):\n            errors = self.flushLoggedErrors(error.ConchError)\n            self.assertEqual(errors[0].value.args, (3, 'unknown channel'))\n            self.assertEqual(len(errors), 1)\n        d.addCallback(cbFailed)\n        return d\n\n\n    def test_maxPacket(self):\n        \"\"\"\n        An L{SSHChannel} can be configured with a maximum packet size to\n        receive.\n        \"\"\"\n        # localWindow needs to be at least 11 otherwise the assertion about it\n        # in cbClosed is invalid.\n        channel = self._ourServerOurClientTest(\n            localWindow=11, localMaxPacket=1)\n\n        def cbChannel(channel):\n            self.channel = channel\n            return channel.conn.sendRequest(\n                channel, b'exec', common.NS(b'secho hello'), 1)\n        channel.addCallback(cbChannel)\n\n        def cbExec(ignored):\n            return self.channel.onClose\n        channel.addCallback(cbExec)\n\n        def cbClosed(ignored):\n            self.assertEqual(self.channel.status, 0)\n            self.assertEqual(b\"\".join(self.channel.received), b\"hello\\r\\n\")\n            self.assertEqual(b\"\".join(self.channel.receivedExt), b\"hello\\r\\n\")\n            self.assertEqual(self.channel.localWindowLeft, 11)\n            self.assertTrue(self.channel.eofCalled)\n        channel.addCallback(cbClosed)\n        return channel\n\n\n    def test_echo(self):\n        \"\"\"\n        Normal standard out bytes are sent to the channel's C{dataReceived}\n        method.\n        \"\"\"\n        channel = self._ourServerOurClientTest(localWindow=4, localMaxPacket=5)\n\n        def cbChannel(channel):\n            self.channel = channel\n            return channel.conn.sendRequest(\n                channel, b'exec', common.NS(b'echo hello'), 1)\n        channel.addCallback(cbChannel)\n\n        def cbEcho(ignored):\n            return defer.gatherResults([\n                    self.channel.onClose,\n                    self.realm.avatar._testSession.onClose])\n        channel.addCallback(cbEcho)\n\n        def cbClosed(ignored):\n            self.assertEqual(self.channel.status, 0)\n            self.assertEqual(b\"\".join(self.channel.received), b\"hello\\r\\n\")\n            self.assertEqual(self.channel.localWindowLeft, 4)\n            self.assertTrue(self.channel.eofCalled)\n            self.assertEqual(\n                self.channel.localWindowLeft,\n                self.realm.avatar._testSession.remoteWindowLeftAtClose)\n        channel.addCallback(cbClosed)\n        return channel\n\n\n\nclass SSHFactoryTests(unittest.TestCase):\n\n    if not cryptography:\n        skip = \"can't run without cryptography\"\n\n    if not pyasn1:\n        skip = \"Cannot run without PyASN1\"\n\n    def makeSSHFactory(self, primes=None):\n        sshFactory = factory.SSHFactory()\n        gpk = lambda: {'ssh-rsa' : keys.Key(None)}\n        sshFactory.getPrimes = lambda: primes\n        sshFactory.getPublicKeys = sshFactory.getPrivateKeys = gpk\n        sshFactory.startFactory()\n        return sshFactory\n\n\n    def test_buildProtocol(self):\n        \"\"\"\n        By default, buildProtocol() constructs an instance of\n        SSHServerTransport.\n        \"\"\"\n        factory = self.makeSSHFactory()\n        protocol = factory.buildProtocol(None)\n        self.assertIsInstance(protocol, transport.SSHServerTransport)\n\n\n    def test_buildProtocolRespectsProtocol(self):\n        \"\"\"\n        buildProtocol() calls 'self.protocol()' to construct a protocol\n        instance.\n        \"\"\"\n        calls = []\n        def makeProtocol(*args):\n            calls.append(args)\n            return transport.SSHServerTransport()\n        factory = self.makeSSHFactory()\n        factory.protocol = makeProtocol\n        factory.buildProtocol(None)\n        self.assertEqual([()], calls)\n\n\n    def test_buildProtocolNoPrimes(self):\n        \"\"\"\n        Group key exchanges are not supported when we don't have the primes\n        database.\n        \"\"\"\n        f1 = self.makeSSHFactory(primes=None)\n\n        p1 = f1.buildProtocol(None)\n\n        self.assertNotIn(\n            b'diffie-hellman-group-exchange-sha1', p1.supportedKeyExchanges)\n        self.assertNotIn(\n            b'diffie-hellman-group-exchange-sha256', p1.supportedKeyExchanges)\n\n\n    def test_buildProtocolWithPrimes(self):\n        \"\"\"\n        Group key exchanges are supported when we have the primes database.\n        \"\"\"\n        f2 = self.makeSSHFactory(primes={1:(2,3)})\n\n        p2 = f2.buildProtocol(None)\n\n        self.assertIn(\n            b'diffie-hellman-group-exchange-sha1', p2.supportedKeyExchanges)\n        self.assertIn(\n            b'diffie-hellman-group-exchange-sha256', p2.supportedKeyExchanges)\n\n\n\nclass MPTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{common.getMP}.\n\n    @cvar getMP: a method providing a MP parser.\n    @type getMP: C{callable}\n    \"\"\"\n    if not cryptography:\n        skip = \"can't run without cryptography\"\n\n    if not pyasn1:\n        skip = \"Cannot run without PyASN1\"\n\n    if cryptography:\n        getMP = staticmethod(common.getMP)\n\n    def test_getMP(self):\n        \"\"\"\n        L{common.getMP} should parse the a multiple precision integer from a\n        string: a 4-byte length followed by length bytes of the integer.\n        \"\"\"\n        self.assertEqual(\n            self.getMP(b'\\x00\\x00\\x00\\x04\\x00\\x00\\x00\\x01'),\n            (1, b''))\n\n\n    def test_getMPBigInteger(self):\n        \"\"\"\n        L{common.getMP} should be able to parse a big enough integer\n        (that doesn't fit on one byte).\n        \"\"\"\n        self.assertEqual(\n            self.getMP(b'\\x00\\x00\\x00\\x04\\x01\\x02\\x03\\x04'),\n            (16909060, b''))\n\n\n    def test_multipleGetMP(self):\n        \"\"\"\n        L{common.getMP} has the ability to parse multiple integer in the same\n        string.\n        \"\"\"\n        self.assertEqual(\n            self.getMP(b'\\x00\\x00\\x00\\x04\\x00\\x00\\x00\\x01'\n                       b'\\x00\\x00\\x00\\x04\\x00\\x00\\x00\\x02', 2),\n            (1, 2, b''))\n\n\n    def test_getMPRemainingData(self):\n        \"\"\"\n        When more data than needed is sent to L{common.getMP}, it should return\n        the remaining data.\n        \"\"\"\n        self.assertEqual(\n            self.getMP(b'\\x00\\x00\\x00\\x04\\x00\\x00\\x00\\x01foo'),\n            (1, b'foo'))\n\n\n    def test_notEnoughData(self):\n        \"\"\"\n        When the string passed to L{common.getMP} doesn't even make 5 bytes,\n        it should raise a L{struct.error}.\n        \"\"\"\n        self.assertRaises(struct.error, self.getMP, b'\\x02\\x00')\n\n\nclass GMPYInstallDeprecationTests(unittest.TestCase):\n    \"\"\"\n    Tests for the deprecation of former GMPY accidental public API.\n    \"\"\"\n\n    if not cryptography:\n        skip = \"cannot run without cryptography\"\n\n    def test_deprecated(self):\n        \"\"\"\n        L{twisted.conch.ssh.common.install} is deprecated.\n        \"\"\"\n        common.install()\n        warnings = self.flushWarnings([self.test_deprecated])\n        self.assertEqual(len(warnings), 1)\n        self.assertEqual(\n            warnings[0][\"message\"],\n            \"twisted.conch.ssh.common.install was deprecated in Twisted 16.5.0\"\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_tap.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.tap}.\n\"\"\"\n\ntry:\n    import cryptography\nexcept ImportError:\n    cryptography = None\n\ntry:\n    import pyasn1\nexcept ImportError:\n    pyasn1 = None\n\ntry:\n    from twisted.conch import unix\nexcept ImportError:\n    unix = None\n\nif cryptography and pyasn1 and unix:\n    from twisted.conch import tap\n    from twisted.conch.openssh_compat.factory import OpenSSHFactory\n\nfrom twisted.application.internet import StreamServerEndpointService\nfrom twisted.cred import error\nfrom twisted.cred.credentials import ISSHPrivateKey\nfrom twisted.cred.credentials import IUsernamePassword, UsernamePassword\n\nfrom twisted.trial.unittest import TestCase\n\n\n\nclass MakeServiceTests(TestCase):\n    \"\"\"\n    Tests for L{tap.makeService}.\n    \"\"\"\n\n    if not cryptography:\n        skip = \"can't run without cryptography\"\n\n    if not pyasn1:\n        skip = \"Cannot run without PyASN1\"\n\n    if not unix:\n        skip = \"can't run on non-posix computers\"\n\n    usernamePassword = (b'iamuser', b'thisispassword')\n\n    def setUp(self):\n        \"\"\"\n        Create a file with two users.\n        \"\"\"\n        self.filename = self.mktemp()\n        with open(self.filename, 'wb+') as f:\n            f.write(b':'.join(self.usernamePassword))\n        self.options = tap.Options()\n\n\n    def test_basic(self):\n        \"\"\"\n        L{tap.makeService} returns a L{StreamServerEndpointService} instance\n        running on TCP port 22, and the linked protocol factory is an instance\n        of L{OpenSSHFactory}.\n        \"\"\"\n        config = tap.Options()\n        service = tap.makeService(config)\n        self.assertIsInstance(service, StreamServerEndpointService)\n        self.assertEqual(service.endpoint._port, 22)\n        self.assertIsInstance(service.factory, OpenSSHFactory)\n\n\n    def test_defaultAuths(self):\n        \"\"\"\n        Make sure that if the C{--auth} command-line option is not passed,\n        the default checkers are (for backwards compatibility): SSH and UNIX\n        \"\"\"\n        numCheckers = 2\n\n        self.assertIn(ISSHPrivateKey, self.options['credInterfaces'],\n            \"SSH should be one of the default checkers\")\n        self.assertIn(IUsernamePassword, self.options['credInterfaces'],\n            \"UNIX should be one of the default checkers\")\n        self.assertEqual(numCheckers, len(self.options['credCheckers']),\n            \"There should be %d checkers by default\" % (numCheckers,))\n\n\n    def test_authAdded(self):\n        \"\"\"\n        The C{--auth} command-line option will add a checker to the list of\n        checkers, and it should be the only auth checker\n        \"\"\"\n        self.options.parseOptions(['--auth', 'file:' + self.filename])\n        self.assertEqual(len(self.options['credCheckers']), 1)\n\n\n    def test_multipleAuthAdded(self):\n        \"\"\"\n        Multiple C{--auth} command-line options will add all checkers specified\n        to the list ofcheckers, and there should only be the specified auth\n        checkers (no default checkers).\n        \"\"\"\n        self.options.parseOptions(['--auth', 'file:' + self.filename,\n                                   '--auth', 'memory:testuser:testpassword'])\n        self.assertEqual(len(self.options['credCheckers']), 2)\n\n\n    def test_authFailure(self):\n        \"\"\"\n        The checker created by the C{--auth} command-line option returns a\n        L{Deferred} that fails with L{UnauthorizedLogin} when\n        presented with credentials that are unknown to that checker.\n        \"\"\"\n        self.options.parseOptions(['--auth', 'file:' + self.filename])\n        checker = self.options['credCheckers'][-1]\n        invalid = UsernamePassword(self.usernamePassword[0], 'fake')\n        # Wrong password should raise error\n        return self.assertFailure(\n            checker.requestAvatarId(invalid), error.UnauthorizedLogin)\n\n\n    def test_authSuccess(self):\n        \"\"\"\n        The checker created by the C{--auth} command-line option returns a\n        L{Deferred} that returns the avatar id when presented with credentials\n        that are known to that checker.\n        \"\"\"\n        self.options.parseOptions(['--auth', 'file:' + self.filename])\n        checker = self.options['credCheckers'][-1]\n        correct = UsernamePassword(*self.usernamePassword)\n        d = checker.requestAvatarId(correct)\n\n        def checkSuccess(username):\n            self.assertEqual(username, correct.username)\n\n        return d.addCallback(checkSuccess)\n\n\n    def test_checkers(self):\n        \"\"\"\n        The L{OpenSSHFactory} built by L{tap.makeService} has a portal with\n        L{ISSHPrivateKey} and L{IUsernamePassword} interfaces registered as\n        checkers.\n        \"\"\"\n        config = tap.Options()\n        service = tap.makeService(config)\n        portal = service.factory.portal\n        self.assertEqual(\n            set(portal.checkers.keys()),\n            set([ISSHPrivateKey, IUsernamePassword]))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_telnet.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_telnet -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.conch.telnet}.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom zope.interface import implementer\nfrom zope.interface.verify import verifyObject\n\nfrom twisted.internet import defer\n\nfrom twisted.conch import telnet\n\nfrom twisted.trial import unittest\nfrom twisted.test import proto_helpers\nfrom twisted.python.compat import iterbytes\n\n\n@implementer(telnet.ITelnetProtocol)\nclass TestProtocol:\n    localEnableable = ()\n    remoteEnableable = ()\n\n    def __init__(self):\n        self.data = b''\n        self.subcmd = []\n        self.calls = []\n\n        self.enabledLocal = []\n        self.enabledRemote = []\n        self.disabledLocal = []\n        self.disabledRemote = []\n\n\n    def makeConnection(self, transport):\n        d = transport.negotiationMap = {}\n        d[b'\\x12'] = self.neg_TEST_COMMAND\n\n        d = transport.commandMap = transport.commandMap.copy()\n        for cmd in ('NOP', 'DM', 'BRK', 'IP', 'AO', 'AYT', 'EC', 'EL', 'GA'):\n            d[getattr(telnet, cmd)] = lambda arg, cmd=cmd: self.calls.append(cmd)\n\n\n    def dataReceived(self, data):\n        self.data += data\n\n\n    def connectionLost(self, reason):\n        pass\n\n\n    def neg_TEST_COMMAND(self, payload):\n        self.subcmd = payload\n\n\n    def enableLocal(self, option):\n        if option in self.localEnableable:\n            self.enabledLocal.append(option)\n            return True\n        return False\n\n\n    def disableLocal(self, option):\n        self.disabledLocal.append(option)\n\n\n    def enableRemote(self, option):\n        if option in self.remoteEnableable:\n            self.enabledRemote.append(option)\n            return True\n        return False\n\n\n    def disableRemote(self, option):\n        self.disabledRemote.append(option)\n\n\n\nclass InterfacesTests(unittest.TestCase):\n    def test_interface(self):\n        \"\"\"\n        L{telnet.TelnetProtocol} implements L{telnet.ITelnetProtocol}\n        \"\"\"\n        p = telnet.TelnetProtocol()\n        verifyObject(telnet.ITelnetProtocol, p)\n\n\n\nclass TelnetTransportTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{telnet.TelnetTransport}.\n    \"\"\"\n    def setUp(self):\n        self.p = telnet.TelnetTransport(TestProtocol)\n        self.t = proto_helpers.StringTransport()\n        self.p.makeConnection(self.t)\n\n\n    def testRegularBytes(self):\n        # Just send a bunch of bytes.  None of these do anything\n        # with telnet.  They should pass right through to the\n        # application layer.\n        h = self.p.protocol\n\n        L = [b\"here are some bytes la la la\",\n             b\"some more arrive here\",\n             b\"lots of bytes to play with\",\n             b\"la la la\",\n             b\"ta de da\",\n             b\"dum\"]\n        for b in L:\n            self.p.dataReceived(b)\n\n        self.assertEqual(h.data, b''.join(L))\n\n\n    def testNewlineHandling(self):\n        # Send various kinds of newlines and make sure they get translated\n        # into \\n.\n        h = self.p.protocol\n\n        L = [b\"here is the first line\\r\\n\",\n             b\"here is the second line\\r\\0\",\n             b\"here is the third line\\r\\n\",\n             b\"here is the last line\\r\\0\"]\n\n        for b in L:\n            self.p.dataReceived(b)\n\n        self.assertEqual(h.data, L[0][:-2] + b'\\n' +\n                          L[1][:-2] + b'\\r' +\n                          L[2][:-2] + b'\\n' +\n                          L[3][:-2] + b'\\r')\n\n\n    def testIACEscape(self):\n        # Send a bunch of bytes and a couple quoted \\xFFs.  Unquoted,\n        # \\xFF is a telnet command.  Quoted, one of them from each pair\n        # should be passed through to the application layer.\n        h = self.p.protocol\n\n        L = [b\"here are some bytes\\xff\\xff with an embedded IAC\",\n             b\"and here is a test of a border escape\\xff\",\n             b\"\\xff did you get that IAC?\"]\n\n        for b in L:\n            self.p.dataReceived(b)\n\n        self.assertEqual(h.data, b''.join(L).replace(b'\\xff\\xff', b'\\xff'))\n\n\n    def _simpleCommandTest(self, cmdName):\n        # Send a single simple telnet command and make sure\n        # it gets noticed and the appropriate method gets\n        # called.\n        h = self.p.protocol\n\n        cmd = telnet.IAC + getattr(telnet, cmdName)\n        L = [b\"Here's some bytes, tra la la\",\n             b\"But ono!\" + cmd + b\" an interrupt\"]\n\n        for b in L:\n            self.p.dataReceived(b)\n\n        self.assertEqual(h.calls, [cmdName])\n        self.assertEqual(h.data, b''.join(L).replace(cmd, b''))\n\n\n    def testInterrupt(self):\n        self._simpleCommandTest(\"IP\")\n\n\n    def testNoOperation(self):\n        self._simpleCommandTest(\"NOP\")\n\n\n    def testDataMark(self):\n        self._simpleCommandTest(\"DM\")\n\n\n    def testBreak(self):\n        self._simpleCommandTest(\"BRK\")\n\n\n    def testAbortOutput(self):\n        self._simpleCommandTest(\"AO\")\n\n\n    def testAreYouThere(self):\n        self._simpleCommandTest(\"AYT\")\n\n\n    def testEraseCharacter(self):\n        self._simpleCommandTest(\"EC\")\n\n\n    def testEraseLine(self):\n        self._simpleCommandTest(\"EL\")\n\n\n    def testGoAhead(self):\n        self._simpleCommandTest(\"GA\")\n\n\n    def testSubnegotiation(self):\n        # Send a subnegotiation command and make sure it gets\n        # parsed and that the correct method is called.\n        h = self.p.protocol\n\n        cmd = telnet.IAC + telnet.SB + b'\\x12hello world' + telnet.IAC + telnet.SE\n        L = [b\"These are some bytes but soon\" + cmd,\n             b\"there will be some more\"]\n\n        for b in L:\n            self.p.dataReceived(b)\n\n        self.assertEqual(h.data, b''.join(L).replace(cmd, b''))\n        self.assertEqual(h.subcmd, list(iterbytes(b\"hello world\")))\n\n\n    def testSubnegotiationWithEmbeddedSE(self):\n        # Send a subnegotiation command with an embedded SE.  Make sure\n        # that SE gets passed to the correct method.\n        h = self.p.protocol\n\n        cmd = (telnet.IAC + telnet.SB +\n               b'\\x12' + telnet.SE +\n               telnet.IAC + telnet.SE)\n\n        L = [b\"Some bytes are here\" + cmd + b\"and here\",\n             b\"and here\"]\n\n        for b in L:\n            self.p.dataReceived(b)\n\n        self.assertEqual(h.data, b''.join(L).replace(cmd, b''))\n        self.assertEqual(h.subcmd, [telnet.SE])\n\n\n    def testBoundarySubnegotiation(self):\n        # Send a subnegotiation command.  Split it at every possible byte boundary\n        # and make sure it always gets parsed and that it is passed to the correct\n        # method.\n        cmd = (telnet.IAC + telnet.SB +\n               b'\\x12' + telnet.SE + b'hello' +\n               telnet.IAC + telnet.SE)\n\n        for i in range(len(cmd)):\n            h = self.p.protocol = TestProtocol()\n            h.makeConnection(self.p)\n\n            a, b = cmd[:i], cmd[i:]\n            L = [b\"first part\" + a,\n                 b + b\"last part\"]\n\n            for data in L:\n                self.p.dataReceived(data)\n\n            self.assertEqual(h.data, b''.join(L).replace(cmd, b''))\n            self.assertEqual(h.subcmd, [telnet.SE] + list(iterbytes(b'hello')))\n\n\n    def _enabledHelper(self, o, eL=[], eR=[], dL=[], dR=[]):\n        self.assertEqual(o.enabledLocal, eL)\n        self.assertEqual(o.enabledRemote, eR)\n        self.assertEqual(o.disabledLocal, dL)\n        self.assertEqual(o.disabledRemote, dR)\n\n\n    def testRefuseWill(self):\n        # Try to enable an option.  The server should refuse to enable it.\n        cmd = telnet.IAC + telnet.WILL + b'\\x12'\n\n        data = b\"surrounding bytes\" + cmd + b\"to spice things up\"\n        self.p.dataReceived(data)\n\n        self.assertEqual(self.p.protocol.data, data.replace(cmd, b''))\n        self.assertEqual(self.t.value(), telnet.IAC + telnet.DONT + b'\\x12')\n        self._enabledHelper(self.p.protocol)\n\n\n    def testRefuseDo(self):\n        # Try to enable an option.  The server should refuse to enable it.\n        cmd = telnet.IAC + telnet.DO + b'\\x12'\n\n        data = b\"surrounding bytes\" + cmd + b\"to spice things up\"\n        self.p.dataReceived(data)\n\n        self.assertEqual(self.p.protocol.data, data.replace(cmd, b''))\n        self.assertEqual(self.t.value(), telnet.IAC + telnet.WONT + b'\\x12')\n        self._enabledHelper(self.p.protocol)\n\n\n    def testAcceptDo(self):\n        # Try to enable an option.  The option is in our allowEnable\n        # list, so we will allow it to be enabled.\n        cmd = telnet.IAC + telnet.DO + b'\\x19'\n        data = b'padding' + cmd + b'trailer'\n\n        h = self.p.protocol\n        h.localEnableable = (b'\\x19',)\n        self.p.dataReceived(data)\n\n        self.assertEqual(self.t.value(), telnet.IAC + telnet.WILL + b'\\x19')\n        self._enabledHelper(h, eL=[b'\\x19'])\n\n\n    def testAcceptWill(self):\n        # Same as testAcceptDo, but reversed.\n        cmd = telnet.IAC + telnet.WILL + b'\\x91'\n        data = b'header' + cmd + b'padding'\n\n        h = self.p.protocol\n        h.remoteEnableable = (b'\\x91',)\n        self.p.dataReceived(data)\n\n        self.assertEqual(self.t.value(), telnet.IAC + telnet.DO + b'\\x91')\n        self._enabledHelper(h, eR=[b'\\x91'])\n\n\n    def testAcceptWont(self):\n        # Try to disable an option.  The server must allow any option to\n        # be disabled at any time.  Make sure it disables it and sends\n        # back an acknowledgement of this.\n        cmd = telnet.IAC + telnet.WONT + b'\\x29'\n\n        # Jimmy it - after these two lines, the server will be in a state\n        # such that it believes the option to have been previously enabled\n        # via normal negotiation.\n        s = self.p.getOptionState(b'\\x29')\n        s.him.state = 'yes'\n\n        data = b\"fiddle dee\" + cmd\n        self.p.dataReceived(data)\n\n        self.assertEqual(self.p.protocol.data, data.replace(cmd, b''))\n        self.assertEqual(self.t.value(), telnet.IAC + telnet.DONT + b'\\x29')\n        self.assertEqual(s.him.state, 'no')\n        self._enabledHelper(self.p.protocol, dR=[b'\\x29'])\n\n\n    def testAcceptDont(self):\n        # Try to disable an option.  The server must allow any option to\n        # be disabled at any time.  Make sure it disables it and sends\n        # back an acknowledgement of this.\n        cmd = telnet.IAC + telnet.DONT + b'\\x29'\n\n        # Jimmy it - after these two lines, the server will be in a state\n        # such that it believes the option to have beenp previously enabled\n        # via normal negotiation.\n        s = self.p.getOptionState(b'\\x29')\n        s.us.state = 'yes'\n\n        data = b\"fiddle dum \" + cmd\n        self.p.dataReceived(data)\n\n        self.assertEqual(self.p.protocol.data, data.replace(cmd, b''))\n        self.assertEqual(self.t.value(), telnet.IAC + telnet.WONT + b'\\x29')\n        self.assertEqual(s.us.state, 'no')\n        self._enabledHelper(self.p.protocol, dL=[b'\\x29'])\n\n\n    def testIgnoreWont(self):\n        # Try to disable an option.  The option is already disabled.  The\n        # server should send nothing in response to this.\n        cmd = telnet.IAC + telnet.WONT + b'\\x47'\n\n        data = b\"dum de dum\" + cmd + b\"tra la la\"\n        self.p.dataReceived(data)\n\n        self.assertEqual(self.p.protocol.data, data.replace(cmd, b''))\n        self.assertEqual(self.t.value(), b'')\n        self._enabledHelper(self.p.protocol)\n\n\n    def testIgnoreDont(self):\n        # Try to disable an option.  The option is already disabled.  The\n        # server should send nothing in response to this.  Doing so could\n        # lead to a negotiation loop.\n        cmd = telnet.IAC + telnet.DONT + b'\\x47'\n\n        data = b\"dum de dum\" + cmd + b\"tra la la\"\n        self.p.dataReceived(data)\n\n        self.assertEqual(self.p.protocol.data, data.replace(cmd, b''))\n        self.assertEqual(self.t.value(), b'')\n        self._enabledHelper(self.p.protocol)\n\n\n    def testIgnoreWill(self):\n        # Try to enable an option.  The option is already enabled.  The\n        # server should send nothing in response to this.  Doing so could\n        # lead to a negotiation loop.\n        cmd = telnet.IAC + telnet.WILL + b'\\x56'\n\n        # Jimmy it - after these two lines, the server will be in a state\n        # such that it believes the option to have been previously enabled\n        # via normal negotiation.\n        s = self.p.getOptionState(b'\\x56')\n        s.him.state = 'yes'\n\n        data = b\"tra la la\" + cmd + b\"dum de dum\"\n        self.p.dataReceived(data)\n\n        self.assertEqual(self.p.protocol.data, data.replace(cmd, b''))\n        self.assertEqual(self.t.value(), b'')\n        self._enabledHelper(self.p.protocol)\n\n\n    def testIgnoreDo(self):\n        # Try to enable an option.  The option is already enabled.  The\n        # server should send nothing in response to this.  Doing so could\n        # lead to a negotiation loop.\n        cmd = telnet.IAC + telnet.DO + b'\\x56'\n\n        # Jimmy it - after these two lines, the server will be in a state\n        # such that it believes the option to have been previously enabled\n        # via normal negotiation.\n        s = self.p.getOptionState(b'\\x56')\n        s.us.state = 'yes'\n\n        data = b\"tra la la\" + cmd + b\"dum de dum\"\n        self.p.dataReceived(data)\n\n        self.assertEqual(self.p.protocol.data, data.replace(cmd, b''))\n        self.assertEqual(self.t.value(), b'')\n        self._enabledHelper(self.p.protocol)\n\n\n    def testAcceptedEnableRequest(self):\n        # Try to enable an option through the user-level API.  This\n        # returns a Deferred that fires when negotiation about the option\n        # finishes.  Make sure it fires, make sure state gets updated\n        # properly, make sure the result indicates the option was enabled.\n        d = self.p.do(b'\\x42')\n\n        h = self.p.protocol\n        h.remoteEnableable = (b'\\x42',)\n\n        self.assertEqual(self.t.value(), telnet.IAC + telnet.DO + b'\\x42')\n\n        self.p.dataReceived(telnet.IAC + telnet.WILL + b'\\x42')\n\n        d.addCallback(self.assertEqual, True)\n        d.addCallback(lambda _:  self._enabledHelper(h, eR=[b'\\x42']))\n        return d\n\n\n    def test_refusedEnableRequest(self):\n        \"\"\"\n        If the peer refuses to enable an option we request it to enable, the\n        L{Deferred} returned by L{TelnetProtocol.do} fires with an\n        L{OptionRefused} L{Failure}.\n        \"\"\"\n        # Try to enable an option through the user-level API.  This returns a\n        # Deferred that fires when negotiation about the option finishes.  Make\n        # sure it fires, make sure state gets updated properly, make sure the\n        # result indicates the option was enabled.\n        self.p.protocol.remoteEnableable = (b'\\x42',)\n        d = self.p.do(b'\\x42')\n\n        self.assertEqual(self.t.value(), telnet.IAC + telnet.DO + b'\\x42')\n\n        s = self.p.getOptionState(b'\\x42')\n        self.assertEqual(s.him.state, 'no')\n        self.assertEqual(s.us.state, 'no')\n        self.assertTrue(s.him.negotiating)\n        self.assertFalse(s.us.negotiating)\n\n        self.p.dataReceived(telnet.IAC + telnet.WONT + b'\\x42')\n\n        d = self.assertFailure(d, telnet.OptionRefused)\n        d.addCallback(lambda ignored: self._enabledHelper(self.p.protocol))\n        d.addCallback(\n            lambda ignored: self.assertFalse(s.him.negotiating))\n        return d\n\n\n    def test_refusedEnableOffer(self):\n        \"\"\"\n        If the peer refuses to allow us to enable an option, the L{Deferred}\n        returned by L{TelnetProtocol.will} fires with an L{OptionRefused}\n        L{Failure}.\n        \"\"\"\n        # Try to offer an option through the user-level API.  This returns a\n        # Deferred that fires when negotiation about the option finishes.  Make\n        # sure it fires, make sure state gets updated properly, make sure the\n        # result indicates the option was enabled.\n        self.p.protocol.localEnableable = (b'\\x42',)\n        d = self.p.will(b'\\x42')\n\n        self.assertEqual(self.t.value(), telnet.IAC + telnet.WILL + b'\\x42')\n\n        s = self.p.getOptionState(b'\\x42')\n        self.assertEqual(s.him.state, 'no')\n        self.assertEqual(s.us.state, 'no')\n        self.assertFalse(s.him.negotiating)\n        self.assertTrue(s.us.negotiating)\n\n        self.p.dataReceived(telnet.IAC + telnet.DONT + b'\\x42')\n\n        d = self.assertFailure(d, telnet.OptionRefused)\n        d.addCallback(lambda ignored: self._enabledHelper(self.p.protocol))\n        d.addCallback(\n            lambda ignored: self.assertFalse(s.us.negotiating))\n        return d\n\n\n    def testAcceptedDisableRequest(self):\n        # Try to disable an option through the user-level API.  This\n        # returns a Deferred that fires when negotiation about the option\n        # finishes.  Make sure it fires, make sure state gets updated\n        # properly, make sure the result indicates the option was enabled.\n        s = self.p.getOptionState(b'\\x42')\n        s.him.state = 'yes'\n\n        d = self.p.dont(b'\\x42')\n\n        self.assertEqual(self.t.value(), telnet.IAC + telnet.DONT + b'\\x42')\n\n        self.p.dataReceived(telnet.IAC + telnet.WONT + b'\\x42')\n\n        d.addCallback(self.assertEqual, True)\n        d.addCallback(lambda _: self._enabledHelper(self.p.protocol,\n                                                    dR=[b'\\x42']))\n        return d\n\n\n    def testNegotiationBlocksFurtherNegotiation(self):\n        # Try to disable an option, then immediately try to enable it, then\n        # immediately try to disable it.  Ensure that the 2nd and 3rd calls\n        # fail quickly with the right exception.\n        s = self.p.getOptionState(b'\\x24')\n        s.him.state = 'yes'\n        self.p.dont(b'\\x24') # fires after the first line of _final\n\n        def _do(x):\n            d = self.p.do(b'\\x24')\n            return self.assertFailure(d, telnet.AlreadyNegotiating)\n\n\n        def _dont(x):\n            d = self.p.dont(b'\\x24')\n            return self.assertFailure(d, telnet.AlreadyNegotiating)\n\n\n        def _final(x):\n            self.p.dataReceived(telnet.IAC + telnet.WONT + b'\\x24')\n            # an assertion that only passes if d2 has fired\n            self._enabledHelper(self.p.protocol, dR=[b'\\x24'])\n            # Make sure we allow this\n            self.p.protocol.remoteEnableable = (b'\\x24',)\n            d = self.p.do(b'\\x24')\n            self.p.dataReceived(telnet.IAC + telnet.WILL + b'\\x24')\n            d.addCallback(self.assertEqual, True)\n            d.addCallback(lambda _: self._enabledHelper(self.p.protocol,\n                                                        eR=[b'\\x24'],\n                                                        dR=[b'\\x24']))\n            return d\n\n        d = _do(None)\n        d.addCallback(_dont)\n        d.addCallback(_final)\n        return d\n\n\n    def testSuperfluousDisableRequestRaises(self):\n        # Try to disable a disabled option.  Make sure it fails properly.\n        d = self.p.dont(b'\\xab')\n        return self.assertFailure(d, telnet.AlreadyDisabled)\n\n\n    def testSuperfluousEnableRequestRaises(self):\n        # Try to disable a disabled option.  Make sure it fails properly.\n        s = self.p.getOptionState(b'\\xab')\n        s.him.state = 'yes'\n        d = self.p.do(b'\\xab')\n        return self.assertFailure(d, telnet.AlreadyEnabled)\n\n\n    def testLostConnectionFailsDeferreds(self):\n        d1 = self.p.do(b'\\x12')\n        d2 = self.p.do(b'\\x23')\n        d3 = self.p.do(b'\\x34')\n\n        class TestException(Exception):\n            pass\n\n        self.p.connectionLost(TestException(\"Total failure!\"))\n\n        d1 = self.assertFailure(d1, TestException)\n        d2 = self.assertFailure(d2, TestException)\n        d3 = self.assertFailure(d3, TestException)\n        return defer.gatherResults([d1, d2, d3])\n\n\nclass TestTelnet(telnet.Telnet):\n    \"\"\"\n    A trivial extension of the telnet protocol class useful to unit tests.\n    \"\"\"\n    def __init__(self):\n        telnet.Telnet.__init__(self)\n        self.events = []\n\n\n    def applicationDataReceived(self, data):\n        \"\"\"\n        Record the given data in C{self.events}.\n        \"\"\"\n        self.events.append(('bytes', data))\n\n\n    def unhandledCommand(self, command, data):\n        \"\"\"\n        Record the given command in C{self.events}.\n        \"\"\"\n        self.events.append(('command', command, data))\n\n\n    def unhandledSubnegotiation(self, command, data):\n        \"\"\"\n        Record the given subnegotiation command in C{self.events}.\n        \"\"\"\n        self.events.append(('negotiate', command, data))\n\n\n\nclass TelnetTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{telnet.Telnet}.\n\n    L{telnet.Telnet} implements the TELNET protocol (RFC 854), including option\n    and suboption negotiation, and option state tracking.\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Create an unconnected L{telnet.Telnet} to be used by tests.\n        \"\"\"\n        self.protocol = TestTelnet()\n\n\n    def test_enableLocal(self):\n        \"\"\"\n        L{telnet.Telnet.enableLocal} should reject all options, since\n        L{telnet.Telnet} does not know how to implement any options.\n        \"\"\"\n        self.assertFalse(self.protocol.enableLocal(b'\\0'))\n\n\n    def test_enableRemote(self):\n        \"\"\"\n        L{telnet.Telnet.enableRemote} should reject all options, since\n        L{telnet.Telnet} does not know how to implement any options.\n        \"\"\"\n        self.assertFalse(self.protocol.enableRemote(b'\\0'))\n\n\n    def test_disableLocal(self):\n        \"\"\"\n        It is an error for L{telnet.Telnet.disableLocal} to be called, since\n        L{telnet.Telnet.enableLocal} will never allow any options to be enabled\n        locally.  If a subclass overrides enableLocal, it must also override\n        disableLocal.\n        \"\"\"\n        self.assertRaises(NotImplementedError, self.protocol.disableLocal, b'\\0')\n\n\n    def test_disableRemote(self):\n        \"\"\"\n        It is an error for L{telnet.Telnet.disableRemote} to be called, since\n        L{telnet.Telnet.enableRemote} will never allow any options to be\n        enabled remotely.  If a subclass overrides enableRemote, it must also\n        override disableRemote.\n        \"\"\"\n        self.assertRaises(NotImplementedError, self.protocol.disableRemote, b'\\0')\n\n\n    def test_requestNegotiation(self):\n        \"\"\"\n        L{telnet.Telnet.requestNegotiation} formats the feature byte and the\n        payload bytes into the subnegotiation format and sends them.\n\n        See RFC 855.\n        \"\"\"\n        transport = proto_helpers.StringTransport()\n        self.protocol.makeConnection(transport)\n        self.protocol.requestNegotiation(b'\\x01', b'\\x02\\x03')\n        self.assertEqual(\n            transport.value(),\n            # IAC SB feature bytes IAC SE\n            b'\\xff\\xfa\\x01\\x02\\x03\\xff\\xf0')\n\n\n    def test_requestNegotiationEscapesIAC(self):\n        \"\"\"\n        If the payload for a subnegotiation includes I{IAC}, it is escaped by\n        L{telnet.Telnet.requestNegotiation} with another I{IAC}.\n\n        See RFC 855.\n        \"\"\"\n        transport = proto_helpers.StringTransport()\n        self.protocol.makeConnection(transport)\n        self.protocol.requestNegotiation(b'\\x01', b'\\xff')\n        self.assertEqual(\n            transport.value(),\n            b'\\xff\\xfa\\x01\\xff\\xff\\xff\\xf0')\n\n\n    def _deliver(self, data, *expected):\n        \"\"\"\n        Pass the given bytes to the protocol's C{dataReceived} method and\n        assert that the given events occur.\n        \"\"\"\n        received = self.protocol.events = []\n        self.protocol.dataReceived(data)\n        self.assertEqual(received, list(expected))\n\n\n    def test_oneApplicationDataByte(self):\n        \"\"\"\n        One application-data byte in the default state gets delivered right\n        away.\n        \"\"\"\n        self._deliver(b'a', ('bytes', b'a'))\n\n\n    def test_twoApplicationDataBytes(self):\n        \"\"\"\n        Two application-data bytes in the default state get delivered\n        together.\n        \"\"\"\n        self._deliver(b'bc', ('bytes', b'bc'))\n\n\n    def test_threeApplicationDataBytes(self):\n        \"\"\"\n        Three application-data bytes followed by a control byte get\n        delivered, but the control byte doesn't.\n        \"\"\"\n        self._deliver(b'def' + telnet.IAC, ('bytes', b'def'))\n\n\n    def test_escapedControl(self):\n        \"\"\"\n        IAC in the escaped state gets delivered and so does another\n        application-data byte following it.\n        \"\"\"\n        self._deliver(telnet.IAC)\n        self._deliver(telnet.IAC + b'g', ('bytes', telnet.IAC + b'g'))\n\n\n    def test_carriageReturn(self):\n        \"\"\"\n        A carriage return only puts the protocol into the newline state.  A\n        linefeed in the newline state causes just the newline to be\n        delivered.  A nul in the newline state causes a carriage return to\n        be delivered.  An IAC in the newline state causes a carriage return\n        to be delivered and puts the protocol into the escaped state.\n        Anything else causes a carriage return and that thing to be\n        delivered.\n        \"\"\"\n        self._deliver(b'\\r')\n        self._deliver(b'\\n', ('bytes', b'\\n'))\n        self._deliver(b'\\r\\n', ('bytes', b'\\n'))\n\n        self._deliver(b'\\r')\n        self._deliver(b'\\0', ('bytes', b'\\r'))\n        self._deliver(b'\\r\\0', ('bytes', b'\\r'))\n\n        self._deliver(b'\\r')\n        self._deliver(b'a', ('bytes', b'\\ra'))\n        self._deliver(b'\\ra', ('bytes', b'\\ra'))\n\n        self._deliver(b'\\r')\n        self._deliver(\n            telnet.IAC + telnet.IAC + b'x', ('bytes', b'\\r' + telnet.IAC + b'x'))\n\n\n    def test_applicationDataBeforeSimpleCommand(self):\n        \"\"\"\n        Application bytes received before a command are delivered before the\n        command is processed.\n        \"\"\"\n        self._deliver(\n            b'x' + telnet.IAC + telnet.NOP,\n            ('bytes', b'x'), ('command', telnet.NOP, None))\n\n\n    def test_applicationDataBeforeCommand(self):\n        \"\"\"\n        Application bytes received before a WILL/WONT/DO/DONT are delivered\n        before the command is processed.\n        \"\"\"\n        self.protocol.commandMap = {}\n        self._deliver(\n            b'y' + telnet.IAC + telnet.WILL + b'\\x00',\n            ('bytes', b'y'), ('command', telnet.WILL, b'\\x00'))\n\n\n    def test_applicationDataBeforeSubnegotiation(self):\n        \"\"\"\n        Application bytes received before a subnegotiation command are\n        delivered before the negotiation is processed.\n        \"\"\"\n        self._deliver(\n            b'z' + telnet.IAC + telnet.SB + b'Qx' + telnet.IAC + telnet.SE,\n            ('bytes', b'z'), ('negotiate', b'Q', [b'x']))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_text.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_text -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom twisted.trial import unittest\n\nfrom twisted.conch.insults import text\nfrom twisted.conch.insults.text import attributes as A\n\n\n\nclass FormattedTextTests(unittest.TestCase):\n    \"\"\"\n    Tests for assembling formatted text.\n    \"\"\"\n    def test_trivial(self):\n        \"\"\"\n        Using no formatting attributes produces no VT102 control sequences in\n        the flattened output.\n        \"\"\"\n        self.assertEqual(\n            text.assembleFormattedText(A.normal['Hello, world.']),\n            'Hello, world.')\n\n\n    def test_bold(self):\n        \"\"\"\n        The bold formatting attribute, L{A.bold}, emits the VT102 control\n        sequence to enable bold when flattened.\n        \"\"\"\n        self.assertEqual(\n            text.assembleFormattedText(A.bold['Hello, world.']),\n            '\\x1b[1mHello, world.')\n\n\n    def test_underline(self):\n        \"\"\"\n        The underline formatting attribute, L{A.underline}, emits the VT102\n        control sequence to enable underlining when flattened.\n        \"\"\"\n        self.assertEqual(\n            text.assembleFormattedText(A.underline['Hello, world.']),\n            '\\x1b[4mHello, world.')\n\n\n    def test_blink(self):\n        \"\"\"\n        The blink formatting attribute, L{A.blink}, emits the VT102 control\n        sequence to enable blinking when flattened.\n        \"\"\"\n        self.assertEqual(\n            text.assembleFormattedText(A.blink['Hello, world.']),\n            '\\x1b[5mHello, world.')\n\n\n    def test_reverseVideo(self):\n        \"\"\"\n        The reverse-video formatting attribute, L{A.reverseVideo}, emits the\n        VT102 control sequence to enable reversed video when flattened.\n        \"\"\"\n        self.assertEqual(\n            text.assembleFormattedText(A.reverseVideo['Hello, world.']),\n            '\\x1b[7mHello, world.')\n\n\n    def test_minus(self):\n        \"\"\"\n        Formatting attributes prefixed with a minus (C{-}) temporarily disable\n        the prefixed attribute, emitting no VT102 control sequence to enable\n        it in the flattened output.\n        \"\"\"\n        self.assertEqual(\n            text.assembleFormattedText(\n                A.bold[A.blink['Hello', -A.bold[' world'], '.']]),\n            '\\x1b[1;5mHello\\x1b[0;5m world\\x1b[1;5m.')\n\n\n    def test_foreground(self):\n        \"\"\"\n        The foreground color formatting attribute, L{A.fg}, emits the VT102\n        control sequence to set the selected foreground color when flattened.\n        \"\"\"\n        self.assertEqual(\n            text.assembleFormattedText(\n                A.normal[A.fg.red['Hello, '], A.fg.green['world!']]),\n            '\\x1b[31mHello, \\x1b[32mworld!')\n\n\n    def test_background(self):\n        \"\"\"\n        The background color formatting attribute, L{A.bg}, emits the VT102\n        control sequence to set the selected background color when flattened.\n        \"\"\"\n        self.assertEqual(\n            text.assembleFormattedText(\n                A.normal[A.bg.red['Hello, '], A.bg.green['world!']]),\n            '\\x1b[41mHello, \\x1b[42mworld!')\n\n\n    def test_flattenDeprecated(self):\n        \"\"\"\n        L{twisted.conch.insults.text.flatten} emits a deprecation warning when\n        imported or accessed.\n        \"\"\"\n        warningsShown = self.flushWarnings([self.test_flattenDeprecated])\n        self.assertEqual(len(warningsShown), 0)\n\n        # Trigger the deprecation warning.\n        text.flatten\n\n        warningsShown = self.flushWarnings([self.test_flattenDeprecated])\n        self.assertEqual(len(warningsShown), 1)\n        self.assertEqual(warningsShown[0]['category'], DeprecationWarning)\n        self.assertEqual(\n            warningsShown[0]['message'],\n            'twisted.conch.insults.text.flatten was deprecated in Twisted '\n            '13.1.0: Use twisted.conch.insults.text.assembleFormattedText '\n            'instead.')\n\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_transport.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for ssh/transport.py and the classes therein.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport binascii\nimport re\nimport string\nimport struct\nimport types\n\nfrom hashlib import md5, sha1, sha256, sha384, sha512\nfrom twisted import __version__ as twisted_version\nfrom twisted.trial import unittest\nfrom twisted.internet import defer\nfrom twisted.protocols import loopback\nfrom twisted.python import randbytes\nfrom twisted.python.randbytes import insecureRandom\nfrom twisted.python.compat import iterbytes, _bytesChr as chr\nfrom twisted.conch.ssh import address, service, _kex\nfrom twisted.conch.error import ConchError\nfrom twisted.test import proto_helpers\nfrom twisted.python.reflect import requireModule\n\npyasn1 = requireModule(\"pyasn1\")\ncryptography = requireModule(\"cryptography\")\n\nif pyasn1 is not None and cryptography is not None:\n    dependencySkip = None\n    from twisted.conch.ssh import common, transport, keys, factory\n    from twisted.conch.test import keydata\n    from cryptography.hazmat.backends import default_backend\n    from cryptography.hazmat.primitives.asymmetric import dh, ec\n    from cryptography.exceptions import UnsupportedAlgorithm\n    from cryptography.hazmat.primitives import serialization\nelse:\n    if pyasn1 is None:\n        dependencySkip = \"Cannot run without PyASN1\"\n    elif cryptography is None:\n        dependencySkip = \"can't run without cryptography\"\n\n\n    class transport: # fictional modules to make classes work\n        class SSHTransportBase: pass\n        class SSHServerTransport: pass\n        class SSHClientTransport: pass\n\n\n    class factory:\n        class SSHFactory:\n            pass\n\n    class common:\n        @classmethod\n        def NS(self, arg): return b''\n\n\n\ndef _MPpow(x, y, z):\n    \"\"\"\n    Return the MP version of C{(x ** y) % z}.\n    \"\"\"\n    return common.MP(pow(x, y, z))\n\n\n\nclass MockTransportBase(transport.SSHTransportBase):\n    \"\"\"\n    A base class for the client and server protocols.  Stores the messages\n    it receives instead of ignoring them.\n\n    @ivar errors: a list of tuples: (reasonCode, description)\n    @ivar unimplementeds: a list of integers: sequence number\n    @ivar debugs: a list of tuples: (alwaysDisplay, message, lang)\n    @ivar ignoreds: a list of strings: ignored data\n    \"\"\"\n\n    def connectionMade(self):\n        \"\"\"\n        Set up instance variables.\n        \"\"\"\n        transport.SSHTransportBase.connectionMade(self)\n        self.errors = []\n        self.unimplementeds = []\n        self.debugs = []\n        self.ignoreds = []\n        self.gotUnsupportedVersion = None\n\n\n    def _unsupportedVersionReceived(self, remoteVersion):\n        \"\"\"\n        Intercept unsupported version call.\n\n        @type remoteVersion: L{str}\n        \"\"\"\n        self.gotUnsupportedVersion = remoteVersion\n        return transport.SSHTransportBase._unsupportedVersionReceived(\n            self, remoteVersion)\n\n\n    def receiveError(self, reasonCode, description):\n        \"\"\"\n        Store any errors received.\n\n        @type reasonCode: L{int}\n        @type description: L{str}\n        \"\"\"\n        self.errors.append((reasonCode, description))\n\n\n    def receiveUnimplemented(self, seqnum):\n        \"\"\"\n        Store any unimplemented packet messages.\n\n        @type seqnum: L{int}\n        \"\"\"\n        self.unimplementeds.append(seqnum)\n\n\n    def receiveDebug(self, alwaysDisplay, message, lang):\n        \"\"\"\n        Store any debug messages.\n\n        @type alwaysDisplay: L{bool}\n        @type message: L{str}\n        @type lang: L{str}\n        \"\"\"\n        self.debugs.append((alwaysDisplay, message, lang))\n\n\n    def ssh_IGNORE(self, packet):\n        \"\"\"\n        Store any ignored data.\n\n        @type packet: L{str}\n        \"\"\"\n        self.ignoreds.append(packet)\n\n\n\nclass MockCipher(object):\n    \"\"\"\n    A mocked-up version of twisted.conch.ssh.transport.SSHCiphers.\n    \"\"\"\n    outCipType = b'test'\n    encBlockSize = 6\n    inCipType = b'test'\n    decBlockSize = 6\n    inMACType = b'test'\n    outMACType = b'test'\n    verifyDigestSize = 1\n    usedEncrypt = False\n    usedDecrypt = False\n    outMAC = (None, b'', b'', 1)\n    inMAC = (None, b'', b'', 1)\n    keys = ()\n\n\n    def encrypt(self, x):\n        \"\"\"\n        Called to encrypt the packet.  Simply record that encryption was used\n        and return the data unchanged.\n        \"\"\"\n        self.usedEncrypt = True\n        if (len(x) % self.encBlockSize) != 0:\n            raise RuntimeError(\"length %i modulo blocksize %i is not 0: %i\" %\n                    (len(x), self.encBlockSize, len(x) % self.encBlockSize))\n        return x\n\n\n    def decrypt(self, x):\n        \"\"\"\n        Called to decrypt the packet.  Simply record that decryption was used\n        and return the data unchanged.\n        \"\"\"\n        self.usedDecrypt = True\n        if (len(x) % self.encBlockSize) != 0:\n            raise RuntimeError(\"length %i modulo blocksize %i is not 0: %i\" %\n                    (len(x), self.decBlockSize, len(x) % self.decBlockSize))\n        return x\n\n\n    def makeMAC(self, outgoingPacketSequence, payload):\n        \"\"\"\n        Make a Message Authentication Code by sending the character value of\n        the outgoing packet.\n        \"\"\"\n        return chr(outgoingPacketSequence)\n\n\n    def verify(self, incomingPacketSequence, packet, macData):\n        \"\"\"\n        Verify the Message Authentication Code by checking that the packet\n        sequence number is the same.\n        \"\"\"\n        return chr(incomingPacketSequence) == macData\n\n\n    def setKeys(self, ivOut, keyOut, ivIn, keyIn, macIn, macOut):\n        \"\"\"\n        Record the keys.\n        \"\"\"\n        self.keys = (ivOut, keyOut, ivIn, keyIn, macIn, macOut)\n\n\n\nclass MockCompression:\n    \"\"\"\n    A mocked-up compression, based on the zlib interface.  Instead of\n    compressing, it reverses the data and adds a 0x66 byte to the end.\n    \"\"\"\n\n    def compress(self, payload):\n        return payload[::-1] # reversed\n\n\n    def decompress(self, payload):\n        return payload[:-1][::-1]\n\n\n    def flush(self, kind):\n        return b'\\x66'\n\n\n\nclass MockService(service.SSHService):\n    \"\"\"\n    A mocked-up service, based on twisted.conch.ssh.service.SSHService.\n\n    @ivar started: True if this service has been started.\n    @ivar stopped: True if this service has been stopped.\n    \"\"\"\n    name = b\"MockService\"\n    started = False\n    stopped = False\n    protocolMessages = {0xff: \"MSG_TEST\", 71: \"MSG_fiction\"}\n\n\n    def logPrefix(self):\n        return \"MockService\"\n\n\n    def serviceStarted(self):\n        \"\"\"\n        Record that the service was started.\n        \"\"\"\n        self.started = True\n\n\n    def serviceStopped(self):\n        \"\"\"\n        Record that the service was stopped.\n        \"\"\"\n        self.stopped = True\n\n\n    def ssh_TEST(self, packet):\n        \"\"\"\n        A message that this service responds to.\n        \"\"\"\n        self.transport.sendPacket(0xff, packet)\n\n\n\nclass MockFactory(factory.SSHFactory):\n    \"\"\"\n    A mocked-up factory based on twisted.conch.ssh.factory.SSHFactory.\n    \"\"\"\n    services = {\n        b'ssh-userauth': MockService}\n\n\n    def getPublicKeys(self):\n        \"\"\"\n        Return the public keys that authenticate this server.\n        \"\"\"\n        return {\n            b'ssh-rsa': keys.Key.fromString(keydata.publicRSA_openssh),\n            b'ssh-dsa': keys.Key.fromString(keydata.publicDSA_openssh)}\n\n\n    def getPrivateKeys(self):\n        \"\"\"\n        Return the private keys that authenticate this server.\n        \"\"\"\n        return {\n            b'ssh-rsa': keys.Key.fromString(keydata.privateRSA_openssh),\n            b'ssh-dsa': keys.Key.fromString(keydata.privateDSA_openssh)}\n\n\n    def getPrimes(self):\n        \"\"\"\n        Diffie-Hellman primes that can be used for key exchange algorithms\n        that use group exchange to establish a prime / generator group.\n\n        @return: The primes and generators.\n        @rtype: L{dict} mapping the key size to a C{list} of\n            C{(generator, prime)} tuple.\n        \"\"\"\n        # In these tests, we hardwire the prime values to those\n        # defined by the diffie-hellman-group14-sha1 key exchange\n        # algorithm, to avoid requiring a moduli file when running\n        # tests.\n        # See OpenSSHFactory.getPrimes.\n        group14 = _kex.getDHGeneratorAndPrime(b'diffie-hellman-group14-sha1')\n        return {\n            2048: (group14,),\n            4096: ((5, 7),)}\n\n\n\nclass MockOldFactoryPublicKeys(MockFactory):\n    \"\"\"\n    The old SSHFactory returned mappings from key names to strings from\n    getPublicKeys().  We return those here for testing.\n    \"\"\"\n\n    def getPublicKeys(self):\n        \"\"\"\n        We used to map key types to public key blobs as strings.\n        \"\"\"\n        keys = MockFactory.getPublicKeys(self)\n        for name, key in keys.items()[:]:\n            keys[name] = key.blob()\n        return keys\n\n\n\nclass MockOldFactoryPrivateKeys(MockFactory):\n    \"\"\"\n    The old SSHFactory returned mappings from key names to cryptography key\n    objects from getPrivateKeys().  We return those here for testing.\n    \"\"\"\n\n    def getPrivateKeys(self):\n        \"\"\"\n        We used to map key types to cryptography key objects.\n        \"\"\"\n        keys = MockFactory.getPrivateKeys(self)\n        for name, key in keys.items()[:]:\n            keys[name] = key.keyObject\n        return keys\n\n\n\ndef generatePredictableKey(transport):\n    p = transport.p\n    g = transport.g\n    bits = p.bit_length()\n    x = sum(0x9 << x for x\n            in range(0, bits-3, 4))\n    # The cryptography module doesn't let us create a secret key directly from\n    # an \"x\" value; we need to compute the public value ourselves.\n    y = pow(g, x, p)\n    try:\n        transport.dhSecretKey = dh.DHPrivateNumbers(\n            x,\n            dh.DHPublicNumbers(\n                y,\n                dh.DHParameterNumbers(p, g)\n            )\n        ).private_key(default_backend())\n    except ValueError:\n        print(\"\\np=%s\\ng=%s\\nx=%s\\n\" % (p, g, x))\n        raise\n    transport.dhSecretKeyPublicMP = common.MP(\n        transport.dhSecretKey\n        .public_key()\n        .public_numbers()\n        .y\n    )\n\n\n\nclass TransportTestCase(unittest.TestCase):\n    \"\"\"\n    Base class for transport test cases.\n    \"\"\"\n    klass = None\n\n    if dependencySkip:\n        skip = dependencySkip\n\n\n    def setUp(self):\n        self.transport = proto_helpers.StringTransport()\n        self.proto = self.klass()\n        self.packets = []\n        def secureRandom(len):\n            \"\"\"\n            Return a consistent entropy value\n            \"\"\"\n            return b'\\x99' * len\n        self.patch(randbytes, 'secureRandom', secureRandom)\n        self.proto._startEphemeralDH = types.MethodType(\n            generatePredictableKey, self.proto)\n\n        def stubSendPacket(messageType, payload):\n            self.packets.append((messageType, payload))\n\n        self.proto.makeConnection(self.transport)\n        # we just let the kex packet go into the transport\n        self.proto.sendPacket = stubSendPacket\n\n\n    def finishKeyExchange(self, proto):\n        \"\"\"\n        Deliver enough additional messages to C{proto} so that the key exchange\n        which is started in L{SSHTransportBase.connectionMade} completes and\n        non-key exchange messages can be sent and received.\n        \"\"\"\n        proto.dataReceived(b\"SSH-2.0-BogoClient-1.2i\\r\\n\")\n        proto.dispatchMessage(\n            transport.MSG_KEXINIT, self._A_KEXINIT_MESSAGE)\n        proto._keySetup(b\"foo\", b\"bar\")\n        # SSHTransportBase can't handle MSG_NEWKEYS, or it would be the right\n        # thing to deliver next.  _newKeys won't work either, because\n        # sendKexInit (probably) hasn't been called.  sendKexInit is\n        # responsible for setting up certain state _newKeys relies on.  So,\n        # just change the key exchange state to what it would be when key\n        # exchange is finished.\n        proto._keyExchangeState = proto._KEY_EXCHANGE_NONE\n\n\n    def simulateKeyExchange(self, sharedSecret, exchangeHash):\n        \"\"\"\n        Finish a key exchange by calling C{_keySetup} with the given arguments.\n        Also do extra whitebox stuff to satisfy that method's assumption that\n        some kind of key exchange has actually taken place.\n        \"\"\"\n        self.proto._keyExchangeState = self.proto._KEY_EXCHANGE_REQUESTED\n        self.proto._blockedByKeyExchange = []\n        self.proto._keySetup(sharedSecret, exchangeHash)\n\n\n\nclass DHGroupExchangeSHA1Mixin:\n    \"\"\"\n    Mixin for diffie-hellman-group-exchange-sha1 tests.\n    \"\"\"\n\n    kexAlgorithm = b'diffie-hellman-group-exchange-sha1'\n    hashProcessor = sha1\n\n\n\nclass DHGroupExchangeSHA256Mixin:\n    \"\"\"\n    Mixin for diffie-hellman-group-exchange-sha256 tests.\n    \"\"\"\n\n    kexAlgorithm = b'diffie-hellman-group-exchange-sha256'\n    hashProcessor = sha256\n\n\n\nclass ECDHMixin:\n    \"\"\"\n    Mixin for elliptic curve diffie-hellman tests.\n    \"\"\"\n\n    kexAlgorithm = b'ecdh-sha2-nistp256'\n    hashProcessor = sha256\n\n\n\nclass BaseSSHTransportBaseCase:\n    \"\"\"\n    Base case for TransportBase tests.\n    \"\"\"\n\n    klass = MockTransportBase\n\n\n\nclass BaseSSHTransportTests(BaseSSHTransportBaseCase, TransportTestCase):\n    \"\"\"\n    Test TransportBase. It implements the non-server/client specific\n    parts of the SSH transport protocol.\n    \"\"\"\n    if dependencySkip:\n        skip = dependencySkip\n\n    _A_KEXINIT_MESSAGE = (\n        b\"\\xAA\" * 16 +\n        common.NS(b'diffie-hellman-group14-sha1') +\n        common.NS(b'ssh-rsa') +\n        common.NS(b'aes256-ctr') +\n        common.NS(b'aes256-ctr') +\n        common.NS(b'hmac-sha1') +\n        common.NS(b'hmac-sha1') +\n        common.NS(b'none') +\n        common.NS(b'none') +\n        common.NS(b'') +\n        common.NS(b'') +\n        b'\\x00' + b'\\x00\\x00\\x00\\x00')\n\n    def test_sendVersion(self):\n        \"\"\"\n        Test that the first thing sent over the connection is the version\n        string.  The 'softwareversion' part must consist of printable\n        US-ASCII characters, with the exception of whitespace characters and\n        the minus sign.\n\n        RFC 4253, section 4.2.\n        \"\"\"\n        # the other setup was done in the setup method\n        version = self.transport.value().split(b'\\r\\n', 1)[0]\n        self.assertEqual(version,\n                         b\"SSH-2.0-Twisted_\" + twisted_version.encode('ascii'))\n        softwareVersion = version.decode('ascii')[len('SSH-2.0-'):]\n        # This is an inefficient regex, but it's simple to build.\n        softwareVersionRegex = (\n            r'^(' +\n            '|'.join(\n                re.escape(c) for c in string.printable\n                if c != '-' and not c.isspace()) +\n            r')*$')\n        self.assertRegex(softwareVersion, softwareVersionRegex)\n\n\n    def test_sendPacketPlain(self):\n        \"\"\"\n        Test that plain (unencrypted, uncompressed) packets are sent\n        correctly.  The format is::\n            uint32 length (including type and padding length)\n            byte padding length\n            byte type\n            bytes[length-padding length-2] data\n            bytes[padding length] padding\n        \"\"\"\n        proto = MockTransportBase()\n        proto.makeConnection(self.transport)\n        self.finishKeyExchange(proto)\n        self.transport.clear()\n        message = ord('A')\n        payload = b'BCDEFG'\n        proto.sendPacket(message, payload)\n        value = self.transport.value()\n        self.assertEqual(value, b'\\x00\\x00\\x00\\x0c\\x04ABCDEFG\\x99\\x99\\x99\\x99')\n\n\n    def test_sendPacketEncrypted(self):\n        \"\"\"\n        Test that packets sent while encryption is enabled are sent\n        correctly.  The whole packet should be encrypted.\n        \"\"\"\n        proto = MockTransportBase()\n        proto.makeConnection(self.transport)\n        self.finishKeyExchange(proto)\n        proto.currentEncryptions = testCipher = MockCipher()\n        message = ord('A')\n        payload = b'BC'\n        self.transport.clear()\n        proto.sendPacket(message, payload)\n        self.assertTrue(testCipher.usedEncrypt)\n        value = self.transport.value()\n        self.assertEqual(\n            value,\n            # Four byte length prefix\n            b'\\x00\\x00\\x00\\x08'\n            # One byte padding length\n            b'\\x04'\n            # The actual application data\n            b'ABC'\n            # \"Random\" padding - see the secureRandom monkeypatch in setUp\n            b'\\x99\\x99\\x99\\x99'\n            # The MAC\n            b'\\x02')\n\n\n    def test_sendPacketCompressed(self):\n        \"\"\"\n        Test that packets sent while compression is enabled are sent\n        correctly.  The packet type and data should be encrypted.\n        \"\"\"\n        proto = MockTransportBase()\n        proto.makeConnection(self.transport)\n        self.finishKeyExchange(proto)\n        proto.outgoingCompression = MockCompression()\n        self.transport.clear()\n        proto.sendPacket(ord('A'), b'B')\n        value = self.transport.value()\n        self.assertEqual(\n            value,\n            b'\\x00\\x00\\x00\\x0c\\x08BA\\x66\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99')\n\n\n    def test_sendPacketBoth(self):\n        \"\"\"\n        Test that packets sent while compression and encryption are\n        enabled are sent correctly.  The packet type and data should be\n        compressed and then the whole packet should be encrypted.\n        \"\"\"\n        proto = MockTransportBase()\n        proto.makeConnection(self.transport)\n        self.finishKeyExchange(proto)\n        proto.currentEncryptions = testCipher = MockCipher()\n        proto.outgoingCompression = MockCompression()\n        message = ord('A')\n        payload = b'BC'\n        self.transport.clear()\n        proto.sendPacket(message, payload)\n        self.assertTrue(testCipher.usedEncrypt)\n        value = self.transport.value()\n        self.assertEqual(\n            value,\n            # Four byte length prefix\n            b'\\x00\\x00\\x00\\x0e'\n            # One byte padding length\n            b'\\x09'\n            # Compressed application data\n            b'CBA\\x66'\n            # \"Random\" padding - see the secureRandom monkeypatch in setUp\n            b'\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99'\n            # The MAC\n            b'\\x02')\n\n\n    def test_getPacketPlain(self):\n        \"\"\"\n        Test that packets are retrieved correctly out of the buffer when\n        no encryption is enabled.\n        \"\"\"\n        proto = MockTransportBase()\n        proto.makeConnection(self.transport)\n        self.finishKeyExchange(proto)\n        self.transport.clear()\n        proto.sendPacket(ord('A'), b'BC')\n        proto.buf = self.transport.value() + b'extra'\n        self.assertEqual(proto.getPacket(), b'ABC')\n        self.assertEqual(proto.buf, b'extra')\n\n\n    def test_getPacketEncrypted(self):\n        \"\"\"\n        Test that encrypted packets are retrieved correctly.\n        See test_sendPacketEncrypted.\n        \"\"\"\n        proto = MockTransportBase()\n        proto.sendKexInit = lambda: None # don't send packets\n        proto.makeConnection(self.transport)\n        self.transport.clear()\n        proto.currentEncryptions = testCipher = MockCipher()\n        proto.sendPacket(ord('A'), b'BCD')\n        value = self.transport.value()\n        proto.buf = value[:MockCipher.decBlockSize]\n        self.assertIsNone(proto.getPacket())\n        self.assertTrue(testCipher.usedDecrypt)\n        self.assertEqual(proto.first, b'\\x00\\x00\\x00\\x0e\\x09A')\n        proto.buf += value[MockCipher.decBlockSize:]\n        self.assertEqual(proto.getPacket(), b'ABCD')\n        self.assertEqual(proto.buf, b'')\n\n\n    def test_getPacketCompressed(self):\n        \"\"\"\n        Test that compressed packets are retrieved correctly.  See\n        test_sendPacketCompressed.\n        \"\"\"\n        proto = MockTransportBase()\n        proto.makeConnection(self.transport)\n        self.finishKeyExchange(proto)\n        self.transport.clear()\n        proto.outgoingCompression = MockCompression()\n        proto.incomingCompression = proto.outgoingCompression\n        proto.sendPacket(ord('A'), b'BCD')\n        proto.buf = self.transport.value()\n        self.assertEqual(proto.getPacket(), b'ABCD')\n\n\n    def test_getPacketBoth(self):\n        \"\"\"\n        Test that compressed and encrypted packets are retrieved correctly.\n        See test_sendPacketBoth.\n        \"\"\"\n        proto = MockTransportBase()\n        proto.sendKexInit = lambda: None\n        proto.makeConnection(self.transport)\n        self.transport.clear()\n        proto.currentEncryptions = MockCipher()\n        proto.outgoingCompression = MockCompression()\n        proto.incomingCompression = proto.outgoingCompression\n        proto.sendPacket(ord('A'), b'BCDEFG')\n        proto.buf = self.transport.value()\n        self.assertEqual(proto.getPacket(), b'ABCDEFG')\n\n\n    def test_ciphersAreValid(self):\n        \"\"\"\n        Test that all the supportedCiphers are valid.\n        \"\"\"\n        ciphers = transport.SSHCiphers(b'A', b'B', b'C', b'D')\n        iv = key = b'\\x00' * 16\n        for cipName in self.proto.supportedCiphers:\n            self.assertTrue(ciphers._getCipher(cipName, iv, key))\n\n\n    def test_sendKexInit(self):\n        \"\"\"\n        Test that the KEXINIT (key exchange initiation) message is sent\n        correctly.  Payload::\n            bytes[16] cookie\n            string key exchange algorithms\n            string public key algorithms\n            string outgoing ciphers\n            string incoming ciphers\n            string outgoing MACs\n            string incoming MACs\n            string outgoing compressions\n            string incoming compressions\n            bool first packet follows\n            uint32 0\n        \"\"\"\n        value = self.transport.value().split(b'\\r\\n', 1)[1]\n        self.proto.buf = value\n        packet = self.proto.getPacket()\n        self.assertEqual(packet[0:1], chr(transport.MSG_KEXINIT))\n        self.assertEqual(packet[1:17], b'\\x99' * 16)\n        (keyExchanges, pubkeys, ciphers1, ciphers2, macs1, macs2,\n         compressions1, compressions2, languages1, languages2,\n         buf) = common.getNS(packet[17:], 10)\n\n        self.assertEqual(\n            keyExchanges, b','.join(self.proto.supportedKeyExchanges))\n        self.assertEqual(pubkeys, b','.join(self.proto.supportedPublicKeys))\n        self.assertEqual(ciphers1, b','.join(self.proto.supportedCiphers))\n        self.assertEqual(ciphers2, b','.join(self.proto.supportedCiphers))\n        self.assertEqual(macs1, b','.join(self.proto.supportedMACs))\n        self.assertEqual(macs2, b','.join(self.proto.supportedMACs))\n        self.assertEqual(compressions1,\n                         b','.join(self.proto.supportedCompressions))\n        self.assertEqual(compressions2,\n                         b','.join(self.proto.supportedCompressions))\n        self.assertEqual(languages1, b','.join(self.proto.supportedLanguages))\n        self.assertEqual(languages2, b','.join(self.proto.supportedLanguages))\n        self.assertEqual(buf, b'\\x00' * 5)\n\n\n    def test_receiveKEXINITReply(self):\n        \"\"\"\n        Immediately after connecting, the transport expects a KEXINIT message\n        and does not reply to it.\n        \"\"\"\n        self.transport.clear()\n        self.proto.dispatchMessage(\n            transport.MSG_KEXINIT, self._A_KEXINIT_MESSAGE)\n        self.assertEqual(self.packets, [])\n\n\n    def test_sendKEXINITReply(self):\n        \"\"\"\n        When a KEXINIT message is received which is not a reply to an earlier\n        KEXINIT message which was sent, a KEXINIT reply is sent.\n        \"\"\"\n        self.finishKeyExchange(self.proto)\n        del self.packets[:]\n\n        self.proto.dispatchMessage(\n            transport.MSG_KEXINIT, self._A_KEXINIT_MESSAGE)\n        self.assertEqual(len(self.packets), 1)\n        self.assertEqual(self.packets[0][0], transport.MSG_KEXINIT)\n\n\n    def test_sendKexInitTwiceFails(self):\n        \"\"\"\n        A new key exchange cannot be started while a key exchange is already in\n        progress.  If an attempt is made to send a I{KEXINIT} message using\n        L{SSHTransportBase.sendKexInit} while a key exchange is in progress\n        causes that method to raise a L{RuntimeError}.\n        \"\"\"\n        self.assertRaises(RuntimeError, self.proto.sendKexInit)\n\n\n    def test_sendKexInitBlocksOthers(self):\n        \"\"\"\n        After L{SSHTransportBase.sendKexInit} has been called, messages types\n        other than the following are queued and not sent until after I{NEWKEYS}\n        is sent by L{SSHTransportBase._keySetup}.\n\n        RFC 4253, section 7.1.\n        \"\"\"\n        # sendKexInit is called by connectionMade, which is called in setUp.\n        # So we're in the state already.\n        disallowedMessageTypes = [\n            transport.MSG_SERVICE_REQUEST,\n            transport.MSG_KEXINIT,\n            ]\n\n        # Drop all the bytes sent by setUp, they're not relevant to this test.\n        self.transport.clear()\n\n        # Get rid of the sendPacket monkey patch, we are testing the behavior\n        # of sendPacket.\n        del self.proto.sendPacket\n\n        for messageType in disallowedMessageTypes:\n            self.proto.sendPacket(messageType, b'foo')\n            self.assertEqual(self.transport.value(), b\"\")\n\n        self.finishKeyExchange(self.proto)\n        # Make the bytes written to the transport cleartext so it's easier to\n        # make an assertion about them.\n        self.proto.nextEncryptions = MockCipher()\n\n        # Pseudo-deliver the peer's NEWKEYS message, which should flush the\n        # messages which were queued above.\n        self.proto._newKeys()\n        self.assertEqual(self.transport.value().count(b\"foo\"), 2)\n\n\n    def test_sendDebug(self):\n        \"\"\"\n        Test that debug messages are sent correctly.  Payload::\n            bool always display\n            string debug message\n            string language\n        \"\"\"\n        self.proto.sendDebug(b\"test\", True, b'en')\n        self.assertEqual(\n            self.packets,\n            [(transport.MSG_DEBUG,\n              b\"\\x01\\x00\\x00\\x00\\x04test\\x00\\x00\\x00\\x02en\")])\n\n\n    def test_receiveDebug(self):\n        \"\"\"\n        Test that debug messages are received correctly.  See test_sendDebug.\n        \"\"\"\n        self.proto.dispatchMessage(\n            transport.MSG_DEBUG,\n            b'\\x01\\x00\\x00\\x00\\x04test\\x00\\x00\\x00\\x02en')\n        self.proto.dispatchMessage(\n            transport.MSG_DEBUG,\n            b'\\x00\\x00\\x00\\x00\\x06silent\\x00\\x00\\x00\\x02en')\n        self.assertEqual(\n            self.proto.debugs,\n            [(True, b'test', b'en'), (False, b'silent', b'en')])\n\n\n    def test_sendIgnore(self):\n        \"\"\"\n        Test that ignored messages are sent correctly.  Payload::\n            string ignored data\n        \"\"\"\n        self.proto.sendIgnore(b\"test\")\n        self.assertEqual(\n            self.packets, [(transport.MSG_IGNORE,\n                            b'\\x00\\x00\\x00\\x04test')])\n\n\n    def test_receiveIgnore(self):\n        \"\"\"\n        Test that ignored messages are received correctly.  See\n        test_sendIgnore.\n        \"\"\"\n        self.proto.dispatchMessage(transport.MSG_IGNORE, b'test')\n        self.assertEqual(self.proto.ignoreds, [b'test'])\n\n\n    def test_sendUnimplemented(self):\n        \"\"\"\n        Test that unimplemented messages are sent correctly.  Payload::\n            uint32 sequence number\n        \"\"\"\n        self.proto.sendUnimplemented()\n        self.assertEqual(\n            self.packets, [(transport.MSG_UNIMPLEMENTED,\n                            b'\\x00\\x00\\x00\\x00')])\n\n\n    def test_receiveUnimplemented(self):\n        \"\"\"\n        Test that unimplemented messages are received correctly.  See\n        test_sendUnimplemented.\n        \"\"\"\n        self.proto.dispatchMessage(transport.MSG_UNIMPLEMENTED,\n                                   b'\\x00\\x00\\x00\\xff')\n        self.assertEqual(self.proto.unimplementeds, [255])\n\n\n    def test_sendDisconnect(self):\n        \"\"\"\n        Test that disconnection messages are sent correctly.  Payload::\n            uint32 reason code\n            string reason description\n            string language\n        \"\"\"\n        disconnected = [False]\n        def stubLoseConnection():\n            disconnected[0] = True\n        self.transport.loseConnection = stubLoseConnection\n        self.proto.sendDisconnect(0xff, b\"test\")\n        self.assertEqual(\n            self.packets,\n            [(transport.MSG_DISCONNECT,\n              b\"\\x00\\x00\\x00\\xff\\x00\\x00\\x00\\x04test\\x00\\x00\\x00\\x00\")])\n        self.assertTrue(disconnected[0])\n\n\n    def test_receiveDisconnect(self):\n        \"\"\"\n        Test that disconnection messages are received correctly.  See\n        test_sendDisconnect.\n        \"\"\"\n        disconnected = [False]\n        def stubLoseConnection():\n            disconnected[0] = True\n        self.transport.loseConnection = stubLoseConnection\n        self.proto.dispatchMessage(transport.MSG_DISCONNECT,\n                                   b'\\x00\\x00\\x00\\xff\\x00\\x00\\x00\\x04test')\n        self.assertEqual(self.proto.errors, [(255, b'test')])\n        self.assertTrue(disconnected[0])\n\n\n    def test_dataReceived(self):\n        \"\"\"\n        Test that dataReceived parses packets and dispatches them to\n        ssh_* methods.\n        \"\"\"\n        kexInit = [False]\n        def stubKEXINIT(packet):\n            kexInit[0] = True\n        self.proto.ssh_KEXINIT = stubKEXINIT\n        self.proto.dataReceived(self.transport.value())\n        self.assertTrue(self.proto.gotVersion)\n        self.assertEqual(self.proto.ourVersionString,\n                         self.proto.otherVersionString)\n        self.assertTrue(kexInit[0])\n\n\n    def test_service(self):\n        \"\"\"\n        Test that the transport can set the running service and dispatches\n        packets to the service's packetReceived method.\n        \"\"\"\n        service = MockService()\n        self.proto.setService(service)\n        self.assertEqual(self.proto.service, service)\n        self.assertTrue(service.started)\n        self.proto.dispatchMessage(0xff, b\"test\")\n        self.assertEqual(self.packets, [(0xff, b\"test\")])\n\n        service2 = MockService()\n        self.proto.setService(service2)\n        self.assertTrue(service2.started)\n        self.assertTrue(service.stopped)\n\n        self.proto.connectionLost(None)\n        self.assertTrue(service2.stopped)\n\n\n    def test_avatar(self):\n        \"\"\"\n        Test that the transport notifies the avatar of disconnections.\n        \"\"\"\n        disconnected = [False]\n        def logout():\n            disconnected[0] = True\n        self.proto.logoutFunction = logout\n        self.proto.avatar = True\n\n        self.proto.connectionLost(None)\n        self.assertTrue(disconnected[0])\n\n\n    def test_isEncrypted(self):\n        \"\"\"\n        Test that the transport accurately reflects its encrypted status.\n        \"\"\"\n        self.assertFalse(self.proto.isEncrypted('in'))\n        self.assertFalse(self.proto.isEncrypted('out'))\n        self.assertFalse(self.proto.isEncrypted('both'))\n        self.proto.currentEncryptions = MockCipher()\n        self.assertTrue(self.proto.isEncrypted('in'))\n        self.assertTrue(self.proto.isEncrypted('out'))\n        self.assertTrue(self.proto.isEncrypted('both'))\n        self.proto.currentEncryptions = transport.SSHCiphers(b'none', b'none',\n                                                             b'none', b'none')\n        self.assertFalse(self.proto.isEncrypted('in'))\n        self.assertFalse(self.proto.isEncrypted('out'))\n        self.assertFalse(self.proto.isEncrypted('both'))\n\n        self.assertRaises(TypeError, self.proto.isEncrypted, 'bad')\n\n\n    def test_isVerified(self):\n        \"\"\"\n        Test that the transport accurately reflects its verified status.\n        \"\"\"\n        self.assertFalse(self.proto.isVerified('in'))\n        self.assertFalse(self.proto.isVerified('out'))\n        self.assertFalse(self.proto.isVerified('both'))\n        self.proto.currentEncryptions = MockCipher()\n        self.assertTrue(self.proto.isVerified('in'))\n        self.assertTrue(self.proto.isVerified('out'))\n        self.assertTrue(self.proto.isVerified('both'))\n        self.proto.currentEncryptions = transport.SSHCiphers(b'none', b'none',\n                                                             b'none', b'none')\n        self.assertFalse(self.proto.isVerified('in'))\n        self.assertFalse(self.proto.isVerified('out'))\n        self.assertFalse(self.proto.isVerified('both'))\n\n        self.assertRaises(TypeError, self.proto.isVerified, 'bad')\n\n\n    def test_loseConnection(self):\n        \"\"\"\n        Test that loseConnection sends a disconnect message and closes the\n        connection.\n        \"\"\"\n        disconnected = [False]\n        def stubLoseConnection():\n            disconnected[0] = True\n        self.transport.loseConnection = stubLoseConnection\n        self.proto.loseConnection()\n        self.assertEqual(self.packets[0][0], transport.MSG_DISCONNECT)\n        self.assertEqual(self.packets[0][1][3:4],\n                         chr(transport.DISCONNECT_CONNECTION_LOST))\n\n\n    def test_badVersion(self):\n        \"\"\"\n        Test that the transport disconnects when it receives a bad version.\n        \"\"\"\n        def testBad(version):\n            self.packets = []\n            self.proto.gotVersion = False\n            disconnected = [False]\n            def stubLoseConnection():\n                disconnected[0] = True\n            self.transport.loseConnection = stubLoseConnection\n            for c in iterbytes(version + b'\\r\\n'):\n                self.proto.dataReceived(c)\n            self.assertTrue(disconnected[0])\n            self.assertEqual(self.packets[0][0], transport.MSG_DISCONNECT)\n            self.assertEqual(\n                self.packets[0][1][3:4],\n                chr(transport.DISCONNECT_PROTOCOL_VERSION_NOT_SUPPORTED))\n        testBad(b'SSH-1.5-OpenSSH')\n        testBad(b'SSH-3.0-Twisted')\n        testBad(b'GET / HTTP/1.1')\n\n\n    def test_dataBeforeVersion(self):\n        \"\"\"\n        Test that the transport ignores data sent before the version string.\n        \"\"\"\n        proto = MockTransportBase()\n        proto.makeConnection(proto_helpers.StringTransport())\n        data = (b\"\"\"here's some stuff beforehand\nhere's some other stuff\n\"\"\" + proto.ourVersionString + b\"\\r\\n\")\n        [proto.dataReceived(c) for c in iterbytes(data)]\n        self.assertTrue(proto.gotVersion)\n        self.assertEqual(proto.otherVersionString, proto.ourVersionString)\n\n\n    def test_compatabilityVersion(self):\n        \"\"\"\n        Test that the transport treats the compatibility version (1.99)\n        as equivalent to version 2.0.\n        \"\"\"\n        proto = MockTransportBase()\n        proto.makeConnection(proto_helpers.StringTransport())\n        proto.dataReceived(b\"SSH-1.99-OpenSSH\\n\")\n        self.assertTrue(proto.gotVersion)\n        self.assertEqual(proto.otherVersionString, b\"SSH-1.99-OpenSSH\")\n\n\n    def test_dataReceivedSSHVersionUnixNewline(self):\n        \"\"\"\n        It can parse the SSH version string even when it ends only in\n        Unix newlines (CR) and does not follows the RFC 4253 to use\n        network newlines (CR LF).\n        \"\"\"\n        sut = MockTransportBase()\n        sut.makeConnection(proto_helpers.StringTransport())\n\n        sut.dataReceived(\n            b'SSH-2.0-PoorSSHD Some-comment here\\n'\n            b'more-data'\n            )\n\n        self.assertTrue(sut.gotVersion)\n        self.assertEqual(\n            sut.otherVersionString,\n            b'SSH-2.0-PoorSSHD Some-comment here')\n\n\n    def test_dataReceivedSSHVersionTrailingSpaces(self):\n        \"\"\"\n        The trailing spaces from SSH version comment are not removed.\n\n        The SSH version string needs to be kept as received\n        (without CR LF end of line) as they are used in the host\n        authentication process.\n\n        This can happen with a Bitvise SSH server which hides its version.\n        \"\"\"\n        sut = MockTransportBase()\n        sut.makeConnection(proto_helpers.StringTransport())\n\n        sut.dataReceived(\n            b'SSH-2.0-9.99 FlowSsh: Bitvise SSH Server (WinSSHD) \\r\\n'\n            b'more-data'\n            )\n\n        self.assertTrue(sut.gotVersion)\n        self.assertEqual(\n            sut.otherVersionString,\n            b'SSH-2.0-9.99 FlowSsh: Bitvise SSH Server (WinSSHD) ')\n\n\n    def test_supportedVersionsAreAllowed(self):\n        \"\"\"\n        If an unusual SSH version is received and is included in\n        C{supportedVersions}, an unsupported version error is not emitted.\n        \"\"\"\n        proto = MockTransportBase()\n        proto.supportedVersions = (b\"9.99\", )\n        proto.makeConnection(proto_helpers.StringTransport())\n        proto.dataReceived(b\"SSH-9.99-OpenSSH\\n\")\n        self.assertFalse(proto.gotUnsupportedVersion)\n\n\n    def test_unsupportedVersionsCallUnsupportedVersionReceived(self):\n        \"\"\"\n        If an unusual SSH version is received and is not included in\n        C{supportedVersions}, an unsupported version error is emitted.\n        \"\"\"\n        proto = MockTransportBase()\n        proto.supportedVersions = (b\"2.0\", )\n        proto.makeConnection(proto_helpers.StringTransport())\n        proto.dataReceived(b\"SSH-9.99-OpenSSH\\n\")\n        self.assertEqual(b\"9.99\", proto.gotUnsupportedVersion)\n\n\n    def test_badPackets(self):\n        \"\"\"\n        Test that the transport disconnects with an error when it receives\n        bad packets.\n        \"\"\"\n        def testBad(packet, error=transport.DISCONNECT_PROTOCOL_ERROR):\n            self.packets = []\n            self.proto.buf = packet\n            self.assertIsNone(self.proto.getPacket())\n            self.assertEqual(len(self.packets), 1)\n            self.assertEqual(self.packets[0][0], transport.MSG_DISCONNECT)\n            self.assertEqual(self.packets[0][1][3:4], chr(error))\n\n        testBad(b'\\xff' * 8) # big packet\n        testBad(b'\\x00\\x00\\x00\\x05\\x00BCDE') # length not modulo blocksize\n        oldEncryptions = self.proto.currentEncryptions\n        self.proto.currentEncryptions = MockCipher()\n        testBad(b'\\x00\\x00\\x00\\x08\\x06AB123456', # bad MAC\n                transport.DISCONNECT_MAC_ERROR)\n        self.proto.currentEncryptions.decrypt = lambda x: x[:-1]\n        testBad(b'\\x00\\x00\\x00\\x08\\x06BCDEFGHIJK') # bad decryption\n        self.proto.currentEncryptions = oldEncryptions\n        self.proto.incomingCompression = MockCompression()\n        def stubDecompress(payload):\n            raise Exception('bad compression')\n        self.proto.incomingCompression.decompress = stubDecompress\n        testBad(b'\\x00\\x00\\x00\\x04\\x00BCDE', # bad decompression\n                transport.DISCONNECT_COMPRESSION_ERROR)\n        self.flushLoggedErrors()\n\n\n    def test_unimplementedPackets(self):\n        \"\"\"\n        Test that unimplemented packet types cause MSG_UNIMPLEMENTED packets\n        to be sent.\n        \"\"\"\n        seqnum = self.proto.incomingPacketSequence\n        def checkUnimplemented(seqnum=seqnum):\n            self.assertEqual(self.packets[0][0],\n                             transport.MSG_UNIMPLEMENTED)\n            self.assertEqual(self.packets[0][1][3:4], chr(seqnum))\n            self.proto.packets = []\n            seqnum += 1\n\n        self.proto.dispatchMessage(40, b'')\n        checkUnimplemented()\n        transport.messages[41] = b'MSG_fiction'\n        self.proto.dispatchMessage(41, b'')\n        checkUnimplemented()\n        self.proto.dispatchMessage(60, b'')\n        checkUnimplemented()\n        self.proto.setService(MockService())\n        self.proto.dispatchMessage(70, b'')\n        checkUnimplemented()\n        self.proto.dispatchMessage(71, b'')\n        checkUnimplemented()\n\n\n    def test_multipleClasses(self):\n        \"\"\"\n        Test that multiple instances have distinct states.\n        \"\"\"\n        proto = self.proto\n        proto.dataReceived(self.transport.value())\n        proto.currentEncryptions = MockCipher()\n        proto.outgoingCompression = MockCompression()\n        proto.incomingCompression = MockCompression()\n        proto.setService(MockService())\n        proto2 = MockTransportBase()\n        proto2.makeConnection(proto_helpers.StringTransport())\n        proto2.sendIgnore(b'')\n        self.assertNotEqual(proto.gotVersion, proto2.gotVersion)\n        self.assertNotEqual(proto.transport, proto2.transport)\n        self.assertNotEqual(proto.outgoingPacketSequence,\n                            proto2.outgoingPacketSequence)\n        self.assertNotEqual(proto.incomingPacketSequence,\n                            proto2.incomingPacketSequence)\n        self.assertNotEqual(proto.currentEncryptions,\n                            proto2.currentEncryptions)\n        self.assertNotEqual(proto.service, proto2.service)\n\n\n\nclass BaseSSHTransportDHGroupExchangeBaseCase(BaseSSHTransportBaseCase):\n    \"\"\"\n    Diffie-Hellman group exchange tests for TransportBase.\n    \"\"\"\n\n    def test_getKey(self):\n        \"\"\"\n        Test that _getKey generates the correct keys.\n        \"\"\"\n        self.proto.kexAlg = self.kexAlgorithm\n        self.proto.sessionID = b'EF'\n\n        k1 = self.hashProcessor(\n            b'AB' + b'CD' + b'K' + self.proto.sessionID).digest()\n        k2 = self.hashProcessor(b'ABCD' + k1).digest()\n        k3 = self.hashProcessor(b'ABCD' + k1 + k2).digest()\n        k4 = self.hashProcessor(b'ABCD' + k1 + k2 + k3).digest()\n        self.assertEqual(\n            self.proto._getKey(b'K', b'AB', b'CD'), k1 + k2 + k3 + k4)\n\n\n\nclass BaseSSHTransportDHGroupExchangeSHA1Tests(\n        BaseSSHTransportDHGroupExchangeBaseCase, DHGroupExchangeSHA1Mixin,\n        TransportTestCase):\n    \"\"\"\n    diffie-hellman-group-exchange-sha1 tests for TransportBase.\n    \"\"\"\n\n\n\nclass BaseSSHTransportDHGroupExchangeSHA256Tests(\n        BaseSSHTransportDHGroupExchangeBaseCase, DHGroupExchangeSHA256Mixin,\n        TransportTestCase):\n    \"\"\"\n    diffie-hellman-group-exchange-sha256 tests for TransportBase.\n    \"\"\"\n\n\n\nclass BaseSSHTransportEllipticCurveTests(\n        BaseSSHTransportDHGroupExchangeBaseCase, ECDHMixin,\n        TransportTestCase):\n    \"\"\"\n    ecdh-sha2-nistp256 tests for TransportBase\n    \"\"\"\n\n\n\nclass ServerAndClientSSHTransportBaseCase:\n    \"\"\"\n    Tests that need to be run on both the server and the client.\n    \"\"\"\n\n    def checkDisconnected(self, kind=None):\n        \"\"\"\n        Helper function to check if the transport disconnected.\n        \"\"\"\n        if kind is None:\n            kind = transport.DISCONNECT_PROTOCOL_ERROR\n        self.assertEqual(self.packets[-1][0], transport.MSG_DISCONNECT)\n        self.assertEqual(self.packets[-1][1][3:4], chr(kind))\n\n\n    def connectModifiedProtocol(self, protoModification,\n            kind=None):\n        \"\"\"\n        Helper function to connect a modified protocol to the test protocol\n        and test for disconnection.\n        \"\"\"\n        if kind is None:\n            kind = transport.DISCONNECT_KEY_EXCHANGE_FAILED\n        proto2 = self.klass()\n        protoModification(proto2)\n        proto2.makeConnection(proto_helpers.StringTransport())\n        self.proto.dataReceived(proto2.transport.value())\n        if kind:\n            self.checkDisconnected(kind)\n        return proto2\n\n\n    def test_disconnectIfCantMatchKex(self):\n        \"\"\"\n        Test that the transport disconnects if it can't match the key\n        exchange\n        \"\"\"\n        def blankKeyExchanges(proto2):\n            proto2.supportedKeyExchanges = []\n        self.connectModifiedProtocol(blankKeyExchanges)\n\n\n    def test_disconnectIfCantMatchKeyAlg(self):\n        \"\"\"\n        Like test_disconnectIfCantMatchKex, but for the key algorithm.\n        \"\"\"\n        def blankPublicKeys(proto2):\n            proto2.supportedPublicKeys = []\n        self.connectModifiedProtocol(blankPublicKeys)\n\n\n    def test_disconnectIfCantMatchCompression(self):\n        \"\"\"\n        Like test_disconnectIfCantMatchKex, but for the compression.\n        \"\"\"\n        def blankCompressions(proto2):\n            proto2.supportedCompressions = []\n        self.connectModifiedProtocol(blankCompressions)\n\n\n    def test_disconnectIfCantMatchCipher(self):\n        \"\"\"\n        Like test_disconnectIfCantMatchKex, but for the encryption.\n        \"\"\"\n        def blankCiphers(proto2):\n            proto2.supportedCiphers = []\n        self.connectModifiedProtocol(blankCiphers)\n\n\n    def test_disconnectIfCantMatchMAC(self):\n        \"\"\"\n        Like test_disconnectIfCantMatchKex, but for the MAC.\n        \"\"\"\n        def blankMACs(proto2):\n            proto2.supportedMACs = []\n        self.connectModifiedProtocol(blankMACs)\n\n\n    def test_getPeer(self):\n        \"\"\"\n        Test that the transport's L{getPeer} method returns an\n        L{SSHTransportAddress} with the L{IAddress} of the peer.\n        \"\"\"\n        self.assertEqual(self.proto.getPeer(),\n                         address.SSHTransportAddress(\n                             self.proto.transport.getPeer()))\n\n\n    def test_getHost(self):\n        \"\"\"\n        Test that the transport's L{getHost} method returns an\n        L{SSHTransportAddress} with the L{IAddress} of the host.\n        \"\"\"\n        self.assertEqual(self.proto.getHost(),\n                         address.SSHTransportAddress(\n                             self.proto.transport.getHost()))\n\n\n\nclass ServerSSHTransportBaseCase(ServerAndClientSSHTransportBaseCase):\n    \"\"\"\n    Base case for SSHServerTransport tests.\n    \"\"\"\n\n    klass = transport.SSHServerTransport\n\n\n    def setUp(self):\n        TransportTestCase.setUp(self)\n        self.proto.factory = MockFactory()\n        self.proto.factory.startFactory()\n\n\n    def tearDown(self):\n        TransportTestCase.tearDown(self)\n        self.proto.factory.stopFactory()\n        del self.proto.factory\n\n\n\nclass ServerSSHTransportTests(ServerSSHTransportBaseCase, TransportTestCase):\n    \"\"\"\n    Tests for SSHServerTransport.\n    \"\"\"\n\n    def test_KEXINITMultipleAlgorithms(self):\n        \"\"\"\n        Receiving a KEXINIT packet listing multiple supported algorithms will\n        set up the first common algorithm found in the client's preference\n        list.\n        \"\"\"\n        self.proto.dataReceived(\n            b'SSH-2.0-Twisted\\r\\n\\x00\\x00\\x01\\xf4\\x04\\x14'\n            b'\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99'\n            b'\\x99\\x00\\x00\\x00bdiffie-hellman-group1-sha1,diffie-hellman-g'\n            b'roup-exchange-sha1,diffie-hellman-group-exchange-sha256\\x00'\n            b'\\x00\\x00\\x0fssh-dss,ssh-rsa\\x00\\x00\\x00\\x85aes128-ctr,aes128-'\n            b'cbc,aes192-ctr,aes192-cbc,aes256-ctr,aes256-cbc,cast128-ctr,c'\n            b'ast128-cbc,blowfish-ctr,blowfish-cbc,3des-ctr,3des-cbc\\x00'\n            b'\\x00\\x00\\x85aes128-ctr,aes128-cbc,aes192-ctr,aes192-cbc,aes25'\n            b'6-ctr,aes256-cbc,cast128-ctr,cast128-cbc,blowfish-ctr,blowfis'\n            b'h-cbc,3des-ctr,3des-cbc\\x00\\x00\\x00\\x12hmac-md5,hmac-sha1\\x00'\n            b'\\x00\\x00\\x12hmac-md5,hmac-sha1\\x00\\x00\\x00\\tnone,zlib\\x00\\x00'\n            b'\\x00\\tnone,zlib\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00'\n            b'\\x00\\x00\\x99\\x99\\x99\\x99')\n\n        # Even if as server we prefer diffie-hellman-group-exchange-sha256 the\n        # client preference is used, after skipping diffie-hellman-group1-sha1\n        self.assertEqual(self.proto.kexAlg,\n                         b'diffie-hellman-group-exchange-sha1')\n        self.assertEqual(self.proto.keyAlg,\n                         b'ssh-dss')\n        self.assertEqual(self.proto.outgoingCompressionType,\n                         b'none')\n        self.assertEqual(self.proto.incomingCompressionType,\n                         b'none')\n        ne = self.proto.nextEncryptions\n        self.assertEqual(ne.outCipType, b'aes128-ctr')\n        self.assertEqual(ne.inCipType, b'aes128-ctr')\n        self.assertEqual(ne.outMACType, b'hmac-md5')\n        self.assertEqual(ne.inMACType, b'hmac-md5')\n\n\n    def test_ignoreGuessPacketKex(self):\n        \"\"\"\n        The client is allowed to send a guessed key exchange packet\n        after it sends the KEXINIT packet.  However, if the key exchanges\n        do not match, that guess packet must be ignored.  This tests that\n        the packet is ignored in the case of the key exchange method not\n        matching.\n        \"\"\"\n        kexInitPacket = b'\\x00' * 16 + (\n            b''.join([common.NS(x) for x in\n                     [b','.join(y) for y in\n                      [self.proto.supportedKeyExchanges[::-1],\n                       self.proto.supportedPublicKeys,\n                       self.proto.supportedCiphers,\n                       self.proto.supportedCiphers,\n                       self.proto.supportedMACs,\n                       self.proto.supportedMACs,\n                       self.proto.supportedCompressions,\n                       self.proto.supportedCompressions,\n                       self.proto.supportedLanguages,\n                       self.proto.supportedLanguages]]])) + (\n            b'\\xff\\x00\\x00\\x00\\x00')\n        self.proto.ssh_KEXINIT(kexInitPacket)\n        self.assertTrue(self.proto.ignoreNextPacket)\n        self.proto.ssh_DEBUG(b\"\\x01\\x00\\x00\\x00\\x04test\\x00\\x00\\x00\\x00\")\n        self.assertTrue(self.proto.ignoreNextPacket)\n\n        self.proto.ssh_KEX_DH_GEX_REQUEST_OLD(b'\\x00\\x00\\x08\\x00')\n        self.assertFalse(self.proto.ignoreNextPacket)\n        self.assertEqual(self.packets, [])\n        self.proto.ignoreNextPacket = True\n\n        self.proto.ssh_KEX_DH_GEX_REQUEST(b'\\x00\\x00\\x08\\x00' * 3)\n        self.assertFalse(self.proto.ignoreNextPacket)\n        self.assertEqual(self.packets, [])\n\n\n    def test_ignoreGuessPacketKey(self):\n        \"\"\"\n        Like test_ignoreGuessPacketKex, but for an incorrectly guessed\n        public key format.\n        \"\"\"\n        kexInitPacket = b'\\x00' * 16 + (\n            b''.join([common.NS(x) for x in\n                     [b','.join(y) for y in\n                      [self.proto.supportedKeyExchanges,\n                       self.proto.supportedPublicKeys[::-1],\n                       self.proto.supportedCiphers,\n                       self.proto.supportedCiphers,\n                       self.proto.supportedMACs,\n                       self.proto.supportedMACs,\n                       self.proto.supportedCompressions,\n                       self.proto.supportedCompressions,\n                       self.proto.supportedLanguages,\n                       self.proto.supportedLanguages]]])) + (\n            b'\\xff\\x00\\x00\\x00\\x00')\n        self.proto.ssh_KEXINIT(kexInitPacket)\n        self.assertTrue(self.proto.ignoreNextPacket)\n        self.proto.ssh_DEBUG(b\"\\x01\\x00\\x00\\x00\\x04test\\x00\\x00\\x00\\x00\")\n        self.assertTrue(self.proto.ignoreNextPacket)\n\n        self.proto.ssh_KEX_DH_GEX_REQUEST_OLD(b'\\x00\\x00\\x08\\x00')\n        self.assertFalse(self.proto.ignoreNextPacket)\n        self.assertEqual(self.packets, [])\n        self.proto.ignoreNextPacket = True\n\n        self.proto.ssh_KEX_DH_GEX_REQUEST(b'\\x00\\x00\\x08\\x00' * 3)\n        self.assertFalse(self.proto.ignoreNextPacket)\n        self.assertEqual(self.packets, [])\n\n\n    def assertKexDHInitResponse(self, kexAlgorithm, bits):\n        \"\"\"\n        Test that the KEXDH_INIT packet causes the server to send a\n        KEXDH_REPLY with the server's public key and a signature.\n\n        @param kexAlgorithm: The key exchange algorithm to use.\n        @type kexAlgorithm: L{str}\n        \"\"\"\n        self.proto.supportedKeyExchanges = [kexAlgorithm]\n        self.proto.supportedPublicKeys = [b'ssh-rsa']\n        self.proto.dataReceived(self.transport.value())\n\n        g, p = _kex.getDHGeneratorAndPrime(kexAlgorithm)\n        e = pow(g, 5000, p)\n\n        self.proto.ssh_KEX_DH_GEX_REQUEST_OLD(common.MP(e))\n        y = common.getMP(common.NS(b'\\x99' * (bits // 8)))[0]\n        f = _MPpow(self.proto.g, y, self.proto.p)\n        self.assertEqual(self.proto.dhSecretKeyPublicMP, f)\n        sharedSecret = _MPpow(e, y, self.proto.p)\n\n        h = sha1()\n        h.update(common.NS(self.proto.ourVersionString) * 2)\n        h.update(common.NS(self.proto.ourKexInitPayload) * 2)\n        h.update(common.NS(self.proto.factory.publicKeys[b'ssh-rsa'].blob()))\n        h.update(common.MP(e))\n        h.update(f)\n        h.update(sharedSecret)\n        exchangeHash = h.digest()\n\n        signature = self.proto.factory.privateKeys[b'ssh-rsa'].sign(\n            exchangeHash)\n\n        self.assertEqual(\n            self.packets,\n            [(transport.MSG_KEXDH_REPLY,\n              common.NS(self.proto.factory.publicKeys[b'ssh-rsa'].blob())\n              + f + common.NS(signature)),\n             (transport.MSG_NEWKEYS, b'')])\n\n\n    def test_checkBad_KEX_ECDH_INIT_CurveName(self):\n        \"\"\"\n        Test that if the server receives a KEX_DH_GEX_REQUEST_OLD message\n        and the key exchange algorithm is not set, we raise a ConchError.\n        \"\"\"\n        self.proto.kexAlg = b'bad-curve'\n        self.proto.keyAlg = b'ssh-rsa'\n        self.assertRaises(UnsupportedAlgorithm,\n                          self.proto._ssh_KEX_ECDH_INIT,\n                          common.NS(b'unused-key'))\n\n\n    def test_checkBad_KEX_INIT_CurveName(self):\n        \"\"\"\n        Test that if the server received a bad name for a curve\n        we raise an UnsupportedAlgorithm error.\n        \"\"\"\n        kexmsg = (\n            b\"\\xAA\" * 16 +\n            common.NS(b'ecdh-sha2-nistp256') +\n            common.NS(b'ssh-rsa') +\n            common.NS(b'aes256-ctr') +\n            common.NS(b'aes256-ctr') +\n            common.NS(b'hmac-sha1') +\n            common.NS(b'hmac-sha1') +\n            common.NS(b'none') +\n            common.NS(b'none') +\n            common.NS(b'') +\n            common.NS(b'') +\n            b'\\x00' + b'\\x00\\x00\\x00\\x00')\n\n        self.proto.ssh_KEXINIT(kexmsg)\n        self.assertRaises(AttributeError)\n        self.assertRaises(UnsupportedAlgorithm)\n\n\n    def test_KEXDH_INIT_GROUP14(self):\n        \"\"\"\n        KEXDH_INIT messages are processed when the\n        diffie-hellman-group14-sha1 key exchange algorithm is requested.\n        \"\"\"\n        self.assertKexDHInitResponse(b'diffie-hellman-group14-sha1', 2048)\n\n\n    def test_keySetup(self):\n        \"\"\"\n        Test that _keySetup sets up the next encryption keys.\n        \"\"\"\n        self.proto.kexAlg = b'diffie-hellman-group14-sha1'\n        self.proto.nextEncryptions = MockCipher()\n        self.simulateKeyExchange(b'AB', b'CD')\n        self.assertEqual(self.proto.sessionID, b'CD')\n        self.simulateKeyExchange(b'AB', b'EF')\n        self.assertEqual(self.proto.sessionID, b'CD')\n        self.assertEqual(self.packets[-1], (transport.MSG_NEWKEYS, b''))\n        newKeys = [self.proto._getKey(c, b'AB', b'EF')\n                   for c in iterbytes(b'ABCDEF')]\n        self.assertEqual(\n            self.proto.nextEncryptions.keys,\n            (newKeys[1], newKeys[3], newKeys[0], newKeys[2], newKeys[5],\n             newKeys[4]))\n\n\n    def test_ECDH_keySetup(self):\n        \"\"\"\n        Test that _keySetup sets up the next encryption keys.\n        \"\"\"\n        self.proto.kexAlg = b'ecdh-sha2-nistp256'\n        self.proto.nextEncryptions = MockCipher()\n        self.simulateKeyExchange(b'AB', b'CD')\n        self.assertEqual(self.proto.sessionID, b'CD')\n        self.simulateKeyExchange(b'AB', b'EF')\n        self.assertEqual(self.proto.sessionID, b'CD')\n        self.assertEqual(self.packets[-1], (transport.MSG_NEWKEYS, b''))\n        newKeys = [self.proto._getKey(c, b'AB', b'EF')\n                   for c in iterbytes(b'ABCDEF')]\n        self.assertEqual(\n            self.proto.nextEncryptions.keys,\n            (newKeys[1], newKeys[3], newKeys[0], newKeys[2], newKeys[5],\n             newKeys[4]))\n\n\n    def test_NEWKEYS(self):\n        \"\"\"\n        Test that NEWKEYS transitions the keys in nextEncryptions to\n        currentEncryptions.\n        \"\"\"\n        self.test_KEXINITMultipleAlgorithms()\n\n        self.proto.nextEncryptions = transport.SSHCiphers(b'none', b'none',\n                                                          b'none', b'none')\n        self.proto.ssh_NEWKEYS(b'')\n        self.assertIs(self.proto.currentEncryptions,\n                      self.proto.nextEncryptions)\n        self.assertIsNone(self.proto.outgoingCompression)\n        self.assertIsNone(self.proto.incomingCompression)\n        self.proto.outgoingCompressionType = b'zlib'\n        self.simulateKeyExchange(b'AB', b'CD')\n        self.proto.ssh_NEWKEYS(b'')\n        self.assertIsNotNone(self.proto.outgoingCompression)\n        self.proto.incomingCompressionType = b'zlib'\n        self.simulateKeyExchange(b'AB', b'EF')\n        self.proto.ssh_NEWKEYS(b'')\n        self.assertIsNotNone(self.proto.incomingCompression)\n\n\n    def test_SERVICE_REQUEST(self):\n        \"\"\"\n        Test that the SERVICE_REQUEST message requests and starts a\n        service.\n        \"\"\"\n        self.proto.ssh_SERVICE_REQUEST(common.NS(b'ssh-userauth'))\n        self.assertEqual(self.packets, [(transport.MSG_SERVICE_ACCEPT,\n                                         common.NS(b'ssh-userauth'))])\n        self.assertEqual(self.proto.service.name, b'MockService')\n\n\n    def test_disconnectNEWKEYSData(self):\n        \"\"\"\n        Test that NEWKEYS disconnects if it receives data.\n        \"\"\"\n        self.proto.ssh_NEWKEYS(b\"bad packet\")\n        self.checkDisconnected()\n\n\n    def test_disconnectSERVICE_REQUESTBadService(self):\n        \"\"\"\n        Test that SERVICE_REQUESTS disconnects if an unknown service is\n        requested.\n        \"\"\"\n        self.proto.ssh_SERVICE_REQUEST(common.NS(b'no service'))\n        self.checkDisconnected(transport.DISCONNECT_SERVICE_NOT_AVAILABLE)\n\n\n\nclass ServerSSHTransportDHGroupExchangeBaseCase(ServerSSHTransportBaseCase):\n    \"\"\"\n    Diffie-Hellman group exchange tests for SSHServerTransport.\n    \"\"\"\n\n    def test_KEX_DH_GEX_REQUEST_OLD(self):\n        \"\"\"\n        Test that the KEX_DH_GEX_REQUEST_OLD message causes the server\n        to reply with a KEX_DH_GEX_GROUP message with the correct\n        Diffie-Hellman group.\n        \"\"\"\n        self.proto.supportedKeyExchanges = [self.kexAlgorithm]\n        self.proto.supportedPublicKeys = [b'ssh-rsa']\n        self.proto.dataReceived(self.transport.value())\n        self.proto.ssh_KEX_DH_GEX_REQUEST_OLD(b'\\x00\\x00\\x04\\x00')\n        dhGenerator, dhPrime = self.proto.factory.getPrimes().get(2048)[0]\n        self.assertEqual(\n            self.packets,\n            [(transport.MSG_KEX_DH_GEX_GROUP,\n              common.MP(dhPrime) + b'\\x00\\x00\\x00\\x01\\x02')])\n        self.assertEqual(self.proto.g, 2)\n        self.assertEqual(self.proto.p, dhPrime)\n\n\n    def test_KEX_DH_GEX_REQUEST_OLD_badKexAlg(self):\n        \"\"\"\n        Test that if the server receives a KEX_DH_GEX_REQUEST_OLD message\n        and the key exchange algorithm is not set, we raise a ConchError.\n        \"\"\"\n        self.proto.kexAlg = None\n        self.assertRaises(ConchError, self.proto.ssh_KEX_DH_GEX_REQUEST_OLD,\n                None)\n\n\n    def test_KEX_DH_GEX_REQUEST(self):\n        \"\"\"\n        Test that the KEX_DH_GEX_REQUEST message causes the server to reply\n        with a KEX_DH_GEX_GROUP message with the correct Diffie-Hellman\n        group.\n        \"\"\"\n        self.proto.supportedKeyExchanges = [self.kexAlgorithm]\n        self.proto.supportedPublicKeys = [b'ssh-rsa']\n        self.proto.dataReceived(self.transport.value())\n        self.proto.ssh_KEX_DH_GEX_REQUEST(b'\\x00\\x00\\x04\\x00\\x00\\x00\\x08\\x00' +\n                                          b'\\x00\\x00\\x0c\\x00')\n        dhGenerator, dhPrime = self.proto.factory.getPrimes().get(2048)[0]\n        self.assertEqual(\n            self.packets,\n            [(transport.MSG_KEX_DH_GEX_GROUP,\n              common.MP(dhPrime) + b'\\x00\\x00\\x00\\x01\\x02')])\n        self.assertEqual(self.proto.g, 2)\n        self.assertEqual(self.proto.p, dhPrime)\n\n\n    def test_KEX_DH_GEX_INIT_after_REQUEST_OLD(self):\n        \"\"\"\n        Test that the KEX_DH_GEX_INIT message after the client sends\n        KEX_DH_GEX_REQUEST_OLD causes the server to send a KEX_DH_GEX_INIT\n        message with a public key and signature.\n        \"\"\"\n        self.test_KEX_DH_GEX_REQUEST_OLD()\n        e = pow(self.proto.g, 3, self.proto.p)\n        y = common.getMP(b'\\x00\\x00\\x01\\x00' + b'\\x99' * 512)[0]\n        self.assertEqual(self.proto.dhSecretKey.private_numbers().x, y)\n        f = _MPpow(self.proto.g, y, self.proto.p)\n        self.assertEqual(self.proto.dhSecretKeyPublicMP, f)\n        sharedSecret = _MPpow(e, y, self.proto.p)\n        h = self.hashProcessor()\n        h.update(common.NS(self.proto.ourVersionString) * 2)\n        h.update(common.NS(self.proto.ourKexInitPayload) * 2)\n        h.update(common.NS(self.proto.factory.publicKeys[b'ssh-rsa'].blob()))\n        h.update(b'\\x00\\x00\\x04\\x00')\n        h.update(common.MP(self.proto.p))\n        h.update(common.MP(self.proto.g))\n        h.update(common.MP(e))\n        h.update(f)\n        h.update(sharedSecret)\n        exchangeHash = h.digest()\n        self.proto.ssh_KEX_DH_GEX_INIT(common.MP(e))\n        self.assertEqual(\n            self.packets[1:],\n            [(transport.MSG_KEX_DH_GEX_REPLY,\n              common.NS(self.proto.factory.publicKeys[b'ssh-rsa'].blob()) +\n              f + common.NS(self.proto.factory.privateKeys[b'ssh-rsa'].sign(\n                            exchangeHash))),\n             (transport.MSG_NEWKEYS, b'')])\n\n\n    def test_KEX_DH_GEX_INIT_after_REQUEST(self):\n        \"\"\"\n        Test that the KEX_DH_GEX_INIT message after the client sends\n        KEX_DH_GEX_REQUEST causes the server to send a KEX_DH_GEX_INIT message\n        with a public key and signature.\n        \"\"\"\n        self.test_KEX_DH_GEX_REQUEST()\n        e = pow(self.proto.g, 3, self.proto.p)\n        y = common.getMP(b'\\x00\\x00\\x01\\x00' + b'\\x99' * 256)[0]\n        f = _MPpow(self.proto.g, y, self.proto.p)\n        sharedSecret = _MPpow(e, y, self.proto.p)\n\n        h = self.hashProcessor()\n\n        h.update(common.NS(self.proto.ourVersionString) * 2)\n        h.update(common.NS(self.proto.ourKexInitPayload) * 2)\n        h.update(common.NS(self.proto.factory.publicKeys[b'ssh-rsa'].blob()))\n        h.update(b'\\x00\\x00\\x04\\x00\\x00\\x00\\x08\\x00\\x00\\x00\\x0c\\x00')\n        h.update(common.MP(self.proto.p))\n        h.update(common.MP(self.proto.g))\n        h.update(common.MP(e))\n        h.update(f)\n        h.update(sharedSecret)\n        exchangeHash = h.digest()\n        self.proto.ssh_KEX_DH_GEX_INIT(common.MP(e))\n        self.assertEqual(\n            self.packets[1],\n            (transport.MSG_KEX_DH_GEX_REPLY,\n             common.NS(self.proto.factory.publicKeys[b'ssh-rsa'].blob()) +\n             f + common.NS(self.proto.factory.privateKeys[b'ssh-rsa'].sign(\n                 exchangeHash))))\n\n\n\nclass ServerSSHTransportDHGroupExchangeSHA1Tests(\n        ServerSSHTransportDHGroupExchangeBaseCase, DHGroupExchangeSHA1Mixin,\n        TransportTestCase):\n    \"\"\"\n    diffie-hellman-group-exchange-sha1 tests for SSHServerTransport.\n    \"\"\"\n\n\n\nclass ServerSSHTransportDHGroupExchangeSHA256Tests(\n        ServerSSHTransportDHGroupExchangeBaseCase, DHGroupExchangeSHA256Mixin,\n        TransportTestCase):\n    \"\"\"\n    diffie-hellman-group-exchange-sha256 tests for SSHServerTransport.\n    \"\"\"\n\n\n\nclass ClientSSHTransportBaseCase(ServerAndClientSSHTransportBaseCase):\n    \"\"\"\n    Base case for SSHClientTransport tests.\n    \"\"\"\n\n    klass = transport.SSHClientTransport\n\n\n    def verifyHostKey(self, pubKey, fingerprint):\n        \"\"\"\n        Mock version of SSHClientTransport.verifyHostKey.\n        \"\"\"\n        self.calledVerifyHostKey = True\n        self.assertEqual(pubKey, self.blob)\n        self.assertEqual(fingerprint.replace(b':', b''),\n                         binascii.hexlify(md5(pubKey).digest()))\n        return defer.succeed(True)\n\n\n    def setUp(self):\n        TransportTestCase.setUp(self)\n        self.blob = keys.Key.fromString(keydata.publicRSA_openssh).blob()\n        self.privObj = keys.Key.fromString(keydata.privateRSA_openssh)\n        self.calledVerifyHostKey = False\n        self.proto.verifyHostKey = self.verifyHostKey\n\n\n\nclass ClientSSHTransportTests(ClientSSHTransportBaseCase, TransportTestCase):\n    \"\"\"\n    Tests for SSHClientTransport.\n    \"\"\"\n\n    def test_KEXINITMultipleAlgorithms(self):\n        \"\"\"\n        Receiving a KEXINIT packet listing multiple supported\n        algorithms will set up the first common algorithm, ordered after our\n        preference.\n        \"\"\"\n        self.proto.dataReceived(\n            b'SSH-2.0-Twisted\\r\\n\\x00\\x00\\x01\\xf4\\x04\\x14'\n            b'\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99\\x99'\n            b'\\x99\\x00\\x00\\x00bdiffie-hellman-group1-sha1,diffie-hellman-g'\n            b'roup-exchange-sha1,diffie-hellman-group-exchange-sha256\\x00'\n            b'\\x00\\x00\\x0fssh-dss,ssh-rsa\\x00\\x00\\x00\\x85aes128-ctr,aes128-'\n            b'cbc,aes192-ctr,aes192-cbc,aes256-ctr,aes256-cbc,cast128-ctr,c'\n            b'ast128-cbc,blowfish-ctr,blowfish-cbc,3des-ctr,3des-cbc\\x00'\n            b'\\x00\\x00\\x85aes128-ctr,aes128-cbc,aes192-ctr,aes192-cbc,aes25'\n            b'6-ctr,aes256-cbc,cast128-ctr,cast128-cbc,blowfish-ctr,blowfis'\n            b'h-cbc,3des-ctr,3des-cbc\\x00\\x00\\x00\\x12hmac-md5,hmac-sha1\\x00'\n            b'\\x00\\x00\\x12hmac-md5,hmac-sha1\\x00\\x00\\x00\\tzlib,none\\x00\\x00'\n            b'\\x00\\tzlib,none\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00'\n            b'\\x00\\x00\\x99\\x99\\x99\\x99')\n        # Even if client prefer diffie-hellman-group1-sha1, we will go for\n        # diffie-hellman-group-exchange-sha256 as this what we prefer and is\n        # also supported by the server.\n        self.assertEqual(self.proto.kexAlg,\n                         b'diffie-hellman-group-exchange-sha256')\n        self.assertEqual(self.proto.keyAlg,\n                         b'ssh-rsa')\n        self.assertEqual(self.proto.outgoingCompressionType,\n                         b'none')\n        self.assertEqual(self.proto.incomingCompressionType,\n                         b'none')\n        ne = self.proto.nextEncryptions\n        self.assertEqual(ne.outCipType, b'aes256-ctr')\n        self.assertEqual(ne.inCipType, b'aes256-ctr')\n        self.assertEqual(ne.outMACType, b'hmac-sha1')\n        self.assertEqual(ne.inMACType, b'hmac-sha1')\n\n\n    def test_notImplementedClientMethods(self):\n        \"\"\"\n        verifyHostKey() should return a Deferred which fails with a\n        NotImplementedError exception.  connectionSecure() should raise\n        NotImplementedError().\n        \"\"\"\n        self.assertRaises(NotImplementedError, self.klass().connectionSecure)\n        def _checkRaises(f):\n            f.trap(NotImplementedError)\n        d = self.klass().verifyHostKey(None, None)\n        return d.addCallback(self.fail).addErrback(_checkRaises)\n\n\n    def assertKexInitResponseForDH(self, kexAlgorithm, bits):\n        \"\"\"\n        Test that a KEXINIT packet with a group1 or group14 key exchange\n        results in a correct KEXDH_INIT response.\n\n        @param kexAlgorithm: The key exchange algorithm to use\n        @type kexAlgorithm: L{str}\n        \"\"\"\n        self.proto.supportedKeyExchanges = [kexAlgorithm]\n\n        # Imitate reception of server key exchange request contained\n        # in data returned by self.transport.value()\n        self.proto.dataReceived(self.transport.value())\n\n        x = self.proto.dhSecretKey.private_numbers().x\n        self.assertEqual(common.MP(x)[5:], b'\\x99' * (bits // 8))\n\n        # Data sent to server should be a transport.MSG_KEXDH_INIT\n        # message containing our public key.\n        self.assertEqual(\n            self.packets,\n            [(transport.MSG_KEXDH_INIT, self.proto.dhSecretKeyPublicMP)])\n\n\n    def test_KEXINIT_group14(self):\n        \"\"\"\n        KEXINIT messages requesting diffie-hellman-group14-sha1 result in\n        KEXDH_INIT responses.\n        \"\"\"\n        self.assertKexInitResponseForDH(b'diffie-hellman-group14-sha1', 2048)\n\n\n    def test_KEXINIT_badKexAlg(self):\n        \"\"\"\n        Test that the client raises a ConchError if it receives a\n        KEXINIT message but doesn't have a key exchange algorithm that we\n        understand.\n        \"\"\"\n        self.proto.supportedKeyExchanges = [b'diffie-hellman-group24-sha1']\n        data = self.transport.value().replace(b'group14', b'group24')\n        self.assertRaises(ConchError, self.proto.dataReceived, data)\n\n\n    def begin_KEXDH_REPLY(self):\n        \"\"\"\n        Utility for test_KEXDH_REPLY and\n        test_disconnectKEXDH_REPLYBadSignature.\n\n        Begins a Diffie-Hellman key exchange in the named group\n        Group-14 and computes information needed to return either a\n        correct or incorrect signature.\n\n        \"\"\"\n        self.test_KEXINIT_group14()\n\n        f = 2\n        fMP = common.MP(f)\n        x = self.proto.dhSecretKey.private_numbers().x\n        p = self.proto.p\n        sharedSecret = _MPpow(f, x, p)\n        h = sha1()\n        h.update(common.NS(self.proto.ourVersionString) * 2)\n        h.update(common.NS(self.proto.ourKexInitPayload) * 2)\n        h.update(common.NS(self.blob))\n        h.update(self.proto.dhSecretKeyPublicMP)\n        h.update(fMP)\n        h.update(sharedSecret)\n        exchangeHash = h.digest()\n\n        signature = self.privObj.sign(exchangeHash)\n\n        return (exchangeHash, signature, common.NS(self.blob) + fMP)\n\n\n    def test_KEXDH_REPLY(self):\n        \"\"\"\n        Test that the KEXDH_REPLY message verifies the server.\n        \"\"\"\n        (exchangeHash, signature, packetStart) = self.begin_KEXDH_REPLY()\n\n        def _cbTestKEXDH_REPLY(value):\n            self.assertIsNone(value)\n            self.assertTrue(self.calledVerifyHostKey)\n            self.assertEqual(self.proto.sessionID, exchangeHash)\n\n        d = self.proto.ssh_KEX_DH_GEX_GROUP(\n            packetStart + common.NS(signature)\n        )\n        d.addCallback(_cbTestKEXDH_REPLY)\n\n        return d\n\n\n    def test_keySetup(self):\n        \"\"\"\n        Test that _keySetup sets up the next encryption keys.\n        \"\"\"\n        self.proto.kexAlg = b'diffie-hellman-group14-sha1'\n        self.proto.nextEncryptions = MockCipher()\n        self.simulateKeyExchange(b'AB', b'CD')\n        self.assertEqual(self.proto.sessionID, b'CD')\n        self.simulateKeyExchange(b'AB', b'EF')\n        self.assertEqual(self.proto.sessionID, b'CD')\n        self.assertEqual(self.packets[-1], (transport.MSG_NEWKEYS, b''))\n        newKeys = [self.proto._getKey(c, b'AB', b'EF')\n                   for c in iterbytes(b'ABCDEF')]\n        self.assertEqual(self.proto.nextEncryptions.keys,\n                          (newKeys[0], newKeys[2], newKeys[1], newKeys[3],\n                           newKeys[4], newKeys[5]))\n\n\n    def test_NEWKEYS(self):\n        \"\"\"\n        Test that NEWKEYS transitions the keys from nextEncryptions to\n        currentEncryptions.\n        \"\"\"\n        self.test_KEXINITMultipleAlgorithms()\n        secure = [False]\n        def stubConnectionSecure():\n            secure[0] = True\n        self.proto.connectionSecure = stubConnectionSecure\n\n        self.proto.nextEncryptions = transport.SSHCiphers(\n            b'none', b'none', b'none', b'none')\n        self.simulateKeyExchange(b'AB', b'CD')\n        self.assertIsNot(self.proto.currentEncryptions,\n                         self.proto.nextEncryptions)\n\n        self.proto.nextEncryptions = MockCipher()\n        self.proto.ssh_NEWKEYS(b'')\n        self.assertIsNone(self.proto.outgoingCompression)\n        self.assertIsNone(self.proto.incomingCompression)\n        self.assertIs(self.proto.currentEncryptions,\n                      self.proto.nextEncryptions)\n        self.assertTrue(secure[0])\n        self.proto.outgoingCompressionType = b'zlib'\n        self.simulateKeyExchange(b'AB', b'GH')\n        self.proto.ssh_NEWKEYS(b'')\n        self.assertIsNotNone(self.proto.outgoingCompression)\n        self.proto.incomingCompressionType = b'zlib'\n        self.simulateKeyExchange(b'AB', b'IJ')\n        self.proto.ssh_NEWKEYS(b'')\n        self.assertIsNotNone(self.proto.incomingCompression)\n\n\n    def test_SERVICE_ACCEPT(self):\n        \"\"\"\n        Test that the SERVICE_ACCEPT packet starts the requested service.\n        \"\"\"\n        self.proto.instance = MockService()\n        self.proto.ssh_SERVICE_ACCEPT(b'\\x00\\x00\\x00\\x0bMockService')\n        self.assertTrue(self.proto.instance.started)\n\n\n    def test_requestService(self):\n        \"\"\"\n        Test that requesting a service sends a SERVICE_REQUEST packet.\n        \"\"\"\n        self.proto.requestService(MockService())\n        self.assertEqual(self.packets, [(transport.MSG_SERVICE_REQUEST,\n                                         b'\\x00\\x00\\x00\\x0bMockService')])\n\n\n    def test_disconnectKEXDH_REPLYBadSignature(self):\n        \"\"\"\n        Test that KEXDH_REPLY disconnects if the signature is bad.\n        \"\"\"\n        (exchangeHash, signature, packetStart) = self.begin_KEXDH_REPLY()\n\n        d = self.proto.ssh_KEX_DH_GEX_GROUP(\n            packetStart + common.NS(b\"bad signature\")\n        )\n        return d.addCallback(\n            lambda _: self.checkDisconnected(\n                transport.DISCONNECT_KEY_EXCHANGE_FAILED)\n        )\n\n\n    def test_disconnectKEX_ECDH_REPLYBadSignature(self):\n        \"\"\"\n        Test that KEX_ECDH_REPLY disconnects if the signature is bad.\n        \"\"\"\n        kexmsg = (\n            b\"\\xAA\" * 16 +\n            common.NS(b'ecdh-sha2-nistp256') +\n            common.NS(b'ssh-rsa') +\n            common.NS(b'aes256-ctr') +\n            common.NS(b'aes256-ctr') +\n            common.NS(b'hmac-sha1') +\n            common.NS(b'hmac-sha1') +\n            common.NS(b'none') +\n            common.NS(b'none') +\n            common.NS(b'') +\n            common.NS(b'') +\n            b'\\x00' + b'\\x00\\x00\\x00\\x00')\n\n        self.proto.ssh_KEXINIT(kexmsg)\n\n        self.proto.dataReceived(b\"SSH-2.0-OpenSSH\\r\\n\")\n\n        self.proto.ecPriv = ec.generate_private_key(ec.SECP256R1(),\n                                                    default_backend())\n        self.proto.ecPub = self.proto.ecPriv.public_key()\n\n        # Generate the private key\n        thisPriv = ec.generate_private_key(ec.SECP256R1(), default_backend())\n        # Get the public key\n        thisPub = thisPriv.public_key()\n        encPub = thisPub.public_bytes(\n            serialization.Encoding.X962,\n            serialization.PublicFormat.UncompressedPoint\n        )\n        self.proto.curve = ec.SECP256R1()\n\n        self.proto.kexAlg = b'ecdh-sha2-nistp256'\n\n        self.proto._ssh_KEX_ECDH_REPLY(\n             common.NS(MockFactory().getPublicKeys()[b'ssh-rsa'].blob()) +\n                       common.NS(encPub) + common.NS(b'bad-signature'))\n\n        self.checkDisconnected(transport.DISCONNECT_KEY_EXCHANGE_FAILED)\n\n\n    def test_disconnectNEWKEYSData(self):\n        \"\"\"\n        Test that NEWKEYS disconnects if it receives data.\n        \"\"\"\n        self.proto.ssh_NEWKEYS(b\"bad packet\")\n        self.checkDisconnected()\n\n\n    def test_disconnectSERVICE_ACCEPT(self):\n        \"\"\"\n        Test that SERVICE_ACCEPT disconnects if the accepted protocol is\n        differet from the asked-for protocol.\n        \"\"\"\n        self.proto.instance = MockService()\n        self.proto.ssh_SERVICE_ACCEPT(b'\\x00\\x00\\x00\\x03bad')\n        self.checkDisconnected()\n\n\n    def test_noPayloadSERVICE_ACCEPT(self):\n        \"\"\"\n        Some commercial SSH servers don't send a payload with the\n        SERVICE_ACCEPT message.  Conch pretends that it got the correct\n        name of the service.\n        \"\"\"\n        self.proto.instance = MockService()\n        self.proto.ssh_SERVICE_ACCEPT(b'') # no payload\n        self.assertTrue(self.proto.instance.started)\n        self.assertEqual(len(self.packets), 0) # not disconnected\n\n\n\nclass ClientSSHTransportDHGroupExchangeBaseCase(ClientSSHTransportBaseCase):\n    \"\"\"\n    Diffie-Hellman group exchange tests for SSHClientTransport.\n    \"\"\"\n\n    def test_KEXINIT_groupexchange(self):\n        \"\"\"\n        KEXINIT packet with a group-exchange key exchange results\n        in a KEX_DH_GEX_REQUEST message.\n        \"\"\"\n        self.proto.supportedKeyExchanges = [self.kexAlgorithm]\n        self.proto.dataReceived(self.transport.value())\n        # The response will include our advertised group sizes.\n        self.assertEqual(self.packets, [(\n            transport.MSG_KEX_DH_GEX_REQUEST,\n            b'\\x00\\x00\\x04\\x00\\x00\\x00\\x08\\x00\\x00\\x00\\x20\\x00')])\n\n\n    def test_KEX_DH_GEX_GROUP(self):\n        \"\"\"\n        Test that the KEX_DH_GEX_GROUP message results in a\n        KEX_DH_GEX_INIT message with the client's Diffie-Hellman public key.\n        \"\"\"\n        self.test_KEXINIT_groupexchange()\n        self.proto.ssh_KEX_DH_GEX_GROUP(\n            b'\\x00\\x00\\x00\\x03\\x00\\xfe\\xf3\\x00\\x00\\x00\\x01\\x02')\n        self.assertEqual(self.proto.p, 65267)\n        self.assertEqual(self.proto.g, 2)\n        x = self.proto.dhSecretKey.private_numbers().x\n        self.assertEqual(common.MP(x)[5:], b'\\x99' * 2)\n        self.assertEqual(self.proto.dhSecretKeyPublicMP,\n                         common.MP(pow(2, x, 65267)))\n        self.assertEqual(self.packets[1:], [(transport.MSG_KEX_DH_GEX_INIT,\n                                             self.proto.dhSecretKeyPublicMP)])\n\n\n    def begin_KEX_DH_GEX_REPLY(self):\n        \"\"\"\n        Utility for test_KEX_DH_GEX_REPLY and\n        test_disconnectGEX_REPLYBadSignature.\n\n        Begins a Diffie-Hellman key exchange in an unnamed\n        (server-specified) group and computes information needed to\n        return either a correct or incorrect signature.\n        \"\"\"\n        self.test_KEX_DH_GEX_GROUP()\n        p = self.proto.p\n        f = 3\n        fMP = common.MP(f)\n        sharedSecret = _MPpow(\n            f,\n            self.proto.dhSecretKey.private_numbers().x,\n            p)\n        h = self.hashProcessor()\n        h.update(common.NS(self.proto.ourVersionString) * 2)\n        h.update(common.NS(self.proto.ourKexInitPayload) * 2)\n        h.update(common.NS(self.blob))\n        # Here is the wire format for advertised min, pref and max DH sizes.\n        h.update(b'\\x00\\x00\\x04\\x00\\x00\\x00\\x08\\x00\\x00\\x00\\x20\\x00')\n        # And the selected group parameters.\n        h.update(b'\\x00\\x00\\x00\\x03\\x00\\xfe\\xf3\\x00\\x00\\x00\\x01\\x02')\n        h.update(self.proto.dhSecretKeyPublicMP)\n        h.update(fMP)\n        h.update(sharedSecret)\n        exchangeHash = h.digest()\n\n        signature = self.privObj.sign(exchangeHash)\n\n        return (\n            exchangeHash,\n            signature,\n            common.NS(self.blob) + fMP\n        )\n\n\n    def test_KEX_DH_GEX_REPLY(self):\n        \"\"\"\n        Test that the KEX_DH_GEX_REPLY message results in a verified\n        server.\n        \"\"\"\n        (exchangeHash, signature, packetStart) = self.begin_KEX_DH_GEX_REPLY()\n\n        def _cbTestKEX_DH_GEX_REPLY(value):\n            self.assertIsNone(value)\n            self.assertTrue(self.calledVerifyHostKey)\n            self.assertEqual(self.proto.sessionID, exchangeHash)\n\n        d = self.proto.ssh_KEX_DH_GEX_REPLY(packetStart + common.NS(signature))\n        d.addCallback(_cbTestKEX_DH_GEX_REPLY)\n        return d\n\n\n    def test_disconnectGEX_REPLYBadSignature(self):\n        \"\"\"\n        Test that KEX_DH_GEX_REPLY disconnects if the signature is bad.\n        \"\"\"\n        (exchangeHash, signature, packetStart) = self.begin_KEX_DH_GEX_REPLY()\n\n        d = self.proto.ssh_KEX_DH_GEX_REPLY(\n            packetStart + common.NS(b\"bad signature\"))\n        return d.addCallback(\n            lambda _: self.checkDisconnected(\n                transport.DISCONNECT_KEY_EXCHANGE_FAILED)\n        )\n\n\n    def test_disconnectKEX_ECDH_REPLYBadSignature(self):\n        \"\"\"\n        Test that KEX_ECDH_REPLY disconnects if the signature is bad.\n        \"\"\"\n        kexmsg = (\n            b\"\\xAA\" * 16 +\n            common.NS(b'ecdh-sha2-nistp256') +\n            common.NS(b'ssh-rsa') +\n            common.NS(b'aes256-ctr') +\n            common.NS(b'aes256-ctr') +\n            common.NS(b'hmac-sha1') +\n            common.NS(b'hmac-sha1') +\n            common.NS(b'none') +\n            common.NS(b'none') +\n            common.NS(b'') +\n            common.NS(b'') +\n            b'\\x00' + b'\\x00\\x00\\x00\\x00')\n\n        self.proto.ssh_KEXINIT(kexmsg)\n\n        self.proto.dataReceived(b\"SSH-2.0-OpenSSH\\r\\n\")\n\n        self.proto.ecPriv = ec.generate_private_key(ec.SECP256R1(),\n                                                    default_backend())\n        self.proto.ecPub = self.proto.ecPriv.public_key()\n\n        # Generate the private key\n        thisPriv = ec.generate_private_key(ec.SECP256R1(), default_backend())\n        # Get the public key\n        thisPub = thisPriv.public_key()\n        encPub = thisPub.public_bytes(\n            serialization.Encoding.X962,\n            serialization.PublicFormat.UncompressedPoint\n        )\n        self.proto.curve = ec.SECP256R1()\n\n        self.proto.kexAlg = b'ecdh-sha2-nistp256'\n\n        self.proto._ssh_KEX_ECDH_REPLY(\n            common.NS(MockFactory().getPublicKeys()[b'ssh-rsa'].blob()) +\n            common.NS(encPub) + common.NS(b'bad-signature'))\n\n        self.checkDisconnected(transport.DISCONNECT_KEY_EXCHANGE_FAILED)\n\n\n\nclass ClientSSHTransportDHGroupExchangeSHA1Tests(\n        ClientSSHTransportDHGroupExchangeBaseCase, DHGroupExchangeSHA1Mixin,\n        TransportTestCase):\n    \"\"\"\n    diffie-hellman-group-exchange-sha1 tests for SSHClientTransport.\n    \"\"\"\n\n\n\nclass ClientSSHTransportDHGroupExchangeSHA256Tests(\n        ClientSSHTransportDHGroupExchangeBaseCase, DHGroupExchangeSHA256Mixin,\n        TransportTestCase):\n    \"\"\"\n    diffie-hellman-group-exchange-sha256 tests for SSHClientTransport.\n    \"\"\"\n\n\n\nclass GetMACTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{SSHCiphers._getMAC}.\n    \"\"\"\n    if dependencySkip:\n        skip = dependencySkip\n\n\n    def setUp(self):\n        self.ciphers = transport.SSHCiphers(b'A', b'B', b'C', b'D')\n\n\n    def getSharedSecret(self):\n        \"\"\"\n        Generate a new shared secret to be used with the tests.\n\n        @return: A new secret.\n        @rtype: L{bytes}\n        \"\"\"\n        return insecureRandom(64)\n\n\n    def assertGetMAC(self, hmacName, hashProcessor, digestSize, blockPadSize):\n        \"\"\"\n        Check that when L{SSHCiphers._getMAC} is called with a supportd HMAC\n        algorithm name it returns a tuple of\n        (digest object, inner pad, outer pad, digest size) with a C{key}\n        attribute set to the value of the key supplied.\n\n        @param hmacName: Identifier of HMAC algorithm.\n        @type hmacName: L{bytes}\n\n        @param hashProcessor: Callable for the hash algorithm.\n        @type hashProcessor: C{callable}\n\n        @param digestSize: Size of the digest for algorithm.\n        @type digestSize: L{int}\n\n        @param blockPadSize: Size of padding applied to the shared secret to\n            match the block size.\n        @type blockPadSize: L{int}\n        \"\"\"\n        secret = self.getSharedSecret()\n\n        params = self.ciphers._getMAC(hmacName, secret)\n\n        key = secret[:digestSize] + b'\\x00' * blockPadSize\n        innerPad = b''.join(chr(ord(b) ^ 0x36) for b in iterbytes(key))\n        outerPad = b''.join(chr(ord(b) ^ 0x5c) for b in iterbytes(key))\n        self.assertEqual(\n            (hashProcessor, innerPad, outerPad, digestSize), params)\n        self.assertEqual(key, params.key)\n\n\n    def test_hmacsha2512(self):\n        \"\"\"\n        When L{SSHCiphers._getMAC} is called with the C{b\"hmac-sha2-512\"} MAC\n        algorithm name it returns a tuple of (sha512 digest object, inner pad,\n        outer pad, sha512 digest size) with a C{key} attribute set to the\n        value of the key supplied.\n        \"\"\"\n        self.assertGetMAC(\n            b\"hmac-sha2-512\", sha512, digestSize=64, blockPadSize=64)\n\n\n    def test_hmacsha2384(self):\n        \"\"\"\n        When L{SSHCiphers._getMAC} is called with the C{b\"hmac-sha2-384\"} MAC\n        algorithm name it returns a tuple of (sha384 digest object, inner pad,\n        outer pad, sha384 digest size) with a C{key} attribute set to the\n        value of the key supplied.\n        \"\"\"\n        self.assertGetMAC(\n            b\"hmac-sha2-384\", sha384, digestSize=48, blockPadSize=80)\n\n\n    def test_hmacsha2256(self):\n        \"\"\"\n        When L{SSHCiphers._getMAC} is called with the C{b\"hmac-sha2-256\"} MAC\n        algorithm name it returns a tuple of (sha256 digest object, inner pad,\n        outer pad, sha256 digest size) with a C{key} attribute set to the\n        value of the key supplied.\n        \"\"\"\n        self.assertGetMAC(\n            b\"hmac-sha2-256\", sha256, digestSize=32, blockPadSize=32)\n\n\n    def test_hmacsha1(self):\n        \"\"\"\n        When L{SSHCiphers._getMAC} is called with the C{b\"hmac-sha1\"} MAC\n        algorithm name it returns a tuple of (sha1 digest object, inner pad,\n        outer pad, sha1 digest size) with a C{key} attribute set to the value\n        of the key supplied.\n        \"\"\"\n        self.assertGetMAC(b\"hmac-sha1\", sha1, digestSize=20, blockPadSize=44)\n\n\n    def test_hmacmd5(self):\n        \"\"\"\n        When L{SSHCiphers._getMAC} is called with the C{b\"hmac-md5\"} MAC\n        algorithm name it returns a tuple of (md5 digest object, inner pad,\n        outer pad, md5 digest size) with a C{key} attribute set to the value of\n        the key supplied.\n        \"\"\"\n        self.assertGetMAC(b\"hmac-md5\", md5, digestSize=16, blockPadSize=48)\n\n\n    def test_none(self):\n        \"\"\"\n        When L{SSHCiphers._getMAC} is called with the C{b\"none\"} MAC algorithm\n        name it returns a tuple of (None, \"\", \"\", 0).\n        \"\"\"\n        key = self.getSharedSecret()\n\n        params = self.ciphers._getMAC(b\"none\", key)\n\n        self.assertEqual((None, b\"\", b\"\", 0), params)\n\n\n\nclass SSHCiphersTests(unittest.TestCase):\n    \"\"\"\n    Tests for the SSHCiphers helper class.\n    \"\"\"\n    if dependencySkip:\n        skip = dependencySkip\n\n\n    def test_init(self):\n        \"\"\"\n        Test that the initializer sets up the SSHCiphers object.\n        \"\"\"\n        ciphers = transport.SSHCiphers(b'A', b'B', b'C', b'D')\n        self.assertEqual(ciphers.outCipType, b'A')\n        self.assertEqual(ciphers.inCipType, b'B')\n        self.assertEqual(ciphers.outMACType, b'C')\n        self.assertEqual(ciphers.inMACType, b'D')\n\n\n    def test_getCipher(self):\n        \"\"\"\n        Test that the _getCipher method returns the correct cipher.\n        \"\"\"\n        ciphers = transport.SSHCiphers(b'A', b'B', b'C', b'D')\n        iv = key = b'\\x00' * 16\n        for cipName, (algClass, keySize, counter) in ciphers.cipherMap.items():\n            cip = ciphers._getCipher(cipName, iv, key)\n            if cipName == b'none':\n                self.assertIsInstance(cip, transport._DummyCipher)\n            else:\n                self.assertIsInstance(cip.algorithm, algClass)\n\n\n    def test_setKeysCiphers(self):\n        \"\"\"\n        Test that setKeys sets up the ciphers.\n        \"\"\"\n        key = b'\\x00' * 64\n        for cipName in transport.SSHTransportBase.supportedCiphers:\n            modName, keySize, counter = transport.SSHCiphers.cipherMap[cipName]\n            encCipher = transport.SSHCiphers(cipName, b'none', b'none',\n                                             b'none')\n            decCipher = transport.SSHCiphers(b'none', cipName, b'none',\n                                             b'none')\n            cip = encCipher._getCipher(cipName, key, key)\n            bs = cip.algorithm.block_size // 8\n            encCipher.setKeys(key, key, b'', b'', b'', b'')\n            decCipher.setKeys(b'', b'', key, key, b'', b'')\n            self.assertEqual(encCipher.encBlockSize, bs)\n            self.assertEqual(decCipher.decBlockSize, bs)\n            encryptor = cip.encryptor()\n            enc = encryptor.update(key[:bs])\n            enc2 = encryptor.update(key[:bs])\n            self.assertEqual(encCipher.encrypt(key[:bs]), enc)\n            self.assertEqual(encCipher.encrypt(key[:bs]), enc2)\n            self.assertEqual(decCipher.decrypt(enc), key[:bs])\n            self.assertEqual(decCipher.decrypt(enc2), key[:bs])\n\n\n    def test_setKeysMACs(self):\n        \"\"\"\n        Test that setKeys sets up the MACs.\n        \"\"\"\n        key = b'\\x00' * 64\n        for macName, mod in transport.SSHCiphers.macMap.items():\n            outMac = transport.SSHCiphers(b'none', b'none', macName, b'none')\n            inMac = transport.SSHCiphers(b'none', b'none', b'none', macName)\n            outMac.setKeys(b'', b'', b'', b'', key, b'')\n            inMac.setKeys(b'', b'', b'', b'', b'', key)\n            if mod:\n                ds = mod().digest_size\n            else:\n                ds = 0\n            self.assertEqual(inMac.verifyDigestSize, ds)\n            if mod:\n                mod, i, o, ds = outMac._getMAC(macName, key)\n            seqid = 0\n            data = key\n            packet = b'\\x00' * 4 + key\n            if mod:\n                mac = mod(o + mod(i + packet).digest()).digest()\n            else:\n                mac = b''\n            self.assertEqual(outMac.makeMAC(seqid, data), mac)\n            self.assertTrue(inMac.verify(seqid, data, mac))\n\n\n    def test_makeMAC(self):\n        \"\"\"\n        L{SSHCiphers.makeMAC} computes the HMAC of an outgoing SSH message with\n        a particular sequence id and content data.\n        \"\"\"\n        # Use the test vectors given in the appendix of RFC 2104.\n        vectors = [\n            (b\"\\x0b\" * 16, b\"Hi There\",\n             b\"9294727a3638bb1c13f48ef8158bfc9d\"),\n            (b\"Jefe\", b\"what do ya want for nothing?\",\n             b\"750c783e6ab0b503eaa86e310a5db738\"),\n            (b\"\\xAA\" * 16, b\"\\xDD\" * 50,\n             b\"56be34521d144c88dbb8c733f0e8b3f6\"),\n            ]\n\n        for key, data, mac in vectors:\n            outMAC = transport.SSHCiphers(b'none', b'none', b'hmac-md5',\n                                          b'none')\n            outMAC.outMAC = outMAC._getMAC(b\"hmac-md5\", key)\n            (seqid,) = struct.unpack('>L', data[:4])\n            shortened = data[4:]\n            self.assertEqual(\n                mac, binascii.hexlify(outMAC.makeMAC(seqid, shortened)),\n                \"Failed HMAC test vector; key=%r data=%r\" % (key, data))\n\n\n\nclass TransportLoopbackTests(unittest.TestCase):\n    \"\"\"\n    Test the server transport and client transport against each other,\n    \"\"\"\n    if dependencySkip:\n        skip = dependencySkip\n\n\n    def _runClientServer(self, mod):\n        \"\"\"\n        Run an async client and server, modifying each using the mod function\n        provided.  Returns a Deferred called back when both Protocols have\n        disconnected.\n\n        @type mod: C{func}\n        @rtype: C{defer.Deferred}\n        \"\"\"\n        factory = MockFactory()\n        server = transport.SSHServerTransport()\n        server.factory = factory\n        factory.startFactory()\n        server.errors = []\n        server.receiveError = lambda code, desc: server.errors.append((\n                code, desc))\n        client = transport.SSHClientTransport()\n        client.verifyHostKey = lambda x, y: defer.succeed(None)\n        client.errors = []\n        client.receiveError = lambda code, desc: client.errors.append((\n                code, desc))\n        client.connectionSecure = lambda: client.loseConnection()\n        server.supportedPublicKeys = list(\n                server.factory.getPublicKeys().keys())\n        server = mod(server)\n        client = mod(client)\n        def check(ignored, server, client):\n            name = repr([server.supportedCiphers[0],\n                         server.supportedMACs[0],\n                         server.supportedKeyExchanges[0],\n                         server.supportedCompressions[0]])\n            self.assertEqual(client.errors, [])\n            self.assertEqual(server.errors, [(\n                        transport.DISCONNECT_CONNECTION_LOST,\n                        b\"user closed connection\")])\n            if server.supportedCiphers[0] == b'none':\n                self.assertFalse(server.isEncrypted(), name)\n                self.assertFalse(client.isEncrypted(), name)\n            else:\n                self.assertTrue(server.isEncrypted(), name)\n                self.assertTrue(client.isEncrypted(), name)\n            if server.supportedMACs[0] == b'none':\n                self.assertFalse(server.isVerified(), name)\n                self.assertFalse(client.isVerified(), name)\n            else:\n                self.assertTrue(server.isVerified(), name)\n                self.assertTrue(client.isVerified(), name)\n\n        d = loopback.loopbackAsync(server, client)\n        d.addCallback(check, server, client)\n        return d\n\n\n    def test_ciphers(self):\n        \"\"\"\n        Test that the client and server play nicely together, in all\n        the various combinations of ciphers.\n        \"\"\"\n        deferreds = []\n        for cipher in transport.SSHTransportBase.supportedCiphers + [b'none']:\n            def setCipher(proto):\n                proto.supportedCiphers = [cipher]\n                return proto\n            deferreds.append(self._runClientServer(setCipher))\n        return defer.DeferredList(deferreds, fireOnOneErrback=True)\n\n\n    def test_macs(self):\n        \"\"\"\n        Like test_ciphers, but for the various MACs.\n        \"\"\"\n        deferreds = []\n        for mac in transport.SSHTransportBase.supportedMACs + [b'none']:\n            def setMAC(proto):\n                proto.supportedMACs = [mac]\n                return proto\n            deferreds.append(self._runClientServer(setMAC))\n        return defer.DeferredList(deferreds, fireOnOneErrback=True)\n\n\n    def test_keyexchanges(self):\n        \"\"\"\n        Like test_ciphers, but for the various key exchanges.\n        \"\"\"\n        deferreds = []\n        for kexAlgorithm in transport.SSHTransportBase.supportedKeyExchanges:\n            def setKeyExchange(proto):\n                proto.supportedKeyExchanges = [kexAlgorithm]\n                return proto\n            deferreds.append(self._runClientServer(setKeyExchange))\n        return defer.DeferredList(deferreds, fireOnOneErrback=True)\n\n\n    def test_compressions(self):\n        \"\"\"\n        Like test_ciphers, but for the various compressions.\n        \"\"\"\n        deferreds = []\n        for compression in transport.SSHTransportBase.supportedCompressions:\n            def setCompression(proto):\n                proto.supportedCompressions = [compression]\n                return proto\n            deferreds.append(self._runClientServer(setCompression))\n        return defer.DeferredList(deferreds, fireOnOneErrback=True)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_unix.py",
    "content": "# -*- test-case-name: twisted.conch.test.test_unix -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom __future__ import absolute_import\n\nfrom zope.interface import implementer\n\nfrom twisted.internet.interfaces import IReactorProcess\nfrom twisted.python.reflect import requireModule\nfrom twisted.trial import unittest\n\ncryptography = requireModule(\"cryptography\")\nunix = requireModule('twisted.conch.unix')\n\n\n\n@implementer(IReactorProcess)\nclass MockProcessSpawner(object):\n    \"\"\"\n    An L{IReactorProcess} that logs calls to C{spawnProcess}.\n    \"\"\"\n\n    def __init__(self):\n        self._spawnProcessCalls = []\n\n\n    def spawnProcess(self, processProtocol, executable, args=(), env={},\n                     path=None, uid=None, gid=None, usePTY=0, childFDs=None):\n        \"\"\"\n        Log a call to C{spawnProcess}. Do not actually spawn a process.\n        \"\"\"\n        self._spawnProcessCalls.append(\n            {'processProtocol': processProtocol,\n             'executable': executable,\n             'args': args,\n             'env': env,\n             'path': path,\n             'uid': uid,\n             'gid': gid,\n             'usePTY': usePTY,\n             'childFDs': childFDs})\n\n\n\nclass StubUnixConchUser(object):\n    \"\"\"\n    Enough of UnixConchUser to exercise SSHSessionForUnixConchUser in the\n    tests below.\n    \"\"\"\n\n    def __init__(self, homeDirectory):\n        from .test_session import StubConnection, StubClient\n\n        self._homeDirectory = homeDirectory\n        self.conn = StubConnection(transport=StubClient())\n\n\n    def getUserGroupId(self):\n        return (None, None)\n\n\n    def getHomeDir(self):\n        return self._homeDirectory\n\n\n    def getShell(self):\n        pass\n\n\n\nclass TestSSHSessionForUnixConchUser(unittest.TestCase):\n\n    if cryptography is None:\n        skip = \"Cannot run without cryptography\"\n    elif unix is None:\n        skip = \"Unix system required\"\n\n\n    def testExecCommandEnvironment(self):\n        \"\"\"\n        C{execCommand} sets the C{HOME} environment variable to the avatar's home\n        directory.\n        \"\"\"\n        mockReactor = MockProcessSpawner()\n        homeDirectory = \"/made/up/path/\"\n        avatar = StubUnixConchUser(homeDirectory)\n        session = unix.SSHSessionForUnixConchUser(avatar, reactor=mockReactor)\n        protocol = None\n        command = [\"not-actually-executed\"]\n        session.execCommand(protocol, command)\n        [call] = mockReactor._spawnProcessCalls\n        self.assertEqual(homeDirectory, call['env']['HOME'])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_userauth.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for the implementation of the ssh-userauth service.\n\nMaintainer: Paul Swartz\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom zope.interface import implementer\n\nfrom twisted.cred.checkers import ICredentialsChecker\nfrom twisted.cred.credentials import IUsernamePassword, ISSHPrivateKey\nfrom twisted.cred.credentials import IAnonymous\nfrom twisted.cred.error import UnauthorizedLogin\nfrom twisted.cred.portal import IRealm, Portal\nfrom twisted.conch.error import ConchError, ValidPublicKey\nfrom twisted.internet import defer, task\nfrom twisted.protocols import loopback\nfrom twisted.python.reflect import requireModule\nfrom twisted.trial import unittest\nfrom twisted.python.compat import _bytesChr as chr\n\nif requireModule('cryptography') and requireModule('pyasn1'):\n    from twisted.conch.ssh.common import NS\n    from twisted.conch.checkers import SSHProtocolChecker\n    from twisted.conch.ssh import keys, userauth, transport\n    from twisted.conch.test import keydata\nelse:\n    keys = None\n\n\n    class transport:\n        class SSHTransportBase:\n            \"\"\"\n            A stub class so that later class definitions won't die.\n            \"\"\"\n\n    class userauth:\n        class SSHUserAuthClient:\n            \"\"\"\n            A stub class so that later class definitions won't die.\n            \"\"\"\n\n\n\nclass ClientUserAuth(userauth.SSHUserAuthClient):\n    \"\"\"\n    A mock user auth client.\n    \"\"\"\n\n    def getPublicKey(self):\n        \"\"\"\n        If this is the first time we've been called, return a blob for\n        the DSA key.  Otherwise, return a blob\n        for the RSA key.\n        \"\"\"\n        if self.lastPublicKey:\n            return keys.Key.fromString(keydata.publicRSA_openssh)\n        else:\n            return defer.succeed(\n                keys.Key.fromString(keydata.publicDSA_openssh))\n\n\n    def getPrivateKey(self):\n        \"\"\"\n        Return the private key object for the RSA key.\n        \"\"\"\n        return defer.succeed(keys.Key.fromString(keydata.privateRSA_openssh))\n\n\n    def getPassword(self, prompt=None):\n        \"\"\"\n        Return 'foo' as the password.\n        \"\"\"\n        return defer.succeed(b'foo')\n\n\n    def getGenericAnswers(self, name, information, answers):\n        \"\"\"\n        Return 'foo' as the answer to two questions.\n        \"\"\"\n        return defer.succeed(('foo', 'foo'))\n\n\n\nclass OldClientAuth(userauth.SSHUserAuthClient):\n    \"\"\"\n    The old SSHUserAuthClient returned a cryptography key object from\n    getPrivateKey() and a string from getPublicKey\n    \"\"\"\n\n    def getPrivateKey(self):\n        return defer.succeed(keys.Key.fromString(\n            keydata.privateRSA_openssh).keyObject)\n\n\n    def getPublicKey(self):\n        return keys.Key.fromString(keydata.publicRSA_openssh).blob()\n\n\n\nclass ClientAuthWithoutPrivateKey(userauth.SSHUserAuthClient):\n    \"\"\"\n    This client doesn't have a private key, but it does have a public key.\n    \"\"\"\n\n    def getPrivateKey(self):\n        return\n\n\n    def getPublicKey(self):\n        return keys.Key.fromString(keydata.publicRSA_openssh)\n\n\n\nclass FakeTransport(transport.SSHTransportBase):\n    \"\"\"\n    L{userauth.SSHUserAuthServer} expects an SSH transport which has a factory\n    attribute which has a portal attribute. Because the portal is important for\n    testing authentication, we need to be able to provide an interesting portal\n    object to the L{SSHUserAuthServer}.\n\n    In addition, we want to be able to capture any packets sent over the\n    transport.\n\n    @ivar packets: a list of 2-tuples: (messageType, data).  Each 2-tuple is\n        a sent packet.\n    @type packets: C{list}\n    @param lostConnecion: True if loseConnection has been called on us.\n    @type lostConnection: L{bool}\n    \"\"\"\n\n    class Service(object):\n        \"\"\"\n        A mock service, representing the other service offered by the server.\n        \"\"\"\n        name = b'nancy'\n\n\n        def serviceStarted(self):\n            pass\n\n\n    class Factory(object):\n        \"\"\"\n        A mock factory, representing the factory that spawned this user auth\n        service.\n        \"\"\"\n\n        def getService(self, transport, service):\n            \"\"\"\n            Return our fake service.\n            \"\"\"\n            if service == b'none':\n                return FakeTransport.Service\n\n\n    def __init__(self, portal):\n        self.factory = self.Factory()\n        self.factory.portal = portal\n        self.lostConnection = False\n        self.transport = self\n        self.packets = []\n\n\n    def sendPacket(self, messageType, message):\n        \"\"\"\n        Record the packet sent by the service.\n        \"\"\"\n        self.packets.append((messageType, message))\n\n\n    def isEncrypted(self, direction):\n        \"\"\"\n        Pretend that this transport encrypts traffic in both directions. The\n        SSHUserAuthServer disables password authentication if the transport\n        isn't encrypted.\n        \"\"\"\n        return True\n\n\n    def loseConnection(self):\n        self.lostConnection = True\n\n\n\n@implementer(IRealm)\nclass Realm(object):\n    \"\"\"\n    A mock realm for testing L{userauth.SSHUserAuthServer}.\n\n    This realm is not actually used in the course of testing, so it returns the\n    simplest thing that could possibly work.\n    \"\"\"\n\n    def requestAvatar(self, avatarId, mind, *interfaces):\n        return defer.succeed((interfaces[0], None, lambda: None))\n\n\n\n@implementer(ICredentialsChecker)\nclass PasswordChecker(object):\n    \"\"\"\n    A very simple username/password checker which authenticates anyone whose\n    password matches their username and rejects all others.\n    \"\"\"\n    credentialInterfaces = (IUsernamePassword,)\n\n    def requestAvatarId(self, creds):\n        if creds.username == creds.password:\n            return defer.succeed(creds.username)\n        return defer.fail(UnauthorizedLogin(\"Invalid username/password pair\"))\n\n\n\n@implementer(ICredentialsChecker)\nclass PrivateKeyChecker(object):\n    \"\"\"\n    A very simple public key checker which authenticates anyone whose\n    public/private keypair is the same keydata.public/privateRSA_openssh.\n    \"\"\"\n    credentialInterfaces = (ISSHPrivateKey,)\n\n    def requestAvatarId(self, creds):\n        if creds.blob == keys.Key.fromString(keydata.publicRSA_openssh).blob():\n            if creds.signature is not None:\n                obj = keys.Key.fromString(creds.blob)\n                if obj.verify(creds.signature, creds.sigData):\n                    return creds.username\n            else:\n                raise ValidPublicKey()\n        raise UnauthorizedLogin()\n\n\n\n@implementer(ICredentialsChecker)\nclass AnonymousChecker(object):\n    \"\"\"\n    A simple checker which isn't supported by L{SSHUserAuthServer}.\n    \"\"\"\n    credentialInterfaces = (IAnonymous,)\n\n\n\nclass SSHUserAuthServerTests(unittest.TestCase):\n    \"\"\"\n    Tests for SSHUserAuthServer.\n    \"\"\"\n\n    if keys is None:\n        skip = \"cannot run without cryptography\"\n\n\n    def setUp(self):\n        self.realm = Realm()\n        self.portal = Portal(self.realm)\n        self.portal.registerChecker(PasswordChecker())\n        self.portal.registerChecker(PrivateKeyChecker())\n        self.authServer = userauth.SSHUserAuthServer()\n        self.authServer.transport = FakeTransport(self.portal)\n        self.authServer.serviceStarted()\n        self.authServer.supportedAuthentications.sort() # give a consistent\n                                                        # order\n\n\n    def tearDown(self):\n        self.authServer.serviceStopped()\n        self.authServer = None\n\n\n    def _checkFailed(self, ignored):\n        \"\"\"\n        Check that the authentication has failed.\n        \"\"\"\n        self.assertEqual(self.authServer.transport.packets[-1],\n                (userauth.MSG_USERAUTH_FAILURE,\n                NS(b'password,publickey') + b'\\x00'))\n\n\n    def test_noneAuthentication(self):\n        \"\"\"\n        A client may request a list of authentication 'method name' values\n        that may continue by using the \"none\" authentication 'method name'.\n\n        See RFC 4252 Section 5.2.\n        \"\"\"\n        d = self.authServer.ssh_USERAUTH_REQUEST(NS(b'foo') + NS(b'service') +\n                                                 NS(b'none'))\n        return d.addCallback(self._checkFailed)\n\n\n    def test_successfulPasswordAuthentication(self):\n        \"\"\"\n        When provided with correct password authentication information, the\n        server should respond by sending a MSG_USERAUTH_SUCCESS message with\n        no other data.\n\n        See RFC 4252, Section 5.1.\n        \"\"\"\n        packet = b''.join([NS(b'foo'), NS(b'none'), NS(b'password'), chr(0),\n                           NS(b'foo')])\n        d = self.authServer.ssh_USERAUTH_REQUEST(packet)\n        def check(ignored):\n            self.assertEqual(\n                self.authServer.transport.packets,\n                [(userauth.MSG_USERAUTH_SUCCESS, b'')])\n        return d.addCallback(check)\n\n\n    def test_failedPasswordAuthentication(self):\n        \"\"\"\n        When provided with invalid authentication details, the server should\n        respond by sending a MSG_USERAUTH_FAILURE message which states whether\n        the authentication was partially successful, and provides other, open\n        options for authentication.\n\n        See RFC 4252, Section 5.1.\n        \"\"\"\n        # packet = username, next_service, authentication type, FALSE, password\n        packet = b''.join([NS(b'foo'), NS(b'none'), NS(b'password'), chr(0),\n                           NS(b'bar')])\n        self.authServer.clock = task.Clock()\n        d = self.authServer.ssh_USERAUTH_REQUEST(packet)\n        self.assertEqual(self.authServer.transport.packets, [])\n        self.authServer.clock.advance(2)\n        return d.addCallback(self._checkFailed)\n\n\n    def test_successfulPrivateKeyAuthentication(self):\n        \"\"\"\n        Test that private key authentication completes successfully,\n        \"\"\"\n        blob = keys.Key.fromString(keydata.publicRSA_openssh).blob()\n        obj = keys.Key.fromString(keydata.privateRSA_openssh)\n        packet = (NS(b'foo') + NS(b'none') + NS(b'publickey') + b'\\xff'\n                + NS(obj.sshType()) + NS(blob))\n        self.authServer.transport.sessionID = b'test'\n        signature = obj.sign(NS(b'test') + chr(userauth.MSG_USERAUTH_REQUEST)\n                + packet)\n        packet += NS(signature)\n        d = self.authServer.ssh_USERAUTH_REQUEST(packet)\n        def check(ignored):\n            self.assertEqual(self.authServer.transport.packets,\n                    [(userauth.MSG_USERAUTH_SUCCESS, b'')])\n        return d.addCallback(check)\n\n\n    def test_requestRaisesConchError(self):\n        \"\"\"\n        ssh_USERAUTH_REQUEST should raise a ConchError if tryAuth returns\n        None. Added to catch a bug noticed by pyflakes.\n        \"\"\"\n        d = defer.Deferred()\n\n        def mockCbFinishedAuth(self, ignored):\n            self.fail('request should have raised ConochError')\n\n        def mockTryAuth(kind, user, data):\n            return None\n\n        def mockEbBadAuth(reason):\n            d.errback(reason.value)\n\n        self.patch(self.authServer, 'tryAuth', mockTryAuth)\n        self.patch(self.authServer, '_cbFinishedAuth', mockCbFinishedAuth)\n        self.patch(self.authServer, '_ebBadAuth', mockEbBadAuth)\n\n        packet = NS(b'user') + NS(b'none') + NS(b'public-key') + NS(b'data')\n        # If an error other than ConchError is raised, this will trigger an\n        # exception.\n        self.authServer.ssh_USERAUTH_REQUEST(packet)\n        return self.assertFailure(d, ConchError)\n\n\n    def test_verifyValidPrivateKey(self):\n        \"\"\"\n        Test that verifying a valid private key works.\n        \"\"\"\n        blob = keys.Key.fromString(keydata.publicRSA_openssh).blob()\n        packet = (NS(b'foo') + NS(b'none') + NS(b'publickey') + b'\\x00'\n                + NS(b'ssh-rsa') + NS(blob))\n        d = self.authServer.ssh_USERAUTH_REQUEST(packet)\n        def check(ignored):\n            self.assertEqual(self.authServer.transport.packets,\n                    [(userauth.MSG_USERAUTH_PK_OK, NS(b'ssh-rsa') + NS(blob))])\n        return d.addCallback(check)\n\n\n    def test_failedPrivateKeyAuthenticationWithoutSignature(self):\n        \"\"\"\n        Test that private key authentication fails when the public key\n        is invalid.\n        \"\"\"\n        blob = keys.Key.fromString(keydata.publicDSA_openssh).blob()\n        packet = (NS(b'foo') + NS(b'none') + NS(b'publickey') + b'\\x00'\n                + NS(b'ssh-dsa') + NS(blob))\n        d = self.authServer.ssh_USERAUTH_REQUEST(packet)\n        return d.addCallback(self._checkFailed)\n\n\n    def test_failedPrivateKeyAuthenticationWithSignature(self):\n        \"\"\"\n        Test that private key authentication fails when the public key\n        is invalid.\n        \"\"\"\n        blob = keys.Key.fromString(keydata.publicRSA_openssh).blob()\n        obj = keys.Key.fromString(keydata.privateRSA_openssh)\n        packet = (NS(b'foo') + NS(b'none') + NS(b'publickey') + b'\\xff'\n                + NS(b'ssh-rsa') + NS(blob) + NS(obj.sign(blob)))\n        self.authServer.transport.sessionID = b'test'\n        d = self.authServer.ssh_USERAUTH_REQUEST(packet)\n        return d.addCallback(self._checkFailed)\n\n\n    def test_unsupported_publickey(self):\n        \"\"\"\n        Private key authentication fails when the public key type is\n        unsupported or the public key is corrupt.\n        \"\"\"\n        blob = keys.Key.fromString(keydata.publicDSA_openssh).blob()\n\n        # Change the blob to a bad type\n        blob = NS(b'ssh-bad-type') + blob[11:]\n\n        packet = (NS(b'foo') + NS(b'none') + NS(b'publickey') + b'\\x00'\n                  + NS(b'ssh-rsa') + NS(blob))\n        d = self.authServer.ssh_USERAUTH_REQUEST(packet)\n\n        return d.addCallback(self._checkFailed)\n\n\n    def test_ignoreUnknownCredInterfaces(self):\n        \"\"\"\n        L{SSHUserAuthServer} sets up\n        C{SSHUserAuthServer.supportedAuthentications} by checking the portal's\n        credentials interfaces and mapping them to SSH authentication method\n        strings.  If the Portal advertises an interface that\n        L{SSHUserAuthServer} can't map, it should be ignored.  This is a white\n        box test.\n        \"\"\"\n        server = userauth.SSHUserAuthServer()\n        server.transport = FakeTransport(self.portal)\n        self.portal.registerChecker(AnonymousChecker())\n        server.serviceStarted()\n        server.serviceStopped()\n        server.supportedAuthentications.sort() # give a consistent order\n        self.assertEqual(server.supportedAuthentications,\n                          [b'password', b'publickey'])\n\n\n    def test_removePasswordIfUnencrypted(self):\n        \"\"\"\n        Test that the userauth service does not advertise password\n        authentication if the password would be send in cleartext.\n        \"\"\"\n        self.assertIn(b'password', self.authServer.supportedAuthentications)\n        # no encryption\n        clearAuthServer = userauth.SSHUserAuthServer()\n        clearAuthServer.transport = FakeTransport(self.portal)\n        clearAuthServer.transport.isEncrypted = lambda x: False\n        clearAuthServer.serviceStarted()\n        clearAuthServer.serviceStopped()\n        self.assertNotIn(b'password', clearAuthServer.supportedAuthentications)\n        # only encrypt incoming (the direction the password is sent)\n        halfAuthServer = userauth.SSHUserAuthServer()\n        halfAuthServer.transport = FakeTransport(self.portal)\n        halfAuthServer.transport.isEncrypted = lambda x: x == 'in'\n        halfAuthServer.serviceStarted()\n        halfAuthServer.serviceStopped()\n        self.assertIn(b'password', halfAuthServer.supportedAuthentications)\n\n\n    def test_unencryptedConnectionWithoutPasswords(self):\n        \"\"\"\n        If the L{SSHUserAuthServer} is not advertising passwords, then an\n        unencrypted connection should not cause any warnings or exceptions.\n        This is a white box test.\n        \"\"\"\n        # create a Portal without password authentication\n        portal = Portal(self.realm)\n        portal.registerChecker(PrivateKeyChecker())\n\n        # no encryption\n        clearAuthServer = userauth.SSHUserAuthServer()\n        clearAuthServer.transport = FakeTransport(portal)\n        clearAuthServer.transport.isEncrypted = lambda x: False\n        clearAuthServer.serviceStarted()\n        clearAuthServer.serviceStopped()\n        self.assertEqual(clearAuthServer.supportedAuthentications,\n                          [b'publickey'])\n\n        # only encrypt incoming (the direction the password is sent)\n        halfAuthServer = userauth.SSHUserAuthServer()\n        halfAuthServer.transport = FakeTransport(portal)\n        halfAuthServer.transport.isEncrypted = lambda x: x == 'in'\n        halfAuthServer.serviceStarted()\n        halfAuthServer.serviceStopped()\n        self.assertEqual(clearAuthServer.supportedAuthentications,\n                          [b'publickey'])\n\n\n    def test_loginTimeout(self):\n        \"\"\"\n        Test that the login times out.\n        \"\"\"\n        timeoutAuthServer = userauth.SSHUserAuthServer()\n        timeoutAuthServer.clock = task.Clock()\n        timeoutAuthServer.transport = FakeTransport(self.portal)\n        timeoutAuthServer.serviceStarted()\n        timeoutAuthServer.clock.advance(11 * 60 * 60)\n        timeoutAuthServer.serviceStopped()\n        self.assertEqual(timeoutAuthServer.transport.packets,\n                [(transport.MSG_DISCONNECT,\n                b'\\x00' * 3 +\n                chr(transport.DISCONNECT_NO_MORE_AUTH_METHODS_AVAILABLE) +\n                NS(b\"you took too long\") + NS(b''))])\n        self.assertTrue(timeoutAuthServer.transport.lostConnection)\n\n\n    def test_cancelLoginTimeout(self):\n        \"\"\"\n        Test that stopping the service also stops the login timeout.\n        \"\"\"\n        timeoutAuthServer = userauth.SSHUserAuthServer()\n        timeoutAuthServer.clock = task.Clock()\n        timeoutAuthServer.transport = FakeTransport(self.portal)\n        timeoutAuthServer.serviceStarted()\n        timeoutAuthServer.serviceStopped()\n        timeoutAuthServer.clock.advance(11 * 60 * 60)\n        self.assertEqual(timeoutAuthServer.transport.packets, [])\n        self.assertFalse(timeoutAuthServer.transport.lostConnection)\n\n\n    def test_tooManyAttempts(self):\n        \"\"\"\n        Test that the server disconnects if the client fails authentication\n        too many times.\n        \"\"\"\n        packet = b''.join([NS(b'foo'), NS(b'none'), NS(b'password'), chr(0),\n                           NS(b'bar')])\n        self.authServer.clock = task.Clock()\n        for i in range(21):\n            d = self.authServer.ssh_USERAUTH_REQUEST(packet)\n            self.authServer.clock.advance(2)\n        def check(ignored):\n            self.assertEqual(self.authServer.transport.packets[-1],\n                (transport.MSG_DISCONNECT,\n                b'\\x00' * 3 +\n                chr(transport.DISCONNECT_NO_MORE_AUTH_METHODS_AVAILABLE) +\n                NS(b\"too many bad auths\") + NS(b'')))\n        return d.addCallback(check)\n\n\n    def test_failIfUnknownService(self):\n        \"\"\"\n        If the user requests a service that we don't support, the\n        authentication should fail.\n        \"\"\"\n        packet = NS(b'foo') + NS(b'') + NS(b'password') + chr(0) + NS(b'foo')\n        self.authServer.clock = task.Clock()\n        d = self.authServer.ssh_USERAUTH_REQUEST(packet)\n        return d.addCallback(self._checkFailed)\n\n\n    def test_tryAuthEdgeCases(self):\n        \"\"\"\n        tryAuth() has two edge cases that are difficult to reach.\n\n        1) an authentication method auth_* returns None instead of a Deferred.\n        2) an authentication type that is defined does not have a matching\n           auth_* method.\n\n        Both these cases should return a Deferred which fails with a\n        ConchError.\n        \"\"\"\n        def mockAuth(packet):\n            return None\n\n        self.patch(self.authServer, 'auth_publickey', mockAuth) # first case\n        self.patch(self.authServer, 'auth_password', None) # second case\n\n        def secondTest(ignored):\n            d2 = self.authServer.tryAuth(b'password', None, None)\n            return self.assertFailure(d2, ConchError)\n\n        d1 = self.authServer.tryAuth(b'publickey', None, None)\n        return self.assertFailure(d1, ConchError).addCallback(secondTest)\n\n\n\nclass SSHUserAuthClientTests(unittest.TestCase):\n    \"\"\"\n    Tests for SSHUserAuthClient.\n    \"\"\"\n\n    if keys is None:\n        skip = \"cannot run without cryptography\"\n\n\n    def setUp(self):\n        self.authClient = ClientUserAuth(b'foo', FakeTransport.Service())\n        self.authClient.transport = FakeTransport(None)\n        self.authClient.transport.sessionID = b'test'\n        self.authClient.serviceStarted()\n\n\n    def tearDown(self):\n        self.authClient.serviceStopped()\n        self.authClient = None\n\n\n    def test_init(self):\n        \"\"\"\n        Test that client is initialized properly.\n        \"\"\"\n        self.assertEqual(self.authClient.user, b'foo')\n        self.assertEqual(self.authClient.instance.name, b'nancy')\n        self.assertEqual(self.authClient.transport.packets,\n                [(userauth.MSG_USERAUTH_REQUEST, NS(b'foo') + NS(b'nancy')\n                    + NS(b'none'))])\n\n\n    def test_USERAUTH_SUCCESS(self):\n        \"\"\"\n        Test that the client succeeds properly.\n        \"\"\"\n        instance = [None]\n        def stubSetService(service):\n            instance[0] = service\n        self.authClient.transport.setService = stubSetService\n        self.authClient.ssh_USERAUTH_SUCCESS(b'')\n        self.assertEqual(instance[0], self.authClient.instance)\n\n\n    def test_publickey(self):\n        \"\"\"\n        Test that the client can authenticate with a public key.\n        \"\"\"\n        self.authClient.ssh_USERAUTH_FAILURE(NS(b'publickey') + b'\\x00')\n        self.assertEqual(self.authClient.transport.packets[-1],\n                (userauth.MSG_USERAUTH_REQUEST, NS(b'foo') + NS(b'nancy')\n                    + NS(b'publickey') + b'\\x00' + NS(b'ssh-dss')\n                    + NS(keys.Key.fromString(\n                        keydata.publicDSA_openssh).blob())))\n       # that key isn't good\n        self.authClient.ssh_USERAUTH_FAILURE(NS(b'publickey') + b'\\x00')\n        blob = NS(keys.Key.fromString(keydata.publicRSA_openssh).blob())\n        self.assertEqual(self.authClient.transport.packets[-1],\n                (userauth.MSG_USERAUTH_REQUEST, (NS(b'foo') + NS(b'nancy')\n                    + NS(b'publickey') + b'\\x00' + NS(b'ssh-rsa') + blob)))\n        self.authClient.ssh_USERAUTH_PK_OK(NS(b'ssh-rsa')\n            + NS(keys.Key.fromString(keydata.publicRSA_openssh).blob()))\n        sigData = (NS(self.authClient.transport.sessionID)\n                + chr(userauth.MSG_USERAUTH_REQUEST) + NS(b'foo')\n                + NS(b'nancy') + NS(b'publickey') + b'\\x01' + NS(b'ssh-rsa')\n                + blob)\n        obj = keys.Key.fromString(keydata.privateRSA_openssh)\n        self.assertEqual(self.authClient.transport.packets[-1],\n                (userauth.MSG_USERAUTH_REQUEST, NS(b'foo') + NS(b'nancy')\n                    + NS(b'publickey') + b'\\x01' + NS(b'ssh-rsa') + blob\n                    + NS(obj.sign(sigData))))\n\n\n    def test_publickey_without_privatekey(self):\n        \"\"\"\n        If the SSHUserAuthClient doesn't return anything from signData,\n        the client should start the authentication over again by requesting\n        'none' authentication.\n        \"\"\"\n        authClient = ClientAuthWithoutPrivateKey(b'foo',\n                                                 FakeTransport.Service())\n\n        authClient.transport = FakeTransport(None)\n        authClient.transport.sessionID = b'test'\n        authClient.serviceStarted()\n        authClient.tryAuth(b'publickey')\n        authClient.transport.packets = []\n        self.assertIsNone(authClient.ssh_USERAUTH_PK_OK(b''))\n        self.assertEqual(authClient.transport.packets, [\n                (userauth.MSG_USERAUTH_REQUEST, NS(b'foo') + NS(b'nancy') +\n                 NS(b'none'))])\n\n\n    def test_no_publickey(self):\n        \"\"\"\n        If there's no public key, auth_publickey should return a Deferred\n        called back with a False value.\n        \"\"\"\n        self.authClient.getPublicKey = lambda x: None\n        d = self.authClient.tryAuth(b'publickey')\n        def check(result):\n            self.assertFalse(result)\n        return d.addCallback(check)\n\n\n    def test_password(self):\n        \"\"\"\n        Test that the client can authentication with a password.  This\n        includes changing the password.\n        \"\"\"\n        self.authClient.ssh_USERAUTH_FAILURE(NS(b'password') + b'\\x00')\n        self.assertEqual(self.authClient.transport.packets[-1],\n                (userauth.MSG_USERAUTH_REQUEST, NS(b'foo') + NS(b'nancy')\n                    + NS(b'password') + b'\\x00' + NS(b'foo')))\n        self.authClient.ssh_USERAUTH_PK_OK(NS(b'') + NS(b''))\n        self.assertEqual(self.authClient.transport.packets[-1],\n                (userauth.MSG_USERAUTH_REQUEST, NS(b'foo') + NS(b'nancy')\n                    + NS(b'password') + b'\\xff' + NS(b'foo') * 2))\n\n\n    def test_no_password(self):\n        \"\"\"\n        If getPassword returns None, tryAuth should return False.\n        \"\"\"\n        self.authClient.getPassword = lambda: None\n        self.assertFalse(self.authClient.tryAuth(b'password'))\n\n\n    def test_keyboardInteractive(self):\n        \"\"\"\n        Make sure that the client can authenticate with the keyboard\n        interactive method.\n        \"\"\"\n        self.authClient.ssh_USERAUTH_PK_OK_keyboard_interactive(\n            NS(b'') + NS(b'') + NS(b'') + b'\\x00\\x00\\x00\\x01' +\n            NS(b'Password: ') + b'\\x00')\n        self.assertEqual(\n            self.authClient.transport.packets[-1],\n            (userauth.MSG_USERAUTH_INFO_RESPONSE,\n             b'\\x00\\x00\\x00\\x02' + NS(b'foo') + NS(b'foo')))\n\n\n    def test_USERAUTH_PK_OK_unknown_method(self):\n        \"\"\"\n        If C{SSHUserAuthClient} gets a MSG_USERAUTH_PK_OK packet when it's not\n        expecting it, it should fail the current authentication and move on to\n        the next type.\n        \"\"\"\n        self.authClient.lastAuth = b'unknown'\n        self.authClient.transport.packets = []\n        self.authClient.ssh_USERAUTH_PK_OK(b'')\n        self.assertEqual(self.authClient.transport.packets,\n                          [(userauth.MSG_USERAUTH_REQUEST, NS(b'foo') +\n                            NS(b'nancy') + NS(b'none'))])\n\n\n    def test_USERAUTH_FAILURE_sorting(self):\n        \"\"\"\n        ssh_USERAUTH_FAILURE should sort the methods by their position\n        in SSHUserAuthClient.preferredOrder.  Methods that are not in\n        preferredOrder should be sorted at the end of that list.\n        \"\"\"\n        def auth_firstmethod():\n            self.authClient.transport.sendPacket(255, b'here is data')\n        def auth_anothermethod():\n            self.authClient.transport.sendPacket(254, b'other data')\n            return True\n        self.authClient.auth_firstmethod = auth_firstmethod\n        self.authClient.auth_anothermethod = auth_anothermethod\n\n        # although they shouldn't get called, method callbacks auth_* MUST\n        # exist in order for the test to work properly.\n        self.authClient.ssh_USERAUTH_FAILURE(NS(b'anothermethod,password') +\n                                             b'\\x00')\n        # should send password packet\n        self.assertEqual(self.authClient.transport.packets[-1],\n                (userauth.MSG_USERAUTH_REQUEST, NS(b'foo') + NS(b'nancy')\n                    + NS(b'password') + b'\\x00' + NS(b'foo')))\n        self.authClient.ssh_USERAUTH_FAILURE(\n            NS(b'firstmethod,anothermethod,password') + b'\\xff')\n        self.assertEqual(self.authClient.transport.packets[-2:],\n                          [(255, b'here is data'), (254, b'other data')])\n\n\n    def test_disconnectIfNoMoreAuthentication(self):\n        \"\"\"\n        If there are no more available user authentication messages,\n        the SSHUserAuthClient should disconnect with code\n        DISCONNECT_NO_MORE_AUTH_METHODS_AVAILABLE.\n        \"\"\"\n        self.authClient.ssh_USERAUTH_FAILURE(NS(b'password') + b'\\x00')\n        self.authClient.ssh_USERAUTH_FAILURE(NS(b'password') + b'\\xff')\n        self.assertEqual(self.authClient.transport.packets[-1],\n                          (transport.MSG_DISCONNECT, b'\\x00\\x00\\x00\\x0e' +\n                           NS(b'no more authentication methods available') +\n                           b'\\x00\\x00\\x00\\x00'))\n\n\n    def test_ebAuth(self):\n        \"\"\"\n        _ebAuth (the generic authentication error handler) should send\n        a request for the 'none' authentication method.\n        \"\"\"\n        self.authClient.transport.packets = []\n        self.authClient._ebAuth(None)\n        self.assertEqual(self.authClient.transport.packets,\n                [(userauth.MSG_USERAUTH_REQUEST, NS(b'foo') + NS(b'nancy')\n                    + NS(b'none'))])\n\n\n    def test_defaults(self):\n        \"\"\"\n        getPublicKey() should return None.  getPrivateKey() should return a\n        failed Deferred.  getPassword() should return a failed Deferred.\n        getGenericAnswers() should return a failed Deferred.\n        \"\"\"\n        authClient = userauth.SSHUserAuthClient(b'foo',\n                                                FakeTransport.Service())\n        self.assertIsNone(authClient.getPublicKey())\n        def check(result):\n            result.trap(NotImplementedError)\n            d = authClient.getPassword()\n            return d.addCallback(self.fail).addErrback(check2)\n        def check2(result):\n            result.trap(NotImplementedError)\n            d = authClient.getGenericAnswers(None, None, None)\n            return d.addCallback(self.fail).addErrback(check3)\n        def check3(result):\n            result.trap(NotImplementedError)\n        d = authClient.getPrivateKey()\n        return d.addCallback(self.fail).addErrback(check)\n\n\n\nclass LoopbackTests(unittest.TestCase):\n\n    if keys is None:\n        skip = \"cannot run without cryptography or PyASN1\"\n\n\n    class Factory:\n        class Service:\n            name = b'TestService'\n\n\n            def serviceStarted(self):\n                self.transport.loseConnection()\n\n\n            def serviceStopped(self):\n                pass\n\n\n        def getService(self, avatar, name):\n            return self.Service\n\n\n    def test_loopback(self):\n        \"\"\"\n        Test that the userauth server and client play nicely with each other.\n        \"\"\"\n        server = userauth.SSHUserAuthServer()\n        client = ClientUserAuth(b'foo', self.Factory.Service())\n\n        # set up transports\n        server.transport = transport.SSHTransportBase()\n        server.transport.service = server\n        server.transport.isEncrypted = lambda x: True\n        client.transport = transport.SSHTransportBase()\n        client.transport.service = client\n        server.transport.sessionID = client.transport.sessionID = b''\n        # don't send key exchange packet\n        server.transport.sendKexInit = client.transport.sendKexInit = \\\n                lambda: None\n\n        # set up server authentication\n        server.transport.factory = self.Factory()\n        server.passwordDelay = 0 # remove bad password delay\n        realm = Realm()\n        portal = Portal(realm)\n        checker = SSHProtocolChecker()\n        checker.registerChecker(PasswordChecker())\n        checker.registerChecker(PrivateKeyChecker())\n        checker.areDone = lambda aId: (\n            len(checker.successfulCredentials[aId]) == 2)\n        portal.registerChecker(checker)\n        server.transport.factory.portal = portal\n\n        d = loopback.loopbackAsync(server.transport, client.transport)\n        server.transport.transport.logPrefix = lambda: '_ServerLoopback'\n        client.transport.transport.logPrefix = lambda: '_ClientLoopback'\n\n        server.serviceStarted()\n        client.serviceStarted()\n\n        def check(ignored):\n            self.assertEqual(server.transport.service.name, b'TestService')\n        return d.addCallback(check)\n\n\n\nclass ModuleInitializationTests(unittest.TestCase):\n    if keys is None:\n        skip = \"cannot run without cryptography or PyASN1\"\n\n\n    def test_messages(self):\n        # Several message types have value 60, check that MSG_USERAUTH_PK_OK\n        # is always the one which is mapped.\n        self.assertEqual(userauth.SSHUserAuthServer.protocolMessages[60],\n                         'MSG_USERAUTH_PK_OK')\n        self.assertEqual(userauth.SSHUserAuthClient.protocolMessages[60],\n                         'MSG_USERAUTH_PK_OK')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/test/test_window.py",
    "content": "\n\"\"\"\nTests for the insults windowing module, L{twisted.conch.insults.window}.\n\"\"\"\n\nfrom twisted.trial.unittest import TestCase\n\nfrom twisted.conch.insults.window import TopWindow, ScrolledArea, TextOutput\n\n\nclass TopWindowTests(TestCase):\n    \"\"\"\n    Tests for L{TopWindow}, the root window container class.\n    \"\"\"\n\n    def test_paintScheduling(self):\n        \"\"\"\n        Verify that L{TopWindow.repaint} schedules an actual paint to occur\n        using the scheduling object passed to its initializer.\n        \"\"\"\n        paints = []\n        scheduled = []\n        root = TopWindow(lambda: paints.append(None), scheduled.append)\n\n        # Nothing should have happened yet.\n        self.assertEqual(paints, [])\n        self.assertEqual(scheduled, [])\n\n        # Cause a paint to be scheduled.\n        root.repaint()\n        self.assertEqual(paints, [])\n        self.assertEqual(len(scheduled), 1)\n\n        # Do another one to verify nothing else happens as long as the previous\n        # one is still pending.\n        root.repaint()\n        self.assertEqual(paints, [])\n        self.assertEqual(len(scheduled), 1)\n\n        # Run the actual paint call.\n        scheduled.pop()()\n        self.assertEqual(len(paints), 1)\n        self.assertEqual(scheduled, [])\n\n        # Do one more to verify that now that the previous one is finished\n        # future paints will succeed.\n        root.repaint()\n        self.assertEqual(len(paints), 1)\n        self.assertEqual(len(scheduled), 1)\n\n\n\nclass ScrolledAreaTests(TestCase):\n    \"\"\"\n    Tests for L{ScrolledArea}, a widget which creates a viewport containing\n    another widget and can reposition that viewport using scrollbars.\n    \"\"\"\n    def test_parent(self):\n        \"\"\"\n        The parent of the widget passed to L{ScrolledArea} is set to a new\n        L{Viewport} created by the L{ScrolledArea} which itself has the\n        L{ScrolledArea} instance as its parent.\n        \"\"\"\n        widget = TextOutput()\n        scrolled = ScrolledArea(widget)\n        self.assertIs(widget.parent, scrolled._viewport)\n        self.assertIs(scrolled._viewport.parent, scrolled)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ttymodes.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n# \n\nimport tty\n# this module was autogenerated.\n\nVINTR = 1\nVQUIT = 2\nVERASE = 3\nVKILL = 4\nVEOF = 5\nVEOL = 6\nVEOL2 = 7\nVSTART = 8\nVSTOP = 9\nVSUSP = 10\nVDSUSP = 11\nVREPRINT = 12\nVWERASE = 13\nVLNEXT = 14\nVFLUSH = 15\nVSWTCH = 16\nVSTATUS = 17\nVDISCARD = 18\nIGNPAR = 30\nPARMRK = 31\nINPCK = 32\nISTRIP = 33\nINLCR = 34\nIGNCR = 35\nICRNL = 36\nIUCLC = 37\nIXON = 38\nIXANY = 39\nIXOFF = 40\nIMAXBEL = 41\nISIG = 50\nICANON = 51\nXCASE = 52\nECHO = 53\nECHOE = 54\nECHOK = 55\nECHONL = 56\nNOFLSH = 57\nTOSTOP = 58\nIEXTEN = 59\nECHOCTL = 60\nECHOKE = 61\nPENDIN = 62\nOPOST = 70\nOLCUC = 71\nONLCR = 72\nOCRNL = 73\nONOCR = 74\nONLRET = 75\nCS7 = 90\nCS8 = 91\nPARENB = 92\nPARODD = 93\nTTY_OP_ISPEED = 128\nTTY_OP_OSPEED = 129\n\nTTYMODES = {\n    1 : 'VINTR',\n    2 : 'VQUIT',\n    3 : 'VERASE',\n    4 : 'VKILL',\n    5 : 'VEOF',\n    6 : 'VEOL',\n    7 : 'VEOL2',\n    8 : 'VSTART',\n    9 : 'VSTOP',\n    10 : 'VSUSP',\n    11 : 'VDSUSP',\n    12 : 'VREPRINT',\n    13 : 'VWERASE',\n    14 : 'VLNEXT',\n    15 : 'VFLUSH',\n    16 : 'VSWTCH',\n    17 : 'VSTATUS',\n    18 : 'VDISCARD',\n    30 : (tty.IFLAG, 'IGNPAR'),\n    31 : (tty.IFLAG, 'PARMRK'),\n    32 : (tty.IFLAG, 'INPCK'),\n    33 : (tty.IFLAG, 'ISTRIP'),\n    34 : (tty.IFLAG, 'INLCR'),\n    35 : (tty.IFLAG, 'IGNCR'),\n    36 : (tty.IFLAG, 'ICRNL'),\n    37 : (tty.IFLAG, 'IUCLC'),\n    38 : (tty.IFLAG, 'IXON'),\n    39 : (tty.IFLAG, 'IXANY'),\n    40 : (tty.IFLAG, 'IXOFF'),\n    41 : (tty.IFLAG, 'IMAXBEL'),\n    50 : (tty.LFLAG, 'ISIG'),\n    51 : (tty.LFLAG, 'ICANON'),\n    52 : (tty.LFLAG, 'XCASE'),\n    53 : (tty.LFLAG, 'ECHO'),\n    54 : (tty.LFLAG, 'ECHOE'),\n    55 : (tty.LFLAG, 'ECHOK'),\n    56 : (tty.LFLAG, 'ECHONL'),\n    57 : (tty.LFLAG, 'NOFLSH'),\n    58 : (tty.LFLAG, 'TOSTOP'),\n    59 : (tty.LFLAG, 'IEXTEN'),\n    60 : (tty.LFLAG, 'ECHOCTL'),\n    61 : (tty.LFLAG, 'ECHOKE'),\n    62 : (tty.LFLAG, 'PENDIN'),\n    70 : (tty.OFLAG, 'OPOST'),\n    71 : (tty.OFLAG, 'OLCUC'),\n    72 : (tty.OFLAG, 'ONLCR'),\n    73 : (tty.OFLAG, 'OCRNL'),\n    74 : (tty.OFLAG, 'ONOCR'),\n    75 : (tty.OFLAG, 'ONLRET'),\n#   90 : (tty.CFLAG, 'CS7'),\n#   91 : (tty.CFLAG, 'CS8'),\n    92 : (tty.CFLAG, 'PARENB'),\n    93 : (tty.CFLAG, 'PARODD'),\n    128 : 'ISPEED',\n    129 : 'OSPEED'\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ui/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n#\n\n\n\"\"\"\ntwisted.conch.ui is home to the UI elements for tkconch.\n\nMaintainer: Paul Swartz\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ui/ansi.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n#\n\"\"\"Module to parse ANSI escape sequences\n\nMaintainer: Jean-Paul Calderone\n\"\"\"\n\nimport string\n\n# Twisted imports\nfrom twisted.python import log\n\nclass ColorText:\n    \"\"\"\n    Represents an element of text along with the texts colors and\n    additional attributes.\n    \"\"\"\n\n    # The colors to use\n    COLORS = ('b', 'r', 'g', 'y', 'l', 'm', 'c', 'w')\n    BOLD_COLORS = tuple([x.upper() for x in COLORS])\n    BLACK, RED, GREEN, YELLOW, BLUE, MAGENTA, CYAN, WHITE = range(len(COLORS))\n\n    # Color names\n    COLOR_NAMES = (\n        'Black', 'Red', 'Green', 'Yellow', 'Blue', 'Magenta', 'Cyan', 'White'\n    )\n\n    def __init__(self, text, fg, bg, display, bold, underline, flash, reverse):\n        self.text, self.fg, self.bg = text, fg, bg\n        self.display = display\n        self.bold = bold\n        self.underline = underline\n        self.flash = flash\n        self.reverse = reverse\n        if self.reverse:\n            self.fg, self.bg = self.bg, self.fg\n\n\nclass AnsiParser:\n    \"\"\"\n    Parser class for ANSI codes.\n    \"\"\"\n\n    # Terminators for cursor movement ansi controls - unsupported\n    CURSOR_SET = ('H', 'f', 'A', 'B', 'C', 'D', 'R', 's', 'u', 'd','G')\n\n    # Terminators for erasure ansi controls - unsupported\n    ERASE_SET = ('J', 'K', 'P')\n\n    # Terminators for mode change ansi controls - unsupported\n    MODE_SET = ('h', 'l')\n\n    # Terminators for keyboard assignment ansi controls - unsupported\n    ASSIGN_SET = ('p',)\n\n    # Terminators for color change ansi controls - supported\n    COLOR_SET = ('m',)\n\n    SETS = (CURSOR_SET, ERASE_SET, MODE_SET, ASSIGN_SET, COLOR_SET)\n\n    def __init__(self, defaultFG, defaultBG):\n        self.defaultFG, self.defaultBG = defaultFG, defaultBG\n        self.currentFG, self.currentBG = self.defaultFG, self.defaultBG\n        self.bold, self.flash, self.underline, self.reverse = 0, 0, 0, 0\n        self.display = 1\n        self.prepend = ''\n\n\n    def stripEscapes(self, string):\n        \"\"\"\n        Remove all ANSI color escapes from the given string.\n        \"\"\"\n        result = ''\n        show = 1\n        i = 0\n        L = len(string)\n        while i < L:\n            if show == 0 and string[i] in _sets:\n                show = 1\n            elif show:\n                n = string.find('\\x1B', i)\n                if n == -1:\n                    return result + string[i:]\n                else:\n                    result = result + string[i:n]\n                    i = n\n                    show = 0\n            i = i + 1\n        return result\n\n    def writeString(self, colorstr):\n        pass\n\n    def parseString(self, str):\n        \"\"\"\n        Turn a string input into a list of L{ColorText} elements.\n        \"\"\"\n\n        if self.prepend:\n            str = self.prepend + str\n            self.prepend = ''\n        parts = str.split('\\x1B')\n\n        if len(parts) == 1:\n            self.writeString(self.formatText(parts[0]))\n        else:\n            self.writeString(self.formatText(parts[0]))\n            for s in parts[1:]:\n                L = len(s)\n                i = 0\n                type = None\n                while i < L:\n                    if s[i] not in string.digits+'[;?':\n                        break\n                    i+=1\n                if not s:\n                    self.prepend = '\\x1b'\n                    return\n                if s[0]!='[':\n                    self.writeString(self.formatText(s[i+1:]))\n                    continue\n                else:\n                    s=s[1:]\n                    i-=1\n                if i==L-1:\n                    self.prepend = '\\x1b['\n                    return\n                type = _setmap.get(s[i], None)\n                if type is None:\n                    continue\n\n                if type == AnsiParser.COLOR_SET:\n                    self.parseColor(s[:i + 1])\n                    s = s[i + 1:]\n                    self.writeString(self.formatText(s))\n                elif type == AnsiParser.CURSOR_SET:\n                    cursor, s = s[:i+1], s[i+1:]\n                    self.parseCursor(cursor)\n                    self.writeString(self.formatText(s))\n                elif type == AnsiParser.ERASE_SET:\n                    erase, s = s[:i+1], s[i+1:]\n                    self.parseErase(erase)\n                    self.writeString(self.formatText(s))\n                elif type == AnsiParser.MODE_SET:\n                    s = s[i+1:]\n                    #self.parseErase('2J')\n                    self.writeString(self.formatText(s))\n                elif i == L:\n                    self.prepend = '\\x1B[' + s\n                else:\n                    log.msg('Unhandled ANSI control type: %c' % (s[i],))\n                    s = s[i + 1:]\n                    self.writeString(self.formatText(s))\n\n    def parseColor(self, str):\n        \"\"\"\n        Handle a single ANSI color sequence\n        \"\"\"\n        # Drop the trailing 'm'\n        str = str[:-1]\n\n        if not str:\n            str = '0'\n\n        try:\n            parts = map(int, str.split(';'))\n        except ValueError:\n            log.msg('Invalid ANSI color sequence (%d): %s' % (len(str), str))\n            self.currentFG, self.currentBG = self.defaultFG, self.defaultBG\n            return\n\n        for x in parts:\n            if x == 0:\n                self.currentFG, self.currentBG = self.defaultFG, self.defaultBG\n                self.bold, self.flash, self.underline, self.reverse = 0, 0, 0, 0\n                self.display = 1\n            elif x == 1:\n                self.bold = 1\n            elif 30 <= x <= 37:\n                self.currentFG = x - 30\n            elif 40 <= x <= 47:\n                self.currentBG = x - 40\n            elif x == 39:\n                self.currentFG = self.defaultFG\n            elif x == 49:\n                self.currentBG = self.defaultBG\n            elif x == 4:\n                self.underline = 1\n            elif x == 5:\n                self.flash = 1\n            elif x == 7:\n                self.reverse = 1\n            elif x == 8:\n                self.display = 0\n            elif x == 22:\n                self.bold = 0\n            elif x == 24:\n                self.underline = 0\n            elif x == 25:\n                self.blink = 0\n            elif x == 27:\n                self.reverse = 0\n            elif x == 28:\n                self.display = 1\n            else:\n                log.msg('Unrecognised ANSI color command: %d' % (x,))\n\n    def parseCursor(self, cursor):\n        pass\n\n    def parseErase(self, erase):\n        pass\n\n\n    def pickColor(self, value, mode, BOLD = ColorText.BOLD_COLORS):\n        if mode:\n            return ColorText.COLORS[value]\n        else:\n            return self.bold and BOLD[value] or ColorText.COLORS[value]\n\n\n    def formatText(self, text):\n        return ColorText(\n            text,\n            self.pickColor(self.currentFG, 0),\n            self.pickColor(self.currentBG, 1),\n            self.display, self.bold, self.underline, self.flash, self.reverse\n        )\n\n\n_sets = ''.join(map(''.join, AnsiParser.SETS))\n\n_setmap = {}\nfor s in AnsiParser.SETS:\n    for r in s:\n        _setmap[r] = s\ndel s\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/ui/tkvt100.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n#\n\n\"\"\"Module to emulate a VT100 terminal in Tkinter.\n\nMaintainer: Paul Swartz\n\"\"\"\n\ntry:\n    import tkinter as Tkinter\n    import tkinter.font as tkFont\nexcept ImportError:\n    import Tkinter, tkFont\nimport string\nfrom . import ansi\n\nttyFont = None#tkFont.Font(family = 'Courier', size = 10)\nfontWidth, fontHeight = None,None#max(map(ttyFont.measure, string.letters+string.digits)), int(ttyFont.metrics()['linespace'])\n\ncolorKeys = (\n    'b', 'r', 'g', 'y', 'l', 'm', 'c', 'w',\n    'B', 'R', 'G', 'Y', 'L', 'M', 'C', 'W'\n)\n\ncolorMap = {\n    'b': '#000000', 'r': '#c40000', 'g': '#00c400', 'y': '#c4c400',\n    'l': '#000080', 'm': '#c400c4', 'c': '#00c4c4', 'w': '#c4c4c4',\n    'B': '#626262', 'R': '#ff0000', 'G': '#00ff00', 'Y': '#ffff00',\n    'L': '#0000ff', 'M': '#ff00ff', 'C': '#00ffff', 'W': '#ffffff',\n}\n\nclass VT100Frame(Tkinter.Frame):\n    def __init__(self, *args, **kw):\n        global ttyFont, fontHeight, fontWidth\n        ttyFont = tkFont.Font(family = 'Courier', size = 10)\n        fontWidth = max(map(ttyFont.measure, string.ascii_letters+string.digits))\n        fontHeight = int(ttyFont.metrics()['linespace'])\n        self.width = kw.get('width', 80)\n        self.height = kw.get('height', 25)\n        self.callback = kw['callback']\n        del kw['callback']\n        kw['width'] = w = fontWidth * self.width\n        kw['height'] = h = fontHeight * self.height\n        Tkinter.Frame.__init__(self, *args, **kw)\n        self.canvas = Tkinter.Canvas(bg='#000000', width=w, height=h)\n        self.canvas.pack(side=Tkinter.TOP, fill=Tkinter.BOTH, expand=1)\n        self.canvas.bind('<Key>', self.keyPressed)\n        self.canvas.bind('<1>', lambda x: 'break')\n        self.canvas.bind('<Up>', self.upPressed)\n        self.canvas.bind('<Down>', self.downPressed)\n        self.canvas.bind('<Left>', self.leftPressed)\n        self.canvas.bind('<Right>', self.rightPressed)\n        self.canvas.focus()\n\n        self.ansiParser = ansi.AnsiParser(ansi.ColorText.WHITE, ansi.ColorText.BLACK)\n        self.ansiParser.writeString = self.writeString\n        self.ansiParser.parseCursor = self.parseCursor\n        self.ansiParser.parseErase = self.parseErase\n        #for (a, b) in colorMap.items():\n        #    self.canvas.tag_config(a, foreground=b)\n        #    self.canvas.tag_config('b'+a, background=b)\n        #self.canvas.tag_config('underline', underline=1)\n\n        self.x = 0 \n        self.y = 0\n        self.cursor = self.canvas.create_rectangle(0,0,fontWidth-1,fontHeight-1,fill='green',outline='green')\n\n    def _delete(self, sx, sy, ex, ey):\n        csx = sx*fontWidth + 1\n        csy = sy*fontHeight + 1\n        cex = ex*fontWidth + 3\n        cey = ey*fontHeight + 3\n        items = self.canvas.find_overlapping(csx,csy, cex,cey)\n        for item in items:\n            self.canvas.delete(item)\n\n    def _write(self, ch, fg, bg):\n        if self.x == self.width:\n            self.x = 0\n            self.y+=1\n            if self.y == self.height:\n                [self.canvas.move(x,0,-fontHeight) for x in self.canvas.find_all()]\n                self.y-=1\n        canvasX = self.x*fontWidth + 1\n        canvasY = self.y*fontHeight + 1\n        items = self.canvas.find_overlapping(canvasX, canvasY, canvasX+2, canvasY+2)\n        if items:\n            [self.canvas.delete(item) for item in items]\n        if bg:\n            self.canvas.create_rectangle(canvasX, canvasY, canvasX+fontWidth-1, canvasY+fontHeight-1, fill=bg, outline=bg)\n        self.canvas.create_text(canvasX, canvasY, anchor=Tkinter.NW, font=ttyFont, text=ch, fill=fg)\n        self.x+=1\n            \n    def write(self, data):\n        #print self.x,self.y,repr(data)\n        #if len(data)>5: raw_input()\n        self.ansiParser.parseString(data)\n        self.canvas.delete(self.cursor)\n        canvasX = self.x*fontWidth + 1\n        canvasY = self.y*fontHeight + 1\n        self.cursor = self.canvas.create_rectangle(canvasX,canvasY,canvasX+fontWidth-1,canvasY+fontHeight-1, fill='green', outline='green')\n        self.canvas.lower(self.cursor)\n\n    def writeString(self, i):\n        if not i.display:\n            return\n        fg = colorMap[i.fg]\n        bg = i.bg != 'b' and colorMap[i.bg]\n        for ch in i.text:\n            b = ord(ch)\n            if b == 7: # bell\n                self.bell() \n            elif b == 8: # BS\n                if self.x:\n                    self.x-=1\n            elif b == 9: # TAB\n                [self._write(' ',fg,bg) for index in range(8)]\n            elif b == 10:\n                if self.y == self.height-1:\n                    self._delete(0,0,self.width,0)\n                    [self.canvas.move(x,0,-fontHeight) for x in self.canvas.find_all()]\n                else:   \n                    self.y+=1\n            elif b == 13:\n                self.x = 0\n            elif 32 <= b < 127:\n                self._write(ch, fg, bg)\n\n    def parseErase(self, erase):\n        if ';' in erase:\n            end = erase[-1]\n            parts = erase[:-1].split(';')\n            [self.parseErase(x+end) for x in parts]\n            return\n        start = 0\n        x,y = self.x, self.y\n        if len(erase) > 1:\n            start = int(erase[:-1])\n        if erase[-1] == 'J':\n            if start == 0: \n                self._delete(x,y,self.width,self.height)\n            else:\n                self._delete(0,0,self.width,self.height)\n                self.x = 0\n                self.y = 0 \n        elif erase[-1] == 'K':\n            if start == 0:\n                self._delete(x,y,self.width,y)\n            elif start == 1:\n                self._delete(0,y,x,y)\n                self.x = 0\n            else:\n                self._delete(0,y,self.width,y)\n                self.x = 0\n        elif erase[-1] == 'P':\n            self._delete(x,y,x+start,y)\n\n    def parseCursor(self, cursor):\n        #if ';' in cursor and cursor[-1]!='H':\n        #    end = cursor[-1]\n        #    parts = cursor[:-1].split(';')\n        #    [self.parseCursor(x+end) for x in parts]\n        #    return\n        start = 1\n        if len(cursor) > 1 and cursor[-1]!='H':\n            start = int(cursor[:-1])\n        if cursor[-1] == 'C':\n            self.x+=start\n        elif cursor[-1] == 'D':\n            self.x-=start\n        elif cursor[-1]=='d':\n            self.y=start-1\n        elif cursor[-1]=='G':\n            self.x=start-1\n        elif cursor[-1]=='H':\n            if len(cursor)>1:\n                y,x = map(int, cursor[:-1].split(';'))\n                y-=1\n                x-=1\n            else:\n                x,y=0,0\n            self.x = x\n            self.y = y\n\n    def keyPressed(self, event):\n        if self.callback and event.char:\n            self.callback(event.char)\n        return 'break'\n\n    def upPressed(self, event):\n        self.callback('\\x1bOA')\n\n    def downPressed(self, event):\n        self.callback('\\x1bOB')\n\n    def rightPressed(self, event):\n        self.callback('\\x1bOC')\n\n    def leftPressed(self, event):\n        self.callback('\\x1bOD')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/conch/unix.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nA UNIX SSH server.\n\"\"\"\n\nimport fcntl\nimport grp\nimport os\nimport pty\nimport pwd\nimport socket\nimport struct\nimport time\nimport tty\n\nfrom zope.interface import implementer\n\nfrom twisted.conch import ttymodes\nfrom twisted.conch.avatar import ConchUser\nfrom twisted.conch.error import ConchError\nfrom twisted.conch.ls import lsLine\nfrom twisted.conch.ssh import session, forwarding, filetransfer\nfrom twisted.conch.ssh.filetransfer import (\n    FXF_READ, FXF_WRITE, FXF_APPEND, FXF_CREAT, FXF_TRUNC, FXF_EXCL\n)\nfrom twisted.conch.interfaces import ISession, ISFTPServer, ISFTPFile\nfrom twisted.cred import portal\nfrom twisted.internet.error import ProcessExitedAlready\nfrom twisted.python import components, log\nfrom twisted.python.compat import _bytesChr as chr, nativeString\n\ntry:\n    import utmp\nexcept ImportError:\n    utmp = None\n\n\n\n@implementer(portal.IRealm)\nclass UnixSSHRealm:\n    def requestAvatar(self, username, mind, *interfaces):\n        user = UnixConchUser(username)\n        return interfaces[0], user, user.logout\n\n\n\nclass UnixConchUser(ConchUser):\n\n    def __init__(self, username):\n        ConchUser.__init__(self)\n        self.username = username\n        self.pwdData = pwd.getpwnam(self.username)\n        l = [self.pwdData[3]]\n        for groupname, password, gid, userlist in grp.getgrall():\n            if username in userlist:\n                l.append(gid)\n        self.otherGroups = l\n        self.listeners = {}  # Dict mapping (interface, port) -> listener\n        self.channelLookup.update(\n                {b\"session\": session.SSHSession,\n                 b\"direct-tcpip\": forwarding.openConnectForwardingClient})\n\n        self.subsystemLookup.update(\n                {b\"sftp\": filetransfer.FileTransferServer})\n\n\n    def getUserGroupId(self):\n        return self.pwdData[2:4]\n\n\n    def getOtherGroups(self):\n        return self.otherGroups\n\n\n    def getHomeDir(self):\n        return self.pwdData[5]\n\n\n    def getShell(self):\n        return self.pwdData[6]\n\n\n    def global_tcpip_forward(self, data):\n        hostToBind, portToBind = forwarding.unpackGlobal_tcpip_forward(data)\n        from twisted.internet import reactor\n        try:\n            listener = self._runAsUser(\n                reactor.listenTCP, portToBind,\n                forwarding.SSHListenForwardingFactory(\n                    self.conn,\n                    (hostToBind, portToBind),\n                    forwarding.SSHListenServerForwardingChannel),\n                interface=hostToBind)\n        except:\n            return 0\n        else:\n            self.listeners[(hostToBind, portToBind)] = listener\n            if portToBind == 0:\n                portToBind = listener.getHost()[2]  # The port\n                return 1, struct.pack('>L', portToBind)\n            else:\n                return 1\n\n\n    def global_cancel_tcpip_forward(self, data):\n        hostToBind, portToBind = forwarding.unpackGlobal_tcpip_forward(data)\n        listener = self.listeners.get((hostToBind, portToBind), None)\n        if not listener:\n            return 0\n        del self.listeners[(hostToBind, portToBind)]\n        self._runAsUser(listener.stopListening)\n        return 1\n\n\n    def logout(self):\n        # Remove all listeners.\n        for listener in self.listeners.values():\n            self._runAsUser(listener.stopListening)\n        log.msg(\n            'avatar %s logging out (%i)'\n            % (self.username, len(self.listeners)))\n\n\n    def _runAsUser(self, f, *args, **kw):\n        euid = os.geteuid()\n        egid = os.getegid()\n        groups = os.getgroups()\n        uid, gid = self.getUserGroupId()\n        os.setegid(0)\n        os.seteuid(0)\n        os.setgroups(self.getOtherGroups())\n        os.setegid(gid)\n        os.seteuid(uid)\n        try:\n            f = iter(f)\n        except TypeError:\n            f = [(f, args, kw)]\n        try:\n            for i in f:\n                func = i[0]\n                args = len(i) > 1 and i[1] or ()\n                kw = len(i) > 2 and i[2] or {}\n                r = func(*args, **kw)\n        finally:\n            os.setegid(0)\n            os.seteuid(0)\n            os.setgroups(groups)\n            os.setegid(egid)\n            os.seteuid(euid)\n        return r\n\n\n\n@implementer(ISession)\nclass SSHSessionForUnixConchUser:\n    def __init__(self, avatar, reactor=None):\n        \"\"\"\n        Construct an C{SSHSessionForUnixConchUser}.\n\n        @param avatar: The L{UnixConchUser} for whom this is an SSH session.\n        @param reactor: An L{IReactorProcess} used to handle shell and exec\n            requests. Uses the default reactor if None.\n        \"\"\"\n        if reactor is None:\n            from twisted.internet import reactor\n        self._reactor = reactor\n        self.avatar = avatar\n        self.environ = {'PATH': '/bin:/usr/bin:/usr/local/bin'}\n        self.pty = None\n        self.ptyTuple = 0\n\n\n    def addUTMPEntry(self, loggedIn=1):\n        if not utmp:\n            return\n        ipAddress = self.avatar.conn.transport.transport.getPeer().host\n        packedIp, = struct.unpack('L', socket.inet_aton(ipAddress))\n        ttyName = self.ptyTuple[2][5:]\n        t = time.time()\n        t1 = int(t)\n        t2 = int((t-t1) * 1e6)\n        entry = utmp.UtmpEntry()\n        entry.ut_type = loggedIn and utmp.USER_PROCESS or utmp.DEAD_PROCESS\n        entry.ut_pid = self.pty.pid\n        entry.ut_line = ttyName\n        entry.ut_id = ttyName[-4:]\n        entry.ut_tv = (t1, t2)\n        if loggedIn:\n            entry.ut_user = self.avatar.username\n            entry.ut_host = socket.gethostbyaddr(ipAddress)[0]\n            entry.ut_addr_v6 = (packedIp, 0, 0, 0)\n        a = utmp.UtmpRecord(utmp.UTMP_FILE)\n        a.pututline(entry)\n        a.endutent()\n        b = utmp.UtmpRecord(utmp.WTMP_FILE)\n        b.pututline(entry)\n        b.endutent()\n\n\n    def getPty(self, term, windowSize, modes):\n        self.environ['TERM'] = term\n        self.winSize = windowSize\n        self.modes = modes\n        master, slave = pty.openpty()\n        ttyname = os.ttyname(slave)\n        self.environ['SSH_TTY'] = ttyname\n        self.ptyTuple = (master, slave, ttyname)\n\n\n    def openShell(self, proto):\n        if not self.ptyTuple:  # We didn't get a pty-req.\n            log.msg('tried to get shell without pty, failing')\n            raise ConchError(\"no pty\")\n        uid, gid = self.avatar.getUserGroupId()\n        homeDir = self.avatar.getHomeDir()\n        shell = self.avatar.getShell()\n        self.environ['USER'] = self.avatar.username\n        self.environ['HOME'] = homeDir\n        self.environ['SHELL'] = shell\n        shellExec = os.path.basename(shell)\n        peer = self.avatar.conn.transport.transport.getPeer()\n        host = self.avatar.conn.transport.transport.getHost()\n        self.environ['SSH_CLIENT'] = '%s %s %s' % (\n            peer.host, peer.port, host.port)\n        self.getPtyOwnership()\n        self.pty = self._reactor.spawnProcess(\n            proto, shell, ['-%s' % (shellExec,)], self.environ, homeDir, uid,\n            gid, usePTY=self.ptyTuple)\n        self.addUTMPEntry()\n        fcntl.ioctl(self.pty.fileno(), tty.TIOCSWINSZ,\n                    struct.pack('4H', *self.winSize))\n        if self.modes:\n            self.setModes()\n        self.oldWrite = proto.transport.write\n        proto.transport.write = self._writeHack\n        self.avatar.conn.transport.transport.setTcpNoDelay(1)\n\n\n    def execCommand(self, proto, cmd):\n        uid, gid = self.avatar.getUserGroupId()\n        homeDir = self.avatar.getHomeDir()\n        shell = self.avatar.getShell() or '/bin/sh'\n        self.environ['HOME'] = homeDir\n        command = (shell, '-c', cmd)\n        peer = self.avatar.conn.transport.transport.getPeer()\n        host = self.avatar.conn.transport.transport.getHost()\n        self.environ['SSH_CLIENT'] = '%s %s %s' % (\n            peer.host, peer.port, host.port)\n        if self.ptyTuple:\n            self.getPtyOwnership()\n        self.pty = self._reactor.spawnProcess(\n            proto, shell, command, self.environ, homeDir, uid, gid,\n            usePTY=self.ptyTuple or 0)\n        if self.ptyTuple:\n            self.addUTMPEntry()\n            if self.modes:\n                self.setModes()\n        self.avatar.conn.transport.transport.setTcpNoDelay(1)\n\n\n    def getPtyOwnership(self):\n        ttyGid = os.stat(self.ptyTuple[2])[5]\n        uid, gid = self.avatar.getUserGroupId()\n        euid, egid = os.geteuid(), os.getegid()\n        os.setegid(0)\n        os.seteuid(0)\n        try:\n            os.chown(self.ptyTuple[2], uid, ttyGid)\n        finally:\n            os.setegid(egid)\n            os.seteuid(euid)\n\n\n    def setModes(self):\n        pty = self.pty\n        attr = tty.tcgetattr(pty.fileno())\n        for mode, modeValue in self.modes:\n            if mode not in ttymodes.TTYMODES:\n                continue\n            ttyMode = ttymodes.TTYMODES[mode]\n            if len(ttyMode) == 2:  # Flag.\n                flag, ttyAttr = ttyMode\n                if not hasattr(tty, ttyAttr):\n                    continue\n                ttyval = getattr(tty, ttyAttr)\n                if modeValue:\n                    attr[flag] = attr[flag] | ttyval\n                else:\n                    attr[flag] = attr[flag] & ~ttyval\n            elif ttyMode == 'OSPEED':\n                attr[tty.OSPEED] = getattr(tty, 'B%s' % (modeValue,))\n            elif ttyMode == 'ISPEED':\n                attr[tty.ISPEED] = getattr(tty, 'B%s' % (modeValue,))\n            else:\n                if not hasattr(tty, ttyMode):\n                    continue\n                ttyval = getattr(tty, ttyMode)\n                attr[tty.CC][ttyval] = chr(modeValue)\n        tty.tcsetattr(pty.fileno(), tty.TCSANOW, attr)\n\n\n    def eofReceived(self):\n        if self.pty:\n            self.pty.closeStdin()\n\n\n    def closed(self):\n        if self.ptyTuple and os.path.exists(self.ptyTuple[2]):\n            ttyGID = os.stat(self.ptyTuple[2])[5]\n            os.chown(self.ptyTuple[2], 0, ttyGID)\n        if self.pty:\n            try:\n                self.pty.signalProcess('HUP')\n            except (OSError, ProcessExitedAlready):\n                pass\n            self.pty.loseConnection()\n            self.addUTMPEntry(0)\n        log.msg('shell closed')\n\n\n    def windowChanged(self, winSize):\n        self.winSize = winSize\n        fcntl.ioctl(\n            self.pty.fileno(), tty.TIOCSWINSZ,\n            struct.pack('4H', *self.winSize))\n\n\n    def _writeHack(self, data):\n        \"\"\"\n        Hack to send ignore messages when we aren't echoing.\n        \"\"\"\n        if self.pty is not None:\n            attr = tty.tcgetattr(self.pty.fileno())[3]\n            if not attr & tty.ECHO and attr & tty.ICANON:  # No echo.\n                self.avatar.conn.transport.sendIgnore('\\x00'*(8+len(data)))\n        self.oldWrite(data)\n\n\n\n@implementer(ISFTPServer)\nclass SFTPServerForUnixConchUser:\n    def __init__(self, avatar):\n        self.avatar = avatar\n\n\n    def _setAttrs(self, path, attrs):\n        \"\"\"\n        NOTE: this function assumes it runs as the logged-in user:\n        i.e. under _runAsUser()\n        \"\"\"\n        if \"uid\" in attrs and \"gid\" in attrs:\n            os.chown(path, attrs[\"uid\"], attrs[\"gid\"])\n        if \"permissions\" in attrs:\n            os.chmod(path, attrs[\"permissions\"])\n        if \"atime\" in attrs and \"mtime\" in attrs:\n            os.utime(path, (attrs[\"atime\"], attrs[\"mtime\"]))\n\n\n    def _getAttrs(self, s):\n        return {\n            \"size\": s.st_size,\n            \"uid\": s.st_uid,\n            \"gid\": s.st_gid,\n            \"permissions\": s.st_mode,\n            \"atime\": int(s.st_atime),\n            \"mtime\": int(s.st_mtime)\n        }\n\n\n    def _absPath(self, path):\n        home = self.avatar.getHomeDir()\n        return os.path.join(nativeString(home.path), nativeString(path))\n\n\n    def gotVersion(self, otherVersion, extData):\n        return {}\n\n\n    def openFile(self, filename, flags, attrs):\n        return UnixSFTPFile(self, self._absPath(filename), flags, attrs)\n\n\n    def removeFile(self, filename):\n        filename = self._absPath(filename)\n        return self.avatar._runAsUser(os.remove, filename)\n\n\n    def renameFile(self, oldpath, newpath):\n        oldpath = self._absPath(oldpath)\n        newpath = self._absPath(newpath)\n        return self.avatar._runAsUser(os.rename, oldpath, newpath)\n\n\n    def makeDirectory(self, path, attrs):\n        path = self._absPath(path)\n        return self.avatar._runAsUser(\n            [(os.mkdir, (path,)), (self._setAttrs, (path, attrs))])\n\n\n    def removeDirectory(self, path):\n        path = self._absPath(path)\n        self.avatar._runAsUser(os.rmdir, path)\n\n\n    def openDirectory(self, path):\n        return UnixSFTPDirectory(self, self._absPath(path))\n\n\n    def getAttrs(self, path, followLinks):\n        path = self._absPath(path)\n        if followLinks:\n            s = self.avatar._runAsUser(os.stat, path)\n        else:\n            s = self.avatar._runAsUser(os.lstat, path)\n        return self._getAttrs(s)\n\n\n    def setAttrs(self, path, attrs):\n        path = self._absPath(path)\n        self.avatar._runAsUser(self._setAttrs, path, attrs)\n\n\n    def readLink(self, path):\n        path = self._absPath(path)\n        return self.avatar._runAsUser(os.readlink, path)\n\n\n    def makeLink(self, linkPath, targetPath):\n        linkPath = self._absPath(linkPath)\n        targetPath = self._absPath(targetPath)\n        return self.avatar._runAsUser(os.symlink, targetPath, linkPath)\n\n\n    def realPath(self, path):\n        return os.path.realpath(self._absPath(path))\n\n\n    def extendedRequest(self, extName, extData):\n        raise NotImplementedError\n\n\n\n@implementer(ISFTPFile)\nclass UnixSFTPFile:\n    def __init__(self, server, filename, flags, attrs):\n        self.server = server\n        openFlags = 0\n        if flags & FXF_READ == FXF_READ and flags & FXF_WRITE == 0:\n            openFlags = os.O_RDONLY\n        if flags & FXF_WRITE == FXF_WRITE and flags & FXF_READ == 0:\n            openFlags = os.O_WRONLY\n        if flags & FXF_WRITE == FXF_WRITE and flags & FXF_READ == FXF_READ:\n            openFlags = os.O_RDWR\n        if flags & FXF_APPEND == FXF_APPEND:\n            openFlags |= os.O_APPEND\n        if flags & FXF_CREAT == FXF_CREAT:\n            openFlags |= os.O_CREAT\n        if flags & FXF_TRUNC == FXF_TRUNC:\n            openFlags |= os.O_TRUNC\n        if flags & FXF_EXCL == FXF_EXCL:\n            openFlags |= os.O_EXCL\n        if \"permissions\" in attrs:\n            mode = attrs[\"permissions\"]\n            del attrs[\"permissions\"]\n        else:\n            mode = 0o777\n        fd = server.avatar._runAsUser(os.open, filename, openFlags, mode)\n        if attrs:\n            server.avatar._runAsUser(server._setAttrs, filename, attrs)\n        self.fd = fd\n\n\n    def close(self):\n        return self.server.avatar._runAsUser(os.close, self.fd)\n\n\n    def readChunk(self, offset, length):\n        return self.server.avatar._runAsUser(\n            [(os.lseek, (self.fd, offset, 0)),\n             (os.read, (self.fd, length))])\n\n\n    def writeChunk(self, offset, data):\n        return self.server.avatar._runAsUser(\n            [(os.lseek, (self.fd, offset, 0)),\n             (os.write, (self.fd, data))])\n\n\n    def getAttrs(self):\n        s = self.server.avatar._runAsUser(os.fstat, self.fd)\n        return self.server._getAttrs(s)\n\n\n    def setAttrs(self, attrs):\n        raise NotImplementedError\n\n\n\nclass UnixSFTPDirectory:\n\n    def __init__(self, server, directory):\n        self.server = server\n        self.files = server.avatar._runAsUser(os.listdir, directory)\n        self.dir = directory\n\n\n    def __iter__(self):\n        return self\n\n\n    def __next__(self):\n        try:\n            f = self.files.pop(0)\n        except IndexError:\n            raise StopIteration\n        else:\n            s = self.server.avatar._runAsUser(\n                os.lstat, os.path.join(self.dir, f))\n            longname = lsLine(f, s)\n            attrs = self.server._getAttrs(s)\n            return (f, longname, attrs)\n\n    next = __next__\n\n    def close(self):\n        self.files = []\n\n\n\ncomponents.registerAdapter(\n    SFTPServerForUnixConchUser, UnixConchUser, filetransfer.ISFTPServer)\ncomponents.registerAdapter(\n    SSHSessionForUnixConchUser, UnixConchUser, session.ISession)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/copyright.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nCopyright information for Twisted.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__all__ = ['copyright', 'disclaimer', 'longversion' ,'version']\n\nfrom twisted import __version__ as version, version as longversion\n\nlongversion = str(longversion)\n\ncopyright=\"\"\"\\\nCopyright (c) 2001-2019 Twisted Matrix Laboratories.\nSee LICENSE for details.\"\"\"\n\ndisclaimer='''\nTwisted, the Framework of Your Internet\n%s\n\nPermission is hereby granted, free of charge, to any person obtaining\na copy of this software and associated documentation files (the\n\"Software\"), to deal in the Software without restriction, including\nwithout limitation the rights to use, copy, modify, merge, publish,\ndistribute, sublicense, and/or sell copies of the Software, and to\npermit persons to whom the Software is furnished to do so, subject to\nthe following conditions:\n\nThe above copyright notice and this permission notice shall be\nincluded in all copies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND,\nEXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\nMERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND\nNONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE\nLIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION\nOF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION\nWITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n\n''' % (copyright,)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTwisted Cred: Support for verifying credentials, and providing services to user\nbased on those credentials.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/_digest.py",
    "content": "# -*- test-case-name: twisted.cred.test.test_digestauth -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nCalculations for HTTP Digest authentication.\n\n@see: U{http://www.faqs.org/rfcs/rfc2617.html}\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom binascii import hexlify\nfrom hashlib import md5, sha1\n\n\n\n# The digest math\n\nalgorithms = {\n    b'md5': md5,\n\n    # md5-sess is more complicated than just another algorithm.  It requires\n    # H(A1) state to be remembered from the first WWW-Authenticate challenge\n    # issued and re-used to process any Authorization header in response to\n    # that WWW-Authenticate challenge.  It is *not* correct to simply\n    # recalculate H(A1) each time an Authorization header is received.  Read\n    # RFC 2617, section 3.2.2.2 and do not try to make DigestCredentialFactory\n    # support this unless you completely understand it. -exarkun\n    b'md5-sess': md5,\n\n    b'sha': sha1,\n}\n\n# DigestCalcHA1\ndef calcHA1(pszAlg, pszUserName, pszRealm, pszPassword, pszNonce, pszCNonce,\n            preHA1=None):\n    \"\"\"\n    Compute H(A1) from RFC 2617.\n\n    @param pszAlg: The name of the algorithm to use to calculate the digest.\n        Currently supported are md5, md5-sess, and sha.\n    @param pszUserName: The username\n    @param pszRealm: The realm\n    @param pszPassword: The password\n    @param pszNonce: The nonce\n    @param pszCNonce: The cnonce\n\n    @param preHA1: If available this is a str containing a previously\n       calculated H(A1) as a hex string.  If this is given then the values for\n       pszUserName, pszRealm, and pszPassword must be L{None} and are ignored.\n    \"\"\"\n\n    if (preHA1 and (pszUserName or pszRealm or pszPassword)):\n        raise TypeError((\"preHA1 is incompatible with the pszUserName, \"\n                         \"pszRealm, and pszPassword arguments\"))\n\n    if preHA1 is None:\n        # We need to calculate the HA1 from the username:realm:password\n        m = algorithms[pszAlg]()\n        m.update(pszUserName)\n        m.update(b\":\")\n        m.update(pszRealm)\n        m.update(b\":\")\n        m.update(pszPassword)\n        HA1 = hexlify(m.digest())\n    else:\n        # We were given a username:realm:password\n        HA1 = preHA1\n\n    if pszAlg == b\"md5-sess\":\n        m = algorithms[pszAlg]()\n        m.update(HA1)\n        m.update(b\":\")\n        m.update(pszNonce)\n        m.update(b\":\")\n        m.update(pszCNonce)\n        HA1 = hexlify(m.digest())\n\n    return HA1\n\n\ndef calcHA2(algo, pszMethod, pszDigestUri, pszQop, pszHEntity):\n    \"\"\"\n    Compute H(A2) from RFC 2617.\n\n    @param pszAlg: The name of the algorithm to use to calculate the digest.\n        Currently supported are md5, md5-sess, and sha.\n    @param pszMethod: The request method.\n    @param pszDigestUri: The request URI.\n    @param pszQop: The Quality-of-Protection value.\n    @param pszHEntity: The hash of the entity body or L{None} if C{pszQop} is\n        not C{'auth-int'}.\n    @return: The hash of the A2 value for the calculation of the response\n        digest.\n    \"\"\"\n    m = algorithms[algo]()\n    m.update(pszMethod)\n    m.update(b\":\")\n    m.update(pszDigestUri)\n    if pszQop == b\"auth-int\":\n        m.update(b\":\")\n        m.update(pszHEntity)\n    return hexlify(m.digest())\n\n\ndef calcResponse(HA1, HA2, algo, pszNonce, pszNonceCount, pszCNonce, pszQop):\n    \"\"\"\n    Compute the digest for the given parameters.\n\n    @param HA1: The H(A1) value, as computed by L{calcHA1}.\n    @param HA2: The H(A2) value, as computed by L{calcHA2}.\n    @param pszNonce: The challenge nonce.\n    @param pszNonceCount: The (client) nonce count value for this response.\n    @param pszCNonce: The client nonce.\n    @param pszQop: The Quality-of-Protection value.\n    \"\"\"\n    m = algorithms[algo]()\n    m.update(HA1)\n    m.update(b\":\")\n    m.update(pszNonce)\n    m.update(b\":\")\n    if pszNonceCount and pszCNonce:\n        m.update(pszNonceCount)\n        m.update(b\":\")\n        m.update(pszCNonce)\n        m.update(b\":\")\n        m.update(pszQop)\n        m.update(b\":\")\n    m.update(HA2)\n    respHash = hexlify(m.digest())\n    return respHash\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/checkers.py",
    "content": "# -*- test-case-name: twisted.cred.test.test_cred -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom __future__ import division, absolute_import\n\nimport os\n\nfrom zope.interface import implementer, Interface, Attribute\n\nfrom twisted.logger import Logger\nfrom twisted.internet import defer\nfrom twisted.python import failure\nfrom twisted.cred import error, credentials\n\n\nclass ICredentialsChecker(Interface):\n    \"\"\"\n    An object that can check sub-interfaces of ICredentials.\n    \"\"\"\n\n    credentialInterfaces = Attribute(\n        'A list of sub-interfaces of ICredentials which specifies which I may check.')\n\n\n    def requestAvatarId(credentials):\n        \"\"\"\n        @param credentials: something which implements one of the interfaces in\n        self.credentialInterfaces.\n\n        @return: a Deferred which will fire a string which identifies an\n        avatar, an empty tuple to specify an authenticated anonymous user\n        (provided as checkers.ANONYMOUS) or fire a Failure(UnauthorizedLogin).\n        Alternatively, return the result itself.\n\n        @see: L{twisted.cred.credentials}\n        \"\"\"\n\n\n\n# A note on anonymity - We do not want None as the value for anonymous\n# because it is too easy to accidentally return it.  We do not want the\n# empty string, because it is too easy to mistype a password file.  For\n# example, an .htpasswd file may contain the lines: ['hello:asdf',\n# 'world:asdf', 'goodbye', ':world'].  This misconfiguration will have an\n# ill effect in any case, but accidentally granting anonymous access is a\n# worse failure mode than simply granting access to an untypeable\n# username.  We do not want an instance of 'object', because that would\n# create potential problems with persistence.\n\nANONYMOUS = ()\n\n\n@implementer(ICredentialsChecker)\nclass AllowAnonymousAccess:\n    credentialInterfaces = credentials.IAnonymous,\n\n    def requestAvatarId(self, credentials):\n        return defer.succeed(ANONYMOUS)\n\n\n\n@implementer(ICredentialsChecker)\nclass InMemoryUsernamePasswordDatabaseDontUse(object):\n    \"\"\"\n    An extremely simple credentials checker.\n\n    This is only of use in one-off test programs or examples which don't\n    want to focus too much on how credentials are verified.\n\n    You really don't want to use this for anything else.  It is, at best, a\n    toy.  If you need a simple credentials checker for a real application,\n    see L{FilePasswordDB}.\n    \"\"\"\n    credentialInterfaces = (credentials.IUsernamePassword,\n                            credentials.IUsernameHashedPassword)\n\n    def __init__(self, **users):\n        self.users = {x.encode('ascii'):y for x, y in users.items()}\n\n\n    def addUser(self, username, password):\n        self.users[username] = password\n\n\n    def _cbPasswordMatch(self, matched, username):\n        if matched:\n            return username\n        else:\n            return failure.Failure(error.UnauthorizedLogin())\n\n\n    def requestAvatarId(self, credentials):\n        if credentials.username in self.users:\n            return defer.maybeDeferred(\n                credentials.checkPassword,\n                self.users[credentials.username]).addCallback(\n                self._cbPasswordMatch, credentials.username)\n        else:\n            return defer.fail(error.UnauthorizedLogin())\n\n\n\n@implementer(ICredentialsChecker)\nclass FilePasswordDB:\n    \"\"\"\n    A file-based, text-based username/password database.\n\n    Records in the datafile for this class are delimited by a particular\n    string.  The username appears in a fixed field of the columns delimited\n    by this string, as does the password.  Both fields are specifiable.  If\n    the passwords are not stored plaintext, a hash function must be supplied\n    to convert plaintext passwords to the form stored on disk and this\n    CredentialsChecker will only be able to check IUsernamePassword\n    credentials.  If the passwords are stored plaintext,\n    IUsernameHashedPassword credentials will be checkable as well.\n    \"\"\"\n\n    cache = False\n    _credCache = None\n    _cacheTimestamp = 0\n    _log = Logger()\n\n    def __init__(self, filename, delim=b':', usernameField=0, passwordField=1,\n                 caseSensitive=True, hash=None, cache=False):\n        \"\"\"\n        @type filename: C{str}\n        @param filename: The name of the file from which to read username and\n        password information.\n\n        @type delim: C{str}\n        @param delim: The field delimiter used in the file.\n\n        @type usernameField: C{int}\n        @param usernameField: The index of the username after splitting a\n        line on the delimiter.\n\n        @type passwordField: C{int}\n        @param passwordField: The index of the password after splitting a\n        line on the delimiter.\n\n        @type caseSensitive: C{bool}\n        @param caseSensitive: If true, consider the case of the username when\n        performing a lookup.  Ignore it otherwise.\n\n        @type hash: Three-argument callable or L{None}\n        @param hash: A function used to transform the plaintext password\n        received over the network to a format suitable for comparison\n        against the version stored on disk.  The arguments to the callable\n        are the username, the network-supplied password, and the in-file\n        version of the password.  If the return value compares equal to the\n        version stored on disk, the credentials are accepted.\n\n        @type cache: C{bool}\n        @param cache: If true, maintain an in-memory cache of the\n        contents of the password file.  On lookups, the mtime of the\n        file will be checked, and the file will only be re-parsed if\n        the mtime is newer than when the cache was generated.\n        \"\"\"\n        self.filename = filename\n        self.delim = delim\n        self.ufield = usernameField\n        self.pfield = passwordField\n        self.caseSensitive = caseSensitive\n        self.hash = hash\n        self.cache = cache\n\n        if self.hash is None:\n            # The passwords are stored plaintext.  We can support both\n            # plaintext and hashed passwords received over the network.\n            self.credentialInterfaces = (\n                credentials.IUsernamePassword,\n                credentials.IUsernameHashedPassword\n            )\n        else:\n            # The passwords are hashed on disk.  We can support only\n            # plaintext passwords received over the network.\n            self.credentialInterfaces = (\n                credentials.IUsernamePassword,\n            )\n\n\n    def __getstate__(self):\n        d = dict(vars(self))\n        for k in '_credCache', '_cacheTimestamp':\n            try:\n                del d[k]\n            except KeyError:\n                pass\n        return d\n\n\n    def _cbPasswordMatch(self, matched, username):\n        if matched:\n            return username\n        else:\n            return failure.Failure(error.UnauthorizedLogin())\n\n\n    def _loadCredentials(self):\n        \"\"\"\n        Loads the credentials from the configured file.\n\n        @return: An iterable of C{username, password} couples.\n        @rtype: C{iterable}\n\n        @raise UnauthorizedLogin: when failing to read the credentials from the\n            file.\n        \"\"\"\n        try:\n            with open(self.filename, \"rb\") as f:\n                for line in f:\n                    line = line.rstrip()\n                    parts = line.split(self.delim)\n\n                    if self.ufield >= len(parts) or self.pfield >= len(parts):\n                        continue\n                    if self.caseSensitive:\n                        yield parts[self.ufield], parts[self.pfield]\n                    else:\n                        yield parts[self.ufield].lower(), parts[self.pfield]\n        except IOError as e:\n            self._log.error(\"Unable to load credentials db: {e!r}\", e=e)\n            raise error.UnauthorizedLogin()\n\n\n    def getUser(self, username):\n        if not self.caseSensitive:\n            username = username.lower()\n\n        if self.cache:\n            if self._credCache is None or os.path.getmtime(self.filename) > self._cacheTimestamp:\n                self._cacheTimestamp = os.path.getmtime(self.filename)\n                self._credCache = dict(self._loadCredentials())\n            return username, self._credCache[username]\n        else:\n            for u, p in self._loadCredentials():\n                if u == username:\n                    return u, p\n            raise KeyError(username)\n\n\n    def requestAvatarId(self, c):\n        try:\n            u, p = self.getUser(c.username)\n        except KeyError:\n            return defer.fail(error.UnauthorizedLogin())\n        else:\n            up = credentials.IUsernamePassword(c, None)\n            if self.hash:\n                if up is not None:\n                    h = self.hash(up.username, up.password, p)\n                    if h == p:\n                        return defer.succeed(u)\n                return defer.fail(error.UnauthorizedLogin())\n            else:\n                return defer.maybeDeferred(c.checkPassword, p\n                    ).addCallback(self._cbPasswordMatch, u)\n\n\n\n# For backwards compatibility\n# Allow access as the old name.\nOnDiskUsernamePasswordDatabase = FilePasswordDB\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/credentials.py",
    "content": "# -*- test-case-name: twisted.cred.test.test_cred-*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module defines L{ICredentials}, an interface for objects that represent\nauthentication credentials to provide, and also includes a number of useful\nimplementations of that interface.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom zope.interface import implementer, Interface\n\nimport base64\nimport hmac\nimport random\nimport re\nimport time\n\nfrom binascii import hexlify\nfrom hashlib import md5\n\nfrom twisted.python.randbytes import secureRandom\nfrom twisted.python.compat import networkString, nativeString\nfrom twisted.python.compat import intToBytes, unicode\nfrom twisted.cred._digest import calcResponse, calcHA1, calcHA2\nfrom twisted.cred import error\n\n\n\nclass ICredentials(Interface):\n    \"\"\"\n    I check credentials.\n\n    Implementors _must_ specify which sub-interfaces of ICredentials\n    to which it conforms, using L{zope.interface.declarations.implementer}.\n    \"\"\"\n\n\n\nclass IUsernameDigestHash(ICredentials):\n    \"\"\"\n    This credential is used when a CredentialChecker has access to the hash\n    of the username:realm:password as in an Apache .htdigest file.\n    \"\"\"\n    def checkHash(digestHash):\n        \"\"\"\n        @param digestHash: The hashed username:realm:password to check against.\n\n        @return: C{True} if the credentials represented by this object match\n            the given hash, C{False} if they do not, or a L{Deferred} which\n            will be called back with one of these values.\n        \"\"\"\n\n\n\nclass IUsernameHashedPassword(ICredentials):\n    \"\"\"\n    I encapsulate a username and a hashed password.\n\n    This credential is used when a hashed password is received from the\n    party requesting authentication.  CredentialCheckers which check this\n    kind of credential must store the passwords in plaintext (or as\n    password-equivalent hashes) form so that they can be hashed in a manner\n    appropriate for the particular credentials class.\n\n    @type username: L{bytes}\n    @ivar username: The username associated with these credentials.\n    \"\"\"\n\n    def checkPassword(password):\n        \"\"\"\n        Validate these credentials against the correct password.\n\n        @type password: L{bytes}\n        @param password: The correct, plaintext password against which to\n        check.\n\n        @rtype: C{bool} or L{Deferred}\n        @return: C{True} if the credentials represented by this object match the\n            given password, C{False} if they do not, or a L{Deferred} which will\n            be called back with one of these values.\n        \"\"\"\n\n\n\nclass IUsernamePassword(ICredentials):\n    \"\"\"\n    I encapsulate a username and a plaintext password.\n\n    This encapsulates the case where the password received over the network\n    has been hashed with the identity function (That is, not at all).  The\n    CredentialsChecker may store the password in whatever format it desires,\n    it need only transform the stored password in a similar way before\n    performing the comparison.\n\n    @type username: L{bytes}\n    @ivar username: The username associated with these credentials.\n\n    @type password: L{bytes}\n    @ivar password: The password associated with these credentials.\n    \"\"\"\n\n    def checkPassword(password):\n        \"\"\"\n        Validate these credentials against the correct password.\n\n        @type password: L{bytes}\n        @param password: The correct, plaintext password against which to\n        check.\n\n        @rtype: C{bool} or L{Deferred}\n        @return: C{True} if the credentials represented by this object match the\n            given password, C{False} if they do not, or a L{Deferred} which will\n            be called back with one of these values.\n        \"\"\"\n\n\n\nclass IAnonymous(ICredentials):\n    \"\"\"\n    I am an explicitly anonymous request for access.\n    \"\"\"\n\n\n\n@implementer(IUsernameHashedPassword, IUsernameDigestHash)\nclass DigestedCredentials(object):\n    \"\"\"\n    Yet Another Simple HTTP Digest authentication scheme.\n    \"\"\"\n\n    def __init__(self, username, method, realm, fields):\n        self.username = username\n        self.method = method\n        self.realm = realm\n        self.fields = fields\n\n\n    def checkPassword(self, password):\n        \"\"\"\n        Verify that the credentials represented by this object agree with the\n        given plaintext C{password} by hashing C{password} in the same way the\n        response hash represented by this object was generated and comparing\n        the results.\n        \"\"\"\n        response = self.fields.get('response')\n        uri = self.fields.get('uri')\n        nonce = self.fields.get('nonce')\n        cnonce = self.fields.get('cnonce')\n        nc = self.fields.get('nc')\n        algo = self.fields.get('algorithm', b'md5').lower()\n        qop = self.fields.get('qop', b'auth')\n\n        expected = calcResponse(\n            calcHA1(algo, self.username, self.realm, password, nonce, cnonce),\n            calcHA2(algo, self.method, uri, qop, None),\n            algo, nonce, nc, cnonce, qop)\n\n        return expected == response\n\n\n    def checkHash(self, digestHash):\n        \"\"\"\n        Verify that the credentials represented by this object agree with the\n        credentials represented by the I{H(A1)} given in C{digestHash}.\n\n        @param digestHash: A precomputed H(A1) value based on the username,\n            realm, and password associate with this credentials object.\n        \"\"\"\n        response = self.fields.get('response')\n        uri = self.fields.get('uri')\n        nonce = self.fields.get('nonce')\n        cnonce = self.fields.get('cnonce')\n        nc = self.fields.get('nc')\n        algo = self.fields.get('algorithm', b'md5').lower()\n        qop = self.fields.get('qop', b'auth')\n\n        expected = calcResponse(\n            calcHA1(algo, None, None, None, nonce, cnonce, preHA1=digestHash),\n            calcHA2(algo, self.method, uri, qop, None),\n            algo, nonce, nc, cnonce, qop)\n\n        return expected == response\n\n\n\nclass DigestCredentialFactory(object):\n    \"\"\"\n    Support for RFC2617 HTTP Digest Authentication\n\n    @cvar CHALLENGE_LIFETIME_SECS: The number of seconds for which an\n        opaque should be valid.\n\n    @type privateKey: L{bytes}\n    @ivar privateKey: A random string used for generating the secure opaque.\n\n    @type algorithm: L{bytes}\n    @param algorithm: Case insensitive string specifying the hash algorithm to\n        use.  Must be either C{'md5'} or C{'sha'}.  C{'md5-sess'} is B{not}\n        supported.\n\n    @type authenticationRealm: L{bytes}\n    @param authenticationRealm: case sensitive string that specifies the realm\n        portion of the challenge\n    \"\"\"\n\n    _parseparts = re.compile(\n        b'([^= ]+)'    # The key\n        b'='           # Conventional key/value separator (literal)\n        b'(?:'         # Group together a couple options\n          b'\"([^\"]*)\"' # A quoted string of length 0 or more\n        b'|'           # The other option in the group is coming\n          b'([^,]+)'   # An unquoted string of length 1 or more, up to a comma\n        b')'           # That non-matching group ends\n        b',?')         # There might be a comma at the end (none on last pair)\n\n    CHALLENGE_LIFETIME_SECS = 15 * 60    # 15 minutes\n\n    scheme = b\"digest\"\n\n    def __init__(self, algorithm, authenticationRealm):\n        self.algorithm = algorithm\n        self.authenticationRealm = authenticationRealm\n        self.privateKey = secureRandom(12)\n\n\n    def getChallenge(self, address):\n        \"\"\"\n        Generate the challenge for use in the WWW-Authenticate header.\n\n        @param address: The client address to which this challenge is being\n            sent.\n\n        @return: The L{dict} that can be used to generate a WWW-Authenticate\n            header.\n        \"\"\"\n        c = self._generateNonce()\n        o = self._generateOpaque(c, address)\n\n        return {'nonce': c,\n                'opaque': o,\n                'qop': b'auth',\n                'algorithm': self.algorithm,\n                'realm': self.authenticationRealm}\n\n\n    def _generateNonce(self):\n        \"\"\"\n        Create a random value suitable for use as the nonce parameter of a\n        WWW-Authenticate challenge.\n\n        @rtype: L{bytes}\n        \"\"\"\n        return hexlify(secureRandom(12))\n\n\n    def _getTime(self):\n        \"\"\"\n        Parameterize the time based seed used in C{_generateOpaque}\n        so we can deterministically unittest it's behavior.\n        \"\"\"\n        return time.time()\n\n\n    def _generateOpaque(self, nonce, clientip):\n        \"\"\"\n        Generate an opaque to be returned to the client.  This is a unique\n        string that can be returned to us and verified.\n        \"\"\"\n        # Now, what we do is encode the nonce, client ip and a timestamp in the\n        # opaque value with a suitable digest.\n        now = intToBytes(int(self._getTime()))\n\n        if not clientip:\n            clientip = b''\n        elif isinstance(clientip, unicode):\n            clientip = clientip.encode('ascii')\n\n        key = b\",\".join((nonce, clientip, now))\n        digest = hexlify(md5(key + self.privateKey).digest())\n        ekey = base64.b64encode(key)\n        return b\"-\".join((digest, ekey.replace(b'\\n', b'')))\n\n\n    def _verifyOpaque(self, opaque, nonce, clientip):\n        \"\"\"\n        Given the opaque and nonce from the request, as well as the client IP\n        that made the request, verify that the opaque was generated by us.\n        And that it's not too old.\n\n        @param opaque: The opaque value from the Digest response\n        @param nonce: The nonce value from the Digest response\n        @param clientip: The remote IP address of the client making the request\n            or L{None} if the request was submitted over a channel where this\n            does not make sense.\n\n        @return: C{True} if the opaque was successfully verified.\n\n        @raise error.LoginFailed: if C{opaque} could not be parsed or\n            contained the wrong values.\n        \"\"\"\n        # First split the digest from the key\n        opaqueParts = opaque.split(b'-')\n        if len(opaqueParts) != 2:\n            raise error.LoginFailed('Invalid response, invalid opaque value')\n\n        if not clientip:\n            clientip = b''\n        elif isinstance(clientip, unicode):\n            clientip = clientip.encode('ascii')\n\n        # Verify the key\n        key = base64.b64decode(opaqueParts[1])\n        keyParts = key.split(b',')\n\n        if len(keyParts) != 3:\n            raise error.LoginFailed('Invalid response, invalid opaque value')\n\n        if keyParts[0] != nonce:\n            raise error.LoginFailed(\n                'Invalid response, incompatible opaque/nonce values')\n\n        if keyParts[1] != clientip:\n            raise error.LoginFailed(\n                'Invalid response, incompatible opaque/client values')\n\n        try:\n            when = int(keyParts[2])\n        except ValueError:\n            raise error.LoginFailed(\n                'Invalid response, invalid opaque/time values')\n\n        if (int(self._getTime()) - when >\n            DigestCredentialFactory.CHALLENGE_LIFETIME_SECS):\n\n            raise error.LoginFailed(\n                'Invalid response, incompatible opaque/nonce too old')\n\n        # Verify the digest\n        digest = hexlify(md5(key + self.privateKey).digest())\n        if digest != opaqueParts[0]:\n            raise error.LoginFailed('Invalid response, invalid opaque value')\n\n        return True\n\n\n    def decode(self, response, method, host):\n        \"\"\"\n        Decode the given response and attempt to generate a\n        L{DigestedCredentials} from it.\n\n        @type response: L{bytes}\n        @param response: A string of comma separated key=value pairs\n\n        @type method: L{bytes}\n        @param method: The action requested to which this response is addressed\n            (GET, POST, INVITE, OPTIONS, etc).\n\n        @type host: L{bytes}\n        @param host: The address the request was sent from.\n\n        @raise error.LoginFailed: If the response does not contain a username,\n            a nonce, an opaque, or if the opaque is invalid.\n\n        @return: L{DigestedCredentials}\n        \"\"\"\n        response = b' '.join(response.splitlines())\n        parts = self._parseparts.findall(response)\n        auth = {}\n        for (key, bare, quoted) in parts:\n            value = (quoted or bare).strip()\n            auth[nativeString(key.strip())] = value\n\n        username = auth.get('username')\n        if not username:\n            raise error.LoginFailed('Invalid response, no username given.')\n\n        if 'opaque' not in auth:\n            raise error.LoginFailed('Invalid response, no opaque given.')\n\n        if 'nonce' not in auth:\n            raise error.LoginFailed('Invalid response, no nonce given.')\n\n        # Now verify the nonce/opaque values for this client\n        if self._verifyOpaque(auth.get('opaque'), auth.get('nonce'), host):\n            return DigestedCredentials(username,\n                                       method,\n                                       self.authenticationRealm,\n                                       auth)\n\n\n\n@implementer(IUsernameHashedPassword)\nclass CramMD5Credentials(object):\n    \"\"\"\n    An encapsulation of some CramMD5 hashed credentials.\n\n    @ivar challenge: The challenge to be sent to the client.\n    @type challenge: L{bytes}\n\n    @ivar response: The hashed response from the client.\n    @type response: L{bytes}\n\n    @ivar username: The username from the response from the client.\n    @type username: L{bytes} or L{None} if not yet provided.\n    \"\"\"\n    username = None\n    challenge = b''\n    response = b''\n\n    def __init__(self, host=None):\n        self.host = host\n\n\n    def getChallenge(self):\n        if self.challenge:\n            return self.challenge\n        # The data encoded in the first ready response contains an\n        # presumptively arbitrary string of random digits, a timestamp, and\n        # the fully-qualified primary host name of the server.  The syntax of\n        # the unencoded form must correspond to that of an RFC 822 'msg-id'\n        # [RFC822] as described in [POP3].\n        #   -- RFC 2195\n        r = random.randrange(0x7fffffff)\n        t = time.time()\n        self.challenge = networkString('<%d.%d@%s>' % (\n            r, t, nativeString(self.host) if self.host else None))\n        return self.challenge\n\n\n    def setResponse(self, response):\n        self.username, self.response = response.split(None, 1)\n\n\n    def moreChallenges(self):\n        return False\n\n\n    def checkPassword(self, password):\n        verify = hexlify(hmac.HMAC(password, self.challenge).digest())\n        return verify == self.response\n\n\n\n@implementer(IUsernameHashedPassword)\nclass UsernameHashedPassword:\n\n    def __init__(self, username, hashed):\n        self.username = username\n        self.hashed = hashed\n\n    def checkPassword(self, password):\n        return self.hashed == password\n\n\n\n@implementer(IUsernamePassword)\nclass UsernamePassword:\n\n    def __init__(self, username, password):\n        self.username = username\n        self.password = password\n\n    def checkPassword(self, password):\n        return self.password == password\n\n\n\n@implementer(IAnonymous)\nclass Anonymous:\n    pass\n\n\n\nclass ISSHPrivateKey(ICredentials):\n    \"\"\"\n    L{ISSHPrivateKey} credentials encapsulate an SSH public key to be checked\n    against a user's private key.\n\n    @ivar username: The username associated with these credentials.\n    @type username: L{bytes}\n\n    @ivar algName: The algorithm name for the blob.\n    @type algName: L{bytes}\n\n    @ivar blob: The public key blob as sent by the client.\n    @type blob: L{bytes}\n\n    @ivar sigData: The data the signature was made from.\n    @type sigData: L{bytes}\n\n    @ivar signature: The signed data.  This is checked to verify that the user\n        owns the private key.\n    @type signature: L{bytes} or L{None}\n    \"\"\"\n\n\n\n@implementer(ISSHPrivateKey)\nclass SSHPrivateKey:\n    def __init__(self, username, algName, blob, sigData, signature):\n        self.username = username\n        self.algName = algName\n        self.blob = blob\n        self.sigData = sigData\n        self.signature = signature\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/error.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nCred errors.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n\nclass Unauthorized(Exception):\n    \"\"\"Standard unauthorized error.\"\"\"\n\n\n\nclass LoginFailed(Exception):\n    \"\"\"\n    The user's request to log in failed for some reason.\n    \"\"\"\n\n\n\nclass UnauthorizedLogin(LoginFailed, Unauthorized):\n    \"\"\"The user was not authorized to log in.\n    \"\"\"\n\n\n\nclass UnhandledCredentials(LoginFailed):\n    \"\"\"A type of credentials were passed in with no knowledge of how to check\n    them.  This is a server configuration error - it means that a protocol was\n    connected to a Portal without a CredentialChecker that can check all of its\n    potential authentication strategies.\n    \"\"\"\n\n\n\nclass LoginDenied(LoginFailed):\n    \"\"\"\n    The realm rejected this login for some reason.\n\n    Examples of reasons this might be raised include an avatar logging in\n    too frequently, a quota having been fully used, or the overall server\n    load being too high.\n    \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/portal.py",
    "content": "# -*- test-case-name: twisted.cred.test.test_cred -*-\n\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThe point of integration of application and authentication.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.internet import defer\nfrom twisted.internet.defer import maybeDeferred\nfrom twisted.python import failure, reflect\nfrom twisted.cred import error\nfrom zope.interface import providedBy, Interface\n\n\nclass IRealm(Interface):\n    \"\"\"\n    The realm connects application-specific objects to the\n    authentication system.\n    \"\"\"\n    def requestAvatar(avatarId, mind, *interfaces):\n        \"\"\"\n        Return avatar which provides one of the given interfaces.\n\n        @param avatarId: a string that identifies an avatar, as returned by\n            L{ICredentialsChecker.requestAvatarId<twisted.cred.checkers.ICredentialsChecker.requestAvatarId>}\n            (via a Deferred).  Alternatively, it may be\n            C{twisted.cred.checkers.ANONYMOUS}.\n        @param mind: usually None.  See the description of mind in\n            L{Portal.login}.\n        @param interfaces: the interface(s) the returned avatar should\n            implement, e.g.  C{IMailAccount}.  See the description of\n            L{Portal.login}.\n\n        @returns: a deferred which will fire a tuple of (interface,\n            avatarAspect, logout), or the tuple itself.  The interface will be\n            one of the interfaces passed in the 'interfaces' argument.  The\n            'avatarAspect' will implement that interface.  The 'logout' object\n            is a callable which will detach the mind from the avatar.\n        \"\"\"\n\n\nclass Portal(object):\n    \"\"\"\n    A mediator between clients and a realm.\n\n    A portal is associated with one Realm and zero or more credentials checkers.\n    When a login is attempted, the portal finds the appropriate credentials\n    checker for the credentials given, invokes it, and if the credentials are\n    valid, retrieves the appropriate avatar from the Realm.\n\n    This class is not intended to be subclassed.  Customization should be done\n    in the realm object and in the credentials checker objects.\n    \"\"\"\n    def __init__(self, realm, checkers=()):\n        \"\"\"\n        Create a Portal to a L{IRealm}.\n        \"\"\"\n        self.realm = realm\n        self.checkers = {}\n        for checker in checkers:\n            self.registerChecker(checker)\n\n\n    def listCredentialsInterfaces(self):\n        \"\"\"\n        Return list of credentials interfaces that can be used to login.\n        \"\"\"\n        return list(self.checkers.keys())\n\n\n    def registerChecker(self, checker, *credentialInterfaces):\n        if not credentialInterfaces:\n            credentialInterfaces = checker.credentialInterfaces\n        for credentialInterface in credentialInterfaces:\n            self.checkers[credentialInterface] = checker\n\n\n    def login(self, credentials, mind, *interfaces):\n        \"\"\"\n        @param credentials: an implementor of\n            L{twisted.cred.credentials.ICredentials}\n\n        @param mind: an object which implements a client-side interface for\n            your particular realm.  In many cases, this may be None, so if the\n            word 'mind' confuses you, just ignore it.\n\n        @param interfaces: list of interfaces for the perspective that the mind\n            wishes to attach to. Usually, this will be only one interface, for\n            example IMailAccount. For highly dynamic protocols, however, this\n            may be a list like (IMailAccount, IUserChooser, IServiceInfo).  To\n            expand: if we are speaking to the system over IMAP, any information\n            that will be relayed to the user MUST be returned as an\n            IMailAccount implementor; IMAP clients would not be able to\n            understand anything else. Any information about unusual status\n            would have to be relayed as a single mail message in an\n            otherwise-empty mailbox. However, in a web-based mail system, or a\n            PB-based client, the ``mind'' object inside the web server\n            (implemented with a dynamic page-viewing mechanism such as a\n            Twisted Web Resource) or on the user's client program may be\n            intelligent enough to respond to several ``server''-side\n            interfaces.\n\n        @return: A deferred which will fire a tuple of (interface,\n            avatarAspect, logout).  The interface will be one of the interfaces\n            passed in the 'interfaces' argument.  The 'avatarAspect' will\n            implement that interface. The 'logout' object is a callable which\n            will detach the mind from the avatar. It must be called when the\n            user has conceptually disconnected from the service. Although in\n            some cases this will not be in connectionLost (such as in a\n            web-based session), it will always be at the end of a user's\n            interactive session.\n        \"\"\"\n        for i in self.checkers:\n            if i.providedBy(credentials):\n                return maybeDeferred(self.checkers[i].requestAvatarId, credentials\n                    ).addCallback(self.realm.requestAvatar, mind, *interfaces\n                    )\n        ifac = providedBy(credentials)\n        return defer.fail(failure.Failure(error.UnhandledCredentials(\n            \"No checker for %s\" % ', '.join(map(reflect.qual, ifac)))))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/strcred.py",
    "content": "# -*- test-case-name: twisted.cred.test.test_strcred -*-\n#\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n#\n\n\"\"\"\nSupport for resolving command-line strings that represent different\ncheckers available to cred.\n\nExamples:\n - passwd:/etc/passwd\n - memory:admin:asdf:user:lkj\n - unix\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport sys\n\nfrom zope.interface import Interface, Attribute\n\nfrom twisted.plugin import getPlugins\nfrom twisted.python import usage\n\n\n\nclass ICheckerFactory(Interface):\n    \"\"\"\n    A factory for objects which provide\n    L{twisted.cred.checkers.ICredentialsChecker}.\n\n    It's implemented by twistd plugins creating checkers.\n    \"\"\"\n\n    authType = Attribute(\n        'A tag that identifies the authentication method.')\n\n\n    authHelp = Attribute(\n        'A detailed (potentially multi-line) description of precisely '\n        'what functionality this CheckerFactory provides.')\n\n\n    argStringFormat = Attribute(\n        'A short (one-line) description of the argument string format.')\n\n\n    credentialInterfaces = Attribute(\n        'A list of credentials interfaces that this factory will support.')\n\n\n    def generateChecker(argstring):\n        \"\"\"\n        Return an L{twisted.cred.checkers.ICredentialsChecker} provider using the supplied\n        argument string.\n        \"\"\"\n\n\n\nclass StrcredException(Exception):\n    \"\"\"\n    Base exception class for strcred.\n    \"\"\"\n\n\n\nclass InvalidAuthType(StrcredException):\n    \"\"\"\n    Raised when a user provides an invalid identifier for the\n    authentication plugin (known as the authType).\n    \"\"\"\n\n\n\nclass InvalidAuthArgumentString(StrcredException):\n    \"\"\"\n    Raised by an authentication plugin when the argument string\n    provided is formatted incorrectly.\n    \"\"\"\n\n\n\nclass UnsupportedInterfaces(StrcredException):\n    \"\"\"\n    Raised when an application is given a checker to use that does not\n    provide any of the application's supported credentials interfaces.\n    \"\"\"\n\n\n\n# This will be used to warn the users whenever they view help for an\n# authType that is not supported by the application.\nnotSupportedWarning = (\"WARNING: This authType is not supported by \"\n                       \"this application.\")\n\n\n\ndef findCheckerFactories():\n    \"\"\"\n    Find all objects that implement L{ICheckerFactory}.\n    \"\"\"\n    return getPlugins(ICheckerFactory)\n\n\n\ndef findCheckerFactory(authType):\n    \"\"\"\n    Find the first checker factory that supports the given authType.\n    \"\"\"\n    for factory in findCheckerFactories():\n        if factory.authType == authType:\n            return factory\n    raise InvalidAuthType(authType)\n\n\n\ndef makeChecker(description):\n    \"\"\"\n    Returns an L{twisted.cred.checkers.ICredentialsChecker} based on the\n    contents of a descriptive string. Similar to\n    L{twisted.application.strports}.\n    \"\"\"\n    if ':' in description:\n        authType, argstring = description.split(':', 1)\n    else:\n        authType = description\n        argstring = ''\n    return findCheckerFactory(authType).generateChecker(argstring)\n\n\n\nclass AuthOptionMixin:\n    \"\"\"\n    Defines helper methods that can be added on to any\n    L{usage.Options} subclass that needs authentication.\n\n    This mixin implements three new options methods:\n\n    The opt_auth method (--auth) will write two new values to the\n    'self' dictionary: C{credInterfaces} (a dict of lists) and\n    C{credCheckers} (a list).\n\n    The opt_help_auth method (--help-auth) will search for all\n    available checker plugins and list them for the user; it will exit\n    when finished.\n\n    The opt_help_auth_type method (--help-auth-type) will display\n    detailed help for a particular checker plugin.\n\n    @cvar supportedInterfaces: An iterable object that returns\n       credential interfaces which this application is able to support.\n\n    @cvar authOutput: A writeable object to which this options class\n        will send all help-related output. Default: L{sys.stdout}\n    \"\"\"\n\n    supportedInterfaces = None\n    authOutput = sys.stdout\n\n\n    def supportsInterface(self, interface):\n        \"\"\"\n        Returns whether a particular credentials interface is supported.\n        \"\"\"\n        return (self.supportedInterfaces is None\n                or interface in self.supportedInterfaces)\n\n\n    def supportsCheckerFactory(self, factory):\n        \"\"\"\n        Returns whether a checker factory will provide at least one of\n        the credentials interfaces that we care about.\n        \"\"\"\n        for interface in factory.credentialInterfaces:\n            if self.supportsInterface(interface):\n                return True\n        return False\n\n\n    def addChecker(self, checker):\n        \"\"\"\n        Supply a supplied credentials checker to the Options class.\n        \"\"\"\n        # First figure out which interfaces we're willing to support.\n        supported = []\n        if self.supportedInterfaces is None:\n            supported = checker.credentialInterfaces\n        else:\n            for interface in checker.credentialInterfaces:\n                if self.supportsInterface(interface):\n                    supported.append(interface)\n        if not supported:\n            raise UnsupportedInterfaces(checker.credentialInterfaces)\n        # If we get this far, then we know we can use this checker.\n        if 'credInterfaces' not in self:\n            self['credInterfaces'] = {}\n        if 'credCheckers' not in self:\n            self['credCheckers'] = []\n        self['credCheckers'].append(checker)\n        for interface in supported:\n            self['credInterfaces'].setdefault(interface, []).append(checker)\n\n\n    def opt_auth(self, description):\n        \"\"\"\n        Specify an authentication method for the server.\n        \"\"\"\n        try:\n            self.addChecker(makeChecker(description))\n        except UnsupportedInterfaces as e:\n            raise usage.UsageError(\n                'Auth plugin not supported: %s' % e.args[0])\n        except InvalidAuthType as e:\n            raise usage.UsageError(\n                'Auth plugin not recognized: %s' % e.args[0])\n        except Exception as e:\n            raise usage.UsageError('Unexpected error: %s' % e)\n\n\n    def _checkerFactoriesForOptHelpAuth(self):\n        \"\"\"\n        Return a list of which authTypes will be displayed by --help-auth.\n        This makes it a lot easier to test this module.\n        \"\"\"\n        for factory in findCheckerFactories():\n            for interface in factory.credentialInterfaces:\n                if self.supportsInterface(interface):\n                    yield factory\n                    break\n\n\n    def opt_help_auth(self):\n        \"\"\"\n        Show all authentication methods available.\n        \"\"\"\n        self.authOutput.write(\"Usage: --auth AuthType[:ArgString]\\n\")\n        self.authOutput.write(\"For detailed help: --help-auth-type AuthType\\n\")\n        self.authOutput.write('\\n')\n        # Figure out the right width for our columns\n        firstLength = 0\n        for factory in self._checkerFactoriesForOptHelpAuth():\n            if len(factory.authType) > firstLength:\n                firstLength = len(factory.authType)\n        formatString = '  %%-%is\\t%%s\\n' % firstLength\n        self.authOutput.write(formatString % ('AuthType', 'ArgString format'))\n        self.authOutput.write(formatString % ('========', '================'))\n        for factory in self._checkerFactoriesForOptHelpAuth():\n            self.authOutput.write(\n                formatString % (factory.authType, factory.argStringFormat))\n        self.authOutput.write('\\n')\n        raise SystemExit(0)\n\n\n    def opt_help_auth_type(self, authType):\n        \"\"\"\n        Show help for a particular authentication type.\n        \"\"\"\n        try:\n            cf = findCheckerFactory(authType)\n        except InvalidAuthType:\n            raise usage.UsageError(\"Invalid auth type: %s\" % authType)\n        self.authOutput.write(\"Usage: --auth %s[:ArgString]\\n\" % authType)\n        self.authOutput.write(\"ArgString format: %s\\n\" % cf.argStringFormat)\n        self.authOutput.write('\\n')\n        for line in cf.authHelp.strip().splitlines():\n            self.authOutput.write('  %s\\n' % line.rstrip())\n        self.authOutput.write('\\n')\n        if not self.supportsCheckerFactory(cf):\n            self.authOutput.write('  %s\\n' % notSupportedWarning)\n            self.authOutput.write('\\n')\n        raise SystemExit(0)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/test/__init__.py",
    "content": "# -*- test-case-name: twisted.cred.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nUnit tests for C{twisted.cred}.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/test/test_cramauth.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.cred}'s implementation of CRAM-MD5.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom hmac import HMAC\nfrom binascii import hexlify\n\nfrom twisted.trial.unittest import TestCase\nfrom twisted.cred.credentials import CramMD5Credentials\nfrom twisted.cred.credentials import IUsernameHashedPassword\n\n\n\nclass CramMD5CredentialsTests(TestCase):\n    \"\"\"\n    Tests for L{CramMD5Credentials}.\n    \"\"\"\n    def test_idempotentChallenge(self):\n        \"\"\"\n        The same L{CramMD5Credentials} will always provide the same challenge,\n        no matter how many times it is called.\n        \"\"\"\n        c = CramMD5Credentials()\n        chal = c.getChallenge()\n        self.assertEqual(chal, c.getChallenge())\n\n\n    def test_checkPassword(self):\n        \"\"\"\n        When a valid response (which is a hex digest of the challenge that has\n        been encrypted by the user's shared secret) is set on the\n        L{CramMD5Credentials} that created the challenge, and C{checkPassword}\n        is called with the user's shared secret, it will return L{True}.\n        \"\"\"\n        c = CramMD5Credentials()\n        chal = c.getChallenge()\n        c.response = hexlify(HMAC(b'secret', chal).digest())\n        self.assertTrue(c.checkPassword(b'secret'))\n\n\n    def test_noResponse(self):\n        \"\"\"\n        When there is no response set, calling C{checkPassword} will return\n        L{False}.\n        \"\"\"\n        c = CramMD5Credentials()\n        self.assertFalse(c.checkPassword(b'secret'))\n\n\n    def test_wrongPassword(self):\n        \"\"\"\n        When an invalid response is set on the L{CramMD5Credentials} (one that\n        is not the hex digest of the challenge, encrypted with the user's shared\n        secret) and C{checkPassword} is called with the user's correct shared\n        secret, it will return L{False}.\n        \"\"\"\n        c = CramMD5Credentials()\n        chal = c.getChallenge()\n        c.response = hexlify(HMAC(b'thewrongsecret', chal).digest())\n        self.assertFalse(c.checkPassword(b'secret'))\n\n\n    def test_setResponse(self):\n        \"\"\"\n        When C{setResponse} is called with a string that is the username and\n        the hashed challenge separated with a space, they will be set on the\n        L{CramMD5Credentials}.\n        \"\"\"\n        c = CramMD5Credentials()\n        chal = c.getChallenge()\n        c.setResponse(b\" \".join(\n            (b\"squirrel\",\n             hexlify(HMAC(b'supersecret', chal).digest()))))\n        self.assertTrue(c.checkPassword(b'supersecret'))\n        self.assertEqual(c.username, b\"squirrel\")\n\n\n    def test_interface(self):\n        \"\"\"\n        L{CramMD5Credentials} implements the L{IUsernameHashedPassword}\n        interface.\n        \"\"\"\n        self.assertTrue(\n            IUsernameHashedPassword.implementedBy(CramMD5Credentials))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/test/test_cred.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.cred}, now with 30% more starch.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom zope.interface import implementer, Interface\n\nfrom binascii import hexlify, unhexlify\n\nfrom twisted.trial import unittest\nfrom twisted.python.compat import nativeString, networkString\nfrom twisted.python import components\nfrom twisted.internet import defer\nfrom twisted.cred import checkers, credentials, portal, error\n\ntry:\n    from crypt import crypt\nexcept ImportError:\n    crypt = None\n\n\n\nclass ITestable(Interface):\n    \"\"\"\n    An interface for a theoretical protocol.\n    \"\"\"\n    pass\n\n\n\nclass TestAvatar(object):\n    \"\"\"\n    A test avatar.\n    \"\"\"\n    def __init__(self, name):\n        self.name = name\n        self.loggedIn = False\n        self.loggedOut = False\n\n\n    def login(self):\n        assert not self.loggedIn\n        self.loggedIn = True\n\n\n    def logout(self):\n        self.loggedOut = True\n\n\n\n@implementer(ITestable)\nclass Testable(components.Adapter):\n    \"\"\"\n    A theoretical protocol for testing.\n    \"\"\"\n    pass\n\ncomponents.registerAdapter(Testable, TestAvatar, ITestable)\n\n\n\nclass IDerivedCredentials(credentials.IUsernamePassword):\n    pass\n\n\n\n@implementer(IDerivedCredentials, ITestable)\nclass DerivedCredentials(object):\n\n    def __init__(self, username, password):\n        self.username = username\n        self.password = password\n\n\n    def checkPassword(self, password):\n        return password == self.password\n\n\n\n@implementer(portal.IRealm)\nclass TestRealm(object):\n    \"\"\"\n    A basic test realm.\n    \"\"\"\n    def __init__(self):\n        self.avatars = {}\n\n\n    def requestAvatar(self, avatarId, mind, *interfaces):\n        if avatarId in self.avatars:\n            avatar = self.avatars[avatarId]\n        else:\n            avatar = TestAvatar(avatarId)\n            self.avatars[avatarId] = avatar\n        avatar.login()\n        return (interfaces[0], interfaces[0](avatar),\n                avatar.logout)\n\n\n\nclass CredTests(unittest.TestCase):\n    \"\"\"\n    Tests for the meat of L{twisted.cred} -- realms, portals, avatars, and\n    checkers.\n    \"\"\"\n    def setUp(self):\n        self.realm = TestRealm()\n        self.portal = portal.Portal(self.realm)\n        self.checker = checkers.InMemoryUsernamePasswordDatabaseDontUse()\n        self.checker.addUser(b\"bob\", b\"hello\")\n        self.portal.registerChecker(self.checker)\n\n\n    def test_listCheckers(self):\n        \"\"\"\n        The checkers in a portal can check only certain types of credentials.\n        Since this portal has\n        L{checkers.InMemoryUsernamePasswordDatabaseDontUse} registered, it\n        \"\"\"\n        expected = [credentials.IUsernamePassword,\n                    credentials.IUsernameHashedPassword]\n        got = self.portal.listCredentialsInterfaces()\n        self.assertEqual(sorted(got), sorted(expected))\n\n\n    def test_basicLogin(self):\n        \"\"\"\n        Calling C{login} on a portal with correct credentials and an interface\n        that the portal's realm supports works.\n        \"\"\"\n        login = self.successResultOf(self.portal.login(\n            credentials.UsernamePassword(b\"bob\", b\"hello\"), self, ITestable))\n        iface, impl, logout = login\n\n        # whitebox\n        self.assertEqual(iface, ITestable)\n        self.assertTrue(iface.providedBy(impl),\n                        \"%s does not implement %s\" % (impl, iface))\n\n        # greybox\n        self.assertTrue(impl.original.loggedIn)\n        self.assertTrue(not impl.original.loggedOut)\n        logout()\n        self.assertTrue(impl.original.loggedOut)\n\n\n    def test_derivedInterface(self):\n        \"\"\"\n        Logging in with correct derived credentials and an interface\n        that the portal's realm supports works.\n        \"\"\"\n        login = self.successResultOf(self.portal.login(\n            DerivedCredentials(b\"bob\", b\"hello\"), self, ITestable))\n        iface, impl, logout = login\n\n        # whitebox\n        self.assertEqual(iface, ITestable)\n        self.assertTrue(iface.providedBy(impl),\n                        \"%s does not implement %s\" % (impl, iface))\n\n        # greybox\n        self.assertTrue(impl.original.loggedIn)\n        self.assertTrue(not impl.original.loggedOut)\n        logout()\n        self.assertTrue(impl.original.loggedOut)\n\n\n    def test_failedLoginPassword(self):\n        \"\"\"\n        Calling C{login} with incorrect credentials (in this case a wrong\n        password) causes L{error.UnauthorizedLogin} to be raised.\n        \"\"\"\n        login = self.failureResultOf(self.portal.login(\n            credentials.UsernamePassword(b\"bob\", b\"h3llo\"), self, ITestable))\n        self.assertTrue(login)\n        self.assertEqual(error.UnauthorizedLogin, login.type)\n\n\n    def test_failedLoginName(self):\n        \"\"\"\n        Calling C{login} with incorrect credentials (in this case no known\n        user) causes L{error.UnauthorizedLogin} to be raised.\n        \"\"\"\n        login = self.failureResultOf(self.portal.login(\n            credentials.UsernamePassword(b\"jay\", b\"hello\"), self, ITestable))\n        self.assertTrue(login)\n        self.assertEqual(error.UnauthorizedLogin, login.type)\n\n\n\nclass OnDiskDatabaseTests(unittest.TestCase):\n    users = [\n        (b'user1', b'pass1'),\n        (b'user2', b'pass2'),\n        (b'user3', b'pass3'),\n    ]\n\n    def setUp(self):\n        self.dbfile = self.mktemp()\n        with open(self.dbfile, 'wb') as f:\n            for (u, p) in self.users:\n                f.write(u + b\":\" + p + b\"\\n\")\n\n\n    def test_getUserNonexistentDatabase(self):\n        \"\"\"\n        A missing db file will cause a permanent rejection of authorization\n        attempts.\n        \"\"\"\n        self.db = checkers.FilePasswordDB('test_thisbetternoteverexist.db')\n\n        self.assertRaises(error.UnauthorizedLogin, self.db.getUser, 'user')\n\n\n    def testUserLookup(self):\n        self.db = checkers.FilePasswordDB(self.dbfile)\n        for (u, p) in self.users:\n            self.assertRaises(KeyError, self.db.getUser, u.upper())\n            self.assertEqual(self.db.getUser(u), (u, p))\n\n\n    def testCaseInSensitivity(self):\n        self.db = checkers.FilePasswordDB(self.dbfile, caseSensitive=False)\n        for (u, p) in self.users:\n            self.assertEqual(self.db.getUser(u.upper()), (u, p))\n\n\n    def testRequestAvatarId(self):\n        self.db = checkers.FilePasswordDB(self.dbfile)\n        creds = [credentials.UsernamePassword(u, p) for u, p in self.users]\n        d = defer.gatherResults(\n            [defer.maybeDeferred(self.db.requestAvatarId, c) for c in creds])\n        d.addCallback(self.assertEqual, [u for u, p in self.users])\n        return d\n\n\n    def testRequestAvatarId_hashed(self):\n        self.db = checkers.FilePasswordDB(self.dbfile)\n        creds = [credentials.UsernameHashedPassword(u, p)\n                 for u, p in self.users]\n        d = defer.gatherResults(\n            [defer.maybeDeferred(self.db.requestAvatarId, c) for c in creds])\n        d.addCallback(self.assertEqual, [u for u, p in self.users])\n        return d\n\n\n\nclass HashedPasswordOnDiskDatabaseTests(unittest.TestCase):\n    users = [\n        (b'user1', b'pass1'),\n        (b'user2', b'pass2'),\n        (b'user3', b'pass3'),\n    ]\n\n    def setUp(self):\n        dbfile = self.mktemp()\n        self.db = checkers.FilePasswordDB(dbfile, hash=self.hash)\n        with open(dbfile, 'wb') as f:\n            for (u, p) in self.users:\n                f.write(u + b\":\" + self.hash(u, p, u[:2]) + b\"\\n\")\n\n        r = TestRealm()\n        self.port = portal.Portal(r)\n        self.port.registerChecker(self.db)\n\n\n    def hash(self, u, p, s):\n        return networkString(crypt(nativeString(p), nativeString(s)))\n\n\n    def testGoodCredentials(self):\n        goodCreds = [credentials.UsernamePassword(u, p) for u, p in self.users]\n        d = defer.gatherResults([self.db.requestAvatarId(c)\n                                 for c in goodCreds])\n        d.addCallback(self.assertEqual, [u for u, p in self.users])\n        return d\n\n\n    def testGoodCredentials_login(self):\n        goodCreds = [credentials.UsernamePassword(u, p) for u, p in self.users]\n        d = defer.gatherResults([self.port.login(c, None, ITestable)\n                                 for c in goodCreds])\n        d.addCallback(lambda x: [a.original.name for i, a, l in x])\n        d.addCallback(self.assertEqual, [u for u, p in self.users])\n        return d\n\n\n    def testBadCredentials(self):\n        badCreds = [credentials.UsernamePassword(u, 'wrong password')\n                    for u, p in self.users]\n        d = defer.DeferredList([self.port.login(c, None, ITestable)\n                                for c in badCreds], consumeErrors=True)\n        d.addCallback(self._assertFailures, error.UnauthorizedLogin)\n        return d\n\n\n    def testHashedCredentials(self):\n        hashedCreds = [credentials.UsernameHashedPassword(\n            u, self.hash(None, p, u[:2])) for u, p in self.users]\n        d = defer.DeferredList([self.port.login(c, None, ITestable)\n                                for c in hashedCreds], consumeErrors=True)\n        d.addCallback(self._assertFailures, error.UnhandledCredentials)\n        return d\n\n\n    def _assertFailures(self, failures, *expectedFailures):\n        for flag, failure in failures:\n            self.assertEqual(flag, defer.FAILURE)\n            failure.trap(*expectedFailures)\n        return None\n\n    if crypt is None:\n        skip = \"crypt module not available\"\n\n\n\nclass CheckersMixin(object):\n    \"\"\"\n    L{unittest.TestCase} mixin for testing that some checkers accept\n    and deny specified credentials.\n\n    Subclasses must provide\n    - C{getCheckers} which returns a sequence of\n      L{checkers.ICredentialChecker}\n    - C{getGoodCredentials} which returns a list of 2-tuples of\n      credential to check and avaterId to expect.\n    - C{getBadCredentials} which returns a list of credentials\n      which are expected to be unauthorized.\n    \"\"\"\n\n    @defer.inlineCallbacks\n    def test_positive(self):\n        \"\"\"\n        The given credentials are accepted by all the checkers, and give\n        the expected C{avatarID}s\n        \"\"\"\n        for chk in self.getCheckers():\n            for (cred, avatarId) in self.getGoodCredentials():\n                r = yield chk.requestAvatarId(cred)\n                self.assertEqual(r, avatarId)\n\n\n    @defer.inlineCallbacks\n    def test_negative(self):\n        \"\"\"\n        The given credentials are rejected by all the checkers.\n        \"\"\"\n        for chk in self.getCheckers():\n            for cred in self.getBadCredentials():\n                d = chk.requestAvatarId(cred)\n                yield self.assertFailure(d, error.UnauthorizedLogin)\n\n\n\nclass HashlessFilePasswordDBMixin(object):\n    credClass = credentials.UsernamePassword\n    diskHash = None\n    networkHash = staticmethod(lambda x: x)\n\n    _validCredentials = [\n        (b'user1', b'password1'),\n        (b'user2', b'password2'),\n        (b'user3', b'password3')]\n\n\n    def getGoodCredentials(self):\n        for u, p in self._validCredentials:\n            yield self.credClass(u, self.networkHash(p)), u\n\n\n    def getBadCredentials(self):\n        for u, p in [(b'user1', b'password3'),\n                     (b'user2', b'password1'),\n                     (b'bloof', b'blarf')]:\n            yield self.credClass(u, self.networkHash(p))\n\n\n    def getCheckers(self):\n        diskHash = self.diskHash or (lambda x: x)\n        hashCheck = self.diskHash and (lambda username, password,\n                                       stored: self.diskHash(password))\n\n        for cache in True, False:\n            fn = self.mktemp()\n            with open(fn, 'wb') as fObj:\n                for u, p in self._validCredentials:\n                    fObj.write(u + b\":\" + diskHash(p) + b\"\\n\")\n            yield checkers.FilePasswordDB(fn, cache=cache, hash=hashCheck)\n\n            fn = self.mktemp()\n            with open(fn, 'wb') as fObj:\n                for u, p in self._validCredentials:\n                    fObj.write(diskHash(p) + b' dingle dongle ' + u + b'\\n')\n            yield checkers.FilePasswordDB(fn, b' ', 3, 0,\n                                          cache=cache, hash=hashCheck)\n\n            fn = self.mktemp()\n            with open(fn, 'wb') as fObj:\n                for u, p in self._validCredentials:\n                    fObj.write(b'zip,zap,' + u.title() + b',zup,'\\\n                               + diskHash(p) + b'\\n',)\n            yield checkers.FilePasswordDB(fn, b',', 2, 4, False,\n                                          cache=cache, hash=hashCheck)\n\n\n\nclass LocallyHashedFilePasswordDBMixin(HashlessFilePasswordDBMixin):\n    diskHash = staticmethod(lambda x: hexlify(x))\n\n\n\nclass NetworkHashedFilePasswordDBMixin(HashlessFilePasswordDBMixin):\n    networkHash = staticmethod(lambda x: hexlify(x))\n\n    class credClass(credentials.UsernameHashedPassword):\n        def checkPassword(self, password):\n            return unhexlify(self.hashed) == password\n\n\n\nclass HashlessFilePasswordDBCheckerTests(HashlessFilePasswordDBMixin,\n                                         CheckersMixin, unittest.TestCase):\n    pass\n\n\n\nclass LocallyHashedFilePasswordDBCheckerTests(LocallyHashedFilePasswordDBMixin,\n                                              CheckersMixin,\n                                              unittest.TestCase):\n    pass\n\n\n\nclass NetworkHashedFilePasswordDBCheckerTests(NetworkHashedFilePasswordDBMixin,\n                                              CheckersMixin,\n                                              unittest.TestCase):\n    pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/test/test_digestauth.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.cred._digest} and the associated bits in\nL{twisted.cred.credentials}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport base64\n\nfrom binascii import hexlify\nfrom hashlib import md5, sha1\n\nfrom zope.interface.verify import verifyObject\nfrom twisted.trial.unittest import TestCase\nfrom twisted.internet.address import IPv4Address\nfrom twisted.cred.error import LoginFailed\nfrom twisted.cred.credentials import calcHA1, calcHA2, IUsernameDigestHash\nfrom twisted.cred.credentials import calcResponse, DigestCredentialFactory\nfrom twisted.python.compat import networkString\n\ndef b64encode(s):\n    return base64.b64encode(s).strip()\n\n\n\nclass FakeDigestCredentialFactory(DigestCredentialFactory):\n    \"\"\"\n    A Fake Digest Credential Factory that generates a predictable\n    nonce and opaque\n    \"\"\"\n    def __init__(self, *args, **kwargs):\n        super(FakeDigestCredentialFactory, self).__init__(*args, **kwargs)\n        self.privateKey = b\"0\"\n\n\n    def _generateNonce(self):\n        \"\"\"\n        Generate a static nonce\n        \"\"\"\n        return b'178288758716122392881254770685'\n\n\n    def _getTime(self):\n        \"\"\"\n        Return a stable time\n        \"\"\"\n        return 0\n\n\n\nclass DigestAuthTests(TestCase):\n    \"\"\"\n    L{TestCase} mixin class which defines a number of tests for\n    L{DigestCredentialFactory}.  Because this mixin defines C{setUp}, it\n    must be inherited before L{TestCase}.\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Create a DigestCredentialFactory for testing\n        \"\"\"\n        self.username = b\"foobar\"\n        self.password = b\"bazquux\"\n        self.realm = b\"test realm\"\n        self.algorithm = b\"md5\"\n        self.cnonce = b\"29fc54aa1641c6fa0e151419361c8f23\"\n        self.qop = b\"auth\"\n        self.uri = b\"/write/\"\n        self.clientAddress = IPv4Address('TCP', '10.2.3.4', 43125)\n        self.method = b'GET'\n        self.credentialFactory = DigestCredentialFactory(\n            self.algorithm, self.realm)\n\n\n    def test_MD5HashA1(self, _algorithm=b'md5', _hash=md5):\n        \"\"\"\n        L{calcHA1} accepts the C{'md5'} algorithm and returns an MD5 hash of\n        its parameters, excluding the nonce and cnonce.\n        \"\"\"\n        nonce = b'abc123xyz'\n        hashA1 = calcHA1(_algorithm, self.username, self.realm, self.password,\n                         nonce, self.cnonce)\n        a1 = b\":\".join((self.username, self.realm, self.password))\n        expected = hexlify(_hash(a1).digest())\n        self.assertEqual(hashA1, expected)\n\n\n    def test_MD5SessionHashA1(self):\n        \"\"\"\n        L{calcHA1} accepts the C{'md5-sess'} algorithm and returns an MD5 hash\n        of its parameters, including the nonce and cnonce.\n        \"\"\"\n        nonce = b'xyz321abc'\n        hashA1 = calcHA1(b'md5-sess', self.username, self.realm, self.password,\n                         nonce, self.cnonce)\n        a1 = self.username + b':' + self.realm + b':' + self.password\n        ha1 = hexlify(md5(a1).digest())\n        a1 = ha1 + b':' + nonce + b':' + self.cnonce\n        expected = hexlify(md5(a1).digest())\n        self.assertEqual(hashA1, expected)\n\n\n    def test_SHAHashA1(self):\n        \"\"\"\n        L{calcHA1} accepts the C{'sha'} algorithm and returns a SHA hash of its\n        parameters, excluding the nonce and cnonce.\n        \"\"\"\n        self.test_MD5HashA1(b'sha', sha1)\n\n\n    def test_MD5HashA2Auth(self, _algorithm=b'md5', _hash=md5):\n        \"\"\"\n        L{calcHA2} accepts the C{'md5'} algorithm and returns an MD5 hash of\n        its arguments, excluding the entity hash for QOP other than\n        C{'auth-int'}.\n        \"\"\"\n        method = b'GET'\n        hashA2 = calcHA2(_algorithm, method, self.uri, b'auth', None)\n        a2 = method + b':' + self.uri\n        expected = hexlify(_hash(a2).digest())\n        self.assertEqual(hashA2, expected)\n\n\n    def test_MD5HashA2AuthInt(self, _algorithm=b'md5', _hash=md5):\n        \"\"\"\n        L{calcHA2} accepts the C{'md5'} algorithm and returns an MD5 hash of\n        its arguments, including the entity hash for QOP of C{'auth-int'}.\n        \"\"\"\n        method = b'GET'\n        hentity = b'foobarbaz'\n        hashA2 = calcHA2(_algorithm, method, self.uri, b'auth-int', hentity)\n        a2 = method + b':' + self.uri + b':' + hentity\n        expected = hexlify(_hash(a2).digest())\n        self.assertEqual(hashA2, expected)\n\n\n    def test_MD5SessHashA2Auth(self):\n        \"\"\"\n        L{calcHA2} accepts the C{'md5-sess'} algorithm and QOP of C{'auth'} and\n        returns the same value as it does for the C{'md5'} algorithm.\n        \"\"\"\n        self.test_MD5HashA2Auth(b'md5-sess')\n\n\n    def test_MD5SessHashA2AuthInt(self):\n        \"\"\"\n        L{calcHA2} accepts the C{'md5-sess'} algorithm and QOP of C{'auth-int'}\n        and returns the same value as it does for the C{'md5'} algorithm.\n        \"\"\"\n        self.test_MD5HashA2AuthInt(b'md5-sess')\n\n\n    def test_SHAHashA2Auth(self):\n        \"\"\"\n        L{calcHA2} accepts the C{'sha'} algorithm and returns a SHA hash of\n        its arguments, excluding the entity hash for QOP other than\n        C{'auth-int'}.\n        \"\"\"\n        self.test_MD5HashA2Auth(b'sha', sha1)\n\n\n    def test_SHAHashA2AuthInt(self):\n        \"\"\"\n        L{calcHA2} accepts the C{'sha'} algorithm and returns a SHA hash of\n        its arguments, including the entity hash for QOP of C{'auth-int'}.\n        \"\"\"\n        self.test_MD5HashA2AuthInt(b'sha', sha1)\n\n\n    def test_MD5HashResponse(self, _algorithm=b'md5', _hash=md5):\n        \"\"\"\n        L{calcResponse} accepts the C{'md5'} algorithm and returns an MD5 hash\n        of its parameters, excluding the nonce count, client nonce, and QoP\n        value if the nonce count and client nonce are L{None}\n        \"\"\"\n        hashA1 = b'abc123'\n        hashA2 = b'789xyz'\n        nonce = b'lmnopq'\n\n        response = hashA1 + b':' + nonce + b':' + hashA2\n        expected = hexlify(_hash(response).digest())\n\n        digest = calcResponse(hashA1, hashA2, _algorithm, nonce, None, None,\n                              None)\n        self.assertEqual(expected, digest)\n\n\n    def test_MD5SessionHashResponse(self):\n        \"\"\"\n        L{calcResponse} accepts the C{'md5-sess'} algorithm and returns an MD5\n        hash of its parameters, excluding the nonce count, client nonce, and\n        QoP value if the nonce count and client nonce are L{None}\n        \"\"\"\n        self.test_MD5HashResponse(b'md5-sess')\n\n\n    def test_SHAHashResponse(self):\n        \"\"\"\n        L{calcResponse} accepts the C{'sha'} algorithm and returns a SHA hash\n        of its parameters, excluding the nonce count, client nonce, and QoP\n        value if the nonce count and client nonce are L{None}\n        \"\"\"\n        self.test_MD5HashResponse(b'sha', sha1)\n\n\n    def test_MD5HashResponseExtra(self, _algorithm=b'md5', _hash=md5):\n        \"\"\"\n        L{calcResponse} accepts the C{'md5'} algorithm and returns an MD5 hash\n        of its parameters, including the nonce count, client nonce, and QoP\n        value if they are specified.\n        \"\"\"\n        hashA1 = b'abc123'\n        hashA2 = b'789xyz'\n        nonce = b'lmnopq'\n        nonceCount = b'00000004'\n        clientNonce = b'abcxyz123'\n        qop = b'auth'\n\n        response = hashA1 + b':' + nonce + b':' + nonceCount + b':' +\\\n                   clientNonce + b':' + qop + b':' + hashA2\n        expected = hexlify(_hash(response).digest())\n\n        digest = calcResponse(\n            hashA1, hashA2, _algorithm, nonce, nonceCount, clientNonce, qop)\n        self.assertEqual(expected, digest)\n\n\n    def test_MD5SessionHashResponseExtra(self):\n        \"\"\"\n        L{calcResponse} accepts the C{'md5-sess'} algorithm and returns an MD5\n        hash of its parameters, including the nonce count, client nonce, and\n        QoP value if they are specified.\n        \"\"\"\n        self.test_MD5HashResponseExtra(b'md5-sess')\n\n\n    def test_SHAHashResponseExtra(self):\n        \"\"\"\n        L{calcResponse} accepts the C{'sha'} algorithm and returns a SHA hash\n        of its parameters, including the nonce count, client nonce, and QoP\n        value if they are specified.\n        \"\"\"\n        self.test_MD5HashResponseExtra(b'sha', sha1)\n\n\n    def formatResponse(self, quotes=True, **kw):\n        \"\"\"\n        Format all given keyword arguments and their values suitably for use as\n        the value of an HTTP header.\n\n        @types quotes: C{bool}\n        @param quotes: A flag indicating whether to quote the values of each\n            field in the response.\n\n        @param **kw: Keywords and C{bytes} values which will be treated as field\n            name/value pairs to include in the result.\n\n        @rtype: C{bytes}\n        @return: The given fields formatted for use as an HTTP header value.\n        \"\"\"\n        if 'username' not in kw:\n            kw['username'] = self.username\n        if 'realm' not in kw:\n            kw['realm'] = self.realm\n        if 'algorithm' not in kw:\n            kw['algorithm'] = self.algorithm\n        if 'qop' not in kw:\n            kw['qop'] = self.qop\n        if 'cnonce' not in kw:\n            kw['cnonce'] = self.cnonce\n        if 'uri' not in kw:\n            kw['uri'] = self.uri\n        if quotes:\n            quote = b'\"'\n        else:\n            quote = b''\n\n        return b', '.join([\n                b\"\".join((networkString(k), b\"=\", quote, v, quote))\n                for (k, v)\n                in kw.items()\n                if v is not None])\n\n\n    def getDigestResponse(self, challenge, ncount):\n        \"\"\"\n        Calculate the response for the given challenge\n        \"\"\"\n        nonce = challenge.get('nonce')\n        algo = challenge.get('algorithm').lower()\n        qop = challenge.get('qop')\n\n        ha1 = calcHA1(\n            algo, self.username, self.realm, self.password, nonce, self.cnonce)\n        ha2 = calcHA2(algo, b\"GET\", self.uri, qop, None)\n        expected = calcResponse(\n            ha1, ha2, algo, nonce, ncount, self.cnonce, qop)\n        return expected\n\n\n    def test_response(self, quotes=True):\n        \"\"\"\n        L{DigestCredentialFactory.decode} accepts a digest challenge response\n        and parses it into an L{IUsernameHashedPassword} provider.\n        \"\"\"\n        challenge = self.credentialFactory.getChallenge(\n            self.clientAddress.host)\n\n        nc = b\"00000001\"\n        clientResponse = self.formatResponse(\n            quotes=quotes,\n            nonce=challenge['nonce'],\n            response=self.getDigestResponse(challenge, nc),\n            nc=nc,\n            opaque=challenge['opaque'])\n        creds = self.credentialFactory.decode(\n            clientResponse, self.method, self.clientAddress.host)\n        self.assertTrue(creds.checkPassword(self.password))\n        self.assertFalse(creds.checkPassword(self.password + b'wrong'))\n\n\n    def test_responseWithoutQuotes(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} accepts a digest challenge response\n        which does not quote the values of its fields and parses it into an\n        L{IUsernameHashedPassword} provider in the same way it would a\n        response which included quoted field values.\n        \"\"\"\n        self.test_response(False)\n\n\n    def test_responseWithCommaURI(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} accepts a digest challenge response\n        which quotes the values of its fields and includes a C{b\",\"} in the URI\n        field.\n        \"\"\"\n        self.uri = b\"/some,path/\"\n        self.test_response(True)\n\n\n    def test_caseInsensitiveAlgorithm(self):\n        \"\"\"\n        The case of the algorithm value in the response is ignored when\n        checking the credentials.\n        \"\"\"\n        self.algorithm = b'MD5'\n        self.test_response()\n\n\n    def test_md5DefaultAlgorithm(self):\n        \"\"\"\n        The algorithm defaults to MD5 if it is not supplied in the response.\n        \"\"\"\n        self.algorithm = None\n        self.test_response()\n\n\n    def test_responseWithoutClientIP(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} accepts a digest challenge response\n        even if the client address it is passed is L{None}.\n        \"\"\"\n        challenge = self.credentialFactory.getChallenge(None)\n\n        nc = b\"00000001\"\n        clientResponse = self.formatResponse(\n            nonce=challenge['nonce'],\n            response=self.getDigestResponse(challenge, nc),\n            nc=nc,\n            opaque=challenge['opaque'])\n        creds = self.credentialFactory.decode(clientResponse, self.method,\n                                              None)\n        self.assertTrue(creds.checkPassword(self.password))\n        self.assertFalse(creds.checkPassword(self.password + b'wrong'))\n\n\n    def test_multiResponse(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} handles multiple responses to a\n        single challenge.\n        \"\"\"\n        challenge = self.credentialFactory.getChallenge(\n            self.clientAddress.host)\n\n        nc = b\"00000001\"\n        clientResponse = self.formatResponse(\n            nonce=challenge['nonce'],\n            response=self.getDigestResponse(challenge, nc),\n            nc=nc,\n            opaque=challenge['opaque'])\n\n        creds = self.credentialFactory.decode(clientResponse, self.method,\n                                              self.clientAddress.host)\n        self.assertTrue(creds.checkPassword(self.password))\n        self.assertFalse(creds.checkPassword(self.password + b'wrong'))\n\n        nc = b\"00000002\"\n        clientResponse = self.formatResponse(\n            nonce=challenge['nonce'],\n            response=self.getDigestResponse(challenge, nc),\n            nc=nc,\n            opaque=challenge['opaque'])\n\n        creds = self.credentialFactory.decode(clientResponse, self.method,\n                                              self.clientAddress.host)\n        self.assertTrue(creds.checkPassword(self.password))\n        self.assertFalse(creds.checkPassword(self.password + b'wrong'))\n\n\n    def test_failsWithDifferentMethod(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} returns an L{IUsernameHashedPassword}\n        provider which rejects a correct password for the given user if the\n        challenge response request is made using a different HTTP method than\n        was used to request the initial challenge.\n        \"\"\"\n        challenge = self.credentialFactory.getChallenge(\n            self.clientAddress.host)\n\n        nc = b\"00000001\"\n        clientResponse = self.formatResponse(\n            nonce=challenge['nonce'],\n            response=self.getDigestResponse(challenge, nc),\n            nc=nc,\n            opaque=challenge['opaque'])\n        creds = self.credentialFactory.decode(clientResponse, b'POST',\n                                              self.clientAddress.host)\n        self.assertFalse(creds.checkPassword(self.password))\n        self.assertFalse(creds.checkPassword(self.password + b'wrong'))\n\n\n    def test_noUsername(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} raises L{LoginFailed} if the response\n        has no username field or if the username field is empty.\n        \"\"\"\n        # Check for no username\n        e = self.assertRaises(\n            LoginFailed,\n            self.credentialFactory.decode,\n            self.formatResponse(username=None),\n            self.method, self.clientAddress.host)\n        self.assertEqual(str(e), \"Invalid response, no username given.\")\n\n        # Check for an empty username\n        e = self.assertRaises(\n            LoginFailed,\n            self.credentialFactory.decode,\n            self.formatResponse(username=b\"\"),\n            self.method, self.clientAddress.host)\n        self.assertEqual(str(e), \"Invalid response, no username given.\")\n\n\n    def test_noNonce(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} raises L{LoginFailed} if the response\n        has no nonce.\n        \"\"\"\n        e = self.assertRaises(\n            LoginFailed,\n            self.credentialFactory.decode,\n            self.formatResponse(opaque=b\"abc123\"),\n            self.method, self.clientAddress.host)\n        self.assertEqual(str(e), \"Invalid response, no nonce given.\")\n\n\n    def test_noOpaque(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} raises L{LoginFailed} if the response\n        has no opaque.\n        \"\"\"\n        e = self.assertRaises(\n            LoginFailed,\n            self.credentialFactory.decode,\n            self.formatResponse(),\n            self.method, self.clientAddress.host)\n        self.assertEqual(str(e), \"Invalid response, no opaque given.\")\n\n\n    def test_checkHash(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} returns an L{IUsernameDigestHash}\n        provider which can verify a hash of the form 'username:realm:password'.\n        \"\"\"\n        challenge = self.credentialFactory.getChallenge(\n            self.clientAddress.host)\n\n        nc = b\"00000001\"\n        clientResponse = self.formatResponse(\n            nonce=challenge['nonce'],\n            response=self.getDigestResponse(challenge, nc),\n            nc=nc,\n            opaque=challenge['opaque'])\n\n        creds = self.credentialFactory.decode(clientResponse, self.method,\n                                              self.clientAddress.host)\n        self.assertTrue(verifyObject(IUsernameDigestHash, creds))\n\n        cleartext = self.username + b\":\" + self.realm + b\":\" + self.password\n        hash = md5(cleartext)\n        self.assertTrue(creds.checkHash(hexlify(hash.digest())))\n        hash.update(b'wrong')\n        self.assertFalse(creds.checkHash(hexlify(hash.digest())))\n\n\n    def test_invalidOpaque(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} raises L{LoginFailed} when the opaque\n        value does not contain all the required parts.\n        \"\"\"\n        credentialFactory = FakeDigestCredentialFactory(self.algorithm,\n                                                        self.realm)\n        challenge = credentialFactory.getChallenge(self.clientAddress.host)\n\n        exc = self.assertRaises(\n            LoginFailed,\n            credentialFactory._verifyOpaque,\n            b'badOpaque',\n            challenge['nonce'],\n            self.clientAddress.host)\n        self.assertEqual(str(exc), 'Invalid response, invalid opaque value')\n\n        badOpaque = b'foo-' + b64encode(b'nonce,clientip')\n\n        exc = self.assertRaises(\n            LoginFailed,\n            credentialFactory._verifyOpaque,\n            badOpaque,\n            challenge['nonce'],\n            self.clientAddress.host)\n        self.assertEqual(str(exc), 'Invalid response, invalid opaque value')\n\n        exc = self.assertRaises(\n            LoginFailed,\n            credentialFactory._verifyOpaque,\n            b'',\n            challenge['nonce'],\n            self.clientAddress.host)\n        self.assertEqual(str(exc), 'Invalid response, invalid opaque value')\n\n        badOpaque = b'foo-' + b64encode(\n            b\",\".join((challenge['nonce'],\n                       networkString(self.clientAddress.host),\n                       b\"foobar\")))\n        exc = self.assertRaises(\n            LoginFailed,\n            credentialFactory._verifyOpaque,\n            badOpaque,\n            challenge['nonce'],\n            self.clientAddress.host)\n        self.assertEqual(\n            str(exc), 'Invalid response, invalid opaque/time values')\n\n\n    def test_incompatibleNonce(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} raises L{LoginFailed} when the given\n        nonce from the response does not match the nonce encoded in the opaque.\n        \"\"\"\n        credentialFactory = FakeDigestCredentialFactory(self.algorithm,\n                                                        self.realm)\n        challenge = credentialFactory.getChallenge(self.clientAddress.host)\n\n        badNonceOpaque = credentialFactory._generateOpaque(\n            b'1234567890',\n            self.clientAddress.host)\n\n        exc = self.assertRaises(\n            LoginFailed,\n            credentialFactory._verifyOpaque,\n            badNonceOpaque,\n            challenge['nonce'],\n            self.clientAddress.host)\n        self.assertEqual(\n            str(exc),\n            'Invalid response, incompatible opaque/nonce values')\n\n        exc = self.assertRaises(\n            LoginFailed,\n            credentialFactory._verifyOpaque,\n            badNonceOpaque,\n            b'',\n            self.clientAddress.host)\n        self.assertEqual(\n            str(exc),\n            'Invalid response, incompatible opaque/nonce values')\n\n\n    def test_incompatibleClientIP(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} raises L{LoginFailed} when the\n        request comes from a client IP other than what is encoded in the\n        opaque.\n        \"\"\"\n        credentialFactory = FakeDigestCredentialFactory(self.algorithm,\n                                                        self.realm)\n        challenge = credentialFactory.getChallenge(self.clientAddress.host)\n\n        badAddress = '10.0.0.1'\n        # Sanity check\n        self.assertNotEqual(self.clientAddress.host, badAddress)\n\n        badNonceOpaque = credentialFactory._generateOpaque(\n            challenge['nonce'], badAddress)\n\n        self.assertRaises(\n            LoginFailed,\n            credentialFactory._verifyOpaque,\n            badNonceOpaque,\n            challenge['nonce'],\n            self.clientAddress.host)\n\n\n    def test_oldNonce(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} raises L{LoginFailed} when the given\n        opaque is older than C{DigestCredentialFactory.CHALLENGE_LIFETIME_SECS}\n        \"\"\"\n        credentialFactory = FakeDigestCredentialFactory(self.algorithm,\n                                                        self.realm)\n        challenge = credentialFactory.getChallenge(self.clientAddress.host)\n\n        key = b\",\".join((challenge['nonce'],\n                         networkString(self.clientAddress.host),\n                         b'-137876876'))\n        digest = hexlify(md5(key + credentialFactory.privateKey).digest())\n        ekey = b64encode(key)\n\n        oldNonceOpaque = b\"-\".join((digest, ekey.strip(b'\\n')))\n\n        self.assertRaises(\n            LoginFailed,\n            credentialFactory._verifyOpaque,\n            oldNonceOpaque,\n            challenge['nonce'],\n            self.clientAddress.host)\n\n\n    def test_mismatchedOpaqueChecksum(self):\n        \"\"\"\n        L{DigestCredentialFactory.decode} raises L{LoginFailed} when the opaque\n        checksum fails verification.\n        \"\"\"\n        credentialFactory = FakeDigestCredentialFactory(self.algorithm,\n                                                        self.realm)\n        challenge = credentialFactory.getChallenge(self.clientAddress.host)\n\n        key = b\",\".join((challenge['nonce'],\n                         networkString(self.clientAddress.host),\n                         b'0'))\n\n        digest = hexlify(md5(key + b'this is not the right pkey').digest())\n        badChecksum = b\"-\".join((digest, b64encode(key)))\n\n        self.assertRaises(\n            LoginFailed,\n            credentialFactory._verifyOpaque,\n            badChecksum,\n            challenge['nonce'],\n            self.clientAddress.host)\n\n\n    def test_incompatibleCalcHA1Options(self):\n        \"\"\"\n        L{calcHA1} raises L{TypeError} when any of the pszUsername, pszRealm,\n        or pszPassword arguments are specified with the preHA1 keyword\n        argument.\n        \"\"\"\n        arguments = (\n            (b\"user\", b\"realm\", b\"password\", b\"preHA1\"),\n            (None, b\"realm\", None, b\"preHA1\"),\n            (None, None, b\"password\", b\"preHA1\"),\n            )\n\n        for pszUsername, pszRealm, pszPassword, preHA1 in arguments:\n            self.assertRaises(\n                TypeError,\n                calcHA1,\n                b\"md5\",\n                pszUsername,\n                pszRealm,\n                pszPassword,\n                b\"nonce\",\n                b\"cnonce\",\n                preHA1=preHA1)\n\n\n    def test_noNewlineOpaque(self):\n        \"\"\"\n        L{DigestCredentialFactory._generateOpaque} returns a value without\n        newlines, regardless of the length of the nonce.\n        \"\"\"\n        opaque = self.credentialFactory._generateOpaque(\n            b\"long nonce \" * 10, None)\n        self.assertNotIn(b'\\n', opaque)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/test/test_simpleauth.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for basic constructs of L{twisted.cred.credentials}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.trial.unittest import TestCase\nfrom twisted.cred.credentials import UsernamePassword, IUsernamePassword\nfrom twisted.cred.credentials import UsernameHashedPassword\nfrom twisted.cred.credentials import IUsernameHashedPassword\n\n\nclass UsernamePasswordTests(TestCase):\n    \"\"\"\n    Tests for L{UsernamePassword}.\n    \"\"\"\n    def test_initialisation(self):\n        \"\"\"\n        The initialisation of L{UsernamePassword} will set C{username} and\n        C{password} on it.\n        \"\"\"\n        creds = UsernamePassword(b\"foo\", b\"bar\")\n        self.assertEqual(creds.username, b\"foo\")\n        self.assertEqual(creds.password, b\"bar\")\n\n\n    def test_correctPassword(self):\n        \"\"\"\n        Calling C{checkPassword} on a L{UsernamePassword} will return L{True}\n        when the password given is the password on the object.\n        \"\"\"\n        creds = UsernamePassword(b\"user\", b\"pass\")\n        self.assertTrue(creds.checkPassword(b\"pass\"))\n\n\n    def test_wrongPassword(self):\n        \"\"\"\n        Calling C{checkPassword} on a L{UsernamePassword} will return L{False}\n        when the password given is NOT the password on the object.\n        \"\"\"\n        creds = UsernamePassword(b\"user\", b\"pass\")\n        self.assertFalse(creds.checkPassword(b\"someotherpass\"))\n\n\n    def test_interface(self):\n        \"\"\"\n        L{UsernamePassword} implements L{IUsernamePassword}.\n        \"\"\"\n        self.assertTrue(IUsernamePassword.implementedBy(UsernamePassword))\n\n\n\nclass UsernameHashedPasswordTests(TestCase):\n    \"\"\"\n    Tests for L{UsernameHashedPassword}.\n    \"\"\"\n    def test_initialisation(self):\n        \"\"\"\n        The initialisation of L{UsernameHashedPassword} will set C{username}\n        and C{hashed} on it.\n        \"\"\"\n        creds = UsernameHashedPassword(b\"foo\", b\"bar\")\n        self.assertEqual(creds.username, b\"foo\")\n        self.assertEqual(creds.hashed, b\"bar\")\n\n\n    def test_correctPassword(self):\n        \"\"\"\n        Calling C{checkPassword} on a L{UsernameHashedPassword} will return\n        L{True} when the password given is the password on the object.\n        \"\"\"\n        creds = UsernameHashedPassword(b\"user\", b\"pass\")\n        self.assertTrue(creds.checkPassword(b\"pass\"))\n\n\n    def test_wrongPassword(self):\n        \"\"\"\n        Calling C{checkPassword} on a L{UsernameHashedPassword} will return\n        L{False} when the password given is NOT the password on the object.\n        \"\"\"\n        creds = UsernameHashedPassword(b\"user\", b\"pass\")\n        self.assertFalse(creds.checkPassword(b\"someotherpass\"))\n\n\n    def test_interface(self):\n        \"\"\"\n        L{UsernameHashedPassword} implements L{IUsernameHashedPassword}.\n        \"\"\"\n        self.assertTrue(\n            IUsernameHashedPassword.implementedBy(UsernameHashedPassword))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/cred/test/test_strcred.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nL{twisted.cred.strcred}.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport os\n\nfrom twisted import plugin\nfrom twisted.trial import unittest\nfrom twisted.cred import credentials, checkers, error, strcred\nfrom twisted.plugins import cred_file, cred_anonymous, cred_unix\nfrom twisted.python import usage\nfrom twisted.python.compat import NativeStringIO\nfrom twisted.python.filepath import FilePath\nfrom twisted.python.fakepwd import UserDatabase\nfrom twisted.python.reflect import requireModule\n\ntry:\n    import crypt\nexcept ImportError:\n    crypt = None\n\ntry:\n    import pwd\nexcept ImportError:\n    pwd = None\n\ntry:\n    import spwd\nexcept ImportError:\n    spwd = None\n\n\n\ndef getInvalidAuthType():\n    \"\"\"\n    Helper method to produce an auth type that doesn't exist.\n    \"\"\"\n    invalidAuthType = 'ThisPluginDoesNotExist'\n    while (invalidAuthType in\n           [factory.authType for factory in strcred.findCheckerFactories()]):\n        invalidAuthType += '_'\n    return invalidAuthType\n\n\n\nclass PublicAPITests(unittest.TestCase):\n\n    def test_emptyDescription(self):\n        \"\"\"\n        The description string cannot be empty.\n        \"\"\"\n        iat = getInvalidAuthType()\n        self.assertRaises(strcred.InvalidAuthType, strcred.makeChecker, iat)\n        self.assertRaises(\n            strcred.InvalidAuthType, strcred.findCheckerFactory, iat)\n\n\n    def test_invalidAuthType(self):\n        \"\"\"\n        An unrecognized auth type raises an exception.\n        \"\"\"\n        iat = getInvalidAuthType()\n        self.assertRaises(strcred.InvalidAuthType, strcred.makeChecker, iat)\n        self.assertRaises(\n            strcred.InvalidAuthType, strcred.findCheckerFactory, iat)\n\n\n\nclass StrcredFunctionsTests(unittest.TestCase):\n\n    def test_findCheckerFactories(self):\n        \"\"\"\n        L{strcred.findCheckerFactories} returns all available plugins.\n        \"\"\"\n        availablePlugins = list(strcred.findCheckerFactories())\n        for plg in plugin.getPlugins(strcred.ICheckerFactory):\n            self.assertIn(plg, availablePlugins)\n\n\n    def test_findCheckerFactory(self):\n        \"\"\"\n        L{strcred.findCheckerFactory} returns the first plugin\n        available for a given authentication type.\n        \"\"\"\n        self.assertIdentical(strcred.findCheckerFactory('file'),\n                             cred_file.theFileCheckerFactory)\n\n\n\nclass MemoryCheckerTests(unittest.TestCase):\n\n    def setUp(self):\n        self.admin = credentials.UsernamePassword('admin', 'asdf')\n        self.alice = credentials.UsernamePassword('alice', 'foo')\n        self.badPass = credentials.UsernamePassword('alice', 'foobar')\n        self.badUser = credentials.UsernamePassword('x', 'yz')\n        self.checker = strcred.makeChecker('memory:admin:asdf:alice:foo')\n\n\n    def test_isChecker(self):\n        \"\"\"\n        Verifies that strcred.makeChecker('memory') returns an object\n        that implements the L{ICredentialsChecker} interface.\n        \"\"\"\n        self.assertTrue(checkers.ICredentialsChecker.providedBy(self.checker))\n        self.assertIn(credentials.IUsernamePassword,\n                      self.checker.credentialInterfaces)\n\n\n    def test_badFormatArgString(self):\n        \"\"\"\n        An argument string which does not contain user:pass pairs\n        (i.e., an odd number of ':' characters) raises an exception.\n        \"\"\"\n        self.assertRaises(strcred.InvalidAuthArgumentString,\n                          strcred.makeChecker, 'memory:a:b:c')\n\n\n    def test_memoryCheckerSucceeds(self):\n        \"\"\"\n        The checker works with valid credentials.\n        \"\"\"\n        def _gotAvatar(username):\n            self.assertEqual(username, self.admin.username)\n        return (self.checker\n                .requestAvatarId(self.admin)\n                .addCallback(_gotAvatar))\n\n\n    def test_memoryCheckerFailsUsername(self):\n        \"\"\"\n        The checker fails with an invalid username.\n        \"\"\"\n        return self.assertFailure(self.checker.requestAvatarId(self.badUser),\n                                  error.UnauthorizedLogin)\n\n\n    def test_memoryCheckerFailsPassword(self):\n        \"\"\"\n        The checker fails with an invalid password.\n        \"\"\"\n        return self.assertFailure(self.checker.requestAvatarId(self.badPass),\n                                  error.UnauthorizedLogin)\n\n\n\nclass AnonymousCheckerTests(unittest.TestCase):\n\n    def test_isChecker(self):\n        \"\"\"\n        Verifies that strcred.makeChecker('anonymous') returns an object\n        that implements the L{ICredentialsChecker} interface.\n        \"\"\"\n        checker = strcred.makeChecker('anonymous')\n        self.assertTrue(checkers.ICredentialsChecker.providedBy(checker))\n        self.assertIn(credentials.IAnonymous, checker.credentialInterfaces)\n\n\n    def testAnonymousAccessSucceeds(self):\n        \"\"\"\n        We can log in anonymously using this checker.\n        \"\"\"\n        checker = strcred.makeChecker('anonymous')\n        request = checker.requestAvatarId(credentials.Anonymous())\n        def _gotAvatar(avatar):\n            self.assertIdentical(checkers.ANONYMOUS, avatar)\n        return request.addCallback(_gotAvatar)\n\n\n\nclass UnixCheckerTests(unittest.TestCase):\n    users = {\n        'admin': 'asdf',\n        'alice': 'foo',\n        }\n\n\n    def _spwd_getspnam(self, username):\n        return spwd.struct_spwd((username,\n                                 crypt.crypt(self.users[username], 'F/'),\n                                 0, 0, 99999, 7, -1, -1, -1))\n\n\n    def setUp(self):\n        self.admin = credentials.UsernamePassword('admin', 'asdf')\n        self.alice = credentials.UsernamePassword('alice', 'foo')\n        self.badPass = credentials.UsernamePassword('alice', 'foobar')\n        self.badUser = credentials.UsernamePassword('x', 'yz')\n        self.checker = strcred.makeChecker('unix')\n        self.adminBytes = credentials.UsernamePassword(b'admin', b'asdf')\n        self.aliceBytes = credentials.UsernamePassword(b'alice', b'foo')\n        self.badPassBytes = credentials.UsernamePassword(b'alice', b'foobar')\n        self.badUserBytes = credentials.UsernamePassword(b'x', b'yz')\n        self.checkerBytes = strcred.makeChecker('unix')\n\n        # Hack around the pwd and spwd modules, since we can't really\n        # go about reading your /etc/passwd or /etc/shadow files\n        if pwd:\n            database = UserDatabase()\n            for username, password in self.users.items():\n                database.addUser(\n                    username, crypt.crypt(password, 'F/'),\n                    1000, 1000, username, '/home/' + username, '/bin/sh')\n            self.patch(pwd, 'getpwnam', database.getpwnam)\n        if spwd:\n            self.patch(spwd, 'getspnam', self._spwd_getspnam)\n\n\n    def test_isChecker(self):\n        \"\"\"\n        Verifies that strcred.makeChecker('unix') returns an object\n        that implements the L{ICredentialsChecker} interface.\n        \"\"\"\n        self.assertTrue(checkers.ICredentialsChecker.providedBy(self.checker))\n        self.assertIn(credentials.IUsernamePassword,\n                      self.checker.credentialInterfaces)\n        self.assertTrue(checkers.ICredentialsChecker.providedBy(\n                        self.checkerBytes))\n        self.assertIn(credentials.IUsernamePassword,\n                      self.checkerBytes.credentialInterfaces)\n\n\n    def test_unixCheckerSucceeds(self):\n        \"\"\"\n        The checker works with valid credentials.\n        \"\"\"\n        def _gotAvatar(username):\n            self.assertEqual(username, self.admin.username)\n        return (self.checker\n                .requestAvatarId(self.admin)\n                .addCallback(_gotAvatar))\n\n\n    def test_unixCheckerSucceedsBytes(self):\n        \"\"\"\n        The checker works with valid L{bytes} credentials.\n        \"\"\"\n        def _gotAvatar(username):\n            self.assertEqual(username,\n                             self.adminBytes.username.decode(\"utf-8\"))\n        return (self.checkerBytes\n                .requestAvatarId(self.adminBytes)\n                .addCallback(_gotAvatar))\n\n\n    def test_unixCheckerFailsUsername(self):\n        \"\"\"\n        The checker fails with an invalid username.\n        \"\"\"\n        return self.assertFailure(self.checker.requestAvatarId(self.badUser),\n                                  error.UnauthorizedLogin)\n\n\n    def test_unixCheckerFailsUsernameBytes(self):\n        \"\"\"\n        The checker fails with an invalid L{bytes} username.\n        \"\"\"\n        return self.assertFailure(self.checkerBytes.requestAvatarId(\n            self.badUserBytes), error.UnauthorizedLogin)\n\n\n    def test_unixCheckerFailsPassword(self):\n        \"\"\"\n        The checker fails with an invalid password.\n        \"\"\"\n        return self.assertFailure(self.checker.requestAvatarId(self.badPass),\n                                  error.UnauthorizedLogin)\n\n\n    def test_unixCheckerFailsPasswordBytes(self):\n        \"\"\"\n        The checker fails with an invalid L{bytes} password.\n        \"\"\"\n        return self.assertFailure(self.checkerBytes.requestAvatarId(\n            self.badPassBytes), error.UnauthorizedLogin)\n\n\n    if None in (pwd, spwd, crypt):\n        availability = []\n        for module, name in ((pwd, \"pwd\"), (spwd, \"spwd\"), (crypt, \"crypt\")):\n            if module is None:\n                availability += [name]\n        for method in (test_unixCheckerSucceeds,\n                       test_unixCheckerSucceedsBytes,\n                       test_unixCheckerFailsUsername,\n                       test_unixCheckerFailsUsernameBytes,\n                       test_unixCheckerFailsPassword,\n                       test_unixCheckerFailsPasswordBytes):\n            method.skip = (\"Required module(s) are unavailable: \" +\n                           \", \".join(availability))\n\n\nclass CryptTests(unittest.TestCase):\n    \"\"\"\n    L{crypt} has functions for encrypting password.\n    \"\"\"\n    if not crypt:\n        skip = \"Required module is unavailable: crypt\"\n\n    def test_verifyCryptedPassword(self):\n        \"\"\"\n        L{cred_unix.verifyCryptedPassword}\n        \"\"\"\n        password = \"sample password ^%$\"\n\n        for salt in (None, \"ab\"):\n            try:\n                cryptedCorrect = crypt.crypt(password, salt)\n            except TypeError:\n                # Older Python versions would throw a TypeError if\n                # a value of None was is used for the salt.\n                # Newer Python versions allow it.\n                continue\n            cryptedIncorrect = \"$1x1234\"\n            self.assertTrue(cred_unix.verifyCryptedPassword(cryptedCorrect,\n                                                            password))\n            self.assertFalse(cred_unix.verifyCryptedPassword(cryptedIncorrect,\n                                                             password))\n\n\n        # Python 3.3+ has crypt.METHOD_*, but not all\n        # platforms implement all methods.\n        for method in (\"METHOD_SHA512\", \"METHOD_SHA256\", \"METHOD_MD5\",\n                       \"METHOD_CRYPT\"):\n            cryptMethod = getattr(crypt, method, None)\n            if not cryptMethod:\n                continue\n            password = \"interesting password xyz\"\n            crypted = crypt.crypt(password, cryptMethod)\n            incorrectCrypted = crypted + \"blahfooincorrect\"\n            result = cred_unix.verifyCryptedPassword(crypted, password)\n            self.assertTrue(result)\n            # Try to pass in bytes\n            result = cred_unix.verifyCryptedPassword(crypted.encode(\"utf-8\"),\n                                                     password.encode(\"utf-8\"))\n            self.assertTrue(result)\n            result = cred_unix.verifyCryptedPassword(incorrectCrypted, password)\n            self.assertFalse(result)\n            # Try to pass in bytes\n            result = cred_unix.verifyCryptedPassword(incorrectCrypted.encode(\"utf-8\"),\n                                                     password.encode(\"utf-8\"))\n            self.assertFalse(result)\n\n\n\nclass FileDBCheckerTests(unittest.TestCase):\n    \"\"\"\n    C{--auth=file:...} file checker.\n    \"\"\"\n\n    def setUp(self):\n        self.admin = credentials.UsernamePassword(b'admin', b'asdf')\n        self.alice = credentials.UsernamePassword(b'alice', b'foo')\n        self.badPass = credentials.UsernamePassword(b'alice', b'foobar')\n        self.badUser = credentials.UsernamePassword(b'x', b'yz')\n        self.filename = self.mktemp()\n        FilePath(self.filename).setContent(b'admin:asdf\\nalice:foo\\n')\n        self.checker = strcred.makeChecker('file:' + self.filename)\n\n\n    def _fakeFilename(self):\n        filename = '/DoesNotExist'\n        while os.path.exists(filename):\n            filename += '_'\n        return filename\n\n\n    def test_isChecker(self):\n        \"\"\"\n        Verifies that strcred.makeChecker('memory') returns an object\n        that implements the L{ICredentialsChecker} interface.\n        \"\"\"\n        self.assertTrue(checkers.ICredentialsChecker.providedBy(self.checker))\n        self.assertIn(credentials.IUsernamePassword,\n                      self.checker.credentialInterfaces)\n\n\n    def test_fileCheckerSucceeds(self):\n        \"\"\"\n        The checker works with valid credentials.\n        \"\"\"\n        def _gotAvatar(username):\n            self.assertEqual(username, self.admin.username)\n        return (self.checker\n                .requestAvatarId(self.admin)\n                .addCallback(_gotAvatar))\n\n\n    def test_fileCheckerFailsUsername(self):\n        \"\"\"\n        The checker fails with an invalid username.\n        \"\"\"\n        return self.assertFailure(self.checker.requestAvatarId(self.badUser),\n                                  error.UnauthorizedLogin)\n\n\n    def test_fileCheckerFailsPassword(self):\n        \"\"\"\n        The checker fails with an invalid password.\n        \"\"\"\n        return self.assertFailure(self.checker.requestAvatarId(self.badPass),\n                                  error.UnauthorizedLogin)\n\n\n    def test_failsWithEmptyFilename(self):\n        \"\"\"\n        An empty filename raises an error.\n        \"\"\"\n        self.assertRaises(ValueError, strcred.makeChecker, 'file')\n        self.assertRaises(ValueError, strcred.makeChecker, 'file:')\n\n\n    def test_warnWithBadFilename(self):\n        \"\"\"\n        When the file auth plugin is given a file that doesn't exist, it\n        should produce a warning.\n        \"\"\"\n        oldOutput = cred_file.theFileCheckerFactory.errorOutput\n        newOutput = NativeStringIO()\n        cred_file.theFileCheckerFactory.errorOutput = newOutput\n        strcred.makeChecker('file:' + self._fakeFilename())\n        cred_file.theFileCheckerFactory.errorOutput = oldOutput\n        self.assertIn(cred_file.invalidFileWarning, newOutput.getvalue())\n\n\n\nclass SSHCheckerTests(unittest.TestCase):\n    \"\"\"\n    Tests for the C{--auth=sshkey:...} checker.  The majority of the tests for the\n    ssh public key database checker are in\n    L{twisted.conch.test.test_checkers.SSHPublicKeyCheckerTestCase}.\n    \"\"\"\n\n    skip = None\n\n    if requireModule('cryptography') is None:\n        skip = 'cryptography is not available'\n\n    if requireModule('pyasn1') is None:\n        skip = 'pyasn1 is not available'\n\n\n    def test_isChecker(self):\n        \"\"\"\n        Verifies that strcred.makeChecker('sshkey') returns an object\n        that implements the L{ICredentialsChecker} interface.\n        \"\"\"\n        sshChecker = strcred.makeChecker('sshkey')\n        self.assertTrue(checkers.ICredentialsChecker.providedBy(sshChecker))\n        self.assertIn(\n            credentials.ISSHPrivateKey, sshChecker.credentialInterfaces)\n\n\n\nclass DummyOptions(usage.Options, strcred.AuthOptionMixin):\n    \"\"\"\n    Simple options for testing L{strcred.AuthOptionMixin}.\n    \"\"\"\n\n\n\nclass CheckerOptionsTests(unittest.TestCase):\n\n    def test_createsList(self):\n        \"\"\"\n        The C{--auth} command line creates a list in the\n        Options instance and appends values to it.\n        \"\"\"\n        options = DummyOptions()\n        options.parseOptions(['--auth', 'memory'])\n        self.assertEqual(len(options['credCheckers']), 1)\n        options = DummyOptions()\n        options.parseOptions(['--auth', 'memory', '--auth', 'memory'])\n        self.assertEqual(len(options['credCheckers']), 2)\n\n\n    def test_invalidAuthError(self):\n        \"\"\"\n        The C{--auth} command line raises an exception when it\n        gets a parameter it doesn't understand.\n        \"\"\"\n        options = DummyOptions()\n        # If someone adds a 'ThisPluginDoesNotExist' then this unit\n        # test should still run.\n        invalidParameter = getInvalidAuthType()\n        self.assertRaises(\n            usage.UsageError,\n            options.parseOptions, ['--auth', invalidParameter])\n        self.assertRaises(\n            usage.UsageError,\n            options.parseOptions, ['--help-auth-type', invalidParameter])\n\n\n    def test_createsDictionary(self):\n        \"\"\"\n        The C{--auth} command line creates a dictionary mapping supported\n        interfaces to the list of credentials checkers that support it.\n        \"\"\"\n        options = DummyOptions()\n        options.parseOptions(['--auth', 'memory', '--auth', 'anonymous'])\n        chd = options['credInterfaces']\n        self.assertEqual(len(chd[credentials.IAnonymous]), 1)\n        self.assertEqual(len(chd[credentials.IUsernamePassword]), 1)\n        chdAnonymous = chd[credentials.IAnonymous][0]\n        chdUserPass = chd[credentials.IUsernamePassword][0]\n        self.assertTrue(checkers.ICredentialsChecker.providedBy(chdAnonymous))\n        self.assertTrue(checkers.ICredentialsChecker.providedBy(chdUserPass))\n        self.assertIn(credentials.IAnonymous,\n                      chdAnonymous.credentialInterfaces)\n        self.assertIn(credentials.IUsernamePassword,\n                      chdUserPass.credentialInterfaces)\n\n\n    def test_credInterfacesProvidesLists(self):\n        \"\"\"\n        When two C{--auth} arguments are passed along which support the same\n        interface, a list with both is created.\n        \"\"\"\n        options = DummyOptions()\n        options.parseOptions(['--auth', 'memory', '--auth', 'unix'])\n        self.assertEqual(\n            options['credCheckers'],\n            options['credInterfaces'][credentials.IUsernamePassword])\n\n\n    def test_listDoesNotDisplayDuplicates(self):\n        \"\"\"\n        The list for C{--help-auth} does not duplicate items.\n        \"\"\"\n        authTypes = []\n        options = DummyOptions()\n        for cf in options._checkerFactoriesForOptHelpAuth():\n            self.assertNotIn(cf.authType, authTypes)\n            authTypes.append(cf.authType)\n\n\n    def test_displaysListCorrectly(self):\n        \"\"\"\n        The C{--help-auth} argument correctly displays all\n        available authentication plugins, then exits.\n        \"\"\"\n        newStdout = NativeStringIO()\n        options = DummyOptions()\n        options.authOutput = newStdout\n        self.assertRaises(SystemExit, options.parseOptions, ['--help-auth'])\n        for checkerFactory in strcred.findCheckerFactories():\n            self.assertIn(checkerFactory.authType, newStdout.getvalue())\n\n\n    def test_displaysHelpCorrectly(self):\n        \"\"\"\n        The C{--help-auth-for} argument will correctly display the help file for a\n        particular authentication plugin.\n        \"\"\"\n        newStdout = NativeStringIO()\n        options = DummyOptions()\n        options.authOutput = newStdout\n        self.assertRaises(\n            SystemExit, options.parseOptions, ['--help-auth-type', 'file'])\n        for line in cred_file.theFileCheckerFactory.authHelp:\n            if line.strip():\n                self.assertIn(line.strip(), newStdout.getvalue())\n\n\n    def test_unexpectedException(self):\n        \"\"\"\n        When the checker specified by C{--auth} raises an unexpected error, it\n        should be caught and re-raised within a L{usage.UsageError}.\n        \"\"\"\n        options = DummyOptions()\n        err = self.assertRaises(usage.UsageError, options.parseOptions,\n                                ['--auth', 'file'])\n        self.assertEqual(str(err),\n                          \"Unexpected error: 'file' requires a filename\")\n\n\n\nclass OptionsForUsernamePassword(usage.Options, strcred.AuthOptionMixin):\n    supportedInterfaces = (credentials.IUsernamePassword,)\n\n\n\nclass OptionsForUsernameHashedPassword(usage.Options, strcred.AuthOptionMixin):\n    supportedInterfaces = (credentials.IUsernameHashedPassword,)\n\n\n\nclass OptionsSupportsAllInterfaces(usage.Options, strcred.AuthOptionMixin):\n    supportedInterfaces = None\n\n\n\nclass OptionsSupportsNoInterfaces(usage.Options, strcred.AuthOptionMixin):\n    supportedInterfaces = []\n\n\n\nclass LimitingInterfacesTests(unittest.TestCase):\n    \"\"\"\n    Tests functionality that allows an application to limit the\n    credential interfaces it can support. For the purposes of this\n    test, we use IUsernameHashedPassword, although this will never\n    really be used by the command line.\n\n    (I have, to date, not thought of a half-decent way for a user to\n    specify a hash algorithm via the command-line. Nor do I think it's\n    very useful.)\n\n    I should note that, at first, this test is counter-intuitive,\n    because we're using the checker with a pre-defined hash function\n    as the 'bad' checker. See the documentation for\n    L{twisted.cred.checkers.FilePasswordDB.hash} for more details.\n    \"\"\"\n\n    def setUp(self):\n        self.filename = self.mktemp()\n        with open(self.filename, 'wb') as f:\n            f.write(b'admin:asdf\\nalice:foo\\n')\n        self.goodChecker = checkers.FilePasswordDB(self.filename)\n        self.badChecker = checkers.FilePasswordDB(\n            self.filename, hash=self._hash)\n        self.anonChecker = checkers.AllowAnonymousAccess()\n\n\n    def _hash(self, networkUsername, networkPassword, storedPassword):\n        \"\"\"\n        A dumb hash that doesn't really do anything.\n        \"\"\"\n        return networkPassword\n\n\n    def test_supportsInterface(self):\n        \"\"\"\n        The supportsInterface method behaves appropriately.\n        \"\"\"\n        options = OptionsForUsernamePassword()\n        self.assertTrue(\n            options.supportsInterface(credentials.IUsernamePassword))\n        self.assertFalse(\n            options.supportsInterface(credentials.IAnonymous))\n        self.assertRaises(\n            strcred.UnsupportedInterfaces, options.addChecker,\n            self.anonChecker)\n\n\n    def test_supportsAllInterfaces(self):\n        \"\"\"\n        The supportsInterface method behaves appropriately\n        when the supportedInterfaces attribute is None.\n        \"\"\"\n        options = OptionsSupportsAllInterfaces()\n        self.assertTrue(\n            options.supportsInterface(credentials.IUsernamePassword))\n        self.assertTrue(\n            options.supportsInterface(credentials.IAnonymous))\n\n\n    def test_supportsCheckerFactory(self):\n        \"\"\"\n        The supportsCheckerFactory method behaves appropriately.\n        \"\"\"\n        options = OptionsForUsernamePassword()\n        fileCF = cred_file.theFileCheckerFactory\n        anonCF = cred_anonymous.theAnonymousCheckerFactory\n        self.assertTrue(options.supportsCheckerFactory(fileCF))\n        self.assertFalse(options.supportsCheckerFactory(anonCF))\n\n\n    def test_canAddSupportedChecker(self):\n        \"\"\"\n        When addChecker is called with a checker that implements at least one\n        of the interfaces our application supports, it is successful.\n        \"\"\"\n        options = OptionsForUsernamePassword()\n        options.addChecker(self.goodChecker)\n        iface = options.supportedInterfaces[0]\n        # Test that we did get IUsernamePassword\n        self.assertIdentical(\n            options['credInterfaces'][iface][0], self.goodChecker)\n        self.assertIdentical(options['credCheckers'][0], self.goodChecker)\n        # Test that we didn't get IUsernameHashedPassword\n        self.assertEqual(len(options['credInterfaces'][iface]), 1)\n        self.assertEqual(len(options['credCheckers']), 1)\n\n\n    def test_failOnAddingUnsupportedChecker(self):\n        \"\"\"\n        When addChecker is called with a checker that does not implement any\n        supported interfaces, it fails.\n        \"\"\"\n        options = OptionsForUsernameHashedPassword()\n        self.assertRaises(strcred.UnsupportedInterfaces,\n                          options.addChecker, self.badChecker)\n\n\n    def test_unsupportedInterfaceError(self):\n        \"\"\"\n        The C{--auth} command line raises an exception when it\n        gets a checker we don't support.\n        \"\"\"\n        options = OptionsSupportsNoInterfaces()\n        authType = cred_anonymous.theAnonymousCheckerFactory.authType\n        self.assertRaises(\n            usage.UsageError,\n            options.parseOptions, ['--auth', authType])\n\n\n    def test_helpAuthLimitsOutput(self):\n        \"\"\"\n        C{--help-auth} will only list checkers that purport to\n        supply at least one of the credential interfaces our\n        application can use.\n        \"\"\"\n        options = OptionsForUsernamePassword()\n        for factory in options._checkerFactoriesForOptHelpAuth():\n            invalid = True\n            for interface in factory.credentialInterfaces:\n                if options.supportsInterface(interface):\n                    invalid = False\n            if invalid:\n                raise strcred.UnsupportedInterfaces()\n\n\n    def test_helpAuthTypeLimitsOutput(self):\n        \"\"\"\n        C{--help-auth-type} will display a warning if you get\n        help for an authType that does not supply at least one of the\n        credential interfaces our application can use.\n        \"\"\"\n        options = OptionsForUsernamePassword()\n        # Find an interface that we can use for our test\n        invalidFactory = None\n        for factory in strcred.findCheckerFactories():\n            if not options.supportsCheckerFactory(factory):\n                invalidFactory = factory\n                break\n        self.assertNotIdentical(invalidFactory, None)\n        # Capture output and make sure the warning is there\n        newStdout = NativeStringIO()\n        options.authOutput = newStdout\n        self.assertRaises(SystemExit, options.parseOptions,\n                          ['--help-auth-type', 'anonymous'])\n        self.assertIn(strcred.notSupportedWarning, newStdout.getvalue())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/enterprise/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTwisted Enterprise: Database support for Twisted services.\n\"\"\"\n\n__all__ = ['adbapi']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/enterprise/adbapi.py",
    "content": "# -*- test-case-name: twisted.test.test_adbapi -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAn asynchronous mapping to U{DB-API\n2.0<http://www.python.org/topics/database/DatabaseAPI-2.0.html>}.\n\"\"\"\n\nimport sys\n\nfrom twisted.internet import threads\nfrom twisted.python import reflect, log, compat\n\n\nclass ConnectionLost(Exception):\n    \"\"\"\n    This exception means that a db connection has been lost.  Client code may\n    try again.\n    \"\"\"\n\n\n\nclass Connection(object):\n    \"\"\"\n    A wrapper for a DB-API connection instance.\n\n    The wrapper passes almost everything to the wrapped connection and so has\n    the same API. However, the L{Connection} knows about its pool and also\n    handle reconnecting should when the real connection dies.\n    \"\"\"\n\n    def __init__(self, pool):\n        self._pool = pool\n        self._connection = None\n        self.reconnect()\n\n\n    def close(self):\n        # The way adbapi works right now means that closing a connection is\n        # a really bad thing  as it leaves a dead connection associated with\n        # a thread in the thread pool.\n        # Really, I think closing a pooled connection should return it to the\n        # pool but that's handled by the runWithConnection method already so,\n        # rather than upsetting anyone by raising an exception, let's ignore\n        # the request\n        pass\n\n\n    def rollback(self):\n        if not self._pool.reconnect:\n            self._connection.rollback()\n            return\n\n        try:\n            self._connection.rollback()\n            curs = self._connection.cursor()\n            curs.execute(self._pool.good_sql)\n            curs.close()\n            self._connection.commit()\n            return\n        except:\n            log.err(None, \"Rollback failed\")\n\n        self._pool.disconnect(self._connection)\n\n        if self._pool.noisy:\n            log.msg(\"Connection lost.\")\n\n        raise ConnectionLost()\n\n\n    def reconnect(self):\n        if self._connection is not None:\n            self._pool.disconnect(self._connection)\n        self._connection = self._pool.connect()\n\n\n    def __getattr__(self, name):\n        return getattr(self._connection, name)\n\n\n\nclass Transaction:\n    \"\"\"\n    A lightweight wrapper for a DB-API 'cursor' object.\n\n    Relays attribute access to the DB cursor. That is, you can call\n    C{execute()}, C{fetchall()}, etc., and they will be called on the\n    underlying DB-API cursor object. Attributes will also be retrieved from\n    there.\n    \"\"\"\n    _cursor = None\n\n    def __init__(self, pool, connection):\n        self._pool = pool\n        self._connection = connection\n        self.reopen()\n\n\n    def close(self):\n        _cursor = self._cursor\n        self._cursor = None\n        _cursor.close()\n\n\n    def reopen(self):\n        if self._cursor is not None:\n            self.close()\n\n        try:\n            self._cursor = self._connection.cursor()\n            return\n        except:\n            if not self._pool.reconnect:\n                raise\n            else:\n                log.err(None, \"Cursor creation failed\")\n\n        if self._pool.noisy:\n            log.msg('Connection lost, reconnecting')\n\n        self.reconnect()\n        self._cursor = self._connection.cursor()\n\n\n    def reconnect(self):\n        self._connection.reconnect()\n        self._cursor = None\n\n\n    def __getattr__(self, name):\n        return getattr(self._cursor, name)\n\n\n\nclass ConnectionPool:\n    \"\"\"\n    Represent a pool of connections to a DB-API 2.0 compliant database.\n\n    @ivar connectionFactory: factory for connections, default to L{Connection}.\n    @type connectionFactory: any callable.\n\n    @ivar transactionFactory: factory for transactions, default to\n        L{Transaction}.\n    @type transactionFactory: any callable\n\n    @ivar shutdownID: L{None} or a handle on the shutdown event trigger which\n        will be used to stop the connection pool workers when the reactor\n        stops.\n\n    @ivar _reactor: The reactor which will be used to schedule startup and\n        shutdown events.\n    @type _reactor: L{IReactorCore} provider\n    \"\"\"\n\n    CP_ARGS = \"min max name noisy openfun reconnect good_sql\".split()\n\n    noisy = False # If true, generate informational log messages\n    min = 3 # Minimum number of connections in pool\n    max = 5 # Maximum number of connections in pool\n    name = None # Name to assign to thread pool for debugging\n    openfun = None # A function to call on new connections\n    reconnect = False # Reconnect when connections fail\n    good_sql = 'select 1' # A query which should always succeed\n\n    running = False # True when the pool is operating\n    connectionFactory = Connection\n    transactionFactory = Transaction\n\n    # Initialize this to None so it's available in close() even if start()\n    # never runs.\n    shutdownID = None\n\n    def __init__(self, dbapiName, *connargs, **connkw):\n        \"\"\"\n        Create a new L{ConnectionPool}.\n\n        Any positional or keyword arguments other than those documented here\n        are passed to the DB-API object when connecting. Use these arguments to\n        pass database names, usernames, passwords, etc.\n\n        @param dbapiName: an import string to use to obtain a DB-API compatible\n            module (e.g. C{'pyPgSQL.PgSQL'})\n\n        @param cp_min: the minimum number of connections in pool (default 3)\n\n        @param cp_max: the maximum number of connections in pool (default 5)\n\n        @param cp_noisy: generate informational log messages during operation\n            (default C{False})\n\n        @param cp_openfun: a callback invoked after every C{connect()} on the\n            underlying DB-API object. The callback is passed a new DB-API\n            connection object. This callback can setup per-connection state\n            such as charset, timezone, etc.\n\n        @param cp_reconnect: detect connections which have failed and reconnect\n            (default C{False}). Failed connections may result in\n            L{ConnectionLost} exceptions, which indicate the query may need to\n            be re-sent.\n\n        @param cp_good_sql: an sql query which should always succeed and change\n            no state (default C{'select 1'})\n\n        @param cp_reactor: use this reactor instead of the global reactor\n            (added in Twisted 10.2).\n        @type cp_reactor: L{IReactorCore} provider\n        \"\"\"\n        self.dbapiName = dbapiName\n        self.dbapi = reflect.namedModule(dbapiName)\n\n        if getattr(self.dbapi, 'apilevel', None) != '2.0':\n            log.msg('DB API module not DB API 2.0 compliant.')\n\n        if getattr(self.dbapi, 'threadsafety', 0) < 1:\n            log.msg('DB API module not sufficiently thread-safe.')\n\n        reactor = connkw.pop('cp_reactor', None)\n        if reactor is None:\n            from twisted.internet import reactor\n        self._reactor = reactor\n\n        self.connargs = connargs\n        self.connkw = connkw\n\n        for arg in self.CP_ARGS:\n            cpArg = 'cp_%s' % (arg,)\n            if cpArg in connkw:\n                setattr(self, arg, connkw[cpArg])\n                del connkw[cpArg]\n\n        self.min = min(self.min, self.max)\n        self.max = max(self.min, self.max)\n\n        # All connections, hashed on thread id\n        self.connections = {}\n\n        # These are optional so import them here\n        from twisted.python import threadpool\n        from twisted.python import threadable\n\n        self.threadID = threadable.getThreadID\n        self.threadpool = threadpool.ThreadPool(self.min, self.max)\n        self.startID = self._reactor.callWhenRunning(self._start)\n\n\n    def _start(self):\n        self.startID = None\n        return self.start()\n\n\n    def start(self):\n        \"\"\"\n        Start the connection pool.\n\n        If you are using the reactor normally, this function does *not*\n        need to be called.\n        \"\"\"\n        if not self.running:\n            self.threadpool.start()\n            self.shutdownID = self._reactor.addSystemEventTrigger(\n                'during', 'shutdown', self.finalClose)\n            self.running = True\n\n\n    def runWithConnection(self, func, *args, **kw):\n        \"\"\"\n        Execute a function with a database connection and return the result.\n\n        @param func: A callable object of one argument which will be executed\n            in a thread with a connection from the pool. It will be passed as\n            its first argument a L{Connection} instance (whose interface is\n            mostly identical to that of a connection object for your DB-API\n            module of choice), and its results will be returned as a\n            L{Deferred}. If the method raises an exception the transaction will\n            be rolled back. Otherwise, the transaction will be committed.\n            B{Note} that this function is B{not} run in the main thread: it\n            must be threadsafe.\n\n        @param *args: positional arguments to be passed to func\n\n        @param **kw: keyword arguments to be passed to func\n\n        @return: a L{Deferred} which will fire the return value of\n            C{func(Transaction(...), *args, **kw)}, or a\n            L{twisted.python.failure.Failure}.\n        \"\"\"\n        return threads.deferToThreadPool(self._reactor, self.threadpool,\n                                         self._runWithConnection,\n                                         func, *args, **kw)\n\n\n    def _runWithConnection(self, func, *args, **kw):\n        conn = self.connectionFactory(self)\n        try:\n            result = func(conn, *args, **kw)\n            conn.commit()\n            return result\n        except:\n            excType, excValue, excTraceback = sys.exc_info()\n            try:\n                conn.rollback()\n            except:\n                log.err(None, \"Rollback failed\")\n            compat.reraise(excValue, excTraceback)\n\n\n    def runInteraction(self, interaction, *args, **kw):\n        \"\"\"\n        Interact with the database and return the result.\n\n        The 'interaction' is a callable object which will be executed in a\n        thread using a pooled connection. It will be passed an L{Transaction}\n        object as an argument (whose interface is identical to that of the\n        database cursor for your DB-API module of choice), and its results will\n        be returned as a L{Deferred}. If running the method raises an\n        exception, the transaction will be rolled back. If the method returns a\n        value, the transaction will be committed.\n\n        NOTE that the function you pass is *not* run in the main thread: you\n        may have to worry about thread-safety in the function you pass to this\n        if it tries to use non-local objects.\n\n        @param interaction: a callable object whose first argument is an\n            L{adbapi.Transaction}.\n\n        @param *args: additional positional arguments to be passed to\n            interaction\n\n        @param **kw: keyword arguments to be passed to interaction\n\n        @return: a Deferred which will fire the return value of\n            C{interaction(Transaction(...), *args, **kw)}, or a\n            L{twisted.python.failure.Failure}.\n        \"\"\"\n        return threads.deferToThreadPool(self._reactor, self.threadpool,\n                                         self._runInteraction,\n                                         interaction, *args, **kw)\n\n\n    def runQuery(self, *args, **kw):\n        \"\"\"\n        Execute an SQL query and return the result.\n\n        A DB-API cursor which will be invoked with C{cursor.execute(*args,\n        **kw)}. The exact nature of the arguments will depend on the specific\n        flavor of DB-API being used, but the first argument in C{*args} be an\n        SQL statement. The result of a subsequent C{cursor.fetchall()} will be\n        fired to the L{Deferred} which is returned. If either the 'execute' or\n        'fetchall' methods raise an exception, the transaction will be rolled\n        back and a L{twisted.python.failure.Failure} returned.\n\n        The C{*args} and C{**kw} arguments will be passed to the DB-API\n        cursor's 'execute' method.\n\n        @return: a L{Deferred} which will fire the return value of a DB-API\n            cursor's 'fetchall' method, or a L{twisted.python.failure.Failure}.\n        \"\"\"\n        return self.runInteraction(self._runQuery, *args, **kw)\n\n\n    def runOperation(self, *args, **kw):\n        \"\"\"\n        Execute an SQL query and return L{None}.\n\n        A DB-API cursor which will be invoked with C{cursor.execute(*args,\n        **kw)}. The exact nature of the arguments will depend on the specific\n        flavor of DB-API being used, but the first argument in C{*args} will be\n        an SQL statement. This method will not attempt to fetch any results\n        from the query and is thus suitable for C{INSERT}, C{DELETE}, and other\n        SQL statements which do not return values. If the 'execute' method\n        raises an exception, the transaction will be rolled back and a\n        L{Failure} returned.\n\n        The C{*args} and C{*kw} arguments will be passed to the DB-API cursor's\n        'execute' method.\n\n        @return: a L{Deferred} which will fire with L{None} or a\n            L{twisted.python.failure.Failure}.\n        \"\"\"\n        return self.runInteraction(self._runOperation, *args, **kw)\n\n\n    def close(self):\n        \"\"\"\n        Close all pool connections and shutdown the pool.\n        \"\"\"\n        if self.shutdownID:\n            self._reactor.removeSystemEventTrigger(self.shutdownID)\n            self.shutdownID = None\n        if self.startID:\n            self._reactor.removeSystemEventTrigger(self.startID)\n            self.startID = None\n        self.finalClose()\n\n\n    def finalClose(self):\n        \"\"\"\n        This should only be called by the shutdown trigger.\n        \"\"\"\n        self.shutdownID = None\n        self.threadpool.stop()\n        self.running = False\n        for conn in self.connections.values():\n            self._close(conn)\n        self.connections.clear()\n\n\n    def connect(self):\n        \"\"\"\n        Return a database connection when one becomes available.\n\n        This method blocks and should be run in a thread from the internal\n        threadpool. Don't call this method directly from non-threaded code.\n        Using this method outside the external threadpool may exceed the\n        maximum number of connections in the pool.\n\n        @return: a database connection from the pool.\n        \"\"\"\n\n        tid = self.threadID()\n        conn = self.connections.get(tid)\n        if conn is None:\n            if self.noisy:\n                log.msg('adbapi connecting: %s' % (self.dbapiName,))\n            conn = self.dbapi.connect(*self.connargs, **self.connkw)\n            if self.openfun is not None:\n                self.openfun(conn)\n            self.connections[tid] = conn\n        return conn\n\n\n    def disconnect(self, conn):\n        \"\"\"\n        Disconnect a database connection associated with this pool.\n\n        Note: This function should only be used by the same thread which called\n        L{ConnectionPool.connect}. As with C{connect}, this function is not\n        used in normal non-threaded Twisted code.\n        \"\"\"\n        tid = self.threadID()\n        if conn is not self.connections.get(tid):\n            raise Exception(\"wrong connection for thread\")\n        if conn is not None:\n            self._close(conn)\n            del self.connections[tid]\n\n\n    def _close(self, conn):\n        if self.noisy:\n            log.msg('adbapi closing: %s' % (self.dbapiName,))\n        try:\n            conn.close()\n        except:\n            log.err(None, \"Connection close failed\")\n\n\n    def _runInteraction(self, interaction, *args, **kw):\n        conn = self.connectionFactory(self)\n        trans = self.transactionFactory(self, conn)\n        try:\n            result = interaction(trans, *args, **kw)\n            trans.close()\n            conn.commit()\n            return result\n        except:\n            excType, excValue, excTraceback = sys.exc_info()\n            try:\n                conn.rollback()\n            except:\n                log.err(None, \"Rollback failed\")\n            compat.reraise(excValue, excTraceback)\n\n\n    def _runQuery(self, trans, *args, **kw):\n        trans.execute(*args, **kw)\n        return trans.fetchall()\n\n\n    def _runOperation(self, trans, *args, **kw):\n        trans.execute(*args, **kw)\n\n\n    def __getstate__(self):\n        return {'dbapiName': self.dbapiName,\n                'min': self.min,\n                'max': self.max,\n                'noisy': self.noisy,\n                'reconnect': self.reconnect,\n                'good_sql': self.good_sql,\n                'connargs': self.connargs,\n                'connkw': self.connkw}\n\n\n    def __setstate__(self, state):\n        self.__dict__ = state\n        self.__init__(self.dbapiName, *self.connargs, **self.connkw)\n\n\n\n__all__ = ['Transaction', 'ConnectionPool']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTwisted Internet: Asynchronous I/O and Events.\n\nTwisted Internet is a collection of compatible event-loops for Python. It contains\nthe code to dispatch events to interested observers and a portable API so that\nobservers need not care about which event loop is running. Thus, it is possible\nto use the same code for different loops, from Twisted's basic, yet portable,\nselect-based loop to the loops of various GUI toolkits like GTK+ or Tk.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_baseprocess.py",
    "content": "# -*- test-case-name: twisted.test.test_process -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nCross-platform process-related functionality used by different\nL{IReactorProcess} implementations.\n\"\"\"\n\nfrom twisted.python.reflect import qual\nfrom twisted.python.deprecate import getWarningMethod\nfrom twisted.python.failure import Failure\nfrom twisted.python.log import err\n\n_missingProcessExited = (\"Since Twisted 8.2, IProcessProtocol.processExited \"\n                         \"is required.  %s must implement it.\")\n\n\n\nclass BaseProcess(object):\n    pid = None\n    status = None\n    lostProcess = 0\n    proto = None\n\n    def __init__(self, protocol):\n        self.proto = protocol\n\n\n    def _callProcessExited(self, reason):\n        default = object()\n        processExited = getattr(self.proto, 'processExited', default)\n        if processExited is default:\n            getWarningMethod()(\n                _missingProcessExited % (qual(self.proto.__class__),),\n                DeprecationWarning, stacklevel=0)\n        else:\n            try:\n                processExited(Failure(reason))\n            except:\n                err(None, \"unexpected error in processExited\")\n\n\n    def processEnded(self, status):\n        \"\"\"\n        This is called when the child terminates.\n        \"\"\"\n        self.status = status\n        self.lostProcess += 1\n        self.pid = None\n        self._callProcessExited(self._getReason(status))\n        self.maybeCallProcessEnded()\n\n\n    def maybeCallProcessEnded(self):\n        \"\"\"\n        Call processEnded on protocol after final cleanup.\n        \"\"\"\n        if self.proto is not None:\n            reason = self._getReason(self.status)\n            proto = self.proto\n            self.proto = None\n            try:\n                proto.processEnded(Failure(reason))\n            except:\n                err(None, \"unexpected error in processEnded\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_dumbwin32proc.py",
    "content": "# -*- test-case-name: twisted.test.test_process -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nhttp://isometri.cc/strips/gates_in_the_head\n\"\"\"\n\nfrom __future__ import absolute_import, division, print_function\n\nimport os\nimport sys\n\n# Win32 imports\nimport win32api\nimport win32con\nimport win32event\nimport win32file\nimport win32pipe\nimport win32process\nimport win32security\n\nimport pywintypes\n\n# Security attributes for pipes\nPIPE_ATTRS_INHERITABLE = win32security.SECURITY_ATTRIBUTES()\nPIPE_ATTRS_INHERITABLE.bInheritHandle = 1\n\nfrom zope.interface import implementer\nfrom twisted.internet.interfaces import IProcessTransport, IConsumer, IProducer\n\nfrom twisted.python.compat import items, _PY3\nfrom twisted.python.win32 import quoteArguments\nfrom twisted.python.util import _replaceIf\n\nfrom twisted.internet import error\n\nfrom twisted.internet import _pollingfile\nfrom twisted.internet._baseprocess import BaseProcess\n\n\n@_replaceIf(_PY3, getattr(os, 'fsdecode', None))\ndef _fsdecode(x):\n    \"\"\"\n    Decode a string to a L{unicode} representation, passing\n    through existing L{unicode} unchanged.\n\n    @param x: The string to be conditionally decoded.\n    @type x: L{bytes} or L{unicode}\n\n    @return: L{unicode}\n    \"\"\"\n    if isinstance(x, bytes):\n        return x.decode(sys.getfilesystemencoding())\n    else:\n        return x\n\n\n\ndef debug(msg):\n    print(msg)\n    sys.stdout.flush()\n\n\n\nclass _Reaper(_pollingfile._PollableResource):\n\n    def __init__(self, proc):\n        self.proc = proc\n\n\n    def checkWork(self):\n        if win32event.WaitForSingleObject(self.proc.hProcess, 0) != win32event.WAIT_OBJECT_0:\n            return 0\n        exitCode = win32process.GetExitCodeProcess(self.proc.hProcess)\n        self.deactivate()\n        self.proc.processEnded(exitCode)\n        return 0\n\n\n\ndef _findShebang(filename):\n    \"\"\"\n    Look for a #! line, and return the value following the #! if one exists, or\n    None if this file is not a script.\n\n    I don't know if there are any conventions for quoting in Windows shebang\n    lines, so this doesn't support any; therefore, you may not pass any\n    arguments to scripts invoked as filters.  That's probably wrong, so if\n    somebody knows more about the cultural expectations on Windows, please feel\n    free to fix.\n\n    This shebang line support was added in support of the CGI tests;\n    appropriately enough, I determined that shebang lines are culturally\n    accepted in the Windows world through this page::\n\n        http://www.cgi101.com/learn/connect/winxp.html\n\n    @param filename: str representing a filename\n\n    @return: a str representing another filename.\n    \"\"\"\n    with open(filename, 'rU') as f:\n        if f.read(2) == '#!':\n            exe = f.readline(1024).strip('\\n')\n            return exe\n\n\n\ndef _invalidWin32App(pywinerr):\n    \"\"\"\n    Determine if a pywintypes.error is telling us that the given process is\n    'not a valid win32 application', i.e. not a PE format executable.\n\n    @param pywinerr: a pywintypes.error instance raised by CreateProcess\n\n    @return: a boolean\n    \"\"\"\n\n    # Let's do this better in the future, but I have no idea what this error\n    # is; MSDN doesn't mention it, and there is no symbolic constant in\n    # win32process module that represents 193.\n\n    return pywinerr.args[0] == 193\n\n\n\n@implementer(IProcessTransport, IConsumer, IProducer)\nclass Process(_pollingfile._PollingTimer, BaseProcess):\n    \"\"\"\n    A process that integrates with the Twisted event loop.\n\n    If your subprocess is a python program, you need to:\n\n     - Run python.exe with the '-u' command line option - this turns on\n       unbuffered I/O. Buffering stdout/err/in can cause problems, see e.g.\n       http://support.microsoft.com/default.aspx?scid=kb;EN-US;q1903\n\n     - If you don't want Windows messing with data passed over\n       stdin/out/err, set the pipes to be in binary mode::\n\n        import os, sys, mscvrt\n        msvcrt.setmode(sys.stdin.fileno(), os.O_BINARY)\n        msvcrt.setmode(sys.stdout.fileno(), os.O_BINARY)\n        msvcrt.setmode(sys.stderr.fileno(), os.O_BINARY)\n\n    \"\"\"\n    closedNotifies = 0\n\n    def __init__(self, reactor, protocol, command, args, environment, path):\n        \"\"\"\n        Create a new child process.\n        \"\"\"\n        _pollingfile._PollingTimer.__init__(self, reactor)\n        BaseProcess.__init__(self, protocol)\n\n        # security attributes for pipes\n        sAttrs = win32security.SECURITY_ATTRIBUTES()\n        sAttrs.bInheritHandle = 1\n\n        # create the pipes which will connect to the secondary process\n        self.hStdoutR, hStdoutW = win32pipe.CreatePipe(sAttrs, 0)\n        self.hStderrR, hStderrW = win32pipe.CreatePipe(sAttrs, 0)\n        hStdinR, self.hStdinW  = win32pipe.CreatePipe(sAttrs, 0)\n\n        win32pipe.SetNamedPipeHandleState(self.hStdinW,\n                                          win32pipe.PIPE_NOWAIT,\n                                          None,\n                                          None)\n\n        # set the info structure for the new process.\n        StartupInfo = win32process.STARTUPINFO()\n        StartupInfo.hStdOutput = hStdoutW\n        StartupInfo.hStdError  = hStderrW\n        StartupInfo.hStdInput  = hStdinR\n        StartupInfo.dwFlags = win32process.STARTF_USESTDHANDLES\n\n        # Create new handles whose inheritance property is false\n        currentPid = win32api.GetCurrentProcess()\n\n        tmp = win32api.DuplicateHandle(currentPid, self.hStdoutR, currentPid, 0, 0,\n                                       win32con.DUPLICATE_SAME_ACCESS)\n        win32file.CloseHandle(self.hStdoutR)\n        self.hStdoutR = tmp\n\n        tmp = win32api.DuplicateHandle(currentPid, self.hStderrR, currentPid, 0, 0,\n                                       win32con.DUPLICATE_SAME_ACCESS)\n        win32file.CloseHandle(self.hStderrR)\n        self.hStderrR = tmp\n\n        tmp = win32api.DuplicateHandle(currentPid, self.hStdinW, currentPid, 0, 0,\n                                       win32con.DUPLICATE_SAME_ACCESS)\n        win32file.CloseHandle(self.hStdinW)\n        self.hStdinW = tmp\n\n        # Add the specified environment to the current environment - this is\n        # necessary because certain operations are only supported on Windows\n        # if certain environment variables are present.\n\n        env = os.environ.copy()\n        env.update(environment or {})\n        newenv = {}\n        for key, value in items(env):\n\n            key = _fsdecode(key)\n            value = _fsdecode(value)\n\n            newenv[key] = value\n\n        env = newenv\n\n        # Make sure all the arguments are Unicode.\n        args = [_fsdecode(x) for x in args]\n\n        cmdline = quoteArguments(args)\n\n        # The command, too, needs to be Unicode, if it is a value.\n        command = _fsdecode(command) if command else command\n        path = _fsdecode(path) if path else path\n\n        # TODO: error detection here.  See #2787 and #4184.\n        def doCreate():\n            flags = win32con.CREATE_NO_WINDOW\n            self.hProcess, self.hThread, self.pid, dwTid = win32process.CreateProcess(\n                command, cmdline, None, None, 1, flags, env, path, StartupInfo)\n        try:\n            doCreate()\n        except pywintypes.error as pwte:\n            if not _invalidWin32App(pwte):\n                # This behavior isn't _really_ documented, but let's make it\n                # consistent with the behavior that is documented.\n                raise OSError(pwte)\n            else:\n                # look for a shebang line.  Insert the original 'command'\n                # (actually a script) into the new arguments list.\n                sheb = _findShebang(command)\n                if sheb is None:\n                    raise OSError(\n                        \"%r is neither a Windows executable, \"\n                        \"nor a script with a shebang line\" % command)\n                else:\n                    args = list(args)\n                    args.insert(0, command)\n                    cmdline = quoteArguments(args)\n                    origcmd = command\n                    command = sheb\n                    try:\n                        # Let's try again.\n                        doCreate()\n                    except pywintypes.error as pwte2:\n                        # d'oh, failed again!\n                        if _invalidWin32App(pwte2):\n                            raise OSError(\n                                \"%r has an invalid shebang line: \"\n                                \"%r is not a valid executable\" % (\n                                    origcmd, sheb))\n                        raise OSError(pwte2)\n\n        # close handles which only the child will use\n        win32file.CloseHandle(hStderrW)\n        win32file.CloseHandle(hStdoutW)\n        win32file.CloseHandle(hStdinR)\n\n        # set up everything\n        self.stdout = _pollingfile._PollableReadPipe(\n            self.hStdoutR,\n            lambda data: self.proto.childDataReceived(1, data),\n            self.outConnectionLost)\n\n        self.stderr = _pollingfile._PollableReadPipe(\n                self.hStderrR,\n                lambda data: self.proto.childDataReceived(2, data),\n                self.errConnectionLost)\n\n        self.stdin = _pollingfile._PollableWritePipe(\n            self.hStdinW, self.inConnectionLost)\n\n        for pipewatcher in self.stdout, self.stderr, self.stdin:\n            self._addPollableResource(pipewatcher)\n\n        # notify protocol\n        self.proto.makeConnection(self)\n\n        self._addPollableResource(_Reaper(self))\n\n\n    def signalProcess(self, signalID):\n        if self.pid is None:\n            raise error.ProcessExitedAlready()\n        if signalID in (\"INT\", \"TERM\", \"KILL\"):\n            win32process.TerminateProcess(self.hProcess, 1)\n\n\n    def _getReason(self, status):\n        if status == 0:\n            return error.ProcessDone(status)\n        return error.ProcessTerminated(status)\n\n\n    def write(self, data):\n        \"\"\"\n        Write data to the process' stdin.\n\n        @type data: C{bytes}\n        \"\"\"\n        self.stdin.write(data)\n\n\n    def writeSequence(self, seq):\n        \"\"\"\n        Write data to the process' stdin.\n\n        @type data: C{list} of C{bytes}\n        \"\"\"\n        self.stdin.writeSequence(seq)\n\n\n    def writeToChild(self, fd, data):\n        \"\"\"\n        Similar to L{ITransport.write} but also allows the file descriptor in\n        the child process which will receive the bytes to be specified.\n\n        This implementation is limited to writing to the child's standard input.\n\n        @param fd: The file descriptor to which to write.  Only stdin (C{0}) is\n            supported.\n        @type fd: C{int}\n\n        @param data: The bytes to write.\n        @type data: C{bytes}\n\n        @return: L{None}\n\n        @raise KeyError: If C{fd} is anything other than the stdin file\n            descriptor (C{0}).\n        \"\"\"\n        if fd == 0:\n            self.stdin.write(data)\n        else:\n            raise KeyError(fd)\n\n\n    def closeChildFD(self, fd):\n        if fd == 0:\n            self.closeStdin()\n        elif fd == 1:\n            self.closeStdout()\n        elif fd == 2:\n            self.closeStderr()\n        else:\n            raise NotImplementedError(\"Only standard-IO file descriptors available on win32\")\n\n\n    def closeStdin(self):\n        \"\"\"Close the process' stdin.\n        \"\"\"\n        self.stdin.close()\n\n\n    def closeStderr(self):\n        self.stderr.close()\n\n\n    def closeStdout(self):\n        self.stdout.close()\n\n\n    def loseConnection(self):\n        \"\"\"\n        Close the process' stdout, in and err.\n        \"\"\"\n        self.closeStdin()\n        self.closeStdout()\n        self.closeStderr()\n\n\n    def outConnectionLost(self):\n        self.proto.childConnectionLost(1)\n        self.connectionLostNotify()\n\n\n    def errConnectionLost(self):\n        self.proto.childConnectionLost(2)\n        self.connectionLostNotify()\n\n\n    def inConnectionLost(self):\n        self.proto.childConnectionLost(0)\n        self.connectionLostNotify()\n\n\n    def connectionLostNotify(self):\n        \"\"\"\n        Will be called 3 times, by stdout/err threads and process handle.\n        \"\"\"\n        self.closedNotifies += 1\n        self.maybeCallProcessEnded()\n\n\n    def maybeCallProcessEnded(self):\n        if self.closedNotifies == 3 and self.lostProcess:\n            win32file.CloseHandle(self.hProcess)\n            win32file.CloseHandle(self.hThread)\n            self.hProcess = None\n            self.hThread = None\n            BaseProcess.maybeCallProcessEnded(self)\n\n    # IConsumer\n    def registerProducer(self, producer, streaming):\n        self.stdin.registerProducer(producer, streaming)\n\n\n    def unregisterProducer(self):\n        self.stdin.unregisterProducer()\n\n    # IProducer\n    def pauseProducing(self):\n        self._pause()\n\n\n    def resumeProducing(self):\n        self._unpause()\n\n\n    def stopProducing(self):\n        self.loseConnection()\n\n\n    def __repr__(self):\n        \"\"\"\n        Return a string representation of the process.\n        \"\"\"\n        return \"<%s pid=%s>\" % (self.__class__.__name__, self.pid)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_glibbase.py",
    "content": "# -*- test-case-name: twisted.internet.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module provides base support for Twisted to interact with the glib/gtk\nmainloops.\n\nThe classes in this module should not be used directly, but rather you should\nimport gireactor or gtk3reactor for GObject Introspection based applications,\nor glib2reactor or gtk2reactor for applications using legacy static bindings.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport sys\n\nfrom zope.interface import implementer\n\nfrom twisted.internet import base, posixbase, selectreactor\nfrom twisted.internet.interfaces import IReactorFDSet\nfrom twisted.python import log\n\n\n\ndef ensureNotImported(moduleNames, errorMessage, preventImports=[]):\n    \"\"\"\n    Check whether the given modules were imported, and if requested, ensure\n    they will not be importable in the future.\n\n    @param moduleNames: A list of module names we make sure aren't imported.\n    @type moduleNames: C{list} of C{str}\n\n    @param preventImports: A list of module name whose future imports should\n        be prevented.\n    @type preventImports: C{list} of C{str}\n\n    @param errorMessage: Message to use when raising an C{ImportError}.\n    @type errorMessage: C{str}\n\n    @raises: C{ImportError} with given error message if a given module name\n        has already been imported.\n    \"\"\"\n    for name in moduleNames:\n        if sys.modules.get(name) is not None:\n            raise ImportError(errorMessage)\n\n    # Disable module imports to avoid potential problems.\n    for name in preventImports:\n        sys.modules[name] = None\n\n\n\nclass GlibWaker(posixbase._UnixWaker):\n    \"\"\"\n    Run scheduled events after waking up.\n    \"\"\"\n\n    def doRead(self):\n        posixbase._UnixWaker.doRead(self)\n        self.reactor._simulate()\n\n\n\n@implementer(IReactorFDSet)\nclass GlibReactorBase(posixbase.PosixReactorBase, posixbase._PollLikeMixin):\n    \"\"\"\n    Base class for GObject event loop reactors.\n\n    Notification for I/O events (reads and writes on file descriptors) is done\n    by the gobject-based event loop. File descriptors are registered with\n    gobject with the appropriate flags for read/write/disconnect notification.\n\n    Time-based events, the results of C{callLater} and C{callFromThread}, are\n    handled differently. Rather than registering each event with gobject, a\n    single gobject timeout is registered for the earliest scheduled event, the\n    output of C{reactor.timeout()}. For example, if there are timeouts in 1, 2\n    and 3.4 seconds, a single timeout is registered for 1 second in the\n    future. When this timeout is hit, C{_simulate} is called, which calls the\n    appropriate Twisted-level handlers, and a new timeout is added to gobject\n    by the C{_reschedule} method.\n\n    To handle C{callFromThread} events, we use a custom waker that calls\n    C{_simulate} whenever it wakes up.\n\n    @ivar _sources: A dictionary mapping L{FileDescriptor} instances to\n        GSource handles.\n\n    @ivar _reads: A set of L{FileDescriptor} instances currently monitored for\n        reading.\n\n    @ivar _writes: A set of L{FileDescriptor} instances currently monitored for\n        writing.\n\n    @ivar _simtag: A GSource handle for the next L{simulate} call.\n    \"\"\"\n\n    # Install a waker that knows it needs to call C{_simulate} in order to run\n    # callbacks queued from a thread:\n    _wakerFactory = GlibWaker\n\n    def __init__(self, glib_module, gtk_module, useGtk=False):\n        self._simtag = None\n        self._reads = set()\n        self._writes = set()\n        self._sources = {}\n        self._glib = glib_module\n        self._gtk = gtk_module\n        posixbase.PosixReactorBase.__init__(self)\n\n        self._source_remove = self._glib.source_remove\n        self._timeout_add = self._glib.timeout_add\n\n        def _mainquit():\n            if self._gtk.main_level():\n                self._gtk.main_quit()\n\n        if useGtk:\n            self._pending = self._gtk.events_pending\n            self._iteration = self._gtk.main_iteration_do\n            self._crash = _mainquit\n            self._run = self._gtk.main\n        else:\n            self.context = self._glib.main_context_default()\n            self._pending = self.context.pending\n            self._iteration = self.context.iteration\n            self.loop = self._glib.MainLoop()\n            self._crash = lambda: self._glib.idle_add(self.loop.quit)\n            self._run = self.loop.run\n\n\n    def _handleSignals(self):\n        # First, install SIGINT and friends:\n        base._SignalReactorMixin._handleSignals(self)\n        # Next, since certain versions of gtk will clobber our signal handler,\n        # set all signal handlers again after the event loop has started to\n        # ensure they're *really* set. We don't call this twice so we don't\n        # leak file descriptors created in the SIGCHLD initialization:\n        self.callLater(0, posixbase.PosixReactorBase._handleSignals, self)\n\n\n    # The input_add function in pygtk1 checks for objects with a\n    # 'fileno' method and, if present, uses the result of that method\n    # as the input source. The pygtk2 input_add does not do this. The\n    # function below replicates the pygtk1 functionality.\n\n    # In addition, pygtk maps gtk.input_add to _gobject.io_add_watch, and\n    # g_io_add_watch() takes different condition bitfields than\n    # gtk_input_add(). We use g_io_add_watch() here in case pygtk fixes this\n    # bug.\n    def input_add(self, source, condition, callback):\n        if hasattr(source, 'fileno'):\n            # handle python objects\n            def wrapper(ignored, condition):\n                return callback(source, condition)\n            fileno = source.fileno()\n        else:\n            fileno = source\n            wrapper = callback\n        return self._glib.io_add_watch(\n            fileno, condition, wrapper,\n            priority=self._glib.PRIORITY_DEFAULT_IDLE)\n\n\n    def _ioEventCallback(self, source, condition):\n        \"\"\"\n        Called by event loop when an I/O event occurs.\n        \"\"\"\n        log.callWithLogger(\n            source, self._doReadOrWrite, source, source, condition)\n        return True  # True = don't auto-remove the source\n\n\n    def _add(self, source, primary, other, primaryFlag, otherFlag):\n        \"\"\"\n        Add the given L{FileDescriptor} for monitoring either for reading or\n        writing. If the file is already monitored for the other operation, we\n        delete the previous registration and re-register it for both reading\n        and writing.\n        \"\"\"\n        if source in primary:\n            return\n        flags = primaryFlag\n        if source in other:\n            self._source_remove(self._sources[source])\n            flags |= otherFlag\n        self._sources[source] = self.input_add(\n            source, flags, self._ioEventCallback)\n        primary.add(source)\n\n\n    def addReader(self, reader):\n        \"\"\"\n        Add a L{FileDescriptor} for monitoring of data available to read.\n        \"\"\"\n        self._add(reader, self._reads, self._writes,\n                  self.INFLAGS, self.OUTFLAGS)\n\n\n    def addWriter(self, writer):\n        \"\"\"\n        Add a L{FileDescriptor} for monitoring ability to write data.\n        \"\"\"\n        self._add(writer, self._writes, self._reads,\n                  self.OUTFLAGS, self.INFLAGS)\n\n\n    def getReaders(self):\n        \"\"\"\n        Retrieve the list of current L{FileDescriptor} monitored for reading.\n        \"\"\"\n        return list(self._reads)\n\n\n    def getWriters(self):\n        \"\"\"\n        Retrieve the list of current L{FileDescriptor} monitored for writing.\n        \"\"\"\n        return list(self._writes)\n\n\n    def removeAll(self):\n        \"\"\"\n        Remove monitoring for all registered L{FileDescriptor}s.\n        \"\"\"\n        return self._removeAll(self._reads, self._writes)\n\n\n    def _remove(self, source, primary, other, flags):\n        \"\"\"\n        Remove monitoring the given L{FileDescriptor} for either reading or\n        writing. If it's still monitored for the other operation, we\n        re-register the L{FileDescriptor} for only that operation.\n        \"\"\"\n        if source not in primary:\n            return\n        self._source_remove(self._sources[source])\n        primary.remove(source)\n        if source in other:\n            self._sources[source] = self.input_add(\n                source, flags, self._ioEventCallback)\n        else:\n            self._sources.pop(source)\n\n\n    def removeReader(self, reader):\n        \"\"\"\n        Stop monitoring the given L{FileDescriptor} for reading.\n        \"\"\"\n        self._remove(reader, self._reads, self._writes, self.OUTFLAGS)\n\n\n    def removeWriter(self, writer):\n        \"\"\"\n        Stop monitoring the given L{FileDescriptor} for writing.\n        \"\"\"\n        self._remove(writer, self._writes, self._reads, self.INFLAGS)\n\n\n    def iterate(self, delay=0):\n        \"\"\"\n        One iteration of the event loop, for trial's use.\n\n        This is not used for actual reactor runs.\n        \"\"\"\n        self.runUntilCurrent()\n        while self._pending():\n            self._iteration(0)\n\n\n    def crash(self):\n        \"\"\"\n        Crash the reactor.\n        \"\"\"\n        posixbase.PosixReactorBase.crash(self)\n        self._crash()\n\n\n    def stop(self):\n        \"\"\"\n        Stop the reactor.\n        \"\"\"\n        posixbase.PosixReactorBase.stop(self)\n        # The base implementation only sets a flag, to ensure shutting down is\n        # not reentrant. Unfortunately, this flag is not meaningful to the\n        # gobject event loop. We therefore call wakeUp() to ensure the event\n        # loop will call back into Twisted once this iteration is done. This\n        # will result in self.runUntilCurrent() being called, where the stop\n        # flag will trigger the actual shutdown process, eventually calling\n        # crash() which will do the actual gobject event loop shutdown.\n        self.wakeUp()\n\n\n    def run(self, installSignalHandlers=True):\n        \"\"\"\n        Run the reactor.\n        \"\"\"\n        self.callWhenRunning(self._reschedule)\n        self.startRunning(installSignalHandlers=installSignalHandlers)\n        if self._started:\n            self._run()\n\n\n    def callLater(self, *args, **kwargs):\n        \"\"\"\n        Schedule a C{DelayedCall}.\n        \"\"\"\n        result = posixbase.PosixReactorBase.callLater(self, *args, **kwargs)\n        # Make sure we'll get woken up at correct time to handle this new\n        # scheduled call:\n        self._reschedule()\n        return result\n\n\n    def _reschedule(self):\n        \"\"\"\n        Schedule a glib timeout for C{_simulate}.\n        \"\"\"\n        if self._simtag is not None:\n            self._source_remove(self._simtag)\n            self._simtag = None\n        timeout = self.timeout()\n        if timeout is not None:\n            self._simtag = self._timeout_add(\n                int(timeout * 1000), self._simulate,\n                priority=self._glib.PRIORITY_DEFAULT_IDLE)\n\n\n    def _simulate(self):\n        \"\"\"\n        Run timers, and then reschedule glib timeout for next scheduled event.\n        \"\"\"\n        self.runUntilCurrent()\n        self._reschedule()\n\n\n\nclass PortableGlibReactorBase(selectreactor.SelectReactor):\n    \"\"\"\n    Base class for GObject event loop reactors that works on Windows.\n\n    Sockets aren't supported by GObject's input_add on Win32.\n    \"\"\"\n    def __init__(self, glib_module, gtk_module, useGtk=False):\n        self._simtag = None\n        self._glib = glib_module\n        self._gtk = gtk_module\n        selectreactor.SelectReactor.__init__(self)\n\n        self._source_remove = self._glib.source_remove\n        self._timeout_add = self._glib.timeout_add\n\n        def _mainquit():\n            if self._gtk.main_level():\n                self._gtk.main_quit()\n\n        if useGtk:\n            self._crash = _mainquit\n            self._run = self._gtk.main\n        else:\n            self.loop = self._glib.MainLoop()\n            self._crash = lambda: self._glib.idle_add(self.loop.quit)\n            self._run = self.loop.run\n\n\n    def crash(self):\n        selectreactor.SelectReactor.crash(self)\n        self._crash()\n\n\n    def run(self, installSignalHandlers=True):\n        self.startRunning(installSignalHandlers=installSignalHandlers)\n        self._timeout_add(0, self.simulate)\n        if self._started:\n            self._run()\n\n\n    def simulate(self):\n        \"\"\"\n        Run simulation loops and reschedule callbacks.\n        \"\"\"\n        if self._simtag is not None:\n            self._source_remove(self._simtag)\n        self.iterate()\n        timeout = min(self.timeout(), 0.01)\n        if timeout is None:\n            timeout = 0.01\n        self._simtag = self._timeout_add(\n            int(timeout * 1000), self.simulate,\n            priority=self._glib.PRIORITY_DEFAULT_IDLE)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_idna.py",
    "content": "# -*- test-case-name: twisted.test.test_sslverify -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nShared interface to IDNA encoding and decoding, using the C{idna} PyPI package\nif available, otherwise the stdlib implementation.\n\"\"\"\n\ndef _idnaBytes(text):\n    \"\"\"\n    Convert some text typed by a human into some ASCII bytes.\n\n    This is provided to allow us to use the U{partially-broken IDNA\n    implementation in the standard library <http://bugs.python.org/issue17305>}\n    if the more-correct U{idna <https://pypi.python.org/pypi/idna>} package is\n    not available; C{service_identity} is somewhat stricter about this.\n\n    @param text: A domain name, hopefully.\n    @type text: L{unicode}\n\n    @return: The domain name's IDNA representation, encoded as bytes.\n    @rtype: L{bytes}\n    \"\"\"\n    try:\n        import idna\n    except ImportError:\n        return text.encode(\"idna\")\n    else:\n        return idna.encode(text)\n\n\n\ndef _idnaText(octets):\n    \"\"\"\n    Convert some IDNA-encoded octets into some human-readable text.\n\n    Currently only used by the tests.\n\n    @param octets: Some bytes representing a hostname.\n    @type octets: L{bytes}\n\n    @return: A human-readable domain name.\n    @rtype: L{unicode}\n    \"\"\"\n    try:\n        import idna\n    except ImportError:\n        return octets.decode(\"idna\")\n    else:\n        return idna.decode(octets)\n\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_newtls.py",
    "content": "# -*- test-case-name: twisted.test.test_ssl -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module implements memory BIO based TLS support.  It is the preferred\nimplementation and will be used whenever pyOpenSSL 0.10 or newer is installed\n(whenever L{twisted.protocols.tls} is importable).\n\n@since: 11.1\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom zope.interface import implementer\nfrom zope.interface import directlyProvides\n\nfrom twisted.internet.interfaces import ITLSTransport, ISSLTransport\nfrom twisted.internet.abstract import FileDescriptor\n\nfrom twisted.protocols.tls import TLSMemoryBIOFactory, TLSMemoryBIOProtocol\n\n\nclass _BypassTLS(object):\n    \"\"\"\n    L{_BypassTLS} is used as the transport object for the TLS protocol object\n    used to implement C{startTLS}.  Its methods skip any TLS logic which\n    C{startTLS} enables.\n\n    @ivar _base: A transport class L{_BypassTLS} has been mixed in with to which\n        methods will be forwarded.  This class is only responsible for sending\n        bytes over the connection, not doing TLS.\n\n    @ivar _connection: A L{Connection} which TLS has been started on which will\n        be proxied to by this object.  Any method which has its behavior\n        altered after C{startTLS} will be skipped in favor of the base class's\n        implementation.  This allows the TLS protocol object to have direct\n        access to the transport, necessary to actually implement TLS.\n    \"\"\"\n    def __init__(self, base, connection):\n        self._base = base\n        self._connection = connection\n\n\n    def __getattr__(self, name):\n        \"\"\"\n        Forward any extra attribute access to the original transport object.\n        For example, this exposes C{getHost}, the behavior of which does not\n        change after TLS is enabled.\n        \"\"\"\n        return getattr(self._connection, name)\n\n\n    def write(self, data):\n        \"\"\"\n        Write some bytes directly to the connection.\n        \"\"\"\n        return self._base.write(self._connection, data)\n\n\n    def writeSequence(self, iovec):\n        \"\"\"\n        Write a some bytes directly to the connection.\n        \"\"\"\n        return self._base.writeSequence(self._connection, iovec)\n\n\n    def loseConnection(self, *args, **kwargs):\n        \"\"\"\n        Close the underlying connection.\n        \"\"\"\n        return self._base.loseConnection(self._connection, *args, **kwargs)\n\n\n    def registerProducer(self, producer, streaming):\n        \"\"\"\n        Register a producer with the underlying connection.\n        \"\"\"\n        return self._base.registerProducer(self._connection, producer, streaming)\n\n\n    def unregisterProducer(self):\n        \"\"\"\n        Unregister a producer with the underlying connection.\n        \"\"\"\n        return self._base.unregisterProducer(self._connection)\n\n\n\ndef startTLS(transport, contextFactory, normal, bypass):\n    \"\"\"\n    Add a layer of SSL to a transport.\n\n    @param transport: The transport which will be modified.  This can either by\n        a L{FileDescriptor<twisted.internet.abstract.FileDescriptor>} or a\n        L{FileHandle<twisted.internet.iocpreactor.abstract.FileHandle>}.  The\n        actual requirements of this instance are that it have:\n\n          - a C{_tlsClientDefault} attribute indicating whether the transport is\n            a client (C{True}) or a server (C{False})\n          - a settable C{TLS} attribute which can be used to mark the fact\n            that SSL has been started\n          - settable C{getHandle} and C{getPeerCertificate} attributes so\n            these L{ISSLTransport} methods can be added to it\n          - a C{protocol} attribute referring to the L{IProtocol} currently\n            connected to the transport, which can also be set to a new\n            L{IProtocol} for the transport to deliver data to\n\n    @param contextFactory: An SSL context factory defining SSL parameters for\n        the new SSL layer.\n    @type contextFactory: L{twisted.internet.interfaces.IOpenSSLContextFactory}\n\n    @param normal: A flag indicating whether SSL will go in the same direction\n        as the underlying transport goes.  That is, if the SSL client will be\n        the underlying client and the SSL server will be the underlying server.\n        C{True} means it is the same, C{False} means they are switched.\n    @type param: L{bool}\n\n    @param bypass: A transport base class to call methods on to bypass the new\n        SSL layer (so that the SSL layer itself can send its bytes).\n    @type bypass: L{type}\n    \"\"\"\n    # Figure out which direction the SSL goes in.  If normal is True,\n    # we'll go in the direction indicated by the subclass.  Otherwise,\n    # we'll go the other way (client = not normal ^ _tlsClientDefault,\n    # in other words).\n    if normal:\n        client = transport._tlsClientDefault\n    else:\n        client = not transport._tlsClientDefault\n\n    # If we have a producer, unregister it, and then re-register it below once\n    # we've switched to TLS mode, so it gets hooked up correctly:\n    producer, streaming = None, None\n    if transport.producer is not None:\n        producer, streaming = transport.producer, transport.streamingProducer\n        transport.unregisterProducer()\n\n    tlsFactory = TLSMemoryBIOFactory(contextFactory, client, None)\n    tlsProtocol = TLSMemoryBIOProtocol(tlsFactory, transport.protocol, False)\n    transport.protocol = tlsProtocol\n\n    transport.getHandle = tlsProtocol.getHandle\n    transport.getPeerCertificate = tlsProtocol.getPeerCertificate\n\n    # Mark the transport as secure.\n    directlyProvides(transport, ISSLTransport)\n\n    # Remember we did this so that write and writeSequence can send the\n    # data to the right place.\n    transport.TLS = True\n\n    # Hook it up\n    transport.protocol.makeConnection(_BypassTLS(bypass, transport))\n\n    # Restore producer if necessary:\n    if producer:\n        transport.registerProducer(producer, streaming)\n\n\n\n@implementer(ITLSTransport)\nclass ConnectionMixin(object):\n    \"\"\"\n    A mixin for L{twisted.internet.abstract.FileDescriptor} which adds an\n    L{ITLSTransport} implementation.\n\n    @ivar TLS: A flag indicating whether TLS is currently in use on this\n        transport.  This is not a good way for applications to check for TLS,\n        instead use L{twisted.internet.interfaces.ISSLTransport}.\n    \"\"\"\n\n    TLS = False\n\n    def startTLS(self, ctx, normal=True):\n        \"\"\"\n        @see: L{ITLSTransport.startTLS}\n        \"\"\"\n        startTLS(self, ctx, normal, FileDescriptor)\n\n\n    def write(self, bytes):\n        \"\"\"\n        Write some bytes to this connection, passing them through a TLS layer if\n        necessary, or discarding them if the connection has already been lost.\n        \"\"\"\n        if self.TLS:\n            if self.connected:\n                self.protocol.write(bytes)\n        else:\n            FileDescriptor.write(self, bytes)\n\n\n    def writeSequence(self, iovec):\n        \"\"\"\n        Write some bytes to this connection, scatter/gather-style, passing them\n        through a TLS layer if necessary, or discarding them if the connection\n        has already been lost.\n        \"\"\"\n        if self.TLS:\n            if self.connected:\n                self.protocol.writeSequence(iovec)\n        else:\n            FileDescriptor.writeSequence(self, iovec)\n\n\n    def loseConnection(self):\n        \"\"\"\n        Close this connection after writing all pending data.\n\n        If TLS has been negotiated, perform a TLS shutdown.\n        \"\"\"\n        if self.TLS:\n            if self.connected and not self.disconnecting:\n                self.protocol.loseConnection()\n        else:\n            FileDescriptor.loseConnection(self)\n\n\n    def registerProducer(self, producer, streaming):\n        \"\"\"\n        Register a producer.\n\n        If TLS is enabled, the TLS connection handles this.\n        \"\"\"\n        if self.TLS:\n            # Registering a producer before we're connected shouldn't be a\n            # problem. If we end up with a write(), that's already handled in\n            # the write() code above, and there are no other potential\n            # side-effects.\n            self.protocol.registerProducer(producer, streaming)\n        else:\n            FileDescriptor.registerProducer(self, producer, streaming)\n\n\n    def unregisterProducer(self):\n        \"\"\"\n        Unregister a producer.\n\n        If TLS is enabled, the TLS connection handles this.\n        \"\"\"\n        if self.TLS:\n            self.protocol.unregisterProducer()\n        else:\n            FileDescriptor.unregisterProducer(self)\n\n\n\nclass ClientMixin(object):\n    \"\"\"\n    A mixin for L{twisted.internet.tcp.Client} which just marks it as a client\n    for the purposes of the default TLS handshake.\n\n    @ivar _tlsClientDefault: Always C{True}, indicating that this is a client\n        connection, and by default when TLS is negotiated this class will act as\n        a TLS client.\n    \"\"\"\n    _tlsClientDefault = True\n\n\n\nclass ServerMixin(object):\n    \"\"\"\n    A mixin for L{twisted.internet.tcp.Server} which just marks it as a server\n    for the purposes of the default TLS handshake.\n\n    @ivar _tlsClientDefault: Always C{False}, indicating that this is a server\n        connection, and by default when TLS is negotiated this class will act as\n        a TLS server.\n    \"\"\"\n    _tlsClientDefault = False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_pollingfile.py",
    "content": "# -*- test-case-name: twisted.internet.test.test_pollingfile -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nImplements a simple polling interface for file descriptors that don't work with\nselect() - this is pretty much only useful on Windows.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom zope.interface import implementer\nfrom twisted.internet.interfaces import IConsumer, IPushProducer\nfrom twisted.python.compat import unicode\n\n\nMIN_TIMEOUT = 0.000000001\nMAX_TIMEOUT = 0.1\n\n\n\nclass _PollableResource:\n    active = True\n\n    def activate(self):\n        self.active = True\n\n\n    def deactivate(self):\n        self.active = False\n\n\n\nclass _PollingTimer:\n    # Everything is private here because it is really an implementation detail.\n\n    def __init__(self, reactor):\n        self.reactor = reactor\n        self._resources = []\n        self._pollTimer = None\n        self._currentTimeout = MAX_TIMEOUT\n        self._paused = False\n\n    def _addPollableResource(self, res):\n        self._resources.append(res)\n        self._checkPollingState()\n\n    def _checkPollingState(self):\n        for resource in self._resources:\n            if resource.active:\n                self._startPolling()\n                break\n        else:\n            self._stopPolling()\n\n    def _startPolling(self):\n        if self._pollTimer is None:\n            self._pollTimer = self._reschedule()\n\n    def _stopPolling(self):\n        if self._pollTimer is not None:\n            self._pollTimer.cancel()\n            self._pollTimer = None\n\n    def _pause(self):\n        self._paused = True\n\n    def _unpause(self):\n        self._paused = False\n        self._checkPollingState()\n\n    def _reschedule(self):\n        if not self._paused:\n            return self.reactor.callLater(self._currentTimeout, self._pollEvent)\n\n    def _pollEvent(self):\n        workUnits = 0.\n        anyActive = []\n        for resource in self._resources:\n            if resource.active:\n                workUnits += resource.checkWork()\n                # Check AFTER work has been done\n                if resource.active:\n                    anyActive.append(resource)\n\n        newTimeout = self._currentTimeout\n        if workUnits:\n            newTimeout = self._currentTimeout / (workUnits + 1.)\n            if newTimeout < MIN_TIMEOUT:\n                newTimeout = MIN_TIMEOUT\n        else:\n            newTimeout = self._currentTimeout * 2.\n            if newTimeout > MAX_TIMEOUT:\n                newTimeout = MAX_TIMEOUT\n        self._currentTimeout = newTimeout\n        if anyActive:\n            self._pollTimer = self._reschedule()\n\n\n# If we ever (let's hope not) need the above functionality on UNIX, this could\n# be factored into a different module.\n\nimport win32pipe\nimport win32file\nimport win32api\nimport pywintypes\n\n@implementer(IPushProducer)\nclass _PollableReadPipe(_PollableResource):\n\n    def __init__(self, pipe, receivedCallback, lostCallback):\n        # security attributes for pipes\n        self.pipe = pipe\n        self.receivedCallback = receivedCallback\n        self.lostCallback = lostCallback\n\n    def checkWork(self):\n        finished = 0\n        fullDataRead = []\n\n        while 1:\n            try:\n                buffer, bytesToRead, result = win32pipe.PeekNamedPipe(self.pipe, 1)\n                # finished = (result == -1)\n                if not bytesToRead:\n                    break\n                hr, data = win32file.ReadFile(self.pipe, bytesToRead, None)\n                fullDataRead.append(data)\n            except win32api.error:\n                finished = 1\n                break\n\n        dataBuf = b''.join(fullDataRead)\n        if dataBuf:\n            self.receivedCallback(dataBuf)\n        if finished:\n            self.cleanup()\n        return len(dataBuf)\n\n    def cleanup(self):\n        self.deactivate()\n        self.lostCallback()\n\n    def close(self):\n        try:\n            win32api.CloseHandle(self.pipe)\n        except pywintypes.error:\n            # You can't close std handles...?\n            pass\n\n    def stopProducing(self):\n        self.close()\n\n    def pauseProducing(self):\n        self.deactivate()\n\n    def resumeProducing(self):\n        self.activate()\n\n\nFULL_BUFFER_SIZE = 64 * 1024\n\n@implementer(IConsumer)\nclass _PollableWritePipe(_PollableResource):\n\n    def __init__(self, writePipe, lostCallback):\n        self.disconnecting = False\n        self.producer = None\n        self.producerPaused = False\n        self.streamingProducer = 0\n        self.outQueue = []\n        self.writePipe = writePipe\n        self.lostCallback = lostCallback\n        try:\n            win32pipe.SetNamedPipeHandleState(writePipe,\n                                              win32pipe.PIPE_NOWAIT,\n                                              None,\n                                              None)\n        except pywintypes.error:\n            # Maybe it's an invalid handle.  Who knows.\n            pass\n\n    def close(self):\n        self.disconnecting = True\n\n    def bufferFull(self):\n        if self.producer is not None:\n            self.producerPaused = True\n            self.producer.pauseProducing()\n\n    def bufferEmpty(self):\n        if self.producer is not None and ((not self.streamingProducer) or\n                                          self.producerPaused):\n            self.producer.producerPaused = False\n            self.producer.resumeProducing()\n            return True\n        return False\n\n    # almost-but-not-quite-exact copy-paste from abstract.FileDescriptor... ugh\n\n    def registerProducer(self, producer, streaming):\n        \"\"\"Register to receive data from a producer.\n\n        This sets this selectable to be a consumer for a producer.  When this\n        selectable runs out of data on a write() call, it will ask the producer\n        to resumeProducing(). A producer should implement the IProducer\n        interface.\n\n        FileDescriptor provides some infrastructure for producer methods.\n        \"\"\"\n        if self.producer is not None:\n            raise RuntimeError(\n                \"Cannot register producer %s, because producer %s was never \"\n                \"unregistered.\" % (producer, self.producer))\n        if not self.active:\n            producer.stopProducing()\n        else:\n            self.producer = producer\n            self.streamingProducer = streaming\n            if not streaming:\n                producer.resumeProducing()\n\n    def unregisterProducer(self):\n        \"\"\"Stop consuming data from a producer, without disconnecting.\n        \"\"\"\n        self.producer = None\n\n    def writeConnectionLost(self):\n        self.deactivate()\n        try:\n            win32api.CloseHandle(self.writePipe)\n        except pywintypes.error:\n            # OMG what\n            pass\n        self.lostCallback()\n\n\n    def writeSequence(self, seq):\n        \"\"\"\n        Append a C{list} or C{tuple} of bytes to the output buffer.\n\n        @param seq: C{list} or C{tuple} of C{str} instances to be appended to\n            the output buffer.\n\n        @raise TypeError: If C{seq} contains C{unicode}.\n        \"\"\"\n        if unicode in map(type, seq):\n            raise TypeError(\"Unicode not allowed in output buffer.\")\n        self.outQueue.extend(seq)\n\n\n    def write(self, data):\n        \"\"\"\n        Append some bytes to the output buffer.\n\n        @param data: C{str} to be appended to the output buffer.\n        @type data: C{str}.\n\n        @raise TypeError: If C{data} is C{unicode} instead of C{str}.\n        \"\"\"\n        if isinstance(data, unicode):\n            raise TypeError(\"Unicode not allowed in output buffer.\")\n        if self.disconnecting:\n            return\n        self.outQueue.append(data)\n        if sum(map(len, self.outQueue)) > FULL_BUFFER_SIZE:\n            self.bufferFull()\n\n\n    def checkWork(self):\n        numBytesWritten = 0\n        if not self.outQueue:\n            if self.disconnecting:\n                self.writeConnectionLost()\n                return 0\n            try:\n                win32file.WriteFile(self.writePipe, b'', None)\n            except pywintypes.error:\n                self.writeConnectionLost()\n                return numBytesWritten\n        while self.outQueue:\n            data = self.outQueue.pop(0)\n            errCode = 0\n            try:\n                errCode, nBytesWritten = win32file.WriteFile(self.writePipe,\n                                                             data, None)\n            except win32api.error:\n                self.writeConnectionLost()\n                break\n            else:\n                # assert not errCode, \"wtf an error code???\"\n                numBytesWritten += nBytesWritten\n                if len(data) > nBytesWritten:\n                    self.outQueue.insert(0, data[nBytesWritten:])\n                    break\n        else:\n            resumed = self.bufferEmpty()\n            if not resumed and self.disconnecting:\n                self.writeConnectionLost()\n        return numBytesWritten\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_posixserialport.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nSerial Port Protocol\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n# dependent on pyserial ( http://pyserial.sf.net/ )\n# only tested w/ 1.18 (5 Dec 2002)\nfrom serial import PARITY_NONE\nfrom serial import STOPBITS_ONE\nfrom serial import EIGHTBITS\n\nfrom twisted.internet.serialport import BaseSerialPort\n\nfrom twisted.internet import abstract, fdesc\n\n\n\nclass SerialPort(BaseSerialPort, abstract.FileDescriptor):\n    \"\"\"\n    A select()able serial device, acting as a transport.\n    \"\"\"\n\n    connected = 1\n\n    def __init__(self, protocol, deviceNameOrPortNumber, reactor,\n        baudrate = 9600, bytesize = EIGHTBITS, parity = PARITY_NONE,\n        stopbits = STOPBITS_ONE, timeout = 0, xonxoff = 0, rtscts = 0):\n        abstract.FileDescriptor.__init__(self, reactor)\n        self._serial = self._serialFactory(\n            deviceNameOrPortNumber, baudrate=baudrate, bytesize=bytesize,\n            parity=parity, stopbits=stopbits, timeout=timeout,\n            xonxoff=xonxoff, rtscts=rtscts)\n        self.reactor = reactor\n        self.flushInput()\n        self.flushOutput()\n        self.protocol = protocol\n        self.protocol.makeConnection(self)\n        self.startReading()\n\n\n    def fileno(self):\n        return self._serial.fd\n\n\n    def writeSomeData(self, data):\n        \"\"\"\n        Write some data to the serial device.\n        \"\"\"\n        return fdesc.writeToFD(self.fileno(), data)\n\n\n    def doRead(self):\n        \"\"\"\n        Some data's readable from serial device.\n        \"\"\"\n        return fdesc.readFromFD(self.fileno(), self.protocol.dataReceived)\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Called when the serial port disconnects.\n\n        Will call C{connectionLost} on the protocol that is handling the\n        serial data.\n        \"\"\"\n        abstract.FileDescriptor.connectionLost(self, reason)\n        self._serial.close()\n        self.protocol.connectionLost(reason)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_posixstdio.py",
    "content": "# -*- test-case-name: twisted.test.test_stdio -*-\n\n\"\"\"Standard input/out/err support.\n\nFuture Plans::\n\n    support for stderr, perhaps\n    Rewrite to use the reactor instead of an ad-hoc mechanism for connecting\n        protocols to transport.\n\nMaintainer: James Y Knight\n\"\"\"\n\nfrom zope.interface import implementer\n\nfrom twisted.internet import process, error, interfaces\nfrom twisted.python import log, failure\n\n\n@implementer(interfaces.IAddress)\nclass PipeAddress(object):\n    pass\n\n\n@implementer(interfaces.ITransport, interfaces.IProducer,\n             interfaces.IConsumer, interfaces.IHalfCloseableDescriptor)\nclass StandardIO(object):\n\n    _reader = None\n    _writer = None\n    disconnected = False\n    disconnecting = False\n\n    def __init__(self, proto, stdin=0, stdout=1, reactor=None):\n        if reactor is None:\n            from twisted.internet import reactor\n        self.protocol = proto\n\n        self._writer = process.ProcessWriter(reactor, self, 'write', stdout)\n        self._reader = process.ProcessReader(reactor, self, 'read', stdin)\n        self._reader.startReading()\n        self.protocol.makeConnection(self)\n\n    # ITransport\n\n    # XXX Actually, see #3597.\n    def loseWriteConnection(self):\n        if self._writer is not None:\n            self._writer.loseConnection()\n\n    def write(self, data):\n        if self._writer is not None:\n            self._writer.write(data)\n\n    def writeSequence(self, data):\n        if self._writer is not None:\n            self._writer.writeSequence(data)\n\n    def loseConnection(self):\n        self.disconnecting = True\n\n        if self._writer is not None:\n            self._writer.loseConnection()\n        if self._reader is not None:\n            # Don't loseConnection, because we don't want to SIGPIPE it.\n            self._reader.stopReading()\n\n    def getPeer(self):\n        return PipeAddress()\n\n    def getHost(self):\n        return PipeAddress()\n\n\n    # Callbacks from process.ProcessReader/ProcessWriter\n    def childDataReceived(self, fd, data):\n        self.protocol.dataReceived(data)\n\n    def childConnectionLost(self, fd, reason):\n        if self.disconnected:\n            return\n\n        if reason.value.__class__ == error.ConnectionDone:\n            # Normal close\n            if fd == 'read':\n                self._readConnectionLost(reason)\n            else:\n                self._writeConnectionLost(reason)\n        else:\n            self.connectionLost(reason)\n\n    def connectionLost(self, reason):\n        self.disconnected = True\n\n        # Make sure to cleanup the other half\n        _reader = self._reader\n        _writer = self._writer\n        protocol = self.protocol\n        self._reader = self._writer = None\n        self.protocol = None\n\n        if _writer is not None and not _writer.disconnected:\n            _writer.connectionLost(reason)\n\n        if _reader is not None and not _reader.disconnected:\n            _reader.connectionLost(reason)\n\n        try:\n            protocol.connectionLost(reason)\n        except:\n            log.err()\n\n    def _writeConnectionLost(self, reason):\n        self._writer=None\n        if self.disconnecting:\n            self.connectionLost(reason)\n            return\n\n        p = interfaces.IHalfCloseableProtocol(self.protocol, None)\n        if p:\n            try:\n                p.writeConnectionLost()\n            except:\n                log.err()\n                self.connectionLost(failure.Failure())\n\n    def _readConnectionLost(self, reason):\n        self._reader=None\n        p = interfaces.IHalfCloseableProtocol(self.protocol, None)\n        if p:\n            try:\n                p.readConnectionLost()\n            except:\n                log.err()\n                self.connectionLost(failure.Failure())\n        else:\n            self.connectionLost(reason)\n\n    # IConsumer\n    def registerProducer(self, producer, streaming):\n        if self._writer is None:\n            producer.stopProducing()\n        else:\n            self._writer.registerProducer(producer, streaming)\n\n    def unregisterProducer(self):\n        if self._writer is not None:\n            self._writer.unregisterProducer()\n\n    # IProducer\n    def stopProducing(self):\n        self.loseConnection()\n\n    def pauseProducing(self):\n        if self._reader is not None:\n            self._reader.pauseProducing()\n\n    def resumeProducing(self):\n        if self._reader is not None:\n            self._reader.resumeProducing()\n\n    def stopReading(self):\n        \"\"\"Compatibility only, don't use. Call pauseProducing.\"\"\"\n        self.pauseProducing()\n\n    def startReading(self):\n        \"\"\"Compatibility only, don't use. Call resumeProducing.\"\"\"\n        self.resumeProducing()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_producer_helpers.py",
    "content": "# -*- test-case-name: twisted.test.test_producer_helpers -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nHelpers for working with producers.\n\"\"\"\nfrom __future__ import division, absolute_import\n\nfrom zope.interface import implementer\n\nfrom twisted.internet.interfaces import IPushProducer\nfrom twisted.internet.task import cooperate\nfrom twisted.python import log\nfrom twisted.python.reflect import safe_str\n\n\n# This module exports nothing public, it's for internal Twisted use only.\n__all__ = []\n\n\n@implementer(IPushProducer)\nclass _PullToPush(object):\n    \"\"\"\n    An adapter that converts a non-streaming to a streaming producer.\n\n    Because of limitations of the producer API, this adapter requires the\n    cooperation of the consumer. When the consumer's C{registerProducer} is\n    called with a non-streaming producer, it must wrap it with L{_PullToPush}\n    and then call C{startStreaming} on the resulting object. When the\n    consumer's C{unregisterProducer} is called, it must call\n    C{stopStreaming} on the L{_PullToPush} instance.\n\n    If the underlying producer throws an exception from C{resumeProducing},\n    the producer will be unregistered from the consumer.\n\n    @ivar _producer: the underling non-streaming producer.\n\n    @ivar _consumer: the consumer with which the underlying producer was\n                     registered.\n\n    @ivar _finished: C{bool} indicating whether the producer has finished.\n\n    @ivar _coopTask: the result of calling L{cooperate}, the task driving the\n                     streaming producer.\n    \"\"\"\n\n    _finished = False\n\n\n    def __init__(self, pullProducer, consumer):\n        self._producer = pullProducer\n        self._consumer = consumer\n\n\n    def _pull(self):\n        \"\"\"\n        A generator that calls C{resumeProducing} on the underlying producer\n        forever.\n\n        If C{resumeProducing} throws an exception, the producer is\n        unregistered, which should result in streaming stopping.\n        \"\"\"\n        while True:\n            try:\n                self._producer.resumeProducing()\n            except:\n                log.err(None, \"%s failed, producing will be stopped:\" %\n                        (safe_str(self._producer),))\n                try:\n                    self._consumer.unregisterProducer()\n                    # The consumer should now call stopStreaming() on us,\n                    # thus stopping the streaming.\n                except:\n                    # Since the consumer blew up, we may not have had\n                    # stopStreaming() called, so we just stop on our own:\n                    log.err(None, \"%s failed to unregister producer:\" %\n                            (safe_str(self._consumer),))\n                    self._finished = True\n                    return\n            yield None\n\n\n    def startStreaming(self):\n        \"\"\"\n        This should be called by the consumer when the producer is registered.\n\n        Start streaming data to the consumer.\n        \"\"\"\n        self._coopTask = cooperate(self._pull())\n\n\n    def stopStreaming(self):\n        \"\"\"\n        This should be called by the consumer when the producer is\n        unregistered.\n\n        Stop streaming data to the consumer.\n        \"\"\"\n        if self._finished:\n            return\n        self._finished = True\n        self._coopTask.stop()\n\n\n    def pauseProducing(self):\n        \"\"\"\n        @see: C{IPushProducer.pauseProducing}\n        \"\"\"\n        self._coopTask.pause()\n\n\n    def resumeProducing(self):\n        \"\"\"\n        @see: C{IPushProducer.resumeProducing}\n        \"\"\"\n        self._coopTask.resume()\n\n\n    def stopProducing(self):\n        \"\"\"\n        @see: C{IPushProducer.stopProducing}\n        \"\"\"\n        self.stopStreaming()\n        self._producer.stopProducing()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_resolver.py",
    "content": "# -*- test-case-name: twisted.internet.test.test_resolver -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nIPv6-aware hostname resolution.\n\n@see: L{IHostnameResolver}\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__metaclass__ = type\n\nfrom socket import (getaddrinfo, AF_INET, AF_INET6, AF_UNSPEC, SOCK_STREAM,\n                    SOCK_DGRAM, gaierror)\n\nfrom zope.interface import implementer\n\nfrom twisted.internet.interfaces import (IHostnameResolver, IHostResolution,\n                                         IResolverSimple, IResolutionReceiver)\nfrom twisted.internet.error import DNSLookupError\nfrom twisted.internet.defer import Deferred\nfrom twisted.internet.threads import deferToThreadPool\nfrom twisted.internet.address import IPv4Address, IPv6Address\nfrom twisted.python.compat import nativeString\nfrom twisted.internet._idna import _idnaBytes\nfrom twisted.logger import Logger\n\n\n@implementer(IHostResolution)\nclass HostResolution(object):\n    \"\"\"\n    The in-progress resolution of a given hostname.\n    \"\"\"\n\n    def __init__(self, name):\n        \"\"\"\n        Create a L{HostResolution} with the given name.\n        \"\"\"\n        self.name = name\n\n\n\n_any = frozenset([IPv4Address, IPv6Address])\n\n_typesToAF = {\n    frozenset([IPv4Address]): AF_INET,\n    frozenset([IPv6Address]): AF_INET6,\n    _any: AF_UNSPEC,\n}\n\n_afToType = {\n    AF_INET: IPv4Address,\n    AF_INET6: IPv6Address,\n}\n\n_transportToSocket = {\n    'TCP': SOCK_STREAM,\n    'UDP': SOCK_DGRAM,\n}\n\n_socktypeToType = {\n    SOCK_STREAM: 'TCP',\n    SOCK_DGRAM: 'UDP',\n}\n\n\n\n@implementer(IHostnameResolver)\nclass GAIResolver(object):\n    \"\"\"\n    L{IHostnameResolver} implementation that resolves hostnames by calling\n    L{getaddrinfo} in a thread.\n    \"\"\"\n\n    def __init__(self, reactor, getThreadPool=None, getaddrinfo=getaddrinfo):\n        \"\"\"\n        Create a L{GAIResolver}.\n\n        @param reactor: the reactor to schedule result-delivery on\n        @type reactor: L{IReactorThreads}\n\n        @param getThreadPool: a function to retrieve the thread pool to use for\n            scheduling name resolutions.  If not supplied, the use the given\n            C{reactor}'s thread pool.\n        @type getThreadPool: 0-argument callable returning a\n            L{twisted.python.threadpool.ThreadPool}\n\n        @param getaddrinfo: a reference to the L{getaddrinfo} to use - mainly\n            parameterized for testing.\n        @type getaddrinfo: callable with the same signature as L{getaddrinfo}\n        \"\"\"\n        self._reactor = reactor\n        self._getThreadPool = (reactor.getThreadPool if getThreadPool is None\n                               else getThreadPool)\n        self._getaddrinfo = getaddrinfo\n\n\n    def resolveHostName(self, resolutionReceiver, hostName, portNumber=0,\n                        addressTypes=None, transportSemantics='TCP'):\n        \"\"\"\n        See L{IHostnameResolver.resolveHostName}\n\n        @param resolutionReceiver: see interface\n\n        @param hostName: see interface\n\n        @param portNumber: see interface\n\n        @param addressTypes: see interface\n\n        @param transportSemantics: see interface\n\n        @return: see interface\n        \"\"\"\n        pool = self._getThreadPool()\n        addressFamily = _typesToAF[_any if addressTypes is None\n                                   else frozenset(addressTypes)]\n        socketType = _transportToSocket[transportSemantics]\n        def get():\n            try:\n                return self._getaddrinfo(hostName, portNumber, addressFamily,\n                                         socketType)\n            except gaierror:\n                return []\n        d = deferToThreadPool(self._reactor, pool, get)\n        resolution = HostResolution(hostName)\n        resolutionReceiver.resolutionBegan(resolution)\n        @d.addCallback\n        def deliverResults(result):\n            for family, socktype, proto, cannoname, sockaddr in result:\n                addrType = _afToType[family]\n                resolutionReceiver.addressResolved(\n                    addrType(_socktypeToType.get(socktype, 'TCP'), *sockaddr)\n                )\n            resolutionReceiver.resolutionComplete()\n        return resolution\n\n\n\n@implementer(IHostnameResolver)\nclass SimpleResolverComplexifier(object):\n    \"\"\"\n    A converter from L{IResolverSimple} to L{IHostnameResolver}.\n    \"\"\"\n\n    _log = Logger()\n\n    def __init__(self, simpleResolver):\n        \"\"\"\n        Construct a L{SimpleResolverComplexifier} with an L{IResolverSimple}.\n        \"\"\"\n        self._simpleResolver = simpleResolver\n\n\n    def resolveHostName(self, resolutionReceiver, hostName, portNumber=0,\n                        addressTypes=None, transportSemantics='TCP'):\n        \"\"\"\n        See L{IHostnameResolver.resolveHostName}\n\n        @param resolutionReceiver: see interface\n\n        @param hostName: see interface\n\n        @param portNumber: see interface\n\n        @param addressTypes: see interface\n\n        @param transportSemantics: see interface\n\n        @return: see interface\n        \"\"\"\n        # If it's str, we need to make sure that it's just ASCII.\n        try:\n            hostName = hostName.encode('ascii')\n        except UnicodeEncodeError:\n            # If it's not just ASCII, IDNA it. We don't want to give a Unicode\n            # string with non-ASCII in it to Python 3, as if anyone passes that\n            # to a Python 3 stdlib function, it will probably use the wrong\n            # IDNA version and break absolutely everything\n            hostName = _idnaBytes(hostName)\n\n        # Make sure it's passed down as a native str, to maintain the interface\n        hostName = nativeString(hostName)\n\n        resolution = HostResolution(hostName)\n        resolutionReceiver.resolutionBegan(resolution)\n        onAddress = self._simpleResolver.getHostByName(hostName)\n        def addressReceived(address):\n            resolutionReceiver.addressResolved(IPv4Address('TCP', address,\n                                                           portNumber))\n        def errorReceived(error):\n            if not error.check(DNSLookupError):\n                self._log.failure(\"while looking up {name} with {resolver}\",\n                                  error, name=hostName,\n                                  resolver=self._simpleResolver)\n        onAddress.addCallbacks(addressReceived, errorReceived)\n        def finish(result):\n            resolutionReceiver.resolutionComplete()\n        onAddress.addCallback(finish)\n        return resolution\n\n\n\n@implementer(IResolutionReceiver)\nclass FirstOneWins(object):\n    \"\"\"\n    An L{IResolutionReceiver} which fires a L{Deferred} with its first result.\n    \"\"\"\n\n    def __init__(self, deferred):\n        \"\"\"\n        @param deferred: The L{Deferred} to fire when the first resolution\n            result arrives.\n        \"\"\"\n        self._deferred = deferred\n        self._resolved = False\n\n\n    def resolutionBegan(self, resolution):\n        \"\"\"\n        See L{IResolutionReceiver.resolutionBegan}\n\n        @param resolution: See L{IResolutionReceiver.resolutionBegan}\n        \"\"\"\n        self._resolution = resolution\n\n\n    def addressResolved(self, address):\n        \"\"\"\n        See L{IResolutionReceiver.addressResolved}\n\n        @param address: See L{IResolutionReceiver.addressResolved}\n        \"\"\"\n        if self._resolved:\n            return\n        self._resolved = True\n        self._deferred.callback(address.host)\n\n\n    def resolutionComplete(self):\n        \"\"\"\n        See L{IResolutionReceiver.resolutionComplete}\n        \"\"\"\n        if self._resolved:\n            return\n        self._deferred.errback(DNSLookupError(self._resolution.name))\n\n\n\n@implementer(IResolverSimple)\nclass ComplexResolverSimplifier(object):\n    \"\"\"\n    A converter from L{IHostnameResolver} to L{IResolverSimple}\n    \"\"\"\n    def __init__(self, nameResolver):\n        \"\"\"\n        Create a L{ComplexResolverSimplifier} with an L{IHostnameResolver}.\n\n        @param nameResolver: The L{IHostnameResolver} to use.\n        \"\"\"\n        self._nameResolver = nameResolver\n\n\n    def getHostByName(self, name, timeouts=()):\n        \"\"\"\n        See L{IResolverSimple.getHostByName}\n\n        @param name: see L{IResolverSimple.getHostByName}\n\n        @param timeouts: see L{IResolverSimple.getHostByName}\n\n        @return: see L{IResolverSimple.getHostByName}\n        \"\"\"\n        result = Deferred()\n        self._nameResolver.resolveHostName(FirstOneWins(result), name, 0,\n                                           [IPv4Address])\n        return result\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_signals.py",
    "content": "# -*- test-case-name: twisted.internet.test.test_sigchld -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module is used to integrate child process termination into a\nreactor event loop.  This is a challenging feature to provide because\nmost platforms indicate process termination via SIGCHLD and do not\nprovide a way to wait for that signal and arbitrary I/O events at the\nsame time.  The naive implementation involves installing a Python\nSIGCHLD handler; unfortunately this leads to other syscalls being\ninterrupted (whenever SIGCHLD is received) and failing with EINTR\n(which almost no one is prepared to handle).  This interruption can be\ndisabled via siginterrupt(2) (or one of the equivalent mechanisms);\nhowever, if the SIGCHLD is delivered by the platform to a non-main\nthread (not a common occurrence, but difficult to prove impossible),\nthe main thread (waiting on select() or another event notification\nAPI) may not wake up leading to an arbitrary delay before the child\ntermination is noticed.\n\nThe basic solution to all these issues involves enabling SA_RESTART\n(ie, disabling system call interruption) and registering a C signal\nhandler which writes a byte to a pipe.  The other end of the pipe is\nregistered with the event loop, allowing it to wake up shortly after\nSIGCHLD is received.  See L{twisted.internet.posixbase._SIGCHLDWaker}\nfor the implementation of the event loop side of this solution.  The\nuse of a pipe this way is known as the U{self-pipe\ntrick<http://cr.yp.to/docs/selfpipe.html>}.\n\nFrom Python version 2.6, C{signal.siginterrupt} and C{signal.set_wakeup_fd}\nprovide the necessary C signal handler which writes to the pipe to be\nregistered with C{SA_RESTART}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport signal\n\n\ndef installHandler(fd):\n    \"\"\"\n    Install a signal handler which will write a byte to C{fd} when\n    I{SIGCHLD} is received.\n\n    This is implemented by installing a SIGCHLD handler that does nothing,\n    setting the I{SIGCHLD} handler as not allowed to interrupt system calls,\n    and using L{signal.set_wakeup_fd} to do the actual writing.\n\n    @param fd: The file descriptor to which to write when I{SIGCHLD} is\n        received.\n    @type fd: C{int}\n    \"\"\"\n    if fd == -1:\n        signal.signal(signal.SIGCHLD, signal.SIG_DFL)\n    else:\n        def noopSignalHandler(*args):\n            pass\n        signal.signal(signal.SIGCHLD, noopSignalHandler)\n        signal.siginterrupt(signal.SIGCHLD, False)\n    return signal.set_wakeup_fd(fd)\n\n\n\ndef isDefaultHandler():\n    \"\"\"\n    Determine whether the I{SIGCHLD} handler is the default or not.\n    \"\"\"\n    return signal.getsignal(signal.SIGCHLD) == signal.SIG_DFL\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_sslverify.py",
    "content": "# -*- test-case-name: twisted.test.test_sslverify -*-\n# Copyright (c) 2005 Divmod, Inc.\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom __future__ import division, absolute_import\n\nimport warnings\n\nfrom constantly import Names, NamedConstant\nfrom hashlib import md5\n\nfrom OpenSSL import SSL, crypto\nfrom OpenSSL._util import lib as pyOpenSSLlib\n\nfrom twisted.internet.abstract import isIPAddress, isIPv6Address\nfrom twisted.python import log\nfrom twisted.python.randbytes import secureRandom\nfrom twisted.python._oldstyle import _oldStyle\nfrom ._idna import _idnaBytes\n\nfrom zope.interface import Interface, implementer\nfrom constantly import Flags, FlagConstant\nfrom incremental import Version\n\nfrom twisted.internet.defer import Deferred\nfrom twisted.internet.error import VerifyError, CertificateError\nfrom twisted.internet.interfaces import (\n    IAcceptableCiphers, ICipher, IOpenSSLClientConnectionCreator,\n    IOpenSSLContextFactory\n)\n\nfrom twisted.python import util\nfrom twisted.python.deprecate import _mutuallyExclusiveArguments\nfrom twisted.python.compat import nativeString, unicode\nfrom twisted.python.failure import Failure\nfrom twisted.python.util import FancyEqMixin\n\nfrom twisted.python.deprecate import deprecated\n\n\n\nclass TLSVersion(Names):\n    \"\"\"\n    TLS versions that we can negotiate with the client/server.\n    \"\"\"\n    SSLv3 = NamedConstant()\n    TLSv1_0 = NamedConstant()\n    TLSv1_1 = NamedConstant()\n    TLSv1_2 = NamedConstant()\n    TLSv1_3 = NamedConstant()\n\n\n\n_tlsDisableFlags = {\n    TLSVersion.SSLv3: SSL.OP_NO_SSLv3,\n    TLSVersion.TLSv1_0: SSL.OP_NO_TLSv1,\n    TLSVersion.TLSv1_1: SSL.OP_NO_TLSv1_1,\n    TLSVersion.TLSv1_2: SSL.OP_NO_TLSv1_2,\n\n    # If we don't have TLS v1.3 yet, we can't disable it -- this is just so\n    # when it makes it into OpenSSL, connections knowingly bracketed to v1.2\n    # don't end up going to v1.3\n    TLSVersion.TLSv1_3: getattr(SSL, \"OP_NO_TLSv1_3\", 0x00),\n}\n\n\n\ndef _getExcludedTLSProtocols(oldest, newest):\n    \"\"\"\n    Given a pair of L{TLSVersion} constants, figure out what versions we want\n    to disable (as OpenSSL is an exclusion based API).\n\n    @param oldest: The oldest L{TLSVersion} we want to allow.\n    @type oldest: L{TLSVersion} constant\n\n    @param newest: The newest L{TLSVersion} we want to allow, or L{None} for no\n        upper limit.\n    @type newest: L{TLSVersion} constant or L{None}\n\n    @return: The versions we want to disable.\n    @rtype: L{list} of L{TLSVersion} constants.\n    \"\"\"\n    versions = list(TLSVersion.iterconstants())\n    excludedVersions = [x for x in versions[:versions.index(oldest)]]\n\n    if newest:\n        excludedVersions.extend([x for x in versions[versions.index(newest):]])\n\n    return excludedVersions\n\n\n\n\nclass SimpleVerificationError(Exception):\n    \"\"\"\n    Not a very useful verification error.\n    \"\"\"\n\n\n\ndef simpleVerifyHostname(connection, hostname):\n    \"\"\"\n    Check only the common name in the certificate presented by the peer and\n    only for an exact match.\n\n    This is to provide I{something} in the way of hostname verification to\n    users who haven't installed C{service_identity}. This check is overly\n    strict, relies on a deprecated TLS feature (you're supposed to ignore the\n    commonName if the subjectAlternativeName extensions are present, I\n    believe), and lots of valid certificates will fail.\n\n    @param connection: the OpenSSL connection to verify.\n    @type connection: L{OpenSSL.SSL.Connection}\n\n    @param hostname: The hostname expected by the user.\n    @type hostname: L{unicode}\n\n    @raise twisted.internet.ssl.VerificationError: if the common name and\n        hostname don't match.\n    \"\"\"\n    commonName = connection.get_peer_certificate().get_subject().commonName\n    if commonName != hostname:\n        raise SimpleVerificationError(repr(commonName) + \"!=\" +\n                                      repr(hostname))\n\n\n\ndef simpleVerifyIPAddress(connection, hostname):\n    \"\"\"\n    Always fails validation of IP addresses\n\n    @param connection: the OpenSSL connection to verify.\n    @type connection: L{OpenSSL.SSL.Connection}\n\n    @param hostname: The hostname expected by the user.\n    @type hostname: L{unicode}\n\n    @raise twisted.internet.ssl.VerificationError: Always raised\n    \"\"\"\n    raise SimpleVerificationError(\"Cannot verify certificate IP addresses\")\n\n\n\ndef _usablePyOpenSSL(version):\n    \"\"\"\n    Check pyOpenSSL version string whether we can use it for host verification.\n\n    @param version: A pyOpenSSL version string.\n    @type version: L{str}\n\n    @rtype: L{bool}\n    \"\"\"\n    major, minor = (int(part) for part in version.split(\".\")[:2])\n    return (major, minor) >= (0, 12)\n\n\n\ndef _selectVerifyImplementation():\n    \"\"\"\n    Determine if C{service_identity} is installed. If so, use it. If not, use\n    simplistic and incorrect checking as implemented in\n    L{simpleVerifyHostname}.\n\n    @return: 2-tuple of (C{verify_hostname}, C{VerificationError})\n    @rtype: L{tuple}\n    \"\"\"\n\n    whatsWrong = (\n        \"Without the service_identity module, Twisted can perform only \"\n        \"rudimentary TLS client hostname verification.  Many valid \"\n        \"certificate/hostname mappings may be rejected.\"\n    )\n\n    try:\n        from service_identity import VerificationError\n        from service_identity.pyopenssl import (\n            verify_hostname, verify_ip_address\n        )\n        return verify_hostname, verify_ip_address, VerificationError\n    except ImportError as e:\n        warnings.warn_explicit(\n            \"You do not have a working installation of the \"\n            \"service_identity module: '\" + str(e) + \"'.  \"\n            \"Please install it from \"\n            \"<https://pypi.python.org/pypi/service_identity> and make \"\n            \"sure all of its dependencies are satisfied.  \"\n            + whatsWrong,\n            # Unfortunately the lineno is required.\n            category=UserWarning, filename=\"\", lineno=0)\n\n    return simpleVerifyHostname, simpleVerifyIPAddress, SimpleVerificationError\n\n\n\nverifyHostname, verifyIPAddress, VerificationError = \\\n    _selectVerifyImplementation()\n\n\n\nclass ProtocolNegotiationSupport(Flags):\n    \"\"\"\n    L{ProtocolNegotiationSupport} defines flags which are used to indicate the\n    level of NPN/ALPN support provided by the TLS backend.\n\n    @cvar NOSUPPORT: There is no support for NPN or ALPN. This is exclusive\n        with both L{NPN} and L{ALPN}.\n    @cvar NPN: The implementation supports Next Protocol Negotiation.\n    @cvar ALPN: The implementation supports Application Layer Protocol\n        Negotiation.\n    \"\"\"\n    NPN = FlagConstant(0x0001)\n    ALPN = FlagConstant(0x0002)\n\n# FIXME: https://twistedmatrix.com/trac/ticket/8074\n# Currently flags with literal zero values behave incorrectly. However,\n# creating a flag by NOTing a flag with itself appears to work totally fine, so\n# do that instead.\nProtocolNegotiationSupport.NOSUPPORT = (\n    ProtocolNegotiationSupport.NPN ^ ProtocolNegotiationSupport.NPN\n)\n\n\ndef protocolNegotiationMechanisms():\n    \"\"\"\n    Checks whether your versions of PyOpenSSL and OpenSSL are recent enough to\n    support protocol negotiation, and if they are, what kind of protocol\n    negotiation is supported.\n\n    @return: A combination of flags from L{ProtocolNegotiationSupport} that\n        indicate which mechanisms for protocol negotiation are supported.\n    @rtype: L{constantly.FlagConstant}\n    \"\"\"\n    support = ProtocolNegotiationSupport.NOSUPPORT\n    ctx = SSL.Context(SSL.SSLv23_METHOD)\n\n    try:\n        ctx.set_npn_advertise_callback(lambda c: None)\n    except (AttributeError, NotImplementedError):\n        pass\n    else:\n        support |= ProtocolNegotiationSupport.NPN\n\n    try:\n        ctx.set_alpn_select_callback(lambda c: None)\n    except (AttributeError, NotImplementedError):\n        pass\n    else:\n        support |= ProtocolNegotiationSupport.ALPN\n\n    return support\n\n\n\n_x509names = {\n    'CN': 'commonName',\n    'commonName': 'commonName',\n\n    'O': 'organizationName',\n    'organizationName': 'organizationName',\n\n    'OU': 'organizationalUnitName',\n    'organizationalUnitName': 'organizationalUnitName',\n\n    'L': 'localityName',\n    'localityName': 'localityName',\n\n    'ST': 'stateOrProvinceName',\n    'stateOrProvinceName': 'stateOrProvinceName',\n\n    'C': 'countryName',\n    'countryName': 'countryName',\n\n    'emailAddress': 'emailAddress'}\n\n\n\nclass DistinguishedName(dict):\n    \"\"\"\n    Identify and describe an entity.\n\n    Distinguished names are used to provide a minimal amount of identifying\n    information about a certificate issuer or subject.  They are commonly\n    created with one or more of the following fields::\n\n        commonName (CN)\n        organizationName (O)\n        organizationalUnitName (OU)\n        localityName (L)\n        stateOrProvinceName (ST)\n        countryName (C)\n        emailAddress\n\n    A L{DistinguishedName} should be constructed using keyword arguments whose\n    keys can be any of the field names above (as a native string), and the\n    values are either Unicode text which is encodable to ASCII, or L{bytes}\n    limited to the ASCII subset. Any fields passed to the constructor will be\n    set as attributes, accessible using both their extended name and their\n    shortened acronym. The attribute values will be the ASCII-encoded\n    bytes. For example::\n\n        >>> dn = DistinguishedName(commonName=b'www.example.com',\n        ...                        C='US')\n        >>> dn.C\n        b'US'\n        >>> dn.countryName\n        b'US'\n        >>> hasattr(dn, \"organizationName\")\n        False\n\n    L{DistinguishedName} instances can also be used as dictionaries; the keys\n    are extended name of the fields::\n\n        >>> dn.keys()\n        ['countryName', 'commonName']\n        >>> dn['countryName']\n        b'US'\n\n    \"\"\"\n    __slots__ = ()\n\n    def __init__(self, **kw):\n        for k, v in kw.items():\n            setattr(self, k, v)\n\n\n    def _copyFrom(self, x509name):\n        for name in _x509names:\n            value = getattr(x509name, name, None)\n            if value is not None:\n                setattr(self, name, value)\n\n\n    def _copyInto(self, x509name):\n        for k, v in self.items():\n            setattr(x509name, k, nativeString(v))\n\n\n    def __repr__(self):\n        return '<DN %s>' % (dict.__repr__(self)[1:-1])\n\n\n    def __getattr__(self, attr):\n        try:\n            return self[_x509names[attr]]\n        except KeyError:\n            raise AttributeError(attr)\n\n\n    def __setattr__(self, attr, value):\n        if attr not in _x509names:\n            raise AttributeError(\"%s is not a valid OpenSSL X509 name field\" % (attr,))\n        realAttr = _x509names[attr]\n        if not isinstance(value, bytes):\n            value = value.encode(\"ascii\")\n        self[realAttr] = value\n\n\n    def inspect(self):\n        \"\"\"\n        Return a multi-line, human-readable representation of this DN.\n\n        @rtype: L{str}\n        \"\"\"\n        l = []\n        lablen = 0\n        def uniqueValues(mapping):\n            return set(mapping.values())\n        for k in sorted(uniqueValues(_x509names)):\n            label = util.nameToLabel(k)\n            lablen = max(len(label), lablen)\n            v = getattr(self, k, None)\n            if v is not None:\n                l.append((label, nativeString(v)))\n        lablen += 2\n        for n, (label, attr) in enumerate(l):\n            l[n] = (label.rjust(lablen)+': '+ attr)\n        return '\\n'.join(l)\n\nDN = DistinguishedName\n\n\n\n@_oldStyle\nclass CertBase:\n    \"\"\"\n    Base class for public (certificate only) and private (certificate + key\n    pair) certificates.\n\n    @ivar original: The underlying OpenSSL certificate object.\n    @type original: L{OpenSSL.crypto.X509}\n    \"\"\"\n\n    def __init__(self, original):\n        self.original = original\n\n\n    def _copyName(self, suffix):\n        dn = DistinguishedName()\n        dn._copyFrom(getattr(self.original, 'get_'+suffix)())\n        return dn\n\n\n    def getSubject(self):\n        \"\"\"\n        Retrieve the subject of this certificate.\n\n        @return: A copy of the subject of this certificate.\n        @rtype: L{DistinguishedName}\n        \"\"\"\n        return self._copyName('subject')\n\n\n    def __conform__(self, interface):\n        \"\"\"\n        Convert this L{CertBase} into a provider of the given interface.\n\n        @param interface: The interface to conform to.\n        @type interface: L{zope.interface.interfaces.IInterface}\n\n        @return: an L{IOpenSSLTrustRoot} provider or L{NotImplemented}\n        @rtype: L{IOpenSSLTrustRoot} or L{NotImplemented}\n        \"\"\"\n        if interface is IOpenSSLTrustRoot:\n            return OpenSSLCertificateAuthorities([self.original])\n        return NotImplemented\n\n\n\ndef _handleattrhelper(Class, transport, methodName):\n    \"\"\"\n    (private) Helper for L{Certificate.peerFromTransport} and\n    L{Certificate.hostFromTransport} which checks for incompatible handle types\n    and null certificates and raises the appropriate exception or returns the\n    appropriate certificate object.\n    \"\"\"\n    method = getattr(transport.getHandle(),\n                     \"get_%s_certificate\" % (methodName,), None)\n    if method is None:\n        raise CertificateError(\n            \"non-TLS transport %r did not have %s certificate\" % (transport, methodName))\n    cert = method()\n    if cert is None:\n        raise CertificateError(\n            \"TLS transport %r did not have %s certificate\" % (transport, methodName))\n    return Class(cert)\n\n\n\nclass Certificate(CertBase):\n    \"\"\"\n    An x509 certificate.\n    \"\"\"\n    def __repr__(self):\n        return '<%s Subject=%s Issuer=%s>' % (self.__class__.__name__,\n                                              self.getSubject().commonName,\n                                              self.getIssuer().commonName)\n\n\n    def __eq__(self, other):\n        if isinstance(other, Certificate):\n            return self.dump() == other.dump()\n        return False\n\n\n    def __ne__(self, other):\n        return not self.__eq__(other)\n\n\n    @classmethod\n    def load(Class, requestData, format=crypto.FILETYPE_ASN1, args=()):\n        \"\"\"\n        Load a certificate from an ASN.1- or PEM-format string.\n\n        @rtype: C{Class}\n        \"\"\"\n        return Class(crypto.load_certificate(format, requestData), *args)\n\n    # We can't use super() because it is old style still, so we have to hack\n    # around things wanting to call the parent function\n    _load = load\n\n\n    def dumpPEM(self):\n        \"\"\"\n        Dump this certificate to a PEM-format data string.\n\n        @rtype: L{str}\n        \"\"\"\n        return self.dump(crypto.FILETYPE_PEM)\n\n\n    @classmethod\n    def loadPEM(Class, data):\n        \"\"\"\n        Load a certificate from a PEM-format data string.\n\n        @rtype: C{Class}\n        \"\"\"\n        return Class.load(data, crypto.FILETYPE_PEM)\n\n\n    @classmethod\n    def peerFromTransport(Class, transport):\n        \"\"\"\n        Get the certificate for the remote end of the given transport.\n\n        @param transport: an L{ISystemHandle} provider\n\n        @rtype: C{Class}\n\n        @raise: L{CertificateError}, if the given transport does not have a peer\n            certificate.\n        \"\"\"\n        return _handleattrhelper(Class, transport, 'peer')\n\n\n    @classmethod\n    def hostFromTransport(Class, transport):\n        \"\"\"\n        Get the certificate for the local end of the given transport.\n\n        @param transport: an L{ISystemHandle} provider; the transport we will\n\n        @rtype: C{Class}\n\n        @raise: L{CertificateError}, if the given transport does not have a host\n            certificate.\n        \"\"\"\n        return _handleattrhelper(Class, transport, 'host')\n\n\n    def getPublicKey(self):\n        \"\"\"\n        Get the public key for this certificate.\n\n        @rtype: L{PublicKey}\n        \"\"\"\n        return PublicKey(self.original.get_pubkey())\n\n\n    def dump(self, format=crypto.FILETYPE_ASN1):\n        return crypto.dump_certificate(format, self.original)\n\n\n    def serialNumber(self):\n        \"\"\"\n        Retrieve the serial number of this certificate.\n\n        @rtype: L{int}\n        \"\"\"\n        return self.original.get_serial_number()\n\n\n    def digest(self, method='md5'):\n        \"\"\"\n        Return a digest hash of this certificate using the specified hash\n        algorithm.\n\n        @param method: One of C{'md5'} or C{'sha'}.\n\n        @return: The digest of the object, formatted as b\":\"-delimited hex\n            pairs\n        @rtype: L{bytes}\n        \"\"\"\n        return self.original.digest(method)\n\n\n    def _inspect(self):\n        return '\\n'.join(['Certificate For Subject:',\n                          self.getSubject().inspect(),\n                          '\\nIssuer:',\n                          self.getIssuer().inspect(),\n                          '\\nSerial Number: %d' % self.serialNumber(),\n                          'Digest: %s' % nativeString(self.digest())])\n\n\n    def inspect(self):\n        \"\"\"\n        Return a multi-line, human-readable representation of this\n        Certificate, including information about the subject, issuer, and\n        public key.\n        \"\"\"\n        return '\\n'.join((self._inspect(), self.getPublicKey().inspect()))\n\n\n    def getIssuer(self):\n        \"\"\"\n        Retrieve the issuer of this certificate.\n\n        @rtype: L{DistinguishedName}\n        @return: A copy of the issuer of this certificate.\n        \"\"\"\n        return self._copyName('issuer')\n\n\n    def options(self, *authorities):\n        raise NotImplementedError('Possible, but doubtful we need this yet')\n\n\n\nclass CertificateRequest(CertBase):\n    \"\"\"\n    An x509 certificate request.\n\n    Certificate requests are given to certificate authorities to be signed and\n    returned resulting in an actual certificate.\n    \"\"\"\n    @classmethod\n    def load(Class, requestData, requestFormat=crypto.FILETYPE_ASN1):\n        req = crypto.load_certificate_request(requestFormat, requestData)\n        dn = DistinguishedName()\n        dn._copyFrom(req.get_subject())\n        if not req.verify(req.get_pubkey()):\n            raise VerifyError(\"Can't verify that request for %r is self-signed.\" % (dn,))\n        return Class(req)\n\n\n    def dump(self, format=crypto.FILETYPE_ASN1):\n        return crypto.dump_certificate_request(format, self.original)\n\n\n\nclass PrivateCertificate(Certificate):\n    \"\"\"\n    An x509 certificate and private key.\n    \"\"\"\n    def __repr__(self):\n        return Certificate.__repr__(self) + ' with ' + repr(self.privateKey)\n\n\n    def _setPrivateKey(self, privateKey):\n        if not privateKey.matches(self.getPublicKey()):\n            raise VerifyError(\n                \"Certificate public and private keys do not match.\")\n        self.privateKey = privateKey\n        return self\n\n\n    def newCertificate(self, newCertData, format=crypto.FILETYPE_ASN1):\n        \"\"\"\n        Create a new L{PrivateCertificate} from the given certificate data and\n        this instance's private key.\n        \"\"\"\n        return self.load(newCertData, self.privateKey, format)\n\n\n    @classmethod\n    def load(Class, data, privateKey, format=crypto.FILETYPE_ASN1):\n        return Class._load(data, format)._setPrivateKey(privateKey)\n\n\n    def inspect(self):\n        return '\\n'.join([Certificate._inspect(self),\n                          self.privateKey.inspect()])\n\n\n    def dumpPEM(self):\n        \"\"\"\n        Dump both public and private parts of a private certificate to\n        PEM-format data.\n        \"\"\"\n        return self.dump(crypto.FILETYPE_PEM) + self.privateKey.dump(crypto.FILETYPE_PEM)\n\n\n    @classmethod\n    def loadPEM(Class, data):\n        \"\"\"\n        Load both private and public parts of a private certificate from a\n        chunk of PEM-format data.\n        \"\"\"\n        return Class.load(data, KeyPair.load(data, crypto.FILETYPE_PEM),\n                          crypto.FILETYPE_PEM)\n\n\n    @classmethod\n    def fromCertificateAndKeyPair(Class, certificateInstance, privateKey):\n        privcert = Class(certificateInstance.original)\n        return privcert._setPrivateKey(privateKey)\n\n\n    def options(self, *authorities):\n        \"\"\"\n        Create a context factory using this L{PrivateCertificate}'s certificate\n        and private key.\n\n        @param authorities: A list of L{Certificate} object\n\n        @return: A context factory.\n        @rtype: L{CertificateOptions <twisted.internet.ssl.CertificateOptions>}\n        \"\"\"\n        options = dict(privateKey=self.privateKey.original,\n                       certificate=self.original)\n        if authorities:\n            options.update(dict(trustRoot=OpenSSLCertificateAuthorities(\n                [auth.original for auth in authorities]\n            )))\n        return OpenSSLCertificateOptions(**options)\n\n\n    def certificateRequest(self, format=crypto.FILETYPE_ASN1,\n                           digestAlgorithm='sha256'):\n        return self.privateKey.certificateRequest(\n            self.getSubject(),\n            format,\n            digestAlgorithm)\n\n\n    def signCertificateRequest(self,\n                               requestData,\n                               verifyDNCallback,\n                               serialNumber,\n                               requestFormat=crypto.FILETYPE_ASN1,\n                               certificateFormat=crypto.FILETYPE_ASN1):\n        issuer = self.getSubject()\n        return self.privateKey.signCertificateRequest(\n            issuer,\n            requestData,\n            verifyDNCallback,\n            serialNumber,\n            requestFormat,\n            certificateFormat)\n\n\n    def signRequestObject(self, certificateRequest, serialNumber,\n                          secondsToExpiry=60 * 60 * 24 * 365, # One year\n                          digestAlgorithm='sha256'):\n        return self.privateKey.signRequestObject(self.getSubject(),\n                                                 certificateRequest,\n                                                 serialNumber,\n                                                 secondsToExpiry,\n                                                 digestAlgorithm)\n\n\n\n@_oldStyle\nclass PublicKey:\n    \"\"\"\n    A L{PublicKey} is a representation of the public part of a key pair.\n\n    You can't do a whole lot with it aside from comparing it to other\n    L{PublicKey} objects.\n\n    @note: If constructing a L{PublicKey} manually, be sure to pass only a\n        L{OpenSSL.crypto.PKey} that does not contain a private key!\n\n    @ivar original: The original private key.\n    \"\"\"\n\n    def __init__(self, osslpkey):\n        \"\"\"\n        @param osslpkey: The underlying pyOpenSSL key object.\n        @type osslpkey: L{OpenSSL.crypto.PKey}\n        \"\"\"\n        self.original = osslpkey\n\n\n    def matches(self, otherKey):\n        \"\"\"\n        Does this L{PublicKey} contain the same value as another L{PublicKey}?\n\n        @param otherKey: The key to compare C{self} to.\n        @type otherKey: L{PublicKey}\n\n        @return: L{True} if these keys match, L{False} if not.\n        @rtype: L{bool}\n        \"\"\"\n        return self.keyHash() == otherKey.keyHash()\n\n\n    def __repr__(self):\n        return '<%s %s>' % (self.__class__.__name__, self.keyHash())\n\n\n    def keyHash(self):\n        \"\"\"\n        Compute a hash of the underlying PKey object.\n\n        The purpose of this method is to allow you to determine if two\n        certificates share the same public key; it is not really useful for\n        anything else.\n\n        In versions of Twisted prior to 15.0, C{keyHash} used a technique\n        involving certificate requests for computing the hash that was not\n        stable in the face of changes to the underlying OpenSSL library.\n\n        @return: Return a 32-character hexadecimal string uniquely identifying\n            this public key, I{for this version of Twisted}.\n        @rtype: native L{str}\n        \"\"\"\n        raw = crypto.dump_publickey(crypto.FILETYPE_ASN1, self.original)\n        h = md5()\n        h.update(raw)\n        return h.hexdigest()\n\n\n    def inspect(self):\n        return 'Public Key with Hash: %s' % (self.keyHash(),)\n\n\n\nclass KeyPair(PublicKey):\n\n    @classmethod\n    def load(Class, data, format=crypto.FILETYPE_ASN1):\n        return Class(crypto.load_privatekey(format, data))\n\n\n    def dump(self, format=crypto.FILETYPE_ASN1):\n        return crypto.dump_privatekey(format, self.original)\n\n\n    def __getstate__(self):\n        return self.dump()\n\n\n    def __setstate__(self, state):\n        self.__init__(crypto.load_privatekey(crypto.FILETYPE_ASN1, state))\n\n\n    def inspect(self):\n        t = self.original.type()\n        if t == crypto.TYPE_RSA:\n            ts = 'RSA'\n        elif t == crypto.TYPE_DSA:\n            ts = 'DSA'\n        else:\n            ts = '(Unknown Type!)'\n        L = (self.original.bits(), ts, self.keyHash())\n        return '%s-bit %s Key Pair with Hash: %s' % L\n\n\n    @classmethod\n    def generate(Class, kind=crypto.TYPE_RSA, size=2048):\n        pkey = crypto.PKey()\n        pkey.generate_key(kind, size)\n        return Class(pkey)\n\n\n    def newCertificate(self, newCertData, format=crypto.FILETYPE_ASN1):\n        return PrivateCertificate.load(newCertData, self, format)\n\n\n    def requestObject(self, distinguishedName, digestAlgorithm='sha256'):\n        req = crypto.X509Req()\n        req.set_pubkey(self.original)\n        distinguishedName._copyInto(req.get_subject())\n        req.sign(self.original, digestAlgorithm)\n        return CertificateRequest(req)\n\n\n    def certificateRequest(self, distinguishedName,\n                           format=crypto.FILETYPE_ASN1,\n                           digestAlgorithm='sha256'):\n        \"\"\"\n        Create a certificate request signed with this key.\n\n        @return: a string, formatted according to the 'format' argument.\n        \"\"\"\n        return self.requestObject(distinguishedName, digestAlgorithm).dump(format)\n\n\n    def signCertificateRequest(self,\n                               issuerDistinguishedName,\n                               requestData,\n                               verifyDNCallback,\n                               serialNumber,\n                               requestFormat=crypto.FILETYPE_ASN1,\n                               certificateFormat=crypto.FILETYPE_ASN1,\n                               secondsToExpiry=60 * 60 * 24 * 365, # One year\n                               digestAlgorithm='sha256'):\n        \"\"\"\n        Given a blob of certificate request data and a certificate authority's\n        DistinguishedName, return a blob of signed certificate data.\n\n        If verifyDNCallback returns a Deferred, I will return a Deferred which\n        fires the data when that Deferred has completed.\n        \"\"\"\n        hlreq = CertificateRequest.load(requestData, requestFormat)\n\n        dn = hlreq.getSubject()\n        vval = verifyDNCallback(dn)\n\n        def verified(value):\n            if not value:\n                raise VerifyError(\"DN callback %r rejected request DN %r\" % (verifyDNCallback, dn))\n            return self.signRequestObject(issuerDistinguishedName, hlreq,\n                                          serialNumber, secondsToExpiry, digestAlgorithm).dump(certificateFormat)\n\n        if isinstance(vval, Deferred):\n            return vval.addCallback(verified)\n        else:\n            return verified(vval)\n\n\n    def signRequestObject(self,\n                          issuerDistinguishedName,\n                          requestObject,\n                          serialNumber,\n                          secondsToExpiry=60 * 60 * 24 * 365, # One year\n                          digestAlgorithm='sha256'):\n        \"\"\"\n        Sign a CertificateRequest instance, returning a Certificate instance.\n        \"\"\"\n        req = requestObject.original\n        cert = crypto.X509()\n        issuerDistinguishedName._copyInto(cert.get_issuer())\n        cert.set_subject(req.get_subject())\n        cert.set_pubkey(req.get_pubkey())\n        cert.gmtime_adj_notBefore(0)\n        cert.gmtime_adj_notAfter(secondsToExpiry)\n        cert.set_serial_number(serialNumber)\n        cert.sign(self.original, digestAlgorithm)\n        return Certificate(cert)\n\n\n    def selfSignedCert(self, serialNumber, **kw):\n        dn = DN(**kw)\n        return PrivateCertificate.fromCertificateAndKeyPair(\n            self.signRequestObject(dn, self.requestObject(dn), serialNumber),\n            self)\n\nKeyPair.__getstate__ = deprecated(Version(\"Twisted\", 15, 0, 0),\n    \"a real persistence system\")(KeyPair.__getstate__)\nKeyPair.__setstate__ = deprecated(Version(\"Twisted\", 15, 0, 0),\n    \"a real persistence system\")(KeyPair.__setstate__)\n\n\n\nclass IOpenSSLTrustRoot(Interface):\n    \"\"\"\n    Trust settings for an OpenSSL context.\n\n    Note that this interface's methods are private, so things outside of\n    Twisted shouldn't implement it.\n    \"\"\"\n\n    def _addCACertsToContext(context):\n        \"\"\"\n        Add certificate-authority certificates to an SSL context whose\n        connections should trust those authorities.\n\n        @param context: An SSL context for a connection which should be\n            verified by some certificate authority.\n        @type context: L{OpenSSL.SSL.Context}\n\n        @return: L{None}\n        \"\"\"\n\n\n\n@implementer(IOpenSSLTrustRoot)\nclass OpenSSLCertificateAuthorities(object):\n    \"\"\"\n    Trust an explicitly specified set of certificates, represented by a list of\n    L{OpenSSL.crypto.X509} objects.\n    \"\"\"\n\n    def __init__(self, caCerts):\n        \"\"\"\n        @param caCerts: The certificate authorities to trust when using this\n            object as a C{trustRoot} for L{OpenSSLCertificateOptions}.\n        @type caCerts: L{list} of L{OpenSSL.crypto.X509}\n        \"\"\"\n        self._caCerts = caCerts\n\n\n    def _addCACertsToContext(self, context):\n        store = context.get_cert_store()\n        for cert in self._caCerts:\n            store.add_cert(cert)\n\n\n\ndef trustRootFromCertificates(certificates):\n    \"\"\"\n    Builds an object that trusts multiple root L{Certificate}s.\n\n    When passed to L{optionsForClientTLS}, connections using those options will\n    reject any server certificate not signed by at least one of the\n    certificates in the `certificates` list.\n\n    @since: 16.0\n\n    @param certificates: All certificates which will be trusted.\n    @type certificates: C{iterable} of L{CertBase}\n\n    @rtype: L{IOpenSSLTrustRoot}\n    @return: an object suitable for use as the trustRoot= keyword argument to\n        L{optionsForClientTLS}\n    \"\"\"\n\n    certs = []\n    for cert in certificates:\n        # PrivateCertificate or Certificate are both okay\n        if isinstance(cert, CertBase):\n            cert = cert.original\n        else:\n            raise TypeError(\n                \"certificates items must be twisted.internet.ssl.CertBase\"\n                \" instances\"\n            )\n        certs.append(cert)\n    return OpenSSLCertificateAuthorities(certs)\n\n\n\n@implementer(IOpenSSLTrustRoot)\nclass OpenSSLDefaultPaths(object):\n    \"\"\"\n    Trust the set of default verify paths that OpenSSL was built with, as\n    specified by U{SSL_CTX_set_default_verify_paths\n    <https://www.openssl.org/docs/ssl/SSL_CTX_load_verify_locations.html>}.\n    \"\"\"\n\n    def _addCACertsToContext(self, context):\n        context.set_default_verify_paths()\n\n\n\ndef platformTrust():\n    \"\"\"\n    Attempt to discover a set of trusted certificate authority certificates\n    (or, in other words: trust roots, or root certificates) whose trust is\n    managed and updated by tools outside of Twisted.\n\n    If you are writing any client-side TLS code with Twisted, you should use\n    this as the C{trustRoot} argument to L{CertificateOptions\n    <twisted.internet.ssl.CertificateOptions>}.\n\n    The result of this function should be like the up-to-date list of\n    certificates in a web browser.  When developing code that uses\n    C{platformTrust}, you can think of it that way.  However, the choice of\n    which certificate authorities to trust is never Twisted's responsibility.\n    Unless you're writing a very unusual application or library, it's not your\n    code's responsibility either.  The user may use platform-specific tools for\n    defining which server certificates should be trusted by programs using TLS.\n    The purpose of using this API is to respect that decision as much as\n    possible.\n\n    This should be a set of trust settings most appropriate for I{client} TLS\n    connections; i.e. those which need to verify a server's authenticity.  You\n    should probably use this by default for any client TLS connection that you\n    create.  For servers, however, client certificates are typically not\n    verified; or, if they are, their verification will depend on a custom,\n    application-specific certificate authority.\n\n    @since: 14.0\n\n    @note: Currently, L{platformTrust} depends entirely upon your OpenSSL build\n        supporting a set of \"L{default verify paths <OpenSSLDefaultPaths>}\"\n        which correspond to certificate authority trust roots.  Unfortunately,\n        whether this is true of your system is both outside of Twisted's\n        control and difficult (if not impossible) for Twisted to detect\n        automatically.\n\n        Nevertheless, this ought to work as desired by default on:\n\n            - Ubuntu Linux machines with the U{ca-certificates\n              <https://launchpad.net/ubuntu/+source/ca-certificates>} package\n              installed,\n\n            - macOS when using the system-installed version of OpenSSL (i.e.\n              I{not} one installed via MacPorts or Homebrew),\n\n            - any build of OpenSSL which has had certificate authority\n              certificates installed into its default verify paths (by default,\n              C{/usr/local/ssl/certs} if you've built your own OpenSSL), or\n\n            - any process where the C{SSL_CERT_FILE} environment variable is\n              set to the path of a file containing your desired CA certificates\n              bundle.\n\n        Hopefully soon, this API will be updated to use more sophisticated\n        trust-root discovery mechanisms.  Until then, you can follow tickets in\n        the Twisted tracker for progress on this implementation on U{Microsoft\n        Windows <https://twistedmatrix.com/trac/ticket/6371>}, U{macOS\n        <https://twistedmatrix.com/trac/ticket/6372>}, and U{a fallback for\n        other platforms which do not have native trust management tools\n        <https://twistedmatrix.com/trac/ticket/6934>}.\n\n    @return: an appropriate trust settings object for your platform.\n    @rtype: L{IOpenSSLTrustRoot}\n\n    @raise NotImplementedError: if this platform is not yet supported by\n        Twisted.  At present, only OpenSSL is supported.\n    \"\"\"\n    return OpenSSLDefaultPaths()\n\n\n\ndef _tolerateErrors(wrapped):\n    \"\"\"\n    Wrap up an C{info_callback} for pyOpenSSL so that if something goes wrong\n    the error is immediately logged and the connection is dropped if possible.\n\n    This wrapper exists because some versions of pyOpenSSL don't handle errors\n    from callbacks at I{all}, and those which do write tracebacks directly to\n    stderr rather than to a supplied logging system.  This reports unexpected\n    errors to the Twisted logging system.\n\n    Also, this terminates the connection immediately if possible because if\n    you've got bugs in your verification logic it's much safer to just give up.\n\n    @param wrapped: A valid C{info_callback} for pyOpenSSL.\n    @type wrapped: L{callable}\n\n    @return: A valid C{info_callback} for pyOpenSSL that handles any errors in\n        C{wrapped}.\n    @rtype: L{callable}\n    \"\"\"\n    def infoCallback(connection, where, ret):\n        try:\n            return wrapped(connection, where, ret)\n        except:\n            f = Failure()\n            log.err(f, \"Error during info_callback\")\n            connection.get_app_data().failVerification(f)\n    return infoCallback\n\n\n\n@implementer(IOpenSSLClientConnectionCreator)\nclass ClientTLSOptions(object):\n    \"\"\"\n    Client creator for TLS.\n\n    Private implementation type (not exposed to applications) for public\n    L{optionsForClientTLS} API.\n\n    @ivar _ctx: The context to use for new connections.\n    @type _ctx: L{OpenSSL.SSL.Context}\n\n    @ivar _hostname: The hostname to verify, as specified by the application,\n        as some human-readable text.\n    @type _hostname: L{unicode}\n\n    @ivar _hostnameBytes: The hostname to verify, decoded into IDNA-encoded\n        bytes.  This is passed to APIs which think that hostnames are bytes,\n        such as OpenSSL's SNI implementation.\n    @type _hostnameBytes: L{bytes}\n\n    @ivar _hostnameASCII: The hostname, as transcoded into IDNA ASCII-range\n        unicode code points.  This is pre-transcoded because the\n        C{service_identity} package is rather strict about requiring the\n        C{idna} package from PyPI for internationalized domain names, rather\n        than working with Python's built-in (but sometimes broken) IDNA\n        encoding.  ASCII values, however, will always work.\n    @type _hostnameASCII: L{unicode}\n\n    @ivar _hostnameIsDnsName: Whether or not the C{_hostname} is a DNSName.\n        Will be L{False} if C{_hostname} is an IP address or L{True} if\n        C{_hostname} is a DNSName\n    @type _hostnameIsDnsName: L{bool}\n    \"\"\"\n\n    def __init__(self, hostname, ctx):\n        \"\"\"\n        Initialize L{ClientTLSOptions}.\n\n        @param hostname: The hostname to verify as input by a human.\n        @type hostname: L{unicode}\n\n        @param ctx: an L{OpenSSL.SSL.Context} to use for new connections.\n        @type ctx: L{OpenSSL.SSL.Context}.\n        \"\"\"\n        self._ctx = ctx\n        self._hostname = hostname\n\n        if isIPAddress(hostname) or isIPv6Address(hostname):\n            self._hostnameBytes = hostname.encode('ascii')\n            self._hostnameIsDnsName = False\n        else:\n            self._hostnameBytes = _idnaBytes(hostname)\n            self._hostnameIsDnsName = True\n\n        self._hostnameASCII = self._hostnameBytes.decode(\"ascii\")\n        ctx.set_info_callback(\n            _tolerateErrors(self._identityVerifyingInfoCallback)\n        )\n\n\n    def clientConnectionForTLS(self, tlsProtocol):\n        \"\"\"\n        Create a TLS connection for a client.\n\n        @note: This will call C{set_app_data} on its connection.  If you're\n            delegating to this implementation of this method, don't ever call\n            C{set_app_data} or C{set_info_callback} on the returned connection,\n            or you'll break the implementation of various features of this\n            class.\n\n        @param tlsProtocol: the TLS protocol initiating the connection.\n        @type tlsProtocol: L{twisted.protocols.tls.TLSMemoryBIOProtocol}\n\n        @return: the configured client connection.\n        @rtype: L{OpenSSL.SSL.Connection}\n        \"\"\"\n        context = self._ctx\n        connection = SSL.Connection(context, None)\n        connection.set_app_data(tlsProtocol)\n        return connection\n\n\n    def _identityVerifyingInfoCallback(self, connection, where, ret):\n        \"\"\"\n        U{info_callback\n        <http://pythonhosted.org/pyOpenSSL/api/ssl.html#OpenSSL.SSL.Context.set_info_callback>\n        } for pyOpenSSL that verifies the hostname in the presented certificate\n        matches the one passed to this L{ClientTLSOptions}.\n\n        @param connection: the connection which is handshaking.\n        @type connection: L{OpenSSL.SSL.Connection}\n\n        @param where: flags indicating progress through a TLS handshake.\n        @type where: L{int}\n\n        @param ret: ignored\n        @type ret: ignored\n        \"\"\"\n        # Literal IPv4 and IPv6 addresses are not permitted\n        # as host names according to the RFCs\n        if where & SSL.SSL_CB_HANDSHAKE_START and self._hostnameIsDnsName:\n            connection.set_tlsext_host_name(self._hostnameBytes)\n        elif where & SSL.SSL_CB_HANDSHAKE_DONE:\n            try:\n                if self._hostnameIsDnsName:\n                    verifyHostname(connection, self._hostnameASCII)\n                else:\n                    verifyIPAddress(connection, self._hostnameASCII)\n            except VerificationError:\n                f = Failure()\n                transport = connection.get_app_data()\n                transport.failVerification(f)\n\n\n\ndef optionsForClientTLS(hostname, trustRoot=None, clientCertificate=None,\n                        acceptableProtocols=None, **kw):\n    \"\"\"\n    Create a L{client connection creator <IOpenSSLClientConnectionCreator>} for\n    use with APIs such as L{SSL4ClientEndpoint\n    <twisted.internet.endpoints.SSL4ClientEndpoint>}, L{connectSSL\n    <twisted.internet.interfaces.IReactorSSL.connectSSL>}, and L{startTLS\n    <twisted.internet.interfaces.ITLSTransport.startTLS>}.\n\n    @since: 14.0\n\n    @param hostname: The expected name of the remote host. This serves two\n        purposes: first, and most importantly, it verifies that the certificate\n        received from the server correctly identifies the specified hostname.\n        The second purpose is to use the U{Server Name Indication extension\n        <https://en.wikipedia.org/wiki/Server_Name_Indication>} to indicate to\n        the server which certificate should be used.\n    @type hostname: L{unicode}\n\n    @param trustRoot: Specification of trust requirements of peers. This may be\n        a L{Certificate} or the result of L{platformTrust}. By default it is\n        L{platformTrust} and you probably shouldn't adjust it unless you really\n        know what you're doing. Be aware that clients using this interface\n        I{must} verify the server; you cannot explicitly pass L{None} since\n        that just means to use L{platformTrust}.\n    @type trustRoot: L{IOpenSSLTrustRoot}\n\n    @param clientCertificate: The certificate and private key that the client\n        will use to authenticate to the server. If unspecified, the client will\n        not authenticate.\n    @type clientCertificate: L{PrivateCertificate}\n\n    @param acceptableProtocols: The protocols this peer is willing to speak\n        after the TLS negotiation has completed, advertised over both ALPN and\n        NPN. If this argument is specified, and no overlap can be found with\n        the other peer, the connection will fail to be established. If the\n        remote peer does not offer NPN or ALPN, the connection will be\n        established, but no protocol wil be negotiated. Protocols earlier in\n        the list are preferred over those later in the list.\n    @type acceptableProtocols: L{list} of L{bytes}\n\n    @param extraCertificateOptions: keyword-only argument; this is a dictionary\n        of additional keyword arguments to be presented to\n        L{CertificateOptions}. Please avoid using this unless you absolutely\n        need to; any time you need to pass an option here that is a bug in this\n        interface.\n    @type extraCertificateOptions: L{dict}\n\n    @param kw: (Backwards compatibility hack to allow keyword-only arguments on\n        Python 2. Please ignore; arbitrary keyword arguments will be errors.)\n    @type kw: L{dict}\n\n    @return: A client connection creator.\n    @rtype: L{IOpenSSLClientConnectionCreator}\n    \"\"\"\n    extraCertificateOptions = kw.pop('extraCertificateOptions', None) or {}\n    if trustRoot is None:\n        trustRoot = platformTrust()\n    if kw:\n        raise TypeError(\n            \"optionsForClientTLS() got an unexpected keyword argument\"\n            \" '{arg}'\".format(\n                arg=kw.popitem()[0]\n            )\n        )\n    if not isinstance(hostname, unicode):\n        raise TypeError(\n            \"optionsForClientTLS requires text for host names, not \"\n            + hostname.__class__.__name__\n        )\n    if clientCertificate:\n        extraCertificateOptions.update(\n            privateKey=clientCertificate.privateKey.original,\n            certificate=clientCertificate.original\n        )\n    certificateOptions = OpenSSLCertificateOptions(\n        trustRoot=trustRoot,\n        acceptableProtocols=acceptableProtocols,\n        **extraCertificateOptions\n    )\n    return ClientTLSOptions(hostname, certificateOptions.getContext())\n\n\n\n@implementer(IOpenSSLContextFactory)\nclass OpenSSLCertificateOptions(object):\n    \"\"\"\n    A L{CertificateOptions <twisted.internet.ssl.CertificateOptions>} specifies\n    the security properties for a client or server TLS connection used with\n    OpenSSL.\n\n    @ivar _options: Any option flags to set on the L{OpenSSL.SSL.Context}\n        object that will be created.\n    @type _options: L{int}\n\n    @ivar _cipherString: An OpenSSL-specific cipher string.\n    @type _cipherString: L{unicode}\n\n    @ivar _defaultMinimumTLSVersion: The default TLS version that will be\n        negotiated. This should be a \"safe default\", with wide client and\n        server support, vs an optimally secure one that excludes a large number\n        of users. As of late 2016, TLSv1.0 is that safe default.\n    @type _defaultMinimumTLSVersion: L{TLSVersion} constant\n    \"\"\"\n\n    # Factory for creating contexts.  Configurable for testability.\n    _contextFactory = SSL.Context\n    _context = None\n\n    _OP_NO_TLSv1_3 = _tlsDisableFlags[TLSVersion.TLSv1_3]\n\n    _defaultMinimumTLSVersion = TLSVersion.TLSv1_0\n\n    @_mutuallyExclusiveArguments([\n        ['trustRoot', 'requireCertificate'],\n        ['trustRoot', 'verify'],\n        ['trustRoot', 'caCerts'],\n        ['method', 'insecurelyLowerMinimumTo'],\n        ['method', 'raiseMinimumTo'],\n        ['raiseMinimumTo', 'insecurelyLowerMinimumTo'],\n        ['method', 'lowerMaximumSecurityTo'],\n    ])\n    def __init__(self,\n                 privateKey=None,\n                 certificate=None,\n                 method=None,\n                 verify=False,\n                 caCerts=None,\n                 verifyDepth=9,\n                 requireCertificate=True,\n                 verifyOnce=True,\n                 enableSingleUseKeys=True,\n                 enableSessions=True,\n                 fixBrokenPeers=False,\n                 enableSessionTickets=False,\n                 extraCertChain=None,\n                 acceptableCiphers=None,\n                 dhParameters=None,\n                 trustRoot=None,\n                 acceptableProtocols=None,\n                 raiseMinimumTo=None,\n                 insecurelyLowerMinimumTo=None,\n                 lowerMaximumSecurityTo=None,\n                 ):\n        \"\"\"\n        Create an OpenSSL context SSL connection context factory.\n\n        @param privateKey: A PKey object holding the private key.\n\n        @param certificate: An X509 object holding the certificate.\n\n        @param method: Deprecated, use a combination of\n            C{insecurelyLowerMinimumTo}, C{raiseMinimumTo}, or\n            C{lowerMaximumSecurityTo} instead.  The SSL protocol to use, one of\n            C{SSLv23_METHOD}, C{SSLv2_METHOD}, C{SSLv3_METHOD}, C{TLSv1_METHOD}\n            (or any other method constants provided by pyOpenSSL).  By default,\n            a setting will be used which allows TLSv1.0, TLSv1.1, and TLSv1.2.\n            Can not be used with C{insecurelyLowerMinimumTo},\n            C{raiseMinimumTo}, or C{lowerMaximumSecurityTo}\n\n        @param verify: Please use a C{trustRoot} keyword argument instead,\n            since it provides the same functionality in a less error-prone way.\n            By default this is L{False}.\n\n            If L{True}, verify certificates received from the peer and fail the\n            handshake if verification fails.  Otherwise, allow anonymous\n            sessions and sessions with certificates which fail validation.\n\n        @param caCerts: Please use a C{trustRoot} keyword argument instead,\n            since it provides the same functionality in a less error-prone way.\n\n            List of certificate authority certificate objects to use to verify\n            the peer's certificate.  Only used if verify is L{True} and will be\n            ignored otherwise.  Since verify is L{False} by default, this is\n            L{None} by default.\n\n        @type caCerts: L{list} of L{OpenSSL.crypto.X509}\n\n        @param verifyDepth: Depth in certificate chain down to which to verify.\n            If unspecified, use the underlying default (9).\n\n        @param requireCertificate: Please use a C{trustRoot} keyword argument\n            instead, since it provides the same functionality in a less\n            error-prone way.\n\n            If L{True}, do not allow anonymous sessions; defaults to L{True}.\n\n        @param verifyOnce: If True, do not re-verify the certificate on session\n            resumption.\n\n        @param enableSingleUseKeys: If L{True}, generate a new key whenever\n            ephemeral DH and ECDH parameters are used to prevent small subgroup\n            attacks and to ensure perfect forward secrecy.\n\n        @param enableSessions: If True, set a session ID on each context.  This\n            allows a shortened handshake to be used when a known client\n            reconnects.\n\n        @param fixBrokenPeers: If True, enable various non-spec protocol fixes\n            for broken SSL implementations.  This should be entirely safe,\n            according to the OpenSSL documentation, but YMMV.  This option is\n            now off by default, because it causes problems with connections\n            between peers using OpenSSL 0.9.8a.\n\n        @param enableSessionTickets: If L{True}, enable session ticket\n            extension for session resumption per RFC 5077.  Note there is no\n            support for controlling session tickets.  This option is off by\n            default, as some server implementations don't correctly process\n            incoming empty session ticket extensions in the hello.\n\n        @param extraCertChain: List of certificates that I{complete} your\n            verification chain if the certificate authority that signed your\n            C{certificate} isn't widely supported.  Do I{not} add\n            C{certificate} to it.\n        @type extraCertChain: C{list} of L{OpenSSL.crypto.X509}\n\n        @param acceptableCiphers: Ciphers that are acceptable for connections.\n            Uses a secure default if left L{None}.\n        @type acceptableCiphers: L{IAcceptableCiphers}\n\n        @param dhParameters: Key generation parameters that are required for\n            Diffie-Hellman key exchange.  If this argument is left L{None},\n            C{EDH} ciphers are I{disabled} regardless of C{acceptableCiphers}.\n        @type dhParameters: L{DiffieHellmanParameters\n            <twisted.internet.ssl.DiffieHellmanParameters>}\n\n        @param trustRoot: Specification of trust requirements of peers.  If\n            this argument is specified, the peer is verified.  It requires a\n            certificate, and that certificate must be signed by one of the\n            certificate authorities specified by this object.\n\n            Note that since this option specifies the same information as\n            C{caCerts}, C{verify}, and C{requireCertificate}, specifying any of\n            those options in combination with this one will raise a\n            L{TypeError}.\n\n        @type trustRoot: L{IOpenSSLTrustRoot}\n\n        @param acceptableProtocols: The protocols this peer is willing to speak\n            after the TLS negotiation has completed, advertised over both ALPN\n            and NPN.  If this argument is specified, and no overlap can be\n            found with the other peer, the connection will fail to be\n            established.  If the remote peer does not offer NPN or ALPN, the\n            connection will be established, but no protocol wil be negotiated.\n            Protocols earlier in the list are preferred over those later in the\n            list.\n        @type acceptableProtocols: L{list} of L{bytes}\n\n        @param raiseMinimumTo: The minimum TLS version that you want to use, or\n            Twisted's default if it is higher.  Use this if you want to make\n            your client/server more secure than Twisted's default, but will\n            accept Twisted's default instead if it moves higher than this\n            value.  You probably want to use this over\n            C{insecurelyLowerMinimumTo}.\n        @type raiseMinimumTo: L{TLSVersion} constant\n\n        @param insecurelyLowerMinimumTo: The minimum TLS version to use,\n            possibly lower than Twisted's default.  If not specified, it is a\n            generally considered safe default (TLSv1.0).  If you want to raise\n            your minimum TLS version to above that of this default, use\n            C{raiseMinimumTo}.  DO NOT use this argument unless you are\n            absolutely sure this is what you want.\n        @type insecurelyLowerMinimumTo: L{TLSVersion} constant\n\n        @param lowerMaximumSecurityTo: The maximum TLS version to use.  If not\n            specified, it is the most recent your OpenSSL supports.  You only\n            want to set this if the peer that you are communicating with has\n            problems with more recent TLS versions, it lowers your security\n            when communicating with newer peers.  DO NOT use this argument\n            unless you are absolutely sure this is what you want.\n        @type lowerMaximumSecurityTo: L{TLSVersion} constant\n\n        @raise ValueError: when C{privateKey} or C{certificate} are set without\n            setting the respective other.\n        @raise ValueError: when C{verify} is L{True} but C{caCerts} doesn't\n            specify any CA certificates.\n        @raise ValueError: when C{extraCertChain} is passed without specifying\n            C{privateKey} or C{certificate}.\n        @raise ValueError: when C{acceptableCiphers} doesn't yield any usable\n            ciphers for the current platform.\n\n        @raise TypeError: if C{trustRoot} is passed in combination with\n            C{caCert}, C{verify}, or C{requireCertificate}.  Please prefer\n            C{trustRoot} in new code, as its semantics are less tricky.\n        @raise TypeError: if C{method} is passed in combination with\n            C{tlsProtocols}.  Please prefer the more explicit C{tlsProtocols}\n            in new code.\n\n        @raises NotImplementedError: If acceptableProtocols were provided but\n            no negotiation mechanism is available.\n        \"\"\"\n\n        if (privateKey is None) != (certificate is None):\n            raise ValueError(\n                \"Specify neither or both of privateKey and certificate\")\n        self.privateKey = privateKey\n        self.certificate = certificate\n\n        # Set basic security options: disallow insecure SSLv2, disallow TLS\n        # compression to avoid CRIME attack, make the server choose the\n        # ciphers.\n        self._options = (\n            SSL.OP_NO_SSLv2 | SSL.OP_NO_COMPRESSION |\n            SSL.OP_CIPHER_SERVER_PREFERENCE\n        )\n\n        # Set the mode to Release Buffers, which demallocs send/recv buffers on\n        # idle TLS connections to save memory\n        self._mode = SSL.MODE_RELEASE_BUFFERS\n\n        if method is None:\n            self.method = SSL.SSLv23_METHOD\n\n            if raiseMinimumTo:\n                if (lowerMaximumSecurityTo and\n                    raiseMinimumTo > lowerMaximumSecurityTo):\n                    raise ValueError(\n                        (\"raiseMinimumTo needs to be lower than \"\n                         \"lowerMaximumSecurityTo\"))\n\n                if raiseMinimumTo > self._defaultMinimumTLSVersion:\n                    insecurelyLowerMinimumTo = raiseMinimumTo\n\n            if insecurelyLowerMinimumTo is None:\n                insecurelyLowerMinimumTo = self._defaultMinimumTLSVersion\n\n                # If you set the max lower than the default, but don't set the\n                # minimum, pull it down to that\n                if (lowerMaximumSecurityTo and\n                    insecurelyLowerMinimumTo > lowerMaximumSecurityTo):\n                    insecurelyLowerMinimumTo = lowerMaximumSecurityTo\n\n            if (lowerMaximumSecurityTo and\n                insecurelyLowerMinimumTo > lowerMaximumSecurityTo):\n                raise ValueError(\n                    (\"insecurelyLowerMinimumTo needs to be lower than \"\n                     \"lowerMaximumSecurityTo\"))\n\n            excludedVersions = _getExcludedTLSProtocols(\n                insecurelyLowerMinimumTo, lowerMaximumSecurityTo)\n\n            for version in excludedVersions:\n                self._options |= _tlsDisableFlags[version]\n        else:\n            warnings.warn(\n                (\"Passing method to twisted.internet.ssl.CertificateOptions \"\n                 \"was deprecated in Twisted 17.1.0. Please use a combination \"\n                 \"of insecurelyLowerMinimumTo, raiseMinimumTo, and \"\n                 \"lowerMaximumSecurityTo instead, as Twisted will correctly \"\n                 \"configure the method.\"),\n                DeprecationWarning, stacklevel=3)\n\n            # Otherwise respect the application decision.\n            self.method = method\n\n        if verify and not caCerts:\n            raise ValueError(\"Specify client CA certificate information if and\"\n                             \" only if enabling certificate verification\")\n        self.verify = verify\n        if extraCertChain is not None and None in (privateKey, certificate):\n            raise ValueError(\"A private key and a certificate are required \"\n                             \"when adding a supplemental certificate chain.\")\n        if extraCertChain is not None:\n            self.extraCertChain = extraCertChain\n        else:\n            self.extraCertChain = []\n\n        self.caCerts = caCerts\n        self.verifyDepth = verifyDepth\n        self.requireCertificate = requireCertificate\n        self.verifyOnce = verifyOnce\n        self.enableSingleUseKeys = enableSingleUseKeys\n        if enableSingleUseKeys:\n            self._options |= SSL.OP_SINGLE_DH_USE | SSL.OP_SINGLE_ECDH_USE\n        self.enableSessions = enableSessions\n        self.fixBrokenPeers = fixBrokenPeers\n        if fixBrokenPeers:\n            self._options |= SSL.OP_ALL\n        self.enableSessionTickets = enableSessionTickets\n\n        if not enableSessionTickets:\n            self._options |= SSL.OP_NO_TICKET\n        self.dhParameters = dhParameters\n\n        self._ecChooser = _ChooseDiffieHellmanEllipticCurve(\n            SSL.OPENSSL_VERSION_NUMBER,\n            openSSLlib=pyOpenSSLlib,\n            openSSLcrypto=crypto,\n        )\n\n        if acceptableCiphers is None:\n            acceptableCiphers = defaultCiphers\n        # This needs to run when method and _options are finalized.\n        self._cipherString = u':'.join(\n            c.fullName\n            for c in acceptableCiphers.selectCiphers(\n                _expandCipherString(u'ALL', self.method, self._options)\n            )\n        )\n        if self._cipherString == u'':\n            raise ValueError(\n                'Supplied IAcceptableCiphers yielded no usable ciphers '\n                'on this platform.'\n            )\n\n        if trustRoot is None:\n            if self.verify:\n                trustRoot = OpenSSLCertificateAuthorities(caCerts)\n        else:\n            self.verify = True\n            self.requireCertificate = True\n            trustRoot = IOpenSSLTrustRoot(trustRoot)\n        self.trustRoot = trustRoot\n\n        if acceptableProtocols is not None and not protocolNegotiationMechanisms():\n            raise NotImplementedError(\n                \"No support for protocol negotiation on this platform.\"\n            )\n\n        self._acceptableProtocols = acceptableProtocols\n\n\n    def __getstate__(self):\n        d = self.__dict__.copy()\n        try:\n            del d['_context']\n        except KeyError:\n            pass\n        return d\n\n\n    def __setstate__(self, state):\n        self.__dict__ = state\n\n\n    def getContext(self):\n        \"\"\"\n        Return an L{OpenSSL.SSL.Context} object.\n        \"\"\"\n        if self._context is None:\n            self._context = self._makeContext()\n        return self._context\n\n\n    def _makeContext(self):\n        ctx = self._contextFactory(self.method)\n        ctx.set_options(self._options)\n        ctx.set_mode(self._mode)\n\n        if self.certificate is not None and self.privateKey is not None:\n            ctx.use_certificate(self.certificate)\n            ctx.use_privatekey(self.privateKey)\n            for extraCert in self.extraCertChain:\n                ctx.add_extra_chain_cert(extraCert)\n            # Sanity check\n            ctx.check_privatekey()\n\n        verifyFlags = SSL.VERIFY_NONE\n        if self.verify:\n            verifyFlags = SSL.VERIFY_PEER\n            if self.requireCertificate:\n                verifyFlags |= SSL.VERIFY_FAIL_IF_NO_PEER_CERT\n            if self.verifyOnce:\n                verifyFlags |= SSL.VERIFY_CLIENT_ONCE\n            self.trustRoot._addCACertsToContext(ctx)\n\n        # It'd be nice if pyOpenSSL let us pass None here for this behavior (as\n        # the underlying OpenSSL API call allows NULL to be passed).  It\n        # doesn't, so we'll supply a function which does the same thing.\n        def _verifyCallback(conn, cert, errno, depth, preverify_ok):\n            return preverify_ok\n        ctx.set_verify(verifyFlags, _verifyCallback)\n        if self.verifyDepth is not None:\n            ctx.set_verify_depth(self.verifyDepth)\n\n        if self.enableSessions:\n            # 32 bytes is the maximum length supported\n            # Unfortunately pyOpenSSL doesn't provide SSL_MAX_SESSION_ID_LENGTH\n            sessionName = secureRandom(32)\n            ctx.set_session_id(sessionName)\n\n        if self.dhParameters:\n            ctx.load_tmp_dh(self.dhParameters._dhFile.path)\n        ctx.set_cipher_list(self._cipherString.encode('ascii'))\n\n        self._ecChooser.configureECDHCurve(ctx)\n\n        if self._acceptableProtocols:\n            # Try to set NPN and ALPN. _acceptableProtocols cannot be set by\n            # the constructor unless at least one mechanism is supported.\n            _setAcceptableProtocols(ctx, self._acceptableProtocols)\n\n        return ctx\n\n\nOpenSSLCertificateOptions.__getstate__ = deprecated(\n        Version(\"Twisted\", 15, 0, 0),\n        \"a real persistence system\")(OpenSSLCertificateOptions.__getstate__)\nOpenSSLCertificateOptions.__setstate__ = deprecated(\n        Version(\"Twisted\", 15, 0, 0),\n        \"a real persistence system\")(OpenSSLCertificateOptions.__setstate__)\n\n\n\n@implementer(ICipher)\nclass OpenSSLCipher(FancyEqMixin, object):\n    \"\"\"\n    A representation of an OpenSSL cipher.\n    \"\"\"\n    compareAttributes = ('fullName',)\n\n    def __init__(self, fullName):\n        \"\"\"\n        @param fullName: The full name of the cipher. For example\n            C{u\"ECDHE-RSA-AES256-GCM-SHA384\"}.\n        @type fullName: L{unicode}\n        \"\"\"\n        self.fullName = fullName\n\n\n    def __repr__(self):\n        \"\"\"\n        A runnable representation of the cipher.\n        \"\"\"\n        return 'OpenSSLCipher({0!r})'.format(self.fullName)\n\n\n\ndef _expandCipherString(cipherString, method, options):\n    \"\"\"\n    Expand C{cipherString} according to C{method} and C{options} to a list\n    of explicit ciphers that are supported by the current platform.\n\n    @param cipherString: An OpenSSL cipher string to expand.\n    @type cipherString: L{unicode}\n\n    @param method: An OpenSSL method like C{SSL.TLSv1_METHOD} used for\n        determining the effective ciphers.\n\n    @param options: OpenSSL options like C{SSL.OP_NO_SSLv3} ORed together.\n    @type options: L{int}\n\n    @return: The effective list of explicit ciphers that results from the\n        arguments on the current platform.\n    @rtype: L{list} of L{ICipher}\n    \"\"\"\n    ctx = SSL.Context(method)\n    ctx.set_options(options)\n    try:\n        ctx.set_cipher_list(cipherString.encode('ascii'))\n    except SSL.Error as e:\n        # OpenSSL 1.1.1 turns an invalid cipher list into TLS 1.3\n        # ciphers, so pyOpenSSL >= 19.0.0 raises an artificial Error\n        # that lacks a corresponding OpenSSL error if the cipher list\n        # consists only of these after a call to set_cipher_list.\n        if not e.args[0]:\n            return []\n        if e.args[0][0][2] == 'no cipher match':\n            return []\n        else:\n            raise\n    conn = SSL.Connection(ctx, None)\n    ciphers = conn.get_cipher_list()\n    if isinstance(ciphers[0], unicode):\n        return [OpenSSLCipher(cipher) for cipher in ciphers]\n    else:\n        return [OpenSSLCipher(cipher.decode('ascii')) for cipher in ciphers]\n\n\n\n@implementer(IAcceptableCiphers)\nclass OpenSSLAcceptableCiphers(object):\n    \"\"\"\n    A representation of ciphers that are acceptable for TLS connections.\n    \"\"\"\n    def __init__(self, ciphers):\n        self._ciphers = ciphers\n\n\n    def selectCiphers(self, availableCiphers):\n        return [cipher\n                for cipher in self._ciphers\n                if cipher in availableCiphers]\n\n\n    @classmethod\n    def fromOpenSSLCipherString(cls, cipherString):\n        \"\"\"\n        Create a new instance using an OpenSSL cipher string.\n\n        @param cipherString: An OpenSSL cipher string that describes what\n            cipher suites are acceptable.\n            See the documentation of U{OpenSSL\n            <http://www.openssl.org/docs/apps/ciphers.html#CIPHER_STRINGS>} or\n            U{Apache\n            <http://httpd.apache.org/docs/2.4/mod/mod_ssl.html#sslciphersuite>}\n            for details.\n        @type cipherString: L{unicode}\n\n        @return: Instance representing C{cipherString}.\n        @rtype: L{twisted.internet.ssl.AcceptableCiphers}\n        \"\"\"\n        return cls(_expandCipherString(\n            nativeString(cipherString),\n            SSL.SSLv23_METHOD, SSL.OP_NO_SSLv2 | SSL.OP_NO_SSLv3)\n        )\n\n\n# A secure default.\n# Sources for more information on TLS ciphers:\n#\n# - https://wiki.mozilla.org/Security/Server_Side_TLS\n# - https://www.ssllabs.com/projects/best-practices/index.html\n# - https://hynek.me/articles/hardening-your-web-servers-ssl-ciphers/\n#\n# The general intent is:\n# - Prefer cipher suites that offer perfect forward secrecy (DHE/ECDHE),\n# - prefer ECDHE over DHE for better performance,\n# - prefer any AES-GCM and ChaCha20 over any AES-CBC for better performance and\n#   security,\n# - prefer AES-GCM to ChaCha20 because AES hardware support is common,\n# - disable NULL authentication, MD5 MACs and DSS for security reasons.\n#\ndefaultCiphers = OpenSSLAcceptableCiphers.fromOpenSSLCipherString(\n    \"TLS13-AES-256-GCM-SHA384:TLS13-CHACHA20-POLY1305-SHA256:\"\n    \"TLS13-AES-128-GCM-SHA256:\"\n    \"ECDH+AESGCM:ECDH+CHACHA20:DH+AESGCM:DH+CHACHA20:ECDH+AES256:DH+AES256:\"\n    \"ECDH+AES128:DH+AES:RSA+AESGCM:RSA+AES:\"\n    \"!aNULL:!MD5:!DSS\"\n)\n_defaultCurveName = u\"prime256v1\"\n\n\n\nclass _ChooseDiffieHellmanEllipticCurve(object):\n    \"\"\"\n    Chooses the best elliptic curve for Elliptic Curve Diffie-Hellman\n    key exchange, and provides a C{configureECDHCurve} method to set\n    the curve, when appropriate, on a new L{OpenSSL.SSL.Context}.\n\n    The C{configureECDHCurve} method will be set to one of the\n    following based on the provided OpenSSL version and configuration:\n\n        - L{_configureOpenSSL110}\n\n        - L{_configureOpenSSL102}\n\n        - L{_configureOpenSSL101}\n\n        - L{_configureOpenSSL101NoCurves}.\n\n    @param openSSLVersion: The OpenSSL version number.\n    @type openSSLVersion: L{int}\n\n    @see: L{OpenSSL.SSL.OPENSSL_VERSION_NUMBER}\n\n    @param openSSLlib: The OpenSSL C{cffi} library module.\n    @param openSSLlib: The OpenSSL L{crypto} module.\n\n    @see: L{crypto}\n    \"\"\"\n\n    def __init__(self, openSSLVersion, openSSLlib, openSSLcrypto):\n        self._openSSLlib = openSSLlib\n        self._openSSLcrypto = openSSLcrypto\n        if openSSLVersion >= 0x10100000:\n            self.configureECDHCurve = self._configureOpenSSL110\n        elif openSSLVersion >= 0x10002000:\n            self.configureECDHCurve = self._configureOpenSSL102\n        else:\n            try:\n                self._ecCurve = openSSLcrypto.get_elliptic_curve(\n                    _defaultCurveName)\n            except ValueError:\n                # The get_elliptic_curve method raises a ValueError\n                # when the curve does not exist.\n                self.configureECDHCurve = self._configureOpenSSL101NoCurves\n            else:\n                self.configureECDHCurve = self._configureOpenSSL101\n\n\n    def _configureOpenSSL110(self, ctx):\n        \"\"\"\n        OpenSSL 1.1.0 Contexts are preconfigured with an optimal set\n        of ECDH curves.  This method does nothing.\n\n        @param ctx: L{OpenSSL.SSL.Context}\n        \"\"\"\n\n\n    def _configureOpenSSL102(self, ctx):\n        \"\"\"\n        Have the context automatically choose elliptic curves for\n        ECDH.  Run on OpenSSL 1.0.2 and OpenSSL 1.1.0+, but only has\n        an effect on OpenSSL 1.0.2.\n\n        @param ctx: The context which .\n        @type ctx: L{OpenSSL.SSL.Context}\n        \"\"\"\n        ctxPtr = ctx._context\n        try:\n            self._openSSLlib.SSL_CTX_set_ecdh_auto(ctxPtr, True)\n        except:\n            pass\n\n\n    def _configureOpenSSL101(self, ctx):\n        \"\"\"\n        Set the default elliptic curve for ECDH on the context.  Only\n        run on OpenSSL 1.0.1.\n\n        @param ctx: The context on which to set the ECDH curve.\n        @type ctx: L{OpenSSL.SSL.Context}\n        \"\"\"\n        try:\n            ctx.set_tmp_ecdh(self._ecCurve)\n        except:\n            pass\n\n\n    def _configureOpenSSL101NoCurves(self, ctx):\n        \"\"\"\n        No elliptic curves are available on OpenSSL 1.0.1. We can't\n        set anything, so do nothing.\n\n        @param ctx: The context on which to set the ECDH curve.\n        @type ctx: L{OpenSSL.SSL.Context}\n        \"\"\"\n\n\n\nclass OpenSSLDiffieHellmanParameters(object):\n    \"\"\"\n    A representation of key generation parameters that are required for\n    Diffie-Hellman key exchange.\n    \"\"\"\n    def __init__(self, parameters):\n        self._dhFile = parameters\n\n\n    @classmethod\n    def fromFile(cls, filePath):\n        \"\"\"\n        Load parameters from a file.\n\n        Such a file can be generated using the C{openssl} command line tool as\n        following:\n\n        C{openssl dhparam -out dh_param_2048.pem -2 2048}\n\n        Please refer to U{OpenSSL's C{dhparam} documentation\n        <http://www.openssl.org/docs/apps/dhparam.html>} for further details.\n\n        @param filePath: A file containing parameters for Diffie-Hellman key\n            exchange.\n        @type filePath: L{FilePath <twisted.python.filepath.FilePath>}\n\n        @return: An instance that loads its parameters from C{filePath}.\n        @rtype: L{DiffieHellmanParameters\n            <twisted.internet.ssl.DiffieHellmanParameters>}\n        \"\"\"\n        return cls(filePath)\n\n\n\ndef _setAcceptableProtocols(context, acceptableProtocols):\n    \"\"\"\n    Called to set up the L{OpenSSL.SSL.Context} for doing NPN and/or ALPN\n    negotiation.\n\n    @param context: The context which is set up.\n    @type context: L{OpenSSL.SSL.Context}\n\n    @param acceptableProtocols: The protocols this peer is willing to speak\n        after the TLS negotiation has completed, advertised over both ALPN and\n        NPN. If this argument is specified, and no overlap can be found with\n        the other peer, the connection will fail to be established. If the\n        remote peer does not offer NPN or ALPN, the connection will be\n        established, but no protocol wil be negotiated. Protocols earlier in\n        the list are preferred over those later in the list.\n    @type acceptableProtocols: L{list} of L{bytes}\n    \"\"\"\n    def protoSelectCallback(conn, protocols):\n        \"\"\"\n        NPN client-side and ALPN server-side callback used to select\n        the next protocol. Prefers protocols found earlier in\n        C{_acceptableProtocols}.\n\n        @param conn: The context which is set up.\n        @type conn: L{OpenSSL.SSL.Connection}\n\n        @param conn: Protocols advertised by the other side.\n        @type conn: L{list} of L{bytes}\n        \"\"\"\n        overlap = set(protocols) & set(acceptableProtocols)\n\n        for p in acceptableProtocols:\n            if p in overlap:\n                return p\n        else:\n            return b''\n\n    # If we don't actually have protocols to negotiate, don't set anything up.\n    # Depending on OpenSSL version, failing some of the selection callbacks can\n    # cause the handshake to fail, which is presumably not what was intended\n    # here.\n    if not acceptableProtocols:\n        return\n\n    supported = protocolNegotiationMechanisms()\n\n    if supported & ProtocolNegotiationSupport.NPN:\n        def npnAdvertiseCallback(conn):\n            return acceptableProtocols\n\n        context.set_npn_advertise_callback(npnAdvertiseCallback)\n        context.set_npn_select_callback(protoSelectCallback)\n\n    if supported & ProtocolNegotiationSupport.ALPN:\n        context.set_alpn_select_callback(protoSelectCallback)\n        context.set_alpn_protos(acceptableProtocols)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_threadedselect.py",
    "content": "# -*- test-case-name: twisted.test.test_internet -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThreaded select reactor\n\nThe threadedselectreactor is a specialized reactor for integrating with\narbitrary foreign event loop, such as those you find in GUI toolkits.\n\nThere are three things you'll need to do to use this reactor.\n\nInstall the reactor at the beginning of your program, before importing\nthe rest of Twisted::\n\n    | from twisted.internet import _threadedselect\n    | _threadedselect.install()\n\nInterleave this reactor with your foreign event loop, at some point after\nyour event loop is initialized::\n\n    | from twisted.internet import reactor\n    | reactor.interleave(foreignEventLoopWakerFunction)\n    | self.addSystemEventTrigger('after', 'shutdown', foreignEventLoopStop)\n\nInstead of shutting down the foreign event loop directly, shut down the\nreactor::\n\n    | from twisted.internet import reactor\n    | reactor.stop()\n\nIn order for Twisted to do its work in the main thread (the thread that\ninterleave is called from), a waker function is necessary.  The waker function\nwill be called from a \"background\" thread with one argument: func.\nThe waker function's purpose is to call func() from the main thread.\nMany GUI toolkits ship with appropriate waker functions.\nSome examples of this are wxPython's wx.callAfter (may be wxCallAfter in\nolder versions of wxPython) or PyObjC's PyObjCTools.AppHelper.callAfter.\nThese would be used in place of \"foreignEventLoopWakerFunction\" in the above\nexample.\n\nThe other integration point at which the foreign event loop and this reactor\nmust integrate is shutdown.  In order to ensure clean shutdown of Twisted,\nyou must allow for Twisted to come to a complete stop before quitting the\napplication.  Typically, you will do this by setting up an after shutdown\ntrigger to stop your foreign event loop, and call reactor.stop() where you\nwould normally have initiated the shutdown procedure for the foreign event\nloop.  Shutdown functions that could be used in place of\n\"foreignEventloopStop\" would be the ExitMainLoop method of the wxApp instance\nwith wxPython, or the PyObjCTools.AppHelper.stopEventLoop function.\n\"\"\"\n\nfrom functools import partial\nfrom threading import Thread\n\ntry:\n    from queue import Queue, Empty\nexcept ImportError:\n    from Queue import Queue, Empty\nimport sys\n\nfrom zope.interface import implementer\n\nfrom twisted.internet.interfaces import IReactorFDSet\nfrom twisted.internet import posixbase\nfrom twisted.internet.posixbase import _NO_FILENO, _NO_FILEDESC\nfrom twisted.python import log, failure, threadable\n\nimport select\nfrom errno import EINTR, EBADF\n\nfrom twisted.internet.selectreactor import _select\n\n\ndef dictRemove(dct, value):\n    try:\n        del dct[value]\n    except KeyError:\n        pass\n\n\ndef raiseException(e):\n    raise e\n\n\n@implementer(IReactorFDSet)\nclass ThreadedSelectReactor(posixbase.PosixReactorBase):\n    \"\"\"A threaded select() based reactor - runs on all POSIX platforms and on\n    Win32.\n    \"\"\"\n\n    def __init__(self):\n        threadable.init(1)\n        self.reads = {}\n        self.writes = {}\n        self.toThreadQueue = Queue()\n        self.toMainThread = Queue()\n        self.workerThread = None\n        self.mainWaker = None\n        posixbase.PosixReactorBase.__init__(self)\n        self.addSystemEventTrigger('after', 'shutdown', self._mainLoopShutdown)\n\n    def wakeUp(self):\n        # we want to wake up from any thread\n        self.waker.wakeUp()\n\n    def callLater(self, *args, **kw):\n        tple = posixbase.PosixReactorBase.callLater(self, *args, **kw)\n        self.wakeUp()\n        return tple\n\n    def _sendToMain(self, msg, *args):\n        self.toMainThread.put((msg, args))\n        if self.mainWaker is not None:\n            self.mainWaker()\n\n    def _sendToThread(self, fn, *args):\n        self.toThreadQueue.put((fn, args))\n\n    def _preenDescriptorsInThread(self):\n        log.msg(\"Malformed file descriptor found.  Preening lists.\")\n        readers = self.reads.keys()\n        writers = self.writes.keys()\n        self.reads.clear()\n        self.writes.clear()\n        for selDict, selList in ((self.reads, readers), (self.writes, writers)):\n            for selectable in selList:\n                try:\n                    select.select([selectable], [selectable], [selectable], 0)\n                except:\n                    log.msg(\"bad descriptor %s\" % selectable)\n                else:\n                    selDict[selectable] = 1\n\n    def _workerInThread(self):\n        try:\n            while 1:\n                fn, args = self.toThreadQueue.get()\n                fn(*args)\n        except SystemExit:\n            pass  # Exception indicates this thread should exit\n        except:\n            f = failure.Failure()\n            self._sendToMain('Failure', f)\n\n    def _doSelectInThread(self, timeout):\n        \"\"\"Run one iteration of the I/O monitor loop.\n\n        This will run all selectables who had input or output readiness\n        waiting for them.\n        \"\"\"\n        reads = self.reads\n        writes = self.writes\n        while 1:\n            try:\n                r, w, ignored = _select(reads.keys(),\n                                        writes.keys(),\n                                        [], timeout)\n                break\n            except ValueError:\n                # Possibly a file descriptor has gone negative?\n                log.err()\n                self._preenDescriptorsInThread()\n            except TypeError:\n                # Something *totally* invalid (object w/o fileno, non-integral\n                # result) was passed\n                log.err()\n                self._preenDescriptorsInThread()\n            except (select.error, IOError) as se:\n                # select(2) encountered an error\n                if se.args[0] in (0, 2):\n                    # windows does this if it got an empty list\n                    if (not reads) and (not writes):\n                        return\n                    else:\n                        raise\n                elif se.args[0] == EINTR:\n                    return\n                elif se.args[0] == EBADF:\n                    self._preenDescriptorsInThread()\n                else:\n                    # OK, I really don't know what's going on.  Blow up.\n                    raise\n        self._sendToMain('Notify', r, w)\n\n    def _process_Notify(self, r, w):\n        reads = self.reads\n        writes = self.writes\n\n        _drdw = self._doReadOrWrite\n        _logrun = log.callWithLogger\n        for selectables, method, dct in (\n                (r, \"doRead\", reads), (w, \"doWrite\", writes)):\n            for selectable in selectables:\n                # if this was disconnected in another thread, kill it.\n                if selectable not in dct:\n                    continue\n                # This for pausing input when we're not ready for more.\n                _logrun(selectable, _drdw, selectable, method, dct)\n\n    def _process_Failure(self, f):\n        f.raiseException()\n\n    _doIterationInThread = _doSelectInThread\n\n    def ensureWorkerThread(self):\n        if self.workerThread is None or not self.workerThread.isAlive():\n            self.workerThread = Thread(target=self._workerInThread)\n            self.workerThread.start()\n\n    def doThreadIteration(self, timeout):\n        self._sendToThread(self._doIterationInThread, timeout)\n        self.ensureWorkerThread()\n        msg, args = self.toMainThread.get()\n        getattr(self, '_process_' + msg)(*args)\n\n    doIteration = doThreadIteration\n\n    def _interleave(self):\n        while self.running:\n            self.runUntilCurrent()\n            t2 = self.timeout()\n            t = self.running and t2\n            self._sendToThread(self._doIterationInThread, t)\n            yield None\n            msg, args = self.toMainThread.get_nowait()\n            getattr(self, '_process_' + msg)(*args)\n\n    def interleave(self, waker, *args, **kw):\n        \"\"\"\n        interleave(waker) interleaves this reactor with the\n        current application by moving the blocking parts of\n        the reactor (select() in this case) to a separate\n        thread.  This is typically useful for integration with\n        GUI applications which have their own event loop\n        already running.\n\n        See the module docstring for more information.\n        \"\"\"\n        self.startRunning(*args, **kw)\n        loop = self._interleave()\n\n        def mainWaker(waker=waker, loop=loop):\n            waker(partial(next, loop))\n\n        self.mainWaker = mainWaker\n        next(loop)\n        self.ensureWorkerThread()\n\n    def _mainLoopShutdown(self):\n        self.mainWaker = None\n        if self.workerThread is not None:\n            self._sendToThread(raiseException, SystemExit)\n            self.wakeUp()\n            try:\n                while 1:\n                    msg, args = self.toMainThread.get_nowait()\n            except Empty:\n                pass\n            self.workerThread.join()\n            self.workerThread = None\n        try:\n            while 1:\n                fn, args = self.toThreadQueue.get_nowait()\n                if fn is self._doIterationInThread:\n                    log.msg('Iteration is still in the thread queue!')\n                elif fn is raiseException and args[0] is SystemExit:\n                    pass\n                else:\n                    fn(*args)\n        except Empty:\n            pass\n\n    def _doReadOrWrite(self, selectable, method, dict):\n        try:\n            why = getattr(selectable, method)()\n            handfn = getattr(selectable, 'fileno', None)\n            if not handfn:\n                why = _NO_FILENO\n            elif handfn() == -1:\n                why = _NO_FILEDESC\n        except:\n            why = sys.exc_info()[1]\n            log.err()\n        if why:\n            self._disconnectSelectable(selectable, why, method == \"doRead\")\n\n    def addReader(self, reader):\n        \"\"\"Add a FileDescriptor for notification of data available to read.\n        \"\"\"\n        self._sendToThread(self.reads.__setitem__, reader, 1)\n        self.wakeUp()\n\n    def addWriter(self, writer):\n        \"\"\"Add a FileDescriptor for notification of data available to write.\n        \"\"\"\n        self._sendToThread(self.writes.__setitem__, writer, 1)\n        self.wakeUp()\n\n    def removeReader(self, reader):\n        \"\"\"Remove a Selectable for notification of data available to read.\n        \"\"\"\n        self._sendToThread(dictRemove, self.reads, reader)\n\n    def removeWriter(self, writer):\n        \"\"\"Remove a Selectable for notification of data available to write.\n        \"\"\"\n        self._sendToThread(dictRemove, self.writes, writer)\n\n    def removeAll(self):\n        return self._removeAll(self.reads, self.writes)\n\n\n    def getReaders(self):\n        return list(self.reads.keys())\n\n\n    def getWriters(self):\n        return list(self.writes.keys())\n\n\n    def stop(self):\n        \"\"\"\n        Extend the base stop implementation to also wake up the select thread so\n        that C{runUntilCurrent} notices the reactor should stop.\n        \"\"\"\n        posixbase.PosixReactorBase.stop(self)\n        self.wakeUp()\n\n\n    def run(self, installSignalHandlers=True):\n        self.startRunning(installSignalHandlers=installSignalHandlers)\n        self.mainLoop()\n\n    def mainLoop(self):\n        q = Queue()\n        self.interleave(q.put)\n        while self.running:\n            try:\n                q.get()()\n            except StopIteration:\n                break\n\n\ndef install():\n    \"\"\"Configure the twisted mainloop to be run using the select() reactor.\n    \"\"\"\n    reactor = ThreadedSelectReactor()\n    from twisted.internet.main import installReactor\n    installReactor(reactor)\n    return reactor\n\n\n__all__ = ['install']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_win32serialport.py",
    "content": "# -*- test-case-name: twisted.internet.test.test_win32serialport -*-\n\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nSerial port support for Windows.\n\nRequires PySerial and pywin32.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n# system imports\nfrom serial import PARITY_NONE\nfrom serial import STOPBITS_ONE\nfrom serial import EIGHTBITS\nfrom serial.serialutil import to_bytes\nimport win32file, win32event\n\n# twisted imports\nfrom twisted.internet import abstract\n\n# sibling imports\nfrom twisted.internet.serialport import BaseSerialPort\n\n\nclass SerialPort(BaseSerialPort, abstract.FileDescriptor):\n    \"\"\"A serial device, acting as a transport, that uses a win32 event.\"\"\"\n\n    connected = 1\n\n    def __init__(self, protocol, deviceNameOrPortNumber, reactor, \n        baudrate = 9600, bytesize = EIGHTBITS, parity = PARITY_NONE,\n        stopbits = STOPBITS_ONE, xonxoff = 0, rtscts = 0):\n        self._serial = self._serialFactory(\n            deviceNameOrPortNumber, baudrate=baudrate, bytesize=bytesize,\n            parity=parity, stopbits=stopbits, timeout=None,\n            xonxoff=xonxoff, rtscts=rtscts)\n        self.flushInput()\n        self.flushOutput()\n        self.reactor = reactor\n        self.protocol = protocol\n        self.outQueue = []\n        self.closed = 0\n        self.closedNotifies = 0\n        self.writeInProgress = 0\n\n        self.protocol = protocol\n        self._overlappedRead = win32file.OVERLAPPED()\n        self._overlappedRead.hEvent = win32event.CreateEvent(None, 1, 0, None)\n        self._overlappedWrite = win32file.OVERLAPPED()\n        self._overlappedWrite.hEvent = win32event.CreateEvent(None, 0, 0, None)\n\n        self.reactor.addEvent(self._overlappedRead.hEvent, self, 'serialReadEvent')\n        self.reactor.addEvent(self._overlappedWrite.hEvent, self, 'serialWriteEvent')\n\n        self.protocol.makeConnection(self)\n        self._finishPortSetup()\n\n\n    def _finishPortSetup(self):\n        \"\"\"\n        Finish setting up the serial port.\n\n        This is a separate method to facilitate testing.\n        \"\"\"\n        flags, comstat = self._clearCommError()\n        rc, self.read_buf = win32file.ReadFile(self._serial._port_handle,\n                                               win32file.AllocateReadBuffer(1),\n                                               self._overlappedRead)\n\n\n    def _clearCommError(self):\n        return win32file.ClearCommError(self._serial._port_handle)\n\n\n    def serialReadEvent(self):\n        #get that character we set up\n        n = win32file.GetOverlappedResult(self._serial._port_handle, self._overlappedRead, 0)\n        first = to_bytes(self.read_buf[:n])\n        #now we should get everything that is already in the buffer\n        flags, comstat = self._clearCommError()\n        if comstat.cbInQue:\n            win32event.ResetEvent(self._overlappedRead.hEvent)\n            rc, buf = win32file.ReadFile(self._serial._port_handle,\n                                         win32file.AllocateReadBuffer(comstat.cbInQue),\n                                         self._overlappedRead)\n            n = win32file.GetOverlappedResult(self._serial._port_handle, self._overlappedRead, 1)\n            #handle all the received data:\n            self.protocol.dataReceived(first + to_bytes(buf[:n]))\n        else:\n            #handle all the received data:\n            self.protocol.dataReceived(first)\n\n        #set up next one\n        win32event.ResetEvent(self._overlappedRead.hEvent)\n        rc, self.read_buf = win32file.ReadFile(self._serial._port_handle,\n                                               win32file.AllocateReadBuffer(1),\n                                               self._overlappedRead)\n\n\n    def write(self, data):\n        if data:\n            if self.writeInProgress:\n                self.outQueue.append(data)\n            else:\n                self.writeInProgress = 1\n                win32file.WriteFile(self._serial._port_handle, data, self._overlappedWrite)\n\n\n    def serialWriteEvent(self):\n        try:\n            dataToWrite = self.outQueue.pop(0)\n        except IndexError:\n            self.writeInProgress = 0\n            return\n        else:\n            win32file.WriteFile(self._serial._port_handle, dataToWrite, self._overlappedWrite)\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Called when the serial port disconnects.\n\n        Will call C{connectionLost} on the protocol that is handling the\n        serial data.\n        \"\"\"\n        self.reactor.removeEvent(self._overlappedRead.hEvent)\n        self.reactor.removeEvent(self._overlappedWrite.hEvent)\n        abstract.FileDescriptor.connectionLost(self, reason)\n        self._serial.close()\n        self.protocol.connectionLost(reason)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/_win32stdio.py",
    "content": "# -*- test-case-name: twisted.test.test_stdio -*-\n\n\"\"\"\nWindows-specific implementation of the L{twisted.internet.stdio} interface.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport win32api\nimport os\nimport msvcrt\n\nfrom zope.interface import implementer\n\nfrom twisted.internet.interfaces import (IHalfCloseableProtocol, ITransport,\n                                         IConsumer, IPushProducer, IAddress)\n\nfrom twisted.internet import _pollingfile, main\nfrom twisted.python.failure import Failure\n\n@implementer(IAddress)\nclass Win32PipeAddress(object):\n    pass\n\n\n@implementer(ITransport, IConsumer, IPushProducer)\nclass StandardIO(_pollingfile._PollingTimer):\n\n    disconnecting = False\n    disconnected = False\n\n    def __init__(self, proto, reactor=None):\n        \"\"\"\n        Start talking to standard IO with the given protocol.\n\n        Also, put it stdin/stdout/stderr into binary mode.\n        \"\"\"\n        if reactor is None:\n            from twisted.internet import reactor\n\n        for stdfd in range(0, 1, 2):\n            msvcrt.setmode(stdfd, os.O_BINARY)\n\n        _pollingfile._PollingTimer.__init__(self, reactor)\n        self.proto = proto\n\n        hstdin = win32api.GetStdHandle(win32api.STD_INPUT_HANDLE)\n        hstdout = win32api.GetStdHandle(win32api.STD_OUTPUT_HANDLE)\n\n        self.stdin = _pollingfile._PollableReadPipe(\n            hstdin, self.dataReceived, self.readConnectionLost)\n\n        self.stdout = _pollingfile._PollableWritePipe(\n            hstdout, self.writeConnectionLost)\n\n        self._addPollableResource(self.stdin)\n        self._addPollableResource(self.stdout)\n\n        self.proto.makeConnection(self)\n\n\n    def dataReceived(self, data):\n        self.proto.dataReceived(data)\n\n\n    def readConnectionLost(self):\n        if IHalfCloseableProtocol.providedBy(self.proto):\n            self.proto.readConnectionLost()\n        self.checkConnLost()\n\n\n    def writeConnectionLost(self):\n        if IHalfCloseableProtocol.providedBy(self.proto):\n            self.proto.writeConnectionLost()\n        self.checkConnLost()\n\n    connsLost = 0\n\n\n    def checkConnLost(self):\n        self.connsLost += 1\n        if self.connsLost >= 2:\n            self.disconnecting = True\n            self.disconnected = True\n            self.proto.connectionLost(Failure(main.CONNECTION_DONE))\n\n    # ITransport\n\n    def write(self, data):\n        self.stdout.write(data)\n\n\n    def writeSequence(self, seq):\n        self.stdout.write(b''.join(seq))\n\n\n    def loseConnection(self):\n        self.disconnecting = True\n        self.stdin.close()\n        self.stdout.close()\n\n\n    def getPeer(self):\n        return Win32PipeAddress()\n\n\n    def getHost(self):\n        return Win32PipeAddress()\n\n    # IConsumer\n\n    def registerProducer(self, producer, streaming):\n        return self.stdout.registerProducer(producer, streaming)\n\n\n    def unregisterProducer(self):\n        return self.stdout.unregisterProducer()\n\n    # def write() above\n\n    # IProducer\n\n    def stopProducing(self):\n        self.stdin.stopProducing()\n\n    # IPushProducer\n\n    def pauseProducing(self):\n        self.stdin.pauseProducing()\n\n\n    def resumeProducing(self):\n        self.stdin.resumeProducing()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/abstract.py",
    "content": "# -*- test-case-name: twisted.test.test_abstract -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nSupport for generic select()able objects.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom socket import AF_INET, AF_INET6, inet_pton, error\n\nfrom zope.interface import implementer\n\n# Twisted Imports\nfrom twisted.python.compat import unicode, lazyByteSlice, _PY3\nfrom twisted.python import reflect, failure\nfrom twisted.internet import interfaces, main\n\nif _PY3:\n    # Python 3.4+ can join bytes and memoryviews; using a\n    # memoryview prevents the slice from copying\n    def _concatenate(bObj, offset, bArray):\n        return b''.join([memoryview(bObj)[offset:]] + bArray)\nelse:\n    from __builtin__ import buffer\n\n    def _concatenate(bObj, offset, bArray):\n        # Avoid one extra string copy by using a buffer to limit what\n        # we include in the result.\n        return buffer(bObj, offset) + b\"\".join(bArray)\n\n\n\nclass _ConsumerMixin(object):\n    \"\"\"\n    L{IConsumer} implementations can mix this in to get C{registerProducer} and\n    C{unregisterProducer} methods which take care of keeping track of a\n    producer's state.\n\n    Subclasses must provide three attributes which L{_ConsumerMixin} will read\n    but not write:\n\n      - connected: A C{bool} which is C{True} as long as the consumer has\n        someplace to send bytes (for example, a TCP connection), and then\n        C{False} when it no longer does.\n\n      - disconnecting: A C{bool} which is C{False} until something like\n        L{ITransport.loseConnection} is called, indicating that the send buffer\n        should be flushed and the connection lost afterwards.  Afterwards,\n        C{True}.\n\n      - disconnected: A C{bool} which is C{False} until the consumer no longer\n        has a place to send bytes, then C{True}.\n\n    Subclasses must also override the C{startWriting} method.\n\n    @ivar producer: L{None} if no producer is registered, otherwise the\n        registered producer.\n\n    @ivar producerPaused: A flag indicating whether the producer is currently\n        paused.\n    @type producerPaused: L{bool}\n\n    @ivar streamingProducer: A flag indicating whether the producer was\n        registered as a streaming (ie push) producer or not (ie a pull\n        producer).  This will determine whether the consumer may ever need to\n        pause and resume it, or if it can merely call C{resumeProducing} on it\n        when buffer space is available.\n    @ivar streamingProducer: C{bool} or C{int}\n\n    \"\"\"\n    producer = None\n    producerPaused = False\n    streamingProducer = False\n\n    def startWriting(self):\n        \"\"\"\n        Override in a subclass to cause the reactor to monitor this selectable\n        for write events.  This will be called once in C{unregisterProducer} if\n        C{loseConnection} has previously been called, so that the connection can\n        actually close.\n        \"\"\"\n        raise NotImplementedError(\"%r did not implement startWriting\")\n\n\n    def registerProducer(self, producer, streaming):\n        \"\"\"\n        Register to receive data from a producer.\n\n        This sets this selectable to be a consumer for a producer.  When this\n        selectable runs out of data on a write() call, it will ask the producer\n        to resumeProducing(). When the FileDescriptor's internal data buffer is\n        filled, it will ask the producer to pauseProducing(). If the connection\n        is lost, FileDescriptor calls producer's stopProducing() method.\n\n        If streaming is true, the producer should provide the IPushProducer\n        interface. Otherwise, it is assumed that producer provides the\n        IPullProducer interface. In this case, the producer won't be asked to\n        pauseProducing(), but it has to be careful to write() data only when its\n        resumeProducing() method is called.\n        \"\"\"\n        if self.producer is not None:\n            raise RuntimeError(\n                \"Cannot register producer %s, because producer %s was never \"\n                \"unregistered.\" % (producer, self.producer))\n        if self.disconnected:\n            producer.stopProducing()\n        else:\n            self.producer = producer\n            self.streamingProducer = streaming\n            if not streaming:\n                producer.resumeProducing()\n\n\n    def unregisterProducer(self):\n        \"\"\"\n        Stop consuming data from a producer, without disconnecting.\n        \"\"\"\n        self.producer = None\n        if self.connected and self.disconnecting:\n            self.startWriting()\n\n\n\n@implementer(interfaces.ILoggingContext)\nclass _LogOwner(object):\n    \"\"\"\n    Mixin to help implement L{interfaces.ILoggingContext} for transports which\n    have a protocol, the log prefix of which should also appear in the\n    transport's log prefix.\n    \"\"\"\n\n    def _getLogPrefix(self, applicationObject):\n        \"\"\"\n        Determine the log prefix to use for messages related to\n        C{applicationObject}, which may or may not be an\n        L{interfaces.ILoggingContext} provider.\n\n        @return: A C{str} giving the log prefix to use.\n        \"\"\"\n        if interfaces.ILoggingContext.providedBy(applicationObject):\n            return applicationObject.logPrefix()\n        return applicationObject.__class__.__name__\n\n\n    def logPrefix(self):\n        \"\"\"\n        Override this method to insert custom logging behavior.  Its\n        return value will be inserted in front of every line.  It may\n        be called more times than the number of output lines.\n        \"\"\"\n        return \"-\"\n\n\n\n@implementer(\n    interfaces.IPushProducer, interfaces.IReadWriteDescriptor,\n    interfaces.IConsumer, interfaces.ITransport,\n    interfaces.IHalfCloseableDescriptor)\nclass FileDescriptor(_ConsumerMixin, _LogOwner):\n    \"\"\"\n    An object which can be operated on by select().\n\n    This is an abstract superclass of all objects which may be notified when\n    they are readable or writable; e.g. they have a file-descriptor that is\n    valid to be passed to select(2).\n    \"\"\"\n    connected = 0\n    disconnected = 0\n    disconnecting = 0\n    _writeDisconnecting = False\n    _writeDisconnected = False\n    dataBuffer = b\"\"\n    offset = 0\n\n    SEND_LIMIT = 128*1024\n\n    def __init__(self, reactor=None):\n        \"\"\"\n        @param reactor: An L{IReactorFDSet} provider which this descriptor will\n            use to get readable and writeable event notifications.  If no value\n            is given, the global reactor will be used.\n        \"\"\"\n        if not reactor:\n            from twisted.internet import reactor\n        self.reactor = reactor\n        self._tempDataBuffer = [] # will be added to dataBuffer in doWrite\n        self._tempDataLen = 0\n\n\n    def connectionLost(self, reason):\n        \"\"\"The connection was lost.\n\n        This is called when the connection on a selectable object has been\n        lost.  It will be called whether the connection was closed explicitly,\n        an exception occurred in an event handler, or the other end of the\n        connection closed it first.\n\n        Clean up state here, but make sure to call back up to FileDescriptor.\n        \"\"\"\n        self.disconnected = 1\n        self.connected = 0\n        if self.producer is not None:\n            self.producer.stopProducing()\n            self.producer = None\n        self.stopReading()\n        self.stopWriting()\n\n\n    def writeSomeData(self, data):\n        \"\"\"\n        Write as much as possible of the given data, immediately.\n\n        This is called to invoke the lower-level writing functionality, such\n        as a socket's send() method, or a file's write(); this method\n        returns an integer or an exception.  If an integer, it is the number\n        of bytes written (possibly zero); if an exception, it indicates the\n        connection was lost.\n        \"\"\"\n        raise NotImplementedError(\"%s does not implement writeSomeData\" %\n                                  reflect.qual(self.__class__))\n\n\n    def doRead(self):\n        \"\"\"\n        Called when data is available for reading.\n\n        Subclasses must override this method. The result will be interpreted\n        in the same way as a result of doWrite().\n        \"\"\"\n        raise NotImplementedError(\"%s does not implement doRead\" %\n                                  reflect.qual(self.__class__))\n\n    def doWrite(self):\n        \"\"\"\n        Called when data can be written.\n\n        @return: L{None} on success, an exception or a negative integer on\n            failure.\n\n        @see: L{twisted.internet.interfaces.IWriteDescriptor.doWrite}.\n        \"\"\"\n        if len(self.dataBuffer) - self.offset < self.SEND_LIMIT:\n            # If there is currently less than SEND_LIMIT bytes left to send\n            # in the string, extend it with the array data.\n            self.dataBuffer = _concatenate(\n                self.dataBuffer, self.offset, self._tempDataBuffer)\n            self.offset = 0\n            self._tempDataBuffer = []\n            self._tempDataLen = 0\n\n        # Send as much data as you can.\n        if self.offset:\n            l = self.writeSomeData(lazyByteSlice(self.dataBuffer, self.offset))\n        else:\n            l = self.writeSomeData(self.dataBuffer)\n\n        # There is no writeSomeData implementation in Twisted which returns\n        # < 0, but the documentation for writeSomeData used to claim negative\n        # integers meant connection lost.  Keep supporting this here,\n        # although it may be worth deprecating and removing at some point.\n        if isinstance(l, Exception) or l < 0:\n            return l\n        self.offset += l\n        # If there is nothing left to send,\n        if self.offset == len(self.dataBuffer) and not self._tempDataLen:\n            self.dataBuffer = b\"\"\n            self.offset = 0\n            # stop writing.\n            self.stopWriting()\n            # If I've got a producer who is supposed to supply me with data,\n            if self.producer is not None and ((not self.streamingProducer)\n                                              or self.producerPaused):\n                # tell them to supply some more.\n                self.producerPaused = False\n                self.producer.resumeProducing()\n            elif self.disconnecting:\n                # But if I was previously asked to let the connection die, do\n                # so.\n                return self._postLoseConnection()\n            elif self._writeDisconnecting:\n                # I was previously asked to half-close the connection.  We\n                # set _writeDisconnected before calling handler, in case the\n                # handler calls loseConnection(), which will want to check for\n                # this attribute.\n                self._writeDisconnected = True\n                result = self._closeWriteConnection()\n                return result\n        return None\n\n    def _postLoseConnection(self):\n        \"\"\"Called after a loseConnection(), when all data has been written.\n\n        Whatever this returns is then returned by doWrite.\n        \"\"\"\n        # default implementation, telling reactor we're finished\n        return main.CONNECTION_DONE\n\n    def _closeWriteConnection(self):\n        # override in subclasses\n        pass\n\n    def writeConnectionLost(self, reason):\n        # in current code should never be called\n        self.connectionLost(reason)\n\n    def readConnectionLost(self, reason):\n        # override in subclasses\n        self.connectionLost(reason)\n\n\n    def _isSendBufferFull(self):\n        \"\"\"\n        Determine whether the user-space send buffer for this transport is full\n        or not.\n\n        When the buffer contains more than C{self.bufferSize} bytes, it is\n        considered full.  This might be improved by considering the size of the\n        kernel send buffer and how much of it is free.\n\n        @return: C{True} if it is full, C{False} otherwise.\n        \"\"\"\n        return len(self.dataBuffer) + self._tempDataLen > self.bufferSize\n\n\n    def _maybePauseProducer(self):\n        \"\"\"\n        Possibly pause a producer, if there is one and the send buffer is full.\n        \"\"\"\n        # If we are responsible for pausing our producer,\n        if self.producer is not None and self.streamingProducer:\n            # and our buffer is full,\n            if self._isSendBufferFull():\n                # pause it.\n                self.producerPaused = True\n                self.producer.pauseProducing()\n\n\n    def write(self, data):\n        \"\"\"Reliably write some data.\n\n        The data is buffered until the underlying file descriptor is ready\n        for writing. If there is more than C{self.bufferSize} data in the\n        buffer and this descriptor has a registered streaming producer, its\n        C{pauseProducing()} method will be called.\n        \"\"\"\n        if isinstance(data, unicode): # no, really, I mean it\n            raise TypeError(\"Data must not be unicode\")\n        if not self.connected or self._writeDisconnected:\n            return\n        if data:\n            self._tempDataBuffer.append(data)\n            self._tempDataLen += len(data)\n            self._maybePauseProducer()\n            self.startWriting()\n\n\n    def writeSequence(self, iovec):\n        \"\"\"\n        Reliably write a sequence of data.\n\n        Currently, this is a convenience method roughly equivalent to::\n\n            for chunk in iovec:\n                fd.write(chunk)\n\n        It may have a more efficient implementation at a later time or in a\n        different reactor.\n\n        As with the C{write()} method, if a buffer size limit is reached and a\n        streaming producer is registered, it will be paused until the buffered\n        data is written to the underlying file descriptor.\n        \"\"\"\n        for i in iovec:\n            if isinstance(i, unicode): # no, really, I mean it\n                raise TypeError(\"Data must not be unicode\")\n        if not self.connected or not iovec or self._writeDisconnected:\n            return\n        self._tempDataBuffer.extend(iovec)\n        for i in iovec:\n            self._tempDataLen += len(i)\n        self._maybePauseProducer()\n        self.startWriting()\n\n\n    def loseConnection(self, _connDone=failure.Failure(main.CONNECTION_DONE)):\n        \"\"\"Close the connection at the next available opportunity.\n\n        Call this to cause this FileDescriptor to lose its connection.  It will\n        first write any data that it has buffered.\n\n        If there is data buffered yet to be written, this method will cause the\n        transport to lose its connection as soon as it's done flushing its\n        write buffer.  If you have a producer registered, the connection won't\n        be closed until the producer is finished. Therefore, make sure you\n        unregister your producer when it's finished, or the connection will\n        never close.\n        \"\"\"\n\n        if self.connected and not self.disconnecting:\n            if self._writeDisconnected:\n                # doWrite won't trigger the connection close anymore\n                self.stopReading()\n                self.stopWriting()\n                self.connectionLost(_connDone)\n            else:\n                self.stopReading()\n                self.startWriting()\n                self.disconnecting = 1\n\n    def loseWriteConnection(self):\n        self._writeDisconnecting = True\n        self.startWriting()\n\n    def stopReading(self):\n        \"\"\"Stop waiting for read availability.\n\n        Call this to remove this selectable from being notified when it is\n        ready for reading.\n        \"\"\"\n        self.reactor.removeReader(self)\n\n    def stopWriting(self):\n        \"\"\"Stop waiting for write availability.\n\n        Call this to remove this selectable from being notified when it is ready\n        for writing.\n        \"\"\"\n        self.reactor.removeWriter(self)\n\n    def startReading(self):\n        \"\"\"Start waiting for read availability.\n        \"\"\"\n        self.reactor.addReader(self)\n\n    def startWriting(self):\n        \"\"\"Start waiting for write availability.\n\n        Call this to have this FileDescriptor be notified whenever it is ready for\n        writing.\n        \"\"\"\n        self.reactor.addWriter(self)\n\n    # Producer/consumer implementation\n\n    # first, the consumer stuff.  This requires no additional work, as\n    # any object you can write to can be a consumer, really.\n\n    producer = None\n    bufferSize = 2**2**2**2\n\n    def stopConsuming(self):\n        \"\"\"Stop consuming data.\n\n        This is called when a producer has lost its connection, to tell the\n        consumer to go lose its connection (and break potential circular\n        references).\n        \"\"\"\n        self.unregisterProducer()\n        self.loseConnection()\n\n    # producer interface implementation\n\n    def resumeProducing(self):\n        if self.connected and not self.disconnecting:\n            self.startReading()\n\n    def pauseProducing(self):\n        self.stopReading()\n\n    def stopProducing(self):\n        self.loseConnection()\n\n\n    def fileno(self):\n        \"\"\"File Descriptor number for select().\n\n        This method must be overridden or assigned in subclasses to\n        indicate a valid file descriptor for the operating system.\n        \"\"\"\n        return -1\n\n\n\ndef isIPAddress(addr, family=AF_INET):\n    \"\"\"\n    Determine whether the given string represents an IP address of the given\n    family; by default, an IPv4 address.\n\n    @type addr: C{str}\n    @param addr: A string which may or may not be the decimal dotted\n        representation of an IPv4 address.\n\n    @param family: The address family to test for; one of the C{AF_*} constants\n        from the L{socket} module.  (This parameter has only been available\n        since Twisted 17.1.0; previously L{isIPAddress} could only test for IPv4\n        addresses.)\n    @type family: C{int}\n\n    @rtype: C{bool}\n    @return: C{True} if C{addr} represents an IPv4 address, C{False} otherwise.\n    \"\"\"\n    if isinstance(addr, bytes):\n        try:\n            addr = addr.decode(\"ascii\")\n        except UnicodeDecodeError:\n            return False\n    if family == AF_INET6:\n        # On some platforms, inet_ntop fails unless the scope ID is valid; this\n        # is a test for whether the given string *is* an IP address, so strip\n        # any potential scope ID before checking.\n        addr = addr.split(u\"%\", 1)[0]\n    elif family == AF_INET:\n        # On Windows, where 3.5+ implement inet_pton, \"0\" is considered a valid\n        # IPv4 address, but we want to ensure we have all 4 segments.\n        if addr.count(u\".\") != 3:\n            return False\n    else:\n        raise ValueError(\"unknown address family {!r}\".format(family))\n    try:\n        # This might be a native implementation or the one from\n        # twisted.python.compat.\n        inet_pton(family, addr)\n    except (ValueError, error):\n        return False\n    return True\n\n\n\ndef isIPv6Address(addr):\n    \"\"\"\n    Determine whether the given string represents an IPv6 address.\n\n    @param addr: A string which may or may not be the hex\n        representation of an IPv6 address.\n    @type addr: C{str}\n\n    @return: C{True} if C{addr} represents an IPv6 address, C{False}\n        otherwise.\n    @rtype: C{bool}\n    \"\"\"\n    return isIPAddress(addr, AF_INET6)\n\n\n__all__ = [\"FileDescriptor\", \"isIPAddress\", \"isIPv6Address\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/address.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAddress objects for network connections.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport attr\nimport warnings, os\n\nfrom zope.interface import implementer\nfrom twisted.internet.interfaces import IAddress\nfrom twisted.python.filepath import _asFilesystemBytes\nfrom twisted.python.filepath import _coerceToFilesystemEncoding\nfrom twisted.python.runtime import platform\nfrom twisted.python.compat import _PY3\n\n\n@implementer(IAddress)\n@attr.s(hash=True)\nclass IPv4Address(object):\n    \"\"\"\n    An L{IPv4Address} represents the address of an IPv4 socket endpoint.\n\n    @ivar type: A string describing the type of transport, either 'TCP' or\n        'UDP'.\n\n    @ivar host: A string containing a dotted-quad IPv4 address; for example,\n        \"127.0.0.1\".\n    @type host: C{str}\n\n    @ivar port: An integer representing the port number.\n    @type port: C{int}\n    \"\"\"\n    type = attr.ib(validator=attr.validators.in_([\"TCP\", \"UDP\"]))\n    host = attr.ib()\n    port = attr.ib()\n\n\n\n@implementer(IAddress)\n@attr.s(hash=True)\nclass IPv6Address(object):\n    \"\"\"\n    An L{IPv6Address} represents the address of an IPv6 socket endpoint.\n\n    @ivar type: A string describing the type of transport, either 'TCP' or\n        'UDP'.\n\n    @ivar host: A string containing a colon-separated, hexadecimal formatted\n        IPv6 address; for example, \"::1\".\n    @type host: C{str}\n\n    @ivar port: An integer representing the port number.\n    @type port: C{int}\n\n    @ivar flowInfo: the IPv6 flow label.  This can be used by QoS routers to\n        identify flows of traffic; you may generally safely ignore it.\n    @type flowInfo: L{int}\n\n    @ivar scopeID: the IPv6 scope identifier - roughly analagous to what\n        interface traffic destined for this address must be transmitted over.\n    @type scopeID: L{int} or L{str}\n    \"\"\"\n    type = attr.ib(validator=attr.validators.in_([\"TCP\", \"UDP\"]))\n    host = attr.ib()\n    port = attr.ib()\n    flowInfo = attr.ib(default=0)\n    scopeID = attr.ib(default=0)\n\n\n\n@implementer(IAddress)\nclass _ProcessAddress(object):\n    \"\"\"\n    An L{interfaces.IAddress} provider for process transports.\n    \"\"\"\n\n\n\n@attr.s(hash=True)\n@implementer(IAddress)\nclass HostnameAddress(object):\n    \"\"\"\n    A L{HostnameAddress} represents the address of a L{HostnameEndpoint}.\n\n    @ivar hostname: A hostname byte string; for example, b\"example.com\".\n    @type hostname: L{bytes}\n\n    @ivar port: An integer representing the port number.\n    @type port: L{int}\n    \"\"\"\n\n    hostname = attr.ib()\n    port = attr.ib()\n\n\n\n@attr.s(hash=False, repr=False, cmp=False)\n@implementer(IAddress)\nclass UNIXAddress(object):\n    \"\"\"\n    Object representing a UNIX socket endpoint.\n\n    @ivar name: The filename associated with this socket.\n    @type name: C{bytes}\n    \"\"\"\n\n    name = attr.ib(converter=attr.converters.optional(_asFilesystemBytes))\n\n    if getattr(os.path, 'samefile', None) is not None:\n        def __eq__(self, other):\n            \"\"\"\n            Overriding C{attrs} to ensure the os level samefile\n            check is done if the name attributes do not match.\n            \"\"\"\n            if isinstance(other, self.__class__):\n                res = self.name == other.name\n            else:\n                return False\n            if not res and self.name and other.name:\n                try:\n                    return os.path.samefile(self.name, other.name)\n                except OSError:\n                    pass\n                except (TypeError, ValueError) as e:\n                    # On Linux, abstract namespace UNIX sockets start with a\n                    # \\0, which os.path doesn't like.\n                    if not _PY3 and not platform.isLinux():\n                        raise e\n            return res\n    else:\n        def __eq__(self, other):\n            if isinstance(other, self.__class__):\n                return self.name == other.name\n            return False\n\n\n    def __ne__(self, other):\n        if isinstance(other, self.__class__):\n            return not self.__eq__(other)\n        return True\n\n\n    def __repr__(self):\n        name = self.name\n        if name:\n            name = _coerceToFilesystemEncoding('', self.name)\n        return 'UNIXAddress(%r)' % (name,)\n\n\n    def __hash__(self):\n        if self.name is None:\n            return hash((self.__class__, None))\n        try:\n            s1 = os.stat(self.name)\n            return hash((s1.st_ino, s1.st_dev))\n        except OSError:\n            return hash(self.name)\n\n\n\n# These are for buildFactory backwards compatibility due to\n# stupidity-induced inconsistency.\n\nclass _ServerFactoryIPv4Address(IPv4Address):\n    \"\"\"Backwards compatibility hack. Just like IPv4Address in practice.\"\"\"\n\n    def __eq__(self, other):\n        if isinstance(other, tuple):\n            warnings.warn(\"IPv4Address.__getitem__ is deprecated.  Use attributes instead.\",\n                          category=DeprecationWarning, stacklevel=2)\n            return (self.host, self.port) == other\n        elif isinstance(other, IPv4Address):\n            a = (self.type, self.host, self.port)\n            b = (other.type, other.host, other.port)\n            return a == b\n        return False\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/asyncioreactor.py",
    "content": "# -*- test-case-name: twisted.test.test_internet -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nasyncio-based reactor implementation.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport errno\n\nfrom zope.interface import implementer\n\nfrom twisted.logger import Logger\nfrom twisted.internet.base import DelayedCall\nfrom twisted.internet.posixbase import (PosixReactorBase, _NO_FILEDESC,\n                                        _ContinuousPolling)\nfrom twisted.python.log import callWithLogger\nfrom twisted.internet.interfaces import IReactorFDSet\n\ntry:\n    from asyncio import get_event_loop\nexcept ImportError:\n    raise ImportError(\"Requires asyncio.\")\n\n# As per ImportError above, this module is never imported on python 2, but\n# pyflakes still runs on python 2, so let's tell it where the errors come from.\nfrom builtins import PermissionError, BrokenPipeError\n\n\nclass _DCHandle(object):\n    \"\"\"\n    Wraps ephemeral L{asyncio.Handle} instances.  Callbacks can close\n    over this and use it as a mutable reference to asyncio C{Handles}.\n\n    @ivar handle: The current L{asyncio.Handle}\n    \"\"\"\n    def __init__(self, handle):\n        self.handle = handle\n\n\n    def cancel(self):\n        \"\"\"\n        Cancel the inner L{asyncio.Handle}.\n        \"\"\"\n        self.handle.cancel()\n\n\n\n@implementer(IReactorFDSet)\nclass AsyncioSelectorReactor(PosixReactorBase):\n    \"\"\"\n    Reactor running on top of L{asyncio.SelectorEventLoop}.\n    \"\"\"\n    _asyncClosed = False\n    _log = Logger()\n\n    def __init__(self, eventloop=None):\n\n        if eventloop is None:\n            eventloop = get_event_loop()\n\n        self._asyncioEventloop = eventloop\n        self._writers = {}\n        self._readers = {}\n        self._delayedCalls = set()\n        self._continuousPolling = _ContinuousPolling(self)\n        super().__init__()\n\n\n    def _unregisterFDInAsyncio(self, fd):\n        \"\"\"\n        Compensate for a bug in asyncio where it will not unregister a FD that\n        it cannot handle in the epoll loop. It touches internal asyncio code.\n\n        A description of the bug by markrwilliams:\n\n        The C{add_writer} method of asyncio event loops isn't atomic because\n        all the Selector classes in the selector module internally record a\n        file object before passing it to the platform's selector\n        implementation. If the platform's selector decides the file object\n        isn't acceptable, the resulting exception doesn't cause the Selector to\n        un-track the file object.\n\n        The failing/hanging stdio test goes through the following sequence of\n        events (roughly):\n\n        * The first C{connection.write(intToByte(value))} call hits the asyncio\n        reactor's C{addWriter} method.\n\n        * C{addWriter} calls the asyncio loop's C{add_writer} method, which\n        happens to live on C{_BaseSelectorEventLoop}.\n\n        * The asyncio loop's C{add_writer} method checks if the file object has\n        been registered before via the selector's C{get_key} method.\n\n        * It hasn't, so the KeyError block runs and calls the selector's\n        register method\n\n        * Code examples that follow use EpollSelector, but the code flow holds\n        true for any other selector implementation. The selector's register\n        method first calls through to the next register method in the MRO\n\n        * That next method is always C{_BaseSelectorImpl.register} which\n        creates a C{SelectorKey} instance for the file object, stores it under\n        the file object's file descriptor, and then returns it.\n\n        * Control returns to the concrete selector implementation, which asks\n        the operating system to track the file descriptor using the right API.\n\n        * The operating system refuses! An exception is raised that, in this\n        case, the asyncio reactor handles by creating a C{_ContinuousPolling}\n        object to watch the file descriptor.\n\n        * The second C{connection.write(intToByte(value))} call hits the\n        asyncio reactor's C{addWriter} method, which hits the C{add_writer}\n        method. But the loop's selector's get_key method now returns a\n        C{SelectorKey}! Now the asyncio reactor's C{addWriter} method thinks\n        the asyncio loop will watch the file descriptor, even though it won't.\n        \"\"\"\n        try:\n            self._asyncioEventloop._selector.unregister(fd)\n        except:\n            pass\n\n\n    def _readOrWrite(self, selectable, read):\n        method = selectable.doRead if read else selectable.doWrite\n\n        if selectable.fileno() == -1:\n            self._disconnectSelectable(selectable, _NO_FILEDESC, read)\n            return\n\n        try:\n            why = method()\n        except Exception as e:\n            why = e\n            self._log.failure(None)\n        if why:\n            self._disconnectSelectable(selectable, why, read)\n\n\n    def addReader(self, reader):\n        if reader in self._readers.keys() or \\\n           reader in self._continuousPolling._readers:\n            return\n\n        fd = reader.fileno()\n        try:\n            self._asyncioEventloop.add_reader(fd, callWithLogger, reader,\n                                              self._readOrWrite, reader,\n                                              True)\n            self._readers[reader] = fd\n        except IOError as e:\n            self._unregisterFDInAsyncio(fd)\n            if e.errno == errno.EPERM:\n                # epoll(7) doesn't support certain file descriptors,\n                # e.g. filesystem files, so for those we just poll\n                # continuously:\n                self._continuousPolling.addReader(reader)\n            else:\n                raise\n\n\n    def addWriter(self, writer):\n        if writer in self._writers.keys() or \\\n           writer in self._continuousPolling._writers:\n            return\n\n        fd = writer.fileno()\n        try:\n            self._asyncioEventloop.add_writer(fd, callWithLogger, writer,\n                                              self._readOrWrite, writer,\n                                              False)\n            self._writers[writer] = fd\n        except PermissionError:\n            self._unregisterFDInAsyncio(fd)\n            # epoll(7) doesn't support certain file descriptors,\n            # e.g. filesystem files, so for those we just poll\n            # continuously:\n            self._continuousPolling.addWriter(writer)\n        except BrokenPipeError:\n            # The kqueuereactor will raise this if there is a broken pipe\n            self._unregisterFDInAsyncio(fd)\n        except:\n            self._unregisterFDInAsyncio(fd)\n            raise\n\n\n    def removeReader(self, reader):\n\n        # First, see if they're trying to remove a reader that we don't have.\n        if not (reader in self._readers.keys() \\\n                or self._continuousPolling.isReading(reader)):\n            # We don't have it, so just return OK.\n            return\n\n        # If it was a cont. polling reader, check there first.\n        if self._continuousPolling.isReading(reader):\n            self._continuousPolling.removeReader(reader)\n            return\n\n        fd = reader.fileno()\n        if fd == -1:\n            # If the FD is -1, we want to know what its original FD was, to\n            # remove it.\n            fd = self._readers.pop(reader)\n        else:\n            self._readers.pop(reader)\n\n        self._asyncioEventloop.remove_reader(fd)\n\n\n    def removeWriter(self, writer):\n\n        # First, see if they're trying to remove a writer that we don't have.\n        if not (writer in self._writers.keys() \\\n                or self._continuousPolling.isWriting(writer)):\n            # We don't have it, so just return OK.\n            return\n\n        # If it was a cont. polling writer, check there first.\n        if self._continuousPolling.isWriting(writer):\n            self._continuousPolling.removeWriter(writer)\n            return\n\n        fd = writer.fileno()\n\n        if fd == -1:\n            # If the FD is -1, we want to know what its original FD was, to\n            # remove it.\n            fd = self._writers.pop(writer)\n        else:\n            self._writers.pop(writer)\n\n        self._asyncioEventloop.remove_writer(fd)\n\n\n    def removeAll(self):\n        return (self._removeAll(self._readers.keys(), self._writers.keys()) +\n                self._continuousPolling.removeAll())\n\n\n    def getReaders(self):\n        return (list(self._readers.keys()) +\n                self._continuousPolling.getReaders())\n\n\n    def getWriters(self):\n        return (list(self._writers.keys()) +\n                self._continuousPolling.getWriters())\n\n\n    def getDelayedCalls(self):\n        return list(self._delayedCalls)\n\n\n    def iterate(self, timeout):\n        self._asyncioEventloop.call_later(timeout + 0.01,\n                                          self._asyncioEventloop.stop)\n        self._asyncioEventloop.run_forever()\n\n\n    def run(self, installSignalHandlers=True):\n        self.startRunning(installSignalHandlers=installSignalHandlers)\n        self._asyncioEventloop.run_forever()\n        if self._justStopped:\n            self._justStopped = False\n\n\n    def stop(self):\n        super().stop()\n        self.callLater(0, self.fireSystemEvent, \"shutdown\")\n\n\n    def crash(self):\n        super().crash()\n        self._asyncioEventloop.stop()\n\n\n    def seconds(self):\n        return self._asyncioEventloop.time()\n\n\n    def callLater(self, seconds, f, *args, **kwargs):\n        def run():\n            dc.called = True\n            self._delayedCalls.remove(dc)\n            f(*args, **kwargs)\n        handle = self._asyncioEventloop.call_later(seconds, run)\n        dchandle = _DCHandle(handle)\n\n        def cancel(dc):\n            self._delayedCalls.remove(dc)\n            dchandle.cancel()\n\n        def reset(dc):\n            dchandle.handle = self._asyncioEventloop.call_at(dc.time, run)\n\n        dc = DelayedCall(self.seconds() + seconds, run, (), {},\n                         cancel, reset, seconds=self.seconds)\n        self._delayedCalls.add(dc)\n        return dc\n\n\n    def callFromThread(self, f, *args, **kwargs):\n        g = lambda: self.callLater(0, f, *args, **kwargs)\n        self._asyncioEventloop.call_soon_threadsafe(g)\n\n\n\ndef install(eventloop=None):\n    \"\"\"\n    Install an asyncio-based reactor.\n\n    @param eventloop: The asyncio eventloop to wrap. If default, the global one\n        is selected.\n    \"\"\"\n    reactor = AsyncioSelectorReactor(eventloop)\n    from twisted.internet.main import installReactor\n    installReactor(reactor)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/base.py",
    "content": "# -*- test-case-name: twisted.test.test_internet,twisted.internet.test.test_core -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nVery basic functionality for a Reactor implementation.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport socket # needed only for sync-dns\nfrom zope.interface import implementer, classImplements\n\nimport sys\nimport warnings\nfrom heapq import heappush, heappop, heapify\n\nimport traceback\n\nfrom twisted.internet.interfaces import (\n    IReactorCore, IReactorTime, IReactorThreads, IResolverSimple,\n    IReactorPluggableResolver, IReactorPluggableNameResolver, IConnector,\n    IDelayedCall, _ISupportsExitSignalCapturing\n)\n\nfrom twisted.internet import fdesc, main, error, abstract, defer, threads\nfrom twisted.internet._resolver import (\n    GAIResolver as _GAIResolver,\n    ComplexResolverSimplifier as _ComplexResolverSimplifier,\n    SimpleResolverComplexifier as _SimpleResolverComplexifier,\n)\nfrom twisted.python import log, failure, reflect\nfrom twisted.python.compat import unicode, iteritems\nfrom twisted.python.runtime import seconds as runtimeSeconds, platform\nfrom twisted.internet.defer import Deferred, DeferredList\nfrom twisted.python._oldstyle import _oldStyle\n\n# This import is for side-effects!  Even if you don't see any code using it\n# in this module, don't delete it.\nfrom twisted.python import threadable\n\n\n@implementer(IDelayedCall)\n@_oldStyle\nclass DelayedCall:\n\n    # enable .debug to record creator call stack, and it will be logged if\n    # an exception occurs while the function is being run\n    debug = False\n    _repr = None\n\n    def __init__(self, time, func, args, kw, cancel, reset,\n                 seconds=runtimeSeconds):\n        \"\"\"\n        @param time: Seconds from the epoch at which to call C{func}.\n        @param func: The callable to call.\n        @param args: The positional arguments to pass to the callable.\n        @param kw: The keyword arguments to pass to the callable.\n        @param cancel: A callable which will be called with this\n            DelayedCall before cancellation.\n        @param reset: A callable which will be called with this\n            DelayedCall after changing this DelayedCall's scheduled\n            execution time. The callable should adjust any necessary\n            scheduling details to ensure this DelayedCall is invoked\n            at the new appropriate time.\n        @param seconds: If provided, a no-argument callable which will be\n            used to determine the current time any time that information is\n            needed.\n        \"\"\"\n        self.time, self.func, self.args, self.kw = time, func, args, kw\n        self.resetter = reset\n        self.canceller = cancel\n        self.seconds = seconds\n        self.cancelled = self.called = 0\n        self.delayed_time = 0\n        if self.debug:\n            self.creator = traceback.format_stack()[:-2]\n\n    def getTime(self):\n        \"\"\"Return the time at which this call will fire\n\n        @rtype: C{float}\n        @return: The number of seconds after the epoch at which this call is\n        scheduled to be made.\n        \"\"\"\n        return self.time + self.delayed_time\n\n    def cancel(self):\n        \"\"\"Unschedule this call\n\n        @raise AlreadyCancelled: Raised if this call has already been\n        unscheduled.\n\n        @raise AlreadyCalled: Raised if this call has already been made.\n        \"\"\"\n        if self.cancelled:\n            raise error.AlreadyCancelled\n        elif self.called:\n            raise error.AlreadyCalled\n        else:\n            self.canceller(self)\n            self.cancelled = 1\n            if self.debug:\n                self._repr = repr(self)\n            del self.func, self.args, self.kw\n\n    def reset(self, secondsFromNow):\n        \"\"\"Reschedule this call for a different time\n\n        @type secondsFromNow: C{float}\n        @param secondsFromNow: The number of seconds from the time of the\n        C{reset} call at which this call will be scheduled.\n\n        @raise AlreadyCancelled: Raised if this call has been cancelled.\n        @raise AlreadyCalled: Raised if this call has already been made.\n        \"\"\"\n        if self.cancelled:\n            raise error.AlreadyCancelled\n        elif self.called:\n            raise error.AlreadyCalled\n        else:\n            newTime = self.seconds() + secondsFromNow\n            if newTime < self.time:\n                self.delayed_time = 0\n                self.time = newTime\n                self.resetter(self)\n            else:\n                self.delayed_time = newTime - self.time\n\n    def delay(self, secondsLater):\n        \"\"\"Reschedule this call for a later time\n\n        @type secondsLater: C{float}\n        @param secondsLater: The number of seconds after the originally\n        scheduled time for which to reschedule this call.\n\n        @raise AlreadyCancelled: Raised if this call has been cancelled.\n        @raise AlreadyCalled: Raised if this call has already been made.\n        \"\"\"\n        if self.cancelled:\n            raise error.AlreadyCancelled\n        elif self.called:\n            raise error.AlreadyCalled\n        else:\n            self.delayed_time += secondsLater\n            if self.delayed_time < 0:\n                self.activate_delay()\n                self.resetter(self)\n\n    def activate_delay(self):\n        self.time += self.delayed_time\n        self.delayed_time = 0\n\n    def active(self):\n        \"\"\"Determine whether this call is still pending\n\n        @rtype: C{bool}\n        @return: True if this call has not yet been made or cancelled,\n        False otherwise.\n        \"\"\"\n        return not (self.cancelled or self.called)\n\n\n    def __le__(self, other):\n        \"\"\"\n        Implement C{<=} operator between two L{DelayedCall} instances.\n\n        Comparison is based on the C{time} attribute (unadjusted by the\n        delayed time).\n        \"\"\"\n        return self.time <= other.time\n\n\n    def __lt__(self, other):\n        \"\"\"\n        Implement C{<} operator between two L{DelayedCall} instances.\n\n        Comparison is based on the C{time} attribute (unadjusted by the\n        delayed time).\n        \"\"\"\n        return self.time < other.time\n\n\n    def __repr__(self):\n        \"\"\"\n        Implement C{repr()} for L{DelayedCall} instances.\n\n        @rtype: C{str}\n        @returns: String containing details of the L{DelayedCall}.\n        \"\"\"\n        if self._repr is not None:\n            return self._repr\n        if hasattr(self, 'func'):\n            # This code should be replaced by a utility function in reflect;\n            # see ticket #6066:\n            if hasattr(self.func, '__qualname__'):\n                func = self.func.__qualname__\n            elif hasattr(self.func, '__name__'):\n                func = self.func.func_name\n                if hasattr(self.func, 'im_class'):\n                    func = self.func.im_class.__name__ + '.' + func\n            else:\n                func = reflect.safe_repr(self.func)\n        else:\n            func = None\n\n        now = self.seconds()\n        L = [\"<DelayedCall 0x%x [%ss] called=%s cancelled=%s\" % (\n                id(self), self.time - now, self.called,\n                self.cancelled)]\n        if func is not None:\n            L.extend((\" \", func, \"(\"))\n            if self.args:\n                L.append(\", \".join([reflect.safe_repr(e) for e in self.args]))\n                if self.kw:\n                    L.append(\", \")\n            if self.kw:\n                L.append(\", \".join(['%s=%s' % (k, reflect.safe_repr(v)) for (k, v) in self.kw.items()]))\n            L.append(\")\")\n\n        if self.debug:\n            L.append(\"\\n\\ntraceback at creation: \\n\\n%s\" % ('    '.join(self.creator)))\n        L.append('>')\n\n        return \"\".join(L)\n\n\n\n@implementer(IResolverSimple)\nclass ThreadedResolver(object):\n    \"\"\"\n    L{ThreadedResolver} uses a reactor, a threadpool, and\n    L{socket.gethostbyname} to perform name lookups without blocking the\n    reactor thread.  It also supports timeouts indepedently from whatever\n    timeout logic L{socket.gethostbyname} might have.\n\n    @ivar reactor: The reactor the threadpool of which will be used to call\n        L{socket.gethostbyname} and the I/O thread of which the result will be\n        delivered.\n    \"\"\"\n\n    def __init__(self, reactor):\n        self.reactor = reactor\n        self._runningQueries = {}\n\n\n    def _fail(self, name, err):\n        err = error.DNSLookupError(\"address %r not found: %s\" % (name, err))\n        return failure.Failure(err)\n\n\n    def _cleanup(self, name, lookupDeferred):\n        userDeferred, cancelCall = self._runningQueries[lookupDeferred]\n        del self._runningQueries[lookupDeferred]\n        userDeferred.errback(self._fail(name, \"timeout error\"))\n\n\n    def _checkTimeout(self, result, name, lookupDeferred):\n        try:\n            userDeferred, cancelCall = self._runningQueries[lookupDeferred]\n        except KeyError:\n            pass\n        else:\n            del self._runningQueries[lookupDeferred]\n            cancelCall.cancel()\n\n            if isinstance(result, failure.Failure):\n                userDeferred.errback(self._fail(name, result.getErrorMessage()))\n            else:\n                userDeferred.callback(result)\n\n\n    def getHostByName(self, name, timeout = (1, 3, 11, 45)):\n        \"\"\"\n        See L{twisted.internet.interfaces.IResolverSimple.getHostByName}.\n\n        Note that the elements of C{timeout} are summed and the result is used\n        as a timeout for the lookup.  Any intermediate timeout or retry logic\n        is left up to the platform via L{socket.gethostbyname}.\n        \"\"\"\n        if timeout:\n            timeoutDelay = sum(timeout)\n        else:\n            timeoutDelay = 60\n        userDeferred = defer.Deferred()\n        lookupDeferred = threads.deferToThreadPool(\n            self.reactor, self.reactor.getThreadPool(),\n            socket.gethostbyname, name)\n        cancelCall = self.reactor.callLater(\n            timeoutDelay, self._cleanup, name, lookupDeferred)\n        self._runningQueries[lookupDeferred] = (userDeferred, cancelCall)\n        lookupDeferred.addBoth(self._checkTimeout, name, lookupDeferred)\n        return userDeferred\n\n\n\n@implementer(IResolverSimple)\n@_oldStyle\nclass BlockingResolver:\n\n    def getHostByName(self, name, timeout = (1, 3, 11, 45)):\n        try:\n            address = socket.gethostbyname(name)\n        except socket.error:\n            msg = \"address %r not found\" % (name,)\n            err = error.DNSLookupError(msg)\n            return defer.fail(err)\n        else:\n            return defer.succeed(address)\n\n\nclass _ThreePhaseEvent(object):\n    \"\"\"\n    Collection of callables (with arguments) which can be invoked as a group in\n    a particular order.\n\n    This provides the underlying implementation for the reactor's system event\n    triggers.  An instance of this class tracks triggers for all phases of a\n    single type of event.\n\n    @ivar before: A list of the before-phase triggers containing three-tuples\n        of a callable, a tuple of positional arguments, and a dict of keyword\n        arguments\n\n    @ivar finishedBefore: A list of the before-phase triggers which have\n        already been executed.  This is only populated in the C{'BEFORE'} state.\n\n    @ivar during: A list of the during-phase triggers containing three-tuples\n        of a callable, a tuple of positional arguments, and a dict of keyword\n        arguments\n\n    @ivar after: A list of the after-phase triggers containing three-tuples\n        of a callable, a tuple of positional arguments, and a dict of keyword\n        arguments\n\n    @ivar state: A string indicating what is currently going on with this\n        object.  One of C{'BASE'} (for when nothing in particular is happening;\n        this is the initial value), C{'BEFORE'} (when the before-phase triggers\n        are in the process of being executed).\n    \"\"\"\n    def __init__(self):\n        self.before = []\n        self.during = []\n        self.after = []\n        self.state = 'BASE'\n\n\n    def addTrigger(self, phase, callable, *args, **kwargs):\n        \"\"\"\n        Add a trigger to the indicate phase.\n\n        @param phase: One of C{'before'}, C{'during'}, or C{'after'}.\n\n        @param callable: An object to be called when this event is triggered.\n        @param *args: Positional arguments to pass to C{callable}.\n        @param **kwargs: Keyword arguments to pass to C{callable}.\n\n        @return: An opaque handle which may be passed to L{removeTrigger} to\n            reverse the effects of calling this method.\n        \"\"\"\n        if phase not in ('before', 'during', 'after'):\n            raise KeyError(\"invalid phase\")\n        getattr(self, phase).append((callable, args, kwargs))\n        return phase, callable, args, kwargs\n\n\n    def removeTrigger(self, handle):\n        \"\"\"\n        Remove a previously added trigger callable.\n\n        @param handle: An object previously returned by L{addTrigger}.  The\n            trigger added by that call will be removed.\n\n        @raise ValueError: If the trigger associated with C{handle} has already\n            been removed or if C{handle} is not a valid handle.\n        \"\"\"\n        return getattr(self, 'removeTrigger_' + self.state)(handle)\n\n\n    def removeTrigger_BASE(self, handle):\n        \"\"\"\n        Just try to remove the trigger.\n\n        @see: removeTrigger\n        \"\"\"\n        try:\n            phase, callable, args, kwargs = handle\n        except (TypeError, ValueError):\n            raise ValueError(\"invalid trigger handle\")\n        else:\n            if phase not in ('before', 'during', 'after'):\n                raise KeyError(\"invalid phase\")\n            getattr(self, phase).remove((callable, args, kwargs))\n\n\n    def removeTrigger_BEFORE(self, handle):\n        \"\"\"\n        Remove the trigger if it has yet to be executed, otherwise emit a\n        warning that in the future an exception will be raised when removing an\n        already-executed trigger.\n\n        @see: removeTrigger\n        \"\"\"\n        phase, callable, args, kwargs = handle\n        if phase != 'before':\n            return self.removeTrigger_BASE(handle)\n        if (callable, args, kwargs) in self.finishedBefore:\n            warnings.warn(\n                \"Removing already-fired system event triggers will raise an \"\n                \"exception in a future version of Twisted.\",\n                category=DeprecationWarning,\n                stacklevel=3)\n        else:\n            self.removeTrigger_BASE(handle)\n\n\n    def fireEvent(self):\n        \"\"\"\n        Call the triggers added to this event.\n        \"\"\"\n        self.state = 'BEFORE'\n        self.finishedBefore = []\n        beforeResults = []\n        while self.before:\n            callable, args, kwargs = self.before.pop(0)\n            self.finishedBefore.append((callable, args, kwargs))\n            try:\n                result = callable(*args, **kwargs)\n            except:\n                log.err()\n            else:\n                if isinstance(result, Deferred):\n                    beforeResults.append(result)\n        DeferredList(beforeResults).addCallback(self._continueFiring)\n\n\n    def _continueFiring(self, ignored):\n        \"\"\"\n        Call the during and after phase triggers for this event.\n        \"\"\"\n        self.state = 'BASE'\n        self.finishedBefore = []\n        for phase in self.during, self.after:\n            while phase:\n                callable, args, kwargs = phase.pop(0)\n                try:\n                    callable(*args, **kwargs)\n                except:\n                    log.err()\n\n\n\n@implementer(IReactorPluggableNameResolver, IReactorPluggableResolver)\nclass PluggableResolverMixin(object):\n    \"\"\"\n    A mixin which implements the pluggable resolver reactor interfaces.\n\n    @ivar resolver: The installed L{IResolverSimple}.\n    @ivar _nameResolver: The installed L{IHostnameResolver}.\n    \"\"\"\n    resolver = BlockingResolver()\n    _nameResolver = _SimpleResolverComplexifier(resolver)\n\n    # IReactorPluggableResolver\n    def installResolver(self, resolver):\n        \"\"\"\n        See L{IReactorPluggableResolver}.\n\n        @param resolver: see L{IReactorPluggableResolver}.\n\n        @return: see L{IReactorPluggableResolver}.\n        \"\"\"\n        assert IResolverSimple.providedBy(resolver)\n        oldResolver = self.resolver\n        self.resolver = resolver\n        self._nameResolver = _SimpleResolverComplexifier(resolver)\n        return oldResolver\n\n\n    # IReactorPluggableNameResolver\n    def installNameResolver(self, resolver):\n        \"\"\"\n        See L{IReactorPluggableNameResolver}.\n\n        @param resolver: See L{IReactorPluggableNameResolver}.\n\n        @return: see L{IReactorPluggableNameResolver}.\n        \"\"\"\n        previousNameResolver = self._nameResolver\n        self._nameResolver = resolver\n        self.resolver = _ComplexResolverSimplifier(resolver)\n        return previousNameResolver\n\n\n    @property\n    def nameResolver(self):\n        \"\"\"\n        Implementation of read-only\n        L{IReactorPluggableNameResolver.nameResolver}.\n        \"\"\"\n        return self._nameResolver\n\n\n\n@implementer(IReactorCore, IReactorTime, _ISupportsExitSignalCapturing)\nclass ReactorBase(PluggableResolverMixin):\n    \"\"\"\n    Default base class for Reactors.\n\n    @type _stopped: C{bool}\n    @ivar _stopped: A flag which is true between paired calls to C{reactor.run}\n        and C{reactor.stop}.  This should be replaced with an explicit state\n        machine.\n\n    @type _justStopped: C{bool}\n    @ivar _justStopped: A flag which is true between the time C{reactor.stop}\n        is called and the time the shutdown system event is fired.  This is\n        used to determine whether that event should be fired after each\n        iteration through the mainloop.  This should be replaced with an\n        explicit state machine.\n\n    @type _started: C{bool}\n    @ivar _started: A flag which is true from the time C{reactor.run} is called\n        until the time C{reactor.run} returns.  This is used to prevent calls\n        to C{reactor.run} on a running reactor.  This should be replaced with\n        an explicit state machine.\n\n    @ivar running: See L{IReactorCore.running}\n\n    @ivar _registerAsIOThread: A flag controlling whether the reactor will\n        register the thread it is running in as the I/O thread when it starts.\n        If C{True}, registration will be done, otherwise it will not be.\n\n    @ivar _exitSignal: See L{_ISupportsExitSignalCapturing._exitSignal}\n    \"\"\"\n\n    _registerAsIOThread = True\n\n    _stopped = True\n    installed = False\n    usingThreads = False\n    _exitSignal = None\n\n    __name__ = \"twisted.internet.reactor\"\n\n    def __init__(self):\n        super(ReactorBase, self).__init__()\n        self.threadCallQueue = []\n        self._eventTriggers = {}\n        self._pendingTimedCalls = []\n        self._newTimedCalls = []\n        self._cancellations = 0\n        self.running = False\n        self._started = False\n        self._justStopped = False\n        self._startedBefore = False\n        # reactor internal readers, e.g. the waker.\n        self._internalReaders = set()\n        self.waker = None\n\n        # Arrange for the running attribute to change to True at the right time\n        # and let a subclass possibly do other things at that time (eg install\n        # signal handlers).\n        self.addSystemEventTrigger(\n            'during', 'startup', self._reallyStartRunning)\n        self.addSystemEventTrigger('during', 'shutdown', self.crash)\n        self.addSystemEventTrigger('during', 'shutdown', self.disconnectAll)\n\n        if platform.supportsThreads():\n            self._initThreads()\n        self.installWaker()\n\n    # override in subclasses\n\n    _lock = None\n\n    def installWaker(self):\n        raise NotImplementedError(\n            reflect.qual(self.__class__) + \" did not implement installWaker\")\n\n\n    def wakeUp(self):\n        \"\"\"\n        Wake up the event loop.\n        \"\"\"\n        if self.waker:\n            self.waker.wakeUp()\n        # if the waker isn't installed, the reactor isn't running, and\n        # therefore doesn't need to be woken up\n\n    def doIteration(self, delay):\n        \"\"\"\n        Do one iteration over the readers and writers which have been added.\n        \"\"\"\n        raise NotImplementedError(\n            reflect.qual(self.__class__) + \" did not implement doIteration\")\n\n    def addReader(self, reader):\n        raise NotImplementedError(\n            reflect.qual(self.__class__) + \" did not implement addReader\")\n\n    def addWriter(self, writer):\n        raise NotImplementedError(\n            reflect.qual(self.__class__) + \" did not implement addWriter\")\n\n    def removeReader(self, reader):\n        raise NotImplementedError(\n            reflect.qual(self.__class__) + \" did not implement removeReader\")\n\n    def removeWriter(self, writer):\n        raise NotImplementedError(\n            reflect.qual(self.__class__) + \" did not implement removeWriter\")\n\n    def removeAll(self):\n        raise NotImplementedError(\n            reflect.qual(self.__class__) + \" did not implement removeAll\")\n\n\n    def getReaders(self):\n        raise NotImplementedError(\n            reflect.qual(self.__class__) + \" did not implement getReaders\")\n\n\n    def getWriters(self):\n        raise NotImplementedError(\n            reflect.qual(self.__class__) + \" did not implement getWriters\")\n\n\n    # IReactorCore\n    def resolve(self, name, timeout=(1, 3, 11, 45)):\n        \"\"\"Return a Deferred that will resolve a hostname.\n        \"\"\"\n        if not name:\n            # XXX - This is *less than* '::', and will screw up IPv6 servers\n            return defer.succeed('0.0.0.0')\n        if abstract.isIPAddress(name):\n            return defer.succeed(name)\n        return self.resolver.getHostByName(name, timeout)\n\n\n    def stop(self):\n        \"\"\"\n        See twisted.internet.interfaces.IReactorCore.stop.\n        \"\"\"\n        if self._stopped:\n            raise error.ReactorNotRunning(\n                \"Can't stop reactor that isn't running.\")\n        self._stopped = True\n        self._justStopped = True\n        self._startedBefore = True\n\n\n    def crash(self):\n        \"\"\"\n        See twisted.internet.interfaces.IReactorCore.crash.\n\n        Reset reactor state tracking attributes and re-initialize certain\n        state-transition helpers which were set up in C{__init__} but later\n        destroyed (through use).\n        \"\"\"\n        self._started = False\n        self.running = False\n        self.addSystemEventTrigger(\n            'during', 'startup', self._reallyStartRunning)\n\n    def sigInt(self, *args):\n        \"\"\"\n        Handle a SIGINT interrupt.\n\n        @param args: See handler specification in L{signal.signal}\n        \"\"\"\n        log.msg(\"Received SIGINT, shutting down.\")\n        self.callFromThread(self.stop)\n        self._exitSignal = args[0]\n\n\n    def sigBreak(self, *args):\n        \"\"\"\n        Handle a SIGBREAK interrupt.\n\n        @param args: See handler specification in L{signal.signal}\n        \"\"\"\n        log.msg(\"Received SIGBREAK, shutting down.\")\n        self.callFromThread(self.stop)\n        self._exitSignal = args[0]\n\n\n    def sigTerm(self, *args):\n        \"\"\"\n        Handle a SIGTERM interrupt.\n\n        @param args: See handler specification in L{signal.signal}\n        \"\"\"\n        log.msg(\"Received SIGTERM, shutting down.\")\n        self.callFromThread(self.stop)\n        self._exitSignal = args[0]\n\n\n    def disconnectAll(self):\n        \"\"\"Disconnect every reader, and writer in the system.\n        \"\"\"\n        selectables = self.removeAll()\n        for reader in selectables:\n            log.callWithLogger(reader,\n                               reader.connectionLost,\n                               failure.Failure(main.CONNECTION_LOST))\n\n\n    def iterate(self, delay=0):\n        \"\"\"See twisted.internet.interfaces.IReactorCore.iterate.\n        \"\"\"\n        self.runUntilCurrent()\n        self.doIteration(delay)\n\n\n    def fireSystemEvent(self, eventType):\n        \"\"\"See twisted.internet.interfaces.IReactorCore.fireSystemEvent.\n        \"\"\"\n        event = self._eventTriggers.get(eventType)\n        if event is not None:\n            event.fireEvent()\n\n\n    def addSystemEventTrigger(self, _phase, _eventType, _f, *args, **kw):\n        \"\"\"See twisted.internet.interfaces.IReactorCore.addSystemEventTrigger.\n        \"\"\"\n        assert callable(_f), \"%s is not callable\" % _f\n        if _eventType not in self._eventTriggers:\n            self._eventTriggers[_eventType] = _ThreePhaseEvent()\n        return (_eventType, self._eventTriggers[_eventType].addTrigger(\n            _phase, _f, *args, **kw))\n\n\n    def removeSystemEventTrigger(self, triggerID):\n        \"\"\"See twisted.internet.interfaces.IReactorCore.removeSystemEventTrigger.\n        \"\"\"\n        eventType, handle = triggerID\n        self._eventTriggers[eventType].removeTrigger(handle)\n\n\n    def callWhenRunning(self, _callable, *args, **kw):\n        \"\"\"See twisted.internet.interfaces.IReactorCore.callWhenRunning.\n        \"\"\"\n        if self.running:\n            _callable(*args, **kw)\n        else:\n            return self.addSystemEventTrigger('after', 'startup',\n                                              _callable, *args, **kw)\n\n    def startRunning(self):\n        \"\"\"\n        Method called when reactor starts: do some initialization and fire\n        startup events.\n\n        Don't call this directly, call reactor.run() instead: it should take\n        care of calling this.\n\n        This method is somewhat misnamed.  The reactor will not necessarily be\n        in the running state by the time this method returns.  The only\n        guarantee is that it will be on its way to the running state.\n        \"\"\"\n        if self._started:\n            raise error.ReactorAlreadyRunning()\n        if self._startedBefore:\n            raise error.ReactorNotRestartable()\n        self._started = True\n        self._stopped = False\n        if self._registerAsIOThread:\n            threadable.registerAsIOThread()\n        self.fireSystemEvent('startup')\n\n\n    def _reallyStartRunning(self):\n        \"\"\"\n        Method called to transition to the running state.  This should happen\n        in the I{during startup} event trigger phase.\n        \"\"\"\n        self.running = True\n\n    # IReactorTime\n\n    seconds = staticmethod(runtimeSeconds)\n\n    def callLater(self, _seconds, _f, *args, **kw):\n        \"\"\"See twisted.internet.interfaces.IReactorTime.callLater.\n        \"\"\"\n        assert callable(_f), \"%s is not callable\" % _f\n        assert _seconds >= 0, \\\n               \"%s is not greater than or equal to 0 seconds\" % (_seconds,)\n        tple = DelayedCall(self.seconds() + _seconds, _f, args, kw,\n                           self._cancelCallLater,\n                           self._moveCallLaterSooner,\n                           seconds=self.seconds)\n        self._newTimedCalls.append(tple)\n        return tple\n\n    def _moveCallLaterSooner(self, tple):\n        # Linear time find: slow.\n        heap = self._pendingTimedCalls\n        try:\n            pos = heap.index(tple)\n\n            # Move elt up the heap until it rests at the right place.\n            elt = heap[pos]\n            while pos != 0:\n                parent = (pos-1) // 2\n                if heap[parent] <= elt:\n                    break\n                # move parent down\n                heap[pos] = heap[parent]\n                pos = parent\n            heap[pos] = elt\n        except ValueError:\n            # element was not found in heap - oh well...\n            pass\n\n    def _cancelCallLater(self, tple):\n        self._cancellations+=1\n\n\n    def getDelayedCalls(self):\n        \"\"\"\n        Return all the outstanding delayed calls in the system.\n        They are returned in no particular order.\n        This method is not efficient -- it is really only meant for\n        test cases.\n\n        @return: A list of outstanding delayed calls.\n        @type: L{list} of L{DelayedCall}\n        \"\"\"\n        return [x for x in (self._pendingTimedCalls + self._newTimedCalls) if not x.cancelled]\n\n\n    def _insertNewDelayedCalls(self):\n        for call in self._newTimedCalls:\n            if call.cancelled:\n                self._cancellations-=1\n            else:\n                call.activate_delay()\n                heappush(self._pendingTimedCalls, call)\n        self._newTimedCalls = []\n\n\n    def timeout(self):\n        \"\"\"\n        Determine the longest time the reactor may sleep (waiting on I/O\n        notification, perhaps) before it must wake up to service a time-related\n        event.\n\n        @return: The maximum number of seconds the reactor may sleep.\n        @rtype: L{float}\n        \"\"\"\n        # insert new delayed calls to make sure to include them in timeout value\n        self._insertNewDelayedCalls()\n\n        if not self._pendingTimedCalls:\n            return None\n\n        delay = self._pendingTimedCalls[0].time - self.seconds()\n\n        # Pick a somewhat arbitrary maximum possible value for the timeout.\n        # This value is 2 ** 31 / 1000, which is the number of seconds which can\n        # be represented as an integer number of milliseconds in a signed 32 bit\n        # integer.  This particular limit is imposed by the epoll_wait(3)\n        # interface which accepts a timeout as a C \"int\" type and treats it as\n        # representing a number of milliseconds.\n        longest = 2147483\n\n        # Don't let the delay be in the past (negative) or exceed a plausible\n        # maximum (platform-imposed) interval.\n        return max(0, min(longest, delay))\n\n\n    def runUntilCurrent(self):\n        \"\"\"\n        Run all pending timed calls.\n        \"\"\"\n        if self.threadCallQueue:\n            # Keep track of how many calls we actually make, as we're\n            # making them, in case another call is added to the queue\n            # while we're in this loop.\n            count = 0\n            total = len(self.threadCallQueue)\n            for (f, a, kw) in self.threadCallQueue:\n                try:\n                    f(*a, **kw)\n                except:\n                    log.err()\n                count += 1\n                if count == total:\n                    break\n            del self.threadCallQueue[:count]\n            if self.threadCallQueue:\n                self.wakeUp()\n\n        # insert new delayed calls now\n        self._insertNewDelayedCalls()\n\n        now = self.seconds()\n        while self._pendingTimedCalls and (self._pendingTimedCalls[0].time <= now):\n            call = heappop(self._pendingTimedCalls)\n            if call.cancelled:\n                self._cancellations-=1\n                continue\n\n            if call.delayed_time > 0:\n                call.activate_delay()\n                heappush(self._pendingTimedCalls, call)\n                continue\n\n            try:\n                call.called = 1\n                call.func(*call.args, **call.kw)\n            except:\n                log.deferr()\n                if hasattr(call, \"creator\"):\n                    e = \"\\n\"\n                    e += \" C: previous exception occurred in \" + \\\n                         \"a DelayedCall created here:\\n\"\n                    e += \" C:\"\n                    e += \"\".join(call.creator).rstrip().replace(\"\\n\",\"\\n C:\")\n                    e += \"\\n\"\n                    log.msg(e)\n\n\n        if (self._cancellations > 50 and\n             self._cancellations > len(self._pendingTimedCalls) >> 1):\n            self._cancellations = 0\n            self._pendingTimedCalls = [x for x in self._pendingTimedCalls\n                                       if not x.cancelled]\n            heapify(self._pendingTimedCalls)\n\n        if self._justStopped:\n            self._justStopped = False\n            self.fireSystemEvent(\"shutdown\")\n\n    # IReactorProcess\n\n    def _checkProcessArgs(self, args, env):\n        \"\"\"\n        Check for valid arguments and environment to spawnProcess.\n\n        @return: A two element tuple giving values to use when creating the\n        process.  The first element of the tuple is a C{list} of C{bytes}\n        giving the values for argv of the child process.  The second element\n        of the tuple is either L{None} if C{env} was L{None} or a C{dict}\n        mapping C{bytes} environment keys to C{bytes} environment values.\n        \"\"\"\n        # Any unicode string which Python would successfully implicitly\n        # encode to a byte string would have worked before these explicit\n        # checks were added.  Anything which would have failed with a\n        # UnicodeEncodeError during that implicit encoding step would have\n        # raised an exception in the child process and that would have been\n        # a pain in the butt to debug.\n        #\n        # So, we will explicitly attempt the same encoding which Python\n        # would implicitly do later.  If it fails, we will report an error\n        # without ever spawning a child process.  If it succeeds, we'll save\n        # the result so that Python doesn't need to do it implicitly later.\n        #\n        # -exarkun\n\n        defaultEncoding = sys.getfilesystemencoding()\n\n        # Common check function\n        def argChecker(arg):\n            \"\"\"\n            Return either L{bytes} or L{None}.  If the given value is not\n            allowable for some reason, L{None} is returned.  Otherwise, a\n            possibly different object which should be used in place of arg is\n            returned.  This forces unicode encoding to happen now, rather than\n            implicitly later.\n            \"\"\"\n            if isinstance(arg, unicode):\n                try:\n                    arg = arg.encode(defaultEncoding)\n                except UnicodeEncodeError:\n                    return None\n            if isinstance(arg, bytes) and b'\\0' not in arg:\n                return arg\n\n            return None\n\n        # Make a few tests to check input validity\n        if not isinstance(args, (tuple, list)):\n            raise TypeError(\"Arguments must be a tuple or list\")\n\n        outputArgs = []\n        for arg in args:\n            arg = argChecker(arg)\n            if arg is None:\n                raise TypeError(\"Arguments contain a non-string value\")\n            else:\n                outputArgs.append(arg)\n\n        outputEnv = None\n        if env is not None:\n            outputEnv = {}\n            for key, val in iteritems(env):\n                key = argChecker(key)\n                if key is None:\n                    raise TypeError(\"Environment contains a non-string key\")\n                val = argChecker(val)\n                if val is None:\n                    raise TypeError(\"Environment contains a non-string value\")\n                outputEnv[key] = val\n        return outputArgs, outputEnv\n\n    # IReactorThreads\n    if platform.supportsThreads():\n        threadpool = None\n        # ID of the trigger starting the threadpool\n        _threadpoolStartupID = None\n        # ID of the trigger stopping the threadpool\n        threadpoolShutdownID = None\n\n        def _initThreads(self):\n            self.installNameResolver(_GAIResolver(self, self.getThreadPool))\n            self.usingThreads = True\n\n\n        def callFromThread(self, f, *args, **kw):\n            \"\"\"\n            See\n            L{twisted.internet.interfaces.IReactorFromThreads.callFromThread}.\n            \"\"\"\n            assert callable(f), \"%s is not callable\" % (f,)\n            # lists are thread-safe in CPython, but not in Jython\n            # this is probably a bug in Jython, but until fixed this code\n            # won't work in Jython.\n            self.threadCallQueue.append((f, args, kw))\n            self.wakeUp()\n\n        def _initThreadPool(self):\n            \"\"\"\n            Create the threadpool accessible with callFromThread.\n            \"\"\"\n            from twisted.python import threadpool\n            self.threadpool = threadpool.ThreadPool(\n                0, 10, 'twisted.internet.reactor')\n            self._threadpoolStartupID = self.callWhenRunning(\n                self.threadpool.start)\n            self.threadpoolShutdownID = self.addSystemEventTrigger(\n                'during', 'shutdown', self._stopThreadPool)\n\n        def _uninstallHandler(self):\n            pass\n\n        def _stopThreadPool(self):\n            \"\"\"\n            Stop the reactor threadpool.  This method is only valid if there\n            is currently a threadpool (created by L{_initThreadPool}).  It\n            is not intended to be called directly; instead, it will be\n            called by a shutdown trigger created in L{_initThreadPool}.\n            \"\"\"\n            triggers = [self._threadpoolStartupID, self.threadpoolShutdownID]\n            for trigger in filter(None, triggers):\n                try:\n                    self.removeSystemEventTrigger(trigger)\n                except ValueError:\n                    pass\n            self._threadpoolStartupID = None\n            self.threadpoolShutdownID = None\n            self.threadpool.stop()\n            self.threadpool = None\n\n\n        def getThreadPool(self):\n            \"\"\"\n            See L{twisted.internet.interfaces.IReactorThreads.getThreadPool}.\n            \"\"\"\n            if self.threadpool is None:\n                self._initThreadPool()\n            return self.threadpool\n\n\n        def callInThread(self, _callable, *args, **kwargs):\n            \"\"\"\n            See L{twisted.internet.interfaces.IReactorInThreads.callInThread}.\n            \"\"\"\n            self.getThreadPool().callInThread(_callable, *args, **kwargs)\n\n\n        def suggestThreadPoolSize(self, size):\n            \"\"\"\n            See L{twisted.internet.interfaces.IReactorThreads.suggestThreadPoolSize}.\n            \"\"\"\n            self.getThreadPool().adjustPoolsize(maxthreads=size)\n    else:\n        # This is for signal handlers.\n        def callFromThread(self, f, *args, **kw):\n            assert callable(f), \"%s is not callable\" % (f,)\n            # See comment in the other callFromThread implementation.\n            self.threadCallQueue.append((f, args, kw))\n\nif platform.supportsThreads():\n    classImplements(ReactorBase, IReactorThreads)\n\n\n@implementer(IConnector)\n@_oldStyle\nclass BaseConnector:\n    \"\"\"Basic implementation of connector.\n\n    State can be: \"connecting\", \"connected\", \"disconnected\"\n    \"\"\"\n    timeoutID = None\n    factoryStarted = 0\n\n    def __init__(self, factory, timeout, reactor):\n        self.state = \"disconnected\"\n        self.reactor = reactor\n        self.factory = factory\n        self.timeout = timeout\n\n    def disconnect(self):\n        \"\"\"Disconnect whatever our state is.\"\"\"\n        if self.state == 'connecting':\n            self.stopConnecting()\n        elif self.state == 'connected':\n            self.transport.loseConnection()\n\n    def connect(self):\n        \"\"\"Start connection to remote server.\"\"\"\n        if self.state != \"disconnected\":\n            raise RuntimeError(\"can't connect in this state\")\n\n        self.state = \"connecting\"\n        if not self.factoryStarted:\n            self.factory.doStart()\n            self.factoryStarted = 1\n        self.transport = transport = self._makeTransport()\n        if self.timeout is not None:\n            self.timeoutID = self.reactor.callLater(self.timeout, transport.failIfNotConnected, error.TimeoutError())\n        self.factory.startedConnecting(self)\n\n    def stopConnecting(self):\n        \"\"\"Stop attempting to connect.\"\"\"\n        if self.state != \"connecting\":\n            raise error.NotConnectingError(\"we're not trying to connect\")\n\n        self.state = \"disconnected\"\n        self.transport.failIfNotConnected(error.UserError())\n        del self.transport\n\n    def cancelTimeout(self):\n        if self.timeoutID is not None:\n            try:\n                self.timeoutID.cancel()\n            except ValueError:\n                pass\n            del self.timeoutID\n\n    def buildProtocol(self, addr):\n        self.state = \"connected\"\n        self.cancelTimeout()\n        return self.factory.buildProtocol(addr)\n\n    def connectionFailed(self, reason):\n        self.cancelTimeout()\n        self.transport = None\n        self.state = \"disconnected\"\n        self.factory.clientConnectionFailed(self, reason)\n        if self.state == \"disconnected\":\n            # factory hasn't called our connect() method\n            self.factory.doStop()\n            self.factoryStarted = 0\n\n    def connectionLost(self, reason):\n        self.state = \"disconnected\"\n        self.factory.clientConnectionLost(self, reason)\n        if self.state == \"disconnected\":\n            # factory hasn't called our connect() method\n            self.factory.doStop()\n            self.factoryStarted = 0\n\n    def getDestination(self):\n        raise NotImplementedError(\n            reflect.qual(self.__class__) + \" did not implement \"\n            \"getDestination\")\n\n    def __repr__(self):\n        return \"<%s instance at 0x%x %s %s>\" % (\n            reflect.qual(self.__class__), id(self), self.state,\n            self.getDestination())\n\n\n\nclass BasePort(abstract.FileDescriptor):\n    \"\"\"Basic implementation of a ListeningPort.\n\n    Note: This does not actually implement IListeningPort.\n    \"\"\"\n\n    addressFamily = None\n    socketType = None\n\n    def createInternetSocket(self):\n        s = socket.socket(self.addressFamily, self.socketType)\n        s.setblocking(0)\n        fdesc._setCloseOnExec(s.fileno())\n        return s\n\n\n    def doWrite(self):\n        \"\"\"Raises a RuntimeError\"\"\"\n        raise RuntimeError(\n            \"doWrite called on a %s\" % reflect.qual(self.__class__))\n\n\n\nclass _SignalReactorMixin(object):\n    \"\"\"\n    Private mixin to manage signals: it installs signal handlers at start time,\n    and define run method.\n\n    It can only be used mixed in with L{ReactorBase}, and has to be defined\n    first in the inheritance (so that method resolution order finds\n    startRunning first).\n\n    @type _installSignalHandlers: C{bool}\n    @ivar _installSignalHandlers: A flag which indicates whether any signal\n        handlers will be installed during startup.  This includes handlers for\n        SIGCHLD to monitor child processes, and SIGINT, SIGTERM, and SIGBREAK\n        to stop the reactor.\n    \"\"\"\n\n    _installSignalHandlers = False\n\n    def _handleSignals(self):\n        \"\"\"\n        Install the signal handlers for the Twisted event loop.\n        \"\"\"\n        try:\n            import signal\n        except ImportError:\n            log.msg(\"Warning: signal module unavailable -- \"\n                    \"not installing signal handlers.\")\n            return\n\n        if signal.getsignal(signal.SIGINT) == signal.default_int_handler:\n            # only handle if there isn't already a handler, e.g. for Pdb.\n            signal.signal(signal.SIGINT, self.sigInt)\n        signal.signal(signal.SIGTERM, self.sigTerm)\n\n        # Catch Ctrl-Break in windows\n        if hasattr(signal, \"SIGBREAK\"):\n            signal.signal(signal.SIGBREAK, self.sigBreak)\n\n\n    def startRunning(self, installSignalHandlers=True):\n        \"\"\"\n        Extend the base implementation in order to remember whether signal\n        handlers should be installed later.\n\n        @type installSignalHandlers: C{bool}\n        @param installSignalHandlers: A flag which, if set, indicates that\n            handlers for a number of (implementation-defined) signals should be\n            installed during startup.\n        \"\"\"\n        self._installSignalHandlers = installSignalHandlers\n        ReactorBase.startRunning(self)\n\n\n    def _reallyStartRunning(self):\n        \"\"\"\n        Extend the base implementation by also installing signal handlers, if\n        C{self._installSignalHandlers} is true.\n        \"\"\"\n        ReactorBase._reallyStartRunning(self)\n        if self._installSignalHandlers:\n            # Make sure this happens before after-startup events, since the\n            # expectation of after-startup is that the reactor is fully\n            # initialized.  Don't do it right away for historical reasons\n            # (perhaps some before-startup triggers don't want there to be a\n            # custom SIGCHLD handler so that they can run child processes with\n            # some blocking api).\n            self._handleSignals()\n\n\n    def run(self, installSignalHandlers=True):\n        self.startRunning(installSignalHandlers=installSignalHandlers)\n        self.mainLoop()\n\n\n    def mainLoop(self):\n        while self._started:\n            try:\n                while self._started:\n                    # Advance simulation time in delayed event\n                    # processors.\n                    self.runUntilCurrent()\n                    t2 = self.timeout()\n                    t = self.running and t2\n                    self.doIteration(t)\n            except:\n                log.msg(\"Unexpected error in main loop.\")\n                log.err()\n            else:\n                log.msg('Main loop terminated.')\n\n\n\n__all__ = []\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/cfreactor.py",
    "content": "# -*- test-case-name: twisted.internet.test.test_core -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nA reactor for integrating with U{CFRunLoop<http://bit.ly/cfrunloop>}, the\nCoreFoundation main loop used by macOS.\n\nThis is useful for integrating Twisted with U{PyObjC<http://pyobjc.sf.net/>}\napplications.\n\"\"\"\n\n__all__ = [\n    'install',\n    'CFReactor'\n]\n\nimport sys\n\nfrom zope.interface import implementer\n\nfrom twisted.internet.interfaces import IReactorFDSet\nfrom twisted.internet.posixbase import PosixReactorBase, _Waker\nfrom twisted.internet.posixbase import _NO_FILEDESC\n\nfrom twisted.python import log\n\nfrom CoreFoundation import (\n    CFRunLoopAddSource, CFRunLoopRemoveSource, CFRunLoopGetMain, CFRunLoopRun,\n    CFRunLoopStop, CFRunLoopTimerCreate, CFRunLoopAddTimer,\n    CFRunLoopTimerInvalidate, kCFAllocatorDefault, kCFRunLoopCommonModes,\n    CFAbsoluteTimeGetCurrent)\n\nfrom CFNetwork import (\n    CFSocketCreateWithNative, CFSocketSetSocketFlags, CFSocketEnableCallBacks,\n    CFSocketCreateRunLoopSource, CFSocketDisableCallBacks, CFSocketInvalidate,\n    kCFSocketWriteCallBack, kCFSocketReadCallBack, kCFSocketConnectCallBack,\n    kCFSocketAutomaticallyReenableReadCallBack,\n    kCFSocketAutomaticallyReenableWriteCallBack)\n\n\n_READ = 0\n_WRITE = 1\n_preserveSOError = 1 << 6\n\n\nclass _WakerPlus(_Waker):\n    \"\"\"\n    The normal Twisted waker will simply wake up the main loop, which causes an\n    iteration to run, which in turn causes L{ReactorBase.runUntilCurrent}\n    to get invoked.\n\n    L{CFReactor} has a slightly different model of iteration, though: rather\n    than have each iteration process the thread queue, then timed calls, then\n    file descriptors, each callback is run as it is dispatched by the CFRunLoop\n    observer which triggered it.\n\n    So this waker needs to not only unblock the loop, but also make sure the\n    work gets done; so, it reschedules the invocation of C{runUntilCurrent} to\n    be immediate (0 seconds from now) even if there is no timed call work to\n    do.\n    \"\"\"\n\n    def doRead(self):\n        \"\"\"\n        Wake up the loop and force C{runUntilCurrent} to run immediately in the\n        next timed iteration.\n        \"\"\"\n        result = _Waker.doRead(self)\n        self.reactor._scheduleSimulate(True)\n        return result\n\n\n\n@implementer(IReactorFDSet)\nclass CFReactor(PosixReactorBase):\n    \"\"\"\n    The CoreFoundation reactor.\n\n    You probably want to use this via the L{install} API.\n\n    @ivar _fdmap: a dictionary, mapping an integer (a file descriptor) to a\n        4-tuple of:\n\n            - source: a C{CFRunLoopSource}; the source associated with this\n              socket.\n            - socket: a C{CFSocket} wrapping the file descriptor.\n            - descriptor: an L{IReadDescriptor} and/or L{IWriteDescriptor}\n              provider.\n            - read-write: a 2-C{list} of booleans: respectively, whether this\n              descriptor is currently registered for reading or registered for\n              writing.\n\n    @ivar _idmap: a dictionary, mapping the id() of an L{IReadDescriptor} or\n        L{IWriteDescriptor} to a C{fd} in L{_fdmap}.  Implemented in this\n        manner so that we don't have to rely (even more) on the hashability of\n        L{IReadDescriptor} providers, and we know that they won't be collected\n        since these are kept in sync with C{_fdmap}.  Necessary because the\n        .fileno() of a file descriptor may change at will, so we need to be\n        able to look up what its file descriptor I{used} to be, so that we can\n        look it up in C{_fdmap}\n\n    @ivar _cfrunloop: the C{CFRunLoop} pyobjc object wrapped\n        by this reactor.\n\n    @ivar _inCFLoop: Is C{CFRunLoopRun} currently running?\n\n    @type _inCFLoop: L{bool}\n\n    @ivar _currentSimulator: if a CFTimer is currently scheduled with the CF\n        run loop to run Twisted callLater calls, this is a reference to it.\n        Otherwise, it is L{None}\n    \"\"\"\n    def __init__(self, runLoop=None, runner=None):\n        self._fdmap = {}\n        self._idmap = {}\n        if runner is None:\n            runner = CFRunLoopRun\n        self._runner = runner\n\n        if runLoop is None:\n            runLoop = CFRunLoopGetMain()\n        self._cfrunloop = runLoop\n        PosixReactorBase.__init__(self)\n\n\n    def installWaker(self):\n        \"\"\"\n        Override C{installWaker} in order to use L{_WakerPlus}; otherwise this\n        should be exactly the same as the parent implementation.\n        \"\"\"\n        if not self.waker:\n            self.waker = _WakerPlus(self)\n            self._internalReaders.add(self.waker)\n            self.addReader(self.waker)\n\n\n    def _socketCallback(self, cfSocket, callbackType,\n                        ignoredAddress, ignoredData, context):\n        \"\"\"\n        The socket callback issued by CFRunLoop.  This will issue C{doRead} or\n        C{doWrite} calls to the L{IReadDescriptor} and L{IWriteDescriptor}\n        registered with the file descriptor that we are being notified of.\n\n        @param cfSocket: The C{CFSocket} which has got some activity.\n\n        @param callbackType: The type of activity that we are being notified\n            of.  Either C{kCFSocketReadCallBack} or C{kCFSocketWriteCallBack}.\n\n        @param ignoredAddress: Unused, because this is not used for either of\n            the callback types we register for.\n\n        @param ignoredData: Unused, because this is not used for either of the\n            callback types we register for.\n\n        @param context: The data associated with this callback by\n            C{CFSocketCreateWithNative} (in C{CFReactor._watchFD}).  A 2-tuple\n            of C{(int, CFRunLoopSource)}.\n        \"\"\"\n        (fd, smugglesrc) = context\n        if fd not in self._fdmap:\n            # Spurious notifications seem to be generated sometimes if you\n            # CFSocketDisableCallBacks in the middle of an event.  I don't know\n            # about this FD, any more, so let's get rid of it.\n            CFRunLoopRemoveSource(\n                self._cfrunloop, smugglesrc, kCFRunLoopCommonModes\n            )\n            return\n\n        src, skt, readWriteDescriptor, rw = self._fdmap[fd]\n\n        def _drdw():\n            why = None\n            isRead = False\n\n            try:\n                if readWriteDescriptor.fileno() == -1:\n                    why = _NO_FILEDESC\n                else:\n                    isRead = callbackType == kCFSocketReadCallBack\n                    # CFSocket seems to deliver duplicate read/write\n                    # notifications sometimes, especially a duplicate\n                    # writability notification when first registering the\n                    # socket.  This bears further investigation, since I may\n                    # have been mis-interpreting the behavior I was seeing.\n                    # (Running the full Twisted test suite, while thorough, is\n                    # not always entirely clear.) Until this has been more\n                    # thoroughly investigated , we consult our own\n                    # reading/writing state flags to determine whether we\n                    # should actually attempt a doRead/doWrite first.  -glyph\n                    if isRead:\n                        if rw[_READ]:\n                            why = readWriteDescriptor.doRead()\n                    else:\n                        if rw[_WRITE]:\n                            why = readWriteDescriptor.doWrite()\n            except:\n                why = sys.exc_info()[1]\n                log.err()\n            if why:\n                self._disconnectSelectable(readWriteDescriptor, why, isRead)\n\n        log.callWithLogger(readWriteDescriptor, _drdw)\n\n\n    def _watchFD(self, fd, descr, flag):\n        \"\"\"\n        Register a file descriptor with the C{CFRunLoop}, or modify its state\n        so that it's listening for both notifications (read and write) rather\n        than just one; used to implement C{addReader} and C{addWriter}.\n\n        @param fd: The file descriptor.\n\n        @type fd: L{int}\n\n        @param descr: the L{IReadDescriptor} or L{IWriteDescriptor}\n\n        @param flag: the flag to register for callbacks on, either\n            C{kCFSocketReadCallBack} or C{kCFSocketWriteCallBack}\n        \"\"\"\n        if fd == -1:\n            raise RuntimeError(\"Invalid file descriptor.\")\n        if fd in self._fdmap:\n            src, cfs, gotdescr, rw = self._fdmap[fd]\n            # do I need to verify that it's the same descr?\n        else:\n            ctx = []\n            ctx.append(fd)\n            cfs = CFSocketCreateWithNative(\n                kCFAllocatorDefault, fd,\n                kCFSocketReadCallBack | kCFSocketWriteCallBack |\n                kCFSocketConnectCallBack,\n                self._socketCallback, ctx\n            )\n            CFSocketSetSocketFlags(\n                cfs,\n                kCFSocketAutomaticallyReenableReadCallBack |\n                kCFSocketAutomaticallyReenableWriteCallBack |\n\n                # This extra flag is to ensure that CF doesn't (destructively,\n                # because destructively is the only way to do it) retrieve\n                # SO_ERROR and thereby break twisted.internet.tcp.BaseClient,\n                # which needs SO_ERROR to tell it whether or not it needs to\n                # call connect_ex a second time.\n                _preserveSOError\n            )\n            src = CFSocketCreateRunLoopSource(kCFAllocatorDefault, cfs, 0)\n            ctx.append(src)\n            CFRunLoopAddSource(self._cfrunloop, src, kCFRunLoopCommonModes)\n            CFSocketDisableCallBacks(\n                cfs,\n                kCFSocketReadCallBack | kCFSocketWriteCallBack |\n                kCFSocketConnectCallBack\n            )\n            rw = [False, False]\n            self._idmap[id(descr)] = fd\n            self._fdmap[fd] = src, cfs, descr, rw\n        rw[self._flag2idx(flag)] = True\n        CFSocketEnableCallBacks(cfs, flag)\n\n\n    def _flag2idx(self, flag):\n        \"\"\"\n        Convert a C{kCFSocket...} constant to an index into the read/write\n        state list (C{_READ} or C{_WRITE}) (the 4th element of the value of\n        C{self._fdmap}).\n\n        @param flag: C{kCFSocketReadCallBack} or C{kCFSocketWriteCallBack}\n\n        @return: C{_READ} or C{_WRITE}\n        \"\"\"\n        return {kCFSocketReadCallBack: _READ,\n                kCFSocketWriteCallBack: _WRITE}[flag]\n\n\n    def _unwatchFD(self, fd, descr, flag):\n        \"\"\"\n        Unregister a file descriptor with the C{CFRunLoop}, or modify its state\n        so that it's listening for only one notification (read or write) as\n        opposed to both; used to implement C{removeReader} and C{removeWriter}.\n\n        @param fd: a file descriptor\n\n        @type fd: C{int}\n\n        @param descr: an L{IReadDescriptor} or L{IWriteDescriptor}\n\n        @param flag: C{kCFSocketWriteCallBack} C{kCFSocketReadCallBack}\n        \"\"\"\n        if id(descr) not in self._idmap:\n            return\n        if fd == -1:\n            # need to deal with it in this case, I think.\n            realfd = self._idmap[id(descr)]\n        else:\n            realfd = fd\n        src, cfs, descr, rw = self._fdmap[realfd]\n        CFSocketDisableCallBacks(cfs, flag)\n        rw[self._flag2idx(flag)] = False\n        if not rw[_READ] and not rw[_WRITE]:\n            del self._idmap[id(descr)]\n            del self._fdmap[realfd]\n            CFRunLoopRemoveSource(self._cfrunloop, src, kCFRunLoopCommonModes)\n            CFSocketInvalidate(cfs)\n\n\n    def addReader(self, reader):\n        \"\"\"\n        Implement L{IReactorFDSet.addReader}.\n        \"\"\"\n        self._watchFD(reader.fileno(), reader, kCFSocketReadCallBack)\n\n\n    def addWriter(self, writer):\n        \"\"\"\n        Implement L{IReactorFDSet.addWriter}.\n        \"\"\"\n        self._watchFD(writer.fileno(), writer, kCFSocketWriteCallBack)\n\n\n    def removeReader(self, reader):\n        \"\"\"\n        Implement L{IReactorFDSet.removeReader}.\n        \"\"\"\n        self._unwatchFD(reader.fileno(), reader, kCFSocketReadCallBack)\n\n\n    def removeWriter(self, writer):\n        \"\"\"\n        Implement L{IReactorFDSet.removeWriter}.\n        \"\"\"\n        self._unwatchFD(writer.fileno(), writer, kCFSocketWriteCallBack)\n\n\n    def removeAll(self):\n        \"\"\"\n        Implement L{IReactorFDSet.removeAll}.\n        \"\"\"\n        allDesc = set([descr for src, cfs, descr, rw in self._fdmap.values()])\n        allDesc -= set(self._internalReaders)\n        for desc in allDesc:\n            self.removeReader(desc)\n            self.removeWriter(desc)\n        return list(allDesc)\n\n\n    def getReaders(self):\n        \"\"\"\n        Implement L{IReactorFDSet.getReaders}.\n        \"\"\"\n        return [descr for src, cfs, descr, rw in self._fdmap.values()\n                if rw[_READ]]\n\n\n    def getWriters(self):\n        \"\"\"\n        Implement L{IReactorFDSet.getWriters}.\n        \"\"\"\n        return [descr for src, cfs, descr, rw in self._fdmap.values()\n                if rw[_WRITE]]\n\n\n    def _moveCallLaterSooner(self, tple):\n        \"\"\"\n        Override L{PosixReactorBase}'s implementation of L{IDelayedCall.reset}\n        so that it will immediately reschedule.  Normally\n        C{_moveCallLaterSooner} depends on the fact that C{runUntilCurrent} is\n        always run before the mainloop goes back to sleep, so this forces it to\n        immediately recompute how long the loop needs to stay asleep.\n        \"\"\"\n        result = PosixReactorBase._moveCallLaterSooner(self, tple)\n        self._scheduleSimulate()\n        return result\n\n\n    _inCFLoop = False\n\n    def mainLoop(self):\n        \"\"\"\n        Run the runner (C{CFRunLoopRun} or something that calls it), which runs\n        the run loop until C{crash()} is called.\n        \"\"\"\n        self._inCFLoop = True\n        try:\n            self._runner()\n        finally:\n            self._inCFLoop = False\n\n\n    _currentSimulator = None\n\n    def _scheduleSimulate(self, force=False):\n        \"\"\"\n        Schedule a call to C{self.runUntilCurrent}.  This will cancel the\n        currently scheduled call if it is already scheduled.\n\n        @param force: Even if there are no timed calls, make sure that\n            C{runUntilCurrent} runs immediately (in a 0-seconds-from-now\n            C{CFRunLoopTimer}).  This is necessary for calls which need to\n            trigger behavior of C{runUntilCurrent} other than running timed\n            calls, such as draining the thread call queue or calling C{crash()}\n            when the appropriate flags are set.\n\n        @type force: C{bool}\n        \"\"\"\n        if self._currentSimulator is not None:\n            CFRunLoopTimerInvalidate(self._currentSimulator)\n            self._currentSimulator = None\n        timeout = self.timeout()\n        if force:\n            timeout = 0.0\n        if timeout is not None:\n            fireDate = (CFAbsoluteTimeGetCurrent() + timeout)\n            def simulate(cftimer, extra):\n                self._currentSimulator = None\n                self.runUntilCurrent()\n                self._scheduleSimulate()\n            c = self._currentSimulator = CFRunLoopTimerCreate(\n                kCFAllocatorDefault, fireDate,\n                0, 0, 0, simulate, None\n            )\n            CFRunLoopAddTimer(self._cfrunloop, c, kCFRunLoopCommonModes)\n\n\n    def callLater(self, _seconds, _f, *args, **kw):\n        \"\"\"\n        Implement L{IReactorTime.callLater}.\n        \"\"\"\n        delayedCall = PosixReactorBase.callLater(\n            self, _seconds, _f, *args, **kw\n        )\n        self._scheduleSimulate()\n        return delayedCall\n\n\n    def stop(self):\n        \"\"\"\n        Implement L{IReactorCore.stop}.\n        \"\"\"\n        PosixReactorBase.stop(self)\n        self._scheduleSimulate(True)\n\n\n    def crash(self):\n        \"\"\"\n        Implement L{IReactorCore.crash}\n        \"\"\"\n        wasStarted = self._started\n        PosixReactorBase.crash(self)\n        if self._inCFLoop:\n            self._stopNow()\n        else:\n            if wasStarted:\n                self.callLater(0, self._stopNow)\n\n\n    def _stopNow(self):\n        \"\"\"\n        Immediately stop the CFRunLoop (which must be running!).\n        \"\"\"\n        CFRunLoopStop(self._cfrunloop)\n\n\n    def iterate(self, delay=0):\n        \"\"\"\n        Emulate the behavior of C{iterate()} for things that want to call it,\n        by letting the loop run for a little while and then scheduling a timed\n        call to exit it.\n        \"\"\"\n        self.callLater(delay, self._stopNow)\n        self.mainLoop()\n\n\n\ndef install(runLoop=None, runner=None):\n    \"\"\"\n    Configure the twisted mainloop to be run inside CFRunLoop.\n\n    @param runLoop: the run loop to use.\n\n    @param runner: the function to call in order to actually invoke the main\n        loop.  This will default to C{CFRunLoopRun} if not specified.  However,\n        this is not an appropriate choice for GUI applications, as you need to\n        run NSApplicationMain (or something like it).  For example, to run the\n        Twisted mainloop in a PyObjC application, your C{main.py} should look\n        something like this::\n\n            from PyObjCTools import AppHelper\n            from twisted.internet.cfreactor import install\n            install(runner=AppHelper.runEventLoop)\n            # initialize your application\n            reactor.run()\n\n    @return: The installed reactor.\n\n    @rtype: C{CFReactor}\n    \"\"\"\n\n    reactor = CFReactor(runLoop=runLoop, runner=runner)\n    from twisted.internet.main import installReactor\n    installReactor(reactor)\n    return reactor\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/default.py",
    "content": "# -*- test-case-name: twisted.internet.test.test_default -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThe most suitable default reactor for the current platform.\n\nDepending on a specific application's needs, some other reactor may in\nfact be better.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__all__ = [\"install\"]\n\nfrom twisted.python.runtime import platform\n\n\ndef _getInstallFunction(platform):\n    \"\"\"\n    Return a function to install the reactor most suited for the given platform.\n\n    @param platform: The platform for which to select a reactor.\n    @type platform: L{twisted.python.runtime.Platform}\n\n    @return: A zero-argument callable which will install the selected\n        reactor.\n    \"\"\"\n    # Linux: epoll(7) is the default, since it scales well.\n    #\n    # macOS: poll(2) is not exposed by Python because it doesn't support all\n    # file descriptors (in particular, lack of PTY support is a problem) --\n    # see <http://bugs.python.org/issue5154>. kqueue has the same restrictions\n    # as poll(2) as far PTY support goes.\n    #\n    # Windows: IOCP should eventually be default, but still has some serious\n    # bugs, e.g. <http://twistedmatrix.com/trac/ticket/4667>.\n    #\n    # We therefore choose epoll(7) on Linux, poll(2) on other non-macOS POSIX\n    # platforms, and select(2) everywhere else.\n    try:\n        if platform.isLinux():\n            try:\n                from twisted.internet.epollreactor import install\n            except ImportError:\n                from twisted.internet.pollreactor import install\n        elif platform.getType() == 'posix' and not platform.isMacOSX():\n            from twisted.internet.pollreactor import install\n        else:\n            from twisted.internet.selectreactor import install\n    except ImportError:\n        from twisted.internet.selectreactor import install\n    return install\n\n\ninstall = _getInstallFunction(platform)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/defer.py",
    "content": "# -*- test-case-name: twisted.test.test_defer -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nSupport for results that aren't immediately available.\n\nMaintainer: Glyph Lefkowitz\n\n@var _NO_RESULT: The result used to represent the fact that there is no\n    result. B{Never ever ever use this as an actual result for a Deferred}.  You\n    have been warned.\n\n@var _CONTINUE: A marker left in L{Deferred.callback}s to indicate a Deferred\n    chain.  Always accompanied by a Deferred instance in the args tuple pointing\n    at the Deferred which is chained to the Deferred which has this marker.\n\"\"\"\n\nfrom __future__ import division, absolute_import, print_function\n\nimport attr\nimport traceback\nimport types\nimport warnings\nfrom sys import exc_info, version_info\nfrom functools import wraps\nfrom incremental import Version\n\n# Twisted imports\nfrom twisted.python.compat import cmp, comparable\nfrom twisted.python import lockfile, failure\nfrom twisted.logger import Logger\nfrom twisted.python.deprecate import warnAboutFunction, deprecated\nfrom twisted.python._oldstyle import _oldStyle\n\nlog = Logger()\n\n\nclass AlreadyCalledError(Exception):\n    pass\n\n\n\nclass CancelledError(Exception):\n    \"\"\"\n    This error is raised by default when a L{Deferred} is cancelled.\n    \"\"\"\n\n\nclass TimeoutError(Exception):\n    \"\"\"\n    This error is raised by default when a L{Deferred} times out.\n    \"\"\"\n\n\n\ndef logError(err):\n    \"\"\"\n    Log and return failure.\n\n    This method can be used as an errback that passes the failure on to the\n    next errback unmodified. Note that if this is the last errback, and the\n    deferred gets garbage collected after being this errback has been called,\n    the clean up code logs it again.\n    \"\"\"\n    log.failure(None, err)\n    return err\n\n\n\ndef succeed(result):\n    \"\"\"\n    Return a L{Deferred} that has already had C{.callback(result)} called.\n\n    This is useful when you're writing synchronous code to an\n    asynchronous interface: i.e., some code is calling you expecting a\n    L{Deferred} result, but you don't actually need to do anything\n    asynchronous. Just return C{defer.succeed(theResult)}.\n\n    See L{fail} for a version of this function that uses a failing\n    L{Deferred} rather than a successful one.\n\n    @param result: The result to give to the Deferred's 'callback'\n           method.\n\n    @rtype: L{Deferred}\n    \"\"\"\n    d = Deferred()\n    d.callback(result)\n    return d\n\n\n\ndef fail(result=None):\n    \"\"\"\n    Return a L{Deferred} that has already had C{.errback(result)} called.\n\n    See L{succeed}'s docstring for rationale.\n\n    @param result: The same argument that L{Deferred.errback} takes.\n\n    @raise NoCurrentExceptionError: If C{result} is L{None} but there is no\n        current exception state.\n\n    @rtype: L{Deferred}\n    \"\"\"\n    d = Deferred()\n    d.errback(result)\n    return d\n\n\n\ndef execute(callable, *args, **kw):\n    \"\"\"\n    Create a L{Deferred} from a callable and arguments.\n\n    Call the given function with the given arguments.  Return a L{Deferred}\n    which has been fired with its callback as the result of that invocation\n    or its C{errback} with a L{Failure} for the exception thrown.\n    \"\"\"\n    try:\n        result = callable(*args, **kw)\n    except:\n        return fail()\n    else:\n        return succeed(result)\n\n\n\ndef maybeDeferred(f, *args, **kw):\n    \"\"\"\n    Invoke a function that may or may not return a L{Deferred}.\n\n    Call the given function with the given arguments.  If the returned\n    object is a L{Deferred}, return it.  If the returned object is a L{Failure},\n    wrap it with L{fail} and return it.  Otherwise, wrap it in L{succeed} and\n    return it.  If an exception is raised, convert it to a L{Failure}, wrap it\n    in L{fail}, and then return it.\n\n    @type f: Any callable\n    @param f: The callable to invoke\n\n    @param args: The arguments to pass to C{f}\n    @param kw: The keyword arguments to pass to C{f}\n\n    @rtype: L{Deferred}\n    @return: The result of the function call, wrapped in a L{Deferred} if\n    necessary.\n    \"\"\"\n    try:\n        result = f(*args, **kw)\n    except:\n        return fail(failure.Failure(captureVars=Deferred.debug))\n\n    if isinstance(result, Deferred):\n        return result\n    elif isinstance(result, failure.Failure):\n        return fail(result)\n    else:\n        return succeed(result)\n\n\n\n@deprecated(Version('Twisted', 17, 1, 0),\n            replacement='twisted.internet.defer.Deferred.addTimeout')\ndef timeout(deferred):\n    deferred.errback(failure.Failure(TimeoutError(\"Callback timed out\")))\n\n\n\ndef passthru(arg):\n    return arg\n\n\n\ndef setDebugging(on):\n    \"\"\"\n    Enable or disable L{Deferred} debugging.\n\n    When debugging is on, the call stacks from creation and invocation are\n    recorded, and added to any L{AlreadyCalledError}s we raise.\n    \"\"\"\n    Deferred.debug=bool(on)\n\n\n\ndef getDebugging():\n    \"\"\"\n    Determine whether L{Deferred} debugging is enabled.\n    \"\"\"\n    return Deferred.debug\n\n\n# See module docstring.\n_NO_RESULT = object()\n_CONTINUE = object()\n\n\n\n@_oldStyle\nclass Deferred:\n    \"\"\"\n    This is a callback which will be put off until later.\n\n    Why do we want this? Well, in cases where a function in a threaded\n    program would block until it gets a result, for Twisted it should\n    not block. Instead, it should return a L{Deferred}.\n\n    This can be implemented for protocols that run over the network by\n    writing an asynchronous protocol for L{twisted.internet}. For methods\n    that come from outside packages that are not under our control, we use\n    threads (see for example L{twisted.enterprise.adbapi}).\n\n    For more information about Deferreds, see doc/core/howto/defer.html or\n    U{http://twistedmatrix.com/documents/current/core/howto/defer.html}\n\n    When creating a Deferred, you may provide a canceller function, which\n    will be called by d.cancel() to let you do any clean-up necessary if the\n    user decides not to wait for the deferred to complete.\n\n    @ivar called: A flag which is C{False} until either C{callback} or\n        C{errback} is called and afterwards always C{True}.\n    @type called: L{bool}\n\n    @ivar paused: A counter of how many unmatched C{pause} calls have been made\n        on this instance.\n    @type paused: L{int}\n\n    @ivar _suppressAlreadyCalled: A flag used by the cancellation mechanism\n        which is C{True} if the Deferred has no canceller and has been\n        cancelled, C{False} otherwise.  If C{True}, it can be expected that\n        C{callback} or C{errback} will eventually be called and the result\n        should be silently discarded.\n    @type _suppressAlreadyCalled: L{bool}\n\n    @ivar _runningCallbacks: A flag which is C{True} while this instance is\n        executing its callback chain, used to stop recursive execution of\n        L{_runCallbacks}\n    @type _runningCallbacks: L{bool}\n\n    @ivar _chainedTo: If this L{Deferred} is waiting for the result of another\n        L{Deferred}, this is a reference to the other Deferred.  Otherwise,\n        L{None}.\n    \"\"\"\n\n    called = False\n    paused = False\n    _debugInfo = None\n    _suppressAlreadyCalled = False\n\n    # Are we currently running a user-installed callback?  Meant to prevent\n    # recursive running of callbacks when a reentrant call to add a callback is\n    # used.\n    _runningCallbacks = False\n\n    # Keep this class attribute for now, for compatibility with code that\n    # sets it directly.\n    debug = False\n\n    _chainedTo = None\n\n    def __init__(self, canceller=None):\n        \"\"\"\n        Initialize a L{Deferred}.\n\n        @param canceller: a callable used to stop the pending operation\n            scheduled by this L{Deferred} when L{Deferred.cancel} is\n            invoked. The canceller will be passed the deferred whose\n            cancelation is requested (i.e., self).\n\n            If a canceller is not given, or does not invoke its argument's\n            C{callback} or C{errback} method, L{Deferred.cancel} will\n            invoke L{Deferred.errback} with a L{CancelledError}.\n\n            Note that if a canceller is not given, C{callback} or\n            C{errback} may still be invoked exactly once, even though\n            defer.py will have already invoked C{errback}, as described\n            above.  This allows clients of code which returns a L{Deferred}\n            to cancel it without requiring the L{Deferred} instantiator to\n            provide any specific implementation support for cancellation.\n            New in 10.1.\n\n        @type canceller: a 1-argument callable which takes a L{Deferred}. The\n            return result is ignored.\n        \"\"\"\n        self.callbacks = []\n        self._canceller = canceller\n        if self.debug:\n            self._debugInfo = DebugInfo()\n            self._debugInfo.creator = traceback.format_stack()[:-1]\n\n\n    def addCallbacks(self, callback, errback=None,\n                     callbackArgs=None, callbackKeywords=None,\n                     errbackArgs=None, errbackKeywords=None):\n        \"\"\"\n        Add a pair of callbacks (success and error) to this L{Deferred}.\n\n        These will be executed when the 'master' callback is run.\n\n        @return: C{self}.\n        @rtype: a L{Deferred}\n        \"\"\"\n        assert callable(callback)\n        assert errback is None or callable(errback)\n        cbs = ((callback, callbackArgs, callbackKeywords),\n               (errback or (passthru), errbackArgs, errbackKeywords))\n        self.callbacks.append(cbs)\n\n        if self.called:\n            self._runCallbacks()\n        return self\n\n\n    def addCallback(self, callback, *args, **kw):\n        \"\"\"\n        Convenience method for adding just a callback.\n\n        See L{addCallbacks}.\n        \"\"\"\n        return self.addCallbacks(callback, callbackArgs=args,\n                                 callbackKeywords=kw)\n\n\n    def addErrback(self, errback, *args, **kw):\n        \"\"\"\n        Convenience method for adding just an errback.\n\n        See L{addCallbacks}.\n        \"\"\"\n        return self.addCallbacks(passthru, errback,\n                                 errbackArgs=args,\n                                 errbackKeywords=kw)\n\n\n    def addBoth(self, callback, *args, **kw):\n        \"\"\"\n        Convenience method for adding a single callable as both a callback\n        and an errback.\n\n        See L{addCallbacks}.\n        \"\"\"\n        return self.addCallbacks(callback, callback,\n                                 callbackArgs=args, errbackArgs=args,\n                                 callbackKeywords=kw, errbackKeywords=kw)\n\n\n    def addTimeout(self, timeout, clock, onTimeoutCancel=None):\n        \"\"\"\n        Time out this L{Deferred} by scheduling it to be cancelled after\n        C{timeout} seconds.\n\n        The timeout encompasses all the callbacks and errbacks added to this\n        L{defer.Deferred} before the call to L{addTimeout}, and none added\n        after the call.\n\n        If this L{Deferred} gets timed out, it errbacks with a L{TimeoutError},\n        unless a cancelable function was passed to its initialization or unless\n        a different C{onTimeoutCancel} callable is provided.\n\n        @param timeout: number of seconds to wait before timing out this\n            L{Deferred}\n        @type timeout: L{int}\n\n        @param clock: The object which will be used to schedule the timeout.\n        @type clock: L{twisted.internet.interfaces.IReactorTime}\n\n        @param onTimeoutCancel: A callable which is called immediately after\n            this L{Deferred} times out, and not if this L{Deferred} is\n            otherwise cancelled before the timeout. It takes an arbitrary\n            value, which is the value of this L{Deferred} at that exact point\n            in time (probably a L{CancelledError} L{Failure}), and the\n            C{timeout}.  The default callable (if none is provided) will\n            translate a L{CancelledError} L{Failure} into a L{TimeoutError}.\n        @type onTimeoutCancel: L{callable}\n\n        @return: C{self}.\n        @rtype: a L{Deferred}\n\n        @since: 16.5\n        \"\"\"\n        timedOut = [False]\n\n        def timeItOut():\n            timedOut[0] = True\n            self.cancel()\n\n        delayedCall = clock.callLater(timeout, timeItOut)\n\n        def convertCancelled(value):\n            # if C{deferred} was timed out, call the translation function,\n            # if provdied, otherwise just use L{cancelledToTimedOutError}\n            if timedOut[0]:\n                toCall = onTimeoutCancel or _cancelledToTimedOutError\n                return toCall(value, timeout)\n            return value\n\n        self.addBoth(convertCancelled)\n\n        def cancelTimeout(result):\n            # stop the pending call to cancel the deferred if it's been fired\n            if delayedCall.active():\n                delayedCall.cancel()\n            return result\n\n        self.addBoth(cancelTimeout)\n        return self\n\n\n    def chainDeferred(self, d):\n        \"\"\"\n        Chain another L{Deferred} to this L{Deferred}.\n\n        This method adds callbacks to this L{Deferred} to call C{d}'s callback\n        or errback, as appropriate. It is merely a shorthand way of performing\n        the following::\n\n            self.addCallbacks(d.callback, d.errback)\n\n        When you chain a deferred d2 to another deferred d1 with\n        d1.chainDeferred(d2), you are making d2 participate in the callback\n        chain of d1. Thus any event that fires d1 will also fire d2.\n        However, the converse is B{not} true; if d2 is fired d1 will not be\n        affected.\n\n        Note that unlike the case where chaining is caused by a L{Deferred}\n        being returned from a callback, it is possible to cause the call\n        stack size limit to be exceeded by chaining many L{Deferred}s\n        together with C{chainDeferred}.\n\n        @return: C{self}.\n        @rtype: a L{Deferred}\n        \"\"\"\n        d._chainedTo = self\n        return self.addCallbacks(d.callback, d.errback)\n\n\n    def callback(self, result):\n        \"\"\"\n        Run all success callbacks that have been added to this L{Deferred}.\n\n        Each callback will have its result passed as the first argument to\n        the next; this way, the callbacks act as a 'processing chain'.  If\n        the success-callback returns a L{Failure} or raises an L{Exception},\n        processing will continue on the *error* callback chain.  If a\n        callback (or errback) returns another L{Deferred}, this L{Deferred}\n        will be chained to it (and further callbacks will not run until that\n        L{Deferred} has a result).\n\n        An instance of L{Deferred} may only have either L{callback} or\n        L{errback} called on it, and only once.\n\n        @param result: The object which will be passed to the first callback\n            added to this L{Deferred} (via L{addCallback}).\n\n        @raise AlreadyCalledError: If L{callback} or L{errback} has already been\n            called on this L{Deferred}.\n        \"\"\"\n        assert not isinstance(result, Deferred)\n        self._startRunCallbacks(result)\n\n\n    def errback(self, fail=None):\n        \"\"\"\n        Run all error callbacks that have been added to this L{Deferred}.\n\n        Each callback will have its result passed as the first\n        argument to the next; this way, the callbacks act as a\n        'processing chain'. Also, if the error-callback returns a non-Failure\n        or doesn't raise an L{Exception}, processing will continue on the\n        *success*-callback chain.\n\n        If the argument that's passed to me is not a L{failure.Failure} instance,\n        it will be embedded in one. If no argument is passed, a\n        L{failure.Failure} instance will be created based on the current\n        traceback stack.\n\n        Passing a string as `fail' is deprecated, and will be punished with\n        a warning message.\n\n        An instance of L{Deferred} may only have either L{callback} or\n        L{errback} called on it, and only once.\n\n        @param fail: The L{Failure} object which will be passed to the first\n            errback added to this L{Deferred} (via L{addErrback}).\n            Alternatively, a L{Exception} instance from which a L{Failure} will\n            be constructed (with no traceback) or L{None} to create a L{Failure}\n            instance from the current exception state (with a traceback).\n\n        @raise AlreadyCalledError: If L{callback} or L{errback} has already been\n            called on this L{Deferred}.\n\n        @raise NoCurrentExceptionError: If C{fail} is L{None} but there is\n            no current exception state.\n        \"\"\"\n        if fail is None:\n            fail = failure.Failure(captureVars=self.debug)\n        elif not isinstance(fail, failure.Failure):\n            fail = failure.Failure(fail)\n\n        self._startRunCallbacks(fail)\n\n\n    def pause(self):\n        \"\"\"\n        Stop processing on a L{Deferred} until L{unpause}() is called.\n        \"\"\"\n        self.paused = self.paused + 1\n\n\n    def unpause(self):\n        \"\"\"\n        Process all callbacks made since L{pause}() was called.\n        \"\"\"\n        self.paused = self.paused - 1\n        if self.paused:\n            return\n        if self.called:\n            self._runCallbacks()\n\n\n    def cancel(self):\n        \"\"\"\n        Cancel this L{Deferred}.\n\n        If the L{Deferred} has not yet had its C{errback} or C{callback} method\n        invoked, call the canceller function provided to the constructor. If\n        that function does not invoke C{callback} or C{errback}, or if no\n        canceller function was provided, errback with L{CancelledError}.\n\n        If this L{Deferred} is waiting on another L{Deferred}, forward the\n        cancellation to the other L{Deferred}.\n        \"\"\"\n        if not self.called:\n            canceller = self._canceller\n            if canceller:\n                canceller(self)\n            else:\n                # Arrange to eat the callback that will eventually be fired\n                # since there was no real canceller.\n                self._suppressAlreadyCalled = True\n            if not self.called:\n                # There was no canceller, or the canceller didn't call\n                # callback or errback.\n                self.errback(failure.Failure(CancelledError()))\n        elif isinstance(self.result, Deferred):\n            # Waiting for another deferred -- cancel it instead.\n            self.result.cancel()\n\n\n    def _startRunCallbacks(self, result):\n        if self.called:\n            if self._suppressAlreadyCalled:\n                self._suppressAlreadyCalled = False\n                return\n            if self.debug:\n                if self._debugInfo is None:\n                    self._debugInfo = DebugInfo()\n                extra = \"\\n\" + self._debugInfo._getDebugTracebacks()\n                raise AlreadyCalledError(extra)\n            raise AlreadyCalledError\n        if self.debug:\n            if self._debugInfo is None:\n                self._debugInfo = DebugInfo()\n            self._debugInfo.invoker = traceback.format_stack()[:-2]\n        self.called = True\n        self.result = result\n        self._runCallbacks()\n\n\n    def _continuation(self):\n        \"\"\"\n        Build a tuple of callback and errback with L{_CONTINUE}.\n        \"\"\"\n        return ((_CONTINUE, (self,), None),\n                (_CONTINUE, (self,), None))\n\n\n    def _runCallbacks(self):\n        \"\"\"\n        Run the chain of callbacks once a result is available.\n\n        This consists of a simple loop over all of the callbacks, calling each\n        with the current result and making the current result equal to the\n        return value (or raised exception) of that call.\n\n        If L{_runningCallbacks} is true, this loop won't run at all, since\n        it is already running above us on the call stack.  If C{self.paused} is\n        true, the loop also won't run, because that's what it means to be\n        paused.\n\n        The loop will terminate before processing all of the callbacks if a\n        L{Deferred} without a result is encountered.\n\n        If a L{Deferred} I{with} a result is encountered, that result is taken\n        and the loop proceeds.\n\n        @note: The implementation is complicated slightly by the fact that\n            chaining (associating two L{Deferred}s with each other such that one\n            will wait for the result of the other, as happens when a Deferred is\n            returned from a callback on another L{Deferred}) is supported\n            iteratively rather than recursively, to avoid running out of stack\n            frames when processing long chains.\n        \"\"\"\n        if self._runningCallbacks:\n            # Don't recursively run callbacks\n            return\n\n        # Keep track of all the Deferreds encountered while propagating results\n        # up a chain.  The way a Deferred gets onto this stack is by having\n        # added its _continuation() to the callbacks list of a second Deferred\n        # and then that second Deferred being fired.  ie, if ever had _chainedTo\n        # set to something other than None, you might end up on this stack.\n        chain = [self]\n\n        while chain:\n            current = chain[-1]\n\n            if current.paused:\n                # This Deferred isn't going to produce a result at all.  All the\n                # Deferreds up the chain waiting on it will just have to...\n                # wait.\n                return\n\n            finished = True\n            current._chainedTo = None\n            while current.callbacks:\n                item = current.callbacks.pop(0)\n                callback, args, kw = item[\n                    isinstance(current.result, failure.Failure)]\n                args = args or ()\n                kw = kw or {}\n\n                # Avoid recursion if we can.\n                if callback is _CONTINUE:\n                    # Give the waiting Deferred our current result and then\n                    # forget about that result ourselves.\n                    chainee = args[0]\n                    chainee.result = current.result\n                    current.result = None\n                    # Making sure to update _debugInfo\n                    if current._debugInfo is not None:\n                        current._debugInfo.failResult = None\n                    chainee.paused -= 1\n                    chain.append(chainee)\n                    # Delay cleaning this Deferred and popping it from the chain\n                    # until after we've dealt with chainee.\n                    finished = False\n                    break\n\n                try:\n                    current._runningCallbacks = True\n                    try:\n                        current.result = callback(current.result, *args, **kw)\n                        if current.result is current:\n                            warnAboutFunction(\n                                callback,\n                                \"Callback returned the Deferred \"\n                                \"it was attached to; this breaks the \"\n                                \"callback chain and will raise an \"\n                                \"exception in the future.\")\n                    finally:\n                        current._runningCallbacks = False\n                except:\n                    # Including full frame information in the Failure is quite\n                    # expensive, so we avoid it unless self.debug is set.\n                    current.result = failure.Failure(captureVars=self.debug)\n                else:\n                    if isinstance(current.result, Deferred):\n                        # The result is another Deferred.  If it has a result,\n                        # we can take it and keep going.\n                        resultResult = getattr(current.result, 'result', _NO_RESULT)\n                        if resultResult is _NO_RESULT or isinstance(resultResult, Deferred) or current.result.paused:\n                            # Nope, it didn't.  Pause and chain.\n                            current.pause()\n                            current._chainedTo = current.result\n                            # Note: current.result has no result, so it's not\n                            # running its callbacks right now.  Therefore we can\n                            # append to the callbacks list directly instead of\n                            # using addCallbacks.\n                            current.result.callbacks.append(current._continuation())\n                            break\n                        else:\n                            # Yep, it did.  Steal it.\n                            current.result.result = None\n                            # Make sure _debugInfo's failure state is updated.\n                            if current.result._debugInfo is not None:\n                                current.result._debugInfo.failResult = None\n                            current.result = resultResult\n\n            if finished:\n                # As much of the callback chain - perhaps all of it - as can be\n                # processed right now has been.  The current Deferred is waiting on\n                # another Deferred or for more callbacks.  Before finishing with it,\n                # make sure its _debugInfo is in the proper state.\n                if isinstance(current.result, failure.Failure):\n                    # Stash the Failure in the _debugInfo for unhandled error\n                    # reporting.\n                    current.result.cleanFailure()\n                    if current._debugInfo is None:\n                        current._debugInfo = DebugInfo()\n                    current._debugInfo.failResult = current.result\n                else:\n                    # Clear out any Failure in the _debugInfo, since the result\n                    # is no longer a Failure.\n                    if current._debugInfo is not None:\n                        current._debugInfo.failResult = None\n\n                # This Deferred is done, pop it from the chain and move back up\n                # to the Deferred which supplied us with our result.\n                chain.pop()\n\n\n    def __str__(self):\n        \"\"\"\n        Return a string representation of this C{Deferred}.\n        \"\"\"\n        cname = self.__class__.__name__\n        result = getattr(self, 'result', _NO_RESULT)\n        myID = id(self)\n        if self._chainedTo is not None:\n            result = ' waiting on Deferred at 0x%x' % (id(self._chainedTo),)\n        elif result is _NO_RESULT:\n            result = ''\n        else:\n            result = ' current result: %r' % (result,)\n        return \"<%s at 0x%x%s>\" % (cname, myID, result)\n    __repr__ = __str__\n\n\n    def __iter__(self):\n        return self\n\n\n    @failure._extraneous\n    def send(self, value=None):\n        if self.paused:\n            # If we're paused, we have no result to give\n            return self\n\n        result = getattr(self, 'result', _NO_RESULT)\n        if result is _NO_RESULT:\n            return self\n        if isinstance(result, failure.Failure):\n            # Clear the failure on debugInfo so it doesn't raise \"unhandled\n            # exception\"\n            self._debugInfo.failResult = None\n            result.value.__failure__ = result\n            raise result.value\n        else:\n            raise StopIteration(result)\n\n\n    # For PEP-492 support (async/await)\n    __await__ = __iter__\n    __next__ = send\n\n\n    def asFuture(self, loop):\n        \"\"\"\n        Adapt a L{Deferred} into a L{asyncio.Future} which is bound to C{loop}.\n\n        @note: converting a L{Deferred} to an L{asyncio.Future} consumes both\n            its result and its errors, so this method implicitly converts\n            C{self} into a L{Deferred} firing with L{None}, regardless of what\n            its result previously would have been.\n\n        @since: Twisted 17.5.0\n\n        @param loop: The asyncio event loop to bind the L{asyncio.Future} to.\n        @type loop: L{asyncio.AbstractEventLoop} or similar\n\n        @param deferred: The Deferred to adapt.\n        @type deferred: L{Deferred}\n\n        @return: A Future which will fire when the Deferred fires.\n        @rtype: L{asyncio.Future}\n        \"\"\"\n        try:\n            createFuture = loop.create_future\n        except AttributeError:\n            from asyncio import Future\n            def createFuture():\n                return Future(loop=loop)\n        future = createFuture()\n        def checkCancel(futureAgain):\n            if futureAgain.cancelled():\n                self.cancel()\n        def maybeFail(failure):\n            if not future.cancelled():\n                future.set_exception(failure.value)\n        def maybeSucceed(result):\n            if not future.cancelled():\n                future.set_result(result)\n        self.addCallbacks(maybeSucceed, maybeFail)\n        future.add_done_callback(checkCancel)\n        return future\n\n\n    @classmethod\n    def fromFuture(cls, future):\n        \"\"\"\n        Adapt an L{asyncio.Future} to a L{Deferred}.\n\n        @note: This creates a L{Deferred} from a L{asyncio.Future}, I{not} from\n            a C{coroutine}; in other words, you will need to call\n            L{asyncio.ensure_future},\n            L{asyncio.loop.create_task} or create an\n            L{asyncio.Task} yourself to get from a C{coroutine} to a\n            L{asyncio.Future} if what you have is an awaitable coroutine and\n            not a L{asyncio.Future}.  (The length of this list of techniques is\n            exactly why we have left it to the caller!)\n\n        @since: Twisted 17.5.0\n\n        @param future: The Future to adapt.\n        @type future: L{asyncio.Future}\n\n        @return: A Deferred which will fire when the Future fires.\n        @rtype: L{Deferred}\n        \"\"\"\n        def adapt(result):\n            try:\n                extracted = result.result()\n            except:\n                extracted = failure.Failure()\n            adapt.actual.callback(extracted)\n        futureCancel = object()\n        def cancel(reself):\n            future.cancel()\n            reself.callback(futureCancel)\n        self = cls(cancel)\n        adapt.actual = self\n        def uncancel(result):\n            if result is futureCancel:\n                adapt.actual = Deferred()\n                return adapt.actual\n            return result\n        self.addCallback(uncancel)\n        future.add_done_callback(adapt)\n        return self\n\n\n\ndef _cancelledToTimedOutError(value, timeout):\n    \"\"\"\n    A default translation function that translates L{Failure}s that are\n    L{CancelledError}s to L{TimeoutError}s.\n\n    @param value: Anything\n    @type value: Anything\n\n    @param timeout: The timeout\n    @type timeout: L{int}\n\n    @rtype: C{value}\n    @raise: L{TimeoutError}\n\n    @since: 16.5\n    \"\"\"\n    if isinstance(value, failure.Failure):\n        value.trap(CancelledError)\n        raise TimeoutError(timeout, \"Deferred\")\n    return value\n\n\n\ndef ensureDeferred(coro):\n    \"\"\"\n    Schedule the execution of a coroutine that awaits/yields from L{Deferred}s,\n    wrapping it in a L{Deferred} that will fire on success/failure of the\n    coroutine. If a Deferred is passed to this function, it will be returned\n    directly (mimicing C{asyncio}'s C{ensure_future} function).\n\n    Coroutine functions return a coroutine object, similar to how generators\n    work. This function turns that coroutine into a Deferred, meaning that it\n    can be used in regular Twisted code. For example::\n\n        import treq\n        from twisted.internet.defer import ensureDeferred\n        from twisted.internet.task import react\n\n        async def crawl(pages):\n            results = {}\n            for page in pages:\n                results[page] = await treq.content(await treq.get(page))\n            return results\n\n        def main(reactor):\n            pages = [\n                \"http://localhost:8080\"\n            ]\n            d = ensureDeferred(crawl(pages))\n            d.addCallback(print)\n            return d\n\n        react(main)\n\n    @param coro: The coroutine object to schedule, or a L{Deferred}.\n    @type coro: A Python 3.5+ C{async def} C{coroutine}, a Python 3.4+\n        C{yield from} using L{types.GeneratorType}, or a L{Deferred}.\n\n    @rtype: L{Deferred}\n    \"\"\"\n    from types import GeneratorType\n\n    if version_info >= (3, 4, 0):\n        from asyncio import iscoroutine\n\n        if iscoroutine(coro) or isinstance(coro, GeneratorType):\n            return _cancellableInlineCallbacks(coro)\n\n    if not isinstance(coro, Deferred):\n        raise ValueError(\"%r is not a coroutine or a Deferred\" % (coro,))\n\n    # Must be a Deferred\n    return coro\n\n\n\n\n@_oldStyle\nclass DebugInfo:\n    \"\"\"\n    Deferred debug helper.\n    \"\"\"\n\n    failResult = None\n\n    def _getDebugTracebacks(self):\n        info = ''\n        if hasattr(self, \"creator\"):\n            info += \" C: Deferred was created:\\n C:\"\n            info += \"\".join(self.creator).rstrip().replace(\"\\n\", \"\\n C:\")\n            info += \"\\n\"\n        if hasattr(self, \"invoker\"):\n            info += \" I: First Invoker was:\\n I:\"\n            info += \"\".join(self.invoker).rstrip().replace(\"\\n\", \"\\n I:\")\n            info += \"\\n\"\n        return info\n\n\n    def __del__(self):\n        \"\"\"\n        Print tracebacks and die.\n\n        If the *last* (and I do mean *last*) callback leaves me in an error\n        state, print a traceback (if said errback is a L{Failure}).\n        \"\"\"\n        if self.failResult is not None:\n            # Note: this is two separate messages for compatibility with\n            # earlier tests; arguably it should be a single error message.\n            log.critical(\"Unhandled error in Deferred:\",\n                         isError=True)\n\n            debugInfo = self._getDebugTracebacks()\n            if debugInfo:\n                format = \"(debug: {debugInfo})\"\n            else:\n                format = None\n\n            log.failure(format,\n                        self.failResult,\n                        debugInfo=debugInfo)\n\n\n\n@comparable\nclass FirstError(Exception):\n    \"\"\"\n    First error to occur in a L{DeferredList} if C{fireOnOneErrback} is set.\n\n    @ivar subFailure: The L{Failure} that occurred.\n    @type subFailure: L{Failure}\n\n    @ivar index: The index of the L{Deferred} in the L{DeferredList} where\n        it happened.\n    @type index: L{int}\n    \"\"\"\n    def __init__(self, failure, index):\n        Exception.__init__(self, failure, index)\n        self.subFailure = failure\n        self.index = index\n\n\n    def __repr__(self):\n        \"\"\"\n        The I{repr} of L{FirstError} instances includes the repr of the\n        wrapped failure's exception and the index of the L{FirstError}.\n        \"\"\"\n        return 'FirstError[#%d, %r]' % (self.index, self.subFailure.value)\n\n\n    def __str__(self):\n        \"\"\"\n        The I{str} of L{FirstError} instances includes the I{str} of the\n        entire wrapped failure (including its traceback and exception) and\n        the index of the L{FirstError}.\n        \"\"\"\n        return 'FirstError[#%d, %s]' % (self.index, self.subFailure)\n\n\n    def __cmp__(self, other):\n        \"\"\"\n        Comparison between L{FirstError} and other L{FirstError} instances\n        is defined as the comparison of the index and sub-failure of each\n        instance.  L{FirstError} instances don't compare equal to anything\n        that isn't a L{FirstError} instance.\n\n        @since: 8.2\n        \"\"\"\n        if isinstance(other, FirstError):\n            return cmp(\n                (self.index, self.subFailure),\n                (other.index, other.subFailure))\n        return -1\n\n\n\nclass DeferredList(Deferred):\n    \"\"\"\n    L{DeferredList} is a tool for collecting the results of several Deferreds.\n\n    This tracks a list of L{Deferred}s for their results, and makes a single\n    callback when they have all completed.  By default, the ultimate result is a\n    list of (success, result) tuples, 'success' being a boolean.\n    L{DeferredList} exposes the same API that L{Deferred} does, so callbacks and\n    errbacks can be added to it in the same way.\n\n    L{DeferredList} is implemented by adding callbacks and errbacks to each\n    L{Deferred} in the list passed to it.  This means callbacks and errbacks\n    added to the Deferreds before they are passed to L{DeferredList} will change\n    the result that L{DeferredList} sees (i.e., L{DeferredList} is not special).\n    Callbacks and errbacks can also be added to the Deferreds after they are\n    passed to L{DeferredList} and L{DeferredList} may change the result that\n    they see.\n\n    See the documentation for the C{__init__} arguments for more information.\n\n    @ivar _deferredList: The L{list} of L{Deferred}s to track.\n    \"\"\"\n\n    fireOnOneCallback = False\n    fireOnOneErrback = False\n\n    def __init__(self, deferredList, fireOnOneCallback=False,\n                 fireOnOneErrback=False, consumeErrors=False):\n        \"\"\"\n        Initialize a DeferredList.\n\n        @param deferredList: The list of deferreds to track.\n        @type deferredList:  L{list} of L{Deferred}s\n\n        @param fireOnOneCallback: (keyword param) a flag indicating that this\n            L{DeferredList} will fire when the first L{Deferred} in\n            C{deferredList} fires with a non-failure result without waiting for\n            any of the other Deferreds.  When this flag is set, the DeferredList\n            will fire with a two-tuple: the first element is the result of the\n            Deferred which fired; the second element is the index in\n            C{deferredList} of that Deferred.\n        @type fireOnOneCallback: L{bool}\n\n        @param fireOnOneErrback: (keyword param) a flag indicating that this\n            L{DeferredList} will fire when the first L{Deferred} in\n            C{deferredList} fires with a failure result without waiting for any\n            of the other Deferreds.  When this flag is set, if a Deferred in the\n            list errbacks, the DeferredList will errback with a L{FirstError}\n            failure wrapping the failure of that Deferred.\n        @type fireOnOneErrback: L{bool}\n\n        @param consumeErrors: (keyword param) a flag indicating that failures in\n            any of the included L{Deferred}s should not be propagated to\n            errbacks added to the individual L{Deferred}s after this\n            L{DeferredList} is constructed.  After constructing the\n            L{DeferredList}, any errors in the individual L{Deferred}s will be\n            converted to a callback result of L{None}.  This is useful to\n            prevent spurious 'Unhandled error in Deferred' messages from being\n            logged.  This does not prevent C{fireOnOneErrback} from working.\n        @type consumeErrors: L{bool}\n        \"\"\"\n        self._deferredList = list(deferredList)\n        self.resultList = [None] * len(self._deferredList)\n        Deferred.__init__(self)\n        if len(self._deferredList) == 0 and not fireOnOneCallback:\n            self.callback(self.resultList)\n\n        # These flags need to be set *before* attaching callbacks to the\n        # deferreds, because the callbacks use these flags, and will run\n        # synchronously if any of the deferreds are already fired.\n        self.fireOnOneCallback = fireOnOneCallback\n        self.fireOnOneErrback = fireOnOneErrback\n        self.consumeErrors = consumeErrors\n        self.finishedCount = 0\n\n        index = 0\n        for deferred in self._deferredList:\n            deferred.addCallbacks(self._cbDeferred, self._cbDeferred,\n                                  callbackArgs=(index,SUCCESS),\n                                  errbackArgs=(index,FAILURE))\n            index = index + 1\n\n\n    def _cbDeferred(self, result, index, succeeded):\n        \"\"\"\n        (internal) Callback for when one of my deferreds fires.\n        \"\"\"\n        self.resultList[index] = (succeeded, result)\n\n        self.finishedCount += 1\n        if not self.called:\n            if succeeded == SUCCESS and self.fireOnOneCallback:\n                self.callback((result, index))\n            elif succeeded == FAILURE and self.fireOnOneErrback:\n                self.errback(failure.Failure(FirstError(result, index)))\n            elif self.finishedCount == len(self.resultList):\n                self.callback(self.resultList)\n\n        if succeeded == FAILURE and self.consumeErrors:\n            result = None\n\n        return result\n\n\n    def cancel(self):\n        \"\"\"\n        Cancel this L{DeferredList}.\n\n        If the L{DeferredList} hasn't fired yet, cancel every L{Deferred} in\n        the list.\n\n        If the L{DeferredList} has fired, including the case where the\n        C{fireOnOneCallback}/C{fireOnOneErrback} flag is set and the\n        L{DeferredList} fires because one L{Deferred} in the list fires with a\n        non-failure/failure result, do nothing in the C{cancel} method.\n        \"\"\"\n        if not self.called:\n            for deferred in self._deferredList:\n                try:\n                    deferred.cancel()\n                except:\n                    log.failure(\n                        \"Exception raised from user supplied canceller\"\n                    )\n\n\n\ndef _parseDListResult(l, fireOnOneErrback=False):\n    if __debug__:\n        for success, value in l:\n            assert success\n    return [x[1] for x in l]\n\n\n\ndef gatherResults(deferredList, consumeErrors=False):\n    \"\"\"\n    Returns, via a L{Deferred}, a list with the results of the given\n    L{Deferred}s - in effect, a \"join\" of multiple deferred operations.\n\n    The returned L{Deferred} will fire when I{all} of the provided L{Deferred}s\n    have fired, or when any one of them has failed.\n\n    This method can be cancelled by calling the C{cancel} method of the\n    L{Deferred}, all the L{Deferred}s in the list will be cancelled.\n\n    This differs from L{DeferredList} in that you don't need to parse\n    the result for success/failure.\n\n    @type deferredList:  L{list} of L{Deferred}s\n\n    @param consumeErrors: (keyword param) a flag, defaulting to False,\n        indicating that failures in any of the given L{Deferred}s should not be\n        propagated to errbacks added to the individual L{Deferred}s after this\n        L{gatherResults} invocation.  Any such errors in the individual\n        L{Deferred}s will be converted to a callback result of L{None}.  This\n        is useful to prevent spurious 'Unhandled error in Deferred' messages\n        from being logged.  This parameter is available since 11.1.0.\n    @type consumeErrors: L{bool}\n    \"\"\"\n    d = DeferredList(deferredList, fireOnOneErrback=True,\n                                   consumeErrors=consumeErrors)\n    d.addCallback(_parseDListResult)\n    return d\n\n\n\n# Constants for use with DeferredList\n\nSUCCESS = True\nFAILURE = False\n\n\n\n## deferredGenerator\n@_oldStyle\nclass waitForDeferred:\n    \"\"\"\n    See L{deferredGenerator}.\n    \"\"\"\n\n    def __init__(self, d):\n        warnings.warn(\n            \"twisted.internet.defer.waitForDeferred was deprecated in \"\n            \"Twisted 15.0.0; please use twisted.internet.defer.inlineCallbacks \"\n            \"instead\", DeprecationWarning, stacklevel=2)\n\n        if not isinstance(d, Deferred):\n            raise TypeError(\"You must give waitForDeferred a Deferred. You gave it %r.\" % (d,))\n        self.d = d\n\n\n    def getResult(self):\n        if isinstance(self.result, failure.Failure):\n            self.result.raiseException()\n        return self.result\n\n\n\ndef _deferGenerator(g, deferred):\n    \"\"\"\n    See L{deferredGenerator}.\n    \"\"\"\n    result = None\n\n    # This function is complicated by the need to prevent unbounded recursion\n    # arising from repeatedly yielding immediately ready deferreds.  This while\n    # loop and the waiting variable solve that by manually unfolding the\n    # recursion.\n\n    waiting = [True, # defgen is waiting for result?\n               None] # result\n\n    while 1:\n        try:\n            result = next(g)\n        except StopIteration:\n            deferred.callback(result)\n            return deferred\n        except:\n            deferred.errback()\n            return deferred\n\n        # Deferred.callback(Deferred) raises an error; we catch this case\n        # early here and give a nicer error message to the user in case\n        # they yield a Deferred.\n        if isinstance(result, Deferred):\n            return fail(TypeError(\"Yield waitForDeferred(d), not d!\"))\n\n        if isinstance(result, waitForDeferred):\n            # a waitForDeferred was yielded, get the result.\n            # Pass result in so it don't get changed going around the loop\n            # This isn't a problem for waiting, as it's only reused if\n            # gotResult has already been executed.\n            def gotResult(r, result=result):\n                result.result = r\n                if waiting[0]:\n                    waiting[0] = False\n                    waiting[1] = r\n                else:\n                    _deferGenerator(g, deferred)\n            result.d.addBoth(gotResult)\n            if waiting[0]:\n                # Haven't called back yet, set flag so that we get reinvoked\n                # and return from the loop\n                waiting[0] = False\n                return deferred\n            # Reset waiting to initial values for next loop\n            waiting[0] = True\n            waiting[1] = None\n\n            result = None\n\n\n\n@deprecated(Version('Twisted', 15, 0, 0),\n            \"twisted.internet.defer.inlineCallbacks\")\ndef deferredGenerator(f):\n    \"\"\"\n    L{deferredGenerator} and L{waitForDeferred} help you write\n    L{Deferred}-using code that looks like a regular sequential function.\n    Consider the use of L{inlineCallbacks} instead, which can accomplish\n    the same thing in a more concise manner.\n\n    There are two important functions involved: L{waitForDeferred}, and\n    L{deferredGenerator}.  They are used together, like this::\n\n        @deferredGenerator\n        def thingummy():\n            thing = waitForDeferred(makeSomeRequestResultingInDeferred())\n            yield thing\n            thing = thing.getResult()\n            print(thing) #the result! hoorj!\n\n    L{waitForDeferred} returns something that you should immediately yield; when\n    your generator is resumed, calling C{thing.getResult()} will either give you\n    the result of the L{Deferred} if it was a success, or raise an exception if it\n    was a failure.  Calling C{getResult} is B{absolutely mandatory}.  If you do\n    not call it, I{your program will not work}.\n\n    L{deferredGenerator} takes one of these waitForDeferred-using generator\n    functions and converts it into a function that returns a L{Deferred}. The\n    result of the L{Deferred} will be the last value that your generator yielded\n    unless the last value is a L{waitForDeferred} instance, in which case the\n    result will be L{None}.  If the function raises an unhandled exception, the\n    L{Deferred} will errback instead.  Remember that C{return result} won't work;\n    use C{yield result; return} in place of that.\n\n    Note that not yielding anything from your generator will make the L{Deferred}\n    result in L{None}. Yielding a L{Deferred} from your generator is also an error\n    condition; always yield C{waitForDeferred(d)} instead.\n\n    The L{Deferred} returned from your deferred generator may also errback if your\n    generator raised an exception.  For example::\n\n        @deferredGenerator\n        def thingummy():\n            thing = waitForDeferred(makeSomeRequestResultingInDeferred())\n            yield thing\n            thing = thing.getResult()\n            if thing == 'I love Twisted':\n                # will become the result of the Deferred\n                yield 'TWISTED IS GREAT!'\n                return\n            else:\n                # will trigger an errback\n                raise Exception('DESTROY ALL LIFE')\n\n    Put succinctly, these functions connect deferred-using code with this 'fake\n    blocking' style in both directions: L{waitForDeferred} converts from a\n    L{Deferred} to the 'blocking' style, and L{deferredGenerator} converts from the\n    'blocking' style to a L{Deferred}.\n    \"\"\"\n    @wraps(f)\n    def unwindGenerator(*args, **kwargs):\n        return _deferGenerator(f(*args, **kwargs), Deferred())\n    return unwindGenerator\n\n\n## inlineCallbacks\n\n\n\nclass _DefGen_Return(BaseException):\n    def __init__(self, value):\n        self.value = value\n\n\n\ndef returnValue(val):\n    \"\"\"\n    Return val from a L{inlineCallbacks} generator.\n\n    Note: this is currently implemented by raising an exception\n    derived from L{BaseException}.  You might want to change any\n    'except:' clauses to an 'except Exception:' clause so as not to\n    catch this exception.\n\n    Also: while this function currently will work when called from\n    within arbitrary functions called from within the generator, do\n    not rely upon this behavior.\n    \"\"\"\n    raise _DefGen_Return(val)\n\n\n\n@attr.s\nclass _CancellationStatus(object):\n    \"\"\"\n    Cancellation status of an L{inlineCallbacks} invocation.\n\n    @ivar waitingOn: the L{Deferred} being waited upon (which\n        L{_inlineCallbacks} must fill out before returning)\n\n    @ivar deferred: the L{Deferred} to callback or errback when the generator\n        invocation has finished.\n    \"\"\"\n\n    deferred = attr.ib()\n    waitingOn = attr.ib(default=None)\n\n\n\n@failure._extraneous\ndef _inlineCallbacks(result, g, status):\n    \"\"\"\n    Carry out the work of L{inlineCallbacks}.\n\n    Iterate the generator produced by an C{@}L{inlineCallbacks}-decorated\n    function, C{g}, C{send()}ing it the results of each value C{yield}ed by\n    that generator, until a L{Deferred} is yielded, at which point a callback\n    is added to that L{Deferred} to call this function again.\n\n    @param result: The last result seen by this generator.  Note that this is\n        never a L{Deferred} - by the time this function is invoked, the\n        L{Deferred} has been called back and this will be a particular result\n        at a point in its callback chain.\n\n    @param g: a generator object returned by calling a function or method\n        decorated with C{@}L{inlineCallbacks}\n\n    @param status: a L{_CancellationStatus} tracking the current status of C{g}\n    \"\"\"\n    # This function is complicated by the need to prevent unbounded recursion\n    # arising from repeatedly yielding immediately ready deferreds.  This while\n    # loop and the waiting variable solve that by manually unfolding the\n    # recursion.\n\n    waiting = [True, # waiting for result?\n               None] # result\n\n    while 1:\n        try:\n            # Send the last result back as the result of the yield expression.\n            isFailure = isinstance(result, failure.Failure)\n            if isFailure:\n                result = result.throwExceptionIntoGenerator(g)\n            else:\n                result = g.send(result)\n        except StopIteration as e:\n            # fell off the end, or \"return\" statement\n            status.deferred.callback(getattr(e, \"value\", None))\n            return\n        except _DefGen_Return as e:\n            # returnValue() was called; time to give a result to the original\n            # Deferred.  First though, let's try to identify the potentially\n            # confusing situation which results when returnValue() is\n            # accidentally invoked from a different function, one that wasn't\n            # decorated with @inlineCallbacks.\n\n            # The traceback starts in this frame (the one for\n            # _inlineCallbacks); the next one down should be the application\n            # code.\n            appCodeTrace = exc_info()[2].tb_next\n            if isFailure:\n                # If we invoked this generator frame by throwing an exception\n                # into it, then throwExceptionIntoGenerator will consume an\n                # additional stack frame itself, so we need to skip that too.\n                appCodeTrace = appCodeTrace.tb_next\n            # Now that we've identified the frame being exited by the\n            # exception, let's figure out if returnValue was called from it\n            # directly.  returnValue itself consumes a stack frame, so the\n            # application code will have a tb_next, but it will *not* have a\n            # second tb_next.\n            if appCodeTrace.tb_next.tb_next:\n                # If returnValue was invoked non-local to the frame which it is\n                # exiting, identify the frame that ultimately invoked\n                # returnValue so that we can warn the user, as this behavior is\n                # confusing.\n                ultimateTrace = appCodeTrace\n                while ultimateTrace.tb_next.tb_next:\n                    ultimateTrace = ultimateTrace.tb_next\n                filename = ultimateTrace.tb_frame.f_code.co_filename\n                lineno = ultimateTrace.tb_lineno\n                warnings.warn_explicit(\n                    \"returnValue() in %r causing %r to exit: \"\n                    \"returnValue should only be invoked by functions decorated \"\n                    \"with inlineCallbacks\" % (\n                        ultimateTrace.tb_frame.f_code.co_name,\n                        appCodeTrace.tb_frame.f_code.co_name),\n                    DeprecationWarning, filename, lineno)\n            status.deferred.callback(e.value)\n            return\n        except:\n            status.deferred.errback()\n            return\n\n        if isinstance(result, Deferred):\n            # a deferred was yielded, get the result.\n            def gotResult(r):\n                if waiting[0]:\n                    waiting[0] = False\n                    waiting[1] = r\n                else:\n                    # We are not waiting for deferred result any more\n                    _inlineCallbacks(r, g, status)\n\n            result.addBoth(gotResult)\n            if waiting[0]:\n                # Haven't called back yet, set flag so that we get reinvoked\n                # and return from the loop\n                waiting[0] = False\n                status.waitingOn = result\n                return\n\n            result = waiting[1]\n            # Reset waiting to initial values for next loop.  gotResult uses\n            # waiting, but this isn't a problem because gotResult is only\n            # executed once, and if it hasn't been executed yet, the return\n            # branch above would have been taken.\n\n            waiting[0] = True\n            waiting[1] = None\n\n\n\ndef _cancellableInlineCallbacks(g):\n    \"\"\"\n    Make an C{@}L{inlineCallbacks} cancellable.\n\n    @param g: a generator object returned by calling a function or method\n        decorated with C{@}L{inlineCallbacks}\n\n    @return: L{Deferred} for the C{@}L{inlineCallbacks} that is cancellable.\n    \"\"\"\n    def cancel(it):\n        it.callbacks, tmp = [], it.callbacks\n        it.addErrback(handleCancel)\n        it.callbacks.extend(tmp)\n        it.errback(_InternalInlineCallbacksCancelledError())\n    deferred = Deferred(cancel)\n    status = _CancellationStatus(deferred)\n    def handleCancel(result):\n        \"\"\"\n        Propagate the cancellation of an C{@}L{inlineCallbacks} to the\n        L{Deferred} it is waiting on.\n\n        @param result: An L{_InternalInlineCallbacksCancelledError} from\n            C{cancel()}.\n        @return: A new L{Deferred} that the C{@}L{inlineCallback} generator\n            can callback or errback through.\n        \"\"\"\n        result.trap(_InternalInlineCallbacksCancelledError)\n        status.deferred = Deferred(cancel)\n        # We would only end up here if the inlineCallback is waiting on\n        # another Deferred.  It needs to be cancelled.\n        awaited = status.waitingOn\n        awaited.cancel()\n        return status.deferred\n    _inlineCallbacks(None, g, status)\n    return deferred\n\n\n\nclass _InternalInlineCallbacksCancelledError(Exception):\n    \"\"\"\n    A unique exception used only in L{_cancellableInlineCallbacks} to verify\n    that an L{inlineCallbacks} is being cancelled as expected.\n    \"\"\"\n\n\n\ndef inlineCallbacks(f):\n    \"\"\"\n    L{inlineCallbacks} helps you write L{Deferred}-using code that looks like a\n    regular sequential function. For example::\n\n        @inlineCallbacks\n        def thingummy():\n            thing = yield makeSomeRequestResultingInDeferred()\n            print(thing)  # the result! hoorj!\n\n    When you call anything that results in a L{Deferred}, you can simply yield it;\n    your generator will automatically be resumed when the Deferred's result is\n    available. The generator will be sent the result of the L{Deferred} with the\n    'send' method on generators, or if the result was a failure, 'throw'.\n\n    Things that are not L{Deferred}s may also be yielded, and your generator\n    will be resumed with the same object sent back. This means C{yield}\n    performs an operation roughly equivalent to L{maybeDeferred}.\n\n    Your inlineCallbacks-enabled generator will return a L{Deferred} object, which\n    will result in the return value of the generator (or will fail with a\n    failure object if your generator raises an unhandled exception). Note that\n    you can't use C{return result} to return a value; use C{returnValue(result)}\n    instead. Falling off the end of the generator, or simply using C{return}\n    will cause the L{Deferred} to have a result of L{None}.\n\n    Be aware that L{returnValue} will not accept a L{Deferred} as a parameter.\n    If you believe the thing you'd like to return could be a L{Deferred}, do\n    this::\n\n        result = yield result\n        returnValue(result)\n\n    The L{Deferred} returned from your deferred generator may errback if your\n    generator raised an exception::\n\n        @inlineCallbacks\n        def thingummy():\n            thing = yield makeSomeRequestResultingInDeferred()\n            if thing == 'I love Twisted':\n                # will become the result of the Deferred\n                returnValue('TWISTED IS GREAT!')\n            else:\n                # will trigger an errback\n                raise Exception('DESTROY ALL LIFE')\n\n    It is possible to use the C{return} statement instead of L{returnValue}::\n\n        @inlineCallbacks\n        def loadData(url):\n            response = yield makeRequest(url)\n            return json.loads(response)\n\n    You can cancel the L{Deferred} returned from your L{inlineCallbacks}\n    generator before it is fired by your generator completing (either by\n    reaching its end, a C{return} statement, or by calling L{returnValue}).\n    A C{CancelledError} will be raised from the C{yielde}ed L{Deferred} that\n    has been cancelled if that C{Deferred} does not otherwise suppress it.\n    \"\"\"\n    @wraps(f)\n    def unwindGenerator(*args, **kwargs):\n        try:\n            gen = f(*args, **kwargs)\n        except _DefGen_Return:\n            raise TypeError(\n                \"inlineCallbacks requires %r to produce a generator; instead\"\n                \"caught returnValue being used in a non-generator\" % (f,))\n        if not isinstance(gen, types.GeneratorType):\n            raise TypeError(\n                \"inlineCallbacks requires %r to produce a generator; \"\n                \"instead got %r\" % (f, gen))\n        return _cancellableInlineCallbacks(gen)\n    return unwindGenerator\n\n\n## DeferredLock/DeferredQueue\n\nclass _ConcurrencyPrimitive(object):\n    def __init__(self):\n        self.waiting = []\n\n\n    def _releaseAndReturn(self, r):\n        self.release()\n        return r\n\n\n    def run(*args, **kwargs):\n        \"\"\"\n        Acquire, run, release.\n\n        This function takes a callable as its first argument and any\n        number of other positional and keyword arguments.  When the\n        lock or semaphore is acquired, the callable will be invoked\n        with those arguments.\n\n        The callable may return a L{Deferred}; if it does, the lock or\n        semaphore won't be released until that L{Deferred} fires.\n\n        @return: L{Deferred} of function result.\n        \"\"\"\n        if len(args) < 2:\n            if not args:\n                raise TypeError(\"run() takes at least 2 arguments, none given.\")\n            raise TypeError(\"%s.run() takes at least 2 arguments, 1 given\" % (\n                args[0].__class__.__name__,))\n        self, f = args[:2]\n        args = args[2:]\n\n        def execute(ignoredResult):\n            d = maybeDeferred(f, *args, **kwargs)\n            d.addBoth(self._releaseAndReturn)\n            return d\n\n        d = self.acquire()\n        d.addCallback(execute)\n        return d\n\n\n    def __aenter__(self):\n        \"\"\"\n        We can be used as an asynchronous context manager.\n        \"\"\"\n        return self.acquire()\n\n\n    def __aexit__(self, exc_type, exc_val, exc_tb):\n        self.release()\n        # We return False to indicate that we have not consumed the\n        # exception, if any.\n        return succeed(False)\n\n\n\nclass DeferredLock(_ConcurrencyPrimitive):\n    \"\"\"\n    A lock for event driven systems.\n\n    @ivar locked: C{True} when this Lock has been acquired, false at all other\n        times.  Do not change this value, but it is useful to examine for the\n        equivalent of a \"non-blocking\" acquisition.\n    \"\"\"\n\n    locked = False\n\n\n    def _cancelAcquire(self, d):\n        \"\"\"\n        Remove a deferred d from our waiting list, as the deferred has been\n        canceled.\n\n        Note: We do not need to wrap this in a try/except to catch d not\n        being in self.waiting because this canceller will not be called if\n        d has fired. release() pops a deferred out of self.waiting and\n        calls it, so the canceller will no longer be called.\n\n        @param d: The deferred that has been canceled.\n        \"\"\"\n        self.waiting.remove(d)\n\n\n    def acquire(self):\n        \"\"\"\n        Attempt to acquire the lock.  Returns a L{Deferred} that fires on\n        lock acquisition with the L{DeferredLock} as the value.  If the lock\n        is locked, then the Deferred is placed at the end of a waiting list.\n\n        @return: a L{Deferred} which fires on lock acquisition.\n        @rtype: a L{Deferred}\n        \"\"\"\n        d = Deferred(canceller=self._cancelAcquire)\n        if self.locked:\n            self.waiting.append(d)\n        else:\n            self.locked = True\n            d.callback(self)\n        return d\n\n\n    def release(self):\n        \"\"\"\n        Release the lock.  If there is a waiting list, then the first\n        L{Deferred} in that waiting list will be called back.\n\n        Should be called by whomever did the L{acquire}() when the shared\n        resource is free.\n        \"\"\"\n        assert self.locked, \"Tried to release an unlocked lock\"\n        self.locked = False\n        if self.waiting:\n            # someone is waiting to acquire lock\n            self.locked = True\n            d = self.waiting.pop(0)\n            d.callback(self)\n\n\n\nclass DeferredSemaphore(_ConcurrencyPrimitive):\n    \"\"\"\n    A semaphore for event driven systems.\n\n    If you are looking into this as a means of limiting parallelism, you might\n    find L{twisted.internet.task.Cooperator} more useful.\n\n    @ivar limit: At most this many users may acquire this semaphore at\n        once.\n    @type limit: L{int}\n\n    @ivar tokens: The difference between C{limit} and the number of users\n        which have currently acquired this semaphore.\n    @type tokens: L{int}\n    \"\"\"\n\n    def __init__(self, tokens):\n        \"\"\"\n        @param tokens: initial value of L{tokens} and L{limit}\n        @type tokens: L{int}\n        \"\"\"\n        _ConcurrencyPrimitive.__init__(self)\n        if tokens < 1:\n            raise ValueError(\"DeferredSemaphore requires tokens >= 1\")\n        self.tokens = tokens\n        self.limit = tokens\n\n\n    def _cancelAcquire(self, d):\n        \"\"\"\n        Remove a deferred d from our waiting list, as the deferred has been\n        canceled.\n\n        Note: We do not need to wrap this in a try/except to catch d not\n        being in self.waiting because this canceller will not be called if\n        d has fired. release() pops a deferred out of self.waiting and\n        calls it, so the canceller will no longer be called.\n\n        @param d: The deferred that has been canceled.\n        \"\"\"\n        self.waiting.remove(d)\n\n\n    def acquire(self):\n        \"\"\"\n        Attempt to acquire the token.\n\n        @return: a L{Deferred} which fires on token acquisition.\n        \"\"\"\n        assert self.tokens >= 0, \"Internal inconsistency??  tokens should never be negative\"\n        d = Deferred(canceller=self._cancelAcquire)\n        if not self.tokens:\n            self.waiting.append(d)\n        else:\n            self.tokens = self.tokens - 1\n            d.callback(self)\n        return d\n\n\n    def release(self):\n        \"\"\"\n        Release the token.\n\n        Should be called by whoever did the L{acquire}() when the shared\n        resource is free.\n        \"\"\"\n        assert self.tokens < self.limit, \"Someone released me too many times: too many tokens!\"\n        self.tokens = self.tokens + 1\n        if self.waiting:\n            # someone is waiting to acquire token\n            self.tokens = self.tokens - 1\n            d = self.waiting.pop(0)\n            d.callback(self)\n\n\n\nclass QueueOverflow(Exception):\n    pass\n\n\n\nclass QueueUnderflow(Exception):\n    pass\n\n\n\nclass DeferredQueue(object):\n    \"\"\"\n    An event driven queue.\n\n    Objects may be added as usual to this queue.  When an attempt is\n    made to retrieve an object when the queue is empty, a L{Deferred} is\n    returned which will fire when an object becomes available.\n\n    @ivar size: The maximum number of objects to allow into the queue\n    at a time.  When an attempt to add a new object would exceed this\n    limit, L{QueueOverflow} is raised synchronously.  L{None} for no limit.\n\n    @ivar backlog: The maximum number of L{Deferred} gets to allow at\n    one time.  When an attempt is made to get an object which would\n    exceed this limit, L{QueueUnderflow} is raised synchronously.  L{None}\n    for no limit.\n    \"\"\"\n\n    def __init__(self, size=None, backlog=None):\n        self.waiting = []\n        self.pending = []\n        self.size = size\n        self.backlog = backlog\n\n\n    def _cancelGet(self, d):\n        \"\"\"\n        Remove a deferred d from our waiting list, as the deferred has been\n        canceled.\n\n        Note: We do not need to wrap this in a try/except to catch d not\n        being in self.waiting because this canceller will not be called if\n        d has fired. put() pops a deferred out of self.waiting and calls\n        it, so the canceller will no longer be called.\n\n        @param d: The deferred that has been canceled.\n        \"\"\"\n        self.waiting.remove(d)\n\n\n    def put(self, obj):\n        \"\"\"\n        Add an object to this queue.\n\n        @raise QueueOverflow: Too many objects are in this queue.\n        \"\"\"\n        if self.waiting:\n            self.waiting.pop(0).callback(obj)\n        elif self.size is None or len(self.pending) < self.size:\n            self.pending.append(obj)\n        else:\n            raise QueueOverflow()\n\n\n    def get(self):\n        \"\"\"\n        Attempt to retrieve and remove an object from the queue.\n\n        @return: a L{Deferred} which fires with the next object available in\n        the queue.\n\n        @raise QueueUnderflow: Too many (more than C{backlog})\n        L{Deferred}s are already waiting for an object from this queue.\n        \"\"\"\n        if self.pending:\n            return succeed(self.pending.pop(0))\n        elif self.backlog is None or len(self.waiting) < self.backlog:\n            d = Deferred(canceller=self._cancelGet)\n            self.waiting.append(d)\n            return d\n        else:\n            raise QueueUnderflow()\n\n\n\nclass AlreadyTryingToLockError(Exception):\n    \"\"\"\n    Raised when L{DeferredFilesystemLock.deferUntilLocked} is called twice on a\n    single L{DeferredFilesystemLock}.\n    \"\"\"\n\n\n\nclass DeferredFilesystemLock(lockfile.FilesystemLock):\n    \"\"\"\n    A L{FilesystemLock} that allows for a L{Deferred} to be fired when the lock is\n    acquired.\n\n    @ivar _scheduler: The object in charge of scheduling retries. In this\n        implementation this is parameterized for testing.\n\n    @ivar _interval: The retry interval for an L{IReactorTime} based scheduler.\n\n    @ivar _tryLockCall: A L{DelayedCall} based on C{_interval} that will manage\n        the next retry for acquiring the lock.\n\n    @ivar _timeoutCall: A L{DelayedCall} based on C{deferUntilLocked}'s timeout\n        argument.  This is in charge of timing out our attempt to acquire the\n        lock.\n    \"\"\"\n    _interval = 1\n    _tryLockCall = None\n    _timeoutCall = None\n\n\n    def __init__(self, name, scheduler=None):\n        \"\"\"\n        @param name: The name of the lock to acquire\n        @param scheduler: An object which provides L{IReactorTime}\n        \"\"\"\n        lockfile.FilesystemLock.__init__(self, name)\n\n        if scheduler is None:\n            from twisted.internet import reactor\n            scheduler = reactor\n\n        self._scheduler = scheduler\n\n\n    def deferUntilLocked(self, timeout=None):\n        \"\"\"\n        Wait until we acquire this lock.  This method is not safe for\n        concurrent use.\n\n        @type timeout: L{float} or L{int}\n        @param timeout: the number of seconds after which to time out if the\n            lock has not been acquired.\n\n        @return: a L{Deferred} which will callback when the lock is acquired, or\n            errback with a L{TimeoutError} after timing out or an\n            L{AlreadyTryingToLockError} if the L{deferUntilLocked} has already\n            been called and not successfully locked the file.\n        \"\"\"\n        if self._tryLockCall is not None:\n            return fail(\n                AlreadyTryingToLockError(\n                    \"deferUntilLocked isn't safe for concurrent use.\"))\n\n        def _cancelLock(reason):\n            \"\"\"\n            Cancel a L{DeferredFilesystemLock.deferUntilLocked} call.\n\n            @type reason: L{failure.Failure}\n            @param reason: The reason why the call is cancelled.\n            \"\"\"\n            self._tryLockCall.cancel()\n            self._tryLockCall = None\n            if self._timeoutCall is not None and self._timeoutCall.active():\n                self._timeoutCall.cancel()\n                self._timeoutCall = None\n\n            if self.lock():\n                d.callback(None)\n            else:\n                d.errback(reason)\n\n        d = Deferred(lambda deferred: _cancelLock(CancelledError()))\n\n        def _tryLock():\n            if self.lock():\n                if self._timeoutCall is not None:\n                    self._timeoutCall.cancel()\n                    self._timeoutCall = None\n\n                self._tryLockCall = None\n\n                d.callback(None)\n            else:\n                if timeout is not None and self._timeoutCall is None:\n                    reason = failure.Failure(TimeoutError(\n                        \"Timed out acquiring lock: %s after %fs\" % (\n                            self.name,\n                            timeout)))\n                    self._timeoutCall = self._scheduler.callLater(\n                        timeout, _cancelLock, reason)\n\n                self._tryLockCall = self._scheduler.callLater(\n                    self._interval, _tryLock)\n\n        _tryLock()\n\n        return d\n\n\n\n__all__ = [\"Deferred\", \"DeferredList\", \"succeed\", \"fail\", \"FAILURE\", \"SUCCESS\",\n           \"AlreadyCalledError\", \"TimeoutError\", \"gatherResults\",\n           \"maybeDeferred\", \"ensureDeferred\",\n           \"waitForDeferred\", \"deferredGenerator\", \"inlineCallbacks\",\n           \"returnValue\",\n           \"DeferredLock\", \"DeferredSemaphore\", \"DeferredQueue\",\n           \"DeferredFilesystemLock\", \"AlreadyTryingToLockError\",\n           \"CancelledError\",\n          ]\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/endpoints.py",
    "content": "# -*- test-case-name: twisted.internet.test.test_endpoints -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nImplementations of L{IStreamServerEndpoint} and L{IStreamClientEndpoint} that\nwrap the L{IReactorTCP}, L{IReactorSSL}, and L{IReactorUNIX} interfaces.\n\nThis also implements an extensible mini-language for describing endpoints,\nparsed by the L{clientFromString} and L{serverFromString} functions.\n\n@since: 10.1\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport os\nimport re\nimport socket\nfrom unicodedata import normalize\nimport warnings\n\nfrom constantly import NamedConstant, Names\nfrom incremental import Version\n\nfrom zope.interface import implementer, directlyProvides, provider\n\nfrom twisted.internet import interfaces, defer, error, fdesc, threads\nfrom twisted.internet.abstract import isIPv6Address, isIPAddress\nfrom twisted.internet.address import (\n    _ProcessAddress, HostnameAddress, IPv4Address, IPv6Address\n)\nfrom twisted.internet.interfaces import (\n    IStreamServerEndpointStringParser,\n    IStreamClientEndpointStringParserWithReactor, IResolutionReceiver,\n    IReactorPluggableNameResolver,\n    IHostnameResolver,\n)\nfrom twisted.internet.protocol import ClientFactory, Factory\nfrom twisted.internet.protocol import ProcessProtocol, Protocol\n\ntry:\n    from twisted.internet.stdio import StandardIO, PipeAddress\nexcept ImportError:\n    # fallback if pywin32 is not installed\n    StandardIO = None\n    PipeAddress = None\n\nfrom twisted.internet.task import LoopingCall\nfrom twisted.internet._resolver import HostResolution\nfrom twisted.logger import Logger\nfrom twisted.plugin import IPlugin, getPlugins\nfrom twisted.python import deprecate, log\nfrom twisted.python.compat import nativeString, unicode, _matchingString\nfrom twisted.python.components import proxyForInterface\nfrom twisted.python.failure import Failure\nfrom twisted.python.filepath import FilePath\nfrom twisted.python.compat import iterbytes\nfrom twisted.internet.defer import Deferred\nfrom twisted.python.systemd import ListenFDs\n\nfrom ._idna import _idnaBytes, _idnaText\n\ntry:\n    from twisted.protocols.tls import TLSMemoryBIOFactory\n    from twisted.internet.ssl import (\n        optionsForClientTLS, PrivateCertificate, Certificate, KeyPair,\n        CertificateOptions, trustRootFromCertificates\n    )\n    from OpenSSL.SSL import Error as SSLError\nexcept ImportError:\n    TLSMemoryBIOFactory = None\n\n__all__ = [\"clientFromString\", \"serverFromString\",\n           \"TCP4ServerEndpoint\", \"TCP6ServerEndpoint\",\n           \"TCP4ClientEndpoint\", \"TCP6ClientEndpoint\",\n           \"UNIXServerEndpoint\", \"UNIXClientEndpoint\",\n           \"SSL4ServerEndpoint\", \"SSL4ClientEndpoint\",\n           \"AdoptedStreamServerEndpoint\", \"StandardIOEndpoint\",\n           \"ProcessEndpoint\", \"HostnameEndpoint\",\n           \"StandardErrorBehavior\", \"connectProtocol\",\n           \"wrapClientTLS\"]\n\n\n\nclass _WrappingProtocol(Protocol):\n    \"\"\"\n    Wrap another protocol in order to notify my user when a connection has\n    been made.\n    \"\"\"\n\n    def __init__(self, connectedDeferred, wrappedProtocol):\n        \"\"\"\n        @param connectedDeferred: The L{Deferred} that will callback\n            with the C{wrappedProtocol} when it is connected.\n\n        @param wrappedProtocol: An L{IProtocol} provider that will be\n            connected.\n        \"\"\"\n        self._connectedDeferred = connectedDeferred\n        self._wrappedProtocol = wrappedProtocol\n\n        for iface in [interfaces.IHalfCloseableProtocol,\n                      interfaces.IFileDescriptorReceiver,\n                      interfaces.IHandshakeListener]:\n            if iface.providedBy(self._wrappedProtocol):\n                directlyProvides(self, iface)\n\n\n    def logPrefix(self):\n        \"\"\"\n        Transparently pass through the wrapped protocol's log prefix.\n        \"\"\"\n        if interfaces.ILoggingContext.providedBy(self._wrappedProtocol):\n            return self._wrappedProtocol.logPrefix()\n        return self._wrappedProtocol.__class__.__name__\n\n\n    def connectionMade(self):\n        \"\"\"\n        Connect the C{self._wrappedProtocol} to our C{self.transport} and\n        callback C{self._connectedDeferred} with the C{self._wrappedProtocol}\n        \"\"\"\n        self._wrappedProtocol.makeConnection(self.transport)\n        self._connectedDeferred.callback(self._wrappedProtocol)\n\n\n    def dataReceived(self, data):\n        \"\"\"\n        Proxy C{dataReceived} calls to our C{self._wrappedProtocol}\n        \"\"\"\n        return self._wrappedProtocol.dataReceived(data)\n\n\n    def fileDescriptorReceived(self, descriptor):\n        \"\"\"\n        Proxy C{fileDescriptorReceived} calls to our C{self._wrappedProtocol}\n        \"\"\"\n        return self._wrappedProtocol.fileDescriptorReceived(descriptor)\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Proxy C{connectionLost} calls to our C{self._wrappedProtocol}\n        \"\"\"\n        return self._wrappedProtocol.connectionLost(reason)\n\n\n    def readConnectionLost(self):\n        \"\"\"\n        Proxy L{IHalfCloseableProtocol.readConnectionLost} to our\n        C{self._wrappedProtocol}\n        \"\"\"\n        self._wrappedProtocol.readConnectionLost()\n\n\n    def writeConnectionLost(self):\n        \"\"\"\n        Proxy L{IHalfCloseableProtocol.writeConnectionLost} to our\n        C{self._wrappedProtocol}\n        \"\"\"\n        self._wrappedProtocol.writeConnectionLost()\n\n\n    def handshakeCompleted(self):\n        \"\"\"\n        Proxy L{interfaces.IHandshakeListener} to our\n        C{self._wrappedProtocol}.\n        \"\"\"\n        self._wrappedProtocol.handshakeCompleted()\n\n\n\nclass _WrappingFactory(ClientFactory):\n    \"\"\"\n    Wrap a factory in order to wrap the protocols it builds.\n\n    @ivar _wrappedFactory: A provider of I{IProtocolFactory} whose buildProtocol\n        method will be called and whose resulting protocol will be wrapped.\n\n    @ivar _onConnection: A L{Deferred} that fires when the protocol is\n        connected\n\n    @ivar _connector: A L{connector <twisted.internet.interfaces.IConnector>}\n        that is managing the current or previous connection attempt.\n    \"\"\"\n    protocol = _WrappingProtocol\n\n    def __init__(self, wrappedFactory):\n        \"\"\"\n        @param wrappedFactory: A provider of I{IProtocolFactory} whose\n            buildProtocol method will be called and whose resulting protocol\n            will be wrapped.\n        \"\"\"\n        self._wrappedFactory = wrappedFactory\n        self._onConnection = defer.Deferred(canceller=self._canceller)\n\n\n    def startedConnecting(self, connector):\n        \"\"\"\n        A connection attempt was started.  Remember the connector which started\n        said attempt, for use later.\n        \"\"\"\n        self._connector = connector\n\n\n    def _canceller(self, deferred):\n        \"\"\"\n        The outgoing connection attempt was cancelled.  Fail that L{Deferred}\n        with an L{error.ConnectingCancelledError}.\n\n        @param deferred: The L{Deferred <defer.Deferred>} that was cancelled;\n            should be the same as C{self._onConnection}.\n        @type deferred: L{Deferred <defer.Deferred>}\n\n        @note: This relies on startedConnecting having been called, so it may\n            seem as though there's a race condition where C{_connector} may not\n            have been set.  However, using public APIs, this condition is\n            impossible to catch, because a connection API\n            (C{connectTCP}/C{SSL}/C{UNIX}) is always invoked before a\n            L{_WrappingFactory}'s L{Deferred <defer.Deferred>} is returned to\n            C{connect()}'s caller.\n\n        @return: L{None}\n        \"\"\"\n        deferred.errback(\n            error.ConnectingCancelledError(\n                self._connector.getDestination()))\n        self._connector.stopConnecting()\n\n\n    def doStart(self):\n        \"\"\"\n        Start notifications are passed straight through to the wrapped factory.\n        \"\"\"\n        self._wrappedFactory.doStart()\n\n\n    def doStop(self):\n        \"\"\"\n        Stop notifications are passed straight through to the wrapped factory.\n        \"\"\"\n        self._wrappedFactory.doStop()\n\n\n    def buildProtocol(self, addr):\n        \"\"\"\n        Proxy C{buildProtocol} to our C{self._wrappedFactory} or errback the\n        C{self._onConnection} L{Deferred} if the wrapped factory raises an\n        exception or returns L{None}.\n\n        @return: An instance of L{_WrappingProtocol} or L{None}\n        \"\"\"\n        try:\n            proto = self._wrappedFactory.buildProtocol(addr)\n            if proto is None:\n                raise error.NoProtocol()\n        except:\n            self._onConnection.errback()\n        else:\n            return self.protocol(self._onConnection, proto)\n\n\n    def clientConnectionFailed(self, connector, reason):\n        \"\"\"\n        Errback the C{self._onConnection} L{Deferred} when the\n        client connection fails.\n        \"\"\"\n        if not self._onConnection.called:\n            self._onConnection.errback(reason)\n\n\n\n@implementer(interfaces.IStreamServerEndpoint)\nclass StandardIOEndpoint(object):\n    \"\"\"\n    A Standard Input/Output endpoint\n\n    @ivar _stdio: a callable, like L{stdio.StandardIO}, which takes an\n        L{IProtocol} provider and a C{reactor} keyword argument (interface\n        dependent upon your platform).\n    \"\"\"\n\n    _stdio = StandardIO\n\n    def __init__(self, reactor):\n        \"\"\"\n        @param reactor: The reactor for the endpoint.\n        \"\"\"\n        self._reactor = reactor\n\n\n    def listen(self, stdioProtocolFactory):\n        \"\"\"\n        Implement L{IStreamServerEndpoint.listen} to listen on stdin/stdout\n        \"\"\"\n        return defer.execute(self._stdio,\n                             stdioProtocolFactory.buildProtocol(PipeAddress()),\n                             reactor=self._reactor)\n\n\n\nclass _IProcessTransportWithConsumerAndProducer(interfaces.IProcessTransport,\n                                                interfaces.IConsumer,\n                                                interfaces.IPushProducer):\n    \"\"\"\n    An L{_IProcessTransportWithConsumerAndProducer} combines various interfaces\n    to work around the issue that L{interfaces.IProcessTransport} is\n    incompletely defined and doesn't specify flow-control interfaces, and that\n    L{proxyForInterface} doesn't allow for multiple interfaces.\n    \"\"\"\n\n\n\nclass _ProcessEndpointTransport(\n        proxyForInterface(_IProcessTransportWithConsumerAndProducer,\n                          '_process')):\n    \"\"\"\n    An L{ITransport}, L{IProcessTransport}, L{IConsumer}, and L{IPushProducer}\n    provider for the L{IProtocol} instance passed to the process endpoint.\n\n    @ivar _process: An active process transport which will be used by write\n        methods on this object to write data to a child process.\n    @type _process: L{interfaces.IProcessTransport} provider\n    \"\"\"\n\n\n\nclass _WrapIProtocol(ProcessProtocol):\n    \"\"\"\n    An L{IProcessProtocol} provider that wraps an L{IProtocol}.\n\n    @ivar transport: A L{_ProcessEndpointTransport} provider that is hooked to\n        the wrapped L{IProtocol} provider.\n\n    @see: L{protocol.ProcessProtocol}\n    \"\"\"\n\n    def __init__(self, proto, executable, errFlag):\n        \"\"\"\n        @param proto: An L{IProtocol} provider.\n        @param errFlag: A constant belonging to L{StandardErrorBehavior}\n            that determines if stderr is logged or dropped.\n        @param executable: The file name (full path) to spawn.\n        \"\"\"\n        self.protocol = proto\n        self.errFlag = errFlag\n        self.executable = executable\n\n\n    def makeConnection(self, process):\n        \"\"\"\n        Call L{IProtocol} provider's makeConnection method with an\n        L{ITransport} provider.\n\n        @param process: An L{IProcessTransport} provider.\n        \"\"\"\n        self.transport = _ProcessEndpointTransport(process)\n        return self.protocol.makeConnection(self.transport)\n\n\n    def childDataReceived(self, childFD, data):\n        \"\"\"\n        This is called with data from the process's stdout or stderr pipes. It\n        checks the status of the errFlag to setermine if stderr should be\n        logged (default) or dropped.\n        \"\"\"\n        if childFD == 1:\n            return self.protocol.dataReceived(data)\n        elif childFD == 2 and self.errFlag == StandardErrorBehavior.LOG:\n            log.msg(\n                format=\"Process %(executable)r wrote stderr unhandled by \"\n                       \"%(protocol)s: %(data)s\",\n                executable=self.executable, protocol=self.protocol,\n                data=data)\n\n\n    def processEnded(self, reason):\n        \"\"\"\n        If the process ends with L{error.ProcessDone}, this method calls the\n        L{IProtocol} provider's L{connectionLost} with a\n        L{error.ConnectionDone}\n\n        @see: L{ProcessProtocol.processEnded}\n        \"\"\"\n        if (reason.check(error.ProcessDone) == error.ProcessDone) and (\n                reason.value.status == 0):\n            return self.protocol.connectionLost(\n                Failure(error.ConnectionDone()))\n        else:\n            return self.protocol.connectionLost(reason)\n\n\n\nclass StandardErrorBehavior(Names):\n    \"\"\"\n    Constants used in ProcessEndpoint to decide what to do with stderr.\n\n    @cvar LOG: Indicates that stderr is to be logged.\n    @cvar DROP: Indicates that stderr is to be dropped (and not logged).\n\n    @since: 13.1\n    \"\"\"\n    LOG = NamedConstant()\n    DROP = NamedConstant()\n\n\n\n@implementer(interfaces.IStreamClientEndpoint)\nclass ProcessEndpoint(object):\n    \"\"\"\n    An endpoint for child processes\n\n    @ivar _spawnProcess: A hook used for testing the spawning of child process.\n\n    @since: 13.1\n    \"\"\"\n    def __init__(self, reactor, executable, args=(), env={}, path=None,\n                 uid=None, gid=None, usePTY=0, childFDs=None,\n                 errFlag=StandardErrorBehavior.LOG):\n        \"\"\"\n        See L{IReactorProcess.spawnProcess}.\n\n        @param errFlag: Determines if stderr should be logged.\n        @type errFlag: L{endpoints.StandardErrorBehavior}\n        \"\"\"\n        self._reactor = reactor\n        self._executable = executable\n        self._args = args\n        self._env = env\n        self._path = path\n        self._uid = uid\n        self._gid = gid\n        self._usePTY = usePTY\n        self._childFDs = childFDs\n        self._errFlag = errFlag\n        self._spawnProcess = self._reactor.spawnProcess\n\n\n    def connect(self, protocolFactory):\n        \"\"\"\n        Implement L{IStreamClientEndpoint.connect} to launch a child process\n        and connect it to a protocol created by C{protocolFactory}.\n\n        @param protocolFactory: A factory for an L{IProtocol} provider which\n            will be notified of all events related to the created process.\n        \"\"\"\n        proto = protocolFactory.buildProtocol(_ProcessAddress())\n        try:\n            self._spawnProcess(\n                _WrapIProtocol(proto, self._executable, self._errFlag),\n                self._executable, self._args, self._env, self._path, self._uid,\n                self._gid, self._usePTY, self._childFDs)\n        except:\n            return defer.fail()\n        else:\n            return defer.succeed(proto)\n\n\n\n@implementer(interfaces.IStreamServerEndpoint)\nclass _TCPServerEndpoint(object):\n    \"\"\"\n    A TCP server endpoint interface\n    \"\"\"\n\n    def __init__(self, reactor, port, backlog, interface):\n        \"\"\"\n        @param reactor: An L{IReactorTCP} provider.\n\n        @param port: The port number used for listening\n        @type port: int\n\n        @param backlog: Size of the listen queue\n        @type backlog: int\n\n        @param interface: The hostname to bind to\n        @type interface: str\n        \"\"\"\n        self._reactor = reactor\n        self._port = port\n        self._backlog = backlog\n        self._interface = interface\n\n\n    def listen(self, protocolFactory):\n        \"\"\"\n        Implement L{IStreamServerEndpoint.listen} to listen on a TCP\n        socket\n        \"\"\"\n        return defer.execute(self._reactor.listenTCP,\n                             self._port,\n                             protocolFactory,\n                             backlog=self._backlog,\n                             interface=self._interface)\n\n\n\nclass TCP4ServerEndpoint(_TCPServerEndpoint):\n    \"\"\"\n    Implements TCP server endpoint with an IPv4 configuration\n    \"\"\"\n    def __init__(self, reactor, port, backlog=50, interface=''):\n        \"\"\"\n        @param reactor: An L{IReactorTCP} provider.\n\n        @param port: The port number used for listening\n        @type port: int\n\n        @param backlog: Size of the listen queue\n        @type backlog: int\n\n        @param interface: The hostname to bind to, defaults to '' (all)\n        @type interface: str\n        \"\"\"\n        _TCPServerEndpoint.__init__(self, reactor, port, backlog, interface)\n\n\n\nclass TCP6ServerEndpoint(_TCPServerEndpoint):\n    \"\"\"\n    Implements TCP server endpoint with an IPv6 configuration\n    \"\"\"\n    def __init__(self, reactor, port, backlog=50, interface='::'):\n        \"\"\"\n        @param reactor: An L{IReactorTCP} provider.\n\n        @param port: The port number used for listening\n        @type port: int\n\n        @param backlog: Size of the listen queue\n        @type backlog: int\n\n        @param interface: The hostname to bind to, defaults to C{::} (all)\n        @type interface: str\n        \"\"\"\n        _TCPServerEndpoint.__init__(self, reactor, port, backlog, interface)\n\n\n\n@implementer(interfaces.IStreamClientEndpoint)\nclass TCP4ClientEndpoint(object):\n    \"\"\"\n    TCP client endpoint with an IPv4 configuration.\n    \"\"\"\n\n    def __init__(self, reactor, host, port, timeout=30, bindAddress=None):\n        \"\"\"\n        @param reactor: An L{IReactorTCP} provider\n\n        @param host: A hostname, used when connecting\n        @type host: str\n\n        @param port: The port number, used when connecting\n        @type port: int\n\n        @param timeout: The number of seconds to wait before assuming the\n            connection has failed.\n        @type timeout: L{float} or L{int}\n\n        @param bindAddress: A (host, port) tuple of local address to bind to,\n            or None.\n        @type bindAddress: tuple\n        \"\"\"\n        self._reactor = reactor\n        self._host = host\n        self._port = port\n        self._timeout = timeout\n        self._bindAddress = bindAddress\n\n\n    def connect(self, protocolFactory):\n        \"\"\"\n        Implement L{IStreamClientEndpoint.connect} to connect via TCP.\n        \"\"\"\n        try:\n            wf = _WrappingFactory(protocolFactory)\n            self._reactor.connectTCP(\n                self._host, self._port, wf,\n                timeout=self._timeout, bindAddress=self._bindAddress)\n            return wf._onConnection\n        except:\n            return defer.fail()\n\n\n\n@implementer(interfaces.IStreamClientEndpoint)\nclass TCP6ClientEndpoint(object):\n    \"\"\"\n    TCP client endpoint with an IPv6 configuration.\n\n    @ivar _getaddrinfo: A hook used for testing name resolution.\n\n    @ivar _deferToThread: A hook used for testing deferToThread.\n\n    @ivar _GAI_ADDRESS: Index of the address portion in result of\n        getaddrinfo to be used.\n\n    @ivar _GAI_ADDRESS_HOST: Index of the actual host-address in the\n        5-tuple L{_GAI_ADDRESS}.\n    \"\"\"\n\n    _getaddrinfo = staticmethod(socket.getaddrinfo)\n    _deferToThread = staticmethod(threads.deferToThread)\n    _GAI_ADDRESS = 4\n    _GAI_ADDRESS_HOST = 0\n\n    def __init__(self, reactor, host, port, timeout=30, bindAddress=None):\n        \"\"\"\n        @param host: An IPv6 address literal or a hostname with an\n            IPv6 address\n\n        @see: L{twisted.internet.interfaces.IReactorTCP.connectTCP}\n        \"\"\"\n        self._reactor = reactor\n        self._host = host\n        self._port = port\n        self._timeout = timeout\n        self._bindAddress = bindAddress\n\n\n    def connect(self, protocolFactory):\n        \"\"\"\n        Implement L{IStreamClientEndpoint.connect} to connect via TCP,\n        once the hostname resolution is done.\n        \"\"\"\n        if isIPv6Address(self._host):\n            d = self._resolvedHostConnect(self._host, protocolFactory)\n        else:\n            d = self._nameResolution(self._host)\n            d.addCallback(lambda result: result[0][self._GAI_ADDRESS]\n                          [self._GAI_ADDRESS_HOST])\n            d.addCallback(self._resolvedHostConnect, protocolFactory)\n        return d\n\n\n    def _nameResolution(self, host):\n        \"\"\"\n        Resolve the hostname string into a tuple containing the host\n        IPv6 address.\n        \"\"\"\n        return self._deferToThread(\n            self._getaddrinfo, host, 0, socket.AF_INET6)\n\n\n    def _resolvedHostConnect(self, resolvedHost, protocolFactory):\n        \"\"\"\n        Connect to the server using the resolved hostname.\n        \"\"\"\n        try:\n            wf = _WrappingFactory(protocolFactory)\n            self._reactor.connectTCP(resolvedHost, self._port, wf,\n                timeout=self._timeout, bindAddress=self._bindAddress)\n            return wf._onConnection\n        except:\n            return defer.fail()\n\n\n\n@implementer(IHostnameResolver)\nclass _SimpleHostnameResolver(object):\n    \"\"\"\n    An L{IHostnameResolver} provider that invokes a provided callable\n    to resolve hostnames.\n\n    @ivar _nameResolution: the callable L{resolveHostName} invokes to\n        resolve hostnames.\n    @type _nameResolution: A L{callable} that accepts two arguments:\n        the host to resolve and the port number to include in the\n        result.\n    \"\"\"\n    _log = Logger()\n\n    def __init__(self, nameResolution):\n        \"\"\"\n        Create a L{_SimpleHostnameResolver} instance.\n        \"\"\"\n        self._nameResolution = nameResolution\n\n\n    def resolveHostName(self, resolutionReceiver,\n                        hostName,\n                        portNumber=0,\n                        addressTypes=None,\n                        transportSemantics='TCP'):\n        \"\"\"\n        Initiate a hostname resolution.\n\n        @param resolutionReceiver: an object that will receive each resolved\n            address as it arrives.\n        @type resolutionReceiver: L{IResolutionReceiver}\n\n        @param hostName: see interface\n\n        @param portNumber: see interface\n\n        @param addressTypes: Ignored in this implementation.\n\n        @param transportSemantics: Ignored in this implementation.\n\n        @return: The resolution in progress.\n        @rtype: L{IResolutionReceiver}\n        \"\"\"\n        resolutionReceiver.resolutionBegan(HostResolution(hostName))\n        d = self._nameResolution(hostName, portNumber)\n\n        def cbDeliver(gairesult):\n            for family, socktype, proto, canonname, sockaddr in gairesult:\n                if family == socket.AF_INET6:\n                    resolutionReceiver.addressResolved(\n                        IPv6Address('TCP', *sockaddr))\n                elif family == socket.AF_INET:\n                    resolutionReceiver.addressResolved(\n                        IPv4Address('TCP', *sockaddr))\n\n\n        def ebLog(error):\n            self._log.failure(\"while looking up {name} with {callable}\",\n                              error, name=hostName,\n                              callable=self._nameResolution)\n\n        d.addCallback(cbDeliver)\n        d.addErrback(ebLog)\n        d.addBoth(lambda ignored: resolutionReceiver.resolutionComplete())\n        return resolutionReceiver\n\n\n\n\n@implementer(interfaces.IStreamClientEndpoint)\nclass HostnameEndpoint(object):\n    \"\"\"\n    A name-based endpoint that connects to the fastest amongst the resolved\n    host addresses.\n\n    @cvar _DEFAULT_ATTEMPT_DELAY: The default time to use between attempts, in\n        seconds, when no C{attemptDelay} is given to\n        L{HostnameEndpoint.__init__}.\n\n    @ivar _hostText: the textual representation of the hostname passed to the\n        constructor.  Used to pass to the reactor's hostname resolver.\n    @type _hostText: L{unicode}\n\n    @ivar _hostBytes: the encoded bytes-representation of the hostname passed\n        to the constructor.  Used to construct the L{HostnameAddress}\n        associated with this endpoint.\n    @type _hostBytes: L{bytes}\n\n    @ivar _hostStr: the native-string representation of the hostname passed to\n        the constructor, used for exception construction\n    @type _hostStr: native L{str}\n\n    @ivar _badHostname: a flag - hopefully false!  - indicating that an invalid\n        hostname was passed to the constructor.  This might be a textual\n        hostname that isn't valid IDNA, or non-ASCII bytes.\n    @type _badHostname: L{bool}\n    \"\"\"\n    _getaddrinfo = staticmethod(socket.getaddrinfo)\n    _deferToThread = staticmethod(threads.deferToThread)\n    _DEFAULT_ATTEMPT_DELAY = 0.3\n\n    def __init__(self, reactor, host, port, timeout=30, bindAddress=None,\n                 attemptDelay=None):\n        \"\"\"\n        Create a L{HostnameEndpoint}.\n\n        @param reactor: The reactor to use for connections and delayed calls.\n        @type reactor: provider of L{IReactorTCP}, L{IReactorTime} and either\n            L{IReactorPluggableNameResolver} or L{IReactorPluggableResolver}.\n\n        @param host: A hostname to connect to.\n        @type host: L{bytes} or L{unicode}\n\n        @param port: The port number to connect to.\n        @type port: L{int}\n\n        @param timeout: For each individual connection attempt, the number of\n            seconds to wait before assuming the connection has failed.\n        @type timeout: L{float} or L{int}\n\n        @param bindAddress: the local address of the network interface to make\n            the connections from.\n        @type bindAddress: L{bytes}\n\n        @param attemptDelay: The number of seconds to delay between connection\n            attempts.\n        @type attemptDelay: L{float}\n\n        @see: L{twisted.internet.interfaces.IReactorTCP.connectTCP}\n        \"\"\"\n\n        self._reactor = reactor\n        self._nameResolver = self._getNameResolverAndMaybeWarn(reactor)\n        [self._badHostname, self._hostBytes, self._hostText] = (\n            self._hostAsBytesAndText(host)\n        )\n        self._hostStr = self._hostBytes if bytes is str else self._hostText\n        self._port = port\n        self._timeout = timeout\n        self._bindAddress = bindAddress\n        if attemptDelay is None:\n            attemptDelay = self._DEFAULT_ATTEMPT_DELAY\n        self._attemptDelay = attemptDelay\n\n\n    def __repr__(self):\n        \"\"\"\n        Produce a string representation of the L{HostnameEndpoint}.\n\n        @return: A L{str}\n        \"\"\"\n        if self._badHostname:\n            # Use the backslash-encoded version of the string passed to the\n            # constructor, which is already a native string.\n            host = self._hostStr\n        elif isIPv6Address(self._hostStr):\n            host = '[{}]'.format(self._hostStr)\n        else:\n            # Convert the bytes representation to a native string to ensure\n            # that we display the punycoded version of the hostname, which is\n            # more useful than any IDN version as it can be easily copy-pasted\n            # into debugging tools.\n            host = nativeString(self._hostBytes)\n        return \"\".join([\"<HostnameEndpoint \", host, \":\", str(self._port), \">\"])\n\n\n    def _getNameResolverAndMaybeWarn(self, reactor):\n        \"\"\"\n        Retrieve a C{nameResolver} callable and warn the caller's\n        caller that using a reactor which doesn't provide\n        L{IReactorPluggableNameResolver} is deprecated.\n\n        @param reactor: The reactor to check.\n\n        @return: A L{IHostnameResolver} provider.\n        \"\"\"\n        if not IReactorPluggableNameResolver.providedBy(reactor):\n            warningString = deprecate.getDeprecationWarningString(\n                reactor.__class__,\n                Version('Twisted', 17, 5, 0),\n                format=(\"Passing HostnameEndpoint a reactor that does not\"\n                        \" provide IReactorPluggableNameResolver (%(fqpn)s)\"\n                        \" was deprecated in %(version)s\"),\n                replacement=(\"a reactor that provides\"\n                             \" IReactorPluggableNameResolver\"),\n            )\n            warnings.warn(warningString, DeprecationWarning, stacklevel=3)\n            return _SimpleHostnameResolver(self._fallbackNameResolution)\n        return reactor.nameResolver\n\n\n    @staticmethod\n    def _hostAsBytesAndText(host):\n        \"\"\"\n        For various reasons (documented in the C{@ivar}'s in the class\n        docstring) we need both a textual and a binary representation of the\n        hostname given to the constructor.  For compatibility and convenience,\n        we accept both textual and binary representations of the hostname, save\n        the form that was passed, and convert into the other form.  This is\n        mostly just because L{HostnameAddress} chose somewhat poorly to define\n        its attribute as bytes; hopefully we can find a compatible way to clean\n        this up in the future and just operate in terms of text internally.\n\n        @param host: A hostname to convert.\n        @type host: L{bytes} or C{str}\n\n        @return: a 3-tuple of C{(invalid, bytes, text)} where C{invalid} is a\n            boolean indicating the validity of the hostname, C{bytes} is a\n            binary representation of C{host}, and C{text} is a textual\n            representation of C{host}.\n        \"\"\"\n        if isinstance(host, bytes):\n            if isIPAddress(host) or isIPv6Address(host):\n                return False, host, host.decode(\"ascii\")\n            else:\n                try:\n                    return False, host, _idnaText(host)\n                except UnicodeError:\n                    # Convert the host to _some_ kind of text, to handle below.\n                    host = host.decode(\"charmap\")\n        else:\n            host = normalize('NFC', host)\n            if isIPAddress(host) or isIPv6Address(host):\n                return False, host.encode(\"ascii\"), host\n            else:\n                try:\n                    return False, _idnaBytes(host), host\n                except UnicodeError:\n                    pass\n        # `host` has been converted to text by this point either way; it's\n        # invalid as a hostname, and so may contain unprintable characters and\n        # such. escape it with backslashes so the user can get _some_ guess as\n        # to what went wrong.\n        asciibytes = host.encode('ascii', 'backslashreplace')\n        return True, asciibytes, asciibytes.decode('ascii')\n\n\n    def connect(self, protocolFactory):\n        \"\"\"\n        Attempts a connection to each resolved address, and returns a\n        connection which is established first.\n\n        @param protocolFactory: The protocol factory whose protocol\n            will be connected.\n        @type protocolFactory:\n            L{IProtocolFactory<twisted.internet.interfaces.IProtocolFactory>}\n\n        @return: A L{Deferred} that fires with the connected protocol\n            or fails a connection-related error.\n        \"\"\"\n        if self._badHostname:\n            return defer.fail(\n                ValueError(\"invalid hostname: {}\".format(self._hostStr))\n            )\n\n        d = Deferred()\n        addresses = []\n        @provider(IResolutionReceiver)\n        class EndpointReceiver(object):\n            @staticmethod\n            def resolutionBegan(resolutionInProgress):\n                pass\n            @staticmethod\n            def addressResolved(address):\n                addresses.append(address)\n            @staticmethod\n            def resolutionComplete():\n                d.callback(addresses)\n\n        self._nameResolver.resolveHostName(\n            EndpointReceiver, self._hostText, portNumber=self._port\n        )\n\n        d.addErrback(lambda ignored: defer.fail(error.DNSLookupError(\n            \"Couldn't find the hostname '{}'\".format(self._hostStr))))\n        @d.addCallback\n        def resolvedAddressesToEndpoints(addresses):\n            # Yield an endpoint for every address resolved from the name.\n            for eachAddress in addresses:\n                if isinstance(eachAddress, IPv6Address):\n                    yield TCP6ClientEndpoint(\n                        self._reactor, eachAddress.host, eachAddress.port,\n                        self._timeout, self._bindAddress\n                    )\n                if isinstance(eachAddress, IPv4Address):\n                    yield TCP4ClientEndpoint(\n                        self._reactor, eachAddress.host, eachAddress.port,\n                        self._timeout, self._bindAddress\n                    )\n        d.addCallback(list)\n\n        def _canceller(d):\n            # This canceller must remain defined outside of\n            # `startConnectionAttempts`, because Deferred should not\n            # participate in cycles with their cancellers; that would create a\n            # potentially problematic circular reference and possibly\n            # gc.garbage.\n            d.errback(error.ConnectingCancelledError(\n                HostnameAddress(self._hostBytes, self._port)))\n\n        @d.addCallback\n        def startConnectionAttempts(endpoints):\n            \"\"\"\n            Given a sequence of endpoints obtained via name resolution, start\n            connecting to a new one every C{self._attemptDelay} seconds until\n            one of the connections succeeds, all of them fail, or the attempt\n            is cancelled.\n\n            @param endpoints: a list of all the endpoints we might try to\n                connect to, as determined by name resolution.\n            @type endpoints: L{list} of L{IStreamServerEndpoint}\n\n            @return: a Deferred that fires with the result of the\n                C{endpoint.connect} method that completes the fastest, or fails\n                with the first connection error it encountered if none of them\n                succeed.\n            @rtype: L{Deferred} failing with L{error.ConnectingCancelledError}\n                or firing with L{IProtocol}\n            \"\"\"\n            if not endpoints:\n                raise error.DNSLookupError(\n                    \"no results for hostname lookup: {}\".format(self._hostStr)\n                )\n            iterEndpoints = iter(endpoints)\n            pending = []\n            failures = []\n            winner = defer.Deferred(canceller=_canceller)\n\n            def checkDone():\n                if pending or checkDone.completed or checkDone.endpointsLeft:\n                    return\n                winner.errback(failures.pop())\n            checkDone.completed = False\n            checkDone.endpointsLeft = True\n\n            @LoopingCall\n            def iterateEndpoint():\n                endpoint = next(iterEndpoints, None)\n                if endpoint is None:\n                    # The list of endpoints ends.\n                    checkDone.endpointsLeft = False\n                    checkDone()\n                    return\n\n                eachAttempt = endpoint.connect(protocolFactory)\n                pending.append(eachAttempt)\n                @eachAttempt.addBoth\n                def noLongerPending(result):\n                    pending.remove(eachAttempt)\n                    return result\n                @eachAttempt.addCallback\n                def succeeded(result):\n                    winner.callback(result)\n                @eachAttempt.addErrback\n                def failed(reason):\n                    failures.append(reason)\n                    checkDone()\n\n            iterateEndpoint.clock = self._reactor\n            iterateEndpoint.start(self._attemptDelay)\n\n            @winner.addBoth\n            def cancelRemainingPending(result):\n                checkDone.completed = True\n                for remaining in pending[:]:\n                    remaining.cancel()\n                if iterateEndpoint.running:\n                    iterateEndpoint.stop()\n                return result\n            return winner\n\n        return d\n\n\n    def _fallbackNameResolution(self, host, port):\n        \"\"\"\n        Resolve the hostname string into a tuple containing the host\n        address.  This is method is only used when the reactor does\n        not provide L{IReactorPluggableNameResolver}.\n\n        @param host: A unicode hostname to resolve.\n\n        @param port: The port to include in the resolution.\n\n        @return: A L{Deferred} that fires with L{_getaddrinfo}'s\n            return value.\n        \"\"\"\n        return self._deferToThread(self._getaddrinfo, host, port, 0,\n                socket.SOCK_STREAM)\n\n\n\n@implementer(interfaces.IStreamServerEndpoint)\nclass SSL4ServerEndpoint(object):\n    \"\"\"\n    SSL secured TCP server endpoint with an IPv4 configuration.\n    \"\"\"\n\n    def __init__(self, reactor, port, sslContextFactory,\n                 backlog=50, interface=''):\n        \"\"\"\n        @param reactor: An L{IReactorSSL} provider.\n\n        @param port: The port number used for listening\n        @type port: int\n\n        @param sslContextFactory: An instance of\n            L{interfaces.IOpenSSLContextFactory}.\n\n        @param backlog: Size of the listen queue\n        @type backlog: int\n\n        @param interface: The hostname to bind to, defaults to '' (all)\n        @type interface: str\n        \"\"\"\n        self._reactor = reactor\n        self._port = port\n        self._sslContextFactory = sslContextFactory\n        self._backlog = backlog\n        self._interface = interface\n\n\n    def listen(self, protocolFactory):\n        \"\"\"\n        Implement L{IStreamServerEndpoint.listen} to listen for SSL on a\n        TCP socket.\n        \"\"\"\n        return defer.execute(self._reactor.listenSSL, self._port,\n                             protocolFactory,\n                             contextFactory=self._sslContextFactory,\n                             backlog=self._backlog,\n                             interface=self._interface)\n\n\n\n@implementer(interfaces.IStreamClientEndpoint)\nclass SSL4ClientEndpoint(object):\n    \"\"\"\n    SSL secured TCP client endpoint with an IPv4 configuration\n    \"\"\"\n\n    def __init__(self, reactor, host, port, sslContextFactory,\n                 timeout=30, bindAddress=None):\n        \"\"\"\n        @param reactor: An L{IReactorSSL} provider.\n\n        @param host: A hostname, used when connecting\n        @type host: str\n\n        @param port: The port number, used when connecting\n        @type port: int\n\n        @param sslContextFactory: SSL Configuration information as an instance\n            of L{interfaces.IOpenSSLContextFactory}.\n\n        @param timeout: Number of seconds to wait before assuming the\n            connection has failed.\n        @type timeout: int\n\n        @param bindAddress: A (host, port) tuple of local address to bind to,\n            or None.\n        @type bindAddress: tuple\n        \"\"\"\n        self._reactor = reactor\n        self._host = host\n        self._port = port\n        self._sslContextFactory = sslContextFactory\n        self._timeout = timeout\n        self._bindAddress = bindAddress\n\n\n    def connect(self, protocolFactory):\n        \"\"\"\n        Implement L{IStreamClientEndpoint.connect} to connect with SSL over\n        TCP.\n        \"\"\"\n        try:\n            wf = _WrappingFactory(protocolFactory)\n            self._reactor.connectSSL(\n                self._host, self._port, wf, self._sslContextFactory,\n                timeout=self._timeout, bindAddress=self._bindAddress)\n            return wf._onConnection\n        except:\n            return defer.fail()\n\n\n\n@implementer(interfaces.IStreamServerEndpoint)\nclass UNIXServerEndpoint(object):\n    \"\"\"\n    UnixSocket server endpoint.\n    \"\"\"\n    def __init__(self, reactor, address, backlog=50, mode=0o666, wantPID=0):\n        \"\"\"\n        @param reactor: An L{IReactorUNIX} provider.\n        @param address: The path to the Unix socket file, used when listening\n        @param backlog: number of connections to allow in backlog.\n        @param mode: mode to set on the unix socket.  This parameter is\n            deprecated.  Permissions should be set on the directory which\n            contains the UNIX socket.\n        @param wantPID: If True, create a pidfile for the socket.\n        \"\"\"\n        self._reactor = reactor\n        self._address = address\n        self._backlog = backlog\n        self._mode = mode\n        self._wantPID = wantPID\n\n\n    def listen(self, protocolFactory):\n        \"\"\"\n        Implement L{IStreamServerEndpoint.listen} to listen on a UNIX socket.\n        \"\"\"\n        return defer.execute(self._reactor.listenUNIX, self._address,\n                             protocolFactory,\n                             backlog=self._backlog,\n                             mode=self._mode,\n                             wantPID=self._wantPID)\n\n\n\n@implementer(interfaces.IStreamClientEndpoint)\nclass UNIXClientEndpoint(object):\n    \"\"\"\n    UnixSocket client endpoint.\n    \"\"\"\n    def __init__(self, reactor, path, timeout=30, checkPID=0):\n        \"\"\"\n        @param reactor: An L{IReactorUNIX} provider.\n\n        @param path: The path to the Unix socket file, used when connecting\n        @type path: str\n\n        @param timeout: Number of seconds to wait before assuming the\n            connection has failed.\n        @type timeout: int\n\n        @param checkPID: If True, check for a pid file to verify that a server\n            is listening.\n        @type checkPID: bool\n        \"\"\"\n        self._reactor = reactor\n        self._path = path\n        self._timeout = timeout\n        self._checkPID = checkPID\n\n\n    def connect(self, protocolFactory):\n        \"\"\"\n        Implement L{IStreamClientEndpoint.connect} to connect via a\n        UNIX Socket\n        \"\"\"\n        try:\n            wf = _WrappingFactory(protocolFactory)\n            self._reactor.connectUNIX(\n                self._path, wf,\n                timeout=self._timeout,\n                checkPID=self._checkPID)\n            return wf._onConnection\n        except:\n            return defer.fail()\n\n\n\n@implementer(interfaces.IStreamServerEndpoint)\nclass AdoptedStreamServerEndpoint(object):\n    \"\"\"\n    An endpoint for listening on a file descriptor initialized outside of\n    Twisted.\n\n    @ivar _used: A C{bool} indicating whether this endpoint has been used to\n        listen with a factory yet.  C{True} if so.\n    \"\"\"\n    _close = os.close\n    _setNonBlocking = staticmethod(fdesc.setNonBlocking)\n\n    def __init__(self, reactor, fileno, addressFamily):\n        \"\"\"\n        @param reactor: An L{IReactorSocket} provider.\n\n        @param fileno: An integer file descriptor corresponding to a listening\n            I{SOCK_STREAM} socket.\n\n        @param addressFamily: The address family of the socket given by\n            C{fileno}.\n        \"\"\"\n        self.reactor = reactor\n        self.fileno = fileno\n        self.addressFamily = addressFamily\n        self._used = False\n\n\n    def listen(self, factory):\n        \"\"\"\n        Implement L{IStreamServerEndpoint.listen} to start listening on, and\n        then close, C{self._fileno}.\n        \"\"\"\n        if self._used:\n            return defer.fail(error.AlreadyListened())\n        self._used = True\n\n        try:\n            self._setNonBlocking(self.fileno)\n            port = self.reactor.adoptStreamPort(\n                self.fileno, self.addressFamily, factory)\n            self._close(self.fileno)\n        except:\n            return defer.fail()\n        return defer.succeed(port)\n\n\n\ndef _parseTCP(factory, port, interface=\"\", backlog=50):\n    \"\"\"\n    Internal parser function for L{_parseServer} to convert the string\n    arguments for a TCP(IPv4) stream endpoint into the structured arguments.\n\n    @param factory: the protocol factory being parsed, or L{None}.  (This was a\n        leftover argument from when this code was in C{strports}, and is now\n        mostly None and unused.)\n\n    @type factory: L{IProtocolFactory} or L{None}\n\n    @param port: the integer port number to bind\n    @type port: C{str}\n\n    @param interface: the interface IP to listen on\n    @param backlog: the length of the listen queue\n    @type backlog: C{str}\n\n    @return: a 2-tuple of (args, kwargs), describing  the parameters to\n        L{IReactorTCP.listenTCP} (or, modulo argument 2, the factory, arguments\n        to L{TCP4ServerEndpoint}.\n    \"\"\"\n    return (int(port), factory), {'interface': interface,\n                                  'backlog': int(backlog)}\n\n\n\ndef _parseUNIX(factory, address, mode='666', backlog=50, lockfile=True):\n    \"\"\"\n    Internal parser function for L{_parseServer} to convert the string\n    arguments for a UNIX (AF_UNIX/SOCK_STREAM) stream endpoint into the\n    structured arguments.\n\n    @param factory: the protocol factory being parsed, or L{None}.  (This was a\n        leftover argument from when this code was in C{strports}, and is now\n        mostly None and unused.)\n\n    @type factory: L{IProtocolFactory} or L{None}\n\n    @param address: the pathname of the unix socket\n    @type address: C{str}\n\n    @param backlog: the length of the listen queue\n    @type backlog: C{str}\n\n    @param lockfile: A string '0' or '1', mapping to True and False\n        respectively.  See the C{wantPID} argument to C{listenUNIX}\n\n    @return: a 2-tuple of (args, kwargs), describing  the parameters to\n        L{twisted.internet.interfaces.IReactorUNIX.listenUNIX} (or,\n        modulo argument 2, the factory, arguments to L{UNIXServerEndpoint}.\n    \"\"\"\n    return (\n        (address, factory),\n        {'mode': int(mode, 8), 'backlog': int(backlog),\n         'wantPID': bool(int(lockfile))})\n\n\n\ndef _parseSSL(factory, port, privateKey=\"server.pem\", certKey=None,\n              sslmethod=None, interface='', backlog=50, extraCertChain=None,\n              dhParameters=None):\n    \"\"\"\n    Internal parser function for L{_parseServer} to convert the string\n    arguments for an SSL (over TCP/IPv4) stream endpoint into the structured\n    arguments.\n\n    @param factory: the protocol factory being parsed, or L{None}.  (This was a\n        leftover argument from when this code was in C{strports}, and is now\n        mostly None and unused.)\n    @type factory: L{IProtocolFactory} or L{None}\n\n    @param port: the integer port number to bind\n    @type port: C{str}\n\n    @param interface: the interface IP to listen on\n    @param backlog: the length of the listen queue\n    @type backlog: C{str}\n\n    @param privateKey: The file name of a PEM format private key file.\n    @type privateKey: C{str}\n\n    @param certKey: The file name of a PEM format certificate file.\n    @type certKey: C{str}\n\n    @param sslmethod: The string name of an SSL method, based on the name of a\n        constant in C{OpenSSL.SSL}.  Must be one of: \"SSLv23_METHOD\",\n        \"SSLv2_METHOD\", \"SSLv3_METHOD\", \"TLSv1_METHOD\".\n    @type sslmethod: C{str}\n\n    @param extraCertChain: The path of a file containing one or more\n        certificates in PEM format that establish the chain from a root CA to\n        the CA that signed your C{certKey}.\n    @type extraCertChain: L{str}\n\n    @param dhParameters: The file name of a file containing parameters that are\n        required for Diffie-Hellman key exchange.  If this is not specified,\n        the forward secret C{DHE} ciphers aren't available for servers.\n    @type dhParameters: L{str}\n\n    @return: a 2-tuple of (args, kwargs), describing  the parameters to\n        L{IReactorSSL.listenSSL} (or, modulo argument 2, the factory, arguments\n        to L{SSL4ServerEndpoint}.\n    \"\"\"\n    from twisted.internet import ssl\n    if certKey is None:\n        certKey = privateKey\n    kw = {}\n    if sslmethod is not None:\n        kw['method'] = getattr(ssl.SSL, sslmethod)\n    certPEM = FilePath(certKey).getContent()\n    keyPEM = FilePath(privateKey).getContent()\n    privateCertificate = ssl.PrivateCertificate.loadPEM(\n        certPEM + b'\\n' + keyPEM)\n    if extraCertChain is not None:\n        matches = re.findall(\n            r'(-----BEGIN CERTIFICATE-----\\n.+?\\n-----END CERTIFICATE-----)',\n            nativeString(FilePath(extraCertChain).getContent()),\n            flags=re.DOTALL\n        )\n        chainCertificates = [ssl.Certificate.loadPEM(chainCertPEM).original\n                             for chainCertPEM in matches]\n        if not chainCertificates:\n            raise ValueError(\n                \"Specified chain file '%s' doesn't contain any valid \"\n                \"certificates in PEM format.\" % (extraCertChain,)\n            )\n    else:\n        chainCertificates = None\n    if dhParameters is not None:\n        dhParameters = ssl.DiffieHellmanParameters.fromFile(\n            FilePath(dhParameters),\n        )\n\n    cf = ssl.CertificateOptions(\n        privateKey=privateCertificate.privateKey.original,\n        certificate=privateCertificate.original,\n        extraCertChain=chainCertificates,\n        dhParameters=dhParameters,\n        **kw\n    )\n    return ((int(port), factory, cf),\n            {'interface': interface, 'backlog': int(backlog)})\n\n\n\n@implementer(IPlugin, IStreamServerEndpointStringParser)\nclass _StandardIOParser(object):\n    \"\"\"\n    Stream server endpoint string parser for the Standard I/O type.\n\n    @ivar prefix: See L{IStreamServerEndpointStringParser.prefix}.\n    \"\"\"\n    prefix = \"stdio\"\n\n    def _parseServer(self, reactor):\n        \"\"\"\n        Internal parser function for L{_parseServer} to convert the string\n        arguments into structured arguments for the L{StandardIOEndpoint}\n\n        @param reactor: Reactor for the endpoint\n        \"\"\"\n        return StandardIOEndpoint(reactor)\n\n\n    def parseStreamServer(self, reactor, *args, **kwargs):\n        # Redirects to another function (self._parseServer), tricks zope.interface\n        # into believing the interface is correctly implemented.\n        return self._parseServer(reactor)\n\n\n\n@implementer(IPlugin, IStreamServerEndpointStringParser)\nclass _SystemdParser(object):\n    \"\"\"\n    Stream server endpoint string parser for the I{systemd} endpoint type.\n\n    @ivar prefix: See L{IStreamServerEndpointStringParser.prefix}.\n\n    @ivar _sddaemon: A L{ListenFDs} instance used to translate an index into an\n        actual file descriptor.\n    \"\"\"\n    _sddaemon = ListenFDs.fromEnvironment()\n\n    prefix = \"systemd\"\n\n    def _parseServer(self, reactor, domain, index):\n        \"\"\"\n        Internal parser function for L{_parseServer} to convert the string\n        arguments for a systemd server endpoint into structured arguments for\n        L{AdoptedStreamServerEndpoint}.\n\n        @param reactor: An L{IReactorSocket} provider.\n\n        @param domain: The domain (or address family) of the socket inherited\n            from systemd.  This is a string like C{\"INET\"} or C{\"UNIX\"}, ie the\n            name of an address family from the L{socket} module, without the\n            C{\"AF_\"} prefix.\n        @type domain: C{str}\n\n        @param index: An offset into the list of file descriptors inherited from\n            systemd.\n        @type index: C{str}\n\n        @return: A two-tuple of parsed positional arguments and parsed keyword\n            arguments (a tuple and a dictionary).  These can be used to\n            construct an L{AdoptedStreamServerEndpoint}.\n        \"\"\"\n        index = int(index)\n        fileno = self._sddaemon.inheritedDescriptors()[index]\n        addressFamily = getattr(socket, 'AF_' + domain)\n        return AdoptedStreamServerEndpoint(reactor, fileno, addressFamily)\n\n\n    def parseStreamServer(self, reactor, *args, **kwargs):\n        # Delegate to another function with a sane signature.  This function has\n        # an insane signature to trick zope.interface into believing the\n        # interface is correctly implemented.\n        return self._parseServer(reactor, *args, **kwargs)\n\n\n\n@implementer(IPlugin, IStreamServerEndpointStringParser)\nclass _TCP6ServerParser(object):\n    \"\"\"\n    Stream server endpoint string parser for the TCP6ServerEndpoint type.\n\n    @ivar prefix: See L{IStreamServerEndpointStringParser.prefix}.\n    \"\"\"\n    prefix = \"tcp6\"     # Used in _parseServer to identify the plugin with the endpoint type\n\n    def _parseServer(self, reactor, port, backlog=50, interface='::'):\n        \"\"\"\n        Internal parser function for L{_parseServer} to convert the string\n        arguments into structured arguments for the L{TCP6ServerEndpoint}\n\n        @param reactor: An L{IReactorTCP} provider.\n\n        @param port: The port number used for listening\n        @type port: int\n\n        @param backlog: Size of the listen queue\n        @type backlog: int\n\n        @param interface: The hostname to bind to\n        @type interface: str\n        \"\"\"\n        port = int(port)\n        backlog = int(backlog)\n        return TCP6ServerEndpoint(reactor, port, backlog, interface)\n\n\n    def parseStreamServer(self, reactor, *args, **kwargs):\n        # Redirects to another function (self._parseServer), tricks zope.interface\n        # into believing the interface is correctly implemented.\n        return self._parseServer(reactor, *args, **kwargs)\n\n\n\n_serverParsers = {\"tcp\": _parseTCP,\n                  \"unix\": _parseUNIX,\n                  \"ssl\": _parseSSL,\n                  }\n\n_OP, _STRING = range(2)\n\ndef _tokenize(description):\n    \"\"\"\n    Tokenize a strports string and yield each token.\n\n    @param description: a string as described by L{serverFromString} or\n        L{clientFromString}.\n    @type description: L{str} or L{bytes}\n\n    @return: an iterable of 2-tuples of (C{_OP} or C{_STRING}, string).  Tuples\n        starting with C{_OP} will contain a second element of either ':' (i.e.\n        'next parameter') or '=' (i.e. 'assign parameter value').  For example,\n        the string 'hello:greeting=world' would result in a generator yielding\n        these values::\n\n            _STRING, 'hello'\n            _OP, ':'\n            _STRING, 'greet=ing'\n            _OP, '='\n            _STRING, 'world'\n    \"\"\"\n    empty = _matchingString(u'', description)\n    colon = _matchingString(u':', description)\n    equals = _matchingString(u'=', description)\n    backslash = _matchingString(u'\\x5c', description)\n    current = empty\n\n    ops = colon + equals\n    nextOps = {colon: colon + equals, equals: colon}\n    iterdesc = iter(iterbytes(description))\n    for n in iterdesc:\n        if n in iterbytes(ops):\n            yield _STRING, current\n            yield _OP, n\n            current = empty\n            ops = nextOps[n]\n        elif n == backslash:\n            current += next(iterdesc)\n        else:\n            current += n\n    yield _STRING, current\n\n\n\ndef _parse(description):\n    \"\"\"\n    Convert a description string into a list of positional and keyword\n    parameters, using logic vaguely like what Python does.\n\n    @param description: a string as described by L{serverFromString} or\n        L{clientFromString}.\n\n    @return: a 2-tuple of C{(args, kwargs)}, where 'args' is a list of all\n        ':'-separated C{str}s not containing an '=' and 'kwargs' is a map of\n        all C{str}s which do contain an '='.  For example, the result of\n        C{_parse('a:b:d=1:c')} would be C{(['a', 'b', 'c'], {'d': '1'})}.\n    \"\"\"\n    args, kw = [], {}\n    colon = _matchingString(u':', description)\n    def add(sofar):\n        if len(sofar) == 1:\n            args.append(sofar[0])\n        else:\n            kw[nativeString(sofar[0])] = sofar[1]\n    sofar = ()\n    for (type, value) in _tokenize(description):\n        if type is _STRING:\n            sofar += (value,)\n        elif value == colon:\n            add(sofar)\n            sofar = ()\n    add(sofar)\n    return args, kw\n\n\n# Mappings from description \"names\" to endpoint constructors.\n_endpointServerFactories = {\n    'TCP': TCP4ServerEndpoint,\n    'SSL': SSL4ServerEndpoint,\n    'UNIX': UNIXServerEndpoint,\n    }\n\n_endpointClientFactories = {\n    'TCP': TCP4ClientEndpoint,\n    'SSL': SSL4ClientEndpoint,\n    'UNIX': UNIXClientEndpoint,\n    }\n\n\ndef _parseServer(description, factory):\n    \"\"\"\n    Parse a strports description into a 2-tuple of arguments and keyword\n    values.\n\n    @param description: A description in the format explained by\n        L{serverFromString}.\n    @type description: C{str}\n\n    @param factory: A 'factory' argument; this is left-over from\n        twisted.application.strports, it's not really used.\n    @type factory: L{IProtocolFactory} or L{None}\n\n    @return: a 3-tuple of (plugin or name, arguments, keyword arguments)\n    \"\"\"\n    args, kw = _parse(description)\n    endpointType = args[0]\n    parser = _serverParsers.get(endpointType)\n    if parser is None:\n        # If the required parser is not found in _server, check if\n        # a plugin exists for the endpointType\n        plugin = _matchPluginToPrefix(\n            getPlugins(IStreamServerEndpointStringParser), endpointType\n        )\n        return (plugin, args[1:], kw)\n    return (endpointType.upper(),) + parser(factory, *args[1:], **kw)\n\n\n\ndef _matchPluginToPrefix(plugins, endpointType):\n    \"\"\"\n    Match plugin to prefix.\n    \"\"\"\n    endpointType = endpointType.lower()\n    for plugin in plugins:\n        if (_matchingString(plugin.prefix.lower(),\n                            endpointType) == endpointType):\n            return plugin\n    raise ValueError(\"Unknown endpoint type: '%s'\" % (endpointType,))\n\n\n\ndef serverFromString(reactor, description):\n    \"\"\"\n    Construct a stream server endpoint from an endpoint description string.\n\n    The format for server endpoint descriptions is a simple byte string.  It is\n    a prefix naming the type of endpoint, then a colon, then the arguments for\n    that endpoint.\n\n    For example, you can call it like this to create an endpoint that will\n    listen on TCP port 80::\n\n        serverFromString(reactor, \"tcp:80\")\n\n    Additional arguments may be specified as keywords, separated with colons.\n    For example, you can specify the interface for a TCP server endpoint to\n    bind to like this::\n\n        serverFromString(reactor, \"tcp:80:interface=127.0.0.1\")\n\n    SSL server endpoints may be specified with the 'ssl' prefix, and the\n    private key and certificate files may be specified by the C{privateKey} and\n    C{certKey} arguments::\n\n        serverFromString(\n            reactor, \"ssl:443:privateKey=key.pem:certKey=crt.pem\")\n\n    If a private key file name (C{privateKey}) isn't provided, a \"server.pem\"\n    file is assumed to exist which contains the private key. If the certificate\n    file name (C{certKey}) isn't provided, the private key file is assumed to\n    contain the certificate as well.\n\n    You may escape colons in arguments with a backslash, which you will need to\n    use if you want to specify a full pathname argument on Windows::\n\n        serverFromString(reactor,\n            \"ssl:443:privateKey=C\\\\:/key.pem:certKey=C\\\\:/cert.pem\")\n\n    finally, the 'unix' prefix may be used to specify a filesystem UNIX socket,\n    optionally with a 'mode' argument to specify the mode of the socket file\n    created by C{listen}::\n\n        serverFromString(reactor, \"unix:/var/run/finger\")\n        serverFromString(reactor, \"unix:/var/run/finger:mode=660\")\n\n    This function is also extensible; new endpoint types may be registered as\n    L{IStreamServerEndpointStringParser} plugins.  See that interface for more\n    information.\n\n    @param reactor: The server endpoint will be constructed with this reactor.\n\n    @param description: The strports description to parse.\n    @type description: L{str}\n\n    @return: A new endpoint which can be used to listen with the parameters\n        given by C{description}.\n\n    @rtype: L{IStreamServerEndpoint<twisted.internet.interfaces.IStreamServerEndpoint>}\n\n    @raise ValueError: when the 'description' string cannot be parsed.\n\n    @since: 10.2\n    \"\"\"\n    nameOrPlugin, args, kw = _parseServer(description, None)\n    if type(nameOrPlugin) is not str:\n        plugin = nameOrPlugin\n        return plugin.parseStreamServer(reactor, *args, **kw)\n    else:\n        name = nameOrPlugin\n    # Chop out the factory.\n    args = args[:1] + args[2:]\n    return _endpointServerFactories[name](reactor, *args, **kw)\n\n\n\ndef quoteStringArgument(argument):\n    \"\"\"\n    Quote an argument to L{serverFromString} and L{clientFromString}.  Since\n    arguments are separated with colons and colons are escaped with\n    backslashes, some care is necessary if, for example, you have a pathname,\n    you may be tempted to interpolate into a string like this::\n\n        serverFromString(reactor, \"ssl:443:privateKey=%s\" % (myPathName,))\n\n    This may appear to work, but will have portability issues (Windows\n    pathnames, for example).  Usually you should just construct the appropriate\n    endpoint type rather than interpolating strings, which in this case would\n    be L{SSL4ServerEndpoint}.  There are some use-cases where you may need to\n    generate such a string, though; for example, a tool to manipulate a\n    configuration file which has strports descriptions in it.  To be correct in\n    those cases, do this instead::\n\n        serverFromString(reactor, \"ssl:443:privateKey=%s\" %\n                         (quoteStringArgument(myPathName),))\n\n    @param argument: The part of the endpoint description string you want to\n        pass through.\n\n    @type argument: C{str}\n\n    @return: The quoted argument.\n\n    @rtype: C{str}\n    \"\"\"\n    backslash, colon = '\\\\:'\n    for c in backslash, colon:\n        argument = argument.replace(c, backslash + c)\n    return argument\n\n\n\ndef _parseClientTCP(*args, **kwargs):\n    \"\"\"\n    Perform any argument value coercion necessary for TCP client parameters.\n\n    Valid positional arguments to this function are host and port.\n\n    Valid keyword arguments to this function are all L{IReactorTCP.connectTCP}\n    arguments.\n\n    @return: The coerced values as a C{dict}.\n    \"\"\"\n\n    if len(args) == 2:\n        kwargs['port'] = int(args[1])\n        kwargs['host'] = args[0]\n    elif len(args) == 1:\n        if 'host' in kwargs:\n            kwargs['port'] = int(args[0])\n        else:\n            kwargs['host'] = args[0]\n\n    try:\n        kwargs['port'] = int(kwargs['port'])\n    except KeyError:\n        pass\n\n    try:\n        kwargs['timeout'] = int(kwargs['timeout'])\n    except KeyError:\n        pass\n\n    try:\n        kwargs['bindAddress'] = (kwargs['bindAddress'], 0)\n    except KeyError:\n        pass\n\n    return kwargs\n\n\n\ndef _loadCAsFromDir(directoryPath):\n    \"\"\"\n    Load certificate-authority certificate objects in a given directory.\n\n    @param directoryPath: a L{unicode} or L{bytes} pointing at a directory to\n        load .pem files from, or L{None}.\n\n    @return: an L{IOpenSSLTrustRoot} provider.\n    \"\"\"\n    caCerts = {}\n    for child in directoryPath.children():\n        if not child.asTextMode().basename().split(u'.')[-1].lower() == u'pem':\n            continue\n        try:\n            data = child.getContent()\n        except IOError:\n            # Permission denied, corrupt disk, we don't care.\n            continue\n        try:\n            theCert = Certificate.loadPEM(data)\n        except SSLError:\n            # Duplicate certificate, invalid certificate, etc.  We don't care.\n            pass\n        else:\n            caCerts[theCert.digest()] = theCert\n    return trustRootFromCertificates(caCerts.values())\n\n\n\ndef _parseTrustRootPath(pathName):\n    \"\"\"\n    Parse a string referring to a directory full of certificate authorities\n    into a trust root.\n\n    @param pathName: path name\n    @type pathName: L{unicode} or L{bytes} or L{None}\n\n    @return: L{None} or L{IOpenSSLTrustRoot}\n    \"\"\"\n    if pathName is None:\n        return None\n    return _loadCAsFromDir(FilePath(pathName))\n\n\n\ndef _privateCertFromPaths(certificatePath, keyPath):\n    \"\"\"\n    Parse a certificate path and key path, either or both of which might be\n    L{None}, into a certificate object.\n\n    @param certificatePath: the certificate path\n    @type certificatePath: L{bytes} or L{unicode} or L{None}\n\n    @param keyPath: the private key path\n    @type keyPath: L{bytes} or L{unicode} or L{None}\n\n    @return: a L{PrivateCertificate} or L{None}\n    \"\"\"\n    if certificatePath is None:\n        return None\n    certBytes = FilePath(certificatePath).getContent()\n    if keyPath is None:\n        return PrivateCertificate.loadPEM(certBytes)\n    else:\n        return PrivateCertificate.fromCertificateAndKeyPair(\n            Certificate.loadPEM(certBytes),\n            KeyPair.load(FilePath(keyPath).getContent(), 1)\n        )\n\n\n\ndef _parseClientSSLOptions(kwargs):\n    \"\"\"\n    Parse common arguments for SSL endpoints, creating an L{CertificateOptions}\n    instance.\n\n    @param kwargs: A dict of keyword arguments to be parsed, potentially\n        containing keys C{certKey}, C{privateKey}, C{caCertsDir}, and\n        C{hostname}.  See L{_parseClientSSL}.\n    @type kwargs: L{dict}\n\n    @return: The remaining arguments, including a new key C{sslContextFactory}.\n    \"\"\"\n    hostname = kwargs.pop('hostname', None)\n    clientCertificate = _privateCertFromPaths(kwargs.pop('certKey', None),\n                                              kwargs.pop('privateKey', None))\n    trustRoot = _parseTrustRootPath(kwargs.pop('caCertsDir', None))\n    if hostname is not None:\n        configuration = optionsForClientTLS(\n            _idnaText(hostname), trustRoot=trustRoot,\n            clientCertificate=clientCertificate\n        )\n    else:\n        # _really_ though, you should specify a hostname.\n        if clientCertificate is not None:\n            privateKeyOpenSSL = clientCertificate.privateKey.original\n            certificateOpenSSL = clientCertificate.original\n        else:\n            privateKeyOpenSSL = None\n            certificateOpenSSL = None\n        configuration = CertificateOptions(\n            trustRoot=trustRoot,\n            privateKey=privateKeyOpenSSL,\n            certificate=certificateOpenSSL,\n        )\n    kwargs['sslContextFactory'] = configuration\n    return kwargs\n\n\n\ndef _parseClientSSL(*args, **kwargs):\n    \"\"\"\n    Perform any argument value coercion necessary for SSL client parameters.\n\n    Valid keyword arguments to this function are all L{IReactorSSL.connectSSL}\n    arguments except for C{contextFactory}.  Instead, C{certKey} (the path name\n    of the certificate file) C{privateKey} (the path name of the private key\n    associated with the certificate) are accepted and used to construct a\n    context factory.\n\n    Valid positional arguments to this function are host and port.\n\n    @param caCertsDir: The one parameter which is not part of\n        L{IReactorSSL.connectSSL}'s signature, this is a path name used to\n        construct a list of certificate authority certificates.  The directory\n        will be scanned for files ending in C{.pem}, all of which will be\n        considered valid certificate authorities for this connection.\n\n    @type caCertsDir: L{str}\n\n    @param hostname: The hostname to use for validating the server's\n        certificate.\n    @type hostname: L{unicode}\n\n    @return: The coerced values as a L{dict}.\n    \"\"\"\n    kwargs = _parseClientTCP(*args, **kwargs)\n    return _parseClientSSLOptions(kwargs)\n\n\n\ndef _parseClientUNIX(*args, **kwargs):\n    \"\"\"\n    Perform any argument value coercion necessary for UNIX client parameters.\n\n    Valid keyword arguments to this function are all L{IReactorUNIX.connectUNIX}\n    keyword arguments except for C{checkPID}.  Instead, C{lockfile} is accepted\n    and has the same meaning.  Also C{path} is used instead of C{address}.\n\n    Valid positional arguments to this function are C{path}.\n\n    @return: The coerced values as a C{dict}.\n    \"\"\"\n    if len(args) == 1:\n        kwargs['path'] = args[0]\n\n    try:\n        kwargs['checkPID'] = bool(int(kwargs.pop('lockfile')))\n    except KeyError:\n        pass\n    try:\n        kwargs['timeout'] = int(kwargs['timeout'])\n    except KeyError:\n        pass\n    return kwargs\n\n_clientParsers = {\n    'TCP': _parseClientTCP,\n    'SSL': _parseClientSSL,\n    'UNIX': _parseClientUNIX,\n    }\n\n\n\ndef clientFromString(reactor, description):\n    \"\"\"\n    Construct a client endpoint from a description string.\n\n    Client description strings are much like server description strings,\n    although they take all of their arguments as keywords, aside from host and\n    port.\n\n    You can create a TCP client endpoint with the 'host' and 'port' arguments,\n    like so::\n\n        clientFromString(reactor, \"tcp:host=www.example.com:port=80\")\n\n    or, without specifying host and port keywords::\n\n        clientFromString(reactor, \"tcp:www.example.com:80\")\n\n    Or you can specify only one or the other, as in the following 2 examples::\n\n        clientFromString(reactor, \"tcp:host=www.example.com:80\")\n        clientFromString(reactor, \"tcp:www.example.com:port=80\")\n\n    or an SSL client endpoint with those arguments, plus the arguments used by\n    the server SSL, for a client certificate::\n\n        clientFromString(reactor, \"ssl:web.example.com:443:\"\n                                  \"privateKey=foo.pem:certKey=foo.pem\")\n\n    to specify your certificate trust roots, you can identify a directory with\n    PEM files in it with the C{caCertsDir} argument::\n\n        clientFromString(reactor, \"ssl:host=web.example.com:port=443:\"\n                                  \"caCertsDir=/etc/ssl/certs\")\n\n    Both TCP and SSL client endpoint description strings can include a\n    'bindAddress' keyword argument, whose value should be a local IPv4\n    address. This fixes the client socket to that IP address::\n\n        clientFromString(reactor, \"tcp:www.example.com:80:\"\n                                  \"bindAddress=192.0.2.100\")\n\n    NB: Fixed client ports are not currently supported in TCP or SSL\n    client endpoints. The client socket will always use an ephemeral\n    port assigned by the operating system\n\n    You can create a UNIX client endpoint with the 'path' argument and optional\n    'lockfile' and 'timeout' arguments::\n\n        clientFromString(\n            reactor, b\"unix:path=/var/foo/bar:lockfile=1:timeout=9\")\n\n    or, with the path as a positional argument with or without optional\n    arguments as in the following 2 examples::\n\n        clientFromString(reactor, \"unix:/var/foo/bar\")\n        clientFromString(reactor, \"unix:/var/foo/bar:lockfile=1:timeout=9\")\n\n    This function is also extensible; new endpoint types may be registered as\n    L{IStreamClientEndpointStringParserWithReactor} plugins.  See that\n    interface for more information.\n\n    @param reactor: The client endpoint will be constructed with this reactor.\n\n    @param description: The strports description to parse.\n    @type description: L{str}\n\n    @return: A new endpoint which can be used to connect with the parameters\n        given by C{description}.\n    @rtype: L{IStreamClientEndpoint<twisted.internet.interfaces.IStreamClientEndpoint>}\n\n    @since: 10.2\n    \"\"\"\n    args, kwargs = _parse(description)\n    aname = args.pop(0)\n    name = aname.upper()\n    if name not in _clientParsers:\n        plugin = _matchPluginToPrefix(\n            getPlugins(IStreamClientEndpointStringParserWithReactor), name\n        )\n        return plugin.parseStreamClient(reactor, *args, **kwargs)\n    kwargs = _clientParsers[name](*args, **kwargs)\n    return _endpointClientFactories[name](reactor, **kwargs)\n\n\n\ndef connectProtocol(endpoint, protocol):\n    \"\"\"\n    Connect a protocol instance to an endpoint.\n\n    This allows using a client endpoint without having to create a factory.\n\n    @param endpoint: A client endpoint to connect to.\n\n    @param protocol: A protocol instance.\n\n    @return: The result of calling C{connect} on the endpoint, i.e. a\n        L{Deferred} that will fire with the protocol when connected, or an\n        appropriate error.\n\n    @since: 13.1\n    \"\"\"\n    class OneShotFactory(Factory):\n        def buildProtocol(self, addr):\n            return protocol\n    return endpoint.connect(OneShotFactory())\n\n\n\n@implementer(interfaces.IStreamClientEndpoint)\nclass _WrapperEndpoint(object):\n    \"\"\"\n    An endpoint that wraps another endpoint.\n    \"\"\"\n\n    def __init__(self, wrappedEndpoint, wrapperFactory):\n        \"\"\"\n        Construct a L{_WrapperEndpoint}.\n        \"\"\"\n        self._wrappedEndpoint = wrappedEndpoint\n        self._wrapperFactory = wrapperFactory\n\n\n    def connect(self, protocolFactory):\n        \"\"\"\n        Connect the given protocol factory and unwrap its result.\n        \"\"\"\n        return self._wrappedEndpoint.connect(\n            self._wrapperFactory(protocolFactory)\n        ).addCallback(lambda protocol: protocol.wrappedProtocol)\n\n\n\n@implementer(interfaces.IStreamServerEndpoint)\nclass _WrapperServerEndpoint(object):\n    \"\"\"\n    A server endpoint that wraps another server endpoint.\n    \"\"\"\n\n    def __init__(self, wrappedEndpoint, wrapperFactory):\n        \"\"\"\n        Construct a L{_WrapperServerEndpoint}.\n        \"\"\"\n        self._wrappedEndpoint = wrappedEndpoint\n        self._wrapperFactory = wrapperFactory\n\n\n    def listen(self, protocolFactory):\n        \"\"\"\n        Connect the given protocol factory and unwrap its result.\n        \"\"\"\n        return self._wrappedEndpoint.listen(\n            self._wrapperFactory(protocolFactory)\n        )\n\n\n\ndef wrapClientTLS(connectionCreator, wrappedEndpoint):\n    \"\"\"\n    Wrap an endpoint which upgrades to TLS as soon as the connection is\n    established.\n\n    @since: 16.0\n\n    @param connectionCreator: The TLS options to use when connecting; see\n        L{twisted.internet.ssl.optionsForClientTLS} for how to construct this.\n    @type connectionCreator:\n        L{twisted.internet.interfaces.IOpenSSLClientConnectionCreator}\n\n    @param wrappedEndpoint: The endpoint to wrap.\n    @type wrappedEndpoint: An L{IStreamClientEndpoint} provider.\n\n    @return: an endpoint that provides transport level encryption layered on\n        top of C{wrappedEndpoint}\n    @rtype: L{twisted.internet.interfaces.IStreamClientEndpoint}\n    \"\"\"\n    if TLSMemoryBIOFactory is None:\n        raise NotImplementedError(\n            \"OpenSSL not available. Try `pip install twisted[tls]`.\"\n        )\n    return _WrapperEndpoint(\n        wrappedEndpoint,\n        lambda protocolFactory:\n        TLSMemoryBIOFactory(connectionCreator, True, protocolFactory)\n    )\n\n\n\ndef _parseClientTLS(reactor, host, port, timeout=b'30', bindAddress=None,\n                    certificate=None, privateKey=None, trustRoots=None,\n                    endpoint=None, **kwargs):\n    \"\"\"\n    Internal method to construct an endpoint from string parameters.\n\n    @param reactor: The reactor passed to L{clientFromString}.\n\n    @param host: The hostname to connect to.\n    @type host: L{bytes} or L{unicode}\n\n    @param port: The port to connect to.\n    @type port: L{bytes} or L{unicode}\n\n    @param timeout: For each individual connection attempt, the number of\n        seconds to wait before assuming the connection has failed.\n    @type timeout: L{bytes} or L{unicode}\n\n    @param bindAddress: The address to which to bind outgoing connections.\n    @type bindAddress: L{bytes} or L{unicode}\n\n    @param certificate: a string representing a filesystem path to a\n        PEM-encoded certificate.\n    @type certificate: L{bytes} or L{unicode}\n\n    @param privateKey: a string representing a filesystem path to a PEM-encoded\n        certificate.\n    @type privateKey: L{bytes} or L{unicode}\n\n    @param endpoint: an optional string endpoint description of an endpoint to\n        wrap; if this is passed then C{host} is used only for certificate\n        verification.\n    @type endpoint: L{bytes} or L{unicode}\n\n    @return: a client TLS endpoint\n    @rtype: L{IStreamClientEndpoint}\n    \"\"\"\n    if kwargs:\n        raise TypeError('unrecognized keyword arguments present',\n                        list(kwargs.keys()))\n    host = host if isinstance(host, unicode) else host.decode(\"utf-8\")\n    bindAddress = (bindAddress\n                   if isinstance(bindAddress, unicode) or bindAddress is None\n                   else bindAddress.decode(\"utf-8\"))\n    port = int(port)\n    timeout = int(timeout)\n    return wrapClientTLS(\n        optionsForClientTLS(\n            host, trustRoot=_parseTrustRootPath(trustRoots),\n            clientCertificate=_privateCertFromPaths(certificate,\n                                                    privateKey)),\n        clientFromString(reactor, endpoint) if endpoint is not None\n        else HostnameEndpoint(reactor, _idnaBytes(host), port, timeout,\n                              bindAddress)\n    )\n\n\n\n@implementer(IPlugin, IStreamClientEndpointStringParserWithReactor)\nclass _TLSClientEndpointParser(object):\n    \"\"\"\n    Stream client endpoint string parser for L{wrapClientTLS} with\n    L{HostnameEndpoint}.\n\n    @ivar prefix: See\n        L{IStreamClientEndpointStringParserWithReactor.prefix}.\n    \"\"\"\n    prefix = 'tls'\n\n    @staticmethod\n    def parseStreamClient(reactor, *args, **kwargs):\n        \"\"\"\n        Redirects to another function L{_parseClientTLS}; tricks zope.interface\n        into believing the interface is correctly implemented, since the\n        signature is (C{reactor}, C{*args}, C{**kwargs}).  See\n        L{_parseClientTLS} for the specific signature description for this\n        endpoint parser.\n\n        @param reactor: The reactor passed to L{clientFromString}.\n\n        @param args: The positional arguments in the endpoint description.\n        @type args: L{tuple}\n\n        @param kwargs: The named arguments in the endpoint description.\n        @type kwargs: L{dict}\n\n        @return: a client TLS endpoint\n        @rtype: L{IStreamClientEndpoint}\n        \"\"\"\n        return _parseClientTLS(reactor, *args, **kwargs)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/epollreactor.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAn epoll() based implementation of the twisted main loop.\n\nTo install the event loop (and you should do this before any connections,\nlisteners or connectors are added)::\n\n    from twisted.internet import epollreactor\n    epollreactor.install()\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom select import epoll, EPOLLHUP, EPOLLERR, EPOLLIN, EPOLLOUT\nimport errno\n\nfrom zope.interface import implementer\n\nfrom twisted.internet.interfaces import IReactorFDSet\n\nfrom twisted.python import log\nfrom twisted.internet import posixbase\n\n\n@implementer(IReactorFDSet)\nclass EPollReactor(posixbase.PosixReactorBase, posixbase._PollLikeMixin):\n    \"\"\"\n    A reactor that uses epoll(7).\n\n    @ivar _poller: A C{epoll} which will be used to check for I/O\n        readiness.\n\n    @ivar _selectables: A dictionary mapping integer file descriptors to\n        instances of C{FileDescriptor} which have been registered with the\n        reactor.  All C{FileDescriptors} which are currently receiving read or\n        write readiness notifications will be present as values in this\n        dictionary.\n\n    @ivar _reads: A set containing integer file descriptors.  Values in this\n        set will be registered with C{_poller} for read readiness notifications\n        which will be dispatched to the corresponding C{FileDescriptor}\n        instances in C{_selectables}.\n\n    @ivar _writes: A set containing integer file descriptors.  Values in this\n        set will be registered with C{_poller} for write readiness\n        notifications which will be dispatched to the corresponding\n        C{FileDescriptor} instances in C{_selectables}.\n\n    @ivar _continuousPolling: A L{_ContinuousPolling} instance, used to handle\n        file descriptors (e.g. filesystem files) that are not supported by\n        C{epoll(7)}.\n    \"\"\"\n\n    # Attributes for _PollLikeMixin\n    _POLL_DISCONNECTED = (EPOLLHUP | EPOLLERR)\n    _POLL_IN = EPOLLIN\n    _POLL_OUT = EPOLLOUT\n\n    def __init__(self):\n        \"\"\"\n        Initialize epoll object, file descriptor tracking dictionaries, and the\n        base class.\n        \"\"\"\n        # Create the poller we're going to use.  The 1024 here is just a hint\n        # to the kernel, it is not a hard maximum.  After Linux 2.6.8, the size\n        # argument is completely ignored.\n        self._poller = epoll(1024)\n        self._reads = set()\n        self._writes = set()\n        self._selectables = {}\n        self._continuousPolling = posixbase._ContinuousPolling(self)\n        posixbase.PosixReactorBase.__init__(self)\n\n\n    def _add(self, xer, primary, other, selectables, event, antievent):\n        \"\"\"\n        Private method for adding a descriptor from the event loop.\n\n        It takes care of adding it if  new or modifying it if already added\n        for another state (read -> read/write for example).\n        \"\"\"\n        fd = xer.fileno()\n        if fd not in primary:\n            flags = event\n            # epoll_ctl can raise all kinds of IOErrors, and every one\n            # indicates a bug either in the reactor or application-code.\n            # Let them all through so someone sees a traceback and fixes\n            # something.  We'll do the same thing for every other call to\n            # this method in this file.\n            if fd in other:\n                flags |= antievent\n                self._poller.modify(fd, flags)\n            else:\n                self._poller.register(fd, flags)\n\n            # Update our own tracking state *only* after the epoll call has\n            # succeeded.  Otherwise we may get out of sync.\n            primary.add(fd)\n            selectables[fd] = xer\n\n\n    def addReader(self, reader):\n        \"\"\"\n        Add a FileDescriptor for notification of data available to read.\n        \"\"\"\n        try:\n            self._add(reader, self._reads, self._writes, self._selectables,\n                      EPOLLIN, EPOLLOUT)\n        except IOError as e:\n            if e.errno == errno.EPERM:\n                # epoll(7) doesn't support certain file descriptors,\n                # e.g. filesystem files, so for those we just poll\n                # continuously:\n                self._continuousPolling.addReader(reader)\n            else:\n                raise\n\n\n    def addWriter(self, writer):\n        \"\"\"\n        Add a FileDescriptor for notification of data available to write.\n        \"\"\"\n        try:\n            self._add(writer, self._writes, self._reads, self._selectables,\n                      EPOLLOUT, EPOLLIN)\n        except IOError as e:\n            if e.errno == errno.EPERM:\n                # epoll(7) doesn't support certain file descriptors,\n                # e.g. filesystem files, so for those we just poll\n                # continuously:\n                self._continuousPolling.addWriter(writer)\n            else:\n                raise\n\n\n    def _remove(self, xer, primary, other, selectables, event, antievent):\n        \"\"\"\n        Private method for removing a descriptor from the event loop.\n\n        It does the inverse job of _add, and also add a check in case of the fd\n        has gone away.\n        \"\"\"\n        fd = xer.fileno()\n        if fd == -1:\n            for fd, fdes in selectables.items():\n                if xer is fdes:\n                    break\n            else:\n                return\n        if fd in primary:\n            if fd in other:\n                flags = antievent\n                # See comment above modify call in _add.\n                self._poller.modify(fd, flags)\n            else:\n                del selectables[fd]\n                # See comment above _control call in _add.\n                self._poller.unregister(fd)\n            primary.remove(fd)\n\n\n    def removeReader(self, reader):\n        \"\"\"\n        Remove a Selectable for notification of data available to read.\n        \"\"\"\n        if self._continuousPolling.isReading(reader):\n            self._continuousPolling.removeReader(reader)\n            return\n        self._remove(reader, self._reads, self._writes, self._selectables,\n                     EPOLLIN, EPOLLOUT)\n\n\n    def removeWriter(self, writer):\n        \"\"\"\n        Remove a Selectable for notification of data available to write.\n        \"\"\"\n        if self._continuousPolling.isWriting(writer):\n            self._continuousPolling.removeWriter(writer)\n            return\n        self._remove(writer, self._writes, self._reads, self._selectables,\n                     EPOLLOUT, EPOLLIN)\n\n\n    def removeAll(self):\n        \"\"\"\n        Remove all selectables, and return a list of them.\n        \"\"\"\n        return (self._removeAll(\n                [self._selectables[fd] for fd in self._reads],\n                [self._selectables[fd] for fd in self._writes]) +\n                self._continuousPolling.removeAll())\n\n\n    def getReaders(self):\n        return ([self._selectables[fd] for fd in self._reads] +\n                self._continuousPolling.getReaders())\n\n\n    def getWriters(self):\n        return ([self._selectables[fd] for fd in self._writes] +\n                self._continuousPolling.getWriters())\n\n\n    def doPoll(self, timeout):\n        \"\"\"\n        Poll the poller for new events.\n        \"\"\"\n        if timeout is None:\n            timeout = -1  # Wait indefinitely.\n\n        try:\n            # Limit the number of events to the number of io objects we're\n            # currently tracking (because that's maybe a good heuristic) and\n            # the amount of time we block to the value specified by our\n            # caller.\n            l = self._poller.poll(timeout, len(self._selectables))\n        except IOError as err:\n            if err.errno == errno.EINTR:\n                return\n            # See epoll_wait(2) for documentation on the other conditions\n            # under which this can fail.  They can only be due to a serious\n            # programming error on our part, so let's just announce them\n            # loudly.\n            raise\n\n        _drdw = self._doReadOrWrite\n        for fd, event in l:\n            try:\n                selectable = self._selectables[fd]\n            except KeyError:\n                pass\n            else:\n                log.callWithLogger(selectable, _drdw, selectable, fd, event)\n\n    doIteration = doPoll\n\n\ndef install():\n    \"\"\"\n    Install the epoll() reactor.\n    \"\"\"\n    p = EPollReactor()\n    from twisted.internet.main import installReactor\n    installReactor(p)\n\n\n__all__ = [\"EPollReactor\", \"install\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/error.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nExceptions and errors for use in twisted.internet modules.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport socket\n\nfrom twisted.python import deprecate\nfrom incremental import Version\n\n\n\nclass BindError(Exception):\n    \"\"\"An error occurred binding to an interface\"\"\"\n\n    def __str__(self):\n        s = self.__doc__\n        if self.args:\n            s = '%s: %s' % (s, ' '.join(self.args))\n        s = '%s.' % s\n        return s\n\n\n\nclass CannotListenError(BindError):\n    \"\"\"\n    This gets raised by a call to startListening, when the object cannotstart\n    listening.\n\n    @ivar interface: the interface I tried to listen on\n    @ivar port: the port I tried to listen on\n    @ivar socketError: the exception I got when I tried to listen\n    @type socketError: L{socket.error}\n    \"\"\"\n    def __init__(self, interface, port, socketError):\n        BindError.__init__(self, interface, port, socketError)\n        self.interface = interface\n        self.port = port\n        self.socketError = socketError\n\n    def __str__(self):\n        iface = self.interface or 'any'\n        return \"Couldn't listen on %s:%s: %s.\" % (iface, self.port,\n                                                 self.socketError)\n\n\n\nclass MulticastJoinError(Exception):\n    \"\"\"\n    An attempt to join a multicast group failed.\n    \"\"\"\n\n\n\nclass MessageLengthError(Exception):\n    \"\"\"Message is too long to send\"\"\"\n\n    def __str__(self):\n        s = self.__doc__\n        if self.args:\n            s = '%s: %s' % (s, ' '.join(self.args))\n        s = '%s.' % s\n        return s\n\n\n\nclass DNSLookupError(IOError):\n    \"\"\"DNS lookup failed\"\"\"\n\n    def __str__(self):\n        s = self.__doc__\n        if self.args:\n            s = '%s: %s' % (s, ' '.join(self.args))\n        s = '%s.' % s\n        return s\n\n\n\nclass ConnectInProgressError(Exception):\n    \"\"\"A connect operation was started and isn't done yet.\"\"\"\n\n\n# connection errors\n\nclass ConnectError(Exception):\n    \"\"\"An error occurred while connecting\"\"\"\n\n    def __init__(self, osError=None, string=\"\"):\n        self.osError = osError\n        Exception.__init__(self, string)\n\n    def __str__(self):\n        s = self.__doc__ or self.__class__.__name__\n        if self.osError:\n            s = '%s: %s' % (s, self.osError)\n        if self.args[0]:\n            s = '%s: %s' % (s, self.args[0])\n        s = '%s.' % s\n        return s\n\n\n\nclass ConnectBindError(ConnectError):\n    \"\"\"Couldn't bind\"\"\"\n\n\n\nclass UnknownHostError(ConnectError):\n    \"\"\"Hostname couldn't be looked up\"\"\"\n\n\n\nclass NoRouteError(ConnectError):\n    \"\"\"No route to host\"\"\"\n\n\n\nclass ConnectionRefusedError(ConnectError):\n    \"\"\"Connection was refused by other side\"\"\"\n\n\n\nclass TCPTimedOutError(ConnectError):\n    \"\"\"TCP connection timed out\"\"\"\n\n\n\nclass BadFileError(ConnectError):\n    \"\"\"File used for UNIX socket is no good\"\"\"\n\n\n\nclass ServiceNameUnknownError(ConnectError):\n    \"\"\"Service name given as port is unknown\"\"\"\n\n\n\nclass UserError(ConnectError):\n    \"\"\"User aborted connection\"\"\"\n\n\n\nclass TimeoutError(UserError):\n    \"\"\"User timeout caused connection failure\"\"\"\n\n\n\nclass SSLError(ConnectError):\n    \"\"\"An SSL error occurred\"\"\"\n\n\n\nclass VerifyError(Exception):\n    \"\"\"Could not verify something that was supposed to be signed.\n    \"\"\"\n\n\n\nclass PeerVerifyError(VerifyError):\n    \"\"\"The peer rejected our verify error.\n    \"\"\"\n\n\n\nclass CertificateError(Exception):\n    \"\"\"\n    We did not find a certificate where we expected to find one.\n    \"\"\"\n\n\n\ntry:\n    import errno\n    errnoMapping = {\n        errno.ENETUNREACH: NoRouteError,\n        errno.ECONNREFUSED: ConnectionRefusedError,\n        errno.ETIMEDOUT: TCPTimedOutError,\n    }\n    if hasattr(errno, \"WSAECONNREFUSED\"):\n        errnoMapping[errno.WSAECONNREFUSED] = ConnectionRefusedError\n        errnoMapping[errno.WSAENETUNREACH] = NoRouteError\nexcept ImportError:\n    errnoMapping = {}\n\n\n\ndef getConnectError(e):\n    \"\"\"Given a socket exception, return connection error.\"\"\"\n    if isinstance(e, Exception):\n        args = e.args\n    else:\n        args = e\n    try:\n        number, string = args\n    except ValueError:\n        return ConnectError(string=e)\n\n    if hasattr(socket, 'gaierror') and isinstance(e, socket.gaierror):\n        # Only works in 2.2 in newer. Really that means always; #5978 covers\n        # this and other weirdnesses in this function.\n        klass = UnknownHostError\n    else:\n        klass = errnoMapping.get(number, ConnectError)\n    return klass(number, string)\n\n\n\nclass ConnectionClosed(Exception):\n    \"\"\"\n    Connection was closed, whether cleanly or non-cleanly.\n    \"\"\"\n\n\n\nclass ConnectionLost(ConnectionClosed):\n    \"\"\"Connection to the other side was lost in a non-clean fashion\"\"\"\n\n    def __str__(self):\n        s = self.__doc__.strip().splitlines()[0]\n        if self.args:\n            s = '%s: %s' % (s, ' '.join(self.args))\n        s = '%s.' % s\n        return s\n\n\n\nclass ConnectionAborted(ConnectionLost):\n    \"\"\"\n    Connection was aborted locally, using\n    L{twisted.internet.interfaces.ITCPTransport.abortConnection}.\n\n    @since: 11.1\n    \"\"\"\n\n    def __str__(self):\n        s = [(\n            \"Connection was aborted locally using\"\n            \" ITCPTransport.abortConnection\"\n        )]\n        if self.args:\n            s.append(': ')\n            s.append(' '.join(self.args))\n        s.append('.')\n        return ''.join(s)\n\n\n\nclass ConnectionDone(ConnectionClosed):\n    \"\"\"Connection was closed cleanly\"\"\"\n\n    def __str__(self):\n        s = self.__doc__\n        if self.args:\n            s = '%s: %s' % (s, ' '.join(self.args))\n        s = '%s.' % s\n        return s\n\n\n\nclass FileDescriptorOverrun(ConnectionLost):\n    \"\"\"\n    A mis-use of L{IUNIXTransport.sendFileDescriptor} caused the connection to\n    be closed.\n\n    Each file descriptor sent using C{sendFileDescriptor} must be associated\n    with at least one byte sent using L{ITransport.write}.  If at any point\n    fewer bytes have been written than file descriptors have been sent, the\n    connection is closed with this exception.\n    \"\"\"\n\n\n\nclass ConnectionFdescWentAway(ConnectionLost):\n    \"\"\"Uh\"\"\" #TODO\n\n\n\nclass AlreadyCalled(ValueError):\n    \"\"\"Tried to cancel an already-called event\"\"\"\n\n    def __str__(self):\n        s = self.__doc__\n        if self.args:\n            s = '%s: %s' % (s, ' '.join(self.args))\n        s = '%s.' % s\n        return s\n\n\n\nclass AlreadyCancelled(ValueError):\n    \"\"\"Tried to cancel an already-cancelled event\"\"\"\n\n    def __str__(self):\n        s = self.__doc__\n        if self.args:\n            s = '%s: %s' % (s, ' '.join(self.args))\n        s = '%s.' % s\n        return s\n\n\n\nclass PotentialZombieWarning(Warning):\n    \"\"\"\n    Emitted when L{IReactorProcess.spawnProcess} is called in a way which may\n    result in termination of the created child process not being reported.\n\n    Deprecated in Twisted 10.0.\n    \"\"\"\n    MESSAGE = (\n        \"spawnProcess called, but the SIGCHLD handler is not \"\n        \"installed. This probably means you have not yet \"\n        \"called reactor.run, or called \"\n        \"reactor.run(installSignalHandler=0). You will probably \"\n        \"never see this process finish, and it may become a \"\n        \"zombie process.\")\n\ndeprecate.deprecatedModuleAttribute(\n    Version(\"Twisted\", 10, 0, 0),\n    \"There is no longer any potential for zombie process.\",\n    __name__,\n    \"PotentialZombieWarning\")\n\n\n\nclass ProcessDone(ConnectionDone):\n    \"\"\"A process has ended without apparent errors\"\"\"\n\n    def __init__(self, status):\n        Exception.__init__(self, \"process finished with exit code 0\")\n        self.exitCode = 0\n        self.signal = None\n        self.status = status\n\n\n\nclass ProcessTerminated(ConnectionLost):\n    \"\"\"\n    A process has ended with a probable error condition\n\n    @ivar exitCode: See L{__init__}\n    @ivar signal: See L{__init__}\n    @ivar status: See L{__init__}\n    \"\"\"\n    def __init__(self, exitCode=None, signal=None, status=None):\n        \"\"\"\n        @param exitCode: The exit status of the process.  This is roughly like\n            the value you might pass to L{os.exit}.  This is L{None} if the\n            process exited due to a signal.\n        @type exitCode: L{int} or L{None}\n\n        @param signal: The exit signal of the process.  This is L{None} if the\n            process did not exit due to a signal.\n        @type signal: L{int} or L{None}\n\n        @param status: The exit code of the process.  This is a platform\n            specific combination of the exit code and the exit signal.  See\n            L{os.WIFEXITED} and related functions.\n        @type status: L{int}\n        \"\"\"\n        self.exitCode = exitCode\n        self.signal = signal\n        self.status = status\n        s = \"process ended\"\n        if exitCode is not None: s = s + \" with exit code %s\" % exitCode\n        if signal is not None: s = s + \" by signal %s\" % signal\n        Exception.__init__(self, s)\n\n\n\nclass ProcessExitedAlready(Exception):\n    \"\"\"\n    The process has already exited and the operation requested can no longer\n    be performed.\n    \"\"\"\n\n\n\nclass NotConnectingError(RuntimeError):\n    \"\"\"The Connector was not connecting when it was asked to stop connecting\"\"\"\n\n    def __str__(self):\n        s = self.__doc__\n        if self.args:\n            s = '%s: %s' % (s, ' '.join(self.args))\n        s = '%s.' % s\n        return s\n\n\n\nclass NotListeningError(RuntimeError):\n    \"\"\"The Port was not listening when it was asked to stop listening\"\"\"\n\n    def __str__(self):\n        s = self.__doc__\n        if self.args:\n            s = '%s: %s' % (s, ' '.join(self.args))\n        s = '%s.' % s\n        return s\n\n\n\nclass ReactorNotRunning(RuntimeError):\n    \"\"\"\n    Error raised when trying to stop a reactor which is not running.\n    \"\"\"\n\n\nclass ReactorNotRestartable(RuntimeError):\n    \"\"\"\n    Error raised when trying to run a reactor which was stopped.\n    \"\"\"\n\n\n\nclass ReactorAlreadyRunning(RuntimeError):\n    \"\"\"\n    Error raised when trying to start the reactor multiple times.\n    \"\"\"\n\n\nclass ReactorAlreadyInstalledError(AssertionError):\n    \"\"\"\n    Could not install reactor because one is already installed.\n    \"\"\"\n\n\n\nclass ConnectingCancelledError(Exception):\n    \"\"\"\n    An C{Exception} that will be raised when an L{IStreamClientEndpoint} is\n    cancelled before it connects.\n\n    @ivar address: The L{IAddress} that is the destination of the\n        cancelled L{IStreamClientEndpoint}.\n    \"\"\"\n\n    def __init__(self, address):\n        \"\"\"\n        @param address: The L{IAddress} that is the destination of the\n            L{IStreamClientEndpoint} that was cancelled.\n        \"\"\"\n        Exception.__init__(self, address)\n        self.address = address\n\n\n\nclass NoProtocol(Exception):\n    \"\"\"\n    An C{Exception} that will be raised when the factory given to a\n    L{IStreamClientEndpoint} returns L{None} from C{buildProtocol}.\n    \"\"\"\n\n\n\nclass UnsupportedAddressFamily(Exception):\n    \"\"\"\n    An attempt was made to use a socket with an address family (eg I{AF_INET},\n    I{AF_INET6}, etc) which is not supported by the reactor.\n    \"\"\"\n\n\n\nclass UnsupportedSocketType(Exception):\n    \"\"\"\n    An attempt was made to use a socket of a type (eg I{SOCK_STREAM},\n    I{SOCK_DGRAM}, etc) which is not supported by the reactor.\n    \"\"\"\n\n\nclass AlreadyListened(Exception):\n    \"\"\"\n    An attempt was made to listen on a file descriptor which can only be\n    listened on once.\n    \"\"\"\n\n\n\nclass InvalidAddressError(ValueError):\n    \"\"\"\n    An invalid address was specified (i.e. neither IPv4 or IPv6, or expected\n    one and got the other).\n\n    @ivar address: See L{__init__}\n    @ivar message: See L{__init__}\n    \"\"\"\n\n    def __init__(self, address, message):\n        \"\"\"\n        @param address: The address that was provided.\n        @type address: L{bytes}\n        @param message: A native string of additional information provided by\n            the calling context.\n        @type address: L{str}\n        \"\"\"\n        self.address = address\n        self.message = message\n\n\n\n__all__ = [\n    'BindError', 'CannotListenError', 'MulticastJoinError',\n    'MessageLengthError', 'DNSLookupError', 'ConnectInProgressError',\n    'ConnectError', 'ConnectBindError', 'UnknownHostError', 'NoRouteError',\n    'ConnectionRefusedError', 'TCPTimedOutError', 'BadFileError',\n    'ServiceNameUnknownError', 'UserError', 'TimeoutError', 'SSLError',\n    'VerifyError', 'PeerVerifyError', 'CertificateError',\n    'getConnectError', 'ConnectionClosed', 'ConnectionLost',\n    'ConnectionDone', 'ConnectionFdescWentAway', 'AlreadyCalled',\n    'AlreadyCancelled', 'PotentialZombieWarning', 'ProcessDone',\n    'ProcessTerminated', 'ProcessExitedAlready', 'NotConnectingError',\n    'NotListeningError', 'ReactorNotRunning', 'ReactorAlreadyRunning',\n    'ReactorAlreadyInstalledError', 'ConnectingCancelledError',\n    'UnsupportedAddressFamily', 'UnsupportedSocketType', 'InvalidAddressError']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/fdesc.py",
    "content": "# -*- test-case-name: twisted.test.test_fdesc -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nUtility functions for dealing with POSIX file descriptors.\n\"\"\"\n\nimport os\nimport errno\ntry:\n    import fcntl\nexcept ImportError:\n    fcntl = None\n\n# twisted imports\nfrom twisted.internet.main import CONNECTION_LOST, CONNECTION_DONE\n\n\ndef setNonBlocking(fd):\n    \"\"\"\n    Set the file description of the given file descriptor to non-blocking.\n    \"\"\"\n    flags = fcntl.fcntl(fd, fcntl.F_GETFL)\n    flags = flags | os.O_NONBLOCK\n    fcntl.fcntl(fd, fcntl.F_SETFL, flags)\n\n\ndef setBlocking(fd):\n    \"\"\"\n    Set the file description of the given file descriptor to blocking.\n    \"\"\"\n    flags = fcntl.fcntl(fd, fcntl.F_GETFL)\n    flags = flags & ~os.O_NONBLOCK\n    fcntl.fcntl(fd, fcntl.F_SETFL, flags)\n\n\nif fcntl is None:\n    # fcntl isn't available on Windows.  By default, handles aren't\n    # inherited on Windows, so we can do nothing here.\n    _setCloseOnExec = _unsetCloseOnExec = lambda fd: None\nelse:\n    def _setCloseOnExec(fd):\n        \"\"\"\n        Make a file descriptor close-on-exec.\n        \"\"\"\n        flags = fcntl.fcntl(fd, fcntl.F_GETFD)\n        flags = flags | fcntl.FD_CLOEXEC\n        fcntl.fcntl(fd, fcntl.F_SETFD, flags)\n\n\n    def _unsetCloseOnExec(fd):\n        \"\"\"\n        Make a file descriptor close-on-exec.\n        \"\"\"\n        flags = fcntl.fcntl(fd, fcntl.F_GETFD)\n        flags = flags & ~fcntl.FD_CLOEXEC\n        fcntl.fcntl(fd, fcntl.F_SETFD, flags)\n\n\ndef readFromFD(fd, callback):\n    \"\"\"\n    Read from file descriptor, calling callback with resulting data.\n\n    If successful, call 'callback' with a single argument: the\n    resulting data.\n\n    Returns same thing FileDescriptor.doRead would: CONNECTION_LOST,\n    CONNECTION_DONE, or None.\n\n    @type fd: C{int}\n    @param fd: non-blocking file descriptor to be read from.\n    @param callback: a callable which accepts a single argument. If\n    data is read from the file descriptor it will be called with this\n    data. Handling exceptions from calling the callback is up to the\n    caller.\n\n    Note that if the descriptor is still connected but no data is read,\n    None will be returned but callback will not be called.\n\n    @return: CONNECTION_LOST on error, CONNECTION_DONE when fd is\n    closed, otherwise None.\n    \"\"\"\n    try:\n        output = os.read(fd, 8192)\n    except (OSError, IOError) as ioe:\n        if ioe.args[0] in (errno.EAGAIN, errno.EINTR):\n            return\n        else:\n            return CONNECTION_LOST\n    if not output:\n        return CONNECTION_DONE\n    callback(output)\n\n\ndef writeToFD(fd, data):\n    \"\"\"\n    Write data to file descriptor.\n\n    Returns same thing FileDescriptor.writeSomeData would.\n\n    @type fd: C{int}\n    @param fd: non-blocking file descriptor to be written to.\n    @type data: C{str} or C{buffer}\n    @param data: bytes to write to fd.\n\n    @return: number of bytes written, or CONNECTION_LOST.\n    \"\"\"\n    try:\n        return os.write(fd, data)\n    except (OSError, IOError) as io:\n        if io.errno in (errno.EAGAIN, errno.EINTR):\n            return 0\n        return CONNECTION_LOST\n\n\n__all__ = [\"setNonBlocking\", \"setBlocking\", \"readFromFD\", \"writeToFD\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/gireactor.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module provides support for Twisted to interact with the glib\nmainloop via GObject Introspection.\n\nIn order to use this support, simply do the following::\n\n    from twisted.internet import gireactor\n    gireactor.install()\n\nIf you wish to use a GApplication, register it with the reactor::\n\n    from twisted.internet import reactor\n    reactor.registerGApplication(app)\n\nThen use twisted.internet APIs as usual.\n\nOn Python 3, pygobject v3.4 or later is required.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.python.compat import _PY3\nfrom twisted.internet.error import ReactorAlreadyRunning\nfrom twisted.internet import _glibbase\nfrom twisted.python import runtime\n\nif _PY3:\n    # We require a sufficiently new version of pygobject, so always exists:\n    _pygtkcompatPresent = True\nelse:\n    # We can't just try to import gi.pygtkcompat, because that would import\n    # gi, and the goal here is to not import gi in cases where that would\n    # cause segfault.\n    from twisted.python.modules import theSystemPath\n    _pygtkcompatPresent = True\n    try:\n        theSystemPath[\"gi.pygtkcompat\"]\n    except KeyError:\n        _pygtkcompatPresent = False\n\n\n# Modules that we want to ensure aren't imported if we're on older versions of\n# GI:\n_PYGTK_MODULES = ['gobject', 'glib', 'gio', 'gtk']\n\ndef _oldGiInit():\n    \"\"\"\n    Make sure pygtk and gi aren't loaded at the same time, and import Glib if\n    possible.\n    \"\"\"\n    # We can't immediately prevent imports, because that confuses some buggy\n    # code in gi:\n    _glibbase.ensureNotImported(\n        _PYGTK_MODULES,\n        \"Introspected and static glib/gtk bindings must not be mixed; can't \"\n        \"import gireactor since pygtk2 module is already imported.\")\n\n    global GLib\n    from gi.repository import GLib\n    if getattr(GLib, \"threads_init\", None) is not None:\n        GLib.threads_init()\n\n    _glibbase.ensureNotImported([], \"\",\n                                preventImports=_PYGTK_MODULES)\n\n\nif not _pygtkcompatPresent:\n    # Older versions of gi don't have compatibility layer, so just enforce no\n    # imports of pygtk and gi at same time:\n    _oldGiInit()\nelse:\n    # Newer version of gi, so we can try to initialize compatibility layer; if\n    # real pygtk was already imported we'll get ImportError at this point\n    # rather than segfault, so unconditional import is fine.\n    import gi.pygtkcompat\n    gi.pygtkcompat.enable()\n    # At this point importing gobject will get you gi version, and importing\n    # e.g. gtk will either fail in non-segfaulty way or use gi version if user\n    # does gi.pygtkcompat.enable_gtk(). So, no need to prevent imports of\n    # old school pygtk modules.\n    from gi.repository import GLib\n    if getattr(GLib, \"threads_init\", None) is not None:\n        GLib.threads_init()\n\n\n\nclass GIReactor(_glibbase.GlibReactorBase):\n    \"\"\"\n    GObject-introspection event loop reactor.\n\n    @ivar _gapplication: A C{Gio.Application} instance that was registered\n        with C{registerGApplication}.\n    \"\"\"\n    _POLL_DISCONNECTED = (GLib.IOCondition.HUP | GLib.IOCondition.ERR |\n                          GLib.IOCondition.NVAL)\n    _POLL_IN = GLib.IOCondition.IN\n    _POLL_OUT = GLib.IOCondition.OUT\n\n    # glib's iochannel sources won't tell us about any events that we haven't\n    # asked for, even if those events aren't sensible inputs to the poll()\n    # call.\n    INFLAGS = _POLL_IN | _POLL_DISCONNECTED\n    OUTFLAGS = _POLL_OUT | _POLL_DISCONNECTED\n\n    # By default no Application is registered:\n    _gapplication = None\n\n\n    def __init__(self, useGtk=False):\n        _gtk = None\n        if useGtk is True:\n            from gi.repository import Gtk as _gtk\n\n        _glibbase.GlibReactorBase.__init__(self, GLib, _gtk, useGtk=useGtk)\n\n\n    def registerGApplication(self, app):\n        \"\"\"\n        Register a C{Gio.Application} or C{Gtk.Application}, whose main loop\n        will be used instead of the default one.\n\n        We will C{hold} the application so it doesn't exit on its own. In\n        versions of C{python-gi} 3.2 and later, we exit the event loop using\n        the C{app.quit} method which overrides any holds. Older versions are\n        not supported.\n        \"\"\"\n        if self._gapplication is not None:\n            raise RuntimeError(\n                \"Can't register more than one application instance.\")\n        if self._started:\n            raise ReactorAlreadyRunning(\n                \"Can't register application after reactor was started.\")\n        if not hasattr(app, \"quit\"):\n            raise RuntimeError(\"Application registration is not supported in\"\n                               \" versions of PyGObject prior to 3.2.\")\n        self._gapplication = app\n        def run():\n            app.hold()\n            app.run(None)\n        self._run = run\n\n        self._crash = app.quit\n\n\n\nclass PortableGIReactor(_glibbase.PortableGlibReactorBase):\n    \"\"\"\n    Portable GObject Introspection event loop reactor.\n    \"\"\"\n    def __init__(self, useGtk=False):\n        _gtk = None\n        if useGtk is True:\n            from gi.repository import Gtk as _gtk\n\n        _glibbase.PortableGlibReactorBase.__init__(self, GLib, _gtk,\n                                                   useGtk=useGtk)\n\n\n    def registerGApplication(self, app):\n        \"\"\"\n        Register a C{Gio.Application} or C{Gtk.Application}, whose main loop\n        will be used instead of the default one.\n        \"\"\"\n        raise NotImplementedError(\"GApplication is not currently supported on Windows.\")\n\n\n\ndef install(useGtk=False):\n    \"\"\"\n    Configure the twisted mainloop to be run inside the glib mainloop.\n\n    @param useGtk: should GTK+ rather than glib event loop be\n        used (this will be slightly slower but does support GUI).\n    \"\"\"\n    if runtime.platform.getType() == 'posix':\n        reactor = GIReactor(useGtk=useGtk)\n    else:\n        reactor = PortableGIReactor(useGtk=useGtk)\n\n    from twisted.internet.main import installReactor\n    installReactor(reactor)\n    return reactor\n\n\n__all__ = ['install']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/glib2reactor.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module provides support for Twisted to interact with the glib mainloop.\nThis is like gtk2, but slightly faster and does not require a working\n$DISPLAY. However, you cannot run GUIs under this reactor: for that you must\nuse the gtk2reactor instead.\n\nIn order to use this support, simply do the following::\n\n    from twisted.internet import glib2reactor\n    glib2reactor.install()\n\nThen use twisted.internet APIs as usual.  The other methods here are not\nintended to be called directly.\n\"\"\"\n\nfrom twisted.internet import gtk2reactor\n\n\nclass Glib2Reactor(gtk2reactor.Gtk2Reactor):\n    \"\"\"\n    The reactor using the glib mainloop.\n    \"\"\"\n\n    def __init__(self):\n        \"\"\"\n        Override init to set the C{useGtk} flag.\n        \"\"\"\n        gtk2reactor.Gtk2Reactor.__init__(self, useGtk=False)\n\n\n\ndef install():\n    \"\"\"\n    Configure the twisted mainloop to be run inside the glib mainloop.\n    \"\"\"\n    reactor = Glib2Reactor()\n    from twisted.internet.main import installReactor\n    installReactor(reactor)\n\n\n__all__ = ['install']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/gtk2reactor.py",
    "content": "# -*- test-case-name: twisted.internet.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nThis module provides support for Twisted to interact with the glib/gtk2\nmainloop.\n\nIn order to use this support, simply do the following::\n\n    from twisted.internet import gtk2reactor\n    gtk2reactor.install()\n\nThen use twisted.internet APIs as usual.  The other methods here are not\nintended to be called directly.\n\"\"\"\n\n# System Imports\nimport sys\n\n# Twisted Imports\nfrom twisted.internet import _glibbase\nfrom twisted.python import runtime\n\n# Certain old versions of pygtk and gi crash if imported at the same\n# time. This is a problem when running Twisted's unit tests, since they will\n# attempt to run both gtk2 and gtk3/gi tests. However, gireactor makes sure\n# that if we are in such an old version, and gireactor was imported,\n# gtk2reactor will not be importable. So we don't *need* to enforce that here\n# as well; whichever is imported first will still win. Moreover, additional\n# enforcement in this module is unnecessary in modern versions, and downright\n# problematic in certain versions where for some reason importing gtk also\n# imports some subset of gi. So we do nothing here, relying on gireactor to\n# prevent the crash.\n\ntry:\n    if not hasattr(sys, 'frozen'):\n        # Don't want to check this for py2exe\n        import pygtk\n        pygtk.require('2.0')\nexcept (ImportError, AttributeError):\n    pass # maybe we're using pygtk before this hack existed.\n\nimport gobject\nif hasattr(gobject, \"threads_init\"):\n    # recent versions of python-gtk expose this. python-gtk=2.4.1\n    # (wrapping glib-2.4.7) does. python-gtk=2.0.0 (wrapping\n    # glib-2.2.3) does not.\n    gobject.threads_init()\n\n\n\nclass Gtk2Reactor(_glibbase.GlibReactorBase):\n    \"\"\"\n    PyGTK+ 2 event loop reactor.\n    \"\"\"\n    _POLL_DISCONNECTED = gobject.IO_HUP | gobject.IO_ERR | gobject.IO_NVAL\n    _POLL_IN = gobject.IO_IN\n    _POLL_OUT = gobject.IO_OUT\n\n    # glib's iochannel sources won't tell us about any events that we haven't\n    # asked for, even if those events aren't sensible inputs to the poll()\n    # call.\n    INFLAGS = _POLL_IN | _POLL_DISCONNECTED\n    OUTFLAGS = _POLL_OUT | _POLL_DISCONNECTED\n\n    def __init__(self, useGtk=True):\n        _gtk = None\n        if useGtk is True:\n            import gtk as _gtk\n\n        _glibbase.GlibReactorBase.__init__(self, gobject, _gtk, useGtk=useGtk)\n\n\n\nclass PortableGtkReactor(_glibbase.PortableGlibReactorBase):\n    \"\"\"\n    Reactor that works on Windows.\n\n    Sockets aren't supported by GTK+'s input_add on Win32.\n    \"\"\"\n    def __init__(self, useGtk=True):\n        _gtk = None\n        if useGtk is True:\n            import gtk as _gtk\n\n        _glibbase.PortableGlibReactorBase.__init__(self, gobject, _gtk,\n                                                   useGtk=useGtk)\n\n\ndef install(useGtk=True):\n    \"\"\"\n    Configure the twisted mainloop to be run inside the gtk mainloop.\n\n    @param useGtk: should glib rather than GTK+ event loop be\n        used (this will be slightly faster but does not support GUI).\n    \"\"\"\n    reactor = Gtk2Reactor(useGtk)\n    from twisted.internet.main import installReactor\n    installReactor(reactor)\n    return reactor\n\n\ndef portableInstall(useGtk=True):\n    \"\"\"\n    Configure the twisted mainloop to be run inside the gtk mainloop.\n    \"\"\"\n    reactor = PortableGtkReactor()\n    from twisted.internet.main import installReactor\n    installReactor(reactor)\n    return reactor\n\n\nif runtime.platform.getType() == 'posix':\n    install = install\nelse:\n    install = portableInstall\n\n\n__all__ = ['install']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/gtk3reactor.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module provides support for Twisted to interact with the gtk3 mainloop\nvia Gobject introspection. This is like gi, but slightly slower and requires a\nworking $DISPLAY.\n\nIn order to use this support, simply do the following::\n\n    from twisted.internet import gtk3reactor\n    gtk3reactor.install()\n\nIf you wish to use a GApplication, register it with the reactor::\n\n    from twisted.internet import reactor\n    reactor.registerGApplication(app)\n\nThen use twisted.internet APIs as usual.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport os\n\nfrom twisted.internet import gireactor\nfrom twisted.python import runtime\n\n# Newer versions of gtk3/pygoject raise a RuntimeError, or just break in a\n# confusing manner, if the program is not running under X11.  We therefore try\n# to fail in a more reasonable manner, and check for $DISPLAY as a reasonable\n# approximation of availability of X11. This is somewhat over-aggressive,\n# since some older versions of gtk3/pygobject do work with missing $DISPLAY,\n# but it's too hard to figure out which, so we always require it.\nif (runtime.platform.getType() == 'posix' and\n    not runtime.platform.isMacOSX() and not os.environ.get(\"DISPLAY\")):\n    raise ImportError(\n        \"Gtk3 requires X11, and no DISPLAY environment variable is set\")\n\n\nclass Gtk3Reactor(gireactor.GIReactor):\n    \"\"\"\n    A reactor using the gtk3+ event loop.\n    \"\"\"\n\n    def __init__(self):\n        \"\"\"\n        Override init to set the C{useGtk} flag.\n        \"\"\"\n        gireactor.GIReactor.__init__(self, useGtk=True)\n\n\n\nclass PortableGtk3Reactor(gireactor.PortableGIReactor):\n    \"\"\"\n    Portable GTK+ 3.x reactor.\n    \"\"\"\n    def __init__(self):\n        \"\"\"\n        Override init to set the C{useGtk} flag.\n        \"\"\"\n        gireactor.PortableGIReactor.__init__(self, useGtk=True)\n\n\n\ndef install():\n    \"\"\"\n    Configure the Twisted mainloop to be run inside the gtk3+ mainloop.\n    \"\"\"\n    if runtime.platform.getType() == 'posix':\n        reactor = Gtk3Reactor()\n    else:\n        reactor = PortableGtk3Reactor()\n\n    from twisted.internet.main import installReactor\n    installReactor(reactor)\n    return reactor\n\n\n__all__ = ['install']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/inotify.py",
    "content": "# -*- test-case-name: twisted.internet.test.test_inotify -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module provides support for Twisted to linux inotify API.\n\nIn order to use this support, simply do the following (and start a reactor\nat some point)::\n\n    from twisted.internet import inotify\n    from twisted.python import filepath\n\n    def notify(ignored, filepath, mask):\n        \\\"\"\"\n        For historical reasons, an opaque handle is passed as first\n        parameter. This object should never be used.\n\n        @param filepath: FilePath on which the event happened.\n        @param mask: inotify event as hexadecimal masks\n        \\\"\"\"\n        print(\"event %s on %s\" % (\n            ', '.join(inotify.humanReadableMask(mask)), filepath))\n\n    notifier = inotify.INotify()\n    notifier.startReading()\n    notifier.watch(filepath.FilePath(\"/some/directory\"), callbacks=[notify])\n    notifier.watch(filepath.FilePath(b\"/some/directory2\"), callbacks=[notify])\n\nNote that in the above example, a L{FilePath} which is a L{bytes} path name\nor L{str} path name may be used.  However, no matter what type of\nL{FilePath} is passed to this module, internally the L{FilePath} is\nconverted to L{bytes} according to L{sys.getfilesystemencoding}.\nFor any L{FilePath} returned by this module, the caller is responsible for\nconverting from a L{bytes} path name to a L{str} path name.\n\n@since: 10.1\n\"\"\"\n\nfrom __future__ import print_function\n\nimport os\nimport struct\n\nfrom twisted.internet import fdesc\nfrom twisted.internet.abstract import FileDescriptor\nfrom twisted.python import log, _inotify\n\n\n# from /usr/src/linux/include/linux/inotify.h\n\nIN_ACCESS = 0x00000001         # File was accessed\nIN_MODIFY = 0x00000002         # File was modified\nIN_ATTRIB = 0x00000004         # Metadata changed\nIN_CLOSE_WRITE = 0x00000008    # Writeable file was closed\nIN_CLOSE_NOWRITE = 0x00000010  # Unwriteable file closed\nIN_OPEN = 0x00000020           # File was opened\nIN_MOVED_FROM = 0x00000040     # File was moved from X\nIN_MOVED_TO = 0x00000080       # File was moved to Y\nIN_CREATE = 0x00000100         # Subfile was created\nIN_DELETE = 0x00000200         # Subfile was delete\nIN_DELETE_SELF = 0x00000400    # Self was deleted\nIN_MOVE_SELF = 0x00000800      # Self was moved\nIN_UNMOUNT = 0x00002000        # Backing fs was unmounted\nIN_Q_OVERFLOW = 0x00004000     # Event queued overflowed\nIN_IGNORED = 0x00008000        # File was ignored\n\nIN_ONLYDIR = 0x01000000         # only watch the path if it is a directory\nIN_DONT_FOLLOW = 0x02000000     # don't follow a sym link\nIN_MASK_ADD = 0x20000000        # add to the mask of an already existing watch\nIN_ISDIR = 0x40000000           # event occurred against dir\nIN_ONESHOT = 0x80000000         # only send event once\n\nIN_CLOSE = IN_CLOSE_WRITE | IN_CLOSE_NOWRITE     # closes\nIN_MOVED = IN_MOVED_FROM | IN_MOVED_TO           # moves\nIN_CHANGED = IN_MODIFY | IN_ATTRIB               # changes\n\nIN_WATCH_MASK = (IN_MODIFY | IN_ATTRIB |\n                 IN_CREATE | IN_DELETE |\n                 IN_DELETE_SELF | IN_MOVE_SELF |\n                 IN_UNMOUNT | IN_MOVED_FROM | IN_MOVED_TO)\n\n\n_FLAG_TO_HUMAN = [\n    (IN_ACCESS, 'access'),\n    (IN_MODIFY, 'modify'),\n    (IN_ATTRIB, 'attrib'),\n    (IN_CLOSE_WRITE, 'close_write'),\n    (IN_CLOSE_NOWRITE, 'close_nowrite'),\n    (IN_OPEN, 'open'),\n    (IN_MOVED_FROM, 'moved_from'),\n    (IN_MOVED_TO, 'moved_to'),\n    (IN_CREATE, 'create'),\n    (IN_DELETE, 'delete'),\n    (IN_DELETE_SELF, 'delete_self'),\n    (IN_MOVE_SELF, 'move_self'),\n    (IN_UNMOUNT, 'unmount'),\n    (IN_Q_OVERFLOW, 'queue_overflow'),\n    (IN_IGNORED, 'ignored'),\n    (IN_ONLYDIR, 'only_dir'),\n    (IN_DONT_FOLLOW, 'dont_follow'),\n    (IN_MASK_ADD, 'mask_add'),\n    (IN_ISDIR, 'is_dir'),\n    (IN_ONESHOT, 'one_shot')\n]\n\n\n\ndef humanReadableMask(mask):\n    \"\"\"\n    Auxiliary function that converts a hexadecimal mask into a series\n    of human readable flags.\n    \"\"\"\n    s = []\n    for k, v in _FLAG_TO_HUMAN:\n        if k & mask:\n            s.append(v)\n    return s\n\n\n\nclass _Watch(object):\n    \"\"\"\n    Watch object that represents a Watch point in the filesystem. The\n    user should let INotify to create these objects\n\n    @ivar path: The path over which this watch point is monitoring\n    @ivar mask: The events monitored by this watchpoint\n    @ivar autoAdd: Flag that determines whether this watch point\n        should automatically add created subdirectories\n    @ivar callbacks: L{list} of callback functions that will be called\n        when an event occurs on this watch.\n    \"\"\"\n    def __init__(self, path, mask=IN_WATCH_MASK, autoAdd=False,\n                 callbacks=None):\n        self.path = path.asBytesMode()\n        self.mask = mask\n        self.autoAdd = autoAdd\n        if callbacks is None:\n            callbacks = []\n        self.callbacks = callbacks\n\n\n    def _notify(self, filepath, events):\n        \"\"\"\n        Callback function used by L{INotify} to dispatch an event.\n        \"\"\"\n        filepath = filepath.asBytesMode()\n        for callback in self.callbacks:\n            callback(self, filepath, events)\n\n\n\nclass INotify(FileDescriptor, object):\n    \"\"\"\n    The INotify file descriptor, it basically does everything related\n    to INotify, from reading to notifying watch points.\n\n    @ivar _buffer: a L{bytes} containing the data read from the inotify fd.\n\n    @ivar _watchpoints: a L{dict} that maps from inotify watch ids to\n        watchpoints objects\n\n    @ivar _watchpaths: a L{dict} that maps from watched paths to the\n        inotify watch ids\n    \"\"\"\n    _inotify = _inotify\n\n    def __init__(self, reactor=None):\n        FileDescriptor.__init__(self, reactor=reactor)\n\n        # Smart way to allow parametrization of libc so I can override\n        # it and test for the system errors.\n        self._fd = self._inotify.init()\n\n        fdesc.setNonBlocking(self._fd)\n        fdesc._setCloseOnExec(self._fd)\n\n        # The next 2 lines are needed to have self.loseConnection()\n        # to call connectionLost() on us. Since we already created the\n        # fd that talks to inotify we want to be notified even if we\n        # haven't yet started reading.\n        self.connected = 1\n        self._writeDisconnected = True\n\n        self._buffer = b''\n        self._watchpoints = {}\n        self._watchpaths = {}\n\n\n    def _addWatch(self, path, mask, autoAdd, callbacks):\n        \"\"\"\n        Private helper that abstracts the use of ctypes.\n\n        Calls the internal inotify API and checks for any errors after the\n        call. If there's an error L{INotify._addWatch} can raise an\n        INotifyError. If there's no error it proceeds creating a watchpoint and\n        adding a watchpath for inverse lookup of the file descriptor from the\n        path.\n        \"\"\"\n        path = path.asBytesMode()\n        wd = self._inotify.add(self._fd, path, mask)\n\n        iwp = _Watch(path, mask, autoAdd, callbacks)\n\n        self._watchpoints[wd] = iwp\n        self._watchpaths[path] = wd\n\n        return wd\n\n\n    def _rmWatch(self, wd):\n        \"\"\"\n        Private helper that abstracts the use of ctypes.\n\n        Calls the internal inotify API to remove an fd from inotify then\n        removes the corresponding watchpoint from the internal mapping together\n        with the file descriptor from the watchpath.\n        \"\"\"\n        self._inotify.remove(self._fd, wd)\n        iwp = self._watchpoints.pop(wd)\n        self._watchpaths.pop(iwp.path)\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Release the inotify file descriptor and do the necessary cleanup\n        \"\"\"\n        FileDescriptor.connectionLost(self, reason)\n        if self._fd >= 0:\n            try:\n                os.close(self._fd)\n            except OSError as e:\n                log.err(e, \"Couldn't close INotify file descriptor.\")\n\n\n    def fileno(self):\n        \"\"\"\n        Get the underlying file descriptor from this inotify observer.\n        Required by L{abstract.FileDescriptor} subclasses.\n        \"\"\"\n        return self._fd\n\n\n    def doRead(self):\n        \"\"\"\n        Read some data from the observed file descriptors\n        \"\"\"\n        fdesc.readFromFD(self._fd, self._doRead)\n\n\n    def _doRead(self, in_):\n        \"\"\"\n        Work on the data just read from the file descriptor.\n        \"\"\"\n        self._buffer += in_\n        while len(self._buffer) >= 16:\n\n            wd, mask, cookie, size = struct.unpack(\"=LLLL\", self._buffer[0:16])\n\n            if size:\n                name = self._buffer[16:16 + size].rstrip(b'\\0')\n            else:\n                name = None\n\n            self._buffer = self._buffer[16 + size:]\n\n            try:\n                iwp = self._watchpoints[wd]\n            except KeyError:\n                continue\n\n            path = iwp.path.asBytesMode()\n            if name:\n                path = path.child(name)\n            iwp._notify(path, mask)\n\n            if (iwp.autoAdd and mask & IN_ISDIR and mask & IN_CREATE):\n                # mask & IN_ISDIR already guarantees that the path is a\n                # directory. There's no way you can get here without a\n                # directory anyway, so no point in checking for that again.\n                new_wd = self.watch(\n                    path, mask=iwp.mask, autoAdd=True,\n                    callbacks=iwp.callbacks\n                )\n                # This is very very very hacky and I'd rather not do this but\n                # we have no other alternative that is less hacky other than\n                # surrender.  We use callLater because we don't want to have\n                # too many events waiting while we process these subdirs, we\n                # must always answer events as fast as possible or the overflow\n                # might come.\n                self.reactor.callLater(0,\n                    self._addChildren, self._watchpoints[new_wd])\n            if mask & IN_DELETE_SELF:\n                self._rmWatch(wd)\n\n\n    def _addChildren(self, iwp):\n        \"\"\"\n        This is a very private method, please don't even think about using it.\n\n        Note that this is a fricking hack... it's because we cannot be fast\n        enough in adding a watch to a directory and so we basically end up\n        getting here too late if some operations have already been going on in\n        the subdir, we basically need to catchup.  This eventually ends up\n        meaning that we generate double events, your app must be resistant.\n        \"\"\"\n        try:\n            listdir = iwp.path.children()\n        except OSError:\n            # Somebody or something (like a test) removed this directory while\n            # we were in the callLater(0...) waiting. It doesn't make sense to\n            # process it anymore\n            return\n\n        # note that it's true that listdir will only see the subdirs inside\n        # path at the moment of the call but path is monitored already so if\n        # something is created we will receive an event.\n        for f in listdir:\n            # It's a directory, watch it and then add its children\n            if f.isdir():\n                wd = self.watch(\n                    f, mask=iwp.mask, autoAdd=True,\n                    callbacks=iwp.callbacks\n                )\n                iwp._notify(f, IN_ISDIR|IN_CREATE)\n                # now f is watched, we can add its children the callLater is to\n                # avoid recursion\n                self.reactor.callLater(0,\n                    self._addChildren, self._watchpoints[wd])\n\n            # It's a file and we notify it.\n            if f.isfile():\n                iwp._notify(f, IN_CREATE|IN_CLOSE_WRITE)\n\n\n    def watch(self, path, mask=IN_WATCH_MASK, autoAdd=False,\n              callbacks=None, recursive=False):\n        \"\"\"\n        Watch the 'mask' events in given path. Can raise C{INotifyError} when\n        there's a problem while adding a directory.\n\n        @param path: The path needing monitoring\n        @type path: L{FilePath}\n\n        @param mask: The events that should be watched\n        @type mask: L{int}\n\n        @param autoAdd: if True automatically add newly created\n                        subdirectories\n        @type autoAdd: L{bool}\n\n        @param callbacks: A list of callbacks that should be called\n                          when an event happens in the given path.\n                          The callback should accept 3 arguments:\n                          (ignored, filepath, mask)\n        @type callbacks: L{list} of callables\n\n        @param recursive: Also add all the subdirectories in this path\n        @type recursive: L{bool}\n        \"\"\"\n        if recursive:\n            # This behavior is needed to be compatible with the windows\n            # interface for filesystem changes:\n            # http://msdn.microsoft.com/en-us/library/aa365465(VS.85).aspx\n            # ReadDirectoryChangesW can do bWatchSubtree so it doesn't\n            # make sense to implement this at a higher abstraction\n            # level when other platforms support it already\n            for child in path.walk():\n                if child.isdir():\n                    self.watch(child, mask, autoAdd, callbacks,\n                               recursive=False)\n        else:\n            wd = self._isWatched(path)\n            if wd:\n                return wd\n\n            mask = mask | IN_DELETE_SELF # need this to remove the watch\n\n            return self._addWatch(path, mask, autoAdd, callbacks)\n\n\n    def ignore(self, path):\n        \"\"\"\n        Remove the watch point monitoring the given path\n\n        @param path: The path that should be ignored\n        @type path: L{FilePath}\n        \"\"\"\n        path = path.asBytesMode()\n        wd = self._isWatched(path)\n        if wd is None:\n            raise KeyError(\"%r is not watched\" % (path,))\n        else:\n            self._rmWatch(wd)\n\n\n    def _isWatched(self, path):\n        \"\"\"\n        Helper function that checks if the path is already monitored\n        and returns its watchdescriptor if so or None otherwise.\n\n        @param path: The path that should be checked\n        @type path: L{FilePath}\n        \"\"\"\n        path = path.asBytesMode()\n        return self._watchpaths.get(path, None)\n\n\nINotifyError = _inotify.INotifyError\n\n\n__all__ = [\"INotify\", \"humanReadableMask\", \"IN_WATCH_MASK\", \"IN_ACCESS\",\n           \"IN_MODIFY\", \"IN_ATTRIB\", \"IN_CLOSE_NOWRITE\", \"IN_CLOSE_WRITE\",\n           \"IN_OPEN\", \"IN_MOVED_FROM\", \"IN_MOVED_TO\", \"IN_CREATE\",\n           \"IN_DELETE\", \"IN_DELETE_SELF\", \"IN_MOVE_SELF\", \"IN_UNMOUNT\",\n           \"IN_Q_OVERFLOW\", \"IN_IGNORED\", \"IN_ONLYDIR\", \"IN_DONT_FOLLOW\",\n           \"IN_MASK_ADD\", \"IN_ISDIR\", \"IN_ONESHOT\", \"IN_CLOSE\",\n           \"IN_MOVED\", \"IN_CHANGED\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/interfaces.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nInterface documentation.\n\nMaintainer: Itamar Shtull-Trauring\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom zope.interface import Interface, Attribute\n\n\nclass IAddress(Interface):\n    \"\"\"\n    An address, e.g. a TCP C{(host, port)}.\n\n    Default implementations are in L{twisted.internet.address}.\n    \"\"\"\n\n### Reactor Interfaces\n\nclass IConnector(Interface):\n    \"\"\"\n    Object used to interface between connections and protocols.\n\n    Each L{IConnector} manages one connection.\n    \"\"\"\n\n    def stopConnecting():\n        \"\"\"\n        Stop attempting to connect.\n        \"\"\"\n\n    def disconnect():\n        \"\"\"\n        Disconnect regardless of the connection state.\n\n        If we are connected, disconnect, if we are trying to connect,\n        stop trying.\n        \"\"\"\n\n    def connect():\n        \"\"\"\n        Try to connect to remote address.\n        \"\"\"\n\n    def getDestination():\n        \"\"\"\n        Return destination this will try to connect to.\n\n        @return: An object which provides L{IAddress}.\n        \"\"\"\n\n\n\nclass IResolverSimple(Interface):\n    def getHostByName(name, timeout = (1, 3, 11, 45)):\n        \"\"\"\n        Resolve the domain name C{name} into an IP address.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{twisted.internet.defer.Deferred}\n        @return: The callback of the Deferred that is returned will be\n            passed a string that represents the IP address of the\n            specified name, or the errback will be called if the\n            lookup times out.  If multiple types of address records\n            are associated with the name, A6 records will be returned\n            in preference to AAAA records, which will be returned in\n            preference to A records.  If there are multiple records of\n            the type to be returned, one will be selected at random.\n\n        @raise twisted.internet.defer.TimeoutError: Raised\n            (asynchronously) if the name cannot be resolved within the\n            specified timeout period.\n        \"\"\"\n\n\n\nclass IHostResolution(Interface):\n    \"\"\"\n    An L{IHostResolution} represents represents an in-progress recursive query\n    for a DNS name.\n\n    @since: Twisted 17.1.0\n    \"\"\"\n\n    name = Attribute(\n        \"\"\"\n        L{unicode}; the name of the host being resolved.\n        \"\"\"\n    )\n\n    def cancel():\n        \"\"\"\n        Stop the hostname resolution in progress.\n        \"\"\"\n\n\n\nclass IResolutionReceiver(Interface):\n    \"\"\"\n    An L{IResolutionReceiver} receives the results of a hostname resolution in\n    progress, initiated by an L{IHostnameResolver}.\n\n    @since: Twisted 17.1.0\n    \"\"\"\n\n    def resolutionBegan(resolutionInProgress):\n        \"\"\"\n        A hostname resolution began.\n\n        @param resolutionInProgress: an L{IHostResolution}.\n        \"\"\"\n\n\n    def addressResolved(address):\n        \"\"\"\n        An internet address.  This is called when an address for the given name\n        is discovered.  In the current implementation this practically means\n        L{IPv4Address} or L{IPv6Address}, but implementations of this interface\n        should be lenient to other types being passed to this interface as\n        well, for future-proofing.\n\n        @param address: An address object.\n        @type address: L{IAddress}\n        \"\"\"\n\n\n    def resolutionComplete():\n        \"\"\"\n        Resolution has completed; no further addresses will be relayed to\n        L{IResolutionReceiver.addressResolved}.\n        \"\"\"\n\n\n\nclass IHostnameResolver(Interface):\n    \"\"\"\n    An L{IHostnameResolver} can resolve a host name and port number into a\n    series of L{IAddress} objects.\n\n    @since: Twisted 17.1.0\n    \"\"\"\n\n    def resolveHostName(resolutionReceiver, hostName, portNumber=0,\n                        addressTypes=None, transportSemantics='TCP'):\n        \"\"\"\n        Initiate a hostname resolution.\n\n        @param resolutionReceiver: an object that will receive each resolved\n            address as it arrives.\n        @type resolutionReceiver: L{IResolutionReceiver}\n\n        @param hostName: The name of the host to resolve.  If this contains\n            non-ASCII code points, they will be converted to IDNA first.\n        @type hostName: L{unicode}\n\n        @param portNumber: The port number that the returned addresses should\n            include.\n        @type portNumber: L{int} greater than or equal to 0 and less than 65536\n\n        @param addressTypes: An iterable of implementors of L{IAddress} that\n            are acceptable values for C{resolutionReceiver} to receive to its\n            L{addressResolved <IResolutionReceiver.addressResolved>}.  In\n            practice, this means an iterable containing\n            L{twisted.internet.address.IPv4Address},\n            L{twisted.internet.address.IPv6Address}, both, or neither.\n        @type addressTypes: L{collections.abc.Iterable} of L{type}\n\n        @param transportSemantics: A string describing the semantics of the\n            transport; either C{'TCP'} for stream-oriented transports or\n            C{'UDP'} for datagram-oriented; see\n            L{twisted.internet.address.IPv6Address.type} and\n            L{twisted.internet.address.IPv4Address.type}.\n        @type transportSemantics: native L{str}\n\n        @return: The resolution in progress.\n        @rtype: L{IResolutionReceiver}\n        \"\"\"\n\n\n\nclass IResolver(IResolverSimple):\n    def query(query, timeout=None):\n        \"\"\"\n        Dispatch C{query} to the method which can handle its type.\n\n        @type query: L{twisted.names.dns.Query}\n        @param query: The DNS query being issued, to which a response is to be\n            generated.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupAddress(name, timeout=None):\n        \"\"\"\n        Perform an A record lookup.\n\n        @type name: L{bytes}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupAddress6(name, timeout=None):\n        \"\"\"\n        Perform an A6 record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupIPV6Address(name, timeout=None):\n        \"\"\"\n        Perform an AAAA record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupMailExchange(name, timeout=None):\n        \"\"\"\n        Perform an MX record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupNameservers(name, timeout=None):\n        \"\"\"\n        Perform an NS record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupCanonicalName(name, timeout=None):\n        \"\"\"\n        Perform a CNAME record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupMailBox(name, timeout=None):\n        \"\"\"\n        Perform an MB record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupMailGroup(name, timeout=None):\n        \"\"\"\n        Perform an MG record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupMailRename(name, timeout=None):\n        \"\"\"\n        Perform an MR record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupPointer(name, timeout=None):\n        \"\"\"\n        Perform a PTR record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupAuthority(name, timeout=None):\n        \"\"\"\n        Perform an SOA record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupNull(name, timeout=None):\n        \"\"\"\n        Perform a NULL record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupWellKnownServices(name, timeout=None):\n        \"\"\"\n        Perform a WKS record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupHostInfo(name, timeout=None):\n        \"\"\"\n        Perform a HINFO record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupMailboxInfo(name, timeout=None):\n        \"\"\"\n        Perform an MINFO record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupText(name, timeout=None):\n        \"\"\"\n        Perform a TXT record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupResponsibility(name, timeout=None):\n        \"\"\"\n        Perform an RP record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupAFSDatabase(name, timeout=None):\n        \"\"\"\n        Perform an AFSDB record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupService(name, timeout=None):\n        \"\"\"\n        Perform an SRV record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupAllRecords(name, timeout=None):\n        \"\"\"\n        Perform an ALL_RECORD lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupSenderPolicy(name, timeout= 10):\n        \"\"\"\n        Perform a SPF record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupNamingAuthorityPointer(name, timeout=None):\n        \"\"\"\n        Perform a NAPTR record lookup.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n            When the last timeout expires, the query is considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.  The first element of the\n            tuple gives answers.  The second element of the tuple gives\n            authorities.  The third element of the tuple gives additional\n            information.  The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n    def lookupZone(name, timeout=None):\n        \"\"\"\n        Perform an AXFR record lookup.\n\n        NB This is quite different from other DNS requests. See\n        U{http://cr.yp.to/djbdns/axfr-notes.html} for more\n        information.\n\n        NB Unlike other C{lookup*} methods, the timeout here is not a\n        list of ints, it is a single int.\n\n        @type name: C{str}\n        @param name: DNS name to resolve.\n\n        @type timeout: C{int}\n        @param timeout: When this timeout expires, the query is\n            considered failed.\n\n        @rtype: L{Deferred}\n        @return: A L{Deferred} which fires with a three-tuple of lists of\n            L{twisted.names.dns.RRHeader} instances.\n            The first element of the tuple gives answers.\n            The second and third elements are always empty.\n            The L{Deferred} may instead fail with one of the\n            exceptions defined in L{twisted.names.error} or with\n            C{NotImplementedError}.\n        \"\"\"\n\n\n\nclass IReactorTCP(Interface):\n\n    def listenTCP(port, factory, backlog=50, interface=''):\n        \"\"\"\n        Connects a given protocol factory to the given numeric TCP/IP port.\n\n        @param port: a port number on which to listen\n\n        @param factory: a L{twisted.internet.protocol.ServerFactory} instance\n\n        @param backlog: size of the listen queue\n\n        @param interface: The local IPv4 or IPv6 address to which to bind;\n            defaults to '', ie all IPv4 addresses.  To bind to all IPv4 and IPv6\n            addresses, you must call this method twice.\n\n        @return: an object that provides L{IListeningPort}.\n\n        @raise CannotListenError: as defined here\n                                  L{twisted.internet.error.CannotListenError},\n                                  if it cannot listen on this port (e.g., it\n                                  cannot bind to the required port number)\n        \"\"\"\n\n    def connectTCP(host, port, factory, timeout=30, bindAddress=None):\n        \"\"\"\n        Connect a TCP client.\n\n        @param host: A hostname or an IPv4 or IPv6 address literal.\n\n        @type host: L{bytes}\n\n        @param port: a port number\n\n        @param factory: a L{twisted.internet.protocol.ClientFactory} instance\n\n        @param timeout: number of seconds to wait before assuming the\n                        connection has failed.\n\n        @param bindAddress: a (host, port) tuple of local address to bind\n                            to, or None.\n\n        @return: An object which provides L{IConnector}. This connector will\n                 call various callbacks on the factory when a connection is\n                 made, failed, or lost - see\n                 L{ClientFactory<twisted.internet.protocol.ClientFactory>}\n                 docs for details.\n        \"\"\"\n\nclass IReactorSSL(Interface):\n\n    def connectSSL(host, port, factory, contextFactory, timeout=30, bindAddress=None):\n        \"\"\"\n        Connect a client Protocol to a remote SSL socket.\n\n        @param host: a host name\n\n        @param port: a port number\n\n        @param factory: a L{twisted.internet.protocol.ClientFactory} instance\n\n        @param contextFactory: a L{twisted.internet.ssl.ClientContextFactory} object.\n\n        @param timeout: number of seconds to wait before assuming the\n                        connection has failed.\n\n        @param bindAddress: a (host, port) tuple of local address to bind to,\n                            or L{None}.\n\n        @return: An object which provides L{IConnector}.\n        \"\"\"\n\n    def listenSSL(port, factory, contextFactory, backlog=50, interface=''):\n        \"\"\"\n        Connects a given protocol factory to the given numeric TCP/IP port.\n        The connection is a SSL one, using contexts created by the context\n        factory.\n\n        @param port: a port number on which to listen\n\n        @param factory: a L{twisted.internet.protocol.ServerFactory} instance\n\n        @param contextFactory: an implementor of L{IOpenSSLContextFactory}\n\n        @param backlog: size of the listen queue\n\n        @param interface: the hostname to bind to, defaults to '' (all)\n        \"\"\"\n\n\n\nclass IReactorUNIX(Interface):\n    \"\"\"\n    UNIX socket methods.\n    \"\"\"\n\n    def connectUNIX(address, factory, timeout=30, checkPID=0):\n        \"\"\"\n        Connect a client protocol to a UNIX socket.\n\n        @param address: a path to a unix socket on the filesystem.\n\n        @param factory: a L{twisted.internet.protocol.ClientFactory} instance\n\n        @param timeout: number of seconds to wait before assuming the connection\n            has failed.\n\n        @param checkPID: if True, check for a pid file to verify that a server\n            is listening.  If C{address} is a Linux abstract namespace path,\n            this must be C{False}.\n\n        @return: An object which provides L{IConnector}.\n        \"\"\"\n\n\n    def listenUNIX(address, factory, backlog=50, mode=0o666, wantPID=0):\n        \"\"\"\n        Listen on a UNIX socket.\n\n        @param address: a path to a unix socket on the filesystem.\n\n        @param factory: a L{twisted.internet.protocol.Factory} instance.\n\n        @param backlog: number of connections to allow in backlog.\n\n        @param mode: The mode (B{not} umask) to set on the unix socket.  See\n            platform specific documentation for information about how this\n            might affect connection attempts.\n        @type mode: C{int}\n\n        @param wantPID: if True, create a pidfile for the socket.  If C{address}\n            is a Linux abstract namespace path, this must be C{False}.\n\n        @return: An object which provides L{IListeningPort}.\n        \"\"\"\n\n\n\nclass IReactorUNIXDatagram(Interface):\n    \"\"\"\n    Datagram UNIX socket methods.\n    \"\"\"\n\n    def connectUNIXDatagram(address, protocol, maxPacketSize=8192, mode=0o666, bindAddress=None):\n        \"\"\"\n        Connect a client protocol to a datagram UNIX socket.\n\n        @param address: a path to a unix socket on the filesystem.\n\n        @param protocol: a L{twisted.internet.protocol.ConnectedDatagramProtocol} instance\n\n        @param maxPacketSize: maximum packet size to accept\n\n        @param mode: The mode (B{not} umask) to set on the unix socket.  See\n            platform specific documentation for information about how this\n            might affect connection attempts.\n        @type mode: C{int}\n\n        @param bindAddress: address to bind to\n\n        @return: An object which provides L{IConnector}.\n        \"\"\"\n\n\n    def listenUNIXDatagram(address, protocol, maxPacketSize=8192, mode=0o666):\n        \"\"\"\n        Listen on a datagram UNIX socket.\n\n        @param address: a path to a unix socket on the filesystem.\n\n        @param protocol: a L{twisted.internet.protocol.DatagramProtocol} instance.\n\n        @param maxPacketSize: maximum packet size to accept\n\n        @param mode: The mode (B{not} umask) to set on the unix socket.  See\n            platform specific documentation for information about how this\n            might affect connection attempts.\n        @type mode: C{int}\n\n        @return: An object which provides L{IListeningPort}.\n        \"\"\"\n\n\n\nclass IReactorWin32Events(Interface):\n    \"\"\"\n    Win32 Event API methods\n\n    @since: 10.2\n    \"\"\"\n\n    def addEvent(event, fd, action):\n        \"\"\"\n        Add a new win32 event to the event loop.\n\n        @param event: a Win32 event object created using win32event.CreateEvent()\n\n        @param fd: an instance of L{twisted.internet.abstract.FileDescriptor}\n\n        @param action: a string that is a method name of the fd instance.\n                       This method is called in response to the event.\n\n        @return: None\n        \"\"\"\n\n\n    def removeEvent(event):\n        \"\"\"\n        Remove an event.\n\n        @param event: a Win32 event object added using L{IReactorWin32Events.addEvent}\n\n        @return: None\n        \"\"\"\n\n\n\nclass IReactorUDP(Interface):\n    \"\"\"\n    UDP socket methods.\n    \"\"\"\n\n    def listenUDP(port, protocol, interface='', maxPacketSize=8192):\n        \"\"\"\n        Connects a given L{DatagramProtocol} to the given numeric UDP port.\n\n        @param port: A port number on which to listen.\n        @type port: C{int}\n\n        @param protocol: A L{DatagramProtocol} instance which will be\n            connected to the given C{port}.\n        @type protocol: L{DatagramProtocol}\n\n        @param interface: The local IPv4 or IPv6 address to which to bind;\n            defaults to '', ie all IPv4 addresses.\n        @type interface: C{str}\n\n        @param maxPacketSize: The maximum packet size to accept.\n        @type maxPacketSize: C{int}\n\n        @return: object which provides L{IListeningPort}.\n        \"\"\"\n\n\n\nclass IReactorMulticast(Interface):\n    \"\"\"\n    UDP socket methods that support multicast.\n\n    IMPORTANT: This is an experimental new interface. It may change\n    without backwards compatibility. Suggestions are welcome.\n    \"\"\"\n\n    def listenMulticast(port, protocol, interface='', maxPacketSize=8192,\n                        listenMultiple=False):\n        \"\"\"\n        Connects a given\n        L{DatagramProtocol<twisted.internet.protocol.DatagramProtocol>} to the\n        given numeric UDP port.\n\n        @param listenMultiple: If set to True, allows multiple sockets to\n            bind to the same address and port number at the same time.\n        @type listenMultiple: C{bool}\n\n        @returns: An object which provides L{IListeningPort}.\n\n        @see: L{twisted.internet.interfaces.IMulticastTransport}\n        @see: U{http://twistedmatrix.com/documents/current/core/howto/udp.html}\n        \"\"\"\n\n\n\nclass IReactorSocket(Interface):\n    \"\"\"\n    Methods which allow a reactor to use externally created sockets.\n\n    For example, to use C{adoptStreamPort} to implement behavior equivalent\n    to that of L{IReactorTCP.listenTCP}, you might write code like this::\n\n        from socket import SOMAXCONN, AF_INET, SOCK_STREAM, socket\n        portSocket = socket(AF_INET, SOCK_STREAM)\n        # Set FD_CLOEXEC on port, left as an exercise.  Then make it into a\n        # non-blocking listening port:\n        portSocket.setblocking(False)\n        portSocket.bind(('192.168.1.2', 12345))\n        portSocket.listen(SOMAXCONN)\n\n        # Now have the reactor use it as a TCP port\n        port = reactor.adoptStreamPort(\n            portSocket.fileno(), AF_INET, YourFactory())\n\n        # portSocket itself is no longer necessary, and needs to be cleaned\n        # up by us.\n        portSocket.close()\n\n        # Whenever the server is no longer needed, stop it as usual.\n        stoppedDeferred = port.stopListening()\n\n    Another potential use is to inherit a listening descriptor from a parent\n    process (for example, systemd or launchd), or to receive one over a UNIX\n    domain socket.\n\n    Some plans for extending this interface exist.  See:\n\n        - U{http://twistedmatrix.com/trac/ticket/6594}: AF_UNIX SOCK_DGRAM ports\n    \"\"\"\n\n    def adoptStreamPort(fileDescriptor, addressFamily, factory):\n        \"\"\"\n        Add an existing listening I{SOCK_STREAM} socket to the reactor to\n        monitor for new connections to accept and handle.\n\n        @param fileDescriptor: A file descriptor associated with a socket which\n            is already bound to an address and marked as listening.  The socket\n            must be set non-blocking.  Any additional flags (for example,\n            close-on-exec) must also be set by application code.  Application\n            code is responsible for closing the file descriptor, which may be\n            done as soon as C{adoptStreamPort} returns.\n        @type fileDescriptor: C{int}\n\n        @param addressFamily: The address family (or I{domain}) of the socket.\n            For example, L{socket.AF_INET6}.\n\n        @param factory: A L{ServerFactory} instance to use to create new\n            protocols to handle connections accepted via this socket.\n\n        @return: An object providing L{IListeningPort}.\n\n        @raise twisted.internet.error.UnsupportedAddressFamily: If the\n            given address family is not supported by this reactor, or\n            not supported with the given socket type.\n\n        @raise twisted.internet.error.UnsupportedSocketType: If the\n            given socket type is not supported by this reactor, or not\n            supported with the given socket type.\n        \"\"\"\n\n\n    def adoptStreamConnection(fileDescriptor, addressFamily, factory):\n        \"\"\"\n        Add an existing connected I{SOCK_STREAM} socket to the reactor to\n        monitor for data.\n\n        Note that the given factory won't have its C{startFactory} and\n        C{stopFactory} methods called, as there is no sensible time to call\n        them in this situation.\n\n        @param fileDescriptor: A file descriptor associated with a socket which\n            is already connected.  The socket must be set non-blocking.  Any\n            additional flags (for example, close-on-exec) must also be set by\n            application code.  Application code is responsible for closing the\n            file descriptor, which may be done as soon as\n            C{adoptStreamConnection} returns.\n        @type fileDescriptor: C{int}\n\n        @param addressFamily: The address family (or I{domain}) of the socket.\n            For example, L{socket.AF_INET6}.\n\n        @param factory: A L{ServerFactory} instance to use to create a new\n            protocol to handle the connection via this socket.\n\n        @raise UnsupportedAddressFamily: If the given address family is not\n            supported by this reactor, or not supported with the given socket\n            type.\n\n        @raise UnsupportedSocketType: If the given socket type is not supported\n            by this reactor, or not supported with the given socket type.\n        \"\"\"\n\n\n    def adoptDatagramPort(fileDescriptor, addressFamily, protocol,\n                          maxPacketSize=8192):\n        \"\"\"\n        Add an existing listening I{SOCK_DGRAM} socket to the reactor to\n        monitor for read and write readiness.\n\n        @param fileDescriptor: A file descriptor associated with a socket which\n            is already bound to an address and marked as listening.  The socket\n            must be set non-blocking.  Any additional flags (for example,\n            close-on-exec) must also be set by application code.  Application\n            code is responsible for closing the file descriptor, which may be\n            done as soon as C{adoptDatagramPort} returns.\n        @type fileDescriptor: C{int}\n\n        @param addressFamily: The address family or I{domain} of the socket.\n            For example, L{socket.AF_INET6}.\n        @type addressFamily: C{int}\n\n        @param protocol: A L{DatagramProtocol} instance to connect to\n            a UDP transport.\n        @type protocol: L{DatagramProtocol}\n\n        @param maxPacketSize: The maximum packet size to accept.\n        @type maxPacketSize: C{int}\n\n        @return: An object providing L{IListeningPort}.\n\n        @raise UnsupportedAddressFamily: If the given address family is not\n            supported by this reactor, or not supported with the given socket\n            type.\n\n        @raise UnsupportedSocketType: If the given socket type is not supported\n            by this reactor, or not supported with the given socket type.\n        \"\"\"\n\n\n\nclass IReactorProcess(Interface):\n\n    def spawnProcess(processProtocol, executable, args=(), env={}, path=None,\n                     uid=None, gid=None, usePTY=0, childFDs=None):\n        \"\"\"\n        Spawn a process, with a process protocol.\n\n        Arguments given to this function that are listed as L{bytes} or\n        L{unicode} may be encoded or decoded depending on the platform and the\n        argument type given.  On UNIX systems (Linux, FreeBSD, macOS) and\n        Python 2 on Windows, L{unicode} arguments will be encoded down to\n        L{bytes} using the encoding given by L{os.getfilesystemencoding}, to be\n        used with the \"narrow\" OS APIs.  On Python 3 on Windows, L{bytes}\n        arguments will be decoded up to L{unicode} using the encoding given by\n        L{os.getfilesystemencoding} (C{mbcs} before Python 3.6, C{utf8}\n        thereafter) and given to Windows's native \"wide\" APIs.\n\n        @type processProtocol: L{IProcessProtocol} provider\n        @param processProtocol: An object which will be notified of all events\n            related to the created process.\n\n        @param executable: the file name to spawn - the full path should be\n            used.\n        @type executable: L{bytes} or L{unicode}\n\n        @param args: the command line arguments to pass to the process; a\n            sequence of strings.  The first string should be the executable's\n            name.\n        @type args: L{list} with L{bytes} or L{unicode} items.\n\n        @type env: a L{dict} mapping L{bytes}/L{unicode} keys to\n            L{bytes}/L{unicode} items, or L{None}.\n        @param env: the environment variables to pass to the child process.\n            The resulting behavior varies between platforms.  If:\n\n                - C{env} is not set:\n                  - On POSIX: pass an empty environment.\n                  - On Windows: pass L{os.environ}.\n                - C{env} is L{None}:\n                  - On POSIX: pass L{os.environ}.\n                  - On Windows: pass L{os.environ}.\n                - C{env} is a L{dict}:\n                  - On POSIX: pass the key/value pairs in C{env} as the\n                    complete environment.\n                  - On Windows: update L{os.environ} with the key/value\n                    pairs in the L{dict} before passing it. As a\n                    consequence of U{bug #1640\n                    <http://twistedmatrix.com/trac/ticket/1640>}, passing\n                    keys with empty values in an effort to unset\n                    environment variables I{won't} unset them.\n\n        @param path: the path to run the subprocess in - defaults to the\n            current directory.\n        @type path: L{bytes} or L{unicode} or L{None}\n\n        @param uid: user ID to run the subprocess as.  (Only available on POSIX\n            systems.)\n\n        @param gid: group ID to run the subprocess as.  (Only available on\n            POSIX systems.)\n\n        @param usePTY: if true, run this process in a pseudo-terminal.\n            optionally a tuple of C{(masterfd, slavefd, ttyname)}, in which\n            case use those file descriptors.  (Not available on all systems.)\n\n        @param childFDs: A dictionary mapping file descriptors in the new child\n            process to an integer or to the string 'r' or 'w'.\n\n            If the value is an integer, it specifies a file descriptor in the\n            parent process which will be mapped to a file descriptor (specified\n            by the key) in the child process.  This is useful for things like\n            inetd and shell-like file redirection.\n\n            If it is the string 'r', a pipe will be created and attached to the\n            child at that file descriptor: the child will be able to write to\n            that file descriptor and the parent will receive read notification\n            via the L{IProcessProtocol.childDataReceived} callback.  This is\n            useful for the child's stdout and stderr.\n\n            If it is the string 'w', similar setup to the previous case will\n            occur, with the pipe being readable by the child instead of\n            writeable.  The parent process can write to that file descriptor\n            using L{IProcessTransport.writeToChild}.  This is useful for the\n            child's stdin.\n\n            If childFDs is not passed, the default behaviour is to use a\n            mapping that opens the usual stdin/stdout/stderr pipes.\n        @type childFDs: L{dict} of L{int} to L{int} or L{str}\n\n        @see: L{twisted.internet.protocol.ProcessProtocol}\n\n        @return: An object which provides L{IProcessTransport}.\n\n        @raise OSError: Raised with errno C{EAGAIN} or C{ENOMEM} if there are\n            insufficient system resources to create a new process.\n        \"\"\"\n\nclass IReactorTime(Interface):\n    \"\"\"\n    Time methods that a Reactor should implement.\n    \"\"\"\n\n    def seconds():\n        \"\"\"\n        Get the current time in seconds.\n\n        @return: A number-like object of some sort.\n        \"\"\"\n\n\n    def callLater(delay, callable, *args, **kw):\n        \"\"\"\n        Call a function later.\n\n        @type delay:  C{float}\n        @param delay: the number of seconds to wait.\n\n        @param callable: the callable object to call later.\n\n        @param args: the arguments to call it with.\n\n        @param kw: the keyword arguments to call it with.\n\n        @return: An object which provides L{IDelayedCall} and can be used to\n                 cancel the scheduled call, by calling its C{cancel()} method.\n                 It also may be rescheduled by calling its C{delay()} or\n                 C{reset()} methods.\n        \"\"\"\n\n\n    def getDelayedCalls():\n        \"\"\"\n        Retrieve all currently scheduled delayed calls.\n\n        @return: A list of L{IDelayedCall} providers representing all\n                 currently scheduled calls. This is everything that has been\n                 returned by C{callLater} but not yet called or cancelled.\n        \"\"\"\n\n\nclass IDelayedCall(Interface):\n    \"\"\"\n    A scheduled call.\n\n    There are probably other useful methods we can add to this interface;\n    suggestions are welcome.\n    \"\"\"\n\n    def getTime():\n        \"\"\"\n        Get time when delayed call will happen.\n\n        @return: time in seconds since epoch (a float).\n        \"\"\"\n\n    def cancel():\n        \"\"\"\n        Cancel the scheduled call.\n\n        @raises twisted.internet.error.AlreadyCalled: if the call has already\n            happened.\n        @raises twisted.internet.error.AlreadyCancelled: if the call has already\n            been cancelled.\n        \"\"\"\n\n    def delay(secondsLater):\n        \"\"\"\n        Delay the scheduled call.\n\n        @param secondsLater: how many seconds from its current firing time to delay\n\n        @raises twisted.internet.error.AlreadyCalled: if the call has already\n            happened.\n        @raises twisted.internet.error.AlreadyCancelled: if the call has already\n            been cancelled.\n        \"\"\"\n\n    def reset(secondsFromNow):\n        \"\"\"\n        Reset the scheduled call's timer.\n\n        @param secondsFromNow: how many seconds from now it should fire,\n            equivalent to C{.cancel()} and then doing another\n            C{reactor.callLater(secondsLater, ...)}\n\n        @raises twisted.internet.error.AlreadyCalled: if the call has already\n            happened.\n        @raises twisted.internet.error.AlreadyCancelled: if the call has already\n            been cancelled.\n        \"\"\"\n\n    def active():\n        \"\"\"\n        @return: True if this call is still active, False if it has been\n                 called or cancelled.\n        \"\"\"\n\n\n\nclass IReactorFromThreads(Interface):\n    \"\"\"\n    This interface is the set of thread-safe methods which may be invoked on\n    the reactor from other threads.\n\n    @since: 15.4\n    \"\"\"\n\n    def callFromThread(callable, *args, **kw):\n        \"\"\"\n        Cause a function to be executed by the reactor thread.\n\n        Use this method when you want to run a function in the reactor's thread\n        from another thread.  Calling L{callFromThread} should wake up the main\n        thread (where L{reactor.run() <IReactorCore.run>} is executing) and run\n        the given callable in that thread.\n\n        If you're writing a multi-threaded application the C{callable} may need\n        to be thread safe, but this method doesn't require it as such.  If you\n        want to call a function in the next mainloop iteration, but you're in\n        the same thread, use L{callLater} with a delay of 0.\n        \"\"\"\n\n\nclass IReactorInThreads(Interface):\n    \"\"\"\n    This interface contains the methods exposed by a reactor which will let you\n    run functions in another thread.\n\n    @since: 15.4\n    \"\"\"\n\n    def callInThread(callable, *args, **kwargs):\n        \"\"\"\n        Run the given callable object in a separate thread, with the given\n        arguments and keyword arguments.\n        \"\"\"\n\n\n\nclass IReactorThreads(IReactorFromThreads, IReactorInThreads):\n    \"\"\"\n    Dispatch methods to be run in threads.\n\n    Internally, this should use a thread pool and dispatch methods to them.\n    \"\"\"\n\n    def getThreadPool():\n        \"\"\"\n        Return the threadpool used by L{IReactorInThreads.callInThread}.\n        Create it first if necessary.\n\n        @rtype: L{twisted.python.threadpool.ThreadPool}\n        \"\"\"\n\n\n    def suggestThreadPoolSize(size):\n        \"\"\"\n        Suggest the size of the internal threadpool used to dispatch functions\n        passed to L{IReactorInThreads.callInThread}.\n        \"\"\"\n\n\n\nclass IReactorCore(Interface):\n    \"\"\"\n    Core methods that a Reactor must implement.\n    \"\"\"\n\n    running = Attribute(\n        \"A C{bool} which is C{True} from I{during startup} to \"\n        \"I{during shutdown} and C{False} the rest of the time.\")\n\n\n    def resolve(name, timeout=10):\n        \"\"\"\n        Return a L{twisted.internet.defer.Deferred} that will resolve a hostname.\n        \"\"\"\n\n    def run():\n        \"\"\"\n        Fire 'startup' System Events, move the reactor to the 'running'\n        state, then run the main loop until it is stopped with C{stop()} or\n        C{crash()}.\n        \"\"\"\n\n    def stop():\n        \"\"\"\n        Fire 'shutdown' System Events, which will move the reactor to the\n        'stopped' state and cause C{reactor.run()} to exit.\n        \"\"\"\n\n    def crash():\n        \"\"\"\n        Stop the main loop *immediately*, without firing any system events.\n\n        This is named as it is because this is an extremely \"rude\" thing to do;\n        it is possible to lose data and put your system in an inconsistent\n        state by calling this.  However, it is necessary, as sometimes a system\n        can become wedged in a pre-shutdown call.\n        \"\"\"\n\n    def iterate(delay=0):\n        \"\"\"\n        Run the main loop's I/O polling function for a period of time.\n\n        This is most useful in applications where the UI is being drawn \"as\n        fast as possible\", such as games. All pending L{IDelayedCall}s will\n        be called.\n\n        The reactor must have been started (via the C{run()} method) prior to\n        any invocations of this method.  It must also be stopped manually\n        after the last call to this method (via the C{stop()} method).  This\n        method is not re-entrant: you must not call it recursively; in\n        particular, you must not call it while the reactor is running.\n        \"\"\"\n\n    def fireSystemEvent(eventType):\n        \"\"\"\n        Fire a system-wide event.\n\n        System-wide events are things like 'startup', 'shutdown', and\n        'persist'.\n        \"\"\"\n\n    def addSystemEventTrigger(phase, eventType, callable, *args, **kw):\n        \"\"\"\n        Add a function to be called when a system event occurs.\n\n        Each \"system event\" in Twisted, such as 'startup', 'shutdown', and\n        'persist', has 3 phases: 'before', 'during', and 'after' (in that\n        order, of course).  These events will be fired internally by the\n        Reactor.\n\n        An implementor of this interface must only implement those events\n        described here.\n\n        Callbacks registered for the \"before\" phase may return either None or a\n        Deferred.  The \"during\" phase will not execute until all of the\n        Deferreds from the \"before\" phase have fired.\n\n        Once the \"during\" phase is running, all of the remaining triggers must\n        execute; their return values must be ignored.\n\n        @param phase: a time to call the event -- either the string 'before',\n                      'after', or 'during', describing when to call it\n                      relative to the event's execution.\n\n        @param eventType: this is a string describing the type of event.\n\n        @param callable: the object to call before shutdown.\n\n        @param args: the arguments to call it with.\n\n        @param kw: the keyword arguments to call it with.\n\n        @return: an ID that can be used to remove this call with\n                 removeSystemEventTrigger.\n        \"\"\"\n\n    def removeSystemEventTrigger(triggerID):\n        \"\"\"\n        Removes a trigger added with addSystemEventTrigger.\n\n        @param triggerID: a value returned from addSystemEventTrigger.\n\n        @raise KeyError: If there is no system event trigger for the given\n            C{triggerID}.\n\n        @raise ValueError: If there is no system event trigger for the given\n            C{triggerID}.\n\n        @raise TypeError: If there is no system event trigger for the given\n            C{triggerID}.\n        \"\"\"\n\n    def callWhenRunning(callable, *args, **kw):\n        \"\"\"\n        Call a function when the reactor is running.\n\n        If the reactor has not started, the callable will be scheduled\n        to run when it does start. Otherwise, the callable will be invoked\n        immediately.\n\n        @param callable: the callable object to call later.\n\n        @param args: the arguments to call it with.\n\n        @param kw: the keyword arguments to call it with.\n\n        @return: None if the callable was invoked, otherwise a system\n                 event id for the scheduled call.\n        \"\"\"\n\n\n\nclass IReactorPluggableResolver(Interface):\n    \"\"\"\n    An L{IReactorPluggableResolver} is a reactor which can be customized with\n    an L{IResolverSimple}.  This is a fairly limited interface, that supports\n    only IPv4; you should use L{IReactorPluggableNameResolver} instead.\n\n    @see: L{IReactorPluggableNameResolver}\n    \"\"\"\n\n    def installResolver(resolver):\n        \"\"\"\n        Set the internal resolver to use to for name lookups.\n\n        @type resolver: An object implementing the L{IResolverSimple} interface\n        @param resolver: The new resolver to use.\n\n        @return: The previously installed resolver.\n        @rtype: L{IResolverSimple}\n        \"\"\"\n\n\n\nclass IReactorPluggableNameResolver(Interface):\n    \"\"\"\n    An L{IReactorPluggableNameResolver} is a reactor whose name resolver can be\n    set to a user-supplied object.\n    \"\"\"\n\n    nameResolver = Attribute(\n        \"\"\"\n        Read-only attribute; the resolver installed with L{installResolver}.\n        An L{IHostnameResolver}.\n        \"\"\"\n    )\n\n    def installNameResolver(resolver):\n        \"\"\"\n        Set the internal resolver to use for name lookups.\n\n        @type resolver: An object providing the L{IHostnameResolver} interface.\n        @param resolver: The new resolver to use.\n\n        @return: The previously installed resolver.\n        @rtype: L{IHostnameResolver}\n        \"\"\"\n\n\n\nclass IReactorDaemonize(Interface):\n    \"\"\"\n    A reactor which provides hooks that need to be called before and after\n    daemonization.\n\n    Notes:\n       - This interface SHOULD NOT be called by applications.\n       - This interface should only be implemented by reactors as a workaround\n         (in particular, it's implemented currently only by kqueue()).\n         For details please see the comments on ticket #1918.\n    \"\"\"\n\n    def beforeDaemonize():\n        \"\"\"\n        Hook to be called immediately before daemonization. No reactor methods\n        may be called until L{afterDaemonize} is called.\n\n        @return: L{None}.\n        \"\"\"\n\n\n    def afterDaemonize():\n        \"\"\"\n        Hook to be called immediately after daemonization. This may only be\n        called after L{beforeDaemonize} had been called previously.\n\n        @return: L{None}.\n        \"\"\"\n\n\n\nclass IReactorFDSet(Interface):\n    \"\"\"\n    Implement me to be able to use L{IFileDescriptor} type resources.\n\n    This assumes that your main-loop uses UNIX-style numeric file descriptors\n    (or at least similarly opaque IDs returned from a .fileno() method)\n    \"\"\"\n\n    def addReader(reader):\n        \"\"\"\n        I add reader to the set of file descriptors to get read events for.\n\n        @param reader: An L{IReadDescriptor} provider that will be checked for\n                       read events until it is removed from the reactor with\n                       L{removeReader}.\n\n        @return: L{None}.\n        \"\"\"\n\n    def addWriter(writer):\n        \"\"\"\n        I add writer to the set of file descriptors to get write events for.\n\n        @param writer: An L{IWriteDescriptor} provider that will be checked for\n                       write events until it is removed from the reactor with\n                       L{removeWriter}.\n\n        @return: L{None}.\n        \"\"\"\n\n    def removeReader(reader):\n        \"\"\"\n        Removes an object previously added with L{addReader}.\n\n        @return: L{None}.\n        \"\"\"\n\n    def removeWriter(writer):\n        \"\"\"\n        Removes an object previously added with L{addWriter}.\n\n        @return: L{None}.\n        \"\"\"\n\n    def removeAll():\n        \"\"\"\n        Remove all readers and writers.\n\n        Should not remove reactor internal reactor connections (like a waker).\n\n        @return: A list of L{IReadDescriptor} and L{IWriteDescriptor} providers\n                 which were removed.\n        \"\"\"\n\n    def getReaders():\n        \"\"\"\n        Return the list of file descriptors currently monitored for input\n        events by the reactor.\n\n        @return: the list of file descriptors monitored for input events.\n        @rtype: C{list} of C{IReadDescriptor}\n        \"\"\"\n\n    def getWriters():\n        \"\"\"\n        Return the list file descriptors currently monitored for output events\n        by the reactor.\n\n        @return: the list of file descriptors monitored for output events.\n        @rtype: C{list} of C{IWriteDescriptor}\n        \"\"\"\n\n\nclass IListeningPort(Interface):\n    \"\"\"\n    A listening port.\n    \"\"\"\n\n    def startListening():\n        \"\"\"\n        Start listening on this port.\n\n        @raise CannotListenError: If it cannot listen on this port (e.g., it is\n                                  a TCP port and it cannot bind to the required\n                                  port number).\n        \"\"\"\n\n    def stopListening():\n        \"\"\"\n        Stop listening on this port.\n\n        If it does not complete immediately, will return Deferred that fires\n        upon completion.\n        \"\"\"\n\n    def getHost():\n        \"\"\"\n        Get the host that this port is listening for.\n\n        @return: An L{IAddress} provider.\n        \"\"\"\n\n\nclass ILoggingContext(Interface):\n    \"\"\"\n    Give context information that will be used to log events generated by\n    this item.\n    \"\"\"\n\n    def logPrefix():\n        \"\"\"\n        @return: Prefix used during log formatting to indicate context.\n        @rtype: C{str}\n        \"\"\"\n\n\n\nclass IFileDescriptor(ILoggingContext):\n    \"\"\"\n    An interface representing a UNIX-style numeric file descriptor.\n    \"\"\"\n\n    def fileno():\n        \"\"\"\n        @raise: If the descriptor no longer has a valid file descriptor\n            number associated with it.\n\n        @return: The platform-specified representation of a file descriptor\n            number.  Or C{-1} if the descriptor no longer has a valid file\n            descriptor number associated with it.  As long as the descriptor\n            is valid, calls to this method on a particular instance must\n            return the same value.\n        \"\"\"\n\n\n    def connectionLost(reason):\n        \"\"\"\n        Called when the connection was lost.\n\n        This is called when the connection on a selectable object has been\n        lost.  It will be called whether the connection was closed explicitly,\n        an exception occurred in an event handler, or the other end of the\n        connection closed it first.\n\n        See also L{IHalfCloseableDescriptor} if your descriptor wants to be\n        notified separately of the two halves of the connection being closed.\n\n        @param reason: A failure instance indicating the reason why the\n                       connection was lost.  L{error.ConnectionLost} and\n                       L{error.ConnectionDone} are of special note, but the\n                       failure may be of other classes as well.\n        \"\"\"\n\n\n\nclass IReadDescriptor(IFileDescriptor):\n    \"\"\"\n    An L{IFileDescriptor} that can read.\n\n    This interface is generally used in conjunction with L{IReactorFDSet}.\n    \"\"\"\n\n    def doRead():\n        \"\"\"\n        Some data is available for reading on your descriptor.\n\n        @return: If an error is encountered which causes the descriptor to\n            no longer be valid, a L{Failure} should be returned.  Otherwise,\n            L{None}.\n        \"\"\"\n\n\nclass IWriteDescriptor(IFileDescriptor):\n    \"\"\"\n    An L{IFileDescriptor} that can write.\n\n    This interface is generally used in conjunction with L{IReactorFDSet}.\n    \"\"\"\n\n    def doWrite():\n        \"\"\"\n        Some data can be written to your descriptor.\n\n        @return: If an error is encountered which causes the descriptor to\n            no longer be valid, a L{Failure} should be returned.  Otherwise,\n            L{None}.\n        \"\"\"\n\n\nclass IReadWriteDescriptor(IReadDescriptor, IWriteDescriptor):\n    \"\"\"\n    An L{IFileDescriptor} that can both read and write.\n    \"\"\"\n\n\nclass IHalfCloseableDescriptor(Interface):\n    \"\"\"\n    A descriptor that can be half-closed.\n    \"\"\"\n\n    def writeConnectionLost(reason):\n        \"\"\"\n        Indicates write connection was lost.\n        \"\"\"\n\n    def readConnectionLost(reason):\n        \"\"\"\n        Indicates read connection was lost.\n        \"\"\"\n\n\nclass ISystemHandle(Interface):\n    \"\"\"\n    An object that wraps a networking OS-specific handle.\n    \"\"\"\n\n    def getHandle():\n        \"\"\"\n        Return a system- and reactor-specific handle.\n\n        This might be a socket.socket() object, or some other type of\n        object, depending on which reactor is being used. Use and\n        manipulate at your own risk.\n\n        This might be used in cases where you want to set specific\n        options not exposed by the Twisted APIs.\n        \"\"\"\n\n\nclass IConsumer(Interface):\n    \"\"\"\n    A consumer consumes data from a producer.\n    \"\"\"\n\n    def registerProducer(producer, streaming):\n        \"\"\"\n        Register to receive data from a producer.\n\n        This sets self to be a consumer for a producer.  When this object runs\n        out of data (as when a send(2) call on a socket succeeds in moving the\n        last data from a userspace buffer into a kernelspace buffer), it will\n        ask the producer to resumeProducing().\n\n        For L{IPullProducer} providers, C{resumeProducing} will be called once\n        each time data is required.\n\n        For L{IPushProducer} providers, C{pauseProducing} will be called\n        whenever the write buffer fills up and C{resumeProducing} will only be\n        called when it empties.  The consumer will only call C{resumeProducing}\n        to balance a previous C{pauseProducing} call; the producer is assumed\n        to start in an un-paused state.\n\n        @type producer: L{IProducer} provider\n\n        @type streaming: C{bool}\n        @param streaming: C{True} if C{producer} provides L{IPushProducer},\n        C{False} if C{producer} provides L{IPullProducer}.\n\n        @raise RuntimeError: If a producer is already registered.\n\n        @return: L{None}\n        \"\"\"\n\n\n    def unregisterProducer():\n        \"\"\"\n        Stop consuming data from a producer, without disconnecting.\n        \"\"\"\n\n\n    def write(data):\n        \"\"\"\n        The producer will write data by calling this method.\n\n        The implementation must be non-blocking and perform whatever\n        buffering is necessary.  If the producer has provided enough data\n        for now and it is a L{IPushProducer}, the consumer may call its\n        C{pauseProducing} method.\n        \"\"\"\n\n\n\nclass IProducer(Interface):\n    \"\"\"\n    A producer produces data for a consumer.\n\n    Typically producing is done by calling the C{write} method of a class\n    implementing L{IConsumer}.\n    \"\"\"\n\n    def stopProducing():\n        \"\"\"\n        Stop producing data.\n\n        This tells a producer that its consumer has died, so it must stop\n        producing data for good.\n        \"\"\"\n\n\nclass IPushProducer(IProducer):\n    \"\"\"\n    A push producer, also known as a streaming producer is expected to\n    produce (write to this consumer) data on a continuous basis, unless\n    it has been paused. A paused push producer will resume producing\n    after its C{resumeProducing()} method is called.   For a push producer\n    which is not pauseable, these functions may be noops.\n    \"\"\"\n\n    def pauseProducing():\n        \"\"\"\n        Pause producing data.\n\n        Tells a producer that it has produced too much data to process for\n        the time being, and to stop until C{resumeProducing()} is called.\n        \"\"\"\n    def resumeProducing():\n        \"\"\"\n        Resume producing data.\n\n        This tells a producer to re-add itself to the main loop and produce\n        more data for its consumer.\n        \"\"\"\n\n\n\nclass IPullProducer(IProducer):\n    \"\"\"\n    A pull producer, also known as a non-streaming producer, is\n    expected to produce data each time L{resumeProducing()} is called.\n    \"\"\"\n\n    def resumeProducing():\n        \"\"\"\n        Produce data for the consumer a single time.\n\n        This tells a producer to produce data for the consumer once\n        (not repeatedly, once only). Typically this will be done\n        by calling the consumer's C{write} method a single time with\n        produced data. The producer should produce data before returning\n        from C{resumeProducing()}, that is, it should not schedule a deferred\n        write.\n        \"\"\"\n\n\n\nclass IProtocol(Interface):\n\n    def dataReceived(data):\n        \"\"\"\n        Called whenever data is received.\n\n        Use this method to translate to a higher-level message.  Usually, some\n        callback will be made upon the receipt of each complete protocol\n        message.\n\n        Please keep in mind that you will probably need to buffer some data\n        as partial (or multiple) protocol messages may be received!  We\n        recommend that unit tests for protocols call through to this method\n        with differing chunk sizes, down to one byte at a time.\n\n        @param data: bytes of indeterminate length\n        @type data: L{bytes}\n        \"\"\"\n\n    def connectionLost(reason):\n        \"\"\"\n        Called when the connection is shut down.\n\n        Clear any circular references here, and any external references\n        to this Protocol.  The connection has been closed. The C{reason}\n        Failure wraps a L{twisted.internet.error.ConnectionDone} or\n        L{twisted.internet.error.ConnectionLost} instance (or a subclass\n        of one of those).\n\n        @type reason: L{twisted.python.failure.Failure}\n        \"\"\"\n\n    def makeConnection(transport):\n        \"\"\"\n        Make a connection to a transport and a server.\n        \"\"\"\n\n    def connectionMade():\n        \"\"\"\n        Called when a connection is made.\n\n        This may be considered the initializer of the protocol, because\n        it is called when the connection is completed.  For clients,\n        this is called once the connection to the server has been\n        established; for servers, this is called after an accept() call\n        stops blocking and a socket has been received.  If you need to\n        send any greeting or initial message, do it here.\n        \"\"\"\n\n\nclass IProcessProtocol(Interface):\n    \"\"\"\n    Interface for process-related event handlers.\n    \"\"\"\n\n    def makeConnection(process):\n        \"\"\"\n        Called when the process has been created.\n\n        @type process: L{IProcessTransport} provider\n        @param process: An object representing the process which has been\n            created and associated with this protocol.\n        \"\"\"\n\n\n    def childDataReceived(childFD, data):\n        \"\"\"\n        Called when data arrives from the child process.\n\n        @type childFD: L{int}\n        @param childFD: The file descriptor from which the data was\n            received.\n\n        @type data: L{bytes}\n        @param data: The data read from the child's file descriptor.\n        \"\"\"\n\n\n    def childConnectionLost(childFD):\n        \"\"\"\n        Called when a file descriptor associated with the child process is\n        closed.\n\n        @type childFD: C{int}\n        @param childFD: The file descriptor which was closed.\n        \"\"\"\n\n\n    def processExited(reason):\n        \"\"\"\n        Called when the child process exits.\n\n        @type reason: L{twisted.python.failure.Failure}\n        @param reason: A failure giving the reason the child process\n            terminated.  The type of exception for this failure is either\n            L{twisted.internet.error.ProcessDone} or\n            L{twisted.internet.error.ProcessTerminated}.\n\n        @since: 8.2\n        \"\"\"\n\n\n    def processEnded(reason):\n        \"\"\"\n        Called when the child process exits and all file descriptors associated\n        with it have been closed.\n\n        @type reason: L{twisted.python.failure.Failure}\n        @param reason: A failure giving the reason the child process\n            terminated.  The type of exception for this failure is either\n            L{twisted.internet.error.ProcessDone} or\n            L{twisted.internet.error.ProcessTerminated}.\n        \"\"\"\n\n\n\nclass IHalfCloseableProtocol(Interface):\n    \"\"\"\n    Implemented to indicate they want notification of half-closes.\n\n    TCP supports the notion of half-closing the connection, e.g.\n    closing the write side but still not stopping reading. A protocol\n    that implements this interface will be notified of such events,\n    instead of having connectionLost called.\n    \"\"\"\n\n    def readConnectionLost():\n        \"\"\"\n        Notification of the read connection being closed.\n\n        This indicates peer did half-close of write side. It is now\n        the responsibility of the this protocol to call\n        loseConnection().  In addition, the protocol MUST make sure a\n        reference to it still exists (i.e. by doing a callLater with\n        one of its methods, etc.)  as the reactor will only have a\n        reference to it if it is writing.\n\n        If the protocol does not do so, it might get garbage collected\n        without the connectionLost method ever being called.\n        \"\"\"\n\n    def writeConnectionLost():\n        \"\"\"\n        Notification of the write connection being closed.\n\n        This will never be called for TCP connections as TCP does not\n        support notification of this type of half-close.\n        \"\"\"\n\n\n\nclass IHandshakeListener(Interface):\n    \"\"\"\n    An interface implemented by a L{IProtocol} to indicate that it would like\n    to be notified when TLS handshakes complete when run over a TLS-based\n    transport.\n\n    This interface is only guaranteed to be called when run over a TLS-based\n    transport: non TLS-based transports will not respect this interface.\n    \"\"\"\n\n    def handshakeCompleted():\n        \"\"\"\n        Notification of the TLS handshake being completed.\n\n        This notification fires when OpenSSL has completed the TLS handshake.\n        At this point the TLS connection is established, and the protocol can\n        interrogate its transport (usually an L{ISSLTransport}) for details of\n        the TLS connection.\n\n        This notification *also* fires whenever the TLS session is\n        renegotiated. As a result, protocols that have certain minimum security\n        requirements should implement this interface to ensure that they are\n        able to re-evaluate the security of the TLS session if it changes.\n        \"\"\"\n\n\n\nclass IFileDescriptorReceiver(Interface):\n    \"\"\"\n    Protocols may implement L{IFileDescriptorReceiver} to receive file\n    descriptors sent to them.  This is useful in conjunction with\n    L{IUNIXTransport}, which allows file descriptors to be sent between\n    processes on a single host.\n    \"\"\"\n    def fileDescriptorReceived(descriptor):\n        \"\"\"\n        Called when a file descriptor is received over the connection.\n\n        @param descriptor: The descriptor which was received.\n        @type descriptor: C{int}\n\n        @return: L{None}\n        \"\"\"\n\n\n\nclass IProtocolFactory(Interface):\n    \"\"\"\n    Interface for protocol factories.\n    \"\"\"\n\n    def buildProtocol(addr):\n        \"\"\"\n        Called when a connection has been established to addr.\n\n        If None is returned, the connection is assumed to have been refused,\n        and the Port will close the connection.\n\n        @type addr: (host, port)\n        @param addr: The address of the newly-established connection\n\n        @return: None if the connection was refused, otherwise an object\n                 providing L{IProtocol}.\n        \"\"\"\n\n    def doStart():\n        \"\"\"\n        Called every time this is connected to a Port or Connector.\n        \"\"\"\n\n    def doStop():\n        \"\"\"\n        Called every time this is unconnected from a Port or Connector.\n        \"\"\"\n\n\nclass ITransport(Interface):\n    \"\"\"\n    I am a transport for bytes.\n\n    I represent (and wrap) the physical connection and synchronicity\n    of the framework which is talking to the network.  I make no\n    representations about whether calls to me will happen immediately\n    or require returning to a control loop, or whether they will happen\n    in the same or another thread.  Consider methods of this class\n    (aside from getPeer) to be 'thrown over the wall', to happen at some\n    indeterminate time.\n    \"\"\"\n\n    def write(data):\n        \"\"\"\n        Write some data to the physical connection, in sequence, in a\n        non-blocking fashion.\n\n        If possible, make sure that it is all written.  No data will\n        ever be lost, although (obviously) the connection may be closed\n        before it all gets through.\n\n        @type data: L{bytes}\n        @param data: The data to write.\n        \"\"\"\n\n    def writeSequence(data):\n        \"\"\"\n        Write an iterable of byte strings to the physical connection.\n\n        If possible, make sure that all of the data is written to\n        the socket at once, without first copying it all into a\n        single byte string.\n\n        @type data: an iterable of L{bytes}\n        @param data: The data to write.\n        \"\"\"\n\n    def loseConnection():\n        \"\"\"\n        Close my connection, after writing all pending data.\n\n        Note that if there is a registered producer on a transport it\n        will not be closed until the producer has been unregistered.\n        \"\"\"\n\n    def getPeer():\n        \"\"\"\n        Get the remote address of this connection.\n\n        Treat this method with caution.  It is the unfortunate result of the\n        CGI and Jabber standards, but should not be considered reliable for\n        the usual host of reasons; port forwarding, proxying, firewalls, IP\n        masquerading, etc.\n\n        @return: An L{IAddress} provider.\n        \"\"\"\n\n    def getHost():\n        \"\"\"\n        Similar to getPeer, but returns an address describing this side of the\n        connection.\n\n        @return: An L{IAddress} provider.\n        \"\"\"\n\n\nclass ITCPTransport(ITransport):\n    \"\"\"\n    A TCP based transport.\n    \"\"\"\n\n    def loseWriteConnection():\n        \"\"\"\n        Half-close the write side of a TCP connection.\n\n        If the protocol instance this is attached to provides\n        IHalfCloseableProtocol, it will get notified when the operation is\n        done. When closing write connection, as with loseConnection this will\n        only happen when buffer has emptied and there is no registered\n        producer.\n        \"\"\"\n\n\n    def abortConnection():\n        \"\"\"\n        Close the connection abruptly.\n\n        Discards any buffered data, stops any registered producer,\n        and, if possible, notifies the other end of the unclean\n        closure.\n\n        @since: 11.1\n        \"\"\"\n\n\n    def getTcpNoDelay():\n        \"\"\"\n        Return if C{TCP_NODELAY} is enabled.\n        \"\"\"\n\n    def setTcpNoDelay(enabled):\n        \"\"\"\n        Enable/disable C{TCP_NODELAY}.\n\n        Enabling C{TCP_NODELAY} turns off Nagle's algorithm. Small packets are\n        sent sooner, possibly at the expense of overall throughput.\n        \"\"\"\n\n    def getTcpKeepAlive():\n        \"\"\"\n        Return if C{SO_KEEPALIVE} is enabled.\n        \"\"\"\n\n    def setTcpKeepAlive(enabled):\n        \"\"\"\n        Enable/disable C{SO_KEEPALIVE}.\n\n        Enabling C{SO_KEEPALIVE} sends packets periodically when the connection\n        is otherwise idle, usually once every two hours. They are intended\n        to allow detection of lost peers in a non-infinite amount of time.\n        \"\"\"\n\n    def getHost():\n        \"\"\"\n        Returns L{IPv4Address} or L{IPv6Address}.\n        \"\"\"\n\n    def getPeer():\n        \"\"\"\n        Returns L{IPv4Address} or L{IPv6Address}.\n        \"\"\"\n\n\n\nclass IUNIXTransport(ITransport):\n    \"\"\"\n    Transport for stream-oriented unix domain connections.\n    \"\"\"\n    def sendFileDescriptor(descriptor):\n        \"\"\"\n        Send a duplicate of this (file, socket, pipe, etc) descriptor to the\n        other end of this connection.\n\n        The send is non-blocking and will be queued if it cannot be performed\n        immediately.  The send will be processed in order with respect to other\n        C{sendFileDescriptor} calls on this transport, but not necessarily with\n        respect to C{write} calls on this transport.  The send can only be\n        processed if there are also bytes in the normal connection-oriented send\n        buffer (ie, you must call C{write} at least as many times as you call\n        C{sendFileDescriptor}).\n\n        @param descriptor: An C{int} giving a valid file descriptor in this\n            process.  Note that a I{file descriptor} may actually refer to a\n            socket, a pipe, or anything else POSIX tries to treat in the same\n            way as a file.\n\n        @return: L{None}\n        \"\"\"\n\n\n\nclass IOpenSSLServerConnectionCreator(Interface):\n    \"\"\"\n    A provider of L{IOpenSSLServerConnectionCreator} can create\n    L{OpenSSL.SSL.Connection} objects for TLS servers.\n\n    @see: L{twisted.internet.ssl}\n\n    @note: Creating OpenSSL connection objects is subtle, error-prone, and\n        security-critical.  Before implementing this interface yourself,\n        consider using L{twisted.internet.ssl.CertificateOptions} as your\n        C{contextFactory}.  (For historical reasons, that class does not\n        actually I{implement} this interface; nevertheless it is usable in all\n        Twisted APIs which require a provider of this interface.)\n    \"\"\"\n\n    def serverConnectionForTLS(tlsProtocol):\n        \"\"\"\n        Create a connection for the given server protocol.\n\n        @param tlsProtocol: the protocol server making the request.\n        @type tlsProtocol: L{twisted.protocols.tls.TLSMemoryBIOProtocol}.\n\n        @return: an OpenSSL connection object configured appropriately for the\n            given Twisted protocol.\n        @rtype: L{OpenSSL.SSL.Connection}\n        \"\"\"\n\n\n\nclass IOpenSSLClientConnectionCreator(Interface):\n    \"\"\"\n    A provider of L{IOpenSSLClientConnectionCreator} can create\n    L{OpenSSL.SSL.Connection} objects for TLS clients.\n\n    @see: L{twisted.internet.ssl}\n\n    @note: Creating OpenSSL connection objects is subtle, error-prone, and\n        security-critical.  Before implementing this interface yourself,\n        consider using L{twisted.internet.ssl.optionsForClientTLS} as your\n        C{contextFactory}.\n    \"\"\"\n\n    def clientConnectionForTLS(tlsProtocol):\n        \"\"\"\n        Create a connection for the given client protocol.\n\n        @param tlsProtocol: the client protocol making the request.\n        @type tlsProtocol: L{twisted.protocols.tls.TLSMemoryBIOProtocol}.\n\n        @return: an OpenSSL connection object configured appropriately for the\n            given Twisted protocol.\n        @rtype: L{OpenSSL.SSL.Connection}\n        \"\"\"\n\n\n\nclass IProtocolNegotiationFactory(Interface):\n    \"\"\"\n    A provider of L{IProtocolNegotiationFactory} can provide information about\n    the various protocols that the factory can create implementations of. This\n    can be used, for example, to provide protocol names for Next Protocol\n    Negotiation and Application Layer Protocol Negotiation.\n\n    @see: L{twisted.internet.ssl}\n    \"\"\"\n\n    def acceptableProtocols():\n        \"\"\"\n        Returns a list of protocols that can be spoken by the connection\n        factory in the form of ALPN tokens, as laid out in the IANA registry\n        for ALPN tokens.\n\n        @return: a list of ALPN tokens in order of preference.\n        @rtype: L{list} of L{bytes}\n        \"\"\"\n\n\n\nclass IOpenSSLContextFactory(Interface):\n    \"\"\"\n    A provider of L{IOpenSSLContextFactory} is capable of generating\n    L{OpenSSL.SSL.Context} classes suitable for configuring TLS on a\n    connection. A provider will store enough state to be able to generate these\n    contexts as needed for individual connections.\n\n    @see: L{twisted.internet.ssl}\n    \"\"\"\n\n    def getContext():\n        \"\"\"\n        Returns a TLS context object, suitable for securing a TLS connection.\n        This context object will be appropriately customized for the connection\n        based on the state in this object.\n\n        @return: A TLS context object.\n        @rtype: L{OpenSSL.SSL.Context}\n        \"\"\"\n\n\n\nclass ITLSTransport(ITCPTransport):\n    \"\"\"\n    A TCP transport that supports switching to TLS midstream.\n\n    Once TLS mode is started the transport will implement L{ISSLTransport}.\n    \"\"\"\n\n    def startTLS(contextFactory):\n        \"\"\"\n        Initiate TLS negotiation.\n\n        @param contextFactory: An object which creates appropriately configured\n            TLS connections.\n\n            For clients, use L{twisted.internet.ssl.optionsForClientTLS}; for\n            servers, use L{twisted.internet.ssl.CertificateOptions}.\n\n        @type contextFactory: L{IOpenSSLClientConnectionCreator} or\n            L{IOpenSSLServerConnectionCreator}, depending on whether this\n            L{ITLSTransport} is a server or not.  If the appropriate interface\n            is not provided by the value given for C{contextFactory}, it must\n            be an implementor of L{IOpenSSLContextFactory}.\n        \"\"\"\n\n\n\nclass ISSLTransport(ITCPTransport):\n    \"\"\"\n    A SSL/TLS based transport.\n    \"\"\"\n\n    def getPeerCertificate():\n        \"\"\"\n        Return an object with the peer's certificate info.\n        \"\"\"\n\n\n\nclass INegotiated(ISSLTransport):\n    \"\"\"\n    A TLS based transport that supports using ALPN/NPN to negotiate the\n    protocol to be used inside the encrypted tunnel.\n    \"\"\"\n    negotiatedProtocol = Attribute(\n        \"\"\"\n        The protocol selected to be spoken using ALPN/NPN. The result from ALPN\n        is preferred to the result from NPN if both were used. If the remote\n        peer does not support ALPN or NPN, or neither NPN or ALPN are available\n        on this machine, will be L{None}. Otherwise, will be the name of the\n        selected protocol as C{bytes}. Note that until the handshake has\n        completed this property may incorrectly return L{None}: wait until data\n        has been received before trusting it (see\n        https://twistedmatrix.com/trac/ticket/6024).\n        \"\"\"\n    )\n\n\n\nclass ICipher(Interface):\n    \"\"\"\n    A TLS cipher.\n    \"\"\"\n    fullName = Attribute(\n        \"The fully qualified name of the cipher in L{unicode}.\"\n    )\n\n\n\nclass IAcceptableCiphers(Interface):\n    \"\"\"\n    A list of acceptable ciphers for a TLS context.\n    \"\"\"\n    def selectCiphers(availableCiphers):\n        \"\"\"\n        Choose which ciphers to allow to be negotiated on a TLS connection.\n\n        @param availableCiphers: A L{list} of L{ICipher} which gives the names\n            of all ciphers supported by the TLS implementation in use.\n\n        @return: A L{list} of L{ICipher} which represents the ciphers\n            which may be negotiated on the TLS connection.  The result is\n            ordered by preference with more preferred ciphers appearing\n            earlier.\n        \"\"\"\n\n\n\nclass IProcessTransport(ITransport):\n    \"\"\"\n    A process transport.\n    \"\"\"\n\n    pid = Attribute(\n        \"From before L{IProcessProtocol.makeConnection} is called to before \"\n        \"L{IProcessProtocol.processEnded} is called, C{pid} is an L{int} \"\n        \"giving the platform process ID of this process.  C{pid} is L{None} \"\n        \"at all other times.\")\n\n    def closeStdin():\n        \"\"\"\n        Close stdin after all data has been written out.\n        \"\"\"\n\n    def closeStdout():\n        \"\"\"\n        Close stdout.\n        \"\"\"\n\n    def closeStderr():\n        \"\"\"\n        Close stderr.\n        \"\"\"\n\n    def closeChildFD(descriptor):\n        \"\"\"\n        Close a file descriptor which is connected to the child process, identified\n        by its FD in the child process.\n        \"\"\"\n\n    def writeToChild(childFD, data):\n        \"\"\"\n        Similar to L{ITransport.write} but also allows the file descriptor in\n        the child process which will receive the bytes to be specified.\n\n        @type childFD: L{int}\n        @param childFD: The file descriptor to which to write.\n\n        @type data: L{bytes}\n        @param data: The bytes to write.\n\n        @return: L{None}\n\n        @raise KeyError: If C{childFD} is not a file descriptor that was mapped\n            in the child when L{IReactorProcess.spawnProcess} was used to create\n            it.\n        \"\"\"\n\n    def loseConnection():\n        \"\"\"\n        Close stdin, stderr and stdout.\n        \"\"\"\n\n    def signalProcess(signalID):\n        \"\"\"\n        Send a signal to the process.\n\n        @param signalID: can be\n          - one of C{\"KILL\"}, C{\"TERM\"}, or C{\"INT\"}.\n              These will be implemented in a\n              cross-platform manner, and so should be used\n              if possible.\n          - an integer, where it represents a POSIX\n              signal ID.\n\n        @raise twisted.internet.error.ProcessExitedAlready: If the process has\n            already exited.\n        @raise OSError: If the C{os.kill} call fails with an errno different\n            from C{ESRCH}.\n        \"\"\"\n\n\nclass IServiceCollection(Interface):\n    \"\"\"\n    An object which provides access to a collection of services.\n    \"\"\"\n\n    def getServiceNamed(serviceName):\n        \"\"\"\n        Retrieve the named service from this application.\n\n        Raise a C{KeyError} if there is no such service name.\n        \"\"\"\n\n    def addService(service):\n        \"\"\"\n        Add a service to this collection.\n        \"\"\"\n\n    def removeService(service):\n        \"\"\"\n        Remove a service from this collection.\n        \"\"\"\n\n\nclass IUDPTransport(Interface):\n    \"\"\"\n    Transport for UDP DatagramProtocols.\n    \"\"\"\n\n    def write(packet, addr=None):\n        \"\"\"\n        Write packet to given address.\n\n        @param addr: a tuple of (ip, port). For connected transports must\n                     be the address the transport is connected to, or None.\n                     In non-connected mode this is mandatory.\n\n        @raise twisted.internet.error.MessageLengthError: C{packet} was too\n        long.\n        \"\"\"\n\n    def connect(host, port):\n        \"\"\"\n        Connect the transport to an address.\n\n        This changes it to connected mode. Datagrams can only be sent to\n        this address, and will only be received from this address. In addition\n        the protocol's connectionRefused method might get called if destination\n        is not receiving datagrams.\n\n        @param host: an IP address, not a domain name ('127.0.0.1', not 'localhost')\n        @param port: port to connect to.\n        \"\"\"\n\n    def getHost():\n        \"\"\"\n        Get this port's host address.\n\n        @return: an address describing the listening port.\n        @rtype: L{IPv4Address} or L{IPv6Address}.\n        \"\"\"\n\n    def stopListening():\n        \"\"\"\n        Stop listening on this port.\n\n        If it does not complete immediately, will return L{Deferred} that fires\n        upon completion.\n        \"\"\"\n\n    def setBroadcastAllowed(enabled):\n        \"\"\"\n        Set whether this port may broadcast.\n\n        @param enabled: Whether the port may broadcast.\n        @type enabled: L{bool}\n        \"\"\"\n\n    def getBroadcastAllowed():\n        \"\"\"\n        Checks if broadcast is currently allowed on this port.\n\n        @return: Whether this port may broadcast.\n        @rtype: L{bool}\n        \"\"\"\n\n\nclass IUNIXDatagramTransport(Interface):\n    \"\"\"\n    Transport for UDP PacketProtocols.\n    \"\"\"\n\n    def write(packet, address):\n        \"\"\"\n        Write packet to given address.\n        \"\"\"\n\n    def getHost():\n        \"\"\"\n        Returns L{UNIXAddress}.\n        \"\"\"\n\n\nclass IUNIXDatagramConnectedTransport(Interface):\n    \"\"\"\n    Transport for UDP ConnectedPacketProtocols.\n    \"\"\"\n\n    def write(packet):\n        \"\"\"\n        Write packet to address we are connected to.\n        \"\"\"\n\n    def getHost():\n        \"\"\"\n        Returns L{UNIXAddress}.\n        \"\"\"\n\n    def getPeer():\n        \"\"\"\n        Returns L{UNIXAddress}.\n        \"\"\"\n\n\nclass IMulticastTransport(Interface):\n    \"\"\"\n    Additional functionality for multicast UDP.\n    \"\"\"\n\n    def getOutgoingInterface():\n        \"\"\"\n        Return interface of outgoing multicast packets.\n        \"\"\"\n\n    def setOutgoingInterface(addr):\n        \"\"\"\n        Set interface for outgoing multicast packets.\n\n        Returns Deferred of success.\n        \"\"\"\n\n    def getLoopbackMode():\n        \"\"\"\n        Return if loopback mode is enabled.\n        \"\"\"\n\n    def setLoopbackMode(mode):\n        \"\"\"\n        Set if loopback mode is enabled.\n        \"\"\"\n\n    def getTTL():\n        \"\"\"\n        Get time to live for multicast packets.\n        \"\"\"\n\n    def setTTL(ttl):\n        \"\"\"\n        Set time to live on multicast packets.\n        \"\"\"\n\n    def joinGroup(addr, interface=\"\"):\n        \"\"\"\n        Join a multicast group. Returns L{Deferred} of success or failure.\n\n        If an error occurs, the returned L{Deferred} will fail with\n        L{error.MulticastJoinError}.\n        \"\"\"\n\n    def leaveGroup(addr, interface=\"\"):\n        \"\"\"\n        Leave multicast group, return L{Deferred} of success.\n        \"\"\"\n\n\nclass IStreamClientEndpoint(Interface):\n    \"\"\"\n    A stream client endpoint is a place that L{ClientFactory} can connect to.\n    For example, a remote TCP host/port pair would be a TCP client endpoint.\n\n    @since: 10.1\n    \"\"\"\n\n    def connect(protocolFactory):\n        \"\"\"\n        Connect the C{protocolFactory} to the location specified by this\n        L{IStreamClientEndpoint} provider.\n\n        @param protocolFactory: A provider of L{IProtocolFactory}\n        @return: A L{Deferred} that results in an L{IProtocol} upon successful\n            connection otherwise a L{Failure} wrapping L{ConnectError} or\n            L{NoProtocol <twisted.internet.error.NoProtocol>}.\n        \"\"\"\n\n\n\nclass IStreamServerEndpoint(Interface):\n    \"\"\"\n    A stream server endpoint is a place that a L{Factory} can listen for\n    incoming connections.\n\n    @since: 10.1\n    \"\"\"\n\n    def listen(protocolFactory):\n        \"\"\"\n        Listen with C{protocolFactory} at the location specified by this\n        L{IStreamServerEndpoint} provider.\n\n        @param protocolFactory: A provider of L{IProtocolFactory}\n        @return: A L{Deferred} that results in an L{IListeningPort} or an\n            L{CannotListenError}\n        \"\"\"\n\n\n\nclass IStreamServerEndpointStringParser(Interface):\n    \"\"\"\n    An L{IStreamServerEndpointStringParser} is like an\n    L{IStreamClientEndpointStringParserWithReactor}, except for\n    L{IStreamServerEndpoint}s instead of clients.  It integrates with\n    L{endpoints.serverFromString} in much the same way.\n    \"\"\"\n\n    prefix = Attribute(\n        \"\"\"\n        A C{str}, the description prefix to respond to.  For example, an\n        L{IStreamServerEndpointStringParser} plugin which had C{\"foo\"} for its\n        C{prefix} attribute would be called for endpoint descriptions like\n        C{\"foo:bar:baz\"} or C{\"foo:\"}.\n        \"\"\"\n    )\n\n\n    def parseStreamServer(reactor, *args, **kwargs):\n        \"\"\"\n        Parse a stream server endpoint from a reactor and string-only arguments\n        and keyword arguments.\n\n        @see: L{IStreamClientEndpointStringParserWithReactor.parseStreamClient}\n\n        @return: a stream server endpoint\n        @rtype: L{IStreamServerEndpoint}\n        \"\"\"\n\n\nclass IStreamClientEndpointStringParserWithReactor(Interface):\n    \"\"\"\n    An L{IStreamClientEndpointStringParserWithReactor} is a parser which can\n    convert a set of string C{*args} and C{**kwargs} into an\n    L{IStreamClientEndpoint} provider.\n\n    This interface is really only useful in the context of the plugin system\n    for L{endpoints.clientFromString}.  See the document entitled \"I{The\n    Twisted Plugin System}\" for more details on how to write a plugin.\n\n    If you place an L{IStreamClientEndpointStringParserWithReactor} plugin in\n    the C{twisted.plugins} package, that plugin's C{parseStreamClient} method\n    will be used to produce endpoints for any description string that begins\n    with the result of that L{IStreamClientEndpointStringParserWithReactor}'s\n    prefix attribute.\n    \"\"\"\n\n    prefix = Attribute(\n        \"\"\"\n        L{bytes}, the description prefix to respond to.  For example, an\n        L{IStreamClientEndpointStringParserWithReactor} plugin which had\n        C{b\"foo\"} for its C{prefix} attribute would be called for endpoint\n        descriptions like C{b\"foo:bar:baz\"} or C{b\"foo:\"}.\n        \"\"\"\n    )\n\n\n    def parseStreamClient(reactor, *args, **kwargs):\n        \"\"\"\n        This method is invoked by L{endpoints.clientFromString}, if the type of\n        endpoint matches the return value from this\n        L{IStreamClientEndpointStringParserWithReactor}'s C{prefix} method.\n\n        @param reactor: The reactor passed to L{endpoints.clientFromString}.\n\n        @param args: The byte string arguments, minus the endpoint type, in the\n            endpoint description string, parsed according to the rules\n            described in L{endpoints.quoteStringArgument}.  For example, if the\n            description were C{b\"my-type:foo:bar:baz=qux\"}, C{args} would be\n            C{(b'foo', b'bar')}\n\n        @param kwargs: The byte string arguments from the endpoint description\n            passed as keyword arguments.  For example, if the description were\n            C{b\"my-type:foo:bar:baz=qux\"}, C{kwargs} would be\n            C{dict(baz=b'qux')}.\n\n        @return: a client endpoint\n        @rtype: a provider of L{IStreamClientEndpoint}\n        \"\"\"\n\n\n\nclass _ISupportsExitSignalCapturing(Interface):\n    \"\"\"\n    An implementor of L{_ISupportsExitSignalCapturing} will capture the\n    value of any delivered exit signal (SIGINT, SIGTERM, SIGBREAK) for which\n    it has installed a handler.  The caught signal number is made available in\n    the _exitSignal attribute.\n    \"\"\"\n\n    _exitSignal = Attribute(\n        \"\"\"\n        C{int} or C{None}, the integer exit signal delivered to the\n        application, or None if no signal was delivered.\n        \"\"\"\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/iocpreactor/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nI/O Completion Ports reactor\n\"\"\"\n\nfrom twisted.internet.iocpreactor.reactor import install\n\n__all__ = ['install']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/iocpreactor/abstract.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAbstract file handle class\n\"\"\"\n\nfrom twisted.internet import main, error, interfaces\nfrom twisted.internet.abstract import _ConsumerMixin, _LogOwner\nfrom twisted.python import failure\nfrom twisted.python.compat import unicode\n\nfrom zope.interface import implementer\nimport errno\n\nfrom twisted.internet.iocpreactor.const import ERROR_HANDLE_EOF\nfrom twisted.internet.iocpreactor.const import ERROR_IO_PENDING\nfrom twisted.internet.iocpreactor import iocpsupport as _iocp\n\n\n@implementer(interfaces.IPushProducer, interfaces.IConsumer,\n             interfaces.ITransport, interfaces.IHalfCloseableDescriptor)\nclass FileHandle(_ConsumerMixin, _LogOwner):\n    \"\"\"\n    File handle that can read and write asynchronously\n    \"\"\"\n    # read stuff\n    maxReadBuffers = 16\n    readBufferSize = 4096\n    reading = False\n    dynamicReadBuffers = True # set this to false if subclass doesn't do iovecs\n    _readNextBuffer = 0\n    _readSize = 0 # how much data we have in the read buffer\n    _readScheduled = None\n    _readScheduledInOS = False\n\n\n    def startReading(self):\n        self.reactor.addActiveHandle(self)\n        if not self._readScheduled and not self.reading:\n            self.reading = True\n            self._readScheduled = self.reactor.callLater(0,\n                                                         self._resumeReading)\n\n\n    def stopReading(self):\n        if self._readScheduled:\n            self._readScheduled.cancel()\n            self._readScheduled = None\n        self.reading = False\n\n\n    def _resumeReading(self):\n        self._readScheduled = None\n        if self._dispatchData() and not self._readScheduledInOS:\n            self.doRead()\n\n\n    def _dispatchData(self):\n        \"\"\"\n        Dispatch previously read data. Return True if self.reading and we don't\n        have any more data\n        \"\"\"\n        if not self._readSize:\n            return self.reading\n        size = self._readSize\n        full_buffers = size // self.readBufferSize\n        while self._readNextBuffer < full_buffers:\n            self.dataReceived(self._readBuffers[self._readNextBuffer])\n            self._readNextBuffer += 1\n            if not self.reading:\n                return False\n        remainder = size % self.readBufferSize\n        if remainder:\n            self.dataReceived(self._readBuffers[full_buffers][0:remainder])\n        if self.dynamicReadBuffers:\n            total_buffer_size = self.readBufferSize * len(self._readBuffers)\n            # we have one buffer too many\n            if size < total_buffer_size - self.readBufferSize:\n                del self._readBuffers[-1]\n            # we filled all buffers, so allocate one more\n            elif (size == total_buffer_size and\n                  len(self._readBuffers) < self.maxReadBuffers):\n                self._readBuffers.append(bytearray(self.readBufferSize))\n        self._readNextBuffer = 0\n        self._readSize = 0\n        return self.reading\n\n\n    def _cbRead(self, rc, data, evt):\n        self._readScheduledInOS = False\n        if self._handleRead(rc, data, evt):\n            self.doRead()\n\n\n    def _handleRead(self, rc, data, evt):\n        \"\"\"\n        Returns False if we should stop reading for now\n        \"\"\"\n        if self.disconnected:\n            return False\n        # graceful disconnection\n        if (not (rc or data)) or rc in (errno.WSAEDISCON, ERROR_HANDLE_EOF):\n            self.reactor.removeActiveHandle(self)\n            self.readConnectionLost(failure.Failure(main.CONNECTION_DONE))\n            return False\n        # XXX: not handling WSAEWOULDBLOCK\n        # (\"too many outstanding overlapped I/O requests\")\n        elif rc:\n            self.connectionLost(failure.Failure(\n                                error.ConnectionLost(\"read error -- %s (%s)\" %\n                                    (errno.errorcode.get(rc, 'unknown'), rc))))\n            return False\n        else:\n            assert self._readSize == 0\n            assert self._readNextBuffer == 0\n            self._readSize = data\n            return self._dispatchData()\n\n\n    def doRead(self):\n        evt = _iocp.Event(self._cbRead, self)\n\n        evt.buff = buff = self._readBuffers\n        rc, numBytesRead = self.readFromHandle(buff, evt)\n\n        if not rc or rc == ERROR_IO_PENDING:\n            self._readScheduledInOS = True\n        else:\n            self._handleRead(rc, numBytesRead, evt)\n\n\n    def readFromHandle(self, bufflist, evt):\n        raise NotImplementedError() # TODO: this should default to ReadFile\n\n\n    def dataReceived(self, data):\n        raise NotImplementedError\n\n\n    def readConnectionLost(self, reason):\n        self.connectionLost(reason)\n\n\n    # write stuff\n    dataBuffer = b''\n    offset = 0\n    writing = False\n    _writeScheduled = None\n    _writeDisconnecting = False\n    _writeDisconnected = False\n    writeBufferSize = 2**2**2**2\n\n\n    def loseWriteConnection(self):\n        self._writeDisconnecting = True\n        self.startWriting()\n\n\n    def _closeWriteConnection(self):\n        # override in subclasses\n        pass\n\n\n    def writeConnectionLost(self, reason):\n        # in current code should never be called\n        self.connectionLost(reason)\n\n\n    def startWriting(self):\n        self.reactor.addActiveHandle(self)\n\n        if not self._writeScheduled and not self.writing:\n            self.writing = True\n            self._writeScheduled = self.reactor.callLater(0,\n                                                          self._resumeWriting)\n\n\n    def stopWriting(self):\n        if self._writeScheduled:\n            self._writeScheduled.cancel()\n            self._writeScheduled = None\n        self.writing = False\n\n\n    def _resumeWriting(self):\n        self._writeScheduled = None\n        self.doWrite()\n\n\n    def _cbWrite(self, rc, numBytesWritten, evt):\n        if self._handleWrite(rc, numBytesWritten, evt):\n            self.doWrite()\n\n\n    def _handleWrite(self, rc, numBytesWritten, evt):\n        \"\"\"\n        Returns false if we should stop writing for now\n        \"\"\"\n        if self.disconnected or self._writeDisconnected:\n            return False\n        # XXX: not handling WSAEWOULDBLOCK\n        # (\"too many outstanding overlapped I/O requests\")\n        if rc:\n            self.connectionLost(failure.Failure(\n                                error.ConnectionLost(\"write error -- %s (%s)\" %\n                                    (errno.errorcode.get(rc, 'unknown'), rc))))\n            return False\n        else:\n            self.offset += numBytesWritten\n            # If there is nothing left to send,\n            if self.offset == len(self.dataBuffer) and not self._tempDataLen:\n                self.dataBuffer = b\"\"\n                self.offset = 0\n                # stop writing\n                self.stopWriting()\n                # If I've got a producer who is supposed to supply me with data\n                if self.producer is not None and ((not self.streamingProducer)\n                                                  or self.producerPaused):\n                    # tell them to supply some more.\n                    self.producerPaused = True\n                    self.producer.resumeProducing()\n                elif self.disconnecting:\n                    # But if I was previously asked to let the connection die,\n                    # do so.\n                    self.connectionLost(failure.Failure(main.CONNECTION_DONE))\n                elif self._writeDisconnecting:\n                    # I was previously asked to half-close the connection.\n                    self._writeDisconnected = True\n                    self._closeWriteConnection()\n                return False\n            else:\n                return True\n\n\n    def doWrite(self):\n        if len(self.dataBuffer) - self.offset < self.SEND_LIMIT:\n            # If there is currently less than SEND_LIMIT bytes left to send\n            # in the string, extend it with the array data.\n            self.dataBuffer = (self.dataBuffer[self.offset:] +\n                               b\"\".join(self._tempDataBuffer))\n            self.offset = 0\n            self._tempDataBuffer = []\n            self._tempDataLen = 0\n\n        evt = _iocp.Event(self._cbWrite, self)\n\n        # Send as much data as you can.\n        if self.offset:\n            sendView = memoryview(self.dataBuffer)\n            evt.buff = buff = sendView[self.offset:]\n        else:\n            evt.buff = buff = self.dataBuffer\n        rc, data = self.writeToHandle(buff, evt)\n        if rc and rc != ERROR_IO_PENDING:\n            self._handleWrite(rc, data, evt)\n\n\n    def writeToHandle(self, buff, evt):\n        raise NotImplementedError() # TODO: this should default to WriteFile\n\n\n    def write(self, data):\n        \"\"\"Reliably write some data.\n\n        The data is buffered until his file descriptor is ready for writing.\n        \"\"\"\n        if isinstance(data, unicode): # no, really, I mean it\n            raise TypeError(\"Data must not be unicode\")\n        if not self.connected or self._writeDisconnected:\n            return\n        if data:\n            self._tempDataBuffer.append(data)\n            self._tempDataLen += len(data)\n            if self.producer is not None and self.streamingProducer:\n                if (len(self.dataBuffer) + self._tempDataLen\n                    > self.writeBufferSize):\n                    self.producerPaused = True\n                    self.producer.pauseProducing()\n            self.startWriting()\n\n\n    def writeSequence(self, iovec):\n        for i in iovec:\n            if isinstance(i, unicode): # no, really, I mean it\n                raise TypeError(\"Data must not be unicode\")\n        if not self.connected or not iovec or self._writeDisconnected:\n            return\n        self._tempDataBuffer.extend(iovec)\n        for i in iovec:\n            self._tempDataLen += len(i)\n        if self.producer is not None and self.streamingProducer:\n            if len(self.dataBuffer) + self._tempDataLen > self.writeBufferSize:\n                self.producerPaused = True\n                self.producer.pauseProducing()\n        self.startWriting()\n\n\n    # general stuff\n    connected = False\n    disconnected = False\n    disconnecting = False\n    logstr = \"Uninitialized\"\n\n    SEND_LIMIT = 128*1024\n\n\n    def __init__(self, reactor = None):\n        if not reactor:\n            from twisted.internet import reactor\n        self.reactor = reactor\n        self._tempDataBuffer = [] # will be added to dataBuffer in doWrite\n        self._tempDataLen = 0\n        self._readBuffers = [bytearray(self.readBufferSize)]\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        The connection was lost.\n\n        This is called when the connection on a selectable object has been\n        lost.  It will be called whether the connection was closed explicitly,\n        an exception occurred in an event handler, or the other end of the\n        connection closed it first.\n\n        Clean up state here, but make sure to call back up to FileDescriptor.\n        \"\"\"\n\n        self.disconnected = True\n        self.connected = False\n        if self.producer is not None:\n            self.producer.stopProducing()\n            self.producer = None\n        self.stopReading()\n        self.stopWriting()\n        self.reactor.removeActiveHandle(self)\n\n\n    def getFileHandle(self):\n        return -1\n\n\n    def loseConnection(self, _connDone=failure.Failure(main.CONNECTION_DONE)):\n        \"\"\"\n        Close the connection at the next available opportunity.\n\n        Call this to cause this FileDescriptor to lose its connection.  It will\n        first write any data that it has buffered.\n\n        If there is data buffered yet to be written, this method will cause the\n        transport to lose its connection as soon as it's done flushing its\n        write buffer.  If you have a producer registered, the connection won't\n        be closed until the producer is finished. Therefore, make sure you\n        unregister your producer when it's finished, or the connection will\n        never close.\n        \"\"\"\n\n        if self.connected and not self.disconnecting:\n            if self._writeDisconnected:\n                # doWrite won't trigger the connection close anymore\n                self.stopReading()\n                self.stopWriting\n                self.connectionLost(_connDone)\n            else:\n                self.stopReading()\n                self.startWriting()\n                self.disconnecting = 1\n\n\n    # Producer/consumer implementation\n\n    def stopConsuming(self):\n        \"\"\"\n        Stop consuming data.\n\n        This is called when a producer has lost its connection, to tell the\n        consumer to go lose its connection (and break potential circular\n        references).\n        \"\"\"\n        self.unregisterProducer()\n        self.loseConnection()\n\n\n    # producer interface implementation\n\n    def resumeProducing(self):\n        if self.connected and not self.disconnecting:\n            self.startReading()\n\n\n    def pauseProducing(self):\n        self.stopReading()\n\n\n    def stopProducing(self):\n        self.loseConnection()\n\n\n__all__ = ['FileHandle']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/iocpreactor/const.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nWindows constants for IOCP\n\"\"\"\n\n\n# this stuff should really be gotten from Windows headers via pyrex, but it\n# probably is not going to change\n\nERROR_PORT_UNREACHABLE = 1234\nERROR_NETWORK_UNREACHABLE = 1231\nERROR_CONNECTION_REFUSED = 1225\nERROR_IO_PENDING = 997\nERROR_OPERATION_ABORTED = 995\nWAIT_TIMEOUT = 258\nERROR_NETNAME_DELETED = 64\nERROR_HANDLE_EOF = 38\n\nINFINITE = -1\n\nSO_UPDATE_CONNECT_CONTEXT = 0x7010\nSO_UPDATE_ACCEPT_CONTEXT = 0x700B\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/iocpreactor/interfaces.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nInterfaces for iocpreactor\n\"\"\"\n\n\nfrom zope.interface import Interface\n\n\n\nclass IReadHandle(Interface):\n    def readFromHandle(bufflist, evt):\n        \"\"\"\n        Read into the given buffers from this handle.\n\n        @param buff: the buffers to read into\n        @type buff: list of objects implementing the read/write buffer protocol\n\n        @param evt: an IOCP Event object\n\n        @return: tuple (return code, number of bytes read)\n        \"\"\"\n\n\n\nclass IWriteHandle(Interface):\n    def writeToHandle(buff, evt):\n        \"\"\"\n        Write the given buffer to this handle.\n\n        @param buff: the buffer to write\n        @type buff: any object implementing the buffer protocol\n\n        @param evt: an IOCP Event object\n\n        @return: tuple (return code, number of bytes written)\n        \"\"\"\n\n\n\nclass IReadWriteHandle(IReadHandle, IWriteHandle):\n    pass\n\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/iocpreactor/notes.txt",
    "content": "test specifically:\nfailed accept error message -- similar to test_tcp_internals\nimmediate success on accept/connect/recv, including Event.ignore\nparametrize iocpsupport somehow -- via reactor?\n\ndo:\nbreak handling -- WaitForSingleObject on the IOCP handle?\niovecs for write buffer\ndo not wait for a mainloop iteration if resumeProducing (in _handleWrite) does startWriting\ndon't addActiveHandle in every call to startWriting/startReading\niocpified process support\n  win32er-in-a-thread (or run GQCS in a thread -- it can't receive SIGBREAK)\nblocking in sendto() -- I think Windows can do that, especially with local UDP\n\nbuildbot:\nrun in vmware\nstart from a persistent snapshot\n\nuse a stub inside the vm to svnup/run tests/collect stdio\nlift logs through SMB? or ship them via tcp beams to the VM host\n\nhave a timeout on the test run\nif we time out, take a screenshot, save it, kill the VM\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/iocpreactor/reactor.py",
    "content": "# -*- test-case-name: twisted.internet.test.test_iocp -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nReactor that uses IO completion ports\n\"\"\"\n\nimport warnings, socket, sys\n\nfrom zope.interface import implementer\n\nfrom twisted.internet import base, interfaces, main, error\nfrom twisted.python import log, failure\nfrom twisted.internet._dumbwin32proc import Process\nfrom twisted.internet.win32eventreactor import _ThreadedWin32EventsMixin\n\nfrom twisted.internet.iocpreactor import iocpsupport as _iocp\nfrom twisted.internet.iocpreactor.const import WAIT_TIMEOUT\nfrom twisted.internet.iocpreactor import tcp, udp\n\ntry:\n    from twisted.protocols.tls import TLSMemoryBIOFactory\nexcept ImportError:\n    # Either pyOpenSSL isn't installed, or it is too old for this code to work.\n    # The reactor won't provide IReactorSSL.\n    TLSMemoryBIOFactory = None\n    _extraInterfaces = ()\n    warnings.warn(\n        \"pyOpenSSL 0.10 or newer is required for SSL support in iocpreactor. \"\n        \"It is missing, so the reactor will not support SSL APIs.\")\nelse:\n    _extraInterfaces = (interfaces.IReactorSSL,)\n\nMAX_TIMEOUT = 2000 # 2 seconds, see doIteration for explanation\n\nEVENTS_PER_LOOP = 1000 # XXX: what's a good value here?\n\n# keys to associate with normal and waker events\nKEY_NORMAL, KEY_WAKEUP = range(2)\n\n_NO_GETHANDLE = error.ConnectionFdescWentAway(\n                    'Handler has no getFileHandle method')\n_NO_FILEDESC = error.ConnectionFdescWentAway('Filedescriptor went away')\n\n\n\n@implementer(interfaces.IReactorTCP, interfaces.IReactorUDP,\n             interfaces.IReactorMulticast, interfaces.IReactorProcess,\n             *_extraInterfaces)\nclass IOCPReactor(base._SignalReactorMixin, base.ReactorBase,\n                  _ThreadedWin32EventsMixin):\n\n\n    port = None\n\n    def __init__(self):\n        base.ReactorBase.__init__(self)\n        self.port = _iocp.CompletionPort()\n        self.handles = set()\n\n\n    def addActiveHandle(self, handle):\n        self.handles.add(handle)\n\n\n    def removeActiveHandle(self, handle):\n        self.handles.discard(handle)\n\n\n    def doIteration(self, timeout):\n        \"\"\"\n        Poll the IO completion port for new events.\n        \"\"\"\n        # This function sits and waits for an IO completion event.\n        #\n        # There are two requirements: process IO events as soon as they arrive\n        # and process ctrl-break from the user in a reasonable amount of time.\n        #\n        # There are three kinds of waiting.\n        # 1) GetQueuedCompletionStatus (self.port.getEvent) to wait for IO\n        # events only.\n        # 2) Msg* family of wait functions that can stop waiting when\n        # ctrl-break is detected (then, I think, Python converts it into a\n        # KeyboardInterrupt)\n        # 3) *Ex family of wait functions that put the thread into an\n        # \"alertable\" wait state which is supposedly triggered by IO completion\n        #\n        # 2) and 3) can be combined. Trouble is, my IO completion is not\n        # causing 3) to trigger, possibly because I do not use an IO completion\n        # callback. Windows is weird.\n        # There are two ways to handle this. I could use MsgWaitForSingleObject\n        # here and GetQueuedCompletionStatus in a thread. Or I could poll with\n        # a reasonable interval. Guess what! Threads are hard.\n\n        processed_events = 0\n        if timeout is None:\n            timeout = MAX_TIMEOUT\n        else:\n            timeout = min(MAX_TIMEOUT, int(1000*timeout))\n        rc, numBytes, key, evt = self.port.getEvent(timeout)\n        while 1:\n            if rc == WAIT_TIMEOUT:\n                break\n            if key != KEY_WAKEUP:\n                assert key == KEY_NORMAL\n                log.callWithLogger(evt.owner, self._callEventCallback,\n                                   rc, numBytes, evt)\n                processed_events += 1\n            if processed_events >= EVENTS_PER_LOOP:\n                break\n            rc, numBytes, key, evt = self.port.getEvent(0)\n\n\n    def _callEventCallback(self, rc, numBytes, evt):\n        owner = evt.owner\n        why = None\n        try:\n            evt.callback(rc, numBytes, evt)\n            handfn = getattr(owner, 'getFileHandle', None)\n            if not handfn:\n                why = _NO_GETHANDLE\n            elif handfn() == -1:\n                why = _NO_FILEDESC\n            if why:\n                return # ignore handles that were closed\n        except:\n            why = sys.exc_info()[1]\n            log.err()\n        if why:\n            owner.loseConnection(failure.Failure(why))\n\n\n    def installWaker(self):\n        pass\n\n\n    def wakeUp(self):\n        self.port.postEvent(0, KEY_WAKEUP, None)\n\n\n    def registerHandle(self, handle):\n        self.port.addHandle(handle, KEY_NORMAL)\n\n\n    def createSocket(self, af, stype):\n        skt = socket.socket(af, stype)\n        self.registerHandle(skt.fileno())\n        return skt\n\n\n    def listenTCP(self, port, factory, backlog=50, interface=''):\n        \"\"\"\n        @see: twisted.internet.interfaces.IReactorTCP.listenTCP\n        \"\"\"\n        p = tcp.Port(port, factory, backlog, interface, self)\n        p.startListening()\n        return p\n\n\n    def connectTCP(self, host, port, factory, timeout=30, bindAddress=None):\n        \"\"\"\n        @see: twisted.internet.interfaces.IReactorTCP.connectTCP\n        \"\"\"\n        c = tcp.Connector(host, port, factory, timeout, bindAddress, self)\n        c.connect()\n        return c\n\n\n    if TLSMemoryBIOFactory is not None:\n        def listenSSL(self, port, factory, contextFactory, backlog=50, interface=''):\n            \"\"\"\n            @see: twisted.internet.interfaces.IReactorSSL.listenSSL\n            \"\"\"\n            port = self.listenTCP(\n                port,\n                TLSMemoryBIOFactory(contextFactory, False, factory),\n                backlog, interface)\n            port._type = 'TLS'\n            return port\n\n\n        def connectSSL(self, host, port, factory, contextFactory, timeout=30, bindAddress=None):\n            \"\"\"\n            @see: twisted.internet.interfaces.IReactorSSL.connectSSL\n            \"\"\"\n            return self.connectTCP(\n                host, port,\n                TLSMemoryBIOFactory(contextFactory, True, factory),\n                timeout, bindAddress)\n    else:\n        def listenSSL(self, port, factory, contextFactory, backlog=50, interface=''):\n            \"\"\"\n            Non-implementation of L{IReactorSSL.listenSSL}.  Some dependency\n            is not satisfied.  This implementation always raises\n            L{NotImplementedError}.\n            \"\"\"\n            raise NotImplementedError(\n                \"pyOpenSSL 0.10 or newer is required for SSL support in \"\n                \"iocpreactor. It is missing, so the reactor does not support \"\n                \"SSL APIs.\")\n\n\n        def connectSSL(self, host, port, factory, contextFactory, timeout=30, bindAddress=None):\n            \"\"\"\n            Non-implementation of L{IReactorSSL.connectSSL}.  Some dependency\n            is not satisfied.  This implementation always raises\n            L{NotImplementedError}.\n            \"\"\"\n            raise NotImplementedError(\n                \"pyOpenSSL 0.10 or newer is required for SSL support in \"\n                \"iocpreactor. It is missing, so the reactor does not support \"\n                \"SSL APIs.\")\n\n\n    def listenUDP(self, port, protocol, interface='', maxPacketSize=8192):\n        \"\"\"\n        Connects a given L{DatagramProtocol} to the given numeric UDP port.\n\n        @returns: object conforming to L{IListeningPort}.\n        \"\"\"\n        p = udp.Port(port, protocol, interface, maxPacketSize, self)\n        p.startListening()\n        return p\n\n\n    def listenMulticast(self, port, protocol, interface='', maxPacketSize=8192,\n                        listenMultiple=False):\n        \"\"\"\n        Connects a given DatagramProtocol to the given numeric UDP port.\n\n        EXPERIMENTAL.\n\n        @returns: object conforming to IListeningPort.\n        \"\"\"\n        p = udp.MulticastPort(port, protocol, interface, maxPacketSize, self,\n                              listenMultiple)\n        p.startListening()\n        return p\n\n\n    def spawnProcess(self, processProtocol, executable, args=(), env={},\n                     path=None, uid=None, gid=None, usePTY=0, childFDs=None):\n        \"\"\"\n        Spawn a process.\n        \"\"\"\n        if uid is not None:\n            raise ValueError(\"Setting UID is unsupported on this platform.\")\n        if gid is not None:\n            raise ValueError(\"Setting GID is unsupported on this platform.\")\n        if usePTY:\n            raise ValueError(\"PTYs are unsupported on this platform.\")\n        if childFDs is not None:\n            raise ValueError(\n                \"Custom child file descriptor mappings are unsupported on \"\n                \"this platform.\")\n        args, env = self._checkProcessArgs(args, env)\n        return Process(self, processProtocol, executable, args, env, path)\n\n\n    def removeAll(self):\n        res = list(self.handles)\n        self.handles.clear()\n        return res\n\n\n\ndef install():\n    r = IOCPReactor()\n    main.installReactor(r)\n\n\n__all__ = ['IOCPReactor', 'install']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/iocpreactor/setup.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nDistutils file for building low-level IOCP bindings from their Pyrex source\n\"\"\"\n\n\nfrom distutils.core import setup\nfrom distutils.extension import Extension\nfrom Cython.Distutils import build_ext\n\nsetup(name='iocpsupport',\n      ext_modules=[Extension('iocpsupport',\n                   ['iocpsupport/iocpsupport.pyx',\n                    'iocpsupport/winsock_pointers.c'],\n                   libraries = ['ws2_32'],\n                   )\n                  ],\n      cmdclass = {'build_ext': build_ext},\n      )\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/iocpreactor/tcp.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTCP support for IOCP reactor\n\"\"\"\n\nimport socket, operator, errno, struct\n\nfrom zope.interface import implementer, classImplements\n\nfrom twisted.internet import interfaces, error, address, main, defer\nfrom twisted.internet.protocol import Protocol\nfrom twisted.internet.abstract import _LogOwner, isIPv6Address\nfrom twisted.internet.tcp import (\n    _SocketCloser, Connector as TCPConnector, _AbortingMixin, _BaseBaseClient,\n    _BaseTCPClient, _resolveIPv6, _getsockname)\nfrom twisted.python import log, failure, reflect\nfrom twisted.python.compat import _PY3, nativeString\n\nfrom twisted.internet.iocpreactor import iocpsupport as _iocp, abstract\nfrom twisted.internet.iocpreactor.interfaces import IReadWriteHandle\nfrom twisted.internet.iocpreactor.const import ERROR_IO_PENDING\nfrom twisted.internet.iocpreactor.const import SO_UPDATE_CONNECT_CONTEXT\nfrom twisted.internet.iocpreactor.const import SO_UPDATE_ACCEPT_CONTEXT\nfrom twisted.internet.iocpreactor.const import ERROR_CONNECTION_REFUSED\nfrom twisted.internet.iocpreactor.const import ERROR_NETWORK_UNREACHABLE\n\ntry:\n    from twisted.internet._newtls import startTLS as _startTLS\nexcept ImportError:\n    _startTLS = None\n\n# ConnectEx returns these. XXX: find out what it does for timeout\nconnectExErrors = {\n        ERROR_CONNECTION_REFUSED: errno.WSAECONNREFUSED,\n        ERROR_NETWORK_UNREACHABLE: errno.WSAENETUNREACH,\n        }\n\n@implementer(IReadWriteHandle, interfaces.ITCPTransport,\n             interfaces.ISystemHandle)\nclass Connection(abstract.FileHandle, _SocketCloser, _AbortingMixin):\n    \"\"\"\n    @ivar TLS: C{False} to indicate the connection is in normal TCP mode,\n        C{True} to indicate that TLS has been started and that operations must\n        be routed through the L{TLSMemoryBIOProtocol} instance.\n    \"\"\"\n    TLS = False\n\n\n    def __init__(self, sock, proto, reactor=None):\n        abstract.FileHandle.__init__(self, reactor)\n        self.socket = sock\n        self.getFileHandle = sock.fileno\n        self.protocol = proto\n\n\n    def getHandle(self):\n        return self.socket\n\n\n    def dataReceived(self, rbuffer):\n        \"\"\"\n        @param rbuffer: Data received.\n        @type rbuffer: L{bytes} or L{bytearray}\n        \"\"\"\n        if isinstance(rbuffer, bytes):\n            pass\n        elif isinstance(rbuffer, bytearray):\n            # XXX: some day, we'll have protocols that can handle raw buffers\n            rbuffer = bytes(rbuffer)\n        else:\n            raise TypeError(\"data must be bytes or bytearray, not \" +\n                            type(rbuffer))\n\n        self.protocol.dataReceived(rbuffer)\n\n\n    def readFromHandle(self, bufflist, evt):\n        return _iocp.recv(self.getFileHandle(), bufflist, evt)\n\n\n    def writeToHandle(self, buff, evt):\n        \"\"\"\n        Send C{buff} to current file handle using C{_iocp.send}. The buffer\n        sent is limited to a size of C{self.SEND_LIMIT}.\n        \"\"\"\n        writeView = memoryview(buff)\n        return _iocp.send(self.getFileHandle(),\n            writeView[0:self.SEND_LIMIT].tobytes(), evt)\n\n\n    def _closeWriteConnection(self):\n        try:\n            self.socket.shutdown(1)\n        except socket.error:\n            pass\n        p = interfaces.IHalfCloseableProtocol(self.protocol, None)\n        if p:\n            try:\n                p.writeConnectionLost()\n            except:\n                f = failure.Failure()\n                log.err()\n                self.connectionLost(f)\n\n\n    def readConnectionLost(self, reason):\n        p = interfaces.IHalfCloseableProtocol(self.protocol, None)\n        if p:\n            try:\n                p.readConnectionLost()\n            except:\n                log.err()\n                self.connectionLost(failure.Failure())\n        else:\n            self.connectionLost(reason)\n\n\n    def connectionLost(self, reason):\n        if self.disconnected:\n            return\n        abstract.FileHandle.connectionLost(self, reason)\n        isClean = (reason is None or\n                   not reason.check(error.ConnectionAborted))\n        self._closeSocket(isClean)\n        protocol = self.protocol\n        del self.protocol\n        del self.socket\n        del self.getFileHandle\n        protocol.connectionLost(reason)\n\n\n    def logPrefix(self):\n        \"\"\"\n        Return the prefix to log with when I own the logging thread.\n        \"\"\"\n        return self.logstr\n\n\n    def getTcpNoDelay(self):\n        return operator.truth(self.socket.getsockopt(socket.IPPROTO_TCP,\n                                                     socket.TCP_NODELAY))\n\n\n    def setTcpNoDelay(self, enabled):\n        self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY, enabled)\n\n\n    def getTcpKeepAlive(self):\n        return operator.truth(self.socket.getsockopt(socket.SOL_SOCKET,\n                                                     socket.SO_KEEPALIVE))\n\n\n    def setTcpKeepAlive(self, enabled):\n        self.socket.setsockopt(socket.SOL_SOCKET, socket.SO_KEEPALIVE, enabled)\n\n\n    if _startTLS is not None:\n        def startTLS(self, contextFactory, normal=True):\n            \"\"\"\n            @see: L{ITLSTransport.startTLS}\n            \"\"\"\n            _startTLS(self, contextFactory, normal, abstract.FileHandle)\n\n\n    def write(self, data):\n        \"\"\"\n        Write some data, either directly to the underlying handle or, if TLS\n        has been started, to the L{TLSMemoryBIOProtocol} for it to encrypt and\n        send.\n\n        @see: L{twisted.internet.interfaces.ITransport.write}\n        \"\"\"\n        if self.disconnected:\n            return\n        if self.TLS:\n            self.protocol.write(data)\n        else:\n            abstract.FileHandle.write(self, data)\n\n\n    def writeSequence(self, iovec):\n        \"\"\"\n        Write some data, either directly to the underlying handle or, if TLS\n        has been started, to the L{TLSMemoryBIOProtocol} for it to encrypt and\n        send.\n\n        @see: L{twisted.internet.interfaces.ITransport.writeSequence}\n        \"\"\"\n        if self.disconnected:\n            return\n        if self.TLS:\n            self.protocol.writeSequence(iovec)\n        else:\n            abstract.FileHandle.writeSequence(self, iovec)\n\n\n    def loseConnection(self, reason=None):\n        \"\"\"\n        Close the underlying handle or, if TLS has been started, first shut it\n        down.\n\n        @see: L{twisted.internet.interfaces.ITransport.loseConnection}\n        \"\"\"\n        if self.TLS:\n            if self.connected and not self.disconnecting:\n                self.protocol.loseConnection()\n        else:\n            abstract.FileHandle.loseConnection(self, reason)\n\n\n    def registerProducer(self, producer, streaming):\n        \"\"\"\n        Register a producer.\n\n        If TLS is enabled, the TLS connection handles this.\n        \"\"\"\n        if self.TLS:\n            # Registering a producer before we're connected shouldn't be a\n            # problem. If we end up with a write(), that's already handled in\n            # the write() code above, and there are no other potential\n            # side-effects.\n            self.protocol.registerProducer(producer, streaming)\n        else:\n            abstract.FileHandle.registerProducer(self, producer, streaming)\n\n\n    def unregisterProducer(self):\n        \"\"\"\n        Unregister a producer.\n\n        If TLS is enabled, the TLS connection handles this.\n        \"\"\"\n        if self.TLS:\n            self.protocol.unregisterProducer()\n        else:\n            abstract.FileHandle.unregisterProducer(self)\n\nif _startTLS is not None:\n    classImplements(Connection, interfaces.ITLSTransport)\n\n\n\nclass Client(_BaseBaseClient, _BaseTCPClient, Connection):\n    \"\"\"\n    @ivar _tlsClientDefault: Always C{True}, indicating that this is a client\n        connection, and by default when TLS is negotiated this class will act as\n        a TLS client.\n    \"\"\"\n    addressFamily = socket.AF_INET\n    socketType = socket.SOCK_STREAM\n\n    _tlsClientDefault = True\n    _commonConnection = Connection\n\n    def __init__(self, host, port, bindAddress, connector, reactor):\n        # ConnectEx documentation says socket _has_ to be bound\n        if bindAddress is None:\n            bindAddress = ('', 0)\n        self.reactor = reactor # createInternetSocket needs this\n        _BaseTCPClient.__init__(self, host, port, bindAddress, connector,\n                                reactor)\n\n\n    def createInternetSocket(self):\n        \"\"\"\n        Create a socket registered with the IOCP reactor.\n\n        @see: L{_BaseTCPClient}\n        \"\"\"\n        return self.reactor.createSocket(self.addressFamily, self.socketType)\n\n\n    def _collectSocketDetails(self):\n        \"\"\"\n        Clean up potentially circular references to the socket and to its\n        C{getFileHandle} method.\n\n        @see: L{_BaseBaseClient}\n        \"\"\"\n        del self.socket, self.getFileHandle\n\n\n    def _stopReadingAndWriting(self):\n        \"\"\"\n        Remove the active handle from the reactor.\n\n        @see: L{_BaseBaseClient}\n        \"\"\"\n        self.reactor.removeActiveHandle(self)\n\n\n    def cbConnect(self, rc, data, evt):\n        if rc:\n            rc = connectExErrors.get(rc, rc)\n            self.failIfNotConnected(error.getConnectError((rc,\n                                    errno.errorcode.get(rc, 'Unknown error'))))\n        else:\n            self.socket.setsockopt(\n                socket.SOL_SOCKET, SO_UPDATE_CONNECT_CONTEXT,\n                struct.pack('P', self.socket.fileno()))\n            self.protocol = self.connector.buildProtocol(self.getPeer())\n            self.connected = True\n            logPrefix = self._getLogPrefix(self.protocol)\n            self.logstr = logPrefix + \",client\"\n            if self.protocol is None:\n                # Factory.buildProtocol is allowed to return None.  In that\n                # case, make up a protocol to satisfy the rest of the\n                # implementation; connectionLost is going to be called on\n                # something, for example.  This is easier than adding special\n                # case support for a None protocol throughout the rest of the\n                # transport implementation.\n                self.protocol = Protocol()\n                # But dispose of the connection quickly.\n                self.loseConnection()\n            else:\n                self.protocol.makeConnection(self)\n                self.startReading()\n\n\n    def doConnect(self):\n        if not hasattr(self, \"connector\"):\n            # this happens if we connector.stopConnecting in\n            # factory.startedConnecting\n            return\n        assert _iocp.have_connectex\n        self.reactor.addActiveHandle(self)\n        evt = _iocp.Event(self.cbConnect, self)\n\n        rc = _iocp.connect(self.socket.fileno(), self.realAddress, evt)\n        if rc and rc != ERROR_IO_PENDING:\n            self.cbConnect(rc, 0, evt)\n\n\n\nclass Server(Connection):\n    \"\"\"\n    Serverside socket-stream connection class.\n\n    I am a serverside network connection transport; a socket which came from an\n    accept() on a server.\n\n    @ivar _tlsClientDefault: Always C{False}, indicating that this is a server\n        connection, and by default when TLS is negotiated this class will act as\n        a TLS server.\n    \"\"\"\n\n    _tlsClientDefault = False\n\n\n    def __init__(self, sock, protocol, clientAddr, serverAddr, sessionno, reactor):\n        \"\"\"\n        Server(sock, protocol, client, server, sessionno)\n\n        Initialize me with a socket, a protocol, a descriptor for my peer (a\n        tuple of host, port describing the other end of the connection), an\n        instance of Port, and a session number.\n        \"\"\"\n        Connection.__init__(self, sock, protocol, reactor)\n        self.serverAddr = serverAddr\n        self.clientAddr = clientAddr\n        self.sessionno = sessionno\n        logPrefix = self._getLogPrefix(self.protocol)\n        self.logstr = \"%s,%s,%s\" % (logPrefix, sessionno, self.clientAddr.host)\n        self.repstr = \"<%s #%s on %s>\" % (self.protocol.__class__.__name__,\n                                          self.sessionno, self.serverAddr.port)\n        self.connected = True\n        self.startReading()\n\n\n    def __repr__(self):\n        \"\"\"\n        A string representation of this connection.\n        \"\"\"\n        return self.repstr\n\n\n    def getHost(self):\n        \"\"\"\n        Returns an IPv4Address.\n\n        This indicates the server's address.\n        \"\"\"\n        return self.serverAddr\n\n\n    def getPeer(self):\n        \"\"\"\n        Returns an IPv4Address.\n\n        This indicates the client's address.\n        \"\"\"\n        return self.clientAddr\n\n\n\nclass Connector(TCPConnector):\n    def _makeTransport(self):\n        return Client(self.host, self.port, self.bindAddress, self,\n                      self.reactor)\n\n\n\n@implementer(interfaces.IListeningPort)\nclass Port(_SocketCloser, _LogOwner):\n\n    connected = False\n    disconnected = False\n    disconnecting = False\n    addressFamily = socket.AF_INET\n    socketType = socket.SOCK_STREAM\n    _addressType = address.IPv4Address\n    sessionno = 0\n\n    # Actual port number being listened on, only set to a non-None\n    # value when we are actually listening.\n    _realPortNumber = None\n\n    # A string describing the connections which will be created by this port.\n    # Normally this is C{\"TCP\"}, since this is a TCP port, but when the TLS\n    # implementation re-uses this class it overrides the value with C{\"TLS\"}.\n    # Only used for logging.\n    _type = 'TCP'\n\n    def __init__(self, port, factory, backlog=50, interface='', reactor=None):\n        self.port = port\n        self.factory = factory\n        self.backlog = backlog\n        self.interface = interface\n        self.reactor = reactor\n        if isIPv6Address(interface):\n            self.addressFamily = socket.AF_INET6\n            self._addressType = address.IPv6Address\n\n\n    def __repr__(self):\n        if self._realPortNumber is not None:\n            return \"<%s of %s on %s>\" % (self.__class__,\n                                         self.factory.__class__,\n                                         self._realPortNumber)\n        else:\n            return \"<%s of %s (not listening)>\" % (self.__class__,\n                                                   self.factory.__class__)\n\n\n    def startListening(self):\n        try:\n            skt = self.reactor.createSocket(self.addressFamily,\n                                            self.socketType)\n            # TODO: resolve self.interface if necessary\n            if self.addressFamily == socket.AF_INET6:\n                addr = _resolveIPv6(self.interface, self.port)\n            else:\n                addr = (self.interface, self.port)\n            skt.bind(addr)\n        except socket.error as le:\n            raise error.CannotListenError(self.interface, self.port, le)\n\n        self.addrLen = _iocp.maxAddrLen(skt.fileno())\n\n        # Make sure that if we listened on port 0, we update that to\n        # reflect what the OS actually assigned us.\n        self._realPortNumber = skt.getsockname()[1]\n\n        log.msg(\"%s starting on %s\" % (self._getLogPrefix(self.factory),\n                                       self._realPortNumber))\n\n        self.factory.doStart()\n        skt.listen(self.backlog)\n        self.connected = True\n        self.disconnected = False\n        self.reactor.addActiveHandle(self)\n        self.socket = skt\n        self.getFileHandle = self.socket.fileno\n        self.doAccept()\n\n\n    def loseConnection(self, connDone=failure.Failure(main.CONNECTION_DONE)):\n        \"\"\"\n        Stop accepting connections on this port.\n\n        This will shut down my socket and call self.connectionLost().\n        It returns a deferred which will fire successfully when the\n        port is actually closed.\n        \"\"\"\n        self.disconnecting = True\n        if self.connected:\n            self.deferred = defer.Deferred()\n            self.reactor.callLater(0, self.connectionLost, connDone)\n            return self.deferred\n\n    stopListening = loseConnection\n\n\n    def _logConnectionLostMsg(self):\n        \"\"\"\n        Log message for closing port\n        \"\"\"\n        log.msg('(%s Port %s Closed)' % (self._type, self._realPortNumber))\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Cleans up the socket.\n        \"\"\"\n        self._logConnectionLostMsg()\n        self._realPortNumber = None\n        d = None\n        if hasattr(self, \"deferred\"):\n            d = self.deferred\n            del self.deferred\n\n        self.disconnected = True\n        self.reactor.removeActiveHandle(self)\n        self.connected = False\n        self._closeSocket(True)\n        del self.socket\n        del self.getFileHandle\n\n        try:\n            self.factory.doStop()\n        except:\n            self.disconnecting = False\n            if d is not None:\n                d.errback(failure.Failure())\n            else:\n                raise\n        else:\n            self.disconnecting = False\n            if d is not None:\n                d.callback(None)\n\n\n    def logPrefix(self):\n        \"\"\"\n        Returns the name of my class, to prefix log entries with.\n        \"\"\"\n        return reflect.qual(self.factory.__class__)\n\n\n    def getHost(self):\n        \"\"\"\n        Returns an IPv4Address or IPv6Address.\n\n        This indicates the server's address.\n        \"\"\"\n        return self._addressType('TCP', *_getsockname(self.socket))\n\n\n    def cbAccept(self, rc, data, evt):\n        self.handleAccept(rc, evt)\n        if not (self.disconnecting or self.disconnected):\n            self.doAccept()\n\n\n    def handleAccept(self, rc, evt):\n        if self.disconnecting or self.disconnected:\n            return False\n\n        # possible errors:\n        # (WSAEMFILE, WSAENOBUFS, WSAENFILE, WSAENOMEM, WSAECONNABORTED)\n        if rc:\n            log.msg(\"Could not accept new connection -- %s (%s)\" %\n                    (errno.errorcode.get(rc, 'unknown error'), rc))\n            return False\n        else:\n            evt.newskt.setsockopt(\n                socket.SOL_SOCKET, SO_UPDATE_ACCEPT_CONTEXT,\n                struct.pack('P', self.socket.fileno()))\n            family, lAddr, rAddr = _iocp.get_accept_addrs(evt.newskt.fileno(),\n                                                          evt.buff)\n            if not _PY3:\n                # In _makesockaddr(), we use the Win32 API which\n                # gives us an address of the form: (unicode host, port).\n                # Only on Python 2 do we need to convert it to a\n                # non-unicode str.\n                # On Python 3, we leave it alone as unicode.\n                lAddr = (nativeString(lAddr[0]), lAddr[1])\n                rAddr = (nativeString(rAddr[0]), rAddr[1])\n            assert family == self.addressFamily\n\n            # Build an IPv6 address that includes the scopeID, if necessary\n            if \"%\" in lAddr[0]:\n                scope = int(lAddr[0].split(\"%\")[1])\n                lAddr = (lAddr[0], lAddr[1], 0, scope)\n            if \"%\" in rAddr[0]:\n                scope = int(rAddr[0].split(\"%\")[1])\n                rAddr = (rAddr[0], rAddr[1], 0, scope)\n\n            protocol = self.factory.buildProtocol(\n                self._addressType('TCP', *rAddr))\n            if protocol is None:\n                evt.newskt.close()\n            else:\n                s = self.sessionno\n                self.sessionno = s+1\n                transport = Server(evt.newskt, protocol,\n                        self._addressType('TCP', *rAddr),\n                        self._addressType('TCP', *lAddr),\n                        s, self.reactor)\n                protocol.makeConnection(transport)\n            return True\n\n\n    def doAccept(self):\n        evt = _iocp.Event(self.cbAccept, self)\n\n        # see AcceptEx documentation\n        evt.buff = buff = bytearray(2 * (self.addrLen + 16))\n\n        evt.newskt = newskt = self.reactor.createSocket(self.addressFamily,\n                                                        self.socketType)\n        rc = _iocp.accept(self.socket.fileno(), newskt.fileno(), buff, evt)\n\n        if rc and rc != ERROR_IO_PENDING:\n            self.handleAccept(rc, evt)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/iocpreactor/udp.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nUDP support for IOCP reactor\n\"\"\"\n\nimport socket, operator, struct, warnings, errno\n\nfrom zope.interface import implementer\n\nfrom twisted.internet import defer, address, error, interfaces\nfrom twisted.internet.abstract import isIPAddress, isIPv6Address\nfrom twisted.python import log, failure\n\nfrom twisted.internet.iocpreactor.const import ERROR_IO_PENDING\nfrom twisted.internet.iocpreactor.const import ERROR_CONNECTION_REFUSED\nfrom twisted.internet.iocpreactor.const import ERROR_PORT_UNREACHABLE\nfrom twisted.internet.iocpreactor.interfaces import IReadWriteHandle\nfrom twisted.internet.iocpreactor import iocpsupport as _iocp, abstract\n\n\n\n@implementer(IReadWriteHandle, interfaces.IListeningPort,\n             interfaces.IUDPTransport, interfaces.ISystemHandle)\nclass Port(abstract.FileHandle):\n    \"\"\"\n    UDP port, listening for packets.\n\n    @ivar addressFamily: L{socket.AF_INET} or L{socket.AF_INET6}, depending on\n        whether this port is listening on an IPv4 address or an IPv6 address.\n    \"\"\"\n    addressFamily = socket.AF_INET\n    socketType = socket.SOCK_DGRAM\n    dynamicReadBuffers = False\n\n    # Actual port number being listened on, only set to a non-None\n    # value when we are actually listening.\n    _realPortNumber = None\n\n\n    def __init__(self, port, proto, interface='', maxPacketSize=8192,\n                 reactor=None):\n        \"\"\"\n        Initialize with a numeric port to listen on.\n        \"\"\"\n        self.port = port\n        self.protocol = proto\n        self.readBufferSize = maxPacketSize\n        self.interface = interface\n        self.setLogStr()\n        self._connectedAddr = None\n        self._setAddressFamily()\n\n        abstract.FileHandle.__init__(self, reactor)\n\n        skt = socket.socket(self.addressFamily, self.socketType)\n        addrLen = _iocp.maxAddrLen(skt.fileno())\n        self.addressBuffer = bytearray(addrLen)\n        # WSARecvFrom takes an int\n        self.addressLengthBuffer = bytearray(struct.calcsize('i'))\n\n\n    def _setAddressFamily(self):\n        \"\"\"\n        Resolve address family for the socket.\n        \"\"\"\n        if isIPv6Address(self.interface):\n            self.addressFamily = socket.AF_INET6\n        elif isIPAddress(self.interface):\n            self.addressFamily = socket.AF_INET\n        elif self.interface:\n            raise error.InvalidAddressError(\n                self.interface, 'not an IPv4 or IPv6 address')\n\n\n    def __repr__(self):\n        if self._realPortNumber is not None:\n            return (\"<%s on %s>\" %\n                    (self.protocol.__class__, self._realPortNumber))\n        else:\n            return \"<%s not connected>\" % (self.protocol.__class__,)\n\n\n    def getHandle(self):\n        \"\"\"\n        Return a socket object.\n        \"\"\"\n        return self.socket\n\n\n    def startListening(self):\n        \"\"\"\n        Create and bind my socket, and begin listening on it.\n\n        This is called on unserialization, and must be called after creating a\n        server to begin listening on the specified port.\n        \"\"\"\n        self._bindSocket()\n        self._connectToProtocol()\n\n\n    def createSocket(self):\n        return self.reactor.createSocket(self.addressFamily, self.socketType)\n\n\n    def _bindSocket(self):\n        try:\n            skt = self.createSocket()\n            skt.bind((self.interface, self.port))\n        except socket.error as le:\n            raise error.CannotListenError(self.interface, self.port, le)\n\n        # Make sure that if we listened on port 0, we update that to\n        # reflect what the OS actually assigned us.\n        self._realPortNumber = skt.getsockname()[1]\n\n        log.msg(\"%s starting on %s\" % (\n                self._getLogPrefix(self.protocol), self._realPortNumber))\n\n        self.connected = True\n        self.socket = skt\n        self.getFileHandle = self.socket.fileno\n\n\n    def _connectToProtocol(self):\n        self.protocol.makeConnection(self)\n        self.startReading()\n        self.reactor.addActiveHandle(self)\n\n\n    def cbRead(self, rc, data, evt):\n        if self.reading:\n            self.handleRead(rc, data, evt)\n            self.doRead()\n\n\n    def handleRead(self, rc, data, evt):\n        if rc in (errno.WSAECONNREFUSED, errno.WSAECONNRESET,\n                  ERROR_CONNECTION_REFUSED, ERROR_PORT_UNREACHABLE):\n            if self._connectedAddr:\n                self.protocol.connectionRefused()\n        elif rc:\n            log.msg(\"error in recvfrom -- %s (%s)\" %\n                    (errno.errorcode.get(rc, 'unknown error'), rc))\n        else:\n            try:\n                self.protocol.datagramReceived(bytes(evt.buff[:data]),\n                    _iocp.makesockaddr(evt.addr_buff))\n            except:\n                log.err()\n\n\n    def doRead(self):\n        evt = _iocp.Event(self.cbRead, self)\n\n        evt.buff = buff = self._readBuffers[0]\n        evt.addr_buff = addr_buff = self.addressBuffer\n        evt.addr_len_buff = addr_len_buff = self.addressLengthBuffer\n        rc, data = _iocp.recvfrom(self.getFileHandle(), buff,\n                                   addr_buff, addr_len_buff, evt)\n\n        if rc and rc != ERROR_IO_PENDING:\n            self.handleRead(rc, data, evt)\n\n\n    def write(self, datagram, addr=None):\n        \"\"\"\n        Write a datagram.\n\n        @param addr: should be a tuple (ip, port), can be None in connected\n        mode.\n        \"\"\"\n        if self._connectedAddr:\n            assert addr in (None, self._connectedAddr)\n            try:\n                return self.socket.send(datagram)\n            except socket.error as se:\n                no = se.args[0]\n                if no == errno.WSAEINTR:\n                    return self.write(datagram)\n                elif no == errno.WSAEMSGSIZE:\n                    raise error.MessageLengthError(\"message too long\")\n                elif no in (errno.WSAECONNREFUSED, errno.WSAECONNRESET,\n                            ERROR_CONNECTION_REFUSED, ERROR_PORT_UNREACHABLE):\n                    self.protocol.connectionRefused()\n                else:\n                    raise\n        else:\n            assert addr != None\n            if (not isIPAddress(addr[0]) and not isIPv6Address(addr[0])\n                    and addr[0] != \"<broadcast>\"):\n                raise error.InvalidAddressError(\n                    addr[0],\n                    \"write() only accepts IP addresses, not hostnames\")\n            if isIPAddress(addr[0]) and self.addressFamily == socket.AF_INET6:\n                raise error.InvalidAddressError(\n                    addr[0], \"IPv6 port write() called with IPv4 address\")\n            if isIPv6Address(addr[0]) and self.addressFamily == socket.AF_INET:\n                raise error.InvalidAddressError(\n                    addr[0], \"IPv4 port write() called with IPv6 address\")\n            try:\n                return self.socket.sendto(datagram, addr)\n            except socket.error as se:\n                no = se.args[0]\n                if no == errno.WSAEINTR:\n                    return self.write(datagram, addr)\n                elif no == errno.WSAEMSGSIZE:\n                    raise error.MessageLengthError(\"message too long\")\n                elif no in (errno.WSAECONNREFUSED, errno.WSAECONNRESET,\n                            ERROR_CONNECTION_REFUSED, ERROR_PORT_UNREACHABLE):\n                    # in non-connected UDP ECONNREFUSED is platform dependent,\n                    # I think and the info is not necessarily useful.\n                    # Nevertheless maybe we should call connectionRefused? XXX\n                    return\n                else:\n                    raise\n\n\n    def writeSequence(self, seq, addr):\n        self.write(b\"\".join(seq), addr)\n\n\n    def connect(self, host, port):\n        \"\"\"\n        'Connect' to remote server.\n        \"\"\"\n        if self._connectedAddr:\n            raise RuntimeError(\n                \"already connected, reconnecting is not currently supported \"\n                \"(talk to itamar if you want this)\")\n        if not isIPAddress(host) and not isIPv6Address(host):\n            raise error.InvalidAddressError(\n                host, 'not an IPv4 or IPv6 address.')\n        self._connectedAddr = (host, port)\n        self.socket.connect((host, port))\n\n\n    def _loseConnection(self):\n        self.stopReading()\n        self.reactor.removeActiveHandle(self)\n        if self.connected: # actually means if we are *listening*\n            self.reactor.callLater(0, self.connectionLost)\n\n\n    def stopListening(self):\n        if self.connected:\n            result = self.d = defer.Deferred()\n        else:\n            result = None\n        self._loseConnection()\n        return result\n\n\n    def loseConnection(self):\n        warnings.warn(\"Please use stopListening() to disconnect port\",\n                      DeprecationWarning, stacklevel=2)\n        self.stopListening()\n\n\n    def connectionLost(self, reason=None):\n        \"\"\"\n        Cleans up my socket.\n        \"\"\"\n        log.msg('(UDP Port %s Closed)' % self._realPortNumber)\n        self._realPortNumber = None\n        abstract.FileHandle.connectionLost(self, reason)\n        self.protocol.doStop()\n        self.socket.close()\n        del self.socket\n        del self.getFileHandle\n        if hasattr(self, \"d\"):\n            self.d.callback(None)\n            del self.d\n\n\n    def setLogStr(self):\n        \"\"\"\n        Initialize the C{logstr} attribute to be used by C{logPrefix}.\n        \"\"\"\n        logPrefix = self._getLogPrefix(self.protocol)\n        self.logstr = \"%s (UDP)\" % logPrefix\n\n\n    def logPrefix(self):\n        \"\"\"\n        Returns the name of my class, to prefix log entries with.\n        \"\"\"\n        return self.logstr\n\n\n    def getHost(self):\n        \"\"\"\n        Return the local address of the UDP connection\n\n        @returns: the local address of the UDP connection\n        @rtype: L{IPv4Address} or L{IPv6Address}\n        \"\"\"\n        addr = self.socket.getsockname()\n        if self.addressFamily == socket.AF_INET:\n            return address.IPv4Address('UDP', *addr)\n        elif self.addressFamily == socket.AF_INET6:\n            return address.IPv6Address('UDP', *(addr[:2]))\n\n\n    def setBroadcastAllowed(self, enabled):\n        \"\"\"\n        Set whether this port may broadcast. This is disabled by default.\n\n        @param enabled: Whether the port may broadcast.\n        @type enabled: L{bool}\n        \"\"\"\n        self.socket.setsockopt(\n            socket.SOL_SOCKET, socket.SO_BROADCAST, enabled)\n\n\n    def getBroadcastAllowed(self):\n        \"\"\"\n        Checks if broadcast is currently allowed on this port.\n\n        @return: Whether this port may broadcast.\n        @rtype: L{bool}\n        \"\"\"\n        return operator.truth(\n            self.socket.getsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST))\n\n\n\nclass MulticastMixin:\n    \"\"\"\n    Implement multicast functionality.\n    \"\"\"\n\n\n    def getOutgoingInterface(self):\n        i = self.socket.getsockopt(socket.IPPROTO_IP, socket.IP_MULTICAST_IF)\n        return socket.inet_ntoa(struct.pack(\"@i\", i))\n\n\n    def setOutgoingInterface(self, addr):\n        \"\"\"\n        Returns Deferred of success.\n        \"\"\"\n        return self.reactor.resolve(addr).addCallback(self._setInterface)\n\n\n    def _setInterface(self, addr):\n        i = socket.inet_aton(addr)\n        self.socket.setsockopt(socket.IPPROTO_IP, socket.IP_MULTICAST_IF, i)\n        return 1\n\n\n    def getLoopbackMode(self):\n        return self.socket.getsockopt(socket.IPPROTO_IP,\n                                      socket.IP_MULTICAST_LOOP)\n\n\n    def setLoopbackMode(self, mode):\n        mode = struct.pack(\"b\", operator.truth(mode))\n        self.socket.setsockopt(socket.IPPROTO_IP, socket.IP_MULTICAST_LOOP,\n                               mode)\n\n\n    def getTTL(self):\n        return self.socket.getsockopt(socket.IPPROTO_IP,\n                                      socket.IP_MULTICAST_TTL)\n\n\n    def setTTL(self, ttl):\n        ttl = struct.pack(\"B\", ttl)\n        self.socket.setsockopt(socket.IPPROTO_IP, socket.IP_MULTICAST_TTL, ttl)\n\n\n    def joinGroup(self, addr, interface=\"\"):\n        \"\"\"\n        Join a multicast group. Returns Deferred of success.\n        \"\"\"\n        return self.reactor.resolve(addr).addCallback(self._joinAddr1,\n                                                      interface, 1)\n\n\n    def _joinAddr1(self, addr, interface, join):\n        return self.reactor.resolve(interface).addCallback(self._joinAddr2,\n                                                           addr, join)\n\n\n    def _joinAddr2(self, interface, addr, join):\n        addr = socket.inet_aton(addr)\n        interface = socket.inet_aton(interface)\n        if join:\n            cmd = socket.IP_ADD_MEMBERSHIP\n        else:\n            cmd = socket.IP_DROP_MEMBERSHIP\n        try:\n            self.socket.setsockopt(socket.IPPROTO_IP, cmd, addr + interface)\n        except socket.error as e:\n            return failure.Failure(error.MulticastJoinError(addr, interface,\n                                                            *e.args))\n\n\n    def leaveGroup(self, addr, interface=\"\"):\n        \"\"\"\n        Leave multicast group, return Deferred of success.\n        \"\"\"\n        return self.reactor.resolve(addr).addCallback(self._joinAddr1,\n                                                      interface, 0)\n\n\n\n@implementer(interfaces.IMulticastTransport)\nclass MulticastPort(MulticastMixin, Port):\n    \"\"\"\n    UDP Port that supports multicasting.\n    \"\"\"\n\n    def __init__(self, port, proto, interface='', maxPacketSize=8192,\n                 reactor=None, listenMultiple=False):\n        Port.__init__(self, port, proto, interface, maxPacketSize, reactor)\n        self.listenMultiple = listenMultiple\n\n\n    def createSocket(self):\n        skt = Port.createSocket(self)\n        if self.listenMultiple:\n            skt.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)\n            if hasattr(socket, \"SO_REUSEPORT\"):\n                skt.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEPORT, 1)\n        return skt\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/kqreactor.py",
    "content": "# -*- test-case-name: twisted.test.test_kqueuereactor -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nA kqueue()/kevent() based implementation of the Twisted main loop.\n\nTo use this reactor, start your application specifying the kqueue reactor::\n\n   twistd --reactor kqueue ...\n\nTo install the event loop from code (and you should do this before any\nconnections, listeners or connectors are added)::\n\n   from twisted.internet import kqreactor\n   kqreactor.install()\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport errno\nimport select\n\nfrom select import KQ_FILTER_READ, KQ_FILTER_WRITE\nfrom select import KQ_EV_DELETE, KQ_EV_ADD, KQ_EV_EOF\n\nfrom zope.interface import implementer, declarations, Interface, Attribute\n\nfrom twisted.internet import main, posixbase\nfrom twisted.internet.interfaces import IReactorFDSet, IReactorDaemonize\nfrom twisted.python import log, failure\n\n\n\nclass _IKQueue(Interface):\n    \"\"\"\n    An interface for KQueue implementations.\n    \"\"\"\n    kqueue = Attribute(\"An implementation of kqueue(2).\")\n    kevent = Attribute(\"An implementation of kevent(2).\")\n\ndeclarations.directlyProvides(select, _IKQueue)\n\n\n\n@implementer(IReactorFDSet, IReactorDaemonize)\nclass KQueueReactor(posixbase.PosixReactorBase):\n    \"\"\"\n    A reactor that uses kqueue(2)/kevent(2) and relies on Python 2.6 or higher\n    which has built in support for kqueue in the select module.\n\n    @ivar _kq: A C{kqueue} which will be used to check for I/O readiness.\n\n    @ivar _impl: The implementation of L{_IKQueue} to use.\n\n    @ivar _selectables: A dictionary mapping integer file descriptors to\n        instances of L{FileDescriptor} which have been registered with the\n        reactor.  All L{FileDescriptor}s which are currently receiving read or\n        write readiness notifications will be present as values in this\n        dictionary.\n\n    @ivar _reads: A set containing integer file descriptors.  Values in this\n        set will be registered with C{_kq} for read readiness notifications\n        which will be dispatched to the corresponding L{FileDescriptor}\n        instances in C{_selectables}.\n\n    @ivar _writes: A set containing integer file descriptors.  Values in this\n        set will be registered with C{_kq} for write readiness notifications\n        which will be dispatched to the corresponding L{FileDescriptor}\n        instances in C{_selectables}.\n    \"\"\"\n\n    def __init__(self, _kqueueImpl=select):\n        \"\"\"\n        Initialize kqueue object, file descriptor tracking dictionaries, and\n        the base class.\n\n        See:\n            - http://docs.python.org/library/select.html\n            - www.freebsd.org/cgi/man.cgi?query=kqueue\n            - people.freebsd.org/~jlemon/papers/kqueue.pdf\n\n        @param _kqueueImpl: The implementation of L{_IKQueue} to use. A\n            hook for testing.\n        \"\"\"\n        self._impl = _kqueueImpl\n        self._kq = self._impl.kqueue()\n        self._reads = set()\n        self._writes = set()\n        self._selectables = {}\n        posixbase.PosixReactorBase.__init__(self)\n\n\n    def _updateRegistration(self, fd, filter, op):\n        \"\"\"\n        Private method for changing kqueue registration on a given FD\n        filtering for events given filter/op. This will never block and\n        returns nothing.\n        \"\"\"\n        self._kq.control([self._impl.kevent(fd, filter, op)], 0, 0)\n\n\n    def beforeDaemonize(self):\n        \"\"\"\n        Implement L{IReactorDaemonize.beforeDaemonize}.\n        \"\"\"\n        # Twisted-internal method called during daemonization (when application\n        # is started via twistd). This is called right before the magic double\n        # forking done for daemonization. We cleanly close the kqueue() and later\n        # recreate it. This is needed since a) kqueue() are not inherited across\n        # forks and b) twistd will create the reactor already before daemonization\n        # (and will also add at least 1 reader to the reactor, an instance of\n        # twisted.internet.posixbase._UnixWaker).\n        #\n        # See: twisted.scripts._twistd_unix.daemonize()\n        self._kq.close()\n        self._kq = None\n\n\n    def afterDaemonize(self):\n        \"\"\"\n        Implement L{IReactorDaemonize.afterDaemonize}.\n        \"\"\"\n        # Twisted-internal method called during daemonization. This is called right\n        # after daemonization and recreates the kqueue() and any readers/writers\n        # that were added before. Note that you MUST NOT call any reactor methods\n        # in between beforeDaemonize() and afterDaemonize()!\n        self._kq = self._impl.kqueue()\n        for fd in self._reads:\n            self._updateRegistration(fd, KQ_FILTER_READ, KQ_EV_ADD)\n        for fd in self._writes:\n            self._updateRegistration(fd, KQ_FILTER_WRITE, KQ_EV_ADD)\n\n\n    def addReader(self, reader):\n        \"\"\"\n        Implement L{IReactorFDSet.addReader}.\n        \"\"\"\n        fd = reader.fileno()\n        if fd not in self._reads:\n            try:\n                self._updateRegistration(fd, KQ_FILTER_READ, KQ_EV_ADD)\n            except OSError:\n                pass\n            finally:\n                self._selectables[fd] = reader\n                self._reads.add(fd)\n\n\n    def addWriter(self, writer):\n        \"\"\"\n        Implement L{IReactorFDSet.addWriter}.\n        \"\"\"\n        fd = writer.fileno()\n        if fd not in self._writes:\n            try:\n                self._updateRegistration(fd, KQ_FILTER_WRITE, KQ_EV_ADD)\n            except OSError:\n                pass\n            finally:\n                self._selectables[fd] = writer\n                self._writes.add(fd)\n\n\n    def removeReader(self, reader):\n        \"\"\"\n        Implement L{IReactorFDSet.removeReader}.\n        \"\"\"\n        wasLost = False\n        try:\n            fd = reader.fileno()\n        except:\n            fd = -1\n        if fd == -1:\n            for fd, fdes in self._selectables.items():\n                if reader is fdes:\n                    wasLost = True\n                    break\n            else:\n                return\n        if fd in self._reads:\n            self._reads.remove(fd)\n            if fd not in self._writes:\n                del self._selectables[fd]\n            if not wasLost:\n                try:\n                    self._updateRegistration(fd, KQ_FILTER_READ, KQ_EV_DELETE)\n                except OSError:\n                    pass\n\n\n    def removeWriter(self, writer):\n        \"\"\"\n        Implement L{IReactorFDSet.removeWriter}.\n        \"\"\"\n        wasLost = False\n        try:\n            fd = writer.fileno()\n        except:\n            fd = -1\n        if fd == -1:\n            for fd, fdes in self._selectables.items():\n                if writer is fdes:\n                    wasLost = True\n                    break\n            else:\n                return\n        if fd in self._writes:\n            self._writes.remove(fd)\n            if fd not in self._reads:\n                del self._selectables[fd]\n            if not wasLost:\n                try:\n                    self._updateRegistration(fd, KQ_FILTER_WRITE, KQ_EV_DELETE)\n                except OSError:\n                    pass\n\n\n    def removeAll(self):\n        \"\"\"\n        Implement L{IReactorFDSet.removeAll}.\n        \"\"\"\n        return self._removeAll(\n            [self._selectables[fd] for fd in self._reads],\n            [self._selectables[fd] for fd in self._writes])\n\n\n    def getReaders(self):\n        \"\"\"\n        Implement L{IReactorFDSet.getReaders}.\n        \"\"\"\n        return [self._selectables[fd] for fd in self._reads]\n\n\n    def getWriters(self):\n        \"\"\"\n        Implement L{IReactorFDSet.getWriters}.\n        \"\"\"\n        return [self._selectables[fd] for fd in self._writes]\n\n\n    def doKEvent(self, timeout):\n        \"\"\"\n        Poll the kqueue for new events.\n        \"\"\"\n        if timeout is None:\n            timeout = 1\n\n        try:\n            events = self._kq.control([], len(self._selectables), timeout)\n        except OSError as e:\n            # Since this command blocks for potentially a while, it's possible\n            # EINTR can be raised for various reasons (for example, if the user\n            # hits ^C).\n            if e.errno == errno.EINTR:\n                return\n            else:\n                raise\n\n        _drdw = self._doWriteOrRead\n        for event in events:\n            fd = event.ident\n            try:\n                selectable = self._selectables[fd]\n            except KeyError:\n                # Handles the infrequent case where one selectable's\n                # handler disconnects another.\n                continue\n            else:\n                log.callWithLogger(selectable, _drdw, selectable, fd, event)\n\n\n    def _doWriteOrRead(self, selectable, fd, event):\n        \"\"\"\n        Private method called when a FD is ready for reading, writing or was\n        lost. Do the work and raise errors where necessary.\n        \"\"\"\n        why = None\n        inRead = False\n        (filter, flags, data, fflags) = (\n            event.filter, event.flags, event.data, event.fflags)\n\n        if flags & KQ_EV_EOF and data and fflags:\n            why = main.CONNECTION_LOST\n        else:\n            try:\n                if selectable.fileno() == -1:\n                    inRead = False\n                    why = posixbase._NO_FILEDESC\n                else:\n                    if filter == KQ_FILTER_READ:\n                        inRead = True\n                        why = selectable.doRead()\n                    if filter == KQ_FILTER_WRITE:\n                        inRead = False\n                        why = selectable.doWrite()\n            except:\n                # Any exception from application code gets logged and will\n                # cause us to disconnect the selectable.\n                why = failure.Failure()\n                log.err(why, \"An exception was raised from application code\" \\\n                             \" while processing a reactor selectable\")\n\n        if why:\n            self._disconnectSelectable(selectable, why, inRead)\n\n    doIteration = doKEvent\n\n\n\ndef install():\n    \"\"\"\n    Install the kqueue() reactor.\n    \"\"\"\n    p = KQueueReactor()\n    from twisted.internet.main import installReactor\n    installReactor(p)\n\n\n__all__ = [\"KQueueReactor\", \"install\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/main.py",
    "content": "# -*- test-case-name: twisted.internet.test.test_main -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nBackwards compatibility, and utility functions.\n\nIn general, this module should not be used, other than by reactor authors\nwho need to use the 'installReactor' method.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.internet import error\n\nCONNECTION_DONE = error.ConnectionDone('Connection done')\nCONNECTION_LOST = error.ConnectionLost('Connection lost')\n\n\n\ndef installReactor(reactor):\n    \"\"\"\n    Install reactor C{reactor}.\n\n    @param reactor: An object that provides one or more IReactor* interfaces.\n    \"\"\"\n    # this stuff should be common to all reactors.\n    import twisted.internet\n    import sys\n    if 'twisted.internet.reactor' in sys.modules:\n        raise error.ReactorAlreadyInstalledError(\"reactor already installed\")\n    twisted.internet.reactor = reactor\n    sys.modules['twisted.internet.reactor'] = reactor\n\n\n__all__ = [\"CONNECTION_LOST\", \"CONNECTION_DONE\", \"installReactor\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/pollreactor.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nA poll() based implementation of the twisted main loop.\n\nTo install the event loop (and you should do this before any connections,\nlisteners or connectors are added)::\n\n    from twisted.internet import pollreactor\n    pollreactor.install()\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n# System imports\nimport errno\nfrom select import error as SelectError, poll\nfrom select import POLLIN, POLLOUT, POLLHUP, POLLERR, POLLNVAL\n\nfrom zope.interface import implementer\n\n# Twisted imports\nfrom twisted.python import log\nfrom twisted.internet import posixbase\nfrom twisted.internet.interfaces import IReactorFDSet\n\n\n\n@implementer(IReactorFDSet)\nclass PollReactor(posixbase.PosixReactorBase, posixbase._PollLikeMixin):\n    \"\"\"\n    A reactor that uses poll(2).\n\n    @ivar _poller: A L{select.poll} which will be used to check for I/O\n        readiness.\n\n    @ivar _selectables: A dictionary mapping integer file descriptors to\n        instances of L{FileDescriptor} which have been registered with the\n        reactor.  All L{FileDescriptor}s which are currently receiving read or\n        write readiness notifications will be present as values in this\n        dictionary.\n\n    @ivar _reads: A dictionary mapping integer file descriptors to arbitrary\n        values (this is essentially a set).  Keys in this dictionary will be\n        registered with C{_poller} for read readiness notifications which will\n        be dispatched to the corresponding L{FileDescriptor} instances in\n        C{_selectables}.\n\n    @ivar _writes: A dictionary mapping integer file descriptors to arbitrary\n        values (this is essentially a set).  Keys in this dictionary will be\n        registered with C{_poller} for write readiness notifications which will\n        be dispatched to the corresponding L{FileDescriptor} instances in\n        C{_selectables}.\n    \"\"\"\n\n    _POLL_DISCONNECTED = (POLLHUP | POLLERR | POLLNVAL)\n    _POLL_IN = POLLIN\n    _POLL_OUT = POLLOUT\n\n    def __init__(self):\n        \"\"\"\n        Initialize polling object, file descriptor tracking dictionaries, and\n        the base class.\n        \"\"\"\n        self._poller = poll()\n        self._selectables = {}\n        self._reads = {}\n        self._writes = {}\n        posixbase.PosixReactorBase.__init__(self)\n\n\n    def _updateRegistration(self, fd):\n        \"\"\"Register/unregister an fd with the poller.\"\"\"\n        try:\n            self._poller.unregister(fd)\n        except KeyError:\n            pass\n\n        mask = 0\n        if fd in self._reads:\n            mask = mask | POLLIN\n        if fd in self._writes:\n            mask = mask | POLLOUT\n        if mask != 0:\n            self._poller.register(fd, mask)\n        else:\n            if fd in self._selectables:\n                del self._selectables[fd]\n\n    def _dictRemove(self, selectable, mdict):\n        try:\n            # the easy way\n            fd = selectable.fileno()\n            # make sure the fd is actually real.  In some situations we can get\n            # -1 here.\n            mdict[fd]\n        except:\n            # the hard way: necessary because fileno() may disappear at any\n            # moment, thanks to python's underlying sockets impl\n            for fd, fdes in self._selectables.items():\n                if selectable is fdes:\n                    break\n            else:\n                # Hmm, maybe not the right course of action?  This method can't\n                # fail, because it happens inside error detection...\n                return\n        if fd in mdict:\n            del mdict[fd]\n            self._updateRegistration(fd)\n\n    def addReader(self, reader):\n        \"\"\"Add a FileDescriptor for notification of data available to read.\n        \"\"\"\n        fd = reader.fileno()\n        if fd not in self._reads:\n            self._selectables[fd] = reader\n            self._reads[fd] =  1\n            self._updateRegistration(fd)\n\n    def addWriter(self, writer):\n        \"\"\"Add a FileDescriptor for notification of data available to write.\n        \"\"\"\n        fd = writer.fileno()\n        if fd not in self._writes:\n            self._selectables[fd] = writer\n            self._writes[fd] =  1\n            self._updateRegistration(fd)\n\n    def removeReader(self, reader):\n        \"\"\"Remove a Selectable for notification of data available to read.\n        \"\"\"\n        return self._dictRemove(reader, self._reads)\n\n    def removeWriter(self, writer):\n        \"\"\"Remove a Selectable for notification of data available to write.\n        \"\"\"\n        return self._dictRemove(writer, self._writes)\n\n    def removeAll(self):\n        \"\"\"\n        Remove all selectables, and return a list of them.\n        \"\"\"\n        return self._removeAll(\n            [self._selectables[fd] for fd in self._reads],\n            [self._selectables[fd] for fd in self._writes])\n\n\n    def doPoll(self, timeout):\n        \"\"\"Poll the poller for new events.\"\"\"\n        if timeout is not None:\n            timeout = int(timeout * 1000) # convert seconds to milliseconds\n\n        try:\n            l = self._poller.poll(timeout)\n        except SelectError as e:\n            if e.args[0] == errno.EINTR:\n                return\n            else:\n                raise\n        _drdw = self._doReadOrWrite\n        for fd, event in l:\n            try:\n                selectable = self._selectables[fd]\n            except KeyError:\n                # Handles the infrequent case where one selectable's\n                # handler disconnects another.\n                continue\n            log.callWithLogger(selectable, _drdw, selectable, fd, event)\n\n    doIteration = doPoll\n\n    def getReaders(self):\n        return [self._selectables[fd] for fd in self._reads]\n\n\n    def getWriters(self):\n        return [self._selectables[fd] for fd in self._writes]\n\n\n\ndef install():\n    \"\"\"Install the poll() reactor.\"\"\"\n    p = PollReactor()\n    from twisted.internet.main import installReactor\n    installReactor(p)\n\n\n__all__ = [\"PollReactor\", \"install\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/posixbase.py",
    "content": "# -*- test-case-name: twisted.test.test_internet,twisted.internet.test.test_posixbase -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nPosix reactor base class\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport socket\nimport errno\nimport os\nimport sys\n\nfrom zope.interface import implementer, classImplements\n\nfrom twisted.internet import error, udp, tcp\nfrom twisted.internet.base import ReactorBase, _SignalReactorMixin\nfrom twisted.internet.main import CONNECTION_DONE, CONNECTION_LOST\nfrom twisted.internet.interfaces import (\n    IReactorUNIX, IReactorUNIXDatagram, IReactorTCP, IReactorUDP, IReactorSSL,\n    IReactorSocket, IHalfCloseableDescriptor, IReactorProcess,\n    IReactorMulticast, IReactorFDSet)\n\nfrom twisted.python import log, failure, util\nfrom twisted.python.runtime import platformType, platform\n\n# Exceptions that doSelect might return frequently\n_NO_FILENO = error.ConnectionFdescWentAway('Handler has no fileno method')\n_NO_FILEDESC = error.ConnectionFdescWentAway('File descriptor lost')\n\n\ntry:\n    from twisted.protocols import tls\nexcept ImportError:\n    tls = None\n    try:\n        from twisted.internet import ssl\n    except ImportError:\n        ssl = None\n\nunixEnabled = (platformType == 'posix')\n\nprocessEnabled = False\nif unixEnabled:\n    from twisted.internet import fdesc, unix\n    from twisted.internet import process, _signals\n    processEnabled = True\n\n\nif platform.isWindows():\n    try:\n        import win32process\n        processEnabled = True\n    except ImportError:\n        win32process = None\n\n\nclass _SocketWaker(log.Logger):\n    \"\"\"\n    The I{self-pipe trick<http://cr.yp.to/docs/selfpipe.html>}, implemented\n    using a pair of sockets rather than pipes (due to the lack of support in\n    select() on Windows for pipes), used to wake up the main loop from\n    another thread.\n    \"\"\"\n    disconnected = 0\n\n    def __init__(self, reactor):\n        \"\"\"Initialize.\n        \"\"\"\n        self.reactor = reactor\n        # Following select_trigger (from asyncore)'s example;\n        server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)\n        client = socket.socket(socket.AF_INET, socket.SOCK_STREAM)\n        client.setsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY, 1)\n        server.bind(('127.0.0.1', 0))\n        server.listen(1)\n        client.connect(server.getsockname())\n        reader, clientaddr = server.accept()\n        client.setblocking(0)\n        reader.setblocking(0)\n        self.r = reader\n        self.w = client\n        self.fileno = self.r.fileno\n\n    def wakeUp(self):\n        \"\"\"Send a byte to my connection.\n        \"\"\"\n        try:\n            util.untilConcludes(self.w.send, b'x')\n        except socket.error as e:\n            if e.args[0] != errno.WSAEWOULDBLOCK:\n                raise\n\n    def doRead(self):\n        \"\"\"Read some data from my connection.\n        \"\"\"\n        try:\n            self.r.recv(8192)\n        except socket.error:\n            pass\n\n    def connectionLost(self, reason):\n        self.r.close()\n        self.w.close()\n\n\n\nclass _FDWaker(log.Logger, object):\n    \"\"\"\n    The I{self-pipe trick<http://cr.yp.to/docs/selfpipe.html>}, used to wake\n    up the main loop from another thread or a signal handler.\n\n    L{_FDWaker} is a base class for waker implementations based on\n    writing to a pipe being monitored by the reactor.\n\n    @ivar o: The file descriptor for the end of the pipe which can be\n        written to wake up a reactor monitoring this waker.\n\n    @ivar i: The file descriptor which should be monitored in order to\n        be awoken by this waker.\n    \"\"\"\n    disconnected = 0\n\n    i = None\n    o = None\n\n    def __init__(self, reactor):\n        \"\"\"Initialize.\n        \"\"\"\n        self.reactor = reactor\n        self.i, self.o = os.pipe()\n        fdesc.setNonBlocking(self.i)\n        fdesc._setCloseOnExec(self.i)\n        fdesc.setNonBlocking(self.o)\n        fdesc._setCloseOnExec(self.o)\n        self.fileno = lambda: self.i\n\n\n    def doRead(self):\n        \"\"\"\n        Read some bytes from the pipe and discard them.\n        \"\"\"\n        fdesc.readFromFD(self.fileno(), lambda data: None)\n\n\n    def connectionLost(self, reason):\n        \"\"\"Close both ends of my pipe.\n        \"\"\"\n        if not hasattr(self, \"o\"):\n            return\n        for fd in self.i, self.o:\n            try:\n                os.close(fd)\n            except IOError:\n                pass\n        del self.i, self.o\n\n\n\nclass _UnixWaker(_FDWaker):\n    \"\"\"\n    This class provides a simple interface to wake up the event loop.\n\n    This is used by threads or signals to wake up the event loop.\n    \"\"\"\n\n    def wakeUp(self):\n        \"\"\"Write one byte to the pipe, and flush it.\n        \"\"\"\n        # We don't use fdesc.writeToFD since we need to distinguish\n        # between EINTR (try again) and EAGAIN (do nothing).\n        if self.o is not None:\n            try:\n                util.untilConcludes(os.write, self.o, b'x')\n            except OSError as e:\n                # XXX There is no unit test for raising the exception\n                # for other errnos. See #4285.\n                if e.errno != errno.EAGAIN:\n                    raise\n\n\n\nif platformType == 'posix':\n    _Waker = _UnixWaker\nelse:\n    # Primarily Windows and Jython.\n    _Waker = _SocketWaker\n\n\nclass _SIGCHLDWaker(_FDWaker):\n    \"\"\"\n    L{_SIGCHLDWaker} can wake up a reactor whenever C{SIGCHLD} is\n    received.\n\n    @see: L{twisted.internet._signals}\n    \"\"\"\n    def __init__(self, reactor):\n        _FDWaker.__init__(self, reactor)\n\n\n    def install(self):\n        \"\"\"\n        Install the handler necessary to make this waker active.\n        \"\"\"\n        _signals.installHandler(self.o)\n\n\n    def uninstall(self):\n        \"\"\"\n        Remove the handler which makes this waker active.\n        \"\"\"\n        _signals.installHandler(-1)\n\n\n    def doRead(self):\n        \"\"\"\n        Having woken up the reactor in response to receipt of\n        C{SIGCHLD}, reap the process which exited.\n\n        This is called whenever the reactor notices the waker pipe is\n        writeable, which happens soon after any call to the C{wakeUp}\n        method.\n        \"\"\"\n        _FDWaker.doRead(self)\n        process.reapAllProcesses()\n\n\n\n\nclass _DisconnectSelectableMixin(object):\n    \"\"\"\n    Mixin providing the C{_disconnectSelectable} method.\n    \"\"\"\n\n    def _disconnectSelectable(self, selectable, why, isRead, faildict={\n        error.ConnectionDone: failure.Failure(error.ConnectionDone()),\n        error.ConnectionLost: failure.Failure(error.ConnectionLost())\n        }):\n        \"\"\"\n        Utility function for disconnecting a selectable.\n\n        Supports half-close notification, isRead should be boolean indicating\n        whether error resulted from doRead().\n        \"\"\"\n        self.removeReader(selectable)\n        f = faildict.get(why.__class__)\n        if f:\n            if (isRead and why.__class__ ==  error.ConnectionDone\n                and IHalfCloseableDescriptor.providedBy(selectable)):\n                selectable.readConnectionLost(f)\n            else:\n                self.removeWriter(selectable)\n                selectable.connectionLost(f)\n        else:\n            self.removeWriter(selectable)\n            selectable.connectionLost(failure.Failure(why))\n\n\n\n@implementer(IReactorTCP, IReactorUDP, IReactorMulticast)\nclass PosixReactorBase(_SignalReactorMixin, _DisconnectSelectableMixin,\n                       ReactorBase):\n    \"\"\"\n    A basis for reactors that use file descriptors.\n\n    @ivar _childWaker: L{None} or a reference to the L{_SIGCHLDWaker}\n        which is used to properly notice child process termination.\n    \"\"\"\n\n    # Callable that creates a waker, overrideable so that subclasses can\n    # substitute their own implementation:\n    _wakerFactory = _Waker\n\n    def installWaker(self):\n        \"\"\"\n        Install a `waker' to allow threads and signals to wake up the IO thread.\n\n        We use the self-pipe trick (http://cr.yp.to/docs/selfpipe.html) to wake\n        the reactor. On Windows we use a pair of sockets.\n        \"\"\"\n        if not self.waker:\n            self.waker = self._wakerFactory(self)\n            self._internalReaders.add(self.waker)\n            self.addReader(self.waker)\n\n\n    _childWaker = None\n    def _handleSignals(self):\n        \"\"\"\n        Extend the basic signal handling logic to also support\n        handling SIGCHLD to know when to try to reap child processes.\n        \"\"\"\n        _SignalReactorMixin._handleSignals(self)\n        if platformType == 'posix' and processEnabled:\n            if not self._childWaker:\n                self._childWaker = _SIGCHLDWaker(self)\n                self._internalReaders.add(self._childWaker)\n                self.addReader(self._childWaker)\n            self._childWaker.install()\n            # Also reap all processes right now, in case we missed any\n            # signals before we installed the SIGCHLD waker/handler.\n            # This should only happen if someone used spawnProcess\n            # before calling reactor.run (and the process also exited\n            # already).\n            process.reapAllProcesses()\n\n    def _uninstallHandler(self):\n        \"\"\"\n        If a child waker was created and installed, uninstall it now.\n\n        Since this disables reactor functionality and is only called\n        when the reactor is stopping, it doesn't provide any directly\n        useful functionality, but the cleanup of reactor-related\n        process-global state that it does helps in unit tests\n        involving multiple reactors and is generally just a nice\n        thing.\n        \"\"\"\n        # XXX This would probably be an alright place to put all of\n        # the cleanup code for all internal readers (here and in the\n        # base class, anyway).  See #3063 for that cleanup task.\n        if self._childWaker:\n            self._childWaker.uninstall()\n\n    # IReactorProcess\n\n    def spawnProcess(self, processProtocol, executable, args=(),\n                     env={}, path=None,\n                     uid=None, gid=None, usePTY=0, childFDs=None):\n        args, env = self._checkProcessArgs(args, env)\n        if platformType == 'posix':\n            if usePTY:\n                if childFDs is not None:\n                    raise ValueError(\"Using childFDs is not supported with usePTY=True.\")\n                return process.PTYProcess(self, executable, args, env, path,\n                                          processProtocol, uid, gid, usePTY)\n            else:\n                return process.Process(self, executable, args, env, path,\n                                       processProtocol, uid, gid, childFDs)\n        elif platformType == \"win32\":\n            if uid is not None:\n                raise ValueError(\"Setting UID is unsupported on this platform.\")\n            if gid is not None:\n                raise ValueError(\"Setting GID is unsupported on this platform.\")\n            if usePTY:\n                raise ValueError(\"The usePTY parameter is not supported on Windows.\")\n            if childFDs:\n                raise ValueError(\"Customizing childFDs is not supported on Windows.\")\n\n            if win32process:\n                from twisted.internet._dumbwin32proc import Process\n                return Process(self, processProtocol, executable, args, env, path)\n            else:\n                raise NotImplementedError(\n                    \"spawnProcess not available since pywin32 is not installed.\")\n        else:\n            raise NotImplementedError(\n                \"spawnProcess only available on Windows or POSIX.\")\n\n    # IReactorUDP\n\n    def listenUDP(self, port, protocol, interface='', maxPacketSize=8192):\n        \"\"\"Connects a given L{DatagramProtocol} to the given numeric UDP port.\n\n        @returns: object conforming to L{IListeningPort}.\n        \"\"\"\n        p = udp.Port(port, protocol, interface, maxPacketSize, self)\n        p.startListening()\n        return p\n\n    # IReactorMulticast\n\n    def listenMulticast(self, port, protocol, interface='', maxPacketSize=8192, listenMultiple=False):\n        \"\"\"Connects a given DatagramProtocol to the given numeric UDP port.\n\n        EXPERIMENTAL.\n\n        @returns: object conforming to IListeningPort.\n        \"\"\"\n        p = udp.MulticastPort(port, protocol, interface, maxPacketSize, self, listenMultiple)\n        p.startListening()\n        return p\n\n\n    # IReactorUNIX\n\n    def connectUNIX(self, address, factory, timeout=30, checkPID=0):\n        assert unixEnabled, \"UNIX support is not present\"\n        c = unix.Connector(address, factory, timeout, self, checkPID)\n        c.connect()\n        return c\n\n    def listenUNIX(self, address, factory, backlog=50, mode=0o666, wantPID=0):\n        assert unixEnabled, \"UNIX support is not present\"\n        p = unix.Port(address, factory, backlog, mode, self, wantPID)\n        p.startListening()\n        return p\n\n\n    # IReactorUNIXDatagram\n\n    def listenUNIXDatagram(self, address, protocol, maxPacketSize=8192,\n                           mode=0o666):\n        \"\"\"\n        Connects a given L{DatagramProtocol} to the given path.\n\n        EXPERIMENTAL.\n\n        @returns: object conforming to L{IListeningPort}.\n        \"\"\"\n        assert unixEnabled, \"UNIX support is not present\"\n        p = unix.DatagramPort(address, protocol, maxPacketSize, mode, self)\n        p.startListening()\n        return p\n\n    def connectUNIXDatagram(self, address, protocol, maxPacketSize=8192,\n                            mode=0o666, bindAddress=None):\n        \"\"\"\n        Connects a L{ConnectedDatagramProtocol} instance to a path.\n\n        EXPERIMENTAL.\n        \"\"\"\n        assert unixEnabled, \"UNIX support is not present\"\n        p = unix.ConnectedDatagramPort(address, protocol, maxPacketSize, mode, bindAddress, self)\n        p.startListening()\n        return p\n\n\n    # IReactorSocket (no AF_UNIX on Windows)\n\n    if unixEnabled:\n        _supportedAddressFamilies = (\n            socket.AF_INET, socket.AF_INET6, socket.AF_UNIX,\n        )\n    else:\n        _supportedAddressFamilies = (\n            socket.AF_INET, socket.AF_INET6,\n        )\n\n    def adoptStreamPort(self, fileDescriptor, addressFamily, factory):\n        \"\"\"\n        Create a new L{IListeningPort} from an already-initialized socket.\n\n        This just dispatches to a suitable port implementation (eg from\n        L{IReactorTCP}, etc) based on the specified C{addressFamily}.\n\n        @see: L{twisted.internet.interfaces.IReactorSocket.adoptStreamPort}\n        \"\"\"\n        if addressFamily not in self._supportedAddressFamilies:\n            raise error.UnsupportedAddressFamily(addressFamily)\n\n        if unixEnabled and addressFamily == socket.AF_UNIX:\n            p = unix.Port._fromListeningDescriptor(\n                self, fileDescriptor, factory)\n        else:\n            p = tcp.Port._fromListeningDescriptor(\n                self, fileDescriptor, addressFamily, factory)\n        p.startListening()\n        return p\n\n    def adoptStreamConnection(self, fileDescriptor, addressFamily, factory):\n        \"\"\"\n        @see:\n            L{twisted.internet.interfaces.IReactorSocket.adoptStreamConnection}\n        \"\"\"\n        if addressFamily not in self._supportedAddressFamilies:\n            raise error.UnsupportedAddressFamily(addressFamily)\n\n        if unixEnabled and addressFamily == socket.AF_UNIX:\n            return unix.Server._fromConnectedSocket(\n                fileDescriptor, factory, self)\n        else:\n            return tcp.Server._fromConnectedSocket(\n                fileDescriptor, addressFamily, factory, self)\n\n\n    def adoptDatagramPort(self, fileDescriptor, addressFamily, protocol,\n                          maxPacketSize=8192):\n        if addressFamily not in (socket.AF_INET, socket.AF_INET6):\n            raise error.UnsupportedAddressFamily(addressFamily)\n\n        p = udp.Port._fromListeningDescriptor(\n            self, fileDescriptor, addressFamily, protocol,\n            maxPacketSize=maxPacketSize)\n        p.startListening()\n        return p\n\n\n\n    # IReactorTCP\n\n    def listenTCP(self, port, factory, backlog=50, interface=''):\n        p = tcp.Port(port, factory, backlog, interface, self)\n        p.startListening()\n        return p\n\n    def connectTCP(self, host, port, factory, timeout=30, bindAddress=None):\n        c = tcp.Connector(host, port, factory, timeout, bindAddress, self)\n        c.connect()\n        return c\n\n    # IReactorSSL (sometimes, not implemented)\n\n    def connectSSL(self, host, port, factory, contextFactory, timeout=30, bindAddress=None):\n        if tls is not None:\n            tlsFactory = tls.TLSMemoryBIOFactory(contextFactory, True, factory)\n            return self.connectTCP(host, port, tlsFactory, timeout, bindAddress)\n        elif ssl is not None:\n            c = ssl.Connector(\n                host, port, factory, contextFactory, timeout, bindAddress, self)\n            c.connect()\n            return c\n        else:\n            assert False, \"SSL support is not present\"\n\n\n\n    def listenSSL(self, port, factory, contextFactory, backlog=50, interface=''):\n        if tls is not None:\n            tlsFactory = tls.TLSMemoryBIOFactory(contextFactory, False, factory)\n            port = self.listenTCP(port, tlsFactory, backlog, interface)\n            port._type = 'TLS'\n            return port\n        elif ssl is not None:\n            p = ssl.Port(\n                port, factory, contextFactory, backlog, interface, self)\n            p.startListening()\n            return p\n        else:\n            assert False, \"SSL support is not present\"\n\n\n    def _removeAll(self, readers, writers):\n        \"\"\"\n        Remove all readers and writers, and list of removed L{IReadDescriptor}s\n        and L{IWriteDescriptor}s.\n\n        Meant for calling from subclasses, to implement removeAll, like::\n\n          def removeAll(self):\n              return self._removeAll(self._reads, self._writes)\n\n        where C{self._reads} and C{self._writes} are iterables.\n        \"\"\"\n        removedReaders = set(readers) - self._internalReaders\n        for reader in removedReaders:\n            self.removeReader(reader)\n\n        removedWriters = set(writers)\n        for writer in removedWriters:\n            self.removeWriter(writer)\n\n        return list(removedReaders | removedWriters)\n\n\nclass _PollLikeMixin(object):\n    \"\"\"\n    Mixin for poll-like reactors.\n\n    Subclasses must define the following attributes::\n\n      - _POLL_DISCONNECTED - Bitmask for events indicating a connection was\n        lost.\n      - _POLL_IN - Bitmask for events indicating there is input to read.\n      - _POLL_OUT - Bitmask for events indicating output can be written.\n\n    Must be mixed in to a subclass of PosixReactorBase (for\n    _disconnectSelectable).\n    \"\"\"\n\n    def _doReadOrWrite(self, selectable, fd, event):\n        \"\"\"\n        fd is available for read or write, do the work and raise errors if\n        necessary.\n        \"\"\"\n        why = None\n        inRead = False\n        if event & self._POLL_DISCONNECTED and not (event & self._POLL_IN):\n            # Handle disconnection.  But only if we finished processing all\n            # the pending input.\n            if fd in self._reads:\n                # If we were reading from the descriptor then this is a\n                # clean shutdown.  We know there are no read events pending\n                # because we just checked above.  It also might be a\n                # half-close (which is why we have to keep track of inRead).\n                inRead = True\n                why = CONNECTION_DONE\n            else:\n                # If we weren't reading, this is an error shutdown of some\n                # sort.\n                why = CONNECTION_LOST\n        else:\n            # Any non-disconnect event turns into a doRead or a doWrite.\n            try:\n                # First check to see if the descriptor is still valid.  This\n                # gives fileno() a chance to raise an exception, too.\n                # Ideally, disconnection would always be indicated by the\n                # return value of doRead or doWrite (or an exception from\n                # one of those methods), but calling fileno here helps make\n                # buggy applications more transparent.\n                if selectable.fileno() == -1:\n                    # -1 is sort of a historical Python artifact.  Python\n                    # files and sockets used to change their file descriptor\n                    # to -1 when they closed.  For the time being, we'll\n                    # continue to support this anyway in case applications\n                    # replicated it, plus abstract.FileDescriptor.fileno\n                    # returns -1.  Eventually it'd be good to deprecate this\n                    # case.\n                    why = _NO_FILEDESC\n                else:\n                    if event & self._POLL_IN:\n                        # Handle a read event.\n                        why = selectable.doRead()\n                        inRead = True\n                    if not why and event & self._POLL_OUT:\n                        # Handle a write event, as long as doRead didn't\n                        # disconnect us.\n                        why = selectable.doWrite()\n                        inRead = False\n            except:\n                # Any exception from application code gets logged and will\n                # cause us to disconnect the selectable.\n                why = sys.exc_info()[1]\n                log.err()\n        if why:\n            self._disconnectSelectable(selectable, why, inRead)\n\n\n\n@implementer(IReactorFDSet)\nclass _ContinuousPolling(_PollLikeMixin, _DisconnectSelectableMixin):\n    \"\"\"\n    Schedule reads and writes based on the passage of time, rather than\n    notification.\n\n    This is useful for supporting polling filesystem files, which C{epoll(7)}\n    does not support.\n\n    The implementation uses L{_PollLikeMixin}, which is a bit hacky, but\n    re-implementing and testing the relevant code yet again is unappealing.\n\n    @ivar _reactor: The L{EPollReactor} that is using this instance.\n\n    @ivar _loop: A C{LoopingCall} that drives the polling, or L{None}.\n\n    @ivar _readers: A C{set} of C{FileDescriptor} objects that should be read\n        from.\n\n    @ivar _writers: A C{set} of C{FileDescriptor} objects that should be\n        written to.\n    \"\"\"\n\n    # Attributes for _PollLikeMixin\n    _POLL_DISCONNECTED = 1\n    _POLL_IN = 2\n    _POLL_OUT = 4\n\n\n    def __init__(self, reactor):\n        self._reactor = reactor\n        self._loop = None\n        self._readers = set()\n        self._writers = set()\n\n\n    def _checkLoop(self):\n        \"\"\"\n        Start or stop a C{LoopingCall} based on whether there are readers and\n        writers.\n        \"\"\"\n        if self._readers or self._writers:\n            if self._loop is None:\n                from twisted.internet.task import LoopingCall, _EPSILON\n                self._loop = LoopingCall(self.iterate)\n                self._loop.clock = self._reactor\n                # LoopingCall seems unhappy with timeout of 0, so use very\n                # small number:\n                self._loop.start(_EPSILON, now=False)\n        elif self._loop:\n            self._loop.stop()\n            self._loop = None\n\n\n    def iterate(self):\n        \"\"\"\n        Call C{doRead} and C{doWrite} on all readers and writers respectively.\n        \"\"\"\n        for reader in list(self._readers):\n            self._doReadOrWrite(reader, reader, self._POLL_IN)\n        for writer in list(self._writers):\n            self._doReadOrWrite(writer, writer, self._POLL_OUT)\n\n\n    def addReader(self, reader):\n        \"\"\"\n        Add a C{FileDescriptor} for notification of data available to read.\n        \"\"\"\n        self._readers.add(reader)\n        self._checkLoop()\n\n\n    def addWriter(self, writer):\n        \"\"\"\n        Add a C{FileDescriptor} for notification of data available to write.\n        \"\"\"\n        self._writers.add(writer)\n        self._checkLoop()\n\n\n    def removeReader(self, reader):\n        \"\"\"\n        Remove a C{FileDescriptor} from notification of data available to read.\n        \"\"\"\n        try:\n            self._readers.remove(reader)\n        except KeyError:\n            return\n        self._checkLoop()\n\n\n    def removeWriter(self, writer):\n        \"\"\"\n        Remove a C{FileDescriptor} from notification of data available to\n        write.\n        \"\"\"\n        try:\n            self._writers.remove(writer)\n        except KeyError:\n            return\n        self._checkLoop()\n\n\n    def removeAll(self):\n        \"\"\"\n        Remove all readers and writers.\n        \"\"\"\n        result = list(self._readers | self._writers)\n        # Don't reset to new value, since self.isWriting and .isReading refer\n        # to the existing instance:\n        self._readers.clear()\n        self._writers.clear()\n        return result\n\n\n    def getReaders(self):\n        \"\"\"\n        Return a list of the readers.\n        \"\"\"\n        return list(self._readers)\n\n\n    def getWriters(self):\n        \"\"\"\n        Return a list of the writers.\n        \"\"\"\n        return list(self._writers)\n\n\n    def isReading(self, fd):\n        \"\"\"\n        Checks if the file descriptor is currently being observed for read\n        readiness.\n\n        @param fd: The file descriptor being checked.\n        @type fd: L{twisted.internet.abstract.FileDescriptor}\n        @return: C{True} if the file descriptor is being observed for read\n            readiness, C{False} otherwise.\n        @rtype: C{bool}\n        \"\"\"\n        return fd in self._readers\n\n\n    def isWriting(self, fd):\n        \"\"\"\n        Checks if the file descriptor is currently being observed for write\n        readiness.\n\n        @param fd: The file descriptor being checked.\n        @type fd: L{twisted.internet.abstract.FileDescriptor}\n        @return: C{True} if the file descriptor is being observed for write\n            readiness, C{False} otherwise.\n        @rtype: C{bool}\n        \"\"\"\n        return fd in self._writers\n\n\n\nif tls is not None or ssl is not None:\n    classImplements(PosixReactorBase, IReactorSSL)\nif unixEnabled:\n    classImplements(PosixReactorBase, IReactorUNIX, IReactorUNIXDatagram)\nif processEnabled:\n    classImplements(PosixReactorBase, IReactorProcess)\nif getattr(socket, 'fromfd', None) is not None:\n    classImplements(PosixReactorBase, IReactorSocket)\n\n__all__ = [\"PosixReactorBase\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/process.py",
    "content": "# -*- test-case-name: twisted.test.test_process -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nUNIX Process management.\n\nDo NOT use this module directly - use reactor.spawnProcess() instead.\n\nMaintainer: Itamar Shtull-Trauring\n\"\"\"\n\nfrom __future__ import division, absolute_import, print_function\n\nfrom twisted.python.runtime import platform\n\nif platform.isWindows():\n    raise ImportError((\"twisted.internet.process does not work on Windows. \"\n                       \"Use the reactor.spawnProcess() API instead.\"))\n\nimport errno\nimport gc\nimport os\nimport io\nimport signal\nimport stat\nimport sys\nimport traceback\n\ntry:\n    import pty\nexcept ImportError:\n    pty = None\n\ntry:\n    import fcntl, termios\nexcept ImportError:\n    fcntl = None\n\nfrom zope.interface import implementer\n\nfrom twisted.python import log, failure\nfrom twisted.python.util import switchUID\nfrom twisted.python.compat import items, range, _PY3\nfrom twisted.internet import fdesc, abstract, error\nfrom twisted.internet.main import CONNECTION_LOST, CONNECTION_DONE\nfrom twisted.internet._baseprocess import BaseProcess\nfrom twisted.internet.interfaces import IProcessTransport\n\n# Some people were importing this, which is incorrect, just keeping it\n# here for backwards compatibility:\nProcessExitedAlready = error.ProcessExitedAlready\n\nreapProcessHandlers = {}\n\ndef reapAllProcesses():\n    \"\"\"\n    Reap all registered processes.\n    \"\"\"\n    # Coerce this to a list, as reaping the process changes the dictionary and\n    # causes a \"size changed during iteration\" exception\n    for process in list(reapProcessHandlers.values()):\n        process.reapProcess()\n\n\n\ndef registerReapProcessHandler(pid, process):\n    \"\"\"\n    Register a process handler for the given pid, in case L{reapAllProcesses}\n    is called.\n\n    @param pid: the pid of the process.\n    @param process: a process handler.\n    \"\"\"\n    if pid in reapProcessHandlers:\n        raise RuntimeError(\"Try to register an already registered process.\")\n    try:\n        auxPID, status = os.waitpid(pid, os.WNOHANG)\n    except:\n        log.msg('Failed to reap %d:' % pid)\n        log.err()\n        auxPID = None\n    if auxPID:\n        process.processEnded(status)\n    else:\n        # if auxPID is 0, there are children but none have exited\n        reapProcessHandlers[pid] = process\n\n\n\ndef unregisterReapProcessHandler(pid, process):\n    \"\"\"\n    Unregister a process handler previously registered with\n    L{registerReapProcessHandler}.\n    \"\"\"\n    if not (pid in reapProcessHandlers\n            and reapProcessHandlers[pid] == process):\n        raise RuntimeError(\"Try to unregister a process not registered.\")\n    del reapProcessHandlers[pid]\n\n\n\nclass ProcessWriter(abstract.FileDescriptor):\n    \"\"\"\n    (Internal) Helper class to write into a Process's input pipe.\n\n    I am a helper which describes a selectable asynchronous writer to a\n    process's input pipe, including stdin.\n\n    @ivar enableReadHack: A flag which determines how readability on this\n        write descriptor will be handled.  If C{True}, then readability may\n        indicate the reader for this write descriptor has been closed (ie,\n        the connection has been lost).  If C{False}, then readability events\n        are ignored.\n    \"\"\"\n    connected = 1\n    ic = 0\n    enableReadHack = False\n\n    def __init__(self, reactor, proc, name, fileno, forceReadHack=False):\n        \"\"\"\n        Initialize, specifying a Process instance to connect to.\n        \"\"\"\n        abstract.FileDescriptor.__init__(self, reactor)\n        fdesc.setNonBlocking(fileno)\n        self.proc = proc\n        self.name = name\n        self.fd = fileno\n\n        if not stat.S_ISFIFO(os.fstat(self.fileno()).st_mode):\n            # If the fd is not a pipe, then the read hack is never\n            # applicable.  This case arises when ProcessWriter is used by\n            # StandardIO and stdout is redirected to a normal file.\n            self.enableReadHack = False\n        elif forceReadHack:\n            self.enableReadHack = True\n        else:\n            # Detect if this fd is actually a write-only fd. If it's\n            # valid to read, don't try to detect closing via read.\n            # This really only means that we cannot detect a TTY's write\n            # pipe being closed.\n            try:\n                os.read(self.fileno(), 0)\n            except OSError:\n                # It's a write-only pipe end, enable hack\n                self.enableReadHack = True\n\n        if self.enableReadHack:\n            self.startReading()\n\n\n    def fileno(self):\n        \"\"\"\n        Return the fileno() of my process's stdin.\n        \"\"\"\n        return self.fd\n\n\n    def writeSomeData(self, data):\n        \"\"\"\n        Write some data to the open process.\n        \"\"\"\n        rv = fdesc.writeToFD(self.fd, data)\n        if rv == len(data) and self.enableReadHack:\n            # If the send buffer is now empty and it is necessary to monitor\n            # this descriptor for readability to detect close, try detecting\n            # readability now.\n            self.startReading()\n        return rv\n\n\n    def write(self, data):\n        self.stopReading()\n        abstract.FileDescriptor.write(self, data)\n\n\n    def doRead(self):\n        \"\"\"\n        The only way a write pipe can become \"readable\" is at EOF, because the\n        child has closed it, and we're using a reactor which doesn't\n        distinguish between readable and closed (such as the select reactor).\n\n        Except that's not true on linux < 2.6.11. It has the following\n        characteristics: write pipe is completely empty => POLLOUT (writable in\n        select), write pipe is not completely empty => POLLIN (readable in\n        select), write pipe's reader closed => POLLIN|POLLERR (readable and\n        writable in select)\n\n        That's what this funky code is for. If linux was not broken, this\n        function could be simply \"return CONNECTION_LOST\".\n        \"\"\"\n        if self.enableReadHack:\n            return CONNECTION_LOST\n        else:\n            self.stopReading()\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        See abstract.FileDescriptor.connectionLost.\n        \"\"\"\n        # At least on macOS 10.4, exiting while stdout is non-blocking can\n        # result in data loss.  For some reason putting the file descriptor\n        # back into blocking mode seems to resolve this issue.\n        fdesc.setBlocking(self.fd)\n\n        abstract.FileDescriptor.connectionLost(self, reason)\n        self.proc.childConnectionLost(self.name, reason)\n\n\n\nclass ProcessReader(abstract.FileDescriptor):\n    \"\"\"\n    ProcessReader\n\n    I am a selectable representation of a process's output pipe, such as\n    stdout and stderr.\n    \"\"\"\n    connected = True\n\n    def __init__(self, reactor, proc, name, fileno):\n        \"\"\"\n        Initialize, specifying a process to connect to.\n        \"\"\"\n        abstract.FileDescriptor.__init__(self, reactor)\n        fdesc.setNonBlocking(fileno)\n        self.proc = proc\n        self.name = name\n        self.fd = fileno\n        self.startReading()\n\n\n    def fileno(self):\n        \"\"\"\n        Return the fileno() of my process's stderr.\n        \"\"\"\n        return self.fd\n\n\n    def writeSomeData(self, data):\n        # the only time this is actually called is after .loseConnection Any\n        # actual write attempt would fail, so we must avoid that. This hack\n        # allows us to use .loseConnection on both readers and writers.\n        assert data == b\"\"\n        return CONNECTION_LOST\n\n\n    def doRead(self):\n        \"\"\"\n        This is called when the pipe becomes readable.\n        \"\"\"\n        return fdesc.readFromFD(self.fd, self.dataReceived)\n\n\n    def dataReceived(self, data):\n        self.proc.childDataReceived(self.name, data)\n\n\n    def loseConnection(self):\n        if self.connected and not self.disconnecting:\n            self.disconnecting = 1\n            self.stopReading()\n            self.reactor.callLater(0, self.connectionLost,\n                                   failure.Failure(CONNECTION_DONE))\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Close my end of the pipe, signal the Process (which signals the\n        ProcessProtocol).\n        \"\"\"\n        abstract.FileDescriptor.connectionLost(self, reason)\n        self.proc.childConnectionLost(self.name, reason)\n\n\n\nclass _BaseProcess(BaseProcess, object):\n    \"\"\"\n    Base class for Process and PTYProcess.\n    \"\"\"\n    status = None\n    pid = None\n\n    def reapProcess(self):\n        \"\"\"\n        Try to reap a process (without blocking) via waitpid.\n\n        This is called when sigchild is caught or a Process object loses its\n        \"connection\" (stdout is closed) This ought to result in reaping all\n        zombie processes, since it will be called twice as often as it needs\n        to be.\n\n        (Unfortunately, this is a slightly experimental approach, since\n        UNIX has no way to be really sure that your process is going to\n        go away w/o blocking.  I don't want to block.)\n        \"\"\"\n        try:\n            try:\n                pid, status = os.waitpid(self.pid, os.WNOHANG)\n            except OSError as e:\n                if e.errno == errno.ECHILD:\n                    # no child process\n                    pid = None\n                else:\n                    raise\n        except:\n            log.msg('Failed to reap %d:' % self.pid)\n            log.err()\n            pid = None\n        if pid:\n            self.processEnded(status)\n            unregisterReapProcessHandler(pid, self)\n\n\n    def _getReason(self, status):\n        exitCode = sig = None\n        if os.WIFEXITED(status):\n            exitCode = os.WEXITSTATUS(status)\n        else:\n            sig = os.WTERMSIG(status)\n        if exitCode or sig:\n            return error.ProcessTerminated(exitCode, sig, status)\n        return error.ProcessDone(status)\n\n\n    def signalProcess(self, signalID):\n        \"\"\"\n        Send the given signal C{signalID} to the process. It'll translate a\n        few signals ('HUP', 'STOP', 'INT', 'KILL', 'TERM') from a string\n        representation to its int value, otherwise it'll pass directly the\n        value provided\n\n        @type signalID: C{str} or C{int}\n        \"\"\"\n        if signalID in ('HUP', 'STOP', 'INT', 'KILL', 'TERM'):\n            signalID = getattr(signal, 'SIG%s' % (signalID,))\n        if self.pid is None:\n            raise ProcessExitedAlready()\n        try:\n            os.kill(self.pid, signalID)\n        except OSError as e:\n            if e.errno == errno.ESRCH:\n                raise ProcessExitedAlready()\n            else:\n                raise\n\n\n    def _resetSignalDisposition(self):\n        # The Python interpreter ignores some signals, and our child\n        # process will inherit that behaviour. To have a child process\n        # that responds to signals normally, we need to reset our\n        # child process's signal handling (just) after we fork and\n        # before we execvpe.\n        for signalnum in range(1, signal.NSIG):\n            if signal.getsignal(signalnum) == signal.SIG_IGN:\n                # Reset signal handling to the default\n                signal.signal(signalnum, signal.SIG_DFL)\n\n\n    def _fork(self, path, uid, gid, executable, args, environment, **kwargs):\n        \"\"\"\n        Fork and then exec sub-process.\n\n        @param path: the path where to run the new process.\n        @type path: L{bytes} or L{unicode}\n        @param uid: if defined, the uid used to run the new process.\n        @type uid: L{int}\n        @param gid: if defined, the gid used to run the new process.\n        @type gid: L{int}\n        @param executable: the executable to run in a new process.\n        @type executable: L{str}\n        @param args: arguments used to create the new process.\n        @type args: L{list}.\n        @param environment: environment used for the new process.\n        @type environment: L{dict}.\n        @param kwargs: keyword arguments to L{_setupChild} method.\n        \"\"\"\n        collectorEnabled = gc.isenabled()\n        gc.disable()\n        try:\n            self.pid = os.fork()\n        except:\n            # Still in the parent process\n            if collectorEnabled:\n                gc.enable()\n            raise\n        else:\n            if self.pid == 0:\n                # A return value of 0 from fork() indicates that we are now\n                # executing in the child process.\n\n                # Do not put *ANY* code outside the try block. The child\n                # process must either exec or _exit. If it gets outside this\n                # block (due to an exception that is not handled here, but\n                # which might be handled higher up), there will be two copies\n                # of the parent running in parallel, doing all kinds of damage.\n\n                # After each change to this code, review it to make sure there\n                # are no exit paths.\n\n                try:\n                    # Stop debugging. If I am, I don't care anymore.\n                    sys.settrace(None)\n                    self._setupChild(**kwargs)\n                    self._execChild(path, uid, gid, executable, args,\n                                    environment)\n                except:\n                    # If there are errors, try to write something descriptive\n                    # to stderr before exiting.\n\n                    # The parent's stderr isn't *necessarily* fd 2 anymore, or\n                    # even still available; however, even libc assumes that\n                    # write(2, err) is a useful thing to attempt.\n\n                    try:\n                        stderr = os.fdopen(2, 'wb')\n                        msg = (\"Upon execvpe {0} {1} in environment id {2}\"\n                               \"\\n:\").format(executable, str(args),\n                                             id(environment))\n\n                        if _PY3:\n\n                            # On Python 3, print_exc takes a text stream, but\n                            # on Python 2 it still takes a byte stream.  So on\n                            # Python 3 we will wrap up the byte stream returned\n                            # by os.fdopen using TextIOWrapper.\n\n                            # We hard-code UTF-8 as the encoding here, rather\n                            # than looking at something like\n                            # getfilesystemencoding() or sys.stderr.encoding,\n                            # because we want an encoding that will be able to\n                            # encode the full range of code points.  We are\n                            # (most likely) talking to the parent process on\n                            # the other end of this pipe and not the filesystem\n                            # or the original sys.stderr, so there's no point\n                            # in trying to match the encoding of one of those\n                            # objects.\n\n                            stderr = io.TextIOWrapper(stderr, encoding=\"utf-8\")\n\n                        stderr.write(msg)\n                        traceback.print_exc(file=stderr)\n                        stderr.flush()\n\n                        for fd in range(3):\n                            os.close(fd)\n                    except:\n                        # Handle all errors during the error-reporting process\n                        # silently to ensure that the child terminates.\n                        pass\n\n                # See comment above about making sure that we reach this line\n                # of code.\n                os._exit(1)\n\n        # we are now in parent process\n        if collectorEnabled:\n            gc.enable()\n        self.status = -1 # this records the exit status of the child\n\n\n    def _setupChild(self, *args, **kwargs):\n        \"\"\"\n        Setup the child process. Override in subclasses.\n        \"\"\"\n        raise NotImplementedError()\n\n\n    def _execChild(self, path, uid, gid, executable, args, environment):\n        \"\"\"\n        The exec() which is done in the forked child.\n        \"\"\"\n        if path:\n            os.chdir(path)\n        if uid is not None or gid is not None:\n            if uid is None:\n                uid = os.geteuid()\n            if gid is None:\n                gid = os.getegid()\n            # set the UID before I actually exec the process\n            os.setuid(0)\n            os.setgid(0)\n            switchUID(uid, gid)\n        os.execvpe(executable, args, environment)\n\n\n    def __repr__(self):\n        \"\"\"\n        String representation of a process.\n        \"\"\"\n        return \"<%s pid=%s status=%s>\" % (self.__class__.__name__,\n                                          self.pid, self.status)\n\n\n\nclass _FDDetector(object):\n    \"\"\"\n    This class contains the logic necessary to decide which of the available\n    system techniques should be used to detect the open file descriptors for\n    the current process. The chosen technique gets monkey-patched into the\n    _listOpenFDs method of this class so that the detection only needs to occur\n    once.\n\n    @ivar listdir: The implementation of listdir to use. This gets overwritten\n        by the test cases.\n    @ivar getpid: The implementation of getpid to use, returns the PID of the\n        running process.\n    @ivar openfile: The implementation of open() to use, by default the Python\n        builtin.\n    \"\"\"\n    # So that we can unit test this\n    listdir = os.listdir\n    getpid = os.getpid\n    openfile = open\n\n    def __init__(self):\n        self._implementations = [\n            self._procFDImplementation, self._devFDImplementation,\n            self._fallbackFDImplementation]\n\n\n    def _listOpenFDs(self):\n        \"\"\"\n        Return an iterable of file descriptors which I{may} be open in this\n        process.\n\n        This will try to return the fewest possible descriptors without missing\n        any.\n        \"\"\"\n        self._listOpenFDs = self._getImplementation()\n        return self._listOpenFDs()\n\n\n    def _getImplementation(self):\n        \"\"\"\n        Pick a method which gives correct results for C{_listOpenFDs} in this\n        runtime environment.\n\n        This involves a lot of very platform-specific checks, some of which may\n        be relatively expensive.  Therefore the returned method should be saved\n        and re-used, rather than always calling this method to determine what it\n        is.\n\n        See the implementation for the details of how a method is selected.\n        \"\"\"\n        for impl in self._implementations:\n            try:\n                before = impl()\n            except:\n                continue\n            with self.openfile(\"/dev/null\", \"r\"):\n                after = impl()\n            if before != after:\n                return impl\n        # If no implementation can detect the newly opened file above, then just\n        # return the last one.  The last one should therefore always be one\n        # which makes a simple static guess which includes all possible open\n        # file descriptors, but perhaps also many other values which do not\n        # correspond to file descriptors.  For example, the scheme implemented\n        # by _fallbackFDImplementation is suitable to be the last entry.\n        return impl\n\n\n    def _devFDImplementation(self):\n        \"\"\"\n        Simple implementation for systems where /dev/fd actually works.\n        See: http://www.freebsd.org/cgi/man.cgi?fdescfs\n        \"\"\"\n        dname = \"/dev/fd\"\n        result = [int(fd) for fd in self.listdir(dname)]\n        return result\n\n\n    def _procFDImplementation(self):\n        \"\"\"\n        Simple implementation for systems where /proc/pid/fd exists (we assume\n        it works).\n        \"\"\"\n        dname = \"/proc/%d/fd\" % (self.getpid(),)\n        return [int(fd) for fd in self.listdir(dname)]\n\n\n    def _fallbackFDImplementation(self):\n        \"\"\"\n        Fallback implementation where either the resource module can inform us\n        about the upper bound of how many FDs to expect, or where we just guess\n        a constant maximum if there is no resource module.\n\n        All possible file descriptors from 0 to that upper bound are returned\n        with no attempt to exclude invalid file descriptor values.\n        \"\"\"\n        try:\n            import resource\n        except ImportError:\n            maxfds = 1024\n        else:\n            # OS-X reports 9223372036854775808. That's a lot of fds to close.\n            # OS-X should get the /dev/fd implementation instead, so mostly\n            # this check probably isn't necessary.\n            maxfds = min(1024, resource.getrlimit(resource.RLIMIT_NOFILE)[1])\n        return range(maxfds)\n\n\n\ndetector = _FDDetector()\n\ndef _listOpenFDs():\n    \"\"\"\n    Use the global detector object to figure out which FD implementation to\n    use.\n    \"\"\"\n    return detector._listOpenFDs()\n\n\n\n@implementer(IProcessTransport)\nclass Process(_BaseProcess):\n    \"\"\"\n    An operating-system Process.\n\n    This represents an operating-system process with arbitrary input/output\n    pipes connected to it. Those pipes may represent standard input,\n    standard output, and standard error, or any other file descriptor.\n\n    On UNIX, this is implemented using fork(), exec(), pipe()\n    and fcntl(). These calls may not exist elsewhere so this\n    code is not cross-platform. (also, windows can only select\n    on sockets...)\n    \"\"\"\n    debug = False\n    debug_child = False\n\n    status = -1\n    pid = None\n\n    processWriterFactory = ProcessWriter\n    processReaderFactory = ProcessReader\n\n    def __init__(self,\n                 reactor, executable, args, environment, path, proto,\n                 uid=None, gid=None, childFDs=None):\n        \"\"\"\n        Spawn an operating-system process.\n\n        This is where the hard work of disconnecting all currently open\n        files / forking / executing the new process happens.  (This is\n        executed automatically when a Process is instantiated.)\n\n        This will also run the subprocess as a given user ID and group ID, if\n        specified.  (Implementation Note: this doesn't support all the arcane\n        nuances of setXXuid on UNIX: it will assume that either your effective\n        or real UID is 0.)\n        \"\"\"\n        if not proto:\n            assert 'r' not in childFDs.values()\n            assert 'w' not in childFDs.values()\n        _BaseProcess.__init__(self, proto)\n\n        self.pipes = {}\n        # keys are childFDs, we can sense them closing\n        # values are ProcessReader/ProcessWriters\n\n        helpers = {}\n        # keys are childFDs\n        # values are parentFDs\n\n        if childFDs is None:\n            childFDs = {0: \"w\", # we write to the child's stdin\n                        1: \"r\", # we read from their stdout\n                        2: \"r\", # and we read from their stderr\n                        }\n\n        debug = self.debug\n        if debug: print(\"childFDs\", childFDs)\n\n        _openedPipes = []\n        def pipe():\n            r, w = os.pipe()\n            _openedPipes.extend([r, w])\n            return r, w\n\n        # fdmap.keys() are filenos of pipes that are used by the child.\n        fdmap = {} # maps childFD to parentFD\n        try:\n            for childFD, target in items(childFDs):\n                if debug: print(\"[%d]\" % childFD, target)\n                if target == \"r\":\n                    # we need a pipe that the parent can read from\n                    readFD, writeFD = pipe()\n                    if debug: print(\"readFD=%d, writeFD=%d\" % (readFD, writeFD))\n                    fdmap[childFD] = writeFD     # child writes to this\n                    helpers[childFD] = readFD    # parent reads from this\n                elif target == \"w\":\n                    # we need a pipe that the parent can write to\n                    readFD, writeFD = pipe()\n                    if debug: print(\"readFD=%d, writeFD=%d\" % (readFD, writeFD))\n                    fdmap[childFD] = readFD      # child reads from this\n                    helpers[childFD] = writeFD   # parent writes to this\n                else:\n                    assert type(target) == int, '%r should be an int' % (target,)\n                    fdmap[childFD] = target      # parent ignores this\n            if debug: print(\"fdmap\", fdmap)\n            if debug: print(\"helpers\", helpers)\n            # the child only cares about fdmap.values()\n\n            self._fork(path, uid, gid, executable, args, environment, fdmap=fdmap)\n        except:\n            for pipe in _openedPipes:\n                os.close(pipe)\n            raise\n\n        # we are the parent process:\n        self.proto = proto\n\n        # arrange for the parent-side pipes to be read and written\n        for childFD, parentFD in items(helpers):\n            os.close(fdmap[childFD])\n            if childFDs[childFD] == \"r\":\n                reader = self.processReaderFactory(reactor, self, childFD,\n                                        parentFD)\n                self.pipes[childFD] = reader\n\n            if childFDs[childFD] == \"w\":\n                writer = self.processWriterFactory(reactor, self, childFD,\n                                        parentFD, forceReadHack=True)\n                self.pipes[childFD] = writer\n\n        try:\n            # the 'transport' is used for some compatibility methods\n            if self.proto is not None:\n                self.proto.makeConnection(self)\n        except:\n            log.err()\n\n        # The reactor might not be running yet.  This might call back into\n        # processEnded synchronously, triggering an application-visible\n        # callback.  That's probably not ideal.  The replacement API for\n        # spawnProcess should improve upon this situation.\n        registerReapProcessHandler(self.pid, self)\n\n\n    def _setupChild(self, fdmap):\n        \"\"\"\n        fdmap[childFD] = parentFD\n\n        The child wants to end up with 'childFD' attached to what used to be\n        the parent's parentFD. As an example, a bash command run like\n        'command 2>&1' would correspond to an fdmap of {0:0, 1:1, 2:1}.\n        'command >foo.txt' would be {0:0, 1:os.open('foo.txt'), 2:2}.\n\n        This is accomplished in two steps::\n\n            1. close all file descriptors that aren't values of fdmap.  This\n               means 0 .. maxfds (or just the open fds within that range, if\n               the platform supports '/proc/<pid>/fd').\n\n            2. for each childFD::\n\n                 - if fdmap[childFD] == childFD, the descriptor is already in\n                   place.  Make sure the CLOEXEC flag is not set, then delete\n                   the entry from fdmap.\n\n                 - if childFD is in fdmap.values(), then the target descriptor\n                   is busy. Use os.dup() to move it elsewhere, update all\n                   fdmap[childFD] items that point to it, then close the\n                   original. Then fall through to the next case.\n\n                 - now fdmap[childFD] is not in fdmap.values(), and is free.\n                   Use os.dup2() to move it to the right place, then close the\n                   original.\n        \"\"\"\n        debug = self.debug_child\n        if debug:\n            errfd = sys.stderr\n            errfd.write(\"starting _setupChild\\n\")\n\n        destList = fdmap.values()\n        for fd in _listOpenFDs():\n            if fd in destList:\n                continue\n            if debug and fd == errfd.fileno():\n                continue\n            try:\n                os.close(fd)\n            except:\n                pass\n\n        # at this point, the only fds still open are the ones that need to\n        # be moved to their appropriate positions in the child (the targets\n        # of fdmap, i.e. fdmap.values() )\n\n        if debug: print(\"fdmap\", fdmap, file=errfd)\n        for child in sorted(fdmap.keys()):\n            target = fdmap[child]\n            if target == child:\n                # fd is already in place\n                if debug: print(\"%d already in place\" % target, file=errfd)\n                fdesc._unsetCloseOnExec(child)\n            else:\n                if child in fdmap.values():\n                    # we can't replace child-fd yet, as some other mapping\n                    # still needs the fd it wants to target. We must preserve\n                    # that old fd by duping it to a new home.\n                    newtarget = os.dup(child) # give it a safe home\n                    if debug: print(\"os.dup(%d) -> %d\" % (child, newtarget),\n                                    file=errfd)\n                    os.close(child) # close the original\n                    for c, p in items(fdmap):\n                        if p == child:\n                            fdmap[c] = newtarget # update all pointers\n                # now it should be available\n                if debug: print(\"os.dup2(%d,%d)\" % (target, child), file=errfd)\n                os.dup2(target, child)\n\n        # At this point, the child has everything it needs. We want to close\n        # everything that isn't going to be used by the child, i.e.\n        # everything not in fdmap.keys(). The only remaining fds open are\n        # those in fdmap.values().\n\n        # Any given fd may appear in fdmap.values() multiple times, so we\n        # need to remove duplicates first.\n\n        old = []\n        for fd in fdmap.values():\n            if not fd in old:\n                if not fd in fdmap.keys():\n                    old.append(fd)\n        if debug: print(\"old\", old, file=errfd)\n        for fd in old:\n            os.close(fd)\n\n        self._resetSignalDisposition()\n\n\n    def writeToChild(self, childFD, data):\n        self.pipes[childFD].write(data)\n\n\n    def closeChildFD(self, childFD):\n        # for writer pipes, loseConnection tries to write the remaining data\n        # out to the pipe before closing it\n        # if childFD is not in the list of pipes, assume that it is already\n        # closed\n        if childFD in self.pipes:\n            self.pipes[childFD].loseConnection()\n\n\n    def pauseProducing(self):\n        for p in self.pipes.itervalues():\n            if isinstance(p, ProcessReader):\n                p.stopReading()\n\n\n    def resumeProducing(self):\n        for p in self.pipes.itervalues():\n            if isinstance(p, ProcessReader):\n                p.startReading()\n\n    # compatibility\n    def closeStdin(self):\n        \"\"\"\n        Call this to close standard input on this process.\n        \"\"\"\n        self.closeChildFD(0)\n\n\n    def closeStdout(self):\n        self.closeChildFD(1)\n\n\n    def closeStderr(self):\n        self.closeChildFD(2)\n\n\n    def loseConnection(self):\n        self.closeStdin()\n        self.closeStderr()\n        self.closeStdout()\n\n\n    def write(self, data):\n        \"\"\"\n        Call this to write to standard input on this process.\n\n        NOTE: This will silently lose data if there is no standard input.\n        \"\"\"\n        if 0 in self.pipes:\n            self.pipes[0].write(data)\n\n\n    def registerProducer(self, producer, streaming):\n        \"\"\"\n        Call this to register producer for standard input.\n\n        If there is no standard input producer.stopProducing() will\n        be called immediately.\n        \"\"\"\n        if 0 in self.pipes:\n            self.pipes[0].registerProducer(producer, streaming)\n        else:\n            producer.stopProducing()\n\n\n    def unregisterProducer(self):\n        \"\"\"\n        Call this to unregister producer for standard input.\"\"\"\n        if 0 in self.pipes:\n            self.pipes[0].unregisterProducer()\n\n\n    def writeSequence(self, seq):\n        \"\"\"\n        Call this to write to standard input on this process.\n\n        NOTE: This will silently lose data if there is no standard input.\n        \"\"\"\n        if 0 in self.pipes:\n            self.pipes[0].writeSequence(seq)\n\n\n    def childDataReceived(self, name, data):\n        self.proto.childDataReceived(name, data)\n\n\n    def childConnectionLost(self, childFD, reason):\n        # this is called when one of the helpers (ProcessReader or\n        # ProcessWriter) notices their pipe has been closed\n        os.close(self.pipes[childFD].fileno())\n        del self.pipes[childFD]\n        try:\n            self.proto.childConnectionLost(childFD)\n        except:\n            log.err()\n        self.maybeCallProcessEnded()\n\n\n    def maybeCallProcessEnded(self):\n        # we don't call ProcessProtocol.processEnded until:\n        #  the child has terminated, AND\n        #  all writers have indicated an error status, AND\n        #  all readers have indicated EOF\n        # This insures that we've gathered all output from the process.\n        if self.pipes:\n            return\n        if not self.lostProcess:\n            self.reapProcess()\n            return\n        _BaseProcess.maybeCallProcessEnded(self)\n\n\n\n@implementer(IProcessTransport)\nclass PTYProcess(abstract.FileDescriptor, _BaseProcess):\n    \"\"\"\n    An operating-system Process that uses PTY support.\n    \"\"\"\n\n    status = -1\n    pid = None\n\n    def __init__(self, reactor, executable, args, environment, path, proto,\n                 uid=None, gid=None, usePTY=None):\n        \"\"\"\n        Spawn an operating-system process.\n\n        This is where the hard work of disconnecting all currently open\n        files / forking / executing the new process happens.  (This is\n        executed automatically when a Process is instantiated.)\n\n        This will also run the subprocess as a given user ID and group ID, if\n        specified.  (Implementation Note: this doesn't support all the arcane\n        nuances of setXXuid on UNIX: it will assume that either your effective\n        or real UID is 0.)\n        \"\"\"\n        if pty is None and not isinstance(usePTY, (tuple, list)):\n            # no pty module and we didn't get a pty to use\n            raise NotImplementedError(\n                \"cannot use PTYProcess on platforms without the pty module.\")\n        abstract.FileDescriptor.__init__(self, reactor)\n        _BaseProcess.__init__(self, proto)\n\n        if isinstance(usePTY, (tuple, list)):\n            masterfd, slavefd, _ = usePTY\n        else:\n            masterfd, slavefd = pty.openpty()\n\n        try:\n            self._fork(path, uid, gid, executable, args, environment,\n                       masterfd=masterfd, slavefd=slavefd)\n        except:\n            if not isinstance(usePTY, (tuple, list)):\n                os.close(masterfd)\n                os.close(slavefd)\n            raise\n\n        # we are now in parent process:\n        os.close(slavefd)\n        fdesc.setNonBlocking(masterfd)\n        self.fd = masterfd\n        self.startReading()\n        self.connected = 1\n        self.status = -1\n        try:\n            self.proto.makeConnection(self)\n        except:\n            log.err()\n        registerReapProcessHandler(self.pid, self)\n\n\n    def _setupChild(self, masterfd, slavefd):\n        \"\"\"\n        Set up child process after C{fork()} but before C{exec()}.\n\n        This involves:\n\n            - closing C{masterfd}, since it is not used in the subprocess\n\n            - creating a new session with C{os.setsid}\n\n            - changing the controlling terminal of the process (and the new\n              session) to point at C{slavefd}\n\n            - duplicating C{slavefd} to standard input, output, and error\n\n            - closing all other open file descriptors (according to\n              L{_listOpenFDs})\n\n            - re-setting all signal handlers to C{SIG_DFL}\n\n        @param masterfd: The master end of a PTY file descriptors opened with\n            C{openpty}.\n        @type masterfd: L{int}\n\n        @param slavefd: The slave end of a PTY opened with C{openpty}.\n        @type slavefd: L{int}\n        \"\"\"\n        os.close(masterfd)\n        os.setsid()\n        fcntl.ioctl(slavefd, termios.TIOCSCTTY, '')\n\n        for fd in range(3):\n            if fd != slavefd:\n                os.close(fd)\n\n        os.dup2(slavefd, 0) # stdin\n        os.dup2(slavefd, 1) # stdout\n        os.dup2(slavefd, 2) # stderr\n\n        for fd in _listOpenFDs():\n            if fd > 2:\n                try:\n                    os.close(fd)\n                except:\n                    pass\n\n        self._resetSignalDisposition()\n\n\n    def closeStdin(self):\n        # PTYs do not have stdin/stdout/stderr. They only have in and out, just\n        # like sockets. You cannot close one without closing off the entire PTY\n        pass\n\n\n    def closeStdout(self):\n        pass\n\n\n    def closeStderr(self):\n        pass\n\n\n    def doRead(self):\n        \"\"\"\n        Called when my standard output stream is ready for reading.\n        \"\"\"\n        return fdesc.readFromFD(\n            self.fd,\n            lambda data: self.proto.childDataReceived(1, data))\n\n\n    def fileno(self):\n        \"\"\"\n        This returns the file number of standard output on this process.\n        \"\"\"\n        return self.fd\n\n\n    def maybeCallProcessEnded(self):\n        # two things must happen before we call the ProcessProtocol's\n        # processEnded method. 1: the child process must die and be reaped\n        # (which calls our own processEnded method). 2: the child must close\n        # their stdin/stdout/stderr fds, causing the pty to close, causing\n        # our connectionLost method to be called. #2 can also be triggered\n        # by calling .loseConnection().\n        if self.lostProcess == 2:\n            _BaseProcess.maybeCallProcessEnded(self)\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        I call this to clean up when one or all of my connections has died.\n        \"\"\"\n        abstract.FileDescriptor.connectionLost(self, reason)\n        os.close(self.fd)\n        self.lostProcess += 1\n        self.maybeCallProcessEnded()\n\n\n    def writeSomeData(self, data):\n        \"\"\"\n        Write some data to the open process.\n        \"\"\"\n        return fdesc.writeToFD(self.fd, data)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/protocol.py",
    "content": "# -*- test-case-name: twisted.test.test_factories,twisted.internet.test.test_protocol -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nStandard implementations of Twisted protocol-related interfaces.\n\nStart here if you are looking to write a new protocol implementation for\nTwisted.  The Protocol class contains some introductory material.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport random\nfrom zope.interface import implementer\n\nfrom twisted.python import log, failure, components\nfrom twisted.internet import interfaces, error, defer\nfrom twisted.logger import _loggerFor\nfrom twisted.python._oldstyle import _oldStyle\n\n\n@implementer(interfaces.IProtocolFactory, interfaces.ILoggingContext)\n@_oldStyle\nclass Factory:\n    \"\"\"\n    This is a factory which produces protocols.\n\n    By default, buildProtocol will create a protocol of the class given in\n    self.protocol.\n    \"\"\"\n\n    # Put a subclass of Protocol here:\n    protocol = None\n\n    numPorts = 0\n    noisy = True\n\n    @classmethod\n    def forProtocol(cls, protocol, *args, **kwargs):\n        \"\"\"\n        Create a factory for the given protocol.\n\n        It sets the C{protocol} attribute and returns the constructed factory\n        instance.\n\n        @param protocol: A L{Protocol} subclass\n\n        @param args: Positional arguments for the factory.\n\n        @param kwargs: Keyword arguments for the factory.\n\n        @return: A L{Factory} instance wired up to C{protocol}.\n        \"\"\"\n        factory = cls(*args, **kwargs)\n        factory.protocol = protocol\n        return factory\n\n\n    def logPrefix(self):\n        \"\"\"\n        Describe this factory for log messages.\n        \"\"\"\n        return self.__class__.__name__\n\n\n    def doStart(self):\n        \"\"\"\n        Make sure startFactory is called.\n\n        Users should not call this function themselves!\n        \"\"\"\n        if not self.numPorts:\n            if self.noisy:\n                _loggerFor(self).info(\"Starting factory {factory!r}\",\n                                      factory=self)\n            self.startFactory()\n        self.numPorts = self.numPorts + 1\n\n\n    def doStop(self):\n        \"\"\"\n        Make sure stopFactory is called.\n\n        Users should not call this function themselves!\n        \"\"\"\n        if self.numPorts == 0:\n            # This shouldn't happen, but does sometimes and this is better\n            # than blowing up in assert as we did previously.\n            return\n        self.numPorts = self.numPorts - 1\n        if not self.numPorts:\n            if self.noisy:\n                _loggerFor(self).info(\"Stopping factory {factory!r}\",\n                                      factory=self)\n            self.stopFactory()\n\n\n    def startFactory(self):\n        \"\"\"\n        This will be called before I begin listening on a Port or Connector.\n\n        It will only be called once, even if the factory is connected\n        to multiple ports.\n\n        This can be used to perform 'unserialization' tasks that\n        are best put off until things are actually running, such\n        as connecting to a database, opening files, etcetera.\n        \"\"\"\n\n\n    def stopFactory(self):\n        \"\"\"\n        This will be called before I stop listening on all Ports/Connectors.\n\n        This can be overridden to perform 'shutdown' tasks such as disconnecting\n        database connections, closing files, etc.\n\n        It will be called, for example, before an application shuts down,\n        if it was connected to a port. User code should not call this function\n        directly.\n        \"\"\"\n\n\n    def buildProtocol(self, addr):\n        \"\"\"\n        Create an instance of a subclass of Protocol.\n\n        The returned instance will handle input on an incoming server\n        connection, and an attribute \"factory\" pointing to the creating\n        factory.\n\n        Alternatively, L{None} may be returned to immediately close the\n        new connection.\n\n        Override this method to alter how Protocol instances get created.\n\n        @param addr: an object implementing L{twisted.internet.interfaces.IAddress}\n        \"\"\"\n        p = self.protocol()\n        p.factory = self\n        return p\n\n\n\nclass ClientFactory(Factory):\n    \"\"\"\n    A Protocol factory for clients.\n\n    This can be used together with the various connectXXX methods in\n    reactors.\n    \"\"\"\n\n    def startedConnecting(self, connector):\n        \"\"\"\n        Called when a connection has been started.\n\n        You can call connector.stopConnecting() to stop the connection attempt.\n\n        @param connector: a Connector object.\n        \"\"\"\n\n\n    def clientConnectionFailed(self, connector, reason):\n        \"\"\"\n        Called when a connection has failed to connect.\n\n        It may be useful to call connector.connect() - this will reconnect.\n\n        @type reason: L{twisted.python.failure.Failure}\n        \"\"\"\n\n\n    def clientConnectionLost(self, connector, reason):\n        \"\"\"\n        Called when an established connection is lost.\n\n        It may be useful to call connector.connect() - this will reconnect.\n\n        @type reason: L{twisted.python.failure.Failure}\n        \"\"\"\n\n\n\nclass _InstanceFactory(ClientFactory):\n    \"\"\"\n    Factory used by ClientCreator.\n\n    @ivar deferred: The L{Deferred} which represents this connection attempt and\n        which will be fired when it succeeds or fails.\n\n    @ivar pending: After a connection attempt succeeds or fails, a delayed call\n        which will fire the L{Deferred} representing this connection attempt.\n    \"\"\"\n\n    noisy = False\n    pending = None\n\n    def __init__(self, reactor, instance, deferred):\n        self.reactor = reactor\n        self.instance = instance\n        self.deferred = deferred\n\n\n    def __repr__(self):\n        return \"<ClientCreator factory: %r>\" % (self.instance, )\n\n\n    def buildProtocol(self, addr):\n        \"\"\"\n        Return the pre-constructed protocol instance and arrange to fire the\n        waiting L{Deferred} to indicate success establishing the connection.\n        \"\"\"\n        self.pending = self.reactor.callLater(\n            0, self.fire, self.deferred.callback, self.instance)\n        self.deferred = None\n        return self.instance\n\n\n    def clientConnectionFailed(self, connector, reason):\n        \"\"\"\n        Arrange to fire the waiting L{Deferred} with the given failure to\n        indicate the connection could not be established.\n        \"\"\"\n        self.pending = self.reactor.callLater(\n            0, self.fire, self.deferred.errback, reason)\n        self.deferred = None\n\n\n    def fire(self, func, value):\n        \"\"\"\n        Clear C{self.pending} to avoid a reference cycle and then invoke func\n        with the value.\n        \"\"\"\n        self.pending = None\n        func(value)\n\n\n\n@_oldStyle\nclass ClientCreator:\n    \"\"\"\n    Client connections that do not require a factory.\n\n    The various connect* methods create a protocol instance using the given\n    protocol class and arguments, and connect it, returning a Deferred of the\n    resulting protocol instance.\n\n    Useful for cases when we don't really need a factory.  Mainly this\n    is when there is no shared state between protocol instances, and no need\n    to reconnect.\n\n    The C{connectTCP}, C{connectUNIX}, and C{connectSSL} methods each return a\n    L{Deferred} which will fire with an instance of the protocol class passed to\n    L{ClientCreator.__init__}.  These Deferred can be cancelled to abort the\n    connection attempt (in a very unlikely case, cancelling the Deferred may not\n    prevent the protocol from being instantiated and connected to a transport;\n    if this happens, it will be disconnected immediately afterwards and the\n    Deferred will still errback with L{CancelledError}).\n    \"\"\"\n\n    def __init__(self, reactor, protocolClass, *args, **kwargs):\n        self.reactor = reactor\n        self.protocolClass = protocolClass\n        self.args = args\n        self.kwargs = kwargs\n\n\n    def _connect(self, method, *args, **kwargs):\n        \"\"\"\n        Initiate a connection attempt.\n\n        @param method: A callable which will actually start the connection\n            attempt.  For example, C{reactor.connectTCP}.\n\n        @param *args: Positional arguments to pass to C{method}, excluding the\n            factory.\n\n        @param **kwargs: Keyword arguments to pass to C{method}.\n\n        @return: A L{Deferred} which fires with an instance of the protocol\n            class passed to this L{ClientCreator}'s initializer or fails if the\n            connection cannot be set up for some reason.\n        \"\"\"\n        def cancelConnect(deferred):\n            connector.disconnect()\n            if f.pending is not None:\n                f.pending.cancel()\n        d = defer.Deferred(cancelConnect)\n        f = _InstanceFactory(\n            self.reactor, self.protocolClass(*self.args, **self.kwargs), d)\n        connector = method(factory=f, *args, **kwargs)\n        return d\n\n\n    def connectTCP(self, host, port, timeout=30, bindAddress=None):\n        \"\"\"\n        Connect to a TCP server.\n\n        The parameters are all the same as to L{IReactorTCP.connectTCP} except\n        that the factory parameter is omitted.\n\n        @return: A L{Deferred} which fires with an instance of the protocol\n            class passed to this L{ClientCreator}'s initializer or fails if the\n            connection cannot be set up for some reason.\n        \"\"\"\n        return self._connect(\n            self.reactor.connectTCP, host, port, timeout=timeout,\n            bindAddress=bindAddress)\n\n\n    def connectUNIX(self, address, timeout=30, checkPID=False):\n        \"\"\"\n        Connect to a Unix socket.\n\n        The parameters are all the same as to L{IReactorUNIX.connectUNIX} except\n        that the factory parameter is omitted.\n\n        @return: A L{Deferred} which fires with an instance of the protocol\n            class passed to this L{ClientCreator}'s initializer or fails if the\n            connection cannot be set up for some reason.\n        \"\"\"\n        return self._connect(\n            self.reactor.connectUNIX, address, timeout=timeout,\n            checkPID=checkPID)\n\n\n    def connectSSL(self, host, port, contextFactory, timeout=30, bindAddress=None):\n        \"\"\"\n        Connect to an SSL server.\n\n        The parameters are all the same as to L{IReactorSSL.connectSSL} except\n        that the factory parameter is omitted.\n\n        @return: A L{Deferred} which fires with an instance of the protocol\n            class passed to this L{ClientCreator}'s initializer or fails if the\n            connection cannot be set up for some reason.\n        \"\"\"\n        return self._connect(\n            self.reactor.connectSSL, host, port,\n            contextFactory=contextFactory, timeout=timeout,\n            bindAddress=bindAddress)\n\n\n\nclass ReconnectingClientFactory(ClientFactory):\n    \"\"\"\n    Factory which auto-reconnects clients with an exponential back-off.\n\n    Note that clients should call my resetDelay method after they have\n    connected successfully.\n\n    @ivar maxDelay: Maximum number of seconds between connection attempts.\n    @ivar initialDelay: Delay for the first reconnection attempt.\n    @ivar factor: A multiplicitive factor by which the delay grows\n    @ivar jitter: Percentage of randomness to introduce into the delay length\n        to prevent stampeding.\n    @ivar clock: The clock used to schedule reconnection. It's mainly useful to\n        be parametrized in tests. If the factory is serialized, this attribute\n        will not be serialized, and the default value (the reactor) will be\n        restored when deserialized.\n    @type clock: L{IReactorTime}\n    @ivar maxRetries: Maximum number of consecutive unsuccessful connection\n        attempts, after which no further connection attempts will be made. If\n        this is not explicitly set, no maximum is applied.\n    \"\"\"\n    maxDelay = 3600\n    initialDelay = 1.0\n    # Note: These highly sensitive factors have been precisely measured by\n    # the National Institute of Science and Technology.  Take extreme care\n    # in altering them, or you may damage your Internet!\n    # (Seriously: <http://physics.nist.gov/cuu/Constants/index.html>)\n    factor = 2.7182818284590451 # (math.e)\n    # Phi = 1.6180339887498948 # (Phi is acceptable for use as a\n    # factor if e is too large for your application.)\n\n    # This is the value of the molar Planck constant times c, joule\n    # meter/mole.  The value is attributable to\n    # https://physics.nist.gov/cgi-bin/cuu/Value?nahc|search_for=molar+planck+constant+times+c\n    jitter = 0.119626565582\n\n    delay = initialDelay\n    retries = 0\n    maxRetries = None\n    _callID = None\n    connector = None\n    clock = None\n\n    continueTrying = 1\n\n\n    def clientConnectionFailed(self, connector, reason):\n        if self.continueTrying:\n            self.connector = connector\n            self.retry()\n\n\n    def clientConnectionLost(self, connector, unused_reason):\n        if self.continueTrying:\n            self.connector = connector\n            self.retry()\n\n\n    def retry(self, connector=None):\n        \"\"\"\n        Have this connector connect again, after a suitable delay.\n        \"\"\"\n        if not self.continueTrying:\n            if self.noisy:\n                log.msg(\"Abandoning %s on explicit request\" % (connector,))\n            return\n\n        if connector is None:\n            if self.connector is None:\n                raise ValueError(\"no connector to retry\")\n            else:\n                connector = self.connector\n\n        self.retries += 1\n        if self.maxRetries is not None and (self.retries > self.maxRetries):\n            if self.noisy:\n                log.msg(\"Abandoning %s after %d retries.\" %\n                        (connector, self.retries))\n            return\n\n        self.delay = min(self.delay * self.factor, self.maxDelay)\n        if self.jitter:\n            self.delay = random.normalvariate(self.delay,\n                                              self.delay * self.jitter)\n\n        if self.noisy:\n            log.msg(\"%s will retry in %d seconds\" % (connector, self.delay,))\n\n        def reconnector():\n            self._callID = None\n            connector.connect()\n        if self.clock is None:\n            from twisted.internet import reactor\n            self.clock = reactor\n        self._callID = self.clock.callLater(self.delay, reconnector)\n\n\n    def stopTrying(self):\n        \"\"\"\n        Put a stop to any attempt to reconnect in progress.\n        \"\"\"\n        # ??? Is this function really stopFactory?\n        if self._callID:\n            self._callID.cancel()\n            self._callID = None\n        self.continueTrying = 0\n        if self.connector:\n            try:\n                self.connector.stopConnecting()\n            except error.NotConnectingError:\n                pass\n\n\n    def resetDelay(self):\n        \"\"\"\n        Call this method after a successful connection: it resets the delay and\n        the retry counter.\n        \"\"\"\n        self.delay = self.initialDelay\n        self.retries = 0\n        self._callID = None\n        self.continueTrying = 1\n\n\n    def __getstate__(self):\n        \"\"\"\n        Remove all of the state which is mutated by connection attempts and\n        failures, returning just the state which describes how reconnections\n        should be attempted.  This will make the unserialized instance\n        behave just as this one did when it was first instantiated.\n        \"\"\"\n        state = self.__dict__.copy()\n        for key in ['connector', 'retries', 'delay',\n                    'continueTrying', '_callID', 'clock']:\n            if key in state:\n                del state[key]\n        return state\n\n\n\nclass ServerFactory(Factory):\n    \"\"\"\n    Subclass this to indicate that your protocol.Factory is only usable for servers.\n    \"\"\"\n\n\n\n@_oldStyle\nclass BaseProtocol:\n    \"\"\"\n    This is the abstract superclass of all protocols.\n\n    Some methods have helpful default implementations here so that they can\n    easily be shared, but otherwise the direct subclasses of this class are more\n    interesting, L{Protocol} and L{ProcessProtocol}.\n    \"\"\"\n    connected = 0\n    transport = None\n\n    def makeConnection(self, transport):\n        \"\"\"\n        Make a connection to a transport and a server.\n\n        This sets the 'transport' attribute of this Protocol, and calls the\n        connectionMade() callback.\n        \"\"\"\n        self.connected = 1\n        self.transport = transport\n        self.connectionMade()\n\n\n    def connectionMade(self):\n        \"\"\"\n        Called when a connection is made.\n\n        This may be considered the initializer of the protocol, because\n        it is called when the connection is completed.  For clients,\n        this is called once the connection to the server has been\n        established; for servers, this is called after an accept() call\n        stops blocking and a socket has been received.  If you need to\n        send any greeting or initial message, do it here.\n        \"\"\"\n\nconnectionDone = failure.Failure(error.ConnectionDone())\nconnectionDone.cleanFailure()\n\n\n@implementer(interfaces.IProtocol, interfaces.ILoggingContext)\nclass Protocol(BaseProtocol):\n    \"\"\"\n    This is the base class for streaming connection-oriented protocols.\n\n    If you are going to write a new connection-oriented protocol for Twisted,\n    start here.  Any protocol implementation, either client or server, should\n    be a subclass of this class.\n\n    The API is quite simple.  Implement L{dataReceived} to handle both\n    event-based and synchronous input; output can be sent through the\n    'transport' attribute, which is to be an instance that implements\n    L{twisted.internet.interfaces.ITransport}.  Override C{connectionLost} to be\n    notified when the connection ends.\n\n    Some subclasses exist already to help you write common types of protocols:\n    see the L{twisted.protocols.basic} module for a few of them.\n    \"\"\"\n\n    def logPrefix(self):\n        \"\"\"\n        Return a prefix matching the class name, to identify log messages\n        related to this protocol instance.\n        \"\"\"\n        return self.__class__.__name__\n\n\n    def dataReceived(self, data):\n        \"\"\"\n        Called whenever data is received.\n\n        Use this method to translate to a higher-level message.  Usually, some\n        callback will be made upon the receipt of each complete protocol\n        message.\n\n        @param data: a string of indeterminate length.  Please keep in mind\n            that you will probably need to buffer some data, as partial\n            (or multiple) protocol messages may be received!  I recommend\n            that unit tests for protocols call through to this method with\n            differing chunk sizes, down to one byte at a time.\n        \"\"\"\n\n    def connectionLost(self, reason=connectionDone):\n        \"\"\"\n        Called when the connection is shut down.\n\n        Clear any circular references here, and any external references\n        to this Protocol.  The connection has been closed.\n\n        @type reason: L{twisted.python.failure.Failure}\n        \"\"\"\n\n\n\n@implementer(interfaces.IConsumer)\nclass ProtocolToConsumerAdapter(components.Adapter):\n\n    def write(self, data):\n        self.original.dataReceived(data)\n\n\n    def registerProducer(self, producer, streaming):\n        pass\n\n\n    def unregisterProducer(self):\n        pass\n\n\ncomponents.registerAdapter(ProtocolToConsumerAdapter, interfaces.IProtocol,\n                           interfaces.IConsumer)\n\n\n\n@implementer(interfaces.IProtocol)\nclass ConsumerToProtocolAdapter(components.Adapter):\n\n    def dataReceived(self, data):\n        self.original.write(data)\n\n\n    def connectionLost(self, reason):\n        pass\n\n\n    def makeConnection(self, transport):\n        pass\n\n\n    def connectionMade(self):\n        pass\n\n\ncomponents.registerAdapter(ConsumerToProtocolAdapter, interfaces.IConsumer,\n                           interfaces.IProtocol)\n\n\n\n@implementer(interfaces.IProcessProtocol)\nclass ProcessProtocol(BaseProtocol):\n    \"\"\"\n    Base process protocol implementation which does simple dispatching for\n    stdin, stdout, and stderr file descriptors.\n    \"\"\"\n\n    def childDataReceived(self, childFD, data):\n        if childFD == 1:\n            self.outReceived(data)\n        elif childFD == 2:\n            self.errReceived(data)\n\n\n    def outReceived(self, data):\n        \"\"\"\n        Some data was received from stdout.\n        \"\"\"\n\n\n    def errReceived(self, data):\n        \"\"\"\n        Some data was received from stderr.\n        \"\"\"\n\n\n    def childConnectionLost(self, childFD):\n        if childFD == 0:\n            self.inConnectionLost()\n        elif childFD == 1:\n            self.outConnectionLost()\n        elif childFD == 2:\n            self.errConnectionLost()\n\n\n    def inConnectionLost(self):\n        \"\"\"\n        This will be called when stdin is closed.\n        \"\"\"\n\n\n    def outConnectionLost(self):\n        \"\"\"\n        This will be called when stdout is closed.\n        \"\"\"\n\n\n    def errConnectionLost(self):\n        \"\"\"\n        This will be called when stderr is closed.\n        \"\"\"\n\n\n    def processExited(self, reason):\n        \"\"\"\n        This will be called when the subprocess exits.\n\n        @type reason: L{twisted.python.failure.Failure}\n        \"\"\"\n\n\n    def processEnded(self, reason):\n        \"\"\"\n        Called when the child process exits and all file descriptors\n        associated with it have been closed.\n\n        @type reason: L{twisted.python.failure.Failure}\n        \"\"\"\n\n\n\n@_oldStyle\nclass AbstractDatagramProtocol:\n    \"\"\"\n    Abstract protocol for datagram-oriented transports, e.g. IP, ICMP, ARP, UDP.\n    \"\"\"\n\n    transport = None\n    numPorts = 0\n    noisy = True\n\n    def __getstate__(self):\n        d = self.__dict__.copy()\n        d['transport'] = None\n        return d\n\n\n    def doStart(self):\n        \"\"\"\n        Make sure startProtocol is called.\n\n        This will be called by makeConnection(), users should not call it.\n        \"\"\"\n        if not self.numPorts:\n            if self.noisy:\n                log.msg(\"Starting protocol %s\" % self)\n            self.startProtocol()\n        self.numPorts = self.numPorts + 1\n\n\n    def doStop(self):\n        \"\"\"\n        Make sure stopProtocol is called.\n\n        This will be called by the port, users should not call it.\n        \"\"\"\n        assert self.numPorts > 0\n        self.numPorts = self.numPorts - 1\n        self.transport = None\n        if not self.numPorts:\n            if self.noisy:\n                log.msg(\"Stopping protocol %s\" % self)\n            self.stopProtocol()\n\n\n    def startProtocol(self):\n        \"\"\"\n        Called when a transport is connected to this protocol.\n\n        Will only be called once, even if multiple ports are connected.\n        \"\"\"\n\n\n    def stopProtocol(self):\n        \"\"\"\n        Called when the transport is disconnected.\n\n        Will only be called once, after all ports are disconnected.\n        \"\"\"\n\n\n    def makeConnection(self, transport):\n        \"\"\"\n        Make a connection to a transport and a server.\n\n        This sets the 'transport' attribute of this DatagramProtocol, and calls the\n        doStart() callback.\n        \"\"\"\n        assert self.transport == None\n        self.transport = transport\n        self.doStart()\n\n\n    def datagramReceived(self, datagram, addr):\n        \"\"\"\n        Called when a datagram is received.\n\n        @param datagram: the string received from the transport.\n        @param addr: tuple of source of datagram.\n        \"\"\"\n\n\n\n@implementer(interfaces.ILoggingContext)\nclass DatagramProtocol(AbstractDatagramProtocol):\n    \"\"\"\n    Protocol for datagram-oriented transport, e.g. UDP.\n\n    @type transport: L{None} or\n        L{IUDPTransport<twisted.internet.interfaces.IUDPTransport>} provider\n    @ivar transport: The transport with which this protocol is associated,\n        if it is associated with one.\n    \"\"\"\n\n    def logPrefix(self):\n        \"\"\"\n        Return a prefix matching the class name, to identify log messages\n        related to this protocol instance.\n        \"\"\"\n        return self.__class__.__name__\n\n\n    def connectionRefused(self):\n        \"\"\"\n        Called due to error from write in connected mode.\n\n        Note this is a result of ICMP message generated by *previous*\n        write.\n        \"\"\"\n\n\n\nclass ConnectedDatagramProtocol(DatagramProtocol):\n    \"\"\"\n    Protocol for connected datagram-oriented transport.\n\n    No longer necessary for UDP.\n    \"\"\"\n\n    def datagramReceived(self, datagram):\n        \"\"\"\n        Called when a datagram is received.\n\n        @param datagram: the string received from the transport.\n        \"\"\"\n\n    def connectionFailed(self, failure):\n        \"\"\"\n        Called if connecting failed.\n\n        Usually this will be due to a DNS lookup failure.\n        \"\"\"\n\n\n\n@implementer(interfaces.ITransport)\n@_oldStyle\nclass FileWrapper:\n    \"\"\"\n    A wrapper around a file-like object to make it behave as a Transport.\n\n    This doesn't actually stream the file to the attached protocol,\n    and is thus useful mainly as a utility for debugging protocols.\n    \"\"\"\n\n    closed = 0\n    disconnecting = 0\n    producer = None\n    streamingProducer = 0\n\n    def __init__(self, file):\n        self.file = file\n\n\n    def write(self, data):\n        try:\n            self.file.write(data)\n        except:\n            self.handleException()\n\n\n    def _checkProducer(self):\n        # Cheating; this is called at \"idle\" times to allow producers to be\n        # found and dealt with\n        if self.producer:\n            self.producer.resumeProducing()\n\n\n    def registerProducer(self, producer, streaming):\n        \"\"\"\n        From abstract.FileDescriptor\n        \"\"\"\n        self.producer = producer\n        self.streamingProducer = streaming\n        if not streaming:\n            producer.resumeProducing()\n\n\n    def unregisterProducer(self):\n        self.producer = None\n\n\n    def stopConsuming(self):\n        self.unregisterProducer()\n        self.loseConnection()\n\n\n    def writeSequence(self, iovec):\n        self.write(b\"\".join(iovec))\n\n\n    def loseConnection(self):\n        self.closed = 1\n        try:\n            self.file.close()\n        except (IOError, OSError):\n            self.handleException()\n\n\n    def getPeer(self):\n        # FIXME: https://twistedmatrix.com/trac/ticket/7820\n        # According to ITransport, this should return an IAddress!\n        return 'file', 'file'\n\n\n    def getHost(self):\n        # FIXME: https://twistedmatrix.com/trac/ticket/7820\n        # According to ITransport, this should return an IAddress!\n        return 'file'\n\n\n    def handleException(self):\n        pass\n\n\n    def resumeProducing(self):\n        # Never sends data anyways\n        pass\n\n\n    def pauseProducing(self):\n        # Never sends data anyways\n        pass\n\n\n    def stopProducing(self):\n        self.loseConnection()\n\n\n__all__ = [\"Factory\", \"ClientFactory\", \"ReconnectingClientFactory\", \"connectionDone\",\n           \"Protocol\", \"ProcessProtocol\", \"FileWrapper\", \"ServerFactory\",\n           \"AbstractDatagramProtocol\", \"DatagramProtocol\", \"ConnectedDatagramProtocol\",\n           \"ClientCreator\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/pyuisupport.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nThis module integrates PyUI with twisted.internet's mainloop.\n\nMaintainer: Jp Calderone\n\nSee doc/examples/pyuidemo.py for example usage.\n\"\"\"\n\n# System imports\nimport pyui\n\ndef _guiUpdate(reactor, delay):\n    pyui.draw()\n    if pyui.update() == 0:\n        pyui.quit()\n        reactor.stop()\n    else:\n        reactor.callLater(delay, _guiUpdate, reactor, delay)\n\n\ndef install(ms=10, reactor=None, args=(), kw={}):\n    \"\"\"\n    Schedule PyUI's display to be updated approximately every C{ms}\n    milliseconds, and initialize PyUI with the specified arguments.\n    \"\"\"\n    d = pyui.init(*args, **kw)\n\n    if reactor is None:\n        from twisted.internet import reactor\n    _guiUpdate(reactor, ms / 1000.0)\n    return d\n\n__all__ = [\"install\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/reactor.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThe reactor is the Twisted event loop within Twisted, the loop which drives\napplications using Twisted. The reactor provides APIs for networking,\nthreading, dispatching events, and more.\n\nThe default reactor depends on the platform and will be installed if this\nmodule is imported without another reactor being explicitly installed\nbeforehand. Regardless of which reactor is installed, importing this module is\nthe correct way to get a reference to it.\n\nNew application code should prefer to pass and accept the reactor as a\nparameter where it is needed, rather than relying on being able to import this\nmodule to get a reference.  This simplifies unit testing and may make it easier\nto one day support multiple reactors (as a performance enhancement), though\nthis is not currently possible.\n\n@see: L{IReactorCore<twisted.internet.interfaces.IReactorCore>}\n@see: L{IReactorTime<twisted.internet.interfaces.IReactorTime>}\n@see: L{IReactorProcess<twisted.internet.interfaces.IReactorProcess>}\n@see: L{IReactorTCP<twisted.internet.interfaces.IReactorTCP>}\n@see: L{IReactorSSL<twisted.internet.interfaces.IReactorSSL>}\n@see: L{IReactorUDP<twisted.internet.interfaces.IReactorUDP>}\n@see: L{IReactorMulticast<twisted.internet.interfaces.IReactorMulticast>}\n@see: L{IReactorUNIX<twisted.internet.interfaces.IReactorUNIX>}\n@see: L{IReactorUNIXDatagram<twisted.internet.interfaces.IReactorUNIXDatagram>}\n@see: L{IReactorFDSet<twisted.internet.interfaces.IReactorFDSet>}\n@see: L{IReactorThreads<twisted.internet.interfaces.IReactorThreads>}\n@see: L{IReactorPluggableResolver<twisted.internet.interfaces.IReactorPluggableResolver>}\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport sys\ndel sys.modules['twisted.internet.reactor']\nfrom twisted.internet import default\ndefault.install()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/selectreactor.py",
    "content": "# -*- test-case-name: twisted.test.test_internet -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nSelect reactor\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom time import sleep\nimport sys, select, socket\nfrom errno import EINTR, EBADF\n\nfrom zope.interface import implementer\n\nfrom twisted.internet.interfaces import IReactorFDSet\nfrom twisted.internet import posixbase\nfrom twisted.python import log\nfrom twisted.python.runtime import platformType\n\n\ndef win32select(r, w, e, timeout=None):\n    \"\"\"Win32 select wrapper.\"\"\"\n    if not (r or w):\n        # windows select() exits immediately when no sockets\n        if timeout is None:\n            timeout = 0.01\n        else:\n            timeout = min(timeout, 0.001)\n        sleep(timeout)\n        return [], [], []\n    # windows doesn't process 'signals' inside select(), so we set a max\n    # time or ctrl-c will never be recognized\n    if timeout is None or timeout > 0.5:\n        timeout = 0.5\n    r, w, e = select.select(r, w, w, timeout)\n    return r, w + e, []\n\nif platformType == \"win32\":\n    _select = win32select\nelse:\n    _select = select.select\n\n\ntry:\n    from twisted.internet.win32eventreactor import _ThreadedWin32EventsMixin\nexcept ImportError:\n    _extraBase = object\nelse:\n    _extraBase = _ThreadedWin32EventsMixin\n\n\n@implementer(IReactorFDSet)\nclass SelectReactor(posixbase.PosixReactorBase, _extraBase):\n    \"\"\"\n    A select() based reactor - runs on all POSIX platforms and on Win32.\n\n    @ivar _reads: A set containing L{FileDescriptor} instances which will be\n        checked for read events.\n\n    @ivar _writes: A set containing L{FileDescriptor} instances which will be\n        checked for writability.\n    \"\"\"\n\n    def __init__(self):\n        \"\"\"\n        Initialize file descriptor tracking dictionaries and the base class.\n        \"\"\"\n        self._reads = set()\n        self._writes = set()\n        posixbase.PosixReactorBase.__init__(self)\n\n\n    def _preenDescriptors(self):\n        log.msg(\"Malformed file descriptor found.  Preening lists.\")\n        readers = list(self._reads)\n        writers = list(self._writes)\n        self._reads.clear()\n        self._writes.clear()\n        for selSet, selList in ((self._reads, readers),\n                                 (self._writes, writers)):\n            for selectable in selList:\n                try:\n                    select.select([selectable], [selectable], [selectable], 0)\n                except Exception as e:\n                    log.msg(\"bad descriptor %s\" % selectable)\n                    self._disconnectSelectable(selectable, e, False)\n                else:\n                    selSet.add(selectable)\n\n\n    def doSelect(self, timeout):\n        \"\"\"\n        Run one iteration of the I/O monitor loop.\n\n        This will run all selectables who had input or output readiness\n        waiting for them.\n        \"\"\"\n        try:\n            r, w, ignored = _select(self._reads,\n                                    self._writes,\n                                    [], timeout)\n        except ValueError:\n            # Possibly a file descriptor has gone negative?\n            self._preenDescriptors()\n            return\n        except TypeError:\n            # Something *totally* invalid (object w/o fileno, non-integral\n            # result) was passed\n            log.err()\n            self._preenDescriptors()\n            return\n        except (select.error, socket.error, IOError) as se:\n            # select(2) encountered an error, perhaps while calling the fileno()\n            # method of a socket.  (Python 2.6 socket.error is an IOError\n            # subclass, but on Python 2.5 and earlier it is not.)\n            if se.args[0] in (0, 2):\n                # windows does this if it got an empty list\n                if (not self._reads) and (not self._writes):\n                    return\n                else:\n                    raise\n            elif se.args[0] == EINTR:\n                return\n            elif se.args[0] == EBADF:\n                self._preenDescriptors()\n                return\n            else:\n                # OK, I really don't know what's going on.  Blow up.\n                raise\n\n        _drdw = self._doReadOrWrite\n        _logrun = log.callWithLogger\n        for selectables, method, fdset in ((r, \"doRead\", self._reads),\n                                           (w,\"doWrite\", self._writes)):\n            for selectable in selectables:\n                # if this was disconnected in another thread, kill it.\n                # ^^^^ --- what the !@#*?  serious!  -exarkun\n                if selectable not in fdset:\n                    continue\n                # This for pausing input when we're not ready for more.\n                _logrun(selectable, _drdw, selectable, method)\n\n    doIteration = doSelect\n\n    def _doReadOrWrite(self, selectable, method):\n        try:\n            why = getattr(selectable, method)()\n        except:\n            why = sys.exc_info()[1]\n            log.err()\n        if why:\n            self._disconnectSelectable(selectable, why, method==\"doRead\")\n\n    def addReader(self, reader):\n        \"\"\"\n        Add a FileDescriptor for notification of data available to read.\n        \"\"\"\n        self._reads.add(reader)\n\n    def addWriter(self, writer):\n        \"\"\"\n        Add a FileDescriptor for notification of data available to write.\n        \"\"\"\n        self._writes.add(writer)\n\n    def removeReader(self, reader):\n        \"\"\"\n        Remove a Selectable for notification of data available to read.\n        \"\"\"\n        self._reads.discard(reader)\n\n    def removeWriter(self, writer):\n        \"\"\"\n        Remove a Selectable for notification of data available to write.\n        \"\"\"\n        self._writes.discard(writer)\n\n    def removeAll(self):\n        return self._removeAll(self._reads, self._writes)\n\n\n    def getReaders(self):\n        return list(self._reads)\n\n\n    def getWriters(self):\n        return list(self._writes)\n\n\n\ndef install():\n    \"\"\"Configure the twisted mainloop to be run using the select() reactor.\n    \"\"\"\n    reactor = SelectReactor()\n    from twisted.internet.main import installReactor\n    installReactor(reactor)\n\n__all__ = ['install']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/serialport.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nSerial Port Protocol\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n# http://twistedmatrix.com/trac/ticket/3725#comment:24\n# Apparently applications use these names even though they should\n# be imported from pyserial\n__all__ = [\"serial\", \"PARITY_ODD\", \"PARITY_EVEN\", \"PARITY_NONE\",\n           \"STOPBITS_TWO\", \"STOPBITS_ONE\", \"FIVEBITS\",\n           \"EIGHTBITS\", \"SEVENBITS\", \"SIXBITS\",\n# Name this module is actually trying to export\n           \"SerialPort\"]\n\n# all of them require pyserial at the moment, so check that first\nimport serial\nfrom serial import PARITY_NONE, PARITY_EVEN, PARITY_ODD\nfrom serial import STOPBITS_ONE, STOPBITS_TWO\nfrom serial import FIVEBITS, SIXBITS, SEVENBITS, EIGHTBITS\n\nfrom twisted.python._oldstyle import _oldStyle\nfrom twisted.python.runtime import platform\n\n\n\n@_oldStyle\nclass BaseSerialPort:\n    \"\"\"\n    Base class for Windows and POSIX serial ports.\n\n    @ivar _serialFactory: a pyserial C{serial.Serial} factory, used to create\n        the instance stored in C{self._serial}. Overrideable to enable easier\n        testing.\n\n    @ivar _serial: a pyserial C{serial.Serial} instance used to manage the\n        options on the serial port.\n    \"\"\"\n\n    _serialFactory = serial.Serial\n\n\n    def setBaudRate(self, baudrate):\n        if hasattr(self._serial, \"setBaudrate\"):\n            self._serial.setBaudrate(baudrate)\n        else:\n            self._serial.setBaudRate(baudrate)\n\n    def inWaiting(self):\n        return self._serial.inWaiting()\n\n    def flushInput(self):\n        self._serial.flushInput()\n\n    def flushOutput(self):\n        self._serial.flushOutput()\n\n    def sendBreak(self):\n        self._serial.sendBreak()\n\n    def getDSR(self):\n        return self._serial.getDSR()\n\n    def getCD(self):\n        return self._serial.getCD()\n\n    def getRI(self):\n        return self._serial.getRI()\n\n    def getCTS(self):\n        return self._serial.getCTS()\n\n    def setDTR(self, on = 1):\n        self._serial.setDTR(on)\n\n    def setRTS(self, on = 1):\n        self._serial.setRTS(on)\n\n\n\n# Expert appropriate implementation of SerialPort.\nif platform.isWindows():\n    from twisted.internet._win32serialport import SerialPort\nelse:\n    from twisted.internet._posixserialport import SerialPort\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/ssl.py",
    "content": "# -*- test-case-name: twisted.test.test_ssl -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module implements Transport Layer Security (TLS) support for Twisted.  It\nrequires U{PyOpenSSL <https://pypi.python.org/pypi/pyOpenSSL>}.\n\nIf you wish to establish a TLS connection, please use one of the following\nAPIs:\n\n    - SSL endpoints for L{servers\n      <twisted.internet.endpoints.SSL4ServerEndpoint>} and L{clients\n      <twisted.internet.endpoints.SSL4ClientEndpoint>}\n\n    - L{startTLS <twisted.internet.interfaces.ITLSTransport.startTLS>}\n\n    - L{connectSSL <twisted.internet.interfaces.IReactorSSL.connectSSL>}\n\n    - L{listenSSL <twisted.internet.interfaces.IReactorSSL.listenSSL>}\n\nThese APIs all require a C{contextFactory} argument that specifies their\nsecurity properties, such as certificate, private key, certificate authorities\nto verify the peer, allowed TLS protocol versions, cipher suites, and so on.\nThe recommended value for this argument is a L{CertificateOptions} instance;\nsee its documentation for an explanation of the available options.\n\nThe C{contextFactory} name is a bit of an anachronism now, as context factories\nhave been replaced with \"connection creators\", but these objects serve the same\nrole.\n\nBe warned that implementing your own connection creator (i.e.: value for the\nC{contextFactory}) is both difficult and dangerous; the Twisted team has worked\nhard to make L{CertificateOptions}' API comprehensible and unsurprising, and\nthe Twisted team is actively maintaining it to ensure that it becomes more\nsecure over time.\n\nIf you are really absolutely sure that you want to take on the risk of\nimplementing your own connection creator based on the pyOpenSSL API, see the\nL{server connection creator\n<twisted.internet.interfaces.IOpenSSLServerConnectionCreator>} and L{client\nconnection creator\n<twisted.internet.interfaces.IOpenSSLServerConnectionCreator>} interfaces.\n\nDevelopers using Twisted, please ignore the L{Port}, L{Connector}, and\nL{Client} classes defined here, as these are details of certain reactors' TLS\nimplementations, exposed by accident (and remaining here only for compatibility\nreasons).  If you wish to establish a TLS connection, please use one of the\nAPIs listed above.\n\n@note: \"SSL\" (Secure Sockets Layer) is an antiquated synonym for \"TLS\"\n    (Transport Layer Security).  You may see these terms used interchangeably\n    throughout the documentation.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n# System imports\nfrom OpenSSL import SSL\nsupported = True\n\nfrom zope.interface import implementer, implementer_only, implementedBy\n\n# Twisted imports\nfrom twisted.internet import tcp, interfaces\nfrom twisted.python._oldstyle import _oldStyle\n\n\n@implementer(interfaces.IOpenSSLContextFactory)\n@_oldStyle\nclass ContextFactory:\n    \"\"\"A factory for SSL context objects, for server SSL connections.\"\"\"\n\n    isClient = 0\n\n    def getContext(self):\n        \"\"\"Return a SSL.Context object. override in subclasses.\"\"\"\n        raise NotImplementedError\n\n\n\nclass DefaultOpenSSLContextFactory(ContextFactory):\n    \"\"\"\n    L{DefaultOpenSSLContextFactory} is a factory for server-side SSL context\n    objects.  These objects define certain parameters related to SSL\n    handshakes and the subsequent connection.\n\n    @ivar _contextFactory: A callable which will be used to create new\n        context objects.  This is typically L{OpenSSL.SSL.Context}.\n    \"\"\"\n    _context = None\n\n    def __init__(self, privateKeyFileName, certificateFileName,\n                 sslmethod=SSL.SSLv23_METHOD, _contextFactory=SSL.Context):\n        \"\"\"\n        @param privateKeyFileName: Name of a file containing a private key\n        @param certificateFileName: Name of a file containing a certificate\n        @param sslmethod: The SSL method to use\n        \"\"\"\n        self.privateKeyFileName = privateKeyFileName\n        self.certificateFileName = certificateFileName\n        self.sslmethod = sslmethod\n        self._contextFactory = _contextFactory\n\n        # Create a context object right now.  This is to force validation of\n        # the given parameters so that errors are detected earlier rather\n        # than later.\n        self.cacheContext()\n\n\n    def cacheContext(self):\n        if self._context is None:\n            ctx = self._contextFactory(self.sslmethod)\n            # Disallow SSLv2!  It's insecure!  SSLv3 has been around since\n            # 1996.  It's time to move on.\n            ctx.set_options(SSL.OP_NO_SSLv2)\n            ctx.use_certificate_file(self.certificateFileName)\n            ctx.use_privatekey_file(self.privateKeyFileName)\n            self._context = ctx\n\n\n    def __getstate__(self):\n        d = self.__dict__.copy()\n        del d['_context']\n        return d\n\n\n    def __setstate__(self, state):\n        self.__dict__ = state\n\n\n    def getContext(self):\n        \"\"\"\n        Return an SSL context.\n        \"\"\"\n        return self._context\n\n\n\n@implementer(interfaces.IOpenSSLContextFactory)\n@_oldStyle\nclass ClientContextFactory:\n    \"\"\"A context factory for SSL clients.\"\"\"\n\n    isClient = 1\n\n    # SSLv23_METHOD allows SSLv2, SSLv3, and TLSv1.  We disable SSLv2 below,\n    # though.\n    method = SSL.SSLv23_METHOD\n\n    _contextFactory = SSL.Context\n\n    def getContext(self):\n        ctx = self._contextFactory(self.method)\n        # See comment in DefaultOpenSSLContextFactory about SSLv2.\n        ctx.set_options(SSL.OP_NO_SSLv2)\n        return ctx\n\n\n\n@implementer_only(interfaces.ISSLTransport,\n                 *[i for i in implementedBy(tcp.Client)\n                   if i != interfaces.ITLSTransport])\nclass Client(tcp.Client):\n    \"\"\"\n    I am an SSL client.\n    \"\"\"\n\n    def __init__(self, host, port, bindAddress, ctxFactory, connector, reactor=None):\n        # tcp.Client.__init__ depends on self.ctxFactory being set\n        self.ctxFactory = ctxFactory\n        tcp.Client.__init__(self, host, port, bindAddress, connector, reactor)\n\n    def _connectDone(self):\n        self.startTLS(self.ctxFactory)\n        self.startWriting()\n        tcp.Client._connectDone(self)\n\n\n\n@implementer(interfaces.ISSLTransport)\nclass Server(tcp.Server):\n    \"\"\"\n    I am an SSL server.\n    \"\"\"\n\n    def __init__(self, *args, **kwargs):\n        tcp.Server.__init__(self, *args, **kwargs)\n        self.startTLS(self.server.ctxFactory)\n\n\n\nclass Port(tcp.Port):\n    \"\"\"\n    I am an SSL port.\n    \"\"\"\n    transport = Server\n\n    _type = 'TLS'\n\n    def __init__(self, port, factory, ctxFactory, backlog=50, interface='', reactor=None):\n        tcp.Port.__init__(self, port, factory, backlog, interface, reactor)\n        self.ctxFactory = ctxFactory\n\n\n    def _getLogPrefix(self, factory):\n        \"\"\"\n        Override the normal prefix to include an annotation indicating this is a\n        port for TLS connections.\n        \"\"\"\n        return tcp.Port._getLogPrefix(self, factory) + ' (TLS)'\n\n\n\nclass Connector(tcp.Connector):\n    def __init__(self, host, port, factory, contextFactory, timeout, bindAddress, reactor=None):\n        self.contextFactory = contextFactory\n        tcp.Connector.__init__(self, host, port, factory, timeout, bindAddress, reactor)\n\n        # Force some parameter checking in pyOpenSSL.  It's better to fail now\n        # than after we've set up the transport.\n        contextFactory.getContext()\n\n\n    def _makeTransport(self):\n        return Client(self.host, self.port, self.bindAddress, self.contextFactory, self, self.reactor)\n\n\n\nfrom twisted.internet._sslverify import (\n    KeyPair, DistinguishedName, DN, Certificate,\n    CertificateRequest, PrivateCertificate,\n    OpenSSLAcceptableCiphers as AcceptableCiphers,\n    OpenSSLCertificateOptions as CertificateOptions,\n    OpenSSLDiffieHellmanParameters as DiffieHellmanParameters,\n    platformTrust, OpenSSLDefaultPaths, VerificationError,\n    optionsForClientTLS, ProtocolNegotiationSupport,\n    protocolNegotiationMechanisms,\n    trustRootFromCertificates,\n    TLSVersion,\n)\n\n__all__ = [\n    \"ContextFactory\", \"DefaultOpenSSLContextFactory\", \"ClientContextFactory\",\n\n    'DistinguishedName', 'DN',\n    'Certificate', 'CertificateRequest', 'PrivateCertificate',\n    'KeyPair',\n    'AcceptableCiphers', 'CertificateOptions', 'DiffieHellmanParameters',\n    'platformTrust', 'OpenSSLDefaultPaths', 'TLSVersion',\n\n    'VerificationError', 'optionsForClientTLS',\n    'ProtocolNegotiationSupport', 'protocolNegotiationMechanisms',\n    'trustRootFromCertificates',\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/stdio.py",
    "content": "# -*- test-case-name: twisted.test.test_stdio -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nStandard input/out/err support.\n\nThis module exposes one name, StandardIO, which is a factory that takes an\nIProtocol provider as an argument.  It connects that protocol to standard input\nand output on the current process.\n\nIt should work on any UNIX and also on Win32 (with some caveats: due to\nplatform limitations, it will perform very poorly on Win32).\n\nFuture Plans::\n\n    support for stderr, perhaps\n    Rewrite to use the reactor instead of an ad-hoc mechanism for connecting\n        protocols to transport.\n\n\nMaintainer: James Y Knight\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom twisted.python.runtime import platform\n\nif platform.isWindows():\n    from twisted.internet import _win32stdio\n    StandardIO = _win32stdio.StandardIO\n    PipeAddress = _win32stdio.Win32PipeAddress\n\nelse:\n    from twisted.internet._posixstdio import StandardIO, PipeAddress\n\n__all__ = ['StandardIO', 'PipeAddress']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/task.py",
    "content": "# -*- test-case-name: twisted.test.test_task,twisted.test.test_cooperator -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nScheduling utility methods and classes.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__metaclass__ = type\n\nimport sys\nimport time\nimport warnings\n\nfrom zope.interface import implementer\n\nfrom twisted.python import log\nfrom twisted.python import reflect\nfrom twisted.python.deprecate import _getDeprecationWarningString\nfrom twisted.python.failure import Failure\nfrom incremental import Version\n\nfrom twisted.internet import base, defer\nfrom twisted.internet.interfaces import IReactorTime\nfrom twisted.internet.error import ReactorNotRunning\n\n\nclass LoopingCall:\n    \"\"\"Call a function repeatedly.\n\n    If C{f} returns a deferred, rescheduling will not take place until the\n    deferred has fired. The result value is ignored.\n\n    @ivar f: The function to call.\n    @ivar a: A tuple of arguments to pass the function.\n    @ivar kw: A dictionary of keyword arguments to pass to the function.\n    @ivar clock: A provider of\n        L{twisted.internet.interfaces.IReactorTime}.  The default is\n        L{twisted.internet.reactor}. Feel free to set this to\n        something else, but it probably ought to be set *before*\n        calling L{start}.\n\n    @type running: C{bool}\n    @ivar running: A flag which is C{True} while C{f} is scheduled to be called\n        (or is currently being called). It is set to C{True} when L{start} is\n        called and set to C{False} when L{stop} is called or if C{f} raises an\n        exception. In either case, it will be C{False} by the time the\n        C{Deferred} returned by L{start} fires its callback or errback.\n\n    @type _realLastTime: C{float}\n    @ivar _realLastTime: When counting skips, the time at which the skip\n        counter was last invoked.\n\n    @type _runAtStart: C{bool}\n    @ivar _runAtStart: A flag indicating whether the 'now' argument was passed\n        to L{LoopingCall.start}.\n    \"\"\"\n\n    call = None\n    running = False\n    _deferred = None\n    interval = None\n    _runAtStart = False\n    starttime = None\n\n    def __init__(self, f, *a, **kw):\n        self.f = f\n        self.a = a\n        self.kw = kw\n        from twisted.internet import reactor\n        self.clock = reactor\n\n    @property\n    def deferred(self):\n        \"\"\"\n        DEPRECATED. L{Deferred} fired when loop stops or fails.\n\n        Use the L{Deferred} returned by L{LoopingCall.start}.\n        \"\"\"\n        warningString = _getDeprecationWarningString(\n            \"twisted.internet.task.LoopingCall.deferred\",\n            Version(\"Twisted\", 16, 0, 0),\n            replacement='the deferred returned by start()')\n        warnings.warn(warningString, DeprecationWarning, stacklevel=2)\n\n        return self._deferred\n\n    def withCount(cls, countCallable):\n        \"\"\"\n        An alternate constructor for L{LoopingCall} that makes available the\n        number of calls which should have occurred since it was last invoked.\n\n        Note that this number is an C{int} value; It represents the discrete\n        number of calls that should have been made.  For example, if you are\n        using a looping call to display an animation with discrete frames, this\n        number would be the number of frames to advance.\n\n        The count is normally 1, but can be higher. For example, if the reactor\n        is blocked and takes too long to invoke the L{LoopingCall}, a Deferred\n        returned from a previous call is not fired before an interval has\n        elapsed, or if the callable itself blocks for longer than an interval,\n        preventing I{itself} from being called.\n\n        When running with an interval if 0, count will be always 1.\n\n        @param countCallable: A callable that will be invoked each time the\n            resulting LoopingCall is run, with an integer specifying the number\n            of calls that should have been invoked.\n\n        @type countCallable: 1-argument callable which takes an C{int}\n\n        @return: An instance of L{LoopingCall} with call counting enabled,\n            which provides the count as the first positional argument.\n\n        @rtype: L{LoopingCall}\n\n        @since: 9.0\n        \"\"\"\n\n        def counter():\n            now = self.clock.seconds()\n\n            if self.interval == 0:\n                self._realLastTime = now\n                return countCallable(1)\n\n            lastTime = self._realLastTime\n            if lastTime is None:\n                lastTime = self.starttime\n                if self._runAtStart:\n                    lastTime -= self.interval\n            lastInterval = self._intervalOf(lastTime)\n            thisInterval = self._intervalOf(now)\n            count = thisInterval - lastInterval\n            if count > 0:\n                self._realLastTime = now\n                return countCallable(count)\n\n        self = cls(counter)\n\n        self._realLastTime = None\n\n        return self\n\n    withCount = classmethod(withCount)\n\n\n    def _intervalOf(self, t):\n        \"\"\"\n        Determine the number of intervals passed as of the given point in\n        time.\n\n        @param t: The specified time (from the start of the L{LoopingCall}) to\n            be measured in intervals\n\n        @return: The C{int} number of intervals which have passed as of the\n            given point in time.\n        \"\"\"\n        elapsedTime = t - self.starttime\n        intervalNum = int(elapsedTime / self.interval)\n        return intervalNum\n\n\n    def start(self, interval, now=True):\n        \"\"\"\n        Start running function every interval seconds.\n\n        @param interval: The number of seconds between calls.  May be\n        less than one.  Precision will depend on the underlying\n        platform, the available hardware, and the load on the system.\n\n        @param now: If True, run this call right now.  Otherwise, wait\n        until the interval has elapsed before beginning.\n\n        @return: A Deferred whose callback will be invoked with\n        C{self} when C{self.stop} is called, or whose errback will be\n        invoked when the function raises an exception or returned a\n        deferred that has its errback invoked.\n        \"\"\"\n        assert not self.running, (\"Tried to start an already running \"\n                                  \"LoopingCall.\")\n        if interval < 0:\n            raise ValueError(\"interval must be >= 0\")\n        self.running = True\n        # Loop might fail to start and then self._deferred will be cleared.\n        # This why the local C{deferred} variable is used.\n        deferred = self._deferred = defer.Deferred()\n        self.starttime = self.clock.seconds()\n        self.interval = interval\n        self._runAtStart = now\n        if now:\n            self()\n        else:\n            self._scheduleFrom(self.starttime)\n        return deferred\n\n    def stop(self):\n        \"\"\"Stop running function.\n        \"\"\"\n        assert self.running, (\"Tried to stop a LoopingCall that was \"\n                              \"not running.\")\n        self.running = False\n        if self.call is not None:\n            self.call.cancel()\n            self.call = None\n            d, self._deferred = self._deferred, None\n            d.callback(self)\n\n    def reset(self):\n        \"\"\"\n        Skip the next iteration and reset the timer.\n\n        @since: 11.1\n        \"\"\"\n        assert self.running, (\"Tried to reset a LoopingCall that was \"\n                              \"not running.\")\n        if self.call is not None:\n            self.call.cancel()\n            self.call = None\n            self.starttime = self.clock.seconds()\n            self._scheduleFrom(self.starttime)\n\n    def __call__(self):\n        def cb(result):\n            if self.running:\n                self._scheduleFrom(self.clock.seconds())\n            else:\n                d, self._deferred = self._deferred, None\n                d.callback(self)\n\n        def eb(failure):\n            self.running = False\n            d, self._deferred = self._deferred, None\n            d.errback(failure)\n\n        self.call = None\n        d = defer.maybeDeferred(self.f, *self.a, **self.kw)\n        d.addCallback(cb)\n        d.addErrback(eb)\n\n\n    def _scheduleFrom(self, when):\n        \"\"\"\n        Schedule the next iteration of this looping call.\n\n        @param when: The present time from whence the call is scheduled.\n        \"\"\"\n        def howLong():\n            # How long should it take until the next invocation of our\n            # callable?  Split out into a function because there are multiple\n            # places we want to 'return' out of this.\n            if self.interval == 0:\n                # If the interval is 0, just go as fast as possible, always\n                # return zero, call ourselves ASAP.\n                return 0\n            # Compute the time until the next interval; how long has this call\n            # been running for?\n            runningFor = when - self.starttime\n            # And based on that start time, when does the current interval end?\n            untilNextInterval = self.interval - (runningFor % self.interval)\n            # Now that we know how long it would be, we have to tell if the\n            # number is effectively zero.  However, we can't just test against\n            # zero.  If a number with a small exponent is added to a number\n            # with a large exponent, it may be so small that the digits just\n            # fall off the end, which means that adding the increment makes no\n            # difference; it's time to tick over into the next interval.\n            if when == when + untilNextInterval:\n                # If it's effectively zero, then we need to add another\n                # interval.\n                return self.interval\n            # Finally, if everything else is normal, we just return the\n            # computed delay.\n            return untilNextInterval\n        self.call = self.clock.callLater(howLong(), self)\n\n\n    def __repr__(self):\n        if hasattr(self.f, '__qualname__'):\n            func = self.f.__qualname__\n        elif hasattr(self.f, '__name__'):\n            func = self.f.__name__\n            if hasattr(self.f, 'im_class'):\n                func = self.f.im_class.__name__ + '.' + func\n        else:\n            func = reflect.safe_repr(self.f)\n\n        return 'LoopingCall<%r>(%s, *%s, **%s)' % (\n            self.interval, func, reflect.safe_repr(self.a),\n            reflect.safe_repr(self.kw))\n\n\n\nclass SchedulerError(Exception):\n    \"\"\"\n    The operation could not be completed because the scheduler or one of its\n    tasks was in an invalid state.  This exception should not be raised\n    directly, but is a superclass of various scheduler-state-related\n    exceptions.\n    \"\"\"\n\n\n\nclass SchedulerStopped(SchedulerError):\n    \"\"\"\n    The operation could not complete because the scheduler was stopped in\n    progress or was already stopped.\n    \"\"\"\n\n\n\nclass TaskFinished(SchedulerError):\n    \"\"\"\n    The operation could not complete because the task was already completed,\n    stopped, encountered an error or otherwise permanently stopped running.\n    \"\"\"\n\n\n\nclass TaskDone(TaskFinished):\n    \"\"\"\n    The operation could not complete because the task was already completed.\n    \"\"\"\n\n\n\nclass TaskStopped(TaskFinished):\n    \"\"\"\n    The operation could not complete because the task was stopped.\n    \"\"\"\n\n\n\nclass TaskFailed(TaskFinished):\n    \"\"\"\n    The operation could not complete because the task died with an unhandled\n    error.\n    \"\"\"\n\n\n\nclass NotPaused(SchedulerError):\n    \"\"\"\n    This exception is raised when a task is resumed which was not previously\n    paused.\n    \"\"\"\n\n\n\nclass _Timer(object):\n    MAX_SLICE = 0.01\n    def __init__(self):\n        self.end = time.time() + self.MAX_SLICE\n\n\n    def __call__(self):\n        return time.time() >= self.end\n\n\n\n_EPSILON = 0.00000001\ndef _defaultScheduler(x):\n    from twisted.internet import reactor\n    return reactor.callLater(_EPSILON, x)\n\n\nclass CooperativeTask(object):\n    \"\"\"\n    A L{CooperativeTask} is a task object inside a L{Cooperator}, which can be\n    paused, resumed, and stopped.  It can also have its completion (or\n    termination) monitored.\n\n    @see: L{Cooperator.cooperate}\n\n    @ivar _iterator: the iterator to iterate when this L{CooperativeTask} is\n        asked to do work.\n\n    @ivar _cooperator: the L{Cooperator} that this L{CooperativeTask}\n        participates in, which is used to re-insert it upon resume.\n\n    @ivar _deferreds: the list of L{defer.Deferred}s to fire when this task\n        completes, fails, or finishes.\n\n    @type _deferreds: C{list}\n\n    @type _cooperator: L{Cooperator}\n\n    @ivar _pauseCount: the number of times that this L{CooperativeTask} has\n        been paused; if 0, it is running.\n\n    @type _pauseCount: C{int}\n\n    @ivar _completionState: The completion-state of this L{CooperativeTask}.\n        L{None} if the task is not yet completed, an instance of L{TaskStopped}\n        if C{stop} was called to stop this task early, of L{TaskFailed} if the\n        application code in the iterator raised an exception which caused it to\n        terminate, and of L{TaskDone} if it terminated normally via raising\n        C{StopIteration}.\n\n    @type _completionState: L{TaskFinished}\n    \"\"\"\n\n    def __init__(self, iterator, cooperator):\n        \"\"\"\n        A private constructor: to create a new L{CooperativeTask}, see\n        L{Cooperator.cooperate}.\n        \"\"\"\n        self._iterator = iterator\n        self._cooperator = cooperator\n        self._deferreds = []\n        self._pauseCount = 0\n        self._completionState = None\n        self._completionResult = None\n        cooperator._addTask(self)\n\n\n    def whenDone(self):\n        \"\"\"\n        Get a L{defer.Deferred} notification of when this task is complete.\n\n        @return: a L{defer.Deferred} that fires with the C{iterator} that this\n            L{CooperativeTask} was created with when the iterator has been\n            exhausted (i.e. its C{next} method has raised C{StopIteration}), or\n            fails with the exception raised by C{next} if it raises some other\n            exception.\n\n        @rtype: L{defer.Deferred}\n        \"\"\"\n        d = defer.Deferred()\n        if self._completionState is None:\n            self._deferreds.append(d)\n        else:\n            d.callback(self._completionResult)\n        return d\n\n\n    def pause(self):\n        \"\"\"\n        Pause this L{CooperativeTask}.  Stop doing work until\n        L{CooperativeTask.resume} is called.  If C{pause} is called more than\n        once, C{resume} must be called an equal number of times to resume this\n        task.\n\n        @raise TaskFinished: if this task has already finished or completed.\n        \"\"\"\n        self._checkFinish()\n        self._pauseCount += 1\n        if self._pauseCount == 1:\n            self._cooperator._removeTask(self)\n\n\n    def resume(self):\n        \"\"\"\n        Resume processing of a paused L{CooperativeTask}.\n\n        @raise NotPaused: if this L{CooperativeTask} is not paused.\n        \"\"\"\n        if self._pauseCount == 0:\n            raise NotPaused()\n        self._pauseCount -= 1\n        if self._pauseCount == 0 and self._completionState is None:\n            self._cooperator._addTask(self)\n\n\n    def _completeWith(self, completionState, deferredResult):\n        \"\"\"\n        @param completionState: a L{TaskFinished} exception or a subclass\n            thereof, indicating what exception should be raised when subsequent\n            operations are performed.\n\n        @param deferredResult: the result to fire all the deferreds with.\n        \"\"\"\n        self._completionState = completionState\n        self._completionResult = deferredResult\n        if not self._pauseCount:\n            self._cooperator._removeTask(self)\n\n        # The Deferreds need to be invoked after all this is completed, because\n        # a Deferred may want to manipulate other tasks in a Cooperator.  For\n        # example, if you call \"stop()\" on a cooperator in a callback on a\n        # Deferred returned from whenDone(), this CooperativeTask must be gone\n        # from the Cooperator by that point so that _completeWith is not\n        # invoked reentrantly; that would cause these Deferreds to blow up with\n        # an AlreadyCalledError, or the _removeTask to fail with a ValueError.\n        for d in self._deferreds:\n            d.callback(deferredResult)\n\n\n    def stop(self):\n        \"\"\"\n        Stop further processing of this task.\n\n        @raise TaskFinished: if this L{CooperativeTask} has previously\n            completed, via C{stop}, completion, or failure.\n        \"\"\"\n        self._checkFinish()\n        self._completeWith(TaskStopped(), Failure(TaskStopped()))\n\n\n    def _checkFinish(self):\n        \"\"\"\n        If this task has been stopped, raise the appropriate subclass of\n        L{TaskFinished}.\n        \"\"\"\n        if self._completionState is not None:\n            raise self._completionState\n\n\n    def _oneWorkUnit(self):\n        \"\"\"\n        Perform one unit of work for this task, retrieving one item from its\n        iterator, stopping if there are no further items in the iterator, and\n        pausing if the result was a L{defer.Deferred}.\n        \"\"\"\n        try:\n            result = next(self._iterator)\n        except StopIteration:\n            self._completeWith(TaskDone(), self._iterator)\n        except:\n            self._completeWith(TaskFailed(), Failure())\n        else:\n            if isinstance(result, defer.Deferred):\n                self.pause()\n                def failLater(f):\n                    self._completeWith(TaskFailed(), f)\n                result.addCallbacks(lambda result: self.resume(),\n                                    failLater)\n\n\n\nclass Cooperator(object):\n    \"\"\"\n    Cooperative task scheduler.\n\n    A cooperative task is an iterator where each iteration represents an\n    atomic unit of work.  When the iterator yields, it allows the\n    L{Cooperator} to decide which of its tasks to execute next.  If the\n    iterator yields a L{defer.Deferred} then work will pause until the\n    L{defer.Deferred} fires and completes its callback chain.\n\n    When a L{Cooperator} has more than one task, it distributes work between\n    all tasks.\n\n    There are two ways to add tasks to a L{Cooperator}, L{cooperate} and\n    L{coiterate}.  L{cooperate} is the more useful of the two, as it returns a\n    L{CooperativeTask}, which can be L{paused<CooperativeTask.pause>},\n    L{resumed<CooperativeTask.resume>} and L{waited\n    on<CooperativeTask.whenDone>}.  L{coiterate} has the same effect, but\n    returns only a L{defer.Deferred} that fires when the task is done.\n\n    L{Cooperator} can be used for many things, including but not limited to:\n\n      - running one or more computationally intensive tasks without blocking\n      - limiting parallelism by running a subset of the total tasks\n        simultaneously\n      - doing one thing, waiting for a L{Deferred<defer.Deferred>} to fire,\n        doing the next thing, repeat (i.e. serializing a sequence of\n        asynchronous tasks)\n\n    Multiple L{Cooperator}s do not cooperate with each other, so for most\n    cases you should use the L{global cooperator<task.cooperate>}.\n    \"\"\"\n\n    def __init__(self,\n                 terminationPredicateFactory=_Timer,\n                 scheduler=_defaultScheduler,\n                 started=True):\n        \"\"\"\n        Create a scheduler-like object to which iterators may be added.\n\n        @param terminationPredicateFactory: A no-argument callable which will\n        be invoked at the beginning of each step and should return a\n        no-argument callable which will return True when the step should be\n        terminated.  The default factory is time-based and allows iterators to\n        run for 1/100th of a second at a time.\n\n        @param scheduler: A one-argument callable which takes a no-argument\n        callable and should invoke it at some future point.  This will be used\n        to schedule each step of this Cooperator.\n\n        @param started: A boolean which indicates whether iterators should be\n        stepped as soon as they are added, or if they will be queued up until\n        L{Cooperator.start} is called.\n        \"\"\"\n        self._tasks = []\n        self._metarator = iter(())\n        self._terminationPredicateFactory = terminationPredicateFactory\n        self._scheduler = scheduler\n        self._delayedCall = None\n        self._stopped = False\n        self._started = started\n\n\n    def coiterate(self, iterator, doneDeferred=None):\n        \"\"\"\n        Add an iterator to the list of iterators this L{Cooperator} is\n        currently running.\n\n        Equivalent to L{cooperate}, but returns a L{defer.Deferred} that will\n        be fired when the task is done.\n\n        @param doneDeferred: If specified, this will be the Deferred used as\n            the completion deferred.  It is suggested that you use the default,\n            which creates a new Deferred for you.\n\n        @return: a Deferred that will fire when the iterator finishes.\n        \"\"\"\n        if doneDeferred is None:\n            doneDeferred = defer.Deferred()\n        CooperativeTask(iterator, self).whenDone().chainDeferred(doneDeferred)\n        return doneDeferred\n\n\n    def cooperate(self, iterator):\n        \"\"\"\n        Start running the given iterator as a long-running cooperative task, by\n        calling next() on it as a periodic timed event.\n\n        @param iterator: the iterator to invoke.\n\n        @return: a L{CooperativeTask} object representing this task.\n        \"\"\"\n        return CooperativeTask(iterator, self)\n\n\n    def _addTask(self, task):\n        \"\"\"\n        Add a L{CooperativeTask} object to this L{Cooperator}.\n        \"\"\"\n        if self._stopped:\n            self._tasks.append(task) # XXX silly, I know, but _completeWith\n                                     # does the inverse\n            task._completeWith(SchedulerStopped(), Failure(SchedulerStopped()))\n        else:\n            self._tasks.append(task)\n            self._reschedule()\n\n\n    def _removeTask(self, task):\n        \"\"\"\n        Remove a L{CooperativeTask} from this L{Cooperator}.\n        \"\"\"\n        self._tasks.remove(task)\n        # If no work left to do, cancel the delayed call:\n        if not self._tasks and self._delayedCall:\n            self._delayedCall.cancel()\n            self._delayedCall = None\n\n\n    def _tasksWhileNotStopped(self):\n        \"\"\"\n        Yield all L{CooperativeTask} objects in a loop as long as this\n        L{Cooperator}'s termination condition has not been met.\n        \"\"\"\n        terminator = self._terminationPredicateFactory()\n        while self._tasks:\n            for t in self._metarator:\n                yield t\n                if terminator():\n                    return\n            self._metarator = iter(self._tasks)\n\n\n    def _tick(self):\n        \"\"\"\n        Run one scheduler tick.\n        \"\"\"\n        self._delayedCall = None\n        for taskObj in self._tasksWhileNotStopped():\n            taskObj._oneWorkUnit()\n        self._reschedule()\n\n\n    _mustScheduleOnStart = False\n    def _reschedule(self):\n        if not self._started:\n            self._mustScheduleOnStart = True\n            return\n        if self._delayedCall is None and self._tasks:\n            self._delayedCall = self._scheduler(self._tick)\n\n\n    def start(self):\n        \"\"\"\n        Begin scheduling steps.\n        \"\"\"\n        self._stopped = False\n        self._started = True\n        if self._mustScheduleOnStart:\n            del self._mustScheduleOnStart\n            self._reschedule()\n\n\n    def stop(self):\n        \"\"\"\n        Stop scheduling steps.  Errback the completion Deferreds of all\n        iterators which have been added and forget about them.\n        \"\"\"\n        self._stopped = True\n        for taskObj in self._tasks:\n            taskObj._completeWith(SchedulerStopped(),\n                                  Failure(SchedulerStopped()))\n        self._tasks = []\n        if self._delayedCall is not None:\n            self._delayedCall.cancel()\n            self._delayedCall = None\n\n\n    @property\n    def running(self):\n        \"\"\"\n        Is this L{Cooperator} is currently running?\n\n        @return: C{True} if the L{Cooperator} is running, C{False} otherwise.\n        @rtype: C{bool}\n        \"\"\"\n        return (self._started and not self._stopped)\n\n\n\n_theCooperator = Cooperator()\n\ndef coiterate(iterator):\n    \"\"\"\n    Cooperatively iterate over the given iterator, dividing runtime between it\n    and all other iterators which have been passed to this function and not yet\n    exhausted.\n\n    @param iterator: the iterator to invoke.\n\n    @return: a Deferred that will fire when the iterator finishes.\n    \"\"\"\n    return _theCooperator.coiterate(iterator)\n\n\n\ndef cooperate(iterator):\n    \"\"\"\n    Start running the given iterator as a long-running cooperative task, by\n    calling next() on it as a periodic timed event.\n\n    This is very useful if you have computationally expensive tasks that you\n    want to run without blocking the reactor.  Just break each task up so that\n    it yields frequently, pass it in here and the global L{Cooperator} will\n    make sure work is distributed between them without blocking longer than a\n    single iteration of a single task.\n\n    @param iterator: the iterator to invoke.\n\n    @return: a L{CooperativeTask} object representing this task.\n    \"\"\"\n    return _theCooperator.cooperate(iterator)\n\n\n\n@implementer(IReactorTime)\nclass Clock:\n    \"\"\"\n    Provide a deterministic, easily-controlled implementation of\n    L{IReactorTime.callLater}.  This is commonly useful for writing\n    deterministic unit tests for code which schedules events using this API.\n    \"\"\"\n\n    rightNow = 0.0\n\n    def __init__(self):\n        self.calls = []\n\n\n    def seconds(self):\n        \"\"\"\n        Pretend to be time.time().  This is used internally when an operation\n        such as L{IDelayedCall.reset} needs to determine a time value\n        relative to the current time.\n\n        @rtype: C{float}\n        @return: The time which should be considered the current time.\n        \"\"\"\n        return self.rightNow\n\n\n    def _sortCalls(self):\n        \"\"\"\n        Sort the pending calls according to the time they are scheduled.\n        \"\"\"\n        self.calls.sort(key=lambda a: a.getTime())\n\n\n    def callLater(self, when, what, *a, **kw):\n        \"\"\"\n        See L{twisted.internet.interfaces.IReactorTime.callLater}.\n        \"\"\"\n        dc = base.DelayedCall(self.seconds() + when,\n                               what, a, kw,\n                               self.calls.remove,\n                               lambda c: None,\n                               self.seconds)\n        self.calls.append(dc)\n        self._sortCalls()\n        return dc\n\n\n    def getDelayedCalls(self):\n        \"\"\"\n        See L{twisted.internet.interfaces.IReactorTime.getDelayedCalls}\n        \"\"\"\n        return self.calls\n\n\n    def advance(self, amount):\n        \"\"\"\n        Move time on this clock forward by the given amount and run whatever\n        pending calls should be run.\n\n        @type amount: C{float}\n        @param amount: The number of seconds which to advance this clock's\n        time.\n        \"\"\"\n        self.rightNow += amount\n        self._sortCalls()\n        while self.calls and self.calls[0].getTime() <= self.seconds():\n            call = self.calls.pop(0)\n            call.called = 1\n            call.func(*call.args, **call.kw)\n            self._sortCalls()\n\n\n    def pump(self, timings):\n        \"\"\"\n        Advance incrementally by the given set of times.\n\n        @type timings: iterable of C{float}\n        \"\"\"\n        for amount in timings:\n            self.advance(amount)\n\n\n\ndef deferLater(clock, delay, callable=None, *args, **kw):\n    \"\"\"\n    Call the given function after a certain period of time has passed.\n\n    @type clock: L{IReactorTime} provider\n    @param clock: The object which will be used to schedule the delayed\n        call.\n\n    @type delay: C{float} or C{int}\n    @param delay: The number of seconds to wait before calling the function.\n\n    @param callable: The object to call after the delay.\n\n    @param *args: The positional arguments to pass to C{callable}.\n\n    @param **kw: The keyword arguments to pass to C{callable}.\n\n    @rtype: L{defer.Deferred}\n\n    @return: A deferred that fires with the result of the callable when the\n        specified time has elapsed.\n    \"\"\"\n    def deferLaterCancel(deferred):\n        delayedCall.cancel()\n    d = defer.Deferred(deferLaterCancel)\n    if callable is not None:\n        d.addCallback(lambda ignored: callable(*args, **kw))\n    delayedCall = clock.callLater(delay, d.callback, None)\n    return d\n\n\n\ndef react(main, argv=(), _reactor=None):\n    \"\"\"\n    Call C{main} and run the reactor until the L{Deferred} it returns fires.\n\n    This is intended as the way to start up an application with a well-defined\n    completion condition.  Use it to write clients or one-off asynchronous\n    operations.  Prefer this to calling C{reactor.run} directly, as this\n    function will also:\n\n      - Take care to call C{reactor.stop} once and only once, and at the right\n        time.\n      - Log any failures from the C{Deferred} returned by C{main}.\n      - Exit the application when done, with exit code 0 in case of success and\n        1 in case of failure. If C{main} fails with a C{SystemExit} error, the\n        code returned is used.\n\n    The following demonstrates the signature of a C{main} function which can be\n    used with L{react}::\n          def main(reactor, username, password):\n              return defer.succeed('ok')\n\n          task.react(main, ('alice', 'secret'))\n\n    @param main: A callable which returns a L{Deferred}. It should\n        take the reactor as its first parameter, followed by the elements of\n        C{argv}.\n\n    @param argv: A list of arguments to pass to C{main}. If omitted the\n        callable will be invoked with no additional arguments.\n\n    @param _reactor: An implementation detail to allow easier unit testing.  Do\n        not supply this parameter.\n\n    @since: 12.3\n    \"\"\"\n    if _reactor is None:\n        from twisted.internet import reactor as _reactor\n    finished = main(_reactor, *argv)\n    codes = [0]\n\n    stopping = []\n    _reactor.addSystemEventTrigger('before', 'shutdown', stopping.append, True)\n\n    def stop(result, stopReactor):\n        if stopReactor:\n            try:\n                _reactor.stop()\n            except ReactorNotRunning:\n                pass\n\n        if isinstance(result, Failure):\n            if result.check(SystemExit) is not None:\n                code = result.value.code\n            else:\n                log.err(result, \"main function encountered error\")\n                code = 1\n            codes[0] = code\n\n    def cbFinish(result):\n        if stopping:\n            stop(result, False)\n        else:\n            _reactor.callWhenRunning(stop, result, True)\n\n    finished.addBoth(cbFinish)\n    _reactor.run()\n    sys.exit(codes[0])\n\n\n__all__ = [\n    'LoopingCall',\n\n    'Clock',\n\n    'SchedulerStopped', 'Cooperator', 'coiterate',\n\n    'deferLater', 'react']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/tcp.py",
    "content": "# -*- test-case-name: twisted.test.test_tcp -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nVarious asynchronous TCP/IP classes.\n\nEnd users shouldn't use this module directly - use the reactor APIs instead.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n# System Imports\nimport socket\nimport sys\nimport operator\nimport os\nimport struct\n\nimport attr\n\nfrom zope.interface import Interface, implementer\n\nfrom twisted.logger import Logger\nfrom twisted.python.compat import lazyByteSlice, unicode\nfrom twisted.python.runtime import platformType\nfrom twisted.python import versions, deprecate\n\ntry:\n    # Try to get the memory BIO based startTLS implementation, available since\n    # pyOpenSSL 0.10\n    from twisted.internet._newtls import (\n        ConnectionMixin as _TLSConnectionMixin,\n        ClientMixin as _TLSClientMixin,\n        ServerMixin as _TLSServerMixin)\nexcept ImportError:\n    # There is no version of startTLS available\n    class _TLSConnectionMixin(object):\n        TLS = False\n\n\n    class _TLSClientMixin(object):\n        pass\n\n\n    class _TLSServerMixin(object):\n        pass\n\n\nif platformType == 'win32':\n    # no such thing as WSAEPERM or error code 10001 according to winsock.h or MSDN\n    EPERM = object()\n    from errno import WSAEINVAL as EINVAL\n    from errno import WSAEWOULDBLOCK as EWOULDBLOCK\n    from errno import WSAEINPROGRESS as EINPROGRESS\n    from errno import WSAEALREADY as EALREADY\n    from errno import WSAEISCONN as EISCONN\n    from errno import WSAENOBUFS as ENOBUFS\n    from errno import WSAEMFILE as EMFILE\n    # No such thing as WSAENFILE, either.\n    ENFILE = object()\n    # Nor ENOMEM\n    ENOMEM = object()\n    EAGAIN = EWOULDBLOCK\n    from errno import WSAECONNRESET as ECONNABORTED\n\n    from twisted.python.win32 import formatError as strerror\nelse:\n    from errno import EPERM\n    from errno import EINVAL\n    from errno import EWOULDBLOCK\n    from errno import EINPROGRESS\n    from errno import EALREADY\n    from errno import EISCONN\n    from errno import ENOBUFS\n    from errno import EMFILE\n    from errno import ENFILE\n    from errno import ENOMEM\n    from errno import EAGAIN\n    from errno import ECONNABORTED\n\n    from os import strerror\n\n\nfrom errno import errorcode\n\n# Twisted Imports\nfrom twisted.internet import base, address, fdesc\nfrom twisted.internet.task import deferLater\nfrom twisted.python import log, failure, reflect\nfrom twisted.python.util import untilConcludes\nfrom twisted.internet.error import CannotListenError\nfrom twisted.internet import abstract, main, interfaces, error\nfrom twisted.internet.protocol import Protocol\n\n# Not all platforms have, or support, this flag.\n_AI_NUMERICSERV = getattr(socket, \"AI_NUMERICSERV\", 0)\n\n\n# The type for service names passed to socket.getservbyname:\n_portNameType = (str, unicode)\n\n\ndef _getrealname(addr):\n    \"\"\"\n    Return a 2-tuple of socket IP and port for IPv4 and a 4-tuple of\n    socket IP, port, flowInfo, and scopeID for IPv6.  For IPv6, it\n    returns the interface portion (the part after the %) as a part of\n    the IPv6 address, which Python 3.7+ does not include.\n\n    @param addr: A 2-tuple for IPv4 information or a 4-tuple for IPv6\n        information.\n    \"\"\"\n    if len(addr) == 4:\n        # IPv6\n        host = socket.getnameinfo(\n            addr, socket.NI_NUMERICHOST | socket.NI_NUMERICSERV)[0]\n        return tuple([host] + list(addr[1:]))\n    else:\n        return addr[:2]\n\n\n\ndef _getpeername(skt):\n    \"\"\"\n    See L{_getrealname}.\n    \"\"\"\n    return _getrealname(skt.getpeername())\n\n\n\ndef _getsockname(skt):\n    \"\"\"\n    See L{_getrealname}.\n    \"\"\"\n    return _getrealname(skt.getsockname())\n\n\n\nclass _SocketCloser(object):\n    \"\"\"\n    @ivar _shouldShutdown: Set to C{True} if C{shutdown} should be called\n        before calling C{close} on the underlying socket.\n    @type _shouldShutdown: C{bool}\n    \"\"\"\n    _shouldShutdown = True\n\n    def _closeSocket(self, orderly):\n        # The call to shutdown() before close() isn't really necessary, because\n        # we set FD_CLOEXEC now, which will ensure this is the only process\n        # holding the FD, thus ensuring close() really will shutdown the TCP\n        # socket. However, do it anyways, just to be safe.\n        skt = self.socket\n        try:\n            if orderly:\n                if self._shouldShutdown:\n                    skt.shutdown(2)\n            else:\n                # Set SO_LINGER to 1,0 which, by convention, causes a\n                # connection reset to be sent when close is called,\n                # instead of the standard FIN shutdown sequence.\n                self.socket.setsockopt(socket.SOL_SOCKET, socket.SO_LINGER,\n                                       struct.pack(\"ii\", 1, 0))\n\n        except socket.error:\n            pass\n        try:\n            skt.close()\n        except socket.error:\n            pass\n\n\n\nclass _AbortingMixin(object):\n    \"\"\"\n    Common implementation of C{abortConnection}.\n\n    @ivar _aborting: Set to C{True} when C{abortConnection} is called.\n    @type _aborting: C{bool}\n    \"\"\"\n    _aborting = False\n\n    def abortConnection(self):\n        \"\"\"\n        Aborts the connection immediately, dropping any buffered data.\n\n        @since: 11.1\n        \"\"\"\n        if self.disconnected or self._aborting:\n            return\n        self._aborting = True\n        self.stopReading()\n        self.stopWriting()\n        self.doRead = lambda *args, **kwargs: None\n        self.doWrite = lambda *args, **kwargs: None\n        self.reactor.callLater(0, self.connectionLost,\n                               failure.Failure(error.ConnectionAborted()))\n\n\n\n@implementer(interfaces.ITCPTransport, interfaces.ISystemHandle)\nclass Connection(_TLSConnectionMixin, abstract.FileDescriptor, _SocketCloser,\n                 _AbortingMixin):\n    \"\"\"\n    Superclass of all socket-based FileDescriptors.\n\n    This is an abstract superclass of all objects which represent a TCP/IP\n    connection based socket.\n\n    @ivar logstr: prefix used when logging events related to this connection.\n    @type logstr: C{str}\n    \"\"\"\n\n\n    def __init__(self, skt, protocol, reactor=None):\n        abstract.FileDescriptor.__init__(self, reactor=reactor)\n        self.socket = skt\n        self.socket.setblocking(0)\n        self.fileno = skt.fileno\n        self.protocol = protocol\n\n\n    def getHandle(self):\n        \"\"\"Return the socket for this connection.\"\"\"\n        return self.socket\n\n\n    def doRead(self):\n        \"\"\"Calls self.protocol.dataReceived with all available data.\n\n        This reads up to self.bufferSize bytes of data from its socket, then\n        calls self.dataReceived(data) to process it.  If the connection is not\n        lost through an error in the physical recv(), this function will return\n        the result of the dataReceived call.\n        \"\"\"\n        try:\n            data = self.socket.recv(self.bufferSize)\n        except socket.error as se:\n            if se.args[0] == EWOULDBLOCK:\n                return\n            else:\n                return main.CONNECTION_LOST\n\n        return self._dataReceived(data)\n\n\n    def _dataReceived(self, data):\n        if not data:\n            return main.CONNECTION_DONE\n        rval = self.protocol.dataReceived(data)\n        if rval is not None:\n            offender = self.protocol.dataReceived\n            warningFormat = (\n                'Returning a value other than None from %(fqpn)s is '\n                'deprecated since %(version)s.')\n            warningString = deprecate.getDeprecationWarningString(\n                offender, versions.Version('Twisted', 11, 0, 0),\n                format=warningFormat)\n            deprecate.warnAboutFunction(offender, warningString)\n        return rval\n\n\n    def writeSomeData(self, data):\n        \"\"\"\n        Write as much as possible of the given data to this TCP connection.\n\n        This sends up to C{self.SEND_LIMIT} bytes from C{data}.  If the\n        connection is lost, an exception is returned.  Otherwise, the number\n        of bytes successfully written is returned.\n        \"\"\"\n        # Limit length of buffer to try to send, because some OSes are too\n        # stupid to do so themselves (ahem windows)\n        limitedData = lazyByteSlice(data, 0, self.SEND_LIMIT)\n\n        try:\n            return untilConcludes(self.socket.send, limitedData)\n        except socket.error as se:\n            if se.args[0] in (EWOULDBLOCK, ENOBUFS):\n                return 0\n            else:\n                return main.CONNECTION_LOST\n\n\n    def _closeWriteConnection(self):\n        try:\n            self.socket.shutdown(1)\n        except socket.error:\n            pass\n        p = interfaces.IHalfCloseableProtocol(self.protocol, None)\n        if p:\n            try:\n                p.writeConnectionLost()\n            except:\n                f = failure.Failure()\n                log.err()\n                self.connectionLost(f)\n\n\n    def readConnectionLost(self, reason):\n        p = interfaces.IHalfCloseableProtocol(self.protocol, None)\n        if p:\n            try:\n                p.readConnectionLost()\n            except:\n                log.err()\n                self.connectionLost(failure.Failure())\n        else:\n            self.connectionLost(reason)\n\n\n\n    def connectionLost(self, reason):\n        \"\"\"See abstract.FileDescriptor.connectionLost().\n        \"\"\"\n        # Make sure we're not called twice, which can happen e.g. if\n        # abortConnection() is called from protocol's dataReceived and then\n        # code immediately after throws an exception that reaches the\n        # reactor. We can't rely on \"disconnected\" attribute for this check\n        # since twisted.internet._oldtls does evil things to it:\n        if not hasattr(self, \"socket\"):\n            return\n        abstract.FileDescriptor.connectionLost(self, reason)\n        self._closeSocket(not reason.check(error.ConnectionAborted))\n        protocol = self.protocol\n        del self.protocol\n        del self.socket\n        del self.fileno\n        protocol.connectionLost(reason)\n\n\n    logstr = \"Uninitialized\"\n\n    def logPrefix(self):\n        \"\"\"Return the prefix to log with when I own the logging thread.\n        \"\"\"\n        return self.logstr\n\n    def getTcpNoDelay(self):\n        return operator.truth(self.socket.getsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY))\n\n    def setTcpNoDelay(self, enabled):\n        self.socket.setsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY, enabled)\n\n    def getTcpKeepAlive(self):\n        return operator.truth(self.socket.getsockopt(socket.SOL_SOCKET,\n                                                     socket.SO_KEEPALIVE))\n\n    def setTcpKeepAlive(self, enabled):\n        self.socket.setsockopt(socket.SOL_SOCKET, socket.SO_KEEPALIVE, enabled)\n\n\n\n\nclass _BaseBaseClient(object):\n    \"\"\"\n    Code shared with other (non-POSIX) reactors for management of general\n    outgoing connections.\n\n    Requirements upon subclasses are documented as instance variables rather\n    than abstract methods, in order to avoid MRO confusion, since this base is\n    mixed in to unfortunately weird and distinctive multiple-inheritance\n    hierarchies and many of these attributes are provided by peer classes\n    rather than descendant classes in those hierarchies.\n\n    @ivar addressFamily: The address family constant (C{socket.AF_INET},\n        C{socket.AF_INET6}, C{socket.AF_UNIX}) of the underlying socket of this\n        client connection.\n    @type addressFamily: C{int}\n\n    @ivar socketType: The socket type constant (C{socket.SOCK_STREAM} or\n        C{socket.SOCK_DGRAM}) of the underlying socket.\n    @type socketType: C{int}\n\n    @ivar _requiresResolution: A flag indicating whether the address of this\n        client will require name resolution.  C{True} if the hostname of said\n        address indicates a name that must be resolved by hostname lookup,\n        C{False} if it indicates an IP address literal.\n    @type _requiresResolution: C{bool}\n\n    @cvar _commonConnection: Subclasses must provide this attribute, which\n        indicates the L{Connection}-alike class to invoke C{__init__} and\n        C{connectionLost} on.\n    @type _commonConnection: C{type}\n\n    @ivar _stopReadingAndWriting: Subclasses must implement in order to remove\n        this transport from its reactor's notifications in response to a\n        terminated connection attempt.\n    @type _stopReadingAndWriting: 0-argument callable returning L{None}\n\n    @ivar _closeSocket: Subclasses must implement in order to close the socket\n        in response to a terminated connection attempt.\n    @type _closeSocket: 1-argument callable; see L{_SocketCloser._closeSocket}\n\n    @ivar _collectSocketDetails: Clean up references to the attached socket in\n        its underlying OS resource (such as a file descriptor or file handle),\n        as part of post connection-failure cleanup.\n    @type _collectSocketDetails: 0-argument callable returning L{None}.\n\n    @ivar reactor: The class pointed to by C{_commonConnection} should set this\n        attribute in its constructor.\n    @type reactor: L{twisted.internet.interfaces.IReactorTime},\n        L{twisted.internet.interfaces.IReactorCore},\n        L{twisted.internet.interfaces.IReactorFDSet}\n    \"\"\"\n\n    addressFamily = socket.AF_INET\n    socketType = socket.SOCK_STREAM\n\n    def _finishInit(self, whenDone, skt, error, reactor):\n        \"\"\"\n        Called by subclasses to continue to the stage of initialization where\n        the socket connect attempt is made.\n\n        @param whenDone: A 0-argument callable to invoke once the connection is\n            set up.  This is L{None} if the connection could not be prepared\n            due to a previous error.\n\n        @param skt: The socket object to use to perform the connection.\n        @type skt: C{socket._socketobject}\n\n        @param error: The error to fail the connection with.\n\n        @param reactor: The reactor to use for this client.\n        @type reactor: L{twisted.internet.interfaces.IReactorTime}\n        \"\"\"\n        if whenDone:\n            self._commonConnection.__init__(self, skt, None, reactor)\n            reactor.callLater(0, whenDone)\n        else:\n            reactor.callLater(0, self.failIfNotConnected, error)\n\n\n    def resolveAddress(self):\n        \"\"\"\n        Resolve the name that was passed to this L{_BaseBaseClient}, if\n        necessary, and then move on to attempting the connection once an\n        address has been determined.  (The connection will be attempted\n        immediately within this function if either name resolution can be\n        synchronous or the address was an IP address literal.)\n\n        @note: You don't want to call this method from outside, as it won't do\n            anything useful; it's just part of the connection bootstrapping\n            process.  Also, although this method is on L{_BaseBaseClient} for\n            historical reasons, it's not used anywhere except for L{Client}\n            itself.\n\n        @return: L{None}\n        \"\"\"\n        if self._requiresResolution:\n            d = self.reactor.resolve(self.addr[0])\n            d.addCallback(lambda n: (n,) + self.addr[1:])\n            d.addCallbacks(self._setRealAddress, self.failIfNotConnected)\n        else:\n            self._setRealAddress(self.addr)\n\n\n    def _setRealAddress(self, address):\n        \"\"\"\n        Set the resolved address of this L{_BaseBaseClient} and initiate the\n        connection attempt.\n\n        @param address: Depending on whether this is an IPv4 or IPv6 connection\n            attempt, a 2-tuple of C{(host, port)} or a 4-tuple of C{(host,\n            port, flow, scope)}.  At this point it is a fully resolved address,\n            and the 'host' portion will always be an IP address, not a DNS\n            name.\n        \"\"\"\n        if len(address) == 4:\n            # IPv6, make sure we have the scopeID associated\n            hostname = socket.getnameinfo(\n                address, socket.NI_NUMERICHOST | socket.NI_NUMERICSERV)[0]\n            self.realAddress = tuple([hostname] + list(address[1:]))\n        else:\n            self.realAddress = address\n        self.doConnect()\n\n\n    def failIfNotConnected(self, err):\n        \"\"\"\n        Generic method called when the attempts to connect failed. It basically\n        cleans everything it can: call connectionFailed, stop read and write,\n        delete socket related members.\n        \"\"\"\n        if (self.connected or self.disconnected or\n            not hasattr(self, \"connector\")):\n            return\n\n        self._stopReadingAndWriting()\n        try:\n            self._closeSocket(True)\n        except AttributeError:\n            pass\n        else:\n            self._collectSocketDetails()\n        self.connector.connectionFailed(failure.Failure(err))\n        del self.connector\n\n\n    def stopConnecting(self):\n        \"\"\"\n        If a connection attempt is still outstanding (i.e.  no connection is\n        yet established), immediately stop attempting to connect.\n        \"\"\"\n        self.failIfNotConnected(error.UserError())\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Invoked by lower-level logic when it's time to clean the socket up.\n        Depending on the state of the connection, either inform the attached\n        L{Connector} that the connection attempt has failed, or inform the\n        connected L{IProtocol} that the established connection has been lost.\n\n        @param reason: the reason that the connection was terminated\n        @type reason: L{Failure}\n        \"\"\"\n        if not self.connected:\n            self.failIfNotConnected(error.ConnectError(string=reason))\n        else:\n            self._commonConnection.connectionLost(self, reason)\n            self.connector.connectionLost(reason)\n\n\n\nclass BaseClient(_BaseBaseClient, _TLSClientMixin, Connection):\n    \"\"\"\n    A base class for client TCP (and similar) sockets.\n\n    @ivar realAddress: The address object that will be used for socket.connect;\n        this address is an address tuple (the number of elements dependent upon\n        the address family) which does not contain any names which need to be\n        resolved.\n    @type realAddress: C{tuple}\n\n    @ivar _base: L{Connection}, which is the base class of this class which has\n        all of the useful file descriptor methods.  This is used by\n        L{_TLSServerMixin} to call the right methods to directly manipulate the\n        transport, as is necessary for writing TLS-encrypted bytes (whereas\n        those methods on L{Server} will go through another layer of TLS if it\n        has been enabled).\n    \"\"\"\n\n    _base = Connection\n    _commonConnection = Connection\n\n    def _stopReadingAndWriting(self):\n        \"\"\"\n        Implement the POSIX-ish (i.e.\n        L{twisted.internet.interfaces.IReactorFDSet}) method of detaching this\n        socket from the reactor for L{_BaseBaseClient}.\n        \"\"\"\n        if hasattr(self, \"reactor\"):\n            # this doesn't happen if we failed in __init__\n            self.stopReading()\n            self.stopWriting()\n\n\n    def _collectSocketDetails(self):\n        \"\"\"\n        Clean up references to the socket and its file descriptor.\n\n        @see: L{_BaseBaseClient}\n        \"\"\"\n        del self.socket, self.fileno\n\n\n    def createInternetSocket(self):\n        \"\"\"(internal) Create a non-blocking socket using\n        self.addressFamily, self.socketType.\n        \"\"\"\n        s = socket.socket(self.addressFamily, self.socketType)\n        s.setblocking(0)\n        fdesc._setCloseOnExec(s.fileno())\n        return s\n\n\n    def doConnect(self):\n        \"\"\"\n        Initiate the outgoing connection attempt.\n\n        @note: Applications do not need to call this method; it will be invoked\n            internally as part of L{IReactorTCP.connectTCP}.\n        \"\"\"\n        self.doWrite = self.doConnect\n        self.doRead = self.doConnect\n        if not hasattr(self, \"connector\"):\n            # this happens when connection failed but doConnect\n            # was scheduled via a callLater in self._finishInit\n            return\n\n        err = self.socket.getsockopt(socket.SOL_SOCKET, socket.SO_ERROR)\n        if err:\n            self.failIfNotConnected(error.getConnectError((err, strerror(err))))\n            return\n\n        # doConnect gets called twice.  The first time we actually need to\n        # start the connection attempt.  The second time we don't really\n        # want to (SO_ERROR above will have taken care of any errors, and if\n        # it reported none, the mere fact that doConnect was called again is\n        # sufficient to indicate that the connection has succeeded), but it\n        # is not /particularly/ detrimental to do so.  This should get\n        # cleaned up some day, though.\n        try:\n            connectResult = self.socket.connect_ex(self.realAddress)\n        except socket.error as se:\n            connectResult = se.args[0]\n        if connectResult:\n            if connectResult == EISCONN:\n                pass\n            # on Windows EINVAL means sometimes that we should keep trying:\n            # http://msdn.microsoft.com/library/default.asp?url=/library/en-us/winsock/winsock/connect_2.asp\n            elif ((connectResult in (EWOULDBLOCK, EINPROGRESS, EALREADY)) or\n                  (connectResult == EINVAL and platformType == \"win32\")):\n                self.startReading()\n                self.startWriting()\n                return\n            else:\n                self.failIfNotConnected(error.getConnectError((connectResult, strerror(connectResult))))\n                return\n\n        # If I have reached this point without raising or returning, that means\n        # that the socket is connected.\n        del self.doWrite\n        del self.doRead\n        # we first stop and then start, to reset any references to the old doRead\n        self.stopReading()\n        self.stopWriting()\n        self._connectDone()\n\n\n    def _connectDone(self):\n        \"\"\"\n        This is a hook for when a connection attempt has succeeded.\n\n        Here, we build the protocol from the\n        L{twisted.internet.protocol.ClientFactory} that was passed in, compute\n        a log string, begin reading so as to send traffic to the newly built\n        protocol, and finally hook up the protocol itself.\n\n        This hook is overridden by L{ssl.Client} to initiate the TLS protocol.\n        \"\"\"\n        self.protocol = self.connector.buildProtocol(self.getPeer())\n        self.connected = 1\n        logPrefix = self._getLogPrefix(self.protocol)\n        self.logstr = \"%s,client\" % logPrefix\n        if self.protocol is None:\n            # Factory.buildProtocol is allowed to return None.  In that case,\n            # make up a protocol to satisfy the rest of the implementation;\n            # connectionLost is going to be called on something, for example.\n            # This is easier than adding special case support for a None\n            # protocol throughout the rest of the transport implementation.\n            self.protocol = Protocol()\n            # But dispose of the connection quickly.\n            self.loseConnection()\n        else:\n            self.startReading()\n            self.protocol.makeConnection(self)\n\n\n\n_NUMERIC_ONLY = socket.AI_NUMERICHOST | _AI_NUMERICSERV\n\ndef _resolveIPv6(ip, port):\n    \"\"\"\n    Resolve an IPv6 literal into an IPv6 address.\n\n    This is necessary to resolve any embedded scope identifiers to the relevant\n    C{sin6_scope_id} for use with C{socket.connect()}, C{socket.listen()}, or\n    C{socket.bind()}; see U{RFC 3493 <https://tools.ietf.org/html/rfc3493>} for\n    more information.\n\n    @param ip: An IPv6 address literal.\n    @type ip: C{str}\n\n    @param port: A port number.\n    @type port: C{int}\n\n    @return: a 4-tuple of C{(host, port, flow, scope)}, suitable for use as an\n        IPv6 address.\n\n    @raise socket.gaierror: if either the IP or port is not numeric as it\n        should be.\n    \"\"\"\n    return socket.getaddrinfo(ip, port, 0, 0, 0, _NUMERIC_ONLY)[0][4]\n\n\n\nclass _BaseTCPClient(object):\n    \"\"\"\n    Code shared with other (non-POSIX) reactors for management of outgoing TCP\n    connections (both TCPv4 and TCPv6).\n\n    @note: In order to be functional, this class must be mixed into the same\n        hierarchy as L{_BaseBaseClient}.  It would subclass L{_BaseBaseClient}\n        directly, but the class hierarchy here is divided in strange ways out\n        of the need to share code along multiple axes; specifically, with the\n        IOCP reactor and also with UNIX clients in other reactors.\n\n    @ivar _addressType: The Twisted _IPAddress implementation for this client\n    @type _addressType: L{IPv4Address} or L{IPv6Address}\n\n    @ivar connector: The L{Connector} which is driving this L{_BaseTCPClient}'s\n        connection attempt.\n\n    @ivar addr: The address that this socket will be connecting to.\n    @type addr: If IPv4, a 2-C{tuple} of C{(str host, int port)}.  If IPv6, a\n        4-C{tuple} of (C{str host, int port, int ignored, int scope}).\n\n    @ivar createInternetSocket: Subclasses must implement this as a method to\n        create a python socket object of the appropriate address family and\n        socket type.\n    @type createInternetSocket: 0-argument callable returning\n        C{socket._socketobject}.\n    \"\"\"\n\n    _addressType = address.IPv4Address\n\n    def __init__(self, host, port, bindAddress, connector, reactor=None):\n        # BaseClient.__init__ is invoked later\n        self.connector = connector\n        self.addr = (host, port)\n\n        whenDone = self.resolveAddress\n        err = None\n        skt = None\n\n        if abstract.isIPAddress(host):\n            self._requiresResolution = False\n        elif abstract.isIPv6Address(host):\n            self._requiresResolution = False\n            self.addr = _resolveIPv6(host, port)\n            self.addressFamily = socket.AF_INET6\n            self._addressType = address.IPv6Address\n        else:\n            self._requiresResolution = True\n        try:\n            skt = self.createInternetSocket()\n        except socket.error as se:\n            err = error.ConnectBindError(se.args[0], se.args[1])\n            whenDone = None\n        if whenDone and bindAddress is not None:\n            try:\n                if abstract.isIPv6Address(bindAddress[0]):\n                    bindinfo = _resolveIPv6(*bindAddress)\n                else:\n                    bindinfo = bindAddress\n                skt.bind(bindinfo)\n            except socket.error as se:\n                err = error.ConnectBindError(se.args[0], se.args[1])\n                whenDone = None\n        self._finishInit(whenDone, skt, err, reactor)\n\n\n    def getHost(self):\n        \"\"\"\n        Returns an L{IPv4Address} or L{IPv6Address}.\n\n        This indicates the address from which I am connecting.\n        \"\"\"\n        return self._addressType('TCP', *_getsockname(self.socket))\n\n\n    def getPeer(self):\n        \"\"\"\n        Returns an L{IPv4Address} or L{IPv6Address}.\n\n        This indicates the address that I am connected to.\n        \"\"\"\n        return self._addressType('TCP', *self.realAddress)\n\n\n    def __repr__(self):\n        s = '<%s to %s at %x>' % (self.__class__, self.addr, id(self))\n        return s\n\n\n\nclass Client(_BaseTCPClient, BaseClient):\n    \"\"\"\n    A transport for a TCP protocol; either TCPv4 or TCPv6.\n\n    Do not create these directly; use L{IReactorTCP.connectTCP}.\n    \"\"\"\n\n\n\nclass Server(_TLSServerMixin, Connection):\n    \"\"\"\n    Serverside socket-stream connection class.\n\n    This is a serverside network connection transport; a socket which came from\n    an accept() on a server.\n\n    @ivar _base: L{Connection}, which is the base class of this class which has\n        all of the useful file descriptor methods.  This is used by\n        L{_TLSServerMixin} to call the right methods to directly manipulate the\n        transport, as is necessary for writing TLS-encrypted bytes (whereas\n        those methods on L{Server} will go through another layer of TLS if it\n        has been enabled).\n    \"\"\"\n    _base = Connection\n\n    _addressType = address.IPv4Address\n\n    def __init__(self, sock, protocol, client, server, sessionno, reactor):\n        \"\"\"\n        Server(sock, protocol, client, server, sessionno)\n\n        Initialize it with a socket, a protocol, a descriptor for my peer (a\n        tuple of host, port describing the other end of the connection), an\n        instance of Port, and a session number.\n        \"\"\"\n        Connection.__init__(self, sock, protocol, reactor)\n        if len(client) != 2:\n            self._addressType = address.IPv6Address\n        self.server = server\n        self.client = client\n        self.sessionno = sessionno\n        self.hostname = client[0]\n\n        logPrefix = self._getLogPrefix(self.protocol)\n        self.logstr = \"%s,%s,%s\" % (logPrefix,\n                                    sessionno,\n                                    self.hostname)\n        if self.server is not None:\n            self.repstr = \"<%s #%s on %s>\" % (self.protocol.__class__.__name__,\n                                              self.sessionno,\n                                              self.server._realPortNumber)\n        self.startReading()\n        self.connected = 1\n\n    def __repr__(self):\n        \"\"\"\n        A string representation of this connection.\n        \"\"\"\n        return self.repstr\n\n\n    @classmethod\n    def _fromConnectedSocket(cls, fileDescriptor, addressFamily, factory,\n                             reactor):\n        \"\"\"\n        Create a new L{Server} based on an existing connected I{SOCK_STREAM}\n        socket.\n\n        Arguments are the same as to L{Server.__init__}, except where noted.\n\n        @param fileDescriptor: An integer file descriptor associated with a\n            connected socket.  The socket must be in non-blocking mode.  Any\n            additional attributes desired, such as I{FD_CLOEXEC}, must also be\n            set already.\n\n        @param addressFamily: The address family (sometimes called I{domain})\n            of the existing socket.  For example, L{socket.AF_INET}.\n\n        @return: A new instance of C{cls} wrapping the socket given by\n            C{fileDescriptor}.\n        \"\"\"\n        addressType = address.IPv4Address\n        if addressFamily == socket.AF_INET6:\n            addressType = address.IPv6Address\n        skt = socket.fromfd(fileDescriptor, addressFamily, socket.SOCK_STREAM)\n        addr = _getpeername(skt)\n        protocolAddr = addressType('TCP', *addr)\n        localPort = skt.getsockname()[1]\n\n        protocol = factory.buildProtocol(protocolAddr)\n        if protocol is None:\n            skt.close()\n            return\n\n        self = cls(skt, protocol, addr, None, addr[1], reactor)\n        self.repstr = \"<%s #%s on %s>\" % (\n            self.protocol.__class__.__name__, self.sessionno, localPort)\n        protocol.makeConnection(self)\n        return self\n\n\n    def getHost(self):\n        \"\"\"\n        Returns an L{IPv4Address} or L{IPv6Address}.\n\n        This indicates the server's address.\n        \"\"\"\n        addr = _getsockname(self.socket)\n        return self._addressType('TCP', *addr)\n\n\n    def getPeer(self):\n        \"\"\"\n        Returns an L{IPv4Address} or L{IPv6Address}.\n\n        This indicates the client's address.\n        \"\"\"\n        return self._addressType('TCP', *self.client)\n\n\n\nclass _IFileDescriptorReservation(Interface):\n    \"\"\"\n    An open file that represents an emergency reservation in the\n    process' file descriptor table.  If L{Port} encounters C{EMFILE}\n    on C{accept(2)}, it can close this file descriptor, retry the\n    C{accept} so that the incoming connection occupies this file\n    descriptor's space, and then close that connection and reopen this\n    one.\n\n    Calling L{_IFileDescriptorReservation.reserve} attempts to open\n    the reserve file descriptor if it is not already open.\n    L{_IFileDescriptorReservation.available} returns L{True} if the\n    underlying file is open and its descriptor claimed.\n\n    L{_IFileDescriptorReservation} instances are context managers;\n    entering them releases the underlying file descriptor, while\n    exiting them attempts to reacquire it.  The block can take\n    advantage of the free slot in the process' file descriptor table\n    accept and close a client connection.\n\n    Because another thread might open a file descriptor between the\n    time the context manager is entered and the time C{accept} is\n    called, opening the reserve descriptor is best-effort only.\n    \"\"\"\n\n    def available():\n        \"\"\"\n        Is the reservation available?\n\n        @return: L{True} if the reserved file descriptor is open and\n            can thus be closed to allow a new file to be opened in its\n            place; L{False} if it is not open.\n        \"\"\"\n\n\n    def reserve():\n        \"\"\"\n        Attempt to open the reserved file descriptor; if this fails\n        because of C{EMFILE}, internal state is reset so that another\n        reservation attempt can be made.\n\n        @raises: Any exception except an L{OSError} or L{IOError}\n            whose errno is L{EMFILE}.\n        \"\"\"\n\n\n    def __enter__():\n        \"\"\"\n        Release the underlying file descriptor so that code within the\n        context manager can open a new file.\n        \"\"\"\n\n\n    def __exit__(excType, excValue, traceback):\n        \"\"\"\n        Attempt to re-open the reserved file descriptor.  See\n        L{reserve} for caveats.\n\n        @param excType: See L{object.__exit__}\n        @param excValue: See L{object.__exit__}\n        @param traceback: See L{object.__exit__}\n        \"\"\"\n\n\n\n@implementer(_IFileDescriptorReservation)\n@attr.s\nclass _FileDescriptorReservation(object):\n    \"\"\"\n    L{_IFileDescriptorReservation} implementation.\n\n    @ivar fileFactory: A factory that will be called to reserve a\n        file descriptor.\n    @type fileFactory: A L{callable} that accepts no arguments and\n        returns an object with a C{close} method.\n    \"\"\"\n    _log = Logger()\n\n    _fileFactory = attr.ib()\n    _fileDescriptor = attr.ib(init=False, default=None)\n\n\n    def available(self):\n        \"\"\"\n        See L{_IFileDescriptorReservation.available}.\n\n        @return: L{True} if the reserved file descriptor is open and\n            can thus be closed to allow a new file to be opened in its\n            place; L{False} if it is not open.\n        \"\"\"\n        return self._fileDescriptor is not None\n\n\n    def reserve(self):\n        \"\"\"\n        See L{_IFileDescriptorReservation.reserve}.\n        \"\"\"\n        if self._fileDescriptor is None:\n            try:\n                fileDescriptor = self._fileFactory()\n            except (IOError, OSError) as e:\n                if e.errno == EMFILE:\n                    self._log.failure(\n                        \"Could not reserve EMFILE recovery file descriptor.\")\n                else:\n                    raise\n            else:\n                self._fileDescriptor = fileDescriptor\n\n\n    def __enter__(self):\n        \"\"\"\n        See L{_IFileDescriptorReservation.__enter__}.\n        \"\"\"\n        if self._fileDescriptor is None:\n            raise RuntimeError(\n                \"No file reserved.  Have you called my reserve method?\")\n        self._fileDescriptor.close()\n        self._fileDescriptor = None\n\n\n    def __exit__(self, excValue, excType, traceback):\n        \"\"\"\n        See L{_IFileDescriptorReservation.__exit__}.\n        \"\"\"\n        try:\n            self.reserve()\n        except Exception:\n            self._log.failure(\n                \"Could not re-reserve EMFILE recovery file descriptor.\")\n\n\n\n@implementer(_IFileDescriptorReservation)\nclass _NullFileDescriptorReservation(object):\n    \"\"\"\n    A null implementation of L{_IFileDescriptorReservation}.\n    \"\"\"\n\n    def available(self):\n        \"\"\"\n        The reserved file is never available.  See\n        L{_IFileDescriptorReservation.available}.\n\n        @return: L{False}\n        \"\"\"\n        return False\n\n\n    def reserve(self):\n        \"\"\"\n        Do nothing.  See L{_IFileDescriptorReservation.reserve}.\n        \"\"\"\n\n\n    def __enter__(self):\n        \"\"\"\n        Do nothing. See L{_IFileDescriptorReservation.__enter__}\n\n        @return: L{False}\n        \"\"\"\n\n\n    def __exit__(self, excValue, excType, traceback):\n        \"\"\"\n        Do nothing.  See L{_IFileDescriptorReservation.__exit__}.\n\n        @param excType: See L{object.__exit__}\n        @param excValue: See L{object.__exit__}\n        @param traceback: See L{object.__exit__}\n        \"\"\"\n\n\n\n# Don't keep a reserve file descriptor for coping with file descriptor\n# exhaustion on Windows.\n\n# WSAEMFILE occurs when a process has run out of memory, not when a\n# specific limit has been reached.  Windows sockets are handles, which\n# differ from UNIX's file descriptors in that they can refer to any\n# \"named kernel object\", including user interface resources like menu\n# and icons.  The generality of handles results in a much higher limit\n# than UNIX imposes on file descriptors: a single Windows process can\n# allocate up to 16,777,216 handles.  Because they're indexes into a\n# three level table whose upper two layers are allocated from\n# swappable pages, handles compete for heap space with other kernel\n# objects, not with each other.  Closing a given socket handle may not\n# release enough memory to allow the process to make progress.\n#\n# This fundamental difference between file descriptors and handles\n# makes a reserve file descriptor useless on Windows.  Note that other\n# event loops, such as libuv and libevent, also do not special case\n# WSAEMFILE.\n#\n# For an explanation of handles, see the \"Object Manager\"\n# (pp. 140-175) section of\n#\n# Windows Internals, Part 1: Covering Windows Server 2008 R2 and\n# Windows 7 (6th ed.)\n# Mark E. Russinovich, David A. Solomon, and Alex\n# Ionescu. 2012. Microsoft Press.\nif platformType == 'win32':\n    _reservedFD = _NullFileDescriptorReservation()\nelse:\n    _reservedFD = _FileDescriptorReservation(lambda: open(os.devnull))\n\n\n# Linux and other UNIX-like operating systems return EMFILE when a\n# process has reached its soft limit of file descriptors. *BSD and\n# Win32 raise (WSA)ENOBUFS when socket limits are reached.  Linux can\n# give ENFILE if the system is out of inodes, or ENOMEM if there is\n# insufficient memory to allocate a new dentry.  ECONNABORTED is\n# documented as possible on all relevant platforms (Linux, Windows,\n# macOS, and the BSDs) but occurs only on the BSDs.  It occurs when a\n# client sends a FIN or RST after the server sends a SYN|ACK but\n# before application code calls accept(2).  On Linux, calling\n# accept(2) on such a listener returns a connection that fails as\n# though the it were terminated after being fully established.  This\n# appears to be an implementation choice (see inet_accept in\n# inet/ipv4/af_inet.c).  On macOS, such a listener is not considered\n# readable, so accept(2) will never be called.  Calling accept(2) on\n# such a listener, however, does not return at all.\n_ACCEPT_ERRORS = (EMFILE, ENOBUFS, ENFILE, ENOMEM, ECONNABORTED)\n\n\n\n@attr.s\nclass _BuffersLogs(object):\n    \"\"\"\n    A context manager that buffers any log events until after its\n    block exits.\n\n    @ivar _namespace: The namespace of the buffered events.\n    @type _namespace: L{str}.\n\n    @ivar _observer: The observer to which buffered log events will be\n        written\n    @type _observer: L{twisted.logger.ILogObserver}.\n    \"\"\"\n    _namespace = attr.ib()\n    _observer = attr.ib()\n    _logs = attr.ib(default=attr.Factory(list))\n\n    def __enter__(self):\n        \"\"\"\n        Enter a log buffering context.\n\n        @return: A logger that buffers log events.\n        @rtype: L{Logger}.\n        \"\"\"\n        return Logger(namespace=self._namespace, observer=self._logs.append)\n\n\n    def __exit__(self, excValue, excType, traceback):\n        \"\"\"\n        Exit a log buffering context and log all buffered events to\n        the provided observer.\n\n        @param excType: See L{object.__exit__}\n        @param excValue: See L{object.__exit__}\n        @param traceback: See L{object.__exit__}\n        \"\"\"\n        for event in self._logs:\n            self._observer(event)\n\n\n\ndef _accept(logger, accepts, listener, reservedFD):\n    \"\"\"\n    Return a generator that yields client sockets from the provided\n    listening socket until there are none left or an unrecoverable\n    error occurs.\n\n    @param logger: A logger to which C{accept}-related events will be\n        logged.  This should not log to arbitrary observers that might\n        open a file descriptor to avoid claiming the C{EMFILE} file\n        descriptor on UNIX-like systems.\n    @type logger: L{Logger}\n\n    @param accepts: An iterable iterated over to limit the number\n        consecutive C{accept}s.\n    @type accepts: An iterable.\n\n    @param listener: The listening socket.\n    @type listener: L{socket.socket}\n\n    @param reservedFD: A reserved file descriptor that can be used to\n        recover from C{EMFILE} on UNIX-like systems.\n    @type reservedFD: L{_IFileDescriptorReservation}\n\n    @return: A generator that yields C{(socket, addr)} tuples from\n        L{socket.socket.accept}\n    \"\"\"\n    for _ in accepts:\n        try:\n            client, address = listener.accept()\n        except socket.error as e:\n            if e.args[0] in (EWOULDBLOCK, EAGAIN):\n                # No more clients.\n                return\n            elif e.args[0] == EPERM:\n                # Netfilter on Linux may have rejected the\n                # connection, but we get told to try to accept()\n                # anyway.\n                continue\n            elif e.args[0] == EMFILE and reservedFD.available():\n                # Linux and other UNIX-like operating systems return\n                # EMFILE when a process has reached its soft limit of\n                # file descriptors.  The reserved file descriptor is\n                # available, so it can be released to free up a\n                # descriptor for use by listener.accept()'s clients.\n                # Each client socket will be closed until the listener\n                # returns EAGAIN.\n                logger.info(\"EMFILE encountered;\"\n                            \" releasing reserved file descriptor.\")\n                # The following block should not run arbitrary code\n                # that might acquire its own file descriptor.\n                with reservedFD:\n                    clientsToClose = _accept(\n                        logger, accepts, listener, reservedFD)\n                    for clientToClose, closedAddress in clientsToClose:\n                        clientToClose.close()\n                        logger.info(\"EMFILE recovery:\"\n                                    \" Closed socket from {address}\",\n                                    address=closedAddress)\n                    logger.info(\n                        \"Re-reserving EMFILE recovery file descriptor.\")\n                return\n            elif e.args[0] in _ACCEPT_ERRORS:\n                logger.info(\"Could not accept new connection ({acceptError})\",\n                            acceptError=errorcode[e.args[0]])\n                return\n            else:\n                raise\n        else:\n            yield client, address\n\n\n\n@implementer(interfaces.IListeningPort)\nclass Port(base.BasePort, _SocketCloser):\n    \"\"\"\n    A TCP server port, listening for connections.\n\n    When a connection is accepted, this will call a factory's buildProtocol\n    with the incoming address as an argument, according to the specification\n    described in L{twisted.internet.interfaces.IProtocolFactory}.\n\n    If you wish to change the sort of transport that will be used, the\n    C{transport} attribute will be called with the signature expected for\n    C{Server.__init__}, so it can be replaced.\n\n    @ivar deferred: a deferred created when L{stopListening} is called, and\n        that will fire when connection is lost. This is not to be used it\n        directly: prefer the deferred returned by L{stopListening} instead.\n    @type deferred: L{defer.Deferred}\n\n    @ivar disconnecting: flag indicating that the L{stopListening} method has\n        been called and that no connections should be accepted anymore.\n    @type disconnecting: C{bool}\n\n    @ivar connected: flag set once the listen has successfully been called on\n        the socket.\n    @type connected: C{bool}\n\n    @ivar _type: A string describing the connections which will be created by\n        this port.  Normally this is C{\"TCP\"}, since this is a TCP port, but\n        when the TLS implementation re-uses this class it overrides the value\n        with C{\"TLS\"}.  Only used for logging.\n\n    @ivar _preexistingSocket: If not L{None}, a L{socket.socket} instance which\n        was created and initialized outside of the reactor and will be used to\n        listen for connections (instead of a new socket being created by this\n        L{Port}).\n    \"\"\"\n\n    socketType = socket.SOCK_STREAM\n\n    transport = Server\n    sessionno = 0\n    interface = ''\n    backlog = 50\n\n    _type = 'TCP'\n\n    # Actual port number being listened on, only set to a non-None\n    # value when we are actually listening.\n    _realPortNumber = None\n\n    # An externally initialized socket that we will use, rather than creating\n    # our own.\n    _preexistingSocket = None\n\n    addressFamily = socket.AF_INET\n    _addressType = address.IPv4Address\n    _logger = Logger()\n\n    def __init__(self, port, factory, backlog=50, interface='', reactor=None):\n        \"\"\"Initialize with a numeric port to listen on.\n        \"\"\"\n        base.BasePort.__init__(self, reactor=reactor)\n        self.port = port\n        self.factory = factory\n        self.backlog = backlog\n        if abstract.isIPv6Address(interface):\n            self.addressFamily = socket.AF_INET6\n            self._addressType = address.IPv6Address\n        self.interface = interface\n\n\n    @classmethod\n    def _fromListeningDescriptor(cls, reactor, fd, addressFamily, factory):\n        \"\"\"\n        Create a new L{Port} based on an existing listening I{SOCK_STREAM}\n        socket.\n\n        Arguments are the same as to L{Port.__init__}, except where noted.\n\n        @param fd: An integer file descriptor associated with a listening\n            socket.  The socket must be in non-blocking mode.  Any additional\n            attributes desired, such as I{FD_CLOEXEC}, must also be set already.\n\n        @param addressFamily: The address family (sometimes called I{domain}) of\n            the existing socket.  For example, L{socket.AF_INET}.\n\n        @return: A new instance of C{cls} wrapping the socket given by C{fd}.\n        \"\"\"\n        port = socket.fromfd(fd, addressFamily, cls.socketType)\n        interface = _getsockname(port)[0]\n        self = cls(None, factory, None, interface, reactor)\n        self._preexistingSocket = port\n        return self\n\n\n    def __repr__(self):\n        if self._realPortNumber is not None:\n            return \"<%s of %s on %s>\" % (self.__class__,\n                self.factory.__class__, self._realPortNumber)\n        else:\n            return \"<%s of %s (not listening)>\" % (self.__class__, self.factory.__class__)\n\n    def createInternetSocket(self):\n        s = base.BasePort.createInternetSocket(self)\n        if platformType == \"posix\" and sys.platform != \"cygwin\":\n            s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)\n        return s\n\n\n    def startListening(self):\n        \"\"\"Create and bind my socket, and begin listening on it.\n\n        This is called on unserialization, and must be called after creating a\n        server to begin listening on the specified port.\n        \"\"\"\n        _reservedFD.reserve()\n        if self._preexistingSocket is None:\n            # Create a new socket and make it listen\n            try:\n                skt = self.createInternetSocket()\n                if self.addressFamily == socket.AF_INET6:\n                    addr = _resolveIPv6(self.interface, self.port)\n                else:\n                    addr = (self.interface, self.port)\n                skt.bind(addr)\n            except socket.error as le:\n                raise CannotListenError(self.interface, self.port, le)\n            skt.listen(self.backlog)\n        else:\n            # Re-use the externally specified socket\n            skt = self._preexistingSocket\n            self._preexistingSocket = None\n            # Avoid shutting it down at the end.\n            self._shouldShutdown = False\n\n        # Make sure that if we listened on port 0, we update that to\n        # reflect what the OS actually assigned us.\n        self._realPortNumber = skt.getsockname()[1]\n\n        log.msg(\"%s starting on %s\" % (\n                self._getLogPrefix(self.factory), self._realPortNumber))\n\n        # The order of the next 5 lines is kind of bizarre.  If no one\n        # can explain it, perhaps we should re-arrange them.\n        self.factory.doStart()\n        self.connected = True\n        self.socket = skt\n        self.fileno = self.socket.fileno\n        self.numberAccepts = 100\n\n        self.startReading()\n\n    def _buildAddr(self, address):\n        return self._addressType('TCP', *address)\n\n    def doRead(self):\n        \"\"\"\n        Called when my socket is ready for reading.\n\n        This accepts a connection and calls self.protocol() to handle the\n        wire-level protocol.\n        \"\"\"\n        try:\n            if platformType == \"posix\":\n                numAccepts = self.numberAccepts\n            else:\n                # win32 event loop breaks if we do more than one accept()\n                # in an iteration of the event loop.\n                numAccepts = 1\n\n            with _BuffersLogs(self._logger.namespace,\n                              self._logger.observer) as bufferingLogger:\n                accepted = 0\n                clients = _accept(bufferingLogger,\n                                  range(numAccepts),\n                                  self.socket,\n                                  _reservedFD)\n\n                for accepted, (skt, addr) in enumerate(clients, 1):\n                    fdesc._setCloseOnExec(skt.fileno())\n\n                    if len(addr) == 4:\n                        # IPv6, make sure we get the scopeID if it\n                        # exists\n                        host = socket.getnameinfo(\n                            addr,\n                            socket.NI_NUMERICHOST | socket.NI_NUMERICSERV)\n                        addr = tuple([host[0]] + list(addr[1:]))\n\n                    protocol = self.factory.buildProtocol(\n                        self._buildAddr(addr))\n                    if protocol is None:\n                        skt.close()\n                        continue\n                    s = self.sessionno\n                    self.sessionno = s + 1\n                    transport = self.transport(\n                        skt, protocol, addr, self, s, self.reactor)\n                    protocol.makeConnection(transport)\n\n            # Scale our synchronous accept loop according to traffic\n            # Reaching our limit on consecutive accept calls indicates\n            # there might be still more clients to serve the next time\n            # the reactor calls us.  Prepare to accept some more.\n            if accepted == self.numberAccepts:\n                self.numberAccepts += 20\n            # Otherwise, don't attempt to accept any more clients than\n            # we just accepted or any less than 1.\n            else:\n                self.numberAccepts = max(1, accepted)\n        except BaseException:\n            # Note that in TLS mode, this will possibly catch SSL.Errors\n            # raised by self.socket.accept()\n            #\n            # There is no \"except SSL.Error:\" above because SSL may be\n            # None if there is no SSL support.  In any case, all the\n            # \"except SSL.Error:\" suite would probably do is log.deferr()\n            # and return, so handling it here works just as well.\n            log.deferr()\n\n    def loseConnection(self, connDone=failure.Failure(main.CONNECTION_DONE)):\n        \"\"\"\n        Stop accepting connections on this port.\n\n        This will shut down the socket and call self.connectionLost().  It\n        returns a deferred which will fire successfully when the port is\n        actually closed, or with a failure if an error occurs shutting down.\n        \"\"\"\n        self.disconnecting = True\n        self.stopReading()\n        if self.connected:\n            self.deferred = deferLater(\n                self.reactor, 0, self.connectionLost, connDone)\n            return self.deferred\n\n    stopListening = loseConnection\n\n    def _logConnectionLostMsg(self):\n        \"\"\"\n        Log message for closing port\n        \"\"\"\n        log.msg('(%s Port %s Closed)' % (self._type, self._realPortNumber))\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Cleans up the socket.\n        \"\"\"\n        self._logConnectionLostMsg()\n        self._realPortNumber = None\n\n        base.BasePort.connectionLost(self, reason)\n        self.connected = False\n        self._closeSocket(True)\n        del self.socket\n        del self.fileno\n\n        try:\n            self.factory.doStop()\n        finally:\n            self.disconnecting = False\n\n\n    def logPrefix(self):\n        \"\"\"Returns the name of my class, to prefix log entries with.\n        \"\"\"\n        return reflect.qual(self.factory.__class__)\n\n\n    def getHost(self):\n        \"\"\"\n        Return an L{IPv4Address} or L{IPv6Address} indicating the listening\n        address of this port.\n        \"\"\"\n        addr = _getsockname(self.socket)\n        return self._addressType('TCP', *addr)\n\n\n\nclass Connector(base.BaseConnector):\n    \"\"\"\n    A L{Connector} provides of L{twisted.internet.interfaces.IConnector} for\n    all POSIX-style reactors.\n\n    @ivar _addressType: the type returned by L{Connector.getDestination}.\n        Either L{IPv4Address} or L{IPv6Address}, depending on the type of\n        address.\n    @type _addressType: C{type}\n    \"\"\"\n    _addressType = address.IPv4Address\n\n    def __init__(self, host, port, factory, timeout, bindAddress, reactor=None):\n        if isinstance(port, _portNameType):\n            try:\n                port = socket.getservbyname(port, 'tcp')\n            except socket.error as e:\n                raise error.ServiceNameUnknownError(string=\"%s (%r)\" % (e, port))\n        self.host, self.port = host, port\n        if abstract.isIPv6Address(host):\n            self._addressType = address.IPv6Address\n        self.bindAddress = bindAddress\n        base.BaseConnector.__init__(self, factory, timeout, reactor)\n\n\n    def _makeTransport(self):\n        \"\"\"\n        Create a L{Client} bound to this L{Connector}.\n\n        @return: a new L{Client}\n        @rtype: L{Client}\n        \"\"\"\n        return Client(self.host, self.port, self.bindAddress, self, self.reactor)\n\n\n    def getDestination(self):\n        \"\"\"\n        @see: L{twisted.internet.interfaces.IConnector.getDestination}.\n        \"\"\"\n        return self._addressType('TCP', self.host, self.port)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet}.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/_awaittests.py.3only",
    "content": "# -*- test-case-name: twisted.internet.test.test_coroutines -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for C{await} support in Deferreds.\n\nThese tests can only work and be imported on Python 3.5+!\n\"\"\"\n\nimport types\n\nfrom twisted.python.failure import Failure\nfrom twisted.internet.defer import (\n    Deferred, maybeDeferred, ensureDeferred, fail\n)\nfrom twisted.trial.unittest import TestCase\nfrom twisted.internet.task import Clock\n\nclass SampleException(Exception):\n    \"\"\"\n    A specific sample exception for testing.\n    \"\"\"\n\n\nclass AwaitTests(TestCase):\n    \"\"\"\n    Tests for using Deferreds in conjunction with PEP-492.\n    \"\"\"\n    def test_awaitReturnsIterable(self):\n        \"\"\"\n        C{Deferred.__await__} returns an iterable.\n        \"\"\"\n        d = Deferred()\n        awaitedDeferred = d.__await__()\n        self.assertEqual(awaitedDeferred, iter(awaitedDeferred))\n\n\n    def test_ensureDeferred(self):\n        \"\"\"\n        L{ensureDeferred} will turn a coroutine into a L{Deferred}.\n        \"\"\"\n        async def run():\n            d = Deferred()\n            d.callback(\"bar\")\n            await d\n            res = await run2()\n            return res\n\n        async def run2():\n            d = Deferred()\n            d.callback(\"foo\")\n            res = await d\n            return res\n\n        # It's a coroutine...\n        r = run()\n        self.assertIsInstance(r, types.CoroutineType)\n\n        # Now it's a Deferred.\n        d = ensureDeferred(r)\n        self.assertIsInstance(d, Deferred)\n\n        # The Deferred has the result we want.\n        res = self.successResultOf(d)\n        self.assertEqual(res, \"foo\")\n\n\n    def test_basic(self):\n        \"\"\"\n        L{ensureDeferred} allows a function to C{await} on a L{Deferred}.\n        \"\"\"\n        async def run():\n            d = Deferred()\n            d.callback(\"foo\")\n            res = await d\n            return res\n\n        d = ensureDeferred(run())\n        res = self.successResultOf(d)\n        self.assertEqual(res, \"foo\")\n\n\n    def test_exception(self):\n        \"\"\"\n        An exception in a coroutine wrapped with L{ensureDeferred} will cause\n        the returned L{Deferred} to fire with a failure.\n        \"\"\"\n        async def run():\n            d = Deferred()\n            d.callback(\"foo\")\n            await d\n            raise ValueError(\"Oh no!\")\n\n        d = ensureDeferred(run())\n        res = self.failureResultOf(d)\n        self.assertEqual(type(res.value), ValueError)\n        self.assertEqual(res.value.args, (\"Oh no!\",))\n\n\n    def test_synchronousDeferredFailureTraceback(self):\n        \"\"\"\n        When a Deferred is awaited upon that has already failed with a Failure\n        that has a traceback, both the place that the synchronous traceback\n        comes from and the awaiting line are shown in the traceback.\n        \"\"\"\n        def raises():\n            raise SampleException()\n        it = maybeDeferred(raises)\n        async def doomed():\n            return await it\n        failure = self.failureResultOf(ensureDeferred(doomed()))\n\n        self.assertIn(\", in doomed\\n\", failure.getTraceback())\n        self.assertIn(\", in raises\\n\", failure.getTraceback())\n\n\n    def test_asyncDeferredFailureTraceback(self):\n        \"\"\"\n        When a Deferred is awaited upon that later fails with a Failure that\n        has a traceback, both the place that the synchronous traceback comes\n        from and the awaiting line are shown in the traceback.\n        \"\"\"\n        def returnsFailure():\n            try:\n                raise SampleException()\n            except SampleException:\n                return Failure()\n        it = Deferred()\n        async def doomed():\n            return await it\n        started = ensureDeferred(doomed())\n        self.assertNoResult(started)\n        it.errback(returnsFailure())\n        failure = self.failureResultOf(started)\n        self.assertIn(\", in doomed\\n\", failure.getTraceback())\n        self.assertIn(\", in returnsFailure\\n\", failure.getTraceback())\n\n\n    def test_twoDeep(self):\n        \"\"\"\n        A coroutine wrapped with L{ensureDeferred} that awaits a L{Deferred}\n        suspends its execution until the inner L{Deferred} fires.\n        \"\"\"\n        reactor = Clock()\n        sections = []\n\n        async def runone():\n            sections.append(2)\n            d = Deferred()\n            reactor.callLater(1, d.callback, 2)\n            await d\n            sections.append(3)\n            return \"Yay!\"\n\n\n        async def run():\n            sections.append(1)\n            result = await runone()\n            sections.append(4)\n            d = Deferred()\n            reactor.callLater(1, d.callback, 1)\n            await d\n            sections.append(5)\n            return result\n\n        d = ensureDeferred(run())\n\n        reactor.advance(0.9)\n        self.assertEqual(sections, [1, 2])\n\n        reactor.advance(0.1)\n        self.assertEqual(sections, [1, 2, 3, 4])\n\n        reactor.advance(0.9)\n        self.assertEqual(sections, [1, 2, 3, 4])\n\n        reactor.advance(0.1)\n        self.assertEqual(sections, [1, 2, 3, 4, 5])\n\n        res = self.successResultOf(d)\n        self.assertEqual(res, \"Yay!\")\n\n\n    def test_reraise(self):\n        \"\"\"\n        Awaiting an already failed Deferred will raise the exception.\n        \"\"\"\n        async def test():\n            try:\n                await fail(ValueError(\"Boom\"))\n            except ValueError as e:\n                self.assertEqual(e.args, (\"Boom\",))\n                return 1\n            return 0\n\n        res = self.successResultOf(ensureDeferred(test()))\n        self.assertEqual(res, 1)\n\n\n    def test_chained(self):\n        \"\"\"\n        Awaiting a paused & chained Deferred will give the result when it has\n        one.\n        \"\"\"\n        reactor = Clock()\n\n        async def test():\n            d = Deferred()\n            d2 = Deferred()\n            d.addCallback(lambda ignored: d2)\n\n            d.callback(None)\n            reactor.callLater(0, d2.callback, \"bye\")\n            return await d\n\n        d = ensureDeferred(test())\n        reactor.advance(0.1)\n\n        res = self.successResultOf(d)\n        self.assertEqual(res, \"bye\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/_posixifaces.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nPOSIX implementation of local network interface enumeration.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport sys, socket\n\nfrom socket import AF_INET, AF_INET6, inet_ntop\nfrom ctypes import (\n    CDLL, POINTER, Structure, c_char_p, c_ushort, c_int,\n    c_uint32, c_uint8, c_void_p, c_ubyte, pointer, cast)\nfrom ctypes.util import find_library\n\nfrom twisted.python.compat import _PY3, nativeString\n\nif _PY3:\n    # Once #6070 is implemented, this can be replaced with the implementation\n    # from that ticket:\n    def chr(i):\n        \"\"\"\n        Python 3 implementation of Python 2 chr(), i.e. convert an integer to\n        corresponding byte.\n        \"\"\"\n        return bytes([i])\n\n\nlibc = CDLL(find_library(\"c\"))\n\nif sys.platform.startswith('freebsd') or sys.platform == 'darwin':\n    _sockaddrCommon = [\n        (\"sin_len\", c_uint8),\n        (\"sin_family\", c_uint8),\n        ]\nelse:\n    _sockaddrCommon = [\n        (\"sin_family\", c_ushort),\n        ]\n\n\n\nclass in_addr(Structure):\n    _fields_ = [\n        (\"in_addr\", c_ubyte * 4),\n        ]\n\n\n\nclass in6_addr(Structure):\n    _fields_ = [\n        (\"in_addr\", c_ubyte * 16),\n        ]\n\n\n\nclass sockaddr(Structure):\n    _fields_ = _sockaddrCommon + [\n        (\"sin_port\", c_ushort),\n        ]\n\n\n\nclass sockaddr_in(Structure):\n    _fields_ = _sockaddrCommon + [\n        (\"sin_port\", c_ushort),\n        (\"sin_addr\", in_addr),\n        ]\n\n\n\nclass sockaddr_in6(Structure):\n    _fields_ = _sockaddrCommon + [\n        (\"sin_port\", c_ushort),\n        (\"sin_flowinfo\", c_uint32),\n        (\"sin_addr\", in6_addr),\n        ]\n\n\n\nclass ifaddrs(Structure):\n    pass\n\nifaddrs_p = POINTER(ifaddrs)\nifaddrs._fields_ = [\n    ('ifa_next', ifaddrs_p),\n    ('ifa_name', c_char_p),\n    ('ifa_flags', c_uint32),\n    ('ifa_addr', POINTER(sockaddr)),\n    ('ifa_netmask', POINTER(sockaddr)),\n    ('ifa_dstaddr', POINTER(sockaddr)),\n    ('ifa_data', c_void_p)]\n\ngetifaddrs = libc.getifaddrs\ngetifaddrs.argtypes = [POINTER(ifaddrs_p)]\ngetifaddrs.restype = c_int\n\nfreeifaddrs = libc.freeifaddrs\nfreeifaddrs.argtypes = [ifaddrs_p]\n\n\n\ndef _maybeCleanupScopeIndex(family, packed):\n    \"\"\"\n    On FreeBSD, kill the embedded interface indices in link-local scoped\n    addresses.\n\n    @param family: The address family of the packed address - one of the\n        I{socket.AF_*} constants.\n\n    @param packed: The packed representation of the address (ie, the bytes of a\n        I{in_addr} field).\n    @type packed: L{bytes}\n\n    @return: The packed address with any FreeBSD-specific extra bits cleared.\n    @rtype: L{bytes}\n\n    @see: U{https://twistedmatrix.com/trac/ticket/6843}\n    @see: U{http://www.freebsd.org/doc/en/books/developers-handbook/ipv6.html#ipv6-scope-index}\n\n    @note: Indications are that the need for this will be gone in FreeBSD >=10.\n    \"\"\"\n    if sys.platform.startswith('freebsd') and packed[:2] == b\"\\xfe\\x80\":\n        return packed[:2] + b\"\\x00\\x00\" + packed[4:]\n    return packed\n\n\n\ndef _interfaces():\n    \"\"\"\n    Call C{getifaddrs(3)} and return a list of tuples of interface name, address\n    family, and human-readable address representing its results.\n    \"\"\"\n    ifaddrs = ifaddrs_p()\n    if getifaddrs(pointer(ifaddrs)) < 0:\n        raise OSError()\n    results = []\n    try:\n        while ifaddrs:\n            if ifaddrs[0].ifa_addr:\n                family = ifaddrs[0].ifa_addr[0].sin_family\n                if family == AF_INET:\n                    addr = cast(ifaddrs[0].ifa_addr, POINTER(sockaddr_in))\n                elif family == AF_INET6:\n                    addr = cast(ifaddrs[0].ifa_addr, POINTER(sockaddr_in6))\n                else:\n                    addr = None\n\n                if addr:\n                    packed = b''.join(map(chr, addr[0].sin_addr.in_addr[:]))\n                    packed = _maybeCleanupScopeIndex(family, packed)\n                    results.append((\n                            ifaddrs[0].ifa_name,\n                            family,\n                            inet_ntop(family, packed)))\n\n            ifaddrs = ifaddrs[0].ifa_next\n    finally:\n        freeifaddrs(ifaddrs)\n    return results\n\n\n\ndef posixGetLinkLocalIPv6Addresses():\n    \"\"\"\n    Return a list of strings in colon-hex format representing all the link local\n    IPv6 addresses available on the system, as reported by I{getifaddrs(3)}.\n    \"\"\"\n    retList = []\n    for (interface, family, address) in _interfaces():\n        interface = nativeString(interface)\n        address = nativeString(address)\n        if family == socket.AF_INET6 and address.startswith('fe80:'):\n            retList.append('%s%%%s' % (address, interface))\n    return retList\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/_win32ifaces.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nWindows implementation of local network interface enumeration.\n\"\"\"\n\nfrom socket import socket, AF_INET6, SOCK_STREAM\nfrom ctypes import (\n    WinDLL, byref, create_string_buffer, create_unicode_buffer,\n    c_int, c_void_p,\n    POINTER, Structure, cast, wstring_at)\n\nWS2_32 = WinDLL('ws2_32')\n\nSOCKET = c_int\nDWORD = c_int\nLPVOID = c_void_p\nLPSOCKADDR = c_void_p\nLPWSAPROTOCOL_INFO = c_void_p\nLPTSTR = c_void_p\nLPDWORD = c_void_p\nLPWSAOVERLAPPED = c_void_p\nLPWSAOVERLAPPED_COMPLETION_ROUTINE = c_void_p\n\n# http://msdn.microsoft.com/en-us/library/ms741621(v=VS.85).aspx\n# int WSAIoctl(\n#         __in   SOCKET s,\n#         __in   DWORD dwIoControlCode,\n#         __in   LPVOID lpvInBuffer,\n#         __in   DWORD cbInBuffer,\n#         __out  LPVOID lpvOutBuffer,\n#         __in   DWORD cbOutBuffer,\n#         __out  LPDWORD lpcbBytesReturned,\n#         __in   LPWSAOVERLAPPED lpOverlapped,\n#         __in   LPWSAOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine\n#       );\nWSAIoctl = WS2_32.WSAIoctl\nWSAIoctl.argtypes = [\n    SOCKET, DWORD, LPVOID, DWORD, LPVOID, DWORD, LPDWORD,\n    LPWSAOVERLAPPED, LPWSAOVERLAPPED_COMPLETION_ROUTINE]\nWSAIoctl.restype = c_int\n\n# http://msdn.microsoft.com/en-us/library/ms741516(VS.85).aspx\n# INT WSAAPI WSAAddressToString(\n#         __in      LPSOCKADDR lpsaAddress,\n#         __in      DWORD dwAddressLength,\n#         __in_opt  LPWSAPROTOCOL_INFO lpProtocolInfo,\n#         __inout   LPTSTR lpszAddressString,\n#         __inout   LPDWORD lpdwAddressStringLength\n#       );\nWSAAddressToString = WS2_32.WSAAddressToStringW\nWSAAddressToString.argtypes = [\n    LPSOCKADDR, DWORD, LPWSAPROTOCOL_INFO, LPTSTR, LPDWORD]\nWSAAddressToString.restype = c_int\n\n\nSIO_ADDRESS_LIST_QUERY = 0x48000016\nWSAEFAULT = 10014\n\nclass SOCKET_ADDRESS(Structure):\n    _fields_ = [('lpSockaddr', c_void_p),\n                ('iSockaddrLength', c_int)]\n\n\n\ndef make_SAL(ln):\n    class SOCKET_ADDRESS_LIST(Structure):\n        _fields_ = [('iAddressCount', c_int),\n                    ('Address', SOCKET_ADDRESS * ln)]\n    return SOCKET_ADDRESS_LIST\n\n\n\ndef win32GetLinkLocalIPv6Addresses():\n    \"\"\"\n    Return a list of strings in colon-hex format representing all the link local\n    IPv6 addresses available on the system, as reported by\n    I{WSAIoctl}/C{SIO_ADDRESS_LIST_QUERY}.\n    \"\"\"\n    s = socket(AF_INET6, SOCK_STREAM)\n    size = 4096\n    retBytes = c_int()\n    for i in range(2):\n        buf = create_string_buffer(size)\n        ret = WSAIoctl(\n            s.fileno(),\n            SIO_ADDRESS_LIST_QUERY, 0, 0, buf, size, byref(retBytes), 0, 0)\n\n        # WSAIoctl might fail with WSAEFAULT, which means there was not enough\n        # space in the buffer we gave it.  There's no way to check the errno\n        # until Python 2.6, so we don't even try. :/ Maybe if retBytes is still\n        # 0 another error happened, though.\n        if ret and retBytes.value:\n            size = retBytes.value\n        else:\n            break\n\n    # If it failed, then we'll just have to give up.  Still no way to see why.\n    if ret:\n        raise RuntimeError(\"WSAIoctl failure\")\n\n    addrList = cast(buf, POINTER(make_SAL(0)))\n    addrCount = addrList[0].iAddressCount\n    addrList = cast(buf, POINTER(make_SAL(addrCount)))\n\n    addressStringBufLength = 1024\n    addressStringBuf = create_unicode_buffer(addressStringBufLength)\n\n    retList = []\n    for i in range(addrList[0].iAddressCount):\n        retBytes.value = addressStringBufLength\n        address = addrList[0].Address[i]\n        ret = WSAAddressToString(\n            address.lpSockaddr, address.iSockaddrLength, 0, addressStringBuf,\n            byref(retBytes))\n        if ret:\n            raise RuntimeError(\"WSAAddressToString failure\")\n        retList.append(wstring_at(addressStringBuf))\n    return [addr for addr in retList if '%' in addr]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/_yieldfromtests.py.3only",
    "content": "# -*- test-case-name: twisted.internet.test.test_coroutines -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for C{yield from} support in Deferreds.\n\nThese tests can only work and be imported on Python 3!\n\"\"\"\n\nimport types\n\nfrom twisted.internet.defer import Deferred, ensureDeferred, fail\nfrom twisted.trial.unittest import TestCase\nfrom twisted.internet.task import Clock\n\n\nclass YieldFromTests(TestCase):\n    \"\"\"\n    Tests for using Deferreds in conjunction with PEP-380.\n    \"\"\"\n\n    def test_ensureDeferred(self):\n        \"\"\"\n        L{ensureDeferred} will turn a coroutine into a L{Deferred}.\n        \"\"\"\n        def run():\n            d = Deferred()\n            d.callback(\"bar\")\n            yield from d\n            res = yield from run2()\n            return res\n\n        def run2():\n            d = Deferred()\n            d.callback(\"foo\")\n            res = yield from d\n            return res\n\n        # It's a generator...\n        r = run()\n        self.assertIsInstance(r, types.GeneratorType)\n\n        # Now it's a Deferred.\n        d = ensureDeferred(r)\n        self.assertIsInstance(d, Deferred)\n\n        # The Deferred has the result we want.\n        res = self.successResultOf(d)\n        self.assertEqual(res, \"foo\")\n\n\n    def test_basic(self):\n        \"\"\"\n        L{ensureDeferred} allows a function to C{yield from} a L{Deferred}.\n        \"\"\"\n        def run():\n            d = Deferred()\n            d.callback(\"foo\")\n            res = yield from d\n            return res\n\n        d = ensureDeferred(run())\n        res = self.successResultOf(d)\n        self.assertEqual(res, \"foo\")\n\n\n    def test_exception(self):\n        \"\"\"\n        An exception in a generator wrapped with L{ensureDeferred} will cause\n        the returned L{Deferred} to fire with a failure.\n        \"\"\"\n        def run():\n            d = Deferred()\n            d.callback(\"foo\")\n            yield from d\n            raise ValueError(\"Oh no!\")\n\n        d = ensureDeferred(run())\n        res = self.failureResultOf(d)\n        self.assertEqual(type(res.value), ValueError)\n        self.assertEqual(res.value.args, (\"Oh no!\",))\n\n\n    def test_twoDeep(self):\n        \"\"\"\n        An exception in a generator wrapped with L{ensureDeferred} will cause\n        the returned L{Deferred} to fire with a failure.\n        \"\"\"\n        reactor = Clock()\n        sections = []\n\n        def runone():\n            sections.append(2)\n            d = Deferred()\n            reactor.callLater(1, d.callback, None)\n            yield from d\n            sections.append(3)\n            return \"Yay!\"\n\n\n        def run():\n            sections.append(1)\n            result = yield from runone()\n            sections.append(4)\n            d = Deferred()\n            reactor.callLater(1, d.callback, None)\n            yield from d\n            sections.append(5)\n            return result\n\n        d = ensureDeferred(run())\n\n        reactor.advance(0.9)\n        self.assertEqual(sections, [1, 2])\n\n        reactor.advance(0.1)\n        self.assertEqual(sections, [1, 2, 3, 4])\n\n        reactor.advance(0.9)\n        self.assertEqual(sections, [1, 2, 3, 4])\n\n        reactor.advance(0.1)\n        self.assertEqual(sections, [1, 2, 3, 4, 5])\n\n        res = self.successResultOf(d)\n        self.assertEqual(res, \"Yay!\")\n\n\n    def test_reraise(self):\n        \"\"\"\n        Yielding from an already failed Deferred will raise the exception.\n        \"\"\"\n        def test():\n            try:\n                yield from fail(ValueError(\"Boom\"))\n            except ValueError as e:\n                self.assertEqual(e.args, (\"Boom\",))\n                return 1\n            return 0\n\n        res = self.successResultOf(ensureDeferred(test()))\n        self.assertEqual(res, 1)\n\n\n    def test_chained(self):\n        \"\"\"\n        Yielding from a paused & chained Deferred will give the result when it\n        has one.\n        \"\"\"\n        reactor = Clock()\n\n        def test():\n            d = Deferred()\n            d2 = Deferred()\n            d.addCallback(lambda ignored: d2)\n\n            d.callback(None)\n            reactor.callLater(0, d2.callback, \"bye\")\n            res = yield from d\n            return res\n\n        d = ensureDeferred(test())\n        reactor.advance(0.1)\n\n        res = self.successResultOf(d)\n        self.assertEqual(res, \"bye\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/fake_CAs/chain.pem",
    "content": "\nThis is a concatenation of thing1.pem and thing2.pem.\n\n-----BEGIN CERTIFICATE-----\nMIICwjCCAisCAgTSMA0GCSqGSIb3DQEBBAUAMIGoMREwDwYDVQQLEwhTZWN1cml0\neTEcMBoGA1UEChMTVHdpc3RlZCBNYXRyaXggTGFiczEeMBwGA1UEAxMVZmFrZS1j\nYS0xLmV4YW1wbGUuY29tMREwDwYDVQQIEwhOZXcgWW9yazELMAkGA1UEBhMCVVMx\nIjAgBgkqhkiG9w0BCQEWE25vcmVwbHlAZXhhbXBsZS5jb20xETAPBgNVBAcTCE5l\ndyBZb3JrMB4XDTEwMDkyMTAxMjUxNFoXDTExMDkyMTAxMjUxNFowgagxETAPBgNV\nBAsTCFNlY3VyaXR5MRwwGgYDVQQKExNUd2lzdGVkIE1hdHJpeCBMYWJzMR4wHAYD\nVQQDExVmYWtlLWNhLTEuZXhhbXBsZS5jb20xETAPBgNVBAgTCE5ldyBZb3JrMQsw\nCQYDVQQGEwJVUzEiMCAGCSqGSIb3DQEJARYTbm9yZXBseUBleGFtcGxlLmNvbTER\nMA8GA1UEBxMITmV3IFlvcmswgZ8wDQYJKoZIhvcNAQEBBQADgY0AMIGJAoGBALRb\nVqC0CsaFgq1vbwPfs8zoP3ZYC/0sPMv0RJN+f3Dc7Q6YgNHS7o7TM3uAy/McADeW\nrwVuNJGe9k+4ZBHysmBH1sG64fHT5TlK9saPcUQqkubSWj4cKSDtVbQERWqC5Dy+\nqTQeZGYoPEMlnRXgMpST04DG//Dgzi4PYqUOjwxTAgMBAAEwDQYJKoZIhvcNAQEE\nBQADgYEAqNEdMXWEs8Co76wxL3/cSV3MjiAroVxJdI/3EzlnfPi1JeibbdWw31fC\nbn6428KTjjfhS31zo1yHG3YNXFEJXRscwLAH7ogz5kJwZMy/oS/96EFM10bkNwkK\nv+nWKN8i3t/E5TEIl3BPN8tchtWmH0rycVuzs5LwaewwR1AnUE4=\n-----END CERTIFICATE-----\n-----BEGIN CERTIFICATE-----\nMIICwjCCAisCAgTSMA0GCSqGSIb3DQEBBAUAMIGoMREwDwYDVQQLEwhTZWN1cml0\neTEcMBoGA1UEChMTVHdpc3RlZCBNYXRyaXggTGFiczEeMBwGA1UEAxMVZmFrZS1j\nYS0yLmV4YW1wbGUuY29tMREwDwYDVQQIEwhOZXcgWW9yazELMAkGA1UEBhMCVVMx\nIjAgBgkqhkiG9w0BCQEWE25vcmVwbHlAZXhhbXBsZS5jb20xETAPBgNVBAcTCE5l\ndyBZb3JrMB4XDTEwMDkyMTAxMjUzMVoXDTExMDkyMTAxMjUzMVowgagxETAPBgNV\nBAsTCFNlY3VyaXR5MRwwGgYDVQQKExNUd2lzdGVkIE1hdHJpeCBMYWJzMR4wHAYD\nVQQDExVmYWtlLWNhLTIuZXhhbXBsZS5jb20xETAPBgNVBAgTCE5ldyBZb3JrMQsw\nCQYDVQQGEwJVUzEiMCAGCSqGSIb3DQEJARYTbm9yZXBseUBleGFtcGxlLmNvbTER\nMA8GA1UEBxMITmV3IFlvcmswgZ8wDQYJKoZIhvcNAQEBBQADgY0AMIGJAoGBAMNn\nb3EcKqBedQed1qJC4uGVx8PYmn2vxL3QwCVW1w0VjpZXyhCq/2VrYBhJAXRzpfvE\ndCqhtJKcdifwavUrTfr4yXu1MvWA0YuaAkj1TbmlHHQYACf3h+MPOXroYzhT72bO\nFSSLDWuitj0ozR+2Fk15QwLWUxaYLmwylxXAf7vpAgMBAAEwDQYJKoZIhvcNAQEE\nBQADgYEADB2N6VHHhm5M2rJqqGDXMm2dU+7abxiuN+PUygN2LXIsqdGBS6U7/rta\nlJNVeRaM423c8imfuklkIBG9Msn5+xm1xIMIULoi/efActDLbsX1x6IyHQrG5aDP\n/RMKBio9RjS8ajgSwyYVUZiCZBsn/T0/JS8K61YLpiv4Tg8uXmM=\n-----END CERTIFICATE-----\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/fake_CAs/not-a-certificate",
    "content": "This file is not a certificate; it is present to make sure that it will be skipped.\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/fake_CAs/thing1.pem",
    "content": "\nThis is a self-signed certificate authority certificate to be used in tests.\n\nIt was created with the following command: \ncertcreate -f thing1.pem -h fake-ca-1.example.com -e noreply@example.com \\\n           -S 1234 -o 'Twisted Matrix Labs'\n\n'certcreate' may be obtained from <http://divmod.org/trac/wiki/DivmodEpsilon>\n\n-----BEGIN CERTIFICATE-----\nMIICwjCCAisCAgTSMA0GCSqGSIb3DQEBBAUAMIGoMREwDwYDVQQLEwhTZWN1cml0\neTEcMBoGA1UEChMTVHdpc3RlZCBNYXRyaXggTGFiczEeMBwGA1UEAxMVZmFrZS1j\nYS0xLmV4YW1wbGUuY29tMREwDwYDVQQIEwhOZXcgWW9yazELMAkGA1UEBhMCVVMx\nIjAgBgkqhkiG9w0BCQEWE25vcmVwbHlAZXhhbXBsZS5jb20xETAPBgNVBAcTCE5l\ndyBZb3JrMB4XDTEwMDkyMTAxMjUxNFoXDTExMDkyMTAxMjUxNFowgagxETAPBgNV\nBAsTCFNlY3VyaXR5MRwwGgYDVQQKExNUd2lzdGVkIE1hdHJpeCBMYWJzMR4wHAYD\nVQQDExVmYWtlLWNhLTEuZXhhbXBsZS5jb20xETAPBgNVBAgTCE5ldyBZb3JrMQsw\nCQYDVQQGEwJVUzEiMCAGCSqGSIb3DQEJARYTbm9yZXBseUBleGFtcGxlLmNvbTER\nMA8GA1UEBxMITmV3IFlvcmswgZ8wDQYJKoZIhvcNAQEBBQADgY0AMIGJAoGBALRb\nVqC0CsaFgq1vbwPfs8zoP3ZYC/0sPMv0RJN+f3Dc7Q6YgNHS7o7TM3uAy/McADeW\nrwVuNJGe9k+4ZBHysmBH1sG64fHT5TlK9saPcUQqkubSWj4cKSDtVbQERWqC5Dy+\nqTQeZGYoPEMlnRXgMpST04DG//Dgzi4PYqUOjwxTAgMBAAEwDQYJKoZIhvcNAQEE\nBQADgYEAqNEdMXWEs8Co76wxL3/cSV3MjiAroVxJdI/3EzlnfPi1JeibbdWw31fC\nbn6428KTjjfhS31zo1yHG3YNXFEJXRscwLAH7ogz5kJwZMy/oS/96EFM10bkNwkK\nv+nWKN8i3t/E5TEIl3BPN8tchtWmH0rycVuzs5LwaewwR1AnUE4=\n-----END CERTIFICATE-----\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/fake_CAs/thing2-duplicate.pem",
    "content": "\nThis is a self-signed certificate authority certificate to be used in tests.\n\nIt was created with the following command: \ncertcreate -f thing2.pem -h fake-ca-2.example.com -e noreply@example.com \\\n           -S 1234 -o 'Twisted Matrix Labs'\n\n'certcreate' may be obtained from <http://divmod.org/trac/wiki/DivmodEpsilon>\n\n-----BEGIN CERTIFICATE-----\nMIICwjCCAisCAgTSMA0GCSqGSIb3DQEBBAUAMIGoMREwDwYDVQQLEwhTZWN1cml0\neTEcMBoGA1UEChMTVHdpc3RlZCBNYXRyaXggTGFiczEeMBwGA1UEAxMVZmFrZS1j\nYS0yLmV4YW1wbGUuY29tMREwDwYDVQQIEwhOZXcgWW9yazELMAkGA1UEBhMCVVMx\nIjAgBgkqhkiG9w0BCQEWE25vcmVwbHlAZXhhbXBsZS5jb20xETAPBgNVBAcTCE5l\ndyBZb3JrMB4XDTEwMDkyMTAxMjUzMVoXDTExMDkyMTAxMjUzMVowgagxETAPBgNV\nBAsTCFNlY3VyaXR5MRwwGgYDVQQKExNUd2lzdGVkIE1hdHJpeCBMYWJzMR4wHAYD\nVQQDExVmYWtlLWNhLTIuZXhhbXBsZS5jb20xETAPBgNVBAgTCE5ldyBZb3JrMQsw\nCQYDVQQGEwJVUzEiMCAGCSqGSIb3DQEJARYTbm9yZXBseUBleGFtcGxlLmNvbTER\nMA8GA1UEBxMITmV3IFlvcmswgZ8wDQYJKoZIhvcNAQEBBQADgY0AMIGJAoGBAMNn\nb3EcKqBedQed1qJC4uGVx8PYmn2vxL3QwCVW1w0VjpZXyhCq/2VrYBhJAXRzpfvE\ndCqhtJKcdifwavUrTfr4yXu1MvWA0YuaAkj1TbmlHHQYACf3h+MPOXroYzhT72bO\nFSSLDWuitj0ozR+2Fk15QwLWUxaYLmwylxXAf7vpAgMBAAEwDQYJKoZIhvcNAQEE\nBQADgYEADB2N6VHHhm5M2rJqqGDXMm2dU+7abxiuN+PUygN2LXIsqdGBS6U7/rta\nlJNVeRaM423c8imfuklkIBG9Msn5+xm1xIMIULoi/efActDLbsX1x6IyHQrG5aDP\n/RMKBio9RjS8ajgSwyYVUZiCZBsn/T0/JS8K61YLpiv4Tg8uXmM=\n-----END CERTIFICATE-----\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/fake_CAs/thing2.pem",
    "content": "\nThis is a self-signed certificate authority certificate to be used in tests.\n\nIt was created with the following command: \ncertcreate -f thing2.pem -h fake-ca-2.example.com -e noreply@example.com \\\n           -S 1234 -o 'Twisted Matrix Labs'\n\n'certcreate' may be obtained from <http://divmod.org/trac/wiki/DivmodEpsilon>\n\n-----BEGIN CERTIFICATE-----\nMIICwjCCAisCAgTSMA0GCSqGSIb3DQEBBAUAMIGoMREwDwYDVQQLEwhTZWN1cml0\neTEcMBoGA1UEChMTVHdpc3RlZCBNYXRyaXggTGFiczEeMBwGA1UEAxMVZmFrZS1j\nYS0yLmV4YW1wbGUuY29tMREwDwYDVQQIEwhOZXcgWW9yazELMAkGA1UEBhMCVVMx\nIjAgBgkqhkiG9w0BCQEWE25vcmVwbHlAZXhhbXBsZS5jb20xETAPBgNVBAcTCE5l\ndyBZb3JrMB4XDTEwMDkyMTAxMjUzMVoXDTExMDkyMTAxMjUzMVowgagxETAPBgNV\nBAsTCFNlY3VyaXR5MRwwGgYDVQQKExNUd2lzdGVkIE1hdHJpeCBMYWJzMR4wHAYD\nVQQDExVmYWtlLWNhLTIuZXhhbXBsZS5jb20xETAPBgNVBAgTCE5ldyBZb3JrMQsw\nCQYDVQQGEwJVUzEiMCAGCSqGSIb3DQEJARYTbm9yZXBseUBleGFtcGxlLmNvbTER\nMA8GA1UEBxMITmV3IFlvcmswgZ8wDQYJKoZIhvcNAQEBBQADgY0AMIGJAoGBAMNn\nb3EcKqBedQed1qJC4uGVx8PYmn2vxL3QwCVW1w0VjpZXyhCq/2VrYBhJAXRzpfvE\ndCqhtJKcdifwavUrTfr4yXu1MvWA0YuaAkj1TbmlHHQYACf3h+MPOXroYzhT72bO\nFSSLDWuitj0ozR+2Fk15QwLWUxaYLmwylxXAf7vpAgMBAAEwDQYJKoZIhvcNAQEE\nBQADgYEADB2N6VHHhm5M2rJqqGDXMm2dU+7abxiuN+PUygN2LXIsqdGBS6U7/rta\nlJNVeRaM423c8imfuklkIBG9Msn5+xm1xIMIULoi/efActDLbsX1x6IyHQrG5aDP\n/RMKBio9RjS8ajgSwyYVUZiCZBsn/T0/JS8K61YLpiv4Tg8uXmM=\n-----END CERTIFICATE-----\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/fakeendpoint.py",
    "content": "# -*- test-case-name: twisted.internet.test.test_endpoints -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nFake client and server endpoint string parser plugins for testing purposes.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom zope.interface.declarations import implementer\nfrom twisted.plugin import IPlugin\nfrom twisted.internet.interfaces import (\n    IStreamClientEndpoint, IStreamServerEndpoint,\n    IStreamServerEndpointStringParser,\n    IStreamClientEndpointStringParserWithReactor)\n\n\n@implementer(IPlugin)\nclass PluginBase(object):\n\n    def __init__(self, pfx):\n        self.prefix = pfx\n\n\n\n@implementer(IStreamClientEndpointStringParserWithReactor)\nclass FakeClientParserWithReactor(PluginBase):\n\n    def parseStreamClient(self, *a, **kw):\n        return StreamClient(self, a, kw)\n\n\n\n@implementer(IStreamServerEndpointStringParser)\nclass FakeParser(PluginBase):\n\n    def parseStreamServer(self, *a, **kw):\n        return StreamServer(self, a, kw)\n\n\n\nclass EndpointBase(object):\n\n    def __init__(self, parser, args, kwargs):\n        self.parser = parser\n        self.args = args\n        self.kwargs = kwargs\n\n\n\n@implementer(IStreamClientEndpoint)\nclass StreamClient(EndpointBase):\n    pass\n\n\n\n@implementer(IStreamServerEndpoint)\nclass StreamServer(EndpointBase):\n    pass\n\n\n\n# Instantiate plugin interface providers to register them.\nfake = FakeParser('fake')\nfakeClientWithReactor = FakeClientParserWithReactor('crfake')\nfakeClientWithReactorAndPreference = FakeClientParserWithReactor('cpfake')\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/modulehelpers.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTesting helpers related to the module system.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__all__ = ['NoReactor', 'AlternateReactor']\n\nimport sys\n\nimport twisted.internet\nfrom twisted.test.test_twisted import SetAsideModule\n\n\n\nclass NoReactor(SetAsideModule):\n    \"\"\"\n    Context manager that uninstalls the reactor, if any, and then restores it\n    afterwards.\n    \"\"\"\n\n    def __init__(self):\n        SetAsideModule.__init__(self, \"twisted.internet.reactor\")\n\n\n    def __enter__(self):\n        SetAsideModule.__enter__(self)\n        if \"twisted.internet.reactor\" in self.modules:\n            del twisted.internet.reactor\n\n\n    def __exit__(self, excType, excValue, traceback):\n        SetAsideModule.__exit__(self, excType, excValue, traceback)\n        # Clean up 'reactor' attribute that may have been set on\n        # twisted.internet:\n        reactor = self.modules.get(\"twisted.internet.reactor\", None)\n        if reactor is not None:\n            twisted.internet.reactor = reactor\n        else:\n            try:\n                del twisted.internet.reactor\n            except AttributeError:\n                pass\n\n\n\nclass AlternateReactor(NoReactor):\n    \"\"\"\n    A context manager which temporarily installs a different object as the\n    global reactor.\n    \"\"\"\n\n    def __init__(self, reactor):\n        \"\"\"\n        @param reactor: Any object to install as the global reactor.\n        \"\"\"\n        NoReactor.__init__(self)\n        self.alternate = reactor\n\n\n    def __enter__(self):\n        NoReactor.__enter__(self)\n        twisted.internet.reactor = self.alternate\n        sys.modules['twisted.internet.reactor'] = self.alternate\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/process_cli.py",
    "content": "from __future__ import absolute_import, division\n\nimport sys\nimport os\n\ntry:\n    # On Windows, stdout is not opened in binary mode by default,\n    # so newline characters are munged on writing, interfering with\n    # the tests.\n    import msvcrt\n    msvcrt.setmode(sys.stdout.fileno(), os.O_BINARY)\nexcept ImportError:\n    pass\n\n\n# Loop over each of the arguments given and print it to stdout\nfor arg in sys.argv[1:]:\n    res = arg + chr(0)\n\n    if sys.version_info < (3, 0):\n        stdout = sys.stdout\n    else:\n        stdout = sys.stdout.buffer\n        res = res.encode(sys.getfilesystemencoding(), \"surrogateescape\")\n\n    stdout.write(res)\n    stdout.flush()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/process_gireactornocompat.py",
    "content": "import sys\n\n# Override theSystemPath so it throws KeyError on gi.pygtkcompat:\nfrom twisted.python import modules\nmodules.theSystemPath = modules.PythonPath([], moduleDict={})\n\n# Now, when we import gireactor it shouldn't use pygtkcompat, and should\n# instead prevent gobject from being importable:\nfrom twisted.internet import gireactor\nfor name in gireactor._PYGTK_MODULES:\n    if sys.modules[name] is not None:\n        sys.stdout.write(\"failure, sys.modules[%r] is %r, instead of None\" %\n                         (name, sys.modules[\"gobject\"]))\n        sys.exit(0)\n\ntry:\n    import gobject\nexcept ImportError:\n    sys.stdout.write(\"success\")\nelse:\n    sys.stdout.write(\"failure: %s was imported\" % (gobject.__path__,))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/process_helper.py",
    "content": "\n# A program which exits after starting a child which inherits its\n# stdin/stdout/stderr and keeps them open until stdin is closed.\n\nimport sys, os\n\ndef grandchild():\n    sys.stdout.write('grandchild started')\n    sys.stdout.flush()\n    sys.stdin.read()\n\ndef main():\n    if sys.argv[1] == 'child':\n        if sys.argv[2] == 'windows':\n            import win32api as api, win32process as proc\n            info = proc.STARTUPINFO()\n            info.hStdInput = api.GetStdHandle(api.STD_INPUT_HANDLE)\n            info.hStdOutput = api.GetStdHandle(api.STD_OUTPUT_HANDLE)\n            info.hStdError = api.GetStdHandle(api.STD_ERROR_HANDLE)\n            python = sys.executable\n            scriptDir = os.path.dirname(__file__)\n            scriptName = os.path.basename(__file__)\n            proc.CreateProcess(\n                None, \" \".join((python, scriptName, \"grandchild\")), None,\n                None, 1, 0, os.environ, scriptDir, info)\n        else:\n            if os.fork() == 0:\n                grandchild()\n    else:\n        grandchild()\n\nif __name__ == '__main__':\n    main()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/reactormixins.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nUtilities for unit testing reactor implementations.\n\nThe main feature of this module is L{ReactorBuilder}, a base class for use when\nwriting interface/blackbox tests for reactor implementations.  Test case classes\nfor reactor features should subclass L{ReactorBuilder} instead of\nL{SynchronousTestCase}.  All of the features of L{SynchronousTestCase} will be\navailable.  Additionally, the tests will automatically be applied to all\navailable reactor implementations.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__metaclass__ = type\n\n__all__ = ['TestTimeoutError', 'ReactorBuilder', 'needsRunningReactor']\n\nimport os, signal, time\n\nfrom twisted.trial.unittest import SynchronousTestCase, SkipTest\nfrom twisted.trial.util import DEFAULT_TIMEOUT_DURATION, acquireAttribute\nfrom twisted.python.runtime import platform\nfrom twisted.python.reflect import namedAny\nfrom twisted.python.deprecate import _fullyQualifiedName as fullyQualifiedName\n\nfrom twisted.python import log\nfrom twisted.python.failure import Failure\nfrom twisted.python.compat import _PY3\n\n\n# Access private APIs.\nif platform.isWindows():\n    process = None\nelse:\n    from twisted.internet import process\n\n\n\nclass TestTimeoutError(Exception):\n    \"\"\"\n    The reactor was still running after the timeout period elapsed in\n    L{ReactorBuilder.runReactor}.\n    \"\"\"\n\n\n\ndef needsRunningReactor(reactor, thunk):\n    \"\"\"\n    Various functions within these tests need an already-running reactor at\n    some point.  They need to stop the reactor when the test has completed, and\n    that means calling reactor.stop().  However, reactor.stop() raises an\n    exception if the reactor isn't already running, so if the L{Deferred} that\n    a particular API under test returns fires synchronously (as especially an\n    endpoint's C{connect()} method may do, if the connect is to a local\n    interface address) then the test won't be able to stop the reactor being\n    tested and finish.  So this calls C{thunk} only once C{reactor} is running.\n\n    (This is just an alias for\n    L{twisted.internet.interfaces.IReactorCore.callWhenRunning} on the given\n    reactor parameter, in order to centrally reference the above paragraph and\n    repeating it everywhere as a comment.)\n\n    @param reactor: the L{twisted.internet.interfaces.IReactorCore} under test\n\n    @param thunk: a 0-argument callable, which eventually finishes the test in\n        question, probably in a L{Deferred} callback.\n    \"\"\"\n    reactor.callWhenRunning(thunk)\n\n\n\ndef stopOnError(case, reactor, publisher=None):\n    \"\"\"\n    Stop the reactor as soon as any error is logged on the given publisher.\n\n    This is beneficial for tests which will wait for a L{Deferred} to fire\n    before completing (by passing or failing).  Certain implementation bugs may\n    prevent the L{Deferred} from firing with any result at all (consider a\n    protocol's {dataReceived} method that raises an exception: this exception\n    is logged but it won't ever cause a L{Deferred} to fire).  In that case the\n    test would have to complete by timing out which is a much less desirable\n    outcome than completing as soon as the unexpected error is encountered.\n\n    @param case: A L{SynchronousTestCase} to use to clean up the necessary log\n        observer when the test is over.\n    @param reactor: The reactor to stop.\n    @param publisher: A L{LogPublisher} to watch for errors.  If L{None}, the\n        global log publisher will be watched.\n    \"\"\"\n    if publisher is None:\n        from twisted.python import log as publisher\n    running = [None]\n    def stopIfError(event):\n        if running and event.get('isError'):\n            running.pop()\n            reactor.stop()\n    publisher.addObserver(stopIfError)\n    case.addCleanup(publisher.removeObserver, stopIfError)\n\n\n\nclass ReactorBuilder:\n    \"\"\"\n    L{SynchronousTestCase} mixin which provides a reactor-creation API.  This\n    mixin defines C{setUp} and C{tearDown}, so mix it in before\n    L{SynchronousTestCase} or call its methods from the overridden ones in the\n    subclass.\n\n    @cvar skippedReactors: A dict mapping FQPN strings of reactors for\n        which the tests defined by this class will be skipped to strings\n        giving the skip message.\n    @cvar requiredInterfaces: A C{list} of interfaces which the reactor must\n        provide or these tests will be skipped.  The default, L{None}, means\n        that no interfaces are required.\n    @ivar reactorFactory: A no-argument callable which returns the reactor to\n        use for testing.\n    @ivar originalHandler: The SIGCHLD handler which was installed when setUp\n        ran and which will be re-installed when tearDown runs.\n    @ivar _reactors: A list of FQPN strings giving the reactors for which\n        L{SynchronousTestCase}s will be created.\n    \"\"\"\n\n    _reactors = [\n        # Select works everywhere\n        \"twisted.internet.selectreactor.SelectReactor\",\n        ]\n\n    if platform.isWindows():\n        # PortableGtkReactor is only really interesting on Windows,\n        # but not really Windows specific; if you want you can\n        # temporarily move this up to the all-platforms list to test\n        # it on other platforms.  It's not there in general because\n        # it's not _really_ worth it to support on other platforms,\n        # since no one really wants to use it on other platforms.\n        _reactors.extend([\n                \"twisted.internet.gtk2reactor.PortableGtkReactor\",\n                \"twisted.internet.gireactor.PortableGIReactor\",\n                \"twisted.internet.gtk3reactor.PortableGtk3Reactor\",\n                \"twisted.internet.win32eventreactor.Win32Reactor\",\n                \"twisted.internet.iocpreactor.reactor.IOCPReactor\"])\n    else:\n        _reactors.extend([\n                \"twisted.internet.glib2reactor.Glib2Reactor\",\n                \"twisted.internet.gtk2reactor.Gtk2Reactor\",\n                \"twisted.internet.gireactor.GIReactor\",\n                \"twisted.internet.gtk3reactor.Gtk3Reactor\"])\n\n        if _PY3:\n            _reactors.append(\n                \"twisted.internet.asyncioreactor.AsyncioSelectorReactor\")\n\n        if platform.isMacOSX():\n            _reactors.append(\"twisted.internet.cfreactor.CFReactor\")\n        else:\n            _reactors.extend([\n                    \"twisted.internet.pollreactor.PollReactor\",\n                    \"twisted.internet.epollreactor.EPollReactor\"])\n            if not platform.isLinux():\n                # Presumably Linux is not going to start supporting kqueue, so\n                # skip even trying this configuration.\n                _reactors.extend([\n                        # Support KQueue on non-OS-X POSIX platforms for now.\n                        \"twisted.internet.kqreactor.KQueueReactor\",\n                        ])\n\n    reactorFactory = None\n    originalHandler = None\n    requiredInterfaces = None\n    skippedReactors = {}\n\n    def setUp(self):\n        \"\"\"\n        Clear the SIGCHLD handler, if there is one, to ensure an environment\n        like the one which exists prior to a call to L{reactor.run}.\n        \"\"\"\n        if not platform.isWindows():\n            self.originalHandler = signal.signal(signal.SIGCHLD, signal.SIG_DFL)\n\n\n    def tearDown(self):\n        \"\"\"\n        Restore the original SIGCHLD handler and reap processes as long as\n        there seem to be any remaining.\n        \"\"\"\n        if self.originalHandler is not None:\n            signal.signal(signal.SIGCHLD, self.originalHandler)\n        if process is not None:\n            begin = time.time()\n            while process.reapProcessHandlers:\n                log.msg(\n                    \"ReactorBuilder.tearDown reaping some processes %r\" % (\n                        process.reapProcessHandlers,))\n                process.reapAllProcesses()\n\n                # The process should exit on its own.  However, if it\n                # doesn't, we're stuck in this loop forever.  To avoid\n                # hanging the test suite, eventually give the process some\n                # help exiting and move on.\n                time.sleep(0.001)\n                if time.time() - begin > 60:\n                    for pid in process.reapProcessHandlers:\n                        os.kill(pid, signal.SIGKILL)\n                    raise Exception(\n                        \"Timeout waiting for child processes to exit: %r\" % (\n                            process.reapProcessHandlers,))\n\n\n    def unbuildReactor(self, reactor):\n        \"\"\"\n        Clean up any resources which may have been allocated for the given\n        reactor by its creation or by a test which used it.\n        \"\"\"\n        # Chris says:\n        #\n        # XXX These explicit calls to clean up the waker (and any other\n        # internal readers) should become obsolete when bug #3063 is\n        # fixed. -radix, 2008-02-29. Fortunately it should probably cause an\n        # error when bug #3063 is fixed, so it should be removed in the same\n        # branch that fixes it.\n        #\n        # -exarkun\n        reactor._uninstallHandler()\n        if getattr(reactor, '_internalReaders', None) is not None:\n            for reader in reactor._internalReaders:\n                reactor.removeReader(reader)\n                reader.connectionLost(None)\n            reactor._internalReaders.clear()\n\n        # Here's an extra thing unrelated to wakers but necessary for\n        # cleaning up after the reactors we make.  -exarkun\n        reactor.disconnectAll()\n\n        # It would also be bad if any timed calls left over were allowed to\n        # run.\n        calls = reactor.getDelayedCalls()\n        for c in calls:\n            c.cancel()\n\n\n    def buildReactor(self):\n        \"\"\"\n        Create and return a reactor using C{self.reactorFactory}.\n        \"\"\"\n        try:\n            from twisted.internet.cfreactor import CFReactor\n            from twisted.internet import reactor as globalReactor\n        except ImportError:\n            pass\n        else:\n            if (isinstance(globalReactor, CFReactor)\n                and self.reactorFactory is CFReactor):\n                raise SkipTest(\n                    \"CFReactor uses APIs which manipulate global state, \"\n                    \"so it's not safe to run its own reactor-builder tests \"\n                    \"under itself\")\n        try:\n            reactor = self.reactorFactory()\n        except:\n            # Unfortunately, not all errors which result in a reactor\n            # being unusable are detectable without actually\n            # instantiating the reactor.  So we catch some more here\n            # and skip the test if necessary.  We also log it to aid\n            # with debugging, but flush the logged error so the test\n            # doesn't fail.\n            log.err(None, \"Failed to install reactor\")\n            self.flushLoggedErrors()\n            raise SkipTest(Failure().getErrorMessage())\n        else:\n            if self.requiredInterfaces is not None:\n                missing = [\n                    required for required in self.requiredInterfaces\n                    if not required.providedBy(reactor)]\n                if missing:\n                    self.unbuildReactor(reactor)\n                    raise SkipTest(\"%s does not provide %s\" % (\n                        fullyQualifiedName(reactor.__class__),\n                        \",\".join([fullyQualifiedName(x) for x in missing])))\n        self.addCleanup(self.unbuildReactor, reactor)\n        return reactor\n\n\n    def getTimeout(self):\n        \"\"\"\n        Determine how long to run the test before considering it failed.\n\n        @return: A C{int} or C{float} giving a number of seconds.\n        \"\"\"\n        return acquireAttribute(self._parents, 'timeout', DEFAULT_TIMEOUT_DURATION)\n\n\n    def runReactor(self, reactor, timeout=None):\n        \"\"\"\n        Run the reactor for at most the given amount of time.\n\n        @param reactor: The reactor to run.\n\n        @type timeout: C{int} or C{float}\n        @param timeout: The maximum amount of time, specified in seconds, to\n            allow the reactor to run.  If the reactor is still running after\n            this much time has elapsed, it will be stopped and an exception\n            raised.  If L{None}, the default test method timeout imposed by\n            Trial will be used.  This depends on the L{IReactorTime}\n            implementation of C{reactor} for correct operation.\n\n        @raise TestTimeoutError: If the reactor is still running after\n            C{timeout} seconds.\n        \"\"\"\n        if timeout is None:\n            timeout = self.getTimeout()\n\n        timedOut = []\n        def stop():\n            timedOut.append(None)\n            reactor.stop()\n\n        timedOutCall = reactor.callLater(timeout, stop)\n        reactor.run()\n        if timedOut:\n            raise TestTimeoutError(\n                \"reactor still running after %s seconds\" % (timeout,))\n        else:\n            timedOutCall.cancel()\n\n\n    def makeTestCaseClasses(cls):\n        \"\"\"\n        Create a L{SynchronousTestCase} subclass which mixes in C{cls} for each\n        known reactor and return a dict mapping their names to them.\n        \"\"\"\n        classes = {}\n        for reactor in cls._reactors:\n            shortReactorName = reactor.split(\".\")[-1]\n            name = (cls.__name__ + \".\" + shortReactorName + \"Tests\").replace(\".\", \"_\")\n            class testcase(cls, SynchronousTestCase):\n                __module__ = cls.__module__\n                if reactor in cls.skippedReactors:\n                    skip = cls.skippedReactors[reactor]\n                try:\n                    reactorFactory = namedAny(reactor)\n                except:\n                    skip = Failure().getErrorMessage()\n            testcase.__name__ = name\n            if hasattr(cls, \"__qualname__\"):\n                testcase.__qualname__ = \".\".join(cls.__qualname__.split()[0:-1] + [name])\n            classes[testcase.__name__] = testcase\n        return classes\n    makeTestCaseClasses = classmethod(makeTestCaseClasses)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_address.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom __future__ import division, absolute_import\n\nimport os\nimport socket\n\nfrom twisted.trial import unittest\nfrom twisted.internet.address import IPv4Address, UNIXAddress, IPv6Address\nfrom twisted.internet.address import HostnameAddress\nfrom twisted.python.compat import nativeString\nfrom twisted.python.runtime import platform\n\nif not platform._supportsSymlinks():\n    symlinkSkip = \"Platform does not support symlinks\"\nelse:\n    symlinkSkip = None\n\ntry:\n    socket.AF_UNIX\nexcept AttributeError:\n    unixSkip = \"Platform doesn't support UNIX sockets.\"\nelse:\n    unixSkip = None\n\n\nclass AddressTestCaseMixin(object):\n    def test_addressComparison(self):\n        \"\"\"\n        Two different address instances, sharing the same properties are\n        considered equal by C{==} and not considered not equal by C{!=}.\n\n        Note: When applied via UNIXAddress class, this uses the same\n        filename for both objects being compared.\n        \"\"\"\n        self.assertTrue(self.buildAddress() == self.buildAddress())\n        self.assertFalse(self.buildAddress() != self.buildAddress())\n\n\n    def test_hash(self):\n        \"\"\"\n        C{__hash__} can be used to get a hash of an address, allowing\n        addresses to be used as keys in dictionaries, for instance.\n        \"\"\"\n        addr = self.buildAddress()\n        d = {addr: True}\n        self.assertTrue(d[self.buildAddress()])\n\n\n    def test_differentNamesComparison(self):\n        \"\"\"\n        Check that comparison operators work correctly on address objects\n        when a different name is passed in\n        \"\"\"\n        self.assertFalse(self.buildAddress() == self.buildDifferentAddress())\n        self.assertFalse(self.buildDifferentAddress() == self.buildAddress())\n\n        self.assertTrue(self.buildAddress() != self.buildDifferentAddress())\n        self.assertTrue(self.buildDifferentAddress() != self.buildAddress())\n\n\n    def assertDeprecations(self, testMethod, message):\n        \"\"\"\n        Assert that the a DeprecationWarning with the given message was\n        emitted against the given method.\n        \"\"\"\n        warnings = self.flushWarnings([testMethod])\n        self.assertEqual(warnings[0]['category'], DeprecationWarning)\n        self.assertEqual(warnings[0]['message'], message)\n        self.assertEqual(len(warnings), 1)\n\n\n\nclass IPv4AddressTestCaseMixin(AddressTestCaseMixin):\n    addressArgSpec = ((\"type\", \"%s\"), (\"host\", \"%r\"), (\"port\", \"%d\"))\n\n\n\nclass HostnameAddressTests(unittest.TestCase, AddressTestCaseMixin):\n    \"\"\"\n    Test case for L{HostnameAddress}.\n    \"\"\"\n    addressArgSpec = ((\"hostname\", \"%s\"), (\"port\", \"%d\"))\n\n    def buildAddress(self):\n        \"\"\"\n        Create an arbitrary new L{HostnameAddress} instance.\n\n        @return: A L{HostnameAddress} instance.\n        \"\"\"\n        return HostnameAddress(b\"example.com\", 0)\n\n\n    def buildDifferentAddress(self):\n        \"\"\"\n        Like L{buildAddress}, but with a different hostname.\n\n        @return: A L{HostnameAddress} instance.\n        \"\"\"\n        return HostnameAddress(b\"example.net\", 0)\n\n\n\nclass IPv4AddressTCPTests(unittest.SynchronousTestCase,\n                          IPv4AddressTestCaseMixin):\n    def buildAddress(self):\n        \"\"\"\n        Create an arbitrary new L{IPv4Address} instance with a C{\"TCP\"}\n        type.  A new instance is created for each call, but always for the\n        same address.\n        \"\"\"\n        return IPv4Address(\"TCP\", \"127.0.0.1\", 0)\n\n\n    def buildDifferentAddress(self):\n        \"\"\"\n        Like L{buildAddress}, but with a different fixed address.\n        \"\"\"\n        return IPv4Address(\"TCP\", \"127.0.0.2\", 0)\n\n\n\nclass IPv4AddressUDPTests(unittest.SynchronousTestCase,\n                          IPv4AddressTestCaseMixin):\n    def buildAddress(self):\n        \"\"\"\n        Create an arbitrary new L{IPv4Address} instance with a C{\"UDP\"}\n        type.  A new instance is created for each call, but always for the\n        same address.\n        \"\"\"\n        return IPv4Address(\"UDP\", \"127.0.0.1\", 0)\n\n\n    def buildDifferentAddress(self):\n        \"\"\"\n        Like L{buildAddress}, but with a different fixed address.\n        \"\"\"\n        return IPv4Address(\"UDP\", \"127.0.0.2\", 0)\n\n\n\nclass IPv6AddressTests(unittest.SynchronousTestCase, AddressTestCaseMixin):\n    addressArgSpec = ((\"type\", \"%s\"), (\"host\", \"%r\"), (\"port\", \"%d\"))\n\n    def buildAddress(self):\n        \"\"\"\n        Create an arbitrary new L{IPv6Address} instance with a C{\"TCP\"}\n        type.  A new instance is created for each call, but always for the\n        same address.\n        \"\"\"\n        return IPv6Address(\"TCP\", \"::1\", 0)\n\n\n    def buildDifferentAddress(self):\n        \"\"\"\n        Like L{buildAddress}, but with a different fixed address.\n        \"\"\"\n        return IPv6Address(\"TCP\", \"::2\", 0)\n\n\n\nclass UNIXAddressTests(unittest.SynchronousTestCase):\n    skip = unixSkip\n    addressArgSpec = ((\"name\", \"%r\"),)\n\n    def setUp(self):\n        self._socketAddress = self.mktemp()\n        self._otherAddress = self.mktemp()\n\n\n    def buildAddress(self):\n        \"\"\"\n        Create an arbitrary new L{UNIXAddress} instance.  A new instance is\n        created for each call, but always for the same address.\n        \"\"\"\n        return UNIXAddress(self._socketAddress)\n\n\n    def buildDifferentAddress(self):\n        \"\"\"\n        Like L{buildAddress}, but with a different fixed address.\n        \"\"\"\n        return UNIXAddress(self._otherAddress)\n\n\n    def test_repr(self):\n        \"\"\"\n        The repr of L{UNIXAddress} returns with the filename that the\n        L{UNIXAddress} is for.\n        \"\"\"\n        self.assertEqual(repr(self.buildAddress()), \"UNIXAddress('%s')\" % (\n            nativeString(self._socketAddress)))\n\n\n    def test_comparisonOfLinkedFiles(self):\n        \"\"\"\n        UNIXAddress objects compare as equal if they link to the same file.\n        \"\"\"\n        linkName = self.mktemp()\n        with open(self._socketAddress, 'w') as self.fd:\n            os.symlink(os.path.abspath(self._socketAddress), linkName)\n            self.assertEqual(UNIXAddress(self._socketAddress),\n                             UNIXAddress(linkName))\n            self.assertEqual(UNIXAddress(linkName),\n                             UNIXAddress(self._socketAddress))\n    if not unixSkip:\n        test_comparisonOfLinkedFiles.skip = symlinkSkip\n\n\n    def test_hashOfLinkedFiles(self):\n        \"\"\"\n        UNIXAddress Objects that compare as equal have the same hash value.\n        \"\"\"\n        linkName = self.mktemp()\n        with open(self._socketAddress, 'w') as self.fd:\n            os.symlink(os.path.abspath(self._socketAddress), linkName)\n            self.assertEqual(hash(UNIXAddress(self._socketAddress)),\n                            hash(UNIXAddress(linkName)))\n    if not unixSkip:\n        test_hashOfLinkedFiles.skip = symlinkSkip\n\n\n\nclass EmptyUNIXAddressTests(unittest.SynchronousTestCase,\n                            AddressTestCaseMixin):\n    \"\"\"\n    Tests for L{UNIXAddress} operations involving a L{None} address.\n    \"\"\"\n    skip = unixSkip\n    addressArgSpec = ((\"name\", \"%r\"),)\n\n    def setUp(self):\n        self._socketAddress = self.mktemp()\n\n\n    def buildAddress(self):\n        \"\"\"\n        Create an arbitrary new L{UNIXAddress} instance.  A new instance is\n        created for each call, but always for the same address. This builds it\n        with a fixed address of L{None}.\n        \"\"\"\n        return UNIXAddress(None)\n\n\n    def buildDifferentAddress(self):\n        \"\"\"\n        Like L{buildAddress}, but with a random temporary directory.\n        \"\"\"\n        return UNIXAddress(self._socketAddress)\n\n\n    def test_comparisonOfLinkedFiles(self):\n        \"\"\"\n        A UNIXAddress referring to a L{None} address does not compare equal to a\n        UNIXAddress referring to a symlink.\n        \"\"\"\n        linkName = self.mktemp()\n        with open(self._socketAddress, 'w') as self.fd:\n            os.symlink(os.path.abspath(self._socketAddress), linkName)\n            self.assertNotEqual(UNIXAddress(self._socketAddress),\n                                UNIXAddress(None))\n            self.assertNotEqual(UNIXAddress(None),\n                                UNIXAddress(self._socketAddress))\n    if not unixSkip:\n        test_comparisonOfLinkedFiles.skip = symlinkSkip\n\n\n    def test_emptyHash(self):\n        \"\"\"\n        C{__hash__} can be used to get a hash of an address, even one referring\n        to L{None} rather than a real path.\n        \"\"\"\n        addr = self.buildAddress()\n        d = {addr: True}\n        self.assertTrue(d[self.buildAddress()])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_asyncioreactor.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet.asyncioreactor}.\n\"\"\"\n\nfrom twisted.trial.unittest import SynchronousTestCase\nfrom .reactormixins import ReactorBuilder\n\ntry:\n    from twisted.internet.asyncioreactor import AsyncioSelectorReactor\n    import asyncio\nexcept ImportError:\n    AsyncioSelectorReactor = None\n    skipReason = \"Requires asyncio.\"\n\n\n\nclass AsyncioSelectorReactorTests(ReactorBuilder, SynchronousTestCase):\n    \"\"\"\n    L{AsyncioSelectorReactor} tests.\n    \"\"\"\n    if AsyncioSelectorReactor is None:\n        skip = skipReason\n\n\n    def test_defaultEventLoopFromGlobalPolicy(self):\n        \"\"\"\n        L{AsyncioSelectorReactor} wraps the global policy's event loop\n        by default.  This ensures that L{asyncio.Future}s and\n        coroutines created by library code that uses\n        L{asyncio.get_event_loop} are bound to the same loop.\n        \"\"\"\n        reactor = AsyncioSelectorReactor()\n        future = asyncio.Future()\n        result = []\n\n        def completed(future):\n            result.append(future.result())\n            reactor.stop()\n\n        future.add_done_callback(completed)\n        future.set_result(True)\n\n        self.assertEqual(result, [])\n        self.runReactor(reactor, timeout=1)\n        self.assertEqual(result, [True])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_base.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet.base}.\n\"\"\"\n\nimport socket\ntry:\n    from Queue import Queue\nexcept ImportError:\n    from queue import Queue\n\nfrom zope.interface import implementer\n\nfrom twisted.python.threadpool import ThreadPool\nfrom twisted.internet.interfaces import (IReactorTime, IReactorThreads,\n                                         IResolverSimple)\nfrom twisted.internet.error import DNSLookupError\nfrom twisted.internet._resolver import FirstOneWins\nfrom twisted.internet.defer import Deferred\nfrom twisted.internet.base import ThreadedResolver, DelayedCall, ReactorBase\nfrom twisted.internet.task import Clock\nfrom twisted.trial.unittest import TestCase, SkipTest\n\n\n@implementer(IReactorTime, IReactorThreads)\nclass FakeReactor(object):\n    \"\"\"\n    A fake reactor implementation which just supports enough reactor APIs for\n    L{ThreadedResolver}.\n    \"\"\"\n\n    def __init__(self):\n        self._clock = Clock()\n        self.callLater = self._clock.callLater\n\n        self._threadpool = ThreadPool()\n        self._threadpool.start()\n        self.getThreadPool = lambda: self._threadpool\n\n        self._threadCalls = Queue()\n\n\n    def callFromThread(self, f, *args, **kwargs):\n        self._threadCalls.put((f, args, kwargs))\n\n\n    def _runThreadCalls(self):\n        f, args, kwargs = self._threadCalls.get()\n        f(*args, **kwargs)\n\n\n    def _stop(self):\n        self._threadpool.stop()\n\n\n\nclass ThreadedResolverTests(TestCase):\n    \"\"\"\n    Tests for L{ThreadedResolver}.\n    \"\"\"\n    def test_success(self):\n        \"\"\"\n        L{ThreadedResolver.getHostByName} returns a L{Deferred} which fires\n        with the value returned by the call to L{socket.gethostbyname} in the\n        threadpool of the reactor passed to L{ThreadedResolver.__init__}.\n        \"\"\"\n        ip = \"10.0.0.17\"\n        name = \"foo.bar.example.com\"\n        timeout = 30\n\n        reactor = FakeReactor()\n        self.addCleanup(reactor._stop)\n\n        lookedUp = []\n        resolvedTo = []\n        def fakeGetHostByName(name):\n            lookedUp.append(name)\n            return ip\n\n        self.patch(socket, 'gethostbyname', fakeGetHostByName)\n\n        resolver = ThreadedResolver(reactor)\n        d = resolver.getHostByName(name, (timeout,))\n        d.addCallback(resolvedTo.append)\n\n        reactor._runThreadCalls()\n\n        self.assertEqual(lookedUp, [name])\n        self.assertEqual(resolvedTo, [ip])\n\n        # Make sure that any timeout-related stuff gets cleaned up.\n        reactor._clock.advance(timeout + 1)\n        self.assertEqual(reactor._clock.calls, [])\n\n\n    def test_failure(self):\n        \"\"\"\n        L{ThreadedResolver.getHostByName} returns a L{Deferred} which fires a\n        L{Failure} if the call to L{socket.gethostbyname} raises an exception.\n        \"\"\"\n        timeout = 30\n\n        reactor = FakeReactor()\n        self.addCleanup(reactor._stop)\n\n        def fakeGetHostByName(name):\n            raise IOError(\"ENOBUFS (this is a funny joke)\")\n\n        self.patch(socket, 'gethostbyname', fakeGetHostByName)\n\n        failedWith = []\n        resolver = ThreadedResolver(reactor)\n        d = resolver.getHostByName(\"some.name\", (timeout,))\n        self.assertFailure(d, DNSLookupError)\n        d.addCallback(failedWith.append)\n\n        reactor._runThreadCalls()\n\n        self.assertEqual(len(failedWith), 1)\n\n        # Make sure that any timeout-related stuff gets cleaned up.\n        reactor._clock.advance(timeout + 1)\n        self.assertEqual(reactor._clock.calls, [])\n\n\n    def test_timeout(self):\n        \"\"\"\n        If L{socket.gethostbyname} does not complete before the specified\n        timeout elapsed, the L{Deferred} returned by\n        L{ThreadedResolver.getHostByName} fails with L{DNSLookupError}.\n        \"\"\"\n        timeout = 10\n\n        reactor = FakeReactor()\n        self.addCleanup(reactor._stop)\n\n        result = Queue()\n        def fakeGetHostByName(name):\n            raise result.get()\n\n        self.patch(socket, 'gethostbyname', fakeGetHostByName)\n\n        failedWith = []\n        resolver = ThreadedResolver(reactor)\n        d = resolver.getHostByName(\"some.name\", (timeout,))\n        self.assertFailure(d, DNSLookupError)\n        d.addCallback(failedWith.append)\n\n        reactor._clock.advance(timeout - 1)\n        self.assertEqual(failedWith, [])\n        reactor._clock.advance(1)\n        self.assertEqual(len(failedWith), 1)\n\n        # Eventually the socket.gethostbyname does finish - in this case, with\n        # an exception.  Nobody cares, though.\n        result.put(IOError(\"The I/O was errorful\"))\n\n\n    def test_resolverGivenStr(self):\n        \"\"\"\n        L{ThreadedResolver.getHostByName} is passed L{str}, encoded using IDNA\n        if required.\n        \"\"\"\n        calls = []\n\n        @implementer(IResolverSimple)\n        class FakeResolver(object):\n            def getHostByName(self, name, timeouts=()):\n                calls.append(name)\n                return Deferred()\n\n        class JustEnoughReactor(ReactorBase):\n            def installWaker(self):\n                pass\n\n        fake = FakeResolver()\n        reactor = JustEnoughReactor()\n        reactor.installResolver(fake)\n        rec = FirstOneWins(Deferred())\n        reactor.nameResolver.resolveHostName(\n            rec, u\"example.example\")\n        reactor.nameResolver.resolveHostName(\n            rec, \"example.example\")\n        reactor.nameResolver.resolveHostName(\n            rec, u\"v\\xe4\\xe4ntynyt.example\")\n        reactor.nameResolver.resolveHostName(\n            rec, u\"\\u0440\\u0444.example\")\n        reactor.nameResolver.resolveHostName(\n            rec, \"xn----7sbb4ac0ad0be6cf.xn--p1ai\")\n\n        self.assertEqual(len(calls), 5)\n        self.assertEqual(list(map(type, calls)), [str]*5)\n        self.assertEqual(\"example.example\", calls[0])\n        self.assertEqual(\"example.example\", calls[1])\n        self.assertEqual(\"xn--vntynyt-5waa.example\", calls[2])\n        self.assertEqual(\"xn--p1ai.example\", calls[3])\n        self.assertEqual(\"xn----7sbb4ac0ad0be6cf.xn--p1ai\", calls[4])\n\n\n\ndef nothing():\n    \"\"\"\n    Function used by L{DelayedCallTests.test_str}.\n    \"\"\"\n\n\n\nclass DelayedCallMixin(object):\n    \"\"\"\n    L{DelayedCall}\n    \"\"\"\n    def _getDelayedCallAt(self, time):\n        \"\"\"\n        Get a L{DelayedCall} instance at a given C{time}.\n\n        @param time: The absolute time at which the returned L{DelayedCall}\n            will be scheduled.\n        \"\"\"\n        def noop(call):\n            pass\n        return DelayedCall(time, lambda: None, (), {}, noop, noop, None)\n\n\n    def setUp(self):\n        \"\"\"\n        Create two L{DelayedCall} instanced scheduled to run at different\n        times.\n        \"\"\"\n        self.zero = self._getDelayedCallAt(0)\n        self.one = self._getDelayedCallAt(1)\n\n\n    def test_str(self):\n        \"\"\"\n        The string representation of a L{DelayedCall} instance, as returned by\n        L{str}, includes the unsigned id of the instance, as well as its state,\n        the function to be called, and the function arguments.\n        \"\"\"\n        dc = DelayedCall(12, nothing, (3, ), {\"A\": 5}, None, None, lambda: 1.5)\n        self.assertEqual(\n            str(dc),\n            \"<DelayedCall 0x%x [10.5s] called=0 cancelled=0 nothing(3, A=5)>\"\n            % (id(dc),),\n        )\n\n\n    def test_repr(self):\n        \"\"\"\n        The string representation of a L{DelayedCall} instance, as returned by\n        {repr}, is identical to that returned by L{str}.\n        \"\"\"\n        dc = DelayedCall(13, nothing, (6, ), {\"A\": 9}, None, None, lambda: 1.6)\n        self.assertEqual(str(dc), repr(dc))\n\n\n    def test_lt(self):\n        \"\"\"\n        For two instances of L{DelayedCall} C{a} and C{b}, C{a < b} is true\n        if and only if C{a} is scheduled to run before C{b}.\n        \"\"\"\n        zero, one = self.zero, self.one\n        self.assertTrue(zero < one)\n        self.assertFalse(one < zero)\n        self.assertFalse(zero < zero)\n        self.assertFalse(one < one)\n\n\n    def test_le(self):\n        \"\"\"\n        For two instances of L{DelayedCall} C{a} and C{b}, C{a <= b} is true\n        if and only if C{a} is scheduled to run before C{b} or at the same\n        time as C{b}.\n        \"\"\"\n        zero, one = self.zero, self.one\n        self.assertTrue(zero <= one)\n        self.assertFalse(one <= zero)\n        self.assertTrue(zero <= zero)\n        self.assertTrue(one <= one)\n\n\n    def test_gt(self):\n        \"\"\"\n        For two instances of L{DelayedCall} C{a} and C{b}, C{a > b} is true\n        if and only if C{a} is scheduled to run after C{b}.\n        \"\"\"\n        zero, one = self.zero, self.one\n        self.assertTrue(one > zero)\n        self.assertFalse(zero > one)\n        self.assertFalse(zero > zero)\n        self.assertFalse(one > one)\n\n\n    def test_ge(self):\n        \"\"\"\n        For two instances of L{DelayedCall} C{a} and C{b}, C{a > b} is true\n        if and only if C{a} is scheduled to run after C{b} or at the same\n        time as C{b}.\n        \"\"\"\n        zero, one = self.zero, self.one\n        self.assertTrue(one >= zero)\n        self.assertFalse(zero >= one)\n        self.assertTrue(zero >= zero)\n        self.assertTrue(one >= one)\n\n\n    def test_eq(self):\n        \"\"\"\n        A L{DelayedCall} instance is only equal to itself.\n        \"\"\"\n        # Explicitly use == here, instead of assertEqual, to be more\n        # confident __eq__ is being tested.\n        self.assertFalse(self.zero == self.one)\n        self.assertTrue(self.zero == self.zero)\n        self.assertTrue(self.one == self.one)\n\n\n    def test_ne(self):\n        \"\"\"\n        A L{DelayedCall} instance is not equal to any other object.\n        \"\"\"\n        # Explicitly use != here, instead of assertEqual, to be more\n        # confident __ne__ is being tested.\n        self.assertTrue(self.zero != self.one)\n        self.assertFalse(self.zero != self.zero)\n        self.assertFalse(self.one != self.one)\n\n\n\nclass DelayedCallNoDebugTests(DelayedCallMixin, TestCase):\n    \"\"\"\n    L{DelayedCall}\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Turn debug off.\n        \"\"\"\n        self.patch(DelayedCall, 'debug', False)\n        DelayedCallMixin.setUp(self)\n\n\n    def test_str(self):\n        \"\"\"\n        The string representation of a L{DelayedCall} instance, as returned by\n        L{str}, includes the unsigned id of the instance, as well as its state,\n        the function to be called, and the function arguments.\n        \"\"\"\n        dc = DelayedCall(12, nothing, (3, ), {\"A\": 5}, None, None, lambda: 1.5)\n        expected = (\n            \"<DelayedCall 0x{:x} [10.5s] called=0 cancelled=0 \"\n            \"nothing(3, A=5)>\".format(id(dc)))\n        self.assertEqual(str(dc), expected)\n\n\n\nclass DelayedCallDebugTests(DelayedCallMixin, TestCase):\n    \"\"\"\n    L{DelayedCall}\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Turn debug on.\n        \"\"\"\n        self.patch(DelayedCall, 'debug', True)\n        DelayedCallMixin.setUp(self)\n\n\n    def test_str(self):\n        \"\"\"\n        The string representation of a L{DelayedCall} instance, as returned by\n        L{str}, includes the unsigned id of the instance, as well as its state,\n        the function to be called, and the function arguments.\n        \"\"\"\n        dc = DelayedCall(12, nothing, (3, ), {\"A\": 5}, None, None, lambda: 1.5)\n        expectedRegexp = (\n            \"<DelayedCall 0x{:x} \\\\[10.5s\\\\] called=0 cancelled=0 \"\n            \"nothing\\\\(3, A=5\\\\)\\n\\n\"\n            \"traceback at creation:\".format(id(dc)))\n        self.assertRegex(\n            str(dc), expectedRegexp)\n\n\n\nclass TestSpySignalCapturingReactor(ReactorBase):\n\n    \"\"\"\n    Subclass of ReactorBase to capture signals delivered to the\n    reactor for inspection.\n    \"\"\"\n\n    def installWaker(self):\n        \"\"\"\n        Required method, unused.\n        \"\"\"\n\n\n\nclass ReactorBaseSignalTests(TestCase):\n\n    \"\"\"\n    Tests to exercise ReactorBase's signal exit reporting path.\n    \"\"\"\n\n    def test_exitSignalDefaultsToNone(self):\n        \"\"\"\n        The default value of the _exitSignal attribute is None.\n        \"\"\"\n        reactor = TestSpySignalCapturingReactor()\n        self.assertIs(None, reactor._exitSignal)\n\n\n    def test_captureSIGINT(self):\n        \"\"\"\n        ReactorBase's SIGINT handler saves the value of SIGINT to the\n        _exitSignal attribute.\n        \"\"\"\n        reactor = TestSpySignalCapturingReactor()\n        reactor.sigInt(signal.SIGINT, None)\n        self.assertEquals(signal.SIGINT, reactor._exitSignal)\n\n\n    def test_captureSIGTERM(self):\n        \"\"\"\n        ReactorBase's SIGTERM handler saves the value of SIGTERM to the\n        _exitSignal attribute.\n        \"\"\"\n        reactor = TestSpySignalCapturingReactor()\n        reactor.sigTerm(signal.SIGTERM, None)\n        self.assertEquals(signal.SIGTERM, reactor._exitSignal)\n\n\n    def test_captureSIGBREAK(self):\n        \"\"\"\n        ReactorBase's SIGBREAK handler saves the value of SIGBREAK to the\n        _exitSignal attribute.\n        \"\"\"\n        if not hasattr(signal, \"SIGBREAK\"):\n            raise SkipTest(\"signal module does not have SIGBREAK\")\n\n        reactor = TestSpySignalCapturingReactor()\n        reactor.sigBreak(signal.SIGBREAK, None)\n        self.assertEquals(signal.SIGBREAK, reactor._exitSignal)\n\n\n\ntry:\n    import signal\nexcept ImportError:\n    ReactorBaseSignalTests.skip = \"signal module not available\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_baseprocess.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet._baseprocess} which implements process-related\nfunctionality that is useful in all platforms supporting L{IReactorProcess}.\n\"\"\"\n\n__metaclass__ = type\n\nfrom twisted.python.deprecate import getWarningMethod, setWarningMethod\nfrom twisted.trial.unittest import TestCase\nfrom twisted.internet._baseprocess import BaseProcess\n\n\nclass BaseProcessTests(TestCase):\n    \"\"\"\n    Tests for L{BaseProcess}, a parent class for other classes which represent\n    processes which implements functionality common to many different process\n    implementations.\n    \"\"\"\n    def test_callProcessExited(self):\n        \"\"\"\n        L{BaseProcess._callProcessExited} calls the C{processExited} method of\n        its C{proto} attribute and passes it a L{Failure} wrapping the given\n        exception.\n        \"\"\"\n        class FakeProto:\n            reason = None\n\n            def processExited(self, reason):\n                self.reason = reason\n\n        reason = RuntimeError(\"fake reason\")\n        process = BaseProcess(FakeProto())\n        process._callProcessExited(reason)\n        process.proto.reason.trap(RuntimeError)\n        self.assertIs(reason, process.proto.reason.value)\n\n\n    def test_callProcessExitedMissing(self):\n        \"\"\"\n        L{BaseProcess._callProcessExited} emits a L{DeprecationWarning} if the\n        object referred to by its C{proto} attribute has no C{processExited}\n        method.\n        \"\"\"\n        class FakeProto:\n            pass\n\n        reason = object()\n        process = BaseProcess(FakeProto())\n\n        self.addCleanup(setWarningMethod, getWarningMethod())\n        warnings = []\n        def collect(message, category, stacklevel):\n            warnings.append((message, category, stacklevel))\n        setWarningMethod(collect)\n\n        process._callProcessExited(reason)\n\n        [(message, category, stacklevel)] = warnings\n        self.assertEqual(\n            message,\n            \"Since Twisted 8.2, IProcessProtocol.processExited is required.  \"\n            \"%s.%s must implement it.\" % (\n                FakeProto.__module__, FakeProto.__name__))\n        self.assertIs(category, DeprecationWarning)\n        # The stacklevel doesn't really make sense for this kind of\n        # deprecation.  Requiring it to be 0 will at least avoid pointing to\n        # any part of Twisted or a random part of the application's code, which\n        # I think would be more misleading than having it point inside the\n        # warning system itself. -exarkun\n        self.assertEqual(stacklevel, 0)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_core.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for implementations of L{IReactorCore}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__metaclass__ = type\n\nimport signal\nimport time\nimport inspect\n\nfrom twisted.internet.abstract import FileDescriptor\nfrom twisted.internet.error import ReactorAlreadyRunning, ReactorNotRestartable\nfrom twisted.internet.defer import Deferred\nfrom twisted.internet.test.reactormixins import ReactorBuilder\n\n\nclass ObjectModelIntegrationMixin(object):\n    \"\"\"\n    Helpers for tests about the object model of reactor-related objects.\n    \"\"\"\n    def assertFullyNewStyle(self, instance):\n        \"\"\"\n        Assert that the given object is an instance of a new-style class and\n        that there are no classic classes in the inheritance hierarchy of\n        that class.\n\n        This is a beneficial condition because PyPy is better able to\n        optimize attribute lookup on such classes.\n        \"\"\"\n        self.assertIsInstance(instance, object)\n        mro = inspect.getmro(type(instance))\n        for subclass in mro:\n            self.assertTrue(\n                issubclass(subclass, object),\n                \"%r is not new-style\" % (subclass,))\n\n\n\nclass ObjectModelIntegrationTests(ReactorBuilder, ObjectModelIntegrationMixin):\n    \"\"\"\n    Test details of object model integration against all reactors.\n    \"\"\"\n\n    def test_newstyleReactor(self):\n        \"\"\"\n        Checks that all reactors on a platform have method resolution order\n        containing only new style classes.\n        \"\"\"\n        reactor = self.buildReactor()\n        self.assertFullyNewStyle(reactor)\n\n\n\nclass SystemEventTestsBuilder(ReactorBuilder):\n    \"\"\"\n    Builder defining tests relating to L{IReactorCore.addSystemEventTrigger}\n    and L{IReactorCore.fireSystemEvent}.\n    \"\"\"\n    def test_stopWhenNotStarted(self):\n        \"\"\"\n        C{reactor.stop()} raises L{RuntimeError} when called when the reactor\n        has not been started.\n        \"\"\"\n        reactor = self.buildReactor()\n        self.assertRaises(RuntimeError, reactor.stop)\n\n\n    def test_stopWhenAlreadyStopped(self):\n        \"\"\"\n        C{reactor.stop()} raises L{RuntimeError} when called after the reactor\n        has been stopped.\n        \"\"\"\n        reactor = self.buildReactor()\n        reactor.callWhenRunning(reactor.stop)\n        self.runReactor(reactor)\n        self.assertRaises(RuntimeError, reactor.stop)\n\n\n    def test_callWhenRunningOrder(self):\n        \"\"\"\n        Functions are run in the order that they were passed to\n        L{reactor.callWhenRunning}.\n        \"\"\"\n        reactor = self.buildReactor()\n        events = []\n        reactor.callWhenRunning(events.append, \"first\")\n        reactor.callWhenRunning(events.append, \"second\")\n        reactor.callWhenRunning(reactor.stop)\n        self.runReactor(reactor)\n        self.assertEqual(events, [\"first\", \"second\"])\n\n\n    def test_runningForStartupEvents(self):\n        \"\"\"\n        The reactor is not running when C{\"before\"} C{\"startup\"} triggers are\n        called and is running when C{\"during\"} and C{\"after\"} C{\"startup\"}\n        triggers are called.\n        \"\"\"\n        reactor = self.buildReactor()\n        state = {}\n        def beforeStartup():\n            state['before'] = reactor.running\n        def duringStartup():\n            state['during'] = reactor.running\n        def afterStartup():\n            state['after'] = reactor.running\n        reactor.addSystemEventTrigger(\"before\", \"startup\", beforeStartup)\n        reactor.addSystemEventTrigger(\"during\", \"startup\", duringStartup)\n        reactor.addSystemEventTrigger(\"after\", \"startup\", afterStartup)\n        reactor.callWhenRunning(reactor.stop)\n        self.assertEqual(state, {})\n        self.runReactor(reactor)\n        self.assertEqual(\n            state,\n            {\"before\": False,\n             \"during\": True,\n             \"after\": True})\n\n\n    def test_signalHandlersInstalledDuringStartup(self):\n        \"\"\"\n        Signal handlers are installed in responsed to the C{\"during\"}\n        C{\"startup\"}.\n        \"\"\"\n        reactor = self.buildReactor()\n        phase = [None]\n        def beforeStartup():\n            phase[0] = \"before\"\n        def afterStartup():\n            phase[0] = \"after\"\n        reactor.addSystemEventTrigger(\"before\", \"startup\", beforeStartup)\n        reactor.addSystemEventTrigger(\"after\", \"startup\", afterStartup)\n\n        sawPhase = []\n        def fakeSignal(signum, action):\n            sawPhase.append(phase[0])\n        self.patch(signal, 'signal', fakeSignal)\n        reactor.callWhenRunning(reactor.stop)\n        self.assertIsNone(phase[0])\n        self.assertEqual(sawPhase, [])\n        self.runReactor(reactor)\n        self.assertIn(\"before\", sawPhase)\n        self.assertEqual(phase[0], \"after\")\n\n\n    def test_stopShutDownEvents(self):\n        \"\"\"\n        C{reactor.stop()} fires all three phases of shutdown event triggers\n        before it makes C{reactor.run()} return.\n        \"\"\"\n        reactor = self.buildReactor()\n        events = []\n        reactor.addSystemEventTrigger(\n            \"before\", \"shutdown\",\n            lambda: events.append((\"before\", \"shutdown\")))\n        reactor.addSystemEventTrigger(\n            \"during\", \"shutdown\",\n            lambda: events.append((\"during\", \"shutdown\")))\n        reactor.addSystemEventTrigger(\n            \"after\", \"shutdown\",\n            lambda: events.append((\"after\", \"shutdown\")))\n        reactor.callWhenRunning(reactor.stop)\n        self.runReactor(reactor)\n        self.assertEqual(events, [(\"before\", \"shutdown\"),\n                                   (\"during\", \"shutdown\"),\n                                   (\"after\", \"shutdown\")])\n\n\n    def test_shutdownFiresTriggersAsynchronously(self):\n        \"\"\"\n        C{\"before\"} C{\"shutdown\"} triggers are not run synchronously from\n        L{reactor.stop}.\n        \"\"\"\n        reactor = self.buildReactor()\n        events = []\n        reactor.addSystemEventTrigger(\n            \"before\", \"shutdown\", events.append, \"before shutdown\")\n        def stopIt():\n            reactor.stop()\n            events.append(\"stopped\")\n        reactor.callWhenRunning(stopIt)\n        self.assertEqual(events, [])\n        self.runReactor(reactor)\n        self.assertEqual(events, [\"stopped\", \"before shutdown\"])\n\n\n    def test_shutdownDisconnectsCleanly(self):\n        \"\"\"\n        A L{IFileDescriptor.connectionLost} implementation which raises an\n        exception does not prevent the remaining L{IFileDescriptor}s from\n        having their C{connectionLost} method called.\n        \"\"\"\n        lostOK = [False]\n\n        # Subclass FileDescriptor to get logPrefix\n        class ProblematicFileDescriptor(FileDescriptor):\n            def connectionLost(self, reason):\n                raise RuntimeError(\"simulated connectionLost error\")\n\n        class OKFileDescriptor(FileDescriptor):\n            def connectionLost(self, reason):\n                lostOK[0] = True\n\n        reactor = self.buildReactor()\n\n        # Unfortunately, it is necessary to patch removeAll to directly control\n        # the order of the returned values.  The test is only valid if\n        # ProblematicFileDescriptor comes first.  Also, return these\n        # descriptors only the first time removeAll is called so that if it is\n        # called again the file descriptors aren't re-disconnected.\n        fds = iter([ProblematicFileDescriptor(), OKFileDescriptor()])\n        reactor.removeAll = lambda: fds\n        reactor.callWhenRunning(reactor.stop)\n        self.runReactor(reactor)\n        self.assertEqual(len(self.flushLoggedErrors(RuntimeError)), 1)\n        self.assertTrue(lostOK[0])\n\n\n    def test_multipleRun(self):\n        \"\"\"\n        C{reactor.run()} raises L{ReactorAlreadyRunning} when called when\n        the reactor is already running.\n        \"\"\"\n        events = []\n        def reentrantRun():\n            self.assertRaises(ReactorAlreadyRunning, reactor.run)\n            events.append(\"tested\")\n        reactor = self.buildReactor()\n        reactor.callWhenRunning(reentrantRun)\n        reactor.callWhenRunning(reactor.stop)\n        self.runReactor(reactor)\n        self.assertEqual(events, [\"tested\"])\n\n\n    def test_runWithAsynchronousBeforeStartupTrigger(self):\n        \"\"\"\n        When there is a C{'before'} C{'startup'} trigger which returns an\n        unfired L{Deferred}, C{reactor.run()} starts the reactor and does not\n        return until after C{reactor.stop()} is called\n        \"\"\"\n        events = []\n        def trigger():\n            events.append('trigger')\n            d = Deferred()\n            d.addCallback(callback)\n            reactor.callLater(0, d.callback, None)\n            return d\n        def callback(ignored):\n            events.append('callback')\n            reactor.stop()\n        reactor = self.buildReactor()\n        reactor.addSystemEventTrigger('before', 'startup', trigger)\n        self.runReactor(reactor)\n        self.assertEqual(events, ['trigger', 'callback'])\n\n\n    def test_iterate(self):\n        \"\"\"\n        C{reactor.iterate()} does not block.\n        \"\"\"\n        reactor = self.buildReactor()\n        t = reactor.callLater(5, reactor.crash)\n\n        start = time.time()\n        reactor.iterate(0) # Shouldn't block\n        elapsed = time.time() - start\n\n        self.assertTrue(elapsed < 2)\n        t.cancel()\n\n\n    def test_crash(self):\n        \"\"\"\n        C{reactor.crash()} stops the reactor and does not fire shutdown\n        triggers.\n        \"\"\"\n        reactor = self.buildReactor()\n        events = []\n        reactor.addSystemEventTrigger(\n            \"before\", \"shutdown\",\n            lambda: events.append((\"before\", \"shutdown\")))\n        reactor.callWhenRunning(reactor.callLater, 0, reactor.crash)\n        self.runReactor(reactor)\n        self.assertFalse(reactor.running)\n        self.assertFalse(\n            events,\n            \"Shutdown triggers invoked but they should not have been.\")\n\n\n    def test_runAfterCrash(self):\n        \"\"\"\n        C{reactor.run()} restarts the reactor after it has been stopped by\n        C{reactor.crash()}.\n        \"\"\"\n        events = []\n        def crash():\n            events.append('crash')\n            reactor.crash()\n        reactor = self.buildReactor()\n        reactor.callWhenRunning(crash)\n        self.runReactor(reactor)\n        def stop():\n            events.append(('stop', reactor.running))\n            reactor.stop()\n        reactor.callWhenRunning(stop)\n        self.runReactor(reactor)\n        self.assertEqual(events, ['crash', ('stop', True)])\n\n\n    def test_runAfterStop(self):\n        \"\"\"\n        C{reactor.run()} raises L{ReactorNotRestartable} when called when\n        the reactor is being run after getting stopped priorly.\n        \"\"\"\n        events = []\n        def restart():\n            self.assertRaises(ReactorNotRestartable, reactor.run)\n            events.append('tested')\n        reactor = self.buildReactor()\n        reactor.callWhenRunning(reactor.stop)\n        reactor.addSystemEventTrigger('after', 'shutdown', restart)\n        self.runReactor(reactor)\n        self.assertEqual(events, ['tested'])\n\n\n\nglobals().update(SystemEventTestsBuilder.makeTestCaseClasses())\nglobals().update(ObjectModelIntegrationTests.makeTestCaseClasses())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_coroutines.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nA wrapper for L{twisted.internet.test._awaittests}, as that test module\nincludes keywords not valid in Pythons before 3.5.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom twisted.python.compat import _PY35PLUS, _PY3, execfile\nfrom twisted.python.filepath import FilePath\n\n\nif _PY35PLUS:\n    _path = FilePath(__file__).parent().child(\"_awaittests.py.3only\")\n\n    _g = {\"__name__\": __name__ + \".3-only.awaittests\"}\n    execfile(_path.path, _g)\n    AwaitTests = _g[\"AwaitTests\"]\nelse:\n    from twisted.trial.unittest import TestCase\n\n    class AwaitTests(TestCase):\n        \"\"\"\n        A dummy class to show that this test file was discovered but the tests\n        are unable to be ran in this version of Python.\n        \"\"\"\n        skip = \"async/await is not available before Python 3.5\"\n\n        def test_notAvailable(self):\n            \"\"\"\n            A skipped test to show that this was not ran because the Python is\n            too old.\n            \"\"\"\n\n\nif _PY3:\n    _path = FilePath(__file__).parent().child(\"_yieldfromtests.py.3only\")\n\n    _g = {\"__name__\": __name__ + \".3-only.yieldfromtests\"}\n    execfile(_path.path, _g)\n    YieldFromTests = _g[\"YieldFromTests\"]\nelse:\n    from twisted.trial.unittest import TestCase\n\n    class YieldFromTests(TestCase):\n        \"\"\"\n        A dummy class to show that this test file was discovered but the tests\n        are unable to be ran in this version of Python.\n        \"\"\"\n        skip = \"yield from is not available before Python 3\"\n\n        def test_notAvailable(self):\n            \"\"\"\n            A skipped test to show that this was not ran because the Python is\n            too old.\n            \"\"\"\n\n\n__all__ = [\"AwaitTests\", \"YieldFromTests\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_default.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet.default}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport select, sys\nfrom twisted.trial.unittest import SynchronousTestCase\nfrom twisted.python.runtime import Platform\nfrom twisted.python.reflect import requireModule\nfrom twisted.internet import default\nfrom twisted.internet.default import _getInstallFunction, install\nfrom twisted.internet.test.test_main import NoReactor\nfrom twisted.internet.interfaces import IReactorCore\n\nunix = Platform('posix', 'other')\nlinux = Platform('posix', 'linux2')\nwindows = Platform('nt', 'win32')\nosx = Platform('posix', 'darwin')\n\n\nclass PollReactorTests(SynchronousTestCase):\n    \"\"\"\n    Tests for the cases of L{twisted.internet.default._getInstallFunction}\n    in which it picks the poll(2) or epoll(7)-based reactors.\n    \"\"\"\n\n    def assertIsPoll(self, install):\n        \"\"\"\n        Assert the given function will install the poll() reactor, or select()\n        if poll() is unavailable.\n        \"\"\"\n        if hasattr(select, \"poll\"):\n            self.assertEqual(\n                install.__module__, 'twisted.internet.pollreactor')\n        else:\n            self.assertEqual(\n                install.__module__, 'twisted.internet.selectreactor')\n\n\n    def test_unix(self):\n        \"\"\"\n        L{_getInstallFunction} chooses the poll reactor on arbitrary Unix\n        platforms, falling back to select(2) if it is unavailable.\n        \"\"\"\n        install = _getInstallFunction(unix)\n        self.assertIsPoll(install)\n\n\n    def test_linux(self):\n        \"\"\"\n        L{_getInstallFunction} chooses the epoll reactor on Linux, or poll if\n        epoll is unavailable.\n        \"\"\"\n        install = _getInstallFunction(linux)\n        if requireModule('twisted.internet.epollreactor') is None:\n            self.assertIsPoll(install)\n        else:\n            self.assertEqual(\n                install.__module__, 'twisted.internet.epollreactor')\n\n\n\nclass SelectReactorTests(SynchronousTestCase):\n    \"\"\"\n    Tests for the cases of L{twisted.internet.default._getInstallFunction}\n    in which it picks the select(2)-based reactor.\n    \"\"\"\n    def test_osx(self):\n        \"\"\"\n        L{_getInstallFunction} chooses the select reactor on macOS.\n        \"\"\"\n        install = _getInstallFunction(osx)\n        self.assertEqual(\n            install.__module__, 'twisted.internet.selectreactor')\n\n\n    def test_windows(self):\n        \"\"\"\n        L{_getInstallFunction} chooses the select reactor on Windows.\n        \"\"\"\n        install = _getInstallFunction(windows)\n        self.assertEqual(\n            install.__module__, 'twisted.internet.selectreactor')\n\n\n\nclass InstallationTests(SynchronousTestCase):\n    \"\"\"\n    Tests for actual installation of the reactor.\n    \"\"\"\n\n    def test_install(self):\n        \"\"\"\n        L{install} installs a reactor.\n        \"\"\"\n        with NoReactor():\n            install()\n            self.assertIn(\"twisted.internet.reactor\", sys.modules)\n\n\n    def test_reactor(self):\n        \"\"\"\n        Importing L{twisted.internet.reactor} installs the default reactor if\n        none is installed.\n        \"\"\"\n        installed = []\n        def installer():\n            installed.append(True)\n            return install()\n        self.patch(default, \"install\", installer)\n\n        with NoReactor():\n            from twisted.internet import reactor\n            self.assertTrue(IReactorCore.providedBy(reactor))\n            self.assertEqual(installed, [True])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_error.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet.error}\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.trial.unittest import SynchronousTestCase\nfrom twisted.internet import error\n\n\n\nclass ConnectionAbortedTests(SynchronousTestCase):\n    \"\"\"\n    Tests for the L{twisted.internet.error.ConnectionAborted} exception.\n    \"\"\"\n    def test_str(self):\n        \"\"\"\n        The default message of L{ConnectionAborted} is a sentence which points\n        to L{ITCPTransport.abortConnection()}\n        \"\"\"\n        self.assertEqual(\n            (\"Connection was aborted locally\"\n             \" using ITCPTransport.abortConnection.\"),\n            str(error.ConnectionAborted()),\n        )\n\n\n    def test_strArgs(self):\n        \"\"\"\n        Any arguments passed to L{ConnectionAborted} are included in its\n        message.\n        \"\"\"\n        self.assertEqual(\n            (\"Connection was aborted locally using\"\n             \" ITCPTransport.abortConnection:\"\n             \" foo bar.\"),\n            str(error.ConnectionAborted('foo', 'bar')),\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_fdset.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for implementations of L{IReactorFDSet}.\n\"\"\"\n\n__metaclass__ = type\n\nimport os, socket, traceback\n\nfrom zope.interface import implementer\n\nfrom twisted.python.runtime import platform\nfrom twisted.trial.unittest import SkipTest\nfrom twisted.internet.interfaces import IReactorFDSet, IReadDescriptor\nfrom twisted.internet.abstract import FileDescriptor\nfrom twisted.internet.test.reactormixins import ReactorBuilder\n\n# twisted.internet.tcp nicely defines some names with proper values on\n# several different platforms.\nfrom twisted.internet.tcp import EINPROGRESS, EWOULDBLOCK\n\n\ndef socketpair():\n    serverSocket = socket.socket()\n    serverSocket.bind(('127.0.0.1', 0))\n    serverSocket.listen(1)\n    try:\n        client = socket.socket()\n        try:\n            client.setblocking(False)\n            try:\n                client.connect(('127.0.0.1', serverSocket.getsockname()[1]))\n            except socket.error as e:\n                if e.args[0] not in (EINPROGRESS, EWOULDBLOCK):\n                    raise\n            server, addr = serverSocket.accept()\n        except:\n            client.close()\n            raise\n    finally:\n        serverSocket.close()\n\n    return client, server\n\n\nclass ReactorFDSetTestsBuilder(ReactorBuilder):\n    \"\"\"\n    Builder defining tests relating to L{IReactorFDSet}.\n    \"\"\"\n    requiredInterfaces = [IReactorFDSet]\n\n    def _connectedPair(self):\n        \"\"\"\n        Return the two sockets which make up a new TCP connection.\n        \"\"\"\n        client, server = socketpair()\n        self.addCleanup(client.close)\n        self.addCleanup(server.close)\n        return client, server\n\n\n    def _simpleSetup(self):\n        reactor = self.buildReactor()\n\n        client, server = self._connectedPair()\n\n        fd = FileDescriptor(reactor)\n        fd.fileno = client.fileno\n\n        return reactor, fd, server\n\n\n    def test_addReader(self):\n        \"\"\"\n        C{reactor.addReader()} accepts an L{IReadDescriptor} provider and calls\n        its C{doRead} method when there may be data available on its C{fileno}.\n        \"\"\"\n        reactor, fd, server = self._simpleSetup()\n\n        def removeAndStop():\n            reactor.removeReader(fd)\n            reactor.stop()\n        fd.doRead = removeAndStop\n        reactor.addReader(fd)\n        server.sendall(b'x')\n\n        # The reactor will only stop if it calls fd.doRead.\n        self.runReactor(reactor)\n        # Nothing to assert, just be glad we got this far.\n\n\n    def test_removeReader(self):\n        \"\"\"\n        L{reactor.removeReader()} accepts an L{IReadDescriptor} provider\n        previously passed to C{reactor.addReader()} and causes it to no longer\n        be monitored for input events.\n        \"\"\"\n        reactor, fd, server = self._simpleSetup()\n\n        def fail():\n            self.fail(\"doRead should not be called\")\n        fd.doRead = fail\n\n        reactor.addReader(fd)\n        reactor.removeReader(fd)\n        server.sendall(b'x')\n\n        # Give the reactor two timed event passes to notice that there's I/O\n        # (if it is incorrectly watching for I/O).\n        reactor.callLater(0, reactor.callLater, 0, reactor.stop)\n\n        self.runReactor(reactor)\n        # Getting here means the right thing happened probably.\n\n\n    def test_addWriter(self):\n        \"\"\"\n        C{reactor.addWriter()} accepts an L{IWriteDescriptor} provider and\n        calls its C{doWrite} method when it may be possible to write to its\n        C{fileno}.\n        \"\"\"\n        reactor, fd, server = self._simpleSetup()\n\n        def removeAndStop():\n            reactor.removeWriter(fd)\n            reactor.stop()\n        fd.doWrite = removeAndStop\n        reactor.addWriter(fd)\n\n        self.runReactor(reactor)\n        # Getting here is great.\n\n\n    def _getFDTest(self, kind):\n        \"\"\"\n        Helper for getReaders and getWriters tests.\n        \"\"\"\n        reactor = self.buildReactor()\n        get = getattr(reactor, 'get' + kind + 's')\n        add = getattr(reactor, 'add' + kind)\n        remove = getattr(reactor, 'remove' + kind)\n\n        client, server = self._connectedPair()\n\n        self.assertNotIn(client, get())\n        self.assertNotIn(server, get())\n\n        add(client)\n        self.assertIn(client, get())\n        self.assertNotIn(server, get())\n\n        remove(client)\n        self.assertNotIn(client, get())\n        self.assertNotIn(server, get())\n\n\n    def test_getReaders(self):\n        \"\"\"\n        L{IReactorFDSet.getReaders} reflects the additions and removals made\n        with L{IReactorFDSet.addReader} and L{IReactorFDSet.removeReader}.\n        \"\"\"\n        self._getFDTest('Reader')\n\n\n    def test_removeWriter(self):\n        \"\"\"\n        L{reactor.removeWriter()} accepts an L{IWriteDescriptor} provider\n        previously passed to C{reactor.addWriter()} and causes it to no longer\n        be monitored for outputability.\n        \"\"\"\n        reactor, fd, server = self._simpleSetup()\n\n        def fail():\n            self.fail(\"doWrite should not be called\")\n        fd.doWrite = fail\n\n        reactor.addWriter(fd)\n        reactor.removeWriter(fd)\n\n        # Give the reactor two timed event passes to notice that there's I/O\n        # (if it is incorrectly watching for I/O).\n        reactor.callLater(0, reactor.callLater, 0, reactor.stop)\n\n        self.runReactor(reactor)\n        # Getting here means the right thing happened probably.\n\n\n    def test_getWriters(self):\n        \"\"\"\n        L{IReactorFDSet.getWriters} reflects the additions and removals made\n        with L{IReactorFDSet.addWriter} and L{IReactorFDSet.removeWriter}.\n        \"\"\"\n        self._getFDTest('Writer')\n\n\n    def test_removeAll(self):\n        \"\"\"\n        C{reactor.removeAll()} removes all registered L{IReadDescriptor}\n        providers and all registered L{IWriteDescriptor} providers and returns\n        them.\n        \"\"\"\n        reactor = self.buildReactor()\n\n        reactor, fd, server = self._simpleSetup()\n\n        fd.doRead = lambda: self.fail(\"doRead should not be called\")\n        fd.doWrite = lambda: self.fail(\"doWrite should not be called\")\n\n        server.sendall(b'x')\n\n        reactor.addReader(fd)\n        reactor.addWriter(fd)\n\n        removed = reactor.removeAll()\n\n        # Give the reactor two timed event passes to notice that there's I/O\n        # (if it is incorrectly watching for I/O).\n        reactor.callLater(0, reactor.callLater, 0, reactor.stop)\n\n        self.runReactor(reactor)\n        # Getting here means the right thing happened probably.\n\n        self.assertEqual(removed, [fd])\n\n\n    def test_removedFromReactor(self):\n        \"\"\"\n        A descriptor's C{fileno} method should not be called after the\n        descriptor has been removed from the reactor.\n        \"\"\"\n        reactor = self.buildReactor()\n        descriptor = RemovingDescriptor(reactor)\n        reactor.callWhenRunning(descriptor.start)\n        self.runReactor(reactor)\n        self.assertEqual(descriptor.calls, [])\n\n\n    def test_negativeOneFileDescriptor(self):\n        \"\"\"\n        If L{FileDescriptor.fileno} returns C{-1}, the descriptor is removed\n        from the reactor.\n        \"\"\"\n        reactor = self.buildReactor()\n\n        client, server = self._connectedPair()\n\n        class DisappearingDescriptor(FileDescriptor):\n            _fileno = server.fileno()\n\n            _received = b\"\"\n\n            def fileno(self):\n                return self._fileno\n\n            def doRead(self):\n                self._fileno = -1\n                self._received += server.recv(1)\n                client.send(b'y')\n\n            def connectionLost(self, reason):\n                reactor.stop()\n\n        descriptor = DisappearingDescriptor(reactor)\n        reactor.addReader(descriptor)\n        client.send(b'x')\n        self.runReactor(reactor)\n        self.assertEqual(descriptor._received, b\"x\")\n\n\n    def test_lostFileDescriptor(self):\n        \"\"\"\n        The file descriptor underlying a FileDescriptor may be closed and\n        replaced by another at some point.  Bytes which arrive on the new\n        descriptor must not be delivered to the FileDescriptor which was\n        originally registered with the original descriptor of the same number.\n\n        Practically speaking, this is difficult or impossible to detect.  The\n        implementation relies on C{fileno} raising an exception if the original\n        descriptor has gone away.  If C{fileno} continues to return the original\n        file descriptor value, the reactor may deliver events from that\n        descriptor.  This is a best effort attempt to ease certain debugging\n        situations.  Applications should not rely on it intentionally.\n        \"\"\"\n        reactor = self.buildReactor()\n\n        name = reactor.__class__.__name__\n        if name in ('EPollReactor', 'KQueueReactor', 'CFReactor',\n                    'AsyncioSelectorReactor'):\n            # Closing a file descriptor immediately removes it from the epoll\n            # set without generating a notification.  That means epollreactor\n            # will not call any methods on Victim after the close, so there's\n            # no chance to notice the socket is no longer valid.\n            raise SkipTest(\"%r cannot detect lost file descriptors\" % (name,))\n\n        client, server = self._connectedPair()\n\n        class Victim(FileDescriptor):\n            \"\"\"\n            This L{FileDescriptor} will have its socket closed out from under it\n            and another socket will take its place.  It will raise a\n            socket.error from C{fileno} after this happens (because socket\n            objects remember whether they have been closed), so as long as the\n            reactor calls the C{fileno} method the problem will be detected.\n            \"\"\"\n            def fileno(self):\n                return server.fileno()\n\n            def doRead(self):\n                raise Exception(\"Victim.doRead should never be called\")\n\n            def connectionLost(self, reason):\n                \"\"\"\n                When the problem is detected, the reactor should disconnect this\n                file descriptor.  When that happens, stop the reactor so the\n                test ends.\n                \"\"\"\n                reactor.stop()\n\n        reactor.addReader(Victim())\n\n        # Arrange for the socket to be replaced at some unspecified time.\n        # Significantly, this will not be while any I/O processing code is on\n        # the stack.  It is something that happens independently and cannot be\n        # relied upon to happen at a convenient time, such as within a call to\n        # doRead.\n        def messItUp():\n            newC, newS = self._connectedPair()\n            fileno = server.fileno()\n            server.close()\n            os.dup2(newS.fileno(), fileno)\n            newC.send(b\"x\")\n        reactor.callLater(0, messItUp)\n\n        self.runReactor(reactor)\n\n        # If the implementation feels like logging the exception raised by\n        # MessedUp.fileno, that's fine.\n        self.flushLoggedErrors(socket.error)\n    if platform.isWindows():\n        test_lostFileDescriptor.skip = (\n            \"Cannot duplicate socket filenos on Windows\")\n\n\n    def test_connectionLostOnShutdown(self):\n        \"\"\"\n        Any file descriptors added to the reactor have their C{connectionLost}\n        called when C{reactor.stop} is called.\n        \"\"\"\n        reactor = self.buildReactor()\n\n        class DoNothingDescriptor(FileDescriptor):\n            def doRead(self):\n                return None\n            def doWrite(self):\n                return None\n\n        client, server = self._connectedPair()\n\n        fd1 = DoNothingDescriptor(reactor)\n        fd1.fileno = client.fileno\n        fd2 = DoNothingDescriptor(reactor)\n        fd2.fileno = server.fileno\n        reactor.addReader(fd1)\n        reactor.addWriter(fd2)\n\n        reactor.callWhenRunning(reactor.stop)\n        self.runReactor(reactor)\n        self.assertTrue(fd1.disconnected)\n        self.assertTrue(fd2.disconnected)\n\n\n\n@implementer(IReadDescriptor)\nclass RemovingDescriptor(object):\n    \"\"\"\n    A read descriptor which removes itself from the reactor as soon as it\n    gets a chance to do a read and keeps track of when its own C{fileno}\n    method is called.\n\n    @ivar insideReactor: A flag which is true as long as the reactor has\n        this descriptor as a reader.\n\n    @ivar calls: A list of the bottom of the call stack for any call to\n        C{fileno} when C{insideReactor} is false.\n    \"\"\"\n\n\n    def __init__(self, reactor):\n        self.reactor = reactor\n        self.insideReactor = False\n        self.calls = []\n        self.read, self.write = socketpair()\n\n\n    def start(self):\n        self.insideReactor = True\n        self.reactor.addReader(self)\n        self.write.send(b'a')\n\n\n    def logPrefix(self):\n        return 'foo'\n\n\n    def doRead(self):\n        self.reactor.removeReader(self)\n        self.insideReactor = False\n        self.reactor.stop()\n        self.read.close()\n        self.write.close()\n\n\n    def fileno(self):\n        if not self.insideReactor:\n            self.calls.append(traceback.extract_stack(limit=5)[:-1])\n        return self.read.fileno()\n\n\n    def connectionLost(self, reason):\n        # Ideally we'd close the descriptors here... but actually\n        # connectionLost is never called because we remove ourselves from the\n        # reactor before it stops.\n        pass\n\nglobals().update(ReactorFDSetTestsBuilder.makeTestCaseClasses())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_filedescriptor.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nWhitebox tests for L{twisted.internet.abstract.FileDescriptor}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom zope.interface.verify import verifyClass\n\nfrom twisted.internet.abstract import FileDescriptor\nfrom twisted.internet.interfaces import IPushProducer\nfrom twisted.trial.unittest import SynchronousTestCase\n\n\n\nclass MemoryFile(FileDescriptor):\n    \"\"\"\n    A L{FileDescriptor} customization which writes to a Python list in memory\n    with certain limitations.\n\n    @ivar _written: A C{list} of C{bytes} which have been accepted as written.\n\n    @ivar _freeSpace: A C{int} giving the number of bytes which will be accepted\n        by future writes.\n    \"\"\"\n    connected = True\n\n    def __init__(self):\n        FileDescriptor.__init__(self, reactor=object())\n        self._written = []\n        self._freeSpace = 0\n\n\n    def startWriting(self):\n        pass\n\n\n    def stopWriting(self):\n        pass\n\n\n    def writeSomeData(self, data):\n        \"\"\"\n        Copy at most C{self._freeSpace} bytes from C{data} into C{self._written}.\n\n        @return: A C{int} indicating how many bytes were copied from C{data}.\n        \"\"\"\n        acceptLength = min(self._freeSpace, len(data))\n        if acceptLength:\n            self._freeSpace -= acceptLength\n            self._written.append(data[:acceptLength])\n        return acceptLength\n\n\n\nclass FileDescriptorTests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{FileDescriptor}.\n    \"\"\"\n    def test_writeWithUnicodeRaisesException(self):\n        \"\"\"\n        L{FileDescriptor.write} doesn't accept unicode data.\n        \"\"\"\n        fileDescriptor = FileDescriptor(reactor=object())\n        self.assertRaises(TypeError, fileDescriptor.write, u'foo')\n\n\n    def test_writeSequenceWithUnicodeRaisesException(self):\n        \"\"\"\n        L{FileDescriptor.writeSequence} doesn't accept unicode data.\n        \"\"\"\n        fileDescriptor = FileDescriptor(reactor=object())\n        self.assertRaises(\n            TypeError, fileDescriptor.writeSequence, [b'foo', u'bar', b'baz'])\n\n\n    def test_implementInterfaceIPushProducer(self):\n        \"\"\"\n        L{FileDescriptor} should implement L{IPushProducer}.\n        \"\"\"\n        self.assertTrue(verifyClass(IPushProducer, FileDescriptor))\n\n\n\nclass WriteDescriptorTests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{FileDescriptor}'s implementation of L{IWriteDescriptor}.\n    \"\"\"\n    def test_kernelBufferFull(self):\n        \"\"\"\n        When L{FileDescriptor.writeSomeData} returns C{0} to indicate no more\n        data can be written immediately, L{FileDescriptor.doWrite} returns\n        L{None}.\n        \"\"\"\n        descriptor = MemoryFile()\n        descriptor.write(b\"hello, world\")\n        self.assertIsNone(descriptor.doWrite())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_gireactor.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nGI/GTK3 reactor tests.\n\"\"\"\n\nfrom __future__ import division, absolute_import, print_function\n\nimport sys, os\ntry:\n    from twisted.internet import gireactor\n    from gi.repository import Gio\nexcept ImportError:\n    gireactor = None\n    gtk3reactor = None\nelse:\n    # gtk3reactor may be unavailable even if gireactor is available; in\n    # particular in pygobject 3.4/gtk 3.6, when no X11 DISPLAY is found.\n    try:\n        from twisted.internet import gtk3reactor\n    except ImportError:\n        gtk3reactor = None\n    else:\n        from gi.repository import Gtk\n\nfrom twisted.python.filepath import FilePath\nfrom twisted.python.runtime import platform\nfrom twisted.internet.defer import Deferred\nfrom twisted.internet.error import ReactorAlreadyRunning\nfrom twisted.internet.protocol import ProcessProtocol\nfrom twisted.trial.unittest import TestCase, SkipTest\nfrom twisted.internet.test.reactormixins import ReactorBuilder\nfrom twisted.test.test_twisted import SetAsideModule\nfrom twisted.internet.interfaces import IReactorProcess\nfrom twisted.python.compat import _PY3\n\n# Skip all tests if gi is unavailable:\nif gireactor is None:\n    skip = \"gtk3/gi not importable\"\n\n\n\nclass GApplicationRegistrationTests(ReactorBuilder, TestCase):\n    \"\"\"\n    GtkApplication and GApplication are supported by\n    L{twisted.internet.gtk3reactor} and L{twisted.internet.gireactor}.\n\n    We inherit from L{ReactorBuilder} in order to use some of its\n    reactor-running infrastructure, but don't need its test-creation\n    functionality.\n    \"\"\"\n    def runReactor(self, app, reactor):\n        \"\"\"\n        Register the app, run the reactor, make sure app was activated, and\n        that reactor was running, and that reactor can be stopped.\n        \"\"\"\n        if not hasattr(app, \"quit\"):\n            raise SkipTest(\"Version of PyGObject is too old.\")\n\n        result = []\n        def stop():\n            result.append(\"stopped\")\n            reactor.stop()\n        def activate(widget):\n            result.append(\"activated\")\n            reactor.callLater(0, stop)\n        app.connect('activate', activate)\n\n        # We want reactor.stop() to *always* stop the event loop, even if\n        # someone has called hold() on the application and never done the\n        # corresponding release() -- for more details see\n        # http://developer.gnome.org/gio/unstable/GApplication.html.\n        app.hold()\n\n        reactor.registerGApplication(app)\n        ReactorBuilder.runReactor(self, reactor)\n        self.assertEqual(result, [\"activated\", \"stopped\"])\n\n\n    def test_gApplicationActivate(self):\n        \"\"\"\n        L{Gio.Application} instances can be registered with a gireactor.\n        \"\"\"\n        reactor = gireactor.GIReactor(useGtk=False)\n        self.addCleanup(self.unbuildReactor, reactor)\n        app = Gio.Application(\n            application_id='com.twistedmatrix.trial.gireactor',\n            flags=Gio.ApplicationFlags.FLAGS_NONE)\n\n        self.runReactor(app, reactor)\n\n\n    def test_gtkApplicationActivate(self):\n        \"\"\"\n        L{Gtk.Application} instances can be registered with a gtk3reactor.\n        \"\"\"\n        reactor = gtk3reactor.Gtk3Reactor()\n        self.addCleanup(self.unbuildReactor, reactor)\n        app = Gtk.Application(\n            application_id='com.twistedmatrix.trial.gtk3reactor',\n            flags=Gio.ApplicationFlags.FLAGS_NONE)\n\n        self.runReactor(app, reactor)\n\n    if gtk3reactor is None:\n        test_gtkApplicationActivate.skip = (\n            \"Gtk unavailable (may require running with X11 DISPLAY env set)\")\n\n\n    def test_portable(self):\n        \"\"\"\n        L{gireactor.PortableGIReactor} doesn't support application\n        registration at this time.\n        \"\"\"\n        reactor = gireactor.PortableGIReactor()\n        self.addCleanup(self.unbuildReactor, reactor)\n        app = Gio.Application(\n            application_id='com.twistedmatrix.trial.gireactor',\n            flags=Gio.ApplicationFlags.FLAGS_NONE)\n        self.assertRaises(NotImplementedError,\n                          reactor.registerGApplication, app)\n\n\n    def test_noQuit(self):\n        \"\"\"\n        Older versions of PyGObject lack C{Application.quit}, and so won't\n        allow registration.\n        \"\"\"\n        reactor = gireactor.GIReactor(useGtk=False)\n        self.addCleanup(self.unbuildReactor, reactor)\n        # An app with no \"quit\" method:\n        app = object()\n        exc = self.assertRaises(RuntimeError, reactor.registerGApplication, app)\n        self.assertTrue(exc.args[0].startswith(\n                \"Application registration is not\"))\n\n\n    def test_cantRegisterAfterRun(self):\n        \"\"\"\n        It is not possible to register a C{Application} after the reactor has\n        already started.\n        \"\"\"\n        reactor = gireactor.GIReactor(useGtk=False)\n        self.addCleanup(self.unbuildReactor, reactor)\n        app = Gio.Application(\n            application_id='com.twistedmatrix.trial.gireactor',\n            flags=Gio.ApplicationFlags.FLAGS_NONE)\n\n        def tryRegister():\n            exc = self.assertRaises(ReactorAlreadyRunning,\n                                    reactor.registerGApplication, app)\n            self.assertEqual(exc.args[0],\n                             \"Can't register application after reactor was started.\")\n            reactor.stop()\n        reactor.callLater(0, tryRegister)\n        ReactorBuilder.runReactor(self, reactor)\n\n\n    def test_cantRegisterTwice(self):\n        \"\"\"\n        It is not possible to register more than one C{Application}.\n        \"\"\"\n        reactor = gireactor.GIReactor(useGtk=False)\n        self.addCleanup(self.unbuildReactor, reactor)\n        app = Gio.Application(\n            application_id='com.twistedmatrix.trial.gireactor',\n            flags=Gio.ApplicationFlags.FLAGS_NONE)\n        reactor.registerGApplication(app)\n        app2 = Gio.Application(\n            application_id='com.twistedmatrix.trial.gireactor2',\n            flags=Gio.ApplicationFlags.FLAGS_NONE)\n        exc = self.assertRaises(RuntimeError,\n                                    reactor.registerGApplication, app2)\n        self.assertEqual(exc.args[0],\n                         \"Can't register more than one application instance.\")\n\n\n\nclass PygtkCompatibilityTests(TestCase):\n    \"\"\"\n    pygtk imports are either prevented, or a compatibility layer is used if\n    possible.\n    \"\"\"\n    def test_noCompatibilityLayer(self):\n        \"\"\"\n        If no compatibility layer is present, imports of gobject and friends\n        are disallowed.\n\n        We do this by running a process where we make sure gi.pygtkcompat\n        isn't present.\n        \"\"\"\n        if _PY3:\n            raise SkipTest(\"Python3 always has the compatibility layer.\")\n\n        from twisted.internet import reactor\n        if not IReactorProcess.providedBy(reactor):\n            raise SkipTest(\"No process support available in this reactor.\")\n\n        result = Deferred()\n        class Stdout(ProcessProtocol):\n            data = b\"\"\n\n            def errReceived(self, err):\n                print(err)\n\n            def outReceived(self, data):\n                self.data += data\n\n            def processExited(self, reason):\n                result.callback(self.data)\n\n        path = FilePath(__file__).sibling(b\"process_gireactornocompat.py\").path\n        pyExe = FilePath(sys.executable)._asBytesPath()\n        # Pass in a PYTHONPATH that is the test runner's os.path, to make sure\n        # we're running from a checkout\n        reactor.spawnProcess(Stdout(), pyExe, [pyExe, path],\n                             env={\"PYTHONPATH\": \":\".join(sys.path)})\n        result.addCallback(self.assertEqual, b\"success\")\n        return result\n\n\n    def test_compatibilityLayer(self):\n        \"\"\"\n        If compatibility layer is present, importing gobject uses the gi\n        compatibility layer.\n        \"\"\"\n        if \"gi.pygtkcompat\" not in sys.modules:\n            raise SkipTest(\"This version of gi doesn't include pygtkcompat.\")\n        import gobject\n        self.assertTrue(gobject.__name__.startswith(\"gi.\"))\n\n\n\nclass Gtk3ReactorTests(TestCase):\n    \"\"\"\n    Tests for L{gtk3reactor}.\n    \"\"\"\n\n    def test_requiresDISPLAY(self):\n        \"\"\"\n        On X11, L{gtk3reactor} is unimportable if the C{DISPLAY} environment\n        variable is not set.\n        \"\"\"\n        display = os.environ.get(\"DISPLAY\", None)\n        if display is not None:\n            self.addCleanup(os.environ.__setitem__, \"DISPLAY\", display)\n            del os.environ[\"DISPLAY\"]\n        with SetAsideModule(\"twisted.internet.gtk3reactor\"):\n            exc = self.assertRaises(ImportError,\n                                    __import__, \"twisted.internet.gtk3reactor\")\n            self.assertEqual(\n                exc.args[0],\n                \"Gtk3 requires X11, and no DISPLAY environment variable is set\")\n\n    if platform.getType() != \"posix\" or platform.isMacOSX():\n        test_requiresDISPLAY.skip = \"This test is only relevant when using X11\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_inotify.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for the inotify wrapper in L{twisted.internet.inotify}.\n\"\"\"\nimport sys\n\nfrom twisted.internet import defer, reactor\nfrom twisted.python import filepath, runtime\nfrom twisted.python.reflect import requireModule\nfrom twisted.trial import unittest\n\nif requireModule('twisted.python._inotify') is not None:\n    from twisted.internet import inotify\nelse:\n    inotify = None\n\n\n\nclass INotifyTests(unittest.TestCase):\n    \"\"\"\n    Define all the tests for the basic functionality exposed by\n    L{inotify.INotify}.\n    \"\"\"\n    if not runtime.platform.supportsINotify():\n        skip = \"This platform doesn't support INotify.\"\n\n    def setUp(self):\n        self.dirname = filepath.FilePath(self.mktemp())\n        self.dirname.createDirectory()\n        self.inotify = inotify.INotify()\n        self.inotify.startReading()\n        self.addCleanup(self.inotify.loseConnection)\n\n\n    def test_initializationErrors(self):\n        \"\"\"\n        L{inotify.INotify} emits a C{RuntimeError} when initialized\n        in an environment that doesn't support inotify as we expect it.\n\n        We just try to raise an exception for every possible case in\n        the for loop in L{inotify.INotify._inotify__init__}.\n        \"\"\"\n        class FakeINotify:\n            def init(self):\n                raise inotify.INotifyError()\n        self.patch(inotify.INotify, '_inotify', FakeINotify())\n        self.assertRaises(inotify.INotifyError, inotify.INotify)\n\n\n    def _notificationTest(self, mask, operation, expectedPath=None):\n        \"\"\"\n        Test notification from some filesystem operation.\n\n        @param mask: The event mask to use when setting up the watch.\n\n        @param operation: A function which will be called with the\n            name of a file in the watched directory and which should\n            trigger the event.\n\n        @param expectedPath: Optionally, the name of the path which is\n            expected to come back in the notification event; this will\n            also be passed to C{operation} (primarily useful when the\n            operation is being done to the directory itself, not a\n            file in it).\n\n        @return: A L{Deferred} which fires successfully when the\n            expected event has been received or fails otherwise.\n        \"\"\"\n        if expectedPath is None:\n            expectedPath = self.dirname.child(\"foo.bar\")\n        notified = defer.Deferred()\n        def cbNotified(result):\n            (watch, filename, events) = result\n            self.assertEqual(filename.asBytesMode(), expectedPath.asBytesMode())\n            self.assertTrue(events & mask)\n        notified.addCallback(cbNotified)\n\n        self.inotify.watch(\n            self.dirname, mask=mask,\n            callbacks=[lambda *args: notified.callback(args)])\n        operation(expectedPath)\n        return notified\n\n\n    def test_access(self):\n        \"\"\"\n        Reading from a file in a monitored directory sends an\n        C{inotify.IN_ACCESS} event to the callback.\n        \"\"\"\n        def operation(path):\n            path.setContent(b\"foo\")\n            path.getContent()\n\n        return self._notificationTest(inotify.IN_ACCESS, operation)\n\n\n    def test_modify(self):\n        \"\"\"\n        Writing to a file in a monitored directory sends an\n        C{inotify.IN_MODIFY} event to the callback.\n        \"\"\"\n        def operation(path):\n            with path.open(\"w\") as fObj:\n                fObj.write(b'foo')\n\n        return self._notificationTest(inotify.IN_MODIFY, operation)\n\n\n    def test_attrib(self):\n        \"\"\"\n        Changing the metadata of a file in a monitored directory\n        sends an C{inotify.IN_ATTRIB} event to the callback.\n        \"\"\"\n        def operation(path):\n            path.touch()\n            path.touch()\n\n        return self._notificationTest(inotify.IN_ATTRIB, operation)\n\n\n    def test_closeWrite(self):\n        \"\"\"\n        Closing a file which was open for writing in a monitored\n        directory sends an C{inotify.IN_CLOSE_WRITE} event to the\n        callback.\n        \"\"\"\n        def operation(path):\n            path.open(\"w\").close()\n\n        return self._notificationTest(inotify.IN_CLOSE_WRITE, operation)\n\n\n    def test_closeNoWrite(self):\n        \"\"\"\n        Closing a file which was open for reading but not writing in a\n        monitored directory sends an C{inotify.IN_CLOSE_NOWRITE} event\n        to the callback.\n        \"\"\"\n        def operation(path):\n            path.touch()\n            path.open(\"r\").close()\n\n        return self._notificationTest(inotify.IN_CLOSE_NOWRITE, operation)\n\n\n    def test_open(self):\n        \"\"\"\n        Opening a file in a monitored directory sends an\n        C{inotify.IN_OPEN} event to the callback.\n        \"\"\"\n        def operation(path):\n            path.open(\"w\").close()\n\n        return self._notificationTest(inotify.IN_OPEN, operation)\n\n\n    def test_movedFrom(self):\n        \"\"\"\n        Moving a file out of a monitored directory sends an\n        C{inotify.IN_MOVED_FROM} event to the callback.\n        \"\"\"\n        def operation(path):\n            path.open(\"w\").close()\n            path.moveTo(filepath.FilePath(self.mktemp()))\n\n        return self._notificationTest(inotify.IN_MOVED_FROM, operation)\n\n\n    def test_movedTo(self):\n        \"\"\"\n        Moving a file into a monitored directory sends an\n        C{inotify.IN_MOVED_TO} event to the callback.\n        \"\"\"\n        def operation(path):\n            p = filepath.FilePath(self.mktemp())\n            p.touch()\n            p.moveTo(path)\n\n        return self._notificationTest(inotify.IN_MOVED_TO, operation)\n\n\n    def test_create(self):\n        \"\"\"\n        Creating a file in a monitored directory sends an\n        C{inotify.IN_CREATE} event to the callback.\n        \"\"\"\n        def operation(path):\n            path.open(\"w\").close()\n\n        return self._notificationTest(inotify.IN_CREATE, operation)\n\n\n    def test_delete(self):\n        \"\"\"\n        Deleting a file in a monitored directory sends an\n        C{inotify.IN_DELETE} event to the callback.\n        \"\"\"\n        def operation(path):\n            path.touch()\n            path.remove()\n\n        return self._notificationTest(inotify.IN_DELETE, operation)\n\n\n    def test_deleteSelf(self):\n        \"\"\"\n        Deleting the monitored directory itself sends an\n        C{inotify.IN_DELETE_SELF} event to the callback.\n        \"\"\"\n        def operation(path):\n            path.remove()\n\n        return self._notificationTest(\n            inotify.IN_DELETE_SELF, operation, expectedPath=self.dirname)\n\n\n    def test_moveSelf(self):\n        \"\"\"\n        Renaming the monitored directory itself sends an\n        C{inotify.IN_MOVE_SELF} event to the callback.\n        \"\"\"\n        def operation(path):\n            path.moveTo(filepath.FilePath(self.mktemp()))\n\n        return self._notificationTest(\n            inotify.IN_MOVE_SELF, operation, expectedPath=self.dirname)\n\n\n    def test_simpleSubdirectoryAutoAdd(self):\n        \"\"\"\n        L{inotify.INotify} when initialized with autoAdd==True adds\n        also adds the created subdirectories to the watchlist.\n        \"\"\"\n        def _callback(wp, filename, mask):\n            # We are notified before we actually process new\n            # directories, so we need to defer this check.\n            def _():\n                try:\n                    self.assertTrue(self.inotify._isWatched(subdir))\n                    d.callback(None)\n                except Exception:\n                    d.errback()\n            reactor.callLater(0, _)\n\n        checkMask = inotify.IN_ISDIR | inotify.IN_CREATE\n        self.inotify.watch(\n            self.dirname, mask=checkMask, autoAdd=True,\n            callbacks=[_callback])\n        subdir = self.dirname.child('test')\n        d = defer.Deferred()\n        subdir.createDirectory()\n        return d\n\n\n    def test_simpleDeleteDirectory(self):\n        \"\"\"\n        L{inotify.INotify} removes a directory from the watchlist when\n        it's removed from the filesystem.\n        \"\"\"\n        calls = []\n        def _callback(wp, filename, mask):\n            # We are notified before we actually process new\n            # directories, so we need to defer this check.\n            def _():\n                try:\n                    self.assertTrue(self.inotify._isWatched(subdir))\n                    subdir.remove()\n                except Exception:\n                    d.errback()\n            def _eb():\n                # second call, we have just removed the subdir\n                try:\n                    self.assertFalse(self.inotify._isWatched(subdir))\n                    d.callback(None)\n                except Exception:\n                    d.errback()\n\n            if not calls:\n                # first call, it's the create subdir\n                calls.append(filename)\n                reactor.callLater(0, _)\n\n            else:\n                reactor.callLater(0, _eb)\n\n        checkMask = inotify.IN_ISDIR | inotify.IN_CREATE\n        self.inotify.watch(\n            self.dirname, mask=checkMask, autoAdd=True,\n            callbacks=[_callback])\n        subdir = self.dirname.child('test')\n        d = defer.Deferred()\n        subdir.createDirectory()\n        return d\n\n\n    def test_ignoreDirectory(self):\n        \"\"\"\n        L{inotify.INotify.ignore} removes a directory from the watchlist\n        \"\"\"\n        self.inotify.watch(self.dirname, autoAdd=True)\n        self.assertTrue(self.inotify._isWatched(self.dirname))\n        self.inotify.ignore(self.dirname)\n        self.assertFalse(self.inotify._isWatched(self.dirname))\n\n\n    def test_humanReadableMask(self):\n        \"\"\"\n        L{inotify.humaReadableMask} translates all the possible event\n        masks to a human readable string.\n        \"\"\"\n        for mask, value in inotify._FLAG_TO_HUMAN:\n            self.assertEqual(inotify.humanReadableMask(mask)[0], value)\n\n        checkMask = (\n            inotify.IN_CLOSE_WRITE | inotify.IN_ACCESS | inotify.IN_OPEN)\n        self.assertEqual(\n            set(inotify.humanReadableMask(checkMask)),\n            set(['close_write', 'access', 'open']))\n\n\n    def test_recursiveWatch(self):\n        \"\"\"\n        L{inotify.INotify.watch} with recursive==True will add all the\n        subdirectories under the given path to the watchlist.\n        \"\"\"\n        subdir = self.dirname.child('test')\n        subdir2 = subdir.child('test2')\n        subdir3 = subdir2.child('test3')\n        subdir3.makedirs()\n        dirs = [subdir, subdir2, subdir3]\n        self.inotify.watch(self.dirname, recursive=True)\n        # let's even call this twice so that we test that nothing breaks\n        self.inotify.watch(self.dirname, recursive=True)\n        for d in dirs:\n            self.assertTrue(self.inotify._isWatched(d))\n\n\n    def test_connectionLostError(self):\n        \"\"\"\n        L{inotify.INotify.connectionLost} if there's a problem while closing\n        the fd shouldn't raise the exception but should log the error\n        \"\"\"\n        import os\n        in_ = inotify.INotify()\n        os.close(in_._fd)\n        in_.loseConnection()\n        self.flushLoggedErrors()\n\n    def test_noAutoAddSubdirectory(self):\n        \"\"\"\n        L{inotify.INotify.watch} with autoAdd==False will stop inotify\n        from watching subdirectories created under the watched one.\n        \"\"\"\n        def _callback(wp, fp, mask):\n            # We are notified before we actually process new\n            # directories, so we need to defer this check.\n            def _():\n                try:\n                    self.assertFalse(self.inotify._isWatched(subdir))\n                    d.callback(None)\n                except Exception:\n                    d.errback()\n            reactor.callLater(0, _)\n\n        checkMask = inotify.IN_ISDIR | inotify.IN_CREATE\n        self.inotify.watch(\n            self.dirname, mask=checkMask, autoAdd=False,\n            callbacks=[_callback])\n        subdir = self.dirname.child('test')\n        d = defer.Deferred()\n        subdir.createDirectory()\n        return d\n\n\n    def test_seriesOfWatchAndIgnore(self):\n        \"\"\"\n        L{inotify.INotify} will watch a filepath for events even if the same\n        path is repeatedly added/removed/re-added to the watchpoints.\n        \"\"\"\n        expectedPath = self.dirname.child(\"foo.bar2\")\n        expectedPath.touch()\n\n        notified = defer.Deferred()\n        def cbNotified(result):\n            (ignored, filename, events) = result\n            self.assertEqual(filename.asBytesMode(), expectedPath.asBytesMode())\n            self.assertTrue(events & inotify.IN_DELETE_SELF)\n\n        def callIt(*args):\n            notified.callback(args)\n\n        # Watch, ignore, watch again to get into the state being tested.\n        self.assertTrue(self.inotify.watch(expectedPath, callbacks=[callIt]))\n        self.inotify.ignore(expectedPath)\n        self.assertTrue(\n            self.inotify.watch(\n                expectedPath, mask=inotify.IN_DELETE_SELF, callbacks=[callIt]))\n\n        notified.addCallback(cbNotified)\n\n        # Apparently in kernel version < 2.6.25, inofify has a bug in the way\n        # similar events are coalesced.  So, be sure to generate a different\n        # event here than the touch() at the top of this method might have\n        # generated.\n        expectedPath.remove()\n\n        return notified\n\n\n    def test_ignoreFilePath(self):\n        \"\"\"\n        L{inotify.INotify} will ignore a filepath after it has been removed from\n        the watch list.\n        \"\"\"\n        expectedPath = self.dirname.child(\"foo.bar2\")\n        expectedPath.touch()\n        expectedPath2 = self.dirname.child(\"foo.bar3\")\n        expectedPath2.touch()\n\n        notified = defer.Deferred()\n        def cbNotified(result):\n            (ignored, filename, events) = result\n            self.assertEqual(filename.asBytesMode(), expectedPath2.asBytesMode())\n            self.assertTrue(events & inotify.IN_DELETE_SELF)\n\n        def callIt(*args):\n            notified.callback(args)\n\n        self.assertTrue(\n            self.inotify.watch(\n                expectedPath, inotify.IN_DELETE_SELF, callbacks=[callIt]))\n        notified.addCallback(cbNotified)\n\n        self.assertTrue(\n            self.inotify.watch(\n                expectedPath2, inotify.IN_DELETE_SELF, callbacks=[callIt]))\n\n        self.inotify.ignore(expectedPath)\n\n        expectedPath.remove()\n        expectedPath2.remove()\n\n        return notified\n\n\n    def test_ignoreNonWatchedFile(self):\n        \"\"\"\n        L{inotify.INotify} will raise KeyError if a non-watched filepath is\n        ignored.\n        \"\"\"\n        expectedPath = self.dirname.child(\"foo.ignored\")\n        expectedPath.touch()\n\n        self.assertRaises(KeyError, self.inotify.ignore, expectedPath)\n\n\n    def test_complexSubdirectoryAutoAdd(self):\n        \"\"\"\n        L{inotify.INotify} with autoAdd==True for a watched path\n        generates events for every file or directory already present\n        in a newly created subdirectory under the watched one.\n\n        This tests that we solve a race condition in inotify even though\n        we may generate duplicate events.\n        \"\"\"\n        calls = set()\n        def _callback(wp, filename, mask):\n            calls.add(filename)\n            if len(calls) == 6:\n                try:\n                    self.assertTrue(self.inotify._isWatched(subdir))\n                    self.assertTrue(self.inotify._isWatched(subdir2))\n                    self.assertTrue(self.inotify._isWatched(subdir3))\n                    created = someFiles + [subdir, subdir2, subdir3]\n                    created = {f.asBytesMode() for f in created}\n                    self.assertEqual(len(calls), len(created))\n                    self.assertEqual(calls, created)\n                except Exception:\n                    d.errback()\n                else:\n                    d.callback(None)\n\n        checkMask = inotify.IN_ISDIR | inotify.IN_CREATE\n        self.inotify.watch(\n            self.dirname, mask=checkMask, autoAdd=True,\n            callbacks=[_callback])\n        subdir = self.dirname.child('test')\n        subdir2 = subdir.child('test2')\n        subdir3 = subdir2.child('test3')\n        d = defer.Deferred()\n        subdir3.makedirs()\n\n        someFiles = [subdir.child('file1.dat'),\n                     subdir2.child('file2.dat'),\n                     subdir3.child('file3.dat')]\n        # Add some files in pretty much all the directories so that we\n        # see that we process all of them.\n        for i, filename in enumerate(someFiles):\n            filename.setContent(\n                filename.path.encode(sys.getfilesystemencoding()))\n        return d\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_iocp.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet.iocpreactor}.\n\"\"\"\n\nimport errno\nfrom array import array\nfrom struct import pack\nfrom socket import AF_INET6, AF_INET, SOCK_STREAM, SOL_SOCKET, error, socket\n\nfrom zope.interface.verify import verifyClass\n\nfrom twisted.trial import unittest\nfrom twisted.python.log import msg\nfrom twisted.internet.interfaces import IPushProducer\n\ntry:\n    from twisted.internet.iocpreactor import iocpsupport as _iocp, tcp, udp\n    from twisted.internet.iocpreactor.reactor import IOCPReactor, EVENTS_PER_LOOP, KEY_NORMAL\n    from twisted.internet.iocpreactor.interfaces import IReadWriteHandle\n    from twisted.internet.iocpreactor.const import SO_UPDATE_ACCEPT_CONTEXT\n    from twisted.internet.iocpreactor.abstract import FileHandle\nexcept ImportError:\n    skip = 'This test only applies to IOCPReactor'\n\ntry:\n    socket(AF_INET6, SOCK_STREAM).close()\nexcept error as e:\n    ipv6Skip = str(e)\nelse:\n    ipv6Skip = None\n\nclass SupportTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{twisted.internet.iocpreactor.iocpsupport}, low-level reactor\n    implementation helpers.\n    \"\"\"\n    def _acceptAddressTest(self, family, localhost):\n        \"\"\"\n        Create a C{SOCK_STREAM} connection to localhost using a socket with an\n        address family of C{family} and assert that the result of\n        L{iocpsupport.get_accept_addrs} is consistent with the result of\n        C{socket.getsockname} and C{socket.getpeername}.\n        \"\"\"\n        msg(\"family = %r\" % (family,))\n        port = socket(family, SOCK_STREAM)\n        self.addCleanup(port.close)\n        port.bind(('', 0))\n        port.listen(1)\n        client = socket(family, SOCK_STREAM)\n        self.addCleanup(client.close)\n        client.setblocking(False)\n        try:\n            client.connect((localhost, port.getsockname()[1]))\n        except error as e:\n            self.assertIn(e.errno, (errno.EINPROGRESS, errno.EWOULDBLOCK))\n\n        server = socket(family, SOCK_STREAM)\n        self.addCleanup(server.close)\n        buff = array('B', b'\\0' * 256)\n        self.assertEqual(\n            0, _iocp.accept(port.fileno(), server.fileno(), buff, None))\n        server.setsockopt(\n            SOL_SOCKET, SO_UPDATE_ACCEPT_CONTEXT, pack('P', port.fileno()))\n        self.assertEqual(\n            (family, client.getpeername()[:2], client.getsockname()[:2]),\n            _iocp.get_accept_addrs(server.fileno(), buff))\n\n\n    def test_ipv4AcceptAddress(self):\n        \"\"\"\n        L{iocpsupport.get_accept_addrs} returns a three-tuple of address\n        information about the socket associated with the file descriptor passed\n        to it.  For a connection using IPv4:\n\n          - the first element is C{AF_INET}\n          - the second element is a two-tuple of a dotted decimal notation IPv4\n            address and a port number giving the peer address of the connection\n          - the third element is the same type giving the host address of the\n            connection\n        \"\"\"\n        self._acceptAddressTest(AF_INET, '127.0.0.1')\n\n\n    def test_ipv6AcceptAddress(self):\n        \"\"\"\n        Like L{test_ipv4AcceptAddress}, but for IPv6 connections.  In this case:\n\n          - the first element is C{AF_INET6}\n          - the second element is a two-tuple of a hexadecimal IPv6 address\n            literal and a port number giving the peer address of the connection\n          - the third element is the same type giving the host address of the\n            connection\n        \"\"\"\n        self._acceptAddressTest(AF_INET6, '::1')\n    if ipv6Skip is not None:\n        test_ipv6AcceptAddress.skip = ipv6Skip\n\n\n\nclass IOCPReactorTests(unittest.TestCase):\n    def test_noPendingTimerEvents(self):\n        \"\"\"\n        Test reactor behavior (doIteration) when there are no pending time\n        events.\n        \"\"\"\n        ir = IOCPReactor()\n        ir.wakeUp()\n        self.assertFalse(ir.doIteration(None))\n\n\n    def test_reactorInterfaces(self):\n        \"\"\"\n        Verify that IOCP socket-representing classes implement IReadWriteHandle\n        \"\"\"\n        self.assertTrue(verifyClass(IReadWriteHandle, tcp.Connection))\n        self.assertTrue(verifyClass(IReadWriteHandle, udp.Port))\n\n\n    def test_fileHandleInterfaces(self):\n        \"\"\"\n        Verify that L{Filehandle} implements L{IPushProducer}.\n        \"\"\"\n        self.assertTrue(verifyClass(IPushProducer, FileHandle))\n\n\n    def test_maxEventsPerIteration(self):\n        \"\"\"\n        Verify that we don't lose an event when more than EVENTS_PER_LOOP\n        events occur in the same reactor iteration\n        \"\"\"\n        class FakeFD:\n            counter = 0\n            def logPrefix(self):\n                return 'FakeFD'\n            def cb(self, rc, bytes, evt):\n                self.counter += 1\n\n        ir = IOCPReactor()\n        fd = FakeFD()\n        event = _iocp.Event(fd.cb, fd)\n        for _ in range(EVENTS_PER_LOOP + 1):\n            ir.port.postEvent(0, KEY_NORMAL, event)\n        ir.doIteration(None)\n        self.assertEqual(fd.counter, EVENTS_PER_LOOP)\n        ir.doIteration(0)\n        self.assertEqual(fd.counter, EVENTS_PER_LOOP + 1)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_kqueuereactor.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet.kqueuereactor}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport errno\n\nfrom zope.interface import implementer\n\nfrom twisted.trial.unittest import TestCase\n\ntry:\n    from twisted.internet.kqreactor import KQueueReactor, _IKQueue\n    kqueueSkip = None\nexcept ImportError:\n    kqueueSkip = \"KQueue not available.\"\n\n\ndef _fakeKEvent(*args, **kwargs):\n    \"\"\"\n    Do nothing.\n    \"\"\"\n\n\n\ndef makeFakeKQueue(testKQueue, testKEvent):\n    \"\"\"\n    Create a fake that implements L{_IKQueue}.\n\n    @param testKQueue: Something that acts like L{select.kqueue}.\n    @param testKEvent: Something that acts like L{select.kevent}.\n    @return: An implementation of L{_IKQueue} that includes C{testKQueue} and\n        C{testKEvent}.\n    \"\"\"\n    @implementer(_IKQueue)\n    class FakeKQueue(object):\n        kqueue = testKQueue\n        kevent = testKEvent\n\n    return FakeKQueue()\n\n\n\nclass KQueueTests(TestCase):\n    \"\"\"\n    These are tests for L{KQueueReactor}'s implementation, not its real world\n    behaviour. For that, look at\n    L{twisted.internet.test.reactormixins.ReactorBuilder}.\n    \"\"\"\n    skip = kqueueSkip\n\n    def test_EINTR(self):\n        \"\"\"\n        L{KQueueReactor} handles L{errno.EINTR} in C{doKEvent} by returning.\n        \"\"\"\n        class FakeKQueue(object):\n            \"\"\"\n            A fake KQueue that raises L{errno.EINTR} when C{control} is called,\n            like a real KQueue would if it was interrupted.\n            \"\"\"\n            def control(self, *args, **kwargs):\n                raise OSError(errno.EINTR, \"Interrupted\")\n\n        reactor = KQueueReactor(makeFakeKQueue(FakeKQueue, _fakeKEvent))\n        # This should return cleanly -- should not raise the OSError we're\n        # spawning, nor get upset and raise about the incomplete KQueue fake.\n        reactor.doKEvent(0)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_main.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet.main}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.trial import unittest\nfrom twisted.internet.error import ReactorAlreadyInstalledError\nfrom twisted.internet.main import installReactor\n\nfrom twisted.internet.test.modulehelpers import NoReactor\n\n\nclass InstallReactorTests(unittest.SynchronousTestCase):\n    \"\"\"\n    Tests for L{installReactor}.\n    \"\"\"\n\n    def test_installReactor(self):\n        \"\"\"\n        L{installReactor} installs a new reactor if none is present.\n        \"\"\"\n        with NoReactor():\n            newReactor = object()\n            installReactor(newReactor)\n            from twisted.internet import reactor\n            self.assertIs(newReactor, reactor)\n\n\n    def test_alreadyInstalled(self):\n        \"\"\"\n        If a reactor is already installed, L{installReactor} raises\n        L{ReactorAlreadyInstalledError}.\n        \"\"\"\n        with NoReactor():\n            installReactor(object())\n            self.assertRaises(ReactorAlreadyInstalledError, installReactor,\n                              object())\n\n\n    def test_errorIsAnAssertionError(self):\n        \"\"\"\n        For backwards compatibility, L{ReactorAlreadyInstalledError} is an\n        L{AssertionError}.\n        \"\"\"\n        self.assertTrue(issubclass(ReactorAlreadyInstalledError,\n                        AssertionError))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_newtls.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet._newtls}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.trial import unittest\nfrom twisted.internet import interfaces\nfrom twisted.internet.test.reactormixins import ReactorBuilder\nfrom twisted.internet.test.connectionmixins import (\n    ConnectableProtocol, runProtocolsWithReactor)\nfrom twisted.internet.test.test_tls import SSLCreator, TLSMixin\nfrom twisted.internet.test.test_tls import StartTLSClientCreator\nfrom twisted.internet.test.test_tls import ContextGeneratingMixin\nfrom twisted.internet.test.test_tcp import TCPCreator\ntry:\n    from twisted.protocols import tls\n    from twisted.internet import _newtls\nexcept ImportError:\n    _newtls = None\nfrom zope.interface import implementer\n\n\nclass BypassTLSTests(unittest.TestCase):\n    \"\"\"\n    Tests for the L{_newtls._BypassTLS} class.\n    \"\"\"\n\n    if not _newtls:\n        skip = \"Couldn't import _newtls, perhaps pyOpenSSL is old or missing\"\n\n    def test_loseConnectionPassThrough(self):\n        \"\"\"\n        C{_BypassTLS.loseConnection} calls C{loseConnection} on the base\n        class, while preserving any default argument in the base class'\n        C{loseConnection} implementation.\n        \"\"\"\n        default = object()\n        result = []\n\n        class FakeTransport(object):\n            def loseConnection(self, _connDone=default):\n                result.append(_connDone)\n\n        bypass = _newtls._BypassTLS(FakeTransport, FakeTransport())\n\n        # The default from FakeTransport is used:\n        bypass.loseConnection()\n        self.assertEqual(result, [default])\n\n        # And we can pass our own:\n        notDefault = object()\n        bypass.loseConnection(notDefault)\n        self.assertEqual(result, [default, notDefault])\n\n\n\nclass FakeProducer(object):\n    \"\"\"\n    A producer that does nothing.\n    \"\"\"\n\n    def pauseProducing(self):\n        pass\n\n\n    def resumeProducing(self):\n        pass\n\n\n    def stopProducing(self):\n        pass\n\n\n\n@implementer(interfaces.IHandshakeListener)\nclass ProducerProtocol(ConnectableProtocol):\n    \"\"\"\n    Register a producer, unregister it, and verify the producer hooks up to\n    innards of C{TLSMemoryBIOProtocol}.\n    \"\"\"\n\n    def __init__(self, producer, result):\n        self.producer = producer\n        self.result = result\n\n\n    def handshakeCompleted(self):\n        if not isinstance(self.transport.protocol,\n                          tls.TLSMemoryBIOProtocol):\n            # Either the test or the code have a bug...\n            raise RuntimeError(\"TLSMemoryBIOProtocol not hooked up.\")\n\n        self.transport.registerProducer(self.producer, True)\n        # The producer was registered with the TLSMemoryBIOProtocol:\n        self.result.append(self.transport.protocol._producer._producer)\n\n        self.transport.unregisterProducer()\n        # The producer was unregistered from the TLSMemoryBIOProtocol:\n        self.result.append(self.transport.protocol._producer)\n        self.transport.loseConnection()\n\n\n\nclass ProducerTestsMixin(ReactorBuilder, TLSMixin, ContextGeneratingMixin):\n    \"\"\"\n    Test the new TLS code integrates C{TLSMemoryBIOProtocol} correctly.\n    \"\"\"\n\n    if not _newtls:\n        skip = \"Could not import twisted.internet._newtls\"\n\n    def test_producerSSLFromStart(self):\n        \"\"\"\n        C{registerProducer} and C{unregisterProducer} on TLS transports\n        created as SSL from the get go are passed to the\n        C{TLSMemoryBIOProtocol}, not the underlying transport directly.\n        \"\"\"\n        result = []\n        producer = FakeProducer()\n\n        runProtocolsWithReactor(self, ConnectableProtocol(),\n                                ProducerProtocol(producer, result),\n                                SSLCreator())\n        self.assertEqual(result, [producer, None])\n\n\n    def test_producerAfterStartTLS(self):\n        \"\"\"\n        C{registerProducer} and C{unregisterProducer} on TLS transports\n        created by C{startTLS} are passed to the C{TLSMemoryBIOProtocol}, not\n        the underlying transport directly.\n        \"\"\"\n        result = []\n        producer = FakeProducer()\n\n        runProtocolsWithReactor(self, ConnectableProtocol(),\n                                ProducerProtocol(producer, result),\n                                StartTLSClientCreator())\n        self.assertEqual(result, [producer, None])\n\n\n    def startTLSAfterRegisterProducer(self, streaming):\n        \"\"\"\n        When a producer is registered, and then startTLS is called,\n        the producer is re-registered with the C{TLSMemoryBIOProtocol}.\n        \"\"\"\n        clientContext = self.getClientContext()\n        serverContext = self.getServerContext()\n        result = []\n        producer = FakeProducer()\n\n        class RegisterTLSProtocol(ConnectableProtocol):\n            def connectionMade(self):\n                self.transport.registerProducer(producer, streaming)\n                self.transport.startTLS(serverContext)\n                # Store TLSMemoryBIOProtocol and underlying transport producer\n                # status:\n                if streaming:\n                    # _ProducerMembrane -> producer:\n                    result.append(self.transport.protocol._producer._producer)\n                    result.append(self.transport.producer._producer)\n                else:\n                    # _ProducerMembrane -> _PullToPush -> producer:\n                    result.append(\n                        self.transport.protocol._producer._producer._producer)\n                    result.append(self.transport.producer._producer._producer)\n                self.transport.unregisterProducer()\n                self.transport.loseConnection()\n\n        class StartTLSProtocol(ConnectableProtocol):\n            def connectionMade(self):\n                self.transport.startTLS(clientContext)\n\n        runProtocolsWithReactor(self, RegisterTLSProtocol(),\n                                StartTLSProtocol(), TCPCreator())\n        self.assertEqual(result, [producer, producer])\n\n\n    def test_startTLSAfterRegisterProducerStreaming(self):\n        \"\"\"\n        When a streaming producer is registered, and then startTLS is called,\n        the producer is re-registered with the C{TLSMemoryBIOProtocol}.\n        \"\"\"\n        self.startTLSAfterRegisterProducer(True)\n\n\n    def test_startTLSAfterRegisterProducerNonStreaming(self):\n        \"\"\"\n        When a non-streaming producer is registered, and then startTLS is\n        called, the producer is re-registered with the\n        C{TLSMemoryBIOProtocol}.\n        \"\"\"\n        self.startTLSAfterRegisterProducer(False)\n\n\nglobals().update(ProducerTestsMixin.makeTestCaseClasses())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_pollingfile.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet._pollingfile}.\n\"\"\"\n\nfrom twisted.python.runtime import platform\nfrom twisted.trial.unittest import TestCase\n\nif platform.isWindows():\n    from twisted.internet import _pollingfile\nelse:\n    _pollingfile = None\n\n\n\nclass PollableWritePipeTests(TestCase):\n    \"\"\"\n    Tests for L{_pollingfile._PollableWritePipe}.\n    \"\"\"\n\n    def test_writeUnicode(self):\n        \"\"\"\n        L{_pollingfile._PollableWritePipe.write} raises a C{TypeError} if an\n        attempt is made to append unicode data to the output buffer.\n        \"\"\"\n        p = _pollingfile._PollableWritePipe(1, lambda: None)\n        self.assertRaises(TypeError, p.write, u\"test\")\n\n\n    def test_writeSequenceUnicode(self):\n        \"\"\"\n        L{_pollingfile._PollableWritePipe.writeSequence} raises a C{TypeError}\n        if unicode data is part of the data sequence to be appended to the\n        output buffer.\n        \"\"\"\n        p = _pollingfile._PollableWritePipe(1, lambda: None)\n        self.assertRaises(TypeError, p.writeSequence, [u\"test\"])\n        self.assertRaises(TypeError, p.writeSequence, (u\"test\", ))\n\n\n\n\nif _pollingfile is None:\n    PollableWritePipeTests.skip = \"Test will run only on Windows.\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_process.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for implementations of L{IReactorProcess}.\n\n@var properEnv: A copy of L{os.environ} which has L{bytes} keys/values on POSIX\n    platforms and native L{str} keys/values on Windows.\n\"\"\"\n\nfrom __future__ import division, absolute_import, print_function\n\nimport io\nimport os\nimport signal\nimport sys\nimport threading\nimport twisted\nimport subprocess\n\nfrom twisted.trial.unittest import TestCase\nfrom twisted.internet.test.reactormixins import ReactorBuilder\nfrom twisted.python.log import msg, err\nfrom twisted.python.runtime import platform\nfrom twisted.python.filepath import FilePath, _asFilesystemBytes\nfrom twisted.python.compat import (networkString, range, items,\n                                   bytesEnviron, unicode)\nfrom twisted.internet import utils\nfrom twisted.internet.interfaces import IReactorProcess, IProcessTransport\nfrom twisted.internet.defer import Deferred, succeed\nfrom twisted.internet.protocol import ProcessProtocol\nfrom twisted.internet.error import ProcessDone, ProcessTerminated\n\n\n# Get the current Python executable as a bytestring.\npyExe = FilePath(sys.executable)._asBytesPath()\ntwistedRoot = FilePath(twisted.__file__).parent().parent()\n\n_uidgidSkip = None\nif platform.isWindows():\n    resource = None\n    process = None\n    _uidgidSkip = \"Cannot change UID/GID on Windows\"\n\n    properEnv = dict(os.environ)\n    properEnv[\"PYTHONPATH\"] = os.pathsep.join(sys.path)\nelse:\n    import resource\n    from twisted.internet import process\n    if os.getuid() != 0:\n        _uidgidSkip = \"Cannot change UID/GID except as root\"\n\n    properEnv = bytesEnviron()\n    properEnv[b\"PYTHONPATH\"] = os.pathsep.join(sys.path).encode(\n        sys.getfilesystemencoding())\n\n\n\ndef onlyOnPOSIX(testMethod):\n    \"\"\"\n    Only run this test on POSIX platforms.\n\n    @param testMethod: A test function, being decorated.\n\n    @return: the C{testMethod} argument.\n    \"\"\"\n    if resource is None:\n        testMethod.skip = \"Test only applies to POSIX platforms.\"\n    return testMethod\n\n\n\nclass _ShutdownCallbackProcessProtocol(ProcessProtocol):\n    \"\"\"\n    An L{IProcessProtocol} which fires a Deferred when the process it is\n    associated with ends.\n\n    @ivar received: A C{dict} mapping file descriptors to lists of bytes\n        received from the child process on those file descriptors.\n    \"\"\"\n    def __init__(self, whenFinished):\n        self.whenFinished = whenFinished\n        self.received = {}\n\n\n    def childDataReceived(self, fd, bytes):\n        self.received.setdefault(fd, []).append(bytes)\n\n\n    def processEnded(self, reason):\n        self.whenFinished.callback(None)\n\n\n\nclass ProcessTestsBuilderBase(ReactorBuilder):\n    \"\"\"\n    Base class for L{IReactorProcess} tests which defines some tests which\n    can be applied to PTY or non-PTY uses of C{spawnProcess}.\n\n    Subclasses are expected to set the C{usePTY} attribute to C{True} or\n    C{False}.\n    \"\"\"\n    requiredInterfaces = [IReactorProcess]\n\n\n    def test_processTransportInterface(self):\n        \"\"\"\n        L{IReactorProcess.spawnProcess} connects the protocol passed to it\n        to a transport which provides L{IProcessTransport}.\n        \"\"\"\n        ended = Deferred()\n        protocol = _ShutdownCallbackProcessProtocol(ended)\n\n        reactor = self.buildReactor()\n        transport = reactor.spawnProcess(\n            protocol, pyExe, [pyExe, b\"-c\", b\"\"],\n            usePTY=self.usePTY)\n\n        # The transport is available synchronously, so we can check it right\n        # away (unlike many transport-based tests).  This is convenient even\n        # though it's probably not how the spawnProcess interface should really\n        # work.\n        # We're not using verifyObject here because part of\n        # IProcessTransport is a lie - there are no getHost or getPeer\n        # methods.  See #1124.\n        self.assertTrue(IProcessTransport.providedBy(transport))\n\n        # Let the process run and exit so we don't leave a zombie around.\n        ended.addCallback(lambda ignored: reactor.stop())\n        self.runReactor(reactor)\n\n\n    def _writeTest(self, write):\n        \"\"\"\n        Helper for testing L{IProcessTransport} write functionality.  This\n        method spawns a child process and gives C{write} a chance to write some\n        bytes to it.  It then verifies that the bytes were actually written to\n        it (by relying on the child process to echo them back).\n\n        @param write: A two-argument callable.  This is invoked with a process\n            transport and some bytes to write to it.\n        \"\"\"\n        reactor = self.buildReactor()\n\n        ended = Deferred()\n        protocol = _ShutdownCallbackProcessProtocol(ended)\n\n        bytesToSend = b\"hello, world\" + networkString(os.linesep)\n        program = (\n            b\"import sys\\n\"\n            b\"sys.stdout.write(sys.stdin.readline())\\n\"\n            )\n\n        def startup():\n            transport = reactor.spawnProcess(\n                protocol, pyExe, [pyExe, b\"-c\", program])\n            try:\n                write(transport, bytesToSend)\n            except:\n                err(None, \"Unhandled exception while writing\")\n                transport.signalProcess('KILL')\n        reactor.callWhenRunning(startup)\n\n        ended.addCallback(lambda ignored: reactor.stop())\n\n        self.runReactor(reactor)\n        self.assertEqual(bytesToSend, b\"\".join(protocol.received[1]))\n\n\n    def test_write(self):\n        \"\"\"\n        L{IProcessTransport.write} writes the specified C{bytes} to the standard\n        input of the child process.\n        \"\"\"\n        def write(transport, bytesToSend):\n            transport.write(bytesToSend)\n        self._writeTest(write)\n\n\n    def test_writeSequence(self):\n        \"\"\"\n        L{IProcessTransport.writeSequence} writes the specified C{list} of\n        C{bytes} to the standard input of the child process.\n        \"\"\"\n        def write(transport, bytesToSend):\n            transport.writeSequence([bytesToSend])\n        self._writeTest(write)\n\n\n    def test_writeToChild(self):\n        \"\"\"\n        L{IProcessTransport.writeToChild} writes the specified C{bytes} to the\n        specified file descriptor of the child process.\n        \"\"\"\n        def write(transport, bytesToSend):\n            transport.writeToChild(0, bytesToSend)\n        self._writeTest(write)\n\n\n    def test_writeToChildBadFileDescriptor(self):\n        \"\"\"\n        L{IProcessTransport.writeToChild} raises L{KeyError} if passed a file\n        descriptor which is was not set up by L{IReactorProcess.spawnProcess}.\n        \"\"\"\n        def write(transport, bytesToSend):\n            try:\n                self.assertRaises(KeyError, transport.writeToChild, 13, bytesToSend)\n            finally:\n                # Just get the process to exit so the test can complete\n                transport.write(bytesToSend)\n        self._writeTest(write)\n\n\n    def test_spawnProcessEarlyIsReaped(self):\n        \"\"\"\n        If, before the reactor is started with L{IReactorCore.run}, a\n        process is started with L{IReactorProcess.spawnProcess} and\n        terminates, the process is reaped once the reactor is started.\n        \"\"\"\n        reactor = self.buildReactor()\n\n        # Create the process with no shared file descriptors, so that there\n        # are no other events for the reactor to notice and \"cheat\" with.\n        # We want to be sure it's really dealing with the process exiting,\n        # not some associated event.\n        if self.usePTY:\n            childFDs = None\n        else:\n            childFDs = {}\n\n        # Arrange to notice the SIGCHLD.\n        signaled = threading.Event()\n        def handler(*args):\n            signaled.set()\n        signal.signal(signal.SIGCHLD, handler)\n\n        # Start a process - before starting the reactor!\n        ended = Deferred()\n        reactor.spawnProcess(\n            _ShutdownCallbackProcessProtocol(ended), pyExe,\n            [pyExe, b\"-c\", b\"\"], usePTY=self.usePTY, childFDs=childFDs)\n\n        # Wait for the SIGCHLD (which might have been delivered before we got\n        # here, but that's okay because the signal handler was installed above,\n        # before we could have gotten it).\n        signaled.wait(120)\n        if not signaled.isSet():\n            self.fail(\"Timed out waiting for child process to exit.\")\n\n        # Capture the processEnded callback.\n        result = []\n        ended.addCallback(result.append)\n\n        if result:\n            # The synchronous path through spawnProcess / Process.__init__ /\n            # registerReapProcessHandler was encountered.  There's no reason to\n            # start the reactor, because everything is done already.\n            return\n\n        # Otherwise, though, start the reactor so it can tell us the process\n        # exited.\n        ended.addCallback(lambda ignored: reactor.stop())\n        self.runReactor(reactor)\n\n        # Make sure the reactor stopped because the Deferred fired.\n        self.assertTrue(result)\n\n    if getattr(signal, 'SIGCHLD', None) is None:\n        test_spawnProcessEarlyIsReaped.skip = (\n            \"Platform lacks SIGCHLD, early-spawnProcess test can't work.\")\n\n\n    def test_processExitedWithSignal(self):\n        \"\"\"\n        The C{reason} argument passed to L{IProcessProtocol.processExited} is a\n        L{ProcessTerminated} instance if the child process exits with a signal.\n        \"\"\"\n        sigName = 'TERM'\n        sigNum = getattr(signal, 'SIG' + sigName)\n        exited = Deferred()\n        source = (\n            b\"import sys\\n\"\n            # Talk so the parent process knows the process is running.  This is\n            # necessary because ProcessProtocol.makeConnection may be called\n            # before this process is exec'd.  It would be unfortunate if we\n            # SIGTERM'd the Twisted process while it was on its way to doing\n            # the exec.\n            b\"sys.stdout.write('x')\\n\"\n            b\"sys.stdout.flush()\\n\"\n            b\"sys.stdin.read()\\n\")\n\n        class Exiter(ProcessProtocol):\n            def childDataReceived(self, fd, data):\n                msg('childDataReceived(%d, %r)' % (fd, data))\n                self.transport.signalProcess(sigName)\n\n            def childConnectionLost(self, fd):\n                msg('childConnectionLost(%d)' % (fd,))\n\n            def processExited(self, reason):\n                msg('processExited(%r)' % (reason,))\n                # Protect the Deferred from the failure so that it follows\n                # the callback chain.  This doesn't use the errback chain\n                # because it wants to make sure reason is a Failure.  An\n                # Exception would also make an errback-based test pass, and\n                # that would be wrong.\n                exited.callback([reason])\n\n            def processEnded(self, reason):\n                msg('processEnded(%r)' % (reason,))\n\n        reactor = self.buildReactor()\n        reactor.callWhenRunning(\n            reactor.spawnProcess, Exiter(), pyExe,\n            [pyExe, b\"-c\", source], usePTY=self.usePTY)\n\n        def cbExited(args):\n            failure, = args\n            # Trapping implicitly verifies that it's a Failure (rather than\n            # an exception) and explicitly makes sure it's the right type.\n            failure.trap(ProcessTerminated)\n            err = failure.value\n            if platform.isWindows():\n                # Windows can't really /have/ signals, so it certainly can't\n                # report them as the reason for termination.  Maybe there's\n                # something better we could be doing here, anyway?  Hard to\n                # say.  Anyway, this inconsistency between different platforms\n                # is extremely unfortunate and I would remove it if I\n                # could. -exarkun\n                self.assertIsNone(err.signal)\n                self.assertEqual(err.exitCode, 1)\n            else:\n                self.assertEqual(err.signal, sigNum)\n                self.assertIsNone(err.exitCode)\n\n        exited.addCallback(cbExited)\n        exited.addErrback(err)\n        exited.addCallback(lambda ign: reactor.stop())\n\n        self.runReactor(reactor)\n\n\n    def test_systemCallUninterruptedByChildExit(self):\n        \"\"\"\n        If a child process exits while a system call is in progress, the system\n        call should not be interfered with.  In particular, it should not fail\n        with EINTR.\n\n        Older versions of Twisted installed a SIGCHLD handler on POSIX without\n        using the feature exposed by the SA_RESTART flag to sigaction(2).  The\n        most noticeable problem this caused was for blocking reads and writes to\n        sometimes fail with EINTR.\n        \"\"\"\n        reactor = self.buildReactor()\n        result = []\n\n        def f():\n            try:\n                exe = pyExe.decode(sys.getfilesystemencoding())\n\n                subprocess.Popen([exe, \"-c\", \"import time; time.sleep(0.1)\"])\n                f2 = subprocess.Popen([exe, \"-c\",\n                                       (\"import time; time.sleep(0.5);\"\n                                        \"print(\\'Foo\\')\")],\n                                      stdout=subprocess.PIPE)\n                # The read call below will blow up with an EINTR from the\n                # SIGCHLD from the first process exiting if we install a\n                # SIGCHLD handler without SA_RESTART.  (which we used to do)\n                with f2.stdout:\n                    result.append(f2.stdout.read())\n            finally:\n                reactor.stop()\n\n        reactor.callWhenRunning(f)\n        self.runReactor(reactor)\n        self.assertEqual(result, [b\"Foo\" + os.linesep.encode('ascii')])\n\n\n    @onlyOnPOSIX\n    def test_openFileDescriptors(self):\n        \"\"\"\n        Processes spawned with spawnProcess() close all extraneous file\n        descriptors in the parent.  They do have a stdin, stdout, and stderr\n        open.\n        \"\"\"\n\n        # To test this, we are going to open a file descriptor in the parent\n        # that is unlikely to be opened in the child, then verify that it's not\n        # open in the child.\n        source = networkString(\"\"\"\nimport sys\nsys.path.insert(0, '{0}')\nfrom twisted.internet import process\nsys.stdout.write(repr(process._listOpenFDs()))\nsys.stdout.flush()\"\"\".format(twistedRoot.path))\n\n        r, w = os.pipe()\n        self.addCleanup(os.close, r)\n        self.addCleanup(os.close, w)\n\n        # The call to \"os.listdir()\" (in _listOpenFDs's implementation) opens a\n        # file descriptor (with \"opendir\"), which shows up in _listOpenFDs's\n        # result.  And speaking of \"random\" file descriptors, the code required\n        # for _listOpenFDs itself imports logger, which imports random, which\n        # (depending on your Python version) might leave /dev/urandom open.\n\n        # More generally though, even if we were to use an extremely minimal C\n        # program, the operating system would be within its rights to open file\n        # descriptors we might not know about in the C library's\n        # initialization; things like debuggers, profilers, or nsswitch plugins\n        # might open some and this test should pass in those environments.\n\n        # Although some of these file descriptors aren't predictable, we should\n        # at least be able to select a very large file descriptor which is very\n        # unlikely to be opened automatically in the subprocess.  (Apply a\n        # fudge factor to avoid hard-coding something too near a limit\n        # condition like the maximum possible file descriptor, which a library\n        # might at least hypothetically select.)\n\n        fudgeFactor = 17\n        unlikelyFD = (resource.getrlimit(resource.RLIMIT_NOFILE)[0]\n                      - fudgeFactor)\n\n        os.dup2(w, unlikelyFD)\n        self.addCleanup(os.close, unlikelyFD)\n\n        output = io.BytesIO()\n        class GatheringProtocol(ProcessProtocol):\n            outReceived = output.write\n            def processEnded(self, reason):\n                reactor.stop()\n\n        reactor = self.buildReactor()\n\n        reactor.callWhenRunning(\n            reactor.spawnProcess, GatheringProtocol(), pyExe,\n            [pyExe, b\"-Wignore\", b\"-c\", source], usePTY=self.usePTY)\n\n        self.runReactor(reactor)\n        reportedChildFDs = set(eval(output.getvalue()))\n\n        stdFDs = [0, 1, 2]\n\n        # Unfortunately this assertion is still not *entirely* deterministic,\n        # since hypothetically, any library could open any file descriptor at\n        # any time.  See comment above.\n        self.assertEqual(\n            reportedChildFDs.intersection(set(stdFDs + [unlikelyFD])),\n            set(stdFDs)\n        )\n\n\n    @onlyOnPOSIX\n    def test_errorDuringExec(self):\n        \"\"\"\n        When L{os.execvpe} raises an exception, it will format that exception\n        on stderr as UTF-8, regardless of system encoding information.\n        \"\"\"\n\n        def execvpe(*args, **kw):\n            # Ensure that real traceback formatting has some non-ASCII in it,\n            # by forcing the filename of the last frame to contain non-ASCII.\n            filename = u\"<\\N{SNOWMAN}>\"\n            if not isinstance(filename, str):\n                filename = filename.encode(\"utf-8\")\n            codeobj = compile(\"1/0\", filename, \"single\")\n            eval(codeobj)\n\n        self.patch(os, \"execvpe\", execvpe)\n        self.patch(sys, \"getfilesystemencoding\", lambda: \"ascii\")\n\n        reactor = self.buildReactor()\n        output = io.BytesIO()\n\n        @reactor.callWhenRunning\n        def whenRunning():\n            class TracebackCatcher(ProcessProtocol, object):\n                errReceived = output.write\n                def processEnded(self, reason):\n                    reactor.stop()\n            reactor.spawnProcess(TracebackCatcher(), pyExe,\n                                 [pyExe, b\"-c\", b\"\"])\n\n        self.runReactor(reactor, timeout=30)\n        self.assertIn(u\"\\N{SNOWMAN}\".encode(\"utf-8\"), output.getvalue())\n\n\n    def test_timelyProcessExited(self):\n        \"\"\"\n        If a spawned process exits, C{processExited} will be called in a\n        timely manner.\n        \"\"\"\n        reactor = self.buildReactor()\n\n        class ExitingProtocol(ProcessProtocol):\n            exited = False\n\n            def processExited(protoSelf, reason):\n                protoSelf.exited = True\n                reactor.stop()\n                self.assertEqual(reason.value.exitCode, 0)\n\n        protocol = ExitingProtocol()\n        reactor.callWhenRunning(\n            reactor.spawnProcess, protocol, pyExe,\n            [pyExe, b\"-c\", b\"raise SystemExit(0)\"],\n            usePTY=self.usePTY)\n\n        # This will timeout if processExited isn't called:\n        self.runReactor(reactor, timeout=30)\n        self.assertTrue(protocol.exited)\n\n\n    def _changeIDTest(self, which):\n        \"\"\"\n        Launch a child process, using either the C{uid} or C{gid} argument to\n        L{IReactorProcess.spawnProcess} to change either its UID or GID to a\n        different value.  If the child process reports this hasn't happened,\n        raise an exception to fail the test.\n\n        @param which: Either C{b\"uid\"} or C{b\"gid\"}.\n        \"\"\"\n        program = [\n            \"import os\",\n            \"raise SystemExit(os.get%s() != 1)\" % (which,)]\n\n        container = []\n        class CaptureExitStatus(ProcessProtocol):\n            def processEnded(self, reason):\n                container.append(reason)\n                reactor.stop()\n\n        reactor = self.buildReactor()\n        protocol = CaptureExitStatus()\n        reactor.callWhenRunning(\n            reactor.spawnProcess, protocol, pyExe,\n            [pyExe, \"-c\", \"\\n\".join(program)],\n            **{which: 1})\n\n        self.runReactor(reactor)\n\n        self.assertEqual(0, container[0].value.exitCode)\n\n\n    def test_changeUID(self):\n        \"\"\"\n        If a value is passed for L{IReactorProcess.spawnProcess}'s C{uid}, the\n        child process is run with that UID.\n        \"\"\"\n        self._changeIDTest(\"uid\")\n    if _uidgidSkip is not None:\n        test_changeUID.skip = _uidgidSkip\n\n\n    def test_changeGID(self):\n        \"\"\"\n        If a value is passed for L{IReactorProcess.spawnProcess}'s C{gid}, the\n        child process is run with that GID.\n        \"\"\"\n        self._changeIDTest(\"gid\")\n    if _uidgidSkip is not None:\n        test_changeGID.skip = _uidgidSkip\n\n\n    def test_processExitedRaises(self):\n        \"\"\"\n        If L{IProcessProtocol.processExited} raises an exception, it is logged.\n        \"\"\"\n        # Ideally we wouldn't need to poke the process module; see\n        # https://twistedmatrix.com/trac/ticket/6889\n        reactor = self.buildReactor()\n\n        class TestException(Exception):\n            pass\n\n        class Protocol(ProcessProtocol):\n            def processExited(self, reason):\n                reactor.stop()\n                raise TestException(\"processedExited raised\")\n\n        protocol = Protocol()\n        transport = reactor.spawnProcess(\n               protocol, pyExe, [pyExe, b\"-c\", b\"\"],\n               usePTY=self.usePTY)\n        self.runReactor(reactor)\n\n        # Manually clean-up broken process handler.\n        # Only required if the test fails on systems that support\n        # the process module.\n        if process is not None:\n            for pid, handler in items(process.reapProcessHandlers):\n                if handler is not transport:\n                    continue\n                process.unregisterReapProcessHandler(pid, handler)\n                self.fail(\"After processExited raised, transport was left in\"\n                          \" reapProcessHandlers\")\n\n        self.assertEqual(1, len(self.flushLoggedErrors(TestException)))\n\n\n\nclass ProcessTestsBuilder(ProcessTestsBuilderBase):\n    \"\"\"\n    Builder defining tests relating to L{IReactorProcess} for child processes\n    which do not have a PTY.\n    \"\"\"\n    usePTY = False\n\n    keepStdioOpenProgram = b'twisted.internet.test.process_helper'\n    if platform.isWindows():\n        keepStdioOpenArg = b\"windows\"\n    else:\n        # Just a value that doesn't equal \"windows\"\n        keepStdioOpenArg = b\"\"\n\n\n    # Define this test here because PTY-using processes only have stdin and\n    # stdout and the test would need to be different for that to work.\n    def test_childConnectionLost(self):\n        \"\"\"\n        L{IProcessProtocol.childConnectionLost} is called each time a file\n        descriptor associated with a child process is closed.\n        \"\"\"\n        connected = Deferred()\n        lost = {0: Deferred(), 1: Deferred(), 2: Deferred()}\n\n        class Closer(ProcessProtocol):\n            def makeConnection(self, transport):\n                connected.callback(transport)\n\n            def childConnectionLost(self, childFD):\n                lost[childFD].callback(None)\n\n        target = b\"twisted.internet.test.process_loseconnection\"\n\n        reactor = self.buildReactor()\n        reactor.callWhenRunning(\n            reactor.spawnProcess, Closer(), pyExe,\n            [pyExe, b\"-m\", target], env=properEnv, usePTY=self.usePTY)\n\n        def cbConnected(transport):\n            transport.write(b'2\\n')\n            return lost[2].addCallback(lambda ign: transport)\n        connected.addCallback(cbConnected)\n\n        def lostSecond(transport):\n            transport.write(b'1\\n')\n            return lost[1].addCallback(lambda ign: transport)\n        connected.addCallback(lostSecond)\n\n        def lostFirst(transport):\n            transport.write(b'\\n')\n        connected.addCallback(lostFirst)\n        connected.addErrback(err)\n\n        def cbEnded(ignored):\n            reactor.stop()\n        connected.addCallback(cbEnded)\n\n        self.runReactor(reactor)\n\n\n    # This test is here because PTYProcess never delivers childConnectionLost.\n    def test_processEnded(self):\n        \"\"\"\n        L{IProcessProtocol.processEnded} is called after the child process\n        exits and L{IProcessProtocol.childConnectionLost} is called for each of\n        its file descriptors.\n        \"\"\"\n        ended = Deferred()\n        lost = []\n\n        class Ender(ProcessProtocol):\n            def childDataReceived(self, fd, data):\n                msg('childDataReceived(%d, %r)' % (fd, data))\n                self.transport.loseConnection()\n\n            def childConnectionLost(self, childFD):\n                msg('childConnectionLost(%d)' % (childFD,))\n                lost.append(childFD)\n\n            def processExited(self, reason):\n                msg('processExited(%r)' % (reason,))\n\n            def processEnded(self, reason):\n                msg('processEnded(%r)' % (reason,))\n                ended.callback([reason])\n\n        reactor = self.buildReactor()\n        reactor.callWhenRunning(\n            reactor.spawnProcess, Ender(), pyExe,\n            [pyExe, b\"-m\", self.keepStdioOpenProgram, b\"child\",\n             self.keepStdioOpenArg],\n            env=properEnv, usePTY=self.usePTY)\n\n        def cbEnded(args):\n            failure, = args\n            failure.trap(ProcessDone)\n            self.assertEqual(set(lost), set([0, 1, 2]))\n        ended.addCallback(cbEnded)\n\n        ended.addErrback(err)\n        ended.addCallback(lambda ign: reactor.stop())\n\n        self.runReactor(reactor)\n\n\n    # This test is here because PTYProcess.loseConnection does not actually\n    # close the file descriptors to the child process.  This test needs to be\n    # written fairly differently for PTYProcess.\n    def test_processExited(self):\n        \"\"\"\n        L{IProcessProtocol.processExited} is called when the child process\n        exits, even if file descriptors associated with the child are still\n        open.\n        \"\"\"\n        exited = Deferred()\n        allLost = Deferred()\n        lost = []\n\n        class Waiter(ProcessProtocol):\n            def childDataReceived(self, fd, data):\n                msg('childDataReceived(%d, %r)' % (fd, data))\n\n            def childConnectionLost(self, childFD):\n                msg('childConnectionLost(%d)' % (childFD,))\n                lost.append(childFD)\n                if len(lost) == 3:\n                    allLost.callback(None)\n\n            def processExited(self, reason):\n                msg('processExited(%r)' % (reason,))\n                # See test_processExitedWithSignal\n                exited.callback([reason])\n                self.transport.loseConnection()\n\n        reactor = self.buildReactor()\n        reactor.callWhenRunning(\n            reactor.spawnProcess, Waiter(), pyExe,\n            [pyExe, b\"-u\", b\"-m\", self.keepStdioOpenProgram, b\"child\",\n             self.keepStdioOpenArg],\n            env=properEnv, usePTY=self.usePTY)\n\n        def cbExited(args):\n            failure, = args\n            failure.trap(ProcessDone)\n            msg('cbExited; lost = %s' % (lost,))\n            self.assertEqual(lost, [])\n            return allLost\n        exited.addCallback(cbExited)\n\n        def cbAllLost(ignored):\n            self.assertEqual(set(lost), set([0, 1, 2]))\n        exited.addCallback(cbAllLost)\n\n        exited.addErrback(err)\n        exited.addCallback(lambda ign: reactor.stop())\n\n        self.runReactor(reactor)\n\n\n    def makeSourceFile(self, sourceLines):\n        \"\"\"\n        Write the given list of lines to a text file and return the absolute\n        path to it.\n        \"\"\"\n        script = _asFilesystemBytes(self.mktemp())\n        with open(script, 'wt') as scriptFile:\n            scriptFile.write(os.linesep.join(sourceLines) + os.linesep)\n        return os.path.abspath(script)\n\n\n    def test_shebang(self):\n        \"\"\"\n        Spawning a process with an executable which is a script starting\n        with an interpreter definition line (#!) uses that interpreter to\n        evaluate the script.\n        \"\"\"\n        shebangOutput = b'this is the shebang output'\n\n        scriptFile = self.makeSourceFile([\n                \"#!%s\" % (pyExe.decode('ascii'),),\n                \"import sys\",\n                \"sys.stdout.write('%s')\" % (shebangOutput.decode('ascii'),),\n                \"sys.stdout.flush()\"])\n        os.chmod(scriptFile, 0o700)\n\n        reactor = self.buildReactor()\n\n        def cbProcessExited(args):\n            out, err, code = args\n            msg(\"cbProcessExited((%r, %r, %d))\" % (out, err, code))\n            self.assertEqual(out, shebangOutput)\n            self.assertEqual(err, b\"\")\n            self.assertEqual(code, 0)\n\n        def shutdown(passthrough):\n            reactor.stop()\n            return passthrough\n\n        def start():\n            d = utils.getProcessOutputAndValue(scriptFile, reactor=reactor)\n            d.addBoth(shutdown)\n            d.addCallback(cbProcessExited)\n            d.addErrback(err)\n\n        reactor.callWhenRunning(start)\n        self.runReactor(reactor)\n\n\n    def test_processCommandLineArguments(self):\n        \"\"\"\n        Arguments given to spawnProcess are passed to the child process as\n        originally intended.\n        \"\"\"\n        us = b\"twisted.internet.test.process_cli\"\n\n        args = [b'hello', b'\"', b' \\t|<>^&', br'\"\\\\\"hello\\\\\"', br'\"foo\\ bar baz\\\"\"']\n        # Ensure that all non-NUL characters can be passed too.\n        allChars = \"\".join(map(chr, range(1, 255)))\n        if isinstance(allChars, unicode):\n            allChars.encode(\"utf-8\")\n\n        reactor = self.buildReactor()\n\n        def processFinished(finishedArgs):\n            output, err, code = finishedArgs\n            output = output.split(b'\\0')\n            # Drop the trailing \\0.\n            output.pop()\n            self.assertEqual(args, output)\n\n        def shutdown(result):\n            reactor.stop()\n            return result\n\n        def spawnChild():\n            d = succeed(None)\n            d.addCallback(lambda dummy: utils.getProcessOutputAndValue(\n                pyExe, [b\"-m\", us] + args, env=properEnv,\n                reactor=reactor))\n            d.addCallback(processFinished)\n            d.addBoth(shutdown)\n\n        reactor.callWhenRunning(spawnChild)\n        self.runReactor(reactor)\nglobals().update(ProcessTestsBuilder.makeTestCaseClasses())\n\n\n\nclass PTYProcessTestsBuilder(ProcessTestsBuilderBase):\n    \"\"\"\n    Builder defining tests relating to L{IReactorProcess} for child processes\n    which have a PTY.\n    \"\"\"\n    usePTY = True\n\n    if platform.isWindows():\n        skip = \"PTYs are not supported on Windows.\"\n    elif platform.isMacOSX():\n        skip = \"PTYs are flaky from a Darwin bug. See #8840.\"\n\n        skippedReactors = {\n            \"twisted.internet.pollreactor.PollReactor\":\n                \"macOS's poll() does not support PTYs\"}\nglobals().update(PTYProcessTestsBuilder.makeTestCaseClasses())\n\n\n\nclass PotentialZombieWarningTests(TestCase):\n    \"\"\"\n    Tests for L{twisted.internet.error.PotentialZombieWarning}.\n    \"\"\"\n    def test_deprecated(self):\n        \"\"\"\n        Accessing L{PotentialZombieWarning} via the\n        I{PotentialZombieWarning} attribute of L{twisted.internet.error}\n        results in a deprecation warning being emitted.\n        \"\"\"\n        from twisted.internet import error\n        error.PotentialZombieWarning\n\n        warnings = self.flushWarnings([self.test_deprecated])\n        self.assertEqual(warnings[0]['category'], DeprecationWarning)\n        self.assertEqual(\n            warnings[0]['message'],\n            \"twisted.internet.error.PotentialZombieWarning was deprecated in \"\n            \"Twisted 10.0.0: There is no longer any potential for zombie \"\n            \"process.\")\n        self.assertEqual(len(warnings), 1)\n\n\n\nclass ProcessIsUnimportableOnUnsupportedPlatormsTests(TestCase):\n    \"\"\"\n    Tests to ensure that L{twisted.internet.process} is unimportable on\n    platforms where it does not work (namely Windows).\n    \"\"\"\n    def test_unimportableOnWindows(self):\n        \"\"\"\n        L{twisted.internet.process} is unimportable on Windows.\n        \"\"\"\n        with self.assertRaises(ImportError):\n            import twisted.internet.process\n            twisted.internet.process # shh pyflakes\n\n    if not platform.isWindows():\n        test_unimportableOnWindows.skip = \"Only relevant on Windows.\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_resolver.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for implementations of L{IHostnameResolver} and their interactions with\nreactor implementations.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__metaclass__ = type\n\nfrom collections import defaultdict\n\nfrom socket import (\n    getaddrinfo, gaierror, EAI_NONAME, AF_INET, AF_INET6, AF_UNSPEC,\n    SOCK_STREAM, SOCK_DGRAM, IPPROTO_TCP\n)\nfrom threading import local, Lock\n\nfrom zope.interface import implementer\nfrom zope.interface.verify import verifyObject\n\nfrom twisted.internet.interfaces import (\n    IResolutionReceiver, IResolverSimple, IReactorPluggableNameResolver,\n    IHostnameResolver,\n)\n\nfrom twisted.trial.unittest import (\n    SynchronousTestCase as UnitTest\n)\n\nfrom twisted.python.threadpool import ThreadPool\nfrom twisted._threads import createMemoryWorker, Team, LockWorker\n\nfrom twisted.internet.address import IPv4Address, IPv6Address\nfrom twisted.internet._resolver import (\n    GAIResolver, SimpleResolverComplexifier, ComplexResolverSimplifier\n)\n\nfrom twisted.internet.defer import Deferred\nfrom twisted.internet.error import DNSLookupError\nfrom twisted.internet.base import (\n    PluggableResolverMixin,\n    ReactorBase,\n)\n\n\n\nclass DeterministicThreadPool(ThreadPool, object):\n    \"\"\"\n    Create a deterministic L{ThreadPool} object.\n    \"\"\"\n    def __init__(self, team):\n        \"\"\"\n        Create a L{DeterministicThreadPool} from a L{Team}.\n        \"\"\"\n        self.min = 1\n        self.max = 1\n        self.name = None\n        self.threads = []\n        self._team = team\n\n\n\ndef deterministicPool():\n    \"\"\"\n    Create a deterministic threadpool.\n\n    @return: 2-tuple of L{ThreadPool}, 0-argument C{work} callable; when\n        C{work} is called, do the work.\n    \"\"\"\n    worker, doer = createMemoryWorker()\n    return (\n        DeterministicThreadPool(Team(LockWorker(Lock(), local()),\n                                     (lambda: worker), lambda: None)),\n        doer\n    )\n\n\n\ndef deterministicReactorThreads():\n    \"\"\"\n    Create a deterministic L{IReactorThreads}\n\n    @return: a 2-tuple consisting of an L{IReactorThreads}-like object and a\n        0-argument callable that will perform one unit of work invoked via that\n        object's C{callFromThread} method.\n    \"\"\"\n    worker, doer = createMemoryWorker()\n    class CFT(object):\n        def callFromThread(self, f, *a, **k):\n            worker.do(lambda: f(*a, **k))\n    return CFT(), doer\n\n\n\nclass FakeAddrInfoGetter(object):\n    \"\"\"\n    Test object implementing getaddrinfo.\n    \"\"\"\n\n    def __init__(self):\n        \"\"\"\n        Create a L{FakeAddrInfoGetter}.\n        \"\"\"\n        self.calls = []\n        self.results = defaultdict(list)\n\n\n    def getaddrinfo(self, host, port, family=0, socktype=0, proto=0, flags=0):\n        \"\"\"\n        Mock for L{socket.getaddrinfo}.\n\n        @param host: see L{socket.getaddrinfo}\n\n        @param port: see L{socket.getaddrinfo}\n\n        @param family: see L{socket.getaddrinfo}\n\n        @param socktype: see L{socket.getaddrinfo}\n\n        @param proto: see L{socket.getaddrinfo}\n\n        @param flags: see L{socket.getaddrinfo}\n\n        @return: L{socket.getaddrinfo}\n        \"\"\"\n        self.calls.append((host, port, family, socktype, proto, flags))\n        results = self.results[host]\n        if results:\n            return results\n        else:\n            raise gaierror(EAI_NONAME,\n                           'nodename nor servname provided, or not known')\n\n\n    def addResultForHost(self, host, sockaddr, family=AF_INET,\n                         socktype=SOCK_STREAM, proto=IPPROTO_TCP,\n                         canonname=b\"\"):\n        \"\"\"\n        Add a result for a given hostname.  When this hostname is resolved, the\n        result will be a L{list} of all results C{addResultForHost} has been\n        called with using that hostname so far.\n\n        @param host: The hostname to give this result for.  This will be the\n            next result from L{FakeAddrInfoGetter.getaddrinfo} when passed this\n            host.\n\n        @type canonname: native L{str}\n\n        @param sockaddr: The resulting socket address; should be a 2-tuple for\n            IPv4 or a 4-tuple for IPv6.\n\n        @param family: An C{AF_*} constant that will be returned from\n            C{getaddrinfo}.\n\n        @param socktype: A C{SOCK_*} constant that will be returned from\n            C{getaddrinfo}.\n\n        @param proto: An C{IPPROTO_*} constant that will be returned from\n            C{getaddrinfo}.\n\n        @param canonname: A canonical name that will be returned from\n            C{getaddrinfo}.\n        @type canonname: native L{str}\n        \"\"\"\n        self.results[host].append(\n            (family, socktype, proto, canonname, sockaddr)\n        )\n\n\n\n@implementer(IResolutionReceiver)\nclass ResultHolder(object):\n    \"\"\"\n    A resolution receiver which holds onto the results it received.\n    \"\"\"\n    _started = False\n    _ended = False\n\n    def __init__(self, testCase):\n        \"\"\"\n        Create a L{ResultHolder} with a L{UnitTest}.\n        \"\"\"\n        self._testCase  = testCase\n\n\n    def resolutionBegan(self, hostResolution):\n        \"\"\"\n        Hostname resolution began.\n\n        @param hostResolution: see L{IResolutionReceiver}\n        \"\"\"\n        self._started = True\n        self._resolution = hostResolution\n        self._addresses = []\n\n\n    def addressResolved(self, address):\n        \"\"\"\n        An address was resolved.\n\n        @param address: see L{IResolutionReceiver}\n        \"\"\"\n        self._addresses.append(address)\n\n\n    def resolutionComplete(self):\n        \"\"\"\n        Hostname resolution is complete.\n        \"\"\"\n        self._ended = True\n\n\n\nclass HelperTests(UnitTest):\n    \"\"\"\n    Tests for error cases of helpers used in this module.\n    \"\"\"\n\n    def test_logErrorsInThreads(self):\n        \"\"\"\n        L{DeterministicThreadPool} will log any exceptions that its \"thread\"\n        workers encounter.\n        \"\"\"\n        self.pool, self.doThreadWork = deterministicPool()\n        def divideByZero():\n            return 1 / 0\n        self.pool.callInThread(divideByZero)\n        self.doThreadWork()\n        self.assertEqual(len(self.flushLoggedErrors(ZeroDivisionError)), 1)\n\n\n\nclass HostnameResolutionTests(UnitTest):\n    \"\"\"\n    Tests for hostname resolution.\n    \"\"\"\n\n    def setUp(self):\n        \"\"\"\n        Set up a L{GAIResolver}.\n        \"\"\"\n        self.pool, self.doThreadWork = deterministicPool()\n        self.reactor, self.doReactorWork = deterministicReactorThreads()\n        self.getter = FakeAddrInfoGetter()\n        self.resolver = GAIResolver(self.reactor, lambda: self.pool,\n                                    self.getter.getaddrinfo)\n\n\n    def test_resolveOneHost(self):\n        \"\"\"\n        Resolving an individual hostname that results in one address from\n        getaddrinfo results in a single call each to C{resolutionBegan},\n        C{addressResolved}, and C{resolutionComplete}.\n        \"\"\"\n        receiver = ResultHolder(self)\n        self.getter.addResultForHost(u\"sample.example.com\", (\"4.3.2.1\", 0))\n        resolution = self.resolver.resolveHostName(receiver,\n                                                   u\"sample.example.com\")\n        self.assertIs(receiver._resolution, resolution)\n        self.assertEqual(receiver._started, True)\n        self.assertEqual(receiver._ended, False)\n        self.doThreadWork()\n        self.doReactorWork()\n        self.assertEqual(receiver._ended, True)\n        self.assertEqual(receiver._addresses,\n                         [IPv4Address('TCP', '4.3.2.1', 0)])\n\n\n    def test_resolveOneIPv6Host(self):\n        \"\"\"\n        Resolving an individual hostname that results in one address from\n        getaddrinfo results in a single call each to C{resolutionBegan},\n        C{addressResolved}, and C{resolutionComplete}; C{addressResolved} will\n        receive an L{IPv6Address}.\n        \"\"\"\n        receiver = ResultHolder(self)\n        flowInfo = 1\n        scopeID = 2\n        self.getter.addResultForHost(u\"sample.example.com\",\n                                     (\"::1\", 0, flowInfo, scopeID),\n                                     family=AF_INET6)\n        resolution = self.resolver.resolveHostName(receiver,\n                                                   u\"sample.example.com\")\n        self.assertIs(receiver._resolution, resolution)\n        self.assertEqual(receiver._started, True)\n        self.assertEqual(receiver._ended, False)\n        self.doThreadWork()\n        self.doReactorWork()\n        self.assertEqual(receiver._ended, True)\n        self.assertEqual(receiver._addresses,\n                         [IPv6Address('TCP', '::1', 0, flowInfo, scopeID)])\n\n\n    def test_gaierror(self):\n        \"\"\"\n        Resolving a hostname that results in C{getaddrinfo} raising a\n        L{gaierror} will result in the L{IResolutionReceiver} receiving a call\n        to C{resolutionComplete} with no C{addressResolved} calls in between;\n        no failure is logged.\n        \"\"\"\n        receiver = ResultHolder(self)\n        resolution = self.resolver.resolveHostName(receiver,\n                                                   u\"sample.example.com\")\n        self.assertIs(receiver._resolution, resolution)\n        self.doThreadWork()\n        self.doReactorWork()\n        self.assertEqual(receiver._started, True)\n        self.assertEqual(receiver._ended, True)\n        self.assertEqual(receiver._addresses, [])\n\n\n    def _resolveOnlyTest(self, addrTypes, expectedAF):\n        \"\"\"\n        Verify that the given set of address types results in the given C{AF_}\n        constant being passed to C{getaddrinfo}.\n\n        @param addrTypes: iterable of L{IAddress} implementers\n\n        @param expectedAF: an C{AF_*} constant\n        \"\"\"\n        receiver = ResultHolder(self)\n        resolution = self.resolver.resolveHostName(\n            receiver, u\"sample.example.com\", addressTypes=addrTypes\n        )\n        self.assertIs(receiver._resolution, resolution)\n        self.doThreadWork()\n        self.doReactorWork()\n        host, port, family, socktype, proto, flags = self.getter.calls[0]\n        self.assertEqual(family, expectedAF)\n\n\n    def test_resolveOnlyIPv4(self):\n        \"\"\"\n        When passed an C{addressTypes} parameter containing only\n        L{IPv4Address}, L{GAIResolver} will pass C{AF_INET} to C{getaddrinfo}.\n        \"\"\"\n        self._resolveOnlyTest([IPv4Address], AF_INET)\n\n\n    def test_resolveOnlyIPv6(self):\n        \"\"\"\n        When passed an C{addressTypes} parameter containing only\n        L{IPv6Address}, L{GAIResolver} will pass C{AF_INET6} to C{getaddrinfo}.\n        \"\"\"\n        self._resolveOnlyTest([IPv6Address], AF_INET6)\n\n\n    def test_resolveBoth(self):\n        \"\"\"\n        When passed an C{addressTypes} parameter containing both L{IPv4Address}\n        and L{IPv6Address} (or the default of C{None}, which carries the same\n        meaning), L{GAIResolver} will pass C{AF_UNSPEC} to C{getaddrinfo}.\n        \"\"\"\n        self._resolveOnlyTest([IPv4Address, IPv6Address], AF_UNSPEC)\n        self._resolveOnlyTest(None, AF_UNSPEC)\n\n\n    def test_transportSemanticsToSocketType(self):\n        \"\"\"\n        When passed a C{transportSemantics} paramter, C{'TCP'} (the value\n        present in L{IPv4Address.type} to indicate a stream transport) maps to\n        C{SOCK_STREAM} and C{'UDP'} maps to C{SOCK_DGRAM}.\n        \"\"\"\n        receiver = ResultHolder(self)\n        self.resolver.resolveHostName(receiver, u\"example.com\",\n                                      transportSemantics='TCP')\n        receiver2 = ResultHolder(self)\n        self.resolver.resolveHostName(receiver2, u\"example.com\",\n                                      transportSemantics='UDP')\n        self.doThreadWork()\n        self.doReactorWork()\n        self.doThreadWork()\n        self.doReactorWork()\n        host, port, family, socktypeT, proto, flags = self.getter.calls[0]\n        host, port, family, socktypeU, proto, flags = self.getter.calls[1]\n        self.assertEqual(socktypeT, SOCK_STREAM)\n        self.assertEqual(socktypeU, SOCK_DGRAM)\n\n\n    def test_socketTypeToAddressType(self):\n        \"\"\"\n        When L{GAIResolver} receives a C{SOCK_DGRAM} result from\n        C{getaddrinfo}, it returns a C{'TCP'} L{IPv4Address} or L{IPv6Address};\n        if it receives C{SOCK_STREAM} then it returns a C{'UDP'} type of same.\n        \"\"\"\n        receiver = ResultHolder(self)\n        flowInfo = 1\n        scopeID = 2\n        for socktype in SOCK_STREAM, SOCK_DGRAM:\n            self.getter.addResultForHost(\n                \"example.com\", (\"::1\", 0, flowInfo, scopeID), family=AF_INET6,\n                socktype=socktype\n            )\n            self.getter.addResultForHost(\n                \"example.com\", (\"127.0.0.3\", 0), family=AF_INET,\n                socktype=socktype\n            )\n        self.resolver.resolveHostName(receiver, u\"example.com\")\n        self.doThreadWork()\n        self.doReactorWork()\n        stream4, stream6, dgram4, dgram6 = receiver._addresses\n        self.assertEqual(stream4.type, 'TCP')\n        self.assertEqual(stream6.type, 'TCP')\n        self.assertEqual(dgram4.type, 'UDP')\n        self.assertEqual(dgram6.type, 'UDP')\n\n\n\n@implementer(IResolverSimple)\nclass SillyResolverSimple(object):\n    \"\"\"\n    Trivial implementation of L{IResolverSimple}\n    \"\"\"\n    def __init__(self):\n        \"\"\"\n        Create a L{SillyResolverSimple} with a queue of requests it is working\n        on.\n        \"\"\"\n        self._requests = []\n\n\n    def getHostByName(self, name, timeout=()):\n        \"\"\"\n        Implement L{IResolverSimple.getHostByName}.\n\n        @param name: see L{IResolverSimple.getHostByName}.\n\n        @param timeout: see L{IResolverSimple.getHostByName}.\n\n        @return: see L{IResolverSimple.getHostByName}.\n        \"\"\"\n        self._requests.append(Deferred())\n        return self._requests[-1]\n\n\n\nclass LegacyCompatibilityTests(UnitTest, object):\n    \"\"\"\n    Older applications may supply an object to the reactor via\n    C{installResolver} that only provides L{IResolverSimple}.\n    L{SimpleResolverComplexifier} is a wrapper for an L{IResolverSimple}.\n    \"\"\"\n\n    def test_success(self):\n        \"\"\"\n        L{SimpleResolverComplexifier} translates C{resolveHostName} into\n        L{IResolutionReceiver.addressResolved}.\n        \"\"\"\n        simple = SillyResolverSimple()\n        complex = SimpleResolverComplexifier(simple)\n        receiver = ResultHolder(self)\n        self.assertEqual(receiver._started, False)\n        complex.resolveHostName(receiver, u\"example.com\")\n        self.assertEqual(receiver._started, True)\n        self.assertEqual(receiver._ended, False)\n        self.assertEqual(receiver._addresses, [])\n        simple._requests[0].callback(\"192.168.1.1\")\n        self.assertEqual(receiver._addresses,\n                         [IPv4Address('TCP', '192.168.1.1', 0)])\n        self.assertEqual(receiver._ended, True)\n\n\n    def test_failure(self):\n        \"\"\"\n        L{SimpleResolverComplexifier} translates a known error result from\n        L{IResolverSimple.resolveHostName} into an empty result.\n        \"\"\"\n        simple = SillyResolverSimple()\n        complex = SimpleResolverComplexifier(simple)\n        receiver = ResultHolder(self)\n        self.assertEqual(receiver._started, False)\n        complex.resolveHostName(receiver, u\"example.com\")\n        self.assertEqual(receiver._started, True)\n        self.assertEqual(receiver._ended, False)\n        self.assertEqual(receiver._addresses, [])\n        simple._requests[0].errback(DNSLookupError(\"nope\"))\n        self.assertEqual(receiver._ended, True)\n        self.assertEqual(receiver._addresses, [])\n\n\n    def test_error(self):\n        \"\"\"\n        L{SimpleResolverComplexifier} translates an unknown error result from\n        L{IResolverSimple.resolveHostName} into an empty result and a logged\n        error.\n        \"\"\"\n        simple = SillyResolverSimple()\n        complex = SimpleResolverComplexifier(simple)\n        receiver = ResultHolder(self)\n        self.assertEqual(receiver._started, False)\n        complex.resolveHostName(receiver, u\"example.com\")\n        self.assertEqual(receiver._started, True)\n        self.assertEqual(receiver._ended, False)\n        self.assertEqual(receiver._addresses, [])\n        simple._requests[0].errback(ZeroDivisionError(\"zow\"))\n        self.assertEqual(len(self.flushLoggedErrors(ZeroDivisionError)), 1)\n        self.assertEqual(receiver._ended, True)\n        self.assertEqual(receiver._addresses, [])\n\n\n    def test_simplifier(self):\n        \"\"\"\n        L{ComplexResolverSimplifier} translates an L{IHostnameResolver} into an\n        L{IResolverSimple} for applications that still expect the old\n        interfaces to be in place.\n        \"\"\"\n        self.pool, self.doThreadWork = deterministicPool()\n        self.reactor, self.doReactorWork = deterministicReactorThreads()\n        self.getter = FakeAddrInfoGetter()\n        self.resolver = GAIResolver(self.reactor, lambda: self.pool,\n                                    self.getter.getaddrinfo)\n        simpleResolver = ComplexResolverSimplifier(self.resolver)\n        self.getter.addResultForHost('example.com', ('192.168.3.4', 4321))\n        success = simpleResolver.getHostByName('example.com')\n        failure = simpleResolver.getHostByName('nx.example.com')\n        self.doThreadWork()\n        self.doReactorWork()\n        self.doThreadWork()\n        self.doReactorWork()\n        self.assertEqual(self.failureResultOf(failure).type, DNSLookupError)\n        self.assertEqual(self.successResultOf(success), '192.168.3.4')\n\n\n    def test_portNumber(self):\n        \"\"\"\n        L{SimpleResolverComplexifier} preserves the C{port} argument passed to\n        C{resolveHostName} in its returned addresses.\n        \"\"\"\n        simple = SillyResolverSimple()\n        complex = SimpleResolverComplexifier(simple)\n        receiver = ResultHolder(self)\n        complex.resolveHostName(receiver, u\"example.com\", 4321)\n        self.assertEqual(receiver._started, True)\n        self.assertEqual(receiver._ended, False)\n        self.assertEqual(receiver._addresses, [])\n        simple._requests[0].callback(\"192.168.1.1\")\n        self.assertEqual(receiver._addresses,\n                         [IPv4Address('TCP', '192.168.1.1', 4321)])\n        self.assertEqual(receiver._ended, True)\n\n\n\nclass JustEnoughReactor(ReactorBase):\n    \"\"\"\n    Just enough subclass implementation to be a valid L{ReactorBase} subclass.\n    \"\"\"\n    def installWaker(self):\n        \"\"\"\n        Do nothing.\n        \"\"\"\n\n\n\nclass ReactorInstallationTests(UnitTest, object):\n    \"\"\"\n    Tests for installing old and new resolvers onto a\n    L{PluggableResolverMixin} and L{ReactorBase} (from which all of Twisted's\n    reactor implementations derive).\n    \"\"\"\n\n    def test_interfaceCompliance(self):\n        \"\"\"\n        L{PluggableResolverMixin} (and its subclasses) implement both\n        L{IReactorPluggableNameResolver} and L{IReactorPluggableResolver}.\n        \"\"\"\n        reactor = PluggableResolverMixin()\n        verifyObject(IReactorPluggableNameResolver, reactor)\n        verifyObject(IResolverSimple, reactor.resolver)\n        verifyObject(IHostnameResolver, reactor.nameResolver)\n\n\n    def test_installingOldStyleResolver(self):\n        \"\"\"\n        L{PluggableResolverMixin} will wrap an L{IResolverSimple} in a\n        complexifier.\n        \"\"\"\n        reactor = PluggableResolverMixin()\n        it = SillyResolverSimple()\n        verifyObject(IResolverSimple, reactor.installResolver(it))\n        self.assertIsInstance(reactor.nameResolver, SimpleResolverComplexifier)\n        self.assertIs(reactor.nameResolver._simpleResolver, it)\n\n\n    def test_defaultToGAIResolver(self):\n        \"\"\"\n        L{ReactorBase} defaults to using a L{GAIResolver}.\n        \"\"\"\n        reactor = JustEnoughReactor()\n        self.assertIsInstance(reactor.nameResolver, GAIResolver)\n        self.assertIs(reactor.nameResolver._getaddrinfo, getaddrinfo)\n        self.assertIsInstance(reactor.resolver, ComplexResolverSimplifier)\n        self.assertIs(reactor.nameResolver._reactor, reactor)\n        self.assertIs(reactor.resolver._nameResolver, reactor.nameResolver)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_serialport.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet.serialport}.\n\"\"\"\n\nfrom twisted.trial import unittest\nfrom twisted.python.failure import Failure\nfrom twisted.internet.protocol import Protocol\nfrom twisted.internet.error import ConnectionDone\ntry:\n    from twisted.internet import serialport\nexcept ImportError:\n    serialport = None\n\n\n\nclass DoNothing(object):\n    \"\"\"\n    Object with methods that do nothing.\n    \"\"\"\n\n    def __init__(self, *args, **kwargs):\n        pass\n\n\n    def __getattr__(self, attr):\n        return lambda *args, **kwargs: None\n\n\n\nclass SerialPortTests(unittest.TestCase):\n    \"\"\"\n    Minimal testing for Twisted's serial port support.\n\n    See ticket #2462 for the eventual full test suite.\n    \"\"\"\n\n    if serialport is None:\n        skip = \"Serial port support is not available.\"\n\n\n    def test_connectionMadeLost(self):\n        \"\"\"\n        C{connectionMade} and C{connectionLost} are called on the protocol by\n        the C{SerialPort}.\n        \"\"\"\n        # Serial port that doesn't actually connect to anything:\n        class DummySerialPort(serialport.SerialPort):\n            _serialFactory = DoNothing\n\n            def _finishPortSetup(self):\n                pass # override default win32 actions\n\n        events = []\n\n        class SerialProtocol(Protocol):\n            def connectionMade(self):\n                events.append(\"connectionMade\")\n\n            def connectionLost(self, reason):\n                events.append((\"connectionLost\", reason))\n\n        # Creation of port should result in connectionMade call:\n        port = DummySerialPort(SerialProtocol(), \"\", reactor=DoNothing())\n        self.assertEqual(events, [\"connectionMade\"])\n\n        # Simulate reactor calling connectionLost on the SerialPort:\n        f = Failure(ConnectionDone())\n        port.connectionLost(f)\n        self.assertEqual(events, [\"connectionMade\", (\"connectionLost\", f)])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_sigchld.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet._sigchld}, an alternate, superior SIGCHLD\nmonitoring API.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport os, signal, errno\n\nfrom twisted.python.runtime import platformType\nfrom twisted.python.log import msg\nfrom twisted.trial.unittest import SynchronousTestCase\nif platformType == \"posix\":\n    from twisted.internet.fdesc import setNonBlocking\n    from twisted.internet._signals import installHandler, isDefaultHandler\nelse:\n    skip = \"These tests can only run on POSIX platforms.\"\n\n\nclass SetWakeupSIGCHLDTests(SynchronousTestCase):\n    \"\"\"\n    Tests for the L{signal.set_wakeup_fd} implementation of the\n    L{installHandler} and L{isDefaultHandler} APIs.\n    \"\"\"\n\n    def pipe(self):\n        \"\"\"\n        Create a non-blocking pipe which will be closed after the currently\n        running test.\n        \"\"\"\n        read, write = os.pipe()\n        self.addCleanup(os.close, read)\n        self.addCleanup(os.close, write)\n        setNonBlocking(read)\n        setNonBlocking(write)\n        return read, write\n\n\n    def setUp(self):\n        \"\"\"\n        Save the current SIGCHLD handler as reported by L{signal.signal} and\n        the current file descriptor registered with L{installHandler}.\n        \"\"\"\n        handler = signal.getsignal(signal.SIGCHLD)\n        if handler != signal.SIG_DFL:\n            self.signalModuleHandler = handler\n            signal.signal(signal.SIGCHLD, signal.SIG_DFL)\n        else:\n            self.signalModuleHandler = None\n\n        self.oldFD = installHandler(-1)\n\n        if self.signalModuleHandler is not None and self.oldFD != -1:\n            msg(\"Previous test didn't clean up after its SIGCHLD setup: %r %r\"\n                % (self.signalModuleHandler, self.oldFD))\n\n\n    def tearDown(self):\n        \"\"\"\n        Restore whatever signal handler was present when setUp ran.\n        \"\"\"\n        # If tests set up any kind of handlers, clear them out.\n        installHandler(-1)\n        signal.signal(signal.SIGCHLD, signal.SIG_DFL)\n\n        # Now restore whatever the setup was before the test ran.\n        if self.signalModuleHandler is not None:\n            signal.signal(signal.SIGCHLD, self.signalModuleHandler)\n        elif self.oldFD != -1:\n            installHandler(self.oldFD)\n\n\n    def test_isDefaultHandler(self):\n        \"\"\"\n        L{isDefaultHandler} returns true if the SIGCHLD handler is SIG_DFL,\n        false otherwise.\n        \"\"\"\n        self.assertTrue(isDefaultHandler())\n        signal.signal(signal.SIGCHLD, signal.SIG_IGN)\n        self.assertFalse(isDefaultHandler())\n        signal.signal(signal.SIGCHLD, signal.SIG_DFL)\n        self.assertTrue(isDefaultHandler())\n        signal.signal(signal.SIGCHLD, lambda *args: None)\n        self.assertFalse(isDefaultHandler())\n\n\n    def test_returnOldFD(self):\n        \"\"\"\n        L{installHandler} returns the previously registered file descriptor.\n        \"\"\"\n        read, write = self.pipe()\n        oldFD = installHandler(write)\n        self.assertEqual(installHandler(oldFD), write)\n\n\n    def test_uninstallHandler(self):\n        \"\"\"\n        C{installHandler(-1)} removes the SIGCHLD handler completely.\n        \"\"\"\n        read, write = self.pipe()\n        self.assertTrue(isDefaultHandler())\n        installHandler(write)\n        self.assertFalse(isDefaultHandler())\n        installHandler(-1)\n        self.assertTrue(isDefaultHandler())\n\n\n    def test_installHandler(self):\n        \"\"\"\n        The file descriptor passed to L{installHandler} has a byte written to\n        it when SIGCHLD is delivered to the process.\n        \"\"\"\n        read, write = self.pipe()\n        installHandler(write)\n\n        exc = self.assertRaises(OSError, os.read, read, 1)\n        self.assertEqual(exc.errno, errno.EAGAIN)\n\n        os.kill(os.getpid(), signal.SIGCHLD)\n\n        self.assertEqual(len(os.read(read, 5)), 1)\n\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_stdio.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet.stdio}.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom twisted.python.runtime import platform\nfrom twisted.internet.test.reactormixins import ReactorBuilder\nfrom twisted.internet.protocol import Protocol\n\nif not platform.isWindows():\n    from twisted.internet.stdio import StandardIO\n\n\n\nclass StdioFilesTests(ReactorBuilder):\n    \"\"\"\n    L{StandardIO} supports reading and writing to filesystem files.\n    \"\"\"\n\n    def setUp(self):\n        path = self.mktemp()\n        open(path, \"wb\").close()\n        self.extraFile = open(path, \"rb+\")\n        self.addCleanup(self.extraFile.close)\n\n\n    def test_addReader(self):\n        \"\"\"\n        Adding a filesystem file reader to a reactor will make sure it is\n        polled.\n        \"\"\"\n        reactor = self.buildReactor()\n\n        class DataProtocol(Protocol):\n            data = b\"\"\n            def dataReceived(self, data):\n                self.data += data\n                # It'd be better to stop reactor on connectionLost, but that\n                # fails on FreeBSD, probably due to\n                # http://bugs.python.org/issue9591:\n                if self.data == b\"hello!\":\n                    reactor.stop()\n\n        path = self.mktemp()\n\n        with open(path, \"wb\") as f:\n            f.write(b\"hello!\")\n\n        with open(path, \"rb\") as f:\n            # Read bytes from a file, deliver them to a protocol instance:\n            protocol = DataProtocol()\n            StandardIO(protocol, stdin=f.fileno(),\n                       stdout=self.extraFile.fileno(),\n                       reactor=reactor)\n            self.runReactor(reactor)\n\n        self.assertEqual(protocol.data, b\"hello!\")\n\n\n    def test_addWriter(self):\n        \"\"\"\n        Adding a filesystem file writer to a reactor will make sure it is\n        polled.\n        \"\"\"\n        reactor = self.buildReactor()\n\n        class DisconnectProtocol(Protocol):\n            def connectionLost(self, reason):\n                reactor.stop()\n\n        path = self.mktemp()\n\n        with open(path, \"wb\") as f:\n            # Write bytes to a transport, hopefully have them written to a\n            # file:\n            protocol = DisconnectProtocol()\n            StandardIO(protocol, stdout=f.fileno(),\n                       stdin=self.extraFile.fileno(), reactor=reactor)\n            protocol.transport.write(b\"hello\")\n            protocol.transport.write(b\", world\")\n            protocol.transport.loseConnection()\n\n            self.runReactor(reactor)\n\n        with open(path, \"rb\") as f:\n            self.assertEqual(f.read(), b\"hello, world\")\n\n\n    def test_removeReader(self):\n        \"\"\"\n        Removing a filesystem file reader from a reactor will make sure it is\n        no longer polled.\n        \"\"\"\n        reactor = self.buildReactor()\n        self.addCleanup(self.unbuildReactor, reactor)\n\n        path = self.mktemp()\n        open(path, \"wb\").close()\n\n        with open(path, \"rb\") as f:\n            # Have the reader added:\n            stdio = StandardIO(Protocol(), stdin=f.fileno(),\n                               stdout=self.extraFile.fileno(),\n                               reactor=reactor)\n            self.assertIn(stdio._reader, reactor.getReaders())\n            stdio._reader.stopReading()\n            self.assertNotIn(stdio._reader, reactor.getReaders())\n\n\n    def test_removeWriter(self):\n        \"\"\"\n        Removing a filesystem file writer from a reactor will make sure it is\n        no longer polled.\n        \"\"\"\n        reactor = self.buildReactor()\n        self.addCleanup(self.unbuildReactor, reactor)\n\n        # Cleanup might fail if file is GCed too soon:\n        self.f = f = open(self.mktemp(), \"wb\")\n\n        # Have the reader added:\n        protocol = Protocol()\n        stdio = StandardIO(protocol, stdout=f.fileno(),\n                           stdin=self.extraFile.fileno(),\n                           reactor=reactor)\n        protocol.transport.write(b\"hello\")\n        self.assertIn(stdio._writer, reactor.getWriters())\n        stdio._writer.stopWriting()\n        self.assertNotIn(stdio._writer, reactor.getWriters())\n\n\n    def test_removeAll(self):\n        \"\"\"\n        Calling C{removeAll} on a reactor includes descriptors that are\n        filesystem files.\n        \"\"\"\n        reactor = self.buildReactor()\n        self.addCleanup(self.unbuildReactor, reactor)\n\n        path = self.mktemp()\n        open(path, \"wb\").close()\n\n        # Cleanup might fail if file is GCed too soon:\n        self.f = f = open(path, \"rb\")\n\n        # Have the reader added:\n        stdio = StandardIO(Protocol(), stdin=f.fileno(),\n                           stdout=self.extraFile.fileno(), reactor=reactor)\n        # And then removed:\n        removed = reactor.removeAll()\n        self.assertIn(stdio._reader, removed)\n        self.assertNotIn(stdio._reader, reactor.getReaders())\n\n\n    def test_getReaders(self):\n        \"\"\"\n        C{reactor.getReaders} includes descriptors that are filesystem files.\n        \"\"\"\n        reactor = self.buildReactor()\n        self.addCleanup(self.unbuildReactor, reactor)\n\n        path = self.mktemp()\n        open(path, \"wb\").close()\n\n        # Cleanup might fail if file is GCed too soon:\n        with open(path, \"rb\") as f:\n            # Have the reader added:\n            stdio = StandardIO(Protocol(), stdin=f.fileno(),\n                               stdout=self.extraFile.fileno(), reactor=reactor)\n            self.assertIn(stdio._reader, reactor.getReaders())\n\n\n    def test_getWriters(self):\n        \"\"\"\n        C{reactor.getWriters} includes descriptors that are filesystem files.\n        \"\"\"\n        reactor = self.buildReactor()\n        self.addCleanup(self.unbuildReactor, reactor)\n\n        # Cleanup might fail if file is GCed too soon:\n        self.f = f = open(self.mktemp(), \"wb\")\n\n        # Have the reader added:\n        stdio = StandardIO(Protocol(), stdout=f.fileno(),\n                           stdin=self.extraFile.fileno(), reactor=reactor)\n        self.assertNotIn(stdio._writer, reactor.getWriters())\n        stdio._writer.startWriting()\n        self.assertIn(stdio._writer, reactor.getWriters())\n\n    if platform.isWindows():\n        skip = (\"StandardIO does not accept stdout as an argument to Windows. \"\n                \"Testing redirection to a file is therefore harder.\")\n\n\nglobals().update(StdioFilesTests.makeTestCaseClasses())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_tcp.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for implementations of L{IReactorTCP} and the TCP parts of\nL{IReactorSocket}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__metaclass__ = type\n\nimport errno\nimport gc\nimport io\nimport os\nimport socket\n\nfrom functools import wraps\n\nimport attr\n\nfrom zope.interface import Interface, implementer\nfrom zope.interface.verify import verifyClass, verifyObject\n\nfrom twisted.logger import Logger\nfrom twisted.python.compat import long\nfrom twisted.python.runtime import platform\nfrom twisted.python.failure import Failure\nfrom twisted.python import log\n\nfrom twisted.trial.unittest import SkipTest, SynchronousTestCase, TestCase\nfrom twisted.internet.error import (\n    ConnectionLost, UserError, ConnectionRefusedError, ConnectionDone,\n    ConnectionAborted, DNSLookupError, NoProtocol,\n    ConnectBindError, ConnectionClosed,\n)\nfrom twisted.internet.test.connectionmixins import (\n    LogObserverMixin, ConnectionTestsMixin, StreamClientTestsMixin,\n    findFreePort, ConnectableProtocol, EndpointCreator,\n    runProtocolsWithReactor, Stop, BrokenContextFactory)\nfrom twisted.internet.test.reactormixins import (\n    ReactorBuilder, needsRunningReactor, stopOnError)\nfrom twisted.internet.interfaces import (\n    ILoggingContext, IConnector, IReactorFDSet, IReactorSocket, IReactorTCP,\n    IResolverSimple, ITLSTransport)\nfrom twisted.internet.address import IPv4Address, IPv6Address\nfrom twisted.internet.defer import (\n    Deferred, DeferredList, maybeDeferred, gatherResults, succeed, fail)\nfrom twisted.internet.endpoints import TCP4ServerEndpoint, TCP4ClientEndpoint\nfrom twisted.internet.protocol import ServerFactory, ClientFactory, Protocol\nfrom twisted.internet.interfaces import (\n    IPushProducer, IPullProducer, IHalfCloseableProtocol)\nfrom twisted.internet.tcp import (\n    _BuffersLogs,\n    Connection,\n    _FileDescriptorReservation,\n    _IFileDescriptorReservation,\n    _NullFileDescriptorReservation,\n    Server,\n    _resolveIPv6,\n)\nfrom twisted.internet.test.test_core import ObjectModelIntegrationMixin\nfrom twisted.test.test_tcp import MyClientFactory, MyServerFactory\nfrom twisted.test.test_tcp import ClosingFactory, ClientStartStopFactory\nfrom twisted.test.proto_helpers import MemoryReactor, StringTransport\n\ntry:\n    from OpenSSL import SSL\nexcept ImportError:\n    useSSL = False\nelse:\n    from twisted.internet.ssl import ClientContextFactory\n    useSSL = True\n\ns = None\ntry:\n    s = socket.socket(socket.AF_INET6, socket.SOCK_STREAM)\n    s.bind(('::1', 0))\nexcept socket.error as e:\n    ipv6Skip = str(e)\nelse:\n    ipv6Skip = None\nif s is not None:\n    s.close()\n\n\n\nif platform.isWindows():\n    from twisted.internet.test import _win32ifaces\n    getLinkLocalIPv6Addresses = _win32ifaces.win32GetLinkLocalIPv6Addresses\n\n    SKIP_EMFILE = \"Reserved EMFILE file descriptor not supported on Windows.\"\nelse:\n    try:\n        from twisted.internet.test import _posixifaces\n    except ImportError:\n        getLinkLocalIPv6Addresses = lambda: []\n    else:\n        getLinkLocalIPv6Addresses = _posixifaces.posixGetLinkLocalIPv6Addresses\n\n    SKIP_EMFILE = None\n\n\n\ndef getLinkLocalIPv6Address():\n    \"\"\"\n    Find and return a configured link local IPv6 address including a scope\n    identifier using the % separation syntax.  If the system has no link local\n    IPv6 addresses, raise L{SkipTest} instead.\n\n    @raise SkipTest: if no link local address can be found or if the\n        C{netifaces} module is not available.\n\n    @return: a C{str} giving the address\n    \"\"\"\n    addresses = getLinkLocalIPv6Addresses()\n    if addresses:\n        return addresses[0]\n    raise SkipTest(\"Link local IPv6 address unavailable\")\n\n\n\ndef connect(client, destination):\n    \"\"\"\n    Connect a socket to the given destination.\n\n    @param client: A C{socket.socket}.\n\n    @param destination: A tuple of (host, port). The host is a C{str}, the\n        port a C{int}. If the C{host} is an IPv6 IP, the address is resolved\n        using C{getaddrinfo} and the first version found is used.\n    \"\"\"\n    (host, port) = destination\n    if '%' in host or ':' in host:\n        address = socket.getaddrinfo(host, port)[0][4]\n    else:\n        address = (host, port)\n    client.connect(address)\n\n\n\nclass FakeSocket(object):\n    \"\"\"\n    A fake for L{socket.socket} objects.\n\n    @ivar data: A C{str} giving the data which will be returned from\n        L{FakeSocket.recv}.\n\n    @ivar sendBuffer: A C{list} of the objects passed to L{FakeSocket.send}.\n    \"\"\"\n    def __init__(self, data):\n        self.data = data\n        self.sendBuffer = []\n\n    def setblocking(self, blocking):\n        self.blocking = blocking\n\n    def recv(self, size):\n        return self.data\n\n    def send(self, bytes):\n        \"\"\"\n        I{Send} all of C{bytes} by accumulating it into C{self.sendBuffer}.\n\n        @return: The length of C{bytes}, indicating all the data has been\n            accepted.\n        \"\"\"\n        self.sendBuffer.append(bytes)\n        return len(bytes)\n\n\n    def shutdown(self, how):\n        \"\"\"\n        Shutdown is not implemented.  The method is provided since real sockets\n        have it and some code expects it.  No behavior of L{FakeSocket} is\n        affected by a call to it.\n        \"\"\"\n\n\n    def close(self):\n        \"\"\"\n        Close is not implemented.  The method is provided since real sockets\n        have it and some code expects it.  No behavior of L{FakeSocket} is\n        affected by a call to it.\n        \"\"\"\n\n\n    def setsockopt(self, *args):\n        \"\"\"\n        Setsockopt is not implemented.  The method is provided since\n        real sockets have it and some code expects it.  No behavior of\n        L{FakeSocket} is affected by a call to it.\n        \"\"\"\n\n\n    def fileno(self):\n        \"\"\"\n        Return a fake file descriptor.  If actually used, this will have no\n        connection to this L{FakeSocket} and will probably cause surprising\n        results.\n        \"\"\"\n        return 1\n\n\n\nclass FakeSocketTests(TestCase):\n    \"\"\"\n    Test that the FakeSocket can be used by the doRead method of L{Connection}\n    \"\"\"\n\n    def test_blocking(self):\n        skt = FakeSocket(b\"someData\")\n        skt.setblocking(0)\n        self.assertEqual(skt.blocking, 0)\n\n\n    def test_recv(self):\n        skt = FakeSocket(b\"someData\")\n        self.assertEqual(skt.recv(10), b\"someData\")\n\n\n    def test_send(self):\n        \"\"\"\n        L{FakeSocket.send} accepts the entire string passed to it, adds it to\n        its send buffer, and returns its length.\n        \"\"\"\n        skt = FakeSocket(b\"\")\n        count = skt.send(b\"foo\")\n        self.assertEqual(count, 3)\n        self.assertEqual(skt.sendBuffer, [b\"foo\"])\n\n\n\nclass FakeProtocol(Protocol):\n    \"\"\"\n    An L{IProtocol} that returns a value from its dataReceived method.\n    \"\"\"\n    def dataReceived(self, data):\n        \"\"\"\n        Return something other than L{None} to trigger a deprecation warning for\n        that behavior.\n        \"\"\"\n        return ()\n\n\n\n@implementer(IReactorFDSet)\nclass _FakeFDSetReactor(object):\n    \"\"\"\n    An in-memory implementation of L{IReactorFDSet}, which records the current\n    sets of active L{IReadDescriptor} and L{IWriteDescriptor}s.\n\n    @ivar _readers: The set of L{IReadDescriptor}s active on this\n        L{_FakeFDSetReactor}\n    @type _readers: L{set}\n\n    @ivar _writers: The set of L{IWriteDescriptor}s active on this\n        L{_FakeFDSetReactor}\n    @ivar _writers: L{set}\n    \"\"\"\n\n    def __init__(self):\n        self._readers = set()\n        self._writers = set()\n\n\n    def addReader(self, reader):\n        self._readers.add(reader)\n\n\n    def removeReader(self, reader):\n        if reader in self._readers:\n            self._readers.remove(reader)\n\n\n    def addWriter(self, writer):\n        self._writers.add(writer)\n\n\n    def removeWriter(self, writer):\n        if writer in self._writers:\n            self._writers.remove(writer)\n\n\n    def removeAll(self):\n        result = self.getReaders() + self.getWriters()\n        self.__init__()\n        return result\n\n\n    def getReaders(self):\n        return list(self._readers)\n\n\n    def getWriters(self):\n        return list(self._writers)\n\nverifyClass(IReactorFDSet, _FakeFDSetReactor)\n\n\n\nclass TCPServerTests(TestCase):\n    \"\"\"\n    Whitebox tests for L{twisted.internet.tcp.Server}.\n    \"\"\"\n    def setUp(self):\n        self.reactor = _FakeFDSetReactor()\n        class FakePort(object):\n            _realPortNumber = 3\n        self.skt = FakeSocket(b\"\")\n        self.protocol = Protocol()\n        self.server = Server(\n            self.skt, self.protocol, (\"\", 0), FakePort(), None, self.reactor)\n\n\n    def test_writeAfterDisconnect(self):\n        \"\"\"\n        L{Server.write} discards bytes passed to it if called after it has lost\n        its connection.\n        \"\"\"\n        self.server.connectionLost(\n            Failure(Exception(\"Simulated lost connection\")))\n        self.server.write(b\"hello world\")\n        self.assertEqual(self.skt.sendBuffer, [])\n\n\n    def test_writeAfterDisconnectAfterTLS(self):\n        \"\"\"\n        L{Server.write} discards bytes passed to it if called after it has lost\n        its connection when the connection had started TLS.\n        \"\"\"\n        self.server.TLS = True\n        self.test_writeAfterDisconnect()\n\n\n    def test_writeSequenceAfterDisconnect(self):\n        \"\"\"\n        L{Server.writeSequence} discards bytes passed to it if called after it\n        has lost its connection.\n        \"\"\"\n        self.server.connectionLost(\n            Failure(Exception(\"Simulated lost connection\")))\n        self.server.writeSequence([b\"hello world\"])\n        self.assertEqual(self.skt.sendBuffer, [])\n\n\n    def test_writeSequenceAfterDisconnectAfterTLS(self):\n        \"\"\"\n        L{Server.writeSequence} discards bytes passed to it if called after it\n        has lost its connection when the connection had started TLS.\n        \"\"\"\n        self.server.TLS = True\n        self.test_writeSequenceAfterDisconnect()\n\n\n\nclass TCPConnectionTests(TestCase):\n    \"\"\"\n    Whitebox tests for L{twisted.internet.tcp.Connection}.\n    \"\"\"\n    def test_doReadWarningIsRaised(self):\n        \"\"\"\n        When an L{IProtocol} implementation that returns a value from its\n        C{dataReceived} method, a deprecated warning is emitted.\n        \"\"\"\n        skt = FakeSocket(b\"someData\")\n        protocol = FakeProtocol()\n        conn = Connection(skt, protocol)\n        conn.doRead()\n        warnings = self.flushWarnings([FakeProtocol.dataReceived])\n        self.assertEqual(warnings[0]['category'], DeprecationWarning)\n        self.assertEqual(\n            warnings[0][\"message\"],\n            \"Returning a value other than None from \"\n            \"twisted.internet.test.test_tcp.FakeProtocol.dataReceived \"\n            \"is deprecated since Twisted 11.0.0.\")\n        self.assertEqual(len(warnings), 1)\n\n\n    def test_noTLSBeforeStartTLS(self):\n        \"\"\"\n        The C{TLS} attribute of a L{Connection} instance is C{False} before\n        L{Connection.startTLS} is called.\n        \"\"\"\n        skt = FakeSocket(b\"\")\n        protocol = FakeProtocol()\n        conn = Connection(skt, protocol)\n        self.assertFalse(conn.TLS)\n\n\n    def test_tlsAfterStartTLS(self):\n        \"\"\"\n        The C{TLS} attribute of a L{Connection} instance is C{True} after\n        L{Connection.startTLS} is called.\n        \"\"\"\n        skt = FakeSocket(b\"\")\n        protocol = FakeProtocol()\n        conn = Connection(skt, protocol, reactor=_FakeFDSetReactor())\n        conn._tlsClientDefault = True\n        conn.startTLS(ClientContextFactory(), True)\n        self.assertTrue(conn.TLS)\n    if not useSSL:\n        test_tlsAfterStartTLS.skip = \"No SSL support available\"\n\n\n\nclass TCPCreator(EndpointCreator):\n    \"\"\"\n    Create IPv4 TCP endpoints for L{runProtocolsWithReactor}-based tests.\n    \"\"\"\n\n    interface = \"127.0.0.1\"\n\n    def server(self, reactor):\n        \"\"\"\n        Create a server-side TCP endpoint.\n        \"\"\"\n        return TCP4ServerEndpoint(reactor, 0, interface=self.interface)\n\n\n    def client(self, reactor, serverAddress):\n        \"\"\"\n        Create a client end point that will connect to the given address.\n\n        @type serverAddress: L{IPv4Address}\n        \"\"\"\n        return TCP4ClientEndpoint(reactor, self.interface, serverAddress.port)\n\n\n\nclass TCP6Creator(TCPCreator):\n    \"\"\"\n    Create IPv6 TCP endpoints for\n    C{ReactorBuilder.runProtocolsWithReactor}-based tests.\n\n    The endpoint types in question here are still the TCP4 variety, since\n    these simply pass through IPv6 address literals to the reactor, and we are\n    only testing address literals, not name resolution (as name resolution has\n    not yet been implemented).  See http://twistedmatrix.com/trac/ticket/4470\n    for more specific information about new endpoint classes.  The naming is\n    slightly misleading, but presumably if you're passing an IPv6 literal, you\n    know what you're asking for.\n    \"\"\"\n    def __init__(self):\n        self.interface = getLinkLocalIPv6Address()\n\n\n\n@implementer(IResolverSimple)\nclass FakeResolver(object):\n    \"\"\"\n    A resolver implementation based on a C{dict} mapping names to addresses.\n    \"\"\"\n\n    def __init__(self, names):\n        self.names = names\n\n\n    def getHostByName(self, name, timeout):\n        \"\"\"\n        Return the address mapped to C{name} if it exists, or raise a\n        C{DNSLookupError}.\n\n        @param name: The name to resolve.\n\n        @param timeout: The lookup timeout, ignore here.\n        \"\"\"\n        try:\n            return succeed(self.names[name])\n        except KeyError:\n            return fail(DNSLookupError(\"FakeResolver couldn't find \" + name))\n\n\n\nclass TCPClientTestsBase(ReactorBuilder, ConnectionTestsMixin,\n                         StreamClientTestsMixin):\n    \"\"\"\n    Base class for builders defining tests related to\n    L{IReactorTCP.connectTCP}.  Classes which uses this in must provide all of\n    the documented instance variables in order to specify how the test works.\n    These are documented as instance variables rather than declared as methods\n    due to some peculiar inheritance ordering concerns, but they are\n    effectively abstract methods.\n\n    @ivar endpoints: A client/server endpoint creator appropriate to the\n        address family being tested.\n    @type endpoints: L{twisted.internet.test.connectionmixins.EndpointCreator}\n\n    @ivar interface: An IP address literal to locally bind a socket to as well\n        as to connect to.  This can be any valid interface for the local host.\n    @type interface: C{str}\n\n    @ivar port: An unused local listening port to listen on and connect to.\n        This will be used in conjunction with the C{interface}.  (Depending on\n        what they're testing, some tests will locate their own port with\n        L{findFreePort} instead.)\n    @type port: C{int}\n\n    @ivar family: an address family constant, such as L{socket.AF_INET},\n        L{socket.AF_INET6}, or L{socket.AF_UNIX}, which indicates the address\n        family of the transport type under test.\n    @type family: C{int}\n\n    @ivar addressClass: the L{twisted.internet.interfaces.IAddress} implementor\n        associated with the transport type under test.  Must also be a\n        3-argument callable which produces an instance of same.\n    @type addressClass: C{type}\n\n    @ivar fakeDomainName: A fake domain name to use, to simulate hostname\n        resolution and to distinguish between hostnames and IP addresses where\n        necessary.\n    @type fakeDomainName: C{str}\n    \"\"\"\n    requiredInterfaces = (IReactorTCP,)\n\n    _port = None\n\n    @property\n    def port(self):\n        \"\"\"\n        Return the port number to connect to, using C{self._port} set up by\n        C{listen} if available.\n\n        @return: The port number to connect to.\n        @rtype: C{int}\n        \"\"\"\n        if self._port is not None:\n            return self._port.getHost().port\n        return findFreePort(self.interface, self.family)[1]\n\n\n    @property\n    def interface(self):\n        \"\"\"\n        Return the interface attribute from the endpoints object.\n        \"\"\"\n        return self.endpoints.interface\n\n\n    def listen(self, reactor, factory):\n        \"\"\"\n        Start a TCP server with the given C{factory}.\n\n        @param reactor: The reactor to create the TCP port in.\n\n        @param factory: The server factory.\n\n        @return: A TCP port instance.\n        \"\"\"\n        self._port = reactor.listenTCP(0, factory, interface=self.interface)\n        return self._port\n\n\n    def connect(self, reactor, factory):\n        \"\"\"\n        Start a TCP client with the given C{factory}.\n\n        @param reactor: The reactor to create the connection in.\n\n        @param factory: The client factory.\n\n        @return: A TCP connector instance.\n        \"\"\"\n        return reactor.connectTCP(self.interface, self.port, factory)\n\n\n    def test_buildProtocolReturnsNone(self):\n        \"\"\"\n        When the factory's C{buildProtocol} returns L{None} the connection is\n        gracefully closed.\n        \"\"\"\n        connectionLost = Deferred()\n        reactor = self.buildReactor()\n        serverFactory = MyServerFactory()\n        serverFactory.protocolConnectionLost = connectionLost\n\n        # Make sure the test ends quickly.\n        stopOnError(self, reactor)\n\n        class NoneFactory(ServerFactory):\n            def buildProtocol(self, address):\n                return None\n\n        listening = self.endpoints.server(reactor).listen(serverFactory)\n\n        def listened(port):\n            clientFactory = NoneFactory()\n            endpoint = self.endpoints.client(reactor, port.getHost())\n            return endpoint.connect(clientFactory)\n        connecting = listening.addCallback(listened)\n\n        def connectSucceeded(protocol):\n            self.fail(\n                \"Stream client endpoint connect succeeded with %r, \"\n                \"should have failed with NoProtocol.\" % (protocol,))\n        def connectFailed(reason):\n            reason.trap(NoProtocol)\n        connecting.addCallbacks(connectSucceeded, connectFailed)\n\n        def connected(ignored):\n            # Now that the connection attempt has failed continue waiting for\n            # the server-side connection to be lost.  This is the behavior this\n            # test is primarily concerned with.\n            return connectionLost\n        disconnecting = connecting.addCallback(connected)\n\n        # Make sure any errors that happen in that process get logged quickly.\n        disconnecting.addErrback(log.err)\n\n        def disconnected(ignored):\n            # The Deferred has to succeed at this point (because log.err always\n            # returns None).  If an error got logged it will fail the test.\n            # Stop the reactor now so the test can complete one way or the\n            # other now.\n            reactor.stop()\n        disconnecting.addCallback(disconnected)\n\n        self.runReactor(reactor)\n\n\n    def test_addresses(self):\n        \"\"\"\n        A client's transport's C{getHost} and C{getPeer} return L{IPv4Address}\n        instances which have the dotted-quad string form of the resolved\n        address of the local and remote endpoints of the connection\n        respectively as their C{host} attribute, not the hostname originally\n        passed in to\n        L{connectTCP<twisted.internet.interfaces.IReactorTCP.connectTCP>}, if a\n        hostname was used.\n        \"\"\"\n        host, ignored = findFreePort(self.interface, self.family)[:2]\n        reactor = self.buildReactor()\n        fakeDomain = self.fakeDomainName\n        reactor.installResolver(FakeResolver({fakeDomain: self.interface}))\n\n        server = reactor.listenTCP(\n            0, ServerFactory.forProtocol(Protocol), interface=host)\n        serverAddress = server.getHost()\n\n        transportData = {'host': None, 'peer': None, 'instance': None}\n\n        class CheckAddress(Protocol):\n            def makeConnection(self, transport):\n                transportData['host'] = transport.getHost()\n                transportData['peer'] = transport.getPeer()\n                transportData['instance'] = transport\n                reactor.stop()\n\n        clientFactory = Stop(reactor)\n        clientFactory.protocol = CheckAddress\n\n        def connectMe():\n            while True:\n                port = findFreePort(self.interface, self.family)\n                bindAddress = (self.interface, port[1])\n                log.msg(\"Connect attempt with bindAddress {}\".format(\n                    bindAddress\n                ))\n                try:\n                    reactor.connectTCP(\n                        fakeDomain,\n                        server.getHost().port,\n                        clientFactory,\n                        bindAddress=bindAddress,\n                    )\n                except ConnectBindError:\n                    continue\n                else:\n                    clientFactory.boundPort = port[1]\n                    break\n\n        needsRunningReactor(reactor, connectMe)\n\n        self.runReactor(reactor)\n\n        if clientFactory.failReason:\n            self.fail(clientFactory.failReason.getTraceback())\n\n        transportRepr = \"<%s to %s at %x>\" % (\n            transportData['instance'].__class__,\n            transportData['instance'].addr,\n            id(transportData['instance']))\n\n        boundPort = [host] + list(socket.getaddrinfo(\n            self.interface, clientFactory.boundPort)[0][-1][1:])\n        serverPort = [host] + list(socket.getaddrinfo(\n            self.interface, serverAddress.port)[0][-1][1:])\n\n        self.assertEqual(\n            transportData['host'],\n            self.addressClass('TCP', *boundPort))\n        self.assertEqual(\n            transportData['peer'],\n            self.addressClass('TCP', *serverPort))\n        self.assertEqual(\n            repr(transportData['instance']), transportRepr)\n\n\n    def test_badContext(self):\n        \"\"\"\n        If the context factory passed to L{ITCPTransport.startTLS} raises an\n        exception from its C{getContext} method, that exception is raised by\n        L{ITCPTransport.startTLS}.\n        \"\"\"\n        reactor = self.buildReactor()\n\n        brokenFactory = BrokenContextFactory()\n        results = []\n\n        serverFactory = ServerFactory.forProtocol(Protocol)\n        port = reactor.listenTCP(0, serverFactory, interface=self.interface)\n        endpoint = self.endpoints.client(reactor, port.getHost())\n\n        clientFactory = ClientFactory()\n        clientFactory.protocol = Protocol\n        connectDeferred = endpoint.connect(clientFactory)\n\n        def connected(protocol):\n            if not ITLSTransport.providedBy(protocol.transport):\n                results.append(\"skip\")\n            else:\n                results.append(self.assertRaises(ValueError,\n                                                 protocol.transport.startTLS,\n                                                 brokenFactory))\n\n        def connectFailed(failure):\n            results.append(failure)\n\n        def whenRun():\n            connectDeferred.addCallback(connected)\n            connectDeferred.addErrback(connectFailed)\n            connectDeferred.addBoth(lambda ign: reactor.stop())\n        needsRunningReactor(reactor, whenRun)\n\n        self.runReactor(reactor)\n\n        self.assertEqual(len(results), 1,\n                         \"more than one callback result: %s\" % (results,))\n\n        if isinstance(results[0], Failure):\n            # self.fail(Failure)\n            results[0].raiseException()\n        if results[0] == \"skip\":\n            raise SkipTest(\"Reactor does not support ITLSTransport\")\n        self.assertEqual(BrokenContextFactory.message, str(results[0]))\n\n\n\nclass TCP4ClientTestsBuilder(TCPClientTestsBase):\n    \"\"\"\n    Builder configured with IPv4 parameters for tests related to\n    L{IReactorTCP.connectTCP}.\n    \"\"\"\n    fakeDomainName = 'some-fake.domain.example.com'\n    family = socket.AF_INET\n    addressClass = IPv4Address\n\n    endpoints = TCPCreator()\n\n\n\nclass TCP6ClientTestsBuilder(TCPClientTestsBase):\n    \"\"\"\n    Builder configured with IPv6 parameters for tests related to\n    L{IReactorTCP.connectTCP}.\n    \"\"\"\n    if ipv6Skip:\n        skip = ipv6Skip\n\n    family = socket.AF_INET6\n    addressClass = IPv6Address\n\n    def setUp(self):\n        # Only create this object here, so that it won't be created if tests\n        # are being skipped:\n        self.endpoints = TCP6Creator()\n        # This is used by test_addresses to test the distinction between the\n        # resolved name and the name on the socket itself.  All the same\n        # invariants should hold, but giving back an IPv6 address from a\n        # resolver is not something the reactor can handle, so instead, we make\n        # it so that the connect call for the IPv6 address test simply uses an\n        # address literal.\n        self.fakeDomainName = self.endpoints.interface\n\n\n\nclass TCPConnectorTestsBuilder(ReactorBuilder):\n    \"\"\"\n    Tests for the L{IConnector} provider returned by L{IReactorTCP.connectTCP}.\n    \"\"\"\n    requiredInterfaces = (IReactorTCP,)\n\n    def test_connectorIdentity(self):\n        \"\"\"\n        L{IReactorTCP.connectTCP} returns an object which provides\n        L{IConnector}.  The destination of the connector is the address which\n        was passed to C{connectTCP}.  The same connector object is passed to\n        the factory's C{startedConnecting} method as to the factory's\n        C{clientConnectionLost} method.\n        \"\"\"\n        serverFactory = ClosingFactory()\n        reactor = self.buildReactor()\n        tcpPort = reactor.listenTCP(0, serverFactory, interface=self.interface)\n        serverFactory.port = tcpPort\n        portNumber = tcpPort.getHost().port\n\n        seenConnectors = []\n        seenFailures = []\n\n        clientFactory = ClientStartStopFactory()\n        clientFactory.clientConnectionLost = (\n            lambda connector, reason: (seenConnectors.append(connector),\n                                       seenFailures.append(reason)))\n        clientFactory.startedConnecting = seenConnectors.append\n\n        connector = reactor.connectTCP(self.interface, portNumber,\n                                       clientFactory)\n        self.assertTrue(IConnector.providedBy(connector))\n        dest = connector.getDestination()\n        self.assertEqual(dest.type, \"TCP\")\n        self.assertEqual(dest.host, self.interface)\n        self.assertEqual(dest.port, portNumber)\n\n        clientFactory.whenStopped.addBoth(lambda _: reactor.stop())\n\n        self.runReactor(reactor)\n\n        seenFailures[0].trap(ConnectionDone)\n        self.assertEqual(seenConnectors, [connector, connector])\n\n\n    def test_userFail(self):\n        \"\"\"\n        Calling L{IConnector.stopConnecting} in C{Factory.startedConnecting}\n        results in C{Factory.clientConnectionFailed} being called with\n        L{error.UserError} as the reason.\n        \"\"\"\n        serverFactory = MyServerFactory()\n        reactor = self.buildReactor()\n        tcpPort = reactor.listenTCP(0, serverFactory, interface=self.interface)\n        portNumber = tcpPort.getHost().port\n\n        fatalErrors = []\n\n        def startedConnecting(connector):\n            try:\n                connector.stopConnecting()\n            except Exception:\n                fatalErrors.append(Failure())\n                reactor.stop()\n\n        clientFactory = ClientStartStopFactory()\n        clientFactory.startedConnecting = startedConnecting\n\n        clientFactory.whenStopped.addBoth(lambda _: reactor.stop())\n\n        reactor.callWhenRunning(lambda: reactor.connectTCP(self.interface,\n                                                           portNumber,\n                                                           clientFactory))\n\n        self.runReactor(reactor)\n\n        if fatalErrors:\n            self.fail(fatalErrors[0].getTraceback())\n        clientFactory.reason.trap(UserError)\n        self.assertEqual(clientFactory.failed, 1)\n\n\n    def test_reconnect(self):\n        \"\"\"\n        Calling L{IConnector.connect} in C{Factory.clientConnectionLost} causes\n        a new connection attempt to be made.\n        \"\"\"\n        serverFactory = ClosingFactory()\n        reactor = self.buildReactor()\n        tcpPort = reactor.listenTCP(0, serverFactory, interface=self.interface)\n        serverFactory.port = tcpPort\n        portNumber = tcpPort.getHost().port\n\n        clientFactory = MyClientFactory()\n\n        def clientConnectionLost(connector, reason):\n            connector.connect()\n        clientFactory.clientConnectionLost = clientConnectionLost\n        reactor.connectTCP(self.interface, portNumber, clientFactory)\n\n        protocolMadeAndClosed = []\n        def reconnectFailed(ignored):\n            p = clientFactory.protocol\n            protocolMadeAndClosed.append((p.made, p.closed))\n            reactor.stop()\n\n        clientFactory.failDeferred.addCallback(reconnectFailed)\n\n        self.runReactor(reactor)\n\n        clientFactory.reason.trap(ConnectionRefusedError)\n        self.assertEqual(protocolMadeAndClosed, [(1, 1)])\n\n\n\nclass TCP4ConnectorTestsBuilder(TCPConnectorTestsBuilder):\n    interface = '127.0.0.1'\n    family = socket.AF_INET\n    addressClass = IPv4Address\n\n\n\nclass TCP6ConnectorTestsBuilder(TCPConnectorTestsBuilder):\n    family = socket.AF_INET6\n    addressClass = IPv6Address\n\n    if ipv6Skip:\n        skip = ipv6Skip\n\n    def setUp(self):\n        self.interface = getLinkLocalIPv6Address()\n\n\n\ndef createTestSocket(test, addressFamily, socketType):\n    \"\"\"\n    Create a socket for the duration of the given test.\n\n    @param test: the test to add cleanup to.\n\n    @param addressFamily: an C{AF_*} constant\n\n    @param socketType: a C{SOCK_*} constant.\n\n    @return: a socket object.\n    \"\"\"\n    skt = socket.socket(addressFamily, socketType)\n    test.addCleanup(skt.close)\n    return skt\n\n\n\nclass _IExhaustsFileDescriptors(Interface):\n    \"\"\"\n    A way to trigger C{EMFILE}.\n    \"\"\"\n\n    def exhaust():\n        \"\"\"\n        Open file descriptors until C{EMFILE} is reached.\n\n        This can raise any exception except an L{OSError} whose\n        C{errno} is C{EMFILE}.  Any exception raised to the caller\n        implies L{release}.\n        \"\"\"\n\n\n    def release():\n        \"\"\"\n        Release all file descriptors opened by L{exhaust}.\n        \"\"\"\n\n\n    def count():\n        \"\"\"\n        Return the number of opened file descriptors.\n\n        @return: The number of opened file descriptors; this will be\n            zero if this instance has not opened any.\n        @rtype: L{int}\n        \"\"\"\n\n\n\n@implementer(_IExhaustsFileDescriptors)\n@attr.s\nclass _ExhaustsFileDescriptors(object):\n    \"\"\"\n    A class that triggers C{EMFILE} by creating as many file\n    descriptors as necessary.\n\n    @ivar fileDescriptorFactory: A factory that creates a new file\n        descriptor.\n    @type fileDescriptorFactory: A L{callable} that accepts no\n        arguments and returns an integral file descriptor, suitable\n        for passing to L{os.close}.\n    \"\"\"\n    _log = Logger()\n    _fileDescriptorFactory = attr.ib(default=lambda: os.dup(0), repr=False)\n    _close = attr.ib(default=os.close, repr=False)\n    _fileDescriptors = attr.ib(\n        default=attr.Factory(list), init=False, repr=False)\n\n    def exhaust(self):\n        \"\"\"\n        Open file descriptors until C{EMFILE} is reached.\n        \"\"\"\n        # Force a collection to close dangling files.\n        gc.collect()\n        try:\n            while True:\n                try:\n                    fd = self._fileDescriptorFactory()\n                except (IOError, OSError) as e:\n                    if e.errno == errno.EMFILE:\n                        break\n                    raise\n                else:\n                    self._fileDescriptors.append(fd)\n        except Exception:\n            self.release()\n            raise\n        else:\n            self._log.info(\n                \"EMFILE reached by opening\"\n                \" {openedFileDescriptors} file descriptors.\",\n                openedFileDescriptors=self.count(),\n            )\n\n\n    def release(self):\n        \"\"\"\n        Release all file descriptors opened by L{exhaust}.\n        \"\"\"\n        while self._fileDescriptors:\n            fd = self._fileDescriptors.pop()\n            try:\n                self._close(fd)\n            except OSError as e:\n                if e.errno == errno.EBADF:\n                    continue\n                raise\n\n\n    def count(self):\n        \"\"\"\n        Return the number of opened file descriptors.\n\n        @return: The number of opened file descriptors; this will be\n            zero if this instance has not opened any.\n        @rtype: L{int}\n        \"\"\"\n        return len(self._fileDescriptors)\n\n\n\nclass ExhaustsFileDescriptorsTests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{_ExhaustsFileDescriptors}.\n    \"\"\"\n    skip = SKIP_EMFILE\n\n    def setUp(self):\n        self.exhauster = _ExhaustsFileDescriptors()\n        # This assumes release succeeds when there are no file\n        # descriptors to close.\n        self.addCleanup(self.exhauster.release)\n\n\n    def openAFile(self):\n        \"\"\"\n        Attempt to open a file; if successful, the file is immediately\n        closed.\n        \"\"\"\n        open(os.devnull).close()\n\n\n    def test_providesInterface(self):\n        \"\"\"\n        L{_ExhaustsFileDescriptors} instances provide\n        L{_IExhaustsFileDescriptors}.\n        \"\"\"\n        verifyObject(_IExhaustsFileDescriptors, self.exhauster)\n\n\n    def test_count(self):\n        \"\"\"\n        L{_ExhaustsFileDescriptors.count} returns the number of open\n        file descriptors.\n        \"\"\"\n        self.assertEqual(self.exhauster.count(), 0)\n        self.exhauster.exhaust()\n        self.assertGreater(self.exhauster.count(), 0)\n        self.exhauster.release()\n        self.assertEqual(self.exhauster.count(), 0)\n\n\n    def test_exhaustTriggersEMFILE(self):\n        \"\"\"\n        L{_ExhaustsFileDescriptors.exhaust} causes the process to\n        exhaust its available file descriptors.\n        \"\"\"\n        self.addCleanup(self.exhauster.release)\n        self.exhauster.exhaust()\n        exception = self.assertRaises(IOError, self.openAFile)\n        self.assertEqual(exception.errno, errno.EMFILE)\n\n\n    def test_exhaustRaisesOSError(self):\n        \"\"\"\n        An L{OSError} raised within\n        L{_ExhaustsFileDescriptors.exhaust} with an C{errno} other\n        than C{EMFILE} is reraised to the caller.\n        \"\"\"\n        def raiseOSError():\n            raise OSError(errno.EMFILE + 1, \"Not EMFILE\")\n\n        exhauster = _ExhaustsFileDescriptors(raiseOSError)\n        self.assertRaises(OSError, exhauster.exhaust)\n\n\n    def test_release(self):\n        \"\"\"\n        L{_ExhaustsFileDescriptors.release} releases all opened\n        file descriptors.\n        \"\"\"\n        self.exhauster.exhaust()\n        self.exhauster.release()\n        # Does not fail with EMFILE\n        self.openAFile()\n\n\n    def test_fileDescriptorsReleasedOnFailure(self):\n        \"\"\"\n        L{_ExhaustsFileDescriptors.exhaust} closes any opened file\n        descriptors if an exception occurs during its exhaustion loop.\n        \"\"\"\n        fileDescriptors = []\n\n        def failsAfterThree():\n            if len(fileDescriptors) == 3:\n                raise ValueError(\n                    \"test_fileDescriptorsReleasedOnFailure\"\n                    \" fake open exception\")\n            else:\n                fd = os.dup(0)\n                fileDescriptors.append(fd)\n                return fd\n\n        exhauster = _ExhaustsFileDescriptors(failsAfterThree)\n        self.addCleanup(exhauster.release)\n\n        self.assertRaises(ValueError, exhauster.exhaust)\n        self.assertEqual(len(fileDescriptors), 3)\n        self.assertEqual(exhauster.count(), 0)\n\n        for fd in fileDescriptors:\n            exception = self.assertRaises(OSError, os.fstat, fd)\n            self.assertEqual(exception.errno, errno.EBADF)\n\n\n    def test_releaseIgnoresEBADF(self):\n        \"\"\"\n        L{_ExhaustsFileDescriptors.release} continues to close opened\n        file descriptors even when closing one fails with C{EBADF}.\n        \"\"\"\n        fileDescriptors = []\n\n        def recordFileDescriptors():\n            fd = os.dup(0)\n            fileDescriptors.append(fd)\n            return fd\n\n        exhauster = _ExhaustsFileDescriptors(recordFileDescriptors)\n        self.addCleanup(exhauster.release)\n\n        exhauster.exhaust()\n        self.assertGreater(exhauster.count(), 0)\n\n        os.close(fileDescriptors[0])\n\n        exhauster.release()\n        self.assertEqual(exhauster.count(), 0)\n\n\n    def test_releaseRaisesOSError(self):\n        \"\"\"\n        An L{OSError} raised within\n        L{_ExhaustsFileDescriptors.release} with an C{errno} other than\n        C{EBADF} is reraised to the caller.\n        \"\"\"\n        fakeFileDescriptors = []\n\n        def opensThree():\n            if len(fakeFileDescriptors) == 3:\n                raise OSError(errno.EMFILE, \"Too many files\")\n            fakeFileDescriptors.append(-1)\n            return fakeFileDescriptors[-1]\n\n        def failingClose(fd):\n            raise OSError(11, \"test_releaseRaisesOSError fake OSError\")\n\n        exhauster = _ExhaustsFileDescriptors(opensThree,\n                                             close=failingClose)\n\n        self.assertEqual(exhauster.count(), 0)\n        exhauster.exhaust()\n        self.assertGreater(exhauster.count(), 0)\n        self.assertRaises(OSError, exhauster.release)\n\n\n\ndef assertPeerClosedOnEMFILE(\n        testCase,\n        exhauster,\n        reactor,\n        runReactor,\n        listen,\n        connect,\n):\n    \"\"\"\n    Assert that an L{IListeningPort} immediately closes an accepted\n    peer socket when the number of open file descriptors exceeds the\n    soft resource limit.\n\n    @param testCase: The test case under which to run this assertion.\n    @type testCase: L{trial.unittest.SynchronousTestCase}\n\n    @param exhauster: The file descriptor exhauster.\n    @type exhauster: L{_ExhaustsFileDescriptors}\n\n    @param reactor: The reactor under test.\n\n    @param runReactor: A callable that will synchronously run the\n        provided reactor.\n\n    @param listen: A callback to bind to a port.\n    @type listen: A L{callable} that accepts two arguments: the\n        provided C{reactor}; and a L{ServerFactory}.  It must return\n        an L{IListeningPort} provider.\n\n    @param connect: A callback to connect a client to the listening\n        port.\n    @type connect: A L{callable} that accepts three arguments: the\n        provided C{reactor}; the address returned by\n        L{IListeningPort.getHost}; and a L{ClientFactory}.  Its return\n        value is ignored.\n    \"\"\"\n    testCase.addCleanup(exhauster.release)\n\n    serverFactory = MyServerFactory()\n    serverConnectionMade = Deferred()\n    serverFactory.protocolConnectionMade = serverConnectionMade\n    serverConnectionCompleted = [False]\n\n    def stopReactorIfServerAccepted(_):\n        reactor.stop()\n        serverConnectionCompleted[0] = True\n\n    serverConnectionMade.addCallback(\n        stopReactorIfServerAccepted)\n\n    port = listen(reactor, serverFactory)\n    listeningHost = port.getHost()\n    clientFactory = MyClientFactory()\n    connect(reactor, listeningHost, clientFactory)\n\n    reactor.callWhenRunning(exhauster.exhaust)\n\n    def stopReactorAndCloseFileDescriptors(result):\n        exhauster.release()\n        reactor.stop()\n        return result\n\n    clientFactory.deferred.addBoth(stopReactorAndCloseFileDescriptors)\n    clientFactory.failDeferred.addBoth(stopReactorAndCloseFileDescriptors)\n\n    runReactor(reactor)\n\n    noResult = []\n    serverConnectionMade.addBoth(noResult.append)\n    testCase.assertFalse(\n        noResult, \"Server accepted connection; EMFILE not triggered.\")\n    testCase.assertNoResult(clientFactory.failDeferred)\n    testCase.successResultOf(clientFactory.deferred)\n    testCase.assertRaises(\n        ConnectionClosed,\n        clientFactory.lostReason.raiseException,\n    )\n\n\n\nclass AssertPeerClosedOnEMFILETests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{assertPeerClosedOnEMFILE}.\n    \"\"\"\n    skip = SKIP_EMFILE\n\n    @implementer(_IExhaustsFileDescriptors)\n    class NullExhauster(object):\n        \"\"\"\n        An exhauster that does nothing.\n        \"\"\"\n\n        def exhaust(self):\n            \"\"\"\n            See L{_IExhaustsFileDescriptors.exhaust}\n            \"\"\"\n\n\n        def release(self):\n            \"\"\"\n            See L{_IExhaustsFileDescriptors.release}\n            \"\"\"\n\n\n        def count(self):\n            \"\"\"\n            See L{_IExhaustsFileDescriptors.count}\n            \"\"\"\n\n    def setUp(self):\n        self.reactor = MemoryReactor()\n        self.testCase = SynchronousTestCase()\n\n\n    def test_nullExhausterProvidesInterface(self):\n        \"\"\"\n        L{NullExhauster} instances provide\n        L{_IExhaustsFileDescriptors}.\n        \"\"\"\n        verifyObject(_IExhaustsFileDescriptors, self.NullExhauster())\n\n\n    def test_reactorStoppedOnSuccessfulConnection(self):\n        \"\"\"\n        If the exhauster fails to trigger C{EMFILE} and a connection\n        reaches the server, the reactor is stopped and the test fails.\n        \"\"\"\n        exhauster = self.NullExhauster()\n        serverFactory = [None]\n\n        def runReactor(reactor):\n            reactor.run()\n            proto = serverFactory[0].buildProtocol(\n                IPv4Address('TCP', '127.0.0.1', 4321))\n            proto.makeConnection(StringTransport())\n\n        def listen(reactor, factory):\n            port = reactor.listenTCP('127.0.0.1', 1234, factory)\n            factory.doStart()\n            serverFactory[0] = factory\n            return port\n\n        def connect(reactor, address, factory):\n            reactor.connectTCP('127.0.0.1', 0, factory)\n\n        exception = self.assertRaises(\n            self.testCase.failureException,\n            assertPeerClosedOnEMFILE,\n            testCase=self.testCase,\n            exhauster=exhauster,\n            reactor=self.reactor,\n            runReactor=runReactor,\n            listen=listen,\n            connect=connect,\n        )\n\n        self.assertIn(\"EMFILE\", str(exception))\n        self.assertFalse(self.reactor.running)\n\n\n\nclass StreamTransportTestsMixin(LogObserverMixin):\n    \"\"\"\n    Mixin defining tests which apply to any port/connection based transport.\n    \"\"\"\n\n    def test_startedListeningLogMessage(self):\n        \"\"\"\n        When a port starts, a message including a description of the associated\n        factory is logged.\n        \"\"\"\n        loggedMessages = self.observe()\n        reactor = self.buildReactor()\n\n        @implementer(ILoggingContext)\n        class SomeFactory(ServerFactory):\n            def logPrefix(self):\n                return \"Crazy Factory\"\n\n        factory = SomeFactory()\n        p = self.getListeningPort(reactor, factory)\n        expectedMessage = self.getExpectedStartListeningLogMessage(\n            p, \"Crazy Factory\")\n        self.assertEqual((expectedMessage,), loggedMessages[0]['message'])\n\n\n    def test_connectionLostLogMsg(self):\n        \"\"\"\n        When a connection is lost, an informative message should be logged\n        (see L{getExpectedConnectionLostLogMsg}): an address identifying\n        the port and the fact that it was closed.\n        \"\"\"\n\n        loggedMessages = []\n        def logConnectionLostMsg(eventDict):\n            loggedMessages.append(log.textFromEventDict(eventDict))\n\n        reactor = self.buildReactor()\n        p = self.getListeningPort(reactor, ServerFactory())\n        expectedMessage = self.getExpectedConnectionLostLogMsg(p)\n        log.addObserver(logConnectionLostMsg)\n\n        def stopReactor(ignored):\n            log.removeObserver(logConnectionLostMsg)\n            reactor.stop()\n\n        def doStopListening():\n            log.addObserver(logConnectionLostMsg)\n            maybeDeferred(p.stopListening).addCallback(stopReactor)\n\n        reactor.callWhenRunning(doStopListening)\n        reactor.run()\n\n        self.assertIn(expectedMessage, loggedMessages)\n\n\n    def test_allNewStyle(self):\n        \"\"\"\n        The L{IListeningPort} object is an instance of a class with no\n        classic classes in its hierarchy.\n        \"\"\"\n        reactor = self.buildReactor()\n        port = self.getListeningPort(reactor, ServerFactory())\n        self.assertFullyNewStyle(port)\n\n\n    def test_closePeerOnEMFILE(self):\n        \"\"\"\n        See L{assertPeerClosedOnEMFILE}.\n        \"\"\"\n        assertPeerClosedOnEMFILE(\n            testCase=self,\n            exhauster=_ExhaustsFileDescriptors(),\n            reactor=self.buildReactor(),\n            runReactor=self.runReactor,\n            listen=self.getListeningPort,\n            connect=self.connectToListener,\n        )\n\n    if SKIP_EMFILE:\n        test_closePeerOnEMFILE.skip = SKIP_EMFILE\n\n\n\nclass ConnectToTCPListenerMixin(object):\n    \"\"\"\n    Provides L{connectToListener} for TCP transports.\n\n    @ivar LISTENER_HOST: The host on which the port is expected to be\n        listening.  This is specific to avoid compatibility issues\n        with Windows, which cannot connect to the wildcard host.\n    @type LISTENER_HOST: L{str}\n\n    @see: U{http://twistedmatrix.com/trac/ticket/1472}\n    \"\"\"\n    LISTENER_HOST = '127.0.0.1'\n\n\n    def connectToListener(self, reactor, address, factory):\n        \"\"\"\n        Connect to the given listening TCP port.\n\n        @param reactor: The reactor under test.\n        @type reactor: L{IReactorTCP}\n\n        @param address: The listening port's address.  Only the\n            C{port} component is used; see L{LISTENER_HOST}.\n        @type address: L{IPv4Address} or L{IPv6Address}\n\n        @param factory: The client factory.\n        @type factory: L{ClientFactory}\n\n        @return: The connector\n        \"\"\"\n        return reactor.connectTCP(self.LISTENER_HOST, address.port, factory)\n\n\n\nclass ListenTCPMixin(ConnectToTCPListenerMixin):\n    \"\"\"\n    Mixin which uses L{IReactorTCP.listenTCP} to hand out listening TCP ports.\n    \"\"\"\n    def getListeningPort(self, reactor, factory, port=0, interface=''):\n        \"\"\"\n        Get a TCP port from a reactor.\n        \"\"\"\n        return reactor.listenTCP(port, factory, interface=interface)\n\n\n\nclass SocketTCPMixin(ConnectToTCPListenerMixin):\n    \"\"\"\n    Mixin which uses L{IReactorSocket.adoptStreamPort} to hand out\n    listening TCP ports.\n    \"\"\"\n    def getListeningPort(self, reactor, factory, port=0, interface=''):\n        \"\"\"\n        Get a TCP port from a reactor, wrapping an already-initialized file\n        descriptor.\n        \"\"\"\n        if IReactorSocket.providedBy(reactor):\n            if ':' in interface:\n                domain = socket.AF_INET6\n                address = socket.getaddrinfo(interface, port)[0][4]\n            else:\n                domain = socket.AF_INET\n                address = (interface, port)\n            portSock = socket.socket(domain)\n            portSock.bind(address)\n            portSock.listen(3)\n            portSock.setblocking(False)\n            try:\n                return reactor.adoptStreamPort(\n                    portSock.fileno(), portSock.family, factory)\n            finally:\n                # The socket should still be open; fileno will raise if it is\n                # not.\n                portSock.fileno()\n                # Now clean it up, because the rest of the test does not need\n                # it.\n                portSock.close()\n        else:\n            raise SkipTest(\"Reactor does not provide IReactorSocket\")\n\n\n\nclass TCPPortTestsMixin(object):\n    \"\"\"\n    Tests for L{IReactorTCP.listenTCP}\n    \"\"\"\n    requiredInterfaces = (IReactorTCP,)\n\n    def getExpectedStartListeningLogMessage(self, port, factory):\n        \"\"\"\n        Get the message expected to be logged when a TCP port starts listening.\n        \"\"\"\n        return \"%s starting on %d\" % (\n            factory, port.getHost().port)\n\n\n    def getExpectedConnectionLostLogMsg(self, port):\n        \"\"\"\n        Get the expected connection lost message for a TCP port.\n        \"\"\"\n        return \"(TCP Port %s Closed)\" % (port.getHost().port,)\n\n\n    def test_portGetHostOnIPv4(self):\n        \"\"\"\n        When no interface is passed to L{IReactorTCP.listenTCP}, the returned\n        listening port listens on an IPv4 address.\n        \"\"\"\n        reactor = self.buildReactor()\n        port = self.getListeningPort(reactor, ServerFactory())\n        address = port.getHost()\n        self.assertIsInstance(address, IPv4Address)\n\n\n    def test_portGetHostOnIPv6(self):\n        \"\"\"\n        When listening on an IPv6 address, L{IListeningPort.getHost} returns\n        an L{IPv6Address} with C{host} and C{port} attributes reflecting the\n        address the port is bound to.\n        \"\"\"\n        reactor = self.buildReactor()\n        host, portNumber = findFreePort(\n            family=socket.AF_INET6, interface='::1')[:2]\n        port = self.getListeningPort(\n            reactor, ServerFactory(), portNumber, host)\n        address = port.getHost()\n        self.assertIsInstance(address, IPv6Address)\n        self.assertEqual('::1', address.host)\n        self.assertEqual(portNumber, address.port)\n    if ipv6Skip:\n        test_portGetHostOnIPv6.skip = ipv6Skip\n\n\n    def test_portGetHostOnIPv6ScopeID(self):\n        \"\"\"\n        When a link-local IPv6 address including a scope identifier is passed as\n        the C{interface} argument to L{IReactorTCP.listenTCP}, the resulting\n        L{IListeningPort} reports its address as an L{IPv6Address} with a host\n        value that includes the scope identifier.\n        \"\"\"\n        linkLocal = getLinkLocalIPv6Address()\n        reactor = self.buildReactor()\n        port = self.getListeningPort(reactor, ServerFactory(), 0, linkLocal)\n        address = port.getHost()\n        self.assertIsInstance(address, IPv6Address)\n        self.assertEqual(linkLocal, address.host)\n    if ipv6Skip:\n        test_portGetHostOnIPv6ScopeID.skip = ipv6Skip\n\n\n    def _buildProtocolAddressTest(self, client, interface):\n        \"\"\"\n        Connect C{client} to a server listening on C{interface} started with\n        L{IReactorTCP.listenTCP} and return the address passed to the factory's\n        C{buildProtocol} method.\n\n        @param client: A C{SOCK_STREAM} L{socket.socket} created with an address\n            family such that it will be able to connect to a server listening on\n            C{interface}.\n\n        @param interface: A C{str} giving an address for a server to listen on.\n            This should almost certainly be the loopback address for some\n            address family supported by L{IReactorTCP.listenTCP}.\n\n        @return: Whatever object, probably an L{IAddress} provider, is passed to\n            a server factory's C{buildProtocol} method when C{client}\n            establishes a connection.\n        \"\"\"\n        class ObserveAddress(ServerFactory):\n            def buildProtocol(self, address):\n                reactor.stop()\n                self.observedAddress = address\n                return Protocol()\n\n        factory = ObserveAddress()\n        reactor = self.buildReactor()\n        port = self.getListeningPort(reactor, factory, 0, interface)\n        client.setblocking(False)\n        try:\n            connect(client, (port.getHost().host, port.getHost().port))\n        except socket.error as e:\n            self.assertIn(e.errno, (errno.EINPROGRESS, errno.EWOULDBLOCK))\n\n        self.runReactor(reactor)\n\n        return factory.observedAddress\n\n\n    def test_buildProtocolIPv4Address(self):\n        \"\"\"\n        When a connection is accepted over IPv4, an L{IPv4Address} is passed\n        to the factory's C{buildProtocol} method giving the peer's address.\n        \"\"\"\n        interface = '127.0.0.1'\n        client = createTestSocket(self, socket.AF_INET, socket.SOCK_STREAM)\n        observedAddress = self._buildProtocolAddressTest(client, interface)\n        self.assertEqual(\n            IPv4Address('TCP', *client.getsockname()), observedAddress)\n\n\n    def test_buildProtocolIPv6Address(self):\n        \"\"\"\n        When a connection is accepted to an IPv6 address, an L{IPv6Address} is\n        passed to the factory's C{buildProtocol} method giving the peer's\n        address.\n        \"\"\"\n        interface = '::1'\n        client = createTestSocket(self, socket.AF_INET6, socket.SOCK_STREAM)\n        observedAddress = self._buildProtocolAddressTest(client, interface)\n\n        peer = client.getsockname()\n        hostname = socket.getnameinfo(peer, socket.NI_NUMERICHOST)[0]\n\n        self.assertEqual(\n            IPv6Address('TCP', hostname, peer[1]), observedAddress)\n    if ipv6Skip:\n        test_buildProtocolIPv6Address.skip = ipv6Skip\n\n\n    def test_buildProtocolIPv6AddressScopeID(self):\n        \"\"\"\n        When a connection is accepted to a link-local IPv6 address, an\n        L{IPv6Address} is passed to the factory's C{buildProtocol} method\n        giving the peer's address, including a scope identifier.\n        \"\"\"\n        interface = getLinkLocalIPv6Address()\n        client = createTestSocket(self, socket.AF_INET6, socket.SOCK_STREAM)\n        observedAddress = self._buildProtocolAddressTest(client, interface)\n\n        peer = client.getsockname()\n        hostname = socket.getnameinfo(peer, socket.NI_NUMERICHOST)[0]\n\n        self.assertEqual(\n            IPv6Address('TCP', hostname, *peer[1:]), observedAddress)\n    if ipv6Skip:\n        test_buildProtocolIPv6AddressScopeID.skip = ipv6Skip\n\n\n    def _serverGetConnectionAddressTest(self, client, interface, which):\n        \"\"\"\n        Connect C{client} to a server listening on C{interface} started with\n        L{IReactorTCP.listenTCP} and return the address returned by one of the\n        server transport's address lookup methods, C{getHost} or C{getPeer}.\n\n        @param client: A C{SOCK_STREAM} L{socket.socket} created with an address\n            family such that it will be able to connect to a server listening on\n            C{interface}.\n\n        @param interface: A C{str} giving an address for a server to listen on.\n            This should almost certainly be the loopback address for some\n            address family supported by L{IReactorTCP.listenTCP}.\n\n        @param which: A C{str} equal to either C{\"getHost\"} or C{\"getPeer\"}\n            determining which address will be returned.\n\n        @return: Whatever object, probably an L{IAddress} provider, is returned\n            from the method indicated by C{which}.\n        \"\"\"\n        class ObserveAddress(Protocol):\n            def makeConnection(self, transport):\n                reactor.stop()\n                self.factory.address = getattr(transport, which)()\n\n        reactor = self.buildReactor()\n        factory = ServerFactory()\n        factory.protocol = ObserveAddress\n        port = self.getListeningPort(reactor, factory, 0, interface)\n        client.setblocking(False)\n        try:\n            connect(client, (port.getHost().host, port.getHost().port))\n        except socket.error as e:\n            self.assertIn(e.errno, (errno.EINPROGRESS, errno.EWOULDBLOCK))\n        self.runReactor(reactor)\n        return factory.address\n\n\n    def test_serverGetHostOnIPv4(self):\n        \"\"\"\n        When a connection is accepted over IPv4, the server\n        L{ITransport.getHost} method returns an L{IPv4Address} giving the\n        address on which the server accepted the connection.\n        \"\"\"\n        interface = '127.0.0.1'\n        client = createTestSocket(self, socket.AF_INET, socket.SOCK_STREAM)\n        hostAddress = self._serverGetConnectionAddressTest(\n            client, interface, 'getHost')\n        self.assertEqual(\n            IPv4Address('TCP', *client.getpeername()), hostAddress)\n\n\n    def test_serverGetHostOnIPv6(self):\n        \"\"\"\n        When a connection is accepted over IPv6, the server\n        L{ITransport.getHost} method returns an L{IPv6Address} giving the\n        address on which the server accepted the connection.\n        \"\"\"\n        interface = '::1'\n        client = createTestSocket(self, socket.AF_INET6, socket.SOCK_STREAM)\n        hostAddress = self._serverGetConnectionAddressTest(\n            client, interface, 'getHost')\n\n        peer = client.getpeername()\n        hostname = socket.getnameinfo(peer, socket.NI_NUMERICHOST)[0]\n\n        self.assertEqual(\n            IPv6Address('TCP', hostname, *peer[1:]), hostAddress)\n    if ipv6Skip:\n        test_serverGetHostOnIPv6.skip = ipv6Skip\n\n\n    def test_serverGetHostOnIPv6ScopeID(self):\n        \"\"\"\n        When a connection is accepted over IPv6, the server\n        L{ITransport.getHost} method returns an L{IPv6Address} giving the\n        address on which the server accepted the connection, including the scope\n        identifier.\n        \"\"\"\n        interface = getLinkLocalIPv6Address()\n        client = createTestSocket(self, socket.AF_INET6, socket.SOCK_STREAM)\n        hostAddress = self._serverGetConnectionAddressTest(\n            client, interface, 'getHost')\n\n        peer = client.getpeername()\n        hostname = socket.getnameinfo(peer, socket.NI_NUMERICHOST)[0]\n\n        self.assertEqual(\n            IPv6Address('TCP', hostname, *peer[1:]), hostAddress)\n    if ipv6Skip:\n        test_serverGetHostOnIPv6ScopeID.skip = ipv6Skip\n\n\n    def test_serverGetPeerOnIPv4(self):\n        \"\"\"\n        When a connection is accepted over IPv4, the server\n        L{ITransport.getPeer} method returns an L{IPv4Address} giving the\n        address of the remote end of the connection.\n        \"\"\"\n        interface = '127.0.0.1'\n        client = createTestSocket(self, socket.AF_INET, socket.SOCK_STREAM)\n        peerAddress = self._serverGetConnectionAddressTest(\n            client, interface, 'getPeer')\n        self.assertEqual(\n            IPv4Address('TCP', *client.getsockname()), peerAddress)\n\n\n    def test_serverGetPeerOnIPv6(self):\n        \"\"\"\n        When a connection is accepted over IPv6, the server\n        L{ITransport.getPeer} method returns an L{IPv6Address} giving the\n        address on the remote end of the connection.\n        \"\"\"\n        interface = '::1'\n        client = createTestSocket(self, socket.AF_INET6, socket.SOCK_STREAM)\n        peerAddress = self._serverGetConnectionAddressTest(\n            client, interface, 'getPeer')\n\n        peer = client.getsockname()\n        hostname = socket.getnameinfo(peer, socket.NI_NUMERICHOST)[0]\n\n        self.assertEqual(\n            IPv6Address('TCP', hostname, *peer[1:]), peerAddress)\n    if ipv6Skip:\n        test_serverGetPeerOnIPv6.skip = ipv6Skip\n\n\n    def test_serverGetPeerOnIPv6ScopeID(self):\n        \"\"\"\n        When a connection is accepted over IPv6, the server\n        L{ITransport.getPeer} method returns an L{IPv6Address} giving the\n        address on the remote end of the connection, including the scope\n        identifier.\n        \"\"\"\n        interface = getLinkLocalIPv6Address()\n        client = createTestSocket(self, socket.AF_INET6, socket.SOCK_STREAM)\n        peerAddress = self._serverGetConnectionAddressTest(\n            client, interface, 'getPeer')\n\n        peer = client.getsockname()\n        hostname = socket.getnameinfo(peer, socket.NI_NUMERICHOST)[0]\n\n        self.assertEqual(\n            IPv6Address('TCP', hostname, *peer[1:]), peerAddress)\n    if ipv6Skip:\n        test_serverGetPeerOnIPv6ScopeID.skip = ipv6Skip\n\n\n\nclass TCPPortTestsBuilder(ReactorBuilder, ListenTCPMixin, TCPPortTestsMixin,\n                          ObjectModelIntegrationMixin,\n                          StreamTransportTestsMixin):\n    pass\n\n\n\nclass TCPFDPortTestsBuilder(ReactorBuilder, SocketTCPMixin, TCPPortTestsMixin,\n                            ObjectModelIntegrationMixin,\n                            StreamTransportTestsMixin):\n    pass\n\n\n\nclass StopStartReadingProtocol(Protocol):\n    \"\"\"\n    Protocol that pauses and resumes the transport a few times\n    \"\"\"\n\n    def connectionMade(self):\n        self.data = b''\n        self.pauseResumeProducing(3)\n\n\n    def pauseResumeProducing(self, counter):\n        \"\"\"\n        Toggle transport read state, then count down.\n        \"\"\"\n        self.transport.pauseProducing()\n        self.transport.resumeProducing()\n        if counter:\n            self.factory.reactor.callLater(0,\n                    self.pauseResumeProducing, counter - 1)\n        else:\n            self.factory.reactor.callLater(0,\n                    self.factory.ready.callback, self)\n\n\n    def dataReceived(self, data):\n        log.msg('got data', len(data))\n        self.data += data\n        if len(self.data) == 4*4096:\n            self.factory.stop.callback(self.data)\n\n\n\ndef oneTransportTest(testMethod):\n    \"\"\"\n    Decorate a L{ReactorBuilder} test function which tests one reactor and one\n    connected transport.  Run that test method in the context of\n    C{connectionMade}, and immediately drop the connection (and end the test)\n    when that completes.\n\n    @param testMethod: A unit test method on a L{ReactorBuilder} test suite;\n        taking two additional parameters; a C{reactor} as built by the\n        L{ReactorBuilder}, and an L{ITCPTransport} provider.\n    @type testMethod: 3-argument C{function}\n\n    @return: a no-argument test method.\n    @rtype: 1-argument C{function}\n    \"\"\"\n    @wraps(testMethod)\n    def actualTestMethod(builder):\n        other = ConnectableProtocol()\n        class ServerProtocol(ConnectableProtocol):\n            def connectionMade(self):\n                try:\n                    testMethod(builder, self.reactor, self.transport)\n                finally:\n                    if self.transport is not None:\n                        self.transport.loseConnection()\n                    if other.transport is not None:\n                        other.transport.loseConnection()\n        serverProtocol = ServerProtocol()\n        runProtocolsWithReactor(builder, serverProtocol, other, TCPCreator())\n    return actualTestMethod\n\n\n\ndef assertReading(testCase, reactor, transport):\n    \"\"\"\n    Use the given test to assert that the given transport is actively reading\n    in the given reactor.\n\n    @note: Maintainers; for more information on why this is a function rather\n        than a method on a test case, see U{this document on how we structure\n        test tools\n        <http://twistedmatrix.com/trac/wiki/Design/KeepTestToolsOutOfFixtures>}\n\n    @param testCase: a test case to perform the assertion upon.\n    @type testCase: L{TestCase}\n\n    @param reactor: A reactor, possibly one providing L{IReactorFDSet}, or an\n        IOCP reactor.\n\n    @param transport: An L{ITCPTransport}\n    \"\"\"\n    if IReactorFDSet.providedBy(reactor):\n        testCase.assertIn(transport, reactor.getReaders())\n    else:\n        # IOCP.\n        testCase.assertIn(transport, reactor.handles)\n        testCase.assertTrue(transport.reading)\n\n\n\ndef assertNotReading(testCase, reactor, transport):\n    \"\"\"\n    Use the given test to assert that the given transport is I{not} actively\n    reading in the given reactor.\n\n    @note: Maintainers; for more information on why this is a function rather\n        than a method on a test case, see U{this document on how we structure\n        test tools\n        <http://twistedmatrix.com/trac/wiki/Design/KeepTestToolsOutOfFixtures>}\n\n    @param testCase: a test case to perform the assertion upon.\n    @type testCase: L{TestCase}\n\n    @param reactor: A reactor, possibly one providing L{IReactorFDSet}, or an\n        IOCP reactor.\n\n    @param transport: An L{ITCPTransport}\n    \"\"\"\n    if IReactorFDSet.providedBy(reactor):\n        testCase.assertNotIn(transport, reactor.getReaders())\n    else:\n        # IOCP.\n        testCase.assertFalse(transport.reading)\n\n\n\nclass TCPConnectionTestsBuilder(ReactorBuilder):\n    \"\"\"\n    Builder defining tests relating to L{twisted.internet.tcp.Connection}.\n    \"\"\"\n    requiredInterfaces = (IReactorTCP,)\n\n    def test_stopStartReading(self):\n        \"\"\"\n        This test verifies transport socket read state after multiple\n        pause/resumeProducing calls.\n        \"\"\"\n        sf = ServerFactory()\n        reactor = sf.reactor = self.buildReactor()\n\n        skippedReactors = [\"Glib2Reactor\", \"Gtk2Reactor\"]\n        reactorClassName = reactor.__class__.__name__\n        if reactorClassName in skippedReactors and platform.isWindows():\n            raise SkipTest(\n                \"This test is broken on gtk/glib under Windows.\")\n\n        sf.protocol = StopStartReadingProtocol\n        sf.ready = Deferred()\n        sf.stop = Deferred()\n        p = reactor.listenTCP(0, sf)\n        port = p.getHost().port\n        def proceed(protos, port):\n            \"\"\"\n            Send several IOCPReactor's buffers' worth of data.\n            \"\"\"\n            self.assertTrue(protos[0])\n            self.assertTrue(protos[1])\n            protos = protos[0][1], protos[1][1]\n            protos[0].transport.write(b'x' * (2 * 4096) + b'y' * (2 * 4096))\n            return (sf.stop.addCallback(cleanup, protos, port)\n                           .addCallback(lambda ign: reactor.stop()))\n\n        def cleanup(data, protos, port):\n            \"\"\"\n            Make sure IOCPReactor didn't start several WSARecv operations\n            that clobbered each other's results.\n            \"\"\"\n            self.assertEqual(data, b'x'*(2*4096) + b'y'*(2*4096),\n                                 'did not get the right data')\n            return DeferredList([\n                    maybeDeferred(protos[0].transport.loseConnection),\n                    maybeDeferred(protos[1].transport.loseConnection),\n                    maybeDeferred(port.stopListening)])\n\n        cc = TCP4ClientEndpoint(reactor, '127.0.0.1', port)\n        cf = ClientFactory()\n        cf.protocol = Protocol\n        d = DeferredList([cc.connect(cf), sf.ready]).addCallback(proceed, p)\n        d.addErrback(log.err)\n        self.runReactor(reactor)\n\n\n    @oneTransportTest\n    def test_resumeProducing(self, reactor, server):\n        \"\"\"\n        When a L{Server} is connected, its C{resumeProducing} method adds it as\n        a reader to the reactor.\n        \"\"\"\n        server.pauseProducing()\n        assertNotReading(self, reactor, server)\n        server.resumeProducing()\n        assertReading(self, reactor, server)\n\n\n    @oneTransportTest\n    def test_resumeProducingWhileDisconnecting(self, reactor, server):\n        \"\"\"\n        When a L{Server} has already started disconnecting via\n        C{loseConnection}, its C{resumeProducing} method does not add it as a\n        reader to its reactor.\n        \"\"\"\n        server.loseConnection()\n        server.resumeProducing()\n        assertNotReading(self, reactor, server)\n\n\n    @oneTransportTest\n    def test_resumeProducingWhileDisconnected(self, reactor, server):\n        \"\"\"\n        When a L{Server} has already lost its connection, its\n        C{resumeProducing} method does not add it as a reader to its reactor.\n        \"\"\"\n        server.connectionLost(Failure(Exception(\"dummy\")))\n        assertNotReading(self, reactor, server)\n        server.resumeProducing()\n        assertNotReading(self, reactor, server)\n\n\n    def test_connectionLostAfterPausedTransport(self):\n        \"\"\"\n        Alice connects to Bob.  Alice writes some bytes and then shuts down the\n        connection.  Bob receives the bytes from the connection and then pauses\n        the transport object.  Shortly afterwards Bob resumes the transport\n        object.  At that point, Bob is notified that the connection has been\n        closed.\n\n        This is no problem for most reactors.  The underlying event notification\n        API will probably just remind them that the connection has been closed.\n        It is a little tricky for win32eventreactor (MsgWaitForMultipleObjects).\n        MsgWaitForMultipleObjects will only deliver the close notification once.\n        The reactor needs to remember that notification until Bob resumes the\n        transport.\n        \"\"\"\n        class Pauser(ConnectableProtocol):\n            def __init__(self):\n                self.events = []\n\n            def dataReceived(self, bytes):\n                self.events.append(\"paused\")\n                self.transport.pauseProducing()\n                self.reactor.callLater(0, self.resume)\n\n            def resume(self):\n                self.events.append(\"resumed\")\n                self.transport.resumeProducing()\n\n            def connectionLost(self, reason):\n                # This is the event you have been waiting for.\n                self.events.append(\"lost\")\n                ConnectableProtocol.connectionLost(self, reason)\n\n        class Client(ConnectableProtocol):\n            def connectionMade(self):\n                self.transport.write(b\"some bytes for you\")\n                self.transport.loseConnection()\n\n        pauser = Pauser()\n        runProtocolsWithReactor(self, pauser, Client(), TCPCreator())\n        self.assertEqual(pauser.events, [\"paused\", \"resumed\", \"lost\"])\n\n\n    def test_doubleHalfClose(self):\n        \"\"\"\n        If one side half-closes its connection, and then the other side of the\n        connection calls C{loseWriteConnection}, and then C{loseConnection} in\n        {writeConnectionLost}, the connection is closed correctly.\n\n        This rather obscure case used to fail (see ticket #3037).\n        \"\"\"\n        @implementer(IHalfCloseableProtocol)\n        class ListenerProtocol(ConnectableProtocol):\n\n            def readConnectionLost(self):\n                self.transport.loseWriteConnection()\n\n            def writeConnectionLost(self):\n                self.transport.loseConnection()\n\n        class Client(ConnectableProtocol):\n            def connectionMade(self):\n                self.transport.loseConnection()\n\n        # If test fails, reactor won't stop and we'll hit timeout:\n        runProtocolsWithReactor(\n            self, ListenerProtocol(), Client(), TCPCreator())\n\n\n\nclass WriteSequenceTestsMixin(object):\n    \"\"\"\n    Test for L{twisted.internet.abstract.FileDescriptor.writeSequence}.\n    \"\"\"\n    requiredInterfaces = (IReactorTCP,)\n\n    def setWriteBufferSize(self, transport, value):\n        \"\"\"\n        Set the write buffer size for the given transport, mananing possible\n        differences (ie, IOCP). Bug #4322 should remove the need of that hack.\n        \"\"\"\n        if getattr(transport, \"writeBufferSize\", None) is not None:\n            transport.writeBufferSize = value\n        else:\n            transport.bufferSize = value\n\n\n    def test_writeSequeceWithoutWrite(self):\n        \"\"\"\n        C{writeSequence} sends the data even if C{write} hasn't been called.\n        \"\"\"\n\n        def connected(protocols):\n            client, server, port = protocols\n\n            def dataReceived(data):\n                log.msg(\"data received: %r\" % data)\n                self.assertEqual(data, b\"Some sequence splitted\")\n                client.transport.loseConnection()\n\n            server.dataReceived = dataReceived\n\n            client.transport.writeSequence([b\"Some \", b\"sequence \", b\"splitted\"])\n\n        reactor = self.buildReactor()\n        d = self.getConnectedClientAndServer(reactor, \"127.0.0.1\",\n                                             socket.AF_INET)\n        d.addCallback(connected)\n        d.addErrback(log.err)\n        self.runReactor(reactor)\n\n\n    def test_writeSequenceWithUnicodeRaisesException(self):\n        \"\"\"\n        C{writeSequence} with an element in the sequence of type unicode raises\n        C{TypeError}.\n        \"\"\"\n\n        def connected(protocols):\n            client, server, port = protocols\n\n            exc = self.assertRaises(\n                TypeError,\n                server.transport.writeSequence, [u\"Unicode is not kosher\"])\n\n            self.assertEqual(str(exc), \"Data must not be unicode\")\n\n            server.transport.loseConnection()\n\n        reactor = self.buildReactor()\n        d = self.getConnectedClientAndServer(reactor, \"127.0.0.1\",\n                                             socket.AF_INET)\n        d.addCallback(connected)\n        d.addErrback(log.err)\n        self.runReactor(reactor)\n\n\n    def test_streamingProducer(self):\n        \"\"\"\n        C{writeSequence} pauses its streaming producer if too much data is\n        buffered, and then resumes it.\n        \"\"\"\n        @implementer(IPushProducer)\n        class SaveActionProducer(object):\n            client = None\n            server = None\n\n            def __init__(self):\n                self.actions = []\n\n            def pauseProducing(self):\n                self.actions.append(\"pause\")\n\n            def resumeProducing(self):\n                self.actions.append(\"resume\")\n                # Unregister the producer so the connection can close\n                self.client.transport.unregisterProducer()\n                # This is why the code below waits for the server connection\n                # first - so we have it to close here.  We close the server\n                # side because win32evenreactor cannot reliably observe us\n                # closing the client side (#5285).\n                self.server.transport.loseConnection()\n\n            def stopProducing(self):\n                self.actions.append(\"stop\")\n\n        producer = SaveActionProducer()\n\n        def connected(protocols):\n            client, server = protocols[:2]\n            producer.client = client\n            producer.server = server\n            # Register a streaming producer and verify that it gets paused\n            # after it writes more than the local send buffer can hold.\n            client.transport.registerProducer(producer, True)\n            self.assertEqual(producer.actions, [])\n            self.setWriteBufferSize(client.transport, 500)\n            client.transport.writeSequence([b\"x\" * 50] * 20)\n            self.assertEqual(producer.actions, [\"pause\"])\n\n        reactor = self.buildReactor()\n        d = self.getConnectedClientAndServer(reactor, \"127.0.0.1\",\n                                             socket.AF_INET)\n        d.addCallback(connected)\n        d.addErrback(log.err)\n        self.runReactor(reactor)\n        # After the send buffer gets a chance to empty out a bit, the producer\n        # should be resumed.\n        self.assertEqual(producer.actions, [\"pause\", \"resume\"])\n\n\n    def test_nonStreamingProducer(self):\n        \"\"\"\n        C{writeSequence} pauses its producer if too much data is buffered only\n        if this is a streaming producer.\n        \"\"\"\n        test = self\n\n        @implementer(IPullProducer)\n        class SaveActionProducer(object):\n            client = None\n\n            def __init__(self):\n                self.actions = []\n\n            def resumeProducing(self):\n                self.actions.append(\"resume\")\n                if self.actions.count(\"resume\") == 2:\n                    self.client.transport.stopConsuming()\n                else:\n                    test.setWriteBufferSize(self.client.transport, 500)\n                    self.client.transport.writeSequence([b\"x\" * 50] * 20)\n\n            def stopProducing(self):\n                self.actions.append(\"stop\")\n\n\n        producer = SaveActionProducer()\n\n        def connected(protocols):\n            client = protocols[0]\n            producer.client = client\n            # Register a non-streaming producer and verify that it is resumed\n            # immediately.\n            client.transport.registerProducer(producer, False)\n            self.assertEqual(producer.actions, [\"resume\"])\n\n        reactor = self.buildReactor()\n        d = self.getConnectedClientAndServer(reactor, \"127.0.0.1\",\n                                             socket.AF_INET)\n        d.addCallback(connected)\n        d.addErrback(log.err)\n        self.runReactor(reactor)\n        # After the local send buffer empties out, the producer should be\n        # resumed again.\n        self.assertEqual(producer.actions, [\"resume\", \"resume\"])\n\n\n\nclass TCPTransportServerAddressTestMixin(object):\n    \"\"\"\n    Test mixing for TCP server address building and log prefix.\n    \"\"\"\n\n    def getConnectedClientAndServer(self, reactor, interface, addressFamily):\n        \"\"\"\n        Helper method returnine a L{Deferred} firing with a tuple of a client\n        protocol, a server protocol, and a running TCP port.\n        \"\"\"\n        raise NotImplementedError()\n\n\n    def _testServerAddress(self, interface, addressFamily, adressClass):\n        \"\"\"\n        Helper method to test TCP server addresses on either IPv4 or IPv6.\n        \"\"\"\n\n        def connected(protocols):\n            client, server, port = protocols\n            try:\n                self.assertEqual(\n                    \"<AccumulatingProtocol #%s on %s>\" %\n                        (server.transport.sessionno, port.getHost().port),\n                    str(server.transport))\n\n                self.assertEqual(\n                    \"AccumulatingProtocol,%s,%s\" %\n                        (server.transport.sessionno, interface),\n                    server.transport.logstr)\n\n                [peerAddress] = server.factory.peerAddresses\n                self.assertIsInstance(peerAddress, adressClass)\n                self.assertEqual('TCP', peerAddress.type)\n                self.assertEqual(interface, peerAddress.host)\n            finally:\n                # Be certain to drop the connection so the test completes.\n                server.transport.loseConnection()\n\n        reactor = self.buildReactor()\n        d = self.getConnectedClientAndServer(reactor, interface, addressFamily)\n        d.addCallback(connected)\n        d.addErrback(log.err)\n        self.runReactor(reactor)\n\n\n    def test_serverAddressTCP4(self):\n        \"\"\"\n        L{Server} instances have a string representation indicating on which\n        port they're running, and the connected address is stored on the\n        C{peerAddresses} attribute of the factory.\n        \"\"\"\n        return self._testServerAddress(\"127.0.0.1\", socket.AF_INET,\n                                       IPv4Address)\n\n\n    def test_serverAddressTCP6(self):\n        \"\"\"\n        IPv6 L{Server} instances have a string representation indicating on\n        which port they're running, and the connected address is stored on the\n        C{peerAddresses} attribute of the factory.\n        \"\"\"\n        return self._testServerAddress(getLinkLocalIPv6Address(),\n                                       socket.AF_INET6, IPv6Address)\n\n    if ipv6Skip:\n        test_serverAddressTCP6.skip = ipv6Skip\n\n\n\nclass TCPTransportTestsBuilder(TCPTransportServerAddressTestMixin,\n                               WriteSequenceTestsMixin, ReactorBuilder):\n    \"\"\"\n    Test standard L{ITCPTransport}s built with C{listenTCP} and C{connectTCP}.\n    \"\"\"\n\n    def getConnectedClientAndServer(self, reactor, interface, addressFamily):\n        \"\"\"\n        Return a L{Deferred} firing with a L{MyClientFactory} and\n        L{MyServerFactory} connected pair, and the listening C{Port}.\n        \"\"\"\n        server = MyServerFactory()\n        server.protocolConnectionMade = Deferred()\n        server.protocolConnectionLost = Deferred()\n\n        client = MyClientFactory()\n        client.protocolConnectionMade = Deferred()\n        client.protocolConnectionLost = Deferred()\n\n        port = reactor.listenTCP(0, server, interface=interface)\n\n        lostDeferred = gatherResults([client.protocolConnectionLost,\n                                      server.protocolConnectionLost])\n        def stop(result):\n            reactor.stop()\n            return result\n\n        lostDeferred.addBoth(stop)\n\n        startDeferred = gatherResults([client.protocolConnectionMade,\n                                       server.protocolConnectionMade])\n\n        deferred = Deferred()\n\n        def start(protocols):\n            client, server = protocols\n            log.msg(\"client connected %s\" % client)\n            log.msg(\"server connected %s\" % server)\n            deferred.callback((client, server, port))\n\n        startDeferred.addCallback(start)\n\n        reactor.connectTCP(interface, port.getHost().port, client)\n\n        return deferred\n\n\n\nclass AdoptStreamConnectionTestsBuilder(TCPTransportServerAddressTestMixin,\n                                        WriteSequenceTestsMixin,\n                                        ReactorBuilder):\n    \"\"\"\n    Test server transports built using C{adoptStreamConnection}.\n    \"\"\"\n    requiredInterfaces = (IReactorFDSet, IReactorSocket)\n\n    def getConnectedClientAndServer(self, reactor, interface, addressFamily):\n        \"\"\"\n        Return a L{Deferred} firing with a L{MyClientFactory} and\n        L{MyServerFactory} connected pair, and the listening C{Port}. The\n        particularity is that the server protocol has been obtained after doing\n        a C{adoptStreamConnection} against the original server connection.\n        \"\"\"\n        firstServer = MyServerFactory()\n        firstServer.protocolConnectionMade = Deferred()\n\n        server = MyServerFactory()\n        server.protocolConnectionMade = Deferred()\n        server.protocolConnectionLost = Deferred()\n\n        client = MyClientFactory()\n        client.protocolConnectionMade = Deferred()\n        client.protocolConnectionLost = Deferred()\n\n        port = reactor.listenTCP(0, firstServer, interface=interface)\n\n        def firtServerConnected(proto):\n            reactor.removeReader(proto.transport)\n            reactor.removeWriter(proto.transport)\n            reactor.adoptStreamConnection(\n                proto.transport.fileno(), addressFamily, server)\n\n        firstServer.protocolConnectionMade.addCallback(firtServerConnected)\n\n        lostDeferred = gatherResults([client.protocolConnectionLost,\n                                      server.protocolConnectionLost])\n        def stop(result):\n            if reactor.running:\n                reactor.stop()\n            return result\n\n        lostDeferred.addBoth(stop)\n\n        deferred = Deferred()\n        deferred.addErrback(stop)\n\n        startDeferred = gatherResults([client.protocolConnectionMade,\n                                       server.protocolConnectionMade])\n        def start(protocols):\n            client, server = protocols\n            log.msg(\"client connected %s\" % client)\n            log.msg(\"server connected %s\" % server)\n            deferred.callback((client, server, port))\n\n        startDeferred.addCallback(start)\n\n        reactor.connectTCP(interface, port.getHost().port, client)\n        return deferred\n\n\n\nglobals().update(TCP4ClientTestsBuilder.makeTestCaseClasses())\nglobals().update(TCP6ClientTestsBuilder.makeTestCaseClasses())\nglobals().update(TCPPortTestsBuilder.makeTestCaseClasses())\nglobals().update(TCPFDPortTestsBuilder.makeTestCaseClasses())\nglobals().update(TCPConnectionTestsBuilder.makeTestCaseClasses())\nglobals().update(TCP4ConnectorTestsBuilder.makeTestCaseClasses())\nglobals().update(TCP6ConnectorTestsBuilder.makeTestCaseClasses())\nglobals().update(TCPTransportTestsBuilder.makeTestCaseClasses())\nglobals().update(AdoptStreamConnectionTestsBuilder.makeTestCaseClasses())\n\n\n\nclass ServerAbortsTwice(ConnectableProtocol):\n    \"\"\"\n    Call abortConnection() twice.\n    \"\"\"\n\n    def dataReceived(self, data):\n        self.transport.abortConnection()\n        self.transport.abortConnection()\n\n\n\nclass ServerAbortsThenLoses(ConnectableProtocol):\n    \"\"\"\n    Call abortConnection() followed by loseConnection().\n    \"\"\"\n\n    def dataReceived(self, data):\n        self.transport.abortConnection()\n        self.transport.loseConnection()\n\n\n\nclass AbortServerWritingProtocol(ConnectableProtocol):\n    \"\"\"\n    Protocol that writes data upon connection.\n    \"\"\"\n\n    def connectionMade(self):\n        \"\"\"\n        Tell the client that the connection is set up and it's time to abort.\n        \"\"\"\n        self.transport.write(b\"ready\")\n\n\n\nclass ReadAbortServerProtocol(AbortServerWritingProtocol):\n    \"\"\"\n    Server that should never receive any data, except 'X's which are written\n    by the other side of the connection before abortConnection, and so might\n    possibly arrive.\n    \"\"\"\n\n    def dataReceived(self, data):\n        if data.replace(b'X', b''):\n            raise Exception(\"Unexpectedly received data.\")\n\n\n\nclass NoReadServer(ConnectableProtocol):\n    \"\"\"\n    Stop reading immediately on connection.\n\n    This simulates a lost connection that will cause the other side to time\n    out, and therefore call abortConnection().\n    \"\"\"\n\n    def connectionMade(self):\n        self.transport.stopReading()\n\n\n\nclass EventualNoReadServer(ConnectableProtocol):\n    \"\"\"\n    Like NoReadServer, except we Wait until some bytes have been delivered\n    before stopping reading. This means TLS handshake has finished, where\n    applicable.\n    \"\"\"\n\n    gotData = False\n    stoppedReading = False\n\n\n    def dataReceived(self, data):\n        if not self.gotData:\n            self.gotData = True\n            self.transport.registerProducer(self, False)\n            self.transport.write(b\"hello\")\n\n\n    def resumeProducing(self):\n        if self.stoppedReading:\n            return\n        self.stoppedReading = True\n        # We've written out the data:\n        self.transport.stopReading()\n\n\n    def pauseProducing(self):\n        pass\n\n\n    def stopProducing(self):\n        pass\n\n\n\nclass BaseAbortingClient(ConnectableProtocol):\n    \"\"\"\n    Base class for abort-testing clients.\n    \"\"\"\n    inReactorMethod = False\n\n    def connectionLost(self, reason):\n        if self.inReactorMethod:\n            raise RuntimeError(\"BUG: connectionLost was called re-entrantly!\")\n        ConnectableProtocol.connectionLost(self, reason)\n\n\n\nclass WritingButNotAbortingClient(BaseAbortingClient):\n    \"\"\"\n    Write data, but don't abort.\n    \"\"\"\n\n    def connectionMade(self):\n        self.transport.write(b\"hello\")\n\n\n\nclass AbortingClient(BaseAbortingClient):\n    \"\"\"\n    Call abortConnection() after writing some data.\n    \"\"\"\n\n    def dataReceived(self, data):\n        \"\"\"\n        Some data was received, so the connection is set up.\n        \"\"\"\n        self.inReactorMethod = True\n        self.writeAndAbort()\n        self.inReactorMethod = False\n\n\n    def writeAndAbort(self):\n        # X is written before abortConnection, and so there is a chance it\n        # might arrive. Y is written after, and so no Ys should ever be\n        # delivered:\n        self.transport.write(b\"X\" * 10000)\n        self.transport.abortConnection()\n        self.transport.write(b\"Y\" * 10000)\n\n\n\nclass AbortingTwiceClient(AbortingClient):\n    \"\"\"\n    Call abortConnection() twice, after writing some data.\n    \"\"\"\n\n    def writeAndAbort(self):\n        AbortingClient.writeAndAbort(self)\n        self.transport.abortConnection()\n\n\n\nclass AbortingThenLosingClient(AbortingClient):\n    \"\"\"\n    Call abortConnection() and then loseConnection().\n    \"\"\"\n\n    def writeAndAbort(self):\n        AbortingClient.writeAndAbort(self)\n        self.transport.loseConnection()\n\n\n\nclass ProducerAbortingClient(ConnectableProtocol):\n    \"\"\"\n    Call abortConnection from doWrite, via resumeProducing.\n    \"\"\"\n\n    inReactorMethod = True\n    producerStopped = False\n\n    def write(self):\n        self.transport.write(b\"lalala\" * 127000)\n        self.inRegisterProducer = True\n        self.transport.registerProducer(self, False)\n        self.inRegisterProducer = False\n\n\n    def connectionMade(self):\n        self.write()\n\n\n    def resumeProducing(self):\n        self.inReactorMethod = True\n        if not self.inRegisterProducer:\n            self.transport.abortConnection()\n        self.inReactorMethod = False\n\n\n    def stopProducing(self):\n        self.producerStopped = True\n\n\n    def connectionLost(self, reason):\n        if not self.producerStopped:\n            raise RuntimeError(\"BUG: stopProducing() was never called.\")\n        if self.inReactorMethod:\n            raise RuntimeError(\"BUG: connectionLost called re-entrantly!\")\n        ConnectableProtocol.connectionLost(self, reason)\n\n\n\nclass StreamingProducerClient(ConnectableProtocol):\n    \"\"\"\n    Call abortConnection() when the other side has stopped reading.\n\n    In particular, we want to call abortConnection() only once our local\n    socket hits a state where it is no longer writeable. This helps emulate\n    the most common use case for abortConnection(), closing a connection after\n    a timeout, with write buffers being full.\n\n    Since it's very difficult to know when this actually happens, we just\n    write a lot of data, and assume at that point no more writes will happen.\n    \"\"\"\n    paused = False\n    extraWrites = 0\n    inReactorMethod = False\n\n    def connectionMade(self):\n        self.write()\n\n\n    def write(self):\n        \"\"\"\n        Write large amount to transport, then wait for a while for buffers to\n        fill up.\n        \"\"\"\n        self.transport.registerProducer(self, True)\n        for i in range(100):\n            self.transport.write(b\"1234567890\" * 32000)\n\n\n    def resumeProducing(self):\n        self.paused = False\n\n\n    def stopProducing(self):\n        pass\n\n\n    def pauseProducing(self):\n        \"\"\"\n        Called when local buffer fills up.\n\n        The goal is to hit the point where the local file descriptor is not\n        writeable (or the moral equivalent). The fact that pauseProducing has\n        been called is not sufficient, since that can happen when Twisted's\n        buffers fill up but OS hasn't gotten any writes yet. We want to be as\n        close as possible to every buffer (including OS buffers) being full.\n\n        So, we wait a bit more after this for Twisted to write out a few\n        chunks, then abortConnection.\n        \"\"\"\n        if self.paused:\n            return\n        self.paused = True\n        # The amount we wait is arbitrary, we just want to make sure some\n        # writes have happened and outgoing OS buffers filled up -- see\n        # http://twistedmatrix.com/trac/ticket/5303 for details:\n        self.reactor.callLater(0.01, self.doAbort)\n\n\n    def doAbort(self):\n        if not self.paused:\n            log.err(RuntimeError(\"BUG: We should be paused a this point.\"))\n        self.inReactorMethod = True\n        self.transport.abortConnection()\n        self.inReactorMethod = False\n\n\n    def connectionLost(self, reason):\n        # Tell server to start reading again so it knows to go away:\n        self.otherProtocol.transport.startReading()\n        ConnectableProtocol.connectionLost(self, reason)\n\n\n\nclass StreamingProducerClientLater(StreamingProducerClient):\n    \"\"\"\n    Call abortConnection() from dataReceived, after bytes have been\n    exchanged.\n    \"\"\"\n\n    def connectionMade(self):\n        self.transport.write(b\"hello\")\n        self.gotData = False\n\n\n    def dataReceived(self, data):\n        if not self.gotData:\n            self.gotData = True\n            self.write()\n\n\nclass ProducerAbortingClientLater(ProducerAbortingClient):\n    \"\"\"\n    Call abortConnection from doWrite, via resumeProducing.\n\n    Try to do so after some bytes have already been exchanged, so we\n    don't interrupt SSL handshake.\n    \"\"\"\n\n    def connectionMade(self):\n        # Override base class connectionMade().\n        pass\n\n\n    def dataReceived(self, data):\n        self.write()\n\n\n\nclass DataReceivedRaisingClient(AbortingClient):\n    \"\"\"\n    Call abortConnection(), and then throw exception, from dataReceived.\n    \"\"\"\n\n    def dataReceived(self, data):\n        self.transport.abortConnection()\n        raise ZeroDivisionError(\"ONO\")\n\n\n\nclass ResumeThrowsClient(ProducerAbortingClient):\n    \"\"\"\n    Call abortConnection() and throw exception from resumeProducing().\n    \"\"\"\n\n    def resumeProducing(self):\n        if not self.inRegisterProducer:\n            self.transport.abortConnection()\n            raise ZeroDivisionError(\"ono!\")\n\n\n    def connectionLost(self, reason):\n        # Base class assertion about stopProducing being called isn't valid;\n        # if the we blew up in resumeProducing, consumers are justified in\n        # giving up on the producer and not calling stopProducing.\n        ConnectableProtocol.connectionLost(self, reason)\n\n\n\nclass AbortConnectionMixin(object):\n    \"\"\"\n    Unit tests for L{ITransport.abortConnection}.\n    \"\"\"\n    # Override in subclasses, should be an EndpointCreator instance:\n    endpoints = None\n\n    def runAbortTest(self, clientClass, serverClass,\n                     clientConnectionLostReason=None):\n        \"\"\"\n        A test runner utility function, which hooks up a matched pair of client\n        and server protocols.\n\n        We then run the reactor until both sides have disconnected, and then\n        verify that the right exception resulted.\n        \"\"\"\n        clientExpectedExceptions = (ConnectionAborted, ConnectionLost)\n        serverExpectedExceptions = (ConnectionLost, ConnectionDone)\n        # In TLS tests we may get SSL.Error instead of ConnectionLost,\n        # since we're trashing the TLS protocol layer.\n        if useSSL:\n            clientExpectedExceptions = clientExpectedExceptions + (SSL.Error,)\n            serverExpectedExceptions = serverExpectedExceptions + (SSL.Error,)\n\n        client = clientClass()\n        server = serverClass()\n        client.otherProtocol = server\n        server.otherProtocol = client\n        reactor = runProtocolsWithReactor(self, server, client, self.endpoints)\n\n        # Make sure everything was shutdown correctly:\n        self.assertEqual(reactor.removeAll(), [])\n        self.assertEqual(reactor.getDelayedCalls(), [])\n\n        if clientConnectionLostReason is not None:\n            self.assertIsInstance(\n                client.disconnectReason.value,\n                (clientConnectionLostReason,) + clientExpectedExceptions)\n        else:\n            self.assertIsInstance(client.disconnectReason.value,\n                                  clientExpectedExceptions)\n        self.assertIsInstance(server.disconnectReason.value, serverExpectedExceptions)\n\n\n    def test_dataReceivedAbort(self):\n        \"\"\"\n        abortConnection() is called in dataReceived. The protocol should be\n        disconnected, but connectionLost should not be called re-entrantly.\n        \"\"\"\n        return self.runAbortTest(AbortingClient, ReadAbortServerProtocol)\n\n\n    def test_clientAbortsConnectionTwice(self):\n        \"\"\"\n        abortConnection() is called twice by client.\n\n        No exception should be thrown, and the connection will be closed.\n        \"\"\"\n        return self.runAbortTest(AbortingTwiceClient, ReadAbortServerProtocol)\n\n\n    def test_clientAbortsConnectionThenLosesConnection(self):\n        \"\"\"\n        Client calls abortConnection(), followed by loseConnection().\n\n        No exception should be thrown, and the connection will be closed.\n        \"\"\"\n        return self.runAbortTest(AbortingThenLosingClient,\n                                 ReadAbortServerProtocol)\n\n\n    def test_serverAbortsConnectionTwice(self):\n        \"\"\"\n        abortConnection() is called twice by server.\n\n        No exception should be thrown, and the connection will be closed.\n        \"\"\"\n        return self.runAbortTest(WritingButNotAbortingClient, ServerAbortsTwice,\n                                 clientConnectionLostReason=ConnectionLost)\n\n\n    def test_serverAbortsConnectionThenLosesConnection(self):\n        \"\"\"\n        Server calls abortConnection(), followed by loseConnection().\n\n        No exception should be thrown, and the connection will be closed.\n        \"\"\"\n        return self.runAbortTest(WritingButNotAbortingClient,\n                                 ServerAbortsThenLoses,\n                                 clientConnectionLostReason=ConnectionLost)\n\n\n    def test_resumeProducingAbort(self):\n        \"\"\"\n        abortConnection() is called in resumeProducing, before any bytes have\n        been exchanged. The protocol should be disconnected, but\n        connectionLost should not be called re-entrantly.\n        \"\"\"\n        self.runAbortTest(ProducerAbortingClient,\n                          ConnectableProtocol)\n\n\n    def test_resumeProducingAbortLater(self):\n        \"\"\"\n        abortConnection() is called in resumeProducing, after some\n        bytes have been exchanged. The protocol should be disconnected.\n        \"\"\"\n        return self.runAbortTest(ProducerAbortingClientLater,\n                                 AbortServerWritingProtocol)\n\n\n    def test_fullWriteBuffer(self):\n        \"\"\"\n        abortConnection() triggered by the write buffer being full.\n\n        In particular, the server side stops reading. This is supposed\n        to simulate a realistic timeout scenario where the client\n        notices the server is no longer accepting data.\n\n        The protocol should be disconnected, but connectionLost should not be\n        called re-entrantly.\n        \"\"\"\n        self.runAbortTest(StreamingProducerClient,\n                          NoReadServer)\n\n\n    def test_fullWriteBufferAfterByteExchange(self):\n        \"\"\"\n        abortConnection() is triggered by a write buffer being full.\n\n        However, this buffer is filled after some bytes have been exchanged,\n        allowing a TLS handshake if we're testing TLS. The connection will\n        then be lost.\n        \"\"\"\n        return self.runAbortTest(StreamingProducerClientLater,\n                                 EventualNoReadServer)\n\n\n    def test_dataReceivedThrows(self):\n        \"\"\"\n        dataReceived calls abortConnection(), and then raises an exception.\n\n        The connection will be lost, with the thrown exception\n        (C{ZeroDivisionError}) as the reason on the client. The idea here is\n        that bugs should not be masked by abortConnection, in particular\n        unexpected exceptions.\n        \"\"\"\n        self.runAbortTest(DataReceivedRaisingClient,\n                          AbortServerWritingProtocol,\n                          clientConnectionLostReason=ZeroDivisionError)\n        errors = self.flushLoggedErrors(ZeroDivisionError)\n        self.assertEqual(len(errors), 1)\n\n\n    def test_resumeProducingThrows(self):\n        \"\"\"\n        resumeProducing calls abortConnection(), and then raises an exception.\n\n        The connection will be lost, with the thrown exception\n        (C{ZeroDivisionError}) as the reason on the client. The idea here is\n        that bugs should not be masked by abortConnection, in particular\n        unexpected exceptions.\n        \"\"\"\n        self.runAbortTest(ResumeThrowsClient,\n                          ConnectableProtocol,\n                          clientConnectionLostReason=ZeroDivisionError)\n        errors = self.flushLoggedErrors(ZeroDivisionError)\n        self.assertEqual(len(errors), 1)\n\n\n\nclass AbortConnectionTests(ReactorBuilder, AbortConnectionMixin):\n    \"\"\"\n    TCP-specific L{AbortConnectionMixin} tests.\n    \"\"\"\n    requiredInterfaces = (IReactorTCP,)\n\n    endpoints = TCPCreator()\n\nglobals().update(AbortConnectionTests.makeTestCaseClasses())\n\n\n\nclass SimpleUtilityTests(TestCase):\n    \"\"\"\n    Simple, direct tests for helpers within L{twisted.internet.tcp}.\n    \"\"\"\n    if ipv6Skip:\n        skip = ipv6Skip\n\n    def test_resolveNumericHost(self):\n        \"\"\"\n        L{_resolveIPv6} raises a L{socket.gaierror} (L{socket.EAI_NONAME}) when\n        invoked with a non-numeric host.  (In other words, it is passing\n        L{socket.AI_NUMERICHOST} to L{socket.getaddrinfo} and will not\n        accidentally block if it receives bad input.)\n        \"\"\"\n        err = self.assertRaises(socket.gaierror, _resolveIPv6, \"localhost\", 1)\n        self.assertEqual(err.args[0], socket.EAI_NONAME)\n\n\n    def test_resolveNumericService(self):\n        \"\"\"\n        L{_resolveIPv6} raises a L{socket.gaierror} (L{socket.EAI_NONAME}) when\n        invoked with a non-numeric port.  (In other words, it is passing\n        L{socket.AI_NUMERICSERV} to L{socket.getaddrinfo} and will not\n        accidentally block if it receives bad input.)\n        \"\"\"\n        err = self.assertRaises(socket.gaierror, _resolveIPv6, \"::1\", \"http\")\n        self.assertEqual(err.args[0], socket.EAI_NONAME)\n\n    if platform.isWindows():\n        test_resolveNumericService.skip = (\"The AI_NUMERICSERV flag is not \"\n                                           \"supported by Microsoft providers.\")\n        # http://msdn.microsoft.com/en-us/library/windows/desktop/ms738520.aspx\n\n\n    def test_resolveIPv6(self):\n        \"\"\"\n        L{_resolveIPv6} discovers the flow info and scope ID of an IPv6\n        address.\n        \"\"\"\n        result = _resolveIPv6(\"::1\", 2)\n        self.assertEqual(len(result), 4)\n        # We can't say anything more useful about these than that they're\n        # integers, because the whole point of getaddrinfo is that you can never\n        # know a-priori know _anything_ about the network interfaces of the\n        # computer that you're on and you have to ask it.\n        self.assertIsInstance(result[2], (int, long)) # flow info\n        self.assertIsInstance(result[3], (int, long)) # scope id\n        # but, luckily, IP presentation format and what it means to be a port\n        # number are a little better specified.\n        self.assertEqual(result[:2], (\"::1\", 2))\n\n\n\nclass BuffersLogsTests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{_BuffersLogs}.\n    \"\"\"\n\n    def setUp(self):\n        self.namespace = \"name.space\"\n        self.events = []\n        self.logBuffer = _BuffersLogs(self.namespace, self.events.append)\n\n\n    def test_buffersInBlock(self):\n        \"\"\"\n        The context manager's logger does not log to provided observer\n        inside the block.\n        \"\"\"\n        with self.logBuffer as logger:\n            logger.info(\"An event\")\n            self.assertFalse(self.events)\n\n\n    def test_flushesOnExit(self):\n        \"\"\"\n        The context manager flushes its buffered logs when the block\n        terminates without an exception.\n        \"\"\"\n        with self.logBuffer as logger:\n            logger.info(\"An event\")\n            self.assertFalse(self.events)\n        self.assertEqual(1, len(self.events))\n        [event] = self.events\n        self.assertEqual(event['log_format'], \"An event\")\n        self.assertEqual(event['log_namespace'], self.namespace)\n\n\n    def test_flushesOnExitWithException(self):\n        \"\"\"\n        The context manager flushes its buffered logs when the block\n        terminates because of an exception.\n        \"\"\"\n        class TestException(Exception):\n            \"\"\"\n            An exception only raised by this test.\n            \"\"\"\n\n        with self.assertRaises(TestException):\n            with self.logBuffer as logger:\n                logger.info(\"An event\")\n                self.assertFalse(self.events)\n                raise TestException()\n\n        self.assertEqual(1, len(self.events))\n        [event] = self.events\n        self.assertEqual(event['log_format'], \"An event\")\n        self.assertEqual(event['log_namespace'], self.namespace)\n\n\n\nclass FileDescriptorReservationTests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{_FileDescriptorReservation}.\n    \"\"\"\n    skip = SKIP_EMFILE\n\n    def setUp(self):\n        self.reservedFileObjects = []\n        self.tempfile = self.mktemp()\n\n        def fakeFileFactory():\n            self.reservedFileObjects.append(open(self.tempfile, 'w'))\n            return self.reservedFileObjects[-1]\n\n        self.reservedFD = _FileDescriptorReservation(fakeFileFactory)\n\n\n    def test_providesInterface(self):\n        \"\"\"\n        L{_FileDescriptorReservation} instances provide\n        L{_IFileDescriptorReservation}.\n        \"\"\"\n        verifyObject(_IFileDescriptorReservation, self.reservedFD)\n\n\n    def test_reserveOpensFileOnce(self):\n        \"\"\"\n        Multiple acquisitions without releases open the reservation\n        file exactly once.\n        \"\"\"\n        self.assertEqual(len(self.reservedFileObjects), 0)\n\n        for _ in range(10):\n            self.reservedFD.reserve()\n            self.assertEqual(len(self.reservedFileObjects), 1)\n            self.assertFalse(self.reservedFileObjects[0].closed)\n\n\n    def test_reserveEMFILELogged(self):\n        \"\"\"\n        If reserving the file descriptor fails because of C{EMFILE},\n        the exception is suppressed but logged and the reservation\n        remains unavailable.\n        \"\"\"\n        exhauster = _ExhaustsFileDescriptors()\n        self.addCleanup(exhauster.release)\n        exhauster.exhaust()\n\n        self.assertFalse(self.reservedFD.available())\n        self.reservedFD.reserve()\n        self.assertFalse(self.reservedFD.available())\n\n        errors = self.flushLoggedErrors(OSError, IOError)\n        self.assertEqual(len(errors), 1)\n        self.assertEqual(errors[0].value.errno, errno.EMFILE)\n\n\n    def test_reserveRaisesNonEMFILEExceptions(self):\n        \"\"\"\n        Any exception raised while opening the reserve file that is\n        not an L{OSError} or L{IOError} whose errno is C{EMFILE} is\n        allowed through to the caller.\n        \"\"\"\n        for errorClass in (OSError, IOError, ValueError):\n            # Note that the ValueError will present the errno as its\n            # value.\n            def failsWith(errorClass=errorClass):\n                raise errorClass(errno.EMFILE + 1, \"message\")\n\n            reserveFD = _FileDescriptorReservation(failsWith)\n            self.assertRaises(errorClass, reserveFD.reserve)\n\n\n    def test_available(self):\n        \"\"\"\n        The reservation is available after the file descriptor is\n        reserved.\n        \"\"\"\n        self.assertFalse(self.reservedFD.available())\n        self.reservedFD.reserve()\n        self.assertTrue(self.reservedFD.available())\n\n\n    def test_enterFailsWithoutFile(self):\n        \"\"\"\n        A reservation without an open file used as a context manager\n        raises a L{RuntimeError}.\n        \"\"\"\n        with self.assertRaises(RuntimeError):\n            with self.reservedFD:\n                \"\"\"This string cannot raise an exception.\"\"\"\n\n    def test_enterClosesFileExitOpensFile(self):\n        \"\"\"\n        Entering a reservation closes its file for the duration of the\n        context manager's block.\n        \"\"\"\n        self.reservedFD.reserve()\n        self.assertTrue(self.reservedFD.available())\n        with self.reservedFD:\n            self.assertFalse(self.reservedFD.available())\n        self.assertTrue(self.reservedFD.available())\n\n\n    def test_exitOpensFileOnException(self):\n        \"\"\"\n        An exception raised within a reservation context manager's\n        block does not prevent the file from being reopened.\n        \"\"\"\n        class TestException(Exception):\n            \"\"\"\n            An exception only used by this test.\n            \"\"\"\n\n        self.reservedFD.reserve()\n        with self.assertRaises(TestException):\n            with self.reservedFD:\n                raise TestException()\n\n\n    def test_exitSuppressesReservationException(self):\n        \"\"\"\n        An exception raised while re-opening the reserve file exiting\n        a reservation's context manager block is suppressed but\n        logged, allowing an exception raised within the block through.\n        \"\"\"\n        class AllowedException(Exception):\n            \"\"\"\n            The exception allowed out of the block.\n            \"\"\"\n\n        class SuppressedException(Exception):\n            \"\"\"\n            An exception raised by the file descriptor factory.\n            \"\"\"\n\n        called = [False]\n\n        def failsWithSuppressedExceptionAfterSecondOpen():\n            if called[0]:\n                raise SuppressedException()\n            else:\n                called[0] = True\n                return io.BytesIO()\n\n        reservedFD = _FileDescriptorReservation(\n            failsWithSuppressedExceptionAfterSecondOpen)\n\n        reservedFD.reserve()\n        self.assertTrue(reservedFD.available())\n\n        with self.assertRaises(AllowedException):\n            with reservedFD:\n                raise AllowedException()\n\n        errors = self.flushLoggedErrors(SuppressedException)\n        self.assertEqual(len(errors), 1)\n\n\n\nclass NullFileDescriptorReservationTests(SynchronousTestCase):\n    \"\"\"\n    Tests for L{_NullFileDescriptorReservation}.\n    \"\"\"\n\n    def setUp(self):\n        self.nullReservedFD = _NullFileDescriptorReservation()\n\n\n    def test_providesInterface(self):\n        \"\"\"\n        L{_NullFileDescriptorReservation} provides\n        L{_IFileDescriptorReservation}.\n        \"\"\"\n        verifyObject(_IFileDescriptorReservation, self.nullReservedFD)\n\n\n    def test_available(self):\n        \"\"\"\n        The null reserved file descriptor is never available.\n        \"\"\"\n        self.assertFalse(self.nullReservedFD.available())\n\n\n    def test_contextManager(self):\n        \"\"\"\n        The null reserved file descriptor is a null context manager.\n        \"\"\"\n        self.assertFalse(self.nullReservedFD.available())\n        with self.nullReservedFD:\n            self.assertFalse(self.nullReservedFD.available())\n        self.assertFalse(self.nullReservedFD.available())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_testing.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet.testing}.\n\"\"\"\n\nfrom zope.interface.verify import verifyObject\n\nfrom twisted.internet.interfaces import (\n    ITransport,\n    IPushProducer,\n    IConsumer,\n    IReactorTCP,\n    IReactorSSL,\n    IReactorUNIX,\n    IAddress,\n    IListeningPort,\n    IConnector\n)\nfrom twisted.internet.address import IPv4Address\nfrom twisted.trial.unittest import TestCase\nfrom twisted.internet.testing import (\n    StringTransport,\n    MemoryReactor,\n    RaisingMemoryReactor,\n    NonStreamingProducer\n)\nfrom twisted.internet.protocol import ClientFactory, Factory\nfrom twisted.python.reflect import namedAny\n\n\n\nclass StringTransportTests(TestCase):\n    \"\"\"\n    Tests for L{twisted.internet.testing.StringTransport}.\n    \"\"\"\n    def setUp(self):\n        self.transport = StringTransport()\n\n\n    def test_interfaces(self):\n        \"\"\"\n        L{StringTransport} instances provide L{ITransport}, L{IPushProducer},\n        and L{IConsumer}.\n        \"\"\"\n        self.assertTrue(verifyObject(ITransport, self.transport))\n        self.assertTrue(verifyObject(IPushProducer, self.transport))\n        self.assertTrue(verifyObject(IConsumer, self.transport))\n\n\n    def test_registerProducer(self):\n        \"\"\"\n        L{StringTransport.registerProducer} records the arguments supplied to\n        it as instance attributes.\n        \"\"\"\n        producer = object()\n        streaming = object()\n        self.transport.registerProducer(producer, streaming)\n        self.assertIs(self.transport.producer, producer)\n        self.assertIs(self.transport.streaming, streaming)\n\n\n    def test_disallowedRegisterProducer(self):\n        \"\"\"\n        L{StringTransport.registerProducer} raises L{RuntimeError} if a\n        producer is already registered.\n        \"\"\"\n        producer = object()\n        self.transport.registerProducer(producer, True)\n        self.assertRaises(\n            RuntimeError, self.transport.registerProducer, object(), False)\n        self.assertIs(self.transport.producer, producer)\n        self.assertTrue(self.transport.streaming)\n\n\n    def test_unregisterProducer(self):\n        \"\"\"\n        L{StringTransport.unregisterProducer} causes the transport to forget\n        about the registered producer and makes it possible to register a new\n        one.\n        \"\"\"\n        oldProducer = object()\n        newProducer = object()\n        self.transport.registerProducer(oldProducer, False)\n        self.transport.unregisterProducer()\n        self.assertIsNone(self.transport.producer)\n        self.transport.registerProducer(newProducer, True)\n        self.assertIs(self.transport.producer, newProducer)\n        self.assertTrue(self.transport.streaming)\n\n\n    def test_invalidUnregisterProducer(self):\n        \"\"\"\n        L{StringTransport.unregisterProducer} raises L{RuntimeError} if called\n        when no producer is registered.\n        \"\"\"\n        self.assertRaises(RuntimeError, self.transport.unregisterProducer)\n\n\n    def test_initialProducerState(self):\n        \"\"\"\n        L{StringTransport.producerState} is initially C{'producing'}.\n        \"\"\"\n        self.assertEqual(self.transport.producerState, 'producing')\n\n\n    def test_pauseProducing(self):\n        \"\"\"\n        L{StringTransport.pauseProducing} changes the C{producerState} of the\n        transport to C{'paused'}.\n        \"\"\"\n        self.transport.pauseProducing()\n        self.assertEqual(self.transport.producerState, 'paused')\n\n\n    def test_resumeProducing(self):\n        \"\"\"\n        L{StringTransport.resumeProducing} changes the C{producerState} of the\n        transport to C{'producing'}.\n        \"\"\"\n        self.transport.pauseProducing()\n        self.transport.resumeProducing()\n        self.assertEqual(self.transport.producerState, 'producing')\n\n\n    def test_stopProducing(self):\n        \"\"\"\n        L{StringTransport.stopProducing} changes the C{'producerState'} of the\n        transport to C{'stopped'}.\n        \"\"\"\n        self.transport.stopProducing()\n        self.assertEqual(self.transport.producerState, 'stopped')\n\n\n    def test_stoppedTransportCannotPause(self):\n        \"\"\"\n        L{StringTransport.pauseProducing} raises L{RuntimeError} if the\n        transport has been stopped.\n        \"\"\"\n        self.transport.stopProducing()\n        self.assertRaises(RuntimeError, self.transport.pauseProducing)\n\n\n    def test_stoppedTransportCannotResume(self):\n        \"\"\"\n        L{StringTransport.resumeProducing} raises L{RuntimeError} if the\n        transport has been stopped.\n        \"\"\"\n        self.transport.stopProducing()\n        self.assertRaises(RuntimeError, self.transport.resumeProducing)\n\n\n    def test_disconnectingTransportCannotPause(self):\n        \"\"\"\n        L{StringTransport.pauseProducing} raises L{RuntimeError} if the\n        transport is being disconnected.\n        \"\"\"\n        self.transport.loseConnection()\n        self.assertRaises(RuntimeError, self.transport.pauseProducing)\n\n\n    def test_disconnectingTransportCannotResume(self):\n        \"\"\"\n        L{StringTransport.resumeProducing} raises L{RuntimeError} if the\n        transport is being disconnected.\n        \"\"\"\n        self.transport.loseConnection()\n        self.assertRaises(RuntimeError, self.transport.resumeProducing)\n\n\n    def test_loseConnectionSetsDisconnecting(self):\n        \"\"\"\n        L{StringTransport.loseConnection} toggles the C{disconnecting} instance\n        variable to C{True}.\n        \"\"\"\n        self.assertFalse(self.transport.disconnecting)\n        self.transport.loseConnection()\n        self.assertTrue(self.transport.disconnecting)\n\n\n    def test_specifiedHostAddress(self):\n        \"\"\"\n        If a host address is passed to L{StringTransport.__init__}, that\n        value is returned from L{StringTransport.getHost}.\n        \"\"\"\n        address = object()\n        self.assertIs(StringTransport(address).getHost(), address)\n\n\n    def test_specifiedPeerAddress(self):\n        \"\"\"\n        If a peer address is passed to L{StringTransport.__init__}, that\n        value is returned from L{StringTransport.getPeer}.\n        \"\"\"\n        address = object()\n        self.assertIs(\n            StringTransport(peerAddress=address).getPeer(), address)\n\n\n    def test_defaultHostAddress(self):\n        \"\"\"\n        If no host address is passed to L{StringTransport.__init__}, an\n        L{IPv4Address} is returned from L{StringTransport.getHost}.\n        \"\"\"\n        address = StringTransport().getHost()\n        self.assertIsInstance(address, IPv4Address)\n\n\n    def test_defaultPeerAddress(self):\n        \"\"\"\n        If no peer address is passed to L{StringTransport.__init__}, an\n        L{IPv4Address} is returned from L{StringTransport.getPeer}.\n        \"\"\"\n        address = StringTransport().getPeer()\n        self.assertIsInstance(address, IPv4Address)\n\n\n\nclass ReactorTests(TestCase):\n    \"\"\"\n    Tests for L{MemoryReactor} and L{RaisingMemoryReactor}.\n    \"\"\"\n\n    def test_memoryReactorProvides(self):\n        \"\"\"\n        L{MemoryReactor} provides all of the attributes described by the\n        interfaces it advertises.\n        \"\"\"\n        memoryReactor = MemoryReactor()\n        verifyObject(IReactorTCP, memoryReactor)\n        verifyObject(IReactorSSL, memoryReactor)\n        verifyObject(IReactorUNIX, memoryReactor)\n\n\n    def test_raisingReactorProvides(self):\n        \"\"\"\n        L{RaisingMemoryReactor} provides all of the attributes described by the\n        interfaces it advertises.\n        \"\"\"\n        raisingReactor = RaisingMemoryReactor()\n        verifyObject(IReactorTCP, raisingReactor)\n        verifyObject(IReactorSSL, raisingReactor)\n        verifyObject(IReactorUNIX, raisingReactor)\n\n\n    def test_connectDestination(self):\n        \"\"\"\n        L{MemoryReactor.connectTCP}, L{MemoryReactor.connectSSL}, and\n        L{MemoryReactor.connectUNIX} will return an L{IConnector} whose\n        C{getDestination} method returns an L{IAddress} with attributes which\n        reflect the values passed.\n        \"\"\"\n        memoryReactor = MemoryReactor()\n        for connector in [memoryReactor.connectTCP(\n                              \"test.example.com\", 8321, ClientFactory()),\n                          memoryReactor.connectSSL(\n                              \"test.example.com\", 8321, ClientFactory(),\n                              None)]:\n            verifyObject(IConnector, connector)\n            address = connector.getDestination()\n            verifyObject(IAddress, address)\n            self.assertEqual(address.host, \"test.example.com\")\n            self.assertEqual(address.port, 8321)\n        connector = memoryReactor.connectUNIX(b\"/fake/path\", ClientFactory())\n        verifyObject(IConnector, connector)\n        address = connector.getDestination()\n        verifyObject(IAddress, address)\n        self.assertEqual(address.name, b\"/fake/path\")\n\n\n    def test_listenDefaultHost(self):\n        \"\"\"\n        L{MemoryReactor.listenTCP}, L{MemoryReactor.listenSSL} and\n        L{MemoryReactor.listenUNIX} will return an L{IListeningPort} whose\n        C{getHost} method returns an L{IAddress}; C{listenTCP} and C{listenSSL}\n        will have a default host of C{'0.0.0.0'}, and a port that reflects the\n        value passed, and C{listenUNIX} will have a name that reflects the path\n        passed.\n        \"\"\"\n        memoryReactor = MemoryReactor()\n        for port in [memoryReactor.listenTCP(8242, Factory()),\n                     memoryReactor.listenSSL(8242, Factory(), None)]:\n            verifyObject(IListeningPort, port)\n            address = port.getHost()\n            verifyObject(IAddress, address)\n            self.assertEqual(address.host, '0.0.0.0')\n            self.assertEqual(address.port, 8242)\n        port = memoryReactor.listenUNIX(b\"/path/to/socket\", Factory())\n        verifyObject(IListeningPort, port)\n        address = port.getHost()\n        verifyObject(IAddress, address)\n        self.assertEqual(address.name, b\"/path/to/socket\")\n\n\n    def test_readers(self):\n        \"\"\"\n        Adding, removing, and listing readers works.\n        \"\"\"\n        reader = object()\n        reactor = MemoryReactor()\n\n        reactor.addReader(reader)\n        reactor.addReader(reader)\n\n        self.assertEqual(reactor.getReaders(), [reader])\n\n        reactor.removeReader(reader)\n\n        self.assertEqual(reactor.getReaders(), [])\n\n\n    def test_writers(self):\n        \"\"\"\n        Adding, removing, and listing writers works.\n        \"\"\"\n        writer = object()\n        reactor = MemoryReactor()\n\n        reactor.addWriter(writer)\n        reactor.addWriter(writer)\n\n        self.assertEqual(reactor.getWriters(), [writer])\n\n        reactor.removeWriter(writer)\n\n        self.assertEqual(reactor.getWriters(), [])\n\n\n\nclass TestConsumer(object):\n    \"\"\"\n    A very basic test consumer for use with the NonStreamingProducerTests.\n    \"\"\"\n    def __init__(self):\n        self.writes = []\n        self.producer = None\n        self.producerStreaming = None\n\n\n    def registerProducer(self, producer, streaming):\n        \"\"\"\n        Registers a single producer with this consumer. Just keeps track of it.\n\n        @param producer: The producer to register.\n        @param streaming: Whether the producer is a streaming one or not.\n        \"\"\"\n        self.producer = producer\n        self.producerStreaming = streaming\n\n\n    def unregisterProducer(self):\n        \"\"\"\n        Forget the producer we had previously registered.\n        \"\"\"\n        self.producer = None\n        self.producerStreaming = None\n\n\n    def write(self, data):\n        \"\"\"\n        Some data was written to the consumer: stores it for later use.\n\n        @param data: The data to write.\n        \"\"\"\n        self.writes.append(data)\n\n\n\nclass NonStreamingProducerTests(TestCase):\n    \"\"\"\n    Tests for the L{NonStreamingProducer} to validate behaviour.\n    \"\"\"\n    def test_producesOnly10Times(self):\n        \"\"\"\n        When the L{NonStreamingProducer} has resumeProducing called 10 times,\n        it writes the counter each time and then fails.\n        \"\"\"\n        consumer = TestConsumer()\n        producer = NonStreamingProducer(consumer)\n        consumer.registerProducer(producer, False)\n\n        self.assertIs(consumer.producer, producer)\n        self.assertIs(producer.consumer, consumer)\n        self.assertFalse(consumer.producerStreaming)\n\n        for _ in range(10):\n            producer.resumeProducing()\n\n        # We should have unregistered the producer and printed the 10 results.\n        expectedWrites = [\n            b'0', b'1', b'2', b'3', b'4', b'5', b'6', b'7', b'8', b'9'\n        ]\n        self.assertIsNone(consumer.producer)\n        self.assertIsNone(consumer.producerStreaming)\n        self.assertIsNone(producer.consumer)\n        self.assertEqual(consumer.writes, expectedWrites)\n\n        # Another attempt to produce fails.\n        self.assertRaises(RuntimeError, producer.resumeProducing)\n\n\n    def test_cannotPauseProduction(self):\n        \"\"\"\n        When the L{NonStreamingProducer} is paused, it raises a\n        L{RuntimeError}.\n        \"\"\"\n        consumer = TestConsumer()\n        producer = NonStreamingProducer(consumer)\n        consumer.registerProducer(producer, False)\n\n        # Produce once, just to be safe.\n        producer.resumeProducing()\n\n        self.assertRaises(RuntimeError, producer.pauseProducing)\n\n\n\nclass DeprecationTests(TestCase):\n    \"\"\"\n    Deprecations in L{twisted.test.proto_helpers}.\n    \"\"\"\n    def helper(self, test, obj):\n        new_path = 'twisted.internet.testing.{}'.format(obj.__name__)\n        warnings = self.flushWarnings(\n            [test])\n        self.assertEqual(DeprecationWarning, warnings[0]['category'])\n        self.assertEqual(1, len(warnings))\n        self.assertIn(new_path, warnings[0]['message'])\n        self.assertIs(obj, namedAny(new_path))\n\n    def test_accumulatingProtocol(self):\n        from twisted.test.proto_helpers import AccumulatingProtocol\n        self.helper(self.test_accumulatingProtocol,\n                    AccumulatingProtocol)\n\n\n    def test_lineSendingProtocol(self):\n        from twisted.test.proto_helpers import LineSendingProtocol\n        self.helper(self.test_lineSendingProtocol,\n                    LineSendingProtocol)\n\n\n    def test_fakeDatagramTransport(self):\n        from twisted.test.proto_helpers import FakeDatagramTransport\n        self.helper(self.test_fakeDatagramTransport,\n                    FakeDatagramTransport)\n\n\n    def test_stringTransport(self):\n        from twisted.test.proto_helpers import StringTransport\n        self.helper(self.test_stringTransport,\n                    StringTransport)\n\n\n    def test_stringTransportWithDisconnection(self):\n        from twisted.test.proto_helpers import (\n            StringTransportWithDisconnection)\n        self.helper(self.test_stringTransportWithDisconnection,\n                    StringTransportWithDisconnection)\n\n\n    def test_stringIOWithoutClosing(self):\n        from twisted.test.proto_helpers import StringIOWithoutClosing\n        self.helper(self.test_stringIOWithoutClosing,\n                    StringIOWithoutClosing)\n\n\n    def test__fakeConnector(self):\n        from twisted.test.proto_helpers import _FakeConnector\n        self.helper(self.test__fakeConnector,\n                    _FakeConnector)\n\n\n    def test__fakePort(self):\n        from twisted.test.proto_helpers import _FakePort\n        self.helper(self.test__fakePort,\n                    _FakePort)\n\n\n    def test_memoryReactor(self):\n        from twisted.test.proto_helpers import MemoryReactor\n        self.helper(self.test_memoryReactor,\n                    MemoryReactor)\n\n\n    def test_memoryReactorClock(self):\n        from twisted.test.proto_helpers import MemoryReactorClock\n        self.helper(self.test_memoryReactorClock,\n                    MemoryReactorClock)\n\n\n    def test_raisingMemoryReactor(self):\n        from twisted.test.proto_helpers import RaisingMemoryReactor\n        self.helper(self.test_raisingMemoryReactor,\n                    RaisingMemoryReactor)\n\n\n    def test_nonStreamingProducer(self):\n        from twisted.test.proto_helpers import NonStreamingProducer\n        self.helper(self.test_nonStreamingProducer,\n                    NonStreamingProducer)\n\n\n    def test_waitUntilAllDisconnected(self):\n        from twisted.test.proto_helpers import (\n            waitUntilAllDisconnected)\n        self.helper(self.test_waitUntilAllDisconnected,\n                    waitUntilAllDisconnected)\n\n\n    def test_eventLoggingObserver(self):\n        from twisted.test.proto_helpers import EventLoggingObserver\n        self.helper(self.test_eventLoggingObserver,\n                    EventLoggingObserver)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_threads.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for implementations of L{IReactorThreads}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__metaclass__ = type\n\nfrom weakref import ref\nimport gc, threading\n\nfrom twisted.python.threadable import isInIOThread\nfrom twisted.internet.test.reactormixins import ReactorBuilder\nfrom twisted.python.threadpool import ThreadPool\nfrom twisted.internet.interfaces import IReactorThreads\n\n\nclass ThreadTestsBuilder(ReactorBuilder):\n    \"\"\"\n    Builder for defining tests relating to L{IReactorThreads}.\n    \"\"\"\n    requiredInterfaces = (IReactorThreads,)\n\n    def test_getThreadPool(self):\n        \"\"\"\n        C{reactor.getThreadPool()} returns an instance of L{ThreadPool} which\n        starts when C{reactor.run()} is called and stops before it returns.\n        \"\"\"\n        state = []\n        reactor = self.buildReactor()\n\n        pool = reactor.getThreadPool()\n        self.assertIsInstance(pool, ThreadPool)\n        self.assertFalse(\n            pool.started, \"Pool should not start before reactor.run\")\n\n        def f():\n            # Record the state for later assertions\n            state.append(pool.started)\n            state.append(pool.joined)\n            reactor.stop()\n\n        reactor.callWhenRunning(f)\n        self.runReactor(reactor, 2)\n\n        self.assertTrue(\n            state[0], \"Pool should start after reactor.run\")\n        self.assertFalse(\n            state[1], \"Pool should not be joined before reactor.stop\")\n        self.assertTrue(\n            pool.joined,\n            \"Pool should be stopped after reactor.run returns\")\n\n\n    def test_suggestThreadPoolSize(self):\n        \"\"\"\n        C{reactor.suggestThreadPoolSize()} sets the maximum size of the reactor\n        threadpool.\n        \"\"\"\n        reactor = self.buildReactor()\n        reactor.suggestThreadPoolSize(17)\n        pool = reactor.getThreadPool()\n        self.assertEqual(pool.max, 17)\n\n\n    def test_delayedCallFromThread(self):\n        \"\"\"\n        A function scheduled with L{IReactorThreads.callFromThread} invoked\n        from a delayed call is run immediately in the next reactor iteration.\n\n        When invoked from the reactor thread, previous implementations of\n        L{IReactorThreads.callFromThread} would skip the pipe/socket based wake\n        up step, assuming the reactor would wake up on its own.  However, this\n        resulted in the reactor not noticing an insert into the thread queue at\n        the right time (in this case, after the thread queue has been processed\n        for that reactor iteration).\n        \"\"\"\n        reactor = self.buildReactor()\n\n        def threadCall():\n            reactor.stop()\n\n        # Set up the use of callFromThread being tested.\n        reactor.callLater(0, reactor.callFromThread, threadCall)\n\n        before = reactor.seconds()\n        self.runReactor(reactor, 60)\n        after = reactor.seconds()\n\n        # We specified a timeout of 60 seconds.  The timeout code in runReactor\n        # probably won't actually work, though.  If the reactor comes out of\n        # the event notification API just a little bit early, say after 59.9999\n        # seconds instead of after 60 seconds, then the queued thread call will\n        # get processed but the timeout delayed call runReactor sets up won't!\n        # Then the reactor will stop and runReactor will return without the\n        # timeout firing.  As it turns out, select() and poll() are quite\n        # likely to return *slightly* earlier than we ask them to, so the\n        # timeout will rarely happen, even if callFromThread is broken.  So,\n        # instead we'll measure the elapsed time and make sure it's something\n        # less than about half of the timeout we specified.  This is heuristic.\n        # It assumes that select() won't ever return after 30 seconds when we\n        # asked it to timeout after 60 seconds.  And of course like all\n        # time-based tests, it's slightly non-deterministic.  If the OS doesn't\n        # schedule this process for 30 seconds, then the test might fail even\n        # if callFromThread is working.\n        self.assertTrue(after - before < 30)\n\n\n    def test_callFromThread(self):\n        \"\"\"\n        A function scheduled with L{IReactorThreads.callFromThread} invoked\n        from another thread is run in the reactor thread.\n        \"\"\"\n        reactor = self.buildReactor()\n        result = []\n\n        def threadCall():\n            result.append(threading.currentThread())\n            reactor.stop()\n        reactor.callLater(0, reactor.callInThread,\n                          reactor.callFromThread, threadCall)\n        self.runReactor(reactor, 5)\n\n        self.assertEqual(result, [threading.currentThread()])\n\n\n    def test_stopThreadPool(self):\n        \"\"\"\n        When the reactor stops, L{ReactorBase._stopThreadPool} drops the\n        reactor's direct reference to its internal threadpool and removes\n        the associated startup and shutdown triggers.\n\n        This is the case of the thread pool being created before the reactor\n        is run.\n        \"\"\"\n        reactor = self.buildReactor()\n        threadpool = ref(reactor.getThreadPool())\n        reactor.callWhenRunning(reactor.stop)\n        self.runReactor(reactor)\n        gc.collect()\n        self.assertIsNone(threadpool())\n\n\n    def test_stopThreadPoolWhenStartedAfterReactorRan(self):\n        \"\"\"\n        We must handle the case of shutting down the thread pool when it was\n        started after the reactor was run in a special way.\n\n        Some implementation background: The thread pool is started with\n        callWhenRunning, which only returns a system trigger ID when it is\n        invoked before the reactor is started.\n\n        This is the case of the thread pool being created after the reactor\n        is started.\n        \"\"\"\n        reactor = self.buildReactor()\n        threadPoolRefs = []\n        def acquireThreadPool():\n            threadPoolRefs.append(ref(reactor.getThreadPool()))\n            reactor.stop()\n        reactor.callWhenRunning(acquireThreadPool)\n        self.runReactor(reactor)\n        gc.collect()\n        self.assertIsNone(threadPoolRefs[0]())\n\n\n    def test_cleanUpThreadPoolEvenBeforeReactorIsRun(self):\n        \"\"\"\n        When the reactor has its shutdown event fired before it is run, the\n        thread pool is completely destroyed.\n\n        For what it's worth, the reason we support this behavior at all is\n        because Trial does this.\n\n        This is the case of the thread pool being created without the reactor\n        being started at al.\n        \"\"\"\n        reactor = self.buildReactor()\n        threadPoolRef = ref(reactor.getThreadPool())\n        reactor.fireSystemEvent(\"shutdown\")\n\n        if reactor.__class__.__name__ == \"AsyncioSelectorReactor\":\n            self.assertIsNone(reactor.threadpool)\n            # ReactorBase.__init__ sets self.crash as a 'shutdown'\n            # event, which in turn calls stop on the underlying\n            # asyncio event loop, which in turn sets a _stopping\n            # attribute on it that's only unset after an iteration of\n            # the loop.  Subsequent tests can only reuse the asyncio\n            # loop if it's allowed to run and unset that _stopping\n            # attribute.\n            self.runReactor(reactor)\n        else:\n            gc.collect()\n            self.assertIsNone(threadPoolRef())\n\n\n    def test_isInIOThread(self):\n        \"\"\"\n        The reactor registers itself as the I/O thread when it runs so that\n        L{twisted.python.threadable.isInIOThread} returns C{True} if it is\n        called in the thread the reactor is running in.\n        \"\"\"\n        results = []\n        reactor = self.buildReactor()\n        def check():\n            results.append(isInIOThread())\n            reactor.stop()\n        reactor.callWhenRunning(check)\n        self.runReactor(reactor)\n        self.assertEqual([True], results)\n\n\n    def test_isNotInIOThread(self):\n        \"\"\"\n        The reactor registers itself as the I/O thread when it runs so that\n        L{twisted.python.threadable.isInIOThread} returns C{False} if it is\n        called in a different thread than the reactor is running in.\n        \"\"\"\n        results = []\n        reactor = self.buildReactor()\n        def check():\n            results.append(isInIOThread())\n            reactor.callFromThread(reactor.stop)\n        reactor.callInThread(check)\n        self.runReactor(reactor)\n        self.assertEqual([False], results)\n\n\nglobals().update(ThreadTestsBuilder.makeTestCaseClasses())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_time.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for implementations of L{IReactorTime}.\n\"\"\"\n\n__metaclass__ = type\n\nfrom twisted.python.log import msg\nfrom twisted.python.runtime import platform\n\nfrom twisted.trial.unittest import SkipTest\nfrom twisted.internet.test.reactormixins import ReactorBuilder\nfrom twisted.internet.interfaces import IReactorTime, IReactorThreads\n\n\nclass TimeTestsBuilder(ReactorBuilder):\n    \"\"\"\n    Builder for defining tests relating to L{IReactorTime}.\n    \"\"\"\n    requiredInterfaces = (IReactorTime,)\n\n    def test_delayedCallStopsReactor(self):\n        \"\"\"\n        The reactor can be stopped by a delayed call.\n        \"\"\"\n        reactor = self.buildReactor()\n        reactor.callLater(0, reactor.stop)\n        reactor.run()\n\n\n    def test_distantDelayedCall(self):\n        \"\"\"\n        Scheduling a delayed call at a point in the extreme future does not\n        prevent normal reactor operation.\n        \"\"\"\n        reactor = self.buildReactor()\n        if IReactorThreads.providedBy(reactor):\n            def eventSource(reactor, event):\n                msg(format=\"Thread-based event-source scheduling %(event)r\",\n                    event=event)\n                reactor.callFromThread(event)\n        else:\n            raise SkipTest(\"Do not know how to synthesize non-time event to \"\n                           \"stop the test\")\n\n        # Pick a pretty big delay.\n        delayedCall = reactor.callLater(2 ** 128 + 1, lambda: None)\n\n        def stop():\n            msg(\"Stopping the reactor\")\n            reactor.stop()\n\n        # Use repeated invocation of the event source to set up the call to stop\n        # the reactor.  This makes it more likely at least one normal iteration\n        # will take place with the delayed call in place before the slightly\n        # different reactor shutdown logic alters things.\n        eventSource(reactor, lambda: eventSource(reactor, stop))\n\n        # Run the reactor directly, without a timeout.  A timeout would\n        # interfere with the purpose of this test, which is to have the timeout\n        # passed to the reactor's doIterate implementation (potentially) be\n        # very, very large.  Hopefully the event source defined above will work\n        # and cause the reactor to stop.\n        reactor.run()\n\n        # The reactor almost surely stopped before the delayed call\n        # fired... right?\n        self.assertTrue(delayedCall.active())\n        self.assertIn(delayedCall, reactor.getDelayedCalls())\n\n\n\nclass GlibTimeTestsBuilder(ReactorBuilder):\n    \"\"\"\n    Builder for defining tests relating to L{IReactorTime} for reactors based\n    off glib.\n    \"\"\"\n    requiredInterfaces = (IReactorTime,)\n\n    if platform.isWindows():\n        _reactors = [\"twisted.internet.gtk2reactor.PortableGtkReactor\"]\n    else:\n        _reactors = [\"twisted.internet.glib2reactor.Glib2Reactor\",\n                     \"twisted.internet.gtk2reactor.Gtk2Reactor\"]\n\n    def test_timeout_add(self):\n        \"\"\"\n        A\n        L{reactor.callLater<twisted.internet.interfaces.IReactorTime.callLater>}\n        call scheduled from a C{gobject.timeout_add}\n        call is run on time.\n        \"\"\"\n        import gobject\n        reactor = self.buildReactor()\n\n        result = []\n        def gschedule():\n            reactor.callLater(0, callback)\n            return 0\n        def callback():\n            result.append(True)\n            reactor.stop()\n\n        reactor.callWhenRunning(gobject.timeout_add, 10, gschedule)\n        self.runReactor(reactor, 5)\n        self.assertEqual(result, [True])\n\n\nglobals().update(TimeTestsBuilder.makeTestCaseClasses())\nglobals().update(GlibTimeTestsBuilder.makeTestCaseClasses())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_tls.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for implementations of L{ITLSTransport}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__metaclass__ = type\n\nfrom zope.interface import implementer\n\nfrom twisted.python.compat import networkString\nfrom twisted.python.filepath import FilePath\nfrom twisted.internet.test.reactormixins import ReactorBuilder\nfrom twisted.internet.protocol import ServerFactory, ClientFactory, Protocol\nfrom twisted.internet.interfaces import (\n    IReactorSSL, ITLSTransport, IStreamClientEndpoint)\nfrom twisted.internet.defer import Deferred, DeferredList\nfrom twisted.internet.endpoints import (\n    SSL4ServerEndpoint, SSL4ClientEndpoint, TCP4ClientEndpoint)\nfrom twisted.internet.error import ConnectionClosed\nfrom twisted.internet.task import Cooperator\nfrom twisted.trial.unittest import SkipTest\nfrom twisted.python.runtime import platform\n\nfrom twisted.internet.test.test_core import ObjectModelIntegrationMixin\nfrom twisted.internet.test.test_tcp import (\n    ConnectToTCPListenerMixin, StreamTransportTestsMixin, AbortConnectionMixin,\n)\nfrom twisted.internet.test.connectionmixins import (\n    EndpointCreator, ConnectionTestsMixin, BrokenContextFactory)\n\ntry:\n    from OpenSSL.crypto import FILETYPE_PEM\nexcept ImportError:\n    FILETYPE_PEM = None\nelse:\n    from twisted.internet.ssl import PrivateCertificate, KeyPair\n    from twisted.internet.ssl import ClientContextFactory\n\n\nclass TLSMixin:\n    requiredInterfaces = [IReactorSSL]\n\n    if platform.isWindows():\n        msg = (\n            \"For some reason, these reactors don't deal with SSL \"\n            \"disconnection correctly on Windows.  See #3371.\")\n        skippedReactors = {\n            \"twisted.internet.glib2reactor.Glib2Reactor\": msg,\n            \"twisted.internet.gtk2reactor.Gtk2Reactor\": msg}\n\n\nclass ContextGeneratingMixin(object):\n    import twisted\n    _pem = FilePath(\n        networkString(twisted.__file__)).sibling(b\"test\").child(b\"server.pem\")\n    del twisted\n\n    def getServerContext(self):\n        \"\"\"\n        Return a new SSL context suitable for use in a test server.\n        \"\"\"\n        pem = self._pem.getContent()\n        cert = PrivateCertificate.load(\n            pem, KeyPair.load(pem, FILETYPE_PEM), FILETYPE_PEM)\n        return cert.options()\n\n\n    def getClientContext(self):\n        return ClientContextFactory()\n\n\n\n@implementer(IStreamClientEndpoint)\nclass StartTLSClientEndpoint(object):\n    \"\"\"\n    An endpoint which wraps another one and adds a TLS layer immediately when\n    connections are set up.\n\n    @ivar wrapped: A L{IStreamClientEndpoint} provider which will be used to\n        really set up connections.\n\n    @ivar contextFactory: A L{ContextFactory} to use to do TLS.\n    \"\"\"\n\n    def __init__(self, wrapped, contextFactory):\n        self.wrapped = wrapped\n        self.contextFactory = contextFactory\n\n\n    def connect(self, factory):\n        \"\"\"\n        Establish a connection using a protocol build by C{factory} and\n        immediately start TLS on it.  Return a L{Deferred} which fires with the\n        protocol instance.\n        \"\"\"\n        # This would be cleaner when we have ITransport.switchProtocol, which\n        # will be added with ticket #3204:\n        class WrapperFactory(ServerFactory):\n            def buildProtocol(wrapperSelf, addr):\n                protocol = factory.buildProtocol(addr)\n                def connectionMade(orig=protocol.connectionMade):\n                    protocol.transport.startTLS(self.contextFactory)\n                    orig()\n                protocol.connectionMade = connectionMade\n                return protocol\n\n        return self.wrapped.connect(WrapperFactory())\n\n\n\nclass StartTLSClientCreator(EndpointCreator, ContextGeneratingMixin):\n    \"\"\"\n    Create L{ITLSTransport.startTLS} endpoint for the client, and normal SSL\n    for server just because it's easier.\n    \"\"\"\n    def server(self, reactor):\n        \"\"\"\n        Construct an SSL server endpoint.  This should be constructing a TCP\n        server endpoint which immediately calls C{startTLS} instead, but that\n        is hard.\n        \"\"\"\n        return SSL4ServerEndpoint(reactor, 0, self.getServerContext())\n\n\n    def client(self, reactor, serverAddress):\n        \"\"\"\n        Construct a TCP client endpoint wrapped to immediately start TLS.\n        \"\"\"\n        return StartTLSClientEndpoint(\n            TCP4ClientEndpoint(\n                reactor, '127.0.0.1', serverAddress.port),\n            ClientContextFactory())\n\n\n\nclass BadContextTestsMixin(object):\n    \"\"\"\n    Mixin for L{ReactorBuilder} subclasses which defines a helper for testing\n    the handling of broken context factories.\n    \"\"\"\n    def _testBadContext(self, useIt):\n        \"\"\"\n        Assert that the exception raised by a broken context factory's\n        C{getContext} method is raised by some reactor method.  If it is not, an\n        exception will be raised to fail the test.\n\n        @param useIt: A two-argument callable which will be called with a\n            reactor and a broken context factory and which is expected to raise\n            the same exception as the broken context factory's C{getContext}\n            method.\n        \"\"\"\n        reactor = self.buildReactor()\n        exc = self.assertRaises(\n            ValueError, useIt, reactor, BrokenContextFactory())\n        self.assertEqual(BrokenContextFactory.message, str(exc))\n\n\n\nclass StartTLSClientTestsMixin(TLSMixin, ReactorBuilder, ConnectionTestsMixin):\n    \"\"\"\n    Tests for TLS connections established using L{ITLSTransport.startTLS} (as\n    opposed to L{IReactorSSL.connectSSL} or L{IReactorSSL.listenSSL}).\n    \"\"\"\n    endpoints = StartTLSClientCreator()\n\n\n\nclass SSLCreator(EndpointCreator, ContextGeneratingMixin):\n    \"\"\"\n    Create SSL endpoints.\n    \"\"\"\n    def server(self, reactor):\n        \"\"\"\n        Create an SSL server endpoint on a TCP/IP-stack allocated port.\n        \"\"\"\n        return SSL4ServerEndpoint(reactor, 0, self.getServerContext())\n\n\n    def client(self, reactor, serverAddress):\n        \"\"\"\n        Create an SSL client endpoint which will connect localhost on\n        the port given by C{serverAddress}.\n\n        @type serverAddress: L{IPv4Address}\n        \"\"\"\n        return SSL4ClientEndpoint(\n            reactor, '127.0.0.1', serverAddress.port,\n            ClientContextFactory())\n\n\nclass SSLClientTestsMixin(TLSMixin, ReactorBuilder, ContextGeneratingMixin,\n                          ConnectionTestsMixin, BadContextTestsMixin):\n    \"\"\"\n    Mixin defining tests relating to L{ITLSTransport}.\n    \"\"\"\n    endpoints = SSLCreator()\n\n    def test_badContext(self):\n        \"\"\"\n        If the context factory passed to L{IReactorSSL.connectSSL} raises an\n        exception from its C{getContext} method, that exception is raised by\n        L{IReactorSSL.connectSSL}.\n        \"\"\"\n        def useIt(reactor, contextFactory):\n            return reactor.connectSSL(\n                \"127.0.0.1\", 1234, ClientFactory(), contextFactory)\n        self._testBadContext(useIt)\n\n\n    def test_disconnectAfterWriteAfterStartTLS(self):\n        \"\"\"\n        L{ITCPTransport.loseConnection} ends a connection which was set up with\n        L{ITLSTransport.startTLS} and which has recently been written to.  This\n        is intended to verify that a socket send error masked by the TLS\n        implementation doesn't prevent the connection from being reported as\n        closed.\n        \"\"\"\n        class ShortProtocol(Protocol):\n            def connectionMade(self):\n                if not ITLSTransport.providedBy(self.transport):\n                    # Functionality isn't available to be tested.\n                    finished = self.factory.finished\n                    self.factory.finished = None\n                    finished.errback(SkipTest(\"No ITLSTransport support\"))\n                    return\n\n                # Switch the transport to TLS.\n                self.transport.startTLS(self.factory.context)\n                # Force TLS to really get negotiated.  If nobody talks, nothing\n                # will happen.\n                self.transport.write(b\"x\")\n\n            def dataReceived(self, data):\n                # Stuff some bytes into the socket.  This mostly has the effect\n                # of causing the next write to fail with ENOTCONN or EPIPE.\n                # With the pyOpenSSL implementation of ITLSTransport, the error\n                # is swallowed outside of the control of Twisted.\n                self.transport.write(b\"y\")\n                # Now close the connection, which requires a TLS close alert to\n                # be sent.\n                self.transport.loseConnection()\n\n            def connectionLost(self, reason):\n                # This is the success case.  The client and the server want to\n                # get here.\n                finished = self.factory.finished\n                if finished is not None:\n                    self.factory.finished = None\n                    finished.callback(reason)\n\n        reactor = self.buildReactor()\n\n        serverFactory = ServerFactory()\n        serverFactory.finished = Deferred()\n        serverFactory.protocol = ShortProtocol\n        serverFactory.context = self.getServerContext()\n\n        clientFactory = ClientFactory()\n        clientFactory.finished = Deferred()\n        clientFactory.protocol = ShortProtocol\n        clientFactory.context = self.getClientContext()\n        clientFactory.context.method = serverFactory.context.method\n\n        lostConnectionResults = []\n        finished = DeferredList(\n            [serverFactory.finished, clientFactory.finished],\n            consumeErrors=True)\n        def cbFinished(results):\n            lostConnectionResults.extend([results[0][1], results[1][1]])\n        finished.addCallback(cbFinished)\n\n        port = reactor.listenTCP(0, serverFactory, interface='127.0.0.1')\n        self.addCleanup(port.stopListening)\n\n        connector = reactor.connectTCP(\n            port.getHost().host, port.getHost().port, clientFactory)\n        self.addCleanup(connector.disconnect)\n\n        finished.addCallback(lambda ign: reactor.stop())\n        self.runReactor(reactor)\n        lostConnectionResults[0].trap(ConnectionClosed)\n        lostConnectionResults[1].trap(ConnectionClosed)\n\n\n\nclass TLSPortTestsBuilder(TLSMixin, ContextGeneratingMixin,\n                          ObjectModelIntegrationMixin, BadContextTestsMixin,\n                          ConnectToTCPListenerMixin,\n                          StreamTransportTestsMixin, ReactorBuilder):\n    \"\"\"\n    Tests for L{IReactorSSL.listenSSL}\n    \"\"\"\n\n    def getListeningPort(self, reactor, factory):\n        \"\"\"\n        Get a TLS port from a reactor.\n        \"\"\"\n        return reactor.listenSSL(0, factory, self.getServerContext())\n\n\n    def getExpectedStartListeningLogMessage(self, port, factory):\n        \"\"\"\n        Get the message expected to be logged when a TLS port starts listening.\n        \"\"\"\n        return \"%s (TLS) starting on %d\" % (factory, port.getHost().port)\n\n\n    def getExpectedConnectionLostLogMsg(self, port):\n        \"\"\"\n        Get the expected connection lost message for a TLS port.\n        \"\"\"\n        return \"(TLS Port %s Closed)\" % (port.getHost().port,)\n\n\n    def test_badContext(self):\n        \"\"\"\n        If the context factory passed to L{IReactorSSL.listenSSL} raises an\n        exception from its C{getContext} method, that exception is raised by\n        L{IReactorSSL.listenSSL}.\n        \"\"\"\n        def useIt(reactor, contextFactory):\n            return reactor.listenSSL(0, ServerFactory(), contextFactory)\n        self._testBadContext(useIt)\n\n\n    def connectToListener(self, reactor, address, factory):\n        \"\"\"\n        Connect to the given listening TLS port, assuming the\n        underlying transport is TCP.\n\n        @param reactor: The reactor under test.\n        @type reactor: L{IReactorSSL}\n\n        @param address: The listening's address.  Only the C{port}\n            component is used; see\n            L{ConnectToTCPListenerMixin.LISTENER_HOST}.\n        @type address: L{IPv4Address} or L{IPv6Address}\n\n        @param factory: The client factory.\n        @type factory: L{ClientFactory}\n\n        @return: The connector\n        \"\"\"\n        return reactor.connectSSL(\n            self.LISTENER_HOST,\n            address.port,\n            factory,\n            self.getClientContext(),\n        )\n\n\n\nglobals().update(SSLClientTestsMixin.makeTestCaseClasses())\nglobals().update(StartTLSClientTestsMixin.makeTestCaseClasses())\nglobals().update(TLSPortTestsBuilder().makeTestCaseClasses())\n\n\n\nclass AbortSSLConnectionTests(ReactorBuilder, AbortConnectionMixin, ContextGeneratingMixin):\n    \"\"\"\n    C{abortConnection} tests using SSL.\n    \"\"\"\n    requiredInterfaces = (IReactorSSL,)\n    endpoints = SSLCreator()\n\n    def buildReactor(self):\n        reactor = ReactorBuilder.buildReactor(self)\n        from twisted.internet import _producer_helpers\n\n        # Patch twisted.protocols.tls to use this reactor, until we get\n        # around to fixing #5206, or the TLS code uses an explicit reactor:\n        cooperator = Cooperator(\n            scheduler=lambda x: reactor.callLater(0.00001, x))\n        self.patch(_producer_helpers, \"cooperate\", cooperator.cooperate)\n        return reactor\n\n\n    def setUp(self):\n        if FILETYPE_PEM is None:\n            raise SkipTest(\"OpenSSL not available.\")\n\nglobals().update(AbortSSLConnectionTests.makeTestCaseClasses())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_udp.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for implementations of L{IReactorUDP} and the UDP parts of\nL{IReactorSocket}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__metaclass__ = type\n\nimport socket\n\nfrom zope.interface import implementer\nfrom zope.interface.verify import verifyObject\n\nfrom twisted.python import context\nfrom twisted.python.log import ILogContext, err\nfrom twisted.internet.test.reactormixins import ReactorBuilder\nfrom twisted.internet.defer import Deferred, maybeDeferred\nfrom twisted.internet.interfaces import (\n    ILoggingContext, IListeningPort, IReactorUDP, IReactorSocket)\nfrom twisted.internet.address import IPv4Address, IPv6Address\nfrom twisted.internet.protocol import DatagramProtocol\n\nfrom twisted.internet.test.connectionmixins import (LogObserverMixin,\n                                                    findFreePort)\nfrom twisted.internet import defer, error\nfrom twisted.test.test_udp import Server, GoodClient\nfrom twisted.trial.unittest import SkipTest\n\n\ndef _has_ipv6():\n    \"\"\" Returns True if the system can bind an IPv6 address.\"\"\"\n    sock = None\n    has_ipv6 = False\n\n    try:\n        sock = socket.socket(socket.AF_INET6)\n        sock.bind((\"::1\", 0))\n        has_ipv6 = True\n    except socket.error:\n        pass\n\n    if sock:\n        sock.close()\n    return has_ipv6\n\n\nHAS_IPV6 = _has_ipv6()\n\n\ndef skipWithoutIPv6(f):\n    if not HAS_IPV6:\n        f.skip = \"Does not work on systems without IPv6 support.\"\n    return f\n\n\n\nclass DatagramTransportTestsMixin(LogObserverMixin):\n    \"\"\"\n    Mixin defining tests which apply to any port/datagram based transport.\n    \"\"\"\n    def test_startedListeningLogMessage(self):\n        \"\"\"\n        When a port starts, a message including a description of the associated\n        protocol is logged.\n        \"\"\"\n        loggedMessages = self.observe()\n        reactor = self.buildReactor()\n\n        @implementer(ILoggingContext)\n        class SomeProtocol(DatagramProtocol):\n            def logPrefix(self):\n                return \"Crazy Protocol\"\n        protocol = SomeProtocol()\n\n        p = self.getListeningPort(reactor, protocol)\n        expectedMessage = \"Crazy Protocol starting on %d\" % (p.getHost().port,)\n        self.assertEqual((expectedMessage,), loggedMessages[0]['message'])\n\n\n    def test_connectionLostLogMessage(self):\n        \"\"\"\n        When a connection is lost a message is logged containing an\n        address identifying the port and the fact that it was closed.\n        \"\"\"\n        loggedMessages = self.observe()\n        reactor = self.buildReactor()\n        p = self.getListeningPort(reactor, DatagramProtocol())\n        expectedMessage = \"(UDP Port %s Closed)\" % (p.getHost().port,)\n\n        def stopReactor(ignored):\n            reactor.stop()\n\n        def doStopListening():\n            del loggedMessages[:]\n            maybeDeferred(p.stopListening).addCallback(stopReactor)\n\n        reactor.callWhenRunning(doStopListening)\n        self.runReactor(reactor)\n\n        self.assertEqual((expectedMessage,), loggedMessages[0]['message'])\n\n\n    def test_stopProtocolScheduling(self):\n        \"\"\"\n        L{DatagramProtocol.stopProtocol} is called asynchronously (ie, not\n        re-entrantly) when C{stopListening} is used to stop the datagram\n        transport.\n        \"\"\"\n        class DisconnectingProtocol(DatagramProtocol):\n\n            started = False\n            stopped = False\n            inStartProtocol = False\n            stoppedInStart = False\n\n            def startProtocol(self):\n                self.started = True\n                self.inStartProtocol = True\n                self.transport.stopListening()\n                self.inStartProtocol = False\n\n            def stopProtocol(self):\n                self.stopped = True\n                self.stoppedInStart = self.inStartProtocol\n                reactor.stop()\n\n        reactor = self.buildReactor()\n        protocol = DisconnectingProtocol()\n        self.getListeningPort(reactor, protocol)\n        self.runReactor(reactor)\n\n        self.assertTrue(protocol.started)\n        self.assertTrue(protocol.stopped)\n        self.assertFalse(protocol.stoppedInStart)\n\n\n\nclass UDPPortTestsMixin(object):\n    \"\"\"\n    Tests for L{IReactorUDP.listenUDP} and\n    L{IReactorSocket.adoptDatagramPort}.\n    \"\"\"\n    def test_interface(self):\n        \"\"\"\n        L{IReactorUDP.listenUDP} returns an object providing L{IListeningPort}.\n        \"\"\"\n        reactor = self.buildReactor()\n        port = self.getListeningPort(reactor, DatagramProtocol())\n        self.assertTrue(verifyObject(IListeningPort, port))\n\n\n    def test_getHost(self):\n        \"\"\"\n        L{IListeningPort.getHost} returns an L{IPv4Address} giving a\n        dotted-quad of the IPv4 address the port is listening on as well as\n        the port number.\n        \"\"\"\n        host, portNumber = findFreePort(type=socket.SOCK_DGRAM)\n        reactor = self.buildReactor()\n        port = self.getListeningPort(\n            reactor, DatagramProtocol(), port=portNumber, interface=host)\n        self.assertEqual(\n            port.getHost(), IPv4Address('UDP', host, portNumber))\n\n\n    @skipWithoutIPv6\n    def test_getHostIPv6(self):\n        \"\"\"\n        L{IListeningPort.getHost} returns an L{IPv6Address} when listening on\n        an IPv6 interface.\n        \"\"\"\n        reactor = self.buildReactor()\n        port = self.getListeningPort(\n            reactor, DatagramProtocol(), interface='::1')\n        addr = port.getHost()\n        self.assertEqual(addr.host, \"::1\")\n        self.assertIsInstance(addr, IPv6Address)\n\n\n    def test_invalidInterface(self):\n        \"\"\"\n        An L{InvalidAddressError} is raised when trying to listen on an address\n        that isn't a valid IPv4 or IPv6 address.\n        \"\"\"\n        reactor = self.buildReactor()\n        self.assertRaises(\n            error.InvalidAddressError, reactor.listenUDP, DatagramProtocol(),\n            0, interface='example.com')\n\n\n    def test_logPrefix(self):\n        \"\"\"\n        Datagram transports implement L{ILoggingContext.logPrefix} to return a\n        message reflecting the protocol they are running.\n        \"\"\"\n        class CustomLogPrefixDatagramProtocol(DatagramProtocol):\n            def __init__(self, prefix):\n                self._prefix = prefix\n                self.system = Deferred()\n\n            def logPrefix(self):\n                return self._prefix\n\n            def datagramReceived(self, bytes, addr):\n                if self.system is not None:\n                    system = self.system\n                    self.system = None\n                    system.callback(context.get(ILogContext)[\"system\"])\n\n        reactor = self.buildReactor()\n        protocol = CustomLogPrefixDatagramProtocol(\"Custom Datagrams\")\n        d = protocol.system\n        port = self.getListeningPort(reactor, protocol)\n        address = port.getHost()\n\n        def gotSystem(system):\n            self.assertEqual(\"Custom Datagrams (UDP)\", system)\n        d.addCallback(gotSystem)\n        d.addErrback(err)\n        d.addCallback(lambda ignored: reactor.stop())\n\n        port.write(b\"some bytes\", ('127.0.0.1', address.port))\n        self.runReactor(reactor)\n\n\n    def test_writeSequence(self):\n        \"\"\"\n        Write a sequence of L{bytes} to a L{DatagramProtocol}.\n        \"\"\"\n        class SimpleDatagramProtocol(DatagramProtocol):\n            def __init__(self):\n                self.defer = Deferred()\n\n            def datagramReceived(self, data, addr):\n                self.defer.callback(data)\n\n        reactor = self.buildReactor()\n        protocol = SimpleDatagramProtocol()\n        defer = protocol.defer\n        port = self.getListeningPort(reactor, protocol)\n        address = port.getHost()\n        dataToWrite = (b\"some\", b\"bytes\", b\"to\", b\"write\")\n\n        def gotData(data):\n            self.assertEqual(b\"\".join(dataToWrite), data)\n\n        defer.addCallback(gotData)\n        defer.addErrback(err)\n        defer.addCallback(lambda ignored: reactor.stop())\n        port.writeSequence(dataToWrite, ('127.0.0.1', address.port))\n        self.runReactor(reactor)\n\n\n    def test_str(self):\n        \"\"\"\n        C{str()} on the listening port object includes the port number.\n        \"\"\"\n        reactor = self.buildReactor()\n        port = self.getListeningPort(reactor, DatagramProtocol())\n        self.assertIn(str(port.getHost().port), str(port))\n\n\n    def test_repr(self):\n        \"\"\"\n        C{repr()} on the listening port object includes the port number.\n        \"\"\"\n        reactor = self.buildReactor()\n        port = self.getListeningPort(reactor, DatagramProtocol())\n        self.assertIn(repr(port.getHost().port), str(port))\n\n\n    @skipWithoutIPv6\n    def test_writeToIPv6Interface(self):\n        \"\"\"\n        Writing to an IPv6 UDP socket on the loopback interface succeeds.\n        \"\"\"\n        reactor = self.buildReactor()\n        server = Server()\n        serverStarted = server.startedDeferred = defer.Deferred()\n        self.getListeningPort(reactor, server, interface=\"::1\")\n\n        client = GoodClient()\n        clientStarted = client.startedDeferred = defer.Deferred()\n        self.getListeningPort(reactor, client, interface=\"::1\")\n        cAddr = client.transport.getHost()\n\n        def cbClientStarted(ignored):\n            \"\"\"\n            Send a datagram from the client once it's started.\n\n            @param ignored: a list of C{[None, None]}, which is ignored\n            @returns: a deferred which fires when the server has received a\n                datagram.\n            \"\"\"\n            client.transport.write(\n                b\"spam\", (\"::1\", server.transport.getHost().port))\n            serverReceived = server.packetReceived = defer.Deferred()\n            return serverReceived\n\n        def cbServerReceived(ignored):\n            \"\"\"\n            Stop the reactor after a datagram is received.\n\n            @param ignored: L{None}, which is ignored\n            @returns: L{None}\n            \"\"\"\n            reactor.stop()\n\n        d = defer.gatherResults([serverStarted, clientStarted])\n        d.addCallback(cbClientStarted)\n        d.addCallback(cbServerReceived)\n        d.addErrback(err)\n        self.runReactor(reactor)\n\n        packet = server.packets[0]\n        self.assertEqual(packet, (b'spam', (cAddr.host, cAddr.port)))\n\n\n    @skipWithoutIPv6\n    def test_connectedWriteToIPv6Interface(self):\n        \"\"\"\n        An IPv6 address can be passed as the C{interface} argument to\n        L{listenUDP}. The resulting Port accepts IPv6 datagrams.\n        \"\"\"\n        reactor = self.buildReactor()\n        server = Server()\n        serverStarted = server.startedDeferred = defer.Deferred()\n        self.getListeningPort(reactor, server, interface=\"::1\")\n\n        client = GoodClient()\n        clientStarted = client.startedDeferred = defer.Deferred()\n        self.getListeningPort(reactor, client, interface=\"::1\")\n        cAddr = client.transport.getHost()\n\n        def cbClientStarted(ignored):\n            \"\"\"\n            Send a datagram from the client once it's started.\n\n            @param ignored: a list of C{[None, None]}, which is ignored\n            @returns: a deferred which fires when the server has received a\n                datagram.\n            \"\"\"\n\n            client.transport.connect(\"::1\", server.transport.getHost().port)\n            client.transport.write(b\"spam\")\n            serverReceived = server.packetReceived = defer.Deferred()\n            return serverReceived\n\n        def cbServerReceived(ignored):\n            \"\"\"\n            Stop the reactor after a datagram is received.\n\n            @param ignored: L{None}, which is ignored\n            @returns: L{None}\n            \"\"\"\n\n            reactor.stop()\n\n        d = defer.gatherResults([serverStarted, clientStarted])\n        d.addCallback(cbClientStarted)\n        d.addCallback(cbServerReceived)\n        d.addErrback(err)\n        self.runReactor(reactor)\n\n        packet = server.packets[0]\n        self.assertEqual(packet, (b'spam', (cAddr.host, cAddr.port)))\n\n\n    def test_writingToHostnameRaisesInvalidAddressError(self):\n        \"\"\"\n        Writing to a hostname instead of an IP address will raise an\n        L{InvalidAddressError}.\n        \"\"\"\n        reactor = self.buildReactor()\n        port = self.getListeningPort(reactor, DatagramProtocol())\n        self.assertRaises(\n            error.InvalidAddressError,\n            port.write, 'spam', ('example.invalid', 1))\n\n\n    @skipWithoutIPv6\n    def test_writingToIPv6OnIPv4RaisesInvalidAddressError(self):\n        \"\"\"\n        Writing to an IPv6 address on an IPv4 socket will raise an\n        L{InvalidAddressError}.\n        \"\"\"\n        reactor = self.buildReactor()\n        port = self.getListeningPort(\n            reactor, DatagramProtocol(), interface=\"127.0.0.1\")\n        self.assertRaises(\n            error.InvalidAddressError, port.write, 'spam', ('::1', 1))\n\n\n    @skipWithoutIPv6\n    def test_writingToIPv4OnIPv6RaisesInvalidAddressError(self):\n        \"\"\"\n        Writing to an IPv6 address on an IPv4 socket will raise an\n        L{InvalidAddressError}.\n        \"\"\"\n        reactor = self.buildReactor()\n        port = self.getListeningPort(\n            reactor, DatagramProtocol(), interface=\"::1\")\n        self.assertRaises(\n            error.InvalidAddressError, port.write, 'spam', ('127.0.0.1', 1))\n\n\n    def test_connectingToHostnameRaisesInvalidAddressError(self):\n        \"\"\"\n        Connecting to a hostname instead of an IP address will raise an\n        L{InvalidAddressError}.\n        \"\"\"\n        reactor = self.buildReactor()\n        port = self.getListeningPort(reactor, DatagramProtocol())\n        self.assertRaises(\n            error.InvalidAddressError, port.connect, 'example.invalid', 1)\n\n\n    def test_allowBroadcast(self):\n        \"\"\"\n        L{IListeningPort.setBroadcastAllowed} sets broadcast to be allowed\n        on the socket.\n        \"\"\"\n        reactor = self.buildReactor()\n        port = self.getListeningPort(reactor, DatagramProtocol())\n        port.setBroadcastAllowed(True)\n        self.assertTrue(port.getBroadcastAllowed())\n\n\n\nclass UDPServerTestsBuilder(ReactorBuilder,\n                            UDPPortTestsMixin, DatagramTransportTestsMixin):\n    \"\"\"\n    Run L{UDPPortTestsMixin} tests using newly created UDP\n    sockets.\n    \"\"\"\n    requiredInterfaces = (IReactorUDP,)\n\n    def getListeningPort(self, reactor, protocol, port=0, interface='',\n                         maxPacketSize=8192):\n        \"\"\"\n        Get a UDP port from a reactor.\n\n        @param reactor: A reactor used to build the returned\n            L{IListeningPort} provider.\n        @type reactor: L{twisted.internet.interfaces.IReactorUDP}\n\n        @see: L{twisted.internet.IReactorUDP.listenUDP} for other\n            argument and return types.\n        \"\"\"\n        return reactor.listenUDP(port, protocol, interface=interface,\n                                 maxPacketSize=maxPacketSize)\n\n\n\nclass UDPFDServerTestsBuilder(ReactorBuilder,\n                              UDPPortTestsMixin, DatagramTransportTestsMixin):\n    \"\"\"\n    Run L{UDPPortTestsMixin} tests using adopted UDP sockets.\n    \"\"\"\n    requiredInterfaces = (IReactorSocket,)\n\n    def getListeningPort(self, reactor, protocol, port=0, interface='',\n                         maxPacketSize=8192):\n        \"\"\"\n        Get a UDP port from a reactor, wrapping an already-initialized file\n        descriptor.\n\n        @param reactor: A reactor used to build the returned\n            L{IListeningPort} provider.\n        @type reactor: L{twisted.internet.interfaces.IReactorSocket}\n\n        @param port: A port number to which the adopted socket will be\n            bound.\n        @type port: C{int}\n\n        @param interface: The local IPv4 or IPv6 address to which the\n            adopted socket will be bound.  defaults to '', ie all IPv4\n            addresses.\n        @type interface: C{str}\n\n        @see: L{twisted.internet.IReactorSocket.adoptDatagramPort} for other\n            argument and return types.\n        \"\"\"\n        if IReactorSocket.providedBy(reactor):\n            if ':' in interface:\n                domain = socket.AF_INET6\n                address = socket.getaddrinfo(interface, port)[0][4]\n            else:\n                domain = socket.AF_INET\n                address = (interface, port)\n            portSock = socket.socket(domain, socket.SOCK_DGRAM)\n            portSock.bind(address)\n            portSock.setblocking(False)\n            try:\n                return reactor.adoptDatagramPort(\n                    portSock.fileno(), portSock.family, protocol,\n                    maxPacketSize)\n            finally:\n                # The socket should still be open; fileno will raise if it is\n                # not.\n                portSock.fileno()\n                # Now clean it up, because the rest of the test does not need\n                # it.\n                portSock.close()\n        else:\n            raise SkipTest(\"Reactor does not provide IReactorSocket\")\n\n\n\nglobals().update(UDPServerTestsBuilder.makeTestCaseClasses())\nglobals().update(UDPFDServerTestsBuilder.makeTestCaseClasses())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_udp_internals.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for the internal implementation details of L{twisted.internet.udp}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport socket\n\nfrom twisted.trial import unittest\nfrom twisted.internet.protocol import DatagramProtocol\nfrom twisted.internet import udp\nfrom twisted.python.runtime import platformType\n\nif platformType == 'win32':\n    from errno import WSAEWOULDBLOCK as EWOULDBLOCK\nelse:\n    from errno import EWOULDBLOCK\n\n\n\nclass StringUDPSocket(object):\n    \"\"\"\n    A fake UDP socket object, which returns a fixed sequence of strings and/or\n    socket errors.  Useful for testing.\n\n    @ivar retvals: A C{list} containing either strings or C{socket.error}s.\n\n    @ivar connectedAddr: The address the socket is connected to.\n    \"\"\"\n\n    def __init__(self, retvals):\n        self.retvals = retvals\n        self.connectedAddr = None\n\n\n    def connect(self, addr):\n        self.connectedAddr = addr\n\n\n    def recvfrom(self, size):\n        \"\"\"\n        Return (or raise) the next value from C{self.retvals}.\n        \"\"\"\n        ret = self.retvals.pop(0)\n        if isinstance(ret, socket.error):\n            raise ret\n        return ret, None\n\n\n\nclass KeepReads(DatagramProtocol):\n    \"\"\"\n    Accumulate reads in a list.\n    \"\"\"\n\n    def __init__(self):\n        self.reads = []\n\n\n    def datagramReceived(self, data, addr):\n        self.reads.append(data)\n\n\n\nclass ErrorsTests(unittest.SynchronousTestCase):\n    \"\"\"\n    Error handling tests for C{udp.Port}.\n    \"\"\"\n\n    def test_socketReadNormal(self):\n        \"\"\"\n        Socket reads with some good data followed by a socket error which can\n        be ignored causes reading to stop, and no log messages to be logged.\n        \"\"\"\n        # Add a fake error to the list of ignorables:\n        udp._sockErrReadIgnore.append(-7000)\n        self.addCleanup(udp._sockErrReadIgnore.remove, -7000)\n\n        protocol = KeepReads()\n        port = udp.Port(None, protocol)\n\n        # Normal result, no errors\n        port.socket = StringUDPSocket(\n            [b\"result\", b\"123\", socket.error(-7000), b\"456\",\n             socket.error(-7000)])\n        port.doRead()\n        # Read stops on error:\n        self.assertEqual(protocol.reads, [b\"result\", b\"123\"])\n        port.doRead()\n        self.assertEqual(protocol.reads, [b\"result\", b\"123\", b\"456\"])\n\n\n    def test_readImmediateError(self):\n        \"\"\"\n        If the socket is unconnected, socket reads with an immediate\n        connection refusal are ignored, and reading stops. The protocol's\n        C{connectionRefused} method is not called.\n        \"\"\"\n        # Add a fake error to the list of those that count as connection\n        # refused:\n        udp._sockErrReadRefuse.append(-6000)\n        self.addCleanup(udp._sockErrReadRefuse.remove, -6000)\n\n        protocol = KeepReads()\n        # Fail if connectionRefused is called:\n        protocol.connectionRefused = lambda: 1/0\n\n        port = udp.Port(None, protocol)\n\n        # Try an immediate \"connection refused\"\n        port.socket = StringUDPSocket([b\"a\", socket.error(-6000), b\"b\",\n                                       socket.error(EWOULDBLOCK)])\n        port.doRead()\n        # Read stops on error:\n        self.assertEqual(protocol.reads, [b\"a\"])\n        # Read again:\n        port.doRead()\n        self.assertEqual(protocol.reads, [b\"a\", b\"b\"])\n\n\n    def test_connectedReadImmediateError(self):\n        \"\"\"\n        If the socket connected, socket reads with an immediate\n        connection refusal are ignored, and reading stops. The protocol's\n        C{connectionRefused} method is called.\n        \"\"\"\n        # Add a fake error to the list of those that count as connection\n        # refused:\n        udp._sockErrReadRefuse.append(-6000)\n        self.addCleanup(udp._sockErrReadRefuse.remove, -6000)\n\n        protocol = KeepReads()\n        refused = []\n        protocol.connectionRefused = lambda: refused.append(True)\n\n        port = udp.Port(None, protocol)\n        port.socket = StringUDPSocket([b\"a\", socket.error(-6000), b\"b\",\n                                       socket.error(EWOULDBLOCK)])\n        port.connect(\"127.0.0.1\", 9999)\n\n        # Read stops on error:\n        port.doRead()\n        self.assertEqual(protocol.reads, [b\"a\"])\n        self.assertEqual(refused, [True])\n\n        # Read again:\n        port.doRead()\n        self.assertEqual(protocol.reads, [b\"a\", b\"b\"])\n        self.assertEqual(refused, [True])\n\n\n    def test_readUnknownError(self):\n        \"\"\"\n        Socket reads with an unknown socket error are raised.\n        \"\"\"\n        protocol = KeepReads()\n        port = udp.Port(None, protocol)\n\n        # Some good data, followed by an unknown error\n        port.socket = StringUDPSocket([b\"good\", socket.error(-1337)])\n        self.assertRaises(socket.error, port.doRead)\n        self.assertEqual(protocol.reads, [b\"good\"])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_unix.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for implementations of L{IReactorUNIX}.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom stat import S_IMODE\nfrom os import stat, close, urandom, unlink, fstat\nfrom tempfile import mktemp, mkstemp\nfrom socket import AF_INET, SOCK_STREAM, SOL_SOCKET, socket, error\nfrom pprint import pformat\nfrom hashlib import md5\nfrom struct import pack\n\ntry:\n    from socket import AF_UNIX\nexcept ImportError:\n    AF_UNIX = None\n\nfrom zope.interface import implementer\n\nfrom twisted.internet import interfaces, base\nfrom twisted.internet.address import UNIXAddress\nfrom twisted.internet.defer import Deferred, fail, gatherResults\nfrom twisted.internet.endpoints import UNIXServerEndpoint, UNIXClientEndpoint\nfrom twisted.internet.error import (ConnectionClosed, FileDescriptorOverrun,\n    CannotListenError)\nfrom twisted.internet.interfaces import (IFileDescriptorReceiver, IReactorUNIX,\n    IReactorSocket, IReactorFDSet)\nfrom twisted.internet.protocol import DatagramProtocol\nfrom twisted.internet.protocol import ServerFactory, ClientFactory\nfrom twisted.internet.task import LoopingCall\nfrom twisted.internet.test.connectionmixins import EndpointCreator\nfrom twisted.internet.test.reactormixins import ReactorBuilder\nfrom twisted.internet.test.test_core import ObjectModelIntegrationMixin\nfrom twisted.internet.test.test_tcp import (StreamTransportTestsMixin,\n    WriteSequenceTestsMixin, MyClientFactory, MyServerFactory,)\nfrom twisted.internet.test.connectionmixins import ConnectableProtocol\nfrom twisted.internet.test.connectionmixins import ConnectionTestsMixin\nfrom twisted.internet.test.connectionmixins import StreamClientTestsMixin\nfrom twisted.internet.test.connectionmixins import runProtocolsWithReactor\nfrom twisted.python.compat import nativeString, _PY3, iteritems\nfrom twisted.python.failure import Failure\nfrom twisted.python.log import addObserver, removeObserver, err\nfrom twisted.python.runtime import platform\nfrom twisted.python.reflect import requireModule\nfrom twisted.python.filepath import _coerceToFilesystemEncoding\n\nif requireModule(\"twisted.python.sendmsg\") is not None:\n    sendmsgSkip = None\nelse:\n    sendmsgSkip = (\n        \"sendmsg extension unavailable, extended UNIX features disabled\")\n\n\n\nclass UNIXFamilyMixin(object):\n    \"\"\"\n    Test-helper defining mixin for things related to AF_UNIX sockets.\n    \"\"\"\n    def _modeTest(self, methodName, path, factory):\n        \"\"\"\n        Assert that the mode of the created unix socket is set to the mode\n        specified to the reactor method.\n        \"\"\"\n        mode = 0o600\n        reactor = self.buildReactor()\n        unixPort = getattr(reactor, methodName)(path, factory, mode=mode)\n        unixPort.stopListening()\n        self.assertEqual(S_IMODE(stat(path).st_mode), mode)\n\n\ndef _abstractPath(case):\n    \"\"\"\n    Return a new, unique abstract namespace path to be listened on.\n    \"\"\"\n    return md5(urandom(100)).hexdigest()\n\n\n\nclass UNIXCreator(EndpointCreator):\n    \"\"\"\n    Create UNIX socket end points.\n    \"\"\"\n    requiredInterfaces = (interfaces.IReactorUNIX,)\n\n    def server(self, reactor):\n        \"\"\"\n        Construct a UNIX server endpoint.\n        \"\"\"\n        # self.mktemp() often returns a path which is too long to be used.\n        path = mktemp(suffix='.sock', dir='.')\n        return UNIXServerEndpoint(reactor, path)\n\n\n    def client(self, reactor, serverAddress):\n        \"\"\"\n        Construct a UNIX client endpoint.\n        \"\"\"\n        return UNIXClientEndpoint(reactor, serverAddress.name)\n\n\n\nclass SendFileDescriptor(ConnectableProtocol):\n    \"\"\"\n    L{SendFileDescriptorAndBytes} sends a file descriptor and optionally some\n    normal bytes and then closes its connection.\n\n    @ivar reason: The reason the connection was lost, after C{connectionLost}\n        is called.\n    \"\"\"\n    reason = None\n\n    def __init__(self, fd, data):\n        \"\"\"\n        @param fd: A C{int} giving a file descriptor to send over the\n            connection.\n\n        @param data: A C{str} giving data to send over the connection, or\n            L{None} if no data is to be sent.\n        \"\"\"\n        self.fd = fd\n        self.data = data\n\n\n    def connectionMade(self):\n        \"\"\"\n        Send C{self.fd} and, if it is not L{None}, C{self.data}.  Then close the\n        connection.\n        \"\"\"\n        self.transport.sendFileDescriptor(self.fd)\n        if self.data:\n            self.transport.write(self.data)\n        self.transport.loseConnection()\n\n\n    def connectionLost(self, reason):\n        ConnectableProtocol.connectionLost(self, reason)\n        self.reason = reason\n\n\n\n@implementer(IFileDescriptorReceiver)\nclass ReceiveFileDescriptor(ConnectableProtocol):\n    \"\"\"\n    L{ReceiveFileDescriptor} provides an API for waiting for file descriptors to\n    be received.\n\n    @ivar reason: The reason the connection was lost, after C{connectionLost}\n        is called.\n\n    @ivar waiting: A L{Deferred} which fires with a file descriptor once one is\n        received, or with a failure if the connection is lost with no descriptor\n        arriving.\n    \"\"\"\n\n    reason = None\n    waiting = None\n\n    def waitForDescriptor(self):\n        \"\"\"\n        Return a L{Deferred} which will fire with the next file descriptor\n        received, or with a failure if the connection is or has already been\n        lost.\n        \"\"\"\n        if self.reason is None:\n            self.waiting = Deferred()\n            return self.waiting\n        else:\n            return fail(self.reason)\n\n\n    def fileDescriptorReceived(self, descriptor):\n        \"\"\"\n        Fire the waiting Deferred, initialized by C{waitForDescriptor}, with the\n        file descriptor just received.\n        \"\"\"\n        self.waiting.callback(descriptor)\n        self.waiting = None\n\n\n    def dataReceived(self, data):\n        \"\"\"\n        Fail the waiting Deferred, if it has not already been fired by\n        C{fileDescriptorReceived}.  The bytes sent along with a file descriptor\n        are guaranteed to be delivered to the protocol's C{dataReceived} method\n        only after the file descriptor has been delivered to the protocol's\n        C{fileDescriptorReceived}.\n        \"\"\"\n        if self.waiting is not None:\n            self.waiting.errback(Failure(Exception(\n                        \"Received bytes (%r) before descriptor.\" % (data,))))\n            self.waiting = None\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Fail the waiting Deferred, initialized by C{waitForDescriptor}, if there\n        is one.\n        \"\"\"\n        ConnectableProtocol.connectionLost(self, reason)\n        if self.waiting is not None:\n            self.waiting.errback(reason)\n            self.waiting = None\n        self.reason = reason\n\n\n\nclass UNIXTestsBuilder(UNIXFamilyMixin, ReactorBuilder, ConnectionTestsMixin):\n    \"\"\"\n    Builder defining tests relating to L{IReactorUNIX}.\n    \"\"\"\n    requiredInterfaces = (IReactorUNIX,)\n\n    endpoints = UNIXCreator()\n\n\n    def test_mode(self):\n        \"\"\"\n        The UNIX socket created by L{IReactorUNIX.listenUNIX} is created with\n        the mode specified.\n        \"\"\"\n        self._modeTest('listenUNIX', self.mktemp(), ServerFactory())\n\n\n    def test_listenOnLinuxAbstractNamespace(self):\n        \"\"\"\n        On Linux, a UNIX socket path may begin with C{'\\0'} to indicate a socket\n        in the abstract namespace.  L{IReactorUNIX.listenUNIX} accepts such a\n        path.\n        \"\"\"\n        # Don't listen on a path longer than the maximum allowed.\n        path = _abstractPath(self)\n        reactor = self.buildReactor()\n        port = reactor.listenUNIX('\\0' + path, ServerFactory())\n        self.assertEqual(port.getHost(), UNIXAddress('\\0' + path))\n    if not platform.isLinux():\n        test_listenOnLinuxAbstractNamespace.skip = (\n            'Abstract namespace UNIX sockets only supported on Linux.')\n\n\n    def test_listenFailure(self):\n        \"\"\"\n        L{IReactorUNIX.listenUNIX} raises L{CannotListenError} if the\n        underlying port's createInternetSocket raises a socket error.\n        \"\"\"\n        def raiseSocketError(self):\n            raise error('FakeBasePort forced socket.error')\n\n        self.patch(base.BasePort, \"createInternetSocket\", raiseSocketError)\n        reactor = self.buildReactor()\n        with self.assertRaises(CannotListenError):\n            reactor.listenUNIX('not-used', ServerFactory())\n\n\n    def test_connectToLinuxAbstractNamespace(self):\n        \"\"\"\n        L{IReactorUNIX.connectUNIX} also accepts a Linux abstract namespace\n        path.\n        \"\"\"\n        path = _abstractPath(self)\n        reactor = self.buildReactor()\n        connector = reactor.connectUNIX('\\0' + path, ClientFactory())\n        self.assertEqual(connector.getDestination(), UNIXAddress('\\0' + path))\n    if not platform.isLinux():\n        test_connectToLinuxAbstractNamespace.skip = (\n            'Abstract namespace UNIX sockets only supported on Linux.')\n\n\n    def test_addresses(self):\n        \"\"\"\n        A client's transport's C{getHost} and C{getPeer} return L{UNIXAddress}\n        instances which have the filesystem path of the host and peer ends of\n        the connection.\n        \"\"\"\n        class SaveAddress(ConnectableProtocol):\n            def makeConnection(self, transport):\n                self.addresses = dict(\n                    host=transport.getHost(), peer=transport.getPeer())\n                transport.loseConnection()\n\n        server = SaveAddress()\n        client = SaveAddress()\n\n        runProtocolsWithReactor(self, server, client, self.endpoints)\n\n        self.assertEqual(server.addresses['host'], client.addresses['peer'])\n        self.assertEqual(server.addresses['peer'], client.addresses['host'])\n\n\n    def test_sendFileDescriptor(self):\n        \"\"\"\n        L{IUNIXTransport.sendFileDescriptor} accepts an integer file descriptor\n        and sends a copy of it to the process reading from the connection.\n        \"\"\"\n        from socket import fromfd\n\n        s = socket()\n        s.bind(('', 0))\n        server = SendFileDescriptor(s.fileno(), b\"junk\")\n\n        client = ReceiveFileDescriptor()\n        d = client.waitForDescriptor()\n        def checkDescriptor(descriptor):\n            received = fromfd(descriptor, AF_INET, SOCK_STREAM)\n            # Thanks for the free dup, fromfd()\n            close(descriptor)\n\n            # If the sockets have the same local address, they're probably the\n            # same.\n            self.assertEqual(s.getsockname(), received.getsockname())\n\n            # But it would be cheating for them to be identified by the same\n            # file descriptor.  The point was to get a copy, as we might get if\n            # there were two processes involved here.\n            self.assertNotEqual(s.fileno(), received.fileno())\n        d.addCallback(checkDescriptor)\n        d.addErrback(err, \"Sending file descriptor encountered a problem\")\n        d.addBoth(lambda ignored: server.transport.loseConnection())\n\n        runProtocolsWithReactor(self, server, client, self.endpoints)\n    if sendmsgSkip is not None:\n        test_sendFileDescriptor.skip = sendmsgSkip\n\n\n    def test_sendFileDescriptorTriggersPauseProducing(self):\n        \"\"\"\n        If a L{IUNIXTransport.sendFileDescriptor} call fills up the send buffer,\n        any registered producer is paused.\n        \"\"\"\n        class DoesNotRead(ConnectableProtocol):\n            def connectionMade(self):\n                self.transport.pauseProducing()\n\n        class SendsManyFileDescriptors(ConnectableProtocol):\n            paused = False\n\n            def connectionMade(self):\n                self.socket = socket()\n                self.transport.registerProducer(self, True)\n                def sender():\n                    self.transport.sendFileDescriptor(self.socket.fileno())\n                    self.transport.write(b\"x\")\n                self.task = LoopingCall(sender)\n                self.task.clock = self.transport.reactor\n                self.task.start(0).addErrback(err, \"Send loop failure\")\n\n            def stopProducing(self):\n                self._disconnect()\n\n            def resumeProducing(self):\n                self._disconnect()\n\n            def pauseProducing(self):\n                self.paused = True\n                self.transport.unregisterProducer()\n                self._disconnect()\n\n            def _disconnect(self):\n                self.task.stop()\n                self.transport.abortConnection()\n                self.other.transport.abortConnection()\n\n        server = SendsManyFileDescriptors()\n        client = DoesNotRead()\n        server.other = client\n        runProtocolsWithReactor(self, server, client, self.endpoints)\n\n        self.assertTrue(\n            server.paused, \"sendFileDescriptor producer was not paused\")\n    if sendmsgSkip is not None:\n        test_sendFileDescriptorTriggersPauseProducing.skip = sendmsgSkip\n\n\n    def test_fileDescriptorOverrun(self):\n        \"\"\"\n        If L{IUNIXTransport.sendFileDescriptor} is used to queue a greater\n        number of file descriptors than the number of bytes sent using\n        L{ITransport.write}, the connection is closed and the protocol connected\n        to the transport has its C{connectionLost} method called with a failure\n        wrapping L{FileDescriptorOverrun}.\n        \"\"\"\n        cargo = socket()\n        server = SendFileDescriptor(cargo.fileno(), None)\n\n        client = ReceiveFileDescriptor()\n        result = []\n        d = client.waitForDescriptor()\n        d.addBoth(result.append)\n        d.addBoth(lambda ignored: server.transport.loseConnection())\n\n        runProtocolsWithReactor(self, server, client, self.endpoints)\n\n        self.assertIsInstance(result[0], Failure)\n        result[0].trap(ConnectionClosed)\n        self.assertIsInstance(server.reason.value, FileDescriptorOverrun)\n    if sendmsgSkip is not None:\n        test_fileDescriptorOverrun.skip = sendmsgSkip\n\n\n    def _sendmsgMixinFileDescriptorReceivedDriver(self, ancillaryPacker):\n        \"\"\"\n        Drive _SendmsgMixin via sendmsg socket calls to check that\n        L{IFileDescriptorReceiver.fileDescriptorReceived} is called once\n        for each file descriptor received in the ancillary messages.\n\n        @param ancillaryPacker: A callable that will be given a list of\n            two file descriptors and should return a two-tuple where:\n            The first item is an iterable of zero or more (cmsg_level,\n            cmsg_type, cmsg_data) tuples in the same order as the given\n            list for actual sending via sendmsg; the second item is an\n            integer indicating the expected number of FDs to be received.\n        \"\"\"\n        # Strategy:\n        # - Create a UNIX socketpair.\n        # - Associate one end to a FakeReceiver and FakeProtocol.\n        # - Call sendmsg on the other end to send FDs as ancillary data.\n        #   Ancillary data is obtained calling ancillaryPacker with\n        #   the two FDs associated to two temp files (using the socket\n        #   FDs for this fails the device/inode verification tests on\n        #   macOS 10.10, so temp files are used instead).\n        # - Call doRead in the FakeReceiver.\n        # - Verify results on FakeProtocol.\n        #   Using known device/inodes to verify correct order.\n\n        # TODO: replace FakeReceiver test approach with one based in\n        # IReactorSocket.adoptStreamConnection once AF_UNIX support is\n        # implemented; see https://twistedmatrix.com/trac/ticket/5573.\n\n        from socket import socketpair\n        from twisted.internet.unix import _SendmsgMixin\n        from twisted.python.sendmsg import sendmsg\n\n        def deviceInodeTuple(fd):\n            fs = fstat(fd)\n            return (fs.st_dev, fs.st_ino)\n\n        @implementer(IFileDescriptorReceiver)\n        class FakeProtocol(ConnectableProtocol):\n            def __init__(self):\n                self.fds = []\n                self.deviceInodesReceived = []\n            def fileDescriptorReceived(self, fd):\n                self.fds.append(fd)\n                self.deviceInodesReceived.append(deviceInodeTuple(fd))\n                close(fd)\n\n        class FakeReceiver(_SendmsgMixin):\n            bufferSize = 1024\n            def __init__(self, skt, proto):\n                self.socket = skt\n                self.protocol = proto\n            def _dataReceived(self, data):\n                pass\n            def getHost(self):\n                pass\n            def getPeer(self):\n                pass\n            def _getLogPrefix(self, o):\n                pass\n\n        sendSocket, recvSocket = socketpair(AF_UNIX, SOCK_STREAM)\n        self.addCleanup(sendSocket.close)\n        self.addCleanup(recvSocket.close)\n\n        proto = FakeProtocol()\n        receiver = FakeReceiver(recvSocket, proto)\n\n        # Temp files give us two FDs to send/receive/verify.\n        fileOneFD, fileOneName = mkstemp()\n        fileTwoFD, fileTwoName = mkstemp()\n        self.addCleanup(unlink, fileOneName)\n        self.addCleanup(unlink, fileTwoName)\n\n        dataToSend = b'some data needs to be sent'\n        fdsToSend = [fileOneFD, fileTwoFD]\n        ancillary, expectedCount = ancillaryPacker(fdsToSend)\n        sendmsg(sendSocket, dataToSend, ancillary)\n\n        receiver.doRead()\n\n        # Verify that fileDescriptorReceived was called twice.\n        self.assertEqual(len(proto.fds), expectedCount)\n\n        # Verify that received FDs are different from the sent ones.\n        self.assertFalse(set(fdsToSend).intersection(set(proto.fds)))\n\n        # Verify that FDs were received in the same order, if any.\n        if proto.fds:\n            deviceInodesSent = [deviceInodeTuple(fd) for fd in fdsToSend]\n            self.assertEqual(deviceInodesSent, proto.deviceInodesReceived)\n\n\n    def test_multiFileDescriptorReceivedPerRecvmsgOneCMSG(self):\n        \"\"\"\n        _SendmsgMixin handles multiple file descriptors per recvmsg, calling\n        L{IFileDescriptorReceiver.fileDescriptorReceived} once per received\n        file descriptor. Scenario: single CMSG with two FDs.\n        \"\"\"\n        from twisted.python.sendmsg import SCM_RIGHTS\n\n        def ancillaryPacker(fdsToSend):\n            ancillary = [(SOL_SOCKET, SCM_RIGHTS, pack('ii', *fdsToSend))]\n            expectedCount = 2\n            return ancillary, expectedCount\n\n        self._sendmsgMixinFileDescriptorReceivedDriver(ancillaryPacker)\n    if sendmsgSkip is not None:\n        test_multiFileDescriptorReceivedPerRecvmsgOneCMSG.skip = sendmsgSkip\n\n\n    def test_multiFileDescriptorReceivedPerRecvmsgTwoCMSGs(self):\n        \"\"\"\n        _SendmsgMixin handles multiple file descriptors per recvmsg, calling\n        L{IFileDescriptorReceiver.fileDescriptorReceived} once per received\n        file descriptor. Scenario: two CMSGs with one FD each.\n        \"\"\"\n        from twisted.python.sendmsg import SCM_RIGHTS\n\n        def ancillaryPacker(fdsToSend):\n            ancillary = [\n                (SOL_SOCKET, SCM_RIGHTS, pack('i', fd))\n                for fd in fdsToSend\n            ]\n            expectedCount = 2\n            return ancillary, expectedCount\n\n        self._sendmsgMixinFileDescriptorReceivedDriver(ancillaryPacker)\n    if platform.isMacOSX():\n        test_multiFileDescriptorReceivedPerRecvmsgTwoCMSGs.skip = (\n            \"Multi control message ancillary sendmsg not supported on Mac.\")\n    elif sendmsgSkip is not None:\n        test_multiFileDescriptorReceivedPerRecvmsgTwoCMSGs.skip = sendmsgSkip\n\n\n    def test_multiFileDescriptorReceivedPerRecvmsgBadCMSG(self):\n        \"\"\"\n        _SendmsgMixin handles multiple file descriptors per recvmsg, calling\n        L{IFileDescriptorReceiver.fileDescriptorReceived} once per received\n        file descriptor. Scenario: unsupported CMSGs.\n        \"\"\"\n        # Given that we can't just send random/invalid ancillary data via the\n        # packer for it to be sent via sendmsg -- the kernel would not accept\n        # it -- we'll temporarily replace recvmsg with a fake one that produces\n        # a non-supported ancillary message level/type. This being said, from\n        # the perspective of the ancillaryPacker, all that is required is to\n        # let the test driver know that 0 file descriptors are expected.\n        from twisted.python import sendmsg\n\n        def ancillaryPacker(fdsToSend):\n            ancillary = []\n            expectedCount = 0\n            return ancillary, expectedCount\n\n        def fakeRecvmsgUnsupportedAncillary(skt, *args, **kwargs):\n            data = b'some data'\n            ancillary = [(None, None, b'')]\n            flags = 0\n            return sendmsg.RecievedMessage(data, ancillary, flags)\n\n        events = []\n        addObserver(events.append)\n        self.addCleanup(removeObserver, events.append)\n\n        self.patch(sendmsg, \"recvmsg\", fakeRecvmsgUnsupportedAncillary)\n        self._sendmsgMixinFileDescriptorReceivedDriver(ancillaryPacker)\n\n        # Verify the expected message was logged.\n        expectedMessage = 'received unsupported ancillary data'\n        found = any(expectedMessage in e['format'] for e in events)\n        self.assertTrue(found, 'Expected message not found in logged events')\n    if sendmsgSkip is not None:\n        test_multiFileDescriptorReceivedPerRecvmsgBadCMSG.skip = sendmsgSkip\n\n\n    def test_avoidLeakingFileDescriptors(self):\n        \"\"\"\n        If associated with a protocol which does not provide\n        L{IFileDescriptorReceiver}, file descriptors received by the\n        L{IUNIXTransport} implementation are closed and a warning is emitted.\n        \"\"\"\n        # To verify this, establish a connection.  Send one end of the\n        # connection over the IUNIXTransport implementation.  After the copy\n        # should no longer exist, close the original.  If the opposite end of\n        # the connection decides the connection is closed, the copy does not\n        # exist.\n        from socket import socketpair\n        probeClient, probeServer = socketpair()\n\n        events = []\n        addObserver(events.append)\n        self.addCleanup(removeObserver, events.append)\n\n        class RecordEndpointAddresses(SendFileDescriptor):\n            def connectionMade(self):\n                self.hostAddress = self.transport.getHost()\n                self.peerAddress = self.transport.getPeer()\n                SendFileDescriptor.connectionMade(self)\n\n        server = RecordEndpointAddresses(probeClient.fileno(), b\"junk\")\n        client = ConnectableProtocol()\n\n        runProtocolsWithReactor(self, server, client, self.endpoints)\n\n        # Get rid of the original reference to the socket.\n        probeClient.close()\n\n        # A non-blocking recv will return \"\" if the connection is closed, as\n        # desired.  If the connection has not been closed, because the\n        # duplicate file descriptor is still open, it will fail with EAGAIN\n        # instead.\n        probeServer.setblocking(False)\n        self.assertEqual(b\"\", probeServer.recv(1024))\n\n        # This is a surprising circumstance, so it should be logged.\n        format = (\n            \"%(protocolName)s (on %(hostAddress)r) does not \"\n            \"provide IFileDescriptorReceiver; closing file \"\n            \"descriptor received (from %(peerAddress)r).\")\n        clsName = \"ConnectableProtocol\"\n\n        # Reverse host and peer, since the log event is from the client\n        # perspective.\n        expectedEvent = dict(hostAddress=server.peerAddress,\n                             peerAddress=server.hostAddress,\n                             protocolName=clsName,\n                             format=format)\n\n        for logEvent in events:\n            for k, v in iteritems(expectedEvent):\n                if v != logEvent.get(k):\n                    break\n            else:\n                # No mismatches were found, stop looking at events\n                break\n        else:\n            # No fully matching events were found, fail the test.\n            self.fail(\n                \"Expected event (%s) not found in logged events (%s)\" % (\n                    expectedEvent, pformat(events,)))\n    if sendmsgSkip is not None:\n        test_avoidLeakingFileDescriptors.skip = sendmsgSkip\n\n\n    def test_descriptorDeliveredBeforeBytes(self):\n        \"\"\"\n        L{IUNIXTransport.sendFileDescriptor} sends file descriptors before\n        L{ITransport.write} sends normal bytes.\n        \"\"\"\n        @implementer(IFileDescriptorReceiver)\n        class RecordEvents(ConnectableProtocol):\n\n            def connectionMade(self):\n                ConnectableProtocol.connectionMade(self)\n                self.events = []\n\n            def fileDescriptorReceived(innerSelf, descriptor):\n                self.addCleanup(close, descriptor)\n                innerSelf.events.append(type(descriptor))\n\n            def dataReceived(self, data):\n                self.events.extend(data)\n\n        cargo = socket()\n        server = SendFileDescriptor(cargo.fileno(), b\"junk\")\n        client = RecordEvents()\n\n        runProtocolsWithReactor(self, server, client, self.endpoints)\n\n        self.assertEqual(int, client.events[0])\n        if _PY3:\n            self.assertEqual(b\"junk\", bytes(client.events[1:]))\n        else:\n            self.assertEqual(b\"junk\", b\"\".join(client.events[1:]))\n    if sendmsgSkip is not None:\n        test_descriptorDeliveredBeforeBytes.skip = sendmsgSkip\n\n\n\nclass UNIXDatagramTestsBuilder(UNIXFamilyMixin, ReactorBuilder):\n    \"\"\"\n    Builder defining tests relating to L{IReactorUNIXDatagram}.\n    \"\"\"\n    requiredInterfaces = (interfaces.IReactorUNIXDatagram,)\n\n    # There's no corresponding test_connectMode because the mode parameter to\n    # connectUNIXDatagram has been completely ignored since that API was first\n    # introduced.\n    def test_listenMode(self):\n        \"\"\"\n        The UNIX socket created by L{IReactorUNIXDatagram.listenUNIXDatagram}\n        is created with the mode specified.\n        \"\"\"\n        self._modeTest('listenUNIXDatagram', self.mktemp(), DatagramProtocol())\n\n\n    def test_listenOnLinuxAbstractNamespace(self):\n        \"\"\"\n        On Linux, a UNIX socket path may begin with C{'\\0'} to indicate a socket\n        in the abstract namespace.  L{IReactorUNIX.listenUNIXDatagram} accepts\n        such a path.\n        \"\"\"\n        path = _abstractPath(self)\n        reactor = self.buildReactor()\n        port = reactor.listenUNIXDatagram('\\0' + path, DatagramProtocol())\n        self.assertEqual(port.getHost(), UNIXAddress('\\0' + path))\n    if not platform.isLinux():\n        test_listenOnLinuxAbstractNamespace.skip = (\n            'Abstract namespace UNIX sockets only supported on Linux.')\n\n\n\nclass SocketUNIXMixin(object):\n    \"\"\"\n    Mixin which uses L{IReactorSocket.adoptStreamPort} to hand out listening\n    UNIX ports.\n    \"\"\"\n    requiredInterfaces = (IReactorUNIX, IReactorSocket,)\n\n    def getListeningPort(self, reactor, factory):\n        \"\"\"\n        Get a UNIX port from a reactor, wrapping an already-initialized file\n        descriptor.\n        \"\"\"\n        portSock = socket(AF_UNIX)\n        # self.mktemp() often returns a path which is too long to be used.\n        path = mktemp(suffix='.sock', dir='.')\n        portSock.bind(path)\n        portSock.listen(3)\n        portSock.setblocking(False)\n        try:\n            return reactor.adoptStreamPort(\n                portSock.fileno(), portSock.family, factory)\n        finally:\n            portSock.close()\n\n\n    def connectToListener(self, reactor, address, factory):\n        \"\"\"\n        Connect to a listening UNIX socket.\n\n        @param reactor: The reactor under test.\n        @type reactor: L{IReactorUNIX}\n\n        @param address: The listening's address.\n        @type address: L{UNIXAddress}\n\n        @param factory: The client factory.\n        @type factory: L{ClientFactory}\n\n        @return: The connector\n        \"\"\"\n        return reactor.connectUNIX(address.name, factory)\n\n\n\nclass ListenUNIXMixin(object):\n    \"\"\"\n    Mixin which uses L{IReactorTCP.listenUNIX} to hand out listening UNIX\n    ports.\n    \"\"\"\n    def getListeningPort(self, reactor, factory):\n        \"\"\"\n        Get a UNIX port from a reactor\n        \"\"\"\n        # self.mktemp() often returns a path which is too long to be used.\n        path = mktemp(suffix='.sock', dir='.')\n        return reactor.listenUNIX(path, factory)\n\n\n    def connectToListener(self, reactor, address, factory):\n        \"\"\"\n        Connect to a listening UNIX socket.\n\n        @param reactor: The reactor under test.\n        @type reactor: L{IReactorUNIX}\n\n        @param address: The listening's address.\n        @type address: L{UNIXAddress}\n\n        @param factory: The client factory.\n        @type factory: L{ClientFactory}\n\n        @return: The connector\n        \"\"\"\n        return reactor.connectUNIX(address.name, factory)\n\n\n\nclass UNIXPortTestsMixin(object):\n    requiredInterfaces = (IReactorUNIX,)\n\n    def getExpectedStartListeningLogMessage(self, port, factory):\n        \"\"\"\n        Get the message expected to be logged when a UNIX port starts listening.\n        \"\"\"\n        return \"%s starting on %r\" % (factory,\n                                      nativeString(port.getHost().name))\n\n\n    def getExpectedConnectionLostLogMsg(self, port):\n        \"\"\"\n        Get the expected connection lost message for a UNIX port\n        \"\"\"\n        return \"(UNIX Port %s Closed)\" % (nativeString(port.getHost().name),)\n\n\n\nclass UNIXPortTestsBuilder(ListenUNIXMixin, UNIXPortTestsMixin,\n                           ReactorBuilder, ObjectModelIntegrationMixin,\n                           StreamTransportTestsMixin):\n    \"\"\"\n    Tests for L{IReactorUNIX.listenUnix}\n    \"\"\"\n\n\nclass UNIXFDPortTestsBuilder(SocketUNIXMixin, UNIXPortTestsMixin,\n                             ReactorBuilder, ObjectModelIntegrationMixin,\n                             StreamTransportTestsMixin):\n    \"\"\"\n    Tests for L{IReactorUNIX.adoptStreamPort}\n    \"\"\"\n\n\nclass UNIXAdoptStreamConnectionTestsBuilder(WriteSequenceTestsMixin, ReactorBuilder):\n    requiredInterfaces = (IReactorFDSet, IReactorSocket, IReactorUNIX,)\n\n    def test_buildProtocolReturnsNone(self):\n        \"\"\"\n        {IReactorSocket.adoptStreamConnection} returns None if the given\n        factory's buildProtocol returns None.\n        \"\"\"\n\n        # Build reactor before anything else: allow self.buildReactor()\n        # to skip the test if any of the self.requiredInterfaces isn't\n        # provided by the reactor (example: Windows), preventing later\n        # failures unrelated to the test itself.\n        reactor = self.buildReactor()\n\n        from socket import socketpair\n\n        class NoneFactory(ServerFactory):\n            def buildProtocol(self, address):\n                return None\n\n        s1, s2 = socketpair(AF_UNIX, SOCK_STREAM)\n        s1.setblocking(False)\n        self.addCleanup(s1.close)\n        self.addCleanup(s2.close)\n\n        s1FD = s1.fileno()\n        factory = NoneFactory()\n        result = reactor.adoptStreamConnection(s1FD, AF_UNIX, factory)\n        self.assertIsNone(result)\n\n\n    def test_ServerAddressUNIX(self):\n        \"\"\"\n        Helper method to test UNIX server addresses.\n        \"\"\"\n\n        def connected(protocols):\n            client, server, port = protocols\n            try:\n                portPath = _coerceToFilesystemEncoding('', port.getHost().name)\n                self.assertEqual(\n                    \"<AccumulatingProtocol #%s on %s>\" %\n                        (server.transport.sessionno, portPath),\n                    str(server.transport))\n\n                self.assertEqual(\n                    \"AccumulatingProtocol,%s,%s\" %\n                        (server.transport.sessionno, portPath),\n                    server.transport.logstr)\n\n                peerAddress = server.factory.peerAddresses[0]\n                self.assertIsInstance(peerAddress, UNIXAddress)\n            finally:\n                # Be certain to drop the connection so the test completes.\n                server.transport.loseConnection()\n\n        reactor = self.buildReactor()\n        d = self.getConnectedClientAndServer(reactor, interface=None, addressFamily=None)\n        d.addCallback(connected)\n        self.runReactor(reactor)\n\n\n    def getConnectedClientAndServer(self, reactor, interface, addressFamily):\n        \"\"\"\n        Return a L{Deferred} firing with a L{MyClientFactory} and\n        L{MyServerFactory} connected pair, and the listening C{Port}. The\n        particularity is that the server protocol has been obtained after doing\n        a C{adoptStreamConnection} against the original server connection.\n        \"\"\"\n        firstServer = MyServerFactory()\n        firstServer.protocolConnectionMade = Deferred()\n\n        server = MyServerFactory()\n        server.protocolConnectionMade = Deferred()\n        server.protocolConnectionLost = Deferred()\n\n        client = MyClientFactory()\n        client.protocolConnectionMade = Deferred()\n        client.protocolConnectionLost = Deferred()\n\n        # self.mktemp() often returns a path which is too long to be used.\n        path = mktemp(suffix='.sock', dir='.')\n        port = reactor.listenUNIX(path, firstServer)\n\n        def firstServerConnected(proto):\n            reactor.removeReader(proto.transport)\n            reactor.removeWriter(proto.transport)\n            reactor.adoptStreamConnection(\n                proto.transport.fileno(), AF_UNIX, server)\n\n        firstServer.protocolConnectionMade.addCallback(firstServerConnected)\n\n        lostDeferred = gatherResults([client.protocolConnectionLost,\n                                      server.protocolConnectionLost])\n        def stop(result):\n            if reactor.running:\n                reactor.stop()\n            return result\n\n        lostDeferred.addBoth(stop)\n\n        deferred = Deferred()\n        deferred.addErrback(stop)\n\n        startDeferred = gatherResults([client.protocolConnectionMade,\n                                       server.protocolConnectionMade])\n        def start(protocols):\n            client, server = protocols\n            deferred.callback((client, server, port))\n\n        startDeferred.addCallback(start)\n\n        reactor.connectUNIX(port.getHost().name, client)\n        return deferred\n\n\nglobals().update(UNIXTestsBuilder.makeTestCaseClasses())\nglobals().update(UNIXDatagramTestsBuilder.makeTestCaseClasses())\nglobals().update(UNIXPortTestsBuilder.makeTestCaseClasses())\nglobals().update(UNIXFDPortTestsBuilder.makeTestCaseClasses())\nglobals().update(UNIXAdoptStreamConnectionTestsBuilder.makeTestCaseClasses())\n\n\n\nclass UnixClientTestsBuilder(ReactorBuilder, StreamClientTestsMixin):\n    \"\"\"\n    Define tests for L{IReactorUNIX.connectUNIX}.\n    \"\"\"\n    requiredInterfaces = (IReactorUNIX,)\n\n    _path = None\n\n    @property\n    def path(self):\n        \"\"\"\n        Return a path usable by C{connectUNIX} and C{listenUNIX}.\n\n        @return: A path instance, built with C{_abstractPath}.\n        \"\"\"\n        if self._path is None:\n            self._path = _abstractPath(self)\n        return self._path\n\n\n    def listen(self, reactor, factory):\n        \"\"\"\n        Start an UNIX server with the given C{factory}.\n\n        @param reactor: The reactor to create the UNIX port in.\n\n        @param factory: The server factory.\n\n        @return: A UNIX port instance.\n        \"\"\"\n        return reactor.listenUNIX(self.path, factory)\n\n\n    def connect(self, reactor, factory):\n        \"\"\"\n        Start an UNIX client with the given C{factory}.\n\n        @param reactor: The reactor to create the connection in.\n\n        @param factory: The client factory.\n\n        @return: A UNIX connector instance.\n        \"\"\"\n        return reactor.connectUNIX(self.path, factory)\n\n\n\nglobals().update(UnixClientTestsBuilder.makeTestCaseClasses())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_win32events.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for implementations of L{IReactorWin32Events}.\n\"\"\"\n\ntry:\n    import win32event\nexcept ImportError:\n    win32event = None\n\nfrom zope.interface.verify import verifyObject\n\nfrom twisted.python.failure import Failure\nfrom twisted.python.threadable import isInIOThread\nfrom twisted.internet.interfaces import IReactorWin32Events\nfrom twisted.internet.defer import Deferred\nfrom twisted.internet.test.reactormixins import ReactorBuilder\nfrom twisted.python.threadable import getThreadID\n\n\nclass Listener(object):\n    \"\"\"\n    L{Listener} is an object that can be added to a L{IReactorWin32Events}\n    reactor to receive callback notification when a Windows event is set.  It\n    records what thread its callback is invoked in and fires a Deferred.\n\n    @ivar success: A flag which is set to C{True} when the event callback is\n        called.\n\n    @ivar logThreadID: The id of the thread in which the C{logPrefix} method is\n        called.\n\n    @ivar eventThreadID: The id of the thread in which the event callback is\n        called.\n\n    @ivar connLostThreadID: The id of the thread in which the C{connectionLost}\n        method is called.\n\n    @ivar _finished: The L{Deferred} which will be fired when the event callback\n        is called.\n    \"\"\"\n    success = False\n    logThreadID = eventThreadID = connLostThreadID = None\n\n    def __init__(self, finished):\n        self._finished = finished\n\n\n    def logPrefix(self):\n        self.logThreadID = getThreadID()\n        return 'Listener'\n\n\n    def occurred(self):\n        self.success = True\n        self.eventThreadID = getThreadID()\n        self._finished.callback(None)\n\n\n    def brokenOccurred(self):\n        raise RuntimeError(\"Some problem\")\n\n\n    def returnValueOccurred(self):\n        return EnvironmentError(\"Entirely different problem\")\n\n\n    def connectionLost(self, reason):\n        self.connLostThreadID = getThreadID()\n        self._finished.errback(reason)\n\n\n\nclass Win32EventsTestsBuilder(ReactorBuilder):\n    \"\"\"\n    Builder defining tests relating to L{IReactorWin32Events}.\n    \"\"\"\n    requiredInterfaces = [IReactorWin32Events]\n\n    def test_interface(self):\n        \"\"\"\n        An instance of the reactor has all of the methods defined on\n        L{IReactorWin32Events}.\n        \"\"\"\n        reactor = self.buildReactor()\n        verifyObject(IReactorWin32Events, reactor)\n\n\n    def test_addEvent(self):\n        \"\"\"\n        When an event which has been added to the reactor is set, the action\n        associated with the event is invoked in the reactor thread.\n        \"\"\"\n        reactorThreadID = getThreadID()\n        reactor = self.buildReactor()\n        event = win32event.CreateEvent(None, False, False, None)\n        finished = Deferred()\n        finished.addCallback(lambda ignored: reactor.stop())\n        listener = Listener(finished)\n        reactor.addEvent(event, listener, 'occurred')\n        reactor.callWhenRunning(win32event.SetEvent, event)\n        self.runReactor(reactor)\n        self.assertTrue(listener.success)\n        self.assertEqual(reactorThreadID, listener.logThreadID)\n        self.assertEqual(reactorThreadID, listener.eventThreadID)\n\n\n    def test_ioThreadDoesNotChange(self):\n        \"\"\"\n        Using L{IReactorWin32Events.addEvent} does not change which thread is\n        reported as the I/O thread.\n        \"\"\"\n        results = []\n        def check(ignored):\n            results.append(isInIOThread())\n            reactor.stop()\n        reactor = self.buildReactor()\n        event = win32event.CreateEvent(None, False, False, None)\n        finished = Deferred()\n        listener = Listener(finished)\n        finished.addCallback(check)\n        reactor.addEvent(event, listener, 'occurred')\n        reactor.callWhenRunning(win32event.SetEvent, event)\n        self.runReactor(reactor)\n        self.assertTrue(listener.success)\n        self.assertEqual([True], results)\n\n\n    def test_disconnectedOnError(self):\n        \"\"\"\n        If the event handler raises an exception, the event is removed from the\n        reactor and the handler's C{connectionLost} method is called in the I/O\n        thread and the exception is logged.\n        \"\"\"\n        reactorThreadID = getThreadID()\n        reactor = self.buildReactor()\n        event = win32event.CreateEvent(None, False, False, None)\n\n        result = []\n        finished = Deferred()\n        finished.addBoth(result.append)\n        finished.addBoth(lambda ignored: reactor.stop())\n\n        listener = Listener(finished)\n        reactor.addEvent(event, listener, 'brokenOccurred')\n        reactor.callWhenRunning(win32event.SetEvent, event)\n        self.runReactor(reactor)\n\n        self.assertIsInstance(result[0], Failure)\n        result[0].trap(RuntimeError)\n\n        self.assertEqual(reactorThreadID, listener.connLostThreadID)\n        self.assertEqual(1, len(self.flushLoggedErrors(RuntimeError)))\n\n\n    def test_disconnectOnReturnValue(self):\n        \"\"\"\n        If the event handler returns a value, the event is removed from the\n        reactor and the handler's C{connectionLost} method is called in the I/O\n        thread.\n        \"\"\"\n        reactorThreadID = getThreadID()\n        reactor = self.buildReactor()\n        event = win32event.CreateEvent(None, False, False, None)\n\n        result = []\n        finished = Deferred()\n        finished.addBoth(result.append)\n        finished.addBoth(lambda ignored: reactor.stop())\n\n        listener = Listener(finished)\n        reactor.addEvent(event, listener, 'returnValueOccurred')\n        reactor.callWhenRunning(win32event.SetEvent, event)\n        self.runReactor(reactor)\n\n        self.assertIsInstance(result[0], Failure)\n        result[0].trap(EnvironmentError)\n\n        self.assertEqual(reactorThreadID, listener.connLostThreadID)\n\n\n    def test_notDisconnectedOnShutdown(self):\n        \"\"\"\n        Event handlers added with L{IReactorWin32Events.addEvent} do not have\n        C{connectionLost} called on them if they are still active when the\n        reactor shuts down.\n        \"\"\"\n        reactor = self.buildReactor()\n        event = win32event.CreateEvent(None, False, False, None)\n        finished = Deferred()\n        listener = Listener(finished)\n        reactor.addEvent(event, listener, 'occurred')\n        reactor.callWhenRunning(reactor.stop)\n        self.runReactor(reactor)\n        self.assertIsNone(listener.connLostThreadID)\n\nglobals().update(Win32EventsTestsBuilder.makeTestCaseClasses())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/test/test_win32serialport.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.internet.serialport}.\n\"\"\"\n\nimport os\nimport shutil\nimport tempfile\n\nfrom twisted.trial import unittest\nfrom twisted.internet.protocol import Protocol\nfrom twisted.python.failure import Failure\nfrom twisted.python.runtime import platform\nfrom twisted.internet.test.test_serialport import DoNothing\n\ntry:\n    from twisted.internet import serialport\n    import serial\nexcept ImportError:\n    serialport = None\n    serial = None\n\n\nif serialport is not None:\n    class RegularFileSerial(serial.Serial):\n        def __init__(self, *args, **kwargs):\n            super(RegularFileSerial, self).__init__(*args, **kwargs)\n            self.captured_args = args\n            self.captured_kwargs = kwargs\n\n        def _reconfigurePort(self):\n            pass\n\n        def _reconfigure_port(self):\n            pass\n\n\n    class RegularFileSerialPort(serialport.SerialPort):\n        _serialFactory = RegularFileSerial\n\n        def __init__(self, *args, **kwargs):\n            cbInQue = kwargs.get('cbInQue')\n\n            if 'cbInQue' in kwargs:\n                del kwargs['cbInQue']\n\n            self.comstat = serial.win32.COMSTAT\n            self.comstat.cbInQue = cbInQue\n\n            super(RegularFileSerialPort, self).__init__(*args, **kwargs)\n\n        def _clearCommError(self):\n            return True, self.comstat\n\n\nclass CollectReceivedProtocol(Protocol):\n    def __init__(self):\n        self.received_data = []\n\n    def dataReceived(self, data):\n        self.received_data.append(data)\n\n\nclass Win32SerialPortTests(unittest.TestCase):\n    \"\"\"\n    Minimal testing for Twisted's Win32 serial port support.\n    \"\"\"\n\n    if not platform.isWindows():\n        skip = \"This test must run on Windows.\"\n\n    elif not serialport:\n        skip = \"Windows serial port support is not available.\"\n\n    def setUp(self):\n        # Re-usable protocol and reactor\n        self.protocol = Protocol()\n        self.reactor = DoNothing()\n\n        self.directory = tempfile.mkdtemp()\n        self.path = os.path.join(self.directory, 'fake_serial')\n\n        data = b'1234'\n        with open(self.path, 'wb') as f:\n            f.write(data)\n\n    def tearDown(self):\n        shutil.rmtree(self.directory)\n\n    def test_serialPortDefaultArgs(self):\n        \"\"\"\n        Test correct positional and keyword arguments have been\n        passed to the C{serial.Serial} object.\n        \"\"\"\n        port = RegularFileSerialPort(self.protocol, self.path, self.reactor)\n        # Validate args\n        self.assertEqual((self.path,), port._serial.captured_args)\n        # Validate kwargs\n        kwargs = port._serial.captured_kwargs\n        self.assertEqual(9600,                kwargs[\"baudrate\"])\n        self.assertEqual(serial.EIGHTBITS,    kwargs[\"bytesize\"])\n        self.assertEqual(serial.PARITY_NONE,  kwargs[\"parity\"])\n        self.assertEqual(serial.STOPBITS_ONE, kwargs[\"stopbits\"])\n        self.assertEqual(0,                   kwargs[\"xonxoff\"])\n        self.assertEqual(0,                   kwargs[\"rtscts\"])\n        self.assertEqual(None,                kwargs[\"timeout\"])\n        port.connectionLost(Failure(Exception(\"Cleanup\")))\n\n    def test_serialPortInitiallyConnected(self):\n        \"\"\"\n        Test the port is connected at initialization time, and\n        C{Protocol.makeConnection} has been called on the desired protocol.\n        \"\"\"\n        self.assertEqual(0,    self.protocol.connected)\n\n        port = RegularFileSerialPort(self.protocol, self.path, self.reactor)\n        self.assertEqual(1, port.connected)\n        self.assertEqual(1, self.protocol.connected)\n        self.assertEqual(port, self.protocol.transport)\n        port.connectionLost(Failure(Exception(\"Cleanup\")))\n\n    def common_exerciseHandleAccess(self, cbInQue):\n        port = RegularFileSerialPort(\n            protocol=self.protocol,\n            deviceNameOrPortNumber=self.path,\n            reactor=self.reactor,\n            cbInQue=cbInQue,\n        )\n        port.serialReadEvent()\n        port.write(b'')\n        port.write(b'abcd')\n        port.write(b'ABCD')\n        port.serialWriteEvent()\n        port.serialWriteEvent()\n        port.connectionLost(Failure(Exception(\"Cleanup\")))\n\n        # No assertion since the point is simply to make sure that in all cases\n        # the port handle resolves instead of raising an exception.\n\n    def test_exerciseHandleAccess_1(self):\n        self.common_exerciseHandleAccess(cbInQue=False)\n\n    def test_exerciseHandleAccess_2(self):\n        self.common_exerciseHandleAccess(cbInQue=True)\n\n    def common_serialPortReturnsBytes(self, cbInQue):\n        protocol = CollectReceivedProtocol()\n\n        port = RegularFileSerialPort(\n            protocol=protocol,\n            deviceNameOrPortNumber=self.path,\n            reactor=self.reactor,\n            cbInQue=cbInQue,\n        )\n        port.serialReadEvent()\n        self.assertTrue(all(\n            isinstance(d, bytes) for d in protocol.received_data\n        ))\n        port.connectionLost(Failure(Exception(\"Cleanup\")))\n\n    def test_serialPortReturnsBytes_1(self):\n        self.common_serialPortReturnsBytes(cbInQue=False)\n\n    def test_serialPortReturnsBytes_2(self):\n        self.common_serialPortReturnsBytes(cbInQue=True)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/testing.py",
    "content": "# -*- test-case-name: twisted.internet.test.test_testing -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAssorted functionality which is commonly useful when writing unit tests.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom socket import AF_INET, AF_INET6\nfrom io import BytesIO\n\nfrom zope.interface import implementer, implementedBy\nfrom zope.interface.verify import verifyClass\n\nfrom twisted.python import failure\nfrom twisted.python.compat import unicode, intToBytes, Sequence\nfrom twisted.internet.defer import Deferred\nfrom twisted.internet.interfaces import (\n    ITransport, IConsumer, IPushProducer, IConnector,\n    IReactorCore, IReactorTCP, IReactorSSL, IReactorUNIX, IReactorSocket,\n    IListeningPort, IReactorFDSet,\n)\nfrom twisted.internet.abstract import isIPv6Address\nfrom twisted.internet.error import UnsupportedAddressFamily\nfrom twisted.protocols import basic\nfrom twisted.internet import protocol, error, address, task\n\nfrom twisted.internet.task import Clock\nfrom twisted.internet.address import IPv4Address, UNIXAddress, IPv6Address\nfrom twisted.logger import ILogObserver\n\n\n\n__all__ = [\n    'AccumulatingProtocol',\n    'LineSendingProtocol',\n    'FakeDatagramTransport',\n    'StringTransport',\n    'StringTransportWithDisconnection',\n    'StringIOWithoutClosing',\n    '_FakeConnector',\n    '_FakePort',\n    'MemoryReactor',\n    'MemoryReactorClock',\n    'RaisingMemoryReactor',\n    'NonStreamingProducer',\n    'waitUntilAllDisconnected',\n    'EventLoggingObserver'\n]\n\n\n\nclass AccumulatingProtocol(protocol.Protocol):\n    \"\"\"\n    L{AccumulatingProtocol} is an L{IProtocol} implementation which collects\n    the data delivered to it and can fire a Deferred when it is connected or\n    disconnected.\n\n    @ivar made: A flag indicating whether C{connectionMade} has been called.\n    @ivar data: Bytes giving all the data passed to C{dataReceived}.\n    @ivar closed: A flag indicated whether C{connectionLost} has been called.\n    @ivar closedReason: The value of the I{reason} parameter passed to\n        C{connectionLost}.\n    @ivar closedDeferred: If set to a L{Deferred}, this will be fired when\n        C{connectionLost} is called.\n    \"\"\"\n    made = closed = 0\n    closedReason = None\n\n    closedDeferred = None\n\n    data = b\"\"\n\n    factory = None\n\n    def connectionMade(self):\n        self.made = 1\n        if (self.factory is not None and self.factory.protocolConnectionMade\n                is not None):\n            d = self.factory.protocolConnectionMade\n            self.factory.protocolConnectionMade = None\n            d.callback(self)\n\n    def dataReceived(self, data):\n        self.data += data\n\n    def connectionLost(self, reason):\n        self.closed = 1\n        self.closedReason = reason\n        if self.closedDeferred is not None:\n            d, self.closedDeferred = self.closedDeferred, None\n            d.callback(None)\n\n\n\nclass LineSendingProtocol(basic.LineReceiver):\n    lostConn = False\n\n    def __init__(self, lines, start=True):\n        self.lines = lines[:]\n        self.response = []\n        self.start = start\n\n    def connectionMade(self):\n        if self.start:\n            for line in self.lines:\n                self.sendLine(line)\n\n    def lineReceived(self, line):\n        if not self.start:\n            for line in self.lines:\n                self.sendLine(line)\n            self.lines = []\n        self.response.append(line)\n\n    def connectionLost(self, reason):\n        self.lostConn = True\n\n\n\nclass FakeDatagramTransport:\n    noAddr = object()\n\n    def __init__(self):\n        self.written = []\n\n    def write(self, packet, addr=noAddr):\n        self.written.append((packet, addr))\n\n\n\n@implementer(ITransport, IConsumer, IPushProducer)\nclass StringTransport:\n    \"\"\"\n    A transport implementation which buffers data in memory and keeps track of\n    its other state without providing any behavior.\n\n    L{StringTransport} has a number of attributes which are not part of any of\n    the interfaces it claims to implement.  These attributes are provided for\n    testing purposes.  Implementation code should not use any of these\n    attributes; they are not provided by other transports.\n\n    @ivar disconnecting: A C{bool} which is C{False} until L{loseConnection} is\n        called, then C{True}.\n\n    @ivar disconnected: A C{bool} which is C{False} until L{abortConnection} is\n        called, then C{True}.\n\n    @ivar producer: If a producer is currently registered, C{producer} is a\n        reference to it.  Otherwise, L{None}.\n\n    @ivar streaming: If a producer is currently registered, C{streaming} refers\n        to the value of the second parameter passed to C{registerProducer}.\n\n    @ivar hostAddr: L{None} or an object which will be returned as the host\n        address of this transport.  If L{None}, a nasty tuple will be returned\n        instead.\n\n    @ivar peerAddr: L{None} or an object which will be returned as the peer\n        address of this transport.  If L{None}, a nasty tuple will be returned\n        instead.\n\n    @ivar producerState: The state of this L{StringTransport} in its capacity\n        as an L{IPushProducer}.  One of C{'producing'}, C{'paused'}, or\n        C{'stopped'}.\n\n    @ivar io: A L{io.BytesIO} which holds the data which has been written to\n        this transport since the last call to L{clear}.  Use L{value} instead\n        of accessing this directly.\n\n    @ivar _lenient: By default L{StringTransport} enforces that\n        L{resumeProducing} is not called after the connection is lost. This is\n        to ensure that any code that does call L{resumeProducing} after the\n        connection is lost is not blindly expecting L{resumeProducing} to have\n        any impact.\n\n        However, if your test case is calling L{resumeProducing} after\n        connection close on purpose, and you know it won't block expecting\n        further data to show up, this flag may safely be set to L{True}.\n\n        Defaults to L{False}.\n    @type lenient: L{bool}\n    \"\"\"\n\n    disconnecting = False\n    disconnected = False\n\n    producer = None\n    streaming = None\n\n    hostAddr = None\n    peerAddr = None\n\n    producerState = 'producing'\n\n    def __init__(self, hostAddress=None, peerAddress=None, lenient=False):\n        self.clear()\n        if hostAddress is not None:\n            self.hostAddr = hostAddress\n        if peerAddress is not None:\n            self.peerAddr = peerAddress\n        self.connected = True\n        self._lenient = lenient\n\n    def clear(self):\n        \"\"\"\n        Discard all data written to this transport so far.\n\n        This is not a transport method.  It is intended for tests.  Do not use\n        it in implementation code.\n        \"\"\"\n        self.io = BytesIO()\n\n\n    def value(self):\n        \"\"\"\n        Retrieve all data which has been buffered by this transport.\n\n        This is not a transport method.  It is intended for tests.  Do not use\n        it in implementation code.\n\n        @return: A C{bytes} giving all data written to this transport since the\n            last call to L{clear}.\n        @rtype: C{bytes}\n        \"\"\"\n        return self.io.getvalue()\n\n\n    # ITransport\n    def write(self, data):\n        if isinstance(data, unicode):  # no, really, I mean it\n            raise TypeError(\"Data must not be unicode\")\n        self.io.write(data)\n\n\n    def writeSequence(self, data):\n        self.io.write(b''.join(data))\n\n\n    def loseConnection(self):\n        \"\"\"\n        Close the connection. Does nothing besides toggle the C{disconnecting}\n        instance variable to C{True}.\n        \"\"\"\n        self.disconnecting = True\n\n\n    def abortConnection(self):\n        \"\"\"\n        Abort the connection. Same as C{loseConnection}, but also toggles the\n        C{aborted} instance variable to C{True}.\n        \"\"\"\n        self.disconnected = True\n        self.loseConnection()\n\n\n    def getPeer(self):\n        if self.peerAddr is None:\n            return address.IPv4Address('TCP', '192.168.1.1', 54321)\n        return self.peerAddr\n\n\n    def getHost(self):\n        if self.hostAddr is None:\n            return address.IPv4Address('TCP', '10.0.0.1', 12345)\n        return self.hostAddr\n\n\n    # IConsumer\n    def registerProducer(self, producer, streaming):\n        if self.producer is not None:\n            raise RuntimeError(\"Cannot register two producers\")\n        self.producer = producer\n        self.streaming = streaming\n\n\n    def unregisterProducer(self):\n        if self.producer is None:\n            raise RuntimeError(\n                \"Cannot unregister a producer unless one is registered\")\n        self.producer = None\n        self.streaming = None\n\n\n    # IPushProducer\n    def _checkState(self):\n        if self.disconnecting and not self._lenient:\n            raise RuntimeError(\n                \"Cannot resume producing after loseConnection\")\n        if self.producerState == 'stopped':\n            raise RuntimeError(\"Cannot resume a stopped producer\")\n\n\n    def pauseProducing(self):\n        self._checkState()\n        self.producerState = 'paused'\n\n\n    def stopProducing(self):\n        self.producerState = 'stopped'\n\n\n    def resumeProducing(self):\n        self._checkState()\n        self.producerState = 'producing'\n\n\n\nclass StringTransportWithDisconnection(StringTransport):\n    \"\"\"\n    A L{StringTransport} which on disconnection will trigger the connection\n    lost on the attached protocol.\n    \"\"\"\n\n    def loseConnection(self):\n        if self.connected:\n            self.connected = False\n            self.protocol.connectionLost(\n                failure.Failure(error.ConnectionDone(\"Bye.\")))\n\n\n\nclass StringIOWithoutClosing(BytesIO):\n    \"\"\"\n    A BytesIO that can't be closed.\n    \"\"\"\n    def close(self):\n        \"\"\"\n        Do nothing.\n        \"\"\"\n\n\n\n@implementer(IListeningPort)\nclass _FakePort(object):\n    \"\"\"\n    A fake L{IListeningPort} to be used in tests.\n\n    @ivar _hostAddress: The L{IAddress} this L{IListeningPort} is pretending\n        to be listening on.\n    \"\"\"\n\n    def __init__(self, hostAddress):\n        \"\"\"\n        @param hostAddress: An L{IAddress} this L{IListeningPort} should\n            pretend to be listening on.\n        \"\"\"\n        self._hostAddress = hostAddress\n\n\n    def startListening(self):\n        \"\"\"\n        Fake L{IListeningPort.startListening} that doesn't do anything.\n        \"\"\"\n\n\n    def stopListening(self):\n        \"\"\"\n        Fake L{IListeningPort.stopListening} that doesn't do anything.\n        \"\"\"\n\n\n    def getHost(self):\n        \"\"\"\n        Fake L{IListeningPort.getHost} that returns our L{IAddress}.\n        \"\"\"\n        return self._hostAddress\n\n\n\n@implementer(IConnector)\nclass _FakeConnector(object):\n    \"\"\"\n    A fake L{IConnector} that allows us to inspect if it has been told to stop\n    connecting.\n\n    @ivar stoppedConnecting: has this connector's\n        L{_FakeConnector.stopConnecting} method been invoked yet?\n\n    @ivar _address: An L{IAddress} provider that represents our destination.\n    \"\"\"\n    _disconnected = False\n    stoppedConnecting = False\n\n    def __init__(self, address):\n        \"\"\"\n        @param address: An L{IAddress} provider that represents this\n            connector's destination.\n        \"\"\"\n        self._address = address\n\n\n    def stopConnecting(self):\n        \"\"\"\n        Implement L{IConnector.stopConnecting} and set\n        L{_FakeConnector.stoppedConnecting} to C{True}\n        \"\"\"\n        self.stoppedConnecting = True\n\n\n    def disconnect(self):\n        \"\"\"\n        Implement L{IConnector.disconnect} as a no-op.\n        \"\"\"\n        self._disconnected = True\n\n\n    def connect(self):\n        \"\"\"\n        Implement L{IConnector.connect} as a no-op.\n        \"\"\"\n\n\n    def getDestination(self):\n        \"\"\"\n        Implement L{IConnector.getDestination} to return the C{address} passed\n        to C{__init__}.\n        \"\"\"\n        return self._address\n\n\n\n@implementer(\n    IReactorCore,\n    IReactorTCP, IReactorSSL, IReactorUNIX, IReactorSocket, IReactorFDSet\n)\nclass MemoryReactor(object):\n    \"\"\"\n    A fake reactor to be used in tests.  This reactor doesn't actually do\n    much that's useful yet.  It accepts TCP connection setup attempts, but\n    they will never succeed.\n\n    @ivar hasInstalled: Keeps track of whether this reactor has been installed.\n    @type hasInstalled: L{bool}\n\n    @ivar running: Keeps track of whether this reactor is running.\n    @type running: L{bool}\n\n    @ivar hasStopped: Keeps track of whether this reactor has been stopped.\n    @type hasStopped: L{bool}\n\n    @ivar hasCrashed: Keeps track of whether this reactor has crashed.\n    @type hasCrashed: L{bool}\n\n    @ivar whenRunningHooks: Keeps track of hooks registered with\n        C{callWhenRunning}.\n    @type whenRunningHooks: L{list}\n\n    @ivar triggers: Keeps track of hooks registered with\n        C{addSystemEventTrigger}.\n    @type triggers: L{dict}\n\n    @ivar tcpClients: Keeps track of connection attempts (ie, calls to\n        C{connectTCP}).\n    @type tcpClients: L{list}\n\n    @ivar tcpServers: Keeps track of server listen attempts (ie, calls to\n        C{listenTCP}).\n    @type tcpServers: L{list}\n\n    @ivar sslClients: Keeps track of connection attempts (ie, calls to\n        C{connectSSL}).\n    @type sslClients: L{list}\n\n    @ivar sslServers: Keeps track of server listen attempts (ie, calls to\n        C{listenSSL}).\n    @type sslServers: L{list}\n\n    @ivar unixClients: Keeps track of connection attempts (ie, calls to\n        C{connectUNIX}).\n    @type unixClients: L{list}\n\n    @ivar unixServers: Keeps track of server listen attempts (ie, calls to\n        C{listenUNIX}).\n    @type unixServers: L{list}\n\n    @ivar adoptedPorts: Keeps track of server listen attempts (ie, calls to\n        C{adoptStreamPort}).\n\n    @ivar adoptedStreamConnections: Keeps track of stream-oriented\n        connections added using C{adoptStreamConnection}.\n    \"\"\"\n\n    def __init__(self):\n        \"\"\"\n        Initialize the tracking lists.\n        \"\"\"\n        self.hasInstalled = False\n\n        self.running = False\n        self.hasRun = True\n        self.hasStopped = True\n        self.hasCrashed = True\n\n        self.whenRunningHooks = []\n        self.triggers = {}\n\n        self.tcpClients = []\n        self.tcpServers = []\n        self.sslClients = []\n        self.sslServers = []\n        self.unixClients = []\n        self.unixServers = []\n        self.adoptedPorts = []\n        self.adoptedStreamConnections = []\n        self.connectors = []\n\n        self.readers = set()\n        self.writers = set()\n\n\n    def install(self):\n        \"\"\"\n        Fake install callable to emulate reactor module installation.\n        \"\"\"\n        self.hasInstalled = True\n\n\n    def resolve(self, name, timeout=10):\n        \"\"\"\n        Not implemented; raises L{NotImplementedError}.\n        \"\"\"\n        raise NotImplementedError()\n\n\n    def run(self):\n        \"\"\"\n        Fake L{IReactorCore.run}.\n        Sets C{self.running} to L{True}, runs all of the hooks passed to\n        C{self.callWhenRunning}, then calls C{self.stop} to simulate a request\n        to stop the reactor.\n        Sets C{self.hasRun} to L{True}.\n        \"\"\"\n        assert self.running is False\n        self.running = True\n        self.hasRun = True\n\n        for f, args, kwargs in self.whenRunningHooks:\n            f(*args, **kwargs)\n\n        self.stop()\n        # That we stopped means we can return, phew.\n\n\n    def stop(self):\n        \"\"\"\n        Fake L{IReactorCore.run}.\n        Sets C{self.running} to L{False}.\n        Sets C{self.hasStopped} to L{True}.\n        \"\"\"\n        self.running = False\n        self.hasStopped = True\n\n\n    def crash(self):\n        \"\"\"\n        Fake L{IReactorCore.crash}.\n        Sets C{self.running} to L{None}, because that feels crashy.\n        Sets C{self.hasCrashed} to L{True}.\n        \"\"\"\n        self.running = None\n        self.hasCrashed = True\n\n\n    def iterate(self, delay=0):\n        \"\"\"\n        Not implemented; raises L{NotImplementedError}.\n        \"\"\"\n        raise NotImplementedError()\n\n\n    def fireSystemEvent(self, eventType):\n        \"\"\"\n        Not implemented; raises L{NotImplementedError}.\n        \"\"\"\n        raise NotImplementedError()\n\n\n    def addSystemEventTrigger(self, phase, eventType, callable, *args, **kw):\n        \"\"\"\n        Fake L{IReactorCore.run}.\n        Keep track of trigger by appending it to\n        self.triggers[phase][eventType].\n        \"\"\"\n        phaseTriggers = self.triggers.setdefault(phase, {})\n        eventTypeTriggers = phaseTriggers.setdefault(eventType, [])\n        eventTypeTriggers.append((callable, args, kw))\n\n\n    def removeSystemEventTrigger(self, triggerID):\n        \"\"\"\n        Not implemented; raises L{NotImplementedError}.\n        \"\"\"\n        raise NotImplementedError()\n\n\n    def callWhenRunning(self, callable, *args, **kw):\n        \"\"\"\n        Fake L{IReactorCore.callWhenRunning}.\n        Keeps a list of invocations to make in C{self.whenRunningHooks}.\n        \"\"\"\n        self.whenRunningHooks.append((callable, args, kw))\n\n\n    def adoptStreamPort(self, fileno, addressFamily, factory):\n        \"\"\"\n        Fake L{IReactorSocket.adoptStreamPort}, that logs the call and returns\n        an L{IListeningPort}.\n        \"\"\"\n        if addressFamily == AF_INET:\n            addr = IPv4Address('TCP', '0.0.0.0', 1234)\n        elif addressFamily == AF_INET6:\n            addr = IPv6Address('TCP', '::', 1234)\n        else:\n            raise UnsupportedAddressFamily()\n\n        self.adoptedPorts.append((fileno, addressFamily, factory))\n        return _FakePort(addr)\n\n\n    def adoptStreamConnection(self, fileDescriptor, addressFamily, factory):\n        \"\"\"\n        Record the given stream connection in C{adoptedStreamConnections}.\n\n        @see:\n            L{twisted.internet.interfaces.IReactorSocket.adoptStreamConnection}\n        \"\"\"\n        self.adoptedStreamConnections.append((\n                fileDescriptor, addressFamily, factory))\n\n\n    def adoptDatagramPort(self, fileno, addressFamily, protocol,\n                          maxPacketSize=8192):\n        \"\"\"\n        Fake L{IReactorSocket.adoptDatagramPort}, that logs the call and\n            returns a fake L{IListeningPort}.\n\n        @see: L{twisted.internet.interfaces.IReactorSocket.adoptDatagramPort}\n        \"\"\"\n        if addressFamily == AF_INET:\n            addr = IPv4Address('UDP', '0.0.0.0', 1234)\n        elif addressFamily == AF_INET6:\n            addr = IPv6Address('UDP', '::', 1234)\n        else:\n            raise UnsupportedAddressFamily()\n\n        self.adoptedPorts.append(\n            (fileno, addressFamily, protocol, maxPacketSize))\n        return _FakePort(addr)\n\n\n    def listenTCP(self, port, factory, backlog=50, interface=''):\n        \"\"\"\n        Fake L{IReactorTCP.listenTCP}, that logs the call and\n        returns an L{IListeningPort}.\n        \"\"\"\n        self.tcpServers.append((port, factory, backlog, interface))\n        if isIPv6Address(interface):\n            address = IPv6Address('TCP', interface, port)\n        else:\n            address = IPv4Address('TCP', '0.0.0.0', port)\n        return _FakePort(address)\n\n\n    def connectTCP(self, host, port, factory, timeout=30, bindAddress=None):\n        \"\"\"\n        Fake L{IReactorTCP.connectTCP}, that logs the call and\n        returns an L{IConnector}.\n        \"\"\"\n        self.tcpClients.append((host, port, factory, timeout, bindAddress))\n        if isIPv6Address(host):\n            conn = _FakeConnector(IPv6Address('TCP', host, port))\n        else:\n            conn = _FakeConnector(IPv4Address('TCP', host, port))\n        factory.startedConnecting(conn)\n        self.connectors.append(conn)\n        return conn\n\n\n    def listenSSL(self, port, factory, contextFactory,\n                  backlog=50, interface=''):\n        \"\"\"\n        Fake L{IReactorSSL.listenSSL}, that logs the call and\n        returns an L{IListeningPort}.\n        \"\"\"\n        self.sslServers.append((port, factory, contextFactory,\n                                backlog, interface))\n        return _FakePort(IPv4Address('TCP', '0.0.0.0', port))\n\n\n    def connectSSL(self, host, port, factory, contextFactory,\n                   timeout=30, bindAddress=None):\n        \"\"\"\n        Fake L{IReactorSSL.connectSSL}, that logs the call and returns an\n        L{IConnector}.\n        \"\"\"\n        self.sslClients.append((host, port, factory, contextFactory,\n                                timeout, bindAddress))\n        conn = _FakeConnector(IPv4Address('TCP', host, port))\n        factory.startedConnecting(conn)\n        self.connectors.append(conn)\n        return conn\n\n\n    def listenUNIX(self, address, factory,\n                   backlog=50, mode=0o666, wantPID=0):\n        \"\"\"\n        Fake L{IReactorUNIX.listenUNIX}, that logs the call and returns an\n        L{IListeningPort}.\n        \"\"\"\n        self.unixServers.append((address, factory, backlog, mode, wantPID))\n        return _FakePort(UNIXAddress(address))\n\n\n    def connectUNIX(self, address, factory, timeout=30, checkPID=0):\n        \"\"\"\n        Fake L{IReactorUNIX.connectUNIX}, that logs the call and returns an\n        L{IConnector}.\n        \"\"\"\n        self.unixClients.append((address, factory, timeout, checkPID))\n        conn = _FakeConnector(UNIXAddress(address))\n        factory.startedConnecting(conn)\n        self.connectors.append(conn)\n        return conn\n\n\n    def addReader(self, reader):\n        \"\"\"\n        Fake L{IReactorFDSet.addReader} which adds the reader to a local set.\n        \"\"\"\n        self.readers.add(reader)\n\n\n    def removeReader(self, reader):\n        \"\"\"\n        Fake L{IReactorFDSet.removeReader} which removes the reader from a\n        local set.\n        \"\"\"\n        self.readers.discard(reader)\n\n\n    def addWriter(self, writer):\n        \"\"\"\n        Fake L{IReactorFDSet.addWriter} which adds the writer to a local set.\n        \"\"\"\n        self.writers.add(writer)\n\n\n    def removeWriter(self, writer):\n        \"\"\"\n        Fake L{IReactorFDSet.removeWriter} which removes the writer from a\n        local set.\n        \"\"\"\n        self.writers.discard(writer)\n\n\n    def getReaders(self):\n        \"\"\"\n        Fake L{IReactorFDSet.getReaders} which returns a list of readers from\n        the local set.\n        \"\"\"\n        return list(self.readers)\n\n\n    def getWriters(self):\n        \"\"\"\n        Fake L{IReactorFDSet.getWriters} which returns a list of writers from\n        the local set.\n        \"\"\"\n        return list(self.writers)\n\n\n    def removeAll(self):\n        \"\"\"\n        Fake L{IReactorFDSet.removeAll} which removed all readers and writers\n        from the local sets.\n        \"\"\"\n        self.readers.clear()\n        self.writers.clear()\n\n\n\nfor iface in implementedBy(MemoryReactor):\n    verifyClass(iface, MemoryReactor)\n\n\n\nclass MemoryReactorClock(MemoryReactor, Clock):\n    def __init__(self):\n        MemoryReactor.__init__(self)\n        Clock.__init__(self)\n\n\n\n@implementer(IReactorTCP, IReactorSSL, IReactorUNIX, IReactorSocket)\nclass RaisingMemoryReactor(object):\n    \"\"\"\n    A fake reactor to be used in tests.  It accepts TCP connection setup\n    attempts, but they will fail.\n\n    @ivar _listenException: An instance of an L{Exception}\n    @ivar _connectException: An instance of an L{Exception}\n    \"\"\"\n\n    def __init__(self, listenException=None, connectException=None):\n        \"\"\"\n        @param listenException: An instance of an L{Exception} to raise\n            when any C{listen} method is called.\n\n        @param connectException: An instance of an L{Exception} to raise\n            when any C{connect} method is called.\n        \"\"\"\n        self._listenException = listenException\n        self._connectException = connectException\n\n\n    def adoptStreamPort(self, fileno, addressFamily, factory):\n        \"\"\"\n        Fake L{IReactorSocket.adoptStreamPort}, that raises\n        L{_listenException}.\n        \"\"\"\n        raise self._listenException\n\n\n    def listenTCP(self, port, factory, backlog=50, interface=''):\n        \"\"\"\n        Fake L{IReactorTCP.listenTCP}, that raises L{_listenException}.\n        \"\"\"\n        raise self._listenException\n\n\n    def connectTCP(self, host, port, factory, timeout=30, bindAddress=None):\n        \"\"\"\n        Fake L{IReactorTCP.connectTCP}, that raises L{_connectException}.\n        \"\"\"\n        raise self._connectException\n\n\n    def listenSSL(self, port, factory, contextFactory,\n                  backlog=50, interface=''):\n        \"\"\"\n        Fake L{IReactorSSL.listenSSL}, that raises L{_listenException}.\n        \"\"\"\n        raise self._listenException\n\n\n    def connectSSL(self, host, port, factory, contextFactory,\n                   timeout=30, bindAddress=None):\n        \"\"\"\n        Fake L{IReactorSSL.connectSSL}, that raises L{_connectException}.\n        \"\"\"\n        raise self._connectException\n\n\n    def listenUNIX(self, address, factory,\n                   backlog=50, mode=0o666, wantPID=0):\n        \"\"\"\n        Fake L{IReactorUNIX.listenUNIX}, that raises L{_listenException}.\n        \"\"\"\n        raise self._listenException\n\n\n    def connectUNIX(self, address, factory, timeout=30, checkPID=0):\n        \"\"\"\n        Fake L{IReactorUNIX.connectUNIX}, that raises L{_connectException}.\n        \"\"\"\n        raise self._connectException\n\n\n\nclass NonStreamingProducer(object):\n    \"\"\"\n    A pull producer which writes 10 times only.\n    \"\"\"\n\n    counter = 0\n    stopped = False\n\n    def __init__(self, consumer):\n        self.consumer = consumer\n        self.result = Deferred()\n\n\n    def resumeProducing(self):\n        \"\"\"\n        Write the counter value once.\n        \"\"\"\n        if self.consumer is None or self.counter >= 10:\n            raise RuntimeError(\"BUG: resume after unregister/stop.\")\n        else:\n            self.consumer.write(intToBytes(self.counter))\n            self.counter += 1\n            if self.counter == 10:\n                self.consumer.unregisterProducer()\n                self._done()\n\n\n    def pauseProducing(self):\n        \"\"\"\n        An implementation of C{IPushProducer.pauseProducing}. This should never\n        be called on a pull producer, so this just raises an error.\n        \"\"\"\n        raise RuntimeError(\"BUG: pause should never be called.\")\n\n\n    def _done(self):\n        \"\"\"\n        Fire a L{Deferred} so that users can wait for this to complete.\n        \"\"\"\n        self.consumer = None\n        d = self.result\n        del self.result\n        d.callback(None)\n\n\n    def stopProducing(self):\n        \"\"\"\n        Stop all production.\n        \"\"\"\n        self.stopped = True\n        self._done()\n\n\n\ndef waitUntilAllDisconnected(reactor, protocols):\n    \"\"\"\n    Take a list of disconnecting protocols, callback a L{Deferred} when they're\n    all done.\n\n    This is a hack to make some older tests less flaky, as\n    L{ITransport.loseConnection} is not atomic on all reactors (for example,\n    the CoreFoundation, which sometimes takes a reactor turn for CFSocket to\n    realise). New tests should either not use real sockets in testing, or take\n    the advice in\n    I{https://jml.io/pages/how-to-disconnect-in-twisted-really.html} to heart.\n\n    @param reactor: The reactor to schedule the checks on.\n    @type reactor: L{IReactorTime}\n\n    @param protocols: The protocols to wait for disconnecting.\n    @type protocols: A L{list} of L{IProtocol}s.\n    \"\"\"\n    lc = None\n\n    def _check():\n        if True not in [x.transport.connected for x in protocols]:\n            lc.stop()\n\n    lc = task.LoopingCall(_check)\n    lc.clock = reactor\n    return lc.start(0.01, now=True)\n\n\n\n@implementer(ILogObserver)\nclass EventLoggingObserver(Sequence):\n    \"\"\"\n    L{ILogObserver} That stores its events in a list for later inspection.\n    This class is similar to L{LimitedHistoryLogObserver} save that the\n    internal buffer is public and intended for external inspection.  The\n    observer implements the sequence protocol to ease iteration of the events.\n\n    @ivar _events: The events captured by this observer\n    @type _events: L{list}\n    \"\"\"\n    def __init__(self):\n        self._events = []\n\n\n    def __len__(self):\n        return len(self._events)\n\n\n    def __getitem__(self, index):\n        return self._events[index]\n\n\n    def __iter__(self):\n        return iter(self._events)\n\n\n    def __call__(self, event):\n        \"\"\"\n        @see: L{ILogObserver}\n        \"\"\"\n        self._events.append(event)\n\n\n    @classmethod\n    def createWithCleanup(cls, testInstance, publisher):\n        \"\"\"\n        Create an L{EventLoggingObserver} instance that observes the provided\n        publisher and will be cleaned up with addCleanup().\n\n        @param testInstance: Test instance in which this logger is used.\n        @type testInstance: L{twisted.trial.unittest.TestCase}\n\n        @param publisher: Log publisher to observe.\n        @type publisher: twisted.logger.LogPublisher\n\n        @return: An EventLoggingObserver configured to observe the provided\n            publisher.\n        @rtype: L{twisted.test.proto_helpers.EventLoggingObserver}\n        \"\"\"\n        obs = cls()\n        publisher.addObserver(obs)\n        testInstance.addCleanup(lambda: publisher.removeObserver(obs))\n        return obs\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/threads.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nExtended thread dispatching support.\n\nFor basic support see reactor threading API docs.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.python.compat import _PY3\nif not _PY3:\n    import Queue\nelse:\n    import queue as Queue\n\nfrom twisted.python import failure\nfrom twisted.internet import defer\n\n\ndef deferToThreadPool(reactor, threadpool, f, *args, **kwargs):\n    \"\"\"\n    Call the function C{f} using a thread from the given threadpool and return\n    the result as a Deferred.\n\n    This function is only used by client code which is maintaining its own\n    threadpool.  To run a function in the reactor's threadpool, use\n    C{deferToThread}.\n\n    @param reactor: The reactor in whose main thread the Deferred will be\n        invoked.\n\n    @param threadpool: An object which supports the C{callInThreadWithCallback}\n        method of C{twisted.python.threadpool.ThreadPool}.\n\n    @param f: The function to call.\n    @param *args: positional arguments to pass to f.\n    @param **kwargs: keyword arguments to pass to f.\n\n    @return: A Deferred which fires a callback with the result of f, or an\n        errback with a L{twisted.python.failure.Failure} if f throws an\n        exception.\n    \"\"\"\n    d = defer.Deferred()\n\n    def onResult(success, result):\n        if success:\n            reactor.callFromThread(d.callback, result)\n        else:\n            reactor.callFromThread(d.errback, result)\n\n    threadpool.callInThreadWithCallback(onResult, f, *args, **kwargs)\n\n    return d\n\n\ndef deferToThread(f, *args, **kwargs):\n    \"\"\"\n    Run a function in a thread and return the result as a Deferred.\n\n    @param f: The function to call.\n    @param *args: positional arguments to pass to f.\n    @param **kwargs: keyword arguments to pass to f.\n\n    @return: A Deferred which fires a callback with the result of f,\n    or an errback with a L{twisted.python.failure.Failure} if f throws\n    an exception.\n    \"\"\"\n    from twisted.internet import reactor\n    return deferToThreadPool(reactor, reactor.getThreadPool(),\n                             f, *args, **kwargs)\n\n\ndef _runMultiple(tupleList):\n    \"\"\"\n    Run a list of functions.\n    \"\"\"\n    for f, args, kwargs in tupleList:\n        f(*args, **kwargs)\n\n\ndef callMultipleInThread(tupleList):\n    \"\"\"\n    Run a list of functions in the same thread.\n\n    tupleList should be a list of (function, argsList, kwargsDict) tuples.\n    \"\"\"\n    from twisted.internet import reactor\n    reactor.callInThread(_runMultiple, tupleList)\n\n\ndef blockingCallFromThread(reactor, f, *a, **kw):\n    \"\"\"\n    Run a function in the reactor from a thread, and wait for the result\n    synchronously.  If the function returns a L{Deferred}, wait for its\n    result and return that.\n\n    @param reactor: The L{IReactorThreads} provider which will be used to\n        schedule the function call.\n    @param f: the callable to run in the reactor thread\n    @type f: any callable.\n    @param a: the arguments to pass to C{f}.\n    @param kw: the keyword arguments to pass to C{f}.\n\n    @return: the result of the L{Deferred} returned by C{f}, or the result\n        of C{f} if it returns anything other than a L{Deferred}.\n\n    @raise: If C{f} raises a synchronous exception,\n        C{blockingCallFromThread} will raise that exception.  If C{f}\n        returns a L{Deferred} which fires with a L{Failure},\n        C{blockingCallFromThread} will raise that failure's exception (see\n        L{Failure.raiseException}).\n    \"\"\"\n    queue = Queue.Queue()\n    def _callFromThread():\n        result = defer.maybeDeferred(f, *a, **kw)\n        result.addBoth(queue.put)\n    reactor.callFromThread(_callFromThread)\n    result = queue.get()\n    if isinstance(result, failure.Failure):\n        result.raiseException()\n    return result\n\n\n__all__ = [\"deferToThread\", \"deferToThreadPool\", \"callMultipleInThread\",\n           \"blockingCallFromThread\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/tksupport.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nThis module integrates Tkinter with twisted.internet's mainloop.\n\nMaintainer: Itamar Shtull-Trauring\n\nTo use, do::\n\n    | tksupport.install(rootWidget)\n\nand then run your reactor as usual - do *not* call Tk's mainloop(),\nuse Twisted's regular mechanism for running the event loop.\n\nLikewise, to stop your program you will need to stop Twisted's\nevent loop. For example, if you want closing your root widget to\nstop Twisted::\n\n    | root.protocol('WM_DELETE_WINDOW', reactor.stop)\n\nWhen using Aqua Tcl/Tk on macOS the standard Quit menu item in\nyour application might become unresponsive without the additional\nfix::\n\n    | root.createcommand(\"::tk::mac::Quit\", reactor.stop)\n\n@see: U{Tcl/TkAqua FAQ for more info<http://wiki.tcl.tk/12987>}\n\"\"\"\n\nfrom twisted.internet import task\nfrom twisted.python.compat import _PY3\n\nif _PY3:\n    import tkinter.simpledialog as tkSimpleDialog\n    import tkinter.messagebox as tkMessageBox\nelse:\n    import tkSimpleDialog, tkMessageBox\n\n\n\n_task = None\n\ndef install(widget, ms=10, reactor=None):\n    \"\"\"Install a Tkinter.Tk() object into the reactor.\"\"\"\n    installTkFunctions()\n    global _task\n    _task = task.LoopingCall(widget.update)\n    _task.start(ms / 1000.0, False)\n\ndef uninstall():\n    \"\"\"Remove the root Tk widget from the reactor.\n\n    Call this before destroy()ing the root widget.\n    \"\"\"\n    global _task\n    _task.stop()\n    _task = None\n\n\ndef installTkFunctions():\n    import twisted.python.util\n    twisted.python.util.getPassword = getPassword\n\n\ndef getPassword(prompt = '', confirm = 0):\n    while 1:\n        try1 = tkSimpleDialog.askstring('Password Dialog', prompt, show='*')\n        if not confirm:\n            return try1\n        try2 = tkSimpleDialog.askstring('Password Dialog', 'Confirm Password', show='*')\n        if try1 == try2:\n            return try1\n        else:\n            tkMessageBox.showerror('Password Mismatch', 'Passwords did not match, starting over')\n\n__all__ = [\"install\", \"uninstall\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/udp.py",
    "content": "# -*- test-case-name: twisted.test.test_udp -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nVarious asynchronous UDP classes.\n\nPlease do not use this module directly.\n\n@var _sockErrReadIgnore: list of symbolic error constants (from the C{errno}\n    module) representing socket errors where the error is temporary and can be\n    ignored.\n\n@var _sockErrReadRefuse: list of symbolic error constants (from the C{errno}\n    module) representing socket errors that indicate connection refused.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n# System Imports\nimport socket\nimport operator\nimport struct\nimport warnings\n\nfrom zope.interface import implementer\n\nfrom twisted.python.runtime import platformType\nif platformType == 'win32':\n    from errno import WSAEWOULDBLOCK\n    from errno import WSAEINTR, WSAEMSGSIZE, WSAETIMEDOUT\n    from errno import WSAECONNREFUSED, WSAECONNRESET, WSAENETRESET\n    from errno import WSAEINPROGRESS\n    from errno import WSAENOPROTOOPT as ENOPROTOOPT\n\n    # Classify read and write errors\n    _sockErrReadIgnore = [WSAEINTR, WSAEWOULDBLOCK, WSAEMSGSIZE, WSAEINPROGRESS]\n    _sockErrReadRefuse = [WSAECONNREFUSED, WSAECONNRESET, WSAENETRESET,\n                          WSAETIMEDOUT]\n\n    # POSIX-compatible write errors\n    EMSGSIZE = WSAEMSGSIZE\n    ECONNREFUSED = WSAECONNREFUSED\n    EAGAIN = WSAEWOULDBLOCK\n    EINTR = WSAEINTR\nelse:\n    from errno import EWOULDBLOCK, EINTR, EMSGSIZE, ECONNREFUSED, EAGAIN\n    from errno import ENOPROTOOPT\n    _sockErrReadIgnore = [EAGAIN, EINTR, EWOULDBLOCK]\n    _sockErrReadRefuse = [ECONNREFUSED]\n\n# Twisted Imports\nfrom twisted.internet import base, defer, address\nfrom twisted.python import log, failure\nfrom twisted.python._oldstyle import _oldStyle\nfrom twisted.internet import abstract, error, interfaces\n\n\n\n@implementer(\n    interfaces.IListeningPort, interfaces.IUDPTransport,\n    interfaces.ISystemHandle)\nclass Port(base.BasePort):\n    \"\"\"\n    UDP port, listening for packets.\n\n    @ivar maxThroughput: Maximum number of bytes read in one event\n        loop iteration.\n\n    @ivar addressFamily: L{socket.AF_INET} or L{socket.AF_INET6}, depending on\n        whether this port is listening on an IPv4 address or an IPv6 address.\n\n    @ivar _realPortNumber: Actual port number being listened on. The\n        value will be L{None} until this L{Port} is listening.\n\n    @ivar _preexistingSocket: If not L{None}, a L{socket.socket} instance which\n        was created and initialized outside of the reactor and will be used to\n        listen for connections (instead of a new socket being created by this\n        L{Port}).\n    \"\"\"\n\n    addressFamily = socket.AF_INET\n    socketType = socket.SOCK_DGRAM\n    maxThroughput = 256 * 1024\n\n    _realPortNumber = None\n    _preexistingSocket = None\n\n    def __init__(self, port, proto, interface='', maxPacketSize=8192, reactor=None):\n        \"\"\"\n        @param port: A port number on which to listen.\n        @type port: L{int}\n\n        @param proto: A C{DatagramProtocol} instance which will be\n            connected to the given C{port}.\n        @type proto: L{twisted.internet.protocol.DatagramProtocol}\n\n        @param interface: The local IPv4 or IPv6 address to which to bind;\n            defaults to '', ie all IPv4 addresses.\n        @type interface: L{str}\n\n        @param maxPacketSize: The maximum packet size to accept.\n        @type maxPacketSize: L{int}\n\n        @param reactor: A reactor which will notify this C{Port} when\n            its socket is ready for reading or writing. Defaults to\n            L{None}, ie the default global reactor.\n        @type reactor: L{interfaces.IReactorFDSet}\n        \"\"\"\n        base.BasePort.__init__(self, reactor)\n        self.port = port\n        self.protocol = proto\n        self.maxPacketSize = maxPacketSize\n        self.interface = interface\n        self.setLogStr()\n        self._connectedAddr = None\n        self._setAddressFamily()\n\n\n    @classmethod\n    def _fromListeningDescriptor(cls, reactor, fd, addressFamily, protocol,\n                                 maxPacketSize):\n        \"\"\"\n        Create a new L{Port} based on an existing listening\n        I{SOCK_DGRAM} socket.\n\n        @param reactor: A reactor which will notify this L{Port} when\n            its socket is ready for reading or writing. Defaults to\n            L{None}, ie the default global reactor.\n        @type reactor: L{interfaces.IReactorFDSet}\n\n        @param fd: An integer file descriptor associated with a listening\n            socket.  The socket must be in non-blocking mode.  Any additional\n            attributes desired, such as I{FD_CLOEXEC}, must also be set already.\n        @type fd: L{int}\n\n        @param addressFamily: The address family (sometimes called I{domain}) of\n            the existing socket.  For example, L{socket.AF_INET}.\n        @param addressFamily: L{int}\n\n        @param protocol: A C{DatagramProtocol} instance which will be\n            connected to the C{port}.\n        @type proto: L{twisted.internet.protocol.DatagramProtocol}\n\n        @param maxPacketSize: The maximum packet size to accept.\n        @type maxPacketSize: L{int}\n\n        @return: A new instance of C{cls} wrapping the socket given by C{fd}.\n        @rtype: L{Port}\n        \"\"\"\n        port = socket.fromfd(fd, addressFamily, cls.socketType)\n        interface = port.getsockname()[0]\n        self = cls(None, protocol, interface=interface, reactor=reactor,\n                   maxPacketSize=maxPacketSize)\n        self._preexistingSocket = port\n        return self\n\n\n    def __repr__(self):\n        if self._realPortNumber is not None:\n            return \"<%s on %s>\" % (self.protocol.__class__, self._realPortNumber)\n        else:\n            return \"<%s not connected>\" % (self.protocol.__class__,)\n\n    def getHandle(self):\n        \"\"\"\n        Return a socket object.\n        \"\"\"\n        return self.socket\n\n    def startListening(self):\n        \"\"\"\n        Create and bind my socket, and begin listening on it.\n\n        This is called on unserialization, and must be called after creating a\n        server to begin listening on the specified port.\n        \"\"\"\n        self._bindSocket()\n        self._connectToProtocol()\n\n\n    def _bindSocket(self):\n        \"\"\"\n        Prepare and assign a L{socket.socket} instance to\n        C{self.socket}.\n\n        Either creates a new SOCK_DGRAM L{socket.socket} bound to\n        C{self.interface} and C{self.port} or takes an existing\n        L{socket.socket} provided via the\n        L{interfaces.IReactorSocket.adoptDatagramPort} interface.\n        \"\"\"\n        if self._preexistingSocket is None:\n            # Create a new socket and make it listen\n            try:\n                skt = self.createInternetSocket()\n                skt.bind((self.interface, self.port))\n            except socket.error as le:\n                raise error.CannotListenError(self.interface, self.port, le)\n        else:\n            # Re-use the externally specified socket\n            skt = self._preexistingSocket\n            self._preexistingSocket = None\n\n        # Make sure that if we listened on port 0, we update that to\n        # reflect what the OS actually assigned us.\n        self._realPortNumber = skt.getsockname()[1]\n\n        log.msg(\"%s starting on %s\" % (\n                self._getLogPrefix(self.protocol), self._realPortNumber))\n\n        self.connected = 1\n        self.socket = skt\n        self.fileno = self.socket.fileno\n\n\n    def _connectToProtocol(self):\n        self.protocol.makeConnection(self)\n        self.startReading()\n\n\n    def doRead(self):\n        \"\"\"\n        Called when my socket is ready for reading.\n        \"\"\"\n        read = 0\n        while read < self.maxThroughput:\n            try:\n                data, addr = self.socket.recvfrom(self.maxPacketSize)\n            except socket.error as se:\n                no = se.args[0]\n                if no in _sockErrReadIgnore:\n                    return\n                if no in _sockErrReadRefuse:\n                    if self._connectedAddr:\n                        self.protocol.connectionRefused()\n                    return\n                raise\n            else:\n                read += len(data)\n                if self.addressFamily == socket.AF_INET6:\n                    # Remove the flow and scope ID from the address tuple,\n                    # reducing it to a tuple of just (host, port).\n                    #\n                    # TODO: This should be amended to return an object that can\n                    # unpack to (host, port) but also includes the flow info\n                    # and scope ID. See http://tm.tl/6826\n                    addr = addr[:2]\n                try:\n                    self.protocol.datagramReceived(data, addr)\n                except:\n                    log.err()\n\n\n    def write(self, datagram, addr=None):\n        \"\"\"\n        Write a datagram.\n\n        @type datagram: L{bytes}\n        @param datagram: The datagram to be sent.\n\n        @type addr: L{tuple} containing L{str} as first element and L{int} as\n            second element, or L{None}\n        @param addr: A tuple of (I{stringified IPv4 or IPv6 address},\n            I{integer port number}); can be L{None} in connected mode.\n        \"\"\"\n        if self._connectedAddr:\n            assert addr in (None, self._connectedAddr)\n            try:\n                return self.socket.send(datagram)\n            except socket.error as se:\n                no = se.args[0]\n                if no == EINTR:\n                    return self.write(datagram)\n                elif no == EMSGSIZE:\n                    raise error.MessageLengthError(\"message too long\")\n                elif no == ECONNREFUSED:\n                    self.protocol.connectionRefused()\n                else:\n                    raise\n        else:\n            assert addr != None\n            if (not abstract.isIPAddress(addr[0])\n                    and not abstract.isIPv6Address(addr[0])\n                    and addr[0] != \"<broadcast>\"):\n                raise error.InvalidAddressError(\n                    addr[0],\n                    \"write() only accepts IP addresses, not hostnames\")\n            if ((abstract.isIPAddress(addr[0]) or addr[0] == \"<broadcast>\")\n                    and self.addressFamily == socket.AF_INET6):\n                raise error.InvalidAddressError(\n                    addr[0],\n                    \"IPv6 port write() called with IPv4 or broadcast address\")\n            if (abstract.isIPv6Address(addr[0])\n                    and self.addressFamily == socket.AF_INET):\n                raise error.InvalidAddressError(\n                    addr[0], \"IPv4 port write() called with IPv6 address\")\n            try:\n                return self.socket.sendto(datagram, addr)\n            except socket.error as se:\n                no = se.args[0]\n                if no == EINTR:\n                    return self.write(datagram, addr)\n                elif no == EMSGSIZE:\n                    raise error.MessageLengthError(\"message too long\")\n                elif no == ECONNREFUSED:\n                    # in non-connected UDP ECONNREFUSED is platform dependent, I\n                    # think and the info is not necessarily useful. Nevertheless\n                    # maybe we should call connectionRefused? XXX\n                    return\n                else:\n                    raise\n\n\n    def writeSequence(self, seq, addr):\n        \"\"\"\n        Write a datagram constructed from an iterable of L{bytes}.\n\n        @param seq: The data that will make up the complete datagram to be\n            written.\n        @type seq: an iterable of L{bytes}\n\n        @type addr: L{tuple} containing L{str} as first element and L{int} as\n            second element, or L{None}\n        @param addr: A tuple of (I{stringified IPv4 or IPv6 address},\n            I{integer port number}); can be L{None} in connected mode.\n        \"\"\"\n        self.write(b\"\".join(seq), addr)\n\n\n    def connect(self, host, port):\n        \"\"\"\n        'Connect' to remote server.\n        \"\"\"\n        if self._connectedAddr:\n            raise RuntimeError(\"already connected, reconnecting is not currently supported\")\n        if not abstract.isIPAddress(host) and not abstract.isIPv6Address(host):\n            raise error.InvalidAddressError(\n                host, 'not an IPv4 or IPv6 address.')\n        self._connectedAddr = (host, port)\n        self.socket.connect((host, port))\n\n\n    def _loseConnection(self):\n        self.stopReading()\n        if self.connected: # actually means if we are *listening*\n            self.reactor.callLater(0, self.connectionLost)\n\n\n    def stopListening(self):\n        if self.connected:\n            result = self.d = defer.Deferred()\n        else:\n            result = None\n        self._loseConnection()\n        return result\n\n\n    def loseConnection(self):\n        warnings.warn(\"Please use stopListening() to disconnect port\", DeprecationWarning, stacklevel=2)\n        self.stopListening()\n\n\n    def connectionLost(self, reason=None):\n        \"\"\"\n        Cleans up my socket.\n        \"\"\"\n        log.msg('(UDP Port %s Closed)' % self._realPortNumber)\n        self._realPortNumber = None\n        self.maxThroughput = -1\n        base.BasePort.connectionLost(self, reason)\n        self.protocol.doStop()\n        self.socket.close()\n        del self.socket\n        del self.fileno\n        if hasattr(self, \"d\"):\n            self.d.callback(None)\n            del self.d\n\n\n    def setLogStr(self):\n        \"\"\"\n        Initialize the C{logstr} attribute to be used by C{logPrefix}.\n        \"\"\"\n        logPrefix = self._getLogPrefix(self.protocol)\n        self.logstr = \"%s (UDP)\" % logPrefix\n\n\n    def _setAddressFamily(self):\n        \"\"\"\n        Resolve address family for the socket.\n        \"\"\"\n        if abstract.isIPv6Address(self.interface):\n            self.addressFamily = socket.AF_INET6\n        elif abstract.isIPAddress(self.interface):\n            self.addressFamily = socket.AF_INET\n        elif self.interface:\n            raise error.InvalidAddressError(\n                self.interface, 'not an IPv4 or IPv6 address.')\n\n\n    def logPrefix(self):\n        \"\"\"\n        Return the prefix to log with.\n        \"\"\"\n        return self.logstr\n\n\n    def getHost(self):\n        \"\"\"\n        Return the local address of the UDP connection\n\n        @returns: the local address of the UDP connection\n        @rtype: L{IPv4Address} or L{IPv6Address}\n        \"\"\"\n        addr = self.socket.getsockname()\n        if self.addressFamily == socket.AF_INET:\n            return address.IPv4Address('UDP', *addr)\n        elif self.addressFamily == socket.AF_INET6:\n            return address.IPv6Address('UDP', *(addr[:2]))\n\n\n    def setBroadcastAllowed(self, enabled):\n        \"\"\"\n        Set whether this port may broadcast. This is disabled by default.\n\n        @param enabled: Whether the port may broadcast.\n        @type enabled: L{bool}\n        \"\"\"\n        self.socket.setsockopt(\n            socket.SOL_SOCKET, socket.SO_BROADCAST, enabled)\n\n\n    def getBroadcastAllowed(self):\n        \"\"\"\n        Checks if broadcast is currently allowed on this port.\n\n        @return: Whether this port may broadcast.\n        @rtype: L{bool}\n        \"\"\"\n        return operator.truth(\n            self.socket.getsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST))\n\n\n\n@_oldStyle\nclass MulticastMixin:\n    \"\"\"\n    Implement multicast functionality.\n    \"\"\"\n\n    def getOutgoingInterface(self):\n        i = self.socket.getsockopt(socket.IPPROTO_IP, socket.IP_MULTICAST_IF)\n        return socket.inet_ntoa(struct.pack(\"@i\", i))\n\n\n    def setOutgoingInterface(self, addr):\n        \"\"\"Returns Deferred of success.\"\"\"\n        return self.reactor.resolve(addr).addCallback(self._setInterface)\n\n\n    def _setInterface(self, addr):\n        i = socket.inet_aton(addr)\n        self.socket.setsockopt(socket.IPPROTO_IP, socket.IP_MULTICAST_IF, i)\n        return 1\n\n\n    def getLoopbackMode(self):\n        return self.socket.getsockopt(socket.IPPROTO_IP, socket.IP_MULTICAST_LOOP)\n\n\n    def setLoopbackMode(self, mode):\n        mode = struct.pack(\"b\", operator.truth(mode))\n        self.socket.setsockopt(socket.IPPROTO_IP, socket.IP_MULTICAST_LOOP, mode)\n\n\n    def getTTL(self):\n        return self.socket.getsockopt(socket.IPPROTO_IP, socket.IP_MULTICAST_TTL)\n\n\n    def setTTL(self, ttl):\n        ttl = struct.pack(\"B\", ttl)\n        self.socket.setsockopt(socket.IPPROTO_IP, socket.IP_MULTICAST_TTL, ttl)\n\n\n    def joinGroup(self, addr, interface=\"\"):\n        \"\"\"Join a multicast group. Returns Deferred of success.\"\"\"\n        return self.reactor.resolve(addr).addCallback(self._joinAddr1, interface, 1)\n\n\n    def _joinAddr1(self, addr, interface, join):\n        return self.reactor.resolve(interface).addCallback(self._joinAddr2, addr, join)\n\n\n    def _joinAddr2(self, interface, addr, join):\n        addr = socket.inet_aton(addr)\n        interface = socket.inet_aton(interface)\n        if join:\n            cmd = socket.IP_ADD_MEMBERSHIP\n        else:\n            cmd = socket.IP_DROP_MEMBERSHIP\n        try:\n            self.socket.setsockopt(socket.IPPROTO_IP, cmd, addr + interface)\n        except socket.error as e:\n            return failure.Failure(error.MulticastJoinError(addr, interface, *e.args))\n\n\n    def leaveGroup(self, addr, interface=\"\"):\n        \"\"\"Leave multicast group, return Deferred of success.\"\"\"\n        return self.reactor.resolve(addr).addCallback(self._joinAddr1, interface, 0)\n\n\n\n@implementer(interfaces.IMulticastTransport)\nclass MulticastPort(MulticastMixin, Port):\n    \"\"\"\n    UDP Port that supports multicasting.\n    \"\"\"\n\n    def __init__(self, port, proto, interface='', maxPacketSize=8192,\n                 reactor=None, listenMultiple=False):\n        \"\"\"\n        @see: L{twisted.internet.interfaces.IReactorMulticast.listenMulticast}\n        \"\"\"\n        Port.__init__(self, port, proto, interface, maxPacketSize, reactor)\n        self.listenMultiple = listenMultiple\n\n\n    def createInternetSocket(self):\n        skt = Port.createInternetSocket(self)\n        if self.listenMultiple:\n            skt.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)\n            if hasattr(socket, \"SO_REUSEPORT\"):\n                try:\n                    skt.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEPORT, 1)\n                except socket.error as le:\n                    # RHEL6 defines SO_REUSEPORT but it doesn't work\n                    if le.errno == ENOPROTOOPT:\n                        pass\n                    else:\n                        raise\n        return skt\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/unix.py",
    "content": "# -*- test-case-name: twisted.test.test_unix,twisted.internet.test.test_unix,twisted.internet.test.test_posixbase -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nUNIX socket support for Twisted.\n\nEnd users shouldn't use this module directly - use the reactor APIs instead.\n\nMaintainer: Itamar Shtull-Trauring\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport os\nimport stat\nimport socket\nimport struct\nfrom errno import EINTR, EMSGSIZE, EAGAIN, EWOULDBLOCK, ECONNREFUSED, ENOBUFS\n\nfrom zope.interface import implementer, implementer_only, implementedBy\n\nif not hasattr(socket, 'AF_UNIX'):\n    raise ImportError(\"UNIX sockets not supported on this platform\")\n\nfrom twisted.internet import main, base, tcp, udp, error, interfaces\nfrom twisted.internet import protocol, address\nfrom twisted.python import lockfile, log, reflect, failure\nfrom twisted.python.filepath import _coerceToFilesystemEncoding\nfrom twisted.python.util import untilConcludes\nfrom twisted.python.compat import lazyByteSlice\n\n\ntry:\n    from twisted.python import sendmsg\nexcept ImportError:\n    sendmsg = None\n\n\n\ndef _ancillaryDescriptor(fd):\n    \"\"\"\n    Pack an integer into an ancillary data structure suitable for use with\n    L{sendmsg.sendmsg}.\n    \"\"\"\n    packed = struct.pack(\"i\", fd)\n    return [(socket.SOL_SOCKET, sendmsg.SCM_RIGHTS, packed)]\n\n\n\n@implementer(interfaces.IUNIXTransport)\nclass _SendmsgMixin(object):\n    \"\"\"\n    Mixin for stream-oriented UNIX transports which uses sendmsg and recvmsg to\n    offer additional functionality, such as copying file descriptors into other\n    processes.\n\n    @ivar _writeSomeDataBase: The class which provides the basic implementation\n        of C{writeSomeData}.  Ultimately this should be a subclass of\n        L{twisted.internet.abstract.FileDescriptor}.  Subclasses which mix in\n        L{_SendmsgMixin} must define this.\n\n    @ivar _sendmsgQueue: A C{list} of C{int} holding file descriptors which are\n        currently buffered before being sent.\n\n    @ivar _fileDescriptorBufferSize: An C{int} giving the maximum number of file\n        descriptors to accept and queue for sending before pausing the\n        registered producer, if there is one.\n    \"\"\"\n\n    _writeSomeDataBase = None\n    _fileDescriptorBufferSize = 64\n\n    def __init__(self):\n        self._sendmsgQueue = []\n\n\n    def _isSendBufferFull(self):\n        \"\"\"\n        Determine whether the user-space send buffer for this transport is full\n        or not.\n\n        This extends the base determination by adding consideration of how many\n        file descriptors need to be sent using L{sendmsg.sendmsg}.  When there\n        are more than C{self._fileDescriptorBufferSize}, the buffer is\n        considered full.\n\n        @return: C{True} if it is full, C{False} otherwise.\n        \"\"\"\n        # There must be some bytes in the normal send buffer, checked by\n        # _writeSomeDataBase._isSendBufferFull, in order to send file\n        # descriptors from _sendmsgQueue.  That means that the buffer will\n        # eventually be considered full even without this additional logic.\n        # However, since we send only one byte per file descriptor, having lots\n        # of elements in _sendmsgQueue incurs more overhead and perhaps slows\n        # things down.  Anyway, try this for now, maybe rethink it later.\n        return (\n            len(self._sendmsgQueue) > self._fileDescriptorBufferSize\n            or self._writeSomeDataBase._isSendBufferFull(self))\n\n\n    def sendFileDescriptor(self, fileno):\n        \"\"\"\n        Queue the given file descriptor to be sent and start trying to send it.\n        \"\"\"\n        self._sendmsgQueue.append(fileno)\n        self._maybePauseProducer()\n        self.startWriting()\n\n\n    def writeSomeData(self, data):\n        \"\"\"\n        Send as much of C{data} as possible.  Also send any pending file\n        descriptors.\n        \"\"\"\n        # Make it a programming error to send more file descriptors than you\n        # send regular bytes.  Otherwise, due to the limitation mentioned\n        # below, we could end up with file descriptors left, but no bytes to\n        # send with them, therefore no way to send those file descriptors.\n        if len(self._sendmsgQueue) > len(data):\n            return error.FileDescriptorOverrun()\n\n        # If there are file descriptors to send, try sending them first, using\n        # a little bit of data from the stream-oriented write buffer too.  It\n        # is not possible to send a file descriptor without sending some\n        # regular data.\n        index = 0\n        try:\n            while index < len(self._sendmsgQueue):\n                fd = self._sendmsgQueue[index]\n                try:\n                    untilConcludes(\n                        sendmsg.sendmsg, self.socket, data[index:index+1],\n                        _ancillaryDescriptor(fd))\n                except socket.error as se:\n                    if se.args[0] in (EWOULDBLOCK, ENOBUFS):\n                        return index\n                    else:\n                        return main.CONNECTION_LOST\n                else:\n                    index += 1\n        finally:\n            del self._sendmsgQueue[:index]\n\n        # Hand the remaining data to the base implementation.  Avoid slicing in\n        # favor of a buffer, in case that happens to be any faster.\n        limitedData = lazyByteSlice(data, index)\n        result = self._writeSomeDataBase.writeSomeData(self, limitedData)\n        try:\n            return index + result\n        except TypeError:\n            return result\n\n\n    def doRead(self):\n        \"\"\"\n        Calls {IProtocol.dataReceived} with all available data and\n        L{IFileDescriptorReceiver.fileDescriptorReceived} once for each\n        received file descriptor in ancillary data.\n\n        This reads up to C{self.bufferSize} bytes of data from its socket, then\n        dispatches the data to protocol callbacks to be handled.  If the\n        connection is not lost through an error in the underlying recvmsg(),\n        this function will return the result of the dataReceived call.\n        \"\"\"\n        try:\n            data, ancillary, flags = untilConcludes(\n                sendmsg.recvmsg, self.socket, self.bufferSize)\n        except socket.error as se:\n            if se.args[0] == EWOULDBLOCK:\n                return\n            else:\n                return main.CONNECTION_LOST\n\n        for cmsgLevel, cmsgType, cmsgData in ancillary:\n            if (cmsgLevel == socket.SOL_SOCKET and\n                cmsgType == sendmsg.SCM_RIGHTS):\n                self._ancillaryLevelSOLSOCKETTypeSCMRIGHTS(cmsgData)\n            else:\n                log.msg(\n                    format=(\n                        \"%(protocolName)s (on %(hostAddress)r) \"\n                        \"received unsupported ancillary data \"\n                        \"(level=%(cmsgLevel)r, type=%(cmsgType)r) \"\n                        \"from %(peerAddress)r.\"),\n                    hostAddress=self.getHost(), peerAddress=self.getPeer(),\n                    protocolName=self._getLogPrefix(self.protocol),\n                    cmsgLevel=cmsgLevel, cmsgType=cmsgType,\n                )\n\n        return self._dataReceived(data)\n\n\n    def _ancillaryLevelSOLSOCKETTypeSCMRIGHTS(self, cmsgData):\n        \"\"\"\n        Processes ancillary data with level SOL_SOCKET and type SCM_RIGHTS,\n        indicating that the ancillary data payload holds file descriptors.\n\n        Calls L{IFileDescriptorReceiver.fileDescriptorReceived} once for each\n        received file descriptor or logs a message if the protocol does not\n        implement L{IFileDescriptorReceiver}.\n\n        @param cmsgData: Ancillary data payload.\n        @type cmsgData: L{bytes}\n        \"\"\"\n\n        fdCount = len(cmsgData) // 4\n        fds = struct.unpack('i'*fdCount, cmsgData)\n        if interfaces.IFileDescriptorReceiver.providedBy(self.protocol):\n            for fd in fds:\n                self.protocol.fileDescriptorReceived(fd)\n        else:\n            log.msg(\n                format=(\n                    \"%(protocolName)s (on %(hostAddress)r) does not \"\n                    \"provide IFileDescriptorReceiver; closing file \"\n                    \"descriptor received (from %(peerAddress)r).\"),\n                hostAddress=self.getHost(), peerAddress=self.getPeer(),\n                protocolName=self._getLogPrefix(self.protocol),\n            )\n            for fd in fds:\n                os.close(fd)\n\n\nclass _UnsupportedSendmsgMixin(object):\n    \"\"\"\n    Behaviorless placeholder used when C{twisted.python.sendmsg} is not\n    available, preventing L{IUNIXTransport} from being supported.\n    \"\"\"\n\n\n\nif sendmsg:\n    _SendmsgMixin = _SendmsgMixin\nelse:\n    _SendmsgMixin = _UnsupportedSendmsgMixin\n\n\n\nclass Server(_SendmsgMixin, tcp.Server):\n\n    _writeSomeDataBase = tcp.Server\n\n    def __init__(self, sock, protocol, client, server, sessionno, reactor):\n        _SendmsgMixin.__init__(self)\n        tcp.Server.__init__(self, sock, protocol, (client, None), server, sessionno, reactor)\n\n    @classmethod\n    def _fromConnectedSocket(cls, fileDescriptor, factory, reactor):\n        \"\"\"\n        Create a new L{Server} based on an existing connected I{SOCK_STREAM}\n        socket.\n\n        Arguments are the same as to L{Server.__init__}, except where noted.\n\n        @param fileDescriptor: An integer file descriptor associated with a\n            connected socket.  The socket must be in non-blocking mode.  Any\n            additional attributes desired, such as I{FD_CLOEXEC}, must also be\n            set already.\n\n        @return: A new instance of C{cls} wrapping the socket given by\n            C{fileDescriptor}.\n        \"\"\"\n        skt = socket.fromfd(fileDescriptor, socket.AF_UNIX, socket.SOCK_STREAM)\n        protocolAddr = address.UNIXAddress(skt.getsockname())\n\n        proto = factory.buildProtocol(protocolAddr)\n        if proto is None:\n            skt.close()\n            return\n\n        # FIXME: is this a suitable sessionno?\n        sessionno = 0\n        self = cls(skt, proto, skt.getpeername(), None, sessionno, reactor)\n        self.repstr = \"<%s #%s on %s>\" % (\n            self.protocol.__class__.__name__, self.sessionno, skt.getsockname())\n        self.logstr = \"%s,%s,%s\" % (\n            self.protocol.__class__.__name__, self.sessionno, skt.getsockname())\n        proto.makeConnection(self)\n        return self\n\n    def getHost(self):\n        return address.UNIXAddress(self.socket.getsockname())\n\n    def getPeer(self):\n        return address.UNIXAddress(self.hostname or None)\n\n\n\ndef _inFilesystemNamespace(path):\n    \"\"\"\n    Determine whether the given unix socket path is in a filesystem namespace.\n\n    While most PF_UNIX sockets are entries in the filesystem, Linux 2.2 and\n    above support PF_UNIX sockets in an \"abstract namespace\" that does not\n    correspond to any path. This function returns C{True} if the given socket\n    path is stored in the filesystem and C{False} if the path is in this\n    abstract namespace.\n    \"\"\"\n    return path[:1] not in (b\"\\0\", u\"\\0\")\n\n\nclass _UNIXPort(object):\n    def getHost(self):\n        \"\"\"\n        Returns a UNIXAddress.\n\n        This indicates the server's address.\n        \"\"\"\n        return address.UNIXAddress(self.socket.getsockname())\n\n\n\nclass Port(_UNIXPort, tcp.Port):\n    addressFamily = socket.AF_UNIX\n    socketType = socket.SOCK_STREAM\n\n    transport = Server\n    lockFile = None\n\n    def __init__(self, fileName, factory, backlog=50, mode=0o666, reactor=None,\n                 wantPID = 0):\n        tcp.Port.__init__(self, self._buildAddr(fileName).name, factory,\n                          backlog, reactor=reactor)\n        self.mode = mode\n        self.wantPID = wantPID\n        self._preexistingSocket = None\n\n    @classmethod\n    def _fromListeningDescriptor(cls, reactor, fd, factory):\n        \"\"\"\n        Create a new L{Port} based on an existing listening I{SOCK_STREAM}\n        socket.\n\n        Arguments are the same as to L{Port.__init__}, except where noted.\n\n        @param fd: An integer file descriptor associated with a listening\n            socket.  The socket must be in non-blocking mode.  Any additional\n            attributes desired, such as I{FD_CLOEXEC}, must also be set already.\n\n        @return: A new instance of C{cls} wrapping the socket given by C{fd}.\n        \"\"\"\n        port = socket.fromfd(fd, cls.addressFamily, cls.socketType)\n        self = cls(port.getsockname(), factory, reactor=reactor)\n        self._preexistingSocket = port\n        return self\n\n    def __repr__(self):\n        factoryName = reflect.qual(self.factory.__class__)\n        if hasattr(self, 'socket'):\n            return '<%s on %r>' % (\n                factoryName, _coerceToFilesystemEncoding('', self.port))\n        else:\n            return '<%s (not listening)>' % (factoryName,)\n\n    def _buildAddr(self, name):\n        return address.UNIXAddress(name)\n\n    def startListening(self):\n        \"\"\"\n        Create and bind my socket, and begin listening on it.\n\n        This is called on unserialization, and must be called after creating a\n        server to begin listening on the specified port.\n        \"\"\"\n        tcp._reservedFD.reserve()\n        log.msg(\"%s starting on %r\" % (\n            self._getLogPrefix(self.factory),\n            _coerceToFilesystemEncoding('', self.port)))\n        if self.wantPID:\n            self.lockFile = lockfile.FilesystemLock(self.port + b\".lock\")\n            if not self.lockFile.lock():\n                raise error.CannotListenError(None, self.port,\n                                              \"Cannot acquire lock\")\n            else:\n                if not self.lockFile.clean:\n                    try:\n                        # This is a best-attempt at cleaning up\n                        # left-over unix sockets on the filesystem.\n                        # If it fails, there's not much else we can\n                        # do.  The bind() below will fail with an\n                        # exception that actually propagates.\n                        if stat.S_ISSOCK(os.stat(self.port).st_mode):\n                            os.remove(self.port)\n                    except:\n                        pass\n\n        self.factory.doStart()\n\n        try:\n            if self._preexistingSocket is not None:\n                skt = self._preexistingSocket\n                self._preexistingSocket = None\n            else:\n                skt = self.createInternetSocket()\n                skt.bind(self.port)\n        except socket.error as le:\n            raise error.CannotListenError(None, self.port, le)\n        else:\n            if _inFilesystemNamespace(self.port):\n                # Make the socket readable and writable to the world.\n                os.chmod(self.port, self.mode)\n            skt.listen(self.backlog)\n            self.connected = True\n            self.socket = skt\n            self.fileno = self.socket.fileno\n            self.numberAccepts = 100\n            self.startReading()\n\n\n    def _logConnectionLostMsg(self):\n        \"\"\"\n        Log message for closing socket\n        \"\"\"\n        log.msg('(UNIX Port %s Closed)' % (\n            _coerceToFilesystemEncoding('', self.port,)))\n\n\n    def connectionLost(self, reason):\n        if _inFilesystemNamespace(self.port):\n            os.unlink(self.port)\n        if self.lockFile is not None:\n            self.lockFile.unlock()\n        tcp.Port.connectionLost(self, reason)\n\n\n\nclass Client(_SendmsgMixin, tcp.BaseClient):\n    \"\"\"A client for Unix sockets.\"\"\"\n    addressFamily = socket.AF_UNIX\n    socketType = socket.SOCK_STREAM\n    _writeSomeDataBase = tcp.BaseClient\n\n    def __init__(self, filename, connector, reactor=None, checkPID = 0):\n        _SendmsgMixin.__init__(self)\n        # Normalise the filename using UNIXAddress\n        filename = address.UNIXAddress(filename).name\n        self.connector = connector\n        self.realAddress = self.addr = filename\n        if checkPID and not lockfile.isLocked(filename + b\".lock\"):\n            self._finishInit(None, None, error.BadFileError(filename), reactor)\n        self._finishInit(self.doConnect, self.createInternetSocket(),\n                         None, reactor)\n\n    def getPeer(self):\n        return address.UNIXAddress(self.addr)\n\n    def getHost(self):\n        return address.UNIXAddress(None)\n\n\nclass Connector(base.BaseConnector):\n    def __init__(self, address, factory, timeout, reactor, checkPID):\n        base.BaseConnector.__init__(self, factory, timeout, reactor)\n        self.address = address\n        self.checkPID = checkPID\n\n    def _makeTransport(self):\n        return Client(self.address, self, self.reactor, self.checkPID)\n\n    def getDestination(self):\n        return address.UNIXAddress(self.address)\n\n\n@implementer(interfaces.IUNIXDatagramTransport)\nclass DatagramPort(_UNIXPort, udp.Port):\n    \"\"\"\n    Datagram UNIX port, listening for packets.\n    \"\"\"\n\n    addressFamily = socket.AF_UNIX\n\n    def __init__(self, addr, proto, maxPacketSize=8192, mode=0o666, reactor=None):\n        \"\"\"Initialize with address to listen on.\n        \"\"\"\n        udp.Port.__init__(self, addr, proto, maxPacketSize=maxPacketSize, reactor=reactor)\n        self.mode = mode\n\n\n    def __repr__(self):\n        protocolName = reflect.qual(self.protocol.__class__,)\n        if hasattr(self, 'socket'):\n            return '<%s on %r>' % (protocolName, self.port)\n        else:\n            return '<%s (not listening)>' % (protocolName,)\n\n\n    def _bindSocket(self):\n        log.msg(\"%s starting on %s\"%(self.protocol.__class__, repr(self.port)))\n        try:\n            skt = self.createInternetSocket() # XXX: haha misnamed method\n            if self.port:\n                skt.bind(self.port)\n        except socket.error as le:\n            raise error.CannotListenError(None, self.port, le)\n        if self.port and _inFilesystemNamespace(self.port):\n            # Make the socket readable and writable to the world.\n            os.chmod(self.port, self.mode)\n        self.connected = 1\n        self.socket = skt\n        self.fileno = self.socket.fileno\n\n    def write(self, datagram, address):\n        \"\"\"Write a datagram.\"\"\"\n        try:\n            return self.socket.sendto(datagram, address)\n        except socket.error as se:\n            no = se.args[0]\n            if no == EINTR:\n                return self.write(datagram, address)\n            elif no == EMSGSIZE:\n                raise error.MessageLengthError(\"message too long\")\n            elif no == EAGAIN:\n                # oh, well, drop the data. The only difference from UDP\n                # is that UDP won't ever notice.\n                # TODO: add TCP-like buffering\n                pass\n            else:\n                raise\n\n    def connectionLost(self, reason=None):\n        \"\"\"Cleans up my socket.\n        \"\"\"\n        log.msg('(Port %s Closed)' % repr(self.port))\n        base.BasePort.connectionLost(self, reason)\n        if hasattr(self, \"protocol\"):\n            # we won't have attribute in ConnectedPort, in cases\n            # where there was an error in connection process\n            self.protocol.doStop()\n        self.connected = 0\n        self.socket.close()\n        del self.socket\n        del self.fileno\n        if hasattr(self, \"d\"):\n            self.d.callback(None)\n            del self.d\n\n    def setLogStr(self):\n        self.logstr = reflect.qual(self.protocol.__class__) + \" (UDP)\"\n\n\n\n@implementer_only(interfaces.IUNIXDatagramConnectedTransport,\n                  *(implementedBy(base.BasePort)))\nclass ConnectedDatagramPort(DatagramPort):\n    \"\"\"\n    A connected datagram UNIX socket.\n    \"\"\"\n    def __init__(self, addr, proto, maxPacketSize=8192, mode=0o666,\n                 bindAddress=None, reactor=None):\n        assert isinstance(proto, protocol.ConnectedDatagramProtocol)\n        DatagramPort.__init__(self, bindAddress, proto, maxPacketSize, mode,\n                              reactor)\n        self.remoteaddr = addr\n\n\n    def startListening(self):\n        try:\n            self._bindSocket()\n            self.socket.connect(self.remoteaddr)\n            self._connectToProtocol()\n        except:\n            self.connectionFailed(failure.Failure())\n\n\n    def connectionFailed(self, reason):\n        \"\"\"\n        Called when a connection fails. Stop listening on the socket.\n\n        @type reason: L{Failure}\n        @param reason: Why the connection failed.\n        \"\"\"\n        self.stopListening()\n        self.protocol.connectionFailed(reason)\n        del self.protocol\n\n\n    def doRead(self):\n        \"\"\"\n        Called when my socket is ready for reading.\n        \"\"\"\n        read = 0\n        while read < self.maxThroughput:\n            try:\n                data, addr = self.socket.recvfrom(self.maxPacketSize)\n                read += len(data)\n                self.protocol.datagramReceived(data)\n            except socket.error as se:\n                no = se.args[0]\n                if no in (EAGAIN, EINTR, EWOULDBLOCK):\n                    return\n                if no == ECONNREFUSED:\n                    self.protocol.connectionRefused()\n                else:\n                    raise\n            except:\n                log.deferr()\n\n\n    def write(self, data):\n        \"\"\"\n        Write a datagram.\n        \"\"\"\n        try:\n            return self.socket.send(data)\n        except socket.error as se:\n            no = se.args[0]\n            if no == EINTR:\n                return self.write(data)\n            elif no == EMSGSIZE:\n                raise error.MessageLengthError(\"message too long\")\n            elif no == ECONNREFUSED:\n                self.protocol.connectionRefused()\n            elif no == EAGAIN:\n                # oh, well, drop the data. The only difference from UDP\n                # is that UDP won't ever notice.\n                # TODO: add TCP-like buffering\n                pass\n            else:\n                raise\n\n\n    def getPeer(self):\n        return address.UNIXAddress(self.remoteaddr)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/utils.py",
    "content": "# -*- test-case-name: twisted.test.test_iutils -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nUtility methods.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport sys, warnings\nfrom functools import wraps\n\nfrom twisted.internet import protocol, defer\nfrom twisted.python import failure\nfrom twisted.python.compat import reraise\n\nfrom io import BytesIO\n\n\n\ndef _callProtocolWithDeferred(protocol, executable, args, env, path,\n                              reactor=None, protoArgs=()):\n    if reactor is None:\n        from twisted.internet import reactor\n\n    d = defer.Deferred()\n    p = protocol(d, *protoArgs)\n    reactor.spawnProcess(p, executable, (executable,)+tuple(args), env, path)\n    return d\n\n\n\nclass _UnexpectedErrorOutput(IOError):\n    \"\"\"\n    Standard error data was received where it was not expected.  This is a\n    subclass of L{IOError} to preserve backward compatibility with the previous\n    error behavior of L{getProcessOutput}.\n\n    @ivar processEnded: A L{Deferred} which will fire when the process which\n        produced the data on stderr has ended (exited and all file descriptors\n        closed).\n    \"\"\"\n\n    def __init__(self, text, processEnded):\n        IOError.__init__(self, \"got stderr: %r\" % (text,))\n        self.processEnded = processEnded\n\n\n\nclass _BackRelay(protocol.ProcessProtocol):\n    \"\"\"\n    Trivial protocol for communicating with a process and turning its output\n    into the result of a L{Deferred}.\n\n    @ivar deferred: A L{Deferred} which will be called back with all of stdout\n        and, if C{errortoo} is true, all of stderr as well (mixed together in\n        one string).  If C{errortoo} is false and any bytes are received over\n        stderr, this will fire with an L{_UnexpectedErrorOutput} instance and\n        the attribute will be set to L{None}.\n\n    @ivar onProcessEnded: If C{errortoo} is false and bytes are received over\n        stderr, this attribute will refer to a L{Deferred} which will be called\n        back when the process ends.  This C{Deferred} is also associated with\n        the L{_UnexpectedErrorOutput} which C{deferred} fires with earlier in\n        this case so that users can determine when the process has actually\n        ended, in addition to knowing when bytes have been received via stderr.\n    \"\"\"\n\n    def __init__(self, deferred, errortoo=0):\n        self.deferred = deferred\n        self.s = BytesIO()\n        if errortoo:\n            self.errReceived = self.errReceivedIsGood\n        else:\n            self.errReceived = self.errReceivedIsBad\n\n    def errReceivedIsBad(self, text):\n        if self.deferred is not None:\n            self.onProcessEnded = defer.Deferred()\n            err = _UnexpectedErrorOutput(text, self.onProcessEnded)\n            self.deferred.errback(failure.Failure(err))\n            self.deferred = None\n            self.transport.loseConnection()\n\n    def errReceivedIsGood(self, text):\n        self.s.write(text)\n\n    def outReceived(self, text):\n        self.s.write(text)\n\n    def processEnded(self, reason):\n        if self.deferred is not None:\n            self.deferred.callback(self.s.getvalue())\n        elif self.onProcessEnded is not None:\n            self.onProcessEnded.errback(reason)\n\n\n\ndef getProcessOutput(executable, args=(), env={}, path=None, reactor=None,\n                     errortoo=0):\n    \"\"\"\n    Spawn a process and return its output as a deferred returning a L{bytes}.\n\n    @param executable: The file name to run and get the output of - the\n                       full path should be used.\n\n    @param args: the command line arguments to pass to the process; a\n                 sequence of strings. The first string should B{NOT} be the\n                 executable's name.\n\n    @param env: the environment variables to pass to the process; a\n                dictionary of strings.\n\n    @param path: the path to run the subprocess in - defaults to the\n                 current directory.\n\n    @param reactor: the reactor to use - defaults to the default reactor\n\n    @param errortoo: If true, include stderr in the result.  If false, if\n        stderr is received the returned L{Deferred} will errback with an\n        L{IOError} instance with a C{processEnded} attribute.  The\n        C{processEnded} attribute refers to a L{Deferred} which fires when the\n        executed process ends.\n    \"\"\"\n    return _callProtocolWithDeferred(lambda d:\n                                        _BackRelay(d, errortoo=errortoo),\n                                     executable, args, env, path,\n                                     reactor)\n\n\nclass _ValueGetter(protocol.ProcessProtocol):\n\n    def __init__(self, deferred):\n        self.deferred = deferred\n\n    def processEnded(self, reason):\n        self.deferred.callback(reason.value.exitCode)\n\n\n\ndef getProcessValue(executable, args=(), env={}, path=None, reactor=None):\n    \"\"\"Spawn a process and return its exit code as a Deferred.\"\"\"\n    return _callProtocolWithDeferred(_ValueGetter, executable, args, env, path,\n                                     reactor)\n\n\n\nclass _EverythingGetter(protocol.ProcessProtocol):\n\n    def __init__(self, deferred, stdinBytes=None):\n        self.deferred = deferred\n        self.outBuf = BytesIO()\n        self.errBuf = BytesIO()\n        self.outReceived = self.outBuf.write\n        self.errReceived = self.errBuf.write\n        self.stdinBytes = stdinBytes\n\n    def connectionMade(self):\n        if self.stdinBytes is not None:\n            self.transport.writeToChild(0, self.stdinBytes)\n            # The only compelling reason not to _always_ close stdin here is\n            # backwards compatibility.\n            self.transport.closeStdin()\n\n    def processEnded(self, reason):\n        out = self.outBuf.getvalue()\n        err = self.errBuf.getvalue()\n        e = reason.value\n        code = e.exitCode\n        if e.signal:\n            self.deferred.errback((out, err, e.signal))\n        else:\n            self.deferred.callback((out, err, code))\n\n\n\ndef getProcessOutputAndValue(executable, args=(), env={}, path=None,\n                             reactor=None, stdinBytes=None):\n    \"\"\"Spawn a process and returns a Deferred that will be called back with\n    its output (from stdout and stderr) and it's exit code as (out, err, code)\n    If a signal is raised, the Deferred will errback with the stdout and\n    stderr up to that point, along with the signal, as (out, err, signalNum)\n    \"\"\"\n    return _callProtocolWithDeferred(\n        _EverythingGetter,\n        executable,\n        args,\n        env,\n        path,\n        reactor,\n        protoArgs=(stdinBytes,),\n    )\n\n\n\ndef _resetWarningFilters(passthrough, addedFilters):\n    for f in addedFilters:\n        try:\n            warnings.filters.remove(f)\n        except ValueError:\n            pass\n    return passthrough\n\n\ndef runWithWarningsSuppressed(suppressedWarnings, f, *a, **kw):\n    \"\"\"Run the function C{f}, but with some warnings suppressed.\n\n    @param suppressedWarnings: A list of arguments to pass to filterwarnings.\n                               Must be a sequence of 2-tuples (args, kwargs).\n    @param f: A callable, followed by its arguments and keyword arguments\n    \"\"\"\n    for args, kwargs in suppressedWarnings:\n        warnings.filterwarnings(*args, **kwargs)\n    addedFilters = warnings.filters[:len(suppressedWarnings)]\n    try:\n        result = f(*a, **kw)\n    except:\n        exc_info = sys.exc_info()\n        _resetWarningFilters(None, addedFilters)\n        reraise(exc_info[1], exc_info[2])\n    else:\n        if isinstance(result, defer.Deferred):\n            result.addBoth(_resetWarningFilters, addedFilters)\n        else:\n            _resetWarningFilters(None, addedFilters)\n        return result\n\n\ndef suppressWarnings(f, *suppressedWarnings):\n    \"\"\"\n    Wrap C{f} in a callable which suppresses the indicated warnings before\n    invoking C{f} and unsuppresses them afterwards.  If f returns a Deferred,\n    warnings will remain suppressed until the Deferred fires.\n    \"\"\"\n    @wraps(f)\n    def warningSuppressingWrapper(*a, **kw):\n        return runWithWarningsSuppressed(suppressedWarnings, f, *a, **kw)\n    return warningSuppressingWrapper\n\n\n__all__ = [\n    \"runWithWarningsSuppressed\", \"suppressWarnings\",\n    \"getProcessOutput\", \"getProcessValue\", \"getProcessOutputAndValue\",\n    ]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/win32eventreactor.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nA win32event based implementation of the Twisted main loop.\n\nThis requires pywin32 (formerly win32all) or ActivePython to be installed.\n\nTo install the event loop (and you should do this before any connections,\nlisteners or connectors are added)::\n\n    from twisted.internet import win32eventreactor\n    win32eventreactor.install()\n\nLIMITATIONS:\n 1. WaitForMultipleObjects and thus the event loop can only handle 64 objects.\n 2. Process running has some problems (see L{twisted.internet.process} docstring).\n\n\nTODO:\n 1. Event loop handling of writes is *very* problematic (this is causing failed tests).\n    Switch to doing it the correct way, whatever that means (see below).\n 2. Replace icky socket loopback waker with event based waker (use dummyEvent object)\n 3. Switch everyone to using Free Software so we don't have to deal with proprietary APIs.\n\n\nALTERNATIVE SOLUTIONS:\n - IIRC, sockets can only be registered once. So we switch to a structure\n   like the poll() reactor, thus allowing us to deal with write events in\n   a decent fashion. This should allow us to pass tests, but we're still\n   limited to 64 events.\n\nOr:\n\n - Instead of doing a reactor, we make this an addon to the select reactor.\n   The WFMO event loop runs in a separate thread. This means no need to maintain\n   separate code for networking, 64 event limit doesn't apply to sockets,\n   we can run processes and other win32 stuff in default event loop. The\n   only problem is that we're stuck with the icky socket based waker.\n   Another benefit is that this could be extended to support >64 events\n   in a simpler manner than the previous solution.\n\nThe 2nd solution is probably what will get implemented.\n\"\"\"\n\n# System imports\nimport time\nimport sys\nfrom threading import Thread\nfrom weakref import WeakKeyDictionary\n\nfrom zope.interface import implementer\n\n# Win32 imports\nfrom win32file import FD_READ, FD_CLOSE, FD_ACCEPT, FD_CONNECT, WSAEventSelect\ntry:\n    # WSAEnumNetworkEvents was added in pywin32 215\n    from win32file import WSAEnumNetworkEvents\nexcept ImportError:\n    import warnings\n    warnings.warn(\n        'Reliable disconnection notification requires pywin32 215 or later',\n        category=UserWarning)\n    def WSAEnumNetworkEvents(fd, event):\n        return set([FD_READ])\n\nfrom win32event import CreateEvent, MsgWaitForMultipleObjects\nfrom win32event import WAIT_OBJECT_0, WAIT_TIMEOUT, QS_ALLINPUT\n\nimport win32gui\n\n# Twisted imports\nfrom twisted.internet import posixbase\nfrom twisted.python import log, threadable, failure\nfrom twisted.internet.interfaces import IReactorFDSet\nfrom twisted.internet.interfaces import IReactorWin32Events\nfrom twisted.internet.threads import blockingCallFromThread\n\n\n@implementer(IReactorFDSet, IReactorWin32Events)\nclass Win32Reactor(posixbase.PosixReactorBase):\n    \"\"\"\n    Reactor that uses Win32 event APIs.\n\n    @ivar _reads: A dictionary mapping L{FileDescriptor} instances to a\n        win32 event object used to check for read events for that descriptor.\n\n    @ivar _writes: A dictionary mapping L{FileDescriptor} instances to a\n        arbitrary value.  Keys in this dictionary will be given a chance to\n        write out their data.\n\n    @ivar _events: A dictionary mapping win32 event object to tuples of\n        L{FileDescriptor} instances and event masks.\n\n    @ivar _closedAndReading: Along with C{_closedAndNotReading}, keeps track of\n        descriptors which have had close notification delivered from the OS but\n        which we have not finished reading data from.  MsgWaitForMultipleObjects\n        will only deliver close notification to us once, so we remember it in\n        these two dictionaries until we're ready to act on it.  The OS has\n        delivered close notification for each descriptor in this dictionary, and\n        the descriptors are marked as allowed to handle read events in the\n        reactor, so they can be processed.  When a descriptor is marked as not\n        allowed to handle read events in the reactor (ie, it is passed to\n        L{IReactorFDSet.removeReader}), it is moved out of this dictionary and\n        into C{_closedAndNotReading}.  The descriptors are keys in this\n        dictionary.  The values are arbitrary.\n    @type _closedAndReading: C{dict}\n\n    @ivar _closedAndNotReading: These descriptors have had close notification\n        delivered from the OS, but are not marked as allowed to handle read\n        events in the reactor.  They are saved here to record their closed\n        state, but not processed at all.  When one of these descriptors is\n        passed to L{IReactorFDSet.addReader}, it is moved out of this dictionary\n        and into C{_closedAndReading}.  The descriptors are keys in this\n        dictionary.  The values are arbitrary.  This is a weak key dictionary so\n        that if an application tells the reactor to stop reading from a\n        descriptor and then forgets about that descriptor itself, the reactor\n        will also forget about it.\n    @type _closedAndNotReading: C{WeakKeyDictionary}\n    \"\"\"\n    dummyEvent = CreateEvent(None, 0, 0, None)\n\n    def __init__(self):\n        self._reads = {}\n        self._writes = {}\n        self._events = {}\n        self._closedAndReading = {}\n        self._closedAndNotReading = WeakKeyDictionary()\n        posixbase.PosixReactorBase.__init__(self)\n\n\n    def _makeSocketEvent(self, fd, action, why):\n        \"\"\"\n        Make a win32 event object for a socket.\n        \"\"\"\n        event = CreateEvent(None, 0, 0, None)\n        WSAEventSelect(fd, event, why)\n        self._events[event] = (fd, action)\n        return event\n\n\n    def addEvent(self, event, fd, action):\n        \"\"\"\n        Add a new win32 event to the event loop.\n        \"\"\"\n        self._events[event] = (fd, action)\n\n\n    def removeEvent(self, event):\n        \"\"\"\n        Remove an event.\n        \"\"\"\n        del self._events[event]\n\n\n    def addReader(self, reader):\n        \"\"\"\n        Add a socket FileDescriptor for notification of data available to read.\n        \"\"\"\n        if reader not in self._reads:\n            self._reads[reader] = self._makeSocketEvent(\n                reader, 'doRead', FD_READ | FD_ACCEPT | FD_CONNECT | FD_CLOSE)\n            # If the reader is closed, move it over to the dictionary of reading\n            # descriptors.\n            if reader in self._closedAndNotReading:\n                self._closedAndReading[reader] = True\n                del self._closedAndNotReading[reader]\n\n\n    def addWriter(self, writer):\n        \"\"\"\n        Add a socket FileDescriptor for notification of data available to write.\n        \"\"\"\n        if writer not in self._writes:\n            self._writes[writer] = 1\n\n\n    def removeReader(self, reader):\n        \"\"\"Remove a Selectable for notification of data available to read.\n        \"\"\"\n        if reader in self._reads:\n            del self._events[self._reads[reader]]\n            del self._reads[reader]\n\n            # If the descriptor is closed, move it out of the dictionary of\n            # reading descriptors into the dictionary of waiting descriptors.\n            if reader in self._closedAndReading:\n                self._closedAndNotReading[reader] = True\n                del self._closedAndReading[reader]\n\n\n    def removeWriter(self, writer):\n        \"\"\"Remove a Selectable for notification of data available to write.\n        \"\"\"\n        if writer in self._writes:\n            del self._writes[writer]\n\n\n    def removeAll(self):\n        \"\"\"\n        Remove all selectables, and return a list of them.\n        \"\"\"\n        return self._removeAll(self._reads, self._writes)\n\n\n    def getReaders(self):\n        return list(self._reads.keys())\n\n\n    def getWriters(self):\n        return list(self._writes.keys())\n\n\n    def doWaitForMultipleEvents(self, timeout):\n        log.msg(channel='system', event='iteration', reactor=self)\n        if timeout is None:\n            timeout = 100\n\n        # Keep track of whether we run any application code before we get to the\n        # MsgWaitForMultipleObjects.  If so, there's a chance it will schedule a\n        # new timed call or stop the reactor or do something else that means we\n        # shouldn't block in MsgWaitForMultipleObjects for the full timeout.\n        ranUserCode = False\n\n        # If any descriptors are trying to close, try to get them out of the way\n        # first.\n        for reader in list(self._closedAndReading.keys()):\n            ranUserCode = True\n            self._runAction('doRead', reader)\n\n        for fd in list(self._writes.keys()):\n            ranUserCode = True\n            log.callWithLogger(fd, self._runWrite, fd)\n\n        if ranUserCode:\n            # If application code *might* have scheduled an event, assume it\n            # did.  If we're wrong, we'll get back here shortly anyway.  If\n            # we're right, we'll be sure to handle the event (including reactor\n            # shutdown) in a timely manner.\n            timeout = 0\n\n        if not (self._events or self._writes):\n            # sleep so we don't suck up CPU time\n            time.sleep(timeout)\n            return\n\n        handles = list(self._events.keys()) or [self.dummyEvent]\n        timeout = int(timeout * 1000)\n        val = MsgWaitForMultipleObjects(handles, 0, timeout, QS_ALLINPUT)\n        if val == WAIT_TIMEOUT:\n            return\n        elif val == WAIT_OBJECT_0 + len(handles):\n            exit = win32gui.PumpWaitingMessages()\n            if exit:\n                self.callLater(0, self.stop)\n                return\n        elif val >= WAIT_OBJECT_0 and val < WAIT_OBJECT_0 + len(handles):\n            event = handles[val - WAIT_OBJECT_0]\n            fd, action = self._events[event]\n\n            if fd in self._reads:\n                # Before anything, make sure it's still a valid file descriptor.\n                fileno = fd.fileno()\n                if fileno == -1:\n                    self._disconnectSelectable(fd, posixbase._NO_FILEDESC, False)\n                    return\n\n                # Since it's a socket (not another arbitrary event added via\n                # addEvent) and we asked for FD_READ | FD_CLOSE, check to see if\n                # we actually got FD_CLOSE.  This needs a special check because\n                # it only gets delivered once.  If we miss it, it's gone forever\n                # and we'll never know that the connection is closed.\n                events = WSAEnumNetworkEvents(fileno, event)\n                if FD_CLOSE in events:\n                    self._closedAndReading[fd] = True\n            log.callWithLogger(fd, self._runAction, action, fd)\n\n\n    def _runWrite(self, fd):\n        closed = 0\n        try:\n            closed = fd.doWrite()\n        except:\n            closed = sys.exc_info()[1]\n            log.deferr()\n\n        if closed:\n            self.removeReader(fd)\n            self.removeWriter(fd)\n            try:\n                fd.connectionLost(failure.Failure(closed))\n            except:\n                log.deferr()\n        elif closed is None:\n            return 1\n\n    def _runAction(self, action, fd):\n        try:\n            closed = getattr(fd, action)()\n        except:\n            closed = sys.exc_info()[1]\n            log.deferr()\n        if closed:\n            self._disconnectSelectable(fd, closed, action == 'doRead')\n\n    doIteration = doWaitForMultipleEvents\n\n\n\nclass _ThreadFDWrapper(object):\n    \"\"\"\n    This wraps an event handler and translates notification in the helper\n    L{Win32Reactor} thread into a notification in the primary reactor thread.\n\n    @ivar _reactor: The primary reactor, the one to which event notification\n        will be sent.\n\n    @ivar _fd: The L{FileDescriptor} to which the event will be dispatched.\n\n    @ivar _action: A C{str} giving the method of C{_fd} which handles the event.\n\n    @ivar _logPrefix: The pre-fetched log prefix string for C{_fd}, so that\n        C{_fd.logPrefix} does not need to be called in a non-main thread.\n    \"\"\"\n    def __init__(self, reactor, fd, action, logPrefix):\n        self._reactor = reactor\n        self._fd = fd\n        self._action = action\n        self._logPrefix = logPrefix\n\n\n    def logPrefix(self):\n        \"\"\"\n        Return the original handler's log prefix, as it was given to\n        C{__init__}.\n        \"\"\"\n        return self._logPrefix\n\n\n    def _execute(self):\n        \"\"\"\n        Callback fired when the associated event is set.  Run the C{action}\n        callback on the wrapped descriptor in the main reactor thread and raise\n        or return whatever it raises or returns to cause this event handler to\n        be removed from C{self._reactor} if appropriate.\n        \"\"\"\n        return blockingCallFromThread(\n            self._reactor, lambda: getattr(self._fd, self._action)())\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Pass through to the wrapped descriptor, but in the main reactor thread\n        instead of the helper C{Win32Reactor} thread.\n        \"\"\"\n        self._reactor.callFromThread(self._fd.connectionLost, reason)\n\n\n\n@implementer(IReactorWin32Events)\nclass _ThreadedWin32EventsMixin(object):\n    \"\"\"\n    This mixin implements L{IReactorWin32Events} for another reactor by running\n    a L{Win32Reactor} in a separate thread and dispatching work to it.\n\n    @ivar _reactor: The L{Win32Reactor} running in the other thread.  This is\n        L{None} until it is actually needed.\n\n    @ivar _reactorThread: The L{threading.Thread} which is running the\n        L{Win32Reactor}.  This is L{None} until it is actually needed.\n    \"\"\"\n\n    _reactor = None\n    _reactorThread = None\n\n\n    def _unmakeHelperReactor(self):\n        \"\"\"\n        Stop and discard the reactor started by C{_makeHelperReactor}.\n        \"\"\"\n        self._reactor.callFromThread(self._reactor.stop)\n        self._reactor = None\n\n\n    def _makeHelperReactor(self):\n        \"\"\"\n        Create and (in a new thread) start a L{Win32Reactor} instance to use for\n        the implementation of L{IReactorWin32Events}.\n        \"\"\"\n        self._reactor = Win32Reactor()\n        # This is a helper reactor, it is not the global reactor and its thread\n        # is not \"the\" I/O thread.  Prevent it from registering it as such.\n        self._reactor._registerAsIOThread = False\n        self._reactorThread = Thread(\n            target=self._reactor.run, args=(False,))\n        self.addSystemEventTrigger(\n            'after', 'shutdown', self._unmakeHelperReactor)\n        self._reactorThread.start()\n\n\n    def addEvent(self, event, fd, action):\n        \"\"\"\n        @see: L{IReactorWin32Events}\n        \"\"\"\n        if self._reactor is None:\n            self._makeHelperReactor()\n        self._reactor.callFromThread(\n            self._reactor.addEvent,\n            event, _ThreadFDWrapper(self, fd, action, fd.logPrefix()),\n            \"_execute\")\n\n\n    def removeEvent(self, event):\n        \"\"\"\n        @see: L{IReactorWin32Events}\n        \"\"\"\n        self._reactor.callFromThread(self._reactor.removeEvent, event)\n\n\n\ndef install():\n    threadable.init(1)\n    r = Win32Reactor()\n    from . import main\n    main.installReactor(r)\n\n\n__all__ = [\"Win32Reactor\", \"install\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/wxreactor.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module provides wxPython event loop support for Twisted.\n\nIn order to use this support, simply do the following::\n\n    |  from twisted.internet import wxreactor\n    |  wxreactor.install()\n\nThen, when your root wxApp has been created::\n\n    | from twisted.internet import reactor\n    | reactor.registerWxApp(yourApp)\n    | reactor.run()\n\nThen use twisted.internet APIs as usual. Stop the event loop using\nreactor.stop(), not yourApp.ExitMainLoop().\n\nIMPORTANT: tests will fail when run under this reactor. This is\nexpected and probably does not reflect on the reactor's ability to run\nreal applications.\n\"\"\"\n\ntry:\n    from queue import Empty, Queue\nexcept ImportError:\n    from Queue import Empty, Queue\n\ntry:\n    from wx import PySimpleApp as wxPySimpleApp, CallAfter as wxCallAfter, \\\n         Timer as wxTimer\nexcept ImportError:\n    # older version of wxPython:\n    from wxPython.wx import wxPySimpleApp, wxCallAfter, wxTimer\n\nfrom twisted.python import log, runtime\nfrom twisted.internet import _threadedselect\n\n\nclass ProcessEventsTimer(wxTimer):\n    \"\"\"\n    Timer that tells wx to process pending events.\n\n    This is necessary on macOS, probably due to a bug in wx, if we want\n    wxCallAfters to be handled when modal dialogs, menus, etc.  are open.\n    \"\"\"\n    def __init__(self, wxapp):\n        wxTimer.__init__(self)\n        self.wxapp = wxapp\n    \n\n    def Notify(self):\n        \"\"\"\n        Called repeatedly by wx event loop.\n        \"\"\"\n        self.wxapp.ProcessPendingEvents()\n\n\n\nclass WxReactor(_threadedselect.ThreadedSelectReactor):\n    \"\"\"\n    wxPython reactor.\n\n    wxPython drives the event loop, select() runs in a thread.\n    \"\"\"\n\n    _stopping = False\n\n    def registerWxApp(self, wxapp):\n        \"\"\"\n        Register wxApp instance with the reactor.\n        \"\"\"\n        self.wxapp = wxapp\n\n\n    def _installSignalHandlersAgain(self):\n        \"\"\"\n        wx sometimes removes our own signal handlers, so re-add them.\n        \"\"\"\n        try:\n            # make _handleSignals happy:\n            import signal\n            signal.signal(signal.SIGINT, signal.default_int_handler)\n        except ImportError:\n            return\n        self._handleSignals()\n\n\n    def stop(self):\n        \"\"\"\n        Stop the reactor.\n        \"\"\"\n        if self._stopping:\n            return\n        self._stopping = True\n        _threadedselect.ThreadedSelectReactor.stop(self)\n\n\n    def _runInMainThread(self, f):\n        \"\"\"\n        Schedule function to run in main wx/Twisted thread.\n\n        Called by the select() thread.\n        \"\"\"\n        if hasattr(self, \"wxapp\"):\n            wxCallAfter(f)\n        else:\n            # wx shutdown but twisted hasn't\n            self._postQueue.put(f)\n\n\n    def _stopWx(self):\n        \"\"\"\n        Stop the wx event loop if it hasn't already been stopped.\n\n        Called during Twisted event loop shutdown.\n        \"\"\"\n        if hasattr(self, \"wxapp\"):\n            self.wxapp.ExitMainLoop()\n\n\n    def run(self, installSignalHandlers=True):\n        \"\"\"\n        Start the reactor.\n        \"\"\"\n        self._postQueue = Queue()\n        if not hasattr(self, \"wxapp\"):\n            log.msg(\"registerWxApp() was not called on reactor, \"\n                    \"registering my own wxApp instance.\")\n            self.registerWxApp(wxPySimpleApp())\n\n        # start select() thread:\n        self.interleave(self._runInMainThread,\n                        installSignalHandlers=installSignalHandlers)\n        if installSignalHandlers:\n            self.callLater(0, self._installSignalHandlersAgain)\n\n        # add cleanup events:\n        self.addSystemEventTrigger(\"after\", \"shutdown\", self._stopWx)\n        self.addSystemEventTrigger(\"after\", \"shutdown\",\n                                   lambda: self._postQueue.put(None))\n\n        # On macOS, work around wx bug by starting timer to ensure\n        # wxCallAfter calls are always processed. We don't wake up as\n        # often as we could since that uses too much CPU.\n        if runtime.platform.isMacOSX():\n            t = ProcessEventsTimer(self.wxapp)\n            t.Start(2) # wake up every 2ms\n\n        self.wxapp.MainLoop()\n        wxapp = self.wxapp\n        del self.wxapp\n\n        if not self._stopping:\n            # wx event loop exited without reactor.stop() being\n            # called.  At this point events from select() thread will\n            # be added to _postQueue, but some may still be waiting\n            # unprocessed in wx, thus the ProcessPendingEvents()\n            # below.\n            self.stop()\n            wxapp.ProcessPendingEvents() # deal with any queued wxCallAfters\n            while 1:\n                try:\n                    f = self._postQueue.get(timeout=0.01)\n                except Empty:\n                    continue\n                else:\n                    if f is None:\n                        break\n                    try:\n                        f()\n                    except:\n                        log.err()\n\n\ndef install():\n    \"\"\"\n    Configure the twisted mainloop to be run inside the wxPython mainloop.\n    \"\"\"\n    reactor = WxReactor()\n    from twisted.internet.main import installReactor\n    installReactor(reactor)\n    return reactor\n\n\n__all__ = ['install']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/internet/wxsupport.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n#\n\"\"\"Old method of wxPython support for Twisted.\n\ntwisted.internet.wxreactor is probably a better choice.\n\nTo use::\n\n    | # given a wxApp instance called myWxAppInstance:\n    | from twisted.internet import wxsupport\n    | wxsupport.install(myWxAppInstance)\n\nUse Twisted's APIs for running and stopping the event loop, don't use\nwxPython's methods.\n\nOn Windows the Twisted event loop might block when dialogs are open\nor menus are selected.\n\nMaintainer: Itamar Shtull-Trauring\n\"\"\"\n\nimport warnings\nwarnings.warn(\"wxsupport is not fully functional on Windows, wxreactor is better.\")\n\nfrom twisted.python._oldstyle import _oldStyle\nfrom twisted.internet import reactor\n\n\n\n@_oldStyle\nclass wxRunner:\n    \"\"\"Make sure GUI events are handled.\"\"\"\n\n    def __init__(self, app):\n        self.app = app\n\n    def run(self):\n        \"\"\"\n        Execute pending WX events followed by WX idle events and\n        reschedule.\n        \"\"\"\n        # run wx events\n        while self.app.Pending():\n            self.app.Dispatch()\n\n        # run wx idle events\n        self.app.ProcessIdle()\n        reactor.callLater(0.02, self.run)\n\n\ndef install(app):\n    \"\"\"Install the wxPython support, given a wxApp instance\"\"\"\n    runner = wxRunner(app)\n    reactor.callLater(0.02, runner.run)\n\n\n__all__ = [\"install\"]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/__init__.py",
    "content": "# -*- test-case-name: twisted.logger.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTwisted Logger: Classes and functions to do granular logging.\n\nExample usage in a module C{some.module}::\n\n    from twisted.logger import Logger\n    log = Logger()\n\n    def handleData(data):\n        log.debug(\"Got data: {data!r}.\", data=data)\n\nOr in a class::\n\n    from twisted.logger import Logger\n\n    class Foo(object):\n        log = Logger()\n\n        def oops(self, data):\n            self.log.error(\"Oops! Invalid data from server: {data!r}\",\n                           data=data)\n\nC{Logger}s have namespaces, for which logging can be configured independently.\nNamespaces may be specified by passing in a C{namespace} argument to L{Logger}\nwhen instantiating it, but if none is given, the logger will derive its own\nnamespace by using the module name of the callable that instantiated it, or, in\nthe case of a class, by using the fully qualified name of the class.\n\nIn the first example above, the namespace would be C{some.module}, and in the\nsecond example, it would be C{some.module.Foo}.\n\n@var globalLogPublisher: The L{LogPublisher} that all L{Logger} instances that\n    are not otherwise parameterized will point to by default.\n@type globalLogPublisher: L{LogPublisher}\n\n@var globalLogBeginner: The L{LogBeginner} used to activate the main log\n    observer, whether it's a log file, or an observer pointing at stderr.\n@type globalLogBeginner: L{LogBeginner}\n\"\"\"\n\n__all__ = [\n    # From ._levels\n    \"InvalidLogLevelError\", \"LogLevel\",\n\n    # From ._format\n    \"formatEvent\", \"formatEventAsClassicLogText\",\n    \"formatTime\", \"timeFormatRFC3339\",\n    \"eventAsText\",\n\n    # From ._flatten\n    \"extractField\",\n\n    # From ._logger\n    \"Logger\", \"_loggerFor\",\n\n    # From ._observer\n    \"ILogObserver\", \"LogPublisher\",\n\n    # From ._buffer\n    \"LimitedHistoryLogObserver\",\n\n    # From ._file\n    \"FileLogObserver\", \"textFileLogObserver\",\n\n    # From ._filter\n    \"PredicateResult\", \"ILogFilterPredicate\",\n    \"FilteringLogObserver\", \"LogLevelFilterPredicate\",\n\n    # From ._stdlib\n    \"STDLibLogObserver\",\n\n    # From ._io\n    \"LoggingFile\",\n\n    # From ._legacy\n    \"LegacyLogObserverWrapper\",\n\n    # From ._global\n    \"globalLogPublisher\", \"globalLogBeginner\", \"LogBeginner\",\n\n    # From ._json\n    \"eventAsJSON\", \"eventFromJSON\",\n    \"jsonFileLogObserver\", \"eventsFromJSONLogFile\",\n\n    # From ._capture\n    \"capturedLogs\",\n]\n\nfrom ._levels import InvalidLogLevelError, LogLevel\n\nfrom ._flatten import extractField\n\nfrom ._format import (\n    formatEvent, formatEventAsClassicLogText, formatTime, timeFormatRFC3339,\n    eventAsText\n)\n\nfrom ._logger import Logger, _loggerFor\n\nfrom ._observer import ILogObserver, LogPublisher\n\nfrom ._buffer import LimitedHistoryLogObserver\n\nfrom ._file import FileLogObserver, textFileLogObserver\n\nfrom ._filter import (\n    PredicateResult, ILogFilterPredicate, FilteringLogObserver,\n    LogLevelFilterPredicate\n)\n\nfrom ._stdlib import STDLibLogObserver\n\nfrom ._io import LoggingFile\n\nfrom ._legacy import LegacyLogObserverWrapper\n\nfrom ._global import (\n    globalLogPublisher, globalLogBeginner, LogBeginner\n)\n\nfrom ._json import (\n    eventAsJSON, eventFromJSON,\n    jsonFileLogObserver, eventsFromJSONLogFile\n)\n\nfrom ._capture import capturedLogs\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_buffer.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_buffer -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nLog observer that maintains a buffer.\n\"\"\"\n\nfrom collections import deque\n\nfrom zope.interface import implementer\n\nfrom ._observer import ILogObserver\n\n\n_DEFAULT_BUFFER_MAXIMUM = 64 * 1024\n\n\n\n@implementer(ILogObserver)\nclass LimitedHistoryLogObserver(object):\n    \"\"\"\n    L{ILogObserver} that stores events in a buffer of a fixed size::\n\n        >>> from twisted.logger import LimitedHistoryLogObserver\n        >>> history = LimitedHistoryLogObserver(5)\n        >>> for n in range(10): history({'n': n})\n        ...\n        >>> repeats = []\n        >>> history.replayTo(repeats.append)\n        >>> len(repeats)\n        5\n        >>> repeats\n        [{'n': 5}, {'n': 6}, {'n': 7}, {'n': 8}, {'n': 9}]\n        >>>\n    \"\"\"\n\n    def __init__(self, size=_DEFAULT_BUFFER_MAXIMUM):\n        \"\"\"\n        @param size: The maximum number of events to buffer.  If L{None}, the\n            buffer is unbounded.\n        @type size: L{int}\n        \"\"\"\n        self._buffer = deque(maxlen=size)\n\n\n    def __call__(self, event):\n        self._buffer.append(event)\n\n\n    def replayTo(self, otherObserver):\n        \"\"\"\n        Re-play the buffered events to another log observer.\n\n        @param otherObserver: An observer to replay events to.\n        @type otherObserver: L{ILogObserver}\n        \"\"\"\n        for event in self._buffer:\n            otherObserver(event)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_capture.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_capture -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nContext manager for capturing logs.\n\"\"\"\n\nfrom contextlib import contextmanager\n\nfrom twisted.logger import globalLogPublisher\n\n\n\n@contextmanager\ndef capturedLogs():\n    events = []\n    observer = events.append\n\n    globalLogPublisher.addObserver(observer)\n\n    yield events\n\n    globalLogPublisher.removeObserver(observer)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_filter.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_filter -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nFiltering log observer.\n\"\"\"\n\nfrom functools import partial\n\nfrom zope.interface import Interface, implementer\n\nfrom constantly import NamedConstant, Names\n\nfrom ._levels import InvalidLogLevelError, LogLevel\nfrom ._observer import ILogObserver\n\n\n\nclass PredicateResult(Names):\n    \"\"\"\n    Predicate results.\n\n    @see: L{LogLevelFilterPredicate}\n\n    @cvar yes: Log the specified event.  When this value is used,\n        L{FilteringLogObserver} will always log the message, without\n        evaluating other predicates.\n\n    @cvar no: Do not log the specified event.  When this value is used,\n        L{FilteringLogObserver} will I{not} log the message, without\n        evaluating other predicates.\n\n    @cvar maybe: Do not have an opinion on the event.  When this value is used,\n        L{FilteringLogObserver} will consider subsequent predicate results;\n        if returned by the last predicate being considered, then the event will\n        be logged.\n    \"\"\"\n    yes = NamedConstant()\n    no = NamedConstant()\n    maybe = NamedConstant()\n\n\n\nclass ILogFilterPredicate(Interface):\n    \"\"\"\n    A predicate that determined whether an event should be logged.\n    \"\"\"\n\n    def __call__(event):\n        \"\"\"\n        Determine whether an event should be logged.\n\n        @returns: a L{PredicateResult}.\n        \"\"\"\n\n\n\ndef shouldLogEvent(predicates, event):\n    \"\"\"\n    Determine whether an event should be logged, based on the result of\n    C{predicates}.\n\n    By default, the result is C{True}; so if there are no predicates,\n    everything will be logged.\n\n    If any predicate returns C{yes}, then we will immediately return C{True}.\n\n    If any predicate returns C{no}, then we will immediately return C{False}.\n\n    As predicates return C{maybe}, we keep calling the next predicate until we\n    run out, at which point we return C{True}.\n\n    @param predicates: The predicates to use.\n    @type predicates: iterable of L{ILogFilterPredicate}\n\n    @param event: An event\n    @type event: L{dict}\n\n    @return: True if the message should be forwarded on, C{False} if not.\n    @rtype: L{bool}\n    \"\"\"\n    for predicate in predicates:\n        result = predicate(event)\n        if result == PredicateResult.yes:\n            return True\n        if result == PredicateResult.no:\n            return False\n        if result == PredicateResult.maybe:\n            continue\n        raise TypeError(\"Invalid predicate result: {0!r}\".format(result))\n    return True\n\n\n\n@implementer(ILogObserver)\nclass FilteringLogObserver(object):\n    \"\"\"\n    L{ILogObserver} that wraps another L{ILogObserver}, but filters out events\n    based on applying a series of L{ILogFilterPredicate}s.\n    \"\"\"\n\n    def __init__(\n        self, observer, predicates,\n        negativeObserver=lambda event: None\n    ):\n        \"\"\"\n        @param observer: An observer to which this observer will forward\n            events when C{predictates} yield a positive result.\n        @type observer: L{ILogObserver}\n\n        @param predicates: Predicates to apply to events before forwarding to\n            the wrapped observer.\n        @type predicates: ordered iterable of predicates\n\n        @param negativeObserver: An observer to which this observer will\n            forward events when C{predictates} yield a negative result.\n        @type negativeObserver: L{ILogObserver}\n        \"\"\"\n        self._observer = observer\n        self._shouldLogEvent = partial(shouldLogEvent, list(predicates))\n        self._negativeObserver = negativeObserver\n\n\n    def __call__(self, event):\n        \"\"\"\n        Forward to next observer if predicate allows it.\n        \"\"\"\n        if self._shouldLogEvent(event):\n            if \"log_trace\" in event:\n                event[\"log_trace\"].append((self, self.observer))\n            self._observer(event)\n        else:\n            self._negativeObserver(event)\n\n\n\n@implementer(ILogFilterPredicate)\nclass LogLevelFilterPredicate(object):\n    \"\"\"\n    L{ILogFilterPredicate} that filters out events with a log level lower than\n    the log level for the event's namespace.\n\n    Events that not not have a log level or namespace are also dropped.\n    \"\"\"\n\n    def __init__(self, defaultLogLevel=LogLevel.info):\n        \"\"\"\n        @param defaultLogLevel: The default minimum log level.\n        @type defaultLogLevel: L{LogLevel}\n        \"\"\"\n        self._logLevelsByNamespace = {}\n        self.defaultLogLevel = defaultLogLevel\n        self.clearLogLevels()\n\n\n    def logLevelForNamespace(self, namespace):\n        \"\"\"\n        Determine an appropriate log level for the given namespace.\n\n        This respects dots in namespaces; for example, if you have previously\n        invoked C{setLogLevelForNamespace(\"mypackage\", LogLevel.debug)}, then\n        C{logLevelForNamespace(\"mypackage.subpackage\")} will return\n        C{LogLevel.debug}.\n\n        @param namespace: A logging namespace, or L{None} for the default\n            namespace.\n        @type namespace: L{str} (native string)\n\n        @return: The log level for the specified namespace.\n        @rtype: L{LogLevel}\n        \"\"\"\n        if not namespace:\n            return self._logLevelsByNamespace[None]\n\n        if namespace in self._logLevelsByNamespace:\n            return self._logLevelsByNamespace[namespace]\n\n        segments = namespace.split(\".\")\n        index = len(segments) - 1\n\n        while index > 0:\n            namespace = \".\".join(segments[:index])\n            if namespace in self._logLevelsByNamespace:\n                return self._logLevelsByNamespace[namespace]\n            index -= 1\n\n        return self._logLevelsByNamespace[None]\n\n\n    def setLogLevelForNamespace(self, namespace, level):\n        \"\"\"\n        Sets the log level for a logging namespace.\n\n        @param namespace: A logging namespace.\n        @type namespace: L{str} (native string)\n\n        @param level: The log level for the given namespace.\n        @type level: L{LogLevel}\n        \"\"\"\n        if level not in LogLevel.iterconstants():\n            raise InvalidLogLevelError(level)\n\n        if namespace:\n            self._logLevelsByNamespace[namespace] = level\n        else:\n            self._logLevelsByNamespace[None] = level\n\n\n    def clearLogLevels(self):\n        \"\"\"\n        Clears all log levels to the default.\n        \"\"\"\n        self._logLevelsByNamespace.clear()\n        self._logLevelsByNamespace[None] = self.defaultLogLevel\n\n\n    def __call__(self, event):\n        eventLevel     = event.get(\"log_level\", None)\n        namespace = event.get(\"log_namespace\", None)\n        namespaceLevel = self.logLevelForNamespace(namespace)\n\n        if (\n            eventLevel is None or\n            namespace is None or\n            LogLevel._priorityForLevel(eventLevel) <\n            LogLevel._priorityForLevel(namespaceLevel)\n        ):\n            return PredicateResult.no\n\n        return PredicateResult.maybe\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_format.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_format -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTools for formatting logging events.\n\"\"\"\n\nfrom datetime import datetime as DateTime\n\nfrom twisted.python.compat import unicode\nfrom twisted.python.failure import Failure\nfrom twisted.python.reflect import safe_repr\nfrom twisted.python._tzhelper import FixedOffsetTimeZone\n\nfrom ._flatten import flatFormat, aFormatter\n\ntimeFormatRFC3339 = \"%Y-%m-%dT%H:%M:%S%z\"\n\n\n\ndef formatEvent(event):\n    \"\"\"\n    Formats an event as a L{unicode}, using the format in\n    C{event[\"log_format\"]}.\n\n    This implementation should never raise an exception; if the formatting\n    cannot be done, the returned string will describe the event generically so\n    that a useful message is emitted regardless.\n\n    @param event: A logging event.\n    @type event: L{dict}\n\n    @return: A formatted string.\n    @rtype: L{unicode}\n    \"\"\"\n    return eventAsText(\n        event,\n        includeTraceback=False,\n        includeTimestamp=False,\n        includeSystem=False,\n    )\n\n\n\ndef formatUnformattableEvent(event, error):\n    \"\"\"\n    Formats an event as a L{unicode} that describes the event generically and a\n    formatting error.\n\n    @param event: A logging event.\n    @type event: L{dict}\n\n    @param error: The formatting error.\n    @type error: L{Exception}\n\n    @return: A formatted string.\n    @rtype: L{unicode}\n    \"\"\"\n    try:\n        return (\n            u\"Unable to format event {event!r}: {error}\"\n            .format(event=event, error=error)\n        )\n    except BaseException:\n        # Yikes, something really nasty happened.\n        #\n        # Try to recover as much formattable data as possible; hopefully at\n        # least the namespace is sane, which will help you find the offending\n        # logger.\n        failure = Failure()\n\n        text = u\", \".join(\n            u\" = \".join((safe_repr(key), safe_repr(value)))\n            for key, value in event.items()\n        )\n\n        return (\n            u\"MESSAGE LOST: unformattable object logged: {error}\\n\"\n            u\"Recoverable data: {text}\\n\"\n            u\"Exception during formatting:\\n{failure}\"\n            .format(error=safe_repr(error), failure=failure, text=text)\n        )\n\n\n\ndef formatTime(when, timeFormat=timeFormatRFC3339, default=u\"-\"):\n    \"\"\"\n    Format a timestamp as text.\n\n    Example::\n\n        >>> from time import time\n        >>> from twisted.logger import formatTime\n        >>>\n        >>> t = time()\n        >>> formatTime(t)\n        u'2013-10-22T14:19:11-0700'\n        >>> formatTime(t, timeFormat=\"%Y/%W\")  # Year and week number\n        u'2013/42'\n        >>>\n\n    @param when: A timestamp.\n    @type then: L{float}\n\n    @param timeFormat: A time format.\n    @type timeFormat: L{unicode} or L{None}\n\n    @param default: Text to return if C{when} or C{timeFormat} is L{None}.\n    @type default: L{unicode}\n\n    @return: A formatted time.\n    @rtype: L{unicode}\n    \"\"\"\n    if (timeFormat is None or when is None):\n        return default\n    else:\n        tz = FixedOffsetTimeZone.fromLocalTimeStamp(when)\n        datetime = DateTime.fromtimestamp(when, tz)\n        return unicode(datetime.strftime(timeFormat))\n\n\n\ndef formatEventAsClassicLogText(event, formatTime=formatTime):\n    \"\"\"\n    Format an event as a line of human-readable text for, e.g. traditional log\n    file output.\n\n    The output format is C{u\"{timeStamp} [{system}] {event}\\\\n\"}, where:\n\n        - C{timeStamp} is computed by calling the given C{formatTime} callable\n          on the event's C{\"log_time\"} value\n\n        - C{system} is the event's C{\"log_system\"} value, if set, otherwise,\n          the C{\"log_namespace\"} and C{\"log_level\"}, joined by a C{u\"#\"}.  Each\n          defaults to C{u\"-\"} is not set.\n\n        - C{event} is the event, as formatted by L{formatEvent}.\n\n    Example::\n\n        >>> from __future__ import print_function\n        >>> from time import time\n        >>> from twisted.logger import formatEventAsClassicLogText\n        >>> from twisted.logger import LogLevel\n        >>>\n        >>> formatEventAsClassicLogText(dict())  # No format, returns None\n        >>> formatEventAsClassicLogText(dict(log_format=u\"Hello!\"))\n        u'- [-#-] Hello!\\\\n'\n        >>> formatEventAsClassicLogText(dict(\n        ...     log_format=u\"Hello!\",\n        ...     log_time=time(),\n        ...     log_namespace=\"my_namespace\",\n        ...     log_level=LogLevel.info,\n        ... ))\n        u'2013-10-22T17:30:02-0700 [my_namespace#info] Hello!\\\\n'\n        >>> formatEventAsClassicLogText(dict(\n        ...     log_format=u\"Hello!\",\n        ...     log_time=time(),\n        ...     log_system=\"my_system\",\n        ... ))\n        u'2013-11-11T17:22:06-0800 [my_system] Hello!\\\\n'\n        >>>\n\n    @param event: an event.\n    @type event: L{dict}\n\n    @param formatTime: A time formatter\n    @type formatTime: L{callable} that takes an C{event} argument and returns\n        a L{unicode}\n\n    @return: A formatted event, or L{None} if no output is appropriate.\n    @rtype: L{unicode} or L{None}\n    \"\"\"\n    eventText = eventAsText(event, formatTime=formatTime)\n    if not eventText:\n        return None\n    eventText = eventText.replace(u\"\\n\", u\"\\n\\t\")\n    return eventText + u\"\\n\"\n\n\n\nclass CallMapping(object):\n    \"\"\"\n    Read-only mapping that turns a C{()}-suffix in key names into an invocation\n    of the key rather than a lookup of the key.\n\n    Implementation support for L{formatWithCall}.\n    \"\"\"\n    def __init__(self, submapping):\n        \"\"\"\n        @param submapping: Another read-only mapping which will be used to look\n            up items.\n        \"\"\"\n        self._submapping = submapping\n\n\n    def __getitem__(self, key):\n        \"\"\"\n        Look up an item in the submapping for this L{CallMapping}, calling it\n        if C{key} ends with C{\"()\"}.\n        \"\"\"\n        callit = key.endswith(u\"()\")\n        realKey = key[:-2] if callit else key\n        value = self._submapping[realKey]\n        if callit:\n            value = value()\n        return value\n\n\n\ndef formatWithCall(formatString, mapping):\n    \"\"\"\n    Format a string like L{unicode.format}, but:\n\n        - taking only a name mapping; no positional arguments\n\n        - with the additional syntax that an empty set of parentheses\n          correspond to a formatting item that should be called, and its result\n          C{str}'d, rather than calling C{str} on the element directly as\n          normal.\n\n    For example::\n\n        >>> formatWithCall(\"{string}, {function()}.\",\n        ...                dict(string=\"just a string\",\n        ...                     function=lambda: \"a function\"))\n        'just a string, a function.'\n\n    @param formatString: A PEP-3101 format string.\n    @type formatString: L{unicode}\n\n    @param mapping: A L{dict}-like object to format.\n\n    @return: The string with formatted values interpolated.\n    @rtype: L{unicode}\n    \"\"\"\n    return unicode(\n        aFormatter.vformat(formatString, (), CallMapping(mapping))\n    )\n\n\n\ndef _formatEvent(event):\n    \"\"\"\n    Formats an event as a L{unicode}, using the format in\n    C{event[\"log_format\"]}.\n\n    This implementation should never raise an exception; if the formatting\n    cannot be done, the returned string will describe the event generically so\n    that a useful message is emitted regardless.\n\n    @param event: A logging event.\n    @type event: L{dict}\n\n    @return: A formatted string.\n    @rtype: L{unicode}\n    \"\"\"\n    try:\n        if \"log_flattened\" in event:\n            return flatFormat(event)\n\n        format = event.get(\"log_format\", None)\n        if format is None:\n            return u\"\"\n\n        # Make sure format is unicode.\n        if isinstance(format, bytes):\n            # If we get bytes, assume it's UTF-8 bytes\n            format = format.decode(\"utf-8\")\n        elif not isinstance(format, unicode):\n            raise TypeError(\n                \"Log format must be unicode or bytes, not {0!r}\".format(format)\n            )\n\n        return formatWithCall(format, event)\n\n    except BaseException as e:\n        return formatUnformattableEvent(event, e)\n\n\n\ndef _formatTraceback(failure):\n    \"\"\"\n    Format a failure traceback, assuming UTF-8 and using a replacement\n    strategy for errors.  Every effort is made to provide a usable\n    traceback, but should not that not be possible, a message and the\n    captured exception are logged.\n\n    @param failure: The failure to retrieve a traceback from.\n    @type failure: L{twisted.python.failure.Failure}\n\n    @return: The formatted traceback.\n    @rtype: L{unicode}\n    \"\"\"\n    try:\n        traceback = failure.getTraceback()\n        if isinstance(traceback, bytes):\n            traceback = traceback.decode('utf-8', errors='replace')\n    except BaseException as e:\n        traceback = (\n            u\"(UNABLE TO OBTAIN TRACEBACK FROM EVENT):\" + unicode(e)\n        )\n    return traceback\n\n\n\ndef _formatSystem(event):\n    \"\"\"\n    Format the system specified in the event in the \"log_system\" key if set,\n    otherwise the C{\"log_namespace\"} and C{\"log_level\"}, joined by a C{u\"#\"}.\n    Each defaults to C{u\"-\"} is not set.  If formatting fails completely,\n    \"UNFORMATTABLE\" is returned.\n\n    @param event: The event containing the system specification.\n    @type event: L{dict}\n\n    @return: A formatted string representing the \"log_system\" key.\n    @rtype: L{unicode}\n    \"\"\"\n    system = event.get(\"log_system\", None)\n    if system is None:\n        level = event.get(\"log_level\", None)\n        if level is None:\n            levelName = u\"-\"\n        else:\n            levelName = level.name\n\n        system = u\"{namespace}#{level}\".format(\n            namespace=event.get(\"log_namespace\", u\"-\"),\n            level=levelName,\n        )\n    else:\n        try:\n            system = unicode(system)\n        except Exception:\n            system = u\"UNFORMATTABLE\"\n    return system\n\n\n\ndef eventAsText(\n        event,\n        includeTraceback=True,\n        includeTimestamp=True,\n        includeSystem=True,\n        formatTime=formatTime,\n):\n    r\"\"\"\n    Format an event as a unicode string.  Optionally, attach timestamp,\n    traceback, and system information.\n\n    The full output format is:\n    C{u\"{timeStamp} [{system}] {event}\\n{traceback}\\n\"} where:\n\n        - C{timeStamp} is the event's C{\"log_time\"} value formatted with\n          the provided C{formatTime} callable.\n\n        - C{system} is the event's C{\"log_system\"} value, if set, otherwise,\n          the C{\"log_namespace\"} and C{\"log_level\"}, joined by a C{u\"#\"}.  Each\n          defaults to C{u\"-\"} is not set.\n\n        - C{event} is the event, as formatted by L{formatEvent}.\n\n        - C{traceback} is the traceback if the event contains a\n          C{\"log_failure\"} key.  In the event the original traceback cannot\n          be formatted, a message indicating the failure will be substituted.\n\n    If the event cannot be formatted, and no traceback exists, an empty string\n    is returned, even if includeSystem or includeTimestamp are true.\n\n    @param event: A logging event.\n    @type event: L{dict}\n\n    @param includeTraceback: If true and a C{\"log_failure\"} key exists, append\n        a traceback.\n    @type includeTraceback: L{bool}\n\n    @param includeTimestamp: If true include a formatted timestamp before the\n        event.\n    @type includeTimestamp: L{bool}\n\n    @param includeSystem:  If true, include the event's C{\"log_system\"} value.\n    @type includeSystem: L{bool}\n\n    @param formatTime: A time formatter\n    @type formatTime: L{callable} that takes an C{event} argument and returns\n        a L{unicode}\n\n    @return: A formatted string with specified options.\n    @rtype: L{unicode}\n\n    @since: Twisted 18.9.0\n    \"\"\"\n    eventText = _formatEvent(event)\n    if includeTraceback and 'log_failure' in event:\n        f = event['log_failure']\n        traceback = _formatTraceback(f)\n        eventText = u\"\\n\".join((eventText, traceback))\n\n    if not eventText:\n        return eventText\n\n    timeStamp = u\"\"\n    if includeTimestamp:\n        timeStamp = u\"\".join([formatTime(event.get(\"log_time\", None)), \" \"])\n\n    system = u\"\"\n    if includeSystem:\n        system = u\"\".join([\n            u\"[\",\n            _formatSystem(event),\n            u\"]\",\n            u\" \"\n        ])\n\n    return u\"{timeStamp}{system}{eventText}\".format(\n        timeStamp=timeStamp,\n        system=system,\n        eventText=eventText,\n    )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_global.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_global -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nThis module includes process-global state associated with the logging system,\nand implementation of logic for managing that global state.\n\"\"\"\n\nimport sys\nimport warnings\n\nfrom twisted.python.compat import currentframe\nfrom twisted.python.reflect import qual\n\nfrom ._buffer import LimitedHistoryLogObserver\nfrom ._observer import LogPublisher\nfrom ._filter import FilteringLogObserver, LogLevelFilterPredicate\nfrom ._logger import Logger\nfrom ._format import eventAsText\nfrom ._levels import LogLevel\nfrom ._io import LoggingFile\nfrom ._file import FileLogObserver\n\n\n\nMORE_THAN_ONCE_WARNING = (\n    \"Warning: primary log target selected twice at <{fileNow}:{lineNow}> - \"\n    \"previously selected at <{fileThen}:{lineThen}>.  Remove one of the calls \"\n    \"to beginLoggingTo.\"\n)\n\n\n\nclass LogBeginner(object):\n    \"\"\"\n    A L{LogBeginner} holds state related to logging before logging has begun,\n    and begins logging when told to do so.  Logging \"begins\" when someone has\n    selected a set of observers, like, for example, a L{FileLogObserver} that\n    writes to a file on disk, or to standard output.\n\n    Applications will not typically need to instantiate this class, except\n    those which intend to initialize the global logging system themselves,\n    which may wish to instantiate this for testing.  The global instance for\n    the current process is exposed as\n    L{twisted.logger.globalLogBeginner}.\n\n    Before logging has begun, a L{LogBeginner} will:\n\n        1. Log any critical messages (e.g.: unhandled exceptions) to the given\n           file-like object.\n\n        2. Save (a limited number of) log events in a\n           L{LimitedHistoryLogObserver}.\n\n    @ivar _initialBuffer: A buffer of messages logged before logging began.\n    @type _initialBuffer: L{LimitedHistoryLogObserver}\n\n    @ivar _publisher: The log publisher passed in to L{LogBeginner}'s\n        constructor.\n    @type _publisher: L{LogPublisher}\n\n    @ivar _log: The logger used to log messages about the operation of the\n        L{LogBeginner} itself.\n    @type _log: L{Logger}\n\n    @ivar _temporaryObserver: If not L{None}, an L{ILogObserver} that observes\n        events on C{_publisher} for this L{LogBeginner}.\n    @type _temporaryObserver: L{ILogObserver} or L{None}\n\n    @ivar _stdio: An object with C{stderr} and C{stdout} attributes (like the\n        L{sys} module) which will be replaced when redirecting standard I/O.\n    @type _stdio: L{object}\n\n    @cvar _DEFAULT_BUFFER_SIZE: The default size for the initial log events\n        buffer.\n    @type _DEFAULT_BUFFER_SIZE: L{int}\n    \"\"\"\n\n    _DEFAULT_BUFFER_SIZE = 200\n\n    def __init__(\n        self, publisher, errorStream, stdio, warningsModule,\n        initialBufferSize=None,\n    ):\n        \"\"\"\n        Initialize this L{LogBeginner}.\n\n        @param initialBufferSize: The size of the event buffer into which\n            events are collected until C{beginLoggingTo} is called.  Or\n            C{None} to use the default size.\n        @type initialBufferSize: L{int} or L{types.NoneType}\n        \"\"\"\n        if initialBufferSize is None:\n            initialBufferSize = self._DEFAULT_BUFFER_SIZE\n        self._initialBuffer = LimitedHistoryLogObserver(size=initialBufferSize)\n        self._publisher = publisher\n        self._log = Logger(observer=publisher)\n        self._stdio = stdio\n        self._warningsModule = warningsModule\n        self._temporaryObserver = LogPublisher(\n            self._initialBuffer,\n            FilteringLogObserver(\n                FileLogObserver(\n                    errorStream,\n                    lambda event: eventAsText(\n                        event,\n                        includeTimestamp=False,\n                        includeSystem=False,\n                    ) + '\\n'\n                ),\n                [LogLevelFilterPredicate(defaultLogLevel=LogLevel.critical)]\n            )\n        )\n        publisher.addObserver(self._temporaryObserver)\n        self._oldshowwarning = warningsModule.showwarning\n\n\n    def beginLoggingTo(\n        self, observers, discardBuffer=False, redirectStandardIO=True\n    ):\n        \"\"\"\n        Begin logging to the given set of observers.  This will:\n\n            1. Add all the observers given in C{observers} to the\n               L{LogPublisher} associated with this L{LogBeginner}.\n\n            2. Optionally re-direct standard output and standard error streams\n               to the logging system.\n\n            3. Re-play any messages that were previously logged to that\n               publisher to the new observers, if C{discardBuffer} is not set.\n\n            4. Stop logging critical errors from the L{LogPublisher} as strings\n               to the C{errorStream} associated with this L{LogBeginner}, and\n               allow them to be logged normally.\n\n            5. Re-direct warnings from the L{warnings} module associated with\n               this L{LogBeginner} to log messages.\n\n        @note: Since a L{LogBeginner} is designed to encapsulate the transition\n            between process-startup and log-system-configuration, this method\n            is intended to be invoked I{once}.\n\n        @param observers: The observers to register.\n        @type observers: iterable of L{ILogObserver}s\n\n        @param discardBuffer: Whether to discard the buffer and not re-play it\n            to the added observers.  (This argument is provided mainly for\n            compatibility with legacy concerns.)\n        @type discardBuffer: L{bool}\n\n        @param redirectStandardIO: If true, redirect standard output and\n            standard error to the observers.\n        @type redirectStandardIO: L{bool}\n        \"\"\"\n        caller = currentframe(1)\n        filename, lineno = caller.f_code.co_filename, caller.f_lineno\n\n        for observer in observers:\n            self._publisher.addObserver(observer)\n\n        if self._temporaryObserver is not None:\n            self._publisher.removeObserver(self._temporaryObserver)\n            if not discardBuffer:\n                self._initialBuffer.replayTo(self._publisher)\n            self._temporaryObserver = None\n            self._warningsModule.showwarning = self.showwarning\n        else:\n            previousFile, previousLine = self._previousBegin\n            self._log.warn(\n                MORE_THAN_ONCE_WARNING,\n                fileNow=filename, lineNow=lineno,\n                fileThen=previousFile, lineThen=previousLine,\n            )\n\n        self._previousBegin = filename, lineno\n        if redirectStandardIO:\n            streams = [(\"stdout\", LogLevel.info), (\"stderr\", LogLevel.error)]\n        else:\n            streams = []\n\n        for (stream, level) in streams:\n            oldStream = getattr(self._stdio, stream)\n            loggingFile = LoggingFile(\n                logger=Logger(namespace=stream, observer=self._publisher),\n                level=level,\n                encoding=getattr(oldStream, \"encoding\", None),\n            )\n            setattr(self._stdio, stream, loggingFile)\n\n\n    def showwarning(\n        self, message, category, filename, lineno, file=None, line=None\n    ):\n        \"\"\"\n        Twisted-enabled wrapper around L{warnings.showwarning}.\n\n        If C{file} is L{None}, the default behaviour is to emit the warning to\n        the log system, otherwise the original L{warnings.showwarning} Python\n        function is called.\n\n        @param message: A warning message to emit.\n        @type message: L{str}\n\n        @param category: A warning category to associate with C{message}.\n        @type category: L{warnings.Warning}\n\n        @param filename: A file name for the source code file issuing the\n            warning.\n        @type warning: L{str}\n\n        @param lineno: A line number in the source file where the warning was\n            issued.\n        @type lineno: L{int}\n\n        @param file: A file to write the warning message to.  If L{None},\n            write to L{sys.stderr}.\n        @type file: file-like object\n\n        @param line: A line of source code to include with the warning message.\n            If L{None}, attempt to read the line from C{filename} and\n            C{lineno}.\n        @type line: L{str}\n        \"\"\"\n        if file is None:\n            self._log.warn(\n                \"{filename}:{lineno}: {category}: {warning}\",\n                warning=message, category=qual(category),\n                filename=filename, lineno=lineno,\n            )\n        else:\n            self._oldshowwarning(\n                message, category, filename, lineno, file, line\n            )\n\n\n\nglobalLogPublisher = LogPublisher()\nglobalLogBeginner = LogBeginner(globalLogPublisher, sys.stderr, sys, warnings)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_io.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_io -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nFile-like object that logs.\n\"\"\"\n\nimport sys\n\nfrom ._levels import LogLevel\n\n\n\nclass LoggingFile(object):\n    \"\"\"\n    File-like object that turns C{write()} calls into logging events.\n\n    Note that because event formats are C{unicode}, C{bytes} received via\n    C{write()} are converted to C{unicode}, which is the opposite of what\n    C{file} does.\n\n    @ivar softspace: File-like L{'softspace' attribute <file.softspace>}; zero\n        or one.\n    @type softspace: L{int}\n    \"\"\"\n\n    softspace = 0\n\n\n    def __init__(self, logger, level=LogLevel.info, encoding=None):\n        \"\"\"\n        @param logger: the logger to log through.\n\n        @param level: the log level to emit events with.\n\n        @param encoding: The encoding to expect when receiving bytes via\n            C{write()}.  If L{None}, use C{sys.getdefaultencoding()}.\n        @type encoding: L{str}\n\n        @param log: The logger to send events to.\n        @type log: L{Logger}\n        \"\"\"\n        self.level = level\n        self.log = logger\n\n        if encoding is None:\n            self._encoding = sys.getdefaultencoding()\n        else:\n            self._encoding = encoding\n\n        self._buffer = \"\"\n        self._closed = False\n\n\n    @property\n    def closed(self):\n        \"\"\"\n        Read-only property.  Is the file closed?\n\n        @return: true if closed, otherwise false.\n        @rtype: L{bool}\n        \"\"\"\n        return self._closed\n\n\n    @property\n    def encoding(self):\n        \"\"\"\n        Read-only property.   File encoding.\n\n        @return: an encoding.\n        @rtype: L{str}\n        \"\"\"\n        return self._encoding\n\n\n    @property\n    def mode(self):\n        \"\"\"\n        Read-only property.  File mode.\n\n        @return: \"w\"\n        @rtype: L{str}\n        \"\"\"\n        return \"w\"\n\n\n    @property\n    def newlines(self):\n        \"\"\"\n        Read-only property.  Types of newlines encountered.\n\n        @return: L{None}\n        @rtype: L{None}\n        \"\"\"\n        return None\n\n\n    @property\n    def name(self):\n        \"\"\"\n        The name of this file; a repr-style string giving information about its\n        namespace.\n\n        @return: A file name.\n        @rtype: L{str}\n        \"\"\"\n        return (\n            \"<{0} {1}#{2}>\".format(\n                self.__class__.__name__,\n                self.log.namespace,\n                self.level.name,\n            )\n        )\n\n\n    def close(self):\n        \"\"\"\n        Close this file so it can no longer be written to.\n        \"\"\"\n        self._closed = True\n\n\n    def flush(self):\n        \"\"\"\n        No-op; this file does not buffer.\n        \"\"\"\n        pass\n\n\n    def fileno(self):\n        \"\"\"\n        Returns an invalid file descriptor, since this is not backed by an FD.\n\n        @return: C{-1}\n        @rtype: L{int}\n        \"\"\"\n        return -1\n\n\n    def isatty(self):\n        \"\"\"\n        A L{LoggingFile} is not a TTY.\n\n        @return: C{False}\n        @rtype: L{bool}\n        \"\"\"\n        return False\n\n\n    def write(self, string):\n        \"\"\"\n        Log the given message.\n\n        @param string: Data to write.\n        @type string: L{bytes} in this file's preferred encoding or L{unicode}\n        \"\"\"\n        if self._closed:\n            raise ValueError(\"I/O operation on closed file\")\n\n        if isinstance(string, bytes):\n            string = string.decode(self._encoding)\n\n        lines = (self._buffer + string).split(\"\\n\")\n        self._buffer = lines[-1]\n        lines = lines[0:-1]\n\n        for line in lines:\n            self.log.emit(self.level, format=u\"{log_io}\", log_io=line)\n\n\n    def writelines(self, lines):\n        \"\"\"\n        Log each of the given lines as a separate message.\n\n        @param lines: Data to write.\n        @type lines: iterable of L{unicode} or L{bytes} in this file's\n            declared encoding\n        \"\"\"\n        for line in lines:\n            self.write(line)\n\n\n    def _unsupported(self, *args):\n        \"\"\"\n        Template for unsupported operations.\n\n        @param args: Arguments.\n        @type args: tuple of L{object}\n        \"\"\"\n        raise IOError(\"unsupported operation\")\n\n\n    read       = _unsupported\n    next       = _unsupported\n    readline   = _unsupported\n    readlines  = _unsupported\n    xreadlines = _unsupported\n    seek       = _unsupported\n    tell       = _unsupported\n    truncate   = _unsupported\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_json.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_json -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTools for saving and loading log events in a structured format.\n\"\"\"\n\nimport types\n\nfrom constantly import NamedConstant\nfrom json import dumps, loads\nfrom uuid import UUID\n\nfrom ._flatten import flattenEvent\nfrom ._file import FileLogObserver\nfrom ._levels import LogLevel\nfrom ._logger import Logger\n\nfrom twisted.python.compat import unicode, _PY3\nfrom twisted.python.failure import Failure\n\nlog = Logger()\n\n\n\ndef failureAsJSON(failure):\n    \"\"\"\n    Convert a failure to a JSON-serializable data structure.\n\n    @param failure: A failure to serialize.\n    @type failure: L{Failure}\n\n    @return: a mapping of strings to ... stuff, mostly reminiscent of\n        L{Failure.__getstate__}\n    @rtype: L{dict}\n    \"\"\"\n    return dict(\n        failure.__getstate__(),\n        type=dict(\n            __module__=failure.type.__module__,\n            __name__=failure.type.__name__,\n        )\n    )\n\n\n\ndef asBytes(obj):\n    \"\"\"\n    On Python 2, we really need native strings in a variety of places;\n    attribute names will sort of work in a __dict__, but they're subtly wrong;\n    however, printing tracebacks relies on I/O to containers that only support\n    bytes.  This function converts _all_ native strings within a\n    JSON-deserialized object to bytes.\n\n    @param obj: An object to convert to bytes.\n    @type obj: L{object}\n\n    @return: A string of UTF-8 bytes.\n    @rtype: L{bytes}\n    \"\"\"\n    if isinstance(obj, list):\n        return map(asBytes, obj)\n    elif isinstance(obj, dict):\n        return dict((asBytes(k), asBytes(v)) for k, v in obj.items())\n    elif isinstance(obj, unicode):\n        return obj.encode(\"utf-8\")\n    else:\n        return obj\n\n\n\ndef failureFromJSON(failureDict):\n    \"\"\"\n    Load a L{Failure} from a dictionary deserialized from JSON.\n\n    @param failureDict: a JSON-deserialized object like one previously returned\n        by L{failureAsJSON}.\n    @type failureDict: L{dict} mapping L{unicode} to attributes\n\n    @return: L{Failure}\n    @rtype: L{Failure}\n    \"\"\"\n    # InstanceType() is only available in Python 2 and lower.\n    # __new__ is only available on new-style classes.\n    newFailure = getattr(Failure, \"__new__\", None)\n    if newFailure is None:\n        f = types.InstanceType(Failure)\n    else:\n        f = newFailure(Failure)\n\n    if not _PY3:\n        # Python 2 needs the failure dictionary as purely bytes, not text\n        failureDict = asBytes(failureDict)\n\n    typeInfo = failureDict[\"type\"]\n    failureDict[\"type\"] = type(typeInfo[\"__name__\"], (), typeInfo)\n    f.__dict__ = failureDict\n    return f\n\n\n\nclassInfo = [\n    (\n        lambda level: (\n            isinstance(level, NamedConstant) and\n            getattr(LogLevel, level.name, None) is level\n        ),\n        UUID(\"02E59486-F24D-46AD-8224-3ACDF2A5732A\"),\n        lambda level: dict(name=level.name),\n        lambda level: getattr(LogLevel, level[\"name\"], None)\n    ),\n\n    (\n        lambda o: isinstance(o, Failure),\n        UUID(\"E76887E2-20ED-49BF-A8F8-BA25CC586F2D\"),\n        failureAsJSON, failureFromJSON\n    ),\n]\n\n\n\nuuidToLoader = dict([\n    (uuid, loader) for (predicate, uuid, saver, loader) in classInfo\n])\n\n\n\ndef objectLoadHook(aDict):\n    \"\"\"\n    Dictionary-to-object-translation hook for certain value types used within\n    the logging system.\n\n    @see: the C{object_hook} parameter to L{json.load}\n\n    @param aDict: A dictionary loaded from a JSON object.\n    @type aDict: L{dict}\n\n    @return: C{aDict} itself, or the object represented by C{aDict}\n    @rtype: L{object}\n    \"\"\"\n    if \"__class_uuid__\" in aDict:\n        return uuidToLoader[UUID(aDict[\"__class_uuid__\"])](aDict)\n    return aDict\n\n\n\ndef objectSaveHook(pythonObject):\n    \"\"\"\n    Object-to-serializable hook for certain value types used within the logging\n    system.\n\n    @see: the C{default} parameter to L{json.dump}\n\n    @param pythonObject: Any object.\n    @type pythonObject: L{object}\n\n    @return: If the object is one of the special types the logging system\n        supports, a specially-formatted dictionary; otherwise, a marker\n        dictionary indicating that it could not be serialized.\n    \"\"\"\n    for (predicate, uuid, saver, loader) in classInfo:\n        if predicate(pythonObject):\n            result = saver(pythonObject)\n            result[\"__class_uuid__\"] = str(uuid)\n            return result\n    return {\"unpersistable\": True}\n\n\n\ndef eventAsJSON(event):\n    \"\"\"\n    Encode an event as JSON, flattening it if necessary to preserve as much\n    structure as possible.\n\n    Not all structure from the log event will be preserved when it is\n    serialized.\n\n    @param event: A log event dictionary.\n    @type event: L{dict} with arbitrary keys and values\n\n    @return: A string of the serialized JSON; note that this will contain no\n        newline characters, and may thus safely be stored in a line-delimited\n        file.\n    @rtype: L{unicode}\n    \"\"\"\n    if bytes is str:\n        kw = dict(default=objectSaveHook, encoding=\"charmap\", skipkeys=True)\n    else:\n        def default(unencodable):\n            \"\"\"\n            Serialize an object not otherwise serializable by L{dumps}.\n\n            @param unencodable: An unencodable object.\n            @return: C{unencodable}, serialized\n            \"\"\"\n            if isinstance(unencodable, bytes):\n                return unencodable.decode(\"charmap\")\n            return objectSaveHook(unencodable)\n\n        kw = dict(default=default, skipkeys=True)\n\n    flattenEvent(event)\n    result = dumps(event, **kw)\n    if not isinstance(result, unicode):\n        return unicode(result, \"utf-8\", \"replace\")\n    return result\n\n\n\ndef eventFromJSON(eventText):\n    \"\"\"\n    Decode a log event from JSON.\n\n    @param eventText: The output of a previous call to L{eventAsJSON}\n    @type eventText: L{unicode}\n\n    @return: A reconstructed version of the log event.\n    @rtype: L{dict}\n    \"\"\"\n    loaded = loads(eventText, object_hook=objectLoadHook)\n    return loaded\n\n\n\ndef jsonFileLogObserver(outFile, recordSeparator=u\"\\x1e\"):\n    \"\"\"\n    Create a L{FileLogObserver} that emits JSON-serialized events to a\n    specified (writable) file-like object.\n\n    Events are written in the following form::\n\n        RS + JSON + NL\n\n    C{JSON} is the serialized event, which is JSON text.  C{NL} is a newline\n    (C{u\"\\\\n\"}).  C{RS} is a record separator.  By default, this is a single\n    RS character (C{u\"\\\\x1e\"}), which makes the default output conform to the\n    IETF draft document \"draft-ietf-json-text-sequence-13\".\n\n    @param outFile: A file-like object.  Ideally one should be passed which\n        accepts L{unicode} data.  Otherwise, UTF-8 L{bytes} will be used.\n    @type outFile: L{io.IOBase}\n\n    @param recordSeparator: The record separator to use.\n    @type recordSeparator: L{unicode}\n\n    @return: A file log observer.\n    @rtype: L{FileLogObserver}\n    \"\"\"\n    return FileLogObserver(\n        outFile,\n        lambda event: u\"{0}{1}\\n\".format(recordSeparator, eventAsJSON(event))\n    )\n\n\n\ndef eventsFromJSONLogFile(inFile, recordSeparator=None, bufferSize=4096):\n    \"\"\"\n    Load events from a file previously saved with L{jsonFileLogObserver}.\n    Event records that are truncated or otherwise unreadable are ignored.\n\n    @param inFile: A (readable) file-like object.  Data read from C{inFile}\n        should be L{unicode} or UTF-8 L{bytes}.\n    @type inFile: iterable of lines\n\n    @param recordSeparator: The expected record separator.\n        If L{None}, attempt to automatically detect the record separator from\n        one of C{u\"\\\\x1e\"} or C{u\"\"}.\n    @type recordSeparator: L{unicode}\n\n    @param bufferSize: The size of the read buffer used while reading from\n        C{inFile}.\n    @type bufferSize: integer\n\n    @return: Log events as read from C{inFile}.\n    @rtype: iterable of L{dict}\n    \"\"\"\n    def asBytes(s):\n        if type(s) is bytes:\n            return s\n        else:\n            return s.encode(\"utf-8\")\n\n    def eventFromBytearray(record):\n        try:\n            text = bytes(record).decode(\"utf-8\")\n        except UnicodeDecodeError:\n            log.error(\n                u\"Unable to decode UTF-8 for JSON record: {record!r}\",\n                record=bytes(record)\n            )\n            return None\n\n        try:\n            return eventFromJSON(text)\n        except ValueError:\n            log.error(\n                u\"Unable to read JSON record: {record!r}\",\n                record=bytes(record)\n            )\n            return None\n\n    if recordSeparator is None:\n        first = asBytes(inFile.read(1))\n\n        if first == b\"\\x1e\":\n            # This looks json-text-sequence compliant.\n            recordSeparator = first\n        else:\n            # Default to simpler newline-separated stream, which does not use\n            # a record separator.\n            recordSeparator = b\"\"\n\n    else:\n        recordSeparator = asBytes(recordSeparator)\n        first = b\"\"\n\n    if recordSeparator == b\"\":\n        recordSeparator = b\"\\n\"  # Split on newlines below\n\n        eventFromRecord = eventFromBytearray\n\n    else:\n        def eventFromRecord(record):\n            if record[-1] == ord(\"\\n\"):\n                return eventFromBytearray(record)\n            else:\n                log.error(\n                    u\"Unable to read truncated JSON record: {record!r}\",\n                    record=bytes(record)\n                )\n            return None\n\n    buffer = bytearray(first)\n\n    while True:\n        newData = inFile.read(bufferSize)\n\n        if not newData:\n            if len(buffer) > 0:\n                event = eventFromRecord(buffer)\n                if event is not None:\n                    yield event\n            break\n\n        buffer += asBytes(newData)\n        records = buffer.split(recordSeparator)\n\n        for record in records[:-1]:\n            if len(record) > 0:\n                event = eventFromRecord(record)\n                if event is not None:\n                    yield event\n\n        buffer = records[-1]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_legacy.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_legacy -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nIntegration with L{twisted.python.log}.\n\"\"\"\n\nfrom zope.interface import implementer\n\nfrom ._levels import LogLevel\nfrom ._format import formatEvent\nfrom ._observer import ILogObserver\nfrom ._stdlib import fromStdlibLogLevelMapping, StringifiableFromEvent\n\n\n\n@implementer(ILogObserver)\nclass LegacyLogObserverWrapper(object):\n    \"\"\"\n    L{ILogObserver} that wraps an L{twisted.python.log.ILogObserver}.\n\n    Received (new-style) events are modified prior to forwarding to\n    the legacy observer to ensure compatibility with observers that\n    expect legacy events.\n    \"\"\"\n\n    def __init__(self, legacyObserver):\n        \"\"\"\n        @param legacyObserver: a legacy observer to which this observer will\n            forward events.\n        @type legacyObserver: L{twisted.python.log.ILogObserver}\n        \"\"\"\n        self.legacyObserver = legacyObserver\n\n\n    def __repr__(self):\n        return (\n            \"{self.__class__.__name__}({self.legacyObserver})\"\n            .format(self=self)\n        )\n\n\n    def __call__(self, event):\n        \"\"\"\n        Forward events to the legacy observer after editing them to\n        ensure compatibility.\n\n        @param event: an event\n        @type event: L{dict}\n        \"\"\"\n\n        # The \"message\" key is required by textFromEventDict()\n        if \"message\" not in event:\n            event[\"message\"] = ()\n\n        if \"time\" not in event:\n            event[\"time\"] = event[\"log_time\"]\n\n        if \"system\" not in event:\n            event[\"system\"] = event.get(\"log_system\", \"-\")\n\n        # Format new style -> old style\n        if \"format\" not in event and event.get(\"log_format\", None) is not None:\n            # Create an object that implements __str__() in order to defer the\n            # work of formatting until it's needed by a legacy log observer.\n            event[\"format\"] = \"%(log_legacy)s\"\n            event[\"log_legacy\"] = StringifiableFromEvent(event.copy())\n\n            # In the old-style system, the 'message' key always holds a tuple\n            # of messages. If we find the 'message' key here to not be a\n            # tuple, it has been passed as new-style parameter. We drop it\n            # here because we render it using the old-style 'format' key,\n            # which otherwise doesn't get precedence, and the original event\n            # has been copied above.\n            if not isinstance(event[\"message\"], tuple):\n                event[\"message\"] = ()\n\n        # From log.failure() -> isError blah blah\n        if \"log_failure\" in event:\n            if \"failure\" not in event:\n                event[\"failure\"] = event[\"log_failure\"]\n            if \"isError\" not in event:\n                event[\"isError\"] = 1\n            if \"why\" not in event:\n                event[\"why\"] = formatEvent(event)\n        elif \"isError\" not in event:\n            if event[\"log_level\"] in (LogLevel.error, LogLevel.critical):\n                event[\"isError\"] = 1\n            else:\n                event[\"isError\"] = 0\n\n        self.legacyObserver(event)\n\n\n\ndef publishToNewObserver(observer, eventDict, textFromEventDict):\n    \"\"\"\n    Publish an old-style (L{twisted.python.log}) event to a new-style\n    (L{twisted.logger}) observer.\n\n    @note: It's possible that a new-style event was sent to a\n        L{LegacyLogObserverWrapper}, and may now be getting sent back to a\n        new-style observer.  In this case, it's already a new-style event,\n        adapted to also look like an old-style event, and we don't need to\n        tweak it again to be a new-style event, hence the checks for\n        already-defined new-style keys.\n\n    @param observer: A new-style observer to handle this event.\n    @type observer: L{ILogObserver}\n\n    @param eventDict: An L{old-style <twisted.python.log>}, log event.\n    @type eventDict: L{dict}\n\n    @param textFromEventDict: callable that can format an old-style event as a\n        string.  Passed here rather than imported to avoid circular dependency.\n    @type textFromEventDict: 1-arg L{callable} taking L{dict} returning L{str}\n\n    @return: L{None}\n    \"\"\"\n\n    if \"log_time\" not in eventDict:\n        eventDict[\"log_time\"] = eventDict[\"time\"]\n\n    if \"log_format\" not in eventDict:\n        text = textFromEventDict(eventDict)\n        if text is not None:\n            eventDict[\"log_text\"] = text\n            eventDict[\"log_format\"] = u\"{log_text}\"\n\n    if \"log_level\" not in eventDict:\n        if \"logLevel\" in eventDict:\n            try:\n                level = fromStdlibLogLevelMapping[eventDict[\"logLevel\"]]\n            except KeyError:\n                level = None\n        elif \"isError\" in eventDict:\n            if eventDict[\"isError\"]:\n                level = LogLevel.critical\n            else:\n                level = LogLevel.info\n        else:\n            level = LogLevel.info\n\n        if level is not None:\n            eventDict[\"log_level\"] = level\n\n    if \"log_namespace\" not in eventDict:\n        eventDict[\"log_namespace\"] = u\"log_legacy\"\n\n    if \"log_system\" not in eventDict and \"system\" in eventDict:\n        eventDict[\"log_system\"] = eventDict[\"system\"]\n\n    observer(eventDict)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_levels.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_levels -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nLog levels.\n\"\"\"\n\nfrom constantly import NamedConstant, Names\n\n\n\nclass InvalidLogLevelError(Exception):\n    \"\"\"\n    Someone tried to use a L{LogLevel} that is unknown to the logging system.\n    \"\"\"\n    def __init__(self, level):\n        \"\"\"\n        @param level: A log level.\n        @type level: L{LogLevel}\n        \"\"\"\n        super(InvalidLogLevelError, self).__init__(str(level))\n        self.level = level\n\n\n\nclass LogLevel(Names):\n    \"\"\"\n    Constants describing log levels.\n\n    @cvar debug: Debugging events: Information of use to a developer of the\n        software, not generally of interest to someone running the software\n        unless they are attempting to diagnose a software issue.\n\n    @cvar info: Informational events: Routine information about the status of\n        an application, such as incoming connections, startup of a subsystem,\n        etc.\n\n    @cvar warn: Warning events: Events that may require greater attention than\n        informational events but are not a systemic failure condition, such as\n        authorization failures, bad data from a network client, etc.  Such\n        events are of potential interest to system administrators, and should\n        ideally be phrased in such a way, or documented, so as to indicate an\n        action that an administrator might take to mitigate the warning.\n\n    @cvar error: Error conditions: Events indicating a systemic failure, such\n        as programming errors in the form of unhandled exceptions, loss of\n        connectivity to an external system without which no useful work can\n        proceed, such as a database or API endpoint, or resource exhaustion.\n        Similarly to warnings, errors that are related to operational\n        parameters may be actionable to system administrators and should\n        provide references to resources which an administrator might use to\n        resolve them.\n\n    @cvar critical: Critical failures: Errors indicating systemic failure (ie.\n        service outage), data corruption, imminent data loss, etc. which must\n        be handled immediately.  This includes errors unanticipated by the\n        software, such as unhandled exceptions, wherein the cause and\n        consequences are unknown.\n    \"\"\"\n\n    debug = NamedConstant()\n    info = NamedConstant()\n    warn = NamedConstant()\n    error = NamedConstant()\n    critical = NamedConstant()\n\n\n    @classmethod\n    def levelWithName(cls, name):\n        \"\"\"\n        Get the log level with the given name.\n\n        @param name: The name of a log level.\n        @type name: L{str} (native string)\n\n        @return: The L{LogLevel} with the specified C{name}.\n        @rtype: L{LogLevel}\n\n        @raise InvalidLogLevelError: if the C{name} does not name a valid log\n            level.\n        \"\"\"\n        try:\n            return cls.lookupByName(name)\n        except ValueError:\n            raise InvalidLogLevelError(name)\n\n\n    @classmethod\n    def _priorityForLevel(cls, level):\n        \"\"\"\n        We want log levels to have defined ordering - the order of definition -\n        but they aren't value constants (the only value is the name).  This is\n        arguably a bug in Twisted, so this is just a workaround for U{until\n        this is fixed in some way\n        <https://twistedmatrix.com/trac/ticket/6523>}.\n\n        @param level: A log level.\n        @type level: L{LogLevel}\n\n        @return: A numeric index indicating priority (lower is higher level).\n        @rtype: L{int}\n        \"\"\"\n        return cls._levelPriorities[level]\n\n\nLogLevel._levelPriorities = dict(\n    (level, index) for (index, level) in\n    (enumerate(LogLevel.iterconstants()))\n)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_logger.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_logger -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nLogger class.\n\"\"\"\n\nfrom time import time\n\nfrom twisted.python.compat import currentframe\nfrom twisted.python.failure import Failure\nfrom ._levels import InvalidLogLevelError, LogLevel\n\n\n\nclass Logger(object):\n    \"\"\"\n    A L{Logger} emits log messages to an observer.  You should instantiate it\n    as a class or module attribute, as documented in L{this module's\n    documentation <twisted.logger>}.\n\n    @type namespace: L{str}\n    @ivar namespace: the namespace for this logger\n\n    @type source: L{object}\n    @ivar source: The object which is emitting events via this logger\n\n    @type: L{ILogObserver}\n    @ivar observer: The observer that this logger will send events to.\n    \"\"\"\n\n    @staticmethod\n    def _namespaceFromCallingContext():\n        \"\"\"\n        Derive a namespace from the module containing the caller's caller.\n\n        @return: the fully qualified python name of a module.\n        @rtype: L{str} (native string)\n        \"\"\"\n        try:\n            return currentframe(2).f_globals[\"__name__\"]\n        except KeyError:\n            return \"<unknown>\"\n\n\n    def __init__(self, namespace=None, source=None, observer=None):\n        \"\"\"\n        @param namespace: The namespace for this logger.  Uses a dotted\n            notation, as used by python modules.  If not L{None}, then the name\n            of the module of the caller is used.\n        @type namespace: L{str} (native string)\n\n        @param source: The object which is emitting events via this\n            logger; this is automatically set on instances of a class\n            if this L{Logger} is an attribute of that class.\n        @type source: L{object}\n\n        @param observer: The observer that this logger will send events to.\n            If L{None}, use the L{global log publisher <globalLogPublisher>}.\n        @type observer: L{ILogObserver}\n        \"\"\"\n        if namespace is None:\n            namespace = self._namespaceFromCallingContext()\n\n        self.namespace = namespace\n        self.source = source\n\n        if observer is None:\n            from ._global import globalLogPublisher\n            self.observer = globalLogPublisher\n        else:\n            self.observer = observer\n\n\n    def __get__(self, oself, type=None):\n        \"\"\"\n        When used as a descriptor, i.e.::\n\n            # File: athing.py\n            class Something(object):\n                log = Logger()\n                def hello(self):\n                    self.log.info(\"Hello\")\n\n        a L{Logger}'s namespace will be set to the name of the class it is\n        declared on.  In the above example, the namespace would be\n        C{athing.Something}.\n\n        Additionally, its source will be set to the actual object referring to\n        the L{Logger}.  In the above example, C{Something.log.source} would be\n        C{Something}, and C{Something().log.source} would be an instance of\n        C{Something}.\n        \"\"\"\n        if oself is None:\n            source = type\n        else:\n            source = oself\n\n        return self.__class__(\n            \".\".join([type.__module__, type.__name__]),\n            source,\n            observer=self.observer,\n        )\n\n\n    def __repr__(self):\n        return \"<%s %r>\" % (self.__class__.__name__, self.namespace)\n\n\n    def emit(self, level, format=None, **kwargs):\n        \"\"\"\n        Emit a log event to all log observers at the given level.\n\n        @param level: a L{LogLevel}\n\n        @param format: a message format using new-style (PEP 3101)\n            formatting.  The logging event (which is a L{dict}) is\n            used to render this format string.\n\n        @param kwargs: additional key/value pairs to include in the event.\n            Note that values which are later mutated may result in\n            non-deterministic behavior from observers that schedule work for\n            later execution.\n        \"\"\"\n        if level not in LogLevel.iterconstants():\n            self.failure(\n                \"Got invalid log level {invalidLevel!r} in {logger}.emit().\",\n                Failure(InvalidLogLevelError(level)),\n                invalidLevel=level,\n                logger=self,\n            )\n            return\n\n        event = kwargs\n        event.update(\n            log_logger=self, log_level=level, log_namespace=self.namespace,\n            log_source=self.source, log_format=format, log_time=time(),\n        )\n\n        if \"log_trace\" in event:\n            event[\"log_trace\"].append((self, self.observer))\n\n        self.observer(event)\n\n\n    def failure(self, format, failure=None, level=LogLevel.critical, **kwargs):\n        \"\"\"\n        Log a failure and emit a traceback.\n\n        For example::\n\n            try:\n                frob(knob)\n            except Exception:\n                log.failure(\"While frobbing {knob}\", knob=knob)\n\n        or::\n\n            d = deferredFrob(knob)\n            d.addErrback(lambda f: log.failure(\"While frobbing {knob}\",\n                                               f, knob=knob))\n\n        This method is generally meant to capture unexpected exceptions in\n        code; an exception that is caught and handled somehow should be logged,\n        if appropriate, via L{Logger.error} instead.  If some unknown exception\n        occurs and your code doesn't know how to handle it, as in the above\n        example, then this method provides a means to describe the failure in\n        nerd-speak.  This is done at L{LogLevel.critical} by default, since no\n        corrective guidance can be offered to an user/administrator, and the\n        impact of the condition is unknown.\n\n        @param format: a message format using new-style (PEP 3101) formatting.\n            The logging event (which is a L{dict}) is used to render this\n            format string.\n\n        @param failure: a L{Failure} to log.  If L{None}, a L{Failure} is\n            created from the exception in flight.\n\n        @param level: a L{LogLevel} to use.\n\n        @param kwargs: additional key/value pairs to include in the event.\n            Note that values which are later mutated may result in\n            non-deterministic behavior from observers that schedule work for\n            later execution.\n        \"\"\"\n        if failure is None:\n            failure = Failure()\n\n        self.emit(level, format, log_failure=failure, **kwargs)\n\n\n    def debug(self, format=None, **kwargs):\n        \"\"\"\n        Emit a log event at log level L{LogLevel.debug}.\n\n        @param format: a message format using new-style (PEP 3101) formatting.\n            The logging event (which is a L{dict}) is used to render this\n            format string.\n\n        @param kwargs: additional key/value pairs to include in the event.\n            Note that values which are later mutated may result in\n            non-deterministic behavior from observers that schedule work for\n            later execution.\n        \"\"\"\n        self.emit(LogLevel.debug, format, **kwargs)\n\n\n    def info(self, format=None, **kwargs):\n        \"\"\"\n        Emit a log event at log level L{LogLevel.info}.\n\n        @param format: a message format using new-style (PEP 3101) formatting.\n            The logging event (which is a L{dict}) is used to render this\n            format string.\n\n        @param kwargs: additional key/value pairs to include in the event.\n            Note that values which are later mutated may result in\n            non-deterministic behavior from observers that schedule work for\n            later execution.\n        \"\"\"\n        self.emit(LogLevel.info, format, **kwargs)\n\n\n    def warn(self, format=None, **kwargs):\n        \"\"\"\n        Emit a log event at log level L{LogLevel.warn}.\n\n        @param format: a message format using new-style (PEP 3101) formatting.\n            The logging event (which is a L{dict}) is used to render this\n            format string.\n\n        @param kwargs: additional key/value pairs to include in the event.\n            Note that values which are later mutated may result in\n            non-deterministic behavior from observers that schedule work for\n            later execution.\n        \"\"\"\n        self.emit(LogLevel.warn, format, **kwargs)\n\n\n    def error(self, format=None, **kwargs):\n        \"\"\"\n        Emit a log event at log level L{LogLevel.error}.\n\n        @param format: a message format using new-style (PEP 3101) formatting.\n            The logging event (which is a L{dict}) is used to render this\n            format string.\n\n        @param kwargs: additional key/value pairs to include in the event.\n            Note that values which are later mutated may result in\n            non-deterministic behavior from observers that schedule work for\n            later execution.\n        \"\"\"\n        self.emit(LogLevel.error, format, **kwargs)\n\n\n    def critical(self, format=None, **kwargs):\n        \"\"\"\n        Emit a log event at log level L{LogLevel.critical}.\n\n        @param format: a message format using new-style (PEP 3101) formatting.\n            The logging event (which is a L{dict}) is used to render this\n            format string.\n\n        @param kwargs: additional key/value pairs to include in the event.\n            Note that values which are later mutated may result in\n            non-deterministic behavior from observers that schedule work for\n            later execution.\n        \"\"\"\n        self.emit(LogLevel.critical, format, **kwargs)\n\n\n\n_log = Logger()\n_loggerFor = lambda obj:_log.__get__(obj, obj.__class__)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_observer.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_observer -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nBasic log observers.\n\"\"\"\n\nfrom zope.interface import Interface, implementer\n\nfrom twisted.python.failure import Failure\nfrom ._logger import Logger\n\n\n\nOBSERVER_DISABLED = (\n    \"Temporarily disabling observer {observer} due to exception: {log_failure}\"\n)\n\n\n\nclass ILogObserver(Interface):\n    \"\"\"\n    An observer which can handle log events.\n\n    Unlike most interfaces within Twisted, an L{ILogObserver} I{must be\n    thread-safe}.  Log observers may be called indiscriminately from many\n    different threads, as any thread may wish to log a message at any time.\n    \"\"\"\n\n    def __call__(event):\n        \"\"\"\n        Log an event.\n\n        @type event: C{dict} with (native) C{str} keys.\n        @param event: A dictionary with arbitrary keys as defined by the\n            application emitting logging events, as well as keys added by the\n            logging system.  The logging system reserves the right to set any\n            key beginning with the prefix C{\"log_\"}; applications should not\n            use any key so named.  Currently, the following keys are used by\n            the logging system in some way, if they are present (they are all\n            optional):\n\n                - C{\"log_format\"}: a PEP-3101-style format string which draws\n                  upon the keys in the event as its values, used to format the\n                  event for human consumption.\n\n                - C{\"log_flattened\"}: a dictionary mapping keys derived from\n                  the names and format values used in the C{\"log_format\"}\n                  string to their values.  This is used to preserve some\n                  structured information for use with\n                  L{twisted.logger.extractField}.\n\n                - C{\"log_trace\"}: A L{list} designed to capture information\n                  about which L{LogPublisher}s have observed the event.\n\n                - C{\"log_level\"}: a L{log level\n                  <twisted.logger.LogLevel>} constant, indicating the\n                  importance of and audience for this event.\n\n                - C{\"log_namespace\"}: a namespace for the emitter of the event,\n                  given as a unicode string.\n\n                - C{\"log_system\"}: a string indicating the network event or\n                  method call which resulted in the message being logged.\n        \"\"\"\n\n\n\n@implementer(ILogObserver)\nclass LogPublisher(object):\n    \"\"\"\n    I{ILogObserver} that fans out events to other observers.\n\n    Keeps track of a set of L{ILogObserver} objects and forwards\n    events to each.\n    \"\"\"\n\n    def __init__(self, *observers):\n        self._observers = list(observers)\n        self.log = Logger(observer=self)\n\n\n    def addObserver(self, observer):\n        \"\"\"\n        Registers an observer with this publisher.\n\n        @param observer: An L{ILogObserver} to add.\n        \"\"\"\n        if not callable(observer):\n            raise TypeError(\"Observer is not callable: {0!r}\".format(observer))\n        if observer not in self._observers:\n            self._observers.append(observer)\n\n\n    def removeObserver(self, observer):\n        \"\"\"\n        Unregisters an observer with this publisher.\n\n        @param observer: An L{ILogObserver} to remove.\n        \"\"\"\n        try:\n            self._observers.remove(observer)\n        except ValueError:\n            pass\n\n\n    def __call__(self, event):\n        \"\"\"\n        Forward events to contained observers.\n        \"\"\"\n        if \"log_trace\" in event:\n            def trace(observer):\n                \"\"\"\n                Add tracing information for an observer.\n\n                @param observer: an observer being forwarded to\n                @type observer: L{ILogObserver}\n                \"\"\"\n                event[\"log_trace\"].append((self, observer))\n        else:\n            trace = None\n\n        brokenObservers = []\n\n        for observer in self._observers:\n            if trace is not None:\n                trace(observer)\n\n            try:\n                observer(event)\n            except Exception:\n                brokenObservers.append((observer, Failure()))\n\n        for brokenObserver, failure in brokenObservers:\n            errorLogger = self._errorLoggerForObserver(brokenObserver)\n            errorLogger.failure(\n                OBSERVER_DISABLED,\n                failure=failure,\n                observer=brokenObserver,\n            )\n\n\n    def _errorLoggerForObserver(self, observer):\n        \"\"\"\n        Create an error-logger based on this logger, which does not contain the\n        given bad observer.\n\n        @param observer: The observer which previously had an error.\n        @type observer: L{ILogObserver}\n\n        @return: L{None}\n        \"\"\"\n        errorPublisher = LogPublisher(*[\n            obs for obs in self._observers\n            if obs is not observer\n        ])\n        return Logger(observer=errorPublisher)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_stdlib.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_stdlib -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nIntegration with Python standard library logging.\n\"\"\"\n\nimport logging as stdlibLogging\n\nfrom zope.interface import implementer\n\nfrom twisted.python.compat import _PY3, currentframe, unicode\nfrom ._levels import LogLevel\nfrom ._format import formatEvent\nfrom ._observer import ILogObserver\n\n\n\n# Mappings to Python's logging module\ntoStdlibLogLevelMapping = {\n    LogLevel.debug: stdlibLogging.DEBUG,\n    LogLevel.info: stdlibLogging.INFO,\n    LogLevel.warn: stdlibLogging.WARNING,\n    LogLevel.error: stdlibLogging.ERROR,\n    LogLevel.critical: stdlibLogging.CRITICAL,\n}\n\ndef _reverseLogLevelMapping():\n    \"\"\"\n    Reverse the above mapping, adding both the numerical keys used above and\n    the corresponding string keys also used by python logging.\n    @return: the reversed mapping\n    \"\"\"\n    mapping = {}\n    for logLevel, pyLogLevel in toStdlibLogLevelMapping.items():\n        mapping[pyLogLevel] = logLevel\n        mapping[stdlibLogging.getLevelName(pyLogLevel)] = logLevel\n    return mapping\n\nfromStdlibLogLevelMapping = _reverseLogLevelMapping()\n\n\n\n@implementer(ILogObserver)\nclass STDLibLogObserver(object):\n    \"\"\"\n    Log observer that writes to the python standard library's C{logging}\n    module.\n\n    @note: Warning: specific logging configurations (example: network) can lead\n        to this observer blocking.  Nothing is done here to prevent that, so be\n        sure to not to configure the standard library logging module to block\n        when used in conjunction with this module: code within Twisted, such as\n        twisted.web, assumes that logging does not block.\n\n    @cvar defaultStackDepth: This is the default number of frames that it takes\n        to get from L{STDLibLogObserver} through the logging module, plus one;\n        in other words, the number of frames if you were to call a\n        L{STDLibLogObserver} directly.  This is useful to use as an offset for\n        the C{stackDepth} parameter to C{__init__}, to add frames for other\n        publishers.\n    \"\"\"\n\n    defaultStackDepth = 4\n\n    def __init__(self, name=\"twisted\", stackDepth=defaultStackDepth):\n        \"\"\"\n        @param loggerName: logger identifier.\n        @type loggerName: C{str}\n\n        @param stackDepth: The depth of the stack to investigate for caller\n            metadata.\n        @type stackDepth: L{int}\n        \"\"\"\n        self.logger = stdlibLogging.getLogger(name)\n        self.logger.findCaller = self._findCaller\n        self.stackDepth = stackDepth\n\n\n    def _findCaller(self, stackInfo=False, stackLevel=1):\n        \"\"\"\n        Based on the stack depth passed to this L{STDLibLogObserver}, identify\n        the calling function.\n\n        @param stackInfo: Whether or not to construct stack information.\n            (Currently ignored.)\n        @type stackInfo: L{bool}\n\n        @param stackLevel: The number of stack frames to skip when determining\n            the caller (currently ignored; use stackDepth on the instance).\n        @type stackLevel: L{int}\n\n        @return: Depending on Python version, either a 3-tuple of (filename,\n            lineno, name) or a 4-tuple of that plus stack information.\n        @rtype: L{tuple}\n        \"\"\"\n        f = currentframe(self.stackDepth)\n        co = f.f_code\n        if _PY3:\n            extra = (None,)\n        else:\n            extra = ()\n        return (co.co_filename, f.f_lineno, co.co_name) + extra\n\n\n    def __call__(self, event):\n        \"\"\"\n        Format an event and bridge it to Python logging.\n        \"\"\"\n        level = event.get(\"log_level\", LogLevel.info)\n        failure = event.get('log_failure')\n        if failure is None:\n            excInfo = None\n        else:\n            excInfo = (\n                failure.type, failure.value, failure.getTracebackObject())\n        stdlibLevel = toStdlibLogLevelMapping.get(level, stdlibLogging.INFO)\n        self.logger.log(\n            stdlibLevel, StringifiableFromEvent(event), exc_info=excInfo)\n\n\n\nclass StringifiableFromEvent(object):\n    \"\"\"\n    An object that implements C{__str__()} in order to defer the work of\n    formatting until it's converted into a C{str}.\n    \"\"\"\n    def __init__(self, event):\n        \"\"\"\n        @param event: An event.\n        @type event: L{dict}\n        \"\"\"\n        self.event = event\n\n\n    def __unicode__(self):\n        return formatEvent(self.event)\n\n\n    def __bytes__(self):\n        return unicode(self).encode(\"utf-8\")\n\n    if _PY3:\n        __str__ = __unicode__\n    else:\n        __str__ = __bytes__\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/_util.py",
    "content": "# -*- test-case-name: twisted.logger.test.test_util -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nLogging utilities.\n\"\"\"\n\n\n\ndef formatTrace(trace):\n    \"\"\"\n    Format a trace (that is, the contents of the C{log_trace} key of a log\n    event) as a visual indication of the message's propagation through various\n    observers.\n\n    @param trace: the contents of the C{log_trace} key from an event.\n    @type trace: object\n\n    @return: A multi-line string with indentation and arrows indicating the\n        flow of the message through various observers.\n    @rtype: L{unicode}\n    \"\"\"\n    def formatWithName(obj):\n        if hasattr(obj, \"name\"):\n            return u\"{0} ({1})\".format(obj, obj.name)\n        else:\n            return u\"{0}\".format(obj)\n\n    result = []\n    lineage = []\n\n    for parent, child in trace:\n        if not lineage or lineage[-1] is not parent:\n            if parent in lineage:\n                while lineage[-1] is not parent:\n                    lineage.pop()\n\n            else:\n                if not lineage:\n                    result.append(u\"{0}\\n\".format(formatWithName(parent)))\n\n                lineage.append(parent)\n\n        result.append(u\"  \" * len(lineage))\n        result.append(u\"-> {0}\\n\".format(formatWithName(child)))\n\n    return u\"\".join(result)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/__init__.py",
    "content": "# -*- test-case-name: twisted.logger.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nUnit tests for L{twisted.logger}.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_buffer.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._buffer}.\n\"\"\"\n\nfrom zope.interface.verify import verifyObject, BrokenMethodImplementation\n\nfrom twisted.trial import unittest\n\nfrom .._observer import ILogObserver\nfrom .._buffer import LimitedHistoryLogObserver\n\n\n\nclass LimitedHistoryLogObserverTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{LimitedHistoryLogObserver}.\n    \"\"\"\n\n    def test_interface(self):\n        \"\"\"\n        L{LimitedHistoryLogObserver} provides L{ILogObserver}.\n        \"\"\"\n        observer = LimitedHistoryLogObserver(0)\n        try:\n            verifyObject(ILogObserver, observer)\n        except BrokenMethodImplementation as e:\n            self.fail(e)\n\n\n    def test_order(self):\n        \"\"\"\n        L{LimitedHistoryLogObserver} saves history in the order it is received.\n        \"\"\"\n        size = 4\n        events = [dict(n=n) for n in range(size//2)]\n        observer = LimitedHistoryLogObserver(size)\n\n        for event in events:\n            observer(event)\n\n        outEvents = []\n        observer.replayTo(outEvents.append)\n        self.assertEqual(events, outEvents)\n\n\n    def test_limit(self):\n        \"\"\"\n        When more events than a L{LimitedHistoryLogObserver}'s maximum size are\n        buffered, older events will be dropped.\n        \"\"\"\n        size = 4\n        events = [dict(n=n) for n in range(size*2)]\n        observer = LimitedHistoryLogObserver(size)\n\n        for event in events:\n            observer(event)\n        outEvents = []\n        observer.replayTo(outEvents.append)\n        self.assertEqual(events[-size:], outEvents)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_capture.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._capture}.\n\"\"\"\n\nfrom twisted.logger import Logger, LogLevel\nfrom twisted.trial.unittest import TestCase\n\nfrom .._capture import capturedLogs\n\n\n\nclass LogCaptureTests(TestCase):\n    \"\"\"\n    Tests for L{LogCaptureTests}.\n    \"\"\"\n\n    log = Logger()\n\n\n    def test_capture(self):\n        \"\"\"\n        Events logged within context are captured.\n        \"\"\"\n        foo = object()\n\n        with capturedLogs() as captured:\n            self.log.debug(\"Capture this, please\", foo=foo)\n            self.log.info(\"Capture this too, please\", foo=foo)\n\n        self.assertTrue(len(captured) == 2)\n        self.assertEqual(captured[0][\"log_format\"], \"Capture this, please\")\n        self.assertEqual(captured[0][\"log_level\"], LogLevel.debug)\n        self.assertEqual(captured[0][\"foo\"], foo)\n        self.assertEqual(captured[1][\"log_format\"], \"Capture this too, please\")\n        self.assertEqual(captured[1][\"log_level\"], LogLevel.info)\n        self.assertEqual(captured[1][\"foo\"], foo)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_file.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._file}.\n\"\"\"\n\nfrom io import StringIO\n\nfrom zope.interface.verify import verifyObject, BrokenMethodImplementation\n\nfrom twisted.trial.unittest import TestCase\n\nfrom twisted.python.failure import Failure\nfrom twisted.python.compat import unicode\nfrom .._observer import ILogObserver\nfrom .._file import FileLogObserver\nfrom .._file import textFileLogObserver\n\n\n\nclass FileLogObserverTests(TestCase):\n    \"\"\"\n    Tests for L{FileLogObserver}.\n    \"\"\"\n\n    def test_interface(self):\n        \"\"\"\n        L{FileLogObserver} is an L{ILogObserver}.\n        \"\"\"\n        with StringIO() as fileHandle:\n            observer = FileLogObserver(fileHandle, lambda e: unicode(e))\n            try:\n                verifyObject(ILogObserver, observer)\n            except BrokenMethodImplementation as e:\n                self.fail(e)\n\n\n    def test_observeWrites(self):\n        \"\"\"\n        L{FileLogObserver} writes to the given file when it observes events.\n        \"\"\"\n        with StringIO() as fileHandle:\n            observer = FileLogObserver(fileHandle, lambda e: unicode(e))\n            event = dict(x=1)\n            observer(event)\n            self.assertEqual(fileHandle.getvalue(), unicode(event))\n\n\n    def _test_observeWrites(self, what, count):\n        \"\"\"\n        Verify that observer performs an expected number of writes when the\n        formatter returns a given value.\n\n        @param what: the value for the formatter to return.\n        @type what: L{unicode}\n\n        @param count: the expected number of writes.\n        @type count: L{int}\n        \"\"\"\n        with DummyFile() as fileHandle:\n            observer = FileLogObserver(fileHandle, lambda e: what)\n            event = dict(x=1)\n            observer(event)\n            self.assertEqual(fileHandle.writes, count)\n\n\n    def test_observeWritesNone(self):\n        \"\"\"\n        L{FileLogObserver} does not write to the given file when it observes\n        events and C{formatEvent} returns L{None}.\n        \"\"\"\n        self._test_observeWrites(None, 0)\n\n\n    def test_observeWritesEmpty(self):\n        \"\"\"\n        L{FileLogObserver} does not write to the given file when it observes\n        events and C{formatEvent} returns C{u\"\"}.\n        \"\"\"\n        self._test_observeWrites(u\"\", 0)\n\n\n    def test_observeFlushes(self):\n        \"\"\"\n        L{FileLogObserver} calles C{flush()} on the output file when it\n        observes an event.\n        \"\"\"\n        with DummyFile() as fileHandle:\n            observer = FileLogObserver(fileHandle, lambda e: unicode(e))\n            event = dict(x=1)\n            observer(event)\n            self.assertEqual(fileHandle.flushes, 1)\n\n\nclass TextFileLogObserverTests(TestCase):\n    \"\"\"\n    Tests for L{textFileLogObserver}.\n    \"\"\"\n\n    def test_returnsFileLogObserver(self):\n        \"\"\"\n        L{textFileLogObserver} returns a L{FileLogObserver}.\n        \"\"\"\n        with StringIO() as fileHandle:\n            observer = textFileLogObserver(fileHandle)\n            self.assertIsInstance(observer, FileLogObserver)\n\n\n    def test_outFile(self):\n        \"\"\"\n        Returned L{FileLogObserver} has the correct outFile.\n        \"\"\"\n        with StringIO() as fileHandle:\n            observer = textFileLogObserver(fileHandle)\n            self.assertIs(observer._outFile, fileHandle)\n\n\n    def test_timeFormat(self):\n        \"\"\"\n        Returned L{FileLogObserver} has the correct outFile.\n        \"\"\"\n        with StringIO() as fileHandle:\n            observer = textFileLogObserver(fileHandle, timeFormat=u\"%f\")\n            observer(dict(log_format=u\"XYZZY\", log_time=112345.6))\n            self.assertEqual(fileHandle.getvalue(), u\"600000 [-#-] XYZZY\\n\")\n\n\n    def test_observeFailure(self):\n        \"\"\"\n        If the C{\"log_failure\"} key exists in an event, the observer appends\n        the failure's traceback to the output.\n        \"\"\"\n        with StringIO() as fileHandle:\n            observer = textFileLogObserver(fileHandle)\n\n            try:\n                1 / 0\n            except ZeroDivisionError:\n                failure = Failure()\n\n            event = dict(log_failure=failure)\n            observer(event)\n            output = fileHandle.getvalue()\n            self.assertTrue(output.split(\"\\n\")[1].startswith(\"\\tTraceback \"),\n                            msg=repr(output))\n\n\n    def test_observeFailureThatRaisesInGetTraceback(self):\n        \"\"\"\n        If the C{\"log_failure\"} key exists in an event, and contains an object\n        that raises when you call its C{getTraceback()}, then the observer\n        appends a message noting the problem, instead of raising.\n        \"\"\"\n        with StringIO() as fileHandle:\n            observer = textFileLogObserver(fileHandle)\n            event = dict(log_failure=object())  # object has no getTraceback()\n            observer(event)\n            output = fileHandle.getvalue()\n            expected = (\n                \"(UNABLE TO OBTAIN TRACEBACK FROM EVENT)\"\n            )\n            self.assertIn(expected, output)\n\n\n\nclass DummyFile(object):\n    \"\"\"\n    File that counts writes and flushes.\n    \"\"\"\n\n    def __init__(self):\n        self.writes = 0\n        self.flushes = 0\n\n\n    def write(self, data):\n        \"\"\"\n        Write data.\n\n        @param data: data\n        @type data: L{unicode} or L{bytes}\n        \"\"\"\n        self.writes += 1\n\n\n    def flush(self):\n        \"\"\"\n        Flush buffers.\n        \"\"\"\n        self.flushes += 1\n\n\n    def __enter__(self):\n        return self\n\n\n    def __exit__(self, exc_type, exc_value, traceback):\n        pass\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_filter.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._filter}.\n\"\"\"\n\nfrom zope.interface.verify import verifyObject, BrokenMethodImplementation\n\nfrom twisted.trial import unittest\n\nfrom .._levels import InvalidLogLevelError\nfrom .._levels import LogLevel\nfrom .._observer import ILogObserver\nfrom .._observer import LogPublisher\nfrom .._filter import FilteringLogObserver\nfrom .._filter import PredicateResult\nfrom .._filter import LogLevelFilterPredicate\n\n\n\nclass FilteringLogObserverTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{FilteringLogObserver}.\n    \"\"\"\n\n    def test_interface(self):\n        \"\"\"\n        L{FilteringLogObserver} is an L{ILogObserver}.\n        \"\"\"\n        observer = FilteringLogObserver(lambda e: None, ())\n        try:\n            verifyObject(ILogObserver, observer)\n        except BrokenMethodImplementation as e:\n            self.fail(e)\n\n\n    def filterWith(self, filters, other=False):\n        \"\"\"\n        Apply a set of pre-defined filters on a known set of events and return\n        the filtered list of event numbers.\n\n        The pre-defined events are four events with a C{count} attribute set to\n        C{0}, C{1}, C{2}, and C{3}.\n\n        @param filters: names of the filters to apply.\n\n            Options are:\n\n                - C{\"twoMinus\"} (count <=2),\n\n                - C{\"twoPlus\"} (count >= 2),\n\n                - C{\"notTwo\"} (count != 2),\n\n                - C{\"no\"} (False).\n\n        @type filters: iterable of str\n\n        @param other: Whether to return a list of filtered events as well.\n        @type other: L{bool}\n\n        @return: event numbers or 2-tuple of lists of event numbers.\n        @rtype: L{list} of L{int} or 2-L{tuple} of L{list} of L{int}\n        \"\"\"\n        events = [\n            dict(count=0),\n            dict(count=1),\n            dict(count=2),\n            dict(count=3),\n        ]\n\n        class Filters(object):\n            @staticmethod\n            def twoMinus(event):\n                \"\"\"\n                count <= 2\n\n                @param event: an event\n                @type event: dict\n\n                @return: L{PredicateResult.yes} if C{event[\"count\"] <= 2},\n                    otherwise L{PredicateResult.maybe}.\n                \"\"\"\n                if event[\"count\"] <= 2:\n                    return PredicateResult.yes\n                return PredicateResult.maybe\n\n            @staticmethod\n            def twoPlus(event):\n                \"\"\"\n                count >= 2\n\n                @param event: an event\n                @type event: dict\n\n                @return: L{PredicateResult.yes} if C{event[\"count\"] >= 2},\n                    otherwise L{PredicateResult.maybe}.\n                \"\"\"\n                if event[\"count\"] >= 2:\n                    return PredicateResult.yes\n                return PredicateResult.maybe\n\n            @staticmethod\n            def notTwo(event):\n                \"\"\"\n                count != 2\n\n                @param event: an event\n                @type event: dict\n\n                @return: L{PredicateResult.yes} if C{event[\"count\"] != 2},\n                    otherwise L{PredicateResult.maybe}.\n                \"\"\"\n                if event[\"count\"] == 2:\n                    return PredicateResult.no\n                return PredicateResult.maybe\n\n            @staticmethod\n            def no(event):\n                \"\"\"\n                No way, man.\n\n                @param event: an event\n                @type event: dict\n\n                @return: L{PredicateResult.no}\n                \"\"\"\n                return PredicateResult.no\n\n            @staticmethod\n            def bogus(event):\n                \"\"\"\n                Bogus result.\n\n                @param event: an event\n                @type event: dict\n\n                @return: something other than a valid predicate result.\n                \"\"\"\n                return None\n\n        predicates = (getattr(Filters, f) for f in filters)\n        eventsSeen = []\n        eventsNotSeen = []\n        trackingObserver = eventsSeen.append\n        if other:\n            extra = [eventsNotSeen.append]\n        else:\n            extra = []\n        filteringObserver = FilteringLogObserver(\n            trackingObserver, predicates, *extra\n        )\n        for e in events:\n            filteringObserver(e)\n\n        if extra:\n            return (\n                [e[\"count\"] for e in eventsSeen],\n                [e[\"count\"] for e in eventsNotSeen],\n            )\n        return [e[\"count\"] for e in eventsSeen]\n\n\n    def test_shouldLogEventNoFilters(self):\n        \"\"\"\n        No filters: all events come through.\n        \"\"\"\n        self.assertEqual(self.filterWith([]), [0, 1, 2, 3])\n\n\n    def test_shouldLogEventNoFilter(self):\n        \"\"\"\n        Filter with negative predicate result.\n        \"\"\"\n        self.assertEqual(self.filterWith([\"notTwo\"]), [0, 1, 3])\n\n\n    def test_shouldLogEventOtherObserver(self):\n        \"\"\"\n        Filtered results get sent to the other observer, if passed.\n        \"\"\"\n        self.assertEqual(self.filterWith([\"notTwo\"], True), ([0, 1, 3], [2]))\n\n\n    def test_shouldLogEventYesFilter(self):\n        \"\"\"\n        Filter with positive predicate result.\n        \"\"\"\n        self.assertEqual(self.filterWith([\"twoPlus\"]), [0, 1, 2, 3])\n\n\n    def test_shouldLogEventYesNoFilter(self):\n        \"\"\"\n        Series of filters with positive and negative predicate results.\n        \"\"\"\n        self.assertEqual(self.filterWith([\"twoPlus\", \"no\"]), [2, 3])\n\n\n    def test_shouldLogEventYesYesNoFilter(self):\n        \"\"\"\n        Series of filters with positive, positive and negative predicate\n        results.\n        \"\"\"\n        self.assertEqual(\n            self.filterWith([\"twoPlus\", \"twoMinus\", \"no\"]),\n            [0, 1, 2, 3]\n        )\n\n\n    def test_shouldLogEventBadPredicateResult(self):\n        \"\"\"\n        Filter with invalid predicate result.\n        \"\"\"\n        self.assertRaises(TypeError, self.filterWith, [\"bogus\"])\n\n\n    def test_call(self):\n        \"\"\"\n        Test filtering results from each predicate type.\n        \"\"\"\n        e = dict(obj=object())\n\n        def callWithPredicateResult(result):\n            seen = []\n            observer = FilteringLogObserver(\n                lambda e: seen.append(e),\n                (lambda e: result,)\n            )\n            observer(e)\n            return seen\n\n        self.assertIn(e, callWithPredicateResult(PredicateResult.yes))\n        self.assertIn(e, callWithPredicateResult(PredicateResult.maybe))\n        self.assertNotIn(e, callWithPredicateResult(PredicateResult.no))\n\n\n    def test_trace(self):\n        \"\"\"\n        Tracing keeps track of forwarding through the filtering observer.\n        \"\"\"\n        event = dict(log_trace=[])\n\n        oYes = lambda e: None\n        oNo = lambda e: None\n\n        def testObserver(e):\n            self.assertIs(e, event)\n            self.assertEqual(\n                event[\"log_trace\"],\n                [\n                    (publisher, yesFilter),\n                    (yesFilter, oYes),\n                    (publisher, noFilter),\n                    # ... noFilter doesn't call oNo\n                    (publisher, oTest),\n                ]\n            )\n        oTest = testObserver\n\n        yesFilter = FilteringLogObserver(\n            oYes,\n            (lambda e: PredicateResult.yes,)\n        )\n        noFilter = FilteringLogObserver(\n            oNo,\n            (lambda e: PredicateResult.no,)\n        )\n\n        publisher = LogPublisher(yesFilter, noFilter, testObserver)\n        publisher(event)\n\n\n\nclass LogLevelFilterPredicateTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{LogLevelFilterPredicate}.\n    \"\"\"\n\n    def test_defaultLogLevel(self):\n        \"\"\"\n        Default log level is used.\n        \"\"\"\n        predicate = LogLevelFilterPredicate()\n\n        self.assertEqual(\n            predicate.logLevelForNamespace(None),\n            predicate.defaultLogLevel\n        )\n        self.assertEqual(\n            predicate.logLevelForNamespace(\"\"),\n            predicate.defaultLogLevel\n        )\n        self.assertEqual(\n            predicate.logLevelForNamespace(\"rocker.cool.namespace\"),\n            predicate.defaultLogLevel\n        )\n\n\n    def test_setLogLevel(self):\n        \"\"\"\n        Setting and retrieving log levels.\n        \"\"\"\n        predicate = LogLevelFilterPredicate()\n\n        predicate.setLogLevelForNamespace(None, LogLevel.error)\n        predicate.setLogLevelForNamespace(\"twext.web2\", LogLevel.debug)\n        predicate.setLogLevelForNamespace(\"twext.web2.dav\", LogLevel.warn)\n\n        self.assertEqual(\n            predicate.logLevelForNamespace(None),\n            LogLevel.error\n        )\n        self.assertEqual(\n            predicate.logLevelForNamespace(\"twisted\"),\n            LogLevel.error\n        )\n        self.assertEqual(\n            predicate.logLevelForNamespace(\"twext.web2\"),\n            LogLevel.debug\n        )\n        self.assertEqual(\n            predicate.logLevelForNamespace(\"twext.web2.dav\"),\n            LogLevel.warn\n        )\n        self.assertEqual(\n            predicate.logLevelForNamespace(\"twext.web2.dav.test\"),\n            LogLevel.warn\n        )\n        self.assertEqual(\n            predicate.logLevelForNamespace(\"twext.web2.dav.test1.test2\"),\n            LogLevel.warn\n        )\n\n\n    def test_setInvalidLogLevel(self):\n        \"\"\"\n        Can't pass invalid log levels to C{setLogLevelForNamespace()}.\n        \"\"\"\n        predicate = LogLevelFilterPredicate()\n\n        self.assertRaises(\n            InvalidLogLevelError,\n            predicate.setLogLevelForNamespace, \"twext.web2\", object()\n        )\n\n        # Level must be a constant, not the name of a constant\n        self.assertRaises(\n            InvalidLogLevelError,\n            predicate.setLogLevelForNamespace, \"twext.web2\", \"debug\"\n        )\n\n\n    def test_clearLogLevels(self):\n        \"\"\"\n        Clearing log levels.\n        \"\"\"\n        predicate = LogLevelFilterPredicate()\n\n        predicate.setLogLevelForNamespace(\"twext.web2\", LogLevel.debug)\n        predicate.setLogLevelForNamespace(\"twext.web2.dav\", LogLevel.error)\n\n        predicate.clearLogLevels()\n\n        self.assertEqual(\n            predicate.logLevelForNamespace(\"twisted\"),\n            predicate.defaultLogLevel\n        )\n        self.assertEqual(\n            predicate.logLevelForNamespace(\"twext.web2\"),\n            predicate.defaultLogLevel\n        )\n        self.assertEqual(\n            predicate.logLevelForNamespace(\"twext.web2.dav\"),\n            predicate.defaultLogLevel\n        )\n        self.assertEqual(\n            predicate.logLevelForNamespace(\"twext.web2.dav.test\"),\n            predicate.defaultLogLevel\n        )\n        self.assertEqual(\n            predicate.logLevelForNamespace(\"twext.web2.dav.test1.test2\"),\n            predicate.defaultLogLevel\n        )\n\n\n    def test_filtering(self):\n        \"\"\"\n        Events are filtered based on log level/namespace.\n        \"\"\"\n        predicate = LogLevelFilterPredicate()\n\n        predicate.setLogLevelForNamespace(None, LogLevel.error)\n        predicate.setLogLevelForNamespace(\"twext.web2\", LogLevel.debug)\n        predicate.setLogLevelForNamespace(\"twext.web2.dav\", LogLevel.warn)\n\n        def checkPredicate(namespace, level, expectedResult):\n            event = dict(log_namespace=namespace, log_level=level)\n            self.assertEqual(expectedResult, predicate(event))\n\n        checkPredicate(\"\", LogLevel.debug, PredicateResult.no)\n        checkPredicate(\"\", LogLevel.error, PredicateResult.maybe)\n\n        checkPredicate(\"twext.web2\", LogLevel.debug, PredicateResult.maybe)\n        checkPredicate(\"twext.web2\", LogLevel.error, PredicateResult.maybe)\n\n        checkPredicate(\"twext.web2.dav\", LogLevel.debug, PredicateResult.no)\n        checkPredicate(\"twext.web2.dav\", LogLevel.error, PredicateResult.maybe)\n\n        checkPredicate(None, LogLevel.critical, PredicateResult.no)\n        checkPredicate(\"twext.web2\", None, PredicateResult.no)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_flatten.py",
    "content": "# -*- coding: utf-8 -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._format}.\n\"\"\"\n\nfrom itertools import count\nimport json\n\ntry:\n    from time import tzset\n    # We should upgrade to a version of pyflakes that does not require this.\n    tzset\nexcept ImportError:\n    tzset = None\n\nfrom twisted.trial import unittest\n\nfrom .._format import formatEvent\nfrom .._flatten import (\n    flattenEvent, extractField, KeyFlattener, aFormatter\n)\n\n\n\nclass FlatFormattingTests(unittest.TestCase):\n    \"\"\"\n    Tests for flattened event formatting functions.\n    \"\"\"\n\n    def test_formatFlatEvent(self):\n        \"\"\"\n        L{flattenEvent} will \"flatten\" an event so that, if scrubbed of all but\n        serializable objects, it will preserve all necessary data to be\n        formatted once serialized.  When presented with an event thusly\n        flattened, L{formatEvent} will produce the same output.\n        \"\"\"\n        counter = count()\n\n        class Ephemeral(object):\n            attribute = \"value\"\n\n        event1 = dict(\n            log_format=(\n                \"callable: {callme()} \"\n                \"attribute: {object.attribute} \"\n                \"numrepr: {number!r} \"\n                \"numstr: {number!s} \"\n                \"strrepr: {string!r} \"\n                \"unistr: {unistr!s}\"\n            ),\n            callme=lambda: next(counter), object=Ephemeral(),\n            number=7, string=\"hello\", unistr=u\"ö\"\n        )\n\n        flattenEvent(event1)\n\n        event2 = dict(event1)\n        del event2[\"callme\"]\n        del event2[\"object\"]\n        event3 = json.loads(json.dumps(event2))\n        self.assertEqual(\n            formatEvent(event3),\n            (\n                u\"callable: 0 \"\n                \"attribute: value \"\n                \"numrepr: 7 \"\n                \"numstr: 7 \"\n                \"strrepr: 'hello' \"\n                u\"unistr: ö\"\n            )\n        )\n\n\n    def test_formatFlatEventBadFormat(self):\n        \"\"\"\n        If the format string is invalid, an error is produced.\n        \"\"\"\n        event1 = dict(\n            log_format=(\n                \"strrepr: {string!X}\"\n            ),\n            string=\"hello\",\n        )\n\n        flattenEvent(event1)\n        event2 = json.loads(json.dumps(event1))\n\n        self.assertTrue(\n            formatEvent(event2).startswith(u\"Unable to format event\")\n        )\n\n\n    def test_formatFlatEventWithMutatedFields(self):\n        \"\"\"\n        L{formatEvent} will prefer the stored C{str()} or C{repr()} value for\n        an object, in case the other version.\n        \"\"\"\n        class Unpersistable(object):\n            \"\"\"\n            Unpersitable object.\n            \"\"\"\n            destructed = False\n\n            def selfDestruct(self):\n                \"\"\"\n                Self destruct.\n                \"\"\"\n                self.destructed = True\n\n            def __repr__(self):\n                if self.destructed:\n                    return \"post-serialization garbage\"\n                else:\n                    return \"un-persistable\"\n\n        up = Unpersistable()\n        event1 = dict(\n            log_format=\"unpersistable: {unpersistable}\", unpersistable=up\n        )\n\n        flattenEvent(event1)\n        up.selfDestruct()\n\n        self.assertEqual(formatEvent(event1), \"unpersistable: un-persistable\")\n\n\n    def test_keyFlattening(self):\n        \"\"\"\n        Test that L{KeyFlattener.flatKey} returns the expected keys for format\n        fields.\n        \"\"\"\n\n        def keyFromFormat(format):\n            for (\n                literalText,\n                fieldName,\n                formatSpec,\n                conversion,\n            ) in aFormatter.parse(format):\n                return KeyFlattener().flatKey(\n                    fieldName, formatSpec, conversion\n                )\n\n        # No name\n        try:\n            self.assertEqual(keyFromFormat(\"{}\"), \"!:\")\n        except ValueError:\n            # In python 2.6, an empty field name causes Formatter.parse to\n            # raise ValueError.\n            # In Python 2.7, it's allowed, so this exception is unexpected.\n            raise\n\n        # Just a name\n        self.assertEqual(keyFromFormat(\"{foo}\"), \"foo!:\")\n\n        # Add conversion\n        self.assertEqual(keyFromFormat(\"{foo!s}\"), \"foo!s:\")\n        self.assertEqual(keyFromFormat(\"{foo!r}\"), \"foo!r:\")\n\n        # Add format spec\n        self.assertEqual(keyFromFormat(\"{foo:%s}\"), \"foo!:%s\")\n        self.assertEqual(keyFromFormat(\"{foo:!}\"), \"foo!:!\")\n        self.assertEqual(keyFromFormat(\"{foo::}\"), \"foo!::\")\n\n        # Both\n        self.assertEqual(keyFromFormat(\"{foo!s:%s}\"), \"foo!s:%s\")\n        self.assertEqual(keyFromFormat(\"{foo!s:!}\"), \"foo!s:!\")\n        self.assertEqual(keyFromFormat(\"{foo!s::}\"), \"foo!s::\")\n        [keyPlusLiteral] = aFormatter.parse(\"{x}\")\n        key = keyPlusLiteral[1:]\n        sameFlattener = KeyFlattener()\n        self.assertEqual(sameFlattener.flatKey(*key), \"x!:\")\n        self.assertEqual(sameFlattener.flatKey(*key), \"x!:/2\")\n\n\n    def _test_formatFlatEvent_fieldNamesSame(self, event=None):\n        \"\"\"\n        The same format field used twice in one event is rendered twice.\n\n        @param event: An event to flatten.  If L{None}, create a new event.\n        @return: C{event} or the event created.\n        \"\"\"\n        if event is None:\n            counter = count()\n\n            class CountStr(object):\n                \"\"\"\n                Hack\n                \"\"\"\n                def __str__(self):\n                    return str(next(counter))\n\n            event = dict(\n                log_format=\"{x} {x}\",\n                x=CountStr(),\n            )\n\n        flattenEvent(event)\n        self.assertEqual(formatEvent(event), u\"0 1\")\n\n        return event\n\n\n    def test_formatFlatEventFieldNamesSame(self):\n        \"\"\"\n        The same format field used twice in one event is rendered twice.\n        \"\"\"\n        self._test_formatFlatEvent_fieldNamesSame()\n\n\n    def test_formatFlatEventFieldNamesSameAgain(self):\n        \"\"\"\n        The same event flattened twice gives the same (already rendered)\n        result.\n        \"\"\"\n        event = self._test_formatFlatEvent_fieldNamesSame()\n        self._test_formatFlatEvent_fieldNamesSame(event)\n\n\n    def test_formatEventFlatTrailingText(self):\n        \"\"\"\n        L{formatEvent} will handle a flattened event with tailing text after\n        a replacement field.\n        \"\"\"\n        event = dict(\n            log_format=\"test {x} trailing\",\n            x='value',\n        )\n        flattenEvent(event)\n\n        result = formatEvent(event)\n\n        self.assertEqual(result, u\"test value trailing\")\n\n\n    def test_extractField(self, flattenFirst=lambda x: x):\n        \"\"\"\n        L{extractField} will extract a field used in the format string.\n\n        @param flattenFirst: callable to flatten an event\n        \"\"\"\n        class ObjectWithRepr(object):\n            def __repr__(self):\n                return \"repr\"\n\n        class Something(object):\n            def __init__(self):\n                self.number = 7\n                self.object = ObjectWithRepr()\n\n            def __getstate__(self):\n                raise NotImplementedError(\"Just in case.\")\n\n        event = dict(\n            log_format=\"{something.number} {something.object}\",\n            something=Something(),\n        )\n\n        flattened = flattenFirst(event)\n\n        def extract(field):\n            return extractField(field, flattened)\n\n        self.assertEqual(extract(\"something.number\"), 7)\n        self.assertEqual(extract(\"something.number!s\"), \"7\")\n        self.assertEqual(extract(\"something.object!s\"), \"repr\")\n\n\n    def test_extractFieldFlattenFirst(self):\n        \"\"\"\n        L{extractField} behaves identically if the event is explicitly\n        flattened first.\n        \"\"\"\n        def flattened(evt):\n            flattenEvent(evt)\n            return evt\n        self.test_extractField(flattened)\n\n\n    def test_flattenEventWithoutFormat(self):\n        \"\"\"\n        L{flattenEvent} will do nothing to an event with no format string.\n        \"\"\"\n        inputEvent = {'a': 'b', 'c': 1}\n        flattenEvent(inputEvent)\n        self.assertEqual(inputEvent, {'a': 'b', 'c': 1})\n\n\n    def test_flattenEventWithInertFormat(self):\n        \"\"\"\n        L{flattenEvent} will do nothing to an event with a format string that\n        contains no format fields.\n        \"\"\"\n        inputEvent = {'a': 'b', 'c': 1, 'log_format': 'simple message'}\n        flattenEvent(inputEvent)\n        self.assertEqual(\n            inputEvent,\n            {\n                'a': 'b',\n                'c': 1,\n                'log_format': 'simple message',\n            }\n        )\n\n\n    def test_flattenEventWithNoneFormat(self):\n        \"\"\"\n        L{flattenEvent} will do nothing to an event with log_format set to\n        None.\n        \"\"\"\n        inputEvent = {'a': 'b', 'c': 1, 'log_format': None}\n        flattenEvent(inputEvent)\n        self.assertEqual(\n            inputEvent,\n            {\n                'a': 'b',\n                'c': 1,\n                'log_format': None,\n            }\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_global.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._global}.\n\"\"\"\n\nfrom __future__ import print_function\n\nimport io\n\nfrom twisted.trial import unittest\n\nfrom .._file import textFileLogObserver\nfrom .._observer import LogPublisher\nfrom .._logger import Logger\nfrom .._global import LogBeginner\nfrom .._global import MORE_THAN_ONCE_WARNING\nfrom .._levels import LogLevel\nfrom ..test.test_stdlib import nextLine\nfrom twisted.python.failure import Failure\n\n\n\ndef compareEvents(test, actualEvents, expectedEvents):\n    \"\"\"\n    Compare two sequences of log events, examining only the the keys which are\n    present in both.\n\n    @param test: a test case doing the comparison\n    @type test: L{unittest.TestCase}\n\n    @param actualEvents: A list of log events that were emitted by a logger.\n    @type actualEvents: L{list} of L{dict}\n\n    @param expectedEvents: A list of log events that were expected by a test.\n    @type expected: L{list} of L{dict}\n    \"\"\"\n    if len(actualEvents) != len(expectedEvents):\n        test.assertEqual(actualEvents, expectedEvents)\n    allMergedKeys = set()\n\n    for event in expectedEvents:\n        allMergedKeys |= set(event.keys())\n\n    def simplify(event):\n        copy = event.copy()\n        for key in event.keys():\n            if key not in allMergedKeys:\n                copy.pop(key)\n        return copy\n\n    simplifiedActual = [simplify(event) for event in actualEvents]\n    test.assertEqual(simplifiedActual, expectedEvents)\n\n\n\nclass LogBeginnerTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{LogBeginner}.\n    \"\"\"\n\n    def setUp(self):\n        self.publisher = LogPublisher()\n        self.errorStream = io.StringIO()\n\n        class NotSys(object):\n            stdout = object()\n            stderr = object()\n\n        class NotWarnings(object):\n            def __init__(self):\n                self.warnings = []\n\n            def showwarning(\n                self, message, category, filename, lineno,\n                file=None, line=None\n            ):\n                \"\"\"\n                Emulate warnings.showwarning.\n\n                @param message: A warning message to emit.\n                @type message: L{str}\n\n                @param category: A warning category to associate with\n                    C{message}.\n                @type category: L{warnings.Warning}\n\n                @param filename: A file name for the source code file issuing\n                    the warning.\n                @type warning: L{str}\n\n                @param lineno: A line number in the source file where the\n                    warning was issued.\n                @type lineno: L{int}\n\n                @param file: A file to write the warning message to.  If\n                    L{None}, write to L{sys.stderr}.\n                @type file: file-like object\n\n                @param line: A line of source code to include with the warning\n                    message. If L{None}, attempt to read the line from\n                    C{filename} and C{lineno}.\n                @type line: L{str}\n                \"\"\"\n                self.warnings.append(\n                    (message, category, filename, lineno, file, line)\n                )\n\n        self.sysModule = NotSys()\n        self.warningsModule = NotWarnings()\n        self.beginner = LogBeginner(\n            self.publisher, self.errorStream, self.sysModule,\n            self.warningsModule\n        )\n\n\n    def test_beginLoggingToAddObservers(self):\n        \"\"\"\n        Test that C{beginLoggingTo()} adds observers.\n        \"\"\"\n        event = dict(foo=1, bar=2)\n\n        events1 = []\n        events2 = []\n\n        o1 = lambda e: events1.append(e)\n        o2 = lambda e: events2.append(e)\n\n        self.beginner.beginLoggingTo((o1, o2))\n        self.publisher(event)\n\n        self.assertEqual([event], events1)\n        self.assertEqual([event], events2)\n\n\n    def test_beginLoggingToBufferedEvents(self):\n        \"\"\"\n        Test that events are buffered until C{beginLoggingTo()} is\n        called.\n        \"\"\"\n        event = dict(foo=1, bar=2)\n\n        events1 = []\n        events2 = []\n\n        o1 = lambda e: events1.append(e)\n        o2 = lambda e: events2.append(e)\n\n        self.publisher(event)  # Before beginLoggingTo; this is buffered\n        self.beginner.beginLoggingTo((o1, o2))\n\n        self.assertEqual([event], events1)\n        self.assertEqual([event], events2)\n\n\n    def _bufferLimitTest(self, limit, beginner):\n        \"\"\"\n        Verify that when more than C{limit} events are logged to L{LogBeginner},\n        only the last C{limit} are replayed by L{LogBeginner.beginLoggingTo}.\n\n        @param limit: The maximum number of events the log beginner should\n            buffer.\n        @type limit: L{int}\n\n        @param beginner: The L{LogBeginner} against which to verify.\n        @type beginner: L{LogBeginner}\n\n        @raise: C{self.failureException} if the wrong events are replayed by\n            C{beginner}.\n\n        @return: L{None}\n        \"\"\"\n        for count in range(limit + 1):\n            self.publisher(dict(count=count))\n        events = []\n        beginner.beginLoggingTo([events.append])\n        self.assertEqual(\n            list(range(1, limit + 1)),\n            list(event[\"count\"] for event in events),\n        )\n\n\n    def test_defaultBufferLimit(self):\n        \"\"\"\n        Up to C{LogBeginner._DEFAULT_BUFFER_SIZE} log events are buffered for\n        replay by L{LogBeginner.beginLoggingTo}.\n        \"\"\"\n        limit = LogBeginner._DEFAULT_BUFFER_SIZE\n        self._bufferLimitTest(limit, self.beginner)\n\n\n    def test_overrideBufferLimit(self):\n        \"\"\"\n        The size of the L{LogBeginner} event buffer can be overridden with the\n        C{initialBufferSize} initilizer argument.\n        \"\"\"\n        limit = 3\n        beginner = LogBeginner(\n            self.publisher, self.errorStream, self.sysModule,\n            self.warningsModule, initialBufferSize=limit,\n        )\n        self._bufferLimitTest(limit, beginner)\n\n\n    def test_beginLoggingToTwice(self):\n        \"\"\"\n        When invoked twice, L{LogBeginner.beginLoggingTo} will emit a log\n        message warning the user that they previously began logging, and add\n        the new log observers.\n        \"\"\"\n        events1 = []\n        events2 = []\n        fileHandle = io.StringIO()\n        textObserver = textFileLogObserver(fileHandle)\n        self.publisher(dict(event=\"prebuffer\"))\n        firstFilename, firstLine = nextLine()\n        self.beginner.beginLoggingTo([events1.append, textObserver])\n        self.publisher(dict(event=\"postbuffer\"))\n        secondFilename, secondLine = nextLine()\n        self.beginner.beginLoggingTo([events2.append, textObserver])\n        self.publisher(dict(event=\"postwarn\"))\n        warning = dict(\n            log_format=MORE_THAN_ONCE_WARNING,\n            log_level=LogLevel.warn,\n            fileNow=secondFilename, lineNow=secondLine,\n            fileThen=firstFilename, lineThen=firstLine\n        )\n\n        compareEvents(\n            self, events1,\n            [\n                dict(event=\"prebuffer\"),\n                dict(event=\"postbuffer\"),\n                warning,\n                dict(event=\"postwarn\")\n            ]\n        )\n        compareEvents(self, events2, [warning, dict(event=\"postwarn\")])\n\n        output = fileHandle.getvalue()\n        self.assertIn('<{0}:{1}>'.format(firstFilename, firstLine),\n                      output)\n        self.assertIn('<{0}:{1}>'.format(secondFilename, secondLine),\n                      output)\n\n\n    def test_criticalLogging(self):\n        \"\"\"\n        Critical messages will be written as text to the error stream.\n        \"\"\"\n        log = Logger(observer=self.publisher)\n        log.info(\"ignore this\")\n        log.critical(\"a critical {message}\", message=\"message\")\n        self.assertEqual(self.errorStream.getvalue(), u\"a critical message\\n\")\n\n\n    def test_criticalLoggingStops(self):\n        \"\"\"\n        Once logging has begun with C{beginLoggingTo}, critical messages are no\n        longer written to the output stream.\n        \"\"\"\n        log = Logger(observer=self.publisher)\n        self.beginner.beginLoggingTo(())\n        log.critical(\"another critical message\")\n        self.assertEqual(self.errorStream.getvalue(), u\"\")\n\n\n    def test_beginLoggingToRedirectStandardIO(self):\n        \"\"\"\n        L{LogBeginner.beginLoggingTo} will re-direct the standard output and\n        error streams by setting the C{stdio} and C{stderr} attributes on its\n        sys module object.\n        \"\"\"\n        x = []\n        self.beginner.beginLoggingTo([x.append])\n        print(\"Hello, world.\", file=self.sysModule.stdout)\n        compareEvents(\n            self, x, [dict(log_namespace=\"stdout\", log_io=\"Hello, world.\")]\n        )\n        del x[:]\n        print(\"Error, world.\", file=self.sysModule.stderr)\n        compareEvents(\n            self, x, [dict(log_namespace=\"stderr\", log_io=\"Error, world.\")]\n        )\n\n\n    def test_beginLoggingToDontRedirect(self):\n        \"\"\"\n        L{LogBeginner.beginLoggingTo} will leave the existing stdout/stderr in\n        place if it has been told not to replace them.\n        \"\"\"\n        oldOut = self.sysModule.stdout\n        oldErr = self.sysModule.stderr\n        self.beginner.beginLoggingTo((), redirectStandardIO=False)\n        self.assertIs(self.sysModule.stdout, oldOut)\n        self.assertIs(self.sysModule.stderr, oldErr)\n\n\n    def test_beginLoggingToPreservesEncoding(self):\n        \"\"\"\n        When L{LogBeginner.beginLoggingTo} redirects stdout/stderr streams, the\n        replacement streams will preserve the encoding of the replaced streams,\n        to minimally disrupt any application relying on a specific encoding.\n        \"\"\"\n\n        weird = io.TextIOWrapper(io.BytesIO(), \"shift-JIS\")\n        weirderr = io.TextIOWrapper(io.BytesIO(), \"big5\")\n\n        self.sysModule.stdout = weird\n        self.sysModule.stderr = weirderr\n\n        x = []\n        self.beginner.beginLoggingTo([x.append])\n        self.assertEqual(self.sysModule.stdout.encoding, \"shift-JIS\")\n        self.assertEqual(self.sysModule.stderr.encoding, \"big5\")\n\n        self.sysModule.stdout.write(b\"\\x97\\x9B\\n\")\n        self.sysModule.stderr.write(b\"\\xBC\\xFC\\n\")\n        compareEvents(\n            self, x, [dict(log_io=u\"\\u674e\"), dict(log_io=u\"\\u7469\")]\n        )\n\n\n    def test_warningsModule(self):\n        \"\"\"\n        L{LogBeginner.beginLoggingTo} will redirect the warnings of its\n        warnings module into the logging system.\n        \"\"\"\n        self.warningsModule.showwarning(\n            \"a message\", DeprecationWarning, __file__, 1\n        )\n        x = []\n        self.beginner.beginLoggingTo([x.append])\n        self.warningsModule.showwarning(\n            \"another message\", DeprecationWarning, __file__, 2\n        )\n        f = io.StringIO()\n        self.warningsModule.showwarning(\n            \"yet another\", DeprecationWarning, __file__, 3, file=f\n        )\n        self.assertEqual(\n            self.warningsModule.warnings,\n            [\n                (\"a message\", DeprecationWarning, __file__, 1, None, None),\n                (\"yet another\", DeprecationWarning, __file__, 3, f, None),\n            ]\n        )\n        compareEvents(\n            self, x,\n            [dict(\n                warning=\"another message\",\n                category=(\n                    DeprecationWarning.__module__ + \".\" +\n                    DeprecationWarning.__name__\n                ),\n                filename=__file__, lineno=2,\n            )]\n        )\n\n\n    def test_failuresAppendTracebacks(self):\n        \"\"\"\n        The string resulting from a logged failure contains a traceback.\n        \"\"\"\n        f = Failure(Exception(\"this is not the behavior you are looking for\"))\n        log = Logger(observer=self.publisher)\n        log.failure('a failure', failure=f)\n        msg = self.errorStream.getvalue()\n        self.assertIn('a failure', msg)\n        self.assertIn('this is not the behavior you are looking for', msg)\n        self.assertIn('Traceback', msg)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_io.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._io}.\n\"\"\"\n\nfrom __future__ import print_function\n\nimport sys\n\nfrom twisted.trial import unittest\n\nfrom .._levels import LogLevel\nfrom .._logger import Logger\nfrom .._observer import LogPublisher\nfrom .._io import LoggingFile\n\n\n\nclass LoggingFileTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{LoggingFile}.\n    \"\"\"\n\n    def setUp(self):\n        \"\"\"\n        Create a logger for test L{LoggingFile} instances to use.\n        \"\"\"\n        self.publisher = LogPublisher()\n        self.logger = Logger(observer=self.publisher)\n\n\n    def test_softspace(self):\n        \"\"\"\n        L{LoggingFile.softspace} is 0.\n        \"\"\"\n        self.assertEqual(LoggingFile.softspace, 0)\n\n\n    def test_readOnlyAttributes(self):\n        \"\"\"\n        Some L{LoggingFile} attributes are read-only.\n        \"\"\"\n        f = LoggingFile(self.logger)\n\n        self.assertRaises(AttributeError, setattr, f, \"closed\", True)\n        self.assertRaises(AttributeError, setattr, f, \"encoding\", \"utf-8\")\n        self.assertRaises(AttributeError, setattr, f, \"mode\", \"r\")\n        self.assertRaises(AttributeError, setattr, f, \"newlines\", [\"\\n\"])\n        self.assertRaises(AttributeError, setattr, f, \"name\", \"foo\")\n\n\n    def test_unsupportedMethods(self):\n        \"\"\"\n        Some L{LoggingFile} methods are unsupported.\n        \"\"\"\n        f = LoggingFile(self.logger)\n\n        self.assertRaises(IOError, f.read)\n        self.assertRaises(IOError, f.next)\n        self.assertRaises(IOError, f.readline)\n        self.assertRaises(IOError, f.readlines)\n        self.assertRaises(IOError, f.xreadlines)\n        self.assertRaises(IOError, f.seek)\n        self.assertRaises(IOError, f.tell)\n        self.assertRaises(IOError, f.truncate)\n\n\n    def test_level(self):\n        \"\"\"\n        Default level is L{LogLevel.info} if not set.\n        \"\"\"\n        f = LoggingFile(self.logger)\n        self.assertEqual(f.level, LogLevel.info)\n\n        f = LoggingFile(self.logger, level=LogLevel.error)\n        self.assertEqual(f.level, LogLevel.error)\n\n\n    def test_encoding(self):\n        \"\"\"\n        Default encoding is C{sys.getdefaultencoding()} if not set.\n        \"\"\"\n        f = LoggingFile(self.logger)\n        self.assertEqual(f.encoding, sys.getdefaultencoding())\n\n        f = LoggingFile(self.logger, encoding=\"utf-8\")\n        self.assertEqual(f.encoding, \"utf-8\")\n\n\n    def test_mode(self):\n        \"\"\"\n        Reported mode is C{\"w\"}.\n        \"\"\"\n        f = LoggingFile(self.logger)\n        self.assertEqual(f.mode, \"w\")\n\n\n    def test_newlines(self):\n        \"\"\"\n        The C{newlines} attribute is L{None}.\n        \"\"\"\n        f = LoggingFile(self.logger)\n        self.assertIsNone(f.newlines)\n\n\n    def test_name(self):\n        \"\"\"\n        The C{name} attribute is fixed.\n        \"\"\"\n        f = LoggingFile(self.logger)\n        self.assertEqual(\n            f.name,\n            \"<LoggingFile twisted.logger.test.test_io#info>\"\n        )\n\n\n    def test_close(self):\n        \"\"\"\n        L{LoggingFile.close} closes the file.\n        \"\"\"\n        f = LoggingFile(self.logger)\n        f.close()\n\n        self.assertTrue(f.closed)\n        self.assertRaises(ValueError, f.write, \"Hello\")\n\n\n    def test_flush(self):\n        \"\"\"\n        L{LoggingFile.flush} does nothing.\n        \"\"\"\n        f = LoggingFile(self.logger)\n        f.flush()\n\n\n    def test_fileno(self):\n        \"\"\"\n        L{LoggingFile.fileno} returns C{-1}.\n        \"\"\"\n        f = LoggingFile(self.logger)\n        self.assertEqual(f.fileno(), -1)\n\n\n    def test_isatty(self):\n        \"\"\"\n        L{LoggingFile.isatty} returns C{False}.\n        \"\"\"\n        f = LoggingFile(self.logger)\n        self.assertFalse(f.isatty())\n\n\n    def test_writeBuffering(self):\n        \"\"\"\n        Writing buffers correctly.\n        \"\"\"\n        f = self.observedFile()\n        f.write(\"Hello\")\n        self.assertEqual(f.messages, [])\n        f.write(\", world!\\n\")\n        self.assertEqual(f.messages, [u\"Hello, world!\"])\n        f.write(\"It's nice to meet you.\\n\\nIndeed.\")\n        self.assertEqual(\n            f.messages,\n            [\n                u\"Hello, world!\",\n                u\"It's nice to meet you.\",\n                u\"\",\n            ]\n        )\n\n\n    def test_writeBytesDecoded(self):\n        \"\"\"\n        Bytes are decoded to unicode.\n        \"\"\"\n        f = self.observedFile(encoding=\"utf-8\")\n        f.write(b\"Hello, Mr. S\\xc3\\xa1nchez\\n\")\n        self.assertEqual(f.messages, [u\"Hello, Mr. S\\xe1nchez\"])\n\n\n    def test_writeUnicode(self):\n        \"\"\"\n        Unicode is unmodified.\n        \"\"\"\n        f = self.observedFile(encoding=\"utf-8\")\n        f.write(u\"Hello, Mr. S\\xe1nchez\\n\")\n        self.assertEqual(f.messages, [u\"Hello, Mr. S\\xe1nchez\"])\n\n\n    def test_writeLevel(self):\n        \"\"\"\n        Log level is emitted properly.\n        \"\"\"\n        f = self.observedFile()\n        f.write(\"Hello\\n\")\n        self.assertEqual(len(f.events), 1)\n        self.assertEqual(f.events[0][\"log_level\"], LogLevel.info)\n\n        f = self.observedFile(level=LogLevel.error)\n        f.write(\"Hello\\n\")\n        self.assertEqual(len(f.events), 1)\n        self.assertEqual(f.events[0][\"log_level\"], LogLevel.error)\n\n\n    def test_writeFormat(self):\n        \"\"\"\n        Log format is C{u\"{message}\"}.\n        \"\"\"\n        f = self.observedFile()\n        f.write(\"Hello\\n\")\n        self.assertEqual(len(f.events), 1)\n        self.assertEqual(f.events[0][\"log_format\"], u\"{log_io}\")\n\n\n    def test_writelinesBuffering(self):\n        \"\"\"\n        C{writelines} does not add newlines.\n        \"\"\"\n        # Note this is different behavior than t.p.log.StdioOnnaStick.\n        f = self.observedFile()\n        f.writelines((\"Hello\", \", \", \"\"))\n        self.assertEqual(f.messages, [])\n        f.writelines((\"world!\\n\",))\n        self.assertEqual(f.messages, [u\"Hello, world!\"])\n        f.writelines((\"It's nice to meet you.\\n\\n\", \"Indeed.\"))\n        self.assertEqual(\n            f.messages,\n            [\n                u\"Hello, world!\",\n                u\"It's nice to meet you.\",\n                u\"\",\n            ]\n        )\n\n\n    def test_print(self):\n        \"\"\"\n        L{LoggingFile} can replace L{sys.stdout}.\n        \"\"\"\n        f = self.observedFile()\n        self.patch(sys, \"stdout\", f)\n\n        print(\"Hello,\", end=\" \")\n        print(\"world.\")\n\n        self.assertEqual(f.messages, [u\"Hello, world.\"])\n\n\n    def observedFile(self, **kwargs):\n        \"\"\"\n        Construct a L{LoggingFile} with a built-in observer.\n\n        @param kwargs: keyword arguments for the L{LoggingFile}.\n        @type kwargs: L{dict}\n\n        @return: a L{LoggingFile} with an observer that appends received\n            events into the file's C{events} attribute (a L{list}) and\n            event messages into the file's C{messages} attribute (a L{list}).\n        @rtype: L{LoggingFile}\n        \"\"\"\n        def observer(event):\n            f.events.append(event)\n            if \"log_io\" in event:\n                f.messages.append(event[\"log_io\"])\n\n        log = Logger(observer=observer)\n\n        f = LoggingFile(logger=log, **kwargs)\n        f.events = []\n        f.messages = []\n\n        return f\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_json.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.logger._json}.\n\"\"\"\n\nfrom io import StringIO, BytesIO\n\nfrom zope.interface.verify import verifyObject, BrokenMethodImplementation\n\nfrom twisted.python.compat import unicode\n\nfrom twisted.trial.unittest import TestCase\n\nfrom twisted.python.failure import Failure\n\nfrom .._observer import ILogObserver, LogPublisher\nfrom .._format import formatEvent\nfrom .._levels import LogLevel\nfrom .._flatten import extractField\nfrom .._global import globalLogPublisher\nfrom .._json import (\n    eventAsJSON, eventFromJSON, jsonFileLogObserver, eventsFromJSONLogFile,\n    log as jsonLog\n)\nfrom .._logger import Logger\n\n\ndef savedJSONInvariants(testCase, savedJSON):\n    \"\"\"\n    Assert a few things about the result of L{eventAsJSON}, then return it.\n\n    @param testCase: The L{TestCase} with which to perform the assertions.\n    @type testCase: L{TestCase}\n\n    @param savedJSON: The result of L{eventAsJSON}.\n    @type savedJSON: L{unicode} (we hope)\n\n    @return: C{savedJSON}\n    @rtype: L{unicode}\n\n    @raise AssertionError: If any of the preconditions fail.\n    \"\"\"\n    testCase.assertIsInstance(savedJSON, unicode)\n    testCase.assertEqual(savedJSON.count(\"\\n\"), 0)\n    return savedJSON\n\n\n\nclass SaveLoadTests(TestCase):\n    \"\"\"\n    Tests for loading and saving log events.\n    \"\"\"\n\n    def savedEventJSON(self, event):\n        \"\"\"\n        Serialize some an events, assert some things about it, and return the\n        JSON.\n\n        @param event: An event.\n        @type event: L{dict}\n\n        @return: JSON.\n        \"\"\"\n        return savedJSONInvariants(self, eventAsJSON(event))\n\n\n    def test_simpleSaveLoad(self):\n        \"\"\"\n        Saving and loading an empty dictionary results in an empty dictionary.\n        \"\"\"\n        self.assertEqual(eventFromJSON(self.savedEventJSON({})), {})\n\n\n    def test_saveLoad(self):\n        \"\"\"\n        Saving and loading a dictionary with some simple values in it results\n        in those same simple values in the output; according to JSON's rules,\n        though, all dictionary keys must be L{unicode} and any non-L{unicode}\n        keys will be converted.\n        \"\"\"\n        self.assertEqual(\n            eventFromJSON(self.savedEventJSON({1: 2, u\"3\": u\"4\"})),\n            {u\"1\": 2, u\"3\": u\"4\"}\n        )\n\n\n    def test_saveUnPersistable(self):\n        \"\"\"\n        Saving and loading an object which cannot be represented in JSON will\n        result in a placeholder.\n        \"\"\"\n        self.assertEqual(\n            eventFromJSON(self.savedEventJSON({u\"1\": 2, u\"3\": object()})),\n            {u\"1\": 2, u\"3\": {u\"unpersistable\": True}}\n        )\n\n\n    def test_saveNonASCII(self):\n        \"\"\"\n        Non-ASCII keys and values can be saved and loaded.\n        \"\"\"\n        self.assertEqual(\n            eventFromJSON(self.savedEventJSON(\n                {u\"\\u1234\": u\"\\u4321\", u\"3\": object()}\n            )),\n            {u\"\\u1234\": u\"\\u4321\", u\"3\": {u\"unpersistable\": True}}\n        )\n\n\n    def test_saveBytes(self):\n        \"\"\"\n        Any L{bytes} objects will be saved as if they are latin-1 so they can\n        be faithfully re-loaded.\n        \"\"\"\n        def asbytes(x):\n            if bytes is str:\n                return b\"\".join(map(chr, x))\n            else:\n                return bytes(x)\n\n        inputEvent = {\"hello\": asbytes(range(255))}\n        if bytes is not str:\n            # On Python 3, bytes keys will be skipped by the JSON encoder. Not\n            # much we can do about that.  Let's make sure that we don't get an\n            # error, though.\n            inputEvent.update({b\"skipped\": \"okay\"})\n        self.assertEqual(\n            eventFromJSON(self.savedEventJSON(inputEvent)),\n            {u\"hello\": asbytes(range(255)).decode(\"charmap\")}\n        )\n\n\n    def test_saveUnPersistableThenFormat(self):\n        \"\"\"\n        Saving and loading an object which cannot be represented in JSON, but\n        has a string representation which I{can} be saved as JSON, will result\n        in the same string formatting; any extractable fields will retain their\n        data types.\n        \"\"\"\n        class Reprable(object):\n            def __init__(self, value):\n                self.value = value\n\n            def __repr__(self):\n                return(\"reprable\")\n\n        inputEvent = {\n            \"log_format\": \"{object} {object.value}\",\n            \"object\": Reprable(7)\n        }\n        outputEvent = eventFromJSON(self.savedEventJSON(inputEvent))\n        self.assertEqual(formatEvent(outputEvent), \"reprable 7\")\n\n\n    def test_extractingFieldsPostLoad(self):\n        \"\"\"\n        L{extractField} can extract fields from an object that's been saved and\n        loaded from JSON.\n        \"\"\"\n        class Obj(object):\n            def __init__(self):\n                self.value = 345\n\n        inputEvent = dict(log_format=\"{object.value}\", object=Obj())\n        loadedEvent = eventFromJSON(self.savedEventJSON(inputEvent))\n        self.assertEqual(extractField(\"object.value\", loadedEvent), 345)\n\n        # The behavior of extractField is consistent between pre-persistence\n        # and post-persistence events, although looking up the key directly\n        # won't be:\n        self.assertRaises(KeyError, extractField, \"object\", loadedEvent)\n        self.assertRaises(KeyError, extractField, \"object\", inputEvent)\n\n\n    def test_failureStructurePreserved(self):\n        \"\"\"\n        Round-tripping a failure through L{eventAsJSON} preserves its class and\n        structure.\n        \"\"\"\n        events = []\n        log = Logger(observer=events.append)\n        try:\n            1 / 0\n        except ZeroDivisionError:\n            f = Failure()\n            log.failure(\"a message about failure\", f)\n        import sys\n        if sys.exc_info()[0] is not None:\n            # Make sure we don't get the same Failure by accident.\n            sys.exc_clear()\n        self.assertEqual(len(events), 1)\n        loaded = eventFromJSON(self.savedEventJSON(events[0]))['log_failure']\n        self.assertIsInstance(loaded, Failure)\n        self.assertTrue(loaded.check(ZeroDivisionError))\n        self.assertIsInstance(loaded.getTraceback(), str)\n\n\n    def test_saveLoadLevel(self):\n        \"\"\"\n        It's important that the C{log_level} key remain a\n        L{constantly.NamedConstant} object.\n        \"\"\"\n        inputEvent = dict(log_level=LogLevel.warn)\n        loadedEvent = eventFromJSON(self.savedEventJSON(inputEvent))\n        self.assertIs(loadedEvent[\"log_level\"], LogLevel.warn)\n\n\n    def test_saveLoadUnknownLevel(self):\n        \"\"\"\n        If a saved bit of JSON (let's say, from a future version of Twisted)\n        were to persist a different log_level, it will resolve as None.\n        \"\"\"\n        loadedEvent = eventFromJSON(\n            '{\"log_level\": {\"name\": \"other\", '\n            '\"__class_uuid__\": \"02E59486-F24D-46AD-8224-3ACDF2A5732A\"}}'\n        )\n        self.assertEqual(loadedEvent, dict(log_level=None))\n\n\n\nclass FileLogObserverTests(TestCase):\n    \"\"\"\n    Tests for L{jsonFileLogObserver}.\n    \"\"\"\n\n    def test_interface(self):\n        \"\"\"\n        A L{FileLogObserver} returned by L{jsonFileLogObserver} is an\n        L{ILogObserver}.\n        \"\"\"\n        with StringIO() as fileHandle:\n            observer = jsonFileLogObserver(fileHandle)\n            try:\n                verifyObject(ILogObserver, observer)\n            except BrokenMethodImplementation as e:\n                self.fail(e)\n\n\n    def assertObserverWritesJSON(self, **kwargs):\n        \"\"\"\n        Asserts that an observer created by L{jsonFileLogObserver} with the\n        given arguments writes events serialized as JSON text, using the given\n        record separator.\n\n        @param recordSeparator: A record separator.\n        @type recordSeparator: L{unicode}\n\n        @param kwargs: Keyword arguments to pass to L{jsonFileLogObserver}.\n        @type kwargs: L{dict}\n        \"\"\"\n        recordSeparator = kwargs.get(\"recordSeparator\", u\"\\x1e\")\n\n        with StringIO() as fileHandle:\n            observer = jsonFileLogObserver(fileHandle, **kwargs)\n            event = dict(x=1)\n            observer(event)\n            self.assertEqual(\n                fileHandle.getvalue(),\n                u'{0}{{\"x\": 1}}\\n'.format(recordSeparator)\n            )\n\n\n    def test_observeWritesDefaultRecordSeparator(self):\n        \"\"\"\n        A L{FileLogObserver} created by L{jsonFileLogObserver} writes events\n        serialzed as JSON text to a file when it observes events.\n        By default, the record separator is C{u\"\\\\x1e\"}.\n        \"\"\"\n        self.assertObserverWritesJSON()\n\n\n    def test_observeWritesEmptyRecordSeparator(self):\n        \"\"\"\n        A L{FileLogObserver} created by L{jsonFileLogObserver} writes events\n        serialzed as JSON text to a file when it observes events.\n        This test sets the record separator to C{u\"\"}.\n        \"\"\"\n        self.assertObserverWritesJSON(recordSeparator=u\"\")\n\n\n    def test_failureFormatting(self):\n        \"\"\"\n        A L{FileLogObserver} created by L{jsonFileLogObserver} writes failures\n        serialized as JSON text to a file when it observes events.\n        \"\"\"\n        io = StringIO()\n        publisher = LogPublisher()\n        logged = []\n        publisher.addObserver(logged.append)\n        publisher.addObserver(jsonFileLogObserver(io))\n        logger = Logger(observer=publisher)\n        try:\n            1 / 0\n        except:\n            logger.failure(\"failed as expected\")\n        reader = StringIO(io.getvalue())\n        deserialized = list(eventsFromJSONLogFile(reader))\n        def checkEvents(logEvents):\n            self.assertEqual(len(logEvents), 1)\n            [failureEvent] = logEvents\n            self.assertIn(\"log_failure\", failureEvent)\n            failureObject = failureEvent[\"log_failure\"]\n            self.assertIsInstance(failureObject, Failure)\n            tracebackObject = failureObject.getTracebackObject()\n            self.assertEqual(\n                tracebackObject.tb_frame.f_code.co_filename.rstrip(\"co\"),\n                __file__.rstrip(\"co\")\n            )\n        checkEvents(logged)\n        checkEvents(deserialized)\n\n\n\nclass LogFileReaderTests(TestCase):\n    \"\"\"\n    Tests for L{eventsFromJSONLogFile}.\n    \"\"\"\n\n    def setUp(self):\n        self.errorEvents = []\n\n        def observer(event):\n            if (\n                event[\"log_namespace\"] == jsonLog.namespace and\n                \"record\" in event\n            ):\n                self.errorEvents.append(event)\n\n        self.logObserver = observer\n\n        globalLogPublisher.addObserver(observer)\n\n\n    def tearDown(self):\n        globalLogPublisher.removeObserver(self.logObserver)\n\n\n    def _readEvents(self, fileHandle, **kwargs):\n        \"\"\"\n        Test that L{eventsFromJSONLogFile} reads two pre-defined events from a\n        file: C{{u\"x\": 1}} and C{{u\"y\": 2}}.\n\n        @param fileHandle: The file to read from.\n\n        @param kwargs: Keyword arguments to pass to L{eventsFromJSONLogFile}.\n        \"\"\"\n        events = eventsFromJSONLogFile(fileHandle, **kwargs)\n\n        self.assertEqual(next(events), {u\"x\": 1})\n        self.assertEqual(next(events), {u\"y\": 2})\n        self.assertRaises(StopIteration, next, events)  # No more events\n\n\n    def test_readEventsAutoWithRecordSeparator(self):\n        \"\"\"\n        L{eventsFromJSONLogFile} reads events from a file and automatically\n        detects use of C{u\"\\\\x1e\"} as the record separator.\n        \"\"\"\n        with StringIO(\n            u'\\x1e{\"x\": 1}\\n'\n            u'\\x1e{\"y\": 2}\\n'\n        ) as fileHandle:\n            self._readEvents(fileHandle)\n            self.assertEqual(len(self.errorEvents), 0)\n\n\n    def test_readEventsAutoEmptyRecordSeparator(self):\n        \"\"\"\n        L{eventsFromJSONLogFile} reads events from a file and automatically\n        detects use of C{u\"\"} as the record separator.\n        \"\"\"\n        with StringIO(\n            u'{\"x\": 1}\\n'\n            u'{\"y\": 2}\\n'\n        ) as fileHandle:\n            self._readEvents(fileHandle)\n            self.assertEqual(len(self.errorEvents), 0)\n\n\n    def test_readEventsExplicitRecordSeparator(self):\n        \"\"\"\n        L{eventsFromJSONLogFile} reads events from a file and is told to use\n        a specific record separator.\n        \"\"\"\n        # Use u\"\\x08\" (backspace)... because that seems weird enough.\n        with StringIO(\n            u'\\x08{\"x\": 1}\\n'\n            u'\\x08{\"y\": 2}\\n'\n        ) as fileHandle:\n            self._readEvents(fileHandle, recordSeparator=u\"\\x08\")\n            self.assertEqual(len(self.errorEvents), 0)\n\n\n    def test_readEventsPartialBuffer(self):\n        \"\"\"\n        L{eventsFromJSONLogFile} handles buffering a partial event.\n        \"\"\"\n        with StringIO(\n            u'\\x1e{\"x\": 1}\\n'\n            u'\\x1e{\"y\": 2}\\n'\n        ) as fileHandle:\n            # Use a buffer size smaller than the event text.\n            self._readEvents(fileHandle, bufferSize=1)\n            self.assertEqual(len(self.errorEvents), 0)\n\n\n    def test_readTruncated(self):\n        \"\"\"\n        If the JSON text for a record is truncated, skip it.\n        \"\"\"\n        with StringIO(\n            u'\\x1e{\"x\": 1'\n            u'\\x1e{\"y\": 2}\\n'\n        ) as fileHandle:\n            events = eventsFromJSONLogFile(fileHandle)\n\n            self.assertEqual(next(events), {u\"y\": 2})\n            self.assertRaises(StopIteration, next, events)  # No more events\n\n            # We should have logged the lost record\n            self.assertEqual(len(self.errorEvents), 1)\n            self.assertEqual(\n                self.errorEvents[0][\"log_format\"],\n                u\"Unable to read truncated JSON record: {record!r}\"\n            )\n            self.assertEqual(self.errorEvents[0][\"record\"], b'{\"x\": 1')\n\n\n    def test_readUnicode(self):\n        \"\"\"\n        If the file being read from vends L{unicode}, strings decode from JSON\n        as-is.\n        \"\"\"\n        # The Euro currency sign is u\"\\u20ac\"\n        with StringIO(u'\\x1e{\"currency\": \"\\u20ac\"}\\n') as fileHandle:\n            events = eventsFromJSONLogFile(fileHandle)\n\n            self.assertEqual(next(events), {u\"currency\": u\"\\u20ac\"})\n            self.assertRaises(StopIteration, next, events)  # No more events\n            self.assertEqual(len(self.errorEvents), 0)\n\n\n    def test_readUTF8Bytes(self):\n        \"\"\"\n        If the file being read from vends L{bytes}, strings decode from JSON as\n        UTF-8.\n        \"\"\"\n        # The Euro currency sign is b\"\\xe2\\x82\\xac\" in UTF-8\n        with BytesIO(b'\\x1e{\"currency\": \"\\xe2\\x82\\xac\"}\\n') as fileHandle:\n            events = eventsFromJSONLogFile(fileHandle)\n\n            # The Euro currency sign is u\"\\u20ac\"\n            self.assertEqual(next(events), {u\"currency\": u\"\\u20ac\"})\n            self.assertRaises(StopIteration, next, events)  # No more events\n            self.assertEqual(len(self.errorEvents), 0)\n\n\n    def test_readTruncatedUTF8Bytes(self):\n        \"\"\"\n        If the JSON text for a record is truncated in the middle of a two-byte\n        Unicode codepoint, we don't want to see a codec exception and the\n        stream is read properly when the additional data arrives.\n        \"\"\"\n        # The Euro currency sign is u\"\\u20ac\" and encodes in UTF-8 as three\n        # bytes: b\"\\xe2\\x82\\xac\".\n        with BytesIO(b'\\x1e{\"x\": \"\\xe2\\x82\\xac\"}\\n') as fileHandle:\n            events = eventsFromJSONLogFile(fileHandle, bufferSize=8)\n\n            self.assertEqual(next(events), {u\"x\": u\"\\u20ac\"})  # Got unicode\n            self.assertRaises(StopIteration, next, events)  # No more events\n            self.assertEqual(len(self.errorEvents), 0)\n\n\n    def test_readInvalidUTF8Bytes(self):\n        \"\"\"\n        If the JSON text for a record contains invalid UTF-8 text, ignore that\n        record.\n        \"\"\"\n        # The string b\"\\xe2\\xac\" is bogus\n        with BytesIO(\n            b'\\x1e{\"x\": \"\\xe2\\xac\"}\\n'\n            b'\\x1e{\"y\": 2}\\n'\n        ) as fileHandle:\n            events = eventsFromJSONLogFile(fileHandle)\n\n            self.assertEqual(next(events), {u\"y\": 2})\n            self.assertRaises(StopIteration, next, events)  # No more events\n\n            # We should have logged the lost record\n            self.assertEqual(len(self.errorEvents), 1)\n            self.assertEqual(\n                self.errorEvents[0][\"log_format\"],\n                u\"Unable to decode UTF-8 for JSON record: {record!r}\"\n            )\n            self.assertEqual(\n                self.errorEvents[0][\"record\"],\n                b'{\"x\": \"\\xe2\\xac\"}\\n'\n            )\n\n\n    def test_readInvalidJSON(self):\n        \"\"\"\n        If the JSON text for a record is invalid, skip it.\n        \"\"\"\n        with StringIO(\n            u'\\x1e{\"x\": }\\n'\n            u'\\x1e{\"y\": 2}\\n'\n        ) as fileHandle:\n            events = eventsFromJSONLogFile(fileHandle)\n\n            self.assertEqual(next(events), {u\"y\": 2})\n            self.assertRaises(StopIteration, next, events)  # No more events\n\n            # We should have logged the lost record\n            self.assertEqual(len(self.errorEvents), 1)\n            self.assertEqual(\n                self.errorEvents[0][\"log_format\"],\n                u\"Unable to read JSON record: {record!r}\"\n            )\n            self.assertEqual(self.errorEvents[0][\"record\"], b'{\"x\": }\\n')\n\n\n    def test_readUnseparated(self):\n        \"\"\"\n        Multiple events without a record separator are skipped.\n        \"\"\"\n        with StringIO(\n            u'\\x1e{\"x\": 1}\\n'\n            u'{\"y\": 2}\\n'\n        ) as fileHandle:\n            events = eventsFromJSONLogFile(fileHandle)\n\n            self.assertRaises(StopIteration, next, events)  # No more events\n\n            # We should have logged the lost record\n            self.assertEqual(len(self.errorEvents), 1)\n            self.assertEqual(\n                self.errorEvents[0][\"log_format\"],\n                u\"Unable to read JSON record: {record!r}\"\n            )\n            self.assertEqual(\n                self.errorEvents[0][\"record\"],\n                b'{\"x\": 1}\\n{\"y\": 2}\\n'\n            )\n\n\n    def test_roundTrip(self):\n        \"\"\"\n        Data written by a L{FileLogObserver} returned by L{jsonFileLogObserver}\n        and read by L{eventsFromJSONLogFile} is reconstructed properly.\n        \"\"\"\n        event = dict(x=1)\n\n        with StringIO() as fileHandle:\n            observer = jsonFileLogObserver(fileHandle)\n            observer(event)\n\n            fileHandle.seek(0)\n            events = eventsFromJSONLogFile(fileHandle)\n\n            self.assertEqual(tuple(events), (event,))\n            self.assertEqual(len(self.errorEvents), 0)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_legacy.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._legacy}.\n\"\"\"\n\nfrom time import time\nimport logging as py_logging\n\nfrom zope.interface.verify import verifyObject, BrokenMethodImplementation\n\nfrom twisted.trial import unittest\n\nfrom twisted.python import context\nfrom twisted.python import log as legacyLog\nfrom twisted.python.failure import Failure\n\nfrom .._levels import LogLevel\nfrom .._observer import ILogObserver\nfrom .._format import formatEvent\nfrom .._legacy import LegacyLogObserverWrapper\nfrom .._legacy import publishToNewObserver\n\n\n\nclass LegacyLogObserverWrapperTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{LegacyLogObserverWrapper}.\n    \"\"\"\n\n    def test_interface(self):\n        \"\"\"\n        L{LegacyLogObserverWrapper} is an L{ILogObserver}.\n        \"\"\"\n        legacyObserver = lambda e: None\n        observer = LegacyLogObserverWrapper(legacyObserver)\n        try:\n            verifyObject(ILogObserver, observer)\n        except BrokenMethodImplementation as e:\n            self.fail(e)\n\n\n    def test_repr(self):\n        \"\"\"\n        L{LegacyLogObserverWrapper} returns the expected string.\n        \"\"\"\n        class LegacyObserver(object):\n            def __repr__(self):\n                return \"<Legacy Observer>\"\n\n            def __call__(self):\n                return\n\n        observer = LegacyLogObserverWrapper(LegacyObserver())\n\n        self.assertEqual(\n            repr(observer),\n            \"LegacyLogObserverWrapper(<Legacy Observer>)\"\n        )\n\n\n    def observe(self, event):\n        \"\"\"\n        Send an event to a wrapped legacy observer and capture the event as\n        seen by that observer.\n\n        @param event: an event\n        @type event: L{dict}\n\n        @return: the event as observed by the legacy wrapper\n        \"\"\"\n        events = []\n\n        legacyObserver = lambda e: events.append(e)\n        observer = LegacyLogObserverWrapper(legacyObserver)\n        observer(event)\n        self.assertEqual(len(events), 1)\n\n        return events[0]\n\n\n    def forwardAndVerify(self, event):\n        \"\"\"\n        Send an event to a wrapped legacy observer and verify that its data is\n        preserved.\n\n        @param event: an event\n        @type event: L{dict}\n\n        @return: the event as observed by the legacy wrapper\n        \"\"\"\n        # Make sure keys that are expected by the logging system are present\n        event.setdefault(\"log_time\", time())\n        event.setdefault(\"log_system\", \"-\")\n        event.setdefault(\"log_level\", LogLevel.info)\n\n        # Send a copy: don't mutate me, bro\n        observed = self.observe(dict(event))\n\n        # Don't expect modifications\n        for key, value in event.items():\n            self.assertIn(key, observed)\n\n        return observed\n\n\n    def test_forward(self):\n        \"\"\"\n        Basic forwarding: event keys as observed by a legacy observer are the\n        same.\n        \"\"\"\n        self.forwardAndVerify(dict(foo=1, bar=2))\n\n\n    def test_time(self):\n        \"\"\"\n        The new-style C{\"log_time\"} key is copied to the old-style C{\"time\"}\n        key.\n        \"\"\"\n        stamp = time()\n        event = self.forwardAndVerify(dict(log_time=stamp))\n        self.assertEqual(event[\"time\"], stamp)\n\n\n    def test_timeAlreadySet(self):\n        \"\"\"\n        The new-style C{\"log_time\"} key does not step on a pre-existing\n        old-style C{\"time\"} key.\n        \"\"\"\n        stamp = time()\n        event = self.forwardAndVerify(dict(log_time=stamp + 1, time=stamp))\n        self.assertEqual(event[\"time\"], stamp)\n\n\n    def test_system(self):\n        \"\"\"\n        The new-style C{\"log_system\"} key is copied to the old-style\n        C{\"system\"} key.\n        \"\"\"\n        event = self.forwardAndVerify(dict(log_system=\"foo\"))\n        self.assertEqual(event[\"system\"], \"foo\")\n\n\n    def test_systemAlreadySet(self):\n        \"\"\"\n        The new-style C{\"log_system\"} key does not step on a pre-existing\n        old-style C{\"system\"} key.\n        \"\"\"\n        event = self.forwardAndVerify(dict(log_system=\"foo\", system=\"bar\"))\n        self.assertEqual(event[\"system\"], \"bar\")\n\n\n    def test_noSystem(self):\n        \"\"\"\n        If the new-style C{\"log_system\"} key is absent, the old-style\n        C{\"system\"} key is set to C{\"-\"}.\n        \"\"\"\n        # Don't use forwardAndVerify(), since that sets log_system.\n        event = dict(log_time=time(), log_level=LogLevel.info)\n        observed = self.observe(dict(event))\n        self.assertEqual(observed[\"system\"], \"-\")\n\n\n    def test_levelNotChange(self):\n        \"\"\"\n        If explicitly set, the C{isError} key will be preserved when forwarding\n        from a new-style logging emitter to a legacy logging observer,\n        regardless of log level.\n        \"\"\"\n        self.forwardAndVerify(dict(log_level=LogLevel.info, isError=1))\n        self.forwardAndVerify(dict(log_level=LogLevel.warn, isError=1))\n        self.forwardAndVerify(dict(log_level=LogLevel.error, isError=0))\n        self.forwardAndVerify(dict(log_level=LogLevel.critical, isError=0))\n\n\n    def test_pythonLogLevelNotSet(self):\n        \"\"\"\n        The new-style C{\"log_level\"} key is not translated to the old-style\n        C{\"logLevel\"} key.\n\n        Events are forwarded from the old module from to new module and are\n        then seen by old-style observers.\n        We don't want to add unexpected keys to old-style events.\n        \"\"\"\n        event = self.forwardAndVerify(dict(log_level=LogLevel.info))\n        self.assertNotIn(\"logLevel\", event)\n\n\n    def test_stringPythonLogLevel(self):\n        \"\"\"\n        If a stdlib log level was provided as a string (eg. C{\"WARNING\"}) in\n        the legacy \"logLevel\" key, it does not get converted to a number.\n        The documentation suggested that numerical values should be used but\n        this was not a requirement.\n        \"\"\"\n        event = self.forwardAndVerify(dict(\n            logLevel=\"WARNING\",  # py_logging.WARNING is 30\n        ))\n        self.assertEqual(event[\"logLevel\"], \"WARNING\")\n\n\n    def test_message(self):\n        \"\"\"\n        The old-style C{\"message\"} key is added, even if no new-style\n        C{\"log_format\"} is given, as it is required, but may be empty.\n        \"\"\"\n        event = self.forwardAndVerify(dict())\n        self.assertEqual(event[\"message\"], ())  # \"message\" is a tuple\n\n\n    def test_messageAlreadySet(self):\n        \"\"\"\n        The old-style C{\"message\"} key is not modified if it already exists.\n        \"\"\"\n        event = self.forwardAndVerify(dict(message=(\"foo\", \"bar\")))\n        self.assertEqual(event[\"message\"], (\"foo\", \"bar\"))\n\n\n    def test_format(self):\n        \"\"\"\n        Formatting is translated such that text is rendered correctly, even\n        though old-style logging doesn't use PEP 3101 formatting.\n        \"\"\"\n        event = self.forwardAndVerify(\n            dict(log_format=\"Hello, {who}!\", who=\"world\")\n        )\n        self.assertEqual(\n            legacyLog.textFromEventDict(event),\n            \"Hello, world!\"\n        )\n\n\n    def test_formatMessage(self):\n        \"\"\"\n        Using the message key, which is special in old-style, works for\n        new-style formatting.\n        \"\"\"\n        event = self.forwardAndVerify(\n            dict(log_format=\"Hello, {message}!\", message=\"world\")\n        )\n        self.assertEqual(\n            legacyLog.textFromEventDict(event),\n            \"Hello, world!\"\n        )\n\n\n    def test_formatAlreadySet(self):\n        \"\"\"\n        Formatting is not altered if the old-style C{\"format\"} key already\n        exists.\n        \"\"\"\n        event = self.forwardAndVerify(\n            dict(log_format=\"Hello!\", format=\"Howdy!\")\n        )\n        self.assertEqual(legacyLog.textFromEventDict(event), \"Howdy!\")\n\n\n    def eventWithFailure(self, **values):\n        \"\"\"\n        Create a new-style event with a captured failure.\n\n        @param values: Additional values to include in the event.\n        @type values: L{dict}\n\n        @return: the new event\n        @rtype: L{dict}\n        \"\"\"\n        failure = Failure(RuntimeError(\"nyargh!\"))\n        return self.forwardAndVerify(dict(\n            log_failure=failure,\n            log_format=\"oopsie...\",\n            **values\n        ))\n\n\n    def test_failure(self):\n        \"\"\"\n        Captured failures in the new style set the old-style C{\"failure\"},\n        C{\"isError\"}, and C{\"why\"} keys.\n        \"\"\"\n        event = self.eventWithFailure()\n        self.assertIs(event[\"failure\"], event[\"log_failure\"])\n        self.assertTrue(event[\"isError\"])\n        self.assertEqual(event[\"why\"], \"oopsie...\")\n\n\n    def test_failureAlreadySet(self):\n        \"\"\"\n        Captured failures in the new style do not step on a pre-existing\n        old-style C{\"failure\"} key.\n        \"\"\"\n        failure = Failure(RuntimeError(\"Weak salsa!\"))\n        event = self.eventWithFailure(failure=failure)\n        self.assertIs(event[\"failure\"], failure)\n\n\n    def test_isErrorAlreadySet(self):\n        \"\"\"\n        Captured failures in the new style do not step on a pre-existing\n        old-style C{\"isError\"} key.\n        \"\"\"\n        event = self.eventWithFailure(isError=0)\n        self.assertEqual(event[\"isError\"], 0)\n\n\n    def test_whyAlreadySet(self):\n        \"\"\"\n        Captured failures in the new style do not step on a pre-existing\n        old-style C{\"failure\"} key.\n        \"\"\"\n        event = self.eventWithFailure(why=\"blah\")\n        self.assertEqual(event[\"why\"], \"blah\")\n\n\n\nclass PublishToNewObserverTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{publishToNewObserver}.\n    \"\"\"\n\n    def setUp(self):\n        self.events = []\n        self.observer = self.events.append\n\n\n    def legacyEvent(self, *message, **values):\n        \"\"\"\n        Return a basic old-style event as would be created by L{legacyLog.msg}.\n\n        @param message: a message event value in the legacy event format\n        @type message: L{tuple} of L{bytes}\n\n        @param values: additional event values in the legacy event format\n        @type event: L{dict}\n\n        @return: a legacy event\n        \"\"\"\n        event = (context.get(legacyLog.ILogContext) or {}).copy()\n        event.update(values)\n        event[\"message\"] = message\n        event[\"time\"] = time()\n        if \"isError\" not in event:\n            event[\"isError\"] = 0\n        return event\n\n\n    def test_observed(self):\n        \"\"\"\n        The observer is called exactly once.\n        \"\"\"\n        publishToNewObserver(\n            self.observer, self.legacyEvent(), legacyLog.textFromEventDict\n        )\n        self.assertEqual(len(self.events), 1)\n\n\n    def test_time(self):\n        \"\"\"\n        The old-style C{\"time\"} key is copied to the new-style C{\"log_time\"}\n        key.\n        \"\"\"\n        publishToNewObserver(\n            self.observer, self.legacyEvent(), legacyLog.textFromEventDict\n        )\n        self.assertEqual(\n            self.events[0][\"log_time\"], self.events[0][\"time\"]\n        )\n\n\n    def test_message(self):\n        \"\"\"\n        A published old-style event should format as text in the same way as\n        the given C{textFromEventDict} callable would format it.\n        \"\"\"\n        def textFromEventDict(event):\n            return \"\".join(reversed(\" \".join(event[\"message\"])))\n\n        event = self.legacyEvent(\"Hello,\", \"world!\")\n        text = textFromEventDict(event)\n\n        publishToNewObserver(self.observer, event, textFromEventDict)\n        self.assertEqual(formatEvent(self.events[0]), text)\n\n\n    def test_defaultLogLevel(self):\n        \"\"\"\n        Published event should have log level of L{LogLevel.info}.\n        \"\"\"\n        publishToNewObserver(\n            self.observer, self.legacyEvent(), legacyLog.textFromEventDict\n        )\n        self.assertEqual(self.events[0][\"log_level\"], LogLevel.info)\n\n\n    def test_isError(self):\n        \"\"\"\n        If C{\"isError\"} is set to C{1} (true) on the legacy event, the\n        C{\"log_level\"} key should get set to L{LogLevel.critical}.\n        \"\"\"\n        publishToNewObserver(\n            self.observer,\n            self.legacyEvent(isError=1),\n            legacyLog.textFromEventDict\n        )\n        self.assertEqual(self.events[0][\"log_level\"], LogLevel.critical)\n\n\n    def test_stdlibLogLevel(self):\n        \"\"\"\n        If the old-style C{\"logLevel\"} key is set to a standard library logging\n        level, using a predefined (L{int}) constant, the new-style\n        C{\"log_level\"} key should get set to the corresponding log level.\n        \"\"\"\n        publishToNewObserver(\n            self.observer,\n            self.legacyEvent(logLevel=py_logging.WARNING),\n            legacyLog.textFromEventDict\n        )\n        self.assertEqual(self.events[0][\"log_level\"], LogLevel.warn)\n\n\n    def test_stdlibLogLevelWithString(self):\n        \"\"\"\n        If the old-style C{\"logLevel\"} key is set to a standard library logging\n        level, using a string value, the new-style C{\"log_level\"} key should\n        get set to the corresponding log level.\n        \"\"\"\n        publishToNewObserver(\n            self.observer,\n            self.legacyEvent(logLevel=\"WARNING\"),\n            legacyLog.textFromEventDict\n        )\n        self.assertEqual(self.events[0][\"log_level\"], LogLevel.warn)\n\n\n    def test_stdlibLogLevelWithGarbage(self):\n        \"\"\"\n        If the old-style C{\"logLevel\"} key is set to a standard library logging\n        level, using an unknown value, the new-style C{\"log_level\"} key should\n        not get set.\n        \"\"\"\n        publishToNewObserver(\n            self.observer,\n            self.legacyEvent(logLevel=\"Foo!!!!!\"),\n            legacyLog.textFromEventDict\n        )\n        self.assertNotIn(\"log_level\", self.events[0])\n\n\n    def test_defaultNamespace(self):\n        \"\"\"\n        Published event should have a namespace of C{\"log_legacy\"} to indicate\n        that it was forwarded from legacy logging.\n        \"\"\"\n        publishToNewObserver(\n            self.observer, self.legacyEvent(), legacyLog.textFromEventDict\n        )\n        self.assertEqual(self.events[0][\"log_namespace\"], \"log_legacy\")\n\n\n    def test_system(self):\n        \"\"\"\n        The old-style C{\"system\"} key is copied to the new-style\n        C{\"log_system\"} key.\n        \"\"\"\n        publishToNewObserver(\n            self.observer, self.legacyEvent(), legacyLog.textFromEventDict\n        )\n        self.assertEqual(\n            self.events[0][\"log_system\"], self.events[0][\"system\"]\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_levels.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._levels}.\n\"\"\"\n\nfrom twisted.trial import unittest\n\nfrom .._levels import InvalidLogLevelError\nfrom .._levels import LogLevel\n\n\n\nclass LogLevelTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{LogLevel}.\n    \"\"\"\n\n    def test_levelWithName(self):\n        \"\"\"\n        Look up log level by name.\n        \"\"\"\n        for level in LogLevel.iterconstants():\n            self.assertIs(LogLevel.levelWithName(level.name), level)\n\n\n    def test_levelWithInvalidName(self):\n        \"\"\"\n        You can't make up log level names.\n        \"\"\"\n        bogus = \"*bogus*\"\n        try:\n            LogLevel.levelWithName(bogus)\n        except InvalidLogLevelError as e:\n            self.assertIs(e.level, bogus)\n        else:\n            self.fail(\"Expected InvalidLogLevelError.\")\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_logger.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._logger}.\n\"\"\"\n\nfrom twisted.trial import unittest\n\nfrom .._levels import InvalidLogLevelError\nfrom .._levels import LogLevel\nfrom .._format import formatEvent\nfrom .._logger import Logger\nfrom .._global import globalLogPublisher\n\n\n\nclass TestLogger(Logger):\n    \"\"\"\n    L{Logger} with an overridden C{emit} method that keeps track of received\n    events.\n    \"\"\"\n\n    def emit(self, level, format=None, **kwargs):\n        def observer(event):\n            self.event = event\n\n        globalLogPublisher.addObserver(observer)\n        try:\n            Logger.emit(self, level, format, **kwargs)\n        finally:\n            globalLogPublisher.removeObserver(observer)\n\n        self.emitted = {\n            \"level\": level,\n            \"format\": format,\n            \"kwargs\": kwargs,\n        }\n\n\n\nclass LogComposedObject(object):\n    \"\"\"\n    A regular object, with a logger attached.\n    \"\"\"\n    log = TestLogger()\n\n    def __init__(self, state=None):\n        self.state = state\n\n\n    def __str__(self):\n        return \"<LogComposedObject {state}>\".format(state=self.state)\n\n\n\nclass LoggerTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{Logger}.\n    \"\"\"\n\n    def test_repr(self):\n        \"\"\"\n        repr() on Logger\n        \"\"\"\n        namespace = \"bleargh\"\n        log = Logger(namespace)\n        self.assertEqual(repr(log), \"<Logger {0}>\".format(repr(namespace)))\n\n\n    def test_namespaceDefault(self):\n        \"\"\"\n        Default namespace is module name.\n        \"\"\"\n        log = Logger()\n        self.assertEqual(log.namespace, __name__)\n\n\n    def test_namespaceOMGItsTooHard(self):\n        \"\"\"\n        Default namespace is C{\"<unknown>\"} when a logger is created from a\n        context in which is can't be determined automatically and no namespace\n        was specified.\n        \"\"\"\n        result = []\n        exec(\n            \"result.append(Logger())\",\n            dict(Logger=Logger), locals(),\n        )\n        self.assertEqual(result[0].namespace, \"<unknown>\")\n\n\n    def test_namespaceAttribute(self):\n        \"\"\"\n        Default namespace for classes using L{Logger} as a descriptor is the\n        class name they were retrieved from.\n        \"\"\"\n        obj = LogComposedObject()\n        expectedNamespace = \"{0}.{1}\".format(\n            obj.__module__,\n            obj.__class__.__name__,\n        )\n        self.assertEqual(obj.log.namespace, expectedNamespace)\n        self.assertEqual(LogComposedObject.log.namespace, expectedNamespace)\n        self.assertIs(LogComposedObject.log.source, LogComposedObject)\n        self.assertIs(obj.log.source, obj)\n        self.assertIsNone(Logger().source)\n\n\n    def test_descriptorObserver(self):\n        \"\"\"\n        When used as a descriptor, the observer is propagated.\n        \"\"\"\n        observed = []\n\n        class MyObject(object):\n            log = Logger(observer=observed.append)\n\n        MyObject.log.info(\"hello\")\n        self.assertEqual(len(observed), 1)\n        self.assertEqual(observed[0]['log_format'], \"hello\")\n\n\n    def test_sourceAvailableForFormatting(self):\n        \"\"\"\n        On instances that have a L{Logger} class attribute, the C{log_source}\n        key is available to format strings.\n        \"\"\"\n        obj = LogComposedObject(\"hello\")\n        log = obj.log\n        log.error(\"Hello, {log_source}.\")\n\n        self.assertIn(\"log_source\", log.event)\n        self.assertEqual(log.event[\"log_source\"], obj)\n\n        stuff = formatEvent(log.event)\n        self.assertIn(\"Hello, <LogComposedObject hello>.\", stuff)\n\n\n    def test_basicLogger(self):\n        \"\"\"\n        Test that log levels and messages are emitted correctly for\n        Logger.\n        \"\"\"\n        log = TestLogger()\n\n        for level in LogLevel.iterconstants():\n            format = \"This is a {level_name} message\"\n            message = format.format(level_name=level.name)\n\n            logMethod = getattr(log, level.name)\n            logMethod(format, junk=message, level_name=level.name)\n\n            # Ensure that test_emit got called with expected arguments\n            self.assertEqual(log.emitted[\"level\"], level)\n            self.assertEqual(log.emitted[\"format\"], format)\n            self.assertEqual(log.emitted[\"kwargs\"][\"junk\"], message)\n\n            self.assertTrue(hasattr(log, \"event\"), \"No event observed.\")\n\n            self.assertEqual(log.event[\"log_format\"], format)\n            self.assertEqual(log.event[\"log_level\"], level)\n            self.assertEqual(log.event[\"log_namespace\"], __name__)\n            self.assertIsNone(log.event[\"log_source\"])\n            self.assertEqual(log.event[\"junk\"], message)\n\n            self.assertEqual(formatEvent(log.event), message)\n\n\n    def test_sourceOnClass(self):\n        \"\"\"\n        C{log_source} event key refers to the class.\n        \"\"\"\n        def observer(event):\n            self.assertEqual(event[\"log_source\"], Thingo)\n\n        class Thingo(object):\n            log = TestLogger(observer=observer)\n\n        Thingo.log.info()\n\n\n    def test_sourceOnInstance(self):\n        \"\"\"\n        C{log_source} event key refers to the instance.\n        \"\"\"\n        def observer(event):\n            self.assertEqual(event[\"log_source\"], thingo)\n\n        class Thingo(object):\n            log = TestLogger(observer=observer)\n\n        thingo = Thingo()\n        thingo.log.info()\n\n\n    def test_sourceUnbound(self):\n        \"\"\"\n        C{log_source} event key is L{None}.\n        \"\"\"\n        def observer(event):\n            self.assertIsNone(event[\"log_source\"])\n\n        log = TestLogger(observer=observer)\n        log.info()\n\n\n    def test_defaultFailure(self):\n        \"\"\"\n        Test that log.failure() emits the right data.\n        \"\"\"\n        log = TestLogger()\n        try:\n            raise RuntimeError(\"baloney!\")\n        except RuntimeError:\n            log.failure(\"Whoops\")\n\n        errors = self.flushLoggedErrors(RuntimeError)\n        self.assertEqual(len(errors), 1)\n\n        self.assertEqual(log.emitted[\"level\"], LogLevel.critical)\n        self.assertEqual(log.emitted[\"format\"], \"Whoops\")\n\n\n    def test_conflictingKwargs(self):\n        \"\"\"\n        Make sure that kwargs conflicting with args don't pass through.\n        \"\"\"\n        log = TestLogger()\n\n        log.warn(\n            u\"*\",\n            log_format=\"#\",\n            log_level=LogLevel.error,\n            log_namespace=\"*namespace*\",\n            log_source=\"*source*\",\n        )\n\n        self.assertEqual(log.event[\"log_format\"], u\"*\")\n        self.assertEqual(log.event[\"log_level\"], LogLevel.warn)\n        self.assertEqual(log.event[\"log_namespace\"], log.namespace)\n        self.assertIsNone(log.event[\"log_source\"])\n\n\n    def test_logInvalidLogLevel(self):\n        \"\"\"\n        Test passing in a bogus log level to C{emit()}.\n        \"\"\"\n        log = TestLogger()\n\n        log.emit(\"*bogus*\")\n\n        errors = self.flushLoggedErrors(InvalidLogLevelError)\n        self.assertEqual(len(errors), 1)\n\n\n    def test_trace(self):\n        \"\"\"\n        Tracing keeps track of forwarding to the publisher.\n        \"\"\"\n        def publisher(event):\n            observer(event)\n\n        def observer(event):\n            self.assertEqual(event[\"log_trace\"], [(log, publisher)])\n\n        log = TestLogger(observer=publisher)\n        log.info(\"Hello.\", log_trace=[])\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_observer.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._observer}.\n\"\"\"\n\nfrom zope.interface.verify import verifyObject, BrokenMethodImplementation\n\nfrom twisted.trial import unittest\n\nfrom .._logger import Logger\nfrom .._observer import ILogObserver\nfrom .._observer import LogPublisher\n\n\n\nclass LogPublisherTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{LogPublisher}.\n    \"\"\"\n\n    def test_interface(self):\n        \"\"\"\n        L{LogPublisher} is an L{ILogObserver}.\n        \"\"\"\n        publisher = LogPublisher()\n        try:\n            verifyObject(ILogObserver, publisher)\n        except BrokenMethodImplementation as e:\n            self.fail(e)\n\n\n    def test_observers(self):\n        \"\"\"\n        L{LogPublisher.observers} returns the observers.\n        \"\"\"\n        o1 = lambda e: None\n        o2 = lambda e: None\n\n        publisher = LogPublisher(o1, o2)\n        self.assertEqual(set((o1, o2)), set(publisher._observers))\n\n\n    def test_addObserver(self):\n        \"\"\"\n        L{LogPublisher.addObserver} adds an observer.\n        \"\"\"\n        o1 = lambda e: None\n        o2 = lambda e: None\n        o3 = lambda e: None\n\n        publisher = LogPublisher(o1, o2)\n        publisher.addObserver(o3)\n        self.assertEqual(set((o1, o2, o3)), set(publisher._observers))\n\n\n    def test_addObserverNotCallable(self):\n        \"\"\"\n        L{LogPublisher.addObserver} refuses to add an observer that's\n        not callable.\n        \"\"\"\n        publisher = LogPublisher()\n        self.assertRaises(TypeError, publisher.addObserver, object())\n\n\n    def test_removeObserver(self):\n        \"\"\"\n        L{LogPublisher.removeObserver} removes an observer.\n        \"\"\"\n        o1 = lambda e: None\n        o2 = lambda e: None\n        o3 = lambda e: None\n\n        publisher = LogPublisher(o1, o2, o3)\n        publisher.removeObserver(o2)\n        self.assertEqual(set((o1, o3)), set(publisher._observers))\n\n\n    def test_removeObserverNotRegistered(self):\n        \"\"\"\n        L{LogPublisher.removeObserver} removes an observer that is not\n        registered.\n        \"\"\"\n        o1 = lambda e: None\n        o2 = lambda e: None\n        o3 = lambda e: None\n\n        publisher = LogPublisher(o1, o2)\n        publisher.removeObserver(o3)\n        self.assertEqual(set((o1, o2)), set(publisher._observers))\n\n\n    def test_fanOut(self):\n        \"\"\"\n        L{LogPublisher} calls its observers.\n        \"\"\"\n        event = dict(foo=1, bar=2)\n\n        events1 = []\n        events2 = []\n        events3 = []\n\n        o1 = lambda e: events1.append(e)\n        o2 = lambda e: events2.append(e)\n        o3 = lambda e: events3.append(e)\n\n        publisher = LogPublisher(o1, o2, o3)\n        publisher(event)\n        self.assertIn(event, events1)\n        self.assertIn(event, events2)\n        self.assertIn(event, events3)\n\n\n    def test_observerRaises(self):\n        \"\"\"\n        Observer raises an exception during fan out: a failure is logged, but\n        not re-raised.  Life goes on.\n        \"\"\"\n        event = dict(foo=1, bar=2)\n        exception = RuntimeError(\"ARGH! EVIL DEATH!\")\n\n        events = []\n\n        def observer(event):\n            shouldRaise = not events\n            events.append(event)\n            if shouldRaise:\n                raise exception\n\n        collector = []\n\n        publisher = LogPublisher(observer, collector.append)\n        publisher(event)\n\n        # Verify that the observer saw my event\n        self.assertIn(event, events)\n\n        # Verify that the observer raised my exception\n        errors = [\n            e[\"log_failure\"] for e in collector\n            if \"log_failure\" in e\n        ]\n        self.assertEqual(len(errors), 1)\n        self.assertIs(errors[0].value, exception)\n        # Make sure the exceptional observer does not receive its own error.\n        self.assertEqual(len(events), 1)\n\n\n    def test_observerRaisesAndLoggerHatesMe(self):\n        \"\"\"\n        Observer raises an exception during fan out and the publisher's Logger\n        pukes when the failure is reported.  The exception does not propagate\n        back to the caller.\n        \"\"\"\n        event = dict(foo=1, bar=2)\n        exception = RuntimeError(\"ARGH! EVIL DEATH!\")\n\n        def observer(event):\n            raise RuntimeError(\"Sad panda\")\n\n        class GurkLogger(Logger):\n            def failure(self, *args, **kwargs):\n                raise exception\n\n        publisher = LogPublisher(observer)\n        publisher.log = GurkLogger()\n        publisher(event)\n\n        # Here, the lack of an exception thus far is a success, of sorts\n\n\n    def test_trace(self):\n        \"\"\"\n        Tracing keeps track of forwarding to observers.\n        \"\"\"\n        event = dict(foo=1, bar=2, log_trace=[])\n\n        traces = {}\n\n        # Copy trace to a tuple; otherwise, both observers will store the same\n        # mutable list, and we won't be able to see o1's view distinctly.\n        o1 = lambda e: traces.setdefault(1, tuple(e[\"log_trace\"]))\n        o2 = lambda e: traces.setdefault(2, tuple(e[\"log_trace\"]))\n\n        publisher = LogPublisher(o1, o2)\n        publisher(event)\n\n        self.assertEqual(traces[1], ((publisher, o1),))\n        self.assertEqual(traces[2], ((publisher, o1), (publisher, o2)))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_stdlib.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._format}.\n\"\"\"\n\nimport sys\nfrom io import BytesIO, TextIOWrapper\nimport logging as py_logging\nfrom inspect import getsourcefile\n\nfrom zope.interface.verify import verifyObject, BrokenMethodImplementation\n\nfrom twisted.python.compat import _PY3, currentframe\nfrom twisted.python.failure import Failure\nfrom twisted.trial import unittest\n\nfrom .._levels import LogLevel\nfrom .._observer import ILogObserver\nfrom .._stdlib import STDLibLogObserver\n\n\ndef nextLine():\n    \"\"\"\n    Retrive the file name and line number immediately after where this function\n    is called.\n\n    @return: the file name and line number\n    @rtype: 2-L{tuple} of L{str}, L{int}\n    \"\"\"\n    caller = currentframe(1)\n    return (getsourcefile(sys.modules[caller.f_globals['__name__']]),\n            caller.f_lineno + 1)\n\n\n\nclass STDLibLogObserverTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{STDLibLogObserver}.\n    \"\"\"\n\n    def test_interface(self):\n        \"\"\"\n        L{STDLibLogObserver} is an L{ILogObserver}.\n        \"\"\"\n        observer = STDLibLogObserver()\n        try:\n            verifyObject(ILogObserver, observer)\n        except BrokenMethodImplementation as e:\n            self.fail(e)\n\n\n    def py_logger(self):\n        \"\"\"\n        Create a logging object we can use to test with.\n\n        @return: a stdlib-style logger\n        @rtype: L{StdlibLoggingContainer}\n        \"\"\"\n        logger = StdlibLoggingContainer()\n        self.addCleanup(logger.close)\n        return logger\n\n\n    def logEvent(self, *events):\n        \"\"\"\n        Send one or more events to Python's logging module, and\n        capture the emitted L{logging.LogRecord}s and output stream as\n        a string.\n\n        @param events: events\n        @type events: L{tuple} of L{dict}\n\n        @return: a tuple: (records, output)\n        @rtype: 2-tuple of (L{list} of L{logging.LogRecord}, L{bytes}.)\n        \"\"\"\n        pl = self.py_logger()\n        observer = STDLibLogObserver(\n            # Add 1 to default stack depth to skip *this* frame, since\n            # tests will want to know about their own frames.\n            stackDepth=STDLibLogObserver.defaultStackDepth + 1\n        )\n        for event in events:\n            observer(event)\n        return pl.bufferedHandler.records, pl.outputAsText()\n\n\n    def test_name(self):\n        \"\"\"\n        Logger name.\n        \"\"\"\n        records, output = self.logEvent({})\n\n        self.assertEqual(len(records), 1)\n        self.assertEqual(records[0].name, \"twisted\")\n\n\n    def test_levels(self):\n        \"\"\"\n        Log levels.\n        \"\"\"\n        levelMapping = {\n            None: py_logging.INFO,  # Default\n            LogLevel.debug: py_logging.DEBUG,\n            LogLevel.info: py_logging.INFO,\n            LogLevel.warn: py_logging.WARNING,\n            LogLevel.error: py_logging.ERROR,\n            LogLevel.critical: py_logging.CRITICAL,\n        }\n\n        # Build a set of events for each log level\n        events = []\n        for level, pyLevel in levelMapping.items():\n            event = {}\n\n            # Set the log level on the event, except for default\n            if level is not None:\n                event[\"log_level\"] = level\n\n            # Remember the Python log level we expect to see for this\n            # event (as an int)\n            event[\"py_levelno\"] = int(pyLevel)\n\n            events.append(event)\n\n        records, output = self.logEvent(*events)\n        self.assertEqual(len(records), len(levelMapping))\n\n        # Check that each event has the correct level\n        for i in range(len(records)):\n            self.assertEqual(records[i].levelno, events[i][\"py_levelno\"])\n\n\n    def test_callerInfo(self):\n        \"\"\"\n        C{pathname}, C{lineno}, C{exc_info}, C{func} is set properly on\n        records.\n        \"\"\"\n        filename, logLine = nextLine()\n        records, output = self.logEvent({})\n\n        self.assertEqual(len(records), 1)\n        self.assertEqual(records[0].pathname, filename)\n        self.assertEqual(records[0].lineno, logLine)\n        self.assertIsNone(records[0].exc_info)\n\n        # Attribute \"func\" is missing from record, which is weird because it's\n        # documented.\n        # self.assertEqual(records[0].func, \"test_callerInfo\")\n\n\n    def test_basicFormat(self):\n        \"\"\"\n        Basic formattable event passes the format along correctly.\n        \"\"\"\n        event = dict(log_format=\"Hello, {who}!\", who=\"dude\")\n        records, output = self.logEvent(event)\n\n        self.assertEqual(len(records), 1)\n        self.assertEqual(str(records[0].msg), u\"Hello, dude!\")\n        self.assertEqual(records[0].args, ())\n\n\n    def test_basicFormatRendered(self):\n        \"\"\"\n        Basic formattable event renders correctly.\n        \"\"\"\n        event = dict(log_format=\"Hello, {who}!\", who=\"dude\")\n        records, output = self.logEvent(event)\n\n        self.assertEqual(len(records), 1)\n        self.assertTrue(output.endswith(u\":Hello, dude!\\n\"),\n                        repr(output))\n\n\n    def test_noFormat(self):\n        \"\"\"\n        Event with no format.\n        \"\"\"\n        records, output = self.logEvent({})\n\n        self.assertEqual(len(records), 1)\n        self.assertEqual(str(records[0].msg), \"\")\n\n\n    def test_failure(self):\n        \"\"\"\n        An event with a failure logs the failure details as well.\n        \"\"\"\n        def failing_func():\n            1 / 0\n        try:\n            failing_func()\n        except ZeroDivisionError:\n            failure = Failure()\n        event = dict(log_format='Hi mom', who='me', log_failure=failure)\n        records, output = self.logEvent(event)\n        self.assertEqual(len(records), 1)\n        self.assertIn(u'Hi mom', output)\n        self.assertIn(u'in failing_func', output)\n        self.assertIn(u'ZeroDivisionError', output)\n\n\n    def test_cleanedFailure(self):\n        \"\"\"\n        A cleaned Failure object has a fake traceback object; make sure that\n        logging such a failure still results in the exception details being\n        logged.\n        \"\"\"\n        def failing_func():\n            1 / 0\n        try:\n            failing_func()\n        except ZeroDivisionError:\n            failure = Failure()\n        failure.cleanFailure()\n        event = dict(log_format='Hi mom', who='me', log_failure=failure)\n        records, output = self.logEvent(event)\n        self.assertEqual(len(records), 1)\n        self.assertIn(u'Hi mom', output)\n        self.assertIn(u'in failing_func', output)\n        self.assertIn(u'ZeroDivisionError', output)\n\n\n\nclass StdlibLoggingContainer(object):\n    \"\"\"\n    Continer for a test configuration of stdlib logging objects.\n    \"\"\"\n\n    def __init__(self):\n        self.rootLogger = py_logging.getLogger(\"\")\n\n        self.originalLevel = self.rootLogger.getEffectiveLevel()\n        self.rootLogger.setLevel(py_logging.DEBUG)\n\n        self.bufferedHandler = BufferedHandler()\n        self.rootLogger.addHandler(self.bufferedHandler)\n\n        self.streamHandler, self.output = handlerAndBytesIO()\n        self.rootLogger.addHandler(self.streamHandler)\n\n\n    def close(self):\n        \"\"\"\n        Close the logger.\n        \"\"\"\n        self.rootLogger.setLevel(self.originalLevel)\n        self.rootLogger.removeHandler(self.bufferedHandler)\n        self.rootLogger.removeHandler(self.streamHandler)\n        self.streamHandler.close()\n        self.output.close()\n\n\n    def outputAsText(self):\n        \"\"\"\n        Get the output to the underlying stream as text.\n\n        @return: the output text\n        @rtype: L{unicode}\n        \"\"\"\n        return self.output.getvalue().decode(\"utf-8\")\n\n\n\ndef handlerAndBytesIO():\n    \"\"\"\n    Construct a 2-tuple of C{(StreamHandler, BytesIO)} for testing interaction\n    with the 'logging' module.\n\n    @return: handler and io object\n    @rtype: tuple of L{StreamHandler} and L{io.BytesIO}\n    \"\"\"\n    output = BytesIO()\n    stream = output\n    template = py_logging.BASIC_FORMAT\n    if _PY3:\n        stream = TextIOWrapper(output, encoding=\"utf-8\", newline=\"\\n\")\n    formatter = py_logging.Formatter(template)\n    handler = py_logging.StreamHandler(stream)\n    handler.setFormatter(formatter)\n    return handler, output\n\n\n\nclass BufferedHandler(py_logging.Handler):\n    \"\"\"\n    A L{py_logging.Handler} that remembers all logged records in a list.\n    \"\"\"\n\n    def __init__(self):\n        \"\"\"\n        Initialize this L{BufferedHandler}.\n        \"\"\"\n        py_logging.Handler.__init__(self)\n        self.records = []\n\n\n    def emit(self, record):\n        \"\"\"\n        Remember the record.\n        \"\"\"\n        self.records.append(record)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/logger/test/test_util.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for L{twisted.logger._util}.\n\"\"\"\n\nfrom twisted.trial import unittest\n\nfrom .._observer import LogPublisher\nfrom .._util import formatTrace\n\n\n\nclass UtilTests(unittest.TestCase):\n    \"\"\"\n    Utility tests.\n    \"\"\"\n\n    def test_trace(self):\n        \"\"\"\n        Tracing keeps track of forwarding done by the publisher.\n        \"\"\"\n        publisher = LogPublisher()\n\n        event = dict(log_trace=[])\n\n        o1 = lambda e: None\n\n        def o2(e):\n            self.assertIs(e, event)\n            self.assertEqual(\n                e[\"log_trace\"],\n                [\n                    (publisher, o1),\n                    (publisher, o2),\n                    # Event hasn't been sent to o3 yet\n                ]\n            )\n\n        def o3(e):\n            self.assertIs(e, event)\n            self.assertEqual(\n                e[\"log_trace\"],\n                [\n                    (publisher, o1),\n                    (publisher, o2),\n                    (publisher, o3),\n                ]\n            )\n\n        publisher.addObserver(o1)\n        publisher.addObserver(o2)\n        publisher.addObserver(o3)\n        publisher(event)\n\n\n    def test_formatTrace(self):\n        \"\"\"\n        Format trace as string.\n        \"\"\"\n        event = dict(log_trace=[])\n\n        def noOp(e):\n            pass\n\n        o1, o2, o3, o4, o5 = noOp, noOp, noOp, noOp, noOp\n\n        o1.name = \"root/o1\"\n        o2.name = \"root/p1/o2\"\n        o3.name = \"root/p1/o3\"\n        o4.name = \"root/p1/p2/o4\"\n        o5.name = \"root/o5\"\n\n        def testObserver(e):\n            self.assertIs(e, event)\n            trace = formatTrace(e[\"log_trace\"])\n            self.assertEqual(\n                trace,\n                (\n                    u\"{root} ({root.name})\\n\"\n                    u\"  -> {o1} ({o1.name})\\n\"\n                    u\"  -> {p1} ({p1.name})\\n\"\n                    u\"    -> {o2} ({o2.name})\\n\"\n                    u\"    -> {o3} ({o3.name})\\n\"\n                    u\"    -> {p2} ({p2.name})\\n\"\n                    u\"      -> {o4} ({o4.name})\\n\"\n                    u\"  -> {o5} ({o5.name})\\n\"\n                    u\"  -> {oTest}\\n\"\n                ).format(\n                    root=root,\n                    o1=o1, o2=o2, o3=o3, o4=o4, o5=o5,\n                    p1=p1, p2=p2,\n                    oTest=oTest\n                )\n            )\n        oTest = testObserver\n\n        p2 = LogPublisher(o4)\n        p1 = LogPublisher(o2, o3, p2)\n\n        p2.name = \"root/p1/p2/\"\n        p1.name = \"root/p1/\"\n\n        root = LogPublisher(o1, p1, o5, oTest)\n        root.name = \"root/\"\n        root(event)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTwisted Mail: Servers and clients for POP3, ESMTP, and IMAP.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/_cred.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nCredential managers for L{twisted.mail}.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport hmac\n\nfrom zope.interface import implementer\n\nfrom twisted.cred import credentials\nfrom twisted.python.compat import nativeString\nfrom twisted.mail._except import IllegalClientResponse\nfrom twisted.mail.interfaces import IClientAuthentication, IChallengeResponse\n\n\n@implementer(IClientAuthentication)\nclass CramMD5ClientAuthenticator:\n    def __init__(self, user):\n        self.user = user\n\n\n    def getName(self):\n        return b\"CRAM-MD5\"\n\n\n    def challengeResponse(self, secret, chal):\n        response = hmac.HMAC(secret, chal).hexdigest().encode('ascii')\n        return self.user + b' ' + response\n\n\n\n@implementer(IClientAuthentication)\nclass LOGINAuthenticator:\n    def __init__(self, user):\n        self.user = user\n        self.challengeResponse = self.challengeUsername\n\n\n    def getName(self):\n        return b\"LOGIN\"\n\n\n    def challengeUsername(self, secret, chal):\n        # Respond to something like \"Username:\"\n        self.challengeResponse = self.challengeSecret\n        return self.user\n\n\n    def challengeSecret(self, secret, chal):\n        # Respond to something like \"Password:\"\n        return secret\n\n\n\n@implementer(IClientAuthentication)\nclass PLAINAuthenticator:\n    def __init__(self, user):\n        self.user = user\n\n\n    def getName(self):\n        return b\"PLAIN\"\n\n\n    def challengeResponse(self, secret, chal):\n        return b'\\0' + self.user + b'\\0' + secret\n\n\n\n@implementer(IChallengeResponse)\nclass LOGINCredentials(credentials.UsernamePassword):\n    def __init__(self):\n        self.challenges = [b'Password\\0', b'User Name\\0']\n        self.responses = [b'password', b'username']\n        credentials.UsernamePassword.__init__(self, None, None)\n\n\n    def getChallenge(self):\n        return self.challenges.pop()\n\n\n    def setResponse(self, response):\n        setattr(self, nativeString(self.responses.pop()), response)\n\n\n    def moreChallenges(self):\n        return bool(self.challenges)\n\n\n\n@implementer(IChallengeResponse)\nclass PLAINCredentials(credentials.UsernamePassword):\n    def __init__(self):\n        credentials.UsernamePassword.__init__(self, None, None)\n\n\n    def getChallenge(self):\n        return b''\n\n\n    def setResponse(self, response):\n        parts = response.split(b'\\0')\n        if len(parts) != 3:\n            raise IllegalClientResponse(\n                \"Malformed Response - wrong number of parts\")\n        useless, self.username, self.password = parts\n\n\n    def moreChallenges(self):\n        return False\n\n\n__all__ = [\n    \"CramMD5ClientAuthenticator\",\n    \"LOGINCredentials\", \"LOGINAuthenticator\",\n    \"PLAINCredentials\", \"PLAINAuthenticator\",\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/_except.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nExceptions in L{twisted.mail}.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom twisted.python.compat import _PY3, unicode\n\n\nclass IMAP4Exception(Exception):\n    pass\n\n\n\nclass IllegalClientResponse(IMAP4Exception):\n    pass\n\n\n\nclass IllegalOperation(IMAP4Exception):\n    pass\n\n\n\nclass IllegalMailboxEncoding(IMAP4Exception):\n    pass\n\n\n\nclass MailboxException(IMAP4Exception):\n    pass\n\n\n\nclass MailboxCollision(MailboxException):\n    def __str__(self):\n        return 'Mailbox named %s already exists' % self.args\n\n\n\nclass NoSuchMailbox(MailboxException):\n    def __str__(self):\n        return 'No mailbox named %s exists' % self.args\n\n\n\nclass ReadOnlyMailbox(MailboxException):\n    def __str__(self):\n        return 'Mailbox open in read-only state'\n\n\nclass UnhandledResponse(IMAP4Exception):\n    pass\n\n\n\nclass NegativeResponse(IMAP4Exception):\n    pass\n\n\n\nclass NoSupportedAuthentication(IMAP4Exception):\n    def __init__(self, serverSupports, clientSupports):\n        IMAP4Exception.__init__(\n            self, 'No supported authentication schemes available')\n        self.serverSupports = serverSupports\n        self.clientSupports = clientSupports\n\n    def __str__(self):\n        return (IMAP4Exception.__str__(self)\n            + ': Server supports %r, client supports %r'\n            % (self.serverSupports, self.clientSupports))\n\n\n\nclass IllegalServerResponse(IMAP4Exception):\n    pass\n\n\n\nclass IllegalIdentifierError(IMAP4Exception):\n    pass\n\n\n\nclass IllegalQueryError(IMAP4Exception):\n    pass\n\n\n\nclass MismatchedNesting(IMAP4Exception):\n    pass\n\n\n\nclass MismatchedQuoting(IMAP4Exception):\n    pass\n\n\n\nclass SMTPError(Exception):\n    pass\n\n\n\nclass SMTPClientError(SMTPError):\n    \"\"\"\n    Base class for SMTP client errors.\n    \"\"\"\n    def __init__(self, code, resp, log=None, addresses=None, isFatal=False,\n                 retry=False):\n        \"\"\"\n        @param code: The SMTP response code associated with this error.\n\n        @param resp: The string response associated with this error.\n\n        @param log: A string log of the exchange leading up to and including\n            the error.\n        @type log: L{bytes}\n\n        @param isFatal: A boolean indicating whether this connection can\n            proceed or not. If True, the connection will be dropped.\n\n        @param retry: A boolean indicating whether the delivery should be\n            retried. If True and the factory indicates further retries are\n            desirable, they will be attempted, otherwise the delivery will be\n            failed.\n        \"\"\"\n        self.code = code\n        self.resp = resp\n        self.log = log\n        self.addresses = addresses\n        self.isFatal = isFatal\n        self.retry = retry\n\n\n    def __str__(self):\n        if _PY3:\n            return self.__bytes__().decode(\"utf-8\")\n        else:\n            return self.__bytes__()\n\n\n    def __bytes__(self):\n        if self.code > 0:\n            res = [u\"{:03d} {}\".format(self.code, self.resp)]\n        else:\n            res = [self.resp]\n        if self.log:\n            res.append(self.log)\n            res.append(b'')\n        for (i, r) in enumerate(res):\n            if isinstance(r, unicode):\n                res[i] = r.encode('utf-8')\n        return b'\\n'.join(res)\n\n\n\nclass ESMTPClientError(SMTPClientError):\n    \"\"\"\n    Base class for ESMTP client errors.\n    \"\"\"\n\n\n\nclass EHLORequiredError(ESMTPClientError):\n    \"\"\"\n    The server does not support EHLO.\n\n    This is considered a non-fatal error (the connection will not be dropped).\n    \"\"\"\n\n\n\nclass AUTHRequiredError(ESMTPClientError):\n    \"\"\"\n    Authentication was required but the server does not support it.\n\n    This is considered a non-fatal error (the connection will not be dropped).\n    \"\"\"\n\n\n\nclass TLSRequiredError(ESMTPClientError):\n    \"\"\"\n    Transport security was required but the server does not support it.\n\n    This is considered a non-fatal error (the connection will not be dropped).\n    \"\"\"\n\n\n\nclass AUTHDeclinedError(ESMTPClientError):\n    \"\"\"\n    The server rejected our credentials.\n\n    Either the username, password, or challenge response\n    given to the server was rejected.\n\n    This is considered a non-fatal error (the connection will not be\n    dropped).\n    \"\"\"\n\n\n\nclass AuthenticationError(ESMTPClientError):\n    \"\"\"\n    An error occurred while authenticating.\n\n    Either the server rejected our request for authentication or the\n    challenge received was malformed.\n\n    This is considered a non-fatal error (the connection will not be\n    dropped).\n    \"\"\"\n\n\n\nclass SMTPTLSError(ESMTPClientError):\n    \"\"\"\n    An error occurred while negiotiating for transport security.\n\n    This is considered a non-fatal error (the connection will not be dropped).\n    \"\"\"\n\n\n\nclass SMTPConnectError(SMTPClientError):\n    \"\"\"\n    Failed to connect to the mail exchange host.\n\n    This is considered a fatal error.  A retry will be made.\n    \"\"\"\n    def __init__(self, code, resp, log=None, addresses=None, isFatal=True,\n                 retry=True):\n        SMTPClientError.__init__(self, code, resp, log, addresses, isFatal,\n                                 retry)\n\n\n\nclass SMTPTimeoutError(SMTPClientError):\n    \"\"\"\n    Failed to receive a response from the server in the expected time period.\n\n    This is considered a fatal error.  A retry will be made.\n    \"\"\"\n    def __init__(self, code, resp, log=None, addresses=None, isFatal=True,\n                 retry=True):\n        SMTPClientError.__init__(self, code, resp, log, addresses, isFatal,\n                                 retry)\n\n\n\nclass SMTPProtocolError(SMTPClientError):\n    \"\"\"\n    The server sent a mangled response.\n\n    This is considered a fatal error.  A retry will not be made.\n    \"\"\"\n    def __init__(self, code, resp, log=None, addresses=None, isFatal=True,\n                 retry=False):\n        SMTPClientError.__init__(self, code, resp, log, addresses, isFatal,\n                                 retry)\n\n\n\nclass SMTPDeliveryError(SMTPClientError):\n    \"\"\"\n    Indicates that a delivery attempt has had an error.\n    \"\"\"\n\n\n\nclass SMTPServerError(SMTPError):\n    def __init__(self, code, resp):\n        self.code = code\n        self.resp = resp\n\n\n    def __str__(self):\n        return \"%.3d %s\" % (self.code, self.resp)\n\n\n\nclass SMTPAddressError(SMTPServerError):\n    def __init__(self, addr, code, resp):\n        from twisted.mail.smtp import Address\n\n        SMTPServerError.__init__(self, code, resp)\n        self.addr = Address(addr)\n\n\n    def __str__(self):\n        return \"%.3d <%s>... %s\" % (self.code, self.addr, self.resp)\n\n\n\nclass SMTPBadRcpt(SMTPAddressError):\n    def __init__(self, addr, code=550,\n                 resp='Cannot receive for specified address'):\n        SMTPAddressError.__init__(self, addr, code, resp)\n\n\n\nclass SMTPBadSender(SMTPAddressError):\n    def __init__(self, addr, code=550, resp='Sender not acceptable'):\n        SMTPAddressError.__init__(self, addr, code, resp)\n\n\n\nclass AddressError(SMTPError):\n    \"\"\"\n    Parse error in address\n    \"\"\"\n\n\nclass POP3Error(Exception):\n    \"\"\"\n    The base class for POP3 errors.\n    \"\"\"\n    pass\n\n\n\nclass _POP3MessageDeleted(Exception):\n    \"\"\"\n    An internal control-flow error which indicates that a deleted message was\n    requested.\n    \"\"\"\n\n\n\nclass POP3ClientError(Exception):\n    \"\"\"\n    The base class for all exceptions raised by POP3Client.\n    \"\"\"\n\n\n\nclass InsecureAuthenticationDisallowed(POP3ClientError):\n    \"\"\"\n    An error indicating secure authentication was required but no mechanism\n    could be found.\n    \"\"\"\n\n\n\nclass TLSError(POP3ClientError):\n    \"\"\"\n    An error indicating secure authentication was required but either the\n    transport does not support TLS or no TLS context factory was supplied.\n    \"\"\"\n\n\n\nclass TLSNotSupportedError(POP3ClientError):\n    \"\"\"\n    An error indicating secure authentication was required but the server does\n    not support TLS.\n    \"\"\"\n\n\n\nclass ServerErrorResponse(POP3ClientError):\n    \"\"\"\n    An error indicating that the server returned an error response to a\n    request.\n\n    @ivar consumer: See L{__init__}\n    \"\"\"\n    def __init__(self, reason, consumer=None):\n        \"\"\"\n        @type reason: L{bytes}\n        @param reason: The server response minus the status indicator.\n\n        @type consumer: callable that takes L{object}\n        @param consumer: The function meant to handle the values for a\n            multi-line response.\n        \"\"\"\n        POP3ClientError.__init__(self, reason)\n        self.consumer = consumer\n\n\n\nclass LineTooLong(POP3ClientError):\n    \"\"\"\n    An error indicating that the server sent a line which exceeded the\n    maximum line length (L{LineOnlyReceiver.MAX_LENGTH}).\n    \"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/imap4.py",
    "content": "# -*- test-case-name: twisted.mail.test.test_imap.IMAP4HelperTests -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAn IMAP4 protocol implementation\n\n@author: Jp Calderone\n\nTo do::\n  Suspend idle timeout while server is processing\n  Use an async message parser instead of buffering in memory\n  Figure out a way to not queue multi-message client requests (Flow? A simple callback?)\n  Clarify some API docs (Query, etc)\n  Make APPEND recognize (again) non-existent mailboxes before accepting the literal\n\"\"\"\n\nimport binascii\nimport codecs\nimport copy\nimport functools\nimport re\nimport string\nimport tempfile\nimport time\nimport uuid\n\nimport email.utils\n\nfrom itertools import chain\nfrom io import BytesIO\n\nfrom zope.interface import implementer\n\nfrom twisted.protocols import basic\nfrom twisted.protocols import policies\nfrom twisted.internet import defer\nfrom twisted.internet import error\nfrom twisted.internet.defer import maybeDeferred\nfrom twisted.python import log, text\nfrom twisted.python.compat import (\n    _bytesChr, unichr as chr, _b64decodebytes as decodebytes,\n    _b64encodebytes as encodebytes,\n    intToBytes, iterbytes, long, nativeString, networkString, unicode,\n    _matchingString, _PY3, _get_async_param,\n)\nfrom twisted.internet import interfaces\n\nfrom twisted.cred import credentials\nfrom twisted.cred.error import UnauthorizedLogin, UnhandledCredentials\n\n# Re-exported for compatibility reasons\nfrom twisted.mail.interfaces import (\n    IClientAuthentication, INamespacePresenter,\n    IAccountIMAP as IAccount,\n    IMessageIMAPPart as IMessagePart,\n    IMessageIMAP as IMessage,\n    IMessageIMAPFile as IMessageFile,\n    ISearchableIMAPMailbox as ISearchableMailbox,\n    IMessageIMAPCopier as IMessageCopier,\n    IMailboxIMAPInfo as IMailboxInfo,\n    IMailboxIMAP as IMailbox,\n    ICloseableMailboxIMAP as ICloseableMailbox,\n    IMailboxIMAPListener as IMailboxListener\n)\nfrom twisted.mail._cred import (\n    CramMD5ClientAuthenticator,\n    LOGINAuthenticator, LOGINCredentials,\n    PLAINAuthenticator, PLAINCredentials)\nfrom twisted.mail._except import (\n    IMAP4Exception, IllegalClientResponse, IllegalOperation, MailboxException,\n    IllegalMailboxEncoding, MailboxCollision, NoSuchMailbox, ReadOnlyMailbox,\n    UnhandledResponse, NegativeResponse, NoSupportedAuthentication,\n    IllegalIdentifierError, IllegalQueryError, MismatchedNesting,\n    MismatchedQuoting, IllegalServerResponse,\n)\n\n# locale-independent month names to use instead of strftime's\n_MONTH_NAMES = dict(zip(\n        range(1, 13),\n        \"Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec\".split()))\n\n\ndef _swap(this, that, ifIs):\n    \"\"\"\n    Swap C{this} with C{that} if C{this} is C{ifIs}.\n\n    @param this: The object that may be replaced.\n\n    @param that: The object that may replace C{this}.\n\n    @param ifIs: An object whose identity will be compared to\n        C{this}.\n    \"\"\"\n    return that if this is ifIs else this\n\n\ndef _swapAllPairs(of, that, ifIs):\n    \"\"\"\n    Swap each element in each pair in C{of} with C{that} it is\n    C{ifIs}.\n\n    @param of: A list of 2-L{tuple}s, whose members may be the object\n        C{that}\n    @type of: L{list} of 2-L{tuple}s\n\n    @param ifIs: An object whose identity will be compared to members\n        of each pair in C{of}\n\n    @return: A L{list} of 2-L{tuple}s with all occurences of C{ifIs}\n        replaced with C{that}\n    \"\"\"\n    return [(_swap(first, that, ifIs), _swap(second, that, ifIs))\n            for first, second in of]\n\n\nclass MessageSet(object):\n    \"\"\"\n    A set of message identifiers usable by both L{IMAP4Client} and\n    L{IMAP4Server} via L{IMailboxIMAP.store} and\n    L{IMailboxIMAP.fetch}.\n\n    These identifiers can be either message sequence numbers or unique\n    identifiers.  See Section 2.3.1, \"Message Numbers\", RFC 3501.\n\n    This represents the C{sequence-set} described in Section 9,\n    \"Formal Syntax\" of RFC 3501:\n\n        - A L{MessageSet} can describe a single identifier, e.g.\n          C{MessageSet(1)}\n\n        - A L{MessageSet} can describe C{*} via L{None}, e.g.\n          C{MessageSet(None)}\n\n        - A L{MessageSet} can describe a range of identifiers, e.g.\n          C{MessageSet(1, 2)}.  The range is inclusive and unordered\n          (see C{seq-range} in RFC 3501, Section 9), so that\n          C{Message(2, 1)} is equivalent to C{MessageSet(1, 2)}, and\n          both describe messages 1 and 2.  Ranges can include C{*} by\n          specifying L{None}, e.g. C{MessageSet(None, 1)}.  In all\n          cases ranges are normalized so that the smallest identifier\n          comes first, and L{None} always comes last; C{Message(2, 1)}\n          becomes C{MessageSet(1, 2)} and C{MessageSet(None, 1)}\n          becomes C{MessageSet(1, None)}\n\n        - A L{MessageSet} can describe a sequence of single\n          identifiers and ranges, constructed by addition.\n          C{MessageSet(1) + MessageSet(5, 10)} refers the message\n          identified by C{1} and the messages identified by C{5}\n          through C{10}.\n\n    B{NB: The meaning of * varies, but it always represents the\n    largest number in use}.\n\n    B{For servers}: Your L{IMailboxIMAP} provider must set\n    L{MessageSet.last} to the highest-valued identifier (unique or\n    message sequence) before iterating over it.\n\n    B{For clients}: C{*} consumes ranges smaller than it, e.g.\n    C{MessageSet(1, 100) + MessageSet(50, None)} is equivalent to\n    C{1:*}.\n\n    @type getnext: Function taking L{int} returning L{int}\n    @ivar getnext: A function that returns the next message number,\n        used when iterating through the L{MessageSet}.  By default, a\n        function returning the next integer is supplied, but as this\n        can be rather inefficient for sparse UID iterations, it is\n        recommended to supply one when messages are requested by UID.\n        The argument is provided as a hint to the implementation and\n        may be ignored if it makes sense to do so (eg, if an iterator\n        is being used that maintains its own state, it is guaranteed\n        that it will not be called out-of-order).\n    \"\"\"\n    _empty = []\n    _infinity = float('inf')\n\n    def __init__(self, start=_empty, end=_empty):\n        \"\"\"\n        Create a new MessageSet()\n\n        @type start: Optional L{int}\n        @param start: Start of range, or only message number\n\n        @type end: Optional L{int}\n        @param end: End of range.\n        \"\"\"\n        self._last = self._empty # Last message/UID in use\n        self.ranges = [] # List of ranges included\n        self.getnext = lambda x: x+1 # A function which will return the next\n                                     # message id. Handy for UID requests.\n\n        if start is self._empty:\n            return\n\n        if isinstance(start, list):\n            self.ranges = start[:]\n            self.clean()\n        else:\n            self.add(start,end)\n\n\n    # Ooo.  A property.\n    def last():\n        def _setLast(self, value):\n            if self._last is not self._empty:\n                raise ValueError(\"last already set\")\n\n            self._last = value\n            for i, (l, h) in enumerate(self.ranges):\n                if l is None:\n                    l = value\n                if h is None:\n                    h = value\n                if l > h:\n                    l, h = h, l\n                self.ranges[i] = (l, h)\n            self.clean()\n\n        def _getLast(self):\n            return self._last\n\n        doc = '''\n              Replaces all occurrences of \"*\".  This should be the\n              largest number in use.  Must be set before attempting to\n              use the MessageSet as a container.\n\n              @raises: L{ValueError} if a largest value has already\n                  been set.\n              '''\n        return _getLast, _setLast, None, doc\n    last = property(*last())\n\n\n    def add(self, start, end=_empty):\n        \"\"\"\n        Add another range\n\n        @type start: L{int}\n        @param start: Start of range, or only message number\n\n        @type end: Optional L{int}\n        @param end: End of range.\n        \"\"\"\n        if end is self._empty:\n            end = start\n\n        if self._last is not self._empty:\n            if start is None:\n                start = self.last\n            if end is None:\n                end = self.last\n\n        start, end = sorted(\n            [start, end],\n            key=functools.partial(_swap, that=self._infinity, ifIs=None))\n        self.ranges.append((start, end))\n        self.clean()\n\n\n    def __add__(self, other):\n        if isinstance(other, MessageSet):\n            ranges = self.ranges + other.ranges\n            return MessageSet(ranges)\n        else:\n            res = MessageSet(self.ranges)\n            if self.last is not self._empty:\n                res.last = self.last\n            try:\n                res.add(*other)\n            except TypeError:\n                res.add(other)\n            return res\n\n\n    def extend(self, other):\n        \"\"\"\n        Extend our messages with another message or set of messages.\n\n        @param other: The messages to include.\n        @type other: L{MessageSet}, L{tuple} of two L{int}s, or a\n            single L{int}\n        \"\"\"\n        if isinstance(other, MessageSet):\n            self.ranges.extend(other.ranges)\n            self.clean()\n        else:\n            try:\n                self.add(*other)\n            except TypeError:\n                self.add(other)\n\n        return self\n\n\n    def clean(self):\n        \"\"\"\n        Clean ranges list, combining adjacent ranges\n        \"\"\"\n\n        ranges = sorted(_swapAllPairs(self.ranges,\n                                      that=self._infinity,\n                                      ifIs=None))\n\n        mergedRanges = [(float('-inf'), float('-inf'))]\n\n\n        for low, high in ranges:\n            previousLow, previousHigh = mergedRanges[-1]\n\n            if previousHigh < low - 1:\n                mergedRanges.append((low, high))\n                continue\n\n            mergedRanges[-1] = (min(previousLow, low),\n                                max(previousHigh, high))\n\n        self.ranges = _swapAllPairs(mergedRanges[1:],\n                                    that=None,\n                                    ifIs=self._infinity)\n\n\n    def _noneInRanges(self):\n        \"\"\"\n        Is there a L{None} in our ranges?\n\n        L{MessageSet.clean} merges overlapping or consecutive ranges.\n        None is represents a value larger than any number.  There are\n        thus two cases:\n\n            1. C{(x, *) + (y, z)} such that C{x} is smaller than C{y}\n\n            2. C{(z, *) + (x, y)} such that C{z} is larger than C{y}\n\n        (Other cases, such as C{y < x < z}, can be split into these\n        two cases; for example C{(y - 1, y)} + C{(x, x) + (z, z + 1)})\n\n        In case 1, C{* > y} and C{* > z}, so C{(x, *) + (y, z) = (x,\n        *)}\n\n        In case 2, C{z > x and z > y}, so the intervals do not merge,\n        and the ranges are sorted as C{[(x, y), (z, *)]}.  C{*} is\n        represented as C{(*, *)}, so this is the same as 2.  but with\n        a C{z} that is greater than everything.\n\n        The result is that there is a maximum of two L{None}s, and one\n        of them has to be the high element in the last tuple in\n        C{self.ranges}.  That means checking if C{self.ranges[-1][-1]}\n        is L{None} suffices to check if I{any} element is L{None}.\n\n        @return: L{True} if L{None} is in some range in ranges and\n            L{False} if otherwise.\n        \"\"\"\n        return self.ranges[-1][-1] is None\n\n\n    def __contains__(self, value):\n        \"\"\"\n        May raise TypeError if we encounter an open-ended range\n\n        @param value: Is this in our ranges?\n        @type value: L{int}\n        \"\"\"\n\n        if self._noneInRanges():\n            raise TypeError(\n                \"Can't determine membership; last value not set\")\n\n        for low, high in self.ranges:\n            if low <= value <= high:\n                return True\n\n        return False\n\n\n    def _iterator(self):\n        for l, h in self.ranges:\n            l = self.getnext(l-1)\n            while l <= h:\n                yield l\n                l = self.getnext(l)\n\n\n    def __iter__(self):\n        if self._noneInRanges():\n            raise TypeError(\"Can't iterate; last value not set\")\n\n        return self._iterator()\n\n\n    def __len__(self):\n        res = 0\n        for l, h in self.ranges:\n            if l is None:\n                res += 1\n            elif h is None:\n                raise TypeError(\"Can't size object; last value not set\")\n            else:\n                res += (h - l) + 1\n\n        return res\n\n\n    def __str__(self):\n        p = []\n        for low, high in self.ranges:\n            if low == high:\n                if low is None:\n                    p.append('*')\n                else:\n                    p.append(str(low))\n            elif high is None:\n                p.append('%d:*' % (low,))\n            else:\n                p.append('%d:%d' % (low, high))\n        return ','.join(p)\n\n\n    def __repr__(self):\n        return '<MessageSet %s>' % (str(self),)\n\n\n    def __eq__(self, other):\n        if isinstance(other, MessageSet):\n            return self.ranges == other.ranges\n        return False\n\n    def __ne__(self, other):\n        return not self.__eq__(other)\n\n\nclass LiteralString:\n    def __init__(self, size, defered):\n        self.size = size\n        self.data = []\n        self.defer = defered\n\n\n    def write(self, data):\n        self.size -= len(data)\n        passon = None\n        if self.size > 0:\n            self.data.append(data)\n        else:\n            if self.size:\n                data, passon = data[:self.size], data[self.size:]\n            else:\n                passon = b''\n            if data:\n                self.data.append(data)\n\n        return passon\n\n\n    def callback(self, line):\n        \"\"\"\n        Call deferred with data and rest of line\n        \"\"\"\n        self.defer.callback((b''.join(self.data), line))\n\n\n\nclass LiteralFile:\n    _memoryFileLimit = 1024 * 1024 * 10\n\n    def __init__(self, size, defered):\n        self.size = size\n        self.defer = defered\n        if size > self._memoryFileLimit:\n            self.data = tempfile.TemporaryFile()\n        else:\n            self.data = BytesIO()\n\n\n    def write(self, data):\n        self.size -= len(data)\n        passon = None\n        if self.size > 0:\n            self.data.write(data)\n        else:\n            if self.size:\n                data, passon = data[:self.size], data[self.size:]\n            else:\n                passon = b''\n            if data:\n                self.data.write(data)\n        return passon\n\n\n    def callback(self, line):\n        \"\"\"\n        Call deferred with data and rest of line\n        \"\"\"\n        self.data.seek(0,0)\n        self.defer.callback((self.data, line))\n\n\n\nclass WriteBuffer:\n    \"\"\"\n    Buffer up a bunch of writes before sending them all to a transport at once.\n    \"\"\"\n    def __init__(self, transport, size=8192):\n        self.bufferSize = size\n        self.transport = transport\n        self._length = 0\n        self._writes = []\n\n\n    def write(self, s):\n        self._length += len(s)\n        self._writes.append(s)\n        if self._length > self.bufferSize:\n            self.flush()\n\n\n    def flush(self):\n        if self._writes:\n            self.transport.writeSequence(self._writes)\n            self._writes = []\n            self._length = 0\n\n\n\nclass Command:\n    _1_RESPONSES = (b'CAPABILITY', b'FLAGS', b'LIST', b'LSUB', b'STATUS', b'SEARCH', b'NAMESPACE')\n    _2_RESPONSES = (b'EXISTS', b'EXPUNGE', b'FETCH', b'RECENT')\n    _OK_RESPONSES = (b'UIDVALIDITY', b'UNSEEN', b'READ-WRITE', b'READ-ONLY', b'UIDNEXT', b'PERMANENTFLAGS')\n    defer = None\n\n    def __init__(self, command, args=None, wantResponse=(),\n                 continuation=None, *contArgs, **contKw):\n        self.command = command\n        self.args = args\n        self.wantResponse = wantResponse\n        self.continuation = lambda x: continuation(x, *contArgs, **contKw)\n        self.lines = []\n\n\n    def __repr__(self):\n        return \"<imap4.Command {!r} {!r} {!r} {!r} {!r}>\".format(\n            self.command, self.args, self.wantResponse, self.continuation,\n            self.lines\n        )\n\n\n    def format(self, tag):\n        if self.args is None:\n            return b' '.join((tag, self.command))\n        return b' '.join((tag, self.command, self.args))\n\n\n    def finish(self, lastLine, unusedCallback):\n        send = []\n        unuse = []\n        for L in self.lines:\n            names = parseNestedParens(L)\n            N = len(names)\n            if (N >= 1 and names[0] in self._1_RESPONSES or\n                N >= 2 and names[1] in self._2_RESPONSES or\n                N >= 2 and names[0] == b'OK' and isinstance(names[1], list)\n               and names[1][0] in self._OK_RESPONSES):\n                send.append(names)\n            else:\n                unuse.append(names)\n        d, self.defer = self.defer, None\n        d.callback((send, lastLine))\n        if unuse:\n            unusedCallback(unuse)\n\n\n\n# Some constants to help define what an atom is and is not - see the grammar\n# section of the IMAP4 RFC - <https://tools.ietf.org/html/rfc3501#section-9>.\n# Some definitions (SP, CTL, DQUOTE) are also from the ABNF RFC -\n# <https://tools.ietf.org/html/rfc2234>.\n_SP = b' '\n_CTL = b''.join(_bytesChr(ch) for ch in chain(range(0x21), range(0x80, 0x100)))\n\n# It is easier to define ATOM-CHAR in terms of what it does not match than in\n# terms of what it does match.\n_nonAtomChars = b']\\\\\\\\(){%*\"' + _SP + _CTL\n\n# _nonAtomRE is only used in Query, so it uses native strings.\nif _PY3:\n    #\n    _nativeNonAtomChars = _nonAtomChars.decode('charmap')\nelse:\n    _nativeNonAtomChars = _nonAtomChars\n_nonAtomRE = re.compile('[' + _nativeNonAtomChars + ']')\n\n# This is all the bytes that match the ATOM-CHAR from the grammar in the RFC.\n_atomChars = b''.join(_bytesChr(ch) for ch in list(range(0x100)) if _bytesChr(ch) not in _nonAtomChars)\n\n@implementer(IMailboxListener)\nclass IMAP4Server(basic.LineReceiver, policies.TimeoutMixin):\n    \"\"\"\n    Protocol implementation for an IMAP4rev1 server.\n\n    The server can be in any of four states:\n        - Non-authenticated\n        - Authenticated\n        - Selected\n        - Logout\n    \"\"\"\n    # Identifier for this server software\n    IDENT = b'Twisted IMAP4rev1 Ready'\n\n    # Number of seconds before idle timeout\n    # Initially 1 minute.  Raised to 30 minutes after login.\n    timeOut = 60\n\n    POSTAUTH_TIMEOUT = 60 * 30\n\n    # Whether STARTTLS has been issued successfully yet or not.\n    startedTLS = False\n\n    # Whether our transport supports TLS\n    canStartTLS = False\n\n    # Mapping of tags to commands we have received\n    tags = None\n\n    # The object which will handle logins for us\n    portal = None\n\n    # The account object for this connection\n    account = None\n\n    # Logout callback\n    _onLogout = None\n\n    # The currently selected mailbox\n    mbox = None\n\n    # Command data to be processed when literal data is received\n    _pendingLiteral = None\n\n    # Maximum length to accept for a \"short\" string literal\n    _literalStringLimit = 4096\n\n    # IChallengeResponse factories for AUTHENTICATE command\n    challengers = None\n\n    # Search terms the implementation of which needs to be passed both the last\n    # message identifier (UID) and the last sequence id.\n    _requiresLastMessageInfo = set([b\"OR\", b\"NOT\", b\"UID\"])\n\n    state = 'unauth'\n\n    parseState = 'command'\n\n    def __init__(self, chal = None, contextFactory = None, scheduler = None):\n        if chal is None:\n            chal = {}\n        self.challengers = chal\n        self.ctx = contextFactory\n        if scheduler is None:\n            scheduler = iterateInReactor\n        self._scheduler = scheduler\n        self._queuedAsync = []\n\n\n    def capabilities(self):\n        cap = {b'AUTH': list(self.challengers.keys())}\n        if self.ctx and self.canStartTLS:\n            if not self.startedTLS and interfaces.ISSLTransport(self.transport, None) is None:\n                cap[b'LOGINDISABLED'] = None\n                cap[b'STARTTLS'] = None\n        cap[b'NAMESPACE'] = None\n        cap[b'IDLE'] = None\n        return cap\n\n\n    def connectionMade(self):\n        self.tags = {}\n        self.canStartTLS = interfaces.ITLSTransport(self.transport, None) is not None\n        self.setTimeout(self.timeOut)\n        self.sendServerGreeting()\n\n\n    def connectionLost(self, reason):\n        self.setTimeout(None)\n        if self._onLogout:\n            self._onLogout()\n            self._onLogout = None\n\n\n    def timeoutConnection(self):\n        self.sendLine(b'* BYE Autologout; connection idle too long')\n        self.transport.loseConnection()\n        if self.mbox:\n            self.mbox.removeListener(self)\n            cmbx = ICloseableMailbox(self.mbox, None)\n            if cmbx is not None:\n                maybeDeferred(cmbx.close).addErrback(log.err)\n            self.mbox = None\n        self.state = 'timeout'\n\n\n    def rawDataReceived(self, data):\n        self.resetTimeout()\n        passon = self._pendingLiteral.write(data)\n        if passon is not None:\n            self.setLineMode(passon)\n\n    # Avoid processing commands while buffers are being dumped to\n    # our transport\n    blocked = None\n\n    def _unblock(self):\n        commands = self.blocked\n        self.blocked = None\n        while commands and self.blocked is None:\n            self.lineReceived(commands.pop(0))\n        if self.blocked is not None:\n            self.blocked.extend(commands)\n\n\n    def lineReceived(self, line):\n        if self.blocked is not None:\n            self.blocked.append(line)\n            return\n\n        self.resetTimeout()\n        f = getattr(self, 'parse_' + self.parseState)\n        try:\n            f(line)\n        except Exception as e:\n            self.sendUntaggedResponse(b'BAD Server error: ' + networkString(str(e)))\n            log.err()\n\n\n    def parse_command(self, line):\n        args = line.split(None, 2)\n        rest = None\n        if len(args) == 3:\n            tag, cmd, rest = args\n        elif len(args) == 2:\n            tag, cmd = args\n        elif len(args) == 1:\n            tag = args[0]\n            self.sendBadResponse(tag, b'Missing command')\n            return None\n        else:\n            self.sendBadResponse(None, b'Null command')\n            return None\n\n        cmd = cmd.upper()\n        try:\n            return self.dispatchCommand(tag, cmd, rest)\n        except IllegalClientResponse as e:\n            self.sendBadResponse(tag, b'Illegal syntax: ' + networkString(str(e)))\n        except IllegalOperation as e:\n            self.sendNegativeResponse(tag, b'Illegal operation: ' + networkString(str(e)))\n        except IllegalMailboxEncoding as e:\n            self.sendNegativeResponse(tag, b'Illegal mailbox name: ' + networkString(str(e)))\n\n\n    def parse_pending(self, line):\n        d = self._pendingLiteral\n        self._pendingLiteral = None\n        self.parseState = 'command'\n        d.callback(line)\n\n\n    def dispatchCommand(self, tag, cmd, rest, uid=None):\n        f = self.lookupCommand(cmd)\n        if f:\n            fn = f[0]\n            parseargs = f[1:]\n            self.__doCommand(tag, fn, [self, tag], parseargs, rest, uid)\n        else:\n            self.sendBadResponse(tag, b'Unsupported command')\n\n\n    def lookupCommand(self, cmd):\n        return getattr(self, '_'.join((self.state, nativeString(cmd.upper()))), None)\n\n\n    def __doCommand(self, tag, handler, args, parseargs, line, uid):\n        for (i, arg) in enumerate(parseargs):\n            if callable(arg):\n                parseargs = parseargs[i+1:]\n                maybeDeferred(arg, self, line).addCallback(\n                    self.__cbDispatch, tag, handler, args,\n                    parseargs, uid).addErrback(self.__ebDispatch, tag)\n                return\n            else:\n                args.append(arg)\n\n        if line:\n            # Too many arguments\n            raise IllegalClientResponse(\"Too many arguments for command: \" + repr(line))\n\n        if uid is not None:\n            handler(uid=uid, *args)\n        else:\n            handler(*args)\n\n\n    def __cbDispatch(self, result, tag, fn, args, parseargs, uid):\n        (arg, rest) = result\n        args.append(arg)\n        self.__doCommand(tag, fn, args, parseargs, rest, uid)\n\n\n    def __ebDispatch(self, failure, tag):\n        if failure.check(IllegalClientResponse):\n            self.sendBadResponse(tag, b'Illegal syntax: ' + networkString(str(failure.value)))\n        elif failure.check(IllegalOperation):\n            self.sendNegativeResponse(tag, b'Illegal operation: ' +\n                                      networkString(str(failure.value)))\n        elif failure.check(IllegalMailboxEncoding):\n            self.sendNegativeResponse(tag, b'Illegal mailbox name: ' +\n                                      networkString(str(failure.value)))\n        else:\n            self.sendBadResponse(tag, b'Server error: ' + networkString(str(failure.value)))\n            log.err(failure)\n\n\n    def _stringLiteral(self, size):\n        if size > self._literalStringLimit:\n            raise IllegalClientResponse(\n                \"Literal too long! I accept at most %d octets\" %\n                (self._literalStringLimit,))\n        d = defer.Deferred()\n        self.parseState = 'pending'\n        self._pendingLiteral = LiteralString(size, d)\n        self.sendContinuationRequest(\n            networkString('Ready for %d octets of text' % size))\n        self.setRawMode()\n        return d\n\n\n    def _fileLiteral(self, size):\n        d = defer.Deferred()\n        self.parseState = 'pending'\n        self._pendingLiteral = LiteralFile(size, d)\n        self.sendContinuationRequest(\n            networkString('Ready for %d octets of data' % size))\n        self.setRawMode()\n        return d\n\n\n    def arg_finalastring(self, line):\n        \"\"\"\n        Parse an astring from line that represents a command's final\n        argument.  This special case exists to enable parsing empty\n        string literals.\n\n        @param line: A line that contains a string literal.\n        @type line: L{bytes}\n\n        @return: A 2-tuple containing the parsed argument and any\n            trailing data, or a L{Deferred} that fires with that\n            2-tuple\n        @rtype: L{tuple} of (L{bytes}, L{bytes}) or a L{Deferred}\n\n        @see: https://twistedmatrix.com/trac/ticket/9207\n        \"\"\"\n        return self.arg_astring(line, final=True)\n\n\n    def arg_astring(self, line, final=False):\n        \"\"\"\n        Parse an astring from the line, return (arg, rest), possibly\n        via a deferred (to handle literals)\n\n        @param line: A line that contains a string literal.\n        @type line: L{bytes}\n\n        @param final: Is this the final argument?\n        @type final L{bool}\n\n        @return: A 2-tuple containing the parsed argument and any\n            trailing data, or a L{Deferred} that fires with that\n            2-tuple\n        @rtype: L{tuple} of (L{bytes}, L{bytes}) or a L{Deferred}\n\n        \"\"\"\n        line = line.strip()\n        if not line:\n            raise IllegalClientResponse(\"Missing argument\")\n        d = None\n        arg, rest = None, None\n        if line[0:1] == b'\"':\n            try:\n                spam, arg, rest = line.split(b'\"',2)\n                rest = rest[1:] # Strip space\n            except ValueError:\n                raise IllegalClientResponse(\"Unmatched quotes\")\n        elif line[0:1] == b'{':\n            # literal\n            if line[-1:] != b'}':\n                raise IllegalClientResponse(\"Malformed literal\")\n            try:\n                size = int(line[1:-1])\n            except ValueError:\n                raise IllegalClientResponse(\n                    \"Bad literal size: \" + repr(line[1:-1]))\n            if final and not size:\n                return (b'', b'')\n            d = self._stringLiteral(size)\n        else:\n            arg = line.split(b' ',1)\n            if len(arg) == 1:\n                arg.append(b'')\n            arg, rest = arg\n        return d or (arg, rest)\n\n    # ATOM: Any CHAR except ( ) { % * \" \\ ] CTL SP (CHAR is 7bit)\n    atomre = re.compile(b'(?P<atom>[' + re.escape(_atomChars) + b']+)( (?P<rest>.*$)|$)')\n\n\n    def arg_atom(self, line):\n        \"\"\"\n        Parse an atom from the line\n        \"\"\"\n        if not line:\n            raise IllegalClientResponse(\"Missing argument\")\n        m = self.atomre.match(line)\n        if m:\n            return m.group('atom'), m.group('rest')\n        else:\n            raise IllegalClientResponse(\"Malformed ATOM\")\n\n\n    def arg_plist(self, line):\n        \"\"\"\n        Parse a (non-nested) parenthesised list from the line\n        \"\"\"\n        if not line:\n            raise IllegalClientResponse(\"Missing argument\")\n\n        if line[:1] != b\"(\":\n            raise IllegalClientResponse(\"Missing parenthesis\")\n\n        i = line.find(b\")\")\n\n        if i == -1:\n            raise IllegalClientResponse(\"Mismatched parenthesis\")\n\n        return (parseNestedParens(line[1:i],0), line[i+2:])\n\n\n    def arg_literal(self, line):\n        \"\"\"\n        Parse a literal from the line\n        \"\"\"\n        if not line:\n            raise IllegalClientResponse(\"Missing argument\")\n\n        if line[:1] != b'{':\n            raise IllegalClientResponse(\"Missing literal\")\n\n        if line[-1:] != b'}':\n            raise IllegalClientResponse(\"Malformed literal\")\n\n        try:\n            size = int(line[1:-1])\n        except ValueError:\n            raise IllegalClientResponse(\n                \"Bad literal size: {!r}\".format(line[1:-1]))\n\n        return self._fileLiteral(size)\n\n\n    def arg_searchkeys(self, line):\n        \"\"\"\n        searchkeys\n        \"\"\"\n        query = parseNestedParens(line)\n        # XXX Should really use list of search terms and parse into\n        # a proper tree\n        return (query, b'')\n\n\n    def arg_seqset(self, line):\n        \"\"\"\n        sequence-set\n        \"\"\"\n        rest = b''\n        arg = line.split(b' ',1)\n        if len(arg) == 2:\n            rest = arg[1]\n        arg = arg[0]\n\n        try:\n            return (parseIdList(arg), rest)\n        except IllegalIdentifierError as e:\n            raise IllegalClientResponse(\"Bad message number \" + str(e))\n\n\n    def arg_fetchatt(self, line):\n        \"\"\"\n        fetch-att\n        \"\"\"\n        p = _FetchParser()\n        p.parseString(line)\n        return (p.result, b'')\n\n\n    def arg_flaglist(self, line):\n        \"\"\"\n        Flag part of store-att-flag\n        \"\"\"\n        flags = []\n        if line[0:1] == b'(':\n            if line[-1:] != b')':\n                raise IllegalClientResponse(\"Mismatched parenthesis\")\n            line = line[1:-1]\n\n        while line:\n            m = self.atomre.search(line)\n            if not m:\n                raise IllegalClientResponse(\"Malformed flag\")\n            if line[0:1] == b'\\\\' and m.start() == 1:\n                flags.append(b'\\\\' + m.group('atom'))\n            elif m.start() == 0:\n                flags.append(m.group('atom'))\n            else:\n                raise IllegalClientResponse(\"Malformed flag\")\n            line = m.group('rest')\n\n        return (flags, b'')\n\n\n    def arg_line(self, line):\n        \"\"\"\n        Command line of UID command\n        \"\"\"\n        return (line, b'')\n\n\n    def opt_plist(self, line):\n        \"\"\"\n        Optional parenthesised list\n        \"\"\"\n        if line.startswith(b'('):\n            return self.arg_plist(line)\n        else:\n            return (None, line)\n\n\n    def opt_datetime(self, line):\n        \"\"\"\n        Optional date-time string\n        \"\"\"\n        if line.startswith(b'\"'):\n            try:\n                spam, date, rest = line.split(b'\"',2)\n            except ValueError:\n                raise IllegalClientResponse(\"Malformed date-time\")\n            return (date, rest[1:])\n        else:\n            return (None, line)\n\n\n    def opt_charset(self, line):\n        \"\"\"\n        Optional charset of SEARCH command\n        \"\"\"\n        if line[:7].upper() == b'CHARSET':\n            arg = line.split(b' ',2)\n            if len(arg) == 1:\n                raise IllegalClientResponse(\"Missing charset identifier\")\n            if len(arg) == 2:\n                arg.append(b'')\n            spam, arg, rest = arg\n            return (arg, rest)\n        else:\n            return (None, line)\n\n\n    def sendServerGreeting(self):\n        msg = (b'[CAPABILITY ' + b' '.join(self.listCapabilities()) + b'] ' +\n              self.IDENT)\n        self.sendPositiveResponse(message=msg)\n\n\n    def sendBadResponse(self, tag = None, message = b''):\n        self._respond(b'BAD', tag, message)\n\n\n    def sendPositiveResponse(self, tag = None, message = b''):\n        self._respond(b'OK', tag, message)\n\n\n    def sendNegativeResponse(self, tag = None, message = b''):\n        self._respond(b'NO', tag, message)\n\n\n    def sendUntaggedResponse(self, message, isAsync=None, **kwargs):\n        isAsync = _get_async_param(isAsync, **kwargs)\n        if not isAsync or (self.blocked is None):\n            self._respond(message, None, None)\n        else:\n            self._queuedAsync.append(message)\n\n\n    def sendContinuationRequest(self, msg = b'Ready for additional command text'):\n        if msg:\n            self.sendLine(b'+ ' + msg)\n        else:\n            self.sendLine(b'+')\n\n\n    def _respond(self, state, tag, message):\n        if state in (b'OK', b'NO', b'BAD') and self._queuedAsync:\n            lines = self._queuedAsync\n            self._queuedAsync = []\n            for msg in lines:\n                self._respond(msg, None, None)\n        if not tag:\n            tag = b'*'\n        if message:\n            self.sendLine(b' '.join((tag, state, message)))\n        else:\n            self.sendLine(b' '.join((tag, state)))\n\n\n    def listCapabilities(self):\n        caps = [b'IMAP4rev1']\n        for c, v in self.capabilities().items():\n            if v is None:\n                caps.append(c)\n            elif len(v):\n                caps.extend([(c + b'=' + cap) for cap in v])\n        return caps\n\n\n    def do_CAPABILITY(self, tag):\n        self.sendUntaggedResponse(b'CAPABILITY ' + b' '.join(self.listCapabilities()))\n        self.sendPositiveResponse(tag, b'CAPABILITY completed')\n\n    unauth_CAPABILITY = (do_CAPABILITY,)\n    auth_CAPABILITY = unauth_CAPABILITY\n    select_CAPABILITY = unauth_CAPABILITY\n    logout_CAPABILITY = unauth_CAPABILITY\n\n\n    def do_LOGOUT(self, tag):\n        self.sendUntaggedResponse(b'BYE Nice talking to you')\n        self.sendPositiveResponse(tag, b'LOGOUT successful')\n        self.transport.loseConnection()\n\n    unauth_LOGOUT = (do_LOGOUT,)\n    auth_LOGOUT = unauth_LOGOUT\n    select_LOGOUT = unauth_LOGOUT\n    logout_LOGOUT = unauth_LOGOUT\n\n\n    def do_NOOP(self, tag):\n        self.sendPositiveResponse(tag, b'NOOP No operation performed')\n\n    unauth_NOOP = (do_NOOP,)\n    auth_NOOP = unauth_NOOP\n    select_NOOP = unauth_NOOP\n    logout_NOOP = unauth_NOOP\n\n\n    def do_AUTHENTICATE(self, tag, args):\n        args = args.upper().strip()\n        if args not in self.challengers:\n            self.sendNegativeResponse(tag, b'AUTHENTICATE method unsupported')\n        else:\n            self.authenticate(self.challengers[args](), tag)\n\n    unauth_AUTHENTICATE = (do_AUTHENTICATE, arg_atom)\n\n\n    def authenticate(self, chal, tag):\n        if self.portal is None:\n            self.sendNegativeResponse(tag, b'Temporary authentication failure')\n            return\n\n        self._setupChallenge(chal, tag)\n\n\n    def _setupChallenge(self, chal, tag):\n        try:\n            challenge = chal.getChallenge()\n        except Exception as e:\n            self.sendBadResponse(tag, b'Server error: ' + networkString(str(e)))\n        else:\n            coded = encodebytes(challenge)[:-1]\n            self.parseState = 'pending'\n            self._pendingLiteral = defer.Deferred()\n            self.sendContinuationRequest(coded)\n            self._pendingLiteral.addCallback(self.__cbAuthChunk, chal, tag)\n            self._pendingLiteral.addErrback(self.__ebAuthChunk, tag)\n\n\n    def __cbAuthChunk(self, result, chal, tag):\n        try:\n            uncoded = decodebytes(result)\n        except binascii.Error:\n            raise IllegalClientResponse(\"Malformed Response - not base64\")\n\n        chal.setResponse(uncoded)\n        if chal.moreChallenges():\n            self._setupChallenge(chal, tag)\n        else:\n            self.portal.login(chal, None, IAccount).addCallbacks(\n                self.__cbAuthResp,\n                self.__ebAuthResp,\n                (tag,), None, (tag,), None\n            )\n\n\n    def __cbAuthResp(self, result, tag):\n        (iface, avatar, logout) = result\n        assert iface is IAccount, \"IAccount is the only supported interface\"\n        self.account = avatar\n        self.state = 'auth'\n        self._onLogout = logout\n        self.sendPositiveResponse(tag, b'Authentication successful')\n        self.setTimeout(self.POSTAUTH_TIMEOUT)\n\n\n    def __ebAuthResp(self, failure, tag):\n        if failure.check(UnauthorizedLogin):\n            self.sendNegativeResponse(tag, b'Authentication failed: unauthorized')\n        elif failure.check(UnhandledCredentials):\n            self.sendNegativeResponse(tag, b'Authentication failed: server misconfigured')\n        else:\n            self.sendBadResponse(tag, b'Server error: login failed unexpectedly')\n            log.err(failure)\n\n\n    def __ebAuthChunk(self, failure, tag):\n        self.sendNegativeResponse(tag, b'Authentication failed: ' + networkString(str(failure.value)))\n\n\n    def do_STARTTLS(self, tag):\n        if self.startedTLS:\n            self.sendNegativeResponse(tag, b'TLS already negotiated')\n        elif self.ctx and self.canStartTLS:\n            self.sendPositiveResponse(tag, b'Begin TLS negotiation now')\n            self.transport.startTLS(self.ctx)\n            self.startedTLS = True\n            self.challengers = self.challengers.copy()\n            if b'LOGIN' not in self.challengers:\n                self.challengers[b'LOGIN'] = LOGINCredentials\n            if b'PLAIN' not in self.challengers:\n                self.challengers[b'PLAIN'] = PLAINCredentials\n        else:\n            self.sendNegativeResponse(tag, b'TLS not available')\n\n    unauth_STARTTLS = (do_STARTTLS,)\n\n\n    def do_LOGIN(self, tag, user, passwd):\n        if b'LOGINDISABLED' in self.capabilities():\n            self.sendBadResponse(tag, b'LOGIN is disabled before STARTTLS')\n            return\n\n        maybeDeferred(self.authenticateLogin, user, passwd\n            ).addCallback(self.__cbLogin, tag\n            ).addErrback(self.__ebLogin, tag\n            )\n\n    unauth_LOGIN = (do_LOGIN, arg_astring, arg_finalastring)\n\n\n    def authenticateLogin(self, user, passwd):\n        \"\"\"\n        Lookup the account associated with the given parameters\n\n        Override this method to define the desired authentication behavior.\n\n        The default behavior is to defer authentication to C{self.portal}\n        if it is not None, or to deny the login otherwise.\n\n        @type user: L{str}\n        @param user: The username to lookup\n\n        @type passwd: L{str}\n        @param passwd: The password to login with\n        \"\"\"\n        if self.portal:\n            return self.portal.login(\n                credentials.UsernamePassword(user, passwd),\n                None, IAccount\n            )\n        raise UnauthorizedLogin()\n\n\n    def __cbLogin(self, result, tag):\n        (iface, avatar, logout) = result\n        if iface is not IAccount:\n            self.sendBadResponse(tag, b'Server error: login returned unexpected value')\n            log.err(\"__cbLogin called with %r, IAccount expected\" % (iface,))\n        else:\n            self.account = avatar\n            self._onLogout = logout\n            self.sendPositiveResponse(tag, b'LOGIN succeeded')\n            self.state = 'auth'\n            self.setTimeout(self.POSTAUTH_TIMEOUT)\n\n\n    def __ebLogin(self, failure, tag):\n        if failure.check(UnauthorizedLogin):\n            self.sendNegativeResponse(tag, b'LOGIN failed')\n        else:\n            self.sendBadResponse(tag, b'Server error: ' + networkString(str(failure.value)))\n            log.err(failure)\n\n\n    def do_NAMESPACE(self, tag):\n        personal = public = shared = None\n        np = INamespacePresenter(self.account, None)\n        if np is not None:\n            personal = np.getPersonalNamespaces()\n            public = np.getSharedNamespaces()\n            shared = np.getSharedNamespaces()\n        self.sendUntaggedResponse(b'NAMESPACE ' + collapseNestedLists([personal, public, shared]))\n        self.sendPositiveResponse(tag, b\"NAMESPACE command completed\")\n\n    auth_NAMESPACE = (do_NAMESPACE,)\n    select_NAMESPACE = auth_NAMESPACE\n\n\n    def _selectWork(self, tag, name, rw, cmdName):\n        if self.mbox:\n            self.mbox.removeListener(self)\n            cmbx = ICloseableMailbox(self.mbox, None)\n            if cmbx is not None:\n                maybeDeferred(cmbx.close).addErrback(log.err)\n            self.mbox = None\n            self.state = 'auth'\n\n        name = _parseMbox(name)\n        maybeDeferred(self.account.select, _parseMbox(name), rw\n            ).addCallback(self._cbSelectWork, cmdName, tag\n            ).addErrback(self._ebSelectWork, cmdName, tag\n            )\n\n\n    def _ebSelectWork(self, failure, cmdName, tag):\n        self.sendBadResponse(tag, cmdName + b\" failed: Server error\")\n        log.err(failure)\n\n\n    def _cbSelectWork(self, mbox, cmdName, tag):\n        if mbox is None:\n            self.sendNegativeResponse(tag, b'No such mailbox')\n            return\n        if '\\\\noselect' in [s.lower() for s in mbox.getFlags()]:\n            self.sendNegativeResponse(tag, 'Mailbox cannot be selected')\n            return\n\n        flags = [networkString(flag) for flag in mbox.getFlags()]\n        self.sendUntaggedResponse(intToBytes(mbox.getMessageCount()) + b' EXISTS')\n        self.sendUntaggedResponse(intToBytes(mbox.getRecentCount()) + b' RECENT')\n        self.sendUntaggedResponse(b'FLAGS (' + b' '.join(flags) + b')')\n        self.sendPositiveResponse(None, b'[UIDVALIDITY ' + intToBytes(mbox.getUIDValidity()) + b']')\n\n        s = mbox.isWriteable() and b'READ-WRITE' or b'READ-ONLY'\n        mbox.addListener(self)\n        self.sendPositiveResponse(tag, b'[' + s + b'] ' + cmdName + b' successful')\n        self.state = 'select'\n        self.mbox = mbox\n\n    auth_SELECT = ( _selectWork, arg_astring, 1, b'SELECT' )\n    select_SELECT = auth_SELECT\n\n    auth_EXAMINE = ( _selectWork, arg_astring, 0, b'EXAMINE' )\n    select_EXAMINE = auth_EXAMINE\n\n\n    def do_IDLE(self, tag):\n        self.sendContinuationRequest(None)\n        self.parseTag = tag\n        self.lastState = self.parseState\n        self.parseState = 'idle'\n\n\n    def parse_idle(self, *args):\n        self.parseState = self.lastState\n        del self.lastState\n        self.sendPositiveResponse(self.parseTag, b\"IDLE terminated\")\n        del self.parseTag\n\n    select_IDLE = ( do_IDLE, )\n    auth_IDLE = select_IDLE\n\n\n    def do_CREATE(self, tag, name):\n        name = _parseMbox(name)\n        try:\n            result = self.account.create(name)\n        except MailboxException as c:\n            self.sendNegativeResponse(tag, networkString(str(c)))\n        except:\n            self.sendBadResponse(tag, b\"Server error encountered while creating mailbox\")\n            log.err()\n        else:\n            if result:\n                self.sendPositiveResponse(tag, b'Mailbox created')\n            else:\n                self.sendNegativeResponse(tag, b'Mailbox not created')\n\n    auth_CREATE = (do_CREATE, arg_finalastring)\n    select_CREATE = auth_CREATE\n\n\n    def do_DELETE(self, tag, name):\n        name = _parseMbox(name)\n        if name.lower() == 'inbox':\n            self.sendNegativeResponse(tag, b'You cannot delete the inbox')\n            return\n        try:\n            self.account.delete(name)\n        except MailboxException as m:\n            self.sendNegativeResponse(tag, str(m).encode(\"imap4-utf-7\"))\n        except:\n            self.sendBadResponse(tag, b\"Server error encountered while deleting mailbox\")\n            log.err()\n        else:\n            self.sendPositiveResponse(tag, b'Mailbox deleted')\n\n    auth_DELETE = (do_DELETE, arg_finalastring)\n    select_DELETE = auth_DELETE\n\n\n    def do_RENAME(self, tag, oldname, newname):\n        oldname, newname = [_parseMbox(n) for n in (oldname, newname)]\n        if oldname.lower() == 'inbox' or newname.lower() == 'inbox':\n            self.sendNegativeResponse(tag, b'You cannot rename the inbox, or rename another mailbox to inbox.')\n            return\n        try:\n            self.account.rename(oldname, newname)\n        except TypeError:\n            self.sendBadResponse(tag, b'Invalid command syntax')\n        except MailboxException as m:\n            self.sendNegativeResponse(tag, networkString(str(m)))\n        except:\n            self.sendBadResponse(tag, b\"Server error encountered while renaming mailbox\")\n            log.err()\n        else:\n            self.sendPositiveResponse(tag, b'Mailbox renamed')\n\n    auth_RENAME = (do_RENAME, arg_astring, arg_finalastring)\n    select_RENAME = auth_RENAME\n\n\n    def do_SUBSCRIBE(self, tag, name):\n        name = _parseMbox(name)\n        try:\n            self.account.subscribe(name)\n        except MailboxException as m:\n            self.sendNegativeResponse(tag, networkString(str(m)))\n        except:\n            self.sendBadResponse(tag, b\"Server error encountered while subscribing to mailbox\")\n            log.err()\n        else:\n            self.sendPositiveResponse(tag, b'Subscribed')\n\n    auth_SUBSCRIBE = (do_SUBSCRIBE, arg_finalastring)\n    select_SUBSCRIBE = auth_SUBSCRIBE\n\n\n    def do_UNSUBSCRIBE(self, tag, name):\n        name = _parseMbox(name)\n        try:\n            self.account.unsubscribe(name)\n        except MailboxException as m:\n            self.sendNegativeResponse(tag, networkString(str(m)))\n        except:\n            self.sendBadResponse(tag, b\"Server error encountered while unsubscribing from mailbox\")\n            log.err()\n        else:\n            self.sendPositiveResponse(tag, b'Unsubscribed')\n\n    auth_UNSUBSCRIBE = (do_UNSUBSCRIBE, arg_finalastring)\n    select_UNSUBSCRIBE = auth_UNSUBSCRIBE\n\n\n    def _listWork(self, tag, ref, mbox, sub, cmdName):\n        mbox = _parseMbox(mbox)\n        ref = _parseMbox(ref)\n        maybeDeferred(self.account.listMailboxes, ref, mbox\n            ).addCallback(self._cbListWork, tag, sub, cmdName\n            ).addErrback(self._ebListWork, tag\n            )\n\n\n    def _cbListWork(self, mailboxes, tag, sub, cmdName):\n        for (name, box) in mailboxes:\n            if not sub or self.account.isSubscribed(name):\n                flags = [networkString(flag) for flag in box.getFlags()]\n                delim = box.getHierarchicalDelimiter().encode('imap4-utf-7')\n                resp = (DontQuoteMe(cmdName), map(DontQuoteMe, flags), delim, name.encode('imap4-utf-7'))\n                self.sendUntaggedResponse(collapseNestedLists(resp))\n        self.sendPositiveResponse(tag, cmdName + b' completed')\n\n\n    def _ebListWork(self, failure, tag):\n        self.sendBadResponse(tag, b\"Server error encountered while listing mailboxes.\")\n        log.err(failure)\n\n    auth_LIST = (_listWork, arg_astring, arg_astring, 0, b'LIST')\n    select_LIST = auth_LIST\n\n    auth_LSUB = (_listWork, arg_astring, arg_astring, 1, b'LSUB')\n    select_LSUB = auth_LSUB\n\n\n    def do_STATUS(self, tag, mailbox, names):\n        nativeNames = []\n        for name in names:\n            nativeNames.append(nativeString(name))\n\n        mailbox = _parseMbox(mailbox)\n\n        maybeDeferred(self.account.select, mailbox, 0\n            ).addCallback(self._cbStatusGotMailbox, tag, mailbox, nativeNames\n            ).addErrback(self._ebStatusGotMailbox, tag\n            )\n\n\n    def _cbStatusGotMailbox(self, mbox, tag, mailbox, names):\n        if mbox:\n            maybeDeferred(mbox.requestStatus, names).addCallbacks(\n                self.__cbStatus, self.__ebStatus,\n                (tag, mailbox), None, (tag, mailbox), None\n            )\n        else:\n            self.sendNegativeResponse(tag, b\"Could not open mailbox\")\n\n\n    def _ebStatusGotMailbox(self, failure, tag):\n        self.sendBadResponse(tag, b\"Server error encountered while opening mailbox.\")\n        log.err(failure)\n\n    auth_STATUS = (do_STATUS, arg_astring, arg_plist)\n    select_STATUS = auth_STATUS\n\n\n    def __cbStatus(self, status, tag, box):\n        # STATUS names should only be ASCII\n        line = networkString(' '.join(['%s %s' % x for x in status.items()]))\n        self.sendUntaggedResponse(b'STATUS ' + box.encode('imap4-utf-7') + b' ('+ line + b')')\n        self.sendPositiveResponse(tag, b'STATUS complete')\n\n\n    def __ebStatus(self, failure, tag, box):\n        self.sendBadResponse(tag, b'STATUS '+ box + b' failed: ' +\n                             networkString(str(failure.value)))\n\n\n    def do_APPEND(self, tag, mailbox, flags, date, message):\n        mailbox = _parseMbox(mailbox)\n        maybeDeferred(self.account.select, mailbox\n            ).addCallback(self._cbAppendGotMailbox, tag, flags, date, message\n            ).addErrback(self._ebAppendGotMailbox, tag\n            )\n\n\n    def _cbAppendGotMailbox(self, mbox, tag, flags, date, message):\n        if not mbox:\n            self.sendNegativeResponse(tag, '[TRYCREATE] No such mailbox')\n            return\n\n        decodedFlags = [nativeString(flag) for flag in flags]\n        d = mbox.addMessage(message, decodedFlags, date)\n        d.addCallback(self.__cbAppend, tag, mbox)\n        d.addErrback(self.__ebAppend, tag)\n\n\n    def _ebAppendGotMailbox(self, failure, tag):\n        self.sendBadResponse(tag, b\"Server error encountered while opening mailbox.\")\n        log.err(failure)\n\n    auth_APPEND = (do_APPEND, arg_astring, opt_plist, opt_datetime,\n                   arg_literal)\n    select_APPEND = auth_APPEND\n\n\n    def __cbAppend(self, result, tag, mbox):\n        self.sendUntaggedResponse(intToBytes(mbox.getMessageCount()) + b' EXISTS')\n        self.sendPositiveResponse(tag, b'APPEND complete')\n\n\n    def __ebAppend(self, failure, tag):\n        self.sendBadResponse(tag, b'APPEND failed: ' +\n                             networkString(str(failure.value)))\n\n\n    def do_CHECK(self, tag):\n        d = self.checkpoint()\n        if d is None:\n            self.__cbCheck(None, tag)\n        else:\n            d.addCallbacks(\n                self.__cbCheck,\n                self.__ebCheck,\n                callbackArgs=(tag,),\n                errbackArgs=(tag,)\n            )\n    select_CHECK = (do_CHECK,)\n\n\n    def __cbCheck(self, result, tag):\n        self.sendPositiveResponse(tag, b'CHECK completed')\n\n\n    def __ebCheck(self, failure, tag):\n        self.sendBadResponse(tag, b'CHECK failed: ' +\n                             networkString(str(failure.value)))\n\n\n    def checkpoint(self):\n        \"\"\"\n        Called when the client issues a CHECK command.\n\n        This should perform any checkpoint operations required by the server.\n        It may be a long running operation, but may not block.  If it returns\n        a deferred, the client will only be informed of success (or failure)\n        when the deferred's callback (or errback) is invoked.\n        \"\"\"\n        return None\n\n\n    def do_CLOSE(self, tag):\n        d = None\n        if self.mbox.isWriteable():\n            d = maybeDeferred(self.mbox.expunge)\n        cmbx = ICloseableMailbox(self.mbox, None)\n        if cmbx is not None:\n            if d is not None:\n                d.addCallback(lambda result: cmbx.close())\n            else:\n                d = maybeDeferred(cmbx.close)\n        if d is not None:\n            d.addCallbacks(self.__cbClose, self.__ebClose, (tag,), None, (tag,), None)\n        else:\n            self.__cbClose(None, tag)\n\n    select_CLOSE = (do_CLOSE,)\n\n\n    def __cbClose(self, result, tag):\n        self.sendPositiveResponse(tag, b'CLOSE completed')\n        self.mbox.removeListener(self)\n        self.mbox = None\n        self.state = 'auth'\n\n\n    def __ebClose(self, failure, tag):\n        self.sendBadResponse(tag, b'CLOSE failed: ' +\n                             networkString(str(failure.value)))\n\n\n    def do_EXPUNGE(self, tag):\n        if self.mbox.isWriteable():\n            maybeDeferred(self.mbox.expunge).addCallbacks(\n                self.__cbExpunge, self.__ebExpunge, (tag,), None, (tag,), None\n            )\n        else:\n            self.sendNegativeResponse(tag, b'EXPUNGE ignored on read-only mailbox')\n\n    select_EXPUNGE = (do_EXPUNGE,)\n\n\n    def __cbExpunge(self, result, tag):\n        for e in result:\n            self.sendUntaggedResponse(intToBytes(e) + b' EXPUNGE')\n        self.sendPositiveResponse(tag, b'EXPUNGE completed')\n\n\n    def __ebExpunge(self, failure, tag):\n        self.sendBadResponse(tag, b'EXPUNGE failed: ' +\n                             networkString(str(failure.value)))\n        log.err(failure)\n\n\n    def do_SEARCH(self, tag, charset, query, uid=0):\n        sm = ISearchableMailbox(self.mbox, None)\n        if sm is not None:\n            maybeDeferred(sm.search, query, uid=uid\n                          ).addCallback(self.__cbSearch, tag, self.mbox, uid\n                          ).addErrback(self.__ebSearch, tag)\n        else:\n            # that's not the ideal way to get all messages, there should be a\n            # method on mailboxes that gives you all of them\n            s = parseIdList(b'1:*')\n            maybeDeferred(self.mbox.fetch, s, uid=uid\n                          ).addCallback(self.__cbManualSearch,\n                                        tag, self.mbox, query, uid\n                          ).addErrback(self.__ebSearch, tag)\n\n    select_SEARCH = (do_SEARCH, opt_charset, arg_searchkeys)\n\n\n    def __cbSearch(self, result, tag, mbox, uid):\n        if uid:\n            result = map(mbox.getUID, result)\n        ids = networkString(' '.join([str(i) for i in result]))\n        self.sendUntaggedResponse(b'SEARCH ' + ids)\n        self.sendPositiveResponse(tag, b'SEARCH completed')\n\n\n    def __cbManualSearch(self, result, tag, mbox, query, uid,\n                         searchResults=None):\n        \"\"\"\n        Apply the search filter to a set of messages. Send the response to the\n        client.\n\n        @type result: L{list} of L{tuple} of (L{int}, provider of\n            L{imap4.IMessage})\n        @param result: A list two tuples of messages with their sequence ids,\n            sorted by the ids in descending order.\n\n        @type tag: L{str}\n        @param tag: A command tag.\n\n        @type mbox: Provider of L{imap4.IMailbox}\n        @param mbox: The searched mailbox.\n\n        @type query: L{list}\n        @param query: A list representing the parsed form of the search query.\n\n        @param uid: A flag indicating whether the search is over message\n            sequence numbers or UIDs.\n\n        @type searchResults: L{list}\n        @param searchResults: The search results so far or L{None} if no\n            results yet.\n        \"\"\"\n        if searchResults is None:\n            searchResults = []\n        i = 0\n\n        # result is a list of tuples (sequenceId, Message)\n        lastSequenceId = result and result[-1][0]\n        lastMessageId = result and result[-1][1].getUID()\n        for (i, (msgId, msg)) in list(zip(range(5), result)):\n            # searchFilter and singleSearchStep will mutate the query.  Dang.\n            # Copy it here or else things will go poorly for subsequent\n            # messages.\n            if self._searchFilter(copy.deepcopy(query), msgId, msg,\n                                  lastSequenceId, lastMessageId):\n                if uid:\n                    searchResults.append(intToBytes(msg.getUID()))\n                else:\n                    searchResults.append(intToBytes(msgId))\n\n        if i == 4:\n            from twisted.internet import reactor\n            reactor.callLater(\n                0, self.__cbManualSearch, list(result[5:]), tag, mbox, query, uid,\n                searchResults)\n        else:\n            if searchResults:\n                self.sendUntaggedResponse(b'SEARCH ' + b' '.join(searchResults))\n            self.sendPositiveResponse(tag, b'SEARCH completed')\n\n\n    def _searchFilter(self, query, id, msg, lastSequenceId, lastMessageId):\n        \"\"\"\n        Pop search terms from the beginning of C{query} until there are none\n        left and apply them to the given message.\n\n        @param query: A list representing the parsed form of the search query.\n\n        @param id: The sequence number of the message being checked.\n\n        @param msg: The message being checked.\n\n        @type lastSequenceId: L{int}\n        @param lastSequenceId: The highest sequence number of any message in\n            the mailbox being searched.\n\n        @type lastMessageId: L{int}\n        @param lastMessageId: The highest UID of any message in the mailbox\n            being searched.\n\n        @return: Boolean indicating whether all of the query terms match the\n            message.\n        \"\"\"\n        while query:\n            if not self._singleSearchStep(query, id, msg,\n                                          lastSequenceId, lastMessageId):\n                return False\n        return True\n\n\n    def _singleSearchStep(self, query, msgId, msg, lastSequenceId, lastMessageId):\n        \"\"\"\n        Pop one search term from the beginning of C{query} (possibly more than\n        one element) and return whether it matches the given message.\n\n        @param query: A list representing the parsed form of the search query.\n\n        @param msgId: The sequence number of the message being checked.\n\n        @param msg: The message being checked.\n\n        @param lastSequenceId: The highest sequence number of any message in\n            the mailbox being searched.\n\n        @param lastMessageId: The highest UID of any message in the mailbox\n            being searched.\n\n        @return: Boolean indicating whether the query term matched the message.\n        \"\"\"\n\n        q = query.pop(0)\n        if isinstance(q, list):\n            if not self._searchFilter(q, msgId, msg,\n                                      lastSequenceId, lastMessageId):\n                return False\n        else:\n            c = q.upper()\n            if not c[:1].isalpha():\n                # A search term may be a word like ALL, ANSWERED, BCC, etc (see\n                # below) or it may be a message sequence set.  Here we\n                # recognize a message sequence set \"N:M\".\n                messageSet = parseIdList(c, lastSequenceId)\n                return msgId in messageSet\n            else:\n                f = getattr(self, 'search_' + nativeString(c), None)\n                if f is None:\n                    raise IllegalQueryError(\"Invalid search command %s\" % nativeString(c))\n\n                if c in self._requiresLastMessageInfo:\n                    result = f(query, msgId, msg, (lastSequenceId,\n                                                   lastMessageId))\n                else:\n                    result = f(query, msgId, msg)\n\n                if not result:\n                    return False\n        return True\n\n\n    def search_ALL(self, query, id, msg):\n        \"\"\"\n        Returns C{True} if the message matches the ALL search key (always).\n\n        @type query: A L{list} of L{str}\n        @param query: A list representing the parsed query string.\n\n        @type id: L{int}\n        @param id: The sequence number of the message being checked.\n\n        @type msg: Provider of L{imap4.IMessage}\n        \"\"\"\n        return True\n\n\n    def search_ANSWERED(self, query, id, msg):\n        \"\"\"\n        Returns C{True} if the message has been answered.\n\n        @type query: A L{list} of L{str}\n        @param query: A list representing the parsed query string.\n\n        @type id: L{int}\n        @param id: The sequence number of the message being checked.\n\n        @type msg: Provider of L{imap4.IMessage}\n        \"\"\"\n        return '\\\\Answered' in msg.getFlags()\n\n\n    def search_BCC(self, query, id, msg):\n        \"\"\"\n        Returns C{True} if the message has a BCC address matching the query.\n\n        @type query: A L{list} of L{str}\n        @param query: A list whose first element is a BCC L{str}\n\n        @type id: L{int}\n        @param id: The sequence number of the message being checked.\n\n        @type msg: Provider of L{imap4.IMessage}\n        \"\"\"\n        bcc = msg.getHeaders(False, 'bcc').get('bcc', '')\n        return bcc.lower().find(query.pop(0).lower()) != -1\n\n\n    def search_BEFORE(self, query, id, msg):\n        date = parseTime(query.pop(0))\n        return email.utils.parsedate(nativeString(msg.getInternalDate())) < date\n\n\n    def search_BODY(self, query, id, msg):\n        body = query.pop(0).lower()\n        return text.strFile(body, msg.getBodyFile(), False)\n\n\n    def search_CC(self, query, id, msg):\n        cc = msg.getHeaders(False, 'cc').get('cc', '')\n        return cc.lower().find(query.pop(0).lower()) != -1\n\n\n    def search_DELETED(self, query, id, msg):\n        return '\\\\Deleted' in msg.getFlags()\n\n\n    def search_DRAFT(self, query, id, msg):\n        return '\\\\Draft' in msg.getFlags()\n\n\n    def search_FLAGGED(self, query, id, msg):\n        return '\\\\Flagged' in msg.getFlags()\n\n\n    def search_FROM(self, query, id, msg):\n        fm = msg.getHeaders(False, 'from').get('from', '')\n        return fm.lower().find(query.pop(0).lower()) != -1\n\n\n    def search_HEADER(self, query, id, msg):\n        hdr = query.pop(0).lower()\n        hdr = msg.getHeaders(False, hdr).get(hdr, '')\n        return hdr.lower().find(query.pop(0).lower()) != -1\n\n\n    def search_KEYWORD(self, query, id, msg):\n        query.pop(0)\n        return False\n\n\n    def search_LARGER(self, query, id, msg):\n        return int(query.pop(0)) < msg.getSize()\n\n\n    def search_NEW(self, query, id, msg):\n        return '\\\\Recent' in msg.getFlags() and '\\\\Seen' not in msg.getFlags()\n\n\n    def search_NOT(self, query, id, msg, lastIDs):\n        \"\"\"\n        Returns C{True} if the message does not match the query.\n\n        @type query: A L{list} of L{str}\n        @param query: A list representing the parsed form of the search query.\n\n        @type id: L{int}\n        @param id: The sequence number of the message being checked.\n\n        @type msg: Provider of L{imap4.IMessage}\n        @param msg: The message being checked.\n\n        @type lastIDs: L{tuple}\n        @param lastIDs: A tuple of (last sequence id, last message id).\n        The I{last sequence id} is an L{int} containing the highest sequence\n        number of a message in the mailbox.  The I{last message id} is an\n        L{int} containing the highest UID of a message in the mailbox.\n        \"\"\"\n        (lastSequenceId, lastMessageId) = lastIDs\n        return not self._singleSearchStep(query, id, msg,\n                                          lastSequenceId, lastMessageId)\n\n\n    def search_OLD(self, query, id, msg):\n        return '\\\\Recent' not in msg.getFlags()\n\n\n    def search_ON(self, query, id, msg):\n        date = parseTime(query.pop(0))\n        return email.utils.parsedate(msg.getInternalDate()) == date\n\n\n    def search_OR(self, query, id, msg, lastIDs):\n        \"\"\"\n        Returns C{True} if the message matches any of the first two query\n        items.\n\n        @type query: A L{list} of L{str}\n        @param query: A list representing the parsed form of the search query.\n\n        @type id: L{int}\n        @param id: The sequence number of the message being checked.\n\n        @type msg: Provider of L{imap4.IMessage}\n        @param msg: The message being checked.\n\n        @type lastIDs: L{tuple}\n        @param lastIDs: A tuple of (last sequence id, last message id).\n        The I{last sequence id} is an L{int} containing the highest sequence\n        number of a message in the mailbox.  The I{last message id} is an\n        L{int} containing the highest UID of a message in the mailbox.\n        \"\"\"\n        (lastSequenceId, lastMessageId) = lastIDs\n        a = self._singleSearchStep(query, id, msg,\n                                   lastSequenceId, lastMessageId)\n        b = self._singleSearchStep(query, id, msg,\n                                   lastSequenceId, lastMessageId)\n        return a or b\n\n\n    def search_RECENT(self, query, id, msg):\n        return '\\\\Recent' in msg.getFlags()\n\n\n    def search_SEEN(self, query, id, msg):\n        return '\\\\Seen' in msg.getFlags()\n\n\n    def search_SENTBEFORE(self, query, id, msg):\n        \"\"\"\n        Returns C{True} if the message date is earlier than the query date.\n\n        @type query: A L{list} of L{str}\n        @param query: A list whose first element starts with a stringified date\n            that is a fragment of an L{imap4.Query()}. The date must be in the\n            format 'DD-Mon-YYYY', for example '03-March-2003' or '03-Mar-2003'.\n\n        @type id: L{int}\n        @param id: The sequence number of the message being checked.\n\n        @type msg: Provider of L{imap4.IMessage}\n        \"\"\"\n        date = msg.getHeaders(False, 'date').get('date', '')\n        date = email.utils.parsedate(date)\n        return date < parseTime(query.pop(0))\n\n\n    def search_SENTON(self, query, id, msg):\n        \"\"\"\n        Returns C{True} if the message date is the same as the query date.\n\n        @type query: A L{list} of L{str}\n        @param query: A list whose first element starts with a stringified date\n            that is a fragment of an L{imap4.Query()}. The date must be in the\n            format 'DD-Mon-YYYY', for example '03-March-2003' or '03-Mar-2003'.\n\n        @type msg: Provider of L{imap4.IMessage}\n        \"\"\"\n        date = msg.getHeaders(False, 'date').get('date', '')\n        date = email.utils.parsedate(date)\n        return date[:3] == parseTime(query.pop(0))[:3]\n\n\n    def search_SENTSINCE(self, query, id, msg):\n        \"\"\"\n        Returns C{True} if the message date is later than the query date.\n\n        @type query: A L{list} of L{str}\n        @param query: A list whose first element starts with a stringified date\n            that is a fragment of an L{imap4.Query()}. The date must be in the\n            format 'DD-Mon-YYYY', for example '03-March-2003' or '03-Mar-2003'.\n\n        @type msg: Provider of L{imap4.IMessage}\n        \"\"\"\n        date = msg.getHeaders(False, 'date').get('date', '')\n        date = email.utils.parsedate(date)\n        return date > parseTime(query.pop(0))\n\n\n    def search_SINCE(self, query, id, msg):\n        date = parseTime(query.pop(0))\n        return email.utils.parsedate(msg.getInternalDate()) > date\n\n\n    def search_SMALLER(self, query, id, msg):\n        return int(query.pop(0)) > msg.getSize()\n\n\n    def search_SUBJECT(self, query, id, msg):\n        subj = msg.getHeaders(False, 'subject').get('subject', '')\n        return subj.lower().find(query.pop(0).lower()) != -1\n\n\n    def search_TEXT(self, query, id, msg):\n        # XXX - This must search headers too\n        body = query.pop(0).lower()\n        return text.strFile(body, msg.getBodyFile(), False)\n\n\n    def search_TO(self, query, id, msg):\n        to = msg.getHeaders(False, 'to').get('to', '')\n        return to.lower().find(query.pop(0).lower()) != -1\n\n\n    def search_UID(self, query, id, msg, lastIDs):\n        \"\"\"\n        Returns C{True} if the message UID is in the range defined by the\n        search query.\n\n        @type query: A L{list} of L{bytes}\n        @param query: A list representing the parsed form of the search\n            query. Its first element should be a L{str} that can be interpreted\n            as a sequence range, for example '2:4,5:*'.\n\n        @type id: L{int}\n        @param id: The sequence number of the message being checked.\n\n        @type msg: Provider of L{imap4.IMessage}\n        @param msg: The message being checked.\n\n        @type lastIDs: L{tuple}\n        @param lastIDs: A tuple of (last sequence id, last message id).\n        The I{last sequence id} is an L{int} containing the highest sequence\n        number of a message in the mailbox.  The I{last message id} is an\n        L{int} containing the highest UID of a message in the mailbox.\n        \"\"\"\n        (lastSequenceId, lastMessageId) = lastIDs\n        c = query.pop(0)\n        m = parseIdList(c, lastMessageId)\n        return msg.getUID() in m\n\n\n    def search_UNANSWERED(self, query, id, msg):\n        return '\\\\Answered' not in msg.getFlags()\n\n\n    def search_UNDELETED(self, query, id, msg):\n        return '\\\\Deleted' not in msg.getFlags()\n\n\n    def search_UNDRAFT(self, query, id, msg):\n        return '\\\\Draft' not in msg.getFlags()\n\n\n    def search_UNFLAGGED(self, query, id, msg):\n        return '\\\\Flagged' not in msg.getFlags()\n\n\n    def search_UNKEYWORD(self, query, id, msg):\n        query.pop(0)\n        return False\n\n\n    def search_UNSEEN(self, query, id, msg):\n        return '\\\\Seen' not in msg.getFlags()\n\n\n    def __ebSearch(self, failure, tag):\n        self.sendBadResponse(tag, b'SEARCH failed: ' +\n                             networkString(str(failure.value)))\n        log.err(failure)\n\n\n    def do_FETCH(self, tag, messages, query, uid=0):\n        if query:\n            self._oldTimeout = self.setTimeout(None)\n            maybeDeferred(self.mbox.fetch, messages, uid=uid\n                ).addCallback(iter\n                ).addCallback(self.__cbFetch, tag, query, uid\n                ).addErrback(self.__ebFetch, tag\n                )\n        else:\n            self.sendPositiveResponse(tag, b'FETCH complete')\n\n    select_FETCH = (do_FETCH, arg_seqset, arg_fetchatt)\n\n\n    def __cbFetch(self, results, tag, query, uid):\n        if self.blocked is None:\n            self.blocked = []\n        try:\n            id, msg = next(results)\n        except StopIteration:\n            # The idle timeout was suspended while we delivered results,\n            # restore it now.\n            self.setTimeout(self._oldTimeout)\n            del self._oldTimeout\n\n            # All results have been processed, deliver completion notification.\n\n            # It's important to run this *after* resetting the timeout to \"rig\n            # a race\" in some test code. writing to the transport will\n            # synchronously call test code, which synchronously loses the\n            # connection, calling our connectionLost method, which cancels the\n            # timeout. We want to make sure that timeout is cancelled *after*\n            # we reset it above, so that the final state is no timed\n            # calls. This avoids reactor uncleanliness errors in the test\n            # suite.\n            # XXX: Perhaps loopback should be fixed to not call the user code\n            # synchronously in transport.write?\n            self.sendPositiveResponse(tag, b'FETCH completed')\n\n            # Instance state is now consistent again (ie, it is as though\n            # the fetch command never ran), so allow any pending blocked\n            # commands to execute.\n            self._unblock()\n        else:\n            self.spewMessage(id, msg, query, uid\n                ).addCallback(lambda _: self.__cbFetch(results, tag, query, uid)\n                ).addErrback(self.__ebSpewMessage\n                )\n\n\n    def __ebSpewMessage(self, failure):\n        # This indicates a programming error.\n        # There's no reliable way to indicate anything to the client, since we\n        # may have already written an arbitrary amount of data in response to\n        # the command.\n        log.err(failure)\n        self.transport.loseConnection()\n\n\n    def spew_envelope(self, id, msg, _w=None, _f=None):\n        if _w is None:\n            _w = self.transport.write\n        _w(b'ENVELOPE ' + collapseNestedLists([getEnvelope(msg)]))\n\n\n    def spew_flags(self, id, msg, _w=None, _f=None):\n        if _w is None:\n            _w = self.transport.writen\n        encodedFlags = [networkString(flag) for flag in msg.getFlags()]\n        _w(b'FLAGS ' + b'(' + b' '.join(encodedFlags) + b')')\n\n\n    def spew_internaldate(self, id, msg, _w=None, _f=None):\n        if _w is None:\n            _w = self.transport.write\n        idate = msg.getInternalDate()\n        ttup = email.utils.parsedate_tz(nativeString(idate))\n        if ttup is None:\n            log.msg(\"%d:%r: unpareseable internaldate: %r\" % (id, msg, idate))\n            raise IMAP4Exception(\"Internal failure generating INTERNALDATE\")\n\n        # need to specify the month manually, as strftime depends on locale\n        strdate = time.strftime(\"%d-%%s-%Y %H:%M:%S \", ttup[:9])\n        odate = networkString(strdate % (_MONTH_NAMES[ttup[1]],))\n        if ttup[9] is None:\n            odate = odate + b\"+0000\"\n        else:\n            if ttup[9] >= 0:\n                sign = b\"+\"\n            else:\n                sign = b\"-\"\n            odate = odate + sign + intToBytes(\n                ((abs(ttup[9]) // 3600) * 100 +\n                 (abs(ttup[9]) % 3600) // 60)\n            ).zfill(4)\n        _w(b'INTERNALDATE ' + _quote(odate))\n\n\n    def spew_rfc822header(self, id, msg, _w=None, _f=None):\n        if _w is None:\n            _w = self.transport.write\n        hdrs = _formatHeaders(msg.getHeaders(True))\n        _w(b'RFC822.HEADER ' + _literal(hdrs))\n\n\n    def spew_rfc822text(self, id, msg, _w=None, _f=None):\n        if _w is None:\n            _w = self.transport.write\n        _w(b'RFC822.TEXT ')\n        _f()\n        return FileProducer(msg.getBodyFile()\n            ).beginProducing(self.transport\n            )\n\n\n    def spew_rfc822size(self, id, msg, _w=None, _f=None):\n        if _w is None:\n            _w = self.transport.write\n        _w(b'RFC822.SIZE ' + intToBytes(msg.getSize()))\n\n\n    def spew_rfc822(self, id, msg, _w=None, _f=None):\n        if _w is None:\n            _w = self.transport.write\n        _w(b'RFC822 ')\n        _f()\n        mf = IMessageFile(msg, None)\n        if mf is not None:\n            return FileProducer(mf.open()\n                ).beginProducing(self.transport\n                )\n        return MessageProducer(msg, None, self._scheduler\n            ).beginProducing(self.transport\n            )\n\n\n    def spew_uid(self, id, msg, _w=None, _f=None):\n        if _w is None:\n            _w = self.transport.write\n        _w(b'UID ' + intToBytes(msg.getUID()))\n\n\n    def spew_bodystructure(self, id, msg, _w=None, _f=None):\n        _w(b'BODYSTRUCTURE ' + collapseNestedLists([getBodyStructure(msg, True)]))\n\n\n    def spew_body(self, part, id, msg, _w=None, _f=None):\n        if _w is None:\n            _w = self.transport.write\n        for p in part.part:\n            if msg.isMultipart():\n                msg = msg.getSubPart(p)\n            elif p > 0:\n                # Non-multipart messages have an implicit first part but no\n                # other parts - reject any request for any other part.\n                raise TypeError(\"Requested subpart of non-multipart message\")\n\n        if part.header:\n            hdrs = msg.getHeaders(part.header.negate, *part.header.fields)\n            hdrs = _formatHeaders(hdrs)\n            _w(part.__bytes__() + b' ' + _literal(hdrs))\n        elif part.text:\n            _w(part.__bytes__() + b' ')\n            _f()\n            return FileProducer(msg.getBodyFile()\n                ).beginProducing(self.transport\n                )\n        elif part.mime:\n            hdrs = _formatHeaders(msg.getHeaders(True))\n            _w(part.__bytes__() + b' ' + _literal(hdrs))\n        elif part.empty:\n            _w(part.__bytes__() + b' ')\n            _f()\n            if part.part:\n                return FileProducer(msg.getBodyFile()\n                    ).beginProducing(self.transport\n                    )\n            else:\n                mf = IMessageFile(msg, None)\n                if mf is not None:\n                    return FileProducer(mf.open()).beginProducing(self.transport)\n                return MessageProducer(msg, None, self._scheduler).beginProducing(self.transport)\n\n        else:\n            _w(b'BODY ' + collapseNestedLists([getBodyStructure(msg)]))\n\n\n    def spewMessage(self, id, msg, query, uid):\n        wbuf = WriteBuffer(self.transport)\n        write = wbuf.write\n        flush = wbuf.flush\n        def start():\n            write(b'* ' + intToBytes(id) + b' FETCH (')\n        def finish():\n            write(b')\\r\\n')\n        def space():\n            write(b' ')\n\n        def spew():\n            seenUID = False\n            start()\n            for part in query:\n                if part.type == 'uid':\n                    seenUID = True\n                if part.type == 'body':\n                    yield self.spew_body(part, id, msg, write, flush)\n                else:\n                    f = getattr(self, 'spew_' + part.type)\n                    yield f(id, msg, write, flush)\n                if part is not query[-1]:\n                    space()\n            if uid and not seenUID:\n                space()\n                yield self.spew_uid(id, msg, write, flush)\n            finish()\n            flush()\n        return self._scheduler(spew())\n\n\n    def __ebFetch(self, failure, tag):\n        self.setTimeout(self._oldTimeout)\n        del self._oldTimeout\n        log.err(failure)\n        self.sendBadResponse(tag, b'FETCH failed: ' +\n                             networkString(str(failure.value)))\n\n\n    def do_STORE(self, tag, messages, mode, flags, uid=0):\n        mode = mode.upper()\n        silent = mode.endswith(b'SILENT')\n        if mode.startswith(b'+'):\n            mode = 1\n        elif mode.startswith(b'-'):\n            mode = -1\n        else:\n            mode = 0\n\n        flags = [nativeString(flag) for flag in flags]\n        maybeDeferred(self.mbox.store, messages, flags, mode, uid=uid).addCallbacks(\n            self.__cbStore, self.__ebStore, (tag, self.mbox, uid, silent), None, (tag,), None\n        )\n\n    select_STORE = (do_STORE, arg_seqset, arg_atom, arg_flaglist)\n\n\n    def __cbStore(self, result, tag, mbox, uid, silent):\n        if result and not silent:\n            for (k, v) in result.items():\n                if uid:\n                    uidstr = b' UID ' + intToBytes(mbox.getUID(k))\n                else:\n                    uidstr = b''\n\n                flags = [networkString(flag) for flag in v]\n                self.sendUntaggedResponse(\n                    intToBytes(k) +\n                    b' FETCH (FLAGS ('+ b' '.join(flags) + b')' +\n                    uidstr + b')')\n        self.sendPositiveResponse(tag, b'STORE completed')\n\n\n    def __ebStore(self, failure, tag):\n        self.sendBadResponse(tag, b'Server error: ' +\n                             networkString(str(failure.value)))\n\n\n    def do_COPY(self, tag, messages, mailbox, uid=0):\n        mailbox = self._parseMbox(mailbox)\n        maybeDeferred(self.account.select, mailbox\n            ).addCallback(self._cbCopySelectedMailbox, tag, messages, mailbox, uid\n            ).addErrback(self._ebCopySelectedMailbox, tag\n            )\n    select_COPY = (do_COPY, arg_seqset, arg_finalastring)\n\n\n    def _cbCopySelectedMailbox(self, mbox, tag, messages, mailbox, uid):\n        if not mbox:\n            self.sendNegativeResponse(tag, 'No such mailbox: ' + mailbox)\n        else:\n            maybeDeferred(self.mbox.fetch, messages, uid\n                ).addCallback(self.__cbCopy, tag, mbox\n                ).addCallback(self.__cbCopied, tag, mbox\n                ).addErrback(self.__ebCopy, tag\n                )\n\n\n    def _ebCopySelectedMailbox(self, failure, tag):\n        self.sendBadResponse(tag, b'Server error: ' +\n                             networkString(str(failure.value)))\n\n\n    def __cbCopy(self, messages, tag, mbox):\n        # XXX - This should handle failures with a rollback or something\n        addedDeferreds = []\n\n        fastCopyMbox = IMessageCopier(mbox, None)\n        for (id, msg) in messages:\n            if fastCopyMbox is not None:\n                d = maybeDeferred(fastCopyMbox.copy, msg)\n                addedDeferreds.append(d)\n                continue\n\n            # XXX - The following should be an implementation of IMessageCopier.copy\n            # on an IMailbox->IMessageCopier adapter.\n\n            flags = msg.getFlags()\n            date = msg.getInternalDate()\n\n            body = IMessageFile(msg, None)\n            if body is not None:\n                bodyFile = body.open()\n                d = maybeDeferred(mbox.addMessage, bodyFile, flags, date)\n            else:\n                def rewind(f):\n                    f.seek(0)\n                    return f\n                buffer = tempfile.TemporaryFile()\n                d = MessageProducer(msg, buffer, self._scheduler\n                    ).beginProducing(None\n                    ).addCallback(lambda _, b=buffer, f=flags, d=date: mbox.addMessage(rewind(b), f, d)\n                    )\n            addedDeferreds.append(d)\n        return defer.DeferredList(addedDeferreds)\n\n\n    def __cbCopied(self, deferredIds, tag, mbox):\n        ids = []\n        failures = []\n        for (status, result) in deferredIds:\n            if status:\n                ids.append(result)\n            else:\n                failures.append(result.value)\n        if failures:\n            self.sendNegativeResponse(tag, '[ALERT] Some messages were not copied')\n        else:\n            self.sendPositiveResponse(tag, b'COPY completed')\n\n\n    def __ebCopy(self, failure, tag):\n        self.sendBadResponse(tag, b'COPY failed:' +\n                             networkString(str(failure.value)))\n        log.err(failure)\n\n\n    def do_UID(self, tag, command, line):\n        command = command.upper()\n\n        if command not in (b'COPY', b'FETCH', b'STORE', b'SEARCH'):\n            raise IllegalClientResponse(command)\n\n        self.dispatchCommand(tag, command, line, uid=1)\n\n    select_UID = (do_UID, arg_atom, arg_line)\n\n\n    #\n    # IMailboxListener implementation\n    #\n    def modeChanged(self, writeable):\n        if writeable:\n            self.sendUntaggedResponse(message=b'[READ-WRITE]', isAsync=True)\n        else:\n            self.sendUntaggedResponse(message=b'[READ-ONLY]', isAsync=True)\n\n\n    def flagsChanged(self, newFlags):\n        for (mId, flags) in newFlags.items():\n            encodedFlags = [networkString(flag) for flag in flags]\n            msg = intToBytes(mId) + (\n                b' FETCH (FLAGS (' + b' '.join(encodedFlags) + b'))'\n            )\n            self.sendUntaggedResponse(msg, isAsync=True)\n\n\n    def newMessages(self, exists, recent):\n        if exists is not None:\n            self.sendUntaggedResponse(\n                intToBytes(exists) + b' EXISTS', isAsync=True)\n        if recent is not None:\n            self.sendUntaggedResponse(\n                intToBytes(recent) + b' RECENT', isAsync=True)\n\n\n\nTIMEOUT_ERROR = error.TimeoutError()\n\n@implementer(IMailboxListener)\nclass IMAP4Client(basic.LineReceiver, policies.TimeoutMixin):\n    \"\"\"IMAP4 client protocol implementation\n\n    @ivar state: A string representing the state the connection is currently\n    in.\n    \"\"\"\n    tags = None\n    waiting = None\n    queued = None\n    tagID = 1\n    state = None\n\n    startedTLS = False\n\n    # Number of seconds to wait before timing out a connection.\n    # If the number is <= 0 no timeout checking will be performed.\n    timeout = 0\n\n    # Capabilities are not allowed to change during the session\n    # So cache the first response and use that for all later\n    # lookups\n    _capCache = None\n\n    _memoryFileLimit = 1024 * 1024 * 10\n\n    # Authentication is pluggable.  This maps names to IClientAuthentication\n    # objects.\n    authenticators = None\n\n    STATUS_CODES = ('OK', 'NO', 'BAD', 'PREAUTH', 'BYE')\n\n    STATUS_TRANSFORMATIONS = {\n        'MESSAGES': int, 'RECENT': int, 'UNSEEN': int\n    }\n\n    context = None\n\n    def __init__(self, contextFactory = None):\n        self.tags = {}\n        self.queued = []\n        self.authenticators = {}\n        self.context = contextFactory\n\n        self._tag = None\n        self._parts = None\n        self._lastCmd = None\n\n\n    def registerAuthenticator(self, auth):\n        \"\"\"\n        Register a new form of authentication\n\n        When invoking the authenticate() method of IMAP4Client, the first\n        matching authentication scheme found will be used.  The ordering is\n        that in which the server lists support authentication schemes.\n\n        @type auth: Implementor of C{IClientAuthentication}\n        @param auth: The object to use to perform the client\n        side of this authentication scheme.\n        \"\"\"\n        self.authenticators[auth.getName().upper()] = auth\n\n\n    def rawDataReceived(self, data):\n        if self.timeout > 0:\n            self.resetTimeout()\n\n        self._pendingSize -= len(data)\n        if self._pendingSize > 0:\n            self._pendingBuffer.write(data)\n        else:\n            passon = b''\n            if self._pendingSize < 0:\n                data, passon = data[:self._pendingSize], data[self._pendingSize:]\n            self._pendingBuffer.write(data)\n            rest = self._pendingBuffer\n            self._pendingBuffer = None\n            self._pendingSize = None\n            rest.seek(0, 0)\n            self._parts.append(rest.read())\n            self.setLineMode(passon.lstrip(b'\\r\\n'))\n\n#    def sendLine(self, line):\n#        print 'S:', repr(line)\n#        return basic.LineReceiver.sendLine(self, line)\n\n\n    def _setupForLiteral(self, rest, octets):\n        self._pendingBuffer = self.messageFile(octets)\n        self._pendingSize = octets\n        if self._parts is None:\n            self._parts = [rest, b'\\r\\n']\n        else:\n            self._parts.extend([rest, b'\\r\\n'])\n        self.setRawMode()\n\n\n    def connectionMade(self):\n        if self.timeout > 0:\n            self.setTimeout(self.timeout)\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        We are no longer connected\n        \"\"\"\n        if self.timeout > 0:\n            self.setTimeout(None)\n        if self.queued is not None:\n            queued = self.queued\n            self.queued = None\n            for cmd in queued:\n                cmd.defer.errback(reason)\n        if self.tags is not None:\n            tags = self.tags\n            self.tags = None\n            for cmd in tags.values():\n                if cmd is not None and cmd.defer is not None:\n                    cmd.defer.errback(reason)\n\n\n    def lineReceived(self, line):\n        \"\"\"\n        Attempt to parse a single line from the server.\n\n        @type line: L{bytes}\n        @param line: The line from the server, without the line delimiter.\n\n        @raise IllegalServerResponse: If the line or some part of the line\n            does not represent an allowed message from the server at this time.\n        \"\"\"\n#        print('C: ' + repr(line))\n        if self.timeout > 0:\n            self.resetTimeout()\n\n        lastPart = line.rfind(b'{')\n        if lastPart != -1:\n            lastPart = line[lastPart + 1:]\n            if lastPart.endswith(b'}'):\n                # It's a literal a-comin' in\n                try:\n                    octets = int(lastPart[:-1])\n                except ValueError:\n                    raise IllegalServerResponse(line)\n                if self._parts is None:\n                    self._tag, parts = line.split(None, 1)\n                else:\n                    parts = line\n                self._setupForLiteral(parts, octets)\n                return\n\n        if self._parts is None:\n            # It isn't a literal at all\n            self._regularDispatch(line)\n        else:\n            # If an expression is in progress, no tag is required here\n            # Since we didn't find a literal indicator, this expression\n            # is done.\n            self._parts.append(line)\n            tag, rest = self._tag, b''.join(self._parts)\n            self._tag = self._parts = None\n            self.dispatchCommand(tag, rest)\n\n\n    def timeoutConnection(self):\n        if self._lastCmd and self._lastCmd.defer is not None:\n            d, self._lastCmd.defer = self._lastCmd.defer, None\n            d.errback(TIMEOUT_ERROR)\n\n        if self.queued:\n            for cmd in self.queued:\n                if cmd.defer is not None:\n                    d, cmd.defer = cmd.defer, d\n                    d.errback(TIMEOUT_ERROR)\n\n        self.transport.loseConnection()\n\n\n    def _regularDispatch(self, line):\n        parts = line.split(None, 1)\n        if len(parts) != 2:\n            parts.append(b'')\n        tag, rest = parts\n        self.dispatchCommand(tag, rest)\n\n\n    def messageFile(self, octets):\n        \"\"\"\n        Create a file to which an incoming message may be written.\n\n        @type octets: L{int}\n        @param octets: The number of octets which will be written to the file\n\n        @rtype: Any object which implements C{write(string)} and\n        C{seek(int, int)}\n        @return: A file-like object\n        \"\"\"\n        if octets > self._memoryFileLimit:\n            return tempfile.TemporaryFile()\n        else:\n            return BytesIO()\n\n\n    def makeTag(self):\n        tag = (u'%0.4X' % self.tagID).encode(\"ascii\")\n        self.tagID += 1\n        return tag\n\n\n    def dispatchCommand(self, tag, rest):\n        if self.state is None:\n            f = self.response_UNAUTH\n        else:\n            f = getattr(self, 'response_' + self.state.upper(), None)\n        if f:\n            try:\n                f(tag, rest)\n            except:\n                log.err()\n                self.transport.loseConnection()\n        else:\n            log.err(\"Cannot dispatch: %s, %r, %r\" % (self.state, tag, rest))\n            self.transport.loseConnection()\n\n\n    def response_UNAUTH(self, tag, rest):\n        if self.state is None:\n            # Server greeting, this is\n            status, rest = rest.split(None, 1)\n            if status.upper() == b'OK':\n                self.state = 'unauth'\n            elif status.upper() == b'PREAUTH':\n                self.state = 'auth'\n            else:\n                # XXX - This is rude.\n                self.transport.loseConnection()\n                raise IllegalServerResponse(tag + b' ' + rest)\n\n            b, e = rest.find(b'['), rest.find(b']')\n            if b != -1 and e != -1:\n                self.serverGreeting(\n                    self.__cbCapabilities(\n                        ([parseNestedParens(rest[b + 1:e])], None)))\n            else:\n                self.serverGreeting(None)\n        else:\n            self._defaultHandler(tag, rest)\n\n\n    def response_AUTH(self, tag, rest):\n        self._defaultHandler(tag, rest)\n\n\n    def _defaultHandler(self, tag, rest):\n        if tag == b'*' or tag == b'+':\n            if not self.waiting:\n                self._extraInfo([parseNestedParens(rest)])\n            else:\n                cmd = self.tags[self.waiting]\n                if tag == b'+':\n                    cmd.continuation(rest)\n                else:\n                    cmd.lines.append(rest)\n        else:\n            try:\n                cmd = self.tags[tag]\n            except KeyError:\n                # XXX - This is rude.\n                self.transport.loseConnection()\n                raise IllegalServerResponse(tag + b' ' + rest)\n            else:\n                status, line = rest.split(None, 1)\n                if status == b'OK':\n                    # Give them this last line, too\n                    cmd.finish(rest, self._extraInfo)\n                else:\n                    cmd.defer.errback(IMAP4Exception(line))\n                del self.tags[tag]\n                self.waiting = None\n                self._flushQueue()\n\n\n    def _flushQueue(self):\n        if self.queued:\n            cmd = self.queued.pop(0)\n            t = self.makeTag()\n            self.tags[t] = cmd\n            self.sendLine(cmd.format(t))\n            self.waiting = t\n\n\n    def _extraInfo(self, lines):\n        # XXX - This is terrible.\n        # XXX - Also, this should collapse temporally proximate calls into single\n        #       invocations of IMailboxListener methods, where possible.\n        flags = {}\n        recent = exists = None\n        for response in lines:\n            elements = len(response)\n            if elements == 1 and response[0] == [b'READ-ONLY']:\n                self.modeChanged(False)\n            elif elements == 1 and response[0] == [b'READ-WRITE']:\n                self.modeChanged(True)\n            elif elements == 2 and response[1] == b'EXISTS':\n                exists = int(response[0])\n            elif elements == 2 and response[1] == b'RECENT':\n                recent = int(response[0])\n            elif elements == 3 and response[1] == b'FETCH':\n                mId = int(response[0])\n                values, _ = self._parseFetchPairs(response[2])\n                flags.setdefault(mId, []).extend(values.get('FLAGS', ()))\n            else:\n                log.msg('Unhandled unsolicited response: %s' % (response,))\n\n        if flags:\n            self.flagsChanged(flags)\n        if recent is not None or exists is not None:\n            self.newMessages(exists, recent)\n\n\n    def sendCommand(self, cmd):\n        cmd.defer = defer.Deferred()\n        if self.waiting:\n            self.queued.append(cmd)\n            return cmd.defer\n        t = self.makeTag()\n        self.tags[t] = cmd\n        self.sendLine(cmd.format(t))\n        self.waiting = t\n        self._lastCmd = cmd\n        return cmd.defer\n\n\n    def getCapabilities(self, useCache=1):\n        \"\"\"\n        Request the capabilities available on this server.\n\n        This command is allowed in any state of connection.\n\n        @type useCache: C{bool}\n        @param useCache: Specify whether to use the capability-cache or to\n        re-retrieve the capabilities from the server.  Server capabilities\n        should never change, so for normal use, this flag should never be\n        false.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback will be invoked with a\n        dictionary mapping capability types to lists of supported\n        mechanisms, or to None if a support list is not applicable.\n        \"\"\"\n        if useCache and self._capCache is not None:\n            return defer.succeed(self._capCache)\n        cmd = b'CAPABILITY'\n        resp = (b'CAPABILITY',)\n        d = self.sendCommand(Command(cmd, wantResponse=resp))\n        d.addCallback(self.__cbCapabilities)\n        return d\n\n\n    def __cbCapabilities(self, result):\n        (lines, tagline) = result\n        caps = {}\n        for rest in lines:\n            for cap in rest[1:]:\n                parts = cap.split(b'=', 1)\n                if len(parts) == 1:\n                    category, value = parts[0], None\n                else:\n                    category, value = parts\n                caps.setdefault(category, []).append(value)\n\n        # Preserve a non-ideal API for backwards compatibility.  It would\n        # probably be entirely sensible to have an object with a wider API than\n        # dict here so this could be presented less insanely.\n        for category in caps:\n            if caps[category] == [None]:\n                caps[category] = None\n        self._capCache = caps\n        return caps\n\n\n    def logout(self):\n        \"\"\"\n        Inform the server that we are done with the connection.\n\n        This command is allowed in any state of connection.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback will be invoked with None\n        when the proper server acknowledgement has been received.\n        \"\"\"\n        d = self.sendCommand(Command(b'LOGOUT', wantResponse=(b'BYE',)))\n        d.addCallback(self.__cbLogout)\n        return d\n\n\n    def __cbLogout(self, result):\n        (lines, tagline) = result\n        self.transport.loseConnection()\n        # We don't particularly care what the server said\n        return None\n\n\n    def noop(self):\n        \"\"\"\n        Perform no operation.\n\n        This command is allowed in any state of connection.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback will be invoked with a list\n        of untagged status updates the server responds with.\n        \"\"\"\n        d = self.sendCommand(Command(b'NOOP'))\n        d.addCallback(self.__cbNoop)\n        return d\n\n\n    def __cbNoop(self, result):\n        # Conceivable, this is elidable.\n        # It is, afterall, a no-op.\n        (lines, tagline) = result\n        return lines\n\n\n    def startTLS(self, contextFactory=None):\n        \"\"\"\n        Initiates a 'STARTTLS' request and negotiates the TLS / SSL\n        Handshake.\n\n        @param contextFactory: The TLS / SSL Context Factory to\n        leverage.  If the contextFactory is None the IMAP4Client will\n        either use the current TLS / SSL Context Factory or attempt to\n        create a new one.\n\n        @type contextFactory: C{ssl.ClientContextFactory}\n\n        @return: A Deferred which fires when the transport has been\n        secured according to the given contextFactory, or which fails\n        if the transport cannot be secured.\n        \"\"\"\n        assert not self.startedTLS, \"Client and Server are currently communicating via TLS\"\n        if contextFactory is None:\n            contextFactory = self._getContextFactory()\n\n        if contextFactory is None:\n            return defer.fail(IMAP4Exception(\n                \"IMAP4Client requires a TLS context to \"\n                \"initiate the STARTTLS handshake\"))\n\n        if b'STARTTLS' not in self._capCache:\n            return defer.fail(IMAP4Exception(\n                \"Server does not support secure communication \"\n                \"via TLS / SSL\"))\n\n        tls = interfaces.ITLSTransport(self.transport, None)\n        if tls is None:\n            return defer.fail(IMAP4Exception(\n                \"IMAP4Client transport does not implement \"\n                \"interfaces.ITLSTransport\"))\n\n        d = self.sendCommand(Command(b'STARTTLS'))\n        d.addCallback(self._startedTLS, contextFactory)\n        d.addCallback(lambda _: self.getCapabilities())\n        return d\n\n\n    def authenticate(self, secret):\n        \"\"\"\n        Attempt to enter the authenticated state with the server\n\n        This command is allowed in the Non-Authenticated state.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked if the authentication\n        succeeds and whose errback will be invoked otherwise.\n        \"\"\"\n        if self._capCache is None:\n            d = self.getCapabilities()\n        else:\n            d = defer.succeed(self._capCache)\n        d.addCallback(self.__cbAuthenticate, secret)\n        return d\n\n\n    def __cbAuthenticate(self, caps, secret):\n        auths = caps.get(b'AUTH', ())\n        for scheme in auths:\n            if scheme.upper() in self.authenticators:\n                cmd = Command(b'AUTHENTICATE', scheme, (),\n                              self.__cbContinueAuth, scheme,\n                              secret)\n                return self.sendCommand(cmd)\n\n        if self.startedTLS:\n            return defer.fail(NoSupportedAuthentication(\n                auths, self.authenticators.keys()))\n        else:\n            def ebStartTLS(err):\n                err.trap(IMAP4Exception)\n                # We couldn't negotiate TLS for some reason\n                return defer.fail(NoSupportedAuthentication(\n                    auths, self.authenticators.keys()))\n\n            d = self.startTLS()\n            d.addErrback(ebStartTLS)\n            d.addCallback(lambda _: self.getCapabilities())\n            d.addCallback(self.__cbAuthTLS, secret)\n            return d\n\n\n    def __cbContinueAuth(self, rest, scheme, secret):\n        try:\n            chal = decodebytes(rest + b'\\n')\n        except binascii.Error:\n            self.sendLine(b'*')\n            raise IllegalServerResponse(rest)\n        else:\n            auth = self.authenticators[scheme]\n            chal = auth.challengeResponse(secret, chal)\n            self.sendLine(encodebytes(chal).strip())\n\n\n    def __cbAuthTLS(self, caps, secret):\n        auths = caps.get(b'AUTH', ())\n        for scheme in auths:\n            if scheme.upper() in self.authenticators:\n                cmd = Command(b'AUTHENTICATE', scheme, (),\n                              self.__cbContinueAuth, scheme,\n                              secret)\n                return self.sendCommand(cmd)\n        raise NoSupportedAuthentication(auths, self.authenticators.keys())\n\n\n    def login(self, username, password):\n        \"\"\"\n        Authenticate with the server using a username and password\n\n        This command is allowed in the Non-Authenticated state.  If the\n        server supports the STARTTLS capability and our transport supports\n        TLS, TLS is negotiated before the login command is issued.\n\n        A more secure way to log in is to use C{startTLS} or\n        C{authenticate} or both.\n\n        @type username: L{str}\n        @param username: The username to log in with\n\n        @type password: L{str}\n        @param password: The password to log in with\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked if login is successful\n        and whose errback is invoked otherwise.\n        \"\"\"\n        d = maybeDeferred(self.getCapabilities)\n        d.addCallback(self.__cbLoginCaps, username, password)\n        return d\n\n\n    def serverGreeting(self, caps):\n        \"\"\"\n        Called when the server has sent us a greeting.\n\n        @type caps: C{dict}\n        @param caps: Capabilities the server advertised in its greeting.\n        \"\"\"\n\n\n    def _getContextFactory(self):\n        if self.context is not None:\n            return self.context\n        try:\n            from twisted.internet import ssl\n        except ImportError:\n            return None\n        else:\n            context = ssl.ClientContextFactory()\n            context.method = ssl.SSL.TLSv1_METHOD\n            return context\n\n\n    def __cbLoginCaps(self, capabilities, username, password):\n        # If the server advertises STARTTLS, we might want to try to switch to TLS\n        tryTLS = b'STARTTLS' in capabilities\n\n        # If our transport supports switching to TLS, we might want to try to switch to TLS.\n        tlsableTransport = interfaces.ITLSTransport(self.transport, None) is not None\n\n        # If our transport is not already using TLS, we might want to try to switch to TLS.\n        nontlsTransport = interfaces.ISSLTransport(self.transport, None) is None\n\n        if not self.startedTLS and tryTLS and tlsableTransport and nontlsTransport:\n            d = self.startTLS()\n\n            d.addCallbacks(\n                self.__cbLoginTLS,\n                self.__ebLoginTLS,\n                callbackArgs=(username, password),\n                )\n            return d\n        else:\n            if nontlsTransport:\n                log.msg(\"Server has no TLS support. logging in over cleartext!\")\n            args = b' '.join((_quote(username), _quote(password)))\n            return self.sendCommand(Command(b'LOGIN', args))\n\n\n    def _startedTLS(self, result, context):\n        self.transport.startTLS(context)\n        self._capCache = None\n        self.startedTLS = True\n        return result\n\n\n    def __cbLoginTLS(self, result, username, password):\n        args = b' '.join((_quote(username), _quote(password)))\n        return self.sendCommand(Command(b'LOGIN', args))\n\n\n    def __ebLoginTLS(self, failure):\n        log.err(failure)\n        return failure\n\n\n    def namespace(self):\n        \"\"\"\n        Retrieve information about the namespaces available to this account\n\n        This command is allowed in the Authenticated and Selected states.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with namespace\n        information.  An example of this information is::\n\n            [[['', '/']], [], []]\n\n        which indicates a single personal namespace called '' with '/'\n        as its hierarchical delimiter, and no shared or user namespaces.\n        \"\"\"\n        cmd = b'NAMESPACE'\n        resp = (b'NAMESPACE',)\n        d = self.sendCommand(Command(cmd, wantResponse=resp))\n        d.addCallback(self.__cbNamespace)\n        return d\n\n\n    def __cbNamespace(self, result):\n        (lines, last) = result\n\n        # Namespaces and their delimiters qualify and delimit\n        # mailboxes, so they should be native strings\n        #\n        # On Python 2, no decoding is necessary to maintain\n        # the API contract.\n        #\n        # On Python 3, users specify mailboxes with native strings, so\n        # they should receive namespaces and delimiters as native\n        # strings.  Both cases are possible because of the imap4-utf-7\n        # encoding.\n        if _PY3:\n            def _prepareNamespaceOrDelimiter(namespaceList):\n                return [\n                    element.decode('imap4-utf-7') for element in namespaceList\n                ]\n        else:\n            def _prepareNamespaceOrDelimiter(element):\n                return element\n\n        for parts in lines:\n            if len(parts) == 4 and parts[0] == b'NAMESPACE':\n                return [\n                    []\n                    if pairOrNone is None else\n                    [\n                        _prepareNamespaceOrDelimiter(value)\n                        for value in pairOrNone\n                    ]\n                    for pairOrNone in parts[1:]\n                ]\n        log.err(\"No NAMESPACE response to NAMESPACE command\")\n        return [[], [], []]\n\n\n    def select(self, mailbox):\n        \"\"\"\n        Select a mailbox\n\n        This command is allowed in the Authenticated and Selected states.\n\n        @type mailbox: L{str}\n        @param mailbox: The name of the mailbox to select\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with mailbox\n        information if the select is successful and whose errback is\n        invoked otherwise.  Mailbox information consists of a dictionary\n        with the following L{str} keys and values::\n\n                FLAGS: A list of strings containing the flags settable on\n                        messages in this mailbox.\n\n                EXISTS: An integer indicating the number of messages in this\n                        mailbox.\n\n                RECENT: An integer indicating the number of \"recent\"\n                        messages in this mailbox.\n\n                UNSEEN: The message sequence number (an integer) of the\n                        first unseen message in the mailbox.\n\n                PERMANENTFLAGS: A list of strings containing the flags that\n                        can be permanently set on messages in this mailbox.\n\n                UIDVALIDITY: An integer uniquely identifying this mailbox.\n        \"\"\"\n        cmd = b'SELECT'\n        args = _prepareMailboxName(mailbox)\n        # This appears not to be used, so we can use native strings to\n        # indicate that the return type is native strings.\n        resp = ('FLAGS', 'EXISTS', 'RECENT',\n                'UNSEEN', 'PERMANENTFLAGS', 'UIDVALIDITY')\n        d = self.sendCommand(Command(cmd, args, wantResponse=resp))\n        d.addCallback(self.__cbSelect, 1)\n        return d\n\n\n    def examine(self, mailbox):\n        \"\"\"\n        Select a mailbox in read-only mode\n\n        This command is allowed in the Authenticated and Selected states.\n\n        @type mailbox: L{str}\n        @param mailbox: The name of the mailbox to examine\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with mailbox\n        information if the examine is successful and whose errback\n        is invoked otherwise.  Mailbox information consists of a dictionary\n        with the following keys and values::\n\n            'FLAGS': A list of strings containing the flags settable on\n                        messages in this mailbox.\n\n            'EXISTS': An integer indicating the number of messages in this\n                        mailbox.\n\n            'RECENT': An integer indicating the number of \\\"recent\\\"\n                        messages in this mailbox.\n\n            'UNSEEN': An integer indicating the number of messages not\n                        flagged \\\\Seen in this mailbox.\n\n            'PERMANENTFLAGS': A list of strings containing the flags that\n                        can be permanently set on messages in this mailbox.\n\n            'UIDVALIDITY': An integer uniquely identifying this mailbox.\n        \"\"\"\n        cmd = b'EXAMINE'\n        args = _prepareMailboxName(mailbox)\n        resp = (b'FLAGS', b'EXISTS', b'RECENT', b'UNSEEN', b'PERMANENTFLAGS', b'UIDVALIDITY')\n        d = self.sendCommand(Command(cmd, args, wantResponse=resp))\n        d.addCallback(self.__cbSelect, 0)\n        return d\n\n\n    def _intOrRaise(self, value, phrase):\n        \"\"\"\n        Parse C{value} as an integer and return the result or raise\n        L{IllegalServerResponse} with C{phrase} as an argument if C{value}\n        cannot be parsed as an integer.\n        \"\"\"\n        try:\n            return int(value)\n        except ValueError:\n            raise IllegalServerResponse(phrase)\n\n\n    def __cbSelect(self, result, rw):\n        \"\"\"\n        Handle lines received in response to a SELECT or EXAMINE command.\n\n        See RFC 3501, section 6.3.1.\n        \"\"\"\n        (lines, tagline) = result\n        # In the absence of specification, we are free to assume:\n        #   READ-WRITE access\n        datum = {'READ-WRITE': rw}\n        lines.append(parseNestedParens(tagline))\n        for split in lines:\n            if len(split) > 0 and split[0].upper() == b'OK':\n                # Handle all the kinds of OK response.\n                content = split[1]\n                if isinstance(content, list):\n                    key = content[0]\n                else:\n                    # not multi-valued, like OK LOGIN\n                    key = content\n                key = key.upper()\n                if key == b'READ-ONLY':\n                    datum['READ-WRITE'] = False\n                elif key == b'READ-WRITE':\n                    datum['READ-WRITE'] = True\n                elif key == b'UIDVALIDITY':\n                    datum['UIDVALIDITY'] = self._intOrRaise(content[1], split)\n                elif key == b'UNSEEN':\n                    datum['UNSEEN'] = self._intOrRaise(content[1], split)\n                elif key == b'UIDNEXT':\n                    datum['UIDNEXT'] = self._intOrRaise(content[1], split)\n                elif key == b'PERMANENTFLAGS':\n                    datum['PERMANENTFLAGS'] = tuple(\n                        nativeString(flag) for flag in content[1])\n                else:\n                    log.err('Unhandled SELECT response (2): %s' % (split,))\n            elif len(split) == 2:\n                # Handle FLAGS, EXISTS, and RECENT\n                if split[0].upper() == b'FLAGS':\n                    datum['FLAGS'] = tuple(\n                        nativeString(flag) for flag in split[1])\n                elif isinstance(split[1], bytes):\n                    # Must make sure things are strings before treating them as\n                    # strings since some other forms of response have nesting in\n                    # places which results in lists instead.\n                    if split[1].upper() == b'EXISTS':\n                        datum['EXISTS'] = self._intOrRaise(split[0], split)\n                    elif split[1].upper() == b'RECENT':\n                        datum['RECENT'] = self._intOrRaise(split[0], split)\n                    else:\n                        log.err('Unhandled SELECT response (0): %s' % (split,))\n                else:\n                    log.err('Unhandled SELECT response (1): %s' % (split,))\n            else:\n                log.err('Unhandled SELECT response (4): %s' % (split,))\n        return datum\n\n\n    def create(self, name):\n        \"\"\"\n        Create a new mailbox on the server\n\n        This command is allowed in the Authenticated and Selected states.\n\n        @type name: L{str}\n        @param name: The name of the mailbox to create.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked if the mailbox creation\n        is successful and whose errback is invoked otherwise.\n        \"\"\"\n        return self.sendCommand(Command(b'CREATE', _prepareMailboxName(name)))\n\n\n    def delete(self, name):\n        \"\"\"\n        Delete a mailbox\n\n        This command is allowed in the Authenticated and Selected states.\n\n        @type name: L{str}\n        @param name: The name of the mailbox to delete.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose calblack is invoked if the mailbox is\n        deleted successfully and whose errback is invoked otherwise.\n        \"\"\"\n        return self.sendCommand(Command(b'DELETE', _prepareMailboxName(name)))\n\n\n    def rename(self, oldname, newname):\n        \"\"\"\n        Rename a mailbox\n\n        This command is allowed in the Authenticated and Selected states.\n\n        @type oldname: L{str}\n        @param oldname: The current name of the mailbox to rename.\n\n        @type newname: L{str}\n        @param newname: The new name to give the mailbox.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked if the rename is\n        successful and whose errback is invoked otherwise.\n        \"\"\"\n        oldname = _prepareMailboxName(oldname)\n        newname = _prepareMailboxName(newname)\n        return self.sendCommand(Command(b'RENAME', b' '.join((oldname, newname))))\n\n\n    def subscribe(self, name):\n        \"\"\"\n        Add a mailbox to the subscription list\n\n        This command is allowed in the Authenticated and Selected states.\n\n        @type name: L{str}\n        @param name: The mailbox to mark as 'active' or 'subscribed'\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked if the subscription\n        is successful and whose errback is invoked otherwise.\n        \"\"\"\n        return self.sendCommand(Command(b'SUBSCRIBE', _prepareMailboxName(name)))\n\n\n    def unsubscribe(self, name):\n        \"\"\"\n        Remove a mailbox from the subscription list\n\n        This command is allowed in the Authenticated and Selected states.\n\n        @type name: L{str}\n        @param name: The mailbox to unsubscribe\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked if the unsubscription\n        is successful and whose errback is invoked otherwise.\n        \"\"\"\n        return self.sendCommand(Command(b'UNSUBSCRIBE', _prepareMailboxName(name)))\n\n\n    def list(self, reference, wildcard):\n        \"\"\"\n        List a subset of the available mailboxes\n\n        This command is allowed in the Authenticated and Selected\n        states.\n\n        @type reference: L{str}\n        @param reference: The context in which to interpret\n            C{wildcard}\n\n        @type wildcard: L{str}\n        @param wildcard: The pattern of mailbox names to match,\n            optionally including either or both of the '*' and '%'\n            wildcards.  '*' will match zero or more characters and\n            cross hierarchical boundaries.  '%' will also match zero\n            or more characters, but is limited to a single\n            hierarchical level.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a list of\n            L{tuple}s, the first element of which is a L{tuple} of\n            mailbox flags, the second element of which is the\n            hierarchy delimiter for this mailbox, and the third of\n            which is the mailbox name; if the command is unsuccessful,\n            the deferred's errback is invoked instead.  B{NB}: the\n            delimiter and the mailbox name are L{str}s.\n        \"\"\"\n        cmd = b'LIST'\n        args = ('\"%s\" \"%s\"' % (reference, wildcard)).encode(\"imap4-utf-7\")\n        resp = (b'LIST',)\n        d = self.sendCommand(Command(cmd, args, wantResponse=resp))\n        d.addCallback(self.__cbList, b'LIST')\n        return d\n\n\n    def lsub(self, reference, wildcard):\n        \"\"\"\n        List a subset of the subscribed available mailboxes\n\n        This command is allowed in the Authenticated and Selected states.\n\n        The parameters and returned object are the same as for the L{list}\n        method, with one slight difference: Only mailboxes which have been\n        subscribed can be included in the resulting list.\n        \"\"\"\n        cmd = b'LSUB'\n\n        encodedReference = reference.encode('ascii')\n        encodedWildcard = wildcard.encode('imap4-utf-7')\n        args = b\"\".join([\n            b'\"', encodedReference, b'\"'\n            b' \"', encodedWildcard, b'\"',\n        ])\n        resp = (b'LSUB',)\n        d = self.sendCommand(Command(cmd, args, wantResponse=resp))\n        d.addCallback(self.__cbList, b'LSUB')\n        return d\n\n\n    def __cbList(self, result, command):\n        (lines, last) = result\n        results = []\n\n        for parts in lines:\n            if len(parts) == 4 and parts[0] == command:\n                # flags\n                parts[1] = tuple(nativeString(flag) for flag in parts[1])\n\n                # The mailbox should be a native string.\n                # On Python 2, this maintains the API's contract.\n                #\n                # On Python 3, users specify mailboxes with native\n                # strings, so they should receive mailboxes as native\n                # strings.  Both cases are possible because of the\n                # imap4-utf-7 encoding.\n                #\n                # Mailbox names contain the hierarchical delimiter, so\n                # it too should be a native string.\n                if _PY3:\n                    # delimiter\n                    parts[2] = parts[2].decode('imap4-utf-7')\n                    # mailbox\n                    parts[3] = parts[3].decode('imap4-utf-7')\n\n                results.append(tuple(parts[1:]))\n        return results\n\n\n    _statusNames = {\n        name: name.encode('ascii') for name in (\n            'MESSAGES',\n            'RECENT',\n            'UIDNEXT',\n            'UIDVALIDITY',\n            'UNSEEN',\n        )\n    }\n\n    def status(self, mailbox, *names):\n        \"\"\"\n        Retrieve the status of the given mailbox\n\n        This command is allowed in the Authenticated and Selected states.\n\n        @type mailbox: L{str}\n        @param mailbox: The name of the mailbox to query\n\n        @type *names: L{bytes}\n        @param *names: The status names to query.  These may be any number of:\n            C{'MESSAGES'}, C{'RECENT'}, C{'UIDNEXT'}, C{'UIDVALIDITY'}, and\n            C{'UNSEEN'}.\n\n        @rtype: L{Deferred}\n        @return: A deferred which fires with the status information if the\n            command is successful and whose errback is invoked otherwise.  The\n            status information is in the form of a C{dict}.  Each element of\n            C{names} is a key in the dictionary.  The value for each key is the\n            corresponding response from the server.\n        \"\"\"\n        cmd = b'STATUS'\n\n        preparedMailbox = _prepareMailboxName(mailbox)\n        try:\n            names = b' '.join(self._statusNames[name] for name in names)\n        except KeyError:\n            raise ValueError(\"Unknown names: {!r}\".format(\n                set(names) - set(self._statusNames)\n            ))\n\n        args = b''.join([preparedMailbox,\n                         b\" (\", names, b\")\"])\n        resp = (b'STATUS',)\n        d = self.sendCommand(Command(cmd, args, wantResponse=resp))\n        d.addCallback(self.__cbStatus)\n        return d\n\n\n    def __cbStatus(self, result):\n        (lines, last) = result\n        status = {}\n        for parts in lines:\n            if parts[0] == b'STATUS':\n                items = parts[2]\n                items = [items[i:i+2] for i in range(0, len(items), 2)]\n                for k, v in items:\n                    try:\n                        status[nativeString(k)] = v\n                    except UnicodeDecodeError:\n                        raise IllegalServerResponse(repr(items))\n        for k in status.keys():\n            t = self.STATUS_TRANSFORMATIONS.get(k)\n            if t:\n                try:\n                    status[k] = t(status[k])\n                except Exception as e:\n                    raise IllegalServerResponse('(' + k + ' '+ status[k] + '): ' + str(e))\n        return status\n\n\n    def append(self, mailbox, message, flags = (), date = None):\n        \"\"\"\n        Add the given message to the given mailbox.\n\n        This command is allowed in the Authenticated and Selected states.\n\n        @type mailbox: L{str}\n        @param mailbox: The mailbox to which to add this message.\n\n        @type message: Any file-like object opened in B{binary mode}.\n        @param message: The message to add, in RFC822 format.  Newlines\n        in this file should be \\\\r\\\\n-style.\n\n        @type flags: Any iterable of L{str}\n        @param flags: The flags to associated with this message.\n\n        @type date: L{str}\n        @param date: The date to associate with this message.  This should\n        be of the format DD-MM-YYYY HH:MM:SS +/-HHMM.  For example, in\n        Eastern Standard Time, on July 1st 2004 at half past 1 PM,\n        \\\"01-07-2004 13:30:00 -0500\\\".\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked when this command\n        succeeds or whose errback is invoked if it fails.\n        \"\"\"\n        message.seek(0, 2)\n        L = message.tell()\n        message.seek(0, 0)\n        if date:\n            date = networkString(' \"%s\"' % nativeString(date))\n        else:\n            date = b''\n\n        encodedFlags = [networkString(flag) for flag in flags]\n\n        cmd = b''.join([\n            _prepareMailboxName(mailbox),\n            b\" (\", b\" \".join(encodedFlags), b\")\",\n            date,\n            b\" {\", intToBytes(L), b\"}\",\n        ])\n\n        d = self.sendCommand(Command(b'APPEND', cmd, (), self.__cbContinueAppend, message))\n        return d\n\n\n    def __cbContinueAppend(self, lines, message):\n        s = basic.FileSender()\n        return s.beginFileTransfer(message, self.transport, None\n            ).addCallback(self.__cbFinishAppend)\n\n\n    def __cbFinishAppend(self, foo):\n        self.sendLine(b'')\n\n\n    def check(self):\n        \"\"\"\n        Tell the server to perform a checkpoint\n\n        This command is allowed in the Selected state.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked when this command\n        succeeds or whose errback is invoked if it fails.\n        \"\"\"\n        return self.sendCommand(Command(b'CHECK'))\n\n\n    def close(self):\n        \"\"\"\n        Return the connection to the Authenticated state.\n\n        This command is allowed in the Selected state.\n\n        Issuing this command will also remove all messages flagged \\\\Deleted\n        from the selected mailbox if it is opened in read-write mode,\n        otherwise it indicates success by no messages are removed.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked when the command\n        completes successfully or whose errback is invoked if it fails.\n        \"\"\"\n        return self.sendCommand(Command(b'CLOSE'))\n\n\n    def expunge(self):\n        \"\"\"\n        Return the connection to the Authenticate state.\n\n        This command is allowed in the Selected state.\n\n        Issuing this command will perform the same actions as issuing the\n        close command, but will also generate an 'expunge' response for\n        every message deleted.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a list of the\n        'expunge' responses when this command is successful or whose errback\n        is invoked otherwise.\n        \"\"\"\n        cmd = b'EXPUNGE'\n        resp = (b'EXPUNGE',)\n        d = self.sendCommand(Command(cmd, wantResponse=resp))\n        d.addCallback(self.__cbExpunge)\n        return d\n\n\n    def __cbExpunge(self, result):\n        (lines, last) = result\n        ids = []\n        for parts in lines:\n            if len(parts) == 2 and parts[1] == b'EXPUNGE':\n                ids.append(self._intOrRaise(parts[0], parts))\n        return ids\n\n\n    def search(self, *queries, **kwarg):\n        \"\"\"\n        Search messages in the currently selected mailbox\n\n        This command is allowed in the Selected state.\n\n        Any non-zero number of queries are accepted by this method, as returned\n        by the C{Query}, C{Or}, and C{Not} functions.\n\n        @param uid: if true, the server is asked to return message UIDs instead\n            of message sequence numbers.  (This is a keyword-only argument.)\n        @type uid: L{bool}\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback will be invoked with a list of all\n            the message sequence numbers return by the search, or whose errback\n            will be invoked if there is an error.\n        \"\"\"\n        # Queries should be encoded as ASCII unless a charset\n        # identifier is provided.  See #9201.\n        if _PY3:\n            queries = [query.encode('charmap') for query in queries]\n\n        if kwarg.get('uid'):\n            cmd = b'UID SEARCH'\n        else:\n            cmd = b'SEARCH'\n        args = b' '.join(queries)\n        d = self.sendCommand(Command(cmd, args, wantResponse=(cmd,)))\n        d.addCallback(self.__cbSearch)\n        return d\n\n\n    def __cbSearch(self, result):\n        (lines, end) = result\n        ids = []\n        for parts in lines:\n            if len(parts) > 0 and parts[0] == b'SEARCH':\n                ids.extend([self._intOrRaise(p, parts) for p in parts[1:]])\n        return ids\n\n\n    def fetchUID(self, messages, uid=0):\n        \"\"\"\n        Retrieve the unique identifier for one or more messages\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a dict mapping\n        message sequence numbers to unique message identifiers, or whose\n        errback is invoked if there is an error.\n        \"\"\"\n        return self._fetch(messages, useUID=uid, uid=1)\n\n\n    def fetchFlags(self, messages, uid=0):\n        \"\"\"\n        Retrieve the flags for one or more messages\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: The messages for which to retrieve flags.\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a dict mapping\n        message numbers to lists of flags, or whose errback is invoked if\n        there is an error.\n        \"\"\"\n        return self._fetch(messages, useUID=uid, flags=1)\n\n\n    def fetchInternalDate(self, messages, uid=0):\n        \"\"\"\n        Retrieve the internal date associated with one or more messages\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: The messages for which to retrieve the internal date.\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a dict mapping\n        message numbers to date strings, or whose errback is invoked\n        if there is an error.  Date strings take the format of\n        \\\"day-month-year time timezone\\\".\n        \"\"\"\n        return self._fetch(messages, useUID=uid, internaldate=1)\n\n\n    def fetchEnvelope(self, messages, uid=0):\n        \"\"\"\n        Retrieve the envelope data for one or more messages\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: The messages for which to retrieve envelope\n            data.\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of\n            message numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a dict\n            mapping message numbers to envelope data, or whose errback\n            is invoked if there is an error.  Envelope data consists\n            of a sequence of the date, subject, from, sender,\n            reply-to, to, cc, bcc, in-reply-to, and message-id header\n            fields.  The date, subject, in-reply-to, and message-id\n            fields are L{str}, while the from, sender, reply-to, to,\n            cc, and bcc fields contain address data as L{str}s.\n            Address data consists of a sequence of name, source route,\n            mailbox name, and hostname.  Fields which are not present\n            for a particular address may be L{None}.\n        \"\"\"\n        return self._fetch(messages, useUID=uid, envelope=1)\n\n\n    def fetchBodyStructure(self, messages, uid=0):\n        \"\"\"\n        Retrieve the structure of the body of one or more messages\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: The messages for which to retrieve body structure\n        data.\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a dict mapping\n        message numbers to body structure data, or whose errback is invoked\n        if there is an error.  Body structure data describes the MIME-IMB\n        format of a message and consists of a sequence of mime type, mime\n        subtype, parameters, content id, description, encoding, and size.\n        The fields following the size field are variable: if the mime\n        type/subtype is message/rfc822, the contained message's envelope\n        information, body structure data, and number of lines of text; if\n        the mime type is text, the number of lines of text.  Extension fields\n        may also be included; if present, they are: the MD5 hash of the body,\n        body disposition, body language.\n        \"\"\"\n        return self._fetch(messages, useUID=uid, bodystructure=1)\n\n\n    def fetchSimplifiedBody(self, messages, uid=0):\n        \"\"\"\n        Retrieve the simplified body structure of one or more messages\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type uid: C{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a dict mapping\n        message numbers to body data, or whose errback is invoked\n        if there is an error.  The simplified body structure is the same\n        as the body structure, except that extension fields will never be\n        present.\n        \"\"\"\n        return self._fetch(messages, useUID=uid, body=1)\n\n\n    def fetchMessage(self, messages, uid=0):\n        \"\"\"\n        Retrieve one or more entire messages\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type uid: C{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n\n        @return: A L{Deferred} which will fire with a C{dict} mapping message\n            sequence numbers to C{dict}s giving message data for the\n            corresponding message.  If C{uid} is true, the inner dictionaries\n            have a C{'UID'} key mapped to a L{str} giving the UID for the\n            message.  The text of the message is a L{str} associated with the\n            C{'RFC822'} key in each dictionary.\n        \"\"\"\n        return self._fetch(messages, useUID=uid, rfc822=1)\n\n\n    def fetchHeaders(self, messages, uid=0):\n        \"\"\"\n        Retrieve headers of one or more messages\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a dict mapping\n        message numbers to dicts of message headers, or whose errback is\n        invoked if there is an error.\n        \"\"\"\n        return self._fetch(messages, useUID=uid, rfc822header=1)\n\n\n    def fetchBody(self, messages, uid=0):\n        \"\"\"\n        Retrieve body text of one or more messages\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a dict mapping\n        message numbers to file-like objects containing body text, or whose\n        errback is invoked if there is an error.\n        \"\"\"\n        return self._fetch(messages, useUID=uid, rfc822text=1)\n\n\n    def fetchSize(self, messages, uid=0):\n        \"\"\"\n        Retrieve the size, in octets, of one or more messages\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a dict mapping\n        message numbers to sizes, or whose errback is invoked if there is\n        an error.\n        \"\"\"\n        return self._fetch(messages, useUID=uid, rfc822size=1)\n\n\n    def fetchFull(self, messages, uid=0):\n        \"\"\"\n        Retrieve several different fields of one or more messages\n\n        This command is allowed in the Selected state.  This is equivalent\n        to issuing all of the C{fetchFlags}, C{fetchInternalDate},\n        C{fetchSize}, C{fetchEnvelope}, and C{fetchSimplifiedBody}\n        functions.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a dict mapping\n        message numbers to dict of the retrieved data values, or whose\n        errback is invoked if there is an error.  They dictionary keys\n        are \"flags\", \"date\", \"size\", \"envelope\", and \"body\".\n        \"\"\"\n        return self._fetch(\n            messages, useUID=uid, flags=1, internaldate=1,\n            rfc822size=1, envelope=1, body=1)\n\n\n    def fetchAll(self, messages, uid=0):\n        \"\"\"\n        Retrieve several different fields of one or more messages\n\n        This command is allowed in the Selected state.  This is equivalent\n        to issuing all of the C{fetchFlags}, C{fetchInternalDate},\n        C{fetchSize}, and C{fetchEnvelope} functions.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a dict mapping\n        message numbers to dict of the retrieved data values, or whose\n        errback is invoked if there is an error.  They dictionary keys\n        are \"flags\", \"date\", \"size\", and \"envelope\".\n        \"\"\"\n        return self._fetch(\n            messages, useUID=uid, flags=1, internaldate=1,\n            rfc822size=1, envelope=1)\n\n\n    def fetchFast(self, messages, uid=0):\n        \"\"\"\n        Retrieve several different fields of one or more messages\n\n        This command is allowed in the Selected state.  This is equivalent\n        to issuing all of the C{fetchFlags}, C{fetchInternalDate}, and\n        C{fetchSize} functions.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a dict mapping\n        message numbers to dict of the retrieved data values, or whose\n        errback is invoked if there is an error.  They dictionary keys are\n        \"flags\", \"date\", and \"size\".\n        \"\"\"\n        return self._fetch(\n            messages, useUID=uid, flags=1, internaldate=1, rfc822size=1)\n\n\n    def _parseFetchPairs(self, fetchResponseList):\n        \"\"\"\n        Given the result of parsing a single I{FETCH} response, construct a\n        L{dict} mapping response keys to response values.\n\n        @param fetchResponseList: The result of parsing a I{FETCH} response\n            with L{parseNestedParens} and extracting just the response data\n            (that is, just the part that comes after C{\"FETCH\"}).  The form\n            of this input (and therefore the output of this method) is very\n            disagreeable.  A valuable improvement would be to enumerate the\n            possible keys (representing them as structured objects of some\n            sort) rather than using strings and tuples of tuples of strings\n            and so forth.  This would allow the keys to be documented more\n            easily and would allow for a much simpler application-facing API\n            (one not based on looking up somewhat hard to predict keys in a\n            dict).  Since C{fetchResponseList} notionally represents a\n            flattened sequence of pairs (identifying keys followed by their\n            associated values), collapsing such complex elements of this\n            list as C{[\"BODY\", [\"HEADER.FIELDS\", [\"SUBJECT\"]]]} into a\n            single object would also greatly simplify the implementation of\n            this method.\n\n        @return: A C{dict} of the response data represented by C{pairs}.  Keys\n            in this dictionary are things like C{\"RFC822.TEXT\"}, C{\"FLAGS\"}, or\n            C{(\"BODY\", (\"HEADER.FIELDS\", (\"SUBJECT\",)))}.  Values are entirely\n            dependent on the key with which they are associated, but retain the\n            same structured as produced by L{parseNestedParens}.\n        \"\"\"\n\n        # TODO: RFC 3501 Section 7.4.2, \"FETCH Response\", says for\n        # BODY responses that \"8-bit textual data is permitted if a\n        # charset identifier is part of the body parameter\n        # parenthesized list\".  Every other component is 7-bit.  This\n        # should parse out the charset identifier and use it to decode\n        # 8-bit bodies.  Until then, on Python 2 it should continue to\n        # return native (byte) strings, while on Python 3 it should\n        # decode bytes to native strings via charmap, ensuring data\n        # fidelity at the cost of mojibake.\n        if _PY3:\n            def nativeStringResponse(thing):\n                if isinstance(thing, bytes):\n                    return thing.decode('charmap')\n                elif isinstance(thing, list):\n                    return [nativeStringResponse(subthing)\n                            for subthing in thing]\n        else:\n            def nativeStringResponse(thing):\n                return thing\n\n        values = {}\n        unstructured = []\n\n        responseParts = iter(fetchResponseList)\n        while True:\n            try:\n                key = next(responseParts)\n            except StopIteration:\n                break\n\n            try:\n                value = next(responseParts)\n            except StopIteration:\n                raise IllegalServerResponse(\n                    b\"Not enough arguments\", fetchResponseList)\n\n            # The parsed forms of responses like:\n            #\n            # BODY[] VALUE\n            # BODY[TEXT] VALUE\n            # BODY[HEADER.FIELDS (SUBJECT)] VALUE\n            # BODY[HEADER.FIELDS (SUBJECT)]<N.M> VALUE\n            #\n            # are:\n            #\n            # [\"BODY\", [], VALUE]\n            # [\"BODY\", [\"TEXT\"], VALUE]\n            # [\"BODY\", [\"HEADER.FIELDS\", [\"SUBJECT\"]], VALUE]\n            # [\"BODY\", [\"HEADER.FIELDS\", [\"SUBJECT\"]], \"<N.M>\", VALUE]\n            #\n            # Additionally, BODY responses for multipart messages are\n            # represented as:\n            #\n            #    [\"BODY\", VALUE]\n            #\n            # with list as the type of VALUE and the type of VALUE[0].\n            #\n            # See #6281 for ideas on how this might be improved.\n\n            if key not in (b\"BODY\", b\"BODY.PEEK\"):\n                # Only BODY (and by extension, BODY.PEEK) responses can have\n                # body sections.\n                hasSection = False\n            elif not isinstance(value, list):\n                # A BODY section is always represented as a list.  Any non-list\n                # is not a BODY section.\n                hasSection = False\n            elif len(value) > 2:\n                # The list representing a BODY section has at most two elements.\n                hasSection = False\n            elif value and isinstance(value[0], list):\n                # A list containing a list represents the body structure of a\n                # multipart message, instead.\n                hasSection = False\n            else:\n                # Otherwise it must have a BODY section to examine.\n                hasSection = True\n\n            # If it has a BODY section, grab some extra elements and shuffle\n            # around the shape of the key a little bit.\n\n            key = nativeString(key)\n            unstructured.append(key)\n\n            if hasSection:\n                if len(value) < 2:\n                    value = [nativeString(v) for v in value]\n                    unstructured.append(value)\n\n                    key = (key, tuple(value))\n                else:\n                    valueHead = nativeString(value[0])\n                    valueTail = [nativeString(v) for v in value[1]]\n                    unstructured.append([valueHead, valueTail])\n\n                    key = (key, (valueHead, tuple(valueTail)))\n                try:\n                    value = next(responseParts)\n                except StopIteration:\n                    raise IllegalServerResponse(\n                        b\"Not enough arguments\", fetchResponseList)\n\n                # Handle partial ranges\n                if value.startswith(b'<') and value.endswith(b'>'):\n                    try:\n                        int(value[1:-1])\n                    except ValueError:\n                        # This isn't really a range, it's some content.\n                        pass\n                    else:\n                        value = nativeString(value)\n                        unstructured.append(value)\n                        key = key + (value,)\n                        try:\n                            value = next(responseParts)\n                        except StopIteration:\n                            raise IllegalServerResponse(\n                                b\"Not enough arguments\", fetchResponseList)\n\n            value = nativeStringResponse(value)\n            unstructured.append(value)\n            values[key] = value\n\n        return values, unstructured\n\n\n    def _cbFetch(self, result, requestedParts, structured):\n        (lines, last) = result\n        info = {}\n        for parts in lines:\n            if len(parts) == 3 and parts[1] == b'FETCH':\n                id = self._intOrRaise(parts[0], parts)\n                if id not in info:\n                    info[id] = [parts[2]]\n                else:\n                    info[id][0].extend(parts[2])\n\n        results = {}\n        decodedInfo = {}\n        for (messageId, values) in info.items():\n            structuredMap, unstructuredList = self._parseFetchPairs(values[0])\n            decodedInfo.setdefault(messageId, [[]])[0].extend(unstructuredList)\n            results.setdefault(messageId, {}).update(structuredMap)\n        info = decodedInfo\n\n        flagChanges = {}\n        for messageId in list(results.keys()):\n            values = results[messageId]\n            for part in list(values.keys()):\n                if part not in requestedParts and part == 'FLAGS':\n                    flagChanges[messageId] = values['FLAGS']\n                    # Find flags in the result and get rid of them.\n                    for i in range(len(info[messageId][0])):\n                        if info[messageId][0][i] == 'FLAGS':\n                            del info[messageId][0][i:i+2]\n                            break\n                    del values['FLAGS']\n                    if not values:\n                        del results[messageId]\n\n        if flagChanges:\n            self.flagsChanged(flagChanges)\n\n        if structured:\n            return results\n        else:\n            return info\n\n\n    def fetchSpecific(self, messages, uid=0, headerType=None,\n                      headerNumber=None, headerArgs=None, peek=None,\n                      offset=None, length=None):\n        \"\"\"\n        Retrieve a specific section of one or more messages\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n            numbers or of unique message IDs.\n\n        @type headerType: L{str}\n        @param headerType: If specified, must be one of HEADER, HEADER.FIELDS,\n            HEADER.FIELDS.NOT, MIME, or TEXT, and will determine which part of\n            the message is retrieved.  For HEADER.FIELDS and HEADER.FIELDS.NOT,\n            C{headerArgs} must be a sequence of header names.  For MIME,\n            C{headerNumber} must be specified.\n\n        @type headerNumber: L{int} or L{int} sequence\n        @param headerNumber: The nested rfc822 index specifying the entity to\n            retrieve.  For example, C{1} retrieves the first entity of the\n            message, and C{(2, 1, 3}) retrieves the 3rd entity inside the first\n            entity inside the second entity of the message.\n\n        @type headerArgs: A sequence of L{str}\n        @param headerArgs: If C{headerType} is HEADER.FIELDS, these are the\n            headers to retrieve.  If it is HEADER.FIELDS.NOT, these are the\n            headers to exclude from retrieval.\n\n        @type peek: C{bool}\n        @param peek: If true, cause the server to not set the \\\\Seen flag on\n            this message as a result of this command.\n\n        @type offset: L{int}\n        @param offset: The number of octets at the beginning of the result to\n            skip.\n\n        @type length: L{int}\n        @param length: The number of octets to retrieve.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a mapping of message\n            numbers to retrieved data, or whose errback is invoked if there is\n            an error.\n        \"\"\"\n        fmt = '%s BODY%s[%s%s%s]%s'\n        if headerNumber is None:\n            number = ''\n        elif isinstance(headerNumber, int):\n            number = str(headerNumber)\n        else:\n            number = '.'.join(map(str, headerNumber))\n        if headerType is None:\n            header = ''\n        elif number:\n            header = '.' + headerType\n        else:\n            header = headerType\n        if header and headerType in ('HEADER.FIELDS', 'HEADER.FIELDS.NOT'):\n            if headerArgs is not None:\n                payload = ' (%s)' % ' '.join(headerArgs)\n            else:\n                payload = ' ()'\n        else:\n            payload = ''\n        if offset is None:\n            extra = ''\n        else:\n            extra = '<%d.%d>' % (offset, length)\n        fetch = uid and b'UID FETCH' or b'FETCH'\n        cmd = fmt % (messages, peek and '.PEEK' or '', number, header, payload, extra)\n\n        # APPEND components should be encoded as ASCII unless a\n        # charset identifier is provided.  See #9201.\n        if _PY3:\n            cmd = cmd.encode('charmap')\n\n        d = self.sendCommand(Command(fetch, cmd, wantResponse=(b'FETCH',)))\n        d.addCallback(self._cbFetch, (), False)\n        return d\n\n\n    def _fetch(self, messages, useUID=0, **terms):\n        messages = str(messages).encode('ascii')\n        fetch = useUID and b'UID FETCH' or b'FETCH'\n\n        if 'rfc822text' in terms:\n            del terms['rfc822text']\n            terms['rfc822.text'] = True\n        if 'rfc822size' in terms:\n            del terms['rfc822size']\n            terms['rfc822.size'] = True\n        if 'rfc822header' in terms:\n            del terms['rfc822header']\n            terms['rfc822.header'] = True\n\n        # The terms in 6.4.5 are all ASCII congruent, so wing it.\n        # Note that this isn't a public API, so terms in responses\n        # should not be decoded to native strings.\n        encodedTerms = [networkString(s) for s in terms]\n        cmd = messages + b' (' + b' '.join(\n            [s.upper() for s in encodedTerms]\n        ) + b')'\n\n        d = self.sendCommand(Command(fetch, cmd, wantResponse=(b'FETCH',)))\n        d.addCallback(self._cbFetch, [t.upper() for t in terms.keys()], True)\n        return d\n\n\n    def setFlags(self, messages, flags, silent=1, uid=0):\n        \"\"\"\n        Set the flags for one or more messages.\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type flags: Any iterable of L{str}\n        @param flags: The flags to set\n\n        @type silent: L{bool}\n        @param silent: If true, cause the server to suppress its verbose\n        response.\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a list of the\n        server's responses (C{[]} if C{silent} is true) or whose\n        errback is invoked if there is an error.\n        \"\"\"\n        return self._store(messages, b'FLAGS', silent, flags, uid)\n\n\n    def addFlags(self, messages, flags, silent=1, uid=0):\n        \"\"\"\n        Add to the set flags for one or more messages.\n\n        This command is allowed in the Selected state.\n\n        @type messages: C{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type flags: Any iterable of L{str}\n        @param flags: The flags to set\n\n        @type silent: C{bool}\n        @param silent: If true, cause the server to suppress its verbose\n        response.\n\n        @type uid: C{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a list of the\n        server's responses (C{[]} if C{silent} is true) or whose\n        errback is invoked if there is an error.\n        \"\"\"\n        return self._store(messages, b'+FLAGS', silent, flags, uid)\n\n\n    def removeFlags(self, messages, flags, silent=1, uid=0):\n        \"\"\"\n        Remove from the set flags for one or more messages.\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type flags: Any iterable of L{str}\n        @param flags: The flags to set\n\n        @type silent: L{bool}\n        @param silent: If true, cause the server to suppress its verbose\n        response.\n\n        @type uid: L{bool}\n        @param uid: Indicates whether the message sequence set is of message\n        numbers or of unique message IDs.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a list of the\n        server's responses (C{[]} if C{silent} is true) or whose\n        errback is invoked if there is an error.\n        \"\"\"\n        return self._store(messages, b'-FLAGS', silent, flags, uid)\n\n\n    def _store(self, messages, cmd, silent, flags, uid):\n        messages = str(messages).encode('ascii')\n        encodedFlags = [networkString(flag) for flag in flags]\n        if silent:\n            cmd = cmd + b'.SILENT'\n        store = uid and b'UID STORE' or b'STORE'\n        args = b' '.join((messages, cmd, b'('+ b' '.join(encodedFlags) + b')'))\n        d = self.sendCommand(Command(store, args, wantResponse=(b'FETCH',)))\n        expected = ()\n        if not silent:\n            expected = ('FLAGS',)\n        d.addCallback(self._cbFetch, expected, True)\n        return d\n\n\n    def copy(self, messages, mailbox, uid):\n        \"\"\"\n        Copy the specified messages to the specified mailbox.\n\n        This command is allowed in the Selected state.\n\n        @type messages: L{MessageSet} or L{str}\n        @param messages: A message sequence set\n\n        @type mailbox: L{str}\n        @param mailbox: The mailbox to which to copy the messages\n\n        @type uid: C{bool}\n        @param uid: If true, the C{messages} refers to message UIDs, rather\n        than message sequence numbers.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with a true value\n        when the copy is successful, or whose errback is invoked if there\n        is an error.\n        \"\"\"\n        messages = str(messages).encode('ascii')\n        if uid:\n            cmd = b'UID COPY'\n        else:\n            cmd = b'COPY'\n        args = b' '.join([messages, _prepareMailboxName(mailbox)])\n        return self.sendCommand(Command(cmd, args))\n\n    #\n    # IMailboxListener methods\n    #\n    def modeChanged(self, writeable):\n        \"\"\"Override me\"\"\"\n\n    def flagsChanged(self, newFlags):\n        \"\"\"Override me\"\"\"\n\n    def newMessages(self, exists, recent):\n        \"\"\"Override me\"\"\"\n\n\n\ndef parseIdList(s, lastMessageId=None):\n    \"\"\"\n    Parse a message set search key into a C{MessageSet}.\n\n    @type s: L{bytes}\n    @param s: A string description of an id list, for example \"1:3, 4:*\"\n\n    @type lastMessageId: L{int}\n    @param lastMessageId: The last message sequence id or UID, depending on\n        whether we are parsing the list in UID or sequence id context. The\n        caller should pass in the correct value.\n\n    @rtype: C{MessageSet}\n    @return: A C{MessageSet} that contains the ids defined in the list\n    \"\"\"\n    res = MessageSet()\n    parts = s.split(b',')\n    for p in parts:\n        if b':' in p:\n            low, high = p.split(b':', 1)\n            try:\n                if low == b'*':\n                    low = None\n                else:\n                    low = int(low)\n                if high == b'*':\n                    high = None\n                else:\n                    high = int(high)\n                if low is high is None:\n                    # *:* does not make sense\n                    raise IllegalIdentifierError(p)\n                # non-positive values are illegal according to RFC 3501\n                if ((low is not None and low <= 0) or\n                    (high is not None and high <= 0)):\n                    raise IllegalIdentifierError(p)\n                # star means \"highest value of an id in the mailbox\"\n                high = high or lastMessageId\n                low = low or lastMessageId\n\n                res.add(low, high)\n            except ValueError:\n                raise IllegalIdentifierError(p)\n        else:\n            try:\n                if p == b'*':\n                    p = None\n                else:\n                    p = int(p)\n                if p is not None and p <= 0:\n                    raise IllegalIdentifierError(p)\n            except ValueError:\n                raise IllegalIdentifierError(p)\n            else:\n                res.extend(p or lastMessageId)\n    return res\n\n\n\n_SIMPLE_BOOL = (\n    'ALL', 'ANSWERED', 'DELETED', 'DRAFT', 'FLAGGED', 'NEW', 'OLD',\n    'RECENT', 'SEEN', 'UNANSWERED', 'UNDELETED', 'UNDRAFT', 'UNFLAGGED',\n    'UNSEEN'\n)\n\n_NO_QUOTES = (\n    'LARGER', 'SMALLER', 'UID'\n)\n\n_sorted = sorted\n\ndef Query(sorted=0, **kwarg):\n    \"\"\"\n    Create a query string\n\n    Among the accepted keywords are::\n\n        all         : If set to a true value, search all messages in the\n                      current mailbox\n\n        answered    : If set to a true value, search messages flagged with\n                      \\\\Answered\n\n        bcc         : A substring to search the BCC header field for\n\n        before      : Search messages with an internal date before this\n                      value.  The given date should be a string in the format\n                      of 'DD-Mon-YYYY'.  For example, '03-Mar-2003'.\n\n        body        : A substring to search the body of the messages for\n\n        cc          : A substring to search the CC header field for\n\n        deleted     : If set to a true value, search messages flagged with\n                      \\\\Deleted\n\n        draft       : If set to a true value, search messages flagged with\n                      \\\\Draft\n\n        flagged     : If set to a true value, search messages flagged with\n                      \\\\Flagged\n\n        from        : A substring to search the From header field for\n\n        header      : A two-tuple of a header name and substring to search\n                      for in that header\n\n        keyword     : Search for messages with the given keyword set\n\n        larger      : Search for messages larger than this number of octets\n\n        messages    : Search only the given message sequence set.\n\n        new         : If set to a true value, search messages flagged with\n                      \\\\Recent but not \\\\Seen\n\n        old         : If set to a true value, search messages not flagged with\n                      \\\\Recent\n\n        on          : Search messages with an internal date which is on this\n                      date.  The given date should be a string in the format\n                      of 'DD-Mon-YYYY'.  For example, '03-Mar-2003'.\n\n        recent      : If set to a true value, search for messages flagged with\n                      \\\\Recent\n\n        seen        : If set to a true value, search for messages flagged with\n                      \\\\Seen\n\n        sentbefore  : Search for messages with an RFC822 'Date' header before\n                      this date.  The given date should be a string in the format\n                      of 'DD-Mon-YYYY'.  For example, '03-Mar-2003'.\n\n        senton      : Search for messages with an RFC822 'Date' header which is\n                      on this date  The given date should be a string in the format\n                      of 'DD-Mon-YYYY'.  For example, '03-Mar-2003'.\n\n        sentsince   : Search for messages with an RFC822 'Date' header which is\n                      after this date.  The given date should be a string in the format\n                      of 'DD-Mon-YYYY'.  For example, '03-Mar-2003'.\n\n        since       : Search for messages with an internal date that is after\n                      this date..  The given date should be a string in the format\n                      of 'DD-Mon-YYYY'.  For example, '03-Mar-2003'.\n\n        smaller     : Search for messages smaller than this number of octets\n\n        subject     : A substring to search the 'subject' header for\n\n        text        : A substring to search the entire message for\n\n        to          : A substring to search the 'to' header for\n\n        uid         : Search only the messages in the given message set\n\n        unanswered  : If set to a true value, search for messages not\n                      flagged with \\\\Answered\n\n        undeleted   : If set to a true value, search for messages not\n                      flagged with \\\\Deleted\n\n        undraft     : If set to a true value, search for messages not\n                      flagged with \\\\Draft\n\n        unflagged   : If set to a true value, search for messages not\n                      flagged with \\\\Flagged\n\n        unkeyword   : Search for messages without the given keyword set\n\n        unseen      : If set to a true value, search for messages not\n                      flagged with \\\\Seen\n\n    @type sorted: C{bool}\n    @param sorted: If true, the output will be sorted, alphabetically.\n    The standard does not require it, but it makes testing this function\n    easier.  The default is zero, and this should be acceptable for any\n    application.\n\n    @rtype: L{str}\n    @return: The formatted query string\n    \"\"\"\n    cmd = []\n    keys = kwarg.keys()\n    if sorted:\n        keys = _sorted(keys)\n    for k in keys:\n        v = kwarg[k]\n        k = k.upper()\n        if k in _SIMPLE_BOOL and v:\n            cmd.append(k)\n        elif k == 'HEADER':\n            cmd.extend([k, str(v[0]), str(v[1])])\n        elif k == 'KEYWORD' or k == 'UNKEYWORD':\n            # Discard anything that does not fit into an \"atom\".  Perhaps turn\n            # the case where this actually removes bytes from the value into a\n            # warning and then an error, eventually.  See #6277.\n            v = _nonAtomRE.sub(\"\", v)\n            cmd.extend([k, v])\n        elif k not in _NO_QUOTES:\n            if isinstance(v, MessageSet):\n                fmt = '\"%s\"'\n            elif isinstance(v, str):\n                fmt = '\"%s\"'\n            else:\n                fmt = '\"%d\"'\n            cmd.extend([k, fmt % (v,)])\n        elif isinstance(v, int):\n            cmd.extend([k, '%d' % (v,)])\n        else:\n            cmd.extend([k, '%s' % (v,)])\n    if len(cmd) > 1:\n        return '(' + ' '.join(cmd) + ')'\n    else:\n        return ' '.join(cmd)\n\n\n\ndef Or(*args):\n    \"\"\"\n    The disjunction of two or more queries\n    \"\"\"\n    if len(args) < 2:\n        raise IllegalQueryError(args)\n    elif len(args) == 2:\n        return '(OR %s %s)' % args\n    else:\n        return '(OR %s %s)' % (args[0], Or(*args[1:]))\n\ndef Not(query):\n    \"\"\"The negation of a query\"\"\"\n    return '(NOT %s)' % (query,)\n\n\ndef wildcardToRegexp(wildcard, delim=None):\n    wildcard = wildcard.replace('*', '(?:.*?)')\n    if delim is None:\n        wildcard = wildcard.replace('%', '(?:.*?)')\n    else:\n        wildcard = wildcard.replace('%', '(?:(?:[^%s])*?)' % re.escape(delim))\n    return re.compile(wildcard, re.I)\n\n\n\ndef splitQuoted(s):\n    \"\"\"\n    Split a string into whitespace delimited tokens\n\n    Tokens that would otherwise be separated but are surrounded by \\\"\n    remain as a single token.  Any token that is not quoted and is\n    equal to \\\"NIL\\\" is tokenized as L{None}.\n\n    @type s: L{bytes}\n    @param s: The string to be split\n\n    @rtype: L{list} of L{bytes}\n    @return: A list of the resulting tokens\n\n    @raise MismatchedQuoting: Raised if an odd number of quotes are present\n    \"\"\"\n    s = s.strip()\n    result = []\n    word = []\n    inQuote = inWord = False\n    qu = _matchingString('\"', s)\n    esc = _matchingString('\\x5c', s)\n    empty = _matchingString('', s)\n    nil = _matchingString('NIL', s)\n    for i, c in enumerate(iterbytes(s)):\n        if c == qu:\n            if i and s[i-1:i] == esc:\n                word.pop()\n                word.append(qu)\n            elif not inQuote:\n                inQuote = True\n            else:\n                inQuote = False\n                result.append(empty.join(word))\n                word = []\n        elif (\n                not inWord and not inQuote and\n                c not in (qu + (string.whitespace.encode(\"ascii\")))\n        ):\n            inWord = True\n            word.append(c)\n        elif inWord and not inQuote and c in string.whitespace.encode(\"ascii\"):\n            w = empty.join(word)\n            if w == nil:\n                result.append(None)\n            else:\n                result.append(w)\n            word = []\n            inWord = False\n        elif inWord or inQuote:\n            word.append(c)\n\n    if inQuote:\n        raise MismatchedQuoting(s)\n    if inWord:\n        w = empty.join(word)\n        if w == nil:\n            result.append(None)\n        else:\n            result.append(w)\n\n    return result\n\n\n\ndef splitOn(sequence, predicate, transformers):\n    result = []\n    mode = predicate(sequence[0])\n    tmp = [sequence[0]]\n    for e in sequence[1:]:\n        p = predicate(e)\n        if p != mode:\n            result.extend(transformers[mode](tmp))\n            tmp = [e]\n            mode = p\n        else:\n            tmp.append(e)\n    result.extend(transformers[mode](tmp))\n    return result\n\n\n\ndef collapseStrings(results):\n    \"\"\"\n    Turns a list of length-one strings and lists into a list of longer\n    strings and lists.  For example,\n\n    ['a', 'b', ['c', 'd']] is returned as ['ab', ['cd']]\n\n    @type results: L{list} of L{bytes} and L{list}\n    @param results: The list to be collapsed\n\n    @rtype: L{list} of L{bytes} and L{list}\n    @return: A new list which is the collapsed form of C{results}\n    \"\"\"\n    copy = []\n    begun = None\n\n    pred = lambda e: isinstance(e, tuple)\n    tran = {\n        0: lambda e: splitQuoted(b''.join(e)),\n        1: lambda e: [b''.join([i[0] for i in e])]\n    }\n    for i, c in enumerate(results):\n        if isinstance(c, list):\n            if begun is not None:\n                copy.extend(splitOn(results[begun:i], pred, tran))\n                begun = None\n            copy.append(collapseStrings(c))\n        elif begun is None:\n            begun = i\n    if begun is not None:\n        copy.extend(splitOn(results[begun:], pred, tran))\n    return copy\n\n\n\ndef parseNestedParens(s, handleLiteral = 1):\n    \"\"\"\n    Parse an s-exp-like string into a more useful data structure.\n\n    @type s: L{bytes}\n    @param s: The s-exp-like string to parse\n\n    @rtype: L{list} of L{bytes} and L{list}\n    @return: A list containing the tokens present in the input.\n\n    @raise MismatchedNesting: Raised if the number or placement\n    of opening or closing parenthesis is invalid.\n    \"\"\"\n    s = s.strip()\n    inQuote = 0\n    contentStack = [[]]\n    try:\n        i = 0\n        L = len(s)\n        while i < L:\n            c = s[i:i+1]\n            if inQuote:\n                if c == b'\\\\':\n                    contentStack[-1].append(s[i:i+2])\n                    i += 2\n                    continue\n                elif c == b'\"':\n                    inQuote = not inQuote\n                contentStack[-1].append(c)\n                i += 1\n            else:\n                if c == b'\"':\n                    contentStack[-1].append(c)\n                    inQuote = not inQuote\n                    i += 1\n                elif handleLiteral and c == b'{':\n                    end = s.find(b'}', i)\n                    if end == -1:\n                        raise ValueError(\"Malformed literal\")\n                    literalSize = int(s[i+1:end])\n                    contentStack[-1].append((s[end+3:end+3+literalSize],))\n                    i = end + 3 + literalSize\n                elif c == b'(' or c == b'[':\n                    contentStack.append([])\n                    i += 1\n                elif c == b')' or c == b']':\n                    contentStack[-2].append(contentStack.pop())\n                    i += 1\n                else:\n                    contentStack[-1].append(c)\n                    i += 1\n    except IndexError:\n        raise MismatchedNesting(s)\n    if len(contentStack) != 1:\n        raise MismatchedNesting(s)\n    return collapseStrings(contentStack[0])\n\n\n\ndef _quote(s):\n    qu = _matchingString('\"', s)\n    esc = _matchingString('\\x5c', s)\n    return qu + s.replace(esc, esc + esc).replace(qu, esc + qu) + qu\n\n\n\ndef _literal(s):\n    return b'{' + intToBytes(len(s)) + b'}\\r\\n' + s\n\n\n\nclass DontQuoteMe:\n    def __init__(self, value):\n        self.value = value\n\n\n    def __str__(self):\n        return str(self.value)\n\n\n\n_ATOM_SPECIALS = b'(){ %*\"'\ndef _needsQuote(s):\n    if s == b'':\n        return 1\n    for c in iterbytes(s):\n        if c < b'\\x20' or c > b'\\x7f':\n            return 1\n        if c in _ATOM_SPECIALS:\n            return 1\n    return 0\n\n\n\ndef _parseMbox(name):\n    if isinstance(name, unicode):\n        return name\n    try:\n        return name.decode('imap4-utf-7')\n    except:\n        log.err()\n        raise IllegalMailboxEncoding(name)\n\n\n\ndef _prepareMailboxName(name):\n    if not isinstance(name, unicode):\n        name = name.decode(\"charmap\")\n    name = name.encode('imap4-utf-7')\n    if _needsQuote(name):\n        return _quote(name)\n    return name\n\n\n\n\ndef _needsLiteral(s):\n    # change this to \"return 1\" to wig out stupid clients\n    cr = _matchingString(\"\\n\", s)\n    lf = _matchingString(\"\\r\", s)\n    return cr in s or lf in s or len(s) > 1000\n\n\n\ndef collapseNestedLists(items):\n    \"\"\"\n    Turn a nested list structure into an s-exp-like string.\n\n    Strings in C{items} will be sent as literals if they contain CR or LF,\n    otherwise they will be quoted.  References to None in C{items} will be\n    translated to the atom NIL.  Objects with a 'read' attribute will have\n    it called on them with no arguments and the returned string will be\n    inserted into the output as a literal.  Integers will be converted to\n    strings and inserted into the output unquoted.  Instances of\n    C{DontQuoteMe} will be converted to strings and inserted into the output\n    unquoted.\n\n    This function used to be much nicer, and only quote things that really\n    needed to be quoted (and C{DontQuoteMe} did not exist), however, many\n    broken IMAP4 clients were unable to deal with this level of sophistication,\n    forcing the current behavior to be adopted for practical reasons.\n\n    @type items: Any iterable\n\n    @rtype: L{str}\n    \"\"\"\n    pieces = []\n    for i in items:\n        if isinstance(i, unicode):\n            # anything besides ASCII will have to wait for an RFC 5738\n            # implementation.  See\n            # https://twistedmatrix.com/trac/ticket/9258\n            i = i.encode(\"ascii\")\n        if i is None:\n            pieces.extend([b' ', b'NIL'])\n        elif isinstance(i, (int, long)):\n            pieces.extend([b' ', networkString(str(i))])\n        elif isinstance(i, DontQuoteMe):\n            pieces.extend([b' ', i.value])\n        elif isinstance(i, bytes):\n            # XXX warning\n            if _needsLiteral(i):\n                pieces.extend([b' ', b'{', intToBytes(len(i)), b'}',\n                               IMAP4Server.delimiter, i])\n            else:\n                pieces.extend([b' ', _quote(i)])\n        elif hasattr(i, 'read'):\n            d = i.read()\n            pieces.extend([b' ', b'{', intToBytes(len(d)), b'}',\n                           IMAP4Server.delimiter, d])\n        else:\n            pieces.extend([b' ', b'(' + collapseNestedLists(i) + b')'])\n    return b''.join(pieces[1:])\n\n\n\n@implementer(IAccount)\nclass MemoryAccountWithoutNamespaces(object):\n    mailboxes = None\n    subscriptions = None\n    top_id = 0\n\n    def __init__(self, name):\n        self.name = name\n        self.mailboxes = {}\n        self.subscriptions = []\n\n\n    def allocateID(self):\n        id = self.top_id\n        self.top_id += 1\n        return id\n\n\n    ##\n    ## IAccount\n    ##\n    def addMailbox(self, name, mbox = None):\n        name = _parseMbox(name.upper())\n        if name in self.mailboxes:\n            raise MailboxCollision(name)\n        if mbox is None:\n            mbox = self._emptyMailbox(name, self.allocateID())\n        self.mailboxes[name] = mbox\n        return 1\n\n\n    def create(self, pathspec):\n        paths = [path for path in pathspec.split('/') if path]\n        for accum in range(1, len(paths)):\n            try:\n                self.addMailbox('/'.join(paths[:accum]))\n            except MailboxCollision:\n                pass\n        try:\n            self.addMailbox('/'.join(paths))\n        except MailboxCollision:\n            if not pathspec.endswith('/'):\n                return False\n        return True\n\n\n    def _emptyMailbox(self, name, id):\n        raise NotImplementedError\n\n\n    def select(self, name, readwrite=1):\n        return self.mailboxes.get(_parseMbox(name.upper()))\n\n\n    def delete(self, name):\n        name = _parseMbox(name.upper())\n        # See if this mailbox exists at all\n        mbox = self.mailboxes.get(name)\n        if not mbox:\n            raise MailboxException(\"No such mailbox\")\n        # See if this box is flagged \\Noselect\n        if r'\\Noselect' in mbox.getFlags():\n            # Check for hierarchically inferior mailboxes with this one\n            # as part of their root.\n            for others in self.mailboxes.keys():\n                if others != name and others.startswith(name):\n                    raise MailboxException(\"Hierarchically inferior mailboxes exist and \\\\Noselect is set\")\n        mbox.destroy()\n\n        # iff there are no hierarchically inferior names, we will\n        # delete it from our ken.\n        if len(self._inferiorNames(name)) > 1:\n            raise MailboxException(\n                'Name \"%s\" has inferior hierarchical names' % (name,))\n        del self.mailboxes[name]\n\n\n    def rename(self, oldname, newname):\n        oldname = _parseMbox(oldname.upper())\n        newname = _parseMbox(newname.upper())\n        if oldname not in self.mailboxes:\n            raise NoSuchMailbox(oldname)\n\n        inferiors = self._inferiorNames(oldname)\n        inferiors = [(o, o.replace(oldname, newname, 1)) for o in inferiors]\n\n        for (old, new) in inferiors:\n            if new in self.mailboxes:\n                raise MailboxCollision(new)\n\n        for (old, new) in inferiors:\n            self.mailboxes[new] = self.mailboxes[old]\n            del self.mailboxes[old]\n\n\n    def _inferiorNames(self, name):\n        inferiors = []\n        for infname in self.mailboxes.keys():\n            if infname.startswith(name):\n                inferiors.append(infname)\n        return inferiors\n\n\n    def isSubscribed(self, name):\n        return _parseMbox(name.upper()) in self.subscriptions\n\n\n    def subscribe(self, name):\n        name = _parseMbox(name.upper())\n        if name not in self.subscriptions:\n            self.subscriptions.append(name)\n\n\n    def unsubscribe(self, name):\n        name = _parseMbox(name.upper())\n        if name not in self.subscriptions:\n            raise MailboxException(\"Not currently subscribed to %s\" % (name,))\n        self.subscriptions.remove(name)\n\n\n    def listMailboxes(self, ref, wildcard):\n        ref = self._inferiorNames(_parseMbox(ref.upper()))\n        wildcard = wildcardToRegexp(wildcard, '/')\n        return [(i, self.mailboxes[i]) for i in ref if wildcard.match(i)]\n\n\n@implementer(INamespacePresenter)\nclass MemoryAccount(MemoryAccountWithoutNamespaces):\n    ##\n    ## INamespacePresenter\n    ##\n    def getPersonalNamespaces(self):\n        return [[b\"\", b\"/\"]]\n\n\n    def getSharedNamespaces(self):\n        return None\n\n\n    def getOtherNamespaces(self):\n        return None\n\n\n\n_statusRequestDict = {\n    'MESSAGES': 'getMessageCount',\n    'RECENT': 'getRecentCount',\n    'UIDNEXT': 'getUIDNext',\n    'UIDVALIDITY': 'getUIDValidity',\n    'UNSEEN': 'getUnseenCount'\n}\n\ndef statusRequestHelper(mbox, names):\n    r = {}\n    for n in names:\n        r[n] = getattr(mbox, _statusRequestDict[n.upper()])()\n    return r\n\n\n\ndef parseAddr(addr):\n    if addr is None:\n        return [(None, None, None),]\n    addr = email.utils.getaddresses([addr])\n    return [[fn or None, None] + address.split('@') for fn, address in addr]\n\n\n\ndef getEnvelope(msg):\n    headers = msg.getHeaders(True)\n    date = headers.get('date')\n    subject = headers.get('subject')\n    from_ = headers.get('from')\n    sender = headers.get('sender', from_)\n    reply_to = headers.get('reply-to', from_)\n    to = headers.get('to')\n    cc = headers.get('cc')\n    bcc = headers.get('bcc')\n    in_reply_to = headers.get('in-reply-to')\n    mid = headers.get('message-id')\n    return (date, subject, parseAddr(from_), parseAddr(sender),\n            reply_to and parseAddr(reply_to), to and parseAddr(to),\n            cc and parseAddr(cc), bcc and parseAddr(bcc), in_reply_to, mid)\n\n\n\ndef getLineCount(msg):\n    # XXX - Super expensive, CACHE THIS VALUE FOR LATER RE-USE\n    # XXX - This must be the number of lines in the ENCODED version\n    lines = 0\n    for _ in msg.getBodyFile():\n        lines += 1\n    return lines\n\n\n\ndef unquote(s):\n    if s[0] == s[-1] == '\"':\n        return s[1:-1]\n    return s\n\n\n\ndef _getContentType(msg):\n    \"\"\"\n    Return a two-tuple of the main and subtype of the given message.\n    \"\"\"\n    attrs = None\n    mm = msg.getHeaders(False, 'content-type').get('content-type', '')\n    mm = ''.join(mm.splitlines())\n    if mm:\n        mimetype = mm.split(';')\n        type = mimetype[0].split('/', 1)\n        if len(type) == 1:\n            major = type[0]\n            minor = None\n        else:\n            # length must be 2, because of split('/', 1)\n            major, minor = type\n        attrs = dict(x.strip().lower().split('=', 1) for x in mimetype[1:])\n    else:\n        major = minor = None\n    return major, minor, attrs\n\n\n\ndef _getMessageStructure(message):\n    \"\"\"\n    Construct an appropriate type of message structure object for the given\n    message object.\n\n    @param message: A L{IMessagePart} provider\n\n    @return: A L{_MessageStructure} instance of the most specific type available\n        for the given message, determined by inspecting the MIME type of the\n        message.\n    \"\"\"\n    main, subtype, attrs = _getContentType(message)\n    if main is not None:\n        main = main.lower()\n    if subtype is not None:\n        subtype = subtype.lower()\n    if main == 'multipart':\n        return _MultipartMessageStructure(message, subtype, attrs)\n    elif (main, subtype) == ('message', 'rfc822'):\n        return _RFC822MessageStructure(message, main, subtype, attrs)\n    elif main == 'text':\n        return _TextMessageStructure(message, main, subtype, attrs)\n    else:\n        return _SinglepartMessageStructure(message, main, subtype, attrs)\n\n\n\nclass _MessageStructure(object):\n    \"\"\"\n    L{_MessageStructure} is a helper base class for message structure classes\n    representing the structure of particular kinds of messages, as defined by\n    their MIME type.\n    \"\"\"\n    def __init__(self, message, attrs):\n        \"\"\"\n        @param message: An L{IMessagePart} provider which this structure object\n            reports on.\n\n        @param attrs: A C{dict} giving the parameters of the I{Content-Type}\n            header of the message.\n        \"\"\"\n        self.message = message\n        self.attrs = attrs\n\n\n    def _disposition(self, disp):\n        \"\"\"\n        Parse a I{Content-Disposition} header into a two-sequence of the\n        disposition and a flattened list of its parameters.\n\n        @return: L{None} if there is no disposition header value, a L{list} with\n            two elements otherwise.\n        \"\"\"\n        if disp:\n            disp = disp.split('; ')\n            if len(disp) == 1:\n                disp = (disp[0].lower(), None)\n            elif len(disp) > 1:\n                # XXX Poorly tested parser\n                params = [x for param in disp[1:] for x in param.split('=', 1)]\n                disp = [disp[0].lower(), params]\n            return disp\n        else:\n            return None\n\n\n    def _unquotedAttrs(self):\n        \"\"\"\n        @return: The I{Content-Type} parameters, unquoted, as a flat list with\n            each Nth element giving a parameter name and N+1th element giving\n            the corresponding parameter value.\n        \"\"\"\n        if self.attrs:\n            unquoted = [(k, unquote(v)) for (k, v) in self.attrs.items()]\n            return [y for x in sorted(unquoted) for y in x]\n        return None\n\n\n\nclass _SinglepartMessageStructure(_MessageStructure):\n    \"\"\"\n    L{_SinglepartMessageStructure} represents the message structure of a\n    non-I{multipart/*} message.\n    \"\"\"\n    _HEADERS = [\n        'content-id', 'content-description',\n        'content-transfer-encoding']\n\n    def __init__(self, message, main, subtype, attrs):\n        \"\"\"\n        @param message: An L{IMessagePart} provider which this structure object\n            reports on.\n\n        @param main: A L{str} giving the main MIME type of the message (for\n            example, C{\"text\"}).\n\n        @param subtype: A L{str} giving the MIME subtype of the message (for\n            example, C{\"plain\"}).\n\n        @param attrs: A C{dict} giving the parameters of the I{Content-Type}\n            header of the message.\n        \"\"\"\n        _MessageStructure.__init__(self, message, attrs)\n        self.main = main\n        self.subtype = subtype\n        self.attrs = attrs\n\n\n    def _basicFields(self):\n        \"\"\"\n        Return a list of the basic fields for a single-part message.\n        \"\"\"\n        headers = self.message.getHeaders(False, *self._HEADERS)\n\n        # Number of octets total\n        size = self.message.getSize()\n\n        major, minor = self.main, self.subtype\n\n        # content-type parameter list\n        unquotedAttrs = self._unquotedAttrs()\n\n        return [\n            major, minor, unquotedAttrs,\n            headers.get('content-id'),\n            headers.get('content-description'),\n            headers.get('content-transfer-encoding'),\n            size,\n            ]\n\n\n    def encode(self, extended):\n        \"\"\"\n        Construct and return a list of the basic and extended fields for a\n        single-part message.  The list suitable to be encoded into a BODY or\n        BODYSTRUCTURE response.\n        \"\"\"\n        result = self._basicFields()\n        if extended:\n            result.extend(self._extended())\n        return result\n\n\n    def _extended(self):\n        \"\"\"\n        The extension data of a non-multipart body part are in the\n        following order:\n\n          1. body MD5\n\n             A string giving the body MD5 value as defined in [MD5].\n\n          2. body disposition\n\n             A parenthesized list with the same content and function as\n             the body disposition for a multipart body part.\n\n          3. body language\n\n             A string or parenthesized list giving the body language\n             value as defined in [LANGUAGE-TAGS].\n\n          4. body location\n\n             A string list giving the body content URI as defined in\n             [LOCATION].\n\n        \"\"\"\n        result = []\n        headers = self.message.getHeaders(\n            False, 'content-md5', 'content-disposition',\n            'content-language', 'content-language')\n\n        result.append(headers.get('content-md5'))\n        result.append(self._disposition(headers.get('content-disposition')))\n        result.append(headers.get('content-language'))\n        result.append(headers.get('content-location'))\n\n        return result\n\n\n\nclass _TextMessageStructure(_SinglepartMessageStructure):\n    \"\"\"\n    L{_TextMessageStructure} represents the message structure of a I{text/*}\n    message.\n    \"\"\"\n    def encode(self, extended):\n        \"\"\"\n        A body type of type TEXT contains, immediately after the basic\n        fields, the size of the body in text lines.  Note that this\n        size is the size in its content transfer encoding and not the\n        resulting size after any decoding.\n        \"\"\"\n        result = _SinglepartMessageStructure._basicFields(self)\n        result.append(getLineCount(self.message))\n        if extended:\n            result.extend(self._extended())\n        return result\n\n\n\nclass _RFC822MessageStructure(_SinglepartMessageStructure):\n    \"\"\"\n    L{_RFC822MessageStructure} represents the message structure of a\n    I{message/rfc822} message.\n    \"\"\"\n    def encode(self, extended):\n        \"\"\"\n        A body type of type MESSAGE and subtype RFC822 contains,\n        immediately after the basic fields, the envelope structure,\n        body structure, and size in text lines of the encapsulated\n        message.\n        \"\"\"\n        result = _SinglepartMessageStructure.encode(self, extended)\n        contained = self.message.getSubPart(0)\n        result.append(getEnvelope(contained))\n        result.append(getBodyStructure(contained, False))\n        result.append(getLineCount(contained))\n        return result\n\n\n\nclass _MultipartMessageStructure(_MessageStructure):\n    \"\"\"\n    L{_MultipartMessageStructure} represents the message structure of a\n    I{multipart/*} message.\n    \"\"\"\n    def __init__(self, message, subtype, attrs):\n        \"\"\"\n        @param message: An L{IMessagePart} provider which this structure object\n            reports on.\n\n        @param subtype: A L{str} giving the MIME subtype of the message (for\n            example, C{\"plain\"}).\n\n        @param attrs: A C{dict} giving the parameters of the I{Content-Type}\n            header of the message.\n        \"\"\"\n        _MessageStructure.__init__(self, message, attrs)\n        self.subtype = subtype\n\n\n    def _getParts(self):\n        \"\"\"\n        Return an iterator over all of the sub-messages of this message.\n        \"\"\"\n        i = 0\n        while True:\n            try:\n                part = self.message.getSubPart(i)\n            except IndexError:\n                break\n            else:\n                yield part\n                i += 1\n\n\n    def encode(self, extended):\n        \"\"\"\n        Encode each sub-message and added the additional I{multipart} fields.\n        \"\"\"\n        result = [_getMessageStructure(p).encode(extended) for p in self._getParts()]\n        result.append(self.subtype)\n        if extended:\n            result.extend(self._extended())\n        return result\n\n\n    def _extended(self):\n        \"\"\"\n        The extension data of a multipart body part are in the following order:\n\n          1. body parameter parenthesized list\n               A parenthesized list of attribute/value pairs [e.g., (\"foo\"\n               \"bar\" \"baz\" \"rag\") where \"bar\" is the value of \"foo\", and\n               \"rag\" is the value of \"baz\"] as defined in [MIME-IMB].\n\n          2. body disposition\n               A parenthesized list, consisting of a disposition type\n               string, followed by a parenthesized list of disposition\n               attribute/value pairs as defined in [DISPOSITION].\n\n          3. body language\n               A string or parenthesized list giving the body language\n               value as defined in [LANGUAGE-TAGS].\n\n          4. body location\n               A string list giving the body content URI as defined in\n               [LOCATION].\n        \"\"\"\n        result = []\n        headers = self.message.getHeaders(\n            False, 'content-language', 'content-location',\n            'content-disposition')\n\n        result.append(self._unquotedAttrs())\n        result.append(self._disposition(headers.get('content-disposition')))\n        result.append(headers.get('content-language', None))\n        result.append(headers.get('content-location', None))\n\n        return result\n\n\n\ndef getBodyStructure(msg, extended=False):\n    \"\"\"\n    RFC 3501, 7.4.2, BODYSTRUCTURE::\n\n      A parenthesized list that describes the [MIME-IMB] body structure of a\n      message.  This is computed by the server by parsing the [MIME-IMB] header\n      fields, defaulting various fields as necessary.\n\n        For example, a simple text message of 48 lines and 2279 octets can have\n        a body structure of: (\"TEXT\" \"PLAIN\" (\"CHARSET\" \"US-ASCII\") NIL NIL\n        \"7BIT\" 2279 48)\n\n    This is represented as::\n\n        [\"TEXT\", \"PLAIN\", [\"CHARSET\", \"US-ASCII\"], None, None, \"7BIT\", 2279, 48]\n\n    These basic fields are documented in the RFC as:\n\n      1. body type\n\n         A string giving the content media type name as defined in\n         [MIME-IMB].\n\n      2. body subtype\n\n         A string giving the content subtype name as defined in\n         [MIME-IMB].\n\n      3. body parameter parenthesized list\n\n         A parenthesized list of attribute/value pairs [e.g., (\"foo\"\n         \"bar\" \"baz\" \"rag\") where \"bar\" is the value of \"foo\" and\n         \"rag\" is the value of \"baz\"] as defined in [MIME-IMB].\n\n      4. body id\n\n         A string giving the content id as defined in [MIME-IMB].\n\n      5. body description\n\n         A string giving the content description as defined in\n         [MIME-IMB].\n\n      6. body encoding\n\n         A string giving the content transfer encoding as defined in\n         [MIME-IMB].\n\n      7. body size\n\n         A number giving the size of the body in octets.  Note that this size is\n         the size in its transfer encoding and not the resulting size after any\n         decoding.\n\n    Put another way, the body structure is a list of seven elements.  The\n    semantics of the elements of this list are:\n\n       1. Byte string giving the major MIME type\n       2. Byte string giving the minor MIME type\n       3. A list giving the Content-Type parameters of the message\n       4. A byte string giving the content identifier for the message part, or\n          None if it has no content identifier.\n       5. A byte string giving the content description for the message part, or\n          None if it has no content description.\n       6. A byte string giving the Content-Encoding of the message body\n       7. An integer giving the number of octets in the message body\n\n    The RFC goes on::\n\n        Multiple parts are indicated by parenthesis nesting.  Instead of a body\n        type as the first element of the parenthesized list, there is a sequence\n        of one or more nested body structures.  The second element of the\n        parenthesized list is the multipart subtype (mixed, digest, parallel,\n        alternative, etc.).\n\n        For example, a two part message consisting of a text and a\n        BASE64-encoded text attachment can have a body structure of: ((\"TEXT\"\n        \"PLAIN\" (\"CHARSET\" \"US-ASCII\") NIL NIL \"7BIT\" 1152 23)(\"TEXT\" \"PLAIN\"\n        (\"CHARSET\" \"US-ASCII\" \"NAME\" \"cc.diff\")\n        \"<960723163407.20117h@cac.washington.edu>\" \"Compiler diff\" \"BASE64\" 4554\n        73) \"MIXED\")\n\n    This is represented as::\n\n        [[\"TEXT\", \"PLAIN\", [\"CHARSET\", \"US-ASCII\"], None, None, \"7BIT\", 1152,\n          23],\n         [\"TEXT\", \"PLAIN\", [\"CHARSET\", \"US-ASCII\", \"NAME\", \"cc.diff\"],\n          \"<960723163407.20117h@cac.washington.edu>\", \"Compiler diff\",\n          \"BASE64\", 4554, 73],\n         \"MIXED\"]\n\n    In other words, a list of N + 1 elements, where N is the number of parts in\n    the message.  The first N elements are structures as defined by the previous\n    section.  The last element is the minor MIME subtype of the multipart\n    message.\n\n    Additionally, the RFC describes extension data::\n\n        Extension data follows the multipart subtype.  Extension data is never\n        returned with the BODY fetch, but can be returned with a BODYSTRUCTURE\n        fetch.  Extension data, if present, MUST be in the defined order.\n\n    The C{extended} flag controls whether extension data might be returned with\n    the normal data.\n    \"\"\"\n    return _getMessageStructure(msg).encode(extended)\n\n\ndef _formatHeaders(headers):\n    # TODO: This should use email.header.Header, which handles encoding\n    hdrs = [': '.join((k.title(), '\\r\\n'.join(v.splitlines()))) for (k, v)\n            in headers.items()]\n    hdrs = '\\r\\n'.join(hdrs) + '\\r\\n'\n    return networkString(hdrs)\n\ndef subparts(m):\n    i = 0\n    try:\n        while True:\n            yield m.getSubPart(i)\n            i += 1\n    except IndexError:\n        pass\n\n\n\ndef iterateInReactor(i):\n    \"\"\"\n    Consume an interator at most a single iteration per reactor iteration.\n\n    If the iterator produces a Deferred, the next iteration will not occur\n    until the Deferred fires, otherwise the next iteration will be taken\n    in the next reactor iteration.\n\n    @rtype: C{Deferred}\n    @return: A deferred which fires (with None) when the iterator is\n    exhausted or whose errback is called if there is an exception.\n    \"\"\"\n    from twisted.internet import reactor\n    d = defer.Deferred()\n    def go(last):\n        try:\n            r = next(i)\n        except StopIteration:\n            d.callback(last)\n        except:\n            d.errback()\n        else:\n            if isinstance(r, defer.Deferred):\n                r.addCallback(go)\n            else:\n                reactor.callLater(0, go, r)\n    go(None)\n    return d\n\n\n\nclass MessageProducer:\n    CHUNK_SIZE = 2 ** 2 ** 2 ** 2\n    _uuid4 = staticmethod(uuid.uuid4)\n\n    def __init__(self, msg, buffer = None, scheduler = None):\n        \"\"\"\n        Produce this message.\n\n        @param msg: The message I am to produce.\n        @type msg: L{IMessage}\n\n        @param buffer: A buffer to hold the message in.  If None, I will\n            use a L{tempfile.TemporaryFile}.\n        @type buffer: file-like\n        \"\"\"\n        self.msg = msg\n        if buffer is None:\n            buffer = tempfile.TemporaryFile()\n        self.buffer = buffer\n        if scheduler is None:\n            scheduler = iterateInReactor\n        self.scheduler = scheduler\n        self.write = self.buffer.write\n\n\n    def beginProducing(self, consumer):\n        self.consumer = consumer\n        return self.scheduler(self._produce())\n\n\n    def _produce(self):\n        headers = self.msg.getHeaders(True)\n        boundary = None\n        if self.msg.isMultipart():\n            content = headers.get('content-type')\n            parts = [x.split('=', 1) for x in content.split(';')[1:]]\n            parts = dict([(k.lower().strip(), v) for (k, v) in parts])\n            boundary = parts.get('boundary')\n            if boundary is None:\n                # Bastards\n                boundary = '----=%s' % (self._uuid4().hex,)\n                headers['content-type'] += '; boundary=\"%s\"' % (boundary,)\n            else:\n                if boundary.startswith('\"') and boundary.endswith('\"'):\n                    boundary = boundary[1:-1]\n            boundary = networkString(boundary)\n\n        self.write(_formatHeaders(headers))\n        self.write(b'\\r\\n')\n        if self.msg.isMultipart():\n            for p in subparts(self.msg):\n                self.write(b'\\r\\n--' + boundary + b'\\r\\n')\n                yield MessageProducer(p, self.buffer, self.scheduler\n                    ).beginProducing(None\n                    )\n            self.write(b'\\r\\n--' + boundary + b'--\\r\\n' )\n        else:\n            f = self.msg.getBodyFile()\n            while True:\n                b = f.read(self.CHUNK_SIZE)\n                if b:\n                    self.buffer.write(b)\n                    yield None\n                else:\n                    break\n        if self.consumer:\n            self.buffer.seek(0, 0)\n            yield FileProducer(self.buffer\n                ).beginProducing(self.consumer\n                ).addCallback(lambda _: self\n                )\n\n\n\nclass _FetchParser:\n    class Envelope:\n        # Response should be a list of fields from the message:\n        #   date, subject, from, sender, reply-to, to, cc, bcc, in-reply-to,\n        #   and message-id.\n        #\n        # from, sender, reply-to, to, cc, and bcc are themselves lists of\n        # address information:\n        #   personal name, source route, mailbox name, host name\n        #\n        # reply-to and sender must not be None.  If not present in a message\n        # they should be defaulted to the value of the from field.\n        type = 'envelope'\n        __str__ = lambda self: 'envelope'\n\n\n    class Flags:\n        type = 'flags'\n        __str__ = lambda self: 'flags'\n\n\n    class InternalDate:\n        type = 'internaldate'\n        __str__ = lambda self: 'internaldate'\n\n\n    class RFC822Header:\n        type = 'rfc822header'\n        __str__ = lambda self: 'rfc822.header'\n\n\n    class RFC822Text:\n        type = 'rfc822text'\n        __str__ = lambda self: 'rfc822.text'\n\n\n    class RFC822Size:\n        type = 'rfc822size'\n        __str__ = lambda self: 'rfc822.size'\n\n\n    class RFC822:\n        type = 'rfc822'\n        __str__ = lambda self: 'rfc822'\n\n\n    class UID:\n        type = 'uid'\n        __str__ = lambda self: 'uid'\n\n\n    class Body:\n        type = 'body'\n        peek = False\n        header = None\n        mime = None\n        text = None\n        part = ()\n        empty = False\n        partialBegin = None\n        partialLength = None\n\n        def __str__(self):\n            return nativeString(self.__bytes__())\n\n        def __bytes__(self):\n            base = b'BODY'\n            part = b''\n            separator = b''\n            if self.part:\n                part = b'.'.join([unicode(x + 1).encode(\"ascii\")\n                                  for x in self.part])\n                separator = b'.'\n#            if self.peek:\n#                base += '.PEEK'\n            if self.header:\n                base += (b'[' + part + separator +\n                         str(self.header).encode(\"ascii\") + b']')\n            elif self.text:\n                base += b'[' + part + separator + b'TEXT]'\n            elif self.mime:\n                base += b'[' + part + separator + b'MIME]'\n            elif self.empty:\n                base += b'[' + part + b']'\n            if self.partialBegin is not None:\n                base += b'<' + intToBytes(self.partialBegin) + b'.' + intToBytes(self.partialLength) + b'>'\n            return base\n\n\n    class BodyStructure:\n        type = 'bodystructure'\n        __str__ = lambda self: 'bodystructure'\n\n\n    # These three aren't top-level, they don't need type indicators\n    class Header:\n        negate = False\n        fields = None\n        part = None\n\n        def __str__(self):\n            return nativeString(self.__bytes__())\n\n\n        def __bytes__(self):\n            base = b'HEADER'\n            if self.fields:\n                base += b'.FIELDS'\n                if self.negate:\n                    base += b'.NOT'\n                fields = []\n                for f in self.fields:\n                    f = f.title()\n                    if _needsQuote(f):\n                        f = _quote(f)\n                    fields.append(f)\n                base += b' (' + b' '.join(fields) + b')'\n            if self.part:\n                # TODO: _FetchParser never assigns Header.part - dead\n                # code?\n                base = b'.'.join([(x + 1).__bytes__() for x in self.part]) + b'.' + base\n            return base\n\n\n    class Text:\n        pass\n\n\n    class MIME:\n        pass\n\n    parts = None\n\n    _simple_fetch_att = [\n        (b'envelope', Envelope),\n        (b'flags', Flags),\n        (b'internaldate', InternalDate),\n        (b'rfc822.header', RFC822Header),\n        (b'rfc822.text', RFC822Text),\n        (b'rfc822.size', RFC822Size),\n        (b'rfc822', RFC822),\n        (b'uid', UID),\n        (b'bodystructure', BodyStructure),\n    ]\n\n    def __init__(self):\n        self.state = ['initial']\n        self.result = []\n        self.remaining = b''\n\n\n    def parseString(self, s):\n        s = self.remaining + s\n        try:\n            while s or self.state:\n                if not self.state:\n                    raise IllegalClientResponse(\"Invalid Argument\")\n                # print 'Entering state_' + self.state[-1] + ' with', repr(s)\n                state = self.state.pop()\n                try:\n                    used = getattr(self, 'state_' + state)(s)\n                except:\n                    self.state.append(state)\n                    raise\n                else:\n                    # print state, 'consumed', repr(s[:used])\n                    s = s[used:]\n        finally:\n            self.remaining = s\n\n\n    def state_initial(self, s):\n        # In the initial state, the literals \"ALL\", \"FULL\", and \"FAST\"\n        # are accepted, as is a ( indicating the beginning of a fetch_att\n        # token, as is the beginning of a fetch_att token.\n        if s == b'':\n            return 0\n\n        l = s.lower()\n        if l.startswith(b'all'):\n            self.result.extend((\n                self.Flags(), self.InternalDate(),\n                self.RFC822Size(), self.Envelope()\n            ))\n            return 3\n        if l.startswith(b'full'):\n            self.result.extend((\n                self.Flags(), self.InternalDate(),\n                self.RFC822Size(), self.Envelope(),\n                self.Body()\n            ))\n            return 4\n        if l.startswith(b'fast'):\n            self.result.extend((\n                self.Flags(), self.InternalDate(), self.RFC822Size(),\n            ))\n            return 4\n\n        if l.startswith(b'('):\n            self.state.extend(('close_paren', 'maybe_fetch_att', 'fetch_att'))\n            return 1\n\n        self.state.append('fetch_att')\n        return 0\n\n\n    def state_close_paren(self, s):\n        if s.startswith(b')'):\n            return 1\n        # TODO: does maybe_fetch_att's startswith(b')') make this dead\n        # code?\n        raise Exception(\"Missing )\")\n\n\n    def state_whitespace(self, s):\n        # Eat up all the leading whitespace\n        if not s or not s[0:1].isspace():\n            raise Exception(\"Whitespace expected, none found\")\n        i = 0\n        for i in range(len(s)):\n            if not s[i:i + 1].isspace():\n                break\n        return i\n\n\n    def state_maybe_fetch_att(self, s):\n        if not s.startswith(b')'):\n            self.state.extend(('maybe_fetch_att', 'fetch_att', 'whitespace'))\n        return 0\n\n\n    def state_fetch_att(self, s):\n        # Allowed fetch_att tokens are \"ENVELOPE\", \"FLAGS\", \"INTERNALDATE\",\n        # \"RFC822\", \"RFC822.HEADER\", \"RFC822.SIZE\", \"RFC822.TEXT\", \"BODY\",\n        # \"BODYSTRUCTURE\", \"UID\",\n        # \"BODY [\".PEEK\"] [<section>] [\"<\" <number> \".\" <nz_number> \">\"]\n\n        l = s.lower()\n        for (name, cls) in self._simple_fetch_att:\n            if l.startswith(name):\n                self.result.append(cls())\n                return len(name)\n\n        b = self.Body()\n        if l.startswith(b'body.peek'):\n            b.peek = True\n            used = 9\n        elif l.startswith(b'body'):\n            used = 4\n        else:\n            raise Exception(\"Nothing recognized in fetch_att: %s\" % (l,))\n\n        self.pending_body = b\n        self.state.extend(('got_body', 'maybe_partial', 'maybe_section'))\n        return used\n\n\n    def state_got_body(self, s):\n        self.result.append(self.pending_body)\n        del self.pending_body\n        return 0\n\n\n    def state_maybe_section(self, s):\n        if not s.startswith(b\"[\"):\n            return 0\n\n        self.state.extend(('section', 'part_number'))\n        return 1\n\n    _partExpr = re.compile(b'(\\d+(?:\\.\\d+)*)\\.?')\n\n\n    def state_part_number(self, s):\n        m = self._partExpr.match(s)\n        if m is not None:\n            self.parts = [int(p) - 1 for p in m.groups()[0].split(b'.')]\n            return m.end()\n        else:\n            self.parts = []\n            return 0\n\n\n    def state_section(self, s):\n        # Grab \"HEADER]\" or \"HEADER.FIELDS (Header list)]\" or\n        # \"HEADER.FIELDS.NOT (Header list)]\" or \"TEXT]\" or \"MIME]\" or\n        # just \"]\".\n\n        l = s.lower()\n        used = 0\n        if l.startswith(b']'):\n            self.pending_body.empty = True\n            used += 1\n        elif l.startswith(b'header]'):\n            h = self.pending_body.header = self.Header()\n            h.negate = True\n            h.fields = ()\n            used += 7\n        elif l.startswith(b'text]'):\n            self.pending_body.text = self.Text()\n            used += 5\n        elif l.startswith(b'mime]'):\n            self.pending_body.mime = self.MIME()\n            used += 5\n        else:\n            h = self.Header()\n            if l.startswith(b'header.fields.not'):\n                h.negate = True\n                used += 17\n            elif l.startswith(b'header.fields'):\n                used += 13\n            else:\n                raise Exception(\"Unhandled section contents: %r\" % (l,))\n\n            self.pending_body.header = h\n            self.state.extend(('finish_section', 'header_list', 'whitespace'))\n        self.pending_body.part = tuple(self.parts)\n        self.parts = None\n        return used\n\n\n    def state_finish_section(self, s):\n        if not s.startswith(b']'):\n            raise Exception(\"section must end with ]\")\n        return 1\n\n\n    def state_header_list(self, s):\n        if not s.startswith(b'('):\n            raise Exception(\"Header list must begin with (\")\n        end = s.find(b')')\n        if end == -1:\n            raise Exception(\"Header list must end with )\")\n\n        headers = s[1:end].split()\n        self.pending_body.header.fields = [h.upper() for h in headers]\n        return end + 1\n\n\n    def state_maybe_partial(self, s):\n        # Grab <number.number> or nothing at all\n        if not s.startswith(b'<'):\n            return 0\n        end = s.find(b'>')\n        if end == -1:\n            raise Exception(\"Found < but not >\")\n\n        partial = s[1:end]\n        parts = partial.split(b'.', 1)\n        if len(parts) != 2:\n            raise Exception(\"Partial specification did not include two .-delimited integers\")\n        begin, length = map(int, parts)\n        self.pending_body.partialBegin = begin\n        self.pending_body.partialLength = length\n\n        return end + 1\n\n\n\nclass FileProducer:\n    CHUNK_SIZE = 2 ** 2 ** 2 ** 2\n\n    firstWrite = True\n\n    def __init__(self, f):\n        self.f = f\n\n\n    def beginProducing(self, consumer):\n        self.consumer = consumer\n        self.produce = consumer.write\n        d = self._onDone = defer.Deferred()\n        self.consumer.registerProducer(self, False)\n        return d\n\n\n    def resumeProducing(self):\n        b = b''\n        if self.firstWrite:\n            b = b'{' + intToBytes(self._size()) + b'}\\r\\n'\n            self.firstWrite = False\n        if not self.f:\n            return\n        b = b + self.f.read(self.CHUNK_SIZE)\n        if not b:\n            self.consumer.unregisterProducer()\n            self._onDone.callback(self)\n            self._onDone = self.f = self.consumer = None\n        else:\n            self.produce(b)\n\n\n    def pauseProducing(self):\n        \"\"\"\n        Pause the producer.  This does nothing.\n        \"\"\"\n\n\n    def stopProducing(self):\n        \"\"\"\n        Stop the producer.  This does nothing.\n        \"\"\"\n\n\n    def _size(self):\n        b = self.f.tell()\n        self.f.seek(0, 2)\n        e = self.f.tell()\n        self.f.seek(b, 0)\n        return e - b\n\n\n\ndef parseTime(s):\n    # XXX - This may require localization :(\n    months = [\n        'jan', 'feb', 'mar', 'apr', 'may', 'jun', 'jul', 'aug', 'sep', 'oct',\n        'nov', 'dec', 'january', 'february', 'march', 'april', 'may', 'june',\n        'july', 'august', 'september', 'october', 'november', 'december'\n    ]\n    expr = {\n        'day': r\"(?P<day>3[0-1]|[1-2]\\d|0[1-9]|[1-9]| [1-9])\",\n        'mon': r\"(?P<mon>\\w+)\",\n        'year': r\"(?P<year>\\d\\d\\d\\d)\"\n    }\n    m = re.match('%(day)s-%(mon)s-%(year)s' % expr, s)\n    if not m:\n        raise ValueError(\"Cannot parse time string %r\" % (s,))\n    d = m.groupdict()\n    try:\n        d['mon'] = 1 + (months.index(d['mon'].lower()) % 12)\n        d['year'] = int(d['year'])\n        d['day'] = int(d['day'])\n    except ValueError:\n        raise ValueError(\"Cannot parse time string %r\" % (s,))\n    else:\n        return time.struct_time(\n            (d['year'], d['mon'], d['day'], 0, 0, 0, -1, -1, -1)\n        )\n\n# we need to cast Python >=3.3 memoryview to chars (from unsigned bytes), but\n# cast is absent in previous versions: thus, the lambda returns the\n# memoryview instance while ignoring the format\nmemory_cast = getattr(memoryview, \"cast\", lambda *x: x[0])\n\ndef modified_base64(s):\n    s_utf7 = s.encode('utf-7')\n    return s_utf7[1:-1].replace(b'/', b',')\n\ndef modified_unbase64(s):\n    s_utf7 = b'+' + s.replace(b',', b'/') + b'-'\n    return s_utf7.decode('utf-7')\n\ndef encoder(s, errors=None):\n    \"\"\"\n    Encode the given C{unicode} string using the IMAP4 specific variation of\n    UTF-7.\n\n    @type s: C{unicode}\n    @param s: The text to encode.\n\n    @param errors: Policy for handling encoding errors.  Currently ignored.\n\n    @return: L{tuple} of a L{str} giving the encoded bytes and an L{int}\n        giving the number of code units consumed from the input.\n    \"\"\"\n    r = bytearray()\n    _in = []\n    valid_chars = set(map(chr, range(0x20,0x7f))) - {u\"&\"}\n    for c in s:\n        if c in valid_chars:\n            if _in:\n                r += b'&' + modified_base64(''.join(_in)) + b'-'\n                del _in[:]\n            r.append(ord(c))\n        elif c == u'&':\n            if _in:\n                r += b'&' + modified_base64(''.join(_in)) + b'-'\n                del _in[:]\n            r += b'&-'\n        else:\n            _in.append(c)\n    if _in:\n        r.extend(b'&' + modified_base64(''.join(_in)) + b'-')\n    return (bytes(r), len(s))\n\n\n\n\ndef decoder(s, errors=None):\n    \"\"\"\n    Decode the given L{str} using the IMAP4 specific variation of UTF-7.\n\n    @type s: L{str}\n    @param s: The bytes to decode.\n\n    @param errors: Policy for handling decoding errors.  Currently ignored.\n\n    @return: a L{tuple} of a C{unicode} string giving the text which was\n        decoded and an L{int} giving the number of bytes consumed from the\n        input.\n    \"\"\"\n    r = []\n    decode = []\n    s = memory_cast(memoryview(s), 'c')\n    for c in s:\n        if c == b'&' and not decode:\n            decode.append(b'&')\n        elif c == b'-' and decode:\n            if len(decode) == 1:\n                r.append(u'&')\n            else:\n                r.append(modified_unbase64(b''.join(decode[1:])))\n            decode = []\n        elif decode:\n            decode.append(c)\n        else:\n            r.append(c.decode())\n    if decode:\n        r.append(modified_unbase64(b''.join(decode[1:])))\n    return (u''.join(r), len(s))\n\n\n\nclass StreamReader(codecs.StreamReader):\n    def decode(self, s, errors='strict'):\n        return decoder(s)\n\n\n\nclass StreamWriter(codecs.StreamWriter):\n    def encode(self, s, errors='strict'):\n        return encoder(s)\n\n\n_codecInfo = codecs.CodecInfo(encoder, decoder, StreamReader, StreamWriter)\n\n\ndef imap4_utf_7(name):\n    if name == 'imap4-utf-7':\n        return _codecInfo\n\ncodecs.register(imap4_utf_7)\n\n__all__ = [\n    # Protocol classes\n    'IMAP4Server', 'IMAP4Client',\n\n    # Interfaces\n    'IMailboxListener', 'IClientAuthentication', 'IAccount', 'IMailbox',\n    'INamespacePresenter', 'ICloseableMailbox', 'IMailboxInfo',\n    'IMessage', 'IMessageCopier', 'IMessageFile', 'ISearchableMailbox',\n    'IMessagePart',\n\n    # Exceptions\n    'IMAP4Exception', 'IllegalClientResponse', 'IllegalOperation',\n    'IllegalMailboxEncoding', 'UnhandledResponse', 'NegativeResponse',\n    'NoSupportedAuthentication', 'IllegalServerResponse',\n    'IllegalIdentifierError', 'IllegalQueryError', 'MismatchedNesting',\n    'MismatchedQuoting', 'MailboxException', 'MailboxCollision',\n    'NoSuchMailbox', 'ReadOnlyMailbox',\n\n    # Auth objects\n    'CramMD5ClientAuthenticator', 'PLAINAuthenticator', 'LOGINAuthenticator',\n    'PLAINCredentials', 'LOGINCredentials',\n\n    # Simple query interface\n    'Query', 'Not', 'Or',\n\n    # Miscellaneous\n    'MemoryAccount',\n    'statusRequestHelper',\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/interfaces.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nInterfaces for L{twisted.mail}.\n\n@since: 16.5\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom zope.interface import Interface\n\n\nclass IChallengeResponse(Interface):\n    \"\"\"\n    An C{IMAPrev4} authorization challenge mechanism.\n    \"\"\"\n\n    def getChallenge():\n        \"\"\"\n        Return a client challenge.\n\n        @return: A challenge.\n        @rtype: L{bytes}\n        \"\"\"\n\n\n    def setResponse(response):\n        \"\"\"\n        Extract a username and possibly a password from a response and\n        assign them to C{username} and C{password} instance variables.\n\n        @param response: A decoded response.\n        @type response: L{bytes}\n\n        @see: L{credentials.IUsernamePassword} or\n            L{credentials.IUsernameHashedPassword}\n        \"\"\"\n\n\n    def moreChallenges():\n        \"\"\"\n        Are there more challenges than just the first?  If so, callers\n        should challenge clients with the result of L{getChallenge},\n        and check their response with L{setResponse} in a loop until\n        this returns L{False}\n\n        @return: Are there more challenges?\n        @rtype: L{bool}\n        \"\"\"\n\n\n\nclass IClientAuthentication(Interface):\n\n    def getName():\n        \"\"\"\n        Return an identifier associated with this authentication scheme.\n\n        @rtype: L{bytes}\n        \"\"\"\n\n    def challengeResponse(secret, challenge):\n        \"\"\"\n        Generate a challenge response string.\n        \"\"\"\n\n\n\nclass IServerFactoryPOP3(Interface):\n    \"\"\"\n    An interface for querying capabilities of a POP3 server.\n\n    Any cap_* method may raise L{NotImplementedError} if the particular\n    capability is not supported. If L{cap_EXPIRE()} does not raise\n    L{NotImplementedError}, L{perUserExpiration()} must be implemented,\n    otherwise they are optional. If L{cap_LOGIN_DELAY()} is implemented,\n    L{perUserLoginDelay()} must be implemented, otherwise they are optional.\n\n    @type challengers: L{dict} of L{bytes} -> L{IUsernameHashedPassword\n        <cred.credentials.IUsernameHashedPassword>}\n    @ivar challengers: A mapping of challenger names to\n        L{IUsernameHashedPassword <cred.credentials.IUsernameHashedPassword>}\n        provider.\n    \"\"\"\n    def cap_IMPLEMENTATION():\n        \"\"\"\n        Return a string describing the POP3 server implementation.\n\n        @rtype: L{bytes}\n        @return: Server implementation information.\n        \"\"\"\n\n\n    def cap_EXPIRE():\n        \"\"\"\n        Return the minimum number of days messages are retained.\n\n        @rtype: L{int} or L{None}\n        @return: The minimum number of days messages are retained or none, if\n            the server never deletes messages.\n        \"\"\"\n\n\n    def perUserExpiration():\n        \"\"\"\n        Indicate whether the message expiration policy differs per user.\n\n        @rtype: L{bool}\n        @return: C{True} when the message expiration policy differs per user,\n            C{False} otherwise.\n        \"\"\"\n\n\n    def cap_LOGIN_DELAY():\n        \"\"\"\n        Return the minimum number of seconds between client logins.\n\n        @rtype: L{int}\n        @return: The minimum number of seconds between client logins.\n        \"\"\"\n\n\n    def perUserLoginDelay():\n        \"\"\"\n        Indicate whether the login delay period differs per user.\n\n        @rtype: L{bool}\n        @return: C{True} when the login delay differs per user, C{False}\n            otherwise.\n        \"\"\"\n\n\n\nclass IMailboxPOP3(Interface):\n    \"\"\"\n    An interface for mailbox access.\n\n    Message indices are 0-based.\n\n    @type loginDelay: L{int}\n    @ivar loginDelay: The number of seconds between allowed logins for the\n        user associated with this mailbox.\n\n    @type messageExpiration: L{int}\n    @ivar messageExpiration: The number of days messages in this mailbox will\n        remain on the server before being deleted.\n    \"\"\"\n    def listMessages(index=None):\n        \"\"\"\n        Retrieve the size of a message, or, if none is specified, the size of\n        each message in the mailbox.\n\n        @type index: L{int} or L{None}\n        @param index: The 0-based index of the message.\n\n        @rtype: L{int}, sequence of L{int}, or L{Deferred <defer.Deferred>}\n        @return: The number of octets in the specified message, or, if an\n            index is not specified, a sequence of the number of octets for\n            all messages in the mailbox or a deferred which fires with\n            one of those. Any value which corresponds to a deleted message\n            is set to 0.\n\n        @raise ValueError or IndexError: When the index does not correspond to\n            a message in the mailbox.  The use of ValueError is preferred.\n        \"\"\"\n\n\n    def getMessage(index):\n        \"\"\"\n        Retrieve a file containing the contents of a message.\n\n        @type index: L{int}\n        @param index: The 0-based index of a message.\n\n        @rtype: file-like object\n        @return: A file containing the message.\n\n        @raise ValueError or IndexError: When the index does not correspond to\n            a message in the mailbox.  The use of ValueError is preferred.\n        \"\"\"\n\n\n    def getUidl(index):\n        \"\"\"\n        Get a unique identifier for a message.\n\n        @type index: L{int}\n        @param index: The 0-based index of a message.\n\n        @rtype: L{bytes}\n        @return: A string of printable characters uniquely identifying the\n            message for all time.\n\n        @raise ValueError or IndexError: When the index does not correspond to\n            a message in the mailbox.  The use of ValueError is preferred.\n        \"\"\"\n\n\n    def deleteMessage(index):\n        \"\"\"\n        Mark a message for deletion.\n\n        This must not change the number of messages in this mailbox.  Further\n        requests for the size of the deleted message should return 0.  Further\n        requests for the message itself may raise an exception.\n\n        @type index: L{int}\n        @param index: The 0-based index of a message.\n\n        @raise ValueError or IndexError: When the index does not correspond to\n            a message in the mailbox.  The use of ValueError is preferred.\n        \"\"\"\n\n\n    def undeleteMessages():\n        \"\"\"\n        Undelete all messages marked for deletion.\n\n        Any message which can be undeleted should be returned to its original\n        position in the message sequence and retain its original UID.\n        \"\"\"\n\n\n    def sync():\n        \"\"\"\n        Discard the contents of any message marked for deletion.\n        \"\"\"\n\n\n\nclass IDomain(Interface):\n    \"\"\"\n    An interface for email domains.\n    \"\"\"\n    def exists(user):\n        \"\"\"\n        Check whether a user exists in this domain.\n\n        @type user: L{User}\n        @param user: A user.\n\n        @rtype: no-argument callable which returns L{IMessageSMTP} provider\n        @return: A function which takes no arguments and returns a message\n            receiver for the user.\n\n        @raise SMTPBadRcpt: When the given user does not exist in this domain.\n        \"\"\"\n\n\n    def addUser(user, password):\n        \"\"\"\n        Add a user to this domain.\n\n        @type user: L{bytes}\n        @param user: A username.\n\n        @type password: L{bytes}\n        @param password: A password.\n        \"\"\"\n\n\n    def getCredentialsCheckers():\n        \"\"\"\n        Return credentials checkers for this domain.\n\n        @rtype: L{list} of L{ICredentialsChecker\n            <twisted.cred.checkers.ICredentialsChecker>} provider\n        @return: Credentials checkers for this domain.\n        \"\"\"\n\n\n\nclass IAlias(Interface):\n    \"\"\"\n    An interface for aliases.\n    \"\"\"\n    def createMessageReceiver():\n        \"\"\"\n        Create a message receiver.\n\n        @rtype: L{IMessageSMTP} provider\n        @return: A message receiver.\n        \"\"\"\n\n\n\nclass IAliasableDomain(IDomain):\n    \"\"\"\n    An interface for email domains which can be aliased to other domains.\n    \"\"\"\n    def setAliasGroup(aliases):\n        \"\"\"\n        Set the group of defined aliases for this domain.\n\n        @type aliases: L{dict} of L{bytes} -> L{IAlias} provider\n        @param aliases: A mapping of domain name to alias.\n        \"\"\"\n\n\n    def exists(user, memo=None):\n        \"\"\"\n        Check whether a user exists in this domain or an alias of it.\n\n        @type user: L{User}\n        @param user: A user.\n\n        @type memo: L{None} or L{dict} of\n            L{AliasBase <twisted.mail.alias.AliasBase>}\n        @param memo: A record of the addresses already considered while\n            resolving aliases. The default value should be used by all external\n            code.\n\n        @rtype: no-argument callable which returns L{IMessageSMTP} provider\n        @return: A function which takes no arguments and returns a message\n            receiver for the user.\n\n        @raise SMTPBadRcpt: When the given user does not exist in this domain\n            or an alias of it.\n        \"\"\"\n\n\n\nclass IMessageDelivery(Interface):\n\n    def receivedHeader(helo, origin, recipients):\n        \"\"\"\n        Generate the Received header for a message.\n\n        @type helo: 2-L{tuple} of L{bytes} and L{bytes}.\n        @param helo: The argument to the HELO command and the client's IP\n        address.\n\n        @type origin: L{Address}\n        @param origin: The address the message is from\n\n        @type recipients: L{list} of L{User}\n        @param recipients: A list of the addresses for which this message\n        is bound.\n\n        @rtype: L{bytes}\n        @return: The full C{\"Received\"} header string.\n        \"\"\"\n\n    def validateTo(user):\n        \"\"\"\n        Validate the address for which the message is destined.\n\n        @type user: L{User}\n        @param user: The address to validate.\n\n        @rtype: no-argument callable\n        @return: A L{Deferred} which becomes, or a callable which takes no\n            arguments and returns an object implementing L{IMessageSMTP}. This\n            will be called and the returned object used to deliver the message\n            when it arrives.\n\n        @raise SMTPBadRcpt: Raised if messages to the address are not to be\n            accepted.\n        \"\"\"\n\n    def validateFrom(helo, origin):\n        \"\"\"\n        Validate the address from which the message originates.\n\n        @type helo: 2-L{tuple} of L{bytes} and L{bytes}.\n        @param helo: The argument to the HELO command and the client's IP\n        address.\n\n        @type origin: L{Address}\n        @param origin: The address the message is from\n\n        @rtype: L{Deferred} or L{Address}\n        @return: C{origin} or a L{Deferred} whose callback will be\n        passed C{origin}.\n\n        @raise SMTPBadSender: Raised of messages from this address are\n        not to be accepted.\n        \"\"\"\n\n\n\nclass IMessageDeliveryFactory(Interface):\n    \"\"\"\n    An alternate interface to implement for handling message delivery.\n\n    It is useful to implement this interface instead of L{IMessageDelivery}\n    directly because it allows the implementor to distinguish between different\n    messages delivery over the same connection. This can be used to optimize\n    delivery of a single message to multiple recipients, something which cannot\n    be done by L{IMessageDelivery} implementors due to their lack of\n    information.\n    \"\"\"\n    def getMessageDelivery():\n        \"\"\"\n        Return an L{IMessageDelivery} object.\n\n        This will be called once per message.\n        \"\"\"\n\n\n\nclass IMessageSMTP(Interface):\n    \"\"\"\n    Interface definition for messages that can be sent via SMTP.\n    \"\"\"\n\n    def lineReceived(line):\n        \"\"\"\n        Handle another line.\n        \"\"\"\n\n    def eomReceived():\n        \"\"\"\n        Handle end of message.\n\n        return a deferred. The deferred should be called with either:\n        callback(string) or errback(error)\n\n        @rtype: L{Deferred}\n        \"\"\"\n\n    def connectionLost():\n        \"\"\"\n        Handle message truncated.\n\n        semantics should be to discard the message\n        \"\"\"\n\n\n\nclass IMessageIMAPPart(Interface):\n    def getHeaders(negate, *names):\n        \"\"\"\n        Retrieve a group of message headers.\n\n        @type names: L{tuple} of L{str}\n        @param names: The names of the headers to retrieve or omit.\n\n        @type negate: L{bool}\n        @param negate: If True, indicates that the headers listed in C{names}\n            should be omitted from the return value, rather than included.\n\n        @rtype: L{dict}\n        @return: A mapping of header field names to header field values\n        \"\"\"\n\n\n    def getBodyFile():\n        \"\"\"\n        Retrieve a file object containing only the body of this message.\n        \"\"\"\n\n\n    def getSize():\n        \"\"\"\n        Retrieve the total size, in octets, of this message.\n\n        @rtype: L{int}\n        \"\"\"\n\n\n    def isMultipart():\n        \"\"\"\n        Indicate whether this message has subparts.\n\n        @rtype: L{bool}\n        \"\"\"\n\n\n    def getSubPart(part):\n        \"\"\"\n        Retrieve a MIME sub-message\n\n        @type part: L{int}\n        @param part: The number of the part to retrieve, indexed from 0.\n\n        @raise IndexError: Raised if the specified part does not exist.\n        @raise TypeError: Raised if this message is not multipart.\n\n        @rtype: Any object implementing L{IMessageIMAPPart}.\n        @return: The specified sub-part.\n        \"\"\"\n\n\n\nclass IMessageIMAP(IMessageIMAPPart):\n\n    def getUID():\n        \"\"\"\n        Retrieve the unique identifier associated with this message.\n        \"\"\"\n\n\n    def getFlags():\n        \"\"\"\n        Retrieve the flags associated with this message.\n\n        @rtype: C{iterable}\n        @return: The flags, represented as strings.\n        \"\"\"\n\n\n    def getInternalDate():\n        \"\"\"\n        Retrieve the date internally associated with this message.\n\n        @rtype: L{bytes}\n        @return: An RFC822-formatted date string.\n        \"\"\"\n\n\n\nclass IMessageIMAPFile(Interface):\n    \"\"\"\n    Optional message interface for representing messages as files.\n\n    If provided by message objects, this interface will be used instead the\n    more complex MIME-based interface.\n    \"\"\"\n\n    def open():\n        \"\"\"\n        Return a file-like object opened for reading.\n\n        Reading from the returned file will return all the bytes of which this\n        message consists.\n        \"\"\"\n\n\n\nclass ISearchableIMAPMailbox(Interface):\n\n    def search(query, uid):\n        \"\"\"\n        Search for messages that meet the given query criteria.\n\n        If this interface is not implemented by the mailbox,\n        L{IMailboxIMAP.fetch} and various methods of L{IMessageIMAP} will be\n        used instead.\n\n        Implementations which wish to offer better performance than the default\n        implementation should implement this interface.\n\n        @type query: L{list}\n        @param query: The search criteria\n\n        @type uid: L{bool}\n        @param uid: If true, the IDs specified in the query are UIDs; otherwise\n            they are message sequence IDs.\n\n        @rtype: L{list} or L{Deferred}\n        @return: A list of message sequence numbers or message UIDs which match\n            the search criteria or a L{Deferred} whose callback will be invoked\n            with such a list.\n\n        @raise IllegalQueryError: Raised when query is not valid.\n        \"\"\"\n\n\n\nclass IMailboxIMAPListener(Interface):\n    \"\"\"\n    Interface for objects interested in mailbox events\n    \"\"\"\n\n    def modeChanged(writeable):\n        \"\"\"\n        Indicates that the write status of a mailbox has changed.\n\n        @type writeable: L{bool}\n        @param writeable: A true value if write is now allowed, false\n            otherwise.\n        \"\"\"\n\n\n    def flagsChanged(newFlags):\n        \"\"\"\n        Indicates that the flags of one or more messages have changed.\n\n        @type newFlags: L{dict}\n        @param newFlags: A mapping of message identifiers to tuples of flags\n            now set on that message.\n        \"\"\"\n\n\n    def newMessages(exists, recent):\n        \"\"\"\n        Indicates that the number of messages in a mailbox has changed.\n\n        @type exists: L{int} or L{None}\n        @param exists: The total number of messages now in this mailbox. If the\n            total number of messages has not changed, this should be L{None}.\n\n        @type recent: L{int}\n        @param recent: The number of messages now flagged C{\\\\Recent}. If the\n            number of recent messages has not changed, this should be L{None}.\n        \"\"\"\n\n\n\nclass IMessageIMAPCopier(Interface):\n    def copy(messageObject):\n        \"\"\"\n        Copy the given message object into this mailbox.\n\n        The message object will be one which was previously returned by\n        L{IMailboxIMAP.fetch}.\n\n        Implementations which wish to offer better performance than the default\n        implementation should implement this interface.\n\n        If this interface is not implemented by the mailbox,\n        L{IMailboxIMAP.addMessage} will be used instead.\n\n        @rtype: L{Deferred} or L{int}\n        @return: Either the UID of the message or a Deferred which fires with\n            the UID when the copy finishes.\n        \"\"\"\n\n\n\nclass IMailboxIMAPInfo(Interface):\n    \"\"\"\n    Interface specifying only the methods required for C{listMailboxes}.\n\n    Implementations can return objects implementing only these methods for\n    return to C{listMailboxes} if it can allow them to operate more\n    efficiently.\n    \"\"\"\n\n    def getFlags():\n        \"\"\"\n        Return the flags defined in this mailbox\n\n        Flags with the \\\\ prefix are reserved for use as system flags.\n\n        @rtype: L{list} of L{str}\n        @return: A list of the flags that can be set on messages in this\n            mailbox.\n        \"\"\"\n\n\n    def getHierarchicalDelimiter():\n        \"\"\"\n        Get the character which delimits namespaces for in this mailbox.\n\n        @rtype: L{bytes}\n        \"\"\"\n\n\n\nclass IMailboxIMAP(IMailboxIMAPInfo):\n    def getUIDValidity():\n        \"\"\"\n        Return the unique validity identifier for this mailbox.\n\n        @rtype: L{int}\n        \"\"\"\n\n\n    def getUIDNext():\n        \"\"\"\n        Return the likely UID for the next message added to this mailbox.\n\n        @rtype: L{int}\n        \"\"\"\n\n\n    def getUID(message):\n        \"\"\"\n        Return the UID of a message in the mailbox\n\n        @type message: L{int}\n        @param message: The message sequence number\n\n        @rtype: L{int}\n        @return: The UID of the message.\n        \"\"\"\n\n\n    def getMessageCount():\n        \"\"\"\n        Return the number of messages in this mailbox.\n\n        @rtype: L{int}\n        \"\"\"\n\n\n    def getRecentCount():\n        \"\"\"\n        Return the number of messages with the 'Recent' flag.\n\n        @rtype: L{int}\n        \"\"\"\n\n\n    def getUnseenCount():\n        \"\"\"\n        Return the number of messages with the 'Unseen' flag.\n\n        @rtype: L{int}\n        \"\"\"\n\n\n    def isWriteable():\n        \"\"\"\n        Get the read/write status of the mailbox.\n\n        @rtype: L{int}\n        @return: A true value if write permission is allowed, a false value\n            otherwise.\n        \"\"\"\n\n\n    def destroy():\n        \"\"\"\n        Called before this mailbox is deleted, permanently.\n\n        If necessary, all resources held by this mailbox should be cleaned up\n        here. This function _must_ set the \\\\Noselect flag on this mailbox.\n        \"\"\"\n\n\n    def requestStatus(names):\n        \"\"\"\n        Return status information about this mailbox.\n\n        Mailboxes which do not intend to do any special processing to generate\n        the return value, C{statusRequestHelper} can be used to build the\n        dictionary by calling the other interface methods which return the data\n        for each name.\n\n        @type names: Any iterable\n        @param names: The status names to return information regarding. The\n            possible values for each name are: MESSAGES, RECENT, UIDNEXT,\n            UIDVALIDITY, UNSEEN.\n\n        @rtype: L{dict} or L{Deferred}\n        @return: A dictionary containing status information about the requested\n            names is returned. If the process of looking this information up\n            would be costly, a deferred whose callback will eventually be\n            passed this dictionary is returned instead.\n        \"\"\"\n\n\n    def addListener(listener):\n        \"\"\"\n        Add a mailbox change listener\n\n        @type listener: Any object which implements C{IMailboxIMAPListener}\n        @param listener: An object to add to the set of those which will be\n            notified when the contents of this mailbox change.\n        \"\"\"\n\n\n    def removeListener(listener):\n        \"\"\"\n        Remove a mailbox change listener\n\n        @type listener: Any object previously added to and not removed from\n            this mailbox as a listener.\n        @param listener: The object to remove from the set of listeners.\n\n        @raise ValueError: Raised when the given object is not a listener for\n            this mailbox.\n        \"\"\"\n\n\n    def addMessage(message, flags=(), date=None):\n        \"\"\"\n        Add the given message to this mailbox.\n\n        @type message: A file-like object\n        @param message: The RFC822 formatted message\n\n        @type flags: Any iterable of L{bytes}\n        @param flags: The flags to associate with this message\n\n        @type date: L{bytes}\n        @param date: If specified, the date to associate with this message.\n\n        @rtype: L{Deferred}\n        @return: A deferred whose callback is invoked with the message id if\n            the message is added successfully and whose errback is invoked\n            otherwise.\n\n        @raise ReadOnlyMailbox: Raised if this Mailbox is not open for\n            read-write.\n        \"\"\"\n\n\n    def expunge():\n        \"\"\"\n        Remove all messages flagged \\\\Deleted.\n\n        @rtype: L{list} or L{Deferred}\n        @return: The list of message sequence numbers which were deleted, or a\n            L{Deferred} whose callback will be invoked with such a list.\n\n        @raise ReadOnlyMailbox: Raised if this Mailbox is not open for\n            read-write.\n        \"\"\"\n\n\n    def fetch(messages, uid):\n        \"\"\"\n        Retrieve one or more messages.\n\n        @type messages: C{MessageSet}\n        @param messages: The identifiers of messages to retrieve information\n            about\n\n        @type uid: L{bool}\n        @param uid: If true, the IDs specified in the query are UIDs; otherwise\n            they are message sequence IDs.\n\n        @rtype: Any iterable of two-tuples of message sequence numbers and\n            implementors of C{IMessageIMAP}.\n        \"\"\"\n\n\n    def store(messages, flags, mode, uid):\n        \"\"\"\n        Set the flags of one or more messages.\n\n        @type messages: A MessageSet object with the list of messages requested\n        @param messages: The identifiers of the messages to set the flags of.\n\n        @type flags: sequence of L{str}\n        @param flags: The flags to set, unset, or add.\n\n        @type mode: -1, 0, or 1\n        @param mode: If mode is -1, these flags should be removed from the\n            specified messages. If mode is 1, these flags should be added to\n            the specified messages. If mode is 0, all existing flags should be\n            cleared and these flags should be added.\n\n        @type uid: L{bool}\n        @param uid: If true, the IDs specified in the query are UIDs; otherwise\n            they are message sequence IDs.\n\n        @rtype: L{dict} or L{Deferred}\n        @return: A L{dict} mapping message sequence numbers to sequences of\n            L{str} representing the flags set on the message after this\n            operation has been performed, or a L{Deferred} whose callback will\n            be invoked with such a L{dict}.\n\n        @raise ReadOnlyMailbox: Raised if this mailbox is not open for\n            read-write.\n        \"\"\"\n\n\n\nclass ICloseableMailboxIMAP(Interface):\n    \"\"\"\n    A supplementary interface for mailboxes which require cleanup on close.\n\n    Implementing this interface is optional. If it is implemented, the protocol\n    code will call the close method defined whenever a mailbox is closed.\n    \"\"\"\n\n    def close():\n        \"\"\"\n        Close this mailbox.\n\n        @return: A L{Deferred} which fires when this mailbox has been closed,\n            or None if the mailbox can be closed immediately.\n        \"\"\"\n\n\n\nclass IAccountIMAP(Interface):\n    \"\"\"\n    Interface for Account classes\n\n    Implementors of this interface should consider implementing\n    C{INamespacePresenter}.\n    \"\"\"\n\n    def addMailbox(name, mbox=None):\n        \"\"\"\n        Add a new mailbox to this account\n\n        @type name: L{bytes}\n        @param name: The name associated with this mailbox. It may not contain\n            multiple hierarchical parts.\n\n        @type mbox: An object implementing C{IMailboxIMAP}\n        @param mbox: The mailbox to associate with this name. If L{None}, a\n            suitable default is created and used.\n\n        @rtype: L{Deferred} or L{bool}\n        @return: A true value if the creation succeeds, or a deferred whose\n            callback will be invoked when the creation succeeds.\n\n        @raise MailboxException: Raised if this mailbox cannot be added for\n            some reason. This may also be raised asynchronously, if a\n            L{Deferred} is returned.\n        \"\"\"\n\n\n    def create(pathspec):\n        \"\"\"\n        Create a new mailbox from the given hierarchical name.\n\n        @type pathspec: L{bytes}\n        @param pathspec: The full hierarchical name of a new mailbox to create.\n            If any of the inferior hierarchical names to this one do not exist,\n            they are created as well.\n\n        @rtype: L{Deferred} or L{bool}\n        @return: A true value if the creation succeeds, or a deferred whose\n            callback will be invoked when the creation succeeds.\n\n        @raise MailboxException: Raised if this mailbox cannot be added. This\n            may also be raised asynchronously, if a L{Deferred} is returned.\n        \"\"\"\n\n\n    def select(name, rw=True):\n        \"\"\"\n        Acquire a mailbox, given its name.\n\n        @type name: L{bytes}\n        @param name: The mailbox to acquire\n\n        @type rw: L{bool}\n        @param rw: If a true value, request a read-write version of this\n            mailbox. If a false value, request a read-only version.\n\n        @rtype: Any object implementing C{IMailboxIMAP} or L{Deferred}\n        @return: The mailbox object, or a L{Deferred} whose callback will be\n            invoked with the mailbox object. None may be returned if the\n            specified mailbox may not be selected for any reason.\n        \"\"\"\n\n\n    def delete(name):\n        \"\"\"\n        Delete the mailbox with the specified name.\n\n        @type name: L{bytes}\n        @param name: The mailbox to delete.\n\n        @rtype: L{Deferred} or L{bool}\n        @return: A true value if the mailbox is successfully deleted, or a\n            L{Deferred} whose callback will be invoked when the deletion\n            completes.\n\n        @raise MailboxException: Raised if this mailbox cannot be deleted. This\n            may also be raised asynchronously, if a L{Deferred} is returned.\n        \"\"\"\n\n\n    def rename(oldname, newname):\n        \"\"\"\n        Rename a mailbox\n\n        @type oldname: L{bytes}\n        @param oldname: The current name of the mailbox to rename.\n\n        @type newname: L{bytes}\n        @param newname: The new name to associate with the mailbox.\n\n        @rtype: L{Deferred} or L{bool}\n        @return: A true value if the mailbox is successfully renamed, or a\n            L{Deferred} whose callback will be invoked when the rename\n            operation is completed.\n\n        @raise MailboxException: Raised if this mailbox cannot be renamed. This\n            may also be raised asynchronously, if a L{Deferred} is returned.\n        \"\"\"\n\n\n    def isSubscribed(name):\n        \"\"\"\n        Check the subscription status of a mailbox\n\n        @type name: L{bytes}\n        @param name: The name of the mailbox to check\n\n        @rtype: L{Deferred} or L{bool}\n        @return: A true value if the given mailbox is currently subscribed to,\n            a false value otherwise. A L{Deferred} may also be returned whose\n            callback will be invoked with one of these values.\n        \"\"\"\n\n\n    def subscribe(name):\n        \"\"\"\n        Subscribe to a mailbox\n\n        @type name: L{bytes}\n        @param name: The name of the mailbox to subscribe to\n\n        @rtype: L{Deferred} or L{bool}\n        @return: A true value if the mailbox is subscribed to successfully, or\n            a Deferred whose callback will be invoked with this value when the\n            subscription is successful.\n\n        @raise MailboxException: Raised if this mailbox cannot be subscribed\n            to. This may also be raised asynchronously, if a L{Deferred} is\n            returned.\n        \"\"\"\n\n\n    def unsubscribe(name):\n        \"\"\"\n        Unsubscribe from a mailbox\n\n        @type name: L{bytes}\n        @param name: The name of the mailbox to unsubscribe from\n\n        @rtype: L{Deferred} or L{bool}\n        @return: A true value if the mailbox is unsubscribed from successfully,\n            or a Deferred whose callback will be invoked with this value when\n            the unsubscription is successful.\n\n        @raise MailboxException: Raised if this mailbox cannot be unsubscribed\n            from. This may also be raised asynchronously, if a L{Deferred} is\n            returned.\n        \"\"\"\n\n\n    def listMailboxes(ref, wildcard):\n        \"\"\"\n        List all the mailboxes that meet a certain criteria\n\n        @type ref: L{bytes}\n        @param ref: The context in which to apply the wildcard\n\n        @type wildcard: L{bytes}\n        @param wildcard: An expression against which to match mailbox names.\n            '*' matches any number of characters in a mailbox name, and '%'\n            matches similarly, but will not match across hierarchical\n            boundaries.\n\n        @rtype: L{list} of L{tuple}\n        @return: A list of C{(mailboxName, mailboxObject)} which meet the given\n            criteria. C{mailboxObject} should implement either\n            C{IMailboxIMAPInfo} or C{IMailboxIMAP}. A Deferred may also be\n            returned.\n        \"\"\"\n\n\n\nclass INamespacePresenter(Interface):\n\n    def getPersonalNamespaces():\n        \"\"\"\n        Report the available personal namespaces.\n\n        Typically there should be only one personal namespace. A common name\n        for it is C{\\\"\\\"}, and its hierarchical delimiter is usually C{\\\"/\\\"}.\n\n        @rtype: iterable of two-tuples of strings\n        @return: The personal namespaces and their hierarchical delimiters. If\n            no namespaces of this type exist, None should be returned.\n        \"\"\"\n\n\n    def getSharedNamespaces():\n        \"\"\"\n        Report the available shared namespaces.\n\n        Shared namespaces do not belong to any individual user but are usually\n        to one or more of them. Examples of shared namespaces might be\n        C{\\\"#news\\\"} for a usenet gateway.\n\n        @rtype: iterable of two-tuples of strings\n        @return: The shared namespaces and their hierarchical delimiters. If no\n            namespaces of this type exist, None should be returned.\n        \"\"\"\n\n\n    def getUserNamespaces():\n        \"\"\"\n        Report the available user namespaces.\n\n        These are namespaces that contain folders belonging to other users\n        access to which this account has been granted.\n\n        @rtype: iterable of two-tuples of strings\n        @return: The user namespaces and their hierarchical delimiters. If no\n            namespaces of this type exist, None should be returned.\n        \"\"\"\n\n\n\n__all__ = [\n    # IMAP\n    'IAccountIMAP', 'ICloseableMailboxIMAP', 'IMailboxIMAP',\n    'IMailboxIMAPInfo', 'IMailboxIMAPListener', 'IMessageIMAP',\n    'IMessageIMAPCopier', 'IMessageIMAPFile', 'IMessageIMAPPart',\n    'ISearchableIMAPMailbox', 'INamespacePresenter',\n\n    # SMTP\n    'IMessageDelivery', 'IMessageDeliveryFactory', 'IMessageSMTP',\n\n    # Domains and aliases\n    'IDomain', 'IAlias', 'IAliasableDomain',\n\n    # POP3\n    'IMailboxPOP3', 'IServerFactoryPOP3',\n\n    # Authentication\n    'IClientAuthentication',\n]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/pop3.py",
    "content": "# -*- test-case-name: twisted.mail.test.test_pop3 -*-\n#\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nPost-office Protocol version 3.\n\n@author: Glyph Lefkowitz\n@author: Jp Calderone\n\"\"\"\n\nimport base64\nimport binascii\nimport warnings\nfrom hashlib import md5\n\nfrom zope.interface import implementer\n\nfrom twisted import cred\nfrom twisted.internet import task\nfrom twisted.internet import defer\nfrom twisted.internet import interfaces\nfrom twisted.mail import smtp\nfrom twisted.mail.interfaces import (\n    IServerFactoryPOP3 as IServerFactory,\n    IMailboxPOP3 as IMailbox,\n)\nfrom twisted.mail._except import (\n    POP3Error, _POP3MessageDeleted, POP3ClientError\n)\nfrom twisted.protocols import basic\nfrom twisted.protocols import policies\nfrom twisted.python import log\nfrom twisted.python.compat import _PY3, intToBytes\n\n# Authentication\n@implementer(cred.credentials.IUsernamePassword)\nclass APOPCredentials:\n    \"\"\"\n    Credentials for use in APOP authentication.\n\n    @ivar magic: See L{__init__}\n    @ivar username: See L{__init__}\n    @ivar digest: See L{__init__}\n    \"\"\"\n    def __init__(self, magic, username, digest):\n        \"\"\"\n        @type magic: L{bytes}\n        @param magic: The challenge string used to encrypt the password.\n\n        @type username: L{bytes}\n        @param username: The username associated with these credentials.\n\n        @type digest: L{bytes}\n        @param digest: An encrypted version of the user's password.  Should be\n            generated as an MD5 hash of the challenge string concatenated with\n            the plaintext password.\n        \"\"\"\n        self.magic = magic\n        self.username = username\n        self.digest = digest\n\n\n    def checkPassword(self, password):\n        \"\"\"\n        Validate a plaintext password against the credentials.\n\n        @type password: L{bytes}\n        @param password: A plaintext password.\n\n        @rtype: L{bool}\n        @return: C{True} if the credentials represented by this object match\n        the given password, C{False} if they do not.\n        \"\"\"\n        seed = self.magic + password\n        myDigest = md5(seed).hexdigest()\n        return myDigest == self.digest\n\n\n\nclass _HeadersPlusNLines:\n    \"\"\"\n    A utility class to retrieve the header and some lines of the body of a mail\n    message.\n\n    @ivar _file: See L{__init__}\n    @ivar _extraLines: See L{__init__}\n\n    @type linecount: L{int}\n    @ivar linecount: The number of full lines of the message body scanned.\n\n    @type headers: L{bool}\n    @ivar headers: An indication of which part of the message is being scanned.\n        C{True} for the header and C{False} for the body.\n\n    @type done: L{bool}\n    @ivar done: A flag indicating when the desired part of the message has been\n        scanned.\n\n    @type buf: L{bytes}\n    @ivar buf: The portion of the message body that has been scanned, up to\n        C{n} lines.\n    \"\"\"\n    def __init__(self, file, extraLines):\n        \"\"\"\n        @type file: file-like object\n        @param file: A file containing a mail message.\n\n        @type extraLines: L{int}\n        @param extraLines: The number of lines of the message body to retrieve.\n        \"\"\"\n        self._file = file\n        self._extraLines = extraLines\n        self.linecount = 0\n        self.headers = 1\n        self.done = 0\n        self.buf = b''\n\n\n    def read(self, bytes):\n        \"\"\"\n        Scan bytes from the file.\n\n        @type bytes: L{int}\n        @param bytes: The number of bytes to read from the file.\n\n        @rtype: L{bytes}\n        @return: Each portion of the header as it is scanned.  Then, full lines\n            of the message body as they are scanned.  When more than one line\n            of the header and/or body has been scanned, the result is the\n            concatenation of the lines.  When the scan results in no full\n            lines, the empty string is returned.\n        \"\"\"\n        if self.done:\n            return b''\n        data = self._file.read(bytes)\n        if not data:\n            return data\n        if self.headers:\n            df, sz = data.find(b'\\r\\n\\r\\n'), 4\n            if df == -1:\n                df, sz = data.find(b'\\n\\n'), 2\n            if df != -1:\n                df += sz\n                val = data[:df]\n                data = data[df:]\n                self.linecount = 1\n                self.headers = 0\n        else:\n            val = b''\n        if self.linecount > 0:\n            dsplit = (self.buf + data).split(b'\\n')\n            self.buf = dsplit[-1]\n            for ln in dsplit[:-1]:\n                if self.linecount > self._extraLines:\n                    self.done = 1\n                    return val\n                val += (ln + b'\\n')\n                self.linecount += 1\n            return val\n        else:\n            return data\n\n\n\nclass _IteratorBuffer(object):\n    \"\"\"\n    An iterator which buffers the elements of a container and periodically\n    passes them as input to a writer.\n\n    @ivar write: See L{__init__}.\n    @ivar memoryBufferSize: See L{__init__}.\n\n    @type bufSize: L{int}\n    @ivar bufSize: The number of bytes currently in the buffer.\n\n    @type lines: L{list} of L{bytes}\n    @ivar lines: The buffer, which is a list of strings.\n\n    @type iterator: iterator which yields L{bytes}\n    @ivar iterator: An iterator over a container of strings.\n    \"\"\"\n    bufSize = 0\n\n    def __init__(self, write, iterable, memoryBufferSize=None):\n        \"\"\"\n        @type write: callable that takes L{list} of L{bytes}\n        @param write: A writer which is a callable that takes a list of\n            strings.\n\n        @type iterable: iterable which yields L{bytes}\n        @param iterable: An iterable container of strings.\n\n        @type memoryBufferSize: L{int} or L{None}\n        @param memoryBufferSize: The number of bytes to buffer before flushing\n            the buffer to the writer.\n        \"\"\"\n        self.lines = []\n        self.write = write\n        self.iterator = iter(iterable)\n        if memoryBufferSize is None:\n            memoryBufferSize = 2 ** 16\n        self.memoryBufferSize = memoryBufferSize\n\n\n    def __iter__(self):\n        \"\"\"\n        Return an iterator.\n\n        @rtype: iterator which yields L{bytes}\n        @return: An iterator over strings.\n        \"\"\"\n        return self\n\n\n    def __next__(self):\n        \"\"\"\n        Get the next string from the container, buffer it, and possibly send\n        the buffer to the writer.\n\n        The contents of the buffer are written when it is full or when no\n        further values are available from the container.\n\n        @raise StopIteration: When no further values are available from the\n        container.\n        \"\"\"\n        try:\n            v = next(self.iterator)\n        except StopIteration:\n            if self.lines:\n                self.write(self.lines)\n            # Drop some references, in case they're edges in a cycle.\n            del self.iterator, self.lines, self.write\n            raise\n        else:\n            if v is not None:\n                self.lines.append(v)\n                self.bufSize += len(v)\n                if self.bufSize > self.memoryBufferSize:\n                    self.write(self.lines)\n                    self.lines = []\n                    self.bufSize = 0\n\n    if not _PY3:\n        next = __next__\n\n\n\ndef iterateLineGenerator(proto, gen):\n    \"\"\"\n    Direct the output of an iterator to the transport of a protocol and arrange\n    for iteration to take place.\n\n    @type proto: L{POP3}\n    @param proto: A POP3 server protocol.\n\n    @type gen: iterator which yields L{bytes}\n    @param gen: An iterator over strings.\n\n    @rtype: L{Deferred <defer.Deferred>}\n    @return: A deferred which fires when the iterator finishes.\n    \"\"\"\n    coll = _IteratorBuffer(proto.transport.writeSequence, gen)\n    return proto.schedule(coll)\n\n\n\ndef successResponse(response):\n    \"\"\"\n    Format an object as a positive response.\n\n    @type response: stringifyable L{object}\n    @param response: An object with a string representation.\n\n    @rtype: L{bytes}\n    @return: A positive POP3 response string.\n    \"\"\"\n    if not isinstance(response, bytes):\n        response = str(response).encode(\"utf-8\")\n    return b'+OK ' + response + b'\\r\\n'\n\n\n\ndef formatStatResponse(msgs):\n    \"\"\"\n    Format a list of message sizes into a STAT response.\n\n    This generator function is intended to be used with\n    L{Cooperator <twisted.internet.task.Cooperator>}.\n\n    @type msgs: L{list} of L{int}\n    @param msgs: A list of message sizes.\n\n    @rtype: L{None} or L{bytes}\n    @return: Yields none until a result is available, then a string that is\n        suitable for use in a STAT response. The string consists of the number\n        of messages and the total size of the messages in octets.\n    \"\"\"\n    i = 0\n    bytes = 0\n    for size in msgs:\n        i += 1\n        bytes += size\n        yield None\n    yield successResponse(intToBytes(i) + b' ' + intToBytes(bytes))\n\n\n\ndef formatListLines(msgs):\n    \"\"\"\n    Format a list of message sizes for use in a LIST response.\n\n    @type msgs: L{list} of L{int}\n    @param msgs: A list of message sizes.\n\n    @rtype: L{bytes}\n    @return: Yields a series of strings that are suitable for use as scan\n        listings in a LIST response. Each string consists of a message number\n        and its size in octets.\n    \"\"\"\n    i = 0\n    for size in msgs:\n        i += 1\n        yield intToBytes(i) + b' ' + intToBytes(size) + b'\\r\\n'\n\n\n\ndef formatListResponse(msgs):\n    \"\"\"\n    Format a list of message sizes into a complete LIST response.\n\n    This generator function is intended to be used with\n    L{Cooperator <twisted.internet.task.Cooperator>}.\n\n    @type msgs: L{list} of L{int}\n    @param msgs: A list of message sizes.\n\n    @rtype: L{bytes}\n    @return: Yields a series of strings which make up a complete LIST response.\n    \"\"\"\n    yield successResponse(intToBytes(len(msgs)))\n    for ele in formatListLines(msgs):\n        yield ele\n    yield b'.\\r\\n'\n\n\n\ndef formatUIDListLines(msgs, getUidl):\n    \"\"\"\n    Format a list of message sizes for use in a UIDL response.\n\n    @param msgs: See L{formatUIDListResponse}\n    @param getUidl: See L{formatUIDListResponse}\n\n    @rtype: L{bytes}\n    @return: Yields a series of strings that are suitable for use as unique-id\n        listings in a UIDL response. Each string consists of a message number\n        and its unique id.\n    \"\"\"\n    for i, m in enumerate(msgs):\n        if m is not None:\n            uid = getUidl(i)\n            if not isinstance(uid, bytes):\n                uid = str(uid).encode(\"utf-8\")\n            yield intToBytes(i + 1) + b' ' + uid + b'\\r\\n'\n\n\n\ndef formatUIDListResponse(msgs, getUidl):\n    \"\"\"\n    Format a list of message sizes into a complete UIDL response.\n\n    This generator function is intended to be used with\n    L{Cooperator <twisted.internet.task.Cooperator>}.\n\n    @type msgs: L{list} of L{int}\n    @param msgs: A list of message sizes.\n\n    @type getUidl: one-argument callable returning bytes\n    @param getUidl: A callable which takes a message index number and returns\n        the UID of the corresponding message in the mailbox.\n\n    @rtype: L{bytes}\n    @return: Yields a series of strings which make up a complete UIDL response.\n    \"\"\"\n    yield successResponse('')\n    for ele in formatUIDListLines(msgs, getUidl):\n        yield ele\n    yield b'.\\r\\n'\n\n\n\n@implementer(interfaces.IProducer)\nclass POP3(basic.LineOnlyReceiver, policies.TimeoutMixin):\n    \"\"\"\n    A POP3 server protocol.\n\n    @type portal: L{Portal}\n    @ivar portal: A portal for authentication.\n\n    @type factory: L{IServerFactory} provider\n    @ivar factory: A server factory which provides an interface for querying\n        capabilities of the server.\n\n    @type timeOut: L{int}\n    @ivar timeOut: The number of seconds to wait for a command from the client\n        before disconnecting.\n\n    @type schedule: callable that takes interator and returns\n        L{Deferred <defer.Deferred>}\n    @ivar schedule: A callable that arranges for an iterator to be\n        cooperatively iterated over along with all other iterators which have\n        been passed to it such that runtime is divided between all of them.  It\n        returns a deferred which fires when the iterator finishes.\n\n    @type magic: L{bytes} or L{None}\n    @ivar magic: An APOP challenge.  If not set, an APOP challenge string\n        will be generated when a connection is made.\n\n    @type _userIs: L{bytes} or L{None}\n    @ivar _userIs: The username sent with the USER command.\n\n    @type _onLogout: no-argument callable or L{None}\n    @ivar _onLogout: The function to be executed when the connection is\n        lost.\n\n    @type mbox: L{IMailbox} provider\n    @ivar mbox: The mailbox for the authenticated user.\n\n    @type state: L{bytes}\n    @ivar state: The state which indicates what type of messages are expected\n        from the client.  Valid states are 'COMMAND' and 'AUTH'\n\n    @type blocked: L{None} or L{list} of 2-L{tuple} of\n        (E{1}) L{bytes} (E{2}) L{tuple} of L{bytes}\n    @ivar blocked: A list of blocked commands.  While a response to a command\n        is being generated by the server, other commands are blocked.  When\n        no command is outstanding, C{blocked} is set to none.  Otherwise, it\n        contains a list of information about blocked commands.  Each list\n        entry consists of the command and the arguments to the command.\n\n    @type _highest: L{int}\n    @ivar _highest: The 1-based index of the highest message retrieved.\n\n    @type _auth: L{IUsernameHashedPassword\n        <cred.credentials.IUsernameHashedPassword>} provider\n    @ivar _auth: Authorization credentials.\n    \"\"\"\n    magic = None\n    _userIs = None\n    _onLogout = None\n\n    AUTH_CMDS = [b'CAPA', b'USER', b'PASS', b'APOP', b'AUTH', b'RPOP', b'QUIT']\n\n    portal = None\n    factory = None\n\n    # The mailbox we're serving\n    mbox = None\n\n    # Set this pretty low -- POP3 clients are expected to log in, download\n    # everything, and log out.\n    timeOut = 300\n\n    state = \"COMMAND\"\n\n    # PIPELINE\n    blocked = None\n\n    # Cooperate and suchlike.\n    schedule = staticmethod(task.coiterate)\n\n    _highest = 0\n\n    def connectionMade(self):\n        \"\"\"\n        Send a greeting to the client after the connection has been made.\n        \"\"\"\n        if self.magic is None:\n            self.magic = self.generateMagic()\n        self.successResponse(self.magic)\n        self.setTimeout(self.timeOut)\n        if getattr(self.factory, 'noisy', True):\n            log.msg(\"New connection from \" + str(self.transport.getPeer()))\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Clean up when the connection has been lost.\n\n        @type reason: L{Failure}\n        @param reason: The reason the connection was terminated.\n        \"\"\"\n        if self._onLogout is not None:\n            self._onLogout()\n            self._onLogout = None\n        self.setTimeout(None)\n\n\n    def generateMagic(self):\n        \"\"\"\n        Generate an APOP challenge.\n\n        @rtype: L{bytes}\n        @return: An RFC 822 message id format string.\n        \"\"\"\n        return smtp.messageid()\n\n\n    def successResponse(self, message=''):\n        \"\"\"\n        Send a response indicating success.\n\n        @type message: stringifyable L{object}\n        @param message: An object whose string representation should be\n            included in the response.\n        \"\"\"\n        self.transport.write(successResponse(message))\n\n\n    def failResponse(self, message=b''):\n        \"\"\"\n        Send a response indicating failure.\n\n        @type message: stringifyable L{object}\n        @param message: An object whose string representation should be\n            included in the response.\n        \"\"\"\n        if not isinstance(message, bytes):\n            message = str(message).encode(\"utf-8\")\n        self.sendLine(b'-ERR ' + message)\n\n\n    def lineReceived(self, line):\n        \"\"\"\n        Pass a received line to a state machine function.\n\n        @type line: L{bytes}\n        @param line: A received line.\n        \"\"\"\n        self.resetTimeout()\n        getattr(self, 'state_' + self.state)(line)\n\n\n    def _unblock(self, _):\n        \"\"\"\n        Process as many blocked commands as possible.\n\n        If there are no more blocked commands, set up for the next command to\n        be sent immediately.\n\n        @type _: L{object}\n        @param _: Ignored.\n        \"\"\"\n        commands = self.blocked\n        self.blocked = None\n        while commands and self.blocked is None:\n            cmd, args = commands.pop(0)\n            self.processCommand(cmd, *args)\n        if self.blocked is not None:\n            self.blocked.extend(commands)\n\n\n    def state_COMMAND(self, line):\n        \"\"\"\n        Handle received lines for the COMMAND state in which commands from the\n        client are expected.\n\n        @type line: L{bytes}\n        @param line: A received command.\n        \"\"\"\n        try:\n            return self.processCommand(*line.split(b' '))\n        except (ValueError, AttributeError, POP3Error, TypeError) as e:\n            log.err()\n            self.failResponse('bad protocol or server: {}: {}'.format(\n                e.__class__.__name__, e))\n\n\n    def processCommand(self, command, *args):\n        \"\"\"\n        Dispatch a command from the client for handling.\n\n        @type command: L{bytes}\n        @param command: A POP3 command.\n\n        @type args: L{tuple} of L{bytes}\n        @param args: Arguments to the command.\n\n        @raise POP3Error: When the command is invalid or the command requires\n            prior authentication which hasn't been performed.\n        \"\"\"\n        if self.blocked is not None:\n            self.blocked.append((command, args))\n            return\n\n        command = command.upper()\n        authCmd = command in self.AUTH_CMDS\n        if not self.mbox and not authCmd:\n            raise POP3Error(b\"not authenticated yet: cannot do \" + command)\n        f = getattr(self, 'do_' + command.decode(\"utf-8\"), None)\n        if f:\n            return f(*args)\n        raise POP3Error(b\"Unknown protocol command: \" + command)\n\n\n    def listCapabilities(self):\n        \"\"\"\n        Return a list of server capabilities suitable for use in a CAPA\n        response.\n\n        @rtype: L{list} of L{bytes}\n        @return: A list of server capabilities.\n        \"\"\"\n        baseCaps = [\n            b\"TOP\",\n            b\"USER\",\n            b\"UIDL\",\n            b\"PIPELINE\",\n            b\"CELERITY\",\n            b\"AUSPEX\",\n            b\"POTENCE\",\n        ]\n\n        if IServerFactory.providedBy(self.factory):\n            # Oh my god.  We can't just loop over a list of these because\n            # each has spectacularly different return value semantics!\n            try:\n                v = self.factory.cap_IMPLEMENTATION()\n                if v and not isinstance(v, bytes):\n                    v = str(v).encode(\"utf-8\")\n            except NotImplementedError:\n                pass\n            except:\n                log.err()\n            else:\n                baseCaps.append(b\"IMPLEMENTATION \" + v)\n\n            try:\n                v = self.factory.cap_EXPIRE()\n                if v and not isinstance(v, bytes):\n                    v = str(v).encode(\"utf-8\")\n            except NotImplementedError:\n                pass\n            except:\n                log.err()\n            else:\n                if v is None:\n                    v = b\"NEVER\"\n                if self.factory.perUserExpiration():\n                    if self.mbox:\n                        v = str(self.mbox.messageExpiration).encode(\"utf-8\")\n                    else:\n                        v = v + b\" USER\"\n                baseCaps.append(b\"EXPIRE \" + v)\n\n            try:\n                v = self.factory.cap_LOGIN_DELAY()\n                if v and not isinstance(v, bytes):\n                    v = str(v).encode(\"utf-8\")\n            except NotImplementedError:\n                pass\n            except:\n                log.err()\n            else:\n                if self.factory.perUserLoginDelay():\n                    if self.mbox:\n                        v = str(self.mbox.loginDelay).encode(\"utf-8\")\n                    else:\n                        v = v + b\" USER\"\n                baseCaps.append(b\"LOGIN-DELAY \" + v)\n\n            try:\n                v = self.factory.challengers\n            except AttributeError:\n                pass\n            except:\n                log.err()\n            else:\n                baseCaps.append(b\"SASL \" + b' '.join(v.keys()))\n        return baseCaps\n\n\n    def do_CAPA(self):\n        \"\"\"\n        Handle a CAPA command.\n\n        Respond with the server capabilities.\n        \"\"\"\n        self.successResponse(b\"I can do the following:\")\n        for cap in self.listCapabilities():\n            self.sendLine(cap)\n        self.sendLine(b\".\")\n\n\n    def do_AUTH(self, args=None):\n        \"\"\"\n        Handle an AUTH command.\n\n        If the AUTH extension is not supported, send an error response.  If an\n        authentication mechanism was not specified in the command, send a list\n        of all supported authentication methods.  Otherwise, send an\n        authentication challenge to the client and transition to the\n        AUTH state.\n\n        @type args: L{bytes} or L{None}\n        @param args: The name of an authentication mechanism.\n        \"\"\"\n        if not getattr(self.factory, 'challengers', None):\n            self.failResponse(b\"AUTH extension unsupported\")\n            return\n\n        if args is None:\n            self.successResponse(\"Supported authentication methods:\")\n            for a in self.factory.challengers:\n                self.sendLine(a.upper())\n            self.sendLine(b\".\")\n            return\n\n        auth = self.factory.challengers.get(args.strip().upper())\n        if not self.portal or not auth:\n            self.failResponse(b\"Unsupported SASL selected\")\n            return\n\n        self._auth = auth()\n        chal = self._auth.getChallenge()\n\n        self.sendLine(b'+ ' + base64.encodestring(chal).rstrip(b'\\n'))\n        self.state = 'AUTH'\n\n\n    def state_AUTH(self, line):\n        \"\"\"\n        Handle received lines for the AUTH state in which an authentication\n        challenge response from the client is expected.\n\n        Transition back to the COMMAND state.  Check the credentials and\n        complete the authorization process with the L{_cbMailbox}\n        callback function on success or the L{_ebMailbox} and L{_ebUnexpected}\n        errback functions on failure.\n\n        @type line: L{bytes}\n        @param line: The challenge response.\n        \"\"\"\n        self.state = \"COMMAND\"\n        try:\n            parts = base64.decodestring(line).split(None, 1)\n        except binascii.Error:\n            self.failResponse(b\"Invalid BASE64 encoding\")\n        else:\n            if len(parts) != 2:\n                self.failResponse(b\"Invalid AUTH response\")\n                return\n            self._auth.username = parts[0]\n            self._auth.response = parts[1]\n            d = self.portal.login(self._auth, None, IMailbox)\n            d.addCallback(self._cbMailbox, parts[0])\n            d.addErrback(self._ebMailbox)\n            d.addErrback(self._ebUnexpected)\n\n\n    def do_APOP(self, user, digest):\n        \"\"\"\n        Handle an APOP command.\n\n        Perform APOP authentication and complete the authorization process with\n        the L{_cbMailbox} callback function on success or the L{_ebMailbox}\n        and L{_ebUnexpected} errback functions on failure.\n\n        @type user: L{bytes}\n        @param user: A username.\n\n        @type digest: L{bytes}\n        @param digest: An MD5 digest string.\n        \"\"\"\n        d = defer.maybeDeferred(self.authenticateUserAPOP, user, digest)\n        d.addCallbacks(self._cbMailbox, self._ebMailbox, callbackArgs=(user,)\n        ).addErrback(self._ebUnexpected)\n\n\n    def _cbMailbox(self, result, user):\n        \"\"\"\n        Complete successful authentication.\n\n        Save the mailbox and logout function for the authenticated user and\n        send a successful response to the client.\n\n        @type result: C{tuple}\n        @param interface_avatar_logout: The first item of the tuple is a\n            C{zope.interface.Interface} which is the interface\n            supported by the avatar.  The second item of the tuple is a\n            L{IMailbox} provider which is the mailbox for the\n            authenticated user.  The third item of the tuple is a no-argument\n            callable which is a function to be invoked when the session is\n            terminated.\n\n        @type user: L{bytes}\n        @param user: The user being authenticated.\n        \"\"\"\n        (interface, avatar, logout) = result\n        if interface is not IMailbox:\n            self.failResponse(b'Authentication failed')\n            log.err(\n                \"_cbMailbox() called with an interface other than IMailbox\"\n            )\n            return\n\n        self.mbox = avatar\n        self._onLogout = logout\n        self.successResponse('Authentication succeeded')\n        if getattr(self.factory, 'noisy', True):\n            log.msg(b\"Authenticated login for \" + user)\n\n\n    def _ebMailbox(self, failure):\n        \"\"\"\n        Handle an expected authentication failure.\n\n        Send an appropriate error response for a L{LoginDenied} or\n        L{LoginFailed} authentication failure.\n\n        @type failure: L{Failure}\n        @param failure: The authentication error.\n        \"\"\"\n        failure = failure.trap(cred.error.LoginDenied, cred.error.LoginFailed)\n        if issubclass(failure, cred.error.LoginDenied):\n            self.failResponse(\"Access denied: \" + str(failure))\n        elif issubclass(failure, cred.error.LoginFailed):\n            self.failResponse(b'Authentication failed')\n        if getattr(self.factory, 'noisy', True):\n            log.msg(\n                \"Denied login attempt from \" + str(self.transport.getPeer())\n            )\n\n\n    def _ebUnexpected(self, failure):\n        \"\"\"\n        Handle an unexpected authentication failure.\n\n        Send an error response for an unexpected authentication failure.\n\n        @type failure: L{Failure}\n        @param failure: The authentication error.\n        \"\"\"\n        self.failResponse('Server error: ' + failure.getErrorMessage())\n        log.err(failure)\n\n\n    def do_USER(self, user):\n        \"\"\"\n        Handle a USER command.\n\n        Save the username and send a successful response prompting the client\n        for the password.\n\n        @type user: L{bytes}\n        @param user: A username.\n        \"\"\"\n        self._userIs = user\n        self.successResponse(b'USER accepted, send PASS')\n\n\n    def do_PASS(self, password):\n        \"\"\"\n        Handle a PASS command.\n\n        If a USER command was previously received, authenticate the user and\n        complete the authorization process with the L{_cbMailbox} callback\n        function on success or the L{_ebMailbox} and L{_ebUnexpected} errback\n        functions on failure.  If a USER command was not previously received,\n        send an error response.\n\n        @type password: L{bytes}\n        @param password: A password.\n        \"\"\"\n        if self._userIs is None:\n            self.failResponse(b\"USER required before PASS\")\n            return\n        user = self._userIs\n        self._userIs = None\n        d = defer.maybeDeferred(self.authenticateUserPASS, user, password)\n        d.addCallbacks(self._cbMailbox, self._ebMailbox, callbackArgs=(user,)\n        ).addErrback(self._ebUnexpected)\n\n\n    def _longOperation(self, d):\n        \"\"\"\n        Stop timeouts and block further command processing while a long\n        operation completes.\n\n        @type d: L{Deferred <defer.Deferred>}\n        @param d: A deferred which triggers at the completion of a long\n            operation.\n\n        @rtype: L{Deferred <defer.Deferred>}\n        @return: A deferred which triggers after command processing resumes and\n            timeouts restart after the completion of a long operation.\n        \"\"\"\n        timeOut = self.timeOut\n        self.setTimeout(None)\n        self.blocked = []\n        d.addCallback(self._unblock)\n        d.addCallback(lambda ign: self.setTimeout(timeOut))\n        return d\n\n\n    def _coiterate(self, gen):\n        \"\"\"\n        Direct the output of an iterator to the transport and arrange for\n        iteration to take place.\n\n        @type gen: iterable which yields L{bytes}\n        @param gen: An iterator over strings.\n\n        @rtype: L{Deferred <defer.Deferred>}\n        @return: A deferred which fires when the iterator finishes.\n        \"\"\"\n        return self.schedule(\n            _IteratorBuffer(self.transport.writeSequence, gen)\n        )\n\n\n    def do_STAT(self):\n        \"\"\"\n        Handle a STAT command.\n\n        @rtype: L{Deferred <defer.Deferred>}\n        @return: A deferred which triggers after the response to the STAT\n            command has been issued.\n        \"\"\"\n        d = defer.maybeDeferred(self.mbox.listMessages)\n        def cbMessages(msgs):\n            return self._coiterate(formatStatResponse(msgs))\n        def ebMessages(err):\n            self.failResponse(err.getErrorMessage())\n            log.msg(\"Unexpected do_STAT failure:\")\n            log.err(err)\n        return self._longOperation(d.addCallbacks(cbMessages, ebMessages))\n\n\n    def do_LIST(self, i=None):\n        \"\"\"\n        Handle a LIST command.\n\n        @type i: L{bytes} or L{None}\n        @param i: A 1-based message index.\n\n        @rtype: L{Deferred <defer.Deferred>}\n        @return: A deferred which triggers after the response to the LIST\n            command has been issued.\n        \"\"\"\n        if i is None:\n            d = defer.maybeDeferred(self.mbox.listMessages)\n            def cbMessages(msgs):\n                return self._coiterate(formatListResponse(msgs))\n            def ebMessages(err):\n                self.failResponse(err.getErrorMessage())\n                log.msg(\"Unexpected do_LIST failure:\")\n                log.err(err)\n            return self._longOperation(d.addCallbacks(cbMessages, ebMessages))\n        else:\n            try:\n                i = int(i)\n                if i < 1:\n                    raise ValueError()\n            except ValueError:\n                if not isinstance(i, bytes):\n                    i = str(i).encode(\"utf-8\")\n                self.failResponse(b\"Invalid message-number: \" + i)\n            else:\n                d = defer.maybeDeferred(self.mbox.listMessages, i - 1)\n                def cbMessage(msg):\n                    self.successResponse(intToBytes(i) + b' ' +\n                                         intToBytes(msg))\n                def ebMessage(err):\n                    errcls = err.check(ValueError, IndexError)\n                    if errcls is not None:\n                        if errcls is IndexError:\n                            # IndexError was supported for a while, but really\n                            # shouldn't be.  One error condition, one exception\n                            # type.  See ticket #6669.\n                            warnings.warn(\n                                \"twisted.mail.pop3.IMailbox.listMessages may \"\n                                \"not raise IndexError for out-of-bounds \"\n                                \"message numbers: raise ValueError instead.\",\n                                PendingDeprecationWarning)\n                        invalidNum = i\n                        if invalidNum and not isinstance(invalidNum, bytes):\n                            invalidNum = str(invalidNum).encode(\"utf-8\")\n                        self.failResponse(b\"Invalid message-number: \" +\n                                          invalidNum)\n                    else:\n                        self.failResponse(err.getErrorMessage())\n                        log.msg(\"Unexpected do_LIST failure:\")\n                        log.err(err)\n                d.addCallbacks(cbMessage, ebMessage)\n                return self._longOperation(d)\n\n\n    def do_UIDL(self, i=None):\n        \"\"\"\n        Handle a UIDL command.\n\n        @type i: L{bytes} or L{None}\n        @param i: A 1-based message index.\n\n        @rtype: L{Deferred <defer.Deferred>}\n        @return: A deferred which triggers after the response to the UIDL\n            command has been issued.\n        \"\"\"\n        if i is None:\n            d = defer.maybeDeferred(self.mbox.listMessages)\n            def cbMessages(msgs):\n                return self._coiterate(\n                    formatUIDListResponse(msgs, self.mbox.getUidl),\n                )\n            def ebMessages(err):\n                self.failResponse(err.getErrorMessage())\n                log.msg(\"Unexpected do_UIDL failure:\")\n                log.err(err)\n            return self._longOperation(d.addCallbacks(cbMessages, ebMessages))\n        else:\n            try:\n                i = int(i)\n                if i < 1:\n                    raise ValueError()\n            except ValueError:\n                self.failResponse(\"Bad message number argument\")\n            else:\n                try:\n                    msg = self.mbox.getUidl(i - 1)\n                except IndexError:\n                    # XXX TODO See above comment regarding IndexError.\n                    warnings.warn(\n                        \"twisted.mail.pop3.IMailbox.getUidl may not \"\n                        \"raise IndexError for out-of-bounds message numbers: \"\n                        \"raise ValueError instead.\",\n                        PendingDeprecationWarning)\n                    self.failResponse(\"Bad message number argument\")\n                except ValueError:\n                    self.failResponse(\"Bad message number argument\")\n                else:\n                    if not isinstance(msg, bytes):\n                        msg = str(msg).encode(\"utf-8\")\n                    self.successResponse(msg)\n\n\n    def _getMessageFile(self, i):\n        \"\"\"\n        Retrieve the size and contents of a message.\n\n        @type i: L{bytes}\n        @param i: A 1-based message index.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            2-L{tuple} of (E{1}) L{int}, (E{2}) file-like object\n        @return: A deferred which successfully fires with the size of the\n            message and a file containing the contents of the message.\n        \"\"\"\n        try:\n            msg = int(i) - 1\n            if msg < 0:\n                raise ValueError()\n        except ValueError:\n            self.failResponse(\"Bad message number argument\")\n            return defer.succeed(None)\n\n        sizeDeferred = defer.maybeDeferred(self.mbox.listMessages, msg)\n        def cbMessageSize(size):\n            if not size:\n                return defer.fail(_POP3MessageDeleted())\n            fileDeferred = defer.maybeDeferred(self.mbox.getMessage, msg)\n            fileDeferred.addCallback(lambda fObj: (size, fObj))\n            return fileDeferred\n\n        def ebMessageSomething(err):\n            errcls = err.check(_POP3MessageDeleted, ValueError, IndexError)\n            if errcls is _POP3MessageDeleted:\n                self.failResponse(\"message deleted\")\n            elif errcls in (ValueError, IndexError):\n                if errcls is IndexError:\n                    # XXX TODO See above comment regarding IndexError.\n                    warnings.warn(\n                        \"twisted.mail.pop3.IMailbox.listMessages may not \"\n                        \"raise IndexError for out-of-bounds message numbers: \"\n                        \"raise ValueError instead.\",\n                        PendingDeprecationWarning)\n                self.failResponse(\"Bad message number argument\")\n            else:\n                log.msg(\"Unexpected _getMessageFile failure:\")\n                log.err(err)\n            return None\n\n        sizeDeferred.addCallback(cbMessageSize)\n        sizeDeferred.addErrback(ebMessageSomething)\n        return sizeDeferred\n\n\n    def _sendMessageContent(self, i, fpWrapper, successResponse):\n        \"\"\"\n        Send the contents of a message.\n\n        @type i: L{bytes}\n        @param i: A 1-based message index.\n\n        @type fpWrapper: callable that takes a file-like object and returns\n            a file-like object\n        @param fpWrapper:\n\n        @type successResponse: callable that takes L{int} and returns\n            L{bytes}\n        @param successResponse:\n\n        @rtype: L{Deferred}\n        @return: A deferred which triggers after the message has been sent.\n        \"\"\"\n        d = self._getMessageFile(i)\n        def cbMessageFile(info):\n            if info is None:\n                # Some error occurred - a failure response has been sent\n                # already, just give up.\n                return\n\n            self._highest = max(self._highest, int(i))\n            resp, fp = info\n            fp = fpWrapper(fp)\n            self.successResponse(successResponse(resp))\n            s = basic.FileSender()\n            d = s.beginFileTransfer(fp, self.transport, self.transformChunk)\n\n            def cbFileTransfer(lastsent):\n                if lastsent != b'\\n':\n                    line = b'\\r\\n.'\n                else:\n                    line = b'.'\n                self.sendLine(line)\n\n            def ebFileTransfer(err):\n                self.transport.loseConnection()\n                log.msg(\"Unexpected error in _sendMessageContent:\")\n                log.err(err)\n\n            d.addCallback(cbFileTransfer)\n            d.addErrback(ebFileTransfer)\n            return d\n        return self._longOperation(d.addCallback(cbMessageFile))\n\n\n    def do_TOP(self, i, size):\n        \"\"\"\n        Handle a TOP command.\n\n        @type i: L{bytes}\n        @param i: A 1-based message index.\n\n        @type size: L{bytes}\n        @param size: The number of lines of the message to retrieve.\n\n        @rtype: L{Deferred}\n        @return: A deferred which triggers after the response to the TOP\n            command has been issued.\n        \"\"\"\n        try:\n            size = int(size)\n            if size < 0:\n                raise ValueError\n        except ValueError:\n            self.failResponse(\"Bad line count argument\")\n        else:\n            return self._sendMessageContent(\n                i,\n                lambda fp: _HeadersPlusNLines(fp, size),\n                lambda size: \"Top of message follows\")\n\n\n    def do_RETR(self, i):\n        \"\"\"\n        Handle a RETR command.\n\n        @type i: L{bytes}\n        @param i: A 1-based message index.\n\n        @rtype: L{Deferred}\n        @return: A deferred which triggers after the response to the RETR\n            command has been issued.\n        \"\"\"\n        return self._sendMessageContent(\n            i,\n            lambda fp: fp,\n            lambda size: \"%d\" % (size,))\n\n\n    def transformChunk(self, chunk):\n        \"\"\"\n        Transform a chunk of a message to POP3 message format.\n\n        Make sure each line ends with C{'\\\\r\\\\n'} and byte-stuff the\n        termination character (C{'.'}) by adding an extra one when one appears\n        at the beginning of a line.\n\n        @type chunk: L{bytes}\n        @param chunk: A string to transform.\n\n        @rtype: L{bytes}\n        @return: The transformed string.\n        \"\"\"\n        return chunk.replace(b'\\n', b'\\r\\n').replace(b'\\r\\n.', b'\\r\\n..')\n\n\n    def finishedFileTransfer(self, lastsent):\n        \"\"\"\n        Send the termination sequence.\n\n        @type lastsent: L{bytes}\n        @param lastsent: The last character of the file.\n        \"\"\"\n        if lastsent != b'\\n':\n            line = b'\\r\\n.'\n        else:\n            line = b'.'\n        self.sendLine(line)\n\n\n    def do_DELE(self, i):\n        \"\"\"\n        Handle a DELE command.\n\n        Mark a message for deletion and issue a successful response.\n\n        @type i: L{int}\n        @param i: A 1-based message index.\n        \"\"\"\n        i = int(i)-1\n        self.mbox.deleteMessage(i)\n        self.successResponse()\n\n\n    def do_NOOP(self):\n        \"\"\"\n        Handle a NOOP command.\n\n        Do nothing but issue a successful response.\n        \"\"\"\n        self.successResponse()\n\n\n    def do_RSET(self):\n        \"\"\"\n        Handle a RSET command.\n\n        Unmark any messages that have been flagged for deletion.\n        \"\"\"\n        try:\n            self.mbox.undeleteMessages()\n        except:\n            log.err()\n            self.failResponse()\n        else:\n            self._highest = 0\n            self.successResponse()\n\n\n    def do_LAST(self):\n        \"\"\"\n        Handle a LAST command.\n\n        Respond with the 1-based index of the highest retrieved message.\n        \"\"\"\n        self.successResponse(self._highest)\n\n\n    def do_RPOP(self, user):\n        \"\"\"\n        Handle an RPOP command.\n\n        RPOP is not supported.  Send an error response.\n\n        @type user: L{bytes}\n        @param user: A username.\n\n        \"\"\"\n        self.failResponse('permission denied, sucker')\n\n\n    def do_QUIT(self):\n        \"\"\"\n        Handle a QUIT command.\n\n        Remove any messages marked for deletion, issue a successful response,\n        and drop the connection.\n        \"\"\"\n        if self.mbox:\n            self.mbox.sync()\n        self.successResponse()\n        self.transport.loseConnection()\n\n\n    def authenticateUserAPOP(self, user, digest):\n        \"\"\"\n        Perform APOP authentication.\n\n        @type user: L{bytes}\n        @param user: The name of the user attempting to log in.\n\n        @type digest: L{bytes}\n        @param digest: The challenge response.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully results in\n            3-L{tuple} of (E{1}) L{IMailbox <pop3.IMailbox>}, (E{2})\n            L{IMailbox <pop3.IMailbox>} provider, (E{3}) no-argument callable\n        @return: A deferred which fires when authentication is complete.  If\n            successful, it returns an L{IMailbox <pop3.IMailbox>} interface, a\n            mailbox, and a function to be invoked with the session is\n            terminated.  If authentication fails, the deferred fails with an\n            L{UnathorizedLogin <cred.error.UnauthorizedLogin>} error.\n\n        @raise cred.error.UnauthorizedLogin: When authentication fails.\n        \"\"\"\n        if self.portal is not None:\n            return self.portal.login(\n                APOPCredentials(self.magic, user, digest),\n                None,\n                IMailbox\n            )\n        raise cred.error.UnauthorizedLogin()\n\n\n    def authenticateUserPASS(self, user, password):\n        \"\"\"\n        Perform authentication for a username/password login.\n\n        @type user: L{bytes}\n        @param user: The name of the user attempting to log in.\n\n        @type password: L{bytes}\n        @param password: The password to authenticate with.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully results in\n            3-L{tuple} of (E{1}) L{IMailbox <pop3.IMailbox>}, (E{2}) L{IMailbox\n            <pop3.IMailbox>} provider, (E{3}) no-argument callable\n        @return: A deferred which fires when authentication is complete.  If\n            successful, it returns a L{pop3.IMailbox} interface, a mailbox,\n            and a function to be invoked with the session is terminated.\n            If authentication fails, the deferred fails with an\n            L{UnathorizedLogin <cred.error.UnauthorizedLogin>} error.\n\n        @raise cred.error.UnauthorizedLogin: When authentication fails.\n        \"\"\"\n        if self.portal is not None:\n            return self.portal.login(\n                cred.credentials.UsernamePassword(user, password),\n                None,\n                IMailbox\n            )\n        raise cred.error.UnauthorizedLogin()\n\n\n\n@implementer(IMailbox)\nclass Mailbox:\n    \"\"\"\n    A base class for mailboxes.\n    \"\"\"\n    def listMessages(self, i=None):\n        \"\"\"\n        Retrieve the size of a message, or, if none is specified, the size of\n        each message in the mailbox.\n\n        @type i: L{int} or L{None}\n        @param i: The 0-based index of the message.\n\n        @rtype: L{int}, sequence of L{int}, or L{Deferred <defer.Deferred>}\n        @return: The number of octets in the specified message, or, if an\n            index is not specified, a sequence of the number of octets for\n            all messages in the mailbox or a deferred which fires with\n            one of those. Any value which corresponds to a deleted message\n            is set to 0.\n\n        @raise ValueError or IndexError: When the index does not correspond to\n            a message in the mailbox.  The use of ValueError is preferred.\n        \"\"\"\n        return []\n\n\n    def getMessage(self, i):\n        \"\"\"\n        Retrieve a file containing the contents of a message.\n\n        @type i: L{int}\n        @param i: The 0-based index of a message.\n\n        @rtype: file-like object\n        @return: A file containing the message.\n\n        @raise ValueError or IndexError: When the index does not correspond to\n            a message in the mailbox.  The use of ValueError is preferred.\n        \"\"\"\n        raise ValueError\n\n\n    def getUidl(self, i):\n        \"\"\"\n        Get a unique identifier for a message.\n\n        @type i: L{int}\n        @param i: The 0-based index of a message.\n\n        @rtype: L{bytes}\n        @return: A string of printable characters uniquely identifying the\n            message for all time.\n\n        @raise ValueError or IndexError: When the index does not correspond to\n            a message in the mailbox.  The use of ValueError is preferred.\n        \"\"\"\n        raise ValueError\n\n\n    def deleteMessage(self, i):\n        \"\"\"\n        Mark a message for deletion.\n\n        This must not change the number of messages in this mailbox.  Further\n        requests for the size of the deleted message should return 0.  Further\n        requests for the message itself may raise an exception.\n\n        @type i: L{int}\n        @param i: The 0-based index of a message.\n\n        @raise ValueError or IndexError: When the index does not correspond to\n            a message in the mailbox.  The use of ValueError is preferred.\n        \"\"\"\n        raise ValueError\n\n\n    def undeleteMessages(self):\n        \"\"\"\n        Undelete all messages marked for deletion.\n\n        Any message which can be undeleted should be returned to its original\n        position in the message sequence and retain its original UID.\n        \"\"\"\n        pass\n\n\n    def sync(self):\n        \"\"\"\n        Discard the contents of any message marked for deletion.\n        \"\"\"\n        pass\n\n\n\nNONE, SHORT, FIRST_LONG, LONG = range(4)\n\nNEXT = {}\nNEXT[NONE] = NONE\nNEXT[SHORT] = NONE\nNEXT[FIRST_LONG] = LONG\nNEXT[LONG] = NONE\n\n\n\nclass POP3Client(basic.LineOnlyReceiver):\n    \"\"\"\n    A POP3 client protocol.\n\n    @type mode: L{int}\n    @ivar mode: The type of response expected from the server.  Choices include\n    none (0), a one line response (1), the first line of a multi-line\n    response (2), and subsequent lines of a multi-line response (3).\n\n    @type command: L{bytes}\n    @ivar command: The command most recently sent to the server.\n\n    @type welcomeRe: L{RegexObject <re.RegexObject>}\n    @ivar welcomeRe: A regular expression which matches the APOP challenge in\n        the server greeting.\n\n    @type welcomeCode: L{bytes}\n    @ivar welcomeCode: The APOP challenge passed in the server greeting.\n    \"\"\"\n    mode = SHORT\n    command = b'WELCOME'\n    import re\n    welcomeRe = re.compile(b'<(.*)>')\n\n    def __init__(self):\n        \"\"\"\n        Issue deprecation warning.\n        \"\"\"\n        import warnings\n        warnings.warn(\"twisted.mail.pop3.POP3Client is deprecated, \"\n                      \"please use twisted.mail.pop3.AdvancedPOP3Client \"\n                      \"instead.\", DeprecationWarning,\n                      stacklevel=3)\n\n\n    def sendShort(self, command, params=None):\n        \"\"\"\n        Send a POP3 command to which a short response is expected.\n\n        @type command: L{bytes}\n        @param command: A POP3 command.\n\n        @type params: stringifyable L{object} or L{None}\n        @param params: Command arguments.\n        \"\"\"\n        if params is not None:\n            if not isinstance(params, bytes):\n                params = str(params).encode(\"utf-8\")\n            self.sendLine(command + b' ' + params)\n        else:\n            self.sendLine(command)\n        self.command = command\n        self.mode = SHORT\n\n\n    def sendLong(self, command, params):\n        \"\"\"\n        Send a POP3 command to which a long response is expected.\n\n        @type command: L{bytes}\n        @param command: A POP3 command.\n\n        @type params: stringifyable L{object}\n        @param params: Command arguments.\n        \"\"\"\n        if params:\n            if not isinstance(params, bytes):\n                params = str(params).encode(\"utf-8\")\n            self.sendLine(command + b' ' + params)\n        else:\n            self.sendLine(command)\n        self.command = command\n        self.mode = FIRST_LONG\n\n\n    def handle_default(self, line):\n        \"\"\"\n        Handle responses from the server for which no other handler exists.\n\n        @type line: L{bytes}\n        @param line: A received line.\n        \"\"\"\n        if line[:-4] == b'-ERR':\n            self.mode = NONE\n\n\n    def handle_WELCOME(self, line):\n        \"\"\"\n        Handle a server response which is expected to be a server greeting.\n\n        @type line: L{bytes}\n        @param line: A received line.\n        \"\"\"\n        code, data = line.split(b' ', 1)\n        if code != b'+OK':\n            self.transport.loseConnection()\n        else:\n            m = self.welcomeRe.match(line)\n            if m:\n                self.welcomeCode = m.group(1)\n\n\n    def _dispatch(self, command, default, *args):\n        \"\"\"\n        Dispatch a response from the server for handling.\n\n        Command X is dispatched to handle_X() if it exists.  If not, it is\n        dispatched to the default handler.\n\n        @type command: L{bytes}\n        @param command: The command.\n\n        @type default: callable that takes L{bytes} or\n            L{None}\n        @param default: The default handler.\n\n        @type args: L{tuple} or L{None}\n        @param args: Arguments to the handler function.\n        \"\"\"\n        try:\n            method = getattr(self, 'handle_' + command.decode(\"utf-8\"),\n                             default)\n            if method is not None:\n                method(*args)\n        except:\n            log.err()\n\n\n    def lineReceived(self, line):\n        \"\"\"\n        Dispatch a received line for processing.\n\n        The choice of function to handle the received line is based on the\n        type of response expected to the command sent to the server and how\n        much of that response has been received.\n\n        An expected one line response to command X is handled by handle_X().\n        The first line of a multi-line response to command X is also handled by\n        handle_X().  Subsequent lines of the multi-line response are handled by\n        handle_X_continue() except for the last line which is handled by\n        handle_X_end().\n\n        @type line: L{bytes}\n        @param line: A received line.\n        \"\"\"\n        if self.mode == SHORT or self.mode == FIRST_LONG:\n            self.mode = NEXT[self.mode]\n            self._dispatch(self.command, self.handle_default, line)\n        elif self.mode == LONG:\n            if line == b'.':\n                self.mode = NEXT[self.mode]\n                self._dispatch(self.command + b'_end', None)\n                return\n            if line[:1] == b'.':\n                line = line[1:]\n            self._dispatch(self.command + b\"_continue\", None, line)\n\n\n    def apopAuthenticate(self, user, password, magic):\n        \"\"\"\n        Perform an authenticated login.\n\n        @type user: L{bytes}\n        @param user: The username with which to log in.\n\n        @type password: L{bytes}\n        @param password: The password with which to log in.\n\n        @type magic: L{bytes}\n        @param magic: The challenge provided by the server.\n        \"\"\"\n        digest = md5(magic + password).hexdigest().encode(\"ascii\")\n        self.apop(user, digest)\n\n\n    def apop(self, user, digest):\n        \"\"\"\n        Send an APOP command to perform authenticated login.\n\n        @type user: L{bytes}\n        @param user: The username with which to log in.\n\n        @type digest: L{bytes}\n        @param digest: The challenge response with which to authenticate.\n        \"\"\"\n        self.sendLong(b'APOP', b' '.join((user, digest)))\n\n\n    def retr(self, i):\n        \"\"\"\n        Send a RETR command to retrieve a message from the server.\n\n        @type i: L{int} or L{bytes}\n        @param i: A 0-based message index.\n        \"\"\"\n        self.sendLong(b'RETR', i)\n\n\n    def dele(self, i):\n        \"\"\"\n        Send a DELE command to delete a message from the server.\n\n        @type i: L{int} or L{bytes}\n        @param i: A 0-based message index.\n        \"\"\"\n        self.sendShort(b'DELE', i)\n\n\n    def list(self, i=''):\n        \"\"\"\n        Send a LIST command to retrieve the size of a message or, if no message\n        is specified, the sizes of all messages.\n\n        @type i: L{int} or L{bytes}\n        @param i: A 0-based message index or the empty string to specify all\n            messages.\n        \"\"\"\n        self.sendLong(b'LIST', i)\n\n\n    def uidl(self, i=''):\n        \"\"\"\n        Send a UIDL command to retrieve the unique identifier of a message or,\n        if no message is specified, the unique identifiers of all messages.\n\n        @type i: L{int} or L{bytes}\n        @param i: A 0-based message index or the empty string to specify all\n            messages.\n        \"\"\"\n        self.sendLong(b'UIDL', i)\n\n\n    def user(self, name):\n        \"\"\"\n        Send a USER command to perform the first half of a plaintext login.\n\n        @type name: L{bytes}\n        @param name: The username with which to log in.\n        \"\"\"\n        self.sendShort(b'USER', name)\n\n\n    def password(self, password):\n        \"\"\"\n        Perform the second half of a plaintext login.\n\n        @type password: L{bytes}\n        @param password: The plaintext password with which to authenticate.\n        \"\"\"\n        self.sendShort(b'PASS', password)\n\n    pass_ = password\n\n    def quit(self):\n        \"\"\"\n        Send a QUIT command to disconnect from the server.\n        \"\"\"\n        self.sendShort(b'QUIT')\n\n\nfrom twisted.mail.pop3client import POP3Client as AdvancedPOP3Client\nfrom twisted.mail.pop3client import InsecureAuthenticationDisallowed\nfrom twisted.mail.pop3client import ServerErrorResponse\nfrom twisted.mail.pop3client import LineTooLong\nfrom twisted.mail.pop3client import TLSError\nfrom twisted.mail.pop3client import TLSNotSupportedError\n\n__all__ = [\n    # Interfaces\n    'IMailbox', 'IServerFactory',\n\n    # Exceptions\n    'POP3Error', 'POP3ClientError', 'InsecureAuthenticationDisallowed',\n    'ServerErrorResponse', 'LineTooLong', 'TLSError', 'TLSNotSupportedError',\n\n    # Protocol classes\n    'POP3', 'POP3Client', 'AdvancedPOP3Client',\n\n    # Misc\n    'APOPCredentials', 'Mailbox']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/pop3client.py",
    "content": "# -*- test-case-name: twisted.mail.test.test_pop3client -*-\n# Copyright (c) 2001-2004 Divmod Inc.\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nA POP3 client protocol implementation.\n\nDon't use this module directly.  Use twisted.mail.pop3 instead.\n\n@author: Jp Calderone\n\"\"\"\n\nimport re\nfrom hashlib import md5\n\nfrom twisted.python import log\nfrom twisted.python.compat import intToBytes\nfrom twisted.internet import defer\nfrom twisted.protocols import basic\nfrom twisted.protocols import policies\nfrom twisted.internet import error\nfrom twisted.internet import interfaces\nfrom twisted.mail._except import (\n    InsecureAuthenticationDisallowed, TLSError,\n    TLSNotSupportedError, ServerErrorResponse, LineTooLong)\n\nOK = b'+OK'\nERR = b'-ERR'\n\n\n\nclass _ListSetter:\n    \"\"\"\n    A utility class to construct a list from a multi-line response accounting\n    for deleted messages.\n\n    POP3 responses sometimes occur in the form of a list of lines containing\n    two pieces of data, a message index and a value of some sort.  When a\n    message is deleted, it is omitted from these responses.  The L{setitem}\n    method of this class is meant to be called with these two values.  In the\n    cases where indices are skipped, it takes care of padding out the missing\n    values with L{None}.\n\n    @ivar L: See L{__init__}\n    \"\"\"\n    def __init__(self, L):\n        \"\"\"\n        @type L: L{list} of L{object}\n        @param L: The list being constructed.  An empty list should be\n            passed in.\n        \"\"\"\n        self.L = L\n\n\n    def setitem(self, itemAndValue):\n        \"\"\"\n        Add the value at the specified position, padding out missing entries.\n\n        @type itemAndValue: C{tuple}\n        @param item: A tuple of (item, value).  The I{item} is the 0-based\n        index in the list at which the value should be placed.  The value is\n        is an L{object} to put in the list.\n        \"\"\"\n        (item, value) = itemAndValue\n        diff = item - len(self.L) + 1\n        if diff > 0:\n            self.L.extend([None] * diff)\n        self.L[item] = value\n\n\n\ndef _statXform(line):\n    \"\"\"\n    Parse the response to a STAT command.\n\n    @type line: L{bytes}\n    @param line: The response from the server to a STAT command minus the\n        status indicator.\n\n    @rtype: 2-L{tuple} of (0) L{int}, (1) L{int}\n    @return: The number of messages in the mailbox and the size of the mailbox.\n    \"\"\"\n    numMsgs, totalSize = line.split(None, 1)\n    return int(numMsgs), int(totalSize)\n\n\n\ndef _listXform(line):\n    \"\"\"\n    Parse a line of the response to a LIST command.\n\n    The line from the LIST response consists of a 1-based message number\n    followed by a size.\n\n    @type line: L{bytes}\n    @param line: A non-initial line from the multi-line response to a LIST\n        command.\n\n    @rtype: 2-L{tuple} of (0) L{int}, (1) L{int}\n    @return: The 0-based index of the message and the size of the message.\n    \"\"\"\n    index, size = line.split(None, 1)\n    return int(index) - 1, int(size)\n\n\n\ndef _uidXform(line):\n    \"\"\"\n    Parse a line of the response to a UIDL command.\n\n    The line from the UIDL response consists of a 1-based message number\n    followed by a unique id.\n\n    @type line: L{bytes}\n    @param line: A non-initial line from the multi-line response to a UIDL\n        command.\n\n    @rtype: 2-L{tuple} of (0) L{int}, (1) L{bytes}\n    @return: The 0-based index of the message and the unique identifier\n        for the message.\n    \"\"\"\n    index, uid = line.split(None, 1)\n    return int(index) - 1, uid\n\n\n\ndef _codeStatusSplit(line):\n    \"\"\"\n    Parse the first line of a multi-line server response.\n\n    @type line: L{bytes}\n    @param line: The first line of a multi-line server response.\n\n    @rtype: 2-tuple of (0) L{bytes}, (1) L{bytes}\n    @return: The status indicator and the rest of the server response.\n    \"\"\"\n    parts = line.split(b' ', 1)\n    if len(parts) == 1:\n        return parts[0], b''\n    return parts\n\n\n\ndef _dotUnquoter(line):\n    \"\"\"\n    Remove a byte-stuffed termination character at the beginning of a line if\n    present.\n\n    When the termination character (C{'.'}) appears at the beginning of a line,\n    the server byte-stuffs it by adding another termination character to\n    avoid confusion with the terminating sequence (C{'.\\\\r\\\\n'}).\n\n    @type line: L{bytes}\n    @param line: A received line.\n\n    @rtype: L{bytes}\n    @return: The line without the byte-stuffed termination character at the\n        beginning if it was present. Otherwise, the line unchanged.\n    \"\"\"\n    if line.startswith(b'..'):\n        return line[1:]\n    return line\n\n\n\nclass POP3Client(basic.LineOnlyReceiver, policies.TimeoutMixin):\n    \"\"\"\n    A POP3 client protocol.\n\n    Instances of this class provide a convenient, efficient API for\n    retrieving and deleting messages from a POP3 server.\n\n    This API provides a pipelining interface but POP3 pipelining\n    on the network is not yet supported.\n\n    @type startedTLS: L{bool}\n    @ivar startedTLS: An indication of whether TLS has been negotiated\n        successfully.\n\n    @type allowInsecureLogin: L{bool}\n    @ivar allowInsecureLogin: An indication of whether plaintext login should\n        be allowed when the server offers no authentication challenge and the\n        transport does not offer any protection via encryption.\n\n    @type serverChallenge: L{bytes} or L{None}\n    @ivar serverChallenge: The challenge received in the server greeting.\n\n    @type timeout: L{int}\n    @ivar timeout: The number of seconds to wait on a response from the server\n        before timing out a connection.  If the number is <= 0, no timeout\n        checking will be performed.\n\n    @type _capCache: L{None} or L{dict} mapping L{bytes}\n        to L{list} of L{bytes} and/or L{bytes} to L{None}\n    @ivar _capCache: The cached server capabilities.  Capabilities are not\n        allowed to change during the session (except when TLS is negotiated),\n        so the first response to a capabilities command can be used for\n        later lookups.\n\n    @type _challengeMagicRe: L{RegexObject <re.RegexObject>}\n    @ivar _challengeMagicRe: A regular expression which matches the\n        challenge in the server greeting.\n\n    @type _blockedQueue: L{None} or L{list} of 3-L{tuple}\n        of (0) L{Deferred <defer.Deferred>}, (1) callable which results\n        in a L{Deferred <defer.Deferred>}, (2) L{tuple}\n    @ivar _blockedQueue: A list of blocked commands.  While a command is\n        awaiting a response from the server, other commands are blocked.  When\n        no command is outstanding, C{_blockedQueue} is set to L{None}.\n        Otherwise, it contains a list of information about blocked commands.\n        Each list entry provides the following information about a blocked\n        command: the deferred that should be called when the response to the\n        command is received, the function that sends the command, and the\n        arguments to the function.\n\n    @type _waiting: L{Deferred <defer.Deferred>} or\n        L{None}\n    @ivar _waiting: A deferred which fires when the response to the\n        outstanding command is received from the server.\n\n    @type _timedOut: L{bool}\n    @ivar _timedOut: An indication of whether the connection was dropped\n        because of a timeout.\n\n    @type _greetingError: L{bytes} or L{None}\n    @ivar _greetingError: The server greeting minus the status indicator, when\n        the connection was dropped because of an error in the server greeting.\n        Otherwise, L{None}.\n\n    @type state: L{bytes}\n    @ivar state: The state which indicates what type of response is expected\n        from the server.  Valid states are: 'WELCOME', 'WAITING', 'SHORT',\n        'LONG_INITIAL', 'LONG'.\n\n    @type _xform: L{None} or callable that takes L{bytes}\n        and returns L{object}\n    @ivar _xform: The transform function which is used to convert each\n        line of a multi-line response into usable values for use by the\n        consumer function.  If L{None}, each line of the multi-line response\n        is sent directly to the consumer function.\n\n    @type _consumer: callable that takes L{object}\n    @ivar _consumer: The consumer function which is used to store the\n        values derived by the transform function from each line of a\n        multi-line response into a list.\n    \"\"\"\n    startedTLS = False\n    allowInsecureLogin = False\n    timeout = 0\n    serverChallenge = None\n\n    _capCache = None\n    _challengeMagicRe = re.compile(b'(<[^>]+>)')\n    _blockedQueue = None\n    _waiting = None\n    _timedOut = False\n    _greetingError = None\n\n    def _blocked(self, f, *a):\n        \"\"\"\n        Block a command, if necessary.\n\n        If commands are being blocked, append information about the function\n        which sends the command to a list and return a deferred that will be\n        chained with the return value of the function when it eventually runs.\n        Otherwise, set up for subsequent commands to be blocked and return\n        L{None}.\n\n        @type f: callable\n        @param f: A function which sends a command.\n\n        @type a: L{tuple}\n        @param a: Arguments to the function.\n\n        @rtype: L{None} or L{Deferred <defer.Deferred>}\n        @return: L{None} if the command can run immediately.  Otherwise,\n            a deferred that will eventually trigger with the return value of\n            the function.\n         \"\"\"\n        if self._blockedQueue is not None:\n            d = defer.Deferred()\n            self._blockedQueue.append((d, f, a))\n            return d\n        self._blockedQueue = []\n        return None\n\n\n    def _unblock(self):\n        \"\"\"\n        Send the next blocked command.\n\n        If there are no more commands in the blocked queue, set up for the next\n        command to be sent immediately.\n        \"\"\"\n        if self._blockedQueue == []:\n            self._blockedQueue = None\n        elif self._blockedQueue is not None:\n            _blockedQueue = self._blockedQueue\n            self._blockedQueue = None\n\n            d, f, a = _blockedQueue.pop(0)\n            d2 = f(*a)\n            d2.chainDeferred(d)\n            # f is a function which uses _blocked (otherwise it wouldn't\n            # have gotten into the blocked queue), which means it will have\n            # re-set _blockedQueue to an empty list, so we can put the rest\n            # of the blocked queue back into it now.\n            self._blockedQueue.extend(_blockedQueue)\n\n\n    def sendShort(self, cmd, args):\n        \"\"\"\n        Send a POP3 command to which a short response is expected.\n\n        Block all further commands from being sent until the response is\n        received.  Transition the state to SHORT.\n\n        @type cmd: L{bytes}\n        @param cmd: A POP3 command.\n\n        @type args: L{bytes}\n        @param args: The command arguments.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes} or fails with L{ServerErrorResponse}\n        @return: A deferred which fires when the entire response is received.\n            On an OK response, it returns the response from the server minus\n            the status indicator.  On an ERR response, it issues a server\n            error response failure with the response from the server minus the\n            status indicator.\n        \"\"\"\n        d = self._blocked(self.sendShort, cmd, args)\n        if d is not None:\n            return d\n\n        if args:\n            self.sendLine(cmd + b' ' + args)\n        else:\n            self.sendLine(cmd)\n        self.state = 'SHORT'\n        self._waiting = defer.Deferred()\n        return self._waiting\n\n\n    def sendLong(self, cmd, args, consumer, xform):\n        \"\"\"\n        Send a POP3 command to which a multi-line response is expected.\n\n        Block all further commands from being sent until the entire response is\n        received.  Transition the state to LONG_INITIAL.\n\n        @type cmd: L{bytes}\n        @param cmd: A POP3 command.\n\n        @type args: L{bytes}\n        @param args: The command arguments.\n\n        @type consumer: callable that takes L{object}\n        @param consumer: A consumer function which should be used to put\n            the values derived by a transform function from each line of the\n            multi-line response into a list.\n\n        @type xform: L{None} or callable that takes\n            L{bytes} and returns L{object}\n        @param xform: A transform function which should be used to transform\n            each line of the multi-line response into usable values for use by\n            a consumer function.  If L{None}, each line of the multi-line\n            response should be sent directly to the consumer function.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            callable that takes L{object} and fails with L{ServerErrorResponse}\n        @return: A deferred which fires when the entire response is received.\n            On an OK response, it returns the consumer function.  On an ERR\n            response, it issues a server error response failure with the\n            response from the server minus the status indicator and the\n            consumer function.\n        \"\"\"\n        d = self._blocked(self.sendLong, cmd, args, consumer, xform)\n        if d is not None:\n            return d\n\n        if args:\n            self.sendLine(cmd + b' ' + args)\n        else:\n            self.sendLine(cmd)\n        self.state = 'LONG_INITIAL'\n        self._xform = xform\n        self._consumer = consumer\n        self._waiting = defer.Deferred()\n        return self._waiting\n\n\n    # Twisted protocol callback\n    def connectionMade(self):\n        \"\"\"\n        Wait for a greeting from the server after the connection has been made.\n\n        Start the connection in the WELCOME state.\n        \"\"\"\n        if self.timeout > 0:\n            self.setTimeout(self.timeout)\n\n        self.state = 'WELCOME'\n        self._blockedQueue = []\n\n\n    def timeoutConnection(self):\n        \"\"\"\n        Drop the connection when the server does not respond in time.\n        \"\"\"\n        self._timedOut = True\n        self.transport.loseConnection()\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Clean up when the connection has been lost.\n\n        When the loss of connection was initiated by the client due to a\n        timeout, the L{_timedOut} flag will be set.  When it was initiated by\n        the client due to an error in the server greeting, L{_greetingError}\n        will be set to the server response minus the status indicator.\n\n        @type reason: L{Failure <twisted.python.failure.Failure>}\n        @param reason: The reason the connection was terminated.\n        \"\"\"\n        if self.timeout > 0:\n            self.setTimeout(None)\n\n        if self._timedOut:\n            reason = error.TimeoutError()\n        elif self._greetingError:\n            reason = ServerErrorResponse(self._greetingError)\n\n        d = []\n        if self._waiting is not None:\n            d.append(self._waiting)\n            self._waiting = None\n        if self._blockedQueue is not None:\n            d.extend([deferred for (deferred, f, a) in self._blockedQueue])\n            self._blockedQueue = None\n        for w in d:\n            w.errback(reason)\n\n\n    def lineReceived(self, line):\n        \"\"\"\n        Pass a received line to a state machine function and\n        transition to the next state.\n\n        @type line: L{bytes}\n        @param line: A received line.\n        \"\"\"\n        if self.timeout > 0:\n            self.resetTimeout()\n\n        state = self.state\n        self.state = None\n        state = getattr(self, 'state_' + state)(line) or state\n        if self.state is None:\n            self.state = state\n\n\n    def lineLengthExceeded(self, buffer):\n        \"\"\"\n        Drop the connection when a server response exceeds the maximum line\n        length (L{LineOnlyReceiver.MAX_LENGTH}).\n\n        @type buffer: L{bytes}\n        @param buffer: A received line which exceeds the maximum line length.\n        \"\"\"\n        # XXX - We need to be smarter about this\n        if self._waiting is not None:\n            waiting, self._waiting = self._waiting, None\n            waiting.errback(LineTooLong())\n        self.transport.loseConnection()\n\n\n    # POP3 Client state logic - don't touch this.\n    def state_WELCOME(self, line):\n        \"\"\"\n        Handle server responses for the WELCOME state in which the server\n        greeting is expected.\n\n        WELCOME is the first state.  The server should send one line of text\n        with a greeting and possibly an APOP challenge.  Transition the state\n        to WAITING.\n\n        @type line: L{bytes}\n        @param line: A line received from the server.\n\n        @rtype: L{bytes}\n        @return: The next state.\n        \"\"\"\n        code, status = _codeStatusSplit(line)\n        if code != OK:\n            self._greetingError = status\n            self.transport.loseConnection()\n        else:\n            m = self._challengeMagicRe.search(status)\n\n            if m is not None:\n                self.serverChallenge = m.group(1)\n\n            self.serverGreeting(status)\n\n        self._unblock()\n        return 'WAITING'\n\n\n    def state_WAITING(self, line):\n        \"\"\"\n        Log an error for server responses received in the WAITING state during\n        which the server is not expected to send anything.\n\n        @type line: L{bytes}\n        @param line: A line received from the server.\n        \"\"\"\n        log.msg(\"Illegal line from server: \" + repr(line))\n\n\n    def state_SHORT(self, line):\n        \"\"\"\n        Handle server responses for the SHORT state in which the server is\n        expected to send a single line response.\n\n        Parse the response and fire the deferred which is waiting on receipt of\n        a complete response.  Transition the state back to WAITING.\n\n        @type line: L{bytes}\n        @param line: A line received from the server.\n\n        @rtype: L{bytes}\n        @return: The next state.\n        \"\"\"\n        deferred, self._waiting = self._waiting, None\n        self._unblock()\n        code, status = _codeStatusSplit(line)\n        if code == OK:\n            deferred.callback(status)\n        else:\n            deferred.errback(ServerErrorResponse(status))\n        return 'WAITING'\n\n\n    def state_LONG_INITIAL(self, line):\n        \"\"\"\n        Handle server responses for the LONG_INITIAL state in which the server\n        is expected to send the first line of a multi-line response.\n\n        Parse the response.  On an OK response, transition the state to\n        LONG.  On an ERR response, cleanup and transition the state to\n        WAITING.\n\n        @type line: L{bytes}\n        @param line: A line received from the server.\n\n        @rtype: L{bytes}\n        @return: The next state.\n        \"\"\"\n        code, status = _codeStatusSplit(line)\n        if code == OK:\n            return 'LONG'\n        consumer = self._consumer\n        deferred = self._waiting\n        self._consumer = self._waiting = self._xform = None\n        self._unblock()\n        deferred.errback(ServerErrorResponse(status, consumer))\n        return 'WAITING'\n\n\n    def state_LONG(self, line):\n        \"\"\"\n        Handle server responses for the LONG state in which the server is\n        expected to send a non-initial line of a multi-line response.\n\n        On receipt of the last line of the response, clean up, fire the\n        deferred which is waiting on receipt of a complete response, and\n        transition the state to WAITING. Otherwise, pass the line to the\n        transform function, if provided, and then the consumer function.\n\n        @type line: L{bytes}\n        @param line: A line received from the server.\n\n        @rtype: L{bytes}\n        @return: The next state.\n        \"\"\"\n        # This is the state for each line of a long response.\n        if line == b'.':\n            consumer = self._consumer\n            deferred = self._waiting\n            self._consumer = self._waiting = self._xform = None\n            self._unblock()\n            deferred.callback(consumer)\n            return 'WAITING'\n        else:\n            if self._xform is not None:\n                self._consumer(self._xform(line))\n            else:\n                self._consumer(line)\n            return 'LONG'\n\n\n    # Callbacks - override these\n    def serverGreeting(self, greeting):\n        \"\"\"\n        Handle the server greeting.\n\n        @type greeting: L{bytes}\n        @param greeting: The server greeting minus the status indicator.\n            For servers implementing APOP authentication, this will contain a\n            challenge string.\n        \"\"\"\n\n\n    # External API - call these (most of 'em anyway)\n    def startTLS(self, contextFactory=None):\n        \"\"\"\n        Switch to encrypted communication using TLS.\n\n        The first step of switching to encrypted communication is obtaining\n        the server's capabilities.  When that is complete, the L{_startTLS}\n        callback function continues the switching process.\n\n        @type contextFactory: L{None} or\n            L{ClientContextFactory <twisted.internet.ssl.ClientContextFactory>}\n        @param contextFactory: The context factory with which to negotiate TLS.\n            If not provided, try to create a new one.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully results in\n            L{dict} mapping L{bytes} to L{list} of L{bytes} and/or L{bytes} to\n            L{None} or fails with L{TLSError}\n        @return: A deferred which fires when the transport has been\n            secured according to the given context factory with the server\n            capabilities, or which fails with a TLS error if the transport\n            cannot be secured.\n        \"\"\"\n        tls = interfaces.ITLSTransport(self.transport, None)\n        if tls is None:\n            return defer.fail(TLSError(\n                \"POP3Client transport does not implement \"\n                \"interfaces.ITLSTransport\"))\n\n        if contextFactory is None:\n            contextFactory = self._getContextFactory()\n\n        if contextFactory is None:\n            return defer.fail(TLSError(\n                \"POP3Client requires a TLS context to \"\n                \"initiate the STLS handshake\"))\n\n        d = self.capabilities()\n        d.addCallback(self._startTLS, contextFactory, tls)\n        return d\n\n\n    def _startTLS(self, caps, contextFactory, tls):\n        \"\"\"\n        Continue the process of switching to encrypted communication.\n\n        This callback function runs after the server capabilities are received.\n\n        The next step is sending the server an STLS command to request a\n        switch to encrypted communication.  When an OK response is received,\n        the L{_startedTLS} callback function completes the switch to encrypted\n        communication. Then, the new server capabilities are requested.\n\n        @type caps: L{dict} mapping L{bytes} to L{list} of L{bytes} and/or\n            L{bytes} to L{None}\n        @param caps: The server capabilities.\n\n        @type contextFactory: L{ClientContextFactory\n            <twisted.internet.ssl.ClientContextFactory>}\n        @param contextFactory: A context factory with which to negotiate TLS.\n\n        @type tls: L{ITLSTransport <interfaces.ITLSTransport>}\n        @param tls: A TCP transport that supports switching to TLS midstream.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully triggers with\n            L{dict} mapping L{bytes} to L{list} of L{bytes} and/or L{bytes} to\n            L{None} or fails with L{TLSNotSupportedError}\n        @return: A deferred which successfully fires when the response from\n            the server to the request to start TLS has been received and the\n            new server capabilities have been received or fails when the server\n            does not support TLS.\n        \"\"\"\n        assert not self.startedTLS, \"Client and Server are currently communicating via TLS\"\n\n        if b'STLS' not in caps:\n            return defer.fail(TLSNotSupportedError(\n                \"Server does not support secure communication \"\n                \"via TLS / SSL\"))\n\n        d = self.sendShort(b'STLS', None)\n        d.addCallback(self._startedTLS, contextFactory, tls)\n        d.addCallback(lambda _: self.capabilities())\n        return d\n\n\n    def _startedTLS(self, result, context, tls):\n        \"\"\"\n        Complete the process of switching to encrypted communication.\n\n        This callback function runs after the response to the STLS command has\n        been received.\n\n        The final steps are discarding the cached capabilities and initiating\n        TLS negotiation on the transport.\n\n        @type result: L{dict} mapping L{bytes} to L{list} of L{bytes} and/or\n            L{bytes} to L{None}\n        @param result: The server capabilities.\n\n        @type context: L{ClientContextFactory\n            <twisted.internet.ssl.ClientContextFactory>}\n        @param context: A context factory with which to negotiate TLS.\n\n        @type tls: L{ITLSTransport <interfaces.ITLSTransport>}\n        @param tls: A TCP transport that supports switching to TLS midstream.\n\n        @rtype: L{dict} mapping L{bytes} to L{list} of L{bytes} and/or L{bytes}\n            to L{None}\n        @return: The server capabilities.\n        \"\"\"\n        self.transport = tls\n        self.transport.startTLS(context)\n        self._capCache = None\n        self.startedTLS = True\n        return result\n\n\n    def _getContextFactory(self):\n        \"\"\"\n        Get a context factory with which to negotiate TLS.\n\n        @rtype: L{None} or\n            L{ClientContextFactory <twisted.internet.ssl.ClientContextFactory>}\n        @return: A context factory or L{None} if TLS is not supported on the\n            client.\n        \"\"\"\n        try:\n            from twisted.internet import ssl\n        except ImportError:\n            return None\n        else:\n            context = ssl.ClientContextFactory()\n            context.method = ssl.SSL.TLSv1_METHOD\n            return context\n\n\n    def login(self, username, password):\n        \"\"\"\n        Log in to the server.\n\n        If APOP is available it will be used.  Otherwise, if TLS is\n        available, an encrypted session will be started and plaintext\n        login will proceed.  Otherwise, if L{allowInsecureLogin} is set,\n        insecure plaintext login will proceed.  Otherwise,\n        L{InsecureAuthenticationDisallowed} will be raised.\n\n        The first step of logging into the server is obtaining the server's\n        capabilities.  When that is complete, the L{_login} callback function\n        continues the login process.\n\n        @type username: L{bytes}\n        @param username: The username with which to log in.\n\n        @type password: L{bytes}\n        @param password: The password with which to log in.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes}\n        @return: A deferred which fires when the login process is complete.\n            On a successful login, it returns the server's response minus the\n            status indicator.\n        \"\"\"\n        d = self.capabilities()\n        d.addCallback(self._login, username, password)\n        return d\n\n\n    def _login(self, caps, username, password):\n        \"\"\"\n        Continue the process of logging in to the server.\n\n        This callback function runs after the server capabilities are received.\n\n        If the server provided a challenge in the greeting, proceed with an\n        APOP login.  Otherwise, if the server and the transport support\n        encrypted communication, try to switch to TLS and then complete\n        the login process with the L{_loginTLS} callback function.  Otherwise,\n        if insecure authentication is allowed, do a plaintext login.\n        Otherwise, fail with an L{InsecureAuthenticationDisallowed} error.\n\n        @type caps: L{dict} mapping L{bytes} to L{list} of L{bytes} and/or\n            L{bytes} to L{None}\n        @param caps: The server capabilities.\n\n        @type username: L{bytes}\n        @param username: The username with which to log in.\n\n        @type password: L{bytes}\n        @param password: The password with which to log in.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes}\n        @return: A deferred which fires when the login process is complete.\n            On a successful login, it returns the server's response minus the\n            status indicator.\n        \"\"\"\n        if self.serverChallenge is not None:\n            return self._apop(username, password, self.serverChallenge)\n\n        tryTLS = b'STLS' in caps\n\n        # If our transport supports switching to TLS, we might want to\n        # try to switch to TLS.\n        tlsableTransport = interfaces.ITLSTransport(self.transport, None) is not None\n\n        # If our transport is not already using TLS, we might want to\n        # try to switch to TLS.\n        nontlsTransport = interfaces.ISSLTransport(self.transport, None) is None\n\n        if not self.startedTLS and tryTLS and tlsableTransport and nontlsTransport:\n            d = self.startTLS()\n\n            d.addCallback(self._loginTLS, username, password)\n            return d\n\n        elif self.startedTLS or not nontlsTransport or self.allowInsecureLogin:\n            return self._plaintext(username, password)\n        else:\n            return defer.fail(InsecureAuthenticationDisallowed())\n\n\n    def _loginTLS(self, res, username, password):\n        \"\"\"\n        Do a plaintext login over an encrypted transport.\n\n        This callback function runs after the transport switches to encrypted\n        communication.\n\n        @type res: L{dict} mapping L{bytes} to L{list} of L{bytes} and/or\n            L{bytes} to L{None}\n        @param res: The server capabilities.\n\n        @type username: L{bytes}\n        @param username: The username with which to log in.\n\n        @type password: L{bytes}\n        @param password: The password with which to log in.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes} or fails with L{ServerErrorResponse}\n        @return: A deferred which fires when the server accepts the username\n            and password or fails when the server rejects either.  On a\n            successful login, it returns the server's response minus the\n            status indicator.\n        \"\"\"\n        return self._plaintext(username, password)\n\n\n    def _plaintext(self, username, password):\n        \"\"\"\n        Perform a plaintext login.\n\n        @type username: L{bytes}\n        @param username: The username with which to log in.\n\n        @type password: L{bytes}\n        @param password: The password with which to log in.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes} or fails with L{ServerErrorResponse}\n        @return: A deferred which fires when the server accepts the username\n            and password or fails when the server rejects either.  On a\n            successful login, it returns the server's response minus the\n            status indicator.\n        \"\"\"\n        return self.user(username).addCallback(lambda r: self.password(password))\n\n\n    def _apop(self, username, password, challenge):\n        \"\"\"\n        Perform an APOP login.\n\n        @type username: L{bytes}\n        @param username: The username with which to log in.\n\n        @type password: L{bytes}\n        @param password: The password with which to log in.\n\n        @type challenge: L{bytes}\n        @param challenge: A challenge string.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes} or fails with L{ServerErrorResponse}\n        @return: A deferred which fires when the server response is received.\n            On a successful login, it returns the server response minus\n            the status indicator.\n        \"\"\"\n        digest = md5(challenge + password).hexdigest().encode(\"ascii\")\n        return self.apop(username, digest)\n\n\n    def apop(self, username, digest):\n        \"\"\"\n        Send an APOP command to perform authenticated login.\n\n        This should be used in special circumstances only, when it is\n        known that the server supports APOP authentication, and APOP\n        authentication is absolutely required.  For the common case,\n        use L{login} instead.\n\n        @type username: L{bytes}\n        @param username: The username with which to log in.\n\n        @type digest: L{bytes}\n        @param digest: The challenge response to authenticate with.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes} or fails with L{ServerErrorResponse}\n        @return: A deferred which fires when the server response is received.\n            On an OK response, the deferred succeeds with the server\n            response minus the status indicator.  On an ERR response, the\n            deferred fails with a server error response failure.\n        \"\"\"\n        return self.sendShort(b'APOP', username + b' ' + digest)\n\n\n    def user(self, username):\n        \"\"\"\n        Send a USER command to perform the first half of plaintext login.\n\n        Unless this is absolutely required, use the L{login} method instead.\n\n        @type username: L{bytes}\n        @param username: The username with which to log in.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes} or fails with L{ServerErrorResponse}\n        @return: A deferred which fires when the server response is received.\n            On an OK response, the deferred succeeds with the server\n            response minus the status indicator.  On an ERR response, the\n            deferred fails with a server error response failure.\n        \"\"\"\n        return self.sendShort(b'USER', username)\n\n\n    def password(self, password):\n        \"\"\"\n        Send a PASS command to perform the second half of plaintext login.\n\n        Unless this is absolutely required, use the L{login} method instead.\n\n        @type password: L{bytes}\n        @param password: The plaintext password with which to authenticate.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes} or fails with L{ServerErrorResponse}\n        @return: A deferred which fires when the server response is received.\n            On an OK response, the deferred succeeds with the server\n            response minus the status indicator.  On an ERR response, the\n            deferred fails with a server error response failure.\n        \"\"\"\n        return self.sendShort(b'PASS', password)\n\n\n    def delete(self, index):\n        \"\"\"\n        Send a DELE command to delete a message from the server.\n\n        @type index: L{int}\n        @param index: The 0-based index of the message to delete.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes} or fails with L{ServerErrorResponse}\n        @return: A deferred which fires when the server response is received.\n            On an OK response, the deferred succeeds with the server\n            response minus the status indicator.  On an ERR response, the\n            deferred fails with a server error response failure.\n        \"\"\"\n        return self.sendShort(b'DELE', intToBytes(index + 1))\n\n\n    def _consumeOrSetItem(self, cmd, args, consumer, xform):\n        \"\"\"\n        Send a command to which a long response is expected and process the\n        multi-line response into a list accounting for deleted messages.\n\n        @type cmd: L{bytes}\n        @param cmd: A POP3 command to which a long response is expected.\n\n        @type args: L{bytes}\n        @param args: The command arguments.\n\n        @type consumer: L{None} or callable that takes\n            L{object}\n        @param consumer: L{None} or a function that consumes the output from\n            the transform function.\n\n        @type xform: L{None}, callable that takes\n            L{bytes} and returns 2-L{tuple} of (0) L{int}, (1) L{object},\n            or callable that takes L{bytes} and returns L{object}\n        @param xform: A function that parses a line from a multi-line response\n            and transforms the values into usable form for input to the\n            consumer function.  If no consumer function is specified, the\n            output must be a message index and corresponding value.  If no\n            transform function is specified, the line is used as is.\n\n        @rtype: L{Deferred <defer.Deferred>} which fires with L{list} of\n            L{object} or callable that takes L{list} of L{object}\n        @return: A deferred which fires when the entire response has been\n            received.  When a consumer is not provided, the return value is a\n            list of the value for each message or L{None} for deleted messages.\n            Otherwise, it returns the consumer itself.\n        \"\"\"\n        if consumer is None:\n            L = []\n            consumer = _ListSetter(L).setitem\n            return self.sendLong(cmd, args, consumer, xform).addCallback(lambda r: L)\n        return self.sendLong(cmd, args, consumer, xform)\n\n\n    def _consumeOrAppend(self, cmd, args, consumer, xform):\n        \"\"\"\n        Send a command to which a long response is expected and process the\n        multi-line response into a list.\n\n        @type cmd: L{bytes}\n        @param cmd: A POP3 command which expects a long response.\n\n        @type args: L{bytes}\n        @param args: The command arguments.\n\n        @type consumer: L{None} or callable that takes\n            L{object}\n        @param consumer: L{None} or a function that consumes the output from the\n            transform function.\n\n        @type xform: L{None} or callable that takes\n            L{bytes} and returns L{object}\n        @param xform: A function that transforms a line from a multi-line\n            response into usable form for input to the consumer function.  If\n            no transform function is specified, the line is used as is.\n\n        @rtype: L{Deferred <defer.Deferred>} which fires with L{list} of\n            2-L{tuple} of (0) L{int}, (1) L{object} or callable that\n            takes 2-L{tuple} of (0) L{int}, (1) L{object}\n        @return: A deferred which fires when the entire response has been\n            received.  When a consumer is not provided, the return value is a\n            list of the transformed lines.  Otherwise, it returns the consumer\n            itself.\n        \"\"\"\n        if consumer is None:\n            L = []\n            consumer = L.append\n            return self.sendLong(cmd, args, consumer, xform).addCallback(lambda r: L)\n        return self.sendLong(cmd, args, consumer, xform)\n\n\n    def capabilities(self, useCache=True):\n        \"\"\"\n        Send a CAPA command to retrieve the capabilities supported by\n        the server.\n\n        Not all servers support this command.  If the server does not\n        support this, it is treated as though it returned a successful\n        response listing no capabilities.  At some future time, this may be\n        changed to instead seek out information about a server's\n        capabilities in some other fashion (only if it proves useful to do\n        so, and only if there are servers still in use which do not support\n        CAPA but which do support POP3 extensions that are useful).\n\n        @type useCache: L{bool}\n        @param useCache: A flag that determines whether previously retrieved\n            results should be used if available.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully results in\n            L{dict} mapping L{bytes} to L{list} of L{bytes} and/or L{bytes} to\n            L{None}\n        @return: A deferred which fires with a mapping of capability name to\n        parameters.  For example::\n\n            C: CAPA\n            S: +OK Capability list follows\n            S: TOP\n            S: USER\n            S: SASL CRAM-MD5 KERBEROS_V4\n            S: RESP-CODES\n            S: LOGIN-DELAY 900\n            S: PIPELINING\n            S: EXPIRE 60\n            S: UIDL\n            S: IMPLEMENTATION Shlemazle-Plotz-v302\n            S: .\n\n        will be lead to a result of::\n\n            | {'TOP': None,\n            |  'USER': None,\n            |  'SASL': ['CRAM-MD5', 'KERBEROS_V4'],\n            |  'RESP-CODES': None,\n            |  'LOGIN-DELAY': ['900'],\n            |  'PIPELINING': None,\n            |  'EXPIRE': ['60'],\n            |  'UIDL': None,\n            |  'IMPLEMENTATION': ['Shlemazle-Plotz-v302']}\n        \"\"\"\n        if useCache and self._capCache is not None:\n            return defer.succeed(self._capCache)\n\n        cache = {}\n        def consume(line):\n            tmp = line.split()\n            if len(tmp) == 1:\n                cache[tmp[0]] = None\n            elif len(tmp) > 1:\n                cache[tmp[0]] = tmp[1:]\n\n        def capaNotSupported(err):\n            err.trap(ServerErrorResponse)\n            return None\n\n        def gotCapabilities(result):\n            self._capCache = cache\n            return cache\n\n        d = self._consumeOrAppend(b'CAPA', None, consume, None)\n        d.addErrback(capaNotSupported).addCallback(gotCapabilities)\n        return d\n\n\n    def noop(self):\n        \"\"\"\n        Send a NOOP command asking the server to do nothing but respond.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes} or fails with L{ServerErrorResponse}\n        @return: A deferred which fires when the server response is received.\n            On an OK response, the deferred succeeds with the server\n            response minus the status indicator.  On an ERR response, the\n            deferred fails with a server error response failure.\n        \"\"\"\n        return self.sendShort(b\"NOOP\", None)\n\n\n    def reset(self):\n        \"\"\"\n        Send a RSET command to unmark any messages that have been flagged\n        for deletion on the server.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes} or fails with L{ServerErrorResponse}\n        @return: A deferred which fires when the server response is received.\n            On an OK response, the deferred succeeds with the server\n            response minus the status indicator.  On an ERR response, the\n            deferred fails with a server error response failure.\n        \"\"\"\n        return self.sendShort(b\"RSET\", None)\n\n\n    def retrieve(self, index, consumer=None, lines=None):\n        \"\"\"\n        Send a RETR or TOP command to retrieve all or part of a message from\n        the server.\n\n        @type index: L{int}\n        @param index: A 0-based message index.\n\n        @type consumer: L{None} or callable that takes\n            L{bytes}\n        @param consumer: A function which consumes each transformed line from a\n            multi-line response as it is received.\n\n        @type lines: L{None} or L{int}\n        @param lines: If specified, the number of lines of the message to be\n            retrieved.  Otherwise, the entire message is retrieved.\n\n        @rtype: L{Deferred <defer.Deferred>} which fires with L{list} of\n            L{bytes}, or callable that takes 2-L{tuple} of (0) L{int},\n            (1) L{object}\n        @return: A deferred which fires when the entire response has been\n            received.  When a consumer is not provided, the return value is a\n            list of the transformed lines.  Otherwise, it returns the consumer\n            itself.\n        \"\"\"\n        idx = intToBytes(index + 1)\n        if lines is None:\n            return self._consumeOrAppend(b'RETR', idx, consumer, _dotUnquoter)\n\n        return self._consumeOrAppend(b'TOP', idx + b' ' + intToBytes(lines),\n                                     consumer, _dotUnquoter)\n\n\n    def stat(self):\n        \"\"\"\n        Send a STAT command to get information about the size of the mailbox.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            a 2-tuple of (0) L{int}, (1) L{int} or fails with\n            L{ServerErrorResponse}\n        @return: A deferred which fires when the server response is received.\n            On an OK response, the deferred succeeds with the number of\n            messages in the mailbox and the size of the mailbox in octets.\n            On an ERR response, the deferred fails with a server error\n            response failure.\n        \"\"\"\n        return self.sendShort(b'STAT', None).addCallback(_statXform)\n\n\n    def listSize(self, consumer=None):\n        \"\"\"\n        Send a LIST command to retrieve the sizes of all messages on the\n        server.\n\n        @type consumer: L{None} or callable that takes\n            2-L{tuple} of (0) L{int}, (1) L{int}\n        @param consumer: A function which consumes the 0-based message index\n            and message size derived from the server response.\n\n        @rtype: L{Deferred <defer.Deferred>} which fires L{list} of L{int} or\n            callable that takes 2-L{tuple} of (0) L{int}, (1) L{int}\n        @return: A deferred which fires when the entire response has been\n            received.  When a consumer is not provided, the return value is a\n            list of message sizes.  Otherwise, it returns the consumer itself.\n        \"\"\"\n        return self._consumeOrSetItem(b'LIST', None, consumer, _listXform)\n\n\n    def listUID(self, consumer=None):\n        \"\"\"\n        Send a UIDL command to retrieve the UIDs of all messages on the server.\n\n        @type consumer: L{None} or callable that takes\n            2-L{tuple} of (0) L{int}, (1) L{bytes}\n        @param consumer: A function which consumes the 0-based message index\n            and UID derived from the server response.\n\n        @rtype: L{Deferred <defer.Deferred>} which fires with L{list} of\n            L{object} or callable that takes 2-L{tuple} of (0) L{int},\n            (1) L{bytes}\n        @return: A deferred which fires when the entire response has been\n            received.  When a consumer is not provided, the return value is a\n            list of message sizes.  Otherwise, it returns the consumer itself.\n        \"\"\"\n        return self._consumeOrSetItem(b'UIDL', None, consumer, _uidXform)\n\n\n    def quit(self):\n        \"\"\"\n        Send a QUIT command to disconnect from the server.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            L{bytes} or fails with L{ServerErrorResponse}\n        @return: A deferred which fires when the server response is received.\n            On an OK response, the deferred succeeds with the server\n            response minus the status indicator.  On an ERR response, the\n            deferred fails with a server error response failure.\n        \"\"\"\n        return self.sendShort(b'QUIT', None)\n\n__all__ = []\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/protocols.py",
    "content": "# -*- test-case-name: twisted.mail.test.test_mail -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nMail protocol support.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nfrom twisted.mail import pop3\nfrom twisted.mail import smtp\nfrom twisted.internet import protocol\nfrom twisted.internet import defer\nfrom twisted.copyright import longversion\nfrom twisted.python import log\n\nfrom twisted.cred.credentials import CramMD5Credentials, UsernamePassword\nfrom twisted.cred.error import UnauthorizedLogin\n\nfrom twisted.mail import relay\n\nfrom zope.interface import implementer\n\n\n\n@implementer(smtp.IMessageDelivery)\nclass DomainDeliveryBase:\n    \"\"\"\n    A base class for message delivery using the domains of a mail service.\n\n    @ivar service: See L{__init__}\n    @ivar user: See L{__init__}\n    @ivar host: See L{__init__}\n\n    @type protocolName: L{bytes}\n    @ivar protocolName: The protocol being used to deliver the mail.\n        Sub-classes should set this appropriately.\n    \"\"\"\n    service = None\n    protocolName = None\n\n    def __init__(self, service, user, host=smtp.DNSNAME):\n        \"\"\"\n        @type service: L{MailService}\n        @param service: A mail service.\n\n        @type user: L{bytes} or L{None}\n        @param user: The authenticated SMTP user.\n\n        @type host: L{bytes}\n        @param host: The hostname.\n        \"\"\"\n        self.service = service\n        self.user = user\n        self.host = host\n\n\n    def receivedHeader(self, helo, origin, recipients):\n        \"\"\"\n        Generate a received header string for a message.\n\n        @type helo: 2-L{tuple} of (L{bytes}, L{bytes})\n        @param helo: The client's identity as sent in the HELO command and its\n            IP address.\n\n        @type origin: L{Address}\n        @param origin: The origination address of the message.\n\n        @type recipients: L{list} of L{User}\n        @param recipients: The destination addresses for the message.\n\n        @rtype: L{bytes}\n        @return: A received header string.\n        \"\"\"\n        authStr = heloStr = b\"\"\n        if self.user:\n            authStr = b\" auth=\" + self.user.encode('xtext')\n        if helo[0]:\n            heloStr = b\" helo=\" + helo[0]\n        fromUser = (b\"from \" + helo[0] + b\" ([\" + helo[1] + b\"]\" +\n                 heloStr + authStr)\n        by = (b\"by \" + self.host + b\" with \" + self.protocolName +\n              b\" (\" + longversion.encode(\"ascii\") + b\")\")\n        forUser = (b\"for <\" + b' '.join(map(bytes, recipients)) + b\"> \" +\n                smtp.rfc822date())\n        return (b\"Received: \" + fromUser + b\"\\n\\t\" + by +\n                b\"\\n\\t\" + forUser)\n\n\n    def validateTo(self, user):\n        \"\"\"\n        Validate the address for which a message is destined.\n\n        @type user: L{User}\n        @param user: The destination address.\n\n        @rtype: L{Deferred <defer.Deferred>} which successfully fires with\n            no-argument callable which returns L{IMessage <smtp.IMessage>}\n            provider.\n        @return: A deferred which successfully fires with a no-argument\n            callable which returns a message receiver for the destination.\n\n        @raise SMTPBadRcpt: When messages cannot be accepted for the\n            destination address.\n        \"\"\"\n        # XXX - Yick.  This needs cleaning up.\n        if self.user and self.service.queue:\n            d = self.service.domains.get(user.dest.domain, None)\n            if d is None:\n                d = relay.DomainQueuer(self.service, True)\n        else:\n            d = self.service.domains[user.dest.domain]\n        return defer.maybeDeferred(d.exists, user)\n\n\n    def validateFrom(self, helo, origin):\n        \"\"\"\n        Validate the address from which a message originates.\n\n        @type helo: 2-L{tuple} of (L{bytes}, L{bytes})\n        @param helo: The client's identity as sent in the HELO command and its\n            IP address.\n\n        @type origin: L{Address}\n        @param origin: The origination address of the message.\n\n        @rtype: L{Address}\n        @return: The origination address.\n\n        @raise SMTPBadSender: When messages cannot be accepted from the\n            origination address.\n        \"\"\"\n        if not helo:\n            raise smtp.SMTPBadSender(origin, 503,\n                                     \"Who are you?  Say HELO first.\")\n        if origin.local != b'' and origin.domain == b'':\n            raise smtp.SMTPBadSender(origin, 501,\n                                     \"Sender address must contain domain.\")\n        return origin\n\n\n\nclass SMTPDomainDelivery(DomainDeliveryBase):\n    \"\"\"\n    A domain delivery base class for use in an SMTP server.\n    \"\"\"\n    protocolName = b'smtp'\n\n\n\nclass ESMTPDomainDelivery(DomainDeliveryBase):\n    \"\"\"\n    A domain delivery base class for use in an ESMTP server.\n    \"\"\"\n    protocolName = b'esmtp'\n\n\n\nclass SMTPFactory(smtp.SMTPFactory):\n    \"\"\"\n    An SMTP server protocol factory.\n\n    @ivar service: See L{__init__}\n    @ivar portal: See L{__init__}\n\n    @type protocol: no-argument callable which returns a L{Protocol\n        <protocol.Protocol>} subclass\n    @ivar protocol: A callable which creates a protocol.  The default value is\n        L{SMTP}.\n    \"\"\"\n    protocol = smtp.SMTP\n    portal = None\n\n    def __init__(self, service, portal = None):\n        \"\"\"\n        @type service: L{MailService}\n        @param service: An email service.\n\n        @type portal: L{Portal <twisted.cred.portal.Portal>} or\n            L{None}\n        @param portal: A portal to use for authentication.\n        \"\"\"\n        smtp.SMTPFactory.__init__(self)\n        self.service = service\n        self.portal = portal\n\n\n    def buildProtocol(self, addr):\n        \"\"\"\n        Create an instance of an SMTP server protocol.\n\n        @type addr: L{IAddress <twisted.internet.interfaces.IAddress>} provider\n        @param addr: The address of the SMTP client.\n\n        @rtype: L{SMTP}\n        @return: An SMTP protocol.\n        \"\"\"\n        log.msg('Connection from %s' % (addr,))\n        p = smtp.SMTPFactory.buildProtocol(self, addr)\n        p.service = self.service\n        p.portal = self.portal\n        return p\n\n\n\nclass ESMTPFactory(SMTPFactory):\n    \"\"\"\n    An ESMTP server protocol factory.\n\n    @type protocol: no-argument callable which returns a L{Protocol\n        <protocol.Protocol>} subclass\n    @ivar protocol: A callable which creates a protocol.  The default value is\n        L{ESMTP}.\n\n    @type context: L{IOpenSSLContextFactory\n        <twisted.internet.interfaces.IOpenSSLContextFactory>} or L{None}\n    @ivar context: A factory to generate contexts to be used in negotiating\n        encrypted communication.\n\n    @type challengers: L{dict} mapping L{bytes} to no-argument callable which\n        returns L{ICredentials <twisted.cred.credentials.ICredentials>}\n        subclass provider.\n    @ivar challengers: A mapping of acceptable authorization mechanism to\n        callable which creates credentials to use for authentication.\n    \"\"\"\n    protocol = smtp.ESMTP\n    context = None\n\n    def __init__(self, *args):\n        \"\"\"\n        @param args: Arguments for L{SMTPFactory.__init__}\n\n        @see: L{SMTPFactory.__init__}\n        \"\"\"\n        SMTPFactory.__init__(self, *args)\n        self.challengers = {\n            b'CRAM-MD5': CramMD5Credentials\n        }\n\n\n    def buildProtocol(self, addr):\n        \"\"\"\n        Create an instance of an ESMTP server protocol.\n\n        @type addr: L{IAddress <twisted.internet.interfaces.IAddress>} provider\n        @param addr: The address of the ESMTP client.\n\n        @rtype: L{ESMTP}\n        @return: An ESMTP protocol.\n        \"\"\"\n        p = SMTPFactory.buildProtocol(self, addr)\n        p.challengers = self.challengers\n        p.ctx = self.context\n        return p\n\n\n\nclass VirtualPOP3(pop3.POP3):\n    \"\"\"\n    A virtual hosting POP3 server.\n\n    @type service: L{MailService}\n    @ivar service: The email service that created this server.  This must be\n        set by the service.\n\n    @type domainSpecifier: L{bytes}\n    @ivar domainSpecifier: The character to use to split an email address into\n        local-part and domain. The default is '@'.\n    \"\"\"\n    service = None\n\n    domainSpecifier = b'@'  # Gaagh! I hate POP3. No standardized way\n                            # to indicate user@host. '@' doesn't work\n                            # with NS, e.g.\n\n    def authenticateUserAPOP(self, user, digest):\n        \"\"\"\n        Perform APOP authentication.\n\n        Override the default lookup scheme to allow virtual domains.\n\n        @type user: L{bytes}\n        @param user: The name of the user attempting to log in.\n\n        @type digest: L{bytes}\n        @param digest: The challenge response.\n\n        @rtype: L{Deferred} which successfully results in 3-L{tuple} of\n            (L{IMailbox <pop3.IMailbox>}, L{IMailbox <pop3.IMailbox>}\n            provider, no-argument callable)\n        @return: A deferred which fires when authentication is complete.\n            If successful, it returns an L{IMailbox <pop3.IMailbox>} interface,\n            a mailbox and a logout function. If authentication fails, the\n            deferred fails with an L{UnauthorizedLogin\n            <twisted.cred.error.UnauthorizedLogin>} error.\n        \"\"\"\n        user, domain = self.lookupDomain(user)\n        try:\n            portal = self.service.lookupPortal(domain)\n        except KeyError:\n            return defer.fail(UnauthorizedLogin())\n        else:\n            return portal.login(\n                pop3.APOPCredentials(self.magic, user, digest),\n                None,\n                pop3.IMailbox\n            )\n\n\n    def authenticateUserPASS(self, user, password):\n        \"\"\"\n        Perform authentication for a username/password login.\n\n        Override the default lookup scheme to allow virtual domains.\n\n        @type user: L{bytes}\n        @param user: The name of the user attempting to log in.\n\n        @type password: L{bytes}\n        @param password: The password to authenticate with.\n\n        @rtype: L{Deferred} which successfully results in 3-L{tuple} of\n            (L{IMailbox <pop3.IMailbox>}, L{IMailbox <pop3.IMailbox>}\n            provider, no-argument callable)\n        @return: A deferred which fires when authentication is complete.\n            If successful, it returns an L{IMailbox <pop3.IMailbox>} interface,\n            a mailbox and a logout function. If authentication fails, the\n            deferred fails with an L{UnauthorizedLogin\n            <twisted.cred.error.UnauthorizedLogin>} error.\n        \"\"\"\n        user, domain = self.lookupDomain(user)\n        try:\n            portal = self.service.lookupPortal(domain)\n        except KeyError:\n            return defer.fail(UnauthorizedLogin())\n        else:\n            return portal.login(\n                UsernamePassword(user, password),\n                None,\n                pop3.IMailbox\n            )\n\n\n    def lookupDomain(self, user):\n        \"\"\"\n        Check whether a domain is among the virtual domains supported by the\n        mail service.\n\n        @type user: L{bytes}\n        @param user: An email address.\n\n        @rtype: 2-L{tuple} of (L{bytes}, L{bytes})\n        @return: The local part and the domain part of the email address if the\n            domain is supported.\n\n        @raise POP3Error: When the domain is not supported by the mail service.\n        \"\"\"\n        try:\n            user, domain = user.split(self.domainSpecifier, 1)\n        except ValueError:\n            domain = b''\n        if domain not in self.service.domains:\n            raise pop3.POP3Error(\n                \"no such domain {}\".format(domain.decode(\"utf-8\")))\n        return user, domain\n\n\n\nclass POP3Factory(protocol.ServerFactory):\n    \"\"\"\n    A POP3 server protocol factory.\n\n    @ivar service: See L{__init__}\n\n    @type protocol: no-argument callable which returns a L{Protocol\n        <protocol.Protocol>} subclass\n    @ivar protocol: A callable which creates a protocol.  The default value is\n        L{VirtualPOP3}.\n    \"\"\"\n    protocol = VirtualPOP3\n    service = None\n\n    def __init__(self, service):\n        \"\"\"\n        @type service: L{MailService}\n        @param service: An email service.\n        \"\"\"\n        self.service = service\n\n\n    def buildProtocol(self, addr):\n        \"\"\"\n        Create an instance of a POP3 server protocol.\n\n        @type addr: L{IAddress <twisted.internet.interfaces.IAddress>} provider\n        @param addr: The address of the POP3 client.\n\n        @rtype: L{POP3}\n        @return: A POP3 protocol.\n        \"\"\"\n        p = protocol.ServerFactory.buildProtocol(self, addr)\n        p.service = self.service\n        return p\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/relay.py",
    "content": "# -*- test-case-name: twisted.mail.test.test_mail -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nSupport for relaying mail.\n\"\"\"\n\nfrom twisted.mail import smtp\nfrom twisted.python import log\nfrom twisted.internet.address import UNIXAddress\n\nimport os\n\ntry:\n    import cPickle as pickle\nexcept ImportError:\n    import pickle\n\n\n\nclass DomainQueuer:\n    \"\"\"\n    An SMTP domain which add messages to a queue intended for relaying.\n    \"\"\"\n\n    def __init__(self, service, authenticated=False):\n        self.service = service\n        self.authed = authenticated\n\n\n    def exists(self, user):\n        \"\"\"\n        Check whether mail can be relayed to a user.\n\n        @type user: L{User}\n        @param user: A user.\n\n        @rtype: no-argument callable which returns L{IMessage <smtp.IMessage>}\n            provider\n        @return: A function which takes no arguments and returns a message\n            receiver for the user.\n\n        @raise SMTPBadRcpt: When mail cannot be relayed to the user.\n        \"\"\"\n        if self.willRelay(user.dest, user.protocol):\n            # The most cursor form of verification of the addresses\n            orig = filter(None, str(user.orig).split('@', 1))\n            dest = filter(None, str(user.dest).split('@', 1))\n            if len(orig) == 2 and len(dest) == 2:\n                return lambda: self.startMessage(user)\n        raise smtp.SMTPBadRcpt(user)\n\n\n    def willRelay(self, address, protocol):\n        \"\"\"\n        Check whether we agree to relay.\n\n        The default is to relay for all connections over UNIX\n        sockets and all connections from localhost.\n        \"\"\"\n        peer = protocol.transport.getPeer()\n        return (self.authed or isinstance(peer, UNIXAddress) or\n            peer.host == '127.0.0.1')\n\n\n    def startMessage(self, user):\n        \"\"\"\n        Create an envelope and a message receiver for the relay queue.\n\n        @type user: L{User}\n        @param user: A user.\n\n        @rtype: L{IMessage <smtp.IMessage>}\n        @return: A message receiver.\n        \"\"\"\n        queue = self.service.queue\n        envelopeFile, smtpMessage = queue.createNewMessage()\n        with envelopeFile:\n            log.msg('Queueing mail %r -> %r' % (str(user.orig),\n                str(user.dest)))\n            pickle.dump([str(user.orig), str(user.dest)], envelopeFile)\n        return smtpMessage\n\n\n\nclass RelayerMixin:\n\n    # XXX - This is -totally- bogus\n    # It opens about a -hundred- -billion- files\n    # and -leaves- them open!\n\n    def loadMessages(self, messagePaths):\n        self.messages = []\n        self.names = []\n        for message in messagePaths:\n            with open(message + '-H') as fp:\n                messageContents = pickle.load(fp)\n            fp = open(message + '-D')\n            messageContents.append(fp)\n            self.messages.append(messageContents)\n            self.names.append(message)\n\n\n    def getMailFrom(self):\n        if not self.messages:\n            return None\n        return self.messages[0][0]\n\n\n    def getMailTo(self):\n        if not self.messages:\n            return None\n        return [self.messages[0][1]]\n\n\n    def getMailData(self):\n        if not self.messages:\n            return None\n        return self.messages[0][2]\n\n\n    def sentMail(self, code, resp, numOk, addresses, log):\n        \"\"\"Since we only use one recipient per envelope, this\n        will be called with 0 or 1 addresses. We probably want\n        to do something with the error message if we failed.\n        \"\"\"\n        if code in smtp.SUCCESS:\n            # At least one, i.e. all, recipients successfully delivered\n            os.remove(self.names[0] + '-D')\n            os.remove(self.names[0] + '-H')\n        del self.messages[0]\n        del self.names[0]\n\n\n\nclass SMTPRelayer(RelayerMixin, smtp.SMTPClient):\n    \"\"\"\n    A base class for SMTP relayers.\n    \"\"\"\n    def __init__(self, messagePaths, *args, **kw):\n        \"\"\"\n        @type messagePaths: L{list} of L{bytes}\n        @param messagePaths: The base filename for each message to be relayed.\n\n        @type args: 1-L{tuple} of (0) L{bytes} or 2-L{tuple} of\n            (0) L{bytes}, (1) L{int}\n        @param args: Positional arguments for L{SMTPClient.__init__}\n\n        @type kw: L{dict}\n        @param kw: Keyword arguments for L{SMTPClient.__init__}\n        \"\"\"\n        smtp.SMTPClient.__init__(self, *args, **kw)\n        self.loadMessages(messagePaths)\n\n\n\nclass ESMTPRelayer(RelayerMixin, smtp.ESMTPClient):\n    \"\"\"\n    A base class for ESMTP relayers.\n    \"\"\"\n    def __init__(self, messagePaths, *args, **kw):\n        \"\"\"\n        @type messagePaths: L{list} of L{bytes}\n        @param messagePaths: The base filename for each message to be relayed.\n\n        @type args: 3-L{tuple} of (0) L{bytes}, (1) L{None} or\n            L{ClientContextFactory\n            <twisted.internet.ssl.ClientContextFactory>},\n            (2) L{bytes} or 4-L{tuple} of (0) L{bytes}, (1) L{None}\n            or L{ClientContextFactory\n            <twisted.internet.ssl.ClientContextFactory>}, (2) L{bytes},\n            (3) L{int}\n        @param args: Positional arguments for L{ESMTPClient.__init__}\n\n        @type kw: L{dict}\n        @param kw: Keyword arguments for L{ESMTPClient.__init__}\n        \"\"\"\n        smtp.ESMTPClient.__init__(self, *args, **kw)\n        self.loadMessages(messagePaths)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/scripts/mailmail.py",
    "content": "# -*- test-case-name: twisted.mail.test.test_mailmail -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nImplementation module for the I{mailmail} command.\n\"\"\"\n\nfrom __future__ import print_function\n\nimport email.utils\nimport os\nimport sys\nimport getpass\ntry:\n    # Python 3\n    from configparser import ConfigParser\nexcept ImportError:\n    # Python 2\n    from ConfigParser import ConfigParser\n\nfrom twisted.copyright import version\nfrom twisted.internet import reactor\nfrom twisted.logger import Logger, textFileLogObserver\nfrom twisted.mail import smtp\nfrom twisted.python.compat import NativeStringIO\n\nGLOBAL_CFG = \"/etc/mailmail\"\nLOCAL_CFG = os.path.expanduser(\"~/.twisted/mailmail\")\nSMARTHOST = '127.0.0.1'\n\nERROR_FMT = \"\"\"\\\nSubject: Failed Message Delivery\n\n  Message delivery failed.  The following occurred:\n\n  %s\n--\nThe Twisted sendmail application.\n\"\"\"\n\n_logObserver = textFileLogObserver(sys.stderr)\n_log = Logger(observer=_logObserver)\n\n\n\nclass Options:\n    \"\"\"\n    Store the values of the parsed command-line options to the I{mailmail}\n    script.\n\n    @type to: L{list} of L{str}\n    @ivar to: The addresses to which to deliver this message.\n\n    @type sender: L{str}\n    @ivar sender: The address from which this message is being sent.\n\n    @type body: C{file}\n    @ivar body: The object from which the message is to be read.\n    \"\"\"\n\n\n\ndef getlogin():\n    try:\n        return os.getlogin()\n    except:\n        return getpass.getuser()\n\n\n_unsupportedOption = SystemExit(\"Unsupported option.\")\n\n\n\ndef parseOptions(argv):\n    o = Options()\n    o.to = [e for e in argv if not e.startswith('-')]\n    o.sender = getlogin()\n\n    # Just be very stupid\n\n    # Skip -bm -- it is the default\n\n    # Add a non-standard option for querying the version of this tool.\n    if '--version' in argv:\n        print('mailmail version:', version)\n        raise SystemExit()\n\n    # -bp lists queue information.  Screw that.\n    if '-bp' in argv:\n        raise _unsupportedOption\n\n    # -bs makes sendmail use stdin/stdout as its transport.  Screw that.\n    if '-bs' in argv:\n        raise _unsupportedOption\n\n    # -F sets who the mail is from, but is overridable by the From header\n    if '-F' in argv:\n        o.sender = argv[argv.index('-F') + 1]\n        o.to.remove(o.sender)\n\n    # -i and -oi makes us ignore lone \".\"\n    if ('-i' in argv) or ('-oi' in argv):\n        raise _unsupportedOption\n\n    # -odb is background delivery\n    if '-odb' in argv:\n        o.background = True\n    else:\n        o.background = False\n\n    # -odf is foreground delivery\n    if '-odf' in argv:\n        o.background = False\n    else:\n        o.background = True\n\n    # -oem and -em cause errors to be mailed back to the sender.\n    # It is also the default.\n\n    # -oep and -ep cause errors to be printed to stderr\n    if ('-oep' in argv) or ('-ep' in argv):\n        o.printErrors = True\n    else:\n        o.printErrors = False\n\n    # -om causes a copy of the message to be sent to the sender if the sender\n    # appears in an alias expansion.  We do not support aliases.\n    if '-om' in argv:\n        raise _unsupportedOption\n\n    # -t causes us to pick the recipients of the message from\n    # the To, Cc, and Bcc headers, and to remove the Bcc header\n    # if present.\n    if '-t' in argv:\n        o.recipientsFromHeaders = True\n        o.excludeAddresses = o.to\n        o.to = []\n    else:\n        o.recipientsFromHeaders = False\n        o.exludeAddresses = []\n\n    requiredHeaders = {\n        'from': [],\n        'to': [],\n        'cc': [],\n        'bcc': [],\n        'date': [],\n    }\n\n    buffer = NativeStringIO()\n    while 1:\n        write = 1\n        line = sys.stdin.readline()\n        if not line.strip():\n            break\n\n        hdrs = line.split(': ', 1)\n\n        hdr = hdrs[0].lower()\n        if o.recipientsFromHeaders and hdr in ('to', 'cc', 'bcc'):\n            o.to.extend([\n                email.utils.parseaddr(hdrs[1])[1]\n            ])\n            if hdr == 'bcc':\n                write = 0\n        elif hdr == 'from':\n            o.sender = email.utils.parseaddr(hdrs[1])[1]\n\n        if hdr in requiredHeaders:\n            requiredHeaders[hdr].append(hdrs[1])\n\n        if write:\n            buffer.write(line)\n\n    if not requiredHeaders['from']:\n        buffer.write('From: {}\\r\\n'.format(o.sender))\n    if not requiredHeaders['to']:\n        if not o.to:\n            raise SystemExit(\"No recipients specified.\")\n        buffer.write('To: {}\\r\\n'.format(', '.join(o.to)))\n    if not requiredHeaders['date']:\n        buffer.write('Date: {}\\r\\n'.format(smtp.rfc822date()))\n\n    buffer.write(line)\n\n    if o.recipientsFromHeaders:\n        for a in o.excludeAddresses:\n            try:\n                o.to.remove(a)\n            except:\n                pass\n\n    buffer.seek(0, 0)\n    o.body = NativeStringIO(buffer.getvalue() + sys.stdin.read())\n    return o\n\n\n\nclass Configuration:\n    \"\"\"\n\n    @ivar allowUIDs: A list of UIDs which are allowed to send mail.\n    @ivar allowGIDs: A list of GIDs which are allowed to send mail.\n    @ivar denyUIDs: A list of UIDs which are not allowed to send mail.\n    @ivar denyGIDs: A list of GIDs which are not allowed to send mail.\n\n    @type defaultAccess: L{bool}\n    @ivar defaultAccess: L{True} if access will be allowed when no other access\n    control rule matches or L{False} if it will be denied in that case.\n\n    @ivar useraccess: Either C{'allow'} to check C{allowUID} first\n    or C{'deny'} to check C{denyUID} first.\n\n    @ivar groupaccess: Either C{'allow'} to check C{allowGID} first or\n    C{'deny'} to check C{denyGID} first.\n\n    @ivar identities: A L{dict} mapping hostnames to credentials to use when\n    sending mail to that host.\n\n    @ivar smarthost: L{None} or a hostname through which all outgoing mail will\n    be sent.\n\n    @ivar domain: L{None} or the hostname with which to identify ourselves when\n    connecting to an MTA.\n    \"\"\"\n    def __init__(self):\n        self.allowUIDs = []\n        self.denyUIDs = []\n        self.allowGIDs = []\n        self.denyGIDs = []\n        self.useraccess = 'deny'\n        self.groupaccess = 'deny'\n\n        self.identities = {}\n        self.smarthost = None\n        self.domain = None\n\n        self.defaultAccess = True\n\n\n\ndef loadConfig(path):\n    # [useraccess]\n    # allow=uid1,uid2,...\n    # deny=uid1,uid2,...\n    # order=allow,deny\n    # [groupaccess]\n    # allow=gid1,gid2,...\n    # deny=gid1,gid2,...\n    # order=deny,allow\n    # [identity]\n    # host1=username:password\n    # host2=username:password\n    # [addresses]\n    # smarthost=a.b.c.d\n    # default_domain=x.y.z\n\n    c = Configuration()\n\n    if not os.access(path, os.R_OK):\n        return c\n\n    p = ConfigParser()\n    p.read(path)\n\n    au = c.allowUIDs\n    du = c.denyUIDs\n    ag = c.allowGIDs\n    dg = c.denyGIDs\n    for (section, a, d) in (('useraccess', au, du), ('groupaccess', ag, dg)):\n        if p.has_section(section):\n            for (mode, L) in (('allow', a), ('deny', d)):\n                if p.has_option(section, mode) and p.get(section, mode):\n                    for sectionID in p.get(section, mode).split(','):\n                        try:\n                            sectionID = int(sectionID)\n                        except ValueError:\n                            _log.error(\n                                \"Illegal {prefix}ID in \"\n                                \"[{section}] section: {sectionID}\",\n                                prefix=section[0].upper(),\n                                section=section, sectionID=sectionID)\n                        else:\n                            L.append(sectionID)\n            order = p.get(section, 'order')\n            order = [s.split()\n                     for s in [s.lower()\n                               for s in order.split(',')]]\n            if order[0] == 'allow':\n                setattr(c, section, 'allow')\n            else:\n                setattr(c, section, 'deny')\n\n    if p.has_section('identity'):\n        for (host, up) in p.items('identity'):\n            parts = up.split(':', 1)\n            if len(parts) != 2:\n                _log.error(\"Illegal entry in [identity] section: {section}\",\n                           section=up)\n                continue\n            c.identities[host] = parts\n\n    if p.has_section('addresses'):\n        if p.has_option('addresses', 'smarthost'):\n            c.smarthost = p.get('addresses', 'smarthost')\n        if p.has_option('addresses', 'default_domain'):\n            c.domain = p.get('addresses', 'default_domain')\n\n    return c\n\n\n\ndef success(result):\n    reactor.stop()\n\n\n\nfailed = None\ndef failure(f):\n    global failed\n    reactor.stop()\n    failed = f\n\n\n\ndef sendmail(host, options, ident):\n    d = smtp.sendmail(host, options.sender, options.to, options.body)\n    d.addCallbacks(success, failure)\n    reactor.run()\n\n\n\ndef senderror(failure, options):\n    recipient = [options.sender]\n    sender = '\"Internally Generated Message ({})\"<postmaster@{}>'.format(\n             sys.argv[0], smtp.DNSNAME.decode(\"ascii\"))\n    error = NativeStringIO()\n    failure.printTraceback(file=error)\n    body = NativeStringIO(ERROR_FMT % error.getvalue())\n    d = smtp.sendmail('localhost', sender, recipient, body)\n    d.addBoth(lambda _: reactor.stop())\n\n\n\ndef deny(conf):\n    uid = os.getuid()\n    gid = os.getgid()\n\n    if conf.useraccess == 'deny':\n        if uid in conf.denyUIDs:\n            return True\n        if uid in conf.allowUIDs:\n            return False\n    else:\n        if uid in conf.allowUIDs:\n            return False\n        if uid in conf.denyUIDs:\n            return True\n\n    if conf.groupaccess == 'deny':\n        if gid in conf.denyGIDs:\n            return True\n        if gid in conf.allowGIDs:\n            return False\n    else:\n        if gid in conf.allowGIDs:\n            return False\n        if gid in conf.denyGIDs:\n            return True\n\n    return not conf.defaultAccess\n\n\n\ndef run():\n    o = parseOptions(sys.argv[1:])\n    gConf = loadConfig(GLOBAL_CFG)\n    lConf = loadConfig(LOCAL_CFG)\n\n    if deny(gConf) or deny(lConf):\n        _log.error(\"Permission denied\")\n        return\n\n    host = lConf.smarthost or gConf.smarthost or SMARTHOST\n\n    ident = gConf.identities.copy()\n    ident.update(lConf.identities)\n\n    if lConf.domain:\n        smtp.DNSNAME = lConf.domain\n    elif gConf.domain:\n        smtp.DNSNAME = gConf.domain\n\n    sendmail(host, o, ident)\n\n    if failed:\n        if o.printErrors:\n            failed.printTraceback(file=sys.stderr)\n            raise SystemExit(1)\n        else:\n            senderror(failed, o)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/smtp.py",
    "content": "# -*- test-case-name: twisted.mail.test.test_smtp -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n#\n# pylint: disable=I0011,C0103,C9302\n\n\"\"\"\nSimple Mail Transfer Protocol implementation.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport time\nimport re\nimport base64\nimport socket\nimport os\nimport random\nimport binascii\nimport warnings\n\nfrom email.utils import parseaddr\n\nfrom zope.interface import implementer\n\nfrom twisted import cred\nfrom twisted.copyright import longversion\nfrom twisted.protocols import basic\nfrom twisted.protocols import policies\nfrom twisted.internet import protocol\nfrom twisted.internet import defer\nfrom twisted.internet import error\nfrom twisted.internet import reactor\nfrom twisted.internet.interfaces import ITLSTransport, ISSLTransport\nfrom twisted.python import log\nfrom twisted.python import util\nfrom twisted.python.compat import (_PY3, range, long, unicode, networkString,\n                                   nativeString, iteritems, _keys, _bytesChr,\n                                   iterbytes)\nfrom twisted.python.runtime import platform\n\nfrom twisted.mail.interfaces import (IClientAuthentication,\n                                     IMessageSMTP as IMessage,\n                                     IMessageDeliveryFactory, IMessageDelivery)\nfrom twisted.mail._cred import (CramMD5ClientAuthenticator, LOGINAuthenticator,\n                                LOGINCredentials as _lcredentials)\nfrom twisted.mail._except import (\n    AUTHDeclinedError, AUTHRequiredError, AddressError,\n    AuthenticationError, EHLORequiredError, ESMTPClientError,\n    SMTPAddressError, SMTPBadRcpt, SMTPBadSender, SMTPClientError,\n    SMTPConnectError, SMTPDeliveryError, SMTPError, SMTPServerError,\n    SMTPTimeoutError, SMTPTLSError as TLSError, TLSRequiredError,\n    SMTPProtocolError)\n\n\nfrom io import BytesIO\n\n\n__all__ = [\n    'AUTHDeclinedError', 'AUTHRequiredError', 'AddressError',\n    'AuthenticationError',  'EHLORequiredError', 'ESMTPClientError',\n    'SMTPAddressError', 'SMTPBadRcpt', 'SMTPBadSender', 'SMTPClientError',\n    'SMTPConnectError', 'SMTPDeliveryError', 'SMTPError', 'SMTPServerError',\n    'SMTPTimeoutError', 'TLSError', 'TLSRequiredError', 'SMTPProtocolError',\n\n    'IClientAuthentication', 'IMessage', 'IMessageDelivery',\n    'IMessageDeliveryFactory',\n\n    'CramMD5ClientAuthenticator', 'LOGINAuthenticator', 'LOGINCredentials',\n    'PLAINAuthenticator',\n\n    'Address', 'User', 'sendmail', 'SenderMixin',\n    'ESMTP', 'ESMTPClient', 'ESMTPSender', 'ESMTPSenderFactory',\n    'SMTP', 'SMTPClient', 'SMTPFactory',  'SMTPSender', 'SMTPSenderFactory',\n\n    'idGenerator', 'messageid', 'quoteaddr', 'rfc822date', 'xtextStreamReader',\n    'xtextStreamWriter', 'xtext_codec', 'xtext_decode', 'xtext_encode'\n]\n\n\n# Cache the hostname (XXX Yes - this is broken)\nif platform.isMacOSX():\n    # On macOS, getfqdn() is ridiculously slow - use the\n    # probably-identical-but-sometimes-not gethostname() there.\n    DNSNAME = socket.gethostname()\nelse:\n    DNSNAME = socket.getfqdn()\n\n# Encode the DNS name into something we can send over the wire\nDNSNAME = DNSNAME.encode('ascii')\n\n# Used for fast success code lookup\nSUCCESS = dict.fromkeys(range(200, 300))\n\n\n\ndef rfc822date(timeinfo=None, local=1):\n    \"\"\"\n    Format an RFC-2822 compliant date string.\n\n    @param timeinfo: (optional) A sequence as returned by C{time.localtime()}\n        or C{time.gmtime()}. Default is now.\n    @param local: (optional) Indicates if the supplied time is local or\n        universal time, or if no time is given, whether now should be local or\n        universal time. Default is local, as suggested (SHOULD) by rfc-2822.\n\n    @returns: A L{bytes} representing the time and date in RFC-2822 format.\n    \"\"\"\n    if not timeinfo:\n        if local:\n            timeinfo = time.localtime()\n        else:\n            timeinfo = time.gmtime()\n    if local:\n        if timeinfo[8]:\n            # DST\n            tz = -time.altzone\n        else:\n            tz = -time.timezone\n\n        (tzhr, tzmin) = divmod(abs(tz), 3600)\n        if tz:\n            tzhr *= int(abs(tz)//tz)\n        (tzmin, tzsec) = divmod(tzmin, 60)\n    else:\n        (tzhr, tzmin) = (0, 0)\n\n    return networkString(\"%s, %02d %s %04d %02d:%02d:%02d %+03d%02d\" % (\n        ['Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun'][timeinfo[6]],\n        timeinfo[2],\n        ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun',\n         'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'][timeinfo[1] - 1],\n        timeinfo[0], timeinfo[3], timeinfo[4], timeinfo[5],\n        tzhr, tzmin))\n\n\n\ndef idGenerator():\n    i = 0\n    while True:\n        yield i\n        i += 1\n\n_gen = idGenerator()\n\n\n\ndef messageid(uniq=None, N=lambda: next(_gen)):\n    \"\"\"\n    Return a globally unique random string in RFC 2822 Message-ID format\n\n    <datetime.pid.random@host.dom.ain>\n\n    Optional uniq string will be added to strengthen uniqueness if given.\n    \"\"\"\n    datetime = time.strftime('%Y%m%d%H%M%S', time.gmtime())\n    pid = os.getpid()\n    rand = random.randrange(2**31-1)\n    if uniq is None:\n        uniq = ''\n    else:\n        uniq = '.' + uniq\n\n    return '<%s.%s.%s%s.%s@%s>' % (datetime, pid, rand, uniq, N(), DNSNAME)\n\n\n\ndef quoteaddr(addr):\n    \"\"\"\n    Turn an email address, possibly with realname part etc, into\n    a form suitable for and SMTP envelope.\n    \"\"\"\n\n    if isinstance(addr, Address):\n        return b'<' + bytes(addr) + b'>'\n\n    if isinstance(addr, bytes):\n        addr = addr.decode('ascii')\n\n    res = parseaddr(addr)\n\n    if res == (None, None):\n        # It didn't parse, use it as-is\n        return  b'<' + bytes(addr) + b'>'\n    else:\n        return  b'<' + res[1].encode('ascii') + b'>'\n\nCOMMAND, DATA, AUTH = 'COMMAND', 'DATA', 'AUTH'\n\n\n# Character classes for parsing addresses\natom = br\"[-A-Za-z0-9!\\#$%&'*+/=?^_`{|}~]\"\n\nclass Address:\n    \"\"\"Parse and hold an RFC 2821 address.\n\n    Source routes are stipped and ignored, UUCP-style bang-paths\n    and %-style routing are not parsed.\n\n    @type domain: C{bytes}\n    @ivar domain: The domain within which this address resides.\n\n    @type local: C{bytes}\n    @ivar local: The local (\\\"user\\\") portion of this address.\n    \"\"\"\n\n    tstring = re.compile(br'''( # A string of\n                           (?:\"[^\"]*\" # quoted string\n                           |\\\\. # backslash-escaped characted\n                           |''' + atom + br''' # atom character\n                           )+|.) # or any single character''', re.X)\n    atomre = re.compile(atom) # match any one atom character\n\n\n    def __init__(self, addr, defaultDomain=None):\n        if isinstance(addr, User):\n            addr = addr.dest\n        if isinstance(addr, Address):\n            self.__dict__ = addr.__dict__.copy()\n            return\n        elif not isinstance(addr, bytes):\n            addr = str(addr).encode('ascii')\n\n        self.addrstr = addr\n\n        # Tokenize\n        atl = list(filter(None, self.tstring.split(addr)))\n        local = []\n        domain = []\n\n        while atl:\n            if atl[0] == b'<':\n                if atl[-1] != b'>':\n                    raise AddressError(\"Unbalanced <>\")\n                atl = atl[1:-1]\n            elif atl[0] == b'@':\n                atl = atl[1:]\n                if not local:\n                    # Source route\n                    while atl and atl[0] != b':':\n                        # remove it\n                        atl = atl[1:]\n                    if not atl:\n                        raise AddressError(\"Malformed source route\")\n                    atl = atl[1:] # remove :\n                elif domain:\n                    raise AddressError(\"Too many @\")\n                else:\n                    # Now in domain\n                    domain = [b'']\n            elif (len(atl[0]) == 1 and\n                  not self.atomre.match(atl[0]) and\n                  atl[0] != b'.'):\n                raise AddressError(\"Parse error at %r of %r\" % (atl[0], (addr, atl)))\n            else:\n                if not domain:\n                    local.append(atl[0])\n                else:\n                    domain.append(atl[0])\n                atl = atl[1:]\n\n        self.local = b''.join(local)\n        self.domain = b''.join(domain)\n        if self.local != b'' and self.domain == b'':\n            if defaultDomain is None:\n                defaultDomain = DNSNAME\n            self.domain = defaultDomain\n\n    dequotebs = re.compile(br'\\\\(.)')\n\n\n    def dequote(self, addr):\n        \"\"\"\n        Remove RFC-2821 quotes from address.\n        \"\"\"\n        res = []\n\n        if not isinstance(addr, bytes):\n            addr = str(addr).encode('ascii')\n\n        atl = filter(None, self.tstring.split(addr))\n\n        for t in atl:\n            if t[0] == b'\"' and t[-1] == b'\"':\n                res.append(t[1:-1])\n            elif '\\\\' in t:\n                res.append(self.dequotebs.sub(br'\\1', t))\n            else:\n                res.append(t)\n\n        return b''.join(res)\n\n    if _PY3:\n        def __str__(self):\n            return nativeString(bytes(self))\n    else:\n        def __str__(self):\n            return self.__bytes__()\n\n\n    def __bytes__(self):\n        if self.local or self.domain:\n            return b'@'.join((self.local, self.domain))\n        else:\n            return b''\n\n\n    def __repr__(self):\n        return \"%s.%s(%s)\" % (self.__module__, self.__class__.__name__,\n                              repr(str(self)))\n\n\n\nclass User:\n    \"\"\"\n    Hold information about and SMTP message recipient,\n    including information on where the message came from\n    \"\"\"\n    def __init__(self, destination, helo, protocol, orig):\n        try:\n            host = protocol.host\n        except AttributeError:\n            host = None\n        self.dest = Address(destination, host)\n        self.helo = helo\n        self.protocol = protocol\n        if isinstance(orig, Address):\n            self.orig = orig\n        else:\n            self.orig = Address(orig, host)\n\n\n    def __getstate__(self):\n        \"\"\"\n        Helper for pickle.\n\n        protocol isn't picklabe, but we want User to be, so skip it in\n        the pickle.\n        \"\"\"\n        return { 'dest' : self.dest,\n                 'helo' : self.helo,\n                 'protocol' : None,\n                 'orig' : self.orig }\n\n\n    def __str__(self):\n        return nativeString(bytes(self.dest))\n\n\n    def __bytes__(self):\n        return bytes(self.dest)\n\n\n\nclass SMTP(basic.LineOnlyReceiver, policies.TimeoutMixin):\n    \"\"\"\n    SMTP server-side protocol.\n\n    @ivar host: The hostname of this mail server.\n    @type host: L{bytes}\n    \"\"\"\n\n    timeout = 600\n    portal = None\n\n    # Control whether we log SMTP events\n    noisy = True\n\n    # A factory for IMessageDelivery objects.  If an\n    # avatar implementing IMessageDeliveryFactory can\n    # be acquired from the portal, it will be used to\n    # create a new IMessageDelivery object for each\n    # message which is received.\n    deliveryFactory = None\n\n    # An IMessageDelivery object.  A new instance is\n    # used for each message received if we can get an\n    # IMessageDeliveryFactory from the portal.  Otherwise,\n    # a single instance is used throughout the lifetime\n    # of the connection.\n    delivery = None\n\n    # Cred cleanup function.\n    _onLogout = None\n\n    def __init__(self, delivery=None, deliveryFactory=None):\n        self.mode = COMMAND\n        self._from = None\n        self._helo = None\n        self._to = []\n        self.delivery = delivery\n        self.deliveryFactory = deliveryFactory\n        self.host = DNSNAME\n\n\n    @property\n    def host(self):\n        return self._host\n\n\n    @host.setter\n    def host(self, toSet):\n        if not isinstance(toSet, bytes):\n            toSet = str(toSet).encode('ascii')\n        self._host = toSet\n\n\n\n    def timeoutConnection(self):\n        msg = self.host + b' Timeout. Try talking faster next time!'\n        self.sendCode(421, msg)\n        self.transport.loseConnection()\n\n\n    def greeting(self):\n        return self.host + b' NO UCE NO UBE NO RELAY PROBES'\n\n\n    def connectionMade(self):\n        # Ensure user-code always gets something sane for _helo\n        peer = self.transport.getPeer()\n        try:\n            host = peer.host\n        except AttributeError: # not an IPv4Address\n            host = str(peer)\n        self._helo = (None, host)\n        self.sendCode(220, self.greeting())\n        self.setTimeout(self.timeout)\n\n\n    def sendCode(self, code, message=b''):\n        \"\"\"\n        Send an SMTP code with a message.\n        \"\"\"\n        lines = message.splitlines()\n        lastline = lines[-1:]\n        for line in lines[:-1]:\n            self.sendLine(networkString('%3.3d-' % (code,)) + line)\n        self.sendLine(networkString('%3.3d ' % (code,)) +\n                                    (lastline and lastline[0] or b''))\n\n\n    def lineReceived(self, line):\n        self.resetTimeout()\n        return getattr(self, 'state_' + self.mode)(line)\n\n\n    def state_COMMAND(self, line):\n        # Ignore leading and trailing whitespace, as well as an arbitrary\n        # amount of whitespace between the command and its argument, though\n        # it is not required by the protocol, for it is a nice thing to do.\n        line = line.strip()\n\n        parts = line.split(None, 1)\n        if parts:\n            method = self.lookupMethod(parts[0]) or self.do_UNKNOWN\n            if len(parts) == 2:\n                method(parts[1])\n            else:\n                method(b'')\n        else:\n            self.sendSyntaxError()\n\n\n    def sendSyntaxError(self):\n        self.sendCode(500, b'Error: bad syntax')\n\n\n    def lookupMethod(self, command):\n        \"\"\"\n\n        @param command: The command to get from this class.\n        @type command: L{str}\n        @return: The function which executes this command.\n        \"\"\"\n        if not isinstance(command, str):\n            command = nativeString(command)\n\n        return getattr(self, 'do_' + command.upper(), None)\n\n\n    def lineLengthExceeded(self, line):\n        if self.mode is DATA:\n            for message in self.__messages:\n                message.connectionLost()\n            self.mode = COMMAND\n            del self.__messages\n        self.sendCode(500, b'Line too long')\n\n\n    def do_UNKNOWN(self, rest):\n        self.sendCode(500, b'Command not implemented')\n\n\n    def do_HELO(self, rest):\n        peer = self.transport.getPeer()\n        try:\n            host = peer.host\n        except AttributeError:\n            host = str(peer)\n\n        if not isinstance(host, bytes):\n            host = host.encode('idna')\n\n        self._helo = (rest, host)\n        self._from = None\n        self._to = []\n        self.sendCode(250,\n                      self.host + b' Hello ' + host + b', nice to meet you')\n\n\n    def do_QUIT(self, rest):\n        self.sendCode(221, b'See you later')\n        self.transport.loseConnection()\n\n    # A string of quoted strings, backslash-escaped character or\n    # atom characters + '@.,:'\n    qstring = br'(\"[^\"]*\"|\\\\.|' + atom + br'|[@.,:])+'\n\n    mail_re = re.compile(br'''\\s*FROM:\\s*(?P<path><> # Empty <>\n                          |<''' + qstring + br'''> # <addr>\n                          |''' + qstring + br''' # addr\n                          )\\s*(\\s(?P<opts>.*))? # Optional WS + ESMTP options\n                          $''', re.I|re.X)\n    rcpt_re = re.compile(br'\\s*TO:\\s*(?P<path><' + qstring + br'''> # <addr>\n                          |''' + qstring + br''' # addr\n                          )\\s*(\\s(?P<opts>.*))? # Optional WS + ESMTP options\n                          $''', re.I|re.X)\n\n    def do_MAIL(self, rest):\n        if self._from:\n            self.sendCode(503, b\"Only one sender per message, please\")\n            return\n        # Clear old recipient list\n        self._to = []\n        m = self.mail_re.match(rest)\n        if not m:\n            self.sendCode(501, b\"Syntax error\")\n            return\n\n        try:\n            addr = Address(m.group('path'), self.host)\n        except AddressError as e:\n            self.sendCode(553, networkString(str(e)))\n            return\n\n        validated = defer.maybeDeferred(self.validateFrom, self._helo, addr)\n        validated.addCallbacks(self._cbFromValidate, self._ebFromValidate)\n\n\n    def _cbFromValidate(self, fromEmail, code=250,\n                        msg=b'Sender address accepted'):\n        self._from = fromEmail\n        self.sendCode(code, msg)\n\n\n    def _ebFromValidate(self, failure):\n        if failure.check(SMTPBadSender):\n            self.sendCode(failure.value.code,\n                          (b'Cannot receive from specified address ' +\n                            quoteaddr(failure.value.addr) + b': ' +\n                            networkString(failure.value.resp)))\n        elif failure.check(SMTPServerError):\n            self.sendCode(failure.value.code,\n                          networkString(failure.value.resp))\n        else:\n            log.err(failure, \"SMTP sender validation failure\")\n            self.sendCode(\n                451,\n                b'Requested action aborted: local error in processing')\n\n\n    def do_RCPT(self, rest):\n        if not self._from:\n            self.sendCode(503, b\"Must have sender before recipient\")\n            return\n        m = self.rcpt_re.match(rest)\n        if not m:\n            self.sendCode(501, b\"Syntax error\")\n            return\n\n        try:\n            user = User(m.group('path'), self._helo, self, self._from)\n        except AddressError as e:\n            self.sendCode(553, networkString(str(e)))\n            return\n\n        d = defer.maybeDeferred(self.validateTo, user)\n        d.addCallbacks(\n            self._cbToValidate,\n            self._ebToValidate,\n            callbackArgs=(user,)\n        )\n\n\n    def _cbToValidate(self, to, user=None, code=250,\n                      msg=b'Recipient address accepted'):\n        if user is None:\n            user = to\n        self._to.append((user, to))\n        self.sendCode(code, msg)\n\n\n    def _ebToValidate(self, failure):\n        if failure.check(SMTPBadRcpt, SMTPServerError):\n            self.sendCode(failure.value.code,\n                          networkString(failure.value.resp))\n        else:\n            log.err(failure)\n            self.sendCode(\n                451,\n                b'Requested action aborted: local error in processing'\n            )\n\n\n    def _disconnect(self, msgs):\n        for msg in msgs:\n            try:\n                msg.connectionLost()\n            except:\n                log.msg(\"msg raised exception from connectionLost\")\n                log.err()\n\n\n    def do_DATA(self, rest):\n        if self._from is None or (not self._to):\n            self.sendCode(503, b'Must have valid receiver and originator')\n            return\n        self.mode = DATA\n        helo, origin = self._helo, self._from\n        recipients = self._to\n\n        self._from = None\n        self._to = []\n        self.datafailed = None\n\n        msgs = []\n        for (user, msgFunc) in recipients:\n            try:\n                msg = msgFunc()\n                rcvdhdr = self.receivedHeader(helo, origin, [user])\n                if rcvdhdr:\n                    msg.lineReceived(rcvdhdr)\n                msgs.append(msg)\n            except SMTPServerError as e:\n                self.sendCode(e.code, e.resp)\n                self.mode = COMMAND\n                self._disconnect(msgs)\n                return\n            except:\n                log.err()\n                self.sendCode(550, b\"Internal server error\")\n                self.mode = COMMAND\n                self._disconnect(msgs)\n                return\n        self.__messages = msgs\n\n        self.__inheader = self.__inbody = 0\n        self.sendCode(354, b'Continue')\n\n        if self.noisy:\n            fmt = 'Receiving message for delivery: from=%s to=%s'\n            log.msg(fmt % (origin, [str(u) for (u, f) in recipients]))\n\n\n    def connectionLost(self, reason):\n        # self.sendCode(421, 'Dropping connection.') # This does nothing...\n        # Ideally, if we (rather than the other side) lose the connection,\n        # we should be able to tell the other side that we are going away.\n        # RFC-2821 requires that we try.\n        if self.mode is DATA:\n            try:\n                for message in self.__messages:\n                    try:\n                        message.connectionLost()\n                    except:\n                        log.err()\n                del self.__messages\n            except AttributeError:\n                pass\n        if self._onLogout:\n            self._onLogout()\n            self._onLogout = None\n        self.setTimeout(None)\n\n\n    def do_RSET(self, rest):\n        self._from = None\n        self._to = []\n        self.sendCode(250, b'I remember nothing.')\n\n\n    def dataLineReceived(self, line):\n        if line[:1] == b'.':\n            if line == b'.':\n                self.mode = COMMAND\n                if self.datafailed:\n                    self.sendCode(self.datafailed.code,\n                                  self.datafailed.resp)\n                    return\n                if not self.__messages:\n                    self._messageHandled(\"thrown away\")\n                    return\n                defer.DeferredList([\n                    m.eomReceived() for m in self.__messages\n                ], consumeErrors=True).addCallback(self._messageHandled\n                                                   )\n                del self.__messages\n                return\n            line = line[1:]\n\n        if self.datafailed:\n            return\n\n        try:\n            # Add a blank line between the generated Received:-header\n            # and the message body if the message comes in without any\n            # headers\n            if not self.__inheader and not self.__inbody:\n                if b':' in line:\n                    self.__inheader = 1\n                elif line:\n                    for message in self.__messages:\n                        message.lineReceived(b'')\n                    self.__inbody = 1\n\n            if not line:\n                self.__inbody = 1\n\n            for message in self.__messages:\n                message.lineReceived(line)\n        except SMTPServerError as e:\n            self.datafailed = e\n            for message in self.__messages:\n                message.connectionLost()\n    state_DATA = dataLineReceived\n\n\n    def _messageHandled(self, resultList):\n        failures = 0\n        for (success, result) in resultList:\n            if not success:\n                failures += 1\n                log.err(result)\n        if failures:\n            msg = 'Could not send e-mail'\n            resultLen = len(resultList)\n            if resultLen > 1:\n                msg += ' (%d failures out of %d recipients)'.format(\n                    failures, resultLen)\n            self.sendCode(550, networkString(msg))\n        else:\n            self.sendCode(250, b'Delivery in progress')\n\n\n    def _cbAnonymousAuthentication(self, result):\n        \"\"\"\n        Save the state resulting from a successful anonymous cred login.\n        \"\"\"\n        (iface, avatar, logout) = result\n        if issubclass(iface, IMessageDeliveryFactory):\n            self.deliveryFactory = avatar\n            self.delivery = None\n        elif issubclass(iface, IMessageDelivery):\n            self.deliveryFactory = None\n            self.delivery = avatar\n        else:\n            raise RuntimeError(\"%s is not a supported interface\" % (iface.__name__,))\n        self._onLogout = logout\n        self.challenger = None\n\n\n    # overridable methods:\n    def validateFrom(self, helo, origin):\n        \"\"\"\n        Validate the address from which the message originates.\n\n        @type helo: C{(bytes, bytes)}\n        @param helo: The argument to the HELO command and the client's IP\n        address.\n\n        @type origin: C{Address}\n        @param origin: The address the message is from\n\n        @rtype: C{Deferred} or C{Address}\n        @return: C{origin} or a C{Deferred} whose callback will be\n        passed C{origin}.\n\n        @raise SMTPBadSender: Raised of messages from this address are\n        not to be accepted.\n        \"\"\"\n        if self.deliveryFactory is not None:\n            self.delivery = self.deliveryFactory.getMessageDelivery()\n\n        if self.delivery is not None:\n            return defer.maybeDeferred(self.delivery.validateFrom,\n                                       helo, origin)\n\n        # No login has been performed, no default delivery object has been\n        # provided: try to perform an anonymous login and then invoke this\n        # method again.\n        if self.portal:\n\n            result = self.portal.login(\n                cred.credentials.Anonymous(),\n                None,\n                IMessageDeliveryFactory, IMessageDelivery)\n\n            def ebAuthentication(err):\n                \"\"\"\n                Translate cred exceptions into SMTP exceptions so that the\n                protocol code which invokes C{validateFrom} can properly report\n                the failure.\n                \"\"\"\n                if err.check(cred.error.UnauthorizedLogin):\n                    exc = SMTPBadSender(origin)\n                elif err.check(cred.error.UnhandledCredentials):\n                    exc = SMTPBadSender(\n                        origin, resp=\"Unauthenticated senders not allowed\")\n                else:\n                    return err\n                return defer.fail(exc)\n\n            result.addCallbacks(\n                self._cbAnonymousAuthentication, ebAuthentication)\n\n            def continueValidation(ignored):\n                \"\"\"\n                Re-attempt from address validation.\n                \"\"\"\n                return self.validateFrom(helo, origin)\n\n            result.addCallback(continueValidation)\n            return result\n\n        raise SMTPBadSender(origin)\n\n\n    def validateTo(self, user):\n        \"\"\"\n        Validate the address for which the message is destined.\n\n        @type user: L{User}\n        @param user: The address to validate.\n\n        @rtype: no-argument callable\n        @return: A C{Deferred} which becomes, or a callable which\n        takes no arguments and returns an object implementing C{IMessage}.\n        This will be called and the returned object used to deliver the\n        message when it arrives.\n\n        @raise SMTPBadRcpt: Raised if messages to the address are\n        not to be accepted.\n        \"\"\"\n        if self.delivery is not None:\n            return self.delivery.validateTo(user)\n        raise SMTPBadRcpt(user)\n\n\n    def receivedHeader(self, helo, origin, recipients):\n        if self.delivery is not None:\n            return self.delivery.receivedHeader(helo, origin, recipients)\n\n        heloStr = b\"\"\n        if helo[0]:\n            heloStr = b\" helo=\" + helo[0]\n        domain = networkString(self.transport.getHost().host)\n\n        from_ = b\"from \" + helo[0] + b\" ([\" + helo[1] + b\"]\" + heloStr + b\")\"\n        by = b\"by %s with %s (%s)\" % (domain,\n                                     self.__class__.__name__,\n                                     longversion)\n        for_ = b\"for %s; %s\" % (' '.join(map(str, recipients)),\n                               rfc822date())\n        return b\"Received: \" + from_ + b\"\\n\\t\" + by + b\"\\n\\t\" + for_\n\n\n\nclass SMTPFactory(protocol.ServerFactory):\n    \"\"\"\n    Factory for SMTP.\n    \"\"\"\n\n    # override in instances or subclasses\n    domain = DNSNAME\n    timeout = 600\n    protocol = SMTP\n\n    portal = None\n\n    def __init__(self, portal = None):\n        self.portal = portal\n\n\n    def buildProtocol(self, addr):\n        p = protocol.ServerFactory.buildProtocol(self, addr)\n        p.portal = self.portal\n        p.host = self.domain\n        return p\n\n\n\nclass SMTPClient(basic.LineReceiver, policies.TimeoutMixin):\n    \"\"\"\n    SMTP client for sending emails.\n\n    After the client has connected to the SMTP server, it repeatedly calls\n    L{SMTPClient.getMailFrom}, L{SMTPClient.getMailTo} and\n    L{SMTPClient.getMailData} and uses this information to send an email.\n    It then calls L{SMTPClient.getMailFrom} again; if it returns L{None}, the\n    client will disconnect, otherwise it will continue as normal i.e. call\n    L{SMTPClient.getMailTo} and L{SMTPClient.getMailData} and send a new email.\n    \"\"\"\n\n    # If enabled then log SMTP client server communication\n    debug = True\n\n    # Number of seconds to wait before timing out a connection.  If\n    # None, perform no timeout checking.\n    timeout = None\n\n    def __init__(self, identity, logsize=10):\n        if isinstance(identity, unicode):\n            identity = identity.encode('ascii')\n\n        self.identity = identity or b''\n        self.toAddressesResult = []\n        self.successAddresses = []\n        self._from = None\n        self.resp = []\n        self.code = -1\n        self.log = util.LineLog(logsize)\n\n\n    def sendLine(self, line):\n        # Log sendLine only if you are in debug mode for performance\n        if self.debug:\n            self.log.append(b'>>> ' + line)\n\n        basic.LineReceiver.sendLine(self,line)\n\n\n    def connectionMade(self):\n        self.setTimeout(self.timeout)\n\n        self._expected = [ 220 ]\n        self._okresponse = self.smtpState_helo\n        self._failresponse = self.smtpConnectionFailed\n\n\n    def connectionLost(self, reason=protocol.connectionDone):\n        \"\"\"\n        We are no longer connected\n        \"\"\"\n        self.setTimeout(None)\n        self.mailFile = None\n\n\n    def timeoutConnection(self):\n        self.sendError(\n            SMTPTimeoutError(\n                -1, b\"Timeout waiting for SMTP server response\",\n                 self.log.str()))\n\n\n    def lineReceived(self, line):\n        self.resetTimeout()\n\n        # Log lineReceived only if you are in debug mode for performance\n        if self.debug:\n            self.log.append(b'<<< ' + line)\n\n        why = None\n\n        try:\n            self.code = int(line[:3])\n        except ValueError:\n            # This is a fatal error and will disconnect the transport\n            # lineReceived will not be called again.\n            self.sendError(SMTPProtocolError(-1,\n                \"Invalid response from SMTP server: {}\".format(line),\n                self.log.str()))\n            return\n\n        if line[0:1] == b'0':\n            # Verbose informational message, ignore it\n            return\n\n        self.resp.append(line[4:])\n\n        if line[3:4] == b'-':\n            # Continuation\n            return\n\n        if self.code in self._expected:\n            why = self._okresponse(self.code, b'\\n'.join(self.resp))\n        else:\n            why = self._failresponse(self.code, b'\\n'.join(self.resp))\n\n        self.code = -1\n        self.resp = []\n        return why\n\n\n    def smtpConnectionFailed(self, code, resp):\n        self.sendError(SMTPConnectError(code, resp, self.log.str()))\n\n\n    def smtpTransferFailed(self, code, resp):\n        if code < 0:\n            self.sendError(SMTPProtocolError(code, resp, self.log.str()))\n        else:\n            self.smtpState_msgSent(code, resp)\n\n\n    def smtpState_helo(self, code, resp):\n        self.sendLine(b'HELO ' + self.identity)\n        self._expected = SUCCESS\n        self._okresponse = self.smtpState_from\n\n\n    def smtpState_from(self, code, resp):\n        self._from = self.getMailFrom()\n        self._failresponse = self.smtpTransferFailed\n        if self._from is not None:\n            self.sendLine(b'MAIL FROM:' + quoteaddr(self._from))\n            self._expected = [250]\n            self._okresponse = self.smtpState_to\n        else:\n            # All messages have been sent, disconnect\n            self._disconnectFromServer()\n\n\n    def smtpState_disconnect(self, code, resp):\n        self.transport.loseConnection()\n\n\n    def smtpState_to(self, code, resp):\n        self.toAddresses = iter(self.getMailTo())\n        self.toAddressesResult = []\n        self.successAddresses = []\n        self._okresponse = self.smtpState_toOrData\n        self._expected = range(0, 1000)\n        self.lastAddress = None\n        return self.smtpState_toOrData(0, b'')\n\n\n    def smtpState_toOrData(self, code, resp):\n        if self.lastAddress is not None:\n            self.toAddressesResult.append((self.lastAddress, code, resp))\n            if code in SUCCESS:\n                self.successAddresses.append(self.lastAddress)\n        try:\n            self.lastAddress = next(self.toAddresses)\n        except StopIteration:\n            if self.successAddresses:\n                self.sendLine(b'DATA')\n                self._expected = [ 354 ]\n                self._okresponse = self.smtpState_data\n            else:\n                return self.smtpState_msgSent(code,'No recipients accepted')\n        else:\n            self.sendLine(b'RCPT TO:' + quoteaddr(self.lastAddress))\n\n\n    def smtpState_data(self, code, resp):\n        s = basic.FileSender()\n        d = s.beginFileTransfer(\n            self.getMailData(), self.transport, self.transformChunk)\n        def ebTransfer(err):\n            self.sendError(err.value)\n        d.addCallbacks(self.finishedFileTransfer, ebTransfer)\n        self._expected = SUCCESS\n        self._okresponse = self.smtpState_msgSent\n\n\n    def smtpState_msgSent(self, code, resp):\n        if self._from is not None:\n            self.sentMail(code, resp, len(self.successAddresses),\n                          self.toAddressesResult, self.log)\n\n        self.toAddressesResult = []\n        self._from = None\n        self.sendLine(b'RSET')\n        self._expected = SUCCESS\n        self._okresponse = self.smtpState_from\n\n\n    ##\n    ## Helpers for FileSender\n    ##\n    def transformChunk(self, chunk):\n        \"\"\"\n        Perform the necessary local to network newline conversion and escape\n        leading periods.\n\n        This method also resets the idle timeout so that as long as process is\n        being made sending the message body, the client will not time out.\n        \"\"\"\n        self.resetTimeout()\n        return chunk.replace(b'\\n', b'\\r\\n').replace(b'\\r\\n.', b'\\r\\n..')\n\n\n    def finishedFileTransfer(self, lastsent):\n        if lastsent != b'\\n':\n            line = b'\\r\\n.'\n        else:\n            line = b'.'\n        self.sendLine(line)\n\n\n    ##\n    # these methods should be overridden in subclasses\n    def getMailFrom(self):\n        \"\"\"\n        Return the email address the mail is from.\n        \"\"\"\n        raise NotImplementedError\n\n\n    def getMailTo(self):\n        \"\"\"\n        Return a list of emails to send to.\n        \"\"\"\n        raise NotImplementedError\n\n\n    def getMailData(self):\n        \"\"\"\n        Return file-like object containing data of message to be sent.\n\n        Lines in the file should be delimited by '\\\\n'.\n        \"\"\"\n        raise NotImplementedError\n\n\n    def sendError(self, exc):\n        \"\"\"\n        If an error occurs before a mail message is sent sendError will be\n        called.  This base class method sends a QUIT if the error is\n        non-fatal and disconnects the connection.\n\n        @param exc: The SMTPClientError (or child class) raised\n        @type exc: C{SMTPClientError}\n        \"\"\"\n        if isinstance(exc, SMTPClientError) and not exc.isFatal:\n            self._disconnectFromServer()\n        else:\n            # If the error was fatal then the communication channel with the\n            # SMTP Server is broken so just close the transport connection\n            self.smtpState_disconnect(-1, None)\n\n\n    def sentMail(self, code, resp, numOk, addresses, log):\n        \"\"\"\n        Called when an attempt to send an email is completed.\n\n        If some addresses were accepted, code and resp are the response\n        to the DATA command. If no addresses were accepted, code is -1\n        and resp is an informative message.\n\n        @param code: the code returned by the SMTP Server\n        @param resp: The string response returned from the SMTP Server\n        @param numOK: the number of addresses accepted by the remote host.\n        @param addresses: is a list of tuples (address, code, resp) listing\n                          the response to each RCPT command.\n        @param log: is the SMTP session log\n        \"\"\"\n        raise NotImplementedError\n\n\n    def _disconnectFromServer(self):\n        self._expected = range(0, 1000)\n        self._okresponse = self.smtpState_disconnect\n        self.sendLine(b'QUIT')\n\n\n\nclass ESMTPClient(SMTPClient):\n    \"\"\"\n    A client for sending emails over ESMTP.\n\n    @ivar heloFallback: Whether or not to fall back to plain SMTP if the C{EHLO}\n        command is not recognised by the server. If L{requireAuthentication} is\n        C{True}, or L{requireTransportSecurity} is C{True} and the connection is\n        not over TLS, this fallback flag will not be honored.\n    @type heloFallback: L{bool}\n\n    @ivar requireAuthentication: If C{True}, refuse to proceed if authentication\n        cannot be performed. Overrides L{heloFallback}.\n    @type requireAuthentication: L{bool}\n\n    @ivar requireTransportSecurity: If C{True}, refuse to proceed if the\n        transport cannot be secured. If the transport layer is not already\n        secured via TLS, this will override L{heloFallback}.\n    @type requireAuthentication: L{bool}\n\n    @ivar context: The context factory to use for STARTTLS, if desired.\n    @type context: L{ssl.ClientContextFactory}\n\n    @ivar _tlsMode: Whether or not the connection is over TLS.\n    @type _tlsMode: L{bool}\n    \"\"\"\n    heloFallback = True\n    requireAuthentication = False\n    requireTransportSecurity = False\n    context = None\n    _tlsMode = False\n\n    def __init__(self, secret, contextFactory=None, *args, **kw):\n        SMTPClient.__init__(self, *args, **kw)\n        self.authenticators = []\n        self.secret = secret\n        self.context = contextFactory\n\n\n    def __getattr__(self, name):\n        if name == \"tlsMode\":\n            warnings.warn(\n                \"tlsMode attribute of twisted.mail.smtp.ESMTPClient \"\n                \"is deprecated since Twisted 13.0\",\n                category=DeprecationWarning, stacklevel=2)\n            return self._tlsMode\n        else:\n            raise AttributeError(\n                '%s instance has no attribute %r' % (\n                    self.__class__.__name__, name,))\n\n\n    def __setattr__(self, name, value):\n        if name == \"tlsMode\":\n            warnings.warn(\n                \"tlsMode attribute of twisted.mail.smtp.ESMTPClient \"\n                \"is deprecated since Twisted 13.0\",\n                category=DeprecationWarning, stacklevel=2)\n            self._tlsMode = value\n        else:\n            self.__dict__[name] = value\n\n\n    def esmtpEHLORequired(self, code=-1, resp=None):\n        \"\"\"\n        Fail because authentication is required, but the server does not support\n        ESMTP, which is required for authentication.\n\n        @param code: The server status code from the most recently received\n            server message.\n        @type code: L{int}\n\n        @param resp: The server status response from the most recently received\n            server message.\n        @type resp: L{bytes}\n        \"\"\"\n        self.sendError(EHLORequiredError(502, b\"Server does not support ESMTP \"\n            b\"Authentication\", self.log.str()))\n\n\n    def esmtpAUTHRequired(self, code=-1, resp=None):\n        \"\"\"\n        Fail because authentication is required, but the server does not support\n        any schemes we support.\n\n        @param code: The server status code from the most recently received\n            server message.\n        @type code: L{int}\n\n        @param resp: The server status response from the most recently received\n            server message.\n        @type resp: L{bytes}\n        \"\"\"\n        tmp = []\n\n        for a in self.authenticators:\n            tmp.append(a.getName().upper())\n\n        auth = b\"[%s]\" % b\", \".join(tmp)\n\n        self.sendError(AUTHRequiredError(502, b\"Server does not support Client \"\n            b\"Authentication schemes %s\" % auth, self.log.str()))\n\n\n    def esmtpTLSRequired(self, code=-1, resp=None):\n        \"\"\"\n        Fail because TLS is required and the server does not support it.\n\n        @param code: The server status code from the most recently received\n            server message.\n        @type code: L{int}\n\n        @param resp: The server status response from the most recently received\n            server message.\n        @type resp: L{bytes}\n        \"\"\"\n        self.sendError(TLSRequiredError(502, b\"Server does not support secure \"\n            b\"communication via TLS / SSL\", self.log.str()))\n\n\n    def esmtpTLSFailed(self, code=-1, resp=None):\n        \"\"\"\n        Fail because the TLS handshake wasn't able to be completed.\n\n        @param code: The server status code from the most recently received\n            server message.\n        @type code: L{int}\n\n        @param resp: The server status response from the most recently received\n            server message.\n        @type resp: L{bytes}\n        \"\"\"\n        self.sendError(TLSError(code, b\"Could not complete the SSL/TLS \"\n            b\"handshake\", self.log.str()))\n\n\n    def esmtpAUTHDeclined(self, code=-1, resp=None):\n        \"\"\"\n        Fail because the authentication was rejected.\n\n        @param code: The server status code from the most recently received\n            server message.\n        @type code: L{int}\n\n        @param resp: The server status response from the most recently received\n            server message.\n        @type resp: L{bytes}\n        \"\"\"\n        self.sendError(AUTHDeclinedError(code, resp, self.log.str()))\n\n\n    def esmtpAUTHMalformedChallenge(self, code=-1, resp=None):\n        \"\"\"\n        Fail because the server sent a malformed authentication challenge.\n\n        @param code: The server status code from the most recently received\n            server message.\n        @type code: L{int}\n\n        @param resp: The server status response from the most recently received\n            server message.\n        @type resp: L{bytes}\n        \"\"\"\n        self.sendError(AuthenticationError(501, b\"Login failed because the \"\n            b\"SMTP Server returned a malformed Authentication Challenge\",\n            self.log.str()))\n\n\n    def esmtpAUTHServerError(self, code=-1, resp=None):\n        \"\"\"\n        Fail because of some other authentication error.\n\n        @param code: The server status code from the most recently received\n            server message.\n        @type code: L{int}\n\n        @param resp: The server status response from the most recently received\n            server message.\n        @type resp: L{bytes}\n        \"\"\"\n        self.sendError(AuthenticationError(code, resp, self.log.str()))\n\n\n    def registerAuthenticator(self, auth):\n        \"\"\"\n        Registers an Authenticator with the ESMTPClient. The ESMTPClient will\n        attempt to login to the SMTP Server in the order the Authenticators are\n        registered. The most secure Authentication mechanism should be\n        registered first.\n\n        @param auth: The Authentication mechanism to register\n        @type auth: L{IClientAuthentication} implementor\n\n        @return: L{None}\n        \"\"\"\n        self.authenticators.append(auth)\n\n\n    def connectionMade(self):\n        \"\"\"\n        Called when a connection has been made, and triggers sending an C{EHLO}\n        to the server.\n        \"\"\"\n        self._tlsMode = ISSLTransport.providedBy(self.transport)\n        SMTPClient.connectionMade(self)\n        self._okresponse = self.esmtpState_ehlo\n\n\n    def esmtpState_ehlo(self, code, resp):\n        \"\"\"\n        Send an C{EHLO} to the server.\n\n        If L{heloFallback} is C{True}, and there is no requirement for TLS or\n        authentication, the client will fall back to basic SMTP.\n\n        @param code: The server status code from the most recently received\n            server message.\n        @type code: L{int}\n\n        @param resp: The server status response from the most recently received\n            server message.\n        @type resp: L{bytes}\n\n        @return: L{None}\n        \"\"\"\n        self._expected = SUCCESS\n\n        self._okresponse = self.esmtpState_serverConfig\n        self._failresponse = self.esmtpEHLORequired\n\n        if self._tlsMode:\n            needTLS = False\n        else:\n            needTLS = self.requireTransportSecurity\n\n        if self.heloFallback and not self.requireAuthentication and not needTLS:\n            self._failresponse = self.smtpState_helo\n\n        self.sendLine(b\"EHLO \" + self.identity)\n\n\n    def esmtpState_serverConfig(self, code, resp):\n        \"\"\"\n        Handle a positive response to the I{EHLO} command by parsing the\n        capabilities in the server's response and then taking the most\n        appropriate next step towards entering a mail transaction.\n        \"\"\"\n        items = {}\n        for line in resp.splitlines():\n            e = line.split(None, 1)\n            if len(e) > 1:\n                items[e[0]] = e[1]\n            else:\n                items[e[0]] = None\n\n        self.tryTLS(code, resp, items)\n\n\n    def tryTLS(self, code, resp, items):\n        \"\"\"\n        Take a necessary step towards being able to begin a mail transaction.\n\n        The step may be to ask the server to being a TLS session.  If TLS is\n        already in use or not necessary and not available then the step may be\n        to authenticate with the server.  If TLS is necessary and not available,\n        fail the mail transmission attempt.\n\n        This is an internal helper method.\n\n        @param code: The server status code from the most recently received\n            server message.\n        @type code: L{int}\n\n        @param resp: The server status response from the most recently received\n            server message.\n        @type resp: L{bytes}\n\n        @param items: A mapping of ESMTP extensions offered by the server.  Keys\n            are extension identifiers and values are the associated values.\n        @type items: L{dict} mapping L{bytes} to L{bytes}\n\n        @return: L{None}\n        \"\"\"\n\n        # has tls        can tls         must tls       result\n        #   t               t               t           authenticate\n        #   t               t               f           authenticate\n        #   t               f               t           authenticate\n        #   t               f               f           authenticate\n\n        #   f               t               t           STARTTLS\n        #   f               t               f           STARTTLS\n        #   f               f               t           esmtpTLSRequired\n        #   f               f               f           authenticate\n\n        hasTLS = self._tlsMode\n        canTLS = self.context and b\"STARTTLS\" in items\n        mustTLS = self.requireTransportSecurity\n\n        if hasTLS or not (canTLS or mustTLS):\n            self.authenticate(code, resp, items)\n        elif canTLS:\n            self._expected = [220]\n            self._okresponse = self.esmtpState_starttls\n            self._failresponse = self.esmtpTLSFailed\n            self.sendLine(b\"STARTTLS\")\n        else:\n            self.esmtpTLSRequired()\n\n\n    def esmtpState_starttls(self, code, resp):\n        \"\"\"\n        Handle a positive response to the I{STARTTLS} command by starting a new\n        TLS session on C{self.transport}.\n\n        Upon success, re-handshake with the server to discover what capabilities\n        it has when TLS is in use.\n        \"\"\"\n        try:\n            self.transport.startTLS(self.context)\n            self._tlsMode = True\n        except:\n            log.err()\n            self.esmtpTLSFailed(451)\n\n        # Send another EHLO once TLS has been started to\n        # get the TLS / AUTH schemes. Some servers only allow AUTH in TLS mode.\n        self.esmtpState_ehlo(code, resp)\n\n\n    def authenticate(self, code, resp, items):\n        if self.secret and items.get(b'AUTH'):\n            schemes = items[b'AUTH'].split()\n            tmpSchemes = {}\n\n            #XXX: May want to come up with a more efficient way to do this\n            for s in schemes:\n                tmpSchemes[s.upper()] = 1\n\n            for a in self.authenticators:\n                auth = a.getName().upper()\n\n                if auth in tmpSchemes:\n                    self._authinfo = a\n\n                    # Special condition handled\n                    if auth == b\"PLAIN\":\n                        self._okresponse = self.smtpState_from\n                        self._failresponse = self._esmtpState_plainAuth\n                        self._expected = [235]\n                        challenge = base64.b64encode(\n                            self._authinfo.challengeResponse(self.secret, 1))\n                        self.sendLine(b\"AUTH %s %s\" % (auth, challenge))\n                    else:\n                        self._expected = [334]\n                        self._okresponse = self.esmtpState_challenge\n                        # If some error occurs here, the server declined the\n                        # AUTH before the user / password phase. This would be\n                        # a very rare case\n                        self._failresponse = self.esmtpAUTHServerError\n                        self.sendLine(b'AUTH ' + auth)\n                    return\n\n        if self.requireAuthentication:\n            self.esmtpAUTHRequired()\n        else:\n            self.smtpState_from(code, resp)\n\n\n    def _esmtpState_plainAuth(self, code, resp):\n        self._okresponse = self.smtpState_from\n        self._failresponse = self.esmtpAUTHDeclined\n        self._expected = [235]\n        challenge = base64.b64encode(\n                        self._authinfo.challengeResponse(self.secret, 2))\n        self.sendLine(b'AUTH PLAIN ' + challenge)\n\n\n    def esmtpState_challenge(self, code, resp):\n        self._authResponse(self._authinfo, resp)\n\n\n    def _authResponse(self, auth, challenge):\n        self._failresponse = self.esmtpAUTHDeclined\n        try:\n            challenge = base64.b64decode(challenge)\n        except binascii.Error:\n            # Illegal challenge, give up, then quit\n            self.sendLine(b'*')\n            self._okresponse = self.esmtpAUTHMalformedChallenge\n            self._failresponse = self.esmtpAUTHMalformedChallenge\n        else:\n            resp = auth.challengeResponse(self.secret, challenge)\n            self._expected = [235, 334]\n            self._okresponse = self.smtpState_maybeAuthenticated\n            self.sendLine(base64.b64encode(resp))\n\n\n    def smtpState_maybeAuthenticated(self, code, resp):\n        \"\"\"\n        Called to handle the next message from the server after sending a\n        response to a SASL challenge.  The server response might be another\n        challenge or it might indicate authentication has succeeded.\n        \"\"\"\n        if code == 235:\n            # Yes, authenticated!\n            del self._authinfo\n            self.smtpState_from(code, resp)\n        else:\n            # No, not authenticated yet.  Keep trying.\n            self._authResponse(self._authinfo, resp)\n\n\n\nclass ESMTP(SMTP):\n    ctx = None\n    canStartTLS = False\n    startedTLS = False\n\n    authenticated = False\n\n    def __init__(self, chal=None, contextFactory=None):\n        SMTP.__init__(self)\n        if chal is None:\n            chal = {}\n        self.challengers = chal\n        self.authenticated = False\n        self.ctx = contextFactory\n\n\n    def connectionMade(self):\n        SMTP.connectionMade(self)\n        self.canStartTLS = ITLSTransport.providedBy(self.transport)\n        self.canStartTLS = self.canStartTLS and (self.ctx is not None)\n\n\n    def greeting(self):\n        return SMTP.greeting(self) + b' ESMTP'\n\n\n    def extensions(self):\n        \"\"\"\n        SMTP service extensions\n\n        @return: the SMTP service extensions that are supported.\n        @rtype: L{dict} with L{bytes} keys and a value of either L{None} or a\n            L{list} of L{bytes}.\n        \"\"\"\n        ext = {b'AUTH': _keys(self.challengers)}\n        if self.canStartTLS and not self.startedTLS:\n            ext[b'STARTTLS'] = None\n        return ext\n\n\n    def lookupMethod(self, command):\n        command = nativeString(command)\n\n        m = SMTP.lookupMethod(self, command)\n        if m is None:\n            m = getattr(self, 'ext_' + command.upper(), None)\n        return m\n\n\n    def listExtensions(self):\n        r = []\n        for (c, v) in iteritems(self.extensions()):\n            if v is not None:\n                if v:\n                    # Intentionally omit extensions with empty argument lists\n                    r.append(c + b' ' +  b' '.join(v))\n            else:\n                r.append(c)\n\n        return b'\\n'.join(r)\n\n\n    def do_EHLO(self, rest):\n        peer = self.transport.getPeer().host\n\n        if not isinstance(peer, bytes):\n            peer = peer.encode('idna')\n\n        self._helo = (rest, peer)\n        self._from = None\n        self._to = []\n        self.sendCode(\n            250,\n            (self.host + b' Hello ' + peer + b', nice to meet you\\n' +\n             self.listExtensions())\n        )\n\n\n    def ext_STARTTLS(self, rest):\n        if self.startedTLS:\n            self.sendCode(503, b'TLS already negotiated')\n        elif self.ctx and self.canStartTLS:\n            self.sendCode(220, b'Begin TLS negotiation now')\n            self.transport.startTLS(self.ctx)\n            self.startedTLS = True\n        else:\n            self.sendCode(454, b'TLS not available')\n\n\n    def ext_AUTH(self, rest):\n        if self.authenticated:\n            self.sendCode(503, b'Already authenticated')\n            return\n        parts = rest.split(None, 1)\n        chal = self.challengers.get(parts[0].upper(), lambda: None)()\n        if not chal:\n            self.sendCode(504, b'Unrecognized authentication type')\n            return\n\n        self.mode = AUTH\n        self.challenger = chal\n\n        if len(parts) > 1:\n            chal.getChallenge() # Discard it, apparently the client does not\n                                # care about it.\n            rest = parts[1]\n        else:\n            rest = None\n        self.state_AUTH(rest)\n\n\n    def _cbAuthenticated(self, loginInfo):\n        \"\"\"\n        Save the state resulting from a successful cred login and mark this\n        connection as authenticated.\n        \"\"\"\n        result = SMTP._cbAnonymousAuthentication(self, loginInfo)\n        self.authenticated = True\n        return result\n\n\n    def _ebAuthenticated(self, reason):\n        \"\"\"\n        Handle cred login errors by translating them to the SMTP authenticate\n        failed.  Translate all other errors into a generic SMTP error code and\n        log the failure for inspection.  Stop all errors from propagating.\n\n        @param reason: Reason for failure.\n        \"\"\"\n        self.challenge = None\n        if reason.check(cred.error.UnauthorizedLogin):\n            self.sendCode(535, b'Authentication failed')\n        else:\n            log.err(reason, \"SMTP authentication failure\")\n            self.sendCode(\n                451,\n                b'Requested action aborted: local error in processing')\n\n\n    def state_AUTH(self, response):\n        \"\"\"\n        Handle one step of challenge/response authentication.\n\n        @param response: The text of a response. If None, this\n        function has been called as a result of an AUTH command with\n        no initial response. A response of '*' aborts authentication,\n        as per RFC 2554.\n        \"\"\"\n        if self.portal is None:\n            self.sendCode(454, b'Temporary authentication failure')\n            self.mode = COMMAND\n            return\n\n        if response is None:\n            challenge = self.challenger.getChallenge()\n            encoded = base64.b64encode(challenge)\n            self.sendCode(334, encoded)\n            return\n\n        if response == b'*':\n            self.sendCode(501, b'Authentication aborted')\n            self.challenger = None\n            self.mode = COMMAND\n            return\n\n        try:\n            uncoded = base64.b64decode(response)\n        except (TypeError, binascii.Error):\n            self.sendCode(501, b'Syntax error in parameters or arguments')\n            self.challenger = None\n            self.mode = COMMAND\n            return\n\n        self.challenger.setResponse(uncoded)\n        if self.challenger.moreChallenges():\n            challenge = self.challenger.getChallenge()\n            coded = base64.b64encode(challenge)\n            self.sendCode(334, coded)\n            return\n\n        self.mode = COMMAND\n        result = self.portal.login(\n            self.challenger, None,\n            IMessageDeliveryFactory, IMessageDelivery)\n        result.addCallback(self._cbAuthenticated)\n        result.addCallback(lambda ign: self.sendCode(235,\n                           b'Authentication successful.'))\n        result.addErrback(self._ebAuthenticated)\n\n\n\nclass SenderMixin:\n    \"\"\"\n    Utility class for sending emails easily.\n\n    Use with SMTPSenderFactory or ESMTPSenderFactory.\n    \"\"\"\n    done = 0\n\n    def getMailFrom(self):\n        if not self.done:\n            self.done = 1\n            return str(self.factory.fromEmail)\n        else:\n            return None\n\n\n    def getMailTo(self):\n        return self.factory.toEmail\n\n\n    def getMailData(self):\n        return self.factory.file\n\n\n    def sendError(self, exc):\n        # Call the base class to close the connection with the SMTP server\n        SMTPClient.sendError(self, exc)\n\n        #  Do not retry to connect to SMTP Server if:\n        #   1. No more retries left (This allows the correct error to be returned to the errorback)\n        #   2. retry is false\n        #   3. The error code is not in the 4xx range (Communication Errors)\n\n        if (self.factory.retries >= 0 or\n            (not exc.retry and not (exc.code >= 400 and exc.code < 500))):\n            self.factory.sendFinished = True\n            self.factory.result.errback(exc)\n\n\n    def sentMail(self, code, resp, numOk, addresses, log):\n        # Do not retry, the SMTP server acknowledged the request\n        self.factory.sendFinished = True\n        if code not in SUCCESS:\n            errlog = []\n            for addr, acode, aresp in addresses:\n                if acode not in SUCCESS:\n                    errlog.append((addr + b\": \" +\n                                   networkString(\"%03d\" % (acode,)) +\n                                   b\" \" + aresp))\n\n            errlog.append(log.str())\n\n            exc = SMTPDeliveryError(code, resp, b'\\n'.join(errlog), addresses)\n            self.factory.result.errback(exc)\n        else:\n            self.factory.result.callback((numOk, addresses))\n\n\n\nclass SMTPSender(SenderMixin, SMTPClient):\n    \"\"\"\n    SMTP protocol that sends a single email based on information it\n    gets from its factory, a L{SMTPSenderFactory}.\n    \"\"\"\n\n\n\nclass SMTPSenderFactory(protocol.ClientFactory):\n    \"\"\"\n    Utility factory for sending emails easily.\n\n    @type currentProtocol: L{SMTPSender}\n    @ivar currentProtocol: The current running protocol returned by\n        L{buildProtocol}.\n\n    @type sendFinished: C{bool}\n    @ivar sendFinished: When the value is set to True, it means the message has\n        been sent or there has been an unrecoverable error or the sending has\n        been cancelled. The default value is False.\n    \"\"\"\n\n    domain = DNSNAME\n    protocol = SMTPSender\n\n    def __init__(self, fromEmail, toEmail, file, deferred, retries=5,\n                 timeout=None):\n        \"\"\"\n        @param fromEmail: The RFC 2821 address from which to send this\n        message.\n\n        @param toEmail: A sequence of RFC 2821 addresses to which to\n        send this message.\n\n        @param file: A file-like object containing the message to send.\n\n        @param deferred: A Deferred to callback or errback when sending\n        of this message completes.\n        @type deferred: L{defer.Deferred}\n\n        @param retries: The number of times to retry delivery of this\n        message.\n\n        @param timeout: Period, in seconds, for which to wait for\n        server responses, or None to wait forever.\n        \"\"\"\n        assert isinstance(retries, (int, long))\n\n        if isinstance(toEmail, unicode):\n            toEmail = [toEmail.encode('ascii')]\n        elif isinstance(toEmail, bytes):\n            toEmail = [toEmail]\n        else:\n            toEmailFinal = []\n            for _email in toEmail:\n                if not isinstance(_email, bytes):\n                    _email = _email.encode('ascii')\n\n                toEmailFinal.append(_email)\n            toEmail = toEmailFinal\n\n        self.fromEmail = Address(fromEmail)\n        self.nEmails = len(toEmail)\n        self.toEmail = toEmail\n        self.file = file\n        self.result = deferred\n        self.result.addBoth(self._removeDeferred)\n        self.sendFinished = False\n        self.currentProtocol = None\n\n        self.retries = -retries\n        self.timeout = timeout\n\n\n    def _removeDeferred(self, result):\n        del self.result\n        return result\n\n\n    def clientConnectionFailed(self, connector, err):\n        self._processConnectionError(connector, err)\n\n\n    def clientConnectionLost(self, connector, err):\n        self._processConnectionError(connector, err)\n\n\n    def _processConnectionError(self, connector, err):\n        self.currentProtocol = None\n        if (self.retries < 0) and (not self.sendFinished):\n            log.msg(\"SMTP Client retrying server. Retry: %s\" % -self.retries)\n\n            # Rewind the file in case part of it was read while attempting to\n            # send the message.\n            self.file.seek(0, 0)\n            connector.connect()\n            self.retries += 1\n        elif not self.sendFinished:\n            # If we were unable to communicate with the SMTP server a ConnectionDone will be\n            # returned. We want a more clear error message for debugging\n            if err.check(error.ConnectionDone):\n                err.value = SMTPConnectError(-1, \"Unable to connect to server.\")\n            self.result.errback(err.value)\n\n\n    def buildProtocol(self, addr):\n        p = self.protocol(self.domain, self.nEmails*2+2)\n        p.factory = self\n        p.timeout = self.timeout\n        self.currentProtocol = p\n        self.result.addBoth(self._removeProtocol)\n        return p\n\n\n    def _removeProtocol(self, result):\n        \"\"\"\n        Remove the protocol created in C{buildProtocol}.\n\n        @param result: The result/error passed to the callback/errback of\n            L{defer.Deferred}.\n\n        @return: The C{result} untouched.\n        \"\"\"\n        if self.currentProtocol:\n            self.currentProtocol = None\n        return result\n\n\n\nclass LOGINCredentials(_lcredentials):\n    \"\"\"\n    L{LOGINCredentials} generates challenges for I{LOGIN} authentication.\n\n    For interoperability with Outlook, the challenge generated does not exactly\n    match the one defined in the\n    U{draft specification<http://sepp.oetiker.ch/sasl-2.1.19-ds/draft-murchison-sasl-login-00.txt>}.\n    \"\"\"\n\n    def __init__(self):\n        _lcredentials.__init__(self)\n        self.challenges = [b'Password:', b'Username:']\n\n\n\n@implementer(IClientAuthentication)\nclass PLAINAuthenticator:\n    def __init__(self, user):\n        self.user = user\n\n\n    def getName(self):\n        return b\"PLAIN\"\n\n\n    def challengeResponse(self, secret, chal=1):\n        if chal == 1:\n            return self.user + b'\\0' + self.user + b'\\0' + secret\n        else:\n            return b'\\0' + self.user + b'\\0' + secret\n\n\n\nclass ESMTPSender(SenderMixin, ESMTPClient):\n\n    requireAuthentication = True\n    requireTransportSecurity = True\n\n    def __init__(self, username, secret, contextFactory=None, *args, **kw):\n        self.heloFallback = 0\n        self.username = username\n\n        if contextFactory is None:\n            contextFactory = self._getContextFactory()\n\n        ESMTPClient.__init__(self, secret, contextFactory, *args, **kw)\n\n        self._registerAuthenticators()\n\n\n    def _registerAuthenticators(self):\n        # Register Authenticator in order from most secure to least secure\n        self.registerAuthenticator(CramMD5ClientAuthenticator(self.username))\n        self.registerAuthenticator(LOGINAuthenticator(self.username))\n        self.registerAuthenticator(PLAINAuthenticator(self.username))\n\n\n    def _getContextFactory(self):\n        if self.context is not None:\n            return self.context\n        try:\n            from twisted.internet import ssl\n        except ImportError:\n            return None\n        else:\n            try:\n                context = ssl.ClientContextFactory()\n                context.method = ssl.SSL.TLSv1_METHOD\n                return context\n            except AttributeError:\n                return None\n\n\n\nclass ESMTPSenderFactory(SMTPSenderFactory):\n    \"\"\"\n    Utility factory for sending emails easily.\n\n    @type currentProtocol: L{ESMTPSender}\n    @ivar currentProtocol: The current running protocol as made by\n        L{buildProtocol}.\n    \"\"\"\n    protocol = ESMTPSender\n\n    def __init__(self, username, password, fromEmail, toEmail, file,\n                 deferred, retries=5, timeout=None,\n                 contextFactory=None, heloFallback=False,\n                 requireAuthentication=True,\n                 requireTransportSecurity=True):\n\n        SMTPSenderFactory.__init__(self, fromEmail, toEmail, file, deferred, retries, timeout)\n        self.username = username\n        self.password = password\n        self._contextFactory = contextFactory\n        self._heloFallback = heloFallback\n        self._requireAuthentication = requireAuthentication\n        self._requireTransportSecurity = requireTransportSecurity\n\n\n    def buildProtocol(self, addr):\n        \"\"\"\n        Build an L{ESMTPSender} protocol configured with C{heloFallback},\n        C{requireAuthentication}, and C{requireTransportSecurity} as specified\n        in L{__init__}.\n\n        This sets L{currentProtocol} on the factory, as well as returning it.\n\n        @rtype: L{ESMTPSender}\n        \"\"\"\n        p = self.protocol(self.username, self.password, self._contextFactory,\n                          self.domain, self.nEmails*2+2)\n        p.heloFallback = self._heloFallback\n        p.requireAuthentication = self._requireAuthentication\n        p.requireTransportSecurity = self._requireTransportSecurity\n        p.factory = self\n        p.timeout = self.timeout\n        self.currentProtocol = p\n        self.result.addBoth(self._removeProtocol)\n        return p\n\n\n\ndef sendmail(smtphost, from_addr, to_addrs, msg, senderDomainName=None, port=25,\n             reactor=reactor, username=None, password=None,\n             requireAuthentication=False, requireTransportSecurity=False):\n    \"\"\"\n    Send an email.\n\n    This interface is intended to be a replacement for L{smtplib.SMTP.sendmail}\n    and related methods. To maintain backwards compatibility, it will fall back\n    to plain SMTP, if ESMTP support is not available. If ESMTP support is\n    available, it will attempt to provide encryption via STARTTLS and\n    authentication if a secret is provided.\n\n    @param smtphost: The host the message should be sent to.\n    @type smtphost: L{bytes}\n\n    @param from_addr: The (envelope) address sending this mail.\n    @type from_addr: L{bytes}\n\n    @param to_addrs: A list of addresses to send this mail to.  A string will\n        be treated as a list of one address.\n    @type to_addr: L{list} of L{bytes} or L{bytes}\n\n    @param msg: The message, including headers, either as a file or a string.\n        File-like objects need to support read() and close(). Lines must be\n        delimited by '\\\\n'. If you pass something that doesn't look like a file,\n        we try to convert it to a string (so you should be able to pass an\n        L{email.message} directly, but doing the conversion with\n        L{email.generator} manually will give you more control over the process).\n\n    @param senderDomainName: Name by which to identify. If None, try to pick\n        something sane (but this depends on external configuration and may not\n        succeed).\n    @type senderDomainName: L{bytes}\n\n    @param port: Remote port to which to connect.\n    @type port: L{int}\n\n    @param username: The username to use, if wanting to authenticate.\n    @type username: L{bytes} or L{unicode}\n\n    @param password: The secret to use, if wanting to authenticate. If you do\n        not specify this, SMTP authentication will not occur.\n    @type password: L{bytes} or L{unicode}\n\n    @param requireTransportSecurity: Whether or not STARTTLS is required.\n    @type requireTransportSecurity: L{bool}\n\n    @param requireAuthentication: Whether or not authentication is required.\n    @type requireAuthentication: L{bool}\n\n    @param reactor: The L{reactor} used to make the TCP connection.\n\n    @rtype: L{Deferred}\n    @returns: A cancellable L{Deferred}, its callback will be called if a\n        message is sent to ANY address, the errback if no message is sent. When\n        the C{cancel} method is called, it will stop retrying and disconnect\n        the connection immediately.\n\n        The callback will be called with a tuple (numOk, addresses) where numOk\n        is the number of successful recipient addresses and addresses is a list\n        of tuples (address, code, resp) giving the response to the RCPT command\n        for each address.\n    \"\"\"\n    if not hasattr(msg, 'read'):\n        # It's not a file\n        msg = BytesIO(bytes(msg))\n\n\n    def cancel(d):\n        \"\"\"\n        Cancel the L{twisted.mail.smtp.sendmail} call, tell the factory not to\n        retry and disconnect the connection.\n\n        @param d: The L{defer.Deferred} to be cancelled.\n        \"\"\"\n        factory.sendFinished = True\n        if factory.currentProtocol:\n            factory.currentProtocol.transport.abortConnection()\n        else:\n            # Connection hasn't been made yet\n            connector.disconnect()\n\n    d = defer.Deferred(cancel)\n\n    if isinstance(username, unicode):\n        username = username.encode(\"utf-8\")\n    if isinstance(password, unicode):\n        password = password.encode(\"utf-8\")\n\n    factory = ESMTPSenderFactory(username, password, from_addr, to_addrs, msg,\n        d, heloFallback=True, requireAuthentication=requireAuthentication,\n        requireTransportSecurity=requireTransportSecurity)\n\n    if senderDomainName is not None:\n        factory.domain = networkString(senderDomainName)\n\n    connector = reactor.connectTCP(smtphost, port, factory)\n\n    return d\n\n\n\nimport codecs\ndef xtext_encode(s, errors=None):\n    r = []\n    for ch in iterbytes(s):\n        o = ord(ch)\n        if ch == '+' or ch == '=' or o < 33 or o > 126:\n            r.append(networkString('+%02X' % (o,)))\n        else:\n            r.append(_bytesChr(o))\n    return (b''.join(r), len(s))\n\n\n\ndef xtext_decode(s, errors=None):\n    \"\"\"\n    Decode the xtext-encoded string C{s}.\n\n    @param s: String to decode.\n    @param errors: codec error handling scheme.\n    @return: The decoded string.\n    \"\"\"\n    r = []\n    i = 0\n    while i < len(s):\n        if s[i:i+1] == b'+':\n            try:\n                r.append(chr(int(bytes(s[i + 1:i + 3]), 16)))\n            except ValueError:\n                r.append(ord(s[i:i + 3]))\n            i += 3\n        else:\n            r.append(bytes(s[i:i+1]).decode('ascii'))\n            i += 1\n    return (''.join(r), len(s))\n\n\n\nclass xtextStreamReader(codecs.StreamReader):\n    def decode(self, s, errors='strict'):\n        return xtext_decode(s)\n\n\n\nclass xtextStreamWriter(codecs.StreamWriter):\n    def decode(self, s, errors='strict'):\n        return xtext_encode(s)\n\n\n\ndef xtext_codec(name):\n    if name == 'xtext':\n        return (xtext_encode, xtext_decode, xtextStreamReader, xtextStreamWriter)\ncodecs.register(xtext_codec)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/test/__init__.py",
    "content": "\"Tests for twistd.mail\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/test/pop3testserver.py",
    "content": "#!/usr/bin/env python\n# -*- test-case-name: twisted.mail.test.test_pop3client -*-\n\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\nfrom __future__ import print_function\n\nfrom twisted.internet.protocol import Factory\nfrom twisted.protocols import basic\nfrom twisted.internet import reactor\nimport sys\n\nUSER = \"test\"\nPASS = \"twisted\"\n\nPORT = 1100\n\nSSL_SUPPORT = True\nUIDL_SUPPORT = True\nINVALID_SERVER_RESPONSE = False\nINVALID_CAPABILITY_RESPONSE = False\nINVALID_LOGIN_RESPONSE = False\nDENY_CONNECTION = False\nDROP_CONNECTION = False\nBAD_TLS_RESPONSE = False\nTIMEOUT_RESPONSE = False\nTIMEOUT_DEFERRED = False\nSLOW_GREETING = False\n\n\"\"\"Commands\"\"\"\nCONNECTION_MADE = b\"+OK POP3 localhost v2003.83 server ready\"\n\nCAPABILITIES = [\nb\"TOP\",\nb\"LOGIN-DELAY 180\",\nb\"USER\",\nb\"SASL LOGIN\"\n]\n\nCAPABILITIES_SSL = b\"STLS\"\nCAPABILITIES_UIDL = b\"UIDL\"\n\n\nINVALID_RESPONSE = b\"-ERR Unknown request\"\nVALID_RESPONSE = b\"+OK Command Completed\"\nAUTH_DECLINED = b\"-ERR LOGIN failed\"\nAUTH_ACCEPTED = b\"+OK Mailbox open, 0 messages\"\nTLS_ERROR = b\"-ERR server side error start TLS handshake\"\nLOGOUT_COMPLETE = b\"+OK quit completed\"\nNOT_LOGGED_IN = b\"-ERR Unknown AUHORIZATION state command\"\nSTAT = b\"+OK 0 0\"\nUIDL = b\"+OK Unique-ID listing follows\\r\\n.\"\nLIST = b\"+OK Mailbox scan listing follows\\r\\n.\"\nCAP_START = b\"+OK Capability list follows:\"\n\n\nclass POP3TestServer(basic.LineReceiver):\n    def __init__(self, contextFactory = None):\n        self.loggedIn = False\n        self.caps = None\n        self.tmpUser = None\n        self.ctx = contextFactory\n\n\n    def sendSTATResp(self, req):\n        self.sendLine(STAT)\n\n\n    def sendUIDLResp(self, req):\n        self.sendLine(UIDL)\n\n\n    def sendLISTResp(self, req):\n        self.sendLine(LIST)\n\n\n    def sendCapabilities(self):\n        if self.caps is None:\n            self.caps = [CAP_START]\n\n        if UIDL_SUPPORT:\n            self.caps.append(CAPABILITIES_UIDL)\n\n        if SSL_SUPPORT:\n            self.caps.append(CAPABILITIES_SSL)\n\n        for cap in CAPABILITIES:\n            self.caps.append(cap)\n        resp = b'\\r\\n'.join(self.caps)\n        resp += b'\\r\\n.'\n\n        self.sendLine(resp)\n\n\n    def connectionMade(self):\n        if DENY_CONNECTION:\n            self.disconnect()\n            return\n\n        if SLOW_GREETING:\n            reactor.callLater(20, self.sendGreeting)\n\n        else:\n            self.sendGreeting()\n\n\n    def sendGreeting(self):\n        self.sendLine(CONNECTION_MADE)\n\n\n    def lineReceived(self, line):\n        \"\"\"Error Conditions\"\"\"\n\n        uline = line.upper()\n        find = lambda s: uline.find(s) != -1\n\n        if TIMEOUT_RESPONSE:\n            # Do not respond to clients request\n            return\n\n        if DROP_CONNECTION:\n            self.disconnect()\n            return\n\n        elif find(b\"CAPA\"):\n            if INVALID_CAPABILITY_RESPONSE:\n                self.sendLine(INVALID_RESPONSE)\n            else:\n                self.sendCapabilities()\n\n        elif find(b\"STLS\") and SSL_SUPPORT:\n            self.startTLS()\n\n        elif find(b\"USER\"):\n            if INVALID_LOGIN_RESPONSE:\n                self.sendLine(INVALID_RESPONSE)\n                return\n\n            resp = None\n            try:\n                self.tmpUser = line.split(\" \")[1]\n                resp = VALID_RESPONSE\n            except:\n                resp = AUTH_DECLINED\n\n            self.sendLine(resp)\n\n        elif find(b\"PASS\"):\n            resp = None\n            try:\n                pwd = line.split(\" \")[1]\n\n                if self.tmpUser is None or pwd is None:\n                    resp = AUTH_DECLINED\n                elif self.tmpUser == USER and pwd == PASS:\n                    resp = AUTH_ACCEPTED\n                    self.loggedIn = True\n                else:\n                    resp = AUTH_DECLINED\n            except:\n                resp = AUTH_DECLINED\n\n            self.sendLine(resp)\n\n        elif find(b\"QUIT\"):\n            self.loggedIn = False\n            self.sendLine(LOGOUT_COMPLETE)\n            self.disconnect()\n\n        elif INVALID_SERVER_RESPONSE:\n            self.sendLine(INVALID_RESPONSE)\n\n        elif not self.loggedIn:\n            self.sendLine(NOT_LOGGED_IN)\n\n        elif find(b\"NOOP\"):\n            self.sendLine(VALID_RESPONSE)\n\n        elif find(b\"STAT\"):\n            if TIMEOUT_DEFERRED:\n                return\n            self.sendLine(STAT)\n\n        elif find(b\"LIST\"):\n            if TIMEOUT_DEFERRED:\n                return\n            self.sendLine(LIST)\n\n        elif find(b\"UIDL\"):\n            if TIMEOUT_DEFERRED:\n                return\n            elif not UIDL_SUPPORT:\n                self.sendLine(INVALID_RESPONSE)\n                return\n\n            self.sendLine(UIDL)\n\n\n    def startTLS(self):\n        if self.ctx is None:\n            self.getContext()\n\n        if SSL_SUPPORT and self.ctx is not None:\n            self.sendLine(b'+OK Begin TLS negotiation now')\n            self.transport.startTLS(self.ctx)\n        else:\n            self.sendLine(b'-ERR TLS not available')\n\n\n    def disconnect(self):\n        self.transport.loseConnection()\n\n\n    def getContext(self):\n        try:\n            from twisted.internet import ssl\n        except ImportError:\n           self.ctx = None\n        else:\n            self.ctx = ssl.ClientContextFactory()\n            self.ctx.method = ssl.SSL.TLSv1_METHOD\n\n\nusage = \"\"\"popServer.py [arg] (default is Standard POP Server with no messages)\nno_ssl  - Start with no SSL support\nno_uidl - Start with no UIDL support\nbad_resp - Send a non-RFC compliant response to the Client\nbad_cap_resp - send a non-RFC compliant response when the Client sends a 'CAPABILITY' request\nbad_login_resp - send a non-RFC compliant response when the Client sends a 'LOGIN' request\ndeny - Deny the connection\ndrop - Drop the connection after sending the greeting\nbad_tls - Send a bad response to a STARTTLS\ntimeout - Do not return a response to a Client request\nto_deferred - Do not return a response on a 'Select' request. This\n              will test Deferred callback handling\nslow - Wait 20 seconds after the connection is made to return a Server Greeting\n\"\"\"\n\ndef printMessage(msg):\n    print(\"Server Starting in %s mode\" % msg)\n\n\n\ndef processArg(arg):\n\n    if arg.lower() == 'no_ssl':\n        global SSL_SUPPORT\n        SSL_SUPPORT = False\n        printMessage(\"NON-SSL\")\n\n    elif arg.lower() == 'no_uidl':\n        global UIDL_SUPPORT\n        UIDL_SUPPORT = False\n        printMessage(\"NON-UIDL\")\n\n    elif arg.lower() == 'bad_resp':\n        global INVALID_SERVER_RESPONSE\n        INVALID_SERVER_RESPONSE = True\n        printMessage(\"Invalid Server Response\")\n\n    elif arg.lower() == 'bad_cap_resp':\n        global INVALID_CAPABILITY_RESPONSE\n        INVALID_CAPABILITY_RESPONSE = True\n        printMessage(\"Invalid Capability Response\")\n\n    elif arg.lower() == 'bad_login_resp':\n        global INVALID_LOGIN_RESPONSE\n        INVALID_LOGIN_RESPONSE = True\n        printMessage(\"Invalid Capability Response\")\n\n    elif arg.lower() == 'deny':\n        global DENY_CONNECTION\n        DENY_CONNECTION = True\n        printMessage(\"Deny Connection\")\n\n    elif arg.lower() == 'drop':\n        global DROP_CONNECTION\n        DROP_CONNECTION = True\n        printMessage(\"Drop Connection\")\n\n    elif arg.lower() == 'bad_tls':\n        global BAD_TLS_RESPONSE\n        BAD_TLS_RESPONSE = True\n        printMessage(\"Bad TLS Response\")\n\n    elif arg.lower() == 'timeout':\n        global TIMEOUT_RESPONSE\n        TIMEOUT_RESPONSE = True\n        printMessage(\"Timeout Response\")\n\n    elif arg.lower() == 'to_deferred':\n        global TIMEOUT_DEFERRED\n        TIMEOUT_DEFERRED = True\n        printMessage(\"Timeout Deferred Response\")\n\n    elif arg.lower() == 'slow':\n        global SLOW_GREETING\n        SLOW_GREETING = True\n        printMessage(\"Slow Greeting\")\n\n    elif arg.lower() == '--help':\n        print(usage)\n        sys.exit()\n\n    else:\n        print(usage)\n        sys.exit()\n\ndef main():\n\n    if len(sys.argv) < 2:\n        printMessage(\"POP3 with no messages\")\n    else:\n        args = sys.argv[1:]\n\n        for arg in args:\n            processArg(arg)\n\n    f = Factory()\n    f.protocol = POP3TestServer\n    reactor.listenTCP(PORT, f)\n    reactor.run()\n\nif __name__ == '__main__':\n    main()\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/test/test_imap.py",
    "content": "# -*- test-case-name: twisted.mail.test.test_imap -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\n\"\"\"\nTest case for twisted.mail.imap4\n\"\"\"\n\nimport base64\nimport codecs\nimport functools\nimport locale\nimport os\nfrom io import BytesIO\nimport uuid\n\nfrom itertools import chain\nfrom collections import OrderedDict\n\nfrom zope.interface import implementer\nfrom zope.interface.verify import verifyClass, verifyObject\n\nfrom twisted.internet import defer\nfrom twisted.internet import error\nfrom twisted.internet import interfaces\nfrom twisted.internet import reactor\nfrom twisted.internet.task import Clock\nfrom twisted.mail import imap4\nfrom twisted.mail.interfaces import (IChallengeResponse,\n                                     IClientAuthentication,\n                                     ICloseableMailboxIMAP)\nfrom twisted.mail.imap4 import MessageSet\nfrom twisted.protocols import loopback\nfrom twisted.python import failure\nfrom twisted.python import util, log\nfrom twisted.python.compat import (intToBytes, range, nativeString,\n                                   networkString, iterbytes, _PY3)\nfrom twisted.trial import unittest\n\nfrom twisted.cred.portal import Portal, IRealm\nfrom twisted.cred.checkers import InMemoryUsernamePasswordDatabaseDontUse\nfrom twisted.cred.error import UnauthorizedLogin\nfrom twisted.cred.credentials import (\n    IUsernameHashedPassword, IUsernamePassword, CramMD5Credentials)\n\nfrom twisted.test.proto_helpers import StringTransport, StringTransportWithDisconnection\n\ntry:\n    from twisted.test.ssl_helpers import ClientTLSContext, ServerTLSContext\nexcept ImportError:\n    ClientTLSContext = ServerTLSContext = None\n\n\n\ndef strip(f):\n    return lambda result, f=f: f()\n\n\n\nclass IMAP4UTF7Tests(unittest.TestCase):\n    tests = [\n        [u'Hello world', b'Hello world'],\n        [u'Hello & world', b'Hello &- world'],\n        [u'Hello\\xffworld', b'Hello&AP8-world'],\n        [u'\\xff\\xfe\\xfd\\xfc', b'&AP8A,gD9APw-'],\n        [u'~peter/mail/\\u65e5\\u672c\\u8a9e/\\u53f0\\u5317',\n         b'~peter/mail/&ZeVnLIqe-/&U,BTFw-'], # example from RFC 2060\n    ]\n\n    def test_encodeWithErrors(self):\n        \"\"\"\n        Specifying an error policy to C{unicode.encode} with the\n        I{imap4-utf-7} codec should produce the same result as not\n        specifying the error policy.\n        \"\"\"\n        text = u'Hello world'\n        self.assertEqual(\n            text.encode('imap4-utf-7', 'strict'),\n            text.encode('imap4-utf-7'))\n\n\n    def test_decodeWithErrors(self):\n        \"\"\"\n        Similar to L{test_encodeWithErrors}, but for C{bytes.decode}.\n        \"\"\"\n        bytes = b'Hello world'\n        self.assertEqual(\n            bytes.decode('imap4-utf-7', 'strict'),\n            bytes.decode('imap4-utf-7'))\n\n\n    def test_encodeAmpersand(self):\n        \"\"\"\n        Unicode strings that contain an ampersand (C{&}) can be\n        encoded to bytes with the I{imap4-utf-7} codec.\n        \"\"\"\n        text = u\"&Hello&\\N{VULGAR FRACTION ONE HALF}&\"\n        self.assertEqual(\n            text.encode(\"imap4-utf-7\"),\n            b'&-Hello&-&AL0-&-',\n        )\n\n\n    def test_decodeWithoutFinalASCIIShift(self):\n        \"\"\"\n        An I{imap4-utf-7} encoded string that does not shift back to\n        ASCII (i.e., it lacks a final C{-}) can be decoded.\n        \"\"\"\n        self.assertEqual(\n            b'&AL0'.decode('imap4-utf-7'),\n            u\"\\N{VULGAR FRACTION ONE HALF}\",\n        )\n\n\n    def test_getreader(self):\n        \"\"\"\n        C{codecs.getreader('imap4-utf-7')} returns the I{imap4-utf-7} stream\n        reader class.\n        \"\"\"\n        reader = codecs.getreader('imap4-utf-7')(BytesIO(b'Hello&AP8-world'))\n        self.assertEqual(reader.read(), u'Hello\\xffworld')\n\n\n    def test_getwriter(self):\n        \"\"\"\n        C{codecs.getwriter('imap4-utf-7')} returns the I{imap4-utf-7} stream\n        writer class.\n        \"\"\"\n        output = BytesIO()\n        writer = codecs.getwriter('imap4-utf-7')(output)\n        writer.write(u'Hello\\xffworld')\n        self.assertEqual(output.getvalue(), b'Hello&AP8-world')\n\n\n    def test_encode(self):\n        \"\"\"\n        The I{imap4-utf-7} can be used to encode a unicode string into a byte\n        string according to the IMAP4 modified UTF-7 encoding rules.\n        \"\"\"\n        for (input, output) in self.tests:\n            self.assertEqual(input.encode('imap4-utf-7'), output)\n\n\n    def test_decode(self):\n        \"\"\"\n        The I{imap4-utf-7} can be used to decode a byte string into a unicode\n        string according to the IMAP4 modified UTF-7 encoding rules.\n        \"\"\"\n        for (input, output) in self.tests:\n            self.assertEqual(input, output.decode('imap4-utf-7'))\n\n\n    def test_printableSingletons(self):\n        \"\"\"\n        The IMAP4 modified UTF-7 implementation encodes all printable\n        characters which are in ASCII using the corresponding ASCII byte.\n        \"\"\"\n        # All printables represent themselves\n        for o in chain(range(0x20, 0x26), range(0x27, 0x7f)):\n            charbyte = chr(o).encode()\n            self.assertEqual(charbyte, chr(o).encode('imap4-utf-7'))\n            self.assertEqual(chr(o), charbyte.decode('imap4-utf-7'))\n        self.assertEqual(u'&'.encode('imap4-utf-7'), b'&-')\n        self.assertEqual(b'&-'.decode('imap4-utf-7'), u'&')\n\n\n\nclass BufferingConsumer:\n    def __init__(self):\n        self.buffer = []\n\n\n    def write(self, bytes):\n        self.buffer.append(bytes)\n        if self.consumer:\n            self.consumer.resumeProducing()\n\n\n    def registerProducer(self, consumer, streaming):\n        self.consumer = consumer\n        self.consumer.resumeProducing()\n\n\n    def unregisterProducer(self):\n        self.consumer = None\n\n\n\nclass MessageProducerTests(unittest.SynchronousTestCase):\n\n    def testSinglePart(self):\n        body = b'This is body text.  Rar.'\n        headers = OrderedDict()\n        headers['from'] = 'sender@host'\n        headers['to'] = 'recipient@domain'\n        headers['subject'] = 'booga booga boo'\n        headers['content-type'] = 'text/plain'\n\n        msg = FakeyMessage(headers, (), None, body, 123, None )\n\n        c = BufferingConsumer()\n        p = imap4.MessageProducer(msg)\n        d = p.beginProducing(c)\n\n        def cbProduced(result):\n            self.assertIdentical(result, p)\n            self.assertEqual(\n                b''.join(c.buffer),\n\n                b'{119}\\r\\n'\n                b'From: sender@host\\r\\n'\n                b'To: recipient@domain\\r\\n'\n                b'Subject: booga booga boo\\r\\n'\n                b'Content-Type: text/plain\\r\\n'\n                b'\\r\\n'\n                + body)\n        return d.addCallback(cbProduced)\n\n\n    def testSingleMultiPart(self):\n        outerBody = b''\n        innerBody = b'Contained body message text.  Squarge.'\n        headers = OrderedDict()\n        headers['from'] = 'sender@host'\n        headers['to'] = 'recipient@domain'\n        headers['subject'] = 'booga booga boo'\n        headers['content-type'] = 'multipart/alternative; boundary=\"xyz\"'\n\n        innerHeaders = OrderedDict()\n        innerHeaders['subject'] = 'this is subject text'\n        innerHeaders['content-type'] = 'text/plain'\n        msg = FakeyMessage(headers, (), None, outerBody, 123,\n                           [FakeyMessage(innerHeaders, (), None, innerBody,\n                                         None, None)],\n                           )\n\n        c = BufferingConsumer()\n        p = imap4.MessageProducer(msg)\n        d = p.beginProducing(c)\n\n        def cbProduced(result):\n            self.failUnlessIdentical(result, p)\n\n            self.assertEqual(\n                b''.join(c.buffer),\n\n                b'{239}\\r\\n'\n                b'From: sender@host\\r\\n'\n                b'To: recipient@domain\\r\\n'\n                b'Subject: booga booga boo\\r\\n'\n                b'Content-Type: multipart/alternative; boundary=\"xyz\"\\r\\n'\n                b'\\r\\n'\n                b'\\r\\n'\n                b'--xyz\\r\\n'\n                b'Subject: this is subject text\\r\\n'\n                b'Content-Type: text/plain\\r\\n'\n                b'\\r\\n'\n                + innerBody\n                + b'\\r\\n--xyz--\\r\\n')\n\n        return d.addCallback(cbProduced)\n\n\n    def testMultipleMultiPart(self):\n        outerBody = b''\n        innerBody1 = b'Contained body message text.  Squarge.'\n        innerBody2 = b'Secondary <i>message</i> text of squarge body.'\n        headers = OrderedDict()\n        headers['from'] = 'sender@host'\n        headers['to'] = 'recipient@domain'\n        headers['subject'] = 'booga booga boo'\n        headers['content-type'] = 'multipart/alternative; boundary=\"xyz\"'\n        innerHeaders = OrderedDict()\n        innerHeaders['subject'] = 'this is subject text'\n        innerHeaders['content-type'] = 'text/plain'\n        innerHeaders2 = OrderedDict()\n        innerHeaders2['subject'] = '<b>this is subject</b>'\n        innerHeaders2['content-type'] = 'text/html'\n        msg = FakeyMessage(headers, (), None, outerBody, 123, [\n            FakeyMessage(innerHeaders, (), None, innerBody1, None, None),\n            FakeyMessage(innerHeaders2, (), None, innerBody2, None, None)\n            ],\n        )\n\n        c = BufferingConsumer()\n        p = imap4.MessageProducer(msg)\n        d = p.beginProducing(c)\n\n\n        def cbProduced(result):\n            self.failUnlessIdentical(result, p)\n\n            self.assertEqual(\n                b''.join(c.buffer),\n\n                b'{354}\\r\\n'\n                b'From: sender@host\\r\\n'\n                b'To: recipient@domain\\r\\n'\n                b'Subject: booga booga boo\\r\\n'\n                b'Content-Type: multipart/alternative; boundary=\"xyz\"\\r\\n'\n                b'\\r\\n'\n                b'\\r\\n'\n                b'--xyz\\r\\n'\n                b'Subject: this is subject text\\r\\n'\n                b'Content-Type: text/plain\\r\\n'\n                b'\\r\\n'\n                + innerBody1\n                + b'\\r\\n--xyz\\r\\n'\n                b'Subject: <b>this is subject</b>\\r\\n'\n                b'Content-Type: text/html\\r\\n'\n                b'\\r\\n'\n                + innerBody2\n                + b'\\r\\n--xyz--\\r\\n')\n        return d.addCallback(cbProduced)\n\n\n    def test_multiPartNoBoundary(self):\n        \"\"\"\n        A boundary is generated if none is provided.\n        \"\"\"\n        outerBody = b''\n        innerBody = b'Contained body message text.  Squarge.'\n        headers = OrderedDict()\n        headers['from'] = 'sender@host'\n        headers['to'] = 'recipient@domain'\n        headers['subject'] = 'booga booga boo'\n        headers['content-type'] = 'multipart/alternative'\n\n        innerHeaders = OrderedDict()\n        innerHeaders['subject'] = 'this is subject text'\n        innerHeaders['content-type'] = 'text/plain'\n        msg = FakeyMessage(headers, (), None, outerBody, 123,\n                           [FakeyMessage(innerHeaders, (), None, innerBody,\n                                         None, None)],\n                           )\n\n        c = BufferingConsumer()\n        p = imap4.MessageProducer(msg)\n        p._uuid4 = lambda: uuid.UUID('aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa')\n\n        d = p.beginProducing(c)\n\n        def cbProduced(result):\n            self.failUnlessIdentical(result, p)\n            self.assertEqual(\n                b''.join(c.buffer),\n\n                b'{341}\\r\\n'\n                b'From: sender@host\\r\\n'\n                b'To: recipient@domain\\r\\n'\n                b'Subject: booga booga boo\\r\\n'\n                b'Content-Type: multipart/alternative; boundary='\n                b'\"----=aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\"'\n                b'\\r\\n'\n                b'\\r\\n'\n                b'\\r\\n'\n                b'------=aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa\\r\\n'\n                b'Subject: this is subject text\\r\\n'\n                b'Content-Type: text/plain\\r\\n'\n                b'\\r\\n'\n                + innerBody\n                + b'\\r\\n------=aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa--\\r\\n')\n\n        return d.addCallback(cbProduced)\n\n\n    def test_multiPartNoQuotes(self):\n        \"\"\"\n        A boundary without does not have them added.\n        \"\"\"\n        outerBody = b''\n        innerBody = b'Contained body message text.  Squarge.'\n        headers = OrderedDict()\n        headers['from'] = 'sender@host'\n        headers['to'] = 'recipient@domain'\n        headers['subject'] = 'booga booga boo'\n        headers['content-type'] = 'multipart/alternative; boundary=xyz'\n\n        innerHeaders = OrderedDict()\n        innerHeaders['subject'] = 'this is subject text'\n        innerHeaders['content-type'] = 'text/plain'\n        msg = FakeyMessage(headers, (), None, outerBody, 123,\n                           [FakeyMessage(innerHeaders, (), None, innerBody,\n                                         None, None)],\n                           )\n\n        c = BufferingConsumer()\n        p = imap4.MessageProducer(msg)\n        d = p.beginProducing(c)\n\n        def cbProduced(result):\n            self.failUnlessIdentical(result, p)\n            self.assertEqual(\n                b''.join(c.buffer),\n\n                b'{237}\\r\\n'\n                b'From: sender@host\\r\\n'\n                b'To: recipient@domain\\r\\n'\n                b'Subject: booga booga boo\\r\\n'\n                b'Content-Type: multipart/alternative; boundary='\n                b'xyz'\n                b'\\r\\n'\n                b'\\r\\n'\n                b'\\r\\n'\n                b'--xyz\\r\\n'\n                b'Subject: this is subject text\\r\\n'\n                b'Content-Type: text/plain\\r\\n'\n                b'\\r\\n'\n                + innerBody\n                + b'\\r\\n--xyz--\\r\\n')\n\n        return d.addCallback(cbProduced)\n\n\n\nclass MessageSetTests(unittest.SynchronousTestCase):\n    \"\"\"\n    Tests for L{MessageSet}.\n    \"\"\"\n\n    def test_equalityIterationAndAddition(self):\n        \"\"\"\n        Test the following properties of L{MessageSet} addition and\n        equality:\n\n            1. Two empty L{MessageSet}s are equal to each other;\n\n            2. A L{MessageSet} is not equal to any other object;\n\n            2. Adding a L{MessageSet} and another L{MessageSet} or an\n               L{int} representing a single message or a sequence of\n               L{int}s representing a sequence of message numbers\n               produces a new L{MessageSet} that:\n\n            3. Has a length equal to the number of messages within\n               each sequence of message numbers;\n\n            4. Yields each message number in ascending order when\n               iterated over;\n\n            6. L{MessageSet.add} with a single message or a start and\n               end message satisfies 3 and 4 above.\n        \"\"\"\n        m1 = MessageSet()\n        m2 = MessageSet()\n\n        self.assertEqual(m1, m2)\n        self.assertNotEqual(m1, ())\n\n        m1 = m1 + 1\n        self.assertEqual(len(m1), 1)\n        self.assertEqual(list(m1), [1])\n\n        m1 = m1 + (1, 3)\n        self.assertEqual(len(m1), 3)\n        self.assertEqual(list(m1), [1, 2, 3])\n\n        m2 = m2 + (1, 3)\n        self.assertEqual(m1, m2)\n        self.assertEqual(list(m1 + m2), [1, 2, 3])\n\n        m1.add(5)\n        self.assertEqual(len(m1), 4)\n        self.assertEqual(list(m1), [1, 2, 3, 5])\n\n        self.assertNotEqual(m1, m2)\n\n        m1.add(6, 8)\n        self.assertEqual(len(m1), 7)\n        self.assertEqual(list(m1), [1, 2, 3, 5, 6, 7, 8])\n\n\n    def test_lengthWithWildcardRange(self):\n        \"\"\"\n        A L{MessageSet} that has a range that ends with L{None} raises\n        a L{TypeError} when its length is requested.\n        \"\"\"\n        self.assertRaises(TypeError, len, MessageSet(1, None))\n\n\n    def test_reprSanity(self):\n        \"\"\"\n        L{MessageSet.__repr__} does not raise an exception\n        \"\"\"\n        repr(MessageSet(1, 2))\n\n\n    def test_stringRepresentationWithWildcards(self):\n        \"\"\"\n        In a L{MessageSet}, in the presence of wildcards, if the\n        highest message id is known, the wildcard should get replaced\n        by that high value.\n        \"\"\"\n        inputs = [\n            imap4.parseIdList(b'*'),\n            imap4.parseIdList(b'1:*'),\n            imap4.parseIdList(b'3:*', 6),\n            imap4.parseIdList(b'*:2', 6),\n        ]\n\n        outputs = [\n            \"*\",\n            \"1:*\",\n            \"3:6\",\n            \"2:6\",\n        ]\n\n        for i, o in zip(inputs, outputs):\n            self.assertEqual(str(i), o)\n\n\n    def test_stringRepresentationWithInversion(self):\n        \"\"\"\n        In a L{MessageSet}, inverting the high and low numbers in a\n        range doesn't affect the meaning of the range.  For example,\n        3:2 displays just like 2:3, because according to the RFC they\n        have the same meaning.\n        \"\"\"\n        inputs = [\n            imap4.parseIdList(b'2:3'),\n            imap4.parseIdList(b'3:2'),\n        ]\n\n        outputs = [\n            \"2:3\",\n            \"2:3\",\n        ]\n\n        for i, o in zip(inputs, outputs):\n            self.assertEqual(str(i), o)\n\n\n    def test_createWithSingleMessageNumber(self):\n        \"\"\"\n        Creating a L{MessageSet} with a single message number adds\n        only that message to the L{MessageSet}; its serialized form\n        includes only that message number, its length is one, and it\n        yields only that message number.\n        \"\"\"\n        m = MessageSet(1)\n        self.assertEqual(str(m), \"1\")\n        self.assertEqual(len(m), 1)\n        self.assertEqual(list(m), [1])\n\n\n    def test_createWithSequence(self):\n        \"\"\"\n        Creating a L{MessageSet} with both a start and end message\n        number adds the sequence between to the L{MessageSet}; its\n        serialized form consists that range, its length is the length\n        of the sequence, and it yields the message numbers inclusively\n        between the start and end.\n        \"\"\"\n        m = MessageSet(1, 10)\n        self.assertEqual(str(m), \"1:10\")\n        self.assertEqual(len(m), 10)\n        self.assertEqual(list(m), [1, 2, 3, 4, 5, 6, 7, 8, 9, 10])\n\n\n    def test_createWithSingleWildcard(self):\n        \"\"\"\n        Creating a L{MessageSet} with a single L{None}, representing\n        C{*}, adds C{*} to the range; its serialized form includes\n        only C{*}, its length is one, but it cannot be iterated over\n        because its endpoint is unknown.\n        \"\"\"\n        m = MessageSet(None)\n        self.assertEqual(str(m), \"*\")\n        self.assertEqual(len(m), 1)\n        self.assertRaises(TypeError, list, m)\n\n\n    def test_setLastSingleWildcard(self):\n        \"\"\"\n        Setting L{MessageSet.last} replaces L{None}, representing\n        C{*}, with that number, making that L{MessageSet} iterable.\n        \"\"\"\n        singleMessageReplaced = MessageSet(None)\n        singleMessageReplaced.last = 10\n        self.assertEqual(list(singleMessageReplaced), [10])\n\n        rangeReplaced = MessageSet(3, None)\n        rangeReplaced.last = 1\n        self.assertEqual(list(rangeReplaced), [1, 2, 3])\n\n\n    def test_setLastWithWildcardRange(self):\n        \"\"\"\n        Setting L{MessageSet.last} replaces L{None} in all ranges.\n        \"\"\"\n        m = MessageSet(1, None)\n        m.add(2, None)\n        m.last = 5\n        self.assertEqual(list(m), [1, 2, 3, 4, 5])\n\n\n    def test_setLastTwiceFails(self):\n        \"\"\"\n        L{MessageSet.last} cannot be set twice.\n        \"\"\"\n        m = MessageSet(1, None)\n        m.last = 2\n        with self.assertRaises(ValueError):\n            m.last = 3\n\n\n    def test_lastOverridesNoneInAdd(self):\n        \"\"\"\n        Adding a L{None}, representing C{*}, or a sequence that\n        includes L{None} to a L{MessageSet} whose\n        L{last<MessageSet.last>} property has been set replaces all\n        occurrences of L{None} with the value of\n        L{last<MessageSet.last>}.\n        \"\"\"\n        hasLast = MessageSet(1)\n        hasLast.last = 4\n\n        hasLast.add(None)\n        self.assertEqual(list(hasLast), [1, 4])\n\n        self.assertEqual(list(hasLast + (None, 5)), [1, 4, 5])\n\n        hasLast.add(3, None)\n        self.assertEqual(list(hasLast), [1, 3, 4])\n\n\n    def test_getLast(self):\n        \"\"\"\n        Accessing L{MessageSet.last} returns the last value.\n        \"\"\"\n        m = MessageSet(1, None)\n        m.last = 2\n        self.assertEqual(m.last, 2)\n\n\n    def test_extend(self):\n        \"\"\"\n        L{MessageSet.extend} accepts as its arugment an L{int} or\n        L{None}, or a sequence L{int}s or L{None}s of length two, or\n        another L{MessageSet}, combining its argument with its\n        instance's existing ranges.\n        \"\"\"\n        extendWithInt = MessageSet()\n        extendWithInt.extend(1)\n        self.assertEqual(list(extendWithInt), [1])\n\n        extendWithNone = MessageSet()\n        extendWithNone.extend(None)\n        self.assertEqual(str(extendWithNone), \"*\")\n\n        extendWithSequenceOfInts = MessageSet()\n        extendWithSequenceOfInts.extend((1, 3))\n        self.assertEqual(list(extendWithSequenceOfInts), [1, 2, 3])\n\n        extendWithSequenceOfNones = MessageSet()\n        extendWithSequenceOfNones.extend((None, None))\n        self.assertEqual(str(extendWithSequenceOfNones), \"*\")\n\n        extendWithMessageSet = MessageSet()\n        extendWithMessageSet.extend(MessageSet(1, 3))\n        self.assertEqual(list(extendWithMessageSet), [1, 2, 3])\n\n\n    def test_contains(self):\n        \"\"\"\n        A L{MessageSet} contains a number if the number falls within\n        one of its ranges, and raises L{TypeError} if any range\n        contains L{None}.\n        \"\"\"\n        hasFive = MessageSet(1, 7)\n        doesNotHaveFive = MessageSet(1, 4) + MessageSet(6, 7)\n\n        self.assertIn(5, hasFive)\n        self.assertNotIn(5, doesNotHaveFive)\n\n        hasFiveButHasNone = hasFive + None\n        with self.assertRaises(TypeError):\n            5 in hasFiveButHasNone\n\n        hasFiveButHasNoneInSequence = hasFive + (10, 12)\n        hasFiveButHasNoneInSequence.add(8, None)\n        with self.assertRaises(TypeError):\n            5 in hasFiveButHasNoneInSequence\n\n\n    def test_rangesMerged(self):\n        \"\"\"\n        Adding a sequence of message numbers to a L{MessageSet} that\n        begins or ends immediately before or after an existing\n        sequence in that L{MessageSet}, or overlaps one, merges the two.\n        \"\"\"\n\n        mergeAfter = MessageSet(1, 3)\n        mergeBefore = MessageSet(6, 8)\n\n        mergeBetweenSequence = mergeAfter + mergeBefore\n        mergeBetweenNumber = mergeAfter + MessageSet(5, 7)\n\n        self.assertEqual(list(mergeAfter + (2, 4)), [1, 2, 3, 4])\n        self.assertEqual(list(mergeAfter + (3, 5)), [1, 2, 3, 4, 5])\n\n        self.assertEqual(list(mergeBefore + (5, 7)), [5, 6, 7, 8])\n        self.assertEqual(list(mergeBefore + (4, 6)), [4, 5, 6, 7, 8])\n\n        self.assertEqual(list(mergeBetweenSequence + (3, 5)),\n                         [1, 2, 3, 4, 5, 6, 7, 8])\n        self.assertEqual(list(mergeBetweenNumber + MessageSet(4)),\n                         [1, 2, 3, 4, 5, 6, 7])\n\n\n    def test_seq_rangeExamples(self):\n        \"\"\"\n        Test the C{seq-range} examples from Section 9, \"Formal Syntax\"\n        of RFC 3501::\n\n            Example: 2:4 and 4:2 are equivalent and indicate values\n                     2, 3, and 4.\n\n            Example: a unique identifier sequence range of\n                     3291:* includes the UID of the last message in\n                     the mailbox, even if that value is less than 3291.\n\n        @see: U{http://tools.ietf.org/html/rfc3501#section-9}\n        \"\"\"\n\n        self.assertEqual(MessageSet(2, 4), MessageSet(4, 2))\n        self.assertEqual(list(MessageSet(2, 4)), [2, 3, 4])\n\n        m = MessageSet(3291, None)\n        m.last = 3290\n        self.assertEqual(list(m), [3290, 3291])\n\n\n    def test_sequence_setExamples(self):\n        \"\"\"\n        Test the C{sequence-set} examples from Section 9, \"Formal\n        Syntax\" of RFC 3501.  In particular, L{MessageSet} reorders\n        and coalesces overlaps::\n\n            Example: a message sequence number set of\n                     2,4:7,9,12:* for a mailbox with 15 messages is\n                     equivalent to 2,4,5,6,7,9,12,13,14,15\n\n            Example: a message sequence number set of *:4,5:7\n                     for a mailbox with 10 messages is equivalent to\n                     10,9,8,7,6,5,4,5,6,7 and MAY be reordered and\n                     overlap coalesced to be 4,5,6,7,8,9,10.\n\n        @see: U{http://tools.ietf.org/html/rfc3501#section-9}\n        \"\"\"\n        fromFifteenMessages = (\n            MessageSet(2) +\n            MessageSet(4, 7) +\n            MessageSet(9) +\n            MessageSet(12, None)\n        )\n        fromFifteenMessages.last = 15\n        self.assertEqual(','.join(str(i) for i in fromFifteenMessages),\n                         \"2,4,5,6,7,9,12,13,14,15\")\n\n        fromTenMessages = (\n            MessageSet(None, 4) +\n            MessageSet(5, 7)\n        )\n        fromTenMessages.last = 10\n        self.assertEqual(','.join(str(i) for i in fromTenMessages),\n                         \"4,5,6,7,8,9,10\")\n\n\n\nclass IMAP4HelperTests(unittest.TestCase):\n    \"\"\"\n    Tests for various helper utilities in the IMAP4 module.\n    \"\"\"\n    def test_commandRepr(self):\n        \"\"\"\n        L{imap4.Command}'s C{repr} does not raise an exception.\n        \"\"\"\n        repr(imap4.Command(b\"COMMAND\", [b\"arg\"], (b'extra')))\n\n\n    def test_fileProducer(self):\n        b = ((b'x' * 1) + (b'y' * 1) + (b'z' * 1)) * 10\n        c = BufferingConsumer()\n        f = BytesIO(b)\n        p = imap4.FileProducer(f)\n        d = p.beginProducing(c)\n\n        def cbProduced(result):\n            self.failUnlessIdentical(result, p)\n            self.assertEqual(\n                (b'{' + intToBytes(len(b)) + b'}' + b'\\r\\n' + b),\n                b''.join(c.buffer))\n            return result\n\n        def cbResume(result):\n            # Calling resumeProducing after completion does not raise\n            # an exception\n            p.resumeProducing()\n            return result\n\n        d.addCallback(cbProduced)\n        d.addCallback(cbResume)\n        # The second cbProduced ensures calling resumeProducing after\n        # completion does not change the result.\n        return d.addCallback(cbProduced)\n\n\n    def test_wildcard(self):\n        cases = [\n            ['foo/%gum/bar',\n                ['foo/bar', 'oo/lalagum/bar', 'foo/gumx/bar', 'foo/gum/baz'],\n                ['foo/xgum/bar', 'foo/gum/bar'],\n            ], ['foo/x%x/bar',\n                ['foo', 'bar', 'fuz fuz fuz', 'foo/*/bar', 'foo/xyz/bar', 'foo/xx/baz'],\n                ['foo/xyx/bar', 'foo/xx/bar', 'foo/xxxxxxxxxxxxxx/bar'],\n            ], ['foo/xyz*abc/bar',\n                ['foo/xyz/bar', 'foo/abc/bar', 'foo/xyzab/cbar', 'foo/xyza/bcbar'],\n                ['foo/xyzabc/bar', 'foo/xyz/abc/bar', 'foo/xyz/123/abc/bar'],\n            ]\n        ]\n\n        for (wildcard, fail, succeed) in cases:\n            wildcard = imap4.wildcardToRegexp(wildcard, '/')\n            for x in fail:\n                self.assertFalse(wildcard.match(x))\n            for x in succeed:\n                self.assertTrue(wildcard.match(x))\n\n\n    def test_wildcardNoDelim(self):\n        cases = [\n            ['foo/%gum/bar',\n                ['foo/bar', 'oo/lalagum/bar', 'foo/gumx/bar', 'foo/gum/baz'],\n                ['foo/xgum/bar', 'foo/gum/bar', 'foo/x/gum/bar'],\n            ], ['foo/x%x/bar',\n                ['foo', 'bar', 'fuz fuz fuz', 'foo/*/bar', 'foo/xyz/bar', 'foo/xx/baz'],\n                ['foo/xyx/bar', 'foo/xx/bar', 'foo/xxxxxxxxxxxxxx/bar', 'foo/x/x/bar'],\n            ], ['foo/xyz*abc/bar',\n                ['foo/xyz/bar', 'foo/abc/bar', 'foo/xyzab/cbar', 'foo/xyza/bcbar'],\n                ['foo/xyzabc/bar', 'foo/xyz/abc/bar', 'foo/xyz/123/abc/bar'],\n            ]\n        ]\n\n        for (wildcard, fail, succeed) in cases:\n            wildcard = imap4.wildcardToRegexp(wildcard, None)\n            for x in fail:\n                self.assertFalse(wildcard.match(x), x)\n            for x in succeed:\n                self.assertTrue(wildcard.match(x), x)\n\n\n    def test_headerFormatter(self):\n        \"\"\"\n        L{imap4._formatHeaders} accepts a C{dict} of header name/value pairs and\n        returns a string representing those headers in the standard multiline,\n        C{\":\"}-separated format.\n        \"\"\"\n        cases = [\n            ({'Header1': 'Value1', 'Header2': 'Value2'},\n             b'Header2: Value2\\r\\nHeader1: Value1\\r\\n'),\n        ]\n\n        for (input, expected) in cases:\n            output = imap4._formatHeaders(input)\n            self.assertEqual(sorted(output.splitlines(True)),\n                             sorted(expected.splitlines(True)))\n\n\n    def test_quotedSplitter(self):\n        cases = [\n            b'''Hello World''',\n            b'''Hello \"World!\"''',\n            b'''World \"Hello\" \"How are you?\"''',\n            b'''\"Hello world\" How \"are you?\"''',\n            b'''foo bar \"baz buz\" NIL''',\n            b'''foo bar \"baz buz\" \"NIL\"''',\n            b'''foo NIL \"baz buz\" bar''',\n            b'''foo \"NIL\" \"baz buz\" bar''',\n            b'''\"NIL\" bar \"baz buz\" foo''',\n            b'oo \\\\\"oo\\\\\" oo',\n            b'\"oo \\\\\"oo\\\\\" oo\"',\n            b'oo \\t oo',\n            b'\"oo \\t oo\"',\n            b'oo \\\\t oo',\n            b'\"oo \\\\t oo\"',\n            b'oo \\o oo',\n            b'\"oo \\o oo\"',\n            b'oo \\\\o oo',\n            b'\"oo \\\\o oo\"',\n        ]\n\n        answers = [\n            [b'Hello', b'World'],\n            [b'Hello', b'World!'],\n            [b'World', b'Hello', b'How are you?'],\n            [b'Hello world', b'How', b'are you?'],\n            [b'foo', b'bar', b'baz buz', None],\n            [b'foo', b'bar', b'baz buz', b'NIL'],\n            [b'foo', None, b'baz buz', b'bar'],\n            [b'foo', b'NIL', b'baz buz', b'bar'],\n            [b'NIL', b'bar', b'baz buz', b'foo'],\n            [b'oo', b'\"oo\"', b'oo'],\n            [b'oo \"oo\" oo'],\n            [b'oo', b'oo'],\n            [b'oo \\t oo'],\n            [b'oo', b'\\\\t', b'oo'],\n            [b'oo \\\\t oo'],\n            [b'oo', b'\\o', b'oo'],\n            [b'oo \\o oo'],\n            [b'oo', b'\\\\o', b'oo'],\n            [b'oo \\\\o oo'],\n\n        ]\n\n        errors = [\n            b'\"mismatched quote',\n            b'mismatched quote\"',\n            b'mismatched\"quote',\n            b'\"oops here is\" another\"',\n        ]\n\n        for s in errors:\n            self.assertRaises(imap4.MismatchedQuoting, imap4.splitQuoted, s)\n\n        for (case, expected) in zip(cases, answers):\n            self.assertEqual(imap4.splitQuoted(case), expected)\n\n\n    def test_stringCollapser(self):\n        cases = [\n            [b'a', b'b', b'c', b'd', b'e'],\n            [b'a', b' ', b'\"', b'b', b'c', b' ', b'\"', b' ', b'd', b'e'],\n            [[b'a', b'b', b'c'], b'd', b'e'],\n            [b'a', [b'b', b'c', b'd'], b'e'],\n            [b'a', b'b', [b'c', b'd', b'e']],\n            [b'\"', b'a', b' ', b'\"', [b'b', b'c', b'd'], b'\"', b' ', b'e',\n             b'\"'],\n            [b'a', [b'\"', b' ', b'b', b'c', b' ', b' ', b'\"'], b'd', b'e'],\n        ]\n\n        answers = [\n            [b'abcde'],\n            [b'a', b'bc ', b'de'],\n            [[b'abc'], b'de'],\n            [b'a', [b'bcd'], b'e'],\n            [b'ab', [b'cde']],\n            [b'a ', [b'bcd'], b' e'],\n            [b'a', [b' bc  '], b'de'],\n        ]\n\n        for (case, expected) in zip(cases, answers):\n            self.assertEqual(imap4.collapseStrings(case), expected)\n\n\n    def test_parenParser(self):\n        s = b'\\r\\n'.join([b'xx'] * 4)\n        def check(case, expected):\n            parsed = imap4.parseNestedParens(case)\n            self.assertEqual(parsed, [expected])\n            # XXX This code used to work, but changes occurred within the\n            # imap4.py module which made it no longer necessary for *all* of it\n            # to work.  In particular, only the part that makes\n            # 'BODY.PEEK[HEADER.FIELDS.NOT (Subject Bcc Cc)]' come out\n            # correctly no longer needs to work.  So, I am loathe to delete the\n            # entire section of the test. --exarkun\n\n            # self.assertEqual(b'(' + imap4.collapseNestedLists(parsed) + b')',\n            #                  expected)\n\n\n        check(\n            b'(BODY.PEEK[HEADER.FIELDS.NOT (subject bcc cc)] {' +\n            intToBytes(len(s)) + b'}\\r\\n' + s + b')',\n            [b'BODY.PEEK', [b'HEADER.FIELDS.NOT', [b'subject', b'bcc', b'cc']],\n             s],\n        )\n        check(\n            b'(FLAGS (\\Seen) INTERNALDATE \"17-Jul-1996 02:44:25 -0700\" '\n            b'RFC822.SIZE 4286 ENVELOPE (\"Wed, 17 Jul 1996 02:23:25 -0700 (PDT)\" '\n            b'\"IMAP4rev1 WG mtg summary and minutes\" '\n            b'((\"Terry Gray\" NIL gray cac.washington.edu)) '\n            b'((\"Terry Gray\" NIL gray cac.washington.edu)) '\n            b'((\"Terry Gray\" NIL gray cac.washington.edu)) '\n            b'((NIL NIL imap cac.washington.edu)) '\n            b'((NIL NIL minutes CNRI.Reston.VA.US) '\n            b'(\"John Klensin\" NIL KLENSIN INFOODS.MIT.EDU)) NIL NIL '\n            b'<B27397-0100000@cac.washington.edu>) '\n            b'BODY (TEXT PLAIN (CHARSET US-ASCII) NIL NIL 7BIT 3028 92))',\n            [b'FLAGS', [br'\\Seen'], b'INTERNALDATE',\n             b'17-Jul-1996 02:44:25 -0700', b'RFC822.SIZE', b'4286',\n             b'ENVELOPE',\n             [b'Wed, 17 Jul 1996 02:23:25 -0700 (PDT)',\n              b'IMAP4rev1 WG mtg summary and minutes',\n              [[b\"Terry Gray\", None, b\"gray\", b\"cac.washington.edu\"]],\n              [[b\"Terry Gray\", None, b\"gray\", b\"cac.washington.edu\"]],\n              [[b\"Terry Gray\", None, b\"gray\", b\"cac.washington.edu\"]],\n              [[None, None, b\"imap\", b\"cac.washington.edu\"]],\n              [[None, None, b\"minutes\", b\"CNRI.Reston.VA.US\"],\n               [b\"John Klensin\", None, b\"KLENSIN\", b\"INFOODS.MIT.EDU\"]],\n              None, None, b\"<B27397-0100000@cac.washington.edu>\"],\n             b\"BODY\",\n             [b\"TEXT\", b\"PLAIN\", [b\"CHARSET\", b\"US-ASCII\"], None, None,\n              b\"7BIT\", b\"3028\", b\"92\"]]\n        )\n\n        check(b'(\"oo \\\\\"oo\\\\\" oo\")', [b'oo \"oo\" oo'])\n        check(b'(\"oo \\\\\\\\ oo\")', [b'oo \\\\\\\\ oo'])\n        check(b'(\"oo \\\\ oo\")', [b'oo \\\\ oo'])\n\n        check(b'(\"oo \\\\o\")', [b'oo \\\\o'])\n        check(b'(\"oo \\o\")', [b'oo \\o'])\n        check(b'(oo \\o)', [b'oo', b'\\o'])\n        check(b'(oo \\\\o)', [b'oo', b'\\\\o'])\n\n\n    def test_fetchParserSimple(self):\n        cases = [\n            ['ENVELOPE', 'Envelope', 'envelope'],\n            ['FLAGS', 'Flags', 'flags'],\n            ['INTERNALDATE', 'InternalDate', 'internaldate'],\n            ['RFC822.HEADER', 'RFC822Header', 'rfc822.header'],\n            ['RFC822.SIZE', 'RFC822Size', 'rfc822.size'],\n            ['RFC822.TEXT', 'RFC822Text', 'rfc822.text'],\n            ['RFC822', 'RFC822', 'rfc822'],\n            ['UID', 'UID', 'uid'],\n            ['BODYSTRUCTURE', 'BodyStructure', 'bodystructure'],\n        ]\n\n        for (inp, outp, asString) in cases:\n            inp = inp.encode('ascii')\n            p = imap4._FetchParser()\n            p.parseString(inp)\n            self.assertEqual(len(p.result), 1)\n            self.assertTrue(isinstance(p.result[0], getattr(p, outp)))\n            self.assertEqual(str(p.result[0]), asString)\n\n\n    def test_fetchParserMacros(self):\n        cases = [\n            [b'ALL', (4, [b'flags', b'internaldate', b'rfc822.size',\n                          b'envelope'])],\n            [b'FULL', (5, [b'flags', b'internaldate', b'rfc822.size',\n                           b'envelope', b'body'])],\n            [b'FAST', (3, [b'flags', b'internaldate', b'rfc822.size'])],\n        ]\n\n        for (inp, outp) in cases:\n            p = imap4._FetchParser()\n            p.parseString(inp)\n            self.assertEqual(len(p.result), outp[0])\n            expectedResult = [str(token).lower().encode(\"ascii\")\n                              for token in p.result]\n            expectedResult.sort()\n            outp[1].sort()\n            self.assertEqual(expectedResult, outp[1])\n\n\n    def test_fetchParserBody(self):\n        P = imap4._FetchParser\n\n        p = P()\n        p.parseString(b'BODY')\n        self.assertEqual(len(p.result), 1)\n        self.assertTrue(isinstance(p.result[0], p.Body))\n        self.assertEqual(p.result[0].peek, False)\n        self.assertEqual(p.result[0].header, None)\n        self.assertEqual(str(p.result[0]), 'BODY')\n\n        p = P()\n        p.parseString(b'BODY.PEEK')\n        self.assertEqual(len(p.result), 1)\n        self.assertTrue(isinstance(p.result[0], p.Body))\n        self.assertEqual(p.result[0].peek, True)\n        self.assertEqual(str(p.result[0]), 'BODY')\n\n        p = P()\n        p.parseString(b'BODY[]')\n        self.assertEqual(len(p.result), 1)\n        self.assertTrue(isinstance(p.result[0], p.Body))\n        self.assertEqual(p.result[0].empty, True)\n        self.assertEqual(str(p.result[0]), 'BODY[]')\n\n        p = P()\n        p.parseString(b'BODY[HEADER]')\n        self.assertEqual(len(p.result), 1)\n        self.assertTrue(isinstance(p.result[0], p.Body))\n        self.assertEqual(p.result[0].peek, False)\n        self.assertTrue(isinstance(p.result[0].header, p.Header))\n        self.assertEqual(p.result[0].header.negate, True)\n        self.assertEqual(p.result[0].header.fields, ())\n        self.assertEqual(p.result[0].empty, False)\n        self.assertEqual(str(p.result[0]), 'BODY[HEADER]')\n\n        p = P()\n        p.parseString(b'BODY.PEEK[HEADER]')\n        self.assertEqual(len(p.result), 1)\n        self.assertTrue(isinstance(p.result[0], p.Body))\n        self.assertEqual(p.result[0].peek, True)\n        self.assertTrue(isinstance(p.result[0].header, p.Header))\n        self.assertEqual(p.result[0].header.negate, True)\n        self.assertEqual(p.result[0].header.fields, ())\n        self.assertEqual(p.result[0].empty, False)\n        self.assertEqual(str(p.result[0]), 'BODY[HEADER]')\n\n        p = P()\n        p.parseString(b'BODY[HEADER.FIELDS (Subject Cc Message-Id)]')\n        self.assertEqual(len(p.result), 1)\n        self.assertTrue(isinstance(p.result[0], p.Body))\n        self.assertEqual(p.result[0].peek, False)\n        self.assertTrue(isinstance(p.result[0].header, p.Header))\n        self.assertEqual(p.result[0].header.negate, False)\n        self.assertEqual(p.result[0].header.fields,\n                         [b'SUBJECT', b'CC', b'MESSAGE-ID'])\n        self.assertEqual(p.result[0].empty, False)\n        self.assertEqual(bytes(p.result[0]),\n                         b'BODY[HEADER.FIELDS (Subject Cc Message-Id)]')\n\n        p = P()\n        p.parseString(b'BODY.PEEK[HEADER.FIELDS (Subject Cc Message-Id)]')\n        self.assertEqual(len(p.result), 1)\n        self.assertTrue(isinstance(p.result[0], p.Body))\n        self.assertEqual(p.result[0].peek, True)\n        self.assertTrue(isinstance(p.result[0].header, p.Header))\n        self.assertEqual(p.result[0].header.negate, False)\n        self.assertEqual(p.result[0].header.fields,\n                         [b'SUBJECT', b'CC', b'MESSAGE-ID'])\n        self.assertEqual(p.result[0].empty, False)\n        self.assertEqual(bytes(p.result[0]),\n                         b'BODY[HEADER.FIELDS (Subject Cc Message-Id)]')\n\n        p = P()\n        p.parseString(b'BODY.PEEK[HEADER.FIELDS.NOT (Subject Cc Message-Id)]')\n        self.assertEqual(len(p.result), 1)\n        self.assertTrue(isinstance(p.result[0], p.Body))\n        self.assertEqual(p.result[0].peek, True)\n        self.assertTrue(isinstance(p.result[0].header, p.Header))\n        self.assertEqual(p.result[0].header.negate, True)\n        self.assertEqual(p.result[0].header.fields,\n                         [b'SUBJECT', b'CC', b'MESSAGE-ID'])\n        self.assertEqual(p.result[0].empty, False)\n        self.assertEqual(bytes(p.result[0]),\n                         b'BODY[HEADER.FIELDS.NOT (Subject Cc Message-Id)]')\n\n        p = P()\n        p.parseString(b'BODY[1.MIME]<10.50>')\n        self.assertEqual(len(p.result), 1)\n        self.assertTrue(isinstance(p.result[0], p.Body))\n        self.assertEqual(p.result[0].peek, False)\n        self.assertTrue(isinstance(p.result[0].mime, p.MIME))\n        self.assertEqual(p.result[0].part, (0,))\n        self.assertEqual(p.result[0].partialBegin, 10)\n        self.assertEqual(p.result[0].partialLength, 50)\n        self.assertEqual(p.result[0].empty, False)\n        self.assertEqual(bytes(p.result[0]), b'BODY[1.MIME]<10.50>')\n\n        p = P()\n        p.parseString(\n            b'BODY.PEEK[1.3.9.11.HEADER.FIELDS.NOT (Message-Id Date)]<103.69>')\n        self.assertEqual(len(p.result), 1)\n        self.assertTrue(isinstance(p.result[0], p.Body))\n        self.assertEqual(p.result[0].peek, True)\n        self.assertTrue(isinstance(p.result[0].header, p.Header))\n        self.assertEqual(p.result[0].part, (0, 2, 8, 10))\n        self.assertEqual(p.result[0].header.fields, [b'MESSAGE-ID', b'DATE'])\n        self.assertEqual(p.result[0].partialBegin, 103)\n        self.assertEqual(p.result[0].partialLength, 69)\n        self.assertEqual(p.result[0].empty, False)\n        self.assertEqual(\n            bytes(p.result[0]),\n            b'BODY[1.3.9.11.HEADER.FIELDS.NOT (Message-Id Date)]<103.69>'\n        )\n\n\n    def test_fetchParserQuotedHeader(self):\n        \"\"\"\n        Parsing a C{BODY} whose C{HEADER} values require quoting\n        results in a object that perserves that quoting when\n        serialized.\n        \"\"\"\n        p = imap4._FetchParser()\n        p.parseString(b'BODY[HEADER.FIELDS ((Quoted)]')\n        self.assertEqual(len(p.result), 1)\n        self.assertEqual(p.result[0].peek, False)\n        self.assertIsInstance(p.result[0], p.Body)\n        self.assertIsInstance(p.result[0].header, p.Header)\n        self.assertEqual(bytes(p.result[0]),\n                         b'BODY[HEADER.FIELDS (\"(Quoted\")]')\n\n\n    def test_fetchParserEmptyString(self):\n        \"\"\"\n        Parsing an empty string results in no data.\n        \"\"\"\n        p = imap4._FetchParser()\n        p.parseString(b'')\n        self.assertFalse(len(p.result))\n\n\n    def test_fetchParserUnknownAttribute(self):\n        \"\"\"\n        Parsing a string with an unknown attribute raises an\n        L{Exception}.\n        \"\"\"\n        p = imap4._FetchParser()\n        self.assertRaises(Exception, p.parseString, b\"UNKNOWN\")\n\n\n    def test_fetchParserIncompleteStringEndsInWhitespace(self):\n        \"\"\"\n        Parsing a string that prematurely ends in whitespace raises an\n        L{Exception}.\n        \"\"\"\n        p = imap4._FetchParser()\n        self.assertRaises(Exception, p.parseString, b\"BODY[HEADER.FIELDS  \")\n\n\n    def test_fetchParserExpectedWhitespace(self):\n        \"\"\"\n        Parsing a string that contains an unexpected character rather\n        than whitespace raises an L{Exception}.\n        \"\"\"\n        p = imap4._FetchParser()\n        self.assertRaises(Exception, p.parseString, b\"BODY[HEADER.FIELDS!]\")\n\n\n    def test_fetchParserTextSection(self):\n        \"\"\"\n        A C{BODY} can contain a C{TEXT} section.\n        \"\"\"\n        p = imap4._FetchParser()\n        p.parseString(b\"BODY[TEXT]\")\n        self.assertEqual(len(p.result), 1)\n        self.assertIsInstance(p.result[0], p.Body)\n        self.assertEqual(p.result[0].peek, False)\n        self.assertIsInstance(p.result[0].text, p.Text)\n        self.assertEqual(bytes(p.result[0]), b'BODY[TEXT]')\n\n\n    def test_fetchParserUnknownSection(self):\n        \"\"\"\n        Parsing a C{BODY} with an unknown section raises an\n        L{Exception}.\n        \"\"\"\n        p = imap4._FetchParser()\n        self.assertRaises(Exception, p.parseString, b\"BODY[UNKNOWN]\")\n\n\n    def test_fetchParserMissingSectionClose(self):\n        \"\"\"\n        Parsing a C{BODY} with an unterminated section list raises an\n        L{Exception}.\n        \"\"\"\n        p = imap4._FetchParser()\n        self.assertRaises(Exception,\n                          p.parseString, b'BODY[HEADER')\n        p = imap4._FetchParser()\n        self.assertRaises(Exception,\n                          p.parseString, b'BODY[HEADER.FIELDS (SUBJECT)')\n\n\n    def test_fetchParserHeaderMissingParentheses(self):\n        \"\"\"\n        Parsing a C{BODY} whose C{HEADER.FIELDS} list does not begin\n        with an open parenthesis (C{(}) or end with a close\n        parenthesis (C{)}) raises an L{Exception}.\n        \"\"\"\n        p = imap4._FetchParser()\n        self.assertRaises(Exception,\n                          p.parseString, b\"BODY[HEADER.FIELDS Missing)]\")\n        p = imap4._FetchParser()\n        self.assertRaises(Exception,\n                          p.parseString, b'BODY[HEADER.FIELDS (Missing]')\n\n\n    def test_fetchParserDotlessPartial(self):\n        \"\"\"\n        Parsing a C{BODY} with a range that lacks a period (C{.})\n        raises an L{Exception}.\n        \"\"\"\n        p = imap4._FetchParser()\n        self.assertRaises(Exception,\n                          p.parseString, b\"BODY<01>\")\n\n\n    def test_fetchParserUnclosedPartial(self):\n        \"\"\"\n        Parsing a C{BODY} with a partial range that's missing its\n        closing greater than sign (C{>}) raises an L{EXCEPTION}.\n        \"\"\"\n        p = imap4._FetchParser()\n        self.assertRaises(Exception,\n                          p.parseString, b\"BODY<0\")\n\n\n    def test_files(self):\n        inputStructure = [\n            'foo', 'bar', 'baz', BytesIO(b'this is a file\\r\\n'), 'buz',\n            u'biz'\n        ]\n\n        output = b'\"foo\" \"bar\" \"baz\" {16}\\r\\nthis is a file\\r\\n \"buz\" \"biz\"'\n\n        self.assertEqual(imap4.collapseNestedLists(inputStructure), output)\n\n\n    def test_quoteAvoider(self):\n        input = [\n            b'foo', imap4.DontQuoteMe(b'bar'), b\"baz\",\n            BytesIO(b'this is a file\\r\\n'),\n            b\"this is\\r\\nquoted\",\n            imap4.DontQuoteMe(b'buz'), b\"\"\n        ]\n\n        output = (b'\"foo\" bar \"baz\"'\n                  b' {16}\\r\\nthis is a file\\r\\n '\n                  b'{15}\\r\\nthis is\\r\\nquoted'\n                  b' buz \"\"')\n\n        self.assertEqual(imap4.collapseNestedLists(input), output)\n\n\n    def test_literals(self):\n        cases = [\n            (b'({10}\\r\\n0123456789)', [[b'0123456789']]),\n        ]\n\n        for (case, expected) in cases:\n            self.assertEqual(imap4.parseNestedParens(case), expected)\n\n\n    def test_queryBuilder(self):\n        inputs = [\n            imap4.Query(flagged=1),\n            imap4.Query(sorted=1, unflagged=1, deleted=1),\n            imap4.Or(imap4.Query(flagged=1), imap4.Query(deleted=1)),\n            imap4.Query(before='today'),\n            imap4.Or(\n                imap4.Query(deleted=1),\n                imap4.Query(unseen=1),\n                imap4.Query(new=1)\n            ),\n            imap4.Or(\n                imap4.Not(\n                    imap4.Or(\n                        imap4.Query(sorted=1, since='yesterday', smaller=1000),\n                        imap4.Query(sorted=1, before='tuesday', larger=10000),\n                        imap4.Query(sorted=1, unseen=1, deleted=1, before='today'),\n                        imap4.Not(\n                            imap4.Query(subject='spam')\n                        ),\n                    ),\n                ),\n                imap4.Not(\n                    imap4.Query(uid='1:5')\n                ),\n            )\n        ]\n\n        outputs = [\n            'FLAGGED',\n            '(DELETED UNFLAGGED)',\n            '(OR FLAGGED DELETED)',\n            '(BEFORE \"today\")',\n            '(OR DELETED (OR UNSEEN NEW))',\n            '(OR (NOT (OR (SINCE \"yesterday\" SMALLER 1000) ' # Continuing\n            '(OR (BEFORE \"tuesday\" LARGER 10000) (OR (BEFORE ' # Some more\n            '\"today\" DELETED UNSEEN) (NOT (SUBJECT \"spam\")))))) ' # And more\n            '(NOT (UID 1:5)))',\n        ]\n\n        for (query, expected) in zip(inputs, outputs):\n            self.assertEqual(query, expected)\n\n\n    def test_queryKeywordFlagWithQuotes(self):\n        \"\"\"\n        When passed the C{keyword} argument, L{imap4.Query} returns an unquoted\n        string.\n\n        @see: U{http://tools.ietf.org/html/rfc3501#section-9}\n        @see: U{http://tools.ietf.org/html/rfc3501#section-6.4.4}\n        \"\"\"\n        query = imap4.Query(keyword='twisted')\n        self.assertEqual('(KEYWORD twisted)', query)\n\n\n    def test_queryUnkeywordFlagWithQuotes(self):\n        \"\"\"\n        When passed the C{unkeyword} argument, L{imap4.Query} returns an\n        unquoted string.\n\n        @see: U{http://tools.ietf.org/html/rfc3501#section-9}\n        @see: U{http://tools.ietf.org/html/rfc3501#section-6.4.4}\n        \"\"\"\n        query = imap4.Query(unkeyword='twisted')\n        self.assertEqual('(UNKEYWORD twisted)', query)\n\n\n    def test_queryWithMesssageSet(self):\n        \"\"\"\n        When passed a L{MessageSet}, L{imap4.Query} returns a query\n        containing a quoted string representing the ID sequence.\n        \"\"\"\n        query = imap4.Query(messages=imap4.MessageSet(1, None))\n        self.assertEqual(query, '(MESSAGES \"1:*\")')\n\n\n    def test_queryWithInteger(self):\n        \"\"\"\n        When passed an L{int}, L{imap4.Query} returns a query\n        containing a quoted integer.\n        \"\"\"\n        query = imap4.Query(messages=1)\n        self.assertEqual(query, '(MESSAGES \"1\")')\n\n\n    def test_queryOrIllegalQuery(self):\n        \"\"\"\n        An L{imap4.Or} query with less than two arguments raises an\n        L{imap4.IllegalQueryError}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalQueryError,\n                          imap4.Or, imap4.Query(messages=1))\n\n\n    def _keywordFilteringTest(self, keyword):\n        \"\"\"\n        Helper to implement tests for value filtering of KEYWORD and UNKEYWORD\n        queries.\n\n        @param keyword: A native string giving the name of the L{imap4.Query}\n            keyword argument to test.\n        \"\"\"\n        # Check all the printable exclusions\n        self.assertEqual(\n            '(%s twistedrocks)' % (keyword.upper(),),\n            imap4.Query(**{keyword: r'twisted (){%*\"\\] rocks'}))\n\n        # Check all the non-printable exclusions\n        self.assertEqual(\n            '(%s twistedrocks)' % (keyword.upper(),),\n            imap4.Query(**{\n                    keyword: 'twisted %s rocks' % (\n                    ''.join(chr(ch) for ch in range(33)),)}))\n\n\n    def test_queryKeywordFlag(self):\n        \"\"\"\n        When passed the C{keyword} argument, L{imap4.Query} returns an\n        C{atom} that consists of one or more non-special characters.\n\n        List of the invalid characters:\n\n            ( ) { % * \" \\ ] CTL SP\n\n        @see: U{ABNF definition of CTL and SP<https://tools.ietf.org/html/rfc2234>}\n        @see: U{IMAP4 grammar<http://tools.ietf.org/html/rfc3501#section-9>}\n        @see: U{IMAP4 SEARCH specification<http://tools.ietf.org/html/rfc3501#section-6.4.4>}\n        \"\"\"\n        self._keywordFilteringTest(\"keyword\")\n\n\n    def test_queryUnkeywordFlag(self):\n        \"\"\"\n        When passed the C{unkeyword} argument, L{imap4.Query} returns an\n        C{atom} that consists of one or more non-special characters.\n\n        List of the invalid characters:\n\n            ( ) { % * \" \\ ] CTL SP\n\n        @see: U{ABNF definition of CTL and SP<https://tools.ietf.org/html/rfc2234>}\n        @see: U{IMAP4 grammar<http://tools.ietf.org/html/rfc3501#section-9>}\n        @see: U{IMAP4 SEARCH specification<http://tools.ietf.org/html/rfc3501#section-6.4.4>}\n        \"\"\"\n        self._keywordFilteringTest(\"unkeyword\")\n\n\n    def test_invalidIdListParser(self):\n        \"\"\"\n        Trying to parse an invalid representation of a sequence range raises an\n        L{IllegalIdentifierError}.\n        \"\"\"\n        inputs = [\n            b'*:*',\n            b'foo',\n            b'4:',\n            b'bar:5'\n        ]\n\n        for input in inputs:\n            self.assertRaises(imap4.IllegalIdentifierError,\n                              imap4.parseIdList, input, 12345)\n\n\n    def test_invalidIdListParserNonPositive(self):\n        \"\"\"\n        Zeroes and negative values are not accepted in id range expressions. RFC\n        3501 states that sequence numbers and sequence ranges consist of\n        non-negative numbers (RFC 3501 section 9, the seq-number grammar item).\n        \"\"\"\n        inputs = [\n            b'0:5',\n            b'0:0',\n            b'*:0',\n            b'0',\n            b'-3:5',\n            b'1:-2',\n            b'-1'\n        ]\n\n        for input in inputs:\n            self.assertRaises(imap4.IllegalIdentifierError,\n                              imap4.parseIdList, input, 12345)\n\n\n    def test_parseIdList(self):\n        \"\"\"\n        The function to parse sequence ranges yields appropriate L{MessageSet}\n        objects.\n        \"\"\"\n        inputs = [\n            b'1:*',\n            b'5:*',\n            b'1:2,5:*',\n            b'*',\n            b'1',\n            b'1,2',\n            b'1,3,5',\n            b'1:10',\n            b'1:10,11',\n            b'1:5,10:20',\n            b'1,5:10',\n            b'1,5:10,15:20',\n            b'1:10,15,20:25',\n            b'4:2'\n        ]\n\n        outputs = [\n            MessageSet(1, None),\n            MessageSet(5, None),\n            MessageSet(5, None) + MessageSet(1, 2),\n            MessageSet(None, None),\n            MessageSet(1),\n            MessageSet(1, 2),\n            MessageSet(1) + MessageSet(3) + MessageSet(5),\n            MessageSet(1, 10),\n            MessageSet(1, 11),\n            MessageSet(1, 5) + MessageSet(10, 20),\n            MessageSet(1) + MessageSet(5, 10),\n            MessageSet(1) + MessageSet(5, 10) + MessageSet(15, 20),\n            MessageSet(1, 10) + MessageSet(15) + MessageSet(20, 25),\n            MessageSet(2, 4),\n        ]\n\n        lengths = [\n            None, None, None,\n            1, 1, 2, 3, 10, 11, 16, 7, 13, 17, 3\n        ]\n\n        for (input, expected) in zip(inputs, outputs):\n            self.assertEqual(imap4.parseIdList(input), expected)\n\n        for (input, expected) in zip(inputs, lengths):\n            if expected is None:\n                self.assertRaises(TypeError, len, imap4.parseIdList(input))\n            else:\n                L = len(imap4.parseIdList(input))\n                self.assertEqual(L, expected,\n                                  \"len(%r) = %r != %r\" % (input, L, expected))\n\n\n    def test_parseTimeInvalidFormat(self):\n        \"\"\"\n        L{imap4.parseTime} raises L{ValueError} when given a a time\n        string whose format is invalid.\n        \"\"\"\n        self.assertRaises(ValueError, imap4.parseTime, u\"invalid\")\n\n\n    def test_parseTimeInvalidValues(self):\n        \"\"\"\n        L{imap4.parseTime} raises L{ValueError} when given a time\n        string composed of invalid values.\n        \"\"\"\n        invalidStrings = [\n            \"invalid-July-2017\",\n            \"2-invalid-2017\",\n            \"2-July-invalid\",\n        ]\n        for invalid in invalidStrings:\n            self.assertRaises(ValueError, imap4.parseTime, invalid)\n\n\n    def test_statusRequestHelper(self):\n        \"\"\"\n        L{imap4.statusRequestHelper} builds a L{dict} mapping the\n        requested status names to values extracted from the provided\n        L{IMailboxIMAP}'s.\n        \"\"\"\n        mbox = SimpleMailbox()\n\n        expected = {\n            'MESSAGES': mbox.getMessageCount(),\n            'RECENT': mbox.getRecentCount(),\n            'UIDNEXT': mbox.getUIDNext(),\n            'UIDVALIDITY': mbox.getUIDValidity(),\n            'UNSEEN': mbox.getUnseenCount(),\n        }\n\n        result = imap4.statusRequestHelper(mbox, expected.keys())\n\n        self.assertEqual(expected, result)\n\n\n\n@implementer(imap4.IMailboxInfo, imap4.IMailbox, imap4.ICloseableMailbox)\nclass SimpleMailbox:\n    flags = ('\\\\Flag1', 'Flag2', '\\\\AnotherSysFlag', 'LastFlag')\n    messages = []\n    mUID = 0\n    rw = 1\n    closed = False\n\n    def __init__(self):\n        self.listeners = []\n        self.addListener = self.listeners.append\n        self.removeListener = self.listeners.remove\n\n\n    def getFlags(self):\n        return self.flags\n\n\n    def getUIDValidity(self):\n        return 42\n\n\n    def getUIDNext(self):\n        return len(self.messages) + 1\n\n\n    def getMessageCount(self):\n        return 9\n\n\n    def getRecentCount(self):\n        return 3\n\n\n    def getUnseenCount(self):\n        return 4\n\n\n    def isWriteable(self):\n        return self.rw\n\n\n    def destroy(self):\n        pass\n\n\n    def getHierarchicalDelimiter(self):\n        return '/'\n\n\n    def requestStatus(self, names):\n        r = {}\n        if 'MESSAGES' in names:\n            r['MESSAGES'] = self.getMessageCount()\n        if 'RECENT' in names:\n            r['RECENT'] = self.getRecentCount()\n        if 'UIDNEXT' in names:\n            r['UIDNEXT'] = self.getMessageCount() + 1\n        if 'UIDVALIDITY' in names:\n            r['UIDVALIDITY'] = self.getUID()\n        if 'UNSEEN' in names:\n            r['UNSEEN'] = self.getUnseenCount()\n        return defer.succeed(r)\n\n\n    def addMessage(self, message, flags, date = None):\n        self.messages.append((message, flags, date, self.mUID))\n        self.mUID += 1\n        return defer.succeed(None)\n\n\n    def expunge(self):\n        delete = []\n        for i in self.messages:\n            if '\\\\Deleted' in i[1]:\n                delete.append(i)\n        for i in delete:\n            self.messages.remove(i)\n        return [i[3] for i in delete]\n\n\n    def close(self):\n        self.closed = True\n\n\n\n@implementer(imap4.IMailboxInfo, imap4.IMailbox)\nclass UncloseableMailbox(object):\n    \"\"\"\n    A mailbox that cannot be closed.\n    \"\"\"\n    flags = ('\\\\Flag1', 'Flag2', '\\\\AnotherSysFlag', 'LastFlag')\n    messages = []\n    mUID = 0\n    rw = 1\n    closed = False\n\n    def __init__(self):\n        self.listeners = []\n        self.addListener = self.listeners.append\n        self.removeListener = self.listeners.remove\n\n\n    def getFlags(self):\n        \"\"\"\n        The flags\n\n        @return: A sequence of flags.\n        \"\"\"\n        return self.flags\n\n\n    def getUIDValidity(self):\n        \"\"\"\n        The UID validity value.\n\n        @return: The value.\n        \"\"\"\n        return 42\n\n\n    def getUIDNext(self):\n        \"\"\"\n        The next UID.\n\n        @return: The UID.\n        \"\"\"\n        return len(self.messages) + 1\n\n\n    def getMessageCount(self):\n        \"\"\"\n        The number of messages.\n\n        @return: The number.\n        \"\"\"\n        return 9\n\n\n    def getRecentCount(self):\n        \"\"\"\n        The recent messages.\n\n        @return: The number.\n        \"\"\"\n        return 3\n\n\n    def getUnseenCount(self):\n        \"\"\"\n        The recent messages.\n\n        @return: The number.\n        \"\"\"\n        return 4\n\n\n    def isWriteable(self):\n        \"\"\"\n        The recent messages.\n\n        @return: Whether or not the mailbox is writable.\n        \"\"\"\n        return self.rw\n\n\n    def destroy(self):\n        \"\"\"\n        Destroy this mailbox.\n        \"\"\"\n        pass\n\n\n    def getHierarchicalDelimiter(self):\n        \"\"\"\n        Return the hierarchical delimiter.\n\n        @return: The delimiter.\n        \"\"\"\n        return '/'\n\n\n    def requestStatus(self, names):\n        \"\"\"\n        Return the mailbox's status.\n\n        @param names: The status items to include.\n\n        @return: A L{dict} of status data.\n        \"\"\"\n        r = {}\n        if 'MESSAGES' in names:\n            r['MESSAGES'] = self.getMessageCount()\n        if 'RECENT' in names:\n            r['RECENT'] = self.getRecentCount()\n        if 'UIDNEXT' in names:\n            r['UIDNEXT'] = self.getMessageCount() + 1\n        if 'UIDVALIDITY' in names:\n            r['UIDVALIDITY'] = self.getUID()\n        if 'UNSEEN' in names:\n            r['UNSEEN'] = self.getUnseenCount()\n        return defer.succeed(r)\n\n\n    def addMessage(self, message, flags, date = None):\n        \"\"\"\n        Add a message to the mailbox.\n\n        @param message: The message body.\n\n        @param flags: The message flags.\n\n        @param date: The message date.\n\n        @return: A L{Deferred} that fires when the message has been\n            added.\n        \"\"\"\n        self.messages.append((message, flags, date, self.mUID))\n        self.mUID += 1\n        return defer.succeed(None)\n\n\n    def expunge(self):\n        \"\"\"\n        Delete messages marked for deletion.\n\n        @return: A L{list} of deleted message IDs.\n        \"\"\"\n        delete = []\n        for i in self.messages:\n            if '\\\\Deleted' in i[1]:\n                delete.append(i)\n        for i in delete:\n            self.messages.remove(i)\n        return [i[3] for i in delete]\n\n\n\nclass AccountWithoutNamespaces(imap4.MemoryAccountWithoutNamespaces):\n    \"\"\"\n    An in-memory account that does not provide L{INamespacePresenter}.\n    \"\"\"\n    mailboxFactory = SimpleMailbox\n    def _emptyMailbox(self, name, id):\n        return self.mailboxFactory()\n\n\n    def select(self, name, rw=1):\n        mbox = imap4.MemoryAccount.select(self, name)\n        if mbox is not None:\n            mbox.rw = rw\n        return mbox\n\n\n\nclass Account(AccountWithoutNamespaces, imap4.MemoryAccount):\n    \"\"\"\n    An in-memory account that provides L{INamespacePresenter}.\n    \"\"\"\n\n\n\nclass SimpleServer(imap4.IMAP4Server, object):\n    theAccount = Account(b'testuser')\n    def __init__(self, *args, **kw):\n        imap4.IMAP4Server.__init__(self, *args, **kw)\n        realm = TestRealm(accountHolder=self)\n        portal = Portal(realm)\n        c = InMemoryUsernamePasswordDatabaseDontUse()\n        c.addUser(b'testuser', b'password-test')\n        self.checker = c\n        self.portal = portal\n        portal.registerChecker(c)\n        self.timeoutTest = False\n\n\n    def lineReceived(self, line):\n        if self.timeoutTest:\n            #Do not send a response\n            return\n\n        imap4.IMAP4Server.lineReceived(self, line)\n\n\n\nclass SimpleClient(imap4.IMAP4Client):\n    def __init__(self, deferred, contextFactory = None):\n        imap4.IMAP4Client.__init__(self, contextFactory)\n        self.deferred = deferred\n        self.events = []\n\n\n    def serverGreeting(self, caps):\n        self.deferred.callback(None)\n\n\n    def modeChanged(self, writeable):\n        self.events.append(['modeChanged', writeable])\n        self.transport.loseConnection()\n\n\n    def flagsChanged(self, newFlags):\n        self.events.append(['flagsChanged', newFlags])\n        self.transport.loseConnection()\n\n\n    def newMessages(self, exists, recent):\n        self.events.append(['newMessages', exists, recent])\n        self.transport.loseConnection()\n\n\n\nclass IMAP4HelperMixin:\n\n    serverCTX = None\n    clientCTX = None\n\n    def setUp(self):\n        d = defer.Deferred()\n        self.server = SimpleServer(contextFactory=self.serverCTX)\n        self.client = SimpleClient(d, contextFactory=self.clientCTX)\n        self.connected = d\n\n        SimpleMailbox.messages = []\n        theAccount = Account(b'testuser')\n        theAccount.mboxType = SimpleMailbox\n        SimpleServer.theAccount = theAccount\n\n\n    def tearDown(self):\n        del self.server\n        del self.client\n        del self.connected\n\n\n    def _cbStopClient(self, ignore):\n        self.client.transport.loseConnection()\n\n\n    def _ebGeneral(self, failure):\n        self.client.transport.loseConnection()\n        self.server.transport.loseConnection()\n        log.err(failure, \"Problem with \" + str(self))\n\n\n    def loopback(self):\n        return loopback.loopbackAsync(self.server, self.client)\n\n\n    def assertClientFailureMessage(self, failure, expected):\n        \"\"\"\n        Assert that the provided failure is an L{IMAP4Exception} with\n        the given message.\n\n        @param failure: A failure whose value L{IMAP4Exception}\n        @type failure: L{failure.Failure}\n\n        @param expected: The expected failure message.\n        @type expected: L{bytes}\n        \"\"\"\n        failure.trap(imap4.IMAP4Exception)\n        message = str(failure.value)\n        if _PY3:\n            expected = repr(expected)\n\n        self.assertEqual(message, expected)\n\n\n\nclass IMAP4ServerTests(IMAP4HelperMixin, unittest.TestCase):\n    def testCapability(self):\n        caps = {}\n        def getCaps():\n            def gotCaps(c):\n                caps.update(c)\n                self.server.transport.loseConnection()\n            return self.client.getCapabilities().addCallback(gotCaps)\n        d1 = self.connected.addCallback(strip(getCaps)).addErrback(self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        expected = {b'IMAP4rev1': None, b'NAMESPACE': None, b'IDLE': None}\n        return d.addCallback(lambda _: self.assertEqual(expected, caps))\n\n\n    def testCapabilityWithAuth(self):\n        caps = {}\n        self.server.challengers[b'CRAM-MD5'] = CramMD5Credentials\n        def getCaps():\n            def gotCaps(c):\n                caps.update(c)\n                self.server.transport.loseConnection()\n            return self.client.getCapabilities().addCallback(gotCaps)\n        d1 = self.connected.addCallback(strip(getCaps)).addErrback(self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n\n        expCap = {b'IMAP4rev1': None, b'NAMESPACE': None,\n                  b'IDLE': None, b'AUTH': [b'CRAM-MD5']}\n\n        return d.addCallback(lambda _: self.assertEqual(expCap, caps))\n\n\n    def testLogout(self):\n        self.loggedOut = 0\n        def logout():\n            def setLoggedOut():\n                self.loggedOut = 1\n            self.client.logout().addCallback(strip(setLoggedOut))\n        self.connected.addCallback(strip(logout)).addErrback(self._ebGeneral)\n        d = self.loopback()\n        return d.addCallback(lambda _: self.assertEqual(self.loggedOut, 1))\n\n\n    def testNoop(self):\n        self.responses = None\n        def noop():\n            def setResponses(responses):\n                self.responses = responses\n                self.server.transport.loseConnection()\n            self.client.noop().addCallback(setResponses)\n        self.connected.addCallback(strip(noop)).addErrback(self._ebGeneral)\n        d = self.loopback()\n        return d.addCallback(lambda _: self.assertEqual(self.responses, []))\n\n\n    def testLogin(self):\n        def login():\n            d = self.client.login(b'testuser', b'password-test')\n            d.addCallback(self._cbStopClient)\n        d1 = self.connected.addCallback(strip(login)).addErrback(self._ebGeneral)\n        d = defer.gatherResults([d1, self.loopback()])\n        return d.addCallback(self._cbTestLogin)\n\n\n    def _cbTestLogin(self, ignored):\n        self.assertEqual(self.server.account, SimpleServer.theAccount)\n        self.assertEqual(self.server.state, 'auth')\n\n\n    def testFailedLogin(self):\n        def login():\n            d = self.client.login(b'testuser', b'wrong-password')\n            d.addBoth(self._cbStopClient)\n\n        d1 = self.connected.addCallback(strip(login)).addErrback(self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        return d.addCallback(self._cbTestFailedLogin)\n\n\n    def _cbTestFailedLogin(self, ignored):\n        self.assertEqual(self.server.account, None)\n        self.assertEqual(self.server.state, 'unauth')\n\n\n    def test_loginWithoutPortal(self):\n        \"\"\"\n        Attempting to log into a server that has no L{Portal} results\n        in a failed login.\n        \"\"\"\n        self.server.portal = None\n        def login():\n            d = self.client.login(b'testuser', b'wrong-password')\n            d.addBoth(self._cbStopClient)\n\n        d1 = self.connected.addCallback(strip(login)).addErrback(self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        return d.addCallback(self._cbTestFailedLogin)\n\n\n    def test_nonIAccountAvatar(self):\n        \"\"\"\n        The server responds with a C{BAD} response when its portal\n        attempts to log a user in with checker that claims to support\n        L{IAccount} but returns an an avatar interface that is not\n        L{IAccount}.\n        \"\"\"\n\n        def brokenRequestAvatar(*_, **__):\n            return (\"Not IAccount\", \"Not an account\", lambda: None)\n\n        self.server.portal.realm.requestAvatar = brokenRequestAvatar\n\n        def login():\n            d = self.client.login(b'testuser', b'password-test')\n            d.addBoth(self._cbStopClient)\n\n        d1 = self.connected.addCallback(strip(login)).addErrback(self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        return d.addCallback(self._cbTestFailedLogin)\n\n\n    def test_loginException(self):\n        \"\"\"\n        Any exception raised by L{IMAP4Server.authenticateLogin} that\n        is not L{UnauthorizedLogin} is logged results in a C{BAD}\n        response.\n        \"\"\"\n\n        class UnexpectedException(Exception):\n            \"\"\"\n            An unexpected exception.\n            \"\"\"\n\n        def raisesUnexpectedException(user, passwd):\n            raise UnexpectedException(\"Whoops\")\n\n        self.server.authenticateLogin = raisesUnexpectedException\n\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n\n        d1 = self.connected.addCallback(strip(login))\n\n        d1.addErrback(self.assertClientFailureMessage, b\"Server error: Whoops\")\n\n        @d1.addCallback\n        def assertErrorLogged(_):\n            self.assertTrue(self.flushLoggedErrors(UnexpectedException))\n\n        d1.addErrback(self._ebGeneral)\n        d1.addBoth(self._cbStopClient)\n\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        return d.addCallback(self._cbTestFailedLogin)\n\n\n    def testLoginRequiringQuoting(self):\n        self.server.checker.users = {b'{test}user': b'{test}password'}\n\n        def login():\n            d = self.client.login(b'{test}user', b'{test}password')\n            d.addErrback(log.err, \"Problem with \" + str(self))\n            d.addCallback(self._cbStopClient)\n\n        d1 = self.connected.addCallback(strip(login)).addErrback(self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d.addCallback(self._cbTestLoginRequiringQuoting)\n\n\n    def _cbTestLoginRequiringQuoting(self, ignored):\n        self.assertEqual(self.server.account, SimpleServer.theAccount)\n        self.assertEqual(self.server.state, 'auth')\n\n\n    def testNamespace(self):\n        self.namespaceArgs = None\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def namespace():\n            def gotNamespace(args):\n                self.namespaceArgs = args\n                self._cbStopClient(None)\n            return self.client.namespace().addCallback(gotNamespace)\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(namespace))\n        d1.addErrback(self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n\n        @d.addCallback\n        def assertAllPairsNativeStrings(ignored):\n            for namespaces in self.namespaceArgs:\n                for pair in namespaces:\n                    for value in pair:\n                        self.assertIsInstance(value, str)\n            return self.namespaceArgs\n\n        d.addCallback(self.assertEqual, [[['', '/']], [], []])\n        return d\n\n\n    def test_mailboxWithoutNamespace(self):\n        \"\"\"\n        A mailbox that does not provide L{INamespacePresenter} returns\n        empty L{list}s for its personal, shared, and user namespaces.\n        \"\"\"\n        self.server.theAccount = AccountWithoutNamespaces(b'testuser')\n        self.namespaceArgs = None\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def namespace():\n            def gotNamespace(args):\n                self.namespaceArgs = args\n                self._cbStopClient(None)\n            return self.client.namespace().addCallback(gotNamespace)\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(namespace))\n        d1.addErrback(self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        d.addCallback(lambda _: self.namespaceArgs)\n        d.addCallback(self.assertEqual, [[], [], []])\n        return d\n\n\n    def testSelect(self):\n        SimpleServer.theAccount.addMailbox('test-mailbox')\n        self.selectedArgs = None\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def select():\n            def selected(args):\n                self.selectedArgs = args\n                self._cbStopClient(None)\n            d = self.client.select('test-mailbox')\n            d.addCallback(selected)\n            return d\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(select))\n        d1.addErrback(self._ebGeneral)\n        d2 = self.loopback()\n        return defer.gatherResults([d1, d2]).addCallback(self._cbTestSelect)\n\n\n    def test_selectWithoutMailbox(self):\n        \"\"\"\n        A client that selects a mailbox that does not exist receives a\n        C{NO} response.\n        \"\"\"\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def select():\n            return self.client.select('test-mailbox')\n\n        self.connected.addCallback(strip(login))\n        self.connected.addCallback(strip(select))\n        self.connected.addErrback(self.assertClientFailureMessage,\n                                  b\"No such mailbox\")\n        self.connected.addCallback(self._cbStopClient)\n        self.connected.addErrback(self._ebGeneral)\n\n        connectionComplete = defer.gatherResults(\n            [self.connected, self.loopback()]\n        )\n\n        @connectionComplete.addCallback\n        def assertNoMailboxSelected(_):\n            self.assertIsNone(self.server.mbox)\n\n        return connectionComplete\n\n\n    def _cbTestSelect(self, ignored):\n        mbox = SimpleServer.theAccount.mailboxes['TEST-MAILBOX']\n        self.assertEqual(self.server.mbox, mbox)\n        self.assertEqual(self.selectedArgs, {\n            'EXISTS': 9, 'RECENT': 3, 'UIDVALIDITY': 42,\n            'FLAGS': ('\\\\Flag1', 'Flag2', '\\\\AnotherSysFlag', 'LastFlag'),\n            'READ-WRITE': True\n        })\n\n\n    def test_examine(self):\n        \"\"\"\n        L{IMAP4Client.examine} issues an I{EXAMINE} command to the server and\n        returns a L{Deferred} which fires with a C{dict} with as many of the\n        following keys as the server includes in its response: C{'FLAGS'},\n        C{'EXISTS'}, C{'RECENT'}, C{'UNSEEN'}, C{'READ-WRITE'}, C{'READ-ONLY'},\n        C{'UIDVALIDITY'}, and C{'PERMANENTFLAGS'}.\n\n        Unfortunately the server doesn't generate all of these so it's hard to\n        test the client's handling of them here.  See\n        L{IMAP4ClientExamineTests} below.\n\n        See U{RFC 3501<http://www.faqs.org/rfcs/rfc3501.html>}, section 6.3.2,\n        for details.\n        \"\"\"\n        SimpleServer.theAccount.addMailbox('test-mailbox')\n        self.examinedArgs = None\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def examine():\n            def examined(args):\n                self.examinedArgs = args\n                self._cbStopClient(None)\n            d = self.client.examine('test-mailbox')\n            d.addCallback(examined)\n            return d\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(examine))\n        d1.addErrback(self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        return d.addCallback(self._cbTestExamine)\n\n\n    def _cbTestExamine(self, ignored):\n        mbox = SimpleServer.theAccount.mailboxes['TEST-MAILBOX']\n        self.assertEqual(self.server.mbox, mbox)\n        self.assertEqual(self.examinedArgs, {\n            'EXISTS': 9, 'RECENT': 3, 'UIDVALIDITY': 42,\n            'FLAGS': ('\\\\Flag1', 'Flag2', '\\\\AnotherSysFlag', 'LastFlag'),\n            'READ-WRITE': False})\n\n\n    def testCreate(self):\n        succeed = ('testbox', 'test/box', 'test/', 'test/box/box', 'INBOX')\n        fail = ('testbox', 'test/box')\n\n        def cb(): self.result.append(1)\n\n        def eb(failure): self.result.append(0)\n\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n\n        def create():\n            for name in succeed + fail:\n                d = self.client.create(name)\n                d.addCallback(strip(cb)).addErrback(eb)\n            d.addCallbacks(self._cbStopClient, self._ebGeneral)\n\n        self.result = []\n        d1 = self.connected.addCallback(strip(login)).addCallback(strip(create))\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        return d.addCallback(self._cbTestCreate, succeed, fail)\n\n\n    def _cbTestCreate(self, ignored, succeed, fail):\n        self.assertEqual(self.result, [1] * len(succeed) + [0] * len(fail))\n        mbox = sorted(SimpleServer.theAccount.mailboxes)\n        answers = sorted(['inbox', 'testbox', 'test/box', 'test',\n                          'test/box/box'])\n        self.assertEqual(mbox, [a.upper() for a in answers])\n\n\n    def testDelete(self):\n        SimpleServer.theAccount.addMailbox('delete/me')\n\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def delete():\n            return self.client.delete('delete/me')\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(delete), self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        d.addCallback(\n            lambda _:\n            self.assertEqual(list(SimpleServer.theAccount.mailboxes), []))\n        return d\n\n\n    def testDeleteWithInferiorHierarchicalNames(self):\n        \"\"\"\n        Attempting to delete a mailbox with hierarchically inferior\n        names fails with an informative error.\n\n        @see: U{https://tools.ietf.org/html/rfc3501#section-6.3.4}\n\n        @return: A L{Deferred} with assertions.\n        \"\"\"\n        SimpleServer.theAccount.addMailbox('delete')\n        SimpleServer.theAccount.addMailbox('delete/me')\n\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def delete():\n            return self.client.delete('delete')\n\n        def assertIMAPException(failure):\n            failure.trap(imap4.IMAP4Exception)\n            self.assertEqual(\n                str(failure.value),\n                str(b'Name \"DELETE\" has inferior hierarchical names'),\n            )\n\n        loggedIn = self.connected.addCallback(strip(login))\n        loggedIn.addCallbacks(strip(delete), self._ebGeneral)\n        loggedIn.addErrback(assertIMAPException)\n        loggedIn.addCallbacks(self._cbStopClient)\n\n        loopedBack  = self.loopback()\n        d = defer.gatherResults([loggedIn, loopedBack])\n        d.addCallback(\n            lambda _:\n            self.assertEqual(sorted(SimpleServer.theAccount.mailboxes),\n                             [\"DELETE\", \"DELETE/ME\"]))\n        return d\n\n\n    def testIllegalInboxDelete(self):\n        self.stashed = None\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def delete():\n            return self.client.delete('inbox')\n        def stash(result):\n            self.stashed = result\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(delete), self._ebGeneral)\n        d1.addBoth(stash)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        d.addCallback(lambda _: self.assertTrue(isinstance(self.stashed,\n                                                           failure.Failure)))\n        return d\n\n\n    def testNonExistentDelete(self):\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def delete():\n            return self.client.delete('delete/me')\n        def deleteFailed(failure):\n            self.failure = failure\n\n        self.failure = None\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(delete)).addErrback(deleteFailed)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        d.addCallback(lambda _: self.assertEqual(str(self.failure.value),\n                                                 str(b'No such mailbox')))\n        return d\n\n\n    def testIllegalDelete(self):\n        m = SimpleMailbox()\n        m.flags = (r'\\Noselect',)\n        SimpleServer.theAccount.addMailbox('delete', m)\n        SimpleServer.theAccount.addMailbox('delete/me')\n\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def delete():\n            return self.client.delete('delete')\n        def deleteFailed(failure):\n            self.failure = failure\n\n        self.failure = None\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(delete)).addErrback(deleteFailed)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        expected = str(b\"Hierarchically inferior mailboxes exist \"\n                       b\"and \\\\Noselect is set\")\n        d.addCallback(lambda _:\n                      self.assertEqual(str(self.failure.value), expected))\n        return d\n\n\n    def testRename(self):\n        SimpleServer.theAccount.addMailbox('oldmbox')\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def rename():\n            return self.client.rename(b'oldmbox', b'newname')\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(rename), self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        d.addCallback(lambda _:\n                      self.assertEqual(\n                          list(SimpleServer.theAccount.mailboxes.keys()),\n                          ['NEWNAME']\n                      ))\n        return d\n\n\n    def testIllegalInboxRename(self):\n        self.stashed = None\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def rename():\n            return self.client.rename('inbox', 'frotz')\n        def stash(stuff):\n            self.stashed = stuff\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(rename), self._ebGeneral)\n        d1.addBoth(stash)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        d.addCallback(lambda _:\n                      self.assertTrue(isinstance(self.stashed, failure.Failure)))\n        return d\n\n\n    def testHierarchicalRename(self):\n        SimpleServer.theAccount.create('oldmbox/m1')\n        SimpleServer.theAccount.create('oldmbox/m2')\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def rename():\n            return self.client.rename('oldmbox', 'newname')\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(rename), self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        return d.addCallback(self._cbTestHierarchicalRename)\n\n\n    def _cbTestHierarchicalRename(self, ignored):\n        mboxes = SimpleServer.theAccount.mailboxes.keys()\n        expected = ['newname', 'newname/m1', 'newname/m2']\n        mboxes = list(sorted(mboxes))\n        self.assertEqual(mboxes, [s.upper() for s in expected])\n\n\n    def testSubscribe(self):\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def subscribe():\n            return self.client.subscribe('this/mbox')\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(subscribe), self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        d.addCallback(lambda _:\n                      self.assertEqual(SimpleServer.theAccount.subscriptions,\n                                        ['THIS/MBOX']))\n        return d\n\n\n    def testUnsubscribe(self):\n        SimpleServer.theAccount.subscriptions = ['THIS/MBOX', 'THAT/MBOX']\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def unsubscribe():\n            return self.client.unsubscribe('this/mbox')\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(unsubscribe), self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        d.addCallback(lambda _:\n                      self.assertEqual(SimpleServer.theAccount.subscriptions,\n                                        ['THAT/MBOX']))\n        return d\n\n\n    def _listSetup(self, f):\n        SimpleServer.theAccount.addMailbox('root/subthing')\n        SimpleServer.theAccount.addMailbox('root/another-thing')\n        SimpleServer.theAccount.addMailbox('non-root/subthing')\n\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def listed(answers):\n            self.listed = answers\n\n        self.listed = None\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(f), self._ebGeneral)\n        d1.addCallbacks(listed, self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        return defer.gatherResults([d1, d2]).addCallback(lambda _: self.listed)\n\n\n    def assertListDelimiterAndMailboxAreStrings(self, results):\n        \"\"\"\n        Assert a C{LIST} response's delimiter and mailbox are native\n        strings.\n\n        @param results: A list of tuples as returned by\n            L{IMAP4Client.list} or L{IMAP4Client.lsub}.\n        \"\"\"\n        for result in results:\n            self.assertIsInstance(result[1], str,\n                                  \"delimiter %r is not a str\")\n            self.assertIsInstance(result[2], str,\n                                  \"mailbox %r is not a str\")\n        return results\n\n\n    def testList(self):\n        def mailboxList():\n            return self.client.list('root', '%')\n        d = self._listSetup(mailboxList)\n        @d.addCallback\n        def assertListContents(listed):\n            expectedContents = [\n                (sorted(SimpleMailbox.flags), \"/\", \"ROOT/SUBTHING\"),\n                (sorted(SimpleMailbox.flags), \"/\", \"ROOT/ANOTHER-THING\")\n            ]\n\n            for _ in range(2):\n                flags, delimiter, mailbox = listed.pop(0)\n                self.assertIn(\n                    (sorted(flags), delimiter, mailbox),\n                    expectedContents,\n                )\n\n            self.assertFalse(listed,\n                             \"More results than expected: {!r}\".format(listed))\n\n        return d\n\n\n    def testLSub(self):\n        SimpleServer.theAccount.subscribe('ROOT/SUBTHING')\n        def lsub():\n            return self.client.lsub('root', '%')\n        d = self._listSetup(lsub)\n        d.addCallback(self.assertListDelimiterAndMailboxAreStrings)\n        d.addCallback(self.assertEqual,\n                      [(SimpleMailbox.flags, \"/\", \"ROOT/SUBTHING\")])\n        return d\n\n\n    def testStatus(self):\n        SimpleServer.theAccount.addMailbox('root/subthing')\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def status():\n            return self.client.status('root/subthing', 'MESSAGES', 'UIDNEXT', 'UNSEEN')\n        def statused(result):\n            self.statused = result\n\n        self.statused = None\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(status), self._ebGeneral)\n        d1.addCallbacks(statused, self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        d.addCallback(lambda _: self.assertEqual(\n            self.statused,\n            {'MESSAGES': 9, 'UIDNEXT': b'10', 'UNSEEN': 4}\n        ))\n        return d\n\n\n    def testFailedStatus(self):\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def status():\n            return self.client.status('root/nonexistent',\n                                      'MESSAGES', 'UIDNEXT', 'UNSEEN')\n        def statused(result):\n            self.statused = result\n        def failed(failure):\n            self.failure = failure\n\n        self.statused = self.failure = None\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(status), self._ebGeneral)\n        d1.addCallbacks(statused, failed)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        return defer.gatherResults([d1, d2]).addCallback(self._cbTestFailedStatus)\n\n\n    def _cbTestFailedStatus(self, ignored):\n        self.assertEqual(\n            self.statused, None\n        )\n        self.assertEqual(\n            self.failure.value.args,\n            (b'Could not open mailbox',)\n        )\n\n\n    def testFullAppend(self):\n        infile = util.sibpath(__file__, 'rfc822.message')\n        SimpleServer.theAccount.addMailbox('root/subthing')\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n\n        @defer.inlineCallbacks\n        def append():\n            with open(infile, \"rb\") as message:\n                result = yield self.client.append(\n                    'root/subthing',\n                    message,\n                    ('\\\\SEEN', '\\\\DELETED'),\n                    'Tue, 17 Jun 2003 11:22:16 -0600 (MDT)',\n                )\n                defer.returnValue(result)\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(append), self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n\n        d = defer.gatherResults([d1, d2])\n\n        return d.addCallback(self._cbTestFullAppend, infile)\n\n\n    def _cbTestFullAppend(self, ignored, infile):\n        mb = SimpleServer.theAccount.mailboxes['ROOT/SUBTHING']\n        self.assertEqual(1, len(mb.messages))\n        self.assertEqual(\n            (['\\\\SEEN', '\\\\DELETED'],\n             b'Tue, 17 Jun 2003 11:22:16 -0600 (MDT)',\n             0),\n            mb.messages[0][1:]\n        )\n        with open(infile, \"rb\") as f:\n            self.assertEqual(f.read(), mb.messages[0][0].getvalue())\n\n\n    def testPartialAppend(self):\n        infile = util.sibpath(__file__, 'rfc822.message')\n        SimpleServer.theAccount.addMailbox('PARTIAL/SUBTHING')\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n\n        @defer.inlineCallbacks\n        def append():\n            with open(infile, 'rb') as message:\n                result = yield self.client.sendCommand(\n                    imap4.Command(\n                        b'APPEND',\n                        # Using networkString is cheating!  In this\n                        # particular case the mailbox name happens to\n                        # be ASCII.  In real code, the mailbox would\n                        # be encoded with imap4-utf-7.\n                        networkString(\n                            'PARTIAL/SUBTHING '\n                            '(\\\\SEEN) \"Right now\" '\n                            '{%d}' % (os.path.getsize(infile),)\n                        ),\n                        (),\n                        self.client._IMAP4Client__cbContinueAppend, message\n                    )\n                )\n                defer.returnValue(result)\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(append), self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        return d.addCallback(self._cbTestPartialAppend, infile)\n\n\n    def _cbTestPartialAppend(self, ignored, infile):\n        mb = SimpleServer.theAccount.mailboxes['PARTIAL/SUBTHING']\n        self.assertEqual(1, len(mb.messages))\n        self.assertEqual(\n            (['\\\\SEEN'], b'Right now', 0),\n            mb.messages[0][1:]\n        )\n        with open(infile, 'rb') as f:\n            self.assertEqual(f.read(), mb.messages[0][0].getvalue())\n\n\n    def _testCheck(self):\n        SimpleServer.theAccount.addMailbox(b'root/subthing')\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def select():\n            return self.client.select(b'root/subthing')\n        def check():\n            return self.client.check()\n\n        d = self.connected.addCallback(strip(login))\n        d.addCallbacks(strip(select), self._ebGeneral)\n        d.addCallbacks(strip(check), self._ebGeneral)\n        d.addCallbacks(self._cbStopClient, self._ebGeneral)\n        return self.loopback()\n\n\n    def test_check(self):\n        \"\"\"\n        Trigger the L{imap.IMAP4Server._cbSelectWork} callback\n        by selecting an mbox.\n        \"\"\"\n        return self._testCheck()\n\n\n    def test_checkFail(self):\n        \"\"\"\n        Trigger the L{imap.IMAP4Server._ebSelectWork} errback\n        by failing when we select an mbox.\n        \"\"\"\n        def failSelect(self, name, rw=1):\n            raise imap4.IllegalMailboxEncoding(\"encoding\")\n\n        def checkResponse(ignore):\n            failures = self.flushLoggedErrors()\n            self.assertEqual(failures[1].value.args[0],\n                             b'SELECT failed: Server error')\n\n        self.patch(Account, \"select\", failSelect)\n        d = self._testCheck()\n        return d.addCallback(checkResponse)\n\n\n    def testClose(self):\n        m = SimpleMailbox()\n        m.messages = [\n            (b'Message 1', ('\\\\Deleted', 'AnotherFlag'), None, 0),\n            (b'Message 2', ('AnotherFlag',), None, 1),\n            (b'Message 3', ('\\\\Deleted',), None, 2),\n        ]\n        SimpleServer.theAccount.addMailbox('mailbox', m)\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def select():\n            return self.client.select(b'mailbox')\n        def close():\n            return self.client.close()\n\n        d = self.connected.addCallback(strip(login))\n        d.addCallbacks(strip(select), self._ebGeneral)\n        d.addCallbacks(strip(close), self._ebGeneral)\n        d.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        return defer.gatherResults([d, d2]).addCallback(self._cbTestClose, m)\n\n\n    def _cbTestClose(self, ignored, m):\n        self.assertEqual(len(m.messages), 1)\n        self.assertEqual(\n            m.messages[0], (b'Message 2', ('AnotherFlag',), None, 1))\n        self.assertTrue(m.closed)\n\n\n    def testExpunge(self):\n        m = SimpleMailbox()\n        m.messages = [\n            (b'Message 1', ('\\\\Deleted', 'AnotherFlag'), None, 0),\n            (b'Message 2', ('AnotherFlag',), None, 1),\n            (b'Message 3', ('\\\\Deleted',), None, 2),\n        ]\n        SimpleServer.theAccount.addMailbox('mailbox', m)\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n\n\n        def select():\n            return self.client.select('mailbox')\n\n\n        def expunge():\n            return self.client.expunge()\n\n\n        def expunged(results):\n            self.assertFalse(self.server.mbox is None)\n            self.results = results\n\n        self.results = None\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallbacks(strip(select), self._ebGeneral)\n        d1.addCallbacks(strip(expunge), self._ebGeneral)\n        d1.addCallbacks(expunged, self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        return d.addCallback(self._cbTestExpunge, m)\n\n\n    def _cbTestExpunge(self, ignored, m):\n        self.assertEqual(len(m.messages), 1)\n        self.assertEqual(m.messages[0], (b'Message 2', ('AnotherFlag',), None, 1))\n\n        self.assertEqual(self.results, [0, 2])\n\n\n\nclass IMAP4ServerParsingTests(unittest.SynchronousTestCase):\n    \"\"\"\n    Test L{imap4.IMAP4Server}'s command parsing.\n    \"\"\"\n\n    def setUp(self):\n        self.transport = StringTransport()\n        self.server = imap4.IMAP4Server()\n        self.server.makeConnection(self.transport)\n        self.transport.clear()\n\n\n    def tearDown(self):\n        self.server.connectionLost(failure.Failure(error.ConnectionDone()))\n\n\n    def test_parseMethodExceptionLogged(self):\n        \"\"\"\n        L{imap4.IMAP4Server} logs exceptions raised by parse methods.\n        \"\"\"\n\n        class UnhandledException(Exception):\n            \"\"\"\n            An unhandled exception.\n            \"\"\"\n\n        def raisesValueError(line):\n            raise UnhandledException\n\n        self.server.parseState = \"command\"\n        self.server.parse_command = raisesValueError\n\n        self.server.lineReceived(b\"invalid\")\n\n        self.assertTrue(self.flushLoggedErrors(UnhandledException))\n\n\n    def test_missingCommand(self):\n        \"\"\"\n        L{imap4.IMAP4Server.parse_command} sends a C{BAD} response to\n        a line that includes a tag but no command.\n        \"\"\"\n        self.server.parse_command(b\"001\")\n\n        self.assertEqual(self.transport.value(),\n                         b\"001 BAD Missing command\\r\\n\")\n\n        self.server.connectionLost(\n            failure.Failure(error.ConnectionDone(\"Done\")),\n        )\n\n\n    def test_emptyLine(self):\n        \"\"\"\n        L{imap4.IMAP4Server.parse_command} sends a C{BAD} response to\n        an empty line.\n        \"\"\"\n        self.server.parse_command(b\"\")\n\n        self.assertEqual(self.transport.value(), b\"* BAD Null command\\r\\n\")\n\n\n    def assertParseExceptionResponse(self,\n                                     exception, tag, expectedResponse):\n        \"\"\"\n        Assert that the given exception results in the expected\n        response.\n\n        @param exception: The exception to raise.\n        @type exception: L{Exception}\n\n        @param tag: The IMAP tag.\n\n        @type: L{bytes}\n\n        @param expectedResponse: The expected bad response.\n        @type expectedResponse: L{bytes}\n        \"\"\"\n        def raises(tag, cmd, rest):\n            raise exception\n\n        self.server.dispatchCommand = raises\n\n        self.server.parse_command(b' '.join([tag, b\"invalid\"]))\n\n        self.assertEqual(self.transport.value(),\n                         b' '.join([tag, expectedResponse]))\n\n\n    def test_parsingRaisesIllegalClientResponse(self):\n        \"\"\"\n        When a parsing method raises L{IllegalClientResponse}, the\n        server sends a C{BAD} response.\n        \"\"\"\n        self.assertParseExceptionResponse(\n            imap4.IllegalClientResponse(\"client response\"),\n            b\"001\", b\"BAD Illegal syntax: client response\\r\\n\",\n        )\n\n\n    def test_parsingRaisesIllegalOperationResponse(self):\n        \"\"\"\n        When a parsing method raises L{IllegalOperation}, the server\n        sends a C{NO} response.\n        \"\"\"\n        self.assertParseExceptionResponse(\n            imap4.IllegalOperation(\"operation\"),\n            b\"001\", b\"NO Illegal operation: operation\\r\\n\",\n        )\n\n\n    def test_parsingRaisesIllegalMailboxEncoding(self):\n        \"\"\"\n        When a parsing method raises L{IllegalMailboxEncoding}, the\n        server sends a C{NO} response.\n        \"\"\"\n        self.assertParseExceptionResponse(\n            imap4.IllegalMailboxEncoding(\"encoding\"),\n            b\"001\", b\"NO Illegal mailbox name: encoding\\r\\n\",\n        )\n\n\n    def test_unsupportedCommand(self):\n        \"\"\"\n        L{imap4.IMAP4Server} responds to an unsupported command with a\n        C{BAD} response.\n        \"\"\"\n        self.server.lineReceived(b\"001 HULLABALOO\")\n        self.assertEqual(self.transport.value(),\n                         b\"001 BAD Unsupported command\\r\\n\")\n\n\n    def test_tooManyArgumentsForCommand(self):\n        \"\"\"\n        L{imap4.IMAP4Server} responds with a C{BAD} response to a\n        command with more arguments than expected.\n        \"\"\"\n        self.server.lineReceived(b\"001 LOGIN A B C\")\n        self.assertEqual(\n            self.transport.value(),\n            (b\"001 BAD Illegal syntax:\" +\n             b\" Too many arguments for command: \" +\n             repr(b'C').encode(\"utf-8\") +\n             b\"\\r\\n\"\n            )\n        )\n\n\n    def assertCommandExceptionResponse(self,\n                                        exception, tag, expectedResponse):\n        \"\"\"\n        Assert that the given exception results in the expected\n        response.\n\n        @param exception: The exception to raise.\n        @type exception: L{Exception}\n\n        @param: The IMAP tag.\n\n        @type: L{bytes}\n\n        @param expectedResponse: The expected bad response.\n        @type expectedResponse: L{bytes}\n        \"\"\"\n        def raises(serverInstance, tag, user, passwd):\n            raise exception\n\n        self.assertEqual(self.server.state, \"unauth\")\n\n        self.server.unauth_LOGIN = (raises,) + self.server.unauth_LOGIN[1:]\n\n        self.server.dispatchCommand(tag, b\"LOGIN\", b\"user passwd\")\n\n        self.assertEqual(self.transport.value(),\n                         b' '.join([tag, expectedResponse]))\n\n\n    def test_commandRaisesIllegalClientResponse(self):\n        \"\"\"\n        When a command raises L{IllegalClientResponse}, the\n        server sends a C{BAD} response.\n        \"\"\"\n        self.assertCommandExceptionResponse(\n            imap4.IllegalClientResponse(\"client response\"),\n            b\"001\", b\"BAD Illegal syntax: client response\\r\\n\",\n        )\n\n\n    def test_commandRaisesIllegalOperationResponse(self):\n        \"\"\"\n        When a command raises L{IllegalOperation}, the server sends a\n        C{NO} response.\n        \"\"\"\n        self.assertCommandExceptionResponse(\n            imap4.IllegalOperation(\"operation\"),\n            b\"001\", b\"NO Illegal operation: operation\\r\\n\",\n        )\n\n\n    def test_commandRaisesIllegalMailboxEncoding(self):\n        \"\"\"\n        When a command raises L{IllegalMailboxEncoding}, the server\n        sends a C{NO} response.\n        \"\"\"\n        self.assertCommandExceptionResponse(\n            imap4.IllegalMailboxEncoding(\"encoding\"),\n            b\"001\", b\"NO Illegal mailbox name: encoding\\r\\n\",\n        )\n\n\n    def test_commandRaisesUnhandledException(self):\n        \"\"\"\n        Wehn a command raises an unhandled exception, the server sends\n        a C{BAD} response and logs the exception.\n        \"\"\"\n\n        class UnhandledException(Exception):\n            \"\"\"\n            An unhandled exception.\n            \"\"\"\n\n        self.assertCommandExceptionResponse(\n            UnhandledException(\"unhandled\"),\n            b\"001\", b\"BAD Server error: unhandled\\r\\n\",\n        )\n\n        self.assertTrue(self.flushLoggedErrors(UnhandledException))\n\n\n    def test_stringLiteralTooLong(self):\n        \"\"\"\n        A string literal whose length exceeds the maximum allowed\n        length results in a C{BAD} response.\n        \"\"\"\n        self.server._literalStringLimit = 4\n        self.server.lineReceived(b\"001 LOGIN {5}\\r\\n\")\n\n        self.assertEqual(self.transport.value(),\n                         b\"001 BAD Illegal syntax: Literal too long!\"\n                         b\" I accept at most 4 octets\\r\\n\")\n\n\n    def test_arg_astringEmptyLine(self):\n        \"\"\"\n        An empty string argument raises L{imap4.IllegalClientResponse}.\n        \"\"\"\n        for empty in [b\"\", b\"\\r\\n\", b\" \"]:\n            self.assertRaises(imap4.IllegalClientResponse,\n                              self.server.arg_astring, empty)\n\n\n    def test_arg_astringUnmatchedQuotes(self):\n        \"\"\"\n        An unmatched quote in a string argument raises\n        L{imap4.IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_astring, b'\"open')\n\n\n    def test_arg_astringUnmatchedLiteralBraces(self):\n        \"\"\"\n        An unmatched brace in a string literal's size raises\n        L{imap4.IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_astring, b'{0')\n\n\n    def test_arg_astringInvalidLiteralSize(self):\n        \"\"\"\n        A non-integral string literal size raises\n        L{imap4.IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_astring, b'{[object Object]}')\n\n\n    def test_arg_atomEmptyLine(self):\n        \"\"\"\n        An empty atom raises L{IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_atom, b\"\")\n\n\n    def test_arg_atomMalformedAtom(self):\n        \"\"\"\n        A malformed atom raises L{IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_atom, b\" not an atom \")\n\n\n    def test_arg_plistEmptyLine(self):\n        \"\"\"\n        An empty parenthesized list raises L{IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_plist, b\"\")\n\n\n    def test_arg_plistUnmatchedParentheses(self):\n        \"\"\"\n        A parenthesized with unmatched parentheses raises\n        L{IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_plist, b\"(foo\")\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_plist, b\"foo)\")\n\n\n    def test_arg_literalEmptyLine(self):\n        \"\"\"\n        An empty file literal raises L{IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_literal, b\"\")\n\n\n    def test_arg_literalUnmatchedBraces(self):\n        \"\"\"\n        A literal with unmatched braces raises\n        L{IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_literal, b\"{10\")\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_literal, b\"10}\")\n\n\n    def test_arg_literalInvalidLiteralSize(self):\n        \"\"\"\n        A non-integral literal size raises\n        L{imap4.IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_literal, b'{[object Object]}')\n\n\n    def test_arg_seqsetReturnsRest(self):\n        \"\"\"\n        A sequence set returns the unparsed portion of a line.\n        \"\"\"\n        sequence = b\"1:* blah blah blah\"\n        _, rest = self.server.arg_seqset(sequence)\n        self.assertEqual(rest, b\"blah blah blah\")\n\n\n    def test_arg_seqsetInvalidSequence(self):\n        \"\"\"\n        An invalid sequence raises L{imap4.IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_seqset, b\"x:y\")\n\n\n    def test_arg_flaglistOneFlag(self):\n        \"\"\"\n        A single flag that is not contained in a list is parsed.\n        \"\"\"\n        flag = b\"flag\"\n        parsed, rest = self.server.arg_flaglist(flag)\n        self.assertEqual(parsed, [flag])\n        self.assertFalse(rest)\n\n\n    def test_arg_flaglistMismatchedParentehses(self):\n        \"\"\"\n        A list of flags with unmatched parentheses raises\n        L{imap4.IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(\n            imap4.IllegalClientResponse,\n            self.server.arg_flaglist, b\"(invalid\",\n        )\n\n\n    def test_arg_flaglistMalformedFlag(self):\n        \"\"\"\n        A list of flags that contains a malformed flag raises\n        L{imap4.IllegalClientResponse}.\n        \"\"\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_flaglist, b\"(first \\x00)\")\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.arg_flaglist, b\"(first \\x00second)\")\n\n\n    def test_opt_plistMissingOpenParenthesis(self):\n        \"\"\"\n        A line that does not begin with an open parenthesis (C{(}) is\n        parsed as L{None}, and the remainder is the whole line.\n        \"\"\"\n        line = b\"not (\"\n        plist, remainder = self.server.opt_plist(line)\n        self.assertIsNone(plist)\n        self.assertEqual(remainder, line)\n\n\n    def test_opt_datetimeMissingOpenQuote(self):\n        \"\"\"\n        A line that does not begin with a double quote (C{\"}) is\n        parsed as L{None}, and the remainder is the whole line.\n        \"\"\"\n        line = b'not \"'\n        dt, remainder = self.server.opt_datetime(line)\n        self.assertIsNone(dt)\n        self.assertEqual(remainder, line)\n\n\n    def test_opt_datetimeMissingCloseQuote(self):\n        \"\"\"\n        A line that does not have a closing double quote (C{\"}) raises\n        L{imap4.IllegalClientResponse}.\n        \"\"\"\n        line = b'\"21-Jul-2017 19:37:07 -0700'\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.opt_datetime, line)\n\n\n    def test_opt_charsetMissingIdentifier(self):\n        \"\"\"\n        A line that contains C{CHARSET} but no character set\n        identifier raises L{imap4.IllegalClientResponse}.\n        \"\"\"\n        line = b\"CHARSET\"\n        self.assertRaises(imap4.IllegalClientResponse,\n                          self.server.opt_charset, line)\n\n\n    def test_opt_charsetEndOfLine(self):\n        \"\"\"\n        A line that ends with a C{CHARSET} identifier is parsed as\n        that identifier, and the remainder is the empty string.\n        \"\"\"\n        line = b\"CHARSET UTF-8\"\n        identifier, remainder = self.server.opt_charset(line)\n        self.assertEqual(identifier, b\"UTF-8\")\n        self.assertEqual(remainder, b\"\")\n\n\n    def test_opt_charsetWithRemainder(self):\n        \"\"\"\n        A line that has additional data after a C{CHARSET} identifier\n        is parsed as that identifier, and the remainder is that\n        additional data.\n        \"\"\"\n        line = b\"CHARSET UTF-8 remainder\"\n        identifier, remainder = self.server.opt_charset(line)\n        self.assertEqual(identifier, b\"UTF-8\")\n        self.assertEqual(remainder, b\"remainder\")\n\n\n\nclass IMAP4ServerSearchTests(IMAP4HelperMixin, unittest.TestCase):\n    \"\"\"\n    Tests for the behavior of the search_* functions in L{imap4.IMAP4Server}.\n    \"\"\"\n    def setUp(self):\n        IMAP4HelperMixin.setUp(self)\n        self.earlierQuery = [\"10-Dec-2009\"]\n        self.sameDateQuery = [\"13-Dec-2009\"]\n        self.laterQuery = [\"16-Dec-2009\"]\n        self.seq = 0\n        self.msg = FakeyMessage({\"date\" : \"Mon, 13 Dec 2009 21:25:10 GMT\"}, [],\n                                '13 Dec 2009 00:00:00 GMT', '', 1234, None)\n\n\n    def test_searchSentBefore(self):\n        \"\"\"\n        L{imap4.IMAP4Server.search_SENTBEFORE} returns True if the message date\n        is earlier than the query date.\n        \"\"\"\n        self.assertFalse(\n            self.server.search_SENTBEFORE(self.earlierQuery, self.seq, self.msg))\n        self.assertTrue(\n            self.server.search_SENTBEFORE(self.laterQuery, self.seq, self.msg))\n\n\n    def test_searchWildcard(self):\n        \"\"\"\n        L{imap4.IMAP4Server.search_UID} returns True if the message UID is in\n        the search range.\n        \"\"\"\n        self.assertFalse(\n            self.server.search_UID([b'2:3'], self.seq, self.msg, (1, 1234)))\n        # 2:* should get translated to 2:<max UID> and then to 1:2\n        self.assertTrue(\n            self.server.search_UID([b'2:*'], self.seq, self.msg, (1, 1234)))\n        self.assertTrue(\n            self.server.search_UID([b'*'], self.seq, self.msg, (1, 1234)))\n\n\n    def test_searchWildcardHigh(self):\n        \"\"\"\n        L{imap4.IMAP4Server.search_UID} should return True if there is a\n        wildcard, because a wildcard means \"highest UID in the mailbox\".\n        \"\"\"\n        self.assertTrue(\n            self.server.search_UID([b'1235:*'], self.seq, self.msg, (1234, 1)))\n\n\n    def test_reversedSearchTerms(self):\n        \"\"\"\n        L{imap4.IMAP4Server.search_SENTON} returns True if the message date is\n        the same as the query date.\n        \"\"\"\n        msgset = imap4.parseIdList(b'4:2')\n        self.assertEqual(list(msgset), [2, 3, 4])\n\n\n    def test_searchSentOn(self):\n        \"\"\"\n        L{imap4.IMAP4Server.search_SENTON} returns True if the message date is\n        the same as the query date.\n        \"\"\"\n        self.assertFalse(\n            self.server.search_SENTON(self.earlierQuery, self.seq, self.msg))\n        self.assertTrue(\n            self.server.search_SENTON(self.sameDateQuery, self.seq, self.msg))\n        self.assertFalse(\n            self.server.search_SENTON(self.laterQuery, self.seq, self.msg))\n\n\n    def test_searchSentSince(self):\n        \"\"\"\n        L{imap4.IMAP4Server.search_SENTSINCE} returns True if the message date\n        is later than the query date.\n        \"\"\"\n        self.assertTrue(\n            self.server.search_SENTSINCE(self.earlierQuery, self.seq, self.msg))\n        self.assertFalse(\n            self.server.search_SENTSINCE(self.laterQuery, self.seq, self.msg))\n\n\n    def test_searchOr(self):\n        \"\"\"\n        L{imap4.IMAP4Server.search_OR} returns true if either of the two\n        expressions supplied to it returns true and returns false if neither\n        does.\n        \"\"\"\n        self.assertTrue(\n            self.server.search_OR(\n                [\"SENTSINCE\"] + self.earlierQuery +\n                [\"SENTSINCE\"] + self.laterQuery,\n            self.seq, self.msg, (None, None)))\n        self.assertTrue(\n            self.server.search_OR(\n                [\"SENTSINCE\"] + self.laterQuery +\n                [\"SENTSINCE\"] + self.earlierQuery,\n            self.seq, self.msg, (None, None)))\n        self.assertFalse(\n            self.server.search_OR(\n                [\"SENTON\"] + self.laterQuery +\n                [\"SENTSINCE\"] + self.laterQuery,\n            self.seq, self.msg, (None, None)))\n\n\n    def test_searchNot(self):\n        \"\"\"\n        L{imap4.IMAP4Server.search_NOT} returns the negation of the result\n        of the expression supplied to it.\n        \"\"\"\n        self.assertFalse(self.server.search_NOT(\n                [\"SENTSINCE\"] + self.earlierQuery, self.seq, self.msg,\n                (None, None)))\n        self.assertTrue(self.server.search_NOT(\n                [\"SENTON\"] + self.laterQuery, self.seq, self.msg,\n                (None, None)))\n\n\n    def test_searchBefore(self):\n        \"\"\"\n        L{imap4.IMAP4Server.search_BEFORE} returns True if the\n        internal message date is before the query date.\n        \"\"\"\n        self.assertFalse(\n            self.server.search_BEFORE(self.earlierQuery, self.seq, self.msg))\n        self.assertFalse(\n            self.server.search_BEFORE(self.sameDateQuery, self.seq, self.msg))\n        self.assertTrue(\n            self.server.search_BEFORE(self.laterQuery, self.seq, self.msg))\n\n\n    def test_searchOn(self):\n        \"\"\"\n        L{imap4.IMAP4Server.search_ON} returns True if the\n        internal message date is the same as the query date.\n        \"\"\"\n        self.assertFalse(\n            self.server.search_ON(self.earlierQuery, self.seq, self.msg))\n        self.assertFalse(\n            self.server.search_ON(self.sameDateQuery, self.seq, self.msg))\n        self.assertFalse(\n            self.server.search_ON(self.laterQuery, self.seq, self.msg))\n\n\n    def test_searchSince(self):\n        \"\"\"\n        L{imap4.IMAP4Server.search_SINCE} returns True if the\n        internal message date is greater than the query date.\n        \"\"\"\n        self.assertTrue(\n            self.server.search_SINCE(self.earlierQuery, self.seq, self.msg))\n        self.assertTrue(\n            self.server.search_SINCE(self.sameDateQuery, self.seq, self.msg))\n        self.assertFalse(\n            self.server.search_SINCE(self.laterQuery, self.seq, self.msg))\n\n\n\n@implementer(IRealm)\nclass TestRealm:\n    \"\"\"\n    A L{IRealm} for tests.\n\n    @cvar theAccount: An C{Account} instance.  Tests can set this to\n        ensure predictable account retrieval.\n    \"\"\"\n    theAccount = None\n\n    def __init__(self, accountHolder=None):\n        \"\"\"\n        Create a realm for testing.\n\n        @param accountHolder: (optional) An object whose C{theAccount}\n            attribute will be returned instead of\n            L{TestRealm.theAccount}.  Attribute access occurs on every\n            avatar request, so any modifications to\n            C{accountHolder.theAccount} will be reflected here.\n        \"\"\"\n        if accountHolder:\n            self._getAccount = lambda: accountHolder.theAccount\n        else:\n            self._getAccount = lambda: self.theAccount\n\n\n    def requestAvatar(self, avatarId, mind, *interfaces):\n        return imap4.IAccount, self._getAccount(), lambda: None\n\n\n\nclass TestChecker:\n    credentialInterfaces = (IUsernameHashedPassword, IUsernamePassword)\n\n    users = {\n        b'testuser': b'secret'\n    }\n\n    def requestAvatarId(self, credentials):\n        if credentials.username in self.users:\n            return defer.maybeDeferred(\n                credentials.checkPassword, self.users[credentials.username]\n        ).addCallback(self._cbCheck, credentials.username)\n\n\n    def _cbCheck(self, result, username):\n        if result:\n            return username\n        raise UnauthorizedLogin()\n\n\n\nclass AuthenticatorTests(IMAP4HelperMixin, unittest.TestCase):\n    def setUp(self):\n        IMAP4HelperMixin.setUp(self)\n\n        realm = TestRealm()\n        realm.theAccount = Account(b'testuser')\n        self.portal = Portal(realm)\n        self.portal.registerChecker(TestChecker())\n        self.server.portal = self.portal\n\n        self.authenticated = 0\n        self.account = realm.theAccount\n\n\n    def test_customChallengers(self):\n        \"\"\"\n        L{imap4.IMAP4Server} accepts a L{dict} mapping challenge type\n        names to L{twisted.mail.interfaces.IChallengeResponse}\n        providers.\n        \"\"\"\n\n        @implementer(IChallengeResponse, IUsernamePassword)\n        class SPECIALAuth(object):\n\n            def getChallenge(self):\n                return b'SPECIAL'\n\n\n            def setResponse(self, response):\n                self.username, self.password = response.split(None, 1)\n\n\n            def moreChallenges(self):\n                return False\n\n\n            def checkPassword(self, password):\n                self.password = self.password\n\n        special = SPECIALAuth()\n        verifyObject(IChallengeResponse, special)\n\n        server = imap4.IMAP4Server({b'SPECIAL': SPECIALAuth})\n        server.portal = self.portal\n\n        transport = StringTransport()\n        server.makeConnection(transport)\n        self.addCleanup(server.connectionLost,\n                        error.ConnectionDone(\"Connection done.\"))\n\n        self.assertIn(b\"AUTH=SPECIAL\", transport.value())\n\n        transport.clear()\n        server.dataReceived(b'001 AUTHENTICATE SPECIAL\\r\\n')\n\n        self.assertIn(base64.b64encode(special.getChallenge()),\n                      transport.value())\n\n        transport.clear()\n        server.dataReceived(base64.b64encode(b'username password') + b'\\r\\n')\n\n        self.assertEqual(transport.value(),\n                         b\"001 OK Authentication successful\\r\\n\")\n\n\n    def test_unsupportedMethod(self):\n        \"\"\"\n        An unsupported C{AUTHENTICATE} method results in a negative\n        response.\n        \"\"\"\n        server = imap4.IMAP4Server()\n        server.portal = self.portal\n\n        transport = StringTransport()\n        server.makeConnection(transport)\n        self.addCleanup(server.connectionLost,\n                        error.ConnectionDone(\"Connection done.\"))\n\n        transport.clear()\n\n        server.dataReceived(b'001 AUTHENTICATE UNKNOWN\\r\\n')\n        self.assertEqual(transport.value(),\n                         b\"001 NO AUTHENTICATE method unsupported\\r\\n\")\n\n\n    def test_missingPortal(self):\n        \"\"\"\n        An L{imap4.IMAP4Server} that is missing a L{Portal} responds\n        negatively to an authentication\n        \"\"\"\n        self.server.challengers[b'LOGIN'] = imap4.LOGINCredentials\n\n        cAuth = imap4.LOGINAuthenticator(b'testuser')\n        self.client.registerAuthenticator(cAuth)\n\n        self.server.portal = None\n\n        def auth():\n            return self.client.authenticate(b'secret')\n\n        d = self.connected.addCallback(strip(auth))\n        d.addErrback(self.assertClientFailureMessage,\n                     b\"Temporary authentication failure\")\n        d.addCallbacks(self._cbStopClient, self._ebGeneral)\n\n        return defer.gatherResults([d, self.loopback()])\n\n\n    def test_challengerRaisesException(self):\n        \"\"\"\n        When a challenger's\n        L{getChallenge<IChallengeResponse.getChallenge>} method raises\n        any exception, a C{NO} response is sent.\n        \"\"\"\n\n        @implementer(IChallengeResponse)\n        class ValueErrorAuthChallenge(object):\n            message = b\"A challenge failure\"\n\n            def getChallenge(self):\n                raise ValueError(self.message)\n\n\n            def setResponse(self, response):\n                \"\"\"\n                Never called.\n\n                @param response: See L{IChallengeResponse.setResponse}\n                \"\"\"\n\n\n            def moreChallenges(self):\n                \"\"\"\n                Never called.\n                \"\"\"\n\n        @implementer(IClientAuthentication)\n        class ValueErrorAuthenticator(object):\n\n            def getName(self):\n                return b\"ERROR\"\n\n            def challengeResponse(self, secret, chal):\n                return b\"IGNORED\"\n\n        bad = ValueErrorAuthChallenge()\n        verifyObject(IChallengeResponse, bad)\n\n        self.server.challengers[b'ERROR'] = ValueErrorAuthChallenge\n        self.client.registerAuthenticator(ValueErrorAuthenticator())\n\n        def auth():\n            return self.client.authenticate(b'secret')\n\n        d = self.connected.addCallback(strip(auth))\n        d.addErrback(self.assertClientFailureMessage,\n                     (\"Server error: \"\n                      + str(ValueErrorAuthChallenge.message)).encode('ascii'))\n        d.addCallbacks(self._cbStopClient, self._ebGeneral)\n\n        return defer.gatherResults([d, self.loopback()])\n\n\n    def test_authNotBase64(self):\n        \"\"\"\n        A client that responds with a challenge that cannot be decoded\n        as Base 64 receives an L{IllegalClientResponse}.\n        \"\"\"\n        @implementer(IChallengeResponse)\n        class NotBase64AuthChallenge(object):\n            message = b\"Malformed Response - not base64\"\n\n            def getChallenge(self):\n                return b\"SomeChallenge\"\n\n\n            def setResponse(self, response):\n                \"\"\"\n                Never called.\n\n                @param response: See L{IChallengeResponse.setResponse}\n                \"\"\"\n\n\n            def moreChallenges(self):\n                \"\"\"\n                Never called.\n                \"\"\"\n\n        notBase64 = NotBase64AuthChallenge()\n        verifyObject(IChallengeResponse, notBase64)\n\n        server = imap4.IMAP4Server()\n        server.portal = self.portal\n        server.challengers[b'NOTBASE64'] = NotBase64AuthChallenge\n\n        transport = StringTransport()\n        server.makeConnection(transport)\n        self.addCleanup(server.connectionLost,\n                        error.ConnectionDone(\"Connection done.\"))\n\n        self.assertIn(b\"AUTH=NOTBASE64\", transport.value())\n\n        transport.clear()\n        server.dataReceived(b'001 AUTHENTICATE NOTBASE64\\r\\n')\n\n        self.assertIn(base64.b64encode(notBase64.getChallenge()),\n                      transport.value())\n\n        transport.clear()\n        server.dataReceived(b'\\x00 Not base64\\r\\n')\n\n        self.assertEqual(transport.value(),\n                         b\"\".join([\n                             b\"001 NO Authentication failed: \",\n                             notBase64.message,\n                             b\"\\r\\n\"]))\n\n\n    def test_unhandledCredentials(self):\n        \"\"\"\n        A challenger that causes the login to fail\n        L{UnhandledCredentials} results in an C{NO} response.\n\n        @return: A L{Deferred} that fires when the authorization has\n            failed.\n        \"\"\"\n        realm = TestRealm()\n        portal = Portal(realm)\n        # This portal has no checkers, so all logins will fail with\n        # UnhandledCredentials\n        self.server.portal = portal\n\n        self.server.challengers[b'LOGIN'] = loginCred = imap4.LOGINCredentials\n\n        verifyClass(IChallengeResponse, loginCred)\n\n        cAuth = imap4.LOGINAuthenticator(b'testuser')\n        self.client.registerAuthenticator(cAuth)\n\n        def auth():\n            return self.client.authenticate(b'secret')\n\n        d1 = self.connected.addCallback(strip(auth))\n        d1.addErrback(self.assertClientFailureMessage,\n                      b\"Authentication failed: server misconfigured\")\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d\n\n\n    def test_unexpectedLoginFailure(self):\n        \"\"\"\n        If the portal raises an exception other than\n        L{UnauthorizedLogin} or L{UnhandledCredentials}, the server\n        responds with a C{BAD} response and the exception is logged.\n        \"\"\"\n\n        class UnexpectedException(Exception):\n            \"\"\"\n            An unexpected exception.\n            \"\"\"\n\n        class FailingChecker:\n            \"\"\"\n            A credentials checker whose L{requestAvatarId} method\n            raises L{UnexpectedException}.\n            \"\"\"\n            credentialInterfaces = (IUsernameHashedPassword,\n                                    IUsernamePassword)\n\n            def requestAvatarId(self, credentials):\n                raise UnexpectedException(\"Unexpected error.\")\n\n        realm = TestRealm()\n        portal = Portal(realm)\n        portal.registerChecker(FailingChecker())\n        self.server.portal = portal\n\n        self.server.challengers[b'LOGIN'] = loginCred = imap4.LOGINCredentials\n\n        verifyClass(IChallengeResponse, loginCred)\n\n        cAuth = imap4.LOGINAuthenticator(b'testuser')\n        self.client.registerAuthenticator(cAuth)\n\n        def auth():\n            return self.client.authenticate(b'secret')\n\n        def assertUnexpectedExceptionLogged():\n            self.assertTrue(self.flushLoggedErrors(UnexpectedException))\n\n        d1 = self.connected.addCallback(strip(auth))\n        d1.addErrback(self.assertClientFailureMessage,\n                      b\"Server error: login failed unexpectedly\")\n        d1.addCallback(strip(assertUnexpectedExceptionLogged))\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d\n\n\n    def testCramMD5(self):\n        self.server.challengers[b'CRAM-MD5'] = CramMD5Credentials\n        cAuth = imap4.CramMD5ClientAuthenticator(b'testuser')\n        self.client.registerAuthenticator(cAuth)\n\n        def auth():\n            return self.client.authenticate(b'secret')\n        def authed():\n            self.authenticated = 1\n\n        d1 = self.connected.addCallback(strip(auth))\n        d1.addCallbacks(strip(authed), self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d2 = self.loopback()\n        d = defer.gatherResults([d1, d2])\n        return d.addCallback(self._cbTestCramMD5)\n\n\n    def _cbTestCramMD5(self, ignored):\n        self.assertEqual(self.authenticated, 1)\n        self.assertEqual(self.server.account, self.account)\n\n\n    def testFailedCramMD5(self):\n        self.server.challengers[b'CRAM-MD5'] = CramMD5Credentials\n        cAuth = imap4.CramMD5ClientAuthenticator(b'testuser')\n        self.client.registerAuthenticator(cAuth)\n\n        def misauth():\n            return self.client.authenticate(b'not the secret')\n        def authed():\n            self.authenticated = 1\n        def misauthed():\n            self.authenticated = -1\n\n        d1 = self.connected.addCallback(strip(misauth))\n        d1.addCallbacks(strip(authed), strip(misauthed))\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d.addCallback(self._cbTestFailedCramMD5)\n\n\n    def _cbTestFailedCramMD5(self, ignored):\n        self.assertEqual(self.authenticated, -1)\n        self.assertEqual(self.server.account, None)\n\n\n    def testLOGIN(self):\n        self.server.challengers[b'LOGIN'] = loginCred = imap4.LOGINCredentials\n\n        verifyClass(IChallengeResponse, loginCred)\n\n        cAuth = imap4.LOGINAuthenticator(b'testuser')\n        self.client.registerAuthenticator(cAuth)\n\n        def auth():\n            return self.client.authenticate(b'secret')\n        def authed():\n            self.authenticated = 1\n\n        d1 = self.connected.addCallback(strip(auth))\n        d1.addCallbacks(strip(authed), self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d.addCallback(self._cbTestLOGIN)\n\n\n    def _cbTestLOGIN(self, ignored):\n        self.assertEqual(self.authenticated, 1)\n        self.assertEqual(self.server.account, self.account)\n\n\n    def testFailedLOGIN(self):\n        self.server.challengers[b'LOGIN'] = imap4.LOGINCredentials\n        cAuth = imap4.LOGINAuthenticator(b'testuser')\n        self.client.registerAuthenticator(cAuth)\n\n        def misauth():\n            return self.client.authenticate(b'not the secret')\n\n\n        def authed():\n            self.authenticated = 1\n\n\n        def misauthed():\n            self.authenticated = -1\n\n        d1 = self.connected.addCallback(strip(misauth))\n        d1.addCallbacks(strip(authed), strip(misauthed))\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d.addCallback(self._cbTestFailedLOGIN)\n\n\n    def _cbTestFailedLOGIN(self, ignored):\n        self.assertEqual(self.authenticated, -1)\n        self.assertEqual(self.server.account, None)\n\n\n    def testPLAIN(self):\n        self.server.challengers[b'PLAIN'] = plainCred = imap4.PLAINCredentials\n\n        verifyClass(IChallengeResponse, plainCred)\n\n        cAuth = imap4.PLAINAuthenticator(b'testuser')\n        self.client.registerAuthenticator(cAuth)\n\n        def auth():\n            return self.client.authenticate(b'secret')\n\n        def authed():\n            self.authenticated = 1\n\n        d1 = self.connected.addCallback(strip(auth))\n        d1.addCallbacks(strip(authed), self._ebGeneral)\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d.addCallback(self._cbTestPLAIN)\n\n\n    def _cbTestPLAIN(self, ignored):\n        self.assertEqual(self.authenticated, 1)\n        self.assertEqual(self.server.account, self.account)\n\n\n    def testFailedPLAIN(self):\n        self.server.challengers[b'PLAIN'] = imap4.PLAINCredentials\n        cAuth = imap4.PLAINAuthenticator(b'testuser')\n        self.client.registerAuthenticator(cAuth)\n\n        def misauth():\n            return self.client.authenticate(b'not the secret')\n        def authed():\n            self.authenticated = 1\n        def misauthed():\n            self.authenticated = -1\n\n        d1 = self.connected.addCallback(strip(misauth))\n        d1.addCallbacks(strip(authed), strip(misauthed))\n        d1.addCallbacks(self._cbStopClient, self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d.addCallback(self._cbTestFailedPLAIN)\n\n\n    def _cbTestFailedPLAIN(self, ignored):\n        self.assertEqual(self.authenticated, -1)\n        self.assertEqual(self.server.account, None)\n\n\n\nclass SASLPLAINTests(unittest.TestCase):\n    \"\"\"\n    Tests for I{SASL PLAIN} authentication, as implemented by\n    L{imap4.PLAINAuthenticator} and L{imap4.PLAINCredentials}.\n\n    @see: U{http://www.faqs.org/rfcs/rfc2595.html}\n    @see: U{http://www.faqs.org/rfcs/rfc4616.html}\n    \"\"\"\n    def test_authenticatorChallengeResponse(self):\n        \"\"\"\n        L{PLAINAuthenticator.challengeResponse} returns challenge strings of\n        the form::\n\n            NUL<authn-id>NUL<secret>\n        \"\"\"\n        username = b'testuser'\n        secret = b'secret'\n        chal = b'challenge'\n        cAuth = imap4.PLAINAuthenticator(username)\n        response = cAuth.challengeResponse(secret, chal)\n        self.assertEqual(response, b'\\0' + username + b'\\0' + secret)\n\n\n    def test_credentialsSetResponse(self):\n        \"\"\"\n        L{PLAINCredentials.setResponse} parses challenge strings of the\n        form::\n\n            NUL<authn-id>NUL<secret>\n        \"\"\"\n        cred = imap4.PLAINCredentials()\n        cred.setResponse(b'\\0testuser\\0secret')\n        self.assertEqual(cred.username, b'testuser')\n        self.assertEqual(cred.password, b'secret')\n\n\n    def test_credentialsInvalidResponse(self):\n        \"\"\"\n        L{PLAINCredentials.setResponse} raises L{imap4.IllegalClientResponse}\n        when passed a string not of the expected form.\n        \"\"\"\n        cred = imap4.PLAINCredentials()\n        self.assertRaises(\n            imap4.IllegalClientResponse, cred.setResponse, b'hello')\n        self.assertRaises(\n            imap4.IllegalClientResponse, cred.setResponse, b'hello\\0world')\n        self.assertRaises(\n            imap4.IllegalClientResponse, cred.setResponse,\n            b'hello\\0world\\0Zoom!\\0')\n\n\n\nclass UnsolicitedResponseTests(IMAP4HelperMixin, unittest.TestCase):\n    def testReadWrite(self):\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def loggedIn():\n            self.server.modeChanged(1)\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(loggedIn)).addErrback(self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d.addCallback(self._cbTestReadWrite)\n\n\n    def _cbTestReadWrite(self, ignored):\n        E = self.client.events\n        self.assertEqual(E, [['modeChanged', 1]])\n\n\n    def testReadOnly(self):\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def loggedIn():\n            self.server.modeChanged(0)\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(loggedIn)).addErrback(self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d.addCallback(self._cbTestReadOnly)\n\n\n    def _cbTestReadOnly(self, ignored):\n        E = self.client.events\n        self.assertEqual(E, [['modeChanged', 0]])\n\n\n    def testFlagChange(self):\n        flags = {\n            1: ['\\\\Answered', '\\\\Deleted'],\n            5: [],\n            10: ['\\\\Recent']\n        }\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def loggedIn():\n            self.server.flagsChanged(flags)\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(loggedIn)).addErrback(self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d.addCallback(self._cbTestFlagChange, flags)\n\n\n    def _cbTestFlagChange(self, ignored, flags):\n        E = self.client.events\n        expect = [['flagsChanged', {x[0]: x[1]}] for x in flags.items()]\n        E.sort(key=lambda o: o[0])\n        expect.sort(key=lambda o: o[0])\n        self.assertEqual(E, expect)\n\n\n    def testNewMessages(self):\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def loggedIn():\n            self.server.newMessages(10, None)\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(loggedIn)).addErrback(self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d.addCallback(self._cbTestNewMessages)\n\n\n    def _cbTestNewMessages(self, ignored):\n        E = self.client.events\n        self.assertEqual(E, [['newMessages', 10, None]])\n\n\n    def testNewRecentMessages(self):\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n        def loggedIn():\n            self.server.newMessages(None, 10)\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(loggedIn)).addErrback(self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d.addCallback(self._cbTestNewRecentMessages)\n\n\n    def _cbTestNewRecentMessages(self, ignored):\n        E = self.client.events\n        self.assertEqual(E, [['newMessages', None, 10]])\n\n\n    def testNewMessagesAndRecent(self):\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n\n        def loggedIn():\n            self.server.newMessages(20, 10)\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(loggedIn)).addErrback(self._ebGeneral)\n        d = defer.gatherResults([self.loopback(), d1])\n        return d.addCallback(self._cbTestNewMessagesAndRecent)\n\n\n    def _cbTestNewMessagesAndRecent(self, ignored):\n        E = self.client.events\n        self.assertEqual(E, [['newMessages', 20, None], ['newMessages', None, 10]])\n\n\n\nclass ClientCapabilityTests(unittest.TestCase):\n    \"\"\"\n    Tests for issuance of the CAPABILITY command and handling of its response.\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Create an L{imap4.IMAP4Client} connected to a L{StringTransport}.\n        \"\"\"\n        self.transport = StringTransport()\n        self.protocol = imap4.IMAP4Client()\n        self.protocol.makeConnection(self.transport)\n        self.protocol.dataReceived(b'* OK [IMAP4rev1]\\r\\n')\n\n\n    def test_simpleAtoms(self):\n        \"\"\"\n        A capability response consisting only of atoms without C{'='} in them\n        should result in a dict mapping those atoms to L{None}.\n        \"\"\"\n        capabilitiesResult = self.protocol.getCapabilities(useCache=False)\n        self.protocol.dataReceived(b'* CAPABILITY IMAP4rev1 LOGINDISABLED\\r\\n')\n        self.protocol.dataReceived(b'0001 OK Capability completed.\\r\\n')\n        def gotCapabilities(capabilities):\n            self.assertEqual(\n                capabilities, {b'IMAP4rev1': None, b'LOGINDISABLED': None})\n        capabilitiesResult.addCallback(gotCapabilities)\n        return capabilitiesResult\n\n\n    def test_categoryAtoms(self):\n        \"\"\"\n        A capability response consisting of atoms including C{'='} should have\n        those atoms split on that byte and have capabilities in the same\n        category aggregated into lists in the resulting dictionary.\n\n        (n.b. - I made up the word \"category atom\"; the protocol has no notion\n        of structure here, but rather allows each capability to define the\n        semantics of its entry in the capability response in a freeform manner.\n        If I had realized this earlier, the API for capabilities would look\n        different.  As it is, we can hope that no one defines any crazy\n        semantics which are incompatible with this API, or try to figure out a\n        better API when someone does. -exarkun)\n        \"\"\"\n        capabilitiesResult = self.protocol.getCapabilities(useCache=False)\n        self.protocol.dataReceived(b'* CAPABILITY IMAP4rev1 AUTH=LOGIN AUTH=PLAIN\\r\\n')\n        self.protocol.dataReceived(b'0001 OK Capability completed.\\r\\n')\n        def gotCapabilities(capabilities):\n            self.assertEqual(\n                capabilities, {b'IMAP4rev1': None, b'AUTH': [b'LOGIN', b'PLAIN']})\n        capabilitiesResult.addCallback(gotCapabilities)\n        return capabilitiesResult\n\n\n    def test_mixedAtoms(self):\n        \"\"\"\n        A capability response consisting of both simple and category atoms of\n        the same type should result in a list containing L{None} as well as the\n        values for the category.\n        \"\"\"\n        capabilitiesResult = self.protocol.getCapabilities(useCache=False)\n        # Exercise codepath for both orderings of =-having and =-missing\n        # capabilities.\n        self.protocol.dataReceived(\n            b'* CAPABILITY IMAP4rev1 FOO FOO=BAR BAR=FOO BAR\\r\\n')\n        self.protocol.dataReceived(b'0001 OK Capability completed.\\r\\n')\n        def gotCapabilities(capabilities):\n            self.assertEqual(capabilities, {b'IMAP4rev1': None,\n                                            b'FOO': [None, b'BAR'],\n                                            b'BAR': [b'FOO', None]})\n        capabilitiesResult.addCallback(gotCapabilities)\n        return capabilitiesResult\n\n\n\nclass StillSimplerClient(imap4.IMAP4Client):\n    \"\"\"\n    An IMAP4 client which keeps track of unsolicited flag changes.\n    \"\"\"\n    def __init__(self):\n        imap4.IMAP4Client.__init__(self)\n        self.flags = {}\n\n\n    def flagsChanged(self, newFlags):\n        self.flags.update(newFlags)\n\n\n\nclass HandCraftedTests(IMAP4HelperMixin, unittest.TestCase):\n    def testTrailingLiteral(self):\n        transport = StringTransport()\n        c = imap4.IMAP4Client()\n        c.makeConnection(transport)\n        c.lineReceived(b'* OK [IMAP4rev1]')\n\n        def cbCheckTransport(ignored):\n            self.assertEqual(\n                transport.value().splitlines()[-1],\n                b\"0003 FETCH 1 (RFC822)\",\n            )\n\n        def cbSelect(ignored):\n            d = c.fetchMessage('1')\n            c.dataReceived(b'* 1 FETCH (RFC822 {10}\\r\\n0123456789\\r\\n RFC822.SIZE 10)\\r\\n')\n            c.dataReceived(b'0003 OK FETCH\\r\\n')\n            d.addCallback(cbCheckTransport)\n            return d\n\n\n        def cbLogin(ignored):\n            d = c.select('inbox')\n            c.lineReceived(b'0002 OK SELECT')\n            d.addCallback(cbSelect)\n            return d\n\n        d = c.login(b'blah', b'blah')\n        c.dataReceived(b'0001 OK LOGIN\\r\\n')\n        d.addCallback(cbLogin)\n        return d\n\n\n    def test_fragmentedStringLiterals(self):\n        \"\"\"\n        String literals whose data is not immediately available are\n        parsed.\n        \"\"\"\n        self.server.checker.addUser(b'testuser', b'password-test')\n        transport = StringTransport()\n        self.server.makeConnection(transport)\n\n        transport.clear()\n        self.server.dataReceived(b\"01 LOGIN {8}\\r\\n\")\n        self.assertEqual(transport.value(), b\"+ Ready for 8 octets of text\\r\\n\")\n\n        transport.clear()\n        self.server.dataReceived(b\"testuser {13}\\r\\n\")\n        self.assertEqual(transport.value(), b\"+ Ready for 13 octets of text\\r\\n\")\n\n        transport.clear()\n        self.server.dataReceived(b\"password\")\n        self.assertNot(transport.value())\n        self.server.dataReceived(b\"-test\\r\\n\")\n        self.assertEqual(transport.value(), b\"01 OK LOGIN succeeded\\r\\n\")\n        self.assertEqual(self.server.state, 'auth')\n\n        self.server.connectionLost(error.ConnectionDone(\"Connection done.\"))\n\n\n    def test_emptyStringLiteral(self):\n        \"\"\"\n        Empty string literals are parsed.\n        \"\"\"\n        self.server.checker.users = {b\"\": b\"\"}\n        transport = StringTransport()\n        self.server.makeConnection(transport)\n\n        transport.clear()\n        self.server.dataReceived(b\"01 LOGIN {0}\\r\\n\")\n        self.assertEqual(transport.value(),\n                         b\"+ Ready for 0 octets of text\\r\\n\")\n\n        transport.clear()\n        self.server.dataReceived(b\"{0}\\r\\n\")\n        self.assertEqual(transport.value(), b\"01 OK LOGIN succeeded\\r\\n\")\n        self.assertEqual(self.server.state, 'auth')\n\n        self.server.connectionLost(error.ConnectionDone(\"Connection done.\"))\n\n\n    def test_unsolicitedResponseMixedWithSolicitedResponse(self):\n        \"\"\"\n        If unsolicited data is received along with solicited data in the\n        response to a I{FETCH} command issued by L{IMAP4Client.fetchSpecific},\n        the unsolicited data is passed to the appropriate callback and not\n        included in the result with which the L{Deferred} returned by\n        L{IMAP4Client.fetchSpecific} fires.\n        \"\"\"\n        transport = StringTransport()\n        c = StillSimplerClient()\n        c.makeConnection(transport)\n        c.lineReceived(b'* OK [IMAP4rev1]')\n\n        def login():\n            d = c.login(b'blah', b'blah')\n            c.dataReceived(b'0001 OK LOGIN\\r\\n')\n            return d\n        def select():\n            d = c.select('inbox')\n            c.lineReceived(b'0002 OK SELECT')\n            return d\n        def fetch():\n            d = c.fetchSpecific('1:*',\n                headerType = 'HEADER.FIELDS',\n                headerArgs = ['SUBJECT'])\n            c.dataReceived(b'* 1 FETCH (BODY[HEADER.FIELDS (\"SUBJECT\")] {38}\\r\\n')\n            c.dataReceived(b'Subject: Suprise for your woman...\\r\\n')\n            c.dataReceived(b'\\r\\n')\n            c.dataReceived(b')\\r\\n')\n            c.dataReceived(b'* 1 FETCH (FLAGS (\\Seen))\\r\\n')\n            c.dataReceived(b'* 2 FETCH (BODY[HEADER.FIELDS (\"SUBJECT\")] {75}\\r\\n')\n            c.dataReceived(b'Subject: What you been doing. Order your meds here . ,. handcuff madsen\\r\\n')\n            c.dataReceived(b'\\r\\n')\n            c.dataReceived(b')\\r\\n')\n            c.dataReceived(b'0003 OK FETCH completed\\r\\n')\n            return d\n        def test(res):\n            self.assertEqual(\n                transport.value().splitlines()[-1],\n                b\"0003 FETCH 1:* BODY[HEADER.FIELDS (SUBJECT)]\",\n            )\n\n            self.assertEqual(res, {\n                1: [['BODY', ['HEADER.FIELDS', ['SUBJECT']],\n                    'Subject: Suprise for your woman...\\r\\n\\r\\n']],\n                2: [['BODY', ['HEADER.FIELDS', ['SUBJECT']],\n                    'Subject: What you been doing. Order your meds here . ,. handcuff madsen\\r\\n\\r\\n']]\n            })\n\n            self.assertEqual(c.flags, {1: ['\\\\Seen']})\n\n        return login(\n            ).addCallback(strip(select)\n            ).addCallback(strip(fetch)\n            ).addCallback(test)\n\n\n    def test_literalWithoutPrecedingWhitespace(self):\n        \"\"\"\n        Literals should be recognized even when they are not preceded by\n        whitespace.\n        \"\"\"\n        transport = StringTransport()\n        protocol = imap4.IMAP4Client()\n\n        protocol.makeConnection(transport)\n        protocol.lineReceived(b'* OK [IMAP4rev1]')\n\n        def login():\n            d = protocol.login(b'blah', b'blah')\n            protocol.dataReceived(b'0001 OK LOGIN\\r\\n')\n            return d\n        def select():\n            d = protocol.select(b'inbox')\n            protocol.lineReceived(b'0002 OK SELECT')\n            return d\n        def fetch():\n            d = protocol.fetchSpecific('1:*',\n                headerType='HEADER.FIELDS',\n                headerArgs=['SUBJECT'])\n            protocol.dataReceived(\n                b'* 1 FETCH (BODY[HEADER.FIELDS ({7}\\r\\nSUBJECT)] \"Hello\")\\r\\n')\n            protocol.dataReceived(b'0003 OK FETCH completed\\r\\n')\n            return d\n        def test(result):\n            self.assertEqual(\n                transport.value().splitlines()[-1],\n                b\"0003 FETCH 1:* BODY[HEADER.FIELDS (SUBJECT)]\",\n            )\n            self.assertEqual(\n                result,  {1: [['BODY', ['HEADER.FIELDS', ['SUBJECT']], 'Hello']]})\n\n        d = login()\n        d.addCallback(strip(select))\n        d.addCallback(strip(fetch))\n        d.addCallback(test)\n        return d\n\n\n    def test_nonIntegerLiteralLength(self):\n        \"\"\"\n        If the server sends a literal length which cannot be parsed as an\n        integer, L{IMAP4Client.lineReceived} should cause the protocol to be\n        disconnected by raising L{imap4.IllegalServerResponse}.\n        \"\"\"\n        transport = StringTransport()\n        protocol = imap4.IMAP4Client()\n\n        protocol.makeConnection(transport)\n        protocol.lineReceived(b'* OK [IMAP4rev1]')\n\n        def login():\n            d = protocol.login(b'blah', b'blah')\n            protocol.dataReceived(b'0001 OK LOGIN\\r\\n')\n            return d\n        def select():\n            d = protocol.select('inbox')\n            protocol.lineReceived(b'0002 OK SELECT')\n            return d\n        def fetch():\n            protocol.fetchSpecific(\n                '1:*',\n                headerType='HEADER.FIELDS',\n                headerArgs=['SUBJECT'])\n\n            self.assertEqual(\n                transport.value().splitlines()[-1],\n                b\"0003 FETCH 1:* BODY[HEADER.FIELDS (SUBJECT)]\",\n            )\n\n            self.assertRaises(\n                imap4.IllegalServerResponse,\n                protocol.dataReceived,\n                b'* 1 FETCH {xyz}\\r\\n...')\n        d = login()\n        d.addCallback(strip(select))\n        d.addCallback(strip(fetch))\n        return d\n\n\n    def test_flagsChangedInsideFetchSpecificResponse(self):\n        \"\"\"\n        Any unrequested flag information received along with other requested\n        information in an untagged I{FETCH} received in response to a request\n        issued with L{IMAP4Client.fetchSpecific} is passed to the\n        C{flagsChanged} callback.\n        \"\"\"\n        transport = StringTransport()\n        c = StillSimplerClient()\n        c.makeConnection(transport)\n        c.lineReceived(b'* OK [IMAP4rev1]')\n\n\n        def login():\n            d = c.login(b'blah', b'blah')\n            c.dataReceived(b'0001 OK LOGIN\\r\\n')\n            return d\n\n\n        def select():\n            d = c.select('inbox')\n            c.lineReceived(b'0002 OK SELECT')\n            return d\n\n\n        def fetch():\n            d = c.fetchSpecific(b'1:*',\n                headerType='HEADER.FIELDS',\n                headerArgs=['SUBJECT'])\n            # This response includes FLAGS after the requested data.\n            c.dataReceived(b'* 1 FETCH (BODY[HEADER.FIELDS (\"SUBJECT\")] {22}\\r\\n')\n            c.dataReceived(b'Subject: subject one\\r\\n')\n            c.dataReceived(b' FLAGS (\\\\Recent))\\r\\n')\n            # And this one includes it before!  Either is possible.\n            c.dataReceived(b'* 2 FETCH (FLAGS (\\\\Seen) BODY[HEADER.FIELDS (\"SUBJECT\")] {22}\\r\\n')\n            c.dataReceived(b'Subject: subject two\\r\\n')\n            c.dataReceived(b')\\r\\n')\n            c.dataReceived(b'0003 OK FETCH completed\\r\\n')\n            return d\n\n\n        def test(res):\n            self.assertEqual(res, {\n                1: [['BODY', ['HEADER.FIELDS', ['SUBJECT']],\n                     'Subject: subject one\\r\\n']],\n                2: [['BODY', ['HEADER.FIELDS', ['SUBJECT']],\n                     'Subject: subject two\\r\\n']]\n            })\n\n            self.assertEqual(c.flags, {1: ['\\\\Recent'], 2: ['\\\\Seen']})\n\n        return login(\n            ).addCallback(strip(select)\n            ).addCallback(strip(fetch)\n            ).addCallback(test)\n\n\n    def test_flagsChangedInsideFetchMessageResponse(self):\n        \"\"\"\n        Any unrequested flag information received along with other requested\n        information in an untagged I{FETCH} received in response to a request\n        issued with L{IMAP4Client.fetchMessage} is passed to the\n        C{flagsChanged} callback.\n        \"\"\"\n        transport = StringTransport()\n        c = StillSimplerClient()\n        c.makeConnection(transport)\n        c.lineReceived(b'* OK [IMAP4rev1]')\n\n        def login():\n            d = c.login(b'blah', b'blah')\n            c.dataReceived(b'0001 OK LOGIN\\r\\n')\n            return d\n        def select():\n            d = c.select('inbox')\n            c.lineReceived(b'0002 OK SELECT')\n            return d\n        def fetch():\n            d = c.fetchMessage('1:*')\n            c.dataReceived(b'* 1 FETCH (RFC822 {24}\\r\\n')\n            c.dataReceived(b'Subject: first subject\\r\\n')\n            c.dataReceived(b' FLAGS (\\Seen))\\r\\n')\n            c.dataReceived(b'* 2 FETCH (FLAGS (\\Recent \\Seen) RFC822 {25}\\r\\n')\n            c.dataReceived(b'Subject: second subject\\r\\n')\n            c.dataReceived(b')\\r\\n')\n            c.dataReceived(b'0003 OK FETCH completed\\r\\n')\n            return d\n\n\n        def test(res):\n            self.assertEqual(\n                transport.value().splitlines()[-1],\n                b'0003 FETCH 1:* (RFC822)',\n                )\n\n            self.assertEqual(res, {\n                1: {'RFC822': 'Subject: first subject\\r\\n'},\n                2: {'RFC822': 'Subject: second subject\\r\\n'}})\n\n            self.assertEqual(\n                c.flags, {1: ['\\\\Seen'], 2: ['\\\\Recent', '\\\\Seen']})\n\n        return login(\n            ).addCallback(strip(select)\n            ).addCallback(strip(fetch)\n            ).addCallback(test)\n\n\n    def test_authenticationChallengeDecodingException(self):\n        \"\"\"\n        When decoding a base64 encoded authentication message from the server,\n        decoding errors are logged and then the client closes the connection.\n        \"\"\"\n        transport = StringTransportWithDisconnection()\n        protocol = imap4.IMAP4Client()\n        transport.protocol = protocol\n\n        protocol.makeConnection(transport)\n        protocol.lineReceived(\n            b'* OK [CAPABILITY IMAP4rev1 IDLE NAMESPACE AUTH=CRAM-MD5] '\n            b'Twisted IMAP4rev1 Ready')\n        cAuth = imap4.CramMD5ClientAuthenticator(b'testuser')\n        protocol.registerAuthenticator(cAuth)\n\n        d = protocol.authenticate('secret')\n        # Should really be something describing the base64 decode error.  See\n        # #6021.\n        self.assertFailure(d, error.ConnectionDone)\n\n        protocol.dataReceived(b'+ Something bad! and bad\\r\\n')\n\n        # This should not really be logged.  See #6021.\n        logged = self.flushLoggedErrors(imap4.IllegalServerResponse)\n        self.assertEqual(len(logged), 1)\n        self.assertEqual(logged[0].value.args[0], b\"Something bad! and bad\")\n        return d\n\n\n\nclass PreauthIMAP4ClientMixin(object):\n    \"\"\"\n    Mixin for L{unittest.SynchronousTestCase} subclasses which\n    provides a C{setUp} method which creates an L{IMAP4Client}\n    connected to a L{StringTransport} and puts it into the\n    I{authenticated} state.\n\n    @ivar transport: A L{StringTransport} to which C{client} is\n        connected.\n\n    @ivar client: An L{IMAP4Client} which is connected to\n        C{transport}.\n    \"\"\"\n    clientProtocol = imap4.IMAP4Client\n\n    def setUp(self):\n        \"\"\"\n        Create an IMAP4Client connected to a fake transport and in the\n        authenticated state.\n        \"\"\"\n        self.transport = StringTransport()\n        self.client = self.clientProtocol()\n        self.client.makeConnection(self.transport)\n        self.client.dataReceived(b'* PREAUTH Hello unittest\\r\\n')\n\n\n\nclass SelectionTestsMixin(PreauthIMAP4ClientMixin):\n    \"\"\"\n    Mixin for test cases which defines tests which apply to both I{EXAMINE} and\n    I{SELECT} support.\n    \"\"\"\n    def _examineOrSelect(self):\n        \"\"\"\n        Issue either an I{EXAMINE} or I{SELECT} command (depending on\n        C{self.method}), assert that the correct bytes are written to the\n        transport, and return the L{Deferred} returned by whichever method was\n        called.\n        \"\"\"\n        d = getattr(self.client, self.method)('foobox')\n        self.assertEqual(\n            self.transport.value(), b'0001 ' + self.command + b' foobox\\r\\n')\n        return d\n\n\n    def _response(self, *lines):\n        \"\"\"\n        Deliver the given (unterminated) response lines to C{self.client} and\n        then deliver a tagged SELECT or EXAMINE completion line to finish the\n        SELECT or EXAMINE response.\n        \"\"\"\n        for line in lines:\n            self.client.dataReceived(line + b'\\r\\n')\n        self.client.dataReceived(\n            b'0001 OK [READ-ONLY] ' + self.command + b' completed\\r\\n')\n\n\n    def test_exists(self):\n        \"\"\"\n        If the server response to a I{SELECT} or I{EXAMINE} command includes an\n        I{EXISTS} response, the L{Deferred} return by L{IMAP4Client.select} or\n        L{IMAP4Client.examine} fires with a C{dict} including the value\n        associated with the C{'EXISTS'} key.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(b'* 3 EXISTS')\n        self.assertEqual(\n            self.successResultOf(d),\n            {'READ-WRITE': False, 'EXISTS': 3})\n\n\n    def test_nonIntegerExists(self):\n        \"\"\"\n        If the server returns a non-integer EXISTS value in its response to a\n        I{SELECT} or I{EXAMINE} command, the L{Deferred} returned by\n        L{IMAP4Client.select} or L{IMAP4Client.examine} fails with\n        L{IllegalServerResponse}.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(b'* foo EXISTS')\n        self.failureResultOf(d, imap4.IllegalServerResponse)\n\n\n    def test_recent(self):\n        \"\"\"\n        If the server response to a I{SELECT} or I{EXAMINE} command includes an\n        I{RECENT} response, the L{Deferred} return by L{IMAP4Client.select} or\n        L{IMAP4Client.examine} fires with a C{dict} including the value\n        associated with the C{'RECENT'} key.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(b'* 5 RECENT')\n        self.assertEqual(\n            self.successResultOf(d),\n            {'READ-WRITE': False, 'RECENT': 5})\n\n\n    def test_nonIntegerRecent(self):\n        \"\"\"\n        If the server returns a non-integer RECENT value in its response to a\n        I{SELECT} or I{EXAMINE} command, the L{Deferred} returned by\n        L{IMAP4Client.select} or L{IMAP4Client.examine} fails with\n        L{IllegalServerResponse}.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(b'* foo RECENT')\n        self.failureResultOf(d, imap4.IllegalServerResponse)\n\n\n    def test_unseen(self):\n        \"\"\"\n        If the server response to a I{SELECT} or I{EXAMINE} command includes an\n        I{UNSEEN} response, the L{Deferred} returned by L{IMAP4Client.select} or\n        L{IMAP4Client.examine} fires with a C{dict} including the value\n        associated with the C{'UNSEEN'} key.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(b'* OK [UNSEEN 8] Message 8 is first unseen')\n        self.assertEqual(\n            self.successResultOf(d),\n            {'READ-WRITE': False, 'UNSEEN': 8})\n\n\n    def test_nonIntegerUnseen(self):\n        \"\"\"\n        If the server returns a non-integer UNSEEN value in its response to a\n        I{SELECT} or I{EXAMINE} command, the L{Deferred} returned by\n        L{IMAP4Client.select} or L{IMAP4Client.examine} fails with\n        L{IllegalServerResponse}.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(b'* OK [UNSEEN foo] Message foo is first unseen')\n        self.failureResultOf(d, imap4.IllegalServerResponse)\n\n\n    def test_uidvalidity(self):\n        \"\"\"\n        If the server response to a I{SELECT} or I{EXAMINE} command includes an\n        I{UIDVALIDITY} response, the L{Deferred} returned by\n        L{IMAP4Client.select} or L{IMAP4Client.examine} fires with a C{dict}\n        including the value associated with the C{'UIDVALIDITY'} key.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(b'* OK [UIDVALIDITY 12345] UIDs valid')\n        self.assertEqual(\n            self.successResultOf(d),\n            {'READ-WRITE': False, 'UIDVALIDITY': 12345})\n\n\n    def test_nonIntegerUIDVALIDITY(self):\n        \"\"\"\n        If the server returns a non-integer UIDVALIDITY value in its response to\n        a I{SELECT} or I{EXAMINE} command, the L{Deferred} returned by\n        L{IMAP4Client.select} or L{IMAP4Client.examine} fails with\n        L{IllegalServerResponse}.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(b'* OK [UIDVALIDITY foo] UIDs valid')\n        self.failureResultOf(d, imap4.IllegalServerResponse)\n\n\n    def test_uidnext(self):\n        \"\"\"\n        If the server response to a I{SELECT} or I{EXAMINE} command includes an\n        I{UIDNEXT} response, the L{Deferred} returned by L{IMAP4Client.select}\n        or L{IMAP4Client.examine} fires with a C{dict} including the value\n        associated with the C{'UIDNEXT'} key.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(b'* OK [UIDNEXT 4392] Predicted next UID')\n        self.assertEqual(\n            self.successResultOf(d),\n            {'READ-WRITE': False, 'UIDNEXT': 4392})\n\n\n    def test_nonIntegerUIDNEXT(self):\n        \"\"\"\n        If the server returns a non-integer UIDNEXT value in its response to a\n        I{SELECT} or I{EXAMINE} command, the L{Deferred} returned by\n        L{IMAP4Client.select} or L{IMAP4Client.examine} fails with\n        L{IllegalServerResponse}.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(b'* OK [UIDNEXT foo] Predicted next UID')\n        self.failureResultOf(d, imap4.IllegalServerResponse)\n\n\n    def test_flags(self):\n        \"\"\"\n        If the server response to a I{SELECT} or I{EXAMINE} command includes an\n        I{FLAGS} response, the L{Deferred} returned by L{IMAP4Client.select} or\n        L{IMAP4Client.examine} fires with a C{dict} including the value\n        associated with the C{'FLAGS'} key.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(\n            b'* FLAGS (\\\\Answered \\\\Flagged \\\\Deleted \\\\Seen \\\\Draft)')\n        self.assertEqual(\n            self.successResultOf(d), {\n                'READ-WRITE': False,\n                'FLAGS': ('\\\\Answered', '\\\\Flagged', '\\\\Deleted', '\\\\Seen',\n                          '\\\\Draft')})\n\n\n    def test_permanentflags(self):\n        \"\"\"\n        If the server response to a I{SELECT} or I{EXAMINE} command includes an\n        I{FLAGS} response, the L{Deferred} returned by L{IMAP4Client.select} or\n        L{IMAP4Client.examine} fires with a C{dict} including the value\n        associated with the C{'FLAGS'} key.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(\n            b'* OK [PERMANENTFLAGS (\\\\Starred)] Just one permanent flag in '\n            b'that list up there')\n        self.assertEqual(\n            self.successResultOf(d), {\n                'READ-WRITE': False,\n                'PERMANENTFLAGS': ('\\\\Starred',)})\n\n\n    def test_unrecognizedOk(self):\n        \"\"\"\n        If the server response to a I{SELECT} or I{EXAMINE} command includes an\n        I{OK} with unrecognized response code text, parsing does not fail.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(\n            b'* OK [X-MADE-UP] I just made this response text up.')\n        # The value won't show up in the result.  It would be okay if it did\n        # someday, perhaps.  This shouldn't ever happen, though.\n        self.assertEqual(\n            self.successResultOf(d), {'READ-WRITE': False})\n\n\n    def test_bareOk(self):\n        \"\"\"\n        If the server response to a I{SELECT} or I{EXAMINE} command includes an\n        I{OK} with no response code text, parsing does not fail.\n        \"\"\"\n        d = self._examineOrSelect()\n        self._response(b'* OK')\n        self.assertEqual(\n            self.successResultOf(d), {'READ-WRITE': False})\n\n\n\nclass IMAP4ClientExamineTests(SelectionTestsMixin,\n                              unittest.SynchronousTestCase):\n    \"\"\"\n    Tests for the L{IMAP4Client.examine} method.\n\n    An example of usage of the EXAMINE command from RFC 3501, section 6.3.2::\n\n        S: * 17 EXISTS\n        S: * 2 RECENT\n        S: * OK [UNSEEN 8] Message 8 is first unseen\n        S: * OK [UIDVALIDITY 3857529045] UIDs valid\n        S: * OK [UIDNEXT 4392] Predicted next UID\n        S: * FLAGS (\\\\Answered \\\\Flagged \\\\Deleted \\\\Seen \\\\Draft)\n        S: * OK [PERMANENTFLAGS ()] No permanent flags permitted\n        S: A932 OK [READ-ONLY] EXAMINE completed\n    \"\"\"\n    method = 'examine'\n    command = b'EXAMINE'\n\n\n\nclass IMAP4ClientSelectTests(SelectionTestsMixin,\n                             unittest.SynchronousTestCase):\n    \"\"\"\n    Tests for the L{IMAP4Client.select} method.\n\n    An example of usage of the SELECT command from RFC 3501, section 6.3.1::\n\n        C: A142 SELECT INBOX\n        S: * 172 EXISTS\n        S: * 1 RECENT\n        S: * OK [UNSEEN 12] Message 12 is first unseen\n        S: * OK [UIDVALIDITY 3857529045] UIDs valid\n        S: * OK [UIDNEXT 4392] Predicted next UID\n        S: * FLAGS (\\Answered \\Flagged \\Deleted \\Seen \\Draft)\n        S: * OK [PERMANENTFLAGS (\\Deleted \\Seen \\*)] Limited\n        S: A142 OK [READ-WRITE] SELECT completed\n    \"\"\"\n    method = 'select'\n    command = b'SELECT'\n\n\n\nclass IMAP4ClientExpungeTests(PreauthIMAP4ClientMixin,\n                              unittest.SynchronousTestCase):\n    \"\"\"\n    Tests for the L{IMAP4Client.expunge} method.\n\n    An example of usage of the EXPUNGE command from RFC 3501, section 6.4.3::\n\n        C: A202 EXPUNGE\n        S: * 3 EXPUNGE\n        S: * 3 EXPUNGE\n        S: * 5 EXPUNGE\n        S: * 8 EXPUNGE\n        S: A202 OK EXPUNGE completed\n    \"\"\"\n    def _expunge(self):\n        d = self.client.expunge()\n        self.assertEqual(self.transport.value(), b'0001 EXPUNGE\\r\\n')\n        self.transport.clear()\n        return d\n\n\n    def _response(self, sequenceNumbers):\n        for number in sequenceNumbers:\n            self.client.lineReceived(networkString('* %s EXPUNGE' % (number,)))\n        self.client.lineReceived(b'0001 OK EXPUNGE COMPLETED')\n\n\n    def test_expunge(self):\n        \"\"\"\n        L{IMAP4Client.expunge} sends the I{EXPUNGE} command and returns a\n        L{Deferred} which fires with a C{list} of message sequence numbers\n        given by the server's response.\n        \"\"\"\n        d = self._expunge()\n        self._response([3, 3, 5, 8])\n        self.assertEqual(self.successResultOf(d), [3, 3, 5, 8])\n\n\n    def test_nonIntegerExpunged(self):\n        \"\"\"\n        If the server responds with a non-integer where a message sequence\n        number is expected, the L{Deferred} returned by L{IMAP4Client.expunge}\n        fails with L{IllegalServerResponse}.\n        \"\"\"\n        d = self._expunge()\n        self._response([3, 3, 'foo', 8])\n        self.failureResultOf(d, imap4.IllegalServerResponse)\n\n\n\nclass IMAP4ClientSearchTests(PreauthIMAP4ClientMixin,\n                             unittest.SynchronousTestCase):\n    \"\"\"\n    Tests for the L{IMAP4Client.search} method.\n\n    An example of usage of the SEARCH command from RFC 3501, section 6.4.4::\n\n        C: A282 SEARCH FLAGGED SINCE 1-Feb-1994 NOT FROM \"Smith\"\n        S: * SEARCH 2 84 882\n        S: A282 OK SEARCH completed\n        C: A283 SEARCH TEXT \"string not in mailbox\"\n        S: * SEARCH\n        S: A283 OK SEARCH completed\n        C: A284 SEARCH CHARSET UTF-8 TEXT {6}\n        C: XXXXXX\n        S: * SEARCH 43\n        S: A284 OK SEARCH completed\n    \"\"\"\n    def _search(self):\n        d = self.client.search(imap4.Query(text=\"ABCDEF\"))\n        self.assertEqual(\n            self.transport.value(), b'0001 SEARCH (TEXT \"ABCDEF\")\\r\\n')\n        return d\n\n\n    def _response(self, messageNumbers):\n        self.client.lineReceived(\n            b\"* SEARCH \" + networkString(\" \".join(map(str, messageNumbers))))\n        self.client.lineReceived(b\"0001 OK SEARCH completed\")\n\n\n    def test_search(self):\n        \"\"\"\n        L{IMAP4Client.search} sends the I{SEARCH} command and returns a\n        L{Deferred} which fires with a C{list} of message sequence numbers\n        given by the server's response.\n        \"\"\"\n        d = self._search()\n        self._response([2, 5, 10])\n        self.assertEqual(self.successResultOf(d), [2, 5, 10])\n\n\n    def test_nonIntegerFound(self):\n        \"\"\"\n        If the server responds with a non-integer where a message sequence\n        number is expected, the L{Deferred} returned by L{IMAP4Client.search}\n        fails with L{IllegalServerResponse}.\n        \"\"\"\n        d = self._search()\n        self._response([2, \"foo\", 10])\n        self.failureResultOf(d, imap4.IllegalServerResponse)\n\n\n\nclass IMAP4ClientFetchTests(PreauthIMAP4ClientMixin,\n                            unittest.SynchronousTestCase):\n    \"\"\"\n    Tests for the L{IMAP4Client.fetch} method.\n\n    See RFC 3501, section 6.4.5.\n    \"\"\"\n    def test_fetchUID(self):\n        \"\"\"\n        L{IMAP4Client.fetchUID} sends the I{FETCH UID} command and returns a\n        L{Deferred} which fires with a C{dict} mapping message sequence numbers\n        to C{dict}s mapping C{'UID'} to that message's I{UID} in the server's\n        response.\n        \"\"\"\n        d = self.client.fetchUID('1:7')\n        self.assertEqual(self.transport.value(), b'0001 FETCH 1:7 (UID)\\r\\n')\n        self.client.lineReceived(b'* 2 FETCH (UID 22)')\n        self.client.lineReceived(b'* 3 FETCH (UID 23)')\n        self.client.lineReceived(b'* 4 FETCH (UID 24)')\n        self.client.lineReceived(b'* 5 FETCH (UID 25)')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.assertEqual(\n            self.successResultOf(d), {\n                2: {'UID': '22'},\n                3: {'UID': '23'},\n                4: {'UID': '24'},\n                5: {'UID': '25'}})\n\n\n    def test_fetchUIDNonIntegerFound(self):\n        \"\"\"\n        If the server responds with a non-integer where a message sequence\n        number is expected, the L{Deferred} returned by L{IMAP4Client.fetchUID}\n        fails with L{IllegalServerResponse}.\n        \"\"\"\n        d = self.client.fetchUID('1')\n        self.assertEqual(self.transport.value(), b'0001 FETCH 1 (UID)\\r\\n')\n        self.client.lineReceived(b'* foo FETCH (UID 22)')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.failureResultOf(d, imap4.IllegalServerResponse)\n\n\n    def test_incompleteFetchUIDResponse(self):\n        \"\"\"\n        If the server responds with an incomplete I{FETCH} response line, the\n        L{Deferred} returned by L{IMAP4Client.fetchUID} fails with\n        L{IllegalServerResponse}.\n        \"\"\"\n        d = self.client.fetchUID('1:7')\n        self.assertEqual(self.transport.value(), b'0001 FETCH 1:7 (UID)\\r\\n')\n        self.client.lineReceived(b'* 2 FETCH (UID 22)')\n        self.client.lineReceived(b'* 3 FETCH (UID)')\n        self.client.lineReceived(b'* 4 FETCH (UID 24)')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.failureResultOf(d, imap4.IllegalServerResponse)\n\n\n    def test_fetchBody(self):\n        \"\"\"\n        L{IMAP4Client.fetchBody} sends the I{FETCH BODY} command and returns a\n        L{Deferred} which fires with a C{dict} mapping message sequence numbers\n        to C{dict}s mapping C{'RFC822.TEXT'} to that message's body as given in\n        the server's response.\n        \"\"\"\n        d = self.client.fetchBody('3')\n        self.assertEqual(\n            self.transport.value(), b'0001 FETCH 3 (RFC822.TEXT)\\r\\n')\n        self.client.lineReceived(b'* 3 FETCH (RFC822.TEXT \"Message text\")')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.assertEqual(\n            self.successResultOf(d),\n            {3: {'RFC822.TEXT': 'Message text'}})\n\n\n    def test_fetchSpecific(self):\n        \"\"\"\n        L{IMAP4Client.fetchSpecific} sends the I{BODY[]} command if no\n        parameters beyond the message set to retrieve are given.  It returns a\n        L{Deferred} which fires with a C{dict} mapping message sequence numbers\n        to C{list}s of corresponding message data given by the server's\n        response.\n        \"\"\"\n        d = self.client.fetchSpecific('7')\n        self.assertEqual(\n            self.transport.value(), b'0001 FETCH 7 BODY[]\\r\\n')\n        self.client.lineReceived(b'* 7 FETCH (BODY[] \"Some body\")')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.assertEqual(\n            self.successResultOf(d), {7: [['BODY', [], \"Some body\"]]})\n\n\n    def test_fetchSpecificPeek(self):\n        \"\"\"\n        L{IMAP4Client.fetchSpecific} issues a I{BODY.PEEK[]} command if passed\n        C{True} for the C{peek} parameter.\n        \"\"\"\n        d = self.client.fetchSpecific('6', peek=True)\n        self.assertEqual(\n            self.transport.value(), b'0001 FETCH 6 BODY.PEEK[]\\r\\n')\n        # BODY.PEEK responses are just BODY\n        self.client.lineReceived(b'* 6 FETCH (BODY[] \"Some body\")')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.assertEqual(\n            self.successResultOf(d), {6: [['BODY', [], \"Some body\"]]})\n\n\n    def test_fetchSpecificNumbered(self):\n        \"\"\"\n        L{IMAP4Client.fetchSpecific}, when passed a sequence for\n        C{headerNumber}, sends the I{BODY[N.M]} command.  It returns a\n        L{Deferred} which fires with a C{dict} mapping message sequence numbers\n        to C{list}s of corresponding message data given by the server's\n        response.\n        \"\"\"\n        d = self.client.fetchSpecific('7', headerNumber=(1, 2, 3))\n        self.assertEqual(\n            self.transport.value(), b'0001 FETCH 7 BODY[1.2.3]\\r\\n')\n        self.client.lineReceived(b'* 7 FETCH (BODY[1.2.3] \"Some body\")')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.assertEqual(\n            self.successResultOf(d),\n            {7: [['BODY', ['1.2.3'], \"Some body\"]]})\n\n\n    def test_fetchSpecificText(self):\n        \"\"\"\n        L{IMAP4Client.fetchSpecific}, when passed C{'TEXT'} for C{headerType},\n        sends the I{BODY[TEXT]} command.  It returns a L{Deferred} which fires\n        with a C{dict} mapping message sequence numbers to C{list}s of\n        corresponding message data given by the server's response.\n        \"\"\"\n        d = self.client.fetchSpecific('8', headerType='TEXT')\n        self.assertEqual(\n            self.transport.value(), b'0001 FETCH 8 BODY[TEXT]\\r\\n')\n        self.client.lineReceived(b'* 8 FETCH (BODY[TEXT] \"Some body\")')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.assertEqual(\n            self.successResultOf(d),\n            {8: [['BODY', ['TEXT'], \"Some body\"]]})\n\n\n    def test_fetchSpecificNumberedText(self):\n        \"\"\"\n        If passed a value for the C{headerNumber} parameter and C{'TEXT'} for\n        the C{headerType} parameter, L{IMAP4Client.fetchSpecific} sends a\n        I{BODY[number.TEXT]} request and returns a L{Deferred} which fires with\n        a C{dict} mapping message sequence numbers to C{list}s of message data\n        given by the server's response.\n        \"\"\"\n        d = self.client.fetchSpecific('4', headerType='TEXT', headerNumber=7)\n        self.assertEqual(\n            self.transport.value(), b'0001 FETCH 4 BODY[7.TEXT]\\r\\n')\n        self.client.lineReceived(b'* 4 FETCH (BODY[7.TEXT] \"Some body\")')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.assertEqual(\n            self.successResultOf(d),\n            {4: [['BODY', ['7.TEXT'], \"Some body\"]]})\n\n\n    def test_incompleteFetchSpecificTextResponse(self):\n        \"\"\"\n        If the server responds to a I{BODY[TEXT]} request with a I{FETCH} line\n        which is truncated after the I{BODY[TEXT]} tokens, the L{Deferred}\n        returned by L{IMAP4Client.fetchUID} fails with\n        L{IllegalServerResponse}.\n        \"\"\"\n        d = self.client.fetchSpecific('8', headerType='TEXT')\n        self.assertEqual(\n            self.transport.value(), b'0001 FETCH 8 BODY[TEXT]\\r\\n')\n        self.client.lineReceived(b'* 8 FETCH (BODY[TEXT])')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.failureResultOf(d, imap4.IllegalServerResponse)\n\n\n    def test_fetchSpecificMIME(self):\n        \"\"\"\n        L{IMAP4Client.fetchSpecific}, when passed C{'MIME'} for C{headerType},\n        sends the I{BODY[MIME]} command.  It returns a L{Deferred} which fires\n        with a C{dict} mapping message sequence numbers to C{list}s of\n        corresponding message data given by the server's response.\n        \"\"\"\n        d = self.client.fetchSpecific('8', headerType='MIME')\n        self.assertEqual(\n            self.transport.value(), b'0001 FETCH 8 BODY[MIME]\\r\\n')\n        self.client.lineReceived(b'* 8 FETCH (BODY[MIME] \"Some body\")')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.assertEqual(\n            self.successResultOf(d),\n            {8: [['BODY', ['MIME'], \"Some body\"]]})\n\n\n    def test_fetchSpecificPartial(self):\n        \"\"\"\n        L{IMAP4Client.fetchSpecific}, when passed C{offset} and C{length},\n        sends a partial content request (like I{BODY[TEXT]<offset.length>}).\n        It returns a L{Deferred} which fires with a C{dict} mapping message\n        sequence numbers to C{list}s of corresponding message data given by the\n        server's response.\n        \"\"\"\n        d = self.client.fetchSpecific(\n            '9', headerType='TEXT', offset=17, length=3)\n        self.assertEqual(\n            self.transport.value(), b'0001 FETCH 9 BODY[TEXT]<17.3>\\r\\n')\n        self.client.lineReceived(b'* 9 FETCH (BODY[TEXT]<17> \"foo\")')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.assertEqual(\n            self.successResultOf(d),\n            {9: [['BODY', ['TEXT'], '<17>', 'foo']]})\n\n\n    def test_incompleteFetchSpecificPartialResponse(self):\n        \"\"\"\n        If the server responds to a I{BODY[TEXT]} request with a I{FETCH} line\n        which is truncated after the I{BODY[TEXT]<offset>} tokens, the\n        L{Deferred} returned by L{IMAP4Client.fetchUID} fails with\n        L{IllegalServerResponse}.\n        \"\"\"\n        d = self.client.fetchSpecific('8', headerType='TEXT')\n        self.assertEqual(\n            self.transport.value(), b'0001 FETCH 8 BODY[TEXT]\\r\\n')\n        self.client.lineReceived(b'* 8 FETCH (BODY[TEXT]<17>)')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.failureResultOf(d, imap4.IllegalServerResponse)\n\n\n    def test_fetchSpecificHTML(self):\n        \"\"\"\n        If the body of a message begins with I{<} and ends with I{>} (as,\n        for example, HTML bodies typically will), this is still interpreted\n        as the body by L{IMAP4Client.fetchSpecific} (and particularly, not\n        as a length indicator for a response to a request for a partial\n        body).\n        \"\"\"\n        d = self.client.fetchSpecific('7')\n        self.assertEqual(\n            self.transport.value(), b'0001 FETCH 7 BODY[]\\r\\n')\n        self.client.lineReceived(b'* 7 FETCH (BODY[] \"<html>test</html>\")')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.assertEqual(\n            self.successResultOf(d), {7: [['BODY', [], \"<html>test</html>\"]]})\n\n\n    def assertFetchSpecificFieldsWithEmptyList(self, section):\n        \"\"\"\n        Assert that the provided C{BODY} section, when invoked with no\n        arguments, produces an empty list, and that it returns a\n        L{Deferred} which fires with a C{dict} mapping message\n        sequence numbers to C{list}s of corresponding message data\n        given by the server's response.\n\n        @param section: The C{BODY} section to test: either\n            C{'HEADER.FIELDS'} or C{'HEADER.FIELDS.NOT'}\n        @type section: L{str}\n        \"\"\"\n        d = self.client.fetchSpecific('10', headerType=section)\n        self.assertEqual(\n            self.transport.value(),\n            b'0001 FETCH 10 BODY[' + section.encode('ascii') + b' ()]\\r\\n')\n        # It's unclear what the response would look like - would it be\n        # an empty string?  No IMAP server parses an empty list of headers\n        self.client.lineReceived(\n            b'* 10 FETCH (BODY[' + section.encode('ascii') + b' ()] \"\")')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.assertEqual(\n            self.successResultOf(d),\n            {10: [['BODY', [section, []], \"\"]]})\n\n\n    def test_fetchSpecificHeaderFieldsWithoutHeaders(self):\n        \"\"\"\n        L{IMAP4Client.fetchSpecific}, when passed C{'HEADER.FIELDS'}\n        for C{headerType} but no C{headerArgs}, sends the\n        I{BODY[HEADER.FIELDS]} command with no arguments.  It returns\n        a L{Deferred} which fires with a C{dict} mapping message\n        sequence numbers to C{list}s of corresponding message data\n        given by the server's response.\n        \"\"\"\n        self.assertFetchSpecificFieldsWithEmptyList(\"HEADER.FIELDS\")\n\n\n    def test_fetchSpecificHeaderFieldsNotWithoutHeaders(self):\n        \"\"\"\n        L{IMAP4Client.fetchSpecific}, when passed\n        C{'HEADER.FIELDS.NOT'} for C{headerType} but no C{headerArgs},\n        sends the I{BODY[HEADER.FIELDS.NOT]} command with no\n        arguments.  It returns a L{Deferred} which fires with a\n        C{dict} mapping message sequence numbers to C{list}s of\n        corresponding message data given by the server's response.\n        \"\"\"\n        self.assertFetchSpecificFieldsWithEmptyList(\"HEADER.FIELDS.NOT\")\n\n\n    def test_fetchSpecificHeader(self):\n        \"\"\"\n        L{IMAP4Client.fetchSpecific}, when passed C{'HEADER'} for\n        C{headerType}, sends the I{BODY[HEADER]} command.  It returns\n        a L{Deferred} which fires with a C{dict} mapping message\n        sequence numbers to C{list}s of corresponding message data\n        given by the server's response.\n        \"\"\"\n        d = self.client.fetchSpecific('11', headerType='HEADER')\n        self.assertEqual(\n            self.transport.value(), b'0001 FETCH 11 BODY[HEADER]\\r\\n')\n        self.client.lineReceived(\n            b'* 11 FETCH (BODY[HEADER]'\n            b' \"From: someone@localhost\\r\\nSubject: Some subject\")')\n        self.client.lineReceived(b'0001 OK FETCH completed')\n        self.assertEqual(\n            self.successResultOf(d),\n            {11: [['BODY', ['HEADER'],\n                  \"From: someone@localhost\\r\\nSubject: Some subject\"]]})\n\n\n\nclass IMAP4ClientStoreTests(PreauthIMAP4ClientMixin, unittest.TestCase):\n    \"\"\"\n    Tests for the L{IMAP4Client.setFlags}, L{IMAP4Client.addFlags}, and\n    L{IMAP4Client.removeFlags} methods.\n\n    An example of usage of the STORE command, in terms of which these three\n    methods are implemented, from RFC 3501, section 6.4.6::\n\n        C: A003 STORE 2:4 +FLAGS (\\Deleted)\n        S: * 2 FETCH (FLAGS (\\Deleted \\Seen))\n        S: * 3 FETCH (FLAGS (\\Deleted))\n        S: * 4 FETCH (FLAGS (\\Deleted \\Flagged \\Seen))\n        S: A003 OK STORE completed\n    \"\"\"\n    clientProtocol = StillSimplerClient\n\n    def _flagsTest(self, method, item):\n        \"\"\"\n        Test a non-silent flag modifying method.  Call the method, assert that\n        the correct bytes are sent, deliver a I{FETCH} response, and assert\n        that the result of the Deferred returned by the method is correct.\n\n        @param method: The name of the method to test.\n        @param item: The data item which is expected to be specified.\n        \"\"\"\n        d = getattr(self.client, method)('3', ('\\\\Read', '\\\\Seen'), False)\n        self.assertEqual(\n            self.transport.value(),\n            b'0001 STORE 3 ' + item + b' (\\\\Read \\\\Seen)\\r\\n')\n        self.client.lineReceived(b'* 3 FETCH (FLAGS (\\\\Read \\\\Seen))')\n        self.client.lineReceived(b'0001 OK STORE completed')\n        self.assertEqual(\n            self.successResultOf(d),\n            {3: {'FLAGS': ['\\\\Read', '\\\\Seen']}})\n\n\n    def _flagsSilentlyTest(self, method, item):\n        \"\"\"\n        Test a silent flag modifying method.  Call the method, assert that the\n        correct bytes are sent, deliver an I{OK} response, and assert that the\n        result of the Deferred returned by the method is correct.\n\n        @param method: The name of the method to test.\n        @param item: The data item which is expected to be specified.\n        \"\"\"\n        d = getattr(self.client, method)('3', ('\\\\Read', '\\\\Seen'), True)\n        self.assertEqual(\n            self.transport.value(),\n            b'0001 STORE 3 ' + item + b' (\\\\Read \\\\Seen)\\r\\n')\n        self.client.lineReceived(b'0001 OK STORE completed')\n        self.assertEqual(self.successResultOf(d), {})\n\n\n    def _flagsSilentlyWithUnsolicitedDataTest(self, method, item):\n        \"\"\"\n        Test unsolicited data received in response to a silent flag modifying\n        method.  Call the method, assert that the correct bytes are sent,\n        deliver the unsolicited I{FETCH} response, and assert that the result\n        of the Deferred returned by the method is correct.\n\n        @param method: The name of the method to test.\n        @param item: The data item which is expected to be specified.\n        \"\"\"\n        d = getattr(self.client, method)('3', ('\\\\Read', '\\\\Seen'), True)\n        self.assertEqual(\n            self.transport.value(),\n            b'0001 STORE 3 ' + item + b' (\\\\Read \\\\Seen)\\r\\n')\n        self.client.lineReceived(b'* 2 FETCH (FLAGS (\\\\Read \\\\Seen))')\n        self.client.lineReceived(b'0001 OK STORE completed')\n        self.assertEqual(self.successResultOf(d), {})\n        self.assertEqual(self.client.flags, {2: ['\\\\Read', '\\\\Seen']})\n\n\n    def test_setFlags(self):\n        \"\"\"\n        When passed a C{False} value for the C{silent} parameter,\n        L{IMAP4Client.setFlags} sends the I{STORE} command with a I{FLAGS} data\n        item and returns a L{Deferred} which fires with a C{dict} mapping\n        message sequence numbers to C{dict}s mapping C{'FLAGS'} to the new\n        flags of those messages.\n        \"\"\"\n        self._flagsTest('setFlags', b'FLAGS')\n\n\n    def test_setFlagsSilently(self):\n        \"\"\"\n        When passed a C{True} value for the C{silent} parameter,\n        L{IMAP4Client.setFlags} sends the I{STORE} command with a\n        I{FLAGS.SILENT} data item and returns a L{Deferred} which fires with an\n        empty dictionary.\n        \"\"\"\n        self._flagsSilentlyTest('setFlags', b'FLAGS.SILENT')\n\n\n    def test_setFlagsSilentlyWithUnsolicitedData(self):\n        \"\"\"\n        If unsolicited flag data is received in response to a I{STORE}\n        I{FLAGS.SILENT} request, that data is passed to the C{flagsChanged}\n        callback.\n        \"\"\"\n        self._flagsSilentlyWithUnsolicitedDataTest('setFlags', b'FLAGS.SILENT')\n\n\n    def test_addFlags(self):\n        \"\"\"\n        L{IMAP4Client.addFlags} is like L{IMAP4Client.setFlags}, but sends\n        I{+FLAGS} instead of I{FLAGS}.\n        \"\"\"\n        self._flagsTest('addFlags', b'+FLAGS')\n\n\n    def test_addFlagsSilently(self):\n        \"\"\"\n        L{IMAP4Client.addFlags} with a C{True} value for C{silent} behaves like\n        L{IMAP4Client.setFlags} with a C{True} value for C{silent}, but it\n        sends I{+FLAGS.SILENT} instead of I{FLAGS.SILENT}.\n        \"\"\"\n        self._flagsSilentlyTest('addFlags', b'+FLAGS.SILENT')\n\n\n    def test_addFlagsSilentlyWithUnsolicitedData(self):\n        \"\"\"\n        L{IMAP4Client.addFlags} behaves like L{IMAP4Client.setFlags} when used\n        in silent mode and unsolicited data is received.\n        \"\"\"\n        self._flagsSilentlyWithUnsolicitedDataTest('addFlags', b'+FLAGS.SILENT')\n\n\n    def test_removeFlags(self):\n        \"\"\"\n        L{IMAP4Client.removeFlags} is like L{IMAP4Client.setFlags}, but sends\n        I{-FLAGS} instead of I{FLAGS}.\n        \"\"\"\n        self._flagsTest('removeFlags', b'-FLAGS')\n\n\n    def test_removeFlagsSilently(self):\n        \"\"\"\n        L{IMAP4Client.removeFlags} with a C{True} value for C{silent} behaves\n        like L{IMAP4Client.setFlags} with a C{True} value for C{silent}, but it\n        sends I{-FLAGS.SILENT} instead of I{FLAGS.SILENT}.\n        \"\"\"\n        self._flagsSilentlyTest('removeFlags', b'-FLAGS.SILENT')\n\n\n    def test_removeFlagsSilentlyWithUnsolicitedData(self):\n        \"\"\"\n        L{IMAP4Client.removeFlags} behaves like L{IMAP4Client.setFlags} when\n        used in silent mode and unsolicited data is received.\n        \"\"\"\n        self._flagsSilentlyWithUnsolicitedDataTest('removeFlags', b'-FLAGS.SILENT')\n\n\n\nclass IMAP4ClientStatusTests(PreauthIMAP4ClientMixin,\n                             unittest.SynchronousTestCase):\n    \"\"\"\n    Tests for the L{IMAP4Client.status} method.\n\n    An example of usage of the STATUS command from RFC 3501, section\n    5.1.2::\n\n        C: A042 STATUS blurdybloop (UIDNEXT MESSAGES)\n        S: * STATUS blurdybloop (MESSAGES 231 UIDNEXT 44292)\n        S: A042 OK STATUS completed\n\n    @see: U{https://tools.ietf.org/html/rfc3501#section-5.1.2}\n    \"\"\"\n\n    def testUnknownName(self):\n        \"\"\"\n        Only allow sending the C{STATUS} names defined in RFC 3501.\n\n        @see: U{https://tools.ietf.org/html/rfc3501#section-5.1.2}\n        \"\"\"\n        exc = self.assertRaises(\n            ValueError,\n            self.client.status,\n            \"ignored\", \"IMPOSSIBLE?!\",\n        )\n        self.assertEqual(str(exc),\n                         \"Unknown names: \" + repr(set([\"IMPOSSIBLE?!\"])))\n\n\n    def testUndecodableName(self):\n        \"\"\"\n        C{STATUS} names that cannot be decoded as ASCII cause the\n        status Deferred to fail with L{IllegalServerResponse}\n        \"\"\"\n\n        d = self.client.status(\"blurdybloop\", \"MESSAGES\")\n        self.assertEqual(\n            self.transport.value(),\n            b\"0001 STATUS blurdybloop (MESSAGES)\\r\\n\",\n        )\n\n        self.client.lineReceived(\n            b\"* STATUS blurdybloop \"\n            b'(MESSAGES 1 ASCIINAME \"OK\" NOT\\xffASCII \"NO\")'\n        )\n        self.client.lineReceived(b\"0001 OK STATUS completed\")\n        self.failureResultOf(d, imap4.IllegalServerResponse)\n\n\n\nclass IMAP4ClientCopyTests(PreauthIMAP4ClientMixin,\n                           unittest.SynchronousTestCase):\n    \"\"\"\n    Tests for the L{IMAP4Client.copy} method.\n\n    An example of the C{COPY} command, which this method implements,\n    from RFC 3501, section 6.4.7::\n\n        C: A003 COPY 2:4 MEETING\n        S: A003 OK COPY completed\n    \"\"\"\n    clientProtocol = StillSimplerClient\n\n\n    def test_copySequenceNumbers(self):\n        \"\"\"\n        L{IMAP4Client.copy} copies the messages identified by their\n        sequence numbers to the mailbox, returning a L{Deferred} that\n        succeeds with a true value.\n        \"\"\"\n        d = self.client.copy(\"2:3\", \"MEETING\", uid=False)\n\n        self.assertEqual(\n            self.transport.value(),\n            b\"0001 COPY 2:3 MEETING\\r\\n\",\n        )\n\n        self.client.lineReceived(b\"0001 OK COPY completed\")\n        self.assertEqual(self.successResultOf(d),\n                         ([], b'OK COPY completed'))\n\n\n    def test_copySequenceNumbersFails(self):\n        \"\"\"\n        L{IMAP4Client.copy} returns a L{Deferred} that fails with an\n        L{IMAP4Exception} when the messages specified by the given\n        sequence numbers could not be copied to the mailbox.\n        \"\"\"\n        d = self.client.copy(\"2:3\", \"MEETING\", uid=False)\n\n        self.assertEqual(\n            self.transport.value(),\n            b\"0001 COPY 2:3 MEETING\\r\\n\",\n        )\n\n        self.client.lineReceived(b\"0001 BAD COPY failed\")\n        self.assertIsInstance(self.failureResultOf(d).value,\n                              imap4.IMAP4Exception)\n\n\n    def test_copyUIDs(self):\n        \"\"\"\n        L{IMAP4Client.copy} copies the messages identified by their\n        UIDs to the mailbox, returning a L{Deferred} that succeeds\n        with a true value.\n        \"\"\"\n        d = self.client.copy(\"2:3\", \"MEETING\", uid=True)\n\n        self.assertEqual(\n            self.transport.value(),\n            b\"0001 UID COPY 2:3 MEETING\\r\\n\",\n        )\n\n        self.client.lineReceived(b\"0001 OK COPY completed\")\n        self.assertEqual(self.successResultOf(d),\n                         ([], b'OK COPY completed'))\n\n\n    def test_copyUIDsFails(self):\n        \"\"\"\n        L{IMAP4Client.copy} returns a L{Deferred} that fails with an\n        L{IMAP4Exception} when the messages specified by the given\n        UIDs could not be copied to the mailbox.\n        \"\"\"\n        d = self.client.copy(\"2:3\", \"MEETING\", uid=True)\n\n        self.assertEqual(\n            self.transport.value(),\n            b\"0001 UID COPY 2:3 MEETING\\r\\n\",\n        )\n\n        self.client.lineReceived(b\"0001 BAD COPY failed\")\n        self.assertIsInstance(self.failureResultOf(d).value,\n                              imap4.IMAP4Exception)\n\n\n\nclass FakeyServer(imap4.IMAP4Server):\n    state = 'select'\n    timeout = None\n\n    def sendServerGreeting(self):\n        pass\n\n\n\n@implementer(imap4.IMessage)\nclass FakeyMessage(util.FancyStrMixin):\n    showAttributes = ('headers', 'flags', 'date', '_body', 'uid')\n\n    def __init__(self, headers, flags, date, body, uid, subpart):\n        self.headers = headers\n        self.flags = flags\n        self._body = body\n        self.size = len(body)\n        self.date = date\n        self.uid = uid\n        self.subpart = subpart\n\n\n    def getHeaders(self, negate, *names):\n        self.got_headers = negate, names\n        return self.headers\n\n\n    def getFlags(self):\n        return self.flags\n\n\n    def getInternalDate(self):\n        return self.date\n\n\n    def getBodyFile(self):\n        return BytesIO(self._body)\n\n\n    def getSize(self):\n        return self.size\n\n\n    def getUID(self):\n        return self.uid\n\n\n    def isMultipart(self):\n        return self.subpart is not None\n\n\n    def getSubPart(self, part):\n        self.got_subpart = part\n        return self.subpart[part]\n\n\n\nclass NewStoreTests(unittest.TestCase, IMAP4HelperMixin):\n    result = None\n    storeArgs = None\n\n    def setUp(self):\n        self.received_messages = self.received_uid = None\n\n        self.server = imap4.IMAP4Server()\n        self.server.state = 'select'\n        self.server.mbox = self\n        self.connected = defer.Deferred()\n        self.client = SimpleClient(self.connected)\n\n\n    def addListener(self, x):\n        pass\n\n\n    def removeListener(self, x):\n        pass\n\n\n    def store(self, *args, **kw):\n        self.storeArgs = args, kw\n        return self.response\n\n\n    def _storeWork(self):\n        def connected():\n            return self.function(self.messages, self.flags, self.silent, self.uid)\n\n        def result(R):\n            self.result = R\n\n        self.connected.addCallback(strip(connected)\n        ).addCallback(result\n        ).addCallback(self._cbStopClient\n        ).addErrback(self._ebGeneral)\n\n\n        def check(ignored):\n            self.assertEqual(self.result, self.expected)\n            self.assertEqual(self.storeArgs, self.expectedArgs)\n        d = loopback.loopbackTCP(self.server, self.client, noisy=False)\n        d.addCallback(check)\n        return d\n\n\n    def testSetFlags(self, uid=0):\n        self.function = self.client.setFlags\n        self.messages = '1,5,9'\n        self.flags = ['\\\\A', '\\\\B', 'C']\n        self.silent = False\n        self.uid = uid\n        self.response = {\n            1: ['\\\\A', '\\\\B', 'C'],\n            5: ['\\\\A', '\\\\B', 'C'],\n            9: ['\\\\A', '\\\\B', 'C'],\n        }\n        self.expected = {\n            1: {'FLAGS': ['\\\\A', '\\\\B', 'C']},\n            5: {'FLAGS': ['\\\\A', '\\\\B', 'C']},\n            9: {'FLAGS': ['\\\\A', '\\\\B', 'C']},\n        }\n        msg = imap4.MessageSet()\n        msg.add(1)\n        msg.add(5)\n        msg.add(9)\n        self.expectedArgs = ((msg, ['\\\\A', '\\\\B', 'C'], 0), {'uid': 0})\n        return self._storeWork()\n\n\n\nclass GetBodyStructureTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{imap4.getBodyStructure}, a helper for constructing a list which\n    directly corresponds to the wire information needed for a I{BODY} or\n    I{BODYSTRUCTURE} response.\n    \"\"\"\n    def test_singlePart(self):\n        \"\"\"\n        L{imap4.getBodyStructure} accepts a L{IMessagePart} provider and returns\n        a list giving the basic fields for the I{BODY} response for that\n        message.\n        \"\"\"\n        body = b'hello, world'\n        major = 'image'\n        minor = 'jpeg'\n        charset = 'us-ascii'\n        identifier = 'some kind of id'\n        description = 'great justice'\n        encoding = 'maximum'\n        msg = FakeyMessage({\n                'content-type': major + '/' + minor +\n                                 '; charset=' + charset + '; x=y',\n                'content-id': identifier,\n                'content-description': description,\n                'content-transfer-encoding': encoding,\n                }, (), b'', body, 123, None)\n        structure = imap4.getBodyStructure(msg)\n        self.assertEqual(\n            [major, minor, [\"charset\", charset, 'x', 'y'], identifier,\n             description, encoding, len(body)],\n            structure)\n\n\n    def test_emptyContentType(self):\n        \"\"\"\n        L{imap4.getBodyStructure} returns L{None} for the major and\n        minor MIME types of a L{IMessagePart} provider whose headers\n        lack a C{Content-Type}, or have an empty value for it.\n        \"\"\"\n        missing = FakeyMessage({}, (), b'', b'', 123, None)\n        missingContentTypeStructure = imap4.getBodyStructure(missing)\n        missingMajor, missingMinor = missingContentTypeStructure[:2]\n        self.assertIs(None, missingMajor)\n        self.assertIs(None, missingMinor)\n\n        empty = FakeyMessage({\"content-type\": \"\"}, (), b'', b'', 123, None)\n        emptyContentTypeStructure = imap4.getBodyStructure(empty)\n        emptyMajor, emptyMinor = emptyContentTypeStructure[:2]\n        self.assertIs(None, emptyMajor)\n        self.assertIs(None, emptyMinor)\n\n        newline = FakeyMessage({\"content-type\": \"\\n\"}, (), b'', b'', 123, None)\n        newlineContentTypeStructure = imap4.getBodyStructure(newline)\n        newlineMajor, newlineMinor = newlineContentTypeStructure[:2]\n        self.assertIs(None, newlineMajor)\n        self.assertIs(None, newlineMinor)\n\n\n    def test_onlyMajorContentType(self):\n        \"\"\"\n        L{imap4.getBodyStructure} returns only a non-L{None} major\n        MIME type for a L{IMessagePart} provider whose headers only\n        have a main a C{Content-Type}.\n        \"\"\"\n        main = FakeyMessage({\"content-type\": \"main\"}, (), b'', b'', 123, None)\n        mainStructure = imap4.getBodyStructure(main)\n        mainMajor, mainMinor = mainStructure[:2]\n        self.assertEqual(mainMajor, \"main\")\n        self.assertIs(mainMinor, None)\n\n\n    def test_singlePartExtended(self):\n        \"\"\"\n        L{imap4.getBodyStructure} returns a list giving the basic and extended\n        fields for a I{BODYSTRUCTURE} response if passed C{True} for the\n        C{extended} parameter.\n        \"\"\"\n        body = b'hello, world'\n        major = 'image'\n        minor = 'jpeg'\n        charset = 'us-ascii'\n        identifier = 'some kind of id'\n        description = 'great justice'\n        encoding = 'maximum'\n        md5 = 'abcdefabcdef'\n        msg = FakeyMessage({\n                'content-type': major + '/' + minor +\n                                 '; charset=' + charset + '; x=y',\n                'content-id': identifier,\n                'content-description': description,\n                'content-transfer-encoding': encoding,\n                'content-md5': md5,\n                'content-disposition': 'attachment; name=foo; size=bar',\n                'content-language': 'fr',\n                'content-location': 'France',\n                }, (), '', body, 123, None)\n        structure = imap4.getBodyStructure(msg, extended=True)\n        self.assertEqual(\n            [major, minor, [\"charset\", charset, 'x', 'y'], identifier,\n             description, encoding, len(body), md5,\n             ['attachment', ['name', 'foo', 'size', 'bar']], 'fr', 'France'],\n            structure)\n\n\n    def test_singlePartWithMissing(self):\n        \"\"\"\n        For fields with no information contained in the message headers,\n        L{imap4.getBodyStructure} fills in L{None} values in its result.\n        \"\"\"\n        major = 'image'\n        minor = 'jpeg'\n        body = b'hello, world'\n        msg = FakeyMessage({\n                'content-type': major + '/' + minor\n                }, (), b'', body, 123, None)\n        structure = imap4.getBodyStructure(msg, extended=True)\n        self.assertEqual(\n            [major, minor, None, None, None, None, len(body), None, None,\n             None, None],\n            structure)\n\n\n    def test_textPart(self):\n        \"\"\"\n        For a I{text/*} message, the number of lines in the message body are\n        included after the common single-part basic fields.\n        \"\"\"\n        body = b'hello, world\\nhow are you?\\ngoodbye\\n'\n        major = 'text'\n        minor = 'jpeg'\n        charset = 'us-ascii'\n        identifier = 'some kind of id'\n        description = 'great justice'\n        encoding = 'maximum'\n        msg = FakeyMessage({\n                'content-type': major + '/' + minor +\n                                 '; charset=' + charset + '; x=y',\n                'content-id': identifier,\n                'content-description': description,\n                'content-transfer-encoding': encoding,\n                }, (), b'', body, 123, None)\n        structure = imap4.getBodyStructure(msg)\n        self.assertEqual(\n            [major, minor, [\"charset\", charset, 'x', 'y'], identifier,\n             description, encoding, len(body), len(body.splitlines())],\n            structure)\n\n\n    def test_rfc822Message(self):\n        \"\"\"\n        For a I{message/rfc822} message, the common basic fields are followed\n        by information about the contained message.\n        \"\"\"\n        body = b'hello, world\\nhow are you?\\ngoodbye\\n'\n        major = 'text'\n        minor = 'jpeg'\n        charset = 'us-ascii'\n        identifier = 'some kind of id'\n        description = 'great justice'\n        encoding = 'maximum'\n        msg = FakeyMessage({\n                'content-type': major + '/' + minor +\n                                 '; charset=' + charset + '; x=y',\n                'from': 'Alice <alice@example.com>',\n                'to': 'Bob <bob@example.com>',\n                'content-id': identifier,\n                'content-description': description,\n                'content-transfer-encoding': encoding,\n                }, (), '', body, 123, None)\n\n        container = FakeyMessage({\n                'content-type': 'message/rfc822',\n                }, (), b'', b'', 123, [msg])\n\n        structure = imap4.getBodyStructure(container)\n        self.assertEqual(\n            ['message', 'rfc822', None, None, None, None, 0,\n             imap4.getEnvelope(msg), imap4.getBodyStructure(msg), 3],\n            structure)\n\n\n    def test_multiPart(self):\n        \"\"\"\n        For a I{multipart/*} message, L{imap4.getBodyStructure} returns a list\n        containing the body structure information for each part of the message\n        followed by an element giving the MIME subtype of the message.\n        \"\"\"\n        oneSubPart = FakeyMessage({\n                'content-type': 'image/jpeg; x=y',\n                'content-id': 'some kind of id',\n                'content-description': 'great justice',\n                'content-transfer-encoding': 'maximum',\n                }, (), b'', b'hello world', 123, None)\n\n        anotherSubPart = FakeyMessage({\n                'content-type': 'text/plain; charset=us-ascii',\n                }, (), b'', b'some stuff', 321, None)\n\n        container = FakeyMessage({\n                'content-type': 'multipart/related',\n                }, (), b'', b'', 555, [oneSubPart, anotherSubPart])\n\n        self.assertEqual(\n            [imap4.getBodyStructure(oneSubPart),\n             imap4.getBodyStructure(anotherSubPart),\n             'related'],\n            imap4.getBodyStructure(container))\n\n\n    def test_multiPartExtended(self):\n        \"\"\"\n        When passed a I{multipart/*} message and C{True} for the C{extended}\n        argument, L{imap4.getBodyStructure} includes extended structure\n        information from the parts of the multipart message and extended\n        structure information about the multipart message itself.\n        \"\"\"\n        oneSubPart = FakeyMessage({\n                b'content-type': b'image/jpeg; x=y',\n                b'content-id': b'some kind of id',\n                b'content-description': b'great justice',\n                b'content-transfer-encoding': b'maximum',\n                }, (), b'', b'hello world', 123, None)\n\n        anotherSubPart = FakeyMessage({\n                b'content-type': b'text/plain; charset=us-ascii',\n                }, (), b'', b'some stuff', 321, None)\n\n        container = FakeyMessage({\n                'content-type': 'multipart/related; foo=bar',\n                'content-language': 'es',\n                'content-location': 'Spain',\n                'content-disposition': 'attachment; name=monkeys',\n                }, (), b'', b'', 555, [oneSubPart, anotherSubPart])\n\n        self.assertEqual(\n            [imap4.getBodyStructure(oneSubPart, extended=True),\n             imap4.getBodyStructure(anotherSubPart, extended=True),\n             'related', ['foo', 'bar'], ['attachment', ['name', 'monkeys']],\n             'es', 'Spain'],\n            imap4.getBodyStructure(container, extended=True))\n\n\n\nclass NewFetchTests(unittest.TestCase, IMAP4HelperMixin):\n    def setUp(self):\n        self.received_messages = self.received_uid = None\n        self.result = None\n\n        self.server = imap4.IMAP4Server()\n        self.server.state = 'select'\n        self.server.mbox = self\n        self.connected = defer.Deferred()\n        self.client = SimpleClient(self.connected)\n\n\n    def addListener(self, x):\n        pass\n\n\n    def removeListener(self, x):\n        pass\n\n\n    def fetch(self, messages, uid):\n        self.received_messages = messages\n        self.received_uid = uid\n        return iter(zip(range(len(self.msgObjs)), self.msgObjs))\n\n\n    def _fetchWork(self, uid):\n        if uid:\n            for (i, msg) in zip(range(len(self.msgObjs)), self.msgObjs):\n                self.expected[i]['UID'] = str(msg.getUID())\n\n        def result(R):\n            self.result = R\n\n        self.connected.addCallback(lambda _: self.function(self.messages, uid)\n        ).addCallback(result\n        ).addCallback(self._cbStopClient\n        ).addErrback(self._ebGeneral)\n\n        d = loopback.loopbackTCP(self.server, self.client, noisy=False)\n        d.addCallback(lambda x : self.assertEqual(self.result, self.expected))\n        return d\n\n\n    def testFetchUID(self):\n        self.function = lambda m, u: self.client.fetchUID(m)\n\n        self.messages = '7'\n        self.msgObjs = [\n            FakeyMessage({}, (), b'', b'', 12345, None),\n            FakeyMessage({}, (), b'', b'', 999, None),\n            FakeyMessage({}, (), b'', b'', 10101, None),\n        ]\n        self.expected = {\n            0: {'UID': '12345'},\n            1: {'UID': '999'},\n            2: {'UID': '10101'},\n        }\n        return self._fetchWork(0)\n\n\n    def testFetchFlags(self, uid=0):\n        self.function = self.client.fetchFlags\n        self.messages = '9'\n        self.msgObjs = [\n            FakeyMessage({}, ['FlagA', 'FlagB', '\\\\FlagC'],\n                         b'', b'', 54321, None),\n            FakeyMessage({}, ['\\\\FlagC', 'FlagA', 'FlagB'],\n                         b'', b'', 12345, None),\n        ]\n        self.expected = {\n            0: {'FLAGS': ['FlagA', 'FlagB', '\\\\FlagC']},\n            1: {'FLAGS': ['\\\\FlagC', 'FlagA', 'FlagB']},\n        }\n        return self._fetchWork(uid)\n\n\n    def testFetchFlagsUID(self):\n        return self.testFetchFlags(1)\n\n\n    def testFetchInternalDate(self, uid=0):\n        self.function = self.client.fetchInternalDate\n        self.messages = '13'\n        self.msgObjs = [\n            FakeyMessage({}, (), b'Fri, 02 Nov 2003 21:25:10 GMT', b'', 23232, None),\n            FakeyMessage({}, (), b'Thu, 29 Dec 2013 11:31:52 EST', b'', 101, None),\n            FakeyMessage({}, (), b'Mon, 10 Mar 1992 02:44:30 CST', b'', 202, None),\n            FakeyMessage({}, (), b'Sat, 11 Jan 2000 14:40:24 PST', b'', 303, None),\n        ]\n        self.expected = {\n            0: {'INTERNALDATE': '02-Nov-2003 21:25:10 +0000'},\n            1: {'INTERNALDATE': '29-Dec-2013 11:31:52 -0500'},\n            2: {'INTERNALDATE': '10-Mar-1992 02:44:30 -0600'},\n            3: {'INTERNALDATE': '11-Jan-2000 14:40:24 -0800'},\n        }\n        return self._fetchWork(uid)\n\n\n    def testFetchInternalDateUID(self):\n        return self.testFetchInternalDate(1)\n\n\n    def test_fetchInternalDateLocaleIndependent(self):\n        \"\"\"\n        The month name in the date is locale independent.\n        \"\"\"\n        # Fake that we're in a language where December is not Dec\n        currentLocale = locale.setlocale(locale.LC_ALL, None)\n        locale.setlocale(locale.LC_ALL, \"es_AR.UTF8\")\n        self.addCleanup(locale.setlocale, locale.LC_ALL, currentLocale)\n        return self.testFetchInternalDate(1)\n\n    # if alternate locale is not available, the previous test will be skipped,\n    # please install this locale for it to run.  Avoid using locale.getlocale to\n    # learn the current locale; its values don't round-trip well on all\n    # platforms.  Fortunately setlocale returns a value which does round-trip\n    # well.\n    currentLocale = locale.setlocale(locale.LC_ALL, None)\n    try:\n        locale.setlocale(locale.LC_ALL, \"es_AR.UTF8\")\n    except locale.Error:\n        test_fetchInternalDateLocaleIndependent.skip = (\n            \"The es_AR.UTF8 locale is not installed.\")\n    else:\n        locale.setlocale(locale.LC_ALL, currentLocale)\n\n\n    def testFetchEnvelope(self, uid=0):\n        self.function = self.client.fetchEnvelope\n        self.messages = '15'\n        self.msgObjs = [\n            FakeyMessage({\n                'from': 'user@domain',\n                'to': 'resu@domain',\n                'date': 'thursday',\n                'subject': 'it is a message',\n                'message-id': 'id-id-id-yayaya'\n            }, (), b'', b'', 65656, None),\n        ]\n        self.expected = {\n            0: {'ENVELOPE':\n                ['thursday', 'it is a message',\n                    [[None, None, 'user', 'domain']],\n                    [[None, None, 'user', 'domain']],\n                    [[None, None, 'user', 'domain']],\n                    [[None, None, 'resu', 'domain']],\n                    None, None, None, 'id-id-id-yayaya']\n            }\n        }\n        return self._fetchWork(uid)\n\n\n    def testFetchEnvelopeUID(self):\n        return self.testFetchEnvelope(1)\n\n\n    def test_fetchBodyStructure(self, uid=0):\n        \"\"\"\n        L{IMAP4Client.fetchBodyStructure} issues a I{FETCH BODYSTRUCTURE}\n        command and returns a Deferred which fires with a structure giving the\n        result of parsing the server's response.  The structure is a list\n        reflecting the parenthesized data sent by the server, as described by\n        RFC 3501, section 7.4.2.\n        \"\"\"\n        self.function = self.client.fetchBodyStructure\n        self.messages = '3:9,10:*'\n        self.msgObjs = [FakeyMessage({\n                'content-type': 'text/plain; name=thing; key=\"value\"',\n                'content-id': 'this-is-the-content-id',\n                'content-description': 'describing-the-content-goes-here!',\n                'content-transfer-encoding': '8BIT',\n                'content-md5': 'abcdef123456',\n                'content-disposition': 'attachment; filename=monkeys',\n                'content-language': 'es',\n                'content-location': 'http://example.com/monkeys',\n            }, (), '', b'Body\\nText\\nGoes\\nHere\\n', 919293, None)]\n        self.expected = {0: {'BODYSTRUCTURE': [\n            'text', 'plain', ['key', 'value', 'name', 'thing'],\n            'this-is-the-content-id', 'describing-the-content-goes-here!',\n            '8BIT', '20', '4', 'abcdef123456',\n            ['attachment', ['filename', 'monkeys']], 'es',\n             'http://example.com/monkeys']}}\n        return self._fetchWork(uid)\n\n\n    def testFetchBodyStructureUID(self):\n        \"\"\"\n        If passed C{True} for the C{uid} argument, C{fetchBodyStructure} can\n        also issue a I{UID FETCH BODYSTRUCTURE} command.\n        \"\"\"\n        return self.test_fetchBodyStructure(1)\n\n\n    def test_fetchBodyStructureMultipart(self, uid=0):\n        \"\"\"\n        L{IMAP4Client.fetchBodyStructure} can also parse the response to a\n        I{FETCH BODYSTRUCTURE} command for a multipart message.\n        \"\"\"\n        self.function = self.client.fetchBodyStructure\n        self.messages = '3:9,10:*'\n        innerMessage = FakeyMessage({\n                'content-type': 'text/plain; name=thing; key=\"value\"',\n                'content-id': 'this-is-the-content-id',\n                'content-description': 'describing-the-content-goes-here!',\n                'content-transfer-encoding': '8BIT',\n                'content-language': 'fr',\n                'content-md5': '123456abcdef',\n                'content-disposition': 'inline',\n                'content-location': 'outer space',\n            }, (), b'', b'Body\\nText\\nGoes\\nHere\\n', 919293, None)\n        self.msgObjs = [FakeyMessage({\n                'content-type': 'multipart/mixed; boundary=\"xyz\"',\n                'content-language': 'en',\n                'content-location': 'nearby',\n            }, (), b'', b'', 919293, [innerMessage])]\n        self.expected = {0: {'BODYSTRUCTURE': [\n            ['text', 'plain', ['key', 'value', 'name', 'thing'],\n             'this-is-the-content-id', 'describing-the-content-goes-here!',\n             '8BIT', '20', '4', '123456abcdef', ['inline', None], 'fr',\n             'outer space'],\n            'mixed', ['boundary', 'xyz'], None, 'en', 'nearby'\n            ]}}\n        return self._fetchWork(uid)\n\n\n    def testFetchSimplifiedBody(self, uid=0):\n        self.function = self.client.fetchSimplifiedBody\n        self.messages = '21'\n        self.msgObjs = [FakeyMessage({}, (), b'', b'Yea whatever', 91825,\n            [FakeyMessage({'content-type': 'image/jpg'}, (), b'',\n                b'Body Body Body', None, None\n            )]\n        )]\n        self.expected = {0:\n            {'BODY':\n                [None, None, None, None, None, None, '12']\n            }\n        }\n\n        return self._fetchWork(uid)\n\n\n    def testFetchSimplifiedBodyUID(self):\n        return self.testFetchSimplifiedBody(1)\n\n\n    def testFetchSimplifiedBodyText(self, uid=0):\n        self.function = self.client.fetchSimplifiedBody\n        self.messages = '21'\n        self.msgObjs = [FakeyMessage({'content-type': 'text/plain'},\n            (), b'', b'Yea whatever', 91825, None)]\n        self.expected = {0:\n            {'BODY':\n                ['text', 'plain', None, None, None, None,\n                    '12', '1'\n                ]\n            }\n        }\n\n        return self._fetchWork(uid)\n\n\n    def testFetchSimplifiedBodyTextUID(self):\n        return self.testFetchSimplifiedBodyText(1)\n\n\n    def testFetchSimplifiedBodyRFC822(self, uid=0):\n        self.function = self.client.fetchSimplifiedBody\n        self.messages = '21'\n        self.msgObjs = [FakeyMessage({'content-type': 'message/rfc822'},\n            (), b'', b'Yea whatever', 91825,\n            [FakeyMessage({'content-type': 'image/jpg'}, (), '',\n                b'Body Body Body', None, None\n            )]\n        )]\n        self.expected = {0:\n            {'BODY':\n                ['message', 'rfc822', None, None, None, None,\n                    '12', [None, None, [[None, None, None]],\n                    [[None, None, None]], None, None, None,\n                    None, None, None], ['image', 'jpg', None,\n                    None, None, None, '14'], '1'\n                ]\n            }\n        }\n\n        return self._fetchWork(uid)\n\n\n    def testFetchSimplifiedBodyRFC822UID(self):\n        return self.testFetchSimplifiedBodyRFC822(1)\n\n\n    def test_fetchSimplifiedBodyMultipart(self):\n        \"\"\"\n        L{IMAP4Client.fetchSimplifiedBody} returns a dictionary mapping message\n        sequence numbers to fetch responses for the corresponding messages.  In\n        particular, for a multipart message, the value in the dictionary maps\n        the string C{\"BODY\"} to a list giving the body structure information for\n        that message, in the form of a list of subpart body structure\n        information followed by the subtype of the message (eg C{\"alternative\"}\n        for a I{multipart/alternative} message).  This structure is self-similar\n        in the case where a subpart is itself multipart.\n        \"\"\"\n        self.function = self.client.fetchSimplifiedBody\n        self.messages = '21'\n\n        # A couple non-multipart messages to use as the inner-most payload\n        singles = [\n            FakeyMessage(\n                {'content-type': 'text/plain'},\n                (), b'date', b'Stuff', 54321,  None),\n            FakeyMessage(\n                {'content-type': 'text/html'},\n                (), b'date', b'Things', 32415, None)]\n\n        # A multipart/alternative message containing the above non-multipart\n        # messages.  This will be the payload of the outer-most message.\n        alternative = FakeyMessage(\n            {'content-type': 'multipart/alternative'},\n            (), b'', b'Irrelevant', 12345, singles)\n\n        # The outer-most message, also with a multipart type, containing just\n        # the single middle message.\n        mixed = FakeyMessage(\n            # The message is multipart/mixed\n            {'content-type': 'multipart/mixed'},\n            (), b'', b'RootOf', 98765, [alternative])\n\n        self.msgObjs = [mixed]\n\n        self.expected = {\n            0: {'BODY': [\n                    [['text', 'plain', None, None, None, None, '5', '1'],\n                     ['text', 'html', None, None, None, None, '6', '1'],\n                     'alternative'],\n                    'mixed']}}\n\n        return self._fetchWork(False)\n\n\n    def testFetchMessage(self, uid=0):\n        self.function = self.client.fetchMessage\n        self.messages = '1,3,7,10101'\n        self.msgObjs = [\n            FakeyMessage({'Header': 'Value'}, (), b'', b'BODY TEXT\\r\\n', 91, None),\n        ]\n        self.expected = {\n            0: {'RFC822': 'Header: Value\\r\\n\\r\\nBODY TEXT\\r\\n'}\n        }\n        return self._fetchWork(uid)\n\n\n    def testFetchMessageUID(self):\n        return self.testFetchMessage(1)\n\n\n    def testFetchHeaders(self, uid=0):\n        self.function = self.client.fetchHeaders\n        self.messages = '9,6,2'\n        self.msgObjs = [\n            FakeyMessage({'H1': 'V1', 'H2': 'V2'}, (), b'', b'', 99, None),\n        ]\n\n        headers = nativeString(\n            imap4._formatHeaders({'H1': 'V1', 'H2': 'V2'}))\n\n        self.expected = {\n            0: {'RFC822.HEADER': headers},\n        }\n        return self._fetchWork(uid)\n\n\n    def testFetchHeadersUID(self):\n        return self.testFetchHeaders(1)\n\n\n    def testFetchBody(self, uid=0):\n        self.function = self.client.fetchBody\n        self.messages = '1,2,3,4,5,6,7'\n        self.msgObjs = [\n            FakeyMessage({'Header': 'Value'}, (), '', b'Body goes here\\r\\n', 171, None),\n        ]\n        self.expected = {\n            0: {'RFC822.TEXT': 'Body goes here\\r\\n'},\n        }\n        return self._fetchWork(uid)\n\n\n    def testFetchBodyUID(self):\n        return self.testFetchBody(1)\n\n\n    def testFetchBodyParts(self):\n        \"\"\"\n        Test the server's handling of requests for specific body sections.\n        \"\"\"\n        self.function = self.client.fetchSpecific\n        self.messages = '1'\n        outerBody = ''\n        innerBody1 = b'Contained body message text.  Squarge.'\n        innerBody2 = b'Secondary <i>message</i> text of squarge body.'\n        headers = OrderedDict()\n        headers['from'] = 'sender@host'\n        headers['to'] = 'recipient@domain'\n        headers['subject'] = 'booga booga boo'\n        headers['content-type'] = 'multipart/alternative; boundary=\"xyz\"'\n        innerHeaders = OrderedDict()\n        innerHeaders['subject'] = 'this is subject text'\n        innerHeaders['content-type'] = 'text/plain'\n        innerHeaders2 = OrderedDict()\n        innerHeaders2['subject'] = '<b>this is subject</b>'\n        innerHeaders2['content-type'] = 'text/html'\n        self.msgObjs = [FakeyMessage(\n            headers, (), None, outerBody, 123,\n            [FakeyMessage(innerHeaders, (), None, innerBody1, None, None),\n             FakeyMessage(innerHeaders2, (), None, innerBody2, None, None)])]\n        self.expected = {\n            0: [['BODY', ['1'], 'Contained body message text.  Squarge.']]}\n\n\n        def result(R):\n            self.result = R\n\n        self.connected.addCallback(\n            lambda _: self.function(self.messages, headerNumber=1))\n        self.connected.addCallback(result)\n        self.connected.addCallback(self._cbStopClient)\n        self.connected.addErrback(self._ebGeneral)\n\n        d = loopback.loopbackTCP(self.server, self.client, noisy=False)\n        d.addCallback(lambda ign: self.assertEqual(self.result, self.expected))\n        return d\n\n\n    def test_fetchBodyPartOfNonMultipart(self):\n        \"\"\"\n        Single-part messages have an implicit first part which clients\n        should be able to retrieve explicitly.  Test that a client\n        requesting part 1 of a text/plain message receives the body of the\n        text/plain part.\n        \"\"\"\n        self.function = self.client.fetchSpecific\n        self.messages = '1'\n        parts = [1]\n        outerBody = b'DA body'\n        headers = OrderedDict()\n        headers['from'] = 'sender@host'\n        headers['to'] = 'recipient@domain'\n        headers['subject'] = 'booga booga boo'\n        headers['content-type'] = 'text/plain'\n        self.msgObjs = [FakeyMessage(\n            headers, (), None, outerBody, 123, None)]\n\n        self.expected = {0: [['BODY', ['1'], 'DA body']]}\n\n        def result(R):\n            self.result = R\n\n        self.connected.addCallback(\n            lambda _: self.function(self.messages, headerNumber=parts))\n        self.connected.addCallback(result)\n        self.connected.addCallback(self._cbStopClient)\n        self.connected.addErrback(self._ebGeneral)\n\n        d = loopback.loopbackTCP(self.server, self.client, noisy=False)\n        d.addCallback(lambda ign: self.assertEqual(self.result, self.expected))\n        return d\n\n\n    def testFetchSize(self, uid=0):\n        self.function = self.client.fetchSize\n        self.messages = '1:100,2:*'\n        self.msgObjs = [\n            FakeyMessage({}, (), b'', b'x' * 20, 123, None),\n        ]\n        self.expected = {\n            0: {'RFC822.SIZE': '20'},\n        }\n        return self._fetchWork(uid)\n\n\n    def testFetchSizeUID(self):\n        return self.testFetchSize(1)\n\n\n    def testFetchFull(self, uid=0):\n        self.function = self.client.fetchFull\n        self.messages = '1,3'\n        self.msgObjs = [\n            FakeyMessage({}, ('\\\\XYZ', '\\\\YZX', 'Abc'),\n                b'Sun, 25 Jul 2010 06:20:30 -0400 (EDT)',\n                b'xyz' * 2, 654, None),\n            FakeyMessage({}, ('\\\\One', '\\\\Two', 'Three'),\n                b'Mon, 14 Apr 2003 19:43:44 -0400',\n                b'abc' * 4, 555, None),\n        ]\n        self.expected = {\n            0: {'FLAGS': ['\\\\XYZ', '\\\\YZX', 'Abc'],\n                'INTERNALDATE': '25-Jul-2010 06:20:30 -0400',\n                'RFC822.SIZE': '6',\n                'ENVELOPE': [None, None, [[None, None, None]], [[None, None, None]], None, None, None, None, None, None],\n                'BODY': [None, None, None, None, None, None, '6']},\n            1: {'FLAGS': ['\\\\One', '\\\\Two', 'Three'],\n                'INTERNALDATE': '14-Apr-2003 19:43:44 -0400',\n                'RFC822.SIZE': '12',\n                'ENVELOPE': [None, None, [[None, None, None]], [[None, None, None]], None, None, None, None, None, None],\n                'BODY': [None, None, None, None, None, None, '12']},\n        }\n        return self._fetchWork(uid)\n\n\n    def testFetchFullUID(self):\n        return self.testFetchFull(1)\n\n\n    def testFetchAll(self, uid=0):\n        self.function = self.client.fetchAll\n        self.messages = '1,2:3'\n        self.msgObjs = [\n            FakeyMessage({}, (), b'Mon, 14 Apr 2003 19:43:44 +0400',\n                b'Lalala', 10101, None),\n            FakeyMessage({}, (), b'Tue, 15 Apr 2003 19:43:44 +0200',\n                b'Alalal', 20202, None),\n        ]\n        self.expected = {\n            0: {'ENVELOPE': [None, None, [[None, None, None]], [[None, None, None]], None, None, None, None, None, None],\n                'RFC822.SIZE': '6',\n                'INTERNALDATE': '14-Apr-2003 19:43:44 +0400',\n                'FLAGS': []},\n            1: {'ENVELOPE': [None, None, [[None, None, None]], [[None, None, None]], None, None, None, None, None, None],\n                'RFC822.SIZE': '6',\n                'INTERNALDATE': '15-Apr-2003 19:43:44 +0200',\n                'FLAGS': []},\n        }\n        return self._fetchWork(uid)\n\n\n    def testFetchAllUID(self):\n        return self.testFetchAll(1)\n\n\n    def testFetchFast(self, uid=0):\n        self.function = self.client.fetchFast\n        self.messages = '1'\n        self.msgObjs = [\n            FakeyMessage({}, ('\\\\X',), b'19 Mar 2003 19:22:21 -0500', b'', 9, None),\n        ]\n        self.expected = {\n            0: {'FLAGS': ['\\\\X'],\n                'INTERNALDATE': '19-Mar-2003 19:22:21 -0500',\n                'RFC822.SIZE': '0'},\n        }\n        return self._fetchWork(uid)\n\n\n    def testFetchFastUID(self):\n        return self.testFetchFast(1)\n\n\n\nclass DefaultSearchTests(IMAP4HelperMixin, unittest.TestCase):\n    \"\"\"\n    Test the behavior of the server's SEARCH implementation, particularly in\n    the face of unhandled search terms.\n    \"\"\"\n    def setUp(self):\n        self.server = imap4.IMAP4Server()\n        self.server.state = 'select'\n        self.server.mbox = self\n        self.connected = defer.Deferred()\n        self.client = SimpleClient(self.connected)\n        self.msgObjs = [\n            FakeyMessage({}, (), b'', b'', 999, None),\n            FakeyMessage({}, (), b'', b'', 10101, None),\n            FakeyMessage({}, (), b'', b'', 12345, None),\n            FakeyMessage({}, (), b'', b'', 20001, None),\n            FakeyMessage({}, (), b'', b'', 20002, None),\n        ]\n\n\n    def fetch(self, messages, uid):\n        \"\"\"\n        Pretend to be a mailbox and let C{self.server} lookup messages on me.\n        \"\"\"\n        return list(zip(range(1, len(self.msgObjs) + 1), self.msgObjs))\n\n\n    def _messageSetSearchTest(self, queryTerms, expectedMessages):\n        \"\"\"\n        Issue a search with given query and verify that the returned messages\n        match the given expected messages.\n\n        @param queryTerms: A string giving the search query.\n        @param expectedMessages: A list of the message sequence numbers\n            expected as the result of the search.\n        @return: A L{Deferred} which fires when the test is complete.\n        \"\"\"\n        def search():\n            return self.client.search(queryTerms)\n\n        d = self.connected.addCallback(strip(search))\n        def searched(results):\n            self.assertEqual(results, expectedMessages)\n        d.addCallback(searched)\n        d.addCallback(self._cbStopClient)\n        d.addErrback(self._ebGeneral)\n        self.loopback()\n        return d\n\n\n    def test_searchMessageSet(self):\n        \"\"\"\n        Test that a search which starts with a message set properly limits\n        the search results to messages in that set.\n        \"\"\"\n        return self._messageSetSearchTest('1', [1])\n\n\n    def test_searchMessageSetWithStar(self):\n        \"\"\"\n        If the search filter ends with a star, all the message from the\n        starting point are returned.\n        \"\"\"\n        return self._messageSetSearchTest('2:*', [2, 3, 4, 5])\n\n\n    def test_searchMessageSetWithStarFirst(self):\n        \"\"\"\n        If the search filter starts with a star, the result should be identical\n        with if the filter would end with a star.\n        \"\"\"\n        return self._messageSetSearchTest('*:2', [2, 3, 4, 5])\n\n\n    def test_searchMessageSetUIDWithStar(self):\n        \"\"\"\n        If the search filter ends with a star, all the message from the\n        starting point are returned (also for the SEARCH UID case).\n        \"\"\"\n        return self._messageSetSearchTest('UID 10000:*', [2, 3, 4, 5])\n\n\n    def test_searchMessageSetUIDWithStarFirst(self):\n        \"\"\"\n        If the search filter starts with a star, the result should be identical\n        with if the filter would end with a star (also for the SEARCH UID case).\n        \"\"\"\n        return self._messageSetSearchTest('UID *:10000', [2, 3, 4, 5])\n\n\n    def test_searchMessageSetUIDWithStarAndHighStart(self):\n        \"\"\"\n        A search filter of 1234:* should include the UID of the last message in\n        the mailbox, even if its UID is less than 1234.\n        \"\"\"\n        # in our fake mbox the highest message UID is 20002\n        return self._messageSetSearchTest('UID 30000:*', [5])\n\n\n    def test_searchMessageSetWithList(self):\n        \"\"\"\n        If the search filter contains nesting terms, one of which includes a\n        message sequence set with a wildcard, IT ALL WORKS GOOD.\n        \"\"\"\n        # 6 is bigger than the biggest message sequence number, but that's\n        # okay, because N:* includes the biggest message sequence number even\n        # if N is bigger than that (read the rfc nub).\n        return self._messageSetSearchTest('(6:*)', [5])\n\n\n    def test_searchOr(self):\n        \"\"\"\n        If the search filter contains an I{OR} term, all messages\n        which match either subexpression are returned.\n        \"\"\"\n        return self._messageSetSearchTest('OR 1 2', [1, 2])\n\n\n    def test_searchOrMessageSet(self):\n        \"\"\"\n        If the search filter contains an I{OR} term with a\n        subexpression which includes a message sequence set wildcard,\n        all messages in that set are considered for inclusion in the\n        results.\n        \"\"\"\n        return self._messageSetSearchTest('OR 2:* 2:*', [2, 3, 4, 5])\n\n\n    def test_searchNot(self):\n        \"\"\"\n        If the search filter contains a I{NOT} term, all messages\n        which do not match the subexpression are returned.\n        \"\"\"\n        return self._messageSetSearchTest('NOT 3', [1, 2, 4, 5])\n\n\n    def test_searchNotMessageSet(self):\n        \"\"\"\n        If the search filter contains a I{NOT} term with a\n        subexpression which includes a message sequence set wildcard,\n        no messages in that set are considered for inclusion in the\n        result.\n        \"\"\"\n        return self._messageSetSearchTest('NOT 2:*', [1])\n\n\n    def test_searchAndMessageSet(self):\n        \"\"\"\n        If the search filter contains multiple terms implicitly\n        conjoined with a message sequence set wildcard, only the\n        intersection of the results of each term are returned.\n        \"\"\"\n        return self._messageSetSearchTest('2:* 3', [3])\n\n\n    def test_searchInvalidCriteria(self):\n        \"\"\"\n        If the search criteria is not a valid key, a NO result is returned to\n        the client (resulting in an error callback), and an IllegalQueryError is\n        logged on the server side.\n        \"\"\"\n        queryTerms = 'FOO'\n        def search():\n            return self.client.search(queryTerms)\n\n        d = self.connected.addCallback(strip(search))\n        d = self.assertFailure(d, imap4.IMAP4Exception)\n\n        def errorReceived(results):\n            \"\"\"\n            Verify that the server logs an IllegalQueryError and the\n            client raises an IMAP4Exception with 'Search failed:...'\n            \"\"\"\n            self.client.transport.loseConnection()\n            self.server.transport.loseConnection()\n\n            # Check what the server logs\n            errors = self.flushLoggedErrors(imap4.IllegalQueryError)\n            self.assertEqual(len(errors), 1)\n\n            # Verify exception given to client has the correct message\n            self.assertEqual(\n                str(b\"SEARCH failed: Invalid search command FOO\"),\n                str(results),\n            )\n\n        d.addCallback(errorReceived)\n        d.addErrback(self._ebGeneral)\n        self.loopback()\n        return d\n\n\n\n@implementer(imap4.ISearchableMailbox)\nclass FetchSearchStoreTests(unittest.TestCase, IMAP4HelperMixin):\n    def setUp(self):\n        self.expected = self.result = None\n        self.server_received_query = None\n        self.server_received_uid = None\n        self.server_received_parts = None\n        self.server_received_messages = None\n\n        self.server = imap4.IMAP4Server()\n        self.server.state = 'select'\n        self.server.mbox = self\n        self.connected = defer.Deferred()\n        self.client = SimpleClient(self.connected)\n\n\n    def search(self, query, uid):\n        # Look for a specific bad query, so we can verify we handle it properly\n        if query == [b'FOO']:\n            raise imap4.IllegalQueryError(\"FOO is not a valid search criteria\")\n\n        self.server_received_query = query\n        self.server_received_uid = uid\n        return self.expected\n\n\n    def addListener(self, *a, **kw):\n        pass\n    removeListener = addListener\n\n\n    def _searchWork(self, uid):\n        def search():\n            return self.client.search(self.query, uid=uid)\n        def result(R):\n            self.result = R\n\n        self.connected.addCallback(strip(search)\n        ).addCallback(result\n        ).addCallback(self._cbStopClient\n        ).addErrback(self._ebGeneral)\n\n        def check(ignored):\n            # Ensure no short-circuiting weirdness is going on\n            self.assertFalse(self.result is self.expected)\n\n            self.assertEqual(self.result, self.expected)\n            self.assertEqual(self.uid, self.server_received_uid)\n            self.assertEqual(\n                # Queries should be decoded as ASCII unless a charset\n                # identifier is provided.  See #9201.\n                imap4.parseNestedParens(self.query.encode('charmap')),\n                self.server_received_query\n            )\n        d = loopback.loopbackTCP(self.server, self.client, noisy=False)\n        d.addCallback(check)\n        return d\n\n\n    def testSearch(self):\n        self.query = imap4.Or(\n            imap4.Query(header=('subject', 'substring')),\n            imap4.Query(larger=1024, smaller=4096),\n        )\n        self.expected = [1, 4, 5, 7]\n        self.uid = 0\n        return self._searchWork(0)\n\n\n    def testUIDSearch(self):\n        self.query = imap4.Or(\n            imap4.Query(header=('subject', 'substring')),\n            imap4.Query(larger=1024, smaller=4096),\n        )\n        self.uid = 1\n        self.expected = [1, 2, 3]\n        return self._searchWork(1)\n\n\n    def getUID(self, msg):\n        try:\n            return self.expected[msg]['UID']\n        except (TypeError, IndexError):\n            return self.expected[msg-1]\n        except KeyError:\n            return 42\n\n\n    def fetch(self, messages, uid):\n        self.server_received_uid = uid\n        self.server_received_messages = str(messages)\n        return self.expected\n\n\n    def _fetchWork(self, fetch):\n        def result(R):\n            self.result = R\n\n        self.connected.addCallback(strip(fetch)\n        ).addCallback(result\n        ).addCallback(self._cbStopClient\n        ).addErrback(self._ebGeneral)\n\n        def check(ignored):\n            # Ensure no short-circuiting weirdness is going on\n            self.assertFalse(self.result is self.expected)\n\n            self.parts and self.parts.sort()\n            self.server_received_parts and self.server_received_parts.sort()\n\n            if self.uid:\n                for (k, v) in self.expected.items():\n                    v['UID'] = str(k)\n\n            self.assertEqual(self.result, self.expected)\n            self.assertEqual(self.uid, self.server_received_uid)\n            self.assertEqual(self.parts, self.server_received_parts)\n            self.assertEqual(imap4.parseIdList(self.messages),\n                              imap4.parseIdList(self.server_received_messages))\n\n        d = loopback.loopbackTCP(self.server, self.client, noisy=False)\n        d.addCallback(check)\n        return d\n\n\n    def test_invalidTerm(self):\n        \"\"\"\n        If, as part of a search, an ISearchableMailbox raises an\n        IllegalQueryError (e.g. due to invalid search criteria), client sees a\n        failure response, and an IllegalQueryError is logged on the server.\n        \"\"\"\n        query = 'FOO'\n\n        def search():\n            return self.client.search(query)\n\n        d = self.connected.addCallback(strip(search))\n        d = self.assertFailure(d, imap4.IMAP4Exception)\n\n        def errorReceived(results):\n            \"\"\"\n            Verify that the server logs an IllegalQueryError and the\n            client raises an IMAP4Exception with 'Search failed:...'\n            \"\"\"\n            self.client.transport.loseConnection()\n            self.server.transport.loseConnection()\n\n            # Check what the server logs\n            errors = self.flushLoggedErrors(imap4.IllegalQueryError)\n            self.assertEqual(len(errors), 1)\n\n            # Verify exception given to client has the correct message\n            self.assertEqual(\n                str(b\"SEARCH failed: FOO is not a valid search criteria\"),\n                str(results))\n\n        d.addCallback(errorReceived)\n        d.addErrback(self._ebGeneral)\n        self.loopback()\n        return d\n\n\n\nclass FakeMailbox:\n    def __init__(self):\n        self.args = []\n\n\n    def addMessage(self, body, flags, date):\n        self.args.append((body, flags, date))\n        return defer.succeed(None)\n\n\n\n@implementer(imap4.IMessageFile)\nclass FeaturefulMessage:\n    def getFlags(self):\n        return 'flags'\n\n\n    def getInternalDate(self):\n        return 'internaldate'\n\n\n    def open(self):\n        return BytesIO(b\"open\")\n\n\n\n@implementer(imap4.IMessageCopier)\nclass MessageCopierMailbox:\n    def __init__(self):\n        self.msgs = []\n\n\n    def copy(self, msg):\n        self.msgs.append(msg)\n        return len(self.msgs)\n\n\n\nclass CopyWorkerTests(unittest.TestCase):\n    def testFeaturefulMessage(self):\n        s = imap4.IMAP4Server()\n\n        # Yes.  I am grabbing this uber-non-public method to test it.\n        # It is complex.  It needs to be tested directly!\n        # Perhaps it should be refactored, simplified, or split up into\n        # not-so-private components, but that is a task for another day.\n\n        # Ha ha! Addendum!  Soon it will be split up, and this test will\n        # be re-written to just use the default adapter for IMailbox to\n        # IMessageCopier and call .copy on that adapter.\n        f = s._IMAP4Server__cbCopy\n\n        m = FakeMailbox()\n        d = f([(i, FeaturefulMessage()) for i in range(1, 11)], 'tag', m)\n\n        def cbCopy(results):\n            for a in m.args:\n                self.assertEqual(a[0].read(), b\"open\")\n                self.assertEqual(a[1], \"flags\")\n                self.assertEqual(a[2], \"internaldate\")\n\n            for (status, result) in results:\n                self.assertTrue(status)\n                self.assertEqual(result, None)\n\n        return d.addCallback(cbCopy)\n\n\n    def testUnfeaturefulMessage(self):\n        s = imap4.IMAP4Server()\n\n        # See above comment\n        f = s._IMAP4Server__cbCopy\n\n        m = FakeMailbox()\n        msgs = [FakeyMessage({'Header-Counter': str(i)},\n                             (),\n                             b'Date',\n                             b'Body ' + intToBytes(i),\n                             i + 10, None)\n                for i in range(1, 11)]\n        d = f([im for im in zip(range(1, 11), msgs)], 'tag', m)\n\n        def cbCopy(results):\n            seen = []\n            for a in m.args:\n                seen.append(a[0].read())\n                self.assertEqual(a[1], ())\n                self.assertEqual(a[2], b\"Date\")\n\n            seen.sort()\n            exp = [b\"Header-Counter: \" + intToBytes(i) + b\"\\r\\n\\r\\nBody \" +intToBytes(i) for i in range(1, 11)]\n            exp.sort()\n            self.assertEqual(seen, exp)\n\n            for (status, result) in results:\n                self.assertTrue(status)\n                self.assertEqual(result, None)\n\n        return d.addCallback(cbCopy)\n\n\n    def testMessageCopier(self):\n        s = imap4.IMAP4Server()\n\n        # See above comment\n        f = s._IMAP4Server__cbCopy\n\n        m = MessageCopierMailbox()\n        msgs = [object() for i in range(1, 11)]\n        d = f([im for im in zip(range(1, 11), msgs)], b'tag', m)\n\n        def cbCopy(results):\n            self.assertEqual(results, list(zip([1] * 10, range(1, 11))))\n            for (orig, new) in zip(msgs, m.msgs):\n                self.assertIdentical(orig, new)\n\n        return d.addCallback(cbCopy)\n\n\n\nclass TLSTests(IMAP4HelperMixin, unittest.TestCase):\n    serverCTX = ServerTLSContext and ServerTLSContext()\n    clientCTX = ClientTLSContext and ClientTLSContext()\n\n    def loopback(self):\n        return loopback.loopbackTCP(self.server, self.client, noisy=False)\n\n\n    def testAPileOfThings(self):\n        SimpleServer.theAccount.addMailbox(b'inbox')\n        called = []\n        def login():\n            called.append(None)\n            return self.client.login(b'testuser', b'password-test')\n        def list():\n            called.append(None)\n            return self.client.list(b'inbox', b'%')\n        def status():\n            called.append(None)\n            return self.client.status(b'inbox', 'UIDNEXT')\n        def examine():\n            called.append(None)\n            return self.client.examine(b'inbox')\n        def logout():\n            called.append(None)\n            return self.client.logout()\n\n        self.client.requireTransportSecurity = True\n\n        methods = [login, list, status, examine, logout]\n        for method in methods:\n            self.connected.addCallback(strip(method))\n\n        self.connected.addCallbacks(self._cbStopClient, self._ebGeneral)\n        def check(ignored):\n            self.assertEqual(self.server.startedTLS, True)\n            self.assertEqual(self.client.startedTLS, True)\n            self.assertEqual(len(called), len(methods))\n        d = self.loopback()\n        d.addCallback(check)\n        return d\n\n\n    def testLoginLogin(self):\n        self.server.checker.addUser(b'testuser', b'password-test')\n        success = []\n        self.client.registerAuthenticator(imap4.LOGINAuthenticator(b'testuser'))\n        self.connected.addCallback(\n                lambda _: self.client.authenticate(b'password-test')\n            ).addCallback(\n                lambda _: self.client.logout()\n            ).addCallback(success.append\n            ).addCallback(self._cbStopClient\n            ).addErrback(self._ebGeneral)\n\n        d = self.loopback()\n        d.addCallback(lambda x : self.assertEqual(len(success), 1))\n        return d\n\n\n    def startTLSAndAssertSession(self):\n        \"\"\"\n        Begin a C{STARTTLS} sequence and assert that it results in a\n        TLS session.\n\n        @return: A L{Deferred} that fires when the underlying\n            connection between the client and server has been terminated.\n        \"\"\"\n        success = []\n        self.connected.addCallback(strip(self.client.startTLS))\n        def checkSecure(ignored):\n            self.assertTrue(\n                interfaces.ISSLTransport.providedBy(self.client.transport))\n        self.connected.addCallback(checkSecure)\n        self.connected.addCallback(success.append)\n\n        d = self.loopback()\n        d.addCallback(lambda x : self.assertTrue(success))\n        return defer.gatherResults([d, self.connected])\n\n\n    def test_startTLS(self):\n        \"\"\"\n        L{IMAP4Client.startTLS} triggers TLS negotiation and returns a\n        L{Deferred} which fires after the client's transport is using\n        encryption.\n        \"\"\"\n        disconnected = self.startTLSAndAssertSession()\n        self.connected.addCallback(self._cbStopClient)\n        self.connected.addErrback(self._ebGeneral)\n        return disconnected\n\n\n    def test_doubleSTARTTLS(self):\n        \"\"\"\n        A server that receives a second C{STARTTLS} sends a C{NO}\n        response.\n        \"\"\"\n\n        class DoubleSTARTTLSClient(SimpleClient):\n\n            def startTLS(self):\n                if not self.startedTLS:\n                    return SimpleClient.startTLS(self)\n\n                return self.sendCommand(imap4.Command(b\"STARTTLS\"))\n\n        self.client = DoubleSTARTTLSClient(self.connected,\n                                           contextFactory=self.clientCTX)\n\n        disconnected = self.startTLSAndAssertSession()\n\n        self.connected.addCallback(strip(self.client.startTLS))\n        self.connected.addErrback(self.assertClientFailureMessage, b\"TLS already negotiated\")\n\n        self.connected.addCallback(self._cbStopClient)\n        self.connected.addErrback(self._ebGeneral)\n\n        return disconnected\n\n\n    def test_startTLSWithExistingChallengers(self):\n        \"\"\"\n        Starting a TLS negotiation with an L{IMAP4Server} that already\n        has C{LOGIN} and C{PLAIN} L{IChallengeResponse} factories uses\n        those factories.\n        \"\"\"\n        self.server.challengers = {b\"LOGIN\": imap4.LOGINCredentials,\n                                   b\"PLAIN\": imap4.PLAINCredentials}\n\n        @defer.inlineCallbacks\n        def assertLOGINandPLAIN():\n            capabilities = yield self.client.getCapabilities()\n            self.assertIn(b\"AUTH\", capabilities)\n            self.assertIn(b\"LOGIN\", capabilities[b\"AUTH\"])\n            self.assertIn(b\"PLAIN\", capabilities[b\"AUTH\"])\n\n        self.connected.addCallback(strip(assertLOGINandPLAIN))\n\n        disconnected = self.startTLSAndAssertSession()\n\n        self.connected.addCallback(strip(assertLOGINandPLAIN))\n\n        self.connected.addCallback(self._cbStopClient)\n        self.connected.addErrback(self._ebGeneral)\n\n        return disconnected\n\n\n    def test_loginBeforeSTARTTLS(self):\n        \"\"\"\n        A client that attempts to log in before issuing the\n        C{STARTTLS} command receives a C{NO} response.\n        \"\"\"\n        # Prevent the client from issuing STARTTLS.\n        self.client.startTLS = lambda: defer.succeed(\n            ([], 'OK Begin TLS negotiation now')\n        )\n        self.connected.addCallback(\n            lambda _: self.client.login(b\"wrong\", b\"time\"),\n        )\n\n        self.connected.addErrback(\n            self.assertClientFailureMessage,\n            b\"LOGIN is disabled before STARTTLS\",\n        )\n\n        self.connected.addCallback(self._cbStopClient)\n        self.connected.addErrback(self._ebGeneral)\n\n        return defer.gatherResults([self.loopback(), self.connected])\n\n\n    def testFailedStartTLS(self):\n        failures = []\n        def breakServerTLS(ign):\n            self.server.canStartTLS = False\n\n        self.connected.addCallback(breakServerTLS)\n        self.connected.addCallback(lambda ign: self.client.startTLS())\n        self.connected.addErrback(\n            lambda err: failures.append(err.trap(imap4.IMAP4Exception)))\n        self.connected.addCallback(self._cbStopClient)\n        self.connected.addErrback(self._ebGeneral)\n\n        def check(ignored):\n            self.assertTrue(failures)\n            self.assertIdentical(failures[0], imap4.IMAP4Exception)\n        return self.loopback().addCallback(check)\n\n\n\nclass SlowMailbox(SimpleMailbox):\n    howSlow = 2\n    callLater = None\n    fetchDeferred = None\n\n    # Not a very nice implementation of fetch(), but it'll\n    # do for the purposes of testing.\n    def fetch(self, messages, uid):\n        d = defer.Deferred()\n        self.callLater(self.howSlow, d.callback, ())\n        self.fetchDeferred.callback(None)\n        return d\n\n\n\nclass TimeoutTests(IMAP4HelperMixin, unittest.TestCase):\n\n    def test_serverTimeout(self):\n        \"\"\"\n        The *client* has a timeout mechanism which will close connections that\n        are inactive for a period.\n        \"\"\"\n        c = Clock()\n        self.server.timeoutTest = True\n        self.client.timeout = 5 #seconds\n        self.client.callLater = c.callLater\n        self.selectedArgs = None\n\n        def login():\n            d = self.client.login(b'testuser', b'password-test')\n            c.advance(5)\n            d.addErrback(timedOut)\n            return d\n\n        def timedOut(failure):\n            self._cbStopClient(None)\n            failure.trap(error.TimeoutError)\n\n        d = self.connected.addCallback(strip(login))\n        d.addErrback(self._ebGeneral)\n        return defer.gatherResults([d, self.loopback()])\n\n\n    def test_serverTimesOut(self):\n        \"\"\"\n        The server times out a connection.\n        \"\"\"\n        c = Clock()\n        self.server.callLater = c.callLater\n\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n\n        def expireTime():\n            c.advance(self.server.POSTAUTH_TIMEOUT * 2)\n\n        d = self.connected.addCallback(strip(login))\n        d.addCallback(strip(expireTime))\n\n        # The loopback method's Deferred fires the connection is\n        # closed, and the server closes the connection as a result of\n        # expireTime.\n        return defer.gatherResults([d, self.loopback()])\n\n\n    def test_serverUnselectsMailbox(self):\n        \"\"\"\n        The server unsets the selected mailbox when timing out a\n        connection.\n        \"\"\"\n        self.patch(SimpleServer.theAccount, \"mailboxFactory\",\n                   UncloseableMailbox)\n        SimpleServer.theAccount.addMailbox('mailbox-test')\n        mbox = SimpleServer.theAccount.mailboxes[u'MAILBOX-TEST']\n        self.assertFalse(ICloseableMailboxIMAP.providedBy(mbox))\n\n        c = Clock()\n        self.server.callLater = c.callLater\n\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n\n        def select():\n            return self.client.select(\"mailbox-test\")\n\n        def assertSet():\n            self.assertIs(mbox, self.server.mbox)\n\n        def expireTime():\n            c.advance(self.server.POSTAUTH_TIMEOUT * 2)\n\n        def assertUnset():\n            self.assertFalse(self.server.mbox)\n\n        d = self.connected.addCallback(strip(login))\n        d.addCallback(strip(select))\n        d.addCallback(strip(assertSet))\n        d.addCallback(strip(expireTime))\n        d.addCallback(strip(assertUnset))\n\n        # The loopback method's Deferred fires the connection is\n        # closed, and the server closes the connection as a result of\n        # expireTime.\n        return defer.gatherResults([d, self.loopback()])\n\n\n    def test_serverTimesOutAndClosesMailbox(self):\n        \"\"\"\n        The server closes the selected, closeable mailbox when timing\n        out a connection.\n        \"\"\"\n        SimpleServer.theAccount.addMailbox('mailbox-test')\n        mbox = SimpleServer.theAccount.mailboxes[u'MAILBOX-TEST']\n        verifyObject(ICloseableMailboxIMAP, mbox)\n\n        c = Clock()\n        self.server.callLater = c.callLater\n\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n\n        def select():\n            return self.client.select(\"mailbox-test\")\n\n        def assertMailboxOpen():\n            self.assertFalse(mbox.closed)\n\n        def expireTime():\n            c.advance(self.server.POSTAUTH_TIMEOUT * 2)\n\n        def assertMailboxClosed():\n            self.assertTrue(mbox.closed)\n\n        d = self.connected.addCallback(strip(login))\n        d.addCallback(strip(select))\n        d.addCallback(strip(assertMailboxOpen))\n        d.addCallback(strip(expireTime))\n        d.addCallback(strip(assertMailboxClosed))\n\n        # The loopback method's Deferred fires the connection is\n        # closed, and the server closes the connection as a result of\n        # expireTime.\n        return defer.gatherResults([d, self.loopback()])\n\n\n    def test_longFetchDoesntTimeout(self):\n        \"\"\"\n        The connection timeout does not take effect during fetches.\n        \"\"\"\n        c = Clock()\n        SlowMailbox.callLater = c.callLater\n        SlowMailbox.fetchDeferred = defer.Deferred()\n        self.server.callLater = c.callLater\n        SimpleServer.theAccount.mailboxFactory = SlowMailbox\n        SimpleServer.theAccount.addMailbox('mailbox-test')\n\n        self.server.setTimeout(1)\n\n        def login():\n            return self.client.login(b'testuser', b'password-test')\n\n        def select():\n            self.server.setTimeout(1)\n            return self.client.select('mailbox-test')\n\n        def fetch():\n            return self.client.fetchUID('1:*')\n\n        def stillConnected():\n            self.assertNotEqual(self.server.state, 'timeout')\n\n        def cbAdvance(ignored):\n            for i in range(4):\n                c.advance(.5)\n\n        SlowMailbox.fetchDeferred.addCallback(cbAdvance)\n\n        d1 = self.connected.addCallback(strip(login))\n        d1.addCallback(strip(select))\n        d1.addCallback(strip(fetch))\n        d1.addCallback(strip(stillConnected))\n        d1.addCallback(self._cbStopClient)\n        d1.addErrback(self._ebGeneral)\n        d = defer.gatherResults([d1, self.loopback()])\n        return d\n\n\n    def test_idleClientDoesDisconnect(self):\n        \"\"\"\n        The *server* has a timeout mechanism which will close connections that\n        are inactive for a period.\n        \"\"\"\n        c = Clock()\n        # Hook up our server protocol\n        transport = StringTransportWithDisconnection()\n        transport.protocol = self.server\n        self.server.callLater = c.callLater\n        self.server.makeConnection(transport)\n\n        # Make sure we can notice when the connection goes away\n        lost = []\n        connLost = self.server.connectionLost\n        self.server.connectionLost = lambda reason: (lost.append(None), connLost(reason))[1]\n\n        # 2/3rds of the idle timeout elapses...\n        c.pump([0.0] + [self.server.timeOut / 3.0] * 2)\n        self.assertFalse(lost, lost)\n\n        # Now some more\n        c.pump([0.0, self.server.timeOut / 2.0])\n        self.assertTrue(lost)\n\n\n\nclass DisconnectionTests(unittest.TestCase):\n    def testClientDisconnectFailsDeferreds(self):\n        c = imap4.IMAP4Client()\n        t = StringTransportWithDisconnection()\n        c.makeConnection(t)\n        d = self.assertFailure(c.login(b'testuser', 'example.com'), error.ConnectionDone)\n        c.connectionLost(error.ConnectionDone(\"Connection closed\"))\n        return d\n\n\n\nclass SynchronousMailbox(object):\n    \"\"\"\n    Trivial, in-memory mailbox implementation which can produce a message\n    synchronously.\n    \"\"\"\n    def __init__(self, messages):\n        self.messages = messages\n\n\n    def fetch(self, msgset, uid):\n        assert not uid, \"Cannot handle uid requests.\"\n        for msg in msgset:\n            yield msg, self.messages[msg - 1]\n\n\n\nclass PipeliningTests(unittest.TestCase):\n    \"\"\"\n    Tests for various aspects of the IMAP4 server's pipelining support.\n    \"\"\"\n    messages = [\n        FakeyMessage({}, [], b'', b'0', None, None),\n        FakeyMessage({}, [], b'', b'1', None, None),\n        FakeyMessage({}, [], b'', b'2', None, None),\n        ]\n\n    def setUp(self):\n        self.iterators = []\n\n        self.transport = StringTransport()\n        self.server = imap4.IMAP4Server(None, None, self.iterateInReactor)\n        self.server.makeConnection(self.transport)\n\n        mailbox = SynchronousMailbox(self.messages)\n\n        # Skip over authentication and folder selection\n        self.server.state = 'select'\n        self.server.mbox = mailbox\n\n        # Get rid of any greeting junk\n        self.transport.clear()\n\n\n    def iterateInReactor(self, iterator):\n        \"\"\"\n        A fake L{imap4.iterateInReactor} that records the iterators it\n        receives.\n\n        @param iterator: An iterator.\n\n        @return: A L{Deferred} associated with this iterator.\n        \"\"\"\n        d = defer.Deferred()\n        self.iterators.append((iterator, d))\n        return d\n\n\n    def flushPending(self, asLongAs=lambda: True):\n        \"\"\"\n        Advance pending iterators enqueued with L{iterateInReactor} in\n        a round-robin fashion, resuming the transport's producer until\n        it has completed.  This ensures bodies are flushed.\n\n        @param asLongAs: (optional) An optional predicate function.\n            Flushing iterators continues as long as there are\n            iterators and this returns L{True}.\n        \"\"\"\n        while self.iterators and asLongAs():\n            for e in self.iterators[0][0]:\n                while self.transport.producer:\n                    self.transport.producer.resumeProducing()\n            else:\n                self.iterators.pop(0)[1].callback(None)\n\n\n    def tearDown(self):\n        self.server.connectionLost(failure.Failure(error.ConnectionDone()))\n\n\n    def test_synchronousFetch(self):\n        \"\"\"\n        Test that pipelined FETCH commands which can be responded to\n        synchronously are responded to correctly.\n        \"\"\"\n        # Here's some pipelined stuff\n        self.server.dataReceived(\n            b'01 FETCH 1 BODY[]\\r\\n'\n            b'02 FETCH 2 BODY[]\\r\\n'\n            b'03 FETCH 3 BODY[]\\r\\n')\n\n        self.flushPending()\n\n        self.assertEqual(\n            self.transport.value(), b''.join([\n                b'* 1 FETCH (BODY[] )\\r\\n',\n                networkString(\n                    '01 OK FETCH completed\\r\\n{5}\\r\\n\\r\\n\\r\\n%s' % (\n                        nativeString(self.messages[0].getBodyFile().read()),\n                    )\n                ),\n                b'* 2 FETCH (BODY[] )\\r\\n',\n                networkString(\n                    '02 OK FETCH completed\\r\\n{5}\\r\\n\\r\\n\\r\\n%s' % (\n                        nativeString(self.messages[1].getBodyFile().read()),\n                    )\n                ),\n                b'* 3 FETCH (BODY[] )\\r\\n',\n                networkString(\n                    '03 OK FETCH completed\\r\\n{5}\\r\\n\\r\\n\\r\\n%s' % (\n                        nativeString(self.messages[2].getBodyFile().read()),\n                    )\n                ),\n            ]))\n\n\n    def test_bufferedServerStatus(self):\n        \"\"\"\n        When a server status change occurs during an ongoing FETCH\n        command, the server status is buffered until the FETCH\n        completes.\n        \"\"\"\n        self.server.dataReceived(\n            b'01 FETCH 1,2 BODY[]\\r\\n'\n        )\n\n        # Two iterations yields the untagged response and the first\n        # fetched message's body\n        twice = functools.partial(next, iter([True,  True, False]))\n        self.flushPending(asLongAs=twice)\n\n        self.assertEqual(\n            self.transport.value(), b''.join([\n                # The untagged response...\n                b'* 1 FETCH (BODY[] )\\r\\n',\n                # ...and its body\n                networkString(\n                    '{5}\\r\\n\\r\\n\\r\\n%s' % (\n                        nativeString(self.messages[0].getBodyFile().read()),\n                    )\n                ),\n            ]))\n\n        self.transport.clear()\n\n        # A server status change...\n        self.server.modeChanged(writeable=True)\n\n        # ...remains buffered...\n        self.assertFalse(self.transport.value())\n\n        self.flushPending()\n\n        self.assertEqual(self.transport.value(), b''.join([\n            # The untagged response...\n            b'* 2 FETCH (BODY[] )\\r\\n',\n            # ...the status change...\n            b\"* [READ-WRITE]\\r\\n\",\n            # ...and the completion status and final message's body\n            networkString(\n                '01 OK FETCH completed\\r\\n{5}\\r\\n\\r\\n\\r\\n%s' % (\n                    nativeString(self.messages[1].getBodyFile().read()),\n                )\n            ),\n        ]))\n\n\nif ClientTLSContext is None:\n    for case in (TLSTests,):\n        case.skip = \"OpenSSL not present\"\nelif interfaces.IReactorSSL(reactor, None) is None:\n    for case in (TLSTests,):\n        case.skip = \"Reactor doesn't support SSL\"\n\n\n\nclass IMAP4ServerFetchTests(unittest.TestCase):\n    \"\"\"\n    This test case is for the FETCH tests that require\n    a C{StringTransport}.\n    \"\"\"\n\n    def setUp(self):\n        self.transport = StringTransport()\n        self.server = imap4.IMAP4Server()\n        self.server.state = 'select'\n        self.server.makeConnection(self.transport)\n\n\n    def test_fetchWithPartialValidArgument(self):\n        \"\"\"\n        If by any chance, extra bytes got appended at the end of a valid\n        FETCH arguments, the client should get a BAD - arguments invalid\n        response.\n\n        See U{RFC 3501<http://tools.ietf.org/html/rfc3501#section-6.4.5>},\n        section 6.4.5,\n        \"\"\"\n        # We need to clear out the welcome message.\n        self.transport.clear()\n        # Let's send out the faulty command.\n        self.server.dataReceived(b\"0001 FETCH 1 FULLL\\r\\n\")\n        expected = b\"0001 BAD Illegal syntax: Invalid Argument\\r\\n\"\n        self.assertEqual(self.transport.value(), expected)\n        self.transport.clear()\n        self.server.connectionLost(error.ConnectionDone(\"Connection closed\"))\n\n\n\nclass LiteralTestsMixin(object):\n    \"\"\"\n    Shared tests for literal classes.\n\n    @ivar literalFactory: A callable that returns instances of the\n        literal under test.\n    \"\"\"\n\n    def setUp(self):\n        \"\"\"\n        Shared setup.\n        \"\"\"\n        self.deferred = defer.Deferred()\n\n\n    def test_partialWrite(self):\n        \"\"\"\n        The literal returns L{None} when given less data than the\n        literal requires.\n        \"\"\"\n        literal = self.literalFactory(1024, self.deferred)\n        self.assertIs(None, literal.write(b\"incomplete\"))\n        self.assertNoResult(self.deferred)\n\n\n    def test_exactWrite(self):\n        \"\"\"\n        The literal returns an empty L{bytes} instance when given\n        exactly the data the literal requires.\n        \"\"\"\n        data = b\"complete\"\n        literal = self.literalFactory(len(data), self.deferred)\n        leftover = literal.write(data)\n\n        self.assertIsInstance(leftover, bytes)\n        self.assertFalse(leftover)\n        self.assertNoResult(self.deferred)\n\n\n    def test_overlongWrite(self):\n        \"\"\"\n        The literal returns any left over L{bytes} when given more\n        data than the literal requires.\n        \"\"\"\n        data = b\"completeleftover\"\n        literal = self.literalFactory(len(b\"complete\"), self.deferred)\n\n        leftover = literal.write(data)\n\n        self.assertEqual(leftover, b\"leftover\")\n\n\n    def test_emptyLiteral(self):\n        \"\"\"\n        The literal returns an empty L{bytes} instance\n        when given an empty L{bytes} instance.\n        \"\"\"\n        literal = self.literalFactory(0, self.deferred)\n        data = b\"leftover\"\n\n        leftover = literal.write(data)\n\n        self.assertEqual(leftover, data)\n\n\n\nclass LiteralStringTests(LiteralTestsMixin, unittest.SynchronousTestCase):\n    \"\"\"\n    Tests for L{self.literalFactory}.\n    \"\"\"\n    literalFactory = imap4.LiteralString\n\n    def test_callback(self):\n        \"\"\"\n        Calling L{imap4.LiteralString.callback} with a line fires the\n        instance's L{Deferred} with a 2-L{tuple} whose first element\n        is the collected data and whose second is the provided line.\n        \"\"\"\n        data = b\"data\"\n        extra = b\"extra\"\n\n        literal = imap4.LiteralString(len(data), self.deferred)\n\n        for c in iterbytes(data):\n            literal.write(c)\n\n        literal.callback(b\"extra\")\n\n        result = self.successResultOf(self.deferred)\n        self.assertEqual(result, (data, extra))\n\n\n\nclass LiteralFileTests(LiteralTestsMixin, unittest.TestCase):\n    \"\"\"\n    Tests for L{imap4.LiteralFile}.\n    \"\"\"\n    literalFactory = imap4.LiteralFile\n\n\n    def test_callback(self):\n        \"\"\"\n        Calling L{imap4.LiteralFile.callback} with a line fires the\n        instance's L{Deferred} with a 2-L{tuple} whose first element\n        is the file and whose second is the provided line.\n        \"\"\"\n        data = b\"data\"\n        extra = b\"extra\"\n\n        literal = imap4.LiteralFile(len(data), self.deferred)\n\n        for c in iterbytes(data):\n            literal.write(c)\n\n        literal.callback(b\"extra\")\n\n        result = self.successResultOf(self.deferred)\n        self.assertEqual(len(result), 2)\n\n        dataFile, extra = result\n        self.assertEqual(dataFile.read(), b\"data\")\n\n\n    def test_callbackSpooledToDisk(self):\n        \"\"\"\n        A L{imap4.LiteralFile} whose size exceeds the maximum\n        in-memory size spools its content to disk, and invoking its\n        L{callback} with a line fires the instance's L{Deferred} with\n        a 2-L{tuple} whose first element is the spooled file and whose second\n        is the provided line.\n        \"\"\"\n        data = b\"data\"\n        extra = b\"extra\"\n\n        self.patch(imap4.LiteralFile, \"_memoryFileLimit\", 1)\n\n        literal = imap4.LiteralFile(len(data), self.deferred)\n\n        for c in iterbytes(data):\n            literal.write(c)\n\n        literal.callback(b\"extra\")\n\n        result = self.successResultOf(self.deferred)\n        self.assertEqual(len(result), 2)\n\n        dataFile, extra = result\n        self.assertEqual(dataFile.read(), b\"data\")\n\n\n\nclass WriteBufferTests(unittest.SynchronousTestCase):\n    \"\"\"\n    Tests for L{imap4.WriteBuffer}.\n    \"\"\"\n\n    def setUp(self):\n        self.transport = StringTransport()\n\n\n    def test_partialWrite(self):\n        \"\"\"\n        L{imap4.WriteBuffer} buffers writes that are smaller than its\n        buffer size.\n        \"\"\"\n        buf = imap4.WriteBuffer(self.transport)\n        data = b'x' * buf.bufferSize\n\n        buf.write(data)\n\n        self.assertFalse(self.transport.value())\n\n\n    def test_overlongWrite(self):\n        \"\"\"\n        L{imap4.WriteBuffer} writes data without buffering it when\n        the size of the data exceeds the size of its buffer.\n        \"\"\"\n        buf = imap4.WriteBuffer(self.transport)\n        data = b'x' * (buf.bufferSize + 1)\n\n        buf.write(data)\n\n        self.assertEqual(self.transport.value(), data)\n\n\n    def test_writesImplyFlush(self):\n        \"\"\"\n        L{imap4.WriteBuffer} buffers writes until its buffer's size\n        exceeds its maximum value.\n        \"\"\"\n        buf = imap4.WriteBuffer(self.transport)\n        firstData = b'x' * buf.bufferSize\n        secondData = b'y'\n\n        buf.write(firstData)\n\n        self.assertFalse(self.transport.value())\n\n        buf.write(secondData)\n\n        self.assertEqual(self.transport.value(), firstData + secondData)\n\n\n    def test_explicitFlush(self):\n        \"\"\"\n        L{imap4.WriteBuffer.flush} flushes the buffer even when its\n        size is smaller than the buffer size.\n        \"\"\"\n        buf = imap4.WriteBuffer(self.transport)\n        data = b'x' * (buf.bufferSize)\n\n        buf.write(data)\n\n        self.assertFalse(self.transport.value())\n\n        buf.flush()\n\n        self.assertEqual(self.transport.value(), data)\n\n\n    def test_explicitFlushEmptyBuffer(self):\n        \"\"\"\n        L{imap4.WriteBuffer.flush} has no effect if when the buffer is\n        empty.\n        \"\"\"\n        buf = imap4.WriteBuffer(self.transport)\n\n        buf.flush()\n\n        self.assertFalse(self.transport.value())\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/test/test_mailmail.py",
    "content": "# -*- test-case-name: twisted.mail.test.test_mailmail -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTests for L{twisted.mail.scripts.mailmail}, the implementation of the\ncommand line program I{mailmail}.\n\"\"\"\n\nimport os\nimport sys\n\nfrom twisted.copyright import version\nfrom twisted.internet.defer import Deferred\nfrom twisted.mail import smtp\nfrom twisted.mail.scripts import mailmail\nfrom twisted.mail.scripts.mailmail import parseOptions\nfrom twisted.python.compat import NativeStringIO\nfrom twisted.python.failure import Failure\nfrom twisted.python.runtime import platformType\nfrom twisted.test.proto_helpers import MemoryReactor\nfrom twisted.trial.unittest import TestCase\n\n\n\nclass OptionsTests(TestCase):\n    \"\"\"\n    Tests for L{parseOptions} which parses command line arguments and reads\n    message text from stdin to produce an L{Options} instance which can be\n    used to send a message.\n    \"\"\"\n    memoryReactor = MemoryReactor()\n\n    def setUp(self):\n        \"\"\"\n        Override some things in mailmail, so that we capture C{stdout},\n        and do not call L{reactor.stop}.\n        \"\"\"\n        self.out = NativeStringIO()\n        # Override the mailmail logger, so we capture stderr output\n        from twisted.logger import textFileLogObserver, Logger\n        logObserver = textFileLogObserver(self.out)\n        self.patch(mailmail, '_log', Logger(observer=logObserver))\n        self.host = None\n        self.options = None\n        self.ident = None\n\n        # Override mailmail.sendmail, so we don't call reactor.stop()\n        def sendmail(host, options, ident):\n            self.host = host\n            self.options = options\n            self.ident = ident\n            return smtp.sendmail(host, options.sender, options.to,\n                                 options.body, reactor=self.memoryReactor)\n\n        self.patch(mailmail, 'sendmail', sendmail)\n\n\n    def test_unspecifiedRecipients(self):\n        \"\"\"\n        If no recipients are given in the argument list and there is no\n        recipient header in the message text, L{parseOptions} raises\n        L{SystemExit} with a string describing the problem.\n        \"\"\"\n        self.patch(sys, 'stdin', NativeStringIO(\n            'Subject: foo\\n'\n            '\\n'\n            'Hello, goodbye.\\n'))\n        exc = self.assertRaises(SystemExit, parseOptions, [])\n        self.assertEqual(exc.args, ('No recipients specified.',))\n\n\n    def test_listQueueInformation(self):\n        \"\"\"\n        The I{-bp} option for listing queue information is unsupported and\n        if it is passed to L{parseOptions}, L{SystemExit} is raised.\n        \"\"\"\n        exc = self.assertRaises(SystemExit, parseOptions, ['-bp'])\n        self.assertEqual(exc.args, (\"Unsupported option.\",))\n\n\n    def test_stdioTransport(self):\n        \"\"\"\n        The I{-bs} option for using stdin and stdout as the SMTP transport\n        is unsupported and if it is passed to L{parseOptions}, L{SystemExit}\n        is raised.\n        \"\"\"\n        exc = self.assertRaises(SystemExit, parseOptions, ['-bs'])\n        self.assertEqual(exc.args, (\"Unsupported option.\",))\n\n\n    def test_ignoreFullStop(self):\n        \"\"\"\n        The I{-i} and I{-oi} options for ignoring C{\".\"} by itself on a line\n        are unsupported and if either is passed to L{parseOptions},\n        L{SystemExit} is raised.\n        \"\"\"\n        exc = self.assertRaises(SystemExit, parseOptions, ['-i'])\n        self.assertEqual(exc.args, (\"Unsupported option.\",))\n        exc = self.assertRaises(SystemExit, parseOptions, ['-oi'])\n        self.assertEqual(exc.args, (\"Unsupported option.\",))\n\n\n    def test_copyAliasedSender(self):\n        \"\"\"\n        The I{-om} option for copying the sender if they appear in an alias\n        expansion is unsupported and if it is passed to L{parseOptions},\n        L{SystemExit} is raised.\n        \"\"\"\n        exc = self.assertRaises(SystemExit, parseOptions, ['-om'])\n        self.assertEqual(exc.args, (\"Unsupported option.\",))\n\n\n    def test_version(self):\n        \"\"\"\n        The I{--version} option displays the version and raises\n        L{SystemExit} with L{None} as the exit code.\n        \"\"\"\n        out = NativeStringIO()\n        self.patch(sys, 'stdout', out)\n        systemExitCode = self.assertRaises(SystemExit, parseOptions,\n                                           '--version')\n        # SystemExit.code is None on success\n        self.assertEqual(systemExitCode.code, None)\n        data = out.getvalue()\n        self.assertEqual(data, \"mailmail version: {}\\n\".format(version))\n\n\n    def test_backgroundDelivery(self):\n        \"\"\"\n        The I{-odb} flag specifies background delivery.\n        \"\"\"\n        stdin = NativeStringIO('\\n')\n        self.patch(sys, 'stdin', stdin)\n        o = parseOptions(\"-odb\")\n        self.assertTrue(o.background)\n\n\n    def test_foregroundDelivery(self):\n        \"\"\"\n        The I{-odf} flags specifies foreground delivery.\n        \"\"\"\n        stdin = NativeStringIO('\\n')\n        self.patch(sys, 'stdin', stdin)\n        o = parseOptions(\"-odf\")\n        self.assertFalse(o.background)\n\n\n    def test_recipientsFromHeaders(self):\n        \"\"\"\n        The I{-t} flags specifies that recipients should be obtained\n        from headers.\n        \"\"\"\n        stdin = NativeStringIO(\n            'To: Curly <invaliduser2@example.com>\\n'\n            'Cc: Larry <invaliduser1@example.com>\\n'\n            'Bcc: Moe <invaliduser3@example.com>\\n'\n            '\\n'\n            'Oh, a wise guy?\\n')\n        self.patch(sys, 'stdin', stdin)\n        o = parseOptions(\"-t\")\n        self.assertEqual(len(o.to), 3)\n\n\n    def test_setFrom(self):\n        \"\"\"\n        When a message has no I{From:} header, a I{From:} value can be\n        specified with the I{-F} flag.\n        \"\"\"\n        stdin = NativeStringIO(\n            'To: invaliduser2@example.com\\n'\n            'Subject: A wise guy?\\n\\n')\n        self.patch(sys, 'stdin', stdin)\n        o = parseOptions([\"-F\", \"Larry <invaliduser1@example.com>\", \"-t\"])\n        self.assertEqual(o.sender, \"Larry <invaliduser1@example.com>\")\n\n\n    def test_overrideFromFlagByFromHeader(self):\n        \"\"\"\n        The I{-F} flag specifies the From: value.  However, I{-F} flag is\n        overriden by the value of From: in the e-mail header.\n        \"\"\"\n        stdin = NativeStringIO(\n            'To: Curly <invaliduser4@example.com>\\n'\n            'From: Shemp <invaliduser4@example.com>\\n')\n        self.patch(sys, 'stdin', stdin)\n        o = parseOptions([\"-F\", \"Groucho <invaliduser5@example.com>\", \"-t\"])\n        self.assertEqual(o.sender, \"invaliduser4@example.com\")\n\n\n    def test_runErrorsToStderr(self):\n        \"\"\"\n        Call L{mailmail.run}, and specify I{-oep} to print errors\n        to stderr.  The sender, to, and printErrors options should be\n        set and there should be no failure.\n        \"\"\"\n        argv = (\"test_mailmail.py\", \"invaliduser2@example.com\", \"-oep\")\n        stdin = NativeStringIO('\\n')\n        self.patch(sys, 'argv', argv)\n        self.patch(sys, 'stdin', stdin)\n        mailmail.run()\n        self.assertEqual(self.options.sender, mailmail.getlogin())\n        self.assertEqual(self.options.to, [\"invaliduser2@example.com\"])\n        # We should have printErrors set because we specified \"-oep\"\n        self.assertTrue(self.options.printErrors)\n        # We should not have any failures.\n        self.assertIsNone(mailmail.failed)\n\n    if platformType == \"win32\":\n        test_runErrorsToStderr.skip = (\n            \"mailmail.run() does not work on win32 due to lack of support for\"\n            \" getuid()\")\n\n\n    def test_readInvalidConfig(self):\n        \"\"\"\n        Error messages for illegal UID value, illegal GID value, and illegal\n        identity entry will be sent to stderr.\n        \"\"\"\n        stdin = NativeStringIO('\\n')\n        self.patch(sys, 'stdin', stdin)\n\n        filename = self.mktemp()\n        myUid = os.getuid()\n        myGid = os.getgid()\n\n        with open(filename, \"w\") as f:\n            # Create a config file with some invalid values\n            f.write(\"[useraccess]\\n\"\n                    \"allow=invaliduser2,invaliduser1\\n\"\n                    \"deny=invaliduser3,invaliduser4,{}\\n\"\n                    \"order=allow,deny\\n\"\n                    \"[groupaccess]\\n\"\n                    \"allow=invalidgid1,invalidgid2\\n\"\n                    \"deny=invalidgid1,invalidgid2,{}\\n\"\n                    \"order=deny,allow\\n\"\n                    \"[identity]\\n\"\n                    \"localhost=funny\\n\"\n                    \"[addresses]\\n\"\n                    \"smarthost=localhost\\n\"\n                    \"default_domain=example.com\\n\".format(myUid, myGid))\n\n        # The mailmail script looks in\n        # the twisted.mail.scripts.GLOBAL_CFG variable\n        # and then the twisted.mail.scripts.LOCAL_CFG\n        # variable for the path to it's  config file.\n        #\n        # Override twisted.mail.scripts.LOCAL_CFG with the file we just\n        # created.\n        self.patch(mailmail, \"LOCAL_CFG\", filename)\n\n        argv = (\"test_mailmail.py\", \"invaliduser2@example.com\", \"-oep\")\n        self.patch(sys, 'argv', argv)\n        mailmail.run()\n        self.assertRegex(self.out.getvalue(),\n                         \"Illegal UID in \\\\[useraccess\\\\] section: \"\n                         \"invaliduser1\")\n        self.assertRegex(self.out.getvalue(),\n                         \"Illegal GID in \\\\[groupaccess\\\\] section: \"\n                         \"invalidgid1\")\n        self.assertRegex(self.out.getvalue(),\n                         'Illegal entry in \\\\[identity\\\\] section: funny')\n\n    if platformType == \"win32\":\n        test_readInvalidConfig.skip = (\"mailmail.run() does not work on win32\"\n                                       \" due to lack of support for getuid()\")\n\n\n    def getConfigFromFile(self, config):\n        \"\"\"\n        Read a mailmail configuration file.\n\n        The mailmail script checks the twisted.mail.scripts.mailmail.GLOBAL_CFG\n        variable and then the twisted.mail.scripts.mailmail.LOCAL_CFG\n        variable for the path to its  config file.\n\n        @param config: path to config file\n        @type config: L{str}\n\n        @return: A parsed config.\n        @rtype: L{twisted.mail.scripts.mailmail.Configuration}\n        \"\"\"\n\n        from twisted.mail.scripts.mailmail import loadConfig\n\n        filename = self.mktemp()\n\n        with open(filename, \"w\") as f:\n            f.write(config)\n\n        return loadConfig(filename)\n\n\n    def test_loadConfig(self):\n        \"\"\"\n        L{twisted.mail.scripts.mailmail.loadConfig}\n        parses the config file for mailmail.\n        \"\"\"\n        config = self.getConfigFromFile(\"\"\"\n[addresses]\nsmarthost=localhost\"\"\")\n        self.assertEqual(config.smarthost, \"localhost\")\n\n        config = self.getConfigFromFile(\"\"\"\n[addresses]\ndefault_domain=example.com\"\"\")\n        self.assertEqual(config.domain, \"example.com\")\n\n        config = self.getConfigFromFile(\"\"\"\n[addresses]\nsmarthost=localhost\ndefault_domain=example.com\"\"\")\n        self.assertEqual(config.smarthost, \"localhost\")\n        self.assertEqual(config.domain, \"example.com\")\n\n        config = self.getConfigFromFile(\"\"\"\n[identity]\nhost1=invalid\nhost2=username:password\"\"\")\n        self.assertNotIn(\"host1\", config.identities)\n        self.assertEqual(config.identities[\"host2\"], [\"username\", \"password\"])\n\n        config = self.getConfigFromFile(\"\"\"\n[useraccess]\nallow=invalid1,35\norder=allow\"\"\")\n        self.assertEqual(config.allowUIDs, [35])\n\n        config = self.getConfigFromFile(\"\"\"\n[useraccess]\ndeny=35,36\norder=deny\"\"\")\n        self.assertEqual(config.denyUIDs, [35, 36])\n\n        config = self.getConfigFromFile(\"\"\"\n[useraccess]\nallow=35,36\ndeny=37,38\norder=deny\"\"\")\n        self.assertEqual(config.allowUIDs, [35, 36])\n        self.assertEqual(config.denyUIDs, [37, 38])\n\n        config = self.getConfigFromFile(\"\"\"\n[groupaccess]\nallow=gid1,41\norder=allow\"\"\")\n        self.assertEqual(config.allowGIDs, [41])\n\n        config = self.getConfigFromFile(\"\"\"\n[groupaccess]\ndeny=41\norder=deny\"\"\")\n        self.assertEqual(config.denyGIDs, [41])\n\n        config = self.getConfigFromFile(\"\"\"\n[groupaccess]\nallow=41,42\ndeny=43,44\norder=allow,deny\"\"\")\n        self.assertEqual(config.allowGIDs, [41, 42])\n        self.assertEqual(config.denyGIDs, [43, 44])\n\n\n    def test_senderror(self):\n        \"\"\"\n        L{twisted.mail.scripts.mailmail.senderror} sends mail back to the\n        sender if an error occurs while sending mail to the recipient.\n        \"\"\"\n        def sendmail(host, sender, recipient, body):\n            self.assertRegex(sender, \"postmaster@\")\n            self.assertEqual(recipient, [\"testsender\"])\n            self.assertRegex(body.getvalue(), \"ValueError\")\n            return Deferred()\n\n        self.patch(smtp, \"sendmail\", sendmail)\n        opts = mailmail.Options()\n        opts.sender = \"testsender\"\n        fail = Failure(ValueError())\n        mailmail.senderror(fail, opts)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/test/test_pop3.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for Ltwisted.mail.pop3} module.\n\"\"\"\n\nfrom __future__ import print_function\n\nimport hmac\nimport base64\nimport itertools\n\nfrom collections import OrderedDict\nfrom io import BytesIO\n\nfrom zope.interface import implementer\n\nfrom twisted import cred\nfrom twisted import internet\nfrom twisted import mail\nfrom twisted.internet import defer\nfrom twisted.mail import pop3\nfrom twisted.protocols import loopback\nfrom twisted.python import failure\nfrom twisted.python.compat import intToBytes\nfrom twisted.test.proto_helpers import LineSendingProtocol\nfrom twisted.trial import unittest, util\nimport twisted.cred.checkers\nimport twisted.cred.credentials\nimport twisted.cred.portal\nimport twisted.internet.protocol\nimport twisted.mail.pop3\nimport twisted.mail.protocols\n\n\nclass UtilityTests(unittest.TestCase):\n    \"\"\"\n    Test the various helper functions and classes used by the POP3 server\n    protocol implementation.\n    \"\"\"\n\n    def test_LineBuffering(self):\n        \"\"\"\n        Test creating a LineBuffer and feeding it some lines.  The lines should\n        build up in its internal buffer for a while and then get spat out to\n        the writer.\n        \"\"\"\n        output = []\n        input = iter(itertools.cycle(['012', '345', '6', '7', '8', '9']))\n        c = pop3._IteratorBuffer(output.extend, input, 6)\n        i = iter(c)\n        self.assertEqual(output, [])  # Nothing is buffer\n        next(i)\n        self.assertEqual(output, [])  # '012' is buffered\n        next(i)\n        self.assertEqual(output, [])  # '012345' is buffered\n        next(i)\n        self.assertEqual(output, ['012', '345', '6'])  # Nothing is buffered\n        for n in range(5):\n            next(i)\n        self.assertEqual(output, ['012', '345', '6', '7', '8', '9', '012',\n                                  '345'])\n\n\n    def test_FinishLineBuffering(self):\n        \"\"\"\n        Test that a LineBuffer flushes everything when its iterator is\n        exhausted, and itself raises StopIteration.\n        \"\"\"\n        output = []\n        input = iter(['a', 'b', 'c'])\n        c = pop3._IteratorBuffer(output.extend, input, 5)\n        for i in c:\n            pass\n        self.assertEqual(output, ['a', 'b', 'c'])\n\n\n    def test_SuccessResponseFormatter(self):\n        \"\"\"\n        Test that the thing that spits out POP3 'success responses' works\n        right.\n        \"\"\"\n        self.assertEqual(\n            pop3.successResponse(b'Great.'),\n            b'+OK Great.\\r\\n')\n\n\n    def test_StatLineFormatter(self):\n        \"\"\"\n        Test that the function which formats stat lines does so appropriately.\n        \"\"\"\n        statLine = list(pop3.formatStatResponse([]))[-1]\n        self.assertEqual(statLine, b'+OK 0 0\\r\\n')\n\n        statLine = list(pop3.formatStatResponse([10, 31, 0, 10101]))[-1]\n        self.assertEqual(statLine, b'+OK 4 10142\\r\\n')\n\n\n    def test_ListLineFormatter(self):\n        \"\"\"\n        Test that the function which formats the lines in response to a LIST\n        command does so appropriately.\n        \"\"\"\n        listLines = list(pop3.formatListResponse([]))\n        self.assertEqual(\n            listLines,\n            [b'+OK 0\\r\\n', b'.\\r\\n'])\n\n        listLines = list(pop3.formatListResponse([1, 2, 3, 100]))\n        self.assertEqual(\n            listLines,\n            [b'+OK 4\\r\\n', b'1 1\\r\\n', b'2 2\\r\\n', b'3 3\\r\\n', b'4 100\\r\\n',\n             b'.\\r\\n'])\n\n\n    def test_UIDListLineFormatter(self):\n        \"\"\"\n        Test that the function which formats lines in response to a UIDL\n        command does so appropriately.\n        \"\"\"\n        uids = ['abc', 'def', 'ghi']\n        listLines = list(pop3.formatUIDListResponse([], uids.__getitem__))\n        self.assertEqual(\n            listLines,\n            [b'+OK \\r\\n', b'.\\r\\n'])\n\n        listLines = list(pop3.formatUIDListResponse([123, 431, 591],\n                         uids.__getitem__))\n        self.assertEqual(\n            listLines,\n            [b'+OK \\r\\n', b'1 abc\\r\\n', b'2 def\\r\\n', b'3 ghi\\r\\n', b'.\\r\\n'])\n\n        listLines = list(pop3.formatUIDListResponse([0, None, 591],\n                         uids.__getitem__))\n        self.assertEqual(\n            listLines,\n            [b'+OK \\r\\n', b'1 abc\\r\\n', b'3 ghi\\r\\n', b'.\\r\\n'])\n\n\n\nclass MyVirtualPOP3(mail.protocols.VirtualPOP3):\n    \"\"\"\n    A virtual-domain-supporting POP3 server.\n    \"\"\"\n    magic = b'<moshez>'\n\n    def authenticateUserAPOP(self, user, digest):\n        \"\"\"\n        Authenticate against a user against a virtual domain.\n\n        @param user: The username.\n        @param digest: The digested password.\n\n        @return: A three-tuple like the one returned by\n            L{IRealm.requestAvatar}.  The mailbox will be for the user given\n            by C{user}.\n        \"\"\"\n        user, domain = self.lookupDomain(user)\n        return self.service.domains[b'baz.com'].authenticateUserAPOP(\n            user, digest, self.magic, domain)\n\n\n\nclass DummyDomain:\n    \"\"\"\n    A virtual domain for a POP3 server.\n    \"\"\"\n\n    def __init__(self):\n        self.users = {}\n\n\n    def addUser(self, name):\n        \"\"\"\n        Create a mailbox for a new user.\n\n        @param name: The username.\n        \"\"\"\n        self.users[name] = []\n\n\n    def addMessage(self, name, message):\n        \"\"\"\n        Add a message to the mailbox of the named user.\n\n        @param name: The username.\n        @param message: The contents of the message.\n        \"\"\"\n        self.users[name].append(message)\n\n\n    def authenticateUserAPOP(self, name, digest, magic, domain):\n        \"\"\"\n        Succeed with a L{ListMailbox}.\n\n        @param name: The name of the user authenticating.\n        @param digest: ignored\n        @param magic: ignored\n        @param domain: ignored\n\n        @return: A three-tuple like the one returned by\n            L{IRealm.requestAvatar}.  The mailbox will be for the user given\n            by C{name}.\n        \"\"\"\n        return pop3.IMailbox, ListMailbox(self.users[name]), lambda: None\n\n\n\nclass ListMailbox:\n    \"\"\"\n    A simple in-memory list implementation of L{IMailbox}.\n    \"\"\"\n    def __init__(self, list):\n        \"\"\"\n        @param list: The messages.\n        \"\"\"\n        self.list = list\n\n\n    def listMessages(self, i=None):\n        \"\"\"\n        Get some message information.\n\n        @param i: See L{pop3.IMailbox.listMessages}.\n        @return: See L{pop3.IMailbox.listMessages}.\n        \"\"\"\n        if i is None:\n            return [len(l) for l in self.list]\n        return len(self.list[i])\n\n\n    def getMessage(self, i):\n        \"\"\"\n        Get the message content.\n\n        @param i: See L{pop3.IMailbox.getMessage}.\n        @return: See L{pop3.IMailbox.getMessage}.\n        \"\"\"\n        return BytesIO(self.list[i])\n\n\n    def getUidl(self, i):\n        \"\"\"\n        Construct a UID by using the given index value.\n\n        @param i: See L{pop3.IMailbox.getUidl}.\n        @return: See L{pop3.IMailbox.getUidl}.\n        \"\"\"\n        return i\n\n\n    def deleteMessage(self, i):\n        \"\"\"\n        Wipe the message at the given index.\n\n        @param i: See L{pop3.IMailbox.deleteMessage}.\n        \"\"\"\n        self.list[i] = b''\n\n\n    def sync(self):\n        \"\"\"\n        No-op.\n\n        @see: L{pop3.IMailbox.sync}\n        \"\"\"\n\n\n\nclass MyPOP3Downloader(pop3.POP3Client):\n    \"\"\"\n    A POP3 client which downloads all messages from the server.\n    \"\"\"\n    def handle_WELCOME(self, line):\n        \"\"\"\n        Authenticate.\n\n        @param line: The welcome response.\n        \"\"\"\n        pop3.POP3Client.handle_WELCOME(self, line)\n        self.apop(b'hello@baz.com', b'world')\n\n\n    def handle_APOP(self, line):\n        \"\"\"\n        Require an I{OK} response to I{APOP}.\n\n        @param line: The I{APOP} response.\n        \"\"\"\n        parts = line.split()\n        code = parts[0]\n        if code != b'+OK':\n            raise AssertionError('code is: %s , parts is: %s ' % (code, parts))\n        self.lines = []\n        self.retr(1)\n\n\n    def handle_RETR_continue(self, line):\n        \"\"\"\n        Record one line of message information.\n\n        @param line: A I{RETR} response line.\n        \"\"\"\n        self.lines.append(line)\n\n\n    def handle_RETR_end(self):\n        \"\"\"\n        Record the received message information.\n        \"\"\"\n        self.message = b'\\n'.join(self.lines) + b'\\n'\n        self.quit()\n\n\n    def handle_QUIT(self, line):\n        \"\"\"\n        Require an I{OK} response to I{QUIT}.\n\n        @param line: The I{QUIT} response.\n        \"\"\"\n        if line[:3] != b'+OK':\n            raise AssertionError(b'code is ' + line)\n\n\n\nclass POP3Tests(unittest.TestCase):\n    \"\"\"\n    Tests for L{pop3.POP3}.\n    \"\"\"\n\n    message = b'''\\\nSubject: urgent\n\nSomeone set up us the bomb!\n'''\n\n    expectedOutput = (b'''\\\n+OK <moshez>\\015\n+OK Authentication succeeded\\015\n+OK \\015\n1 0\\015\n.\\015\n+OK ''' + intToBytes(len(message)) + b'''\\015\nSubject: urgent\\015\n\\015\nSomeone set up us the bomb!\\015\n.\\015\n+OK \\015\n''')\n\n    def setUp(self):\n        \"\"\"\n        Set up a POP3 server with virtual domain support.\n        \"\"\"\n        self.factory = internet.protocol.Factory()\n        self.factory.domains = {}\n        self.factory.domains[b'baz.com'] = DummyDomain()\n        self.factory.domains[b'baz.com'].addUser(b'hello')\n        self.factory.domains[b'baz.com'].addMessage(b'hello', self.message)\n\n\n    def test_messages(self):\n        \"\"\"\n        Messages can be downloaded over a loopback TCP connection.\n        \"\"\"\n        client = LineSendingProtocol([\n            b'APOP hello@baz.com world',\n            b'UIDL',\n            b'RETR 1',\n            b'QUIT',\n        ])\n        server = MyVirtualPOP3()\n        server.service = self.factory\n        def check(ignored):\n            output = b'\\r\\n'.join(client.response) + b'\\r\\n'\n            self.assertEqual(output, self.expectedOutput)\n        return loopback.loopbackTCP(server, client).addCallback(check)\n\n\n    def test_loopback(self):\n        \"\"\"\n        Messages can be downloaded over a loopback connection.\n        \"\"\"\n        protocol = MyVirtualPOP3()\n        protocol.service = self.factory\n        clientProtocol = MyPOP3Downloader()\n        def check(ignored):\n            self.assertEqual(clientProtocol.message, self.message)\n            protocol.connectionLost(\n                failure.Failure(Exception(\"Test harness disconnect\")))\n        d = loopback.loopbackAsync(protocol, clientProtocol)\n        return d.addCallback(check)\n    test_loopback.suppress = [util.suppress(\n         message=\"twisted.mail.pop3.POP3Client is deprecated\")]\n\n\n    def test_incorrectDomain(self):\n        \"\"\"\n        Look up a user in a domain which this server does not support.\n        \"\"\"\n        factory = internet.protocol.Factory()\n        factory.domains = {}\n        factory.domains[b'twistedmatrix.com'] = DummyDomain()\n\n        server = MyVirtualPOP3()\n        server.service = factory\n        exc = self.assertRaises(pop3.POP3Error,\n            server.authenticateUserAPOP, b'nobody@baz.com', b'password')\n        self.assertEqual(exc.args[0], 'no such domain baz.com')\n\n\n\nclass DummyPOP3(pop3.POP3):\n    \"\"\"\n    A simple POP3 server with a hard-coded mailbox for any user.\n    \"\"\"\n    magic = b'<moshez>'\n\n    def authenticateUserAPOP(self, user, password):\n        \"\"\"\n        Succeed with a L{DummyMailbox}.\n\n        @param user: ignored\n        @param password: ignored\n\n        @return: A three-tuple like the one returned by\n            L{IRealm.requestAvatar}.\n        \"\"\"\n        return pop3.IMailbox, DummyMailbox(ValueError), lambda: None\n\n\n\nclass DummyMailbox(pop3.Mailbox):\n    \"\"\"\n    An in-memory L{pop3.IMailbox} implementation.\n\n    @ivar messages: A sequence of L{bytes} defining the messages in this\n        mailbox.\n\n    @ivar exceptionType: The type of exception to raise when an out-of-bounds\n        index is addressed.\n    \"\"\"\n    messages = [b'From: moshe\\nTo: moshe\\n\\nHow are you, friend?\\n']\n\n    def __init__(self, exceptionType):\n        self.messages = DummyMailbox.messages[:]\n        self.exceptionType = exceptionType\n\n\n    def listMessages(self, i=None):\n        \"\"\"\n        Get some message information.\n\n        @param i: See L{pop3.IMailbox.listMessages}.\n        @return: See L{pop3.IMailbox.listMessages}.\n        \"\"\"\n        if i is None:\n            return [len(m) for m in self.messages]\n        if i >= len(self.messages):\n            raise self.exceptionType()\n        return len(self.messages[i])\n\n\n    def getMessage(self, i):\n        \"\"\"\n        Get the message content.\n\n        @param i: See L{pop3.IMailbox.getMessage}.\n        @return: See L{pop3.IMailbox.getMessage}.\n        \"\"\"\n        return BytesIO(self.messages[i])\n\n\n    def getUidl(self, i):\n        \"\"\"\n        Construct a UID which is simply the string representation of the given\n        index.\n\n        @param i: See L{pop3.IMailbox.getUidl}.\n        @return: See L{pop3.IMailbox.getUidl}.\n        \"\"\"\n        if i >= len(self.messages):\n            raise self.exceptionType()\n        return intToBytes(i)\n\n\n    def deleteMessage(self, i):\n        \"\"\"\n        Wipe the message at the given index.\n\n        @param i: See L{pop3.IMailbox.deleteMessage}.\n        \"\"\"\n        self.messages[i] = b''\n\n\n\nclass AnotherPOP3Tests(unittest.TestCase):\n    \"\"\"\n    Additional L{pop3.POP3} tests.\n    \"\"\"\n    def runTest(self, lines, expectedOutput):\n        \"\"\"\n        Assert that when C{lines} are delivered to L{pop3.POP3} it responds\n        with C{expectedOutput}.\n\n        @param lines: A sequence of L{bytes} representing lines to deliver to\n            the server.\n\n        @param expectedOutput: A sequence of L{bytes} representing the\n            expected response from the server.\n\n        @return: A L{Deferred} that fires when the lines have been delivered\n            and the output checked.\n        \"\"\"\n        dummy = DummyPOP3()\n        client = LineSendingProtocol(lines)\n        d = loopback.loopbackAsync(dummy, client)\n        return d.addCallback(self._cbRunTest, client, dummy, expectedOutput)\n\n\n    def _cbRunTest(self, ignored, client, dummy, expectedOutput):\n        self.assertEqual(b'\\r\\n'.join(expectedOutput),\n                         b'\\r\\n'.join(client.response))\n        dummy.connectionLost(failure.Failure(\n                             Exception(\"Test harness disconnect\")))\n        return ignored\n\n\n    def test_buffer(self):\n        \"\"\"\n        Test a lot of different POP3 commands in an extremely pipelined\n        scenario.\n\n        This test may cover legitimate behavior, but the intent and\n        granularity are not very good.  It would likely be an improvement to\n        split it into a number of smaller, more focused tests.\n        \"\"\"\n        return self.runTest(\n            [b\"APOP moshez dummy\",\n             b\"LIST\",\n             b\"UIDL\",\n             b\"RETR 1\",\n             b\"RETR 2\",\n             b\"DELE 1\",\n             b\"RETR 1\",\n             b\"QUIT\"],\n            [b'+OK <moshez>',\n             b'+OK Authentication succeeded',\n             b'+OK 1',\n             b'1 44',\n             b'.',\n             b'+OK ',\n             b'1 0',\n             b'.',\n             b'+OK 44',\n             b'From: moshe',\n             b'To: moshe',\n             b'',\n             b'How are you, friend?',\n             b'.',\n             b'-ERR Bad message number argument',\n             b'+OK ',\n             b'-ERR message deleted',\n             b'+OK '])\n\n\n    def test_noop(self):\n        \"\"\"\n        Test the no-op command.\n        \"\"\"\n        return self.runTest(\n            [b'APOP spiv dummy',\n             b'NOOP',\n             b'QUIT'],\n            [b'+OK <moshez>',\n             b'+OK Authentication succeeded',\n             b'+OK ',\n             b'+OK '])\n\n\n    def test_authListing(self):\n        \"\"\"\n        L{pop3.POP3} responds to an I{AUTH} command with a list of supported\n        authentication types based on its factory's C{challengers}.\n        \"\"\"\n        p = DummyPOP3()\n        p.factory = internet.protocol.Factory()\n        p.factory.challengers = {b'Auth1': None, b'secondAuth': None,\n                                 b'authLast': None}\n        client = LineSendingProtocol([\n            b\"AUTH\",\n            b\"QUIT\",\n        ])\n\n        d = loopback.loopbackAsync(p, client)\n        return d.addCallback(self._cbTestAuthListing, client)\n\n\n    def _cbTestAuthListing(self, ignored, client):\n        self.assertTrue(client.response[1].startswith(b'+OK'))\n        self.assertEqual(sorted(client.response[2:5]),\n                         [b\"AUTH1\", b\"AUTHLAST\", b\"SECONDAUTH\"])\n        self.assertEqual(client.response[5], b\".\")\n\n\n    def test_illegalPASS(self):\n        \"\"\"\n        L{pop3.POP3} handles a I{PASS} command before a I{USER} command with an\n        error indicating the out-of-sequence operation.\n        \"\"\"\n        dummy = DummyPOP3()\n        client = LineSendingProtocol([\n            b\"PASS fooz\",\n            b\"QUIT\"\n        ])\n        d = loopback.loopbackAsync(dummy, client)\n        return d.addCallback(self._cbTestIllegalPASS, client, dummy)\n\n\n    def _cbTestIllegalPASS(self, ignored, client, dummy):\n        expectedOutput = (\n            b'+OK <moshez>\\r\\n-ERR USER required before PASS\\r\\n+OK \\r\\n')\n        self.assertEqual(expectedOutput,\n                         b'\\r\\n'.join(client.response) + b'\\r\\n')\n        dummy.connectionLost(failure.Failure(\n                             Exception(\"Test harness disconnect\")))\n\n\n    def test_emptyPASS(self):\n        \"\"\"\n        L{pop3.POP3} handles a I{PASS} command with a password equal to C{\"\"}\n        as it would any other value.\n        \"\"\"\n        dummy = DummyPOP3()\n        client = LineSendingProtocol([\n            b\"PASS \",\n            b\"QUIT\"\n        ])\n        d = loopback.loopbackAsync(dummy, client)\n        return d.addCallback(self._cbTestEmptyPASS, client, dummy)\n\n\n    def _cbTestEmptyPASS(self, ignored, client, dummy):\n        expectedOutput = (\n            b'+OK <moshez>\\r\\n-ERR USER required before PASS\\r\\n+OK \\r\\n')\n        self.assertEqual(expectedOutput,\n                         b'\\r\\n'.join(client.response) + b'\\r\\n')\n        dummy.connectionLost(failure.Failure(\n                             Exception(\"Test harness disconnect\")))\n\n\n    def test_badUTF8CharactersInCommand(self):\n        \"\"\"\n        Sending a command with invalid UTF-8 characters\n        will raise a L{pop3.POP3Error}.\n        \"\"\"\n        error = str(b'not authenticated yet: cannot do \\x81PASS')\n        if not isinstance(error, bytes):\n            error = error.encode(\"utf-8\")\n        d = self.runTest(\n            [b'\\x81PASS',\n             b'QUIT'],\n            [b'+OK <moshez>',\n             b\"-ERR bad protocol or server: POP3Error: \" +\n             error,\n             b'+OK '])\n        errors = self.flushLoggedErrors(pop3.POP3Error)\n        self.assertEqual(len(errors), 1)\n        return d\n\n\n\n@implementer(pop3.IServerFactory)\nclass TestServerFactory:\n    \"\"\"\n    A L{pop3.IServerFactory} implementation, for use by the test suite, with\n    some behavior controlled by the values of (settable) public attributes and\n    other behavior based on values hard-coded both here and in some test\n    methods.\n    \"\"\"\n    def cap_IMPLEMENTATION(self):\n        \"\"\"\n        Return the hard-coded value.\n\n        @return: L{pop3.IServerFactory}\n        \"\"\"\n        return \"Test Implementation String\"\n\n\n    def cap_EXPIRE(self):\n        \"\"\"\n        Return the hard-coded value.\n\n        @return: L{pop3.IServerFactory}\n        \"\"\"\n        return 60\n\n    challengers = OrderedDict([(b\"SCHEME_1\", None), (b\"SCHEME_2\", None)])\n\n    def cap_LOGIN_DELAY(self):\n        \"\"\"\n        Return the hard-coded value.\n\n        @return: L{pop3.IServerFactory}\n        \"\"\"\n        return 120\n\n    pue = True\n    def perUserExpiration(self):\n        \"\"\"\n        Return the hard-coded value.\n\n        @return: L{pop3.IServerFactory}\n        \"\"\"\n        return self.pue\n\n    puld = True\n    def perUserLoginDelay(self):\n        \"\"\"\n        Return the hard-coded value.\n\n        @return: L{pop3.IServerFactory}\n        \"\"\"\n        return self.puld\n\n\n\nclass TestMailbox:\n    \"\"\"\n    An incomplete L{IMailbox} implementation with certain per-user values\n    hard-coded and known by tests in this module.\n\n\n    This is useful for testing the server's per-user capability\n    implementation.\n    \"\"\"\n    loginDelay = 100\n    messageExpiration = 25\n\n\n\ndef contained(testcase, s, *caps):\n    \"\"\"\n    Assert that the given capability is included in all of the capability\n    sets.\n\n    @param testcase: A L{unittest.TestCase} to use to make assertions.\n\n    @param s: The capability for which to check.\n    @type s: L{bytes}\n\n    @param caps: The capability sets in which to check.\n    @type caps: L{tuple} of iterable\n    \"\"\"\n    for c in caps:\n        testcase.assertIn(s, c)\n\n\n\nclass CapabilityTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{pop3.POP3}'s per-user capability handling.\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Create a POP3 server with some capabilities.\n        \"\"\"\n        s = BytesIO()\n        p = pop3.POP3()\n        p.factory = TestServerFactory()\n        p.transport = internet.protocol.FileWrapper(s)\n        p.connectionMade()\n        p.do_CAPA()\n\n        self.caps = p.listCapabilities()\n        self.pcaps = s.getvalue().splitlines()\n\n        s = BytesIO()\n        p.mbox = TestMailbox()\n        p.transport = internet.protocol.FileWrapper(s)\n        p.do_CAPA()\n\n        self.lpcaps = s.getvalue().splitlines()\n        p.connectionLost(failure.Failure(Exception(\"Test harness disconnect\")))\n\n\n    def test_UIDL(self):\n        \"\"\"\n        The server can advertise the I{UIDL} capability.\n        \"\"\"\n        contained(self, b\"UIDL\", self.caps, self.pcaps, self.lpcaps)\n\n\n    def test_TOP(self):\n        \"\"\"\n        The server can advertise the I{TOP} capability.\n        \"\"\"\n        contained(self, b\"TOP\", self.caps, self.pcaps, self.lpcaps)\n\n\n    def test_USER(self):\n        \"\"\"\n        The server can advertise the I{USER} capability.\n        \"\"\"\n        contained(self, b\"USER\", self.caps, self.pcaps, self.lpcaps)\n\n\n    def test_EXPIRE(self):\n        \"\"\"\n        The server can advertise its per-user expiration as well as a global\n        expiration.\n        \"\"\"\n        contained(self, b\"EXPIRE 60 USER\", self.caps, self.pcaps)\n        contained(self, b\"EXPIRE 25\", self.lpcaps)\n\n\n    def test_IMPLEMENTATION(self):\n        \"\"\"\n        The server can advertise its implementation string.\n        \"\"\"\n        contained(\n            self,\n            b\"IMPLEMENTATION Test Implementation String\",\n            self.caps, self.pcaps, self.lpcaps\n        )\n\n\n    def test_SASL(self):\n        \"\"\"\n        The server can advertise the SASL schemes it supports.\n        \"\"\"\n        contained(\n            self,\n            b\"SASL SCHEME_1 SCHEME_2\",\n            self.caps, self.pcaps, self.lpcaps\n        )\n\n\n    def test_LOGIN_DELAY(self):\n        \"\"\"\n        The can advertise a per-user login delay as well as a global login\n        delay.\n        \"\"\"\n        contained(self, b\"LOGIN-DELAY 120 USER\", self.caps, self.pcaps)\n        self.assertIn(b\"LOGIN-DELAY 100\", self.lpcaps)\n\n\n\nclass GlobalCapabilitiesTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{pop3.POP3}'s global capability handling.\n    \"\"\"\n    def setUp(self):\n        \"\"\"\n        Create a POP3 server with some capabilities.\n        \"\"\"\n        s = BytesIO()\n        p = pop3.POP3()\n        p.factory = TestServerFactory()\n        p.factory.pue = p.factory.puld = False\n        p.transport = internet.protocol.FileWrapper(s)\n        p.connectionMade()\n        p.do_CAPA()\n\n        self.caps = p.listCapabilities()\n        self.pcaps = s.getvalue().splitlines()\n\n        s = BytesIO()\n        p.mbox = TestMailbox()\n        p.transport = internet.protocol.FileWrapper(s)\n        p.do_CAPA()\n\n        self.lpcaps = s.getvalue().splitlines()\n        p.connectionLost(failure.Failure(Exception(\"Test harness disconnect\")))\n\n\n    def test_EXPIRE(self):\n        \"\"\"\n        I{EXPIRE} is in the server's advertised capabilities.\n        \"\"\"\n        contained(self, b\"EXPIRE 60\", self.caps, self.pcaps, self.lpcaps)\n\n\n    def test_LOGIN_DELAY(self):\n        \"\"\"\n        I{LOGIN-DELAY} is in the server's advertised capabilities.\n        \"\"\"\n        contained(self, b\"LOGIN-DELAY 120\", self.caps, self.pcaps, self.lpcaps)\n\n\n\nclass TestRealm:\n    \"\"\"\n    An L{IRealm} which knows about a single test account's mailbox.\n    \"\"\"\n    def requestAvatar(self, avatarId, mind, *interfaces):\n        \"\"\"\n        Retrieve a mailbox for I{testuser} or fail.\n\n        @param avatarId: See L{IRealm.requestAvatar}.\n        @param mind: See L{IRealm.requestAvatar}.\n        @param interfaces: See L{IRealm.requestAvatar}.\n\n        @raises: L{AssertionError} when requesting an C{avatarId} other than\n            I{testuser}.\n        \"\"\"\n        if avatarId == b'testuser':\n            return pop3.IMailbox, DummyMailbox(ValueError), lambda: None\n        assert False\n\n\n\nclass SASLTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{pop3.POP3}'s SASL implementation.\n    \"\"\"\n    def test_ValidLogin(self):\n        \"\"\"\n        A CRAM-MD5-based SASL login attempt succeeds if it uses a username and\n        a hashed password known to the server's credentials checker.\n        \"\"\"\n        p = pop3.POP3()\n        p.factory = TestServerFactory()\n        p.factory.challengers = {b'CRAM-MD5':\n                                 cred.credentials.CramMD5Credentials}\n        p.portal = cred.portal.Portal(TestRealm())\n        ch = cred.checkers.InMemoryUsernamePasswordDatabaseDontUse()\n        ch.addUser(b'testuser', b'testpassword')\n        p.portal.registerChecker(ch)\n\n        s = BytesIO()\n        p.transport = internet.protocol.FileWrapper(s)\n        p.connectionMade()\n\n        p.lineReceived(b\"CAPA\")\n        self.assertTrue(s.getvalue().find(b\"SASL CRAM-MD5\") >= 0)\n\n        p.lineReceived(b\"AUTH CRAM-MD5\")\n        chal = s.getvalue().splitlines()[-1][2:]\n        chal = base64.decodestring(chal)\n        response = hmac.HMAC(b'testpassword', chal).hexdigest().encode(\"ascii\")\n\n        p.lineReceived(\n            base64.encodestring(b'testuser ' + response).rstrip(b'\\n'))\n        self.assertTrue(p.mbox)\n        self.assertTrue(s.getvalue().splitlines()[-1].find(b\"+OK\") >= 0)\n        p.connectionLost(failure.Failure(Exception(\"Test harness disconnect\")))\n\n\n\nclass CommandMixin:\n    \"\"\"\n    Tests for all the commands a POP3 server is allowed to receive.\n    \"\"\"\n\n    extraMessage = b'''\\\nFrom: guy\nTo: fellow\n\nMore message text for you.\n'''\n\n\n    def setUp(self):\n        \"\"\"\n        Make a POP3 server protocol instance hooked up to a simple mailbox and\n        a transport that buffers output to a BytesIO.\n        \"\"\"\n        p = pop3.POP3()\n        p.mbox = self.mailboxType(self.exceptionType)\n        p.schedule = list\n        self.pop3Server = p\n\n        s = BytesIO()\n        p.transport = internet.protocol.FileWrapper(s)\n        p.connectionMade()\n        s.seek(0)\n        s.truncate(0)\n        self.pop3Transport = s\n\n\n    def tearDown(self):\n        \"\"\"\n        Disconnect the server protocol so it can clean up anything it might\n        need to clean up.\n        \"\"\"\n        self.pop3Server.connectionLost(failure.Failure(\n                                       Exception(\"Test harness disconnect\")))\n\n\n    def _flush(self):\n        \"\"\"\n        Do some of the things that the reactor would take care of, if the\n        reactor were actually running.\n        \"\"\"\n        # Oh man FileWrapper is pooh.\n        self.pop3Server.transport._checkProducer()\n\n\n    def test_LIST(self):\n        \"\"\"\n        Test the two forms of list: with a message index number, which should\n        return a short-form response, and without a message index number, which\n        should return a long-form response, one line per message.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n\n        p.lineReceived(b\"LIST 1\")\n        self._flush()\n        self.assertEqual(s.getvalue(), b\"+OK 1 44\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n        p.lineReceived(b\"LIST\")\n        self._flush()\n        self.assertEqual(s.getvalue(), b\"+OK 1\\r\\n1 44\\r\\n.\\r\\n\")\n\n\n    def test_LISTWithBadArgument(self):\n        \"\"\"\n        Test that non-integers and out-of-bound integers produce appropriate\n        error responses.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n\n        p.lineReceived(b\"LIST a\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Invalid message-number: a\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n        p.lineReceived(b\"LIST 0\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Invalid message-number: 0\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n        p.lineReceived(b\"LIST 2\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Invalid message-number: 2\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n\n    def test_UIDL(self):\n        \"\"\"\n        Test the two forms of the UIDL command.  These are just like the two\n        forms of the LIST command.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n\n        p.lineReceived(b\"UIDL 1\")\n        self.assertEqual(s.getvalue(), b\"+OK 0\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n        p.lineReceived(b\"UIDL\")\n        self._flush()\n        self.assertEqual(s.getvalue(), b\"+OK \\r\\n1 0\\r\\n.\\r\\n\")\n\n\n    def test_UIDLWithBadArgument(self):\n        \"\"\"\n        Test that UIDL with a non-integer or an out-of-bounds integer produces\n        the appropriate error response.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n\n        p.lineReceived(b\"UIDL a\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Bad message number argument\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n        p.lineReceived(b\"UIDL 0\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Bad message number argument\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n        p.lineReceived(b\"UIDL 2\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Bad message number argument\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n\n    def test_STAT(self):\n        \"\"\"\n        Test the single form of the STAT command, which returns a short-form\n        response of the number of messages in the mailbox and their total size.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n\n        p.lineReceived(b\"STAT\")\n        self._flush()\n        self.assertEqual(s.getvalue(), b\"+OK 1 44\\r\\n\")\n\n\n    def test_RETR(self):\n        \"\"\"\n        Test downloading a message.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n\n        p.lineReceived(b\"RETR 1\")\n        self._flush()\n        self.assertEqual(\n            s.getvalue(),\n            b\"+OK 44\\r\\n\"\n            b\"From: moshe\\r\\n\"\n            b\"To: moshe\\r\\n\"\n            b\"\\r\\n\"\n            b\"How are you, friend?\\r\\n\"\n            b\".\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n\n    def test_RETRWithBadArgument(self):\n        \"\"\"\n        Test that trying to download a message with a bad argument, either not\n        an integer or an out-of-bounds integer, fails with the appropriate\n        error response.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n\n        p.lineReceived(b\"RETR a\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Bad message number argument\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n        p.lineReceived(b\"RETR 0\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Bad message number argument\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n        p.lineReceived(b\"RETR 2\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Bad message number argument\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n\n    def test_TOP(self):\n        \"\"\"\n        Test downloading the headers and part of the body of a message.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n        p.mbox.messages.append(self.extraMessage)\n\n        p.lineReceived(b\"TOP 1 0\")\n        self._flush()\n        self.assertEqual(\n            s.getvalue(),\n            b\"+OK Top of message follows\\r\\n\"\n            b\"From: moshe\\r\\n\"\n            b\"To: moshe\\r\\n\"\n            b\"\\r\\n\"\n            b\".\\r\\n\")\n\n\n    def test_TOPWithBadArgument(self):\n        \"\"\"\n        Test that trying to download a message with a bad argument, either a\n        message number which isn't an integer or is an out-of-bounds integer or\n        a number of lines which isn't an integer or is a negative integer,\n        fails with the appropriate error response.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n        p.mbox.messages.append(self.extraMessage)\n\n        p.lineReceived(b\"TOP 1 a\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Bad line count argument\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n        p.lineReceived(b\"TOP 1 -1\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Bad line count argument\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n        p.lineReceived(b\"TOP a 1\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Bad message number argument\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n        p.lineReceived(b\"TOP 0 1\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Bad message number argument\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n        p.lineReceived(b\"TOP 3 1\")\n        self.assertEqual(\n            s.getvalue(),\n            b\"-ERR Bad message number argument\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n\n    def test_LAST(self):\n        \"\"\"\n        Test the exceedingly pointless LAST command, which tells you the\n        highest message index which you have already downloaded.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n        p.mbox.messages.append(self.extraMessage)\n\n        p.lineReceived(b'LAST')\n        self.assertEqual(\n            s.getvalue(),\n            b\"+OK 0\\r\\n\")\n        s.seek(0)\n        s.truncate(0)\n\n\n    def test_RetrieveUpdatesHighest(self):\n        \"\"\"\n        Test that issuing a RETR command updates the LAST response.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n        p.mbox.messages.append(self.extraMessage)\n\n        p.lineReceived(b'RETR 2')\n        self._flush()\n        s.seek(0)\n        s.truncate(0)\n        p.lineReceived(b'LAST')\n        self.assertEqual(\n            s.getvalue(),\n            b'+OK 2\\r\\n')\n        s.seek(0)\n        s.truncate(0)\n\n\n    def test_TopUpdatesHighest(self):\n        \"\"\"\n        Test that issuing a TOP command updates the LAST response.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n        p.mbox.messages.append(self.extraMessage)\n\n        p.lineReceived(b'TOP 2 10')\n        self._flush()\n        s.seek(0)\n        s.truncate(0)\n        p.lineReceived(b'LAST')\n        self.assertEqual(\n            s.getvalue(),\n            b'+OK 2\\r\\n')\n\n\n    def test_HighestOnlyProgresses(self):\n        \"\"\"\n        Test that downloading a message with a smaller index than the current\n        LAST response doesn't change the LAST response.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n        p.mbox.messages.append(self.extraMessage)\n\n        p.lineReceived(b'RETR 2')\n        self._flush()\n        p.lineReceived(b'TOP 1 10')\n        self._flush()\n        s.seek(0)\n        s.truncate(0)\n        p.lineReceived(b'LAST')\n        self.assertEqual(\n            s.getvalue(),\n            b'+OK 2\\r\\n')\n\n\n    def test_ResetClearsHighest(self):\n        \"\"\"\n        Test that issuing RSET changes the LAST response to 0.\n        \"\"\"\n        p = self.pop3Server\n        s = self.pop3Transport\n        p.mbox.messages.append(self.extraMessage)\n\n        p.lineReceived(b'RETR 2')\n        self._flush()\n        p.lineReceived(b'RSET')\n        s.seek(0)\n        s.truncate(0)\n        p.lineReceived(b'LAST')\n        self.assertEqual(\n            s.getvalue(),\n            b'+OK 0\\r\\n')\n\n\n\n_listMessageDeprecation = (\n    \"twisted.mail.pop3.IMailbox.listMessages may not \"\n    \"raise IndexError for out-of-bounds message numbers: \"\n    \"raise ValueError instead.\")\n_listMessageSuppression = util.suppress(\n    message=_listMessageDeprecation,\n    category=PendingDeprecationWarning)\n\n_getUidlDeprecation = (\n    \"twisted.mail.pop3.IMailbox.getUidl may not \"\n    \"raise IndexError for out-of-bounds message numbers: \"\n    \"raise ValueError instead.\")\n_getUidlSuppression = util.suppress(\n    message=_getUidlDeprecation,\n    category=PendingDeprecationWarning)\n\nclass IndexErrorCommandTests(CommandMixin, unittest.TestCase):\n    \"\"\"\n    Run all of the command tests against a mailbox which raises IndexError\n    when an out of bounds request is made.  This behavior will be deprecated\n    shortly and then removed.\n    \"\"\"\n    exceptionType = IndexError\n    mailboxType = DummyMailbox\n\n    def test_LISTWithBadArgument(self):\n        \"\"\"\n        An attempt to get metadata about a message with a bad argument fails\n        with an I{ERR} response even if the mailbox implementation raises\n        L{IndexError}.\n        \"\"\"\n        return CommandMixin.test_LISTWithBadArgument(self)\n    test_LISTWithBadArgument.suppress = [_listMessageSuppression]\n\n\n    def test_UIDLWithBadArgument(self):\n        \"\"\"\n        An attempt to look up the UID of a message with a bad argument fails\n        with an I{ERR} response even if the mailbox implementation raises\n        L{IndexError}.\n        \"\"\"\n        return CommandMixin.test_UIDLWithBadArgument(self)\n    test_UIDLWithBadArgument.suppress = [_getUidlSuppression]\n\n\n    def test_TOPWithBadArgument(self):\n        \"\"\"\n        An attempt to download some of a message with a bad argument fails with\n        an I{ERR} response even if the mailbox implementation raises\n        L{IndexError}.\n        \"\"\"\n        return CommandMixin.test_TOPWithBadArgument(self)\n    test_TOPWithBadArgument.suppress = [_listMessageSuppression]\n\n\n    def test_RETRWithBadArgument(self):\n        \"\"\"\n        An attempt to download a message with a bad argument fails with an\n        I{ERR} response even if the mailbox implementation raises\n        L{IndexError}.\n        \"\"\"\n        return CommandMixin.test_RETRWithBadArgument(self)\n    test_RETRWithBadArgument.suppress = [_listMessageSuppression]\n\n\n\nclass ValueErrorCommandTests(CommandMixin, unittest.TestCase):\n    \"\"\"\n    Run all of the command tests against a mailbox which raises ValueError\n    when an out of bounds request is made.  This is the correct behavior and\n    after support for mailboxes which raise IndexError is removed, this will\n    become just C{CommandTestCase}.\n    \"\"\"\n    exceptionType = ValueError\n    mailboxType = DummyMailbox\n\n\n\nclass SyncDeferredMailbox(DummyMailbox):\n    \"\"\"\n    Mailbox which has a listMessages implementation which returns a Deferred\n    which has already fired.\n    \"\"\"\n    def listMessages(self, n=None):\n        \"\"\"\n        Synchronously list messages.\n\n        @type n: L{int} or L{None}\n        @param n: The 0-based index of the message.\n\n        @return: A L{Deferred} which already has a message list result.\n        \"\"\"\n        return defer.succeed(DummyMailbox.listMessages(self, n))\n\n\n\nclass IndexErrorSyncDeferredCommandTests(IndexErrorCommandTests):\n    \"\"\"\n    Run all of the L{IndexErrorCommandTests} tests with a\n    synchronous-Deferred returning IMailbox implementation.\n    \"\"\"\n    mailboxType = SyncDeferredMailbox\n\n\n\nclass ValueErrorSyncDeferredCommandTests(ValueErrorCommandTests):\n    \"\"\"\n    Run all of the L{ValueErrorCommandTests} tests with a\n    synchronous-Deferred returning IMailbox implementation.\n    \"\"\"\n    mailboxType = SyncDeferredMailbox\n\n\n\nclass AsyncDeferredMailbox(DummyMailbox):\n    \"\"\"\n    Mailbox which has a listMessages implementation which returns a Deferred\n    which has not yet fired.\n    \"\"\"\n    def __init__(self, *a, **kw):\n        self.waiting = []\n        DummyMailbox.__init__(self, *a, **kw)\n\n\n    def listMessages(self, n=None):\n        \"\"\"\n        Record a new unfired L{Deferred} in C{self.waiting} and return it.\n\n        @type n: L{int} or L{None}\n        @param n: The 0-based index of the message.\n\n        @return: The L{Deferred}\n        \"\"\"\n        d = defer.Deferred()\n        # See AsyncDeferredMailbox._flush\n        self.waiting.append((d, DummyMailbox.listMessages(self, n)))\n        return d\n\n\n\nclass IndexErrorAsyncDeferredCommandTests(IndexErrorCommandTests):\n    \"\"\"\n    Run all of the L{IndexErrorCommandTests} tests with an\n    asynchronous-Deferred returning IMailbox implementation.\n    \"\"\"\n    mailboxType = AsyncDeferredMailbox\n\n    def _flush(self):\n        \"\"\"\n        Fire whatever Deferreds we've built up in our mailbox.\n        \"\"\"\n        while self.pop3Server.mbox.waiting:\n            d, a = self.pop3Server.mbox.waiting.pop()\n            d.callback(a)\n        IndexErrorCommandTests._flush(self)\n\n\n\nclass ValueErrorAsyncDeferredCommandTests(ValueErrorCommandTests):\n    \"\"\"\n    Run all of the L{IndexErrorCommandTests} tests with an\n    asynchronous-Deferred returning IMailbox implementation.\n    \"\"\"\n    mailboxType = AsyncDeferredMailbox\n\n    def _flush(self):\n        \"\"\"\n        Fire whatever Deferreds we've built up in our mailbox.\n        \"\"\"\n        while self.pop3Server.mbox.waiting:\n            d, a = self.pop3Server.mbox.waiting.pop()\n            d.callback(a)\n        ValueErrorCommandTests._flush(self)\n\n\n\nclass POP3MiscTests(unittest.TestCase):\n    \"\"\"\n    Miscellaneous tests more to do with module/package structure than\n    anything to do with the Post Office Protocol.\n    \"\"\"\n    def test_all(self):\n        \"\"\"\n        This test checks that all names listed in\n        twisted.mail.pop3.__all__ are actually present in the module.\n        \"\"\"\n        mod = twisted.mail.pop3\n        for attr in mod.__all__:\n            self.assertTrue(hasattr(mod, attr))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/test/test_pop3client.py",
    "content": "# -*- test-case-name: twisted.mail.test.test_pop3client -*-\n# Copyright (c) 2001-2004 Divmod Inc.\n# See LICENSE for details.\n\nimport sys\nimport inspect\n\nfrom zope.interface import directlyProvides\n\nfrom twisted.internet import reactor, defer, error, protocol, interfaces\nfrom twisted.mail.pop3 import AdvancedPOP3Client as POP3Client\nfrom twisted.mail.pop3 import InsecureAuthenticationDisallowed\nfrom twisted.mail.pop3 import ServerErrorResponse\nfrom twisted.mail.test import pop3testserver\nfrom twisted.protocols import basic, loopback\nfrom twisted.python import log\nfrom twisted.python.compat import intToBytes\nfrom twisted.test.proto_helpers import StringTransport\nfrom twisted.trial import unittest\n\n\ntry:\n    from twisted.test.ssl_helpers import ClientTLSContext, ServerTLSContext\nexcept ImportError:\n    ClientTLSContext = ServerTLSContext = None\n\n\n\nclass StringTransportWithConnectionLosing(StringTransport):\n    def loseConnection(self):\n        self.protocol.connectionLost(error.ConnectionDone())\n\n\ncapCache = {b\"TOP\": None, b\"LOGIN-DELAY\": b\"180\", b\"UIDL\": None, \\\n            b\"STLS\": None, b\"USER\": None, b\"SASL\": b\"LOGIN\"}\ndef setUp(greet=True):\n    p = POP3Client()\n\n    # Skip the CAPA login will issue if it doesn't already have a\n    # capability cache\n    p._capCache = capCache\n\n    t = StringTransportWithConnectionLosing()\n    t.protocol = p\n    p.makeConnection(t)\n\n    if greet:\n        p.dataReceived(b'+OK Hello!\\r\\n')\n\n    return p, t\n\n\n\ndef strip(f):\n    return lambda result, f=f: f()\n\n\n\nclass POP3ClientLoginTests(unittest.TestCase):\n    def testNegativeGreeting(self):\n        p, t = setUp(greet=False)\n        p.allowInsecureLogin = True\n        d = p.login(b\"username\", b\"password\")\n        p.dataReceived(b'-ERR Offline for maintenance\\r\\n')\n        return self.assertFailure(\n            d, ServerErrorResponse).addCallback(\n            lambda exc: self.assertEqual(exc.args[0],\n                b\"Offline for maintenance\"))\n\n\n    def testOkUser(self):\n        p, t = setUp()\n        d = p.user(b\"username\")\n        self.assertEqual(t.value(), b\"USER username\\r\\n\")\n        p.dataReceived(b\"+OK send password\\r\\n\")\n        return d.addCallback(self.assertEqual, b\"send password\")\n\n\n    def testBadUser(self):\n        p, t = setUp()\n        d = p.user(b\"username\")\n        self.assertEqual(t.value(), b\"USER username\\r\\n\")\n        p.dataReceived(b\"-ERR account suspended\\r\\n\")\n        return self.assertFailure(\n            d, ServerErrorResponse).addCallback(\n            lambda exc: self.assertEqual(exc.args[0], b\"account suspended\"))\n\n\n    def testOkPass(self):\n        p, t = setUp()\n        d = p.password(b\"password\")\n        self.assertEqual(t.value(), b\"PASS password\\r\\n\")\n        p.dataReceived(b\"+OK you're in!\\r\\n\")\n        return d.addCallback(self.assertEqual, b\"you're in!\")\n\n\n    def testBadPass(self):\n        p, t = setUp()\n        d = p.password(b\"password\")\n        self.assertEqual(t.value(), b\"PASS password\\r\\n\")\n        p.dataReceived(b\"-ERR go away\\r\\n\")\n        return self.assertFailure(\n            d, ServerErrorResponse).addCallback(\n            lambda exc: self.assertEqual(exc.args[0], b\"go away\"))\n\n\n    def testOkLogin(self):\n        p, t = setUp()\n        p.allowInsecureLogin = True\n        d = p.login(b\"username\", b\"password\")\n        self.assertEqual(t.value(), b\"USER username\\r\\n\")\n        p.dataReceived(b\"+OK go ahead\\r\\n\")\n        self.assertEqual(t.value(), b\"USER username\\r\\nPASS password\\r\\n\")\n        p.dataReceived(b\"+OK password accepted\\r\\n\")\n        return d.addCallback(self.assertEqual, b\"password accepted\")\n\n\n    def testBadPasswordLogin(self):\n        p, t = setUp()\n        p.allowInsecureLogin = True\n        d = p.login(b\"username\", b\"password\")\n        self.assertEqual(t.value(), b\"USER username\\r\\n\")\n        p.dataReceived(b\"+OK waiting on you\\r\\n\")\n        self.assertEqual(t.value(), b\"USER username\\r\\nPASS password\\r\\n\")\n        p.dataReceived(b\"-ERR bogus login\\r\\n\")\n        return self.assertFailure(\n            d, ServerErrorResponse).addCallback(\n            lambda exc: self.assertEqual(exc.args[0], b\"bogus login\"))\n\n\n    def testBadUsernameLogin(self):\n        p, t = setUp()\n        p.allowInsecureLogin = True\n        d = p.login(b\"username\", b\"password\")\n        self.assertEqual(t.value(), b\"USER username\\r\\n\")\n        p.dataReceived(b\"-ERR bogus login\\r\\n\")\n        return self.assertFailure(\n            d, ServerErrorResponse).addCallback(\n            lambda exc: self.assertEqual(exc.args[0], b\"bogus login\"))\n\n\n    def testServerGreeting(self):\n        p, t = setUp(greet=False)\n        p.dataReceived(b\"+OK lalala this has no challenge\\r\\n\")\n        self.assertEqual(p.serverChallenge, None)\n\n\n    def testServerGreetingWithChallenge(self):\n        p, t = setUp(greet=False)\n        p.dataReceived(b\"+OK <here is the challenge>\\r\\n\")\n        self.assertEqual(p.serverChallenge, b\"<here is the challenge>\")\n\n\n    def testAPOP(self):\n        p, t = setUp(greet=False)\n        p.dataReceived(b\"+OK <challenge string goes here>\\r\\n\")\n        d = p.login(b\"username\", b\"password\")\n        self.assertEqual(t.value(),\n            b\"APOP username f34f1e464d0d7927607753129cabe39a\\r\\n\")\n        p.dataReceived(b\"+OK Welcome!\\r\\n\")\n        return d.addCallback(self.assertEqual, b\"Welcome!\")\n\n\n    def testInsecureLoginRaisesException(self):\n        p, t = setUp(greet=False)\n        p.dataReceived(b\"+OK Howdy\\r\\n\")\n        d = p.login(b\"username\", b\"password\")\n        self.assertFalse(t.value())\n        return self.assertFailure(\n            d, InsecureAuthenticationDisallowed)\n\n\n    def testSSLTransportConsideredSecure(self):\n        \"\"\"\n        If a server doesn't offer APOP but the transport is secured using\n        SSL or TLS, a plaintext login should be allowed, not rejected with\n        an InsecureAuthenticationDisallowed exception.\n        \"\"\"\n        p, t = setUp(greet=False)\n        directlyProvides(t, interfaces.ISSLTransport)\n        p.dataReceived(b\"+OK Howdy\\r\\n\")\n        d = p.login(b\"username\", b\"password\")\n        self.assertEqual(t.value(), b\"USER username\\r\\n\")\n        t.clear()\n        p.dataReceived(b\"+OK\\r\\n\")\n        self.assertEqual(t.value(), b\"PASS password\\r\\n\")\n        p.dataReceived(b\"+OK\\r\\n\")\n        return d\n\n\n\nclass ListConsumer:\n    def __init__(self):\n        self.data = {}\n\n\n    def consume(self, result):\n        (item, value) = result\n        self.data.setdefault(item, []).append(value)\n\n\n\nclass MessageConsumer:\n    def __init__(self):\n        self.data = []\n\n\n    def consume(self, line):\n        self.data.append(line)\n\n\n\nclass POP3ClientListTests(unittest.TestCase):\n    def testListSize(self):\n        p, t = setUp()\n        d = p.listSize()\n        self.assertEqual(t.value(), b\"LIST\\r\\n\")\n        p.dataReceived(b\"+OK Here it comes\\r\\n\")\n        p.dataReceived(b\"1 3\\r\\n2 2\\r\\n3 1\\r\\n.\\r\\n\")\n        return d.addCallback(self.assertEqual, [3, 2, 1])\n\n\n    def testListSizeWithConsumer(self):\n        p, t = setUp()\n        c = ListConsumer()\n        f = c.consume\n        d = p.listSize(f)\n        self.assertEqual(t.value(), b\"LIST\\r\\n\")\n        p.dataReceived(b\"+OK Here it comes\\r\\n\")\n        p.dataReceived(b\"1 3\\r\\n2 2\\r\\n3 1\\r\\n\")\n        self.assertEqual(c.data, {0: [3], 1: [2], 2: [1]})\n        p.dataReceived(b\"5 3\\r\\n6 2\\r\\n7 1\\r\\n\")\n        self.assertEqual(c.data, {0: [3], 1: [2], 2: [1], 4: [3], 5: [2],\n                                  6: [1]})\n        p.dataReceived(b\".\\r\\n\")\n        return d.addCallback(self.assertIdentical, f)\n\n\n    def testFailedListSize(self):\n        p, t = setUp()\n        d = p.listSize()\n        self.assertEqual(t.value(), b\"LIST\\r\\n\")\n        p.dataReceived(b\"-ERR Fatal doom server exploded\\r\\n\")\n        return self.assertFailure(\n            d, ServerErrorResponse).addCallback(\n            lambda exc: self.assertEqual(exc.args[0],\n                b\"Fatal doom server exploded\"))\n\n\n    def testListUID(self):\n        p, t = setUp()\n        d = p.listUID()\n        self.assertEqual(t.value(), b\"UIDL\\r\\n\")\n        p.dataReceived(b\"+OK Here it comes\\r\\n\")\n        p.dataReceived(b\"1 abc\\r\\n2 def\\r\\n3 ghi\\r\\n.\\r\\n\")\n        return d.addCallback(self.assertEqual, [b\"abc\", b\"def\", b\"ghi\"])\n\n\n    def testListUIDWithConsumer(self):\n        p, t = setUp()\n        c = ListConsumer()\n        f = c.consume\n        d = p.listUID(f)\n        self.assertEqual(t.value(), b\"UIDL\\r\\n\")\n        p.dataReceived(b\"+OK Here it comes\\r\\n\")\n        p.dataReceived(b\"1 xyz\\r\\n2 abc\\r\\n5 mno\\r\\n\")\n        self.assertEqual(c.data, {0: [b\"xyz\"], 1: [b\"abc\"], 4: [b\"mno\"]})\n        p.dataReceived(b\".\\r\\n\")\n        return d.addCallback(self.assertIdentical, f)\n\n\n    def testFailedListUID(self):\n        p, t = setUp()\n        d = p.listUID()\n        self.assertEqual(t.value(), b\"UIDL\\r\\n\")\n        p.dataReceived(b\"-ERR Fatal doom server exploded\\r\\n\")\n        return self.assertFailure(\n            d, ServerErrorResponse).addCallback(\n            lambda exc: self.assertEqual(exc.args[0],\n                b\"Fatal doom server exploded\"))\n\n\n\nclass POP3ClientMessageTests(unittest.TestCase):\n    def testRetrieve(self):\n        p, t = setUp()\n        d = p.retrieve(7)\n        self.assertEqual(t.value(), b\"RETR 8\\r\\n\")\n        p.dataReceived(b\"+OK Message incoming\\r\\n\")\n        p.dataReceived(b\"La la la here is message text\\r\\n\")\n        p.dataReceived(b\"..Further message text tra la la\\r\\n\")\n        p.dataReceived(b\".\\r\\n\")\n        return d.addCallback(\n            self.assertEqual,\n            [b\"La la la here is message text\",\n             b\".Further message text tra la la\"])\n\n\n    def testRetrieveWithConsumer(self):\n        p, t = setUp()\n        c = MessageConsumer()\n        f = c.consume\n        d = p.retrieve(7, f)\n        self.assertEqual(t.value(), b\"RETR 8\\r\\n\")\n        p.dataReceived(b\"+OK Message incoming\\r\\n\")\n        p.dataReceived(b\"La la la here is message text\\r\\n\")\n        p.dataReceived(b\"..Further message text\\r\\n.\\r\\n\")\n        return d.addCallback(self._cbTestRetrieveWithConsumer, f, c)\n\n\n    def _cbTestRetrieveWithConsumer(self, result, f, c):\n        self.assertIdentical(result, f)\n        self.assertEqual(c.data, [b\"La la la here is message text\",\n                                   b\".Further message text\"])\n\n\n    def testPartialRetrieve(self):\n        p, t = setUp()\n        d = p.retrieve(7, lines=2)\n        self.assertEqual(t.value(), b\"TOP 8 2\\r\\n\")\n        p.dataReceived(b\"+OK 2 lines on the way\\r\\n\")\n        p.dataReceived(b\"Line the first!  Woop\\r\\n\")\n        p.dataReceived(b\"Line the last!  Bye\\r\\n\")\n        p.dataReceived(b\".\\r\\n\")\n        return d.addCallback(\n            self.assertEqual,\n            [b\"Line the first!  Woop\",\n             b\"Line the last!  Bye\"])\n\n\n    def testPartialRetrieveWithConsumer(self):\n        p, t = setUp()\n        c = MessageConsumer()\n        f = c.consume\n        d = p.retrieve(7, f, lines=2)\n        self.assertEqual(t.value(), b\"TOP 8 2\\r\\n\")\n        p.dataReceived(b\"+OK 2 lines on the way\\r\\n\")\n        p.dataReceived(b\"Line the first!  Woop\\r\\n\")\n        p.dataReceived(b\"Line the last!  Bye\\r\\n\")\n        p.dataReceived(b\".\\r\\n\")\n        return d.addCallback(self._cbTestPartialRetrieveWithConsumer, f, c)\n\n\n    def _cbTestPartialRetrieveWithConsumer(self, result, f, c):\n        self.assertIdentical(result, f)\n        self.assertEqual(c.data, [b\"Line the first!  Woop\",\n                                  b\"Line the last!  Bye\"])\n\n\n    def testFailedRetrieve(self):\n        p, t = setUp()\n        d = p.retrieve(0)\n        self.assertEqual(t.value(), b\"RETR 1\\r\\n\")\n        p.dataReceived(b\"-ERR Fatal doom server exploded\\r\\n\")\n        return self.assertFailure(\n            d, ServerErrorResponse).addCallback(\n            lambda exc: self.assertEqual(exc.args[0],\n                b\"Fatal doom server exploded\"))\n\n\n    def test_concurrentRetrieves(self):\n        \"\"\"\n        Issue three retrieve calls immediately without waiting for any to\n        succeed and make sure they all do succeed eventually.\n        \"\"\"\n        p, t = setUp()\n        messages = [\n            p.retrieve(i).addCallback(\n                self.assertEqual,\n                [b\"First line of \" + intToBytes(i + 1) + b\".\",\n                 b\"Second line of \" + intToBytes(i + 1) + b\".\"])\n            for i\n            in range(3)]\n\n        for i in range(1, 4):\n            self.assertEqual(t.value(), b\"RETR \" + intToBytes(i) + b\"\\r\\n\")\n            t.clear()\n            p.dataReceived(b\"+OK 2 lines on the way\\r\\n\")\n            p.dataReceived(b\"First line of \" + intToBytes(i) + b\".\\r\\n\")\n            p.dataReceived(b\"Second line of \" + intToBytes(i) + b\".\\r\\n\")\n            self.assertEqual(t.value(), b\"\")\n            p.dataReceived(b\".\\r\\n\")\n\n        return defer.DeferredList(messages, fireOnOneErrback=True)\n\n\n\nclass POP3ClientMiscTests(unittest.TestCase):\n    def testCapability(self):\n        p, t = setUp()\n        d = p.capabilities(useCache=0)\n        self.assertEqual(t.value(), b\"CAPA\\r\\n\")\n        p.dataReceived(b\"+OK Capabilities on the way\\r\\n\")\n        p.dataReceived(b\"X\\r\\nY\\r\\nZ\\r\\nA 1 2 3\\r\\nB 1 2\\r\\nC 1\\r\\n.\\r\\n\")\n        return d.addCallback(\n            self.assertEqual,\n            {b\"X\": None, b\"Y\": None, b\"Z\": None,\n             b\"A\": [b\"1\", b\"2\", b\"3\"],\n             b\"B\": [b\"1\", b\"2\"],\n             b\"C\": [b\"1\"]})\n\n\n    def testCapabilityError(self):\n        p, t = setUp()\n        d = p.capabilities(useCache=0)\n        self.assertEqual(t.value(), b\"CAPA\\r\\n\")\n        p.dataReceived(b\"-ERR This server is lame!\\r\\n\")\n        return d.addCallback(self.assertEqual, {})\n\n\n    def testStat(self):\n        p, t = setUp()\n        d = p.stat()\n        self.assertEqual(t.value(), b\"STAT\\r\\n\")\n        p.dataReceived(b\"+OK 1 1212\\r\\n\")\n        return d.addCallback(self.assertEqual, (1, 1212))\n\n\n    def testStatError(self):\n        p, t = setUp()\n        d = p.stat()\n        self.assertEqual(t.value(), b\"STAT\\r\\n\")\n        p.dataReceived(b\"-ERR This server is lame!\\r\\n\")\n        return self.assertFailure(\n            d, ServerErrorResponse).addCallback(\n            lambda exc: self.assertEqual(exc.args[0], b\"This server is lame!\"))\n\n\n    def testNoop(self):\n        p, t = setUp()\n        d = p.noop()\n        self.assertEqual(t.value(), b\"NOOP\\r\\n\")\n        p.dataReceived(b\"+OK No-op to you too!\\r\\n\")\n        return d.addCallback(self.assertEqual, b\"No-op to you too!\")\n\n\n    def testNoopError(self):\n        p, t = setUp()\n        d = p.noop()\n        self.assertEqual(t.value(), b\"NOOP\\r\\n\")\n        p.dataReceived(b\"-ERR This server is lame!\\r\\n\")\n        return self.assertFailure(\n            d, ServerErrorResponse).addCallback(\n            lambda exc: self.assertEqual(exc.args[0], b\"This server is lame!\"))\n\n\n    def testRset(self):\n        p, t = setUp()\n        d = p.reset()\n        self.assertEqual(t.value(), b\"RSET\\r\\n\")\n        p.dataReceived(b\"+OK Reset state\\r\\n\")\n        return d.addCallback(self.assertEqual, b\"Reset state\")\n\n\n    def testRsetError(self):\n        p, t = setUp()\n        d = p.reset()\n        self.assertEqual(t.value(), b\"RSET\\r\\n\")\n        p.dataReceived(b\"-ERR This server is lame!\\r\\n\")\n        return self.assertFailure(\n            d, ServerErrorResponse).addCallback(\n            lambda exc: self.assertEqual(exc.args[0], b\"This server is lame!\"))\n\n\n    def testDelete(self):\n        p, t = setUp()\n        d = p.delete(3)\n        self.assertEqual(t.value(), b\"DELE 4\\r\\n\")\n        p.dataReceived(b\"+OK Hasta la vista\\r\\n\")\n        return d.addCallback(self.assertEqual, b\"Hasta la vista\")\n\n\n    def testDeleteError(self):\n        p, t = setUp()\n        d = p.delete(3)\n        self.assertEqual(t.value(), b\"DELE 4\\r\\n\")\n        p.dataReceived(b\"-ERR Winner is not you.\\r\\n\")\n        return self.assertFailure(\n            d, ServerErrorResponse).addCallback(\n            lambda exc: self.assertEqual(exc.args[0], b\"Winner is not you.\"))\n\n\n\nclass SimpleClient(POP3Client):\n    def __init__(self, deferred, contextFactory=None):\n        self.deferred = deferred\n        self.allowInsecureLogin = True\n\n\n    def serverGreeting(self, challenge):\n        self.deferred.callback(None)\n\n\n\nclass POP3HelperMixin:\n    serverCTX = None\n    clientCTX = None\n\n    def setUp(self):\n        d = defer.Deferred()\n        self.server = pop3testserver.POP3TestServer(\n            contextFactory=self.serverCTX)\n        self.client = SimpleClient(d, contextFactory=self.clientCTX)\n        self.client.timeout = 30\n        self.connected = d\n\n\n    def tearDown(self):\n        del self.server\n        del self.client\n        del self.connected\n\n\n    def _cbStopClient(self, ignore):\n        self.client.transport.loseConnection()\n\n\n    def _ebGeneral(self, failure):\n        self.client.transport.loseConnection()\n        self.server.transport.loseConnection()\n        return failure\n\n\n    def loopback(self):\n        return loopback.loopbackTCP(self.server, self.client, noisy=False)\n\n\n\nclass TLSServerFactory(protocol.ServerFactory):\n    class protocol(basic.LineReceiver):\n        context = None\n        output = []\n        def connectionMade(self):\n            self.factory.input = []\n            self.output = self.output[:]\n            for line in self.output.pop(0):\n                self.sendLine(line)\n\n\n        def lineReceived(self, line):\n            self.factory.input.append(line)\n            [self.sendLine(l) for l in self.output.pop(0)]\n            if line == b'STLS':\n                self.transport.startTLS(self.context)\n\n\n\nclass POP3TLSTests(unittest.TestCase):\n    \"\"\"\n    Tests for POP3Client's support for TLS connections.\n    \"\"\"\n\n    def test_startTLS(self):\n        \"\"\"\n        POP3Client.startTLS starts a TLS session over its existing TCP\n        connection.\n        \"\"\"\n        sf = TLSServerFactory()\n        sf.protocol.output = [\n            [b'+OK'],  # Server greeting\n            [b'+OK', b'STLS', b'.'],  # CAPA response\n            [b'+OK'],  # STLS response\n            [b'+OK', b'.'],  # Second CAPA response\n            [b'+OK']  # QUIT response\n            ]\n        sf.protocol.context = ServerTLSContext()\n        port = reactor.listenTCP(0, sf, interface='127.0.0.1')\n        self.addCleanup(port.stopListening)\n        H = port.getHost().host\n        P = port.getHost().port\n\n        connLostDeferred = defer.Deferred()\n        cp = SimpleClient(defer.Deferred(), ClientTLSContext())\n        def connectionLost(reason):\n            SimpleClient.connectionLost(cp, reason)\n            connLostDeferred.callback(None)\n        cp.connectionLost = connectionLost\n        cf = protocol.ClientFactory()\n        cf.protocol = lambda: cp\n\n        conn = reactor.connectTCP(H, P, cf)\n\n        def cbConnected(ignored):\n            log.msg(\"Connected to server; starting TLS\")\n            return cp.startTLS()\n\n        def cbStartedTLS(ignored):\n            log.msg(\"Started TLS; disconnecting\")\n            return cp.quit()\n\n        def cbDisconnected(ign):\n            log.msg(\"Disconnected; asserting correct input received\")\n            self.assertEqual(\n                sf.input,\n                [b'CAPA', b'STLS', b'CAPA', b'QUIT'])\n\n        def cleanup(result):\n            log.msg(\"Asserted correct input; disconnecting \"\n                    \"client and shutting down server\")\n            conn.disconnect()\n            return connLostDeferred\n\n        cp.deferred.addCallback(cbConnected)\n        cp.deferred.addCallback(cbStartedTLS)\n        cp.deferred.addCallback(cbDisconnected)\n        cp.deferred.addBoth(cleanup)\n\n        return cp.deferred\n\n\n\nclass POP3TimeoutTests(POP3HelperMixin, unittest.TestCase):\n    def testTimeout(self):\n        def login():\n            d = self.client.login('test', 'twisted')\n            d.addCallback(loggedIn)\n            d.addErrback(timedOut)\n            return d\n\n        def loggedIn(result):\n            self.fail(\"Successfully logged in!?  Impossible!\")\n\n\n        def timedOut(failure):\n            failure.trap(error.TimeoutError)\n            self._cbStopClient(None)\n\n        def quit():\n            return self.client.quit()\n\n        self.client.timeout = 0.01\n\n        # Tell the server to not return a response to client.  This\n        # will trigger a timeout.\n        pop3testserver.TIMEOUT_RESPONSE = True\n\n        methods = [login, quit]\n        map(self.connected.addCallback, map(strip, methods))\n        self.connected.addCallback(self._cbStopClient)\n        self.connected.addErrback(self._ebGeneral)\n        return self.loopback()\n\n\n\nif ClientTLSContext is None:\n    for case in (POP3TLSTests,):\n        case.skip = \"OpenSSL not present\"\nelif interfaces.IReactorSSL(reactor, None) is None:\n    for case in (POP3TLSTests,):\n        case.skip = \"Reactor doesn't support SSL\"\n\n\n\nimport twisted.mail.pop3client\n\nclass POP3ClientModuleStructureTests(unittest.TestCase):\n    \"\"\"\n    Miscellaneous tests more to do with module/package structure than\n    anything to do with the POP3 client.\n    \"\"\"\n    def test_all(self):\n        \"\"\"\n        twisted.mail.pop3client.__all__ should be empty because all classes\n        should be imported through twisted.mail.pop3.\n        \"\"\"\n        self.assertEqual(twisted.mail.pop3client.__all__, [])\n\n\n    def test_import(self):\n        \"\"\"\n        Every public class in twisted.mail.pop3client should be available as a\n        member of twisted.mail.pop3 with the exception of\n        twisted.mail.pop3client.POP3Client which should be available as\n        twisted.mail.pop3.AdvancedClient.\n        \"\"\"\n        publicClasses = [c[0] for c in inspect.getmembers(\n                                       sys.modules['twisted.mail.pop3client'],\n                                       inspect.isclass)\n                         if not c[0][0] == '_']\n\n        for pc in publicClasses:\n            if not pc == 'POP3Client':\n                self.assertTrue(hasattr(twisted.mail.pop3, pc))\n            else:\n                self.assertTrue(hasattr(twisted.mail.pop3,\n                    'AdvancedPOP3Client'))\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/mail/test/test_smtp.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTest cases for twisted.mail.smtp module.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport inspect\nimport base64\n\nfrom io import BytesIO\n\nfrom zope.interface import implementer, directlyProvides\n\nfrom twisted.python.util import LineLog\nfrom twisted.trial import unittest\nfrom twisted.protocols import basic, loopback\nfrom twisted.internet import defer, protocol, reactor, interfaces\nfrom twisted.internet import address, error, task\nfrom twisted.test.proto_helpers import MemoryReactor, StringTransport\n\nfrom twisted import cred\nimport twisted.cred.error\nimport twisted.cred.portal\nimport twisted.cred.checkers\nimport twisted.cred.credentials\n\nfrom twisted.cred.portal import IRealm, Portal\nfrom twisted.cred.checkers import ICredentialsChecker, AllowAnonymousAccess\nfrom twisted.cred.credentials import IAnonymous\nfrom twisted.cred.error import UnauthorizedLogin\n\nfrom twisted.mail import smtp\nfrom twisted.mail._cred import LOGINCredentials\n\n\ntry:\n    from twisted.test.ssl_helpers import ClientTLSContext, ServerTLSContext\nexcept ImportError:\n    sslSkip = \"OpenSSL not present\"\nelse:\n    sslSkip = None\n\nimport re\n\n\ndef spameater(*spam, **eggs):\n    return None\n\n\n\n@implementer(smtp.IMessage)\nclass BrokenMessage(object):\n    \"\"\"\n    L{BrokenMessage} is an L{IMessage} which raises an unexpected exception\n    from its C{eomReceived} method.  This is useful for creating a server which\n    can be used to test client retry behavior.\n    \"\"\"\n    def __init__(self, user):\n        pass\n\n\n    def lineReceived(self, line):\n        pass\n\n\n    def eomReceived(self):\n        raise RuntimeError(\"Some problem, delivery is failing.\")\n\n\n    def connectionLost(self):\n        pass\n\n\n\nclass DummyMessage(object):\n    \"\"\"\n    L{BrokenMessage} is an L{IMessage} which saves the message delivered to it\n    to its domain object.\n\n    @ivar domain: A L{DummyDomain} which will be used to store the message once\n        it is received.\n    \"\"\"\n    def __init__(self, domain, user):\n        self.domain = domain\n        self.user = user\n        self.buffer = []\n\n\n    def lineReceived(self, line):\n        # Throw away the generated Received: header\n        if not re.match(b'Received: From yyy.com \\(\\[.*\\]\\) by localhost;',\n                        line):\n            self.buffer.append(line)\n\n\n    def eomReceived(self):\n        message = b'\\n'.join(self.buffer) + b'\\n'\n        self.domain.messages[self.user.dest.local].append(message)\n        deferred = defer.Deferred()\n        deferred.callback(b\"saved\")\n        return deferred\n\n\n\nclass DummyDomain(object):\n    \"\"\"\n    L{DummyDomain} is an L{IDomain} which keeps track of messages delivered to\n    it in memory.\n    \"\"\"\n    def __init__(self, names):\n        self.messages = {}\n        for name in names:\n            self.messages[name] = []\n\n\n    def exists(self, user):\n        if user.dest.local in self.messages:\n            return defer.succeed(lambda: DummyMessage(self, user))\n        return defer.fail(smtp.SMTPBadRcpt(user))\n\n\n\nmail = b'''\\\nSubject: hello\n\nGoodbye\n'''\n\nclass MyClient:\n    def __init__(self, messageInfo=None):\n        if messageInfo is None:\n            messageInfo = (\n                'moshez@foo.bar', ['moshez@foo.bar'], BytesIO(mail))\n        self._sender = messageInfo[0]\n        self._recipient = messageInfo[1]\n        self._data = messageInfo[2]\n\n\n    def getMailFrom(self):\n        return self._sender\n\n\n    def getMailTo(self):\n        return self._recipient\n\n\n    def getMailData(self):\n        return self._data\n\n\n    def sendError(self, exc):\n        self._error = exc\n\n\n    def sentMail(self, code, resp, numOk, addresses, log):\n        # Prevent another mail from being sent.\n        self._sender = None\n        self._recipient = None\n        self._data = None\n\n\n\nclass MySMTPClient(MyClient, smtp.SMTPClient):\n    def __init__(self, messageInfo=None):\n        smtp.SMTPClient.__init__(self, b'foo.baz')\n        MyClient.__init__(self, messageInfo)\n\n\n\nclass MyESMTPClient(MyClient, smtp.ESMTPClient):\n    def __init__(self, secret = b'', contextFactory = None):\n        smtp.ESMTPClient.__init__(self, secret, contextFactory, b'foo.baz')\n        MyClient.__init__(self)\n\n\n\nclass LoopbackMixin:\n    def loopback(self, server, client):\n        return loopback.loopbackTCP(server, client)\n\n\n\nclass FakeSMTPServer(basic.LineReceiver):\n\n    clientData = [\n        b'220 hello', b'250 nice to meet you',\n        b'250 great', b'250 great', b'354 go on, lad'\n    ]\n\n    def connectionMade(self):\n        self.buffer = []\n        self.clientData = self.clientData[:]\n        self.clientData.reverse()\n        self.sendLine(self.clientData.pop())\n\n\n    def lineReceived(self, line):\n        self.buffer.append(line)\n        if line == b\"QUIT\":\n            self.transport.write(b\"221 see ya around\\r\\n\")\n            self.transport.loseConnection()\n        elif line == b\".\":\n            self.transport.write(b\"250 gotcha\\r\\n\")\n        elif line == b\"RSET\":\n            self.transport.loseConnection()\n\n        if self.clientData:\n            self.sendLine(self.clientData.pop())\n\n\n\nclass SMTPClientTests(unittest.TestCase, LoopbackMixin):\n    \"\"\"\n    Tests for L{smtp.SMTPClient}.\n    \"\"\"\n\n    def test_timeoutConnection(self):\n        \"\"\"\n        L{smtp.SMTPClient.timeoutConnection} calls the C{sendError} hook with a\n        fatal L{SMTPTimeoutError} with the current line log.\n        \"\"\"\n        errors = []\n        client = MySMTPClient()\n        client.sendError = errors.append\n        client.makeConnection(StringTransport())\n        client.lineReceived(b\"220 hello\")\n        client.timeoutConnection()\n        self.assertIsInstance(errors[0], smtp.SMTPTimeoutError)\n        self.assertTrue(errors[0].isFatal)\n        self.assertEqual(\n            bytes(errors[0]),\n            b\"Timeout waiting for SMTP server response\\n\"\n            b\"<<< 220 hello\\n\"\n            b\">>> HELO foo.baz\\n\")\n\n    expected_output = [\n        b'HELO foo.baz', b'MAIL FROM:<moshez@foo.bar>',\n        b'RCPT TO:<moshez@foo.bar>', b'DATA',\n        b'Subject: hello', b'', b'Goodbye', b'.', b'RSET'\n    ]\n\n\n    def test_messages(self):\n        \"\"\"\n        L{smtp.SMTPClient} sends I{HELO}, I{MAIL FROM}, I{RCPT TO}, and I{DATA}\n        commands based on the return values of its C{getMailFrom},\n        C{getMailTo}, and C{getMailData} methods.\n        \"\"\"\n        client = MySMTPClient()\n        server = FakeSMTPServer()\n        d = self.loopback(server, client)\n        d.addCallback(lambda x :\n                      self.assertEqual(server.buffer, self.expected_output))\n        return d\n\n\n    def test_transferError(self):\n        \"\"\"\n        If there is an error while producing the message body to the\n        connection, the C{sendError} callback is invoked.\n        \"\"\"\n        client = MySMTPClient(\n            ('alice@example.com', ['bob@example.com'], BytesIO(b\"foo\")))\n        transport = StringTransport()\n        client.makeConnection(transport)\n        client.dataReceived(\n            b'220 Ok\\r\\n' # Greeting\n            b'250 Ok\\r\\n' # EHLO response\n            b'250 Ok\\r\\n' # MAIL FROM response\n            b'250 Ok\\r\\n' # RCPT TO response\n            b'354 Ok\\r\\n' # DATA response\n            )\n\n        # Sanity check - a pull producer should be registered now.\n        self.assertNotIdentical(transport.producer, None)\n        self.assertFalse(transport.streaming)\n\n        # Now stop the producer prematurely, meaning the message was not sent.\n        transport.producer.stopProducing()\n\n        # The sendError hook should have been invoked as a result.\n        self.assertIsInstance(client._error, Exception)\n\n\n    def test_sendFatalError(self):\n        \"\"\"\n        If L{smtp.SMTPClient.sendError} is called with an L{SMTPClientError}\n        which is fatal, it disconnects its transport without writing anything\n        more to it.\n        \"\"\"\n        client = smtp.SMTPClient(None)\n        transport = StringTransport()\n        client.makeConnection(transport)\n        client.sendError(smtp.SMTPClientError(123, \"foo\", isFatal=True))\n        self.assertEqual(transport.value(), b\"\")\n        self.assertTrue(transport.disconnecting)\n\n\n    def test_sendNonFatalError(self):\n        \"\"\"\n        If L{smtp.SMTPClient.sendError} is called with an L{SMTPClientError}\n        which is not fatal, it sends C{\"QUIT\"} and waits for the server to\n        close the connection.\n        \"\"\"\n        client = smtp.SMTPClient(None)\n        transport = StringTransport()\n        client.makeConnection(transport)\n        client.sendError(smtp.SMTPClientError(123, \"foo\", isFatal=False))\n        self.assertEqual(transport.value(), b\"QUIT\\r\\n\")\n        self.assertFalse(transport.disconnecting)\n\n\n    def test_sendOtherError(self):\n        \"\"\"\n        If L{smtp.SMTPClient.sendError} is called with an exception which is\n        not an L{SMTPClientError}, it disconnects its transport without\n        writing anything more to it.\n        \"\"\"\n        client = smtp.SMTPClient(None)\n        transport = StringTransport()\n        client.makeConnection(transport)\n        client.sendError(Exception(\"foo\"))\n        self.assertEqual(transport.value(), b\"\")\n        self.assertTrue(transport.disconnecting)\n\n\n\nclass DummySMTPMessage(object):\n\n    def __init__(self, protocol, users):\n        self.protocol = protocol\n        self.users = users\n        self.buffer = []\n\n\n    def lineReceived(self, line):\n        self.buffer.append(line)\n\n\n    def eomReceived(self):\n        message = b'\\n'.join(self.buffer) + b'\\n'\n        helo, origin = self.users[0].helo[0], bytes(self.users[0].orig)\n        recipients = []\n        for user in self.users:\n            recipients.append(bytes(user))\n        self.protocol.message[tuple(recipients)] = (helo, origin, recipients,\n                                                    message)\n        return defer.succeed(b\"saved\")\n\n\n\nclass DummyProto:\n\n    def connectionMade(self):\n        self.dummyMixinBase.connectionMade(self)\n        self.message = {}\n\n\n    def receivedHeader(*spam):\n        return None\n\n\n    def validateTo(self, user):\n        self.delivery = SimpleDelivery(None)\n        return lambda: DummySMTPMessage(self, [user])\n\n\n    def validateFrom(self, helo, origin):\n        return origin\n\n\n\nclass DummySMTP(DummyProto, smtp.SMTP):\n    dummyMixinBase = smtp.SMTP\n\n\n\nclass DummyESMTP(DummyProto, smtp.ESMTP):\n    dummyMixinBase = smtp.ESMTP\n\n\n\nclass AnotherTestCase:\n    serverClass = None\n    clientClass = None\n\n    messages = [ (b'foo.com', b'moshez@foo.com', [b'moshez@bar.com'],\n                  b'moshez@foo.com', [b'moshez@bar.com'], b'''\\\nFrom: Moshe\nTo: Moshe\n\nHi,\nhow are you?\n'''),\n                 (b'foo.com', b'tttt@rrr.com', [b'uuu@ooo', b'yyy@eee'],\n                  b'tttt@rrr.com', [b'uuu@ooo', b'yyy@eee'], b'''\\\nSubject: pass\n\n..rrrr..\n'''),\n                 (b'foo.com', b'@this,@is,@ignored:foo@bar.com',\n                  [b'@ignore,@this,@too:bar@foo.com'],\n                  b'foo@bar.com', [b'bar@foo.com'], b'''\\\nSubject: apa\nTo: foo\n\n123\n.\n456\n'''),\n              ]\n\n    data = [\n        (b'', b'220.*\\r\\n$', None, None),\n        (b'HELO foo.com\\r\\n', b'250.*\\r\\n$', None, None),\n        (b'RSET\\r\\n', b'250.*\\r\\n$', None, None),\n        ]\n    for helo_, from_, to_, realfrom, realto, msg in messages:\n        data.append((b'MAIL FROM:<' + from_ + b'>\\r\\n', b'250.*\\r\\n',\n                     None, None))\n        for rcpt in to_:\n            data.append((b'RCPT TO:<' + rcpt + b'>\\r\\n', b'250.*\\r\\n',\n                         None, None))\n\n        data.append((b'DATA\\r\\n', b'354.*\\r\\n',\n                     msg, (b'250.*\\r\\n',\n                           (helo_, realfrom, realto, msg))))\n\n\n    def test_buffer(self):\n        \"\"\"\n        Exercise a lot of the SMTP client code.  This is a \"shotgun\" style unit\n        test.  It does a lot of things and hopes that something will go really\n        wrong if it is going to go wrong.  This test should be replaced with a\n        suite of nicer tests.\n        \"\"\"\n        transport = StringTransport()\n        a = self.serverClass()\n        class fooFactory:\n            domain = b'foo.com'\n\n        a.factory = fooFactory()\n        a.makeConnection(transport)\n        for (send, expect, msg, msgexpect) in self.data:\n            if send:\n                a.dataReceived(send)\n            data = transport.value()\n            transport.clear()\n            if not re.match(expect, data):\n                raise AssertionError(send, expect, data)\n            if data[:3] == b'354':\n                for line in msg.splitlines():\n                    if line and line[0:1] == b'.':\n                        line = b'.' + line\n                    a.dataReceived(line + b'\\r\\n')\n                a.dataReceived(b'.\\r\\n')\n                # Special case for DATA. Now we want a 250, and then\n                # we compare the messages\n                data = transport.value()\n                transport.clear()\n                resp, msgdata = msgexpect\n                if not re.match(resp, data):\n                    raise AssertionError(resp, data)\n                for recip in msgdata[2]:\n                    expected = list(msgdata[:])\n                    expected[2] = [recip]\n                    self.assertEqual(\n                        a.message[(recip,)],\n                        tuple(expected)\n                    )\n        a.setTimeout(None)\n\n\n\nclass AnotherESMTPTests(AnotherTestCase, unittest.TestCase):\n    serverClass = DummyESMTP\n    clientClass = MyESMTPClient\n\n\n\nclass AnotherSMTPTests(AnotherTestCase, unittest.TestCase):\n    serverClass = DummySMTP\n    clientClass = MySMTPClient\n\n\n\n@implementer(cred.checkers.ICredentialsChecker)\nclass DummyChecker:\n    users = {\n        b'testuser': b'testpassword'\n    }\n\n    credentialInterfaces = (cred.credentials.IUsernamePassword,\n                            cred.credentials.IUsernameHashedPassword)\n\n    def requestAvatarId(self, credentials):\n        return defer.maybeDeferred(\n            credentials.checkPassword, self.users[credentials.username]\n        ).addCallback(self._cbCheck, credentials.username)\n\n    def _cbCheck(self, result, username):\n        if result:\n            return username\n        raise cred.error.UnauthorizedLogin()\n\n\n\n@implementer(smtp.IMessageDelivery)\nclass SimpleDelivery(object):\n    \"\"\"\n    L{SimpleDelivery} is a message delivery factory with no interesting\n    behavior.\n    \"\"\"\n    def __init__(self, messageFactory):\n        self._messageFactory = messageFactory\n\n\n    def receivedHeader(self, helo, origin, recipients):\n        return None\n\n\n    def validateFrom(self, helo, origin):\n        return origin\n\n\n    def validateTo(self, user):\n        return lambda: self._messageFactory(user)\n\n\n\nclass DummyRealm:\n    def requestAvatar(self, avatarId, mind, *interfaces):\n        return smtp.IMessageDelivery, SimpleDelivery(None), lambda: None\n\n\n\nclass AuthTests(unittest.TestCase, LoopbackMixin):\n    def test_crammd5Auth(self):\n        \"\"\"\n        L{ESMTPClient} can authenticate using the I{CRAM-MD5} SASL mechanism.\n\n        @see: U{http://tools.ietf.org/html/rfc2195}\n        \"\"\"\n        realm = DummyRealm()\n        p = cred.portal.Portal(realm)\n        p.registerChecker(DummyChecker())\n\n        server = DummyESMTP({b'CRAM-MD5': cred.credentials.CramMD5Credentials})\n        server.portal = p\n        client = MyESMTPClient(b'testpassword')\n\n        cAuth = smtp.CramMD5ClientAuthenticator(b'testuser')\n        client.registerAuthenticator(cAuth)\n\n        d = self.loopback(server, client)\n        d.addCallback(lambda x: self.assertEqual(server.authenticated, 1))\n        return d\n\n\n    def test_loginAuth(self):\n        \"\"\"\n        L{ESMTPClient} can authenticate using the I{LOGIN} SASL mechanism.\n\n        @see: U{http://sepp.oetiker.ch/sasl-2.1.19-ds/draft-murchison-sasl-login-00.txt}\n        \"\"\"\n        realm = DummyRealm()\n        p = cred.portal.Portal(realm)\n        p.registerChecker(DummyChecker())\n\n        server = DummyESMTP({b'LOGIN': LOGINCredentials})\n        server.portal = p\n        client = MyESMTPClient(b'testpassword')\n\n        cAuth = smtp.LOGINAuthenticator(b'testuser')\n        client.registerAuthenticator(cAuth)\n\n        d = self.loopback(server, client)\n        d.addCallback(lambda x: self.assertTrue(server.authenticated))\n        return d\n\n\n    def test_loginAgainstWeirdServer(self):\n        \"\"\"\n        When communicating with a server which implements the I{LOGIN} SASL\n        mechanism using C{\"Username:\"} as the challenge (rather than C{\"User\n        Name\\\\0\"}), L{ESMTPClient} can still authenticate successfully using\n        the I{LOGIN} mechanism.\n        \"\"\"\n        realm = DummyRealm()\n        p = cred.portal.Portal(realm)\n        p.registerChecker(DummyChecker())\n\n        server = DummyESMTP({b'LOGIN': smtp.LOGINCredentials})\n        server.portal = p\n\n        client = MyESMTPClient(b'testpassword')\n        cAuth = smtp.LOGINAuthenticator(b'testuser')\n        client.registerAuthenticator(cAuth)\n\n        d = self.loopback(server, client)\n        d.addCallback(lambda x: self.assertTrue(server.authenticated))\n        return d\n\n\n\nclass SMTPHelperTests(unittest.TestCase):\n    def testMessageID(self):\n        d = {}\n        for i in range(1000):\n            m = smtp.messageid('testcase')\n            self.assertFalse(m in d)\n            d[m] = None\n\n\n    def testQuoteAddr(self):\n        cases = [\n            [b'user@host.name', b'<user@host.name>'],\n            [b'\"User Name\" <user@host.name>', b'<user@host.name>'],\n            [smtp.Address(b'someguy@someplace'), b'<someguy@someplace>'],\n            [b'', b'<>'],\n            [smtp.Address(b''), b'<>'],\n        ]\n\n        for (c, e) in cases:\n            self.assertEqual(smtp.quoteaddr(c), e)\n\n\n    def testUser(self):\n        u = smtp.User(b'user@host', b'helo.host.name', None, None)\n        self.assertEqual(str(u), 'user@host')\n\n\n    def testXtextEncoding(self):\n        cases = [\n            (u'Hello world', b'Hello+20world'),\n            (u'Hello+world', b'Hello+2Bworld'),\n            (u'\\0\\1\\2\\3\\4\\5', b'+00+01+02+03+04+05'),\n            (u'e=mc2@example.com', b'e+3Dmc2@example.com')\n        ]\n\n        for (case, expected) in cases:\n            self.assertEqual(smtp.xtext_encode(case), (expected, len(case)))\n            self.assertEqual(case.encode('xtext'), expected)\n            self.assertEqual(\n                smtp.xtext_decode(expected), (case, len(expected)))\n            self.assertEqual(expected.decode('xtext'), case)\n\n\n    def test_encodeWithErrors(self):\n        \"\"\"\n        Specifying an error policy to C{unicode.encode} with the\n        I{xtext} codec should produce the same result as not\n        specifying the error policy.\n        \"\"\"\n        text = u'Hello world'\n        self.assertEqual(\n            smtp.xtext_encode(text, 'strict'),\n            (text.encode('xtext'), len(text)))\n        self.assertEqual(\n            text.encode('xtext', 'strict'),\n            text.encode('xtext'))\n\n\n    def test_decodeWithErrors(self):\n        \"\"\"\n        Similar to L{test_encodeWithErrors}, but for C{bytes.decode}.\n        \"\"\"\n        bytes = b'Hello world'\n        self.assertEqual(\n            smtp.xtext_decode(bytes, 'strict'),\n            (bytes.decode('xtext'), len(bytes)))\n        self.assertEqual(\n            bytes.decode('xtext', 'strict'),\n            bytes.decode('xtext'))\n\n\n\nclass NoticeTLSClient(MyESMTPClient):\n    tls = False\n\n\n    def esmtpState_starttls(self, code, resp):\n        MyESMTPClient.esmtpState_starttls(self, code, resp)\n        self.tls = True\n\n\n\nclass TLSTests(unittest.TestCase, LoopbackMixin):\n    if sslSkip is not None:\n        skip = sslSkip\n\n\n    def testTLS(self):\n        clientCTX = ClientTLSContext()\n        serverCTX = ServerTLSContext()\n\n        client = NoticeTLSClient(contextFactory=clientCTX)\n        server = DummyESMTP(contextFactory=serverCTX)\n\n        def check(ignored):\n            self.assertEqual(client.tls, True)\n            self.assertEqual(server.startedTLS, True)\n\n        return self.loopback(server, client).addCallback(check)\n\nif not interfaces.IReactorSSL.providedBy(reactor):\n    for case in (TLSTests,):\n        case.skip = \"Reactor doesn't support SSL\"\n\n\n\nclass EmptyLineTests(unittest.TestCase):\n\n    def test_emptyLineSyntaxError(self):\n        \"\"\"\n        If L{smtp.SMTP} receives an empty line, it responds with a 500 error\n        response code and a message about a syntax error.\n        \"\"\"\n        proto = smtp.SMTP()\n        transport = StringTransport()\n        proto.makeConnection(transport)\n        proto.lineReceived(b'')\n        proto.setTimeout(None)\n\n        out = transport.value().splitlines()\n        self.assertEqual(len(out), 2)\n        self.assertTrue(out[0].startswith(b'220'))\n        self.assertEqual(out[1], b\"500 Error: bad syntax\")\n\n\n\nclass TimeoutTests(unittest.TestCase, LoopbackMixin):\n    \"\"\"\n    Check that SMTP client factories correctly use the timeout.\n    \"\"\"\n\n    def _timeoutTest(self, onDone, clientFactory):\n        \"\"\"\n        Connect the clientFactory, and check the timeout on the request.\n        \"\"\"\n        clock = task.Clock()\n        client = clientFactory.buildProtocol(\n            address.IPv4Address('TCP', 'example.net', 25))\n        client.callLater = clock.callLater\n        t = StringTransport()\n        client.makeConnection(t)\n        t.protocol = client\n        def check(ign):\n            self.assertEqual(clock.seconds(), 0.5)\n        d = self.assertFailure(onDone, smtp.SMTPTimeoutError\n            ).addCallback(check)\n        # The first call should not trigger the timeout\n        clock.advance(0.1)\n        # But this one should\n        clock.advance(0.4)\n        return d\n\n\n    def test_SMTPClientRecipientBytes(self):\n        \"\"\"\n        Test timeout for L{smtp.SMTPSenderFactory}: the response L{Deferred}\n        should be errback with a L{smtp.SMTPTimeoutError}.\n        \"\"\"\n        onDone = defer.Deferred()\n        clientFactory = smtp.SMTPSenderFactory(\n            'source@address', b'recipient@address',\n            BytesIO(b\"Message body\"), onDone,\n            retries=0, timeout=0.5)\n        return self._timeoutTest(onDone, clientFactory)\n\n\n    def test_SMTPClientRecipientUnicode(self):\n        \"\"\"\n        Use a L{unicode} recipient.\n        \"\"\"\n        onDone = defer.Deferred()\n        clientFactory = smtp.SMTPSenderFactory(\n            'source@address', u'recipient@address',\n            BytesIO(b\"Message body\"), onDone,\n            retries=0, timeout=0.5)\n        return self._timeoutTest(onDone, clientFactory)\n\n\n    def test_SMTPClientRecipientList(self):\n        \"\"\"\n        Use a L{list} of recipients.\n        \"\"\"\n        onDone = defer.Deferred()\n        clientFactory = smtp.SMTPSenderFactory(\n            'source@address', (u'recipient1@address', b'recipient2@address'),\n            BytesIO(b\"Message body\"), onDone,\n            retries=0, timeout=0.5)\n        return self._timeoutTest(onDone, clientFactory)\n\n\n    def test_ESMTPClient(self):\n        \"\"\"\n        Test timeout for L{smtp.ESMTPSenderFactory}: the response L{Deferred}\n        should be errback with a L{smtp.SMTPTimeoutError}.\n        \"\"\"\n        onDone = defer.Deferred()\n        clientFactory = smtp.ESMTPSenderFactory(\n            'username', 'password',\n            'source@address', 'recipient@address',\n            BytesIO(b\"Message body\"), onDone,\n            retries=0, timeout=0.5)\n        return self._timeoutTest(onDone, clientFactory)\n\n\n    def test_resetTimeoutWhileSending(self):\n        \"\"\"\n        The timeout is not allowed to expire after the server has accepted a\n        DATA command and the client is actively sending data to it.\n        \"\"\"\n        class SlowFile:\n            \"\"\"\n            A file-like which returns one byte from each read call until the\n            specified number of bytes have been returned.\n            \"\"\"\n            def __init__(self, size):\n                self._size = size\n\n            def read(self, max=None):\n                if self._size:\n                    self._size -= 1\n                    return b'x'\n                return b''\n\n        failed = []\n        onDone = defer.Deferred()\n        onDone.addErrback(failed.append)\n        clientFactory = smtp.SMTPSenderFactory(\n            'source@address', 'recipient@address',\n            SlowFile(1), onDone, retries=0, timeout=3)\n        clientFactory.domain = b\"example.org\"\n        clock = task.Clock()\n        client = clientFactory.buildProtocol(\n            address.IPv4Address('TCP', 'example.net', 25))\n        client.callLater = clock.callLater\n        transport = StringTransport()\n        client.makeConnection(transport)\n\n        client.dataReceived(\n            b\"220 Ok\\r\\n\" # Greet the client\n            b\"250 Ok\\r\\n\" # Respond to HELO\n            b\"250 Ok\\r\\n\" # Respond to MAIL FROM\n            b\"250 Ok\\r\\n\" # Respond to RCPT TO\n            b\"354 Ok\\r\\n\" # Respond to DATA\n            )\n\n        # Now the client is producing data to the server.  Any time\n        # resumeProducing is called on the producer, the timeout should be\n        # extended.  First, a sanity check.  This test is only written to\n        # handle pull producers.\n        self.assertNotIdentical(transport.producer, None)\n        self.assertFalse(transport.streaming)\n\n        # Now, allow 2 seconds (1 less than the timeout of 3 seconds) to\n        # elapse.\n        clock.advance(2)\n\n        # The timeout has not expired, so the failure should not have happened.\n        self.assertEqual(failed, [])\n\n        # Let some bytes be produced, extending the timeout.  Then advance the\n        # clock some more and verify that the timeout still hasn't happened.\n        transport.producer.resumeProducing()\n        clock.advance(2)\n        self.assertEqual(failed, [])\n\n        # The file has been completely produced - the next resume producing\n        # finishes the upload, successfully.\n        transport.producer.resumeProducing()\n        client.dataReceived(b\"250 Ok\\r\\n\")\n        self.assertEqual(failed, [])\n\n        # Verify that the client actually did send the things expected.\n        self.assertEqual(\n            transport.value(),\n            b\"HELO example.org\\r\\n\"\n            b\"MAIL FROM:<source@address>\\r\\n\"\n            b\"RCPT TO:<recipient@address>\\r\\n\"\n            b\"DATA\\r\\n\"\n            b\"x\\r\\n\"\n            b\".\\r\\n\"\n            # This RSET is just an implementation detail.  It's nice, but this\n            # test doesn't really care about it.\n            b\"RSET\\r\\n\")\n\n\n\nclass MultipleDeliveryFactorySMTPServerFactory(protocol.ServerFactory):\n    \"\"\"\n    L{MultipleDeliveryFactorySMTPServerFactory} creates SMTP server protocol\n    instances with message delivery factory objects supplied to it.  Each\n    factory is used for one connection and then discarded.  Factories are used\n    in the order they are supplied.\n    \"\"\"\n    def __init__(self, messageFactories):\n        self._messageFactories = messageFactories\n\n\n    def buildProtocol(self, addr):\n        p = protocol.ServerFactory.buildProtocol(self, addr)\n        p.delivery = SimpleDelivery(self._messageFactories.pop(0))\n        return p\n\n\n\nclass SMTPSenderFactoryTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{smtp.SMTPSenderFactory}.\n    \"\"\"\n    def test_removeCurrentProtocolWhenClientConnectionLost(self):\n        \"\"\"\n        L{smtp.SMTPSenderFactory} removes the current protocol when the client\n        connection is lost.\n        \"\"\"\n        reactor = MemoryReactor()\n        sentDeferred = defer.Deferred()\n        clientFactory = smtp.SMTPSenderFactory(\n            \"source@address\", \"recipient@address\",\n            BytesIO(b\"message\"), sentDeferred)\n        connector = reactor.connectTCP(\"localhost\", 25, clientFactory)\n        clientFactory.buildProtocol(None)\n        clientFactory.clientConnectionLost(connector,\n                                           error.ConnectionDone(\"Bye.\"))\n        self.assertEqual(clientFactory.currentProtocol, None)\n\n\n    def test_removeCurrentProtocolWhenClientConnectionFailed(self):\n        \"\"\"\n        L{smtp.SMTPSenderFactory} removes the current protocol when the client\n        connection is failed.\n        \"\"\"\n        reactor = MemoryReactor()\n        sentDeferred = defer.Deferred()\n        clientFactory = smtp.SMTPSenderFactory(\n            \"source@address\", \"recipient@address\",\n            BytesIO(b\"message\"), sentDeferred)\n        connector = reactor.connectTCP(\"localhost\", 25, clientFactory)\n        clientFactory.buildProtocol(None)\n        clientFactory.clientConnectionFailed(connector,\n                                             error.ConnectionDone(\"Bye.\"))\n        self.assertEqual(clientFactory.currentProtocol, None)\n\n\n\nclass SMTPSenderFactoryRetryTests(unittest.TestCase):\n    \"\"\"\n    Tests for the retry behavior of L{smtp.SMTPSenderFactory}.\n    \"\"\"\n    def test_retryAfterDisconnect(self):\n        \"\"\"\n        If the protocol created by L{SMTPSenderFactory} loses its connection\n        before receiving confirmation of message delivery, it reconnects and\n        tries to deliver the message again.\n        \"\"\"\n        recipient = b'alice'\n        message = b\"some message text\"\n        domain = DummyDomain([recipient])\n\n        class CleanSMTP(smtp.SMTP):\n            \"\"\"\n            An SMTP subclass which ensures that its transport will be\n            disconnected before the test ends.\n            \"\"\"\n            def makeConnection(innerSelf, transport):\n                self.addCleanup(transport.loseConnection)\n                smtp.SMTP.makeConnection(innerSelf, transport)\n\n        # Create a server which will fail the first message deliver attempt to\n        # it with a 500 and a disconnect, but which will accept a message\n        # delivered over the 2nd connection to it.\n        serverFactory = MultipleDeliveryFactorySMTPServerFactory([\n                BrokenMessage,\n                lambda user: DummyMessage(domain, user)])\n        serverFactory.protocol = CleanSMTP\n        serverPort = reactor.listenTCP(0, serverFactory, interface='127.0.0.1')\n        serverHost = serverPort.getHost()\n        self.addCleanup(serverPort.stopListening)\n\n        # Set up a client to try to deliver a message to the above created\n        # server.\n        sentDeferred = defer.Deferred()\n        clientFactory = smtp.SMTPSenderFactory(\n            b\"bob@example.org\", recipient + b\"@example.com\",\n            BytesIO(message), sentDeferred)\n        clientFactory.domain = b\"example.org\"\n        clientConnector = reactor.connectTCP(\n            serverHost.host, serverHost.port, clientFactory)\n        self.addCleanup(clientConnector.disconnect)\n\n        def cbSent(ignored):\n            \"\"\"\n            Verify that the message was successfully delivered and flush the\n            error which caused the first attempt to fail.\n            \"\"\"\n            self.assertEqual(\n                domain.messages,\n                {recipient: [b\"\\n\" + message + b\"\\n\"]})\n            # Flush the RuntimeError that BrokenMessage caused to be logged.\n            self.assertEqual(len(self.flushLoggedErrors(RuntimeError)), 1)\n        sentDeferred.addCallback(cbSent)\n        return sentDeferred\n\n\n\n@implementer(IRealm)\nclass SingletonRealm(object):\n    \"\"\"\n    Trivial realm implementation which is constructed with an interface and an\n    avatar and returns that avatar when asked for that interface.\n    \"\"\"\n    def __init__(self, interface, avatar):\n        self.interface = interface\n        self.avatar = avatar\n\n\n    def requestAvatar(self, avatarId, mind, *interfaces):\n        for iface in interfaces:\n            if iface is self.interface:\n                return iface, self.avatar, lambda: None\n\n\n\nclass NotImplementedDelivery(object):\n    \"\"\"\n    Non-implementation of L{smtp.IMessageDelivery} which only has methods which\n    raise L{NotImplementedError}.  Subclassed by various tests to provide the\n    particular behavior being tested.\n    \"\"\"\n    def validateFrom(self, helo, origin):\n        raise NotImplementedError(\"This oughtn't be called in the course of this test.\")\n\n\n    def validateTo(self, user):\n        raise NotImplementedError(\"This oughtn't be called in the course of this test.\")\n\n\n    def receivedHeader(self, helo, origin, recipients):\n        raise NotImplementedError(\"This oughtn't be called in the course of this test.\")\n\n\n\nclass SMTPServerTests(unittest.TestCase):\n    \"\"\"\n    Test various behaviors of L{twisted.mail.smtp.SMTP} and\n    L{twisted.mail.smtp.ESMTP}.\n    \"\"\"\n    def testSMTPGreetingHost(self, serverClass=smtp.SMTP):\n        \"\"\"\n        Test that the specified hostname shows up in the SMTP server's\n        greeting.\n        \"\"\"\n        s = serverClass()\n        s.host = b\"example.com\"\n        t = StringTransport()\n        s.makeConnection(t)\n        s.connectionLost(error.ConnectionDone())\n        self.assertIn(b\"example.com\", t.value())\n\n\n    def testSMTPGreetingNotExtended(self):\n        \"\"\"\n        Test that the string \"ESMTP\" does not appear in the SMTP server's\n        greeting since that string strongly suggests the presence of support\n        for various SMTP extensions which are not supported by L{smtp.SMTP}.\n        \"\"\"\n        s = smtp.SMTP()\n        t = StringTransport()\n        s.makeConnection(t)\n        s.connectionLost(error.ConnectionDone())\n        self.assertNotIn(b\"ESMTP\", t.value())\n\n\n    def testESMTPGreetingHost(self):\n        \"\"\"\n        Similar to testSMTPGreetingHost, but for the L{smtp.ESMTP} class.\n        \"\"\"\n        self.testSMTPGreetingHost(smtp.ESMTP)\n\n\n    def testESMTPGreetingExtended(self):\n        \"\"\"\n        Test that the string \"ESMTP\" does appear in the ESMTP server's\n        greeting since L{smtp.ESMTP} does support the SMTP extensions which\n        that advertises to the client.\n        \"\"\"\n        s = smtp.ESMTP()\n        t = StringTransport()\n        s.makeConnection(t)\n        s.connectionLost(error.ConnectionDone())\n        self.assertIn(b\"ESMTP\", t.value())\n\n\n    def test_SMTPUnknownCommand(self):\n        \"\"\"\n        Sending an unimplemented command is responded to with a 500.\n        \"\"\"\n        s = smtp.SMTP()\n        t = StringTransport()\n        s.makeConnection(t)\n        s.lineReceived(b\"DOAGOODTHING\")\n        s.connectionLost(error.ConnectionDone())\n        self.assertIn(b\"500 Command not implemented\", t.value())\n\n\n    def test_acceptSenderAddress(self):\n        \"\"\"\n        Test that a C{MAIL FROM} command with an acceptable address is\n        responded to with the correct success code.\n        \"\"\"\n        class AcceptanceDelivery(NotImplementedDelivery):\n            \"\"\"\n            Delivery object which accepts all senders as valid.\n            \"\"\"\n            def validateFrom(self, helo, origin):\n                return origin\n\n        realm = SingletonRealm(smtp.IMessageDelivery, AcceptanceDelivery())\n        portal = Portal(realm, [AllowAnonymousAccess()])\n        proto = smtp.SMTP()\n        proto.portal = portal\n        trans = StringTransport()\n        proto.makeConnection(trans)\n\n        # Deal with the necessary preliminaries\n        proto.dataReceived(b'HELO example.com\\r\\n')\n        trans.clear()\n\n        # Try to specify our sender address\n        proto.dataReceived(b'MAIL FROM:<alice@example.com>\\r\\n')\n\n        # Clean up the protocol before doing anything that might raise an\n        # exception.\n        proto.connectionLost(error.ConnectionLost())\n\n        # Make sure that we received exactly the correct response\n        self.assertEqual(\n            trans.value(),\n            b'250 Sender address accepted\\r\\n')\n\n\n    def test_deliveryRejectedSenderAddress(self):\n        \"\"\"\n        Test that a C{MAIL FROM} command with an address rejected by a\n        L{smtp.IMessageDelivery} instance is responded to with the correct\n        error code.\n        \"\"\"\n        class RejectionDelivery(NotImplementedDelivery):\n            \"\"\"\n            Delivery object which rejects all senders as invalid.\n            \"\"\"\n            def validateFrom(self, helo, origin):\n                raise smtp.SMTPBadSender(origin)\n\n        realm = SingletonRealm(smtp.IMessageDelivery, RejectionDelivery())\n        portal = Portal(realm, [AllowAnonymousAccess()])\n        proto = smtp.SMTP()\n        proto.portal = portal\n        trans = StringTransport()\n        proto.makeConnection(trans)\n\n        # Deal with the necessary preliminaries\n        proto.dataReceived(b'HELO example.com\\r\\n')\n        trans.clear()\n\n        # Try to specify our sender address\n        proto.dataReceived(b'MAIL FROM:<alice@example.com>\\r\\n')\n\n        # Clean up the protocol before doing anything that might raise an\n        # exception.\n        proto.connectionLost(error.ConnectionLost())\n\n        # Make sure that we received exactly the correct response\n        self.assertEqual(\n            trans.value(),\n            b'550 Cannot receive from specified address '\n            b'<alice@example.com>: Sender not acceptable\\r\\n')\n\n\n    @implementer(ICredentialsChecker)\n    def test_portalRejectedSenderAddress(self):\n        \"\"\"\n        Test that a C{MAIL FROM} command with an address rejected by an\n        L{smtp.SMTP} instance's portal is responded to with the correct error\n        code.\n        \"\"\"\n        class DisallowAnonymousAccess(object):\n            \"\"\"\n            Checker for L{IAnonymous} which rejects authentication attempts.\n            \"\"\"\n            credentialInterfaces = (IAnonymous,)\n\n            def requestAvatarId(self, credentials):\n                return defer.fail(UnauthorizedLogin())\n\n        realm = SingletonRealm(smtp.IMessageDelivery, NotImplementedDelivery())\n        portal = Portal(realm, [DisallowAnonymousAccess()])\n        proto = smtp.SMTP()\n        proto.portal = portal\n        trans = StringTransport()\n        proto.makeConnection(trans)\n\n        # Deal with the necessary preliminaries\n        proto.dataReceived(b'HELO example.com\\r\\n')\n        trans.clear()\n\n        # Try to specify our sender address\n        proto.dataReceived(b'MAIL FROM:<alice@example.com>\\r\\n')\n\n        # Clean up the protocol before doing anything that might raise an\n        # exception.\n        proto.connectionLost(error.ConnectionLost())\n\n        # Make sure that we received exactly the correct response\n        self.assertEqual(\n            trans.value(),\n            b'550 Cannot receive from specified address '\n            b'<alice@example.com>: Sender not acceptable\\r\\n')\n\n\n    def test_portalRejectedAnonymousSender(self):\n        \"\"\"\n        Test that a C{MAIL FROM} command issued without first authenticating\n        when a portal has been configured to disallow anonymous logins is\n        responded to with the correct error code.\n        \"\"\"\n        realm = SingletonRealm(smtp.IMessageDelivery, NotImplementedDelivery())\n        portal = Portal(realm, [])\n        proto = smtp.SMTP()\n        proto.portal = portal\n        trans = StringTransport()\n        proto.makeConnection(trans)\n\n        # Deal with the necessary preliminaries\n        proto.dataReceived(b'HELO example.com\\r\\n')\n        trans.clear()\n\n        # Try to specify our sender address\n        proto.dataReceived(b'MAIL FROM:<alice@example.com>\\r\\n')\n\n        # Clean up the protocol before doing anything that might raise an\n        # exception.\n        proto.connectionLost(error.ConnectionLost())\n\n        # Make sure that we received exactly the correct response\n        self.assertEqual(\n            trans.value(),\n            b'550 Cannot receive from specified address '\n            b'<alice@example.com>: Unauthenticated senders not allowed\\r\\n')\n\n\n\nclass ESMTPAuthenticationTests(unittest.TestCase):\n    def assertServerResponse(self, bytes, response):\n        \"\"\"\n        Assert that when the given bytes are delivered to the ESMTP server\n        instance, it responds with the indicated lines.\n\n        @type bytes: str\n        @type response: list of str\n        \"\"\"\n        self.transport.clear()\n        self.server.dataReceived(bytes)\n        self.assertEqual(\n            response,\n            self.transport.value().splitlines())\n\n\n    def assertServerAuthenticated(self, loginArgs, username=b\"username\",\n                                  password=b\"password\"):\n        \"\"\"\n        Assert that a login attempt has been made, that the credentials and\n        interfaces passed to it are correct, and that when the login request\n        is satisfied, a successful response is sent by the ESMTP server\n        instance.\n\n        @param loginArgs: A C{list} previously passed to L{portalFactory}.\n        @param username: The login user.\n        @param password: The login password.\n        \"\"\"\n        d, credentials, mind, interfaces = loginArgs.pop()\n        self.assertEqual(loginArgs, [])\n        self.assertTrue(twisted.cred.credentials.IUsernamePassword.providedBy(credentials))\n        self.assertEqual(credentials.username, username)\n        self.assertTrue(credentials.checkPassword(password))\n        self.assertIn(smtp.IMessageDeliveryFactory, interfaces)\n        self.assertIn(smtp.IMessageDelivery, interfaces)\n        d.callback((smtp.IMessageDeliveryFactory, None, lambda: None))\n\n        self.assertEqual(\n            [b\"235 Authentication successful.\"],\n            self.transport.value().splitlines())\n\n\n    def setUp(self):\n        \"\"\"\n        Create an ESMTP instance attached to a StringTransport.\n        \"\"\"\n        self.server = smtp.ESMTP({\n                b'LOGIN': LOGINCredentials})\n        self.server.host = b'localhost'\n        self.transport = StringTransport(\n            peerAddress=address.IPv4Address('TCP', '127.0.0.1', 12345))\n        self.server.makeConnection(self.transport)\n\n\n    def tearDown(self):\n        \"\"\"\n        Disconnect the ESMTP instance to clean up its timeout DelayedCall.\n        \"\"\"\n        self.server.connectionLost(error.ConnectionDone())\n\n\n    def portalFactory(self, loginList):\n        class DummyPortal:\n            def login(self, credentials, mind, *interfaces):\n                d = defer.Deferred()\n                loginList.append((d, credentials, mind, interfaces))\n                return d\n        return DummyPortal()\n\n\n    def test_authenticationCapabilityAdvertised(self):\n        \"\"\"\n        Test that AUTH is advertised to clients which issue an EHLO command.\n        \"\"\"\n        self.transport.clear()\n        self.server.dataReceived(b'EHLO\\r\\n')\n        responseLines = self.transport.value().splitlines()\n        self.assertEqual(\n            responseLines[0],\n            b\"250-localhost Hello 127.0.0.1, nice to meet you\")\n        self.assertEqual(\n            responseLines[1],\n            b\"250 AUTH LOGIN\")\n        self.assertEqual(len(responseLines), 2)\n\n\n    def test_plainAuthentication(self):\n        \"\"\"\n        Test that the LOGIN authentication mechanism can be used\n        \"\"\"\n        loginArgs = []\n        self.server.portal = self.portalFactory(loginArgs)\n\n        self.server.dataReceived(b'EHLO\\r\\n')\n        self.transport.clear()\n\n        self.assertServerResponse(\n            b'AUTH LOGIN\\r\\n',\n            [b\"334 \" + base64.b64encode(b\"User Name\\0\").strip()])\n\n        self.assertServerResponse(\n            base64.b64encode(b'username') + b'\\r\\n',\n            [b\"334 \" + base64.b64encode(b\"Password\\0\").strip()])\n\n        self.assertServerResponse(\n            base64.b64encode(b'password').strip() + b'\\r\\n',\n            [])\n\n        self.assertServerAuthenticated(loginArgs)\n\n\n    def test_plainAuthenticationEmptyPassword(self):\n        \"\"\"\n        Test that giving an empty password for plain auth succeeds.\n        \"\"\"\n        loginArgs = []\n        self.server.portal = self.portalFactory(loginArgs)\n\n        self.server.dataReceived(b'EHLO\\r\\n')\n        self.transport.clear()\n\n        self.assertServerResponse(\n            b'AUTH LOGIN\\r\\n',\n            [b\"334 \" + base64.b64encode(b\"User Name\\0\").strip()])\n\n        self.assertServerResponse(\n            base64.b64encode(b'username') + b'\\r\\n',\n            [b\"334 \" + base64.b64encode(b\"Password\\0\").strip()])\n\n        self.assertServerResponse(b'\\r\\n', [])\n        self.assertServerAuthenticated(loginArgs, password=b'')\n\n\n    def test_plainAuthenticationInitialResponse(self):\n        \"\"\"\n        The response to the first challenge may be included on the AUTH command\n        line.  Test that this is also supported.\n        \"\"\"\n        loginArgs = []\n        self.server.portal = self.portalFactory(loginArgs)\n\n        self.server.dataReceived(b'EHLO\\r\\n')\n        self.transport.clear()\n\n        self.assertServerResponse(\n            b'AUTH LOGIN ' + base64.b64encode(b\"username\").strip() + b'\\r\\n',\n            [b\"334 \" + base64.b64encode(b\"Password\\0\").strip()])\n\n        self.assertServerResponse(\n            base64.b64encode(b'password').strip() + b'\\r\\n',\n            [])\n\n        self.assertServerAuthenticated(loginArgs)\n\n\n    def test_abortAuthentication(self):\n        \"\"\"\n        Test that a challenge/response sequence can be aborted by the client.\n        \"\"\"\n        loginArgs = []\n        self.server.portal = self.portalFactory(loginArgs)\n\n        self.server.dataReceived(b'EHLO\\r\\n')\n        self.server.dataReceived(b'AUTH LOGIN\\r\\n')\n\n        self.assertServerResponse(\n            b'*\\r\\n',\n            [b'501 Authentication aborted'])\n\n\n    def test_invalidBase64EncodedResponse(self):\n        \"\"\"\n        Test that a response which is not properly Base64 encoded results in\n        the appropriate error code.\n        \"\"\"\n        loginArgs = []\n        self.server.portal = self.portalFactory(loginArgs)\n\n        self.server.dataReceived(b'EHLO\\r\\n')\n        self.server.dataReceived(b'AUTH LOGIN\\r\\n')\n\n        self.assertServerResponse(\n            b'x\\r\\n',\n            [b'501 Syntax error in parameters or arguments'])\n\n        self.assertEqual(loginArgs, [])\n\n\n    def test_invalidBase64EncodedInitialResponse(self):\n        \"\"\"\n        Like L{test_invalidBase64EncodedResponse} but for the case of an\n        initial response included with the C{AUTH} command.\n        \"\"\"\n        loginArgs = []\n        self.server.portal = self.portalFactory(loginArgs)\n\n        self.server.dataReceived(b'EHLO\\r\\n')\n        self.assertServerResponse(\n            b'AUTH LOGIN x\\r\\n',\n            [b'501 Syntax error in parameters or arguments'])\n\n        self.assertEqual(loginArgs, [])\n\n\n    def test_unexpectedLoginFailure(self):\n        \"\"\"\n        If the L{Deferred} returned by L{Portal.login} fires with an\n        exception of any type other than L{UnauthorizedLogin}, the exception\n        is logged and the client is informed that the authentication attempt\n        has failed.\n        \"\"\"\n        loginArgs = []\n        self.server.portal = self.portalFactory(loginArgs)\n\n        self.server.dataReceived(b'EHLO\\r\\n')\n        self.transport.clear()\n\n        self.assertServerResponse(\n            b'AUTH LOGIN ' + base64.b64encode(b'username').strip() + b'\\r\\n',\n            [b'334 ' + base64.b64encode(b'Password\\0').strip()])\n        self.assertServerResponse(\n            base64.b64encode(b'password').strip() + b'\\r\\n',\n            [])\n\n        d, credentials, mind, interfaces = loginArgs.pop()\n        d.errback(RuntimeError(\"Something wrong with the server\"))\n\n        self.assertEqual(\n            b'451 Requested action aborted: local error in processing\\r\\n',\n            self.transport.value())\n\n        self.assertEqual(len(self.flushLoggedErrors(RuntimeError)), 1)\n\n\n\nclass SMTPClientErrorTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{smtp.SMTPClientError}.\n    \"\"\"\n    def test_str(self):\n        \"\"\"\n        The string representation of a L{SMTPClientError} instance includes\n        the response code and response string.\n        \"\"\"\n        err = smtp.SMTPClientError(123, \"some text\")\n        self.assertEqual(str(err), \"123 some text\")\n\n\n    def test_strWithNegativeCode(self):\n        \"\"\"\n        If the response code supplied to L{SMTPClientError} is negative, it\n        is excluded from the string representation.\n        \"\"\"\n        err = smtp.SMTPClientError(-1, b\"foo bar\")\n        self.assertEqual(str(err), \"foo bar\")\n\n\n    def test_strWithLog(self):\n        \"\"\"\n        If a line log is supplied to L{SMTPClientError}, its contents are\n        included in the string representation of the exception instance.\n        \"\"\"\n        log = LineLog(10)\n        log.append(b\"testlog\")\n        log.append(b\"secondline\")\n        err = smtp.SMTPClientError(100, \"test error\", log=log.str())\n        self.assertEqual(\n            str(err),\n            \"100 test error\\n\"\n            \"testlog\\n\"\n            \"secondline\\n\")\n\n\n\nclass SenderMixinSentMailTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{smtp.SenderMixin.sentMail}, used in particular by\n    L{smtp.SMTPSenderFactory} and L{smtp.ESMTPSenderFactory}.\n    \"\"\"\n    def test_onlyLogFailedAddresses(self):\n        \"\"\"\n        L{smtp.SenderMixin.sentMail} adds only the addresses with failing\n        SMTP response codes to the log passed to the factory's errback.\n        \"\"\"\n        onDone = self.assertFailure(defer.Deferred(), smtp.SMTPDeliveryError)\n        onDone.addCallback(lambda e: self.assertEqual(\n                e.log, b\"bob@example.com: 199 Error in sending.\\n\"))\n\n        clientFactory = smtp.SMTPSenderFactory(\n            'source@address', 'recipient@address',\n            BytesIO(b\"Message body\"), onDone,\n            retries=0, timeout=0.5)\n\n        client = clientFactory.buildProtocol(\n            address.IPv4Address('TCP', 'example.net', 25))\n\n        addresses = [(b\"alice@example.com\", 200, b\"No errors here!\"),\n                     (b\"bob@example.com\", 199, b\"Error in sending.\")]\n        client.sentMail(199, b\"Test response\", 1, addresses, client.log)\n\n        return onDone\n\n\n\nclass ESMTPDowngradeTestCase(unittest.TestCase):\n    \"\"\"\n    Tests for the ESMTP -> SMTP downgrade functionality in L{smtp.ESMTPClient}.\n    \"\"\"\n    def setUp(self):\n        self.clientProtocol = smtp.ESMTPClient(\n            b\"testpassword\", None, b\"testuser\")\n\n\n    def test_requireHELOFallbackOperates(self):\n        \"\"\"\n        If both authentication and transport security are not required, and it\n        is asked for, it will fall back to allowing HELO.\n        \"\"\"\n        transport = StringTransport()\n        self.clientProtocol.requireAuthentication = False\n        self.clientProtocol.requireTransportSecurity = False\n        self.clientProtocol.heloFallback = True\n        self.clientProtocol.makeConnection(transport)\n\n        self.clientProtocol.dataReceived(b\"220 localhost\\r\\n\")\n        transport.clear()\n        self.clientProtocol.dataReceived(b\"500 not an esmtp server\\r\\n\")\n        self.assertEqual(b\"HELO testuser\\r\\n\", transport.value())\n\n\n    def test_requireAuthFailsHELOFallback(self):\n        \"\"\"\n        If authentication is required, and HELO fallback is on, HELO fallback\n        must not be honoured, as authentication requires EHLO to succeed.\n        \"\"\"\n        transport = StringTransport()\n        self.clientProtocol.requireAuthentication = True\n        self.clientProtocol.requireTransportSecurity = False\n        self.clientProtocol.heloFallback = True\n        self.clientProtocol.makeConnection(transport)\n\n        self.clientProtocol.dataReceived(b\"220 localhost\\r\\n\")\n        transport.clear()\n        self.clientProtocol.dataReceived(b\"500 not an esmtp server\\r\\n\")\n        self.assertEqual(b\"QUIT\\r\\n\", transport.value())\n\n\n    def test_requireTLSFailsHELOFallback(self):\n        \"\"\"\n        If TLS is required and the connection is insecure, HELO fallback must\n        not be honoured, as STARTTLS requires EHLO to succeed.\n        \"\"\"\n        transport = StringTransport()\n        self.clientProtocol.requireAuthentication = False\n        self.clientProtocol.requireTransportSecurity = True\n        self.clientProtocol.heloFallback = True\n        self.clientProtocol.makeConnection(transport)\n\n        self.clientProtocol.dataReceived(b\"220 localhost\\r\\n\")\n        transport.clear()\n        self.clientProtocol.dataReceived(b\"500 not an esmtp server\\r\\n\")\n        self.assertEqual(b\"QUIT\\r\\n\", transport.value())\n\n\n    def test_requireTLSAndHELOFallbackSucceedsIfOverTLS(self):\n        \"\"\"\n        If TLS is provided at the transport level, we can honour the HELO\n        fallback if we're set to require TLS.\n        \"\"\"\n        transport = StringTransport()\n        directlyProvides(transport, interfaces.ISSLTransport)\n        self.clientProtocol.requireAuthentication = False\n        self.clientProtocol.requireTransportSecurity = True\n        self.clientProtocol.heloFallback = True\n        self.clientProtocol.makeConnection(transport)\n\n        self.clientProtocol.dataReceived(b\"220 localhost\\r\\n\")\n        transport.clear()\n        self.clientProtocol.dataReceived(b\"500 not an esmtp server\\r\\n\")\n        self.assertEqual(b\"HELO testuser\\r\\n\", transport.value())\n\n\n\nclass SSLTestCase(unittest.TestCase):\n    \"\"\"\n    Tests for the TLS negotiation done by L{smtp.ESMTPClient}.\n    \"\"\"\n    if sslSkip is not None:\n        skip = sslSkip\n\n    SERVER_GREETING = b\"220 localhost NO UCE NO UBE NO RELAY PROBES ESMTP\\r\\n\"\n    EHLO_RESPONSE = b\"250-localhost Hello 127.0.0.1, nice to meet you\\r\\n\"\n\n    def setUp(self):\n        self.clientProtocol = smtp.ESMTPClient(\n            b\"testpassword\", ClientTLSContext(), b\"testuser\")\n        self.clientProtocol.requireTransportSecurity = True\n        self.clientProtocol.getMailFrom = lambda: \"test@example.org\"\n\n\n    def _requireTransportSecurityOverSSLTest(self, capabilities):\n        \"\"\"\n        Verify that when L{smtp.ESMTPClient} connects to a server over a\n        transport providing L{ISSLTransport}, C{requireTransportSecurity} is\n        C{True}, and it is presented with the given capabilities, it will try\n        to send its mail and not first attempt to negotiate TLS using the\n        I{STARTTLS} protocol action.\n\n        @param capabilities: Bytes to include in the test server's capability\n            response.  These must be formatted exactly as required by the\n            protocol, including a line which ends the capability response.\n        @type param: L{bytes}\n\n        @raise: C{self.failureException} if the behavior of\n            C{self.clientProtocol} is not as described.\n        \"\"\"\n        transport = StringTransport()\n        directlyProvides(transport, interfaces.ISSLTransport)\n        self.clientProtocol.makeConnection(transport)\n\n        # Get the handshake out of the way\n        self.clientProtocol.dataReceived(self.SERVER_GREETING)\n        transport.clear()\n\n        # Tell the client about the server's capabilities\n        self.clientProtocol.dataReceived(self.EHLO_RESPONSE + capabilities)\n\n        # The client should now try to send a message - without first trying to\n        # negotiate TLS, since the transport is already secure.\n        self.assertEqual(\n            b\"MAIL FROM:<test@example.org>\\r\\n\",\n            transport.value())\n\n\n    def test_requireTransportSecurityOverSSL(self):\n        \"\"\"\n        When C{requireTransportSecurity} is C{True} and the client is connected\n        over an SSL transport, mail may be delivered.\n        \"\"\"\n        self._requireTransportSecurityOverSSLTest(b\"250 AUTH LOGIN\\r\\n\")\n\n\n    def test_requireTransportSecurityTLSOffered(self):\n        \"\"\"\n        When C{requireTransportSecurity} is C{True} and the client is connected\n        over a non-SSL transport, if the server offers the I{STARTTLS}\n        extension, it is used before mail is delivered.\n        \"\"\"\n        transport = StringTransport()\n        self.clientProtocol.makeConnection(transport)\n\n        # Get the handshake out of the way\n        self.clientProtocol.dataReceived(self.SERVER_GREETING)\n        transport.clear()\n\n        # Tell the client about the server's capabilities - including STARTTLS\n        self.clientProtocol.dataReceived(\n            self.EHLO_RESPONSE +\n            b\"250-AUTH LOGIN\\r\\n\"\n            b\"250 STARTTLS\\r\\n\")\n\n        # The client should try to start TLS before sending the message.\n        self.assertEqual(b\"STARTTLS\\r\\n\", transport.value())\n\n\n    def test_requireTransportSecurityTLSOfferedOverSSL(self):\n        \"\"\"\n        When C{requireTransportSecurity} is C{True} and the client is connected\n        over an SSL transport, if the server offers the I{STARTTLS}\n        extension, it is not used before mail is delivered.\n        \"\"\"\n        self._requireTransportSecurityOverSSLTest(\n            b\"250-AUTH LOGIN\\r\\n\"\n            b\"250 STARTTLS\\r\\n\")\n\n\n    def test_requireTransportSecurityTLSNotOffered(self):\n        \"\"\"\n        When C{requireTransportSecurity} is C{True} and the client is connected\n        over a non-SSL transport, if the server does not offer the I{STARTTLS}\n        extension, mail is not delivered.\n        \"\"\"\n        transport = StringTransport()\n        self.clientProtocol.makeConnection(transport)\n\n        # Get the handshake out of the way\n        self.clientProtocol.dataReceived(self.SERVER_GREETING)\n        transport.clear()\n\n        # Tell the client about the server's capabilities - excluding STARTTLS\n        self.clientProtocol.dataReceived(\n            self.EHLO_RESPONSE +\n            b\"250 AUTH LOGIN\\r\\n\")\n\n        # The client give up\n        self.assertEqual(b\"QUIT\\r\\n\", transport.value())\n\n\n    def test_esmtpClientTlsModeDeprecationGet(self):\n        \"\"\"\n        L{smtp.ESMTPClient.tlsMode} is deprecated.\n        \"\"\"\n        val = self.clientProtocol.tlsMode\n        del val\n        warningsShown = self.flushWarnings(\n            offendingFunctions=[self.test_esmtpClientTlsModeDeprecationGet])\n        self.assertEqual(len(warningsShown), 1)\n        self.assertIdentical(\n            warningsShown[0]['category'], DeprecationWarning)\n        self.assertEqual(\n            warningsShown[0]['message'],\n            \"tlsMode attribute of twisted.mail.smtp.ESMTPClient \"\n            \"is deprecated since Twisted 13.0\")\n\n\n    def test_esmtpClientTlsModeDeprecationGetAttributeError(self):\n        \"\"\"\n        L{smtp.ESMTPClient.__getattr__} raises an attribute error for other\n        attribute names which do not exist.\n        \"\"\"\n        self.assertRaises(\n            AttributeError, lambda: self.clientProtocol.doesNotExist)\n\n\n    def test_esmtpClientTlsModeDeprecationSet(self):\n        \"\"\"\n        L{smtp.ESMTPClient.tlsMode} is deprecated.\n        \"\"\"\n        self.clientProtocol.tlsMode = False\n        warningsShown = self.flushWarnings(\n            offendingFunctions=[self.test_esmtpClientTlsModeDeprecationSet])\n        self.assertEqual(len(warningsShown), 1)\n        self.assertIdentical(\n            warningsShown[0]['category'], DeprecationWarning)\n        self.assertEqual(\n            warningsShown[0]['message'],\n            \"tlsMode attribute of twisted.mail.smtp.ESMTPClient \"\n            \"is deprecated since Twisted 13.0\")\n\n\n\nclass AbortableStringTransport(StringTransport):\n    \"\"\"\n    A version of L{StringTransport} that supports C{abortConnection}.\n    \"\"\"\n    # This should be replaced by a common version in #6530.\n    aborting = False\n\n\n    def abortConnection(self):\n        \"\"\"\n        A testable version of the C{ITCPTransport.abortConnection} method.\n\n        Since this is a special case of closing the connection,\n        C{loseConnection} is also called.\n        \"\"\"\n        self.aborting = True\n        self.loseConnection()\n\n\n\nclass SendmailTests(unittest.TestCase):\n    \"\"\"\n    Tests for L{twisted.mail.smtp.sendmail}.\n    \"\"\"\n    def test_defaultReactorIsGlobalReactor(self):\n        \"\"\"\n        The default C{reactor} parameter of L{twisted.mail.smtp.sendmail} is\n        L{twisted.internet.reactor}.\n        \"\"\"\n        args, varArgs, keywords, defaults = inspect.getargspec(smtp.sendmail)\n        self.assertEqual(reactor, defaults[2])\n\n\n    def _honorsESMTPArguments(self, username, password):\n        \"\"\"\n        L{twisted.mail.smtp.sendmail} creates the ESMTP factory with the ESMTP\n        arguments.\n        \"\"\"\n        reactor = MemoryReactor()\n        smtp.sendmail(\"localhost\", \"source@address\", \"recipient@address\",\n                      b\"message\", reactor=reactor, username=username,\n                      password=password, requireTransportSecurity=True,\n                      requireAuthentication=True)\n        factory = reactor.tcpClients[0][2]\n        self.assertEqual(factory._requireTransportSecurity, True)\n        self.assertEqual(factory._requireAuthentication, True)\n        self.assertEqual(factory.username, b\"foo\")\n        self.assertEqual(factory.password, b\"bar\")\n\n\n    def test_honorsESMTPArgumentsUnicodeUserPW(self):\n        \"\"\"\n        L{twisted.mail.smtp.sendmail} should accept C{username} and C{password}\n        which are L{unicode}.\n        \"\"\"\n        return self._honorsESMTPArguments(username=u\"foo\", password=u\"bar\")\n\n\n    def test_honorsESMTPArgumentsBytesUserPW(self):\n        \"\"\"\n        L{twisted.mail.smtp.sendmail} should accept C{username} and C{password}\n        which are L{bytes}.\n        \"\"\"\n        return self._honorsESMTPArguments(username=b\"foo\", password=b\"bar\")\n\n\n    def test_messageFilePassthrough(self):\n        \"\"\"\n        L{twisted.mail.smtp.sendmail} will pass through the message untouched\n        if it is a file-like object.\n        \"\"\"\n        reactor = MemoryReactor()\n        messageFile = BytesIO(b\"File!\")\n\n        smtp.sendmail(\"localhost\", \"source@address\", \"recipient@address\",\n                      messageFile, reactor=reactor)\n        factory = reactor.tcpClients[0][2]\n        self.assertIs(factory.file, messageFile)\n\n\n    def test_messageStringMadeFile(self):\n        \"\"\"\n        L{twisted.mail.smtp.sendmail} will turn non-file-like objects\n        (eg. strings) into file-like objects before sending.\n        \"\"\"\n        reactor = MemoryReactor()\n        smtp.sendmail(\"localhost\", \"source@address\", \"recipient@address\",\n                      b\"message\", reactor=reactor)\n        factory = reactor.tcpClients[0][2]\n        messageFile = factory.file\n        messageFile.seek(0)\n        self.assertEqual(messageFile.read(), b\"message\")\n\n\n    def test_senderDomainName(self):\n        \"\"\"\n        L{twisted.mail.smtp.sendmail} passes through the sender domain name, if\n        provided.\n        \"\"\"\n        reactor = MemoryReactor()\n        smtp.sendmail(\"localhost\", \"source@address\", \"recipient@address\",\n                      b\"message\", reactor=reactor, senderDomainName=\"foo\")\n        factory = reactor.tcpClients[0][2]\n        self.assertEqual(factory.domain, b\"foo\")\n\n\n    def test_cancelBeforeConnectionMade(self):\n        \"\"\"\n        When a user cancels L{twisted.mail.smtp.sendmail} before the connection\n        is made, the connection is closed by\n        L{twisted.internet.interfaces.IConnector.disconnect}.\n        \"\"\"\n        reactor = MemoryReactor()\n        d = smtp.sendmail(\"localhost\", \"source@address\", \"recipient@address\",\n                          b\"message\", reactor=reactor)\n        d.cancel()\n        self.assertEqual(reactor.connectors[0]._disconnected, True)\n        failure = self.failureResultOf(d)\n        failure.trap(defer.CancelledError)\n\n\n    def test_cancelAfterConnectionMade(self):\n        \"\"\"\n        When a user cancels L{twisted.mail.smtp.sendmail} after the connection\n        is made, the connection is closed by\n        L{twisted.internet.interfaces.ITransport.abortConnection}.\n        \"\"\"\n        reactor = MemoryReactor()\n        transport = AbortableStringTransport()\n        d = smtp.sendmail(\"localhost\", \"source@address\", \"recipient@address\",\n                          b\"message\", reactor=reactor)\n        factory = reactor.tcpClients[0][2]\n        p = factory.buildProtocol(None)\n        p.makeConnection(transport)\n        d.cancel()\n        self.assertEqual(transport.aborting, True)\n        self.assertEqual(transport.disconnecting, True)\n        failure = self.failureResultOf(d)\n        failure.trap(defer.CancelledError)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/names/__init__.py",
    "content": "# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nTwisted Names: DNS server and client implementations.\n\"\"\"\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/names/_rfc1982.py",
    "content": "# -*- test-case-name: twisted.names.test.test_rfc1982 -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nUtilities for handling RFC1982 Serial Number Arithmetic.\n\n@see: U{http://tools.ietf.org/html/rfc1982}\n\n@var RFC4034_TIME_FORMAT: RRSIG Time field presentation format. The Signature\n   Expiration Time and Inception Time field values MUST be represented either\n   as an unsigned decimal integer indicating seconds since 1 January 1970\n   00:00:00 UTC, or in the form YYYYMMDDHHmmSS in UTC. See U{RRSIG Presentation\n   Format<https://tools.ietf.org/html/rfc4034#section-3.2>}\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport calendar\nfrom datetime import datetime, timedelta\n\nfrom twisted.python.compat import nativeString\nfrom twisted.python.util import FancyStrMixin\n\n\nRFC4034_TIME_FORMAT = '%Y%m%d%H%M%S'\n\n\n\nclass SerialNumber(FancyStrMixin, object):\n    \"\"\"\n    An RFC1982 Serial Number.\n\n    This class implements RFC1982 DNS Serial Number Arithmetic.\n\n    SNA is used in DNS and specifically in DNSSEC as defined in RFC4034 in the\n    DNSSEC Signature Expiration and Inception Fields.\n\n    @see: U{https://tools.ietf.org/html/rfc1982}\n    @see: U{https://tools.ietf.org/html/rfc4034}\n\n    @ivar _serialBits: See C{serialBits} of L{__init__}.\n    @ivar _number: See C{number} of L{__init__}.\n    @ivar _modulo: The value at which wrapping will occur.\n    @ivar _halfRing: Half C{_modulo}. If another L{SerialNumber} value is larger\n        than this, it would lead to a wrapped value which is larger than the\n        first and comparisons are therefore ambiguous.\n    @ivar _maxAdd: Half C{_modulo} plus 1. If another L{SerialNumber} value is\n        larger than this, it would lead to a wrapped value which is larger than\n        the first. Comparisons with the original value would therefore be\n        ambiguous.\n    \"\"\"\n\n    showAttributes = (\n        ('_number', 'number', '%d'),\n        ('_serialBits', 'serialBits', '%d'),\n    )\n\n    def __init__(self, number, serialBits=32):\n        \"\"\"\n        Construct an L{SerialNumber} instance.\n\n        @param number: An L{int} which will be stored as the modulo\n            C{number % 2 ^ serialBits}\n        @type number: L{int}\n\n        @param serialBits: The size of the serial number space. The power of two\n            which results in one larger than the largest integer corresponding\n            to a serial number value.\n        @type serialBits: L{int}\n        \"\"\"\n        self._serialBits = serialBits\n        self._modulo = 2 ** serialBits\n        self._halfRing = 2 ** (serialBits - 1)\n        self._maxAdd = 2 ** (serialBits - 1) - 1\n        self._number = int(number) % self._modulo\n\n\n    def _convertOther(self, other):\n        \"\"\"\n        Check that a foreign object is suitable for use in the comparison or\n        arithmetic magic methods of this L{SerialNumber} instance. Raise\n        L{TypeError} if not.\n\n        @param other: The foreign L{object} to be checked.\n        @return: C{other} after compatibility checks and possible coercion.\n        @raises: L{TypeError} if C{other} is not compatible.\n        \"\"\"\n        if not isinstance(other, SerialNumber):\n            raise TypeError(\n                'cannot compare or combine %r and %r' % (self, other))\n\n        if self._serialBits != other._serialBits:\n            raise TypeError(\n                'cannot compare or combine SerialNumber instances with '\n                'different serialBits. %r and %r' % (self, other))\n\n        return other\n\n\n    def __str__(self):\n        \"\"\"\n        Return a string representation of this L{SerialNumber} instance.\n\n        @rtype: L{nativeString}\n        \"\"\"\n        return nativeString('%d' % (self._number,))\n\n\n    def __int__(self):\n        \"\"\"\n        @return: The integer value of this L{SerialNumber} instance.\n        @rtype: L{int}\n        \"\"\"\n        return self._number\n\n\n    def __eq__(self, other):\n        \"\"\"\n        Allow rich equality comparison with another L{SerialNumber} instance.\n\n        @type other: L{SerialNumber}\n        \"\"\"\n        other = self._convertOther(other)\n        return other._number == self._number\n\n\n    def __ne__(self, other):\n        \"\"\"\n        Allow rich equality comparison with another L{SerialNumber} instance.\n\n        @type other: L{SerialNumber}\n        \"\"\"\n        return not self.__eq__(other)\n\n\n    def __lt__(self, other):\n        \"\"\"\n        Allow I{less than} comparison with another L{SerialNumber} instance.\n\n        @type other: L{SerialNumber}\n        \"\"\"\n        other = self._convertOther(other)\n        return (\n            (self._number < other._number\n             and (other._number - self._number) < self._halfRing)\n            or\n            (self._number > other._number\n             and (self._number - other._number) > self._halfRing)\n        )\n\n\n    def __gt__(self, other):\n        \"\"\"\n        Allow I{greater than} comparison with another L{SerialNumber} instance.\n\n        @type other: L{SerialNumber}\n        @rtype: L{bool}\n        \"\"\"\n        other = self._convertOther(other)\n        return (\n            (self._number < other._number\n             and (other._number - self._number) > self._halfRing)\n            or\n            (self._number > other._number\n             and (self._number - other._number) < self._halfRing)\n        )\n\n\n    def __le__(self, other):\n        \"\"\"\n        Allow I{less than or equal} comparison with another L{SerialNumber}\n        instance.\n\n        @type other: L{SerialNumber}\n        @rtype: L{bool}\n        \"\"\"\n        other = self._convertOther(other)\n        return self == other or self < other\n\n\n    def __ge__(self, other):\n        \"\"\"\n        Allow I{greater than or equal} comparison with another L{SerialNumber}\n        instance.\n\n        @type other: L{SerialNumber}\n        @rtype: L{bool}\n        \"\"\"\n        other = self._convertOther(other)\n        return self == other or self > other\n\n\n    def __add__(self, other):\n        \"\"\"\n        Allow I{addition} with another L{SerialNumber} instance.\n\n        Serial numbers may be incremented by the addition of a positive\n        integer n, where n is taken from the range of integers\n        [0 .. (2^(SERIAL_BITS - 1) - 1)].  For a sequence number s, the\n        result of such an addition, s', is defined as\n\n        s' = (s + n) modulo (2 ^ SERIAL_BITS)\n\n        where the addition and modulus operations here act upon values that are\n        non-negative values of unbounded size in the usual ways of integer\n        arithmetic.\n\n        Addition of a value outside the range\n        [0 .. (2^(SERIAL_BITS - 1) - 1)] is undefined.\n\n        @see: U{http://tools.ietf.org/html/rfc1982#section-3.1}\n\n        @type other: L{SerialNumber}\n        @rtype: L{SerialNumber}\n        @raises: L{ArithmeticError} if C{other} is more than C{_maxAdd}\n            ie more than half the maximum value of this serial number.\n        \"\"\"\n        other = self._convertOther(other)\n        if other._number <= self._maxAdd:\n            return SerialNumber(\n                (self._number + other._number) % self._modulo,\n                serialBits=self._serialBits)\n        else:\n            raise ArithmeticError(\n                'value %r outside the range 0 .. %r' % (\n                    other._number, self._maxAdd,))\n\n\n    def __hash__(self):\n        \"\"\"\n        Allow L{SerialNumber} instances to be hashed for use as L{dict} keys.\n\n        @rtype: L{int}\n        \"\"\"\n        return hash(self._number)\n\n\n    @classmethod\n    def fromRFC4034DateString(cls, utcDateString):\n        \"\"\"\n        Create an L{SerialNumber} instance from a date string in format\n        'YYYYMMDDHHMMSS' described in U{RFC4034\n        3.2<https://tools.ietf.org/html/rfc4034#section-3.2>}.\n\n        The L{SerialNumber} instance stores the date as a 32bit UNIX timestamp.\n\n        @see: U{https://tools.ietf.org/html/rfc4034#section-3.1.5}\n\n        @param utcDateString: A UTC date/time string of format I{YYMMDDhhmmss}\n            which will be converted to seconds since the UNIX epoch.\n        @type utcDateString: L{unicode}\n\n        @return: An L{SerialNumber} instance containing the supplied date as a\n            32bit UNIX timestamp.\n        \"\"\"\n        parsedDate = datetime.strptime(utcDateString, RFC4034_TIME_FORMAT)\n        secondsSinceEpoch = calendar.timegm(parsedDate.utctimetuple())\n        return cls(secondsSinceEpoch, serialBits=32)\n\n\n    def toRFC4034DateString(self):\n        \"\"\"\n        Calculate a date by treating the current L{SerialNumber} value as a UNIX\n        timestamp and return a date string in the format described in\n        U{RFC4034 3.2<https://tools.ietf.org/html/rfc4034#section-3.2>}.\n\n        @return: The date string.\n        \"\"\"\n        # Can't use datetime.utcfromtimestamp, because it seems to overflow the\n        # signed 32bit int used in the underlying C library. SNA is unsigned\n        # and capable of handling all timestamps up to 2**32.\n        d = datetime(1970, 1, 1) + timedelta(seconds=self._number)\n        return nativeString(d.strftime(RFC4034_TIME_FORMAT))\n\n\n\n__all__ = ['SerialNumber']\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/names/authority.py",
    "content": "# -*- test-case-name: twisted.names.test.test_names -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAuthoritative resolvers.\n\"\"\"\n\nfrom __future__ import absolute_import, division\n\nimport os\nimport time\n\nfrom twisted.names import dns, error, common\nfrom twisted.internet import defer\nfrom twisted.python import failure\nfrom twisted.python.compat import execfile, nativeString, _PY3\nfrom twisted.python.filepath import FilePath\n\n\n\ndef getSerial(filename='/tmp/twisted-names.serial'):\n    \"\"\"\n    Return a monotonically increasing (across program runs) integer.\n\n    State is stored in the given file.  If it does not exist, it is\n    created with rw-/---/--- permissions.\n\n    @param filename: Path to a file that is used to store the state across\n        program runs.\n    @type filename: L{str}\n\n    @return: a monotonically increasing number\n    @rtype: L{str}\n    \"\"\"\n    serial = time.strftime('%Y%m%d')\n\n    o = os.umask(0o177)\n    try:\n        if not os.path.exists(filename):\n            with open(filename, 'w') as f:\n                f.write(serial + ' 0')\n    finally:\n        os.umask(o)\n\n    with open(filename, 'r') as serialFile:\n        lastSerial, zoneID = serialFile.readline().split()\n\n    zoneID = (lastSerial == serial) and (int(zoneID) + 1) or 0\n\n    with open(filename, 'w') as serialFile:\n        serialFile.write('%s %d' % (serial, zoneID))\n\n    serial = serial + ('%02d' % (zoneID,))\n    return serial\n\n\n\nclass FileAuthority(common.ResolverBase):\n    \"\"\"\n    An Authority that is loaded from a file.\n\n    @ivar _ADDITIONAL_PROCESSING_TYPES: Record types for which additional\n        processing will be done.\n\n    @ivar _ADDRESS_TYPES: Record types which are useful for inclusion in the\n        additional section generated during additional processing.\n\n    @ivar soa: A 2-tuple containing the SOA domain name as a L{bytes} and a\n        L{dns.Record_SOA}.\n    \"\"\"\n    # See https://twistedmatrix.com/trac/ticket/6650\n    _ADDITIONAL_PROCESSING_TYPES = (dns.CNAME, dns.MX, dns.NS)\n    _ADDRESS_TYPES = (dns.A, dns.AAAA)\n\n    soa = None\n    records = None\n\n    def __init__(self, filename):\n        common.ResolverBase.__init__(self)\n        self.loadFile(filename)\n        self._cache = {}\n\n\n    def __setstate__(self, state):\n        self.__dict__ = state\n\n\n    def _additionalRecords(self, answer, authority, ttl):\n        \"\"\"\n        Find locally known information that could be useful to the consumer of\n        the response and construct appropriate records to include in the\n        I{additional} section of that response.\n\n        Essentially, implement RFC 1034 section 4.3.2 step 6.\n\n        @param answer: A L{list} of the records which will be included in the\n            I{answer} section of the response.\n\n        @param authority: A L{list} of the records which will be included in\n            the I{authority} section of the response.\n\n        @param ttl: The default TTL for records for which this is not otherwise\n            specified.\n\n        @return: A generator of L{dns.RRHeader} instances for inclusion in the\n            I{additional} section.  These instances represent extra information\n            about the records in C{answer} and C{authority}.\n        \"\"\"\n        for record in answer + authority:\n            if record.type in self._ADDITIONAL_PROCESSING_TYPES:\n                name = record.payload.name.name\n                for rec in self.records.get(name.lower(), ()):\n                    if rec.TYPE in self._ADDRESS_TYPES:\n                        yield dns.RRHeader(\n                            name, rec.TYPE, dns.IN,\n                            rec.ttl or ttl, rec, auth=True)\n\n\n    def _lookup(self, name, cls, type, timeout=None):\n        \"\"\"\n        Determine a response to a particular DNS query.\n\n        @param name: The name which is being queried and for which to lookup a\n            response.\n        @type name: L{bytes}\n\n        @param cls: The class which is being queried.  Only I{IN} is\n            implemented here and this value is presently disregarded.\n        @type cls: L{int}\n\n        @param type: The type of records being queried.  See the types defined\n            in L{twisted.names.dns}.\n        @type type: L{int}\n\n        @param timeout: All processing is done locally and a result is\n            available immediately, so the timeout value is ignored.\n\n        @return: A L{Deferred} that fires with a L{tuple} of three sets of\n            response records (to comprise the I{answer}, I{authority}, and\n            I{additional} sections of a DNS response) or with a L{Failure} if\n            there is a problem processing the query.\n        \"\"\"\n        cnames = []\n        results = []\n        authority = []\n        additional = []\n        default_ttl = max(self.soa[1].minimum, self.soa[1].expire)\n\n        domain_records = self.records.get(name.lower())\n\n        if domain_records:\n            for record in domain_records:\n                if record.ttl is not None:\n                    ttl = record.ttl\n                else:\n                    ttl = default_ttl\n\n                if (record.TYPE == dns.NS and\n                        name.lower() != self.soa[0].lower()):\n                    # NS record belong to a child zone: this is a referral.  As\n                    # NS records are authoritative in the child zone, ours here\n                    # are not.  RFC 2181, section 6.1.\n                    authority.append(\n                        dns.RRHeader(\n                            name, record.TYPE, dns.IN, ttl, record, auth=False\n                        )\n                    )\n                elif record.TYPE == type or type == dns.ALL_RECORDS:\n                    results.append(\n                        dns.RRHeader(\n                            name, record.TYPE, dns.IN, ttl, record, auth=True\n                        )\n                    )\n                if record.TYPE == dns.CNAME:\n                    cnames.append(\n                        dns.RRHeader(\n                            name, record.TYPE, dns.IN, ttl, record, auth=True\n                        )\n                    )\n            if not results:\n                results = cnames\n\n            # Sort of https://tools.ietf.org/html/rfc1034#section-4.3.2 .\n            # See https://twistedmatrix.com/trac/ticket/6732\n            additionalInformation = self._additionalRecords(\n                results, authority, default_ttl)\n            if cnames:\n                results.extend(additionalInformation)\n            else:\n                additional.extend(additionalInformation)\n\n            if not results and not authority:\n                # Empty response. Include SOA record to allow clients to cache\n                # this response. RFC 1034, sections 3.7 and 4.3.4, and RFC 2181\n                # section 7.1.\n                authority.append(\n                    dns.RRHeader(\n                        self.soa[0], dns.SOA, dns.IN, ttl, self.soa[1],\n                        auth=True\n                    )\n                )\n            return defer.succeed((results, authority, additional))\n        else:\n            if dns._isSubdomainOf(name, self.soa[0]):\n                # We may be the authority and we didn't find it.\n                # XXX: The QNAME may also be in a delegated child zone. See\n                # #6581 and #6580\n                return defer.fail(\n                    failure.Failure(dns.AuthoritativeDomainError(name))\n                )\n            else:\n                # The QNAME is not a descendant of this zone. Fail with\n                # DomainError so that the next chained authority or\n                # resolver will be queried.\n                return defer.fail(failure.Failure(error.DomainError(name)))\n\n\n    def lookupZone(self, name, timeout=10):\n        if self.soa[0].lower() == name.lower():\n            # Wee hee hee hooo yea\n            default_ttl = max(self.soa[1].minimum, self.soa[1].expire)\n            if self.soa[1].ttl is not None:\n                soa_ttl = self.soa[1].ttl\n            else:\n                soa_ttl = default_ttl\n            results = [\n                dns.RRHeader(\n                    self.soa[0], dns.SOA, dns.IN, soa_ttl, self.soa[1],\n                    auth=True\n                )\n            ]\n            for (k, r) in self.records.items():\n                for rec in r:\n                    if rec.ttl is not None:\n                        ttl = rec.ttl\n                    else:\n                        ttl = default_ttl\n                    if rec.TYPE != dns.SOA:\n                        results.append(\n                            dns.RRHeader(\n                                k, rec.TYPE, dns.IN, ttl, rec, auth=True\n                            )\n                        )\n            results.append(results[0])\n            return defer.succeed((results, (), ()))\n        return defer.fail(failure.Failure(dns.DomainError(name)))\n\n\n    def _cbAllRecords(self, results):\n        ans, auth, add = [], [], []\n        for res in results:\n            if res[0]:\n                ans.extend(res[1][0])\n                auth.extend(res[1][1])\n                add.extend(res[1][2])\n        return ans, auth, add\n\n\n\nclass PySourceAuthority(FileAuthority):\n    \"\"\"\n    A FileAuthority that is built up from Python source code.\n    \"\"\"\n    def loadFile(self, filename):\n        g, l = self.setupConfigNamespace(), {}\n        execfile(filename, g, l)\n        if 'zone' not in l:\n            raise ValueError(\"No zone defined in \" + filename)\n\n        self.records = {}\n        for rr in l['zone']:\n            if isinstance(rr[1], dns.Record_SOA):\n                self.soa = rr\n            self.records.setdefault(rr[0].lower(), []).append(rr[1])\n\n\n    def wrapRecord(self, type):\n        return lambda name, *arg, **kw: (name, type(*arg, **kw))\n\n\n    def setupConfigNamespace(self):\n        r = {}\n        items = dns.__dict__.iterkeys()\n        for record in [x for x in items if x.startswith('Record_')]:\n            type = getattr(dns, record)\n            f = self.wrapRecord(type)\n            r[record[len('Record_'):]] = f\n        return r\n\n\n\nclass BindAuthority(FileAuthority):\n    \"\"\"\n    An Authority that loads U{BIND zone files\n    <https://en.wikipedia.org/wiki/Zone_file>}.\n\n    Supports only C{$ORIGIN} and C{$TTL} directives.\n    \"\"\"\n    def loadFile(self, filename):\n        \"\"\"\n        Load records from C{filename}.\n\n        @param filename: file to read from\n        @type filename: L{bytes}\n        \"\"\"\n        fp = FilePath(filename)\n        # Not the best way to set an origin. It can be set using $ORIGIN\n        # though.\n        self.origin = nativeString(fp.basename() + b'.')\n\n        lines = fp.getContent().splitlines(True)\n        lines = self.stripComments(lines)\n        lines = self.collapseContinuations(lines)\n        self.parseLines(lines)\n\n\n    def stripComments(self, lines):\n        \"\"\"\n        Strip comments from C{lines}.\n\n        @param lines: lines to work on\n        @type lines: iterable of L{bytes}\n\n        @return: C{lines} sans comments.\n        \"\"\"\n        return (\n            a.find(b';') == -1 and a or a[:a.find(b';')] for a in [\n                b.strip() for b in lines\n            ]\n        )\n\n\n    def collapseContinuations(self, lines):\n        \"\"\"\n        Transform multiline statements into single lines.\n\n        @param lines: lines to work on\n        @type lines: iterable of L{bytes}\n\n        @return: iterable of continuous lines\n        \"\"\"\n        l = []\n        state = 0\n        for line in lines:\n            if state == 0:\n                if line.find(b'(') == -1:\n                    l.append(line)\n                else:\n                    l.append(line[:line.find(b'(')])\n                    state = 1\n            else:\n                if line.find(b')') != -1:\n                    l[-1] += b' ' + line[:line.find(b')')]\n                    state = 0\n                else:\n                    l[-1] += b' ' + line\n        return filter(None, (line.split() for line in l))\n\n\n    def parseLines(self, lines):\n        \"\"\"\n        Parse C{lines}.\n\n        @param lines: lines to work on\n        @type lines: iterable of L{bytes}\n        \"\"\"\n        ttl = 60 * 60 * 3\n        origin = self.origin\n\n        self.records = {}\n\n        for line in lines:\n            if line[0] == b'$TTL':\n                ttl = dns.str2time(line[1])\n            elif line[0] == b'$ORIGIN':\n                origin = line[1]\n            elif line[0] == b'$INCLUDE':\n                raise NotImplementedError('$INCLUDE directive not implemented')\n            elif line[0] == b'$GENERATE':\n                raise NotImplementedError(\n                    '$GENERATE directive not implemented'\n                )\n            else:\n                self.parseRecordLine(origin, ttl, line)\n\n        # If the origin changed, reflect that within the instance.\n        self.origin = origin\n\n\n    def addRecord(self, owner, ttl, type, domain, cls, rdata):\n        \"\"\"\n        Add a record to our authority.  Expand domain with origin if necessary.\n\n        @param owner: origin?\n        @type owner: L{bytes}\n\n        @param ttl: time to live for the record\n        @type ttl: L{int}\n\n        @param domain: the domain for which the record is to be added\n        @type domain: L{bytes}\n\n        @param type: record type\n        @type type: L{str}\n\n        @param cls: record class\n        @type cls: L{str}\n\n        @param rdata: record data\n        @type rdata: L{list} of L{bytes}\n        \"\"\"\n        if not domain.endswith(b'.'):\n            domain = domain + b'.' + owner[:-1]\n        else:\n            domain = domain[:-1]\n        f = getattr(self, 'class_%s' % (cls,), None)\n        if f:\n            f(ttl, type, domain, rdata)\n        else:\n            raise NotImplementedError(\n                \"Record class %r not supported\" % (cls,)\n            )\n\n\n    def class_IN(self, ttl, type, domain, rdata):\n        \"\"\"\n        Simulate a class IN and recurse into the actual class.\n\n        @param ttl: time to live for the record\n        @type ttl: L{int}\n\n        @param type: record type\n        @type type: str\n\n        @param domain: the domain\n        @type domain: bytes\n\n        @param rdata:\n        @type rdate: bytes\n        \"\"\"\n        record = getattr(dns, 'Record_%s' % (nativeString(type),), None)\n        if record:\n            r = record(*rdata)\n            r.ttl = ttl\n            self.records.setdefault(domain.lower(), []).append(r)\n\n            if type == 'SOA':\n                self.soa = (domain, r)\n        else:\n            raise NotImplementedError(\n                \"Record type %r not supported\" % (nativeString(type),)\n            )\n\n\n    def parseRecordLine(self, origin, ttl, line):\n        \"\"\"\n        Parse a C{line} from a zone file respecting C{origin} and C{ttl}.\n\n        Add resulting records to authority.\n\n        @param origin: starting point for the zone\n        @type origin: L{bytes}\n\n        @param ttl: time to live for the record\n        @type ttl: L{int}\n\n        @param line: zone file line to parse; split by word\n        @type line: L{list} of L{bytes}\n        \"\"\"\n        if _PY3:\n            queryClasses = set(\n                qc.encode(\"ascii\") for qc in dns.QUERY_CLASSES.values()\n            )\n            queryTypes = set(\n                qt.encode(\"ascii\") for qt in dns.QUERY_TYPES.values()\n            )\n        else:\n            queryClasses = set(dns.QUERY_CLASSES.values())\n            queryTypes = set(dns.QUERY_TYPES.values())\n\n        markers = queryClasses | queryTypes\n\n        cls = b'IN'\n        owner = origin\n\n        if line[0] == b'@':\n            line = line[1:]\n            owner = origin\n        elif not line[0].isdigit() and line[0] not in markers:\n            owner = line[0]\n            line = line[1:]\n\n        if line[0].isdigit() or line[0] in markers:\n            domain = owner\n            owner = origin\n        else:\n            domain = line[0]\n            line = line[1:]\n\n        if line[0] in queryClasses:\n            cls = line[0]\n            line = line[1:]\n            if line[0].isdigit():\n                ttl = int(line[0])\n                line = line[1:]\n        elif line[0].isdigit():\n            ttl = int(line[0])\n            line = line[1:]\n            if line[0] in queryClasses:\n                cls = line[0]\n                line = line[1:]\n\n        type = line[0]\n        rdata = line[1:]\n\n        self.addRecord(\n            owner, ttl, nativeString(type), domain, nativeString(cls), rdata\n        )\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/names/cache.py",
    "content": "# -*- test-case-name: twisted.names.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAn in-memory caching resolver.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nfrom twisted.names import dns, common\nfrom twisted.python import failure, log\nfrom twisted.internet import defer\n\n\n\nclass CacheResolver(common.ResolverBase):\n    \"\"\"\n    A resolver that serves records from a local, memory cache.\n\n    @ivar _reactor: A provider of L{interfaces.IReactorTime}.\n    \"\"\"\n    cache = None\n\n    def __init__(self, cache=None, verbose=0, reactor=None):\n        common.ResolverBase.__init__(self)\n\n        self.cache = {}\n        self.verbose = verbose\n        self.cancel = {}\n        if reactor is None:\n            from twisted.internet import reactor\n        self._reactor = reactor\n\n        if cache:\n            for query, (seconds, payload) in cache.items():\n                self.cacheResult(query, payload, seconds)\n\n\n    def __setstate__(self, state):\n        self.__dict__ = state\n\n        now = self._reactor.seconds()\n        for (k, (when, (ans, add, ns))) in self.cache.items():\n            diff = now - when\n            for rec in ans + add + ns:\n                if rec.ttl < diff:\n                    del self.cache[k]\n                    break\n\n\n    def __getstate__(self):\n        for c in self.cancel.values():\n            c.cancel()\n        self.cancel.clear()\n        return self.__dict__\n\n\n    def _lookup(self, name, cls, type, timeout):\n        now = self._reactor.seconds()\n        q = dns.Query(name, type, cls)\n        try:\n            when, (ans, auth, add) = self.cache[q]\n        except KeyError:\n            if self.verbose > 1:\n                log.msg('Cache miss for ' + repr(name))\n            return defer.fail(failure.Failure(dns.DomainError(name)))\n        else:\n            if self.verbose:\n                log.msg('Cache hit for ' + repr(name))\n            diff = now - when\n\n            try:\n                result = (\n                    [dns.RRHeader(r.name.name, r.type, r.cls, r.ttl - diff,\n                                  r.payload) for r in ans],\n                    [dns.RRHeader(r.name.name, r.type, r.cls, r.ttl - diff,\n                                  r.payload) for r in auth],\n                    [dns.RRHeader(r.name.name, r.type, r.cls, r.ttl - diff,\n                                  r.payload) for r in add])\n            except ValueError:\n                return defer.fail(failure.Failure(dns.DomainError(name)))\n            else:\n                return defer.succeed(result)\n\n\n    def lookupAllRecords(self, name, timeout = None):\n        return defer.fail(failure.Failure(dns.DomainError(name)))\n\n\n    def cacheResult(self, query, payload, cacheTime=None):\n        \"\"\"\n        Cache a DNS entry.\n\n        @param query: a L{dns.Query} instance.\n\n        @param payload: a 3-tuple of lists of L{dns.RRHeader} records, the\n            matching result of the query (answers, authority and additional).\n\n        @param cacheTime: The time (seconds since epoch) at which the entry is\n            considered to have been added to the cache. If L{None} is given,\n            the current time is used.\n        \"\"\"\n        if self.verbose > 1:\n            log.msg('Adding %r to cache' % query)\n\n        self.cache[query] = (cacheTime or self._reactor.seconds(), payload)\n\n        if query in self.cancel:\n            self.cancel[query].cancel()\n\n        s = list(payload[0]) + list(payload[1]) + list(payload[2])\n        if s:\n            m = s[0].ttl\n            for r in s:\n                m = min(m, r.ttl)\n        else:\n            m = 0\n\n        self.cancel[query] = self._reactor.callLater(m, self.clearEntry, query)\n\n\n    def clearEntry(self, query):\n        del self.cache[query]\n        del self.cancel[query]\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/names/client.py",
    "content": "# -*- test-case-name: twisted.names.test.test_names -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nAsynchronous client DNS\n\nThe functions exposed in this module can be used for asynchronous name\nresolution and dns queries.\n\nIf you need to create a resolver with specific requirements, such as needing to\ndo queries against a particular host, the L{createResolver} function will\nreturn an C{IResolver}.\n\nFuture plans: Proper nameserver acquisition on Windows/MacOS,\nbetter caching, respect timeouts\n\"\"\"\n\nimport os\nimport errno\nimport warnings\n\nfrom zope.interface import moduleProvides\n\n# Twisted imports\nfrom twisted.python.compat import nativeString\nfrom twisted.python.runtime import platform\nfrom twisted.python.filepath import FilePath\nfrom twisted.internet import error, defer, interfaces, protocol\nfrom twisted.python import log, failure\nfrom twisted.names import (\n    dns, common, resolve, cache, root, hosts as hostsModule)\nfrom twisted.internet.abstract import isIPv6Address\n\n\n\nmoduleProvides(interfaces.IResolver)\n\n\n\nclass Resolver(common.ResolverBase):\n    \"\"\"\n    @ivar _waiting: A C{dict} mapping tuple keys of query name/type/class to\n        Deferreds which will be called back with the result of those queries.\n        This is used to avoid issuing the same query more than once in\n        parallel.  This is more efficient on the network and helps avoid a\n        \"birthday paradox\" attack by keeping the number of outstanding requests\n        for a particular query fixed at one instead of allowing the attacker to\n        raise it to an arbitrary number.\n\n    @ivar _reactor: A provider of L{IReactorTCP}, L{IReactorUDP}, and\n        L{IReactorTime} which will be used to set up network resources and\n        track timeouts.\n    \"\"\"\n    index = 0\n    timeout = None\n\n    factory = None\n    servers = None\n    dynServers = ()\n    pending = None\n    connections = None\n\n    resolv = None\n    _lastResolvTime = None\n    _resolvReadInterval = 60\n\n    def __init__(self, resolv=None, servers=None, timeout=(1, 3, 11, 45), reactor=None):\n        \"\"\"\n        Construct a resolver which will query domain name servers listed in\n        the C{resolv.conf(5)}-format file given by C{resolv} as well as\n        those in the given C{servers} list.  Servers are queried in a\n        round-robin fashion.  If given, C{resolv} is periodically checked\n        for modification and re-parsed if it is noticed to have changed.\n\n        @type servers: C{list} of C{(str, int)} or L{None}\n        @param servers: If not None, interpreted as a list of (host, port)\n            pairs specifying addresses of domain name servers to attempt to use\n            for this lookup.  Host addresses should be in IPv4 dotted-quad\n            form.  If specified, overrides C{resolv}.\n\n        @type resolv: C{str}\n        @param resolv: Filename to read and parse as a resolver(5)\n            configuration file.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Default number of seconds after which to reissue the\n            query.  When the last timeout expires, the query is considered\n            failed.\n\n        @param reactor: A provider of L{IReactorTime}, L{IReactorUDP}, and\n            L{IReactorTCP} which will be used to establish connections, listen\n            for DNS datagrams, and enforce timeouts.  If not provided, the\n            global reactor will be used.\n\n        @raise ValueError: Raised if no nameserver addresses can be found.\n        \"\"\"\n        common.ResolverBase.__init__(self)\n\n        if reactor is None:\n            from twisted.internet import reactor\n        self._reactor = reactor\n\n        self.timeout = timeout\n\n        if servers is None:\n            self.servers = []\n        else:\n            self.servers = servers\n\n        self.resolv = resolv\n\n        if not len(self.servers) and not resolv:\n            raise ValueError(\"No nameservers specified\")\n\n        self.factory = DNSClientFactory(self, timeout)\n        self.factory.noisy = 0   # Be quiet by default\n\n        self.connections = []\n        self.pending = []\n\n        self._waiting = {}\n\n        self.maybeParseConfig()\n\n\n    def __getstate__(self):\n        d = self.__dict__.copy()\n        d['connections'] = []\n        d['_parseCall'] = None\n        return d\n\n\n    def __setstate__(self, state):\n        self.__dict__.update(state)\n        self.maybeParseConfig()\n\n\n    def _openFile(self, path):\n        \"\"\"\n        Wrapper used for opening files in the class, exists primarily for unit\n        testing purposes.\n        \"\"\"\n        return FilePath(path).open()\n\n\n    def maybeParseConfig(self):\n        if self.resolv is None:\n            # Don't try to parse it, don't set up a call loop\n            return\n\n        try:\n            resolvConf = self._openFile(self.resolv)\n        except IOError as e:\n            if e.errno == errno.ENOENT:\n                # Missing resolv.conf is treated the same as an empty resolv.conf\n                self.parseConfig(())\n            else:\n                raise\n        else:\n            with resolvConf:\n                mtime = os.fstat(resolvConf.fileno()).st_mtime\n                if mtime != self._lastResolvTime:\n                    log.msg('%s changed, reparsing' % (self.resolv,))\n                    self._lastResolvTime = mtime\n                    self.parseConfig(resolvConf)\n\n        # Check again in a little while\n        self._parseCall = self._reactor.callLater(\n            self._resolvReadInterval, self.maybeParseConfig)\n\n\n    def parseConfig(self, resolvConf):\n        servers = []\n        for L in resolvConf:\n            L = L.strip()\n            if L.startswith(b'nameserver'):\n                resolver = (nativeString(L.split()[1]), dns.PORT)\n                servers.append(resolver)\n                log.msg(\"Resolver added %r to server list\" % (resolver,))\n            elif L.startswith(b'domain'):\n                try:\n                    self.domain = L.split()[1]\n                except IndexError:\n                    self.domain = b''\n                self.search = None\n            elif L.startswith(b'search'):\n                self.search = L.split()[1:]\n                self.domain = None\n        if not servers:\n            servers.append(('127.0.0.1', dns.PORT))\n        self.dynServers = servers\n\n\n    def pickServer(self):\n        \"\"\"\n        Return the address of a nameserver.\n\n        TODO: Weight servers for response time so faster ones can be\n        preferred.\n        \"\"\"\n        if not self.servers and not self.dynServers:\n            return None\n        serverL = len(self.servers)\n        dynL = len(self.dynServers)\n\n        self.index += 1\n        self.index %= (serverL + dynL)\n        if self.index < serverL:\n            return self.servers[self.index]\n        else:\n            return self.dynServers[self.index - serverL]\n\n\n    def _connectedProtocol(self, interface=''):\n        \"\"\"\n        Return a new L{DNSDatagramProtocol} bound to a randomly selected port\n        number.\n        \"\"\"\n        failures = 0\n        proto = dns.DNSDatagramProtocol(self, reactor=self._reactor)\n\n        while True:\n            try:\n                self._reactor.listenUDP(dns.randomSource(), proto,\n                                        interface=interface)\n            except error.CannotListenError as e:\n                failures += 1\n\n                if (hasattr(e.socketError, \"errno\") and\n                   e.socketError.errno == errno.EMFILE):\n                    # We've run out of file descriptors. Stop trying.\n                    raise\n\n                if failures >= 1000:\n                    # We've tried a thousand times and haven't found a port.\n                    # This is almost impossible, and likely means something\n                    # else weird is going on. Raise, as to not infinite loop.\n                    raise\n            else:\n                return proto\n\n\n    def connectionMade(self, protocol):\n        \"\"\"\n        Called by associated L{dns.DNSProtocol} instances when they connect.\n        \"\"\"\n        self.connections.append(protocol)\n        for (d, q, t) in self.pending:\n            self.queryTCP(q, t).chainDeferred(d)\n        del self.pending[:]\n\n\n    def connectionLost(self, protocol):\n        \"\"\"\n        Called by associated L{dns.DNSProtocol} instances when they disconnect.\n        \"\"\"\n        if protocol in self.connections:\n            self.connections.remove(protocol)\n\n\n    def messageReceived(self, message, protocol, address = None):\n        log.msg(\"Unexpected message (%d) received from %r\" % (message.id, address))\n\n\n    def _query(self, *args):\n        \"\"\"\n        Get a new L{DNSDatagramProtocol} instance from L{_connectedProtocol},\n        issue a query to it using C{*args}, and arrange for it to be\n        disconnected from its transport after the query completes.\n\n        @param *args: Positional arguments to be passed to\n            L{DNSDatagramProtocol.query}.\n\n        @return: A L{Deferred} which will be called back with the result of the\n            query.\n        \"\"\"\n        if isIPv6Address(args[0][0]):\n            protocol = self._connectedProtocol(interface='::')\n        else:\n            protocol = self._connectedProtocol()\n        d = protocol.query(*args)\n        def cbQueried(result):\n            protocol.transport.stopListening()\n            return result\n        d.addBoth(cbQueried)\n        return d\n\n\n    def queryUDP(self, queries, timeout = None):\n        \"\"\"\n        Make a number of DNS queries via UDP.\n\n        @type queries: A C{list} of C{dns.Query} instances\n        @param queries: The queries to make.\n\n        @type timeout: Sequence of C{int}\n        @param timeout: Number of seconds after which to reissue the query.\n        When the last timeout expires, the query is considered failed.\n\n        @rtype: C{Deferred}\n        @raise C{twisted.internet.defer.TimeoutError}: When the query times\n        out.\n        \"\"\"\n        if timeout is None:\n            timeout = self.timeout\n\n        addresses = self.servers + list(self.dynServers)\n        if not addresses:\n            return defer.fail(IOError(\"No domain name servers available\"))\n\n        # Make sure we go through servers in the list in the order they were\n        # specified.\n        addresses.reverse()\n\n        used = addresses.pop()\n        d = self._query(used, queries, timeout[0])\n        d.addErrback(self._reissue, addresses, [used], queries, timeout)\n        return d\n\n\n    def _reissue(self, reason, addressesLeft, addressesUsed, query, timeout):\n        reason.trap(dns.DNSQueryTimeoutError)\n\n        # If there are no servers left to be tried, adjust the timeout\n        # to the next longest timeout period and move all the\n        # \"used\" addresses back to the list of addresses to try.\n        if not addressesLeft:\n            addressesLeft = addressesUsed\n            addressesLeft.reverse()\n            addressesUsed = []\n            timeout = timeout[1:]\n\n        # If all timeout values have been used this query has failed.  Tell the\n        # protocol we're giving up on it and return a terminal timeout failure\n        # to our caller.\n        if not timeout:\n            return failure.Failure(defer.TimeoutError(query))\n\n        # Get an address to try.  Take it out of the list of addresses\n        # to try and put it ino the list of already tried addresses.\n        address = addressesLeft.pop()\n        addressesUsed.append(address)\n\n        # Issue a query to a server.  Use the current timeout.  Add this\n        # function as a timeout errback in case another retry is required.\n        d = self._query(address, query, timeout[0], reason.value.id)\n        d.addErrback(self._reissue, addressesLeft, addressesUsed, query, timeout)\n        return d\n\n\n    def queryTCP(self, queries, timeout = 10):\n        \"\"\"\n        Make a number of DNS queries via TCP.\n\n        @type queries: Any non-zero number of C{dns.Query} instances\n        @param queries: The queries to make.\n\n        @type timeout: C{int}\n        @param timeout: The number of seconds after which to fail.\n\n        @rtype: C{Deferred}\n        \"\"\"\n        if not len(self.connections):\n            address = self.pickServer()\n            if address is None:\n                return defer.fail(IOError(\"No domain name servers available\"))\n            host, port = address\n            self._reactor.connectTCP(host, port, self.factory)\n            self.pending.append((defer.Deferred(), queries, timeout))\n            return self.pending[-1][0]\n        else:\n            return self.connections[0].query(queries, timeout)\n\n\n    def filterAnswers(self, message):\n        \"\"\"\n        Extract results from the given message.\n\n        If the message was truncated, re-attempt the query over TCP and return\n        a Deferred which will fire with the results of that query.\n\n        If the message's result code is not C{twisted.names.dns.OK}, return a\n        Failure indicating the type of error which occurred.\n\n        Otherwise, return a three-tuple of lists containing the results from\n        the answers section, the authority section, and the additional section.\n        \"\"\"\n        if message.trunc:\n            return self.queryTCP(message.queries).addCallback(self.filterAnswers)\n        if message.rCode != dns.OK:\n            return failure.Failure(self.exceptionForCode(message.rCode)(message))\n        return (message.answers, message.authority, message.additional)\n\n\n    def _lookup(self, name, cls, type, timeout):\n        \"\"\"\n        Build a L{dns.Query} for the given parameters and dispatch it via UDP.\n\n        If this query is already outstanding, it will not be re-issued.\n        Instead, when the outstanding query receives a response, that response\n        will be re-used for this query as well.\n\n        @type name: C{str}\n        @type type: C{int}\n        @type cls: C{int}\n\n        @return: A L{Deferred} which fires with a three-tuple giving the\n            answer, authority, and additional sections of the response or with\n            a L{Failure} if the response code is anything other than C{dns.OK}.\n        \"\"\"\n        key = (name, type, cls)\n        waiting = self._waiting.get(key)\n        if waiting is None:\n            self._waiting[key] = []\n            d = self.queryUDP([dns.Query(name, type, cls)], timeout)\n            def cbResult(result):\n                for d in self._waiting.pop(key):\n                    d.callback(result)\n                return result\n            d.addCallback(self.filterAnswers)\n            d.addBoth(cbResult)\n        else:\n            d = defer.Deferred()\n            waiting.append(d)\n        return d\n\n\n    # This one doesn't ever belong on UDP\n    def lookupZone(self, name, timeout=10):\n        address = self.pickServer()\n        if address is None:\n            return defer.fail(IOError('No domain name servers available'))\n        host, port = address\n        d = defer.Deferred()\n        controller = AXFRController(name, d)\n        factory = DNSClientFactory(controller, timeout)\n        factory.noisy = False #stfu\n\n        connector = self._reactor.connectTCP(host, port, factory)\n        controller.timeoutCall = self._reactor.callLater(\n            timeout or 10, self._timeoutZone, d, controller,\n            connector, timeout or 10)\n\n        def eliminateTimeout(failure):\n            controller.timeoutCall.cancel()\n            controller.timeoutCall = None\n            return failure\n\n        return d.addCallbacks(self._cbLookupZone, eliminateTimeout,\n                              callbackArgs=(connector,))\n\n\n    def _timeoutZone(self, d, controller, connector, seconds):\n        connector.disconnect()\n        controller.timeoutCall = None\n        controller.deferred = None\n        d.errback(error.TimeoutError(\"Zone lookup timed out after %d seconds\" % (seconds,)))\n\n\n    def _cbLookupZone(self, result, connector):\n        connector.disconnect()\n        return (result, [], [])\n\n\n\nclass AXFRController:\n    timeoutCall = None\n\n    def __init__(self, name, deferred):\n        self.name = name\n        self.deferred = deferred\n        self.soa = None\n        self.records = []\n        self.pending = [(deferred,)]\n\n\n    def connectionMade(self, protocol):\n        # dig saids recursion-desired to 0, so I will too\n        message = dns.Message(protocol.pickID(), recDes=0)\n        message.queries = [dns.Query(self.name, dns.AXFR, dns.IN)]\n        protocol.writeMessage(message)\n\n\n    def connectionLost(self, protocol):\n        # XXX Do something here - see #3428\n        pass\n\n\n    def messageReceived(self, message, protocol):\n        # Caveat: We have to handle two cases: All records are in 1\n        # message, or all records are in N messages.\n\n        # According to http://cr.yp.to/djbdns/axfr-notes.html,\n        # 'authority' and 'additional' are always empty, and only\n        # 'answers' is present.\n        self.records.extend(message.answers)\n        if not self.records:\n            return\n        if not self.soa:\n            if self.records[0].type == dns.SOA:\n                #print \"first SOA!\"\n                self.soa = self.records[0]\n        if len(self.records) > 1 and self.records[-1].type == dns.SOA:\n            #print \"It's the second SOA! We're done.\"\n            if self.timeoutCall is not None:\n                self.timeoutCall.cancel()\n                self.timeoutCall = None\n            if self.deferred is not None:\n                self.deferred.callback(self.records)\n                self.deferred = None\n\n\n\nfrom twisted.internet.base import ThreadedResolver as _ThreadedResolverImpl\n\nclass ThreadedResolver(_ThreadedResolverImpl):\n    def __init__(self, reactor=None):\n        if reactor is None:\n            from twisted.internet import reactor\n        _ThreadedResolverImpl.__init__(self, reactor)\n        warnings.warn(\n            \"twisted.names.client.ThreadedResolver is deprecated since \"\n            \"Twisted 9.0, use twisted.internet.base.ThreadedResolver \"\n            \"instead.\",\n            category=DeprecationWarning, stacklevel=2)\n\n\n\nclass DNSClientFactory(protocol.ClientFactory):\n    def __init__(self, controller, timeout = 10):\n        self.controller = controller\n        self.timeout = timeout\n\n\n    def clientConnectionLost(self, connector, reason):\n        pass\n\n\n    def clientConnectionFailed(self, connector, reason):\n        \"\"\"\n        Fail all pending TCP DNS queries if the TCP connection attempt\n        fails.\n\n        @see: L{twisted.internet.protocol.ClientFactory}\n\n        @param connector: Not used.\n        @type connector: L{twisted.internet.interfaces.IConnector}\n\n        @param reason: A C{Failure} containing information about the\n            cause of the connection failure. This will be passed as the\n            argument to C{errback} on every pending TCP query\n            C{deferred}.\n        @type reason: L{twisted.python.failure.Failure}\n        \"\"\"\n        # Copy the current pending deferreds then reset the master\n        # pending list. This prevents triggering new deferreds which\n        # may be added by callback or errback functions on the current\n        # deferreds.\n        pending = self.controller.pending[:]\n        del self.controller.pending[:]\n        for pendingState in pending:\n            d = pendingState[0]\n            d.errback(reason)\n\n\n    def buildProtocol(self, addr):\n        p = dns.DNSProtocol(self.controller)\n        p.factory = self\n        return p\n\n\n\ndef createResolver(servers=None, resolvconf=None, hosts=None):\n    \"\"\"\n    Create and return a Resolver.\n\n    @type servers: C{list} of C{(str, int)} or L{None}\n\n    @param servers: If not L{None}, interpreted as a list of domain name servers\n    to attempt to use. Each server is a tuple of address in C{str} dotted-quad\n    form and C{int} port number.\n\n    @type resolvconf: C{str} or L{None}\n    @param resolvconf: If not L{None}, on posix systems will be interpreted as\n    an alternate resolv.conf to use. Will do nothing on windows systems. If\n    L{None}, /etc/resolv.conf will be used.\n\n    @type hosts: C{str} or L{None}\n    @param hosts: If not L{None}, an alternate hosts file to use. If L{None}\n    on posix systems, /etc/hosts will be used. On windows, C:\\windows\\hosts\n    will be used.\n\n    @rtype: C{IResolver}\n    \"\"\"\n    if platform.getType() == 'posix':\n        if resolvconf is None:\n            resolvconf = b'/etc/resolv.conf'\n        if hosts is None:\n            hosts = b'/etc/hosts'\n        theResolver = Resolver(resolvconf, servers)\n        hostResolver = hostsModule.Resolver(hosts)\n    else:\n        if hosts is None:\n            hosts = r'c:\\windows\\hosts'\n        from twisted.internet import reactor\n        bootstrap = _ThreadedResolverImpl(reactor)\n        hostResolver = hostsModule.Resolver(hosts)\n        theResolver = root.bootstrap(bootstrap, resolverFactory=Resolver)\n\n    L = [hostResolver, cache.CacheResolver(), theResolver]\n    return resolve.ResolverChain(L)\n\n\n\ntheResolver = None\ndef getResolver():\n    \"\"\"\n    Get a Resolver instance.\n\n    Create twisted.names.client.theResolver if it is L{None}, and then return\n    that value.\n\n    @rtype: C{IResolver}\n    \"\"\"\n    global theResolver\n    if theResolver is None:\n        try:\n            theResolver = createResolver()\n        except ValueError:\n            theResolver = createResolver(servers=[('127.0.0.1', 53)])\n    return theResolver\n\n\n\ndef getHostByName(name, timeout=None, effort=10):\n    \"\"\"\n    Resolve a name to a valid ipv4 or ipv6 address.\n\n    Will errback with C{DNSQueryTimeoutError} on a timeout, C{DomainError} or\n    C{AuthoritativeDomainError} (or subclasses) on other errors.\n\n    @type name: C{str}\n    @param name: DNS name to resolve.\n\n    @type timeout: Sequence of C{int}\n    @param timeout: Number of seconds after which to reissue the query.\n    When the last timeout expires, the query is considered failed.\n\n    @type effort: C{int}\n    @param effort: How many times CNAME and NS records to follow while\n    resolving this name.\n\n    @rtype: C{Deferred}\n    \"\"\"\n    return getResolver().getHostByName(name, timeout, effort)\n\n\n\ndef query(query, timeout=None):\n    return getResolver().query(query, timeout)\n\n\n\ndef lookupAddress(name, timeout=None):\n    return getResolver().lookupAddress(name, timeout)\n\n\n\ndef lookupIPV6Address(name, timeout=None):\n    return getResolver().lookupIPV6Address(name, timeout)\n\n\n\ndef lookupAddress6(name, timeout=None):\n    return getResolver().lookupAddress6(name, timeout)\n\n\n\ndef lookupMailExchange(name, timeout=None):\n    return getResolver().lookupMailExchange(name, timeout)\n\n\n\ndef lookupNameservers(name, timeout=None):\n    return getResolver().lookupNameservers(name, timeout)\n\n\n\ndef lookupCanonicalName(name, timeout=None):\n    return getResolver().lookupCanonicalName(name, timeout)\n\n\n\ndef lookupMailBox(name, timeout=None):\n    return getResolver().lookupMailBox(name, timeout)\n\n\n\ndef lookupMailGroup(name, timeout=None):\n    return getResolver().lookupMailGroup(name, timeout)\n\n\n\ndef lookupMailRename(name, timeout=None):\n    return getResolver().lookupMailRename(name, timeout)\n\n\n\ndef lookupPointer(name, timeout=None):\n    return getResolver().lookupPointer(name, timeout)\n\n\n\ndef lookupAuthority(name, timeout=None):\n    return getResolver().lookupAuthority(name, timeout)\n\n\n\ndef lookupNull(name, timeout=None):\n    return getResolver().lookupNull(name, timeout)\n\n\n\ndef lookupWellKnownServices(name, timeout=None):\n    return getResolver().lookupWellKnownServices(name, timeout)\n\n\n\ndef lookupService(name, timeout=None):\n    return getResolver().lookupService(name, timeout)\n\n\n\ndef lookupHostInfo(name, timeout=None):\n    return getResolver().lookupHostInfo(name, timeout)\n\n\n\ndef lookupMailboxInfo(name, timeout=None):\n    return getResolver().lookupMailboxInfo(name, timeout)\n\n\n\ndef lookupText(name, timeout=None):\n    return getResolver().lookupText(name, timeout)\n\n\n\ndef lookupSenderPolicy(name, timeout=None):\n    return getResolver().lookupSenderPolicy(name, timeout)\n\n\n\ndef lookupResponsibility(name, timeout=None):\n    return getResolver().lookupResponsibility(name, timeout)\n\n\n\ndef lookupAFSDatabase(name, timeout=None):\n    return getResolver().lookupAFSDatabase(name, timeout)\n\n\n\ndef lookupZone(name, timeout=None):\n    return getResolver().lookupZone(name, timeout)\n\n\n\ndef lookupAllRecords(name, timeout=None):\n    return getResolver().lookupAllRecords(name, timeout)\n\n\n\ndef lookupNamingAuthorityPointer(name, timeout=None):\n    return getResolver().lookupNamingAuthorityPointer(name, timeout)\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/names/common.py",
    "content": "# -*- test-case-name: twisted.names.test -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nBase functionality useful to various parts of Twisted Names.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\nimport socket\n\nfrom zope.interface import implementer\n\nfrom twisted.names import dns\nfrom twisted.names.error import DNSFormatError, DNSServerError, DNSNameError\nfrom twisted.names.error import DNSNotImplementedError, DNSQueryRefusedError\nfrom twisted.names.error import DNSUnknownError\n\nfrom twisted.internet import defer, error, interfaces\n\nfrom twisted.logger import Logger\n\n# Helpers for indexing the three-tuples that get thrown around by this code a\n# lot.\n_ANS, _AUTH, _ADD = range(3)\n\nEMPTY_RESULT = (), (), ()\n\n\n\n@implementer(interfaces.IResolver)\nclass ResolverBase:\n    \"\"\"\n    L{ResolverBase} is a base class for implementations of\n    L{interfaces.IResolver} which deals with a lot\n    of the boilerplate of implementing all of the lookup methods.\n\n    @cvar _errormap: A C{dict} mapping DNS protocol failure response codes\n        to exception classes which will be used to represent those failures.\n    \"\"\"\n    _log = Logger()\n    _errormap = {\n        dns.EFORMAT: DNSFormatError,\n        dns.ESERVER: DNSServerError,\n        dns.ENAME: DNSNameError,\n        dns.ENOTIMP: DNSNotImplementedError,\n        dns.EREFUSED: DNSQueryRefusedError}\n\n    typeToMethod = None\n\n    def __init__(self):\n        self.typeToMethod = {}\n        for (k, v) in typeToMethod.items():\n            self.typeToMethod[k] = getattr(self, v)\n\n\n    def exceptionForCode(self, responseCode):\n        \"\"\"\n        Convert a response code (one of the possible values of\n        L{dns.Message.rCode} to an exception instance representing it.\n\n        @since: 10.0\n        \"\"\"\n        return self._errormap.get(responseCode, DNSUnknownError)\n\n\n    def query(self, query, timeout=None):\n        try:\n            method = self.typeToMethod[query.type]\n        except KeyError:\n            self._log.debug(\n                'Query of unknown type {query.type} for {query.name.name!r}',\n                query=query)\n            return defer.maybeDeferred(\n                self._lookup, query.name.name, dns.IN, query.type, timeout)\n        else:\n            return defer.maybeDeferred(method, query.name.name, timeout)\n\n\n    def _lookup(self, name, cls, type, timeout):\n        return defer.fail(NotImplementedError(\"ResolverBase._lookup\"))\n\n\n    def lookupAddress(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.A, timeout)\n\n\n    def lookupIPV6Address(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.AAAA, timeout)\n\n\n    def lookupAddress6(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.A6, timeout)\n\n\n    def lookupMailExchange(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.MX, timeout)\n\n\n    def lookupNameservers(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.NS, timeout)\n\n\n    def lookupCanonicalName(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.CNAME, timeout)\n\n\n    def lookupMailBox(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.MB, timeout)\n\n\n    def lookupMailGroup(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.MG, timeout)\n\n\n    def lookupMailRename(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.MR, timeout)\n\n\n    def lookupPointer(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.PTR, timeout)\n\n\n    def lookupAuthority(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.SOA, timeout)\n\n\n    def lookupNull(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.NULL, timeout)\n\n\n    def lookupWellKnownServices(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.WKS, timeout)\n\n\n    def lookupService(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.SRV, timeout)\n\n\n    def lookupHostInfo(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.HINFO, timeout)\n\n\n    def lookupMailboxInfo(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.MINFO, timeout)\n\n\n    def lookupText(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.TXT, timeout)\n\n\n    def lookupSenderPolicy(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.SPF, timeout)\n\n\n    def lookupResponsibility(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.RP, timeout)\n\n\n    def lookupAFSDatabase(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.AFSDB, timeout)\n\n\n    def lookupZone(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.AXFR, timeout)\n\n\n    def lookupNamingAuthorityPointer(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.NAPTR, timeout)\n\n\n    def lookupAllRecords(self, name, timeout=None):\n        return self._lookup(name, dns.IN, dns.ALL_RECORDS, timeout)\n\n\n    # IResolverSimple\n    def getHostByName(self, name, timeout=None, effort=10):\n        # XXX - respect timeout\n        return self.lookupAllRecords(name, timeout\n            ).addCallback(self._cbRecords, name, effort\n            )\n\n\n    def _cbRecords(self, records, name, effort):\n        (ans, auth, add) = records\n        result = extractRecord(self, dns.Name(name), ans + auth + add, effort)\n        if not result:\n            raise error.DNSLookupError(name)\n        return result\n\n\n\ndef extractRecord(resolver, name, answers, level=10):\n    if not level:\n        return None\n    if hasattr(socket, 'inet_ntop'):\n        for r in answers:\n            if r.name == name and r.type == dns.A6:\n                return socket.inet_ntop(socket.AF_INET6, r.payload.address)\n        for r in answers:\n            if r.name == name and r.type == dns.AAAA:\n                return socket.inet_ntop(socket.AF_INET6, r.payload.address)\n    for r in answers:\n        if r.name == name and r.type == dns.A:\n            return socket.inet_ntop(socket.AF_INET, r.payload.address)\n    for r in answers:\n        if r.name == name and r.type == dns.CNAME:\n            result = extractRecord(\n                resolver, r.payload.name, answers, level - 1)\n            if not result:\n                return resolver.getHostByName(\n                    str(r.payload.name), effort=level - 1)\n            return result\n    # No answers, but maybe there's a hint at who we should be asking about\n    # this\n    for r in answers:\n        if r.type == dns.NS:\n            from twisted.names import client\n            r = client.Resolver(servers=[(str(r.payload.name), dns.PORT)])\n            return r.lookupAddress(str(name)\n                ).addCallback(\n                    lambda records: extractRecord(\n                        r, name,\n                        records[_ANS] + records[_AUTH] + records[_ADD],\n                        level - 1))\n\n\n\ntypeToMethod = {\n    dns.A:     'lookupAddress',\n    dns.AAAA:  'lookupIPV6Address',\n    dns.A6:    'lookupAddress6',\n    dns.NS:    'lookupNameservers',\n    dns.CNAME: 'lookupCanonicalName',\n    dns.SOA:   'lookupAuthority',\n    dns.MB:    'lookupMailBox',\n    dns.MG:    'lookupMailGroup',\n    dns.MR:    'lookupMailRename',\n    dns.NULL:  'lookupNull',\n    dns.WKS:   'lookupWellKnownServices',\n    dns.PTR:   'lookupPointer',\n    dns.HINFO: 'lookupHostInfo',\n    dns.MINFO: 'lookupMailboxInfo',\n    dns.MX:    'lookupMailExchange',\n    dns.TXT:   'lookupText',\n    dns.SPF:   'lookupSenderPolicy',\n\n    dns.RP:    'lookupResponsibility',\n    dns.AFSDB: 'lookupAFSDatabase',\n    dns.SRV:   'lookupService',\n    dns.NAPTR: 'lookupNamingAuthorityPointer',\n    dns.AXFR:         'lookupZone',\n    dns.ALL_RECORDS:  'lookupAllRecords',\n}\n"
  },
  {
    "path": "stackoverflow/venv/lib/python3.6/site-packages/twisted/names/dns.py",
    "content": "# -*- test-case-name: twisted.names.test.test_dns -*-\n# Copyright (c) Twisted Matrix Laboratories.\n# See LICENSE for details.\n\n\"\"\"\nDNS protocol implementation.\n\nFuture Plans:\n    - Get rid of some toplevels, maybe.\n\"\"\"\n\nfrom __future__ import division, absolute_import\n\n__all__ = [\n    'IEncodable', 'IRecord',\n\n    'A', 'A6', 'AAAA', 'AFSDB', 'CNAME', 'DNAME', 'HINFO',\n    'MAILA', 'MAILB', 'MB', 'MD', 'MF', 'MG', 'MINFO', 'MR', 'MX',\n    'NAPTR', 'NS', 'NULL', 'OPT', 'PTR', 'RP', 'SOA', 'SPF', 'SRV', 'TXT',\n    'SSHFP', 'TSIG', 'WKS',\n\n    'ANY', 'CH', 'CS', 'HS', 'IN',\n\n    'ALL_RECORDS', 'AXFR', 'IXFR',\n\n    'EFORMAT', 'ENAME', 'ENOTIMP', 'EREFUSED', 'ESERVER', 'EBADVERSION',\n    'EBADSIG', 'EBADKEY', 'EBADTIME',\n\n    'Record_A', 'Record_A6', 'Record_AAAA', 'Record_AFSDB', 'Record_CNAME',\n    'Record_DNAME', 'Record_HINFO', 'Record_MB', 'Record_MD', 'Record_MF',\n    'Record_MG', 'Record_MINFO', 'Record_MR', 'Record_MX', 'Record_NAPTR',\n    'Record_NS', 'Record_NULL', 'Record_PTR', 'Record_RP', 'Record_SOA',\n    'Record_SPF', 'Record_SRV', 'Record_SSHFP', 'Record_TSIG', 'Record_TXT',\n    'Record_WKS',\n    'UnknownRecord',\n\n    'QUERY_CLASSES', 'QUERY_TYPES', 'REV_CLASSES', 'REV_TYPES', 'EXT_QUERIES',\n\n    'Charstr', 'Message', 'Name', 'Query', 'RRHeader', 'SimpleRecord',\n    'DNSDatagramProtocol', 'DNSMixin', 'DNSProtocol',\n\n    'OK', 'OP_INVERSE', 'OP_NOTIFY', 'OP_QUERY', 'OP_STATUS', 'OP_UPDATE',\n    'PORT',\n\n    'AuthoritativeDomainError', 'DNSQueryTimeoutError', 'DomainError',\n    ]\n\n\n# System imports\nimport inspect, struct, random, socket\nfrom itertools import chain\n\nfrom io import BytesIO\n\nAF_INET6 = socket.AF_INET6\n\nfrom zope.interface import implementer, Interface, Attribute\n\n\n# Twisted imports\nfrom twisted.internet import protocol, defer\nfrom twisted.internet.error import CannotListenError\nfrom twisted.python import log, failure\nfrom twisted.python import util as tputil\nfrom twisted.python import randbytes\nfrom twisted.python.compat import _PY3, unicode, comparable, cmp, nativeString\n\n\nif _PY3:\n    def _ord2bytes(ordinal):\n        \"\"\"\n        Construct a bytes object representing a single byte with the given\n        ordinal value.\n\n        @type ordinal: L{int}\n        @rtype: L{bytes}\n        \"\"\"\n        return bytes([ordinal])\n\n\n    def _nicebytes(bytes):\n        \"\"\"\n        Represent a mostly textful bytes object in a way suitable for presentation\n        to an end user.\n\n        @param bytes: The bytes to represent.\n        @rtype: L{str}\n        \"\"\"\n        return repr(bytes)[1:]\n\n\n    def _nicebyteslist(list):\n        \"\"\"\n        Represent a list of mostly textful bytes objects in a way suitable for\n        presentation to an end user.\n\n        @param list: The list of bytes to represent.\n        @rtype: L{str}\n        \"\"\"\n        return '[%s]' % (\n            ', '.join([_nicebytes(b) for b in list]),)\nelse:\n    _ord2bytes = chr\n    _nicebytes = _nicebyteslist = repr\n\n\n\ndef randomSource():\n    \"\"\"\n    Wrapper around L{twisted.python.randbytes.RandomFactory.secureRandom} to return\n    2 random chars.\n    \"\"\"\n    return struct.unpack('H', randbytes.secureRandom(2, fallback=True))[0]\n\n\nPORT = 53\n\n(A, NS, MD, MF, CNAME, SOA, MB, MG, MR, NULL, WKS, PTR, HINFO, MINFO, MX, TXT,\n RP, AFSDB) = range(1, 19)\nAAAA = 28\nSRV = 33\nNAPTR = 35\nA6 = 38\nDNAME = 39\nOPT = 41\nSSHFP = 44\nSPF = 99\n\n# These record types do not exist in zones, but are transferred in\n# messages the same way normal RRs are.\nTKEY = 249\nTSIG = 250\n\nQUERY_TYPES = {\n    A: 'A',\n    NS: 'NS',\n    MD: 'MD',\n    MF: 'MF',\n    CNAME: 'CNAME',\n    SOA: 'SOA',\n    MB: 'MB',\n    MG: 'MG',\n    MR: 'MR',\n    NULL: 'NULL',\n    WKS: 'WKS',\n    PTR: 'PTR',\n    HINFO: 'HINFO',\n    MINFO: 'MINFO',\n    MX: 'MX',\n    TXT: 'TXT',\n    RP: 'RP',\n    AFSDB: 'AFSDB',\n\n    # 19 through 27?  Eh, I'll get to 'em.\n\n    AAAA: 'AAAA',\n    SRV: 'SRV',\n    NAPTR: 'NAPTR',\n    A6: 'A6',\n    DNAME: 'DNAME',\n    OPT: 'OPT',\n    SSHFP: 'SSHFP',\n    SPF: 'SPF',\n\n    TKEY: 'TKEY',\n    TSIG: 'TSIG',\n}\n\nIXFR, AXFR, MAILB, MAILA, ALL_RECORDS = range(251, 256)\n\n# \"Extended\" queries (Hey, half of these are deprecated, good job)\nEXT_QUERIES = {\n    IXFR: 'IXFR',\n    AXFR: 'AXFR',\n    MAILB: 'MAILB',\n    MAILA: 'MAILA',\n    ALL_RECORDS: 'ALL_RECORDS'\n}\n\nREV_TYPES = dict([\n    (v, k) for (k, v) in chain(QUERY_TYPES.items(), EXT_QUERIES.items())\n])\n\nIN, CS, CH, HS = range(1, 5)\nANY = 255\n\nQUERY_CLASSES = {\n    IN: 'IN',\n    CS: 'CS',\n    CH: 'CH',\n    HS: 'HS',\n    ANY: 'ANY'\n}\nREV_CLASSES = dict([\n    (v, k) for (k, v) in QUERY_CLASSES.items()\n])\n\n\n# Opcodes\nOP_QUERY, OP_INVERSE, OP_STATUS = range(3)\nOP_NOTIFY = 4 # RFC 1996\nOP_UPDATE = 5 # RFC 2136\n\n\n# Response Codes\nOK, EFORMAT, ESERVER, ENAME, ENOTIMP, EREFUSED = range(6)\n# https://tools.ietf.org/html/rfc6891#section-9\nEBADVERSION = 16\n# RFC 2845\nEBADSIG, EBADKEY, EBADTIME = range(16, 19)\n\n\n\nclass IRecord(Interface):\n    \"\"\"\n    A single entry in a zone of authority.\n    \"\"\"\n\n    TYPE = Attribute(\"An indicator of what kind of record this is.\")\n\n\n# Backwards compatibility aliases - these should be deprecated or something I\n# suppose. -exarkun\nfrom twisted.names.error import DomainError, AuthoritativeDomainError\nfrom twisted.names.error import DNSQueryTimeoutError\n\n\n\ndef _nameToLabels(name):\n    \"\"\"\n    Split a domain name into its constituent labels.\n\n    @type name: L{bytes}\n    @param name: A fully qualified domain name (with or without a\n        trailing dot).\n\n    @return: A L{list} of labels ending with an empty label\n        representing the DNS root zone.\n    \"\"\"\n    if name in (b'', b'.'):\n        return [b'']\n    labels = name.split(b'.')\n    if labels[-1] != b'':\n        labels.append(b'')\n    return labels\n\n\n\ndef _isSubdomainOf(descendantName, ancestorName):\n    \"\"\"\n    Test whether C{descendantName} is equal to or is a I{subdomain} of\n    C{ancestorName}.\n\n    The names are compared case-insensitively.\n\n    The names are treated as byte strings containing one or more\n    DNS labels separated by B{.}.\n\n    C{descendantName} is considered equal if its sequence of labels\n    exactly matches the labels of C{ancestorName}.\n\n    C{descendantName} is considered a I{subdomain} if its sequence of\n    labels ends with the labels of C{ancestorName}.\n\n    @type descendantName: L{bytes}\n    @param descendantName: The DNS subdomain name.\n\n    @type ancestorName: L{bytes}\n    @param ancestorName: The DNS parent or ancestor domain name.\n\n    @return: C{True} if C{descendantName} is equal to or if it is a\n        subdomain of C{ancestorName}. Otherwise returns C{False}.\n    \"\"\"\n    descendantLabels = _nameToLabels(descendantName.lower())\n    ancestorLabels = _nameToLabels(ancestorName.lower())\n    return descendantLabels[-len(ancestorLabels):] == ancestorLabels\n\n\n\ndef str2time(s):\n    \"\"\"\n    Parse a string description of an interval into an integer number of seconds.\n\n    @param s: An interval definition constructed as an interval duration\n        followed by an interval unit.  An interval duration is a base ten\n        representation of an integer.  An interval unit is one of the following\n        letters: S (seconds), M (minutes), H (hours), D (days), W (weeks), or Y\n        (years).  For example: C{\"3S\"} indicates an interval of three seconds;\n        C{\"5D\"} indicates an interval of five days.  Alternatively, C{s} may be\n        any non-string and it will be returned unmodified.\n    @type s: text string (L{bytes} or L{unicode}) for parsing; anything else\n        for passthrough.\n\n    @return: an L{int} giving the interval represented by the string C{s}, or\n        whatever C{s} is if it is not a string.\n    \"\"\"\n    suffixes = (\n        ('S', 1), ('M', 60), ('H', 60 * 60), ('D', 60 * 60 * 24),\n        ('W', 60 * 60 * 24 * 7), ('Y', 60 * 60 * 24 * 365)\n    )\n    if _PY3 and isinstance(s, bytes):\n        s = s.decode('ascii')\n\n    if isinstance(s, str):\n        s = s.upper().strip()\n        for (suff, mult) in suffixes:\n            if s.endswith(suff):\n                return int(float(s[:-1]) * mult)\n        try:\n            s = int(s)\n        except ValueError:\n            raise ValueError(\"Invalid time interval specifier: \" + s)\n    return s\n\n\ndef readPrecisely(file, l):\n    buff = file.read(l)\n    if len(buff) < l:\n        raise EOFError\n    return buff\n\n\nclass IEncodable(Interface):\n    \"\"\"\n    Interface for something which can be encoded to and decoded\n    from a file object.\n    \"\"\"\n\n    def encode(strio, compDict = None):\n        \"\"\"\n        Write a representation of this object to the given\n        file object.\n\n        @type strio: File-like object\n        @param strio: The stream to which to write bytes\n\n        @type compDict: C{dict} or L{None}\n        @param compDict: A dictionary of backreference addresses that have\n        already been written to this stream and that may be used for\n        compression.\n        \"\"\"\n\n    def decode(strio, length = None):\n        \"\"\"\n        Reconstruct an object from data read from the given\n        file object.\n\n        @type strio: File-like object\n        @param strio: The stream from which bytes may be read\n\n        @type length: L{int} or L{None}\n        @param length: The number of bytes in this RDATA field.  Most\n        implementations can ignore this value.  Only in the case of\n        records similar to TXT where the total length is in no way\n        encoded in the data is it necessary.\n        \"\"\"\n\n\n\n@implementer(IEncodable)\nclass Charstr(object):\n\n    def __init__(self, string=b''):\n        if not isinstance(string, bytes):\n            raise ValueError(\"%r is not a byte string\" % (string,))\n        self.string = string\n\n\n    def encode(self, strio, compDict=None):\n        \"\"\"\n        Encode this Character string into the appropriate byte format.\n\n        @type strio: file\n        @param strio: The byte representation of this Charstr will be written\n            to this file.\n        \"\"\"\n        string = self.string\n        ind = len(string)\n        strio.write(_ord2bytes(ind))\n        strio.write(string)\n\n\n    def decode(self, strio, length=None):\n        \"\"\"\n        Decode a byte string into this Charstr.\n\n        @type strio: file\n        @param strio: Bytes will be read from this file until the full string\n            is decoded.\n\n        @raise EOFError: Raised when there are not enough bytes available from\n            C{strio}.\n        \"\"\"\n        self.string = b''\n        l = ord(readPrecisely(strio, 1))\n        self.string = readPrecisely(strio, l)\n\n\n    def __eq__(self, other):\n        if isinstance(other, Charstr):\n            return self.string == other.string\n        return NotImplemented\n\n\n    def __ne__(self, other):\n        if isinstance(other, Charstr):\n            return self.string != other.string\n        return NotImplemented\n\n\n    def __hash__(self):\n        return hash(self.string)\n\n\n    def __str__(self):\n        \"\"\"\n        Represent this L{Charstr} instance by its string value.\n        \"\"\"\n        return nativeString(self.string)\n\n\n\n@implementer(IEncodable)\nclass Name:\n    \"\"\"\n    A name in the domain name system, made up of multiple labels.  For example,\n    I{twistedmatrix.com}.\n\n    @ivar name: A byte string giving the name.\n    @type name: L{bytes}\n    \"\"\"\n    def __init__(self, name=b''):\n        \"\"\"\n        @param name: A name.\n        @type name: L{unicode} or L{bytes}\n        \"\"\"\n        if isinstance(name, unicode):\n            name = name.encode('idna')\n        if not isinstance(name, bytes):\n            raise TypeError(\"%r is not a byte string\" % (name,))\n        self.name = name\n\n\n    def encode(self, strio, compDict=None):\n        \"\"\"\n        Encode this Name into the appropriate byte format.\n\n        @type strio: file\n        @param strio: The byte representation of this Name will be written to\n        this file.\n\n        @type compDict: dict\n        @param compDict: dictionary of Names that have already been encoded\n        and whose addresses may be backreferenced by this Name (for the purpose\n        of reducing the message size).\n        \"\"\"\n        name = self.name\n        while name:\n            if compDict is not None:\n                if name in compDict:\n                    strio.write(\n                        struct.pack(\"!H\", 0xc000 | compDict[name]))\n                    return\n                else:\n                    compDict[name] = strio.tell() + Message.headerSize\n            ind = name.find(b'.')\n            if ind > 0:\n                label, name = name[:ind], name[ind + 1:]\n            else:\n                # This is the last label, end the loop after handling it.\n                label = name\n                name = None\n                ind = len(label)\n            strio.write(_ord2bytes(ind))\n            strio.write(label)\n        strio.write(b'\\x00')\n\n\n    def decode(self, strio, length=None):\n        \"\"\"\n        Decode a byte string into this Name.\n\n        @type strio: file\n        @param strio: Bytes will be read from this file until the full Name\n        is decoded.\n\n        @raise EOFError: Raised when there are not enough bytes available\n        from C{strio}.\n\n        @raise ValueError: Raised when the name cannot be decoded (for example,\n            because it contains a loop).\n        \"\"\"\n        visited = set()\n        self.name = b''\n        off = 0\n        while 1:\n            l = ord(readPrecisely(strio, 1))\n            if l == 0:\n                if off > 0:\n                    strio.seek(off)\n                return\n            if (l >> 6) == 3:\n                new_off = ((l&63) << 8\n                            | ord(readPrecisely(strio, 1)))\n                if new_off in visited:\n                    raise ValueError(\"Compression loop in encoded name\")\n                visited.add(new_off)\n                if off == 0:\n                    off = strio.tell()\n                strio.seek(new_off)\n                continue\n            label = readPrecisely(strio, l)\n            if self.name == b'':\n                self.name = label\n            else:\n                self.name = self.name + b'.' + label\n\n    def __eq__(self, other):\n        if isinstance(other, Name):\n            return self.name.lower() == other.name.lower()\n        return NotImplemented\n\n\n    def __ne__(self, other):\n        if isinstance(other, Name):\n            return self.name.lower() != other.name.lower()\n        return NotImplemented\n\n\n    def __hash__(self):\n        return hash(self.name)\n\n\n    def __str__(self):\n        \"\"\"\n        Represent this L{Name} instance by its string name.\n        \"\"\"\n        return nativeString(self.name)\n\n\n\n@comparable\n@implementer(IEncodable)\nclass Query:\n    \"\"\"\n    Represent a single DNS query.\n\n    @ivar name: The name about which this query is requesting information.\n    @type name: L{Name}\n\n    @ivar type: The query type.\n    @type type: L{int}\n\n    @ivar cls: The query class.\n    @type cls: L{int}\n    \"\"\"\n    name = None\n    type = None\n    cls = None\n\n    def __init__(self, name=b'', type=A, cls=IN):\n        \"\"\"\n        @type name: L{bytes} or L{unicode}\n        @param name: See L{Query.name}\n\n        @type type: L{int}\n        @param type: The query type.\n\n        @type cls: L{int}\n        @param cls: The query class.\n        \"\"\"\n        self.name = Name(name)\n        self.type = type\n        self.cls = cls\n\n\n    def encode(self, strio, compDict=None):\n        self.name.encode(strio, compDict)\n        strio.write(struct.pack(\"!HH\", self.type, self.cls))\n\n\n    def decode(self, strio, length = None):\n        self.name.decode(strio)\n        buff = readPrecisely(strio, 4)\n        self.type, self.cls = struct.unpack(\"!HH\", buff)\n\n\n    def __hash__(self):\n        return hash((str(self.name).lower(), self.type, self.cls))\n\n\n    def __cmp__(self, other):\n        if isinstance(other, Query):\n            return cmp(\n                (str(self.name).lower(), self.type, self.cls),\n                (str(other.name).lower(), other.type, other.cls))\n        return NotImplemented\n\n\n    def __str__(self):\n        t = QUERY_TYPES.get(self.type, EXT_QUERIES.get(self.type, 'UNKNOWN (%d)' % self.type))\n        c = QUERY_CLASSES.get(self.cls, 'UNKNOWN (%d)' % self.cls)\n        return '<Query %s %s %s>' % (self.name, t, c)\n\n\n    def __repr__(self):\n        return 'Query(%r, %r, %r)' % (str(self.name), self.type, self.cls)\n\n\n\n@implementer(IEncodable)\nclass _OPTHeader(tputil.FancyStrMixin, tputil.FancyEqMixin, object):\n    \"\"\"\n    An OPT record header.\n\n    @ivar name: The DNS name associated with this record. Since this\n        is a pseudo record, the name is always an L{Name} instance\n        with value b'', which represents the DNS root zone. This\n        attribute is a readonly property.\n\n    @ivar type: The DNS record type. This is a fixed value of 41\n        C{dns.OPT} for OPT Record. This attribute is a readonly\n        property.\n\n    @see: L{_OPTHeader.__init__} for documentation of other public\n        instance attributes.\n\n    @see: U{https://tools.ietf.org/html/rfc6891#section-6.1.2}\n\n    @since: 13.2\n    \"\"\"\n    showAttributes = (\n        ('name', lambda n: nativeString(n.name)), 'type', 'udpPayloadSize',\n        'extendedRCODE', 'version', 'dnssecOK', 'options')\n\n    compareAttributes = (\n        'name', 'type', 'udpPayloadSize', 'extendedRCODE', 'version',\n        'dnssecOK', 'options')\n\n    def __init__(self, udpPayloadSize=4096, extendedRCODE=0, version=0,\n                 dnssecOK=False, options=None):\n        \"\"\"\n        @type udpPayloadSize: L{int}\n        @param payload: The number of octets of the largest UDP\n            payload that can be reassembled and delivered in the\n            requestor's network stack.\n\n        @type extendedRCODE: L{int}\n        @param extendedRCODE: Forms the upper 8 bits of extended\n            12-bit RCODE (together with the 4 bits defined in\n            [RFC1035].  Note that EXTENDED-RCODE value 0 indicates\n            that an unextended RCODE is in use (values 0 through 15).\n\n        @type version: L{int}\n        @param version: Indicates the implementation level of the\n            setter.  Full conformance with this specification is\n            indicated by version C{0}.\n\n        @type dnssecOK: L{bool}\n        @param dnssecOK: DNSSEC OK bit as defined by [RFC3225].\n\n        @type options: L{list}\n        @param options: A L{list} of 0 or more L{_OPTVariableOption}\n            instances.\n        \"\"\"\n        self.udpPayloadSize = udpPayloadSize\n        self.extendedRCODE = extendedRCODE\n        self.version = version\n        self.dnssecOK = dnssecOK\n\n        if options is None:\n            options = []\n        self.options = options\n\n\n    @property\n    def name(self):\n        \"\"\"\n        A readonly property for accessing the C{name} attribute of\n        this record.\n\n        @return: The DNS name associated with this record. Since this\n            is a pseudo record, the name is always an L{Name} instance\n            with value b'', which represents the DNS root zone.\n        \"\"\"\n        return Name(b'')\n\n\n    @property\n    def type(self):\n        \"\"\"\n        A readonly property for accessing the C{type} attribute of\n        this record.\n\n        @return: The DNS record type. This is a fixed value of 41\n            (C{dns.OPT} for OPT Record.\n        \"\"\"\n        return OPT\n\n\n    def encode(self, strio, compDict=None):\n        \"\"\"\n        Encode this L{_OPTHeader} instance to bytes.\n\n        @type strio: L{file}\n        @param strio: the byte representation of this L{_OPTHeader}\n            will be written to this file.\n\n        @type compDict: L{dict} or L{None}\n        @param compDict: A dictionary of backreference addresses that\n            have already been written to this stream and that may\n            be used for DNS name compression.\n        \"\"\"\n        b = BytesIO()\n        for o in self.options:\n            o.encode(b)\n        optionBytes = b.getvalue()\n\n        RRHeader(\n            name=self.name.name,\n            type=self.type,\n            cls=self.udpPayloadSize,\n            ttl=(\n                self.extendedRCODE << 24\n                | self.version << 16\n                | self.dnssecOK << 15),\n            payload=UnknownRecord(optionBytes)\n        ).encode(strio, compDict)\n\n\n    def decode(self, strio, length=None):\n        \"\"\"\n        Decode bytes into an L{_OPTHeader} instance.\n\n        @type strio: L{file}\n        @param strio: Bytes will be read from this file until the full\n            L{_OPTHeader} is decoded.\n\n        @type length: L{int} or L{None}\n        @param length: Not used.\n        \"\"\"\n\n        h = RRHeader()\n        h.decode(strio, length)\n        h.payload = UnknownRecord(readPrecisely(strio, h.rdlength))\n\n        newOptHeader = self.fromRRHeader(h)\n\n        for attrName in self.compareAttributes:\n            if attrName not in ('name', 'type'):\n                setattr(self, attrName, getattr(newOptHeader, attrName))\n\n\n    @classmethod\n    def fromRRHeader(cls, rrHeader):\n        \"\"\"\n        A classmethod for constructing a new L{_OPTHeader} from the\n        attributes and payload of an existing L{RRHeader} instance.\n\n        @type rrHeader: L{RRHeader}\n        @param rrHeader: An L{RRHeader} instance containing an\n            L{UnknownRecord} payload.\n\n        @return: An instance of L{_OPTHeader}.\n        @rtype: L{_OPTHeader}\n        \"\"\"\n        options = None\n        if rrHeader.payload is not None:\n            options = []\n            optionsBytes = BytesIO(rrHeader.payload.data)\n            optionsBytesLength = len(rrHeader.payload.data)\n            while optionsBytes.tell() < optionsBytesLength:\n                o = _OPTVariableOption()\n                o.decode(optionsBytes)\n                options.append(o)\n\n        # Decode variable options if present\n        return cls(\n            udpPayloadSize=rrHeader.cls,\n            extendedRCODE=rrHeader.ttl >> 24,\n            version=rrHeader.ttl >> 16 & 0xff,\n            dnssecOK=(rrHeader.ttl & 0xffff) >> 15,\n            options=options\n            )\n\n\n\n@implementer(IEncodable)\nclass _OPTVariableOption(tputil.FancyStrMixin, tputil.FancyEqMixin, object):\n    \"\"\"\n    A class to represent OPT record variable options.\n\n    @see: L{_OPTVariableOption.__init__} for documentation of public\n        instance attributes.\n\n    @see: U{https://tools.ietf.org/html/rfc6891#section-6.1.2}\n\n    @since: 13.2\n    \"\"\"\n    showAttributes = ('code', ('data', nativeString))\n    compareAttributes = ('code', 'data')\n\n    _fmt = '!HH'\n\n    def __init__(self, code=0, data=b''):\n        \"\"\"\n        @type code: L{int}\n        @param code: The option code\n\n        @type data: L{bytes}\n        @param data: The option data\n        \"\"\"\n        self.code = code\n        self.data = data\n\n\n    def encode(self, strio, compDict=None):\n        \"\"\"\n        Encode this L{_OPTVariableOption} to bytes.\n\n        @type strio: L{file}\n        @param strio: the byte representation of this\n            L{_OPTVariableOption} will be written to this file.\n\n        @type compDict: L{dict} or L{None}\n        @param compDict: A dictionary of backreference addresses that\n            have already been written to this stream and that may\n            be used for DNS name compression.\n        \"\"\"\n        strio.write(\n            struct.pack(self._fmt, self.code, len(self.data)) + self.data)\n\n\n    def decode(self, strio, length=None):\n        \"\"\"\n        Decode bytes into an L{_OPTVariableOption} instance.\n\n        @type strio: L{file}\n        @param strio: Bytes will be read from this file until the full\n            L{_OPTVariableOption} is decoded.\n\n        @type length: L{int} or L{None}\n        @param length: Not used.\n        \"\"\"\n        l = struct.calcsize(self._fmt)\n        buff = readPrecisely(strio, l)\n        self.code, length = struct.unpack(self._fmt, buff)\n        self.data = readPrecisely(strio, length)\n\n\n\n@implementer(IEncodable)\nclass RRHeader(tputil.FancyEqMixin):\n    \"\"\"\n    A resource record header.\n\n    @cvar fmt: L{str} specifying the byte format of an RR.\n\n    @ivar name: The name about which this reply contains information.\n    @type name: L{Name}\n\n    @ivar type: The query type of the original request.\n    @type type: L{int}\n\n    @ivar cls: The query class of the original request.\n\n    @ivar ttl: The time-to-live for this record.\n    @type ttl: L{int}\n\n    @ivar payload: An object that implements the L{IEncodable} interface\n\n    @ivar auth: A L{bool} indicating whether this C{RRHeader} was parsed from\n        an authoritative message.\n    \"\"\"\n    compareAttributes = ('name', 'type', 'cls', 'ttl', 'payload', 'auth')\n\n    fmt = \"!HHIH\"\n\n    name = None\n    type = None\n    cls = None\n    ttl = None\n    payload = None\n    rdlength = None\n\n    cachedResponse = None\n\n    def __init__(self, name=b'', type=A, cls=IN, ttl=0, payload=None,\n                 auth=False):\n        \"\"\"\n        @type name: L{bytes} or L{unicode}\n        @param name: See L{RRHeader.name}\n\n        @type type: L{int}\n        @param type: The query type.\n\n        @type cls: L{int}\n        @param cls: The query class.\n\n        @type ttl: L{int}\n        @param ttl: Time to live for this record.  This will be\n            converted to an L{int}.\n\n        @type payload: An object implementing C{IEncodable}\n        @param payload: A Query Type specific data object.\n\n        @raises TypeError: if the ttl cannot be converted to an L{int}.\n        @raises ValueError: if the ttl is negative.\n        \"\"\"\n        assert (payload is None) or isinstance(payload, UnknownRecord) or (payload.TYPE == type)\n\n        integralTTL = int(ttl)\n\n        if integralTTL < 0:\n            raise ValueError(\"TTL cannot be negative\")\n\n        self.name = Name(name)\n        self.type = type\n        self.cls = cls\n        self.ttl = integralTTL\n        self.payload = payload\n        self.auth = auth\n\n\n    def encode(self, strio, compDict=None):\n        self.name.encode(strio, compDict)\n        strio.write(struct.pack(self.fmt, self.type, self.cls, self.ttl, 0))\n        if self.payload:\n            prefix = strio.tell()\n            self.payload.encode(strio, compDict)\n            aft = strio.tell()\n            strio.seek(prefix - 2, 0)\n            strio.write(struct.pack('!H', aft - prefix))\n            strio.seek(aft, 0)\n\n\n    def decode(self, strio, length = None):\n        self.name.decode(strio)\n        l = struct.calcsize(self.fmt)\n        buff = readPrecisely(strio, l)\n        r = struct.unpack(self.fmt, buff)\n        self.type, self.cls, self.ttl, self.rdlength = r\n\n\n    def isAuthoritative(self):\n        return self.auth\n\n\n    def __str__(self):\n        t = QUERY_TYPES.get(self.type, EXT_QUERIES.get(self.type, 'UNKNOWN (%d)' % self.type))\n        c = QUERY_CLASSES.get(self.cls, 'UNKNOWN (%d)' % self.cls)\n        return '<RR name=%s type=%s class=%s ttl=%ds auth=%s>' % (self.name, t, c, self.ttl, self.auth and 'True' or 'False')\n\n\n    __repr__ = __str__\n\n\n\n@implementer(IEncodable, IRecord)\nclass SimpleRecord(tputil.FancyStrMixin, tputil.FancyEqMixin):\n    \"\"\"\n    A Resource Record which consists of a single RFC 1035 domain-name.\n\n    @type name: L{Name}\n    @ivar name: The name associated with this record.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n    \"\"\"\n    showAttributes = (('name', 'name', '%s'), 'ttl')\n    compareAttributes = ('name', 'ttl')\n\n    TYPE = None\n    name = None\n\n    def __init__(self, name=b'', ttl=None):\n        \"\"\"\n        @param name: See L{SimpleRecord.name}\n        @type name: L{bytes} or L{unicode}\n        \"\"\"\n        self.name = Name(name)\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict = None):\n        self.name.encode(strio, compDict)\n\n\n    def decode(self, strio, length = None):\n        self.name = Name()\n        self.name.decode(strio)\n\n\n    def __hash__(self):\n        return hash(self.name)\n\n\n# Kinds of RRs - oh my!\nclass Record_NS(SimpleRecord):\n    \"\"\"\n    An authoritative nameserver.\n    \"\"\"\n    TYPE = NS\n    fancybasename = 'NS'\n\n\n\nclass Record_MD(SimpleRecord):\n    \"\"\"\n    A mail destination.\n\n    This record type is obsolete.\n\n    @see: L{Record_MX}\n    \"\"\"\n    TYPE = MD\n    fancybasename = 'MD'\n\n\n\nclass Record_MF(SimpleRecord):\n    \"\"\"\n    A mail forwarder.\n\n    This record type is obsolete.\n\n    @see: L{Record_MX}\n    \"\"\"\n    TYPE = MF\n    fancybasename = 'MF'\n\n\n\nclass Record_CNAME(SimpleRecord):\n    \"\"\"\n    The canonical name for an alias.\n    \"\"\"\n    TYPE = CNAME\n    fancybasename = 'CNAME'\n\n\n\nclass Record_MB(SimpleRecord):\n    \"\"\"\n    A mailbox domain name.\n\n    This is an experimental record type.\n    \"\"\"\n    TYPE = MB\n    fancybasename = 'MB'\n\n\n\nclass Record_MG(SimpleRecord):\n    \"\"\"\n    A mail group member.\n\n    This is an experimental record type.\n    \"\"\"\n    TYPE = MG\n    fancybasename = 'MG'\n\n\n\nclass Record_MR(SimpleRecord):\n    \"\"\"\n    A mail rename domain name.\n\n    This is an experimental record type.\n    \"\"\"\n    TYPE = MR\n    fancybasename = 'MR'\n\n\n\nclass Record_PTR(SimpleRecord):\n    \"\"\"\n    A domain name pointer.\n    \"\"\"\n    TYPE = PTR\n    fancybasename = 'PTR'\n\n\n\nclass Record_DNAME(SimpleRecord):\n    \"\"\"\n    A non-terminal DNS name redirection.\n\n    This record type provides the capability to map an entire subtree of the\n    DNS name space to another domain.  It differs from the CNAME record which\n    maps a single node of the name space.\n\n    @see: U{http://www.faqs.org/rfcs/rfc2672.html}\n    @see: U{http://www.faqs.org/rfcs/rfc3363.html}\n    \"\"\"\n    TYPE = DNAME\n    fancybasename = 'DNAME'\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_A(tputil.FancyEqMixin):\n    \"\"\"\n    An IPv4 host address.\n\n    @type address: L{bytes}\n    @ivar address: The packed network-order representation of the IPv4 address\n        associated with this record.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n    \"\"\"\n    compareAttributes = ('address', 'ttl')\n\n    TYPE = A\n    address = None\n\n    def __init__(self, address='0.0.0.0', ttl=None):\n        \"\"\"\n        @type address: L{bytes} or L{unicode}\n        @param address: The IPv4 address associated with this record, in\n            quad-dotted notation.\n        \"\"\"\n        if _PY3 and isinstance(address, bytes):\n            address = address.decode('idna')\n\n        address = socket.inet_aton(address)\n        self.address = address\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict = None):\n        strio.write(self.address)\n\n\n    def decode(self, strio, length = None):\n        self.address = readPrecisely(strio, 4)\n\n\n    def __hash__(self):\n        return hash(self.address)\n\n\n    def __str__(self):\n        return '<A address=%s ttl=%s>' % (self.dottedQuad(), self.ttl)\n    __repr__ = __str__\n\n\n    def dottedQuad(self):\n        return socket.inet_ntoa(self.address)\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_SOA(tputil.FancyEqMixin, tputil.FancyStrMixin):\n    \"\"\"\n    Marks the start of a zone of authority.\n\n    This record describes parameters which are shared by all records within a\n    particular zone.\n\n    @type mname: L{Name}\n    @ivar mname: The domain-name of the name server that was the original or\n        primary source of data for this zone.\n\n    @type rname: L{Name}\n    @ivar rname: A domain-name which specifies the mailbox of the person\n        responsible for this zone.\n\n    @type serial: L{int}\n    @ivar serial: The unsigned 32 bit version number of the original copy of\n        the zone.  Zone transfers preserve this value.  This value wraps and\n        should be compared using sequence space arithmetic.\n\n    @type refresh: L{int}\n    @ivar refresh: A 32 bit time interval before the zone should be refreshed.\n\n    @type minimum: L{int}\n    @ivar minimum: The unsigned 32 bit minimum TTL field that should be\n        exported with any RR from this zone.\n\n    @type expire: L{int}\n    @ivar expire: A 32 bit time value that specifies the upper limit on the\n        time interval that can elapse before the zone is no longer\n        authoritative.\n\n    @type retry: L{int}\n    @ivar retry: A 32 bit time interval that should elapse before a failed\n        refresh should be retried.\n\n    @type ttl: L{int}\n    @ivar ttl: The default TTL to use for records served from this zone.\n    \"\"\"\n    fancybasename = 'SOA'\n    compareAttributes = ('serial', 'mname', 'rname', 'refresh', 'expire', 'retry', 'minimum', 'ttl')\n    showAttributes = (('mname', 'mname', '%s'), ('rname', 'rname', '%s'), 'serial', 'refresh', 'retry', 'expire', 'minimum', 'ttl')\n\n    TYPE = SOA\n\n    def __init__(self, mname=b'', rname=b'', serial=0, refresh=0, retry=0,\n                 expire=0, minimum=0, ttl=None):\n        \"\"\"\n        @param mname: See L{Record_SOA.mname}\n        @type mname: L{bytes} or L{unicode}\n\n        @param rname: See L{Record_SOA.rname}\n        @type rname: L{bytes} or L{unicode}\n        \"\"\"\n        self.mname, self.rname = Name(mname), Name(rname)\n        self.serial, self.refresh = str2time(serial), str2time(refresh)\n        self.minimum, self.expire = str2time(minimum), str2time(expire)\n        self.retry = str2time(retry)\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict = None):\n        self.mname.encode(strio, compDict)\n        self.rname.encode(strio, compDict)\n        strio.write(\n            struct.pack(\n                '!LlllL',\n                self.serial, self.refresh, self.retry, self.expire,\n                self.minimum\n            )\n        )\n\n\n    def decode(self, strio, length = None):\n        self.mname, self.rname = Name(), Name()\n        self.mname.decode(strio)\n        self.rname.decode(strio)\n        r = struct.unpack('!LlllL', readPrecisely(strio, 20))\n        self.serial, self.refresh, self.retry, self.expire, self.minimum = r\n\n\n    def __hash__(self):\n        return hash((\n            self.serial, self.mname, self.rname,\n            self.refresh, self.expire, self.retry\n        ))\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_NULL(tputil.FancyStrMixin, tputil.FancyEqMixin):\n    \"\"\"\n    A null record.\n\n    This is an experimental record type.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n    \"\"\"\n    fancybasename = 'NULL'\n    showAttributes = (('payload', _nicebytes), 'ttl')\n    compareAttributes = ('payload', 'ttl')\n\n    TYPE = NULL\n\n    def __init__(self, payload=None, ttl=None):\n        self.payload = payload\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict = None):\n        strio.write(self.payload)\n\n\n    def decode(self, strio, length = None):\n        self.payload = readPrecisely(strio, length)\n\n\n    def __hash__(self):\n        return hash(self.payload)\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_WKS(tputil.FancyEqMixin, tputil.FancyStrMixin):\n    \"\"\"\n    A well known service description.\n\n    This record type is obsolete.  See L{Record_SRV}.\n\n    @type address: L{bytes}\n    @ivar address: The packed network-order representation of the IPv4 address\n        associated with this record.\n\n    @type protocol: L{int}\n    @ivar protocol: The 8 bit IP protocol number for which this service map is\n        relevant.\n\n    @type map: L{bytes}\n    @ivar map: A bitvector indicating the services available at the specified\n        address.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n    \"\"\"\n    fancybasename = \"WKS\"\n    compareAttributes = ('address', 'protocol', 'map', 'ttl')\n    showAttributes = [('_address', 'address', '%s'), 'protocol', 'ttl']\n\n    TYPE = WKS\n\n    _address = property(lambda self: socket.inet_ntoa(self.address))\n\n    def __init__(self, address='0.0.0.0', protocol=0, map=b'', ttl=None):\n        \"\"\"\n        @type address: L{bytes} or L{unicode}\n        @param address: The IPv4 address associated with this record, in\n            quad-dotted notation.\n        \"\"\"\n        if _PY3 and isinstance(address, bytes):\n            address = address.decode('idna')\n\n        self.address = socket.inet_aton(address)\n        self.protocol, self.map = protocol, map\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict = None):\n        strio.write(self.address)\n        strio.write(struct.pack('!B', self.protocol))\n        strio.write(self.map)\n\n\n    def decode(self, strio, length = None):\n        self.address = readPrecisely(strio, 4)\n        self.protocol = struct.unpack('!B', readPrecisely(strio, 1))[0]\n        self.map = readPrecisely(strio, length - 5)\n\n\n    def __hash__(self):\n        return hash((self.address, self.protocol, self.map))\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_AAAA(tputil.FancyEqMixin, tputil.FancyStrMixin):\n    \"\"\"\n    An IPv6 host address.\n\n    @type address: L{bytes}\n    @ivar address: The packed network-order representation of the IPv6 address\n        associated with this record.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n\n    @see: U{http://www.faqs.org/rfcs/rfc1886.html}\n    \"\"\"\n    TYPE = AAAA\n\n    fancybasename = 'AAAA'\n    showAttributes = (('_address', 'address', '%s'), 'ttl')\n    compareAttributes = ('address', 'ttl')\n\n    _address = property(lambda self: socket.inet_ntop(AF_INET6, self.address))\n\n    def __init__(self, address='::', ttl=None):\n        \"\"\"\n        @type address: L{bytes} or L{unicode}\n        @param address: The IPv6 address for this host, in RFC 2373 format.\n        \"\"\"\n        if _PY3 and isinstance(address, bytes):\n            address = address.decode('idna')\n\n        self.address = socket.inet_pton(AF_INET6, address)\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict = None):\n        strio.write(self.address)\n\n\n    def decode(self, strio, length = None):\n        self.address = readPrecisely(strio, 16)\n\n\n    def __hash__(self):\n        return hash(self.address)\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_A6(tputil.FancyStrMixin, tputil.FancyEqMixin):\n    \"\"\"\n    An IPv6 address.\n\n    This is an experimental record type.\n\n    @type prefixLen: L{int}\n    @ivar prefixLen: The length of the suffix.\n\n    @type suffix: L{bytes}\n    @ivar suffix: An IPv6 address suffix in network order.\n\n    @type prefix: L{Name}\n    @ivar prefix: If specified, a name which will be used as a prefix for other\n        A6 records.\n\n    @type bytes: L{int}\n    @ivar bytes: The length of the prefix.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n\n    @see: U{http://www.faqs.org/rfcs/rfc2874.html}\n    @see: U{http://www.faqs.org/rfcs/rfc3363.html}\n    @see: U{http://www.faqs.org/rfcs/rfc3364.html}\n    \"\"\"\n    TYPE = A6\n\n    fancybasename = 'A6'\n    showAttributes = (('_suffix', 'suffix', '%s'), ('prefix', 'prefix', '%s'), 'ttl')\n    compareAttributes = ('prefixLen', 'prefix', 'suffix', 'ttl')\n\n    _suffix = property(lambda self: socket.inet_ntop(AF_INET6, self.suffix))\n\n    def __init__(self, prefixLen=0, suffix='::', prefix=b'', ttl=None):\n        \"\"\"\n        @param suffix: An IPv6 address suffix in in RFC 2373 format.\n        @type suffix: L{bytes} or L{unicode}\n\n        @param prefix: An IPv6 address prefix for other A6 records.\n        @type prefix: L{bytes} or L{unicode}\n        \"\"\"\n        if _PY3 and isinstance(suffix, bytes):\n            suffix = suffix.decode('idna')\n\n        self.prefixLen = prefixLen\n        self.suffix = socket.inet_pton(AF_INET6, suffix)\n        self.prefix = Name(prefix)\n        self.bytes = int((128 - self.prefixLen) / 8.0)\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict = None):\n        strio.write(struct.pack('!B', self.prefixLen))\n        if self.bytes:\n            strio.write(self.suffix[-self.bytes:])\n        if self.prefixLen:\n            # This may not be compressed\n            self.prefix.encode(strio, None)\n\n\n    def decode(self, strio, length = None):\n        self.prefixLen = struct.unpack('!B', readPrecisely(strio, 1))[0]\n        self.bytes = int((128 - self.prefixLen) / 8.0)\n        if self.bytes:\n            self.suffix = b'\\x00' * (16 - self.bytes) + readPrecisely(strio, self.bytes)\n        if self.prefixLen:\n            self.prefix.decode(strio)\n\n\n    def __eq__(self, other):\n        if isinstance(other, Record_A6):\n            return (self.prefixLen == other.prefixLen and\n                    self.suffix[-self.bytes:] == other.suffix[-self.bytes:] and\n                    self.prefix == other.prefix and\n                    self.ttl == other.ttl)\n        return NotImplemented\n\n\n    def __hash__(self):\n        return hash((self.prefixLen, self.suffix[-self.bytes:], self.prefix))\n\n\n    def __str__(self):\n        return '<A6 %s %s (%d) ttl=%s>' % (\n            self.prefix,\n            socket.inet_ntop(AF_INET6, self.suffix),\n            self.prefixLen, self.ttl\n        )\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_SRV(tputil.FancyEqMixin, tputil.FancyStrMixin):\n    \"\"\"\n    The location of the server(s) for a specific protocol and domain.\n\n    This is an experimental record type.\n\n    @type priority: L{int}\n    @ivar priority: The priority of this target host.  A client MUST attempt to\n        contact the target host with the lowest-numbered priority it can reach;\n        target hosts with the same priority SHOULD be tried in an order defined\n        by the weight field.\n\n    @type weight: L{int}\n    @ivar weight: Specifies a relative weight for entries with the same\n        priority. Larger weights SHOULD be given a proportionately higher\n        probability of being selected.\n\n    @type port: L{int}\n    @ivar port: The port on this target host of this service.\n\n    @type target: L{Name}\n    @ivar target: The domain name of the target host.  There MUST be one or\n        more address records for this name, the name MUST NOT be an alias (in\n        the sense of RFC 1034 or RFC 2181).  Implementors are urged, but not\n        required, to return the address record(s) in the Additional Data\n        section.  Unless and until permitted by future standards action, name\n        compression is not to be used for this field.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n\n    @see: U{http://www.faqs.org/rfcs/rfc2782.html}\n    \"\"\"\n    TYPE = SRV\n\n    fancybasename = 'SRV'\n    compareAttributes = ('priority', 'weight', 'target', 'port', 'ttl')\n    showAttributes = ('priority', 'weight', ('target', 'target', '%s'), 'port', 'ttl')\n\n    def __init__(self, priority=0, weight=0, port=0, target=b'', ttl=None):\n        \"\"\"\n        @param target: See L{Record_SRV.target}\n        @type target: L{bytes} or L{unicode}\n        \"\"\"\n        self.priority = int(priority)\n        self.weight = int(weight)\n        self.port = int(port)\n        self.target = Name(target)\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict = None):\n        strio.write(struct.pack('!HHH', self.priority, self.weight, self.port))\n        # This can't be compressed\n        self.target.encode(strio, None)\n\n\n    def decode(self, strio, length = None):\n        r = struct.unpack('!HHH', readPrecisely(strio, struct.calcsize('!HHH')))\n        self.priority, self.weight, self.port = r\n        self.target = Name()\n        self.target.decode(strio)\n\n\n    def __hash__(self):\n        return hash((self.priority, self.weight, self.port, self.target))\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_NAPTR(tputil.FancyEqMixin, tputil.FancyStrMixin):\n    \"\"\"\n    The location of the server(s) for a specific protocol and domain.\n\n    @type order: L{int}\n    @ivar order: An integer specifying the order in which the NAPTR records\n        MUST be processed to ensure the correct ordering of rules.  Low numbers\n        are processed before high numbers.\n\n    @type preference: L{int}\n    @ivar preference: An integer that specifies the order in which NAPTR\n        records with equal \"order\" values SHOULD be processed, low numbers\n        being processed before high numbers.\n\n    @type flag: L{Charstr}\n    @ivar flag: A <character-string> containing flags to control aspects of the\n        rewriting and interpretation of the fields in the record.  Flags\n        are single characters from the set [A-Z0-9].  The case of the alphabetic\n        characters is not significant.\n\n        At this time only four flags, \"S\", \"A\", \"U\", and \"P\", are defined.\n\n    @type service: L{Charstr}\n    @ivar service: Specifies the service(s) available down this rewrite path.\n        It may also specify the particular protocol that is used to talk with a\n        service.  A protocol MUST be specified if the flags field states that\n        the NAPTR is terminal.\n\n    @type regexp: L{Charstr}\n    @ivar regexp: A STRING containing a substitution expression that is applied\n        to the original string held by the client in order to construct the\n        next domain name to lookup.\n\n    @type replacement: L{Name}\n    @ivar replacement: The next NAME to query for NAPTR, SRV, or address\n        records depending on the value of the flags field.  This MUST be a\n        fully qualified domain-name.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n\n    @see: U{http://www.faqs.org/rfcs/rfc2915.html}\n    \"\"\"\n    TYPE = NAPTR\n\n    compareAttributes = ('order', 'preference', 'flags', 'service', 'regexp',\n                         'replacement')\n    fancybasename = 'NAPTR'\n\n    showAttributes = ('order', 'preference', ('flags', 'flags', '%s'),\n                      ('service', 'service', '%s'), ('regexp', 'regexp', '%s'),\n                      ('replacement', 'replacement', '%s'), 'ttl')\n\n    def __init__(self, order=0, preference=0, flags=b'', service=b'',\n                 regexp=b'', replacement=b'', ttl=None):\n        \"\"\"\n        @param replacement: See L{Record_NAPTR.replacement}\n        @type replacement: L{bytes} or L{unicode}\n        \"\"\"\n        self.order = int(order)\n        self.preference = int(preference)\n        self.flags = Charstr(flags)\n        self.service = Charstr(service)\n        self.regexp = Charstr(regexp)\n        self.replacement = Name(replacement)\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict=None):\n        strio.write(struct.pack('!HH', self.order, self.preference))\n        # This can't be compressed\n        self.flags.encode(strio, None)\n        self.service.encode(strio, None)\n        self.regexp.encode(strio, None)\n        self.replacement.encode(strio, None)\n\n\n    def decode(self, strio, length=None):\n        r = struct.unpack('!HH', readPrecisely(strio, struct.calcsize('!HH')))\n        self.order, self.preference = r\n        self.flags = Charstr()\n        self.service = Charstr()\n        self.regexp = Charstr()\n        self.replacement = Name()\n        self.flags.decode(strio)\n        self.service.decode(strio)\n        self.regexp.decode(strio)\n        self.replacement.decode(strio)\n\n\n    def __hash__(self):\n        return hash((\n            self.order, self.preference, self.flags,\n            self.service, self.regexp, self.replacement))\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_AFSDB(tputil.FancyStrMixin, tputil.FancyEqMixin):\n    \"\"\"\n    Map from a domain name to the name of an AFS cell database server.\n\n    @type subtype: L{int}\n    @ivar subtype: In the case of subtype 1, the host has an AFS version 3.0\n        Volume Location Server for the named AFS cell.  In the case of subtype\n        2, the host has an authenticated name server holding the cell-root\n        directory node for the named DCE/NCA cell.\n\n    @type hostname: L{Name}\n    @ivar hostname: The domain name of a host that has a server for the cell\n        named by this record.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n\n    @see: U{http://www.faqs.org/rfcs/rfc1183.html}\n    \"\"\"\n    TYPE = AFSDB\n\n    fancybasename = 'AFSDB'\n    compareAttributes = ('subtype', 'hostname', 'ttl')\n    showAttributes = ('subtype', ('hostname', 'hostname', '%s'), 'ttl')\n\n    def __init__(self, subtype=0, hostname=b'', ttl=None):\n        \"\"\"\n        @param hostname: See L{Record_AFSDB.hostname}\n        @type hostname: L{bytes} or L{unicode}\n        \"\"\"\n        self.subtype = int(subtype)\n        self.hostname = Name(hostname)\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict = None):\n        strio.write(struct.pack('!H', self.subtype))\n        self.hostname.encode(strio, compDict)\n\n\n    def decode(self, strio, length = None):\n        r = struct.unpack('!H', readPrecisely(strio, struct.calcsize('!H')))\n        self.subtype, = r\n        self.hostname.decode(strio)\n\n\n    def __hash__(self):\n        return hash((self.subtype, self.hostname))\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_RP(tputil.FancyEqMixin, tputil.FancyStrMixin):\n    \"\"\"\n    The responsible person for a domain.\n\n    @type mbox: L{Name}\n    @ivar mbox: A domain name that specifies the mailbox for the responsible\n        person.\n\n    @type txt: L{Name}\n    @ivar txt: A domain name for which TXT RR's exist (indirection through\n        which allows information sharing about the contents of this RP record).\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n\n    @see: U{http://www.faqs.org/rfcs/rfc1183.html}\n    \"\"\"\n    TYPE = RP\n\n    fancybasename = 'RP'\n    compareAttributes = ('mbox', 'txt', 'ttl')\n    showAttributes = (('mbox', 'mbox', '%s'), ('txt', 'txt', '%s'), 'ttl')\n\n    def __init__(self, mbox=b'', txt=b'', ttl=None):\n        \"\"\"\n        @param mbox: See L{Record_RP.mbox}.\n        @type mbox: L{bytes} or L{unicode}\n\n        @param txt: See L{Record_RP.txt}\n        @type txt: L{bytes} or L{unicode}\n        \"\"\"\n        self.mbox = Name(mbox)\n        self.txt = Name(txt)\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict = None):\n        self.mbox.encode(strio, compDict)\n        self.txt.encode(strio, compDict)\n\n\n    def decode(self, strio, length = None):\n        self.mbox = Name()\n        self.txt = Name()\n        self.mbox.decode(strio)\n        self.txt.decode(strio)\n\n\n    def __hash__(self):\n        return hash((self.mbox, self.txt))\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_HINFO(tputil.FancyStrMixin, tputil.FancyEqMixin):\n    \"\"\"\n    Host information.\n\n    @type cpu: L{bytes}\n    @ivar cpu: Specifies the CPU type.\n\n    @type os: L{bytes}\n    @ivar os: Specifies the OS.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n    \"\"\"\n    TYPE = HINFO\n\n    fancybasename = 'HINFO'\n    showAttributes = (('cpu', _nicebytes), ('os', _nicebytes), 'ttl')\n    compareAttributes = ('cpu', 'os', 'ttl')\n\n    def __init__(self, cpu=b'', os=b'', ttl=None):\n        self.cpu, self.os = cpu, os\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict = None):\n        strio.write(struct.pack('!B', len(self.cpu)) + self.cpu)\n        strio.write(struct.pack('!B', len(self.os)) + self.os)\n\n\n    def decode(self, strio, length = None):\n        cpu = struct.unpack('!B', readPrecisely(strio, 1))[0]\n        self.cpu = readPrecisely(strio, cpu)\n        os = struct.unpack('!B', readPrecisely(strio, 1))[0]\n        self.os = readPrecisely(strio, os)\n\n\n    def __eq__(self, other):\n        if isinstance(other, Record_HINFO):\n            return (self.os.lower() == other.os.lower() and\n                    self.cpu.lower() == other.cpu.lower() and\n                    self.ttl == other.ttl)\n        return NotImplemented\n\n\n    def __hash__(self):\n        return hash((self.os.lower(), self.cpu.lower()))\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_MINFO(tputil.FancyEqMixin, tputil.FancyStrMixin):\n    \"\"\"\n    Mailbox or mail list information.\n\n    This is an experimental record type.\n\n    @type rmailbx: L{Name}\n    @ivar rmailbx: A domain-name which specifies a mailbox which is responsible\n        for the mailing list or mailbox.  If this domain name names the root,\n        the owner of the MINFO RR is responsible for itself.\n\n    @type emailbx: L{Name}\n    @ivar emailbx: A domain-name which specifies a mailbox which is to receive\n        error messages related to the mailing list or mailbox specified by the\n        owner of the MINFO record.  If this domain name names the root, errors\n        should be returned to the sender of the message.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n    \"\"\"\n    TYPE = MINFO\n\n    rmailbx = None\n    emailbx = None\n\n    fancybasename = 'MINFO'\n    compareAttributes = ('rmailbx', 'emailbx', 'ttl')\n    showAttributes = (('rmailbx', 'responsibility', '%s'),\n                      ('emailbx', 'errors', '%s'),\n                      'ttl')\n\n    def __init__(self, rmailbx=b'', emailbx=b'', ttl=None):\n        \"\"\"\n        @param rmailbx: See L{Record_MINFO.rmailbx}.\n        @type rmailbx: L{bytes} or L{unicode}\n\n        @param emailbx: See L{Record_MINFO.rmailbx}.\n        @type emailbx: L{bytes} or L{unicode}\n        \"\"\"\n        self.rmailbx, self.emailbx = Name(rmailbx), Name(emailbx)\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict = None):\n        self.rmailbx.encode(strio, compDict)\n        self.emailbx.encode(strio, compDict)\n\n\n    def decode(self, strio, length = None):\n        self.rmailbx, self.emailbx = Name(), Name()\n        self.rmailbx.decode(strio)\n        self.emailbx.decode(strio)\n\n\n    def __hash__(self):\n        return hash((self.rmailbx, self.emailbx))\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_MX(tputil.FancyStrMixin, tputil.FancyEqMixin):\n    \"\"\"\n    Mail exchange.\n\n    @type preference: L{int}\n    @ivar preference: Specifies the preference given to this RR among others at\n        the same owner.  Lower values are preferred.\n\n    @type name: L{Name}\n    @ivar name: A domain-name which specifies a host willing to act as a mail\n        exchange.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be\n        cached.\n    \"\"\"\n    TYPE = MX\n\n    fancybasename = 'MX'\n    compareAttributes = ('preference', 'name', 'ttl')\n    showAttributes = ('preference', ('name', 'name', '%s'), 'ttl')\n\n    def __init__(self, preference=0, name=b'', ttl=None, **kwargs):\n        \"\"\"\n        @param name: See L{Record_MX.name}.\n        @type name: L{bytes} or L{unicode}\n        \"\"\"\n        self.preference = int(preference)\n        self.name = Name(kwargs.get('exchange', name))\n        self.ttl = str2time(ttl)\n\n    def encode(self, strio, compDict = None):\n        strio.write(struct.pack('!H', self.preference))\n        self.name.encode(strio, compDict)\n\n\n    def decode(self, strio, length = None):\n        self.preference = struct.unpack('!H', readPrecisely(strio, 2))[0]\n        self.name = Name()\n        self.name.decode(strio)\n\n    def __hash__(self):\n        return hash((self.preference, self.name))\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_SSHFP(tputil.FancyEqMixin, tputil.FancyStrMixin):\n    \"\"\"\n    A record containing the fingerprint of an SSH key.\n\n    @type algorithm: L{int}\n    @ivar algorithm: The SSH key's algorithm, such as L{ALGORITHM_RSA}.\n        Note that the numbering used for SSH key algorithms is specific\n        to the SSHFP record, and is not the same as the numbering\n        used for KEY or SIG records.\n\n    @type fingerprintType: L{int}\n    @ivar fingerprintType: The fingerprint type,\n        such as L{FINGERPRINT_TYPE_SHA256}.\n\n    @type fingerprint: L{bytes}\n    @ivar fingerprint: The key's fingerprint, e.g. a 32-byte SHA-256 digest.\n\n    @cvar ALGORITHM_RSA: The algorithm value for C{ssh-rsa} keys.\n    @cvar ALGORITHM_DSS: The algorithm value for C{ssh-dss} keys.\n    @cvar ALGORITHM_ECDSA: The algorithm value for C{ecdsa-sha2-*} keys.\n    @cvar ALGORITHM_Ed25519: The algorithm value for C{ed25519} keys.\n\n    @cvar FINGERPRINT_TYPE_SHA1: The type for SHA-1 fingerprints.\n    @cvar FINGERPRINT_TYPE_SHA256: The type for SHA-256 fingerprints.\n\n    @see: U{RFC 4255 <https://tools.ietf.org/html/rfc4255>}\n          and\n          U{RFC 6594 <https://tools.ietf.org/html/rfc6594>}\n    \"\"\"\n    fancybasename = \"SSHFP\"\n    compareAttributes = ('algorithm', 'fingerprintType', 'fingerprint', 'ttl')\n    showAttributes = ('algorithm', 'fingerprintType', 'fingerprint')\n\n    TYPE = SSHFP\n\n    ALGORITHM_RSA = 1\n    ALGORITHM_DSS = 2\n    ALGORITHM_ECDSA = 3\n    ALGORITHM_Ed25519 = 4\n\n    FINGERPRINT_TYPE_SHA1 = 1\n    FINGERPRINT_TYPE_SHA256 = 2\n\n    def __init__(self, algorithm=0, fingerprintType=0, fingerprint=b'', ttl=0):\n        self.algorithm = algorithm\n        self.fingerprintType = fingerprintType\n        self.fingerprint = fingerprint\n        self.ttl = ttl\n\n\n    def encode(self, strio, compDict=None):\n        strio.write(struct.pack('!BB',\n                                self.algorithm, self.fingerprintType))\n        strio.write(self.fingerprint)\n\n\n    def decode(self, strio, length=None):\n        r = struct.unpack('!BB', readPrecisely(strio, 2))\n        (self.algorithm, self.fingerprintType) = r\n        self.fingerprint = readPrecisely(strio, length - 2)\n\n\n    def __hash__(self):\n        return hash((self.algorithm, self.fingerprintType, self.fingerprint))\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_TXT(tputil.FancyEqMixin, tputil.FancyStrMixin):\n    \"\"\"\n    Freeform text.\n\n    @type data: L{list} of L{bytes}\n    @ivar data: Freeform text which makes up this record.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be cached.\n    \"\"\"\n    TYPE = TXT\n\n    fancybasename = 'TXT'\n    showAttributes = (('data', _nicebyteslist), 'ttl')\n    compareAttributes = ('data', 'ttl')\n\n    def __init__(self, *data, **kw):\n        self.data = list(data)\n        # arg man python sucks so bad\n        self.ttl = str2time(kw.get('ttl', None))\n\n\n    def encode(self, strio, compDict=None):\n        for d in self.data:\n            strio.write(struct.pack('!B', len(d)) + d)\n\n\n    def decode(self, strio, length=None):\n        soFar = 0\n        self.data = []\n        while soFar < length:\n            L = struct.unpack('!B', readPrecisely(strio, 1))[0]\n            self.data.append(readPrecisely(strio, L))\n            soFar += L + 1\n        if soFar != length:\n            log.msg(\n                \"Decoded %d bytes in %s record, but rdlength is %d\" % (\n                    soFar, self.fancybasename, length\n                )\n            )\n\n\n    def __hash__(self):\n        return hash(tuple(self.data))\n\n\n\n@implementer(IEncodable, IRecord)\nclass UnknownRecord(tputil.FancyEqMixin, tputil.FancyStrMixin, object):\n    \"\"\"\n    Encapsulate the wire data for unknown record types so that they can\n    pass through the system unchanged.\n\n    @type data: L{bytes}\n    @ivar data: Wire data which makes up this record.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds which this record should be cached.\n\n    @since: 11.1\n    \"\"\"\n    fancybasename = 'UNKNOWN'\n    compareAttributes = ('data', 'ttl')\n    showAttributes = (('data', _nicebytes), 'ttl')\n\n    def __init__(self, data=b'', ttl=None):\n        self.data = data\n        self.ttl = str2time(ttl)\n\n\n    def encode(self, strio, compDict=None):\n        \"\"\"\n        Write the raw bytes corresponding to this record's payload to the\n        stream.\n        \"\"\"\n        strio.write(self.data)\n\n\n    def decode(self, strio, length=None):\n        \"\"\"\n        Load the bytes which are part of this record from the stream and store\n        them unparsed and unmodified.\n        \"\"\"\n        if length is None:\n            raise Exception('must know length for unknown record types')\n        self.data = readPrecisely(strio, length)\n\n\n    def __hash__(self):\n        return hash((self.data, self.ttl))\n\n\n\nclass Record_SPF(Record_TXT):\n    \"\"\"\n    Structurally, freeform text. Semantically, a policy definition, formatted\n    as defined in U{rfc 4408<http://www.faqs.org/rfcs/rfc4408.html>}.\n\n    @type data: L{list} of L{bytes}\n    @ivar data: Freeform text which makes up this record.\n\n    @type ttl: L{int}\n    @ivar ttl: The maximum number of seconds\n               which this record should be cached.\n    \"\"\"\n    TYPE = SPF\n    fancybasename = 'SPF'\n\n\n\n@implementer(IEncodable, IRecord)\nclass Record_TSIG(tputil.FancyEqMixin, tputil.FancyStrMixin):\n    \"\"\"\n    A transaction signature, encapsulated in a RR, as described\n    in U{RFC 2845 <https://tools.ietf.org/html/rfc2845>}.\n\n    @type algorithm: L{Name}\n    @ivar algorithm: The name of the signature or MAC algorithm.\n\n    @type timeSigned: L{int}\n    @ivar timeSigned: Signing time, as seconds from the POSIX epoch.\n\n    @type fudge: L{int}\n    @ivar fudge: Allowable time skew, in seconds.\n\n    @type MAC: L{bytes}\n    @ivar MAC: The message digest or signature.\n\n    @type originalID: L{int}\n    @ivar originalID: A message ID.\n\n    @type error: L{int}\n    @ivar error: An error code (extended C{RCODE}) carried\n          in exceptional cases.\n\n    @type otherData: L{bytes}\n    @ivar otherData: Other data carried in exceptional cases.\n\n    \"\"\"\n    fancybasename = \"TSIG\"\n    compareAttributes = ('algorithm', 'timeSigned', 'fudge',\n                         'MAC', 'originalID', 'error', 'otherData',\n                         'ttl')\n    showAttributes = ['algorithm', 'timeSigned', 'MAC', 'error', 'otherData']\n\n    TYPE = TSIG\n\n    def __init__(self, algorithm=None, timeSigned=None,\n                 fudge=5, MAC=None, originalID=0,\n                 error=OK, otherData=b'', ttl=0):\n        # All of our init arguments have to have defaults, because of\n        # the way IEncodable and Message.parseRecords() work, but for\n        # some of our arguments there is no reasonable default; we use\n        # invalid values here to prevent a user of this class from\n        # relying on what's really an internal implementation detail.\n        self.algorithm = None if algorithm is None else Name(algorithm)\n        self.timeSigned = timeSigned\n        self.fudge = str2time(fudge)\n        self.MAC = MAC\n        self.originalID = originalID\n        self.error = error\n        self.otherData = otherData\n        self.ttl = ttl\n\n\n    def encode(self, strio, compDict=None):\n        self.algorithm.encode(strio, compDict)\n        strio.write(struct.pack('!Q', self.timeSigned)[2:])  # 48-bit number\n        strio.write(struct.pack('!HH', self.fudge, len(self.MAC)))\n        strio.write(self.MAC)\n        strio.write(struct.pack('!HHH',\n                                self.originalID, self.error,\n                                len(self.otherData)))\n        strio.write(self.otherData)\n\n\n    def decode(self, strio, length=None):\n        algorithm = Name()\n        algorithm.decode(strio)\n        self.algorithm = algorithm\n        fields = struct.unpack('!QHH', b'\\x00\\x00' + readPrecisely(strio, 10))\n        self.timeSigned, self.fudge, macLength = fields\n        self.MAC = readPrecisely(strio, macLength)\n        fields = struct.unpack('!HHH', readPrecisely(strio, 6))\n        self.originalID, self.error, otherLength = fields\n        self.otherData = readPrecisely(strio, otherLength)\n\n\n    def __hash__(self):\n        return hash((self.algorithm, self.timeSigned,\n                     self.MAC, self.originalID))\n\n\n\ndef _responseFromMessage(responseConstructor, message, **kwargs):\n    \"\"\"\n    Generate a L{Message} like instance suitable for use as the response to\n    C{message}.\n\n    The C{queries}, C{id} attributes will be copied from C{message} and the\n    C{answer} flag will be set to L{True}.\n\n    @param responseConstructor: A response message constructor with an\n         initializer signature matching L{dns.Message.__init__}.\n    @type responseConstructor: C{callable}\n\n    @param message: A request message.\n    @type message: L{Message}\n\n    @param kwargs: Keyword arguments which will be passed to the initialiser\n        of the response message.\n    @type kwargs: L{dict}\n\n    @return: A L{Message} like response instance.\n    @rtype: C{responseConstructor}\n    \"\"\"\n    response = responseConstructor(id=message.id, answer=True, **kwargs)\n    response.queries = message.queries[:]\n    return response\n\n\n\ndef _getDisplayableArguments(obj, alwaysShow, fieldNames):\n    \"\"\"\n    Inspect the function signature of C{obj}'s constructor,\n    and get a list of which arguments should be displayed.\n    This is a helper function for C{_compactRepr}.\n\n    @param obj: The instance whose repr is being generated.\n    @param alwaysShow: A L{list} of field names which should always be shown.\n    @param fieldNames: A L{list} of field attribute names which should be shown\n        if they have non-default values.\n    @return: A L{list} of displayable arguments.\n    \"\"\"\n    displayableArgs = []\n    if _PY3:\n        # Get the argument names and values from the constructor.\n        signature = inspect.signature(obj.__class__.__init__)\n        for name in fieldNames:\n            defaultValue = signature.parameters[name].default\n            fieldValue = getattr(obj, name, defaultValue)\n            if (name in alwaysShow) or (fieldValue != defaultValue):\n                displayableArgs.append(' %s=%r' % (name, fieldValue))\n    else:\n        # Get the argument names and values from the constructor.\n        argspec = inspect.getargspec(obj.__class__.__init__)\n        # Reverse the args and defaults to avoid mapping positional arguments\n        # which don't have a default.\n        defaults = dict(zip(reversed(argspec.args), reversed(argspec.defaults)))\n        for name in fieldNames:\n            defaultValue = defaults.get(name)\n            fieldValue = getattr(obj, name, defaultValue)\n            if (name in alwaysShow) or (fieldValue != defaultValue):\n                displayableArgs.append(' %s=%r' % (name, fieldValue))\n\n    return displayableArgs\n\n\n\ndef _compactRepr(obj, alwaysShow=None, flagNames=None, fieldNames=None,\n                 sectionNames=None):\n    \"\"\"\n    Return a L{str} representation of C{obj} which only shows fields with\n    non-default values, flags which are True and sections which have been\n    explicitly set.\n\n    @param obj: The instance whose repr is being generated.\n    @param alwaysShow: A L{list} of field names which should always be shown.\n    @param flagNames: A L{list} of flag attribute names which should be shown if\n        they are L{True}.\n    @param fieldNames: A L{list} of field attribute names which should be shown\n        if they have non-default values.\n    @param sectionNames: A L{list} of section attribute names which should be\n        shown if they have been assigned a value.\n\n    @return: A L{str} representation of C{obj}.\n    \"\"\"\n    if alwaysShow is None:\n        alwaysShow = []\n\n    if flagNames is None:\n        flagNames = []\n\n    if fieldNames is None:\n        fieldNames = []\n\n    if sectionNames is None:\n        sectionNames = []\n\n    setFlags = []\n    for name in flagNames:\n        if name in alwaysShow or getattr(obj, name, False) == True:\n            setFlags.append(name)\n\n    displayableArgs = _getDisplayableArguments(obj, alwaysShow, fieldNames)\n    out = ['<', obj.__class__.__name__] + displayableArgs\n\n    if setFlags:\n        out.append(' flags=%s' % (','.join(setFlags),))\n\n    for name in sectionNames:\n        section = getattr(obj, name, [])\n        if section:\n            out.append(' %s=%r' % (name, section))\n\n    out.append('>')\n\n    return ''.join(out)\n\n\n\nclass Message(tputil.FancyEqMixin):\n    \"\"\"\n    L{Message} contains all the information represented by a single\n    DNS request or response.\n\n    @ivar id: See L{__init__}\n    @ivar answer: See L{__init__}\n    @ivar opCode: See L{__init__}\n    @ivar recDes: See L{__init__}\n    @ivar recAv: See L{__init__}\n    @ivar auth: See L{__init__}\n    @ivar rCode: See L{__init__}\n    @ivar trunc: See L{__init__}\n    @ivar maxSize: See L{__init__}\n    @ivar authenticData: See L{__init__}\n    @ivar checkingDisabled: See L{__init__}\n\n    @ivar queries: The queries which are being asked of or answered by\n        DNS server.\n    @type queries: L{list} of L{Query}\n\n    @ivar answers: Records containing the answers to C{queries} if\n        this is a response message.\n    @type answers: L{list} of L{RRHeader}\n\n    @ivar authority: Records containing information about the\n        authoritative DNS servers for the names in C{queries}.\n    @type authority: L{list} of L{RRHeader}\n\n    @ivar additional: Records containing IP addresses of host names\n        in C{answers} and C{authority}.\n    @type additional: L{list} of L{RRHeader}\n\n    @ivar _flagNames: The names of attributes representing the flag header\n        fields.\n    @ivar _fieldNames: The names of attributes representing non-flag fixed\n        header fields.\n    @ivar _sectionNames: The names of attributes representing the record\n        sections of this message.\n    \"\"\"\n    compareAttributes = (\n        'id', 'answer', 'opCode', 'recDes', 'recAv',\n        'auth', 'rCode', 'trunc', 'maxSize',\n        'authenticData', 'checkingDisabled',\n        'queries', 'answers', 'authority', 'additional'\n    )\n\n    headerFmt = \"!H2B4H\"\n    headerSize = struct.calcsize(headerFmt)\n\n    # Question, answer, additional, and nameserver lists\n    queries = answers = add = ns = None\n\n    def __init__(self, id=0, answer=0, opCode=0, recDes=0, recAv=0,\n                       auth=0, rCode=OK, trunc=0, maxSize=512,\n                       authenticData=0, checkingDisabled=0):\n        \"\"\"\n        @param id: A 16 bit identifier assigned by the program that\n            generates any kind of query.  This identifier is copied to\n            the corresponding reply and can be used by the requester\n            to match up replies to outstanding queries.\n        @type id: L{int}\n\n        @param answer: A one bit field that specifies whether this\n            message is a query (0), or a response (1).\n        @type answer: L{int}\n\n        @param opCode: A four bit field that specifies kind of query in\n            this message.  This value is set by the originator of a query\n            and copied into the response.\n        @type opCode: L{int}\n\n        @param recDes: Recursion Desired - this bit may be set in a\n            query and is copied into the response.  If RD is set, it\n            directs the name server to pursue the query recursively.\n            Recursive query support is optional.\n        @type recDes: L{int}\n\n        @param recAv: Recursion Available - this bit is set or cleared\n            in a response and denotes whether recursive query support\n            is available in the name server.\n        @type recAv: L{int}\n\n        @param auth: Authoritative Answer - this bit is valid in\n            responses and specifies that the responding name server\n            is an authority for the domain name in question section.\n        @type auth: L{int}\n\n        @ivar rCode: A response code, used to indicate success or failure in a\n            message which is a response from a server to a client request.\n        @type rCode: C{0 <= int < 16}\n\n        @param trunc: A flag indicating that this message was\n            truncated due to length greater than that permitted on the\n            transmission channel.\n        @type trunc: L{int}\n\n        @param maxSize: The requestor's UDP payload size is the number\n            of octets of the largest UDP payload that can be\n            reassembled and delivered in the requestor's network\n            stack.\n        @type maxSize: L{int}\n\n        @param authenticData: A flag indicating in a response that all\n            the data included in the answer and authority portion of\n            the response has been authenticated by the server\n            according to the policies of that server.\n            See U{RFC2535 section-6.1<https://tools.ietf.org/html/rfc2535#section-6.1>}.\n        @type authenticData: L{int}\n\n        @param checkingDisabled: A flag indicating in a query that\n            pending (non-authenticated) data is acceptable to the\n            resolver sending the query.\n            See U{RFC2535 section-6.1<https://tools.ietf.org/html/rfc2535#section-6.1>}.\n        @type authenticData: L{int}\n        \"\"\"\n        self.maxSize = maxSize\n        self.id = id\n        self.answer = answer\n        self.opCode = opCode\n        self.auth = auth\n        self.trunc = trunc\n        self.recDes = recDes\n        self.recAv = recAv\n        self.rCode = rCode\n        self.authenticData = authenticData\n        self.checkingDisabled = checkingDisabled\n\n        self.queries = []\n        self.answers = []\n        self.authority = []\n        self.additional = []\n\n\n    def __repr__(self):\n        \"\"\"\n        Generate a repr of this L{Message}.\n\n        Only includes the non-default fields and sections and only includes\n        flags which are set. The C{id} is always shown.\n\n        @return: The native string repr.\n        \"\"\"\n        return _compactRepr(\n            self,\n            flagNames=('answer', 'auth', 'trunc', 'recDes', 'recAv',\n                       'authenticData', 'checkingDisabled'),\n            fieldNames=('id', 'opCode', 'rCode', 'maxSize'),\n            sectionNames=('queries', 'answers', 'authority', 'additional'),\n            alwaysShow=('id',)\n        )\n\n\n    def addQuery(self, name, type=ALL_RECORDS, cls=IN):\n        \"\"\"\n        Add another query to this Message.\n\n        @type name: L{bytes}\n        @param name: The name to query.\n\n        @type type: L{int}\n        @param type: Query type\n\n        @type cls: L{int}\n        @param cls: Query class\n        \"\"\"\n        self.queries.append(Query(name, type, cls))\n\n\n    def encode(self, strio):\n        compDict = {}\n        body_tmp = BytesIO()\n        for q in self.queries:\n            q.encode(body_tmp, compDict)\n        for q in self.answers:\n            q.encode(body_tmp, compDict)\n        for q in self.authority:\n            q.encode(body_tmp, compDict)\n        for q in self.additional:\n            q.encode(body_tmp, compDict)\n        body = body_tmp.getvalue()\n        size = len(body) + self.headerSize\n        if self.maxSize and size > self.maxSize:\n            self.trunc = 1\n            body = body[:self.maxSize - self.headerSize]\n        byte3 = (( ( self.answer & 1 ) << 7 )\n                 | ((self.opCode & 0xf ) << 3 )\n                 | ((self.auth & 1 ) << 2 )\n                 | ((self.trunc & 1 ) << 1 )\n                 | ( self.recDes & 1 ) )\n        byte4 = ( ( (self.recAv & 1 ) << 7 )\n                  | ((self.authenticData & 1) << 5)\n                  | ((self.checkingDisabled & 1) << 4)\n                  | (self.rCode & 0xf ) )\n\n        strio.write(struct.pack(self.headerFmt, self.id, byte3, byte4,\n                                len(self.queries), len(self.answers),\n                                len(self.authority), len(self.additional)))\n        strio.write(body)\n\n\n    def decode(self, strio, length=None):\n        self.maxSize = 0\n        header = readPrecisely(strio, self.headerSize)\n        r = struct.unpack(self.headerFmt, header)\n        self.id, byte3, byte4, nqueries, nans, nns, nadd = r\n        self.answer = ( byte3 >> 7 ) & 1\n        self.opCode = ( byte3 >> 3 ) & 0xf\n        self.auth = ( byte3 >> 2 ) & 1\n        self.trunc = ( byte3 >> 1 ) & 1\n        self.recDes = byte3 & 1\n        self.recAv = ( byte4 >> 7 ) & 1\n        self.authenticData = ( byte4 >> 5 ) & 1\n        self.checkingDisabled = ( byte4 >> 4 ) & 1\n        self.rCode = byte4 & 0xf\n\n        self.queries = []\n        for i in range(nqueries):\n            q = Query()\n            try:\n                q.decode(strio)\n            except EOFError:\n                return\n            self.queries.append(q)\n\n        items = (\n            (self.answers, nans),\n            (self.authority, nns),\n            (self.additional, nadd))\n\n        for (l, n) in items:\n            self.parseRecords(l, n, strio)\n\n\n    def parseRecords(self, list, num, strio):\n        for i in range(num):\n            header = RRHeader(auth=self.auth)\n            try:\n                header.decode(strio)\n            except EOFError:\n                return\n            t = self.lookupRecordType(header.type)\n            if not t:\n                continue\n            header.payload = t(ttl=header.ttl)\n            try:\n                header.payload.decode(strio, header.rdlength)\n            except EOFError:\n                return\n            list.append(header)\n\n\n    # Create a mapping from record types to their corresponding Record_*\n    # classes.  This relies on the global state which has been created so\n    # far in initializing this module (so don't define Record classes after\n    # this).\n    _recordTypes = {}\n    for name in globals():\n        if name.startswith('Record_'):\n            _recordTypes[globals()[name].TYPE] = globals()[name]\n\n    # Clear the iteration variable out of the class namespace so it\n    # doesn't become an attribute.\n    del name\n\n\n    def lookupRecordType(self, type):\n        \"\"\"\n        Retrieve the L{IRecord} implementation for the given record type.\n\n        @param type: A record type, such as C{A} or L{NS}.\n        @type type: L{int}\n\n        @return: An object which implements L{IRecord} or L{None} if none\n            can be found for the given type.\n        @rtype: L{types.ClassType}\n        \"\"\"\n        return self._recordTypes.get(type, UnknownRecord)\n\n\n    def toStr(self):\n        \"\"\"\n        Encode this L{Message} into a byte string in the format described by RFC\n        1035.\n\n        @rtype: L{bytes}\n        \"\"\"\n        strio = BytesIO()\n        self.encode(strio)\n        return strio.getvalue()\n\n\n    def fromStr(self, str):\n        \"\"\"\n        Decode a byte string in the format described by RFC 1035 into this\n        L{Message}.\n\n        @param str: L{bytes}\n        \"\"\"\n        strio = BytesIO(str)\n        self.decode(strio)\n\n\n\nclass _EDNSMessage(tputil.FancyEqMixin, object):\n    \"\"\"\n    An I{EDNS} message.\n\n    Designed for compatibility with L{Message} but with a narrower public\n    interface.\n\n    Most importantly, L{_EDNSMessage.fromStr} will interpret and remove I{OPT}\n    records that are present in the additional records section.\n\n    The I{OPT} records are used to populate certain I{EDNS} specific attributes.\n\n    L{_EDNSMessage.toStr} will add suitable I{OPT} records to the additional\n    section to represent the extended EDNS information.\n\n    @see: U{https://tools.ietf.org/html/rfc6891}\n\n    @ivar id: See L{__init__}\n    @ivar answer: See L{__init__}\n    @ivar opCode: See L{__init__}\n    @ivar auth: See L{__init__}\n    @ivar trunc: See L{__init__}\n    @ivar recDes: See L{__init__}\n    @ivar recAv: See L{__init__}\n    @ivar rCode: See L{__init__}\n    @ivar ednsVersion: See L{__init__}\n    @ivar dnssecOK: See L{__init__}\n    @ivar authenticData: See L{__init__}\n    @ivar checkingDisabled: See L{__init__}\n    @ivar maxSize: See L{__init__}\n\n    @ivar queries: See L{__init__}\n    @ivar answers: See L{__init__}\n    @ivar authority: See L{__init__}\n    @ivar additional: See L{__init__}\n\n    @ivar _messageFactory: A constructor of L{Message} instances. Called by\n        C{_toMessage} and C{_fromMessage}.\n    \"\"\"\n\n    compareAttributes = (\n        'id', 'answer', 'opCode', 'auth', 'trunc',\n        'recDes', 'recAv', 'rCode', 'ednsVersion', 'dnssecOK',\n        'authenticData', 'checkingDisabled', 'maxSize',\n        'queries', 'answers', 'authority', 'additional')\n\n    _messageFactory = Message\n\n    def __init__(self, id=0, answer=False, opCode=OP_QUERY, auth=False,\n                 trunc=False, recDes=False, recAv=False, rCode=0,\n                 ednsVersion=0, dnssecOK=False, authenticData=False,\n                 checkingDisabled=False, maxSize=512,\n                 queries=None, answers=None, authority=None, additional=None):\n        \"\"\"\n        Construct a new L{_EDNSMessage}\n\n        @see: U{RFC1035 section-4.1.1<https://tools.ietf.org/html/rfc1035#section-4.1.1>}\n        @see: U{RFC2535 section-6.1<https://tools.ietf.org/html/rfc2535#section-6.1>}\n        @see: U{RFC3225 section-3<https://tools.ietf.org/html/rfc3225#section-3>}\n        @see: U{RFC6891 section-6.1.3<https://tools.ietf.org/html/rfc6891#section-6.1.3>}\n\n        @param id: A 16 bit identifier assigned by the program that generates\n            any kind of query.  This identifier is copied the corresponding\n            reply and can be used by the requester to match up replies to\n            outstanding queries.\n        @type id: L{int}\n\n        @param answer: A one bit field that specifies whether this message is a\n            query (0), or a response (1).\n        @type answer: L{bool}\n\n        @param opCode: A four bit field that specifies kind of query in this\n            message.  This value is set by the originator of a query and copied\n            into the response.\n        @type opCode: L{int}\n\n        @param auth: Authoritative Answer - this bit is valid in responses, and\n            specifies that the responding name server is an authority for the\n            domain name in question section.\n        @type auth: L{bool}\n\n        @param trunc: Truncation - specifies that this message was truncated due\n            to length greater than that permitted on the transmission channel.\n        @type trunc: L{bool}\n\n        @param recDes: Recursion Desired - this bit may be set in a query and is\n            copied into the response.  If set, it directs the name server to\n            pursue the query recursively. Recursive query support is optional.\n        @type recDes: L{bool}\n\n        @param recAv: Recursion Available - this bit is set or cleared in a\n            response, and denotes whether recursive query support is available\n            in the name server.\n        @type recAv: L{bool}\n\n        @param rCode: Extended 12-bit RCODE. Derived from the 4 bits defined in\n            U{RFC1035 4.1.1<https://tools.ietf.org/html/rfc1035#section-4.1.1>}\n            and the upper 8bits defined in U{RFC6891\n            6.1.3<https://tools.ietf.org/html/rfc6891#section-6.1.3>}.\n        @type rCode: L{int}\n\n        @param ednsVersion: Indicates the EDNS implementation level. Set to\n            L{None} to prevent any EDNS attributes and options being added to\n            the encoded byte string.\n        @type ednsVersion: L{int} or L{None}\n\n        @param dnssecOK: DNSSEC OK bit as defined by\n            U{RFC3225 3<https://tools.ietf.org/html/rfc3225#section-3>}.\n        @type dnssecOK: L{bool}\n\n        @param authenticData: A flag indicating in a response that all the data\n            included in the answer and authority portion of the response has\n            been authenticated by the server according to the policies of that\n            server.\n            See U{RFC2535 section-6.1<https://tools.ietf.org/html/rfc2535#section-6.1>}.\n        @type authenticData: L{bool}\n\n        @param checkingDisabled: A flag indicating in a query that pending\n            (non-authenticated) data is acceptable to the resolver sending the\n            query.\n            See U{RFC2535 section-6.1<https://tools.ietf.org/html/rfc2535#section-6.1>}.\n        @type authenticData: L{bool}\n\n        @param maxSize: The requestor's UDP payload size is the number of octets\n            of the largest UDP payload that can be reassembled and delivered in\n            the requestor's network stack.\n        @type maxSize: L{int}\n\n        @param queries: The L{list} of L{Query} associated with this message.\n        @type queries: L{list} of L{Query}\n\n        @param answers: The L{list} of answers associated with this message.\n        @type answers: L{list} of L{RRHeader}\n\n        @param authority: The L{list} of authority records associated with this\n            message.\n        @type authority: L{list} of L{RRHeader}\n\n        @param additional: The L{list} of additional records associated with\n            this message.\n        @type additional: L{list} of L{RRHeader}\n        \"\"\"\n        self.id = id\n        self.answer = answer\n        self.opCode = opCode\n        self.auth = auth\n        self.trunc = trunc\n        self.recDes = recDes\n        self.recAv = recAv\n        self.rCode = rCode\n        self.ednsVersion = ednsVersion\n        self.dnssecOK = dnssecOK\n        self.authenticData = authenticData\n        self.checkingDisabled = checkingDisabled\n        self.maxSize = maxSize\n\n        if queries is None:\n            queries = []\n        self.queries = queries\n\n        if answers is None:\n            answers = []\n        self.answers = answers\n\n        if authority is None:\n            authority = []\n        self.authority = authority\n\n        if additional is None:\n            additional = []\n        self.additional = additional\n\n\n    def __repr__(self):\n        return _compactRepr(\n            self,\n            flagNames=('answer', 'auth', 'trunc', 'recDes', 'recAv',\n                       'authenticData', 'checkingDisabled', 'dnssecOK'),\n            fieldNames=('id', 'opCode', 'rCode', 'maxSize', 'ednsVersion'),\n            sectionNames=('queries', 'answers', 'authority', 'additional'),\n            alwaysShow=('id',)\n        )\n\n\n    def _toMessage(self):\n        \"\"\"\n        Convert to a standard L{dns.Message}.\n\n        If C{ednsVersion} is not None, an L{_OPTHeader} instance containing all\n        the I{EDNS} specific attributes and options will be appended to the list\n        of C{additional} records.\n\n        @return: A L{dns.Message}\n        @rtype: L{dns.Message}\n        \"\"\"\n        m = self._messageFactory(\n            id=self.id,\n            answer=self.answer,\n            opCode=self.opCode,\n            auth=self.auth,\n            trunc=self.trunc,\n            recDes=self.recDes,\n            recAv=self.recAv,\n            # Assign the lower 4 bits to the message\n            rCode=self.rCode & 0xf,\n            authenticData=self.authenticData,\n            checkingDisabled=self.checkingDisabled)\n\n        m.queries = self.queries[:]\n        m.answers = self.answers[:]\n        m.authority = self.authority[:]\n        m.additional = self.additional[:]\n\n        if self.ednsVersion is not None:\n            o = _OPTHeader(version=self.ednsVersion,\n                           dnssecOK=self.dnssecOK,\n                           udpPayloadSize=self.maxSize,\n                           # Assign the upper 8 bits to the OPT record\n                           extendedRCODE=self.rCode >> 4)\n            m.additional.append(o)\n\n        return m\n\n\n    def toStr(self):\n        \"\"\"\n        Encode to wire format by first converting to a standard L{dns.Message}.\n\n        @return: A L{bytes} string.\n        \"\"\"\n        return self._toMessage().toStr()\n\n\n    @classmethod\n    def _fromMessage(cls, message):\n        \"\"\"\n        Construct and return a new L{_EDNSMessage} whose attributes and records\n        are derived from the attributes and records of C{message} (a L{Message}\n        instance).\n\n        If present, an C{OPT} record will be extracted from the C{additional}\n        section and its attributes and options will be used to set the EDNS\n        specific attributes C{extendedRCODE}, C{ednsVersion}, C{dnssecOK},\n        C{ednsOptions}.\n\n        The C{extendedRCODE} will be combined with C{message.rCode} and assigned\n        to C{self.rCode}.\n\n        @param message: The source L{Message}.\n        @type message: L{Message}\n\n        @return: A new L{_EDNSMessage}\n        @rtype: L{_EDNSMessage}\n        \"\"\"\n        additional = []\n        optRecords = []\n        for r in message.additional:\n            if r.type == OPT:\n                optRecords.append(_OPTHeader.fromRRHeader(r))\n            else:\n                additional.append(r)\n\n        newMessage = cls(\n            id=message.id,\n            answer=message.answer,\n            opCode=message.opCode,\n            auth=message.auth,\n            trunc=message.trunc,\n            recDes=message.recDes,\n            recAv=message.recAv,\n            rCode=message.rCode,\n            authenticData=message.authenticData,\n            checkingDisabled=message.checkingDisabled,\n            # Default to None, it will be updated later when the OPT records are\n            # parsed.\n            ednsVersion=None,\n            dnssecOK=False,\n            queries=message.queries[:],\n            answers=message.answers[:],\n            authority=message.authority[:],\n            additional=additional,\n            )\n\n        if len(optRecords) == 1:\n            # XXX: If multiple OPT records are received, an EDNS server should\n            # respond with FORMERR. See ticket:5669#comment:1.\n            opt = optRecords[0]\n            newMessage.ednsVersion = opt.version\n            newMessage.dnssecOK = opt.dnssecOK\n            newMessage.maxSize = opt.udpPayloadSize\n            newMessage.rCode = opt.extendedRCODE << 4 | message.rCode\n\n        return newMessage\n\n\n    def fromStr(self, bytes):\n        \"\"\"\n        Decode from wire format, saving flags, values and records to this\n        L{_EDNSMessage} instance in place.\n\n        @param bytes: The full byte string to be decoded.\n        @type bytes: L{bytes}\n        \"\"\"\n        m = self._messageFactory()\n        m.fromStr(bytes)\n\n        ednsMessage = self._fromMessage(m)\n        for attrName in self.compareAttributes:\n            setattr(self, attrName, getattr(ednsMessage, attrName))\n\n\n\nclass DNSMixin(object):\n    \"\"\"\n    DNS protocol mixin shared by UDP and TCP implementations.\n\n    @ivar _reactor: A L{IReactorTime} and L{IReactorUDP} provider which will\n        be used to issue DNS queries and manage request timeouts.\n    \"\"\"\n    id = None\n    liveMessages = None\n\n    def __init__(self, controller, reactor=None):\n        self.controller = controller\n        self.id = random.randrange(2 ** 10, 2 ** 15)\n        if reactor is None:\n            from twisted.internet import reactor\n        self._reactor = reactor\n\n\n    def pickID(self):\n        \"\"\"\n        Return a unique ID for queries.\n        \"\"\"\n        while True:\n            id = randomSource()\n            if id not in self.liveMessages:\n                return id\n\n\n    def callLater(self, period, func, *args):\n        \"\"\"\n        Wrapper around reactor.callLater, mainly for test purpose.\n        \"\"\"\n        return self._reactor.callLater(period, func, *args)\n\n\n    def _query(self, queries, timeout, id, writeMessage):\n        \"\"\"\n        Send out a message with the given queries.\n\n        @type queries: L{list} of C{Query} instances\n        @param queries: The queries to transmit\n\n        @type timeout: L{int} or C{float}\n        @param timeout: How long to wait before giving up\n\n        @type id: L{int}\n        @param id: Unique key for this request\n\n        @type writeMessage: C{callable}\n        @param writeMessage: One-parameter callback which writes the message\n\n        @rtype: C{Deferred}\n        @return: a C{Deferred} which will be fired with the result of the\n            query, or errbacked with any errors that could happen (exceptions\n            during writing of the query, timeout errors, ...).\n        \"\"\"\n        m = Message(id, recDes=1)\n        m.queries = queries\n\n        try:\n            writeMessage(m)\n        except:\n            return defer.fail()\n\n        resultDeferred = defer.Deferred()\n        cancelCall = self.callLater(timeout, self._clearFailed, resultDeferred, id)\n        self.liveMessages[id] = (resultDeferred, cancelCall)\n\n        return resultDeferred\n\n    def _clearFailed(self, deferred, id):\n        \"\"\"\n        Clean the Deferred after a timeout.\n        \"\"\"\n        try:\n            del self.liveMessages[id]\n        except KeyError:\n            pass\n        deferred.errback(failure.Failure(DNSQueryTimeoutError(id)))\n\n\nclass DNSDatagramProtocol(DNSMixin, protocol.DatagramProtocol):\n    \"\"\"\n    DNS protocol over UDP.\n    \"\"\"\n    resends = None\n\n    def stopProtocol(self):\n        \"\"\"\n        Stop protocol: reset state variables.\n        \"\"\"\n        self.liveMessages = {}\n        self.resends = {}\n        self.transport = None\n\n    def startProtocol(self):\n        \"\"\"\n        Upon start, reset internal state.\n        \"\"\"\n        self.liveMessages = {}\n        self.resends = {}\n\n    def writeMessage(self, message, address):\n        \"\"\"\n        Send a message holding DNS queries.\n\n        @type message: L{Message}\n        \"\"\"\n        self.transport.write(message.toStr(), address)\n\n    def startListening(self):\n        self._reactor.listenUDP(0, self, maxPacketSize=512)\n\n    def datagramReceived(self, data, addr):\n        \"\"\"\n        Read a datagram, extract the message in it and trigger the associated\n        Deferred.\n        \"\"\"\n        m = Message()\n        try:\n            m.fromStr(data)\n        except EOFError:\n            log.msg(\"Truncated packet (%d bytes) from %s\" % (len(data), addr))\n            return\n        except:\n            # Nothing should trigger this, but since we're potentially\n            # invoking a lot of different decoding methods, we might as well\n            # be extra cautious.  Anything that triggers this is itself\n            # buggy.\n            log.err(failure.Failure(), \"Unexpected decoding error\")\n            return\n\n        if m.id in self.liveMessages:\n            d, canceller = self.liveMessages[m.id]\n            del self.liveMessages[m.id]\n            canceller.cancel()\n            # XXX we shouldn't need this hack of catching exception on callback()\n            try:\n                d.callback(m)\n            except:\n                log.err()\n        else:\n            if m.id not in self.resends:\n                self.controller.messageReceived(m, self, addr)\n\n\n    def removeResend(self, id):\n        \"\"\"\n        Mark message ID as no longer having duplication suppression.\n        \"\"\"\n        try:\n            del self.resends[id]\n        except KeyError:\n            pass\n\n    def query(self, address, queries, timeout=10, id=None):\n        \"\"\"\n        Send out a message with the given queries.\n\n        @type address: L{tuple} of L{str} and L{int}\n        @param address: The address to which to send the query\n\n        @type queries: L{list} of C{Query} instances\n        @param queries: The queries to transmit\n\n        @rtype: C{Deferred}\n        \"\"\"\n        if not self.transport:\n            # XXX transport might not get created automatically, use callLater?\n            try:\n                self.startListening()\n            except CannotListenError:\n                return defer.fail()\n\n        if id is None:\n            id = self.pickID()\n        else:\n            self.resends[id] = 1\n\n        def writeMessage(m):\n            self.writeMessage(m, address)\n\n        return self._query(queries, timeout, id, writeMessage)\n\n\nclass DNSProtocol(DNSMixin, protocol.Protocol):\n    \"\"\"\n    DNS protocol over TCP.\n    \"\"\"\n    length = None\n    buffer = b''\n\n    def writeMessage(self, message):\n        \"\"\"\n        Send a message holding DNS queries.\n\n        @type message: L{Message}\n        \"\"\"\n        s = message.toStr()\n        self.transport.write(struct.pack('!H', len(s)) + s)\n\n    def connectionMade(self):\n        \"\"\"\n        Connection is made: reset internal state, and notify the controller.\n        \"\"\"\n        self.liveMessages = {}\n        self.controller.connectionMade(self)\n\n\n    def connectionLost(self, reason):\n        \"\"\"\n        Notify the controller that this protocol is no longer\n        connected.\n        \"\"\"\n        self.controller.connectionLost(self)\n\n\n    def dataReceived(self, data):\n        self.buffer += data\n\n        while self.buffer:\n            if self.length is None and len(self.buffer) >= 2:\n                self.length = struct.unpack('!H', self.buffer[:2])[0]\n                self.buffer = self.buffer[2:]\n\n            if len(self.buffer) >= self.length:\n                myChunk = self.buffer[:self.length]\n                m = Message()\n                m.fromStr(myChunk)\n\n                try:\n                    d, canceller = self.liveMessages[m.id]\n                except KeyError:\n                    self.controller.messageReceived(m, self)\n                else:\n                    del self.liveMessages[m.id]\n                    canceller.cancel()\n                    # XXX we shouldn't need this hack\n                    try:\n                        d.callback(m)\n                    except:\n                        log.err()\n\n                self.buffer = self.buffer[self.length:]\n                self.length = None\n            else:\n                break\n\n\n    def query(self, queries, timeout=60):\n        \"\"\"\n        Send out a message with the given queries.\n\n        @type queries: L{list} of C{Query} instances\n        @param queries: The queries to transmit\n\n        @rtype: C{Deferred}\n        \"\"\"\n        id = self.pickID()\n        return self._query(queries, timeout, id, self.writeMessage)\n"
  }
]